[
  {
    "path": ".classpath",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<classpath>\n\t<classpathentry kind=\"src\" path=\"prism/src\"/>\n\t<classpathentry kind=\"src\" path=\"prism/unit-tests\"/>\n\t<classpathentry kind=\"con\" path=\"org.eclipse.jdt.launching.JRE_CONTAINER\"/>\n\t<classpathentry kind=\"con\" path=\"org.eclipse.jdt.junit.JUNIT_CONTAINER/5\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/epsgraphics.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/jcommon.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/jfreechart.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/jhoafparser.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/colt.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/pepa.zip\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/lpsolve55j.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/jas.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/log4j-api.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/log4j-core.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"prism/lib/nailgun-server.jar\"/>\n\t<classpathentry kind=\"output\" path=\"prism/classes\"/>\n</classpath>\n"
  },
  {
    "path": ".gitattributes",
    "content": "# Handle line endings automatically for text files\n* text=auto\n\n# Force LF for build scripts (for make etc. on Cygwin)\n*.sh      text eol=lf\n*.py      text eol=lf\nMakefile  text eol=lf\n"
  },
  {
    "path": ".github/workflows/make-tests.yml",
    "content": "name: Regression tests\n\non:\n  push:\n    branches: [ master ]\n  pull_request:\n    branches: [ master ]\n\njobs:\n\n  build:\n    strategy:\n      matrix:\n        java: [11, 21]\n        os: [ubuntu-latest, macos-latest]\n        #java: [11, 17, 21]\n        #os: [ubuntu-20.04, ubuntu-22.04, ubuntu-24.04, macos-14, macos-15, macos-26, ubuntu-22.04-arm, ubuntu-24.04-arm, macos-15-intel]\n    runs-on: ${{ matrix.os }}\n\n    steps:\n    - uses: actions/checkout@v4\n    - name: Set up JDK\n      uses: actions/setup-java@v4\n      with:\n        java-version: ${{ matrix.java }}\n        distribution: temurin\n    - name: make tests\n      shell: bash\n      working-directory: ./prism\n      run: |\n        make\n        make unittests\n        make tests\n\n  build-win:\n    strategy:\n      matrix:\n        java: [11, 21]\n        os: [windows-latest]\n        #java: [11, 17, 21]\n        #os: [windows-2019, windows-2022, windows-2025] #, windows-11-arm]\n        #exclude:\n          #- os: windows-11-arm\n            #java: 11\n          #- os: windows-11-arm\n            #java: 17\n    runs-on: ${{ matrix.os }}\n\n    steps:\n    - run: git config --global core.autocrlf input\n    - uses: actions/checkout@v4\n    - name: Set up JDK\n      uses: actions/setup-java@v4\n      with:\n        java-version: ${{ matrix.java }}\n        distribution: temurin\n    - name: Install Cygwin Dependencies\n      uses: cygwin/cygwin-install-action@v4\n      with:\n        packages: |\n          make,\n          mingw64-x86_64-gcc-g++,\n          binutils,\n          dos2unix,\n          wget,\n          unzip,\n          python\n    - name: make tests\n      shell: bash\n      env:\n        CYGWIN: winsymlinks:native\n      working-directory: ./prism\n      run: >-\n        make &&\n        make unittests &&\n        make tests\n"
  },
  {
    "path": ".github/workflows/release.yml",
    "content": "name: Build/publish release source & binaries (Linux, Mac, Windows)\n\non:\n  # Trigger on version tags: v4.10 etc.\n  push:\n    tags:\n      - 'v*'\n  # Allows manual triggering\n  workflow_dispatch:\n      inputs:\n        tag_name:\n          description: 'Target tag (e.g., v4.10)'\n          required: true\n          type: string\n        do_publish:\n          description: 'Upload to the GitHub release?'\n          required: true\n          type: boolean\n          default: false\n\njobs:\n\n  build_src:\n    runs-on: ubuntu-latest\n    steps:\n    - uses: actions/checkout@v4\n      with:\n        # Use the tag from manual input, otherwise fall back to the git ref\n        ref: ${{ github.event.inputs.tag_name || github.ref }}\n        fetch-depth: 0 # Fetches all tags and history\n    - name: Build source\n      shell: bash\n      working-directory: ./prism\n      run: |\n        make release_source BRANCH=HEAD\n    - name: Upload artifact\n      uses: actions/upload-artifact@v4\n      with:\n        name: prism-src\n        path: prism/release/*.tar.gz\n\n  build:\n    strategy:\n      matrix:\n        include:\n          - os: ubuntu-latest\n            artifact_name: prism-linux64-x86\n          - os: ubuntu-22.04-arm\n            artifact_name: prism-linux64-arm\n          - os: macos-latest\n            artifact_name: prism-mac64-arm\n          - os: macos-15-intel\n            artifact_name: prism-mac64-x86\n    runs-on: ${{ matrix.os }}\n\n    steps:\n    - uses: actions/checkout@v4\n      with:\n        # Use the tag from manual input, otherwise fall back to the git ref\n        ref: ${{ github.event.inputs.tag_name || github.ref }}\n        fetch-depth: 0 # Fetches all tags and history\n    - name: Set up JDK\n      uses: actions/setup-java@v4\n      with:\n        java-version: '17'\n        distribution: 'temurin'\n    - name: Build\n      shell: bash\n      working-directory: ./prism\n      run: |\n        make release\n    - name: Upload artifact\n      uses: actions/upload-artifact@v4\n      with:\n        name: ${{ matrix.artifact_name }}\n        path: prism/release/*.tar.gz\n\n  build_win:\n    strategy:\n      matrix:\n        include:\n          - os: windows-latest\n            artifact_name: prism-win64\n    runs-on: ${{ matrix.os }}\n\n    steps:\n    - run: git config --global core.autocrlf input\n    - uses: actions/checkout@v4\n      with:\n        # Use the tag from manual input, otherwise fall back to the git ref\n        ref: ${{ github.event.inputs.tag_name || github.ref }}\n        fetch-depth: 0 # Fetches all tags and history\n    - name: Set up JDK\n      uses: actions/setup-java@v4\n      with:\n        java-version: '17'\n        distribution: 'temurin'\n    - name: Install Cygwin Dependencies\n      uses: cygwin/cygwin-install-action@v4\n      with:\n        packages: |\n          make,\n          mingw64-x86_64-gcc-g++,\n          binutils,\n          dos2unix,\n          wget,\n          unzip,\n          python\n    - name: Install NSIS\n      uses: negrutiu/nsis-install@v2\n    - name: Build\n      shell: bash\n      env:\n        CYGWIN: winsymlinks:native\n      working-directory: ./prism\n      run: >-\n        make release\n    - name: Upload artifact\n      uses: actions/upload-artifact@v4\n      with:\n        name: ${{ matrix.artifact_name }}\n        path: prism/release/*.exe\n\n  test_release:\n    needs: build\n    strategy:\n      matrix:\n        include:\n          - os: ubuntu-latest\n            artifact_name: prism-linux64-x86\n          - os: ubuntu-22.04-arm\n            artifact_name: prism-linux64-arm\n          - os: macos-latest\n            artifact_name: prism-mac64-arm\n          - os: macos-15-intel\n            artifact_name: prism-mac64-x86\n    runs-on: ${{ matrix.os }}\n    \n    steps:\n    - name: Download Artifact\n      uses: actions/download-artifact@v4\n      with:\n        name: ${{ matrix.artifact_name }}\n        path: test-dir\n    - name: Verify download\n      run: ls -R test-dir/\n    - name: Build and run smoke test\n      shell: bash\n      working-directory: ./test-dir\n      run: |\n        tar -xzf prism*.tar.gz\n        rm prism*.tar.gz\n        cd prism-*\n        ./install.sh\n        etc/tests/run.sh\n\n  publish:\n      needs: [build_src, build, build_win, test_release]\n      runs-on: ubuntu-latest\n      permissions:\n        # Crucial for creating releases\n        contents: write\n      if: startsWith(github.ref, 'refs/tags/') || github.event.inputs.do_publish == 'true'\n      \n      steps:\n        - name: Download all artifacts\n          uses: actions/download-artifact@v4\n          with:\n            # This downloads all job artifacts into subfolders\n            path: ./artifacts\n  \n        - name: Organize files and Generate Checksums\n          # Move files from subfolders into one flat directory for the release\n          shell: bash\n          run: |\n            mkdir -p release-assets\n            find ./artifacts -type f \\( -name \"*.tar.gz\" -o -name \"*.exe\" -o -name \"*.zip\" \\) -exec cp {} ./release-assets/ \\;\n            cd release-assets\n            sha256sum * > checksums.txt\n            echo \"Assets to be published:\"\n            ls -lh\n  \n        - name: Create or update GitHub release\n          uses: softprops/action-gh-release@v2\n          with:\n            # Use the tag from manual input, otherwise fall back to the git ref\n            tag_name: ${{ github.event.inputs.tag_name || github.ref_name }}\n            # Upload files (omit checksums for now)\n            files: |\n              release-assets/*.tar.gz\n              release-assets/*.exe\n              release-assets/*.zip\n            # These are safe even if the release exists; it won't overwrite your text\n            generate_release_notes: false \n            draft: true\n"
  },
  {
    "path": ".gitignore",
    "content": "# general patterns to ignore\n# Emacs backup files\n*~\n# OS X system files\n.DS_Store\n\n\n# build artefacts by pattern:\n*.o\n*.a\n*.class\n*.dylib\n*.jnilib\n*.so\n*.dll\n\n# build artefact directories:\nprism/bin/\nprism/classes/\nprism/obj/\n\n# temporary build files:\nprism/prism-sources.txt\n\n# generated JAR files:\nprism/lib/lpsolve55j.jar\nprism/lib/prism.jar\nprism/lib/prism-sources.jar\n\n# generated CUDD headers:\ncudd/include/*.h\n\n# Eclipse project files (should not be versioned)\n\\.project\nprism/\\.project\n# Eclipse project custom settings\n\\.settings/\nprism/\\.settings/\n\n# Dependency management via Gradle\nprism/etc/jars/.gradle/\nprism/etc/jars/build/\nprism/etc/jars/local-libs/\n"
  },
  {
    "path": "CHANGELOG.txt",
    "content": "This file contains details of the changes in each new version of PRISM.\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.10.1 (first released 2/4/2026)\r\n-----------------------------------------------------------------------------\r\n\r\n* Simplify and optimise Makefile and build process\r\n\r\n* Simplify and improve native shared libraries\r\n  - unify into a single native shared library: libprism.{so,dylib}\r\n  - fix soname/install_name/rpath (no need for (DY)LD_LIBRARY_PATH now)\r\n  - shared libraries can be absent when using the explicit engine\r\n\r\n* Update and document JAR file dependencies\r\n\r\n* Various bugfixes\r\n\r\n* Development and code-level changes:\r\n  - add Gradle-based maintenance of JAR files\r\n  - IntelliJ IDEA config files (run \"make intellij\")\r\n  - update Java language level from 9 to 11\r\n  - PrismLog fixes, tidying and optimisations\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.10 (first released 29/1/2026)\r\n-----------------------------------------------------------------------------\r\n\r\n* Import/export functionality\r\n  - import/export from/to UMB (Unified Markov Binary) format\r\n  - import of POMDPs from explicit files (.tra, .obs, etc.)\r\n  - optionally, export/import initial state info via .tra file\r\n    (currently only done for POMDPs))\r\n\r\n* Full LTL for interval MDPs/DTMCs.\r\n\r\n* Construction and export (but not solution) of:\r\n  - negative rewards\r\n  - interval POMDPs\r\n  - exact interval models\r\n\r\n* Use JVM defaults for max heap size\r\n\r\n* Various bugfixes\r\n\r\n* Development and code-level changes\r\n  - fix to allow cross-compiling Arm->Intel on macOS.\r\n  - ModelInfo stores actions, aligns with Model\r\n  - models stored using BigRational not Function in exact mode\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.9 (first released 11/8/2025)\r\n-----------------------------------------------------------------------------\r\n\r\n* Explicit engine improvements\r\n  - support for actions and transition rewards in Markov chains\r\n\r\n* Export functionality\r\n  - export of exact and parametric models\r\n  - preliminary DRN (Storm) output\r\n  - multiple -exportmodel switches allowed\r\n  - options for -exportmodel: format/actions/header/precision\r\n  - export of Markov chain actions\r\n  - remove old options (MRMC format, unordered, spy)\r\n  - align -exportstrat and -exportadv switches\r\n\r\n* Model import functionality (from explicit files)\r\n  - import of transition rewards\r\n  - import for exact mode, LTSs\r\n  - import progress display (symbolic engine)\r\n  - import directly to sparse classes in explicit engine\r\n    (now assume ascending states/choices in .tra files)\r\n\r\n* Minor modelling language updates\r\n  - new power operator a^b, equivalent to pow(a,b)\r\n  - fix: implication (=>) is right-associative\r\n\r\n* New/improved functionality\r\n  - simplified/updated LTL-to-automaton scripts\r\n  - simulator can take a random seed (API only)\r\n  - exact model checking supported from GUI\r\n  - optimal strategy synthesis for Rmax=? [ C ] (explicit)\r\n\r\n* Various bugfixes\r\n\r\n* Development and code-level changes\r\n  - prism.Prism API: new/updated model export methods\r\n  - prism.Prism API: remove some old deprecated methods\r\n  - prism.Prism: refactored storage/access for model info\r\n  - prism.Prism: integration of exact model building/checking\r\n  - improved access to actions and their indices in models\r\n  - redesign/refactoring of explicit engine reward classes\r\n  - refactoring of explicit engine model import/export code\r\n    (centralised in io package, export moved from model classes)\r\n  - parametric engine refactored to use explicit models/rewards\r\n  - refactoring of (explicit engine) interval model storage\r\n  - symbolic code rearranged (new symbolic package)\r\n  - symbolic model storage refactored, simplified, documented\r\n  - extension of strategy classes, especially for induced models\r\n  - Java-based symbolic-to-explicit model conversion\r\n  - prism-auto: --errors-only switch\r\n\r\n* [More minor development and code-level changes]\r\n\r\n  - explicit engine product construction refactoring\r\n  - explicit model refactoring (infoString etc.)\r\n  - default implementation of getVarDeclarationType in ModelGenerator\r\n  - POMDP observation info storage refactoring\r\n  - Expression.toString() respects operator precedence\r\n  - VarList aware of EvaluationContext/EvalMode\r\n  - parametric engine: improved error reporting and formatting\r\n  - prism.API: exportprism moved from setting to API call\r\n  - model export refactoring, including ModelExportTask\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.8.1 (first released 13/1/2024)\r\n-----------------------------------------------------------------------------\r\n\r\n* Migrate to CUDD version 3\r\n* Transition reward export (MDP-like models) for explicit engine\r\n* Fix broken transient probability computation\r\n* Updates/fixes in install/launch/testing scripts and build process\r\n* New tests in etc/tests available for easier build tests\r\n* New -javaversion switch to show Java version used\r\n* New --print-failures switch for prism-auto\r\n* Various bugfixes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.8 (first released 5/7/2023)\r\n-----------------------------------------------------------------------------\r\n\r\n* Support for interval DTMC (IDTMC) and interval MDP (IMDP) model checking\r\n\r\n* Improved strategy (policy) generation\r\n  - switch -exportstrat exports to tra/dot/txt format\r\n  - additional export options (restrict/reduce, states, reach)\r\n  - strategy generation extended for bounded reachability, LTL, POMDPs\r\n  - GUI support for generating, exporting and simulating strategies\r\n\r\n* Other features/enhancements:\r\n  - PTA model checking supports global/non-local variables\r\n  - ModelGenerator interface now supports real-time models (e.g., PTAs)\r\n  - new -javaparams switch to pass command-line arguments to JVM\r\n  - prism-log-extract: new field 'dd_nodes' for model MTBDD size\r\n\r\n* Import/export enhancements:\r\n  - import of multiple (and named) reward structures\r\n  - reward exports include header with name/type\r\n  - new setting for model export precision (-exportmodelprecision)\r\n  - new \"proplabels\" option for -exportmodel and -exportlabels\r\n  - new -exportproplabels switch to export (just) properties file labels\r\n  - explicit model import without -importmodel: prism model.all\r\n  - results export to new formats: PRISM comment, dataframe\r\n  - results import from dataframe format (-importresults or GUI)\r\n  - observation export for POMDPs (-exportobs or GUI)\r\n\r\n* Fixes / upgrades\r\n  - compile fix for newer MacOS\r\n  - library updates: JAS (2.7.90), Log4j (2.16.0), jhoafparser (1.1.1)\r\n  - various bugfixes\r\n\r\n* Development and code-level changes\r\n  - automated testing via GitHub Actions\r\n  - unit testing via JUnit\r\n  - JavaCC upgraded from version 6.0 to 7.0\r\n  - major refactoring:\r\n    > generic model/reward classes\r\n    > ASTElement deepCopy()\r\n    > Expression evaluation\r\n    > explicit.StateValues\r\n    > Strategy and related classes\r\n    > Modules2MTBDD\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.7 (first released 19/3/2021)\r\n-----------------------------------------------------------------------------\r\n\r\n* New model checking functionality\r\n  - support for POMDP/POPTA model checking\r\n  - support for LTS model checking\r\n  - reporting of model checking accuracy\r\n\r\n* Features/enhancements:\r\n  - bounded properties (e.g. P<p) raise error if results are too inaccurate\r\n  - improved model type auto-detection (MDP/PTA/LTS/POMDP/POPTA)\r\n  - new -dir switch to set current working dir in command line and GUI\r\n  - support HOA input (HOAF2DA) without a number-of-states header\r\n\r\n* Fixes\r\n  - fixed to compile on Java 14\r\n  - fixed to compile on 64-bit Arm Linux/Mac\r\n  - consistent treatment of negative/infinite/NaN rewards in symbolic/explicit engines\r\n  - disable tree of model info in GUI\r\n  \r\n* Development and code-level changes\r\n  - code base now allows/assumes Java 9\r\n  - testing RESULT specifications can be intervals [a,b]\r\n  - prism-log-extract: new (meta)fields: prog_name, prog_version, prog\r\n  - ModelGenerator improvements: auto-generates VarList; stores module info\r\n  - explicit model refactoring: more default implementations in interfaces\r\n  - bugfixes & refactoring\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.6 (first released 21/4/2020)\r\n-----------------------------------------------------------------------------\r\n  \r\n* New model checking features/enhancements:\r\n  - digital clocks engine now supports time-bounded reachability\r\n  - explicit engine support for steady-state computation (and S, R[S] properties)\r\n  - improved support in MTBDD engine for very large (>2^63) state spaces\r\n  - the -heuristic switch triggers automatic selection of some engines/settings\r\n  - the -prop switch accepts multiple (comma-separated) property indices/names\r\n  - MTBDD engine support for non-sparse vector printing (printall filter)\r\n  - many minor bugfixes\r\n  \r\n* New import/export features:\r\n  - export of result values for all states of a model (-exportvector)\r\n  - basic auto-detection of model type for explicit file import\r\n  - simulation (path generation and statistical model checking) for explicit model imports\r\n  - explicit engine support for state reward import from files\r\n  - MTBDD engine support for export of transient/steady-state probabilities\r\n\r\n* Examples directory tidied up and now grouped by model type\r\n\r\n* Development changes and enhancements:\r\n  - extended/improved ModelGenerator interface, including methods to support simulation\r\n  - new RewardGenerator interface for specifying information about rewards for a model\r\n  - PRISM API improvements: properties can be parsed against the currently loaded model\r\n  - Makefile improvements: better configurability of directiories\r\n  - Makefile improvements: better handling of variables and sub-Makefiles, incl. CUDD\r\n  - new release_source Makefile target for building source releases\r\n\r\n* Benchmarking/testing changes and enhancements:\r\n  - new prism-log-extract script for processing PRISM log files\r\n  - prism-auto: new options/features (--log-subdirs, --filter-models, --args-list)\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.5 (first released 19/4/2019)\r\n-----------------------------------------------------------------------------\r\n\r\n* New features\r\n  - add round function to language (rounds to nearest integer)\r\n  - Java stack size can be set via command-line switch -javastack (or PRISM_JAVASTACKSIZE)\r\n  - fractional values allowed for constants in -const switch and in GUI\r\n  - allow rewards to be included in simulation paths exported from GUI (like for -simpath)\r\n\r\n* Enhancements and fixes:\r\n  - PRISM GUI settings file (.prism) moved to more standard locations\r\n  - ITE supported in exact/parametric mode\r\n  - various improvements to model checking in \"exact\" mode\r\n  - bugfix for incorrect model construction during fast adaptive uniformisation\r\n  - faster explicit construction of models with no labels\r\n  - command-line -exportsteadystates switch implies -steadystate\r\n  - GUI shortcuts: double-clicks for addition of constants, labels\r\n  - fixed Mac launch scripts for Java 10 (removed -d64 and -d32)\r\n  - improved auto switching between model checking engines in some cases\r\n  - many minor bugfixes\r\n\r\n* Development changes and enhancements:\r\n  - alignment of source code releases and GitHub repos (some files moved to top-level)\r\n  - move/simplify release building Makefile scripts (see GitHub wiki)\r\n  - utility scripts for installing PRISM on fresh OSs (in etc/scripts)\r\n  - HTML copy of manual now included in repo\r\n  - make clean_all cleans external libs too, e.g. lpsolve\r\n  - switch from javah (deprecated since Java 8) to javac for JNI header generation\r\n  - launch scripts now use exec to start Java by default (PRISM_NO_EXEC=yes to revert)\r\n\r\n* Benchmarking/testing changes and enhancements:\r\n  - integration of prism-tests into main repo\r\n  - fractions/exact numbers allowed in testing RESULT specs\r\n  - Travis build config for continuous integration testing\r\n  - prism-auto guesses ngprism location\r\n  - prism-auto options: --skip-export-runs, --skip-duplicate-runs, --timeout\r\n  - Makefile targets/settings: test, testsecho, testsfull, TESTS_ARGS, source-jar\r\n  - NG_MAINCLASS setting for running PRISM in Nailgun server mode (prism -ng)\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.4 (first released 23/7/2017)\r\n-----------------------------------------------------------------------------\r\n\r\n* New model checking functionality:\r\n  - expected reward to satisfy a co-safe LTL formula (MDPs, D/CTMCs, all engines)\r\n  - interval iteration (MDPs, D/CTMCs, all engines)\r\n  - topological value iteration (MDPs, D/CTMCs, explicit engine)\r\n  - expected total reward (R[C] operator) for CTMCs and MDPs (max), all engines\r\n  - CTL model checking in the explicit engine\r\n  - non-probabilistic LTL model checking in the explicit engine\r\n  - instantaneous reward computation (Rmax/min[I=x]) in the explicit engine\r\n  - DTMC transient probability computation for the explicit engine\r\n\r\n* Imports and exports:\r\n  - model import from explicit files for the explicit engine (-import... switches)\r\n  - full import of labels during explicit model import (all engines)\r\n  - import of state rewards during explicit model import (symbolic engines)\r\n  - export of state rewards from explicit engine\r\n  - export of models to .dot format via the -exportmodel switch\r\n\r\n* Miscellaneous:\r\n  - built-in support for Nailgun client/server\r\n  - new timeout feature (-timeout switch)\r\n  - performance improvements in explicit engine\r\n  - GUI also supports -javamaxmem switch to set Java memory\r\n  - better error handling when CUDD runs out of memory\r\n  - various bug fixes and performance improvements\r\n\r\n* Features for developers:\r\n  - new ModelGenerator interface for specifying models programmatically\r\n  - extensions to test mode: complex expressions for RESULT specifications\r\n  - prism-auto: new options/features (e.g., --show-warnings, --nailgun, --ngprism, --verbose-test)\r\n  - DD debugging options: -dddebug and -ddtrace switches, improved ref count debugging\r\n  - new option -exportiterations for visualising iterative numerical methods\r\n  - code base now allows/assumes Java 8\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.3.1 (first released 26/5/2016)\r\n-----------------------------------------------------------------------------\r\n\r\n* Bug fixes:\r\n- launch scripts on OS X (especially El Capitan)\r\n- lpsolve compile fix for recent Linux distributions\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.3 (first released 14/7/2015)\r\n-----------------------------------------------------------------------------\r\n\r\n* Support for external LTL-to-automata converters via the HOA format\r\n  - including model checking for Generalised Rabin (GR) conditions\r\n\r\n* New model checking functionality/optimisations\r\n  - lower time-bounds for properties of DTMCs/MDPs (e.g. P=? [ F>=2 \"target\" ])\r\n  - expected total rewards (R[C]) implemented for DTMCs\r\n  - backwards reachability algorithm implemented for model checking PTAs\r\n  - exact (arbitrary precision) model checking via the parametric engine (experimental)\r\n  - various LTL model checking optimisations\r\n  - faster precomputation by pre-computing predecessors (explicit engine)\r\n\r\n* Options/switches:\r\n  - new -pathviaautomata switch to force model checking via automaton construction\r\n  - new \"comment\" option for exporting results (exports in regression test format)\r\n  - new -javamaxmem switch (equivalent to setting PRISM_JAVAMAXMEM)\r\n  - more convenient format for CUDD max memory setting (125k, 50m, 4g, etc.)\r\n  - higher default values for CUDD/Java memory limits\r\n  \r\n* Additional functionality in prism-auto testing/benchmarking script\r\n  - export testing, .auto files, debug mode, colouring, custom model files, ...\r\n  \r\n* New sbml2prism script\r\n\r\n* Bug fixes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.2.1 (first released 4/12/2014)\r\n-----------------------------------------------------------------------------\r\n\r\n* Bug fixes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.2 (beta first released 12/5/2014)\r\n-----------------------------------------------------------------------------\r\n\r\n* Parametric model checking\r\n\r\n* New model checking and export functionality\r\n  - fast adaptive uniformisation for CTMC transient analysis\r\n  - added R[C<=k] operator for MDPs (sparse, explicit)\r\n  - new -exportmecs and -exportsccs switches\r\n  - additional functionality in explicit engine (export BSCCs, LTL)\r\n  - improved adversary strategy generation in explicit engine\r\n  - integer variables can be unbounded (e.g. \"x:int;\"), for simulation-based analysis\r\n\r\n* New options/switches:\r\n  - new -exportmodel and -importmodel convenience switches\r\n  - new -sumroundoff switch (used when checking probabilities sum to 1)\r\n  - some new '-help xxx' switches (const,simpath,exportresults,aroptions,exportmodel,importmodel)\r\n  - allow command-line switches of form --sw (as well as -sw)\r\n  - slight change to notation for -exportresults to match -exportmodel\r\n\r\n* Additional functionality available in GUI:\r\n  - export steady-state/transient probabilities from GUI\r\n  - export/view labels from model/properties from GUI\r\n  - small improvements to usability of the GUI simulator transition table\r\n  - additional graph zoom functionality on popup menu\r\n\r\n* Updates to build process\r\n  - fixed building on new versions of Cygwin (32/64-bit Windows)\r\n  - update CUDD to version 2.5.0\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.1 (first released 20/12/2012)\r\n-----------------------------------------------------------------------------\r\n\r\n* Multi-objective model checking for MDPs\r\n\r\n* New explicit-state (pure Java) model checking engine\r\n  - coverage of much, but not all, of PRISM's model checking functionality\r\n  - new methods for MDPs: policy iteration (-politer -modpoliter) and Gauss-Seidel (-gs)\r\n  - accompanying significant changes to underlying PRISM (Java) API\r\n\r\n* GUI improvements\r\n  - easy plotting of graphs for simulation paths in the GUI\r\n  - command-line GUI call (xprism)  takes both model and properties files as arguments\r\n  - easier zoom-out (double click) for graphs in GUI\r\n\r\n* CTL model checking (most operators)\r\n  - and counterexample/witness generation for A[G ...] or E[F ...]\r\n  \r\n* Changes to deadlock handling:\r\n  - new option for \"fix deadlocks\" (defaults to *true*) (and new switch -nofixdl) \r\n  - consistent deadlock handling everywhere, incl. GUI and experiments\r\n\r\n* Model checking improvements\r\n  - incremental computation of ranges of transient probabilities\r\n    when called from command-line (e.g. -tr 0.1:0.01:0.2) \r\n  - new \"printall\" filter (shows zero results too, unlike \"print\")\r\n  - -importinit option works for steady-state as well as transient probabilities\r\n  - additional output in log of progress for numerical solution techniques\r\n\r\n* Improvements to simulation path generation using -simpath switch\r\n  - more efficient path generation (on-the-fly) where possible\r\n  - new 'snapshot' option to only show states at certain time-points\r\n  - added 'probs' option to display transition probabilities/rates\r\n  - rewards are not displayed by default; use 'rewards' option to show\r\n  \r\n* Changes to usage of PRISM settings file\r\n  - settings file ~/.prism only read by GUI (not command-line) by default\r\n  - new switch -settings to read a settings file from command-line PRISM\r\n\r\n* New file extensions for model/properties files: .prism, .props\r\n* New scripts for testing and benchmarking: prism-auto/prism-test/prism-filler\r\n* New -exportdigital switch for exporting PRISM code built by digital clocks PTA engine\r\n* New syntax for (CTMC) transient probabilities in P operator: P=? [ F=T \"target\" ]\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.0.3 (released 30/1/2012)\r\n-----------------------------------------------------------------------------\r\n\r\n* Property names\r\n  - properties can be named, by prefixing with \"name\":\r\n  - properties can appear as sub-formulae of other properties using name references\r\n  - command-line -prop switch allows selection of property to check by name\r\n* New options for results export\r\n  - export in matrix form, e.g. for surface plots\r\n  - export in CSV (rather than tab-separated) form\r\n  - expanded switch: -exportresults file[,opt1,opt2,...] with options: matrix,csv\r\n* Automatic engine switching if numerical computation not supported\r\n* Optimised Rabin automata for a few common LTL formulae\r\n* Added -pf as a command-line switch alias for -pctl/-csl\r\n* Add .props as a properties file extension (in GUI)\r\n* New switches -noprob0/-noprob1 to disable individual precomputation algorithms\r\n* Added prominence given to log warning messages in command-line/GUI\r\n* GUI on Macs uses Cmd, not Ctrl\r\n* Added PrismTest class to illustrate programmatic use of PRISM\r\n* Command-line scripts can signal termination via growlnotify/notify-send \r\n* Bash completion scripts + additional syntax highlighters\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.0.2 (released 9/10/2011)\r\n-----------------------------------------------------------------------------\r\n\r\n* Better handling of undefined constants in properties\r\n* Added -exportprodtrans and -exportprodstates switches\r\n* More improvements to explicit engine\r\n* Simulator fix: ignores \"max path length\" for time-bounded properties\r\n* Fixed to compile on Java 7\r\n* Fixed anti-aliasing in GUI model editor\r\n* Various bug fixes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.0.1 (released 27/7/2011)\r\n-----------------------------------------------------------------------------\r\n\r\n* Added if-and-only-if operator (<=>) for use in models/properties\r\n* Updated version of explicit model checking library\r\n* Testing mode (-test and -testall switches)\r\n* Various bug fixes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 4.0 (released 28/6/2011)\r\n-----------------------------------------------------------------------------\r\n\r\n* Support for probabilistic timed automata (PTAs)\r\n  - new modelling language features: clocks, invariants\r\n  - model checking of timed/untimed probabilistic reachability properties\r\n  - two model checking engines: abstraction-refinement, digital clocks\r\n  - support for expected reward properties (i.e. priced PTAs)\r\n\r\n* New approximate/statistical model checking functionality\r\n  - additional confidence-interval (CI) based approximation methods\r\n  - acceptance sampling: sequential probabilistic ratio test (SPRT) method\r\n\r\n* Optimal adversary generation for MDPs\r\n  - and for PTAs, via digital clocks engine\r\n  \r\n* Improvements to the property language and model checking\r\n  - enhanced filters for property result processing\r\n  - new, clearer reporting of results from PRISM\r\n\r\n* Improved model export functionality\r\n  - option to include state information in dot files (e.g. -exporttransdotstates)\r\n  - action labels included in dot/transition matrix exports\r\n  - clearer for file export for MDPs\r\n\r\n* Additional functionality for transient/steady-state probabilities\r\n  - option to specify initial distribution for transient analysis\r\n  - option to export steady-state/transient probabilities to a file\r\n\r\n* New components/libraries for developers:\r\n  - completely re-written discrete-event simulation engine\r\n  - explicit-state probabilistic model checking library\r\n  - a quantitative abstraction-refinement engine \r\n\r\n* Other improvements/additions:\r\n  - Strict upper time-bounds allowed in properties\r\n  - Formulas used in properties are left unexpanded for legibility\r\n  - Added check for existence of zero-reward loops in MDPs\r\n  - New -exportprism/-exportprismconst/-nobuild switches\r\n  - New -exporttarget switch\r\n  - New versions of jcommon (1.0.16) and jfreechart (1.0.13)\r\n\r\n* Changes since 4.0.beta2 (released 10/6/2011)\r\n  - None\r\n\r\n* Changes since 4.0.beta (released 16/12/2010)\r\n  - Bug fixes: simulator, error messages, typos and examples)\r\n  \r\n-----------------------------------------------------------------------------\r\nVersion 3.3.1 (released 22/11/2009)\r\n-----------------------------------------------------------------------------\r\n\r\n* Bug fixes:\r\n  - Building on new 64-bit Macs\r\n  - Simulator bug (crashes on min/max function)\r\n  - CTMC transient probs with MTBDD engine crash\r\n  - State/transition reward mix-up in parser\r\n  - Approximate verification of lower time-bounded properties for CTMCs\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.3 (released 29/10/2009)\r\n-----------------------------------------------------------------------------\r\n\r\n* Bug fixes:\r\n  - Building on new Macs\r\n  - Copy+paste bug in GUI\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.3.beta2 (released 29/7/2009)\r\n-----------------------------------------------------------------------------\r\n\r\n* Bug fixes:\r\n  - LTL model checking (svn: 1112, 1132)\r\n  - Approximate model checking (svn: 1214)\r\n  - Building on new Macs (svn: 1103, 1105, 1349)\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.3.beta1 (released 20/5/2009) (svn: trunk rev 1066)\r\n-----------------------------------------------------------------------------\r\n\r\n* New language parser:\r\n  - improved efficiency, especially on large/complex models\r\n  - more accurate error reporting\r\n* GUI model editor improvements:\r\n  - error highlighting\r\n  - line numbers\r\n  - undo/redo feature\r\n* Expanded property specification language\r\n  - LTL (and PCTL*) now supported\r\n  - arbitrary expressions allowed, e.g. 1-P=?[...]\r\n  - support for weak until (W) and release (R) added\r\n  - steady-state operators (S=?[...], R=?[S]) allowed for DTMCs\r\n  - optional semicolons to terminate properties in properties files\r\n* Modelling language changes:\r\n  - cleaner notation for functions, e.g. mod(i,n), not func(mod,i,n)\r\n  - function names can be renamed in module renaming\r\n  - language strictness: updates (x'=...) must be parenthesised\r\n  - ranges (x=1..3,5) no longer supported\r\n  - added conversion tool for old models (etc/scripts/prism3to4)\r\n* Other minor technical changes to language:\r\n  - implication allowed in any expression (not just properties)\r\n  - floor/ceil are now identifiers, not keywords\r\n  - relational operators now have precedence over equality operators\r\n  - better but slightly different parsing of problem cases like \"F<=a b\"\r\n* Improvements to memory handling, especially in sparse/hybrid engines\r\n* Updated JFreeChart library\r\n* Multiple -const switches allowed at command-line\r\n* Efficiency improvements to precomputation algorithms\r\n* Added symmetry reduction functionality\r\n* New -exportbsccs option \r\n* Initial state info for explicit import is now via -importlabels\r\n* Added prism2html/prism2latex tools (in etc/scripts)\r\n* Sparse/hybrid versions of instantaneous reward properties (R=?[I=k]) for DTMCs\r\n* Easier viewing of model checking results in GUI\r\n* Steady-state/transient probability computation for DTMCs\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.2.beta1 (released 25/2/2008) (svn: trunk rev 568)\r\n-----------------------------------------------------------------------------\r\n\r\n* Fix to allow building on Mac OS X v10.5 (Leopard)\r\n* New option for displaying extra info during reachability (-extrareachinfo switch)\r\n* Addition of some missing reward model checking algorithms\r\n  - instantaneous reward properties (R=?[I=k]) for DTMCs/MDPs (MTBDD/sparse engines only)\r\n  - cumulative reward properties (R=?[C<=k]) for DTMCs\r\n  - sparse engine version of reach reward properties (R=?[F...]) for MDPs\r\n* New option for displaying extra (MT)BDD info (-extraddinfo switch)\r\n* Font increase/decrease feature in GUI\r\n* Labels (for use in properties file) can be defined in the model file\r\n* Properties files can use formulas from model file\r\n* Partially correct property files can be loaded into the GUI\r\n* New icon set and graphics\r\n* New graph plotting engine using JFreeChart\r\n* Prototype SBML-to-PRISM translator\r\n* New option for -simpath feature: can enable/disable loop checking\r\n* New option for -simpath feature: generation of multiple paths to find deadlock\r\n* New \"rows\" option for matrix exports (-exportrows switch)\r\n* Support for 64-bit architectures\r\n* Addition of F and G operators to property language (eventually/globally)\r\n* Redesign of the simulator GUI, plus new features:\r\n  - ability to display cumulated time/rewards\r\n  - new \"Configure view\" dialog\r\n  - easier selection of next step (double click) \r\n* Resizeable experiment results table \r\n* Function \"log\" for use in expressions\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.1.1 (5/4/2007) (svn: derived from 3.1 tag)\r\n-----------------------------------------------------------------------------\r\n\r\n* Minor bug fixes:\r\n  - bug in \"New Graph\" dialog which fails on Java 6\r\n  - threading bug which can cause graph plotting to freeze\r\n  - fix to possible failure of Windows launch scripts\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.1 (15/11/2006) (svn: derived from 3.1.beta1 tag)\r\n-----------------------------------------------------------------------------\r\n\r\n* No changes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.1.beta1 (3/11/2006) (svn: trunk rev 116)\r\n-----------------------------------------------------------------------------\r\n\r\n* New installer for Windows binary\r\n* Models can now have multiple (named) reward structures\r\n* New -simpath switch for command-line generation of random paths with simulator\r\n* Minor PRISM language improvements:\r\n  - type keyword does not need to be first thing in model file\r\n  - doubles in exponential form (1.4e-9) and unary minus (-1) allowed\r\n* PRISM settings file now used by command-line version too\r\n* Small GUI improvements\r\n* New option to disable steady-state detection for CTMC transient analysis\r\n* Bug fixes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.0 (6/7/2006) (svn: trunk rev 55)\r\n-----------------------------------------------------------------------------\r\n\r\n* Bug fixes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 3.0.beta1 (29/3/2006) (svn: trunk rev 45)\r\n-----------------------------------------------------------------------------\r\n\r\n* Changes to export functionality\r\n  - transition matrix graph can be exported to a Dot file (-exporttransdot)\r\n  - can export state/transition rewards\r\n  - can export labels and their satisfying states\r\n  - can export to stdout/log instead of a file\r\n  - can export in MRMC format\r\n  - improved support for Matlab format export\r\n  - exported matrices now ordered by default (by row)\r\n  - new/rearranged command-line switches\r\n* Added new options to Model|View menu in GUI\r\n* Additional checks when parsing models:\r\n  - synchronous commands modifying globals\r\n    (now disallowed, previously just advised against)\r\n  - modification of local variables by another module\r\n    (previously detected later at build-time)\r\n* Improvements/changes to explicit import functionality:\r\n  - -importstates understands Boolean variables now\r\n  - -importinit option added\r\n  - Default module variable (x) indexed from 0, not 1\r\n* Non-convergence of iterative methods is an error, not a warning\r\n* Changed layout of simulator transition table (4 -> 3 columns)\r\n* Bugfixes\r\n* Makefile improvements  \r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev11.sim8 (3/3/2006)\r\n-----------------------------------------------------------------------------\r\n\r\n* Bug fix: computation of powers in simulator\r\n* Bug fix: calculation of transition rewards from multiple actions\r\n* Bug fixes: loop detection and deadlocks in simulator\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev11.sim7 (5/1/2006)\r\n-----------------------------------------------------------------------------\r\n\r\n* Bug fixes, tidying\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev11.sim6 (16/12/2005)\r\n-----------------------------------------------------------------------------\r\n\r\n* Merged with simulator branch\r\n* Improved options management including saving of user settings\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev11 (5/12/2005)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Bugfixes in GUI syntax highlighting, esp. for large model files\r\n* Bugfix: out-of-range initial values banned\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev10 (21/10/2005)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* GUI syntax highlighting restructure and efficiency improvement\r\n* Bugfix/tidy in GUI experiments, esp. with Booleans\r\n* Bugfix/improvements in modulo operations\r\n* Improvements to checks of probabilities/rates, e.g. for NaN\r\n* Ability to disable checks of probabilities/rates\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev9 (27/05/2005)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Tidied up simulator code/stubs\r\n* Graphical model editor disabled\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev8 (11/05/2005)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Can now be built on OS X\r\n* Makefile improvements including better OS detection\r\n* Bug fix improving efficiency of BSCC computation\r\n* Improved reporting of multiple missing constants\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev7 (22/2/2005)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Graphical model editor (temporarily?) enabled\r\n* Addition of simulator code and stubs\r\n* Tweaked main Makefile: stops after first error\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev6 (18/2/2005)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Bug fix - alphabet for default synchronisation is now derived syntactically\r\n* Updates to some APMC code\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev5 (11/2/2005)\r\n-----------------------------------------------------------------------------\r\n\r\nPartially completed changes:\r\n\r\n* PRISM Preprocessor\r\n* Improved hybrid GS\r\n* Improved syntax highlighting\r\n\r\nChanges:\r\n\r\n* Max memory for Java VM modifiable via PRISM_JAVAMAXMEM environment variable\r\n* Reorganisation of Linux/Solaris launch scripts\r\n* New notation for functions in PRISM language: func(f,x,y)\r\n* New built-in functions in PRISM language (new notation only) - power(pow), modulo(mod)\r\n* Upgrade to newest version of CUDD (2.4.0)\r\n* GUI supports multi-line comments for properties\r\n* Command-line override of model type allowed (-dtmc,-ctmc,-mdp switches)\r\n* Tidy up of output generated by filters in P/S operators\r\n* Added built-in label \"deadlock\", true in states where deadlocks fixed by PRISM\r\n* Conditional evaluation operator now allows bracketless nesting, e.g. a?b:c?d:e\r\n* Bug fixes\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev4 (21/1/2005)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* New syntax for transition rewards (within rewards construct)\r\n* Bugfix in Prob1A precomputation algorithm\r\n* Bugfix: disappearing \"{min}\"/\"{max}\" from P/R operators\r\n* Numerous improvements to graph plotting tool\r\n  - Export of graphs to Matlab\r\n  - Import/export of graphs from/to XML\r\n  - Enhanced scale behaviour/options\r\n  - Improved editing of series properties/data\r\n  - Various bug fixes\r\n* More thorough checks of commands during model construction\r\n  - each command must define transitions for all states satisfying guard\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev3 (17/11/2004)\r\n-----------------------------------------------------------------------------\r\n\r\nPartially completed changes:\r\n\r\n* Graphical model editor significantly improved (but disabled for now)\r\n\r\nChanges:\r\n\r\n* Support for import of (explicit) transition matrix and state space\r\n  (command-line only, via -importtrans/-importstates switches (and -dtmc,-ctmc,-mdp))\r\n* Improvements to graph plotting functionality\r\n* Log in GUI now operates with a limited size buffer to avoid out-of-memory problems\r\n\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev2 (20/10/2004)\r\n-----------------------------------------------------------------------------\r\n\r\nPartially completed changes:\r\n\r\n* Support for costs/rewards\r\n  - DTMC: R[F] H/S/M\r\n  - MDP: R[F] M ok, H partial\r\n  - CTMC: R[F] H/S/M, R[I=t] H/S/M, R[S] H/S/M, C[<=t] H/S/M\r\n\r\nChanges:\r\n\r\n* Added facility to compute transient probabilities\r\n\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1.dev1 (7/10/2004)\r\n-----------------------------------------------------------------------------\r\n\r\nPartially completed changes:\r\n\r\n* Support for costs/rewards\r\n* Checks during model construction that rates are non-negative and probabilities sum to one\r\n\r\nChanges:\r\n\r\n* Multiple initial states init...endinit\r\n* Support for displaying min/max of a range of probabilities using {} notation\r\n* New \"compact\" storage schemes (distinct values only) added to sparse/hybrid engines\r\n* Sparse storage schemes now use (more compact) counts instead of start indices for rows/cols\r\n* True Gauss-Seidel algorithm for hybrid engine\r\n* New switches (-pgs, -psor, -bpgs, -bpsor) to access hybrid \"psuedo\" methods\r\n* Language modification: updates can be \"true\", i.e. no variables change\r\n* Added conditional evaluation operator (cond ? then : else) to PRISM language\r\n\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.1 (released 8/9/2004)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Now possible to build/run PRISM on Windows\r\n* Compilation/installation procedures slightly simplified\r\n* Splash screen on load\r\n\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 2.0 (released 17/3/2004)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Completely new graphical user interface, including:\r\n  - Text editor for PRISM language\r\n  - Automated results collection/graph plotting\r\n  \r\n* Enhancements to PRISM language:\r\n  - Types (ints, doubles and booleans) and type checking added\r\n  - Probabilities/rates can now be expressions\r\n  - Variable ranges/initial values can now be expressions\r\n  - Constant/formula definitions can be expressions (including in terms of each other)\r\n  - Process algebra style definitions allowed for MDPs too (via \"system\" construct)\r\n  \r\n* Enhancements to property specifications:\r\n  - Probability/time bounds in PCTL/CSL properties can now be expressions\r\n  - Use of constants now permitted: both those from the model and newly declared ones\r\n  - Added \"init\" keyword to PCTL/CSL (atomic proposition true only in initial state)\r\n  - Can define and reuse \"labels\" (atomic propositions) (like formulas in model files)\r\n  - Can write properties of the form \"P=?[...]\" which return the actual probability\r\n  \r\n * Additional features:\r\n  - Automatic handling of multiple model checking computations,\r\n    e.g. check \"P~p[true U<=k error]\" for k=1..100\r\n  - Added -exportstates switch, exports reachable states to text file\r\n  - Added -nobscc switch for optional bypass of BSCC computation\r\n  - Added explicit versions of export options (including first export option for MDPs)\r\n  - Export options can now be used in conjunction with each other and with model checking\r\n  - Added -version switch to display version\r\n  \r\n* Efficiency improvements\r\n  - Improved heuristics for hybrid engine (sb/sbmax/gsl switches -> sbmax/sbl/gsmax/gsl)\r\n  - More efficient construction process for unstructured models\r\n  - General restructuring/improvements to model construction process implementation\r\n  \r\n* Miscellaneous\r\n  - Various bug fixes\r\n  - Fairness (for MDP model checking) now OFF by default (used to be ON)\r\n\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 1.3.1 (released 20/2/2003)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Bug fixes in model construction code\r\n\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 1.3 (released 10/2/2003)\r\n-----------------------------------------------------------------------------\r\n\r\nChanges:\r\n\r\n* Steady-state probability computation improved to include strongly connected component (SCC) computation\r\n* Extended support for CSL time-bounded until operator to include arbitrary intervals\r\n* More flexible parallel composition options in the PRISM language (for DTMCs and CTMCs)\r\n* Added option to import PEPA process algebra descriptions as models\r\n* Improved range of numerical methods: (Backwards) Gauss-Seidel and (Backwards) SOR (plus variants for hybrid engine)\r\n* Added -pctl/-csl switches to allow command line specification of properties\r\n* Improved handling of deadlock states: can add self-loops to these states automatically (e.g. -fixdl switch)\r\n* Steady-state probabilities are no longer automatically computed for CTMCs: use the -ss switch\r\n* Addition of {} operator to PCTL/CSL formulas to support printing of probabilities\r\n* Resolved problem with PRISM language syntax: updates must now be parenthesised\r\n* Default value for maximum number of iterations reduced from 500,000 to (more sensible) 10,000\r\n* Added switches to control CUDD behaviour (-cuddmaxmem, -cuddepsilon)\r\n* Additional example files\r\n* Numerous bug fixes\r\n* Now released under the GPL license\r\n\r\n\r\n-----------------------------------------------------------------------------\r\nVersion 1.2 (released 17/9/2001)\r\n-----------------------------------------------------------------------------\r\n\r\nFirst public release\r\n\r\n"
  },
  {
    "path": "COPYING.txt",
    "content": "\t\t    GNU GENERAL PUBLIC LICENSE\r\n\t\t       Version 2, June 1991\r\n\r\n Copyright (C) 1989, 1991 Free Software Foundation, Inc.\r\n                       59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n Everyone is permitted to copy and distribute verbatim copies\r\n of this license document, but changing it is not allowed.\r\n\r\n\t\t\t    Preamble\r\n\r\n  The licenses for most software are designed to take away your\r\nfreedom to share and change it.  By contrast, the GNU General Public\r\nLicense is intended to guarantee your freedom to share and change free\r\nsoftware--to make sure the software is free for all its users.  This\r\nGeneral Public License applies to most of the Free Software\r\nFoundation's software and to any other program whose authors commit to\r\nusing it.  (Some other Free Software Foundation software is covered by\r\nthe GNU Library General Public License instead.)  You can apply it to\r\nyour programs, too.\r\n\r\n  When we speak of free software, we are referring to freedom, not\r\nprice.  Our General Public Licenses are designed to make sure that you\r\nhave the freedom to distribute copies of free software (and charge for\r\nthis service if you wish), that you receive source code or can get it\r\nif you want it, that you can change the software or use pieces of it\r\nin new free programs; and that you know you can do these things.\r\n\r\n  To protect your rights, we need to make restrictions that forbid\r\nanyone to deny you these rights or to ask you to surrender the rights.\r\nThese restrictions translate to certain responsibilities for you if you\r\ndistribute copies of the software, or if you modify it.\r\n\r\n  For example, if you distribute copies of such a program, whether\r\ngratis or for a fee, you must give the recipients all the rights that\r\nyou have.  You must make sure that they, too, receive or can get the\r\nsource code.  And you must show them these terms so they know their\r\nrights.\r\n\r\n  We protect your rights with two steps: (1) copyright the software, and\r\n(2) offer you this license which gives you legal permission to copy,\r\ndistribute and/or modify the software.\r\n\r\n  Also, for each author's protection and ours, we want to make certain\r\nthat everyone understands that there is no warranty for this free\r\nsoftware.  If the software is modified by someone else and passed on, we\r\nwant its recipients to know that what they have is not the original, so\r\nthat any problems introduced by others will not reflect on the original\r\nauthors' reputations.\r\n\r\n  Finally, any free program is threatened constantly by software\r\npatents.  We wish to avoid the danger that redistributors of a free\r\nprogram will individually obtain patent licenses, in effect making the\r\nprogram proprietary.  To prevent this, we have made it clear that any\r\npatent must be licensed for everyone's free use or not licensed at all.\r\n\r\n  The precise terms and conditions for copying, distribution and\r\nmodification follow.\r\n\f\r\n\t\t    GNU GENERAL PUBLIC LICENSE\r\n   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION\r\n\r\n  0. This License applies to any program or other work which contains\r\na notice placed by the copyright holder saying it may be distributed\r\nunder the terms of this General Public License.  The \"Program\", below,\r\nrefers to any such program or work, and a \"work based on the Program\"\r\nmeans either the Program or any derivative work under copyright law:\r\nthat is to say, a work containing the Program or a portion of it,\r\neither verbatim or with modifications and/or translated into another\r\nlanguage.  (Hereinafter, translation is included without limitation in\r\nthe term \"modification\".)  Each licensee is addressed as \"you\".\r\n\r\nActivities other than copying, distribution and modification are not\r\ncovered by this License; they are outside its scope.  The act of\r\nrunning the Program is not restricted, and the output from the Program\r\nis covered only if its contents constitute a work based on the\r\nProgram (independent of having been made by running the Program).\r\nWhether that is true depends on what the Program does.\r\n\r\n  1. You may copy and distribute verbatim copies of the Program's\r\nsource code as you receive it, in any medium, provided that you\r\nconspicuously and appropriately publish on each copy an appropriate\r\ncopyright notice and disclaimer of warranty; keep intact all the\r\nnotices that refer to this License and to the absence of any warranty;\r\nand give any other recipients of the Program a copy of this License\r\nalong with the Program.\r\n\r\nYou may charge a fee for the physical act of transferring a copy, and\r\nyou may at your option offer warranty protection in exchange for a fee.\r\n\r\n  2. You may modify your copy or copies of the Program or any portion\r\nof it, thus forming a work based on the Program, and copy and\r\ndistribute such modifications or work under the terms of Section 1\r\nabove, provided that you also meet all of these conditions:\r\n\r\n    a) You must cause the modified files to carry prominent notices\r\n    stating that you changed the files and the date of any change.\r\n\r\n    b) You must cause any work that you distribute or publish, that in\r\n    whole or in part contains or is derived from the Program or any\r\n    part thereof, to be licensed as a whole at no charge to all third\r\n    parties under the terms of this License.\r\n\r\n    c) If the modified program normally reads commands interactively\r\n    when run, you must cause it, when started running for such\r\n    interactive use in the most ordinary way, to print or display an\r\n    announcement including an appropriate copyright notice and a\r\n    notice that there is no warranty (or else, saying that you provide\r\n    a warranty) and that users may redistribute the program under\r\n    these conditions, and telling the user how to view a copy of this\r\n    License.  (Exception: if the Program itself is interactive but\r\n    does not normally print such an announcement, your work based on\r\n    the Program is not required to print an announcement.)\r\n\f\r\nThese requirements apply to the modified work as a whole.  If\r\nidentifiable sections of that work are not derived from the Program,\r\nand can be reasonably considered independent and separate works in\r\nthemselves, then this License, and its terms, do not apply to those\r\nsections when you distribute them as separate works.  But when you\r\ndistribute the same sections as part of a whole which is a work based\r\non the Program, the distribution of the whole must be on the terms of\r\nthis License, whose permissions for other licensees extend to the\r\nentire whole, and thus to each and every part regardless of who wrote it.\r\n\r\nThus, it is not the intent of this section to claim rights or contest\r\nyour rights to work written entirely by you; rather, the intent is to\r\nexercise the right to control the distribution of derivative or\r\ncollective works based on the Program.\r\n\r\nIn addition, mere aggregation of another work not based on the Program\r\nwith the Program (or with a work based on the Program) on a volume of\r\na storage or distribution medium does not bring the other work under\r\nthe scope of this License.\r\n\r\n  3. You may copy and distribute the Program (or a work based on it,\r\nunder Section 2) in object code or executable form under the terms of\r\nSections 1 and 2 above provided that you also do one of the following:\r\n\r\n    a) Accompany it with the complete corresponding machine-readable\r\n    source code, which must be distributed under the terms of Sections\r\n    1 and 2 above on a medium customarily used for software interchange; or,\r\n\r\n    b) Accompany it with a written offer, valid for at least three\r\n    years, to give any third party, for a charge no more than your\r\n    cost of physically performing source distribution, a complete\r\n    machine-readable copy of the corresponding source code, to be\r\n    distributed under the terms of Sections 1 and 2 above on a medium\r\n    customarily used for software interchange; or,\r\n\r\n    c) Accompany it with the information you received as to the offer\r\n    to distribute corresponding source code.  (This alternative is\r\n    allowed only for noncommercial distribution and only if you\r\n    received the program in object code or executable form with such\r\n    an offer, in accord with Subsection b above.)\r\n\r\nThe source code for a work means the preferred form of the work for\r\nmaking modifications to it.  For an executable work, complete source\r\ncode means all the source code for all modules it contains, plus any\r\nassociated interface definition files, plus the scripts used to\r\ncontrol compilation and installation of the executable.  However, as a\r\nspecial exception, the source code distributed need not include\r\nanything that is normally distributed (in either source or binary\r\nform) with the major components (compiler, kernel, and so on) of the\r\noperating system on which the executable runs, unless that component\r\nitself accompanies the executable.\r\n\r\nIf distribution of executable or object code is made by offering\r\naccess to copy from a designated place, then offering equivalent\r\naccess to copy the source code from the same place counts as\r\ndistribution of the source code, even though third parties are not\r\ncompelled to copy the source along with the object code.\r\n\f\r\n  4. You may not copy, modify, sublicense, or distribute the Program\r\nexcept as expressly provided under this License.  Any attempt\r\notherwise to copy, modify, sublicense or distribute the Program is\r\nvoid, and will automatically terminate your rights under this License.\r\nHowever, parties who have received copies, or rights, from you under\r\nthis License will not have their licenses terminated so long as such\r\nparties remain in full compliance.\r\n\r\n  5. You are not required to accept this License, since you have not\r\nsigned it.  However, nothing else grants you permission to modify or\r\ndistribute the Program or its derivative works.  These actions are\r\nprohibited by law if you do not accept this License.  Therefore, by\r\nmodifying or distributing the Program (or any work based on the\r\nProgram), you indicate your acceptance of this License to do so, and\r\nall its terms and conditions for copying, distributing or modifying\r\nthe Program or works based on it.\r\n\r\n  6. Each time you redistribute the Program (or any work based on the\r\nProgram), the recipient automatically receives a license from the\r\noriginal licensor to copy, distribute or modify the Program subject to\r\nthese terms and conditions.  You may not impose any further\r\nrestrictions on the recipients' exercise of the rights granted herein.\r\nYou are not responsible for enforcing compliance by third parties to\r\nthis License.\r\n\r\n  7. If, as a consequence of a court judgment or allegation of patent\r\ninfringement or for any other reason (not limited to patent issues),\r\nconditions are imposed on you (whether by court order, agreement or\r\notherwise) that contradict the conditions of this License, they do not\r\nexcuse you from the conditions of this License.  If you cannot\r\ndistribute so as to satisfy simultaneously your obligations under this\r\nLicense and any other pertinent obligations, then as a consequence you\r\nmay not distribute the Program at all.  For example, if a patent\r\nlicense would not permit royalty-free redistribution of the Program by\r\nall those who receive copies directly or indirectly through you, then\r\nthe only way you could satisfy both it and this License would be to\r\nrefrain entirely from distribution of the Program.\r\n\r\nIf any portion of this section is held invalid or unenforceable under\r\nany particular circumstance, the balance of the section is intended to\r\napply and the section as a whole is intended to apply in other\r\ncircumstances.\r\n\r\nIt is not the purpose of this section to induce you to infringe any\r\npatents or other property right claims or to contest validity of any\r\nsuch claims; this section has the sole purpose of protecting the\r\nintegrity of the free software distribution system, which is\r\nimplemented by public license practices.  Many people have made\r\ngenerous contributions to the wide range of software distributed\r\nthrough that system in reliance on consistent application of that\r\nsystem; it is up to the author/donor to decide if he or she is willing\r\nto distribute software through any other system and a licensee cannot\r\nimpose that choice.\r\n\r\nThis section is intended to make thoroughly clear what is believed to\r\nbe a consequence of the rest of this License.\r\n\f\r\n  8. If the distribution and/or use of the Program is restricted in\r\ncertain countries either by patents or by copyrighted interfaces, the\r\noriginal copyright holder who places the Program under this License\r\nmay add an explicit geographical distribution limitation excluding\r\nthose countries, so that distribution is permitted only in or among\r\ncountries not thus excluded.  In such case, this License incorporates\r\nthe limitation as if written in the body of this License.\r\n\r\n  9. The Free Software Foundation may publish revised and/or new versions\r\nof the General Public License from time to time.  Such new versions will\r\nbe similar in spirit to the present version, but may differ in detail to\r\naddress new problems or concerns.\r\n\r\nEach version is given a distinguishing version number.  If the Program\r\nspecifies a version number of this License which applies to it and \"any\r\nlater version\", you have the option of following the terms and conditions\r\neither of that version or of any later version published by the Free\r\nSoftware Foundation.  If the Program does not specify a version number of\r\nthis License, you may choose any version ever published by the Free Software\r\nFoundation.\r\n\r\n  10. If you wish to incorporate parts of the Program into other free\r\nprograms whose distribution conditions are different, write to the author\r\nto ask for permission.  For software which is copyrighted by the Free\r\nSoftware Foundation, write to the Free Software Foundation; we sometimes\r\nmake exceptions for this.  Our decision will be guided by the two goals\r\nof preserving the free status of all derivatives of our free software and\r\nof promoting the sharing and reuse of software generally.\r\n\r\n\t\t\t    NO WARRANTY\r\n\r\n  11. BECAUSE THE PROGRAM IS LICENSED FREE OF CHARGE, THERE IS NO WARRANTY\r\nFOR THE PROGRAM, TO THE EXTENT PERMITTED BY APPLICABLE LAW.  EXCEPT WHEN\r\nOTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR OTHER PARTIES\r\nPROVIDE THE PROGRAM \"AS IS\" WITHOUT WARRANTY OF ANY KIND, EITHER EXPRESSED\r\nOR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF\r\nMERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE.  THE ENTIRE RISK AS\r\nTO THE QUALITY AND PERFORMANCE OF THE PROGRAM IS WITH YOU.  SHOULD THE\r\nPROGRAM PROVE DEFECTIVE, YOU ASSUME THE COST OF ALL NECESSARY SERVICING,\r\nREPAIR OR CORRECTION.\r\n\r\n  12. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN WRITING\r\nWILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY AND/OR\r\nREDISTRIBUTE THE PROGRAM AS PERMITTED ABOVE, BE LIABLE TO YOU FOR DAMAGES,\r\nINCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR CONSEQUENTIAL DAMAGES ARISING\r\nOUT OF THE USE OR INABILITY TO USE THE PROGRAM (INCLUDING BUT NOT LIMITED\r\nTO LOSS OF DATA OR DATA BEING RENDERED INACCURATE OR LOSSES SUSTAINED BY\r\nYOU OR THIRD PARTIES OR A FAILURE OF THE PROGRAM TO OPERATE WITH ANY OTHER\r\nPROGRAMS), EVEN IF SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE\r\nPOSSIBILITY OF SUCH DAMAGES.\r\n\r\n\t\t     END OF TERMS AND CONDITIONS\r\n\f\r\n\t    How to Apply These Terms to Your New Programs\r\n\r\n  If you develop a new program, and you want it to be of the greatest\r\npossible use to the public, the best way to achieve this is to make it\r\nfree software which everyone can redistribute and change under these terms.\r\n\r\n  To do so, attach the following notices to the program.  It is safest\r\nto attach them to the start of each source file to most effectively\r\nconvey the exclusion of warranty; and each file should have at least\r\nthe \"copyright\" line and a pointer to where the full notice is found.\r\n\r\n    <one line to give the program's name and a brief idea of what it does.>\r\n    Copyright (C) <year>  <name of author>\r\n\r\n    This program is free software; you can redistribute it and/or modify\r\n    it under the terms of the GNU General Public License as published by\r\n    the Free Software Foundation; either version 2 of the License, or\r\n    (at your option) any later version.\r\n\r\n    This program is distributed in the hope that it will be useful,\r\n    but WITHOUT ANY WARRANTY; without even the implied warranty of\r\n    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r\n    GNU General Public License for more details.\r\n\r\n    You should have received a copy of the GNU General Public License\r\n    along with this program; if not, write to the Free Software\r\n    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n\r\n\r\nAlso add information on how to contact you by electronic and paper mail.\r\n\r\nIf the program is interactive, make it output a short notice like this\r\nwhen it starts in an interactive mode:\r\n\r\n    Gnomovision version 69, Copyright (C) year name of author\r\n    Gnomovision comes with ABSOLUTELY NO WARRANTY; for details type `show w'.\r\n    This is free software, and you are welcome to redistribute it\r\n    under certain conditions; type `show c' for details.\r\n\r\nThe hypothetical commands `show w' and `show c' should show the appropriate\r\nparts of the General Public License.  Of course, the commands you use may\r\nbe called something other than `show w' and `show c'; they could even be\r\nmouse-clicks or menu items--whatever suits your program.\r\n\r\nYou should also get your employer (if you work as a programmer) or your\r\nschool, if any, to sign a \"copyright disclaimer\" for the program, if\r\nnecessary.  Here is a sample; alter the names:\r\n\r\n  Yoyodyne, Inc., hereby disclaims all copyright interest in the program\r\n  `Gnomovision' (which makes passes at compilers) written by James Hacker.\r\n\r\n  <signature of Ty Coon>, 1 April 1989\r\n  Ty Coon, President of Vice\r\n\r\nThis General Public License does not permit incorporating your program into\r\nproprietary programs.  If your program is a subroutine library, you may\r\nconsider it more useful to permit linking proprietary applications with the\r\nlibrary.  If this is what you want to do, use the GNU Library General\r\nPublic License instead of this License.\r\n"
  },
  {
    "path": "README.md",
    "content": "# PRISM\r\n\r\nThis is PRISM (Probabilistic Symbolic Model Checker).\r\n\r\n\r\n## Installation\r\n\r\nFor detailed installation instructions, check the online manual at:\r\n\r\n  https://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions\r\n  \r\nor see the local copy included in this distribution:\r\n\r\n * `manual/InstallingPRISM/Instructions.html`\r\n\r\nVery abbreviated instructions for installing/running PRISM are as follows:\r\n\r\nFor Windows binary distributions:\r\n\r\n * to install, run `prism-XXX-win64-installer.exe`\r\n * to run, use Desktop/Start menu shortcuts or double-click `bin\\xprism.bat`\r\n\r\nFor other binary distributions:\r\n\r\n * to install, enter the PRISM directory and type `./install.sh`\r\n * to run, execute `bin/xprism` or `bin/prism`\r\n\r\nFor source code distributions:\r\n\r\n * enter the PRISM directory and type `cd prism` then `make`\r\n * to check the install, type `make test` or `etc/tests/run.sh`\r\n * to run, execute `bin/xprism` or `bin/prism`\r\n\r\nIf you have problems check the manual, especially the section \"Common Problems And Questions\".\r\n\r\n\r\n## Documentation\r\n\r\nThe best source of information about using PRISM is the online manual:\r\n\r\n  https://www.prismmodelchecker.org/manual/\r\n\r\nYou can also view the local copy included in this distribution:\r\n\r\n  * `manual/index.html`\r\n\r\nFor other PRISM-related information, see the website:\r\n\r\n  https://www.prismmodelchecker.org/doc\r\n\r\nInformation for developers is kept here:\r\n\r\n  https://github.com/prismmodelchecker/prism/wiki\r\n\r\n## Licensing\r\n\r\nPRISM is distributed under the GNU General Public License (GPL), version 2.\r\nA copy of this license can be found in the file `COPYING.txt`.\r\nFor more information, see:\r\n\r\n  https://www.gnu.org/licenses/\r\n\r\nPRISM also uses various other libraries (mainly to be found in the lib directory).\r\nFor details of those, including licenses and links to downloads and source code, see:\r\n\r\nhttps://www.prismmodelchecker.org/other-downloads.php\r\n\r\n\r\n## Acknowledgements\r\n\r\nPRISM was created and is still actively maintained by:\r\n\r\n * Dave Parker (University of Oxford)\r\n * Gethin Norman (University of Glasgow)\r\n * Marta Kwiatkowska (University of Oxford) \r\n\r\nDevelopment of the tool is currently led from Oxford by Dave Parker.\r\n\r\nThe following have made a wide range of contributions to\r\nPRISM covering many different aspects of the tool\r\n(in approximately reverse chronological order):\r\n\r\n * Steffen Märcker (Technische Universität Dresden)\r\n * Joachim Klein (formerly Technische Universität Dresden)\r\n * Vojtech Forejt (formerly University of Oxford)\r\n\r\nWe also gratefully acknowledge contributions to the PRISM code-base from\r\n(in approximately reverse chronological order):\r\n\r\n * Max Kurze: Language parser code improvements\r\n * Ludwig Pauly: Reward import/export\r\n * Alberto Puggelli: First version of interval DTMC/MDP code\r\n * Xueyi Zou: Partially observable Markov decision processes (POMDPs)\r\n * Chris Novakovic: Build infrastructure and explicit engine improvements\r\n * Ernst Moritz Hahn: Parametric model checking, fast adaptive uniformisation + various other features\r\n * Frits Dannenberg: Fast adaptive uniformisation\r\n * Hongyang Qu: Multi-objective model checking\r\n * Mateusz Ujma: Bug fixes and GUI improvements\r\n * Christian von Essen: Symbolic/explicit-state model checking\r\n * Vincent Nimal: Approximate (simulation-based) model checking techniques\r\n * Mark Kattenbelt: Wide range of enhancements/additions, especially in the GUI\r\n * Carlos Bederian (working with Pedro D'Argenio): LTL model checking for MDPs\r\n * Gethin Norman: Precomputation algorithms, abstraction\r\n * Alistair John Strachan: Port to 64-bit architectures\r\n * Alistair John Strachan, Mike Arthur and Zak Cohen: Integration of JFreeChart into PRISM\r\n * Charles Harley and Sebastian Vermehren: GUI enhancements\r\n * Rashid Mehmood: Improvements to low-level data structures and numerical solution algorithms\r\n * Stephen Gilmore: Support for the stochastic process algebra PEPA\r\n * Paolo Ballarini & Kenneth Chan: Port to Mac OS X\r\n * Andrew Hinton: Original versions of the GUI, Windows port and simulator\r\n * Joachim Meyer-Kayser: Original implementation of the \"Fox-Glynn\" algorithm \r\n\r\nFor more details see:\r\n\r\n  https://www.prismmodelchecker.org/people.php\r\n\r\n\r\n## Contact\r\n\r\nIf you have problems or questions regarding PRISM, please use the help forum provided. See:\r\n\r\n  https://www.prismmodelchecker.org/support.php\r\n\r\nOther comments and feedback about any aspect of PRISM are also very welcome. Please contact:\r\n\r\n  Dave Parker  \r\n  (david.parker@cs.ox.ac.uk)  \r\n  Department of Computer Science  \r\n  University of Oxford  \r\n  Oxford  \r\n  OX1 3QG\r\n  UK\r\n"
  },
  {
    "path": "cudd/.gitignore",
    "content": "# general patterns to ignore\n# Emacs backup files\n*~\n# OS X system files\n.DS_Store\n\n# build artefacts by pattern:\n*.o\n*.a\n*.class\n*.dylib\n*.jnilib\n*.so\n*.dll\n*.lo\n*.la\n*.dirstamp\n.deps\n.libs\n\n# build artefacts:\nconfig.h\nconfig.log\nconfig.status\nMakefile\nlibtool\nstamp-h1\ndoc/cudd.tex\ndddmp/exp/*.sh\ninclude\n"
  },
  {
    "path": "cudd/Doxyfile.in",
    "content": "# Doxyfile 1.8.9.1\n\n# This file describes the settings to be used by the documentation system\n# doxygen (www.doxygen.org) for a project.\n#\n# All text after a double hash (##) is considered a comment and is placed in\n# front of the TAG it is preceding.\n#\n# All text after a single hash (#) is considered a comment and will be ignored.\n# The format is:\n# TAG = value [value, ...]\n# For lists, items can also be appended using:\n# TAG += value [value, ...]\n# Values that contain spaces should be placed between quotes (\\\" \\\").\n\n#---------------------------------------------------------------------------\n# Project related configuration options\n#---------------------------------------------------------------------------\n\n# This tag specifies the encoding used for all characters in the config file\n# that follow. The default is UTF-8 which is also the encoding used for all text\n# before the first occurrence of this tag. Doxygen uses libiconv (or the iconv\n# built into libc) for the transcoding. See http://www.gnu.org/software/libiconv\n# for the list of possible encodings.\n# The default value is: UTF-8.\n\nDOXYFILE_ENCODING      = UTF-8\n\n# The PROJECT_NAME tag is a single word (or a sequence of words surrounded by\n# double-quotes, unless you are using Doxywizard) that should identify the\n# project for which the documentation is generated. This name is used in the\n# title of most generated pages and in a few other places.\n# The default value is: My Project.\n\nPROJECT_NAME           = @PACKAGE_NAME@\n\n# The PROJECT_NUMBER tag can be used to enter a project or revision number. This\n# could be handy for archiving the generated documentation or if some version\n# control system is used.\n\nPROJECT_NUMBER         = @PACKAGE_VERSION@\n\n# Using the PROJECT_BRIEF tag one can provide an optional one line description\n# for a project that appears at the top of each page and should give viewer a\n# quick idea about the purpose of the project. Keep the description short.\n\nPROJECT_BRIEF          = \"The University of Colorado Decision Diagram Package\"\n\n# With the PROJECT_LOGO tag one can specify a logo or an icon that is included\n# in the documentation. The maximum height of the logo should not exceed 55\n# pixels and the maximum width should not exceed 200 pixels. Doxygen will copy\n# the logo to the output directory.\n\nPROJECT_LOGO           =\n\n# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) path\n# into which the generated documentation will be written. If a relative path is\n# entered, it will be relative to the location where doxygen was started. If\n# left blank the current directory will be used.\n\nOUTPUT_DIRECTORY       =\n\n# If the CREATE_SUBDIRS tag is set to YES then doxygen will create 4096 sub-\n# directories (in 2 levels) under the output directory of each output format and\n# will distribute the generated files over these directories. Enabling this\n# option can be useful when feeding doxygen a huge amount of source files, where\n# putting all generated files in the same directory would otherwise causes\n# performance problems for the file system.\n# The default value is: NO.\n\nCREATE_SUBDIRS         = NO\n\n# If the ALLOW_UNICODE_NAMES tag is set to YES, doxygen will allow non-ASCII\n# characters to appear in the names of generated files. If set to NO, non-ASCII\n# characters will be escaped, for example _xE3_x81_x84 will be used for Unicode\n# U+3044.\n# The default value is: NO.\n\nALLOW_UNICODE_NAMES    = NO\n\n# The OUTPUT_LANGUAGE tag is used to specify the language in which all\n# documentation generated by doxygen is written. Doxygen will use this\n# information to generate all constant output in the proper language.\n# Possible values are: Afrikaans, Arabic, Armenian, Brazilian, Catalan, Chinese,\n# Chinese-Traditional, Croatian, Czech, Danish, Dutch, English (United States),\n# Esperanto, Farsi (Persian), Finnish, French, German, Greek, Hungarian,\n# Indonesian, Italian, Japanese, Japanese-en (Japanese with English messages),\n# Korean, Korean-en (Korean with English messages), Latvian, Lithuanian,\n# Macedonian, Norwegian, Persian (Farsi), Polish, Portuguese, Romanian, Russian,\n# Serbian, Serbian-Cyrillic, Slovak, Slovene, Spanish, Swedish, Turkish,\n# Ukrainian and Vietnamese.\n# The default value is: English.\n\nOUTPUT_LANGUAGE        = English\n\n# If the BRIEF_MEMBER_DESC tag is set to YES, doxygen will include brief member\n# descriptions after the members that are listed in the file and class\n# documentation (similar to Javadoc). Set to NO to disable this.\n# The default value is: YES.\n\nBRIEF_MEMBER_DESC      = YES\n\n# If the REPEAT_BRIEF tag is set to YES, doxygen will prepend the brief\n# description of a member or function before the detailed description\n#\n# Note: If both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the\n# brief descriptions will be completely suppressed.\n# The default value is: YES.\n\nREPEAT_BRIEF           = YES\n\n# This tag implements a quasi-intelligent brief description abbreviator that is\n# used to form the text in various listings. Each string in this list, if found\n# as the leading text of the brief description, will be stripped from the text\n# and the result, after processing the whole list, is used as the annotated\n# text. Otherwise, the brief description is used as-is. If left blank, the\n# following values are used ($name is automatically replaced with the name of\n# the entity):The $name class, The $name widget, The $name file, is, provides,\n# specifies, contains, represents, a, an and the.\n\nABBREVIATE_BRIEF       =\n\n# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then\n# doxygen will generate a detailed section even if there is only a brief\n# description.\n# The default value is: NO.\n\nALWAYS_DETAILED_SEC    = NO\n\n# If the INLINE_INHERITED_MEMB tag is set to YES, doxygen will show all\n# inherited members of a class in the documentation of that class as if those\n# members were ordinary class members. Constructors, destructors and assignment\n# operators of the base classes will not be shown.\n# The default value is: NO.\n\nINLINE_INHERITED_MEMB  = NO\n\n# If the FULL_PATH_NAMES tag is set to YES, doxygen will prepend the full path\n# before files name in the file list and in the header files. If set to NO the\n# shortest path that makes the file name unique will be used\n# The default value is: YES.\n\nFULL_PATH_NAMES        = YES\n\n# The STRIP_FROM_PATH tag can be used to strip a user-defined part of the path.\n# Stripping is only done if one of the specified strings matches the left-hand\n# part of the path. The tag can be used to show relative paths in the file list.\n# If left blank the directory from which doxygen is run is used as the path to\n# strip.\n#\n# Note that you can specify absolute paths here, but also relative paths, which\n# will be relative from the directory where doxygen is started.\n# This tag requires that the tag FULL_PATH_NAMES is set to YES.\n\nSTRIP_FROM_PATH        = @top_srcdir@\n\n# The STRIP_FROM_INC_PATH tag can be used to strip a user-defined part of the\n# path mentioned in the documentation of a class, which tells the reader which\n# header file to include in order to use a class. If left blank only the name of\n# the header file containing the class definition is used. Otherwise one should\n# specify the list of include paths that are normally passed to the compiler\n# using the -I flag.\n\nSTRIP_FROM_INC_PATH    =\n\n# If the SHORT_NAMES tag is set to YES, doxygen will generate much shorter (but\n# less readable) file names. This can be useful is your file systems doesn't\n# support long names like on DOS, Mac, or CD-ROM.\n# The default value is: NO.\n\nSHORT_NAMES            = NO\n\n# If the JAVADOC_AUTOBRIEF tag is set to YES then doxygen will interpret the\n# first line (until the first dot) of a Javadoc-style comment as the brief\n# description. If set to NO, the Javadoc-style will behave just like regular Qt-\n# style comments (thus requiring an explicit @brief command for a brief\n# description.)\n# The default value is: NO.\n\nJAVADOC_AUTOBRIEF      = NO\n\n# If the QT_AUTOBRIEF tag is set to YES then doxygen will interpret the first\n# line (until the first dot) of a Qt-style comment as the brief description. If\n# set to NO, the Qt-style will behave just like regular Qt-style comments (thus\n# requiring an explicit \\brief command for a brief description.)\n# The default value is: NO.\n\nQT_AUTOBRIEF           = NO\n\n# The MULTILINE_CPP_IS_BRIEF tag can be set to YES to make doxygen treat a\n# multi-line C++ special comment block (i.e. a block of //! or /// comments) as\n# a brief description. This used to be the default behavior. The new default is\n# to treat a multi-line C++ comment block as a detailed description. Set this\n# tag to YES if you prefer the old behavior instead.\n#\n# Note that setting this tag to YES also means that rational rose comments are\n# not recognized any more.\n# The default value is: NO.\n\nMULTILINE_CPP_IS_BRIEF = NO\n\n# If the INHERIT_DOCS tag is set to YES then an undocumented member inherits the\n# documentation from any documented member that it re-implements.\n# The default value is: YES.\n\nINHERIT_DOCS           = YES\n\n# If the SEPARATE_MEMBER_PAGES tag is set to YES then doxygen will produce a new\n# page for each member. If set to NO, the documentation of a member will be part\n# of the file/class/namespace that contains it.\n# The default value is: NO.\n\nSEPARATE_MEMBER_PAGES  = NO\n\n# The TAB_SIZE tag can be used to set the number of spaces in a tab. Doxygen\n# uses this value to replace tabs by spaces in code fragments.\n# Minimum value: 1, maximum value: 16, default value: 4.\n\nTAB_SIZE               = 4\n\n# This tag can be used to specify a number of aliases that act as commands in\n# the documentation. An alias has the form:\n# name=value\n# For example adding\n# \"sideeffect=@par Side effects\\n\"\n# will allow you to put the command \\sideeffect (or @sideeffect) in the\n# documentation, which will result in a user-defined paragraph with heading\n# \"Side Effects:\". You can put \\n's in the value part of an alias to insert\n# newlines.\n\nALIASES                = sideeffect=\"\\par Side effects\\n\"\n\n# This tag can be used to specify a number of word-keyword mappings (TCL only).\n# A mapping has the form \"name=value\". For example adding \"class=itcl::class\"\n# will allow you to use the command class in the itcl::class meaning.\n\nTCL_SUBST              =\n\n# Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C sources\n# only. Doxygen will then generate output that is more tailored for C. For\n# instance, some of the names that are used will be different. The list of all\n# members will be omitted, etc.\n# The default value is: NO.\n\nOPTIMIZE_OUTPUT_FOR_C  = YES\n\n# Set the OPTIMIZE_OUTPUT_JAVA tag to YES if your project consists of Java or\n# Python sources only. Doxygen will then generate output that is more tailored\n# for that language. For instance, namespaces will be presented as packages,\n# qualified scopes will look different, etc.\n# The default value is: NO.\n\nOPTIMIZE_OUTPUT_JAVA   = NO\n\n# Set the OPTIMIZE_FOR_FORTRAN tag to YES if your project consists of Fortran\n# sources. Doxygen will then generate output that is tailored for Fortran.\n# The default value is: NO.\n\nOPTIMIZE_FOR_FORTRAN   = NO\n\n# Set the OPTIMIZE_OUTPUT_VHDL tag to YES if your project consists of VHDL\n# sources. Doxygen will then generate output that is tailored for VHDL.\n# The default value is: NO.\n\nOPTIMIZE_OUTPUT_VHDL   = NO\n\n# Doxygen selects the parser to use depending on the extension of the files it\n# parses. With this tag you can assign which parser to use for a given\n# extension. Doxygen has a built-in mapping, but you can override or extend it\n# using this tag. The format is ext=language, where ext is a file extension, and\n# language is one of the parsers supported by doxygen: IDL, Java, Javascript,\n# C#, C, C++, D, PHP, Objective-C, Python, Fortran (fixed format Fortran:\n# FortranFixed, free formatted Fortran: FortranFree, unknown formatted Fortran:\n# Fortran. In the later case the parser tries to guess whether the code is fixed\n# or free formatted code, this is the default for Fortran type files), VHDL. For\n# instance to make doxygen treat .inc files as Fortran files (default is PHP),\n# and .f files as C (default is Fortran), use: inc=Fortran f=C.\n#\n# Note: For files without extension you can use no_extension as a placeholder.\n#\n# Note that for custom extensions you also need to set FILE_PATTERNS otherwise\n# the files are not read by doxygen.\n\nEXTENSION_MAPPING      =\n\n# If the MARKDOWN_SUPPORT tag is enabled then doxygen pre-processes all comments\n# according to the Markdown format, which allows for more readable\n# documentation. See http://daringfireball.net/projects/markdown/ for details.\n# The output of markdown processing is further processed by doxygen, so you can\n# mix doxygen, HTML, and XML commands with Markdown formatting. Disable only in\n# case of backward compatibilities issues.\n# The default value is: YES.\n\nMARKDOWN_SUPPORT       = YES\n\n# When enabled doxygen tries to link words that correspond to documented\n# classes, or namespaces to their corresponding documentation. Such a link can\n# be prevented in individual cases by putting a % sign in front of the word or\n# globally by setting AUTOLINK_SUPPORT to NO.\n# The default value is: YES.\n\nAUTOLINK_SUPPORT       = YES\n\n# If you use STL classes (i.e. std::string, std::vector, etc.) but do not want\n# to include (a tag file for) the STL sources as input, then you should set this\n# tag to YES in order to let doxygen match functions declarations and\n# definitions whose arguments contain STL classes (e.g. func(std::string);\n# versus func(std::string) {}). This also make the inheritance and collaboration\n# diagrams that involve STL classes more complete and accurate.\n# The default value is: NO.\n\nBUILTIN_STL_SUPPORT    = NO\n\n# If you use Microsoft's C++/CLI language, you should set this option to YES to\n# enable parsing support.\n# The default value is: NO.\n\nCPP_CLI_SUPPORT        = NO\n\n# Set the SIP_SUPPORT tag to YES if your project consists of sip (see:\n# http://www.riverbankcomputing.co.uk/software/sip/intro) sources only. Doxygen\n# will parse them like normal C++ but will assume all classes use public instead\n# of private inheritance when no explicit protection keyword is present.\n# The default value is: NO.\n\nSIP_SUPPORT            = NO\n\n# For Microsoft's IDL there are propget and propput attributes to indicate\n# getter and setter methods for a property. Setting this option to YES will make\n# doxygen to replace the get and set methods by a property in the documentation.\n# This will only work if the methods are indeed getting or setting a simple\n# type. If this is not the case, or you want to show the methods anyway, you\n# should set this option to NO.\n# The default value is: YES.\n\nIDL_PROPERTY_SUPPORT   = YES\n\n# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC\n# tag is set to YES then doxygen will reuse the documentation of the first\n# member in the group (if any) for the other members of the group. By default\n# all members of a group must be documented explicitly.\n# The default value is: NO.\n\nDISTRIBUTE_GROUP_DOC   = NO\n\n# Set the SUBGROUPING tag to YES to allow class member groups of the same type\n# (for instance a group of public functions) to be put as a subgroup of that\n# type (e.g. under the Public Functions section). Set it to NO to prevent\n# subgrouping. Alternatively, this can be done per class using the\n# \\nosubgrouping command.\n# The default value is: YES.\n\nSUBGROUPING            = YES\n\n# When the INLINE_GROUPED_CLASSES tag is set to YES, classes, structs and unions\n# are shown inside the group in which they are included (e.g. using \\ingroup)\n# instead of on a separate page (for HTML and Man pages) or section (for LaTeX\n# and RTF).\n#\n# Note that this feature does not work in combination with\n# SEPARATE_MEMBER_PAGES.\n# The default value is: NO.\n\nINLINE_GROUPED_CLASSES = NO\n\n# When the INLINE_SIMPLE_STRUCTS tag is set to YES, structs, classes, and unions\n# with only public data fields or simple typedef fields will be shown inline in\n# the documentation of the scope in which they are defined (i.e. file,\n# namespace, or group documentation), provided this scope is documented. If set\n# to NO, structs, classes, and unions are shown on a separate page (for HTML and\n# Man pages) or section (for LaTeX and RTF).\n# The default value is: NO.\n\nINLINE_SIMPLE_STRUCTS  = NO\n\n# When TYPEDEF_HIDES_STRUCT tag is enabled, a typedef of a struct, union, or\n# enum is documented as struct, union, or enum with the name of the typedef. So\n# typedef struct TypeS {} TypeT, will appear in the documentation as a struct\n# with name TypeT. When disabled the typedef will appear as a member of a file,\n# namespace, or class. And the struct will be named TypeS. This can typically be\n# useful for C code in case the coding convention dictates that all compound\n# types are typedef'ed and only the typedef is referenced, never the tag name.\n# The default value is: NO.\n\nTYPEDEF_HIDES_STRUCT   = NO\n\n# The size of the symbol lookup cache can be set using LOOKUP_CACHE_SIZE. This\n# cache is used to resolve symbols given their name and scope. Since this can be\n# an expensive process and often the same symbol appears multiple times in the\n# code, doxygen keeps a cache of pre-resolved symbols. If the cache is too small\n# doxygen will become slower. If the cache is too large, memory is wasted. The\n# cache size is given by this formula: 2^(16+LOOKUP_CACHE_SIZE). The valid range\n# is 0..9, the default is 0, corresponding to a cache size of 2^16=65536\n# symbols. At the end of a run doxygen will report the cache usage and suggest\n# the optimal cache size from a speed point of view.\n# Minimum value: 0, maximum value: 9, default value: 0.\n\nLOOKUP_CACHE_SIZE      = 0\n\n#---------------------------------------------------------------------------\n# Build related configuration options\n#---------------------------------------------------------------------------\n\n# If the EXTRACT_ALL tag is set to YES, doxygen will assume all entities in\n# documentation are documented, even if no documentation was available. Private\n# class members and static file members will be hidden unless the\n# EXTRACT_PRIVATE respectively EXTRACT_STATIC tags are set to YES.\n# Note: This will also disable the warnings about undocumented members that are\n# normally produced when WARNINGS is set to YES.\n# The default value is: NO.\n\nEXTRACT_ALL            = NO\n\n# If the EXTRACT_PRIVATE tag is set to YES, all private members of a class will\n# be included in the documentation.\n# The default value is: NO.\n\nEXTRACT_PRIVATE        = NO\n\n# If the EXTRACT_PACKAGE tag is set to YES, all members with package or internal\n# scope will be included in the documentation.\n# The default value is: NO.\n\nEXTRACT_PACKAGE        = NO\n\n# If the EXTRACT_STATIC tag is set to YES, all static members of a file will be\n# included in the documentation.\n# The default value is: NO.\n\nEXTRACT_STATIC         = YES\n\n# If the EXTRACT_LOCAL_CLASSES tag is set to YES, classes (and structs) defined\n# locally in source files will be included in the documentation. If set to NO,\n# only classes defined in header files are included. Does not have any effect\n# for Java sources.\n# The default value is: YES.\n\nEXTRACT_LOCAL_CLASSES  = YES\n\n# This flag is only useful for Objective-C code. If set to YES, local methods,\n# which are defined in the implementation section but not in the interface are\n# included in the documentation. If set to NO, only methods in the interface are\n# included.\n# The default value is: NO.\n\nEXTRACT_LOCAL_METHODS  = NO\n\n# If this flag is set to YES, the members of anonymous namespaces will be\n# extracted and appear in the documentation as a namespace called\n# 'anonymous_namespace{file}', where file will be replaced with the base name of\n# the file that contains the anonymous namespace. By default anonymous namespace\n# are hidden.\n# The default value is: NO.\n\nEXTRACT_ANON_NSPACES   = NO\n\n# If the HIDE_UNDOC_MEMBERS tag is set to YES, doxygen will hide all\n# undocumented members inside documented classes or files. If set to NO these\n# members will be included in the various overviews, but no documentation\n# section is generated. This option has no effect if EXTRACT_ALL is enabled.\n# The default value is: NO.\n\nHIDE_UNDOC_MEMBERS     = NO\n\n# If the HIDE_UNDOC_CLASSES tag is set to YES, doxygen will hide all\n# undocumented classes that are normally visible in the class hierarchy. If set\n# to NO, these classes will be included in the various overviews. This option\n# has no effect if EXTRACT_ALL is enabled.\n# The default value is: NO.\n\nHIDE_UNDOC_CLASSES     = NO\n\n# If the HIDE_FRIEND_COMPOUNDS tag is set to YES, doxygen will hide all friend\n# (class|struct|union) declarations. If set to NO, these declarations will be\n# included in the documentation.\n# The default value is: NO.\n\nHIDE_FRIEND_COMPOUNDS  = NO\n\n# If the HIDE_IN_BODY_DOCS tag is set to YES, doxygen will hide any\n# documentation blocks found inside the body of a function. If set to NO, these\n# blocks will be appended to the function's detailed documentation block.\n# The default value is: NO.\n\nHIDE_IN_BODY_DOCS      = NO\n\n# The INTERNAL_DOCS tag determines if documentation that is typed after a\n# \\internal command is included. If the tag is set to NO then the documentation\n# will be excluded. Set it to YES to include the internal documentation.\n# The default value is: NO.\n\nINTERNAL_DOCS          = NO\n\n# If the CASE_SENSE_NAMES tag is set to NO then doxygen will only generate file\n# names in lower-case letters. If set to YES, upper-case letters are also\n# allowed. This is useful if you have classes or files whose names only differ\n# in case and if your file system supports case sensitive file names. Windows\n# and Mac users are advised to set this option to NO.\n# The default value is: system dependent.\n\nCASE_SENSE_NAMES       = YES\n\n# If the HIDE_SCOPE_NAMES tag is set to NO then doxygen will show members with\n# their full class and namespace scopes in the documentation. If set to YES, the\n# scope will be hidden.\n# The default value is: NO.\n\nHIDE_SCOPE_NAMES       = NO\n\n# If the HIDE_COMPOUND_REFERENCE tag is set to NO (default) then doxygen will\n# append additional text to a page's title, such as Class Reference. If set to\n# YES the compound reference will be hidden.\n# The default value is: NO.\n\nHIDE_COMPOUND_REFERENCE= NO\n\n# If the SHOW_INCLUDE_FILES tag is set to YES then doxygen will put a list of\n# the files that are included by a file in the documentation of that file.\n# The default value is: YES.\n\nSHOW_INCLUDE_FILES     = YES\n\n# If the SHOW_GROUPED_MEMB_INC tag is set to YES then Doxygen will add for each\n# grouped member an include statement to the documentation, telling the reader\n# which file to include in order to use the member.\n# The default value is: NO.\n\nSHOW_GROUPED_MEMB_INC  = NO\n\n# If the FORCE_LOCAL_INCLUDES tag is set to YES then doxygen will list include\n# files with double quotes in the documentation rather than with sharp brackets.\n# The default value is: NO.\n\nFORCE_LOCAL_INCLUDES   = NO\n\n# If the INLINE_INFO tag is set to YES then a tag [inline] is inserted in the\n# documentation for inline members.\n# The default value is: YES.\n\nINLINE_INFO            = YES\n\n# If the SORT_MEMBER_DOCS tag is set to YES then doxygen will sort the\n# (detailed) documentation of file and class members alphabetically by member\n# name. If set to NO, the members will appear in declaration order.\n# The default value is: YES.\n\nSORT_MEMBER_DOCS       = YES\n\n# If the SORT_BRIEF_DOCS tag is set to YES then doxygen will sort the brief\n# descriptions of file, namespace and class members alphabetically by member\n# name. If set to NO, the members will appear in declaration order. Note that\n# this will also influence the order of the classes in the class list.\n# The default value is: NO.\n\nSORT_BRIEF_DOCS        = NO\n\n# If the SORT_MEMBERS_CTORS_1ST tag is set to YES then doxygen will sort the\n# (brief and detailed) documentation of class members so that constructors and\n# destructors are listed first. If set to NO the constructors will appear in the\n# respective orders defined by SORT_BRIEF_DOCS and SORT_MEMBER_DOCS.\n# Note: If SORT_BRIEF_DOCS is set to NO this option is ignored for sorting brief\n# member documentation.\n# Note: If SORT_MEMBER_DOCS is set to NO this option is ignored for sorting\n# detailed member documentation.\n# The default value is: NO.\n\nSORT_MEMBERS_CTORS_1ST = NO\n\n# If the SORT_GROUP_NAMES tag is set to YES then doxygen will sort the hierarchy\n# of group names into alphabetical order. If set to NO the group names will\n# appear in their defined order.\n# The default value is: NO.\n\nSORT_GROUP_NAMES       = NO\n\n# If the SORT_BY_SCOPE_NAME tag is set to YES, the class list will be sorted by\n# fully-qualified names, including namespaces. If set to NO, the class list will\n# be sorted only by class name, not including the namespace part.\n# Note: This option is not very useful if HIDE_SCOPE_NAMES is set to YES.\n# Note: This option applies only to the class list, not to the alphabetical\n# list.\n# The default value is: NO.\n\nSORT_BY_SCOPE_NAME     = NO\n\n# If the STRICT_PROTO_MATCHING option is enabled and doxygen fails to do proper\n# type resolution of all parameters of a function it will reject a match between\n# the prototype and the implementation of a member function even if there is\n# only one candidate or it is obvious which candidate to choose by doing a\n# simple string match. By disabling STRICT_PROTO_MATCHING doxygen will still\n# accept a match between prototype and implementation in such cases.\n# The default value is: NO.\n\nSTRICT_PROTO_MATCHING  = NO\n\n# The GENERATE_TODOLIST tag can be used to enable (YES) or disable (NO) the todo\n# list. This list is created by putting \\todo commands in the documentation.\n# The default value is: YES.\n\nGENERATE_TODOLIST      = YES\n\n# The GENERATE_TESTLIST tag can be used to enable (YES) or disable (NO) the test\n# list. This list is created by putting \\test commands in the documentation.\n# The default value is: YES.\n\nGENERATE_TESTLIST      = YES\n\n# The GENERATE_BUGLIST tag can be used to enable (YES) or disable (NO) the bug\n# list. This list is created by putting \\bug commands in the documentation.\n# The default value is: YES.\n\nGENERATE_BUGLIST       = YES\n\n# The GENERATE_DEPRECATEDLIST tag can be used to enable (YES) or disable (NO)\n# the deprecated list. This list is created by putting \\deprecated commands in\n# the documentation.\n# The default value is: YES.\n\nGENERATE_DEPRECATEDLIST= YES\n\n# The ENABLED_SECTIONS tag can be used to enable conditional documentation\n# sections, marked by \\if <section_label> ... \\endif and \\cond <section_label>\n# ... \\endcond blocks.\n\nENABLED_SECTIONS       =\n\n# The MAX_INITIALIZER_LINES tag determines the maximum number of lines that the\n# initial value of a variable or macro / define can have for it to appear in the\n# documentation. If the initializer consists of more lines than specified here\n# it will be hidden. Use a value of 0 to hide initializers completely. The\n# appearance of the value of individual variables and macros / defines can be\n# controlled using \\showinitializer or \\hideinitializer command in the\n# documentation regardless of this setting.\n# Minimum value: 0, maximum value: 10000, default value: 30.\n\nMAX_INITIALIZER_LINES  = 30\n\n# Set the SHOW_USED_FILES tag to NO to disable the list of files generated at\n# the bottom of the documentation of classes and structs. If set to YES, the\n# list will mention the files that were used to generate the documentation.\n# The default value is: YES.\n\nSHOW_USED_FILES        = YES\n\n# Set the SHOW_FILES tag to NO to disable the generation of the Files page. This\n# will remove the Files entry from the Quick Index and from the Folder Tree View\n# (if specified).\n# The default value is: YES.\n\nSHOW_FILES             = YES\n\n# Set the SHOW_NAMESPACES tag to NO to disable the generation of the Namespaces\n# page. This will remove the Namespaces entry from the Quick Index and from the\n# Folder Tree View (if specified).\n# The default value is: YES.\n\nSHOW_NAMESPACES        = YES\n\n# The FILE_VERSION_FILTER tag can be used to specify a program or script that\n# doxygen should invoke to get the current version for each file (typically from\n# the version control system). Doxygen will invoke the program by executing (via\n# popen()) the command command input-file, where command is the value of the\n# FILE_VERSION_FILTER tag, and input-file is the name of an input file provided\n# by doxygen. Whatever the program writes to standard output is used as the file\n# version. For an example see the documentation.\n\nFILE_VERSION_FILTER    =\n\n# The LAYOUT_FILE tag can be used to specify a layout file which will be parsed\n# by doxygen. The layout file controls the global structure of the generated\n# output files in an output format independent way. To create the layout file\n# that represents doxygen's defaults, run doxygen with the -l option. You can\n# optionally specify a file name after the option, if omitted DoxygenLayout.xml\n# will be used as the name of the layout file.\n#\n# Note that if you run doxygen from a directory containing a file called\n# DoxygenLayout.xml, doxygen will parse it automatically even if the LAYOUT_FILE\n# tag is left empty.\n\nLAYOUT_FILE            =\n\n# The CITE_BIB_FILES tag can be used to specify one or more bib files containing\n# the reference definitions. This must be a list of .bib files. The .bib\n# extension is automatically appended if omitted. This requires the bibtex tool\n# to be installed. See also http://en.wikipedia.org/wiki/BibTeX for more info.\n# For LaTeX the style of the bibliography can be controlled using\n# LATEX_BIB_STYLE. To use this feature you need bibtex and perl available in the\n# search path. See also \\cite for info how to create references.\n\nCITE_BIB_FILES         =\n\n#---------------------------------------------------------------------------\n# Configuration options related to warning and progress messages\n#---------------------------------------------------------------------------\n\n# The QUIET tag can be used to turn on/off the messages that are generated to\n# standard output by doxygen. If QUIET is set to YES this implies that the\n# messages are off.\n# The default value is: NO.\n\nQUIET                  = NO\n\n# The WARNINGS tag can be used to turn on/off the warning messages that are\n# generated to standard error (stderr) by doxygen. If WARNINGS is set to YES\n# this implies that the warnings are on.\n#\n# Tip: Turn warnings on while writing the documentation.\n# The default value is: YES.\n\nWARNINGS               = YES\n\n# If the WARN_IF_UNDOCUMENTED tag is set to YES then doxygen will generate\n# warnings for undocumented members. If EXTRACT_ALL is set to YES then this flag\n# will automatically be disabled.\n# The default value is: YES.\n\nWARN_IF_UNDOCUMENTED   = YES\n\n# If the WARN_IF_DOC_ERROR tag is set to YES, doxygen will generate warnings for\n# potential errors in the documentation, such as not documenting some parameters\n# in a documented function, or documenting parameters that don't exist or using\n# markup commands wrongly.\n# The default value is: YES.\n\nWARN_IF_DOC_ERROR      = YES\n\n# This WARN_NO_PARAMDOC option can be enabled to get warnings for functions that\n# are documented, but have no documentation for their parameters or return\n# value. If set to NO, doxygen will only warn about wrong or incomplete\n# parameter documentation, but not about the absence of documentation.\n# The default value is: NO.\n\nWARN_NO_PARAMDOC       = NO\n\n# The WARN_FORMAT tag determines the format of the warning messages that doxygen\n# can produce. The string should contain the $file, $line, and $text tags, which\n# will be replaced by the file and line number from which the warning originated\n# and the warning text. Optionally the format may contain $version, which will\n# be replaced by the version of the file (if it could be obtained via\n# FILE_VERSION_FILTER)\n# The default value is: $file:$line: $text.\n\nWARN_FORMAT            = \"$file:$line: $text\"\n\n# The WARN_LOGFILE tag can be used to specify a file to which warning and error\n# messages should be written. If left blank the output is written to standard\n# error (stderr).\n\nWARN_LOGFILE           =\n\n#---------------------------------------------------------------------------\n# Configuration options related to the input files\n#---------------------------------------------------------------------------\n\n# The INPUT tag is used to specify the files and/or directories that contain\n# documented source files. You may enter file names like myfile.cpp or\n# directories like /usr/src/myproject. Separate the files or directories with\n# spaces.\n# Note: If this tag is empty the current directory is searched.\n\nINPUT                  = @top_srcdir@ @top_srcdir@/cudd @top_srcdir@/mtr @top_srcdir@/epd @top_srcdir@/st @top_srcdir@/util @top_srcdir@/cplusplus @top_srcdir@/nanotrav\n\n# This tag can be used to specify the character encoding of the source files\n# that doxygen parses. Internally doxygen uses the UTF-8 encoding. Doxygen uses\n# libiconv (or the iconv built into libc) for the transcoding. See the libiconv\n# documentation (see: http://www.gnu.org/software/libiconv) for the list of\n# possible encodings.\n# The default value is: UTF-8.\n\nINPUT_ENCODING         = UTF-8\n\n# If the value of the INPUT tag contains directories, you can use the\n# FILE_PATTERNS tag to specify one or more wildcard patterns (like *.cpp and\n# *.h) to filter out the source-files in the directories. If left blank the\n# following patterns are tested:*.c, *.cc, *.cxx, *.cpp, *.c++, *.java, *.ii,\n# *.ixx, *.ipp, *.i++, *.inl, *.idl, *.ddl, *.odl, *.h, *.hh, *.hxx, *.hpp,\n# *.h++, *.cs, *.d, *.php, *.php4, *.php5, *.phtml, *.inc, *.m, *.markdown,\n# *.md, *.mm, *.dox, *.py, *.f90, *.f, *.for, *.tcl, *.vhd, *.vhdl, *.ucf,\n# *.qsf, *.as and *.js.\n\nFILE_PATTERNS          =\n\n# The RECURSIVE tag can be used to specify whether or not subdirectories should\n# be searched for input files as well.\n# The default value is: NO.\n\nRECURSIVE              = NO\n\n# The EXCLUDE tag can be used to specify files and/or directories that should be\n# excluded from the INPUT source files. This way you can easily exclude a\n# subdirectory from a directory tree whose root is specified with the INPUT tag.\n#\n# Note that relative paths are relative to the directory from which doxygen is\n# run.\n\nEXCLUDE                = config.h\n\n# The EXCLUDE_SYMLINKS tag can be used to select whether or not files or\n# directories that are symbolic links (a Unix file system feature) are excluded\n# from the input.\n# The default value is: NO.\n\nEXCLUDE_SYMLINKS       = NO\n\n# If the value of the INPUT tag contains directories, you can use the\n# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude\n# certain files from those directories.\n#\n# Note that the wildcards are matched against the file with absolute path, so to\n# exclude all test directories for example use the pattern */test/*\n\nEXCLUDE_PATTERNS       =\n\n# The EXCLUDE_SYMBOLS tag can be used to specify one or more symbol names\n# (namespaces, classes, functions, etc.) that should be excluded from the\n# output. The symbol name can be a fully qualified name, a word, or if the\n# wildcard * is used, a substring. Examples: ANamespace, AClass,\n# AClass::ANamespace, ANamespace::*Test\n#\n# Note that the wildcards are matched against the file with absolute path, so to\n# exclude all test directories use the pattern */test/*\n\nEXCLUDE_SYMBOLS        =\n\n# The EXAMPLE_PATH tag can be used to specify one or more files or directories\n# that contain example code fragments that are included (see the \\include\n# command).\n\nEXAMPLE_PATH           =\n\n# If the value of the EXAMPLE_PATH tag contains directories, you can use the\n# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp and\n# *.h) to filter out the source-files in the directories. If left blank all\n# files are included.\n\nEXAMPLE_PATTERNS       =\n\n# If the EXAMPLE_RECURSIVE tag is set to YES then subdirectories will be\n# searched for input files to be used with the \\include or \\dontinclude commands\n# irrespective of the value of the RECURSIVE tag.\n# The default value is: NO.\n\nEXAMPLE_RECURSIVE      = NO\n\n# The IMAGE_PATH tag can be used to specify one or more files or directories\n# that contain images that are to be included in the documentation (see the\n# \\image command).\n\nIMAGE_PATH             =\n\n# The INPUT_FILTER tag can be used to specify a program that doxygen should\n# invoke to filter for each input file. Doxygen will invoke the filter program\n# by executing (via popen()) the command:\n#\n# <filter> <input-file>\n#\n# where <filter> is the value of the INPUT_FILTER tag, and <input-file> is the\n# name of an input file. Doxygen will then use the output that the filter\n# program writes to standard output. If FILTER_PATTERNS is specified, this tag\n# will be ignored.\n#\n# Note that the filter must not add or remove lines; it is applied before the\n# code is scanned, but not when the output code is generated. If lines are added\n# or removed, the anchors will not be placed correctly.\n\nINPUT_FILTER           =\n\n# The FILTER_PATTERNS tag can be used to specify filters on a per file pattern\n# basis. Doxygen will compare the file name with each pattern and apply the\n# filter if there is a match. The filters are a list of the form: pattern=filter\n# (like *.cpp=my_cpp_filter). See INPUT_FILTER for further information on how\n# filters are used. If the FILTER_PATTERNS tag is empty or if none of the\n# patterns match the file name, INPUT_FILTER is applied.\n\nFILTER_PATTERNS        =\n\n# If the FILTER_SOURCE_FILES tag is set to YES, the input filter (if set using\n# INPUT_FILTER) will also be used to filter the input files that are used for\n# producing the source files to browse (i.e. when SOURCE_BROWSER is set to YES).\n# The default value is: NO.\n\nFILTER_SOURCE_FILES    = NO\n\n# The FILTER_SOURCE_PATTERNS tag can be used to specify source filters per file\n# pattern. A pattern will override the setting for FILTER_PATTERN (if any) and\n# it is also possible to disable source filtering for a specific pattern using\n# *.ext= (so without naming a filter).\n# This tag requires that the tag FILTER_SOURCE_FILES is set to YES.\n\nFILTER_SOURCE_PATTERNS =\n\n# If the USE_MDFILE_AS_MAINPAGE tag refers to the name of a markdown file that\n# is part of the input, its contents will be placed on the main page\n# (index.html). This can be useful if you have a project on for instance GitHub\n# and want to reuse the introduction page also for the doxygen output.\n\nUSE_MDFILE_AS_MAINPAGE =\n\n#---------------------------------------------------------------------------\n# Configuration options related to source browsing\n#---------------------------------------------------------------------------\n\n# If the SOURCE_BROWSER tag is set to YES then a list of source files will be\n# generated. Documented entities will be cross-referenced with these sources.\n#\n# Note: To get rid of all source code in the generated output, make sure that\n# also VERBATIM_HEADERS is set to NO.\n# The default value is: NO.\n\nSOURCE_BROWSER         = NO\n\n# Setting the INLINE_SOURCES tag to YES will include the body of functions,\n# classes and enums directly into the documentation.\n# The default value is: NO.\n\nINLINE_SOURCES         = NO\n\n# Setting the STRIP_CODE_COMMENTS tag to YES will instruct doxygen to hide any\n# special comment blocks from generated source code fragments. Normal C, C++ and\n# Fortran comments will always remain visible.\n# The default value is: YES.\n\nSTRIP_CODE_COMMENTS    = YES\n\n# If the REFERENCED_BY_RELATION tag is set to YES then for each documented\n# function all documented functions referencing it will be listed.\n# The default value is: NO.\n\nREFERENCED_BY_RELATION = NO\n\n# If the REFERENCES_RELATION tag is set to YES then for each documented function\n# all documented entities called/used by that function will be listed.\n# The default value is: NO.\n\nREFERENCES_RELATION    = NO\n\n# If the REFERENCES_LINK_SOURCE tag is set to YES and SOURCE_BROWSER tag is set\n# to YES then the hyperlinks from functions in REFERENCES_RELATION and\n# REFERENCED_BY_RELATION lists will link to the source code. Otherwise they will\n# link to the documentation.\n# The default value is: YES.\n\nREFERENCES_LINK_SOURCE = YES\n\n# If SOURCE_TOOLTIPS is enabled (the default) then hovering a hyperlink in the\n# source code will show a tooltip with additional information such as prototype,\n# brief description and links to the definition and documentation. Since this\n# will make the HTML file larger and loading of large files a bit slower, you\n# can opt to disable this feature.\n# The default value is: YES.\n# This tag requires that the tag SOURCE_BROWSER is set to YES.\n\nSOURCE_TOOLTIPS        = YES\n\n# If the USE_HTAGS tag is set to YES then the references to source code will\n# point to the HTML generated by the htags(1) tool instead of doxygen built-in\n# source browser. The htags tool is part of GNU's global source tagging system\n# (see http://www.gnu.org/software/global/global.html). You will need version\n# 4.8.6 or higher.\n#\n# To use it do the following:\n# - Install the latest version of global\n# - Enable SOURCE_BROWSER and USE_HTAGS in the config file\n# - Make sure the INPUT points to the root of the source tree\n# - Run doxygen as normal\n#\n# Doxygen will invoke htags (and that will in turn invoke gtags), so these\n# tools must be available from the command line (i.e. in the search path).\n#\n# The result: instead of the source browser generated by doxygen, the links to\n# source code will now point to the output of htags.\n# The default value is: NO.\n# This tag requires that the tag SOURCE_BROWSER is set to YES.\n\nUSE_HTAGS              = NO\n\n# If the VERBATIM_HEADERS tag is set the YES then doxygen will generate a\n# verbatim copy of the header file for each class for which an include is\n# specified. Set to NO to disable this.\n# See also: Section \\class.\n# The default value is: YES.\n\nVERBATIM_HEADERS       = YES\n\n# If the CLANG_ASSISTED_PARSING tag is set to YES then doxygen will use the\n# clang parser (see: http://clang.llvm.org/) for more accurate parsing at the\n# cost of reduced performance. This can be particularly helpful with template\n# rich C++ code for which doxygen's built-in parser lacks the necessary type\n# information.\n# Note: The availability of this option depends on whether or not doxygen was\n# compiled with the --with-libclang option.\n# The default value is: NO.\n\nCLANG_ASSISTED_PARSING = NO\n\n# If clang assisted parsing is enabled you can provide the compiler with command\n# line options that you would normally use when invoking the compiler. Note that\n# the include paths will already be set by doxygen for the files and directories\n# specified with INPUT and INCLUDE_PATH.\n# This tag requires that the tag CLANG_ASSISTED_PARSING is set to YES.\n\nCLANG_OPTIONS          =\n\n#---------------------------------------------------------------------------\n# Configuration options related to the alphabetical class index\n#---------------------------------------------------------------------------\n\n# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index of all\n# compounds will be generated. Enable this if the project contains a lot of\n# classes, structs, unions or interfaces.\n# The default value is: YES.\n\nALPHABETICAL_INDEX     = YES\n\n# The COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns in\n# which the alphabetical index list will be split.\n# Minimum value: 1, maximum value: 20, default value: 5.\n# This tag requires that the tag ALPHABETICAL_INDEX is set to YES.\n\nCOLS_IN_ALPHA_INDEX    = 5\n\n# In case all classes in a project start with a common prefix, all classes will\n# be put under the same header in the alphabetical index. The IGNORE_PREFIX tag\n# can be used to specify a prefix (or a list of prefixes) that should be ignored\n# while generating the index headers.\n# This tag requires that the tag ALPHABETICAL_INDEX is set to YES.\n\nIGNORE_PREFIX          =\n\n#---------------------------------------------------------------------------\n# Configuration options related to the HTML output\n#---------------------------------------------------------------------------\n\n# If the GENERATE_HTML tag is set to YES, doxygen will generate HTML output\n# The default value is: YES.\n\nGENERATE_HTML          = YES\n\n# The HTML_OUTPUT tag is used to specify where the HTML docs will be put. If a\n# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of\n# it.\n# The default directory is: html.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_OUTPUT            = html\n\n# The HTML_FILE_EXTENSION tag can be used to specify the file extension for each\n# generated HTML page (for example: .htm, .php, .asp).\n# The default value is: .html.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_FILE_EXTENSION    = .html\n\n# The HTML_HEADER tag can be used to specify a user-defined HTML header file for\n# each generated HTML page. If the tag is left blank doxygen will generate a\n# standard header.\n#\n# To get valid HTML the header file that includes any scripts and style sheets\n# that doxygen needs, which is dependent on the configuration options used (e.g.\n# the setting GENERATE_TREEVIEW). It is highly recommended to start with a\n# default header using\n# doxygen -w html new_header.html new_footer.html new_stylesheet.css\n# YourConfigFile\n# and then modify the file new_header.html. See also section \"Doxygen usage\"\n# for information on how to generate the default header that doxygen normally\n# uses.\n# Note: The header is subject to change so you typically have to regenerate the\n# default header when upgrading to a newer version of doxygen. For a description\n# of the possible markers and block names see the documentation.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_HEADER            =\n\n# The HTML_FOOTER tag can be used to specify a user-defined HTML footer for each\n# generated HTML page. If the tag is left blank doxygen will generate a standard\n# footer. See HTML_HEADER for more information on how to generate a default\n# footer and what special commands can be used inside the footer. See also\n# section \"Doxygen usage\" for information on how to generate the default footer\n# that doxygen normally uses.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_FOOTER            =\n\n# The HTML_STYLESHEET tag can be used to specify a user-defined cascading style\n# sheet that is used by each HTML page. It can be used to fine-tune the look of\n# the HTML output. If left blank doxygen will generate a default style sheet.\n# See also section \"Doxygen usage\" for information on how to generate the style\n# sheet that doxygen normally uses.\n# Note: It is recommended to use HTML_EXTRA_STYLESHEET instead of this tag, as\n# it is more robust and this tag (HTML_STYLESHEET) will in the future become\n# obsolete.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_STYLESHEET        =\n\n# The HTML_EXTRA_STYLESHEET tag can be used to specify additional user-defined\n# cascading style sheets that are included after the standard style sheets\n# created by doxygen. Using this option one can overrule certain style aspects.\n# This is preferred over using HTML_STYLESHEET since it does not replace the\n# standard style sheet and is therefore more robust against future updates.\n# Doxygen will copy the style sheet files to the output directory.\n# Note: The order of the extra style sheet files is of importance (e.g. the last\n# style sheet in the list overrules the setting of the previous ones in the\n# list). For an example see the documentation.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_EXTRA_STYLESHEET  =\n\n# The HTML_EXTRA_FILES tag can be used to specify one or more extra images or\n# other source files which should be copied to the HTML output directory. Note\n# that these files will be copied to the base HTML output directory. Use the\n# $relpath^ marker in the HTML_HEADER and/or HTML_FOOTER files to load these\n# files. In the HTML_STYLESHEET file, use the file name only. Also note that the\n# files will be copied as-is; there are no commands or markers available.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_EXTRA_FILES       =\n\n# The HTML_COLORSTYLE_HUE tag controls the color of the HTML output. Doxygen\n# will adjust the colors in the style sheet and background images according to\n# this color. Hue is specified as an angle on a colorwheel, see\n# http://en.wikipedia.org/wiki/Hue for more information. For instance the value\n# 0 represents red, 60 is yellow, 120 is green, 180 is cyan, 240 is blue, 300\n# purple, and 360 is red again.\n# Minimum value: 0, maximum value: 359, default value: 220.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_COLORSTYLE_HUE    = 220\n\n# The HTML_COLORSTYLE_SAT tag controls the purity (or saturation) of the colors\n# in the HTML output. For a value of 0 the output will use grayscales only. A\n# value of 255 will produce the most vivid colors.\n# Minimum value: 0, maximum value: 255, default value: 100.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_COLORSTYLE_SAT    = 100\n\n# The HTML_COLORSTYLE_GAMMA tag controls the gamma correction applied to the\n# luminance component of the colors in the HTML output. Values below 100\n# gradually make the output lighter, whereas values above 100 make the output\n# darker. The value divided by 100 is the actual gamma applied, so 80 represents\n# a gamma of 0.8, The value 220 represents a gamma of 2.2, and 100 does not\n# change the gamma.\n# Minimum value: 40, maximum value: 240, default value: 80.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_COLORSTYLE_GAMMA  = 80\n\n# If the HTML_TIMESTAMP tag is set to YES then the footer of each generated HTML\n# page will contain the date and time when the page was generated. Setting this\n# to NO can help when comparing the output of multiple runs.\n# The default value is: YES.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_TIMESTAMP         = YES\n\n# If the HTML_DYNAMIC_SECTIONS tag is set to YES then the generated HTML\n# documentation will contain sections that can be hidden and shown after the\n# page has loaded.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_DYNAMIC_SECTIONS  = NO\n\n# With HTML_INDEX_NUM_ENTRIES one can control the preferred number of entries\n# shown in the various tree structured indices initially; the user can expand\n# and collapse entries dynamically later on. Doxygen will expand the tree to\n# such a level that at most the specified number of entries are visible (unless\n# a fully collapsed tree already exceeds this amount). So setting the number of\n# entries 1 will produce a full collapsed tree by default. 0 is a special value\n# representing an infinite number of entries and will result in a full expanded\n# tree by default.\n# Minimum value: 0, maximum value: 9999, default value: 100.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nHTML_INDEX_NUM_ENTRIES = 100\n\n# If the GENERATE_DOCSET tag is set to YES, additional index files will be\n# generated that can be used as input for Apple's Xcode 3 integrated development\n# environment (see: http://developer.apple.com/tools/xcode/), introduced with\n# OSX 10.5 (Leopard). To create a documentation set, doxygen will generate a\n# Makefile in the HTML output directory. Running make will produce the docset in\n# that directory and running make install will install the docset in\n# ~/Library/Developer/Shared/Documentation/DocSets so that Xcode will find it at\n# startup. See http://developer.apple.com/tools/creatingdocsetswithdoxygen.html\n# for more information.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nGENERATE_DOCSET        = NO\n\n# This tag determines the name of the docset feed. A documentation feed provides\n# an umbrella under which multiple documentation sets from a single provider\n# (such as a company or product suite) can be grouped.\n# The default value is: Doxygen generated docs.\n# This tag requires that the tag GENERATE_DOCSET is set to YES.\n\nDOCSET_FEEDNAME        = \"Doxygen generated docs\"\n\n# This tag specifies a string that should uniquely identify the documentation\n# set bundle. This should be a reverse domain-name style string, e.g.\n# com.mycompany.MyDocSet. Doxygen will append .docset to the name.\n# The default value is: org.doxygen.Project.\n# This tag requires that the tag GENERATE_DOCSET is set to YES.\n\nDOCSET_BUNDLE_ID       = org.doxygen.Project\n\n# The DOCSET_PUBLISHER_ID tag specifies a string that should uniquely identify\n# the documentation publisher. This should be a reverse domain-name style\n# string, e.g. com.mycompany.MyDocSet.documentation.\n# The default value is: org.doxygen.Publisher.\n# This tag requires that the tag GENERATE_DOCSET is set to YES.\n\nDOCSET_PUBLISHER_ID    = org.doxygen.Publisher\n\n# The DOCSET_PUBLISHER_NAME tag identifies the documentation publisher.\n# The default value is: Publisher.\n# This tag requires that the tag GENERATE_DOCSET is set to YES.\n\nDOCSET_PUBLISHER_NAME  = Publisher\n\n# If the GENERATE_HTMLHELP tag is set to YES then doxygen generates three\n# additional HTML index files: index.hhp, index.hhc, and index.hhk. The\n# index.hhp is a project file that can be read by Microsoft's HTML Help Workshop\n# (see: http://www.microsoft.com/en-us/download/details.aspx?id=21138) on\n# Windows.\n#\n# The HTML Help Workshop contains a compiler that can convert all HTML output\n# generated by doxygen into a single compiled HTML file (.chm). Compiled HTML\n# files are now used as the Windows 98 help format, and will replace the old\n# Windows help format (.hlp) on all Windows platforms in the future. Compressed\n# HTML files also contain an index, a table of contents, and you can search for\n# words in the documentation. The HTML workshop also contains a viewer for\n# compressed HTML files.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nGENERATE_HTMLHELP      = NO\n\n# The CHM_FILE tag can be used to specify the file name of the resulting .chm\n# file. You can add a path in front of the file if the result should not be\n# written to the html output directory.\n# This tag requires that the tag GENERATE_HTMLHELP is set to YES.\n\nCHM_FILE               =\n\n# The HHC_LOCATION tag can be used to specify the location (absolute path\n# including file name) of the HTML help compiler (hhc.exe). If non-empty,\n# doxygen will try to run the HTML help compiler on the generated index.hhp.\n# The file has to be specified with full path.\n# This tag requires that the tag GENERATE_HTMLHELP is set to YES.\n\nHHC_LOCATION           =\n\n# The GENERATE_CHI flag controls if a separate .chi index file is generated\n# (YES) or that it should be included in the master .chm file (NO).\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTMLHELP is set to YES.\n\nGENERATE_CHI           = NO\n\n# The CHM_INDEX_ENCODING is used to encode HtmlHelp index (hhk), content (hhc)\n# and project file content.\n# This tag requires that the tag GENERATE_HTMLHELP is set to YES.\n\nCHM_INDEX_ENCODING     =\n\n# The BINARY_TOC flag controls whether a binary table of contents is generated\n# (YES) or a normal table of contents (NO) in the .chm file. Furthermore it\n# enables the Previous and Next buttons.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTMLHELP is set to YES.\n\nBINARY_TOC             = NO\n\n# The TOC_EXPAND flag can be set to YES to add extra items for group members to\n# the table of contents of the HTML help documentation and to the tree view.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTMLHELP is set to YES.\n\nTOC_EXPAND             = NO\n\n# If the GENERATE_QHP tag is set to YES and both QHP_NAMESPACE and\n# QHP_VIRTUAL_FOLDER are set, an additional index file will be generated that\n# can be used as input for Qt's qhelpgenerator to generate a Qt Compressed Help\n# (.qch) of the generated HTML documentation.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nGENERATE_QHP           = NO\n\n# If the QHG_LOCATION tag is specified, the QCH_FILE tag can be used to specify\n# the file name of the resulting .qch file. The path specified is relative to\n# the HTML output folder.\n# This tag requires that the tag GENERATE_QHP is set to YES.\n\nQCH_FILE               =\n\n# The QHP_NAMESPACE tag specifies the namespace to use when generating Qt Help\n# Project output. For more information please see Qt Help Project / Namespace\n# (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#namespace).\n# The default value is: org.doxygen.Project.\n# This tag requires that the tag GENERATE_QHP is set to YES.\n\nQHP_NAMESPACE          = org.doxygen.Project\n\n# The QHP_VIRTUAL_FOLDER tag specifies the namespace to use when generating Qt\n# Help Project output. For more information please see Qt Help Project / Virtual\n# Folders (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#virtual-\n# folders).\n# The default value is: doc.\n# This tag requires that the tag GENERATE_QHP is set to YES.\n\nQHP_VIRTUAL_FOLDER     = doc\n\n# If the QHP_CUST_FILTER_NAME tag is set, it specifies the name of a custom\n# filter to add. For more information please see Qt Help Project / Custom\n# Filters (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#custom-\n# filters).\n# This tag requires that the tag GENERATE_QHP is set to YES.\n\nQHP_CUST_FILTER_NAME   =\n\n# The QHP_CUST_FILTER_ATTRS tag specifies the list of the attributes of the\n# custom filter to add. For more information please see Qt Help Project / Custom\n# Filters (see: http://qt-project.org/doc/qt-4.8/qthelpproject.html#custom-\n# filters).\n# This tag requires that the tag GENERATE_QHP is set to YES.\n\nQHP_CUST_FILTER_ATTRS  =\n\n# The QHP_SECT_FILTER_ATTRS tag specifies the list of the attributes this\n# project's filter section matches. Qt Help Project / Filter Attributes (see:\n# http://qt-project.org/doc/qt-4.8/qthelpproject.html#filter-attributes).\n# This tag requires that the tag GENERATE_QHP is set to YES.\n\nQHP_SECT_FILTER_ATTRS  =\n\n# The QHG_LOCATION tag can be used to specify the location of Qt's\n# qhelpgenerator. If non-empty doxygen will try to run qhelpgenerator on the\n# generated .qhp file.\n# This tag requires that the tag GENERATE_QHP is set to YES.\n\nQHG_LOCATION           =\n\n# If the GENERATE_ECLIPSEHELP tag is set to YES, additional index files will be\n# generated, together with the HTML files, they form an Eclipse help plugin. To\n# install this plugin and make it available under the help contents menu in\n# Eclipse, the contents of the directory containing the HTML and XML files needs\n# to be copied into the plugins directory of eclipse. The name of the directory\n# within the plugins directory should be the same as the ECLIPSE_DOC_ID value.\n# After copying Eclipse needs to be restarted before the help appears.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nGENERATE_ECLIPSEHELP   = NO\n\n# A unique identifier for the Eclipse help plugin. When installing the plugin\n# the directory name containing the HTML and XML files should also have this\n# name. Each documentation set should have its own identifier.\n# The default value is: org.doxygen.Project.\n# This tag requires that the tag GENERATE_ECLIPSEHELP is set to YES.\n\nECLIPSE_DOC_ID         = org.doxygen.Project\n\n# If you want full control over the layout of the generated HTML pages it might\n# be necessary to disable the index and replace it with your own. The\n# DISABLE_INDEX tag can be used to turn on/off the condensed index (tabs) at top\n# of each HTML page. A value of NO enables the index and the value YES disables\n# it. Since the tabs in the index contain the same information as the navigation\n# tree, you can set this option to YES if you also set GENERATE_TREEVIEW to YES.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nDISABLE_INDEX          = NO\n\n# The GENERATE_TREEVIEW tag is used to specify whether a tree-like index\n# structure should be generated to display hierarchical information. If the tag\n# value is set to YES, a side panel will be generated containing a tree-like\n# index structure (just like the one that is generated for HTML Help). For this\n# to work a browser that supports JavaScript, DHTML, CSS and frames is required\n# (i.e. any modern browser). Windows users are probably better off using the\n# HTML help feature. Via custom style sheets (see HTML_EXTRA_STYLESHEET) one can\n# further fine-tune the look of the index. As an example, the default style\n# sheet generated by doxygen has an example that shows how to put an image at\n# the root of the tree instead of the PROJECT_NAME. Since the tree basically has\n# the same information as the tab index, you could consider setting\n# DISABLE_INDEX to YES when enabling this option.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nGENERATE_TREEVIEW      = NO\n\n# The ENUM_VALUES_PER_LINE tag can be used to set the number of enum values that\n# doxygen will group on one line in the generated HTML documentation.\n#\n# Note that a value of 0 will completely suppress the enum values from appearing\n# in the overview section.\n# Minimum value: 0, maximum value: 20, default value: 4.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nENUM_VALUES_PER_LINE   = 4\n\n# If the treeview is enabled (see GENERATE_TREEVIEW) then this tag can be used\n# to set the initial width (in pixels) of the frame in which the tree is shown.\n# Minimum value: 0, maximum value: 1500, default value: 250.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nTREEVIEW_WIDTH         = 250\n\n# If the EXT_LINKS_IN_WINDOW option is set to YES, doxygen will open links to\n# external symbols imported via tag files in a separate window.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nEXT_LINKS_IN_WINDOW    = NO\n\n# Use this tag to change the font size of LaTeX formulas included as images in\n# the HTML documentation. When you change the font size after a successful\n# doxygen run you need to manually remove any form_*.png images from the HTML\n# output directory to force them to be regenerated.\n# Minimum value: 8, maximum value: 50, default value: 10.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nFORMULA_FONTSIZE       = 10\n\n# Use the FORMULA_TRANPARENT tag to determine whether or not the images\n# generated for formulas are transparent PNGs. Transparent PNGs are not\n# supported properly for IE 6.0, but are supported on all modern browsers.\n#\n# Note that when changing this option you need to delete any form_*.png files in\n# the HTML output directory before the changes have effect.\n# The default value is: YES.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nFORMULA_TRANSPARENT    = YES\n\n# Enable the USE_MATHJAX option to render LaTeX formulas using MathJax (see\n# http://www.mathjax.org) which uses client side Javascript for the rendering\n# instead of using pre-rendered bitmaps. Use this if you do not have LaTeX\n# installed or if you want to formulas look prettier in the HTML output. When\n# enabled you may also need to install MathJax separately and configure the path\n# to it using the MATHJAX_RELPATH option.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nUSE_MATHJAX            = NO\n\n# When MathJax is enabled you can set the default output format to be used for\n# the MathJax output. See the MathJax site (see:\n# http://docs.mathjax.org/en/latest/output.html) for more details.\n# Possible values are: HTML-CSS (which is slower, but has the best\n# compatibility), NativeMML (i.e. MathML) and SVG.\n# The default value is: HTML-CSS.\n# This tag requires that the tag USE_MATHJAX is set to YES.\n\nMATHJAX_FORMAT         = HTML-CSS\n\n# When MathJax is enabled you need to specify the location relative to the HTML\n# output directory using the MATHJAX_RELPATH option. The destination directory\n# should contain the MathJax.js script. For instance, if the mathjax directory\n# is located at the same level as the HTML output directory, then\n# MATHJAX_RELPATH should be ../mathjax. The default value points to the MathJax\n# Content Delivery Network so you can quickly see the result without installing\n# MathJax. However, it is strongly recommended to install a local copy of\n# MathJax from http://www.mathjax.org before deployment.\n# The default value is: http://cdn.mathjax.org/mathjax/latest.\n# This tag requires that the tag USE_MATHJAX is set to YES.\n\nMATHJAX_RELPATH        = http://cdn.mathjax.org/mathjax/latest\n\n# The MATHJAX_EXTENSIONS tag can be used to specify one or more MathJax\n# extension names that should be enabled during MathJax rendering. For example\n# MATHJAX_EXTENSIONS = TeX/AMSmath TeX/AMSsymbols\n# This tag requires that the tag USE_MATHJAX is set to YES.\n\nMATHJAX_EXTENSIONS     =\n\n# The MATHJAX_CODEFILE tag can be used to specify a file with javascript pieces\n# of code that will be used on startup of the MathJax code. See the MathJax site\n# (see: http://docs.mathjax.org/en/latest/output.html) for more details. For an\n# example see the documentation.\n# This tag requires that the tag USE_MATHJAX is set to YES.\n\nMATHJAX_CODEFILE       =\n\n# When the SEARCHENGINE tag is enabled doxygen will generate a search box for\n# the HTML output. The underlying search engine uses javascript and DHTML and\n# should work on any modern browser. Note that when using HTML help\n# (GENERATE_HTMLHELP), Qt help (GENERATE_QHP), or docsets (GENERATE_DOCSET)\n# there is already a search function so this one should typically be disabled.\n# For large projects the javascript based search engine can be slow, then\n# enabling SERVER_BASED_SEARCH may provide a better solution. It is possible to\n# search using the keyboard; to jump to the search box use <access key> + S\n# (what the <access key> is depends on the OS and browser, but it is typically\n# <CTRL>, <ALT>/<option>, or both). Inside the search box use the <cursor down\n# key> to jump into the search results window, the results can be navigated\n# using the <cursor keys>. Press <Enter> to select an item or <escape> to cancel\n# the search. The filter options can be selected when the cursor is inside the\n# search box by pressing <Shift>+<cursor down>. Also here use the <cursor keys>\n# to select a filter and <Enter> or <escape> to activate or cancel the filter\n# option.\n# The default value is: YES.\n# This tag requires that the tag GENERATE_HTML is set to YES.\n\nSEARCHENGINE           = YES\n\n# When the SERVER_BASED_SEARCH tag is enabled the search engine will be\n# implemented using a web server instead of a web client using Javascript. There\n# are two flavors of web server based searching depending on the EXTERNAL_SEARCH\n# setting. When disabled, doxygen will generate a PHP script for searching and\n# an index file used by the script. When EXTERNAL_SEARCH is enabled the indexing\n# and searching needs to be provided by external tools. See the section\n# \"External Indexing and Searching\" for details.\n# The default value is: NO.\n# This tag requires that the tag SEARCHENGINE is set to YES.\n\nSERVER_BASED_SEARCH    = NO\n\n# When EXTERNAL_SEARCH tag is enabled doxygen will no longer generate the PHP\n# script for searching. Instead the search results are written to an XML file\n# which needs to be processed by an external indexer. Doxygen will invoke an\n# external search engine pointed to by the SEARCHENGINE_URL option to obtain the\n# search results.\n#\n# Doxygen ships with an example indexer (doxyindexer) and search engine\n# (doxysearch.cgi) which are based on the open source search engine library\n# Xapian (see: http://xapian.org/).\n#\n# See the section \"External Indexing and Searching\" for details.\n# The default value is: NO.\n# This tag requires that the tag SEARCHENGINE is set to YES.\n\nEXTERNAL_SEARCH        = NO\n\n# The SEARCHENGINE_URL should point to a search engine hosted by a web server\n# which will return the search results when EXTERNAL_SEARCH is enabled.\n#\n# Doxygen ships with an example indexer (doxyindexer) and search engine\n# (doxysearch.cgi) which are based on the open source search engine library\n# Xapian (see: http://xapian.org/). See the section \"External Indexing and\n# Searching\" for details.\n# This tag requires that the tag SEARCHENGINE is set to YES.\n\nSEARCHENGINE_URL       =\n\n# When SERVER_BASED_SEARCH and EXTERNAL_SEARCH are both enabled the unindexed\n# search data is written to a file for indexing by an external tool. With the\n# SEARCHDATA_FILE tag the name of this file can be specified.\n# The default file is: searchdata.xml.\n# This tag requires that the tag SEARCHENGINE is set to YES.\n\nSEARCHDATA_FILE        = searchdata.xml\n\n# When SERVER_BASED_SEARCH and EXTERNAL_SEARCH are both enabled the\n# EXTERNAL_SEARCH_ID tag can be used as an identifier for the project. This is\n# useful in combination with EXTRA_SEARCH_MAPPINGS to search through multiple\n# projects and redirect the results back to the right project.\n# This tag requires that the tag SEARCHENGINE is set to YES.\n\nEXTERNAL_SEARCH_ID     =\n\n# The EXTRA_SEARCH_MAPPINGS tag can be used to enable searching through doxygen\n# projects other than the one defined by this configuration file, but that are\n# all added to the same external search index. Each project needs to have a\n# unique id set via EXTERNAL_SEARCH_ID. The search mapping then maps the id of\n# to a relative location where the documentation can be found. The format is:\n# EXTRA_SEARCH_MAPPINGS = tagname1=loc1 tagname2=loc2 ...\n# This tag requires that the tag SEARCHENGINE is set to YES.\n\nEXTRA_SEARCH_MAPPINGS  =\n\n#---------------------------------------------------------------------------\n# Configuration options related to the LaTeX output\n#---------------------------------------------------------------------------\n\n# If the GENERATE_LATEX tag is set to YES, doxygen will generate LaTeX output.\n# The default value is: YES.\n\nGENERATE_LATEX         = NO\n\n# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put. If a\n# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of\n# it.\n# The default directory is: latex.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_OUTPUT           = latex\n\n# The LATEX_CMD_NAME tag can be used to specify the LaTeX command name to be\n# invoked.\n#\n# Note that when enabling USE_PDFLATEX this option is only used for generating\n# bitmaps for formulas in the HTML output, but not in the Makefile that is\n# written to the output directory.\n# The default file is: latex.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_CMD_NAME         = latex\n\n# The MAKEINDEX_CMD_NAME tag can be used to specify the command name to generate\n# index for LaTeX.\n# The default file is: makeindex.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nMAKEINDEX_CMD_NAME     = makeindex\n\n# If the COMPACT_LATEX tag is set to YES, doxygen generates more compact LaTeX\n# documents. This may be useful for small projects and may help to save some\n# trees in general.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nCOMPACT_LATEX          = NO\n\n# The PAPER_TYPE tag can be used to set the paper type that is used by the\n# printer.\n# Possible values are: a4 (210 x 297 mm), letter (8.5 x 11 inches), legal (8.5 x\n# 14 inches) and executive (7.25 x 10.5 inches).\n# The default value is: a4.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nPAPER_TYPE             = a4\n\n# The EXTRA_PACKAGES tag can be used to specify one or more LaTeX package names\n# that should be included in the LaTeX output. To get the times font for\n# instance you can specify\n# EXTRA_PACKAGES=times\n# If left blank no extra packages will be included.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nEXTRA_PACKAGES         =\n\n# The LATEX_HEADER tag can be used to specify a personal LaTeX header for the\n# generated LaTeX document. The header should contain everything until the first\n# chapter. If it is left blank doxygen will generate a standard header. See\n# section \"Doxygen usage\" for information on how to let doxygen write the\n# default header to a separate file.\n#\n# Note: Only use a user-defined header if you know what you are doing! The\n# following commands have a special meaning inside the header: $title,\n# $datetime, $date, $doxygenversion, $projectname, $projectnumber,\n# $projectbrief, $projectlogo. Doxygen will replace $title with the empty\n# string, for the replacement values of the other commands the user is referred\n# to HTML_HEADER.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_HEADER           =\n\n# The LATEX_FOOTER tag can be used to specify a personal LaTeX footer for the\n# generated LaTeX document. The footer should contain everything after the last\n# chapter. If it is left blank doxygen will generate a standard footer. See\n# LATEX_HEADER for more information on how to generate a default footer and what\n# special commands can be used inside the footer.\n#\n# Note: Only use a user-defined footer if you know what you are doing!\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_FOOTER           =\n\n# The LATEX_EXTRA_STYLESHEET tag can be used to specify additional user-defined\n# LaTeX style sheets that are included after the standard style sheets created\n# by doxygen. Using this option one can overrule certain style aspects. Doxygen\n# will copy the style sheet files to the output directory.\n# Note: The order of the extra style sheet files is of importance (e.g. the last\n# style sheet in the list overrules the setting of the previous ones in the\n# list).\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_EXTRA_STYLESHEET =\n\n# The LATEX_EXTRA_FILES tag can be used to specify one or more extra images or\n# other source files which should be copied to the LATEX_OUTPUT output\n# directory. Note that the files will be copied as-is; there are no commands or\n# markers available.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_EXTRA_FILES      =\n\n# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated is\n# prepared for conversion to PDF (using ps2pdf or pdflatex). The PDF file will\n# contain links (just like the HTML output) instead of page references. This\n# makes the output suitable for online browsing using a PDF viewer.\n# The default value is: YES.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nPDF_HYPERLINKS         = YES\n\n# If the USE_PDFLATEX tag is set to YES, doxygen will use pdflatex to generate\n# the PDF file directly from the LaTeX files. Set this option to YES, to get a\n# higher quality PDF documentation.\n# The default value is: YES.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nUSE_PDFLATEX           = YES\n\n# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \\batchmode\n# command to the generated LaTeX files. This will instruct LaTeX to keep running\n# if errors occur, instead of asking the user for help. This option is also used\n# when generating formulas in HTML.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_BATCHMODE        = NO\n\n# If the LATEX_HIDE_INDICES tag is set to YES then doxygen will not include the\n# index chapters (such as File Index, Compound Index, etc.) in the output.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_HIDE_INDICES     = NO\n\n# If the LATEX_SOURCE_CODE tag is set to YES then doxygen will include source\n# code with syntax highlighting in the LaTeX output.\n#\n# Note that which sources are shown also depends on other settings such as\n# SOURCE_BROWSER.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_SOURCE_CODE      = NO\n\n# The LATEX_BIB_STYLE tag can be used to specify the style to use for the\n# bibliography, e.g. plainnat, or ieeetr. See\n# http://en.wikipedia.org/wiki/BibTeX and \\cite for more info.\n# The default value is: plain.\n# This tag requires that the tag GENERATE_LATEX is set to YES.\n\nLATEX_BIB_STYLE        = plain\n\n#---------------------------------------------------------------------------\n# Configuration options related to the RTF output\n#---------------------------------------------------------------------------\n\n# If the GENERATE_RTF tag is set to YES, doxygen will generate RTF output. The\n# RTF output is optimized for Word 97 and may not look too pretty with other RTF\n# readers/editors.\n# The default value is: NO.\n\nGENERATE_RTF           = NO\n\n# The RTF_OUTPUT tag is used to specify where the RTF docs will be put. If a\n# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of\n# it.\n# The default directory is: rtf.\n# This tag requires that the tag GENERATE_RTF is set to YES.\n\nRTF_OUTPUT             = rtf\n\n# If the COMPACT_RTF tag is set to YES, doxygen generates more compact RTF\n# documents. This may be useful for small projects and may help to save some\n# trees in general.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_RTF is set to YES.\n\nCOMPACT_RTF            = NO\n\n# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated will\n# contain hyperlink fields. The RTF file will contain links (just like the HTML\n# output) instead of page references. This makes the output suitable for online\n# browsing using Word or some other Word compatible readers that support those\n# fields.\n#\n# Note: WordPad (write) and others do not support links.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_RTF is set to YES.\n\nRTF_HYPERLINKS         = NO\n\n# Load stylesheet definitions from file. Syntax is similar to doxygen's config\n# file, i.e. a series of assignments. You only have to provide replacements,\n# missing definitions are set to their default value.\n#\n# See also section \"Doxygen usage\" for information on how to generate the\n# default style sheet that doxygen normally uses.\n# This tag requires that the tag GENERATE_RTF is set to YES.\n\nRTF_STYLESHEET_FILE    =\n\n# Set optional variables used in the generation of an RTF document. Syntax is\n# similar to doxygen's config file. A template extensions file can be generated\n# using doxygen -e rtf extensionFile.\n# This tag requires that the tag GENERATE_RTF is set to YES.\n\nRTF_EXTENSIONS_FILE    =\n\n# If the RTF_SOURCE_CODE tag is set to YES then doxygen will include source code\n# with syntax highlighting in the RTF output.\n#\n# Note that which sources are shown also depends on other settings such as\n# SOURCE_BROWSER.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_RTF is set to YES.\n\nRTF_SOURCE_CODE        = NO\n\n#---------------------------------------------------------------------------\n# Configuration options related to the man page output\n#---------------------------------------------------------------------------\n\n# If the GENERATE_MAN tag is set to YES, doxygen will generate man pages for\n# classes and files.\n# The default value is: NO.\n\nGENERATE_MAN           = NO\n\n# The MAN_OUTPUT tag is used to specify where the man pages will be put. If a\n# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of\n# it. A directory man3 will be created inside the directory specified by\n# MAN_OUTPUT.\n# The default directory is: man.\n# This tag requires that the tag GENERATE_MAN is set to YES.\n\nMAN_OUTPUT             = man\n\n# The MAN_EXTENSION tag determines the extension that is added to the generated\n# man pages. In case the manual section does not start with a number, the number\n# 3 is prepended. The dot (.) at the beginning of the MAN_EXTENSION tag is\n# optional.\n# The default value is: .3.\n# This tag requires that the tag GENERATE_MAN is set to YES.\n\nMAN_EXTENSION          = .3\n\n# The MAN_SUBDIR tag determines the name of the directory created within\n# MAN_OUTPUT in which the man pages are placed. If defaults to man followed by\n# MAN_EXTENSION with the initial . removed.\n# This tag requires that the tag GENERATE_MAN is set to YES.\n\nMAN_SUBDIR             =\n\n# If the MAN_LINKS tag is set to YES and doxygen generates man output, then it\n# will generate one additional man file for each entity documented in the real\n# man page(s). These additional files only source the real man page, but without\n# them the man command would be unable to find the correct page.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_MAN is set to YES.\n\nMAN_LINKS              = NO\n\n#---------------------------------------------------------------------------\n# Configuration options related to the XML output\n#---------------------------------------------------------------------------\n\n# If the GENERATE_XML tag is set to YES, doxygen will generate an XML file that\n# captures the structure of the code including all documentation.\n# The default value is: NO.\n\nGENERATE_XML           = NO\n\n# The XML_OUTPUT tag is used to specify where the XML pages will be put. If a\n# relative path is entered the value of OUTPUT_DIRECTORY will be put in front of\n# it.\n# The default directory is: xml.\n# This tag requires that the tag GENERATE_XML is set to YES.\n\nXML_OUTPUT             = xml\n\n# If the XML_PROGRAMLISTING tag is set to YES, doxygen will dump the program\n# listings (including syntax highlighting and cross-referencing information) to\n# the XML output. Note that enabling this will significantly increase the size\n# of the XML output.\n# The default value is: YES.\n# This tag requires that the tag GENERATE_XML is set to YES.\n\nXML_PROGRAMLISTING     = YES\n\n#---------------------------------------------------------------------------\n# Configuration options related to the DOCBOOK output\n#---------------------------------------------------------------------------\n\n# If the GENERATE_DOCBOOK tag is set to YES, doxygen will generate Docbook files\n# that can be used to generate PDF.\n# The default value is: NO.\n\nGENERATE_DOCBOOK       = NO\n\n# The DOCBOOK_OUTPUT tag is used to specify where the Docbook pages will be put.\n# If a relative path is entered the value of OUTPUT_DIRECTORY will be put in\n# front of it.\n# The default directory is: docbook.\n# This tag requires that the tag GENERATE_DOCBOOK is set to YES.\n\nDOCBOOK_OUTPUT         = docbook\n\n# If the DOCBOOK_PROGRAMLISTING tag is set to YES, doxygen will include the\n# program listings (including syntax highlighting and cross-referencing\n# information) to the DOCBOOK output. Note that enabling this will significantly\n# increase the size of the DOCBOOK output.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_DOCBOOK is set to YES.\n\nDOCBOOK_PROGRAMLISTING = NO\n\n#---------------------------------------------------------------------------\n# Configuration options for the AutoGen Definitions output\n#---------------------------------------------------------------------------\n\n# If the GENERATE_AUTOGEN_DEF tag is set to YES, doxygen will generate an\n# AutoGen Definitions (see http://autogen.sf.net) file that captures the\n# structure of the code including all documentation. Note that this feature is\n# still experimental and incomplete at the moment.\n# The default value is: NO.\n\nGENERATE_AUTOGEN_DEF   = NO\n\n#---------------------------------------------------------------------------\n# Configuration options related to the Perl module output\n#---------------------------------------------------------------------------\n\n# If the GENERATE_PERLMOD tag is set to YES, doxygen will generate a Perl module\n# file that captures the structure of the code including all documentation.\n#\n# Note that this feature is still experimental and incomplete at the moment.\n# The default value is: NO.\n\nGENERATE_PERLMOD       = NO\n\n# If the PERLMOD_LATEX tag is set to YES, doxygen will generate the necessary\n# Makefile rules, Perl scripts and LaTeX code to be able to generate PDF and DVI\n# output from the Perl module output.\n# The default value is: NO.\n# This tag requires that the tag GENERATE_PERLMOD is set to YES.\n\nPERLMOD_LATEX          = NO\n\n# If the PERLMOD_PRETTY tag is set to YES, the Perl module output will be nicely\n# formatted so it can be parsed by a human reader. This is useful if you want to\n# understand what is going on. On the other hand, if this tag is set to NO, the\n# size of the Perl module output will be much smaller and Perl will parse it\n# just the same.\n# The default value is: YES.\n# This tag requires that the tag GENERATE_PERLMOD is set to YES.\n\nPERLMOD_PRETTY         = YES\n\n# The names of the make variables in the generated doxyrules.make file are\n# prefixed with the string contained in PERLMOD_MAKEVAR_PREFIX. This is useful\n# so different doxyrules.make files included by the same Makefile don't\n# overwrite each other's variables.\n# This tag requires that the tag GENERATE_PERLMOD is set to YES.\n\nPERLMOD_MAKEVAR_PREFIX =\n\n#---------------------------------------------------------------------------\n# Configuration options related to the preprocessor\n#---------------------------------------------------------------------------\n\n# If the ENABLE_PREPROCESSING tag is set to YES, doxygen will evaluate all\n# C-preprocessor directives found in the sources and include files.\n# The default value is: YES.\n\nENABLE_PREPROCESSING   = YES\n\n# If the MACRO_EXPANSION tag is set to YES, doxygen will expand all macro names\n# in the source code. If set to NO, only conditional compilation will be\n# performed. Macro expansion can be done in a controlled way by setting\n# EXPAND_ONLY_PREDEF to YES.\n# The default value is: NO.\n# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.\n\nMACRO_EXPANSION        = YES\n\n# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES then\n# the macro expansion is limited to the macros specified with the PREDEFINED and\n# EXPAND_AS_DEFINED tags.\n# The default value is: NO.\n# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.\n\nEXPAND_ONLY_PREDEF     = NO\n\n# If the SEARCH_INCLUDES tag is set to YES, the include files in the\n# INCLUDE_PATH will be searched if a #include is found.\n# The default value is: YES.\n# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.\n\nSEARCH_INCLUDES        = YES\n\n# The INCLUDE_PATH tag can be used to specify one or more directories that\n# contain include files that are not input files but should be processed by the\n# preprocessor.\n# This tag requires that the tag SEARCH_INCLUDES is set to YES.\n\nINCLUDE_PATH           = @top_srcdir@\n\n# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard\n# patterns (like *.h and *.hpp) to filter out the header-files in the\n# directories. If left blank, the patterns specified with FILE_PATTERNS will be\n# used.\n# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.\n\nINCLUDE_FILE_PATTERNS  =\n\n# The PREDEFINED tag can be used to specify one or more macro names that are\n# defined before the preprocessor is started (similar to the -D option of e.g.\n# gcc). The argument of the tag is a list of macros of the form: name or\n# name=definition (no spaces). If the definition and the \"=\" are omitted, \"=1\"\n# is assumed. To prevent a macro definition from being undefined via #undef or\n# recursively expanded use the := operator instead of the = operator.\n# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.\n\nPREDEFINED             = HAVE_CONFIG_H\n\n# If the MACRO_EXPANSION and EXPAND_ONLY_PREDEF tags are set to YES then this\n# tag can be used to specify a list of macro names that should be expanded. The\n# macro definition that is found in the sources will be used. Use the PREDEFINED\n# tag if you want to use a different macro definition that overrules the\n# definition found in the source code.\n# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.\n\nEXPAND_AS_DEFINED      =\n\n# If the SKIP_FUNCTION_MACROS tag is set to YES then doxygen's preprocessor will\n# remove all references to function-like macros that are alone on a line, have\n# an all uppercase name, and do not end with a semicolon. Such function macros\n# are typically used for boiler-plate code, and will confuse the parser if not\n# removed.\n# The default value is: YES.\n# This tag requires that the tag ENABLE_PREPROCESSING is set to YES.\n\nSKIP_FUNCTION_MACROS   = YES\n\n#---------------------------------------------------------------------------\n# Configuration options related to external references\n#---------------------------------------------------------------------------\n\n# The TAGFILES tag can be used to specify one or more tag files. For each tag\n# file the location of the external documentation should be added. The format of\n# a tag file without this location is as follows:\n# TAGFILES = file1 file2 ...\n# Adding location for the tag files is done as follows:\n# TAGFILES = file1=loc1 \"file2 = loc2\" ...\n# where loc1 and loc2 can be relative or absolute paths or URLs. See the\n# section \"Linking to external documentation\" for more information about the use\n# of tag files.\n# Note: Each tag file must have a unique name (where the name does NOT include\n# the path). If a tag file is not located in the directory in which doxygen is\n# run, you must also specify the path to the tagfile here.\n\nTAGFILES               =\n\n# When a file name is specified after GENERATE_TAGFILE, doxygen will create a\n# tag file that is based on the input files it reads. See section \"Linking to\n# external documentation\" for more information about the usage of tag files.\n\nGENERATE_TAGFILE       =\n\n# If the ALLEXTERNALS tag is set to YES, all external class will be listed in\n# the class index. If set to NO, only the inherited external classes will be\n# listed.\n# The default value is: NO.\n\nALLEXTERNALS           = NO\n\n# If the EXTERNAL_GROUPS tag is set to YES, all external groups will be listed\n# in the modules index. If set to NO, only the current project's groups will be\n# listed.\n# The default value is: YES.\n\nEXTERNAL_GROUPS        = YES\n\n# If the EXTERNAL_PAGES tag is set to YES, all external pages will be listed in\n# the related pages index. If set to NO, only the current project's pages will\n# be listed.\n# The default value is: YES.\n\nEXTERNAL_PAGES         = YES\n\n# The PERL_PATH should be the absolute path and name of the perl script\n# interpreter (i.e. the result of 'which perl').\n# The default file (with absolute path) is: /usr/bin/perl.\n\nPERL_PATH              = /usr/bin/perl\n\n#---------------------------------------------------------------------------\n# Configuration options related to the dot tool\n#---------------------------------------------------------------------------\n\n# If the CLASS_DIAGRAMS tag is set to YES, doxygen will generate a class diagram\n# (in HTML and LaTeX) for classes with base or super classes. Setting the tag to\n# NO turns the diagrams off. Note that this option also works with HAVE_DOT\n# disabled, but it is recommended to install and use dot, since it yields more\n# powerful graphs.\n# The default value is: YES.\n\nCLASS_DIAGRAMS         = YES\n\n# You can define message sequence charts within doxygen comments using the \\msc\n# command. Doxygen will then run the mscgen tool (see:\n# http://www.mcternan.me.uk/mscgen/)) to produce the chart and insert it in the\n# documentation. The MSCGEN_PATH tag allows you to specify the directory where\n# the mscgen tool resides. If left empty the tool is assumed to be found in the\n# default search path.\n\nMSCGEN_PATH            =\n\n# You can include diagrams made with dia in doxygen documentation. Doxygen will\n# then run dia to produce the diagram and insert it in the documentation. The\n# DIA_PATH tag allows you to specify the directory where the dia binary resides.\n# If left empty dia is assumed to be found in the default search path.\n\nDIA_PATH               =\n\n# If set to YES the inheritance and collaboration graphs will hide inheritance\n# and usage relations if the target is undocumented or is not a class.\n# The default value is: YES.\n\nHIDE_UNDOC_RELATIONS   = YES\n\n# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is\n# available from the path. This tool is part of Graphviz (see:\n# http://www.graphviz.org/), a graph visualization toolkit from AT&T and Lucent\n# Bell Labs. The other options in this section have no effect if this option is\n# set to NO\n# The default value is: YES.\n\nHAVE_DOT               = YES\n\n# The DOT_NUM_THREADS specifies the number of dot invocations doxygen is allowed\n# to run in parallel. When set to 0 doxygen will base this on the number of\n# processors available in the system. You can set it explicitly to a value\n# larger than 0 to get control over the balance between CPU load and processing\n# speed.\n# Minimum value: 0, maximum value: 32, default value: 0.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_NUM_THREADS        = 0\n\n# When you want a differently looking font in the dot files that doxygen\n# generates you can specify the font name using DOT_FONTNAME. You need to make\n# sure dot is able to find the font, which can be done by putting it in a\n# standard location or by setting the DOTFONTPATH environment variable or by\n# setting DOT_FONTPATH to the directory containing the font.\n# The default value is: Helvetica.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_FONTNAME           = Helvetica\n\n# The DOT_FONTSIZE tag can be used to set the size (in points) of the font of\n# dot graphs.\n# Minimum value: 4, maximum value: 24, default value: 10.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_FONTSIZE           = 10\n\n# By default doxygen will tell dot to use the default font as specified with\n# DOT_FONTNAME. If you specify a different font using DOT_FONTNAME you can set\n# the path where dot can find it using this tag.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_FONTPATH           =\n\n# If the CLASS_GRAPH tag is set to YES then doxygen will generate a graph for\n# each documented class showing the direct and indirect inheritance relations.\n# Setting this tag to YES will force the CLASS_DIAGRAMS tag to NO.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nCLASS_GRAPH            = YES\n\n# If the COLLABORATION_GRAPH tag is set to YES then doxygen will generate a\n# graph for each documented class showing the direct and indirect implementation\n# dependencies (inheritance, containment, and class references variables) of the\n# class with other documented classes.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nCOLLABORATION_GRAPH    = YES\n\n# If the GROUP_GRAPHS tag is set to YES then doxygen will generate a graph for\n# groups, showing the direct groups dependencies.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nGROUP_GRAPHS           = YES\n\n# If the UML_LOOK tag is set to YES, doxygen will generate inheritance and\n# collaboration diagrams in a style similar to the OMG's Unified Modeling\n# Language.\n# The default value is: NO.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nUML_LOOK               = NO\n\n# If the UML_LOOK tag is enabled, the fields and methods are shown inside the\n# class node. If there are many fields or methods and many nodes the graph may\n# become too big to be useful. The UML_LIMIT_NUM_FIELDS threshold limits the\n# number of items for each type to make the size more manageable. Set this to 0\n# for no limit. Note that the threshold may be exceeded by 50% before the limit\n# is enforced. So when you set the threshold to 10, up to 15 fields may appear,\n# but if the number exceeds 15, the total amount of fields shown is limited to\n# 10.\n# Minimum value: 0, maximum value: 100, default value: 10.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nUML_LIMIT_NUM_FIELDS   = 10\n\n# If the TEMPLATE_RELATIONS tag is set to YES then the inheritance and\n# collaboration graphs will show the relations between templates and their\n# instances.\n# The default value is: NO.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nTEMPLATE_RELATIONS     = NO\n\n# If the INCLUDE_GRAPH, ENABLE_PREPROCESSING and SEARCH_INCLUDES tags are set to\n# YES then doxygen will generate a graph for each documented file showing the\n# direct and indirect include dependencies of the file with other documented\n# files.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nINCLUDE_GRAPH          = YES\n\n# If the INCLUDED_BY_GRAPH, ENABLE_PREPROCESSING and SEARCH_INCLUDES tags are\n# set to YES then doxygen will generate a graph for each documented file showing\n# the direct and indirect include dependencies of the file with other documented\n# files.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nINCLUDED_BY_GRAPH      = NO\n\n# If the CALL_GRAPH tag is set to YES then doxygen will generate a call\n# dependency graph for every global function or class method.\n#\n# Note that enabling this option will significantly increase the time of a run.\n# So in most cases it will be better to enable call graphs for selected\n# functions only using the \\callgraph command.\n# The default value is: NO.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nCALL_GRAPH             = NO\n\n# If the CALLER_GRAPH tag is set to YES then doxygen will generate a caller\n# dependency graph for every global function or class method.\n#\n# Note that enabling this option will significantly increase the time of a run.\n# So in most cases it will be better to enable caller graphs for selected\n# functions only using the \\callergraph command.\n# The default value is: NO.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nCALLER_GRAPH           = NO\n\n# If the GRAPHICAL_HIERARCHY tag is set to YES then doxygen will graphical\n# hierarchy of all classes instead of a textual one.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nGRAPHICAL_HIERARCHY    = YES\n\n# If the DIRECTORY_GRAPH tag is set to YES then doxygen will show the\n# dependencies a directory has on other directories in a graphical way. The\n# dependency relations are determined by the #include relations between the\n# files in the directories.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDIRECTORY_GRAPH        = YES\n\n# The DOT_IMAGE_FORMAT tag can be used to set the image format of the images\n# generated by dot.\n# Note: If you choose svg you need to set HTML_FILE_EXTENSION to xhtml in order\n# to make the SVG files visible in IE 9+ (other browsers do not have this\n# requirement).\n# Possible values are: png, png:cairo, png:cairo:cairo, png:cairo:gd, png:gd,\n# png:gd:gd, jpg, jpg:cairo, jpg:cairo:gd, jpg:gd, jpg:gd:gd, gif, gif:cairo,\n# gif:cairo:gd, gif:gd, gif:gd:gd and svg.\n# The default value is: png.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_IMAGE_FORMAT       = png\n\n# If DOT_IMAGE_FORMAT is set to svg, then this option can be set to YES to\n# enable generation of interactive SVG images that allow zooming and panning.\n#\n# Note that this requires a modern browser other than Internet Explorer. Tested\n# and working are Firefox, Chrome, Safari, and Opera.\n# Note: For IE 9+ you need to set HTML_FILE_EXTENSION to xhtml in order to make\n# the SVG files visible. Older versions of IE do not have SVG support.\n# The default value is: NO.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nINTERACTIVE_SVG        = NO\n\n# The DOT_PATH tag can be used to specify the path where the dot tool can be\n# found. If left blank, it is assumed the dot tool can be found in the path.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_PATH               =\n\n# The DOTFILE_DIRS tag can be used to specify one or more directories that\n# contain dot files that are included in the documentation (see the \\dotfile\n# command).\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOTFILE_DIRS           =\n\n# The MSCFILE_DIRS tag can be used to specify one or more directories that\n# contain msc files that are included in the documentation (see the \\mscfile\n# command).\n\nMSCFILE_DIRS           =\n\n# The DIAFILE_DIRS tag can be used to specify one or more directories that\n# contain dia files that are included in the documentation (see the \\diafile\n# command).\n\nDIAFILE_DIRS           =\n\n# When using plantuml, the PLANTUML_JAR_PATH tag should be used to specify the\n# path where java can find the plantuml.jar file. If left blank, it is assumed\n# PlantUML is not used or called during a preprocessing step. Doxygen will\n# generate a warning when it encounters a \\startuml command in this case and\n# will not generate output for the diagram.\n\nPLANTUML_JAR_PATH      =\n\n# When using plantuml, the specified paths are searched for files specified by\n# the !include statement in a plantuml block.\n\nPLANTUML_INCLUDE_PATH  =\n\n# The DOT_GRAPH_MAX_NODES tag can be used to set the maximum number of nodes\n# that will be shown in the graph. If the number of nodes in a graph becomes\n# larger than this value, doxygen will truncate the graph, which is visualized\n# by representing a node as a red box. Note that doxygen if the number of direct\n# children of the root node in a graph is already larger than\n# DOT_GRAPH_MAX_NODES then the graph will not be shown at all. Also note that\n# the size of a graph can be further restricted by MAX_DOT_GRAPH_DEPTH.\n# Minimum value: 0, maximum value: 10000, default value: 50.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_GRAPH_MAX_NODES    = 50\n\n# The MAX_DOT_GRAPH_DEPTH tag can be used to set the maximum depth of the graphs\n# generated by dot. A depth value of 3 means that only nodes reachable from the\n# root by following a path via at most 3 edges will be shown. Nodes that lay\n# further from the root node will be omitted. Note that setting this option to 1\n# or 2 may greatly reduce the computation time needed for large code bases. Also\n# note that the size of a graph can be further restricted by\n# DOT_GRAPH_MAX_NODES. Using a depth of 0 means no depth restriction.\n# Minimum value: 0, maximum value: 1000, default value: 0.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nMAX_DOT_GRAPH_DEPTH    = 0\n\n# Set the DOT_TRANSPARENT tag to YES to generate images with a transparent\n# background. This is disabled by default, because dot on Windows does not seem\n# to support this out of the box.\n#\n# Warning: Depending on the platform used, enabling this option may lead to\n# badly anti-aliased labels on the edges of a graph (i.e. they become hard to\n# read).\n# The default value is: NO.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_TRANSPARENT        = NO\n\n# Set the DOT_MULTI_TARGETS tag to YES to allow dot to generate multiple output\n# files in one run (i.e. multiple -o and -T options on the command line). This\n# makes dot run faster, but since only newer versions of dot (>1.8.10) support\n# this, this feature is disabled by default.\n# The default value is: NO.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_MULTI_TARGETS      = NO\n\n# If the GENERATE_LEGEND tag is set to YES doxygen will generate a legend page\n# explaining the meaning of the various boxes and arrows in the dot generated\n# graphs.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nGENERATE_LEGEND        = YES\n\n# If the DOT_CLEANUP tag is set to YES, doxygen will remove the intermediate dot\n# files that are used to generate the various graphs.\n# The default value is: YES.\n# This tag requires that the tag HAVE_DOT is set to YES.\n\nDOT_CLEANUP            = YES\n"
  },
  {
    "path": "cudd/LICENSE",
    "content": "Copyright (c) 1995-2004, Regents of the University of Colorado\n\nAll rights reserved.\n\nRedistribution and use in source and binary forms, with or without\nmodification, are permitted provided that the following conditions\nare met:\n\nRedistributions of source code must retain the above copyright\nnotice, this list of conditions and the following disclaimer.\n\nRedistributions in binary form must reproduce the above copyright\nnotice, this list of conditions and the following disclaimer in the\ndocumentation and/or other materials provided with the distribution.\n\nNeither the name of the University of Colorado nor the names of its\ncontributors may be used to endorse or promote products derived from\nthis software without specific prior written permission.\n\nTHIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n\"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\nLIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\nFOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\nCOPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\nINCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\nBUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\nLOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\nCAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\nLIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\nANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\nPOSSIBILITY OF SUCH DAMAGE.\n"
  },
  {
    "path": "cudd/Makefile.am",
    "content": "ACLOCAL_AMFLAGS = -I m4\n\ninclude_HEADERS = cudd/cudd.h\nif DDDMP\ninclude_HEADERS += dddmp/dddmp.h\nendif\nif OBJ\ninclude_HEADERS += cplusplus/cuddObj.hh\nendif\n\ncheck_PROGRAMS =\ncheck_SCRIPTS =\ndist_check_DATA =\nEXTRA_DIST = README RELEASE.NOTES LICENSE groups.dox\nTESTS =\nCLEANFILES =\nnoinst_LTLIBRARIES =\nTEST_LOG_DRIVER = env AM_TAP_AWK='$(AWK)' $(SHELL) \\\n  $(top_srcdir)/build-aux/tap-driver.sh\n\ndo_subst = sed \\\n  -e 's,[@]EXEEXT[@],$(EXEEXT),g' \\\n  -e 's,[@]srcdir[@],$(srcdir),g'\n\ninclude $(top_srcdir)/cudd/Included.am\ninclude $(top_srcdir)/util/Included.am\ninclude $(top_srcdir)/st/Included.am\ninclude $(top_srcdir)/epd/Included.am\ninclude $(top_srcdir)/mtr/Included.am\ninclude $(top_srcdir)/dddmp/Included.am\ninclude $(top_srcdir)/cplusplus/Included.am\n#include $(top_srcdir)/nanotrav/Included.am\n#include $(top_srcdir)/doc/Included.am\n\ndist-hook:\n\trm -rf `find $(distdir) -name .svn`\n\n.PHONY : \n\nall: #html/index.html doc/cudd.pdf\n\nif HAVE_DOXYGEN\n\nhtml/index.html: Doxyfile $(lib_LTLIBRARIES)\n\t@if $(AM_V_P); then dest='2>&1'; else dest='> /dev/null 2>&1'; fi; \\\n\teval \"$(DOXYGEN) $< $${dest}\"\n\nclean-local:\n\trm -rf html doxygen_sqlite3.db\n\nelse\n\nhtml/index.html:\n\nendif\n\nCLEANFILES += $(check_SCRIPTS)\n"
  },
  {
    "path": "cudd/Makefile.in",
    "content": "# Makefile.in generated by automake 1.16.5 from Makefile.am.\n# @configure_input@\n\n# Copyright (C) 1994-2021 Free Software Foundation, Inc.\n\n# This Makefile.in is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# This program is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY, to the extent permitted by law; without\n# even the implied warranty of MERCHANTABILITY or FITNESS FOR A\n# PARTICULAR PURPOSE.\n\n@SET_MAKE@\n\n\nVPATH = @srcdir@\nam__is_gnu_make = { \\\n  if test -z '$(MAKELEVEL)'; then \\\n    false; \\\n  elif test -n '$(MAKE_HOST)'; then \\\n    true; \\\n  elif test -n '$(MAKE_VERSION)' && test -n '$(CURDIR)'; then \\\n    true; \\\n  else \\\n    false; \\\n  fi; \\\n}\nam__make_running_with_option = \\\n  case $${target_option-} in \\\n      ?) ;; \\\n      *) echo \"am__make_running_with_option: internal error: invalid\" \\\n              \"target option '$${target_option-}' specified\" >&2; \\\n         exit 1;; \\\n  esac; \\\n  has_opt=no; \\\n  sane_makeflags=$$MAKEFLAGS; \\\n  if $(am__is_gnu_make); then \\\n    sane_makeflags=$$MFLAGS; \\\n  else \\\n    case $$MAKEFLAGS in \\\n      *\\\\[\\ \\\t]*) \\\n        bs=\\\\; \\\n        sane_makeflags=`printf '%s\\n' \"$$MAKEFLAGS\" \\\n          | sed \"s/$$bs$$bs[$$bs $$bs\t]*//g\"`;; \\\n    esac; \\\n  fi; \\\n  skip_next=no; \\\n  strip_trailopt () \\\n  { \\\n    flg=`printf '%s\\n' \"$$flg\" | sed \"s/$$1.*$$//\"`; \\\n  }; \\\n  for flg in $$sane_makeflags; do \\\n    test $$skip_next = yes && { skip_next=no; continue; }; \\\n    case $$flg in \\\n      *=*|--*) continue;; \\\n        -*I) strip_trailopt 'I'; skip_next=yes;; \\\n      -*I?*) strip_trailopt 'I';; \\\n        -*O) strip_trailopt 'O'; skip_next=yes;; \\\n      -*O?*) strip_trailopt 'O';; \\\n        -*l) strip_trailopt 'l'; skip_next=yes;; \\\n      -*l?*) strip_trailopt 'l';; \\\n      -[dEDm]) skip_next=yes;; \\\n      -[JT]) skip_next=yes;; \\\n    esac; \\\n    case $$flg in \\\n      *$$target_option*) has_opt=yes; break;; \\\n    esac; \\\n  done; \\\n  test $$has_opt = yes\nam__make_dryrun = (target_option=n; $(am__make_running_with_option))\nam__make_keepgoing = (target_option=k; $(am__make_running_with_option))\npkgdatadir = $(datadir)/@PACKAGE@\npkgincludedir = $(includedir)/@PACKAGE@\npkglibdir = $(libdir)/@PACKAGE@\npkglibexecdir = $(libexecdir)/@PACKAGE@\nam__cd = CDPATH=\"$${ZSH_VERSION+.}$(PATH_SEPARATOR)\" && cd\ninstall_sh_DATA = $(install_sh) -c -m 644\ninstall_sh_PROGRAM = $(install_sh) -c\ninstall_sh_SCRIPT = $(install_sh) -c\nINSTALL_HEADER = $(INSTALL_DATA)\ntransform = $(program_transform_name)\nNORMAL_INSTALL = :\nPRE_INSTALL = :\nPOST_INSTALL = :\nNORMAL_UNINSTALL = :\nPRE_UNINSTALL = :\nPOST_UNINSTALL = :\nbuild_triplet = @build@\nhost_triplet = @host@\n@DDDMP_TRUE@am__append_1 = dddmp/dddmp.h\n@OBJ_TRUE@am__append_2 = cplusplus/cuddObj.hh\ncheck_PROGRAMS = cudd/testcudd$(EXEEXT) cudd/testextra$(EXEEXT) \\\n\tst/testst$(EXEEXT) mtr/testmtr$(EXEEXT) \\\n\tdddmp/testdddmp$(EXEEXT) cplusplus/testobj$(EXEEXT) \\\n\tcplusplus/testmulti$(EXEEXT)\n@CROSS_COMPILING_FALSE@am__append_3 = cudd/test_cudd.test \\\n@CROSS_COMPILING_FALSE@\tst/test_st.test mtr/test_mtr.test \\\n@CROSS_COMPILING_FALSE@\tdddmp/test_dddmp.test \\\n@CROSS_COMPILING_FALSE@\tcplusplus/test_obj.test\n@DDDMP_TRUE@am__append_4 = $(dddmp_sources)\n@DDDMP_FALSE@am__append_5 = dddmp/libdddmp.la\n@OBJ_TRUE@am__append_6 = $(cplusplus_sources)\n@OBJ_FALSE@am__append_7 = cplusplus/libobj.la\nsubdir = .\nACLOCAL_M4 = $(top_srcdir)/aclocal.m4\nam__aclocal_m4_deps = $(top_srcdir)/m4/libtool.m4 \\\n\t$(top_srcdir)/m4/ltoptions.m4 $(top_srcdir)/m4/ltsugar.m4 \\\n\t$(top_srcdir)/m4/ltversion.m4 $(top_srcdir)/m4/lt~obsolete.m4 \\\n\t$(top_srcdir)/m4/modern_cxx.m4 $(top_srcdir)/m4/w32.m4 \\\n\t$(top_srcdir)/configure.ac\nam__configure_deps = $(am__aclocal_m4_deps) $(CONFIGURE_DEPENDENCIES) \\\n\t$(ACLOCAL_M4)\nDIST_COMMON = $(srcdir)/Makefile.am $(top_srcdir)/configure \\\n\t$(am__configure_deps) $(dist_check_DATA) \\\n\t$(am__include_HEADERS_DIST) $(am__DIST_COMMON)\nam__CONFIG_DISTCLEAN_FILES = config.status config.cache config.log \\\n configure.lineno config.status.lineno\nmkinstalldirs = $(install_sh) -d\nCONFIG_HEADER = config.h\nCONFIG_CLEAN_FILES = Doxyfile doc/cudd.tex dddmp/exp/test1.sh \\\n\tdddmp/exp/test2.sh dddmp/exp/test3.sh dddmp/exp/test4.sh \\\n\tdddmp/exp/test5.sh dddmp/exp/test6.sh dddmp/exp/test7.sh\nCONFIG_CLEAN_VPATH_FILES =\nam__vpath_adj_setup = srcdirstrip=`echo \"$(srcdir)\" | sed 's|.|.|g'`;\nam__vpath_adj = case $$p in \\\n    $(srcdir)/*) f=`echo \"$$p\" | sed \"s|^$$srcdirstrip/||\"`;; \\\n    *) f=$$p;; \\\n  esac;\nam__strip_dir = f=`echo $$p | sed -e 's|^.*/||'`;\nam__install_max = 40\nam__nobase_strip_setup = \\\n  srcdirstrip=`echo \"$(srcdir)\" | sed 's/[].[^$$\\\\*|]/\\\\\\\\&/g'`\nam__nobase_strip = \\\n  for p in $$list; do echo \"$$p\"; done | sed -e \"s|$$srcdirstrip/||\"\nam__nobase_list = $(am__nobase_strip_setup); \\\n  for p in $$list; do echo \"$$p $$p\"; done | \\\n  sed \"s| $$srcdirstrip/| |;\"' / .*\\//!s/ .*/ ./; s,\\( .*\\)/[^/]*$$,\\1,' | \\\n  $(AWK) 'BEGIN { files[\".\"] = \"\" } { files[$$2] = files[$$2] \" \" $$1; \\\n    if (++n[$$2] == $(am__install_max)) \\\n      { print $$2, files[$$2]; n[$$2] = 0; files[$$2] = \"\" } } \\\n    END { for (dir in files) print dir, files[dir] }'\nam__base_list = \\\n  sed '$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;$$!N;s/\\n/ /g' | \\\n  sed '$$!N;$$!N;$$!N;$$!N;s/\\n/ /g'\nam__uninstall_files_from_dir = { \\\n  test -z \"$$files\" \\\n    || { test ! -d \"$$dir\" && test ! -f \"$$dir\" && test ! -r \"$$dir\"; } \\\n    || { echo \" ( cd '$$dir' && rm -f\" $$files \")\"; \\\n         $(am__cd) \"$$dir\" && rm -f $$files; }; \\\n  }\nam__installdirs = \"$(DESTDIR)$(libdir)\" \"$(DESTDIR)$(includedir)\"\nLTLIBRARIES = $(lib_LTLIBRARIES) $(noinst_LTLIBRARIES)\ncplusplus_libobj_la_LIBADD =\nam__cplusplus_libobj_la_SOURCES_DIST = cplusplus/cuddObj.hh \\\n\tcplusplus/cuddObj.cc\nam__dirstamp = $(am__leading_dot)dirstamp\nam__objects_1 = cplusplus/libobj_la-cuddObj.lo\n@OBJ_FALSE@am_cplusplus_libobj_la_OBJECTS = $(am__objects_1)\ncplusplus_libobj_la_OBJECTS = $(am_cplusplus_libobj_la_OBJECTS)\nAM_V_lt = $(am__v_lt_@AM_V@)\nam__v_lt_ = $(am__v_lt_@AM_DEFAULT_V@)\nam__v_lt_0 = --silent\nam__v_lt_1 = \n@OBJ_FALSE@am_cplusplus_libobj_la_rpath =\ncudd_libcudd_la_DEPENDENCIES =\nam__cudd_libcudd_la_SOURCES_DIST = cudd/cudd.h cudd/cuddInt.h \\\n\tcudd/cuddAddAbs.c cudd/cuddAddApply.c cudd/cuddAddFind.c \\\n\tcudd/cuddAddInv.c cudd/cuddAddIte.c cudd/cuddAddNeg.c \\\n\tcudd/cuddAddWalsh.c cudd/cuddAndAbs.c cudd/cuddAnneal.c \\\n\tcudd/cuddApa.c cudd/cuddAPI.c cudd/cuddApprox.c \\\n\tcudd/cuddBddAbs.c cudd/cuddBddCorr.c cudd/cuddBddIte.c \\\n\tcudd/cuddBridge.c cudd/cuddCache.c cudd/cuddCheck.c \\\n\tcudd/cuddClip.c cudd/cuddCof.c cudd/cuddCompose.c \\\n\tcudd/cuddDecomp.c cudd/cuddEssent.c cudd/cuddExact.c \\\n\tcudd/cuddExport.c cudd/cuddGenCof.c cudd/cuddGenetic.c \\\n\tcudd/cuddGroup.c cudd/cuddHarwell.c cudd/cuddInit.c \\\n\tcudd/cuddInteract.c cudd/cuddLCache.c cudd/cuddLevelQ.c \\\n\tcudd/cuddLinear.c cudd/cuddLiteral.c cudd/cuddMatMult.c \\\n\tcudd/cuddPriority.c cudd/cuddRead.c cudd/cuddRef.c \\\n\tcudd/cuddReorder.c cudd/cuddSat.c cudd/cuddSign.c \\\n\tcudd/cuddSolve.c cudd/cuddSplit.c cudd/cuddSubsetHB.c \\\n\tcudd/cuddSubsetSP.c cudd/cuddSymmetry.c cudd/cuddTable.c \\\n\tcudd/cuddUtil.c cudd/cuddWindow.c cudd/cuddZddCount.c \\\n\tcudd/cuddZddFuncs.c cudd/cuddZddGroup.c cudd/cuddZddIsop.c \\\n\tcudd/cuddZddLin.c cudd/cuddZddMisc.c cudd/cuddZddPort.c \\\n\tcudd/cuddZddReord.c cudd/cuddZddSetop.c cudd/cuddZddSymm.c \\\n\tcudd/cuddZddUtil.c util/util.h util/cstringstream.h \\\n\tutil/cpu_stats.c util/cpu_time.c util/cstringstream.c \\\n\tutil/datalimit.c util/pathsearch.c util/pipefork.c \\\n\tutil/prtime.c util/safe_mem.c util/strsav.c util/texpand.c \\\n\tutil/ucbqsort.c st/st.h st/st.c epd/epd.c epd/epdInt.h \\\n\tepd/epd.h mtr/mtr.h mtr/mtrInt.h mtr/mtrBasic.c mtr/mtrGroup.c \\\n\tdddmp/dddmp.h dddmp/dddmpInt.h dddmp/dddmpBinary.c \\\n\tdddmp/dddmpConvert.c dddmp/dddmpDbg.c dddmp/dddmpLoad.c \\\n\tdddmp/dddmpLoadCnf.c dddmp/dddmpNodeAdd.c dddmp/dddmpNodeBdd.c \\\n\tdddmp/dddmpNodeCnf.c dddmp/dddmpStoreAdd.c \\\n\tdddmp/dddmpStoreBdd.c dddmp/dddmpStoreCnf.c \\\n\tdddmp/dddmpStoreMisc.c dddmp/dddmpUtil.c cplusplus/cuddObj.hh \\\n\tcplusplus/cuddObj.cc\nam__objects_2 = dddmp/cudd_libcudd_la-dddmpBinary.lo \\\n\tdddmp/cudd_libcudd_la-dddmpConvert.lo \\\n\tdddmp/cudd_libcudd_la-dddmpDbg.lo \\\n\tdddmp/cudd_libcudd_la-dddmpLoad.lo \\\n\tdddmp/cudd_libcudd_la-dddmpLoadCnf.lo \\\n\tdddmp/cudd_libcudd_la-dddmpNodeAdd.lo \\\n\tdddmp/cudd_libcudd_la-dddmpNodeBdd.lo \\\n\tdddmp/cudd_libcudd_la-dddmpNodeCnf.lo \\\n\tdddmp/cudd_libcudd_la-dddmpStoreAdd.lo \\\n\tdddmp/cudd_libcudd_la-dddmpStoreBdd.lo \\\n\tdddmp/cudd_libcudd_la-dddmpStoreCnf.lo \\\n\tdddmp/cudd_libcudd_la-dddmpStoreMisc.lo \\\n\tdddmp/cudd_libcudd_la-dddmpUtil.lo\n@DDDMP_TRUE@am__objects_3 = $(am__objects_2)\nam__objects_4 = cplusplus/cudd_libcudd_la-cuddObj.lo\n@OBJ_TRUE@am__objects_5 = $(am__objects_4)\nam_cudd_libcudd_la_OBJECTS = cudd/libcudd_la-cuddAddAbs.lo \\\n\tcudd/libcudd_la-cuddAddApply.lo cudd/libcudd_la-cuddAddFind.lo \\\n\tcudd/libcudd_la-cuddAddInv.lo cudd/libcudd_la-cuddAddIte.lo \\\n\tcudd/libcudd_la-cuddAddNeg.lo cudd/libcudd_la-cuddAddWalsh.lo \\\n\tcudd/libcudd_la-cuddAndAbs.lo cudd/libcudd_la-cuddAnneal.lo \\\n\tcudd/libcudd_la-cuddApa.lo cudd/libcudd_la-cuddAPI.lo \\\n\tcudd/libcudd_la-cuddApprox.lo cudd/libcudd_la-cuddBddAbs.lo \\\n\tcudd/libcudd_la-cuddBddCorr.lo cudd/libcudd_la-cuddBddIte.lo \\\n\tcudd/libcudd_la-cuddBridge.lo cudd/libcudd_la-cuddCache.lo \\\n\tcudd/libcudd_la-cuddCheck.lo cudd/libcudd_la-cuddClip.lo \\\n\tcudd/libcudd_la-cuddCof.lo cudd/libcudd_la-cuddCompose.lo \\\n\tcudd/libcudd_la-cuddDecomp.lo cudd/libcudd_la-cuddEssent.lo \\\n\tcudd/libcudd_la-cuddExact.lo cudd/libcudd_la-cuddExport.lo \\\n\tcudd/libcudd_la-cuddGenCof.lo cudd/libcudd_la-cuddGenetic.lo \\\n\tcudd/libcudd_la-cuddGroup.lo cudd/libcudd_la-cuddHarwell.lo \\\n\tcudd/libcudd_la-cuddInit.lo cudd/libcudd_la-cuddInteract.lo \\\n\tcudd/libcudd_la-cuddLCache.lo cudd/libcudd_la-cuddLevelQ.lo \\\n\tcudd/libcudd_la-cuddLinear.lo cudd/libcudd_la-cuddLiteral.lo \\\n\tcudd/libcudd_la-cuddMatMult.lo cudd/libcudd_la-cuddPriority.lo \\\n\tcudd/libcudd_la-cuddRead.lo cudd/libcudd_la-cuddRef.lo \\\n\tcudd/libcudd_la-cuddReorder.lo cudd/libcudd_la-cuddSat.lo \\\n\tcudd/libcudd_la-cuddSign.lo cudd/libcudd_la-cuddSolve.lo \\\n\tcudd/libcudd_la-cuddSplit.lo cudd/libcudd_la-cuddSubsetHB.lo \\\n\tcudd/libcudd_la-cuddSubsetSP.lo \\\n\tcudd/libcudd_la-cuddSymmetry.lo cudd/libcudd_la-cuddTable.lo \\\n\tcudd/libcudd_la-cuddUtil.lo cudd/libcudd_la-cuddWindow.lo \\\n\tcudd/libcudd_la-cuddZddCount.lo \\\n\tcudd/libcudd_la-cuddZddFuncs.lo \\\n\tcudd/libcudd_la-cuddZddGroup.lo cudd/libcudd_la-cuddZddIsop.lo \\\n\tcudd/libcudd_la-cuddZddLin.lo cudd/libcudd_la-cuddZddMisc.lo \\\n\tcudd/libcudd_la-cuddZddPort.lo cudd/libcudd_la-cuddZddReord.lo \\\n\tcudd/libcudd_la-cuddZddSetop.lo cudd/libcudd_la-cuddZddSymm.lo \\\n\tcudd/libcudd_la-cuddZddUtil.lo \\\n\tutil/cudd_libcudd_la-cpu_stats.lo \\\n\tutil/cudd_libcudd_la-cpu_time.lo \\\n\tutil/cudd_libcudd_la-cstringstream.lo \\\n\tutil/cudd_libcudd_la-datalimit.lo \\\n\tutil/cudd_libcudd_la-pathsearch.lo \\\n\tutil/cudd_libcudd_la-pipefork.lo \\\n\tutil/cudd_libcudd_la-prtime.lo \\\n\tutil/cudd_libcudd_la-safe_mem.lo \\\n\tutil/cudd_libcudd_la-strsav.lo util/cudd_libcudd_la-texpand.lo \\\n\tutil/cudd_libcudd_la-ucbqsort.lo st/cudd_libcudd_la-st.lo \\\n\tepd/cudd_libcudd_la-epd.lo mtr/cudd_libcudd_la-mtrBasic.lo \\\n\tmtr/cudd_libcudd_la-mtrGroup.lo $(am__objects_3) \\\n\t$(am__objects_5)\ncudd_libcudd_la_OBJECTS = $(am_cudd_libcudd_la_OBJECTS)\ncudd_libcudd_la_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CXX \\\n\t$(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link \\\n\t$(CXXLD) $(AM_CXXFLAGS) $(CXXFLAGS) $(cudd_libcudd_la_LDFLAGS) \\\n\t$(LDFLAGS) -o $@\ndddmp_libdddmp_la_LIBADD =\nam__dddmp_libdddmp_la_SOURCES_DIST = dddmp/dddmp.h dddmp/dddmpInt.h \\\n\tdddmp/dddmpBinary.c dddmp/dddmpConvert.c dddmp/dddmpDbg.c \\\n\tdddmp/dddmpLoad.c dddmp/dddmpLoadCnf.c dddmp/dddmpNodeAdd.c \\\n\tdddmp/dddmpNodeBdd.c dddmp/dddmpNodeCnf.c \\\n\tdddmp/dddmpStoreAdd.c dddmp/dddmpStoreBdd.c \\\n\tdddmp/dddmpStoreCnf.c dddmp/dddmpStoreMisc.c dddmp/dddmpUtil.c\nam__objects_6 = dddmp/libdddmp_la-dddmpBinary.lo \\\n\tdddmp/libdddmp_la-dddmpConvert.lo \\\n\tdddmp/libdddmp_la-dddmpDbg.lo dddmp/libdddmp_la-dddmpLoad.lo \\\n\tdddmp/libdddmp_la-dddmpLoadCnf.lo \\\n\tdddmp/libdddmp_la-dddmpNodeAdd.lo \\\n\tdddmp/libdddmp_la-dddmpNodeBdd.lo \\\n\tdddmp/libdddmp_la-dddmpNodeCnf.lo \\\n\tdddmp/libdddmp_la-dddmpStoreAdd.lo \\\n\tdddmp/libdddmp_la-dddmpStoreBdd.lo \\\n\tdddmp/libdddmp_la-dddmpStoreCnf.lo \\\n\tdddmp/libdddmp_la-dddmpStoreMisc.lo \\\n\tdddmp/libdddmp_la-dddmpUtil.lo\n@DDDMP_FALSE@am_dddmp_libdddmp_la_OBJECTS = $(am__objects_6)\ndddmp_libdddmp_la_OBJECTS = $(am_dddmp_libdddmp_la_OBJECTS)\n@DDDMP_FALSE@am_dddmp_libdddmp_la_rpath =\nam_cplusplus_testmulti_OBJECTS =  \\\n\tcplusplus/testmulti-testmulti.$(OBJEXT)\ncplusplus_testmulti_OBJECTS = $(am_cplusplus_testmulti_OBJECTS)\n@OBJ_FALSE@cplusplus_testmulti_DEPENDENCIES = cplusplus/libobj.la \\\n@OBJ_FALSE@\tcudd/libcudd.la\n@OBJ_TRUE@cplusplus_testmulti_DEPENDENCIES = cudd/libcudd.la\ncplusplus_testmulti_LINK = $(LIBTOOL) $(AM_V_lt) --tag=CXX \\\n\t$(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=link $(CXXLD) \\\n\t$(AM_CXXFLAGS) $(CXXFLAGS) $(cplusplus_testmulti_LDFLAGS) \\\n\t$(LDFLAGS) -o $@\nam_cplusplus_testobj_OBJECTS = cplusplus/testobj-testobj.$(OBJEXT)\ncplusplus_testobj_OBJECTS = $(am_cplusplus_testobj_OBJECTS)\n@OBJ_FALSE@cplusplus_testobj_DEPENDENCIES = cplusplus/libobj.la \\\n@OBJ_FALSE@\tcudd/libcudd.la\n@OBJ_TRUE@cplusplus_testobj_DEPENDENCIES = cudd/libcudd.la\nam_cudd_testcudd_OBJECTS = cudd/testcudd-testcudd.$(OBJEXT)\ncudd_testcudd_OBJECTS = $(am_cudd_testcudd_OBJECTS)\ncudd_testcudd_DEPENDENCIES = cudd/libcudd.la\nam_cudd_testextra_OBJECTS = cudd/testextra-testextra.$(OBJEXT)\ncudd_testextra_OBJECTS = $(am_cudd_testextra_OBJECTS)\ncudd_testextra_DEPENDENCIES = cudd/libcudd.la\nam_dddmp_testdddmp_OBJECTS = dddmp/testdddmp-testdddmp.$(OBJEXT)\ndddmp_testdddmp_OBJECTS = $(am_dddmp_testdddmp_OBJECTS)\n@DDDMP_FALSE@dddmp_testdddmp_DEPENDENCIES = dddmp/libdddmp.la \\\n@DDDMP_FALSE@\tcudd/libcudd.la\n@DDDMP_TRUE@dddmp_testdddmp_DEPENDENCIES = cudd/libcudd.la\nam_mtr_testmtr_OBJECTS = mtr/testmtr-testmtr.$(OBJEXT)\nmtr_testmtr_OBJECTS = $(am_mtr_testmtr_OBJECTS)\nmtr_testmtr_DEPENDENCIES = cudd/libcudd.la\nam_st_testst_OBJECTS = st/testst-testst.$(OBJEXT)\nst_testst_OBJECTS = $(am_st_testst_OBJECTS)\nst_testst_DEPENDENCIES = cudd/libcudd.la\nAM_V_P = $(am__v_P_@AM_V@)\nam__v_P_ = $(am__v_P_@AM_DEFAULT_V@)\nam__v_P_0 = false\nam__v_P_1 = :\nAM_V_GEN = $(am__v_GEN_@AM_V@)\nam__v_GEN_ = $(am__v_GEN_@AM_DEFAULT_V@)\nam__v_GEN_0 = @echo \"  GEN     \" $@;\nam__v_GEN_1 = \nAM_V_at = $(am__v_at_@AM_V@)\nam__v_at_ = $(am__v_at_@AM_DEFAULT_V@)\nam__v_at_0 = @\nam__v_at_1 = \nDEFAULT_INCLUDES = -I.@am__isrc@\ndepcomp = $(SHELL) $(top_srcdir)/build-aux/depcomp\nam__maybe_remake_depfiles = depfiles\nam__depfiles_remade = cplusplus/$(DEPDIR)/cudd_libcudd_la-cuddObj.Plo \\\n\tcplusplus/$(DEPDIR)/libobj_la-cuddObj.Plo \\\n\tcplusplus/$(DEPDIR)/testmulti-testmulti.Po \\\n\tcplusplus/$(DEPDIR)/testobj-testobj.Po \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAPI.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAddAbs.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAddApply.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAddFind.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAddInv.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAddIte.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAddNeg.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAddWalsh.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAndAbs.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddAnneal.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddApa.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddApprox.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddBddAbs.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddBddCorr.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddBddIte.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddBridge.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddCache.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddCheck.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddClip.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddCof.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddCompose.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddDecomp.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddEssent.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddExact.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddExport.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddGenCof.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddGenetic.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddGroup.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddHarwell.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddInit.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddInteract.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddLCache.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddLevelQ.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddLinear.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddLiteral.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddMatMult.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddPriority.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddRead.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddRef.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddReorder.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddSat.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddSign.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddSolve.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddSplit.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddSubsetHB.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddSubsetSP.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddSymmetry.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddTable.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddUtil.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddWindow.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddCount.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddFuncs.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddGroup.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddIsop.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddLin.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddMisc.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddPort.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddReord.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddSetop.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddSymm.Plo \\\n\tcudd/$(DEPDIR)/libcudd_la-cuddZddUtil.Plo \\\n\tcudd/$(DEPDIR)/testcudd-testcudd.Po \\\n\tcudd/$(DEPDIR)/testextra-testextra.Po \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpBinary.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpConvert.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpDbg.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoad.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoadCnf.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeAdd.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeBdd.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeCnf.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreAdd.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreBdd.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreCnf.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreMisc.Plo \\\n\tdddmp/$(DEPDIR)/cudd_libcudd_la-dddmpUtil.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpBinary.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpConvert.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpDbg.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpLoad.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpLoadCnf.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpNodeAdd.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpNodeBdd.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpNodeCnf.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpStoreAdd.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpStoreBdd.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpStoreCnf.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpStoreMisc.Plo \\\n\tdddmp/$(DEPDIR)/libdddmp_la-dddmpUtil.Plo \\\n\tdddmp/$(DEPDIR)/testdddmp-testdddmp.Po \\\n\tepd/$(DEPDIR)/cudd_libcudd_la-epd.Plo \\\n\tmtr/$(DEPDIR)/cudd_libcudd_la-mtrBasic.Plo \\\n\tmtr/$(DEPDIR)/cudd_libcudd_la-mtrGroup.Plo \\\n\tmtr/$(DEPDIR)/testmtr-testmtr.Po \\\n\tst/$(DEPDIR)/cudd_libcudd_la-st.Plo \\\n\tst/$(DEPDIR)/testst-testst.Po \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-cpu_stats.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-cpu_time.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-cstringstream.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-datalimit.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-pathsearch.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-pipefork.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-prtime.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-safe_mem.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-strsav.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-texpand.Plo \\\n\tutil/$(DEPDIR)/cudd_libcudd_la-ucbqsort.Plo\nam__mv = mv -f\nCOMPILE = $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) \\\n\t$(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS)\nLTCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \\\n\t$(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) \\\n\t$(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \\\n\t$(AM_CFLAGS) $(CFLAGS)\nAM_V_CC = $(am__v_CC_@AM_V@)\nam__v_CC_ = $(am__v_CC_@AM_DEFAULT_V@)\nam__v_CC_0 = @echo \"  CC      \" $@;\nam__v_CC_1 = \nCCLD = $(CC)\nLINK = $(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) \\\n\t$(LIBTOOLFLAGS) --mode=link $(CCLD) $(AM_CFLAGS) $(CFLAGS) \\\n\t$(AM_LDFLAGS) $(LDFLAGS) -o $@\nAM_V_CCLD = $(am__v_CCLD_@AM_V@)\nam__v_CCLD_ = $(am__v_CCLD_@AM_DEFAULT_V@)\nam__v_CCLD_0 = @echo \"  CCLD    \" $@;\nam__v_CCLD_1 = \nCXXCOMPILE = $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) \\\n\t$(AM_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS)\nLTCXXCOMPILE = $(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) \\\n\t$(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) \\\n\t$(DEFAULT_INCLUDES) $(INCLUDES) $(AM_CPPFLAGS) $(CPPFLAGS) \\\n\t$(AM_CXXFLAGS) $(CXXFLAGS)\nAM_V_CXX = $(am__v_CXX_@AM_V@)\nam__v_CXX_ = $(am__v_CXX_@AM_DEFAULT_V@)\nam__v_CXX_0 = @echo \"  CXX     \" $@;\nam__v_CXX_1 = \nCXXLD = $(CXX)\nCXXLINK = $(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) \\\n\t$(LIBTOOLFLAGS) --mode=link $(CXXLD) $(AM_CXXFLAGS) \\\n\t$(CXXFLAGS) $(AM_LDFLAGS) $(LDFLAGS) -o $@\nAM_V_CXXLD = $(am__v_CXXLD_@AM_V@)\nam__v_CXXLD_ = $(am__v_CXXLD_@AM_DEFAULT_V@)\nam__v_CXXLD_0 = @echo \"  CXXLD   \" $@;\nam__v_CXXLD_1 = \nSOURCES = $(cplusplus_libobj_la_SOURCES) $(cudd_libcudd_la_SOURCES) \\\n\t$(dddmp_libdddmp_la_SOURCES) $(cplusplus_testmulti_SOURCES) \\\n\t$(cplusplus_testobj_SOURCES) $(cudd_testcudd_SOURCES) \\\n\t$(cudd_testextra_SOURCES) $(dddmp_testdddmp_SOURCES) \\\n\t$(mtr_testmtr_SOURCES) $(st_testst_SOURCES)\nDIST_SOURCES = $(am__cplusplus_libobj_la_SOURCES_DIST) \\\n\t$(am__cudd_libcudd_la_SOURCES_DIST) \\\n\t$(am__dddmp_libdddmp_la_SOURCES_DIST) \\\n\t$(cplusplus_testmulti_SOURCES) $(cplusplus_testobj_SOURCES) \\\n\t$(cudd_testcudd_SOURCES) $(cudd_testextra_SOURCES) \\\n\t$(dddmp_testdddmp_SOURCES) $(mtr_testmtr_SOURCES) \\\n\t$(st_testst_SOURCES)\nam__can_run_installinfo = \\\n  case $$AM_UPDATE_INFO_DIR in \\\n    n|no|NO) false;; \\\n    *) (install-info --version) >/dev/null 2>&1;; \\\n  esac\nam__include_HEADERS_DIST = cudd/cudd.h dddmp/dddmp.h \\\n\tcplusplus/cuddObj.hh\nHEADERS = $(include_HEADERS)\nam__tagged_files = $(HEADERS) $(SOURCES) $(TAGS_FILES) $(LISP) \\\n\tconfig.h.in\n# Read a list of newline-separated strings from the standard input,\n# and print each of them once, without duplicates.  Input order is\n# *not* preserved.\nam__uniquify_input = $(AWK) '\\\n  BEGIN { nonempty = 0; } \\\n  { items[$$0] = 1; nonempty = 1; } \\\n  END { if (nonempty) { for (i in items) print i; }; } \\\n'\n# Make sure the list of sources is unique.  This is necessary because,\n# e.g., the same source file might be shared among _SOURCES variables\n# for different programs/libraries.\nam__define_uniq_tagged_files = \\\n  list='$(am__tagged_files)'; \\\n  unique=`for i in $$list; do \\\n    if test -f \"$$i\"; then echo $$i; else echo $(srcdir)/$$i; fi; \\\n  done | $(am__uniquify_input)`\nAM_RECURSIVE_TARGETS = cscope check recheck\nam__tty_colors_dummy = \\\n  mgn= red= grn= lgn= blu= brg= std=; \\\n  am__color_tests=no\nam__tty_colors = { \\\n  $(am__tty_colors_dummy); \\\n  if test \"X$(AM_COLOR_TESTS)\" = Xno; then \\\n    am__color_tests=no; \\\n  elif test \"X$(AM_COLOR_TESTS)\" = Xalways; then \\\n    am__color_tests=yes; \\\n  elif test \"X$$TERM\" != Xdumb && { test -t 1; } 2>/dev/null; then \\\n    am__color_tests=yes; \\\n  fi; \\\n  if test $$am__color_tests = yes; then \\\n    red='\u001b[0;31m'; \\\n    grn='\u001b[0;32m'; \\\n    lgn='\u001b[1;32m'; \\\n    blu='\u001b[1;34m'; \\\n    mgn='\u001b[0;35m'; \\\n    brg='\u001b[1m'; \\\n    std='\u001b[m'; \\\n  fi; \\\n}\nam__recheck_rx = ^[ \t]*:recheck:[ \t]*\nam__global_test_result_rx = ^[ \t]*:global-test-result:[ \t]*\nam__copy_in_global_log_rx = ^[ \t]*:copy-in-global-log:[ \t]*\n# A command that, given a newline-separated list of test names on the\n# standard input, print the name of the tests that are to be re-run\n# upon \"make recheck\".\nam__list_recheck_tests = $(AWK) '{ \\\n  recheck = 1; \\\n  while ((rc = (getline line < ($$0 \".trs\"))) != 0) \\\n    { \\\n      if (rc < 0) \\\n        { \\\n          if ((getline line2 < ($$0 \".log\")) < 0) \\\n\t    recheck = 0; \\\n          break; \\\n        } \\\n      else if (line ~ /$(am__recheck_rx)[nN][Oo]/) \\\n        { \\\n          recheck = 0; \\\n          break; \\\n        } \\\n      else if (line ~ /$(am__recheck_rx)[yY][eE][sS]/) \\\n        { \\\n          break; \\\n        } \\\n    }; \\\n  if (recheck) \\\n    print $$0; \\\n  close ($$0 \".trs\"); \\\n  close ($$0 \".log\"); \\\n}'\n# A command that, given a newline-separated list of test names on the\n# standard input, create the global log from their .trs and .log files.\nam__create_global_log = $(AWK) ' \\\nfunction fatal(msg) \\\n{ \\\n  print \"fatal: making $@: \" msg | \"cat >&2\"; \\\n  exit 1; \\\n} \\\nfunction rst_section(header) \\\n{ \\\n  print header; \\\n  len = length(header); \\\n  for (i = 1; i <= len; i = i + 1) \\\n    printf \"=\"; \\\n  printf \"\\n\\n\"; \\\n} \\\n{ \\\n  copy_in_global_log = 1; \\\n  global_test_result = \"RUN\"; \\\n  while ((rc = (getline line < ($$0 \".trs\"))) != 0) \\\n    { \\\n      if (rc < 0) \\\n         fatal(\"failed to read from \" $$0 \".trs\"); \\\n      if (line ~ /$(am__global_test_result_rx)/) \\\n        { \\\n          sub(\"$(am__global_test_result_rx)\", \"\", line); \\\n          sub(\"[ \t]*$$\", \"\", line); \\\n          global_test_result = line; \\\n        } \\\n      else if (line ~ /$(am__copy_in_global_log_rx)[nN][oO]/) \\\n        copy_in_global_log = 0; \\\n    }; \\\n  if (copy_in_global_log) \\\n    { \\\n      rst_section(global_test_result \": \" $$0); \\\n      while ((rc = (getline line < ($$0 \".log\"))) != 0) \\\n      { \\\n        if (rc < 0) \\\n          fatal(\"failed to read from \" $$0 \".log\"); \\\n        print line; \\\n      }; \\\n      printf \"\\n\"; \\\n    }; \\\n  close ($$0 \".trs\"); \\\n  close ($$0 \".log\"); \\\n}'\n# Restructured Text title.\nam__rst_title = { sed 's/.*/   &   /;h;s/./=/g;p;x;s/ *$$//;p;g' && echo; }\n# Solaris 10 'make', and several other traditional 'make' implementations,\n# pass \"-e\" to $(SHELL), and POSIX 2008 even requires this.  Work around it\n# by disabling -e (using the XSI extension \"set +e\") if it's set.\nam__sh_e_setup = case $$- in *e*) set +e;; esac\n# Default flags passed to test drivers.\nam__common_driver_flags = \\\n  --color-tests \"$$am__color_tests\" \\\n  --enable-hard-errors \"$$am__enable_hard_errors\" \\\n  --expect-failure \"$$am__expect_failure\"\n# To be inserted before the command running the test.  Creates the\n# directory for the log if needed.  Stores in $dir the directory\n# containing $f, in $tst the test, in $log the log.  Executes the\n# developer- defined test setup AM_TESTS_ENVIRONMENT (if any), and\n# passes TESTS_ENVIRONMENT.  Set up options for the wrapper that\n# will run the test scripts (or their associated LOG_COMPILER, if\n# thy have one).\nam__check_pre = \\\n$(am__sh_e_setup);\t\t\t\t\t\\\n$(am__vpath_adj_setup) $(am__vpath_adj)\t\t\t\\\n$(am__tty_colors);\t\t\t\t\t\\\nsrcdir=$(srcdir); export srcdir;\t\t\t\\\ncase \"$@\" in\t\t\t\t\t\t\\\n  */*) am__odir=`echo \"./$@\" | sed 's|/[^/]*$$||'`;;\t\\\n    *) am__odir=.;; \t\t\t\t\t\\\nesac;\t\t\t\t\t\t\t\\\ntest \"x$$am__odir\" = x\".\" || test -d \"$$am__odir\" \t\\\n  || $(MKDIR_P) \"$$am__odir\" || exit $$?;\t\t\\\nif test -f \"./$$f\"; then dir=./;\t\t\t\\\nelif test -f \"$$f\"; then dir=;\t\t\t\t\\\nelse dir=\"$(srcdir)/\"; fi;\t\t\t\t\\\ntst=$$dir$$f; log='$@'; \t\t\t\t\\\nif test -n '$(DISABLE_HARD_ERRORS)'; then\t\t\\\n  am__enable_hard_errors=no; \t\t\t\t\\\nelse\t\t\t\t\t\t\t\\\n  am__enable_hard_errors=yes; \t\t\t\t\\\nfi; \t\t\t\t\t\t\t\\\ncase \" $(XFAIL_TESTS) \" in\t\t\t\t\\\n  *[\\ \\\t]$$f[\\ \\\t]* | *[\\ \\\t]$$dir$$f[\\ \\\t]*) \\\n    am__expect_failure=yes;;\t\t\t\t\\\n  *)\t\t\t\t\t\t\t\\\n    am__expect_failure=no;;\t\t\t\t\\\nesac; \t\t\t\t\t\t\t\\\n$(AM_TESTS_ENVIRONMENT) $(TESTS_ENVIRONMENT)\n# A shell command to get the names of the tests scripts with any registered\n# extension removed (i.e., equivalently, the names of the test logs, with\n# the '.log' extension removed).  The result is saved in the shell variable\n# '$bases'.  This honors runtime overriding of TESTS and TEST_LOGS.  Sadly,\n# we cannot use something simpler, involving e.g., \"$(TEST_LOGS:.log=)\",\n# since that might cause problem with VPATH rewrites for suffix-less tests.\n# See also 'test-harness-vpath-rewrite.sh' and 'test-trs-basic.sh'.\nam__set_TESTS_bases = \\\n  bases='$(TEST_LOGS)'; \\\n  bases=`for i in $$bases; do echo $$i; done | sed 's/\\.log$$//'`; \\\n  bases=`echo $$bases`\nAM_TESTSUITE_SUMMARY_HEADER = ' for $(PACKAGE_STRING)'\nRECHECK_LOGS = $(TEST_LOGS)\nTEST_SUITE_LOG = test-suite.log\nTEST_EXTENSIONS = @EXEEXT@ .test\nam__test_logs1 = $(TESTS:=.log)\nam__test_logs2 = $(am__test_logs1:@EXEEXT@.log=.log)\nTEST_LOGS = $(am__test_logs2:.test.log=.log)\nTEST_LOG_COMPILE = $(TEST_LOG_COMPILER) $(AM_TEST_LOG_FLAGS) \\\n\t$(TEST_LOG_FLAGS)\nam__set_b = \\\n  case '$@' in \\\n    */*) \\\n      case '$*' in \\\n        */*) b='$*';; \\\n          *) b=`echo '$@' | sed 's/\\.log$$//'`; \\\n       esac;; \\\n    *) \\\n      b='$*';; \\\n  esac\nam__DIST_COMMON = $(srcdir)/Doxyfile.in $(srcdir)/Makefile.in \\\n\t$(srcdir)/config.h.in $(top_srcdir)/build-aux/ar-lib \\\n\t$(top_srcdir)/build-aux/compile \\\n\t$(top_srcdir)/build-aux/config.guess \\\n\t$(top_srcdir)/build-aux/config.sub \\\n\t$(top_srcdir)/build-aux/depcomp \\\n\t$(top_srcdir)/build-aux/install-sh \\\n\t$(top_srcdir)/build-aux/ltmain.sh \\\n\t$(top_srcdir)/build-aux/missing \\\n\t$(top_srcdir)/build-aux/tap-driver.sh \\\n\t$(top_srcdir)/cplusplus/Included.am \\\n\t$(top_srcdir)/cudd/Included.am $(top_srcdir)/dddmp/Included.am \\\n\t$(top_srcdir)/dddmp/exp/test1.sh.in \\\n\t$(top_srcdir)/dddmp/exp/test2.sh.in \\\n\t$(top_srcdir)/dddmp/exp/test3.sh.in \\\n\t$(top_srcdir)/dddmp/exp/test4.sh.in \\\n\t$(top_srcdir)/dddmp/exp/test5.sh.in \\\n\t$(top_srcdir)/dddmp/exp/test6.sh.in \\\n\t$(top_srcdir)/dddmp/exp/test7.sh.in \\\n\t$(top_srcdir)/doc/cudd.tex.in $(top_srcdir)/epd/Included.am \\\n\t$(top_srcdir)/mtr/Included.am $(top_srcdir)/st/Included.am \\\n\t$(top_srcdir)/util/Included.am README build-aux/ar-lib \\\n\tbuild-aux/compile build-aux/config.guess build-aux/config.sub \\\n\tbuild-aux/depcomp build-aux/install-sh build-aux/ltmain.sh \\\n\tbuild-aux/missing\nDISTFILES = $(DIST_COMMON) $(DIST_SOURCES) $(TEXINFOS) $(EXTRA_DIST)\ndistdir = $(PACKAGE)-$(VERSION)\ntop_distdir = $(distdir)\nam__remove_distdir = \\\n  if test -d \"$(distdir)\"; then \\\n    find \"$(distdir)\" -type d ! -perm -200 -exec chmod u+w {} ';' \\\n      && rm -rf \"$(distdir)\" \\\n      || { sleep 5 && rm -rf \"$(distdir)\"; }; \\\n  else :; fi\nam__post_remove_distdir = $(am__remove_distdir)\nDIST_ARCHIVES = $(distdir).tar.gz\nGZIP_ENV = --best\nDIST_TARGETS = dist-gzip\n# Exists only to be overridden by the user if desired.\nAM_DISTCHECK_DVI_TARGET = dvi\ndistuninstallcheck_listfiles = find . -type f -print\nam__distuninstallcheck_listfiles = $(distuninstallcheck_listfiles) \\\n  | sed 's|^\\./|$(prefix)/|' | grep -v '$(infodir)/dir$$'\ndistcleancheck_listfiles = find . -type f -print\nACLOCAL = @ACLOCAL@\nAMTAR = @AMTAR@\nAM_DEFAULT_VERBOSITY = @AM_DEFAULT_VERBOSITY@\nAR = @AR@\nAS = @AS@\nAUTOCONF = @AUTOCONF@\nAUTOHEADER = @AUTOHEADER@\nAUTOMAKE = @AUTOMAKE@\nAWK = @AWK@\nCC = @CC@\nCCDEPMODE = @CCDEPMODE@\nCFLAGS = @CFLAGS@\nCPPFLAGS = @CPPFLAGS@\nCSCOPE = @CSCOPE@\nCTAGS = @CTAGS@\nCXX = @CXX@\nCXXCPP = @CXXCPP@\nCXXDEPMODE = @CXXDEPMODE@\nCXXFLAGS = @CXXFLAGS@\nCYGPATH_W = @CYGPATH_W@\nDEFS = @DEFS@\nDEPDIR = @DEPDIR@\nDLLTOOL = @DLLTOOL@\nDOXYGEN = @DOXYGEN@\nDSYMUTIL = @DSYMUTIL@\nDUMPBIN = @DUMPBIN@\nECHO_C = @ECHO_C@\nECHO_N = @ECHO_N@\nECHO_T = @ECHO_T@\nEGREP = @EGREP@\nETAGS = @ETAGS@\nEXEEXT = @EXEEXT@\nFGREP = @FGREP@\nFILECMD = @FILECMD@\nGREP = @GREP@\nINSTALL = @INSTALL@\nINSTALL_DATA = @INSTALL_DATA@\nINSTALL_PROGRAM = @INSTALL_PROGRAM@\nINSTALL_SCRIPT = @INSTALL_SCRIPT@\nINSTALL_STRIP_PROGRAM = @INSTALL_STRIP_PROGRAM@\nLD = @LD@\nLDFLAGS = @LDFLAGS@\nLIBOBJS = @LIBOBJS@\nLIBS = @LIBS@\nLIBTOOL = @LIBTOOL@\nLIPO = @LIPO@\nLN_S = @LN_S@\nLTLIBOBJS = @LTLIBOBJS@\nLT_SYS_LIBRARY_PATH = @LT_SYS_LIBRARY_PATH@\nMAKEINDEX = @MAKEINDEX@\nMAKEINFO = @MAKEINFO@\nMANIFEST_TOOL = @MANIFEST_TOOL@\nMKDIR_P = @MKDIR_P@\nNM = @NM@\nNMEDIT = @NMEDIT@\nOBJDUMP = @OBJDUMP@\nOBJEXT = @OBJEXT@\nOTOOL = @OTOOL@\nOTOOL64 = @OTOOL64@\nPACKAGE = @PACKAGE@\nPACKAGE_BUGREPORT = @PACKAGE_BUGREPORT@\nPACKAGE_NAME = @PACKAGE_NAME@\nPACKAGE_STRING = @PACKAGE_STRING@\nPACKAGE_TARNAME = @PACKAGE_TARNAME@\nPACKAGE_URL = @PACKAGE_URL@\nPACKAGE_VERSION = @PACKAGE_VERSION@\nPATH_SEPARATOR = @PATH_SEPARATOR@\nPDFLATEX = @PDFLATEX@\nRANLIB = @RANLIB@\nSED = @SED@\nSET_MAKE = @SET_MAKE@\nSHELL = @SHELL@\nSTRIP = @STRIP@\nVERSION = @VERSION@\nabs_builddir = @abs_builddir@\nabs_srcdir = @abs_srcdir@\nabs_top_builddir = @abs_top_builddir@\nabs_top_srcdir = @abs_top_srcdir@\nac_ct_AR = @ac_ct_AR@\nac_ct_CC = @ac_ct_CC@\nac_ct_CXX = @ac_ct_CXX@\nac_ct_DUMPBIN = @ac_ct_DUMPBIN@\nam__include = @am__include@\nam__leading_dot = @am__leading_dot@\nam__quote = @am__quote@\nam__tar = @am__tar@\nam__untar = @am__untar@\nbindir = @bindir@\nbuild = @build@\nbuild_alias = @build_alias@\nbuild_cpu = @build_cpu@\nbuild_os = @build_os@\nbuild_vendor = @build_vendor@\nbuilddir = @builddir@\ndatadir = @datadir@\ndatarootdir = @datarootdir@\ndocdir = @docdir@\ndvidir = @dvidir@\nexec_prefix = @exec_prefix@\nhost = @host@\nhost_alias = @host_alias@\nhost_cpu = @host_cpu@\nhost_os = @host_os@\nhost_vendor = @host_vendor@\nhtmldir = @htmldir@\nincludedir = @includedir@\ninfodir = @infodir@\ninstall_sh = @install_sh@\nlibdir = @libdir@\nlibexecdir = @libexecdir@\nlocaledir = @localedir@\nlocalstatedir = @localstatedir@\nmandir = @mandir@\nmkdir_p = @mkdir_p@\noldincludedir = @oldincludedir@\npdfdir = @pdfdir@\nprefix = @prefix@\nprogram_transform_name = @program_transform_name@\npsdir = @psdir@\nrunstatedir = @runstatedir@\nsbindir = @sbindir@\nsharedstatedir = @sharedstatedir@\nsrcdir = @srcdir@\nsysconfdir = @sysconfdir@\ntarget_alias = @target_alias@\ntop_build_prefix = @top_build_prefix@\ntop_builddir = @top_builddir@\ntop_srcdir = @top_srcdir@\nACLOCAL_AMFLAGS = -I m4\ninclude_HEADERS = cudd/cudd.h $(am__append_1) $(am__append_2)\ncheck_SCRIPTS = cudd/test_cudd.test st/test_st.test mtr/test_mtr.test \\\n\tdddmp/test_dddmp.test cplusplus/test_obj.test\ndist_check_DATA = cudd/r7x8.1.mat cudd/r7x8.1.out cudd/extra.out \\\n\tmtr/test.groups mtr/test.out cplusplus/test.out \\\n\tcplusplus/multi.out\nEXTRA_DIST = README RELEASE.NOTES LICENSE groups.dox \\\n\tcudd/test_cudd.test.in st/test_st.test.in mtr/test_mtr.test.in \\\n\tdddmp/README.dddmp dddmp/README.testdddmp dddmp/RELEASE_NOTES \\\n\tdddmp/doc dddmp/test_dddmp.test.in dddmp/exp/test1.sh.in \\\n\tdddmp/exp/test2.sh.in dddmp/exp/test3.sh.in \\\n\tdddmp/exp/test4.sh.in dddmp/exp/test5.sh.in \\\n\tdddmp/exp/test6.sh.in dddmp/exp/test7.sh.in dddmp/exp/0.add \\\n\tdddmp/exp/0.bdd dddmp/exp/0or1.bdd dddmp/exp/1.add \\\n\tdddmp/exp/1.bdd dddmp/exp/2and3.bdd dddmp/exp/2.bdd \\\n\tdddmp/exp/3.bdd dddmp/exp/4.bdd dddmp/exp/4.bdd.bis1 \\\n\tdddmp/exp/4.bdd.bis2 dddmp/exp/4.bdd.bis3 dddmp/exp/4.bdd.bis4 \\\n\tdddmp/exp/4bis.bdd dddmp/exp/4.cnf dddmp/exp/4.cnf.bis \\\n\tdddmp/exp/4.max1 dddmp/exp/4.max2 dddmp/exp/4xor5.bdd \\\n\tdddmp/exp/5.bdd dddmp/exp/composeids.txt dddmp/exp/one.bdd \\\n\tdddmp/exp/s27deltaDddmp1.bdd dddmp/exp/s27deltaDddmp1.bdd.bis \\\n\tdddmp/exp/s27deltaDddmp2.bdd dddmp/exp/s27RP1.bdd \\\n\tdddmp/exp/varauxids.ord dddmp/exp/varnames.ord \\\n\tdddmp/exp/zero.bdd cplusplus/test_obj.test.in\nTESTS = $(am__append_3)\nCLEANFILES = cudd/r7x8.1.tst cudd/extra.tst mtr/test.tst \\\n\tdddmp/exp/test1.sh dddmp/exp/test2.sh dddmp/exp/test3.sh \\\n\tdddmp/exp/test4.sh dddmp/exp/test5.sh dddmp/exp/test6.sh \\\n\tdddmp/exp/test7.sh cplusplus/test.tst cplusplus/multi.tst \\\n\t$(check_SCRIPTS)\nnoinst_LTLIBRARIES = $(am__append_5) $(am__append_7)\nTEST_LOG_DRIVER = env AM_TAP_AWK='$(AWK)' $(SHELL) \\\n  $(top_srcdir)/build-aux/tap-driver.sh\n\ndo_subst = sed \\\n  -e 's,[@]EXEEXT[@],$(EXEEXT),g' \\\n  -e 's,[@]srcdir[@],$(srcdir),g'\n\nlib_LTLIBRARIES = cudd/libcudd.la\ncudd_libcudd_la_SOURCES = cudd/cudd.h cudd/cuddInt.h cudd/cuddAddAbs.c \\\n\tcudd/cuddAddApply.c cudd/cuddAddFind.c cudd/cuddAddInv.c \\\n\tcudd/cuddAddIte.c cudd/cuddAddNeg.c cudd/cuddAddWalsh.c \\\n\tcudd/cuddAndAbs.c cudd/cuddAnneal.c cudd/cuddApa.c \\\n\tcudd/cuddAPI.c cudd/cuddApprox.c cudd/cuddBddAbs.c \\\n\tcudd/cuddBddCorr.c cudd/cuddBddIte.c cudd/cuddBridge.c \\\n\tcudd/cuddCache.c cudd/cuddCheck.c cudd/cuddClip.c \\\n\tcudd/cuddCof.c cudd/cuddCompose.c cudd/cuddDecomp.c \\\n\tcudd/cuddEssent.c cudd/cuddExact.c cudd/cuddExport.c \\\n\tcudd/cuddGenCof.c cudd/cuddGenetic.c cudd/cuddGroup.c \\\n\tcudd/cuddHarwell.c cudd/cuddInit.c cudd/cuddInteract.c \\\n\tcudd/cuddLCache.c cudd/cuddLevelQ.c cudd/cuddLinear.c \\\n\tcudd/cuddLiteral.c cudd/cuddMatMult.c cudd/cuddPriority.c \\\n\tcudd/cuddRead.c cudd/cuddRef.c cudd/cuddReorder.c \\\n\tcudd/cuddSat.c cudd/cuddSign.c cudd/cuddSolve.c \\\n\tcudd/cuddSplit.c cudd/cuddSubsetHB.c cudd/cuddSubsetSP.c \\\n\tcudd/cuddSymmetry.c cudd/cuddTable.c cudd/cuddUtil.c \\\n\tcudd/cuddWindow.c cudd/cuddZddCount.c cudd/cuddZddFuncs.c \\\n\tcudd/cuddZddGroup.c cudd/cuddZddIsop.c cudd/cuddZddLin.c \\\n\tcudd/cuddZddMisc.c cudd/cuddZddPort.c cudd/cuddZddReord.c \\\n\tcudd/cuddZddSetop.c cudd/cuddZddSymm.c cudd/cuddZddUtil.c \\\n\tutil/util.h util/cstringstream.h util/cpu_stats.c \\\n\tutil/cpu_time.c util/cstringstream.c util/datalimit.c \\\n\tutil/pathsearch.c util/pipefork.c util/prtime.c \\\n\tutil/safe_mem.c util/strsav.c util/texpand.c util/ucbqsort.c \\\n\tst/st.h st/st.c epd/epd.c epd/epdInt.h epd/epd.h mtr/mtr.h \\\n\tmtr/mtrInt.h mtr/mtrBasic.c mtr/mtrGroup.c $(am__append_4) \\\n\t$(am__append_6)\ncudd_libcudd_la_CPPFLAGS = -I$(top_srcdir)/cudd -I$(top_srcdir)/st \\\n  -I$(top_srcdir)/epd -I$(top_srcdir)/mtr -I$(top_srcdir)/util\n\n@OBJ_TRUE@cudd_libcudd_la_LIBTOOLFLAGS = --tag=CXX\ncudd_libcudd_la_LDFLAGS = -release @PACKAGE_VERSION@ -version-info 0:0:0 \\\n  -no-undefined\n\ncudd_testcudd_SOURCES = cudd/testcudd.c\ncudd_testcudd_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\ncudd_testcudd_LDADD = cudd/libcudd.la\ncudd_testextra_SOURCES = cudd/testextra.c\ncudd_testextra_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\ncudd_testextra_LDADD = cudd/libcudd.la\n@CROSS_COMPILING_TRUE@@MINGW64_TRUE@cudd_libcudd_la_LIBADD = -lws2_32 -lpsapi\nst_testst_SOURCES = st/testst.c\nst_testst_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\nst_testst_LDADD = cudd/libcudd.la\nmtr_testmtr_SOURCES = mtr/testmtr.c\nmtr_testmtr_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\nmtr_testmtr_LDADD = cudd/libcudd.la\ndddmp_sources = dddmp/dddmp.h dddmp/dddmpInt.h \\\n  dddmp/dddmpBinary.c dddmp/dddmpConvert.c dddmp/dddmpDbg.c \\\n  dddmp/dddmpLoad.c dddmp/dddmpLoadCnf.c dddmp/dddmpNodeAdd.c \\\n  dddmp/dddmpNodeBdd.c dddmp/dddmpNodeCnf.c dddmp/dddmpStoreAdd.c \\\n  dddmp/dddmpStoreBdd.c dddmp/dddmpStoreCnf.c dddmp/dddmpStoreMisc.c \\\n  dddmp/dddmpUtil.c\n\n@DDDMP_FALSE@dddmp_libdddmp_la_SOURCES = $(dddmp_sources)\n@DDDMP_FALSE@dddmp_libdddmp_la_CPPFLAGS = -I$(top_srcdir)/util -I$(top_srcdir)/mtr \\\n@DDDMP_FALSE@  -I$(top_srcdir)/epd -I$(top_srcdir)/cudd -I$(top_srcdir)/st\n\ndddmp_testdddmp_SOURCES = dddmp/testdddmp.c\n@DDDMP_FALSE@dddmp_testdddmp_CPPFLAGS = $(dddmp_libdddmp_la_CPPFLAGS)\n@DDDMP_TRUE@dddmp_testdddmp_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\n@DDDMP_FALSE@dddmp_testdddmp_LDADD = dddmp/libdddmp.la cudd/libcudd.la\n@DDDMP_TRUE@dddmp_testdddmp_LDADD = cudd/libcudd.la\ncplusplus_sources = cplusplus/cuddObj.hh cplusplus/cuddObj.cc\n@OBJ_FALSE@cplusplus_libobj_la_SOURCES = $(cplusplus_sources)\n@OBJ_FALSE@cplusplus_libobj_la_CPPFLAGS = -I$(top_srcdir)/cudd -I$(top_srcdir)/mtr \\\n@OBJ_FALSE@  -I$(top_srcdir)/epd -I$(top_srcdir)/st\n\ncplusplus_testobj_SOURCES = cplusplus/testobj.cc\n@OBJ_FALSE@cplusplus_testobj_CPPFLAGS = $(cplusplus_libobj_la_CPPFLAGS)\n@OBJ_TRUE@cplusplus_testobj_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\n@OBJ_FALSE@cplusplus_testobj_LDADD = cplusplus/libobj.la \\\n@OBJ_FALSE@\tcudd/libcudd.la\n@OBJ_TRUE@cplusplus_testobj_LDADD = cudd/libcudd.la\ncplusplus_testmulti_SOURCES = cplusplus/testmulti.cc\n@OBJ_FALSE@cplusplus_testmulti_CPPFLAGS = $(cplusplus_libobj_la_CPPFLAGS)\n@OBJ_TRUE@cplusplus_testmulti_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\n@OBJ_FALSE@cplusplus_testmulti_LDADD = cplusplus/libobj.la \\\n@OBJ_FALSE@\tcudd/libcudd.la\n@OBJ_TRUE@cplusplus_testmulti_LDADD = cudd/libcudd.la\n@HAVE_PTHREADS_TRUE@cplusplus_testmulti_LDFLAGS = -pthread\nall: config.h\n\t$(MAKE) $(AM_MAKEFLAGS) all-am\n\n.SUFFIXES:\n.SUFFIXES: .c .cc .lo .log .o .obj .test .test$(EXEEXT) .trs\nam--refresh: Makefile\n\t@:\n$(srcdir)/Makefile.in:  $(srcdir)/Makefile.am $(top_srcdir)/cudd/Included.am $(top_srcdir)/util/Included.am $(top_srcdir)/st/Included.am $(top_srcdir)/epd/Included.am $(top_srcdir)/mtr/Included.am $(top_srcdir)/dddmp/Included.am $(top_srcdir)/cplusplus/Included.am $(am__configure_deps)\n\t@for dep in $?; do \\\n\t  case '$(am__configure_deps)' in \\\n\t    *$$dep*) \\\n\t      echo ' cd $(srcdir) && $(AUTOMAKE) --foreign'; \\\n\t      $(am__cd) $(srcdir) && $(AUTOMAKE) --foreign \\\n\t\t&& exit 0; \\\n\t      exit 1;; \\\n\t  esac; \\\n\tdone; \\\n\techo ' cd $(top_srcdir) && $(AUTOMAKE) --foreign Makefile'; \\\n\t$(am__cd) $(top_srcdir) && \\\n\t  $(AUTOMAKE) --foreign Makefile\nMakefile: $(srcdir)/Makefile.in $(top_builddir)/config.status\n\t@case '$?' in \\\n\t  *config.status*) \\\n\t    echo ' $(SHELL) ./config.status'; \\\n\t    $(SHELL) ./config.status;; \\\n\t  *) \\\n\t    echo ' cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__maybe_remake_depfiles)'; \\\n\t    cd $(top_builddir) && $(SHELL) ./config.status $@ $(am__maybe_remake_depfiles);; \\\n\tesac;\n$(top_srcdir)/cudd/Included.am $(top_srcdir)/util/Included.am $(top_srcdir)/st/Included.am $(top_srcdir)/epd/Included.am $(top_srcdir)/mtr/Included.am $(top_srcdir)/dddmp/Included.am $(top_srcdir)/cplusplus/Included.am $(am__empty):\n\n$(top_builddir)/config.status: $(top_srcdir)/configure $(CONFIG_STATUS_DEPENDENCIES)\n\t$(SHELL) ./config.status --recheck\n\n$(top_srcdir)/configure:  $(am__configure_deps)\n\t$(am__cd) $(srcdir) && $(AUTOCONF)\n$(ACLOCAL_M4):  $(am__aclocal_m4_deps)\n\t$(am__cd) $(srcdir) && $(ACLOCAL) $(ACLOCAL_AMFLAGS)\n$(am__aclocal_m4_deps):\n\nconfig.h: stamp-h1\n\t@test -f $@ || rm -f stamp-h1\n\t@test -f $@ || $(MAKE) $(AM_MAKEFLAGS) stamp-h1\n\nstamp-h1: $(srcdir)/config.h.in $(top_builddir)/config.status\n\t@rm -f stamp-h1\n\tcd $(top_builddir) && $(SHELL) ./config.status config.h\n$(srcdir)/config.h.in:  $(am__configure_deps) \n\t($(am__cd) $(top_srcdir) && $(AUTOHEADER))\n\trm -f stamp-h1\n\ttouch $@\n\ndistclean-hdr:\n\t-rm -f config.h stamp-h1\n@HAVE_DOXYGEN_TRUE@Doxyfile: $(top_builddir)/config.status $(srcdir)/Doxyfile.in\n@HAVE_DOXYGEN_TRUE@\tcd $(top_builddir) && $(SHELL) ./config.status $@\n@HAVE_PDFLATEX_TRUE@doc/cudd.tex: $(top_builddir)/config.status $(top_srcdir)/doc/cudd.tex.in\n@HAVE_PDFLATEX_TRUE@\tcd $(top_builddir) && $(SHELL) ./config.status $@\ndddmp/exp/test1.sh: $(top_builddir)/config.status $(top_srcdir)/dddmp/exp/test1.sh.in\n\tcd $(top_builddir) && $(SHELL) ./config.status $@\ndddmp/exp/test2.sh: $(top_builddir)/config.status $(top_srcdir)/dddmp/exp/test2.sh.in\n\tcd $(top_builddir) && $(SHELL) ./config.status $@\ndddmp/exp/test3.sh: $(top_builddir)/config.status $(top_srcdir)/dddmp/exp/test3.sh.in\n\tcd $(top_builddir) && $(SHELL) ./config.status $@\ndddmp/exp/test4.sh: $(top_builddir)/config.status $(top_srcdir)/dddmp/exp/test4.sh.in\n\tcd $(top_builddir) && $(SHELL) ./config.status $@\ndddmp/exp/test5.sh: $(top_builddir)/config.status $(top_srcdir)/dddmp/exp/test5.sh.in\n\tcd $(top_builddir) && $(SHELL) ./config.status $@\ndddmp/exp/test6.sh: $(top_builddir)/config.status $(top_srcdir)/dddmp/exp/test6.sh.in\n\tcd $(top_builddir) && $(SHELL) ./config.status $@\ndddmp/exp/test7.sh: $(top_builddir)/config.status $(top_srcdir)/dddmp/exp/test7.sh.in\n\tcd $(top_builddir) && $(SHELL) ./config.status $@\n\nclean-checkPROGRAMS:\n\t@list='$(check_PROGRAMS)'; test -n \"$$list\" || exit 0; \\\n\techo \" rm -f\" $$list; \\\n\trm -f $$list || exit $$?; \\\n\ttest -n \"$(EXEEXT)\" || exit 0; \\\n\tlist=`for p in $$list; do echo \"$$p\"; done | sed 's/$(EXEEXT)$$//'`; \\\n\techo \" rm -f\" $$list; \\\n\trm -f $$list\n\ninstall-libLTLIBRARIES: $(lib_LTLIBRARIES)\n\t@$(NORMAL_INSTALL)\n\t@list='$(lib_LTLIBRARIES)'; test -n \"$(libdir)\" || list=; \\\n\tlist2=; for p in $$list; do \\\n\t  if test -f $$p; then \\\n\t    list2=\"$$list2 $$p\"; \\\n\t  else :; fi; \\\n\tdone; \\\n\ttest -z \"$$list2\" || { \\\n\t  echo \" $(MKDIR_P) '$(DESTDIR)$(libdir)'\"; \\\n\t  $(MKDIR_P) \"$(DESTDIR)$(libdir)\" || exit 1; \\\n\t  echo \" $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 '$(DESTDIR)$(libdir)'\"; \\\n\t  $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=install $(INSTALL) $(INSTALL_STRIP_FLAG) $$list2 \"$(DESTDIR)$(libdir)\"; \\\n\t}\n\nuninstall-libLTLIBRARIES:\n\t@$(NORMAL_UNINSTALL)\n\t@list='$(lib_LTLIBRARIES)'; test -n \"$(libdir)\" || list=; \\\n\tfor p in $$list; do \\\n\t  $(am__strip_dir) \\\n\t  echo \" $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f '$(DESTDIR)$(libdir)/$$f'\"; \\\n\t  $(LIBTOOL) $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=uninstall rm -f \"$(DESTDIR)$(libdir)/$$f\"; \\\n\tdone\n\nclean-libLTLIBRARIES:\n\t-test -z \"$(lib_LTLIBRARIES)\" || rm -f $(lib_LTLIBRARIES)\n\t@list='$(lib_LTLIBRARIES)'; \\\n\tlocs=`for p in $$list; do echo $$p; done | \\\n\t      sed 's|^[^/]*$$|.|; s|/[^/]*$$||; s|$$|/so_locations|' | \\\n\t      sort -u`; \\\n\ttest -z \"$$locs\" || { \\\n\t  echo rm -f $${locs}; \\\n\t  rm -f $${locs}; \\\n\t}\n\nclean-noinstLTLIBRARIES:\n\t-test -z \"$(noinst_LTLIBRARIES)\" || rm -f $(noinst_LTLIBRARIES)\n\t@list='$(noinst_LTLIBRARIES)'; \\\n\tlocs=`for p in $$list; do echo $$p; done | \\\n\t      sed 's|^[^/]*$$|.|; s|/[^/]*$$||; s|$$|/so_locations|' | \\\n\t      sort -u`; \\\n\ttest -z \"$$locs\" || { \\\n\t  echo rm -f $${locs}; \\\n\t  rm -f $${locs}; \\\n\t}\ncplusplus/$(am__dirstamp):\n\t@$(MKDIR_P) cplusplus\n\t@: > cplusplus/$(am__dirstamp)\ncplusplus/$(DEPDIR)/$(am__dirstamp):\n\t@$(MKDIR_P) cplusplus/$(DEPDIR)\n\t@: > cplusplus/$(DEPDIR)/$(am__dirstamp)\ncplusplus/libobj_la-cuddObj.lo: cplusplus/$(am__dirstamp) \\\n\tcplusplus/$(DEPDIR)/$(am__dirstamp)\n\ncplusplus/libobj.la: $(cplusplus_libobj_la_OBJECTS) $(cplusplus_libobj_la_DEPENDENCIES) $(EXTRA_cplusplus_libobj_la_DEPENDENCIES) cplusplus/$(am__dirstamp)\n\t$(AM_V_CXXLD)$(CXXLINK) $(am_cplusplus_libobj_la_rpath) $(cplusplus_libobj_la_OBJECTS) $(cplusplus_libobj_la_LIBADD) $(LIBS)\ncudd/$(am__dirstamp):\n\t@$(MKDIR_P) cudd\n\t@: > cudd/$(am__dirstamp)\ncudd/$(DEPDIR)/$(am__dirstamp):\n\t@$(MKDIR_P) cudd/$(DEPDIR)\n\t@: > cudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAddAbs.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAddApply.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAddFind.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAddInv.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAddIte.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAddNeg.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAddWalsh.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAndAbs.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAnneal.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddApa.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddAPI.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddApprox.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddBddAbs.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddBddCorr.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddBddIte.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddBridge.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddCache.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddCheck.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddClip.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddCof.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddCompose.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddDecomp.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddEssent.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddExact.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddExport.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddGenCof.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddGenetic.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddGroup.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddHarwell.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddInit.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddInteract.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddLCache.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddLevelQ.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddLinear.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddLiteral.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddMatMult.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddPriority.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddRead.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddRef.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddReorder.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddSat.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddSign.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddSolve.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddSplit.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddSubsetHB.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddSubsetSP.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddSymmetry.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddTable.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddUtil.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddWindow.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddCount.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddFuncs.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddGroup.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddIsop.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddLin.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddMisc.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddPort.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddReord.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddSetop.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddSymm.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\ncudd/libcudd_la-cuddZddUtil.lo: cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\nutil/$(am__dirstamp):\n\t@$(MKDIR_P) util\n\t@: > util/$(am__dirstamp)\nutil/$(DEPDIR)/$(am__dirstamp):\n\t@$(MKDIR_P) util/$(DEPDIR)\n\t@: > util/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-cpu_stats.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-cpu_time.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-cstringstream.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-datalimit.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-pathsearch.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-pipefork.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-prtime.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-safe_mem.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-strsav.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-texpand.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nutil/cudd_libcudd_la-ucbqsort.lo: util/$(am__dirstamp) \\\n\tutil/$(DEPDIR)/$(am__dirstamp)\nst/$(am__dirstamp):\n\t@$(MKDIR_P) st\n\t@: > st/$(am__dirstamp)\nst/$(DEPDIR)/$(am__dirstamp):\n\t@$(MKDIR_P) st/$(DEPDIR)\n\t@: > st/$(DEPDIR)/$(am__dirstamp)\nst/cudd_libcudd_la-st.lo: st/$(am__dirstamp) \\\n\tst/$(DEPDIR)/$(am__dirstamp)\nepd/$(am__dirstamp):\n\t@$(MKDIR_P) epd\n\t@: > epd/$(am__dirstamp)\nepd/$(DEPDIR)/$(am__dirstamp):\n\t@$(MKDIR_P) epd/$(DEPDIR)\n\t@: > epd/$(DEPDIR)/$(am__dirstamp)\nepd/cudd_libcudd_la-epd.lo: epd/$(am__dirstamp) \\\n\tepd/$(DEPDIR)/$(am__dirstamp)\nmtr/$(am__dirstamp):\n\t@$(MKDIR_P) mtr\n\t@: > mtr/$(am__dirstamp)\nmtr/$(DEPDIR)/$(am__dirstamp):\n\t@$(MKDIR_P) mtr/$(DEPDIR)\n\t@: > mtr/$(DEPDIR)/$(am__dirstamp)\nmtr/cudd_libcudd_la-mtrBasic.lo: mtr/$(am__dirstamp) \\\n\tmtr/$(DEPDIR)/$(am__dirstamp)\nmtr/cudd_libcudd_la-mtrGroup.lo: mtr/$(am__dirstamp) \\\n\tmtr/$(DEPDIR)/$(am__dirstamp)\ndddmp/$(am__dirstamp):\n\t@$(MKDIR_P) dddmp\n\t@: > dddmp/$(am__dirstamp)\ndddmp/$(DEPDIR)/$(am__dirstamp):\n\t@$(MKDIR_P) dddmp/$(DEPDIR)\n\t@: > dddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpBinary.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpConvert.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpDbg.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpLoad.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpLoadCnf.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpNodeAdd.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpNodeBdd.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpNodeCnf.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpStoreAdd.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpStoreBdd.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpStoreCnf.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpStoreMisc.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/cudd_libcudd_la-dddmpUtil.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ncplusplus/cudd_libcudd_la-cuddObj.lo: cplusplus/$(am__dirstamp) \\\n\tcplusplus/$(DEPDIR)/$(am__dirstamp)\n\ncudd/libcudd.la: $(cudd_libcudd_la_OBJECTS) $(cudd_libcudd_la_DEPENDENCIES) $(EXTRA_cudd_libcudd_la_DEPENDENCIES) cudd/$(am__dirstamp)\n\t$(AM_V_CXXLD)$(cudd_libcudd_la_LINK) -rpath $(libdir) $(cudd_libcudd_la_OBJECTS) $(cudd_libcudd_la_LIBADD) $(LIBS)\ndddmp/libdddmp_la-dddmpBinary.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpConvert.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpDbg.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpLoad.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpLoadCnf.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpNodeAdd.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpNodeBdd.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpNodeCnf.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpStoreAdd.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpStoreBdd.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpStoreCnf.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpStoreMisc.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\ndddmp/libdddmp_la-dddmpUtil.lo: dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\n\ndddmp/libdddmp.la: $(dddmp_libdddmp_la_OBJECTS) $(dddmp_libdddmp_la_DEPENDENCIES) $(EXTRA_dddmp_libdddmp_la_DEPENDENCIES) dddmp/$(am__dirstamp)\n\t$(AM_V_CCLD)$(LINK) $(am_dddmp_libdddmp_la_rpath) $(dddmp_libdddmp_la_OBJECTS) $(dddmp_libdddmp_la_LIBADD) $(LIBS)\ncplusplus/testmulti-testmulti.$(OBJEXT): cplusplus/$(am__dirstamp) \\\n\tcplusplus/$(DEPDIR)/$(am__dirstamp)\n\ncplusplus/testmulti$(EXEEXT): $(cplusplus_testmulti_OBJECTS) $(cplusplus_testmulti_DEPENDENCIES) $(EXTRA_cplusplus_testmulti_DEPENDENCIES) cplusplus/$(am__dirstamp)\n\t@rm -f cplusplus/testmulti$(EXEEXT)\n\t$(AM_V_CXXLD)$(cplusplus_testmulti_LINK) $(cplusplus_testmulti_OBJECTS) $(cplusplus_testmulti_LDADD) $(LIBS)\ncplusplus/testobj-testobj.$(OBJEXT): cplusplus/$(am__dirstamp) \\\n\tcplusplus/$(DEPDIR)/$(am__dirstamp)\n\ncplusplus/testobj$(EXEEXT): $(cplusplus_testobj_OBJECTS) $(cplusplus_testobj_DEPENDENCIES) $(EXTRA_cplusplus_testobj_DEPENDENCIES) cplusplus/$(am__dirstamp)\n\t@rm -f cplusplus/testobj$(EXEEXT)\n\t$(AM_V_CXXLD)$(CXXLINK) $(cplusplus_testobj_OBJECTS) $(cplusplus_testobj_LDADD) $(LIBS)\ncudd/testcudd-testcudd.$(OBJEXT): cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\n\ncudd/testcudd$(EXEEXT): $(cudd_testcudd_OBJECTS) $(cudd_testcudd_DEPENDENCIES) $(EXTRA_cudd_testcudd_DEPENDENCIES) cudd/$(am__dirstamp)\n\t@rm -f cudd/testcudd$(EXEEXT)\n\t$(AM_V_CCLD)$(LINK) $(cudd_testcudd_OBJECTS) $(cudd_testcudd_LDADD) $(LIBS)\ncudd/testextra-testextra.$(OBJEXT): cudd/$(am__dirstamp) \\\n\tcudd/$(DEPDIR)/$(am__dirstamp)\n\ncudd/testextra$(EXEEXT): $(cudd_testextra_OBJECTS) $(cudd_testextra_DEPENDENCIES) $(EXTRA_cudd_testextra_DEPENDENCIES) cudd/$(am__dirstamp)\n\t@rm -f cudd/testextra$(EXEEXT)\n\t$(AM_V_CCLD)$(LINK) $(cudd_testextra_OBJECTS) $(cudd_testextra_LDADD) $(LIBS)\ndddmp/testdddmp-testdddmp.$(OBJEXT): dddmp/$(am__dirstamp) \\\n\tdddmp/$(DEPDIR)/$(am__dirstamp)\n\ndddmp/testdddmp$(EXEEXT): $(dddmp_testdddmp_OBJECTS) $(dddmp_testdddmp_DEPENDENCIES) $(EXTRA_dddmp_testdddmp_DEPENDENCIES) dddmp/$(am__dirstamp)\n\t@rm -f dddmp/testdddmp$(EXEEXT)\n\t$(AM_V_CCLD)$(LINK) $(dddmp_testdddmp_OBJECTS) $(dddmp_testdddmp_LDADD) $(LIBS)\nmtr/testmtr-testmtr.$(OBJEXT): mtr/$(am__dirstamp) \\\n\tmtr/$(DEPDIR)/$(am__dirstamp)\n\nmtr/testmtr$(EXEEXT): $(mtr_testmtr_OBJECTS) $(mtr_testmtr_DEPENDENCIES) $(EXTRA_mtr_testmtr_DEPENDENCIES) mtr/$(am__dirstamp)\n\t@rm -f mtr/testmtr$(EXEEXT)\n\t$(AM_V_CCLD)$(LINK) $(mtr_testmtr_OBJECTS) $(mtr_testmtr_LDADD) $(LIBS)\nst/testst-testst.$(OBJEXT): st/$(am__dirstamp) \\\n\tst/$(DEPDIR)/$(am__dirstamp)\n\nst/testst$(EXEEXT): $(st_testst_OBJECTS) $(st_testst_DEPENDENCIES) $(EXTRA_st_testst_DEPENDENCIES) st/$(am__dirstamp)\n\t@rm -f st/testst$(EXEEXT)\n\t$(AM_V_CCLD)$(LINK) $(st_testst_OBJECTS) $(st_testst_LDADD) $(LIBS)\n\nmostlyclean-compile:\n\t-rm -f *.$(OBJEXT)\n\t-rm -f cplusplus/*.$(OBJEXT)\n\t-rm -f cplusplus/*.lo\n\t-rm -f cudd/*.$(OBJEXT)\n\t-rm -f cudd/*.lo\n\t-rm -f dddmp/*.$(OBJEXT)\n\t-rm -f dddmp/*.lo\n\t-rm -f epd/*.$(OBJEXT)\n\t-rm -f epd/*.lo\n\t-rm -f mtr/*.$(OBJEXT)\n\t-rm -f mtr/*.lo\n\t-rm -f st/*.$(OBJEXT)\n\t-rm -f st/*.lo\n\t-rm -f util/*.$(OBJEXT)\n\t-rm -f util/*.lo\n\ndistclean-compile:\n\t-rm -f *.tab.c\n\n@AMDEP_TRUE@@am__include@ @am__quote@cplusplus/$(DEPDIR)/cudd_libcudd_la-cuddObj.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cplusplus/$(DEPDIR)/libobj_la-cuddObj.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cplusplus/$(DEPDIR)/testmulti-testmulti.Po@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cplusplus/$(DEPDIR)/testobj-testobj.Po@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAPI.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAddAbs.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAddApply.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAddFind.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAddInv.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAddIte.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAddNeg.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAddWalsh.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAndAbs.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddAnneal.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddApa.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddApprox.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddBddAbs.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddBddCorr.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddBddIte.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddBridge.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddCache.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddCheck.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddClip.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddCof.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddCompose.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddDecomp.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddEssent.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddExact.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddExport.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddGenCof.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddGenetic.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddGroup.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddHarwell.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddInit.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddInteract.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddLCache.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddLevelQ.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddLinear.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddLiteral.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddMatMult.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddPriority.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddRead.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddRef.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddReorder.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddSat.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddSign.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddSolve.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddSplit.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddSubsetHB.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddSubsetSP.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddSymmetry.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddTable.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddUtil.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddWindow.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddCount.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddFuncs.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddGroup.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddIsop.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddLin.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddMisc.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddPort.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddReord.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddSetop.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddSymm.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/libcudd_la-cuddZddUtil.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/testcudd-testcudd.Po@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@cudd/$(DEPDIR)/testextra-testextra.Po@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpBinary.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpConvert.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpDbg.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoad.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoadCnf.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeAdd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeBdd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeCnf.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreAdd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreBdd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreCnf.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreMisc.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpUtil.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpBinary.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpConvert.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpDbg.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpLoad.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpLoadCnf.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeAdd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeBdd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeCnf.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreAdd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreBdd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreCnf.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreMisc.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/libdddmp_la-dddmpUtil.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@dddmp/$(DEPDIR)/testdddmp-testdddmp.Po@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@epd/$(DEPDIR)/cudd_libcudd_la-epd.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@mtr/$(DEPDIR)/cudd_libcudd_la-mtrBasic.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@mtr/$(DEPDIR)/cudd_libcudd_la-mtrGroup.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@mtr/$(DEPDIR)/testmtr-testmtr.Po@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@st/$(DEPDIR)/cudd_libcudd_la-st.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@st/$(DEPDIR)/testst-testst.Po@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-cpu_stats.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-cpu_time.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-cstringstream.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-datalimit.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-pathsearch.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-pipefork.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-prtime.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-safe_mem.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-strsav.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-texpand.Plo@am__quote@ # am--include-marker\n@AMDEP_TRUE@@am__include@ @am__quote@util/$(DEPDIR)/cudd_libcudd_la-ucbqsort.Plo@am__quote@ # am--include-marker\n\n$(am__depfiles_remade):\n\t@$(MKDIR_P) $(@D)\n\t@echo '# dummy' >$@-t && $(am__mv) $@-t $@\n\nam--depfiles: $(am__depfiles_remade)\n\n.c.o:\n@am__fastdepCC_TRUE@\t$(AM_V_CC)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\\.o$$||'`;\\\n@am__fastdepCC_TRUE@\t$(COMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ $< &&\\\n@am__fastdepCC_TRUE@\t$(am__mv) $$depbase.Tpo $$depbase.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ $<\n\n.c.obj:\n@am__fastdepCC_TRUE@\t$(AM_V_CC)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\\.obj$$||'`;\\\n@am__fastdepCC_TRUE@\t$(COMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ `$(CYGPATH_W) '$<'` &&\\\n@am__fastdepCC_TRUE@\t$(am__mv) $$depbase.Tpo $$depbase.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(COMPILE) -c -o $@ `$(CYGPATH_W) '$<'`\n\n.c.lo:\n@am__fastdepCC_TRUE@\t$(AM_V_CC)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\\.lo$$||'`;\\\n@am__fastdepCC_TRUE@\t$(LTCOMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ $< &&\\\n@am__fastdepCC_TRUE@\t$(am__mv) $$depbase.Tpo $$depbase.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LTCOMPILE) -c -o $@ $<\n\ncudd/libcudd_la-cuddAddAbs.lo: cudd/cuddAddAbs.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAddAbs.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAddAbs.Tpo -c -o cudd/libcudd_la-cuddAddAbs.lo `test -f 'cudd/cuddAddAbs.c' || echo '$(srcdir)/'`cudd/cuddAddAbs.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAddAbs.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAddAbs.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAddAbs.c' object='cudd/libcudd_la-cuddAddAbs.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAddAbs.lo `test -f 'cudd/cuddAddAbs.c' || echo '$(srcdir)/'`cudd/cuddAddAbs.c\n\ncudd/libcudd_la-cuddAddApply.lo: cudd/cuddAddApply.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAddApply.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAddApply.Tpo -c -o cudd/libcudd_la-cuddAddApply.lo `test -f 'cudd/cuddAddApply.c' || echo '$(srcdir)/'`cudd/cuddAddApply.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAddApply.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAddApply.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAddApply.c' object='cudd/libcudd_la-cuddAddApply.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAddApply.lo `test -f 'cudd/cuddAddApply.c' || echo '$(srcdir)/'`cudd/cuddAddApply.c\n\ncudd/libcudd_la-cuddAddFind.lo: cudd/cuddAddFind.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAddFind.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAddFind.Tpo -c -o cudd/libcudd_la-cuddAddFind.lo `test -f 'cudd/cuddAddFind.c' || echo '$(srcdir)/'`cudd/cuddAddFind.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAddFind.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAddFind.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAddFind.c' object='cudd/libcudd_la-cuddAddFind.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAddFind.lo `test -f 'cudd/cuddAddFind.c' || echo '$(srcdir)/'`cudd/cuddAddFind.c\n\ncudd/libcudd_la-cuddAddInv.lo: cudd/cuddAddInv.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAddInv.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAddInv.Tpo -c -o cudd/libcudd_la-cuddAddInv.lo `test -f 'cudd/cuddAddInv.c' || echo '$(srcdir)/'`cudd/cuddAddInv.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAddInv.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAddInv.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAddInv.c' object='cudd/libcudd_la-cuddAddInv.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAddInv.lo `test -f 'cudd/cuddAddInv.c' || echo '$(srcdir)/'`cudd/cuddAddInv.c\n\ncudd/libcudd_la-cuddAddIte.lo: cudd/cuddAddIte.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAddIte.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAddIte.Tpo -c -o cudd/libcudd_la-cuddAddIte.lo `test -f 'cudd/cuddAddIte.c' || echo '$(srcdir)/'`cudd/cuddAddIte.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAddIte.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAddIte.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAddIte.c' object='cudd/libcudd_la-cuddAddIte.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAddIte.lo `test -f 'cudd/cuddAddIte.c' || echo '$(srcdir)/'`cudd/cuddAddIte.c\n\ncudd/libcudd_la-cuddAddNeg.lo: cudd/cuddAddNeg.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAddNeg.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAddNeg.Tpo -c -o cudd/libcudd_la-cuddAddNeg.lo `test -f 'cudd/cuddAddNeg.c' || echo '$(srcdir)/'`cudd/cuddAddNeg.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAddNeg.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAddNeg.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAddNeg.c' object='cudd/libcudd_la-cuddAddNeg.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAddNeg.lo `test -f 'cudd/cuddAddNeg.c' || echo '$(srcdir)/'`cudd/cuddAddNeg.c\n\ncudd/libcudd_la-cuddAddWalsh.lo: cudd/cuddAddWalsh.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAddWalsh.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAddWalsh.Tpo -c -o cudd/libcudd_la-cuddAddWalsh.lo `test -f 'cudd/cuddAddWalsh.c' || echo '$(srcdir)/'`cudd/cuddAddWalsh.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAddWalsh.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAddWalsh.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAddWalsh.c' object='cudd/libcudd_la-cuddAddWalsh.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAddWalsh.lo `test -f 'cudd/cuddAddWalsh.c' || echo '$(srcdir)/'`cudd/cuddAddWalsh.c\n\ncudd/libcudd_la-cuddAndAbs.lo: cudd/cuddAndAbs.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAndAbs.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAndAbs.Tpo -c -o cudd/libcudd_la-cuddAndAbs.lo `test -f 'cudd/cuddAndAbs.c' || echo '$(srcdir)/'`cudd/cuddAndAbs.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAndAbs.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAndAbs.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAndAbs.c' object='cudd/libcudd_la-cuddAndAbs.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAndAbs.lo `test -f 'cudd/cuddAndAbs.c' || echo '$(srcdir)/'`cudd/cuddAndAbs.c\n\ncudd/libcudd_la-cuddAnneal.lo: cudd/cuddAnneal.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAnneal.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAnneal.Tpo -c -o cudd/libcudd_la-cuddAnneal.lo `test -f 'cudd/cuddAnneal.c' || echo '$(srcdir)/'`cudd/cuddAnneal.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAnneal.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAnneal.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAnneal.c' object='cudd/libcudd_la-cuddAnneal.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAnneal.lo `test -f 'cudd/cuddAnneal.c' || echo '$(srcdir)/'`cudd/cuddAnneal.c\n\ncudd/libcudd_la-cuddApa.lo: cudd/cuddApa.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddApa.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddApa.Tpo -c -o cudd/libcudd_la-cuddApa.lo `test -f 'cudd/cuddApa.c' || echo '$(srcdir)/'`cudd/cuddApa.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddApa.Tpo cudd/$(DEPDIR)/libcudd_la-cuddApa.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddApa.c' object='cudd/libcudd_la-cuddApa.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddApa.lo `test -f 'cudd/cuddApa.c' || echo '$(srcdir)/'`cudd/cuddApa.c\n\ncudd/libcudd_la-cuddAPI.lo: cudd/cuddAPI.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddAPI.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddAPI.Tpo -c -o cudd/libcudd_la-cuddAPI.lo `test -f 'cudd/cuddAPI.c' || echo '$(srcdir)/'`cudd/cuddAPI.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddAPI.Tpo cudd/$(DEPDIR)/libcudd_la-cuddAPI.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddAPI.c' object='cudd/libcudd_la-cuddAPI.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddAPI.lo `test -f 'cudd/cuddAPI.c' || echo '$(srcdir)/'`cudd/cuddAPI.c\n\ncudd/libcudd_la-cuddApprox.lo: cudd/cuddApprox.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddApprox.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddApprox.Tpo -c -o cudd/libcudd_la-cuddApprox.lo `test -f 'cudd/cuddApprox.c' || echo '$(srcdir)/'`cudd/cuddApprox.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddApprox.Tpo cudd/$(DEPDIR)/libcudd_la-cuddApprox.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddApprox.c' object='cudd/libcudd_la-cuddApprox.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddApprox.lo `test -f 'cudd/cuddApprox.c' || echo '$(srcdir)/'`cudd/cuddApprox.c\n\ncudd/libcudd_la-cuddBddAbs.lo: cudd/cuddBddAbs.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddBddAbs.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddBddAbs.Tpo -c -o cudd/libcudd_la-cuddBddAbs.lo `test -f 'cudd/cuddBddAbs.c' || echo '$(srcdir)/'`cudd/cuddBddAbs.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddBddAbs.Tpo cudd/$(DEPDIR)/libcudd_la-cuddBddAbs.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddBddAbs.c' object='cudd/libcudd_la-cuddBddAbs.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddBddAbs.lo `test -f 'cudd/cuddBddAbs.c' || echo '$(srcdir)/'`cudd/cuddBddAbs.c\n\ncudd/libcudd_la-cuddBddCorr.lo: cudd/cuddBddCorr.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddBddCorr.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddBddCorr.Tpo -c -o cudd/libcudd_la-cuddBddCorr.lo `test -f 'cudd/cuddBddCorr.c' || echo '$(srcdir)/'`cudd/cuddBddCorr.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddBddCorr.Tpo cudd/$(DEPDIR)/libcudd_la-cuddBddCorr.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddBddCorr.c' object='cudd/libcudd_la-cuddBddCorr.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddBddCorr.lo `test -f 'cudd/cuddBddCorr.c' || echo '$(srcdir)/'`cudd/cuddBddCorr.c\n\ncudd/libcudd_la-cuddBddIte.lo: cudd/cuddBddIte.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddBddIte.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddBddIte.Tpo -c -o cudd/libcudd_la-cuddBddIte.lo `test -f 'cudd/cuddBddIte.c' || echo '$(srcdir)/'`cudd/cuddBddIte.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddBddIte.Tpo cudd/$(DEPDIR)/libcudd_la-cuddBddIte.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddBddIte.c' object='cudd/libcudd_la-cuddBddIte.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddBddIte.lo `test -f 'cudd/cuddBddIte.c' || echo '$(srcdir)/'`cudd/cuddBddIte.c\n\ncudd/libcudd_la-cuddBridge.lo: cudd/cuddBridge.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddBridge.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddBridge.Tpo -c -o cudd/libcudd_la-cuddBridge.lo `test -f 'cudd/cuddBridge.c' || echo '$(srcdir)/'`cudd/cuddBridge.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddBridge.Tpo cudd/$(DEPDIR)/libcudd_la-cuddBridge.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddBridge.c' object='cudd/libcudd_la-cuddBridge.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddBridge.lo `test -f 'cudd/cuddBridge.c' || echo '$(srcdir)/'`cudd/cuddBridge.c\n\ncudd/libcudd_la-cuddCache.lo: cudd/cuddCache.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddCache.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddCache.Tpo -c -o cudd/libcudd_la-cuddCache.lo `test -f 'cudd/cuddCache.c' || echo '$(srcdir)/'`cudd/cuddCache.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddCache.Tpo cudd/$(DEPDIR)/libcudd_la-cuddCache.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddCache.c' object='cudd/libcudd_la-cuddCache.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddCache.lo `test -f 'cudd/cuddCache.c' || echo '$(srcdir)/'`cudd/cuddCache.c\n\ncudd/libcudd_la-cuddCheck.lo: cudd/cuddCheck.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddCheck.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddCheck.Tpo -c -o cudd/libcudd_la-cuddCheck.lo `test -f 'cudd/cuddCheck.c' || echo '$(srcdir)/'`cudd/cuddCheck.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddCheck.Tpo cudd/$(DEPDIR)/libcudd_la-cuddCheck.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddCheck.c' object='cudd/libcudd_la-cuddCheck.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddCheck.lo `test -f 'cudd/cuddCheck.c' || echo '$(srcdir)/'`cudd/cuddCheck.c\n\ncudd/libcudd_la-cuddClip.lo: cudd/cuddClip.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddClip.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddClip.Tpo -c -o cudd/libcudd_la-cuddClip.lo `test -f 'cudd/cuddClip.c' || echo '$(srcdir)/'`cudd/cuddClip.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddClip.Tpo cudd/$(DEPDIR)/libcudd_la-cuddClip.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddClip.c' object='cudd/libcudd_la-cuddClip.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddClip.lo `test -f 'cudd/cuddClip.c' || echo '$(srcdir)/'`cudd/cuddClip.c\n\ncudd/libcudd_la-cuddCof.lo: cudd/cuddCof.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddCof.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddCof.Tpo -c -o cudd/libcudd_la-cuddCof.lo `test -f 'cudd/cuddCof.c' || echo '$(srcdir)/'`cudd/cuddCof.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddCof.Tpo cudd/$(DEPDIR)/libcudd_la-cuddCof.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddCof.c' object='cudd/libcudd_la-cuddCof.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddCof.lo `test -f 'cudd/cuddCof.c' || echo '$(srcdir)/'`cudd/cuddCof.c\n\ncudd/libcudd_la-cuddCompose.lo: cudd/cuddCompose.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddCompose.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddCompose.Tpo -c -o cudd/libcudd_la-cuddCompose.lo `test -f 'cudd/cuddCompose.c' || echo '$(srcdir)/'`cudd/cuddCompose.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddCompose.Tpo cudd/$(DEPDIR)/libcudd_la-cuddCompose.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddCompose.c' object='cudd/libcudd_la-cuddCompose.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddCompose.lo `test -f 'cudd/cuddCompose.c' || echo '$(srcdir)/'`cudd/cuddCompose.c\n\ncudd/libcudd_la-cuddDecomp.lo: cudd/cuddDecomp.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddDecomp.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddDecomp.Tpo -c -o cudd/libcudd_la-cuddDecomp.lo `test -f 'cudd/cuddDecomp.c' || echo '$(srcdir)/'`cudd/cuddDecomp.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddDecomp.Tpo cudd/$(DEPDIR)/libcudd_la-cuddDecomp.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddDecomp.c' object='cudd/libcudd_la-cuddDecomp.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddDecomp.lo `test -f 'cudd/cuddDecomp.c' || echo '$(srcdir)/'`cudd/cuddDecomp.c\n\ncudd/libcudd_la-cuddEssent.lo: cudd/cuddEssent.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddEssent.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddEssent.Tpo -c -o cudd/libcudd_la-cuddEssent.lo `test -f 'cudd/cuddEssent.c' || echo '$(srcdir)/'`cudd/cuddEssent.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddEssent.Tpo cudd/$(DEPDIR)/libcudd_la-cuddEssent.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddEssent.c' object='cudd/libcudd_la-cuddEssent.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddEssent.lo `test -f 'cudd/cuddEssent.c' || echo '$(srcdir)/'`cudd/cuddEssent.c\n\ncudd/libcudd_la-cuddExact.lo: cudd/cuddExact.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddExact.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddExact.Tpo -c -o cudd/libcudd_la-cuddExact.lo `test -f 'cudd/cuddExact.c' || echo '$(srcdir)/'`cudd/cuddExact.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddExact.Tpo cudd/$(DEPDIR)/libcudd_la-cuddExact.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddExact.c' object='cudd/libcudd_la-cuddExact.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddExact.lo `test -f 'cudd/cuddExact.c' || echo '$(srcdir)/'`cudd/cuddExact.c\n\ncudd/libcudd_la-cuddExport.lo: cudd/cuddExport.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddExport.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddExport.Tpo -c -o cudd/libcudd_la-cuddExport.lo `test -f 'cudd/cuddExport.c' || echo '$(srcdir)/'`cudd/cuddExport.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddExport.Tpo cudd/$(DEPDIR)/libcudd_la-cuddExport.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddExport.c' object='cudd/libcudd_la-cuddExport.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddExport.lo `test -f 'cudd/cuddExport.c' || echo '$(srcdir)/'`cudd/cuddExport.c\n\ncudd/libcudd_la-cuddGenCof.lo: cudd/cuddGenCof.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddGenCof.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddGenCof.Tpo -c -o cudd/libcudd_la-cuddGenCof.lo `test -f 'cudd/cuddGenCof.c' || echo '$(srcdir)/'`cudd/cuddGenCof.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddGenCof.Tpo cudd/$(DEPDIR)/libcudd_la-cuddGenCof.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddGenCof.c' object='cudd/libcudd_la-cuddGenCof.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddGenCof.lo `test -f 'cudd/cuddGenCof.c' || echo '$(srcdir)/'`cudd/cuddGenCof.c\n\ncudd/libcudd_la-cuddGenetic.lo: cudd/cuddGenetic.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddGenetic.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddGenetic.Tpo -c -o cudd/libcudd_la-cuddGenetic.lo `test -f 'cudd/cuddGenetic.c' || echo '$(srcdir)/'`cudd/cuddGenetic.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddGenetic.Tpo cudd/$(DEPDIR)/libcudd_la-cuddGenetic.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddGenetic.c' object='cudd/libcudd_la-cuddGenetic.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddGenetic.lo `test -f 'cudd/cuddGenetic.c' || echo '$(srcdir)/'`cudd/cuddGenetic.c\n\ncudd/libcudd_la-cuddGroup.lo: cudd/cuddGroup.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddGroup.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddGroup.Tpo -c -o cudd/libcudd_la-cuddGroup.lo `test -f 'cudd/cuddGroup.c' || echo '$(srcdir)/'`cudd/cuddGroup.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddGroup.Tpo cudd/$(DEPDIR)/libcudd_la-cuddGroup.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddGroup.c' object='cudd/libcudd_la-cuddGroup.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddGroup.lo `test -f 'cudd/cuddGroup.c' || echo '$(srcdir)/'`cudd/cuddGroup.c\n\ncudd/libcudd_la-cuddHarwell.lo: cudd/cuddHarwell.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddHarwell.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddHarwell.Tpo -c -o cudd/libcudd_la-cuddHarwell.lo `test -f 'cudd/cuddHarwell.c' || echo '$(srcdir)/'`cudd/cuddHarwell.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddHarwell.Tpo cudd/$(DEPDIR)/libcudd_la-cuddHarwell.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddHarwell.c' object='cudd/libcudd_la-cuddHarwell.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddHarwell.lo `test -f 'cudd/cuddHarwell.c' || echo '$(srcdir)/'`cudd/cuddHarwell.c\n\ncudd/libcudd_la-cuddInit.lo: cudd/cuddInit.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddInit.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddInit.Tpo -c -o cudd/libcudd_la-cuddInit.lo `test -f 'cudd/cuddInit.c' || echo '$(srcdir)/'`cudd/cuddInit.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddInit.Tpo cudd/$(DEPDIR)/libcudd_la-cuddInit.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddInit.c' object='cudd/libcudd_la-cuddInit.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddInit.lo `test -f 'cudd/cuddInit.c' || echo '$(srcdir)/'`cudd/cuddInit.c\n\ncudd/libcudd_la-cuddInteract.lo: cudd/cuddInteract.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddInteract.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddInteract.Tpo -c -o cudd/libcudd_la-cuddInteract.lo `test -f 'cudd/cuddInteract.c' || echo '$(srcdir)/'`cudd/cuddInteract.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddInteract.Tpo cudd/$(DEPDIR)/libcudd_la-cuddInteract.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddInteract.c' object='cudd/libcudd_la-cuddInteract.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddInteract.lo `test -f 'cudd/cuddInteract.c' || echo '$(srcdir)/'`cudd/cuddInteract.c\n\ncudd/libcudd_la-cuddLCache.lo: cudd/cuddLCache.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddLCache.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddLCache.Tpo -c -o cudd/libcudd_la-cuddLCache.lo `test -f 'cudd/cuddLCache.c' || echo '$(srcdir)/'`cudd/cuddLCache.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddLCache.Tpo cudd/$(DEPDIR)/libcudd_la-cuddLCache.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddLCache.c' object='cudd/libcudd_la-cuddLCache.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddLCache.lo `test -f 'cudd/cuddLCache.c' || echo '$(srcdir)/'`cudd/cuddLCache.c\n\ncudd/libcudd_la-cuddLevelQ.lo: cudd/cuddLevelQ.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddLevelQ.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddLevelQ.Tpo -c -o cudd/libcudd_la-cuddLevelQ.lo `test -f 'cudd/cuddLevelQ.c' || echo '$(srcdir)/'`cudd/cuddLevelQ.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddLevelQ.Tpo cudd/$(DEPDIR)/libcudd_la-cuddLevelQ.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddLevelQ.c' object='cudd/libcudd_la-cuddLevelQ.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddLevelQ.lo `test -f 'cudd/cuddLevelQ.c' || echo '$(srcdir)/'`cudd/cuddLevelQ.c\n\ncudd/libcudd_la-cuddLinear.lo: cudd/cuddLinear.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddLinear.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddLinear.Tpo -c -o cudd/libcudd_la-cuddLinear.lo `test -f 'cudd/cuddLinear.c' || echo '$(srcdir)/'`cudd/cuddLinear.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddLinear.Tpo cudd/$(DEPDIR)/libcudd_la-cuddLinear.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddLinear.c' object='cudd/libcudd_la-cuddLinear.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddLinear.lo `test -f 'cudd/cuddLinear.c' || echo '$(srcdir)/'`cudd/cuddLinear.c\n\ncudd/libcudd_la-cuddLiteral.lo: cudd/cuddLiteral.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddLiteral.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddLiteral.Tpo -c -o cudd/libcudd_la-cuddLiteral.lo `test -f 'cudd/cuddLiteral.c' || echo '$(srcdir)/'`cudd/cuddLiteral.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddLiteral.Tpo cudd/$(DEPDIR)/libcudd_la-cuddLiteral.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddLiteral.c' object='cudd/libcudd_la-cuddLiteral.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddLiteral.lo `test -f 'cudd/cuddLiteral.c' || echo '$(srcdir)/'`cudd/cuddLiteral.c\n\ncudd/libcudd_la-cuddMatMult.lo: cudd/cuddMatMult.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddMatMult.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddMatMult.Tpo -c -o cudd/libcudd_la-cuddMatMult.lo `test -f 'cudd/cuddMatMult.c' || echo '$(srcdir)/'`cudd/cuddMatMult.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddMatMult.Tpo cudd/$(DEPDIR)/libcudd_la-cuddMatMult.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddMatMult.c' object='cudd/libcudd_la-cuddMatMult.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddMatMult.lo `test -f 'cudd/cuddMatMult.c' || echo '$(srcdir)/'`cudd/cuddMatMult.c\n\ncudd/libcudd_la-cuddPriority.lo: cudd/cuddPriority.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddPriority.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddPriority.Tpo -c -o cudd/libcudd_la-cuddPriority.lo `test -f 'cudd/cuddPriority.c' || echo '$(srcdir)/'`cudd/cuddPriority.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddPriority.Tpo cudd/$(DEPDIR)/libcudd_la-cuddPriority.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddPriority.c' object='cudd/libcudd_la-cuddPriority.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddPriority.lo `test -f 'cudd/cuddPriority.c' || echo '$(srcdir)/'`cudd/cuddPriority.c\n\ncudd/libcudd_la-cuddRead.lo: cudd/cuddRead.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddRead.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddRead.Tpo -c -o cudd/libcudd_la-cuddRead.lo `test -f 'cudd/cuddRead.c' || echo '$(srcdir)/'`cudd/cuddRead.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddRead.Tpo cudd/$(DEPDIR)/libcudd_la-cuddRead.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddRead.c' object='cudd/libcudd_la-cuddRead.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddRead.lo `test -f 'cudd/cuddRead.c' || echo '$(srcdir)/'`cudd/cuddRead.c\n\ncudd/libcudd_la-cuddRef.lo: cudd/cuddRef.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddRef.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddRef.Tpo -c -o cudd/libcudd_la-cuddRef.lo `test -f 'cudd/cuddRef.c' || echo '$(srcdir)/'`cudd/cuddRef.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddRef.Tpo cudd/$(DEPDIR)/libcudd_la-cuddRef.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddRef.c' object='cudd/libcudd_la-cuddRef.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddRef.lo `test -f 'cudd/cuddRef.c' || echo '$(srcdir)/'`cudd/cuddRef.c\n\ncudd/libcudd_la-cuddReorder.lo: cudd/cuddReorder.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddReorder.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddReorder.Tpo -c -o cudd/libcudd_la-cuddReorder.lo `test -f 'cudd/cuddReorder.c' || echo '$(srcdir)/'`cudd/cuddReorder.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddReorder.Tpo cudd/$(DEPDIR)/libcudd_la-cuddReorder.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddReorder.c' object='cudd/libcudd_la-cuddReorder.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddReorder.lo `test -f 'cudd/cuddReorder.c' || echo '$(srcdir)/'`cudd/cuddReorder.c\n\ncudd/libcudd_la-cuddSat.lo: cudd/cuddSat.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddSat.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddSat.Tpo -c -o cudd/libcudd_la-cuddSat.lo `test -f 'cudd/cuddSat.c' || echo '$(srcdir)/'`cudd/cuddSat.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddSat.Tpo cudd/$(DEPDIR)/libcudd_la-cuddSat.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddSat.c' object='cudd/libcudd_la-cuddSat.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddSat.lo `test -f 'cudd/cuddSat.c' || echo '$(srcdir)/'`cudd/cuddSat.c\n\ncudd/libcudd_la-cuddSign.lo: cudd/cuddSign.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddSign.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddSign.Tpo -c -o cudd/libcudd_la-cuddSign.lo `test -f 'cudd/cuddSign.c' || echo '$(srcdir)/'`cudd/cuddSign.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddSign.Tpo cudd/$(DEPDIR)/libcudd_la-cuddSign.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddSign.c' object='cudd/libcudd_la-cuddSign.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddSign.lo `test -f 'cudd/cuddSign.c' || echo '$(srcdir)/'`cudd/cuddSign.c\n\ncudd/libcudd_la-cuddSolve.lo: cudd/cuddSolve.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddSolve.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddSolve.Tpo -c -o cudd/libcudd_la-cuddSolve.lo `test -f 'cudd/cuddSolve.c' || echo '$(srcdir)/'`cudd/cuddSolve.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddSolve.Tpo cudd/$(DEPDIR)/libcudd_la-cuddSolve.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddSolve.c' object='cudd/libcudd_la-cuddSolve.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddSolve.lo `test -f 'cudd/cuddSolve.c' || echo '$(srcdir)/'`cudd/cuddSolve.c\n\ncudd/libcudd_la-cuddSplit.lo: cudd/cuddSplit.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddSplit.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddSplit.Tpo -c -o cudd/libcudd_la-cuddSplit.lo `test -f 'cudd/cuddSplit.c' || echo '$(srcdir)/'`cudd/cuddSplit.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddSplit.Tpo cudd/$(DEPDIR)/libcudd_la-cuddSplit.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddSplit.c' object='cudd/libcudd_la-cuddSplit.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddSplit.lo `test -f 'cudd/cuddSplit.c' || echo '$(srcdir)/'`cudd/cuddSplit.c\n\ncudd/libcudd_la-cuddSubsetHB.lo: cudd/cuddSubsetHB.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddSubsetHB.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddSubsetHB.Tpo -c -o cudd/libcudd_la-cuddSubsetHB.lo `test -f 'cudd/cuddSubsetHB.c' || echo '$(srcdir)/'`cudd/cuddSubsetHB.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddSubsetHB.Tpo cudd/$(DEPDIR)/libcudd_la-cuddSubsetHB.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddSubsetHB.c' object='cudd/libcudd_la-cuddSubsetHB.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddSubsetHB.lo `test -f 'cudd/cuddSubsetHB.c' || echo '$(srcdir)/'`cudd/cuddSubsetHB.c\n\ncudd/libcudd_la-cuddSubsetSP.lo: cudd/cuddSubsetSP.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddSubsetSP.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddSubsetSP.Tpo -c -o cudd/libcudd_la-cuddSubsetSP.lo `test -f 'cudd/cuddSubsetSP.c' || echo '$(srcdir)/'`cudd/cuddSubsetSP.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddSubsetSP.Tpo cudd/$(DEPDIR)/libcudd_la-cuddSubsetSP.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddSubsetSP.c' object='cudd/libcudd_la-cuddSubsetSP.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddSubsetSP.lo `test -f 'cudd/cuddSubsetSP.c' || echo '$(srcdir)/'`cudd/cuddSubsetSP.c\n\ncudd/libcudd_la-cuddSymmetry.lo: cudd/cuddSymmetry.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddSymmetry.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddSymmetry.Tpo -c -o cudd/libcudd_la-cuddSymmetry.lo `test -f 'cudd/cuddSymmetry.c' || echo '$(srcdir)/'`cudd/cuddSymmetry.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddSymmetry.Tpo cudd/$(DEPDIR)/libcudd_la-cuddSymmetry.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddSymmetry.c' object='cudd/libcudd_la-cuddSymmetry.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddSymmetry.lo `test -f 'cudd/cuddSymmetry.c' || echo '$(srcdir)/'`cudd/cuddSymmetry.c\n\ncudd/libcudd_la-cuddTable.lo: cudd/cuddTable.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddTable.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddTable.Tpo -c -o cudd/libcudd_la-cuddTable.lo `test -f 'cudd/cuddTable.c' || echo '$(srcdir)/'`cudd/cuddTable.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddTable.Tpo cudd/$(DEPDIR)/libcudd_la-cuddTable.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddTable.c' object='cudd/libcudd_la-cuddTable.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddTable.lo `test -f 'cudd/cuddTable.c' || echo '$(srcdir)/'`cudd/cuddTable.c\n\ncudd/libcudd_la-cuddUtil.lo: cudd/cuddUtil.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddUtil.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddUtil.Tpo -c -o cudd/libcudd_la-cuddUtil.lo `test -f 'cudd/cuddUtil.c' || echo '$(srcdir)/'`cudd/cuddUtil.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddUtil.Tpo cudd/$(DEPDIR)/libcudd_la-cuddUtil.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddUtil.c' object='cudd/libcudd_la-cuddUtil.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddUtil.lo `test -f 'cudd/cuddUtil.c' || echo '$(srcdir)/'`cudd/cuddUtil.c\n\ncudd/libcudd_la-cuddWindow.lo: cudd/cuddWindow.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddWindow.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddWindow.Tpo -c -o cudd/libcudd_la-cuddWindow.lo `test -f 'cudd/cuddWindow.c' || echo '$(srcdir)/'`cudd/cuddWindow.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddWindow.Tpo cudd/$(DEPDIR)/libcudd_la-cuddWindow.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddWindow.c' object='cudd/libcudd_la-cuddWindow.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddWindow.lo `test -f 'cudd/cuddWindow.c' || echo '$(srcdir)/'`cudd/cuddWindow.c\n\ncudd/libcudd_la-cuddZddCount.lo: cudd/cuddZddCount.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddCount.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddCount.Tpo -c -o cudd/libcudd_la-cuddZddCount.lo `test -f 'cudd/cuddZddCount.c' || echo '$(srcdir)/'`cudd/cuddZddCount.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddCount.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddCount.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddCount.c' object='cudd/libcudd_la-cuddZddCount.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddCount.lo `test -f 'cudd/cuddZddCount.c' || echo '$(srcdir)/'`cudd/cuddZddCount.c\n\ncudd/libcudd_la-cuddZddFuncs.lo: cudd/cuddZddFuncs.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddFuncs.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddFuncs.Tpo -c -o cudd/libcudd_la-cuddZddFuncs.lo `test -f 'cudd/cuddZddFuncs.c' || echo '$(srcdir)/'`cudd/cuddZddFuncs.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddFuncs.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddFuncs.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddFuncs.c' object='cudd/libcudd_la-cuddZddFuncs.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddFuncs.lo `test -f 'cudd/cuddZddFuncs.c' || echo '$(srcdir)/'`cudd/cuddZddFuncs.c\n\ncudd/libcudd_la-cuddZddGroup.lo: cudd/cuddZddGroup.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddGroup.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddGroup.Tpo -c -o cudd/libcudd_la-cuddZddGroup.lo `test -f 'cudd/cuddZddGroup.c' || echo '$(srcdir)/'`cudd/cuddZddGroup.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddGroup.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddGroup.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddGroup.c' object='cudd/libcudd_la-cuddZddGroup.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddGroup.lo `test -f 'cudd/cuddZddGroup.c' || echo '$(srcdir)/'`cudd/cuddZddGroup.c\n\ncudd/libcudd_la-cuddZddIsop.lo: cudd/cuddZddIsop.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddIsop.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddIsop.Tpo -c -o cudd/libcudd_la-cuddZddIsop.lo `test -f 'cudd/cuddZddIsop.c' || echo '$(srcdir)/'`cudd/cuddZddIsop.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddIsop.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddIsop.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddIsop.c' object='cudd/libcudd_la-cuddZddIsop.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddIsop.lo `test -f 'cudd/cuddZddIsop.c' || echo '$(srcdir)/'`cudd/cuddZddIsop.c\n\ncudd/libcudd_la-cuddZddLin.lo: cudd/cuddZddLin.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddLin.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddLin.Tpo -c -o cudd/libcudd_la-cuddZddLin.lo `test -f 'cudd/cuddZddLin.c' || echo '$(srcdir)/'`cudd/cuddZddLin.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddLin.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddLin.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddLin.c' object='cudd/libcudd_la-cuddZddLin.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddLin.lo `test -f 'cudd/cuddZddLin.c' || echo '$(srcdir)/'`cudd/cuddZddLin.c\n\ncudd/libcudd_la-cuddZddMisc.lo: cudd/cuddZddMisc.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddMisc.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddMisc.Tpo -c -o cudd/libcudd_la-cuddZddMisc.lo `test -f 'cudd/cuddZddMisc.c' || echo '$(srcdir)/'`cudd/cuddZddMisc.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddMisc.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddMisc.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddMisc.c' object='cudd/libcudd_la-cuddZddMisc.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddMisc.lo `test -f 'cudd/cuddZddMisc.c' || echo '$(srcdir)/'`cudd/cuddZddMisc.c\n\ncudd/libcudd_la-cuddZddPort.lo: cudd/cuddZddPort.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddPort.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddPort.Tpo -c -o cudd/libcudd_la-cuddZddPort.lo `test -f 'cudd/cuddZddPort.c' || echo '$(srcdir)/'`cudd/cuddZddPort.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddPort.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddPort.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddPort.c' object='cudd/libcudd_la-cuddZddPort.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddPort.lo `test -f 'cudd/cuddZddPort.c' || echo '$(srcdir)/'`cudd/cuddZddPort.c\n\ncudd/libcudd_la-cuddZddReord.lo: cudd/cuddZddReord.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddReord.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddReord.Tpo -c -o cudd/libcudd_la-cuddZddReord.lo `test -f 'cudd/cuddZddReord.c' || echo '$(srcdir)/'`cudd/cuddZddReord.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddReord.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddReord.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddReord.c' object='cudd/libcudd_la-cuddZddReord.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddReord.lo `test -f 'cudd/cuddZddReord.c' || echo '$(srcdir)/'`cudd/cuddZddReord.c\n\ncudd/libcudd_la-cuddZddSetop.lo: cudd/cuddZddSetop.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddSetop.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddSetop.Tpo -c -o cudd/libcudd_la-cuddZddSetop.lo `test -f 'cudd/cuddZddSetop.c' || echo '$(srcdir)/'`cudd/cuddZddSetop.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddSetop.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddSetop.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddSetop.c' object='cudd/libcudd_la-cuddZddSetop.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddSetop.lo `test -f 'cudd/cuddZddSetop.c' || echo '$(srcdir)/'`cudd/cuddZddSetop.c\n\ncudd/libcudd_la-cuddZddSymm.lo: cudd/cuddZddSymm.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddSymm.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddSymm.Tpo -c -o cudd/libcudd_la-cuddZddSymm.lo `test -f 'cudd/cuddZddSymm.c' || echo '$(srcdir)/'`cudd/cuddZddSymm.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddSymm.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddSymm.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddSymm.c' object='cudd/libcudd_la-cuddZddSymm.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddSymm.lo `test -f 'cudd/cuddZddSymm.c' || echo '$(srcdir)/'`cudd/cuddZddSymm.c\n\ncudd/libcudd_la-cuddZddUtil.lo: cudd/cuddZddUtil.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/libcudd_la-cuddZddUtil.lo -MD -MP -MF cudd/$(DEPDIR)/libcudd_la-cuddZddUtil.Tpo -c -o cudd/libcudd_la-cuddZddUtil.lo `test -f 'cudd/cuddZddUtil.c' || echo '$(srcdir)/'`cudd/cuddZddUtil.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/libcudd_la-cuddZddUtil.Tpo cudd/$(DEPDIR)/libcudd_la-cuddZddUtil.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/cuddZddUtil.c' object='cudd/libcudd_la-cuddZddUtil.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/libcudd_la-cuddZddUtil.lo `test -f 'cudd/cuddZddUtil.c' || echo '$(srcdir)/'`cudd/cuddZddUtil.c\n\nutil/cudd_libcudd_la-cpu_stats.lo: util/cpu_stats.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-cpu_stats.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-cpu_stats.Tpo -c -o util/cudd_libcudd_la-cpu_stats.lo `test -f 'util/cpu_stats.c' || echo '$(srcdir)/'`util/cpu_stats.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-cpu_stats.Tpo util/$(DEPDIR)/cudd_libcudd_la-cpu_stats.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/cpu_stats.c' object='util/cudd_libcudd_la-cpu_stats.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-cpu_stats.lo `test -f 'util/cpu_stats.c' || echo '$(srcdir)/'`util/cpu_stats.c\n\nutil/cudd_libcudd_la-cpu_time.lo: util/cpu_time.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-cpu_time.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-cpu_time.Tpo -c -o util/cudd_libcudd_la-cpu_time.lo `test -f 'util/cpu_time.c' || echo '$(srcdir)/'`util/cpu_time.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-cpu_time.Tpo util/$(DEPDIR)/cudd_libcudd_la-cpu_time.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/cpu_time.c' object='util/cudd_libcudd_la-cpu_time.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-cpu_time.lo `test -f 'util/cpu_time.c' || echo '$(srcdir)/'`util/cpu_time.c\n\nutil/cudd_libcudd_la-cstringstream.lo: util/cstringstream.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-cstringstream.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-cstringstream.Tpo -c -o util/cudd_libcudd_la-cstringstream.lo `test -f 'util/cstringstream.c' || echo '$(srcdir)/'`util/cstringstream.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-cstringstream.Tpo util/$(DEPDIR)/cudd_libcudd_la-cstringstream.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/cstringstream.c' object='util/cudd_libcudd_la-cstringstream.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-cstringstream.lo `test -f 'util/cstringstream.c' || echo '$(srcdir)/'`util/cstringstream.c\n\nutil/cudd_libcudd_la-datalimit.lo: util/datalimit.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-datalimit.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-datalimit.Tpo -c -o util/cudd_libcudd_la-datalimit.lo `test -f 'util/datalimit.c' || echo '$(srcdir)/'`util/datalimit.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-datalimit.Tpo util/$(DEPDIR)/cudd_libcudd_la-datalimit.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/datalimit.c' object='util/cudd_libcudd_la-datalimit.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-datalimit.lo `test -f 'util/datalimit.c' || echo '$(srcdir)/'`util/datalimit.c\n\nutil/cudd_libcudd_la-pathsearch.lo: util/pathsearch.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-pathsearch.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-pathsearch.Tpo -c -o util/cudd_libcudd_la-pathsearch.lo `test -f 'util/pathsearch.c' || echo '$(srcdir)/'`util/pathsearch.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-pathsearch.Tpo util/$(DEPDIR)/cudd_libcudd_la-pathsearch.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/pathsearch.c' object='util/cudd_libcudd_la-pathsearch.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-pathsearch.lo `test -f 'util/pathsearch.c' || echo '$(srcdir)/'`util/pathsearch.c\n\nutil/cudd_libcudd_la-pipefork.lo: util/pipefork.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-pipefork.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-pipefork.Tpo -c -o util/cudd_libcudd_la-pipefork.lo `test -f 'util/pipefork.c' || echo '$(srcdir)/'`util/pipefork.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-pipefork.Tpo util/$(DEPDIR)/cudd_libcudd_la-pipefork.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/pipefork.c' object='util/cudd_libcudd_la-pipefork.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-pipefork.lo `test -f 'util/pipefork.c' || echo '$(srcdir)/'`util/pipefork.c\n\nutil/cudd_libcudd_la-prtime.lo: util/prtime.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-prtime.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-prtime.Tpo -c -o util/cudd_libcudd_la-prtime.lo `test -f 'util/prtime.c' || echo '$(srcdir)/'`util/prtime.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-prtime.Tpo util/$(DEPDIR)/cudd_libcudd_la-prtime.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/prtime.c' object='util/cudd_libcudd_la-prtime.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-prtime.lo `test -f 'util/prtime.c' || echo '$(srcdir)/'`util/prtime.c\n\nutil/cudd_libcudd_la-safe_mem.lo: util/safe_mem.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-safe_mem.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-safe_mem.Tpo -c -o util/cudd_libcudd_la-safe_mem.lo `test -f 'util/safe_mem.c' || echo '$(srcdir)/'`util/safe_mem.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-safe_mem.Tpo util/$(DEPDIR)/cudd_libcudd_la-safe_mem.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/safe_mem.c' object='util/cudd_libcudd_la-safe_mem.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-safe_mem.lo `test -f 'util/safe_mem.c' || echo '$(srcdir)/'`util/safe_mem.c\n\nutil/cudd_libcudd_la-strsav.lo: util/strsav.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-strsav.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-strsav.Tpo -c -o util/cudd_libcudd_la-strsav.lo `test -f 'util/strsav.c' || echo '$(srcdir)/'`util/strsav.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-strsav.Tpo util/$(DEPDIR)/cudd_libcudd_la-strsav.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/strsav.c' object='util/cudd_libcudd_la-strsav.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-strsav.lo `test -f 'util/strsav.c' || echo '$(srcdir)/'`util/strsav.c\n\nutil/cudd_libcudd_la-texpand.lo: util/texpand.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-texpand.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-texpand.Tpo -c -o util/cudd_libcudd_la-texpand.lo `test -f 'util/texpand.c' || echo '$(srcdir)/'`util/texpand.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-texpand.Tpo util/$(DEPDIR)/cudd_libcudd_la-texpand.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/texpand.c' object='util/cudd_libcudd_la-texpand.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-texpand.lo `test -f 'util/texpand.c' || echo '$(srcdir)/'`util/texpand.c\n\nutil/cudd_libcudd_la-ucbqsort.lo: util/ucbqsort.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT util/cudd_libcudd_la-ucbqsort.lo -MD -MP -MF util/$(DEPDIR)/cudd_libcudd_la-ucbqsort.Tpo -c -o util/cudd_libcudd_la-ucbqsort.lo `test -f 'util/ucbqsort.c' || echo '$(srcdir)/'`util/ucbqsort.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) util/$(DEPDIR)/cudd_libcudd_la-ucbqsort.Tpo util/$(DEPDIR)/cudd_libcudd_la-ucbqsort.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='util/ucbqsort.c' object='util/cudd_libcudd_la-ucbqsort.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o util/cudd_libcudd_la-ucbqsort.lo `test -f 'util/ucbqsort.c' || echo '$(srcdir)/'`util/ucbqsort.c\n\nst/cudd_libcudd_la-st.lo: st/st.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT st/cudd_libcudd_la-st.lo -MD -MP -MF st/$(DEPDIR)/cudd_libcudd_la-st.Tpo -c -o st/cudd_libcudd_la-st.lo `test -f 'st/st.c' || echo '$(srcdir)/'`st/st.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) st/$(DEPDIR)/cudd_libcudd_la-st.Tpo st/$(DEPDIR)/cudd_libcudd_la-st.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='st/st.c' object='st/cudd_libcudd_la-st.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o st/cudd_libcudd_la-st.lo `test -f 'st/st.c' || echo '$(srcdir)/'`st/st.c\n\nepd/cudd_libcudd_la-epd.lo: epd/epd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT epd/cudd_libcudd_la-epd.lo -MD -MP -MF epd/$(DEPDIR)/cudd_libcudd_la-epd.Tpo -c -o epd/cudd_libcudd_la-epd.lo `test -f 'epd/epd.c' || echo '$(srcdir)/'`epd/epd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) epd/$(DEPDIR)/cudd_libcudd_la-epd.Tpo epd/$(DEPDIR)/cudd_libcudd_la-epd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='epd/epd.c' object='epd/cudd_libcudd_la-epd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o epd/cudd_libcudd_la-epd.lo `test -f 'epd/epd.c' || echo '$(srcdir)/'`epd/epd.c\n\nmtr/cudd_libcudd_la-mtrBasic.lo: mtr/mtrBasic.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT mtr/cudd_libcudd_la-mtrBasic.lo -MD -MP -MF mtr/$(DEPDIR)/cudd_libcudd_la-mtrBasic.Tpo -c -o mtr/cudd_libcudd_la-mtrBasic.lo `test -f 'mtr/mtrBasic.c' || echo '$(srcdir)/'`mtr/mtrBasic.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) mtr/$(DEPDIR)/cudd_libcudd_la-mtrBasic.Tpo mtr/$(DEPDIR)/cudd_libcudd_la-mtrBasic.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='mtr/mtrBasic.c' object='mtr/cudd_libcudd_la-mtrBasic.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o mtr/cudd_libcudd_la-mtrBasic.lo `test -f 'mtr/mtrBasic.c' || echo '$(srcdir)/'`mtr/mtrBasic.c\n\nmtr/cudd_libcudd_la-mtrGroup.lo: mtr/mtrGroup.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT mtr/cudd_libcudd_la-mtrGroup.lo -MD -MP -MF mtr/$(DEPDIR)/cudd_libcudd_la-mtrGroup.Tpo -c -o mtr/cudd_libcudd_la-mtrGroup.lo `test -f 'mtr/mtrGroup.c' || echo '$(srcdir)/'`mtr/mtrGroup.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) mtr/$(DEPDIR)/cudd_libcudd_la-mtrGroup.Tpo mtr/$(DEPDIR)/cudd_libcudd_la-mtrGroup.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='mtr/mtrGroup.c' object='mtr/cudd_libcudd_la-mtrGroup.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o mtr/cudd_libcudd_la-mtrGroup.lo `test -f 'mtr/mtrGroup.c' || echo '$(srcdir)/'`mtr/mtrGroup.c\n\ndddmp/cudd_libcudd_la-dddmpBinary.lo: dddmp/dddmpBinary.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpBinary.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpBinary.Tpo -c -o dddmp/cudd_libcudd_la-dddmpBinary.lo `test -f 'dddmp/dddmpBinary.c' || echo '$(srcdir)/'`dddmp/dddmpBinary.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpBinary.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpBinary.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpBinary.c' object='dddmp/cudd_libcudd_la-dddmpBinary.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpBinary.lo `test -f 'dddmp/dddmpBinary.c' || echo '$(srcdir)/'`dddmp/dddmpBinary.c\n\ndddmp/cudd_libcudd_la-dddmpConvert.lo: dddmp/dddmpConvert.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpConvert.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpConvert.Tpo -c -o dddmp/cudd_libcudd_la-dddmpConvert.lo `test -f 'dddmp/dddmpConvert.c' || echo '$(srcdir)/'`dddmp/dddmpConvert.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpConvert.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpConvert.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpConvert.c' object='dddmp/cudd_libcudd_la-dddmpConvert.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpConvert.lo `test -f 'dddmp/dddmpConvert.c' || echo '$(srcdir)/'`dddmp/dddmpConvert.c\n\ndddmp/cudd_libcudd_la-dddmpDbg.lo: dddmp/dddmpDbg.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpDbg.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpDbg.Tpo -c -o dddmp/cudd_libcudd_la-dddmpDbg.lo `test -f 'dddmp/dddmpDbg.c' || echo '$(srcdir)/'`dddmp/dddmpDbg.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpDbg.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpDbg.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpDbg.c' object='dddmp/cudd_libcudd_la-dddmpDbg.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpDbg.lo `test -f 'dddmp/dddmpDbg.c' || echo '$(srcdir)/'`dddmp/dddmpDbg.c\n\ndddmp/cudd_libcudd_la-dddmpLoad.lo: dddmp/dddmpLoad.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpLoad.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoad.Tpo -c -o dddmp/cudd_libcudd_la-dddmpLoad.lo `test -f 'dddmp/dddmpLoad.c' || echo '$(srcdir)/'`dddmp/dddmpLoad.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoad.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoad.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpLoad.c' object='dddmp/cudd_libcudd_la-dddmpLoad.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpLoad.lo `test -f 'dddmp/dddmpLoad.c' || echo '$(srcdir)/'`dddmp/dddmpLoad.c\n\ndddmp/cudd_libcudd_la-dddmpLoadCnf.lo: dddmp/dddmpLoadCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpLoadCnf.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoadCnf.Tpo -c -o dddmp/cudd_libcudd_la-dddmpLoadCnf.lo `test -f 'dddmp/dddmpLoadCnf.c' || echo '$(srcdir)/'`dddmp/dddmpLoadCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoadCnf.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoadCnf.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpLoadCnf.c' object='dddmp/cudd_libcudd_la-dddmpLoadCnf.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpLoadCnf.lo `test -f 'dddmp/dddmpLoadCnf.c' || echo '$(srcdir)/'`dddmp/dddmpLoadCnf.c\n\ndddmp/cudd_libcudd_la-dddmpNodeAdd.lo: dddmp/dddmpNodeAdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpNodeAdd.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeAdd.Tpo -c -o dddmp/cudd_libcudd_la-dddmpNodeAdd.lo `test -f 'dddmp/dddmpNodeAdd.c' || echo '$(srcdir)/'`dddmp/dddmpNodeAdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeAdd.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeAdd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpNodeAdd.c' object='dddmp/cudd_libcudd_la-dddmpNodeAdd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpNodeAdd.lo `test -f 'dddmp/dddmpNodeAdd.c' || echo '$(srcdir)/'`dddmp/dddmpNodeAdd.c\n\ndddmp/cudd_libcudd_la-dddmpNodeBdd.lo: dddmp/dddmpNodeBdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpNodeBdd.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeBdd.Tpo -c -o dddmp/cudd_libcudd_la-dddmpNodeBdd.lo `test -f 'dddmp/dddmpNodeBdd.c' || echo '$(srcdir)/'`dddmp/dddmpNodeBdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeBdd.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeBdd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpNodeBdd.c' object='dddmp/cudd_libcudd_la-dddmpNodeBdd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpNodeBdd.lo `test -f 'dddmp/dddmpNodeBdd.c' || echo '$(srcdir)/'`dddmp/dddmpNodeBdd.c\n\ndddmp/cudd_libcudd_la-dddmpNodeCnf.lo: dddmp/dddmpNodeCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpNodeCnf.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeCnf.Tpo -c -o dddmp/cudd_libcudd_la-dddmpNodeCnf.lo `test -f 'dddmp/dddmpNodeCnf.c' || echo '$(srcdir)/'`dddmp/dddmpNodeCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeCnf.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeCnf.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpNodeCnf.c' object='dddmp/cudd_libcudd_la-dddmpNodeCnf.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpNodeCnf.lo `test -f 'dddmp/dddmpNodeCnf.c' || echo '$(srcdir)/'`dddmp/dddmpNodeCnf.c\n\ndddmp/cudd_libcudd_la-dddmpStoreAdd.lo: dddmp/dddmpStoreAdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpStoreAdd.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreAdd.Tpo -c -o dddmp/cudd_libcudd_la-dddmpStoreAdd.lo `test -f 'dddmp/dddmpStoreAdd.c' || echo '$(srcdir)/'`dddmp/dddmpStoreAdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreAdd.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreAdd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpStoreAdd.c' object='dddmp/cudd_libcudd_la-dddmpStoreAdd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpStoreAdd.lo `test -f 'dddmp/dddmpStoreAdd.c' || echo '$(srcdir)/'`dddmp/dddmpStoreAdd.c\n\ndddmp/cudd_libcudd_la-dddmpStoreBdd.lo: dddmp/dddmpStoreBdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpStoreBdd.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreBdd.Tpo -c -o dddmp/cudd_libcudd_la-dddmpStoreBdd.lo `test -f 'dddmp/dddmpStoreBdd.c' || echo '$(srcdir)/'`dddmp/dddmpStoreBdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreBdd.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreBdd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpStoreBdd.c' object='dddmp/cudd_libcudd_la-dddmpStoreBdd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpStoreBdd.lo `test -f 'dddmp/dddmpStoreBdd.c' || echo '$(srcdir)/'`dddmp/dddmpStoreBdd.c\n\ndddmp/cudd_libcudd_la-dddmpStoreCnf.lo: dddmp/dddmpStoreCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpStoreCnf.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreCnf.Tpo -c -o dddmp/cudd_libcudd_la-dddmpStoreCnf.lo `test -f 'dddmp/dddmpStoreCnf.c' || echo '$(srcdir)/'`dddmp/dddmpStoreCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreCnf.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreCnf.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpStoreCnf.c' object='dddmp/cudd_libcudd_la-dddmpStoreCnf.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpStoreCnf.lo `test -f 'dddmp/dddmpStoreCnf.c' || echo '$(srcdir)/'`dddmp/dddmpStoreCnf.c\n\ndddmp/cudd_libcudd_la-dddmpStoreMisc.lo: dddmp/dddmpStoreMisc.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpStoreMisc.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreMisc.Tpo -c -o dddmp/cudd_libcudd_la-dddmpStoreMisc.lo `test -f 'dddmp/dddmpStoreMisc.c' || echo '$(srcdir)/'`dddmp/dddmpStoreMisc.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreMisc.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreMisc.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpStoreMisc.c' object='dddmp/cudd_libcudd_la-dddmpStoreMisc.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpStoreMisc.lo `test -f 'dddmp/dddmpStoreMisc.c' || echo '$(srcdir)/'`dddmp/dddmpStoreMisc.c\n\ndddmp/cudd_libcudd_la-dddmpUtil.lo: dddmp/dddmpUtil.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/cudd_libcudd_la-dddmpUtil.lo -MD -MP -MF dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpUtil.Tpo -c -o dddmp/cudd_libcudd_la-dddmpUtil.lo `test -f 'dddmp/dddmpUtil.c' || echo '$(srcdir)/'`dddmp/dddmpUtil.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpUtil.Tpo dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpUtil.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpUtil.c' object='dddmp/cudd_libcudd_la-dddmpUtil.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/cudd_libcudd_la-dddmpUtil.lo `test -f 'dddmp/dddmpUtil.c' || echo '$(srcdir)/'`dddmp/dddmpUtil.c\n\ndddmp/libdddmp_la-dddmpBinary.lo: dddmp/dddmpBinary.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpBinary.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpBinary.Tpo -c -o dddmp/libdddmp_la-dddmpBinary.lo `test -f 'dddmp/dddmpBinary.c' || echo '$(srcdir)/'`dddmp/dddmpBinary.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpBinary.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpBinary.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpBinary.c' object='dddmp/libdddmp_la-dddmpBinary.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpBinary.lo `test -f 'dddmp/dddmpBinary.c' || echo '$(srcdir)/'`dddmp/dddmpBinary.c\n\ndddmp/libdddmp_la-dddmpConvert.lo: dddmp/dddmpConvert.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpConvert.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpConvert.Tpo -c -o dddmp/libdddmp_la-dddmpConvert.lo `test -f 'dddmp/dddmpConvert.c' || echo '$(srcdir)/'`dddmp/dddmpConvert.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpConvert.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpConvert.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpConvert.c' object='dddmp/libdddmp_la-dddmpConvert.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpConvert.lo `test -f 'dddmp/dddmpConvert.c' || echo '$(srcdir)/'`dddmp/dddmpConvert.c\n\ndddmp/libdddmp_la-dddmpDbg.lo: dddmp/dddmpDbg.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpDbg.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpDbg.Tpo -c -o dddmp/libdddmp_la-dddmpDbg.lo `test -f 'dddmp/dddmpDbg.c' || echo '$(srcdir)/'`dddmp/dddmpDbg.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpDbg.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpDbg.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpDbg.c' object='dddmp/libdddmp_la-dddmpDbg.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpDbg.lo `test -f 'dddmp/dddmpDbg.c' || echo '$(srcdir)/'`dddmp/dddmpDbg.c\n\ndddmp/libdddmp_la-dddmpLoad.lo: dddmp/dddmpLoad.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpLoad.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpLoad.Tpo -c -o dddmp/libdddmp_la-dddmpLoad.lo `test -f 'dddmp/dddmpLoad.c' || echo '$(srcdir)/'`dddmp/dddmpLoad.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpLoad.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpLoad.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpLoad.c' object='dddmp/libdddmp_la-dddmpLoad.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpLoad.lo `test -f 'dddmp/dddmpLoad.c' || echo '$(srcdir)/'`dddmp/dddmpLoad.c\n\ndddmp/libdddmp_la-dddmpLoadCnf.lo: dddmp/dddmpLoadCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpLoadCnf.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpLoadCnf.Tpo -c -o dddmp/libdddmp_la-dddmpLoadCnf.lo `test -f 'dddmp/dddmpLoadCnf.c' || echo '$(srcdir)/'`dddmp/dddmpLoadCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpLoadCnf.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpLoadCnf.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpLoadCnf.c' object='dddmp/libdddmp_la-dddmpLoadCnf.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpLoadCnf.lo `test -f 'dddmp/dddmpLoadCnf.c' || echo '$(srcdir)/'`dddmp/dddmpLoadCnf.c\n\ndddmp/libdddmp_la-dddmpNodeAdd.lo: dddmp/dddmpNodeAdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpNodeAdd.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeAdd.Tpo -c -o dddmp/libdddmp_la-dddmpNodeAdd.lo `test -f 'dddmp/dddmpNodeAdd.c' || echo '$(srcdir)/'`dddmp/dddmpNodeAdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeAdd.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeAdd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpNodeAdd.c' object='dddmp/libdddmp_la-dddmpNodeAdd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpNodeAdd.lo `test -f 'dddmp/dddmpNodeAdd.c' || echo '$(srcdir)/'`dddmp/dddmpNodeAdd.c\n\ndddmp/libdddmp_la-dddmpNodeBdd.lo: dddmp/dddmpNodeBdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpNodeBdd.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeBdd.Tpo -c -o dddmp/libdddmp_la-dddmpNodeBdd.lo `test -f 'dddmp/dddmpNodeBdd.c' || echo '$(srcdir)/'`dddmp/dddmpNodeBdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeBdd.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeBdd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpNodeBdd.c' object='dddmp/libdddmp_la-dddmpNodeBdd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpNodeBdd.lo `test -f 'dddmp/dddmpNodeBdd.c' || echo '$(srcdir)/'`dddmp/dddmpNodeBdd.c\n\ndddmp/libdddmp_la-dddmpNodeCnf.lo: dddmp/dddmpNodeCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpNodeCnf.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeCnf.Tpo -c -o dddmp/libdddmp_la-dddmpNodeCnf.lo `test -f 'dddmp/dddmpNodeCnf.c' || echo '$(srcdir)/'`dddmp/dddmpNodeCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeCnf.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeCnf.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpNodeCnf.c' object='dddmp/libdddmp_la-dddmpNodeCnf.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpNodeCnf.lo `test -f 'dddmp/dddmpNodeCnf.c' || echo '$(srcdir)/'`dddmp/dddmpNodeCnf.c\n\ndddmp/libdddmp_la-dddmpStoreAdd.lo: dddmp/dddmpStoreAdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpStoreAdd.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreAdd.Tpo -c -o dddmp/libdddmp_la-dddmpStoreAdd.lo `test -f 'dddmp/dddmpStoreAdd.c' || echo '$(srcdir)/'`dddmp/dddmpStoreAdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreAdd.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreAdd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpStoreAdd.c' object='dddmp/libdddmp_la-dddmpStoreAdd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpStoreAdd.lo `test -f 'dddmp/dddmpStoreAdd.c' || echo '$(srcdir)/'`dddmp/dddmpStoreAdd.c\n\ndddmp/libdddmp_la-dddmpStoreBdd.lo: dddmp/dddmpStoreBdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpStoreBdd.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreBdd.Tpo -c -o dddmp/libdddmp_la-dddmpStoreBdd.lo `test -f 'dddmp/dddmpStoreBdd.c' || echo '$(srcdir)/'`dddmp/dddmpStoreBdd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreBdd.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreBdd.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpStoreBdd.c' object='dddmp/libdddmp_la-dddmpStoreBdd.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpStoreBdd.lo `test -f 'dddmp/dddmpStoreBdd.c' || echo '$(srcdir)/'`dddmp/dddmpStoreBdd.c\n\ndddmp/libdddmp_la-dddmpStoreCnf.lo: dddmp/dddmpStoreCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpStoreCnf.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreCnf.Tpo -c -o dddmp/libdddmp_la-dddmpStoreCnf.lo `test -f 'dddmp/dddmpStoreCnf.c' || echo '$(srcdir)/'`dddmp/dddmpStoreCnf.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreCnf.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreCnf.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpStoreCnf.c' object='dddmp/libdddmp_la-dddmpStoreCnf.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpStoreCnf.lo `test -f 'dddmp/dddmpStoreCnf.c' || echo '$(srcdir)/'`dddmp/dddmpStoreCnf.c\n\ndddmp/libdddmp_la-dddmpStoreMisc.lo: dddmp/dddmpStoreMisc.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpStoreMisc.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreMisc.Tpo -c -o dddmp/libdddmp_la-dddmpStoreMisc.lo `test -f 'dddmp/dddmpStoreMisc.c' || echo '$(srcdir)/'`dddmp/dddmpStoreMisc.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreMisc.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreMisc.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpStoreMisc.c' object='dddmp/libdddmp_la-dddmpStoreMisc.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpStoreMisc.lo `test -f 'dddmp/dddmpStoreMisc.c' || echo '$(srcdir)/'`dddmp/dddmpStoreMisc.c\n\ndddmp/libdddmp_la-dddmpUtil.lo: dddmp/dddmpUtil.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/libdddmp_la-dddmpUtil.lo -MD -MP -MF dddmp/$(DEPDIR)/libdddmp_la-dddmpUtil.Tpo -c -o dddmp/libdddmp_la-dddmpUtil.lo `test -f 'dddmp/dddmpUtil.c' || echo '$(srcdir)/'`dddmp/dddmpUtil.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/libdddmp_la-dddmpUtil.Tpo dddmp/$(DEPDIR)/libdddmp_la-dddmpUtil.Plo\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/dddmpUtil.c' object='dddmp/libdddmp_la-dddmpUtil.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CC $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_libdddmp_la_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/libdddmp_la-dddmpUtil.lo `test -f 'dddmp/dddmpUtil.c' || echo '$(srcdir)/'`dddmp/dddmpUtil.c\n\ncudd/testcudd-testcudd.o: cudd/testcudd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_testcudd_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/testcudd-testcudd.o -MD -MP -MF cudd/$(DEPDIR)/testcudd-testcudd.Tpo -c -o cudd/testcudd-testcudd.o `test -f 'cudd/testcudd.c' || echo '$(srcdir)/'`cudd/testcudd.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/testcudd-testcudd.Tpo cudd/$(DEPDIR)/testcudd-testcudd.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/testcudd.c' object='cudd/testcudd-testcudd.o' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_testcudd_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/testcudd-testcudd.o `test -f 'cudd/testcudd.c' || echo '$(srcdir)/'`cudd/testcudd.c\n\ncudd/testcudd-testcudd.obj: cudd/testcudd.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_testcudd_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/testcudd-testcudd.obj -MD -MP -MF cudd/$(DEPDIR)/testcudd-testcudd.Tpo -c -o cudd/testcudd-testcudd.obj `if test -f 'cudd/testcudd.c'; then $(CYGPATH_W) 'cudd/testcudd.c'; else $(CYGPATH_W) '$(srcdir)/cudd/testcudd.c'; fi`\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/testcudd-testcudd.Tpo cudd/$(DEPDIR)/testcudd-testcudd.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/testcudd.c' object='cudd/testcudd-testcudd.obj' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_testcudd_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/testcudd-testcudd.obj `if test -f 'cudd/testcudd.c'; then $(CYGPATH_W) 'cudd/testcudd.c'; else $(CYGPATH_W) '$(srcdir)/cudd/testcudd.c'; fi`\n\ncudd/testextra-testextra.o: cudd/testextra.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_testextra_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/testextra-testextra.o -MD -MP -MF cudd/$(DEPDIR)/testextra-testextra.Tpo -c -o cudd/testextra-testextra.o `test -f 'cudd/testextra.c' || echo '$(srcdir)/'`cudd/testextra.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/testextra-testextra.Tpo cudd/$(DEPDIR)/testextra-testextra.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/testextra.c' object='cudd/testextra-testextra.o' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_testextra_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/testextra-testextra.o `test -f 'cudd/testextra.c' || echo '$(srcdir)/'`cudd/testextra.c\n\ncudd/testextra-testextra.obj: cudd/testextra.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_testextra_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT cudd/testextra-testextra.obj -MD -MP -MF cudd/$(DEPDIR)/testextra-testextra.Tpo -c -o cudd/testextra-testextra.obj `if test -f 'cudd/testextra.c'; then $(CYGPATH_W) 'cudd/testextra.c'; else $(CYGPATH_W) '$(srcdir)/cudd/testextra.c'; fi`\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) cudd/$(DEPDIR)/testextra-testextra.Tpo cudd/$(DEPDIR)/testextra-testextra.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='cudd/testextra.c' object='cudd/testextra-testextra.obj' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_testextra_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o cudd/testextra-testextra.obj `if test -f 'cudd/testextra.c'; then $(CYGPATH_W) 'cudd/testextra.c'; else $(CYGPATH_W) '$(srcdir)/cudd/testextra.c'; fi`\n\ndddmp/testdddmp-testdddmp.o: dddmp/testdddmp.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_testdddmp_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/testdddmp-testdddmp.o -MD -MP -MF dddmp/$(DEPDIR)/testdddmp-testdddmp.Tpo -c -o dddmp/testdddmp-testdddmp.o `test -f 'dddmp/testdddmp.c' || echo '$(srcdir)/'`dddmp/testdddmp.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/testdddmp-testdddmp.Tpo dddmp/$(DEPDIR)/testdddmp-testdddmp.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/testdddmp.c' object='dddmp/testdddmp-testdddmp.o' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_testdddmp_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/testdddmp-testdddmp.o `test -f 'dddmp/testdddmp.c' || echo '$(srcdir)/'`dddmp/testdddmp.c\n\ndddmp/testdddmp-testdddmp.obj: dddmp/testdddmp.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_testdddmp_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT dddmp/testdddmp-testdddmp.obj -MD -MP -MF dddmp/$(DEPDIR)/testdddmp-testdddmp.Tpo -c -o dddmp/testdddmp-testdddmp.obj `if test -f 'dddmp/testdddmp.c'; then $(CYGPATH_W) 'dddmp/testdddmp.c'; else $(CYGPATH_W) '$(srcdir)/dddmp/testdddmp.c'; fi`\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) dddmp/$(DEPDIR)/testdddmp-testdddmp.Tpo dddmp/$(DEPDIR)/testdddmp-testdddmp.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='dddmp/testdddmp.c' object='dddmp/testdddmp-testdddmp.obj' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(dddmp_testdddmp_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o dddmp/testdddmp-testdddmp.obj `if test -f 'dddmp/testdddmp.c'; then $(CYGPATH_W) 'dddmp/testdddmp.c'; else $(CYGPATH_W) '$(srcdir)/dddmp/testdddmp.c'; fi`\n\nmtr/testmtr-testmtr.o: mtr/testmtr.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(mtr_testmtr_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT mtr/testmtr-testmtr.o -MD -MP -MF mtr/$(DEPDIR)/testmtr-testmtr.Tpo -c -o mtr/testmtr-testmtr.o `test -f 'mtr/testmtr.c' || echo '$(srcdir)/'`mtr/testmtr.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) mtr/$(DEPDIR)/testmtr-testmtr.Tpo mtr/$(DEPDIR)/testmtr-testmtr.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='mtr/testmtr.c' object='mtr/testmtr-testmtr.o' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(mtr_testmtr_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o mtr/testmtr-testmtr.o `test -f 'mtr/testmtr.c' || echo '$(srcdir)/'`mtr/testmtr.c\n\nmtr/testmtr-testmtr.obj: mtr/testmtr.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(mtr_testmtr_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT mtr/testmtr-testmtr.obj -MD -MP -MF mtr/$(DEPDIR)/testmtr-testmtr.Tpo -c -o mtr/testmtr-testmtr.obj `if test -f 'mtr/testmtr.c'; then $(CYGPATH_W) 'mtr/testmtr.c'; else $(CYGPATH_W) '$(srcdir)/mtr/testmtr.c'; fi`\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) mtr/$(DEPDIR)/testmtr-testmtr.Tpo mtr/$(DEPDIR)/testmtr-testmtr.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='mtr/testmtr.c' object='mtr/testmtr-testmtr.obj' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(mtr_testmtr_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o mtr/testmtr-testmtr.obj `if test -f 'mtr/testmtr.c'; then $(CYGPATH_W) 'mtr/testmtr.c'; else $(CYGPATH_W) '$(srcdir)/mtr/testmtr.c'; fi`\n\nst/testst-testst.o: st/testst.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(st_testst_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT st/testst-testst.o -MD -MP -MF st/$(DEPDIR)/testst-testst.Tpo -c -o st/testst-testst.o `test -f 'st/testst.c' || echo '$(srcdir)/'`st/testst.c\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) st/$(DEPDIR)/testst-testst.Tpo st/$(DEPDIR)/testst-testst.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='st/testst.c' object='st/testst-testst.o' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(st_testst_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o st/testst-testst.o `test -f 'st/testst.c' || echo '$(srcdir)/'`st/testst.c\n\nst/testst-testst.obj: st/testst.c\n@am__fastdepCC_TRUE@\t$(AM_V_CC)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(st_testst_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -MT st/testst-testst.obj -MD -MP -MF st/$(DEPDIR)/testst-testst.Tpo -c -o st/testst-testst.obj `if test -f 'st/testst.c'; then $(CYGPATH_W) 'st/testst.c'; else $(CYGPATH_W) '$(srcdir)/st/testst.c'; fi`\n@am__fastdepCC_TRUE@\t$(AM_V_at)$(am__mv) st/$(DEPDIR)/testst-testst.Tpo st/$(DEPDIR)/testst-testst.Po\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\t$(AM_V_CC)source='st/testst.c' object='st/testst-testst.obj' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCC_FALSE@\tDEPDIR=$(DEPDIR) $(CCDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCC_FALSE@\t$(AM_V_CC@am__nodep@)$(CC) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(st_testst_CPPFLAGS) $(CPPFLAGS) $(AM_CFLAGS) $(CFLAGS) -c -o st/testst-testst.obj `if test -f 'st/testst.c'; then $(CYGPATH_W) 'st/testst.c'; else $(CYGPATH_W) '$(srcdir)/st/testst.c'; fi`\n\n.cc.o:\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\\.o$$||'`;\\\n@am__fastdepCXX_TRUE@\t$(CXXCOMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ $< &&\\\n@am__fastdepCXX_TRUE@\t$(am__mv) $$depbase.Tpo $$depbase.Po\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(CXXCOMPILE) -c -o $@ $<\n\n.cc.obj:\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\\.obj$$||'`;\\\n@am__fastdepCXX_TRUE@\t$(CXXCOMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ `$(CYGPATH_W) '$<'` &&\\\n@am__fastdepCXX_TRUE@\t$(am__mv) $$depbase.Tpo $$depbase.Po\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='$<' object='$@' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(CXXCOMPILE) -c -o $@ `$(CYGPATH_W) '$<'`\n\n.cc.lo:\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)depbase=`echo $@ | sed 's|[^/]*$$|$(DEPDIR)/&|;s|\\.lo$$||'`;\\\n@am__fastdepCXX_TRUE@\t$(LTCXXCOMPILE) -MT $@ -MD -MP -MF $$depbase.Tpo -c -o $@ $< &&\\\n@am__fastdepCXX_TRUE@\t$(am__mv) $$depbase.Tpo $$depbase.Plo\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='$<' object='$@' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(LTCXXCOMPILE) -c -o $@ $<\n\ncplusplus/libobj_la-cuddObj.lo: cplusplus/cuddObj.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)$(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_libobj_la_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT cplusplus/libobj_la-cuddObj.lo -MD -MP -MF cplusplus/$(DEPDIR)/libobj_la-cuddObj.Tpo -c -o cplusplus/libobj_la-cuddObj.lo `test -f 'cplusplus/cuddObj.cc' || echo '$(srcdir)/'`cplusplus/cuddObj.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_at)$(am__mv) cplusplus/$(DEPDIR)/libobj_la-cuddObj.Tpo cplusplus/$(DEPDIR)/libobj_la-cuddObj.Plo\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='cplusplus/cuddObj.cc' object='cplusplus/libobj_la-cuddObj.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CXX $(AM_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_libobj_la_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o cplusplus/libobj_la-cuddObj.lo `test -f 'cplusplus/cuddObj.cc' || echo '$(srcdir)/'`cplusplus/cuddObj.cc\n\ncplusplus/cudd_libcudd_la-cuddObj.lo: cplusplus/cuddObj.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)$(LIBTOOL) $(AM_V_lt) --tag=CXX $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT cplusplus/cudd_libcudd_la-cuddObj.lo -MD -MP -MF cplusplus/$(DEPDIR)/cudd_libcudd_la-cuddObj.Tpo -c -o cplusplus/cudd_libcudd_la-cuddObj.lo `test -f 'cplusplus/cuddObj.cc' || echo '$(srcdir)/'`cplusplus/cuddObj.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_at)$(am__mv) cplusplus/$(DEPDIR)/cudd_libcudd_la-cuddObj.Tpo cplusplus/$(DEPDIR)/cudd_libcudd_la-cuddObj.Plo\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='cplusplus/cuddObj.cc' object='cplusplus/cudd_libcudd_la-cuddObj.lo' libtool=yes @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(LIBTOOL) $(AM_V_lt) --tag=CXX $(cudd_libcudd_la_LIBTOOLFLAGS) $(LIBTOOLFLAGS) --mode=compile $(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cudd_libcudd_la_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o cplusplus/cudd_libcudd_la-cuddObj.lo `test -f 'cplusplus/cuddObj.cc' || echo '$(srcdir)/'`cplusplus/cuddObj.cc\n\ncplusplus/testmulti-testmulti.o: cplusplus/testmulti.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_testmulti_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT cplusplus/testmulti-testmulti.o -MD -MP -MF cplusplus/$(DEPDIR)/testmulti-testmulti.Tpo -c -o cplusplus/testmulti-testmulti.o `test -f 'cplusplus/testmulti.cc' || echo '$(srcdir)/'`cplusplus/testmulti.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_at)$(am__mv) cplusplus/$(DEPDIR)/testmulti-testmulti.Tpo cplusplus/$(DEPDIR)/testmulti-testmulti.Po\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='cplusplus/testmulti.cc' object='cplusplus/testmulti-testmulti.o' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_testmulti_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o cplusplus/testmulti-testmulti.o `test -f 'cplusplus/testmulti.cc' || echo '$(srcdir)/'`cplusplus/testmulti.cc\n\ncplusplus/testmulti-testmulti.obj: cplusplus/testmulti.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_testmulti_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT cplusplus/testmulti-testmulti.obj -MD -MP -MF cplusplus/$(DEPDIR)/testmulti-testmulti.Tpo -c -o cplusplus/testmulti-testmulti.obj `if test -f 'cplusplus/testmulti.cc'; then $(CYGPATH_W) 'cplusplus/testmulti.cc'; else $(CYGPATH_W) '$(srcdir)/cplusplus/testmulti.cc'; fi`\n@am__fastdepCXX_TRUE@\t$(AM_V_at)$(am__mv) cplusplus/$(DEPDIR)/testmulti-testmulti.Tpo cplusplus/$(DEPDIR)/testmulti-testmulti.Po\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='cplusplus/testmulti.cc' object='cplusplus/testmulti-testmulti.obj' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_testmulti_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o cplusplus/testmulti-testmulti.obj `if test -f 'cplusplus/testmulti.cc'; then $(CYGPATH_W) 'cplusplus/testmulti.cc'; else $(CYGPATH_W) '$(srcdir)/cplusplus/testmulti.cc'; fi`\n\ncplusplus/testobj-testobj.o: cplusplus/testobj.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_testobj_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT cplusplus/testobj-testobj.o -MD -MP -MF cplusplus/$(DEPDIR)/testobj-testobj.Tpo -c -o cplusplus/testobj-testobj.o `test -f 'cplusplus/testobj.cc' || echo '$(srcdir)/'`cplusplus/testobj.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_at)$(am__mv) cplusplus/$(DEPDIR)/testobj-testobj.Tpo cplusplus/$(DEPDIR)/testobj-testobj.Po\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='cplusplus/testobj.cc' object='cplusplus/testobj-testobj.o' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_testobj_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o cplusplus/testobj-testobj.o `test -f 'cplusplus/testobj.cc' || echo '$(srcdir)/'`cplusplus/testobj.cc\n\ncplusplus/testobj-testobj.obj: cplusplus/testobj.cc\n@am__fastdepCXX_TRUE@\t$(AM_V_CXX)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_testobj_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -MT cplusplus/testobj-testobj.obj -MD -MP -MF cplusplus/$(DEPDIR)/testobj-testobj.Tpo -c -o cplusplus/testobj-testobj.obj `if test -f 'cplusplus/testobj.cc'; then $(CYGPATH_W) 'cplusplus/testobj.cc'; else $(CYGPATH_W) '$(srcdir)/cplusplus/testobj.cc'; fi`\n@am__fastdepCXX_TRUE@\t$(AM_V_at)$(am__mv) cplusplus/$(DEPDIR)/testobj-testobj.Tpo cplusplus/$(DEPDIR)/testobj-testobj.Po\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\t$(AM_V_CXX)source='cplusplus/testobj.cc' object='cplusplus/testobj-testobj.obj' libtool=no @AMDEPBACKSLASH@\n@AMDEP_TRUE@@am__fastdepCXX_FALSE@\tDEPDIR=$(DEPDIR) $(CXXDEPMODE) $(depcomp) @AMDEPBACKSLASH@\n@am__fastdepCXX_FALSE@\t$(AM_V_CXX@am__nodep@)$(CXX) $(DEFS) $(DEFAULT_INCLUDES) $(INCLUDES) $(cplusplus_testobj_CPPFLAGS) $(CPPFLAGS) $(AM_CXXFLAGS) $(CXXFLAGS) -c -o cplusplus/testobj-testobj.obj `if test -f 'cplusplus/testobj.cc'; then $(CYGPATH_W) 'cplusplus/testobj.cc'; else $(CYGPATH_W) '$(srcdir)/cplusplus/testobj.cc'; fi`\n\nmostlyclean-libtool:\n\t-rm -f *.lo\n\nclean-libtool:\n\t-rm -rf .libs _libs\n\t-rm -rf cplusplus/.libs cplusplus/_libs\n\t-rm -rf cudd/.libs cudd/_libs\n\t-rm -rf dddmp/.libs dddmp/_libs\n\t-rm -rf epd/.libs epd/_libs\n\t-rm -rf mtr/.libs mtr/_libs\n\t-rm -rf st/.libs st/_libs\n\t-rm -rf util/.libs util/_libs\n\ndistclean-libtool:\n\t-rm -f libtool config.lt\ninstall-includeHEADERS: $(include_HEADERS)\n\t@$(NORMAL_INSTALL)\n\t@list='$(include_HEADERS)'; test -n \"$(includedir)\" || list=; \\\n\tif test -n \"$$list\"; then \\\n\t  echo \" $(MKDIR_P) '$(DESTDIR)$(includedir)'\"; \\\n\t  $(MKDIR_P) \"$(DESTDIR)$(includedir)\" || exit 1; \\\n\tfi; \\\n\tfor p in $$list; do \\\n\t  if test -f \"$$p\"; then d=; else d=\"$(srcdir)/\"; fi; \\\n\t  echo \"$$d$$p\"; \\\n\tdone | $(am__base_list) | \\\n\twhile read files; do \\\n\t  echo \" $(INSTALL_HEADER) $$files '$(DESTDIR)$(includedir)'\"; \\\n\t  $(INSTALL_HEADER) $$files \"$(DESTDIR)$(includedir)\" || exit $$?; \\\n\tdone\n\nuninstall-includeHEADERS:\n\t@$(NORMAL_UNINSTALL)\n\t@list='$(include_HEADERS)'; test -n \"$(includedir)\" || list=; \\\n\tfiles=`for p in $$list; do echo $$p; done | sed -e 's|^.*/||'`; \\\n\tdir='$(DESTDIR)$(includedir)'; $(am__uninstall_files_from_dir)\n\nID: $(am__tagged_files)\n\t$(am__define_uniq_tagged_files); mkid -fID $$unique\ntags: tags-am\nTAGS: tags\n\ntags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files)\n\tset x; \\\n\there=`pwd`; \\\n\t$(am__define_uniq_tagged_files); \\\n\tshift; \\\n\tif test -z \"$(ETAGS_ARGS)$$*$$unique\"; then :; else \\\n\t  test -n \"$$unique\" || unique=$$empty_fix; \\\n\t  if test $$# -gt 0; then \\\n\t    $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \\\n\t      \"$$@\" $$unique; \\\n\t  else \\\n\t    $(ETAGS) $(ETAGSFLAGS) $(AM_ETAGSFLAGS) $(ETAGS_ARGS) \\\n\t      $$unique; \\\n\t  fi; \\\n\tfi\nctags: ctags-am\n\nCTAGS: ctags\nctags-am: $(TAGS_DEPENDENCIES) $(am__tagged_files)\n\t$(am__define_uniq_tagged_files); \\\n\ttest -z \"$(CTAGS_ARGS)$$unique\" \\\n\t  || $(CTAGS) $(CTAGSFLAGS) $(AM_CTAGSFLAGS) $(CTAGS_ARGS) \\\n\t     $$unique\n\nGTAGS:\n\there=`$(am__cd) $(top_builddir) && pwd` \\\n\t  && $(am__cd) $(top_srcdir) \\\n\t  && gtags -i $(GTAGS_ARGS) \"$$here\"\ncscope: cscope.files\n\ttest ! -s cscope.files \\\n\t  || $(CSCOPE) -b -q $(AM_CSCOPEFLAGS) $(CSCOPEFLAGS) -i cscope.files $(CSCOPE_ARGS)\nclean-cscope:\n\t-rm -f cscope.files\ncscope.files: clean-cscope cscopelist\ncscopelist: cscopelist-am\n\ncscopelist-am: $(am__tagged_files)\n\tlist='$(am__tagged_files)'; \\\n\tcase \"$(srcdir)\" in \\\n\t  [\\\\/]* | ?:[\\\\/]*) sdir=\"$(srcdir)\" ;; \\\n\t  *) sdir=$(subdir)/$(srcdir) ;; \\\n\tesac; \\\n\tfor i in $$list; do \\\n\t  if test -f \"$$i\"; then \\\n\t    echo \"$(subdir)/$$i\"; \\\n\t  else \\\n\t    echo \"$$sdir/$$i\"; \\\n\t  fi; \\\n\tdone >> $(top_builddir)/cscope.files\n\ndistclean-tags:\n\t-rm -f TAGS ID GTAGS GRTAGS GSYMS GPATH tags\n\t-rm -f cscope.out cscope.in.out cscope.po.out cscope.files\n\n# Recover from deleted '.trs' file; this should ensure that\n# \"rm -f foo.log; make foo.trs\" re-run 'foo.test', and re-create\n# both 'foo.log' and 'foo.trs'.  Break the recipe in two subshells\n# to avoid problems with \"make -n\".\n.log.trs:\n\trm -f $< $@\n\t$(MAKE) $(AM_MAKEFLAGS) $<\n\n# Leading 'am--fnord' is there to ensure the list of targets does not\n# expand to empty, as could happen e.g. with make check TESTS=''.\nam--fnord $(TEST_LOGS) $(TEST_LOGS:.log=.trs): $(am__force_recheck)\nam--force-recheck:\n\t@:\n\n$(TEST_SUITE_LOG): $(TEST_LOGS)\n\t@$(am__set_TESTS_bases); \\\n\tam__f_ok () { test -f \"$$1\" && test -r \"$$1\"; }; \\\n\tredo_bases=`for i in $$bases; do \\\n\t              am__f_ok $$i.trs && am__f_ok $$i.log || echo $$i; \\\n\t            done`; \\\n\tif test -n \"$$redo_bases\"; then \\\n\t  redo_logs=`for i in $$redo_bases; do echo $$i.log; done`; \\\n\t  redo_results=`for i in $$redo_bases; do echo $$i.trs; done`; \\\n\t  if $(am__make_dryrun); then :; else \\\n\t    rm -f $$redo_logs && rm -f $$redo_results || exit 1; \\\n\t  fi; \\\n\tfi; \\\n\tif test -n \"$$am__remaking_logs\"; then \\\n\t  echo \"fatal: making $(TEST_SUITE_LOG): possible infinite\" \\\n\t       \"recursion detected\" >&2; \\\n\telif test -n \"$$redo_logs\"; then \\\n\t  am__remaking_logs=yes $(MAKE) $(AM_MAKEFLAGS) $$redo_logs; \\\n\tfi; \\\n\tif $(am__make_dryrun); then :; else \\\n\t  st=0;  \\\n\t  errmsg=\"fatal: making $(TEST_SUITE_LOG): failed to create\"; \\\n\t  for i in $$redo_bases; do \\\n\t    test -f $$i.trs && test -r $$i.trs \\\n\t      || { echo \"$$errmsg $$i.trs\" >&2; st=1; }; \\\n\t    test -f $$i.log && test -r $$i.log \\\n\t      || { echo \"$$errmsg $$i.log\" >&2; st=1; }; \\\n\t  done; \\\n\t  test $$st -eq 0 || exit 1; \\\n\tfi\n\t@$(am__sh_e_setup); $(am__tty_colors); $(am__set_TESTS_bases); \\\n\tws='[ \t]'; \\\n\tresults=`for b in $$bases; do echo $$b.trs; done`; \\\n\ttest -n \"$$results\" || results=/dev/null; \\\n\tall=`  grep \"^$$ws*:test-result:\"           $$results | wc -l`; \\\n\tpass=` grep \"^$$ws*:test-result:$$ws*PASS\"  $$results | wc -l`; \\\n\tfail=` grep \"^$$ws*:test-result:$$ws*FAIL\"  $$results | wc -l`; \\\n\tskip=` grep \"^$$ws*:test-result:$$ws*SKIP\"  $$results | wc -l`; \\\n\txfail=`grep \"^$$ws*:test-result:$$ws*XFAIL\" $$results | wc -l`; \\\n\txpass=`grep \"^$$ws*:test-result:$$ws*XPASS\" $$results | wc -l`; \\\n\terror=`grep \"^$$ws*:test-result:$$ws*ERROR\" $$results | wc -l`; \\\n\tif test `expr $$fail + $$xpass + $$error` -eq 0; then \\\n\t  success=true; \\\n\telse \\\n\t  success=false; \\\n\tfi; \\\n\tbr='==================='; br=$$br$$br$$br$$br; \\\n\tresult_count () \\\n\t{ \\\n\t    if test x\"$$1\" = x\"--maybe-color\"; then \\\n\t      maybe_colorize=yes; \\\n\t    elif test x\"$$1\" = x\"--no-color\"; then \\\n\t      maybe_colorize=no; \\\n\t    else \\\n\t      echo \"$@: invalid 'result_count' usage\" >&2; exit 4; \\\n\t    fi; \\\n\t    shift; \\\n\t    desc=$$1 count=$$2; \\\n\t    if test $$maybe_colorize = yes && test $$count -gt 0; then \\\n\t      color_start=$$3 color_end=$$std; \\\n\t    else \\\n\t      color_start= color_end=; \\\n\t    fi; \\\n\t    echo \"$${color_start}# $$desc $$count$${color_end}\"; \\\n\t}; \\\n\tcreate_testsuite_report () \\\n\t{ \\\n\t  result_count $$1 \"TOTAL:\" $$all   \"$$brg\"; \\\n\t  result_count $$1 \"PASS: \" $$pass  \"$$grn\"; \\\n\t  result_count $$1 \"SKIP: \" $$skip  \"$$blu\"; \\\n\t  result_count $$1 \"XFAIL:\" $$xfail \"$$lgn\"; \\\n\t  result_count $$1 \"FAIL: \" $$fail  \"$$red\"; \\\n\t  result_count $$1 \"XPASS:\" $$xpass \"$$red\"; \\\n\t  result_count $$1 \"ERROR:\" $$error \"$$mgn\"; \\\n\t}; \\\n\t{\t\t\t\t\t\t\t\t\\\n\t  echo \"$(PACKAGE_STRING): $(subdir)/$(TEST_SUITE_LOG)\" |\t\\\n\t    $(am__rst_title);\t\t\t\t\t\t\\\n\t  create_testsuite_report --no-color;\t\t\t\t\\\n\t  echo;\t\t\t\t\t\t\t\t\\\n\t  echo \".. contents:: :depth: 2\";\t\t\t\t\\\n\t  echo;\t\t\t\t\t\t\t\t\\\n\t  for b in $$bases; do echo $$b; done\t\t\t\t\\\n\t    | $(am__create_global_log);\t\t\t\t\t\\\n\t} >$(TEST_SUITE_LOG).tmp || exit 1;\t\t\t\t\\\n\tmv $(TEST_SUITE_LOG).tmp $(TEST_SUITE_LOG);\t\t\t\\\n\tif $$success; then\t\t\t\t\t\t\\\n\t  col=\"$$grn\";\t\t\t\t\t\t\t\\\n\t else\t\t\t\t\t\t\t\t\\\n\t  col=\"$$red\";\t\t\t\t\t\t\t\\\n\t  test x\"$$VERBOSE\" = x || cat $(TEST_SUITE_LOG);\t\t\\\n\tfi;\t\t\t\t\t\t\t\t\\\n\techo \"$${col}$$br$${std}\"; \t\t\t\t\t\\\n\techo \"$${col}Testsuite summary\"$(AM_TESTSUITE_SUMMARY_HEADER)\"$${std}\";\t\\\n\techo \"$${col}$$br$${std}\"; \t\t\t\t\t\\\n\tcreate_testsuite_report --maybe-color;\t\t\t\t\\\n\techo \"$$col$$br$$std\";\t\t\t\t\t\t\\\n\tif $$success; then :; else\t\t\t\t\t\\\n\t  echo \"$${col}See $(subdir)/$(TEST_SUITE_LOG)$${std}\";\t\t\\\n\t  if test -n \"$(PACKAGE_BUGREPORT)\"; then\t\t\t\\\n\t    echo \"$${col}Please report to $(PACKAGE_BUGREPORT)$${std}\";\t\\\n\t  fi;\t\t\t\t\t\t\t\t\\\n\t  echo \"$$col$$br$$std\";\t\t\t\t\t\\\n\tfi;\t\t\t\t\t\t\t\t\\\n\t$$success || exit 1\n\ncheck-TESTS: $(check_PROGRAMS) $(check_SCRIPTS) $(dist_check_DATA)\n\t@list='$(RECHECK_LOGS)';           test -z \"$$list\" || rm -f $$list\n\t@list='$(RECHECK_LOGS:.log=.trs)'; test -z \"$$list\" || rm -f $$list\n\t@test -z \"$(TEST_SUITE_LOG)\" || rm -f $(TEST_SUITE_LOG)\n\t@set +e; $(am__set_TESTS_bases); \\\n\tlog_list=`for i in $$bases; do echo $$i.log; done`; \\\n\ttrs_list=`for i in $$bases; do echo $$i.trs; done`; \\\n\tlog_list=`echo $$log_list`; trs_list=`echo $$trs_list`; \\\n\t$(MAKE) $(AM_MAKEFLAGS) $(TEST_SUITE_LOG) TEST_LOGS=\"$$log_list\"; \\\n\texit $$?;\nrecheck: all $(check_PROGRAMS) $(check_SCRIPTS) $(dist_check_DATA)\n\t@test -z \"$(TEST_SUITE_LOG)\" || rm -f $(TEST_SUITE_LOG)\n\t@set +e; $(am__set_TESTS_bases); \\\n\tbases=`for i in $$bases; do echo $$i; done \\\n\t         | $(am__list_recheck_tests)` || exit 1; \\\n\tlog_list=`for i in $$bases; do echo $$i.log; done`; \\\n\tlog_list=`echo $$log_list`; \\\n\t$(MAKE) $(AM_MAKEFLAGS) $(TEST_SUITE_LOG) \\\n\t        am__force_recheck=am--force-recheck \\\n\t        TEST_LOGS=\"$$log_list\"; \\\n\texit $$?\n.test.log:\n\t@p='$<'; \\\n\t$(am__set_b); \\\n\t$(am__check_pre) $(TEST_LOG_DRIVER) --test-name \"$$f\" \\\n\t--log-file $$b.log --trs-file $$b.trs \\\n\t$(am__common_driver_flags) $(AM_TEST_LOG_DRIVER_FLAGS) $(TEST_LOG_DRIVER_FLAGS) -- $(TEST_LOG_COMPILE) \\\n\t\"$$tst\" $(AM_TESTS_FD_REDIRECT)\n@am__EXEEXT_TRUE@.test$(EXEEXT).log:\n@am__EXEEXT_TRUE@\t@p='$<'; \\\n@am__EXEEXT_TRUE@\t$(am__set_b); \\\n@am__EXEEXT_TRUE@\t$(am__check_pre) $(TEST_LOG_DRIVER) --test-name \"$$f\" \\\n@am__EXEEXT_TRUE@\t--log-file $$b.log --trs-file $$b.trs \\\n@am__EXEEXT_TRUE@\t$(am__common_driver_flags) $(AM_TEST_LOG_DRIVER_FLAGS) $(TEST_LOG_DRIVER_FLAGS) -- $(TEST_LOG_COMPILE) \\\n@am__EXEEXT_TRUE@\t\"$$tst\" $(AM_TESTS_FD_REDIRECT)\ndistdir: $(BUILT_SOURCES)\n\t$(MAKE) $(AM_MAKEFLAGS) distdir-am\n\ndistdir-am: $(DISTFILES)\n\t$(am__remove_distdir)\n\ttest -d \"$(distdir)\" || mkdir \"$(distdir)\"\n\t@srcdirstrip=`echo \"$(srcdir)\" | sed 's/[].[^$$\\\\*]/\\\\\\\\&/g'`; \\\n\ttopsrcdirstrip=`echo \"$(top_srcdir)\" | sed 's/[].[^$$\\\\*]/\\\\\\\\&/g'`; \\\n\tlist='$(DISTFILES)'; \\\n\t  dist_files=`for file in $$list; do echo $$file; done | \\\n\t  sed -e \"s|^$$srcdirstrip/||;t\" \\\n\t      -e \"s|^$$topsrcdirstrip/|$(top_builddir)/|;t\"`; \\\n\tcase $$dist_files in \\\n\t  */*) $(MKDIR_P) `echo \"$$dist_files\" | \\\n\t\t\t   sed '/\\//!d;s|^|$(distdir)/|;s,/[^/]*$$,,' | \\\n\t\t\t   sort -u` ;; \\\n\tesac; \\\n\tfor file in $$dist_files; do \\\n\t  if test -f $$file || test -d $$file; then d=.; else d=$(srcdir); fi; \\\n\t  if test -d $$d/$$file; then \\\n\t    dir=`echo \"/$$file\" | sed -e 's,/[^/]*$$,,'`; \\\n\t    if test -d \"$(distdir)/$$file\"; then \\\n\t      find \"$(distdir)/$$file\" -type d ! -perm -700 -exec chmod u+rwx {} \\;; \\\n\t    fi; \\\n\t    if test -d $(srcdir)/$$file && test $$d != $(srcdir); then \\\n\t      cp -fpR $(srcdir)/$$file \"$(distdir)$$dir\" || exit 1; \\\n\t      find \"$(distdir)/$$file\" -type d ! -perm -700 -exec chmod u+rwx {} \\;; \\\n\t    fi; \\\n\t    cp -fpR $$d/$$file \"$(distdir)$$dir\" || exit 1; \\\n\t  else \\\n\t    test -f \"$(distdir)/$$file\" \\\n\t    || cp -p $$d/$$file \"$(distdir)/$$file\" \\\n\t    || exit 1; \\\n\t  fi; \\\n\tdone\n\t$(MAKE) $(AM_MAKEFLAGS) \\\n\t  top_distdir=\"$(top_distdir)\" distdir=\"$(distdir)\" \\\n\t  dist-hook\n\t-test -n \"$(am__skip_mode_fix)\" \\\n\t|| find \"$(distdir)\" -type d ! -perm -755 \\\n\t\t-exec chmod u+rwx,go+rx {} \\; -o \\\n\t  ! -type d ! -perm -444 -links 1 -exec chmod a+r {} \\; -o \\\n\t  ! -type d ! -perm -400 -exec chmod a+r {} \\; -o \\\n\t  ! -type d ! -perm -444 -exec $(install_sh) -c -m a+r {} {} \\; \\\n\t|| chmod -R a+r \"$(distdir)\"\ndist-gzip: distdir\n\ttardir=$(distdir) && $(am__tar) | eval GZIP= gzip $(GZIP_ENV) -c >$(distdir).tar.gz\n\t$(am__post_remove_distdir)\n\ndist-bzip2: distdir\n\ttardir=$(distdir) && $(am__tar) | BZIP2=$${BZIP2--9} bzip2 -c >$(distdir).tar.bz2\n\t$(am__post_remove_distdir)\n\ndist-lzip: distdir\n\ttardir=$(distdir) && $(am__tar) | lzip -c $${LZIP_OPT--9} >$(distdir).tar.lz\n\t$(am__post_remove_distdir)\n\ndist-xz: distdir\n\ttardir=$(distdir) && $(am__tar) | XZ_OPT=$${XZ_OPT--e} xz -c >$(distdir).tar.xz\n\t$(am__post_remove_distdir)\n\ndist-zstd: distdir\n\ttardir=$(distdir) && $(am__tar) | zstd -c $${ZSTD_CLEVEL-$${ZSTD_OPT--19}} >$(distdir).tar.zst\n\t$(am__post_remove_distdir)\n\ndist-tarZ: distdir\n\t@echo WARNING: \"Support for distribution archives compressed with\" \\\n\t\t       \"legacy program 'compress' is deprecated.\" >&2\n\t@echo WARNING: \"It will be removed altogether in Automake 2.0\" >&2\n\ttardir=$(distdir) && $(am__tar) | compress -c >$(distdir).tar.Z\n\t$(am__post_remove_distdir)\n\ndist-shar: distdir\n\t@echo WARNING: \"Support for shar distribution archives is\" \\\n\t               \"deprecated.\" >&2\n\t@echo WARNING: \"It will be removed altogether in Automake 2.0\" >&2\n\tshar $(distdir) | eval GZIP= gzip $(GZIP_ENV) -c >$(distdir).shar.gz\n\t$(am__post_remove_distdir)\n\ndist-zip: distdir\n\t-rm -f $(distdir).zip\n\tzip -rq $(distdir).zip $(distdir)\n\t$(am__post_remove_distdir)\n\ndist dist-all:\n\t$(MAKE) $(AM_MAKEFLAGS) $(DIST_TARGETS) am__post_remove_distdir='@:'\n\t$(am__post_remove_distdir)\n\n# This target untars the dist file and tries a VPATH configuration.  Then\n# it guarantees that the distribution is self-contained by making another\n# tarfile.\ndistcheck: dist\n\tcase '$(DIST_ARCHIVES)' in \\\n\t*.tar.gz*) \\\n\t  eval GZIP= gzip $(GZIP_ENV) -dc $(distdir).tar.gz | $(am__untar) ;;\\\n\t*.tar.bz2*) \\\n\t  bzip2 -dc $(distdir).tar.bz2 | $(am__untar) ;;\\\n\t*.tar.lz*) \\\n\t  lzip -dc $(distdir).tar.lz | $(am__untar) ;;\\\n\t*.tar.xz*) \\\n\t  xz -dc $(distdir).tar.xz | $(am__untar) ;;\\\n\t*.tar.Z*) \\\n\t  uncompress -c $(distdir).tar.Z | $(am__untar) ;;\\\n\t*.shar.gz*) \\\n\t  eval GZIP= gzip $(GZIP_ENV) -dc $(distdir).shar.gz | unshar ;;\\\n\t*.zip*) \\\n\t  unzip $(distdir).zip ;;\\\n\t*.tar.zst*) \\\n\t  zstd -dc $(distdir).tar.zst | $(am__untar) ;;\\\n\tesac\n\tchmod -R a-w $(distdir)\n\tchmod u+w $(distdir)\n\tmkdir $(distdir)/_build $(distdir)/_build/sub $(distdir)/_inst\n\tchmod a-w $(distdir)\n\ttest -d $(distdir)/_build || exit 0; \\\n\tdc_install_base=`$(am__cd) $(distdir)/_inst && pwd | sed -e 's,^[^:\\\\/]:[\\\\/],/,'` \\\n\t  && dc_destdir=\"$${TMPDIR-/tmp}/am-dc-$$$$/\" \\\n\t  && am__cwd=`pwd` \\\n\t  && $(am__cd) $(distdir)/_build/sub \\\n\t  && ../../configure \\\n\t    $(AM_DISTCHECK_CONFIGURE_FLAGS) \\\n\t    $(DISTCHECK_CONFIGURE_FLAGS) \\\n\t    --srcdir=../.. --prefix=\"$$dc_install_base\" \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) $(AM_DISTCHECK_DVI_TARGET) \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) check \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) install \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) installcheck \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) uninstall \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) distuninstallcheck_dir=\"$$dc_install_base\" \\\n\t        distuninstallcheck \\\n\t  && chmod -R a-w \"$$dc_install_base\" \\\n\t  && ({ \\\n\t       (cd ../.. && umask 077 && mkdir \"$$dc_destdir\") \\\n\t       && $(MAKE) $(AM_MAKEFLAGS) DESTDIR=\"$$dc_destdir\" install \\\n\t       && $(MAKE) $(AM_MAKEFLAGS) DESTDIR=\"$$dc_destdir\" uninstall \\\n\t       && $(MAKE) $(AM_MAKEFLAGS) DESTDIR=\"$$dc_destdir\" \\\n\t            distuninstallcheck_dir=\"$$dc_destdir\" distuninstallcheck; \\\n\t      } || { rm -rf \"$$dc_destdir\"; exit 1; }) \\\n\t  && rm -rf \"$$dc_destdir\" \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) dist \\\n\t  && rm -rf $(DIST_ARCHIVES) \\\n\t  && $(MAKE) $(AM_MAKEFLAGS) distcleancheck \\\n\t  && cd \"$$am__cwd\" \\\n\t  || exit 1\n\t$(am__post_remove_distdir)\n\t@(echo \"$(distdir) archives ready for distribution: \"; \\\n\t  list='$(DIST_ARCHIVES)'; for i in $$list; do echo $$i; done) | \\\n\t  sed -e 1h -e 1s/./=/g -e 1p -e 1x -e '$$p' -e '$$x'\ndistuninstallcheck:\n\t@test -n '$(distuninstallcheck_dir)' || { \\\n\t  echo 'ERROR: trying to run $@ with an empty' \\\n\t       '$$(distuninstallcheck_dir)' >&2; \\\n\t  exit 1; \\\n\t}; \\\n\t$(am__cd) '$(distuninstallcheck_dir)' || { \\\n\t  echo 'ERROR: cannot chdir into $(distuninstallcheck_dir)' >&2; \\\n\t  exit 1; \\\n\t}; \\\n\ttest `$(am__distuninstallcheck_listfiles) | wc -l` -eq 0 \\\n\t   || { echo \"ERROR: files left after uninstall:\" ; \\\n\t        if test -n \"$(DESTDIR)\"; then \\\n\t          echo \"  (check DESTDIR support)\"; \\\n\t        fi ; \\\n\t        $(distuninstallcheck_listfiles) ; \\\n\t        exit 1; } >&2\ndistcleancheck: distclean\n\t@if test '$(srcdir)' = . ; then \\\n\t  echo \"ERROR: distcleancheck can only run from a VPATH build\" ; \\\n\t  exit 1 ; \\\n\tfi\n\t@test `$(distcleancheck_listfiles) | wc -l` -eq 0 \\\n\t  || { echo \"ERROR: files left in build directory after distclean:\" ; \\\n\t       $(distcleancheck_listfiles) ; \\\n\t       exit 1; } >&2\ncheck-am: all-am\n\t$(MAKE) $(AM_MAKEFLAGS) $(check_PROGRAMS) $(check_SCRIPTS) \\\n\t  $(dist_check_DATA)\n\t$(MAKE) $(AM_MAKEFLAGS) check-TESTS\ncheck: check-am\nall-am: Makefile $(LTLIBRARIES) $(HEADERS) config.h\ninstall-checkPROGRAMS: install-libLTLIBRARIES\n\ninstalldirs:\n\tfor dir in \"$(DESTDIR)$(libdir)\" \"$(DESTDIR)$(includedir)\"; do \\\n\t  test -z \"$$dir\" || $(MKDIR_P) \"$$dir\"; \\\n\tdone\ninstall: install-am\ninstall-exec: install-exec-am\ninstall-data: install-data-am\nuninstall: uninstall-am\n\ninstall-am: all-am\n\t@$(MAKE) $(AM_MAKEFLAGS) install-exec-am install-data-am\n\ninstallcheck: installcheck-am\ninstall-strip:\n\tif test -z '$(STRIP)'; then \\\n\t  $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM=\"$(INSTALL_STRIP_PROGRAM)\" \\\n\t    install_sh_PROGRAM=\"$(INSTALL_STRIP_PROGRAM)\" INSTALL_STRIP_FLAG=-s \\\n\t      install; \\\n\telse \\\n\t  $(MAKE) $(AM_MAKEFLAGS) INSTALL_PROGRAM=\"$(INSTALL_STRIP_PROGRAM)\" \\\n\t    install_sh_PROGRAM=\"$(INSTALL_STRIP_PROGRAM)\" INSTALL_STRIP_FLAG=-s \\\n\t    \"INSTALL_PROGRAM_ENV=STRIPPROG='$(STRIP)'\" install; \\\n\tfi\nmostlyclean-generic:\n\t-test -z \"$(TEST_LOGS)\" || rm -f $(TEST_LOGS)\n\t-test -z \"$(TEST_LOGS:.log=.trs)\" || rm -f $(TEST_LOGS:.log=.trs)\n\t-test -z \"$(TEST_SUITE_LOG)\" || rm -f $(TEST_SUITE_LOG)\n\nclean-generic:\n\t-test -z \"$(CLEANFILES)\" || rm -f $(CLEANFILES)\n\ndistclean-generic:\n\t-test -z \"$(CONFIG_CLEAN_FILES)\" || rm -f $(CONFIG_CLEAN_FILES)\n\t-test . = \"$(srcdir)\" || test -z \"$(CONFIG_CLEAN_VPATH_FILES)\" || rm -f $(CONFIG_CLEAN_VPATH_FILES)\n\t-rm -f cplusplus/$(DEPDIR)/$(am__dirstamp)\n\t-rm -f cplusplus/$(am__dirstamp)\n\t-rm -f cudd/$(DEPDIR)/$(am__dirstamp)\n\t-rm -f cudd/$(am__dirstamp)\n\t-rm -f dddmp/$(DEPDIR)/$(am__dirstamp)\n\t-rm -f dddmp/$(am__dirstamp)\n\t-rm -f epd/$(DEPDIR)/$(am__dirstamp)\n\t-rm -f epd/$(am__dirstamp)\n\t-rm -f mtr/$(DEPDIR)/$(am__dirstamp)\n\t-rm -f mtr/$(am__dirstamp)\n\t-rm -f st/$(DEPDIR)/$(am__dirstamp)\n\t-rm -f st/$(am__dirstamp)\n\t-rm -f util/$(DEPDIR)/$(am__dirstamp)\n\t-rm -f util/$(am__dirstamp)\n\nmaintainer-clean-generic:\n\t@echo \"This command is intended for maintainers to use\"\n\t@echo \"it deletes files that may require special tools to rebuild.\"\n@HAVE_DOXYGEN_FALSE@clean-local:\nclean: clean-am\n\nclean-am: clean-checkPROGRAMS clean-generic clean-libLTLIBRARIES \\\n\tclean-libtool clean-local clean-noinstLTLIBRARIES \\\n\tmostlyclean-am\n\ndistclean: distclean-am\n\t-rm -f $(am__CONFIG_DISTCLEAN_FILES)\n\t\t-rm -f cplusplus/$(DEPDIR)/cudd_libcudd_la-cuddObj.Plo\n\t-rm -f cplusplus/$(DEPDIR)/libobj_la-cuddObj.Plo\n\t-rm -f cplusplus/$(DEPDIR)/testmulti-testmulti.Po\n\t-rm -f cplusplus/$(DEPDIR)/testobj-testobj.Po\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAPI.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddAbs.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddApply.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddFind.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddInv.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddIte.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddNeg.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddWalsh.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAndAbs.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAnneal.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddApa.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddApprox.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddBddAbs.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddBddCorr.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddBddIte.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddBridge.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddCache.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddCheck.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddClip.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddCof.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddCompose.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddDecomp.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddEssent.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddExact.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddExport.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddGenCof.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddGenetic.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddGroup.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddHarwell.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddInit.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddInteract.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddLCache.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddLevelQ.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddLinear.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddLiteral.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddMatMult.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddPriority.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddRead.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddRef.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddReorder.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSat.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSign.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSolve.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSplit.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSubsetHB.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSubsetSP.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSymmetry.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddTable.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddUtil.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddWindow.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddCount.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddFuncs.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddGroup.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddIsop.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddLin.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddMisc.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddPort.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddReord.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddSetop.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddSymm.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddUtil.Plo\n\t-rm -f cudd/$(DEPDIR)/testcudd-testcudd.Po\n\t-rm -f cudd/$(DEPDIR)/testextra-testextra.Po\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpBinary.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpConvert.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpDbg.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoad.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoadCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeAdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeBdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreAdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreBdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreMisc.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpUtil.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpBinary.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpConvert.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpDbg.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpLoad.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpLoadCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeAdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeBdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreAdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreBdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreMisc.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpUtil.Plo\n\t-rm -f dddmp/$(DEPDIR)/testdddmp-testdddmp.Po\n\t-rm -f epd/$(DEPDIR)/cudd_libcudd_la-epd.Plo\n\t-rm -f mtr/$(DEPDIR)/cudd_libcudd_la-mtrBasic.Plo\n\t-rm -f mtr/$(DEPDIR)/cudd_libcudd_la-mtrGroup.Plo\n\t-rm -f mtr/$(DEPDIR)/testmtr-testmtr.Po\n\t-rm -f st/$(DEPDIR)/cudd_libcudd_la-st.Plo\n\t-rm -f st/$(DEPDIR)/testst-testst.Po\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-cpu_stats.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-cpu_time.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-cstringstream.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-datalimit.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-pathsearch.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-pipefork.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-prtime.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-safe_mem.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-strsav.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-texpand.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-ucbqsort.Plo\n\t-rm -f Makefile\ndistclean-am: clean-am distclean-compile distclean-generic \\\n\tdistclean-hdr distclean-libtool distclean-tags\n\ndvi: dvi-am\n\ndvi-am:\n\nhtml: html-am\n\nhtml-am:\n\ninfo: info-am\n\ninfo-am:\n\ninstall-data-am: install-includeHEADERS\n\ninstall-dvi: install-dvi-am\n\ninstall-dvi-am:\n\ninstall-exec-am: install-libLTLIBRARIES\n\ninstall-html: install-html-am\n\ninstall-html-am:\n\ninstall-info: install-info-am\n\ninstall-info-am:\n\ninstall-man:\n\ninstall-pdf: install-pdf-am\n\ninstall-pdf-am:\n\ninstall-ps: install-ps-am\n\ninstall-ps-am:\n\ninstallcheck-am:\n\nmaintainer-clean: maintainer-clean-am\n\t-rm -f $(am__CONFIG_DISTCLEAN_FILES)\n\t-rm -rf $(top_srcdir)/autom4te.cache\n\t\t-rm -f cplusplus/$(DEPDIR)/cudd_libcudd_la-cuddObj.Plo\n\t-rm -f cplusplus/$(DEPDIR)/libobj_la-cuddObj.Plo\n\t-rm -f cplusplus/$(DEPDIR)/testmulti-testmulti.Po\n\t-rm -f cplusplus/$(DEPDIR)/testobj-testobj.Po\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAPI.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddAbs.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddApply.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddFind.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddInv.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddIte.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddNeg.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAddWalsh.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAndAbs.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddAnneal.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddApa.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddApprox.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddBddAbs.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddBddCorr.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddBddIte.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddBridge.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddCache.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddCheck.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddClip.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddCof.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddCompose.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddDecomp.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddEssent.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddExact.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddExport.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddGenCof.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddGenetic.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddGroup.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddHarwell.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddInit.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddInteract.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddLCache.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddLevelQ.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddLinear.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddLiteral.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddMatMult.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddPriority.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddRead.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddRef.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddReorder.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSat.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSign.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSolve.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSplit.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSubsetHB.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSubsetSP.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddSymmetry.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddTable.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddUtil.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddWindow.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddCount.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddFuncs.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddGroup.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddIsop.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddLin.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddMisc.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddPort.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddReord.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddSetop.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddSymm.Plo\n\t-rm -f cudd/$(DEPDIR)/libcudd_la-cuddZddUtil.Plo\n\t-rm -f cudd/$(DEPDIR)/testcudd-testcudd.Po\n\t-rm -f cudd/$(DEPDIR)/testextra-testextra.Po\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpBinary.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpConvert.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpDbg.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoad.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpLoadCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeAdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeBdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpNodeCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreAdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreBdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpStoreMisc.Plo\n\t-rm -f dddmp/$(DEPDIR)/cudd_libcudd_la-dddmpUtil.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpBinary.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpConvert.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpDbg.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpLoad.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpLoadCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeAdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeBdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpNodeCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreAdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreBdd.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreCnf.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpStoreMisc.Plo\n\t-rm -f dddmp/$(DEPDIR)/libdddmp_la-dddmpUtil.Plo\n\t-rm -f dddmp/$(DEPDIR)/testdddmp-testdddmp.Po\n\t-rm -f epd/$(DEPDIR)/cudd_libcudd_la-epd.Plo\n\t-rm -f mtr/$(DEPDIR)/cudd_libcudd_la-mtrBasic.Plo\n\t-rm -f mtr/$(DEPDIR)/cudd_libcudd_la-mtrGroup.Plo\n\t-rm -f mtr/$(DEPDIR)/testmtr-testmtr.Po\n\t-rm -f st/$(DEPDIR)/cudd_libcudd_la-st.Plo\n\t-rm -f st/$(DEPDIR)/testst-testst.Po\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-cpu_stats.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-cpu_time.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-cstringstream.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-datalimit.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-pathsearch.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-pipefork.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-prtime.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-safe_mem.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-strsav.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-texpand.Plo\n\t-rm -f util/$(DEPDIR)/cudd_libcudd_la-ucbqsort.Plo\n\t-rm -f Makefile\nmaintainer-clean-am: distclean-am maintainer-clean-generic\n\nmostlyclean: mostlyclean-am\n\nmostlyclean-am: mostlyclean-compile mostlyclean-generic \\\n\tmostlyclean-libtool\n\npdf: pdf-am\n\npdf-am:\n\nps: ps-am\n\nps-am:\n\nuninstall-am: uninstall-includeHEADERS uninstall-libLTLIBRARIES\n\n.MAKE: all check-am install-am install-strip\n\n.PHONY: CTAGS GTAGS TAGS all all-am am--depfiles am--refresh check \\\n\tcheck-TESTS check-am clean clean-checkPROGRAMS clean-cscope \\\n\tclean-generic clean-libLTLIBRARIES clean-libtool clean-local \\\n\tclean-noinstLTLIBRARIES cscope cscopelist-am ctags ctags-am \\\n\tdist dist-all dist-bzip2 dist-gzip dist-hook dist-lzip \\\n\tdist-shar dist-tarZ dist-xz dist-zip dist-zstd distcheck \\\n\tdistclean distclean-compile distclean-generic distclean-hdr \\\n\tdistclean-libtool distclean-tags distcleancheck distdir \\\n\tdistuninstallcheck dvi dvi-am html html-am info info-am \\\n\tinstall install-am install-data install-data-am install-dvi \\\n\tinstall-dvi-am install-exec install-exec-am install-html \\\n\tinstall-html-am install-includeHEADERS install-info \\\n\tinstall-info-am install-libLTLIBRARIES install-man install-pdf \\\n\tinstall-pdf-am install-ps install-ps-am install-strip \\\n\tinstallcheck installcheck-am installdirs maintainer-clean \\\n\tmaintainer-clean-generic mostlyclean mostlyclean-compile \\\n\tmostlyclean-generic mostlyclean-libtool pdf pdf-am ps ps-am \\\n\trecheck tags tags-am uninstall uninstall-am \\\n\tuninstall-includeHEADERS uninstall-libLTLIBRARIES\n\n.PRECIOUS: Makefile\n\n\ncudd/test_cudd.test: cudd/test_cudd.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\nst/test_st.test: st/test_st.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\nmtr/test_mtr.test: mtr/test_mtr.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\ndddmp/test_dddmp.test: dddmp/test_dddmp.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\ncplusplus/test_obj.test: cplusplus/test_obj.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\n#include $(top_srcdir)/nanotrav/Included.am\n#include $(top_srcdir)/doc/Included.am\n\ndist-hook:\n\trm -rf `find $(distdir) -name .svn`\n\n.PHONY : \n\nall: #html/index.html doc/cudd.pdf\n\n@HAVE_DOXYGEN_TRUE@html/index.html: Doxyfile $(lib_LTLIBRARIES)\n@HAVE_DOXYGEN_TRUE@\t@if $(AM_V_P); then dest='2>&1'; else dest='> /dev/null 2>&1'; fi; \\\n@HAVE_DOXYGEN_TRUE@\teval \"$(DOXYGEN) $< $${dest}\"\n\n@HAVE_DOXYGEN_TRUE@clean-local:\n@HAVE_DOXYGEN_TRUE@\trm -rf html doxygen_sqlite3.db\n\n@HAVE_DOXYGEN_FALSE@html/index.html:\n\n# Tell versions [3.59,3.63) of GNU make to not export all variables.\n# Otherwise a system limit (for SysV at least) may be exceeded.\n.NOEXPORT:\n"
  },
  {
    "path": "cudd/README",
    "content": "The CUDD package is a package written in C for the manipulation of\ndecision diagrams.  It supports binary decision diagrams (BDDs),\nalgebraic decision diagrams (ADDs), and Zero-Suppressed BDDs (ZDDs).\n\nThis directory contains a set of packages that allow you to build a test\napplication based on the CUDD package.\n\nThe test application provided in this kit is called nanotrav and is a\nsimple-minded FSM traversal program.  (See the README file and the man\npage nanotrav.1 in the nanotrav directory for the details.)  It is\nincluded so that you can run a sanity check on your installation.\n\nAlso included in this distribution are the dddmp libray by Giampiero\nCabodi and Stefano Quer and a C++ object-oriented wrapper for CUDD.\n\nBUILD AND INSTALLATION\n\nIn the simplest form, you can build the static libraries with:\n\n  ./configure\n  make\n  make check\n\nThe configure script provides a few options, which can be listed with\n\n  ./configure --help\n\nNotable options include\n\n  --enable-silent-rules\n  --enable-shared\n  --enable-dddmp\n  --enable-obj\n  --with-system-qsort\n\nThe --enable-silent-rules option is a standard option that streamlines the\nmessages produced by the build process.  The remaining options are specific\nto CUDD.\n\nThe three \"enable\" options control the build of shared libraries.  By\ndefault, only static libraries are built.  With --enable-shared, a\nshared library for libcudd is built.  (Before installation, it can be\nfound in cudd/.libs.)\n\nThe last two \"enable\" options control the inclusion of the dddmp\nlibrary and C++ wrapper in the shared library, which by default only\ncontains the core CUDD library.\n\nThe --with-system-qsort option requests use of the qsort from the\nstandard library instead of the portable one shipped with CUDD.  This\noption is provided for backward compatibility and is not otherwise\nrecommended.  Some of the tests of \"make check\" may fail with the\nsystem qsort because variable orders may be generated that are\ndifferent from the reference ones.\n\nAs an example, a more elaborate build command sequence may be:\n\n  ./configure CC=clang CXX=clang++ --enable-silent-rules \\\n    --enable-shared --enable-obj\n  make -j4 check\n  make install\n\nwhich selects alternate compilers instead of gcc and g++, causes the\nC++ wrapper to be included in the shared library, enables parallel\ncompilation (with -j4) and finally installs the shared library using\nthe default prefix /usr/local.\n\nFor those unfamiliar with libtool it may be worth noting that the\nlibraries it builds go in .libs subdirectories.  One should also note\nthat with shared libraries enabled, the test programs immediately\nvisible to the user are shell scripts that make sure dynamic linking\nworks before installation.  If you want to run valgrind on, say, a\ndynamically linked nanotrav, specify the option --trace-children=yes.\n\nPLATFORMS\n\nThis kit has been successfully built on the following configurations:\n\n    PC (x86 and x86_64) running Ubuntu with gcc and clang\n    PC (x86 and x86_64) running Ubuntu with g++\n    PC (x86 and x86_64) running Linux RedHat with gcc\n    PC (x86 and x86_64) running Linux RedHat with g++\n    PC (x86_64) running 32-bit Cygwin on Windows 7 and Vista with gcc\n    PC (x86_64) running 32-bit Cygwin on Windows 7 and Vista with g++\n    PC (x86_64) running 64-bit Cygwin on Windows 8.1 with gcc and g++\n    PC (x86_64) running MinGW-w64 on Windows 8.1 with gcc\n\nIn all these cases, the C++ wrapper was compiled with the matching C++\ncompiler (g++ for gcc and clang++ for clang).  To compile under MSYS2\n(MinGW-w64) one has to pass --build=x86_64-w64-mingw32 to ./configure.\n\nSANITY CHECK\n\nThe directory `nanotrav' contains a simple application based on the\nCUDD package.  The `nanotrav' directory contains a man page that\ndescribes the options nanotrav supports.  The files *.blif are sample\ninput files for nanotrav.  The *.out files are the reference output\nfiles.\n\nDOCUMENTATION\n\nIf doxygen is installed, running \"make\" puts HTML documentation for\nthe CUDD package in directory cudd-3.0.0/cudd/html. The recommended\nstarting point is index.html.  The user's manual in PDF format is\nbuilt in cudd-3.0.0/doc if pdflatex and makeindex are installed.\nDocumentation for the dddmp library is in the dddmp/doc subdirectory.\n\nFEEDBACK:\n\nSend feedback to:\n\nFabio Somenzi\nUniversity of Colorado at Boulder\nECE Dept.\nBoulder, CO 80309-0425\nFabio@Colorado.EDU\nhttp://vlsi.colorado.edu/~fabio\n"
  },
  {
    "path": "cudd/RELEASE.NOTES",
    "content": "Release 3.0.0 of Cudd uses autotools for its build.  It can also\nproduce a shared library.  The shared library contains the core CUDD\nfunctions, and, optionally, the dddmp functions and the C++ wrapper.\nIt is now safe to use separate CUDD managers in different threads.\n\nThere are changes in the API, discussed later.  The documentation is\nnow extracted from the code by Doxygen.  About a dozen bugs were fixed\nin seldom-used functions.\n\nThe switch to autotools means that one no longer needs to edit the\nconfiguration section of the main Makefile.  It was also instrumental\nin providing shared library support (via libtool) on multiple\nplatforms and a \"check\" make target worth its name.  Initial support\nfor cross compilation has been added.\n\nBuild time is significantly longer, especially the first time, and\nespecially when shared libraries are enabled.  In return one gets\ndependency tracking, support for VPATH builds, packaging of\ndistributions, and so on.\n\nThe CUDD package and its sub-packages now expose significantly fewer\ndetails of their implementations to the applications.  It is now\npossible to compile a CUDD-based application while including only the\ncudd.h header and linking only libcudd.a (or the equivalent shared\nlibrary).  A few const type qualifiers have been added to APIs too.\n\nSome macros have been turned into functions to improve encapsulation,\nnamely Cudd_T, Cudd_E, Cudd_V, and Cudd_IsConstant.  Another API\nchange brought about by this restructuring is that the digits of\narbitrary-precision integers are now always 32-bit wide.  As a\nconsequence, the function Cudd_ApaIntDivision is now deprecated.\n\nThe malloc/realloc/free wrappers in safe_mem.c have been simplified\nand made more consistent with the standard functions.  (The majority\nof what the wrappers did was supplying functionality that any modern\ncompliant implementation of C would supply anyway.)  Some parts of the\nutil library are no longer distributed with CUDD.  (They were never\nused by it.)\n\nApplications that call functions from the mtr or epd packages now have\nto explicitly include their headers _before_ including cudd.h.\nApplications that access data structures that are no longer exposed\nshould declare their close kinship with those data structure by\nincluding the internal headers.\n\nThere is a new function in the API, Cudd_PrintSummary, that is\nanalogous to Cudd_PrintDebug, but only prints one line using\narbitrary-precision arithmetic to compute the number of minterms.  The\nfunction Cudd_ApaPrintExponential now behaves like printf of glibc with\na \"g\" conversion specifier.  These changes were motivated by the\ndiscrepancies between printfs on Linux and Windows that affected \"make\ncheck.\"\n\nCUDD now explicitly calls an implementation of qsort that is included\nin the util library.  While this version of qsort has been shipped\nwith CUDD since Release 1.0.0, it was up to the application to decide\nwhether to link it or not.  However, dynamic linking on Windows and OS\nX makes it difficult to replace the system qsort with a function of\nthe same name; hence, there is now a util_qsort in the CUDD library.\n(The main reasons for not using the system qsort are repeatability and\nperformance of variable reordering.)  To use the system qsort,\nconfigure CUDD with the --with-system-qsort option.  Keep in mind that\nsome tests in \"make check\" may fail in this case by producing variable\norders different from the reference ones.\n\nThe random number generator is now local to a manager.  The interface\nhas changed accordingly.  The only global variable in the whole\npackage is the one used to store the out-of-memory handler.  As long\nas it is not modified, distinct CUDD managers can be run in different\nthreads.\n\nEven with a portable sort routine and random number generator, CUDD\ndoes not guarantee the same output on all platforms.  For instance,\nthe simulated annealing reordering algorithm uses floating-point\narithmetic, and the results on i686 machines occasionally differ from\nthose on x86_64 machines.\n\nIn the C++ wrapper, the default error handler now throws an exception\ninstead of failing.  A new function helps in handling failed memory\nallocations: Cudd_InstallOutOfMemoryHandler; it can be used to modify\nthe default behavior, which is to terminate the program.  There are a\nfew new functions in the C++ API and a substantial clean-up has taken\nplace.  Several functions have had some of their parameters given\ndefault values, and in a few cases the order of the parameters has\nbeen changed to improve consistency.\n\nNew functions:\n\nDD_OOMFP Cudd_InstallOutOfMemoryHandler(DD_OOMFP newHandler);\n\nDD_OOMFP Cudd_RegisterOutOfMemoryCallback(DdManager *unique, DD_OOMFP callback);\n\nvoid Cudd_UnregisterOutOfMemoryCallback(DdManager *unique);\n\nvoid Cudd_OutOfMemSilent(size_t size);\n\nDdNode * Cudd_bddInterpolate(DdManager * dd, DdNode * l, DdNode * u);\n\nint Cudd_VarsAreSymmetric(DdManager * dd, DdNode * f, int index1, int index2);\n\nint Cudd_PrintSummary(DdManager * dd, DdNode * f, int n, int mode);\n\nvoid Cudd_FreeApaNumber(DdApaNumber number);\n\nchar * Cudd_ApaStringDecimal(int digits, DdConstApaNumber number);\n\nlong double Cudd_LdblCountMinterm(DdManager const *manager, DdNode *node,\n    int nvars);\n\nint Cudd_EpdPrintMinterm(DdManager const * dd, DdNode * node, int nvars);\n\nst_table * st_init_table_with_params_and_arg(st_compare_arg_t,\n    st_hash_arg_t, void const *, int, int, double, int);\n\nst_table * st_init_table_with_arg(st_compare_arg_t, st_hash_arg_t,\n    void const *);\n\nvoid ABDD::summary(int nvars, int mode = 0) const;\n\nDD_OOMFP Cudd::InstallOutOfMemoryHandler(DD_OOMFP newHandler) const;\n\nDD_OOMFP RegisterOutOfMemoryCallback(DD_OOMFP callback) const;\n\nvoid UnregisterOutOfMemoryCallback(void) const;\n\nBDD computeCube(std::vector<BDD> const & vars) const;\n\nADD computeCube(std::vector<ADD> const & vars) const;\n\nBDD BDD::Interpolate(const BDD& u) const;\n\nbool BDD::VarAreSymmetric(int index1, int index2) const;\n\nstd::string ApaStringDecimal(int digits, DdApaNumber number) const;\n\nvoid Cudd::ApaPrintExponential(int digits, DdApaNumber number,\n                               int precision = 6, FILE * fp = stdout) const;\n\nvoid ApaPrintMintermExp(int nvars, int precision = 6, FILE * fp = stdout) const;\n\nlong double LdblCountMinterm(int nvars) const;\n\nADD Cudd::Harwell(FILE * fp, std::vector<ADD>& x, std::vector<ADD>& y,\n                  std::vector<ADD>& xn, std::vector<ADD>& yn_,\n                  int * m, int * n, int bx = 0, int sx = 2, int by = 1,\n                  int sy = 2, int pr = 0) const;\n\nADD Cudd::Read(FILE * fp, std::vector<ADD>& x, std::vector<ADD>& y,\n               std::vector<ADD>& xn, std::vector<ADD>& yn_, int * m, int * n,\n               int bx = 0, int sx = 2, int by = 1, int sy = 2) const;\nBDD Cudd::Read(FILE * fp, std::vector<BDD>& x, std::vector<BDD>& y,\n               int * m, int * n, int bx = 0, int sx = 2, int by = 1,\n               int sy = 2) const;\n\nstd::string Cudd::OrderString(void) const;\n\nSpecial thanks go to Hubert Garavel for the many discussions that have\ngreatly contributed to shaping this new CUDD release.\n\n----------------------------------------------------------------------\n\nRelease 2.6.0 of Cudd is the first release to compile out of the box\nwith MinGW-w64.  This is achieved primarily by using types and macros\ndefined in inttypes.h.  The only visible changes in the API are some\nparameter types that are now \"size_t\" instead of \"unsinged long.\"\n\nSupport for multi-threaded applications has been slightly enhanced.\nThe Makefile has been slightly enhanced and finally supports creation\nof top-level tag files for both emacs and vi.\n\nThe code has been cleaned up a bit so that all warnings that would be\nproduced by gcc with \"-Wextra\" have been removed.  The tests run by\nnanotrav/tst.sh and obj/testobj cover a bit more of the package's\nfunctionality.\n\n----------------------------------------------------------------------\n\nRelease 2.5.1 of Cudd improves support for multi-threaded applications.\nSpecifically, an application may now register a callback function that\nis called from time to time to check whether computation should be\nterminated because another thread has found the result.\n\nThe C++ interface allows the application to register variable names with\nthe manager and implements operator<< for BDDs.  The interfaces of\nSolveEqn and VerifySol now take std::vectors instead of plain arrays.\n\nFixed a few bugs in CUDD and a bug in the mtr package.\n\nAdded const qualifiers to dumping function interfaces\n(Cudd_DumpDot,...).\n\nThe Makefile now supports gmake's -j option.  Change \"@+\" back to \"@\" if\nthis causes problems with your make program.\n\nBuggy documentation that was shipped with 2.5.0 has been fixed.\n\nNew functions:\n\nint Cudd_bddIsVar(DdManager * dd, DdNode * f);\n\nvoid Cudd_RegisterTerminationCallback(DdManager *unique,\n\nvoid Cudd_UnregisterTerminationCallback(DdManager *unique);\n\nvoid Cudd_SetApplicationHook(DdManager *dd, void * value);\n\nvoid * Cudd_ReadApplicationHook(DdManager *dd);\n\nchar * Cudd_FactoredFormString(DdManager *dd, DdNode *f,\n    char const * const * inames);\n\n----------------------------------------------------------------------\n\nReleas 2.5.0 of Cudd introduces the ability to set timeouts.  The\nfunction that is interrupted returns NULL (which the application must\nbe prepared to handle,) but the BDDs are uncorrupted and the invoking\nprogram can continue to use the manager.\n\nIn addition, reordering is now aware of timeouts, so that it gives up\nwhen a timeout is approaching to give the invoking program a chance to\nobtain some results.\n\nThe response time to the timeout is not immediate, though most of the time\nit is well below one second.  Checking for timeouts has a small overhead.\nIn experiments, less than 1% has been observed on average.\n\nCreation of BDD managers with many variables (e.g., tens or hundreds\nof thousands) is now much more efficient.  Computing small supports of\nBDDs when there are many variables is also much more efficient, but\nthis has been at the cost of separating the function for BDDs and ADDs\n(Cudd_Support) from that for ZDDs (Cudd_zddSupport).\n\nThe C++ interface has undergone a major upgrade.\n\nThe handling of variable gruops in reordering has been much improved.\n(Thanks to Arie Gurfinkel for a very detailed bug report!)  A handful\nof other bugs have been fixed as well.\n\n\nNew Functions:\n\nunsigned long Cudd_ReadStartTime(DdManager *unique);\n\nunsigned long Cudd_ReadElapsedTime(DdManager *unique);\n\nvoid Cudd_SetStartTime(DdManager *unique, unsigned long st);\n\nvoid Cudd_ResetStartTime(DdManager *unique);\n\nunsigned long Cudd_ReadTimeLimit(DdManager *unique);\n\nvoid Cudd_SetTimeLimit(DdManager *unique, unsigned long tl);\n\nvoid Cudd_UpdateTimeLimit(DdManager * unique);\n\nvoid Cudd_IncreaseTimeLimit(DdManager * unique, unsigned long increase);\n\nvoid Cudd_UnsetTimeLimit(DdManager *unique);\n\nint Cudd_TimeLimited(DdManager *unique);\n\nunsigned int Cudd_ReadMaxReorderings (DdManager *dd);\n\nvoid Cudd_SetMaxReorderings (DdManager *dd, unsigned int mr);\n\nunsigned int Cudd_ReadOrderRandomization(DdManager * dd);\n\nvoid Cudd_SetOrderRandomization(DdManager * dd, unsigned int factor);\n\nint Cudd_PrintGroupedOrder(DdManager * dd, const char *str, void *data);\n\nint Cudd_EnableOrderingMonitoring(DdManager *dd);\n\nint Cudd_DisableOrderingMonitoring(DdManager *dd);\n\nint Cudd_OrderingMonitoring(DdManager *dd);\n\nDdNode * Cudd_bddExistAbstractLimit(DdManager * manager, DdNode * f, DdNode * cube, unsigned int limit);\n\nDdNode * Cudd_bddIteLimit (DdManager *dd, DdNode *f, DdNode *g, DdNode *h, unsigned int limit);\n\nDdNode * Cudd_bddOrLimit (DdManager *dd, DdNode *f, DdNode *g, unsigned int limit);\n\nDdNode * Cudd_bddXnorLimit (DdManager *dd, DdNode *f, DdNode *g, unsigned int limit);\n\nint Cudd_CheckCube (DdManager *dd, DdNode *g);\n\nDdNode * Cudd_bddMaximallyExpand(DdManager *dd, DdNode *lb, DdNode *ub, DdNode *f);\n\nDdNode * Cudd_bddLargestPrimeUnate(DdManager *dd , DdNode *f, DdNode *phaseBdd);\n\nint Cudd_Reserve(DdManager *manager, int amount);\n\nint Cudd_SupportIndices(DdManager * dd, DdNode * f, int **indices);\n\nint Cudd_VectorSupportIndices(DdManager * dd, DdNode ** F, int n, int **indices);\n\nDdNode * Cudd_zddSupport(DdManager * dd, DdNode * f);\n\n\nChanged prototypes:\n\nunsigned int Cudd_ReadReorderings (DdManager *dd);\n\n----------------------------------------------------------------------\n\nRelease 2.4.2 of Cudd features several bug fixes.  The most important\nare those that prevented Cudd from making full use of up to 4 GB of\nmemory when using 32-bit pointers.  A handful of bugs were discovered by\nCoverity.  (Thanks to Christian Stangier!)\n\nThis release can be compiled with either 64-bit pointers or 32-bit\npointers on x86_64 platforms if sizeof(long) = sizeof(void *) = 8 and\nsizeof(int) = 4.  This is known as the LP64 model.  For 32-bit pointers,\none usually needs supplementary libraries.  On Ubuntu and Debian Linux,\none needs g++-multilib, which can be installed with\n\"apt-get install g++-multilib.\"\n\nAdded functions \n\nDdNode *Cudd_Inequality (DdManager * dd, int  N, int c, DdNode ** x,\nDdNode ** y);\n\nDdNode * Cudd_Disequality (DdManager * dd, int  N, int c, DdNode ** x,\nDdNode ** y);\n\nDdNode * Cudd_bddInterval (DdManager * dd, int  N, DdNode ** x,\nunsigned int lowerB, unsigned int upperB);\n\nChanged prototypes:\n\nint Cudd_DumpBlif (DdManager *dd, int n, DdNode **f, char\n**inames, char **onames, char *mname, FILE *fp, int mv);\n\nint Cudd_DumpBlifBody (DdManager *dd, int n, DdNode **f, char\n**inames, char **onames, FILE *fp, int mv);\n\nThe additional parameter allows the caller to choose between plain blif\nand blif-MV.\n\n----------------------------------------------------------------------\n\nRelease 2.4.1 of Cudd features one major change with respect to previous\nreleases.  The licensing terms are now explicitly stated.\n"
  },
  {
    "path": "cudd/aclocal.m4",
    "content": "# generated automatically by aclocal 1.16.5 -*- Autoconf -*-\n\n# Copyright (C) 1996-2021 Free Software Foundation, Inc.\n\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# This program is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY, to the extent permitted by law; without\n# even the implied warranty of MERCHANTABILITY or FITNESS FOR A\n# PARTICULAR PURPOSE.\n\nm4_ifndef([AC_CONFIG_MACRO_DIRS], [m4_defun([_AM_CONFIG_MACRO_DIRS], [])m4_defun([AC_CONFIG_MACRO_DIRS], [_AM_CONFIG_MACRO_DIRS($@)])])\nm4_ifndef([AC_AUTOCONF_VERSION],\n  [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl\nm4_if(m4_defn([AC_AUTOCONF_VERSION]), [2.72],,\n[m4_warning([this file was generated for autoconf 2.72.\nYou have another version of autoconf.  It may work, but is not guaranteed to.\nIf you have problems, you may need to regenerate the build system entirely.\nTo do so, use the procedure documented by the package, typically 'autoreconf'.])])\n\n# Copyright (C) 2002-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_AUTOMAKE_VERSION(VERSION)\n# ----------------------------\n# Automake X.Y traces this macro to ensure aclocal.m4 has been\n# generated from the m4 files accompanying Automake X.Y.\n# (This private macro should not be called outside this file.)\nAC_DEFUN([AM_AUTOMAKE_VERSION],\n[am__api_version='1.16'\ndnl Some users find AM_AUTOMAKE_VERSION and mistake it for a way to\ndnl require some minimum version.  Point them to the right macro.\nm4_if([$1], [1.16.5], [],\n      [AC_FATAL([Do not call $0, use AM_INIT_AUTOMAKE([$1]).])])dnl\n])\n\n# _AM_AUTOCONF_VERSION(VERSION)\n# -----------------------------\n# aclocal traces this macro to find the Autoconf version.\n# This is a private macro too.  Using m4_define simplifies\n# the logic in aclocal, which can simply ignore this definition.\nm4_define([_AM_AUTOCONF_VERSION], [])\n\n# AM_SET_CURRENT_AUTOMAKE_VERSION\n# -------------------------------\n# Call AM_AUTOMAKE_VERSION and AM_AUTOMAKE_VERSION so they can be traced.\n# This function is AC_REQUIREd by AM_INIT_AUTOMAKE.\nAC_DEFUN([AM_SET_CURRENT_AUTOMAKE_VERSION],\n[AM_AUTOMAKE_VERSION([1.16.5])dnl\nm4_ifndef([AC_AUTOCONF_VERSION],\n  [m4_copy([m4_PACKAGE_VERSION], [AC_AUTOCONF_VERSION])])dnl\n_AM_AUTOCONF_VERSION(m4_defn([AC_AUTOCONF_VERSION]))])\n\n# Copyright (C) 2011-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_PROG_AR([ACT-IF-FAIL])\n# -------------------------\n# Try to determine the archiver interface, and trigger the ar-lib wrapper\n# if it is needed.  If the detection of archiver interface fails, run\n# ACT-IF-FAIL (default is to abort configure with a proper error message).\nAC_DEFUN([AM_PROG_AR],\n[AC_BEFORE([$0], [LT_INIT])dnl\nAC_BEFORE([$0], [AC_PROG_LIBTOOL])dnl\nAC_REQUIRE([AM_AUX_DIR_EXPAND])dnl\nAC_REQUIRE_AUX_FILE([ar-lib])dnl\nAC_CHECK_TOOLS([AR], [ar lib \"link -lib\"], [false])\n: ${AR=ar}\n\nAC_CACHE_CHECK([the archiver ($AR) interface], [am_cv_ar_interface],\n  [AC_LANG_PUSH([C])\n   am_cv_ar_interface=ar\n   AC_COMPILE_IFELSE([AC_LANG_SOURCE([[int some_variable = 0;]])],\n     [am_ar_try='$AR cru libconftest.a conftest.$ac_objext >&AS_MESSAGE_LOG_FD'\n      AC_TRY_EVAL([am_ar_try])\n      if test \"$ac_status\" -eq 0; then\n        am_cv_ar_interface=ar\n      else\n        am_ar_try='$AR -NOLOGO -OUT:conftest.lib conftest.$ac_objext >&AS_MESSAGE_LOG_FD'\n        AC_TRY_EVAL([am_ar_try])\n        if test \"$ac_status\" -eq 0; then\n          am_cv_ar_interface=lib\n        else\n          am_cv_ar_interface=unknown\n        fi\n      fi\n      rm -f conftest.lib libconftest.a\n     ])\n   AC_LANG_POP([C])])\n\ncase $am_cv_ar_interface in\nar)\n  ;;\nlib)\n  # Microsoft lib, so override with the ar-lib wrapper script.\n  # FIXME: It is wrong to rewrite AR.\n  # But if we don't then we get into trouble of one sort or another.\n  # A longer-term fix would be to have automake use am__AR in this case,\n  # and then we could set am__AR=\"$am_aux_dir/ar-lib \\$(AR)\" or something\n  # similar.\n  AR=\"$am_aux_dir/ar-lib $AR\"\n  ;;\nunknown)\n  m4_default([$1],\n             [AC_MSG_ERROR([could not determine $AR interface])])\n  ;;\nesac\nAC_SUBST([AR])dnl\n])\n\n# AM_AUX_DIR_EXPAND                                         -*- Autoconf -*-\n\n# Copyright (C) 2001-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# For projects using AC_CONFIG_AUX_DIR([foo]), Autoconf sets\n# $ac_aux_dir to '$srcdir/foo'.  In other projects, it is set to\n# '$srcdir', '$srcdir/..', or '$srcdir/../..'.\n#\n# Of course, Automake must honor this variable whenever it calls a\n# tool from the auxiliary directory.  The problem is that $srcdir (and\n# therefore $ac_aux_dir as well) can be either absolute or relative,\n# depending on how configure is run.  This is pretty annoying, since\n# it makes $ac_aux_dir quite unusable in subdirectories: in the top\n# source directory, any form will work fine, but in subdirectories a\n# relative path needs to be adjusted first.\n#\n# $ac_aux_dir/missing\n#    fails when called from a subdirectory if $ac_aux_dir is relative\n# $top_srcdir/$ac_aux_dir/missing\n#    fails if $ac_aux_dir is absolute,\n#    fails when called from a subdirectory in a VPATH build with\n#          a relative $ac_aux_dir\n#\n# The reason of the latter failure is that $top_srcdir and $ac_aux_dir\n# are both prefixed by $srcdir.  In an in-source build this is usually\n# harmless because $srcdir is '.', but things will broke when you\n# start a VPATH build or use an absolute $srcdir.\n#\n# So we could use something similar to $top_srcdir/$ac_aux_dir/missing,\n# iff we strip the leading $srcdir from $ac_aux_dir.  That would be:\n#   am_aux_dir='\\$(top_srcdir)/'`expr \"$ac_aux_dir\" : \"$srcdir//*\\(.*\\)\"`\n# and then we would define $MISSING as\n#   MISSING=\"\\${SHELL} $am_aux_dir/missing\"\n# This will work as long as MISSING is not called from configure, because\n# unfortunately $(top_srcdir) has no meaning in configure.\n# However there are other variables, like CC, which are often used in\n# configure, and could therefore not use this \"fixed\" $ac_aux_dir.\n#\n# Another solution, used here, is to always expand $ac_aux_dir to an\n# absolute PATH.  The drawback is that using absolute paths prevent a\n# configured tree to be moved without reconfiguration.\n\nAC_DEFUN([AM_AUX_DIR_EXPAND],\n[AC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT])dnl\n# Expand $ac_aux_dir to an absolute path.\nam_aux_dir=`cd \"$ac_aux_dir\" && pwd`\n])\n\n# AM_COND_IF                                            -*- Autoconf -*-\n\n# Copyright (C) 2008-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# _AM_COND_IF\n# _AM_COND_ELSE\n# _AM_COND_ENDIF\n# --------------\n# These macros are only used for tracing.\nm4_define([_AM_COND_IF])\nm4_define([_AM_COND_ELSE])\nm4_define([_AM_COND_ENDIF])\n\n# AM_COND_IF(COND, [IF-TRUE], [IF-FALSE])\n# ---------------------------------------\n# If the shell condition COND is true, execute IF-TRUE, otherwise execute\n# IF-FALSE.  Allow automake to learn about conditional instantiating macros\n# (the AC_CONFIG_FOOS).\nAC_DEFUN([AM_COND_IF],\n[m4_ifndef([_AM_COND_VALUE_$1],\n\t   [m4_fatal([$0: no such condition \"$1\"])])dnl\n_AM_COND_IF([$1])dnl\nif test -z \"$$1_TRUE\"; then :\n  m4_n([$2])[]dnl\nm4_ifval([$3],\n[_AM_COND_ELSE([$1])dnl\nelse\n  $3\n])dnl\n_AM_COND_ENDIF([$1])dnl\nfi[]dnl\n])\n\n# AM_CONDITIONAL                                            -*- Autoconf -*-\n\n# Copyright (C) 1997-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_CONDITIONAL(NAME, SHELL-CONDITION)\n# -------------------------------------\n# Define a conditional.\nAC_DEFUN([AM_CONDITIONAL],\n[AC_PREREQ([2.52])dnl\n m4_if([$1], [TRUE],  [AC_FATAL([$0: invalid condition: $1])],\n       [$1], [FALSE], [AC_FATAL([$0: invalid condition: $1])])dnl\nAC_SUBST([$1_TRUE])dnl\nAC_SUBST([$1_FALSE])dnl\n_AM_SUBST_NOTMAKE([$1_TRUE])dnl\n_AM_SUBST_NOTMAKE([$1_FALSE])dnl\nm4_define([_AM_COND_VALUE_$1], [$2])dnl\nif $2; then\n  $1_TRUE=\n  $1_FALSE='#'\nelse\n  $1_TRUE='#'\n  $1_FALSE=\nfi\nAC_CONFIG_COMMANDS_PRE(\n[if test -z \"${$1_TRUE}\" && test -z \"${$1_FALSE}\"; then\n  AC_MSG_ERROR([[conditional \"$1\" was never defined.\nUsually this means the macro was only invoked conditionally.]])\nfi])])\n\n# Copyright (C) 1999-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n\n# There are a few dirty hacks below to avoid letting 'AC_PROG_CC' be\n# written in clear, in which case automake, when reading aclocal.m4,\n# will think it sees a *use*, and therefore will trigger all it's\n# C support machinery.  Also note that it means that autoscan, seeing\n# CC etc. in the Makefile, will ask for an AC_PROG_CC use...\n\n\n# _AM_DEPENDENCIES(NAME)\n# ----------------------\n# See how the compiler implements dependency checking.\n# NAME is \"CC\", \"CXX\", \"OBJC\", \"OBJCXX\", \"UPC\", or \"GJC\".\n# We try a few techniques and use that to set a single cache variable.\n#\n# We don't AC_REQUIRE the corresponding AC_PROG_CC since the latter was\n# modified to invoke _AM_DEPENDENCIES(CC); we would have a circular\n# dependency, and given that the user is not expected to run this macro,\n# just rely on AC_PROG_CC.\nAC_DEFUN([_AM_DEPENDENCIES],\n[AC_REQUIRE([AM_SET_DEPDIR])dnl\nAC_REQUIRE([AM_OUTPUT_DEPENDENCY_COMMANDS])dnl\nAC_REQUIRE([AM_MAKE_INCLUDE])dnl\nAC_REQUIRE([AM_DEP_TRACK])dnl\n\nm4_if([$1], [CC],   [depcc=\"$CC\"   am_compiler_list=],\n      [$1], [CXX],  [depcc=\"$CXX\"  am_compiler_list=],\n      [$1], [OBJC], [depcc=\"$OBJC\" am_compiler_list='gcc3 gcc'],\n      [$1], [OBJCXX], [depcc=\"$OBJCXX\" am_compiler_list='gcc3 gcc'],\n      [$1], [UPC],  [depcc=\"$UPC\"  am_compiler_list=],\n      [$1], [GCJ],  [depcc=\"$GCJ\"  am_compiler_list='gcc3 gcc'],\n                    [depcc=\"$$1\"   am_compiler_list=])\n\nAC_CACHE_CHECK([dependency style of $depcc],\n               [am_cv_$1_dependencies_compiler_type],\n[if test -z \"$AMDEP_TRUE\" && test -f \"$am_depcomp\"; then\n  # We make a subdir and do the tests there.  Otherwise we can end up\n  # making bogus files that we don't know about and never remove.  For\n  # instance it was reported that on HP-UX the gcc test will end up\n  # making a dummy file named 'D' -- because '-MD' means \"put the output\n  # in D\".\n  rm -rf conftest.dir\n  mkdir conftest.dir\n  # Copy depcomp to subdir because otherwise we won't find it if we're\n  # using a relative directory.\n  cp \"$am_depcomp\" conftest.dir\n  cd conftest.dir\n  # We will build objects and dependencies in a subdirectory because\n  # it helps to detect inapplicable dependency modes.  For instance\n  # both Tru64's cc and ICC support -MD to output dependencies as a\n  # side effect of compilation, but ICC will put the dependencies in\n  # the current directory while Tru64 will put them in the object\n  # directory.\n  mkdir sub\n\n  am_cv_$1_dependencies_compiler_type=none\n  if test \"$am_compiler_list\" = \"\"; then\n     am_compiler_list=`sed -n ['s/^#*\\([a-zA-Z0-9]*\\))$/\\1/p'] < ./depcomp`\n  fi\n  am__universal=false\n  m4_case([$1], [CC],\n    [case \" $depcc \" in #(\n     *\\ -arch\\ *\\ -arch\\ *) am__universal=true ;;\n     esac],\n    [CXX],\n    [case \" $depcc \" in #(\n     *\\ -arch\\ *\\ -arch\\ *) am__universal=true ;;\n     esac])\n\n  for depmode in $am_compiler_list; do\n    # Setup a source with many dependencies, because some compilers\n    # like to wrap large dependency lists on column 80 (with \\), and\n    # we should not choose a depcomp mode which is confused by this.\n    #\n    # We need to recreate these files for each test, as the compiler may\n    # overwrite some of them when testing with obscure command lines.\n    # This happens at least with the AIX C compiler.\n    : > sub/conftest.c\n    for i in 1 2 3 4 5 6; do\n      echo '#include \"conftst'$i'.h\"' >> sub/conftest.c\n      # Using \": > sub/conftst$i.h\" creates only sub/conftst1.h with\n      # Solaris 10 /bin/sh.\n      echo '/* dummy */' > sub/conftst$i.h\n    done\n    echo \"${am__include} ${am__quote}sub/conftest.Po${am__quote}\" > confmf\n\n    # We check with '-c' and '-o' for the sake of the \"dashmstdout\"\n    # mode.  It turns out that the SunPro C++ compiler does not properly\n    # handle '-M -o', and we need to detect this.  Also, some Intel\n    # versions had trouble with output in subdirs.\n    am__obj=sub/conftest.${OBJEXT-o}\n    am__minus_obj=\"-o $am__obj\"\n    case $depmode in\n    gcc)\n      # This depmode causes a compiler race in universal mode.\n      test \"$am__universal\" = false || continue\n      ;;\n    nosideeffect)\n      # After this tag, mechanisms are not by side-effect, so they'll\n      # only be used when explicitly requested.\n      if test \"x$enable_dependency_tracking\" = xyes; then\n\tcontinue\n      else\n\tbreak\n      fi\n      ;;\n    msvc7 | msvc7msys | msvisualcpp | msvcmsys)\n      # This compiler won't grok '-c -o', but also, the minuso test has\n      # not run yet.  These depmodes are late enough in the game, and\n      # so weak that their functioning should not be impacted.\n      am__obj=conftest.${OBJEXT-o}\n      am__minus_obj=\n      ;;\n    none) break ;;\n    esac\n    if depmode=$depmode \\\n       source=sub/conftest.c object=$am__obj \\\n       depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \\\n       $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \\\n         >/dev/null 2>conftest.err &&\n       grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 &&\n       grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 &&\n       grep $am__obj sub/conftest.Po > /dev/null 2>&1 &&\n       ${MAKE-make} -s -f confmf > /dev/null 2>&1; then\n      # icc doesn't choke on unknown options, it will just issue warnings\n      # or remarks (even with -Werror).  So we grep stderr for any message\n      # that says an option was ignored or not supported.\n      # When given -MP, icc 7.0 and 7.1 complain thusly:\n      #   icc: Command line warning: ignoring option '-M'; no argument required\n      # The diagnosis changed in icc 8.0:\n      #   icc: Command line remark: option '-MP' not supported\n      if (grep 'ignoring option' conftest.err ||\n          grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else\n        am_cv_$1_dependencies_compiler_type=$depmode\n        break\n      fi\n    fi\n  done\n\n  cd ..\n  rm -rf conftest.dir\nelse\n  am_cv_$1_dependencies_compiler_type=none\nfi\n])\nAC_SUBST([$1DEPMODE], [depmode=$am_cv_$1_dependencies_compiler_type])\nAM_CONDITIONAL([am__fastdep$1], [\n  test \"x$enable_dependency_tracking\" != xno \\\n  && test \"$am_cv_$1_dependencies_compiler_type\" = gcc3])\n])\n\n\n# AM_SET_DEPDIR\n# -------------\n# Choose a directory name for dependency files.\n# This macro is AC_REQUIREd in _AM_DEPENDENCIES.\nAC_DEFUN([AM_SET_DEPDIR],\n[AC_REQUIRE([AM_SET_LEADING_DOT])dnl\nAC_SUBST([DEPDIR], [\"${am__leading_dot}deps\"])dnl\n])\n\n\n# AM_DEP_TRACK\n# ------------\nAC_DEFUN([AM_DEP_TRACK],\n[AC_ARG_ENABLE([dependency-tracking], [dnl\nAS_HELP_STRING(\n  [--enable-dependency-tracking],\n  [do not reject slow dependency extractors])\nAS_HELP_STRING(\n  [--disable-dependency-tracking],\n  [speeds up one-time build])])\nif test \"x$enable_dependency_tracking\" != xno; then\n  am_depcomp=\"$ac_aux_dir/depcomp\"\n  AMDEPBACKSLASH='\\'\n  am__nodep='_no'\nfi\nAM_CONDITIONAL([AMDEP], [test \"x$enable_dependency_tracking\" != xno])\nAC_SUBST([AMDEPBACKSLASH])dnl\n_AM_SUBST_NOTMAKE([AMDEPBACKSLASH])dnl\nAC_SUBST([am__nodep])dnl\n_AM_SUBST_NOTMAKE([am__nodep])dnl\n])\n\n# Generate code to set up dependency tracking.              -*- Autoconf -*-\n\n# Copyright (C) 1999-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# _AM_OUTPUT_DEPENDENCY_COMMANDS\n# ------------------------------\nAC_DEFUN([_AM_OUTPUT_DEPENDENCY_COMMANDS],\n[{\n  # Older Autoconf quotes --file arguments for eval, but not when files\n  # are listed without --file.  Let's play safe and only enable the eval\n  # if we detect the quoting.\n  # TODO: see whether this extra hack can be removed once we start\n  # requiring Autoconf 2.70 or later.\n  AS_CASE([$CONFIG_FILES],\n          [*\\'*], [eval set x \"$CONFIG_FILES\"],\n          [*], [set x $CONFIG_FILES])\n  shift\n  # Used to flag and report bootstrapping failures.\n  am_rc=0\n  for am_mf\n  do\n    # Strip MF so we end up with the name of the file.\n    am_mf=`AS_ECHO([\"$am_mf\"]) | sed -e 's/:.*$//'`\n    # Check whether this is an Automake generated Makefile which includes\n    # dependency-tracking related rules and includes.\n    # Grep'ing the whole file directly is not great: AIX grep has a line\n    # limit of 2048, but all sed's we know have understand at least 4000.\n    sed -n 's,^am--depfiles:.*,X,p' \"$am_mf\" | grep X >/dev/null 2>&1 \\\n      || continue\n    am_dirpart=`AS_DIRNAME([\"$am_mf\"])`\n    am_filepart=`AS_BASENAME([\"$am_mf\"])`\n    AM_RUN_LOG([cd \"$am_dirpart\" \\\n      && sed -e '/# am--include-marker/d' \"$am_filepart\" \\\n        | $MAKE -f - am--depfiles]) || am_rc=$?\n  done\n  if test $am_rc -ne 0; then\n    AC_MSG_FAILURE([Something went wrong bootstrapping makefile fragments\n    for automatic dependency tracking.  If GNU make was not used, consider\n    re-running the configure script with MAKE=\"gmake\" (or whatever is\n    necessary).  You can also try re-running configure with the\n    '--disable-dependency-tracking' option to at least be able to build\n    the package (albeit without support for automatic dependency tracking).])\n  fi\n  AS_UNSET([am_dirpart])\n  AS_UNSET([am_filepart])\n  AS_UNSET([am_mf])\n  AS_UNSET([am_rc])\n  rm -f conftest-deps.mk\n}\n])# _AM_OUTPUT_DEPENDENCY_COMMANDS\n\n\n# AM_OUTPUT_DEPENDENCY_COMMANDS\n# -----------------------------\n# This macro should only be invoked once -- use via AC_REQUIRE.\n#\n# This code is only required when automatic dependency tracking is enabled.\n# This creates each '.Po' and '.Plo' makefile fragment that we'll need in\n# order to bootstrap the dependency handling code.\nAC_DEFUN([AM_OUTPUT_DEPENDENCY_COMMANDS],\n[AC_CONFIG_COMMANDS([depfiles],\n     [test x\"$AMDEP_TRUE\" != x\"\" || _AM_OUTPUT_DEPENDENCY_COMMANDS],\n     [AMDEP_TRUE=\"$AMDEP_TRUE\" MAKE=\"${MAKE-make}\"])])\n\n# Do all the work for Automake.                             -*- Autoconf -*-\n\n# Copyright (C) 1996-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# This macro actually does too much.  Some checks are only needed if\n# your package does certain things.  But this isn't really a big deal.\n\ndnl Redefine AC_PROG_CC to automatically invoke _AM_PROG_CC_C_O.\nm4_define([AC_PROG_CC],\nm4_defn([AC_PROG_CC])\n[_AM_PROG_CC_C_O\n])\n\n# AM_INIT_AUTOMAKE(PACKAGE, VERSION, [NO-DEFINE])\n# AM_INIT_AUTOMAKE([OPTIONS])\n# -----------------------------------------------\n# The call with PACKAGE and VERSION arguments is the old style\n# call (pre autoconf-2.50), which is being phased out.  PACKAGE\n# and VERSION should now be passed to AC_INIT and removed from\n# the call to AM_INIT_AUTOMAKE.\n# We support both call styles for the transition.  After\n# the next Automake release, Autoconf can make the AC_INIT\n# arguments mandatory, and then we can depend on a new Autoconf\n# release and drop the old call support.\nAC_DEFUN([AM_INIT_AUTOMAKE],\n[AC_PREREQ([2.65])dnl\nm4_ifdef([_$0_ALREADY_INIT],\n  [m4_fatal([$0 expanded multiple times\n]m4_defn([_$0_ALREADY_INIT]))],\n  [m4_define([_$0_ALREADY_INIT], m4_expansion_stack)])dnl\ndnl Autoconf wants to disallow AM_ names.  We explicitly allow\ndnl the ones we care about.\nm4_pattern_allow([^AM_[A-Z]+FLAGS$])dnl\nAC_REQUIRE([AM_SET_CURRENT_AUTOMAKE_VERSION])dnl\nAC_REQUIRE([AC_PROG_INSTALL])dnl\nif test \"`cd $srcdir && pwd`\" != \"`pwd`\"; then\n  # Use -I$(srcdir) only when $(srcdir) != ., so that make's output\n  # is not polluted with repeated \"-I.\"\n  AC_SUBST([am__isrc], [' -I$(srcdir)'])_AM_SUBST_NOTMAKE([am__isrc])dnl\n  # test to see if srcdir already configured\n  if test -f $srcdir/config.status; then\n    AC_MSG_ERROR([source directory already configured; run \"make distclean\" there first])\n  fi\nfi\n\n# test whether we have cygpath\nif test -z \"$CYGPATH_W\"; then\n  if (cygpath --version) >/dev/null 2>/dev/null; then\n    CYGPATH_W='cygpath -w'\n  else\n    CYGPATH_W=echo\n  fi\nfi\nAC_SUBST([CYGPATH_W])\n\n# Define the identity of the package.\ndnl Distinguish between old-style and new-style calls.\nm4_ifval([$2],\n[AC_DIAGNOSE([obsolete],\n             [$0: two- and three-arguments forms are deprecated.])\nm4_ifval([$3], [_AM_SET_OPTION([no-define])])dnl\n AC_SUBST([PACKAGE], [$1])dnl\n AC_SUBST([VERSION], [$2])],\n[_AM_SET_OPTIONS([$1])dnl\ndnl Diagnose old-style AC_INIT with new-style AM_AUTOMAKE_INIT.\nm4_if(\n  m4_ifset([AC_PACKAGE_NAME], [ok]):m4_ifset([AC_PACKAGE_VERSION], [ok]),\n  [ok:ok],,\n  [m4_fatal([AC_INIT should be called with package and version arguments])])dnl\n AC_SUBST([PACKAGE], ['AC_PACKAGE_TARNAME'])dnl\n AC_SUBST([VERSION], ['AC_PACKAGE_VERSION'])])dnl\n\n_AM_IF_OPTION([no-define],,\n[AC_DEFINE_UNQUOTED([PACKAGE], [\"$PACKAGE\"], [Name of package])\n AC_DEFINE_UNQUOTED([VERSION], [\"$VERSION\"], [Version number of package])])dnl\n\n# Some tools Automake needs.\nAC_REQUIRE([AM_SANITY_CHECK])dnl\nAC_REQUIRE([AC_ARG_PROGRAM])dnl\nAM_MISSING_PROG([ACLOCAL], [aclocal-${am__api_version}])\nAM_MISSING_PROG([AUTOCONF], [autoconf])\nAM_MISSING_PROG([AUTOMAKE], [automake-${am__api_version}])\nAM_MISSING_PROG([AUTOHEADER], [autoheader])\nAM_MISSING_PROG([MAKEINFO], [makeinfo])\nAC_REQUIRE([AM_PROG_INSTALL_SH])dnl\nAC_REQUIRE([AM_PROG_INSTALL_STRIP])dnl\nAC_REQUIRE([AC_PROG_MKDIR_P])dnl\n# For better backward compatibility.  To be removed once Automake 1.9.x\n# dies out for good.  For more background, see:\n# <https://lists.gnu.org/archive/html/automake/2012-07/msg00001.html>\n# <https://lists.gnu.org/archive/html/automake/2012-07/msg00014.html>\nAC_SUBST([mkdir_p], ['$(MKDIR_P)'])\n# We need awk for the \"check\" target (and possibly the TAP driver).  The\n# system \"awk\" is bad on some platforms.\nAC_REQUIRE([AC_PROG_AWK])dnl\nAC_REQUIRE([AC_PROG_MAKE_SET])dnl\nAC_REQUIRE([AM_SET_LEADING_DOT])dnl\n_AM_IF_OPTION([tar-ustar], [_AM_PROG_TAR([ustar])],\n\t      [_AM_IF_OPTION([tar-pax], [_AM_PROG_TAR([pax])],\n\t\t\t     [_AM_PROG_TAR([v7])])])\n_AM_IF_OPTION([no-dependencies],,\n[AC_PROVIDE_IFELSE([AC_PROG_CC],\n\t\t  [_AM_DEPENDENCIES([CC])],\n\t\t  [m4_define([AC_PROG_CC],\n\t\t\t     m4_defn([AC_PROG_CC])[_AM_DEPENDENCIES([CC])])])dnl\nAC_PROVIDE_IFELSE([AC_PROG_CXX],\n\t\t  [_AM_DEPENDENCIES([CXX])],\n\t\t  [m4_define([AC_PROG_CXX],\n\t\t\t     m4_defn([AC_PROG_CXX])[_AM_DEPENDENCIES([CXX])])])dnl\nAC_PROVIDE_IFELSE([AC_PROG_OBJC],\n\t\t  [_AM_DEPENDENCIES([OBJC])],\n\t\t  [m4_define([AC_PROG_OBJC],\n\t\t\t     m4_defn([AC_PROG_OBJC])[_AM_DEPENDENCIES([OBJC])])])dnl\nAC_PROVIDE_IFELSE([AC_PROG_OBJCXX],\n\t\t  [_AM_DEPENDENCIES([OBJCXX])],\n\t\t  [m4_define([AC_PROG_OBJCXX],\n\t\t\t     m4_defn([AC_PROG_OBJCXX])[_AM_DEPENDENCIES([OBJCXX])])])dnl\n])\n# Variables for tags utilities; see am/tags.am\nif test -z \"$CTAGS\"; then\n  CTAGS=ctags\nfi\nAC_SUBST([CTAGS])\nif test -z \"$ETAGS\"; then\n  ETAGS=etags\nfi\nAC_SUBST([ETAGS])\nif test -z \"$CSCOPE\"; then\n  CSCOPE=cscope\nfi\nAC_SUBST([CSCOPE])\n\nAC_REQUIRE([AM_SILENT_RULES])dnl\ndnl The testsuite driver may need to know about EXEEXT, so add the\ndnl 'am__EXEEXT' conditional if _AM_COMPILER_EXEEXT was seen.  This\ndnl macro is hooked onto _AC_COMPILER_EXEEXT early, see below.\nAC_CONFIG_COMMANDS_PRE(dnl\n[m4_provide_if([_AM_COMPILER_EXEEXT],\n  [AM_CONDITIONAL([am__EXEEXT], [test -n \"$EXEEXT\"])])])dnl\n\n# POSIX will say in a future version that running \"rm -f\" with no argument\n# is OK; and we want to be able to make that assumption in our Makefile\n# recipes.  So use an aggressive probe to check that the usage we want is\n# actually supported \"in the wild\" to an acceptable degree.\n# See automake bug#10828.\n# To make any issue more visible, cause the running configure to be aborted\n# by default if the 'rm' program in use doesn't match our expectations; the\n# user can still override this though.\nif rm -f && rm -fr && rm -rf; then : OK; else\n  cat >&2 <<'END'\nOops!\n\nYour 'rm' program seems unable to run without file operands specified\non the command line, even when the '-f' option is present.  This is contrary\nto the behaviour of most rm programs out there, and not conforming with\nthe upcoming POSIX standard: <http://austingroupbugs.net/view.php?id=542>\n\nPlease tell bug-automake@gnu.org about your system, including the value\nof your $PATH and any error possibly output before this message.  This\ncan help us improve future automake versions.\n\nEND\n  if test x\"$ACCEPT_INFERIOR_RM_PROGRAM\" = x\"yes\"; then\n    echo 'Configuration will proceed anyway, since you have set the' >&2\n    echo 'ACCEPT_INFERIOR_RM_PROGRAM variable to \"yes\"' >&2\n    echo >&2\n  else\n    cat >&2 <<'END'\nAborting the configuration process, to ensure you take notice of the issue.\n\nYou can download and install GNU coreutils to get an 'rm' implementation\nthat behaves properly: <https://www.gnu.org/software/coreutils/>.\n\nIf you want to complete the configuration process using your problematic\n'rm' anyway, export the environment variable ACCEPT_INFERIOR_RM_PROGRAM\nto \"yes\", and re-run configure.\n\nEND\n    AC_MSG_ERROR([Your 'rm' program is bad, sorry.])\n  fi\nfi\ndnl The trailing newline in this macro's definition is deliberate, for\ndnl backward compatibility and to allow trailing 'dnl'-style comments\ndnl after the AM_INIT_AUTOMAKE invocation. See automake bug#16841.\n])\n\ndnl Hook into '_AC_COMPILER_EXEEXT' early to learn its expansion.  Do not\ndnl add the conditional right here, as _AC_COMPILER_EXEEXT may be further\ndnl mangled by Autoconf and run in a shell conditional statement.\nm4_define([_AC_COMPILER_EXEEXT],\nm4_defn([_AC_COMPILER_EXEEXT])[m4_provide([_AM_COMPILER_EXEEXT])])\n\n# When config.status generates a header, we must update the stamp-h file.\n# This file resides in the same directory as the config header\n# that is generated.  The stamp files are numbered to have different names.\n\n# Autoconf calls _AC_AM_CONFIG_HEADER_HOOK (when defined) in the\n# loop where config.status creates the headers, so we can generate\n# our stamp files there.\nAC_DEFUN([_AC_AM_CONFIG_HEADER_HOOK],\n[# Compute $1's index in $config_headers.\n_am_arg=$1\n_am_stamp_count=1\nfor _am_header in $config_headers :; do\n  case $_am_header in\n    $_am_arg | $_am_arg:* )\n      break ;;\n    * )\n      _am_stamp_count=`expr $_am_stamp_count + 1` ;;\n  esac\ndone\necho \"timestamp for $_am_arg\" >`AS_DIRNAME([\"$_am_arg\"])`/stamp-h[]$_am_stamp_count])\n\n# Copyright (C) 2001-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_PROG_INSTALL_SH\n# ------------------\n# Define $install_sh.\nAC_DEFUN([AM_PROG_INSTALL_SH],\n[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl\nif test x\"${install_sh+set}\" != xset; then\n  case $am_aux_dir in\n  *\\ * | *\\\t*)\n    install_sh=\"\\${SHELL} '$am_aux_dir/install-sh'\" ;;\n  *)\n    install_sh=\"\\${SHELL} $am_aux_dir/install-sh\"\n  esac\nfi\nAC_SUBST([install_sh])])\n\n# Copyright (C) 2003-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# Check whether the underlying file-system supports filenames\n# with a leading dot.  For instance MS-DOS doesn't.\nAC_DEFUN([AM_SET_LEADING_DOT],\n[rm -rf .tst 2>/dev/null\nmkdir .tst 2>/dev/null\nif test -d .tst; then\n  am__leading_dot=.\nelse\n  am__leading_dot=_\nfi\nrmdir .tst 2>/dev/null\nAC_SUBST([am__leading_dot])])\n\n# Check to see how 'make' treats includes.\t            -*- Autoconf -*-\n\n# Copyright (C) 2001-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_MAKE_INCLUDE()\n# -----------------\n# Check whether make has an 'include' directive that can support all\n# the idioms we need for our automatic dependency tracking code.\nAC_DEFUN([AM_MAKE_INCLUDE],\n[AC_MSG_CHECKING([whether ${MAKE-make} supports the include directive])\ncat > confinc.mk << 'END'\nam__doit:\n\t@echo this is the am__doit target >confinc.out\n.PHONY: am__doit\nEND\nam__include=\"#\"\nam__quote=\n# BSD make does it like this.\necho '.include \"confinc.mk\" # ignored' > confmf.BSD\n# Other make implementations (GNU, Solaris 10, AIX) do it like this.\necho 'include confinc.mk # ignored' > confmf.GNU\n_am_result=no\nfor s in GNU BSD; do\n  AM_RUN_LOG([${MAKE-make} -f confmf.$s && cat confinc.out])\n  AS_CASE([$?:`cat confinc.out 2>/dev/null`],\n      ['0:this is the am__doit target'],\n      [AS_CASE([$s],\n          [BSD], [am__include='.include' am__quote='\"'],\n          [am__include='include' am__quote=''])])\n  if test \"$am__include\" != \"#\"; then\n    _am_result=\"yes ($s style)\"\n    break\n  fi\ndone\nrm -f confinc.* confmf.*\nAC_MSG_RESULT([${_am_result}])\nAC_SUBST([am__include])])\nAC_SUBST([am__quote])])\n\n# Fake the existence of programs that GNU maintainers use.  -*- Autoconf -*-\n\n# Copyright (C) 1997-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_MISSING_PROG(NAME, PROGRAM)\n# ------------------------------\nAC_DEFUN([AM_MISSING_PROG],\n[AC_REQUIRE([AM_MISSING_HAS_RUN])\n$1=${$1-\"${am_missing_run}$2\"}\nAC_SUBST($1)])\n\n# AM_MISSING_HAS_RUN\n# ------------------\n# Define MISSING if not defined so far and test if it is modern enough.\n# If it is, set am_missing_run to use it, otherwise, to nothing.\nAC_DEFUN([AM_MISSING_HAS_RUN],\n[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl\nAC_REQUIRE_AUX_FILE([missing])dnl\nif test x\"${MISSING+set}\" != xset; then\n  MISSING=\"\\${SHELL} '$am_aux_dir/missing'\"\nfi\n# Use eval to expand $SHELL\nif eval \"$MISSING --is-lightweight\"; then\n  am_missing_run=\"$MISSING \"\nelse\n  am_missing_run=\n  AC_MSG_WARN(['missing' script is too old or missing])\nfi\n])\n\n# Helper functions for option handling.                     -*- Autoconf -*-\n\n# Copyright (C) 2001-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# _AM_MANGLE_OPTION(NAME)\n# -----------------------\nAC_DEFUN([_AM_MANGLE_OPTION],\n[[_AM_OPTION_]m4_bpatsubst($1, [[^a-zA-Z0-9_]], [_])])\n\n# _AM_SET_OPTION(NAME)\n# --------------------\n# Set option NAME.  Presently that only means defining a flag for this option.\nAC_DEFUN([_AM_SET_OPTION],\n[m4_define(_AM_MANGLE_OPTION([$1]), [1])])\n\n# _AM_SET_OPTIONS(OPTIONS)\n# ------------------------\n# OPTIONS is a space-separated list of Automake options.\nAC_DEFUN([_AM_SET_OPTIONS],\n[m4_foreach_w([_AM_Option], [$1], [_AM_SET_OPTION(_AM_Option)])])\n\n# _AM_IF_OPTION(OPTION, IF-SET, [IF-NOT-SET])\n# -------------------------------------------\n# Execute IF-SET if OPTION is set, IF-NOT-SET otherwise.\nAC_DEFUN([_AM_IF_OPTION],\n[m4_ifset(_AM_MANGLE_OPTION([$1]), [$2], [$3])])\n\n# Copyright (C) 1999-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# _AM_PROG_CC_C_O\n# ---------------\n# Like AC_PROG_CC_C_O, but changed for automake.  We rewrite AC_PROG_CC\n# to automatically call this.\nAC_DEFUN([_AM_PROG_CC_C_O],\n[AC_REQUIRE([AM_AUX_DIR_EXPAND])dnl\nAC_REQUIRE_AUX_FILE([compile])dnl\nAC_LANG_PUSH([C])dnl\nAC_CACHE_CHECK(\n  [whether $CC understands -c and -o together],\n  [am_cv_prog_cc_c_o],\n  [AC_LANG_CONFTEST([AC_LANG_PROGRAM([])])\n  # Make sure it works both with $CC and with simple cc.\n  # Following AC_PROG_CC_C_O, we do the test twice because some\n  # compilers refuse to overwrite an existing .o file with -o,\n  # though they will create one.\n  am_cv_prog_cc_c_o=yes\n  for am_i in 1 2; do\n    if AM_RUN_LOG([$CC -c conftest.$ac_ext -o conftest2.$ac_objext]) \\\n         && test -f conftest2.$ac_objext; then\n      : OK\n    else\n      am_cv_prog_cc_c_o=no\n      break\n    fi\n  done\n  rm -f core conftest*\n  unset am_i])\nif test \"$am_cv_prog_cc_c_o\" != yes; then\n   # Losing compiler, so override with the script.\n   # FIXME: It is wrong to rewrite CC.\n   # But if we don't then we get into trouble of one sort or another.\n   # A longer-term fix would be to have automake use am__CC in this case,\n   # and then we could set am__CC=\"\\$(top_srcdir)/compile \\$(CC)\"\n   CC=\"$am_aux_dir/compile $CC\"\nfi\nAC_LANG_POP([C])])\n\n# For backward compatibility.\nAC_DEFUN_ONCE([AM_PROG_CC_C_O], [AC_REQUIRE([AC_PROG_CC])])\n\n# Copyright (C) 2001-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_RUN_LOG(COMMAND)\n# -------------------\n# Run COMMAND, save the exit status in ac_status, and log it.\n# (This has been adapted from Autoconf's _AC_RUN_LOG macro.)\nAC_DEFUN([AM_RUN_LOG],\n[{ echo \"$as_me:$LINENO: $1\" >&AS_MESSAGE_LOG_FD\n   ($1) >&AS_MESSAGE_LOG_FD 2>&AS_MESSAGE_LOG_FD\n   ac_status=$?\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&AS_MESSAGE_LOG_FD\n   (exit $ac_status); }])\n\n# Check to make sure that the build environment is sane.    -*- Autoconf -*-\n\n# Copyright (C) 1996-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_SANITY_CHECK\n# ---------------\nAC_DEFUN([AM_SANITY_CHECK],\n[AC_MSG_CHECKING([whether build environment is sane])\n# Reject unsafe characters in $srcdir or the absolute working directory\n# name.  Accept space and tab only in the latter.\nam_lf='\n'\ncase `pwd` in\n  *[[\\\\\\\"\\#\\$\\&\\'\\`$am_lf]]*)\n    AC_MSG_ERROR([unsafe absolute working directory name]);;\nesac\ncase $srcdir in\n  *[[\\\\\\\"\\#\\$\\&\\'\\`$am_lf\\ \\\t]]*)\n    AC_MSG_ERROR([unsafe srcdir value: '$srcdir']);;\nesac\n\n# Do 'set' in a subshell so we don't clobber the current shell's\n# arguments.  Must try -L first in case configure is actually a\n# symlink; some systems play weird games with the mod time of symlinks\n# (eg FreeBSD returns the mod time of the symlink's containing\n# directory).\nif (\n   am_has_slept=no\n   for am_try in 1 2; do\n     echo \"timestamp, slept: $am_has_slept\" > conftest.file\n     set X `ls -Lt \"$srcdir/configure\" conftest.file 2> /dev/null`\n     if test \"$[*]\" = \"X\"; then\n\t# -L didn't work.\n\tset X `ls -t \"$srcdir/configure\" conftest.file`\n     fi\n     if test \"$[*]\" != \"X $srcdir/configure conftest.file\" \\\n\t&& test \"$[*]\" != \"X conftest.file $srcdir/configure\"; then\n\n\t# If neither matched, then we have a broken ls.  This can happen\n\t# if, for instance, CONFIG_SHELL is bash and it inherits a\n\t# broken ls alias from the environment.  This has actually\n\t# happened.  Such a system could not be considered \"sane\".\n\tAC_MSG_ERROR([ls -t appears to fail.  Make sure there is not a broken\n  alias in your environment])\n     fi\n     if test \"$[2]\" = conftest.file || test $am_try -eq 2; then\n       break\n     fi\n     # Just in case.\n     sleep 1\n     am_has_slept=yes\n   done\n   test \"$[2]\" = conftest.file\n   )\nthen\n   # Ok.\n   :\nelse\n   AC_MSG_ERROR([newly created file is older than distributed files!\nCheck your system clock])\nfi\nAC_MSG_RESULT([yes])\n# If we didn't sleep, we still need to ensure time stamps of config.status and\n# generated files are strictly newer.\nam_sleep_pid=\nif grep 'slept: no' conftest.file >/dev/null 2>&1; then\n  ( sleep 1 ) &\n  am_sleep_pid=$!\nfi\nAC_CONFIG_COMMANDS_PRE(\n  [AC_MSG_CHECKING([that generated files are newer than configure])\n   if test -n \"$am_sleep_pid\"; then\n     # Hide warnings about reused PIDs.\n     wait $am_sleep_pid 2>/dev/null\n   fi\n   AC_MSG_RESULT([done])])\nrm -f conftest.file\n])\n\n# Copyright (C) 2009-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_SILENT_RULES([DEFAULT])\n# --------------------------\n# Enable less verbose build rules; with the default set to DEFAULT\n# (\"yes\" being less verbose, \"no\" or empty being verbose).\nAC_DEFUN([AM_SILENT_RULES],\n[AC_ARG_ENABLE([silent-rules], [dnl\nAS_HELP_STRING(\n  [--enable-silent-rules],\n  [less verbose build output (undo: \"make V=1\")])\nAS_HELP_STRING(\n  [--disable-silent-rules],\n  [verbose build output (undo: \"make V=0\")])dnl\n])\ncase $enable_silent_rules in @%:@ (((\n  yes) AM_DEFAULT_VERBOSITY=0;;\n   no) AM_DEFAULT_VERBOSITY=1;;\n    *) AM_DEFAULT_VERBOSITY=m4_if([$1], [yes], [0], [1]);;\nesac\ndnl\ndnl A few 'make' implementations (e.g., NonStop OS and NextStep)\ndnl do not support nested variable expansions.\ndnl See automake bug#9928 and bug#10237.\nam_make=${MAKE-make}\nAC_CACHE_CHECK([whether $am_make supports nested variables],\n   [am_cv_make_support_nested_variables],\n   [if AS_ECHO([['TRUE=$(BAR$(V))\nBAR0=false\nBAR1=true\nV=1\nam__doit:\n\t@$(TRUE)\n.PHONY: am__doit']]) | $am_make -f - >/dev/null 2>&1; then\n  am_cv_make_support_nested_variables=yes\nelse\n  am_cv_make_support_nested_variables=no\nfi])\nif test $am_cv_make_support_nested_variables = yes; then\n  dnl Using '$V' instead of '$(V)' breaks IRIX make.\n  AM_V='$(V)'\n  AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)'\nelse\n  AM_V=$AM_DEFAULT_VERBOSITY\n  AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY\nfi\nAC_SUBST([AM_V])dnl\nAM_SUBST_NOTMAKE([AM_V])dnl\nAC_SUBST([AM_DEFAULT_V])dnl\nAM_SUBST_NOTMAKE([AM_DEFAULT_V])dnl\nAC_SUBST([AM_DEFAULT_VERBOSITY])dnl\nAM_BACKSLASH='\\'\nAC_SUBST([AM_BACKSLASH])dnl\n_AM_SUBST_NOTMAKE([AM_BACKSLASH])dnl\n])\n\n# Copyright (C) 2001-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# AM_PROG_INSTALL_STRIP\n# ---------------------\n# One issue with vendor 'install' (even GNU) is that you can't\n# specify the program used to strip binaries.  This is especially\n# annoying in cross-compiling environments, where the build's strip\n# is unlikely to handle the host's binaries.\n# Fortunately install-sh will honor a STRIPPROG variable, so we\n# always use install-sh in \"make install-strip\", and initialize\n# STRIPPROG with the value of the STRIP variable (set by the user).\nAC_DEFUN([AM_PROG_INSTALL_STRIP],\n[AC_REQUIRE([AM_PROG_INSTALL_SH])dnl\n# Installed binaries are usually stripped using 'strip' when the user\n# run \"make install-strip\".  However 'strip' might not be the right\n# tool to use in cross-compilation environments, therefore Automake\n# will honor the 'STRIP' environment variable to overrule this program.\ndnl Don't test for $cross_compiling = yes, because it might be 'maybe'.\nif test \"$cross_compiling\" != no; then\n  AC_CHECK_TOOL([STRIP], [strip], :)\nfi\nINSTALL_STRIP_PROGRAM=\"\\$(install_sh) -c -s\"\nAC_SUBST([INSTALL_STRIP_PROGRAM])])\n\n# Copyright (C) 2006-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# _AM_SUBST_NOTMAKE(VARIABLE)\n# ---------------------------\n# Prevent Automake from outputting VARIABLE = @VARIABLE@ in Makefile.in.\n# This macro is traced by Automake.\nAC_DEFUN([_AM_SUBST_NOTMAKE])\n\n# AM_SUBST_NOTMAKE(VARIABLE)\n# --------------------------\n# Public sister of _AM_SUBST_NOTMAKE.\nAC_DEFUN([AM_SUBST_NOTMAKE], [_AM_SUBST_NOTMAKE($@)])\n\n# Check how to create a tarball.                            -*- Autoconf -*-\n\n# Copyright (C) 2004-2021 Free Software Foundation, Inc.\n#\n# This file is free software; the Free Software Foundation\n# gives unlimited permission to copy and/or distribute it,\n# with or without modifications, as long as this notice is preserved.\n\n# _AM_PROG_TAR(FORMAT)\n# --------------------\n# Check how to create a tarball in format FORMAT.\n# FORMAT should be one of 'v7', 'ustar', or 'pax'.\n#\n# Substitute a variable $(am__tar) that is a command\n# writing to stdout a FORMAT-tarball containing the directory\n# $tardir.\n#     tardir=directory && $(am__tar) > result.tar\n#\n# Substitute a variable $(am__untar) that extract such\n# a tarball read from stdin.\n#     $(am__untar) < result.tar\n#\nAC_DEFUN([_AM_PROG_TAR],\n[# Always define AMTAR for backward compatibility.  Yes, it's still used\n# in the wild :-(  We should find a proper way to deprecate it ...\nAC_SUBST([AMTAR], ['$${TAR-tar}'])\n\n# We'll loop over all known methods to create a tar archive until one works.\n_am_tools='gnutar m4_if([$1], [ustar], [plaintar]) pax cpio none'\n\nm4_if([$1], [v7],\n  [am__tar='$${TAR-tar} chof - \"$$tardir\"' am__untar='$${TAR-tar} xf -'],\n\n  [m4_case([$1],\n    [ustar],\n     [# The POSIX 1988 'ustar' format is defined with fixed-size fields.\n      # There is notably a 21 bits limit for the UID and the GID.  In fact,\n      # the 'pax' utility can hang on bigger UID/GID (see automake bug#8343\n      # and bug#13588).\n      am_max_uid=2097151 # 2^21 - 1\n      am_max_gid=$am_max_uid\n      # The $UID and $GID variables are not portable, so we need to resort\n      # to the POSIX-mandated id(1) utility.  Errors in the 'id' calls\n      # below are definitely unexpected, so allow the users to see them\n      # (that is, avoid stderr redirection).\n      am_uid=`id -u || echo unknown`\n      am_gid=`id -g || echo unknown`\n      AC_MSG_CHECKING([whether UID '$am_uid' is supported by ustar format])\n      if test $am_uid -le $am_max_uid; then\n         AC_MSG_RESULT([yes])\n      else\n         AC_MSG_RESULT([no])\n         _am_tools=none\n      fi\n      AC_MSG_CHECKING([whether GID '$am_gid' is supported by ustar format])\n      if test $am_gid -le $am_max_gid; then\n         AC_MSG_RESULT([yes])\n      else\n        AC_MSG_RESULT([no])\n        _am_tools=none\n      fi],\n\n  [pax],\n    [],\n\n  [m4_fatal([Unknown tar format])])\n\n  AC_MSG_CHECKING([how to create a $1 tar archive])\n\n  # Go ahead even if we have the value already cached.  We do so because we\n  # need to set the values for the 'am__tar' and 'am__untar' variables.\n  _am_tools=${am_cv_prog_tar_$1-$_am_tools}\n\n  for _am_tool in $_am_tools; do\n    case $_am_tool in\n    gnutar)\n      for _am_tar in tar gnutar gtar; do\n        AM_RUN_LOG([$_am_tar --version]) && break\n      done\n      am__tar=\"$_am_tar --format=m4_if([$1], [pax], [posix], [$1]) -chf - \"'\"$$tardir\"'\n      am__tar_=\"$_am_tar --format=m4_if([$1], [pax], [posix], [$1]) -chf - \"'\"$tardir\"'\n      am__untar=\"$_am_tar -xf -\"\n      ;;\n    plaintar)\n      # Must skip GNU tar: if it does not support --format= it doesn't create\n      # ustar tarball either.\n      (tar --version) >/dev/null 2>&1 && continue\n      am__tar='tar chf - \"$$tardir\"'\n      am__tar_='tar chf - \"$tardir\"'\n      am__untar='tar xf -'\n      ;;\n    pax)\n      am__tar='pax -L -x $1 -w \"$$tardir\"'\n      am__tar_='pax -L -x $1 -w \"$tardir\"'\n      am__untar='pax -r'\n      ;;\n    cpio)\n      am__tar='find \"$$tardir\" -print | cpio -o -H $1 -L'\n      am__tar_='find \"$tardir\" -print | cpio -o -H $1 -L'\n      am__untar='cpio -i -H $1 -d'\n      ;;\n    none)\n      am__tar=false\n      am__tar_=false\n      am__untar=false\n      ;;\n    esac\n\n    # If the value was cached, stop now.  We just wanted to have am__tar\n    # and am__untar set.\n    test -n \"${am_cv_prog_tar_$1}\" && break\n\n    # tar/untar a dummy directory, and stop if the command works.\n    rm -rf conftest.dir\n    mkdir conftest.dir\n    echo GrepMe > conftest.dir/file\n    AM_RUN_LOG([tardir=conftest.dir && eval $am__tar_ >conftest.tar])\n    rm -rf conftest.dir\n    if test -s conftest.tar; then\n      AM_RUN_LOG([$am__untar <conftest.tar])\n      AM_RUN_LOG([cat conftest.dir/file])\n      grep GrepMe conftest.dir/file >/dev/null 2>&1 && break\n    fi\n  done\n  rm -rf conftest.dir\n\n  AC_CACHE_VAL([am_cv_prog_tar_$1], [am_cv_prog_tar_$1=$_am_tool])\n  AC_MSG_RESULT([$am_cv_prog_tar_$1])])\n\nAC_SUBST([am__tar])\nAC_SUBST([am__untar])\n]) # _AM_PROG_TAR\n\nm4_include([m4/libtool.m4])\nm4_include([m4/ltoptions.m4])\nm4_include([m4/ltsugar.m4])\nm4_include([m4/ltversion.m4])\nm4_include([m4/lt~obsolete.m4])\nm4_include([m4/modern_cxx.m4])\nm4_include([m4/w32.m4])\n"
  },
  {
    "path": "cudd/build-aux/ar-lib",
    "content": "#! /bin/sh\n# Wrapper for Microsoft lib.exe\n\nme=ar-lib\nscriptversion=2012-03-01.08; # UTC\n\n# Copyright (C) 2010-2013 Free Software Foundation, Inc.\n# Written by Peter Rosin <peda@lysator.liu.se>.\n#\n# This program is free software; you can redistribute it and/or modify\n# it under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 2, or (at your option)\n# any later version.\n#\n# This program is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n# GNU General Public License for more details.\n#\n# You should have received a copy of the GNU General Public License\n# along with this program.  If not, see <http://www.gnu.org/licenses/>.\n\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program that contains a\n# configuration script generated by Autoconf, you may include it under\n# the same distribution terms that you use for the rest of that program.\n\n# This file is maintained in Automake, please report\n# bugs to <bug-automake@gnu.org> or send patches to\n# <automake-patches@gnu.org>.\n\n\n# func_error message\nfunc_error ()\n{\n  echo \"$me: $1\" 1>&2\n  exit 1\n}\n\nfile_conv=\n\n# func_file_conv build_file\n# Convert a $build file to $host form and store it in $file\n# Currently only supports Windows hosts.\nfunc_file_conv ()\n{\n  file=$1\n  case $file in\n    / | /[!/]*) # absolute file, and not a UNC file\n      if test -z \"$file_conv\"; then\n\t# lazily determine how to convert abs files\n\tcase `uname -s` in\n\t  MINGW*)\n\t    file_conv=mingw\n\t    ;;\n\t  CYGWIN*)\n\t    file_conv=cygwin\n\t    ;;\n\t  *)\n\t    file_conv=wine\n\t    ;;\n\tesac\n      fi\n      case $file_conv in\n\tmingw)\n\t  file=`cmd //C echo \"$file \" | sed -e 's/\"\\(.*\\) \" *$/\\1/'`\n\t  ;;\n\tcygwin)\n\t  file=`cygpath -m \"$file\" || echo \"$file\"`\n\t  ;;\n\twine)\n\t  file=`winepath -w \"$file\" || echo \"$file\"`\n\t  ;;\n      esac\n      ;;\n  esac\n}\n\n# func_at_file at_file operation archive\n# Iterate over all members in AT_FILE performing OPERATION on ARCHIVE\n# for each of them.\n# When interpreting the content of the @FILE, do NOT use func_file_conv,\n# since the user would need to supply preconverted file names to\n# binutils ar, at least for MinGW.\nfunc_at_file ()\n{\n  operation=$2\n  archive=$3\n  at_file_contents=`cat \"$1\"`\n  eval set x \"$at_file_contents\"\n  shift\n\n  for member\n  do\n    $AR -NOLOGO $operation:\"$member\" \"$archive\" || exit $?\n  done\n}\n\ncase $1 in\n  '')\n     func_error \"no command.  Try '$0 --help' for more information.\"\n     ;;\n  -h | --h*)\n    cat <<EOF\nUsage: $me [--help] [--version] PROGRAM ACTION ARCHIVE [MEMBER...]\n\nMembers may be specified in a file named with @FILE.\nEOF\n    exit $?\n    ;;\n  -v | --v*)\n    echo \"$me, version $scriptversion\"\n    exit $?\n    ;;\nesac\n\nif test $# -lt 3; then\n  func_error \"you must specify a program, an action and an archive\"\nfi\n\nAR=$1\nshift\nwhile :\ndo\n  if test $# -lt 2; then\n    func_error \"you must specify a program, an action and an archive\"\n  fi\n  case $1 in\n    -lib | -LIB \\\n    | -ltcg | -LTCG \\\n    | -machine* | -MACHINE* \\\n    | -subsystem* | -SUBSYSTEM* \\\n    | -verbose | -VERBOSE \\\n    | -wx* | -WX* )\n      AR=\"$AR $1\"\n      shift\n      ;;\n    *)\n      action=$1\n      shift\n      break\n      ;;\n  esac\ndone\norig_archive=$1\nshift\nfunc_file_conv \"$orig_archive\"\narchive=$file\n\n# strip leading dash in $action\naction=${action#-}\n\ndelete=\nextract=\nlist=\nquick=\nreplace=\nindex=\ncreate=\n\nwhile test -n \"$action\"\ndo\n  case $action in\n    d*) delete=yes  ;;\n    x*) extract=yes ;;\n    t*) list=yes    ;;\n    q*) quick=yes   ;;\n    r*) replace=yes ;;\n    s*) index=yes   ;;\n    S*)             ;; # the index is always updated implicitly\n    c*) create=yes  ;;\n    u*)             ;; # TODO: don't ignore the update modifier\n    v*)             ;; # TODO: don't ignore the verbose modifier\n    *)\n      func_error \"unknown action specified\"\n      ;;\n  esac\n  action=${action#?}\ndone\n\ncase $delete$extract$list$quick$replace,$index in\n  yes,* | ,yes)\n    ;;\n  yesyes*)\n    func_error \"more than one action specified\"\n    ;;\n  *)\n    func_error \"no action specified\"\n    ;;\nesac\n\nif test -n \"$delete\"; then\n  if test ! -f \"$orig_archive\"; then\n    func_error \"archive not found\"\n  fi\n  for member\n  do\n    case $1 in\n      @*)\n        func_at_file \"${1#@}\" -REMOVE \"$archive\"\n        ;;\n      *)\n        func_file_conv \"$1\"\n        $AR -NOLOGO -REMOVE:\"$file\" \"$archive\" || exit $?\n        ;;\n    esac\n  done\n\nelif test -n \"$extract\"; then\n  if test ! -f \"$orig_archive\"; then\n    func_error \"archive not found\"\n  fi\n  if test $# -gt 0; then\n    for member\n    do\n      case $1 in\n        @*)\n          func_at_file \"${1#@}\" -EXTRACT \"$archive\"\n          ;;\n        *)\n          func_file_conv \"$1\"\n          $AR -NOLOGO -EXTRACT:\"$file\" \"$archive\" || exit $?\n          ;;\n      esac\n    done\n  else\n    $AR -NOLOGO -LIST \"$archive\" | sed -e 's/\\\\/\\\\\\\\/g' | while read member\n    do\n      $AR -NOLOGO -EXTRACT:\"$member\" \"$archive\" || exit $?\n    done\n  fi\n\nelif test -n \"$quick$replace\"; then\n  if test ! -f \"$orig_archive\"; then\n    if test -z \"$create\"; then\n      echo \"$me: creating $orig_archive\"\n    fi\n    orig_archive=\n  else\n    orig_archive=$archive\n  fi\n\n  for member\n  do\n    case $1 in\n    @*)\n      func_file_conv \"${1#@}\"\n      set x \"$@\" \"@$file\"\n      ;;\n    *)\n      func_file_conv \"$1\"\n      set x \"$@\" \"$file\"\n      ;;\n    esac\n    shift\n    shift\n  done\n\n  if test -n \"$orig_archive\"; then\n    $AR -NOLOGO -OUT:\"$archive\" \"$orig_archive\" \"$@\" || exit $?\n  else\n    $AR -NOLOGO -OUT:\"$archive\" \"$@\" || exit $?\n  fi\n\nelif test -n \"$list\"; then\n  if test ! -f \"$orig_archive\"; then\n    func_error \"archive not found\"\n  fi\n  $AR -NOLOGO -LIST \"$archive\" || exit $?\nfi\n"
  },
  {
    "path": "cudd/build-aux/compile",
    "content": "#! /bin/sh\n# Wrapper for compilers which do not understand '-c -o'.\n\nscriptversion=2012-10-14.11; # UTC\n\n# Copyright (C) 1999-2013 Free Software Foundation, Inc.\n# Written by Tom Tromey <tromey@cygnus.com>.\n#\n# This program is free software; you can redistribute it and/or modify\n# it under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 2, or (at your option)\n# any later version.\n#\n# This program is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n# GNU General Public License for more details.\n#\n# You should have received a copy of the GNU General Public License\n# along with this program.  If not, see <http://www.gnu.org/licenses/>.\n\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program that contains a\n# configuration script generated by Autoconf, you may include it under\n# the same distribution terms that you use for the rest of that program.\n\n# This file is maintained in Automake, please report\n# bugs to <bug-automake@gnu.org> or send patches to\n# <automake-patches@gnu.org>.\n\nnl='\n'\n\n# We need space, tab and new line, in precisely that order.  Quoting is\n# there to prevent tools from complaining about whitespace usage.\nIFS=\" \"\"\t$nl\"\n\nfile_conv=\n\n# func_file_conv build_file lazy\n# Convert a $build file to $host form and store it in $file\n# Currently only supports Windows hosts. If the determined conversion\n# type is listed in (the comma separated) LAZY, no conversion will\n# take place.\nfunc_file_conv ()\n{\n  file=$1\n  case $file in\n    / | /[!/]*) # absolute file, and not a UNC file\n      if test -z \"$file_conv\"; then\n\t# lazily determine how to convert abs files\n\tcase `uname -s` in\n\t  MINGW*)\n\t    file_conv=mingw\n\t    ;;\n\t  CYGWIN*)\n\t    file_conv=cygwin\n\t    ;;\n\t  *)\n\t    file_conv=wine\n\t    ;;\n\tesac\n      fi\n      case $file_conv/,$2, in\n\t*,$file_conv,*)\n\t  ;;\n\tmingw/*)\n\t  file=`cmd //C echo \"$file \" | sed -e 's/\"\\(.*\\) \" *$/\\1/'`\n\t  ;;\n\tcygwin/*)\n\t  file=`cygpath -m \"$file\" || echo \"$file\"`\n\t  ;;\n\twine/*)\n\t  file=`winepath -w \"$file\" || echo \"$file\"`\n\t  ;;\n      esac\n      ;;\n  esac\n}\n\n# func_cl_dashL linkdir\n# Make cl look for libraries in LINKDIR\nfunc_cl_dashL ()\n{\n  func_file_conv \"$1\"\n  if test -z \"$lib_path\"; then\n    lib_path=$file\n  else\n    lib_path=\"$lib_path;$file\"\n  fi\n  linker_opts=\"$linker_opts -LIBPATH:$file\"\n}\n\n# func_cl_dashl library\n# Do a library search-path lookup for cl\nfunc_cl_dashl ()\n{\n  lib=$1\n  found=no\n  save_IFS=$IFS\n  IFS=';'\n  for dir in $lib_path $LIB\n  do\n    IFS=$save_IFS\n    if $shared && test -f \"$dir/$lib.dll.lib\"; then\n      found=yes\n      lib=$dir/$lib.dll.lib\n      break\n    fi\n    if test -f \"$dir/$lib.lib\"; then\n      found=yes\n      lib=$dir/$lib.lib\n      break\n    fi\n    if test -f \"$dir/lib$lib.a\"; then\n      found=yes\n      lib=$dir/lib$lib.a\n      break\n    fi\n  done\n  IFS=$save_IFS\n\n  if test \"$found\" != yes; then\n    lib=$lib.lib\n  fi\n}\n\n# func_cl_wrapper cl arg...\n# Adjust compile command to suit cl\nfunc_cl_wrapper ()\n{\n  # Assume a capable shell\n  lib_path=\n  shared=:\n  linker_opts=\n  for arg\n  do\n    if test -n \"$eat\"; then\n      eat=\n    else\n      case $1 in\n\t-o)\n\t  # configure might choose to run compile as 'compile cc -o foo foo.c'.\n\t  eat=1\n\t  case $2 in\n\t    *.o | *.[oO][bB][jJ])\n\t      func_file_conv \"$2\"\n\t      set x \"$@\" -Fo\"$file\"\n\t      shift\n\t      ;;\n\t    *)\n\t      func_file_conv \"$2\"\n\t      set x \"$@\" -Fe\"$file\"\n\t      shift\n\t      ;;\n\t  esac\n\t  ;;\n\t-I)\n\t  eat=1\n\t  func_file_conv \"$2\" mingw\n\t  set x \"$@\" -I\"$file\"\n\t  shift\n\t  ;;\n\t-I*)\n\t  func_file_conv \"${1#-I}\" mingw\n\t  set x \"$@\" -I\"$file\"\n\t  shift\n\t  ;;\n\t-l)\n\t  eat=1\n\t  func_cl_dashl \"$2\"\n\t  set x \"$@\" \"$lib\"\n\t  shift\n\t  ;;\n\t-l*)\n\t  func_cl_dashl \"${1#-l}\"\n\t  set x \"$@\" \"$lib\"\n\t  shift\n\t  ;;\n\t-L)\n\t  eat=1\n\t  func_cl_dashL \"$2\"\n\t  ;;\n\t-L*)\n\t  func_cl_dashL \"${1#-L}\"\n\t  ;;\n\t-static)\n\t  shared=false\n\t  ;;\n\t-Wl,*)\n\t  arg=${1#-Wl,}\n\t  save_ifs=\"$IFS\"; IFS=','\n\t  for flag in $arg; do\n\t    IFS=\"$save_ifs\"\n\t    linker_opts=\"$linker_opts $flag\"\n\t  done\n\t  IFS=\"$save_ifs\"\n\t  ;;\n\t-Xlinker)\n\t  eat=1\n\t  linker_opts=\"$linker_opts $2\"\n\t  ;;\n\t-*)\n\t  set x \"$@\" \"$1\"\n\t  shift\n\t  ;;\n\t*.cc | *.CC | *.cxx | *.CXX | *.[cC]++)\n\t  func_file_conv \"$1\"\n\t  set x \"$@\" -Tp\"$file\"\n\t  shift\n\t  ;;\n\t*.c | *.cpp | *.CPP | *.lib | *.LIB | *.Lib | *.OBJ | *.obj | *.[oO])\n\t  func_file_conv \"$1\" mingw\n\t  set x \"$@\" \"$file\"\n\t  shift\n\t  ;;\n\t*)\n\t  set x \"$@\" \"$1\"\n\t  shift\n\t  ;;\n      esac\n    fi\n    shift\n  done\n  if test -n \"$linker_opts\"; then\n    linker_opts=\"-link$linker_opts\"\n  fi\n  exec \"$@\" $linker_opts\n  exit 1\n}\n\neat=\n\ncase $1 in\n  '')\n     echo \"$0: No command.  Try '$0 --help' for more information.\" 1>&2\n     exit 1;\n     ;;\n  -h | --h*)\n    cat <<\\EOF\nUsage: compile [--help] [--version] PROGRAM [ARGS]\n\nWrapper for compilers which do not understand '-c -o'.\nRemove '-o dest.o' from ARGS, run PROGRAM with the remaining\narguments, and rename the output as expected.\n\nIf you are trying to build a whole package this is not the\nright script to run: please start by reading the file 'INSTALL'.\n\nReport bugs to <bug-automake@gnu.org>.\nEOF\n    exit $?\n    ;;\n  -v | --v*)\n    echo \"compile $scriptversion\"\n    exit $?\n    ;;\n  cl | *[/\\\\]cl | cl.exe | *[/\\\\]cl.exe )\n    func_cl_wrapper \"$@\"      # Doesn't return...\n    ;;\nesac\n\nofile=\ncfile=\n\nfor arg\ndo\n  if test -n \"$eat\"; then\n    eat=\n  else\n    case $1 in\n      -o)\n\t# configure might choose to run compile as 'compile cc -o foo foo.c'.\n\t# So we strip '-o arg' only if arg is an object.\n\teat=1\n\tcase $2 in\n\t  *.o | *.obj)\n\t    ofile=$2\n\t    ;;\n\t  *)\n\t    set x \"$@\" -o \"$2\"\n\t    shift\n\t    ;;\n\tesac\n\t;;\n      *.c)\n\tcfile=$1\n\tset x \"$@\" \"$1\"\n\tshift\n\t;;\n      *)\n\tset x \"$@\" \"$1\"\n\tshift\n\t;;\n    esac\n  fi\n  shift\ndone\n\nif test -z \"$ofile\" || test -z \"$cfile\"; then\n  # If no '-o' option was seen then we might have been invoked from a\n  # pattern rule where we don't need one.  That is ok -- this is a\n  # normal compilation that the losing compiler can handle.  If no\n  # '.c' file was seen then we are probably linking.  That is also\n  # ok.\n  exec \"$@\"\nfi\n\n# Name of file we expect compiler to create.\ncofile=`echo \"$cfile\" | sed 's|^.*[\\\\/]||; s|^[a-zA-Z]:||; s/\\.c$/.o/'`\n\n# Create the lock directory.\n# Note: use '[/\\\\:.-]' here to ensure that we don't use the same name\n# that we are using for the .o file.  Also, base the name on the expected\n# object file name, since that is what matters with a parallel build.\nlockdir=`echo \"$cofile\" | sed -e 's|[/\\\\:.-]|_|g'`.d\nwhile true; do\n  if mkdir \"$lockdir\" >/dev/null 2>&1; then\n    break\n  fi\n  sleep 1\ndone\n# FIXME: race condition here if user kills between mkdir and trap.\ntrap \"rmdir '$lockdir'; exit 1\" 1 2 15\n\n# Run the compile.\n\"$@\"\nret=$?\n\nif test -f \"$cofile\"; then\n  test \"$cofile\" = \"$ofile\" || mv \"$cofile\" \"$ofile\"\nelif test -f \"${cofile}bj\"; then\n  test \"${cofile}bj\" = \"$ofile\" || mv \"${cofile}bj\" \"$ofile\"\nfi\n\nrmdir \"$lockdir\"\nexit $ret\n\n# Local Variables:\n# mode: shell-script\n# sh-indentation: 2\n# eval: (add-hook 'write-file-hooks 'time-stamp)\n# time-stamp-start: \"scriptversion=\"\n# time-stamp-format: \"%:y-%02m-%02d.%02H\"\n# time-stamp-time-zone: \"UTC\"\n# time-stamp-end: \"; # UTC\"\n# End:\n"
  },
  {
    "path": "cudd/build-aux/config.guess",
    "content": "#! /bin/sh\n# Attempt to guess a canonical system name.\n#   Copyright 1992-2014 Free Software Foundation, Inc.\n\ntimestamp='2014-03-23'\n\n# This file is free software; you can redistribute it and/or modify it\n# under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 3 of the License, or\n# (at your option) any later version.\n#\n# This program is distributed in the hope that it will be useful, but\n# WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# General Public License for more details.\n#\n# You should have received a copy of the GNU General Public License\n# along with this program; if not, see <http://www.gnu.org/licenses/>.\n#\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program that contains a\n# configuration script generated by Autoconf, you may include it under\n# the same distribution terms that you use for the rest of that\n# program.  This Exception is an additional permission under section 7\n# of the GNU General Public License, version 3 (\"GPLv3\").\n#\n# Originally written by Per Bothner.\n#\n# You can get the latest version of this script from:\n# http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess;hb=HEAD\n#\n# Please send patches with a ChangeLog entry to config-patches@gnu.org.\n\n\nme=`echo \"$0\" | sed -e 's,.*/,,'`\n\nusage=\"\\\nUsage: $0 [OPTION]\n\nOutput the configuration name of the system \\`$me' is run on.\n\nOperation modes:\n  -h, --help         print this help, then exit\n  -t, --time-stamp   print date of last modification, then exit\n  -v, --version      print version number, then exit\n\nReport bugs and patches to <config-patches@gnu.org>.\"\n\nversion=\"\\\nGNU config.guess ($timestamp)\n\nOriginally written by Per Bothner.\nCopyright 1992-2014 Free Software Foundation, Inc.\n\nThis is free software; see the source for copying conditions.  There is NO\nwarranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\"\n\nhelp=\"\nTry \\`$me --help' for more information.\"\n\n# Parse command line\nwhile test $# -gt 0 ; do\n  case $1 in\n    --time-stamp | --time* | -t )\n       echo \"$timestamp\" ; exit ;;\n    --version | -v )\n       echo \"$version\" ; exit ;;\n    --help | --h* | -h )\n       echo \"$usage\"; exit ;;\n    -- )     # Stop option processing\n       shift; break ;;\n    - )\t# Use stdin as input.\n       break ;;\n    -* )\n       echo \"$me: invalid option $1$help\" >&2\n       exit 1 ;;\n    * )\n       break ;;\n  esac\ndone\n\nif test $# != 0; then\n  echo \"$me: too many arguments$help\" >&2\n  exit 1\nfi\n\ntrap 'exit 1' 1 2 15\n\n# CC_FOR_BUILD -- compiler used by this script. Note that the use of a\n# compiler to aid in system detection is discouraged as it requires\n# temporary files to be created and, as you can see below, it is a\n# headache to deal with in a portable fashion.\n\n# Historically, `CC_FOR_BUILD' used to be named `HOST_CC'. We still\n# use `HOST_CC' if defined, but it is deprecated.\n\n# Portable tmp directory creation inspired by the Autoconf team.\n\nset_cc_for_build='\ntrap \"exitcode=\\$?; (rm -f \\$tmpfiles 2>/dev/null; rmdir \\$tmp 2>/dev/null) && exit \\$exitcode\" 0 ;\ntrap \"rm -f \\$tmpfiles 2>/dev/null; rmdir \\$tmp 2>/dev/null; exit 1\" 1 2 13 15 ;\n: ${TMPDIR=/tmp} ;\n { tmp=`(umask 077 && mktemp -d \"$TMPDIR/cgXXXXXX\") 2>/dev/null` && test -n \"$tmp\" && test -d \"$tmp\" ; } ||\n { test -n \"$RANDOM\" && tmp=$TMPDIR/cg$$-$RANDOM && (umask 077 && mkdir $tmp) ; } ||\n { tmp=$TMPDIR/cg-$$ && (umask 077 && mkdir $tmp) && echo \"Warning: creating insecure temp directory\" >&2 ; } ||\n { echo \"$me: cannot create a temporary directory in $TMPDIR\" >&2 ; exit 1 ; } ;\ndummy=$tmp/dummy ;\ntmpfiles=\"$dummy.c $dummy.o $dummy.rel $dummy\" ;\ncase $CC_FOR_BUILD,$HOST_CC,$CC in\n ,,)    echo \"int x;\" > $dummy.c ;\n\tfor c in cc gcc c89 c99 ; do\n\t  if ($c -c -o $dummy.o $dummy.c) >/dev/null 2>&1 ; then\n\t     CC_FOR_BUILD=\"$c\"; break ;\n\t  fi ;\n\tdone ;\n\tif test x\"$CC_FOR_BUILD\" = x ; then\n\t  CC_FOR_BUILD=no_compiler_found ;\n\tfi\n\t;;\n ,,*)   CC_FOR_BUILD=$CC ;;\n ,*,*)  CC_FOR_BUILD=$HOST_CC ;;\nesac ; set_cc_for_build= ;'\n\n# This is needed to find uname on a Pyramid OSx when run in the BSD universe.\n# (ghazi@noc.rutgers.edu 1994-08-24)\nif (test -f /.attbin/uname) >/dev/null 2>&1 ; then\n\tPATH=$PATH:/.attbin ; export PATH\nfi\n\nUNAME_MACHINE=`(uname -m) 2>/dev/null` || UNAME_MACHINE=unknown\nUNAME_RELEASE=`(uname -r) 2>/dev/null` || UNAME_RELEASE=unknown\nUNAME_SYSTEM=`(uname -s) 2>/dev/null`  || UNAME_SYSTEM=unknown\nUNAME_VERSION=`(uname -v) 2>/dev/null` || UNAME_VERSION=unknown\n\ncase \"${UNAME_SYSTEM}\" in\nLinux|GNU|GNU/*)\n\t# If the system lacks a compiler, then just pick glibc.\n\t# We could probably try harder.\n\tLIBC=gnu\n\n\teval $set_cc_for_build\n\tcat <<-EOF > $dummy.c\n\t#include <features.h>\n\t#if defined(__UCLIBC__)\n\tLIBC=uclibc\n\t#elif defined(__dietlibc__)\n\tLIBC=dietlibc\n\t#else\n\tLIBC=gnu\n\t#endif\n\tEOF\n\teval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^LIBC' | sed 's, ,,g'`\n\t;;\nesac\n\n# Note: order is significant - the case branches are not exclusive.\n\ncase \"${UNAME_MACHINE}:${UNAME_SYSTEM}:${UNAME_RELEASE}:${UNAME_VERSION}\" in\n    *:NetBSD:*:*)\n\t# NetBSD (nbsd) targets should (where applicable) match one or\n\t# more of the tuples: *-*-netbsdelf*, *-*-netbsdaout*,\n\t# *-*-netbsdecoff* and *-*-netbsd*.  For targets that recently\n\t# switched to ELF, *-*-netbsd* would select the old\n\t# object file format.  This provides both forward\n\t# compatibility and a consistent mechanism for selecting the\n\t# object file format.\n\t#\n\t# Note: NetBSD doesn't particularly care about the vendor\n\t# portion of the name.  We always set it to \"unknown\".\n\tsysctl=\"sysctl -n hw.machine_arch\"\n\tUNAME_MACHINE_ARCH=`(/sbin/$sysctl 2>/dev/null || \\\n\t    /usr/sbin/$sysctl 2>/dev/null || echo unknown)`\n\tcase \"${UNAME_MACHINE_ARCH}\" in\n\t    armeb) machine=armeb-unknown ;;\n\t    arm*) machine=arm-unknown ;;\n\t    sh3el) machine=shl-unknown ;;\n\t    sh3eb) machine=sh-unknown ;;\n\t    sh5el) machine=sh5le-unknown ;;\n\t    *) machine=${UNAME_MACHINE_ARCH}-unknown ;;\n\tesac\n\t# The Operating System including object format, if it has switched\n\t# to ELF recently, or will in the future.\n\tcase \"${UNAME_MACHINE_ARCH}\" in\n\t    arm*|i386|m68k|ns32k|sh3*|sparc|vax)\n\t\teval $set_cc_for_build\n\t\tif echo __ELF__ | $CC_FOR_BUILD -E - 2>/dev/null \\\n\t\t\t| grep -q __ELF__\n\t\tthen\n\t\t    # Once all utilities can be ECOFF (netbsdecoff) or a.out (netbsdaout).\n\t\t    # Return netbsd for either.  FIX?\n\t\t    os=netbsd\n\t\telse\n\t\t    os=netbsdelf\n\t\tfi\n\t\t;;\n\t    *)\n\t\tos=netbsd\n\t\t;;\n\tesac\n\t# The OS release\n\t# Debian GNU/NetBSD machines have a different userland, and\n\t# thus, need a distinct triplet. However, they do not need\n\t# kernel version information, so it can be replaced with a\n\t# suitable tag, in the style of linux-gnu.\n\tcase \"${UNAME_VERSION}\" in\n\t    Debian*)\n\t\trelease='-gnu'\n\t\t;;\n\t    *)\n\t\trelease=`echo ${UNAME_RELEASE}|sed -e 's/[-_].*/\\./'`\n\t\t;;\n\tesac\n\t# Since CPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM:\n\t# contains redundant information, the shorter form:\n\t# CPU_TYPE-MANUFACTURER-OPERATING_SYSTEM is used.\n\techo \"${machine}-${os}${release}\"\n\texit ;;\n    *:Bitrig:*:*)\n\tUNAME_MACHINE_ARCH=`arch | sed 's/Bitrig.//'`\n\techo ${UNAME_MACHINE_ARCH}-unknown-bitrig${UNAME_RELEASE}\n\texit ;;\n    *:OpenBSD:*:*)\n\tUNAME_MACHINE_ARCH=`arch | sed 's/OpenBSD.//'`\n\techo ${UNAME_MACHINE_ARCH}-unknown-openbsd${UNAME_RELEASE}\n\texit ;;\n    *:ekkoBSD:*:*)\n\techo ${UNAME_MACHINE}-unknown-ekkobsd${UNAME_RELEASE}\n\texit ;;\n    *:SolidBSD:*:*)\n\techo ${UNAME_MACHINE}-unknown-solidbsd${UNAME_RELEASE}\n\texit ;;\n    macppc:MirBSD:*:*)\n\techo powerpc-unknown-mirbsd${UNAME_RELEASE}\n\texit ;;\n    *:MirBSD:*:*)\n\techo ${UNAME_MACHINE}-unknown-mirbsd${UNAME_RELEASE}\n\texit ;;\n    alpha:OSF1:*:*)\n\tcase $UNAME_RELEASE in\n\t*4.0)\n\t\tUNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $3}'`\n\t\t;;\n\t*5.*)\n\t\tUNAME_RELEASE=`/usr/sbin/sizer -v | awk '{print $4}'`\n\t\t;;\n\tesac\n\t# According to Compaq, /usr/sbin/psrinfo has been available on\n\t# OSF/1 and Tru64 systems produced since 1995.  I hope that\n\t# covers most systems running today.  This code pipes the CPU\n\t# types through head -n 1, so we only detect the type of CPU 0.\n\tALPHA_CPU_TYPE=`/usr/sbin/psrinfo -v | sed -n -e 's/^  The alpha \\(.*\\) processor.*$/\\1/p' | head -n 1`\n\tcase \"$ALPHA_CPU_TYPE\" in\n\t    \"EV4 (21064)\")\n\t\tUNAME_MACHINE=\"alpha\" ;;\n\t    \"EV4.5 (21064)\")\n\t\tUNAME_MACHINE=\"alpha\" ;;\n\t    \"LCA4 (21066/21068)\")\n\t\tUNAME_MACHINE=\"alpha\" ;;\n\t    \"EV5 (21164)\")\n\t\tUNAME_MACHINE=\"alphaev5\" ;;\n\t    \"EV5.6 (21164A)\")\n\t\tUNAME_MACHINE=\"alphaev56\" ;;\n\t    \"EV5.6 (21164PC)\")\n\t\tUNAME_MACHINE=\"alphapca56\" ;;\n\t    \"EV5.7 (21164PC)\")\n\t\tUNAME_MACHINE=\"alphapca57\" ;;\n\t    \"EV6 (21264)\")\n\t\tUNAME_MACHINE=\"alphaev6\" ;;\n\t    \"EV6.7 (21264A)\")\n\t\tUNAME_MACHINE=\"alphaev67\" ;;\n\t    \"EV6.8CB (21264C)\")\n\t\tUNAME_MACHINE=\"alphaev68\" ;;\n\t    \"EV6.8AL (21264B)\")\n\t\tUNAME_MACHINE=\"alphaev68\" ;;\n\t    \"EV6.8CX (21264D)\")\n\t\tUNAME_MACHINE=\"alphaev68\" ;;\n\t    \"EV6.9A (21264/EV69A)\")\n\t\tUNAME_MACHINE=\"alphaev69\" ;;\n\t    \"EV7 (21364)\")\n\t\tUNAME_MACHINE=\"alphaev7\" ;;\n\t    \"EV7.9 (21364A)\")\n\t\tUNAME_MACHINE=\"alphaev79\" ;;\n\tesac\n\t# A Pn.n version is a patched version.\n\t# A Vn.n version is a released version.\n\t# A Tn.n version is a released field test version.\n\t# A Xn.n version is an unreleased experimental baselevel.\n\t# 1.2 uses \"1.2\" for uname -r.\n\techo ${UNAME_MACHINE}-dec-osf`echo ${UNAME_RELEASE} | sed -e 's/^[PVTX]//' | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`\n\t# Reset EXIT trap before exiting to avoid spurious non-zero exit code.\n\texitcode=$?\n\ttrap '' 0\n\texit $exitcode ;;\n    Alpha\\ *:Windows_NT*:*)\n\t# How do we know it's Interix rather than the generic POSIX subsystem?\n\t# Should we change UNAME_MACHINE based on the output of uname instead\n\t# of the specific Alpha model?\n\techo alpha-pc-interix\n\texit ;;\n    21064:Windows_NT:50:3)\n\techo alpha-dec-winnt3.5\n\texit ;;\n    Amiga*:UNIX_System_V:4.0:*)\n\techo m68k-unknown-sysv4\n\texit ;;\n    *:[Aa]miga[Oo][Ss]:*:*)\n\techo ${UNAME_MACHINE}-unknown-amigaos\n\texit ;;\n    *:[Mm]orph[Oo][Ss]:*:*)\n\techo ${UNAME_MACHINE}-unknown-morphos\n\texit ;;\n    *:OS/390:*:*)\n\techo i370-ibm-openedition\n\texit ;;\n    *:z/VM:*:*)\n\techo s390-ibm-zvmoe\n\texit ;;\n    *:OS400:*:*)\n\techo powerpc-ibm-os400\n\texit ;;\n    arm:RISC*:1.[012]*:*|arm:riscix:1.[012]*:*)\n\techo arm-acorn-riscix${UNAME_RELEASE}\n\texit ;;\n    arm*:riscos:*:*|arm*:RISCOS:*:*)\n\techo arm-unknown-riscos\n\texit ;;\n    SR2?01:HI-UX/MPP:*:* | SR8000:HI-UX/MPP:*:*)\n\techo hppa1.1-hitachi-hiuxmpp\n\texit ;;\n    Pyramid*:OSx*:*:* | MIS*:OSx*:*:* | MIS*:SMP_DC-OSx*:*:*)\n\t# akee@wpdis03.wpafb.af.mil (Earle F. Ake) contributed MIS and NILE.\n\tif test \"`(/bin/universe) 2>/dev/null`\" = att ; then\n\t\techo pyramid-pyramid-sysv3\n\telse\n\t\techo pyramid-pyramid-bsd\n\tfi\n\texit ;;\n    NILE*:*:*:dcosx)\n\techo pyramid-pyramid-svr4\n\texit ;;\n    DRS?6000:unix:4.0:6*)\n\techo sparc-icl-nx6\n\texit ;;\n    DRS?6000:UNIX_SV:4.2*:7* | DRS?6000:isis:4.2*:7*)\n\tcase `/usr/bin/uname -p` in\n\t    sparc) echo sparc-icl-nx7; exit ;;\n\tesac ;;\n    s390x:SunOS:*:*)\n\techo ${UNAME_MACHINE}-ibm-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`\n\texit ;;\n    sun4H:SunOS:5.*:*)\n\techo sparc-hal-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`\n\texit ;;\n    sun4*:SunOS:5.*:* | tadpole*:SunOS:5.*:*)\n\techo sparc-sun-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`\n\texit ;;\n    i86pc:AuroraUX:5.*:* | i86xen:AuroraUX:5.*:*)\n\techo i386-pc-auroraux${UNAME_RELEASE}\n\texit ;;\n    i86pc:SunOS:5.*:* | i86xen:SunOS:5.*:*)\n\teval $set_cc_for_build\n\tSUN_ARCH=\"i386\"\n\t# If there is a compiler, see if it is configured for 64-bit objects.\n\t# Note that the Sun cc does not turn __LP64__ into 1 like gcc does.\n\t# This test works for both compilers.\n\tif [ \"$CC_FOR_BUILD\" != 'no_compiler_found' ]; then\n\t    if (echo '#ifdef __amd64'; echo IS_64BIT_ARCH; echo '#endif') | \\\n\t\t(CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | \\\n\t\tgrep IS_64BIT_ARCH >/dev/null\n\t    then\n\t\tSUN_ARCH=\"x86_64\"\n\t    fi\n\tfi\n\techo ${SUN_ARCH}-pc-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`\n\texit ;;\n    sun4*:SunOS:6*:*)\n\t# According to config.sub, this is the proper way to canonicalize\n\t# SunOS6.  Hard to guess exactly what SunOS6 will be like, but\n\t# it's likely to be more like Solaris than SunOS4.\n\techo sparc-sun-solaris3`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`\n\texit ;;\n    sun4*:SunOS:*:*)\n\tcase \"`/usr/bin/arch -k`\" in\n\t    Series*|S4*)\n\t\tUNAME_RELEASE=`uname -v`\n\t\t;;\n\tesac\n\t# Japanese Language versions have a version number like `4.1.3-JL'.\n\techo sparc-sun-sunos`echo ${UNAME_RELEASE}|sed -e 's/-/_/'`\n\texit ;;\n    sun3*:SunOS:*:*)\n\techo m68k-sun-sunos${UNAME_RELEASE}\n\texit ;;\n    sun*:*:4.2BSD:*)\n\tUNAME_RELEASE=`(sed 1q /etc/motd | awk '{print substr($5,1,3)}') 2>/dev/null`\n\ttest \"x${UNAME_RELEASE}\" = \"x\" && UNAME_RELEASE=3\n\tcase \"`/bin/arch`\" in\n\t    sun3)\n\t\techo m68k-sun-sunos${UNAME_RELEASE}\n\t\t;;\n\t    sun4)\n\t\techo sparc-sun-sunos${UNAME_RELEASE}\n\t\t;;\n\tesac\n\texit ;;\n    aushp:SunOS:*:*)\n\techo sparc-auspex-sunos${UNAME_RELEASE}\n\texit ;;\n    # The situation for MiNT is a little confusing.  The machine name\n    # can be virtually everything (everything which is not\n    # \"atarist\" or \"atariste\" at least should have a processor\n    # > m68000).  The system name ranges from \"MiNT\" over \"FreeMiNT\"\n    # to the lowercase version \"mint\" (or \"freemint\").  Finally\n    # the system name \"TOS\" denotes a system which is actually not\n    # MiNT.  But MiNT is downward compatible to TOS, so this should\n    # be no problem.\n    atarist[e]:*MiNT:*:* | atarist[e]:*mint:*:* | atarist[e]:*TOS:*:*)\n\techo m68k-atari-mint${UNAME_RELEASE}\n\texit ;;\n    atari*:*MiNT:*:* | atari*:*mint:*:* | atarist[e]:*TOS:*:*)\n\techo m68k-atari-mint${UNAME_RELEASE}\n\texit ;;\n    *falcon*:*MiNT:*:* | *falcon*:*mint:*:* | *falcon*:*TOS:*:*)\n\techo m68k-atari-mint${UNAME_RELEASE}\n\texit ;;\n    milan*:*MiNT:*:* | milan*:*mint:*:* | *milan*:*TOS:*:*)\n\techo m68k-milan-mint${UNAME_RELEASE}\n\texit ;;\n    hades*:*MiNT:*:* | hades*:*mint:*:* | *hades*:*TOS:*:*)\n\techo m68k-hades-mint${UNAME_RELEASE}\n\texit ;;\n    *:*MiNT:*:* | *:*mint:*:* | *:*TOS:*:*)\n\techo m68k-unknown-mint${UNAME_RELEASE}\n\texit ;;\n    m68k:machten:*:*)\n\techo m68k-apple-machten${UNAME_RELEASE}\n\texit ;;\n    powerpc:machten:*:*)\n\techo powerpc-apple-machten${UNAME_RELEASE}\n\texit ;;\n    RISC*:Mach:*:*)\n\techo mips-dec-mach_bsd4.3\n\texit ;;\n    RISC*:ULTRIX:*:*)\n\techo mips-dec-ultrix${UNAME_RELEASE}\n\texit ;;\n    VAX*:ULTRIX*:*:*)\n\techo vax-dec-ultrix${UNAME_RELEASE}\n\texit ;;\n    2020:CLIX:*:* | 2430:CLIX:*:*)\n\techo clipper-intergraph-clix${UNAME_RELEASE}\n\texit ;;\n    mips:*:*:UMIPS | mips:*:*:RISCos)\n\teval $set_cc_for_build\n\tsed 's/^\t//' << EOF >$dummy.c\n#ifdef __cplusplus\n#include <stdio.h>  /* for printf() prototype */\n\tint main (int argc, char *argv[]) {\n#else\n\tint main (argc, argv) int argc; char *argv[]; {\n#endif\n\t#if defined (host_mips) && defined (MIPSEB)\n\t#if defined (SYSTYPE_SYSV)\n\t  printf (\"mips-mips-riscos%ssysv\\n\", argv[1]); exit (0);\n\t#endif\n\t#if defined (SYSTYPE_SVR4)\n\t  printf (\"mips-mips-riscos%ssvr4\\n\", argv[1]); exit (0);\n\t#endif\n\t#if defined (SYSTYPE_BSD43) || defined(SYSTYPE_BSD)\n\t  printf (\"mips-mips-riscos%sbsd\\n\", argv[1]); exit (0);\n\t#endif\n\t#endif\n\t  exit (-1);\n\t}\nEOF\n\t$CC_FOR_BUILD -o $dummy $dummy.c &&\n\t  dummyarg=`echo \"${UNAME_RELEASE}\" | sed -n 's/\\([0-9]*\\).*/\\1/p'` &&\n\t  SYSTEM_NAME=`$dummy $dummyarg` &&\n\t    { echo \"$SYSTEM_NAME\"; exit; }\n\techo mips-mips-riscos${UNAME_RELEASE}\n\texit ;;\n    Motorola:PowerMAX_OS:*:*)\n\techo powerpc-motorola-powermax\n\texit ;;\n    Motorola:*:4.3:PL8-*)\n\techo powerpc-harris-powermax\n\texit ;;\n    Night_Hawk:*:*:PowerMAX_OS | Synergy:PowerMAX_OS:*:*)\n\techo powerpc-harris-powermax\n\texit ;;\n    Night_Hawk:Power_UNIX:*:*)\n\techo powerpc-harris-powerunix\n\texit ;;\n    m88k:CX/UX:7*:*)\n\techo m88k-harris-cxux7\n\texit ;;\n    m88k:*:4*:R4*)\n\techo m88k-motorola-sysv4\n\texit ;;\n    m88k:*:3*:R3*)\n\techo m88k-motorola-sysv3\n\texit ;;\n    AViiON:dgux:*:*)\n\t# DG/UX returns AViiON for all architectures\n\tUNAME_PROCESSOR=`/usr/bin/uname -p`\n\tif [ $UNAME_PROCESSOR = mc88100 ] || [ $UNAME_PROCESSOR = mc88110 ]\n\tthen\n\t    if [ ${TARGET_BINARY_INTERFACE}x = m88kdguxelfx ] || \\\n\t       [ ${TARGET_BINARY_INTERFACE}x = x ]\n\t    then\n\t\techo m88k-dg-dgux${UNAME_RELEASE}\n\t    else\n\t\techo m88k-dg-dguxbcs${UNAME_RELEASE}\n\t    fi\n\telse\n\t    echo i586-dg-dgux${UNAME_RELEASE}\n\tfi\n\texit ;;\n    M88*:DolphinOS:*:*)\t# DolphinOS (SVR3)\n\techo m88k-dolphin-sysv3\n\texit ;;\n    M88*:*:R3*:*)\n\t# Delta 88k system running SVR3\n\techo m88k-motorola-sysv3\n\texit ;;\n    XD88*:*:*:*) # Tektronix XD88 system running UTekV (SVR3)\n\techo m88k-tektronix-sysv3\n\texit ;;\n    Tek43[0-9][0-9]:UTek:*:*) # Tektronix 4300 system running UTek (BSD)\n\techo m68k-tektronix-bsd\n\texit ;;\n    *:IRIX*:*:*)\n\techo mips-sgi-irix`echo ${UNAME_RELEASE}|sed -e 's/-/_/g'`\n\texit ;;\n    ????????:AIX?:[12].1:2)   # AIX 2.2.1 or AIX 2.1.1 is RT/PC AIX.\n\techo romp-ibm-aix     # uname -m gives an 8 hex-code CPU id\n\texit ;;               # Note that: echo \"'`uname -s`'\" gives 'AIX '\n    i*86:AIX:*:*)\n\techo i386-ibm-aix\n\texit ;;\n    ia64:AIX:*:*)\n\tif [ -x /usr/bin/oslevel ] ; then\n\t\tIBM_REV=`/usr/bin/oslevel`\n\telse\n\t\tIBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}\n\tfi\n\techo ${UNAME_MACHINE}-ibm-aix${IBM_REV}\n\texit ;;\n    *:AIX:2:3)\n\tif grep bos325 /usr/include/stdio.h >/dev/null 2>&1; then\n\t\teval $set_cc_for_build\n\t\tsed 's/^\t\t//' << EOF >$dummy.c\n\t\t#include <sys/systemcfg.h>\n\n\t\tmain()\n\t\t\t{\n\t\t\tif (!__power_pc())\n\t\t\t\texit(1);\n\t\t\tputs(\"powerpc-ibm-aix3.2.5\");\n\t\t\texit(0);\n\t\t\t}\nEOF\n\t\tif $CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy`\n\t\tthen\n\t\t\techo \"$SYSTEM_NAME\"\n\t\telse\n\t\t\techo rs6000-ibm-aix3.2.5\n\t\tfi\n\telif grep bos324 /usr/include/stdio.h >/dev/null 2>&1; then\n\t\techo rs6000-ibm-aix3.2.4\n\telse\n\t\techo rs6000-ibm-aix3.2\n\tfi\n\texit ;;\n    *:AIX:*:[4567])\n\tIBM_CPU_ID=`/usr/sbin/lsdev -C -c processor -S available | sed 1q | awk '{ print $1 }'`\n\tif /usr/sbin/lsattr -El ${IBM_CPU_ID} | grep ' POWER' >/dev/null 2>&1; then\n\t\tIBM_ARCH=rs6000\n\telse\n\t\tIBM_ARCH=powerpc\n\tfi\n\tif [ -x /usr/bin/oslevel ] ; then\n\t\tIBM_REV=`/usr/bin/oslevel`\n\telse\n\t\tIBM_REV=${UNAME_VERSION}.${UNAME_RELEASE}\n\tfi\n\techo ${IBM_ARCH}-ibm-aix${IBM_REV}\n\texit ;;\n    *:AIX:*:*)\n\techo rs6000-ibm-aix\n\texit ;;\n    ibmrt:4.4BSD:*|romp-ibm:BSD:*)\n\techo romp-ibm-bsd4.4\n\texit ;;\n    ibmrt:*BSD:*|romp-ibm:BSD:*)            # covers RT/PC BSD and\n\techo romp-ibm-bsd${UNAME_RELEASE}   # 4.3 with uname added to\n\texit ;;                             # report: romp-ibm BSD 4.3\n    *:BOSX:*:*)\n\techo rs6000-bull-bosx\n\texit ;;\n    DPX/2?00:B.O.S.:*:*)\n\techo m68k-bull-sysv3\n\texit ;;\n    9000/[34]??:4.3bsd:1.*:*)\n\techo m68k-hp-bsd\n\texit ;;\n    hp300:4.4BSD:*:* | 9000/[34]??:4.3bsd:2.*:*)\n\techo m68k-hp-bsd4.4\n\texit ;;\n    9000/[34678]??:HP-UX:*:*)\n\tHPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`\n\tcase \"${UNAME_MACHINE}\" in\n\t    9000/31? )            HP_ARCH=m68000 ;;\n\t    9000/[34]?? )         HP_ARCH=m68k ;;\n\t    9000/[678][0-9][0-9])\n\t\tif [ -x /usr/bin/getconf ]; then\n\t\t    sc_cpu_version=`/usr/bin/getconf SC_CPU_VERSION 2>/dev/null`\n\t\t    sc_kernel_bits=`/usr/bin/getconf SC_KERNEL_BITS 2>/dev/null`\n\t\t    case \"${sc_cpu_version}\" in\n\t\t      523) HP_ARCH=\"hppa1.0\" ;; # CPU_PA_RISC1_0\n\t\t      528) HP_ARCH=\"hppa1.1\" ;; # CPU_PA_RISC1_1\n\t\t      532)                      # CPU_PA_RISC2_0\n\t\t\tcase \"${sc_kernel_bits}\" in\n\t\t\t  32) HP_ARCH=\"hppa2.0n\" ;;\n\t\t\t  64) HP_ARCH=\"hppa2.0w\" ;;\n\t\t\t  '') HP_ARCH=\"hppa2.0\" ;;   # HP-UX 10.20\n\t\t\tesac ;;\n\t\t    esac\n\t\tfi\n\t\tif [ \"${HP_ARCH}\" = \"\" ]; then\n\t\t    eval $set_cc_for_build\n\t\t    sed 's/^\t\t//' << EOF >$dummy.c\n\n\t\t#define _HPUX_SOURCE\n\t\t#include <stdlib.h>\n\t\t#include <unistd.h>\n\n\t\tint main ()\n\t\t{\n\t\t#if defined(_SC_KERNEL_BITS)\n\t\t    long bits = sysconf(_SC_KERNEL_BITS);\n\t\t#endif\n\t\t    long cpu  = sysconf (_SC_CPU_VERSION);\n\n\t\t    switch (cpu)\n\t\t\t{\n\t\t\tcase CPU_PA_RISC1_0: puts (\"hppa1.0\"); break;\n\t\t\tcase CPU_PA_RISC1_1: puts (\"hppa1.1\"); break;\n\t\t\tcase CPU_PA_RISC2_0:\n\t\t#if defined(_SC_KERNEL_BITS)\n\t\t\t    switch (bits)\n\t\t\t\t{\n\t\t\t\tcase 64: puts (\"hppa2.0w\"); break;\n\t\t\t\tcase 32: puts (\"hppa2.0n\"); break;\n\t\t\t\tdefault: puts (\"hppa2.0\"); break;\n\t\t\t\t} break;\n\t\t#else  /* !defined(_SC_KERNEL_BITS) */\n\t\t\t    puts (\"hppa2.0\"); break;\n\t\t#endif\n\t\t\tdefault: puts (\"hppa1.0\"); break;\n\t\t\t}\n\t\t    exit (0);\n\t\t}\nEOF\n\t\t    (CCOPTS= $CC_FOR_BUILD -o $dummy $dummy.c 2>/dev/null) && HP_ARCH=`$dummy`\n\t\t    test -z \"$HP_ARCH\" && HP_ARCH=hppa\n\t\tfi ;;\n\tesac\n\tif [ ${HP_ARCH} = \"hppa2.0w\" ]\n\tthen\n\t    eval $set_cc_for_build\n\n\t    # hppa2.0w-hp-hpux* has a 64-bit kernel and a compiler generating\n\t    # 32-bit code.  hppa64-hp-hpux* has the same kernel and a compiler\n\t    # generating 64-bit code.  GNU and HP use different nomenclature:\n\t    #\n\t    # $ CC_FOR_BUILD=cc ./config.guess\n\t    # => hppa2.0w-hp-hpux11.23\n\t    # $ CC_FOR_BUILD=\"cc +DA2.0w\" ./config.guess\n\t    # => hppa64-hp-hpux11.23\n\n\t    if echo __LP64__ | (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) |\n\t\tgrep -q __LP64__\n\t    then\n\t\tHP_ARCH=\"hppa2.0w\"\n\t    else\n\t\tHP_ARCH=\"hppa64\"\n\t    fi\n\tfi\n\techo ${HP_ARCH}-hp-hpux${HPUX_REV}\n\texit ;;\n    ia64:HP-UX:*:*)\n\tHPUX_REV=`echo ${UNAME_RELEASE}|sed -e 's/[^.]*.[0B]*//'`\n\techo ia64-hp-hpux${HPUX_REV}\n\texit ;;\n    3050*:HI-UX:*:*)\n\teval $set_cc_for_build\n\tsed 's/^\t//' << EOF >$dummy.c\n\t#include <unistd.h>\n\tint\n\tmain ()\n\t{\n\t  long cpu = sysconf (_SC_CPU_VERSION);\n\t  /* The order matters, because CPU_IS_HP_MC68K erroneously returns\n\t     true for CPU_PA_RISC1_0.  CPU_IS_PA_RISC returns correct\n\t     results, however.  */\n\t  if (CPU_IS_PA_RISC (cpu))\n\t    {\n\t      switch (cpu)\n\t\t{\n\t\t  case CPU_PA_RISC1_0: puts (\"hppa1.0-hitachi-hiuxwe2\"); break;\n\t\t  case CPU_PA_RISC1_1: puts (\"hppa1.1-hitachi-hiuxwe2\"); break;\n\t\t  case CPU_PA_RISC2_0: puts (\"hppa2.0-hitachi-hiuxwe2\"); break;\n\t\t  default: puts (\"hppa-hitachi-hiuxwe2\"); break;\n\t\t}\n\t    }\n\t  else if (CPU_IS_HP_MC68K (cpu))\n\t    puts (\"m68k-hitachi-hiuxwe2\");\n\t  else puts (\"unknown-hitachi-hiuxwe2\");\n\t  exit (0);\n\t}\nEOF\n\t$CC_FOR_BUILD -o $dummy $dummy.c && SYSTEM_NAME=`$dummy` &&\n\t\t{ echo \"$SYSTEM_NAME\"; exit; }\n\techo unknown-hitachi-hiuxwe2\n\texit ;;\n    9000/7??:4.3bsd:*:* | 9000/8?[79]:4.3bsd:*:* )\n\techo hppa1.1-hp-bsd\n\texit ;;\n    9000/8??:4.3bsd:*:*)\n\techo hppa1.0-hp-bsd\n\texit ;;\n    *9??*:MPE/iX:*:* | *3000*:MPE/iX:*:*)\n\techo hppa1.0-hp-mpeix\n\texit ;;\n    hp7??:OSF1:*:* | hp8?[79]:OSF1:*:* )\n\techo hppa1.1-hp-osf\n\texit ;;\n    hp8??:OSF1:*:*)\n\techo hppa1.0-hp-osf\n\texit ;;\n    i*86:OSF1:*:*)\n\tif [ -x /usr/sbin/sysversion ] ; then\n\t    echo ${UNAME_MACHINE}-unknown-osf1mk\n\telse\n\t    echo ${UNAME_MACHINE}-unknown-osf1\n\tfi\n\texit ;;\n    parisc*:Lites*:*:*)\n\techo hppa1.1-hp-lites\n\texit ;;\n    C1*:ConvexOS:*:* | convex:ConvexOS:C1*:*)\n\techo c1-convex-bsd\n\texit ;;\n    C2*:ConvexOS:*:* | convex:ConvexOS:C2*:*)\n\tif getsysinfo -f scalar_acc\n\tthen echo c32-convex-bsd\n\telse echo c2-convex-bsd\n\tfi\n\texit ;;\n    C34*:ConvexOS:*:* | convex:ConvexOS:C34*:*)\n\techo c34-convex-bsd\n\texit ;;\n    C38*:ConvexOS:*:* | convex:ConvexOS:C38*:*)\n\techo c38-convex-bsd\n\texit ;;\n    C4*:ConvexOS:*:* | convex:ConvexOS:C4*:*)\n\techo c4-convex-bsd\n\texit ;;\n    CRAY*Y-MP:*:*:*)\n\techo ymp-cray-unicos${UNAME_RELEASE} | sed -e 's/\\.[^.]*$/.X/'\n\texit ;;\n    CRAY*[A-Z]90:*:*:*)\n\techo ${UNAME_MACHINE}-cray-unicos${UNAME_RELEASE} \\\n\t| sed -e 's/CRAY.*\\([A-Z]90\\)/\\1/' \\\n\t      -e y/ABCDEFGHIJKLMNOPQRSTUVWXYZ/abcdefghijklmnopqrstuvwxyz/ \\\n\t      -e 's/\\.[^.]*$/.X/'\n\texit ;;\n    CRAY*TS:*:*:*)\n\techo t90-cray-unicos${UNAME_RELEASE} | sed -e 's/\\.[^.]*$/.X/'\n\texit ;;\n    CRAY*T3E:*:*:*)\n\techo alphaev5-cray-unicosmk${UNAME_RELEASE} | sed -e 's/\\.[^.]*$/.X/'\n\texit ;;\n    CRAY*SV1:*:*:*)\n\techo sv1-cray-unicos${UNAME_RELEASE} | sed -e 's/\\.[^.]*$/.X/'\n\texit ;;\n    *:UNICOS/mp:*:*)\n\techo craynv-cray-unicosmp${UNAME_RELEASE} | sed -e 's/\\.[^.]*$/.X/'\n\texit ;;\n    F30[01]:UNIX_System_V:*:* | F700:UNIX_System_V:*:*)\n\tFUJITSU_PROC=`uname -m | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz'`\n\tFUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\\///'`\n\tFUJITSU_REL=`echo ${UNAME_RELEASE} | sed -e 's/ /_/'`\n\techo \"${FUJITSU_PROC}-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}\"\n\texit ;;\n    5000:UNIX_System_V:4.*:*)\n\tFUJITSU_SYS=`uname -p | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/\\///'`\n\tFUJITSU_REL=`echo ${UNAME_RELEASE} | tr 'ABCDEFGHIJKLMNOPQRSTUVWXYZ' 'abcdefghijklmnopqrstuvwxyz' | sed -e 's/ /_/'`\n\techo \"sparc-fujitsu-${FUJITSU_SYS}${FUJITSU_REL}\"\n\texit ;;\n    i*86:BSD/386:*:* | i*86:BSD/OS:*:* | *:Ascend\\ Embedded/OS:*:*)\n\techo ${UNAME_MACHINE}-pc-bsdi${UNAME_RELEASE}\n\texit ;;\n    sparc*:BSD/OS:*:*)\n\techo sparc-unknown-bsdi${UNAME_RELEASE}\n\texit ;;\n    *:BSD/OS:*:*)\n\techo ${UNAME_MACHINE}-unknown-bsdi${UNAME_RELEASE}\n\texit ;;\n    *:FreeBSD:*:*)\n\tUNAME_PROCESSOR=`/usr/bin/uname -p`\n\tcase ${UNAME_PROCESSOR} in\n\t    amd64)\n\t\techo x86_64-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;\n\t    *)\n\t\techo ${UNAME_PROCESSOR}-unknown-freebsd`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'` ;;\n\tesac\n\texit ;;\n    i*:CYGWIN*:*)\n\techo ${UNAME_MACHINE}-pc-cygwin\n\texit ;;\n    *:MINGW64*:*)\n\techo ${UNAME_MACHINE}-pc-mingw64\n\texit ;;\n    *:MINGW*:*)\n\techo ${UNAME_MACHINE}-pc-mingw32\n\texit ;;\n    *:MSYS*:*)\n\techo ${UNAME_MACHINE}-pc-msys\n\texit ;;\n    i*:windows32*:*)\n\t# uname -m includes \"-pc\" on this system.\n\techo ${UNAME_MACHINE}-mingw32\n\texit ;;\n    i*:PW*:*)\n\techo ${UNAME_MACHINE}-pc-pw32\n\texit ;;\n    *:Interix*:*)\n\tcase ${UNAME_MACHINE} in\n\t    x86)\n\t\techo i586-pc-interix${UNAME_RELEASE}\n\t\texit ;;\n\t    authenticamd | genuineintel | EM64T)\n\t\techo x86_64-unknown-interix${UNAME_RELEASE}\n\t\texit ;;\n\t    IA64)\n\t\techo ia64-unknown-interix${UNAME_RELEASE}\n\t\texit ;;\n\tesac ;;\n    [345]86:Windows_95:* | [345]86:Windows_98:* | [345]86:Windows_NT:*)\n\techo i${UNAME_MACHINE}-pc-mks\n\texit ;;\n    8664:Windows_NT:*)\n\techo x86_64-pc-mks\n\texit ;;\n    i*:Windows_NT*:* | Pentium*:Windows_NT*:*)\n\t# How do we know it's Interix rather than the generic POSIX subsystem?\n\t# It also conflicts with pre-2.0 versions of AT&T UWIN. Should we\n\t# UNAME_MACHINE based on the output of uname instead of i386?\n\techo i586-pc-interix\n\texit ;;\n    i*:UWIN*:*)\n\techo ${UNAME_MACHINE}-pc-uwin\n\texit ;;\n    amd64:CYGWIN*:*:* | x86_64:CYGWIN*:*:*)\n\techo x86_64-unknown-cygwin\n\texit ;;\n    p*:CYGWIN*:*)\n\techo powerpcle-unknown-cygwin\n\texit ;;\n    prep*:SunOS:5.*:*)\n\techo powerpcle-unknown-solaris2`echo ${UNAME_RELEASE}|sed -e 's/[^.]*//'`\n\texit ;;\n    *:GNU:*:*)\n\t# the GNU system\n\techo `echo ${UNAME_MACHINE}|sed -e 's,[-/].*$,,'`-unknown-${LIBC}`echo ${UNAME_RELEASE}|sed -e 's,/.*$,,'`\n\texit ;;\n    *:GNU/*:*:*)\n\t# other systems with GNU libc and userland\n\techo ${UNAME_MACHINE}-unknown-`echo ${UNAME_SYSTEM} | sed 's,^[^/]*/,,' | tr '[A-Z]' '[a-z]'``echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`-${LIBC}\n\texit ;;\n    i*86:Minix:*:*)\n\techo ${UNAME_MACHINE}-pc-minix\n\texit ;;\n    aarch64:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    aarch64_be:Linux:*:*)\n\tUNAME_MACHINE=aarch64_be\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    alpha:Linux:*:*)\n\tcase `sed -n '/^cpu model/s/^.*: \\(.*\\)/\\1/p' < /proc/cpuinfo` in\n\t  EV5)   UNAME_MACHINE=alphaev5 ;;\n\t  EV56)  UNAME_MACHINE=alphaev56 ;;\n\t  PCA56) UNAME_MACHINE=alphapca56 ;;\n\t  PCA57) UNAME_MACHINE=alphapca56 ;;\n\t  EV6)   UNAME_MACHINE=alphaev6 ;;\n\t  EV67)  UNAME_MACHINE=alphaev67 ;;\n\t  EV68*) UNAME_MACHINE=alphaev68 ;;\n\tesac\n\tobjdump --private-headers /bin/sh | grep -q ld.so.1\n\tif test \"$?\" = 0 ; then LIBC=\"gnulibc1\" ; fi\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    arc:Linux:*:* | arceb:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    arm*:Linux:*:*)\n\teval $set_cc_for_build\n\tif echo __ARM_EABI__ | $CC_FOR_BUILD -E - 2>/dev/null \\\n\t    | grep -q __ARM_EABI__\n\tthen\n\t    echo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\telse\n\t    if echo __ARM_PCS_VFP | $CC_FOR_BUILD -E - 2>/dev/null \\\n\t\t| grep -q __ARM_PCS_VFP\n\t    then\n\t\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}eabi\n\t    else\n\t\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}eabihf\n\t    fi\n\tfi\n\texit ;;\n    avr32*:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    cris:Linux:*:*)\n\techo ${UNAME_MACHINE}-axis-linux-${LIBC}\n\texit ;;\n    crisv32:Linux:*:*)\n\techo ${UNAME_MACHINE}-axis-linux-${LIBC}\n\texit ;;\n    frv:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    hexagon:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    i*86:Linux:*:*)\n\techo ${UNAME_MACHINE}-pc-linux-${LIBC}\n\texit ;;\n    ia64:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    m32r*:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    m68*:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    mips:Linux:*:* | mips64:Linux:*:*)\n\teval $set_cc_for_build\n\tsed 's/^\t//' << EOF >$dummy.c\n\t#undef CPU\n\t#undef ${UNAME_MACHINE}\n\t#undef ${UNAME_MACHINE}el\n\t#if defined(__MIPSEL__) || defined(__MIPSEL) || defined(_MIPSEL) || defined(MIPSEL)\n\tCPU=${UNAME_MACHINE}el\n\t#else\n\t#if defined(__MIPSEB__) || defined(__MIPSEB) || defined(_MIPSEB) || defined(MIPSEB)\n\tCPU=${UNAME_MACHINE}\n\t#else\n\tCPU=\n\t#endif\n\t#endif\nEOF\n\teval `$CC_FOR_BUILD -E $dummy.c 2>/dev/null | grep '^CPU'`\n\ttest x\"${CPU}\" != x && { echo \"${CPU}-unknown-linux-${LIBC}\"; exit; }\n\t;;\n    openrisc*:Linux:*:*)\n\techo or1k-unknown-linux-${LIBC}\n\texit ;;\n    or32:Linux:*:* | or1k*:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    padre:Linux:*:*)\n\techo sparc-unknown-linux-${LIBC}\n\texit ;;\n    parisc64:Linux:*:* | hppa64:Linux:*:*)\n\techo hppa64-unknown-linux-${LIBC}\n\texit ;;\n    parisc:Linux:*:* | hppa:Linux:*:*)\n\t# Look for CPU level\n\tcase `grep '^cpu[^a-z]*:' /proc/cpuinfo 2>/dev/null | cut -d' ' -f2` in\n\t  PA7*) echo hppa1.1-unknown-linux-${LIBC} ;;\n\t  PA8*) echo hppa2.0-unknown-linux-${LIBC} ;;\n\t  *)    echo hppa-unknown-linux-${LIBC} ;;\n\tesac\n\texit ;;\n    ppc64:Linux:*:*)\n\techo powerpc64-unknown-linux-${LIBC}\n\texit ;;\n    ppc:Linux:*:*)\n\techo powerpc-unknown-linux-${LIBC}\n\texit ;;\n    ppc64le:Linux:*:*)\n\techo powerpc64le-unknown-linux-${LIBC}\n\texit ;;\n    ppcle:Linux:*:*)\n\techo powerpcle-unknown-linux-${LIBC}\n\texit ;;\n    s390:Linux:*:* | s390x:Linux:*:*)\n\techo ${UNAME_MACHINE}-ibm-linux-${LIBC}\n\texit ;;\n    sh64*:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    sh*:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    sparc:Linux:*:* | sparc64:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    tile*:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    vax:Linux:*:*)\n\techo ${UNAME_MACHINE}-dec-linux-${LIBC}\n\texit ;;\n    x86_64:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    xtensa*:Linux:*:*)\n\techo ${UNAME_MACHINE}-unknown-linux-${LIBC}\n\texit ;;\n    i*86:DYNIX/ptx:4*:*)\n\t# ptx 4.0 does uname -s correctly, with DYNIX/ptx in there.\n\t# earlier versions are messed up and put the nodename in both\n\t# sysname and nodename.\n\techo i386-sequent-sysv4\n\texit ;;\n    i*86:UNIX_SV:4.2MP:2.*)\n\t# Unixware is an offshoot of SVR4, but it has its own version\n\t# number series starting with 2...\n\t# I am not positive that other SVR4 systems won't match this,\n\t# I just have to hope.  -- rms.\n\t# Use sysv4.2uw... so that sysv4* matches it.\n\techo ${UNAME_MACHINE}-pc-sysv4.2uw${UNAME_VERSION}\n\texit ;;\n    i*86:OS/2:*:*)\n\t# If we were able to find `uname', then EMX Unix compatibility\n\t# is probably installed.\n\techo ${UNAME_MACHINE}-pc-os2-emx\n\texit ;;\n    i*86:XTS-300:*:STOP)\n\techo ${UNAME_MACHINE}-unknown-stop\n\texit ;;\n    i*86:atheos:*:*)\n\techo ${UNAME_MACHINE}-unknown-atheos\n\texit ;;\n    i*86:syllable:*:*)\n\techo ${UNAME_MACHINE}-pc-syllable\n\texit ;;\n    i*86:LynxOS:2.*:* | i*86:LynxOS:3.[01]*:* | i*86:LynxOS:4.[02]*:*)\n\techo i386-unknown-lynxos${UNAME_RELEASE}\n\texit ;;\n    i*86:*DOS:*:*)\n\techo ${UNAME_MACHINE}-pc-msdosdjgpp\n\texit ;;\n    i*86:*:4.*:* | i*86:SYSTEM_V:4.*:*)\n\tUNAME_REL=`echo ${UNAME_RELEASE} | sed 's/\\/MP$//'`\n\tif grep Novell /usr/include/link.h >/dev/null 2>/dev/null; then\n\t\techo ${UNAME_MACHINE}-univel-sysv${UNAME_REL}\n\telse\n\t\techo ${UNAME_MACHINE}-pc-sysv${UNAME_REL}\n\tfi\n\texit ;;\n    i*86:*:5:[678]*)\n\t# UnixWare 7.x, OpenUNIX and OpenServer 6.\n\tcase `/bin/uname -X | grep \"^Machine\"` in\n\t    *486*)\t     UNAME_MACHINE=i486 ;;\n\t    *Pentium)\t     UNAME_MACHINE=i586 ;;\n\t    *Pent*|*Celeron) UNAME_MACHINE=i686 ;;\n\tesac\n\techo ${UNAME_MACHINE}-unknown-sysv${UNAME_RELEASE}${UNAME_SYSTEM}${UNAME_VERSION}\n\texit ;;\n    i*86:*:3.2:*)\n\tif test -f /usr/options/cb.name; then\n\t\tUNAME_REL=`sed -n 's/.*Version //p' </usr/options/cb.name`\n\t\techo ${UNAME_MACHINE}-pc-isc$UNAME_REL\n\telif /bin/uname -X 2>/dev/null >/dev/null ; then\n\t\tUNAME_REL=`(/bin/uname -X|grep Release|sed -e 's/.*= //')`\n\t\t(/bin/uname -X|grep i80486 >/dev/null) && UNAME_MACHINE=i486\n\t\t(/bin/uname -X|grep '^Machine.*Pentium' >/dev/null) \\\n\t\t\t&& UNAME_MACHINE=i586\n\t\t(/bin/uname -X|grep '^Machine.*Pent *II' >/dev/null) \\\n\t\t\t&& UNAME_MACHINE=i686\n\t\t(/bin/uname -X|grep '^Machine.*Pentium Pro' >/dev/null) \\\n\t\t\t&& UNAME_MACHINE=i686\n\t\techo ${UNAME_MACHINE}-pc-sco$UNAME_REL\n\telse\n\t\techo ${UNAME_MACHINE}-pc-sysv32\n\tfi\n\texit ;;\n    pc:*:*:*)\n\t# Left here for compatibility:\n\t# uname -m prints for DJGPP always 'pc', but it prints nothing about\n\t# the processor, so we play safe by assuming i586.\n\t# Note: whatever this is, it MUST be the same as what config.sub\n\t# prints for the \"djgpp\" host, or else GDB configury will decide that\n\t# this is a cross-build.\n\techo i586-pc-msdosdjgpp\n\texit ;;\n    Intel:Mach:3*:*)\n\techo i386-pc-mach3\n\texit ;;\n    paragon:*:*:*)\n\techo i860-intel-osf1\n\texit ;;\n    i860:*:4.*:*) # i860-SVR4\n\tif grep Stardent /usr/include/sys/uadmin.h >/dev/null 2>&1 ; then\n\t  echo i860-stardent-sysv${UNAME_RELEASE} # Stardent Vistra i860-SVR4\n\telse # Add other i860-SVR4 vendors below as they are discovered.\n\t  echo i860-unknown-sysv${UNAME_RELEASE}  # Unknown i860-SVR4\n\tfi\n\texit ;;\n    mini*:CTIX:SYS*5:*)\n\t# \"miniframe\"\n\techo m68010-convergent-sysv\n\texit ;;\n    mc68k:UNIX:SYSTEM5:3.51m)\n\techo m68k-convergent-sysv\n\texit ;;\n    M680?0:D-NIX:5.3:*)\n\techo m68k-diab-dnix\n\texit ;;\n    M68*:*:R3V[5678]*:*)\n\ttest -r /sysV68 && { echo 'm68k-motorola-sysv'; exit; } ;;\n    3[345]??:*:4.0:3.0 | 3[34]??A:*:4.0:3.0 | 3[34]??,*:*:4.0:3.0 | 3[34]??/*:*:4.0:3.0 | 4400:*:4.0:3.0 | 4850:*:4.0:3.0 | SKA40:*:4.0:3.0 | SDS2:*:4.0:3.0 | SHG2:*:4.0:3.0 | S7501*:*:4.0:3.0)\n\tOS_REL=''\n\ttest -r /etc/.relid \\\n\t&& OS_REL=.`sed -n 's/[^ ]* [^ ]* \\([0-9][0-9]\\).*/\\1/p' < /etc/.relid`\n\t/bin/uname -p 2>/dev/null | grep 86 >/dev/null \\\n\t  && { echo i486-ncr-sysv4.3${OS_REL}; exit; }\n\t/bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \\\n\t  && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;\n    3[34]??:*:4.0:* | 3[34]??,*:*:4.0:*)\n\t/bin/uname -p 2>/dev/null | grep 86 >/dev/null \\\n\t  && { echo i486-ncr-sysv4; exit; } ;;\n    NCR*:*:4.2:* | MPRAS*:*:4.2:*)\n\tOS_REL='.3'\n\ttest -r /etc/.relid \\\n\t    && OS_REL=.`sed -n 's/[^ ]* [^ ]* \\([0-9][0-9]\\).*/\\1/p' < /etc/.relid`\n\t/bin/uname -p 2>/dev/null | grep 86 >/dev/null \\\n\t    && { echo i486-ncr-sysv4.3${OS_REL}; exit; }\n\t/bin/uname -p 2>/dev/null | /bin/grep entium >/dev/null \\\n\t    && { echo i586-ncr-sysv4.3${OS_REL}; exit; }\n\t/bin/uname -p 2>/dev/null | /bin/grep pteron >/dev/null \\\n\t    && { echo i586-ncr-sysv4.3${OS_REL}; exit; } ;;\n    m68*:LynxOS:2.*:* | m68*:LynxOS:3.0*:*)\n\techo m68k-unknown-lynxos${UNAME_RELEASE}\n\texit ;;\n    mc68030:UNIX_System_V:4.*:*)\n\techo m68k-atari-sysv4\n\texit ;;\n    TSUNAMI:LynxOS:2.*:*)\n\techo sparc-unknown-lynxos${UNAME_RELEASE}\n\texit ;;\n    rs6000:LynxOS:2.*:*)\n\techo rs6000-unknown-lynxos${UNAME_RELEASE}\n\texit ;;\n    PowerPC:LynxOS:2.*:* | PowerPC:LynxOS:3.[01]*:* | PowerPC:LynxOS:4.[02]*:*)\n\techo powerpc-unknown-lynxos${UNAME_RELEASE}\n\texit ;;\n    SM[BE]S:UNIX_SV:*:*)\n\techo mips-dde-sysv${UNAME_RELEASE}\n\texit ;;\n    RM*:ReliantUNIX-*:*:*)\n\techo mips-sni-sysv4\n\texit ;;\n    RM*:SINIX-*:*:*)\n\techo mips-sni-sysv4\n\texit ;;\n    *:SINIX-*:*:*)\n\tif uname -p 2>/dev/null >/dev/null ; then\n\t\tUNAME_MACHINE=`(uname -p) 2>/dev/null`\n\t\techo ${UNAME_MACHINE}-sni-sysv4\n\telse\n\t\techo ns32k-sni-sysv\n\tfi\n\texit ;;\n    PENTIUM:*:4.0*:*)\t# Unisys `ClearPath HMP IX 4000' SVR4/MP effort\n\t\t\t# says <Richard.M.Bartel@ccMail.Census.GOV>\n\techo i586-unisys-sysv4\n\texit ;;\n    *:UNIX_System_V:4*:FTX*)\n\t# From Gerald Hewes <hewes@openmarket.com>.\n\t# How about differentiating between stratus architectures? -djm\n\techo hppa1.1-stratus-sysv4\n\texit ;;\n    *:*:*:FTX*)\n\t# From seanf@swdc.stratus.com.\n\techo i860-stratus-sysv4\n\texit ;;\n    i*86:VOS:*:*)\n\t# From Paul.Green@stratus.com.\n\techo ${UNAME_MACHINE}-stratus-vos\n\texit ;;\n    *:VOS:*:*)\n\t# From Paul.Green@stratus.com.\n\techo hppa1.1-stratus-vos\n\texit ;;\n    mc68*:A/UX:*:*)\n\techo m68k-apple-aux${UNAME_RELEASE}\n\texit ;;\n    news*:NEWS-OS:6*:*)\n\techo mips-sony-newsos6\n\texit ;;\n    R[34]000:*System_V*:*:* | R4000:UNIX_SYSV:*:* | R*000:UNIX_SV:*:*)\n\tif [ -d /usr/nec ]; then\n\t\techo mips-nec-sysv${UNAME_RELEASE}\n\telse\n\t\techo mips-unknown-sysv${UNAME_RELEASE}\n\tfi\n\texit ;;\n    BeBox:BeOS:*:*)\t# BeOS running on hardware made by Be, PPC only.\n\techo powerpc-be-beos\n\texit ;;\n    BeMac:BeOS:*:*)\t# BeOS running on Mac or Mac clone, PPC only.\n\techo powerpc-apple-beos\n\texit ;;\n    BePC:BeOS:*:*)\t# BeOS running on Intel PC compatible.\n\techo i586-pc-beos\n\texit ;;\n    BePC:Haiku:*:*)\t# Haiku running on Intel PC compatible.\n\techo i586-pc-haiku\n\texit ;;\n    x86_64:Haiku:*:*)\n\techo x86_64-unknown-haiku\n\texit ;;\n    SX-4:SUPER-UX:*:*)\n\techo sx4-nec-superux${UNAME_RELEASE}\n\texit ;;\n    SX-5:SUPER-UX:*:*)\n\techo sx5-nec-superux${UNAME_RELEASE}\n\texit ;;\n    SX-6:SUPER-UX:*:*)\n\techo sx6-nec-superux${UNAME_RELEASE}\n\texit ;;\n    SX-7:SUPER-UX:*:*)\n\techo sx7-nec-superux${UNAME_RELEASE}\n\texit ;;\n    SX-8:SUPER-UX:*:*)\n\techo sx8-nec-superux${UNAME_RELEASE}\n\texit ;;\n    SX-8R:SUPER-UX:*:*)\n\techo sx8r-nec-superux${UNAME_RELEASE}\n\texit ;;\n    Power*:Rhapsody:*:*)\n\techo powerpc-apple-rhapsody${UNAME_RELEASE}\n\texit ;;\n    *:Rhapsody:*:*)\n\techo ${UNAME_MACHINE}-apple-rhapsody${UNAME_RELEASE}\n\texit ;;\n    *:Darwin:*:*)\n\tUNAME_PROCESSOR=`uname -p` || UNAME_PROCESSOR=unknown\n\teval $set_cc_for_build\n\tif test \"$UNAME_PROCESSOR\" = unknown ; then\n\t    UNAME_PROCESSOR=powerpc\n\tfi\n\tif test `echo \"$UNAME_RELEASE\" | sed -e 's/\\..*//'` -le 10 ; then\n\t    if [ \"$CC_FOR_BUILD\" != 'no_compiler_found' ]; then\n\t\tif (echo '#ifdef __LP64__'; echo IS_64BIT_ARCH; echo '#endif') | \\\n\t\t    (CCOPTS= $CC_FOR_BUILD -E - 2>/dev/null) | \\\n\t\t    grep IS_64BIT_ARCH >/dev/null\n\t\tthen\n\t\t    case $UNAME_PROCESSOR in\n\t\t\ti386) UNAME_PROCESSOR=x86_64 ;;\n\t\t\tpowerpc) UNAME_PROCESSOR=powerpc64 ;;\n\t\t    esac\n\t\tfi\n\t    fi\n\telif test \"$UNAME_PROCESSOR\" = i386 ; then\n\t    # Avoid executing cc on OS X 10.9, as it ships with a stub\n\t    # that puts up a graphical alert prompting to install\n\t    # developer tools.  Any system running Mac OS X 10.7 or\n\t    # later (Darwin 11 and later) is required to have a 64-bit\n\t    # processor. This is not true of the ARM version of Darwin\n\t    # that Apple uses in portable devices.\n\t    UNAME_PROCESSOR=x86_64\n\tfi\n\techo ${UNAME_PROCESSOR}-apple-darwin${UNAME_RELEASE}\n\texit ;;\n    *:procnto*:*:* | *:QNX:[0123456789]*:*)\n\tUNAME_PROCESSOR=`uname -p`\n\tif test \"$UNAME_PROCESSOR\" = \"x86\"; then\n\t\tUNAME_PROCESSOR=i386\n\t\tUNAME_MACHINE=pc\n\tfi\n\techo ${UNAME_PROCESSOR}-${UNAME_MACHINE}-nto-qnx${UNAME_RELEASE}\n\texit ;;\n    *:QNX:*:4*)\n\techo i386-pc-qnx\n\texit ;;\n    NEO-?:NONSTOP_KERNEL:*:*)\n\techo neo-tandem-nsk${UNAME_RELEASE}\n\texit ;;\n    NSE-*:NONSTOP_KERNEL:*:*)\n\techo nse-tandem-nsk${UNAME_RELEASE}\n\texit ;;\n    NSR-?:NONSTOP_KERNEL:*:*)\n\techo nsr-tandem-nsk${UNAME_RELEASE}\n\texit ;;\n    *:NonStop-UX:*:*)\n\techo mips-compaq-nonstopux\n\texit ;;\n    BS2000:POSIX*:*:*)\n\techo bs2000-siemens-sysv\n\texit ;;\n    DS/*:UNIX_System_V:*:*)\n\techo ${UNAME_MACHINE}-${UNAME_SYSTEM}-${UNAME_RELEASE}\n\texit ;;\n    *:Plan9:*:*)\n\t# \"uname -m\" is not consistent, so use $cputype instead. 386\n\t# is converted to i386 for consistency with other x86\n\t# operating systems.\n\tif test \"$cputype\" = \"386\"; then\n\t    UNAME_MACHINE=i386\n\telse\n\t    UNAME_MACHINE=\"$cputype\"\n\tfi\n\techo ${UNAME_MACHINE}-unknown-plan9\n\texit ;;\n    *:TOPS-10:*:*)\n\techo pdp10-unknown-tops10\n\texit ;;\n    *:TENEX:*:*)\n\techo pdp10-unknown-tenex\n\texit ;;\n    KS10:TOPS-20:*:* | KL10:TOPS-20:*:* | TYPE4:TOPS-20:*:*)\n\techo pdp10-dec-tops20\n\texit ;;\n    XKL-1:TOPS-20:*:* | TYPE5:TOPS-20:*:*)\n\techo pdp10-xkl-tops20\n\texit ;;\n    *:TOPS-20:*:*)\n\techo pdp10-unknown-tops20\n\texit ;;\n    *:ITS:*:*)\n\techo pdp10-unknown-its\n\texit ;;\n    SEI:*:*:SEIUX)\n\techo mips-sei-seiux${UNAME_RELEASE}\n\texit ;;\n    *:DragonFly:*:*)\n\techo ${UNAME_MACHINE}-unknown-dragonfly`echo ${UNAME_RELEASE}|sed -e 's/[-(].*//'`\n\texit ;;\n    *:*VMS:*:*)\n\tUNAME_MACHINE=`(uname -p) 2>/dev/null`\n\tcase \"${UNAME_MACHINE}\" in\n\t    A*) echo alpha-dec-vms ; exit ;;\n\t    I*) echo ia64-dec-vms ; exit ;;\n\t    V*) echo vax-dec-vms ; exit ;;\n\tesac ;;\n    *:XENIX:*:SysV)\n\techo i386-pc-xenix\n\texit ;;\n    i*86:skyos:*:*)\n\techo ${UNAME_MACHINE}-pc-skyos`echo ${UNAME_RELEASE}` | sed -e 's/ .*$//'\n\texit ;;\n    i*86:rdos:*:*)\n\techo ${UNAME_MACHINE}-pc-rdos\n\texit ;;\n    i*86:AROS:*:*)\n\techo ${UNAME_MACHINE}-pc-aros\n\texit ;;\n    x86_64:VMkernel:*:*)\n\techo ${UNAME_MACHINE}-unknown-esx\n\texit ;;\nesac\n\ncat >&2 <<EOF\n$0: unable to guess system type\n\nThis script, last modified $timestamp, has failed to recognize\nthe operating system you are using. It is advised that you\ndownload the most up to date version of the config scripts from\n\n  http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.guess;hb=HEAD\nand\n  http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub;hb=HEAD\n\nIf the version you run ($0) is already up to date, please\nsend the following data and any information you think might be\npertinent to <config-patches@gnu.org> in order to provide the needed\ninformation to handle your system.\n\nconfig.guess timestamp = $timestamp\n\nuname -m = `(uname -m) 2>/dev/null || echo unknown`\nuname -r = `(uname -r) 2>/dev/null || echo unknown`\nuname -s = `(uname -s) 2>/dev/null || echo unknown`\nuname -v = `(uname -v) 2>/dev/null || echo unknown`\n\n/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null`\n/bin/uname -X     = `(/bin/uname -X) 2>/dev/null`\n\nhostinfo               = `(hostinfo) 2>/dev/null`\n/bin/universe          = `(/bin/universe) 2>/dev/null`\n/usr/bin/arch -k       = `(/usr/bin/arch -k) 2>/dev/null`\n/bin/arch              = `(/bin/arch) 2>/dev/null`\n/usr/bin/oslevel       = `(/usr/bin/oslevel) 2>/dev/null`\n/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null`\n\nUNAME_MACHINE = ${UNAME_MACHINE}\nUNAME_RELEASE = ${UNAME_RELEASE}\nUNAME_SYSTEM  = ${UNAME_SYSTEM}\nUNAME_VERSION = ${UNAME_VERSION}\nEOF\n\nexit 1\n\n# Local variables:\n# eval: (add-hook 'write-file-hooks 'time-stamp)\n# time-stamp-start: \"timestamp='\"\n# time-stamp-format: \"%:y-%02m-%02d\"\n# time-stamp-end: \"'\"\n# End:\n"
  },
  {
    "path": "cudd/build-aux/config.sub",
    "content": "#! /bin/sh\n# Configuration validation subroutine script.\n#   Copyright 1992-2014 Free Software Foundation, Inc.\n\ntimestamp='2014-09-11'\n\n# This file is free software; you can redistribute it and/or modify it\n# under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 3 of the License, or\n# (at your option) any later version.\n#\n# This program is distributed in the hope that it will be useful, but\n# WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# General Public License for more details.\n#\n# You should have received a copy of the GNU General Public License\n# along with this program; if not, see <http://www.gnu.org/licenses/>.\n#\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program that contains a\n# configuration script generated by Autoconf, you may include it under\n# the same distribution terms that you use for the rest of that\n# program.  This Exception is an additional permission under section 7\n# of the GNU General Public License, version 3 (\"GPLv3\").\n\n\n# Please send patches with a ChangeLog entry to config-patches@gnu.org.\n#\n# Configuration subroutine to validate and canonicalize a configuration type.\n# Supply the specified configuration type as an argument.\n# If it is invalid, we print an error message on stderr and exit with code 1.\n# Otherwise, we print the canonical config type on stdout and succeed.\n\n# You can get the latest version of this script from:\n# http://git.savannah.gnu.org/gitweb/?p=config.git;a=blob_plain;f=config.sub;hb=HEAD\n\n# This file is supposed to be the same for all GNU packages\n# and recognize all the CPU types, system types and aliases\n# that are meaningful with *any* GNU software.\n# Each package is responsible for reporting which valid configurations\n# it does not support.  The user should be able to distinguish\n# a failure to support a valid configuration from a meaningless\n# configuration.\n\n# The goal of this file is to map all the various variations of a given\n# machine specification into a single specification in the form:\n#\tCPU_TYPE-MANUFACTURER-OPERATING_SYSTEM\n# or in some cases, the newer four-part form:\n#\tCPU_TYPE-MANUFACTURER-KERNEL-OPERATING_SYSTEM\n# It is wrong to echo any other type of specification.\n\nme=`echo \"$0\" | sed -e 's,.*/,,'`\n\nusage=\"\\\nUsage: $0 [OPTION] CPU-MFR-OPSYS\n       $0 [OPTION] ALIAS\n\nCanonicalize a configuration name.\n\nOperation modes:\n  -h, --help         print this help, then exit\n  -t, --time-stamp   print date of last modification, then exit\n  -v, --version      print version number, then exit\n\nReport bugs and patches to <config-patches@gnu.org>.\"\n\nversion=\"\\\nGNU config.sub ($timestamp)\n\nCopyright 1992-2014 Free Software Foundation, Inc.\n\nThis is free software; see the source for copying conditions.  There is NO\nwarranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\"\n\nhelp=\"\nTry \\`$me --help' for more information.\"\n\n# Parse command line\nwhile test $# -gt 0 ; do\n  case $1 in\n    --time-stamp | --time* | -t )\n       echo \"$timestamp\" ; exit ;;\n    --version | -v )\n       echo \"$version\" ; exit ;;\n    --help | --h* | -h )\n       echo \"$usage\"; exit ;;\n    -- )     # Stop option processing\n       shift; break ;;\n    - )\t# Use stdin as input.\n       break ;;\n    -* )\n       echo \"$me: invalid option $1$help\"\n       exit 1 ;;\n\n    *local*)\n       # First pass through any local machine types.\n       echo $1\n       exit ;;\n\n    * )\n       break ;;\n  esac\ndone\n\ncase $# in\n 0) echo \"$me: missing argument$help\" >&2\n    exit 1;;\n 1) ;;\n *) echo \"$me: too many arguments$help\" >&2\n    exit 1;;\nesac\n\n# Separate what the user gave into CPU-COMPANY and OS or KERNEL-OS (if any).\n# Here we must recognize all the valid KERNEL-OS combinations.\nmaybe_os=`echo $1 | sed 's/^\\(.*\\)-\\([^-]*-[^-]*\\)$/\\2/'`\ncase $maybe_os in\n  nto-qnx* | linux-gnu* | linux-android* | linux-dietlibc | linux-newlib* | \\\n  linux-musl* | linux-uclibc* | uclinux-uclibc* | uclinux-gnu* | kfreebsd*-gnu* | \\\n  knetbsd*-gnu* | netbsd*-gnu* | \\\n  kopensolaris*-gnu* | \\\n  storm-chaos* | os2-emx* | rtmk-nova*)\n    os=-$maybe_os\n    basic_machine=`echo $1 | sed 's/^\\(.*\\)-\\([^-]*-[^-]*\\)$/\\1/'`\n    ;;\n  android-linux)\n    os=-linux-android\n    basic_machine=`echo $1 | sed 's/^\\(.*\\)-\\([^-]*-[^-]*\\)$/\\1/'`-unknown\n    ;;\n  *)\n    basic_machine=`echo $1 | sed 's/-[^-]*$//'`\n    if [ $basic_machine != $1 ]\n    then os=`echo $1 | sed 's/.*-/-/'`\n    else os=; fi\n    ;;\nesac\n\n### Let's recognize common machines as not being operating systems so\n### that things like config.sub decstation-3100 work.  We also\n### recognize some manufacturers as not being operating systems, so we\n### can provide default operating systems below.\ncase $os in\n\t-sun*os*)\n\t\t# Prevent following clause from handling this invalid input.\n\t\t;;\n\t-dec* | -mips* | -sequent* | -encore* | -pc532* | -sgi* | -sony* | \\\n\t-att* | -7300* | -3300* | -delta* | -motorola* | -sun[234]* | \\\n\t-unicom* | -ibm* | -next | -hp | -isi* | -apollo | -altos* | \\\n\t-convergent* | -ncr* | -news | -32* | -3600* | -3100* | -hitachi* |\\\n\t-c[123]* | -convex* | -sun | -crds | -omron* | -dg | -ultra | -tti* | \\\n\t-harris | -dolphin | -highlevel | -gould | -cbm | -ns | -masscomp | \\\n\t-apple | -axis | -knuth | -cray | -microblaze*)\n\t\tos=\n\t\tbasic_machine=$1\n\t\t;;\n\t-bluegene*)\n\t\tos=-cnk\n\t\t;;\n\t-sim | -cisco | -oki | -wec | -winbond)\n\t\tos=\n\t\tbasic_machine=$1\n\t\t;;\n\t-scout)\n\t\t;;\n\t-wrs)\n\t\tos=-vxworks\n\t\tbasic_machine=$1\n\t\t;;\n\t-chorusos*)\n\t\tos=-chorusos\n\t\tbasic_machine=$1\n\t\t;;\n\t-chorusrdb)\n\t\tos=-chorusrdb\n\t\tbasic_machine=$1\n\t\t;;\n\t-hiux*)\n\t\tos=-hiuxwe2\n\t\t;;\n\t-sco6)\n\t\tos=-sco5v6\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-sco5)\n\t\tos=-sco3.2v5\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-sco4)\n\t\tos=-sco3.2v4\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-sco3.2.[4-9]*)\n\t\tos=`echo $os | sed -e 's/sco3.2./sco3.2v/'`\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-sco3.2v[4-9]*)\n\t\t# Don't forget version if it is 3.2v4 or newer.\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-sco5v6*)\n\t\t# Don't forget version if it is 3.2v4 or newer.\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-sco*)\n\t\tos=-sco3.2v2\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-udk*)\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-isc)\n\t\tos=-isc2.2\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-clix*)\n\t\tbasic_machine=clipper-intergraph\n\t\t;;\n\t-isc*)\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-pc/'`\n\t\t;;\n\t-lynx*178)\n\t\tos=-lynxos178\n\t\t;;\n\t-lynx*5)\n\t\tos=-lynxos5\n\t\t;;\n\t-lynx*)\n\t\tos=-lynxos\n\t\t;;\n\t-ptx*)\n\t\tbasic_machine=`echo $1 | sed -e 's/86-.*/86-sequent/'`\n\t\t;;\n\t-windowsnt*)\n\t\tos=`echo $os | sed -e 's/windowsnt/winnt/'`\n\t\t;;\n\t-psos*)\n\t\tos=-psos\n\t\t;;\n\t-mint | -mint[0-9]*)\n\t\tbasic_machine=m68k-atari\n\t\tos=-mint\n\t\t;;\nesac\n\n# Decode aliases for certain CPU-COMPANY combinations.\ncase $basic_machine in\n\t# Recognize the basic CPU types without company name.\n\t# Some are omitted here because they have special meanings below.\n\t1750a | 580 \\\n\t| a29k \\\n\t| aarch64 | aarch64_be \\\n\t| alpha | alphaev[4-8] | alphaev56 | alphaev6[78] | alphapca5[67] \\\n\t| alpha64 | alpha64ev[4-8] | alpha64ev56 | alpha64ev6[78] | alpha64pca5[67] \\\n\t| am33_2.0 \\\n\t| arc | arceb \\\n\t| arm | arm[bl]e | arme[lb] | armv[2-8] | armv[3-8][lb] | armv7[arm] \\\n\t| avr | avr32 \\\n\t| be32 | be64 \\\n\t| bfin \\\n\t| c4x | c8051 | clipper \\\n\t| d10v | d30v | dlx | dsp16xx \\\n\t| epiphany \\\n\t| fido | fr30 | frv \\\n\t| h8300 | h8500 | hppa | hppa1.[01] | hppa2.0 | hppa2.0[nw] | hppa64 \\\n\t| hexagon \\\n\t| i370 | i860 | i960 | ia64 \\\n\t| ip2k | iq2000 \\\n\t| k1om \\\n\t| le32 | le64 \\\n\t| lm32 \\\n\t| m32c | m32r | m32rle | m68000 | m68k | m88k \\\n\t| maxq | mb | microblaze | microblazeel | mcore | mep | metag \\\n\t| mips | mipsbe | mipseb | mipsel | mipsle \\\n\t| mips16 \\\n\t| mips64 | mips64el \\\n\t| mips64octeon | mips64octeonel \\\n\t| mips64orion | mips64orionel \\\n\t| mips64r5900 | mips64r5900el \\\n\t| mips64vr | mips64vrel \\\n\t| mips64vr4100 | mips64vr4100el \\\n\t| mips64vr4300 | mips64vr4300el \\\n\t| mips64vr5000 | mips64vr5000el \\\n\t| mips64vr5900 | mips64vr5900el \\\n\t| mipsisa32 | mipsisa32el \\\n\t| mipsisa32r2 | mipsisa32r2el \\\n\t| mipsisa32r6 | mipsisa32r6el \\\n\t| mipsisa64 | mipsisa64el \\\n\t| mipsisa64r2 | mipsisa64r2el \\\n\t| mipsisa64r6 | mipsisa64r6el \\\n\t| mipsisa64sb1 | mipsisa64sb1el \\\n\t| mipsisa64sr71k | mipsisa64sr71kel \\\n\t| mipsr5900 | mipsr5900el \\\n\t| mipstx39 | mipstx39el \\\n\t| mn10200 | mn10300 \\\n\t| moxie \\\n\t| mt \\\n\t| msp430 \\\n\t| nds32 | nds32le | nds32be \\\n\t| nios | nios2 | nios2eb | nios2el \\\n\t| ns16k | ns32k \\\n\t| open8 | or1k | or1knd | or32 \\\n\t| pdp10 | pdp11 | pj | pjl \\\n\t| powerpc | powerpc64 | powerpc64le | powerpcle \\\n\t| pyramid \\\n\t| riscv32 | riscv64 \\\n\t| rl78 | rx \\\n\t| score \\\n\t| sh | sh[1234] | sh[24]a | sh[24]aeb | sh[23]e | sh[34]eb | sheb | shbe | shle | sh[1234]le | sh3ele \\\n\t| sh64 | sh64le \\\n\t| sparc | sparc64 | sparc64b | sparc64v | sparc86x | sparclet | sparclite \\\n\t| sparcv8 | sparcv9 | sparcv9b | sparcv9v \\\n\t| spu \\\n\t| tahoe | tic4x | tic54x | tic55x | tic6x | tic80 | tron \\\n\t| ubicom32 \\\n\t| v850 | v850e | v850e1 | v850e2 | v850es | v850e2v3 \\\n\t| we32k \\\n\t| x86 | xc16x | xstormy16 | xtensa \\\n\t| z8k | z80)\n\t\tbasic_machine=$basic_machine-unknown\n\t\t;;\n\tc54x)\n\t\tbasic_machine=tic54x-unknown\n\t\t;;\n\tc55x)\n\t\tbasic_machine=tic55x-unknown\n\t\t;;\n\tc6x)\n\t\tbasic_machine=tic6x-unknown\n\t\t;;\n\tm6811 | m68hc11 | m6812 | m68hc12 | m68hcs12x | nvptx | picochip)\n\t\tbasic_machine=$basic_machine-unknown\n\t\tos=-none\n\t\t;;\n\tm88110 | m680[12346]0 | m683?2 | m68360 | m5200 | v70 | w65 | z8k)\n\t\t;;\n\tms1)\n\t\tbasic_machine=mt-unknown\n\t\t;;\n\n\tstrongarm | thumb | xscale)\n\t\tbasic_machine=arm-unknown\n\t\t;;\n\txgate)\n\t\tbasic_machine=$basic_machine-unknown\n\t\tos=-none\n\t\t;;\n\txscaleeb)\n\t\tbasic_machine=armeb-unknown\n\t\t;;\n\n\txscaleel)\n\t\tbasic_machine=armel-unknown\n\t\t;;\n\n\t# We use `pc' rather than `unknown'\n\t# because (1) that's what they normally are, and\n\t# (2) the word \"unknown\" tends to confuse beginning users.\n\ti*86 | x86_64)\n\t  basic_machine=$basic_machine-pc\n\t  ;;\n\t# Object if more than one company name word.\n\t*-*-*)\n\t\techo Invalid configuration \\`$1\\': machine \\`$basic_machine\\' not recognized 1>&2\n\t\texit 1\n\t\t;;\n\t# Recognize the basic CPU types with company name.\n\t580-* \\\n\t| a29k-* \\\n\t| aarch64-* | aarch64_be-* \\\n\t| alpha-* | alphaev[4-8]-* | alphaev56-* | alphaev6[78]-* \\\n\t| alpha64-* | alpha64ev[4-8]-* | alpha64ev56-* | alpha64ev6[78]-* \\\n\t| alphapca5[67]-* | alpha64pca5[67]-* | arc-* | arceb-* \\\n\t| arm-*  | armbe-* | armle-* | armeb-* | armv*-* \\\n\t| avr-* | avr32-* \\\n\t| be32-* | be64-* \\\n\t| bfin-* | bs2000-* \\\n\t| c[123]* | c30-* | [cjt]90-* | c4x-* \\\n\t| c8051-* | clipper-* | craynv-* | cydra-* \\\n\t| d10v-* | d30v-* | dlx-* \\\n\t| elxsi-* \\\n\t| f30[01]-* | f700-* | fido-* | fr30-* | frv-* | fx80-* \\\n\t| h8300-* | h8500-* \\\n\t| hppa-* | hppa1.[01]-* | hppa2.0-* | hppa2.0[nw]-* | hppa64-* \\\n\t| hexagon-* \\\n\t| i*86-* | i860-* | i960-* | ia64-* \\\n\t| ip2k-* | iq2000-* \\\n\t| k1om-* \\\n\t| le32-* | le64-* \\\n\t| lm32-* \\\n\t| m32c-* | m32r-* | m32rle-* \\\n\t| m68000-* | m680[012346]0-* | m68360-* | m683?2-* | m68k-* \\\n\t| m88110-* | m88k-* | maxq-* | mcore-* | metag-* \\\n\t| microblaze-* | microblazeel-* \\\n\t| mips-* | mipsbe-* | mipseb-* | mipsel-* | mipsle-* \\\n\t| mips16-* \\\n\t| mips64-* | mips64el-* \\\n\t| mips64octeon-* | mips64octeonel-* \\\n\t| mips64orion-* | mips64orionel-* \\\n\t| mips64r5900-* | mips64r5900el-* \\\n\t| mips64vr-* | mips64vrel-* \\\n\t| mips64vr4100-* | mips64vr4100el-* \\\n\t| mips64vr4300-* | mips64vr4300el-* \\\n\t| mips64vr5000-* | mips64vr5000el-* \\\n\t| mips64vr5900-* | mips64vr5900el-* \\\n\t| mipsisa32-* | mipsisa32el-* \\\n\t| mipsisa32r2-* | mipsisa32r2el-* \\\n\t| mipsisa32r6-* | mipsisa32r6el-* \\\n\t| mipsisa64-* | mipsisa64el-* \\\n\t| mipsisa64r2-* | mipsisa64r2el-* \\\n\t| mipsisa64r6-* | mipsisa64r6el-* \\\n\t| mipsisa64sb1-* | mipsisa64sb1el-* \\\n\t| mipsisa64sr71k-* | mipsisa64sr71kel-* \\\n\t| mipsr5900-* | mipsr5900el-* \\\n\t| mipstx39-* | mipstx39el-* \\\n\t| mmix-* \\\n\t| mt-* \\\n\t| msp430-* \\\n\t| nds32-* | nds32le-* | nds32be-* \\\n\t| nios-* | nios2-* | nios2eb-* | nios2el-* \\\n\t| none-* | np1-* | ns16k-* | ns32k-* \\\n\t| open8-* \\\n\t| or1k*-* \\\n\t| orion-* \\\n\t| pdp10-* | pdp11-* | pj-* | pjl-* | pn-* | power-* \\\n\t| powerpc-* | powerpc64-* | powerpc64le-* | powerpcle-* \\\n\t| pyramid-* \\\n\t| rl78-* | romp-* | rs6000-* | rx-* \\\n\t| sh-* | sh[1234]-* | sh[24]a-* | sh[24]aeb-* | sh[23]e-* | sh[34]eb-* | sheb-* | shbe-* \\\n\t| shle-* | sh[1234]le-* | sh3ele-* | sh64-* | sh64le-* \\\n\t| sparc-* | sparc64-* | sparc64b-* | sparc64v-* | sparc86x-* | sparclet-* \\\n\t| sparclite-* \\\n\t| sparcv8-* | sparcv9-* | sparcv9b-* | sparcv9v-* | sv1-* | sx?-* \\\n\t| tahoe-* \\\n\t| tic30-* | tic4x-* | tic54x-* | tic55x-* | tic6x-* | tic80-* \\\n\t| tile*-* \\\n\t| tron-* \\\n\t| ubicom32-* \\\n\t| v850-* | v850e-* | v850e1-* | v850es-* | v850e2-* | v850e2v3-* \\\n\t| vax-* \\\n\t| we32k-* \\\n\t| x86-* | x86_64-* | xc16x-* | xps100-* \\\n\t| xstormy16-* | xtensa*-* \\\n\t| ymp-* \\\n\t| z8k-* | z80-*)\n\t\t;;\n\t# Recognize the basic CPU types without company name, with glob match.\n\txtensa*)\n\t\tbasic_machine=$basic_machine-unknown\n\t\t;;\n\t# Recognize the various machine names and aliases which stand\n\t# for a CPU type and a company and sometimes even an OS.\n\t386bsd)\n\t\tbasic_machine=i386-unknown\n\t\tos=-bsd\n\t\t;;\n\t3b1 | 7300 | 7300-att | att-7300 | pc7300 | safari | unixpc)\n\t\tbasic_machine=m68000-att\n\t\t;;\n\t3b*)\n\t\tbasic_machine=we32k-att\n\t\t;;\n\ta29khif)\n\t\tbasic_machine=a29k-amd\n\t\tos=-udi\n\t\t;;\n\tabacus)\n\t\tbasic_machine=abacus-unknown\n\t\t;;\n\tadobe68k)\n\t\tbasic_machine=m68010-adobe\n\t\tos=-scout\n\t\t;;\n\talliant | fx80)\n\t\tbasic_machine=fx80-alliant\n\t\t;;\n\taltos | altos3068)\n\t\tbasic_machine=m68k-altos\n\t\t;;\n\tam29k)\n\t\tbasic_machine=a29k-none\n\t\tos=-bsd\n\t\t;;\n\tamd64)\n\t\tbasic_machine=x86_64-pc\n\t\t;;\n\tamd64-*)\n\t\tbasic_machine=x86_64-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tamdahl)\n\t\tbasic_machine=580-amdahl\n\t\tos=-sysv\n\t\t;;\n\tamiga | amiga-*)\n\t\tbasic_machine=m68k-unknown\n\t\t;;\n\tamigaos | amigados)\n\t\tbasic_machine=m68k-unknown\n\t\tos=-amigaos\n\t\t;;\n\tamigaunix | amix)\n\t\tbasic_machine=m68k-unknown\n\t\tos=-sysv4\n\t\t;;\n\tapollo68)\n\t\tbasic_machine=m68k-apollo\n\t\tos=-sysv\n\t\t;;\n\tapollo68bsd)\n\t\tbasic_machine=m68k-apollo\n\t\tos=-bsd\n\t\t;;\n\taros)\n\t\tbasic_machine=i386-pc\n\t\tos=-aros\n\t\t;;\n\taux)\n\t\tbasic_machine=m68k-apple\n\t\tos=-aux\n\t\t;;\n\tbalance)\n\t\tbasic_machine=ns32k-sequent\n\t\tos=-dynix\n\t\t;;\n\tblackfin)\n\t\tbasic_machine=bfin-unknown\n\t\tos=-linux\n\t\t;;\n\tblackfin-*)\n\t\tbasic_machine=bfin-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\tos=-linux\n\t\t;;\n\tbluegene*)\n\t\tbasic_machine=powerpc-ibm\n\t\tos=-cnk\n\t\t;;\n\tc54x-*)\n\t\tbasic_machine=tic54x-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tc55x-*)\n\t\tbasic_machine=tic55x-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tc6x-*)\n\t\tbasic_machine=tic6x-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tc90)\n\t\tbasic_machine=c90-cray\n\t\tos=-unicos\n\t\t;;\n\tcegcc)\n\t\tbasic_machine=arm-unknown\n\t\tos=-cegcc\n\t\t;;\n\tconvex-c1)\n\t\tbasic_machine=c1-convex\n\t\tos=-bsd\n\t\t;;\n\tconvex-c2)\n\t\tbasic_machine=c2-convex\n\t\tos=-bsd\n\t\t;;\n\tconvex-c32)\n\t\tbasic_machine=c32-convex\n\t\tos=-bsd\n\t\t;;\n\tconvex-c34)\n\t\tbasic_machine=c34-convex\n\t\tos=-bsd\n\t\t;;\n\tconvex-c38)\n\t\tbasic_machine=c38-convex\n\t\tos=-bsd\n\t\t;;\n\tcray | j90)\n\t\tbasic_machine=j90-cray\n\t\tos=-unicos\n\t\t;;\n\tcraynv)\n\t\tbasic_machine=craynv-cray\n\t\tos=-unicosmp\n\t\t;;\n\tcr16 | cr16-*)\n\t\tbasic_machine=cr16-unknown\n\t\tos=-elf\n\t\t;;\n\tcrds | unos)\n\t\tbasic_machine=m68k-crds\n\t\t;;\n\tcrisv32 | crisv32-* | etraxfs*)\n\t\tbasic_machine=crisv32-axis\n\t\t;;\n\tcris | cris-* | etrax*)\n\t\tbasic_machine=cris-axis\n\t\t;;\n\tcrx)\n\t\tbasic_machine=crx-unknown\n\t\tos=-elf\n\t\t;;\n\tda30 | da30-*)\n\t\tbasic_machine=m68k-da30\n\t\t;;\n\tdecstation | decstation-3100 | pmax | pmax-* | pmin | dec3100 | decstatn)\n\t\tbasic_machine=mips-dec\n\t\t;;\n\tdecsystem10* | dec10*)\n\t\tbasic_machine=pdp10-dec\n\t\tos=-tops10\n\t\t;;\n\tdecsystem20* | dec20*)\n\t\tbasic_machine=pdp10-dec\n\t\tos=-tops20\n\t\t;;\n\tdelta | 3300 | motorola-3300 | motorola-delta \\\n\t      | 3300-motorola | delta-motorola)\n\t\tbasic_machine=m68k-motorola\n\t\t;;\n\tdelta88)\n\t\tbasic_machine=m88k-motorola\n\t\tos=-sysv3\n\t\t;;\n\tdicos)\n\t\tbasic_machine=i686-pc\n\t\tos=-dicos\n\t\t;;\n\tdjgpp)\n\t\tbasic_machine=i586-pc\n\t\tos=-msdosdjgpp\n\t\t;;\n\tdpx20 | dpx20-*)\n\t\tbasic_machine=rs6000-bull\n\t\tos=-bosx\n\t\t;;\n\tdpx2* | dpx2*-bull)\n\t\tbasic_machine=m68k-bull\n\t\tos=-sysv3\n\t\t;;\n\tebmon29k)\n\t\tbasic_machine=a29k-amd\n\t\tos=-ebmon\n\t\t;;\n\telxsi)\n\t\tbasic_machine=elxsi-elxsi\n\t\tos=-bsd\n\t\t;;\n\tencore | umax | mmax)\n\t\tbasic_machine=ns32k-encore\n\t\t;;\n\tes1800 | OSE68k | ose68k | ose | OSE)\n\t\tbasic_machine=m68k-ericsson\n\t\tos=-ose\n\t\t;;\n\tfx2800)\n\t\tbasic_machine=i860-alliant\n\t\t;;\n\tgenix)\n\t\tbasic_machine=ns32k-ns\n\t\t;;\n\tgmicro)\n\t\tbasic_machine=tron-gmicro\n\t\tos=-sysv\n\t\t;;\n\tgo32)\n\t\tbasic_machine=i386-pc\n\t\tos=-go32\n\t\t;;\n\th3050r* | hiux*)\n\t\tbasic_machine=hppa1.1-hitachi\n\t\tos=-hiuxwe2\n\t\t;;\n\th8300hms)\n\t\tbasic_machine=h8300-hitachi\n\t\tos=-hms\n\t\t;;\n\th8300xray)\n\t\tbasic_machine=h8300-hitachi\n\t\tos=-xray\n\t\t;;\n\th8500hms)\n\t\tbasic_machine=h8500-hitachi\n\t\tos=-hms\n\t\t;;\n\tharris)\n\t\tbasic_machine=m88k-harris\n\t\tos=-sysv3\n\t\t;;\n\thp300-*)\n\t\tbasic_machine=m68k-hp\n\t\t;;\n\thp300bsd)\n\t\tbasic_machine=m68k-hp\n\t\tos=-bsd\n\t\t;;\n\thp300hpux)\n\t\tbasic_machine=m68k-hp\n\t\tos=-hpux\n\t\t;;\n\thp3k9[0-9][0-9] | hp9[0-9][0-9])\n\t\tbasic_machine=hppa1.0-hp\n\t\t;;\n\thp9k2[0-9][0-9] | hp9k31[0-9])\n\t\tbasic_machine=m68000-hp\n\t\t;;\n\thp9k3[2-9][0-9])\n\t\tbasic_machine=m68k-hp\n\t\t;;\n\thp9k6[0-9][0-9] | hp6[0-9][0-9])\n\t\tbasic_machine=hppa1.0-hp\n\t\t;;\n\thp9k7[0-79][0-9] | hp7[0-79][0-9])\n\t\tbasic_machine=hppa1.1-hp\n\t\t;;\n\thp9k78[0-9] | hp78[0-9])\n\t\t# FIXME: really hppa2.0-hp\n\t\tbasic_machine=hppa1.1-hp\n\t\t;;\n\thp9k8[67]1 | hp8[67]1 | hp9k80[24] | hp80[24] | hp9k8[78]9 | hp8[78]9 | hp9k893 | hp893)\n\t\t# FIXME: really hppa2.0-hp\n\t\tbasic_machine=hppa1.1-hp\n\t\t;;\n\thp9k8[0-9][13679] | hp8[0-9][13679])\n\t\tbasic_machine=hppa1.1-hp\n\t\t;;\n\thp9k8[0-9][0-9] | hp8[0-9][0-9])\n\t\tbasic_machine=hppa1.0-hp\n\t\t;;\n\thppa-next)\n\t\tos=-nextstep3\n\t\t;;\n\thppaosf)\n\t\tbasic_machine=hppa1.1-hp\n\t\tos=-osf\n\t\t;;\n\thppro)\n\t\tbasic_machine=hppa1.1-hp\n\t\tos=-proelf\n\t\t;;\n\ti370-ibm* | ibm*)\n\t\tbasic_machine=i370-ibm\n\t\t;;\n\ti*86v32)\n\t\tbasic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`\n\t\tos=-sysv32\n\t\t;;\n\ti*86v4*)\n\t\tbasic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`\n\t\tos=-sysv4\n\t\t;;\n\ti*86v)\n\t\tbasic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`\n\t\tos=-sysv\n\t\t;;\n\ti*86sol2)\n\t\tbasic_machine=`echo $1 | sed -e 's/86.*/86-pc/'`\n\t\tos=-solaris2\n\t\t;;\n\ti386mach)\n\t\tbasic_machine=i386-mach\n\t\tos=-mach\n\t\t;;\n\ti386-vsta | vsta)\n\t\tbasic_machine=i386-unknown\n\t\tos=-vsta\n\t\t;;\n\tiris | iris4d)\n\t\tbasic_machine=mips-sgi\n\t\tcase $os in\n\t\t    -irix*)\n\t\t\t;;\n\t\t    *)\n\t\t\tos=-irix4\n\t\t\t;;\n\t\tesac\n\t\t;;\n\tisi68 | isi)\n\t\tbasic_machine=m68k-isi\n\t\tos=-sysv\n\t\t;;\n\tm68knommu)\n\t\tbasic_machine=m68k-unknown\n\t\tos=-linux\n\t\t;;\n\tm68knommu-*)\n\t\tbasic_machine=m68k-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\tos=-linux\n\t\t;;\n\tm88k-omron*)\n\t\tbasic_machine=m88k-omron\n\t\t;;\n\tmagnum | m3230)\n\t\tbasic_machine=mips-mips\n\t\tos=-sysv\n\t\t;;\n\tmerlin)\n\t\tbasic_machine=ns32k-utek\n\t\tos=-sysv\n\t\t;;\n\tmicroblaze*)\n\t\tbasic_machine=microblaze-xilinx\n\t\t;;\n\tmingw64)\n\t\tbasic_machine=x86_64-pc\n\t\tos=-mingw64\n\t\t;;\n\tmingw32)\n\t\tbasic_machine=i686-pc\n\t\tos=-mingw32\n\t\t;;\n\tmingw32ce)\n\t\tbasic_machine=arm-unknown\n\t\tos=-mingw32ce\n\t\t;;\n\tminiframe)\n\t\tbasic_machine=m68000-convergent\n\t\t;;\n\t*mint | -mint[0-9]* | *MiNT | *MiNT[0-9]*)\n\t\tbasic_machine=m68k-atari\n\t\tos=-mint\n\t\t;;\n\tmips3*-*)\n\t\tbasic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`\n\t\t;;\n\tmips3*)\n\t\tbasic_machine=`echo $basic_machine | sed -e 's/mips3/mips64/'`-unknown\n\t\t;;\n\tmonitor)\n\t\tbasic_machine=m68k-rom68k\n\t\tos=-coff\n\t\t;;\n\tmorphos)\n\t\tbasic_machine=powerpc-unknown\n\t\tos=-morphos\n\t\t;;\n\tmoxiebox)\n\t\tbasic_machine=moxie-unknown\n\t\tos=-moxiebox\n\t\t;;\n\tmsdos)\n\t\tbasic_machine=i386-pc\n\t\tos=-msdos\n\t\t;;\n\tms1-*)\n\t\tbasic_machine=`echo $basic_machine | sed -e 's/ms1-/mt-/'`\n\t\t;;\n\tmsys)\n\t\tbasic_machine=i686-pc\n\t\tos=-msys\n\t\t;;\n\tmvs)\n\t\tbasic_machine=i370-ibm\n\t\tos=-mvs\n\t\t;;\n\tnacl)\n\t\tbasic_machine=le32-unknown\n\t\tos=-nacl\n\t\t;;\n\tncr3000)\n\t\tbasic_machine=i486-ncr\n\t\tos=-sysv4\n\t\t;;\n\tnetbsd386)\n\t\tbasic_machine=i386-unknown\n\t\tos=-netbsd\n\t\t;;\n\tnetwinder)\n\t\tbasic_machine=armv4l-rebel\n\t\tos=-linux\n\t\t;;\n\tnews | news700 | news800 | news900)\n\t\tbasic_machine=m68k-sony\n\t\tos=-newsos\n\t\t;;\n\tnews1000)\n\t\tbasic_machine=m68030-sony\n\t\tos=-newsos\n\t\t;;\n\tnews-3600 | risc-news)\n\t\tbasic_machine=mips-sony\n\t\tos=-newsos\n\t\t;;\n\tnecv70)\n\t\tbasic_machine=v70-nec\n\t\tos=-sysv\n\t\t;;\n\tnext | m*-next )\n\t\tbasic_machine=m68k-next\n\t\tcase $os in\n\t\t    -nextstep* )\n\t\t\t;;\n\t\t    -ns2*)\n\t\t      os=-nextstep2\n\t\t\t;;\n\t\t    *)\n\t\t      os=-nextstep3\n\t\t\t;;\n\t\tesac\n\t\t;;\n\tnh3000)\n\t\tbasic_machine=m68k-harris\n\t\tos=-cxux\n\t\t;;\n\tnh[45]000)\n\t\tbasic_machine=m88k-harris\n\t\tos=-cxux\n\t\t;;\n\tnindy960)\n\t\tbasic_machine=i960-intel\n\t\tos=-nindy\n\t\t;;\n\tmon960)\n\t\tbasic_machine=i960-intel\n\t\tos=-mon960\n\t\t;;\n\tnonstopux)\n\t\tbasic_machine=mips-compaq\n\t\tos=-nonstopux\n\t\t;;\n\tnp1)\n\t\tbasic_machine=np1-gould\n\t\t;;\n\tneo-tandem)\n\t\tbasic_machine=neo-tandem\n\t\t;;\n\tnse-tandem)\n\t\tbasic_machine=nse-tandem\n\t\t;;\n\tnsr-tandem)\n\t\tbasic_machine=nsr-tandem\n\t\t;;\n\top50n-* | op60c-*)\n\t\tbasic_machine=hppa1.1-oki\n\t\tos=-proelf\n\t\t;;\n\topenrisc | openrisc-*)\n\t\tbasic_machine=or32-unknown\n\t\t;;\n\tos400)\n\t\tbasic_machine=powerpc-ibm\n\t\tos=-os400\n\t\t;;\n\tOSE68000 | ose68000)\n\t\tbasic_machine=m68000-ericsson\n\t\tos=-ose\n\t\t;;\n\tos68k)\n\t\tbasic_machine=m68k-none\n\t\tos=-os68k\n\t\t;;\n\tpa-hitachi)\n\t\tbasic_machine=hppa1.1-hitachi\n\t\tos=-hiuxwe2\n\t\t;;\n\tparagon)\n\t\tbasic_machine=i860-intel\n\t\tos=-osf\n\t\t;;\n\tparisc)\n\t\tbasic_machine=hppa-unknown\n\t\tos=-linux\n\t\t;;\n\tparisc-*)\n\t\tbasic_machine=hppa-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\tos=-linux\n\t\t;;\n\tpbd)\n\t\tbasic_machine=sparc-tti\n\t\t;;\n\tpbb)\n\t\tbasic_machine=m68k-tti\n\t\t;;\n\tpc532 | pc532-*)\n\t\tbasic_machine=ns32k-pc532\n\t\t;;\n\tpc98)\n\t\tbasic_machine=i386-pc\n\t\t;;\n\tpc98-*)\n\t\tbasic_machine=i386-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tpentium | p5 | k5 | k6 | nexgen | viac3)\n\t\tbasic_machine=i586-pc\n\t\t;;\n\tpentiumpro | p6 | 6x86 | athlon | athlon_*)\n\t\tbasic_machine=i686-pc\n\t\t;;\n\tpentiumii | pentium2 | pentiumiii | pentium3)\n\t\tbasic_machine=i686-pc\n\t\t;;\n\tpentium4)\n\t\tbasic_machine=i786-pc\n\t\t;;\n\tpentium-* | p5-* | k5-* | k6-* | nexgen-* | viac3-*)\n\t\tbasic_machine=i586-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tpentiumpro-* | p6-* | 6x86-* | athlon-*)\n\t\tbasic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tpentiumii-* | pentium2-* | pentiumiii-* | pentium3-*)\n\t\tbasic_machine=i686-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tpentium4-*)\n\t\tbasic_machine=i786-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tpn)\n\t\tbasic_machine=pn-gould\n\t\t;;\n\tpower)\tbasic_machine=power-ibm\n\t\t;;\n\tppc | ppcbe)\tbasic_machine=powerpc-unknown\n\t\t;;\n\tppc-* | ppcbe-*)\n\t\tbasic_machine=powerpc-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tppcle | powerpclittle | ppc-le | powerpc-little)\n\t\tbasic_machine=powerpcle-unknown\n\t\t;;\n\tppcle-* | powerpclittle-*)\n\t\tbasic_machine=powerpcle-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tppc64)\tbasic_machine=powerpc64-unknown\n\t\t;;\n\tppc64-*) basic_machine=powerpc64-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tppc64le | powerpc64little | ppc64-le | powerpc64-little)\n\t\tbasic_machine=powerpc64le-unknown\n\t\t;;\n\tppc64le-* | powerpc64little-*)\n\t\tbasic_machine=powerpc64le-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tps2)\n\t\tbasic_machine=i386-ibm\n\t\t;;\n\tpw32)\n\t\tbasic_machine=i586-unknown\n\t\tos=-pw32\n\t\t;;\n\trdos | rdos64)\n\t\tbasic_machine=x86_64-pc\n\t\tos=-rdos\n\t\t;;\n\trdos32)\n\t\tbasic_machine=i386-pc\n\t\tos=-rdos\n\t\t;;\n\trom68k)\n\t\tbasic_machine=m68k-rom68k\n\t\tos=-coff\n\t\t;;\n\trm[46]00)\n\t\tbasic_machine=mips-siemens\n\t\t;;\n\trtpc | rtpc-*)\n\t\tbasic_machine=romp-ibm\n\t\t;;\n\ts390 | s390-*)\n\t\tbasic_machine=s390-ibm\n\t\t;;\n\ts390x | s390x-*)\n\t\tbasic_machine=s390x-ibm\n\t\t;;\n\tsa29200)\n\t\tbasic_machine=a29k-amd\n\t\tos=-udi\n\t\t;;\n\tsb1)\n\t\tbasic_machine=mipsisa64sb1-unknown\n\t\t;;\n\tsb1el)\n\t\tbasic_machine=mipsisa64sb1el-unknown\n\t\t;;\n\tsde)\n\t\tbasic_machine=mipsisa32-sde\n\t\tos=-elf\n\t\t;;\n\tsei)\n\t\tbasic_machine=mips-sei\n\t\tos=-seiux\n\t\t;;\n\tsequent)\n\t\tbasic_machine=i386-sequent\n\t\t;;\n\tsh)\n\t\tbasic_machine=sh-hitachi\n\t\tos=-hms\n\t\t;;\n\tsh5el)\n\t\tbasic_machine=sh5le-unknown\n\t\t;;\n\tsh64)\n\t\tbasic_machine=sh64-unknown\n\t\t;;\n\tsparclite-wrs | simso-wrs)\n\t\tbasic_machine=sparclite-wrs\n\t\tos=-vxworks\n\t\t;;\n\tsps7)\n\t\tbasic_machine=m68k-bull\n\t\tos=-sysv2\n\t\t;;\n\tspur)\n\t\tbasic_machine=spur-unknown\n\t\t;;\n\tst2000)\n\t\tbasic_machine=m68k-tandem\n\t\t;;\n\tstratus)\n\t\tbasic_machine=i860-stratus\n\t\tos=-sysv4\n\t\t;;\n\tstrongarm-* | thumb-*)\n\t\tbasic_machine=arm-`echo $basic_machine | sed 's/^[^-]*-//'`\n\t\t;;\n\tsun2)\n\t\tbasic_machine=m68000-sun\n\t\t;;\n\tsun2os3)\n\t\tbasic_machine=m68000-sun\n\t\tos=-sunos3\n\t\t;;\n\tsun2os4)\n\t\tbasic_machine=m68000-sun\n\t\tos=-sunos4\n\t\t;;\n\tsun3os3)\n\t\tbasic_machine=m68k-sun\n\t\tos=-sunos3\n\t\t;;\n\tsun3os4)\n\t\tbasic_machine=m68k-sun\n\t\tos=-sunos4\n\t\t;;\n\tsun4os3)\n\t\tbasic_machine=sparc-sun\n\t\tos=-sunos3\n\t\t;;\n\tsun4os4)\n\t\tbasic_machine=sparc-sun\n\t\tos=-sunos4\n\t\t;;\n\tsun4sol2)\n\t\tbasic_machine=sparc-sun\n\t\tos=-solaris2\n\t\t;;\n\tsun3 | sun3-*)\n\t\tbasic_machine=m68k-sun\n\t\t;;\n\tsun4)\n\t\tbasic_machine=sparc-sun\n\t\t;;\n\tsun386 | sun386i | roadrunner)\n\t\tbasic_machine=i386-sun\n\t\t;;\n\tsv1)\n\t\tbasic_machine=sv1-cray\n\t\tos=-unicos\n\t\t;;\n\tsymmetry)\n\t\tbasic_machine=i386-sequent\n\t\tos=-dynix\n\t\t;;\n\tt3e)\n\t\tbasic_machine=alphaev5-cray\n\t\tos=-unicos\n\t\t;;\n\tt90)\n\t\tbasic_machine=t90-cray\n\t\tos=-unicos\n\t\t;;\n\ttile*)\n\t\tbasic_machine=$basic_machine-unknown\n\t\tos=-linux-gnu\n\t\t;;\n\ttx39)\n\t\tbasic_machine=mipstx39-unknown\n\t\t;;\n\ttx39el)\n\t\tbasic_machine=mipstx39el-unknown\n\t\t;;\n\ttoad1)\n\t\tbasic_machine=pdp10-xkl\n\t\tos=-tops20\n\t\t;;\n\ttower | tower-32)\n\t\tbasic_machine=m68k-ncr\n\t\t;;\n\ttpf)\n\t\tbasic_machine=s390x-ibm\n\t\tos=-tpf\n\t\t;;\n\tudi29k)\n\t\tbasic_machine=a29k-amd\n\t\tos=-udi\n\t\t;;\n\tultra3)\n\t\tbasic_machine=a29k-nyu\n\t\tos=-sym1\n\t\t;;\n\tv810 | necv810)\n\t\tbasic_machine=v810-nec\n\t\tos=-none\n\t\t;;\n\tvaxv)\n\t\tbasic_machine=vax-dec\n\t\tos=-sysv\n\t\t;;\n\tvms)\n\t\tbasic_machine=vax-dec\n\t\tos=-vms\n\t\t;;\n\tvpp*|vx|vx-*)\n\t\tbasic_machine=f301-fujitsu\n\t\t;;\n\tvxworks960)\n\t\tbasic_machine=i960-wrs\n\t\tos=-vxworks\n\t\t;;\n\tvxworks68)\n\t\tbasic_machine=m68k-wrs\n\t\tos=-vxworks\n\t\t;;\n\tvxworks29k)\n\t\tbasic_machine=a29k-wrs\n\t\tos=-vxworks\n\t\t;;\n\tw65*)\n\t\tbasic_machine=w65-wdc\n\t\tos=-none\n\t\t;;\n\tw89k-*)\n\t\tbasic_machine=hppa1.1-winbond\n\t\tos=-proelf\n\t\t;;\n\txbox)\n\t\tbasic_machine=i686-pc\n\t\tos=-mingw32\n\t\t;;\n\txps | xps100)\n\t\tbasic_machine=xps100-honeywell\n\t\t;;\n\txscale-* | xscalee[bl]-*)\n\t\tbasic_machine=`echo $basic_machine | sed 's/^xscale/arm/'`\n\t\t;;\n\tymp)\n\t\tbasic_machine=ymp-cray\n\t\tos=-unicos\n\t\t;;\n\tz8k-*-coff)\n\t\tbasic_machine=z8k-unknown\n\t\tos=-sim\n\t\t;;\n\tz80-*-coff)\n\t\tbasic_machine=z80-unknown\n\t\tos=-sim\n\t\t;;\n\tnone)\n\t\tbasic_machine=none-none\n\t\tos=-none\n\t\t;;\n\n# Here we handle the default manufacturer of certain CPU types.  It is in\n# some cases the only manufacturer, in others, it is the most popular.\n\tw89k)\n\t\tbasic_machine=hppa1.1-winbond\n\t\t;;\n\top50n)\n\t\tbasic_machine=hppa1.1-oki\n\t\t;;\n\top60c)\n\t\tbasic_machine=hppa1.1-oki\n\t\t;;\n\tromp)\n\t\tbasic_machine=romp-ibm\n\t\t;;\n\tmmix)\n\t\tbasic_machine=mmix-knuth\n\t\t;;\n\trs6000)\n\t\tbasic_machine=rs6000-ibm\n\t\t;;\n\tvax)\n\t\tbasic_machine=vax-dec\n\t\t;;\n\tpdp10)\n\t\t# there are many clones, so DEC is not a safe bet\n\t\tbasic_machine=pdp10-unknown\n\t\t;;\n\tpdp11)\n\t\tbasic_machine=pdp11-dec\n\t\t;;\n\twe32k)\n\t\tbasic_machine=we32k-att\n\t\t;;\n\tsh[1234] | sh[24]a | sh[24]aeb | sh[34]eb | sh[1234]le | sh[23]ele)\n\t\tbasic_machine=sh-unknown\n\t\t;;\n\tsparc | sparcv8 | sparcv9 | sparcv9b | sparcv9v)\n\t\tbasic_machine=sparc-sun\n\t\t;;\n\tcydra)\n\t\tbasic_machine=cydra-cydrome\n\t\t;;\n\torion)\n\t\tbasic_machine=orion-highlevel\n\t\t;;\n\torion105)\n\t\tbasic_machine=clipper-highlevel\n\t\t;;\n\tmac | mpw | mac-mpw)\n\t\tbasic_machine=m68k-apple\n\t\t;;\n\tpmac | pmac-mpw)\n\t\tbasic_machine=powerpc-apple\n\t\t;;\n\t*-unknown)\n\t\t# Make sure to match an already-canonicalized machine name.\n\t\t;;\n\t*)\n\t\techo Invalid configuration \\`$1\\': machine \\`$basic_machine\\' not recognized 1>&2\n\t\texit 1\n\t\t;;\nesac\n\n# Here we canonicalize certain aliases for manufacturers.\ncase $basic_machine in\n\t*-digital*)\n\t\tbasic_machine=`echo $basic_machine | sed 's/digital.*/dec/'`\n\t\t;;\n\t*-commodore*)\n\t\tbasic_machine=`echo $basic_machine | sed 's/commodore.*/cbm/'`\n\t\t;;\n\t*)\n\t\t;;\nesac\n\n# Decode manufacturer-specific aliases for certain operating systems.\n\nif [ x\"$os\" != x\"\" ]\nthen\ncase $os in\n\t# First match some system type aliases\n\t# that might get confused with valid system types.\n\t# -solaris* is a basic system type, with this one exception.\n\t-auroraux)\n\t\tos=-auroraux\n\t\t;;\n\t-solaris1 | -solaris1.*)\n\t\tos=`echo $os | sed -e 's|solaris1|sunos4|'`\n\t\t;;\n\t-solaris)\n\t\tos=-solaris2\n\t\t;;\n\t-svr4*)\n\t\tos=-sysv4\n\t\t;;\n\t-unixware*)\n\t\tos=-sysv4.2uw\n\t\t;;\n\t-gnu/linux*)\n\t\tos=`echo $os | sed -e 's|gnu/linux|linux-gnu|'`\n\t\t;;\n\t# First accept the basic system types.\n\t# The portable systems comes first.\n\t# Each alternative MUST END IN A *, to match a version number.\n\t# -sysv* is not here because it comes later, after sysvr4.\n\t-gnu* | -bsd* | -mach* | -minix* | -genix* | -ultrix* | -irix* \\\n\t      | -*vms* | -sco* | -esix* | -isc* | -aix* | -cnk* | -sunos | -sunos[34]*\\\n\t      | -hpux* | -unos* | -osf* | -luna* | -dgux* | -auroraux* | -solaris* \\\n\t      | -sym* | -kopensolaris* | -plan9* \\\n\t      | -amigaos* | -amigados* | -msdos* | -newsos* | -unicos* | -aof* \\\n\t      | -aos* | -aros* \\\n\t      | -nindy* | -vxsim* | -vxworks* | -ebmon* | -hms* | -mvs* \\\n\t      | -clix* | -riscos* | -uniplus* | -iris* | -rtu* | -xenix* \\\n\t      | -hiux* | -386bsd* | -knetbsd* | -mirbsd* | -netbsd* \\\n\t      | -bitrig* | -openbsd* | -solidbsd* \\\n\t      | -ekkobsd* | -kfreebsd* | -freebsd* | -riscix* | -lynxos* \\\n\t      | -bosx* | -nextstep* | -cxux* | -aout* | -elf* | -oabi* \\\n\t      | -ptx* | -coff* | -ecoff* | -winnt* | -domain* | -vsta* \\\n\t      | -udi* | -eabi* | -lites* | -ieee* | -go32* | -aux* \\\n\t      | -chorusos* | -chorusrdb* | -cegcc* \\\n\t      | -cygwin* | -msys* | -pe* | -psos* | -moss* | -proelf* | -rtems* \\\n\t      | -mingw32* | -mingw64* | -linux-gnu* | -linux-android* \\\n\t      | -linux-newlib* | -linux-musl* | -linux-uclibc* \\\n\t      | -uxpv* | -beos* | -mpeix* | -udk* | -moxiebox* \\\n\t      | -interix* | -uwin* | -mks* | -rhapsody* | -darwin* | -opened* \\\n\t      | -openstep* | -oskit* | -conix* | -pw32* | -nonstopux* \\\n\t      | -storm-chaos* | -tops10* | -tenex* | -tops20* | -its* \\\n\t      | -os2* | -vos* | -palmos* | -uclinux* | -nucleus* \\\n\t      | -morphos* | -superux* | -rtmk* | -rtmk-nova* | -windiss* \\\n\t      | -powermax* | -dnix* | -nx6 | -nx7 | -sei* | -dragonfly* \\\n\t      | -skyos* | -haiku* | -rdos* | -toppers* | -drops* | -es* | -tirtos*)\n\t# Remember, each alternative MUST END IN *, to match a version number.\n\t\t;;\n\t-qnx*)\n\t\tcase $basic_machine in\n\t\t    x86-* | i*86-*)\n\t\t\t;;\n\t\t    *)\n\t\t\tos=-nto$os\n\t\t\t;;\n\t\tesac\n\t\t;;\n\t-nto-qnx*)\n\t\t;;\n\t-nto*)\n\t\tos=`echo $os | sed -e 's|nto|nto-qnx|'`\n\t\t;;\n\t-sim | -es1800* | -hms* | -xray | -os68k* | -none* | -v88r* \\\n\t      | -windows* | -osx | -abug | -netware* | -os9* | -beos* | -haiku* \\\n\t      | -macos* | -mpw* | -magic* | -mmixware* | -mon960* | -lnews*)\n\t\t;;\n\t-mac*)\n\t\tos=`echo $os | sed -e 's|mac|macos|'`\n\t\t;;\n\t-linux-dietlibc)\n\t\tos=-linux-dietlibc\n\t\t;;\n\t-linux*)\n\t\tos=`echo $os | sed -e 's|linux|linux-gnu|'`\n\t\t;;\n\t-sunos5*)\n\t\tos=`echo $os | sed -e 's|sunos5|solaris2|'`\n\t\t;;\n\t-sunos6*)\n\t\tos=`echo $os | sed -e 's|sunos6|solaris3|'`\n\t\t;;\n\t-opened*)\n\t\tos=-openedition\n\t\t;;\n\t-os400*)\n\t\tos=-os400\n\t\t;;\n\t-wince*)\n\t\tos=-wince\n\t\t;;\n\t-osfrose*)\n\t\tos=-osfrose\n\t\t;;\n\t-osf*)\n\t\tos=-osf\n\t\t;;\n\t-utek*)\n\t\tos=-bsd\n\t\t;;\n\t-dynix*)\n\t\tos=-bsd\n\t\t;;\n\t-acis*)\n\t\tos=-aos\n\t\t;;\n\t-atheos*)\n\t\tos=-atheos\n\t\t;;\n\t-syllable*)\n\t\tos=-syllable\n\t\t;;\n\t-386bsd)\n\t\tos=-bsd\n\t\t;;\n\t-ctix* | -uts*)\n\t\tos=-sysv\n\t\t;;\n\t-nova*)\n\t\tos=-rtmk-nova\n\t\t;;\n\t-ns2 )\n\t\tos=-nextstep2\n\t\t;;\n\t-nsk*)\n\t\tos=-nsk\n\t\t;;\n\t# Preserve the version number of sinix5.\n\t-sinix5.*)\n\t\tos=`echo $os | sed -e 's|sinix|sysv|'`\n\t\t;;\n\t-sinix*)\n\t\tos=-sysv4\n\t\t;;\n\t-tpf*)\n\t\tos=-tpf\n\t\t;;\n\t-triton*)\n\t\tos=-sysv3\n\t\t;;\n\t-oss*)\n\t\tos=-sysv3\n\t\t;;\n\t-svr4)\n\t\tos=-sysv4\n\t\t;;\n\t-svr3)\n\t\tos=-sysv3\n\t\t;;\n\t-sysvr4)\n\t\tos=-sysv4\n\t\t;;\n\t# This must come after -sysvr4.\n\t-sysv*)\n\t\t;;\n\t-ose*)\n\t\tos=-ose\n\t\t;;\n\t-es1800*)\n\t\tos=-ose\n\t\t;;\n\t-xenix)\n\t\tos=-xenix\n\t\t;;\n\t-*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)\n\t\tos=-mint\n\t\t;;\n\t-aros*)\n\t\tos=-aros\n\t\t;;\n\t-zvmoe)\n\t\tos=-zvmoe\n\t\t;;\n\t-dicos*)\n\t\tos=-dicos\n\t\t;;\n\t-nacl*)\n\t\t;;\n\t-none)\n\t\t;;\n\t*)\n\t\t# Get rid of the `-' at the beginning of $os.\n\t\tos=`echo $os | sed 's/[^-]*-//'`\n\t\techo Invalid configuration \\`$1\\': system \\`$os\\' not recognized 1>&2\n\t\texit 1\n\t\t;;\nesac\nelse\n\n# Here we handle the default operating systems that come with various machines.\n# The value should be what the vendor currently ships out the door with their\n# machine or put another way, the most popular os provided with the machine.\n\n# Note that if you're going to try to match \"-MANUFACTURER\" here (say,\n# \"-sun\"), then you have to tell the case statement up towards the top\n# that MANUFACTURER isn't an operating system.  Otherwise, code above\n# will signal an error saying that MANUFACTURER isn't an operating\n# system, and we'll never get to this point.\n\ncase $basic_machine in\n\tscore-*)\n\t\tos=-elf\n\t\t;;\n\tspu-*)\n\t\tos=-elf\n\t\t;;\n\t*-acorn)\n\t\tos=-riscix1.2\n\t\t;;\n\tarm*-rebel)\n\t\tos=-linux\n\t\t;;\n\tarm*-semi)\n\t\tos=-aout\n\t\t;;\n\tc4x-* | tic4x-*)\n\t\tos=-coff\n\t\t;;\n\tc8051-*)\n\t\tos=-elf\n\t\t;;\n\thexagon-*)\n\t\tos=-elf\n\t\t;;\n\ttic54x-*)\n\t\tos=-coff\n\t\t;;\n\ttic55x-*)\n\t\tos=-coff\n\t\t;;\n\ttic6x-*)\n\t\tos=-coff\n\t\t;;\n\t# This must come before the *-dec entry.\n\tpdp10-*)\n\t\tos=-tops20\n\t\t;;\n\tpdp11-*)\n\t\tos=-none\n\t\t;;\n\t*-dec | vax-*)\n\t\tos=-ultrix4.2\n\t\t;;\n\tm68*-apollo)\n\t\tos=-domain\n\t\t;;\n\ti386-sun)\n\t\tos=-sunos4.0.2\n\t\t;;\n\tm68000-sun)\n\t\tos=-sunos3\n\t\t;;\n\tm68*-cisco)\n\t\tos=-aout\n\t\t;;\n\tmep-*)\n\t\tos=-elf\n\t\t;;\n\tmips*-cisco)\n\t\tos=-elf\n\t\t;;\n\tmips*-*)\n\t\tos=-elf\n\t\t;;\n\tor32-*)\n\t\tos=-coff\n\t\t;;\n\t*-tti)\t# must be before sparc entry or we get the wrong os.\n\t\tos=-sysv3\n\t\t;;\n\tsparc-* | *-sun)\n\t\tos=-sunos4.1.1\n\t\t;;\n\t*-be)\n\t\tos=-beos\n\t\t;;\n\t*-haiku)\n\t\tos=-haiku\n\t\t;;\n\t*-ibm)\n\t\tos=-aix\n\t\t;;\n\t*-knuth)\n\t\tos=-mmixware\n\t\t;;\n\t*-wec)\n\t\tos=-proelf\n\t\t;;\n\t*-winbond)\n\t\tos=-proelf\n\t\t;;\n\t*-oki)\n\t\tos=-proelf\n\t\t;;\n\t*-hp)\n\t\tos=-hpux\n\t\t;;\n\t*-hitachi)\n\t\tos=-hiux\n\t\t;;\n\ti860-* | *-att | *-ncr | *-altos | *-motorola | *-convergent)\n\t\tos=-sysv\n\t\t;;\n\t*-cbm)\n\t\tos=-amigaos\n\t\t;;\n\t*-dg)\n\t\tos=-dgux\n\t\t;;\n\t*-dolphin)\n\t\tos=-sysv3\n\t\t;;\n\tm68k-ccur)\n\t\tos=-rtu\n\t\t;;\n\tm88k-omron*)\n\t\tos=-luna\n\t\t;;\n\t*-next )\n\t\tos=-nextstep\n\t\t;;\n\t*-sequent)\n\t\tos=-ptx\n\t\t;;\n\t*-crds)\n\t\tos=-unos\n\t\t;;\n\t*-ns)\n\t\tos=-genix\n\t\t;;\n\ti370-*)\n\t\tos=-mvs\n\t\t;;\n\t*-next)\n\t\tos=-nextstep3\n\t\t;;\n\t*-gould)\n\t\tos=-sysv\n\t\t;;\n\t*-highlevel)\n\t\tos=-bsd\n\t\t;;\n\t*-encore)\n\t\tos=-bsd\n\t\t;;\n\t*-sgi)\n\t\tos=-irix\n\t\t;;\n\t*-siemens)\n\t\tos=-sysv4\n\t\t;;\n\t*-masscomp)\n\t\tos=-rtu\n\t\t;;\n\tf30[01]-fujitsu | f700-fujitsu)\n\t\tos=-uxpv\n\t\t;;\n\t*-rom68k)\n\t\tos=-coff\n\t\t;;\n\t*-*bug)\n\t\tos=-coff\n\t\t;;\n\t*-apple)\n\t\tos=-macos\n\t\t;;\n\t*-atari*)\n\t\tos=-mint\n\t\t;;\n\t*)\n\t\tos=-none\n\t\t;;\nesac\nfi\n\n# Here we handle the case where we know the os, and the CPU type, but not the\n# manufacturer.  We pick the logical manufacturer.\nvendor=unknown\ncase $basic_machine in\n\t*-unknown)\n\t\tcase $os in\n\t\t\t-riscix*)\n\t\t\t\tvendor=acorn\n\t\t\t\t;;\n\t\t\t-sunos*)\n\t\t\t\tvendor=sun\n\t\t\t\t;;\n\t\t\t-cnk*|-aix*)\n\t\t\t\tvendor=ibm\n\t\t\t\t;;\n\t\t\t-beos*)\n\t\t\t\tvendor=be\n\t\t\t\t;;\n\t\t\t-hpux*)\n\t\t\t\tvendor=hp\n\t\t\t\t;;\n\t\t\t-mpeix*)\n\t\t\t\tvendor=hp\n\t\t\t\t;;\n\t\t\t-hiux*)\n\t\t\t\tvendor=hitachi\n\t\t\t\t;;\n\t\t\t-unos*)\n\t\t\t\tvendor=crds\n\t\t\t\t;;\n\t\t\t-dgux*)\n\t\t\t\tvendor=dg\n\t\t\t\t;;\n\t\t\t-luna*)\n\t\t\t\tvendor=omron\n\t\t\t\t;;\n\t\t\t-genix*)\n\t\t\t\tvendor=ns\n\t\t\t\t;;\n\t\t\t-mvs* | -opened*)\n\t\t\t\tvendor=ibm\n\t\t\t\t;;\n\t\t\t-os400*)\n\t\t\t\tvendor=ibm\n\t\t\t\t;;\n\t\t\t-ptx*)\n\t\t\t\tvendor=sequent\n\t\t\t\t;;\n\t\t\t-tpf*)\n\t\t\t\tvendor=ibm\n\t\t\t\t;;\n\t\t\t-vxsim* | -vxworks* | -windiss*)\n\t\t\t\tvendor=wrs\n\t\t\t\t;;\n\t\t\t-aux*)\n\t\t\t\tvendor=apple\n\t\t\t\t;;\n\t\t\t-hms*)\n\t\t\t\tvendor=hitachi\n\t\t\t\t;;\n\t\t\t-mpw* | -macos*)\n\t\t\t\tvendor=apple\n\t\t\t\t;;\n\t\t\t-*mint | -mint[0-9]* | -*MiNT | -MiNT[0-9]*)\n\t\t\t\tvendor=atari\n\t\t\t\t;;\n\t\t\t-vos*)\n\t\t\t\tvendor=stratus\n\t\t\t\t;;\n\t\tesac\n\t\tbasic_machine=`echo $basic_machine | sed \"s/unknown/$vendor/\"`\n\t\t;;\nesac\n\necho $basic_machine$os\nexit\n\n# Local variables:\n# eval: (add-hook 'write-file-hooks 'time-stamp)\n# time-stamp-start: \"timestamp='\"\n# time-stamp-format: \"%:y-%02m-%02d\"\n# time-stamp-end: \"'\"\n# End:\n"
  },
  {
    "path": "cudd/build-aux/depcomp",
    "content": "#! /bin/sh\n# depcomp - compile a program generating dependencies as side-effects\n\nscriptversion=2013-05-30.07; # UTC\n\n# Copyright (C) 1999-2013 Free Software Foundation, Inc.\n\n# This program is free software; you can redistribute it and/or modify\n# it under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 2, or (at your option)\n# any later version.\n\n# This program is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n# GNU General Public License for more details.\n\n# You should have received a copy of the GNU General Public License\n# along with this program.  If not, see <http://www.gnu.org/licenses/>.\n\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program that contains a\n# configuration script generated by Autoconf, you may include it under\n# the same distribution terms that you use for the rest of that program.\n\n# Originally written by Alexandre Oliva <oliva@dcc.unicamp.br>.\n\ncase $1 in\n  '')\n    echo \"$0: No command.  Try '$0 --help' for more information.\" 1>&2\n    exit 1;\n    ;;\n  -h | --h*)\n    cat <<\\EOF\nUsage: depcomp [--help] [--version] PROGRAM [ARGS]\n\nRun PROGRAMS ARGS to compile a file, generating dependencies\nas side-effects.\n\nEnvironment variables:\n  depmode     Dependency tracking mode.\n  source      Source file read by 'PROGRAMS ARGS'.\n  object      Object file output by 'PROGRAMS ARGS'.\n  DEPDIR      directory where to store dependencies.\n  depfile     Dependency file to output.\n  tmpdepfile  Temporary file to use when outputting dependencies.\n  libtool     Whether libtool is used (yes/no).\n\nReport bugs to <bug-automake@gnu.org>.\nEOF\n    exit $?\n    ;;\n  -v | --v*)\n    echo \"depcomp $scriptversion\"\n    exit $?\n    ;;\nesac\n\n# Get the directory component of the given path, and save it in the\n# global variables '$dir'.  Note that this directory component will\n# be either empty or ending with a '/' character.  This is deliberate.\nset_dir_from ()\n{\n  case $1 in\n    */*) dir=`echo \"$1\" | sed -e 's|/[^/]*$|/|'`;;\n      *) dir=;;\n  esac\n}\n\n# Get the suffix-stripped basename of the given path, and save it the\n# global variable '$base'.\nset_base_from ()\n{\n  base=`echo \"$1\" | sed -e 's|^.*/||' -e 's/\\.[^.]*$//'`\n}\n\n# If no dependency file was actually created by the compiler invocation,\n# we still have to create a dummy depfile, to avoid errors with the\n# Makefile \"include basename.Plo\" scheme.\nmake_dummy_depfile ()\n{\n  echo \"#dummy\" > \"$depfile\"\n}\n\n# Factor out some common post-processing of the generated depfile.\n# Requires the auxiliary global variable '$tmpdepfile' to be set.\naix_post_process_depfile ()\n{\n  # If the compiler actually managed to produce a dependency file,\n  # post-process it.\n  if test -f \"$tmpdepfile\"; then\n    # Each line is of the form 'foo.o: dependency.h'.\n    # Do two passes, one to just change these to\n    #   $object: dependency.h\n    # and one to simply output\n    #   dependency.h:\n    # which is needed to avoid the deleted-header problem.\n    { sed -e \"s,^.*\\.[$lower]*:,$object:,\" < \"$tmpdepfile\"\n      sed -e \"s,^.*\\.[$lower]*:[$tab ]*,,\" -e 's,$,:,' < \"$tmpdepfile\"\n    } > \"$depfile\"\n    rm -f \"$tmpdepfile\"\n  else\n    make_dummy_depfile\n  fi\n}\n\n# A tabulation character.\ntab='\t'\n# A newline character.\nnl='\n'\n# Character ranges might be problematic outside the C locale.\n# These definitions help.\nupper=ABCDEFGHIJKLMNOPQRSTUVWXYZ\nlower=abcdefghijklmnopqrstuvwxyz\ndigits=0123456789\nalpha=${upper}${lower}\n\nif test -z \"$depmode\" || test -z \"$source\" || test -z \"$object\"; then\n  echo \"depcomp: Variables source, object and depmode must be set\" 1>&2\n  exit 1\nfi\n\n# Dependencies for sub/bar.o or sub/bar.obj go into sub/.deps/bar.Po.\ndepfile=${depfile-`echo \"$object\" |\n  sed 's|[^\\\\/]*$|'${DEPDIR-.deps}'/&|;s|\\.\\([^.]*\\)$|.P\\1|;s|Pobj$|Po|'`}\ntmpdepfile=${tmpdepfile-`echo \"$depfile\" | sed 's/\\.\\([^.]*\\)$/.T\\1/'`}\n\nrm -f \"$tmpdepfile\"\n\n# Avoid interferences from the environment.\ngccflag= dashmflag=\n\n# Some modes work just like other modes, but use different flags.  We\n# parameterize here, but still list the modes in the big case below,\n# to make depend.m4 easier to write.  Note that we *cannot* use a case\n# here, because this file can only contain one case statement.\nif test \"$depmode\" = hp; then\n  # HP compiler uses -M and no extra arg.\n  gccflag=-M\n  depmode=gcc\nfi\n\nif test \"$depmode\" = dashXmstdout; then\n  # This is just like dashmstdout with a different argument.\n  dashmflag=-xM\n  depmode=dashmstdout\nfi\n\ncygpath_u=\"cygpath -u -f -\"\nif test \"$depmode\" = msvcmsys; then\n  # This is just like msvisualcpp but w/o cygpath translation.\n  # Just convert the backslash-escaped backslashes to single forward\n  # slashes to satisfy depend.m4\n  cygpath_u='sed s,\\\\\\\\,/,g'\n  depmode=msvisualcpp\nfi\n\nif test \"$depmode\" = msvc7msys; then\n  # This is just like msvc7 but w/o cygpath translation.\n  # Just convert the backslash-escaped backslashes to single forward\n  # slashes to satisfy depend.m4\n  cygpath_u='sed s,\\\\\\\\,/,g'\n  depmode=msvc7\nfi\n\nif test \"$depmode\" = xlc; then\n  # IBM C/C++ Compilers xlc/xlC can output gcc-like dependency information.\n  gccflag=-qmakedep=gcc,-MF\n  depmode=gcc\nfi\n\ncase \"$depmode\" in\ngcc3)\n## gcc 3 implements dependency tracking that does exactly what\n## we want.  Yay!  Note: for some reason libtool 1.4 doesn't like\n## it if -MD -MP comes after the -MF stuff.  Hmm.\n## Unfortunately, FreeBSD c89 acceptance of flags depends upon\n## the command line argument order; so add the flags where they\n## appear in depend2.am.  Note that the slowdown incurred here\n## affects only configure: in makefiles, %FASTDEP% shortcuts this.\n  for arg\n  do\n    case $arg in\n    -c) set fnord \"$@\" -MT \"$object\" -MD -MP -MF \"$tmpdepfile\" \"$arg\" ;;\n    *)  set fnord \"$@\" \"$arg\" ;;\n    esac\n    shift # fnord\n    shift # $arg\n  done\n  \"$@\"\n  stat=$?\n  if test $stat -ne 0; then\n    rm -f \"$tmpdepfile\"\n    exit $stat\n  fi\n  mv \"$tmpdepfile\" \"$depfile\"\n  ;;\n\ngcc)\n## Note that this doesn't just cater to obsosete pre-3.x GCC compilers.\n## but also to in-use compilers like IMB xlc/xlC and the HP C compiler.\n## (see the conditional assignment to $gccflag above).\n## There are various ways to get dependency output from gcc.  Here's\n## why we pick this rather obscure method:\n## - Don't want to use -MD because we'd like the dependencies to end\n##   up in a subdir.  Having to rename by hand is ugly.\n##   (We might end up doing this anyway to support other compilers.)\n## - The DEPENDENCIES_OUTPUT environment variable makes gcc act like\n##   -MM, not -M (despite what the docs say).  Also, it might not be\n##   supported by the other compilers which use the 'gcc' depmode.\n## - Using -M directly means running the compiler twice (even worse\n##   than renaming).\n  if test -z \"$gccflag\"; then\n    gccflag=-MD,\n  fi\n  \"$@\" -Wp,\"$gccflag$tmpdepfile\"\n  stat=$?\n  if test $stat -ne 0; then\n    rm -f \"$tmpdepfile\"\n    exit $stat\n  fi\n  rm -f \"$depfile\"\n  echo \"$object : \\\\\" > \"$depfile\"\n  # The second -e expression handles DOS-style file names with drive\n  # letters.\n  sed -e 's/^[^:]*: / /' \\\n      -e 's/^['$alpha']:\\/[^:]*: / /' < \"$tmpdepfile\" >> \"$depfile\"\n## This next piece of magic avoids the \"deleted header file\" problem.\n## The problem is that when a header file which appears in a .P file\n## is deleted, the dependency causes make to die (because there is\n## typically no way to rebuild the header).  We avoid this by adding\n## dummy dependencies for each header file.  Too bad gcc doesn't do\n## this for us directly.\n## Some versions of gcc put a space before the ':'.  On the theory\n## that the space means something, we add a space to the output as\n## well.  hp depmode also adds that space, but also prefixes the VPATH\n## to the object.  Take care to not repeat it in the output.\n## Some versions of the HPUX 10.20 sed can't process this invocation\n## correctly.  Breaking it into two sed invocations is a workaround.\n  tr ' ' \"$nl\" < \"$tmpdepfile\" \\\n    | sed -e 's/^\\\\$//' -e '/^$/d' -e \"s|.*$object$||\" -e '/:$/d' \\\n    | sed -e 's/$/ :/' >> \"$depfile\"\n  rm -f \"$tmpdepfile\"\n  ;;\n\nhp)\n  # This case exists only to let depend.m4 do its work.  It works by\n  # looking at the text of this script.  This case will never be run,\n  # since it is checked for above.\n  exit 1\n  ;;\n\nsgi)\n  if test \"$libtool\" = yes; then\n    \"$@\" \"-Wp,-MDupdate,$tmpdepfile\"\n  else\n    \"$@\" -MDupdate \"$tmpdepfile\"\n  fi\n  stat=$?\n  if test $stat -ne 0; then\n    rm -f \"$tmpdepfile\"\n    exit $stat\n  fi\n  rm -f \"$depfile\"\n\n  if test -f \"$tmpdepfile\"; then  # yes, the sourcefile depend on other files\n    echo \"$object : \\\\\" > \"$depfile\"\n    # Clip off the initial element (the dependent).  Don't try to be\n    # clever and replace this with sed code, as IRIX sed won't handle\n    # lines with more than a fixed number of characters (4096 in\n    # IRIX 6.2 sed, 8192 in IRIX 6.5).  We also remove comment lines;\n    # the IRIX cc adds comments like '#:fec' to the end of the\n    # dependency line.\n    tr ' ' \"$nl\" < \"$tmpdepfile\" \\\n      | sed -e 's/^.*\\.o://' -e 's/#.*$//' -e '/^$/ d' \\\n      | tr \"$nl\" ' ' >> \"$depfile\"\n    echo >> \"$depfile\"\n    # The second pass generates a dummy entry for each header file.\n    tr ' ' \"$nl\" < \"$tmpdepfile\" \\\n      | sed -e 's/^.*\\.o://' -e 's/#.*$//' -e '/^$/ d' -e 's/$/:/' \\\n      >> \"$depfile\"\n  else\n    make_dummy_depfile\n  fi\n  rm -f \"$tmpdepfile\"\n  ;;\n\nxlc)\n  # This case exists only to let depend.m4 do its work.  It works by\n  # looking at the text of this script.  This case will never be run,\n  # since it is checked for above.\n  exit 1\n  ;;\n\naix)\n  # The C for AIX Compiler uses -M and outputs the dependencies\n  # in a .u file.  In older versions, this file always lives in the\n  # current directory.  Also, the AIX compiler puts '$object:' at the\n  # start of each line; $object doesn't have directory information.\n  # Version 6 uses the directory in both cases.\n  set_dir_from \"$object\"\n  set_base_from \"$object\"\n  if test \"$libtool\" = yes; then\n    tmpdepfile1=$dir$base.u\n    tmpdepfile2=$base.u\n    tmpdepfile3=$dir.libs/$base.u\n    \"$@\" -Wc,-M\n  else\n    tmpdepfile1=$dir$base.u\n    tmpdepfile2=$dir$base.u\n    tmpdepfile3=$dir$base.u\n    \"$@\" -M\n  fi\n  stat=$?\n  if test $stat -ne 0; then\n    rm -f \"$tmpdepfile1\" \"$tmpdepfile2\" \"$tmpdepfile3\"\n    exit $stat\n  fi\n\n  for tmpdepfile in \"$tmpdepfile1\" \"$tmpdepfile2\" \"$tmpdepfile3\"\n  do\n    test -f \"$tmpdepfile\" && break\n  done\n  aix_post_process_depfile\n  ;;\n\ntcc)\n  # tcc (Tiny C Compiler) understand '-MD -MF file' since version 0.9.26\n  # FIXME: That version still under development at the moment of writing.\n  #        Make that this statement remains true also for stable, released\n  #        versions.\n  # It will wrap lines (doesn't matter whether long or short) with a\n  # trailing '\\', as in:\n  #\n  #   foo.o : \\\n  #    foo.c \\\n  #    foo.h \\\n  #\n  # It will put a trailing '\\' even on the last line, and will use leading\n  # spaces rather than leading tabs (at least since its commit 0394caf7\n  # \"Emit spaces for -MD\").\n  \"$@\" -MD -MF \"$tmpdepfile\"\n  stat=$?\n  if test $stat -ne 0; then\n    rm -f \"$tmpdepfile\"\n    exit $stat\n  fi\n  rm -f \"$depfile\"\n  # Each non-empty line is of the form 'foo.o : \\' or ' dep.h \\'.\n  # We have to change lines of the first kind to '$object: \\'.\n  sed -e \"s|.*:|$object :|\" < \"$tmpdepfile\" > \"$depfile\"\n  # And for each line of the second kind, we have to emit a 'dep.h:'\n  # dummy dependency, to avoid the deleted-header problem.\n  sed -n -e 's|^  *\\(.*\\) *\\\\$|\\1:|p' < \"$tmpdepfile\" >> \"$depfile\"\n  rm -f \"$tmpdepfile\"\n  ;;\n\n## The order of this option in the case statement is important, since the\n## shell code in configure will try each of these formats in the order\n## listed in this file.  A plain '-MD' option would be understood by many\n## compilers, so we must ensure this comes after the gcc and icc options.\npgcc)\n  # Portland's C compiler understands '-MD'.\n  # Will always output deps to 'file.d' where file is the root name of the\n  # source file under compilation, even if file resides in a subdirectory.\n  # The object file name does not affect the name of the '.d' file.\n  # pgcc 10.2 will output\n  #    foo.o: sub/foo.c sub/foo.h\n  # and will wrap long lines using '\\' :\n  #    foo.o: sub/foo.c ... \\\n  #     sub/foo.h ... \\\n  #     ...\n  set_dir_from \"$object\"\n  # Use the source, not the object, to determine the base name, since\n  # that's sadly what pgcc will do too.\n  set_base_from \"$source\"\n  tmpdepfile=$base.d\n\n  # For projects that build the same source file twice into different object\n  # files, the pgcc approach of using the *source* file root name can cause\n  # problems in parallel builds.  Use a locking strategy to avoid stomping on\n  # the same $tmpdepfile.\n  lockdir=$base.d-lock\n  trap \"\n    echo '$0: caught signal, cleaning up...' >&2\n    rmdir '$lockdir'\n    exit 1\n  \" 1 2 13 15\n  numtries=100\n  i=$numtries\n  while test $i -gt 0; do\n    # mkdir is a portable test-and-set.\n    if mkdir \"$lockdir\" 2>/dev/null; then\n      # This process acquired the lock.\n      \"$@\" -MD\n      stat=$?\n      # Release the lock.\n      rmdir \"$lockdir\"\n      break\n    else\n      # If the lock is being held by a different process, wait\n      # until the winning process is done or we timeout.\n      while test -d \"$lockdir\" && test $i -gt 0; do\n        sleep 1\n        i=`expr $i - 1`\n      done\n    fi\n    i=`expr $i - 1`\n  done\n  trap - 1 2 13 15\n  if test $i -le 0; then\n    echo \"$0: failed to acquire lock after $numtries attempts\" >&2\n    echo \"$0: check lockdir '$lockdir'\" >&2\n    exit 1\n  fi\n\n  if test $stat -ne 0; then\n    rm -f \"$tmpdepfile\"\n    exit $stat\n  fi\n  rm -f \"$depfile\"\n  # Each line is of the form `foo.o: dependent.h',\n  # or `foo.o: dep1.h dep2.h \\', or ` dep3.h dep4.h \\'.\n  # Do two passes, one to just change these to\n  # `$object: dependent.h' and one to simply `dependent.h:'.\n  sed \"s,^[^:]*:,$object :,\" < \"$tmpdepfile\" > \"$depfile\"\n  # Some versions of the HPUX 10.20 sed can't process this invocation\n  # correctly.  Breaking it into two sed invocations is a workaround.\n  sed 's,^[^:]*: \\(.*\\)$,\\1,;s/^\\\\$//;/^$/d;/:$/d' < \"$tmpdepfile\" \\\n    | sed -e 's/$/ :/' >> \"$depfile\"\n  rm -f \"$tmpdepfile\"\n  ;;\n\nhp2)\n  # The \"hp\" stanza above does not work with aCC (C++) and HP's ia64\n  # compilers, which have integrated preprocessors.  The correct option\n  # to use with these is +Maked; it writes dependencies to a file named\n  # 'foo.d', which lands next to the object file, wherever that\n  # happens to be.\n  # Much of this is similar to the tru64 case; see comments there.\n  set_dir_from  \"$object\"\n  set_base_from \"$object\"\n  if test \"$libtool\" = yes; then\n    tmpdepfile1=$dir$base.d\n    tmpdepfile2=$dir.libs/$base.d\n    \"$@\" -Wc,+Maked\n  else\n    tmpdepfile1=$dir$base.d\n    tmpdepfile2=$dir$base.d\n    \"$@\" +Maked\n  fi\n  stat=$?\n  if test $stat -ne 0; then\n     rm -f \"$tmpdepfile1\" \"$tmpdepfile2\"\n     exit $stat\n  fi\n\n  for tmpdepfile in \"$tmpdepfile1\" \"$tmpdepfile2\"\n  do\n    test -f \"$tmpdepfile\" && break\n  done\n  if test -f \"$tmpdepfile\"; then\n    sed -e \"s,^.*\\.[$lower]*:,$object:,\" \"$tmpdepfile\" > \"$depfile\"\n    # Add 'dependent.h:' lines.\n    sed -ne '2,${\n               s/^ *//\n               s/ \\\\*$//\n               s/$/:/\n               p\n             }' \"$tmpdepfile\" >> \"$depfile\"\n  else\n    make_dummy_depfile\n  fi\n  rm -f \"$tmpdepfile\" \"$tmpdepfile2\"\n  ;;\n\ntru64)\n  # The Tru64 compiler uses -MD to generate dependencies as a side\n  # effect.  'cc -MD -o foo.o ...' puts the dependencies into 'foo.o.d'.\n  # At least on Alpha/Redhat 6.1, Compaq CCC V6.2-504 seems to put\n  # dependencies in 'foo.d' instead, so we check for that too.\n  # Subdirectories are respected.\n  set_dir_from  \"$object\"\n  set_base_from \"$object\"\n\n  if test \"$libtool\" = yes; then\n    # Libtool generates 2 separate objects for the 2 libraries.  These\n    # two compilations output dependencies in $dir.libs/$base.o.d and\n    # in $dir$base.o.d.  We have to check for both files, because\n    # one of the two compilations can be disabled.  We should prefer\n    # $dir$base.o.d over $dir.libs/$base.o.d because the latter is\n    # automatically cleaned when .libs/ is deleted, while ignoring\n    # the former would cause a distcleancheck panic.\n    tmpdepfile1=$dir$base.o.d          # libtool 1.5\n    tmpdepfile2=$dir.libs/$base.o.d    # Likewise.\n    tmpdepfile3=$dir.libs/$base.d      # Compaq CCC V6.2-504\n    \"$@\" -Wc,-MD\n  else\n    tmpdepfile1=$dir$base.d\n    tmpdepfile2=$dir$base.d\n    tmpdepfile3=$dir$base.d\n    \"$@\" -MD\n  fi\n\n  stat=$?\n  if test $stat -ne 0; then\n    rm -f \"$tmpdepfile1\" \"$tmpdepfile2\" \"$tmpdepfile3\"\n    exit $stat\n  fi\n\n  for tmpdepfile in \"$tmpdepfile1\" \"$tmpdepfile2\" \"$tmpdepfile3\"\n  do\n    test -f \"$tmpdepfile\" && break\n  done\n  # Same post-processing that is required for AIX mode.\n  aix_post_process_depfile\n  ;;\n\nmsvc7)\n  if test \"$libtool\" = yes; then\n    showIncludes=-Wc,-showIncludes\n  else\n    showIncludes=-showIncludes\n  fi\n  \"$@\" $showIncludes > \"$tmpdepfile\"\n  stat=$?\n  grep -v '^Note: including file: ' \"$tmpdepfile\"\n  if test $stat -ne 0; then\n    rm -f \"$tmpdepfile\"\n    exit $stat\n  fi\n  rm -f \"$depfile\"\n  echo \"$object : \\\\\" > \"$depfile\"\n  # The first sed program below extracts the file names and escapes\n  # backslashes for cygpath.  The second sed program outputs the file\n  # name when reading, but also accumulates all include files in the\n  # hold buffer in order to output them again at the end.  This only\n  # works with sed implementations that can handle large buffers.\n  sed < \"$tmpdepfile\" -n '\n/^Note: including file:  *\\(.*\\)/ {\n  s//\\1/\n  s/\\\\/\\\\\\\\/g\n  p\n}' | $cygpath_u | sort -u | sed -n '\ns/ /\\\\ /g\ns/\\(.*\\)/'\"$tab\"'\\1 \\\\/p\ns/.\\(.*\\) \\\\/\\1:/\nH\n$ {\n  s/.*/'\"$tab\"'/\n  G\n  p\n}' >> \"$depfile\"\n  echo >> \"$depfile\" # make sure the fragment doesn't end with a backslash\n  rm -f \"$tmpdepfile\"\n  ;;\n\nmsvc7msys)\n  # This case exists only to let depend.m4 do its work.  It works by\n  # looking at the text of this script.  This case will never be run,\n  # since it is checked for above.\n  exit 1\n  ;;\n\n#nosideeffect)\n  # This comment above is used by automake to tell side-effect\n  # dependency tracking mechanisms from slower ones.\n\ndashmstdout)\n  # Important note: in order to support this mode, a compiler *must*\n  # always write the preprocessed file to stdout, regardless of -o.\n  \"$@\" || exit $?\n\n  # Remove the call to Libtool.\n  if test \"$libtool\" = yes; then\n    while test \"X$1\" != 'X--mode=compile'; do\n      shift\n    done\n    shift\n  fi\n\n  # Remove '-o $object'.\n  IFS=\" \"\n  for arg\n  do\n    case $arg in\n    -o)\n      shift\n      ;;\n    $object)\n      shift\n      ;;\n    *)\n      set fnord \"$@\" \"$arg\"\n      shift # fnord\n      shift # $arg\n      ;;\n    esac\n  done\n\n  test -z \"$dashmflag\" && dashmflag=-M\n  # Require at least two characters before searching for ':'\n  # in the target name.  This is to cope with DOS-style filenames:\n  # a dependency such as 'c:/foo/bar' could be seen as target 'c' otherwise.\n  \"$@\" $dashmflag |\n    sed \"s|^[$tab ]*[^:$tab ][^:][^:]*:[$tab ]*|$object: |\" > \"$tmpdepfile\"\n  rm -f \"$depfile\"\n  cat < \"$tmpdepfile\" > \"$depfile\"\n  # Some versions of the HPUX 10.20 sed can't process this sed invocation\n  # correctly.  Breaking it into two sed invocations is a workaround.\n  tr ' ' \"$nl\" < \"$tmpdepfile\" \\\n    | sed -e 's/^\\\\$//' -e '/^$/d' -e '/:$/d' \\\n    | sed -e 's/$/ :/' >> \"$depfile\"\n  rm -f \"$tmpdepfile\"\n  ;;\n\ndashXmstdout)\n  # This case only exists to satisfy depend.m4.  It is never actually\n  # run, as this mode is specially recognized in the preamble.\n  exit 1\n  ;;\n\nmakedepend)\n  \"$@\" || exit $?\n  # Remove any Libtool call\n  if test \"$libtool\" = yes; then\n    while test \"X$1\" != 'X--mode=compile'; do\n      shift\n    done\n    shift\n  fi\n  # X makedepend\n  shift\n  cleared=no eat=no\n  for arg\n  do\n    case $cleared in\n    no)\n      set \"\"; shift\n      cleared=yes ;;\n    esac\n    if test $eat = yes; then\n      eat=no\n      continue\n    fi\n    case \"$arg\" in\n    -D*|-I*)\n      set fnord \"$@\" \"$arg\"; shift ;;\n    # Strip any option that makedepend may not understand.  Remove\n    # the object too, otherwise makedepend will parse it as a source file.\n    -arch)\n      eat=yes ;;\n    -*|$object)\n      ;;\n    *)\n      set fnord \"$@\" \"$arg\"; shift ;;\n    esac\n  done\n  obj_suffix=`echo \"$object\" | sed 's/^.*\\././'`\n  touch \"$tmpdepfile\"\n  ${MAKEDEPEND-makedepend} -o\"$obj_suffix\" -f\"$tmpdepfile\" \"$@\"\n  rm -f \"$depfile\"\n  # makedepend may prepend the VPATH from the source file name to the object.\n  # No need to regex-escape $object, excess matching of '.' is harmless.\n  sed \"s|^.*\\($object *:\\)|\\1|\" \"$tmpdepfile\" > \"$depfile\"\n  # Some versions of the HPUX 10.20 sed can't process the last invocation\n  # correctly.  Breaking it into two sed invocations is a workaround.\n  sed '1,2d' \"$tmpdepfile\" \\\n    | tr ' ' \"$nl\" \\\n    | sed -e 's/^\\\\$//' -e '/^$/d' -e '/:$/d' \\\n    | sed -e 's/$/ :/' >> \"$depfile\"\n  rm -f \"$tmpdepfile\" \"$tmpdepfile\".bak\n  ;;\n\ncpp)\n  # Important note: in order to support this mode, a compiler *must*\n  # always write the preprocessed file to stdout.\n  \"$@\" || exit $?\n\n  # Remove the call to Libtool.\n  if test \"$libtool\" = yes; then\n    while test \"X$1\" != 'X--mode=compile'; do\n      shift\n    done\n    shift\n  fi\n\n  # Remove '-o $object'.\n  IFS=\" \"\n  for arg\n  do\n    case $arg in\n    -o)\n      shift\n      ;;\n    $object)\n      shift\n      ;;\n    *)\n      set fnord \"$@\" \"$arg\"\n      shift # fnord\n      shift # $arg\n      ;;\n    esac\n  done\n\n  \"$@\" -E \\\n    | sed -n -e '/^# [0-9][0-9]* \"\\([^\"]*\\)\".*/ s:: \\1 \\\\:p' \\\n             -e '/^#line [0-9][0-9]* \"\\([^\"]*\\)\".*/ s:: \\1 \\\\:p' \\\n    | sed '$ s: \\\\$::' > \"$tmpdepfile\"\n  rm -f \"$depfile\"\n  echo \"$object : \\\\\" > \"$depfile\"\n  cat < \"$tmpdepfile\" >> \"$depfile\"\n  sed < \"$tmpdepfile\" '/^$/d;s/^ //;s/ \\\\$//;s/$/ :/' >> \"$depfile\"\n  rm -f \"$tmpdepfile\"\n  ;;\n\nmsvisualcpp)\n  # Important note: in order to support this mode, a compiler *must*\n  # always write the preprocessed file to stdout.\n  \"$@\" || exit $?\n\n  # Remove the call to Libtool.\n  if test \"$libtool\" = yes; then\n    while test \"X$1\" != 'X--mode=compile'; do\n      shift\n    done\n    shift\n  fi\n\n  IFS=\" \"\n  for arg\n  do\n    case \"$arg\" in\n    -o)\n      shift\n      ;;\n    $object)\n      shift\n      ;;\n    \"-Gm\"|\"/Gm\"|\"-Gi\"|\"/Gi\"|\"-ZI\"|\"/ZI\")\n        set fnord \"$@\"\n        shift\n        shift\n        ;;\n    *)\n        set fnord \"$@\" \"$arg\"\n        shift\n        shift\n        ;;\n    esac\n  done\n  \"$@\" -E 2>/dev/null |\n  sed -n '/^#line [0-9][0-9]* \"\\([^\"]*\\)\"/ s::\\1:p' | $cygpath_u | sort -u > \"$tmpdepfile\"\n  rm -f \"$depfile\"\n  echo \"$object : \\\\\" > \"$depfile\"\n  sed < \"$tmpdepfile\" -n -e 's% %\\\\ %g' -e '/^\\(.*\\)$/ s::'\"$tab\"'\\1 \\\\:p' >> \"$depfile\"\n  echo \"$tab\" >> \"$depfile\"\n  sed < \"$tmpdepfile\" -n -e 's% %\\\\ %g' -e '/^\\(.*\\)$/ s::\\1\\::p' >> \"$depfile\"\n  rm -f \"$tmpdepfile\"\n  ;;\n\nmsvcmsys)\n  # This case exists only to let depend.m4 do its work.  It works by\n  # looking at the text of this script.  This case will never be run,\n  # since it is checked for above.\n  exit 1\n  ;;\n\nnone)\n  exec \"$@\"\n  ;;\n\n*)\n  echo \"Unknown depmode $depmode\" 1>&2\n  exit 1\n  ;;\nesac\n\nexit 0\n\n# Local Variables:\n# mode: shell-script\n# sh-indentation: 2\n# eval: (add-hook 'write-file-hooks 'time-stamp)\n# time-stamp-start: \"scriptversion=\"\n# time-stamp-format: \"%:y-%02m-%02d.%02H\"\n# time-stamp-time-zone: \"UTC\"\n# time-stamp-end: \"; # UTC\"\n# End:\n"
  },
  {
    "path": "cudd/build-aux/install-sh",
    "content": "#!/bin/sh\n# install - install a program, script, or datafile\n\nscriptversion=2011-11-20.07; # UTC\n\n# This originates from X11R5 (mit/util/scripts/install.sh), which was\n# later released in X11R6 (xc/config/util/install.sh) with the\n# following copyright and license.\n#\n# Copyright (C) 1994 X Consortium\n#\n# Permission is hereby granted, free of charge, to any person obtaining a copy\n# of this software and associated documentation files (the \"Software\"), to\n# deal in the Software without restriction, including without limitation the\n# rights to use, copy, modify, merge, publish, distribute, sublicense, and/or\n# sell copies of the Software, and to permit persons to whom the Software is\n# furnished to do so, subject to the following conditions:\n#\n# The above copyright notice and this permission notice shall be included in\n# all copies or substantial portions of the Software.\n#\n# THE SOFTWARE IS PROVIDED \"AS IS\", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR\n# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,\n# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.  IN NO EVENT SHALL THE\n# X CONSORTIUM BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN\n# AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNEC-\n# TION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.\n#\n# Except as contained in this notice, the name of the X Consortium shall not\n# be used in advertising or otherwise to promote the sale, use or other deal-\n# ings in this Software without prior written authorization from the X Consor-\n# tium.\n#\n#\n# FSF changes to this file are in the public domain.\n#\n# Calling this script install-sh is preferred over install.sh, to prevent\n# 'make' implicit rules from creating a file called install from it\n# when there is no Makefile.\n#\n# This script is compatible with the BSD install script, but was written\n# from scratch.\n\nnl='\n'\nIFS=\" \"\"\t$nl\"\n\n# set DOITPROG to echo to test this script\n\n# Don't use :- since 4.3BSD and earlier shells don't like it.\ndoit=${DOITPROG-}\nif test -z \"$doit\"; then\n  doit_exec=exec\nelse\n  doit_exec=$doit\nfi\n\n# Put in absolute file names if you don't have them in your path;\n# or use environment vars.\n\nchgrpprog=${CHGRPPROG-chgrp}\nchmodprog=${CHMODPROG-chmod}\nchownprog=${CHOWNPROG-chown}\ncmpprog=${CMPPROG-cmp}\ncpprog=${CPPROG-cp}\nmkdirprog=${MKDIRPROG-mkdir}\nmvprog=${MVPROG-mv}\nrmprog=${RMPROG-rm}\nstripprog=${STRIPPROG-strip}\n\nposix_glob='?'\ninitialize_posix_glob='\n  test \"$posix_glob\" != \"?\" || {\n    if (set -f) 2>/dev/null; then\n      posix_glob=\n    else\n      posix_glob=:\n    fi\n  }\n'\n\nposix_mkdir=\n\n# Desired mode of installed file.\nmode=0755\n\nchgrpcmd=\nchmodcmd=$chmodprog\nchowncmd=\nmvcmd=$mvprog\nrmcmd=\"$rmprog -f\"\nstripcmd=\n\nsrc=\ndst=\ndir_arg=\ndst_arg=\n\ncopy_on_change=false\nno_target_directory=\n\nusage=\"\\\nUsage: $0 [OPTION]... [-T] SRCFILE DSTFILE\n   or: $0 [OPTION]... SRCFILES... DIRECTORY\n   or: $0 [OPTION]... -t DIRECTORY SRCFILES...\n   or: $0 [OPTION]... -d DIRECTORIES...\n\nIn the 1st form, copy SRCFILE to DSTFILE.\nIn the 2nd and 3rd, copy all SRCFILES to DIRECTORY.\nIn the 4th, create DIRECTORIES.\n\nOptions:\n     --help     display this help and exit.\n     --version  display version info and exit.\n\n  -c            (ignored)\n  -C            install only if different (preserve the last data modification time)\n  -d            create directories instead of installing files.\n  -g GROUP      $chgrpprog installed files to GROUP.\n  -m MODE       $chmodprog installed files to MODE.\n  -o USER       $chownprog installed files to USER.\n  -s            $stripprog installed files.\n  -t DIRECTORY  install into DIRECTORY.\n  -T            report an error if DSTFILE is a directory.\n\nEnvironment variables override the default commands:\n  CHGRPPROG CHMODPROG CHOWNPROG CMPPROG CPPROG MKDIRPROG MVPROG\n  RMPROG STRIPPROG\n\"\n\nwhile test $# -ne 0; do\n  case $1 in\n    -c) ;;\n\n    -C) copy_on_change=true;;\n\n    -d) dir_arg=true;;\n\n    -g) chgrpcmd=\"$chgrpprog $2\"\n\tshift;;\n\n    --help) echo \"$usage\"; exit $?;;\n\n    -m) mode=$2\n\tcase $mode in\n\t  *' '* | *'\t'* | *'\n'*\t  | *'*'* | *'?'* | *'['*)\n\t    echo \"$0: invalid mode: $mode\" >&2\n\t    exit 1;;\n\tesac\n\tshift;;\n\n    -o) chowncmd=\"$chownprog $2\"\n\tshift;;\n\n    -s) stripcmd=$stripprog;;\n\n    -t) dst_arg=$2\n\t# Protect names problematic for 'test' and other utilities.\n\tcase $dst_arg in\n\t  -* | [=\\(\\)!]) dst_arg=./$dst_arg;;\n\tesac\n\tshift;;\n\n    -T) no_target_directory=true;;\n\n    --version) echo \"$0 $scriptversion\"; exit $?;;\n\n    --)\tshift\n\tbreak;;\n\n    -*)\techo \"$0: invalid option: $1\" >&2\n\texit 1;;\n\n    *)  break;;\n  esac\n  shift\ndone\n\nif test $# -ne 0 && test -z \"$dir_arg$dst_arg\"; then\n  # When -d is used, all remaining arguments are directories to create.\n  # When -t is used, the destination is already specified.\n  # Otherwise, the last argument is the destination.  Remove it from $@.\n  for arg\n  do\n    if test -n \"$dst_arg\"; then\n      # $@ is not empty: it contains at least $arg.\n      set fnord \"$@\" \"$dst_arg\"\n      shift # fnord\n    fi\n    shift # arg\n    dst_arg=$arg\n    # Protect names problematic for 'test' and other utilities.\n    case $dst_arg in\n      -* | [=\\(\\)!]) dst_arg=./$dst_arg;;\n    esac\n  done\nfi\n\nif test $# -eq 0; then\n  if test -z \"$dir_arg\"; then\n    echo \"$0: no input file specified.\" >&2\n    exit 1\n  fi\n  # It's OK to call 'install-sh -d' without argument.\n  # This can happen when creating conditional directories.\n  exit 0\nfi\n\nif test -z \"$dir_arg\"; then\n  do_exit='(exit $ret); exit $ret'\n  trap \"ret=129; $do_exit\" 1\n  trap \"ret=130; $do_exit\" 2\n  trap \"ret=141; $do_exit\" 13\n  trap \"ret=143; $do_exit\" 15\n\n  # Set umask so as not to create temps with too-generous modes.\n  # However, 'strip' requires both read and write access to temps.\n  case $mode in\n    # Optimize common cases.\n    *644) cp_umask=133;;\n    *755) cp_umask=22;;\n\n    *[0-7])\n      if test -z \"$stripcmd\"; then\n\tu_plus_rw=\n      else\n\tu_plus_rw='% 200'\n      fi\n      cp_umask=`expr '(' 777 - $mode % 1000 ')' $u_plus_rw`;;\n    *)\n      if test -z \"$stripcmd\"; then\n\tu_plus_rw=\n      else\n\tu_plus_rw=,u+rw\n      fi\n      cp_umask=$mode$u_plus_rw;;\n  esac\nfi\n\nfor src\ndo\n  # Protect names problematic for 'test' and other utilities.\n  case $src in\n    -* | [=\\(\\)!]) src=./$src;;\n  esac\n\n  if test -n \"$dir_arg\"; then\n    dst=$src\n    dstdir=$dst\n    test -d \"$dstdir\"\n    dstdir_status=$?\n  else\n\n    # Waiting for this to be detected by the \"$cpprog $src $dsttmp\" command\n    # might cause directories to be created, which would be especially bad\n    # if $src (and thus $dsttmp) contains '*'.\n    if test ! -f \"$src\" && test ! -d \"$src\"; then\n      echo \"$0: $src does not exist.\" >&2\n      exit 1\n    fi\n\n    if test -z \"$dst_arg\"; then\n      echo \"$0: no destination specified.\" >&2\n      exit 1\n    fi\n    dst=$dst_arg\n\n    # If destination is a directory, append the input filename; won't work\n    # if double slashes aren't ignored.\n    if test -d \"$dst\"; then\n      if test -n \"$no_target_directory\"; then\n\techo \"$0: $dst_arg: Is a directory\" >&2\n\texit 1\n      fi\n      dstdir=$dst\n      dst=$dstdir/`basename \"$src\"`\n      dstdir_status=0\n    else\n      # Prefer dirname, but fall back on a substitute if dirname fails.\n      dstdir=`\n\t(dirname \"$dst\") 2>/dev/null ||\n\texpr X\"$dst\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t     X\"$dst\" : 'X\\(//\\)[^/]' \\| \\\n\t     X\"$dst\" : 'X\\(//\\)$' \\| \\\n\t     X\"$dst\" : 'X\\(/\\)' \\| . 2>/dev/null ||\n\techo X\"$dst\" |\n\t    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{\n\t\t   s//\\1/\n\t\t   q\n\t\t }\n\t\t /^X\\(\\/\\/\\)[^/].*/{\n\t\t   s//\\1/\n\t\t   q\n\t\t }\n\t\t /^X\\(\\/\\/\\)$/{\n\t\t   s//\\1/\n\t\t   q\n\t\t }\n\t\t /^X\\(\\/\\).*/{\n\t\t   s//\\1/\n\t\t   q\n\t\t }\n\t\t s/.*/./; q'\n      `\n\n      test -d \"$dstdir\"\n      dstdir_status=$?\n    fi\n  fi\n\n  obsolete_mkdir_used=false\n\n  if test $dstdir_status != 0; then\n    case $posix_mkdir in\n      '')\n\t# Create intermediate dirs using mode 755 as modified by the umask.\n\t# This is like FreeBSD 'install' as of 1997-10-28.\n\tumask=`umask`\n\tcase $stripcmd.$umask in\n\t  # Optimize common cases.\n\t  *[2367][2367]) mkdir_umask=$umask;;\n\t  .*0[02][02] | .[02][02] | .[02]) mkdir_umask=22;;\n\n\t  *[0-7])\n\t    mkdir_umask=`expr $umask + 22 \\\n\t      - $umask % 100 % 40 + $umask % 20 \\\n\t      - $umask % 10 % 4 + $umask % 2\n\t    `;;\n\t  *) mkdir_umask=$umask,go-w;;\n\tesac\n\n\t# With -d, create the new directory with the user-specified mode.\n\t# Otherwise, rely on $mkdir_umask.\n\tif test -n \"$dir_arg\"; then\n\t  mkdir_mode=-m$mode\n\telse\n\t  mkdir_mode=\n\tfi\n\n\tposix_mkdir=false\n\tcase $umask in\n\t  *[123567][0-7][0-7])\n\t    # POSIX mkdir -p sets u+wx bits regardless of umask, which\n\t    # is incompatible with FreeBSD 'install' when (umask & 300) != 0.\n\t    ;;\n\t  *)\n\t    tmpdir=${TMPDIR-/tmp}/ins$RANDOM-$$\n\t    trap 'ret=$?; rmdir \"$tmpdir/d\" \"$tmpdir\" 2>/dev/null; exit $ret' 0\n\n\t    if (umask $mkdir_umask &&\n\t\texec $mkdirprog $mkdir_mode -p -- \"$tmpdir/d\") >/dev/null 2>&1\n\t    then\n\t      if test -z \"$dir_arg\" || {\n\t\t   # Check for POSIX incompatibilities with -m.\n\t\t   # HP-UX 11.23 and IRIX 6.5 mkdir -m -p sets group- or\n\t\t   # other-writable bit of parent directory when it shouldn't.\n\t\t   # FreeBSD 6.1 mkdir -m -p sets mode of existing directory.\n\t\t   ls_ld_tmpdir=`ls -ld \"$tmpdir\"`\n\t\t   case $ls_ld_tmpdir in\n\t\t     d????-?r-*) different_mode=700;;\n\t\t     d????-?--*) different_mode=755;;\n\t\t     *) false;;\n\t\t   esac &&\n\t\t   $mkdirprog -m$different_mode -p -- \"$tmpdir\" && {\n\t\t     ls_ld_tmpdir_1=`ls -ld \"$tmpdir\"`\n\t\t     test \"$ls_ld_tmpdir\" = \"$ls_ld_tmpdir_1\"\n\t\t   }\n\t\t }\n\t      then posix_mkdir=:\n\t      fi\n\t      rmdir \"$tmpdir/d\" \"$tmpdir\"\n\t    else\n\t      # Remove any dirs left behind by ancient mkdir implementations.\n\t      rmdir ./$mkdir_mode ./-p ./-- 2>/dev/null\n\t    fi\n\t    trap '' 0;;\n\tesac;;\n    esac\n\n    if\n      $posix_mkdir && (\n\tumask $mkdir_umask &&\n\t$doit_exec $mkdirprog $mkdir_mode -p -- \"$dstdir\"\n      )\n    then :\n    else\n\n      # The umask is ridiculous, or mkdir does not conform to POSIX,\n      # or it failed possibly due to a race condition.  Create the\n      # directory the slow way, step by step, checking for races as we go.\n\n      case $dstdir in\n\t/*) prefix='/';;\n\t[-=\\(\\)!]*) prefix='./';;\n\t*)  prefix='';;\n      esac\n\n      eval \"$initialize_posix_glob\"\n\n      oIFS=$IFS\n      IFS=/\n      $posix_glob set -f\n      set fnord $dstdir\n      shift\n      $posix_glob set +f\n      IFS=$oIFS\n\n      prefixes=\n\n      for d\n      do\n\ttest X\"$d\" = X && continue\n\n\tprefix=$prefix$d\n\tif test -d \"$prefix\"; then\n\t  prefixes=\n\telse\n\t  if $posix_mkdir; then\n\t    (umask=$mkdir_umask &&\n\t     $doit_exec $mkdirprog $mkdir_mode -p -- \"$dstdir\") && break\n\t    # Don't fail if two instances are running concurrently.\n\t    test -d \"$prefix\" || exit 1\n\t  else\n\t    case $prefix in\n\t      *\\'*) qprefix=`echo \"$prefix\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"`;;\n\t      *) qprefix=$prefix;;\n\t    esac\n\t    prefixes=\"$prefixes '$qprefix'\"\n\t  fi\n\tfi\n\tprefix=$prefix/\n      done\n\n      if test -n \"$prefixes\"; then\n\t# Don't fail if two instances are running concurrently.\n\t(umask $mkdir_umask &&\n\t eval \"\\$doit_exec \\$mkdirprog $prefixes\") ||\n\t  test -d \"$dstdir\" || exit 1\n\tobsolete_mkdir_used=true\n      fi\n    fi\n  fi\n\n  if test -n \"$dir_arg\"; then\n    { test -z \"$chowncmd\" || $doit $chowncmd \"$dst\"; } &&\n    { test -z \"$chgrpcmd\" || $doit $chgrpcmd \"$dst\"; } &&\n    { test \"$obsolete_mkdir_used$chowncmd$chgrpcmd\" = false ||\n      test -z \"$chmodcmd\" || $doit $chmodcmd $mode \"$dst\"; } || exit 1\n  else\n\n    # Make a couple of temp file names in the proper directory.\n    dsttmp=$dstdir/_inst.$$_\n    rmtmp=$dstdir/_rm.$$_\n\n    # Trap to clean up those temp files at exit.\n    trap 'ret=$?; rm -f \"$dsttmp\" \"$rmtmp\" && exit $ret' 0\n\n    # Copy the file name to the temp name.\n    (umask $cp_umask && $doit_exec $cpprog \"$src\" \"$dsttmp\") &&\n\n    # and set any options; do chmod last to preserve setuid bits.\n    #\n    # If any of these fail, we abort the whole thing.  If we want to\n    # ignore errors from any of these, just make sure not to ignore\n    # errors from the above \"$doit $cpprog $src $dsttmp\" command.\n    #\n    { test -z \"$chowncmd\" || $doit $chowncmd \"$dsttmp\"; } &&\n    { test -z \"$chgrpcmd\" || $doit $chgrpcmd \"$dsttmp\"; } &&\n    { test -z \"$stripcmd\" || $doit $stripcmd \"$dsttmp\"; } &&\n    { test -z \"$chmodcmd\" || $doit $chmodcmd $mode \"$dsttmp\"; } &&\n\n    # If -C, don't bother to copy if it wouldn't change the file.\n    if $copy_on_change &&\n       old=`LC_ALL=C ls -dlL \"$dst\"\t2>/dev/null` &&\n       new=`LC_ALL=C ls -dlL \"$dsttmp\"\t2>/dev/null` &&\n\n       eval \"$initialize_posix_glob\" &&\n       $posix_glob set -f &&\n       set X $old && old=:$2:$4:$5:$6 &&\n       set X $new && new=:$2:$4:$5:$6 &&\n       $posix_glob set +f &&\n\n       test \"$old\" = \"$new\" &&\n       $cmpprog \"$dst\" \"$dsttmp\" >/dev/null 2>&1\n    then\n      rm -f \"$dsttmp\"\n    else\n      # Rename the file to the real destination.\n      $doit $mvcmd -f \"$dsttmp\" \"$dst\" 2>/dev/null ||\n\n      # The rename failed, perhaps because mv can't rename something else\n      # to itself, or perhaps because mv is so ancient that it does not\n      # support -f.\n      {\n\t# Now remove or move aside any old file at destination location.\n\t# We try this two ways since rm can't unlink itself on some\n\t# systems and the destination file might be busy for other\n\t# reasons.  In this case, the final cleanup might fail but the new\n\t# file should still install successfully.\n\t{\n\t  test ! -f \"$dst\" ||\n\t  $doit $rmcmd -f \"$dst\" 2>/dev/null ||\n\t  { $doit $mvcmd -f \"$dst\" \"$rmtmp\" 2>/dev/null &&\n\t    { $doit $rmcmd -f \"$rmtmp\" 2>/dev/null; :; }\n\t  } ||\n\t  { echo \"$0: cannot unlink or rename $dst\" >&2\n\t    (exit 1); exit 1\n\t  }\n\t} &&\n\n\t# Now rename the file to the real destination.\n\t$doit $mvcmd \"$dsttmp\" \"$dst\"\n      }\n    fi || exit 1\n\n    trap '' 0\n  fi\ndone\n\n# Local variables:\n# eval: (add-hook 'write-file-hooks 'time-stamp)\n# time-stamp-start: \"scriptversion=\"\n# time-stamp-format: \"%:y-%02m-%02d.%02H\"\n# time-stamp-time-zone: \"UTC\"\n# time-stamp-end: \"; # UTC\"\n# End:\n"
  },
  {
    "path": "cudd/build-aux/ltmain.sh",
    "content": "#! /usr/bin/env sh\n## DO NOT EDIT - This file generated from ./build-aux/ltmain.in\n##               by inline-source v2019-02-19.15\n\n# libtool (GNU libtool) 2.4.7\n# Provide generalized library-building support services.\n# Written by Gordon Matzigkeit <gord@gnu.ai.mit.edu>, 1996\n\n# Copyright (C) 1996-2019, 2021-2022 Free Software Foundation, Inc.\n# This is free software; see the source for copying conditions.  There is NO\n# warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\n# GNU Libtool is free software; you can redistribute it and/or modify\n# it under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 2 of the License, or\n# (at your option) any later version.\n#\n# As a special exception to the GNU General Public License,\n# if you distribute this file as part of a program or library that\n# is built using GNU Libtool, you may include this file under the\n# same distribution terms that you use for the rest of that program.\n#\n# GNU Libtool is distributed in the hope that it will be useful, but\n# WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\n# General Public License for more details.\n#\n# You should have received a copy of the GNU General Public License\n# along with this program.  If not, see <http://www.gnu.org/licenses/>.\n\n\nPROGRAM=libtool\nPACKAGE=libtool\nVERSION=2.4.7\npackage_revision=2.4.7\n\n\n## ------ ##\n## Usage. ##\n## ------ ##\n\n# Run './libtool --help' for help with using this script from the\n# command line.\n\n\n## ------------------------------- ##\n## User overridable command paths. ##\n## ------------------------------- ##\n\n# After configure completes, it has a better idea of some of the\n# shell tools we need than the defaults used by the functions shared\n# with bootstrap, so set those here where they can still be over-\n# ridden by the user, but otherwise take precedence.\n\n: ${AUTOCONF=\"autoconf\"}\n: ${AUTOMAKE=\"automake\"}\n\n\n## -------------------------- ##\n## Source external libraries. ##\n## -------------------------- ##\n\n# Much of our low-level functionality needs to be sourced from external\n# libraries, which are installed to $pkgauxdir.\n\n# Set a version string for this script.\nscriptversion=2019-02-19.15; # UTC\n\n# General shell script boiler plate, and helper functions.\n# Written by Gary V. Vaughan, 2004\n\n# This is free software.  There is NO warranty; not even for\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n#\n# Copyright (C) 2004-2019, 2021 Bootstrap Authors\n#\n# This file is dual licensed under the terms of the MIT license\n# <https://opensource.org/license/MIT>, and GPL version 2 or later\n# <http://www.gnu.org/licenses/gpl-2.0.html>.  You must apply one of\n# these licenses when using or redistributing this software or any of\n# the files within it.  See the URLs above, or the file `LICENSE`\n# included in the Bootstrap distribution for the full license texts.\n\n# Please report bugs or propose patches to:\n# <https://github.com/gnulib-modules/bootstrap/issues>\n\n\n## ------ ##\n## Usage. ##\n## ------ ##\n\n# Evaluate this file near the top of your script to gain access to\n# the functions and variables defined here:\n#\n#   . `echo \"$0\" | ${SED-sed} 's|[^/]*$||'`/build-aux/funclib.sh\n#\n# If you need to override any of the default environment variable\n# settings, do that before evaluating this file.\n\n\n## -------------------- ##\n## Shell normalisation. ##\n## -------------------- ##\n\n# Some shells need a little help to be as Bourne compatible as possible.\n# Before doing anything else, make sure all that help has been provided!\n\nDUALCASE=1; export DUALCASE # for MKS sh\nif test -n \"${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then :\n  emulate sh\n  NULLCMD=:\n  # Pre-4.2 versions of Zsh do word splitting on ${1+\"$@\"}, which\n  # is contrary to our usage.  Disable this feature.\n  alias -g '${1+\"$@\"}'='\"$@\"'\n  setopt NO_GLOB_SUBST\nelse\n  case `(set -o) 2>/dev/null` in *posix*) set -o posix ;; esac\nfi\n\n# NLS nuisances: We save the old values in case they are required later.\n_G_user_locale=\n_G_safe_locale=\nfor _G_var in LANG LANGUAGE LC_ALL LC_CTYPE LC_COLLATE LC_MESSAGES\ndo\n  eval \"if test set = \\\"\\${$_G_var+set}\\\"; then\n          save_$_G_var=\\$$_G_var\n          $_G_var=C\n\t  export $_G_var\n\t  _G_user_locale=\\\"$_G_var=\\\\\\$save_\\$_G_var; \\$_G_user_locale\\\"\n\t  _G_safe_locale=\\\"$_G_var=C; \\$_G_safe_locale\\\"\n\tfi\"\ndone\n# These NLS vars are set unconditionally (bootstrap issue #24).  Unset those\n# in case the environment reset is needed later and the $save_* variant is not\n# defined (see the code above).\nLC_ALL=C\nLANGUAGE=C\nexport LANGUAGE LC_ALL\n\n# Make sure IFS has a sensible default\nsp=' '\nnl='\n'\nIFS=\"$sp\t$nl\"\n\n# There are apparently some retarded systems that use ';' as a PATH separator!\nif test \"${PATH_SEPARATOR+set}\" != set; then\n  PATH_SEPARATOR=:\n  (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {\n    (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||\n      PATH_SEPARATOR=';'\n  }\nfi\n\n\n# func_unset VAR\n# --------------\n# Portably unset VAR.\n# In some shells, an 'unset VAR' statement leaves a non-zero return\n# status if VAR is already unset, which might be problematic if the\n# statement is used at the end of a function (thus poisoning its return\n# value) or when 'set -e' is active (causing even a spurious abort of\n# the script in this case).\nfunc_unset ()\n{\n    { eval $1=; (eval unset $1) >/dev/null 2>&1 && eval unset $1 || : ; }\n}\n\n\n# Make sure CDPATH doesn't cause `cd` commands to output the target dir.\nfunc_unset CDPATH\n\n# Make sure ${,E,F}GREP behave sanely.\nfunc_unset GREP_OPTIONS\n\n\n## ------------------------- ##\n## Locate command utilities. ##\n## ------------------------- ##\n\n\n# func_executable_p FILE\n# ----------------------\n# Check that FILE is an executable regular file.\nfunc_executable_p ()\n{\n    test -f \"$1\" && test -x \"$1\"\n}\n\n\n# func_path_progs PROGS_LIST CHECK_FUNC [PATH]\n# --------------------------------------------\n# Search for either a program that responds to --version with output\n# containing \"GNU\", or else returned by CHECK_FUNC otherwise, by\n# trying all the directories in PATH with each of the elements of\n# PROGS_LIST.\n#\n# CHECK_FUNC should accept the path to a candidate program, and\n# set $func_check_prog_result if it truncates its output less than\n# $_G_path_prog_max characters.\nfunc_path_progs ()\n{\n    _G_progs_list=$1\n    _G_check_func=$2\n    _G_PATH=${3-\"$PATH\"}\n\n    _G_path_prog_max=0\n    _G_path_prog_found=false\n    _G_save_IFS=$IFS; IFS=${PATH_SEPARATOR-:}\n    for _G_dir in $_G_PATH; do\n      IFS=$_G_save_IFS\n      test -z \"$_G_dir\" && _G_dir=.\n      for _G_prog_name in $_G_progs_list; do\n        for _exeext in '' .EXE; do\n          _G_path_prog=$_G_dir/$_G_prog_name$_exeext\n          func_executable_p \"$_G_path_prog\" || continue\n          case `\"$_G_path_prog\" --version 2>&1` in\n            *GNU*) func_path_progs_result=$_G_path_prog _G_path_prog_found=: ;;\n            *)     $_G_check_func $_G_path_prog\n\t\t   func_path_progs_result=$func_check_prog_result\n\t\t   ;;\n          esac\n          $_G_path_prog_found && break 3\n        done\n      done\n    done\n    IFS=$_G_save_IFS\n    test -z \"$func_path_progs_result\" && {\n      echo \"no acceptable sed could be found in \\$PATH\" >&2\n      exit 1\n    }\n}\n\n\n# We want to be able to use the functions in this file before configure\n# has figured out where the best binaries are kept, which means we have\n# to search for them ourselves - except when the results are already set\n# where we skip the searches.\n\n# Unless the user overrides by setting SED, search the path for either GNU\n# sed, or the sed that truncates its output the least.\ntest -z \"$SED\" && {\n  _G_sed_script=s/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb/\n  for _G_i in 1 2 3 4 5 6 7; do\n    _G_sed_script=$_G_sed_script$nl$_G_sed_script\n  done\n  echo \"$_G_sed_script\" 2>/dev/null | sed 99q >conftest.sed\n  _G_sed_script=\n\n  func_check_prog_sed ()\n  {\n    _G_path_prog=$1\n\n    _G_count=0\n    printf 0123456789 >conftest.in\n    while :\n    do\n      cat conftest.in conftest.in >conftest.tmp\n      mv conftest.tmp conftest.in\n      cp conftest.in conftest.nl\n      echo '' >> conftest.nl\n      \"$_G_path_prog\" -f conftest.sed <conftest.nl >conftest.out 2>/dev/null || break\n      diff conftest.out conftest.nl >/dev/null 2>&1 || break\n      _G_count=`expr $_G_count + 1`\n      if test \"$_G_count\" -gt \"$_G_path_prog_max\"; then\n        # Best one so far, save it but keep looking for a better one\n        func_check_prog_result=$_G_path_prog\n        _G_path_prog_max=$_G_count\n      fi\n      # 10*(2^10) chars as input seems more than enough\n      test 10 -lt \"$_G_count\" && break\n    done\n    rm -f conftest.in conftest.tmp conftest.nl conftest.out\n  }\n\n  func_path_progs \"sed gsed\" func_check_prog_sed \"$PATH:/usr/xpg4/bin\"\n  rm -f conftest.sed\n  SED=$func_path_progs_result\n}\n\n\n# Unless the user overrides by setting GREP, search the path for either GNU\n# grep, or the grep that truncates its output the least.\ntest -z \"$GREP\" && {\n  func_check_prog_grep ()\n  {\n    _G_path_prog=$1\n\n    _G_count=0\n    _G_path_prog_max=0\n    printf 0123456789 >conftest.in\n    while :\n    do\n      cat conftest.in conftest.in >conftest.tmp\n      mv conftest.tmp conftest.in\n      cp conftest.in conftest.nl\n      echo 'GREP' >> conftest.nl\n      \"$_G_path_prog\" -e 'GREP$' -e '-(cannot match)-' <conftest.nl >conftest.out 2>/dev/null || break\n      diff conftest.out conftest.nl >/dev/null 2>&1 || break\n      _G_count=`expr $_G_count + 1`\n      if test \"$_G_count\" -gt \"$_G_path_prog_max\"; then\n        # Best one so far, save it but keep looking for a better one\n        func_check_prog_result=$_G_path_prog\n        _G_path_prog_max=$_G_count\n      fi\n      # 10*(2^10) chars as input seems more than enough\n      test 10 -lt \"$_G_count\" && break\n    done\n    rm -f conftest.in conftest.tmp conftest.nl conftest.out\n  }\n\n  func_path_progs \"grep ggrep\" func_check_prog_grep \"$PATH:/usr/xpg4/bin\"\n  GREP=$func_path_progs_result\n}\n\n\n## ------------------------------- ##\n## User overridable command paths. ##\n## ------------------------------- ##\n\n# All uppercase variable names are used for environment variables.  These\n# variables can be overridden by the user before calling a script that\n# uses them if a suitable command of that name is not already available\n# in the command search PATH.\n\n: ${CP=\"cp -f\"}\n: ${ECHO=\"printf %s\\n\"}\n: ${EGREP=\"$GREP -E\"}\n: ${FGREP=\"$GREP -F\"}\n: ${LN_S=\"ln -s\"}\n: ${MAKE=\"make\"}\n: ${MKDIR=\"mkdir\"}\n: ${MV=\"mv -f\"}\n: ${RM=\"rm -f\"}\n: ${SHELL=\"${CONFIG_SHELL-/bin/sh}\"}\n\n\n## -------------------- ##\n## Useful sed snippets. ##\n## -------------------- ##\n\nsed_dirname='s|/[^/]*$||'\nsed_basename='s|^.*/||'\n\n# Sed substitution that helps us do robust quoting.  It backslashifies\n# metacharacters that are still active within double-quoted strings.\nsed_quote_subst='s|\\([`\"$\\\\]\\)|\\\\\\1|g'\n\n# Same as above, but do not quote variable references.\nsed_double_quote_subst='s/\\([\"`\\\\]\\)/\\\\\\1/g'\n\n# Sed substitution that turns a string into a regex matching for the\n# string literally.\nsed_make_literal_regex='s|[].[^$\\\\*\\/]|\\\\&|g'\n\n# Sed substitution that converts a w32 file name or path\n# that contains forward slashes, into one that contains\n# (escaped) backslashes.  A very naive implementation.\nsed_naive_backslashify='s|\\\\\\\\*|\\\\|g;s|/|\\\\|g;s|\\\\|\\\\\\\\|g'\n\n# Re-'\\' parameter expansions in output of sed_double_quote_subst that\n# were '\\'-ed in input to the same.  If an odd number of '\\' preceded a\n# '$' in input to sed_double_quote_subst, that '$' was protected from\n# expansion.  Since each input '\\' is now two '\\'s, look for any number\n# of runs of four '\\'s followed by two '\\'s and then a '$'.  '\\' that '$'.\n_G_bs='\\\\'\n_G_bs2='\\\\\\\\'\n_G_bs4='\\\\\\\\\\\\\\\\'\n_G_dollar='\\$'\nsed_double_backslash=\"\\\n  s/$_G_bs4/&\\\\\n/g\n  s/^$_G_bs2$_G_dollar/$_G_bs&/\n  s/\\\\([^$_G_bs]\\\\)$_G_bs2$_G_dollar/\\\\1$_G_bs2$_G_bs$_G_dollar/g\n  s/\\n//g\"\n\n# require_check_ifs_backslash\n# ---------------------------\n# Check if we can use backslash as IFS='\\' separator, and set\n# $check_ifs_backshlash_broken to ':' or 'false'.\nrequire_check_ifs_backslash=func_require_check_ifs_backslash\nfunc_require_check_ifs_backslash ()\n{\n  _G_save_IFS=$IFS\n  IFS='\\'\n  _G_check_ifs_backshlash='a\\\\b'\n  for _G_i in $_G_check_ifs_backshlash\n  do\n  case $_G_i in\n  a)\n    check_ifs_backshlash_broken=false\n    ;;\n  '')\n    break\n    ;;\n  *)\n    check_ifs_backshlash_broken=:\n    break\n    ;;\n  esac\n  done\n  IFS=$_G_save_IFS\n  require_check_ifs_backslash=:\n}\n\n\n## ----------------- ##\n## Global variables. ##\n## ----------------- ##\n\n# Except for the global variables explicitly listed below, the following\n# functions in the '^func_' namespace, and the '^require_' namespace\n# variables initialised in the 'Resource management' section, sourcing\n# this file will not pollute your global namespace with anything\n# else. There's no portable way to scope variables in Bourne shell\n# though, so actually running these functions will sometimes place\n# results into a variable named after the function, and often use\n# temporary variables in the '^_G_' namespace. If you are careful to\n# avoid using those namespaces casually in your sourcing script, things\n# should continue to work as you expect. And, of course, you can freely\n# overwrite any of the functions or variables defined here before\n# calling anything to customize them.\n\nEXIT_SUCCESS=0\nEXIT_FAILURE=1\nEXIT_MISMATCH=63  # $? = 63 is used to indicate version mismatch to missing.\nEXIT_SKIP=77\t  # $? = 77 is used to indicate a skipped test to automake.\n\n# Allow overriding, eg assuming that you follow the convention of\n# putting '$debug_cmd' at the start of all your functions, you can get\n# bash to show function call trace with:\n#\n#    debug_cmd='eval echo \"${FUNCNAME[0]} $*\" >&2' bash your-script-name\ndebug_cmd=${debug_cmd-\":\"}\nexit_cmd=:\n\n# By convention, finish your script with:\n#\n#    exit $exit_status\n#\n# so that you can set exit_status to non-zero if you want to indicate\n# something went wrong during execution without actually bailing out at\n# the point of failure.\nexit_status=$EXIT_SUCCESS\n\n# Work around backward compatibility issue on IRIX 6.5. On IRIX 6.4+, sh\n# is ksh but when the shell is invoked as \"sh\" and the current value of\n# the _XPG environment variable is not equal to 1 (one), the special\n# positional parameter $0, within a function call, is the name of the\n# function.\nprogpath=$0\n\n# The name of this program.\nprogname=`$ECHO \"$progpath\" |$SED \"$sed_basename\"`\n\n# Make sure we have an absolute progpath for reexecution:\ncase $progpath in\n  [\\\\/]*|[A-Za-z]:\\\\*) ;;\n  *[\\\\/]*)\n     progdir=`$ECHO \"$progpath\" |$SED \"$sed_dirname\"`\n     progdir=`cd \"$progdir\" && pwd`\n     progpath=$progdir/$progname\n     ;;\n  *)\n     _G_IFS=$IFS\n     IFS=${PATH_SEPARATOR-:}\n     for progdir in $PATH; do\n       IFS=$_G_IFS\n       test -x \"$progdir/$progname\" && break\n     done\n     IFS=$_G_IFS\n     test -n \"$progdir\" || progdir=`pwd`\n     progpath=$progdir/$progname\n     ;;\nesac\n\n\n## ----------------- ##\n## Standard options. ##\n## ----------------- ##\n\n# The following options affect the operation of the functions defined\n# below, and should be set appropriately depending on run-time para-\n# meters passed on the command line.\n\nopt_dry_run=false\nopt_quiet=false\nopt_verbose=false\n\n# Categories 'all' and 'none' are always available.  Append any others\n# you will pass as the first argument to func_warning from your own\n# code.\nwarning_categories=\n\n# By default, display warnings according to 'opt_warning_types'.  Set\n# 'warning_func'  to ':' to elide all warnings, or func_fatal_error to\n# treat the next displayed warning as a fatal error.\nwarning_func=func_warn_and_continue\n\n# Set to 'all' to display all warnings, 'none' to suppress all\n# warnings, or a space delimited list of some subset of\n# 'warning_categories' to display only the listed warnings.\nopt_warning_types=all\n\n\n## -------------------- ##\n## Resource management. ##\n## -------------------- ##\n\n# This section contains definitions for functions that each ensure a\n# particular resource (a file, or a non-empty configuration variable for\n# example) is available, and if appropriate to extract default values\n# from pertinent package files. Call them using their associated\n# 'require_*' variable to ensure that they are executed, at most, once.\n#\n# It's entirely deliberate that calling these functions can set\n# variables that don't obey the namespace limitations obeyed by the rest\n# of this file, in order that that they be as useful as possible to\n# callers.\n\n\n# require_term_colors\n# -------------------\n# Allow display of bold text on terminals that support it.\nrequire_term_colors=func_require_term_colors\nfunc_require_term_colors ()\n{\n    $debug_cmd\n\n    test -t 1 && {\n      # COLORTERM and USE_ANSI_COLORS environment variables take\n      # precedence, because most terminfo databases neglect to describe\n      # whether color sequences are supported.\n      test -n \"${COLORTERM+set}\" && : ${USE_ANSI_COLORS=\"1\"}\n\n      if test 1 = \"$USE_ANSI_COLORS\"; then\n        # Standard ANSI escape sequences\n        tc_reset='\u001b[0m'\n        tc_bold='\u001b[1m';   tc_standout='\u001b[7m'\n        tc_red='\u001b[31m';   tc_green='\u001b[32m'\n        tc_blue='\u001b[34m';  tc_cyan='\u001b[36m'\n      else\n        # Otherwise trust the terminfo database after all.\n        test -n \"`tput sgr0 2>/dev/null`\" && {\n          tc_reset=`tput sgr0`\n          test -n \"`tput bold 2>/dev/null`\" && tc_bold=`tput bold`\n          tc_standout=$tc_bold\n          test -n \"`tput smso 2>/dev/null`\" && tc_standout=`tput smso`\n          test -n \"`tput setaf 1 2>/dev/null`\" && tc_red=`tput setaf 1`\n          test -n \"`tput setaf 2 2>/dev/null`\" && tc_green=`tput setaf 2`\n          test -n \"`tput setaf 4 2>/dev/null`\" && tc_blue=`tput setaf 4`\n          test -n \"`tput setaf 5 2>/dev/null`\" && tc_cyan=`tput setaf 5`\n        }\n      fi\n    }\n\n    require_term_colors=:\n}\n\n\n## ----------------- ##\n## Function library. ##\n## ----------------- ##\n\n# This section contains a variety of useful functions to call in your\n# scripts. Take note of the portable wrappers for features provided by\n# some modern shells, which will fall back to slower equivalents on\n# less featureful shells.\n\n\n# func_append VAR VALUE\n# ---------------------\n# Append VALUE onto the existing contents of VAR.\n\n  # We should try to minimise forks, especially on Windows where they are\n  # unreasonably slow, so skip the feature probes when bash or zsh are\n  # being used:\n  if test set = \"${BASH_VERSION+set}${ZSH_VERSION+set}\"; then\n    : ${_G_HAVE_ARITH_OP=\"yes\"}\n    : ${_G_HAVE_XSI_OPS=\"yes\"}\n    # The += operator was introduced in bash 3.1\n    case $BASH_VERSION in\n      [12].* | 3.0 | 3.0*) ;;\n      *)\n        : ${_G_HAVE_PLUSEQ_OP=\"yes\"}\n        ;;\n    esac\n  fi\n\n  # _G_HAVE_PLUSEQ_OP\n  # Can be empty, in which case the shell is probed, \"yes\" if += is\n  # useable or anything else if it does not work.\n  test -z \"$_G_HAVE_PLUSEQ_OP\" \\\n    && (eval 'x=a; x+=\" b\"; test \"a b\" = \"$x\"') 2>/dev/null \\\n    && _G_HAVE_PLUSEQ_OP=yes\n\nif test yes = \"$_G_HAVE_PLUSEQ_OP\"\nthen\n  # This is an XSI compatible shell, allowing a faster implementation...\n  eval 'func_append ()\n  {\n    $debug_cmd\n\n    eval \"$1+=\\$2\"\n  }'\nelse\n  # ...otherwise fall back to using expr, which is often a shell builtin.\n  func_append ()\n  {\n    $debug_cmd\n\n    eval \"$1=\\$$1\\$2\"\n  }\nfi\n\n\n# func_append_quoted VAR VALUE\n# ----------------------------\n# Quote VALUE and append to the end of shell variable VAR, separated\n# by a space.\nif test yes = \"$_G_HAVE_PLUSEQ_OP\"; then\n  eval 'func_append_quoted ()\n  {\n    $debug_cmd\n\n    func_quote_arg pretty \"$2\"\n    eval \"$1+=\\\\ \\$func_quote_arg_result\"\n  }'\nelse\n  func_append_quoted ()\n  {\n    $debug_cmd\n\n    func_quote_arg pretty \"$2\"\n    eval \"$1=\\$$1\\\\ \\$func_quote_arg_result\"\n  }\nfi\n\n\n# func_append_uniq VAR VALUE\n# --------------------------\n# Append unique VALUE onto the existing contents of VAR, assuming\n# entries are delimited by the first character of VALUE.  For example:\n#\n#   func_append_uniq options \" --another-option option-argument\"\n#\n# will only append to $options if \" --another-option option-argument \"\n# is not already present somewhere in $options already (note spaces at\n# each end implied by leading space in second argument).\nfunc_append_uniq ()\n{\n    $debug_cmd\n\n    eval _G_current_value='`$ECHO $'$1'`'\n    _G_delim=`expr \"$2\" : '\\(.\\)'`\n\n    case $_G_delim$_G_current_value$_G_delim in\n      *\"$2$_G_delim\"*) ;;\n      *) func_append \"$@\" ;;\n    esac\n}\n\n\n# func_arith TERM...\n# ------------------\n# Set func_arith_result to the result of evaluating TERMs.\n  test -z \"$_G_HAVE_ARITH_OP\" \\\n    && (eval 'test 2 = $(( 1 + 1 ))') 2>/dev/null \\\n    && _G_HAVE_ARITH_OP=yes\n\nif test yes = \"$_G_HAVE_ARITH_OP\"; then\n  eval 'func_arith ()\n  {\n    $debug_cmd\n\n    func_arith_result=$(( $* ))\n  }'\nelse\n  func_arith ()\n  {\n    $debug_cmd\n\n    func_arith_result=`expr \"$@\"`\n  }\nfi\n\n\n# func_basename FILE\n# ------------------\n# Set func_basename_result to FILE with everything up to and including\n# the last / stripped.\nif test yes = \"$_G_HAVE_XSI_OPS\"; then\n  # If this shell supports suffix pattern removal, then use it to avoid\n  # forking. Hide the definitions single quotes in case the shell chokes\n  # on unsupported syntax...\n  _b='func_basename_result=${1##*/}'\n  _d='case $1 in\n        */*) func_dirname_result=${1%/*}$2 ;;\n        *  ) func_dirname_result=$3        ;;\n      esac'\n\nelse\n  # ...otherwise fall back to using sed.\n  _b='func_basename_result=`$ECHO \"$1\" |$SED \"$sed_basename\"`'\n  _d='func_dirname_result=`$ECHO \"$1\"  |$SED \"$sed_dirname\"`\n      if test \"X$func_dirname_result\" = \"X$1\"; then\n        func_dirname_result=$3\n      else\n        func_append func_dirname_result \"$2\"\n      fi'\nfi\n\neval 'func_basename ()\n{\n    $debug_cmd\n\n    '\"$_b\"'\n}'\n\n\n# func_dirname FILE APPEND NONDIR_REPLACEMENT\n# -------------------------------------------\n# Compute the dirname of FILE.  If nonempty, add APPEND to the result,\n# otherwise set result to NONDIR_REPLACEMENT.\neval 'func_dirname ()\n{\n    $debug_cmd\n\n    '\"$_d\"'\n}'\n\n\n# func_dirname_and_basename FILE APPEND NONDIR_REPLACEMENT\n# --------------------------------------------------------\n# Perform func_basename and func_dirname in a single function\n# call:\n#   dirname:  Compute the dirname of FILE.  If nonempty,\n#             add APPEND to the result, otherwise set result\n#             to NONDIR_REPLACEMENT.\n#             value returned in \"$func_dirname_result\"\n#   basename: Compute filename of FILE.\n#             value retuned in \"$func_basename_result\"\n# For efficiency, we do not delegate to the functions above but instead\n# duplicate the functionality here.\neval 'func_dirname_and_basename ()\n{\n    $debug_cmd\n\n    '\"$_b\"'\n    '\"$_d\"'\n}'\n\n\n# func_echo ARG...\n# ----------------\n# Echo program name prefixed message.\nfunc_echo ()\n{\n    $debug_cmd\n\n    _G_message=$*\n\n    func_echo_IFS=$IFS\n    IFS=$nl\n    for _G_line in $_G_message; do\n      IFS=$func_echo_IFS\n      $ECHO \"$progname: $_G_line\"\n    done\n    IFS=$func_echo_IFS\n}\n\n\n# func_echo_all ARG...\n# --------------------\n# Invoke $ECHO with all args, space-separated.\nfunc_echo_all ()\n{\n    $ECHO \"$*\"\n}\n\n\n# func_echo_infix_1 INFIX ARG...\n# ------------------------------\n# Echo program name, followed by INFIX on the first line, with any\n# additional lines not showing INFIX.\nfunc_echo_infix_1 ()\n{\n    $debug_cmd\n\n    $require_term_colors\n\n    _G_infix=$1; shift\n    _G_indent=$_G_infix\n    _G_prefix=\"$progname: $_G_infix: \"\n    _G_message=$*\n\n    # Strip color escape sequences before counting printable length\n    for _G_tc in \"$tc_reset\" \"$tc_bold\" \"$tc_standout\" \"$tc_red\" \"$tc_green\" \"$tc_blue\" \"$tc_cyan\"\n    do\n      test -n \"$_G_tc\" && {\n        _G_esc_tc=`$ECHO \"$_G_tc\" | $SED \"$sed_make_literal_regex\"`\n        _G_indent=`$ECHO \"$_G_indent\" | $SED \"s|$_G_esc_tc||g\"`\n      }\n    done\n    _G_indent=\"$progname: \"`echo \"$_G_indent\" | $SED 's|.| |g'`\"  \" ## exclude from sc_prohibit_nested_quotes\n\n    func_echo_infix_1_IFS=$IFS\n    IFS=$nl\n    for _G_line in $_G_message; do\n      IFS=$func_echo_infix_1_IFS\n      $ECHO \"$_G_prefix$tc_bold$_G_line$tc_reset\" >&2\n      _G_prefix=$_G_indent\n    done\n    IFS=$func_echo_infix_1_IFS\n}\n\n\n# func_error ARG...\n# -----------------\n# Echo program name prefixed message to standard error.\nfunc_error ()\n{\n    $debug_cmd\n\n    $require_term_colors\n\n    func_echo_infix_1 \"  $tc_standout${tc_red}error$tc_reset\" \"$*\" >&2\n}\n\n\n# func_fatal_error ARG...\n# -----------------------\n# Echo program name prefixed message to standard error, and exit.\nfunc_fatal_error ()\n{\n    $debug_cmd\n\n    func_error \"$*\"\n    exit $EXIT_FAILURE\n}\n\n\n# func_grep EXPRESSION FILENAME\n# -----------------------------\n# Check whether EXPRESSION matches any line of FILENAME, without output.\nfunc_grep ()\n{\n    $debug_cmd\n\n    $GREP \"$1\" \"$2\" >/dev/null 2>&1\n}\n\n\n# func_len STRING\n# ---------------\n# Set func_len_result to the length of STRING. STRING may not\n# start with a hyphen.\n  test -z \"$_G_HAVE_XSI_OPS\" \\\n    && (eval 'x=a/b/c;\n      test 5aa/bb/cc = \"${#x}${x%%/*}${x%/*}${x#*/}${x##*/}\"') 2>/dev/null \\\n    && _G_HAVE_XSI_OPS=yes\n\nif test yes = \"$_G_HAVE_XSI_OPS\"; then\n  eval 'func_len ()\n  {\n    $debug_cmd\n\n    func_len_result=${#1}\n  }'\nelse\n  func_len ()\n  {\n    $debug_cmd\n\n    func_len_result=`expr \"$1\" : \".*\" 2>/dev/null || echo $max_cmd_len`\n  }\nfi\n\n\n# func_mkdir_p DIRECTORY-PATH\n# ---------------------------\n# Make sure the entire path to DIRECTORY-PATH is available.\nfunc_mkdir_p ()\n{\n    $debug_cmd\n\n    _G_directory_path=$1\n    _G_dir_list=\n\n    if test -n \"$_G_directory_path\" && test : != \"$opt_dry_run\"; then\n\n      # Protect directory names starting with '-'\n      case $_G_directory_path in\n        -*) _G_directory_path=./$_G_directory_path ;;\n      esac\n\n      # While some portion of DIR does not yet exist...\n      while test ! -d \"$_G_directory_path\"; do\n        # ...make a list in topmost first order.  Use a colon delimited\n\t# list incase some portion of path contains whitespace.\n        _G_dir_list=$_G_directory_path:$_G_dir_list\n\n        # If the last portion added has no slash in it, the list is done\n        case $_G_directory_path in */*) ;; *) break ;; esac\n\n        # ...otherwise throw away the child directory and loop\n        _G_directory_path=`$ECHO \"$_G_directory_path\" | $SED -e \"$sed_dirname\"`\n      done\n      _G_dir_list=`$ECHO \"$_G_dir_list\" | $SED 's|:*$||'`\n\n      func_mkdir_p_IFS=$IFS; IFS=:\n      for _G_dir in $_G_dir_list; do\n\tIFS=$func_mkdir_p_IFS\n        # mkdir can fail with a 'File exist' error if two processes\n        # try to create one of the directories concurrently.  Don't\n        # stop in that case!\n        $MKDIR \"$_G_dir\" 2>/dev/null || :\n      done\n      IFS=$func_mkdir_p_IFS\n\n      # Bail out if we (or some other process) failed to create a directory.\n      test -d \"$_G_directory_path\" || \\\n        func_fatal_error \"Failed to create '$1'\"\n    fi\n}\n\n\n# func_mktempdir [BASENAME]\n# -------------------------\n# Make a temporary directory that won't clash with other running\n# libtool processes, and avoids race conditions if possible.  If\n# given, BASENAME is the basename for that directory.\nfunc_mktempdir ()\n{\n    $debug_cmd\n\n    _G_template=${TMPDIR-/tmp}/${1-$progname}\n\n    if test : = \"$opt_dry_run\"; then\n      # Return a directory name, but don't create it in dry-run mode\n      _G_tmpdir=$_G_template-$$\n    else\n\n      # If mktemp works, use that first and foremost\n      _G_tmpdir=`mktemp -d \"$_G_template-XXXXXXXX\" 2>/dev/null`\n\n      if test ! -d \"$_G_tmpdir\"; then\n        # Failing that, at least try and use $RANDOM to avoid a race\n        _G_tmpdir=$_G_template-${RANDOM-0}$$\n\n        func_mktempdir_umask=`umask`\n        umask 0077\n        $MKDIR \"$_G_tmpdir\"\n        umask $func_mktempdir_umask\n      fi\n\n      # If we're not in dry-run mode, bomb out on failure\n      test -d \"$_G_tmpdir\" || \\\n        func_fatal_error \"cannot create temporary directory '$_G_tmpdir'\"\n    fi\n\n    $ECHO \"$_G_tmpdir\"\n}\n\n\n# func_normal_abspath PATH\n# ------------------------\n# Remove doubled-up and trailing slashes, \".\" path components,\n# and cancel out any \"..\" path components in PATH after making\n# it an absolute path.\nfunc_normal_abspath ()\n{\n    $debug_cmd\n\n    # These SED scripts presuppose an absolute path with a trailing slash.\n    _G_pathcar='s|^/\\([^/]*\\).*$|\\1|'\n    _G_pathcdr='s|^/[^/]*||'\n    _G_removedotparts=':dotsl\n\t\ts|/\\./|/|g\n\t\tt dotsl\n\t\ts|/\\.$|/|'\n    _G_collapseslashes='s|/\\{1,\\}|/|g'\n    _G_finalslash='s|/*$|/|'\n\n    # Start from root dir and reassemble the path.\n    func_normal_abspath_result=\n    func_normal_abspath_tpath=$1\n    func_normal_abspath_altnamespace=\n    case $func_normal_abspath_tpath in\n      \"\")\n        # Empty path, that just means $cwd.\n        func_stripname '' '/' \"`pwd`\"\n        func_normal_abspath_result=$func_stripname_result\n        return\n        ;;\n      # The next three entries are used to spot a run of precisely\n      # two leading slashes without using negated character classes;\n      # we take advantage of case's first-match behaviour.\n      ///*)\n        # Unusual form of absolute path, do nothing.\n        ;;\n      //*)\n        # Not necessarily an ordinary path; POSIX reserves leading '//'\n        # and for example Cygwin uses it to access remote file shares\n        # over CIFS/SMB, so we conserve a leading double slash if found.\n        func_normal_abspath_altnamespace=/\n        ;;\n      /*)\n        # Absolute path, do nothing.\n        ;;\n      *)\n        # Relative path, prepend $cwd.\n        func_normal_abspath_tpath=`pwd`/$func_normal_abspath_tpath\n        ;;\n    esac\n\n    # Cancel out all the simple stuff to save iterations.  We also want\n    # the path to end with a slash for ease of parsing, so make sure\n    # there is one (and only one) here.\n    func_normal_abspath_tpath=`$ECHO \"$func_normal_abspath_tpath\" | $SED \\\n          -e \"$_G_removedotparts\" -e \"$_G_collapseslashes\" -e \"$_G_finalslash\"`\n    while :; do\n      # Processed it all yet?\n      if test / = \"$func_normal_abspath_tpath\"; then\n        # If we ascended to the root using \"..\" the result may be empty now.\n        if test -z \"$func_normal_abspath_result\"; then\n          func_normal_abspath_result=/\n        fi\n        break\n      fi\n      func_normal_abspath_tcomponent=`$ECHO \"$func_normal_abspath_tpath\" | $SED \\\n          -e \"$_G_pathcar\"`\n      func_normal_abspath_tpath=`$ECHO \"$func_normal_abspath_tpath\" | $SED \\\n          -e \"$_G_pathcdr\"`\n      # Figure out what to do with it\n      case $func_normal_abspath_tcomponent in\n        \"\")\n          # Trailing empty path component, ignore it.\n          ;;\n        ..)\n          # Parent dir; strip last assembled component from result.\n          func_dirname \"$func_normal_abspath_result\"\n          func_normal_abspath_result=$func_dirname_result\n          ;;\n        *)\n          # Actual path component, append it.\n          func_append func_normal_abspath_result \"/$func_normal_abspath_tcomponent\"\n          ;;\n      esac\n    done\n    # Restore leading double-slash if one was found on entry.\n    func_normal_abspath_result=$func_normal_abspath_altnamespace$func_normal_abspath_result\n}\n\n\n# func_notquiet ARG...\n# --------------------\n# Echo program name prefixed message only when not in quiet mode.\nfunc_notquiet ()\n{\n    $debug_cmd\n\n    $opt_quiet || func_echo ${1+\"$@\"}\n\n    # A bug in bash halts the script if the last line of a function\n    # fails when set -e is in force, so we need another command to\n    # work around that:\n    :\n}\n\n\n# func_relative_path SRCDIR DSTDIR\n# --------------------------------\n# Set func_relative_path_result to the relative path from SRCDIR to DSTDIR.\nfunc_relative_path ()\n{\n    $debug_cmd\n\n    func_relative_path_result=\n    func_normal_abspath \"$1\"\n    func_relative_path_tlibdir=$func_normal_abspath_result\n    func_normal_abspath \"$2\"\n    func_relative_path_tbindir=$func_normal_abspath_result\n\n    # Ascend the tree starting from libdir\n    while :; do\n      # check if we have found a prefix of bindir\n      case $func_relative_path_tbindir in\n        $func_relative_path_tlibdir)\n          # found an exact match\n          func_relative_path_tcancelled=\n          break\n          ;;\n        $func_relative_path_tlibdir*)\n          # found a matching prefix\n          func_stripname \"$func_relative_path_tlibdir\" '' \"$func_relative_path_tbindir\"\n          func_relative_path_tcancelled=$func_stripname_result\n          if test -z \"$func_relative_path_result\"; then\n            func_relative_path_result=.\n          fi\n          break\n          ;;\n        *)\n          func_dirname $func_relative_path_tlibdir\n          func_relative_path_tlibdir=$func_dirname_result\n          if test -z \"$func_relative_path_tlibdir\"; then\n            # Have to descend all the way to the root!\n            func_relative_path_result=../$func_relative_path_result\n            func_relative_path_tcancelled=$func_relative_path_tbindir\n            break\n          fi\n          func_relative_path_result=../$func_relative_path_result\n          ;;\n      esac\n    done\n\n    # Now calculate path; take care to avoid doubling-up slashes.\n    func_stripname '' '/' \"$func_relative_path_result\"\n    func_relative_path_result=$func_stripname_result\n    func_stripname '/' '/' \"$func_relative_path_tcancelled\"\n    if test -n \"$func_stripname_result\"; then\n      func_append func_relative_path_result \"/$func_stripname_result\"\n    fi\n\n    # Normalisation. If bindir is libdir, return '.' else relative path.\n    if test -n \"$func_relative_path_result\"; then\n      func_stripname './' '' \"$func_relative_path_result\"\n      func_relative_path_result=$func_stripname_result\n    fi\n\n    test -n \"$func_relative_path_result\" || func_relative_path_result=.\n\n    :\n}\n\n\n# func_quote_portable EVAL ARG\n# ----------------------------\n# Internal function to portably implement func_quote_arg.  Note that we still\n# keep attention to performance here so we as much as possible try to avoid\n# calling sed binary (so far O(N) complexity as long as func_append is O(1)).\nfunc_quote_portable ()\n{\n    $debug_cmd\n\n    $require_check_ifs_backslash\n\n    func_quote_portable_result=$2\n\n    # one-time-loop (easy break)\n    while true\n    do\n      if $1; then\n        func_quote_portable_result=`$ECHO \"$2\" | $SED \\\n          -e \"$sed_double_quote_subst\" -e \"$sed_double_backslash\"`\n        break\n      fi\n\n      # Quote for eval.\n      case $func_quote_portable_result in\n        *[\\\\\\`\\\"\\$]*)\n          # Fallback to sed for $func_check_bs_ifs_broken=:, or when the string\n          # contains the shell wildcard characters.\n          case $check_ifs_backshlash_broken$func_quote_portable_result in\n            :*|*[\\[\\*\\?]*)\n              func_quote_portable_result=`$ECHO \"$func_quote_portable_result\" \\\n                  | $SED \"$sed_quote_subst\"`\n              break\n              ;;\n          esac\n\n          func_quote_portable_old_IFS=$IFS\n          for _G_char in '\\' '`' '\"' '$'\n          do\n            # STATE($1) PREV($2) SEPARATOR($3)\n            set start \"\" \"\"\n            func_quote_portable_result=dummy\"$_G_char$func_quote_portable_result$_G_char\"dummy\n            IFS=$_G_char\n            for _G_part in $func_quote_portable_result\n            do\n              case $1 in\n              quote)\n                func_append func_quote_portable_result \"$3$2\"\n                set quote \"$_G_part\" \"\\\\$_G_char\"\n                ;;\n              start)\n                set first \"\" \"\"\n                func_quote_portable_result=\n                ;;\n              first)\n                set quote \"$_G_part\" \"\"\n                ;;\n              esac\n            done\n          done\n          IFS=$func_quote_portable_old_IFS\n          ;;\n        *) ;;\n      esac\n      break\n    done\n\n    func_quote_portable_unquoted_result=$func_quote_portable_result\n    case $func_quote_portable_result in\n      # double-quote args containing shell metacharacters to delay\n      # word splitting, command substitution and variable expansion\n      # for a subsequent eval.\n      # many bourne shells cannot handle close brackets correctly\n      # in scan sets, so we specify it separately.\n      *[\\[\\~\\#\\^\\&\\*\\(\\)\\{\\}\\|\\;\\<\\>\\?\\'\\ \\\t]*|*]*|\"\")\n        func_quote_portable_result=\\\"$func_quote_portable_result\\\"\n        ;;\n    esac\n}\n\n\n# func_quotefast_eval ARG\n# -----------------------\n# Quote one ARG (internal).  This is equivalent to 'func_quote_arg eval ARG',\n# but optimized for speed.  Result is stored in $func_quotefast_eval.\nif test xyes = `(x=; printf -v x %q yes; echo x\"$x\") 2>/dev/null`; then\n  printf -v _GL_test_printf_tilde %q '~'\n  if test '\\~' = \"$_GL_test_printf_tilde\"; then\n    func_quotefast_eval ()\n    {\n      printf -v func_quotefast_eval_result %q \"$1\"\n    }\n  else\n    # Broken older Bash implementations.  Make those faster too if possible.\n    func_quotefast_eval ()\n    {\n      case $1 in\n        '~'*)\n          func_quote_portable false \"$1\"\n          func_quotefast_eval_result=$func_quote_portable_result\n          ;;\n        *)\n          printf -v func_quotefast_eval_result %q \"$1\"\n          ;;\n      esac\n    }\n  fi\nelse\n  func_quotefast_eval ()\n  {\n    func_quote_portable false \"$1\"\n    func_quotefast_eval_result=$func_quote_portable_result\n  }\nfi\n\n\n# func_quote_arg MODEs ARG\n# ------------------------\n# Quote one ARG to be evaled later.  MODEs argument may contain zero or more\n# specifiers listed below separated by ',' character.  This function returns two\n# values:\n#   i) func_quote_arg_result\n#      double-quoted (when needed), suitable for a subsequent eval\n#  ii) func_quote_arg_unquoted_result\n#      has all characters that are still active within double\n#      quotes backslashified.  Available only if 'unquoted' is specified.\n#\n# Available modes:\n# ----------------\n# 'eval' (default)\n#       - escape shell special characters\n# 'expand'\n#       - the same as 'eval';  but do not quote variable references\n# 'pretty'\n#       - request aesthetic output, i.e. '\"a b\"' instead of 'a\\ b'.  This might\n#         be used later in func_quote to get output like: 'echo \"a b\"' instead\n#         of 'echo a\\ b'.  This is slower than default on some shells.\n# 'unquoted'\n#       - produce also $func_quote_arg_unquoted_result which does not contain\n#         wrapping double-quotes.\n#\n# Examples for 'func_quote_arg pretty,unquoted string':\n#\n#   string      | *_result              | *_unquoted_result\n#   ------------+-----------------------+-------------------\n#   \"           | \\\"                    | \\\"\n#   a b         | \"a b\"                 | a b\n#   \"a b\"       | \"\\\"a b\\\"\"             | \\\"a b\\\"\n#   *           | \"*\"                   | *\n#   z=\"${x-$y}\" | \"z=\\\"\\${x-\\$y}\\\"\"     | z=\\\"\\${x-\\$y}\\\"\n#\n# Examples for 'func_quote_arg pretty,unquoted,expand string':\n#\n#   string        |   *_result          |  *_unquoted_result\n#   --------------+---------------------+--------------------\n#   z=\"${x-$y}\"   | \"z=\\\"${x-$y}\\\"\"     | z=\\\"${x-$y}\\\"\nfunc_quote_arg ()\n{\n    _G_quote_expand=false\n    case ,$1, in\n      *,expand,*)\n        _G_quote_expand=:\n        ;;\n    esac\n\n    case ,$1, in\n      *,pretty,*|*,expand,*|*,unquoted,*)\n        func_quote_portable $_G_quote_expand \"$2\"\n        func_quote_arg_result=$func_quote_portable_result\n        func_quote_arg_unquoted_result=$func_quote_portable_unquoted_result\n        ;;\n      *)\n        # Faster quote-for-eval for some shells.\n        func_quotefast_eval \"$2\"\n        func_quote_arg_result=$func_quotefast_eval_result\n        ;;\n    esac\n}\n\n\n# func_quote MODEs ARGs...\n# ------------------------\n# Quote all ARGs to be evaled later and join them into single command.  See\n# func_quote_arg's description for more info.\nfunc_quote ()\n{\n    $debug_cmd\n    _G_func_quote_mode=$1 ; shift\n    func_quote_result=\n    while test 0 -lt $#; do\n      func_quote_arg \"$_G_func_quote_mode\" \"$1\"\n      if test -n \"$func_quote_result\"; then\n        func_append func_quote_result \" $func_quote_arg_result\"\n      else\n        func_append func_quote_result \"$func_quote_arg_result\"\n      fi\n      shift\n    done\n}\n\n\n# func_stripname PREFIX SUFFIX NAME\n# ---------------------------------\n# strip PREFIX and SUFFIX from NAME, and store in func_stripname_result.\n# PREFIX and SUFFIX must not contain globbing or regex special\n# characters, hashes, percent signs, but SUFFIX may contain a leading\n# dot (in which case that matches only a dot).\nif test yes = \"$_G_HAVE_XSI_OPS\"; then\n  eval 'func_stripname ()\n  {\n    $debug_cmd\n\n    # pdksh 5.2.14 does not do ${X%$Y} correctly if both X and Y are\n    # positional parameters, so assign one to ordinary variable first.\n    func_stripname_result=$3\n    func_stripname_result=${func_stripname_result#\"$1\"}\n    func_stripname_result=${func_stripname_result%\"$2\"}\n  }'\nelse\n  func_stripname ()\n  {\n    $debug_cmd\n\n    case $2 in\n      .*) func_stripname_result=`$ECHO \"$3\" | $SED -e \"s%^$1%%\" -e \"s%\\\\\\\\$2\\$%%\"`;;\n      *)  func_stripname_result=`$ECHO \"$3\" | $SED -e \"s%^$1%%\" -e \"s%$2\\$%%\"`;;\n    esac\n  }\nfi\n\n\n# func_show_eval CMD [FAIL_EXP]\n# -----------------------------\n# Unless opt_quiet is true, then output CMD.  Then, if opt_dryrun is\n# not true, evaluate CMD.  If the evaluation of CMD fails, and FAIL_EXP\n# is given, then evaluate it.\nfunc_show_eval ()\n{\n    $debug_cmd\n\n    _G_cmd=$1\n    _G_fail_exp=${2-':'}\n\n    func_quote_arg pretty,expand \"$_G_cmd\"\n    eval \"func_notquiet $func_quote_arg_result\"\n\n    $opt_dry_run || {\n      eval \"$_G_cmd\"\n      _G_status=$?\n      if test 0 -ne \"$_G_status\"; then\n\teval \"(exit $_G_status); $_G_fail_exp\"\n      fi\n    }\n}\n\n\n# func_show_eval_locale CMD [FAIL_EXP]\n# ------------------------------------\n# Unless opt_quiet is true, then output CMD.  Then, if opt_dryrun is\n# not true, evaluate CMD.  If the evaluation of CMD fails, and FAIL_EXP\n# is given, then evaluate it.  Use the saved locale for evaluation.\nfunc_show_eval_locale ()\n{\n    $debug_cmd\n\n    _G_cmd=$1\n    _G_fail_exp=${2-':'}\n\n    $opt_quiet || {\n      func_quote_arg expand,pretty \"$_G_cmd\"\n      eval \"func_echo $func_quote_arg_result\"\n    }\n\n    $opt_dry_run || {\n      eval \"$_G_user_locale\n\t    $_G_cmd\"\n      _G_status=$?\n      eval \"$_G_safe_locale\"\n      if test 0 -ne \"$_G_status\"; then\n\teval \"(exit $_G_status); $_G_fail_exp\"\n      fi\n    }\n}\n\n\n# func_tr_sh\n# ----------\n# Turn $1 into a string suitable for a shell variable name.\n# Result is stored in $func_tr_sh_result.  All characters\n# not in the set a-zA-Z0-9_ are replaced with '_'. Further,\n# if $1 begins with a digit, a '_' is prepended as well.\nfunc_tr_sh ()\n{\n    $debug_cmd\n\n    case $1 in\n    [0-9]* | *[!a-zA-Z0-9_]*)\n      func_tr_sh_result=`$ECHO \"$1\" | $SED -e 's/^\\([0-9]\\)/_\\1/' -e 's/[^a-zA-Z0-9_]/_/g'`\n      ;;\n    * )\n      func_tr_sh_result=$1\n      ;;\n    esac\n}\n\n\n# func_verbose ARG...\n# -------------------\n# Echo program name prefixed message in verbose mode only.\nfunc_verbose ()\n{\n    $debug_cmd\n\n    $opt_verbose && func_echo \"$*\"\n\n    :\n}\n\n\n# func_warn_and_continue ARG...\n# -----------------------------\n# Echo program name prefixed warning message to standard error.\nfunc_warn_and_continue ()\n{\n    $debug_cmd\n\n    $require_term_colors\n\n    func_echo_infix_1 \"${tc_red}warning$tc_reset\" \"$*\" >&2\n}\n\n\n# func_warning CATEGORY ARG...\n# ----------------------------\n# Echo program name prefixed warning message to standard error. Warning\n# messages can be filtered according to CATEGORY, where this function\n# elides messages where CATEGORY is not listed in the global variable\n# 'opt_warning_types'.\nfunc_warning ()\n{\n    $debug_cmd\n\n    # CATEGORY must be in the warning_categories list!\n    case \" $warning_categories \" in\n      *\" $1 \"*) ;;\n      *) func_internal_error \"invalid warning category '$1'\" ;;\n    esac\n\n    _G_category=$1\n    shift\n\n    case \" $opt_warning_types \" in\n      *\" $_G_category \"*) $warning_func ${1+\"$@\"} ;;\n    esac\n}\n\n\n# func_sort_ver VER1 VER2\n# -----------------------\n# 'sort -V' is not generally available.\n# Note this deviates from the version comparison in automake\n# in that it treats 1.5 < 1.5.0, and treats 1.4.4a < 1.4-p3a\n# but this should suffice as we won't be specifying old\n# version formats or redundant trailing .0 in bootstrap.conf.\n# If we did want full compatibility then we should probably\n# use m4_version_compare from autoconf.\nfunc_sort_ver ()\n{\n    $debug_cmd\n\n    printf '%s\\n%s\\n' \"$1\" \"$2\" \\\n      | sort -t. -k 1,1n -k 2,2n -k 3,3n -k 4,4n -k 5,5n -k 6,6n -k 7,7n -k 8,8n -k 9,9n\n}\n\n# func_lt_ver PREV CURR\n# ---------------------\n# Return true if PREV and CURR are in the correct order according to\n# func_sort_ver, otherwise false.  Use it like this:\n#\n#  func_lt_ver \"$prev_ver\" \"$proposed_ver\" || func_fatal_error \"...\"\nfunc_lt_ver ()\n{\n    $debug_cmd\n\n    test \"x$1\" = x`func_sort_ver \"$1\" \"$2\" | $SED 1q`\n}\n\n\n# Local variables:\n# mode: shell-script\n# sh-indentation: 2\n# eval: (add-hook 'before-save-hook 'time-stamp)\n# time-stamp-pattern: \"10/scriptversion=%:y-%02m-%02d.%02H; # UTC\"\n# time-stamp-time-zone: \"UTC\"\n# End:\n#! /bin/sh\n\n# A portable, pluggable option parser for Bourne shell.\n# Written by Gary V. Vaughan, 2010\n\n# This is free software.  There is NO warranty; not even for\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n#\n# Copyright (C) 2010-2019, 2021 Bootstrap Authors\n#\n# This file is dual licensed under the terms of the MIT license\n# <https://opensource.org/license/MIT>, and GPL version 2 or later\n# <http://www.gnu.org/licenses/gpl-2.0.html>.  You must apply one of\n# these licenses when using or redistributing this software or any of\n# the files within it.  See the URLs above, or the file `LICENSE`\n# included in the Bootstrap distribution for the full license texts.\n\n# Please report bugs or propose patches to:\n# <https://github.com/gnulib-modules/bootstrap/issues>\n\n# Set a version string for this script.\nscriptversion=2019-02-19.15; # UTC\n\n\n## ------ ##\n## Usage. ##\n## ------ ##\n\n# This file is a library for parsing options in your shell scripts along\n# with assorted other useful supporting features that you can make use\n# of too.\n#\n# For the simplest scripts you might need only:\n#\n#   #!/bin/sh\n#   . relative/path/to/funclib.sh\n#   . relative/path/to/options-parser\n#   scriptversion=1.0\n#   func_options ${1+\"$@\"}\n#   eval set dummy \"$func_options_result\"; shift\n#   ...rest of your script...\n#\n# In order for the '--version' option to work, you will need to have a\n# suitably formatted comment like the one at the top of this file\n# starting with '# Written by ' and ending with '# Copyright'.\n#\n# For '-h' and '--help' to work, you will also need a one line\n# description of your script's purpose in a comment directly above the\n# '# Written by ' line, like the one at the top of this file.\n#\n# The default options also support '--debug', which will turn on shell\n# execution tracing (see the comment above debug_cmd below for another\n# use), and '--verbose' and the func_verbose function to allow your script\n# to display verbose messages only when your user has specified\n# '--verbose'.\n#\n# After sourcing this file, you can plug in processing for additional\n# options by amending the variables from the 'Configuration' section\n# below, and following the instructions in the 'Option parsing'\n# section further down.\n\n## -------------- ##\n## Configuration. ##\n## -------------- ##\n\n# You should override these variables in your script after sourcing this\n# file so that they reflect the customisations you have added to the\n# option parser.\n\n# The usage line for option parsing errors and the start of '-h' and\n# '--help' output messages. You can embed shell variables for delayed\n# expansion at the time the message is displayed, but you will need to\n# quote other shell meta-characters carefully to prevent them being\n# expanded when the contents are evaled.\nusage='$progpath [OPTION]...'\n\n# Short help message in response to '-h' and '--help'.  Add to this or\n# override it after sourcing this library to reflect the full set of\n# options your script accepts.\nusage_message=\"\\\n       --debug        enable verbose shell tracing\n   -W, --warnings=CATEGORY\n                      report the warnings falling in CATEGORY [all]\n   -v, --verbose      verbosely report processing\n       --version      print version information and exit\n   -h, --help         print short or long help message and exit\n\"\n\n# Additional text appended to 'usage_message' in response to '--help'.\nlong_help_message=\"\nWarning categories include:\n       'all'          show all warnings\n       'none'         turn off all the warnings\n       'error'        warnings are treated as fatal errors\"\n\n# Help message printed before fatal option parsing errors.\nfatal_help=\"Try '\\$progname --help' for more information.\"\n\n\n\n## ------------------------- ##\n## Hook function management. ##\n## ------------------------- ##\n\n# This section contains functions for adding, removing, and running hooks\n# in the main code.  A hook is just a list of function names that can be\n# run in order later on.\n\n# func_hookable FUNC_NAME\n# -----------------------\n# Declare that FUNC_NAME will run hooks added with\n# 'func_add_hook FUNC_NAME ...'.\nfunc_hookable ()\n{\n    $debug_cmd\n\n    func_append hookable_fns \" $1\"\n}\n\n\n# func_add_hook FUNC_NAME HOOK_FUNC\n# ---------------------------------\n# Request that FUNC_NAME call HOOK_FUNC before it returns.  FUNC_NAME must\n# first have been declared \"hookable\" by a call to 'func_hookable'.\nfunc_add_hook ()\n{\n    $debug_cmd\n\n    case \" $hookable_fns \" in\n      *\" $1 \"*) ;;\n      *) func_fatal_error \"'$1' does not accept hook functions.\" ;;\n    esac\n\n    eval func_append ${1}_hooks '\" $2\"'\n}\n\n\n# func_remove_hook FUNC_NAME HOOK_FUNC\n# ------------------------------------\n# Remove HOOK_FUNC from the list of hook functions to be called by\n# FUNC_NAME.\nfunc_remove_hook ()\n{\n    $debug_cmd\n\n    eval ${1}_hooks='`$ECHO \"\\$'$1'_hooks\" |$SED \"s| '$2'||\"`'\n}\n\n\n# func_propagate_result FUNC_NAME_A FUNC_NAME_B\n# ---------------------------------------------\n# If the *_result variable of FUNC_NAME_A _is set_, assign its value to\n# *_result variable of FUNC_NAME_B.\nfunc_propagate_result ()\n{\n    $debug_cmd\n\n    func_propagate_result_result=:\n    if eval \"test \\\"\\${${1}_result+set}\\\" = set\"\n    then\n      eval \"${2}_result=\\$${1}_result\"\n    else\n      func_propagate_result_result=false\n    fi\n}\n\n\n# func_run_hooks FUNC_NAME [ARG]...\n# ---------------------------------\n# Run all hook functions registered to FUNC_NAME.\n# It's assumed that the list of hook functions contains nothing more\n# than a whitespace-delimited list of legal shell function names, and\n# no effort is wasted trying to catch shell meta-characters or preserve\n# whitespace.\nfunc_run_hooks ()\n{\n    $debug_cmd\n\n    case \" $hookable_fns \" in\n      *\" $1 \"*) ;;\n      *) func_fatal_error \"'$1' does not support hook functions.\" ;;\n    esac\n\n    eval _G_hook_fns=\\$$1_hooks; shift\n\n    for _G_hook in $_G_hook_fns; do\n      func_unset \"${_G_hook}_result\"\n      eval $_G_hook '${1+\"$@\"}'\n      func_propagate_result $_G_hook func_run_hooks\n      if $func_propagate_result_result; then\n        eval set dummy \"$func_run_hooks_result\"; shift\n      fi\n    done\n}\n\n\n\n## --------------- ##\n## Option parsing. ##\n## --------------- ##\n\n# In order to add your own option parsing hooks, you must accept the\n# full positional parameter list from your hook function.  You may remove\n# or edit any options that you action, and then pass back the remaining\n# unprocessed options in '<hooked_function_name>_result', escaped\n# suitably for 'eval'.\n#\n# The '<hooked_function_name>_result' variable is automatically unset\n# before your hook gets called; for best performance, only set the\n# *_result variable when necessary (i.e. don't call the 'func_quote'\n# function unnecessarily because it can be an expensive operation on some\n# machines).\n#\n# Like this:\n#\n#    my_options_prep ()\n#    {\n#        $debug_cmd\n#\n#        # Extend the existing usage message.\n#        usage_message=$usage_message'\n#      -s, --silent       don'\\''t print informational messages\n#    '\n#        # No change in '$@' (ignored completely by this hook).  Leave\n#        # my_options_prep_result variable intact.\n#    }\n#    func_add_hook func_options_prep my_options_prep\n#\n#\n#    my_silent_option ()\n#    {\n#        $debug_cmd\n#\n#        args_changed=false\n#\n#        # Note that, for efficiency, we parse as many options as we can\n#        # recognise in a loop before passing the remainder back to the\n#        # caller on the first unrecognised argument we encounter.\n#        while test $# -gt 0; do\n#          opt=$1; shift\n#          case $opt in\n#            --silent|-s) opt_silent=:\n#                         args_changed=:\n#                         ;;\n#            # Separate non-argument short options:\n#            -s*)         func_split_short_opt \"$_G_opt\"\n#                         set dummy \"$func_split_short_opt_name\" \\\n#                             \"-$func_split_short_opt_arg\" ${1+\"$@\"}\n#                         shift\n#                         args_changed=:\n#                         ;;\n#            *)           # Make sure the first unrecognised option \"$_G_opt\"\n#                         # is added back to \"$@\" in case we need it later,\n#                         # if $args_changed was set to 'true'.\n#                         set dummy \"$_G_opt\" ${1+\"$@\"}; shift; break ;;\n#          esac\n#        done\n#\n#        # Only call 'func_quote' here if we processed at least one argument.\n#        if $args_changed; then\n#          func_quote eval ${1+\"$@\"}\n#          my_silent_option_result=$func_quote_result\n#        fi\n#    }\n#    func_add_hook func_parse_options my_silent_option\n#\n#\n#    my_option_validation ()\n#    {\n#        $debug_cmd\n#\n#        $opt_silent && $opt_verbose && func_fatal_help \"\\\n#    '--silent' and '--verbose' options are mutually exclusive.\"\n#    }\n#    func_add_hook func_validate_options my_option_validation\n#\n# You'll also need to manually amend $usage_message to reflect the extra\n# options you parse.  It's preferable to append if you can, so that\n# multiple option parsing hooks can be added safely.\n\n\n# func_options_finish [ARG]...\n# ----------------------------\n# Finishing the option parse loop (call 'func_options' hooks ATM).\nfunc_options_finish ()\n{\n    $debug_cmd\n\n    func_run_hooks func_options ${1+\"$@\"}\n    func_propagate_result func_run_hooks func_options_finish\n}\n\n\n# func_options [ARG]...\n# ---------------------\n# All the functions called inside func_options are hookable. See the\n# individual implementations for details.\nfunc_hookable func_options\nfunc_options ()\n{\n    $debug_cmd\n\n    _G_options_quoted=false\n\n    for my_func in options_prep parse_options validate_options options_finish\n    do\n      func_unset func_${my_func}_result\n      func_unset func_run_hooks_result\n      eval func_$my_func '${1+\"$@\"}'\n      func_propagate_result func_$my_func func_options\n      if $func_propagate_result_result; then\n        eval set dummy \"$func_options_result\"; shift\n        _G_options_quoted=:\n      fi\n    done\n\n    $_G_options_quoted || {\n      # As we (func_options) are top-level options-parser function and\n      # nobody quoted \"$@\" for us yet, we need to do it explicitly for\n      # caller.\n      func_quote eval ${1+\"$@\"}\n      func_options_result=$func_quote_result\n    }\n}\n\n\n# func_options_prep [ARG]...\n# --------------------------\n# All initialisations required before starting the option parse loop.\n# Note that when calling hook functions, we pass through the list of\n# positional parameters.  If a hook function modifies that list, and\n# needs to propagate that back to rest of this script, then the complete\n# modified list must be put in 'func_run_hooks_result' before returning.\nfunc_hookable func_options_prep\nfunc_options_prep ()\n{\n    $debug_cmd\n\n    # Option defaults:\n    opt_verbose=false\n    opt_warning_types=\n\n    func_run_hooks func_options_prep ${1+\"$@\"}\n    func_propagate_result func_run_hooks func_options_prep\n}\n\n\n# func_parse_options [ARG]...\n# ---------------------------\n# The main option parsing loop.\nfunc_hookable func_parse_options\nfunc_parse_options ()\n{\n    $debug_cmd\n\n    _G_parse_options_requote=false\n    # this just eases exit handling\n    while test $# -gt 0; do\n      # Defer to hook functions for initial option parsing, so they\n      # get priority in the event of reusing an option name.\n      func_run_hooks func_parse_options ${1+\"$@\"}\n      func_propagate_result func_run_hooks func_parse_options\n      if $func_propagate_result_result; then\n        eval set dummy \"$func_parse_options_result\"; shift\n        # Even though we may have changed \"$@\", we passed the \"$@\" array\n        # down into the hook and it quoted it for us (because we are in\n        # this if-branch).  No need to quote it again.\n        _G_parse_options_requote=false\n      fi\n\n      # Break out of the loop if we already parsed every option.\n      test $# -gt 0 || break\n\n      # We expect that one of the options parsed in this function matches\n      # and thus we remove _G_opt from \"$@\" and need to re-quote.\n      _G_match_parse_options=:\n      _G_opt=$1\n      shift\n      case $_G_opt in\n        --debug|-x)   debug_cmd='set -x'\n                      func_echo \"enabling shell trace mode\" >&2\n                      $debug_cmd\n                      ;;\n\n        --no-warnings|--no-warning|--no-warn)\n                      set dummy --warnings none ${1+\"$@\"}\n                      shift\n\t\t      ;;\n\n        --warnings|--warning|-W)\n                      if test $# = 0 && func_missing_arg $_G_opt; then\n                        _G_parse_options_requote=:\n                        break\n                      fi\n                      case \" $warning_categories $1\" in\n                        *\" $1 \"*)\n                          # trailing space prevents matching last $1 above\n                          func_append_uniq opt_warning_types \" $1\"\n                          ;;\n                        *all)\n                          opt_warning_types=$warning_categories\n                          ;;\n                        *none)\n                          opt_warning_types=none\n                          warning_func=:\n                          ;;\n                        *error)\n                          opt_warning_types=$warning_categories\n                          warning_func=func_fatal_error\n                          ;;\n                        *)\n                          func_fatal_error \\\n                             \"unsupported warning category: '$1'\"\n                          ;;\n                      esac\n                      shift\n                      ;;\n\n        --verbose|-v) opt_verbose=: ;;\n        --version)    func_version ;;\n        -\\?|-h)       func_usage ;;\n        --help)       func_help ;;\n\n\t# Separate optargs to long options (plugins may need this):\n\t--*=*)        func_split_equals \"$_G_opt\"\n\t              set dummy \"$func_split_equals_lhs\" \\\n                          \"$func_split_equals_rhs\" ${1+\"$@\"}\n                      shift\n                      ;;\n\n       # Separate optargs to short options:\n        -W*)\n                      func_split_short_opt \"$_G_opt\"\n                      set dummy \"$func_split_short_opt_name\" \\\n                          \"$func_split_short_opt_arg\" ${1+\"$@\"}\n                      shift\n                      ;;\n\n        # Separate non-argument short options:\n        -\\?*|-h*|-v*|-x*)\n                      func_split_short_opt \"$_G_opt\"\n                      set dummy \"$func_split_short_opt_name\" \\\n                          \"-$func_split_short_opt_arg\" ${1+\"$@\"}\n                      shift\n                      ;;\n\n        --)           _G_parse_options_requote=: ; break ;;\n        -*)           func_fatal_help \"unrecognised option: '$_G_opt'\" ;;\n        *)            set dummy \"$_G_opt\" ${1+\"$@\"}; shift\n                      _G_match_parse_options=false\n                      break\n                      ;;\n      esac\n\n      if $_G_match_parse_options; then\n        _G_parse_options_requote=:\n      fi\n    done\n\n    if $_G_parse_options_requote; then\n      # save modified positional parameters for caller\n      func_quote eval ${1+\"$@\"}\n      func_parse_options_result=$func_quote_result\n    fi\n}\n\n\n# func_validate_options [ARG]...\n# ------------------------------\n# Perform any sanity checks on option settings and/or unconsumed\n# arguments.\nfunc_hookable func_validate_options\nfunc_validate_options ()\n{\n    $debug_cmd\n\n    # Display all warnings if -W was not given.\n    test -n \"$opt_warning_types\" || opt_warning_types=\" $warning_categories\"\n\n    func_run_hooks func_validate_options ${1+\"$@\"}\n    func_propagate_result func_run_hooks func_validate_options\n\n    # Bail if the options were screwed!\n    $exit_cmd $EXIT_FAILURE\n}\n\n\n\n## ----------------- ##\n## Helper functions. ##\n## ----------------- ##\n\n# This section contains the helper functions used by the rest of the\n# hookable option parser framework in ascii-betical order.\n\n\n# func_fatal_help ARG...\n# ----------------------\n# Echo program name prefixed message to standard error, followed by\n# a help hint, and exit.\nfunc_fatal_help ()\n{\n    $debug_cmd\n\n    eval \\$ECHO \\\"\"Usage: $usage\"\\\"\n    eval \\$ECHO \\\"\"$fatal_help\"\\\"\n    func_error ${1+\"$@\"}\n    exit $EXIT_FAILURE\n}\n\n\n# func_help\n# ---------\n# Echo long help message to standard output and exit.\nfunc_help ()\n{\n    $debug_cmd\n\n    func_usage_message\n    $ECHO \"$long_help_message\"\n    exit 0\n}\n\n\n# func_missing_arg ARGNAME\n# ------------------------\n# Echo program name prefixed message to standard error and set global\n# exit_cmd.\nfunc_missing_arg ()\n{\n    $debug_cmd\n\n    func_error \"Missing argument for '$1'.\"\n    exit_cmd=exit\n}\n\n\n# func_split_equals STRING\n# ------------------------\n# Set func_split_equals_lhs and func_split_equals_rhs shell variables\n# after splitting STRING at the '=' sign.\ntest -z \"$_G_HAVE_XSI_OPS\" \\\n    && (eval 'x=a/b/c;\n      test 5aa/bb/cc = \"${#x}${x%%/*}${x%/*}${x#*/}${x##*/}\"') 2>/dev/null \\\n    && _G_HAVE_XSI_OPS=yes\n\nif test yes = \"$_G_HAVE_XSI_OPS\"\nthen\n  # This is an XSI compatible shell, allowing a faster implementation...\n  eval 'func_split_equals ()\n  {\n      $debug_cmd\n\n      func_split_equals_lhs=${1%%=*}\n      func_split_equals_rhs=${1#*=}\n      if test \"x$func_split_equals_lhs\" = \"x$1\"; then\n        func_split_equals_rhs=\n      fi\n  }'\nelse\n  # ...otherwise fall back to using expr, which is often a shell builtin.\n  func_split_equals ()\n  {\n      $debug_cmd\n\n      func_split_equals_lhs=`expr \"x$1\" : 'x\\([^=]*\\)'`\n      func_split_equals_rhs=\n      test \"x$func_split_equals_lhs=\" = \"x$1\" \\\n        || func_split_equals_rhs=`expr \"x$1\" : 'x[^=]*=\\(.*\\)$'`\n  }\nfi #func_split_equals\n\n\n# func_split_short_opt SHORTOPT\n# -----------------------------\n# Set func_split_short_opt_name and func_split_short_opt_arg shell\n# variables after splitting SHORTOPT after the 2nd character.\nif test yes = \"$_G_HAVE_XSI_OPS\"\nthen\n  # This is an XSI compatible shell, allowing a faster implementation...\n  eval 'func_split_short_opt ()\n  {\n      $debug_cmd\n\n      func_split_short_opt_arg=${1#??}\n      func_split_short_opt_name=${1%\"$func_split_short_opt_arg\"}\n  }'\nelse\n  # ...otherwise fall back to using expr, which is often a shell builtin.\n  func_split_short_opt ()\n  {\n      $debug_cmd\n\n      func_split_short_opt_name=`expr \"x$1\" : 'x\\(-.\\)'`\n      func_split_short_opt_arg=`expr \"x$1\" : 'x-.\\(.*\\)$'`\n  }\nfi #func_split_short_opt\n\n\n# func_usage\n# ----------\n# Echo short help message to standard output and exit.\nfunc_usage ()\n{\n    $debug_cmd\n\n    func_usage_message\n    $ECHO \"Run '$progname --help |${PAGER-more}' for full usage\"\n    exit 0\n}\n\n\n# func_usage_message\n# ------------------\n# Echo short help message to standard output.\nfunc_usage_message ()\n{\n    $debug_cmd\n\n    eval \\$ECHO \\\"\"Usage: $usage\"\\\"\n    echo\n    $SED -n 's|^# ||\n        /^Written by/{\n          x;p;x\n        }\n\th\n\t/^Written by/q' < \"$progpath\"\n    echo\n    eval \\$ECHO \\\"\"$usage_message\"\\\"\n}\n\n\n# func_version\n# ------------\n# Echo version message to standard output and exit.\n# The version message is extracted from the calling file's header\n# comments, with leading '# ' stripped:\n#   1. First display the progname and version\n#   2. Followed by the header comment line matching  /^# Written by /\n#   3. Then a blank line followed by the first following line matching\n#      /^# Copyright /\n#   4. Immediately followed by any lines between the previous matches,\n#      except lines preceding the intervening completely blank line.\n# For example, see the header comments of this file.\nfunc_version ()\n{\n    $debug_cmd\n\n    printf '%s\\n' \"$progname $scriptversion\"\n    $SED -n '\n        /^# Written by /!b\n        s|^# ||; p; n\n\n        :fwd2blnk\n        /./ {\n          n\n          b fwd2blnk\n        }\n        p; n\n\n        :holdwrnt\n        s|^# ||\n        s|^# *$||\n        /^Copyright /!{\n          /./H\n          n\n          b holdwrnt\n        }\n\n        s|\\((C)\\)[ 0-9,-]*[ ,-]\\([1-9][0-9]* \\)|\\1 \\2|\n        G\n        s|\\(\\n\\)\\n*|\\1|g\n        p; q' < \"$progpath\"\n\n    exit $?\n}\n\n\n# Local variables:\n# mode: shell-script\n# sh-indentation: 2\n# eval: (add-hook 'before-save-hook 'time-stamp)\n# time-stamp-pattern: \"30/scriptversion=%:y-%02m-%02d.%02H; # UTC\"\n# time-stamp-time-zone: \"UTC\"\n# End:\n\n# Set a version string.\nscriptversion='(GNU libtool) 2.4.7'\n\n\n# func_echo ARG...\n# ----------------\n# Libtool also displays the current mode in messages, so override\n# funclib.sh func_echo with this custom definition.\nfunc_echo ()\n{\n    $debug_cmd\n\n    _G_message=$*\n\n    func_echo_IFS=$IFS\n    IFS=$nl\n    for _G_line in $_G_message; do\n      IFS=$func_echo_IFS\n      $ECHO \"$progname${opt_mode+: $opt_mode}: $_G_line\"\n    done\n    IFS=$func_echo_IFS\n}\n\n\n# func_warning ARG...\n# -------------------\n# Libtool warnings are not categorized, so override funclib.sh\n# func_warning with this simpler definition.\nfunc_warning ()\n{\n    $debug_cmd\n\n    $warning_func ${1+\"$@\"}\n}\n\n\n## ---------------- ##\n## Options parsing. ##\n## ---------------- ##\n\n# Hook in the functions to make sure our own options are parsed during\n# the option parsing loop.\n\nusage='$progpath [OPTION]... [MODE-ARG]...'\n\n# Short help message in response to '-h'.\nusage_message=\"Options:\n       --config             show all configuration variables\n       --debug              enable verbose shell tracing\n   -n, --dry-run            display commands without modifying any files\n       --features           display basic configuration information and exit\n       --mode=MODE          use operation mode MODE\n       --no-warnings        equivalent to '-Wnone'\n       --preserve-dup-deps  don't remove duplicate dependency libraries\n       --quiet, --silent    don't print informational messages\n       --tag=TAG            use configuration variables from tag TAG\n   -v, --verbose            print more informational messages than default\n       --version            print version information\n   -W, --warnings=CATEGORY  report the warnings falling in CATEGORY [all]\n   -h, --help, --help-all   print short, long, or detailed help message\n\"\n\n# Additional text appended to 'usage_message' in response to '--help'.\nfunc_help ()\n{\n    $debug_cmd\n\n    func_usage_message\n    $ECHO \"$long_help_message\n\nMODE must be one of the following:\n\n       clean           remove files from the build directory\n       compile         compile a source file into a libtool object\n       execute         automatically set library path, then run a program\n       finish          complete the installation of libtool libraries\n       install         install libraries or executables\n       link            create a library or an executable\n       uninstall       remove libraries from an installed directory\n\nMODE-ARGS vary depending on the MODE.  When passed as first option,\n'--mode=MODE' may be abbreviated as 'MODE' or a unique abbreviation of that.\nTry '$progname --help --mode=MODE' for a more detailed description of MODE.\n\nWhen reporting a bug, please describe a test case to reproduce it and\ninclude the following information:\n\n       host-triplet:   $host\n       shell:          $SHELL\n       compiler:       $LTCC\n       compiler flags: $LTCFLAGS\n       linker:         $LD (gnu? $with_gnu_ld)\n       version:        $progname (GNU libtool) 2.4.7\n       automake:       `($AUTOMAKE --version) 2>/dev/null |$SED 1q`\n       autoconf:       `($AUTOCONF --version) 2>/dev/null |$SED 1q`\n\nReport bugs to <bug-libtool@gnu.org>.\nGNU libtool home page: <http://www.gnu.org/software/libtool/>.\nGeneral help using GNU software: <http://www.gnu.org/gethelp/>.\"\n    exit 0\n}\n\n\n# func_lo2o OBJECT-NAME\n# ---------------------\n# Transform OBJECT-NAME from a '.lo' suffix to the platform specific\n# object suffix.\n\nlo2o=s/\\\\.lo\\$/.$objext/\no2lo=s/\\\\.$objext\\$/.lo/\n\nif test yes = \"$_G_HAVE_XSI_OPS\"; then\n  eval 'func_lo2o ()\n  {\n    case $1 in\n      *.lo) func_lo2o_result=${1%.lo}.$objext ;;\n      *   ) func_lo2o_result=$1               ;;\n    esac\n  }'\n\n  # func_xform LIBOBJ-OR-SOURCE\n  # ---------------------------\n  # Transform LIBOBJ-OR-SOURCE from a '.o' or '.c' (or otherwise)\n  # suffix to a '.lo' libtool-object suffix.\n  eval 'func_xform ()\n  {\n    func_xform_result=${1%.*}.lo\n  }'\nelse\n  # ...otherwise fall back to using sed.\n  func_lo2o ()\n  {\n    func_lo2o_result=`$ECHO \"$1\" | $SED \"$lo2o\"`\n  }\n\n  func_xform ()\n  {\n    func_xform_result=`$ECHO \"$1\" | $SED 's|\\.[^.]*$|.lo|'`\n  }\nfi\n\n\n# func_fatal_configuration ARG...\n# -------------------------------\n# Echo program name prefixed message to standard error, followed by\n# a configuration failure hint, and exit.\nfunc_fatal_configuration ()\n{\n    func_fatal_error ${1+\"$@\"} \\\n      \"See the $PACKAGE documentation for more information.\" \\\n      \"Fatal configuration error.\"\n}\n\n\n# func_config\n# -----------\n# Display the configuration for all the tags in this script.\nfunc_config ()\n{\n    re_begincf='^# ### BEGIN LIBTOOL'\n    re_endcf='^# ### END LIBTOOL'\n\n    # Default configuration.\n    $SED \"1,/$re_begincf CONFIG/d;/$re_endcf CONFIG/,\\$d\" < \"$progpath\"\n\n    # Now print the configurations for the tags.\n    for tagname in $taglist; do\n      $SED -n \"/$re_begincf TAG CONFIG: $tagname\\$/,/$re_endcf TAG CONFIG: $tagname\\$/p\" < \"$progpath\"\n    done\n\n    exit $?\n}\n\n\n# func_features\n# -------------\n# Display the features supported by this script.\nfunc_features ()\n{\n    echo \"host: $host\"\n    if test yes = \"$build_libtool_libs\"; then\n      echo \"enable shared libraries\"\n    else\n      echo \"disable shared libraries\"\n    fi\n    if test yes = \"$build_old_libs\"; then\n      echo \"enable static libraries\"\n    else\n      echo \"disable static libraries\"\n    fi\n\n    exit $?\n}\n\n\n# func_enable_tag TAGNAME\n# -----------------------\n# Verify that TAGNAME is valid, and either flag an error and exit, or\n# enable the TAGNAME tag.  We also add TAGNAME to the global $taglist\n# variable here.\nfunc_enable_tag ()\n{\n    # Global variable:\n    tagname=$1\n\n    re_begincf=\"^# ### BEGIN LIBTOOL TAG CONFIG: $tagname\\$\"\n    re_endcf=\"^# ### END LIBTOOL TAG CONFIG: $tagname\\$\"\n    sed_extractcf=/$re_begincf/,/$re_endcf/p\n\n    # Validate tagname.\n    case $tagname in\n      *[!-_A-Za-z0-9,/]*)\n        func_fatal_error \"invalid tag name: $tagname\"\n        ;;\n    esac\n\n    # Don't test for the \"default\" C tag, as we know it's\n    # there but not specially marked.\n    case $tagname in\n        CC) ;;\n    *)\n        if $GREP \"$re_begincf\" \"$progpath\" >/dev/null 2>&1; then\n\t  taglist=\"$taglist $tagname\"\n\n\t  # Evaluate the configuration.  Be careful to quote the path\n\t  # and the sed script, to avoid splitting on whitespace, but\n\t  # also don't use non-portable quotes within backquotes within\n\t  # quotes we have to do it in 2 steps:\n\t  extractedcf=`$SED -n -e \"$sed_extractcf\" < \"$progpath\"`\n\t  eval \"$extractedcf\"\n        else\n\t  func_error \"ignoring unknown tag $tagname\"\n        fi\n        ;;\n    esac\n}\n\n\n# func_check_version_match\n# ------------------------\n# Ensure that we are using m4 macros, and libtool script from the same\n# release of libtool.\nfunc_check_version_match ()\n{\n    if test \"$package_revision\" != \"$macro_revision\"; then\n      if test \"$VERSION\" != \"$macro_version\"; then\n        if test -z \"$macro_version\"; then\n          cat >&2 <<_LT_EOF\n$progname: Version mismatch error.  This is $PACKAGE $VERSION, but the\n$progname: definition of this LT_INIT comes from an older release.\n$progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION\n$progname: and run autoconf again.\n_LT_EOF\n        else\n          cat >&2 <<_LT_EOF\n$progname: Version mismatch error.  This is $PACKAGE $VERSION, but the\n$progname: definition of this LT_INIT comes from $PACKAGE $macro_version.\n$progname: You should recreate aclocal.m4 with macros from $PACKAGE $VERSION\n$progname: and run autoconf again.\n_LT_EOF\n        fi\n      else\n        cat >&2 <<_LT_EOF\n$progname: Version mismatch error.  This is $PACKAGE $VERSION, revision $package_revision,\n$progname: but the definition of this LT_INIT comes from revision $macro_revision.\n$progname: You should recreate aclocal.m4 with macros from revision $package_revision\n$progname: of $PACKAGE $VERSION and run autoconf again.\n_LT_EOF\n      fi\n\n      exit $EXIT_MISMATCH\n    fi\n}\n\n\n# libtool_options_prep [ARG]...\n# -----------------------------\n# Preparation for options parsed by libtool.\nlibtool_options_prep ()\n{\n    $debug_mode\n\n    # Option defaults:\n    opt_config=false\n    opt_dlopen=\n    opt_dry_run=false\n    opt_help=false\n    opt_mode=\n    opt_preserve_dup_deps=false\n    opt_quiet=false\n\n    nonopt=\n    preserve_args=\n\n    _G_rc_lt_options_prep=:\n\n    # Shorthand for --mode=foo, only valid as the first argument\n    case $1 in\n    clean|clea|cle|cl)\n      shift; set dummy --mode clean ${1+\"$@\"}; shift\n      ;;\n    compile|compil|compi|comp|com|co|c)\n      shift; set dummy --mode compile ${1+\"$@\"}; shift\n      ;;\n    execute|execut|execu|exec|exe|ex|e)\n      shift; set dummy --mode execute ${1+\"$@\"}; shift\n      ;;\n    finish|finis|fini|fin|fi|f)\n      shift; set dummy --mode finish ${1+\"$@\"}; shift\n      ;;\n    install|instal|insta|inst|ins|in|i)\n      shift; set dummy --mode install ${1+\"$@\"}; shift\n      ;;\n    link|lin|li|l)\n      shift; set dummy --mode link ${1+\"$@\"}; shift\n      ;;\n    uninstall|uninstal|uninsta|uninst|unins|unin|uni|un|u)\n      shift; set dummy --mode uninstall ${1+\"$@\"}; shift\n      ;;\n    *)\n      _G_rc_lt_options_prep=false\n      ;;\n    esac\n\n    if $_G_rc_lt_options_prep; then\n      # Pass back the list of options.\n      func_quote eval ${1+\"$@\"}\n      libtool_options_prep_result=$func_quote_result\n    fi\n}\nfunc_add_hook func_options_prep libtool_options_prep\n\n\n# libtool_parse_options [ARG]...\n# ---------------------------------\n# Provide handling for libtool specific options.\nlibtool_parse_options ()\n{\n    $debug_cmd\n\n    _G_rc_lt_parse_options=false\n\n    # Perform our own loop to consume as many options as possible in\n    # each iteration.\n    while test $# -gt 0; do\n      _G_match_lt_parse_options=:\n      _G_opt=$1\n      shift\n      case $_G_opt in\n        --dry-run|--dryrun|-n)\n                        opt_dry_run=:\n                        ;;\n\n        --config)       func_config ;;\n\n        --dlopen|-dlopen)\n                        opt_dlopen=\"${opt_dlopen+$opt_dlopen\n}$1\"\n                        shift\n                        ;;\n\n        --preserve-dup-deps)\n                        opt_preserve_dup_deps=: ;;\n\n        --features)     func_features ;;\n\n        --finish)       set dummy --mode finish ${1+\"$@\"}; shift ;;\n\n        --help)         opt_help=: ;;\n\n        --help-all)     opt_help=': help-all' ;;\n\n        --mode)         test $# = 0 && func_missing_arg $_G_opt && break\n                        opt_mode=$1\n                        case $1 in\n                          # Valid mode arguments:\n                          clean|compile|execute|finish|install|link|relink|uninstall) ;;\n\n                          # Catch anything else as an error\n                          *) func_error \"invalid argument for $_G_opt\"\n                             exit_cmd=exit\n                             break\n                             ;;\n                        esac\n                        shift\n                        ;;\n\n        --no-silent|--no-quiet)\n                        opt_quiet=false\n                        func_append preserve_args \" $_G_opt\"\n                        ;;\n\n        --no-warnings|--no-warning|--no-warn)\n                        opt_warning=false\n                        func_append preserve_args \" $_G_opt\"\n                        ;;\n\n        --no-verbose)\n                        opt_verbose=false\n                        func_append preserve_args \" $_G_opt\"\n                        ;;\n\n        --silent|--quiet)\n                        opt_quiet=:\n                        opt_verbose=false\n                        func_append preserve_args \" $_G_opt\"\n                        ;;\n\n        --tag)          test $# = 0 && func_missing_arg $_G_opt && break\n                        opt_tag=$1\n                        func_append preserve_args \" $_G_opt $1\"\n                        func_enable_tag \"$1\"\n                        shift\n                        ;;\n\n        --verbose|-v)   opt_quiet=false\n                        opt_verbose=:\n                        func_append preserve_args \" $_G_opt\"\n                        ;;\n\n        # An option not handled by this hook function:\n        *)              set dummy \"$_G_opt\" ${1+\"$@\"} ; shift\n                        _G_match_lt_parse_options=false\n                        break\n                        ;;\n      esac\n      $_G_match_lt_parse_options && _G_rc_lt_parse_options=:\n    done\n\n    if $_G_rc_lt_parse_options; then\n      # save modified positional parameters for caller\n      func_quote eval ${1+\"$@\"}\n      libtool_parse_options_result=$func_quote_result\n    fi\n}\nfunc_add_hook func_parse_options libtool_parse_options\n\n\n\n# libtool_validate_options [ARG]...\n# ---------------------------------\n# Perform any sanity checks on option settings and/or unconsumed\n# arguments.\nlibtool_validate_options ()\n{\n    # save first non-option argument\n    if test 0 -lt $#; then\n      nonopt=$1\n      shift\n    fi\n\n    # preserve --debug\n    test : = \"$debug_cmd\" || func_append preserve_args \" --debug\"\n\n    case $host in\n      # Solaris2 added to fix http://debbugs.gnu.org/cgi/bugreport.cgi?bug=16452\n      # see also: http://gcc.gnu.org/bugzilla/show_bug.cgi?id=59788\n      *cygwin* | *mingw* | *pw32* | *cegcc* | *solaris2* | *os2*)\n        # don't eliminate duplications in $postdeps and $predeps\n        opt_duplicate_compiler_generated_deps=:\n        ;;\n      *)\n        opt_duplicate_compiler_generated_deps=$opt_preserve_dup_deps\n        ;;\n    esac\n\n    $opt_help || {\n      # Sanity checks first:\n      func_check_version_match\n\n      test yes != \"$build_libtool_libs\" \\\n        && test yes != \"$build_old_libs\" \\\n        && func_fatal_configuration \"not configured to build any kind of library\"\n\n      # Darwin sucks\n      eval std_shrext=\\\"$shrext_cmds\\\"\n\n      # Only execute mode is allowed to have -dlopen flags.\n      if test -n \"$opt_dlopen\" && test execute != \"$opt_mode\"; then\n        func_error \"unrecognized option '-dlopen'\"\n        $ECHO \"$help\" 1>&2\n        exit $EXIT_FAILURE\n      fi\n\n      # Change the help message to a mode-specific one.\n      generic_help=$help\n      help=\"Try '$progname --help --mode=$opt_mode' for more information.\"\n    }\n\n    # Pass back the unparsed argument list\n    func_quote eval ${1+\"$@\"}\n    libtool_validate_options_result=$func_quote_result\n}\nfunc_add_hook func_validate_options libtool_validate_options\n\n\n# Process options as early as possible so that --help and --version\n# can return quickly.\nfunc_options ${1+\"$@\"}\neval set dummy \"$func_options_result\"; shift\n\n\n\n## ----------- ##\n##    Main.    ##\n## ----------- ##\n\nmagic='%%%MAGIC variable%%%'\nmagic_exe='%%%MAGIC EXE variable%%%'\n\n# Global variables.\nextracted_archives=\nextracted_serial=0\n\n# If this variable is set in any of the actions, the command in it\n# will be execed at the end.  This prevents here-documents from being\n# left over by shells.\nexec_cmd=\n\n\n# A function that is used when there is no print builtin or printf.\nfunc_fallback_echo ()\n{\n  eval 'cat <<_LTECHO_EOF\n$1\n_LTECHO_EOF'\n}\n\n# func_generated_by_libtool\n# True iff stdin has been generated by Libtool. This function is only\n# a basic sanity check; it will hardly flush out determined imposters.\nfunc_generated_by_libtool_p ()\n{\n  $GREP \"^# Generated by .*$PACKAGE\" > /dev/null 2>&1\n}\n\n# func_lalib_p file\n# True iff FILE is a libtool '.la' library or '.lo' object file.\n# This function is only a basic sanity check; it will hardly flush out\n# determined imposters.\nfunc_lalib_p ()\n{\n    test -f \"$1\" &&\n      $SED -e 4q \"$1\" 2>/dev/null | func_generated_by_libtool_p\n}\n\n# func_lalib_unsafe_p file\n# True iff FILE is a libtool '.la' library or '.lo' object file.\n# This function implements the same check as func_lalib_p without\n# resorting to external programs.  To this end, it redirects stdin and\n# closes it afterwards, without saving the original file descriptor.\n# As a safety measure, use it only where a negative result would be\n# fatal anyway.  Works if 'file' does not exist.\nfunc_lalib_unsafe_p ()\n{\n    lalib_p=no\n    if test -f \"$1\" && test -r \"$1\" && exec 5<&0 <\"$1\"; then\n\tfor lalib_p_l in 1 2 3 4\n\tdo\n\t    read lalib_p_line\n\t    case $lalib_p_line in\n\t\t\\#\\ Generated\\ by\\ *$PACKAGE* ) lalib_p=yes; break;;\n\t    esac\n\tdone\n\texec 0<&5 5<&-\n    fi\n    test yes = \"$lalib_p\"\n}\n\n# func_ltwrapper_script_p file\n# True iff FILE is a libtool wrapper script\n# This function is only a basic sanity check; it will hardly flush out\n# determined imposters.\nfunc_ltwrapper_script_p ()\n{\n    test -f \"$1\" &&\n      $lt_truncate_bin < \"$1\" 2>/dev/null | func_generated_by_libtool_p\n}\n\n# func_ltwrapper_executable_p file\n# True iff FILE is a libtool wrapper executable\n# This function is only a basic sanity check; it will hardly flush out\n# determined imposters.\nfunc_ltwrapper_executable_p ()\n{\n    func_ltwrapper_exec_suffix=\n    case $1 in\n    *.exe) ;;\n    *) func_ltwrapper_exec_suffix=.exe ;;\n    esac\n    $GREP \"$magic_exe\" \"$1$func_ltwrapper_exec_suffix\" >/dev/null 2>&1\n}\n\n# func_ltwrapper_scriptname file\n# Assumes file is an ltwrapper_executable\n# uses $file to determine the appropriate filename for a\n# temporary ltwrapper_script.\nfunc_ltwrapper_scriptname ()\n{\n    func_dirname_and_basename \"$1\" \"\" \".\"\n    func_stripname '' '.exe' \"$func_basename_result\"\n    func_ltwrapper_scriptname_result=$func_dirname_result/$objdir/${func_stripname_result}_ltshwrapper\n}\n\n# func_ltwrapper_p file\n# True iff FILE is a libtool wrapper script or wrapper executable\n# This function is only a basic sanity check; it will hardly flush out\n# determined imposters.\nfunc_ltwrapper_p ()\n{\n    func_ltwrapper_script_p \"$1\" || func_ltwrapper_executable_p \"$1\"\n}\n\n\n# func_execute_cmds commands fail_cmd\n# Execute tilde-delimited COMMANDS.\n# If FAIL_CMD is given, eval that upon failure.\n# FAIL_CMD may read-access the current command in variable CMD!\nfunc_execute_cmds ()\n{\n    $debug_cmd\n\n    save_ifs=$IFS; IFS='~'\n    for cmd in $1; do\n      IFS=$sp$nl\n      eval cmd=\\\"$cmd\\\"\n      IFS=$save_ifs\n      func_show_eval \"$cmd\" \"${2-:}\"\n    done\n    IFS=$save_ifs\n}\n\n\n# func_source file\n# Source FILE, adding directory component if necessary.\n# Note that it is not necessary on cygwin/mingw to append a dot to\n# FILE even if both FILE and FILE.exe exist: automatic-append-.exe\n# behavior happens only for exec(3), not for open(2)!  Also, sourcing\n# 'FILE.' does not work on cygwin managed mounts.\nfunc_source ()\n{\n    $debug_cmd\n\n    case $1 in\n    */* | *\\\\*)\t. \"$1\" ;;\n    *)\t\t. \"./$1\" ;;\n    esac\n}\n\n\n# func_resolve_sysroot PATH\n# Replace a leading = in PATH with a sysroot.  Store the result into\n# func_resolve_sysroot_result\nfunc_resolve_sysroot ()\n{\n  func_resolve_sysroot_result=$1\n  case $func_resolve_sysroot_result in\n  =*)\n    func_stripname '=' '' \"$func_resolve_sysroot_result\"\n    func_resolve_sysroot_result=$lt_sysroot$func_stripname_result\n    ;;\n  esac\n}\n\n# func_replace_sysroot PATH\n# If PATH begins with the sysroot, replace it with = and\n# store the result into func_replace_sysroot_result.\nfunc_replace_sysroot ()\n{\n  case $lt_sysroot:$1 in\n  ?*:\"$lt_sysroot\"*)\n    func_stripname \"$lt_sysroot\" '' \"$1\"\n    func_replace_sysroot_result='='$func_stripname_result\n    ;;\n  *)\n    # Including no sysroot.\n    func_replace_sysroot_result=$1\n    ;;\n  esac\n}\n\n# func_infer_tag arg\n# Infer tagged configuration to use if any are available and\n# if one wasn't chosen via the \"--tag\" command line option.\n# Only attempt this if the compiler in the base compile\n# command doesn't match the default compiler.\n# arg is usually of the form 'gcc ...'\nfunc_infer_tag ()\n{\n    $debug_cmd\n\n    if test -n \"$available_tags\" && test -z \"$tagname\"; then\n      CC_quoted=\n      for arg in $CC; do\n\tfunc_append_quoted CC_quoted \"$arg\"\n      done\n      CC_expanded=`func_echo_all $CC`\n      CC_quoted_expanded=`func_echo_all $CC_quoted`\n      case $@ in\n      # Blanks in the command may have been stripped by the calling shell,\n      # but not from the CC environment variable when configure was run.\n      \" $CC \"* | \"$CC \"* | \" $CC_expanded \"* | \"$CC_expanded \"* | \\\n      \" $CC_quoted\"* | \"$CC_quoted \"* | \" $CC_quoted_expanded \"* | \"$CC_quoted_expanded \"*) ;;\n      # Blanks at the start of $base_compile will cause this to fail\n      # if we don't check for them as well.\n      *)\n\tfor z in $available_tags; do\n\t  if $GREP \"^# ### BEGIN LIBTOOL TAG CONFIG: $z$\" < \"$progpath\" > /dev/null; then\n\t    # Evaluate the configuration.\n\t    eval \"`$SED -n -e '/^# ### BEGIN LIBTOOL TAG CONFIG: '$z'$/,/^# ### END LIBTOOL TAG CONFIG: '$z'$/p' < $progpath`\"\n\t    CC_quoted=\n\t    for arg in $CC; do\n\t      # Double-quote args containing other shell metacharacters.\n\t      func_append_quoted CC_quoted \"$arg\"\n\t    done\n\t    CC_expanded=`func_echo_all $CC`\n\t    CC_quoted_expanded=`func_echo_all $CC_quoted`\n\t    case \"$@ \" in\n\t    \" $CC \"* | \"$CC \"* | \" $CC_expanded \"* | \"$CC_expanded \"* | \\\n\t    \" $CC_quoted\"* | \"$CC_quoted \"* | \" $CC_quoted_expanded \"* | \"$CC_quoted_expanded \"*)\n\t      # The compiler in the base compile command matches\n\t      # the one in the tagged configuration.\n\t      # Assume this is the tagged configuration we want.\n\t      tagname=$z\n\t      break\n\t      ;;\n\t    esac\n\t  fi\n\tdone\n\t# If $tagname still isn't set, then no tagged configuration\n\t# was found and let the user know that the \"--tag\" command\n\t# line option must be used.\n\tif test -z \"$tagname\"; then\n\t  func_echo \"unable to infer tagged configuration\"\n\t  func_fatal_error \"specify a tag with '--tag'\"\n#\telse\n#\t  func_verbose \"using $tagname tagged configuration\"\n\tfi\n\t;;\n      esac\n    fi\n}\n\n\n\n# func_write_libtool_object output_name pic_name nonpic_name\n# Create a libtool object file (analogous to a \".la\" file),\n# but don't create it if we're doing a dry run.\nfunc_write_libtool_object ()\n{\n    write_libobj=$1\n    if test yes = \"$build_libtool_libs\"; then\n      write_lobj=\\'$2\\'\n    else\n      write_lobj=none\n    fi\n\n    if test yes = \"$build_old_libs\"; then\n      write_oldobj=\\'$3\\'\n    else\n      write_oldobj=none\n    fi\n\n    $opt_dry_run || {\n      cat >${write_libobj}T <<EOF\n# $write_libobj - a libtool object file\n# Generated by $PROGRAM (GNU $PACKAGE) $VERSION\n#\n# Please DO NOT delete this file!\n# It is necessary for linking the library.\n\n# Name of the PIC object.\npic_object=$write_lobj\n\n# Name of the non-PIC object\nnon_pic_object=$write_oldobj\n\nEOF\n      $MV \"${write_libobj}T\" \"$write_libobj\"\n    }\n}\n\n\n##################################################\n# FILE NAME AND PATH CONVERSION HELPER FUNCTIONS #\n##################################################\n\n# func_convert_core_file_wine_to_w32 ARG\n# Helper function used by file name conversion functions when $build is *nix,\n# and $host is mingw, cygwin, or some other w32 environment. Relies on a\n# correctly configured wine environment available, with the winepath program\n# in $build's $PATH.\n#\n# ARG is the $build file name to be converted to w32 format.\n# Result is available in $func_convert_core_file_wine_to_w32_result, and will\n# be empty on error (or when ARG is empty)\nfunc_convert_core_file_wine_to_w32 ()\n{\n  $debug_cmd\n\n  func_convert_core_file_wine_to_w32_result=$1\n  if test -n \"$1\"; then\n    # Unfortunately, winepath does not exit with a non-zero error code, so we\n    # are forced to check the contents of stdout. On the other hand, if the\n    # command is not found, the shell will set an exit code of 127 and print\n    # *an error message* to stdout. So we must check for both error code of\n    # zero AND non-empty stdout, which explains the odd construction:\n    func_convert_core_file_wine_to_w32_tmp=`winepath -w \"$1\" 2>/dev/null`\n    if test \"$?\" -eq 0 && test -n \"$func_convert_core_file_wine_to_w32_tmp\"; then\n      func_convert_core_file_wine_to_w32_result=`$ECHO \"$func_convert_core_file_wine_to_w32_tmp\" |\n        $SED -e \"$sed_naive_backslashify\"`\n    else\n      func_convert_core_file_wine_to_w32_result=\n    fi\n  fi\n}\n# end: func_convert_core_file_wine_to_w32\n\n\n# func_convert_core_path_wine_to_w32 ARG\n# Helper function used by path conversion functions when $build is *nix, and\n# $host is mingw, cygwin, or some other w32 environment. Relies on a correctly\n# configured wine environment available, with the winepath program in $build's\n# $PATH. Assumes ARG has no leading or trailing path separator characters.\n#\n# ARG is path to be converted from $build format to win32.\n# Result is available in $func_convert_core_path_wine_to_w32_result.\n# Unconvertible file (directory) names in ARG are skipped; if no directory names\n# are convertible, then the result may be empty.\nfunc_convert_core_path_wine_to_w32 ()\n{\n  $debug_cmd\n\n  # unfortunately, winepath doesn't convert paths, only file names\n  func_convert_core_path_wine_to_w32_result=\n  if test -n \"$1\"; then\n    oldIFS=$IFS\n    IFS=:\n    for func_convert_core_path_wine_to_w32_f in $1; do\n      IFS=$oldIFS\n      func_convert_core_file_wine_to_w32 \"$func_convert_core_path_wine_to_w32_f\"\n      if test -n \"$func_convert_core_file_wine_to_w32_result\"; then\n        if test -z \"$func_convert_core_path_wine_to_w32_result\"; then\n          func_convert_core_path_wine_to_w32_result=$func_convert_core_file_wine_to_w32_result\n        else\n          func_append func_convert_core_path_wine_to_w32_result \";$func_convert_core_file_wine_to_w32_result\"\n        fi\n      fi\n    done\n    IFS=$oldIFS\n  fi\n}\n# end: func_convert_core_path_wine_to_w32\n\n\n# func_cygpath ARGS...\n# Wrapper around calling the cygpath program via LT_CYGPATH. This is used when\n# when (1) $build is *nix and Cygwin is hosted via a wine environment; or (2)\n# $build is MSYS and $host is Cygwin, or (3) $build is Cygwin. In case (1) or\n# (2), returns the Cygwin file name or path in func_cygpath_result (input\n# file name or path is assumed to be in w32 format, as previously converted\n# from $build's *nix or MSYS format). In case (3), returns the w32 file name\n# or path in func_cygpath_result (input file name or path is assumed to be in\n# Cygwin format). Returns an empty string on error.\n#\n# ARGS are passed to cygpath, with the last one being the file name or path to\n# be converted.\n#\n# Specify the absolute *nix (or w32) name to cygpath in the LT_CYGPATH\n# environment variable; do not put it in $PATH.\nfunc_cygpath ()\n{\n  $debug_cmd\n\n  if test -n \"$LT_CYGPATH\" && test -f \"$LT_CYGPATH\"; then\n    func_cygpath_result=`$LT_CYGPATH \"$@\" 2>/dev/null`\n    if test \"$?\" -ne 0; then\n      # on failure, ensure result is empty\n      func_cygpath_result=\n    fi\n  else\n    func_cygpath_result=\n    func_error \"LT_CYGPATH is empty or specifies non-existent file: '$LT_CYGPATH'\"\n  fi\n}\n#end: func_cygpath\n\n\n# func_convert_core_msys_to_w32 ARG\n# Convert file name or path ARG from MSYS format to w32 format.  Return\n# result in func_convert_core_msys_to_w32_result.\nfunc_convert_core_msys_to_w32 ()\n{\n  $debug_cmd\n\n  # awkward: cmd appends spaces to result\n  func_convert_core_msys_to_w32_result=`( cmd //c echo \"$1\" ) 2>/dev/null |\n    $SED -e 's/[ ]*$//' -e \"$sed_naive_backslashify\"`\n}\n#end: func_convert_core_msys_to_w32\n\n\n# func_convert_file_check ARG1 ARG2\n# Verify that ARG1 (a file name in $build format) was converted to $host\n# format in ARG2. Otherwise, emit an error message, but continue (resetting\n# func_to_host_file_result to ARG1).\nfunc_convert_file_check ()\n{\n  $debug_cmd\n\n  if test -z \"$2\" && test -n \"$1\"; then\n    func_error \"Could not determine host file name corresponding to\"\n    func_error \"  '$1'\"\n    func_error \"Continuing, but uninstalled executables may not work.\"\n    # Fallback:\n    func_to_host_file_result=$1\n  fi\n}\n# end func_convert_file_check\n\n\n# func_convert_path_check FROM_PATHSEP TO_PATHSEP FROM_PATH TO_PATH\n# Verify that FROM_PATH (a path in $build format) was converted to $host\n# format in TO_PATH. Otherwise, emit an error message, but continue, resetting\n# func_to_host_file_result to a simplistic fallback value (see below).\nfunc_convert_path_check ()\n{\n  $debug_cmd\n\n  if test -z \"$4\" && test -n \"$3\"; then\n    func_error \"Could not determine the host path corresponding to\"\n    func_error \"  '$3'\"\n    func_error \"Continuing, but uninstalled executables may not work.\"\n    # Fallback.  This is a deliberately simplistic \"conversion\" and\n    # should not be \"improved\".  See libtool.info.\n    if test \"x$1\" != \"x$2\"; then\n      lt_replace_pathsep_chars=\"s|$1|$2|g\"\n      func_to_host_path_result=`echo \"$3\" |\n        $SED -e \"$lt_replace_pathsep_chars\"`\n    else\n      func_to_host_path_result=$3\n    fi\n  fi\n}\n# end func_convert_path_check\n\n\n# func_convert_path_front_back_pathsep FRONTPAT BACKPAT REPL ORIG\n# Modifies func_to_host_path_result by prepending REPL if ORIG matches FRONTPAT\n# and appending REPL if ORIG matches BACKPAT.\nfunc_convert_path_front_back_pathsep ()\n{\n  $debug_cmd\n\n  case $4 in\n  $1 ) func_to_host_path_result=$3$func_to_host_path_result\n    ;;\n  esac\n  case $4 in\n  $2 ) func_append func_to_host_path_result \"$3\"\n    ;;\n  esac\n}\n# end func_convert_path_front_back_pathsep\n\n\n##################################################\n# $build to $host FILE NAME CONVERSION FUNCTIONS #\n##################################################\n# invoked via '$to_host_file_cmd ARG'\n#\n# In each case, ARG is the path to be converted from $build to $host format.\n# Result will be available in $func_to_host_file_result.\n\n\n# func_to_host_file ARG\n# Converts the file name ARG from $build format to $host format. Return result\n# in func_to_host_file_result.\nfunc_to_host_file ()\n{\n  $debug_cmd\n\n  $to_host_file_cmd \"$1\"\n}\n# end func_to_host_file\n\n\n# func_to_tool_file ARG LAZY\n# converts the file name ARG from $build format to toolchain format. Return\n# result in func_to_tool_file_result.  If the conversion in use is listed\n# in (the comma separated) LAZY, no conversion takes place.\nfunc_to_tool_file ()\n{\n  $debug_cmd\n\n  case ,$2, in\n    *,\"$to_tool_file_cmd\",*)\n      func_to_tool_file_result=$1\n      ;;\n    *)\n      $to_tool_file_cmd \"$1\"\n      func_to_tool_file_result=$func_to_host_file_result\n      ;;\n  esac\n}\n# end func_to_tool_file\n\n\n# func_convert_file_noop ARG\n# Copy ARG to func_to_host_file_result.\nfunc_convert_file_noop ()\n{\n  func_to_host_file_result=$1\n}\n# end func_convert_file_noop\n\n\n# func_convert_file_msys_to_w32 ARG\n# Convert file name ARG from (mingw) MSYS to (mingw) w32 format; automatic\n# conversion to w32 is not available inside the cwrapper.  Returns result in\n# func_to_host_file_result.\nfunc_convert_file_msys_to_w32 ()\n{\n  $debug_cmd\n\n  func_to_host_file_result=$1\n  if test -n \"$1\"; then\n    func_convert_core_msys_to_w32 \"$1\"\n    func_to_host_file_result=$func_convert_core_msys_to_w32_result\n  fi\n  func_convert_file_check \"$1\" \"$func_to_host_file_result\"\n}\n# end func_convert_file_msys_to_w32\n\n\n# func_convert_file_cygwin_to_w32 ARG\n# Convert file name ARG from Cygwin to w32 format.  Returns result in\n# func_to_host_file_result.\nfunc_convert_file_cygwin_to_w32 ()\n{\n  $debug_cmd\n\n  func_to_host_file_result=$1\n  if test -n \"$1\"; then\n    # because $build is cygwin, we call \"the\" cygpath in $PATH; no need to use\n    # LT_CYGPATH in this case.\n    func_to_host_file_result=`cygpath -m \"$1\"`\n  fi\n  func_convert_file_check \"$1\" \"$func_to_host_file_result\"\n}\n# end func_convert_file_cygwin_to_w32\n\n\n# func_convert_file_nix_to_w32 ARG\n# Convert file name ARG from *nix to w32 format.  Requires a wine environment\n# and a working winepath. Returns result in func_to_host_file_result.\nfunc_convert_file_nix_to_w32 ()\n{\n  $debug_cmd\n\n  func_to_host_file_result=$1\n  if test -n \"$1\"; then\n    func_convert_core_file_wine_to_w32 \"$1\"\n    func_to_host_file_result=$func_convert_core_file_wine_to_w32_result\n  fi\n  func_convert_file_check \"$1\" \"$func_to_host_file_result\"\n}\n# end func_convert_file_nix_to_w32\n\n\n# func_convert_file_msys_to_cygwin ARG\n# Convert file name ARG from MSYS to Cygwin format.  Requires LT_CYGPATH set.\n# Returns result in func_to_host_file_result.\nfunc_convert_file_msys_to_cygwin ()\n{\n  $debug_cmd\n\n  func_to_host_file_result=$1\n  if test -n \"$1\"; then\n    func_convert_core_msys_to_w32 \"$1\"\n    func_cygpath -u \"$func_convert_core_msys_to_w32_result\"\n    func_to_host_file_result=$func_cygpath_result\n  fi\n  func_convert_file_check \"$1\" \"$func_to_host_file_result\"\n}\n# end func_convert_file_msys_to_cygwin\n\n\n# func_convert_file_nix_to_cygwin ARG\n# Convert file name ARG from *nix to Cygwin format.  Requires Cygwin installed\n# in a wine environment, working winepath, and LT_CYGPATH set.  Returns result\n# in func_to_host_file_result.\nfunc_convert_file_nix_to_cygwin ()\n{\n  $debug_cmd\n\n  func_to_host_file_result=$1\n  if test -n \"$1\"; then\n    # convert from *nix to w32, then use cygpath to convert from w32 to cygwin.\n    func_convert_core_file_wine_to_w32 \"$1\"\n    func_cygpath -u \"$func_convert_core_file_wine_to_w32_result\"\n    func_to_host_file_result=$func_cygpath_result\n  fi\n  func_convert_file_check \"$1\" \"$func_to_host_file_result\"\n}\n# end func_convert_file_nix_to_cygwin\n\n\n#############################################\n# $build to $host PATH CONVERSION FUNCTIONS #\n#############################################\n# invoked via '$to_host_path_cmd ARG'\n#\n# In each case, ARG is the path to be converted from $build to $host format.\n# The result will be available in $func_to_host_path_result.\n#\n# Path separators are also converted from $build format to $host format.  If\n# ARG begins or ends with a path separator character, it is preserved (but\n# converted to $host format) on output.\n#\n# All path conversion functions are named using the following convention:\n#   file name conversion function    : func_convert_file_X_to_Y ()\n#   path conversion function         : func_convert_path_X_to_Y ()\n# where, for any given $build/$host combination the 'X_to_Y' value is the\n# same.  If conversion functions are added for new $build/$host combinations,\n# the two new functions must follow this pattern, or func_init_to_host_path_cmd\n# will break.\n\n\n# func_init_to_host_path_cmd\n# Ensures that function \"pointer\" variable $to_host_path_cmd is set to the\n# appropriate value, based on the value of $to_host_file_cmd.\nto_host_path_cmd=\nfunc_init_to_host_path_cmd ()\n{\n  $debug_cmd\n\n  if test -z \"$to_host_path_cmd\"; then\n    func_stripname 'func_convert_file_' '' \"$to_host_file_cmd\"\n    to_host_path_cmd=func_convert_path_$func_stripname_result\n  fi\n}\n\n\n# func_to_host_path ARG\n# Converts the path ARG from $build format to $host format. Return result\n# in func_to_host_path_result.\nfunc_to_host_path ()\n{\n  $debug_cmd\n\n  func_init_to_host_path_cmd\n  $to_host_path_cmd \"$1\"\n}\n# end func_to_host_path\n\n\n# func_convert_path_noop ARG\n# Copy ARG to func_to_host_path_result.\nfunc_convert_path_noop ()\n{\n  func_to_host_path_result=$1\n}\n# end func_convert_path_noop\n\n\n# func_convert_path_msys_to_w32 ARG\n# Convert path ARG from (mingw) MSYS to (mingw) w32 format; automatic\n# conversion to w32 is not available inside the cwrapper.  Returns result in\n# func_to_host_path_result.\nfunc_convert_path_msys_to_w32 ()\n{\n  $debug_cmd\n\n  func_to_host_path_result=$1\n  if test -n \"$1\"; then\n    # Remove leading and trailing path separator characters from ARG.  MSYS\n    # behavior is inconsistent here; cygpath turns them into '.;' and ';.';\n    # and winepath ignores them completely.\n    func_stripname : : \"$1\"\n    func_to_host_path_tmp1=$func_stripname_result\n    func_convert_core_msys_to_w32 \"$func_to_host_path_tmp1\"\n    func_to_host_path_result=$func_convert_core_msys_to_w32_result\n    func_convert_path_check : \";\" \\\n      \"$func_to_host_path_tmp1\" \"$func_to_host_path_result\"\n    func_convert_path_front_back_pathsep \":*\" \"*:\" \";\" \"$1\"\n  fi\n}\n# end func_convert_path_msys_to_w32\n\n\n# func_convert_path_cygwin_to_w32 ARG\n# Convert path ARG from Cygwin to w32 format.  Returns result in\n# func_to_host_file_result.\nfunc_convert_path_cygwin_to_w32 ()\n{\n  $debug_cmd\n\n  func_to_host_path_result=$1\n  if test -n \"$1\"; then\n    # See func_convert_path_msys_to_w32:\n    func_stripname : : \"$1\"\n    func_to_host_path_tmp1=$func_stripname_result\n    func_to_host_path_result=`cygpath -m -p \"$func_to_host_path_tmp1\"`\n    func_convert_path_check : \";\" \\\n      \"$func_to_host_path_tmp1\" \"$func_to_host_path_result\"\n    func_convert_path_front_back_pathsep \":*\" \"*:\" \";\" \"$1\"\n  fi\n}\n# end func_convert_path_cygwin_to_w32\n\n\n# func_convert_path_nix_to_w32 ARG\n# Convert path ARG from *nix to w32 format.  Requires a wine environment and\n# a working winepath.  Returns result in func_to_host_file_result.\nfunc_convert_path_nix_to_w32 ()\n{\n  $debug_cmd\n\n  func_to_host_path_result=$1\n  if test -n \"$1\"; then\n    # See func_convert_path_msys_to_w32:\n    func_stripname : : \"$1\"\n    func_to_host_path_tmp1=$func_stripname_result\n    func_convert_core_path_wine_to_w32 \"$func_to_host_path_tmp1\"\n    func_to_host_path_result=$func_convert_core_path_wine_to_w32_result\n    func_convert_path_check : \";\" \\\n      \"$func_to_host_path_tmp1\" \"$func_to_host_path_result\"\n    func_convert_path_front_back_pathsep \":*\" \"*:\" \";\" \"$1\"\n  fi\n}\n# end func_convert_path_nix_to_w32\n\n\n# func_convert_path_msys_to_cygwin ARG\n# Convert path ARG from MSYS to Cygwin format.  Requires LT_CYGPATH set.\n# Returns result in func_to_host_file_result.\nfunc_convert_path_msys_to_cygwin ()\n{\n  $debug_cmd\n\n  func_to_host_path_result=$1\n  if test -n \"$1\"; then\n    # See func_convert_path_msys_to_w32:\n    func_stripname : : \"$1\"\n    func_to_host_path_tmp1=$func_stripname_result\n    func_convert_core_msys_to_w32 \"$func_to_host_path_tmp1\"\n    func_cygpath -u -p \"$func_convert_core_msys_to_w32_result\"\n    func_to_host_path_result=$func_cygpath_result\n    func_convert_path_check : : \\\n      \"$func_to_host_path_tmp1\" \"$func_to_host_path_result\"\n    func_convert_path_front_back_pathsep \":*\" \"*:\" : \"$1\"\n  fi\n}\n# end func_convert_path_msys_to_cygwin\n\n\n# func_convert_path_nix_to_cygwin ARG\n# Convert path ARG from *nix to Cygwin format.  Requires Cygwin installed in a\n# a wine environment, working winepath, and LT_CYGPATH set.  Returns result in\n# func_to_host_file_result.\nfunc_convert_path_nix_to_cygwin ()\n{\n  $debug_cmd\n\n  func_to_host_path_result=$1\n  if test -n \"$1\"; then\n    # Remove leading and trailing path separator characters from\n    # ARG. msys behavior is inconsistent here, cygpath turns them\n    # into '.;' and ';.', and winepath ignores them completely.\n    func_stripname : : \"$1\"\n    func_to_host_path_tmp1=$func_stripname_result\n    func_convert_core_path_wine_to_w32 \"$func_to_host_path_tmp1\"\n    func_cygpath -u -p \"$func_convert_core_path_wine_to_w32_result\"\n    func_to_host_path_result=$func_cygpath_result\n    func_convert_path_check : : \\\n      \"$func_to_host_path_tmp1\" \"$func_to_host_path_result\"\n    func_convert_path_front_back_pathsep \":*\" \"*:\" : \"$1\"\n  fi\n}\n# end func_convert_path_nix_to_cygwin\n\n\n# func_dll_def_p FILE\n# True iff FILE is a Windows DLL '.def' file.\n# Keep in sync with _LT_DLL_DEF_P in libtool.m4\nfunc_dll_def_p ()\n{\n  $debug_cmd\n\n  func_dll_def_p_tmp=`$SED -n \\\n    -e 's/^[\t ]*//' \\\n    -e '/^\\(;.*\\)*$/d' \\\n    -e 's/^\\(EXPORTS\\|LIBRARY\\)\\([\t ].*\\)*$/DEF/p' \\\n    -e q \\\n    \"$1\"`\n  test DEF = \"$func_dll_def_p_tmp\"\n}\n\n\n# func_mode_compile arg...\nfunc_mode_compile ()\n{\n    $debug_cmd\n\n    # Get the compilation command and the source file.\n    base_compile=\n    srcfile=$nonopt  #  always keep a non-empty value in \"srcfile\"\n    suppress_opt=yes\n    suppress_output=\n    arg_mode=normal\n    libobj=\n    later=\n    pie_flag=\n\n    for arg\n    do\n      case $arg_mode in\n      arg  )\n\t# do not \"continue\".  Instead, add this to base_compile\n\tlastarg=$arg\n\targ_mode=normal\n\t;;\n\n      target )\n\tlibobj=$arg\n\targ_mode=normal\n\tcontinue\n\t;;\n\n      normal )\n\t# Accept any command-line options.\n\tcase $arg in\n\t-o)\n\t  test -n \"$libobj\" && \\\n\t    func_fatal_error \"you cannot specify '-o' more than once\"\n\t  arg_mode=target\n\t  continue\n\t  ;;\n\n\t-pie | -fpie | -fPIE)\n          func_append pie_flag \" $arg\"\n\t  continue\n\t  ;;\n\n\t-shared | -static | -prefer-pic | -prefer-non-pic)\n\t  func_append later \" $arg\"\n\t  continue\n\t  ;;\n\n\t-no-suppress)\n\t  suppress_opt=no\n\t  continue\n\t  ;;\n\n\t-Xcompiler)\n\t  arg_mode=arg  #  the next one goes into the \"base_compile\" arg list\n\t  continue      #  The current \"srcfile\" will either be retained or\n\t  ;;            #  replaced later.  I would guess that would be a bug.\n\n\t-Wc,*)\n\t  func_stripname '-Wc,' '' \"$arg\"\n\t  args=$func_stripname_result\n\t  lastarg=\n\t  save_ifs=$IFS; IFS=,\n\t  for arg in $args; do\n\t    IFS=$save_ifs\n\t    func_append_quoted lastarg \"$arg\"\n\t  done\n\t  IFS=$save_ifs\n\t  func_stripname ' ' '' \"$lastarg\"\n\t  lastarg=$func_stripname_result\n\n\t  # Add the arguments to base_compile.\n\t  func_append base_compile \" $lastarg\"\n\t  continue\n\t  ;;\n\n\t*)\n\t  # Accept the current argument as the source file.\n\t  # The previous \"srcfile\" becomes the current argument.\n\t  #\n\t  lastarg=$srcfile\n\t  srcfile=$arg\n\t  ;;\n\tesac  #  case $arg\n\t;;\n      esac    #  case $arg_mode\n\n      # Aesthetically quote the previous argument.\n      func_append_quoted base_compile \"$lastarg\"\n    done # for arg\n\n    case $arg_mode in\n    arg)\n      func_fatal_error \"you must specify an argument for -Xcompile\"\n      ;;\n    target)\n      func_fatal_error \"you must specify a target with '-o'\"\n      ;;\n    *)\n      # Get the name of the library object.\n      test -z \"$libobj\" && {\n\tfunc_basename \"$srcfile\"\n\tlibobj=$func_basename_result\n      }\n      ;;\n    esac\n\n    # Recognize several different file suffixes.\n    # If the user specifies -o file.o, it is replaced with file.lo\n    case $libobj in\n    *.[cCFSifmso] | \\\n    *.ada | *.adb | *.ads | *.asm | \\\n    *.c++ | *.cc | *.ii | *.class | *.cpp | *.cxx | \\\n    *.[fF][09]? | *.for | *.java | *.go | *.obj | *.sx | *.cu | *.cup)\n      func_xform \"$libobj\"\n      libobj=$func_xform_result\n      ;;\n    esac\n\n    case $libobj in\n    *.lo) func_lo2o \"$libobj\"; obj=$func_lo2o_result ;;\n    *)\n      func_fatal_error \"cannot determine name of library object from '$libobj'\"\n      ;;\n    esac\n\n    func_infer_tag $base_compile\n\n    for arg in $later; do\n      case $arg in\n      -shared)\n\ttest yes = \"$build_libtool_libs\" \\\n\t  || func_fatal_configuration \"cannot build a shared library\"\n\tbuild_old_libs=no\n\tcontinue\n\t;;\n\n      -static)\n\tbuild_libtool_libs=no\n\tbuild_old_libs=yes\n\tcontinue\n\t;;\n\n      -prefer-pic)\n\tpic_mode=yes\n\tcontinue\n\t;;\n\n      -prefer-non-pic)\n\tpic_mode=no\n\tcontinue\n\t;;\n      esac\n    done\n\n    func_quote_arg pretty \"$libobj\"\n    test \"X$libobj\" != \"X$func_quote_arg_result\" \\\n      && $ECHO \"X$libobj\" | $GREP '[]~#^*{};<>?\"'\"'\"'\t &()|`$[]' \\\n      && func_warning \"libobj name '$libobj' may not contain shell special characters.\"\n    func_dirname_and_basename \"$obj\" \"/\" \"\"\n    objname=$func_basename_result\n    xdir=$func_dirname_result\n    lobj=$xdir$objdir/$objname\n\n    test -z \"$base_compile\" && \\\n      func_fatal_help \"you must specify a compilation command\"\n\n    # Delete any leftover library objects.\n    if test yes = \"$build_old_libs\"; then\n      removelist=\"$obj $lobj $libobj ${libobj}T\"\n    else\n      removelist=\"$lobj $libobj ${libobj}T\"\n    fi\n\n    # On Cygwin there's no \"real\" PIC flag so we must build both object types\n    case $host_os in\n    cygwin* | mingw* | pw32* | os2* | cegcc*)\n      pic_mode=default\n      ;;\n    esac\n    if test no = \"$pic_mode\" && test pass_all != \"$deplibs_check_method\"; then\n      # non-PIC code in shared libraries is not supported\n      pic_mode=default\n    fi\n\n    # Calculate the filename of the output object if compiler does\n    # not support -o with -c\n    if test no = \"$compiler_c_o\"; then\n      output_obj=`$ECHO \"$srcfile\" | $SED 's%^.*/%%; s%\\.[^.]*$%%'`.$objext\n      lockfile=$output_obj.lock\n    else\n      output_obj=\n      need_locks=no\n      lockfile=\n    fi\n\n    # Lock this critical section if it is needed\n    # We use this script file to make the link, it avoids creating a new file\n    if test yes = \"$need_locks\"; then\n      until $opt_dry_run || ln \"$progpath\" \"$lockfile\" 2>/dev/null; do\n\tfunc_echo \"Waiting for $lockfile to be removed\"\n\tsleep 2\n      done\n    elif test warn = \"$need_locks\"; then\n      if test -f \"$lockfile\"; then\n\t$ECHO \"\\\n*** ERROR, $lockfile exists and contains:\n`cat $lockfile 2>/dev/null`\n\nThis indicates that another process is trying to use the same\ntemporary object file, and libtool could not work around it because\nyour compiler does not support '-c' and '-o' together.  If you\nrepeat this compilation, it may succeed, by chance, but you had better\navoid parallel builds (make -j) in this platform, or get a better\ncompiler.\"\n\n\t$opt_dry_run || $RM $removelist\n\texit $EXIT_FAILURE\n      fi\n      func_append removelist \" $output_obj\"\n      $ECHO \"$srcfile\" > \"$lockfile\"\n    fi\n\n    $opt_dry_run || $RM $removelist\n    func_append removelist \" $lockfile\"\n    trap '$opt_dry_run || $RM $removelist; exit $EXIT_FAILURE' 1 2 15\n\n    func_to_tool_file \"$srcfile\" func_convert_file_msys_to_w32\n    srcfile=$func_to_tool_file_result\n    func_quote_arg pretty \"$srcfile\"\n    qsrcfile=$func_quote_arg_result\n\n    # Only build a PIC object if we are building libtool libraries.\n    if test yes = \"$build_libtool_libs\"; then\n      # Without this assignment, base_compile gets emptied.\n      fbsd_hideous_sh_bug=$base_compile\n\n      if test no != \"$pic_mode\"; then\n\tcommand=\"$base_compile $qsrcfile $pic_flag\"\n      else\n\t# Don't build PIC code\n\tcommand=\"$base_compile $qsrcfile\"\n      fi\n\n      func_mkdir_p \"$xdir$objdir\"\n\n      if test -z \"$output_obj\"; then\n\t# Place PIC objects in $objdir\n\tfunc_append command \" -o $lobj\"\n      fi\n\n      func_show_eval_locale \"$command\"\t\\\n          'test -n \"$output_obj\" && $RM $removelist; exit $EXIT_FAILURE'\n\n      if test warn = \"$need_locks\" &&\n\t test \"X`cat $lockfile 2>/dev/null`\" != \"X$srcfile\"; then\n\t$ECHO \"\\\n*** ERROR, $lockfile contains:\n`cat $lockfile 2>/dev/null`\n\nbut it should contain:\n$srcfile\n\nThis indicates that another process is trying to use the same\ntemporary object file, and libtool could not work around it because\nyour compiler does not support '-c' and '-o' together.  If you\nrepeat this compilation, it may succeed, by chance, but you had better\navoid parallel builds (make -j) in this platform, or get a better\ncompiler.\"\n\n\t$opt_dry_run || $RM $removelist\n\texit $EXIT_FAILURE\n      fi\n\n      # Just move the object if needed, then go on to compile the next one\n      if test -n \"$output_obj\" && test \"X$output_obj\" != \"X$lobj\"; then\n\tfunc_show_eval '$MV \"$output_obj\" \"$lobj\"' \\\n\t  'error=$?; $opt_dry_run || $RM $removelist; exit $error'\n      fi\n\n      # Allow error messages only from the first compilation.\n      if test yes = \"$suppress_opt\"; then\n\tsuppress_output=' >/dev/null 2>&1'\n      fi\n    fi\n\n    # Only build a position-dependent object if we build old libraries.\n    if test yes = \"$build_old_libs\"; then\n      if test yes != \"$pic_mode\"; then\n\t# Don't build PIC code\n\tcommand=\"$base_compile $qsrcfile$pie_flag\"\n      else\n\tcommand=\"$base_compile $qsrcfile $pic_flag\"\n      fi\n      if test yes = \"$compiler_c_o\"; then\n\tfunc_append command \" -o $obj\"\n      fi\n\n      # Suppress compiler output if we already did a PIC compilation.\n      func_append command \"$suppress_output\"\n      func_show_eval_locale \"$command\" \\\n        '$opt_dry_run || $RM $removelist; exit $EXIT_FAILURE'\n\n      if test warn = \"$need_locks\" &&\n\t test \"X`cat $lockfile 2>/dev/null`\" != \"X$srcfile\"; then\n\t$ECHO \"\\\n*** ERROR, $lockfile contains:\n`cat $lockfile 2>/dev/null`\n\nbut it should contain:\n$srcfile\n\nThis indicates that another process is trying to use the same\ntemporary object file, and libtool could not work around it because\nyour compiler does not support '-c' and '-o' together.  If you\nrepeat this compilation, it may succeed, by chance, but you had better\navoid parallel builds (make -j) in this platform, or get a better\ncompiler.\"\n\n\t$opt_dry_run || $RM $removelist\n\texit $EXIT_FAILURE\n      fi\n\n      # Just move the object if needed\n      if test -n \"$output_obj\" && test \"X$output_obj\" != \"X$obj\"; then\n\tfunc_show_eval '$MV \"$output_obj\" \"$obj\"' \\\n\t  'error=$?; $opt_dry_run || $RM $removelist; exit $error'\n      fi\n    fi\n\n    $opt_dry_run || {\n      func_write_libtool_object \"$libobj\" \"$objdir/$objname\" \"$objname\"\n\n      # Unlock the critical section if it was locked\n      if test no != \"$need_locks\"; then\n\tremovelist=$lockfile\n        $RM \"$lockfile\"\n      fi\n    }\n\n    exit $EXIT_SUCCESS\n}\n\n$opt_help || {\n  test compile = \"$opt_mode\" && func_mode_compile ${1+\"$@\"}\n}\n\nfunc_mode_help ()\n{\n    # We need to display help for each of the modes.\n    case $opt_mode in\n      \"\")\n        # Generic help is extracted from the usage comments\n        # at the start of this file.\n        func_help\n        ;;\n\n      clean)\n        $ECHO \\\n\"Usage: $progname [OPTION]... --mode=clean RM [RM-OPTION]... FILE...\n\nRemove files from the build directory.\n\nRM is the name of the program to use to delete files associated with each FILE\n(typically '/bin/rm').  RM-OPTIONS are options (such as '-f') to be passed\nto RM.\n\nIf FILE is a libtool library, object or program, all the files associated\nwith it are deleted. Otherwise, only FILE itself is deleted using RM.\"\n        ;;\n\n      compile)\n      $ECHO \\\n\"Usage: $progname [OPTION]... --mode=compile COMPILE-COMMAND... SOURCEFILE\n\nCompile a source file into a libtool library object.\n\nThis mode accepts the following additional options:\n\n  -o OUTPUT-FILE    set the output file name to OUTPUT-FILE\n  -no-suppress      do not suppress compiler output for multiple passes\n  -prefer-pic       try to build PIC objects only\n  -prefer-non-pic   try to build non-PIC objects only\n  -shared           do not build a '.o' file suitable for static linking\n  -static           only build a '.o' file suitable for static linking\n  -Wc,FLAG\n  -Xcompiler FLAG   pass FLAG directly to the compiler\n\nCOMPILE-COMMAND is a command to be used in creating a 'standard' object file\nfrom the given SOURCEFILE.\n\nThe output file name is determined by removing the directory component from\nSOURCEFILE, then substituting the C source code suffix '.c' with the\nlibrary object suffix, '.lo'.\"\n        ;;\n\n      execute)\n        $ECHO \\\n\"Usage: $progname [OPTION]... --mode=execute COMMAND [ARGS]...\n\nAutomatically set library path, then run a program.\n\nThis mode accepts the following additional options:\n\n  -dlopen FILE      add the directory containing FILE to the library path\n\nThis mode sets the library path environment variable according to '-dlopen'\nflags.\n\nIf any of the ARGS are libtool executable wrappers, then they are translated\ninto their corresponding uninstalled binary, and any of their required library\ndirectories are added to the library path.\n\nThen, COMMAND is executed, with ARGS as arguments.\"\n        ;;\n\n      finish)\n        $ECHO \\\n\"Usage: $progname [OPTION]... --mode=finish [LIBDIR]...\n\nComplete the installation of libtool libraries.\n\nEach LIBDIR is a directory that contains libtool libraries.\n\nThe commands that this mode executes may require superuser privileges.  Use\nthe '--dry-run' option if you just want to see what would be executed.\"\n        ;;\n\n      install)\n        $ECHO \\\n\"Usage: $progname [OPTION]... --mode=install INSTALL-COMMAND...\n\nInstall executables or libraries.\n\nINSTALL-COMMAND is the installation command.  The first component should be\neither the 'install' or 'cp' program.\n\nThe following components of INSTALL-COMMAND are treated specially:\n\n  -inst-prefix-dir PREFIX-DIR  Use PREFIX-DIR as a staging area for installation\n\nThe rest of the components are interpreted as arguments to that command (only\nBSD-compatible install options are recognized).\"\n        ;;\n\n      link)\n        $ECHO \\\n\"Usage: $progname [OPTION]... --mode=link LINK-COMMAND...\n\nLink object files or libraries together to form another library, or to\ncreate an executable program.\n\nLINK-COMMAND is a command using the C compiler that you would use to create\na program from several object files.\n\nThe following components of LINK-COMMAND are treated specially:\n\n  -all-static       do not do any dynamic linking at all\n  -avoid-version    do not add a version suffix if possible\n  -bindir BINDIR    specify path to binaries directory (for systems where\n                    libraries must be found in the PATH setting at runtime)\n  -dlopen FILE      '-dlpreopen' FILE if it cannot be dlopened at runtime\n  -dlpreopen FILE   link in FILE and add its symbols to lt_preloaded_symbols\n  -export-dynamic   allow symbols from OUTPUT-FILE to be resolved with dlsym(3)\n  -export-symbols SYMFILE\n                    try to export only the symbols listed in SYMFILE\n  -export-symbols-regex REGEX\n                    try to export only the symbols matching REGEX\n  -LLIBDIR          search LIBDIR for required installed libraries\n  -lNAME            OUTPUT-FILE requires the installed library libNAME\n  -module           build a library that can dlopened\n  -no-fast-install  disable the fast-install mode\n  -no-install       link a not-installable executable\n  -no-undefined     declare that a library does not refer to external symbols\n  -o OUTPUT-FILE    create OUTPUT-FILE from the specified objects\n  -objectlist FILE  use a list of object files found in FILE to specify objects\n  -os2dllname NAME  force a short DLL name on OS/2 (no effect on other OSes)\n  -precious-files-regex REGEX\n                    don't remove output files matching REGEX\n  -release RELEASE  specify package release information\n  -rpath LIBDIR     the created library will eventually be installed in LIBDIR\n  -R[ ]LIBDIR       add LIBDIR to the runtime path of programs and libraries\n  -shared           only do dynamic linking of libtool libraries\n  -shrext SUFFIX    override the standard shared library file extension\n  -static           do not do any dynamic linking of uninstalled libtool libraries\n  -static-libtool-libs\n                    do not do any dynamic linking of libtool libraries\n  -version-info CURRENT[:REVISION[:AGE]]\n                    specify library version info [each variable defaults to 0]\n  -weak LIBNAME     declare that the target provides the LIBNAME interface\n  -Wc,FLAG\n  -Xcompiler FLAG   pass linker-specific FLAG directly to the compiler\n  -Wa,FLAG\n  -Xassembler FLAG  pass linker-specific FLAG directly to the assembler\n  -Wl,FLAG\n  -Xlinker FLAG     pass linker-specific FLAG directly to the linker\n  -XCClinker FLAG   pass link-specific FLAG to the compiler driver (CC)\n\nAll other options (arguments beginning with '-') are ignored.\n\nEvery other argument is treated as a filename.  Files ending in '.la' are\ntreated as uninstalled libtool libraries, other files are standard or library\nobject files.\n\nIf the OUTPUT-FILE ends in '.la', then a libtool library is created,\nonly library objects ('.lo' files) may be specified, and '-rpath' is\nrequired, except when creating a convenience library.\n\nIf OUTPUT-FILE ends in '.a' or '.lib', then a standard library is created\nusing 'ar' and 'ranlib', or on Windows using 'lib'.\n\nIf OUTPUT-FILE ends in '.lo' or '.$objext', then a reloadable object file\nis created, otherwise an executable program is created.\"\n        ;;\n\n      uninstall)\n        $ECHO \\\n\"Usage: $progname [OPTION]... --mode=uninstall RM [RM-OPTION]... FILE...\n\nRemove libraries from an installation directory.\n\nRM is the name of the program to use to delete files associated with each FILE\n(typically '/bin/rm').  RM-OPTIONS are options (such as '-f') to be passed\nto RM.\n\nIf FILE is a libtool library, all the files associated with it are deleted.\nOtherwise, only FILE itself is deleted using RM.\"\n        ;;\n\n      *)\n        func_fatal_help \"invalid operation mode '$opt_mode'\"\n        ;;\n    esac\n\n    echo\n    $ECHO \"Try '$progname --help' for more information about other modes.\"\n}\n\n# Now that we've collected a possible --mode arg, show help if necessary\nif $opt_help; then\n  if test : = \"$opt_help\"; then\n    func_mode_help\n  else\n    {\n      func_help noexit\n      for opt_mode in compile link execute install finish uninstall clean; do\n\tfunc_mode_help\n      done\n    } | $SED -n '1p; 2,$s/^Usage:/  or: /p'\n    {\n      func_help noexit\n      for opt_mode in compile link execute install finish uninstall clean; do\n\techo\n\tfunc_mode_help\n      done\n    } |\n    $SED '1d\n      /^When reporting/,/^Report/{\n\tH\n\td\n      }\n      $x\n      /information about other modes/d\n      /more detailed .*MODE/d\n      s/^Usage:.*--mode=\\([^ ]*\\) .*/Description of \\1 mode:/'\n  fi\n  exit $?\nfi\n\n\n# func_mode_execute arg...\nfunc_mode_execute ()\n{\n    $debug_cmd\n\n    # The first argument is the command name.\n    cmd=$nonopt\n    test -z \"$cmd\" && \\\n      func_fatal_help \"you must specify a COMMAND\"\n\n    # Handle -dlopen flags immediately.\n    for file in $opt_dlopen; do\n      test -f \"$file\" \\\n\t|| func_fatal_help \"'$file' is not a file\"\n\n      dir=\n      case $file in\n      *.la)\n\tfunc_resolve_sysroot \"$file\"\n\tfile=$func_resolve_sysroot_result\n\n\t# Check to see that this really is a libtool archive.\n\tfunc_lalib_unsafe_p \"$file\" \\\n\t  || func_fatal_help \"'$lib' is not a valid libtool archive\"\n\n\t# Read the libtool library.\n\tdlname=\n\tlibrary_names=\n\tfunc_source \"$file\"\n\n\t# Skip this library if it cannot be dlopened.\n\tif test -z \"$dlname\"; then\n\t  # Warn if it was a shared library.\n\t  test -n \"$library_names\" && \\\n\t    func_warning \"'$file' was not linked with '-export-dynamic'\"\n\t  continue\n\tfi\n\n\tfunc_dirname \"$file\" \"\" \".\"\n\tdir=$func_dirname_result\n\n\tif test -f \"$dir/$objdir/$dlname\"; then\n\t  func_append dir \"/$objdir\"\n\telse\n\t  if test ! -f \"$dir/$dlname\"; then\n\t    func_fatal_error \"cannot find '$dlname' in '$dir' or '$dir/$objdir'\"\n\t  fi\n\tfi\n\t;;\n\n      *.lo)\n\t# Just add the directory containing the .lo file.\n\tfunc_dirname \"$file\" \"\" \".\"\n\tdir=$func_dirname_result\n\t;;\n\n      *)\n\tfunc_warning \"'-dlopen' is ignored for non-libtool libraries and objects\"\n\tcontinue\n\t;;\n      esac\n\n      # Get the absolute pathname.\n      absdir=`cd \"$dir\" && pwd`\n      test -n \"$absdir\" && dir=$absdir\n\n      # Now add the directory to shlibpath_var.\n      if eval \"test -z \\\"\\$$shlibpath_var\\\"\"; then\n\teval \"$shlibpath_var=\\\"\\$dir\\\"\"\n      else\n\teval \"$shlibpath_var=\\\"\\$dir:\\$$shlibpath_var\\\"\"\n      fi\n    done\n\n    # This variable tells wrapper scripts just to set shlibpath_var\n    # rather than running their programs.\n    libtool_execute_magic=$magic\n\n    # Check if any of the arguments is a wrapper script.\n    args=\n    for file\n    do\n      case $file in\n      -* | *.la | *.lo ) ;;\n      *)\n\t# Do a test to see if this is really a libtool program.\n\tif func_ltwrapper_script_p \"$file\"; then\n\t  func_source \"$file\"\n\t  # Transform arg to wrapped name.\n\t  file=$progdir/$program\n\telif func_ltwrapper_executable_p \"$file\"; then\n\t  func_ltwrapper_scriptname \"$file\"\n\t  func_source \"$func_ltwrapper_scriptname_result\"\n\t  # Transform arg to wrapped name.\n\t  file=$progdir/$program\n\tfi\n\t;;\n      esac\n      # Quote arguments (to preserve shell metacharacters).\n      func_append_quoted args \"$file\"\n    done\n\n    if $opt_dry_run; then\n      # Display what would be done.\n      if test -n \"$shlibpath_var\"; then\n\teval \"\\$ECHO \\\"\\$shlibpath_var=\\$$shlibpath_var\\\"\"\n\techo \"export $shlibpath_var\"\n      fi\n      $ECHO \"$cmd$args\"\n      exit $EXIT_SUCCESS\n    else\n      if test -n \"$shlibpath_var\"; then\n\t# Export the shlibpath_var.\n\teval \"export $shlibpath_var\"\n      fi\n\n      # Restore saved environment variables\n      for lt_var in LANG LANGUAGE LC_ALL LC_CTYPE LC_COLLATE LC_MESSAGES\n      do\n\teval \"if test \\\"\\${save_$lt_var+set}\\\" = set; then\n                $lt_var=\\$save_$lt_var; export $lt_var\n\t      else\n\t\t$lt_unset $lt_var\n\t      fi\"\n      done\n\n      # Now prepare to actually exec the command.\n      exec_cmd=\\$cmd$args\n    fi\n}\n\ntest execute = \"$opt_mode\" && func_mode_execute ${1+\"$@\"}\n\n\n# func_mode_finish arg...\nfunc_mode_finish ()\n{\n    $debug_cmd\n\n    libs=\n    libdirs=\n    admincmds=\n\n    for opt in \"$nonopt\" ${1+\"$@\"}\n    do\n      if test -d \"$opt\"; then\n\tfunc_append libdirs \" $opt\"\n\n      elif test -f \"$opt\"; then\n\tif func_lalib_unsafe_p \"$opt\"; then\n\t  func_append libs \" $opt\"\n\telse\n\t  func_warning \"'$opt' is not a valid libtool archive\"\n\tfi\n\n      else\n\tfunc_fatal_error \"invalid argument '$opt'\"\n      fi\n    done\n\n    if test -n \"$libs\"; then\n      if test -n \"$lt_sysroot\"; then\n        sysroot_regex=`$ECHO \"$lt_sysroot\" | $SED \"$sed_make_literal_regex\"`\n        sysroot_cmd=\"s/\\([ ']\\)$sysroot_regex/\\1/g;\"\n      else\n        sysroot_cmd=\n      fi\n\n      # Remove sysroot references\n      if $opt_dry_run; then\n        for lib in $libs; do\n          echo \"removing references to $lt_sysroot and '=' prefixes from $lib\"\n        done\n      else\n        tmpdir=`func_mktempdir`\n        for lib in $libs; do\n\t  $SED -e \"$sysroot_cmd s/\\([ ']-[LR]\\)=/\\1/g; s/\\([ ']\\)=/\\1/g\" $lib \\\n\t    > $tmpdir/tmp-la\n\t  mv -f $tmpdir/tmp-la $lib\n\tdone\n        ${RM}r \"$tmpdir\"\n      fi\n    fi\n\n    if test -n \"$finish_cmds$finish_eval\" && test -n \"$libdirs\"; then\n      for libdir in $libdirs; do\n\tif test -n \"$finish_cmds\"; then\n\t  # Do each command in the finish commands.\n\t  func_execute_cmds \"$finish_cmds\" 'admincmds=\"$admincmds\n'\"$cmd\"'\"'\n\tfi\n\tif test -n \"$finish_eval\"; then\n\t  # Do the single finish_eval.\n\t  eval cmds=\\\"$finish_eval\\\"\n\t  $opt_dry_run || eval \"$cmds\" || func_append admincmds \"\n       $cmds\"\n\tfi\n      done\n    fi\n\n    # Exit here if they wanted silent mode.\n    $opt_quiet && exit $EXIT_SUCCESS\n\n    if test -n \"$finish_cmds$finish_eval\" && test -n \"$libdirs\"; then\n      echo \"----------------------------------------------------------------------\"\n      echo \"Libraries have been installed in:\"\n      for libdir in $libdirs; do\n\t$ECHO \"   $libdir\"\n      done\n      echo\n      echo \"If you ever happen to want to link against installed libraries\"\n      echo \"in a given directory, LIBDIR, you must either use libtool, and\"\n      echo \"specify the full pathname of the library, or use the '-LLIBDIR'\"\n      echo \"flag during linking and do at least one of the following:\"\n      if test -n \"$shlibpath_var\"; then\n\techo \"   - add LIBDIR to the '$shlibpath_var' environment variable\"\n\techo \"     during execution\"\n      fi\n      if test -n \"$runpath_var\"; then\n\techo \"   - add LIBDIR to the '$runpath_var' environment variable\"\n\techo \"     during linking\"\n      fi\n      if test -n \"$hardcode_libdir_flag_spec\"; then\n\tlibdir=LIBDIR\n\teval flag=\\\"$hardcode_libdir_flag_spec\\\"\n\n\t$ECHO \"   - use the '$flag' linker flag\"\n      fi\n      if test -n \"$admincmds\"; then\n\t$ECHO \"   - have your system administrator run these commands:$admincmds\"\n      fi\n      if test -f /etc/ld.so.conf; then\n\techo \"   - have your system administrator add LIBDIR to '/etc/ld.so.conf'\"\n      fi\n      echo\n\n      echo \"See any operating system documentation about shared libraries for\"\n      case $host in\n\tsolaris2.[6789]|solaris2.1[0-9])\n\t  echo \"more information, such as the ld(1), crle(1) and ld.so(8) manual\"\n\t  echo \"pages.\"\n\t  ;;\n\t*)\n\t  echo \"more information, such as the ld(1) and ld.so(8) manual pages.\"\n\t  ;;\n      esac\n      echo \"----------------------------------------------------------------------\"\n    fi\n    exit $EXIT_SUCCESS\n}\n\ntest finish = \"$opt_mode\" && func_mode_finish ${1+\"$@\"}\n\n\n# func_mode_install arg...\nfunc_mode_install ()\n{\n    $debug_cmd\n\n    # There may be an optional sh(1) argument at the beginning of\n    # install_prog (especially on Windows NT).\n    if test \"$SHELL\" = \"$nonopt\" || test /bin/sh = \"$nonopt\" ||\n       # Allow the use of GNU shtool's install command.\n       case $nonopt in *shtool*) :;; *) false;; esac\n    then\n      # Aesthetically quote it.\n      func_quote_arg pretty \"$nonopt\"\n      install_prog=\"$func_quote_arg_result \"\n      arg=$1\n      shift\n    else\n      install_prog=\n      arg=$nonopt\n    fi\n\n    # The real first argument should be the name of the installation program.\n    # Aesthetically quote it.\n    func_quote_arg pretty \"$arg\"\n    func_append install_prog \"$func_quote_arg_result\"\n    install_shared_prog=$install_prog\n    case \" $install_prog \" in\n      *[\\\\\\ /]cp\\ *) install_cp=: ;;\n      *) install_cp=false ;;\n    esac\n\n    # We need to accept at least all the BSD install flags.\n    dest=\n    files=\n    opts=\n    prev=\n    install_type=\n    isdir=false\n    stripme=\n    no_mode=:\n    for arg\n    do\n      arg2=\n      if test -n \"$dest\"; then\n\tfunc_append files \" $dest\"\n\tdest=$arg\n\tcontinue\n      fi\n\n      case $arg in\n      -d) isdir=: ;;\n      -f)\n\tif $install_cp; then :; else\n\t  prev=$arg\n\tfi\n\t;;\n      -g | -m | -o)\n\tprev=$arg\n\t;;\n      -s)\n\tstripme=\" -s\"\n\tcontinue\n\t;;\n      -*)\n\t;;\n      *)\n\t# If the previous option needed an argument, then skip it.\n\tif test -n \"$prev\"; then\n\t  if test X-m = \"X$prev\" && test -n \"$install_override_mode\"; then\n\t    arg2=$install_override_mode\n\t    no_mode=false\n\t  fi\n\t  prev=\n\telse\n\t  dest=$arg\n\t  continue\n\tfi\n\t;;\n      esac\n\n      # Aesthetically quote the argument.\n      func_quote_arg pretty \"$arg\"\n      func_append install_prog \" $func_quote_arg_result\"\n      if test -n \"$arg2\"; then\n\tfunc_quote_arg pretty \"$arg2\"\n      fi\n      func_append install_shared_prog \" $func_quote_arg_result\"\n    done\n\n    test -z \"$install_prog\" && \\\n      func_fatal_help \"you must specify an install program\"\n\n    test -n \"$prev\" && \\\n      func_fatal_help \"the '$prev' option requires an argument\"\n\n    if test -n \"$install_override_mode\" && $no_mode; then\n      if $install_cp; then :; else\n\tfunc_quote_arg pretty \"$install_override_mode\"\n\tfunc_append install_shared_prog \" -m $func_quote_arg_result\"\n      fi\n    fi\n\n    if test -z \"$files\"; then\n      if test -z \"$dest\"; then\n\tfunc_fatal_help \"no file or destination specified\"\n      else\n\tfunc_fatal_help \"you must specify a destination\"\n      fi\n    fi\n\n    # Strip any trailing slash from the destination.\n    func_stripname '' '/' \"$dest\"\n    dest=$func_stripname_result\n\n    # Check to see that the destination is a directory.\n    test -d \"$dest\" && isdir=:\n    if $isdir; then\n      destdir=$dest\n      destname=\n    else\n      func_dirname_and_basename \"$dest\" \"\" \".\"\n      destdir=$func_dirname_result\n      destname=$func_basename_result\n\n      # Not a directory, so check to see that there is only one file specified.\n      set dummy $files; shift\n      test \"$#\" -gt 1 && \\\n\tfunc_fatal_help \"'$dest' is not a directory\"\n    fi\n    case $destdir in\n    [\\\\/]* | [A-Za-z]:[\\\\/]*) ;;\n    *)\n      for file in $files; do\n\tcase $file in\n\t*.lo) ;;\n\t*)\n\t  func_fatal_help \"'$destdir' must be an absolute directory name\"\n\t  ;;\n\tesac\n      done\n      ;;\n    esac\n\n    # This variable tells wrapper scripts just to set variables rather\n    # than running their programs.\n    libtool_install_magic=$magic\n\n    staticlibs=\n    future_libdirs=\n    current_libdirs=\n    for file in $files; do\n\n      # Do each installation.\n      case $file in\n      *.$libext)\n\t# Do the static libraries later.\n\tfunc_append staticlibs \" $file\"\n\t;;\n\n      *.la)\n\tfunc_resolve_sysroot \"$file\"\n\tfile=$func_resolve_sysroot_result\n\n\t# Check to see that this really is a libtool archive.\n\tfunc_lalib_unsafe_p \"$file\" \\\n\t  || func_fatal_help \"'$file' is not a valid libtool archive\"\n\n\tlibrary_names=\n\told_library=\n\trelink_command=\n\tfunc_source \"$file\"\n\n\t# Add the libdir to current_libdirs if it is the destination.\n\tif test \"X$destdir\" = \"X$libdir\"; then\n\t  case \"$current_libdirs \" in\n\t  *\" $libdir \"*) ;;\n\t  *) func_append current_libdirs \" $libdir\" ;;\n\t  esac\n\telse\n\t  # Note the libdir as a future libdir.\n\t  case \"$future_libdirs \" in\n\t  *\" $libdir \"*) ;;\n\t  *) func_append future_libdirs \" $libdir\" ;;\n\t  esac\n\tfi\n\n\tfunc_dirname \"$file\" \"/\" \"\"\n\tdir=$func_dirname_result\n\tfunc_append dir \"$objdir\"\n\n\tif test -n \"$relink_command\"; then\n\t  # Determine the prefix the user has applied to our future dir.\n\t  inst_prefix_dir=`$ECHO \"$destdir\" | $SED -e \"s%$libdir\\$%%\"`\n\n\t  # Don't allow the user to place us outside of our expected\n\t  # location b/c this prevents finding dependent libraries that\n\t  # are installed to the same prefix.\n\t  # At present, this check doesn't affect windows .dll's that\n\t  # are installed into $libdir/../bin (currently, that works fine)\n\t  # but it's something to keep an eye on.\n\t  test \"$inst_prefix_dir\" = \"$destdir\" && \\\n\t    func_fatal_error \"error: cannot install '$file' to a directory not ending in $libdir\"\n\n\t  if test -n \"$inst_prefix_dir\"; then\n\t    # Stick the inst_prefix_dir data into the link command.\n\t    relink_command=`$ECHO \"$relink_command\" | $SED \"s%@inst_prefix_dir@%-inst-prefix-dir $inst_prefix_dir%\"`\n\t  else\n\t    relink_command=`$ECHO \"$relink_command\" | $SED \"s%@inst_prefix_dir@%%\"`\n\t  fi\n\n\t  func_warning \"relinking '$file'\"\n\t  func_show_eval \"$relink_command\" \\\n\t    'func_fatal_error \"error: relink '\\''$file'\\'' with the above command before installing it\"'\n\tfi\n\n\t# See the names of the shared library.\n\tset dummy $library_names; shift\n\tif test -n \"$1\"; then\n\t  realname=$1\n\t  shift\n\n\t  srcname=$realname\n\t  test -n \"$relink_command\" && srcname=${realname}T\n\n\t  # Install the shared library and build the symlinks.\n\t  func_show_eval \"$install_shared_prog $dir/$srcname $destdir/$realname\" \\\n\t      'exit $?'\n\t  tstripme=$stripme\n\t  case $host_os in\n\t  cygwin* | mingw* | pw32* | cegcc*)\n\t    case $realname in\n\t    *.dll.a)\n\t      tstripme=\n\t      ;;\n\t    esac\n\t    ;;\n\t  os2*)\n\t    case $realname in\n\t    *_dll.a)\n\t      tstripme=\n\t      ;;\n\t    esac\n\t    ;;\n\t  esac\n\t  if test -n \"$tstripme\" && test -n \"$striplib\"; then\n\t    func_show_eval \"$striplib $destdir/$realname\" 'exit $?'\n\t  fi\n\n\t  if test \"$#\" -gt 0; then\n\t    # Delete the old symlinks, and create new ones.\n\t    # Try 'ln -sf' first, because the 'ln' binary might depend on\n\t    # the symlink we replace!  Solaris /bin/ln does not understand -f,\n\t    # so we also need to try rm && ln -s.\n\t    for linkname\n\t    do\n\t      test \"$linkname\" != \"$realname\" \\\n\t\t&& func_show_eval \"(cd $destdir && { $LN_S -f $realname $linkname || { $RM $linkname && $LN_S $realname $linkname; }; })\"\n\t    done\n\t  fi\n\n\t  # Do each command in the postinstall commands.\n\t  lib=$destdir/$realname\n\t  func_execute_cmds \"$postinstall_cmds\" 'exit $?'\n\tfi\n\n\t# Install the pseudo-library for information purposes.\n\tfunc_basename \"$file\"\n\tname=$func_basename_result\n\tinstname=$dir/${name}i\n\tfunc_show_eval \"$install_prog $instname $destdir/$name\" 'exit $?'\n\n\t# Maybe install the static library, too.\n\ttest -n \"$old_library\" && func_append staticlibs \" $dir/$old_library\"\n\t;;\n\n      *.lo)\n\t# Install (i.e. copy) a libtool object.\n\n\t# Figure out destination file name, if it wasn't already specified.\n\tif test -n \"$destname\"; then\n\t  destfile=$destdir/$destname\n\telse\n\t  func_basename \"$file\"\n\t  destfile=$func_basename_result\n\t  destfile=$destdir/$destfile\n\tfi\n\n\t# Deduce the name of the destination old-style object file.\n\tcase $destfile in\n\t*.lo)\n\t  func_lo2o \"$destfile\"\n\t  staticdest=$func_lo2o_result\n\t  ;;\n\t*.$objext)\n\t  staticdest=$destfile\n\t  destfile=\n\t  ;;\n\t*)\n\t  func_fatal_help \"cannot copy a libtool object to '$destfile'\"\n\t  ;;\n\tesac\n\n\t# Install the libtool object if requested.\n\ttest -n \"$destfile\" && \\\n\t  func_show_eval \"$install_prog $file $destfile\" 'exit $?'\n\n\t# Install the old object if enabled.\n\tif test yes = \"$build_old_libs\"; then\n\t  # Deduce the name of the old-style object file.\n\t  func_lo2o \"$file\"\n\t  staticobj=$func_lo2o_result\n\t  func_show_eval \"$install_prog \\$staticobj \\$staticdest\" 'exit $?'\n\tfi\n\texit $EXIT_SUCCESS\n\t;;\n\n      *)\n\t# Figure out destination file name, if it wasn't already specified.\n\tif test -n \"$destname\"; then\n\t  destfile=$destdir/$destname\n\telse\n\t  func_basename \"$file\"\n\t  destfile=$func_basename_result\n\t  destfile=$destdir/$destfile\n\tfi\n\n\t# If the file is missing, and there is a .exe on the end, strip it\n\t# because it is most likely a libtool script we actually want to\n\t# install\n\tstripped_ext=\n\tcase $file in\n\t  *.exe)\n\t    if test ! -f \"$file\"; then\n\t      func_stripname '' '.exe' \"$file\"\n\t      file=$func_stripname_result\n\t      stripped_ext=.exe\n\t    fi\n\t    ;;\n\tesac\n\n\t# Do a test to see if this is really a libtool program.\n\tcase $host in\n\t*cygwin* | *mingw*)\n\t    if func_ltwrapper_executable_p \"$file\"; then\n\t      func_ltwrapper_scriptname \"$file\"\n\t      wrapper=$func_ltwrapper_scriptname_result\n\t    else\n\t      func_stripname '' '.exe' \"$file\"\n\t      wrapper=$func_stripname_result\n\t    fi\n\t    ;;\n\t*)\n\t    wrapper=$file\n\t    ;;\n\tesac\n\tif func_ltwrapper_script_p \"$wrapper\"; then\n\t  notinst_deplibs=\n\t  relink_command=\n\n\t  func_source \"$wrapper\"\n\n\t  # Check the variables that should have been set.\n\t  test -z \"$generated_by_libtool_version\" && \\\n\t    func_fatal_error \"invalid libtool wrapper script '$wrapper'\"\n\n\t  finalize=:\n\t  for lib in $notinst_deplibs; do\n\t    # Check to see that each library is installed.\n\t    libdir=\n\t    if test -f \"$lib\"; then\n\t      func_source \"$lib\"\n\t    fi\n\t    libfile=$libdir/`$ECHO \"$lib\" | $SED 's%^.*/%%g'`\n\t    if test -n \"$libdir\" && test ! -f \"$libfile\"; then\n\t      func_warning \"'$lib' has not been installed in '$libdir'\"\n\t      finalize=false\n\t    fi\n\t  done\n\n\t  relink_command=\n\t  func_source \"$wrapper\"\n\n\t  outputname=\n\t  if test no = \"$fast_install\" && test -n \"$relink_command\"; then\n\t    $opt_dry_run || {\n\t      if $finalize; then\n\t        tmpdir=`func_mktempdir`\n\t\tfunc_basename \"$file$stripped_ext\"\n\t\tfile=$func_basename_result\n\t        outputname=$tmpdir/$file\n\t        # Replace the output file specification.\n\t        relink_command=`$ECHO \"$relink_command\" | $SED 's%@OUTPUT@%'\"$outputname\"'%g'`\n\n\t        $opt_quiet || {\n\t          func_quote_arg expand,pretty \"$relink_command\"\n\t\t  eval \"func_echo $func_quote_arg_result\"\n\t        }\n\t        if eval \"$relink_command\"; then :\n\t          else\n\t\t  func_error \"error: relink '$file' with the above command before installing it\"\n\t\t  $opt_dry_run || ${RM}r \"$tmpdir\"\n\t\t  continue\n\t        fi\n\t        file=$outputname\n\t      else\n\t        func_warning \"cannot relink '$file'\"\n\t      fi\n\t    }\n\t  else\n\t    # Install the binary that we compiled earlier.\n\t    file=`$ECHO \"$file$stripped_ext\" | $SED \"s%\\([^/]*\\)$%$objdir/\\1%\"`\n\t  fi\n\tfi\n\n\t# remove .exe since cygwin /usr/bin/install will append another\n\t# one anyway\n\tcase $install_prog,$host in\n\t*/usr/bin/install*,*cygwin*)\n\t  case $file:$destfile in\n\t  *.exe:*.exe)\n\t    # this is ok\n\t    ;;\n\t  *.exe:*)\n\t    destfile=$destfile.exe\n\t    ;;\n\t  *:*.exe)\n\t    func_stripname '' '.exe' \"$destfile\"\n\t    destfile=$func_stripname_result\n\t    ;;\n\t  esac\n\t  ;;\n\tesac\n\tfunc_show_eval \"$install_prog\\$stripme \\$file \\$destfile\" 'exit $?'\n\t$opt_dry_run || if test -n \"$outputname\"; then\n\t  ${RM}r \"$tmpdir\"\n\tfi\n\t;;\n      esac\n    done\n\n    for file in $staticlibs; do\n      func_basename \"$file\"\n      name=$func_basename_result\n\n      # Set up the ranlib parameters.\n      oldlib=$destdir/$name\n      func_to_tool_file \"$oldlib\" func_convert_file_msys_to_w32\n      tool_oldlib=$func_to_tool_file_result\n\n      func_show_eval \"$install_prog \\$file \\$oldlib\" 'exit $?'\n\n      if test -n \"$stripme\" && test -n \"$old_striplib\"; then\n\tfunc_show_eval \"$old_striplib $tool_oldlib\" 'exit $?'\n      fi\n\n      # Do each command in the postinstall commands.\n      func_execute_cmds \"$old_postinstall_cmds\" 'exit $?'\n    done\n\n    test -n \"$future_libdirs\" && \\\n      func_warning \"remember to run '$progname --finish$future_libdirs'\"\n\n    if test -n \"$current_libdirs\"; then\n      # Maybe just do a dry run.\n      $opt_dry_run && current_libdirs=\" -n$current_libdirs\"\n      exec_cmd='$SHELL \"$progpath\" $preserve_args --finish$current_libdirs'\n    else\n      exit $EXIT_SUCCESS\n    fi\n}\n\ntest install = \"$opt_mode\" && func_mode_install ${1+\"$@\"}\n\n\n# func_generate_dlsyms outputname originator pic_p\n# Extract symbols from dlprefiles and create ${outputname}S.o with\n# a dlpreopen symbol table.\nfunc_generate_dlsyms ()\n{\n    $debug_cmd\n\n    my_outputname=$1\n    my_originator=$2\n    my_pic_p=${3-false}\n    my_prefix=`$ECHO \"$my_originator\" | $SED 's%[^a-zA-Z0-9]%_%g'`\n    my_dlsyms=\n\n    if test -n \"$dlfiles$dlprefiles\" || test no != \"$dlself\"; then\n      if test -n \"$NM\" && test -n \"$global_symbol_pipe\"; then\n\tmy_dlsyms=${my_outputname}S.c\n      else\n\tfunc_error \"not configured to extract global symbols from dlpreopened files\"\n      fi\n    fi\n\n    if test -n \"$my_dlsyms\"; then\n      case $my_dlsyms in\n      \"\") ;;\n      *.c)\n\t# Discover the nlist of each of the dlfiles.\n\tnlist=$output_objdir/$my_outputname.nm\n\n\tfunc_show_eval \"$RM $nlist ${nlist}S ${nlist}T\"\n\n\t# Parse the name list into a source file.\n\tfunc_verbose \"creating $output_objdir/$my_dlsyms\"\n\n\t$opt_dry_run || $ECHO > \"$output_objdir/$my_dlsyms\" \"\\\n/* $my_dlsyms - symbol resolution table for '$my_outputname' dlsym emulation. */\n/* Generated by $PROGRAM (GNU $PACKAGE) $VERSION */\n\n#ifdef __cplusplus\nextern \\\"C\\\" {\n#endif\n\n#if defined __GNUC__ && (((__GNUC__ == 4) && (__GNUC_MINOR__ >= 4)) || (__GNUC__ > 4))\n#pragma GCC diagnostic ignored \\\"-Wstrict-prototypes\\\"\n#endif\n\n/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests.  */\n#if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE\n/* DATA imports from DLLs on WIN32 can't be const, because runtime\n   relocations are performed -- see ld's documentation on pseudo-relocs.  */\n# define LT_DLSYM_CONST\n#elif defined __osf__\n/* This system does not cope well with relocations in const data.  */\n# define LT_DLSYM_CONST\n#else\n# define LT_DLSYM_CONST const\n#endif\n\n#define STREQ(s1, s2) (strcmp ((s1), (s2)) == 0)\n\n/* External symbol declarations for the compiler. */\\\n\"\n\n\tif test yes = \"$dlself\"; then\n\t  func_verbose \"generating symbol list for '$output'\"\n\n\t  $opt_dry_run || echo ': @PROGRAM@ ' > \"$nlist\"\n\n\t  # Add our own program objects to the symbol list.\n\t  progfiles=`$ECHO \"$objs$old_deplibs\" | $SP2NL | $SED \"$lo2o\" | $NL2SP`\n\t  for progfile in $progfiles; do\n\t    func_to_tool_file \"$progfile\" func_convert_file_msys_to_w32\n\t    func_verbose \"extracting global C symbols from '$func_to_tool_file_result'\"\n\t    $opt_dry_run || eval \"$NM $func_to_tool_file_result | $global_symbol_pipe >> '$nlist'\"\n\t  done\n\n\t  if test -n \"$exclude_expsyms\"; then\n\t    $opt_dry_run || {\n\t      eval '$EGREP -v \" ($exclude_expsyms)$\" \"$nlist\" > \"$nlist\"T'\n\t      eval '$MV \"$nlist\"T \"$nlist\"'\n\t    }\n\t  fi\n\n\t  if test -n \"$export_symbols_regex\"; then\n\t    $opt_dry_run || {\n\t      eval '$EGREP -e \"$export_symbols_regex\" \"$nlist\" > \"$nlist\"T'\n\t      eval '$MV \"$nlist\"T \"$nlist\"'\n\t    }\n\t  fi\n\n\t  # Prepare the list of exported symbols\n\t  if test -z \"$export_symbols\"; then\n\t    export_symbols=$output_objdir/$outputname.exp\n\t    $opt_dry_run || {\n\t      $RM $export_symbols\n\t      eval \"$SED -n -e '/^: @PROGRAM@ $/d' -e 's/^.* \\(.*\\)$/\\1/p' \"'< \"$nlist\" > \"$export_symbols\"'\n\t      case $host in\n\t      *cygwin* | *mingw* | *cegcc* )\n                eval \"echo EXPORTS \"'> \"$output_objdir/$outputname.def\"'\n                eval 'cat \"$export_symbols\" >> \"$output_objdir/$outputname.def\"'\n\t        ;;\n\t      esac\n\t    }\n\t  else\n\t    $opt_dry_run || {\n\t      eval \"$SED -e 's/\\([].[*^$]\\)/\\\\\\\\\\1/g' -e 's/^/ /' -e 's/$/$/'\"' < \"$export_symbols\" > \"$output_objdir/$outputname.exp\"'\n\t      eval '$GREP -f \"$output_objdir/$outputname.exp\" < \"$nlist\" > \"$nlist\"T'\n\t      eval '$MV \"$nlist\"T \"$nlist\"'\n\t      case $host in\n\t        *cygwin* | *mingw* | *cegcc* )\n\t          eval \"echo EXPORTS \"'> \"$output_objdir/$outputname.def\"'\n\t          eval 'cat \"$nlist\" >> \"$output_objdir/$outputname.def\"'\n\t          ;;\n\t      esac\n\t    }\n\t  fi\n\tfi\n\n\tfor dlprefile in $dlprefiles; do\n\t  func_verbose \"extracting global C symbols from '$dlprefile'\"\n\t  func_basename \"$dlprefile\"\n\t  name=$func_basename_result\n          case $host in\n\t    *cygwin* | *mingw* | *cegcc* )\n\t      # if an import library, we need to obtain dlname\n\t      if func_win32_import_lib_p \"$dlprefile\"; then\n\t        func_tr_sh \"$dlprefile\"\n\t        eval \"curr_lafile=\\$libfile_$func_tr_sh_result\"\n\t        dlprefile_dlbasename=\n\t        if test -n \"$curr_lafile\" && func_lalib_p \"$curr_lafile\"; then\n\t          # Use subshell, to avoid clobbering current variable values\n\t          dlprefile_dlname=`source \"$curr_lafile\" && echo \"$dlname\"`\n\t          if test -n \"$dlprefile_dlname\"; then\n\t            func_basename \"$dlprefile_dlname\"\n\t            dlprefile_dlbasename=$func_basename_result\n\t          else\n\t            # no lafile. user explicitly requested -dlpreopen <import library>.\n\t            $sharedlib_from_linklib_cmd \"$dlprefile\"\n\t            dlprefile_dlbasename=$sharedlib_from_linklib_result\n\t          fi\n\t        fi\n\t        $opt_dry_run || {\n\t          if test -n \"$dlprefile_dlbasename\"; then\n\t            eval '$ECHO \": $dlprefile_dlbasename\" >> \"$nlist\"'\n\t          else\n\t            func_warning \"Could not compute DLL name from $name\"\n\t            eval '$ECHO \": $name \" >> \"$nlist\"'\n\t          fi\n\t          func_to_tool_file \"$dlprefile\" func_convert_file_msys_to_w32\n\t          eval \"$NM \\\"$func_to_tool_file_result\\\" 2>/dev/null | $global_symbol_pipe |\n\t            $SED -e '/I __imp/d' -e 's/I __nm_/D /;s/_nm__//' >> '$nlist'\"\n\t        }\n\t      else # not an import lib\n\t        $opt_dry_run || {\n\t          eval '$ECHO \": $name \" >> \"$nlist\"'\n\t          func_to_tool_file \"$dlprefile\" func_convert_file_msys_to_w32\n\t          eval \"$NM \\\"$func_to_tool_file_result\\\" 2>/dev/null | $global_symbol_pipe >> '$nlist'\"\n\t        }\n\t      fi\n\t    ;;\n\t    *)\n\t      $opt_dry_run || {\n\t        eval '$ECHO \": $name \" >> \"$nlist\"'\n\t        func_to_tool_file \"$dlprefile\" func_convert_file_msys_to_w32\n\t        eval \"$NM \\\"$func_to_tool_file_result\\\" 2>/dev/null | $global_symbol_pipe >> '$nlist'\"\n\t      }\n\t    ;;\n          esac\n\tdone\n\n\t$opt_dry_run || {\n\t  # Make sure we have at least an empty file.\n\t  test -f \"$nlist\" || : > \"$nlist\"\n\n\t  if test -n \"$exclude_expsyms\"; then\n\t    $EGREP -v \" ($exclude_expsyms)$\" \"$nlist\" > \"$nlist\"T\n\t    $MV \"$nlist\"T \"$nlist\"\n\t  fi\n\n\t  # Try sorting and uniquifying the output.\n\t  if $GREP -v \"^: \" < \"$nlist\" |\n\t      if sort -k 3 </dev/null >/dev/null 2>&1; then\n\t\tsort -k 3\n\t      else\n\t\tsort +2\n\t      fi |\n\t      uniq > \"$nlist\"S; then\n\t    :\n\t  else\n\t    $GREP -v \"^: \" < \"$nlist\" > \"$nlist\"S\n\t  fi\n\n\t  if test -f \"$nlist\"S; then\n\t    eval \"$global_symbol_to_cdecl\"' < \"$nlist\"S >> \"$output_objdir/$my_dlsyms\"'\n\t  else\n\t    echo '/* NONE */' >> \"$output_objdir/$my_dlsyms\"\n\t  fi\n\n\t  func_show_eval '$RM \"${nlist}I\"'\n\t  if test -n \"$global_symbol_to_import\"; then\n\t    eval \"$global_symbol_to_import\"' < \"$nlist\"S > \"$nlist\"I'\n\t  fi\n\n\t  echo >> \"$output_objdir/$my_dlsyms\" \"\\\n\n/* The mapping between symbol names and symbols.  */\ntypedef struct {\n  const char *name;\n  void *address;\n} lt_dlsymlist;\nextern LT_DLSYM_CONST lt_dlsymlist\nlt_${my_prefix}_LTX_preloaded_symbols[];\\\n\"\n\n\t  if test -s \"$nlist\"I; then\n\t    echo >> \"$output_objdir/$my_dlsyms\" \"\\\nstatic void lt_syminit(void)\n{\n  LT_DLSYM_CONST lt_dlsymlist *symbol = lt_${my_prefix}_LTX_preloaded_symbols;\n  for (; symbol->name; ++symbol)\n    {\"\n\t    $SED 's/.*/      if (STREQ (symbol->name, \\\"&\\\")) symbol->address = (void *) \\&&;/' < \"$nlist\"I >> \"$output_objdir/$my_dlsyms\"\n\t    echo >> \"$output_objdir/$my_dlsyms\" \"\\\n    }\n}\"\n\t  fi\n\t  echo >> \"$output_objdir/$my_dlsyms\" \"\\\nLT_DLSYM_CONST lt_dlsymlist\nlt_${my_prefix}_LTX_preloaded_symbols[] =\n{ {\\\"$my_originator\\\", (void *) 0},\"\n\n\t  if test -s \"$nlist\"I; then\n\t    echo >> \"$output_objdir/$my_dlsyms\" \"\\\n  {\\\"@INIT@\\\", (void *) &lt_syminit},\"\n\t  fi\n\n\t  case $need_lib_prefix in\n\t  no)\n\t    eval \"$global_symbol_to_c_name_address\" < \"$nlist\" >> \"$output_objdir/$my_dlsyms\"\n\t    ;;\n\t  *)\n\t    eval \"$global_symbol_to_c_name_address_lib_prefix\" < \"$nlist\" >> \"$output_objdir/$my_dlsyms\"\n\t    ;;\n\t  esac\n\t  echo >> \"$output_objdir/$my_dlsyms\" \"\\\n  {0, (void *) 0}\n};\n\n/* This works around a problem in FreeBSD linker */\n#ifdef FREEBSD_WORKAROUND\nstatic const void *lt_preloaded_setup() {\n  return lt_${my_prefix}_LTX_preloaded_symbols;\n}\n#endif\n\n#ifdef __cplusplus\n}\n#endif\\\n\"\n\t} # !$opt_dry_run\n\n\tpic_flag_for_symtable=\n\tcase \"$compile_command \" in\n\t*\" -static \"*) ;;\n\t*)\n\t  case $host in\n\t  # compiling the symbol table file with pic_flag works around\n\t  # a FreeBSD bug that causes programs to crash when -lm is\n\t  # linked before any other PIC object.  But we must not use\n\t  # pic_flag when linking with -static.  The problem exists in\n\t  # FreeBSD 2.2.6 and is fixed in FreeBSD 3.1.\n\t  *-*-freebsd2.*|*-*-freebsd3.0*|*-*-freebsdelf3.0*)\n\t    pic_flag_for_symtable=\" $pic_flag -DFREEBSD_WORKAROUND\" ;;\n\t  *-*-hpux*)\n\t    pic_flag_for_symtable=\" $pic_flag\"  ;;\n\t  *)\n\t    $my_pic_p && pic_flag_for_symtable=\" $pic_flag\"\n\t    ;;\n\t  esac\n\t  ;;\n\tesac\n\tsymtab_cflags=\n\tfor arg in $LTCFLAGS; do\n\t  case $arg in\n\t  -pie | -fpie | -fPIE) ;;\n\t  *) func_append symtab_cflags \" $arg\" ;;\n\t  esac\n\tdone\n\n\t# Now compile the dynamic symbol file.\n\tfunc_show_eval '(cd $output_objdir && $LTCC$symtab_cflags -c$no_builtin_flag$pic_flag_for_symtable \"$my_dlsyms\")' 'exit $?'\n\n\t# Clean up the generated files.\n\tfunc_show_eval '$RM \"$output_objdir/$my_dlsyms\" \"$nlist\" \"${nlist}S\" \"${nlist}T\" \"${nlist}I\"'\n\n\t# Transform the symbol file into the correct name.\n\tsymfileobj=$output_objdir/${my_outputname}S.$objext\n\tcase $host in\n\t*cygwin* | *mingw* | *cegcc* )\n\t  if test -f \"$output_objdir/$my_outputname.def\"; then\n\t    compile_command=`$ECHO \"$compile_command\" | $SED \"s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%\"`\n\t    finalize_command=`$ECHO \"$finalize_command\" | $SED \"s%@SYMFILE@%$output_objdir/$my_outputname.def $symfileobj%\"`\n\t  else\n\t    compile_command=`$ECHO \"$compile_command\" | $SED \"s%@SYMFILE@%$symfileobj%\"`\n\t    finalize_command=`$ECHO \"$finalize_command\" | $SED \"s%@SYMFILE@%$symfileobj%\"`\n\t  fi\n\t  ;;\n\t*)\n\t  compile_command=`$ECHO \"$compile_command\" | $SED \"s%@SYMFILE@%$symfileobj%\"`\n\t  finalize_command=`$ECHO \"$finalize_command\" | $SED \"s%@SYMFILE@%$symfileobj%\"`\n\t  ;;\n\tesac\n\t;;\n      *)\n\tfunc_fatal_error \"unknown suffix for '$my_dlsyms'\"\n\t;;\n      esac\n    else\n      # We keep going just in case the user didn't refer to\n      # lt_preloaded_symbols.  The linker will fail if global_symbol_pipe\n      # really was required.\n\n      # Nullify the symbol file.\n      compile_command=`$ECHO \"$compile_command\" | $SED \"s% @SYMFILE@%%\"`\n      finalize_command=`$ECHO \"$finalize_command\" | $SED \"s% @SYMFILE@%%\"`\n    fi\n}\n\n# func_cygming_gnu_implib_p ARG\n# This predicate returns with zero status (TRUE) if\n# ARG is a GNU/binutils-style import library. Returns\n# with nonzero status (FALSE) otherwise.\nfunc_cygming_gnu_implib_p ()\n{\n  $debug_cmd\n\n  func_to_tool_file \"$1\" func_convert_file_msys_to_w32\n  func_cygming_gnu_implib_tmp=`$NM \"$func_to_tool_file_result\" | eval \"$global_symbol_pipe\" | $EGREP ' (_head_[A-Za-z0-9_]+_[ad]l*|[A-Za-z0-9_]+_[ad]l*_iname)$'`\n  test -n \"$func_cygming_gnu_implib_tmp\"\n}\n\n# func_cygming_ms_implib_p ARG\n# This predicate returns with zero status (TRUE) if\n# ARG is an MS-style import library. Returns\n# with nonzero status (FALSE) otherwise.\nfunc_cygming_ms_implib_p ()\n{\n  $debug_cmd\n\n  func_to_tool_file \"$1\" func_convert_file_msys_to_w32\n  func_cygming_ms_implib_tmp=`$NM \"$func_to_tool_file_result\" | eval \"$global_symbol_pipe\" | $GREP '_NULL_IMPORT_DESCRIPTOR'`\n  test -n \"$func_cygming_ms_implib_tmp\"\n}\n\n# func_win32_libid arg\n# return the library type of file 'arg'\n#\n# Need a lot of goo to handle *both* DLLs and import libs\n# Has to be a shell function in order to 'eat' the argument\n# that is supplied when $file_magic_command is called.\n# Despite the name, also deal with 64 bit binaries.\nfunc_win32_libid ()\n{\n  $debug_cmd\n\n  win32_libid_type=unknown\n  win32_fileres=`file -L $1 2>/dev/null`\n  case $win32_fileres in\n  *ar\\ archive\\ import\\ library*) # definitely import\n    win32_libid_type=\"x86 archive import\"\n    ;;\n  *ar\\ archive*) # could be an import, or static\n    # Keep the egrep pattern in sync with the one in _LT_CHECK_MAGIC_METHOD.\n    if eval $OBJDUMP -f $1 | $SED -e '10q' 2>/dev/null |\n       $EGREP 'file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)' >/dev/null; then\n      case $nm_interface in\n      \"MS dumpbin\")\n\tif func_cygming_ms_implib_p \"$1\" ||\n\t   func_cygming_gnu_implib_p \"$1\"\n\tthen\n\t  win32_nmres=import\n\telse\n\t  win32_nmres=\n\tfi\n\t;;\n      *)\n\tfunc_to_tool_file \"$1\" func_convert_file_msys_to_w32\n\twin32_nmres=`eval $NM -f posix -A \\\"$func_to_tool_file_result\\\" |\n\t  $SED -n -e '\n\t    1,100{\n\t\t/ I /{\n\t\t    s|.*|import|\n\t\t    p\n\t\t    q\n\t\t}\n\t    }'`\n\t;;\n      esac\n      case $win32_nmres in\n      import*)  win32_libid_type=\"x86 archive import\";;\n      *)        win32_libid_type=\"x86 archive static\";;\n      esac\n    fi\n    ;;\n  *DLL*)\n    win32_libid_type=\"x86 DLL\"\n    ;;\n  *executable*) # but shell scripts are \"executable\" too...\n    case $win32_fileres in\n    *MS\\ Windows\\ PE\\ Intel*)\n      win32_libid_type=\"x86 DLL\"\n      ;;\n    esac\n    ;;\n  esac\n  $ECHO \"$win32_libid_type\"\n}\n\n# func_cygming_dll_for_implib ARG\n#\n# Platform-specific function to extract the\n# name of the DLL associated with the specified\n# import library ARG.\n# Invoked by eval'ing the libtool variable\n#    $sharedlib_from_linklib_cmd\n# Result is available in the variable\n#    $sharedlib_from_linklib_result\nfunc_cygming_dll_for_implib ()\n{\n  $debug_cmd\n\n  sharedlib_from_linklib_result=`$DLLTOOL --identify-strict --identify \"$1\"`\n}\n\n# func_cygming_dll_for_implib_fallback_core SECTION_NAME LIBNAMEs\n#\n# The is the core of a fallback implementation of a\n# platform-specific function to extract the name of the\n# DLL associated with the specified import library LIBNAME.\n#\n# SECTION_NAME is either .idata$6 or .idata$7, depending\n# on the platform and compiler that created the implib.\n#\n# Echos the name of the DLL associated with the\n# specified import library.\nfunc_cygming_dll_for_implib_fallback_core ()\n{\n  $debug_cmd\n\n  match_literal=`$ECHO \"$1\" | $SED \"$sed_make_literal_regex\"`\n  $OBJDUMP -s --section \"$1\" \"$2\" 2>/dev/null |\n    $SED '/^Contents of section '\"$match_literal\"':/{\n      # Place marker at beginning of archive member dllname section\n      s/.*/====MARK====/\n      p\n      d\n    }\n    # These lines can sometimes be longer than 43 characters, but\n    # are always uninteresting\n    /:[\t ]*file format pe[i]\\{,1\\}-/d\n    /^In archive [^:]*:/d\n    # Ensure marker is printed\n    /^====MARK====/p\n    # Remove all lines with less than 43 characters\n    /^.\\{43\\}/!d\n    # From remaining lines, remove first 43 characters\n    s/^.\\{43\\}//' |\n    $SED -n '\n      # Join marker and all lines until next marker into a single line\n      /^====MARK====/ b para\n      H\n      $ b para\n      b\n      :para\n      x\n      s/\\n//g\n      # Remove the marker\n      s/^====MARK====//\n      # Remove trailing dots and whitespace\n      s/[\\. \\t]*$//\n      # Print\n      /./p' |\n    # we now have a list, one entry per line, of the stringified\n    # contents of the appropriate section of all members of the\n    # archive that possess that section. Heuristic: eliminate\n    # all those that have a first or second character that is\n    # a '.' (that is, objdump's representation of an unprintable\n    # character.) This should work for all archives with less than\n    # 0x302f exports -- but will fail for DLLs whose name actually\n    # begins with a literal '.' or a single character followed by\n    # a '.'.\n    #\n    # Of those that remain, print the first one.\n    $SED -e '/^\\./d;/^.\\./d;q'\n}\n\n# func_cygming_dll_for_implib_fallback ARG\n# Platform-specific function to extract the\n# name of the DLL associated with the specified\n# import library ARG.\n#\n# This fallback implementation is for use when $DLLTOOL\n# does not support the --identify-strict option.\n# Invoked by eval'ing the libtool variable\n#    $sharedlib_from_linklib_cmd\n# Result is available in the variable\n#    $sharedlib_from_linklib_result\nfunc_cygming_dll_for_implib_fallback ()\n{\n  $debug_cmd\n\n  if func_cygming_gnu_implib_p \"$1\"; then\n    # binutils import library\n    sharedlib_from_linklib_result=`func_cygming_dll_for_implib_fallback_core '.idata$7' \"$1\"`\n  elif func_cygming_ms_implib_p \"$1\"; then\n    # ms-generated import library\n    sharedlib_from_linklib_result=`func_cygming_dll_for_implib_fallback_core '.idata$6' \"$1\"`\n  else\n    # unknown\n    sharedlib_from_linklib_result=\n  fi\n}\n\n\n# func_extract_an_archive dir oldlib\nfunc_extract_an_archive ()\n{\n    $debug_cmd\n\n    f_ex_an_ar_dir=$1; shift\n    f_ex_an_ar_oldlib=$1\n    if test yes = \"$lock_old_archive_extraction\"; then\n      lockfile=$f_ex_an_ar_oldlib.lock\n      until $opt_dry_run || ln \"$progpath\" \"$lockfile\" 2>/dev/null; do\n\tfunc_echo \"Waiting for $lockfile to be removed\"\n\tsleep 2\n      done\n    fi\n    func_show_eval \"(cd \\$f_ex_an_ar_dir && $AR x \\\"\\$f_ex_an_ar_oldlib\\\")\" \\\n\t\t   'stat=$?; rm -f \"$lockfile\"; exit $stat'\n    if test yes = \"$lock_old_archive_extraction\"; then\n      $opt_dry_run || rm -f \"$lockfile\"\n    fi\n    if ($AR t \"$f_ex_an_ar_oldlib\" | sort | sort -uc >/dev/null 2>&1); then\n     :\n    else\n      func_fatal_error \"object name conflicts in archive: $f_ex_an_ar_dir/$f_ex_an_ar_oldlib\"\n    fi\n}\n\n\n# func_extract_archives gentop oldlib ...\nfunc_extract_archives ()\n{\n    $debug_cmd\n\n    my_gentop=$1; shift\n    my_oldlibs=${1+\"$@\"}\n    my_oldobjs=\n    my_xlib=\n    my_xabs=\n    my_xdir=\n\n    for my_xlib in $my_oldlibs; do\n      # Extract the objects.\n      case $my_xlib in\n\t[\\\\/]* | [A-Za-z]:[\\\\/]*) my_xabs=$my_xlib ;;\n\t*) my_xabs=`pwd`\"/$my_xlib\" ;;\n      esac\n      func_basename \"$my_xlib\"\n      my_xlib=$func_basename_result\n      my_xlib_u=$my_xlib\n      while :; do\n        case \" $extracted_archives \" in\n\t*\" $my_xlib_u \"*)\n\t  func_arith $extracted_serial + 1\n\t  extracted_serial=$func_arith_result\n\t  my_xlib_u=lt$extracted_serial-$my_xlib ;;\n\t*) break ;;\n\tesac\n      done\n      extracted_archives=\"$extracted_archives $my_xlib_u\"\n      my_xdir=$my_gentop/$my_xlib_u\n\n      func_mkdir_p \"$my_xdir\"\n\n      case $host in\n      *-darwin*)\n\tfunc_verbose \"Extracting $my_xabs\"\n\t# Do not bother doing anything if just a dry run\n\t$opt_dry_run || {\n\t  darwin_orig_dir=`pwd`\n\t  cd $my_xdir || exit $?\n\t  darwin_archive=$my_xabs\n\t  darwin_curdir=`pwd`\n\t  func_basename \"$darwin_archive\"\n\t  darwin_base_archive=$func_basename_result\n\t  darwin_arches=`$LIPO -info \"$darwin_archive\" 2>/dev/null | $GREP Architectures 2>/dev/null || true`\n\t  if test -n \"$darwin_arches\"; then\n\t    darwin_arches=`$ECHO \"$darwin_arches\" | $SED -e 's/.*are://'`\n\t    darwin_arch=\n\t    func_verbose \"$darwin_base_archive has multiple architectures $darwin_arches\"\n\t    for darwin_arch in  $darwin_arches; do\n\t      func_mkdir_p \"unfat-$$/$darwin_base_archive-$darwin_arch\"\n\t      $LIPO -thin $darwin_arch -output \"unfat-$$/$darwin_base_archive-$darwin_arch/$darwin_base_archive\" \"$darwin_archive\"\n\t      cd \"unfat-$$/$darwin_base_archive-$darwin_arch\"\n\t      func_extract_an_archive \"`pwd`\" \"$darwin_base_archive\"\n\t      cd \"$darwin_curdir\"\n\t      $RM \"unfat-$$/$darwin_base_archive-$darwin_arch/$darwin_base_archive\"\n\t    done # $darwin_arches\n            ## Okay now we've a bunch of thin objects, gotta fatten them up :)\n\t    darwin_filelist=`find unfat-$$ -type f -name \\*.o -print -o -name \\*.lo -print | $SED -e \"$sed_basename\" | sort -u`\n\t    darwin_file=\n\t    darwin_files=\n\t    for darwin_file in $darwin_filelist; do\n\t      darwin_files=`find unfat-$$ -name $darwin_file -print | sort | $NL2SP`\n\t      $LIPO -create -output \"$darwin_file\" $darwin_files\n\t    done # $darwin_filelist\n\t    $RM -rf unfat-$$\n\t    cd \"$darwin_orig_dir\"\n\t  else\n\t    cd $darwin_orig_dir\n\t    func_extract_an_archive \"$my_xdir\" \"$my_xabs\"\n\t  fi # $darwin_arches\n\t} # !$opt_dry_run\n\t;;\n      *)\n        func_extract_an_archive \"$my_xdir\" \"$my_xabs\"\n\t;;\n      esac\n      my_oldobjs=\"$my_oldobjs \"`find $my_xdir -name \\*.$objext -print -o -name \\*.lo -print | sort | $NL2SP`\n    done\n\n    func_extract_archives_result=$my_oldobjs\n}\n\n\n# func_emit_wrapper [arg=no]\n#\n# Emit a libtool wrapper script on stdout.\n# Don't directly open a file because we may want to\n# incorporate the script contents within a cygwin/mingw\n# wrapper executable.  Must ONLY be called from within\n# func_mode_link because it depends on a number of variables\n# set therein.\n#\n# ARG is the value that the WRAPPER_SCRIPT_BELONGS_IN_OBJDIR\n# variable will take.  If 'yes', then the emitted script\n# will assume that the directory where it is stored is\n# the $objdir directory.  This is a cygwin/mingw-specific\n# behavior.\nfunc_emit_wrapper ()\n{\n\tfunc_emit_wrapper_arg1=${1-no}\n\n\t$ECHO \"\\\n#! $SHELL\n\n# $output - temporary wrapper script for $objdir/$outputname\n# Generated by $PROGRAM (GNU $PACKAGE) $VERSION\n#\n# The $output program cannot be directly executed until all the libtool\n# libraries that it depends on are installed.\n#\n# This wrapper script should never be moved out of the build directory.\n# If it is, it will not operate correctly.\n\n# Sed substitution that helps us do robust quoting.  It backslashifies\n# metacharacters that are still active within double-quoted strings.\nsed_quote_subst='$sed_quote_subst'\n\n# Be Bourne compatible\nif test -n \\\"\\${ZSH_VERSION+set}\\\" && (emulate sh) >/dev/null 2>&1; then\n  emulate sh\n  NULLCMD=:\n  # Zsh 3.x and 4.x performs word splitting on \\${1+\\\"\\$@\\\"}, which\n  # is contrary to our usage.  Disable this feature.\n  alias -g '\\${1+\\\"\\$@\\\"}'='\\\"\\$@\\\"'\n  setopt NO_GLOB_SUBST\nelse\n  case \\`(set -o) 2>/dev/null\\` in *posix*) set -o posix;; esac\nfi\nBIN_SH=xpg4; export BIN_SH # for Tru64\nDUALCASE=1; export DUALCASE # for MKS sh\n\n# The HP-UX ksh and POSIX shell print the target directory to stdout\n# if CDPATH is set.\n(unset CDPATH) >/dev/null 2>&1 && unset CDPATH\n\nrelink_command=\\\"$relink_command\\\"\n\n# This environment variable determines our operation mode.\nif test \\\"\\$libtool_install_magic\\\" = \\\"$magic\\\"; then\n  # install mode needs the following variables:\n  generated_by_libtool_version='$macro_version'\n  notinst_deplibs='$notinst_deplibs'\nelse\n  # When we are sourced in execute mode, \\$file and \\$ECHO are already set.\n  if test \\\"\\$libtool_execute_magic\\\" != \\\"$magic\\\"; then\n    file=\\\"\\$0\\\"\"\n\n    func_quote_arg pretty \"$ECHO\"\n    qECHO=$func_quote_arg_result\n    $ECHO \"\\\n\n# A function that is used when there is no print builtin or printf.\nfunc_fallback_echo ()\n{\n  eval 'cat <<_LTECHO_EOF\n\\$1\n_LTECHO_EOF'\n}\n    ECHO=$qECHO\n  fi\n\n# Very basic option parsing. These options are (a) specific to\n# the libtool wrapper, (b) are identical between the wrapper\n# /script/ and the wrapper /executable/ that is used only on\n# windows platforms, and (c) all begin with the string \"--lt-\"\n# (application programs are unlikely to have options that match\n# this pattern).\n#\n# There are only two supported options: --lt-debug and\n# --lt-dump-script. There is, deliberately, no --lt-help.\n#\n# The first argument to this parsing function should be the\n# script's $0 value, followed by \"$@\".\nlt_option_debug=\nfunc_parse_lt_options ()\n{\n  lt_script_arg0=\\$0\n  shift\n  for lt_opt\n  do\n    case \\\"\\$lt_opt\\\" in\n    --lt-debug) lt_option_debug=1 ;;\n    --lt-dump-script)\n        lt_dump_D=\\`\\$ECHO \\\"X\\$lt_script_arg0\\\" | $SED -e 's/^X//' -e 's%/[^/]*$%%'\\`\n        test \\\"X\\$lt_dump_D\\\" = \\\"X\\$lt_script_arg0\\\" && lt_dump_D=.\n        lt_dump_F=\\`\\$ECHO \\\"X\\$lt_script_arg0\\\" | $SED -e 's/^X//' -e 's%^.*/%%'\\`\n        cat \\\"\\$lt_dump_D/\\$lt_dump_F\\\"\n        exit 0\n      ;;\n    --lt-*)\n        \\$ECHO \\\"Unrecognized --lt- option: '\\$lt_opt'\\\" 1>&2\n        exit 1\n      ;;\n    esac\n  done\n\n  # Print the debug banner immediately:\n  if test -n \\\"\\$lt_option_debug\\\"; then\n    echo \\\"$outputname:$output:\\$LINENO: libtool wrapper (GNU $PACKAGE) $VERSION\\\" 1>&2\n  fi\n}\n\n# Used when --lt-debug. Prints its arguments to stdout\n# (redirection is the responsibility of the caller)\nfunc_lt_dump_args ()\n{\n  lt_dump_args_N=1;\n  for lt_arg\n  do\n    \\$ECHO \\\"$outputname:$output:\\$LINENO: newargv[\\$lt_dump_args_N]: \\$lt_arg\\\"\n    lt_dump_args_N=\\`expr \\$lt_dump_args_N + 1\\`\n  done\n}\n\n# Core function for launching the target application\nfunc_exec_program_core ()\n{\n\"\n  case $host in\n  # Backslashes separate directories on plain windows\n  *-*-mingw | *-*-os2* | *-cegcc*)\n    $ECHO \"\\\n      if test -n \\\"\\$lt_option_debug\\\"; then\n        \\$ECHO \\\"$outputname:$output:\\$LINENO: newargv[0]: \\$progdir\\\\\\\\\\$program\\\" 1>&2\n        func_lt_dump_args \\${1+\\\"\\$@\\\"} 1>&2\n      fi\n      exec \\\"\\$progdir\\\\\\\\\\$program\\\" \\${1+\\\"\\$@\\\"}\n\"\n    ;;\n\n  *)\n    $ECHO \"\\\n      if test -n \\\"\\$lt_option_debug\\\"; then\n        \\$ECHO \\\"$outputname:$output:\\$LINENO: newargv[0]: \\$progdir/\\$program\\\" 1>&2\n        func_lt_dump_args \\${1+\\\"\\$@\\\"} 1>&2\n      fi\n      exec \\\"\\$progdir/\\$program\\\" \\${1+\\\"\\$@\\\"}\n\"\n    ;;\n  esac\n  $ECHO \"\\\n      \\$ECHO \\\"\\$0: cannot exec \\$program \\$*\\\" 1>&2\n      exit 1\n}\n\n# A function to encapsulate launching the target application\n# Strips options in the --lt-* namespace from \\$@ and\n# launches target application with the remaining arguments.\nfunc_exec_program ()\n{\n  case \\\" \\$* \\\" in\n  *\\\\ --lt-*)\n    for lt_wr_arg\n    do\n      case \\$lt_wr_arg in\n      --lt-*) ;;\n      *) set x \\\"\\$@\\\" \\\"\\$lt_wr_arg\\\"; shift;;\n      esac\n      shift\n    done ;;\n  esac\n  func_exec_program_core \\${1+\\\"\\$@\\\"}\n}\n\n  # Parse options\n  func_parse_lt_options \\\"\\$0\\\" \\${1+\\\"\\$@\\\"}\n\n  # Find the directory that this script lives in.\n  thisdir=\\`\\$ECHO \\\"\\$file\\\" | $SED 's%/[^/]*$%%'\\`\n  test \\\"x\\$thisdir\\\" = \\\"x\\$file\\\" && thisdir=.\n\n  # Follow symbolic links until we get to the real thisdir.\n  file=\\`ls -ld \\\"\\$file\\\" | $SED -n 's/.*-> //p'\\`\n  while test -n \\\"\\$file\\\"; do\n    destdir=\\`\\$ECHO \\\"\\$file\\\" | $SED 's%/[^/]*\\$%%'\\`\n\n    # If there was a directory component, then change thisdir.\n    if test \\\"x\\$destdir\\\" != \\\"x\\$file\\\"; then\n      case \\\"\\$destdir\\\" in\n      [\\\\\\\\/]* | [A-Za-z]:[\\\\\\\\/]*) thisdir=\\\"\\$destdir\\\" ;;\n      *) thisdir=\\\"\\$thisdir/\\$destdir\\\" ;;\n      esac\n    fi\n\n    file=\\`\\$ECHO \\\"\\$file\\\" | $SED 's%^.*/%%'\\`\n    file=\\`ls -ld \\\"\\$thisdir/\\$file\\\" | $SED -n 's/.*-> //p'\\`\n  done\n\n  # Usually 'no', except on cygwin/mingw when embedded into\n  # the cwrapper.\n  WRAPPER_SCRIPT_BELONGS_IN_OBJDIR=$func_emit_wrapper_arg1\n  if test \\\"\\$WRAPPER_SCRIPT_BELONGS_IN_OBJDIR\\\" = \\\"yes\\\"; then\n    # special case for '.'\n    if test \\\"\\$thisdir\\\" = \\\".\\\"; then\n      thisdir=\\`pwd\\`\n    fi\n    # remove .libs from thisdir\n    case \\\"\\$thisdir\\\" in\n    *[\\\\\\\\/]$objdir ) thisdir=\\`\\$ECHO \\\"\\$thisdir\\\" | $SED 's%[\\\\\\\\/][^\\\\\\\\/]*$%%'\\` ;;\n    $objdir )   thisdir=. ;;\n    esac\n  fi\n\n  # Try to get the absolute directory name.\n  absdir=\\`cd \\\"\\$thisdir\\\" && pwd\\`\n  test -n \\\"\\$absdir\\\" && thisdir=\\\"\\$absdir\\\"\n\"\n\n\tif test yes = \"$fast_install\"; then\n\t  $ECHO \"\\\n  program=lt-'$outputname'$exeext\n  progdir=\\\"\\$thisdir/$objdir\\\"\n\n  if test ! -f \\\"\\$progdir/\\$program\\\" ||\n     { file=\\`ls -1dt \\\"\\$progdir/\\$program\\\" \\\"\\$progdir/../\\$program\\\" 2>/dev/null | $SED 1q\\`; \\\\\n       test \\\"X\\$file\\\" != \\\"X\\$progdir/\\$program\\\"; }; then\n\n    file=\\\"\\$\\$-\\$program\\\"\n\n    if test ! -d \\\"\\$progdir\\\"; then\n      $MKDIR \\\"\\$progdir\\\"\n    else\n      $RM \\\"\\$progdir/\\$file\\\"\n    fi\"\n\n\t  $ECHO \"\\\n\n    # relink executable if necessary\n    if test -n \\\"\\$relink_command\\\"; then\n      if relink_command_output=\\`eval \\$relink_command 2>&1\\`; then :\n      else\n\t\\$ECHO \\\"\\$relink_command_output\\\" >&2\n\t$RM \\\"\\$progdir/\\$file\\\"\n\texit 1\n      fi\n    fi\n\n    $MV \\\"\\$progdir/\\$file\\\" \\\"\\$progdir/\\$program\\\" 2>/dev/null ||\n    { $RM \\\"\\$progdir/\\$program\\\";\n      $MV \\\"\\$progdir/\\$file\\\" \\\"\\$progdir/\\$program\\\"; }\n    $RM \\\"\\$progdir/\\$file\\\"\n  fi\"\n\telse\n\t  $ECHO \"\\\n  program='$outputname'\n  progdir=\\\"\\$thisdir/$objdir\\\"\n\"\n\tfi\n\n\t$ECHO \"\\\n\n  if test -f \\\"\\$progdir/\\$program\\\"; then\"\n\n\t# fixup the dll searchpath if we need to.\n\t#\n\t# Fix the DLL searchpath if we need to.  Do this before prepending\n\t# to shlibpath, because on Windows, both are PATH and uninstalled\n\t# libraries must come first.\n\tif test -n \"$dllsearchpath\"; then\n\t  $ECHO \"\\\n    # Add the dll search path components to the executable PATH\n    PATH=$dllsearchpath:\\$PATH\n\"\n\tfi\n\n\t# Export our shlibpath_var if we have one.\n\tif test yes = \"$shlibpath_overrides_runpath\" && test -n \"$shlibpath_var\" && test -n \"$temp_rpath\"; then\n\t  $ECHO \"\\\n    # Add our own library path to $shlibpath_var\n    $shlibpath_var=\\\"$temp_rpath\\$$shlibpath_var\\\"\n\n    # Some systems cannot cope with colon-terminated $shlibpath_var\n    # The second colon is a workaround for a bug in BeOS R4 sed\n    $shlibpath_var=\\`\\$ECHO \\\"\\$$shlibpath_var\\\" | $SED 's/::*\\$//'\\`\n\n    export $shlibpath_var\n\"\n\tfi\n\n\t$ECHO \"\\\n    if test \\\"\\$libtool_execute_magic\\\" != \\\"$magic\\\"; then\n      # Run the actual program with our arguments.\n      func_exec_program \\${1+\\\"\\$@\\\"}\n    fi\n  else\n    # The program doesn't exist.\n    \\$ECHO \\\"\\$0: error: '\\$progdir/\\$program' does not exist\\\" 1>&2\n    \\$ECHO \\\"This script is just a wrapper for \\$program.\\\" 1>&2\n    \\$ECHO \\\"See the $PACKAGE documentation for more information.\\\" 1>&2\n    exit 1\n  fi\nfi\\\n\"\n}\n\n\n# func_emit_cwrapperexe_src\n# emit the source code for a wrapper executable on stdout\n# Must ONLY be called from within func_mode_link because\n# it depends on a number of variable set therein.\nfunc_emit_cwrapperexe_src ()\n{\n\tcat <<EOF\n\n/* $cwrappersource - temporary wrapper executable for $objdir/$outputname\n   Generated by $PROGRAM (GNU $PACKAGE) $VERSION\n\n   The $output program cannot be directly executed until all the libtool\n   libraries that it depends on are installed.\n\n   This wrapper executable should never be moved out of the build directory.\n   If it is, it will not operate correctly.\n*/\nEOF\n\t    cat <<\"EOF\"\n#ifdef _MSC_VER\n# define _CRT_SECURE_NO_DEPRECATE 1\n#endif\n#include <stdio.h>\n#include <stdlib.h>\n#ifdef _MSC_VER\n# include <direct.h>\n# include <process.h>\n# include <io.h>\n#else\n# include <unistd.h>\n# include <stdint.h>\n# ifdef __CYGWIN__\n#  include <io.h>\n# endif\n#endif\n#include <malloc.h>\n#include <stdarg.h>\n#include <assert.h>\n#include <string.h>\n#include <ctype.h>\n#include <errno.h>\n#include <fcntl.h>\n#include <sys/stat.h>\n\n#define STREQ(s1, s2) (strcmp ((s1), (s2)) == 0)\n\n/* declarations of non-ANSI functions */\n#if defined __MINGW32__\n# ifdef __STRICT_ANSI__\nint _putenv (const char *);\n# endif\n#elif defined __CYGWIN__\n# ifdef __STRICT_ANSI__\nchar *realpath (const char *, char *);\nint putenv (char *);\nint setenv (const char *, const char *, int);\n# endif\n/* #elif defined other_platform || defined ... */\n#endif\n\n/* portability defines, excluding path handling macros */\n#if defined _MSC_VER\n# define setmode _setmode\n# define stat    _stat\n# define chmod   _chmod\n# define getcwd  _getcwd\n# define putenv  _putenv\n# define S_IXUSR _S_IEXEC\n#elif defined __MINGW32__\n# define setmode _setmode\n# define stat    _stat\n# define chmod   _chmod\n# define getcwd  _getcwd\n# define putenv  _putenv\n#elif defined __CYGWIN__\n# define HAVE_SETENV\n# define FOPEN_WB \"wb\"\n/* #elif defined other platforms ... */\n#endif\n\n#if defined PATH_MAX\n# define LT_PATHMAX PATH_MAX\n#elif defined MAXPATHLEN\n# define LT_PATHMAX MAXPATHLEN\n#else\n# define LT_PATHMAX 1024\n#endif\n\n#ifndef S_IXOTH\n# define S_IXOTH 0\n#endif\n#ifndef S_IXGRP\n# define S_IXGRP 0\n#endif\n\n/* path handling portability macros */\n#ifndef DIR_SEPARATOR\n# define DIR_SEPARATOR '/'\n# define PATH_SEPARATOR ':'\n#endif\n\n#if defined _WIN32 || defined __MSDOS__ || defined __DJGPP__ || \\\n  defined __OS2__\n# define HAVE_DOS_BASED_FILE_SYSTEM\n# define FOPEN_WB \"wb\"\n# ifndef DIR_SEPARATOR_2\n#  define DIR_SEPARATOR_2 '\\\\'\n# endif\n# ifndef PATH_SEPARATOR_2\n#  define PATH_SEPARATOR_2 ';'\n# endif\n#endif\n\n#ifndef DIR_SEPARATOR_2\n# define IS_DIR_SEPARATOR(ch) ((ch) == DIR_SEPARATOR)\n#else /* DIR_SEPARATOR_2 */\n# define IS_DIR_SEPARATOR(ch) \\\n\t(((ch) == DIR_SEPARATOR) || ((ch) == DIR_SEPARATOR_2))\n#endif /* DIR_SEPARATOR_2 */\n\n#ifndef PATH_SEPARATOR_2\n# define IS_PATH_SEPARATOR(ch) ((ch) == PATH_SEPARATOR)\n#else /* PATH_SEPARATOR_2 */\n# define IS_PATH_SEPARATOR(ch) ((ch) == PATH_SEPARATOR_2)\n#endif /* PATH_SEPARATOR_2 */\n\n#ifndef FOPEN_WB\n# define FOPEN_WB \"w\"\n#endif\n#ifndef _O_BINARY\n# define _O_BINARY 0\n#endif\n\n#define XMALLOC(type, num)      ((type *) xmalloc ((num) * sizeof(type)))\n#define XFREE(stale) do { \\\n  if (stale) { free (stale); stale = 0; } \\\n} while (0)\n\n#if defined LT_DEBUGWRAPPER\nstatic int lt_debug = 1;\n#else\nstatic int lt_debug = 0;\n#endif\n\nconst char *program_name = \"libtool-wrapper\"; /* in case xstrdup fails */\n\nvoid *xmalloc (size_t num);\nchar *xstrdup (const char *string);\nconst char *base_name (const char *name);\nchar *find_executable (const char *wrapper);\nchar *chase_symlinks (const char *pathspec);\nint make_executable (const char *path);\nint check_executable (const char *path);\nchar *strendzap (char *str, const char *pat);\nvoid lt_debugprintf (const char *file, int line, const char *fmt, ...);\nvoid lt_fatal (const char *file, int line, const char *message, ...);\nstatic const char *nonnull (const char *s);\nstatic const char *nonempty (const char *s);\nvoid lt_setenv (const char *name, const char *value);\nchar *lt_extend_str (const char *orig_value, const char *add, int to_end);\nvoid lt_update_exe_path (const char *name, const char *value);\nvoid lt_update_lib_path (const char *name, const char *value);\nchar **prepare_spawn (char **argv);\nvoid lt_dump_script (FILE *f);\nEOF\n\n\t    cat <<EOF\n#if __GNUC__ < 4 || (__GNUC__ == 4 && __GNUC_MINOR__ < 5)\n# define externally_visible volatile\n#else\n# define externally_visible __attribute__((externally_visible)) volatile\n#endif\nexternally_visible const char * MAGIC_EXE = \"$magic_exe\";\nconst char * LIB_PATH_VARNAME = \"$shlibpath_var\";\nEOF\n\n\t    if test yes = \"$shlibpath_overrides_runpath\" && test -n \"$shlibpath_var\" && test -n \"$temp_rpath\"; then\n              func_to_host_path \"$temp_rpath\"\n\t      cat <<EOF\nconst char * LIB_PATH_VALUE   = \"$func_to_host_path_result\";\nEOF\n\t    else\n\t      cat <<\"EOF\"\nconst char * LIB_PATH_VALUE   = \"\";\nEOF\n\t    fi\n\n\t    if test -n \"$dllsearchpath\"; then\n              func_to_host_path \"$dllsearchpath:\"\n\t      cat <<EOF\nconst char * EXE_PATH_VARNAME = \"PATH\";\nconst char * EXE_PATH_VALUE   = \"$func_to_host_path_result\";\nEOF\n\t    else\n\t      cat <<\"EOF\"\nconst char * EXE_PATH_VARNAME = \"\";\nconst char * EXE_PATH_VALUE   = \"\";\nEOF\n\t    fi\n\n\t    if test yes = \"$fast_install\"; then\n\t      cat <<EOF\nconst char * TARGET_PROGRAM_NAME = \"lt-$outputname\"; /* hopefully, no .exe */\nEOF\n\t    else\n\t      cat <<EOF\nconst char * TARGET_PROGRAM_NAME = \"$outputname\"; /* hopefully, no .exe */\nEOF\n\t    fi\n\n\n\t    cat <<\"EOF\"\n\n#define LTWRAPPER_OPTION_PREFIX         \"--lt-\"\n\nstatic const char *ltwrapper_option_prefix = LTWRAPPER_OPTION_PREFIX;\nstatic const char *dumpscript_opt       = LTWRAPPER_OPTION_PREFIX \"dump-script\";\nstatic const char *debug_opt            = LTWRAPPER_OPTION_PREFIX \"debug\";\n\nint\nmain (int argc, char *argv[])\n{\n  char **newargz;\n  int  newargc;\n  char *tmp_pathspec;\n  char *actual_cwrapper_path;\n  char *actual_cwrapper_name;\n  char *target_name;\n  char *lt_argv_zero;\n  int rval = 127;\n\n  int i;\n\n  program_name = (char *) xstrdup (base_name (argv[0]));\n  newargz = XMALLOC (char *, (size_t) argc + 1);\n\n  /* very simple arg parsing; don't want to rely on getopt\n   * also, copy all non cwrapper options to newargz, except\n   * argz[0], which is handled differently\n   */\n  newargc=0;\n  for (i = 1; i < argc; i++)\n    {\n      if (STREQ (argv[i], dumpscript_opt))\n\t{\nEOF\n\t    case $host in\n\t      *mingw* | *cygwin* )\n\t\t# make stdout use \"unix\" line endings\n\t\techo \"          setmode(1,_O_BINARY);\"\n\t\t;;\n\t      esac\n\n\t    cat <<\"EOF\"\n\t  lt_dump_script (stdout);\n\t  return 0;\n\t}\n      if (STREQ (argv[i], debug_opt))\n\t{\n          lt_debug = 1;\n          continue;\n\t}\n      if (STREQ (argv[i], ltwrapper_option_prefix))\n        {\n          /* however, if there is an option in the LTWRAPPER_OPTION_PREFIX\n             namespace, but it is not one of the ones we know about and\n             have already dealt with, above (inluding dump-script), then\n             report an error. Otherwise, targets might begin to believe\n             they are allowed to use options in the LTWRAPPER_OPTION_PREFIX\n             namespace. The first time any user complains about this, we'll\n             need to make LTWRAPPER_OPTION_PREFIX a configure-time option\n             or a configure.ac-settable value.\n           */\n          lt_fatal (__FILE__, __LINE__,\n\t\t    \"unrecognized %s option: '%s'\",\n                    ltwrapper_option_prefix, argv[i]);\n        }\n      /* otherwise ... */\n      newargz[++newargc] = xstrdup (argv[i]);\n    }\n  newargz[++newargc] = NULL;\n\nEOF\n\t    cat <<EOF\n  /* The GNU banner must be the first non-error debug message */\n  lt_debugprintf (__FILE__, __LINE__, \"libtool wrapper (GNU $PACKAGE) $VERSION\\n\");\nEOF\n\t    cat <<\"EOF\"\n  lt_debugprintf (__FILE__, __LINE__, \"(main) argv[0]: %s\\n\", argv[0]);\n  lt_debugprintf (__FILE__, __LINE__, \"(main) program_name: %s\\n\", program_name);\n\n  tmp_pathspec = find_executable (argv[0]);\n  if (tmp_pathspec == NULL)\n    lt_fatal (__FILE__, __LINE__, \"couldn't find %s\", argv[0]);\n  lt_debugprintf (__FILE__, __LINE__,\n                  \"(main) found exe (before symlink chase) at: %s\\n\",\n\t\t  tmp_pathspec);\n\n  actual_cwrapper_path = chase_symlinks (tmp_pathspec);\n  lt_debugprintf (__FILE__, __LINE__,\n                  \"(main) found exe (after symlink chase) at: %s\\n\",\n\t\t  actual_cwrapper_path);\n  XFREE (tmp_pathspec);\n\n  actual_cwrapper_name = xstrdup (base_name (actual_cwrapper_path));\n  strendzap (actual_cwrapper_path, actual_cwrapper_name);\n\n  /* wrapper name transforms */\n  strendzap (actual_cwrapper_name, \".exe\");\n  tmp_pathspec = lt_extend_str (actual_cwrapper_name, \".exe\", 1);\n  XFREE (actual_cwrapper_name);\n  actual_cwrapper_name = tmp_pathspec;\n  tmp_pathspec = 0;\n\n  /* target_name transforms -- use actual target program name; might have lt- prefix */\n  target_name = xstrdup (base_name (TARGET_PROGRAM_NAME));\n  strendzap (target_name, \".exe\");\n  tmp_pathspec = lt_extend_str (target_name, \".exe\", 1);\n  XFREE (target_name);\n  target_name = tmp_pathspec;\n  tmp_pathspec = 0;\n\n  lt_debugprintf (__FILE__, __LINE__,\n\t\t  \"(main) libtool target name: %s\\n\",\n\t\t  target_name);\nEOF\n\n\t    cat <<EOF\n  newargz[0] =\n    XMALLOC (char, (strlen (actual_cwrapper_path) +\n\t\t    strlen (\"$objdir\") + 1 + strlen (actual_cwrapper_name) + 1));\n  strcpy (newargz[0], actual_cwrapper_path);\n  strcat (newargz[0], \"$objdir\");\n  strcat (newargz[0], \"/\");\nEOF\n\n\t    cat <<\"EOF\"\n  /* stop here, and copy so we don't have to do this twice */\n  tmp_pathspec = xstrdup (newargz[0]);\n\n  /* do NOT want the lt- prefix here, so use actual_cwrapper_name */\n  strcat (newargz[0], actual_cwrapper_name);\n\n  /* DO want the lt- prefix here if it exists, so use target_name */\n  lt_argv_zero = lt_extend_str (tmp_pathspec, target_name, 1);\n  XFREE (tmp_pathspec);\n  tmp_pathspec = NULL;\nEOF\n\n\t    case $host_os in\n\t      mingw*)\n\t    cat <<\"EOF\"\n  {\n    char* p;\n    while ((p = strchr (newargz[0], '\\\\')) != NULL)\n      {\n\t*p = '/';\n      }\n    while ((p = strchr (lt_argv_zero, '\\\\')) != NULL)\n      {\n\t*p = '/';\n      }\n  }\nEOF\n\t    ;;\n\t    esac\n\n\t    cat <<\"EOF\"\n  XFREE (target_name);\n  XFREE (actual_cwrapper_path);\n  XFREE (actual_cwrapper_name);\n\n  lt_setenv (\"BIN_SH\", \"xpg4\"); /* for Tru64 */\n  lt_setenv (\"DUALCASE\", \"1\");  /* for MSK sh */\n  /* Update the DLL searchpath.  EXE_PATH_VALUE ($dllsearchpath) must\n     be prepended before (that is, appear after) LIB_PATH_VALUE ($temp_rpath)\n     because on Windows, both *_VARNAMEs are PATH but uninstalled\n     libraries must come first. */\n  lt_update_exe_path (EXE_PATH_VARNAME, EXE_PATH_VALUE);\n  lt_update_lib_path (LIB_PATH_VARNAME, LIB_PATH_VALUE);\n\n  lt_debugprintf (__FILE__, __LINE__, \"(main) lt_argv_zero: %s\\n\",\n\t\t  nonnull (lt_argv_zero));\n  for (i = 0; i < newargc; i++)\n    {\n      lt_debugprintf (__FILE__, __LINE__, \"(main) newargz[%d]: %s\\n\",\n\t\t      i, nonnull (newargz[i]));\n    }\n\nEOF\n\n\t    case $host_os in\n\t      mingw*)\n\t\tcat <<\"EOF\"\n  /* execv doesn't actually work on mingw as expected on unix */\n  newargz = prepare_spawn (newargz);\n  rval = (int) _spawnv (_P_WAIT, lt_argv_zero, (const char * const *) newargz);\n  if (rval == -1)\n    {\n      /* failed to start process */\n      lt_debugprintf (__FILE__, __LINE__,\n\t\t      \"(main) failed to launch target \\\"%s\\\": %s\\n\",\n\t\t      lt_argv_zero, nonnull (strerror (errno)));\n      return 127;\n    }\n  return rval;\nEOF\n\t\t;;\n\t      *)\n\t\tcat <<\"EOF\"\n  execv (lt_argv_zero, newargz);\n  return rval; /* =127, but avoids unused variable warning */\nEOF\n\t\t;;\n\t    esac\n\n\t    cat <<\"EOF\"\n}\n\nvoid *\nxmalloc (size_t num)\n{\n  void *p = (void *) malloc (num);\n  if (!p)\n    lt_fatal (__FILE__, __LINE__, \"memory exhausted\");\n\n  return p;\n}\n\nchar *\nxstrdup (const char *string)\n{\n  return string ? strcpy ((char *) xmalloc (strlen (string) + 1),\n\t\t\t  string) : NULL;\n}\n\nconst char *\nbase_name (const char *name)\n{\n  const char *base;\n\n#if defined HAVE_DOS_BASED_FILE_SYSTEM\n  /* Skip over the disk name in MSDOS pathnames. */\n  if (isalpha ((unsigned char) name[0]) && name[1] == ':')\n    name += 2;\n#endif\n\n  for (base = name; *name; name++)\n    if (IS_DIR_SEPARATOR (*name))\n      base = name + 1;\n  return base;\n}\n\nint\ncheck_executable (const char *path)\n{\n  struct stat st;\n\n  lt_debugprintf (__FILE__, __LINE__, \"(check_executable): %s\\n\",\n                  nonempty (path));\n  if ((!path) || (!*path))\n    return 0;\n\n  if ((stat (path, &st) >= 0)\n      && (st.st_mode & (S_IXUSR | S_IXGRP | S_IXOTH)))\n    return 1;\n  else\n    return 0;\n}\n\nint\nmake_executable (const char *path)\n{\n  int rval = 0;\n  struct stat st;\n\n  lt_debugprintf (__FILE__, __LINE__, \"(make_executable): %s\\n\",\n                  nonempty (path));\n  if ((!path) || (!*path))\n    return 0;\n\n  if (stat (path, &st) >= 0)\n    {\n      rval = chmod (path, st.st_mode | S_IXOTH | S_IXGRP | S_IXUSR);\n    }\n  return rval;\n}\n\n/* Searches for the full path of the wrapper.  Returns\n   newly allocated full path name if found, NULL otherwise\n   Does not chase symlinks, even on platforms that support them.\n*/\nchar *\nfind_executable (const char *wrapper)\n{\n  int has_slash = 0;\n  const char *p;\n  const char *p_next;\n  /* static buffer for getcwd */\n  char tmp[LT_PATHMAX + 1];\n  size_t tmp_len;\n  char *concat_name;\n\n  lt_debugprintf (__FILE__, __LINE__, \"(find_executable): %s\\n\",\n                  nonempty (wrapper));\n\n  if ((wrapper == NULL) || (*wrapper == '\\0'))\n    return NULL;\n\n  /* Absolute path? */\n#if defined HAVE_DOS_BASED_FILE_SYSTEM\n  if (isalpha ((unsigned char) wrapper[0]) && wrapper[1] == ':')\n    {\n      concat_name = xstrdup (wrapper);\n      if (check_executable (concat_name))\n\treturn concat_name;\n      XFREE (concat_name);\n    }\n  else\n    {\n#endif\n      if (IS_DIR_SEPARATOR (wrapper[0]))\n\t{\n\t  concat_name = xstrdup (wrapper);\n\t  if (check_executable (concat_name))\n\t    return concat_name;\n\t  XFREE (concat_name);\n\t}\n#if defined HAVE_DOS_BASED_FILE_SYSTEM\n    }\n#endif\n\n  for (p = wrapper; *p; p++)\n    if (*p == '/')\n      {\n\thas_slash = 1;\n\tbreak;\n      }\n  if (!has_slash)\n    {\n      /* no slashes; search PATH */\n      const char *path = getenv (\"PATH\");\n      if (path != NULL)\n\t{\n\t  for (p = path; *p; p = p_next)\n\t    {\n\t      const char *q;\n\t      size_t p_len;\n\t      for (q = p; *q; q++)\n\t\tif (IS_PATH_SEPARATOR (*q))\n\t\t  break;\n\t      p_len = (size_t) (q - p);\n\t      p_next = (*q == '\\0' ? q : q + 1);\n\t      if (p_len == 0)\n\t\t{\n\t\t  /* empty path: current directory */\n\t\t  if (getcwd (tmp, LT_PATHMAX) == NULL)\n\t\t    lt_fatal (__FILE__, __LINE__, \"getcwd failed: %s\",\n                              nonnull (strerror (errno)));\n\t\t  tmp_len = strlen (tmp);\n\t\t  concat_name =\n\t\t    XMALLOC (char, tmp_len + 1 + strlen (wrapper) + 1);\n\t\t  memcpy (concat_name, tmp, tmp_len);\n\t\t  concat_name[tmp_len] = '/';\n\t\t  strcpy (concat_name + tmp_len + 1, wrapper);\n\t\t}\n\t      else\n\t\t{\n\t\t  concat_name =\n\t\t    XMALLOC (char, p_len + 1 + strlen (wrapper) + 1);\n\t\t  memcpy (concat_name, p, p_len);\n\t\t  concat_name[p_len] = '/';\n\t\t  strcpy (concat_name + p_len + 1, wrapper);\n\t\t}\n\t      if (check_executable (concat_name))\n\t\treturn concat_name;\n\t      XFREE (concat_name);\n\t    }\n\t}\n      /* not found in PATH; assume curdir */\n    }\n  /* Relative path | not found in path: prepend cwd */\n  if (getcwd (tmp, LT_PATHMAX) == NULL)\n    lt_fatal (__FILE__, __LINE__, \"getcwd failed: %s\",\n              nonnull (strerror (errno)));\n  tmp_len = strlen (tmp);\n  concat_name = XMALLOC (char, tmp_len + 1 + strlen (wrapper) + 1);\n  memcpy (concat_name, tmp, tmp_len);\n  concat_name[tmp_len] = '/';\n  strcpy (concat_name + tmp_len + 1, wrapper);\n\n  if (check_executable (concat_name))\n    return concat_name;\n  XFREE (concat_name);\n  return NULL;\n}\n\nchar *\nchase_symlinks (const char *pathspec)\n{\n#ifndef S_ISLNK\n  return xstrdup (pathspec);\n#else\n  char buf[LT_PATHMAX];\n  struct stat s;\n  char *tmp_pathspec = xstrdup (pathspec);\n  char *p;\n  int has_symlinks = 0;\n  while (strlen (tmp_pathspec) && !has_symlinks)\n    {\n      lt_debugprintf (__FILE__, __LINE__,\n\t\t      \"checking path component for symlinks: %s\\n\",\n\t\t      tmp_pathspec);\n      if (lstat (tmp_pathspec, &s) == 0)\n\t{\n\t  if (S_ISLNK (s.st_mode) != 0)\n\t    {\n\t      has_symlinks = 1;\n\t      break;\n\t    }\n\n\t  /* search backwards for last DIR_SEPARATOR */\n\t  p = tmp_pathspec + strlen (tmp_pathspec) - 1;\n\t  while ((p > tmp_pathspec) && (!IS_DIR_SEPARATOR (*p)))\n\t    p--;\n\t  if ((p == tmp_pathspec) && (!IS_DIR_SEPARATOR (*p)))\n\t    {\n\t      /* no more DIR_SEPARATORS left */\n\t      break;\n\t    }\n\t  *p = '\\0';\n\t}\n      else\n\t{\n\t  lt_fatal (__FILE__, __LINE__,\n\t\t    \"error accessing file \\\"%s\\\": %s\",\n\t\t    tmp_pathspec, nonnull (strerror (errno)));\n\t}\n    }\n  XFREE (tmp_pathspec);\n\n  if (!has_symlinks)\n    {\n      return xstrdup (pathspec);\n    }\n\n  tmp_pathspec = realpath (pathspec, buf);\n  if (tmp_pathspec == 0)\n    {\n      lt_fatal (__FILE__, __LINE__,\n\t\t\"could not follow symlinks for %s\", pathspec);\n    }\n  return xstrdup (tmp_pathspec);\n#endif\n}\n\nchar *\nstrendzap (char *str, const char *pat)\n{\n  size_t len, patlen;\n\n  assert (str != NULL);\n  assert (pat != NULL);\n\n  len = strlen (str);\n  patlen = strlen (pat);\n\n  if (patlen <= len)\n    {\n      str += len - patlen;\n      if (STREQ (str, pat))\n\t*str = '\\0';\n    }\n  return str;\n}\n\nvoid\nlt_debugprintf (const char *file, int line, const char *fmt, ...)\n{\n  va_list args;\n  if (lt_debug)\n    {\n      (void) fprintf (stderr, \"%s:%s:%d: \", program_name, file, line);\n      va_start (args, fmt);\n      (void) vfprintf (stderr, fmt, args);\n      va_end (args);\n    }\n}\n\nstatic void\nlt_error_core (int exit_status, const char *file,\n\t       int line, const char *mode,\n\t       const char *message, va_list ap)\n{\n  fprintf (stderr, \"%s:%s:%d: %s: \", program_name, file, line, mode);\n  vfprintf (stderr, message, ap);\n  fprintf (stderr, \".\\n\");\n\n  if (exit_status >= 0)\n    exit (exit_status);\n}\n\nvoid\nlt_fatal (const char *file, int line, const char *message, ...)\n{\n  va_list ap;\n  va_start (ap, message);\n  lt_error_core (EXIT_FAILURE, file, line, \"FATAL\", message, ap);\n  va_end (ap);\n}\n\nstatic const char *\nnonnull (const char *s)\n{\n  return s ? s : \"(null)\";\n}\n\nstatic const char *\nnonempty (const char *s)\n{\n  return (s && !*s) ? \"(empty)\" : nonnull (s);\n}\n\nvoid\nlt_setenv (const char *name, const char *value)\n{\n  lt_debugprintf (__FILE__, __LINE__,\n\t\t  \"(lt_setenv) setting '%s' to '%s'\\n\",\n                  nonnull (name), nonnull (value));\n  {\n#ifdef HAVE_SETENV\n    /* always make a copy, for consistency with !HAVE_SETENV */\n    char *str = xstrdup (value);\n    setenv (name, str, 1);\n#else\n    size_t len = strlen (name) + 1 + strlen (value) + 1;\n    char *str = XMALLOC (char, len);\n    sprintf (str, \"%s=%s\", name, value);\n    if (putenv (str) != EXIT_SUCCESS)\n      {\n        XFREE (str);\n      }\n#endif\n  }\n}\n\nchar *\nlt_extend_str (const char *orig_value, const char *add, int to_end)\n{\n  char *new_value;\n  if (orig_value && *orig_value)\n    {\n      size_t orig_value_len = strlen (orig_value);\n      size_t add_len = strlen (add);\n      new_value = XMALLOC (char, add_len + orig_value_len + 1);\n      if (to_end)\n        {\n          strcpy (new_value, orig_value);\n          strcpy (new_value + orig_value_len, add);\n        }\n      else\n        {\n          strcpy (new_value, add);\n          strcpy (new_value + add_len, orig_value);\n        }\n    }\n  else\n    {\n      new_value = xstrdup (add);\n    }\n  return new_value;\n}\n\nvoid\nlt_update_exe_path (const char *name, const char *value)\n{\n  lt_debugprintf (__FILE__, __LINE__,\n\t\t  \"(lt_update_exe_path) modifying '%s' by prepending '%s'\\n\",\n                  nonnull (name), nonnull (value));\n\n  if (name && *name && value && *value)\n    {\n      char *new_value = lt_extend_str (getenv (name), value, 0);\n      /* some systems can't cope with a ':'-terminated path #' */\n      size_t len = strlen (new_value);\n      while ((len > 0) && IS_PATH_SEPARATOR (new_value[len-1]))\n        {\n          new_value[--len] = '\\0';\n        }\n      lt_setenv (name, new_value);\n      XFREE (new_value);\n    }\n}\n\nvoid\nlt_update_lib_path (const char *name, const char *value)\n{\n  lt_debugprintf (__FILE__, __LINE__,\n\t\t  \"(lt_update_lib_path) modifying '%s' by prepending '%s'\\n\",\n                  nonnull (name), nonnull (value));\n\n  if (name && *name && value && *value)\n    {\n      char *new_value = lt_extend_str (getenv (name), value, 0);\n      lt_setenv (name, new_value);\n      XFREE (new_value);\n    }\n}\n\nEOF\n\t    case $host_os in\n\t      mingw*)\n\t\tcat <<\"EOF\"\n\n/* Prepares an argument vector before calling spawn().\n   Note that spawn() does not by itself call the command interpreter\n     (getenv (\"COMSPEC\") != NULL ? getenv (\"COMSPEC\") :\n      ({ OSVERSIONINFO v; v.dwOSVersionInfoSize = sizeof(OSVERSIONINFO);\n         GetVersionEx(&v);\n         v.dwPlatformId == VER_PLATFORM_WIN32_NT;\n      }) ? \"cmd.exe\" : \"command.com\").\n   Instead it simply concatenates the arguments, separated by ' ', and calls\n   CreateProcess().  We must quote the arguments since Win32 CreateProcess()\n   interprets characters like ' ', '\\t', '\\\\', '\"' (but not '<' and '>') in a\n   special way:\n   - Space and tab are interpreted as delimiters. They are not treated as\n     delimiters if they are surrounded by double quotes: \"...\".\n   - Unescaped double quotes are removed from the input. Their only effect is\n     that within double quotes, space and tab are treated like normal\n     characters.\n   - Backslashes not followed by double quotes are not special.\n   - But 2*n+1 backslashes followed by a double quote become\n     n backslashes followed by a double quote (n >= 0):\n       \\\" -> \"\n       \\\\\\\" -> \\\"\n       \\\\\\\\\\\" -> \\\\\"\n */\n#define SHELL_SPECIAL_CHARS \"\\\"\\\\ \\001\\002\\003\\004\\005\\006\\007\\010\\011\\012\\013\\014\\015\\016\\017\\020\\021\\022\\023\\024\\025\\026\\027\\030\\031\\032\\033\\034\\035\\036\\037\"\n#define SHELL_SPACE_CHARS \" \\001\\002\\003\\004\\005\\006\\007\\010\\011\\012\\013\\014\\015\\016\\017\\020\\021\\022\\023\\024\\025\\026\\027\\030\\031\\032\\033\\034\\035\\036\\037\"\nchar **\nprepare_spawn (char **argv)\n{\n  size_t argc;\n  char **new_argv;\n  size_t i;\n\n  /* Count number of arguments.  */\n  for (argc = 0; argv[argc] != NULL; argc++)\n    ;\n\n  /* Allocate new argument vector.  */\n  new_argv = XMALLOC (char *, argc + 1);\n\n  /* Put quoted arguments into the new argument vector.  */\n  for (i = 0; i < argc; i++)\n    {\n      const char *string = argv[i];\n\n      if (string[0] == '\\0')\n\tnew_argv[i] = xstrdup (\"\\\"\\\"\");\n      else if (strpbrk (string, SHELL_SPECIAL_CHARS) != NULL)\n\t{\n\t  int quote_around = (strpbrk (string, SHELL_SPACE_CHARS) != NULL);\n\t  size_t length;\n\t  unsigned int backslashes;\n\t  const char *s;\n\t  char *quoted_string;\n\t  char *p;\n\n\t  length = 0;\n\t  backslashes = 0;\n\t  if (quote_around)\n\t    length++;\n\t  for (s = string; *s != '\\0'; s++)\n\t    {\n\t      char c = *s;\n\t      if (c == '\"')\n\t\tlength += backslashes + 1;\n\t      length++;\n\t      if (c == '\\\\')\n\t\tbackslashes++;\n\t      else\n\t\tbackslashes = 0;\n\t    }\n\t  if (quote_around)\n\t    length += backslashes + 1;\n\n\t  quoted_string = XMALLOC (char, length + 1);\n\n\t  p = quoted_string;\n\t  backslashes = 0;\n\t  if (quote_around)\n\t    *p++ = '\"';\n\t  for (s = string; *s != '\\0'; s++)\n\t    {\n\t      char c = *s;\n\t      if (c == '\"')\n\t\t{\n\t\t  unsigned int j;\n\t\t  for (j = backslashes + 1; j > 0; j--)\n\t\t    *p++ = '\\\\';\n\t\t}\n\t      *p++ = c;\n\t      if (c == '\\\\')\n\t\tbackslashes++;\n\t      else\n\t\tbackslashes = 0;\n\t    }\n\t  if (quote_around)\n\t    {\n\t      unsigned int j;\n\t      for (j = backslashes; j > 0; j--)\n\t\t*p++ = '\\\\';\n\t      *p++ = '\"';\n\t    }\n\t  *p = '\\0';\n\n\t  new_argv[i] = quoted_string;\n\t}\n      else\n\tnew_argv[i] = (char *) string;\n    }\n  new_argv[argc] = NULL;\n\n  return new_argv;\n}\nEOF\n\t\t;;\n\t    esac\n\n            cat <<\"EOF\"\nvoid lt_dump_script (FILE* f)\n{\nEOF\n\t    func_emit_wrapper yes |\n\t      $SED -n -e '\ns/^\\(.\\{79\\}\\)\\(..*\\)/\\1\\\n\\2/\nh\ns/\\([\\\\\"]\\)/\\\\\\1/g\ns/$/\\\\n/\ns/\\([^\\n]*\\).*/  fputs (\"\\1\", f);/p\ng\nD'\n            cat <<\"EOF\"\n}\nEOF\n}\n# end: func_emit_cwrapperexe_src\n\n# func_win32_import_lib_p ARG\n# True if ARG is an import lib, as indicated by $file_magic_cmd\nfunc_win32_import_lib_p ()\n{\n    $debug_cmd\n\n    case `eval $file_magic_cmd \\\"\\$1\\\" 2>/dev/null | $SED -e 10q` in\n    *import*) : ;;\n    *) false ;;\n    esac\n}\n\n# func_suncc_cstd_abi\n# !!ONLY CALL THIS FOR SUN CC AFTER $compile_command IS FULLY EXPANDED!!\n# Several compiler flags select an ABI that is incompatible with the\n# Cstd library. Avoid specifying it if any are in CXXFLAGS.\nfunc_suncc_cstd_abi ()\n{\n    $debug_cmd\n\n    case \" $compile_command \" in\n    *\" -compat=g \"*|*\\ -std=c++[0-9][0-9]\\ *|*\" -library=stdcxx4 \"*|*\" -library=stlport4 \"*)\n      suncc_use_cstd_abi=no\n      ;;\n    *)\n      suncc_use_cstd_abi=yes\n      ;;\n    esac\n}\n\n# func_mode_link arg...\nfunc_mode_link ()\n{\n    $debug_cmd\n\n    case $host in\n    *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*)\n      # It is impossible to link a dll without this setting, and\n      # we shouldn't force the makefile maintainer to figure out\n      # what system we are compiling for in order to pass an extra\n      # flag for every libtool invocation.\n      # allow_undefined=no\n\n      # FIXME: Unfortunately, there are problems with the above when trying\n      # to make a dll that has undefined symbols, in which case not\n      # even a static library is built.  For now, we need to specify\n      # -no-undefined on the libtool link line when we can be certain\n      # that all symbols are satisfied, otherwise we get a static library.\n      allow_undefined=yes\n      ;;\n    *)\n      allow_undefined=yes\n      ;;\n    esac\n    libtool_args=$nonopt\n    base_compile=\"$nonopt $@\"\n    compile_command=$nonopt\n    finalize_command=$nonopt\n\n    compile_rpath=\n    finalize_rpath=\n    compile_shlibpath=\n    finalize_shlibpath=\n    convenience=\n    old_convenience=\n    deplibs=\n    old_deplibs=\n    compiler_flags=\n    linker_flags=\n    dllsearchpath=\n    lib_search_path=`pwd`\n    inst_prefix_dir=\n    new_inherited_linker_flags=\n\n    avoid_version=no\n    bindir=\n    dlfiles=\n    dlprefiles=\n    dlself=no\n    export_dynamic=no\n    export_symbols=\n    export_symbols_regex=\n    generated=\n    libobjs=\n    ltlibs=\n    module=no\n    no_install=no\n    objs=\n    os2dllname=\n    non_pic_objects=\n    precious_files_regex=\n    prefer_static_libs=no\n    preload=false\n    prev=\n    prevarg=\n    release=\n    rpath=\n    xrpath=\n    perm_rpath=\n    temp_rpath=\n    thread_safe=no\n    vinfo=\n    vinfo_number=no\n    weak_libs=\n    single_module=$wl-single_module\n    func_infer_tag $base_compile\n\n    # We need to know -static, to get the right output filenames.\n    for arg\n    do\n      case $arg in\n      -shared)\n\ttest yes != \"$build_libtool_libs\" \\\n\t  && func_fatal_configuration \"cannot build a shared library\"\n\tbuild_old_libs=no\n\tbreak\n\t;;\n      -all-static | -static | -static-libtool-libs)\n\tcase $arg in\n\t-all-static)\n\t  if test yes = \"$build_libtool_libs\" && test -z \"$link_static_flag\"; then\n\t    func_warning \"complete static linking is impossible in this configuration\"\n\t  fi\n\t  if test -n \"$link_static_flag\"; then\n\t    dlopen_self=$dlopen_self_static\n\t  fi\n\t  prefer_static_libs=yes\n\t  ;;\n\t-static)\n\t  if test -z \"$pic_flag\" && test -n \"$link_static_flag\"; then\n\t    dlopen_self=$dlopen_self_static\n\t  fi\n\t  prefer_static_libs=built\n\t  ;;\n\t-static-libtool-libs)\n\t  if test -z \"$pic_flag\" && test -n \"$link_static_flag\"; then\n\t    dlopen_self=$dlopen_self_static\n\t  fi\n\t  prefer_static_libs=yes\n\t  ;;\n\tesac\n\tbuild_libtool_libs=no\n\tbuild_old_libs=yes\n\tbreak\n\t;;\n      esac\n    done\n\n    # See if our shared archives depend on static archives.\n    test -n \"$old_archive_from_new_cmds\" && build_old_libs=yes\n\n    # Go through the arguments, transforming them on the way.\n    while test \"$#\" -gt 0; do\n      arg=$1\n      shift\n      func_quote_arg pretty,unquoted \"$arg\"\n      qarg=$func_quote_arg_unquoted_result\n      func_append libtool_args \" $func_quote_arg_result\"\n\n      # If the previous option needs an argument, assign it.\n      if test -n \"$prev\"; then\n\tcase $prev in\n\toutput)\n\t  func_append compile_command \" @OUTPUT@\"\n\t  func_append finalize_command \" @OUTPUT@\"\n\t  ;;\n\tesac\n\n\tcase $prev in\n\tbindir)\n\t  bindir=$arg\n\t  prev=\n\t  continue\n\t  ;;\n\tdlfiles|dlprefiles)\n\t  $preload || {\n\t    # Add the symbol object into the linking commands.\n\t    func_append compile_command \" @SYMFILE@\"\n\t    func_append finalize_command \" @SYMFILE@\"\n\t    preload=:\n\t  }\n\t  case $arg in\n\t  *.la | *.lo) ;;  # We handle these cases below.\n\t  force)\n\t    if test no = \"$dlself\"; then\n\t      dlself=needless\n\t      export_dynamic=yes\n\t    fi\n\t    prev=\n\t    continue\n\t    ;;\n\t  self)\n\t    if test dlprefiles = \"$prev\"; then\n\t      dlself=yes\n\t    elif test dlfiles = \"$prev\" && test yes != \"$dlopen_self\"; then\n\t      dlself=yes\n\t    else\n\t      dlself=needless\n\t      export_dynamic=yes\n\t    fi\n\t    prev=\n\t    continue\n\t    ;;\n\t  *)\n\t    if test dlfiles = \"$prev\"; then\n\t      func_append dlfiles \" $arg\"\n\t    else\n\t      func_append dlprefiles \" $arg\"\n\t    fi\n\t    prev=\n\t    continue\n\t    ;;\n\t  esac\n\t  ;;\n\texpsyms)\n\t  export_symbols=$arg\n\t  test -f \"$arg\" \\\n\t    || func_fatal_error \"symbol file '$arg' does not exist\"\n\t  prev=\n\t  continue\n\t  ;;\n\texpsyms_regex)\n\t  export_symbols_regex=$arg\n\t  prev=\n\t  continue\n\t  ;;\n\tframework)\n\t  case $host in\n\t    *-*-darwin*)\n\t      case \"$deplibs \" in\n\t\t*\" $qarg.ltframework \"*) ;;\n\t\t*) func_append deplibs \" $qarg.ltframework\" # this is fixed later\n\t\t   ;;\n\t      esac\n\t      ;;\n\t  esac\n\t  prev=\n\t  continue\n\t  ;;\n\tinst_prefix)\n\t  inst_prefix_dir=$arg\n\t  prev=\n\t  continue\n\t  ;;\n\tmllvm)\n\t  # Clang does not use LLVM to link, so we can simply discard any\n\t  # '-mllvm $arg' options when doing the link step.\n\t  prev=\n\t  continue\n\t  ;;\n\tobjectlist)\n\t  if test -f \"$arg\"; then\n\t    save_arg=$arg\n\t    moreargs=\n\t    for fil in `cat \"$save_arg\"`\n\t    do\n#\t      func_append moreargs \" $fil\"\n\t      arg=$fil\n\t      # A libtool-controlled object.\n\n\t      # Check to see that this really is a libtool object.\n\t      if func_lalib_unsafe_p \"$arg\"; then\n\t\tpic_object=\n\t\tnon_pic_object=\n\n\t\t# Read the .lo file\n\t\tfunc_source \"$arg\"\n\n\t\tif test -z \"$pic_object\" ||\n\t\t   test -z \"$non_pic_object\" ||\n\t\t   test none = \"$pic_object\" &&\n\t\t   test none = \"$non_pic_object\"; then\n\t\t  func_fatal_error \"cannot find name of object for '$arg'\"\n\t\tfi\n\n\t\t# Extract subdirectory from the argument.\n\t\tfunc_dirname \"$arg\" \"/\" \"\"\n\t\txdir=$func_dirname_result\n\n\t\tif test none != \"$pic_object\"; then\n\t\t  # Prepend the subdirectory the object is found in.\n\t\t  pic_object=$xdir$pic_object\n\n\t\t  if test dlfiles = \"$prev\"; then\n\t\t    if test yes = \"$build_libtool_libs\" && test yes = \"$dlopen_support\"; then\n\t\t      func_append dlfiles \" $pic_object\"\n\t\t      prev=\n\t\t      continue\n\t\t    else\n\t\t      # If libtool objects are unsupported, then we need to preload.\n\t\t      prev=dlprefiles\n\t\t    fi\n\t\t  fi\n\n\t\t  # CHECK ME:  I think I busted this.  -Ossama\n\t\t  if test dlprefiles = \"$prev\"; then\n\t\t    # Preload the old-style object.\n\t\t    func_append dlprefiles \" $pic_object\"\n\t\t    prev=\n\t\t  fi\n\n\t\t  # A PIC object.\n\t\t  func_append libobjs \" $pic_object\"\n\t\t  arg=$pic_object\n\t\tfi\n\n\t\t# Non-PIC object.\n\t\tif test none != \"$non_pic_object\"; then\n\t\t  # Prepend the subdirectory the object is found in.\n\t\t  non_pic_object=$xdir$non_pic_object\n\n\t\t  # A standard non-PIC object\n\t\t  func_append non_pic_objects \" $non_pic_object\"\n\t\t  if test -z \"$pic_object\" || test none = \"$pic_object\"; then\n\t\t    arg=$non_pic_object\n\t\t  fi\n\t\telse\n\t\t  # If the PIC object exists, use it instead.\n\t\t  # $xdir was prepended to $pic_object above.\n\t\t  non_pic_object=$pic_object\n\t\t  func_append non_pic_objects \" $non_pic_object\"\n\t\tfi\n\t      else\n\t\t# Only an error if not doing a dry-run.\n\t\tif $opt_dry_run; then\n\t\t  # Extract subdirectory from the argument.\n\t\t  func_dirname \"$arg\" \"/\" \"\"\n\t\t  xdir=$func_dirname_result\n\n\t\t  func_lo2o \"$arg\"\n\t\t  pic_object=$xdir$objdir/$func_lo2o_result\n\t\t  non_pic_object=$xdir$func_lo2o_result\n\t\t  func_append libobjs \" $pic_object\"\n\t\t  func_append non_pic_objects \" $non_pic_object\"\n\t        else\n\t\t  func_fatal_error \"'$arg' is not a valid libtool object\"\n\t\tfi\n\t      fi\n\t    done\n\t  else\n\t    func_fatal_error \"link input file '$arg' does not exist\"\n\t  fi\n\t  arg=$save_arg\n\t  prev=\n\t  continue\n\t  ;;\n\tos2dllname)\n\t  os2dllname=$arg\n\t  prev=\n\t  continue\n\t  ;;\n\tprecious_regex)\n\t  precious_files_regex=$arg\n\t  prev=\n\t  continue\n\t  ;;\n\trelease)\n\t  release=-$arg\n\t  prev=\n\t  continue\n\t  ;;\n\trpath | xrpath)\n\t  # We need an absolute path.\n\t  case $arg in\n\t  [\\\\/]* | [A-Za-z]:[\\\\/]*) ;;\n\t  *)\n\t    func_fatal_error \"only absolute run-paths are allowed\"\n\t    ;;\n\t  esac\n\t  if test rpath = \"$prev\"; then\n\t    case \"$rpath \" in\n\t    *\" $arg \"*) ;;\n\t    *) func_append rpath \" $arg\" ;;\n\t    esac\n\t  else\n\t    case \"$xrpath \" in\n\t    *\" $arg \"*) ;;\n\t    *) func_append xrpath \" $arg\" ;;\n\t    esac\n\t  fi\n\t  prev=\n\t  continue\n\t  ;;\n\tshrext)\n\t  shrext_cmds=$arg\n\t  prev=\n\t  continue\n\t  ;;\n\tweak)\n\t  func_append weak_libs \" $arg\"\n\t  prev=\n\t  continue\n\t  ;;\n\txassembler)\n\t  func_append compiler_flags \" -Xassembler $qarg\"\n\t  prev=\n\t  func_append compile_command \" -Xassembler $qarg\"\n\t  func_append finalize_command \" -Xassembler $qarg\"\n\t  continue\n\t  ;;\n\txcclinker)\n\t  func_append linker_flags \" $qarg\"\n\t  func_append compiler_flags \" $qarg\"\n\t  prev=\n\t  func_append compile_command \" $qarg\"\n\t  func_append finalize_command \" $qarg\"\n\t  continue\n\t  ;;\n\txcompiler)\n\t  func_append compiler_flags \" $qarg\"\n\t  prev=\n\t  func_append compile_command \" $qarg\"\n\t  func_append finalize_command \" $qarg\"\n\t  continue\n\t  ;;\n\txlinker)\n\t  func_append linker_flags \" $qarg\"\n\t  func_append compiler_flags \" $wl$qarg\"\n\t  prev=\n\t  func_append compile_command \" $wl$qarg\"\n\t  func_append finalize_command \" $wl$qarg\"\n\t  continue\n\t  ;;\n\t*)\n\t  eval \"$prev=\\\"\\$arg\\\"\"\n\t  prev=\n\t  continue\n\t  ;;\n\tesac\n      fi # test -n \"$prev\"\n\n      prevarg=$arg\n\n      case $arg in\n      -all-static)\n\tif test -n \"$link_static_flag\"; then\n\t  # See comment for -static flag below, for more details.\n\t  func_append compile_command \" $link_static_flag\"\n\t  func_append finalize_command \" $link_static_flag\"\n\tfi\n\tcontinue\n\t;;\n\n      -allow-undefined)\n\t# FIXME: remove this flag sometime in the future.\n\tfunc_fatal_error \"'-allow-undefined' must not be used because it is the default\"\n\t;;\n\n      -avoid-version)\n\tavoid_version=yes\n\tcontinue\n\t;;\n\n      -bindir)\n\tprev=bindir\n\tcontinue\n\t;;\n\n      -dlopen)\n\tprev=dlfiles\n\tcontinue\n\t;;\n\n      -dlpreopen)\n\tprev=dlprefiles\n\tcontinue\n\t;;\n\n      -export-dynamic)\n\texport_dynamic=yes\n\tcontinue\n\t;;\n\n      -export-symbols | -export-symbols-regex)\n\tif test -n \"$export_symbols\" || test -n \"$export_symbols_regex\"; then\n\t  func_fatal_error \"more than one -exported-symbols argument is not allowed\"\n\tfi\n\tif test X-export-symbols = \"X$arg\"; then\n\t  prev=expsyms\n\telse\n\t  prev=expsyms_regex\n\tfi\n\tcontinue\n\t;;\n\n      -framework)\n\tprev=framework\n\tcontinue\n\t;;\n\n      -inst-prefix-dir)\n\tprev=inst_prefix\n\tcontinue\n\t;;\n\n      # The native IRIX linker understands -LANG:*, -LIST:* and -LNO:*\n      # so, if we see these flags be careful not to treat them like -L\n      -L[A-Z][A-Z]*:*)\n\tcase $with_gcc/$host in\n\tno/*-*-irix* | /*-*-irix*)\n\t  func_append compile_command \" $arg\"\n\t  func_append finalize_command \" $arg\"\n\t  ;;\n\tesac\n\tcontinue\n\t;;\n\n      -L*)\n\tfunc_stripname \"-L\" '' \"$arg\"\n\tif test -z \"$func_stripname_result\"; then\n\t  if test \"$#\" -gt 0; then\n\t    func_fatal_error \"require no space between '-L' and '$1'\"\n\t  else\n\t    func_fatal_error \"need path for '-L' option\"\n\t  fi\n\tfi\n\tfunc_resolve_sysroot \"$func_stripname_result\"\n\tdir=$func_resolve_sysroot_result\n\t# We need an absolute path.\n\tcase $dir in\n\t[\\\\/]* | [A-Za-z]:[\\\\/]*) ;;\n\t*)\n\t  absdir=`cd \"$dir\" && pwd`\n\t  test -z \"$absdir\" && \\\n\t    func_fatal_error \"cannot determine absolute directory name of '$dir'\"\n\t  dir=$absdir\n\t  ;;\n\tesac\n\tcase \"$deplibs \" in\n\t*\" -L$dir \"* | *\" $arg \"*)\n\t  # Will only happen for absolute or sysroot arguments\n\t  ;;\n\t*)\n\t  # Preserve sysroot, but never include relative directories\n\t  case $dir in\n\t    [\\\\/]* | [A-Za-z]:[\\\\/]* | =*) func_append deplibs \" $arg\" ;;\n\t    *) func_append deplibs \" -L$dir\" ;;\n\t  esac\n\t  func_append lib_search_path \" $dir\"\n\t  ;;\n\tesac\n\tcase $host in\n\t*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*)\n\t  testbindir=`$ECHO \"$dir\" | $SED 's*/lib$*/bin*'`\n\t  case :$dllsearchpath: in\n\t  *\":$dir:\"*) ;;\n\t  ::) dllsearchpath=$dir;;\n\t  *) func_append dllsearchpath \":$dir\";;\n\t  esac\n\t  case :$dllsearchpath: in\n\t  *\":$testbindir:\"*) ;;\n\t  ::) dllsearchpath=$testbindir;;\n\t  *) func_append dllsearchpath \":$testbindir\";;\n\t  esac\n\t  ;;\n\tesac\n\tcontinue\n\t;;\n\n      -l*)\n\tif test X-lc = \"X$arg\" || test X-lm = \"X$arg\"; then\n\t  case $host in\n\t  *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-beos* | *-cegcc* | *-*-haiku*)\n\t    # These systems don't actually have a C or math library (as such)\n\t    continue\n\t    ;;\n\t  *-*-os2*)\n\t    # These systems don't actually have a C library (as such)\n\t    test X-lc = \"X$arg\" && continue\n\t    ;;\n\t  *-*-openbsd* | *-*-freebsd* | *-*-dragonfly* | *-*-bitrig* | *-*-midnightbsd*)\n\t    # Do not include libc due to us having libc/libc_r.\n\t    test X-lc = \"X$arg\" && continue\n\t    ;;\n\t  *-*-rhapsody* | *-*-darwin1.[012])\n\t    # Rhapsody C and math libraries are in the System framework\n\t    func_append deplibs \" System.ltframework\"\n\t    continue\n\t    ;;\n\t  *-*-sco3.2v5* | *-*-sco5v6*)\n\t    # Causes problems with __ctype\n\t    test X-lc = \"X$arg\" && continue\n\t    ;;\n\t  *-*-sysv4.2uw2* | *-*-sysv5* | *-*-unixware* | *-*-OpenUNIX*)\n\t    # Compiler inserts libc in the correct place for threads to work\n\t    test X-lc = \"X$arg\" && continue\n\t    ;;\n\t  esac\n\telif test X-lc_r = \"X$arg\"; then\n\t case $host in\n\t *-*-openbsd* | *-*-freebsd* | *-*-dragonfly* | *-*-bitrig* | *-*-midnightbsd*)\n\t   # Do not include libc_r directly, use -pthread flag.\n\t   continue\n\t   ;;\n\t esac\n\tfi\n\tfunc_append deplibs \" $arg\"\n\tcontinue\n\t;;\n\n      -mllvm)\n\tprev=mllvm\n\tcontinue\n\t;;\n\n      -module)\n\tmodule=yes\n\tcontinue\n\t;;\n\n      # Tru64 UNIX uses -model [arg] to determine the layout of C++\n      # classes, name mangling, and exception handling.\n      # Darwin uses the -arch flag to determine output architecture.\n      -model|-arch|-isysroot|--sysroot)\n\tfunc_append compiler_flags \" $arg\"\n\tfunc_append compile_command \" $arg\"\n\tfunc_append finalize_command \" $arg\"\n\tprev=xcompiler\n\tcontinue\n\t;;\n     # Solaris ld rejects as of 11.4. Refer to Oracle bug 22985199.\n     -pthread)\n\tcase $host in\n\t  *solaris2*) ;;\n\t  *)\n\t    case \"$new_inherited_linker_flags \" in\n\t        *\" $arg \"*) ;;\n\t        * ) func_append new_inherited_linker_flags \" $arg\" ;;\n\t    esac\n\t  ;;\n\tesac\n\tcontinue\n\t;;\n      -mt|-mthreads|-kthread|-Kthread|-pthreads|--thread-safe \\\n      |-threads|-fopenmp|-openmp|-mp|-xopenmp|-omp|-qsmp=*)\n\tfunc_append compiler_flags \" $arg\"\n\tfunc_append compile_command \" $arg\"\n\tfunc_append finalize_command \" $arg\"\n\tcase \"$new_inherited_linker_flags \" in\n\t    *\" $arg \"*) ;;\n\t    * ) func_append new_inherited_linker_flags \" $arg\" ;;\n\tesac\n\tcontinue\n\t;;\n\n      -multi_module)\n\tsingle_module=$wl-multi_module\n\tcontinue\n\t;;\n\n      -no-fast-install)\n\tfast_install=no\n\tcontinue\n\t;;\n\n      -no-install)\n\tcase $host in\n\t*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-*-darwin* | *-cegcc*)\n\t  # The PATH hackery in wrapper scripts is required on Windows\n\t  # and Darwin in order for the loader to find any dlls it needs.\n\t  func_warning \"'-no-install' is ignored for $host\"\n\t  func_warning \"assuming '-no-fast-install' instead\"\n\t  fast_install=no\n\t  ;;\n\t*) no_install=yes ;;\n\tesac\n\tcontinue\n\t;;\n\n      -no-undefined)\n\tallow_undefined=no\n\tcontinue\n\t;;\n\n      -objectlist)\n\tprev=objectlist\n\tcontinue\n\t;;\n\n      -os2dllname)\n\tprev=os2dllname\n\tcontinue\n\t;;\n\n      -o) prev=output ;;\n\n      -precious-files-regex)\n\tprev=precious_regex\n\tcontinue\n\t;;\n\n      -release)\n\tprev=release\n\tcontinue\n\t;;\n\n      -rpath)\n\tprev=rpath\n\tcontinue\n\t;;\n\n      -R)\n\tprev=xrpath\n\tcontinue\n\t;;\n\n      -R*)\n\tfunc_stripname '-R' '' \"$arg\"\n\tdir=$func_stripname_result\n\t# We need an absolute path.\n\tcase $dir in\n\t[\\\\/]* | [A-Za-z]:[\\\\/]*) ;;\n\t=*)\n\t  func_stripname '=' '' \"$dir\"\n\t  dir=$lt_sysroot$func_stripname_result\n\t  ;;\n\t*)\n\t  func_fatal_error \"only absolute run-paths are allowed\"\n\t  ;;\n\tesac\n\tcase \"$xrpath \" in\n\t*\" $dir \"*) ;;\n\t*) func_append xrpath \" $dir\" ;;\n\tesac\n\tcontinue\n\t;;\n\n      -shared)\n\t# The effects of -shared are defined in a previous loop.\n\tcontinue\n\t;;\n\n      -shrext)\n\tprev=shrext\n\tcontinue\n\t;;\n\n      -static | -static-libtool-libs)\n\t# The effects of -static are defined in a previous loop.\n\t# We used to do the same as -all-static on platforms that\n\t# didn't have a PIC flag, but the assumption that the effects\n\t# would be equivalent was wrong.  It would break on at least\n\t# Digital Unix and AIX.\n\tcontinue\n\t;;\n\n      -thread-safe)\n\tthread_safe=yes\n\tcontinue\n\t;;\n\n      -version-info)\n\tprev=vinfo\n\tcontinue\n\t;;\n\n      -version-number)\n\tprev=vinfo\n\tvinfo_number=yes\n\tcontinue\n\t;;\n\n      -weak)\n        prev=weak\n\tcontinue\n\t;;\n\n      -Wc,*)\n\tfunc_stripname '-Wc,' '' \"$arg\"\n\targs=$func_stripname_result\n\targ=\n\tsave_ifs=$IFS; IFS=,\n\tfor flag in $args; do\n\t  IFS=$save_ifs\n          func_quote_arg pretty \"$flag\"\n\t  func_append arg \" $func_quote_arg_result\"\n\t  func_append compiler_flags \" $func_quote_arg_result\"\n\tdone\n\tIFS=$save_ifs\n\tfunc_stripname ' ' '' \"$arg\"\n\targ=$func_stripname_result\n\t;;\n\n      -Wl,*)\n\tfunc_stripname '-Wl,' '' \"$arg\"\n\targs=$func_stripname_result\n\targ=\n\tsave_ifs=$IFS; IFS=,\n\tfor flag in $args; do\n\t  IFS=$save_ifs\n          func_quote_arg pretty \"$flag\"\n\t  func_append arg \" $wl$func_quote_arg_result\"\n\t  func_append compiler_flags \" $wl$func_quote_arg_result\"\n\t  func_append linker_flags \" $func_quote_arg_result\"\n\tdone\n\tIFS=$save_ifs\n\tfunc_stripname ' ' '' \"$arg\"\n\targ=$func_stripname_result\n\t;;\n\n      -Xassembler)\n        prev=xassembler\n        continue\n        ;;\n\n      -Xcompiler)\n\tprev=xcompiler\n\tcontinue\n\t;;\n\n      -Xlinker)\n\tprev=xlinker\n\tcontinue\n\t;;\n\n      -XCClinker)\n\tprev=xcclinker\n\tcontinue\n\t;;\n\n      # -msg_* for osf cc\n      -msg_*)\n\tfunc_quote_arg pretty \"$arg\"\n\targ=$func_quote_arg_result\n\t;;\n\n      # Flags to be passed through unchanged, with rationale:\n      # -64, -mips[0-9]      enable 64-bit mode for the SGI compiler\n      # -r[0-9][0-9]*        specify processor for the SGI compiler\n      # -xarch=*, -xtarget=* enable 64-bit mode for the Sun compiler\n      # +DA*, +DD*           enable 64-bit mode for the HP compiler\n      # -q*                  compiler args for the IBM compiler\n      # -m*, -t[45]*, -txscale* architecture-specific flags for GCC\n      # -F/path              path to uninstalled frameworks, gcc on darwin\n      # -p, -pg, --coverage, -fprofile-*  profiling flags for GCC\n      # -fstack-protector*   stack protector flags for GCC\n      # @file                GCC response files\n      # -tp=*                Portland pgcc target processor selection\n      # --sysroot=*          for sysroot support\n      # -O*, -g*, -flto*, -fwhopr*, -fuse-linker-plugin GCC link-time optimization\n      # -specs=*             GCC specs files\n      # -stdlib=*            select c++ std lib with clang\n      # -fsanitize=*         Clang/GCC memory and address sanitizer\n      # -fuse-ld=*           Linker select flags for GCC\n      # -Wa,*                Pass flags directly to the assembler\n      -64|-mips[0-9]|-r[0-9][0-9]*|-xarch=*|-xtarget=*|+DA*|+DD*|-q*|-m*| \\\n      -t[45]*|-txscale*|-p|-pg|--coverage|-fprofile-*|-F*|@*|-tp=*|--sysroot=*| \\\n      -O*|-g*|-flto*|-fwhopr*|-fuse-linker-plugin|-fstack-protector*|-stdlib=*| \\\n      -specs=*|-fsanitize=*|-fuse-ld=*|-Wa,*)\n        func_quote_arg pretty \"$arg\"\n\targ=$func_quote_arg_result\n        func_append compile_command \" $arg\"\n        func_append finalize_command \" $arg\"\n        func_append compiler_flags \" $arg\"\n        continue\n        ;;\n\n      -Z*)\n        if test os2 = \"`expr $host : '.*\\(os2\\)'`\"; then\n          # OS/2 uses -Zxxx to specify OS/2-specific options\n\t  compiler_flags=\"$compiler_flags $arg\"\n\t  func_append compile_command \" $arg\"\n\t  func_append finalize_command \" $arg\"\n\t  case $arg in\n\t  -Zlinker | -Zstack)\n\t    prev=xcompiler\n\t    ;;\n\t  esac\n\t  continue\n        else\n\t  # Otherwise treat like 'Some other compiler flag' below\n\t  func_quote_arg pretty \"$arg\"\n\t  arg=$func_quote_arg_result\n        fi\n\t;;\n\n      # Some other compiler flag.\n      -* | +*)\n        func_quote_arg pretty \"$arg\"\n\targ=$func_quote_arg_result\n\t;;\n\n      *.$objext)\n\t# A standard object.\n\tfunc_append objs \" $arg\"\n\t;;\n\n      *.lo)\n\t# A libtool-controlled object.\n\n\t# Check to see that this really is a libtool object.\n\tif func_lalib_unsafe_p \"$arg\"; then\n\t  pic_object=\n\t  non_pic_object=\n\n\t  # Read the .lo file\n\t  func_source \"$arg\"\n\n\t  if test -z \"$pic_object\" ||\n\t     test -z \"$non_pic_object\" ||\n\t     test none = \"$pic_object\" &&\n\t     test none = \"$non_pic_object\"; then\n\t    func_fatal_error \"cannot find name of object for '$arg'\"\n\t  fi\n\n\t  # Extract subdirectory from the argument.\n\t  func_dirname \"$arg\" \"/\" \"\"\n\t  xdir=$func_dirname_result\n\n\t  test none = \"$pic_object\" || {\n\t    # Prepend the subdirectory the object is found in.\n\t    pic_object=$xdir$pic_object\n\n\t    if test dlfiles = \"$prev\"; then\n\t      if test yes = \"$build_libtool_libs\" && test yes = \"$dlopen_support\"; then\n\t\tfunc_append dlfiles \" $pic_object\"\n\t\tprev=\n\t\tcontinue\n\t      else\n\t\t# If libtool objects are unsupported, then we need to preload.\n\t\tprev=dlprefiles\n\t      fi\n\t    fi\n\n\t    # CHECK ME:  I think I busted this.  -Ossama\n\t    if test dlprefiles = \"$prev\"; then\n\t      # Preload the old-style object.\n\t      func_append dlprefiles \" $pic_object\"\n\t      prev=\n\t    fi\n\n\t    # A PIC object.\n\t    func_append libobjs \" $pic_object\"\n\t    arg=$pic_object\n\t  }\n\n\t  # Non-PIC object.\n\t  if test none != \"$non_pic_object\"; then\n\t    # Prepend the subdirectory the object is found in.\n\t    non_pic_object=$xdir$non_pic_object\n\n\t    # A standard non-PIC object\n\t    func_append non_pic_objects \" $non_pic_object\"\n\t    if test -z \"$pic_object\" || test none = \"$pic_object\"; then\n\t      arg=$non_pic_object\n\t    fi\n\t  else\n\t    # If the PIC object exists, use it instead.\n\t    # $xdir was prepended to $pic_object above.\n\t    non_pic_object=$pic_object\n\t    func_append non_pic_objects \" $non_pic_object\"\n\t  fi\n\telse\n\t  # Only an error if not doing a dry-run.\n\t  if $opt_dry_run; then\n\t    # Extract subdirectory from the argument.\n\t    func_dirname \"$arg\" \"/\" \"\"\n\t    xdir=$func_dirname_result\n\n\t    func_lo2o \"$arg\"\n\t    pic_object=$xdir$objdir/$func_lo2o_result\n\t    non_pic_object=$xdir$func_lo2o_result\n\t    func_append libobjs \" $pic_object\"\n\t    func_append non_pic_objects \" $non_pic_object\"\n\t  else\n\t    func_fatal_error \"'$arg' is not a valid libtool object\"\n\t  fi\n\tfi\n\t;;\n\n      *.$libext)\n\t# An archive.\n\tfunc_append deplibs \" $arg\"\n\tfunc_append old_deplibs \" $arg\"\n\tcontinue\n\t;;\n\n      *.la)\n\t# A libtool-controlled library.\n\n\tfunc_resolve_sysroot \"$arg\"\n\tif test dlfiles = \"$prev\"; then\n\t  # This library was specified with -dlopen.\n\t  func_append dlfiles \" $func_resolve_sysroot_result\"\n\t  prev=\n\telif test dlprefiles = \"$prev\"; then\n\t  # The library was specified with -dlpreopen.\n\t  func_append dlprefiles \" $func_resolve_sysroot_result\"\n\t  prev=\n\telse\n\t  func_append deplibs \" $func_resolve_sysroot_result\"\n\tfi\n\tcontinue\n\t;;\n\n      # Some other compiler argument.\n      *)\n\t# Unknown arguments in both finalize_command and compile_command need\n\t# to be aesthetically quoted because they are evaled later.\n\tfunc_quote_arg pretty \"$arg\"\n\targ=$func_quote_arg_result\n\t;;\n      esac # arg\n\n      # Now actually substitute the argument into the commands.\n      if test -n \"$arg\"; then\n\tfunc_append compile_command \" $arg\"\n\tfunc_append finalize_command \" $arg\"\n      fi\n    done # argument parsing loop\n\n    test -n \"$prev\" && \\\n      func_fatal_help \"the '$prevarg' option requires an argument\"\n\n    if test yes = \"$export_dynamic\" && test -n \"$export_dynamic_flag_spec\"; then\n      eval arg=\\\"$export_dynamic_flag_spec\\\"\n      func_append compile_command \" $arg\"\n      func_append finalize_command \" $arg\"\n    fi\n\n    oldlibs=\n    # calculate the name of the file, without its directory\n    func_basename \"$output\"\n    outputname=$func_basename_result\n    libobjs_save=$libobjs\n\n    if test -n \"$shlibpath_var\"; then\n      # get the directories listed in $shlibpath_var\n      eval shlib_search_path=\\`\\$ECHO \\\"\\$$shlibpath_var\\\" \\| \\$SED \\'s/:/ /g\\'\\`\n    else\n      shlib_search_path=\n    fi\n    eval sys_lib_search_path=\\\"$sys_lib_search_path_spec\\\"\n    eval sys_lib_dlsearch_path=\\\"$sys_lib_dlsearch_path_spec\\\"\n\n    # Definition is injected by LT_CONFIG during libtool generation.\n    func_munge_path_list sys_lib_dlsearch_path \"$LT_SYS_LIBRARY_PATH\"\n\n    func_dirname \"$output\" \"/\" \"\"\n    output_objdir=$func_dirname_result$objdir\n    func_to_tool_file \"$output_objdir/\"\n    tool_output_objdir=$func_to_tool_file_result\n    # Create the object directory.\n    func_mkdir_p \"$output_objdir\"\n\n    # Determine the type of output\n    case $output in\n    \"\")\n      func_fatal_help \"you must specify an output file\"\n      ;;\n    *.$libext) linkmode=oldlib ;;\n    *.lo | *.$objext) linkmode=obj ;;\n    *.la) linkmode=lib ;;\n    *) linkmode=prog ;; # Anything else should be a program.\n    esac\n\n    specialdeplibs=\n\n    libs=\n    # Find all interdependent deplibs by searching for libraries\n    # that are linked more than once (e.g. -la -lb -la)\n    for deplib in $deplibs; do\n      if $opt_preserve_dup_deps; then\n\tcase \"$libs \" in\n\t*\" $deplib \"*) func_append specialdeplibs \" $deplib\" ;;\n\tesac\n      fi\n      func_append libs \" $deplib\"\n    done\n\n    if test lib = \"$linkmode\"; then\n      libs=\"$predeps $libs $compiler_lib_search_path $postdeps\"\n\n      # Compute libraries that are listed more than once in $predeps\n      # $postdeps and mark them as special (i.e., whose duplicates are\n      # not to be eliminated).\n      pre_post_deps=\n      if $opt_duplicate_compiler_generated_deps; then\n\tfor pre_post_dep in $predeps $postdeps; do\n\t  case \"$pre_post_deps \" in\n\t  *\" $pre_post_dep \"*) func_append specialdeplibs \" $pre_post_deps\" ;;\n\t  esac\n\t  func_append pre_post_deps \" $pre_post_dep\"\n\tdone\n      fi\n      pre_post_deps=\n    fi\n\n    deplibs=\n    newdependency_libs=\n    newlib_search_path=\n    need_relink=no # whether we're linking any uninstalled libtool libraries\n    notinst_deplibs= # not-installed libtool libraries\n    notinst_path= # paths that contain not-installed libtool libraries\n\n    case $linkmode in\n    lib)\n\tpasses=\"conv dlpreopen link\"\n\tfor file in $dlfiles $dlprefiles; do\n\t  case $file in\n\t  *.la) ;;\n\t  *)\n\t    func_fatal_help \"libraries can '-dlopen' only libtool libraries: $file\"\n\t    ;;\n\t  esac\n\tdone\n\t;;\n    prog)\n\tcompile_deplibs=\n\tfinalize_deplibs=\n\talldeplibs=false\n\tnewdlfiles=\n\tnewdlprefiles=\n\tpasses=\"conv scan dlopen dlpreopen link\"\n\t;;\n    *)  passes=\"conv\"\n\t;;\n    esac\n\n    for pass in $passes; do\n      # The preopen pass in lib mode reverses $deplibs; put it back here\n      # so that -L comes before libs that need it for instance...\n      if test lib,link = \"$linkmode,$pass\"; then\n\t## FIXME: Find the place where the list is rebuilt in the wrong\n\t##        order, and fix it there properly\n        tmp_deplibs=\n\tfor deplib in $deplibs; do\n\t  tmp_deplibs=\"$deplib $tmp_deplibs\"\n\tdone\n\tdeplibs=$tmp_deplibs\n      fi\n\n      if test lib,link = \"$linkmode,$pass\" ||\n\t test prog,scan = \"$linkmode,$pass\"; then\n\tlibs=$deplibs\n\tdeplibs=\n      fi\n      if test prog = \"$linkmode\"; then\n\tcase $pass in\n\tdlopen) libs=$dlfiles ;;\n\tdlpreopen) libs=$dlprefiles ;;\n\tlink) libs=\"$deplibs %DEPLIBS% $dependency_libs\" ;;\n\tesac\n      fi\n      if test lib,dlpreopen = \"$linkmode,$pass\"; then\n\t# Collect and forward deplibs of preopened libtool libs\n\tfor lib in $dlprefiles; do\n\t  # Ignore non-libtool-libs\n\t  dependency_libs=\n\t  func_resolve_sysroot \"$lib\"\n\t  case $lib in\n\t  *.la)\tfunc_source \"$func_resolve_sysroot_result\" ;;\n\t  esac\n\n\t  # Collect preopened libtool deplibs, except any this library\n\t  # has declared as weak libs\n\t  for deplib in $dependency_libs; do\n\t    func_basename \"$deplib\"\n            deplib_base=$func_basename_result\n\t    case \" $weak_libs \" in\n\t    *\" $deplib_base \"*) ;;\n\t    *) func_append deplibs \" $deplib\" ;;\n\t    esac\n\t  done\n\tdone\n\tlibs=$dlprefiles\n      fi\n      if test dlopen = \"$pass\"; then\n\t# Collect dlpreopened libraries\n\tsave_deplibs=$deplibs\n\tdeplibs=\n      fi\n\n      for deplib in $libs; do\n\tlib=\n\tfound=false\n\tcase $deplib in\n\t-mt|-mthreads|-kthread|-Kthread|-pthread|-pthreads|--thread-safe \\\n        |-threads|-fopenmp|-openmp|-mp|-xopenmp|-omp|-qsmp=*)\n\t  if test prog,link = \"$linkmode,$pass\"; then\n\t    compile_deplibs=\"$deplib $compile_deplibs\"\n\t    finalize_deplibs=\"$deplib $finalize_deplibs\"\n\t  else\n\t    func_append compiler_flags \" $deplib\"\n\t    if test lib = \"$linkmode\"; then\n\t\tcase \"$new_inherited_linker_flags \" in\n\t\t    *\" $deplib \"*) ;;\n\t\t    * ) func_append new_inherited_linker_flags \" $deplib\" ;;\n\t\tesac\n\t    fi\n\t  fi\n\t  continue\n\t  ;;\n\t-l*)\n\t  if test lib != \"$linkmode\" && test prog != \"$linkmode\"; then\n\t    func_warning \"'-l' is ignored for archives/objects\"\n\t    continue\n\t  fi\n\t  func_stripname '-l' '' \"$deplib\"\n\t  name=$func_stripname_result\n\t  if test lib = \"$linkmode\"; then\n\t    searchdirs=\"$newlib_search_path $lib_search_path $compiler_lib_search_dirs $sys_lib_search_path $shlib_search_path\"\n\t  else\n\t    searchdirs=\"$newlib_search_path $lib_search_path $sys_lib_search_path $shlib_search_path\"\n\t  fi\n\t  for searchdir in $searchdirs; do\n\t    for search_ext in .la $std_shrext .so .a; do\n\t      # Search the libtool library\n\t      lib=$searchdir/lib$name$search_ext\n\t      if test -f \"$lib\"; then\n\t\tif test .la = \"$search_ext\"; then\n\t\t  found=:\n\t\telse\n\t\t  found=false\n\t\tfi\n\t\tbreak 2\n\t      fi\n\t    done\n\t  done\n\t  if $found; then\n\t    # deplib is a libtool library\n\t    # If $allow_libtool_libs_with_static_runtimes && $deplib is a stdlib,\n\t    # We need to do some special things here, and not later.\n\t    if test yes = \"$allow_libtool_libs_with_static_runtimes\"; then\n\t      case \" $predeps $postdeps \" in\n\t      *\" $deplib \"*)\n\t\tif func_lalib_p \"$lib\"; then\n\t\t  library_names=\n\t\t  old_library=\n\t\t  func_source \"$lib\"\n\t\t  for l in $old_library $library_names; do\n\t\t    ll=$l\n\t\t  done\n\t\t  if test \"X$ll\" = \"X$old_library\"; then # only static version available\n\t\t    found=false\n\t\t    func_dirname \"$lib\" \"\" \".\"\n\t\t    ladir=$func_dirname_result\n\t\t    lib=$ladir/$old_library\n\t\t    if test prog,link = \"$linkmode,$pass\"; then\n\t\t      compile_deplibs=\"$deplib $compile_deplibs\"\n\t\t      finalize_deplibs=\"$deplib $finalize_deplibs\"\n\t\t    else\n\t\t      deplibs=\"$deplib $deplibs\"\n\t\t      test lib = \"$linkmode\" && newdependency_libs=\"$deplib $newdependency_libs\"\n\t\t    fi\n\t\t    continue\n\t\t  fi\n\t\tfi\n\t\t;;\n\t      *) ;;\n\t      esac\n\t    fi\n\t  else\n\t    # deplib doesn't seem to be a libtool library\n\t    if test prog,link = \"$linkmode,$pass\"; then\n\t      compile_deplibs=\"$deplib $compile_deplibs\"\n\t      finalize_deplibs=\"$deplib $finalize_deplibs\"\n\t    else\n\t      deplibs=\"$deplib $deplibs\"\n\t      test lib = \"$linkmode\" && newdependency_libs=\"$deplib $newdependency_libs\"\n\t    fi\n\t    continue\n\t  fi\n\t  ;; # -l\n\t*.ltframework)\n\t  if test prog,link = \"$linkmode,$pass\"; then\n\t    compile_deplibs=\"$deplib $compile_deplibs\"\n\t    finalize_deplibs=\"$deplib $finalize_deplibs\"\n\t  else\n\t    deplibs=\"$deplib $deplibs\"\n\t    if test lib = \"$linkmode\"; then\n\t\tcase \"$new_inherited_linker_flags \" in\n\t\t    *\" $deplib \"*) ;;\n\t\t    * ) func_append new_inherited_linker_flags \" $deplib\" ;;\n\t\tesac\n\t    fi\n\t  fi\n\t  continue\n\t  ;;\n\t-L*)\n\t  case $linkmode in\n\t  lib)\n\t    deplibs=\"$deplib $deplibs\"\n\t    test conv = \"$pass\" && continue\n\t    newdependency_libs=\"$deplib $newdependency_libs\"\n\t    func_stripname '-L' '' \"$deplib\"\n\t    func_resolve_sysroot \"$func_stripname_result\"\n\t    func_append newlib_search_path \" $func_resolve_sysroot_result\"\n\t    ;;\n\t  prog)\n\t    if test conv = \"$pass\"; then\n\t      deplibs=\"$deplib $deplibs\"\n\t      continue\n\t    fi\n\t    if test scan = \"$pass\"; then\n\t      deplibs=\"$deplib $deplibs\"\n\t    else\n\t      compile_deplibs=\"$deplib $compile_deplibs\"\n\t      finalize_deplibs=\"$deplib $finalize_deplibs\"\n\t    fi\n\t    func_stripname '-L' '' \"$deplib\"\n\t    func_resolve_sysroot \"$func_stripname_result\"\n\t    func_append newlib_search_path \" $func_resolve_sysroot_result\"\n\t    ;;\n\t  *)\n\t    func_warning \"'-L' is ignored for archives/objects\"\n\t    ;;\n\t  esac # linkmode\n\t  continue\n\t  ;; # -L\n\t-R*)\n\t  if test link = \"$pass\"; then\n\t    func_stripname '-R' '' \"$deplib\"\n\t    func_resolve_sysroot \"$func_stripname_result\"\n\t    dir=$func_resolve_sysroot_result\n\t    # Make sure the xrpath contains only unique directories.\n\t    case \"$xrpath \" in\n\t    *\" $dir \"*) ;;\n\t    *) func_append xrpath \" $dir\" ;;\n\t    esac\n\t  fi\n\t  deplibs=\"$deplib $deplibs\"\n\t  continue\n\t  ;;\n\t*.la)\n\t  func_resolve_sysroot \"$deplib\"\n\t  lib=$func_resolve_sysroot_result\n\t  ;;\n\t*.$libext)\n\t  if test conv = \"$pass\"; then\n\t    deplibs=\"$deplib $deplibs\"\n\t    continue\n\t  fi\n\t  case $linkmode in\n\t  lib)\n\t    # Linking convenience modules into shared libraries is allowed,\n\t    # but linking other static libraries is non-portable.\n\t    case \" $dlpreconveniencelibs \" in\n\t    *\" $deplib \"*) ;;\n\t    *)\n\t      valid_a_lib=false\n\t      case $deplibs_check_method in\n\t\tmatch_pattern*)\n\t\t  set dummy $deplibs_check_method; shift\n\t\t  match_pattern_regex=`expr \"$deplibs_check_method\" : \"$1 \\(.*\\)\"`\n\t\t  if eval \"\\$ECHO \\\"$deplib\\\"\" 2>/dev/null | $SED 10q \\\n\t\t    | $EGREP \"$match_pattern_regex\" > /dev/null; then\n\t\t    valid_a_lib=:\n\t\t  fi\n\t\t;;\n\t\tpass_all)\n\t\t  valid_a_lib=:\n\t\t;;\n\t      esac\n\t      if $valid_a_lib; then\n\t\techo\n\t\t$ECHO \"*** Warning: Linking the shared library $output against the\"\n\t\t$ECHO \"*** static library $deplib is not portable!\"\n\t\tdeplibs=\"$deplib $deplibs\"\n\t      else\n\t\techo\n\t\t$ECHO \"*** Warning: Trying to link with static lib archive $deplib.\"\n\t\techo \"*** I have the capability to make that library automatically link in when\"\n\t\techo \"*** you link to this library.  But I can only do this if you have a\"\n\t\techo \"*** shared version of the library, which you do not appear to have\"\n\t\techo \"*** because the file extensions .$libext of this argument makes me believe\"\n\t\techo \"*** that it is just a static archive that I should not use here.\"\n\t      fi\n\t      ;;\n\t    esac\n\t    continue\n\t    ;;\n\t  prog)\n\t    if test link != \"$pass\"; then\n\t      deplibs=\"$deplib $deplibs\"\n\t    else\n\t      compile_deplibs=\"$deplib $compile_deplibs\"\n\t      finalize_deplibs=\"$deplib $finalize_deplibs\"\n\t    fi\n\t    continue\n\t    ;;\n\t  esac # linkmode\n\t  ;; # *.$libext\n\t*.lo | *.$objext)\n\t  if test conv = \"$pass\"; then\n\t    deplibs=\"$deplib $deplibs\"\n\t  elif test prog = \"$linkmode\"; then\n\t    if test dlpreopen = \"$pass\" || test yes != \"$dlopen_support\" || test no = \"$build_libtool_libs\"; then\n\t      # If there is no dlopen support or we're linking statically,\n\t      # we need to preload.\n\t      func_append newdlprefiles \" $deplib\"\n\t      compile_deplibs=\"$deplib $compile_deplibs\"\n\t      finalize_deplibs=\"$deplib $finalize_deplibs\"\n\t    else\n\t      func_append newdlfiles \" $deplib\"\n\t    fi\n\t  fi\n\t  continue\n\t  ;;\n\t%DEPLIBS%)\n\t  alldeplibs=:\n\t  continue\n\t  ;;\n\tesac # case $deplib\n\n\t$found || test -f \"$lib\" \\\n\t  || func_fatal_error \"cannot find the library '$lib' or unhandled argument '$deplib'\"\n\n\t# Check to see that this really is a libtool archive.\n\tfunc_lalib_unsafe_p \"$lib\" \\\n\t  || func_fatal_error \"'$lib' is not a valid libtool archive\"\n\n\tfunc_dirname \"$lib\" \"\" \".\"\n\tladir=$func_dirname_result\n\n\tdlname=\n\tdlopen=\n\tdlpreopen=\n\tlibdir=\n\tlibrary_names=\n\told_library=\n\tinherited_linker_flags=\n\t# If the library was installed with an old release of libtool,\n\t# it will not redefine variables installed, or shouldnotlink\n\tinstalled=yes\n\tshouldnotlink=no\n\tavoidtemprpath=\n\n\n\t# Read the .la file\n\tfunc_source \"$lib\"\n\n\t# Convert \"-framework foo\" to \"foo.ltframework\"\n\tif test -n \"$inherited_linker_flags\"; then\n\t  tmp_inherited_linker_flags=`$ECHO \"$inherited_linker_flags\" | $SED 's/-framework \\([^ $]*\\)/\\1.ltframework/g'`\n\t  for tmp_inherited_linker_flag in $tmp_inherited_linker_flags; do\n\t    case \" $new_inherited_linker_flags \" in\n\t      *\" $tmp_inherited_linker_flag \"*) ;;\n\t      *) func_append new_inherited_linker_flags \" $tmp_inherited_linker_flag\";;\n\t    esac\n\t  done\n\tfi\n\tdependency_libs=`$ECHO \" $dependency_libs\" | $SED 's% \\([^ $]*\\).ltframework% -framework \\1%g'`\n\tif test lib,link = \"$linkmode,$pass\" ||\n\t   test prog,scan = \"$linkmode,$pass\" ||\n\t   { test prog != \"$linkmode\" && test lib != \"$linkmode\"; }; then\n\t  test -n \"$dlopen\" && func_append dlfiles \" $dlopen\"\n\t  test -n \"$dlpreopen\" && func_append dlprefiles \" $dlpreopen\"\n\tfi\n\n\tif test conv = \"$pass\"; then\n\t  # Only check for convenience libraries\n\t  deplibs=\"$lib $deplibs\"\n\t  if test -z \"$libdir\"; then\n\t    if test -z \"$old_library\"; then\n\t      func_fatal_error \"cannot find name of link library for '$lib'\"\n\t    fi\n\t    # It is a libtool convenience library, so add in its objects.\n\t    func_append convenience \" $ladir/$objdir/$old_library\"\n\t    func_append old_convenience \" $ladir/$objdir/$old_library\"\n\t  elif test prog != \"$linkmode\" && test lib != \"$linkmode\"; then\n\t    func_fatal_error \"'$lib' is not a convenience library\"\n\t  fi\n\t  tmp_libs=\n\t  for deplib in $dependency_libs; do\n\t    deplibs=\"$deplib $deplibs\"\n\t    if $opt_preserve_dup_deps; then\n\t      case \"$tmp_libs \" in\n\t      *\" $deplib \"*) func_append specialdeplibs \" $deplib\" ;;\n\t      esac\n\t    fi\n\t    func_append tmp_libs \" $deplib\"\n\t  done\n\t  continue\n\tfi # $pass = conv\n\n\n\t# Get the name of the library we link against.\n\tlinklib=\n\tif test -n \"$old_library\" &&\n\t   { test yes = \"$prefer_static_libs\" ||\n\t     test built,no = \"$prefer_static_libs,$installed\"; }; then\n\t  linklib=$old_library\n\telse\n\t  for l in $old_library $library_names; do\n\t    linklib=$l\n\t  done\n\tfi\n\tif test -z \"$linklib\"; then\n\t  func_fatal_error \"cannot find name of link library for '$lib'\"\n\tfi\n\n\t# This library was specified with -dlopen.\n\tif test dlopen = \"$pass\"; then\n\t  test -z \"$libdir\" \\\n\t    && func_fatal_error \"cannot -dlopen a convenience library: '$lib'\"\n\t  if test -z \"$dlname\" ||\n\t     test yes != \"$dlopen_support\" ||\n\t     test no = \"$build_libtool_libs\"\n\t  then\n\t    # If there is no dlname, no dlopen support or we're linking\n\t    # statically, we need to preload.  We also need to preload any\n\t    # dependent libraries so libltdl's deplib preloader doesn't\n\t    # bomb out in the load deplibs phase.\n\t    func_append dlprefiles \" $lib $dependency_libs\"\n\t  else\n\t    func_append newdlfiles \" $lib\"\n\t  fi\n\t  continue\n\tfi # $pass = dlopen\n\n\t# We need an absolute path.\n\tcase $ladir in\n\t[\\\\/]* | [A-Za-z]:[\\\\/]*) abs_ladir=$ladir ;;\n\t*)\n\t  abs_ladir=`cd \"$ladir\" && pwd`\n\t  if test -z \"$abs_ladir\"; then\n\t    func_warning \"cannot determine absolute directory name of '$ladir'\"\n\t    func_warning \"passing it literally to the linker, although it might fail\"\n\t    abs_ladir=$ladir\n\t  fi\n\t  ;;\n\tesac\n\tfunc_basename \"$lib\"\n\tlaname=$func_basename_result\n\n\t# Find the relevant object directory and library name.\n\tif test yes = \"$installed\"; then\n\t  if test ! -f \"$lt_sysroot$libdir/$linklib\" && test -f \"$abs_ladir/$linklib\"; then\n\t    func_warning \"library '$lib' was moved.\"\n\t    dir=$ladir\n\t    absdir=$abs_ladir\n\t    libdir=$abs_ladir\n\t  else\n\t    dir=$lt_sysroot$libdir\n\t    absdir=$lt_sysroot$libdir\n\t  fi\n\t  test yes = \"$hardcode_automatic\" && avoidtemprpath=yes\n\telse\n\t  if test ! -f \"$ladir/$objdir/$linklib\" && test -f \"$abs_ladir/$linklib\"; then\n\t    dir=$ladir\n\t    absdir=$abs_ladir\n\t    # Remove this search path later\n\t    func_append notinst_path \" $abs_ladir\"\n\t  else\n\t    dir=$ladir/$objdir\n\t    absdir=$abs_ladir/$objdir\n\t    # Remove this search path later\n\t    func_append notinst_path \" $abs_ladir\"\n\t  fi\n\tfi # $installed = yes\n\tfunc_stripname 'lib' '.la' \"$laname\"\n\tname=$func_stripname_result\n\n\t# This library was specified with -dlpreopen.\n\tif test dlpreopen = \"$pass\"; then\n\t  if test -z \"$libdir\" && test prog = \"$linkmode\"; then\n\t    func_fatal_error \"only libraries may -dlpreopen a convenience library: '$lib'\"\n\t  fi\n\t  case $host in\n\t    # special handling for platforms with PE-DLLs.\n\t    *cygwin* | *mingw* | *cegcc* )\n\t      # Linker will automatically link against shared library if both\n\t      # static and shared are present.  Therefore, ensure we extract\n\t      # symbols from the import library if a shared library is present\n\t      # (otherwise, the dlopen module name will be incorrect).  We do\n\t      # this by putting the import library name into $newdlprefiles.\n\t      # We recover the dlopen module name by 'saving' the la file\n\t      # name in a special purpose variable, and (later) extracting the\n\t      # dlname from the la file.\n\t      if test -n \"$dlname\"; then\n\t        func_tr_sh \"$dir/$linklib\"\n\t        eval \"libfile_$func_tr_sh_result=\\$abs_ladir/\\$laname\"\n\t        func_append newdlprefiles \" $dir/$linklib\"\n\t      else\n\t        func_append newdlprefiles \" $dir/$old_library\"\n\t        # Keep a list of preopened convenience libraries to check\n\t        # that they are being used correctly in the link pass.\n\t        test -z \"$libdir\" && \\\n\t          func_append dlpreconveniencelibs \" $dir/$old_library\"\n\t      fi\n\t    ;;\n\t    * )\n\t      # Prefer using a static library (so that no silly _DYNAMIC symbols\n\t      # are required to link).\n\t      if test -n \"$old_library\"; then\n\t        func_append newdlprefiles \" $dir/$old_library\"\n\t        # Keep a list of preopened convenience libraries to check\n\t        # that they are being used correctly in the link pass.\n\t        test -z \"$libdir\" && \\\n\t          func_append dlpreconveniencelibs \" $dir/$old_library\"\n\t      # Otherwise, use the dlname, so that lt_dlopen finds it.\n\t      elif test -n \"$dlname\"; then\n\t        func_append newdlprefiles \" $dir/$dlname\"\n\t      else\n\t        func_append newdlprefiles \" $dir/$linklib\"\n\t      fi\n\t    ;;\n\t  esac\n\tfi # $pass = dlpreopen\n\n\tif test -z \"$libdir\"; then\n\t  # Link the convenience library\n\t  if test lib = \"$linkmode\"; then\n\t    deplibs=\"$dir/$old_library $deplibs\"\n\t  elif test prog,link = \"$linkmode,$pass\"; then\n\t    compile_deplibs=\"$dir/$old_library $compile_deplibs\"\n\t    finalize_deplibs=\"$dir/$old_library $finalize_deplibs\"\n\t  else\n\t    deplibs=\"$lib $deplibs\" # used for prog,scan pass\n\t  fi\n\t  continue\n\tfi\n\n\n\tif test prog = \"$linkmode\" && test link != \"$pass\"; then\n\t  func_append newlib_search_path \" $ladir\"\n\t  deplibs=\"$lib $deplibs\"\n\n\t  linkalldeplibs=false\n\t  if test no != \"$link_all_deplibs\" || test -z \"$library_names\" ||\n\t     test no = \"$build_libtool_libs\"; then\n\t    linkalldeplibs=:\n\t  fi\n\n\t  tmp_libs=\n\t  for deplib in $dependency_libs; do\n\t    case $deplib in\n\t    -L*) func_stripname '-L' '' \"$deplib\"\n\t         func_resolve_sysroot \"$func_stripname_result\"\n\t         func_append newlib_search_path \" $func_resolve_sysroot_result\"\n\t\t ;;\n\t    esac\n\t    # Need to link against all dependency_libs?\n\t    if $linkalldeplibs; then\n\t      deplibs=\"$deplib $deplibs\"\n\t    else\n\t      # Need to hardcode shared library paths\n\t      # or/and link against static libraries\n\t      newdependency_libs=\"$deplib $newdependency_libs\"\n\t    fi\n\t    if $opt_preserve_dup_deps; then\n\t      case \"$tmp_libs \" in\n\t      *\" $deplib \"*) func_append specialdeplibs \" $deplib\" ;;\n\t      esac\n\t    fi\n\t    func_append tmp_libs \" $deplib\"\n\t  done # for deplib\n\t  continue\n\tfi # $linkmode = prog...\n\n\tif test prog,link = \"$linkmode,$pass\"; then\n\t  if test -n \"$library_names\" &&\n\t     { { test no = \"$prefer_static_libs\" ||\n\t         test built,yes = \"$prefer_static_libs,$installed\"; } ||\n\t       test -z \"$old_library\"; }; then\n\t    # We need to hardcode the library path\n\t    if test -n \"$shlibpath_var\" && test -z \"$avoidtemprpath\"; then\n\t      # Make sure the rpath contains only unique directories.\n\t      case $temp_rpath: in\n\t      *\"$absdir:\"*) ;;\n\t      *) func_append temp_rpath \"$absdir:\" ;;\n\t      esac\n\t    fi\n\n\t    # Hardcode the library path.\n\t    # Skip directories that are in the system default run-time\n\t    # search path.\n\t    case \" $sys_lib_dlsearch_path \" in\n\t    *\" $absdir \"*) ;;\n\t    *)\n\t      case \"$compile_rpath \" in\n\t      *\" $absdir \"*) ;;\n\t      *) func_append compile_rpath \" $absdir\" ;;\n\t      esac\n\t      ;;\n\t    esac\n\t    case \" $sys_lib_dlsearch_path \" in\n\t    *\" $libdir \"*) ;;\n\t    *)\n\t      case \"$finalize_rpath \" in\n\t      *\" $libdir \"*) ;;\n\t      *) func_append finalize_rpath \" $libdir\" ;;\n\t      esac\n\t      ;;\n\t    esac\n\t  fi # $linkmode,$pass = prog,link...\n\n\t  if $alldeplibs &&\n\t     { test pass_all = \"$deplibs_check_method\" ||\n\t       { test yes = \"$build_libtool_libs\" &&\n\t\t test -n \"$library_names\"; }; }; then\n\t    # We only need to search for static libraries\n\t    continue\n\t  fi\n\tfi\n\n\tlink_static=no # Whether the deplib will be linked statically\n\tuse_static_libs=$prefer_static_libs\n\tif test built = \"$use_static_libs\" && test yes = \"$installed\"; then\n\t  use_static_libs=no\n\tfi\n\tif test -n \"$library_names\" &&\n\t   { test no = \"$use_static_libs\" || test -z \"$old_library\"; }; then\n\t  case $host in\n\t  *cygwin* | *mingw* | *cegcc* | *os2*)\n\t      # No point in relinking DLLs because paths are not encoded\n\t      func_append notinst_deplibs \" $lib\"\n\t      need_relink=no\n\t    ;;\n\t  *)\n\t    if test no = \"$installed\"; then\n\t      func_append notinst_deplibs \" $lib\"\n\t      need_relink=yes\n\t    fi\n\t    ;;\n\t  esac\n\t  # This is a shared library\n\n\t  # Warn about portability, can't link against -module's on some\n\t  # systems (darwin).  Don't bleat about dlopened modules though!\n\t  dlopenmodule=\n\t  for dlpremoduletest in $dlprefiles; do\n\t    if test \"X$dlpremoduletest\" = \"X$lib\"; then\n\t      dlopenmodule=$dlpremoduletest\n\t      break\n\t    fi\n\t  done\n\t  if test -z \"$dlopenmodule\" && test yes = \"$shouldnotlink\" && test link = \"$pass\"; then\n\t    echo\n\t    if test prog = \"$linkmode\"; then\n\t      $ECHO \"*** Warning: Linking the executable $output against the loadable module\"\n\t    else\n\t      $ECHO \"*** Warning: Linking the shared library $output against the loadable module\"\n\t    fi\n\t    $ECHO \"*** $linklib is not portable!\"\n\t  fi\n\t  if test lib = \"$linkmode\" &&\n\t     test yes = \"$hardcode_into_libs\"; then\n\t    # Hardcode the library path.\n\t    # Skip directories that are in the system default run-time\n\t    # search path.\n\t    case \" $sys_lib_dlsearch_path \" in\n\t    *\" $absdir \"*) ;;\n\t    *)\n\t      case \"$compile_rpath \" in\n\t      *\" $absdir \"*) ;;\n\t      *) func_append compile_rpath \" $absdir\" ;;\n\t      esac\n\t      ;;\n\t    esac\n\t    case \" $sys_lib_dlsearch_path \" in\n\t    *\" $libdir \"*) ;;\n\t    *)\n\t      case \"$finalize_rpath \" in\n\t      *\" $libdir \"*) ;;\n\t      *) func_append finalize_rpath \" $libdir\" ;;\n\t      esac\n\t      ;;\n\t    esac\n\t  fi\n\n\t  if test -n \"$old_archive_from_expsyms_cmds\"; then\n\t    # figure out the soname\n\t    set dummy $library_names\n\t    shift\n\t    realname=$1\n\t    shift\n\t    libname=`eval \"\\\\$ECHO \\\"$libname_spec\\\"\"`\n\t    # use dlname if we got it. it's perfectly good, no?\n\t    if test -n \"$dlname\"; then\n\t      soname=$dlname\n\t    elif test -n \"$soname_spec\"; then\n\t      # bleh windows\n\t      case $host in\n\t      *cygwin* | mingw* | *cegcc* | *os2*)\n\t        func_arith $current - $age\n\t\tmajor=$func_arith_result\n\t\tversuffix=-$major\n\t\t;;\n\t      esac\n\t      eval soname=\\\"$soname_spec\\\"\n\t    else\n\t      soname=$realname\n\t    fi\n\n\t    # Make a new name for the extract_expsyms_cmds to use\n\t    soroot=$soname\n\t    func_basename \"$soroot\"\n\t    soname=$func_basename_result\n\t    func_stripname 'lib' '.dll' \"$soname\"\n\t    newlib=libimp-$func_stripname_result.a\n\n\t    # If the library has no export list, then create one now\n\t    if test -f \"$output_objdir/$soname-def\"; then :\n\t    else\n\t      func_verbose \"extracting exported symbol list from '$soname'\"\n\t      func_execute_cmds \"$extract_expsyms_cmds\" 'exit $?'\n\t    fi\n\n\t    # Create $newlib\n\t    if test -f \"$output_objdir/$newlib\"; then :; else\n\t      func_verbose \"generating import library for '$soname'\"\n\t      func_execute_cmds \"$old_archive_from_expsyms_cmds\" 'exit $?'\n\t    fi\n\t    # make sure the library variables are pointing to the new library\n\t    dir=$output_objdir\n\t    linklib=$newlib\n\t  fi # test -n \"$old_archive_from_expsyms_cmds\"\n\n\t  if test prog = \"$linkmode\" || test relink != \"$opt_mode\"; then\n\t    add_shlibpath=\n\t    add_dir=\n\t    add=\n\t    lib_linked=yes\n\t    case $hardcode_action in\n\t    immediate | unsupported)\n\t      if test no = \"$hardcode_direct\"; then\n\t\tadd=$dir/$linklib\n\t\tcase $host in\n\t\t  *-*-sco3.2v5.0.[024]*) add_dir=-L$dir ;;\n\t\t  *-*-sysv4*uw2*) add_dir=-L$dir ;;\n\t\t  *-*-sysv5OpenUNIX* | *-*-sysv5UnixWare7.[01].[10]* | \\\n\t\t    *-*-unixware7*) add_dir=-L$dir ;;\n\t\t  *-*-darwin* )\n\t\t    # if the lib is a (non-dlopened) module then we cannot\n\t\t    # link against it, someone is ignoring the earlier warnings\n\t\t    if /usr/bin/file -L $add 2> /dev/null |\n\t\t\t $GREP \": [^:]* bundle\" >/dev/null; then\n\t\t      if test \"X$dlopenmodule\" != \"X$lib\"; then\n\t\t\t$ECHO \"*** Warning: lib $linklib is a module, not a shared library\"\n\t\t\tif test -z \"$old_library\"; then\n\t\t\t  echo\n\t\t\t  echo \"*** And there doesn't seem to be a static archive available\"\n\t\t\t  echo \"*** The link will probably fail, sorry\"\n\t\t\telse\n\t\t\t  add=$dir/$old_library\n\t\t\tfi\n\t\t      elif test -n \"$old_library\"; then\n\t\t\tadd=$dir/$old_library\n\t\t      fi\n\t\t    fi\n\t\tesac\n\t      elif test no = \"$hardcode_minus_L\"; then\n\t\tcase $host in\n\t\t*-*-sunos*) add_shlibpath=$dir ;;\n\t\tesac\n\t\tadd_dir=-L$dir\n\t\tadd=-l$name\n\t      elif test no = \"$hardcode_shlibpath_var\"; then\n\t\tadd_shlibpath=$dir\n\t\tadd=-l$name\n\t      else\n\t\tlib_linked=no\n\t      fi\n\t      ;;\n\t    relink)\n\t      if test yes = \"$hardcode_direct\" &&\n\t         test no = \"$hardcode_direct_absolute\"; then\n\t\tadd=$dir/$linklib\n\t      elif test yes = \"$hardcode_minus_L\"; then\n\t\tadd_dir=-L$absdir\n\t\t# Try looking first in the location we're being installed to.\n\t\tif test -n \"$inst_prefix_dir\"; then\n\t\t  case $libdir in\n\t\t    [\\\\/]*)\n\t\t      func_append add_dir \" -L$inst_prefix_dir$libdir\"\n\t\t      ;;\n\t\t  esac\n\t\tfi\n\t\tadd=-l$name\n\t      elif test yes = \"$hardcode_shlibpath_var\"; then\n\t\tadd_shlibpath=$dir\n\t\tadd=-l$name\n\t      else\n\t\tlib_linked=no\n\t      fi\n\t      ;;\n\t    *) lib_linked=no ;;\n\t    esac\n\n\t    if test yes != \"$lib_linked\"; then\n\t      func_fatal_configuration \"unsupported hardcode properties\"\n\t    fi\n\n\t    if test -n \"$add_shlibpath\"; then\n\t      case :$compile_shlibpath: in\n\t      *\":$add_shlibpath:\"*) ;;\n\t      *) func_append compile_shlibpath \"$add_shlibpath:\" ;;\n\t      esac\n\t    fi\n\t    if test prog = \"$linkmode\"; then\n\t      test -n \"$add_dir\" && compile_deplibs=\"$add_dir $compile_deplibs\"\n\t      test -n \"$add\" && compile_deplibs=\"$add $compile_deplibs\"\n\t    else\n\t      test -n \"$add_dir\" && deplibs=\"$add_dir $deplibs\"\n\t      test -n \"$add\" && deplibs=\"$add $deplibs\"\n\t      if test yes != \"$hardcode_direct\" &&\n\t\t test yes != \"$hardcode_minus_L\" &&\n\t\t test yes = \"$hardcode_shlibpath_var\"; then\n\t\tcase :$finalize_shlibpath: in\n\t\t*\":$libdir:\"*) ;;\n\t\t*) func_append finalize_shlibpath \"$libdir:\" ;;\n\t\tesac\n\t      fi\n\t    fi\n\t  fi\n\n\t  if test prog = \"$linkmode\" || test relink = \"$opt_mode\"; then\n\t    add_shlibpath=\n\t    add_dir=\n\t    add=\n\t    # Finalize command for both is simple: just hardcode it.\n\t    if test yes = \"$hardcode_direct\" &&\n\t       test no = \"$hardcode_direct_absolute\"; then\n\t      add=$libdir/$linklib\n\t    elif test yes = \"$hardcode_minus_L\"; then\n\t      add_dir=-L$libdir\n\t      add=-l$name\n\t    elif test yes = \"$hardcode_shlibpath_var\"; then\n\t      case :$finalize_shlibpath: in\n\t      *\":$libdir:\"*) ;;\n\t      *) func_append finalize_shlibpath \"$libdir:\" ;;\n\t      esac\n\t      add=-l$name\n\t    elif test yes = \"$hardcode_automatic\"; then\n\t      if test -n \"$inst_prefix_dir\" &&\n\t\t test -f \"$inst_prefix_dir$libdir/$linklib\"; then\n\t\tadd=$inst_prefix_dir$libdir/$linklib\n\t      else\n\t\tadd=$libdir/$linklib\n\t      fi\n\t    else\n\t      # We cannot seem to hardcode it, guess we'll fake it.\n\t      add_dir=-L$libdir\n\t      # Try looking first in the location we're being installed to.\n\t      if test -n \"$inst_prefix_dir\"; then\n\t\tcase $libdir in\n\t\t  [\\\\/]*)\n\t\t    func_append add_dir \" -L$inst_prefix_dir$libdir\"\n\t\t    ;;\n\t\tesac\n\t      fi\n\t      add=-l$name\n\t    fi\n\n\t    if test prog = \"$linkmode\"; then\n\t      test -n \"$add_dir\" && finalize_deplibs=\"$add_dir $finalize_deplibs\"\n\t      test -n \"$add\" && finalize_deplibs=\"$add $finalize_deplibs\"\n\t    else\n\t      test -n \"$add_dir\" && deplibs=\"$add_dir $deplibs\"\n\t      test -n \"$add\" && deplibs=\"$add $deplibs\"\n\t    fi\n\t  fi\n\telif test prog = \"$linkmode\"; then\n\t  # Here we assume that one of hardcode_direct or hardcode_minus_L\n\t  # is not unsupported.  This is valid on all known static and\n\t  # shared platforms.\n\t  if test unsupported != \"$hardcode_direct\"; then\n\t    test -n \"$old_library\" && linklib=$old_library\n\t    compile_deplibs=\"$dir/$linklib $compile_deplibs\"\n\t    finalize_deplibs=\"$dir/$linklib $finalize_deplibs\"\n\t  else\n\t    compile_deplibs=\"-l$name -L$dir $compile_deplibs\"\n\t    finalize_deplibs=\"-l$name -L$dir $finalize_deplibs\"\n\t  fi\n\telif test yes = \"$build_libtool_libs\"; then\n\t  # Not a shared library\n\t  if test pass_all != \"$deplibs_check_method\"; then\n\t    # We're trying link a shared library against a static one\n\t    # but the system doesn't support it.\n\n\t    # Just print a warning and add the library to dependency_libs so\n\t    # that the program can be linked against the static library.\n\t    echo\n\t    $ECHO \"*** Warning: This system cannot link to static lib archive $lib.\"\n\t    echo \"*** I have the capability to make that library automatically link in when\"\n\t    echo \"*** you link to this library.  But I can only do this if you have a\"\n\t    echo \"*** shared version of the library, which you do not appear to have.\"\n\t    if test yes = \"$module\"; then\n\t      echo \"*** But as you try to build a module library, libtool will still create \"\n\t      echo \"*** a static module, that should work as long as the dlopening application\"\n\t      echo \"*** is linked with the -dlopen flag to resolve symbols at runtime.\"\n\t      if test -z \"$global_symbol_pipe\"; then\n\t\techo\n\t\techo \"*** However, this would only work if libtool was able to extract symbol\"\n\t\techo \"*** lists from a program, using 'nm' or equivalent, but libtool could\"\n\t\techo \"*** not find such a program.  So, this module is probably useless.\"\n\t\techo \"*** 'nm' from GNU binutils and a full rebuild may help.\"\n\t      fi\n\t      if test no = \"$build_old_libs\"; then\n\t\tbuild_libtool_libs=module\n\t\tbuild_old_libs=yes\n\t      else\n\t\tbuild_libtool_libs=no\n\t      fi\n\t    fi\n\t  else\n\t    deplibs=\"$dir/$old_library $deplibs\"\n\t    link_static=yes\n\t  fi\n\tfi # link shared/static library?\n\n\tif test lib = \"$linkmode\"; then\n\t  if test -n \"$dependency_libs\" &&\n\t     { test yes != \"$hardcode_into_libs\" ||\n\t       test yes = \"$build_old_libs\" ||\n\t       test yes = \"$link_static\"; }; then\n\t    # Extract -R from dependency_libs\n\t    temp_deplibs=\n\t    for libdir in $dependency_libs; do\n\t      case $libdir in\n\t      -R*) func_stripname '-R' '' \"$libdir\"\n\t           temp_xrpath=$func_stripname_result\n\t\t   case \" $xrpath \" in\n\t\t   *\" $temp_xrpath \"*) ;;\n\t\t   *) func_append xrpath \" $temp_xrpath\";;\n\t\t   esac;;\n\t      *) func_append temp_deplibs \" $libdir\";;\n\t      esac\n\t    done\n\t    dependency_libs=$temp_deplibs\n\t  fi\n\n\t  func_append newlib_search_path \" $absdir\"\n\t  # Link against this library\n\t  test no = \"$link_static\" && newdependency_libs=\"$abs_ladir/$laname $newdependency_libs\"\n\t  # ... and its dependency_libs\n\t  tmp_libs=\n\t  for deplib in $dependency_libs; do\n\t    newdependency_libs=\"$deplib $newdependency_libs\"\n\t    case $deplib in\n              -L*) func_stripname '-L' '' \"$deplib\"\n                   func_resolve_sysroot \"$func_stripname_result\";;\n              *) func_resolve_sysroot \"$deplib\" ;;\n            esac\n\t    if $opt_preserve_dup_deps; then\n\t      case \"$tmp_libs \" in\n\t      *\" $func_resolve_sysroot_result \"*)\n                func_append specialdeplibs \" $func_resolve_sysroot_result\" ;;\n\t      esac\n\t    fi\n\t    func_append tmp_libs \" $func_resolve_sysroot_result\"\n\t  done\n\n\t  if test no != \"$link_all_deplibs\"; then\n\t    # Add the search paths of all dependency libraries\n\t    for deplib in $dependency_libs; do\n\t      path=\n\t      case $deplib in\n\t      -L*) path=$deplib ;;\n\t      *.la)\n\t        func_resolve_sysroot \"$deplib\"\n\t        deplib=$func_resolve_sysroot_result\n\t        func_dirname \"$deplib\" \"\" \".\"\n\t\tdir=$func_dirname_result\n\t\t# We need an absolute path.\n\t\tcase $dir in\n\t\t[\\\\/]* | [A-Za-z]:[\\\\/]*) absdir=$dir ;;\n\t\t*)\n\t\t  absdir=`cd \"$dir\" && pwd`\n\t\t  if test -z \"$absdir\"; then\n\t\t    func_warning \"cannot determine absolute directory name of '$dir'\"\n\t\t    absdir=$dir\n\t\t  fi\n\t\t  ;;\n\t\tesac\n\t\tif $GREP \"^installed=no\" $deplib > /dev/null; then\n\t\tcase $host in\n\t\t*-*-darwin*)\n\t\t  depdepl=\n\t\t  eval deplibrary_names=`$SED -n -e 's/^library_names=\\(.*\\)$/\\1/p' $deplib`\n\t\t  if test -n \"$deplibrary_names\"; then\n\t\t    for tmp in $deplibrary_names; do\n\t\t      depdepl=$tmp\n\t\t    done\n\t\t    if test -f \"$absdir/$objdir/$depdepl\"; then\n\t\t      depdepl=$absdir/$objdir/$depdepl\n\t\t      darwin_install_name=`$OTOOL -L $depdepl | awk '{if (NR == 2) {print $1;exit}}'`\n                      if test -z \"$darwin_install_name\"; then\n                          darwin_install_name=`$OTOOL64 -L $depdepl  | awk '{if (NR == 2) {print $1;exit}}'`\n                      fi\n\t\t      func_append compiler_flags \" $wl-dylib_file $wl$darwin_install_name:$depdepl\"\n\t\t      func_append linker_flags \" -dylib_file $darwin_install_name:$depdepl\"\n\t\t      path=\n\t\t    fi\n\t\t  fi\n\t\t  ;;\n\t\t*)\n\t\t  path=-L$absdir/$objdir\n\t\t  ;;\n\t\tesac\n\t\telse\n\t\t  eval libdir=`$SED -n -e 's/^libdir=\\(.*\\)$/\\1/p' $deplib`\n\t\t  test -z \"$libdir\" && \\\n\t\t    func_fatal_error \"'$deplib' is not a valid libtool archive\"\n\t\t  test \"$absdir\" != \"$libdir\" && \\\n\t\t    func_warning \"'$deplib' seems to be moved\"\n\n\t\t  path=-L$absdir\n\t\tfi\n\t\t;;\n\t      esac\n\t      case \" $deplibs \" in\n\t      *\" $path \"*) ;;\n\t      *) deplibs=\"$path $deplibs\" ;;\n\t      esac\n\t    done\n\t  fi # link_all_deplibs != no\n\tfi # linkmode = lib\n      done # for deplib in $libs\n      if test link = \"$pass\"; then\n\tif test prog = \"$linkmode\"; then\n\t  compile_deplibs=\"$new_inherited_linker_flags $compile_deplibs\"\n\t  finalize_deplibs=\"$new_inherited_linker_flags $finalize_deplibs\"\n\telse\n\t  compiler_flags=\"$compiler_flags \"`$ECHO \" $new_inherited_linker_flags\" | $SED 's% \\([^ $]*\\).ltframework% -framework \\1%g'`\n\tfi\n      fi\n      dependency_libs=$newdependency_libs\n      if test dlpreopen = \"$pass\"; then\n\t# Link the dlpreopened libraries before other libraries\n\tfor deplib in $save_deplibs; do\n\t  deplibs=\"$deplib $deplibs\"\n\tdone\n      fi\n      if test dlopen != \"$pass\"; then\n\ttest conv = \"$pass\" || {\n\t  # Make sure lib_search_path contains only unique directories.\n\t  lib_search_path=\n\t  for dir in $newlib_search_path; do\n\t    case \"$lib_search_path \" in\n\t    *\" $dir \"*) ;;\n\t    *) func_append lib_search_path \" $dir\" ;;\n\t    esac\n\t  done\n\t  newlib_search_path=\n\t}\n\n\tif test prog,link = \"$linkmode,$pass\"; then\n\t  vars=\"compile_deplibs finalize_deplibs\"\n\telse\n\t  vars=deplibs\n\tfi\n\tfor var in $vars dependency_libs; do\n\t  # Add libraries to $var in reverse order\n\t  eval tmp_libs=\\\"\\$$var\\\"\n\t  new_libs=\n\t  for deplib in $tmp_libs; do\n\t    # FIXME: Pedantically, this is the right thing to do, so\n\t    #        that some nasty dependency loop isn't accidentally\n\t    #        broken:\n\t    #new_libs=\"$deplib $new_libs\"\n\t    # Pragmatically, this seems to cause very few problems in\n\t    # practice:\n\t    case $deplib in\n\t    -L*) new_libs=\"$deplib $new_libs\" ;;\n\t    -R*) ;;\n\t    *)\n\t      # And here is the reason: when a library appears more\n\t      # than once as an explicit dependence of a library, or\n\t      # is implicitly linked in more than once by the\n\t      # compiler, it is considered special, and multiple\n\t      # occurrences thereof are not removed.  Compare this\n\t      # with having the same library being listed as a\n\t      # dependency of multiple other libraries: in this case,\n\t      # we know (pedantically, we assume) the library does not\n\t      # need to be listed more than once, so we keep only the\n\t      # last copy.  This is not always right, but it is rare\n\t      # enough that we require users that really mean to play\n\t      # such unportable linking tricks to link the library\n\t      # using -Wl,-lname, so that libtool does not consider it\n\t      # for duplicate removal.\n\t      case \" $specialdeplibs \" in\n\t      *\" $deplib \"*) new_libs=\"$deplib $new_libs\" ;;\n\t      *)\n\t\tcase \" $new_libs \" in\n\t\t*\" $deplib \"*) ;;\n\t\t*) new_libs=\"$deplib $new_libs\" ;;\n\t\tesac\n\t\t;;\n\t      esac\n\t      ;;\n\t    esac\n\t  done\n\t  tmp_libs=\n\t  for deplib in $new_libs; do\n\t    case $deplib in\n\t    -L*)\n\t      case \" $tmp_libs \" in\n\t      *\" $deplib \"*) ;;\n\t      *) func_append tmp_libs \" $deplib\" ;;\n\t      esac\n\t      ;;\n\t    *) func_append tmp_libs \" $deplib\" ;;\n\t    esac\n\t  done\n\t  eval $var=\\\"$tmp_libs\\\"\n\tdone # for var\n      fi\n\n      # Add Sun CC postdeps if required:\n      test CXX = \"$tagname\" && {\n        case $host_os in\n        linux*)\n          case `$CC -V 2>&1 | $SED 5q` in\n          *Sun\\ C*) # Sun C++ 5.9\n            func_suncc_cstd_abi\n\n            if test no != \"$suncc_use_cstd_abi\"; then\n              func_append postdeps ' -library=Cstd -library=Crun'\n            fi\n            ;;\n          esac\n          ;;\n\n        solaris*)\n          func_cc_basename \"$CC\"\n          case $func_cc_basename_result in\n          CC* | sunCC*)\n            func_suncc_cstd_abi\n\n            if test no != \"$suncc_use_cstd_abi\"; then\n              func_append postdeps ' -library=Cstd -library=Crun'\n            fi\n            ;;\n          esac\n          ;;\n        esac\n      }\n\n      # Last step: remove runtime libs from dependency_libs\n      # (they stay in deplibs)\n      tmp_libs=\n      for i in $dependency_libs; do\n\tcase \" $predeps $postdeps $compiler_lib_search_path \" in\n\t*\" $i \"*)\n\t  i=\n\t  ;;\n\tesac\n\tif test -n \"$i\"; then\n\t  func_append tmp_libs \" $i\"\n\tfi\n      done\n      dependency_libs=$tmp_libs\n    done # for pass\n    if test prog = \"$linkmode\"; then\n      dlfiles=$newdlfiles\n    fi\n    if test prog = \"$linkmode\" || test lib = \"$linkmode\"; then\n      dlprefiles=$newdlprefiles\n    fi\n\n    case $linkmode in\n    oldlib)\n      if test -n \"$dlfiles$dlprefiles\" || test no != \"$dlself\"; then\n\tfunc_warning \"'-dlopen' is ignored for archives\"\n      fi\n\n      case \" $deplibs\" in\n      *\\ -l* | *\\ -L*)\n\tfunc_warning \"'-l' and '-L' are ignored for archives\" ;;\n      esac\n\n      test -n \"$rpath\" && \\\n\tfunc_warning \"'-rpath' is ignored for archives\"\n\n      test -n \"$xrpath\" && \\\n\tfunc_warning \"'-R' is ignored for archives\"\n\n      test -n \"$vinfo\" && \\\n\tfunc_warning \"'-version-info/-version-number' is ignored for archives\"\n\n      test -n \"$release\" && \\\n\tfunc_warning \"'-release' is ignored for archives\"\n\n      test -n \"$export_symbols$export_symbols_regex\" && \\\n\tfunc_warning \"'-export-symbols' is ignored for archives\"\n\n      # Now set the variables for building old libraries.\n      build_libtool_libs=no\n      oldlibs=$output\n      func_append objs \"$old_deplibs\"\n      ;;\n\n    lib)\n      # Make sure we only generate libraries of the form 'libNAME.la'.\n      case $outputname in\n      lib*)\n\tfunc_stripname 'lib' '.la' \"$outputname\"\n\tname=$func_stripname_result\n\teval shared_ext=\\\"$shrext_cmds\\\"\n\teval libname=\\\"$libname_spec\\\"\n\t;;\n      *)\n\ttest no = \"$module\" \\\n\t  && func_fatal_help \"libtool library '$output' must begin with 'lib'\"\n\n\tif test no != \"$need_lib_prefix\"; then\n\t  # Add the \"lib\" prefix for modules if required\n\t  func_stripname '' '.la' \"$outputname\"\n\t  name=$func_stripname_result\n\t  eval shared_ext=\\\"$shrext_cmds\\\"\n\t  eval libname=\\\"$libname_spec\\\"\n\telse\n\t  func_stripname '' '.la' \"$outputname\"\n\t  libname=$func_stripname_result\n\tfi\n\t;;\n      esac\n\n      if test -n \"$objs\"; then\n\tif test pass_all != \"$deplibs_check_method\"; then\n\t  func_fatal_error \"cannot build libtool library '$output' from non-libtool objects on this host:$objs\"\n\telse\n\t  echo\n\t  $ECHO \"*** Warning: Linking the shared library $output against the non-libtool\"\n\t  $ECHO \"*** objects $objs is not portable!\"\n\t  func_append libobjs \" $objs\"\n\tfi\n      fi\n\n      test no = \"$dlself\" \\\n\t|| func_warning \"'-dlopen self' is ignored for libtool libraries\"\n\n      set dummy $rpath\n      shift\n      test 1 -lt \"$#\" \\\n\t&& func_warning \"ignoring multiple '-rpath's for a libtool library\"\n\n      install_libdir=$1\n\n      oldlibs=\n      if test -z \"$rpath\"; then\n\tif test yes = \"$build_libtool_libs\"; then\n\t  # Building a libtool convenience library.\n\t  # Some compilers have problems with a '.al' extension so\n\t  # convenience libraries should have the same extension an\n\t  # archive normally would.\n\t  oldlibs=\"$output_objdir/$libname.$libext $oldlibs\"\n\t  build_libtool_libs=convenience\n\t  build_old_libs=yes\n\tfi\n\n\ttest -n \"$vinfo\" && \\\n\t  func_warning \"'-version-info/-version-number' is ignored for convenience libraries\"\n\n\ttest -n \"$release\" && \\\n\t  func_warning \"'-release' is ignored for convenience libraries\"\n      else\n\n\t# Parse the version information argument.\n\tsave_ifs=$IFS; IFS=:\n\tset dummy $vinfo 0 0 0\n\tshift\n\tIFS=$save_ifs\n\n\ttest -n \"$7\" && \\\n\t  func_fatal_help \"too many parameters to '-version-info'\"\n\n\t# convert absolute version numbers to libtool ages\n\t# this retains compatibility with .la files and attempts\n\t# to make the code below a bit more comprehensible\n\n\tcase $vinfo_number in\n\tyes)\n\t  number_major=$1\n\t  number_minor=$2\n\t  number_revision=$3\n\t  #\n\t  # There are really only two kinds -- those that\n\t  # use the current revision as the major version\n\t  # and those that subtract age and use age as\n\t  # a minor version.  But, then there is irix\n\t  # that has an extra 1 added just for fun\n\t  #\n\t  case $version_type in\n\t  # correct linux to gnu/linux during the next big refactor\n\t  darwin|freebsd-elf|linux|midnightbsd-elf|osf|windows|none)\n\t    func_arith $number_major + $number_minor\n\t    current=$func_arith_result\n\t    age=$number_minor\n\t    revision=$number_revision\n\t    ;;\n\t  freebsd-aout|qnx|sunos)\n\t    current=$number_major\n\t    revision=$number_minor\n\t    age=0\n\t    ;;\n\t  irix|nonstopux)\n\t    func_arith $number_major + $number_minor\n\t    current=$func_arith_result\n\t    age=$number_minor\n\t    revision=$number_minor\n\t    lt_irix_increment=no\n\t    ;;\n\t  esac\n\t  ;;\n\tno)\n\t  current=$1\n\t  revision=$2\n\t  age=$3\n\t  ;;\n\tesac\n\n\t# Check that each of the things are valid numbers.\n\tcase $current in\n\t0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;;\n\t*)\n\t  func_error \"CURRENT '$current' must be a nonnegative integer\"\n\t  func_fatal_error \"'$vinfo' is not valid version information\"\n\t  ;;\n\tesac\n\n\tcase $revision in\n\t0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;;\n\t*)\n\t  func_error \"REVISION '$revision' must be a nonnegative integer\"\n\t  func_fatal_error \"'$vinfo' is not valid version information\"\n\t  ;;\n\tesac\n\n\tcase $age in\n\t0|[1-9]|[1-9][0-9]|[1-9][0-9][0-9]|[1-9][0-9][0-9][0-9]|[1-9][0-9][0-9][0-9][0-9]) ;;\n\t*)\n\t  func_error \"AGE '$age' must be a nonnegative integer\"\n\t  func_fatal_error \"'$vinfo' is not valid version information\"\n\t  ;;\n\tesac\n\n\tif test \"$age\" -gt \"$current\"; then\n\t  func_error \"AGE '$age' is greater than the current interface number '$current'\"\n\t  func_fatal_error \"'$vinfo' is not valid version information\"\n\tfi\n\n\t# Calculate the version variables.\n\tmajor=\n\tversuffix=\n\tverstring=\n\tcase $version_type in\n\tnone) ;;\n\n\tdarwin)\n\t  # Like Linux, but with the current version available in\n\t  # verstring for coding it into the library header\n\t  func_arith $current - $age\n\t  major=.$func_arith_result\n\t  versuffix=$major.$age.$revision\n\t  # Darwin ld doesn't like 0 for these options...\n\t  func_arith $current + 1\n\t  minor_current=$func_arith_result\n\t  xlcverstring=\"$wl-compatibility_version $wl$minor_current $wl-current_version $wl$minor_current.$revision\"\n\t  verstring=\"-compatibility_version $minor_current -current_version $minor_current.$revision\"\n          # On Darwin other compilers\n          case $CC in\n              nagfor*)\n                  verstring=\"$wl-compatibility_version $wl$minor_current $wl-current_version $wl$minor_current.$revision\"\n                  ;;\n              *)\n                  verstring=\"-compatibility_version $minor_current -current_version $minor_current.$revision\"\n                  ;;\n          esac\n\t  ;;\n\n\tfreebsd-aout)\n\t  major=.$current\n\t  versuffix=.$current.$revision\n\t  ;;\n\n\tfreebsd-elf | midnightbsd-elf)\n\t  func_arith $current - $age\n\t  major=.$func_arith_result\n\t  versuffix=$major.$age.$revision\n\t  ;;\n\n\tirix | nonstopux)\n\t  if test no = \"$lt_irix_increment\"; then\n\t    func_arith $current - $age\n\t  else\n\t    func_arith $current - $age + 1\n\t  fi\n\t  major=$func_arith_result\n\n\t  case $version_type in\n\t    nonstopux) verstring_prefix=nonstopux ;;\n\t    *)         verstring_prefix=sgi ;;\n\t  esac\n\t  verstring=$verstring_prefix$major.$revision\n\n\t  # Add in all the interfaces that we are compatible with.\n\t  loop=$revision\n\t  while test 0 -ne \"$loop\"; do\n\t    func_arith $revision - $loop\n\t    iface=$func_arith_result\n\t    func_arith $loop - 1\n\t    loop=$func_arith_result\n\t    verstring=$verstring_prefix$major.$iface:$verstring\n\t  done\n\n\t  # Before this point, $major must not contain '.'.\n\t  major=.$major\n\t  versuffix=$major.$revision\n\t  ;;\n\n\tlinux) # correct to gnu/linux during the next big refactor\n\t  func_arith $current - $age\n\t  major=.$func_arith_result\n\t  versuffix=$major.$age.$revision\n\t  ;;\n\n\tosf)\n\t  func_arith $current - $age\n\t  major=.$func_arith_result\n\t  versuffix=.$current.$age.$revision\n\t  verstring=$current.$age.$revision\n\n\t  # Add in all the interfaces that we are compatible with.\n\t  loop=$age\n\t  while test 0 -ne \"$loop\"; do\n\t    func_arith $current - $loop\n\t    iface=$func_arith_result\n\t    func_arith $loop - 1\n\t    loop=$func_arith_result\n\t    verstring=$verstring:$iface.0\n\t  done\n\n\t  # Make executables depend on our current version.\n\t  func_append verstring \":$current.0\"\n\t  ;;\n\n\tqnx)\n\t  major=.$current\n\t  versuffix=.$current\n\t  ;;\n\n\tsco)\n\t  major=.$current\n\t  versuffix=.$current\n\t  ;;\n\n\tsunos)\n\t  major=.$current\n\t  versuffix=.$current.$revision\n\t  ;;\n\n\twindows)\n\t  # Use '-' rather than '.', since we only want one\n\t  # extension on DOS 8.3 file systems.\n\t  func_arith $current - $age\n\t  major=$func_arith_result\n\t  versuffix=-$major\n\t  ;;\n\n\t*)\n\t  func_fatal_configuration \"unknown library version type '$version_type'\"\n\t  ;;\n\tesac\n\n\t# Clear the version info if we defaulted, and they specified a release.\n\tif test -z \"$vinfo\" && test -n \"$release\"; then\n\t  major=\n\t  case $version_type in\n\t  darwin)\n\t    # we can't check for \"0.0\" in archive_cmds due to quoting\n\t    # problems, so we reset it completely\n\t    verstring=\n\t    ;;\n\t  *)\n\t    verstring=0.0\n\t    ;;\n\t  esac\n\t  if test no = \"$need_version\"; then\n\t    versuffix=\n\t  else\n\t    versuffix=.0.0\n\t  fi\n\tfi\n\n\t# Remove version info from name if versioning should be avoided\n\tif test yes,no = \"$avoid_version,$need_version\"; then\n\t  major=\n\t  versuffix=\n\t  verstring=\n\tfi\n\n\t# Check to see if the archive will have undefined symbols.\n\tif test yes = \"$allow_undefined\"; then\n\t  if test unsupported = \"$allow_undefined_flag\"; then\n\t    if test yes = \"$build_old_libs\"; then\n\t      func_warning \"undefined symbols not allowed in $host shared libraries; building static only\"\n\t      build_libtool_libs=no\n\t    else\n\t      func_fatal_error \"can't build $host shared library unless -no-undefined is specified\"\n\t    fi\n\t  fi\n\telse\n\t  # Don't allow undefined symbols.\n\t  allow_undefined_flag=$no_undefined_flag\n\tfi\n\n      fi\n\n      func_generate_dlsyms \"$libname\" \"$libname\" :\n      func_append libobjs \" $symfileobj\"\n      test \" \" = \"$libobjs\" && libobjs=\n\n      if test relink != \"$opt_mode\"; then\n\t# Remove our outputs, but don't remove object files since they\n\t# may have been created when compiling PIC objects.\n\tremovelist=\n\ttempremovelist=`$ECHO \"$output_objdir/*\"`\n\tfor p in $tempremovelist; do\n\t  case $p in\n\t    *.$objext | *.gcno)\n\t       ;;\n\t    $output_objdir/$outputname | $output_objdir/$libname.* | $output_objdir/$libname$release.*)\n\t       if test -n \"$precious_files_regex\"; then\n\t\t if $ECHO \"$p\" | $EGREP -e \"$precious_files_regex\" >/dev/null 2>&1\n\t\t then\n\t\t   continue\n\t\t fi\n\t       fi\n\t       func_append removelist \" $p\"\n\t       ;;\n\t    *) ;;\n\t  esac\n\tdone\n\ttest -n \"$removelist\" && \\\n\t  func_show_eval \"${RM}r \\$removelist\"\n      fi\n\n      # Now set the variables for building old libraries.\n      if test yes = \"$build_old_libs\" && test convenience != \"$build_libtool_libs\"; then\n\tfunc_append oldlibs \" $output_objdir/$libname.$libext\"\n\n\t# Transform .lo files to .o files.\n\toldobjs=\"$objs \"`$ECHO \"$libobjs\" | $SP2NL | $SED \"/\\.$libext$/d; $lo2o\" | $NL2SP`\n      fi\n\n      # Eliminate all temporary directories.\n      #for path in $notinst_path; do\n      #\tlib_search_path=`$ECHO \"$lib_search_path \" | $SED \"s% $path % %g\"`\n      #\tdeplibs=`$ECHO \"$deplibs \" | $SED \"s% -L$path % %g\"`\n      #\tdependency_libs=`$ECHO \"$dependency_libs \" | $SED \"s% -L$path % %g\"`\n      #done\n\n      if test -n \"$xrpath\"; then\n\t# If the user specified any rpath flags, then add them.\n\ttemp_xrpath=\n\tfor libdir in $xrpath; do\n\t  func_replace_sysroot \"$libdir\"\n\t  func_append temp_xrpath \" -R$func_replace_sysroot_result\"\n\t  case \"$finalize_rpath \" in\n\t  *\" $libdir \"*) ;;\n\t  *) func_append finalize_rpath \" $libdir\" ;;\n\t  esac\n\tdone\n\tif test yes != \"$hardcode_into_libs\" || test yes = \"$build_old_libs\"; then\n\t  dependency_libs=\"$temp_xrpath $dependency_libs\"\n\tfi\n      fi\n\n      # Make sure dlfiles contains only unique files that won't be dlpreopened\n      old_dlfiles=$dlfiles\n      dlfiles=\n      for lib in $old_dlfiles; do\n\tcase \" $dlprefiles $dlfiles \" in\n\t*\" $lib \"*) ;;\n\t*) func_append dlfiles \" $lib\" ;;\n\tesac\n      done\n\n      # Make sure dlprefiles contains only unique files\n      old_dlprefiles=$dlprefiles\n      dlprefiles=\n      for lib in $old_dlprefiles; do\n\tcase \"$dlprefiles \" in\n\t*\" $lib \"*) ;;\n\t*) func_append dlprefiles \" $lib\" ;;\n\tesac\n      done\n\n      if test yes = \"$build_libtool_libs\"; then\n\tif test -n \"$rpath\"; then\n\t  case $host in\n\t  *-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-*-beos* | *-cegcc* | *-*-haiku*)\n\t    # these systems don't actually have a c library (as such)!\n\t    ;;\n\t  *-*-rhapsody* | *-*-darwin1.[012])\n\t    # Rhapsody C library is in the System framework\n\t    func_append deplibs \" System.ltframework\"\n\t    ;;\n\t  *-*-netbsd*)\n\t    # Don't link with libc until the a.out ld.so is fixed.\n\t    ;;\n\t  *-*-openbsd* | *-*-freebsd* | *-*-dragonfly* | *-*-midnightbsd*)\n\t    # Do not include libc due to us having libc/libc_r.\n\t    ;;\n\t  *-*-sco3.2v5* | *-*-sco5v6*)\n\t    # Causes problems with __ctype\n\t    ;;\n\t  *-*-sysv4.2uw2* | *-*-sysv5* | *-*-unixware* | *-*-OpenUNIX*)\n\t    # Compiler inserts libc in the correct place for threads to work\n\t    ;;\n\t  *)\n\t    # Add libc to deplibs on all other systems if necessary.\n\t    if test yes = \"$build_libtool_need_lc\"; then\n\t      func_append deplibs \" -lc\"\n\t    fi\n\t    ;;\n\t  esac\n\tfi\n\n\t# Transform deplibs into only deplibs that can be linked in shared.\n\tname_save=$name\n\tlibname_save=$libname\n\trelease_save=$release\n\tversuffix_save=$versuffix\n\tmajor_save=$major\n\t# I'm not sure if I'm treating the release correctly.  I think\n\t# release should show up in the -l (ie -lgmp5) so we don't want to\n\t# add it in twice.  Is that correct?\n\trelease=\n\tversuffix=\n\tmajor=\n\tnewdeplibs=\n\tdroppeddeps=no\n\tcase $deplibs_check_method in\n\tpass_all)\n\t  # Don't check for shared/static.  Everything works.\n\t  # This might be a little naive.  We might want to check\n\t  # whether the library exists or not.  But this is on\n\t  # osf3 & osf4 and I'm not really sure... Just\n\t  # implementing what was already the behavior.\n\t  newdeplibs=$deplibs\n\t  ;;\n\ttest_compile)\n\t  # This code stresses the \"libraries are programs\" paradigm to its\n\t  # limits. Maybe even breaks it.  We compile a program, linking it\n\t  # against the deplibs as a proxy for the library.  Then we can check\n\t  # whether they linked in statically or dynamically with ldd.\n\t  $opt_dry_run || $RM conftest.c\n\t  cat > conftest.c <<EOF\n\t  int main() { return 0; }\nEOF\n\t  $opt_dry_run || $RM conftest\n\t  if $LTCC $LTCFLAGS -o conftest conftest.c $deplibs; then\n\t    ldd_output=`ldd conftest`\n\t    for i in $deplibs; do\n\t      case $i in\n\t      -l*)\n\t\tfunc_stripname -l '' \"$i\"\n\t\tname=$func_stripname_result\n\t\tif test yes = \"$allow_libtool_libs_with_static_runtimes\"; then\n\t\t  case \" $predeps $postdeps \" in\n\t\t  *\" $i \"*)\n\t\t    func_append newdeplibs \" $i\"\n\t\t    i=\n\t\t    ;;\n\t\t  esac\n\t\tfi\n\t\tif test -n \"$i\"; then\n\t\t  libname=`eval \"\\\\$ECHO \\\"$libname_spec\\\"\"`\n\t\t  deplib_matches=`eval \"\\\\$ECHO \\\"$library_names_spec\\\"\"`\n\t\t  set dummy $deplib_matches; shift\n\t\t  deplib_match=$1\n\t\t  if test `expr \"$ldd_output\" : \".*$deplib_match\"` -ne 0; then\n\t\t    func_append newdeplibs \" $i\"\n\t\t  else\n\t\t    droppeddeps=yes\n\t\t    echo\n\t\t    $ECHO \"*** Warning: dynamic linker does not accept needed library $i.\"\n\t\t    echo \"*** I have the capability to make that library automatically link in when\"\n\t\t    echo \"*** you link to this library.  But I can only do this if you have a\"\n\t\t    echo \"*** shared version of the library, which I believe you do not have\"\n\t\t    echo \"*** because a test_compile did reveal that the linker did not use it for\"\n\t\t    echo \"*** its dynamic dependency list that programs get resolved with at runtime.\"\n\t\t  fi\n\t\tfi\n\t\t;;\n\t      *)\n\t\tfunc_append newdeplibs \" $i\"\n\t\t;;\n\t      esac\n\t    done\n\t  else\n\t    # Error occurred in the first compile.  Let's try to salvage\n\t    # the situation: Compile a separate program for each library.\n\t    for i in $deplibs; do\n\t      case $i in\n\t      -l*)\n\t\tfunc_stripname -l '' \"$i\"\n\t\tname=$func_stripname_result\n\t\t$opt_dry_run || $RM conftest\n\t\tif $LTCC $LTCFLAGS -o conftest conftest.c $i; then\n\t\t  ldd_output=`ldd conftest`\n\t\t  if test yes = \"$allow_libtool_libs_with_static_runtimes\"; then\n\t\t    case \" $predeps $postdeps \" in\n\t\t    *\" $i \"*)\n\t\t      func_append newdeplibs \" $i\"\n\t\t      i=\n\t\t      ;;\n\t\t    esac\n\t\t  fi\n\t\t  if test -n \"$i\"; then\n\t\t    libname=`eval \"\\\\$ECHO \\\"$libname_spec\\\"\"`\n\t\t    deplib_matches=`eval \"\\\\$ECHO \\\"$library_names_spec\\\"\"`\n\t\t    set dummy $deplib_matches; shift\n\t\t    deplib_match=$1\n\t\t    if test `expr \"$ldd_output\" : \".*$deplib_match\"` -ne 0; then\n\t\t      func_append newdeplibs \" $i\"\n\t\t    else\n\t\t      droppeddeps=yes\n\t\t      echo\n\t\t      $ECHO \"*** Warning: dynamic linker does not accept needed library $i.\"\n\t\t      echo \"*** I have the capability to make that library automatically link in when\"\n\t\t      echo \"*** you link to this library.  But I can only do this if you have a\"\n\t\t      echo \"*** shared version of the library, which you do not appear to have\"\n\t\t      echo \"*** because a test_compile did reveal that the linker did not use this one\"\n\t\t      echo \"*** as a dynamic dependency that programs can get resolved with at runtime.\"\n\t\t    fi\n\t\t  fi\n\t\telse\n\t\t  droppeddeps=yes\n\t\t  echo\n\t\t  $ECHO \"*** Warning!  Library $i is needed by this library but I was not able to\"\n\t\t  echo \"*** make it link in!  You will probably need to install it or some\"\n\t\t  echo \"*** library that it depends on before this library will be fully\"\n\t\t  echo \"*** functional.  Installing it before continuing would be even better.\"\n\t\tfi\n\t\t;;\n\t      *)\n\t\tfunc_append newdeplibs \" $i\"\n\t\t;;\n\t      esac\n\t    done\n\t  fi\n\t  ;;\n\tfile_magic*)\n\t  set dummy $deplibs_check_method; shift\n\t  file_magic_regex=`expr \"$deplibs_check_method\" : \"$1 \\(.*\\)\"`\n\t  for a_deplib in $deplibs; do\n\t    case $a_deplib in\n\t    -l*)\n\t      func_stripname -l '' \"$a_deplib\"\n\t      name=$func_stripname_result\n\t      if test yes = \"$allow_libtool_libs_with_static_runtimes\"; then\n\t\tcase \" $predeps $postdeps \" in\n\t\t*\" $a_deplib \"*)\n\t\t  func_append newdeplibs \" $a_deplib\"\n\t\t  a_deplib=\n\t\t  ;;\n\t\tesac\n\t      fi\n\t      if test -n \"$a_deplib\"; then\n\t\tlibname=`eval \"\\\\$ECHO \\\"$libname_spec\\\"\"`\n\t\tif test -n \"$file_magic_glob\"; then\n\t\t  libnameglob=`func_echo_all \"$libname\" | $SED -e $file_magic_glob`\n\t\telse\n\t\t  libnameglob=$libname\n\t\tfi\n\t\ttest yes = \"$want_nocaseglob\" && nocaseglob=`shopt -p nocaseglob`\n\t\tfor i in $lib_search_path $sys_lib_search_path $shlib_search_path; do\n\t\t  if test yes = \"$want_nocaseglob\"; then\n\t\t    shopt -s nocaseglob\n\t\t    potential_libs=`ls $i/$libnameglob[.-]* 2>/dev/null`\n\t\t    $nocaseglob\n\t\t  else\n\t\t    potential_libs=`ls $i/$libnameglob[.-]* 2>/dev/null`\n\t\t  fi\n\t\t  for potent_lib in $potential_libs; do\n\t\t      # Follow soft links.\n\t\t      if ls -lLd \"$potent_lib\" 2>/dev/null |\n\t\t\t $GREP \" -> \" >/dev/null; then\n\t\t\tcontinue\n\t\t      fi\n\t\t      # The statement above tries to avoid entering an\n\t\t      # endless loop below, in case of cyclic links.\n\t\t      # We might still enter an endless loop, since a link\n\t\t      # loop can be closed while we follow links,\n\t\t      # but so what?\n\t\t      potlib=$potent_lib\n\t\t      while test -h \"$potlib\" 2>/dev/null; do\n\t\t\tpotliblink=`ls -ld $potlib | $SED 's/.* -> //'`\n\t\t\tcase $potliblink in\n\t\t\t[\\\\/]* | [A-Za-z]:[\\\\/]*) potlib=$potliblink;;\n\t\t\t*) potlib=`$ECHO \"$potlib\" | $SED 's|[^/]*$||'`\"$potliblink\";;\n\t\t\tesac\n\t\t      done\n\t\t      if eval $file_magic_cmd \\\"\\$potlib\\\" 2>/dev/null |\n\t\t\t $SED -e 10q |\n\t\t\t $EGREP \"$file_magic_regex\" > /dev/null; then\n\t\t\tfunc_append newdeplibs \" $a_deplib\"\n\t\t\ta_deplib=\n\t\t\tbreak 2\n\t\t      fi\n\t\t  done\n\t\tdone\n\t      fi\n\t      if test -n \"$a_deplib\"; then\n\t\tdroppeddeps=yes\n\t\techo\n\t\t$ECHO \"*** Warning: linker path does not have real file for library $a_deplib.\"\n\t\techo \"*** I have the capability to make that library automatically link in when\"\n\t\techo \"*** you link to this library.  But I can only do this if you have a\"\n\t\techo \"*** shared version of the library, which you do not appear to have\"\n\t\techo \"*** because I did check the linker path looking for a file starting\"\n\t\tif test -z \"$potlib\"; then\n\t\t  $ECHO \"*** with $libname but no candidates were found. (...for file magic test)\"\n\t\telse\n\t\t  $ECHO \"*** with $libname and none of the candidates passed a file format test\"\n\t\t  $ECHO \"*** using a file magic. Last file checked: $potlib\"\n\t\tfi\n\t      fi\n\t      ;;\n\t    *)\n\t      # Add a -L argument.\n\t      func_append newdeplibs \" $a_deplib\"\n\t      ;;\n\t    esac\n\t  done # Gone through all deplibs.\n\t  ;;\n\tmatch_pattern*)\n\t  set dummy $deplibs_check_method; shift\n\t  match_pattern_regex=`expr \"$deplibs_check_method\" : \"$1 \\(.*\\)\"`\n\t  for a_deplib in $deplibs; do\n\t    case $a_deplib in\n\t    -l*)\n\t      func_stripname -l '' \"$a_deplib\"\n\t      name=$func_stripname_result\n\t      if test yes = \"$allow_libtool_libs_with_static_runtimes\"; then\n\t\tcase \" $predeps $postdeps \" in\n\t\t*\" $a_deplib \"*)\n\t\t  func_append newdeplibs \" $a_deplib\"\n\t\t  a_deplib=\n\t\t  ;;\n\t\tesac\n\t      fi\n\t      if test -n \"$a_deplib\"; then\n\t\tlibname=`eval \"\\\\$ECHO \\\"$libname_spec\\\"\"`\n\t\tfor i in $lib_search_path $sys_lib_search_path $shlib_search_path; do\n\t\t  potential_libs=`ls $i/$libname[.-]* 2>/dev/null`\n\t\t  for potent_lib in $potential_libs; do\n\t\t    potlib=$potent_lib # see symlink-check above in file_magic test\n\t\t    if eval \"\\$ECHO \\\"$potent_lib\\\"\" 2>/dev/null | $SED 10q | \\\n\t\t       $EGREP \"$match_pattern_regex\" > /dev/null; then\n\t\t      func_append newdeplibs \" $a_deplib\"\n\t\t      a_deplib=\n\t\t      break 2\n\t\t    fi\n\t\t  done\n\t\tdone\n\t      fi\n\t      if test -n \"$a_deplib\"; then\n\t\tdroppeddeps=yes\n\t\techo\n\t\t$ECHO \"*** Warning: linker path does not have real file for library $a_deplib.\"\n\t\techo \"*** I have the capability to make that library automatically link in when\"\n\t\techo \"*** you link to this library.  But I can only do this if you have a\"\n\t\techo \"*** shared version of the library, which you do not appear to have\"\n\t\techo \"*** because I did check the linker path looking for a file starting\"\n\t\tif test -z \"$potlib\"; then\n\t\t  $ECHO \"*** with $libname but no candidates were found. (...for regex pattern test)\"\n\t\telse\n\t\t  $ECHO \"*** with $libname and none of the candidates passed a file format test\"\n\t\t  $ECHO \"*** using a regex pattern. Last file checked: $potlib\"\n\t\tfi\n\t      fi\n\t      ;;\n\t    *)\n\t      # Add a -L argument.\n\t      func_append newdeplibs \" $a_deplib\"\n\t      ;;\n\t    esac\n\t  done # Gone through all deplibs.\n\t  ;;\n\tnone | unknown | *)\n\t  newdeplibs=\n\t  tmp_deplibs=`$ECHO \" $deplibs\" | $SED 's/ -lc$//; s/ -[LR][^ ]*//g'`\n\t  if test yes = \"$allow_libtool_libs_with_static_runtimes\"; then\n\t    for i in $predeps $postdeps; do\n\t      # can't use Xsed below, because $i might contain '/'\n\t      tmp_deplibs=`$ECHO \" $tmp_deplibs\" | $SED \"s|$i||\"`\n\t    done\n\t  fi\n\t  case $tmp_deplibs in\n\t  *[!\\\t\\ ]*)\n\t    echo\n\t    if test none = \"$deplibs_check_method\"; then\n\t      echo \"*** Warning: inter-library dependencies are not supported in this platform.\"\n\t    else\n\t      echo \"*** Warning: inter-library dependencies are not known to be supported.\"\n\t    fi\n\t    echo \"*** All declared inter-library dependencies are being dropped.\"\n\t    droppeddeps=yes\n\t    ;;\n\t  esac\n\t  ;;\n\tesac\n\tversuffix=$versuffix_save\n\tmajor=$major_save\n\trelease=$release_save\n\tlibname=$libname_save\n\tname=$name_save\n\n\tcase $host in\n\t*-*-rhapsody* | *-*-darwin1.[012])\n\t  # On Rhapsody replace the C library with the System framework\n\t  newdeplibs=`$ECHO \" $newdeplibs\" | $SED 's/ -lc / System.ltframework /'`\n\t  ;;\n\tesac\n\n\tif test yes = \"$droppeddeps\"; then\n\t  if test yes = \"$module\"; then\n\t    echo\n\t    echo \"*** Warning: libtool could not satisfy all declared inter-library\"\n\t    $ECHO \"*** dependencies of module $libname.  Therefore, libtool will create\"\n\t    echo \"*** a static module, that should work as long as the dlopening\"\n\t    echo \"*** application is linked with the -dlopen flag.\"\n\t    if test -z \"$global_symbol_pipe\"; then\n\t      echo\n\t      echo \"*** However, this would only work if libtool was able to extract symbol\"\n\t      echo \"*** lists from a program, using 'nm' or equivalent, but libtool could\"\n\t      echo \"*** not find such a program.  So, this module is probably useless.\"\n\t      echo \"*** 'nm' from GNU binutils and a full rebuild may help.\"\n\t    fi\n\t    if test no = \"$build_old_libs\"; then\n\t      oldlibs=$output_objdir/$libname.$libext\n\t      build_libtool_libs=module\n\t      build_old_libs=yes\n\t    else\n\t      build_libtool_libs=no\n\t    fi\n\t  else\n\t    echo \"*** The inter-library dependencies that have been dropped here will be\"\n\t    echo \"*** automatically added whenever a program is linked with this library\"\n\t    echo \"*** or is declared to -dlopen it.\"\n\n\t    if test no = \"$allow_undefined\"; then\n\t      echo\n\t      echo \"*** Since this library must not contain undefined symbols,\"\n\t      echo \"*** because either the platform does not support them or\"\n\t      echo \"*** it was explicitly requested with -no-undefined,\"\n\t      echo \"*** libtool will only create a static version of it.\"\n\t      if test no = \"$build_old_libs\"; then\n\t\toldlibs=$output_objdir/$libname.$libext\n\t\tbuild_libtool_libs=module\n\t\tbuild_old_libs=yes\n\t      else\n\t\tbuild_libtool_libs=no\n\t      fi\n\t    fi\n\t  fi\n\tfi\n\t# Done checking deplibs!\n\tdeplibs=$newdeplibs\n      fi\n      # Time to change all our \"foo.ltframework\" stuff back to \"-framework foo\"\n      case $host in\n\t*-*-darwin*)\n\t  newdeplibs=`$ECHO \" $newdeplibs\" | $SED 's% \\([^ $]*\\).ltframework% -framework \\1%g'`\n\t  new_inherited_linker_flags=`$ECHO \" $new_inherited_linker_flags\" | $SED 's% \\([^ $]*\\).ltframework% -framework \\1%g'`\n\t  deplibs=`$ECHO \" $deplibs\" | $SED 's% \\([^ $]*\\).ltframework% -framework \\1%g'`\n\t  ;;\n      esac\n\n      # move library search paths that coincide with paths to not yet\n      # installed libraries to the beginning of the library search list\n      new_libs=\n      for path in $notinst_path; do\n\tcase \" $new_libs \" in\n\t*\" -L$path/$objdir \"*) ;;\n\t*)\n\t  case \" $deplibs \" in\n\t  *\" -L$path/$objdir \"*)\n\t    func_append new_libs \" -L$path/$objdir\" ;;\n\t  esac\n\t  ;;\n\tesac\n      done\n      for deplib in $deplibs; do\n\tcase $deplib in\n\t-L*)\n\t  case \" $new_libs \" in\n\t  *\" $deplib \"*) ;;\n\t  *) func_append new_libs \" $deplib\" ;;\n\t  esac\n\t  ;;\n\t*) func_append new_libs \" $deplib\" ;;\n\tesac\n      done\n      deplibs=$new_libs\n\n      # All the library-specific variables (install_libdir is set above).\n      library_names=\n      old_library=\n      dlname=\n\n      # Test again, we may have decided not to build it any more\n      if test yes = \"$build_libtool_libs\"; then\n\t# Remove $wl instances when linking with ld.\n\t# FIXME: should test the right _cmds variable.\n\tcase $archive_cmds in\n\t  *\\$LD\\ *) wl= ;;\n        esac\n\tif test yes = \"$hardcode_into_libs\"; then\n\t  # Hardcode the library paths\n\t  hardcode_libdirs=\n\t  dep_rpath=\n\t  rpath=$finalize_rpath\n\t  test relink = \"$opt_mode\" || rpath=$compile_rpath$rpath\n\t  for libdir in $rpath; do\n\t    if test -n \"$hardcode_libdir_flag_spec\"; then\n\t      if test -n \"$hardcode_libdir_separator\"; then\n\t\tfunc_replace_sysroot \"$libdir\"\n\t\tlibdir=$func_replace_sysroot_result\n\t\tif test -z \"$hardcode_libdirs\"; then\n\t\t  hardcode_libdirs=$libdir\n\t\telse\n\t\t  # Just accumulate the unique libdirs.\n\t\t  case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in\n\t\t  *\"$hardcode_libdir_separator$libdir$hardcode_libdir_separator\"*)\n\t\t    ;;\n\t\t  *)\n\t\t    func_append hardcode_libdirs \"$hardcode_libdir_separator$libdir\"\n\t\t    ;;\n\t\t  esac\n\t\tfi\n\t      else\n\t\teval flag=\\\"$hardcode_libdir_flag_spec\\\"\n\t\tfunc_append dep_rpath \" $flag\"\n\t      fi\n\t    elif test -n \"$runpath_var\"; then\n\t      case \"$perm_rpath \" in\n\t      *\" $libdir \"*) ;;\n\t      *) func_append perm_rpath \" $libdir\" ;;\n\t      esac\n\t    fi\n\t  done\n\t  # Substitute the hardcoded libdirs into the rpath.\n\t  if test -n \"$hardcode_libdir_separator\" &&\n\t     test -n \"$hardcode_libdirs\"; then\n\t    libdir=$hardcode_libdirs\n\t    eval \"dep_rpath=\\\"$hardcode_libdir_flag_spec\\\"\"\n\t  fi\n\t  if test -n \"$runpath_var\" && test -n \"$perm_rpath\"; then\n\t    # We should set the runpath_var.\n\t    rpath=\n\t    for dir in $perm_rpath; do\n\t      func_append rpath \"$dir:\"\n\t    done\n\t    eval \"$runpath_var='$rpath\\$$runpath_var'; export $runpath_var\"\n\t  fi\n\t  test -n \"$dep_rpath\" && deplibs=\"$dep_rpath $deplibs\"\n\tfi\n\n\tshlibpath=$finalize_shlibpath\n\ttest relink = \"$opt_mode\" || shlibpath=$compile_shlibpath$shlibpath\n\tif test -n \"$shlibpath\"; then\n\t  eval \"$shlibpath_var='$shlibpath\\$$shlibpath_var'; export $shlibpath_var\"\n\tfi\n\n\t# Get the real and link names of the library.\n\teval shared_ext=\\\"$shrext_cmds\\\"\n\teval library_names=\\\"$library_names_spec\\\"\n\tset dummy $library_names\n\tshift\n\trealname=$1\n\tshift\n\n\tif test -n \"$soname_spec\"; then\n\t  eval soname=\\\"$soname_spec\\\"\n\telse\n\t  soname=$realname\n\tfi\n\tif test -z \"$dlname\"; then\n\t  dlname=$soname\n\tfi\n\n\tlib=$output_objdir/$realname\n\tlinknames=\n\tfor link\n\tdo\n\t  func_append linknames \" $link\"\n\tdone\n\n\t# Use standard objects if they are pic\n\ttest -z \"$pic_flag\" && libobjs=`$ECHO \"$libobjs\" | $SP2NL | $SED \"$lo2o\" | $NL2SP`\n\ttest \"X$libobjs\" = \"X \" && libobjs=\n\n\tdelfiles=\n\tif test -n \"$export_symbols\" && test -n \"$include_expsyms\"; then\n\t  $opt_dry_run || cp \"$export_symbols\" \"$output_objdir/$libname.uexp\"\n\t  export_symbols=$output_objdir/$libname.uexp\n\t  func_append delfiles \" $export_symbols\"\n\tfi\n\n\torig_export_symbols=\n\tcase $host_os in\n\tcygwin* | mingw* | cegcc*)\n\t  if test -n \"$export_symbols\" && test -z \"$export_symbols_regex\"; then\n\t    # exporting using user supplied symfile\n\t    func_dll_def_p \"$export_symbols\" || {\n\t      # and it's NOT already a .def file. Must figure out\n\t      # which of the given symbols are data symbols and tag\n\t      # them as such. So, trigger use of export_symbols_cmds.\n\t      # export_symbols gets reassigned inside the \"prepare\n\t      # the list of exported symbols\" if statement, so the\n\t      # include_expsyms logic still works.\n\t      orig_export_symbols=$export_symbols\n\t      export_symbols=\n\t      always_export_symbols=yes\n\t    }\n\t  fi\n\t  ;;\n\tesac\n\n\t# Prepare the list of exported symbols\n\tif test -z \"$export_symbols\"; then\n\t  if test yes = \"$always_export_symbols\" || test -n \"$export_symbols_regex\"; then\n\t    func_verbose \"generating symbol list for '$libname.la'\"\n\t    export_symbols=$output_objdir/$libname.exp\n\t    $opt_dry_run || $RM $export_symbols\n\t    cmds=$export_symbols_cmds\n\t    save_ifs=$IFS; IFS='~'\n\t    for cmd1 in $cmds; do\n\t      IFS=$save_ifs\n\t      # Take the normal branch if the nm_file_list_spec branch\n\t      # doesn't work or if tool conversion is not needed.\n\t      case $nm_file_list_spec~$to_tool_file_cmd in\n\t\t*~func_convert_file_noop | *~func_convert_file_msys_to_w32 | ~*)\n\t\t  try_normal_branch=yes\n\t\t  eval cmd=\\\"$cmd1\\\"\n\t\t  func_len \" $cmd\"\n\t\t  len=$func_len_result\n\t\t  ;;\n\t\t*)\n\t\t  try_normal_branch=no\n\t\t  ;;\n\t      esac\n\t      if test yes = \"$try_normal_branch\" \\\n\t\t && { test \"$len\" -lt \"$max_cmd_len\" \\\n\t\t      || test \"$max_cmd_len\" -le -1; }\n\t      then\n\t\tfunc_show_eval \"$cmd\" 'exit $?'\n\t\tskipped_export=false\n\t      elif test -n \"$nm_file_list_spec\"; then\n\t\tfunc_basename \"$output\"\n\t\toutput_la=$func_basename_result\n\t\tsave_libobjs=$libobjs\n\t\tsave_output=$output\n\t\toutput=$output_objdir/$output_la.nm\n\t\tfunc_to_tool_file \"$output\"\n\t\tlibobjs=$nm_file_list_spec$func_to_tool_file_result\n\t\tfunc_append delfiles \" $output\"\n\t\tfunc_verbose \"creating $NM input file list: $output\"\n\t\tfor obj in $save_libobjs; do\n\t\t  func_to_tool_file \"$obj\"\n\t\t  $ECHO \"$func_to_tool_file_result\"\n\t\tdone > \"$output\"\n\t\teval cmd=\\\"$cmd1\\\"\n\t\tfunc_show_eval \"$cmd\" 'exit $?'\n\t\toutput=$save_output\n\t\tlibobjs=$save_libobjs\n\t\tskipped_export=false\n\t      else\n\t\t# The command line is too long to execute in one step.\n\t\tfunc_verbose \"using reloadable object file for export list...\"\n\t\tskipped_export=:\n\t\t# Break out early, otherwise skipped_export may be\n\t\t# set to false by a later but shorter cmd.\n\t\tbreak\n\t      fi\n\t    done\n\t    IFS=$save_ifs\n\t    if test -n \"$export_symbols_regex\" && test : != \"$skipped_export\"; then\n\t      func_show_eval '$EGREP -e \"$export_symbols_regex\" \"$export_symbols\" > \"${export_symbols}T\"'\n\t      func_show_eval '$MV \"${export_symbols}T\" \"$export_symbols\"'\n\t    fi\n\t  fi\n\tfi\n\n\tif test -n \"$export_symbols\" && test -n \"$include_expsyms\"; then\n\t  tmp_export_symbols=$export_symbols\n\t  test -n \"$orig_export_symbols\" && tmp_export_symbols=$orig_export_symbols\n\t  $opt_dry_run || eval '$ECHO \"$include_expsyms\" | $SP2NL >> \"$tmp_export_symbols\"'\n\tfi\n\n\tif test : != \"$skipped_export\" && test -n \"$orig_export_symbols\"; then\n\t  # The given exports_symbols file has to be filtered, so filter it.\n\t  func_verbose \"filter symbol list for '$libname.la' to tag DATA exports\"\n\t  # FIXME: $output_objdir/$libname.filter potentially contains lots of\n\t  # 's' commands, which not all seds can handle. GNU sed should be fine\n\t  # though. Also, the filter scales superlinearly with the number of\n\t  # global variables. join(1) would be nice here, but unfortunately\n\t  # isn't a blessed tool.\n\t  $opt_dry_run || $SED -e '/[ ,]DATA/!d;s,\\(.*\\)\\([ \\,].*\\),s|^\\1$|\\1\\2|,' < $export_symbols > $output_objdir/$libname.filter\n\t  func_append delfiles \" $export_symbols $output_objdir/$libname.filter\"\n\t  export_symbols=$output_objdir/$libname.def\n\t  $opt_dry_run || $SED -f $output_objdir/$libname.filter < $orig_export_symbols > $export_symbols\n\tfi\n\n\ttmp_deplibs=\n\tfor test_deplib in $deplibs; do\n\t  case \" $convenience \" in\n\t  *\" $test_deplib \"*) ;;\n\t  *)\n\t    func_append tmp_deplibs \" $test_deplib\"\n\t    ;;\n\t  esac\n\tdone\n\tdeplibs=$tmp_deplibs\n\n\tif test -n \"$convenience\"; then\n\t  if test -n \"$whole_archive_flag_spec\" &&\n\t    test yes = \"$compiler_needs_object\" &&\n\t    test -z \"$libobjs\"; then\n\t    # extract the archives, so we have objects to list.\n\t    # TODO: could optimize this to just extract one archive.\n\t    whole_archive_flag_spec=\n\t  fi\n\t  if test -n \"$whole_archive_flag_spec\"; then\n\t    save_libobjs=$libobjs\n\t    eval libobjs=\\\"\\$libobjs $whole_archive_flag_spec\\\"\n\t    test \"X$libobjs\" = \"X \" && libobjs=\n\t  else\n\t    gentop=$output_objdir/${outputname}x\n\t    func_append generated \" $gentop\"\n\n\t    func_extract_archives $gentop $convenience\n\t    func_append libobjs \" $func_extract_archives_result\"\n\t    test \"X$libobjs\" = \"X \" && libobjs=\n\t  fi\n\tfi\n\n\tif test yes = \"$thread_safe\" && test -n \"$thread_safe_flag_spec\"; then\n\t  eval flag=\\\"$thread_safe_flag_spec\\\"\n\t  func_append linker_flags \" $flag\"\n\tfi\n\n\t# Make a backup of the uninstalled library when relinking\n\tif test relink = \"$opt_mode\"; then\n\t  $opt_dry_run || eval '(cd $output_objdir && $RM ${realname}U && $MV $realname ${realname}U)' || exit $?\n\tfi\n\n\t# Do each of the archive commands.\n\tif test yes = \"$module\" && test -n \"$module_cmds\"; then\n\t  if test -n \"$export_symbols\" && test -n \"$module_expsym_cmds\"; then\n\t    eval test_cmds=\\\"$module_expsym_cmds\\\"\n\t    cmds=$module_expsym_cmds\n\t  else\n\t    eval test_cmds=\\\"$module_cmds\\\"\n\t    cmds=$module_cmds\n\t  fi\n\telse\n\t  if test -n \"$export_symbols\" && test -n \"$archive_expsym_cmds\"; then\n\t    eval test_cmds=\\\"$archive_expsym_cmds\\\"\n\t    cmds=$archive_expsym_cmds\n\t  else\n\t    eval test_cmds=\\\"$archive_cmds\\\"\n\t    cmds=$archive_cmds\n\t  fi\n\tfi\n\n\tif test : != \"$skipped_export\" &&\n\t   func_len \" $test_cmds\" &&\n\t   len=$func_len_result &&\n\t   test \"$len\" -lt \"$max_cmd_len\" || test \"$max_cmd_len\" -le -1; then\n\t  :\n\telse\n\t  # The command line is too long to link in one step, link piecewise\n\t  # or, if using GNU ld and skipped_export is not :, use a linker\n\t  # script.\n\n\t  # Save the value of $output and $libobjs because we want to\n\t  # use them later.  If we have whole_archive_flag_spec, we\n\t  # want to use save_libobjs as it was before\n\t  # whole_archive_flag_spec was expanded, because we can't\n\t  # assume the linker understands whole_archive_flag_spec.\n\t  # This may have to be revisited, in case too many\n\t  # convenience libraries get linked in and end up exceeding\n\t  # the spec.\n\t  if test -z \"$convenience\" || test -z \"$whole_archive_flag_spec\"; then\n\t    save_libobjs=$libobjs\n\t  fi\n\t  save_output=$output\n\t  func_basename \"$output\"\n\t  output_la=$func_basename_result\n\n\t  # Clear the reloadable object creation command queue and\n\t  # initialize k to one.\n\t  test_cmds=\n\t  concat_cmds=\n\t  objlist=\n\t  last_robj=\n\t  k=1\n\n\t  if test -n \"$save_libobjs\" && test : != \"$skipped_export\" && test yes = \"$with_gnu_ld\"; then\n\t    output=$output_objdir/$output_la.lnkscript\n\t    func_verbose \"creating GNU ld script: $output\"\n\t    echo 'INPUT (' > $output\n\t    for obj in $save_libobjs\n\t    do\n\t      func_to_tool_file \"$obj\"\n\t      $ECHO \"$func_to_tool_file_result\" >> $output\n\t    done\n\t    echo ')' >> $output\n\t    func_append delfiles \" $output\"\n\t    func_to_tool_file \"$output\"\n\t    output=$func_to_tool_file_result\n\t  elif test -n \"$save_libobjs\" && test : != \"$skipped_export\" && test -n \"$file_list_spec\"; then\n\t    output=$output_objdir/$output_la.lnk\n\t    func_verbose \"creating linker input file list: $output\"\n\t    : > $output\n\t    set x $save_libobjs\n\t    shift\n\t    firstobj=\n\t    if test yes = \"$compiler_needs_object\"; then\n\t      firstobj=\"$1 \"\n\t      shift\n\t    fi\n\t    for obj\n\t    do\n\t      func_to_tool_file \"$obj\"\n\t      $ECHO \"$func_to_tool_file_result\" >> $output\n\t    done\n\t    func_append delfiles \" $output\"\n\t    func_to_tool_file \"$output\"\n\t    output=$firstobj\\\"$file_list_spec$func_to_tool_file_result\\\"\n\t  else\n\t    if test -n \"$save_libobjs\"; then\n\t      func_verbose \"creating reloadable object files...\"\n\t      output=$output_objdir/$output_la-$k.$objext\n\t      eval test_cmds=\\\"$reload_cmds\\\"\n\t      func_len \" $test_cmds\"\n\t      len0=$func_len_result\n\t      len=$len0\n\n\t      # Loop over the list of objects to be linked.\n\t      for obj in $save_libobjs\n\t      do\n\t\tfunc_len \" $obj\"\n\t\tfunc_arith $len + $func_len_result\n\t\tlen=$func_arith_result\n\t\tif test -z \"$objlist\" ||\n\t\t   test \"$len\" -lt \"$max_cmd_len\"; then\n\t\t  func_append objlist \" $obj\"\n\t\telse\n\t\t  # The command $test_cmds is almost too long, add a\n\t\t  # command to the queue.\n\t\t  if test 1 -eq \"$k\"; then\n\t\t    # The first file doesn't have a previous command to add.\n\t\t    reload_objs=$objlist\n\t\t    eval concat_cmds=\\\"$reload_cmds\\\"\n\t\t  else\n\t\t    # All subsequent reloadable object files will link in\n\t\t    # the last one created.\n\t\t    reload_objs=\"$objlist $last_robj\"\n\t\t    eval concat_cmds=\\\"\\$concat_cmds~$reload_cmds~\\$RM $last_robj\\\"\n\t\t  fi\n\t\t  last_robj=$output_objdir/$output_la-$k.$objext\n\t\t  func_arith $k + 1\n\t\t  k=$func_arith_result\n\t\t  output=$output_objdir/$output_la-$k.$objext\n\t\t  objlist=\" $obj\"\n\t\t  func_len \" $last_robj\"\n\t\t  func_arith $len0 + $func_len_result\n\t\t  len=$func_arith_result\n\t\tfi\n\t      done\n\t      # Handle the remaining objects by creating one last\n\t      # reloadable object file.  All subsequent reloadable object\n\t      # files will link in the last one created.\n\t      test -z \"$concat_cmds\" || concat_cmds=$concat_cmds~\n\t      reload_objs=\"$objlist $last_robj\"\n\t      eval concat_cmds=\\\"\\$concat_cmds$reload_cmds\\\"\n\t      if test -n \"$last_robj\"; then\n\t        eval concat_cmds=\\\"\\$concat_cmds~\\$RM $last_robj\\\"\n\t      fi\n\t      func_append delfiles \" $output\"\n\n\t    else\n\t      output=\n\t    fi\n\n\t    ${skipped_export-false} && {\n\t      func_verbose \"generating symbol list for '$libname.la'\"\n\t      export_symbols=$output_objdir/$libname.exp\n\t      $opt_dry_run || $RM $export_symbols\n\t      libobjs=$output\n\t      # Append the command to create the export file.\n\t      test -z \"$concat_cmds\" || concat_cmds=$concat_cmds~\n\t      eval concat_cmds=\\\"\\$concat_cmds$export_symbols_cmds\\\"\n\t      if test -n \"$last_robj\"; then\n\t\teval concat_cmds=\\\"\\$concat_cmds~\\$RM $last_robj\\\"\n\t      fi\n\t    }\n\n\t    test -n \"$save_libobjs\" &&\n\t      func_verbose \"creating a temporary reloadable object file: $output\"\n\n\t    # Loop through the commands generated above and execute them.\n\t    save_ifs=$IFS; IFS='~'\n\t    for cmd in $concat_cmds; do\n\t      IFS=$save_ifs\n\t      $opt_quiet || {\n\t\t  func_quote_arg expand,pretty \"$cmd\"\n\t\t  eval \"func_echo $func_quote_arg_result\"\n\t      }\n\t      $opt_dry_run || eval \"$cmd\" || {\n\t\tlt_exit=$?\n\n\t\t# Restore the uninstalled library and exit\n\t\tif test relink = \"$opt_mode\"; then\n\t\t  ( cd \"$output_objdir\" && \\\n\t\t    $RM \"${realname}T\" && \\\n\t\t    $MV \"${realname}U\" \"$realname\" )\n\t\tfi\n\n\t\texit $lt_exit\n\t      }\n\t    done\n\t    IFS=$save_ifs\n\n\t    if test -n \"$export_symbols_regex\" && ${skipped_export-false}; then\n\t      func_show_eval '$EGREP -e \"$export_symbols_regex\" \"$export_symbols\" > \"${export_symbols}T\"'\n\t      func_show_eval '$MV \"${export_symbols}T\" \"$export_symbols\"'\n\t    fi\n\t  fi\n\n          ${skipped_export-false} && {\n\t    if test -n \"$export_symbols\" && test -n \"$include_expsyms\"; then\n\t      tmp_export_symbols=$export_symbols\n\t      test -n \"$orig_export_symbols\" && tmp_export_symbols=$orig_export_symbols\n\t      $opt_dry_run || eval '$ECHO \"$include_expsyms\" | $SP2NL >> \"$tmp_export_symbols\"'\n\t    fi\n\n\t    if test -n \"$orig_export_symbols\"; then\n\t      # The given exports_symbols file has to be filtered, so filter it.\n\t      func_verbose \"filter symbol list for '$libname.la' to tag DATA exports\"\n\t      # FIXME: $output_objdir/$libname.filter potentially contains lots of\n\t      # 's' commands, which not all seds can handle. GNU sed should be fine\n\t      # though. Also, the filter scales superlinearly with the number of\n\t      # global variables. join(1) would be nice here, but unfortunately\n\t      # isn't a blessed tool.\n\t      $opt_dry_run || $SED -e '/[ ,]DATA/!d;s,\\(.*\\)\\([ \\,].*\\),s|^\\1$|\\1\\2|,' < $export_symbols > $output_objdir/$libname.filter\n\t      func_append delfiles \" $export_symbols $output_objdir/$libname.filter\"\n\t      export_symbols=$output_objdir/$libname.def\n\t      $opt_dry_run || $SED -f $output_objdir/$libname.filter < $orig_export_symbols > $export_symbols\n\t    fi\n\t  }\n\n\t  libobjs=$output\n\t  # Restore the value of output.\n\t  output=$save_output\n\n\t  if test -n \"$convenience\" && test -n \"$whole_archive_flag_spec\"; then\n\t    eval libobjs=\\\"\\$libobjs $whole_archive_flag_spec\\\"\n\t    test \"X$libobjs\" = \"X \" && libobjs=\n\t  fi\n\t  # Expand the library linking commands again to reset the\n\t  # value of $libobjs for piecewise linking.\n\n\t  # Do each of the archive commands.\n\t  if test yes = \"$module\" && test -n \"$module_cmds\"; then\n\t    if test -n \"$export_symbols\" && test -n \"$module_expsym_cmds\"; then\n\t      cmds=$module_expsym_cmds\n\t    else\n\t      cmds=$module_cmds\n\t    fi\n\t  else\n\t    if test -n \"$export_symbols\" && test -n \"$archive_expsym_cmds\"; then\n\t      cmds=$archive_expsym_cmds\n\t    else\n\t      cmds=$archive_cmds\n\t    fi\n\t  fi\n\tfi\n\n\tif test -n \"$delfiles\"; then\n\t  # Append the command to remove temporary files to $cmds.\n\t  eval cmds=\\\"\\$cmds~\\$RM $delfiles\\\"\n\tfi\n\n\t# Add any objects from preloaded convenience libraries\n\tif test -n \"$dlprefiles\"; then\n\t  gentop=$output_objdir/${outputname}x\n\t  func_append generated \" $gentop\"\n\n\t  func_extract_archives $gentop $dlprefiles\n\t  func_append libobjs \" $func_extract_archives_result\"\n\t  test \"X$libobjs\" = \"X \" && libobjs=\n\tfi\n\n\tsave_ifs=$IFS; IFS='~'\n\tfor cmd in $cmds; do\n\t  IFS=$sp$nl\n\t  eval cmd=\\\"$cmd\\\"\n\t  IFS=$save_ifs\n\t  $opt_quiet || {\n\t    func_quote_arg expand,pretty \"$cmd\"\n\t    eval \"func_echo $func_quote_arg_result\"\n\t  }\n\t  $opt_dry_run || eval \"$cmd\" || {\n\t    lt_exit=$?\n\n\t    # Restore the uninstalled library and exit\n\t    if test relink = \"$opt_mode\"; then\n\t      ( cd \"$output_objdir\" && \\\n\t        $RM \"${realname}T\" && \\\n\t\t$MV \"${realname}U\" \"$realname\" )\n\t    fi\n\n\t    exit $lt_exit\n\t  }\n\tdone\n\tIFS=$save_ifs\n\n\t# Restore the uninstalled library and exit\n\tif test relink = \"$opt_mode\"; then\n\t  $opt_dry_run || eval '(cd $output_objdir && $RM ${realname}T && $MV $realname ${realname}T && $MV ${realname}U $realname)' || exit $?\n\n\t  if test -n \"$convenience\"; then\n\t    if test -z \"$whole_archive_flag_spec\"; then\n\t      func_show_eval '${RM}r \"$gentop\"'\n\t    fi\n\t  fi\n\n\t  exit $EXIT_SUCCESS\n\tfi\n\n\t# Create links to the real library.\n\tfor linkname in $linknames; do\n\t  if test \"$realname\" != \"$linkname\"; then\n\t    func_show_eval '(cd \"$output_objdir\" && $RM \"$linkname\" && $LN_S \"$realname\" \"$linkname\")' 'exit $?'\n\t  fi\n\tdone\n\n\t# If -module or -export-dynamic was specified, set the dlname.\n\tif test yes = \"$module\" || test yes = \"$export_dynamic\"; then\n\t  # On all known operating systems, these are identical.\n\t  dlname=$soname\n\tfi\n      fi\n      ;;\n\n    obj)\n      if test -n \"$dlfiles$dlprefiles\" || test no != \"$dlself\"; then\n\tfunc_warning \"'-dlopen' is ignored for objects\"\n      fi\n\n      case \" $deplibs\" in\n      *\\ -l* | *\\ -L*)\n\tfunc_warning \"'-l' and '-L' are ignored for objects\" ;;\n      esac\n\n      test -n \"$rpath\" && \\\n\tfunc_warning \"'-rpath' is ignored for objects\"\n\n      test -n \"$xrpath\" && \\\n\tfunc_warning \"'-R' is ignored for objects\"\n\n      test -n \"$vinfo\" && \\\n\tfunc_warning \"'-version-info' is ignored for objects\"\n\n      test -n \"$release\" && \\\n\tfunc_warning \"'-release' is ignored for objects\"\n\n      case $output in\n      *.lo)\n\ttest -n \"$objs$old_deplibs\" && \\\n\t  func_fatal_error \"cannot build library object '$output' from non-libtool objects\"\n\n\tlibobj=$output\n\tfunc_lo2o \"$libobj\"\n\tobj=$func_lo2o_result\n\t;;\n      *)\n\tlibobj=\n\tobj=$output\n\t;;\n      esac\n\n      # Delete the old objects.\n      $opt_dry_run || $RM $obj $libobj\n\n      # Objects from convenience libraries.  This assumes\n      # single-version convenience libraries.  Whenever we create\n      # different ones for PIC/non-PIC, this we'll have to duplicate\n      # the extraction.\n      reload_conv_objs=\n      gentop=\n      # if reload_cmds runs $LD directly, get rid of -Wl from\n      # whole_archive_flag_spec and hope we can get by with turning comma\n      # into space.\n      case $reload_cmds in\n        *\\$LD[\\ \\$]*) wl= ;;\n      esac\n      if test -n \"$convenience\"; then\n\tif test -n \"$whole_archive_flag_spec\"; then\n\t  eval tmp_whole_archive_flags=\\\"$whole_archive_flag_spec\\\"\n\t  test -n \"$wl\" || tmp_whole_archive_flags=`$ECHO \"$tmp_whole_archive_flags\" | $SED 's|,| |g'`\n\t  reload_conv_objs=$reload_objs\\ $tmp_whole_archive_flags\n\telse\n\t  gentop=$output_objdir/${obj}x\n\t  func_append generated \" $gentop\"\n\n\t  func_extract_archives $gentop $convenience\n\t  reload_conv_objs=\"$reload_objs $func_extract_archives_result\"\n\tfi\n      fi\n\n      # If we're not building shared, we need to use non_pic_objs\n      test yes = \"$build_libtool_libs\" || libobjs=$non_pic_objects\n\n      # Create the old-style object.\n      reload_objs=$objs$old_deplibs' '`$ECHO \"$libobjs\" | $SP2NL | $SED \"/\\.$libext$/d; /\\.lib$/d; $lo2o\" | $NL2SP`' '$reload_conv_objs\n\n      output=$obj\n      func_execute_cmds \"$reload_cmds\" 'exit $?'\n\n      # Exit if we aren't doing a library object file.\n      if test -z \"$libobj\"; then\n\tif test -n \"$gentop\"; then\n\t  func_show_eval '${RM}r \"$gentop\"'\n\tfi\n\n\texit $EXIT_SUCCESS\n      fi\n\n      test yes = \"$build_libtool_libs\" || {\n\tif test -n \"$gentop\"; then\n\t  func_show_eval '${RM}r \"$gentop\"'\n\tfi\n\n\t# Create an invalid libtool object if no PIC, so that we don't\n\t# accidentally link it into a program.\n\t# $show \"echo timestamp > $libobj\"\n\t# $opt_dry_run || eval \"echo timestamp > $libobj\" || exit $?\n\texit $EXIT_SUCCESS\n      }\n\n      if test -n \"$pic_flag\" || test default != \"$pic_mode\"; then\n\t# Only do commands if we really have different PIC objects.\n\treload_objs=\"$libobjs $reload_conv_objs\"\n\toutput=$libobj\n\tfunc_execute_cmds \"$reload_cmds\" 'exit $?'\n      fi\n\n      if test -n \"$gentop\"; then\n\tfunc_show_eval '${RM}r \"$gentop\"'\n      fi\n\n      exit $EXIT_SUCCESS\n      ;;\n\n    prog)\n      case $host in\n\t*cygwin*) func_stripname '' '.exe' \"$output\"\n\t          output=$func_stripname_result.exe;;\n      esac\n      test -n \"$vinfo\" && \\\n\tfunc_warning \"'-version-info' is ignored for programs\"\n\n      test -n \"$release\" && \\\n\tfunc_warning \"'-release' is ignored for programs\"\n\n      $preload \\\n\t&& test unknown,unknown,unknown = \"$dlopen_support,$dlopen_self,$dlopen_self_static\" \\\n\t&& func_warning \"'LT_INIT([dlopen])' not used. Assuming no dlopen support.\"\n\n      case $host in\n      *-*-rhapsody* | *-*-darwin1.[012])\n\t# On Rhapsody replace the C library is the System framework\n\tcompile_deplibs=`$ECHO \" $compile_deplibs\" | $SED 's/ -lc / System.ltframework /'`\n\tfinalize_deplibs=`$ECHO \" $finalize_deplibs\" | $SED 's/ -lc / System.ltframework /'`\n\t;;\n      esac\n\n      case $host in\n      *-*-darwin*)\n\t# Don't allow lazy linking, it breaks C++ global constructors\n\t# But is supposedly fixed on 10.4 or later (yay!).\n\tif test CXX = \"$tagname\"; then\n\t  case ${MACOSX_DEPLOYMENT_TARGET-10.0} in\n\t    10.[0123])\n\t      func_append compile_command \" $wl-bind_at_load\"\n\t      func_append finalize_command \" $wl-bind_at_load\"\n\t    ;;\n\t  esac\n\tfi\n\t# Time to change all our \"foo.ltframework\" stuff back to \"-framework foo\"\n\tcompile_deplibs=`$ECHO \" $compile_deplibs\" | $SED 's% \\([^ $]*\\).ltframework% -framework \\1%g'`\n\tfinalize_deplibs=`$ECHO \" $finalize_deplibs\" | $SED 's% \\([^ $]*\\).ltframework% -framework \\1%g'`\n\t;;\n      esac\n\n\n      # move library search paths that coincide with paths to not yet\n      # installed libraries to the beginning of the library search list\n      new_libs=\n      for path in $notinst_path; do\n\tcase \" $new_libs \" in\n\t*\" -L$path/$objdir \"*) ;;\n\t*)\n\t  case \" $compile_deplibs \" in\n\t  *\" -L$path/$objdir \"*)\n\t    func_append new_libs \" -L$path/$objdir\" ;;\n\t  esac\n\t  ;;\n\tesac\n      done\n      for deplib in $compile_deplibs; do\n\tcase $deplib in\n\t-L*)\n\t  case \" $new_libs \" in\n\t  *\" $deplib \"*) ;;\n\t  *) func_append new_libs \" $deplib\" ;;\n\t  esac\n\t  ;;\n\t*) func_append new_libs \" $deplib\" ;;\n\tesac\n      done\n      compile_deplibs=$new_libs\n\n\n      func_append compile_command \" $compile_deplibs\"\n      func_append finalize_command \" $finalize_deplibs\"\n\n      if test -n \"$rpath$xrpath\"; then\n\t# If the user specified any rpath flags, then add them.\n\tfor libdir in $rpath $xrpath; do\n\t  # This is the magic to use -rpath.\n\t  case \"$finalize_rpath \" in\n\t  *\" $libdir \"*) ;;\n\t  *) func_append finalize_rpath \" $libdir\" ;;\n\t  esac\n\tdone\n      fi\n\n      # Now hardcode the library paths\n      rpath=\n      hardcode_libdirs=\n      for libdir in $compile_rpath $finalize_rpath; do\n\tif test -n \"$hardcode_libdir_flag_spec\"; then\n\t  if test -n \"$hardcode_libdir_separator\"; then\n\t    if test -z \"$hardcode_libdirs\"; then\n\t      hardcode_libdirs=$libdir\n\t    else\n\t      # Just accumulate the unique libdirs.\n\t      case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in\n\t      *\"$hardcode_libdir_separator$libdir$hardcode_libdir_separator\"*)\n\t\t;;\n\t      *)\n\t\tfunc_append hardcode_libdirs \"$hardcode_libdir_separator$libdir\"\n\t\t;;\n\t      esac\n\t    fi\n\t  else\n\t    eval flag=\\\"$hardcode_libdir_flag_spec\\\"\n\t    func_append rpath \" $flag\"\n\t  fi\n\telif test -n \"$runpath_var\"; then\n\t  case \"$perm_rpath \" in\n\t  *\" $libdir \"*) ;;\n\t  *) func_append perm_rpath \" $libdir\" ;;\n\t  esac\n\tfi\n\tcase $host in\n\t*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-os2* | *-cegcc*)\n\t  testbindir=`$ECHO \"$libdir\" | $SED -e 's*/lib$*/bin*'`\n\t  case :$dllsearchpath: in\n\t  *\":$libdir:\"*) ;;\n\t  ::) dllsearchpath=$libdir;;\n\t  *) func_append dllsearchpath \":$libdir\";;\n\t  esac\n\t  case :$dllsearchpath: in\n\t  *\":$testbindir:\"*) ;;\n\t  ::) dllsearchpath=$testbindir;;\n\t  *) func_append dllsearchpath \":$testbindir\";;\n\t  esac\n\t  ;;\n\tesac\n      done\n      # Substitute the hardcoded libdirs into the rpath.\n      if test -n \"$hardcode_libdir_separator\" &&\n\t test -n \"$hardcode_libdirs\"; then\n\tlibdir=$hardcode_libdirs\n\teval rpath=\\\" $hardcode_libdir_flag_spec\\\"\n      fi\n      compile_rpath=$rpath\n\n      rpath=\n      hardcode_libdirs=\n      for libdir in $finalize_rpath; do\n\tif test -n \"$hardcode_libdir_flag_spec\"; then\n\t  if test -n \"$hardcode_libdir_separator\"; then\n\t    if test -z \"$hardcode_libdirs\"; then\n\t      hardcode_libdirs=$libdir\n\t    else\n\t      # Just accumulate the unique libdirs.\n\t      case $hardcode_libdir_separator$hardcode_libdirs$hardcode_libdir_separator in\n\t      *\"$hardcode_libdir_separator$libdir$hardcode_libdir_separator\"*)\n\t\t;;\n\t      *)\n\t\tfunc_append hardcode_libdirs \"$hardcode_libdir_separator$libdir\"\n\t\t;;\n\t      esac\n\t    fi\n\t  else\n\t    eval flag=\\\"$hardcode_libdir_flag_spec\\\"\n\t    func_append rpath \" $flag\"\n\t  fi\n\telif test -n \"$runpath_var\"; then\n\t  case \"$finalize_perm_rpath \" in\n\t  *\" $libdir \"*) ;;\n\t  *) func_append finalize_perm_rpath \" $libdir\" ;;\n\t  esac\n\tfi\n      done\n      # Substitute the hardcoded libdirs into the rpath.\n      if test -n \"$hardcode_libdir_separator\" &&\n\t test -n \"$hardcode_libdirs\"; then\n\tlibdir=$hardcode_libdirs\n\teval rpath=\\\" $hardcode_libdir_flag_spec\\\"\n      fi\n      finalize_rpath=$rpath\n\n      if test -n \"$libobjs\" && test yes = \"$build_old_libs\"; then\n\t# Transform all the library objects into standard objects.\n\tcompile_command=`$ECHO \"$compile_command\" | $SP2NL | $SED \"$lo2o\" | $NL2SP`\n\tfinalize_command=`$ECHO \"$finalize_command\" | $SP2NL | $SED \"$lo2o\" | $NL2SP`\n      fi\n\n      func_generate_dlsyms \"$outputname\" \"@PROGRAM@\" false\n\n      # template prelinking step\n      if test -n \"$prelink_cmds\"; then\n\tfunc_execute_cmds \"$prelink_cmds\" 'exit $?'\n      fi\n\n      wrappers_required=:\n      case $host in\n      *cegcc* | *mingw32ce*)\n        # Disable wrappers for cegcc and mingw32ce hosts, we are cross compiling anyway.\n        wrappers_required=false\n        ;;\n      *cygwin* | *mingw* )\n        test yes = \"$build_libtool_libs\" || wrappers_required=false\n        ;;\n      *)\n        if test no = \"$need_relink\" || test yes != \"$build_libtool_libs\"; then\n          wrappers_required=false\n        fi\n        ;;\n      esac\n      $wrappers_required || {\n\t# Replace the output file specification.\n\tcompile_command=`$ECHO \"$compile_command\" | $SED 's%@OUTPUT@%'\"$output\"'%g'`\n\tlink_command=$compile_command$compile_rpath\n\n\t# We have no uninstalled library dependencies, so finalize right now.\n\texit_status=0\n\tfunc_show_eval \"$link_command\" 'exit_status=$?'\n\n\tif test -n \"$postlink_cmds\"; then\n\t  func_to_tool_file \"$output\"\n\t  postlink_cmds=`func_echo_all \"$postlink_cmds\" | $SED -e 's%@OUTPUT@%'\"$output\"'%g' -e 's%@TOOL_OUTPUT@%'\"$func_to_tool_file_result\"'%g'`\n\t  func_execute_cmds \"$postlink_cmds\" 'exit $?'\n\tfi\n\n\t# Delete the generated files.\n\tif test -f \"$output_objdir/${outputname}S.$objext\"; then\n\t  func_show_eval '$RM \"$output_objdir/${outputname}S.$objext\"'\n\tfi\n\n\texit $exit_status\n      }\n\n      if test -n \"$compile_shlibpath$finalize_shlibpath\"; then\n\tcompile_command=\"$shlibpath_var=\\\"$compile_shlibpath$finalize_shlibpath\\$$shlibpath_var\\\" $compile_command\"\n      fi\n      if test -n \"$finalize_shlibpath\"; then\n\tfinalize_command=\"$shlibpath_var=\\\"$finalize_shlibpath\\$$shlibpath_var\\\" $finalize_command\"\n      fi\n\n      compile_var=\n      finalize_var=\n      if test -n \"$runpath_var\"; then\n\tif test -n \"$perm_rpath\"; then\n\t  # We should set the runpath_var.\n\t  rpath=\n\t  for dir in $perm_rpath; do\n\t    func_append rpath \"$dir:\"\n\t  done\n\t  compile_var=\"$runpath_var=\\\"$rpath\\$$runpath_var\\\" \"\n\tfi\n\tif test -n \"$finalize_perm_rpath\"; then\n\t  # We should set the runpath_var.\n\t  rpath=\n\t  for dir in $finalize_perm_rpath; do\n\t    func_append rpath \"$dir:\"\n\t  done\n\t  finalize_var=\"$runpath_var=\\\"$rpath\\$$runpath_var\\\" \"\n\tfi\n      fi\n\n      if test yes = \"$no_install\"; then\n\t# We don't need to create a wrapper script.\n\tlink_command=$compile_var$compile_command$compile_rpath\n\t# Replace the output file specification.\n\tlink_command=`$ECHO \"$link_command\" | $SED 's%@OUTPUT@%'\"$output\"'%g'`\n\t# Delete the old output file.\n\t$opt_dry_run || $RM $output\n\t# Link the executable and exit\n\tfunc_show_eval \"$link_command\" 'exit $?'\n\n\tif test -n \"$postlink_cmds\"; then\n\t  func_to_tool_file \"$output\"\n\t  postlink_cmds=`func_echo_all \"$postlink_cmds\" | $SED -e 's%@OUTPUT@%'\"$output\"'%g' -e 's%@TOOL_OUTPUT@%'\"$func_to_tool_file_result\"'%g'`\n\t  func_execute_cmds \"$postlink_cmds\" 'exit $?'\n\tfi\n\n\texit $EXIT_SUCCESS\n      fi\n\n      case $hardcode_action,$fast_install in\n        relink,*)\n\t  # Fast installation is not supported\n\t  link_command=$compile_var$compile_command$compile_rpath\n\t  relink_command=$finalize_var$finalize_command$finalize_rpath\n\n\t  func_warning \"this platform does not like uninstalled shared libraries\"\n\t  func_warning \"'$output' will be relinked during installation\"\n\t  ;;\n        *,yes)\n\t  link_command=$finalize_var$compile_command$finalize_rpath\n\t  relink_command=`$ECHO \"$compile_var$compile_command$compile_rpath\" | $SED 's%@OUTPUT@%\\$progdir/\\$file%g'`\n          ;;\n\t*,no)\n\t  link_command=$compile_var$compile_command$compile_rpath\n\t  relink_command=$finalize_var$finalize_command$finalize_rpath\n          ;;\n\t*,needless)\n\t  link_command=$finalize_var$compile_command$finalize_rpath\n\t  relink_command=\n          ;;\n      esac\n\n      # Replace the output file specification.\n      link_command=`$ECHO \"$link_command\" | $SED 's%@OUTPUT@%'\"$output_objdir/$outputname\"'%g'`\n\n      # Delete the old output files.\n      $opt_dry_run || $RM $output $output_objdir/$outputname $output_objdir/lt-$outputname\n\n      func_show_eval \"$link_command\" 'exit $?'\n\n      if test -n \"$postlink_cmds\"; then\n\tfunc_to_tool_file \"$output_objdir/$outputname\"\n\tpostlink_cmds=`func_echo_all \"$postlink_cmds\" | $SED -e 's%@OUTPUT@%'\"$output_objdir/$outputname\"'%g' -e 's%@TOOL_OUTPUT@%'\"$func_to_tool_file_result\"'%g'`\n\tfunc_execute_cmds \"$postlink_cmds\" 'exit $?'\n      fi\n\n      # Now create the wrapper script.\n      func_verbose \"creating $output\"\n\n      # Quote the relink command for shipping.\n      if test -n \"$relink_command\"; then\n\t# Preserve any variables that may affect compiler behavior\n\tfor var in $variables_saved_for_relink; do\n\t  if eval test -z \\\"\\${$var+set}\\\"; then\n\t    relink_command=\"{ test -z \\\"\\${$var+set}\\\" || $lt_unset $var || { $var=; export $var; }; }; $relink_command\"\n\t  elif eval var_value=\\$$var; test -z \"$var_value\"; then\n\t    relink_command=\"$var=; export $var; $relink_command\"\n\t  else\n\t    func_quote_arg pretty \"$var_value\"\n\t    relink_command=\"$var=$func_quote_arg_result; export $var; $relink_command\"\n\t  fi\n\tdone\n\tfunc_quote eval cd \"`pwd`\"\n\tfunc_quote_arg pretty,unquoted \"($func_quote_result; $relink_command)\"\n\trelink_command=$func_quote_arg_unquoted_result\n      fi\n\n      # Only actually do things if not in dry run mode.\n      $opt_dry_run || {\n\t# win32 will think the script is a binary if it has\n\t# a .exe suffix, so we strip it off here.\n\tcase $output in\n\t  *.exe) func_stripname '' '.exe' \"$output\"\n\t         output=$func_stripname_result ;;\n\tesac\n\t# test for cygwin because mv fails w/o .exe extensions\n\tcase $host in\n\t  *cygwin*)\n\t    exeext=.exe\n\t    func_stripname '' '.exe' \"$outputname\"\n\t    outputname=$func_stripname_result ;;\n\t  *) exeext= ;;\n\tesac\n\tcase $host in\n\t  *cygwin* | *mingw* )\n\t    func_dirname_and_basename \"$output\" \"\" \".\"\n\t    output_name=$func_basename_result\n\t    output_path=$func_dirname_result\n\t    cwrappersource=$output_path/$objdir/lt-$output_name.c\n\t    cwrapper=$output_path/$output_name.exe\n\t    $RM $cwrappersource $cwrapper\n\t    trap \"$RM $cwrappersource $cwrapper; exit $EXIT_FAILURE\" 1 2 15\n\n\t    func_emit_cwrapperexe_src > $cwrappersource\n\n\t    # The wrapper executable is built using the $host compiler,\n\t    # because it contains $host paths and files. If cross-\n\t    # compiling, it, like the target executable, must be\n\t    # executed on the $host or under an emulation environment.\n\t    $opt_dry_run || {\n\t      $LTCC $LTCFLAGS -o $cwrapper $cwrappersource\n\t      $STRIP $cwrapper\n\t    }\n\n\t    # Now, create the wrapper script for func_source use:\n\t    func_ltwrapper_scriptname $cwrapper\n\t    $RM $func_ltwrapper_scriptname_result\n\t    trap \"$RM $func_ltwrapper_scriptname_result; exit $EXIT_FAILURE\" 1 2 15\n\t    $opt_dry_run || {\n\t      # note: this script will not be executed, so do not chmod.\n\t      if test \"x$build\" = \"x$host\"; then\n\t\t$cwrapper --lt-dump-script > $func_ltwrapper_scriptname_result\n\t      else\n\t\tfunc_emit_wrapper no > $func_ltwrapper_scriptname_result\n\t      fi\n\t    }\n\t  ;;\n\t  * )\n\t    $RM $output\n\t    trap \"$RM $output; exit $EXIT_FAILURE\" 1 2 15\n\n\t    func_emit_wrapper no > $output\n\t    chmod +x $output\n\t  ;;\n\tesac\n      }\n      exit $EXIT_SUCCESS\n      ;;\n    esac\n\n    # See if we need to build an old-fashioned archive.\n    for oldlib in $oldlibs; do\n\n      case $build_libtool_libs in\n        convenience)\n\t  oldobjs=\"$libobjs_save $symfileobj\"\n\t  addlibs=$convenience\n\t  build_libtool_libs=no\n\t  ;;\n\tmodule)\n\t  oldobjs=$libobjs_save\n\t  addlibs=$old_convenience\n\t  build_libtool_libs=no\n          ;;\n\t*)\n\t  oldobjs=\"$old_deplibs $non_pic_objects\"\n\t  $preload && test -f \"$symfileobj\" \\\n\t    && func_append oldobjs \" $symfileobj\"\n\t  addlibs=$old_convenience\n\t  ;;\n      esac\n\n      if test -n \"$addlibs\"; then\n\tgentop=$output_objdir/${outputname}x\n\tfunc_append generated \" $gentop\"\n\n\tfunc_extract_archives $gentop $addlibs\n\tfunc_append oldobjs \" $func_extract_archives_result\"\n      fi\n\n      # Do each command in the archive commands.\n      if test -n \"$old_archive_from_new_cmds\" && test yes = \"$build_libtool_libs\"; then\n\tcmds=$old_archive_from_new_cmds\n      else\n\n\t# Add any objects from preloaded convenience libraries\n\tif test -n \"$dlprefiles\"; then\n\t  gentop=$output_objdir/${outputname}x\n\t  func_append generated \" $gentop\"\n\n\t  func_extract_archives $gentop $dlprefiles\n\t  func_append oldobjs \" $func_extract_archives_result\"\n\tfi\n\n\t# POSIX demands no paths to be encoded in archives.  We have\n\t# to avoid creating archives with duplicate basenames if we\n\t# might have to extract them afterwards, e.g., when creating a\n\t# static archive out of a convenience library, or when linking\n\t# the entirety of a libtool archive into another (currently\n\t# not supported by libtool).\n\tif (for obj in $oldobjs\n\t    do\n\t      func_basename \"$obj\"\n\t      $ECHO \"$func_basename_result\"\n\t    done | sort | sort -uc >/dev/null 2>&1); then\n\t  :\n\telse\n\t  echo \"copying selected object files to avoid basename conflicts...\"\n\t  gentop=$output_objdir/${outputname}x\n\t  func_append generated \" $gentop\"\n\t  func_mkdir_p \"$gentop\"\n\t  save_oldobjs=$oldobjs\n\t  oldobjs=\n\t  counter=1\n\t  for obj in $save_oldobjs\n\t  do\n\t    func_basename \"$obj\"\n\t    objbase=$func_basename_result\n\t    case \" $oldobjs \" in\n\t    \" \") oldobjs=$obj ;;\n\t    *[\\ /]\"$objbase \"*)\n\t      while :; do\n\t\t# Make sure we don't pick an alternate name that also\n\t\t# overlaps.\n\t\tnewobj=lt$counter-$objbase\n\t\tfunc_arith $counter + 1\n\t\tcounter=$func_arith_result\n\t\tcase \" $oldobjs \" in\n\t\t*[\\ /]\"$newobj \"*) ;;\n\t\t*) if test ! -f \"$gentop/$newobj\"; then break; fi ;;\n\t\tesac\n\t      done\n\t      func_show_eval \"ln $obj $gentop/$newobj || cp $obj $gentop/$newobj\"\n\t      func_append oldobjs \" $gentop/$newobj\"\n\t      ;;\n\t    *) func_append oldobjs \" $obj\" ;;\n\t    esac\n\t  done\n\tfi\n\tfunc_to_tool_file \"$oldlib\" func_convert_file_msys_to_w32\n\ttool_oldlib=$func_to_tool_file_result\n\teval cmds=\\\"$old_archive_cmds\\\"\n\n\tfunc_len \" $cmds\"\n\tlen=$func_len_result\n\tif test \"$len\" -lt \"$max_cmd_len\" || test \"$max_cmd_len\" -le -1; then\n\t  cmds=$old_archive_cmds\n\telif test -n \"$archiver_list_spec\"; then\n\t  func_verbose \"using command file archive linking...\"\n\t  for obj in $oldobjs\n\t  do\n\t    func_to_tool_file \"$obj\"\n\t    $ECHO \"$func_to_tool_file_result\"\n\t  done > $output_objdir/$libname.libcmd\n\t  func_to_tool_file \"$output_objdir/$libname.libcmd\"\n\t  oldobjs=\" $archiver_list_spec$func_to_tool_file_result\"\n\t  cmds=$old_archive_cmds\n\telse\n\t  # the command line is too long to link in one step, link in parts\n\t  func_verbose \"using piecewise archive linking...\"\n\t  save_RANLIB=$RANLIB\n\t  RANLIB=:\n\t  objlist=\n\t  concat_cmds=\n\t  save_oldobjs=$oldobjs\n\t  oldobjs=\n\t  # Is there a better way of finding the last object in the list?\n\t  for obj in $save_oldobjs\n\t  do\n\t    last_oldobj=$obj\n\t  done\n\t  eval test_cmds=\\\"$old_archive_cmds\\\"\n\t  func_len \" $test_cmds\"\n\t  len0=$func_len_result\n\t  len=$len0\n\t  for obj in $save_oldobjs\n\t  do\n\t    func_len \" $obj\"\n\t    func_arith $len + $func_len_result\n\t    len=$func_arith_result\n\t    func_append objlist \" $obj\"\n\t    if test \"$len\" -lt \"$max_cmd_len\"; then\n\t      :\n\t    else\n\t      # the above command should be used before it gets too long\n\t      oldobjs=$objlist\n\t      if test \"$obj\" = \"$last_oldobj\"; then\n\t\tRANLIB=$save_RANLIB\n\t      fi\n\t      test -z \"$concat_cmds\" || concat_cmds=$concat_cmds~\n\t      eval concat_cmds=\\\"\\$concat_cmds$old_archive_cmds\\\"\n\t      objlist=\n\t      len=$len0\n\t    fi\n\t  done\n\t  RANLIB=$save_RANLIB\n\t  oldobjs=$objlist\n\t  if test -z \"$oldobjs\"; then\n\t    eval cmds=\\\"\\$concat_cmds\\\"\n\t  else\n\t    eval cmds=\\\"\\$concat_cmds~\\$old_archive_cmds\\\"\n\t  fi\n\tfi\n      fi\n      func_execute_cmds \"$cmds\" 'exit $?'\n    done\n\n    test -n \"$generated\" && \\\n      func_show_eval \"${RM}r$generated\"\n\n    # Now create the libtool archive.\n    case $output in\n    *.la)\n      old_library=\n      test yes = \"$build_old_libs\" && old_library=$libname.$libext\n      func_verbose \"creating $output\"\n\n      # Preserve any variables that may affect compiler behavior\n      for var in $variables_saved_for_relink; do\n\tif eval test -z \\\"\\${$var+set}\\\"; then\n\t  relink_command=\"{ test -z \\\"\\${$var+set}\\\" || $lt_unset $var || { $var=; export $var; }; }; $relink_command\"\n\telif eval var_value=\\$$var; test -z \"$var_value\"; then\n\t  relink_command=\"$var=; export $var; $relink_command\"\n\telse\n\t  func_quote_arg pretty,unquoted \"$var_value\"\n\t  relink_command=\"$var=$func_quote_arg_unquoted_result; export $var; $relink_command\"\n\tfi\n      done\n      # Quote the link command for shipping.\n      func_quote eval cd \"`pwd`\"\n      relink_command=\"($func_quote_result; $SHELL \\\"$progpath\\\" $preserve_args --mode=relink $libtool_args @inst_prefix_dir@)\"\n      func_quote_arg pretty,unquoted \"$relink_command\"\n      relink_command=$func_quote_arg_unquoted_result\n      if test yes = \"$hardcode_automatic\"; then\n\trelink_command=\n      fi\n\n      # Only create the output if not a dry run.\n      $opt_dry_run || {\n\tfor installed in no yes; do\n\t  if test yes = \"$installed\"; then\n\t    if test -z \"$install_libdir\"; then\n\t      break\n\t    fi\n\t    output=$output_objdir/${outputname}i\n\t    # Replace all uninstalled libtool libraries with the installed ones\n\t    newdependency_libs=\n\t    for deplib in $dependency_libs; do\n\t      case $deplib in\n\t      *.la)\n\t\tfunc_basename \"$deplib\"\n\t\tname=$func_basename_result\n\t\tfunc_resolve_sysroot \"$deplib\"\n\t\teval libdir=`$SED -n -e 's/^libdir=\\(.*\\)$/\\1/p' $func_resolve_sysroot_result`\n\t\ttest -z \"$libdir\" && \\\n\t\t  func_fatal_error \"'$deplib' is not a valid libtool archive\"\n\t\tfunc_append newdependency_libs \" ${lt_sysroot:+=}$libdir/$name\"\n\t\t;;\n\t      -L*)\n\t\tfunc_stripname -L '' \"$deplib\"\n\t\tfunc_replace_sysroot \"$func_stripname_result\"\n\t\tfunc_append newdependency_libs \" -L$func_replace_sysroot_result\"\n\t\t;;\n\t      -R*)\n\t\tfunc_stripname -R '' \"$deplib\"\n\t\tfunc_replace_sysroot \"$func_stripname_result\"\n\t\tfunc_append newdependency_libs \" -R$func_replace_sysroot_result\"\n\t\t;;\n\t      *) func_append newdependency_libs \" $deplib\" ;;\n\t      esac\n\t    done\n\t    dependency_libs=$newdependency_libs\n\t    newdlfiles=\n\n\t    for lib in $dlfiles; do\n\t      case $lib in\n\t      *.la)\n\t        func_basename \"$lib\"\n\t\tname=$func_basename_result\n\t\teval libdir=`$SED -n -e 's/^libdir=\\(.*\\)$/\\1/p' $lib`\n\t\ttest -z \"$libdir\" && \\\n\t\t  func_fatal_error \"'$lib' is not a valid libtool archive\"\n\t\tfunc_append newdlfiles \" ${lt_sysroot:+=}$libdir/$name\"\n\t\t;;\n\t      *) func_append newdlfiles \" $lib\" ;;\n\t      esac\n\t    done\n\t    dlfiles=$newdlfiles\n\t    newdlprefiles=\n\t    for lib in $dlprefiles; do\n\t      case $lib in\n\t      *.la)\n\t\t# Only pass preopened files to the pseudo-archive (for\n\t\t# eventual linking with the app. that links it) if we\n\t\t# didn't already link the preopened objects directly into\n\t\t# the library:\n\t\tfunc_basename \"$lib\"\n\t\tname=$func_basename_result\n\t\teval libdir=`$SED -n -e 's/^libdir=\\(.*\\)$/\\1/p' $lib`\n\t\ttest -z \"$libdir\" && \\\n\t\t  func_fatal_error \"'$lib' is not a valid libtool archive\"\n\t\tfunc_append newdlprefiles \" ${lt_sysroot:+=}$libdir/$name\"\n\t\t;;\n\t      esac\n\t    done\n\t    dlprefiles=$newdlprefiles\n\t  else\n\t    newdlfiles=\n\t    for lib in $dlfiles; do\n\t      case $lib in\n\t\t[\\\\/]* | [A-Za-z]:[\\\\/]*) abs=$lib ;;\n\t\t*) abs=`pwd`\"/$lib\" ;;\n\t      esac\n\t      func_append newdlfiles \" $abs\"\n\t    done\n\t    dlfiles=$newdlfiles\n\t    newdlprefiles=\n\t    for lib in $dlprefiles; do\n\t      case $lib in\n\t\t[\\\\/]* | [A-Za-z]:[\\\\/]*) abs=$lib ;;\n\t\t*) abs=`pwd`\"/$lib\" ;;\n\t      esac\n\t      func_append newdlprefiles \" $abs\"\n\t    done\n\t    dlprefiles=$newdlprefiles\n\t  fi\n\t  $RM $output\n\t  # place dlname in correct position for cygwin\n\t  # In fact, it would be nice if we could use this code for all target\n\t  # systems that can't hard-code library paths into their executables\n\t  # and that have no shared library path variable independent of PATH,\n\t  # but it turns out we can't easily determine that from inspecting\n\t  # libtool variables, so we have to hard-code the OSs to which it\n\t  # applies here; at the moment, that means platforms that use the PE\n\t  # object format with DLL files.  See the long comment at the top of\n\t  # tests/bindir.at for full details.\n\t  tdlname=$dlname\n\t  case $host,$output,$installed,$module,$dlname in\n\t    *cygwin*,*lai,yes,no,*.dll | *mingw*,*lai,yes,no,*.dll | *cegcc*,*lai,yes,no,*.dll)\n\t      # If a -bindir argument was supplied, place the dll there.\n\t      if test -n \"$bindir\"; then\n\t\tfunc_relative_path \"$install_libdir\" \"$bindir\"\n\t\ttdlname=$func_relative_path_result/$dlname\n\t      else\n\t\t# Otherwise fall back on heuristic.\n\t\ttdlname=../bin/$dlname\n\t      fi\n\t      ;;\n\t  esac\n\t  $ECHO > $output \"\\\n# $outputname - a libtool library file\n# Generated by $PROGRAM (GNU $PACKAGE) $VERSION\n#\n# Please DO NOT delete this file!\n# It is necessary for linking the library.\n\n# The name that we can dlopen(3).\ndlname='$tdlname'\n\n# Names of this library.\nlibrary_names='$library_names'\n\n# The name of the static archive.\nold_library='$old_library'\n\n# Linker flags that cannot go in dependency_libs.\ninherited_linker_flags='$new_inherited_linker_flags'\n\n# Libraries that this one depends upon.\ndependency_libs='$dependency_libs'\n\n# Names of additional weak libraries provided by this library\nweak_library_names='$weak_libs'\n\n# Version information for $libname.\ncurrent=$current\nage=$age\nrevision=$revision\n\n# Is this an already installed library?\ninstalled=$installed\n\n# Should we warn about portability when linking against -modules?\nshouldnotlink=$module\n\n# Files to dlopen/dlpreopen\ndlopen='$dlfiles'\ndlpreopen='$dlprefiles'\n\n# Directory that this library needs to be installed in:\nlibdir='$install_libdir'\"\n\t  if test no,yes = \"$installed,$need_relink\"; then\n\t    $ECHO >> $output \"\\\nrelink_command=\\\"$relink_command\\\"\"\n\t  fi\n\tdone\n      }\n\n      # Do a symbolic link so that the libtool archive can be found in\n      # LD_LIBRARY_PATH before the program is installed.\n      func_show_eval '( cd \"$output_objdir\" && $RM \"$outputname\" && $LN_S \"../$outputname\" \"$outputname\" )' 'exit $?'\n      ;;\n    esac\n    exit $EXIT_SUCCESS\n}\n\nif test link = \"$opt_mode\" || test relink = \"$opt_mode\"; then\n  func_mode_link ${1+\"$@\"}\nfi\n\n\n# func_mode_uninstall arg...\nfunc_mode_uninstall ()\n{\n    $debug_cmd\n\n    RM=$nonopt\n    files=\n    rmforce=false\n    exit_status=0\n\n    # This variable tells wrapper scripts just to set variables rather\n    # than running their programs.\n    libtool_install_magic=$magic\n\n    for arg\n    do\n      case $arg in\n      -f) func_append RM \" $arg\"; rmforce=: ;;\n      -*) func_append RM \" $arg\" ;;\n      *) func_append files \" $arg\" ;;\n      esac\n    done\n\n    test -z \"$RM\" && \\\n      func_fatal_help \"you must specify an RM program\"\n\n    rmdirs=\n\n    for file in $files; do\n      func_dirname \"$file\" \"\" \".\"\n      dir=$func_dirname_result\n      if test . = \"$dir\"; then\n\todir=$objdir\n      else\n\todir=$dir/$objdir\n      fi\n      func_basename \"$file\"\n      name=$func_basename_result\n      test uninstall = \"$opt_mode\" && odir=$dir\n\n      # Remember odir for removal later, being careful to avoid duplicates\n      if test clean = \"$opt_mode\"; then\n\tcase \" $rmdirs \" in\n\t  *\" $odir \"*) ;;\n\t  *) func_append rmdirs \" $odir\" ;;\n\tesac\n      fi\n\n      # Don't error if the file doesn't exist and rm -f was used.\n      if { test -L \"$file\"; } >/dev/null 2>&1 ||\n\t { test -h \"$file\"; } >/dev/null 2>&1 ||\n\t test -f \"$file\"; then\n\t:\n      elif test -d \"$file\"; then\n\texit_status=1\n\tcontinue\n      elif $rmforce; then\n\tcontinue\n      fi\n\n      rmfiles=$file\n\n      case $name in\n      *.la)\n\t# Possibly a libtool archive, so verify it.\n\tif func_lalib_p \"$file\"; then\n\t  func_source $dir/$name\n\n\t  # Delete the libtool libraries and symlinks.\n\t  for n in $library_names; do\n\t    func_append rmfiles \" $odir/$n\"\n\t  done\n\t  test -n \"$old_library\" && func_append rmfiles \" $odir/$old_library\"\n\n\t  case $opt_mode in\n\t  clean)\n\t    case \" $library_names \" in\n\t    *\" $dlname \"*) ;;\n\t    *) test -n \"$dlname\" && func_append rmfiles \" $odir/$dlname\" ;;\n\t    esac\n\t    test -n \"$libdir\" && func_append rmfiles \" $odir/$name $odir/${name}i\"\n\t    ;;\n\t  uninstall)\n\t    if test -n \"$library_names\"; then\n\t      # Do each command in the postuninstall commands.\n\t      func_execute_cmds \"$postuninstall_cmds\" '$rmforce || exit_status=1'\n\t    fi\n\n\t    if test -n \"$old_library\"; then\n\t      # Do each command in the old_postuninstall commands.\n\t      func_execute_cmds \"$old_postuninstall_cmds\" '$rmforce || exit_status=1'\n\t    fi\n\t    # FIXME: should reinstall the best remaining shared library.\n\t    ;;\n\t  esac\n\tfi\n\t;;\n\n      *.lo)\n\t# Possibly a libtool object, so verify it.\n\tif func_lalib_p \"$file\"; then\n\n\t  # Read the .lo file\n\t  func_source $dir/$name\n\n\t  # Add PIC object to the list of files to remove.\n\t  if test -n \"$pic_object\" && test none != \"$pic_object\"; then\n\t    func_append rmfiles \" $dir/$pic_object\"\n\t  fi\n\n\t  # Add non-PIC object to the list of files to remove.\n\t  if test -n \"$non_pic_object\" && test none != \"$non_pic_object\"; then\n\t    func_append rmfiles \" $dir/$non_pic_object\"\n\t  fi\n\tfi\n\t;;\n\n      *)\n\tif test clean = \"$opt_mode\"; then\n\t  noexename=$name\n\t  case $file in\n\t  *.exe)\n\t    func_stripname '' '.exe' \"$file\"\n\t    file=$func_stripname_result\n\t    func_stripname '' '.exe' \"$name\"\n\t    noexename=$func_stripname_result\n\t    # $file with .exe has already been added to rmfiles,\n\t    # add $file without .exe\n\t    func_append rmfiles \" $file\"\n\t    ;;\n\t  esac\n\t  # Do a test to see if this is a libtool program.\n\t  if func_ltwrapper_p \"$file\"; then\n\t    if func_ltwrapper_executable_p \"$file\"; then\n\t      func_ltwrapper_scriptname \"$file\"\n\t      relink_command=\n\t      func_source $func_ltwrapper_scriptname_result\n\t      func_append rmfiles \" $func_ltwrapper_scriptname_result\"\n\t    else\n\t      relink_command=\n\t      func_source $dir/$noexename\n\t    fi\n\n\t    # note $name still contains .exe if it was in $file originally\n\t    # as does the version of $file that was added into $rmfiles\n\t    func_append rmfiles \" $odir/$name $odir/${name}S.$objext\"\n\t    if test yes = \"$fast_install\" && test -n \"$relink_command\"; then\n\t      func_append rmfiles \" $odir/lt-$name\"\n\t    fi\n\t    if test \"X$noexename\" != \"X$name\"; then\n\t      func_append rmfiles \" $odir/lt-$noexename.c\"\n\t    fi\n\t  fi\n\tfi\n\t;;\n      esac\n      func_show_eval \"$RM $rmfiles\" 'exit_status=1'\n    done\n\n    # Try to remove the $objdir's in the directories where we deleted files\n    for dir in $rmdirs; do\n      if test -d \"$dir\"; then\n\tfunc_show_eval \"rmdir $dir >/dev/null 2>&1\"\n      fi\n    done\n\n    exit $exit_status\n}\n\nif test uninstall = \"$opt_mode\" || test clean = \"$opt_mode\"; then\n  func_mode_uninstall ${1+\"$@\"}\nfi\n\ntest -z \"$opt_mode\" && {\n  help=$generic_help\n  func_fatal_help \"you must specify a MODE\"\n}\n\ntest -z \"$exec_cmd\" && \\\n  func_fatal_help \"invalid operation mode '$opt_mode'\"\n\nif test -n \"$exec_cmd\"; then\n  eval exec \"$exec_cmd\"\n  exit $EXIT_FAILURE\nfi\n\nexit $exit_status\n\n\n# The TAGs below are defined such that we never get into a situation\n# where we disable both kinds of libraries.  Given conflicting\n# choices, we go for a static library, that is the most portable,\n# since we can't tell whether shared libraries were disabled because\n# the user asked for that or because the platform doesn't support\n# them.  This is particularly important on AIX, because we don't\n# support having both static and shared libraries enabled at the same\n# time on that platform, so we default to a shared-only configuration.\n# If a disable-shared tag is given, we'll fallback to a static-only\n# configuration.  But we'll never go from static-only to shared-only.\n\n# ### BEGIN LIBTOOL TAG CONFIG: disable-shared\nbuild_libtool_libs=no\nbuild_old_libs=yes\n# ### END LIBTOOL TAG CONFIG: disable-shared\n\n# ### BEGIN LIBTOOL TAG CONFIG: disable-static\nbuild_old_libs=`case $build_libtool_libs in yes) echo no;; *) echo yes;; esac`\n# ### END LIBTOOL TAG CONFIG: disable-static\n\n# Local Variables:\n# mode:shell-script\n# sh-indentation:2\n# End:\n"
  },
  {
    "path": "cudd/build-aux/missing",
    "content": "#! /bin/sh\n# Common wrapper for a few potentially missing GNU programs.\n\nscriptversion=2013-10-28.13; # UTC\n\n# Copyright (C) 1996-2013 Free Software Foundation, Inc.\n# Originally written by Fran,cois Pinard <pinard@iro.umontreal.ca>, 1996.\n\n# This program is free software; you can redistribute it and/or modify\n# it under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 2, or (at your option)\n# any later version.\n\n# This program is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n# GNU General Public License for more details.\n\n# You should have received a copy of the GNU General Public License\n# along with this program.  If not, see <http://www.gnu.org/licenses/>.\n\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program that contains a\n# configuration script generated by Autoconf, you may include it under\n# the same distribution terms that you use for the rest of that program.\n\nif test $# -eq 0; then\n  echo 1>&2 \"Try '$0 --help' for more information\"\n  exit 1\nfi\n\ncase $1 in\n\n  --is-lightweight)\n    # Used by our autoconf macros to check whether the available missing\n    # script is modern enough.\n    exit 0\n    ;;\n\n  --run)\n    # Back-compat with the calling convention used by older automake.\n    shift\n    ;;\n\n  -h|--h|--he|--hel|--help)\n    echo \"\\\n$0 [OPTION]... PROGRAM [ARGUMENT]...\n\nRun 'PROGRAM [ARGUMENT]...', returning a proper advice when this fails due\nto PROGRAM being missing or too old.\n\nOptions:\n  -h, --help      display this help and exit\n  -v, --version   output version information and exit\n\nSupported PROGRAM values:\n  aclocal   autoconf  autoheader   autom4te  automake  makeinfo\n  bison     yacc      flex         lex       help2man\n\nVersion suffixes to PROGRAM as well as the prefixes 'gnu-', 'gnu', and\n'g' are ignored when checking the name.\n\nSend bug reports to <bug-automake@gnu.org>.\"\n    exit $?\n    ;;\n\n  -v|--v|--ve|--ver|--vers|--versi|--versio|--version)\n    echo \"missing $scriptversion (GNU Automake)\"\n    exit $?\n    ;;\n\n  -*)\n    echo 1>&2 \"$0: unknown '$1' option\"\n    echo 1>&2 \"Try '$0 --help' for more information\"\n    exit 1\n    ;;\n\nesac\n\n# Run the given program, remember its exit status.\n\"$@\"; st=$?\n\n# If it succeeded, we are done.\ntest $st -eq 0 && exit 0\n\n# Also exit now if we it failed (or wasn't found), and '--version' was\n# passed; such an option is passed most likely to detect whether the\n# program is present and works.\ncase $2 in --version|--help) exit $st;; esac\n\n# Exit code 63 means version mismatch.  This often happens when the user\n# tries to use an ancient version of a tool on a file that requires a\n# minimum version.\nif test $st -eq 63; then\n  msg=\"probably too old\"\nelif test $st -eq 127; then\n  # Program was missing.\n  msg=\"missing on your system\"\nelse\n  # Program was found and executed, but failed.  Give up.\n  exit $st\nfi\n\nperl_URL=http://www.perl.org/\nflex_URL=http://flex.sourceforge.net/\ngnu_software_URL=http://www.gnu.org/software\n\nprogram_details ()\n{\n  case $1 in\n    aclocal|automake)\n      echo \"The '$1' program is part of the GNU Automake package:\"\n      echo \"<$gnu_software_URL/automake>\"\n      echo \"It also requires GNU Autoconf, GNU m4 and Perl in order to run:\"\n      echo \"<$gnu_software_URL/autoconf>\"\n      echo \"<$gnu_software_URL/m4/>\"\n      echo \"<$perl_URL>\"\n      ;;\n    autoconf|autom4te|autoheader)\n      echo \"The '$1' program is part of the GNU Autoconf package:\"\n      echo \"<$gnu_software_URL/autoconf/>\"\n      echo \"It also requires GNU m4 and Perl in order to run:\"\n      echo \"<$gnu_software_URL/m4/>\"\n      echo \"<$perl_URL>\"\n      ;;\n  esac\n}\n\ngive_advice ()\n{\n  # Normalize program name to check for.\n  normalized_program=`echo \"$1\" | sed '\n    s/^gnu-//; t\n    s/^gnu//; t\n    s/^g//; t'`\n\n  printf '%s\\n' \"'$1' is $msg.\"\n\n  configure_deps=\"'configure.ac' or m4 files included by 'configure.ac'\"\n  case $normalized_program in\n    autoconf*)\n      echo \"You should only need it if you modified 'configure.ac',\"\n      echo \"or m4 files included by it.\"\n      program_details 'autoconf'\n      ;;\n    autoheader*)\n      echo \"You should only need it if you modified 'acconfig.h' or\"\n      echo \"$configure_deps.\"\n      program_details 'autoheader'\n      ;;\n    automake*)\n      echo \"You should only need it if you modified 'Makefile.am' or\"\n      echo \"$configure_deps.\"\n      program_details 'automake'\n      ;;\n    aclocal*)\n      echo \"You should only need it if you modified 'acinclude.m4' or\"\n      echo \"$configure_deps.\"\n      program_details 'aclocal'\n      ;;\n   autom4te*)\n      echo \"You might have modified some maintainer files that require\"\n      echo \"the 'autom4te' program to be rebuilt.\"\n      program_details 'autom4te'\n      ;;\n    bison*|yacc*)\n      echo \"You should only need it if you modified a '.y' file.\"\n      echo \"You may want to install the GNU Bison package:\"\n      echo \"<$gnu_software_URL/bison/>\"\n      ;;\n    lex*|flex*)\n      echo \"You should only need it if you modified a '.l' file.\"\n      echo \"You may want to install the Fast Lexical Analyzer package:\"\n      echo \"<$flex_URL>\"\n      ;;\n    help2man*)\n      echo \"You should only need it if you modified a dependency\" \\\n           \"of a man page.\"\n      echo \"You may want to install the GNU Help2man package:\"\n      echo \"<$gnu_software_URL/help2man/>\"\n    ;;\n    makeinfo*)\n      echo \"You should only need it if you modified a '.texi' file, or\"\n      echo \"any other file indirectly affecting the aspect of the manual.\"\n      echo \"You might want to install the Texinfo package:\"\n      echo \"<$gnu_software_URL/texinfo/>\"\n      echo \"The spurious makeinfo call might also be the consequence of\"\n      echo \"using a buggy 'make' (AIX, DU, IRIX), in which case you might\"\n      echo \"want to install GNU make:\"\n      echo \"<$gnu_software_URL/make/>\"\n      ;;\n    *)\n      echo \"You might have modified some files without having the proper\"\n      echo \"tools for further handling them.  Check the 'README' file, it\"\n      echo \"often tells you about the needed prerequisites for installing\"\n      echo \"this package.  You may also peek at any GNU archive site, in\"\n      echo \"case some other package contains this missing '$1' program.\"\n      ;;\n  esac\n}\n\ngive_advice \"$1\" | sed -e '1s/^/WARNING: /' \\\n                       -e '2,$s/^/         /' >&2\n\n# Propagate the correct exit status (expected to be 127 for a program\n# not found, 63 for a program that failed due to version mismatch).\nexit $st\n\n# Local variables:\n# eval: (add-hook 'write-file-hooks 'time-stamp)\n# time-stamp-start: \"scriptversion=\"\n# time-stamp-format: \"%:y-%02m-%02d.%02H\"\n# time-stamp-time-zone: \"UTC\"\n# time-stamp-end: \"; # UTC\"\n# End:\n"
  },
  {
    "path": "cudd/build-aux/tap-driver.sh",
    "content": "#! /bin/sh\n# Copyright (C) 2011-2013 Free Software Foundation, Inc.\n#\n# This program is free software; you can redistribute it and/or modify\n# it under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 2, or (at your option)\n# any later version.\n#\n# This program is distributed in the hope that it will be useful,\n# but WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n# GNU General Public License for more details.\n#\n# You should have received a copy of the GNU General Public License\n# along with this program.  If not, see <http://www.gnu.org/licenses/>.\n\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program that contains a\n# configuration script generated by Autoconf, you may include it under\n# the same distribution terms that you use for the rest of that program.\n\n# This file is maintained in Automake, please report\n# bugs to <bug-automake@gnu.org> or send patches to\n# <automake-patches@gnu.org>.\n\nscriptversion=2013-12-23.17; # UTC\n\n# Make unconditional expansion of undefined variables an error.  This\n# helps a lot in preventing typo-related bugs.\nset -u\n\nme=tap-driver.sh\n\nfatal ()\n{\n  echo \"$me: fatal: $*\" >&2\n  exit 1\n}\n\nusage_error ()\n{\n  echo \"$me: $*\" >&2\n  print_usage >&2\n  exit 2\n}\n\nprint_usage ()\n{\n  cat <<END\nUsage:\n  tap-driver.sh --test-name=NAME --log-file=PATH --trs-file=PATH\n                [--expect-failure={yes|no}] [--color-tests={yes|no}]\n                [--enable-hard-errors={yes|no}] [--ignore-exit]\n                [--diagnostic-string=STRING] [--merge|--no-merge]\n                [--comments|--no-comments] [--] TEST-COMMAND\nThe '--test-name', '-log-file' and '--trs-file' options are mandatory.\nEND\n}\n\n# TODO: better error handling in option parsing (in particular, ensure\n# TODO: $log_file, $trs_file and $test_name are defined).\ntest_name= # Used for reporting.\nlog_file=  # Where to save the result and output of the test script.\ntrs_file=  # Where to save the metadata of the test run.\nexpect_failure=0\ncolor_tests=0\nmerge=0\nignore_exit=0\ncomments=0\ndiag_string='#'\nwhile test $# -gt 0; do\n  case $1 in\n  --help) print_usage; exit $?;;\n  --version) echo \"$me $scriptversion\"; exit $?;;\n  --test-name) test_name=$2; shift;;\n  --log-file) log_file=$2; shift;;\n  --trs-file) trs_file=$2; shift;;\n  --color-tests) color_tests=$2; shift;;\n  --expect-failure) expect_failure=$2; shift;;\n  --enable-hard-errors) shift;; # No-op.\n  --merge) merge=1;;\n  --no-merge) merge=0;;\n  --ignore-exit) ignore_exit=1;;\n  --comments) comments=1;;\n  --no-comments) comments=0;;\n  --diagnostic-string) diag_string=$2; shift;;\n  --) shift; break;;\n  -*) usage_error \"invalid option: '$1'\";;\n  esac\n  shift\ndone\n\ntest $# -gt 0 || usage_error \"missing test command\"\n\ncase $expect_failure in\n  yes) expect_failure=1;;\n    *) expect_failure=0;;\nesac\n\nif test $color_tests = yes; then\n  init_colors='\n    color_map[\"red\"]=\"\u001b[0;31m\" # Red.\n    color_map[\"grn\"]=\"\u001b[0;32m\" # Green.\n    color_map[\"lgn\"]=\"\u001b[1;32m\" # Light green.\n    color_map[\"blu\"]=\"\u001b[1;34m\" # Blue.\n    color_map[\"mgn\"]=\"\u001b[0;35m\" # Magenta.\n    color_map[\"std\"]=\"\u001b[m\"     # No color.\n    color_for_result[\"ERROR\"] = \"mgn\"\n    color_for_result[\"PASS\"]  = \"grn\"\n    color_for_result[\"XPASS\"] = \"red\"\n    color_for_result[\"FAIL\"]  = \"red\"\n    color_for_result[\"XFAIL\"] = \"lgn\"\n    color_for_result[\"SKIP\"]  = \"blu\"'\nelse\n  init_colors=''\nfi\n\n# :; is there to work around a bug in bash 3.2 (and earlier) which\n# does not always set '$?' properly on redirection failure.\n# See the Autoconf manual for more details.\n:;{\n  (\n    # Ignore common signals (in this subshell only!), to avoid potential\n    # problems with Korn shells.  Some Korn shells are known to propagate\n    # to themselves signals that have killed a child process they were\n    # waiting for; this is done at least for SIGINT (and usually only for\n    # it, in truth).  Without the `trap' below, such a behaviour could\n    # cause a premature exit in the current subshell, e.g., in case the\n    # test command it runs gets terminated by a SIGINT.  Thus, the awk\n    # script we are piping into would never seen the exit status it\n    # expects on its last input line (which is displayed below by the\n    # last `echo $?' statement), and would thus die reporting an internal\n    # error.\n    # For more information, see the Autoconf manual and the threads:\n    # <http://lists.gnu.org/archive/html/bug-autoconf/2011-09/msg00004.html>\n    # <http://mail.opensolaris.org/pipermail/ksh93-integration-discuss/2009-February/004121.html>\n    trap : 1 3 2 13 15\n    if test $merge -gt 0; then\n      exec 2>&1\n    else\n      exec 2>&3\n    fi\n    \"$@\"\n    echo $?\n  ) | LC_ALL=C ${AM_TAP_AWK-awk} \\\n        -v me=\"$me\" \\\n        -v test_script_name=\"$test_name\" \\\n        -v log_file=\"$log_file\" \\\n        -v trs_file=\"$trs_file\" \\\n        -v expect_failure=\"$expect_failure\" \\\n        -v merge=\"$merge\" \\\n        -v ignore_exit=\"$ignore_exit\" \\\n        -v comments=\"$comments\" \\\n        -v diag_string=\"$diag_string\" \\\n'\n# TODO: the usages of \"cat >&3\" below could be optimized when using\n#       GNU awk, and/on on systems that supports /dev/fd/.\n\n# Implementation note: in what follows, `result_obj` will be an\n# associative array that (partly) simulates a TAP result object\n# from the `TAP::Parser` perl module.\n\n## ----------- ##\n##  FUNCTIONS  ##\n## ----------- ##\n\nfunction fatal(msg)\n{\n  print me \": \" msg | \"cat >&2\"\n  exit 1\n}\n\nfunction abort(where)\n{\n  fatal(\"internal error \" where)\n}\n\n# Convert a boolean to a \"yes\"/\"no\" string.\nfunction yn(bool)\n{\n  return bool ? \"yes\" : \"no\";\n}\n\nfunction add_test_result(result)\n{\n  if (!test_results_index)\n    test_results_index = 0\n  test_results_list[test_results_index] = result\n  test_results_index += 1\n  test_results_seen[result] = 1;\n}\n\n# Whether the test script should be re-run by \"make recheck\".\nfunction must_recheck()\n{\n  for (k in test_results_seen)\n    if (k != \"XFAIL\" && k != \"PASS\" && k != \"SKIP\")\n      return 1\n  return 0\n}\n\n# Whether the content of the log file associated to this test should\n# be copied into the \"global\" test-suite.log.\nfunction copy_in_global_log()\n{\n  for (k in test_results_seen)\n    if (k != \"PASS\")\n      return 1\n  return 0\n}\n\nfunction get_global_test_result()\n{\n    if (\"ERROR\" in test_results_seen)\n      return \"ERROR\"\n    if (\"FAIL\" in test_results_seen || \"XPASS\" in test_results_seen)\n      return \"FAIL\"\n    all_skipped = 1\n    for (k in test_results_seen)\n      if (k != \"SKIP\")\n        all_skipped = 0\n    if (all_skipped)\n      return \"SKIP\"\n    return \"PASS\";\n}\n\nfunction stringify_result_obj(result_obj)\n{\n  if (result_obj[\"is_unplanned\"] || result_obj[\"number\"] != testno)\n    return \"ERROR\"\n\n  if (plan_seen == LATE_PLAN)\n    return \"ERROR\"\n\n  if (result_obj[\"directive\"] == \"TODO\")\n    return result_obj[\"is_ok\"] ? \"XPASS\" : \"XFAIL\"\n\n  if (result_obj[\"directive\"] == \"SKIP\")\n    return result_obj[\"is_ok\"] ? \"SKIP\" : COOKED_FAIL;\n\n  if (length(result_obj[\"directive\"]))\n      abort(\"in function stringify_result_obj()\")\n\n  return result_obj[\"is_ok\"] ? COOKED_PASS : COOKED_FAIL\n}\n\nfunction decorate_result(result)\n{\n  color_name = color_for_result[result]\n  if (color_name)\n    return color_map[color_name] \"\" result \"\" color_map[\"std\"]\n  # If we are not using colorized output, or if we do not know how\n  # to colorize the given result, we should return it unchanged.\n  return result\n}\n\nfunction report(result, details)\n{\n  if (result ~ /^(X?(PASS|FAIL)|SKIP|ERROR)/)\n    {\n      msg = \": \" test_script_name\n      add_test_result(result)\n    }\n  else if (result == \"#\")\n    {\n      msg = \" \" test_script_name \":\"\n    }\n  else\n    {\n      abort(\"in function report()\")\n    }\n  if (length(details))\n    msg = msg \" \" details\n  # Output on console might be colorized.\n  print decorate_result(result) msg\n  # Log the result in the log file too, to help debugging (this is\n  # especially true when said result is a TAP error or \"Bail out!\").\n  print result msg | \"cat >&3\";\n}\n\nfunction testsuite_error(error_message)\n{\n  report(\"ERROR\", \"- \" error_message)\n}\n\nfunction handle_tap_result()\n{\n  details = result_obj[\"number\"];\n  if (length(result_obj[\"description\"]))\n    details = details \" \" result_obj[\"description\"]\n\n  if (plan_seen == LATE_PLAN)\n    {\n      details = details \" # AFTER LATE PLAN\";\n    }\n  else if (result_obj[\"is_unplanned\"])\n    {\n       details = details \" # UNPLANNED\";\n    }\n  else if (result_obj[\"number\"] != testno)\n    {\n       details = sprintf(\"%s # OUT-OF-ORDER (expecting %d)\",\n                         details, testno);\n    }\n  else if (result_obj[\"directive\"])\n    {\n      details = details \" # \" result_obj[\"directive\"];\n      if (length(result_obj[\"explanation\"]))\n        details = details \" \" result_obj[\"explanation\"]\n    }\n\n  report(stringify_result_obj(result_obj), details)\n}\n\n# `skip_reason` should be empty whenever planned > 0.\nfunction handle_tap_plan(planned, skip_reason)\n{\n  planned += 0 # Avoid getting confused if, say, `planned` is \"00\"\n  if (length(skip_reason) && planned > 0)\n    abort(\"in function handle_tap_plan()\")\n  if (plan_seen)\n    {\n      # Error, only one plan per stream is acceptable.\n      testsuite_error(\"multiple test plans\")\n      return;\n    }\n  planned_tests = planned\n  # The TAP plan can come before or after *all* the TAP results; we speak\n  # respectively of an \"early\" or a \"late\" plan.  If we see the plan line\n  # after at least one TAP result has been seen, assume we have a late\n  # plan; in this case, any further test result seen after the plan will\n  # be flagged as an error.\n  plan_seen = (testno >= 1 ? LATE_PLAN : EARLY_PLAN)\n  # If testno > 0, we have an error (\"too many tests run\") that will be\n  # automatically dealt with later, so do not worry about it here.  If\n  # $plan_seen is true, we have an error due to a repeated plan, and that\n  # has already been dealt with above.  Otherwise, we have a valid \"plan\n  # with SKIP\" specification, and should report it as a particular kind\n  # of SKIP result.\n  if (planned == 0 && testno == 0)\n    {\n      if (length(skip_reason))\n        skip_reason = \"- \"  skip_reason;\n      report(\"SKIP\", skip_reason);\n    }\n}\n\nfunction extract_tap_comment(line)\n{\n  if (index(line, diag_string) == 1)\n    {\n      # Strip leading `diag_string` from `line`.\n      line = substr(line, length(diag_string) + 1)\n      # And strip any leading and trailing whitespace left.\n      sub(\"^[ \\t]*\", \"\", line)\n      sub(\"[ \\t]*$\", \"\", line)\n      # Return what is left (if any).\n      return line;\n    }\n  return \"\";\n}\n\n# When this function is called, we know that line is a TAP result line,\n# so that it matches the (perl) RE \"^(not )?ok\\b\".\nfunction setup_result_obj(line)\n{\n  # Get the result, and remove it from the line.\n  result_obj[\"is_ok\"] = (substr(line, 1, 2) == \"ok\" ? 1 : 0)\n  sub(\"^(not )?ok[ \\t]*\", \"\", line)\n\n  # If the result has an explicit number, get it and strip it; otherwise,\n  # automatically assing the next progresive number to it.\n  if (line ~ /^[0-9]+$/ || line ~ /^[0-9]+[^a-zA-Z0-9_]/)\n    {\n      match(line, \"^[0-9]+\")\n      # The final `+ 0` is to normalize numbers with leading zeros.\n      result_obj[\"number\"] = substr(line, 1, RLENGTH) + 0\n      line = substr(line, RLENGTH + 1)\n    }\n  else\n    {\n      result_obj[\"number\"] = testno\n    }\n\n  if (plan_seen == LATE_PLAN)\n    # No further test results are acceptable after a \"late\" TAP plan\n    # has been seen.\n    result_obj[\"is_unplanned\"] = 1\n  else if (plan_seen && testno > planned_tests)\n    result_obj[\"is_unplanned\"] = 1\n  else\n    result_obj[\"is_unplanned\"] = 0\n\n  # Strip trailing and leading whitespace.\n  sub(\"^[ \\t]*\", \"\", line)\n  sub(\"[ \\t]*$\", \"\", line)\n\n  # This will have to be corrected if we have a \"TODO\"/\"SKIP\" directive.\n  result_obj[\"description\"] = line\n  result_obj[\"directive\"] = \"\"\n  result_obj[\"explanation\"] = \"\"\n\n  if (index(line, \"#\") == 0)\n    return # No possible directive, nothing more to do.\n\n  # Directives are case-insensitive.\n  rx = \"[ \\t]*#[ \\t]*([tT][oO][dD][oO]|[sS][kK][iI][pP])[ \\t]*\"\n\n  # See whether we have the directive, and if yes, where.\n  pos = match(line, rx \"$\")\n  if (!pos)\n    pos = match(line, rx \"[^a-zA-Z0-9_]\")\n\n  # If there was no TAP directive, we have nothing more to do.\n  if (!pos)\n    return\n\n  # Let`s now see if the TAP directive has been escaped.  For example:\n  #  escaped:     ok \\# SKIP\n  #  not escaped: ok \\\\# SKIP\n  #  escaped:     ok \\\\\\\\\\# SKIP\n  #  not escaped: ok \\ # SKIP\n  if (substr(line, pos, 1) == \"#\")\n    {\n      bslash_count = 0\n      for (i = pos; i > 1 && substr(line, i - 1, 1) == \"\\\\\"; i--)\n        bslash_count += 1\n      if (bslash_count % 2)\n        return # Directive was escaped.\n    }\n\n  # Strip the directive and its explanation (if any) from the test\n  # description.\n  result_obj[\"description\"] = substr(line, 1, pos - 1)\n  # Now remove the test description from the line, that has been dealt\n  # with already.\n  line = substr(line, pos)\n  # Strip the directive, and save its value (normalized to upper case).\n  sub(\"^[ \\t]*#[ \\t]*\", \"\", line)\n  result_obj[\"directive\"] = toupper(substr(line, 1, 4))\n  line = substr(line, 5)\n  # Now get the explanation for the directive (if any), with leading\n  # and trailing whitespace removed.\n  sub(\"^[ \\t]*\", \"\", line)\n  sub(\"[ \\t]*$\", \"\", line)\n  result_obj[\"explanation\"] = line\n}\n\nfunction get_test_exit_message(status)\n{\n  if (status == 0)\n    return \"\"\n  if (status !~ /^[1-9][0-9]*$/)\n    abort(\"getting exit status\")\n  if (status < 127)\n    exit_details = \"\"\n  else if (status == 127)\n    exit_details = \" (command not found?)\"\n  else if (status >= 128 && status <= 255)\n    exit_details = sprintf(\" (terminated by signal %d?)\", status - 128)\n  else if (status > 256 && status <= 384)\n    # We used to report an \"abnormal termination\" here, but some Korn\n    # shells, when a child process die due to signal number n, can leave\n    # in $? an exit status of 256+n instead of the more standard 128+n.\n    # Apparently, both behaviours are allowed by POSIX (2008), so be\n    # prepared to handle them both.  See also Austing Group report ID\n    # 0000051 <http://www.austingroupbugs.net/view.php?id=51>\n    exit_details = sprintf(\" (terminated by signal %d?)\", status - 256)\n  else\n    # Never seen in practice.\n    exit_details = \" (abnormal termination)\"\n  return sprintf(\"exited with status %d%s\", status, exit_details)\n}\n\nfunction write_test_results()\n{\n  print \":global-test-result: \" get_global_test_result() > trs_file\n  print \":recheck: \"  yn(must_recheck()) > trs_file\n  print \":copy-in-global-log: \" yn(copy_in_global_log()) > trs_file\n  for (i = 0; i < test_results_index; i += 1)\n    print \":test-result: \" test_results_list[i] > trs_file\n  close(trs_file);\n}\n\nBEGIN {\n\n## ------- ##\n##  SETUP  ##\n## ------- ##\n\n'\"$init_colors\"'\n\n# Properly initialized once the TAP plan is seen.\nplanned_tests = 0\n\nCOOKED_PASS = expect_failure ? \"XPASS\": \"PASS\";\nCOOKED_FAIL = expect_failure ? \"XFAIL\": \"FAIL\";\n\n# Enumeration-like constants to remember which kind of plan (if any)\n# has been seen.  It is important that NO_PLAN evaluates \"false\" as\n# a boolean.\nNO_PLAN = 0\nEARLY_PLAN = 1\nLATE_PLAN = 2\n\ntestno = 0     # Number of test results seen so far.\nbailed_out = 0 # Whether a \"Bail out!\" directive has been seen.\n\n# Whether the TAP plan has been seen or not, and if yes, which kind\n# it is (\"early\" is seen before any test result, \"late\" otherwise).\nplan_seen = NO_PLAN\n\n## --------- ##\n##  PARSING  ##\n## --------- ##\n\nis_first_read = 1\n\nwhile (1)\n  {\n    # Involutions required so that we are able to read the exit status\n    # from the last input line.\n    st = getline\n    if (st < 0) # I/O error.\n      fatal(\"I/O error while reading from input stream\")\n    else if (st == 0) # End-of-input\n      {\n        if (is_first_read)\n          abort(\"in input loop: only one input line\")\n        break\n      }\n    if (is_first_read)\n      {\n        is_first_read = 0\n        nextline = $0\n        continue\n      }\n    else\n      {\n        curline = nextline\n        nextline = $0\n        $0 = curline\n      }\n    # Copy any input line verbatim into the log file.\n    print | \"cat >&3\"\n    # Parsing of TAP input should stop after a \"Bail out!\" directive.\n    if (bailed_out)\n      continue\n\n    # TAP test result.\n    if ($0 ~ /^(not )?ok$/ || $0 ~ /^(not )?ok[^a-zA-Z0-9_]/)\n      {\n        testno += 1\n        setup_result_obj($0)\n        handle_tap_result()\n      }\n    # TAP plan (normal or \"SKIP\" without explanation).\n    else if ($0 ~ /^1\\.\\.[0-9]+[ \\t]*$/)\n      {\n        # The next two lines will put the number of planned tests in $0.\n        sub(\"^1\\\\.\\\\.\", \"\")\n        sub(\"[^0-9]*$\", \"\")\n        handle_tap_plan($0, \"\")\n        continue\n      }\n    # TAP \"SKIP\" plan, with an explanation.\n    else if ($0 ~ /^1\\.\\.0+[ \\t]*#/)\n      {\n        # The next lines will put the skip explanation in $0, stripping\n        # any leading and trailing whitespace.  This is a little more\n        # tricky in truth, since we want to also strip a potential leading\n        # \"SKIP\" string from the message.\n        sub(\"^[^#]*#[ \\t]*(SKIP[: \\t][ \\t]*)?\", \"\")\n        sub(\"[ \\t]*$\", \"\");\n        handle_tap_plan(0, $0)\n      }\n    # \"Bail out!\" magic.\n    # Older versions of prove and TAP::Harness (e.g., 3.17) did not\n    # recognize a \"Bail out!\" directive when preceded by leading\n    # whitespace, but more modern versions (e.g., 3.23) do.  So we\n    # emulate the latter, \"more modern\" behaviour.\n    else if ($0 ~ /^[ \\t]*Bail out!/)\n      {\n        bailed_out = 1\n        # Get the bailout message (if any), with leading and trailing\n        # whitespace stripped.  The message remains stored in `$0`.\n        sub(\"^[ \\t]*Bail out![ \\t]*\", \"\");\n        sub(\"[ \\t]*$\", \"\");\n        # Format the error message for the\n        bailout_message = \"Bail out!\"\n        if (length($0))\n          bailout_message = bailout_message \" \" $0\n        testsuite_error(bailout_message)\n      }\n    # Maybe we have too look for dianogtic comments too.\n    else if (comments != 0)\n      {\n        comment = extract_tap_comment($0);\n        if (length(comment))\n          report(\"#\", comment);\n      }\n  }\n\n## -------- ##\n##  FINISH  ##\n## -------- ##\n\n# A \"Bail out!\" directive should cause us to ignore any following TAP\n# error, as well as a non-zero exit status from the TAP producer.\nif (!bailed_out)\n  {\n    if (!plan_seen)\n      {\n        testsuite_error(\"missing test plan\")\n      }\n    else if (planned_tests != testno)\n      {\n        bad_amount = testno > planned_tests ? \"many\" : \"few\"\n        testsuite_error(sprintf(\"too %s tests run (expected %d, got %d)\",\n                                bad_amount, planned_tests, testno))\n      }\n    if (!ignore_exit)\n      {\n        # Fetch exit status from the last line.\n        exit_message = get_test_exit_message(nextline)\n        if (exit_message)\n          testsuite_error(exit_message)\n      }\n  }\n\nwrite_test_results()\n\nexit 0\n\n} # End of \"BEGIN\" block.\n'\n\n# TODO: document that we consume the file descriptor 3 :-(\n} 3>\"$log_file\"\n\ntest $? -eq 0 || fatal \"I/O or internal error\"\n\n# Local Variables:\n# mode: shell-script\n# sh-indentation: 2\n# eval: (add-hook 'write-file-hooks 'time-stamp)\n# time-stamp-start: \"scriptversion=\"\n# time-stamp-format: \"%:y-%02m-%02d.%02H\"\n# time-stamp-time-zone: \"UTC\"\n# time-stamp-end: \"; # UTC\"\n# End:\n"
  },
  {
    "path": "cudd/clean.sh",
    "content": "#!/bin/sh\n\n# PRISM-customised *un*install script for CUDD\n# Needs to be run from the containing directory\n\nif [ -f Makefile ]; then\n  make uninstall\n  make distclean\nfi\n\nrm -rf include\n"
  },
  {
    "path": "cudd/config.h.in",
    "content": "/* config.h.in.  Generated from configure.ac by autoheader.  */\n\n/* Define if building universal (internal helper macro) */\n#undef AC_APPLE_UNIVERSAL_BUILD\n\n/* Define to 1 if you have the <assert.h> header file. */\n#undef HAVE_ASSERT_H\n\n/* Define to 1 if you have the <dlfcn.h> header file. */\n#undef HAVE_DLFCN_H\n\n/* Define to 1 if you have the <float.h> header file. */\n#undef HAVE_FLOAT_H\n\n/* Define to 1 if you have the 'gethostname' function. */\n#undef HAVE_GETHOSTNAME\n\n/* Define to 1 if you have the 'getrlimit' function. */\n#undef HAVE_GETRLIMIT\n\n/* Define to 1 if you have the 'getrusage' function. */\n#undef HAVE_GETRUSAGE\n\n/* Define to 1 if you have working floating-point infinities */\n#undef HAVE_IEEE_754\n\n/* Define to 1 if you have the <inttypes.h> header file. */\n#undef HAVE_INTTYPES_H\n\n/* Define to 1 if you have the <limits.h> header file. */\n#undef HAVE_LIMITS_H\n\n/* Define to 1 if you have the <math.h> header file. */\n#undef HAVE_MATH_H\n\n/* Define to 1 if your compiler supports enough C++11 */\n#undef HAVE_MODERN_CXX\n\n/* Define to 1 if you have the 'pow' function. */\n#undef HAVE_POW\n\n/* Define to 1 if you have the 'powl' function. */\n#undef HAVE_POWL\n\n/* Define to 1 if the system has the type 'ptrdiff_t'. */\n#undef HAVE_PTRDIFF_T\n\n/* Define to 1 if you have the 'sqrt' function. */\n#undef HAVE_SQRT\n\n/* Define to 1 if you have the <stddef.h> header file. */\n#undef HAVE_STDDEF_H\n\n/* Define to 1 if you have the <stdint.h> header file. */\n#undef HAVE_STDINT_H\n\n/* Define to 1 if you have the <stdio.h> header file. */\n#undef HAVE_STDIO_H\n\n/* Define to 1 if you have the <stdlib.h> header file. */\n#undef HAVE_STDLIB_H\n\n/* Define to 1 if you have the 'strchr' function. */\n#undef HAVE_STRCHR\n\n/* Define to 1 if you have the <strings.h> header file. */\n#undef HAVE_STRINGS_H\n\n/* Define to 1 if you have the <string.h> header file. */\n#undef HAVE_STRING_H\n\n/* Define to 1 if you have the 'strstr' function. */\n#undef HAVE_STRSTR\n\n/* Define to 1 if you have the 'sysconf' function. */\n#undef HAVE_SYSCONF\n\n/* Define to 1 if you have the <sys/resource.h> header file. */\n#undef HAVE_SYS_RESOURCE_H\n\n/* Define to 1 if you have the <sys/stat.h> header file. */\n#undef HAVE_SYS_STAT_H\n\n/* Define to 1 if you have the <sys/times.h> header file. */\n#undef HAVE_SYS_TIMES_H\n\n/* Define to 1 if you have the <sys/time.h> header file. */\n#undef HAVE_SYS_TIME_H\n\n/* Define to 1 if you have the <sys/types.h> header file. */\n#undef HAVE_SYS_TYPES_H\n\n/* Define to 1 if you have the <sys/wait.h> header file. */\n#undef HAVE_SYS_WAIT_H\n\n/* Define to 1 if you have the <unistd.h> header file. */\n#undef HAVE_UNISTD_H\n\n/* Define to 1 if C++ thread header is usable */\n#undef HAVE_WORKING_THREAD\n\n/* Define to 1 if the system has the type '_Bool'. */\n#undef HAVE__BOOL\n\n/* Define to the sub-directory where libtool stores uninstalled libraries. */\n#undef LT_OBJDIR\n\n/* Name of package */\n#undef PACKAGE\n\n/* Define to the address where bug reports for this package should be sent. */\n#undef PACKAGE_BUGREPORT\n\n/* Define to the full name of this package. */\n#undef PACKAGE_NAME\n\n/* Define to the full name and version of this package. */\n#undef PACKAGE_STRING\n\n/* Define to the one symbol short name of this package. */\n#undef PACKAGE_TARNAME\n\n/* Define to the home page for this package. */\n#undef PACKAGE_URL\n\n/* Define to the version of this package. */\n#undef PACKAGE_VERSION\n\n/* The size of 'int', as computed by sizeof. */\n#undef SIZEOF_INT\n\n/* The size of 'long', as computed by sizeof. */\n#undef SIZEOF_LONG\n\n/* The size of 'long double', as computed by sizeof. */\n#undef SIZEOF_LONG_DOUBLE\n\n/* The size of 'void *', as computed by sizeof. */\n#undef SIZEOF_VOID_P\n\n/* Define to 1 if all of the C89 standard headers exist (not just the ones\n   required in a freestanding environment). This macro is provided for\n   backward compatibility; new code need not use it. */\n#undef STDC_HEADERS\n\n/* Define to 1 to use system qsort */\n#undef USE_SYSTEM_QSORT\n\n/* Version number of package */\n#undef VERSION\n\n/* Define WORDS_BIGENDIAN to 1 if your processor stores words with the most\n   significant byte first (like Motorola and SPARC, unlike Intel). */\n#if defined AC_APPLE_UNIVERSAL_BUILD\n# if defined __BIG_ENDIAN__\n#  define WORDS_BIGENDIAN 1\n# endif\n#else\n# ifndef WORDS_BIGENDIAN\n#  undef WORDS_BIGENDIAN\n# endif\n#endif\n\n/* Define for Solaris 2.5.1 so the uint32_t typedef from <sys/synch.h>,\n   <pthread.h>, or <semaphore.h> is not used. If the typedef were allowed, the\n   #define below would cause a syntax error. */\n#undef _UINT32_T\n\n/* Define to 1 to enable C99-compliant printf on MinGW-w64 */\n#undef __USE_MINGW_ANSI_STDIO\n\n/* Define to '__inline__' or '__inline' if that's what the C compiler\n   calls it, or to nothing if 'inline' is not supported under any name.  */\n#ifndef __cplusplus\n#undef inline\n#endif\n\n/* Define as 'unsigned int' if <stddef.h> doesn't define. */\n#undef size_t\n\n/* Define to the type of an unsigned integer type of width exactly 16 bits if\n   such a type exists and the standard includes do not define it. */\n#undef uint16_t\n\n/* Define to the type of an unsigned integer type of width exactly 32 bits if\n   such a type exists and the standard includes do not define it. */\n#undef uint32_t\n"
  },
  {
    "path": "cudd/configure",
    "content": "#! /bin/sh\n# Guess values for system-dependent variables and create Makefiles.\n# Generated by GNU Autoconf 2.72 for cudd 3.0.0.\n#\n# Report bugs to <Fabio@Colorado.EDU>.\n#\n#\n# Copyright (C) 1992-1996, 1998-2017, 2020-2023 Free Software Foundation,\n# Inc.\n#\n#\n# This configure script is free software; the Free Software Foundation\n# gives unlimited permission to copy, distribute and modify it.\n## -------------------- ##\n## M4sh Initialization. ##\n## -------------------- ##\n\n# Be more Bourne compatible\nDUALCASE=1; export DUALCASE # for MKS sh\nif test ${ZSH_VERSION+y} && (emulate sh) >/dev/null 2>&1\nthen :\n  emulate sh\n  NULLCMD=:\n  # Pre-4.2 versions of Zsh do word splitting on ${1+\"$@\"}, which\n  # is contrary to our usage.  Disable this feature.\n  alias -g '${1+\"$@\"}'='\"$@\"'\n  setopt NO_GLOB_SUBST\nelse case e in #(\n  e) case `(set -o) 2>/dev/null` in #(\n  *posix*) :\n    set -o posix ;; #(\n  *) :\n     ;;\nesac ;;\nesac\nfi\n\n\n\n# Reset variables that may have inherited troublesome values from\n# the environment.\n\n# IFS needs to be set, to space, tab, and newline, in precisely that order.\n# (If _AS_PATH_WALK were called with IFS unset, it would have the\n# side effect of setting IFS to empty, thus disabling word splitting.)\n# Quoting is to prevent editors from complaining about space-tab.\nas_nl='\n'\nexport as_nl\nIFS=\" \"\"\t$as_nl\"\n\nPS1='$ '\nPS2='> '\nPS4='+ '\n\n# Ensure predictable behavior from utilities with locale-dependent output.\nLC_ALL=C\nexport LC_ALL\nLANGUAGE=C\nexport LANGUAGE\n\n# We cannot yet rely on \"unset\" to work, but we need these variables\n# to be unset--not just set to an empty or harmless value--now, to\n# avoid bugs in old shells (e.g. pre-3.0 UWIN ksh).  This construct\n# also avoids known problems related to \"unset\" and subshell syntax\n# in other old shells (e.g. bash 2.01 and pdksh 5.2.14).\nfor as_var in BASH_ENV ENV MAIL MAILPATH CDPATH\ndo eval test \\${$as_var+y} \\\n  && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || :\ndone\n\n# Ensure that fds 0, 1, and 2 are open.\nif (exec 3>&0) 2>/dev/null; then :; else exec 0</dev/null; fi\nif (exec 3>&1) 2>/dev/null; then :; else exec 1>/dev/null; fi\nif (exec 3>&2)            ; then :; else exec 2>/dev/null; fi\n\n# The user is always right.\nif ${PATH_SEPARATOR+false} :; then\n  PATH_SEPARATOR=:\n  (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {\n    (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||\n      PATH_SEPARATOR=';'\n  }\nfi\n\n\n# Find who we are.  Look in the path if we contain no directory separator.\nas_myself=\ncase $0 in #((\n  *[\\\\/]* ) as_myself=$0 ;;\n  *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    test -r \"$as_dir$0\" && as_myself=$as_dir$0 && break\n  done\nIFS=$as_save_IFS\n\n     ;;\nesac\n# We did not find ourselves, most probably we were run as 'sh COMMAND'\n# in which case we are not to be found in the path.\nif test \"x$as_myself\" = x; then\n  as_myself=$0\nfi\nif test ! -f \"$as_myself\"; then\n  printf \"%s\\n\" \"$as_myself: error: cannot find myself; rerun with an absolute file name\" >&2\n  exit 1\nfi\n\n\n# Use a proper internal environment variable to ensure we don't fall\n  # into an infinite loop, continuously re-executing ourselves.\n  if test x\"${_as_can_reexec}\" != xno && test \"x$CONFIG_SHELL\" != x; then\n    _as_can_reexec=no; export _as_can_reexec;\n    # We cannot yet assume a decent shell, so we have to provide a\n# neutralization value for shells without unset; and this also\n# works around shells that cannot unset nonexistent variables.\n# Preserve -v and -x to the replacement shell.\nBASH_ENV=/dev/null\nENV=/dev/null\n(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV\ncase $- in # ((((\n  *v*x* | *x*v* ) as_opts=-vx ;;\n  *v* ) as_opts=-v ;;\n  *x* ) as_opts=-x ;;\n  * ) as_opts= ;;\nesac\nexec $CONFIG_SHELL $as_opts \"$as_myself\" ${1+\"$@\"}\n# Admittedly, this is quite paranoid, since all the known shells bail\n# out after a failed 'exec'.\nprintf \"%s\\n\" \"$0: could not re-execute with $CONFIG_SHELL\" >&2\nexit 255\n  fi\n  # We don't want this to propagate to other subprocesses.\n          { _as_can_reexec=; unset _as_can_reexec;}\nif test \"x$CONFIG_SHELL\" = x; then\n  as_bourne_compatible=\"if test \\${ZSH_VERSION+y} && (emulate sh) >/dev/null 2>&1\nthen :\n  emulate sh\n  NULLCMD=:\n  # Pre-4.2 versions of Zsh do word splitting on \\${1+\\\"\\$@\\\"}, which\n  # is contrary to our usage.  Disable this feature.\n  alias -g '\\${1+\\\"\\$@\\\"}'='\\\"\\$@\\\"'\n  setopt NO_GLOB_SUBST\nelse case e in #(\n  e) case \\`(set -o) 2>/dev/null\\` in #(\n  *posix*) :\n    set -o posix ;; #(\n  *) :\n     ;;\nesac ;;\nesac\nfi\n\"\n  as_required=\"as_fn_return () { (exit \\$1); }\nas_fn_success () { as_fn_return 0; }\nas_fn_failure () { as_fn_return 1; }\nas_fn_ret_success () { return 0; }\nas_fn_ret_failure () { return 1; }\n\nexitcode=0\nas_fn_success || { exitcode=1; echo as_fn_success failed.; }\nas_fn_failure && { exitcode=1; echo as_fn_failure succeeded.; }\nas_fn_ret_success || { exitcode=1; echo as_fn_ret_success failed.; }\nas_fn_ret_failure && { exitcode=1; echo as_fn_ret_failure succeeded.; }\nif ( set x; as_fn_ret_success y && test x = \\\"\\$1\\\" )\nthen :\n\nelse case e in #(\n  e) exitcode=1; echo positional parameters were not saved. ;;\nesac\nfi\ntest x\\$exitcode = x0 || exit 1\nblah=\\$(echo \\$(echo blah))\ntest x\\\"\\$blah\\\" = xblah || exit 1\ntest -x / || exit 1\"\n  as_suggested=\"  as_lineno_1=\";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested\" as_lineno_1a=\\$LINENO\n  as_lineno_2=\";as_suggested=$as_suggested$LINENO;as_suggested=$as_suggested\" as_lineno_2a=\\$LINENO\n  eval 'test \\\"x\\$as_lineno_1'\\$as_run'\\\" != \\\"x\\$as_lineno_2'\\$as_run'\\\" &&\n  test \\\"x\\`expr \\$as_lineno_1'\\$as_run' + 1\\`\\\" = \\\"x\\$as_lineno_2'\\$as_run'\\\"' || exit 1\n\n  test -n \\\"\\${ZSH_VERSION+set}\\${BASH_VERSION+set}\\\" || (\n    ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'\n    ECHO=\\$ECHO\\$ECHO\\$ECHO\\$ECHO\\$ECHO\n    ECHO=\\$ECHO\\$ECHO\\$ECHO\\$ECHO\\$ECHO\\$ECHO\n    PATH=/empty FPATH=/empty; export PATH FPATH\n    test \\\"X\\`printf %s \\$ECHO\\`\\\" = \\\"X\\$ECHO\\\" \\\\\n      || test \\\"X\\`print -r -- \\$ECHO\\`\\\" = \\\"X\\$ECHO\\\" ) || exit 1\ntest \\$(( 1 + 1 )) = 2 || exit 1\"\n  if (eval \"$as_required\") 2>/dev/null\nthen :\n  as_have_required=yes\nelse case e in #(\n  e) as_have_required=no ;;\nesac\nfi\n  if test x$as_have_required = xyes && (eval \"$as_suggested\") 2>/dev/null\nthen :\n\nelse case e in #(\n  e) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nas_found=false\nfor as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n  as_found=:\n  case $as_dir in #(\n\t /*)\n\t   for as_base in sh bash ksh sh5; do\n\t     # Try only shells that exist, to save several forks.\n\t     as_shell=$as_dir$as_base\n\t     if { test -f \"$as_shell\" || test -f \"$as_shell.exe\"; } &&\n\t\t    as_run=a \"$as_shell\" -c \"$as_bourne_compatible\"\"$as_required\" 2>/dev/null\nthen :\n  CONFIG_SHELL=$as_shell as_have_required=yes\n\t\t   if as_run=a \"$as_shell\" -c \"$as_bourne_compatible\"\"$as_suggested\" 2>/dev/null\nthen :\n  break 2\nfi\nfi\n\t   done;;\n       esac\n  as_found=false\ndone\nIFS=$as_save_IFS\nif $as_found\nthen :\n\nelse case e in #(\n  e) if { test -f \"$SHELL\" || test -f \"$SHELL.exe\"; } &&\n\t      as_run=a \"$SHELL\" -c \"$as_bourne_compatible\"\"$as_required\" 2>/dev/null\nthen :\n  CONFIG_SHELL=$SHELL as_have_required=yes\nfi ;;\nesac\nfi\n\n\n      if test \"x$CONFIG_SHELL\" != x\nthen :\n  export CONFIG_SHELL\n             # We cannot yet assume a decent shell, so we have to provide a\n# neutralization value for shells without unset; and this also\n# works around shells that cannot unset nonexistent variables.\n# Preserve -v and -x to the replacement shell.\nBASH_ENV=/dev/null\nENV=/dev/null\n(unset BASH_ENV) >/dev/null 2>&1 && unset BASH_ENV ENV\ncase $- in # ((((\n  *v*x* | *x*v* ) as_opts=-vx ;;\n  *v* ) as_opts=-v ;;\n  *x* ) as_opts=-x ;;\n  * ) as_opts= ;;\nesac\nexec $CONFIG_SHELL $as_opts \"$as_myself\" ${1+\"$@\"}\n# Admittedly, this is quite paranoid, since all the known shells bail\n# out after a failed 'exec'.\nprintf \"%s\\n\" \"$0: could not re-execute with $CONFIG_SHELL\" >&2\nexit 255\nfi\n\n    if test x$as_have_required = xno\nthen :\n  printf \"%s\\n\" \"$0: This script requires a shell more modern than all\"\n  printf \"%s\\n\" \"$0: the shells that I found on your system.\"\n  if test ${ZSH_VERSION+y} ; then\n    printf \"%s\\n\" \"$0: In particular, zsh $ZSH_VERSION has bugs and should\"\n    printf \"%s\\n\" \"$0: be upgraded to zsh 4.3.4 or later.\"\n  else\n    printf \"%s\\n\" \"$0: Please tell bug-autoconf@gnu.org and Fabio@Colorado.EDU\n$0: about your system, including any error possibly output\n$0: before this message. Then install a modern shell, or\n$0: manually run the script under such a shell if you do\n$0: have one.\"\n  fi\n  exit 1\nfi ;;\nesac\nfi\nfi\nSHELL=${CONFIG_SHELL-/bin/sh}\nexport SHELL\n# Unset more variables known to interfere with behavior of common tools.\nCLICOLOR_FORCE= GREP_OPTIONS=\nunset CLICOLOR_FORCE GREP_OPTIONS\n\n## --------------------- ##\n## M4sh Shell Functions. ##\n## --------------------- ##\n# as_fn_unset VAR\n# ---------------\n# Portably unset VAR.\nas_fn_unset ()\n{\n  { eval $1=; unset $1;}\n}\nas_unset=as_fn_unset\n\n\n# as_fn_set_status STATUS\n# -----------------------\n# Set $? to STATUS, without forking.\nas_fn_set_status ()\n{\n  return $1\n} # as_fn_set_status\n\n# as_fn_exit STATUS\n# -----------------\n# Exit the shell with STATUS, even in a \"trap 0\" or \"set -e\" context.\nas_fn_exit ()\n{\n  set +e\n  as_fn_set_status $1\n  exit $1\n} # as_fn_exit\n\n# as_fn_mkdir_p\n# -------------\n# Create \"$as_dir\" as a directory, including parents if necessary.\nas_fn_mkdir_p ()\n{\n\n  case $as_dir in #(\n  -*) as_dir=./$as_dir;;\n  esac\n  test -d \"$as_dir\" || eval $as_mkdir_p || {\n    as_dirs=\n    while :; do\n      case $as_dir in #(\n      *\\'*) as_qdir=`printf \"%s\\n\" \"$as_dir\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"`;; #'(\n      *) as_qdir=$as_dir;;\n      esac\n      as_dirs=\"'$as_qdir' $as_dirs\"\n      as_dir=`$as_dirname -- \"$as_dir\" ||\n$as_expr X\"$as_dir\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$as_dir\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$as_dir\" : 'X\\(//\\)$' \\| \\\n\t X\"$as_dir\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X\"$as_dir\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)[^/].*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`\n      test -d \"$as_dir\" && break\n    done\n    test -z \"$as_dirs\" || eval \"mkdir $as_dirs\"\n  } || test -d \"$as_dir\" || as_fn_error $? \"cannot create directory $as_dir\"\n\n\n} # as_fn_mkdir_p\n\n# as_fn_executable_p FILE\n# -----------------------\n# Test if FILE is an executable regular file.\nas_fn_executable_p ()\n{\n  test -f \"$1\" && test -x \"$1\"\n} # as_fn_executable_p\n# as_fn_append VAR VALUE\n# ----------------------\n# Append the text in VALUE to the end of the definition contained in VAR. Take\n# advantage of any shell optimizations that allow amortized linear growth over\n# repeated appends, instead of the typical quadratic growth present in naive\n# implementations.\nif (eval \"as_var=1; as_var+=2; test x\\$as_var = x12\") 2>/dev/null\nthen :\n  eval 'as_fn_append ()\n  {\n    eval $1+=\\$2\n  }'\nelse case e in #(\n  e) as_fn_append ()\n  {\n    eval $1=\\$$1\\$2\n  } ;;\nesac\nfi # as_fn_append\n\n# as_fn_arith ARG...\n# ------------------\n# Perform arithmetic evaluation on the ARGs, and store the result in the\n# global $as_val. Take advantage of shells that can avoid forks. The arguments\n# must be portable across $(()) and expr.\nif (eval \"test \\$(( 1 + 1 )) = 2\") 2>/dev/null\nthen :\n  eval 'as_fn_arith ()\n  {\n    as_val=$(( $* ))\n  }'\nelse case e in #(\n  e) as_fn_arith ()\n  {\n    as_val=`expr \"$@\" || test $? -eq 1`\n  } ;;\nesac\nfi # as_fn_arith\n\n\n# as_fn_error STATUS ERROR [LINENO LOG_FD]\n# ----------------------------------------\n# Output \"`basename $0`: error: ERROR\" to stderr. If LINENO and LOG_FD are\n# provided, also output the error to LOG_FD, referencing LINENO. Then exit the\n# script with STATUS, using 1 if that was 0.\nas_fn_error ()\n{\n  as_status=$1; test $as_status -eq 0 && as_status=1\n  if test \"$4\"; then\n    as_lineno=${as_lineno-\"$3\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: $2\" >&$4\n  fi\n  printf \"%s\\n\" \"$as_me: error: $2\" >&2\n  as_fn_exit $as_status\n} # as_fn_error\n\nif expr a : '\\(a\\)' >/dev/null 2>&1 &&\n   test \"X`expr 00001 : '.*\\(...\\)'`\" = X001; then\n  as_expr=expr\nelse\n  as_expr=false\nfi\n\nif (basename -- /) >/dev/null 2>&1 && test \"X`basename -- / 2>&1`\" = \"X/\"; then\n  as_basename=basename\nelse\n  as_basename=false\nfi\n\nif (as_dir=`dirname -- /` && test \"X$as_dir\" = X/) >/dev/null 2>&1; then\n  as_dirname=dirname\nelse\n  as_dirname=false\nfi\n\nas_me=`$as_basename -- \"$0\" ||\n$as_expr X/\"$0\" : '.*/\\([^/][^/]*\\)/*$' \\| \\\n\t X\"$0\" : 'X\\(//\\)$' \\| \\\n\t X\"$0\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X/\"$0\" |\n    sed '/^.*\\/\\([^/][^/]*\\)\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\/\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\/\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`\n\n# Avoid depending upon Character Ranges.\nas_cr_letters='abcdefghijklmnopqrstuvwxyz'\nas_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'\nas_cr_Letters=$as_cr_letters$as_cr_LETTERS\nas_cr_digits='0123456789'\nas_cr_alnum=$as_cr_Letters$as_cr_digits\n\n\n  as_lineno_1=$LINENO as_lineno_1a=$LINENO\n  as_lineno_2=$LINENO as_lineno_2a=$LINENO\n  eval 'test \"x$as_lineno_1'$as_run'\" != \"x$as_lineno_2'$as_run'\" &&\n  test \"x`expr $as_lineno_1'$as_run' + 1`\" = \"x$as_lineno_2'$as_run'\"' || {\n  # Blame Lee E. McMahon (1931-1989) for sed's syntax.  :-)\n  sed -n '\n    p\n    /[$]LINENO/=\n  ' <$as_myself |\n    sed '\n      t clear\n      :clear\n      s/[$]LINENO.*/&-/\n      t lineno\n      b\n      :lineno\n      N\n      :loop\n      s/[$]LINENO\\([^'$as_cr_alnum'_].*\\n\\)\\(.*\\)/\\2\\1\\2/\n      t loop\n      s/-\\n.*//\n    ' >$as_me.lineno &&\n  chmod +x \"$as_me.lineno\" ||\n    { printf \"%s\\n\" \"$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell\" >&2; as_fn_exit 1; }\n\n  # If we had to re-execute with $CONFIG_SHELL, we're ensured to have\n  # already done that, so ensure we don't try to do so again and fall\n  # in an infinite loop.  This has already happened in practice.\n  _as_can_reexec=no; export _as_can_reexec\n  # Don't try to exec as it changes $[0], causing all sort of problems\n  # (the dirname of $[0] is not the place where we might find the\n  # original and so on.  Autoconf is especially sensitive to this).\n  . \"./$as_me.lineno\"\n  # Exit status is that of the last command.\n  exit\n}\n\n\n# Determine whether it's possible to make 'echo' print without a newline.\n# These variables are no longer used directly by Autoconf, but are AC_SUBSTed\n# for compatibility with existing Makefiles.\nECHO_C= ECHO_N= ECHO_T=\ncase `echo -n x` in #(((((\n-n*)\n  case `echo 'xy\\c'` in\n  *c*) ECHO_T='\t';;\t# ECHO_T is single tab character.\n  xy)  ECHO_C='\\c';;\n  *)   echo `echo ksh88 bug on AIX 6.1` > /dev/null\n       ECHO_T='\t';;\n  esac;;\n*)\n  ECHO_N='-n';;\nesac\n\n# For backward compatibility with old third-party macros, we provide\n# the shell variables $as_echo and $as_echo_n.  New code should use\n# AS_ECHO([\"message\"]) and AS_ECHO_N([\"message\"]), respectively.\nas_echo='printf %s\\n'\nas_echo_n='printf %s'\n\nrm -f conf$$ conf$$.exe conf$$.file\nif test -d conf$$.dir; then\n  rm -f conf$$.dir/conf$$.file\nelse\n  rm -f conf$$.dir\n  mkdir conf$$.dir 2>/dev/null\nfi\nif (echo >conf$$.file) 2>/dev/null; then\n  if ln -s conf$$.file conf$$ 2>/dev/null; then\n    as_ln_s='ln -s'\n    # ... but there are two gotchas:\n    # 1) On MSYS, both 'ln -s file dir' and 'ln file dir' fail.\n    # 2) DJGPP < 2.04 has no symlinks; 'ln -s' creates a wrapper executable.\n    # In both cases, we have to default to 'cp -pR'.\n    ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe ||\n      as_ln_s='cp -pR'\n  elif ln conf$$.file conf$$ 2>/dev/null; then\n    as_ln_s=ln\n  else\n    as_ln_s='cp -pR'\n  fi\nelse\n  as_ln_s='cp -pR'\nfi\nrm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file\nrmdir conf$$.dir 2>/dev/null\n\nif mkdir -p . 2>/dev/null; then\n  as_mkdir_p='mkdir -p \"$as_dir\"'\nelse\n  test -d ./-p && rmdir ./-p\n  as_mkdir_p=false\nfi\n\nas_test_x='test -x'\nas_executable_p=as_fn_executable_p\n\n# Sed expression to map a string onto a valid CPP name.\nas_sed_cpp=\"y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g\"\nas_tr_cpp=\"eval sed '$as_sed_cpp'\" # deprecated\n\n# Sed expression to map a string onto a valid variable name.\nas_sed_sh=\"y%*+%pp%;s%[^_$as_cr_alnum]%_%g\"\nas_tr_sh=\"eval sed '$as_sed_sh'\" # deprecated\n\nSHELL=${CONFIG_SHELL-/bin/sh}\n\n\ntest -n \"$DJDIR\" || exec 7<&0 </dev/null\nexec 6>&1\n\n# Name of the host.\n# hostname on some systems (SVR3.2, old GNU/Linux) returns a bogus exit status,\n# so uname gets run too.\nac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q`\n\n#\n# Initializations.\n#\nac_default_prefix=/usr/local\nac_clean_files=\nac_config_libobj_dir=.\nLIBOBJS=\ncross_compiling=no\nsubdirs=\nMFLAGS=\nMAKEFLAGS=\n\n# Identity of this package.\nPACKAGE_NAME='cudd'\nPACKAGE_TARNAME='cudd'\nPACKAGE_VERSION='3.0.0'\nPACKAGE_STRING='cudd 3.0.0'\nPACKAGE_BUGREPORT='Fabio@Colorado.EDU'\nPACKAGE_URL=''\n\n# Factoring default headers for most tests.\nac_includes_default=\"\\\n#include <stddef.h>\n#ifdef HAVE_STDIO_H\n# include <stdio.h>\n#endif\n#ifdef HAVE_STDLIB_H\n# include <stdlib.h>\n#endif\n#ifdef HAVE_STRING_H\n# include <string.h>\n#endif\n#ifdef HAVE_INTTYPES_H\n# include <inttypes.h>\n#endif\n#ifdef HAVE_STDINT_H\n# include <stdint.h>\n#endif\n#ifdef HAVE_STRINGS_H\n# include <strings.h>\n#endif\n#ifdef HAVE_SYS_TYPES_H\n# include <sys/types.h>\n#endif\n#ifdef HAVE_SYS_STAT_H\n# include <sys/stat.h>\n#endif\n#ifdef HAVE_UNISTD_H\n# include <unistd.h>\n#endif\"\n\nac_header_c_list=\nac_unique_file=\"st/st.c\"\nac_subst_vars='am__EXEEXT_FALSE\nam__EXEEXT_TRUE\nLTLIBOBJS\nLIBOBJS\nMINGW64_FALSE\nMINGW64_TRUE\nHAVE_PTHREADS_FALSE\nHAVE_PTHREADS_TRUE\nHAVE_PDFLATEX_FALSE\nHAVE_PDFLATEX_TRUE\nMAKEINDEX\nPDFLATEX\nHAVE_DOXYGEN_FALSE\nHAVE_DOXYGEN_TRUE\nDOXYGEN\nCROSS_COMPILING_FALSE\nCROSS_COMPILING_TRUE\nCXXCPP\nLT_SYS_LIBRARY_PATH\nOTOOL64\nOTOOL\nLIPO\nNMEDIT\nDSYMUTIL\nMANIFEST_TOOL\nRANLIB\nFILECMD\nLN_S\nNM\nac_ct_DUMPBIN\nDUMPBIN\nLD\nFGREP\nEGREP\nGREP\nSED\nLIBTOOL\nOBJDUMP\nDLLTOOL\nAS\nac_ct_AR\nAR\nam__fastdepCXX_FALSE\nam__fastdepCXX_TRUE\nCXXDEPMODE\nac_ct_CXX\nCXXFLAGS\nCXX\nam__fastdepCC_FALSE\nam__fastdepCC_TRUE\nCCDEPMODE\nam__nodep\nAMDEPBACKSLASH\nAMDEP_FALSE\nAMDEP_TRUE\nam__include\nDEPDIR\nOBJEXT\nEXEEXT\nac_ct_CC\nCPPFLAGS\nLDFLAGS\nCFLAGS\nCC\nOBJ_FALSE\nOBJ_TRUE\nDDDMP_FALSE\nDDDMP_TRUE\nAM_BACKSLASH\nAM_DEFAULT_VERBOSITY\nAM_DEFAULT_V\nAM_V\nCSCOPE\nETAGS\nCTAGS\nam__untar\nam__tar\nAMTAR\nam__leading_dot\nSET_MAKE\nAWK\nmkdir_p\nMKDIR_P\nINSTALL_STRIP_PROGRAM\nSTRIP\ninstall_sh\nMAKEINFO\nAUTOHEADER\nAUTOMAKE\nAUTOCONF\nACLOCAL\nVERSION\nPACKAGE\nCYGPATH_W\nam__isrc\nINSTALL_DATA\nINSTALL_SCRIPT\nINSTALL_PROGRAM\nhost_os\nhost_vendor\nhost_cpu\nhost\nbuild_os\nbuild_vendor\nbuild_cpu\nbuild\ntarget_alias\nhost_alias\nbuild_alias\nLIBS\nECHO_T\nECHO_N\nECHO_C\nDEFS\nmandir\nlocaledir\nlibdir\npsdir\npdfdir\ndvidir\nhtmldir\ninfodir\ndocdir\noldincludedir\nincludedir\nrunstatedir\nlocalstatedir\nsharedstatedir\nsysconfdir\ndatadir\ndatarootdir\nlibexecdir\nsbindir\nbindir\nprogram_transform_name\nprefix\nexec_prefix\nPACKAGE_URL\nPACKAGE_BUGREPORT\nPACKAGE_STRING\nPACKAGE_VERSION\nPACKAGE_TARNAME\nPACKAGE_NAME\nPATH_SEPARATOR\nSHELL\nam__quote'\nac_subst_files=''\nac_user_opts='\nenable_option_checking\nenable_silent_rules\nenable_dddmp\nenable_obj\nwith_system_qsort\nenable_dependency_tracking\nenable_shared\nenable_static\nwith_pic\nenable_fast_install\nwith_aix_soname\nwith_gnu_ld\nwith_sysroot\nenable_libtool_lock\n'\n      ac_precious_vars='build_alias\nhost_alias\ntarget_alias\nCC\nCFLAGS\nLDFLAGS\nLIBS\nCPPFLAGS\nCXX\nCXXFLAGS\nCCC\nLT_SYS_LIBRARY_PATH\nCXXCPP'\n\n\n# Initialize some variables set by options.\nac_init_help=\nac_init_version=false\nac_unrecognized_opts=\nac_unrecognized_sep=\n# The variables have the same names as the options, with\n# dashes changed to underlines.\ncache_file=/dev/null\nexec_prefix=NONE\nno_create=\nno_recursion=\nprefix=NONE\nprogram_prefix=NONE\nprogram_suffix=NONE\nprogram_transform_name=s,x,x,\nsilent=\nsite=\nsrcdir=\nverbose=\nx_includes=NONE\nx_libraries=NONE\n\n# Installation directory options.\n# These are left unexpanded so users can \"make install exec_prefix=/foo\"\n# and all the variables that are supposed to be based on exec_prefix\n# by default will actually change.\n# Use braces instead of parens because sh, perl, etc. also accept them.\n# (The list follows the same order as the GNU Coding Standards.)\nbindir='${exec_prefix}/bin'\nsbindir='${exec_prefix}/sbin'\nlibexecdir='${exec_prefix}/libexec'\ndatarootdir='${prefix}/share'\ndatadir='${datarootdir}'\nsysconfdir='${prefix}/etc'\nsharedstatedir='${prefix}/com'\nlocalstatedir='${prefix}/var'\nrunstatedir='${localstatedir}/run'\nincludedir='${prefix}/include'\noldincludedir='/usr/include'\ndocdir='${datarootdir}/doc/${PACKAGE_TARNAME}'\ninfodir='${datarootdir}/info'\nhtmldir='${docdir}'\ndvidir='${docdir}'\npdfdir='${docdir}'\npsdir='${docdir}'\nlibdir='${exec_prefix}/lib'\nlocaledir='${datarootdir}/locale'\nmandir='${datarootdir}/man'\n\nac_prev=\nac_dashdash=\nfor ac_option\ndo\n  # If the previous option needs an argument, assign it.\n  if test -n \"$ac_prev\"; then\n    eval $ac_prev=\\$ac_option\n    ac_prev=\n    continue\n  fi\n\n  case $ac_option in\n  *=?*) ac_optarg=`expr \"X$ac_option\" : '[^=]*=\\(.*\\)'` ;;\n  *=)   ac_optarg= ;;\n  *)    ac_optarg=yes ;;\n  esac\n\n  case $ac_dashdash$ac_option in\n  --)\n    ac_dashdash=yes ;;\n\n  -bindir | --bindir | --bindi | --bind | --bin | --bi)\n    ac_prev=bindir ;;\n  -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*)\n    bindir=$ac_optarg ;;\n\n  -build | --build | --buil | --bui | --bu)\n    ac_prev=build_alias ;;\n  -build=* | --build=* | --buil=* | --bui=* | --bu=*)\n    build_alias=$ac_optarg ;;\n\n  -cache-file | --cache-file | --cache-fil | --cache-fi \\\n  | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c)\n    ac_prev=cache_file ;;\n  -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \\\n  | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*)\n    cache_file=$ac_optarg ;;\n\n  --config-cache | -C)\n    cache_file=config.cache ;;\n\n  -datadir | --datadir | --datadi | --datad)\n    ac_prev=datadir ;;\n  -datadir=* | --datadir=* | --datadi=* | --datad=*)\n    datadir=$ac_optarg ;;\n\n  -datarootdir | --datarootdir | --datarootdi | --datarootd | --dataroot \\\n  | --dataroo | --dataro | --datar)\n    ac_prev=datarootdir ;;\n  -datarootdir=* | --datarootdir=* | --datarootdi=* | --datarootd=* \\\n  | --dataroot=* | --dataroo=* | --dataro=* | --datar=*)\n    datarootdir=$ac_optarg ;;\n\n  -disable-* | --disable-*)\n    ac_useropt=`expr \"x$ac_option\" : 'x-*disable-\\(.*\\)'`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_useropt\" : \".*[^-+._$as_cr_alnum]\" >/dev/null &&\n      as_fn_error $? \"invalid feature name: '$ac_useropt'\"\n    ac_useropt_orig=$ac_useropt\n    ac_useropt=`printf \"%s\\n\" \"$ac_useropt\" | sed 's/[-+.]/_/g'`\n    case $ac_user_opts in\n      *\"\n\"enable_$ac_useropt\"\n\"*) ;;\n      *) ac_unrecognized_opts=\"$ac_unrecognized_opts$ac_unrecognized_sep--disable-$ac_useropt_orig\"\n\t ac_unrecognized_sep=', ';;\n    esac\n    eval enable_$ac_useropt=no ;;\n\n  -docdir | --docdir | --docdi | --doc | --do)\n    ac_prev=docdir ;;\n  -docdir=* | --docdir=* | --docdi=* | --doc=* | --do=*)\n    docdir=$ac_optarg ;;\n\n  -dvidir | --dvidir | --dvidi | --dvid | --dvi | --dv)\n    ac_prev=dvidir ;;\n  -dvidir=* | --dvidir=* | --dvidi=* | --dvid=* | --dvi=* | --dv=*)\n    dvidir=$ac_optarg ;;\n\n  -enable-* | --enable-*)\n    ac_useropt=`expr \"x$ac_option\" : 'x-*enable-\\([^=]*\\)'`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_useropt\" : \".*[^-+._$as_cr_alnum]\" >/dev/null &&\n      as_fn_error $? \"invalid feature name: '$ac_useropt'\"\n    ac_useropt_orig=$ac_useropt\n    ac_useropt=`printf \"%s\\n\" \"$ac_useropt\" | sed 's/[-+.]/_/g'`\n    case $ac_user_opts in\n      *\"\n\"enable_$ac_useropt\"\n\"*) ;;\n      *) ac_unrecognized_opts=\"$ac_unrecognized_opts$ac_unrecognized_sep--enable-$ac_useropt_orig\"\n\t ac_unrecognized_sep=', ';;\n    esac\n    eval enable_$ac_useropt=\\$ac_optarg ;;\n\n  -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \\\n  | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \\\n  | --exec | --exe | --ex)\n    ac_prev=exec_prefix ;;\n  -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \\\n  | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \\\n  | --exec=* | --exe=* | --ex=*)\n    exec_prefix=$ac_optarg ;;\n\n  -gas | --gas | --ga | --g)\n    # Obsolete; use --with-gas.\n    with_gas=yes ;;\n\n  -help | --help | --hel | --he | -h)\n    ac_init_help=long ;;\n  -help=r* | --help=r* | --hel=r* | --he=r* | -hr*)\n    ac_init_help=recursive ;;\n  -help=s* | --help=s* | --hel=s* | --he=s* | -hs*)\n    ac_init_help=short ;;\n\n  -host | --host | --hos | --ho)\n    ac_prev=host_alias ;;\n  -host=* | --host=* | --hos=* | --ho=*)\n    host_alias=$ac_optarg ;;\n\n  -htmldir | --htmldir | --htmldi | --htmld | --html | --htm | --ht)\n    ac_prev=htmldir ;;\n  -htmldir=* | --htmldir=* | --htmldi=* | --htmld=* | --html=* | --htm=* \\\n  | --ht=*)\n    htmldir=$ac_optarg ;;\n\n  -includedir | --includedir | --includedi | --included | --include \\\n  | --includ | --inclu | --incl | --inc)\n    ac_prev=includedir ;;\n  -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \\\n  | --includ=* | --inclu=* | --incl=* | --inc=*)\n    includedir=$ac_optarg ;;\n\n  -infodir | --infodir | --infodi | --infod | --info | --inf)\n    ac_prev=infodir ;;\n  -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*)\n    infodir=$ac_optarg ;;\n\n  -libdir | --libdir | --libdi | --libd)\n    ac_prev=libdir ;;\n  -libdir=* | --libdir=* | --libdi=* | --libd=*)\n    libdir=$ac_optarg ;;\n\n  -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \\\n  | --libexe | --libex | --libe)\n    ac_prev=libexecdir ;;\n  -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \\\n  | --libexe=* | --libex=* | --libe=*)\n    libexecdir=$ac_optarg ;;\n\n  -localedir | --localedir | --localedi | --localed | --locale)\n    ac_prev=localedir ;;\n  -localedir=* | --localedir=* | --localedi=* | --localed=* | --locale=*)\n    localedir=$ac_optarg ;;\n\n  -localstatedir | --localstatedir | --localstatedi | --localstated \\\n  | --localstate | --localstat | --localsta | --localst | --locals)\n    ac_prev=localstatedir ;;\n  -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \\\n  | --localstate=* | --localstat=* | --localsta=* | --localst=* | --locals=*)\n    localstatedir=$ac_optarg ;;\n\n  -mandir | --mandir | --mandi | --mand | --man | --ma | --m)\n    ac_prev=mandir ;;\n  -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*)\n    mandir=$ac_optarg ;;\n\n  -nfp | --nfp | --nf)\n    # Obsolete; use --without-fp.\n    with_fp=no ;;\n\n  -no-create | --no-create | --no-creat | --no-crea | --no-cre \\\n  | --no-cr | --no-c | -n)\n    no_create=yes ;;\n\n  -no-recursion | --no-recursion | --no-recursio | --no-recursi \\\n  | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r)\n    no_recursion=yes ;;\n\n  -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \\\n  | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \\\n  | --oldin | --oldi | --old | --ol | --o)\n    ac_prev=oldincludedir ;;\n  -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \\\n  | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \\\n  | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*)\n    oldincludedir=$ac_optarg ;;\n\n  -prefix | --prefix | --prefi | --pref | --pre | --pr | --p)\n    ac_prev=prefix ;;\n  -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*)\n    prefix=$ac_optarg ;;\n\n  -program-prefix | --program-prefix | --program-prefi | --program-pref \\\n  | --program-pre | --program-pr | --program-p)\n    ac_prev=program_prefix ;;\n  -program-prefix=* | --program-prefix=* | --program-prefi=* \\\n  | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*)\n    program_prefix=$ac_optarg ;;\n\n  -program-suffix | --program-suffix | --program-suffi | --program-suff \\\n  | --program-suf | --program-su | --program-s)\n    ac_prev=program_suffix ;;\n  -program-suffix=* | --program-suffix=* | --program-suffi=* \\\n  | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*)\n    program_suffix=$ac_optarg ;;\n\n  -program-transform-name | --program-transform-name \\\n  | --program-transform-nam | --program-transform-na \\\n  | --program-transform-n | --program-transform- \\\n  | --program-transform | --program-transfor \\\n  | --program-transfo | --program-transf \\\n  | --program-trans | --program-tran \\\n  | --progr-tra | --program-tr | --program-t)\n    ac_prev=program_transform_name ;;\n  -program-transform-name=* | --program-transform-name=* \\\n  | --program-transform-nam=* | --program-transform-na=* \\\n  | --program-transform-n=* | --program-transform-=* \\\n  | --program-transform=* | --program-transfor=* \\\n  | --program-transfo=* | --program-transf=* \\\n  | --program-trans=* | --program-tran=* \\\n  | --progr-tra=* | --program-tr=* | --program-t=*)\n    program_transform_name=$ac_optarg ;;\n\n  -pdfdir | --pdfdir | --pdfdi | --pdfd | --pdf | --pd)\n    ac_prev=pdfdir ;;\n  -pdfdir=* | --pdfdir=* | --pdfdi=* | --pdfd=* | --pdf=* | --pd=*)\n    pdfdir=$ac_optarg ;;\n\n  -psdir | --psdir | --psdi | --psd | --ps)\n    ac_prev=psdir ;;\n  -psdir=* | --psdir=* | --psdi=* | --psd=* | --ps=*)\n    psdir=$ac_optarg ;;\n\n  -q | -quiet | --quiet | --quie | --qui | --qu | --q \\\n  | -silent | --silent | --silen | --sile | --sil)\n    silent=yes ;;\n\n  -runstatedir | --runstatedir | --runstatedi | --runstated \\\n  | --runstate | --runstat | --runsta | --runst | --runs \\\n  | --run | --ru | --r)\n    ac_prev=runstatedir ;;\n  -runstatedir=* | --runstatedir=* | --runstatedi=* | --runstated=* \\\n  | --runstate=* | --runstat=* | --runsta=* | --runst=* | --runs=* \\\n  | --run=* | --ru=* | --r=*)\n    runstatedir=$ac_optarg ;;\n\n  -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb)\n    ac_prev=sbindir ;;\n  -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \\\n  | --sbi=* | --sb=*)\n    sbindir=$ac_optarg ;;\n\n  -sharedstatedir | --sharedstatedir | --sharedstatedi \\\n  | --sharedstated | --sharedstate | --sharedstat | --sharedsta \\\n  | --sharedst | --shareds | --shared | --share | --shar \\\n  | --sha | --sh)\n    ac_prev=sharedstatedir ;;\n  -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \\\n  | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \\\n  | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \\\n  | --sha=* | --sh=*)\n    sharedstatedir=$ac_optarg ;;\n\n  -site | --site | --sit)\n    ac_prev=site ;;\n  -site=* | --site=* | --sit=*)\n    site=$ac_optarg ;;\n\n  -srcdir | --srcdir | --srcdi | --srcd | --src | --sr)\n    ac_prev=srcdir ;;\n  -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*)\n    srcdir=$ac_optarg ;;\n\n  -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \\\n  | --syscon | --sysco | --sysc | --sys | --sy)\n    ac_prev=sysconfdir ;;\n  -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \\\n  | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*)\n    sysconfdir=$ac_optarg ;;\n\n  -target | --target | --targe | --targ | --tar | --ta | --t)\n    ac_prev=target_alias ;;\n  -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*)\n    target_alias=$ac_optarg ;;\n\n  -v | -verbose | --verbose | --verbos | --verbo | --verb)\n    verbose=yes ;;\n\n  -version | --version | --versio | --versi | --vers | -V)\n    ac_init_version=: ;;\n\n  -with-* | --with-*)\n    ac_useropt=`expr \"x$ac_option\" : 'x-*with-\\([^=]*\\)'`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_useropt\" : \".*[^-+._$as_cr_alnum]\" >/dev/null &&\n      as_fn_error $? \"invalid package name: '$ac_useropt'\"\n    ac_useropt_orig=$ac_useropt\n    ac_useropt=`printf \"%s\\n\" \"$ac_useropt\" | sed 's/[-+.]/_/g'`\n    case $ac_user_opts in\n      *\"\n\"with_$ac_useropt\"\n\"*) ;;\n      *) ac_unrecognized_opts=\"$ac_unrecognized_opts$ac_unrecognized_sep--with-$ac_useropt_orig\"\n\t ac_unrecognized_sep=', ';;\n    esac\n    eval with_$ac_useropt=\\$ac_optarg ;;\n\n  -without-* | --without-*)\n    ac_useropt=`expr \"x$ac_option\" : 'x-*without-\\(.*\\)'`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_useropt\" : \".*[^-+._$as_cr_alnum]\" >/dev/null &&\n      as_fn_error $? \"invalid package name: '$ac_useropt'\"\n    ac_useropt_orig=$ac_useropt\n    ac_useropt=`printf \"%s\\n\" \"$ac_useropt\" | sed 's/[-+.]/_/g'`\n    case $ac_user_opts in\n      *\"\n\"with_$ac_useropt\"\n\"*) ;;\n      *) ac_unrecognized_opts=\"$ac_unrecognized_opts$ac_unrecognized_sep--without-$ac_useropt_orig\"\n\t ac_unrecognized_sep=', ';;\n    esac\n    eval with_$ac_useropt=no ;;\n\n  --x)\n    # Obsolete; use --with-x.\n    with_x=yes ;;\n\n  -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \\\n  | --x-incl | --x-inc | --x-in | --x-i)\n    ac_prev=x_includes ;;\n  -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \\\n  | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*)\n    x_includes=$ac_optarg ;;\n\n  -x-libraries | --x-libraries | --x-librarie | --x-librari \\\n  | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l)\n    ac_prev=x_libraries ;;\n  -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \\\n  | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*)\n    x_libraries=$ac_optarg ;;\n\n  -*) as_fn_error $? \"unrecognized option: '$ac_option'\nTry '$0 --help' for more information\"\n    ;;\n\n  *=*)\n    ac_envvar=`expr \"x$ac_option\" : 'x\\([^=]*\\)='`\n    # Reject names that are not valid shell variable names.\n    case $ac_envvar in #(\n      '' | [0-9]* | *[!_$as_cr_alnum]* )\n      as_fn_error $? \"invalid variable name: '$ac_envvar'\" ;;\n    esac\n    eval $ac_envvar=\\$ac_optarg\n    export $ac_envvar ;;\n\n  *)\n    # FIXME: should be removed in autoconf 3.0.\n    printf \"%s\\n\" \"$as_me: WARNING: you should use --build, --host, --target\" >&2\n    expr \"x$ac_option\" : \".*[^-._$as_cr_alnum]\" >/dev/null &&\n      printf \"%s\\n\" \"$as_me: WARNING: invalid host type: $ac_option\" >&2\n    : \"${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}\"\n    ;;\n\n  esac\ndone\n\nif test -n \"$ac_prev\"; then\n  ac_option=--`echo $ac_prev | sed 's/_/-/g'`\n  as_fn_error $? \"missing argument to $ac_option\"\nfi\n\nif test -n \"$ac_unrecognized_opts\"; then\n  case $enable_option_checking in\n    no) ;;\n    fatal) as_fn_error $? \"unrecognized options: $ac_unrecognized_opts\" ;;\n    *)     printf \"%s\\n\" \"$as_me: WARNING: unrecognized options: $ac_unrecognized_opts\" >&2 ;;\n  esac\nfi\n\n# Check all directory arguments for consistency.\nfor ac_var in\texec_prefix prefix bindir sbindir libexecdir datarootdir \\\n\t\tdatadir sysconfdir sharedstatedir localstatedir includedir \\\n\t\toldincludedir docdir infodir htmldir dvidir pdfdir psdir \\\n\t\tlibdir localedir mandir runstatedir\ndo\n  eval ac_val=\\$$ac_var\n  # Remove trailing slashes.\n  case $ac_val in\n    */ )\n      ac_val=`expr \"X$ac_val\" : 'X\\(.*[^/]\\)' \\| \"X$ac_val\" : 'X\\(.*\\)'`\n      eval $ac_var=\\$ac_val;;\n  esac\n  # Be sure to have absolute directory names.\n  case $ac_val in\n    [\\\\/$]* | ?:[\\\\/]* )  continue;;\n    NONE | '' ) case $ac_var in *prefix ) continue;; esac;;\n  esac\n  as_fn_error $? \"expected an absolute directory name for --$ac_var: $ac_val\"\ndone\n\n# There might be people who depend on the old broken behavior: '$host'\n# used to hold the argument of --host etc.\n# FIXME: To remove some day.\nbuild=$build_alias\nhost=$host_alias\ntarget=$target_alias\n\n# FIXME: To remove some day.\nif test \"x$host_alias\" != x; then\n  if test \"x$build_alias\" = x; then\n    cross_compiling=maybe\n  elif test \"x$build_alias\" != \"x$host_alias\"; then\n    cross_compiling=yes\n  fi\nfi\n\nac_tool_prefix=\ntest -n \"$host_alias\" && ac_tool_prefix=$host_alias-\n\ntest \"$silent\" = yes && exec 6>/dev/null\n\n\nac_pwd=`pwd` && test -n \"$ac_pwd\" &&\nac_ls_di=`ls -di .` &&\nac_pwd_ls_di=`cd \"$ac_pwd\" && ls -di .` ||\n  as_fn_error $? \"working directory cannot be determined\"\ntest \"X$ac_ls_di\" = \"X$ac_pwd_ls_di\" ||\n  as_fn_error $? \"pwd does not report name of working directory\"\n\n\n# Find the source files, if location was not specified.\nif test -z \"$srcdir\"; then\n  ac_srcdir_defaulted=yes\n  # Try the directory containing this script, then the parent directory.\n  ac_confdir=`$as_dirname -- \"$as_myself\" ||\n$as_expr X\"$as_myself\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$as_myself\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$as_myself\" : 'X\\(//\\)$' \\| \\\n\t X\"$as_myself\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X\"$as_myself\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)[^/].*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`\n  srcdir=$ac_confdir\n  if test ! -r \"$srcdir/$ac_unique_file\"; then\n    srcdir=..\n  fi\nelse\n  ac_srcdir_defaulted=no\nfi\nif test ! -r \"$srcdir/$ac_unique_file\"; then\n  test \"$ac_srcdir_defaulted\" = yes && srcdir=\"$ac_confdir or ..\"\n  as_fn_error $? \"cannot find sources ($ac_unique_file) in $srcdir\"\nfi\nac_msg=\"sources are in $srcdir, but 'cd $srcdir' does not work\"\nac_abs_confdir=`(\n\tcd \"$srcdir\" && test -r \"./$ac_unique_file\" || as_fn_error $? \"$ac_msg\"\n\tpwd)`\n# When building in place, set srcdir=.\nif test \"$ac_abs_confdir\" = \"$ac_pwd\"; then\n  srcdir=.\nfi\n# Remove unnecessary trailing slashes from srcdir.\n# Double slashes in file names in object file debugging info\n# mess up M-x gdb in Emacs.\ncase $srcdir in\n*/) srcdir=`expr \"X$srcdir\" : 'X\\(.*[^/]\\)' \\| \"X$srcdir\" : 'X\\(.*\\)'`;;\nesac\nfor ac_var in $ac_precious_vars; do\n  eval ac_env_${ac_var}_set=\\${${ac_var}+set}\n  eval ac_env_${ac_var}_value=\\$${ac_var}\n  eval ac_cv_env_${ac_var}_set=\\${${ac_var}+set}\n  eval ac_cv_env_${ac_var}_value=\\$${ac_var}\ndone\n\n#\n# Report the --help message.\n#\nif test \"$ac_init_help\" = \"long\"; then\n  # Omit some internal or obsolete options to make the list less imposing.\n  # This message is too long to be a string in the A/UX 3.1 sh.\n  cat <<_ACEOF\n'configure' configures cudd 3.0.0 to adapt to many kinds of systems.\n\nUsage: $0 [OPTION]... [VAR=VALUE]...\n\nTo assign environment variables (e.g., CC, CFLAGS...), specify them as\nVAR=VALUE.  See below for descriptions of some of the useful variables.\n\nDefaults for the options are specified in brackets.\n\nConfiguration:\n  -h, --help              display this help and exit\n      --help=short        display options specific to this package\n      --help=recursive    display the short help of all the included packages\n  -V, --version           display version information and exit\n  -q, --quiet, --silent   do not print 'checking ...' messages\n      --cache-file=FILE   cache test results in FILE [disabled]\n  -C, --config-cache      alias for '--cache-file=config.cache'\n  -n, --no-create         do not create output files\n      --srcdir=DIR        find the sources in DIR [configure dir or '..']\n\nInstallation directories:\n  --prefix=PREFIX         install architecture-independent files in PREFIX\n                          [$ac_default_prefix]\n  --exec-prefix=EPREFIX   install architecture-dependent files in EPREFIX\n                          [PREFIX]\n\nBy default, 'make install' will install all the files in\n'$ac_default_prefix/bin', '$ac_default_prefix/lib' etc.  You can specify\nan installation prefix other than '$ac_default_prefix' using '--prefix',\nfor instance '--prefix=\\$HOME'.\n\nFor better control, use the options below.\n\nFine tuning of the installation directories:\n  --bindir=DIR            user executables [EPREFIX/bin]\n  --sbindir=DIR           system admin executables [EPREFIX/sbin]\n  --libexecdir=DIR        program executables [EPREFIX/libexec]\n  --sysconfdir=DIR        read-only single-machine data [PREFIX/etc]\n  --sharedstatedir=DIR    modifiable architecture-independent data [PREFIX/com]\n  --localstatedir=DIR     modifiable single-machine data [PREFIX/var]\n  --runstatedir=DIR       modifiable per-process data [LOCALSTATEDIR/run]\n  --libdir=DIR            object code libraries [EPREFIX/lib]\n  --includedir=DIR        C header files [PREFIX/include]\n  --oldincludedir=DIR     C header files for non-gcc [/usr/include]\n  --datarootdir=DIR       read-only arch.-independent data root [PREFIX/share]\n  --datadir=DIR           read-only architecture-independent data [DATAROOTDIR]\n  --infodir=DIR           info documentation [DATAROOTDIR/info]\n  --localedir=DIR         locale-dependent data [DATAROOTDIR/locale]\n  --mandir=DIR            man documentation [DATAROOTDIR/man]\n  --docdir=DIR            documentation root [DATAROOTDIR/doc/cudd]\n  --htmldir=DIR           html documentation [DOCDIR]\n  --dvidir=DIR            dvi documentation [DOCDIR]\n  --pdfdir=DIR            pdf documentation [DOCDIR]\n  --psdir=DIR             ps documentation [DOCDIR]\n_ACEOF\n\n  cat <<\\_ACEOF\n\nProgram names:\n  --program-prefix=PREFIX            prepend PREFIX to installed program names\n  --program-suffix=SUFFIX            append SUFFIX to installed program names\n  --program-transform-name=PROGRAM   run sed PROGRAM on installed program names\n\nSystem types:\n  --build=BUILD     configure for building on BUILD [guessed]\n  --host=HOST       cross-compile to build programs to run on HOST [BUILD]\n_ACEOF\nfi\n\nif test -n \"$ac_init_help\"; then\n  case $ac_init_help in\n     short | recursive ) echo \"Configuration of cudd 3.0.0:\";;\n   esac\n  cat <<\\_ACEOF\n\nOptional Features:\n  --disable-option-checking  ignore unrecognized --enable/--with options\n  --disable-FEATURE       do not include FEATURE (same as --enable-FEATURE=no)\n  --enable-FEATURE[=ARG]  include FEATURE [ARG=yes]\n  --enable-silent-rules   less verbose build output (undo: \"make V=1\")\n  --disable-silent-rules  verbose build output (undo: \"make V=0\")\n  --enable-dddmp          include libdddmp in libcudd\n  --enable-obj            include libobj in libcudd\n  --enable-dependency-tracking\n                          do not reject slow dependency extractors\n  --disable-dependency-tracking\n                          speeds up one-time build\n  --enable-shared[=PKGS]  build shared libraries [default=no]\n  --enable-static[=PKGS]  build static libraries [default=yes]\n  --enable-fast-install[=PKGS]\n                          optimize for fast installation [default=yes]\n  --disable-libtool-lock  avoid locking (might break parallel builds)\n\nOptional Packages:\n  --with-PACKAGE[=ARG]    use PACKAGE [ARG=yes]\n  --without-PACKAGE       do not use PACKAGE (same as --with-PACKAGE=no)\n  --with-system-qsort     use system qsort instead of portable one\n  --with-pic[=PKGS]       try to use only PIC/non-PIC objects [default=use\n                          both]\n  --with-aix-soname=aix|svr4|both\n                          shared library versioning (aka \"SONAME\") variant to\n                          provide on AIX, [default=aix].\n  --with-gnu-ld           assume the C compiler uses GNU ld [default=no]\n  --with-sysroot[=DIR]    Search for dependent libraries within DIR (or the\n                          compiler's sysroot if not specified).\n\nSome influential environment variables:\n  CC          C compiler command\n  CFLAGS      C compiler flags\n  LDFLAGS     linker flags, e.g. -L<lib dir> if you have libraries in a\n              nonstandard directory <lib dir>\n  LIBS        libraries to pass to the linker, e.g. -l<library>\n  CPPFLAGS    (Objective) C/C++ preprocessor flags, e.g. -I<include dir> if\n              you have headers in a nonstandard directory <include dir>\n  CXX         C++ compiler command\n  CXXFLAGS    C++ compiler flags\n  LT_SYS_LIBRARY_PATH\n              User-defined run-time library search path.\n  CXXCPP      C++ preprocessor\n\nUse these variables to override the choices made by 'configure' or to help\nit to find libraries and programs with nonstandard names/locations.\n\nReport bugs to <Fabio@Colorado.EDU>.\n_ACEOF\nac_status=$?\nfi\n\nif test \"$ac_init_help\" = \"recursive\"; then\n  # If there are subdirs, report their specific --help.\n  for ac_dir in : $ac_subdirs_all; do test \"x$ac_dir\" = x: && continue\n    test -d \"$ac_dir\" ||\n      { cd \"$srcdir\" && ac_pwd=`pwd` && srcdir=. && test -d \"$ac_dir\"; } ||\n      continue\n    ac_builddir=.\n\ncase \"$ac_dir\" in\n.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;;\n*)\n  ac_dir_suffix=/`printf \"%s\\n\" \"$ac_dir\" | sed 's|^\\.[\\\\/]||'`\n  # A \"..\" for each directory in $ac_dir_suffix.\n  ac_top_builddir_sub=`printf \"%s\\n\" \"$ac_dir_suffix\" | sed 's|/[^\\\\/]*|/..|g;s|/||'`\n  case $ac_top_builddir_sub in\n  \"\") ac_top_builddir_sub=. ac_top_build_prefix= ;;\n  *)  ac_top_build_prefix=$ac_top_builddir_sub/ ;;\n  esac ;;\nesac\nac_abs_top_builddir=$ac_pwd\nac_abs_builddir=$ac_pwd$ac_dir_suffix\n# for backward compatibility:\nac_top_builddir=$ac_top_build_prefix\n\ncase $srcdir in\n  .)  # We are building in place.\n    ac_srcdir=.\n    ac_top_srcdir=$ac_top_builddir_sub\n    ac_abs_top_srcdir=$ac_pwd ;;\n  [\\\\/]* | ?:[\\\\/]* )  # Absolute name.\n    ac_srcdir=$srcdir$ac_dir_suffix;\n    ac_top_srcdir=$srcdir\n    ac_abs_top_srcdir=$srcdir ;;\n  *) # Relative name.\n    ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix\n    ac_top_srcdir=$ac_top_build_prefix$srcdir\n    ac_abs_top_srcdir=$ac_pwd/$srcdir ;;\nesac\nac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix\n\n    cd \"$ac_dir\" || { ac_status=$?; continue; }\n    # Check for configure.gnu first; this name is used for a wrapper for\n    # Metaconfig's \"Configure\" on case-insensitive file systems.\n    if test -f \"$ac_srcdir/configure.gnu\"; then\n      echo &&\n      $SHELL \"$ac_srcdir/configure.gnu\" --help=recursive\n    elif test -f \"$ac_srcdir/configure\"; then\n      echo &&\n      $SHELL \"$ac_srcdir/configure\" --help=recursive\n    else\n      printf \"%s\\n\" \"$as_me: WARNING: no configuration information is in $ac_dir\" >&2\n    fi || ac_status=$?\n    cd \"$ac_pwd\" || { ac_status=$?; break; }\n  done\nfi\n\ntest -n \"$ac_init_help\" && exit $ac_status\nif $ac_init_version; then\n  cat <<\\_ACEOF\ncudd configure 3.0.0\ngenerated by GNU Autoconf 2.72\n\nCopyright (C) 2023 Free Software Foundation, Inc.\nThis configure script is free software; the Free Software Foundation\ngives unlimited permission to copy, distribute and modify it.\n_ACEOF\n  exit\nfi\n\n## ------------------------ ##\n## Autoconf initialization. ##\n## ------------------------ ##\n\n# ac_fn_c_try_compile LINENO\n# --------------------------\n# Try to compile conftest.$ac_ext, and return whether this succeeded.\nac_fn_c_try_compile ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  rm -f conftest.$ac_objext conftest.beam\n  if { { ac_try=\"$ac_compile\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_compile\") 2>conftest.err\n  ac_status=$?\n  if test -s conftest.err; then\n    grep -v '^ *+' conftest.err >conftest.er1\n    cat conftest.er1 >&5\n    mv -f conftest.er1 conftest.err\n  fi\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && {\n\t test -z \"$ac_c_werror_flag\" ||\n\t test ! -s conftest.err\n       } && test -s conftest.$ac_objext\nthen :\n  ac_retval=0\nelse case e in #(\n  e) printf \"%s\\n\" \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n\tac_retval=1 ;;\nesac\nfi\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n  as_fn_set_status $ac_retval\n\n} # ac_fn_c_try_compile\n\n# ac_fn_cxx_try_compile LINENO\n# ----------------------------\n# Try to compile conftest.$ac_ext, and return whether this succeeded.\nac_fn_cxx_try_compile ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  rm -f conftest.$ac_objext conftest.beam\n  if { { ac_try=\"$ac_compile\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_compile\") 2>conftest.err\n  ac_status=$?\n  if test -s conftest.err; then\n    grep -v '^ *+' conftest.err >conftest.er1\n    cat conftest.er1 >&5\n    mv -f conftest.er1 conftest.err\n  fi\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && {\n\t test -z \"$ac_cxx_werror_flag\" ||\n\t test ! -s conftest.err\n       } && test -s conftest.$ac_objext\nthen :\n  ac_retval=0\nelse case e in #(\n  e) printf \"%s\\n\" \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n\tac_retval=1 ;;\nesac\nfi\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n  as_fn_set_status $ac_retval\n\n} # ac_fn_cxx_try_compile\n\n# ac_fn_c_try_link LINENO\n# -----------------------\n# Try to link conftest.$ac_ext, and return whether this succeeded.\nac_fn_c_try_link ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  rm -f conftest.$ac_objext conftest.beam conftest$ac_exeext\n  if { { ac_try=\"$ac_link\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_link\") 2>conftest.err\n  ac_status=$?\n  if test -s conftest.err; then\n    grep -v '^ *+' conftest.err >conftest.er1\n    cat conftest.er1 >&5\n    mv -f conftest.er1 conftest.err\n  fi\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && {\n\t test -z \"$ac_c_werror_flag\" ||\n\t test ! -s conftest.err\n       } && test -s conftest$ac_exeext && {\n\t test \"$cross_compiling\" = yes ||\n\t test -x conftest$ac_exeext\n       }\nthen :\n  ac_retval=0\nelse case e in #(\n  e) printf \"%s\\n\" \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n\tac_retval=1 ;;\nesac\nfi\n  # Delete the IPA/IPO (Inter Procedural Analysis/Optimization) information\n  # created by the PGI compiler (conftest_ipa8_conftest.oo), as it would\n  # interfere with the next link command; also delete a directory that is\n  # left behind by Apple's compiler.  We do this before executing the actions.\n  rm -rf conftest.dSYM conftest_ipa8_conftest.oo\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n  as_fn_set_status $ac_retval\n\n} # ac_fn_c_try_link\n\n# ac_fn_c_check_header_compile LINENO HEADER VAR INCLUDES\n# -------------------------------------------------------\n# Tests whether HEADER exists and can be compiled using the include files in\n# INCLUDES, setting the cache variable VAR accordingly.\nac_fn_c_check_header_compile ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $2\" >&5\nprintf %s \"checking for $2... \" >&6; }\nif eval test \\${$3+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\n#include <$2>\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  eval \"$3=yes\"\nelse case e in #(\n  e) eval \"$3=no\" ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\neval ac_res=\\$$3\n\t       { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_res\" >&5\nprintf \"%s\\n\" \"$ac_res\" >&6; }\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n\n} # ac_fn_c_check_header_compile\n\n# ac_fn_c_check_func LINENO FUNC VAR\n# ----------------------------------\n# Tests whether FUNC exists, setting the cache variable VAR accordingly\nac_fn_c_check_func ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $2\" >&5\nprintf %s \"checking for $2... \" >&6; }\nif eval test \\${$3+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n/* Define $2 to an innocuous variant, in case <limits.h> declares $2.\n   For example, HP-UX 11i <limits.h> declares gettimeofday.  */\n#define $2 innocuous_$2\n\n/* System header to define __stub macros and hopefully few prototypes,\n   which can conflict with char $2 (void); below.  */\n\n#include <limits.h>\n#undef $2\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar $2 (void);\n/* The GNU C library defines this for functions which it implements\n    to always fail with ENOSYS.  Some functions are actually named\n    something starting with __ and the normal name is an alias.  */\n#if defined __stub_$2 || defined __stub___$2\nchoke me\n#endif\n\nint\nmain (void)\n{\nreturn $2 ();\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  eval \"$3=yes\"\nelse case e in #(\n  e) eval \"$3=no\" ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext ;;\nesac\nfi\neval ac_res=\\$$3\n\t       { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_res\" >&5\nprintf \"%s\\n\" \"$ac_res\" >&6; }\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n\n} # ac_fn_c_check_func\n\n# ac_fn_cxx_try_cpp LINENO\n# ------------------------\n# Try to preprocess conftest.$ac_ext, and return whether this succeeded.\nac_fn_cxx_try_cpp ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  if { { ac_try=\"$ac_cpp conftest.$ac_ext\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_cpp conftest.$ac_ext\") 2>conftest.err\n  ac_status=$?\n  if test -s conftest.err; then\n    grep -v '^ *+' conftest.err >conftest.er1\n    cat conftest.er1 >&5\n    mv -f conftest.er1 conftest.err\n  fi\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } > conftest.i && {\n\t test -z \"$ac_cxx_preproc_warn_flag$ac_cxx_werror_flag\" ||\n\t test ! -s conftest.err\n       }\nthen :\n  ac_retval=0\nelse case e in #(\n  e) printf \"%s\\n\" \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n    ac_retval=1 ;;\nesac\nfi\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n  as_fn_set_status $ac_retval\n\n} # ac_fn_cxx_try_cpp\n\n# ac_fn_cxx_try_link LINENO\n# -------------------------\n# Try to link conftest.$ac_ext, and return whether this succeeded.\nac_fn_cxx_try_link ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  rm -f conftest.$ac_objext conftest.beam conftest$ac_exeext\n  if { { ac_try=\"$ac_link\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_link\") 2>conftest.err\n  ac_status=$?\n  if test -s conftest.err; then\n    grep -v '^ *+' conftest.err >conftest.er1\n    cat conftest.er1 >&5\n    mv -f conftest.er1 conftest.err\n  fi\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && {\n\t test -z \"$ac_cxx_werror_flag\" ||\n\t test ! -s conftest.err\n       } && test -s conftest$ac_exeext && {\n\t test \"$cross_compiling\" = yes ||\n\t test -x conftest$ac_exeext\n       }\nthen :\n  ac_retval=0\nelse case e in #(\n  e) printf \"%s\\n\" \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n\tac_retval=1 ;;\nesac\nfi\n  # Delete the IPA/IPO (Inter Procedural Analysis/Optimization) information\n  # created by the PGI compiler (conftest_ipa8_conftest.oo), as it would\n  # interfere with the next link command; also delete a directory that is\n  # left behind by Apple's compiler.  We do this before executing the actions.\n  rm -rf conftest.dSYM conftest_ipa8_conftest.oo\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n  as_fn_set_status $ac_retval\n\n} # ac_fn_cxx_try_link\n\n# ac_fn_c_try_run LINENO\n# ----------------------\n# Try to run conftest.$ac_ext, and return whether this succeeded. Assumes that\n# executables *can* be run.\nac_fn_c_try_run ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  if { { ac_try=\"$ac_link\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_link\") 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && { ac_try='./conftest$ac_exeext'\n  { { case \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_try\") 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; }\nthen :\n  ac_retval=0\nelse case e in #(\n  e) printf \"%s\\n\" \"$as_me: program exited with status $ac_status\" >&5\n       printf \"%s\\n\" \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n       ac_retval=$ac_status ;;\nesac\nfi\n  rm -rf conftest.dSYM conftest_ipa8_conftest.oo\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n  as_fn_set_status $ac_retval\n\n} # ac_fn_c_try_run\n\n# ac_fn_c_check_type LINENO TYPE VAR INCLUDES\n# -------------------------------------------\n# Tests whether TYPE exists after having included INCLUDES, setting cache\n# variable VAR accordingly.\nac_fn_c_check_type ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $2\" >&5\nprintf %s \"checking for $2... \" >&6; }\nif eval test \\${$3+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) eval \"$3=no\"\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\nint\nmain (void)\n{\nif (sizeof ($2))\n\t return 0;\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\nint\nmain (void)\n{\nif (sizeof (($2)))\n\t    return 0;\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n\nelse case e in #(\n  e) eval \"$3=yes\" ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\neval ac_res=\\$$3\n\t       { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_res\" >&5\nprintf \"%s\\n\" \"$ac_res\" >&6; }\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n\n} # ac_fn_c_check_type\n\n# ac_fn_c_find_uintX_t LINENO BITS VAR\n# ------------------------------------\n# Finds an unsigned integer type with width BITS, setting cache variable VAR\n# accordingly.\nac_fn_c_find_uintX_t ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for uint$2_t\" >&5\nprintf %s \"checking for uint$2_t... \" >&6; }\nif eval test \\${$3+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) eval \"$3=no\"\n     # Order is important - never check a type that is potentially smaller\n     # than half of the expected target width.\n     for ac_type in uint$2_t 'unsigned int' 'unsigned long int' \\\n\t 'unsigned long long int' 'unsigned short int' 'unsigned char'; do\n       cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$ac_includes_default\nint\nmain (void)\n{\nstatic int test_array [1 - 2 * !((($ac_type) -1 >> ($2 / 2 - 1)) >> ($2 / 2 - 1) == 3)];\ntest_array [0] = 0;\nreturn test_array [0];\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  case $ac_type in #(\n  uint$2_t) :\n    eval \"$3=yes\" ;; #(\n  *) :\n    eval \"$3=\\$ac_type\" ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n       if eval test \\\"x\\$\"$3\"\\\" = x\"no\"\nthen :\n\nelse case e in #(\n  e) break ;;\nesac\nfi\n     done ;;\nesac\nfi\neval ac_res=\\$$3\n\t       { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_res\" >&5\nprintf \"%s\\n\" \"$ac_res\" >&6; }\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n\n} # ac_fn_c_find_uintX_t\n\n# ac_fn_c_compute_int LINENO EXPR VAR INCLUDES\n# --------------------------------------------\n# Tries to find the compile-time value of EXPR in a program that includes\n# INCLUDES, setting VAR accordingly. Returns whether the value could be\n# computed\nac_fn_c_compute_int ()\n{\n  as_lineno=${as_lineno-\"$1\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n  if test \"$cross_compiling\" = yes; then\n    # Depending upon the size, compute the lo and hi bounds.\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\nint\nmain (void)\n{\nstatic int test_array [1 - 2 * !(($2) >= 0)];\ntest_array [0] = 0;\nreturn test_array [0];\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_lo=0 ac_mid=0\n  while :; do\n    cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\nint\nmain (void)\n{\nstatic int test_array [1 - 2 * !(($2) <= $ac_mid)];\ntest_array [0] = 0;\nreturn test_array [0];\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_hi=$ac_mid; break\nelse case e in #(\n  e) as_fn_arith $ac_mid + 1 && ac_lo=$as_val\n\t\t\tif test $ac_lo -le $ac_mid; then\n\t\t\t  ac_lo= ac_hi=\n\t\t\t  break\n\t\t\tfi\n\t\t\tas_fn_arith 2 '*' $ac_mid + 1 && ac_mid=$as_val ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n  done\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\nint\nmain (void)\n{\nstatic int test_array [1 - 2 * !(($2) < 0)];\ntest_array [0] = 0;\nreturn test_array [0];\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_hi=-1 ac_mid=-1\n  while :; do\n    cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\nint\nmain (void)\n{\nstatic int test_array [1 - 2 * !(($2) >= $ac_mid)];\ntest_array [0] = 0;\nreturn test_array [0];\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_lo=$ac_mid; break\nelse case e in #(\n  e) as_fn_arith '(' $ac_mid ')' - 1 && ac_hi=$as_val\n\t\t\tif test $ac_mid -le $ac_hi; then\n\t\t\t  ac_lo= ac_hi=\n\t\t\t  break\n\t\t\tfi\n\t\t\tas_fn_arith 2 '*' $ac_mid && ac_mid=$as_val ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n  done\nelse case e in #(\n  e) ac_lo= ac_hi= ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n# Binary search between lo and hi bounds.\nwhile test \"x$ac_lo\" != \"x$ac_hi\"; do\n  as_fn_arith '(' $ac_hi - $ac_lo ')' / 2 + $ac_lo && ac_mid=$as_val\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\nint\nmain (void)\n{\nstatic int test_array [1 - 2 * !(($2) <= $ac_mid)];\ntest_array [0] = 0;\nreturn test_array [0];\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_hi=$ac_mid\nelse case e in #(\n  e) as_fn_arith '(' $ac_mid ')' + 1 && ac_lo=$as_val ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\ndone\ncase $ac_lo in #((\n?*) eval \"$3=\\$ac_lo\"; ac_retval=0 ;;\n'') ac_retval=1 ;;\nesac\n  else\n    cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$4\nstatic long int longval (void) { return $2; }\nstatic unsigned long int ulongval (void) { return $2; }\n#include <stdio.h>\n#include <stdlib.h>\nint\nmain (void)\n{\n\n  FILE *f = fopen (\"conftest.val\", \"w\");\n  if (! f)\n    return 1;\n  if (($2) < 0)\n    {\n      long int i = longval ();\n      if (i != ($2))\n\treturn 1;\n      fprintf (f, \"%ld\", i);\n    }\n  else\n    {\n      unsigned long int i = ulongval ();\n      if (i != ($2))\n\treturn 1;\n      fprintf (f, \"%lu\", i);\n    }\n  /* Do not output a trailing newline, as this causes \\r\\n confusion\n     on some platforms.  */\n  return ferror (f) || fclose (f) != 0;\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_run \"$LINENO\"\nthen :\n  echo >>conftest.val; read $3 <conftest.val; ac_retval=0\nelse case e in #(\n  e) ac_retval=1 ;;\nesac\nfi\nrm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \\\n  conftest.$ac_objext conftest.beam conftest.$ac_ext\nrm -f conftest.val\n\n  fi\n  eval $as_lineno_stack; ${as_lineno_stack:+:} unset as_lineno\n  as_fn_set_status $ac_retval\n\n} # ac_fn_c_compute_int\nac_configure_args_raw=\nfor ac_arg\ndo\n  case $ac_arg in\n  *\\'*)\n    ac_arg=`printf \"%s\\n\" \"$ac_arg\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"` ;;\n  esac\n  as_fn_append ac_configure_args_raw \" '$ac_arg'\"\ndone\n\ncase $ac_configure_args_raw in\n  *$as_nl*)\n    ac_safe_unquote= ;;\n  *)\n    ac_unsafe_z='|&;<>()$`\\\\\"*?[ ''\t' # This string ends in space, tab.\n    ac_unsafe_a=\"$ac_unsafe_z#~\"\n    ac_safe_unquote=\"s/ '\\\\([^$ac_unsafe_a][^$ac_unsafe_z]*\\\\)'/ \\\\1/g\"\n    ac_configure_args_raw=`      printf \"%s\\n\" \"$ac_configure_args_raw\" | sed \"$ac_safe_unquote\"`;;\nesac\n\ncat >config.log <<_ACEOF\nThis file contains any messages produced by compilers while\nrunning configure, to aid debugging if configure makes a mistake.\n\nIt was created by cudd $as_me 3.0.0, which was\ngenerated by GNU Autoconf 2.72.  Invocation command line was\n\n  $ $0$ac_configure_args_raw\n\n_ACEOF\nexec 5>>config.log\n{\ncat <<_ASUNAME\n## --------- ##\n## Platform. ##\n## --------- ##\n\nhostname = `(hostname || uname -n) 2>/dev/null | sed 1q`\nuname -m = `(uname -m) 2>/dev/null || echo unknown`\nuname -r = `(uname -r) 2>/dev/null || echo unknown`\nuname -s = `(uname -s) 2>/dev/null || echo unknown`\nuname -v = `(uname -v) 2>/dev/null || echo unknown`\n\n/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown`\n/bin/uname -X     = `(/bin/uname -X) 2>/dev/null     || echo unknown`\n\n/bin/arch              = `(/bin/arch) 2>/dev/null              || echo unknown`\n/usr/bin/arch -k       = `(/usr/bin/arch -k) 2>/dev/null       || echo unknown`\n/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown`\n/usr/bin/hostinfo      = `(/usr/bin/hostinfo) 2>/dev/null      || echo unknown`\n/bin/machine           = `(/bin/machine) 2>/dev/null           || echo unknown`\n/usr/bin/oslevel       = `(/usr/bin/oslevel) 2>/dev/null       || echo unknown`\n/bin/universe          = `(/bin/universe) 2>/dev/null          || echo unknown`\n\n_ASUNAME\n\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    printf \"%s\\n\" \"PATH: $as_dir\"\n  done\nIFS=$as_save_IFS\n\n} >&5\n\ncat >&5 <<_ACEOF\n\n\n## ----------- ##\n## Core tests. ##\n## ----------- ##\n\n_ACEOF\n\n\n# Keep a trace of the command line.\n# Strip out --no-create and --no-recursion so they do not pile up.\n# Strip out --silent because we don't want to record it for future runs.\n# Also quote any args containing shell meta-characters.\n# Make two passes to allow for proper duplicate-argument suppression.\nac_configure_args=\nac_configure_args0=\nac_configure_args1=\nac_must_keep_next=false\nfor ac_pass in 1 2\ndo\n  for ac_arg\n  do\n    case $ac_arg in\n    -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;;\n    -q | -quiet | --quiet | --quie | --qui | --qu | --q \\\n    | -silent | --silent | --silen | --sile | --sil)\n      continue ;;\n    *\\'*)\n      ac_arg=`printf \"%s\\n\" \"$ac_arg\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"` ;;\n    esac\n    case $ac_pass in\n    1) as_fn_append ac_configure_args0 \" '$ac_arg'\" ;;\n    2)\n      as_fn_append ac_configure_args1 \" '$ac_arg'\"\n      if test $ac_must_keep_next = true; then\n\tac_must_keep_next=false # Got value, back to normal.\n      else\n\tcase $ac_arg in\n\t  *=* | --config-cache | -C | -disable-* | --disable-* \\\n\t  | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \\\n\t  | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \\\n\t  | -with-* | --with-* | -without-* | --without-* | --x)\n\t    case \"$ac_configure_args0 \" in\n\t      \"$ac_configure_args1\"*\" '$ac_arg' \"* ) continue ;;\n\t    esac\n\t    ;;\n\t  -* ) ac_must_keep_next=true ;;\n\tesac\n      fi\n      as_fn_append ac_configure_args \" '$ac_arg'\"\n      ;;\n    esac\n  done\ndone\n{ ac_configure_args0=; unset ac_configure_args0;}\n{ ac_configure_args1=; unset ac_configure_args1;}\n\n# When interrupted or exit'd, cleanup temporary files, and complete\n# config.log.  We remove comments because anyway the quotes in there\n# would cause problems or look ugly.\n# WARNING: Use '\\'' to represent an apostrophe within the trap.\n# WARNING: Do not start the trap code with a newline, due to a FreeBSD 4.0 bug.\ntrap 'exit_status=$?\n  # Sanitize IFS.\n  IFS=\" \"\"\t$as_nl\"\n  # Save into config.log some information that might help in debugging.\n  {\n    echo\n\n    printf \"%s\\n\" \"## ---------------- ##\n## Cache variables. ##\n## ---------------- ##\"\n    echo\n    # The following way of writing the cache mishandles newlines in values,\n(\n  for ac_var in `(set) 2>&1 | sed -n '\\''s/^\\([a-zA-Z_][a-zA-Z0-9_]*\\)=.*/\\1/p'\\''`; do\n    eval ac_val=\\$$ac_var\n    case $ac_val in #(\n    *${as_nl}*)\n      case $ac_var in #(\n      *_cv_*) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: cache variable $ac_var contains a newline\" >&2;} ;;\n      esac\n      case $ac_var in #(\n      _ | IFS | as_nl) ;; #(\n      BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #(\n      *) { eval $ac_var=; unset $ac_var;} ;;\n      esac ;;\n    esac\n  done\n  (set) 2>&1 |\n    case $as_nl`(ac_space='\\'' '\\''; set) 2>&1` in #(\n    *${as_nl}ac_space=\\ *)\n      sed -n \\\n\t\"s/'\\''/'\\''\\\\\\\\'\\'''\\''/g;\n\t  s/^\\\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\\\)=\\\\(.*\\\\)/\\\\1='\\''\\\\2'\\''/p\"\n      ;; #(\n    *)\n      sed -n \"/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p\"\n      ;;\n    esac |\n    sort\n)\n    echo\n\n    printf \"%s\\n\" \"## ----------------- ##\n## Output variables. ##\n## ----------------- ##\"\n    echo\n    for ac_var in $ac_subst_vars\n    do\n      eval ac_val=\\$$ac_var\n      case $ac_val in\n      *\\'\\''*) ac_val=`printf \"%s\\n\" \"$ac_val\" | sed \"s/'\\''/'\\''\\\\\\\\\\\\\\\\'\\'''\\''/g\"`;;\n      esac\n      printf \"%s\\n\" \"$ac_var='\\''$ac_val'\\''\"\n    done | sort\n    echo\n\n    if test -n \"$ac_subst_files\"; then\n      printf \"%s\\n\" \"## ------------------- ##\n## File substitutions. ##\n## ------------------- ##\"\n      echo\n      for ac_var in $ac_subst_files\n      do\n\teval ac_val=\\$$ac_var\n\tcase $ac_val in\n\t*\\'\\''*) ac_val=`printf \"%s\\n\" \"$ac_val\" | sed \"s/'\\''/'\\''\\\\\\\\\\\\\\\\'\\'''\\''/g\"`;;\n\tesac\n\tprintf \"%s\\n\" \"$ac_var='\\''$ac_val'\\''\"\n      done | sort\n      echo\n    fi\n\n    if test -s confdefs.h; then\n      printf \"%s\\n\" \"## ----------- ##\n## confdefs.h. ##\n## ----------- ##\"\n      echo\n      cat confdefs.h\n      echo\n    fi\n    test \"$ac_signal\" != 0 &&\n      printf \"%s\\n\" \"$as_me: caught signal $ac_signal\"\n    printf \"%s\\n\" \"$as_me: exit $exit_status\"\n  } >&5\n  rm -f core *.core core.conftest.* &&\n    rm -f -r conftest* confdefs* conf$$* $ac_clean_files &&\n    exit $exit_status\n' 0\nfor ac_signal in 1 2 13 15; do\n  trap 'ac_signal='$ac_signal'; as_fn_exit 1' $ac_signal\ndone\nac_signal=0\n\n# confdefs.h avoids OS command line length limits that DEFS can exceed.\nrm -f -r conftest* confdefs.h\n\nprintf \"%s\\n\" \"/* confdefs.h */\" > confdefs.h\n\n# Predefined preprocessor variables.\n\nprintf \"%s\\n\" \"#define PACKAGE_NAME \\\"$PACKAGE_NAME\\\"\" >>confdefs.h\n\nprintf \"%s\\n\" \"#define PACKAGE_TARNAME \\\"$PACKAGE_TARNAME\\\"\" >>confdefs.h\n\nprintf \"%s\\n\" \"#define PACKAGE_VERSION \\\"$PACKAGE_VERSION\\\"\" >>confdefs.h\n\nprintf \"%s\\n\" \"#define PACKAGE_STRING \\\"$PACKAGE_STRING\\\"\" >>confdefs.h\n\nprintf \"%s\\n\" \"#define PACKAGE_BUGREPORT \\\"$PACKAGE_BUGREPORT\\\"\" >>confdefs.h\n\nprintf \"%s\\n\" \"#define PACKAGE_URL \\\"$PACKAGE_URL\\\"\" >>confdefs.h\n\n\n# Let the site file select an alternate cache file if it wants to.\n# Prefer an explicitly selected file to automatically selected ones.\nif test -n \"$CONFIG_SITE\"; then\n  ac_site_files=\"$CONFIG_SITE\"\nelif test \"x$prefix\" != xNONE; then\n  ac_site_files=\"$prefix/share/config.site $prefix/etc/config.site\"\nelse\n  ac_site_files=\"$ac_default_prefix/share/config.site $ac_default_prefix/etc/config.site\"\nfi\n\nfor ac_site_file in $ac_site_files\ndo\n  case $ac_site_file in #(\n  */*) :\n     ;; #(\n  *) :\n    ac_site_file=./$ac_site_file ;;\nesac\n  if test -f \"$ac_site_file\" && test -r \"$ac_site_file\"; then\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: loading site script $ac_site_file\" >&5\nprintf \"%s\\n\" \"$as_me: loading site script $ac_site_file\" >&6;}\n    sed 's/^/| /' \"$ac_site_file\" >&5\n    . \"$ac_site_file\" \\\n      || { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error $? \"failed to load site script $ac_site_file\nSee 'config.log' for more details\" \"$LINENO\" 5; }\n  fi\ndone\n\nif test -r \"$cache_file\"; then\n  # Some versions of bash will fail to source /dev/null (special files\n  # actually), so we avoid doing that.  DJGPP emulates it as a regular file.\n  if test /dev/null != \"$cache_file\" && test -f \"$cache_file\"; then\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: loading cache $cache_file\" >&5\nprintf \"%s\\n\" \"$as_me: loading cache $cache_file\" >&6;}\n    case $cache_file in\n      [\\\\/]* | ?:[\\\\/]* ) . \"$cache_file\";;\n      *)                      . \"./$cache_file\";;\n    esac\n  fi\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: creating cache $cache_file\" >&5\nprintf \"%s\\n\" \"$as_me: creating cache $cache_file\" >&6;}\n  >$cache_file\nfi\n\n# Test code for whether the C compiler supports C89 (global declarations)\nac_c_conftest_c89_globals='\n/* Does the compiler advertise C89 conformance?\n   Do not test the value of __STDC__, because some compilers set it to 0\n   while being otherwise adequately conformant. */\n#if !defined __STDC__\n# error \"Compiler does not advertise C89 conformance\"\n#endif\n\n#include <stddef.h>\n#include <stdarg.h>\nstruct stat;\n/* Most of the following tests are stolen from RCS 5.7 src/conf.sh.  */\nstruct buf { int x; };\nstruct buf * (*rcsopen) (struct buf *, struct stat *, int);\nstatic char *e (char **p, int i)\n{\n  return p[i];\n}\nstatic char *f (char * (*g) (char **, int), char **p, ...)\n{\n  char *s;\n  va_list v;\n  va_start (v,p);\n  s = g (p, va_arg (v,int));\n  va_end (v);\n  return s;\n}\n\n/* C89 style stringification. */\n#define noexpand_stringify(a) #a\nconst char *stringified = noexpand_stringify(arbitrary+token=sequence);\n\n/* C89 style token pasting.  Exercises some of the corner cases that\n   e.g. old MSVC gets wrong, but not very hard. */\n#define noexpand_concat(a,b) a##b\n#define expand_concat(a,b) noexpand_concat(a,b)\nextern int vA;\nextern int vbee;\n#define aye A\n#define bee B\nint *pvA = &expand_concat(v,aye);\nint *pvbee = &noexpand_concat(v,bee);\n\n/* OSF 4.0 Compaq cc is some sort of almost-ANSI by default.  It has\n   function prototypes and stuff, but not \\xHH hex character constants.\n   These do not provoke an error unfortunately, instead are silently treated\n   as an \"x\".  The following induces an error, until -std is added to get\n   proper ANSI mode.  Curiously \\x00 != x always comes out true, for an\n   array size at least.  It is necessary to write \\x00 == 0 to get something\n   that is true only with -std.  */\nint osf4_cc_array ['\\''\\x00'\\'' == 0 ? 1 : -1];\n\n/* IBM C 6 for AIX is almost-ANSI by default, but it replaces macro parameters\n   inside strings and character constants.  */\n#define FOO(x) '\\''x'\\''\nint xlc6_cc_array[FOO(a) == '\\''x'\\'' ? 1 : -1];\n\nint test (int i, double x);\nstruct s1 {int (*f) (int a);};\nstruct s2 {int (*f) (double a);};\nint pairnames (int, char **, int *(*)(struct buf *, struct stat *, int),\n               int, int);'\n\n# Test code for whether the C compiler supports C89 (body of main).\nac_c_conftest_c89_main='\nok |= (argc == 0 || f (e, argv, 0) != argv[0] || f (e, argv, 1) != argv[1]);\n'\n\n# Test code for whether the C compiler supports C99 (global declarations)\nac_c_conftest_c99_globals='\n/* Does the compiler advertise C99 conformance? */\n#if !defined __STDC_VERSION__ || __STDC_VERSION__ < 199901L\n# error \"Compiler does not advertise C99 conformance\"\n#endif\n\n// See if C++-style comments work.\n\n#include <stdbool.h>\nextern int puts (const char *);\nextern int printf (const char *, ...);\nextern int dprintf (int, const char *, ...);\nextern void *malloc (size_t);\nextern void free (void *);\n\n// Check varargs macros.  These examples are taken from C99 6.10.3.5.\n// dprintf is used instead of fprintf to avoid needing to declare\n// FILE and stderr.\n#define debug(...) dprintf (2, __VA_ARGS__)\n#define showlist(...) puts (#__VA_ARGS__)\n#define report(test,...) ((test) ? puts (#test) : printf (__VA_ARGS__))\nstatic void\ntest_varargs_macros (void)\n{\n  int x = 1234;\n  int y = 5678;\n  debug (\"Flag\");\n  debug (\"X = %d\\n\", x);\n  showlist (The first, second, and third items.);\n  report (x>y, \"x is %d but y is %d\", x, y);\n}\n\n// Check long long types.\n#define BIG64 18446744073709551615ull\n#define BIG32 4294967295ul\n#define BIG_OK (BIG64 / BIG32 == 4294967297ull && BIG64 % BIG32 == 0)\n#if !BIG_OK\n  #error \"your preprocessor is broken\"\n#endif\n#if BIG_OK\n#else\n  #error \"your preprocessor is broken\"\n#endif\nstatic long long int bignum = -9223372036854775807LL;\nstatic unsigned long long int ubignum = BIG64;\n\nstruct incomplete_array\n{\n  int datasize;\n  double data[];\n};\n\nstruct named_init {\n  int number;\n  const wchar_t *name;\n  double average;\n};\n\ntypedef const char *ccp;\n\nstatic inline int\ntest_restrict (ccp restrict text)\n{\n  // Iterate through items via the restricted pointer.\n  // Also check for declarations in for loops.\n  for (unsigned int i = 0; *(text+i) != '\\''\\0'\\''; ++i)\n    continue;\n  return 0;\n}\n\n// Check varargs and va_copy.\nstatic bool\ntest_varargs (const char *format, ...)\n{\n  va_list args;\n  va_start (args, format);\n  va_list args_copy;\n  va_copy (args_copy, args);\n\n  const char *str = \"\";\n  int number = 0;\n  float fnumber = 0;\n\n  while (*format)\n    {\n      switch (*format++)\n\t{\n\tcase '\\''s'\\'': // string\n\t  str = va_arg (args_copy, const char *);\n\t  break;\n\tcase '\\''d'\\'': // int\n\t  number = va_arg (args_copy, int);\n\t  break;\n\tcase '\\''f'\\'': // float\n\t  fnumber = va_arg (args_copy, double);\n\t  break;\n\tdefault:\n\t  break;\n\t}\n    }\n  va_end (args_copy);\n  va_end (args);\n\n  return *str && number && fnumber;\n}\n'\n\n# Test code for whether the C compiler supports C99 (body of main).\nac_c_conftest_c99_main='\n  // Check bool.\n  _Bool success = false;\n  success |= (argc != 0);\n\n  // Check restrict.\n  if (test_restrict (\"String literal\") == 0)\n    success = true;\n  char *restrict newvar = \"Another string\";\n\n  // Check varargs.\n  success &= test_varargs (\"s, d'\\'' f .\", \"string\", 65, 34.234);\n  test_varargs_macros ();\n\n  // Check flexible array members.\n  struct incomplete_array *ia =\n    malloc (sizeof (struct incomplete_array) + (sizeof (double) * 10));\n  ia->datasize = 10;\n  for (int i = 0; i < ia->datasize; ++i)\n    ia->data[i] = i * 1.234;\n  // Work around memory leak warnings.\n  free (ia);\n\n  // Check named initializers.\n  struct named_init ni = {\n    .number = 34,\n    .name = L\"Test wide string\",\n    .average = 543.34343,\n  };\n\n  ni.number = 58;\n\n  int dynamic_array[ni.number];\n  dynamic_array[0] = argv[0][0];\n  dynamic_array[ni.number - 1] = 543;\n\n  // work around unused variable warnings\n  ok |= (!success || bignum == 0LL || ubignum == 0uLL || newvar[0] == '\\''x'\\''\n\t || dynamic_array[ni.number - 1] != 543);\n'\n\n# Test code for whether the C compiler supports C11 (global declarations)\nac_c_conftest_c11_globals='\n/* Does the compiler advertise C11 conformance? */\n#if !defined __STDC_VERSION__ || __STDC_VERSION__ < 201112L\n# error \"Compiler does not advertise C11 conformance\"\n#endif\n\n// Check _Alignas.\nchar _Alignas (double) aligned_as_double;\nchar _Alignas (0) no_special_alignment;\nextern char aligned_as_int;\nchar _Alignas (0) _Alignas (int) aligned_as_int;\n\n// Check _Alignof.\nenum\n{\n  int_alignment = _Alignof (int),\n  int_array_alignment = _Alignof (int[100]),\n  char_alignment = _Alignof (char)\n};\n_Static_assert (0 < -_Alignof (int), \"_Alignof is signed\");\n\n// Check _Noreturn.\nint _Noreturn does_not_return (void) { for (;;) continue; }\n\n// Check _Static_assert.\nstruct test_static_assert\n{\n  int x;\n  _Static_assert (sizeof (int) <= sizeof (long int),\n                  \"_Static_assert does not work in struct\");\n  long int y;\n};\n\n// Check UTF-8 literals.\n#define u8 syntax error!\nchar const utf8_literal[] = u8\"happens to be ASCII\" \"another string\";\n\n// Check duplicate typedefs.\ntypedef long *long_ptr;\ntypedef long int *long_ptr;\ntypedef long_ptr long_ptr;\n\n// Anonymous structures and unions -- taken from C11 6.7.2.1 Example 1.\nstruct anonymous\n{\n  union {\n    struct { int i; int j; };\n    struct { int k; long int l; } w;\n  };\n  int m;\n} v1;\n'\n\n# Test code for whether the C compiler supports C11 (body of main).\nac_c_conftest_c11_main='\n  _Static_assert ((offsetof (struct anonymous, i)\n\t\t   == offsetof (struct anonymous, w.k)),\n\t\t  \"Anonymous union alignment botch\");\n  v1.i = 2;\n  v1.w.k = 5;\n  ok |= v1.i != 5;\n'\n\n# Test code for whether the C compiler supports C11 (complete).\nac_c_conftest_c11_program=\"${ac_c_conftest_c89_globals}\n${ac_c_conftest_c99_globals}\n${ac_c_conftest_c11_globals}\n\nint\nmain (int argc, char **argv)\n{\n  int ok = 0;\n  ${ac_c_conftest_c89_main}\n  ${ac_c_conftest_c99_main}\n  ${ac_c_conftest_c11_main}\n  return ok;\n}\n\"\n\n# Test code for whether the C compiler supports C99 (complete).\nac_c_conftest_c99_program=\"${ac_c_conftest_c89_globals}\n${ac_c_conftest_c99_globals}\n\nint\nmain (int argc, char **argv)\n{\n  int ok = 0;\n  ${ac_c_conftest_c89_main}\n  ${ac_c_conftest_c99_main}\n  return ok;\n}\n\"\n\n# Test code for whether the C compiler supports C89 (complete).\nac_c_conftest_c89_program=\"${ac_c_conftest_c89_globals}\n\nint\nmain (int argc, char **argv)\n{\n  int ok = 0;\n  ${ac_c_conftest_c89_main}\n  return ok;\n}\n\"\n\n# Test code for whether the C++ compiler supports C++98 (global declarations)\nac_cxx_conftest_cxx98_globals='\n// Does the compiler advertise C++98 conformance?\n#if !defined __cplusplus || __cplusplus < 199711L\n# error \"Compiler does not advertise C++98 conformance\"\n#endif\n\n// These inclusions are to reject old compilers that\n// lack the unsuffixed header files.\n#include <cstdlib>\n#include <exception>\n\n// <cassert> and <cstring> are *not* freestanding headers in C++98.\nextern void assert (int);\nnamespace std {\n  extern int strcmp (const char *, const char *);\n}\n\n// Namespaces, exceptions, and templates were all added after \"C++ 2.0\".\nusing std::exception;\nusing std::strcmp;\n\nnamespace {\n\nvoid test_exception_syntax()\n{\n  try {\n    throw \"test\";\n  } catch (const char *s) {\n    // Extra parentheses suppress a warning when building autoconf itself,\n    // due to lint rules shared with more typical C programs.\n    assert (!(strcmp) (s, \"test\"));\n  }\n}\n\ntemplate <typename T> struct test_template\n{\n  T const val;\n  explicit test_template(T t) : val(t) {}\n  template <typename U> T add(U u) { return static_cast<T>(u) + val; }\n};\n\n} // anonymous namespace\n'\n\n# Test code for whether the C++ compiler supports C++98 (body of main)\nac_cxx_conftest_cxx98_main='\n  assert (argc);\n  assert (! argv[0]);\n{\n  test_exception_syntax ();\n  test_template<double> tt (2.0);\n  assert (tt.add (4) == 6.0);\n  assert (true && !false);\n}\n'\n\n# Test code for whether the C++ compiler supports C++11 (global declarations)\nac_cxx_conftest_cxx11_globals='\n// Does the compiler advertise C++ 2011 conformance?\n#if !defined __cplusplus || __cplusplus < 201103L\n# error \"Compiler does not advertise C++11 conformance\"\n#endif\n\nnamespace cxx11test\n{\n  constexpr int get_val() { return 20; }\n\n  struct testinit\n  {\n    int i;\n    double d;\n  };\n\n  class delegate\n  {\n  public:\n    delegate(int n) : n(n) {}\n    delegate(): delegate(2354) {}\n\n    virtual int getval() { return this->n; };\n  protected:\n    int n;\n  };\n\n  class overridden : public delegate\n  {\n  public:\n    overridden(int n): delegate(n) {}\n    virtual int getval() override final { return this->n * 2; }\n  };\n\n  class nocopy\n  {\n  public:\n    nocopy(int i): i(i) {}\n    nocopy() = default;\n    nocopy(const nocopy&) = delete;\n    nocopy & operator=(const nocopy&) = delete;\n  private:\n    int i;\n  };\n\n  // for testing lambda expressions\n  template <typename Ret, typename Fn> Ret eval(Fn f, Ret v)\n  {\n    return f(v);\n  }\n\n  // for testing variadic templates and trailing return types\n  template <typename V> auto sum(V first) -> V\n  {\n    return first;\n  }\n  template <typename V, typename... Args> auto sum(V first, Args... rest) -> V\n  {\n    return first + sum(rest...);\n  }\n}\n'\n\n# Test code for whether the C++ compiler supports C++11 (body of main)\nac_cxx_conftest_cxx11_main='\n{\n  // Test auto and decltype\n  auto a1 = 6538;\n  auto a2 = 48573953.4;\n  auto a3 = \"String literal\";\n\n  int total = 0;\n  for (auto i = a3; *i; ++i) { total += *i; }\n\n  decltype(a2) a4 = 34895.034;\n}\n{\n  // Test constexpr\n  short sa[cxx11test::get_val()] = { 0 };\n}\n{\n  // Test initializer lists\n  cxx11test::testinit il = { 4323, 435234.23544 };\n}\n{\n  // Test range-based for\n  int array[] = {9, 7, 13, 15, 4, 18, 12, 10, 5, 3,\n                 14, 19, 17, 8, 6, 20, 16, 2, 11, 1};\n  for (auto &x : array) { x += 23; }\n}\n{\n  // Test lambda expressions\n  using cxx11test::eval;\n  assert (eval ([](int x) { return x*2; }, 21) == 42);\n  double d = 2.0;\n  assert (eval ([&](double x) { return d += x; }, 3.0) == 5.0);\n  assert (d == 5.0);\n  assert (eval ([=](double x) mutable { return d += x; }, 4.0) == 9.0);\n  assert (d == 5.0);\n}\n{\n  // Test use of variadic templates\n  using cxx11test::sum;\n  auto a = sum(1);\n  auto b = sum(1, 2);\n  auto c = sum(1.0, 2.0, 3.0);\n}\n{\n  // Test constructor delegation\n  cxx11test::delegate d1;\n  cxx11test::delegate d2();\n  cxx11test::delegate d3(45);\n}\n{\n  // Test override and final\n  cxx11test::overridden o1(55464);\n}\n{\n  // Test nullptr\n  char *c = nullptr;\n}\n{\n  // Test template brackets\n  test_template<::test_template<int>> v(test_template<int>(12));\n}\n{\n  // Unicode literals\n  char const *utf8 = u8\"UTF-8 string \\u2500\";\n  char16_t const *utf16 = u\"UTF-8 string \\u2500\";\n  char32_t const *utf32 = U\"UTF-32 string \\u2500\";\n}\n'\n\n# Test code for whether the C compiler supports C++11 (complete).\nac_cxx_conftest_cxx11_program=\"${ac_cxx_conftest_cxx98_globals}\n${ac_cxx_conftest_cxx11_globals}\n\nint\nmain (int argc, char **argv)\n{\n  int ok = 0;\n  ${ac_cxx_conftest_cxx98_main}\n  ${ac_cxx_conftest_cxx11_main}\n  return ok;\n}\n\"\n\n# Test code for whether the C compiler supports C++98 (complete).\nac_cxx_conftest_cxx98_program=\"${ac_cxx_conftest_cxx98_globals}\nint\nmain (int argc, char **argv)\n{\n  int ok = 0;\n  ${ac_cxx_conftest_cxx98_main}\n  return ok;\n}\n\"\n\nas_fn_append ac_header_c_list \" stdio.h stdio_h HAVE_STDIO_H\"\nas_fn_append ac_header_c_list \" stdlib.h stdlib_h HAVE_STDLIB_H\"\nas_fn_append ac_header_c_list \" string.h string_h HAVE_STRING_H\"\nas_fn_append ac_header_c_list \" inttypes.h inttypes_h HAVE_INTTYPES_H\"\nas_fn_append ac_header_c_list \" stdint.h stdint_h HAVE_STDINT_H\"\nas_fn_append ac_header_c_list \" strings.h strings_h HAVE_STRINGS_H\"\nas_fn_append ac_header_c_list \" sys/stat.h sys_stat_h HAVE_SYS_STAT_H\"\nas_fn_append ac_header_c_list \" sys/types.h sys_types_h HAVE_SYS_TYPES_H\"\nas_fn_append ac_header_c_list \" unistd.h unistd_h HAVE_UNISTD_H\"\n\n# Auxiliary files required by this configure script.\nac_aux_files=\"ltmain.sh ar-lib compile tap-driver.sh missing install-sh config.guess config.sub\"\n\n# Locations in which to look for auxiliary files.\nac_aux_dir_candidates=\"${srcdir}/build-aux\"\n\n# Search for a directory containing all of the required auxiliary files,\n# $ac_aux_files, from the $PATH-style list $ac_aux_dir_candidates.\n# If we don't find one directory that contains all the files we need,\n# we report the set of missing files from the *first* directory in\n# $ac_aux_dir_candidates and give up.\nac_missing_aux_files=\"\"\nac_first_candidate=:\nprintf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: looking for aux files: $ac_aux_files\" >&5\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nas_found=false\nfor as_dir in $ac_aux_dir_candidates\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n  as_found=:\n\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}:  trying $as_dir\" >&5\n  ac_aux_dir_found=yes\n  ac_install_sh=\n  for ac_aux in $ac_aux_files\n  do\n    # As a special case, if \"install-sh\" is required, that requirement\n    # can be satisfied by any of \"install-sh\", \"install.sh\", or \"shtool\",\n    # and $ac_install_sh is set appropriately for whichever one is found.\n    if test x\"$ac_aux\" = x\"install-sh\"\n    then\n      if test -f \"${as_dir}install-sh\"; then\n        printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}:   ${as_dir}install-sh found\" >&5\n        ac_install_sh=\"${as_dir}install-sh -c\"\n      elif test -f \"${as_dir}install.sh\"; then\n        printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}:   ${as_dir}install.sh found\" >&5\n        ac_install_sh=\"${as_dir}install.sh -c\"\n      elif test -f \"${as_dir}shtool\"; then\n        printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}:   ${as_dir}shtool found\" >&5\n        ac_install_sh=\"${as_dir}shtool install -c\"\n      else\n        ac_aux_dir_found=no\n        if $ac_first_candidate; then\n          ac_missing_aux_files=\"${ac_missing_aux_files} install-sh\"\n        else\n          break\n        fi\n      fi\n    else\n      if test -f \"${as_dir}${ac_aux}\"; then\n        printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}:   ${as_dir}${ac_aux} found\" >&5\n      else\n        ac_aux_dir_found=no\n        if $ac_first_candidate; then\n          ac_missing_aux_files=\"${ac_missing_aux_files} ${ac_aux}\"\n        else\n          break\n        fi\n      fi\n    fi\n  done\n  if test \"$ac_aux_dir_found\" = yes; then\n    ac_aux_dir=\"$as_dir\"\n    break\n  fi\n  ac_first_candidate=false\n\n  as_found=false\ndone\nIFS=$as_save_IFS\nif $as_found\nthen :\n\nelse case e in #(\n  e) as_fn_error $? \"cannot find required auxiliary files:$ac_missing_aux_files\" \"$LINENO\" 5 ;;\nesac\nfi\n\n\n# These three variables are undocumented and unsupported,\n# and are intended to be withdrawn in a future Autoconf release.\n# They can cause serious problems if a builder's source tree is in a directory\n# whose full name contains unusual characters.\nif test -f \"${ac_aux_dir}config.guess\"; then\n  ac_config_guess=\"$SHELL ${ac_aux_dir}config.guess\"\nfi\nif test -f \"${ac_aux_dir}config.sub\"; then\n  ac_config_sub=\"$SHELL ${ac_aux_dir}config.sub\"\nfi\nif test -f \"$ac_aux_dir/configure\"; then\n  ac_configure=\"$SHELL ${ac_aux_dir}configure\"\nfi\n\n# Check that the precious variables saved in the cache have kept the same\n# value.\nac_cache_corrupted=false\nfor ac_var in $ac_precious_vars; do\n  eval ac_old_set=\\$ac_cv_env_${ac_var}_set\n  eval ac_new_set=\\$ac_env_${ac_var}_set\n  eval ac_old_val=\\$ac_cv_env_${ac_var}_value\n  eval ac_new_val=\\$ac_env_${ac_var}_value\n  case $ac_old_set,$ac_new_set in\n    set,)\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: '$ac_var' was set to '$ac_old_val' in the previous run\" >&5\nprintf \"%s\\n\" \"$as_me: error: '$ac_var' was set to '$ac_old_val' in the previous run\" >&2;}\n      ac_cache_corrupted=: ;;\n    ,set)\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: '$ac_var' was not set in the previous run\" >&5\nprintf \"%s\\n\" \"$as_me: error: '$ac_var' was not set in the previous run\" >&2;}\n      ac_cache_corrupted=: ;;\n    ,);;\n    *)\n      if test \"x$ac_old_val\" != \"x$ac_new_val\"; then\n\t# differences in whitespace do not lead to failure.\n\tac_old_val_w=`echo x $ac_old_val`\n\tac_new_val_w=`echo x $ac_new_val`\n\tif test \"$ac_old_val_w\" != \"$ac_new_val_w\"; then\n\t  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: '$ac_var' has changed since the previous run:\" >&5\nprintf \"%s\\n\" \"$as_me: error: '$ac_var' has changed since the previous run:\" >&2;}\n\t  ac_cache_corrupted=:\n\telse\n\t  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: warning: ignoring whitespace changes in '$ac_var' since the previous run:\" >&5\nprintf \"%s\\n\" \"$as_me: warning: ignoring whitespace changes in '$ac_var' since the previous run:\" >&2;}\n\t  eval $ac_var=\\$ac_old_val\n\tfi\n\t{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}:   former value:  '$ac_old_val'\" >&5\nprintf \"%s\\n\" \"$as_me:   former value:  '$ac_old_val'\" >&2;}\n\t{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}:   current value: '$ac_new_val'\" >&5\nprintf \"%s\\n\" \"$as_me:   current value: '$ac_new_val'\" >&2;}\n      fi;;\n  esac\n  # Pass precious variables to config.status.\n  if test \"$ac_new_set\" = set; then\n    case $ac_new_val in\n    *\\'*) ac_arg=$ac_var=`printf \"%s\\n\" \"$ac_new_val\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"` ;;\n    *) ac_arg=$ac_var=$ac_new_val ;;\n    esac\n    case \" $ac_configure_args \" in\n      *\" '$ac_arg' \"*) ;; # Avoid dups.  Use of quotes ensures accuracy.\n      *) as_fn_append ac_configure_args \" '$ac_arg'\" ;;\n    esac\n  fi\ndone\nif $ac_cache_corrupted; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: changes in the environment can compromise the build\" >&5\nprintf \"%s\\n\" \"$as_me: error: changes in the environment can compromise the build\" >&2;}\n  as_fn_error $? \"run '${MAKE-make} distclean' and/or 'rm $cache_file'\n\t    and start over\" \"$LINENO\" 5\nfi\n## -------------------- ##\n## Main body of script. ##\n## -------------------- ##\n\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\n\n\n\n\n\n\n  # Make sure we can run config.sub.\n$SHELL \"${ac_aux_dir}config.sub\" sun4 >/dev/null 2>&1 ||\n  as_fn_error $? \"cannot run $SHELL ${ac_aux_dir}config.sub\" \"$LINENO\" 5\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking build system type\" >&5\nprintf %s \"checking build system type... \" >&6; }\nif test ${ac_cv_build+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_build_alias=$build_alias\ntest \"x$ac_build_alias\" = x &&\n  ac_build_alias=`$SHELL \"${ac_aux_dir}config.guess\"`\ntest \"x$ac_build_alias\" = x &&\n  as_fn_error $? \"cannot guess build type; you must specify one\" \"$LINENO\" 5\nac_cv_build=`$SHELL \"${ac_aux_dir}config.sub\" $ac_build_alias` ||\n  as_fn_error $? \"$SHELL ${ac_aux_dir}config.sub $ac_build_alias failed\" \"$LINENO\" 5\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_build\" >&5\nprintf \"%s\\n\" \"$ac_cv_build\" >&6; }\ncase $ac_cv_build in\n*-*-*) ;;\n*) as_fn_error $? \"invalid value of canonical build\" \"$LINENO\" 5;;\nesac\nbuild=$ac_cv_build\nac_save_IFS=$IFS; IFS='-'\nset x $ac_cv_build\nshift\nbuild_cpu=$1\nbuild_vendor=$2\nshift; shift\n# Remember, the first character of IFS is used to create $*,\n# except with old shells:\nbuild_os=$*\nIFS=$ac_save_IFS\ncase $build_os in *\\ *) build_os=`echo \"$build_os\" | sed 's/ /-/g'`;; esac\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking host system type\" >&5\nprintf %s \"checking host system type... \" >&6; }\nif test ${ac_cv_host+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test \"x$host_alias\" = x; then\n  ac_cv_host=$ac_cv_build\nelse\n  ac_cv_host=`$SHELL \"${ac_aux_dir}config.sub\" $host_alias` ||\n    as_fn_error $? \"$SHELL ${ac_aux_dir}config.sub $host_alias failed\" \"$LINENO\" 5\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_host\" >&5\nprintf \"%s\\n\" \"$ac_cv_host\" >&6; }\ncase $ac_cv_host in\n*-*-*) ;;\n*) as_fn_error $? \"invalid value of canonical host\" \"$LINENO\" 5;;\nesac\nhost=$ac_cv_host\nac_save_IFS=$IFS; IFS='-'\nset x $ac_cv_host\nshift\nhost_cpu=$1\nhost_vendor=$2\nshift; shift\n# Remember, the first character of IFS is used to create $*,\n# except with old shells:\nhost_os=$*\nIFS=$ac_save_IFS\ncase $host_os in *\\ *) host_os=`echo \"$host_os\" | sed 's/ /-/g'`;; esac\n\n\nam__api_version='1.16'\n\n\n  # Find a good install program.  We prefer a C program (faster),\n# so one script is as good as another.  But avoid the broken or\n# incompatible versions:\n# SysV /etc/install, /usr/sbin/install\n# SunOS /usr/etc/install\n# IRIX /sbin/install\n# AIX /bin/install\n# AmigaOS /C/install, which installs bootblocks on floppy discs\n# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag\n# AFS /usr/afsws/bin/install, which mishandles nonexistent args\n# SVR4 /usr/ucb/install, which tries to use the nonexistent group \"staff\"\n# OS/2's system install, which has a completely different semantic\n# ./install, which can be erroneously created by make from ./install.sh.\n# Reject install programs that cannot install multiple files.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for a BSD-compatible install\" >&5\nprintf %s \"checking for a BSD-compatible install... \" >&6; }\nif test -z \"$INSTALL\"; then\nif test ${ac_cv_path_install+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    # Account for fact that we put trailing slashes in our PATH walk.\ncase $as_dir in #((\n  ./ | /[cC]/* | \\\n  /etc/* | /usr/sbin/* | /usr/etc/* | /sbin/* | /usr/afsws/bin/* | \\\n  ?:[\\\\/]os2[\\\\/]install[\\\\/]* | ?:[\\\\/]OS2[\\\\/]INSTALL[\\\\/]* | \\\n  /usr/ucb/* ) ;;\n  *)\n    # OSF1 and SCO ODT 3.0 have their own names for install.\n    # Don't use installbsd from OSF since it installs stuff as root\n    # by default.\n    for ac_prog in ginstall scoinst install; do\n      for ac_exec_ext in '' $ac_executable_extensions; do\n\tif as_fn_executable_p \"$as_dir$ac_prog$ac_exec_ext\"; then\n\t  if test $ac_prog = install &&\n\t    grep dspmsg \"$as_dir$ac_prog$ac_exec_ext\" >/dev/null 2>&1; then\n\t    # AIX install.  It has an incompatible calling convention.\n\t    :\n\t  elif test $ac_prog = install &&\n\t    grep pwplus \"$as_dir$ac_prog$ac_exec_ext\" >/dev/null 2>&1; then\n\t    # program-specific install script used by HP pwplus--don't use.\n\t    :\n\t  else\n\t    rm -rf conftest.one conftest.two conftest.dir\n\t    echo one > conftest.one\n\t    echo two > conftest.two\n\t    mkdir conftest.dir\n\t    if \"$as_dir$ac_prog$ac_exec_ext\" -c conftest.one conftest.two \"`pwd`/conftest.dir/\" &&\n\t      test -s conftest.one && test -s conftest.two &&\n\t      test -s conftest.dir/conftest.one &&\n\t      test -s conftest.dir/conftest.two\n\t    then\n\t      ac_cv_path_install=\"$as_dir$ac_prog$ac_exec_ext -c\"\n\t      break 3\n\t    fi\n\t  fi\n\tfi\n      done\n    done\n    ;;\nesac\n\n  done\nIFS=$as_save_IFS\n\nrm -rf conftest.one conftest.two conftest.dir\n ;;\nesac\nfi\n  if test ${ac_cv_path_install+y}; then\n    INSTALL=$ac_cv_path_install\n  else\n    # As a last resort, use the slow shell script.  Don't cache a\n    # value for INSTALL within a source directory, because that will\n    # break other packages using the cache if that directory is\n    # removed, or if the value is a relative name.\n    INSTALL=$ac_install_sh\n  fi\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $INSTALL\" >&5\nprintf \"%s\\n\" \"$INSTALL\" >&6; }\n\n# Use test -z because SunOS4 sh mishandles braces in ${var-val}.\n# It thinks the first close brace ends the variable substitution.\ntest -z \"$INSTALL_PROGRAM\" && INSTALL_PROGRAM='${INSTALL}'\n\ntest -z \"$INSTALL_SCRIPT\" && INSTALL_SCRIPT='${INSTALL}'\n\ntest -z \"$INSTALL_DATA\" && INSTALL_DATA='${INSTALL} -m 644'\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether build environment is sane\" >&5\nprintf %s \"checking whether build environment is sane... \" >&6; }\n# Reject unsafe characters in $srcdir or the absolute working directory\n# name.  Accept space and tab only in the latter.\nam_lf='\n'\ncase `pwd` in\n  *[\\\\\\\"\\#\\$\\&\\'\\`$am_lf]*)\n    as_fn_error $? \"unsafe absolute working directory name\" \"$LINENO\" 5;;\nesac\ncase $srcdir in\n  *[\\\\\\\"\\#\\$\\&\\'\\`$am_lf\\ \\\t]*)\n    as_fn_error $? \"unsafe srcdir value: '$srcdir'\" \"$LINENO\" 5;;\nesac\n\n# Do 'set' in a subshell so we don't clobber the current shell's\n# arguments.  Must try -L first in case configure is actually a\n# symlink; some systems play weird games with the mod time of symlinks\n# (eg FreeBSD returns the mod time of the symlink's containing\n# directory).\nif (\n   am_has_slept=no\n   for am_try in 1 2; do\n     echo \"timestamp, slept: $am_has_slept\" > conftest.file\n     set X `ls -Lt \"$srcdir/configure\" conftest.file 2> /dev/null`\n     if test \"$*\" = \"X\"; then\n\t# -L didn't work.\n\tset X `ls -t \"$srcdir/configure\" conftest.file`\n     fi\n     if test \"$*\" != \"X $srcdir/configure conftest.file\" \\\n\t&& test \"$*\" != \"X conftest.file $srcdir/configure\"; then\n\n\t# If neither matched, then we have a broken ls.  This can happen\n\t# if, for instance, CONFIG_SHELL is bash and it inherits a\n\t# broken ls alias from the environment.  This has actually\n\t# happened.  Such a system could not be considered \"sane\".\n\tas_fn_error $? \"ls -t appears to fail.  Make sure there is not a broken\n  alias in your environment\" \"$LINENO\" 5\n     fi\n     if test \"$2\" = conftest.file || test $am_try -eq 2; then\n       break\n     fi\n     # Just in case.\n     sleep 1\n     am_has_slept=yes\n   done\n   test \"$2\" = conftest.file\n   )\nthen\n   # Ok.\n   :\nelse\n   as_fn_error $? \"newly created file is older than distributed files!\nCheck your system clock\" \"$LINENO\" 5\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; }\n# If we didn't sleep, we still need to ensure time stamps of config.status and\n# generated files are strictly newer.\nam_sleep_pid=\nif grep 'slept: no' conftest.file >/dev/null 2>&1; then\n  ( sleep 1 ) &\n  am_sleep_pid=$!\nfi\n\nrm -f conftest.file\n\ntest \"$program_prefix\" != NONE &&\n  program_transform_name=\"s&^&$program_prefix&;$program_transform_name\"\n# Use a double $ so make ignores it.\ntest \"$program_suffix\" != NONE &&\n  program_transform_name=\"s&\\$&$program_suffix&;$program_transform_name\"\n# Double any \\ or $.\n# By default was 's,x,x', remove it if useless.\nac_script='s/[\\\\$]/&&/g;s/;s,x,x,$//'\nprogram_transform_name=`printf \"%s\\n\" \"$program_transform_name\" | sed \"$ac_script\"`\n\n\n# Expand $ac_aux_dir to an absolute path.\nam_aux_dir=`cd \"$ac_aux_dir\" && pwd`\n\n\n  if test x\"${MISSING+set}\" != xset; then\n  MISSING=\"\\${SHELL} '$am_aux_dir/missing'\"\nfi\n# Use eval to expand $SHELL\nif eval \"$MISSING --is-lightweight\"; then\n  am_missing_run=\"$MISSING \"\nelse\n  am_missing_run=\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: 'missing' script is too old or missing\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: 'missing' script is too old or missing\" >&2;}\nfi\n\nif test x\"${install_sh+set}\" != xset; then\n  case $am_aux_dir in\n  *\\ * | *\\\t*)\n    install_sh=\"\\${SHELL} '$am_aux_dir/install-sh'\" ;;\n  *)\n    install_sh=\"\\${SHELL} $am_aux_dir/install-sh\"\n  esac\nfi\n\n# Installed binaries are usually stripped using 'strip' when the user\n# run \"make install-strip\".  However 'strip' might not be the right\n# tool to use in cross-compilation environments, therefore Automake\n# will honor the 'STRIP' environment variable to overrule this program.\nif test \"$cross_compiling\" != no; then\n  if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}strip\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}strip; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_STRIP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$STRIP\"; then\n  ac_cv_prog_STRIP=\"$STRIP\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_STRIP=\"${ac_tool_prefix}strip\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nSTRIP=$ac_cv_prog_STRIP\nif test -n \"$STRIP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $STRIP\" >&5\nprintf \"%s\\n\" \"$STRIP\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_STRIP\"; then\n  ac_ct_STRIP=$STRIP\n  # Extract the first word of \"strip\", so it can be a program name with args.\nset dummy strip; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_STRIP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_STRIP\"; then\n  ac_cv_prog_ac_ct_STRIP=\"$ac_ct_STRIP\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_STRIP=\"strip\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_STRIP=$ac_cv_prog_ac_ct_STRIP\nif test -n \"$ac_ct_STRIP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_STRIP\" >&5\nprintf \"%s\\n\" \"$ac_ct_STRIP\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_STRIP\" = x; then\n    STRIP=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    STRIP=$ac_ct_STRIP\n  fi\nelse\n  STRIP=\"$ac_cv_prog_STRIP\"\nfi\n\nfi\nINSTALL_STRIP_PROGRAM=\"\\$(install_sh) -c -s\"\n\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for a race-free mkdir -p\" >&5\nprintf %s \"checking for a race-free mkdir -p... \" >&6; }\nif test -z \"$MKDIR_P\"; then\n  if test ${ac_cv_path_mkdir+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH$PATH_SEPARATOR/opt/sfw/bin\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_prog in mkdir gmkdir; do\n\t for ac_exec_ext in '' $ac_executable_extensions; do\n\t   as_fn_executable_p \"$as_dir$ac_prog$ac_exec_ext\" || continue\n\t   case `\"$as_dir$ac_prog$ac_exec_ext\" --version 2>&1` in #(\n\t     'mkdir ('*'coreutils) '* | \\\n\t     *'BusyBox '* | \\\n\t     'mkdir (fileutils) '4.1*)\n\t       ac_cv_path_mkdir=$as_dir$ac_prog$ac_exec_ext\n\t       break 3;;\n\t   esac\n\t done\n       done\n  done\nIFS=$as_save_IFS\n ;;\nesac\nfi\n\n  test -d ./--version && rmdir ./--version\n  if test ${ac_cv_path_mkdir+y}; then\n    MKDIR_P=\"$ac_cv_path_mkdir -p\"\n  else\n    # As a last resort, use plain mkdir -p,\n    # in the hope it doesn't have the bugs of ancient mkdir.\n    MKDIR_P='mkdir -p'\n  fi\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $MKDIR_P\" >&5\nprintf \"%s\\n\" \"$MKDIR_P\" >&6; }\n\nfor ac_prog in gawk mawk nawk awk\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_AWK+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$AWK\"; then\n  ac_cv_prog_AWK=\"$AWK\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_AWK=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nAWK=$ac_cv_prog_AWK\nif test -n \"$AWK\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $AWK\" >&5\nprintf \"%s\\n\" \"$AWK\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$AWK\" && break\ndone\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether ${MAKE-make} sets \\$(MAKE)\" >&5\nprintf %s \"checking whether ${MAKE-make} sets \\$(MAKE)... \" >&6; }\nset x ${MAKE-make}\nac_make=`printf \"%s\\n\" \"$2\" | sed 's/+/p/g; s/[^a-zA-Z0-9_]/_/g'`\nif eval test \\${ac_cv_prog_make_${ac_make}_set+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat >conftest.make <<\\_ACEOF\nSHELL = /bin/sh\nall:\n\t@echo '@@@%%%=$(MAKE)=@@@%%%'\n_ACEOF\n# GNU make sometimes prints \"make[1]: Entering ...\", which would confuse us.\ncase `${MAKE-make} -f conftest.make 2>/dev/null` in\n  *@@@%%%=?*=@@@%%%*)\n    eval ac_cv_prog_make_${ac_make}_set=yes;;\n  *)\n    eval ac_cv_prog_make_${ac_make}_set=no;;\nesac\nrm -f conftest.make ;;\nesac\nfi\nif eval test \\$ac_cv_prog_make_${ac_make}_set = yes; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; }\n  SET_MAKE=\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\n  SET_MAKE=\"MAKE=${MAKE-make}\"\nfi\n\nrm -rf .tst 2>/dev/null\nmkdir .tst 2>/dev/null\nif test -d .tst; then\n  am__leading_dot=.\nelse\n  am__leading_dot=_\nfi\nrmdir .tst 2>/dev/null\n\n# Check whether --enable-silent-rules was given.\nif test ${enable_silent_rules+y}\nthen :\n  enableval=$enable_silent_rules;\nfi\n\ncase $enable_silent_rules in # (((\n  yes) AM_DEFAULT_VERBOSITY=0;;\n   no) AM_DEFAULT_VERBOSITY=1;;\n    *) AM_DEFAULT_VERBOSITY=1;;\nesac\nam_make=${MAKE-make}\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether $am_make supports nested variables\" >&5\nprintf %s \"checking whether $am_make supports nested variables... \" >&6; }\nif test ${am_cv_make_support_nested_variables+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if printf \"%s\\n\" 'TRUE=$(BAR$(V))\nBAR0=false\nBAR1=true\nV=1\nam__doit:\n\t@$(TRUE)\n.PHONY: am__doit' | $am_make -f - >/dev/null 2>&1; then\n  am_cv_make_support_nested_variables=yes\nelse\n  am_cv_make_support_nested_variables=no\nfi ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $am_cv_make_support_nested_variables\" >&5\nprintf \"%s\\n\" \"$am_cv_make_support_nested_variables\" >&6; }\nif test $am_cv_make_support_nested_variables = yes; then\n    AM_V='$(V)'\n  AM_DEFAULT_V='$(AM_DEFAULT_VERBOSITY)'\nelse\n  AM_V=$AM_DEFAULT_VERBOSITY\n  AM_DEFAULT_V=$AM_DEFAULT_VERBOSITY\nfi\nAM_BACKSLASH='\\'\n\nif test \"`cd $srcdir && pwd`\" != \"`pwd`\"; then\n  # Use -I$(srcdir) only when $(srcdir) != ., so that make's output\n  # is not polluted with repeated \"-I.\"\n  am__isrc=' -I$(srcdir)'\n  # test to see if srcdir already configured\n  if test -f $srcdir/config.status; then\n    as_fn_error $? \"source directory already configured; run \\\"make distclean\\\" there first\" \"$LINENO\" 5\n  fi\nfi\n\n# test whether we have cygpath\nif test -z \"$CYGPATH_W\"; then\n  if (cygpath --version) >/dev/null 2>/dev/null; then\n    CYGPATH_W='cygpath -w'\n  else\n    CYGPATH_W=echo\n  fi\nfi\n\n\n# Define the identity of the package.\n PACKAGE='cudd'\n VERSION='3.0.0'\n\n\nprintf \"%s\\n\" \"#define PACKAGE \\\"$PACKAGE\\\"\" >>confdefs.h\n\n\nprintf \"%s\\n\" \"#define VERSION \\\"$VERSION\\\"\" >>confdefs.h\n\n# Some tools Automake needs.\n\nACLOCAL=${ACLOCAL-\"${am_missing_run}aclocal-${am__api_version}\"}\n\n\nAUTOCONF=${AUTOCONF-\"${am_missing_run}autoconf\"}\n\n\nAUTOMAKE=${AUTOMAKE-\"${am_missing_run}automake-${am__api_version}\"}\n\n\nAUTOHEADER=${AUTOHEADER-\"${am_missing_run}autoheader\"}\n\n\nMAKEINFO=${MAKEINFO-\"${am_missing_run}makeinfo\"}\n\n# For better backward compatibility.  To be removed once Automake 1.9.x\n# dies out for good.  For more background, see:\n# <https://lists.gnu.org/archive/html/automake/2012-07/msg00001.html>\n# <https://lists.gnu.org/archive/html/automake/2012-07/msg00014.html>\nmkdir_p='$(MKDIR_P)'\n\n# We need awk for the \"check\" target (and possibly the TAP driver).  The\n# system \"awk\" is bad on some platforms.\n# Always define AMTAR for backward compatibility.  Yes, it's still used\n# in the wild :-(  We should find a proper way to deprecate it ...\nAMTAR='$${TAR-tar}'\n\n\n# We'll loop over all known methods to create a tar archive until one works.\n_am_tools='gnutar  pax cpio none'\n\nam__tar='$${TAR-tar} chof - \"$$tardir\"' am__untar='$${TAR-tar} xf -'\n\n\n\n\n\n# Variables for tags utilities; see am/tags.am\nif test -z \"$CTAGS\"; then\n  CTAGS=ctags\nfi\n\nif test -z \"$ETAGS\"; then\n  ETAGS=etags\nfi\n\nif test -z \"$CSCOPE\"; then\n  CSCOPE=cscope\nfi\n\n\n\n# POSIX will say in a future version that running \"rm -f\" with no argument\n# is OK; and we want to be able to make that assumption in our Makefile\n# recipes.  So use an aggressive probe to check that the usage we want is\n# actually supported \"in the wild\" to an acceptable degree.\n# See automake bug#10828.\n# To make any issue more visible, cause the running configure to be aborted\n# by default if the 'rm' program in use doesn't match our expectations; the\n# user can still override this though.\nif rm -f && rm -fr && rm -rf; then : OK; else\n  cat >&2 <<'END'\nOops!\n\nYour 'rm' program seems unable to run without file operands specified\non the command line, even when the '-f' option is present.  This is contrary\nto the behaviour of most rm programs out there, and not conforming with\nthe upcoming POSIX standard: <http://austingroupbugs.net/view.php?id=542>\n\nPlease tell bug-automake@gnu.org about your system, including the value\nof your $PATH and any error possibly output before this message.  This\ncan help us improve future automake versions.\n\nEND\n  if test x\"$ACCEPT_INFERIOR_RM_PROGRAM\" = x\"yes\"; then\n    echo 'Configuration will proceed anyway, since you have set the' >&2\n    echo 'ACCEPT_INFERIOR_RM_PROGRAM variable to \"yes\"' >&2\n    echo >&2\n  else\n    cat >&2 <<'END'\nAborting the configuration process, to ensure you take notice of the issue.\n\nYou can download and install GNU coreutils to get an 'rm' implementation\nthat behaves properly: <https://www.gnu.org/software/coreutils/>.\n\nIf you want to complete the configuration process using your problematic\n'rm' anyway, export the environment variable ACCEPT_INFERIOR_RM_PROGRAM\nto \"yes\", and re-run configure.\n\nEND\n    as_fn_error $? \"Your 'rm' program is bad, sorry.\" \"$LINENO\" 5\n  fi\nfi\n\n\n\n\n# Check whether --enable-dddmp was given.\nif test ${enable_dddmp+y}\nthen :\n  enableval=$enable_dddmp;\nfi\n\n if test x$enable_dddmp = xyes; then\n  DDDMP_TRUE=\n  DDDMP_FALSE='#'\nelse\n  DDDMP_TRUE='#'\n  DDDMP_FALSE=\nfi\n\n\n# Check whether --enable-obj was given.\nif test ${enable_obj+y}\nthen :\n  enableval=$enable_obj;\nfi\n\n if test x$enable_obj = xyes; then\n  OBJ_TRUE=\n  OBJ_FALSE='#'\nelse\n  OBJ_TRUE='#'\n  OBJ_FALSE=\nfi\n\n\n\n# Check whether --with-system-qsort was given.\nif test ${with_system_qsort+y}\nthen :\n  withval=$with_system_qsort;\nelse case e in #(\n  e) with_system_qsort=no ;;\nesac\nfi\n\nif test x$with_system_qsort != xno ; then\n\nprintf \"%s\\n\" \"#define USE_SYSTEM_QSORT 1\" >>confdefs.h\n\nfi\n\n# Set our own default (instead of \"-g -O2\") unless CFLAGS is already defined.\n: ${CFLAGS=\"-Wall -Wextra -g -O3\"}\n: ${CXXFLAGS=\"-Wall -Wextra -std=c++0x -g -O3\"}\n\n\n\n\n\n\n\n\n\n\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\nif test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}gcc\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}gcc; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_CC+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_CC=\"${ac_tool_prefix}gcc\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $CC\" >&5\nprintf \"%s\\n\" \"$CC\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_CC\"; then\n  ac_ct_CC=$CC\n  # Extract the first word of \"gcc\", so it can be a program name with args.\nset dummy gcc; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_CC+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_CC\"; then\n  ac_cv_prog_ac_ct_CC=\"$ac_ct_CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_CC=\"gcc\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_CC=$ac_cv_prog_ac_ct_CC\nif test -n \"$ac_ct_CC\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC\" >&5\nprintf \"%s\\n\" \"$ac_ct_CC\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_CC\" = x; then\n    CC=\"\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    CC=$ac_ct_CC\n  fi\nelse\n  CC=\"$ac_cv_prog_CC\"\nfi\n\nif test -z \"$CC\"; then\n          if test -n \"$ac_tool_prefix\"; then\n    # Extract the first word of \"${ac_tool_prefix}cc\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}cc; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_CC+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_CC=\"${ac_tool_prefix}cc\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $CC\" >&5\nprintf \"%s\\n\" \"$CC\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  fi\nfi\nif test -z \"$CC\"; then\n  # Extract the first word of \"cc\", so it can be a program name with args.\nset dummy cc; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_CC+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\n  ac_prog_rejected=no\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    if test \"$as_dir$ac_word$ac_exec_ext\" = \"/usr/ucb/cc\"; then\n       ac_prog_rejected=yes\n       continue\n     fi\n    ac_cv_prog_CC=\"cc\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nif test $ac_prog_rejected = yes; then\n  # We found a bogon in the path, so make sure we never use it.\n  set dummy $ac_cv_prog_CC\n  shift\n  if test $# != 0; then\n    # We chose a different compiler from the bogus one.\n    # However, it has the same basename, so the bogon will be chosen\n    # first if we set CC to just the basename; use the full file name.\n    shift\n    ac_cv_prog_CC=\"$as_dir$ac_word${1+' '}$@\"\n  fi\nfi\nfi ;;\nesac\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $CC\" >&5\nprintf \"%s\\n\" \"$CC\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$CC\"; then\n  if test -n \"$ac_tool_prefix\"; then\n  for ac_prog in cl.exe\n  do\n    # Extract the first word of \"$ac_tool_prefix$ac_prog\", so it can be a program name with args.\nset dummy $ac_tool_prefix$ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_CC+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_CC=\"$ac_tool_prefix$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $CC\" >&5\nprintf \"%s\\n\" \"$CC\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n    test -n \"$CC\" && break\n  done\nfi\nif test -z \"$CC\"; then\n  ac_ct_CC=$CC\n  for ac_prog in cl.exe\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_CC+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_CC\"; then\n  ac_cv_prog_ac_ct_CC=\"$ac_ct_CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_CC=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_CC=$ac_cv_prog_ac_ct_CC\nif test -n \"$ac_ct_CC\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC\" >&5\nprintf \"%s\\n\" \"$ac_ct_CC\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$ac_ct_CC\" && break\ndone\n\n  if test \"x$ac_ct_CC\" = x; then\n    CC=\"\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    CC=$ac_ct_CC\n  fi\nfi\n\nfi\nif test -z \"$CC\"; then\n  if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}clang\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}clang; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_CC+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_CC=\"${ac_tool_prefix}clang\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $CC\" >&5\nprintf \"%s\\n\" \"$CC\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_CC\"; then\n  ac_ct_CC=$CC\n  # Extract the first word of \"clang\", so it can be a program name with args.\nset dummy clang; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_CC+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_CC\"; then\n  ac_cv_prog_ac_ct_CC=\"$ac_ct_CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_CC=\"clang\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_CC=$ac_cv_prog_ac_ct_CC\nif test -n \"$ac_ct_CC\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_CC\" >&5\nprintf \"%s\\n\" \"$ac_ct_CC\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_CC\" = x; then\n    CC=\"\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    CC=$ac_ct_CC\n  fi\nelse\n  CC=\"$ac_cv_prog_CC\"\nfi\n\nfi\n\n\ntest -z \"$CC\" && { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error $? \"no acceptable C compiler found in \\$PATH\nSee 'config.log' for more details\" \"$LINENO\" 5; }\n\n# Provide some information about the compiler.\nprintf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for C compiler version\" >&5\nset X $ac_compile\nac_compiler=$2\nfor ac_option in --version -v -V -qversion -version; do\n  { { ac_try=\"$ac_compiler $ac_option >&5\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_compiler $ac_option >&5\") 2>conftest.err\n  ac_status=$?\n  if test -s conftest.err; then\n    sed '10a\\\n... rest of stderr output deleted ...\n         10q' conftest.err >conftest.er1\n    cat conftest.er1 >&5\n  fi\n  rm -f conftest.er1 conftest.err\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\ndone\n\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nac_clean_files_save=$ac_clean_files\nac_clean_files=\"$ac_clean_files a.out a.out.dSYM a.exe b.out\"\n# Try to create an executable without -o first, disregard a.out.\n# It will help us diagnose broken compilers, and finding out an intuition\n# of exeext.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether the C compiler works\" >&5\nprintf %s \"checking whether the C compiler works... \" >&6; }\nac_link_default=`printf \"%s\\n\" \"$ac_link\" | sed 's/ -o *conftest[^ ]*//'`\n\n# The possible output files:\nac_files=\"a.out conftest.exe conftest a.exe a_out.exe b.out conftest.*\"\n\nac_rmfiles=\nfor ac_file in $ac_files\ndo\n  case $ac_file in\n    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;;\n    * ) ac_rmfiles=\"$ac_rmfiles $ac_file\";;\n  esac\ndone\nrm -f $ac_rmfiles\n\nif { { ac_try=\"$ac_link_default\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_link_default\") 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\nthen :\n  # Autoconf-2.13 could set the ac_cv_exeext variable to 'no'.\n# So ignore a value of 'no', otherwise this would lead to 'EXEEXT = no'\n# in a Makefile.  We should not override ac_cv_exeext if it was cached,\n# so that the user can short-circuit this test for compilers unknown to\n# Autoconf.\nfor ac_file in $ac_files ''\ndo\n  test -f \"$ac_file\" || continue\n  case $ac_file in\n    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj )\n\t;;\n    [ab].out )\n\t# We found the default executable, but exeext='' is most\n\t# certainly right.\n\tbreak;;\n    *.* )\n\tif test ${ac_cv_exeext+y} && test \"$ac_cv_exeext\" != no;\n\tthen :; else\n\t   ac_cv_exeext=`expr \"$ac_file\" : '[^.]*\\(\\..*\\)'`\n\tfi\n\t# We set ac_cv_exeext here because the later test for it is not\n\t# safe: cross compilers may not add the suffix if given an '-o'\n\t# argument, so we may need to know it at that point already.\n\t# Even if this section looks crufty: it has the advantage of\n\t# actually working.\n\tbreak;;\n    * )\n\tbreak;;\n  esac\ndone\ntest \"$ac_cv_exeext\" = no && ac_cv_exeext=\n\nelse case e in #(\n  e) ac_file='' ;;\nesac\nfi\nif test -z \"$ac_file\"\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nprintf \"%s\\n\" \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n{ { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error 77 \"C compiler cannot create executables\nSee 'config.log' for more details\" \"$LINENO\" 5; }\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; } ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for C compiler default output file name\" >&5\nprintf %s \"checking for C compiler default output file name... \" >&6; }\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_file\" >&5\nprintf \"%s\\n\" \"$ac_file\" >&6; }\nac_exeext=$ac_cv_exeext\n\nrm -f -r a.out a.out.dSYM a.exe conftest$ac_cv_exeext b.out\nac_clean_files=$ac_clean_files_save\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for suffix of executables\" >&5\nprintf %s \"checking for suffix of executables... \" >&6; }\nif { { ac_try=\"$ac_link\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_link\") 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\nthen :\n  # If both 'conftest.exe' and 'conftest' are 'present' (well, observable)\n# catch 'conftest.exe'.  For instance with Cygwin, 'ls conftest' will\n# work properly (i.e., refer to 'conftest.exe'), while it won't with\n# 'rm'.\nfor ac_file in conftest.exe conftest conftest.*; do\n  test -f \"$ac_file\" || continue\n  case $ac_file in\n    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM | *.o | *.obj ) ;;\n    *.* ) ac_cv_exeext=`expr \"$ac_file\" : '[^.]*\\(\\..*\\)'`\n\t  break;;\n    * ) break;;\n  esac\ndone\nelse case e in #(\n  e) { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error $? \"cannot compute suffix of executables: cannot compile and link\nSee 'config.log' for more details\" \"$LINENO\" 5; } ;;\nesac\nfi\nrm -f conftest conftest$ac_cv_exeext\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_exeext\" >&5\nprintf \"%s\\n\" \"$ac_cv_exeext\" >&6; }\n\nrm -f conftest.$ac_ext\nEXEEXT=$ac_cv_exeext\nac_exeext=$EXEEXT\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <stdio.h>\nint\nmain (void)\n{\nFILE *f = fopen (\"conftest.out\", \"w\");\n if (!f)\n  return 1;\n return ferror (f) || fclose (f) != 0;\n\n  ;\n  return 0;\n}\n_ACEOF\nac_clean_files=\"$ac_clean_files conftest.out\"\n# Check that the compiler produces executables we can run.  If not, either\n# the compiler is broken, or we cross compile.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether we are cross compiling\" >&5\nprintf %s \"checking whether we are cross compiling... \" >&6; }\nif test \"$cross_compiling\" != yes; then\n  { { ac_try=\"$ac_link\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_link\") 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\n  if { ac_try='./conftest$ac_cv_exeext'\n  { { case \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_try\") 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; }; then\n    cross_compiling=no\n  else\n    if test \"$cross_compiling\" = maybe; then\n\tcross_compiling=yes\n    else\n\t{ { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error 77 \"cannot run C compiled programs.\nIf you meant to cross compile, use '--host'.\nSee 'config.log' for more details\" \"$LINENO\" 5; }\n    fi\n  fi\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $cross_compiling\" >&5\nprintf \"%s\\n\" \"$cross_compiling\" >&6; }\n\nrm -f conftest.$ac_ext conftest$ac_cv_exeext \\\n  conftest.o conftest.obj conftest.out\nac_clean_files=$ac_clean_files_save\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for suffix of object files\" >&5\nprintf %s \"checking for suffix of object files... \" >&6; }\nif test ${ac_cv_objext+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nrm -f conftest.o conftest.obj\nif { { ac_try=\"$ac_compile\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_compile\") 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\nthen :\n  for ac_file in conftest.o conftest.obj conftest.*; do\n  test -f \"$ac_file\" || continue;\n  case $ac_file in\n    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.map | *.inf | *.dSYM ) ;;\n    *) ac_cv_objext=`expr \"$ac_file\" : '.*\\.\\(.*\\)'`\n       break;;\n  esac\ndone\nelse case e in #(\n  e) printf \"%s\\n\" \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n{ { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error $? \"cannot compute suffix of object files: cannot compile\nSee 'config.log' for more details\" \"$LINENO\" 5; } ;;\nesac\nfi\nrm -f conftest.$ac_cv_objext conftest.$ac_ext ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_objext\" >&5\nprintf \"%s\\n\" \"$ac_cv_objext\" >&6; }\nOBJEXT=$ac_cv_objext\nac_objext=$OBJEXT\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether the compiler supports GNU C\" >&5\nprintf %s \"checking whether the compiler supports GNU C... \" >&6; }\nif test ${ac_cv_c_compiler_gnu+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n#ifndef __GNUC__\n       choke me\n#endif\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_compiler_gnu=yes\nelse case e in #(\n  e) ac_compiler_gnu=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\nac_cv_c_compiler_gnu=$ac_compiler_gnu\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_compiler_gnu\" >&5\nprintf \"%s\\n\" \"$ac_cv_c_compiler_gnu\" >&6; }\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\nif test $ac_compiler_gnu = yes; then\n  GCC=yes\nelse\n  GCC=\nfi\nac_test_CFLAGS=${CFLAGS+y}\nac_save_CFLAGS=$CFLAGS\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether $CC accepts -g\" >&5\nprintf %s \"checking whether $CC accepts -g... \" >&6; }\nif test ${ac_cv_prog_cc_g+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_save_c_werror_flag=$ac_c_werror_flag\n   ac_c_werror_flag=yes\n   ac_cv_prog_cc_g=no\n   CFLAGS=\"-g\"\n   cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cc_g=yes\nelse case e in #(\n  e) CFLAGS=\"\"\n      cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n\nelse case e in #(\n  e) ac_c_werror_flag=$ac_save_c_werror_flag\n\t CFLAGS=\"-g\"\n\t cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cc_g=yes\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n   ac_c_werror_flag=$ac_save_c_werror_flag ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_g\" >&5\nprintf \"%s\\n\" \"$ac_cv_prog_cc_g\" >&6; }\nif test $ac_test_CFLAGS; then\n  CFLAGS=$ac_save_CFLAGS\nelif test $ac_cv_prog_cc_g = yes; then\n  if test \"$GCC\" = yes; then\n    CFLAGS=\"-g -O2\"\n  else\n    CFLAGS=\"-g\"\n  fi\nelse\n  if test \"$GCC\" = yes; then\n    CFLAGS=\"-O2\"\n  else\n    CFLAGS=\n  fi\nfi\nac_prog_cc_stdc=no\nif test x$ac_prog_cc_stdc = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $CC option to enable C11 features\" >&5\nprintf %s \"checking for $CC option to enable C11 features... \" >&6; }\nif test ${ac_cv_prog_cc_c11+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_cv_prog_cc_c11=no\nac_save_CC=$CC\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$ac_c_conftest_c11_program\n_ACEOF\nfor ac_arg in '' -std=gnu11\ndo\n  CC=\"$ac_save_CC $ac_arg\"\n  if ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cc_c11=$ac_arg\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam\n  test \"x$ac_cv_prog_cc_c11\" != \"xno\" && break\ndone\nrm -f conftest.$ac_ext\nCC=$ac_save_CC ;;\nesac\nfi\n\nif test \"x$ac_cv_prog_cc_c11\" = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: unsupported\" >&5\nprintf \"%s\\n\" \"unsupported\" >&6; }\nelse case e in #(\n  e) if test \"x$ac_cv_prog_cc_c11\" = x\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: none needed\" >&5\nprintf \"%s\\n\" \"none needed\" >&6; }\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c11\" >&5\nprintf \"%s\\n\" \"$ac_cv_prog_cc_c11\" >&6; }\n     CC=\"$CC $ac_cv_prog_cc_c11\" ;;\nesac\nfi\n  ac_cv_prog_cc_stdc=$ac_cv_prog_cc_c11\n  ac_prog_cc_stdc=c11 ;;\nesac\nfi\nfi\nif test x$ac_prog_cc_stdc = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $CC option to enable C99 features\" >&5\nprintf %s \"checking for $CC option to enable C99 features... \" >&6; }\nif test ${ac_cv_prog_cc_c99+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_cv_prog_cc_c99=no\nac_save_CC=$CC\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$ac_c_conftest_c99_program\n_ACEOF\nfor ac_arg in '' -std=gnu99 -std=c99 -c99 -qlanglvl=extc1x -qlanglvl=extc99 -AC99 -D_STDC_C99=\ndo\n  CC=\"$ac_save_CC $ac_arg\"\n  if ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cc_c99=$ac_arg\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam\n  test \"x$ac_cv_prog_cc_c99\" != \"xno\" && break\ndone\nrm -f conftest.$ac_ext\nCC=$ac_save_CC ;;\nesac\nfi\n\nif test \"x$ac_cv_prog_cc_c99\" = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: unsupported\" >&5\nprintf \"%s\\n\" \"unsupported\" >&6; }\nelse case e in #(\n  e) if test \"x$ac_cv_prog_cc_c99\" = x\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: none needed\" >&5\nprintf \"%s\\n\" \"none needed\" >&6; }\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c99\" >&5\nprintf \"%s\\n\" \"$ac_cv_prog_cc_c99\" >&6; }\n     CC=\"$CC $ac_cv_prog_cc_c99\" ;;\nesac\nfi\n  ac_cv_prog_cc_stdc=$ac_cv_prog_cc_c99\n  ac_prog_cc_stdc=c99 ;;\nesac\nfi\nfi\nif test x$ac_prog_cc_stdc = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $CC option to enable C89 features\" >&5\nprintf %s \"checking for $CC option to enable C89 features... \" >&6; }\nif test ${ac_cv_prog_cc_c89+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_cv_prog_cc_c89=no\nac_save_CC=$CC\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$ac_c_conftest_c89_program\n_ACEOF\nfor ac_arg in '' -qlanglvl=extc89 -qlanglvl=ansi -std -Ae \"-Aa -D_HPUX_SOURCE\" \"-Xc -D__EXTENSIONS__\"\ndo\n  CC=\"$ac_save_CC $ac_arg\"\n  if ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cc_c89=$ac_arg\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam\n  test \"x$ac_cv_prog_cc_c89\" != \"xno\" && break\ndone\nrm -f conftest.$ac_ext\nCC=$ac_save_CC ;;\nesac\nfi\n\nif test \"x$ac_cv_prog_cc_c89\" = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: unsupported\" >&5\nprintf \"%s\\n\" \"unsupported\" >&6; }\nelse case e in #(\n  e) if test \"x$ac_cv_prog_cc_c89\" = x\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: none needed\" >&5\nprintf \"%s\\n\" \"none needed\" >&6; }\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cc_c89\" >&5\nprintf \"%s\\n\" \"$ac_cv_prog_cc_c89\" >&6; }\n     CC=\"$CC $ac_cv_prog_cc_c89\" ;;\nesac\nfi\n  ac_cv_prog_cc_stdc=$ac_cv_prog_cc_c89\n  ac_prog_cc_stdc=c89 ;;\nesac\nfi\nfi\n\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\n\n  ac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether $CC understands -c and -o together\" >&5\nprintf %s \"checking whether $CC understands -c and -o together... \" >&6; }\nif test ${am_cv_prog_cc_c_o+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\n  # Make sure it works both with $CC and with simple cc.\n  # Following AC_PROG_CC_C_O, we do the test twice because some\n  # compilers refuse to overwrite an existing .o file with -o,\n  # though they will create one.\n  am_cv_prog_cc_c_o=yes\n  for am_i in 1 2; do\n    if { echo \"$as_me:$LINENO: $CC -c conftest.$ac_ext -o conftest2.$ac_objext\" >&5\n   ($CC -c conftest.$ac_ext -o conftest2.$ac_objext) >&5 2>&5\n   ac_status=$?\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   (exit $ac_status); } \\\n         && test -f conftest2.$ac_objext; then\n      : OK\n    else\n      am_cv_prog_cc_c_o=no\n      break\n    fi\n  done\n  rm -f core conftest*\n  unset am_i ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $am_cv_prog_cc_c_o\" >&5\nprintf \"%s\\n\" \"$am_cv_prog_cc_c_o\" >&6; }\nif test \"$am_cv_prog_cc_c_o\" != yes; then\n   # Losing compiler, so override with the script.\n   # FIXME: It is wrong to rewrite CC.\n   # But if we don't then we get into trouble of one sort or another.\n   # A longer-term fix would be to have automake use am__CC in this case,\n   # and then we could set am__CC=\"\\$(top_srcdir)/compile \\$(CC)\"\n   CC=\"$am_aux_dir/compile $CC\"\nfi\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\nDEPDIR=\"${am__leading_dot}deps\"\n\nac_config_commands=\"$ac_config_commands depfiles\"\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether ${MAKE-make} supports the include directive\" >&5\nprintf %s \"checking whether ${MAKE-make} supports the include directive... \" >&6; }\ncat > confinc.mk << 'END'\nam__doit:\n\t@echo this is the am__doit target >confinc.out\n.PHONY: am__doit\nEND\nam__include=\"#\"\nam__quote=\n# BSD make does it like this.\necho '.include \"confinc.mk\" # ignored' > confmf.BSD\n# Other make implementations (GNU, Solaris 10, AIX) do it like this.\necho 'include confinc.mk # ignored' > confmf.GNU\n_am_result=no\nfor s in GNU BSD; do\n  { echo \"$as_me:$LINENO: ${MAKE-make} -f confmf.$s && cat confinc.out\" >&5\n   (${MAKE-make} -f confmf.$s && cat confinc.out) >&5 2>&5\n   ac_status=$?\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   (exit $ac_status); }\n  case $?:`cat confinc.out 2>/dev/null` in #(\n  '0:this is the am__doit target') :\n    case $s in #(\n  BSD) :\n    am__include='.include' am__quote='\"' ;; #(\n  *) :\n    am__include='include' am__quote='' ;;\nesac ;; #(\n  *) :\n     ;;\nesac\n  if test \"$am__include\" != \"#\"; then\n    _am_result=\"yes ($s style)\"\n    break\n  fi\ndone\nrm -f confinc.* confmf.*\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: ${_am_result}\" >&5\nprintf \"%s\\n\" \"${_am_result}\" >&6; }\n\n# Check whether --enable-dependency-tracking was given.\nif test ${enable_dependency_tracking+y}\nthen :\n  enableval=$enable_dependency_tracking;\nfi\n\nif test \"x$enable_dependency_tracking\" != xno; then\n  am_depcomp=\"$ac_aux_dir/depcomp\"\n  AMDEPBACKSLASH='\\'\n  am__nodep='_no'\nfi\n if test \"x$enable_dependency_tracking\" != xno; then\n  AMDEP_TRUE=\n  AMDEP_FALSE='#'\nelse\n  AMDEP_TRUE='#'\n  AMDEP_FALSE=\nfi\n\n\n\ndepcc=\"$CC\"   am_compiler_list=\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc\" >&5\nprintf %s \"checking dependency style of $depcc... \" >&6; }\nif test ${am_cv_CC_dependencies_compiler_type+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -z \"$AMDEP_TRUE\" && test -f \"$am_depcomp\"; then\n  # We make a subdir and do the tests there.  Otherwise we can end up\n  # making bogus files that we don't know about and never remove.  For\n  # instance it was reported that on HP-UX the gcc test will end up\n  # making a dummy file named 'D' -- because '-MD' means \"put the output\n  # in D\".\n  rm -rf conftest.dir\n  mkdir conftest.dir\n  # Copy depcomp to subdir because otherwise we won't find it if we're\n  # using a relative directory.\n  cp \"$am_depcomp\" conftest.dir\n  cd conftest.dir\n  # We will build objects and dependencies in a subdirectory because\n  # it helps to detect inapplicable dependency modes.  For instance\n  # both Tru64's cc and ICC support -MD to output dependencies as a\n  # side effect of compilation, but ICC will put the dependencies in\n  # the current directory while Tru64 will put them in the object\n  # directory.\n  mkdir sub\n\n  am_cv_CC_dependencies_compiler_type=none\n  if test \"$am_compiler_list\" = \"\"; then\n     am_compiler_list=`sed -n 's/^#*\\([a-zA-Z0-9]*\\))$/\\1/p' < ./depcomp`\n  fi\n  am__universal=false\n  case \" $depcc \" in #(\n     *\\ -arch\\ *\\ -arch\\ *) am__universal=true ;;\n     esac\n\n  for depmode in $am_compiler_list; do\n    # Setup a source with many dependencies, because some compilers\n    # like to wrap large dependency lists on column 80 (with \\), and\n    # we should not choose a depcomp mode which is confused by this.\n    #\n    # We need to recreate these files for each test, as the compiler may\n    # overwrite some of them when testing with obscure command lines.\n    # This happens at least with the AIX C compiler.\n    : > sub/conftest.c\n    for i in 1 2 3 4 5 6; do\n      echo '#include \"conftst'$i'.h\"' >> sub/conftest.c\n      # Using \": > sub/conftst$i.h\" creates only sub/conftst1.h with\n      # Solaris 10 /bin/sh.\n      echo '/* dummy */' > sub/conftst$i.h\n    done\n    echo \"${am__include} ${am__quote}sub/conftest.Po${am__quote}\" > confmf\n\n    # We check with '-c' and '-o' for the sake of the \"dashmstdout\"\n    # mode.  It turns out that the SunPro C++ compiler does not properly\n    # handle '-M -o', and we need to detect this.  Also, some Intel\n    # versions had trouble with output in subdirs.\n    am__obj=sub/conftest.${OBJEXT-o}\n    am__minus_obj=\"-o $am__obj\"\n    case $depmode in\n    gcc)\n      # This depmode causes a compiler race in universal mode.\n      test \"$am__universal\" = false || continue\n      ;;\n    nosideeffect)\n      # After this tag, mechanisms are not by side-effect, so they'll\n      # only be used when explicitly requested.\n      if test \"x$enable_dependency_tracking\" = xyes; then\n\tcontinue\n      else\n\tbreak\n      fi\n      ;;\n    msvc7 | msvc7msys | msvisualcpp | msvcmsys)\n      # This compiler won't grok '-c -o', but also, the minuso test has\n      # not run yet.  These depmodes are late enough in the game, and\n      # so weak that their functioning should not be impacted.\n      am__obj=conftest.${OBJEXT-o}\n      am__minus_obj=\n      ;;\n    none) break ;;\n    esac\n    if depmode=$depmode \\\n       source=sub/conftest.c object=$am__obj \\\n       depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \\\n       $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \\\n         >/dev/null 2>conftest.err &&\n       grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 &&\n       grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 &&\n       grep $am__obj sub/conftest.Po > /dev/null 2>&1 &&\n       ${MAKE-make} -s -f confmf > /dev/null 2>&1; then\n      # icc doesn't choke on unknown options, it will just issue warnings\n      # or remarks (even with -Werror).  So we grep stderr for any message\n      # that says an option was ignored or not supported.\n      # When given -MP, icc 7.0 and 7.1 complain thusly:\n      #   icc: Command line warning: ignoring option '-M'; no argument required\n      # The diagnosis changed in icc 8.0:\n      #   icc: Command line remark: option '-MP' not supported\n      if (grep 'ignoring option' conftest.err ||\n          grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else\n        am_cv_CC_dependencies_compiler_type=$depmode\n        break\n      fi\n    fi\n  done\n\n  cd ..\n  rm -rf conftest.dir\nelse\n  am_cv_CC_dependencies_compiler_type=none\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $am_cv_CC_dependencies_compiler_type\" >&5\nprintf \"%s\\n\" \"$am_cv_CC_dependencies_compiler_type\" >&6; }\nCCDEPMODE=depmode=$am_cv_CC_dependencies_compiler_type\n\n if\n  test \"x$enable_dependency_tracking\" != xno \\\n  && test \"$am_cv_CC_dependencies_compiler_type\" = gcc3; then\n  am__fastdepCC_TRUE=\n  am__fastdepCC_FALSE='#'\nelse\n  am__fastdepCC_TRUE='#'\n  am__fastdepCC_FALSE=\nfi\n\n\n\n\n\n\n\n\nac_ext=cpp\nac_cpp='$CXXCPP $CPPFLAGS'\nac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_cxx_compiler_gnu\nif test -z \"$CXX\"; then\n  if test -n \"$CCC\"; then\n    CXX=$CCC\n  else\n    if test -n \"$ac_tool_prefix\"; then\n  for ac_prog in g++ c++ gpp aCC CC cxx cc++ cl.exe FCC KCC RCC xlC_r xlC clang++\n  do\n    # Extract the first word of \"$ac_tool_prefix$ac_prog\", so it can be a program name with args.\nset dummy $ac_tool_prefix$ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$CXX\"; then\n  ac_cv_prog_CXX=\"$CXX\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_CXX=\"$ac_tool_prefix$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nCXX=$ac_cv_prog_CXX\nif test -n \"$CXX\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $CXX\" >&5\nprintf \"%s\\n\" \"$CXX\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n    test -n \"$CXX\" && break\n  done\nfi\nif test -z \"$CXX\"; then\n  ac_ct_CXX=$CXX\n  for ac_prog in g++ c++ gpp aCC CC cxx cc++ cl.exe FCC KCC RCC xlC_r xlC clang++\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_CXX\"; then\n  ac_cv_prog_ac_ct_CXX=\"$ac_ct_CXX\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_CXX=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_CXX=$ac_cv_prog_ac_ct_CXX\nif test -n \"$ac_ct_CXX\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_CXX\" >&5\nprintf \"%s\\n\" \"$ac_ct_CXX\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$ac_ct_CXX\" && break\ndone\n\n  if test \"x$ac_ct_CXX\" = x; then\n    CXX=\"g++\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    CXX=$ac_ct_CXX\n  fi\nfi\n\n  fi\nfi\n# Provide some information about the compiler.\nprintf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for C++ compiler version\" >&5\nset X $ac_compile\nac_compiler=$2\nfor ac_option in --version -v -V -qversion; do\n  { { ac_try=\"$ac_compiler $ac_option >&5\"\ncase \"(($ac_try\" in\n  *\\\"* | *\\`* | *\\\\*) ac_try_echo=\\$ac_try;;\n  *) ac_try_echo=$ac_try;;\nesac\neval ac_try_echo=\"\\\"\\$as_me:${as_lineno-$LINENO}: $ac_try_echo\\\"\"\nprintf \"%s\\n\" \"$ac_try_echo\"; } >&5\n  (eval \"$ac_compiler $ac_option >&5\") 2>conftest.err\n  ac_status=$?\n  if test -s conftest.err; then\n    sed '10a\\\n... rest of stderr output deleted ...\n         10q' conftest.err >conftest.er1\n    cat conftest.er1 >&5\n  fi\n  rm -f conftest.er1 conftest.err\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\ndone\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether the compiler supports GNU C++\" >&5\nprintf %s \"checking whether the compiler supports GNU C++... \" >&6; }\nif test ${ac_cv_cxx_compiler_gnu+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n#ifndef __GNUC__\n       choke me\n#endif\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_cxx_try_compile \"$LINENO\"\nthen :\n  ac_compiler_gnu=yes\nelse case e in #(\n  e) ac_compiler_gnu=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\nac_cv_cxx_compiler_gnu=$ac_compiler_gnu\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_cxx_compiler_gnu\" >&5\nprintf \"%s\\n\" \"$ac_cv_cxx_compiler_gnu\" >&6; }\nac_compiler_gnu=$ac_cv_cxx_compiler_gnu\n\nif test $ac_compiler_gnu = yes; then\n  GXX=yes\nelse\n  GXX=\nfi\nac_test_CXXFLAGS=${CXXFLAGS+y}\nac_save_CXXFLAGS=$CXXFLAGS\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether $CXX accepts -g\" >&5\nprintf %s \"checking whether $CXX accepts -g... \" >&6; }\nif test ${ac_cv_prog_cxx_g+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_save_cxx_werror_flag=$ac_cxx_werror_flag\n   ac_cxx_werror_flag=yes\n   ac_cv_prog_cxx_g=no\n   CXXFLAGS=\"-g\"\n   cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_cxx_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cxx_g=yes\nelse case e in #(\n  e) CXXFLAGS=\"\"\n      cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_cxx_try_compile \"$LINENO\"\nthen :\n\nelse case e in #(\n  e) ac_cxx_werror_flag=$ac_save_cxx_werror_flag\n\t CXXFLAGS=\"-g\"\n\t cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_cxx_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cxx_g=yes\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n   ac_cxx_werror_flag=$ac_save_cxx_werror_flag ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cxx_g\" >&5\nprintf \"%s\\n\" \"$ac_cv_prog_cxx_g\" >&6; }\nif test $ac_test_CXXFLAGS; then\n  CXXFLAGS=$ac_save_CXXFLAGS\nelif test $ac_cv_prog_cxx_g = yes; then\n  if test \"$GXX\" = yes; then\n    CXXFLAGS=\"-g -O2\"\n  else\n    CXXFLAGS=\"-g\"\n  fi\nelse\n  if test \"$GXX\" = yes; then\n    CXXFLAGS=\"-O2\"\n  else\n    CXXFLAGS=\n  fi\nfi\nac_prog_cxx_stdcxx=no\nif test x$ac_prog_cxx_stdcxx = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $CXX option to enable C++11 features\" >&5\nprintf %s \"checking for $CXX option to enable C++11 features... \" >&6; }\nif test ${ac_cv_prog_cxx_cxx11+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_cv_prog_cxx_cxx11=no\nac_save_CXX=$CXX\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$ac_cxx_conftest_cxx11_program\n_ACEOF\nfor ac_arg in '' -std=gnu++11 -std=gnu++0x -std=c++11 -std=c++0x -qlanglvl=extended0x -AA\ndo\n  CXX=\"$ac_save_CXX $ac_arg\"\n  if ac_fn_cxx_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cxx_cxx11=$ac_arg\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam\n  test \"x$ac_cv_prog_cxx_cxx11\" != \"xno\" && break\ndone\nrm -f conftest.$ac_ext\nCXX=$ac_save_CXX ;;\nesac\nfi\n\nif test \"x$ac_cv_prog_cxx_cxx11\" = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: unsupported\" >&5\nprintf \"%s\\n\" \"unsupported\" >&6; }\nelse case e in #(\n  e) if test \"x$ac_cv_prog_cxx_cxx11\" = x\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: none needed\" >&5\nprintf \"%s\\n\" \"none needed\" >&6; }\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cxx_cxx11\" >&5\nprintf \"%s\\n\" \"$ac_cv_prog_cxx_cxx11\" >&6; }\n     CXX=\"$CXX $ac_cv_prog_cxx_cxx11\" ;;\nesac\nfi\n  ac_cv_prog_cxx_stdcxx=$ac_cv_prog_cxx_cxx11\n  ac_prog_cxx_stdcxx=cxx11 ;;\nesac\nfi\nfi\nif test x$ac_prog_cxx_stdcxx = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $CXX option to enable C++98 features\" >&5\nprintf %s \"checking for $CXX option to enable C++98 features... \" >&6; }\nif test ${ac_cv_prog_cxx_cxx98+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_cv_prog_cxx_cxx98=no\nac_save_CXX=$CXX\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$ac_cxx_conftest_cxx98_program\n_ACEOF\nfor ac_arg in '' -std=gnu++98 -std=c++98 -qlanglvl=extended -AA\ndo\n  CXX=\"$ac_save_CXX $ac_arg\"\n  if ac_fn_cxx_try_compile \"$LINENO\"\nthen :\n  ac_cv_prog_cxx_cxx98=$ac_arg\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam\n  test \"x$ac_cv_prog_cxx_cxx98\" != \"xno\" && break\ndone\nrm -f conftest.$ac_ext\nCXX=$ac_save_CXX ;;\nesac\nfi\n\nif test \"x$ac_cv_prog_cxx_cxx98\" = xno\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: unsupported\" >&5\nprintf \"%s\\n\" \"unsupported\" >&6; }\nelse case e in #(\n  e) if test \"x$ac_cv_prog_cxx_cxx98\" = x\nthen :\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: none needed\" >&5\nprintf \"%s\\n\" \"none needed\" >&6; }\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_prog_cxx_cxx98\" >&5\nprintf \"%s\\n\" \"$ac_cv_prog_cxx_cxx98\" >&6; }\n     CXX=\"$CXX $ac_cv_prog_cxx_cxx98\" ;;\nesac\nfi\n  ac_cv_prog_cxx_stdcxx=$ac_cv_prog_cxx_cxx98\n  ac_prog_cxx_stdcxx=cxx98 ;;\nesac\nfi\nfi\n\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\ndepcc=\"$CXX\"  am_compiler_list=\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking dependency style of $depcc\" >&5\nprintf %s \"checking dependency style of $depcc... \" >&6; }\nif test ${am_cv_CXX_dependencies_compiler_type+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -z \"$AMDEP_TRUE\" && test -f \"$am_depcomp\"; then\n  # We make a subdir and do the tests there.  Otherwise we can end up\n  # making bogus files that we don't know about and never remove.  For\n  # instance it was reported that on HP-UX the gcc test will end up\n  # making a dummy file named 'D' -- because '-MD' means \"put the output\n  # in D\".\n  rm -rf conftest.dir\n  mkdir conftest.dir\n  # Copy depcomp to subdir because otherwise we won't find it if we're\n  # using a relative directory.\n  cp \"$am_depcomp\" conftest.dir\n  cd conftest.dir\n  # We will build objects and dependencies in a subdirectory because\n  # it helps to detect inapplicable dependency modes.  For instance\n  # both Tru64's cc and ICC support -MD to output dependencies as a\n  # side effect of compilation, but ICC will put the dependencies in\n  # the current directory while Tru64 will put them in the object\n  # directory.\n  mkdir sub\n\n  am_cv_CXX_dependencies_compiler_type=none\n  if test \"$am_compiler_list\" = \"\"; then\n     am_compiler_list=`sed -n 's/^#*\\([a-zA-Z0-9]*\\))$/\\1/p' < ./depcomp`\n  fi\n  am__universal=false\n  case \" $depcc \" in #(\n     *\\ -arch\\ *\\ -arch\\ *) am__universal=true ;;\n     esac\n\n  for depmode in $am_compiler_list; do\n    # Setup a source with many dependencies, because some compilers\n    # like to wrap large dependency lists on column 80 (with \\), and\n    # we should not choose a depcomp mode which is confused by this.\n    #\n    # We need to recreate these files for each test, as the compiler may\n    # overwrite some of them when testing with obscure command lines.\n    # This happens at least with the AIX C compiler.\n    : > sub/conftest.c\n    for i in 1 2 3 4 5 6; do\n      echo '#include \"conftst'$i'.h\"' >> sub/conftest.c\n      # Using \": > sub/conftst$i.h\" creates only sub/conftst1.h with\n      # Solaris 10 /bin/sh.\n      echo '/* dummy */' > sub/conftst$i.h\n    done\n    echo \"${am__include} ${am__quote}sub/conftest.Po${am__quote}\" > confmf\n\n    # We check with '-c' and '-o' for the sake of the \"dashmstdout\"\n    # mode.  It turns out that the SunPro C++ compiler does not properly\n    # handle '-M -o', and we need to detect this.  Also, some Intel\n    # versions had trouble with output in subdirs.\n    am__obj=sub/conftest.${OBJEXT-o}\n    am__minus_obj=\"-o $am__obj\"\n    case $depmode in\n    gcc)\n      # This depmode causes a compiler race in universal mode.\n      test \"$am__universal\" = false || continue\n      ;;\n    nosideeffect)\n      # After this tag, mechanisms are not by side-effect, so they'll\n      # only be used when explicitly requested.\n      if test \"x$enable_dependency_tracking\" = xyes; then\n\tcontinue\n      else\n\tbreak\n      fi\n      ;;\n    msvc7 | msvc7msys | msvisualcpp | msvcmsys)\n      # This compiler won't grok '-c -o', but also, the minuso test has\n      # not run yet.  These depmodes are late enough in the game, and\n      # so weak that their functioning should not be impacted.\n      am__obj=conftest.${OBJEXT-o}\n      am__minus_obj=\n      ;;\n    none) break ;;\n    esac\n    if depmode=$depmode \\\n       source=sub/conftest.c object=$am__obj \\\n       depfile=sub/conftest.Po tmpdepfile=sub/conftest.TPo \\\n       $SHELL ./depcomp $depcc -c $am__minus_obj sub/conftest.c \\\n         >/dev/null 2>conftest.err &&\n       grep sub/conftst1.h sub/conftest.Po > /dev/null 2>&1 &&\n       grep sub/conftst6.h sub/conftest.Po > /dev/null 2>&1 &&\n       grep $am__obj sub/conftest.Po > /dev/null 2>&1 &&\n       ${MAKE-make} -s -f confmf > /dev/null 2>&1; then\n      # icc doesn't choke on unknown options, it will just issue warnings\n      # or remarks (even with -Werror).  So we grep stderr for any message\n      # that says an option was ignored or not supported.\n      # When given -MP, icc 7.0 and 7.1 complain thusly:\n      #   icc: Command line warning: ignoring option '-M'; no argument required\n      # The diagnosis changed in icc 8.0:\n      #   icc: Command line remark: option '-MP' not supported\n      if (grep 'ignoring option' conftest.err ||\n          grep 'not supported' conftest.err) >/dev/null 2>&1; then :; else\n        am_cv_CXX_dependencies_compiler_type=$depmode\n        break\n      fi\n    fi\n  done\n\n  cd ..\n  rm -rf conftest.dir\nelse\n  am_cv_CXX_dependencies_compiler_type=none\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $am_cv_CXX_dependencies_compiler_type\" >&5\nprintf \"%s\\n\" \"$am_cv_CXX_dependencies_compiler_type\" >&6; }\nCXXDEPMODE=depmode=$am_cv_CXX_dependencies_compiler_type\n\n if\n  test \"x$enable_dependency_tracking\" != xno \\\n  && test \"$am_cv_CXX_dependencies_compiler_type\" = gcc3; then\n  am__fastdepCXX_TRUE=\n  am__fastdepCXX_FALSE='#'\nelse\n  am__fastdepCXX_TRUE='#'\n  am__fastdepCXX_FALSE=\nfi\n\n\n\n\n  if test -n \"$ac_tool_prefix\"; then\n  for ac_prog in ar lib \"link -lib\"\n  do\n    # Extract the first word of \"$ac_tool_prefix$ac_prog\", so it can be a program name with args.\nset dummy $ac_tool_prefix$ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_AR+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$AR\"; then\n  ac_cv_prog_AR=\"$AR\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_AR=\"$ac_tool_prefix$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nAR=$ac_cv_prog_AR\nif test -n \"$AR\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $AR\" >&5\nprintf \"%s\\n\" \"$AR\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n    test -n \"$AR\" && break\n  done\nfi\nif test -z \"$AR\"; then\n  ac_ct_AR=$AR\n  for ac_prog in ar lib \"link -lib\"\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_AR+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_AR\"; then\n  ac_cv_prog_ac_ct_AR=\"$ac_ct_AR\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_AR=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_AR=$ac_cv_prog_ac_ct_AR\nif test -n \"$ac_ct_AR\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_AR\" >&5\nprintf \"%s\\n\" \"$ac_ct_AR\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$ac_ct_AR\" && break\ndone\n\n  if test \"x$ac_ct_AR\" = x; then\n    AR=\"false\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    AR=$ac_ct_AR\n  fi\nfi\n\n: ${AR=ar}\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking the archiver ($AR) interface\" >&5\nprintf %s \"checking the archiver ($AR) interface... \" >&6; }\nif test ${am_cv_ar_interface+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\n   am_cv_ar_interface=ar\n   cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\nint some_variable = 0;\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  am_ar_try='$AR cru libconftest.a conftest.$ac_objext >&5'\n      { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$am_ar_try\\\"\"; } >&5\n  (eval $am_ar_try) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\n      if test \"$ac_status\" -eq 0; then\n        am_cv_ar_interface=ar\n      else\n        am_ar_try='$AR -NOLOGO -OUT:conftest.lib conftest.$ac_objext >&5'\n        { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$am_ar_try\\\"\"; } >&5\n  (eval $am_ar_try) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\n        if test \"$ac_status\" -eq 0; then\n          am_cv_ar_interface=lib\n        else\n          am_cv_ar_interface=unknown\n        fi\n      fi\n      rm -f conftest.lib libconftest.a\n\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n   ac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $am_cv_ar_interface\" >&5\nprintf \"%s\\n\" \"$am_cv_ar_interface\" >&6; }\n\ncase $am_cv_ar_interface in\nar)\n  ;;\nlib)\n  # Microsoft lib, so override with the ar-lib wrapper script.\n  # FIXME: It is wrong to rewrite AR.\n  # But if we don't then we get into trouble of one sort or another.\n  # A longer-term fix would be to have automake use am__AR in this case,\n  # and then we could set am__AR=\"$am_aux_dir/ar-lib \\$(AR)\" or something\n  # similar.\n  AR=\"$am_aux_dir/ar-lib $AR\"\n  ;;\nunknown)\n  as_fn_error $? \"could not determine $AR interface\" \"$LINENO\" 5\n  ;;\nesac\n\n\ncase `pwd` in\n  *\\ * | *\\\t*)\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: Libtool does not cope well with whitespace in \\`pwd\\`\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: Libtool does not cope well with whitespace in \\`pwd\\`\" >&2;} ;;\nesac\n\n\n\nmacro_version='2.4.7'\nmacro_revision='2.4.7'\n\n\n\n\n\n\n\n\n\n\n\n\n\n\nltmain=$ac_aux_dir/ltmain.sh\n\n# Backslashify metacharacters that are still active within\n# double-quoted strings.\nsed_quote_subst='s/\\([\"`$\\\\]\\)/\\\\\\1/g'\n\n# Same as above, but do not quote variable references.\ndouble_quote_subst='s/\\([\"`\\\\]\\)/\\\\\\1/g'\n\n# Sed substitution to delay expansion of an escaped shell variable in a\n# double_quote_subst'ed string.\ndelay_variable_subst='s/\\\\\\\\\\\\\\\\\\\\\\$/\\\\\\\\\\\\$/g'\n\n# Sed substitution to delay expansion of an escaped single quote.\ndelay_single_quote_subst='s/'\\''/'\\'\\\\\\\\\\\\\\'\\''/g'\n\n# Sed substitution to avoid accidental globbing in evaled expressions\nno_glob_subst='s/\\*/\\\\\\*/g'\n\nECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'\nECHO=$ECHO$ECHO$ECHO$ECHO$ECHO\nECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to print strings\" >&5\nprintf %s \"checking how to print strings... \" >&6; }\n# Test print first, because it will be a builtin if present.\nif test \"X`( print -r -- -n ) 2>/dev/null`\" = X-n && \\\n   test \"X`print -r -- $ECHO 2>/dev/null`\" = \"X$ECHO\"; then\n  ECHO='print -r --'\nelif test \"X`printf %s $ECHO 2>/dev/null`\" = \"X$ECHO\"; then\n  ECHO='printf %s\\n'\nelse\n  # Use this function as a fallback that always works.\n  func_fallback_echo ()\n  {\n    eval 'cat <<_LTECHO_EOF\n$1\n_LTECHO_EOF'\n  }\n  ECHO='func_fallback_echo'\nfi\n\n# func_echo_all arg...\n# Invoke $ECHO with all args, space-separated.\nfunc_echo_all ()\n{\n    $ECHO \"\"\n}\n\ncase $ECHO in\n  printf*) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: printf\" >&5\nprintf \"%s\\n\" \"printf\" >&6; } ;;\n  print*) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: print -r\" >&5\nprintf \"%s\\n\" \"print -r\" >&6; } ;;\n  *) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: cat\" >&5\nprintf \"%s\\n\" \"cat\" >&6; } ;;\nesac\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for a sed that does not truncate output\" >&5\nprintf %s \"checking for a sed that does not truncate output... \" >&6; }\nif test ${ac_cv_path_SED+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e)           ac_script=s/aaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaaa/bbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbbb/\n     for ac_i in 1 2 3 4 5 6 7; do\n       ac_script=\"$ac_script$as_nl$ac_script\"\n     done\n     echo \"$ac_script\" 2>/dev/null | sed 99q >conftest.sed\n     { ac_script=; unset ac_script;}\n     if test -z \"$SED\"; then\n  ac_path_SED_found=false\n  # Loop through the user's path and test for each of PROGNAME-LIST\n  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_prog in sed gsed\n   do\n    for ac_exec_ext in '' $ac_executable_extensions; do\n      ac_path_SED=\"$as_dir$ac_prog$ac_exec_ext\"\n      as_fn_executable_p \"$ac_path_SED\" || continue\n# Check for GNU ac_path_SED and select it if it is found.\n  # Check for GNU $ac_path_SED\ncase `\"$ac_path_SED\" --version 2>&1` in #(\n*GNU*)\n  ac_cv_path_SED=\"$ac_path_SED\" ac_path_SED_found=:;;\n#(\n*)\n  ac_count=0\n  printf %s 0123456789 >\"conftest.in\"\n  while :\n  do\n    cat \"conftest.in\" \"conftest.in\" >\"conftest.tmp\"\n    mv \"conftest.tmp\" \"conftest.in\"\n    cp \"conftest.in\" \"conftest.nl\"\n    printf \"%s\\n\" '' >> \"conftest.nl\"\n    \"$ac_path_SED\" -f conftest.sed < \"conftest.nl\" >\"conftest.out\" 2>/dev/null || break\n    diff \"conftest.out\" \"conftest.nl\" >/dev/null 2>&1 || break\n    as_fn_arith $ac_count + 1 && ac_count=$as_val\n    if test $ac_count -gt ${ac_path_SED_max-0}; then\n      # Best one so far, save it but keep looking for a better one\n      ac_cv_path_SED=\"$ac_path_SED\"\n      ac_path_SED_max=$ac_count\n    fi\n    # 10*(2^10) chars as input seems more than enough\n    test $ac_count -gt 10 && break\n  done\n  rm -f conftest.in conftest.tmp conftest.nl conftest.out;;\nesac\n\n      $ac_path_SED_found && break 3\n    done\n  done\n  done\nIFS=$as_save_IFS\n  if test -z \"$ac_cv_path_SED\"; then\n    as_fn_error $? \"no acceptable sed could be found in \\$PATH\" \"$LINENO\" 5\n  fi\nelse\n  ac_cv_path_SED=$SED\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_SED\" >&5\nprintf \"%s\\n\" \"$ac_cv_path_SED\" >&6; }\n SED=\"$ac_cv_path_SED\"\n  rm -f conftest.sed\n\ntest -z \"$SED\" && SED=sed\nXsed=\"$SED -e 1s/^X//\"\n\n\n\n\n\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for grep that handles long lines and -e\" >&5\nprintf %s \"checking for grep that handles long lines and -e... \" >&6; }\nif test ${ac_cv_path_GREP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -z \"$GREP\"; then\n  ac_path_GREP_found=false\n  # Loop through the user's path and test for each of PROGNAME-LIST\n  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_prog in grep ggrep\n   do\n    for ac_exec_ext in '' $ac_executable_extensions; do\n      ac_path_GREP=\"$as_dir$ac_prog$ac_exec_ext\"\n      as_fn_executable_p \"$ac_path_GREP\" || continue\n# Check for GNU ac_path_GREP and select it if it is found.\n  # Check for GNU $ac_path_GREP\ncase `\"$ac_path_GREP\" --version 2>&1` in #(\n*GNU*)\n  ac_cv_path_GREP=\"$ac_path_GREP\" ac_path_GREP_found=:;;\n#(\n*)\n  ac_count=0\n  printf %s 0123456789 >\"conftest.in\"\n  while :\n  do\n    cat \"conftest.in\" \"conftest.in\" >\"conftest.tmp\"\n    mv \"conftest.tmp\" \"conftest.in\"\n    cp \"conftest.in\" \"conftest.nl\"\n    printf \"%s\\n\" 'GREP' >> \"conftest.nl\"\n    \"$ac_path_GREP\" -e 'GREP$' -e '-(cannot match)-' < \"conftest.nl\" >\"conftest.out\" 2>/dev/null || break\n    diff \"conftest.out\" \"conftest.nl\" >/dev/null 2>&1 || break\n    as_fn_arith $ac_count + 1 && ac_count=$as_val\n    if test $ac_count -gt ${ac_path_GREP_max-0}; then\n      # Best one so far, save it but keep looking for a better one\n      ac_cv_path_GREP=\"$ac_path_GREP\"\n      ac_path_GREP_max=$ac_count\n    fi\n    # 10*(2^10) chars as input seems more than enough\n    test $ac_count -gt 10 && break\n  done\n  rm -f conftest.in conftest.tmp conftest.nl conftest.out;;\nesac\n\n      $ac_path_GREP_found && break 3\n    done\n  done\n  done\nIFS=$as_save_IFS\n  if test -z \"$ac_cv_path_GREP\"; then\n    as_fn_error $? \"no acceptable grep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin\" \"$LINENO\" 5\n  fi\nelse\n  ac_cv_path_GREP=$GREP\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_GREP\" >&5\nprintf \"%s\\n\" \"$ac_cv_path_GREP\" >&6; }\n GREP=\"$ac_cv_path_GREP\"\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for egrep\" >&5\nprintf %s \"checking for egrep... \" >&6; }\nif test ${ac_cv_path_EGREP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if echo a | $GREP -E '(a|b)' >/dev/null 2>&1\n   then ac_cv_path_EGREP=\"$GREP -E\"\n   else\n     if test -z \"$EGREP\"; then\n  ac_path_EGREP_found=false\n  # Loop through the user's path and test for each of PROGNAME-LIST\n  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_prog in egrep\n   do\n    for ac_exec_ext in '' $ac_executable_extensions; do\n      ac_path_EGREP=\"$as_dir$ac_prog$ac_exec_ext\"\n      as_fn_executable_p \"$ac_path_EGREP\" || continue\n# Check for GNU ac_path_EGREP and select it if it is found.\n  # Check for GNU $ac_path_EGREP\ncase `\"$ac_path_EGREP\" --version 2>&1` in #(\n*GNU*)\n  ac_cv_path_EGREP=\"$ac_path_EGREP\" ac_path_EGREP_found=:;;\n#(\n*)\n  ac_count=0\n  printf %s 0123456789 >\"conftest.in\"\n  while :\n  do\n    cat \"conftest.in\" \"conftest.in\" >\"conftest.tmp\"\n    mv \"conftest.tmp\" \"conftest.in\"\n    cp \"conftest.in\" \"conftest.nl\"\n    printf \"%s\\n\" 'EGREP' >> \"conftest.nl\"\n    \"$ac_path_EGREP\" 'EGREP$' < \"conftest.nl\" >\"conftest.out\" 2>/dev/null || break\n    diff \"conftest.out\" \"conftest.nl\" >/dev/null 2>&1 || break\n    as_fn_arith $ac_count + 1 && ac_count=$as_val\n    if test $ac_count -gt ${ac_path_EGREP_max-0}; then\n      # Best one so far, save it but keep looking for a better one\n      ac_cv_path_EGREP=\"$ac_path_EGREP\"\n      ac_path_EGREP_max=$ac_count\n    fi\n    # 10*(2^10) chars as input seems more than enough\n    test $ac_count -gt 10 && break\n  done\n  rm -f conftest.in conftest.tmp conftest.nl conftest.out;;\nesac\n\n      $ac_path_EGREP_found && break 3\n    done\n  done\n  done\nIFS=$as_save_IFS\n  if test -z \"$ac_cv_path_EGREP\"; then\n    as_fn_error $? \"no acceptable egrep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin\" \"$LINENO\" 5\n  fi\nelse\n  ac_cv_path_EGREP=$EGREP\nfi\n\n   fi ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_EGREP\" >&5\nprintf \"%s\\n\" \"$ac_cv_path_EGREP\" >&6; }\n EGREP=\"$ac_cv_path_EGREP\"\n\n         EGREP_TRADITIONAL=$EGREP\n ac_cv_path_EGREP_TRADITIONAL=$EGREP\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for fgrep\" >&5\nprintf %s \"checking for fgrep... \" >&6; }\nif test ${ac_cv_path_FGREP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if echo 'ab*c' | $GREP -F 'ab*c' >/dev/null 2>&1\n   then ac_cv_path_FGREP=\"$GREP -F\"\n   else\n     if test -z \"$FGREP\"; then\n  ac_path_FGREP_found=false\n  # Loop through the user's path and test for each of PROGNAME-LIST\n  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH$PATH_SEPARATOR/usr/xpg4/bin\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_prog in fgrep\n   do\n    for ac_exec_ext in '' $ac_executable_extensions; do\n      ac_path_FGREP=\"$as_dir$ac_prog$ac_exec_ext\"\n      as_fn_executable_p \"$ac_path_FGREP\" || continue\n# Check for GNU ac_path_FGREP and select it if it is found.\n  # Check for GNU $ac_path_FGREP\ncase `\"$ac_path_FGREP\" --version 2>&1` in #(\n*GNU*)\n  ac_cv_path_FGREP=\"$ac_path_FGREP\" ac_path_FGREP_found=:;;\n#(\n*)\n  ac_count=0\n  printf %s 0123456789 >\"conftest.in\"\n  while :\n  do\n    cat \"conftest.in\" \"conftest.in\" >\"conftest.tmp\"\n    mv \"conftest.tmp\" \"conftest.in\"\n    cp \"conftest.in\" \"conftest.nl\"\n    printf \"%s\\n\" 'FGREP' >> \"conftest.nl\"\n    \"$ac_path_FGREP\" FGREP < \"conftest.nl\" >\"conftest.out\" 2>/dev/null || break\n    diff \"conftest.out\" \"conftest.nl\" >/dev/null 2>&1 || break\n    as_fn_arith $ac_count + 1 && ac_count=$as_val\n    if test $ac_count -gt ${ac_path_FGREP_max-0}; then\n      # Best one so far, save it but keep looking for a better one\n      ac_cv_path_FGREP=\"$ac_path_FGREP\"\n      ac_path_FGREP_max=$ac_count\n    fi\n    # 10*(2^10) chars as input seems more than enough\n    test $ac_count -gt 10 && break\n  done\n  rm -f conftest.in conftest.tmp conftest.nl conftest.out;;\nesac\n\n      $ac_path_FGREP_found && break 3\n    done\n  done\n  done\nIFS=$as_save_IFS\n  if test -z \"$ac_cv_path_FGREP\"; then\n    as_fn_error $? \"no acceptable fgrep could be found in $PATH$PATH_SEPARATOR/usr/xpg4/bin\" \"$LINENO\" 5\n  fi\nelse\n  ac_cv_path_FGREP=$FGREP\nfi\n\n   fi ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_FGREP\" >&5\nprintf \"%s\\n\" \"$ac_cv_path_FGREP\" >&6; }\n FGREP=\"$ac_cv_path_FGREP\"\n\n\ntest -z \"$GREP\" && GREP=grep\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n# Check whether --with-gnu-ld was given.\nif test ${with_gnu_ld+y}\nthen :\n  withval=$with_gnu_ld; test no = \"$withval\" || with_gnu_ld=yes\nelse case e in #(\n  e) with_gnu_ld=no ;;\nesac\nfi\n\nac_prog=ld\nif test yes = \"$GCC\"; then\n  # Check if gcc -print-prog-name=ld gives a path.\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for ld used by $CC\" >&5\nprintf %s \"checking for ld used by $CC... \" >&6; }\n  case $host in\n  *-*-mingw*)\n    # gcc leaves a trailing carriage return, which upsets mingw\n    ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\\015'` ;;\n  *)\n    ac_prog=`($CC -print-prog-name=ld) 2>&5` ;;\n  esac\n  case $ac_prog in\n    # Accept absolute paths.\n    [\\\\/]* | ?:[\\\\/]*)\n      re_direlt='/[^/][^/]*/\\.\\./'\n      # Canonicalize the pathname of ld\n      ac_prog=`$ECHO \"$ac_prog\"| $SED 's%\\\\\\\\%/%g'`\n      while $ECHO \"$ac_prog\" | $GREP \"$re_direlt\" > /dev/null 2>&1; do\n\tac_prog=`$ECHO $ac_prog| $SED \"s%$re_direlt%/%\"`\n      done\n      test -z \"$LD\" && LD=$ac_prog\n      ;;\n  \"\")\n    # If it fails, then pretend we aren't using GCC.\n    ac_prog=ld\n    ;;\n  *)\n    # If it is relative, then search for the first ld in PATH.\n    with_gnu_ld=unknown\n    ;;\n  esac\nelif test yes = \"$with_gnu_ld\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for GNU ld\" >&5\nprintf %s \"checking for GNU ld... \" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for non-GNU ld\" >&5\nprintf %s \"checking for non-GNU ld... \" >&6; }\nfi\nif test ${lt_cv_path_LD+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -z \"$LD\"; then\n  lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR\n  for ac_dir in $PATH; do\n    IFS=$lt_save_ifs\n    test -z \"$ac_dir\" && ac_dir=.\n    if test -f \"$ac_dir/$ac_prog\" || test -f \"$ac_dir/$ac_prog$ac_exeext\"; then\n      lt_cv_path_LD=$ac_dir/$ac_prog\n      # Check to see if the program is GNU ld.  I'd rather use --version,\n      # but apparently some variants of GNU ld only accept -v.\n      # Break only if it was the GNU/non-GNU ld that we prefer.\n      case `\"$lt_cv_path_LD\" -v 2>&1 </dev/null` in\n      *GNU* | *'with BFD'*)\n\ttest no != \"$with_gnu_ld\" && break\n\t;;\n      *)\n\ttest yes != \"$with_gnu_ld\" && break\n\t;;\n      esac\n    fi\n  done\n  IFS=$lt_save_ifs\nelse\n  lt_cv_path_LD=$LD # Let the user override the test with a path.\nfi ;;\nesac\nfi\n\nLD=$lt_cv_path_LD\nif test -n \"$LD\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $LD\" >&5\nprintf \"%s\\n\" \"$LD\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\ntest -z \"$LD\" && as_fn_error $? \"no acceptable ld found in \\$PATH\" \"$LINENO\" 5\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if the linker ($LD) is GNU ld\" >&5\nprintf %s \"checking if the linker ($LD) is GNU ld... \" >&6; }\nif test ${lt_cv_prog_gnu_ld+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) # I'd rather use --version here, but apparently some GNU lds only accept -v.\ncase `$LD -v 2>&1 </dev/null` in\n*GNU* | *'with BFD'*)\n  lt_cv_prog_gnu_ld=yes\n  ;;\n*)\n  lt_cv_prog_gnu_ld=no\n  ;;\nesac ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_gnu_ld\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_gnu_ld\" >&6; }\nwith_gnu_ld=$lt_cv_prog_gnu_ld\n\n\n\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for BSD- or MS-compatible name lister (nm)\" >&5\nprintf %s \"checking for BSD- or MS-compatible name lister (nm)... \" >&6; }\nif test ${lt_cv_path_NM+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$NM\"; then\n  # Let the user override the test.\n  lt_cv_path_NM=$NM\nelse\n  lt_nm_to_check=${ac_tool_prefix}nm\n  if test -n \"$ac_tool_prefix\" && test \"$build\" = \"$host\"; then\n    lt_nm_to_check=\"$lt_nm_to_check nm\"\n  fi\n  for lt_tmp_nm in $lt_nm_to_check; do\n    lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR\n    for ac_dir in $PATH /usr/ccs/bin/elf /usr/ccs/bin /usr/ucb /bin; do\n      IFS=$lt_save_ifs\n      test -z \"$ac_dir\" && ac_dir=.\n      tmp_nm=$ac_dir/$lt_tmp_nm\n      if test -f \"$tmp_nm\" || test -f \"$tmp_nm$ac_exeext\"; then\n\t# Check to see if the nm accepts a BSD-compat flag.\n\t# Adding the 'sed 1q' prevents false positives on HP-UX, which says:\n\t#   nm: unknown option \"B\" ignored\n\t# Tru64's nm complains that /dev/null is an invalid object file\n\t# MSYS converts /dev/null to NUL, MinGW nm treats NUL as empty\n\tcase $build_os in\n\tmingw*) lt_bad_file=conftest.nm/nofile ;;\n\t*) lt_bad_file=/dev/null ;;\n\tesac\n\tcase `\"$tmp_nm\" -B $lt_bad_file 2>&1 | $SED '1q'` in\n\t*$lt_bad_file* | *'Invalid file or object type'*)\n\t  lt_cv_path_NM=\"$tmp_nm -B\"\n\t  break 2\n\t  ;;\n\t*)\n\t  case `\"$tmp_nm\" -p /dev/null 2>&1 | $SED '1q'` in\n\t  */dev/null*)\n\t    lt_cv_path_NM=\"$tmp_nm -p\"\n\t    break 2\n\t    ;;\n\t  *)\n\t    lt_cv_path_NM=${lt_cv_path_NM=\"$tmp_nm\"} # keep the first match, but\n\t    continue # so that we can try to find one that supports BSD flags\n\t    ;;\n\t  esac\n\t  ;;\n\tesac\n      fi\n    done\n    IFS=$lt_save_ifs\n  done\n  : ${lt_cv_path_NM=no}\nfi ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_path_NM\" >&5\nprintf \"%s\\n\" \"$lt_cv_path_NM\" >&6; }\nif test no != \"$lt_cv_path_NM\"; then\n  NM=$lt_cv_path_NM\nelse\n  # Didn't find any BSD compatible name lister, look for dumpbin.\n  if test -n \"$DUMPBIN\"; then :\n    # Let the user override the test.\n  else\n    if test -n \"$ac_tool_prefix\"; then\n  for ac_prog in dumpbin \"link -dump\"\n  do\n    # Extract the first word of \"$ac_tool_prefix$ac_prog\", so it can be a program name with args.\nset dummy $ac_tool_prefix$ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_DUMPBIN+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$DUMPBIN\"; then\n  ac_cv_prog_DUMPBIN=\"$DUMPBIN\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_DUMPBIN=\"$ac_tool_prefix$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nDUMPBIN=$ac_cv_prog_DUMPBIN\nif test -n \"$DUMPBIN\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $DUMPBIN\" >&5\nprintf \"%s\\n\" \"$DUMPBIN\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n    test -n \"$DUMPBIN\" && break\n  done\nfi\nif test -z \"$DUMPBIN\"; then\n  ac_ct_DUMPBIN=$DUMPBIN\n  for ac_prog in dumpbin \"link -dump\"\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_DUMPBIN+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_DUMPBIN\"; then\n  ac_cv_prog_ac_ct_DUMPBIN=\"$ac_ct_DUMPBIN\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_DUMPBIN=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_DUMPBIN=$ac_cv_prog_ac_ct_DUMPBIN\nif test -n \"$ac_ct_DUMPBIN\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_DUMPBIN\" >&5\nprintf \"%s\\n\" \"$ac_ct_DUMPBIN\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$ac_ct_DUMPBIN\" && break\ndone\n\n  if test \"x$ac_ct_DUMPBIN\" = x; then\n    DUMPBIN=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    DUMPBIN=$ac_ct_DUMPBIN\n  fi\nfi\n\n    case `$DUMPBIN -symbols -headers /dev/null 2>&1 | $SED '1q'` in\n    *COFF*)\n      DUMPBIN=\"$DUMPBIN -symbols -headers\"\n      ;;\n    *)\n      DUMPBIN=:\n      ;;\n    esac\n  fi\n\n  if test : != \"$DUMPBIN\"; then\n    NM=$DUMPBIN\n  fi\nfi\ntest -z \"$NM\" && NM=nm\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking the name lister ($NM) interface\" >&5\nprintf %s \"checking the name lister ($NM) interface... \" >&6; }\nif test ${lt_cv_nm_interface+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_nm_interface=\"BSD nm\"\n  echo \"int some_variable = 0;\" > conftest.$ac_ext\n  (eval echo \"\\\"\\$as_me:$LINENO: $ac_compile\\\"\" >&5)\n  (eval \"$ac_compile\" 2>conftest.err)\n  cat conftest.err >&5\n  (eval echo \"\\\"\\$as_me:$LINENO: $NM \\\\\\\"conftest.$ac_objext\\\\\\\"\\\"\" >&5)\n  (eval \"$NM \\\"conftest.$ac_objext\\\"\" 2>conftest.err > conftest.out)\n  cat conftest.err >&5\n  (eval echo \"\\\"\\$as_me:$LINENO: output\\\"\" >&5)\n  cat conftest.out >&5\n  if $GREP 'External.*some_variable' conftest.out > /dev/null; then\n    lt_cv_nm_interface=\"MS dumpbin\"\n  fi\n  rm -f conftest* ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_nm_interface\" >&5\nprintf \"%s\\n\" \"$lt_cv_nm_interface\" >&6; }\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether ln -s works\" >&5\nprintf %s \"checking whether ln -s works... \" >&6; }\nLN_S=$as_ln_s\nif test \"$LN_S\" = \"ln -s\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no, using $LN_S\" >&5\nprintf \"%s\\n\" \"no, using $LN_S\" >&6; }\nfi\n\n# find the maximum length of command line arguments\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking the maximum length of command line arguments\" >&5\nprintf %s \"checking the maximum length of command line arguments... \" >&6; }\nif test ${lt_cv_sys_max_cmd_len+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e)   i=0\n  teststring=ABCD\n\n  case $build_os in\n  msdosdjgpp*)\n    # On DJGPP, this test can blow up pretty badly due to problems in libc\n    # (any single argument exceeding 2000 bytes causes a buffer overrun\n    # during glob expansion).  Even if it were fixed, the result of this\n    # check would be larger than it should be.\n    lt_cv_sys_max_cmd_len=12288;    # 12K is about right\n    ;;\n\n  gnu*)\n    # Under GNU Hurd, this test is not required because there is\n    # no limit to the length of command line arguments.\n    # Libtool will interpret -1 as no limit whatsoever\n    lt_cv_sys_max_cmd_len=-1;\n    ;;\n\n  cygwin* | mingw* | cegcc*)\n    # On Win9x/ME, this test blows up -- it succeeds, but takes\n    # about 5 minutes as the teststring grows exponentially.\n    # Worse, since 9x/ME are not pre-emptively multitasking,\n    # you end up with a \"frozen\" computer, even though with patience\n    # the test eventually succeeds (with a max line length of 256k).\n    # Instead, let's just punt: use the minimum linelength reported by\n    # all of the supported platforms: 8192 (on NT/2K/XP).\n    lt_cv_sys_max_cmd_len=8192;\n    ;;\n\n  mint*)\n    # On MiNT this can take a long time and run out of memory.\n    lt_cv_sys_max_cmd_len=8192;\n    ;;\n\n  amigaos*)\n    # On AmigaOS with pdksh, this test takes hours, literally.\n    # So we just punt and use a minimum line length of 8192.\n    lt_cv_sys_max_cmd_len=8192;\n    ;;\n\n  bitrig* | darwin* | dragonfly* | freebsd* | midnightbsd* | netbsd* | openbsd*)\n    # This has been around since 386BSD, at least.  Likely further.\n    if test -x /sbin/sysctl; then\n      lt_cv_sys_max_cmd_len=`/sbin/sysctl -n kern.argmax`\n    elif test -x /usr/sbin/sysctl; then\n      lt_cv_sys_max_cmd_len=`/usr/sbin/sysctl -n kern.argmax`\n    else\n      lt_cv_sys_max_cmd_len=65536\t# usable default for all BSDs\n    fi\n    # And add a safety zone\n    lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\/ 4`\n    lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\* 3`\n    ;;\n\n  interix*)\n    # We know the value 262144 and hardcode it with a safety zone (like BSD)\n    lt_cv_sys_max_cmd_len=196608\n    ;;\n\n  os2*)\n    # The test takes a long time on OS/2.\n    lt_cv_sys_max_cmd_len=8192\n    ;;\n\n  osf*)\n    # Dr. Hans Ekkehard Plesser reports seeing a kernel panic running configure\n    # due to this test when exec_disable_arg_limit is 1 on Tru64. It is not\n    # nice to cause kernel panics so lets avoid the loop below.\n    # First set a reasonable default.\n    lt_cv_sys_max_cmd_len=16384\n    #\n    if test -x /sbin/sysconfig; then\n      case `/sbin/sysconfig -q proc exec_disable_arg_limit` in\n        *1*) lt_cv_sys_max_cmd_len=-1 ;;\n      esac\n    fi\n    ;;\n  sco3.2v5*)\n    lt_cv_sys_max_cmd_len=102400\n    ;;\n  sysv5* | sco5v6* | sysv4.2uw2*)\n    kargmax=`grep ARG_MAX /etc/conf/cf.d/stune 2>/dev/null`\n    if test -n \"$kargmax\"; then\n      lt_cv_sys_max_cmd_len=`echo $kargmax | $SED 's/.*[\t ]//'`\n    else\n      lt_cv_sys_max_cmd_len=32768\n    fi\n    ;;\n  *)\n    lt_cv_sys_max_cmd_len=`(getconf ARG_MAX) 2> /dev/null`\n    if test -n \"$lt_cv_sys_max_cmd_len\" && \\\n       test undefined != \"$lt_cv_sys_max_cmd_len\"; then\n      lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\/ 4`\n      lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\* 3`\n    else\n      # Make teststring a little bigger before we do anything with it.\n      # a 1K string should be a reasonable start.\n      for i in 1 2 3 4 5 6 7 8; do\n        teststring=$teststring$teststring\n      done\n      SHELL=${SHELL-${CONFIG_SHELL-/bin/sh}}\n      # If test is not a shell built-in, we'll probably end up computing a\n      # maximum length that is only half of the actual maximum length, but\n      # we can't tell.\n      while { test X`env echo \"$teststring$teststring\" 2>/dev/null` \\\n\t         = \"X$teststring$teststring\"; } >/dev/null 2>&1 &&\n\t      test 17 != \"$i\" # 1/2 MB should be enough\n      do\n        i=`expr $i + 1`\n        teststring=$teststring$teststring\n      done\n      # Only check the string length outside the loop.\n      lt_cv_sys_max_cmd_len=`expr \"X$teststring\" : \".*\" 2>&1`\n      teststring=\n      # Add a significant safety factor because C++ compilers can tack on\n      # massive amounts of additional arguments before passing them to the\n      # linker.  It appears as though 1/2 is a usable value.\n      lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\/ 2`\n    fi\n    ;;\n  esac\n ;;\nesac\nfi\n\nif test -n \"$lt_cv_sys_max_cmd_len\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_sys_max_cmd_len\" >&5\nprintf \"%s\\n\" \"$lt_cv_sys_max_cmd_len\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: none\" >&5\nprintf \"%s\\n\" \"none\" >&6; }\nfi\nmax_cmd_len=$lt_cv_sys_max_cmd_len\n\n\n\n\n\n\n: ${CP=\"cp -f\"}\n: ${MV=\"mv -f\"}\n: ${RM=\"rm -f\"}\n\nif ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then\n  lt_unset=unset\nelse\n  lt_unset=false\nfi\n\n\n\n\n\n# test EBCDIC or ASCII\ncase `echo X|tr X '\\101'` in\n A) # ASCII based system\n    # \\n is not interpreted correctly by Solaris 8 /usr/ucb/tr\n  lt_SP2NL='tr \\040 \\012'\n  lt_NL2SP='tr \\015\\012 \\040\\040'\n  ;;\n *) # EBCDIC based system\n  lt_SP2NL='tr \\100 \\n'\n  lt_NL2SP='tr \\r\\n \\100\\100'\n  ;;\nesac\n\n\n\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to convert $build file names to $host format\" >&5\nprintf %s \"checking how to convert $build file names to $host format... \" >&6; }\nif test ${lt_cv_to_host_file_cmd+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) case $host in\n  *-*-mingw* )\n    case $build in\n      *-*-mingw* ) # actually msys\n        lt_cv_to_host_file_cmd=func_convert_file_msys_to_w32\n        ;;\n      *-*-cygwin* )\n        lt_cv_to_host_file_cmd=func_convert_file_cygwin_to_w32\n        ;;\n      * ) # otherwise, assume *nix\n        lt_cv_to_host_file_cmd=func_convert_file_nix_to_w32\n        ;;\n    esac\n    ;;\n  *-*-cygwin* )\n    case $build in\n      *-*-mingw* ) # actually msys\n        lt_cv_to_host_file_cmd=func_convert_file_msys_to_cygwin\n        ;;\n      *-*-cygwin* )\n        lt_cv_to_host_file_cmd=func_convert_file_noop\n        ;;\n      * ) # otherwise, assume *nix\n        lt_cv_to_host_file_cmd=func_convert_file_nix_to_cygwin\n        ;;\n    esac\n    ;;\n  * ) # unhandled hosts (and \"normal\" native builds)\n    lt_cv_to_host_file_cmd=func_convert_file_noop\n    ;;\nesac\n ;;\nesac\nfi\n\nto_host_file_cmd=$lt_cv_to_host_file_cmd\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_to_host_file_cmd\" >&5\nprintf \"%s\\n\" \"$lt_cv_to_host_file_cmd\" >&6; }\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to convert $build file names to toolchain format\" >&5\nprintf %s \"checking how to convert $build file names to toolchain format... \" >&6; }\nif test ${lt_cv_to_tool_file_cmd+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) #assume ordinary cross tools, or native build.\nlt_cv_to_tool_file_cmd=func_convert_file_noop\ncase $host in\n  *-*-mingw* )\n    case $build in\n      *-*-mingw* ) # actually msys\n        lt_cv_to_tool_file_cmd=func_convert_file_msys_to_w32\n        ;;\n    esac\n    ;;\nesac\n ;;\nesac\nfi\n\nto_tool_file_cmd=$lt_cv_to_tool_file_cmd\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_to_tool_file_cmd\" >&5\nprintf \"%s\\n\" \"$lt_cv_to_tool_file_cmd\" >&6; }\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $LD option to reload object files\" >&5\nprintf %s \"checking for $LD option to reload object files... \" >&6; }\nif test ${lt_cv_ld_reload_flag+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_ld_reload_flag='-r' ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_reload_flag\" >&5\nprintf \"%s\\n\" \"$lt_cv_ld_reload_flag\" >&6; }\nreload_flag=$lt_cv_ld_reload_flag\ncase $reload_flag in\n\"\" | \" \"*) ;;\n*) reload_flag=\" $reload_flag\" ;;\nesac\nreload_cmds='$LD$reload_flag -o $output$reload_objs'\ncase $host_os in\n  cygwin* | mingw* | pw32* | cegcc*)\n    if test yes != \"$GCC\"; then\n      reload_cmds=false\n    fi\n    ;;\n  darwin*)\n    if test yes = \"$GCC\"; then\n      reload_cmds='$LTCC $LTCFLAGS -nostdlib $wl-r -o $output$reload_objs'\n    else\n      reload_cmds='$LD$reload_flag -o $output$reload_objs'\n    fi\n    ;;\nesac\n\n\n\n\n\n\n\n\n\nif test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}file\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}file; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_FILECMD+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$FILECMD\"; then\n  ac_cv_prog_FILECMD=\"$FILECMD\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_FILECMD=\"${ac_tool_prefix}file\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nFILECMD=$ac_cv_prog_FILECMD\nif test -n \"$FILECMD\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $FILECMD\" >&5\nprintf \"%s\\n\" \"$FILECMD\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_FILECMD\"; then\n  ac_ct_FILECMD=$FILECMD\n  # Extract the first word of \"file\", so it can be a program name with args.\nset dummy file; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_FILECMD+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_FILECMD\"; then\n  ac_cv_prog_ac_ct_FILECMD=\"$ac_ct_FILECMD\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_FILECMD=\"file\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_FILECMD=$ac_cv_prog_ac_ct_FILECMD\nif test -n \"$ac_ct_FILECMD\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_FILECMD\" >&5\nprintf \"%s\\n\" \"$ac_ct_FILECMD\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_FILECMD\" = x; then\n    FILECMD=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    FILECMD=$ac_ct_FILECMD\n  fi\nelse\n  FILECMD=\"$ac_cv_prog_FILECMD\"\nfi\n\n\n\n\n\n\n\nif test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}objdump\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}objdump; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_OBJDUMP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$OBJDUMP\"; then\n  ac_cv_prog_OBJDUMP=\"$OBJDUMP\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_OBJDUMP=\"${ac_tool_prefix}objdump\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nOBJDUMP=$ac_cv_prog_OBJDUMP\nif test -n \"$OBJDUMP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $OBJDUMP\" >&5\nprintf \"%s\\n\" \"$OBJDUMP\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_OBJDUMP\"; then\n  ac_ct_OBJDUMP=$OBJDUMP\n  # Extract the first word of \"objdump\", so it can be a program name with args.\nset dummy objdump; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_OBJDUMP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_OBJDUMP\"; then\n  ac_cv_prog_ac_ct_OBJDUMP=\"$ac_ct_OBJDUMP\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_OBJDUMP=\"objdump\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_OBJDUMP=$ac_cv_prog_ac_ct_OBJDUMP\nif test -n \"$ac_ct_OBJDUMP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_OBJDUMP\" >&5\nprintf \"%s\\n\" \"$ac_ct_OBJDUMP\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_OBJDUMP\" = x; then\n    OBJDUMP=\"false\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    OBJDUMP=$ac_ct_OBJDUMP\n  fi\nelse\n  OBJDUMP=\"$ac_cv_prog_OBJDUMP\"\nfi\n\ntest -z \"$OBJDUMP\" && OBJDUMP=objdump\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to recognize dependent libraries\" >&5\nprintf %s \"checking how to recognize dependent libraries... \" >&6; }\nif test ${lt_cv_deplibs_check_method+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_file_magic_cmd='$MAGIC_CMD'\nlt_cv_file_magic_test_file=\nlt_cv_deplibs_check_method='unknown'\n# Need to set the preceding variable on all platforms that support\n# interlibrary dependencies.\n# 'none' -- dependencies not supported.\n# 'unknown' -- same as none, but documents that we really don't know.\n# 'pass_all' -- all dependencies passed with no checks.\n# 'test_compile' -- check by making test program.\n# 'file_magic [[regex]]' -- check by looking for files in library path\n# that responds to the $file_magic_cmd with a given extended regex.\n# If you have 'file' or equivalent on your system and you're not sure\n# whether 'pass_all' will *always* work, you probably want this one.\n\ncase $host_os in\naix[4-9]*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nbeos*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nbsdi[45]*)\n  lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (shared object|dynamic lib)'\n  lt_cv_file_magic_cmd='$FILECMD -L'\n  lt_cv_file_magic_test_file=/shlib/libc.so\n  ;;\n\ncygwin*)\n  # func_win32_libid is a shell function defined in ltmain.sh\n  lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL'\n  lt_cv_file_magic_cmd='func_win32_libid'\n  ;;\n\nmingw* | pw32*)\n  # Base MSYS/MinGW do not provide the 'file' command needed by\n  # func_win32_libid shell function, so use a weaker test based on 'objdump',\n  # unless we find 'file', for example because we are cross-compiling.\n  if ( file / ) >/dev/null 2>&1; then\n    lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL'\n    lt_cv_file_magic_cmd='func_win32_libid'\n  else\n    # Keep this pattern in sync with the one in func_win32_libid.\n    lt_cv_deplibs_check_method='file_magic file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)'\n    lt_cv_file_magic_cmd='$OBJDUMP -f'\n  fi\n  ;;\n\ncegcc*)\n  # use the weaker test based on 'objdump'. See mingw*.\n  lt_cv_deplibs_check_method='file_magic file format pe-arm-.*little(.*architecture: arm)?'\n  lt_cv_file_magic_cmd='$OBJDUMP -f'\n  ;;\n\ndarwin* | rhapsody*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nfreebsd* | dragonfly* | midnightbsd*)\n  if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then\n    case $host_cpu in\n    i*86 )\n      # Not sure whether the presence of OpenBSD here was a mistake.\n      # Let's accept both of them until this is cleared up.\n      lt_cv_deplibs_check_method='file_magic (FreeBSD|OpenBSD|DragonFly)/i[3-9]86 (compact )?demand paged shared library'\n      lt_cv_file_magic_cmd=$FILECMD\n      lt_cv_file_magic_test_file=`echo /usr/lib/libc.so.*`\n      ;;\n    esac\n  else\n    lt_cv_deplibs_check_method=pass_all\n  fi\n  ;;\n\nhaiku*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nhpux10.20* | hpux11*)\n  lt_cv_file_magic_cmd=$FILECMD\n  case $host_cpu in\n  ia64*)\n    lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF-[0-9][0-9]) shared object file - IA64'\n    lt_cv_file_magic_test_file=/usr/lib/hpux32/libc.so\n    ;;\n  hppa*64*)\n    lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF[ -][0-9][0-9])(-bit)?( [LM]SB)? shared object( file)?[, -]* PA-RISC [0-9]\\.[0-9]'\n    lt_cv_file_magic_test_file=/usr/lib/pa20_64/libc.sl\n    ;;\n  *)\n    lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|PA-RISC[0-9]\\.[0-9]) shared library'\n    lt_cv_file_magic_test_file=/usr/lib/libc.sl\n    ;;\n  esac\n  ;;\n\ninterix[3-9]*)\n  # PIC code is broken on Interix 3.x, that's why |\\.a not |_pic\\.a here\n  lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\\.so|\\.a)$'\n  ;;\n\nirix5* | irix6* | nonstopux*)\n  case $LD in\n  *-32|*\"-32 \") libmagic=32-bit;;\n  *-n32|*\"-n32 \") libmagic=N32;;\n  *-64|*\"-64 \") libmagic=64-bit;;\n  *) libmagic=never-match;;\n  esac\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\n# This must be glibc/ELF.\nlinux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nnetbsd*)\n  if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then\n    lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\\.so\\.[0-9]+\\.[0-9]+|_pic\\.a)$'\n  else\n    lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\\.so|_pic\\.a)$'\n  fi\n  ;;\n\nnewos6*)\n  lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (executable|dynamic lib)'\n  lt_cv_file_magic_cmd=$FILECMD\n  lt_cv_file_magic_test_file=/usr/lib/libnls.so\n  ;;\n\n*nto* | *qnx*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nopenbsd* | bitrig*)\n  if test -z \"`echo __ELF__ | $CC -E - | $GREP __ELF__`\"; then\n    lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\\.so\\.[0-9]+\\.[0-9]+|\\.so|_pic\\.a)$'\n  else\n    lt_cv_deplibs_check_method='match_pattern /lib[^/]+(\\.so\\.[0-9]+\\.[0-9]+|_pic\\.a)$'\n  fi\n  ;;\n\nosf3* | osf4* | osf5*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nrdos*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nsolaris*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nsysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nsysv4 | sysv4.3*)\n  case $host_vendor in\n  motorola)\n    lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [ML]SB (shared object|dynamic lib) M[0-9][0-9]* Version [0-9]'\n    lt_cv_file_magic_test_file=`echo /usr/lib/libc.so*`\n    ;;\n  ncr)\n    lt_cv_deplibs_check_method=pass_all\n    ;;\n  sequent)\n    lt_cv_file_magic_cmd='/bin/file'\n    lt_cv_deplibs_check_method='file_magic ELF [0-9][0-9]*-bit [LM]SB (shared object|dynamic lib )'\n    ;;\n  sni)\n    lt_cv_file_magic_cmd='/bin/file'\n    lt_cv_deplibs_check_method=\"file_magic ELF [0-9][0-9]*-bit [LM]SB dynamic lib\"\n    lt_cv_file_magic_test_file=/lib/libc.so\n    ;;\n  siemens)\n    lt_cv_deplibs_check_method=pass_all\n    ;;\n  pc)\n    lt_cv_deplibs_check_method=pass_all\n    ;;\n  esac\n  ;;\n\ntpf*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\nos2*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\nesac\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_deplibs_check_method\" >&5\nprintf \"%s\\n\" \"$lt_cv_deplibs_check_method\" >&6; }\n\nfile_magic_glob=\nwant_nocaseglob=no\nif test \"$build\" = \"$host\"; then\n  case $host_os in\n  mingw* | pw32*)\n    if ( shopt | grep nocaseglob ) >/dev/null 2>&1; then\n      want_nocaseglob=yes\n    else\n      file_magic_glob=`echo aAbBcCdDeEfFgGhHiIjJkKlLmMnNoOpPqQrRsStTuUvVwWxXyYzZ | $SED -e \"s/\\(..\\)/s\\/[\\1]\\/[\\1]\\/g;/g\"`\n    fi\n    ;;\n  esac\nfi\n\nfile_magic_cmd=$lt_cv_file_magic_cmd\ndeplibs_check_method=$lt_cv_deplibs_check_method\ntest -z \"$deplibs_check_method\" && deplibs_check_method=unknown\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\nif test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}dlltool\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}dlltool; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_DLLTOOL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$DLLTOOL\"; then\n  ac_cv_prog_DLLTOOL=\"$DLLTOOL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_DLLTOOL=\"${ac_tool_prefix}dlltool\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nDLLTOOL=$ac_cv_prog_DLLTOOL\nif test -n \"$DLLTOOL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $DLLTOOL\" >&5\nprintf \"%s\\n\" \"$DLLTOOL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_DLLTOOL\"; then\n  ac_ct_DLLTOOL=$DLLTOOL\n  # Extract the first word of \"dlltool\", so it can be a program name with args.\nset dummy dlltool; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_DLLTOOL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_DLLTOOL\"; then\n  ac_cv_prog_ac_ct_DLLTOOL=\"$ac_ct_DLLTOOL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_DLLTOOL=\"dlltool\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_DLLTOOL=$ac_cv_prog_ac_ct_DLLTOOL\nif test -n \"$ac_ct_DLLTOOL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_DLLTOOL\" >&5\nprintf \"%s\\n\" \"$ac_ct_DLLTOOL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_DLLTOOL\" = x; then\n    DLLTOOL=\"false\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    DLLTOOL=$ac_ct_DLLTOOL\n  fi\nelse\n  DLLTOOL=\"$ac_cv_prog_DLLTOOL\"\nfi\n\ntest -z \"$DLLTOOL\" && DLLTOOL=dlltool\n\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to associate runtime and link libraries\" >&5\nprintf %s \"checking how to associate runtime and link libraries... \" >&6; }\nif test ${lt_cv_sharedlib_from_linklib_cmd+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_sharedlib_from_linklib_cmd='unknown'\n\ncase $host_os in\ncygwin* | mingw* | pw32* | cegcc*)\n  # two different shell functions defined in ltmain.sh;\n  # decide which one to use based on capabilities of $DLLTOOL\n  case `$DLLTOOL --help 2>&1` in\n  *--identify-strict*)\n    lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib\n    ;;\n  *)\n    lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib_fallback\n    ;;\n  esac\n  ;;\n*)\n  # fallback: assume linklib IS sharedlib\n  lt_cv_sharedlib_from_linklib_cmd=$ECHO\n  ;;\nesac\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_sharedlib_from_linklib_cmd\" >&5\nprintf \"%s\\n\" \"$lt_cv_sharedlib_from_linklib_cmd\" >&6; }\nsharedlib_from_linklib_cmd=$lt_cv_sharedlib_from_linklib_cmd\ntest -z \"$sharedlib_from_linklib_cmd\" && sharedlib_from_linklib_cmd=$ECHO\n\n\n\n\n\n\n\nif test -n \"$ac_tool_prefix\"; then\n  for ac_prog in ar\n  do\n    # Extract the first word of \"$ac_tool_prefix$ac_prog\", so it can be a program name with args.\nset dummy $ac_tool_prefix$ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_AR+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$AR\"; then\n  ac_cv_prog_AR=\"$AR\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_AR=\"$ac_tool_prefix$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nAR=$ac_cv_prog_AR\nif test -n \"$AR\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $AR\" >&5\nprintf \"%s\\n\" \"$AR\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n    test -n \"$AR\" && break\n  done\nfi\nif test -z \"$AR\"; then\n  ac_ct_AR=$AR\n  for ac_prog in ar\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_AR+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_AR\"; then\n  ac_cv_prog_ac_ct_AR=\"$ac_ct_AR\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_AR=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_AR=$ac_cv_prog_ac_ct_AR\nif test -n \"$ac_ct_AR\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_AR\" >&5\nprintf \"%s\\n\" \"$ac_ct_AR\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$ac_ct_AR\" && break\ndone\n\n  if test \"x$ac_ct_AR\" = x; then\n    AR=\"false\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    AR=$ac_ct_AR\n  fi\nfi\n\n: ${AR=ar}\n\n\n\n\n\n\n# Use ARFLAGS variable as AR's operation code to sync the variable naming with\n# Automake.  If both AR_FLAGS and ARFLAGS are specified, AR_FLAGS should have\n# higher priority because thats what people were doing historically (setting\n# ARFLAGS for automake and AR_FLAGS for libtool).  FIXME: Make the AR_FLAGS\n# variable obsoleted/removed.\n\ntest ${AR_FLAGS+y} || AR_FLAGS=${ARFLAGS-cr}\nlt_ar_flags=$AR_FLAGS\n\n\n\n\n\n\n# Make AR_FLAGS overridable by 'make ARFLAGS='.  Don't try to run-time override\n# by AR_FLAGS because that was never working and AR_FLAGS is about to die.\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for archiver @FILE support\" >&5\nprintf %s \"checking for archiver @FILE support... \" >&6; }\nif test ${lt_cv_ar_at_file+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_ar_at_file=no\n   cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  echo conftest.$ac_objext > conftest.lst\n      lt_ar_try='$AR $AR_FLAGS libconftest.a @conftest.lst >&5'\n      { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$lt_ar_try\\\"\"; } >&5\n  (eval $lt_ar_try) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\n      if test 0 -eq \"$ac_status\"; then\n\t# Ensure the archiver fails upon bogus file names.\n\trm -f conftest.$ac_objext libconftest.a\n\t{ { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$lt_ar_try\\\"\"; } >&5\n  (eval $lt_ar_try) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\n\tif test 0 -ne \"$ac_status\"; then\n          lt_cv_ar_at_file=@\n        fi\n      fi\n      rm -f conftest.* libconftest.a\n\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n   ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_ar_at_file\" >&5\nprintf \"%s\\n\" \"$lt_cv_ar_at_file\" >&6; }\n\nif test no = \"$lt_cv_ar_at_file\"; then\n  archiver_list_spec=\nelse\n  archiver_list_spec=$lt_cv_ar_at_file\nfi\n\n\n\n\n\n\n\nif test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}strip\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}strip; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_STRIP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$STRIP\"; then\n  ac_cv_prog_STRIP=\"$STRIP\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_STRIP=\"${ac_tool_prefix}strip\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nSTRIP=$ac_cv_prog_STRIP\nif test -n \"$STRIP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $STRIP\" >&5\nprintf \"%s\\n\" \"$STRIP\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_STRIP\"; then\n  ac_ct_STRIP=$STRIP\n  # Extract the first word of \"strip\", so it can be a program name with args.\nset dummy strip; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_STRIP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_STRIP\"; then\n  ac_cv_prog_ac_ct_STRIP=\"$ac_ct_STRIP\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_STRIP=\"strip\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_STRIP=$ac_cv_prog_ac_ct_STRIP\nif test -n \"$ac_ct_STRIP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_STRIP\" >&5\nprintf \"%s\\n\" \"$ac_ct_STRIP\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_STRIP\" = x; then\n    STRIP=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    STRIP=$ac_ct_STRIP\n  fi\nelse\n  STRIP=\"$ac_cv_prog_STRIP\"\nfi\n\ntest -z \"$STRIP\" && STRIP=:\n\n\n\n\n\n\nif test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}ranlib\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}ranlib; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_RANLIB+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$RANLIB\"; then\n  ac_cv_prog_RANLIB=\"$RANLIB\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_RANLIB=\"${ac_tool_prefix}ranlib\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nRANLIB=$ac_cv_prog_RANLIB\nif test -n \"$RANLIB\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $RANLIB\" >&5\nprintf \"%s\\n\" \"$RANLIB\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_RANLIB\"; then\n  ac_ct_RANLIB=$RANLIB\n  # Extract the first word of \"ranlib\", so it can be a program name with args.\nset dummy ranlib; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_RANLIB+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_RANLIB\"; then\n  ac_cv_prog_ac_ct_RANLIB=\"$ac_ct_RANLIB\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_RANLIB=\"ranlib\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_RANLIB=$ac_cv_prog_ac_ct_RANLIB\nif test -n \"$ac_ct_RANLIB\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_RANLIB\" >&5\nprintf \"%s\\n\" \"$ac_ct_RANLIB\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_RANLIB\" = x; then\n    RANLIB=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    RANLIB=$ac_ct_RANLIB\n  fi\nelse\n  RANLIB=\"$ac_cv_prog_RANLIB\"\nfi\n\ntest -z \"$RANLIB\" && RANLIB=:\n\n\n\n\n\n\n# Determine commands to create old-style static archives.\nold_archive_cmds='$AR $AR_FLAGS $oldlib$oldobjs'\nold_postinstall_cmds='chmod 644 $oldlib'\nold_postuninstall_cmds=\n\nif test -n \"$RANLIB\"; then\n  case $host_os in\n  bitrig* | openbsd*)\n    old_postinstall_cmds=\"$old_postinstall_cmds~\\$RANLIB -t \\$tool_oldlib\"\n    ;;\n  *)\n    old_postinstall_cmds=\"$old_postinstall_cmds~\\$RANLIB \\$tool_oldlib\"\n    ;;\n  esac\n  old_archive_cmds=\"$old_archive_cmds~\\$RANLIB \\$tool_oldlib\"\nfi\n\ncase $host_os in\n  darwin*)\n    lock_old_archive_extraction=yes ;;\n  *)\n    lock_old_archive_extraction=no ;;\nesac\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n# If no C compiler was specified, use CC.\nLTCC=${LTCC-\"$CC\"}\n\n# If no C compiler flags were specified, use CFLAGS.\nLTCFLAGS=${LTCFLAGS-\"$CFLAGS\"}\n\n# Allow CC to be a program name with arguments.\ncompiler=$CC\n\n\n# Check for command to grab the raw symbol name followed by C symbol from nm.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking command to parse $NM output from $compiler object\" >&5\nprintf %s \"checking command to parse $NM output from $compiler object... \" >&6; }\nif test ${lt_cv_sys_global_symbol_pipe+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e)\n# These are sane defaults that work on at least a few old systems.\n# [They come from Ultrix.  What could be older than Ultrix?!! ;)]\n\n# Character class describing NM global symbol codes.\nsymcode='[BCDEGRST]'\n\n# Regexp to match symbols that can be accessed directly from C.\nsympat='\\([_A-Za-z][_A-Za-z0-9]*\\)'\n\n# Define system-specific variables.\ncase $host_os in\naix*)\n  symcode='[BCDT]'\n  ;;\ncygwin* | mingw* | pw32* | cegcc*)\n  symcode='[ABCDGISTW]'\n  ;;\nhpux*)\n  if test ia64 = \"$host_cpu\"; then\n    symcode='[ABCDEGRST]'\n  fi\n  ;;\nirix* | nonstopux*)\n  symcode='[BCDEGRST]'\n  ;;\nosf*)\n  symcode='[BCDEGQRST]'\n  ;;\nsolaris*)\n  symcode='[BDRT]'\n  ;;\nsco3.2v5*)\n  symcode='[DT]'\n  ;;\nsysv4.2uw2*)\n  symcode='[DT]'\n  ;;\nsysv5* | sco5v6* | unixware* | OpenUNIX*)\n  symcode='[ABDT]'\n  ;;\nsysv4)\n  symcode='[DFNSTU]'\n  ;;\nesac\n\n# If we're using GNU nm, then use its standard symbol codes.\ncase `$NM -V 2>&1` in\n*GNU* | *'with BFD'*)\n  symcode='[ABCDGIRSTW]' ;;\nesac\n\nif test \"$lt_cv_nm_interface\" = \"MS dumpbin\"; then\n  # Gets list of data symbols to import.\n  lt_cv_sys_global_symbol_to_import=\"$SED -n -e 's/^I .* \\(.*\\)$/\\1/p'\"\n  # Adjust the below global symbol transforms to fixup imported variables.\n  lt_cdecl_hook=\" -e 's/^I .* \\(.*\\)$/extern __declspec(dllimport) char \\1;/p'\"\n  lt_c_name_hook=\" -e 's/^I .* \\(.*\\)$/  {\\\"\\1\\\", (void *) 0},/p'\"\n  lt_c_name_lib_hook=\"\\\n  -e 's/^I .* \\(lib.*\\)$/  {\\\"\\1\\\", (void *) 0},/p'\\\n  -e 's/^I .* \\(.*\\)$/  {\\\"lib\\1\\\", (void *) 0},/p'\"\nelse\n  # Disable hooks by default.\n  lt_cv_sys_global_symbol_to_import=\n  lt_cdecl_hook=\n  lt_c_name_hook=\n  lt_c_name_lib_hook=\nfi\n\n# Transform an extracted symbol line into a proper C declaration.\n# Some systems (esp. on ia64) link data and code symbols differently,\n# so use this general approach.\nlt_cv_sys_global_symbol_to_cdecl=\"$SED -n\"\\\n$lt_cdecl_hook\\\n\" -e 's/^T .* \\(.*\\)$/extern int \\1();/p'\"\\\n\" -e 's/^$symcode$symcode* .* \\(.*\\)$/extern char \\1;/p'\"\n\n# Transform an extracted symbol line into symbol name and symbol address\nlt_cv_sys_global_symbol_to_c_name_address=\"$SED -n\"\\\n$lt_c_name_hook\\\n\" -e 's/^: \\(.*\\) .*$/  {\\\"\\1\\\", (void *) 0},/p'\"\\\n\" -e 's/^$symcode$symcode* .* \\(.*\\)$/  {\\\"\\1\\\", (void *) \\&\\1},/p'\"\n\n# Transform an extracted symbol line into symbol name with lib prefix and\n# symbol address.\nlt_cv_sys_global_symbol_to_c_name_address_lib_prefix=\"$SED -n\"\\\n$lt_c_name_lib_hook\\\n\" -e 's/^: \\(.*\\) .*$/  {\\\"\\1\\\", (void *) 0},/p'\"\\\n\" -e 's/^$symcode$symcode* .* \\(lib.*\\)$/  {\\\"\\1\\\", (void *) \\&\\1},/p'\"\\\n\" -e 's/^$symcode$symcode* .* \\(.*\\)$/  {\\\"lib\\1\\\", (void *) \\&\\1},/p'\"\n\n# Handle CRLF in mingw tool chain\nopt_cr=\ncase $build_os in\nmingw*)\n  opt_cr=`$ECHO 'x\\{0,1\\}' | tr x '\\015'` # option cr in regexp\n  ;;\nesac\n\n# Try without a prefix underscore, then with it.\nfor ac_symprfx in \"\" \"_\"; do\n\n  # Transform symcode, sympat, and symprfx into a raw symbol and a C symbol.\n  symxfrm=\"\\\\1 $ac_symprfx\\\\2 \\\\2\"\n\n  # Write the raw and C identifiers.\n  if test \"$lt_cv_nm_interface\" = \"MS dumpbin\"; then\n    # Fake it for dumpbin and say T for any non-static function,\n    # D for any global variable and I for any imported variable.\n    # Also find C++ and __fastcall symbols from MSVC++ or ICC,\n    # which start with @ or ?.\n    lt_cv_sys_global_symbol_pipe=\"$AWK '\"\\\n\"     {last_section=section; section=\\$ 3};\"\\\n\"     /^COFF SYMBOL TABLE/{for(i in hide) delete hide[i]};\"\\\n\"     /Section length .*#relocs.*(pick any)/{hide[last_section]=1};\"\\\n\"     /^ *Symbol name *: /{split(\\$ 0,sn,\\\":\\\"); si=substr(sn[2],2)};\"\\\n\"     /^ *Type *: code/{print \\\"T\\\",si,substr(si,length(prfx))};\"\\\n\"     /^ *Type *: data/{print \\\"I\\\",si,substr(si,length(prfx))};\"\\\n\"     \\$ 0!~/External *\\|/{next};\"\\\n\"     / 0+ UNDEF /{next}; / UNDEF \\([^|]\\)*()/{next};\"\\\n\"     {if(hide[section]) next};\"\\\n\"     {f=\\\"D\\\"}; \\$ 0~/\\(\\).*\\|/{f=\\\"T\\\"};\"\\\n\"     {split(\\$ 0,a,/\\||\\r/); split(a[2],s)};\"\\\n\"     s[1]~/^[@?]/{print f,s[1],s[1]; next};\"\\\n\"     s[1]~prfx {split(s[1],t,\\\"@\\\"); print f,t[1],substr(t[1],length(prfx))}\"\\\n\"     ' prfx=^$ac_symprfx\"\n  else\n    lt_cv_sys_global_symbol_pipe=\"$SED -n -e 's/^.*[\t ]\\($symcode$symcode*\\)[\t ][\t ]*$ac_symprfx$sympat$opt_cr$/$symxfrm/p'\"\n  fi\n  lt_cv_sys_global_symbol_pipe=\"$lt_cv_sys_global_symbol_pipe | $SED '/ __gnu_lto/d'\"\n\n  # Check to see that the pipe works correctly.\n  pipe_works=no\n\n  rm -f conftest*\n  cat > conftest.$ac_ext <<_LT_EOF\n#ifdef __cplusplus\nextern \"C\" {\n#endif\nchar nm_test_var;\nvoid nm_test_func(void);\nvoid nm_test_func(void){}\n#ifdef __cplusplus\n}\n#endif\nint main(){nm_test_var='a';nm_test_func();return(0);}\n_LT_EOF\n\n  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; then\n    # Now try to grab the symbols.\n    nlist=conftest.nm\n    if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$NM conftest.$ac_objext \\| \"$lt_cv_sys_global_symbol_pipe\" \\> $nlist\\\"\"; } >&5\n  (eval $NM conftest.$ac_objext \\| \"$lt_cv_sys_global_symbol_pipe\" \\> $nlist) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && test -s \"$nlist\"; then\n      # Try sorting and uniquifying the output.\n      if sort \"$nlist\" | uniq > \"$nlist\"T; then\n\tmv -f \"$nlist\"T \"$nlist\"\n      else\n\trm -f \"$nlist\"T\n      fi\n\n      # Make sure that we snagged all the symbols we need.\n      if $GREP ' nm_test_var$' \"$nlist\" >/dev/null; then\n\tif $GREP ' nm_test_func$' \"$nlist\" >/dev/null; then\n\t  cat <<_LT_EOF > conftest.$ac_ext\n/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests.  */\n#if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE\n/* DATA imports from DLLs on WIN32 can't be const, because runtime\n   relocations are performed -- see ld's documentation on pseudo-relocs.  */\n# define LT_DLSYM_CONST\n#elif defined __osf__\n/* This system does not cope well with relocations in const data.  */\n# define LT_DLSYM_CONST\n#else\n# define LT_DLSYM_CONST const\n#endif\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n_LT_EOF\n\t  # Now generate the symbol file.\n\t  eval \"$lt_cv_sys_global_symbol_to_cdecl\"' < \"$nlist\" | $GREP -v main >> conftest.$ac_ext'\n\n\t  cat <<_LT_EOF >> conftest.$ac_ext\n\n/* The mapping between symbol names and symbols.  */\nLT_DLSYM_CONST struct {\n  const char *name;\n  void       *address;\n}\nlt__PROGRAM__LTX_preloaded_symbols[] =\n{\n  { \"@PROGRAM@\", (void *) 0 },\n_LT_EOF\n\t  $SED \"s/^$symcode$symcode* .* \\(.*\\)$/  {\\\"\\1\\\", (void *) \\&\\1},/\" < \"$nlist\" | $GREP -v main >> conftest.$ac_ext\n\t  cat <<\\_LT_EOF >> conftest.$ac_ext\n  {0, (void *) 0}\n};\n\n/* This works around a problem in FreeBSD linker */\n#ifdef FREEBSD_WORKAROUND\nstatic const void *lt_preloaded_setup() {\n  return lt__PROGRAM__LTX_preloaded_symbols;\n}\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n_LT_EOF\n\t  # Now try linking the two files.\n\t  mv conftest.$ac_objext conftstm.$ac_objext\n\t  lt_globsym_save_LIBS=$LIBS\n\t  lt_globsym_save_CFLAGS=$CFLAGS\n\t  LIBS=conftstm.$ac_objext\n\t  CFLAGS=\"$CFLAGS$lt_prog_compiler_no_builtin_flag\"\n\t  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_link\\\"\"; } >&5\n  (eval $ac_link) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && test -s conftest$ac_exeext; then\n\t    pipe_works=yes\n\t  fi\n\t  LIBS=$lt_globsym_save_LIBS\n\t  CFLAGS=$lt_globsym_save_CFLAGS\n\telse\n\t  echo \"cannot find nm_test_func in $nlist\" >&5\n\tfi\n      else\n\techo \"cannot find nm_test_var in $nlist\" >&5\n      fi\n    else\n      echo \"cannot run $lt_cv_sys_global_symbol_pipe\" >&5\n    fi\n  else\n    echo \"$progname: failed program was:\" >&5\n    cat conftest.$ac_ext >&5\n  fi\n  rm -rf conftest* conftst*\n\n  # Do not use the global_symbol_pipe unless it works.\n  if test yes = \"$pipe_works\"; then\n    break\n  else\n    lt_cv_sys_global_symbol_pipe=\n  fi\ndone\n ;;\nesac\nfi\n\nif test -z \"$lt_cv_sys_global_symbol_pipe\"; then\n  lt_cv_sys_global_symbol_to_cdecl=\nfi\nif test -z \"$lt_cv_sys_global_symbol_pipe$lt_cv_sys_global_symbol_to_cdecl\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: failed\" >&5\nprintf \"%s\\n\" \"failed\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: ok\" >&5\nprintf \"%s\\n\" \"ok\" >&6; }\nfi\n\n# Response file support.\nif test \"$lt_cv_nm_interface\" = \"MS dumpbin\"; then\n  nm_file_list_spec='@'\nelif $NM --help 2>/dev/null | grep '[@]FILE' >/dev/null; then\n  nm_file_list_spec='@'\nfi\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for sysroot\" >&5\nprintf %s \"checking for sysroot... \" >&6; }\n\n# Check whether --with-sysroot was given.\nif test ${with_sysroot+y}\nthen :\n  withval=$with_sysroot;\nelse case e in #(\n  e) with_sysroot=no ;;\nesac\nfi\n\n\nlt_sysroot=\ncase $with_sysroot in #(\n yes)\n   if test yes = \"$GCC\"; then\n     lt_sysroot=`$CC --print-sysroot 2>/dev/null`\n   fi\n   ;; #(\n /*)\n   lt_sysroot=`echo \"$with_sysroot\" | $SED -e \"$sed_quote_subst\"`\n   ;; #(\n no|'')\n   ;; #(\n *)\n   { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $with_sysroot\" >&5\nprintf \"%s\\n\" \"$with_sysroot\" >&6; }\n   as_fn_error $? \"The sysroot must be an absolute path.\" \"$LINENO\" 5\n   ;;\nesac\n\n { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: ${lt_sysroot:-no}\" >&5\nprintf \"%s\\n\" \"${lt_sysroot:-no}\" >&6; }\n\n\n\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for a working dd\" >&5\nprintf %s \"checking for a working dd... \" >&6; }\nif test ${ac_cv_path_lt_DD+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) printf 0123456789abcdef0123456789abcdef >conftest.i\ncat conftest.i conftest.i >conftest2.i\n: ${lt_DD:=$DD}\nif test -z \"$lt_DD\"; then\n  ac_path_lt_DD_found=false\n  # Loop through the user's path and test for each of PROGNAME-LIST\n  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_prog in dd\n   do\n    for ac_exec_ext in '' $ac_executable_extensions; do\n      ac_path_lt_DD=\"$as_dir$ac_prog$ac_exec_ext\"\n      as_fn_executable_p \"$ac_path_lt_DD\" || continue\nif \"$ac_path_lt_DD\" bs=32 count=1 <conftest2.i >conftest.out 2>/dev/null; then\n  cmp -s conftest.i conftest.out \\\n  && ac_cv_path_lt_DD=\"$ac_path_lt_DD\" ac_path_lt_DD_found=:\nfi\n      $ac_path_lt_DD_found && break 3\n    done\n  done\n  done\nIFS=$as_save_IFS\n  if test -z \"$ac_cv_path_lt_DD\"; then\n    :\n  fi\nelse\n  ac_cv_path_lt_DD=$lt_DD\nfi\n\nrm -f conftest.i conftest2.i conftest.out ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_path_lt_DD\" >&5\nprintf \"%s\\n\" \"$ac_cv_path_lt_DD\" >&6; }\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to truncate binary pipes\" >&5\nprintf %s \"checking how to truncate binary pipes... \" >&6; }\nif test ${lt_cv_truncate_bin+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) printf 0123456789abcdef0123456789abcdef >conftest.i\ncat conftest.i conftest.i >conftest2.i\nlt_cv_truncate_bin=\nif \"$ac_cv_path_lt_DD\" bs=32 count=1 <conftest2.i >conftest.out 2>/dev/null; then\n  cmp -s conftest.i conftest.out \\\n  && lt_cv_truncate_bin=\"$ac_cv_path_lt_DD bs=4096 count=1\"\nfi\nrm -f conftest.i conftest2.i conftest.out\ntest -z \"$lt_cv_truncate_bin\" && lt_cv_truncate_bin=\"$SED -e 4q\" ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_truncate_bin\" >&5\nprintf \"%s\\n\" \"$lt_cv_truncate_bin\" >&6; }\n\n\n\n\n\n\n\n# Calculate cc_basename.  Skip known compiler wrappers and cross-prefix.\nfunc_cc_basename ()\n{\n    for cc_temp in $*\"\"; do\n      case $cc_temp in\n        compile | *[\\\\/]compile | ccache | *[\\\\/]ccache ) ;;\n        distcc | *[\\\\/]distcc | purify | *[\\\\/]purify ) ;;\n        \\-*) ;;\n        *) break;;\n      esac\n    done\n    func_cc_basename_result=`$ECHO \"$cc_temp\" | $SED \"s%.*/%%; s%^$host_alias-%%\"`\n}\n\n# Check whether --enable-libtool-lock was given.\nif test ${enable_libtool_lock+y}\nthen :\n  enableval=$enable_libtool_lock;\nfi\n\ntest no = \"$enable_libtool_lock\" || enable_libtool_lock=yes\n\n# Some flags need to be propagated to the compiler or linker for good\n# libtool support.\ncase $host in\nia64-*-hpux*)\n  # Find out what ABI is being produced by ac_compile, and set mode\n  # options accordingly.\n  echo 'int i;' > conftest.$ac_ext\n  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; then\n    case `$FILECMD conftest.$ac_objext` in\n      *ELF-32*)\n\tHPUX_IA64_MODE=32\n\t;;\n      *ELF-64*)\n\tHPUX_IA64_MODE=64\n\t;;\n    esac\n  fi\n  rm -rf conftest*\n  ;;\n*-*-irix6*)\n  # Find out what ABI is being produced by ac_compile, and set linker\n  # options accordingly.\n  echo '#line '$LINENO' \"configure\"' > conftest.$ac_ext\n  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; then\n    if test yes = \"$lt_cv_prog_gnu_ld\"; then\n      case `$FILECMD conftest.$ac_objext` in\n\t*32-bit*)\n\t  LD=\"${LD-ld} -melf32bsmip\"\n\t  ;;\n\t*N32*)\n\t  LD=\"${LD-ld} -melf32bmipn32\"\n\t  ;;\n\t*64-bit*)\n\t  LD=\"${LD-ld} -melf64bmip\"\n\t;;\n      esac\n    else\n      case `$FILECMD conftest.$ac_objext` in\n\t*32-bit*)\n\t  LD=\"${LD-ld} -32\"\n\t  ;;\n\t*N32*)\n\t  LD=\"${LD-ld} -n32\"\n\t  ;;\n\t*64-bit*)\n\t  LD=\"${LD-ld} -64\"\n\t  ;;\n      esac\n    fi\n  fi\n  rm -rf conftest*\n  ;;\n\nmips64*-*linux*)\n  # Find out what ABI is being produced by ac_compile, and set linker\n  # options accordingly.\n  echo '#line '$LINENO' \"configure\"' > conftest.$ac_ext\n  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; then\n    emul=elf\n    case `$FILECMD conftest.$ac_objext` in\n      *32-bit*)\n\temul=\"${emul}32\"\n\t;;\n      *64-bit*)\n\temul=\"${emul}64\"\n\t;;\n    esac\n    case `$FILECMD conftest.$ac_objext` in\n      *MSB*)\n\temul=\"${emul}btsmip\"\n\t;;\n      *LSB*)\n\temul=\"${emul}ltsmip\"\n\t;;\n    esac\n    case `$FILECMD conftest.$ac_objext` in\n      *N32*)\n\temul=\"${emul}n32\"\n\t;;\n    esac\n    LD=\"${LD-ld} -m $emul\"\n  fi\n  rm -rf conftest*\n  ;;\n\nx86_64-*kfreebsd*-gnu|x86_64-*linux*|powerpc*-*linux*| \\\ns390*-*linux*|s390*-*tpf*|sparc*-*linux*)\n  # Find out what ABI is being produced by ac_compile, and set linker\n  # options accordingly.  Note that the listed cases only cover the\n  # situations where additional linker options are needed (such as when\n  # doing 32-bit compilation for a host where ld defaults to 64-bit, or\n  # vice versa); the common cases where no linker options are needed do\n  # not appear in the list.\n  echo 'int i;' > conftest.$ac_ext\n  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; then\n    case `$FILECMD conftest.o` in\n      *32-bit*)\n\tcase $host in\n\t  x86_64-*kfreebsd*-gnu)\n\t    LD=\"${LD-ld} -m elf_i386_fbsd\"\n\t    ;;\n\t  x86_64-*linux*)\n\t    case `$FILECMD conftest.o` in\n\t      *x86-64*)\n\t\tLD=\"${LD-ld} -m elf32_x86_64\"\n\t\t;;\n\t      *)\n\t\tLD=\"${LD-ld} -m elf_i386\"\n\t\t;;\n\t    esac\n\t    ;;\n\t  powerpc64le-*linux*)\n\t    LD=\"${LD-ld} -m elf32lppclinux\"\n\t    ;;\n\t  powerpc64-*linux*)\n\t    LD=\"${LD-ld} -m elf32ppclinux\"\n\t    ;;\n\t  s390x-*linux*)\n\t    LD=\"${LD-ld} -m elf_s390\"\n\t    ;;\n\t  sparc64-*linux*)\n\t    LD=\"${LD-ld} -m elf32_sparc\"\n\t    ;;\n\tesac\n\t;;\n      *64-bit*)\n\tcase $host in\n\t  x86_64-*kfreebsd*-gnu)\n\t    LD=\"${LD-ld} -m elf_x86_64_fbsd\"\n\t    ;;\n\t  x86_64-*linux*)\n\t    LD=\"${LD-ld} -m elf_x86_64\"\n\t    ;;\n\t  powerpcle-*linux*)\n\t    LD=\"${LD-ld} -m elf64lppc\"\n\t    ;;\n\t  powerpc-*linux*)\n\t    LD=\"${LD-ld} -m elf64ppc\"\n\t    ;;\n\t  s390*-*linux*|s390*-*tpf*)\n\t    LD=\"${LD-ld} -m elf64_s390\"\n\t    ;;\n\t  sparc*-*linux*)\n\t    LD=\"${LD-ld} -m elf64_sparc\"\n\t    ;;\n\tesac\n\t;;\n    esac\n  fi\n  rm -rf conftest*\n  ;;\n\n*-*-sco3.2v5*)\n  # On SCO OpenServer 5, we need -belf to get full-featured binaries.\n  SAVE_CFLAGS=$CFLAGS\n  CFLAGS=\"$CFLAGS -belf\"\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether the C compiler needs -belf\" >&5\nprintf %s \"checking whether the C compiler needs -belf... \" >&6; }\nif test ${lt_cv_cc_needs_belf+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\n     cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  lt_cv_cc_needs_belf=yes\nelse case e in #(\n  e) lt_cv_cc_needs_belf=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n     ac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_cc_needs_belf\" >&5\nprintf \"%s\\n\" \"$lt_cv_cc_needs_belf\" >&6; }\n  if test yes != \"$lt_cv_cc_needs_belf\"; then\n    # this is probably gcc 2.8.0, egcs 1.0 or newer; no need for -belf\n    CFLAGS=$SAVE_CFLAGS\n  fi\n  ;;\n*-*solaris*)\n  # Find out what ABI is being produced by ac_compile, and set linker\n  # options accordingly.\n  echo 'int i;' > conftest.$ac_ext\n  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; then\n    case `$FILECMD conftest.o` in\n    *64-bit*)\n      case $lt_cv_prog_gnu_ld in\n      yes*)\n        case $host in\n        i?86-*-solaris*|x86_64-*-solaris*)\n          LD=\"${LD-ld} -m elf_x86_64\"\n          ;;\n        sparc*-*-solaris*)\n          LD=\"${LD-ld} -m elf64_sparc\"\n          ;;\n        esac\n        # GNU ld 2.21 introduced _sol2 emulations.  Use them if available.\n        if ${LD-ld} -V | grep _sol2 >/dev/null 2>&1; then\n          LD=${LD-ld}_sol2\n        fi\n        ;;\n      *)\n\tif ${LD-ld} -64 -r -o conftest2.o conftest.o >/dev/null 2>&1; then\n\t  LD=\"${LD-ld} -64\"\n\tfi\n\t;;\n      esac\n      ;;\n    esac\n  fi\n  rm -rf conftest*\n  ;;\nesac\n\nneed_locks=$enable_libtool_lock\n\nif test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}mt\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}mt; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_MANIFEST_TOOL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$MANIFEST_TOOL\"; then\n  ac_cv_prog_MANIFEST_TOOL=\"$MANIFEST_TOOL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_MANIFEST_TOOL=\"${ac_tool_prefix}mt\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nMANIFEST_TOOL=$ac_cv_prog_MANIFEST_TOOL\nif test -n \"$MANIFEST_TOOL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $MANIFEST_TOOL\" >&5\nprintf \"%s\\n\" \"$MANIFEST_TOOL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_MANIFEST_TOOL\"; then\n  ac_ct_MANIFEST_TOOL=$MANIFEST_TOOL\n  # Extract the first word of \"mt\", so it can be a program name with args.\nset dummy mt; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_MANIFEST_TOOL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_MANIFEST_TOOL\"; then\n  ac_cv_prog_ac_ct_MANIFEST_TOOL=\"$ac_ct_MANIFEST_TOOL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_MANIFEST_TOOL=\"mt\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_MANIFEST_TOOL=$ac_cv_prog_ac_ct_MANIFEST_TOOL\nif test -n \"$ac_ct_MANIFEST_TOOL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_MANIFEST_TOOL\" >&5\nprintf \"%s\\n\" \"$ac_ct_MANIFEST_TOOL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_MANIFEST_TOOL\" = x; then\n    MANIFEST_TOOL=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    MANIFEST_TOOL=$ac_ct_MANIFEST_TOOL\n  fi\nelse\n  MANIFEST_TOOL=\"$ac_cv_prog_MANIFEST_TOOL\"\nfi\n\ntest -z \"$MANIFEST_TOOL\" && MANIFEST_TOOL=mt\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $MANIFEST_TOOL is a manifest tool\" >&5\nprintf %s \"checking if $MANIFEST_TOOL is a manifest tool... \" >&6; }\nif test ${lt_cv_path_mainfest_tool+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_path_mainfest_tool=no\n  echo \"$as_me:$LINENO: $MANIFEST_TOOL '-?'\" >&5\n  $MANIFEST_TOOL '-?' 2>conftest.err > conftest.out\n  cat conftest.err >&5\n  if $GREP 'Manifest Tool' conftest.out > /dev/null; then\n    lt_cv_path_mainfest_tool=yes\n  fi\n  rm -f conftest* ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_path_mainfest_tool\" >&5\nprintf \"%s\\n\" \"$lt_cv_path_mainfest_tool\" >&6; }\nif test yes != \"$lt_cv_path_mainfest_tool\"; then\n  MANIFEST_TOOL=:\nfi\n\n\n\n\n\n\n  case $host_os in\n    rhapsody* | darwin*)\n    if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}dsymutil\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}dsymutil; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_DSYMUTIL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$DSYMUTIL\"; then\n  ac_cv_prog_DSYMUTIL=\"$DSYMUTIL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_DSYMUTIL=\"${ac_tool_prefix}dsymutil\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nDSYMUTIL=$ac_cv_prog_DSYMUTIL\nif test -n \"$DSYMUTIL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $DSYMUTIL\" >&5\nprintf \"%s\\n\" \"$DSYMUTIL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_DSYMUTIL\"; then\n  ac_ct_DSYMUTIL=$DSYMUTIL\n  # Extract the first word of \"dsymutil\", so it can be a program name with args.\nset dummy dsymutil; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_DSYMUTIL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_DSYMUTIL\"; then\n  ac_cv_prog_ac_ct_DSYMUTIL=\"$ac_ct_DSYMUTIL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_DSYMUTIL=\"dsymutil\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_DSYMUTIL=$ac_cv_prog_ac_ct_DSYMUTIL\nif test -n \"$ac_ct_DSYMUTIL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_DSYMUTIL\" >&5\nprintf \"%s\\n\" \"$ac_ct_DSYMUTIL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_DSYMUTIL\" = x; then\n    DSYMUTIL=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    DSYMUTIL=$ac_ct_DSYMUTIL\n  fi\nelse\n  DSYMUTIL=\"$ac_cv_prog_DSYMUTIL\"\nfi\n\n    if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}nmedit\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}nmedit; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_NMEDIT+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$NMEDIT\"; then\n  ac_cv_prog_NMEDIT=\"$NMEDIT\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_NMEDIT=\"${ac_tool_prefix}nmedit\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nNMEDIT=$ac_cv_prog_NMEDIT\nif test -n \"$NMEDIT\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $NMEDIT\" >&5\nprintf \"%s\\n\" \"$NMEDIT\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_NMEDIT\"; then\n  ac_ct_NMEDIT=$NMEDIT\n  # Extract the first word of \"nmedit\", so it can be a program name with args.\nset dummy nmedit; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_NMEDIT+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_NMEDIT\"; then\n  ac_cv_prog_ac_ct_NMEDIT=\"$ac_ct_NMEDIT\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_NMEDIT=\"nmedit\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_NMEDIT=$ac_cv_prog_ac_ct_NMEDIT\nif test -n \"$ac_ct_NMEDIT\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_NMEDIT\" >&5\nprintf \"%s\\n\" \"$ac_ct_NMEDIT\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_NMEDIT\" = x; then\n    NMEDIT=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    NMEDIT=$ac_ct_NMEDIT\n  fi\nelse\n  NMEDIT=\"$ac_cv_prog_NMEDIT\"\nfi\n\n    if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}lipo\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}lipo; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_LIPO+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$LIPO\"; then\n  ac_cv_prog_LIPO=\"$LIPO\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_LIPO=\"${ac_tool_prefix}lipo\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nLIPO=$ac_cv_prog_LIPO\nif test -n \"$LIPO\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $LIPO\" >&5\nprintf \"%s\\n\" \"$LIPO\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_LIPO\"; then\n  ac_ct_LIPO=$LIPO\n  # Extract the first word of \"lipo\", so it can be a program name with args.\nset dummy lipo; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_LIPO+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_LIPO\"; then\n  ac_cv_prog_ac_ct_LIPO=\"$ac_ct_LIPO\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_LIPO=\"lipo\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_LIPO=$ac_cv_prog_ac_ct_LIPO\nif test -n \"$ac_ct_LIPO\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_LIPO\" >&5\nprintf \"%s\\n\" \"$ac_ct_LIPO\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_LIPO\" = x; then\n    LIPO=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    LIPO=$ac_ct_LIPO\n  fi\nelse\n  LIPO=\"$ac_cv_prog_LIPO\"\nfi\n\n    if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}otool\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}otool; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_OTOOL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$OTOOL\"; then\n  ac_cv_prog_OTOOL=\"$OTOOL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_OTOOL=\"${ac_tool_prefix}otool\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nOTOOL=$ac_cv_prog_OTOOL\nif test -n \"$OTOOL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $OTOOL\" >&5\nprintf \"%s\\n\" \"$OTOOL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_OTOOL\"; then\n  ac_ct_OTOOL=$OTOOL\n  # Extract the first word of \"otool\", so it can be a program name with args.\nset dummy otool; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_OTOOL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_OTOOL\"; then\n  ac_cv_prog_ac_ct_OTOOL=\"$ac_ct_OTOOL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_OTOOL=\"otool\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_OTOOL=$ac_cv_prog_ac_ct_OTOOL\nif test -n \"$ac_ct_OTOOL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_OTOOL\" >&5\nprintf \"%s\\n\" \"$ac_ct_OTOOL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_OTOOL\" = x; then\n    OTOOL=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    OTOOL=$ac_ct_OTOOL\n  fi\nelse\n  OTOOL=\"$ac_cv_prog_OTOOL\"\nfi\n\n    if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}otool64\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}otool64; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_OTOOL64+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$OTOOL64\"; then\n  ac_cv_prog_OTOOL64=\"$OTOOL64\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_OTOOL64=\"${ac_tool_prefix}otool64\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nOTOOL64=$ac_cv_prog_OTOOL64\nif test -n \"$OTOOL64\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $OTOOL64\" >&5\nprintf \"%s\\n\" \"$OTOOL64\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_OTOOL64\"; then\n  ac_ct_OTOOL64=$OTOOL64\n  # Extract the first word of \"otool64\", so it can be a program name with args.\nset dummy otool64; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_OTOOL64+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_OTOOL64\"; then\n  ac_cv_prog_ac_ct_OTOOL64=\"$ac_ct_OTOOL64\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_OTOOL64=\"otool64\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_OTOOL64=$ac_cv_prog_ac_ct_OTOOL64\nif test -n \"$ac_ct_OTOOL64\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_OTOOL64\" >&5\nprintf \"%s\\n\" \"$ac_ct_OTOOL64\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_OTOOL64\" = x; then\n    OTOOL64=\":\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    OTOOL64=$ac_ct_OTOOL64\n  fi\nelse\n  OTOOL64=\"$ac_cv_prog_OTOOL64\"\nfi\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for -single_module linker flag\" >&5\nprintf %s \"checking for -single_module linker flag... \" >&6; }\nif test ${lt_cv_apple_cc_single_mod+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_apple_cc_single_mod=no\n      if test -z \"$LT_MULTI_MODULE\"; then\n\t# By default we will add the -single_module flag. You can override\n\t# by either setting the environment variable LT_MULTI_MODULE\n\t# non-empty at configure time, or by adding -multi_module to the\n\t# link flags.\n\trm -rf libconftest.dylib*\n\techo \"int foo(void){return 1;}\" > conftest.c\n\techo \"$LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \\\n-dynamiclib -Wl,-single_module conftest.c\" >&5\n\t$LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \\\n\t  -dynamiclib -Wl,-single_module conftest.c 2>conftest.err\n        _lt_result=$?\n\t# If there is a non-empty error log, and \"single_module\"\n\t# appears in it, assume the flag caused a linker warning\n        if test -s conftest.err && $GREP single_module conftest.err; then\n\t  cat conftest.err >&5\n\t# Otherwise, if the output was created with a 0 exit code from\n\t# the compiler, it worked.\n\telif test -f libconftest.dylib && test 0 = \"$_lt_result\"; then\n\t  lt_cv_apple_cc_single_mod=yes\n\telse\n\t  cat conftest.err >&5\n\tfi\n\trm -rf libconftest.dylib*\n\trm -f conftest.*\n      fi ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_apple_cc_single_mod\" >&5\nprintf \"%s\\n\" \"$lt_cv_apple_cc_single_mod\" >&6; }\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for -exported_symbols_list linker flag\" >&5\nprintf %s \"checking for -exported_symbols_list linker flag... \" >&6; }\nif test ${lt_cv_ld_exported_symbols_list+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_ld_exported_symbols_list=no\n      save_LDFLAGS=$LDFLAGS\n      echo \"_main\" > conftest.sym\n      LDFLAGS=\"$LDFLAGS -Wl,-exported_symbols_list,conftest.sym\"\n      cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  lt_cv_ld_exported_symbols_list=yes\nelse case e in #(\n  e) lt_cv_ld_exported_symbols_list=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n\tLDFLAGS=$save_LDFLAGS\n     ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_exported_symbols_list\" >&5\nprintf \"%s\\n\" \"$lt_cv_ld_exported_symbols_list\" >&6; }\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for -force_load linker flag\" >&5\nprintf %s \"checking for -force_load linker flag... \" >&6; }\nif test ${lt_cv_ld_force_load+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_ld_force_load=no\n      cat > conftest.c << _LT_EOF\nint forced_loaded() { return 2;}\n_LT_EOF\n      echo \"$LTCC $LTCFLAGS -c -o conftest.o conftest.c\" >&5\n      $LTCC $LTCFLAGS -c -o conftest.o conftest.c 2>&5\n      echo \"$AR $AR_FLAGS libconftest.a conftest.o\" >&5\n      $AR $AR_FLAGS libconftest.a conftest.o 2>&5\n      echo \"$RANLIB libconftest.a\" >&5\n      $RANLIB libconftest.a 2>&5\n      cat > conftest.c << _LT_EOF\nint main() { return 0;}\n_LT_EOF\n      echo \"$LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a\" >&5\n      $LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a 2>conftest.err\n      _lt_result=$?\n      if test -s conftest.err && $GREP force_load conftest.err; then\n\tcat conftest.err >&5\n      elif test -f conftest && test 0 = \"$_lt_result\" && $GREP forced_load conftest >/dev/null 2>&1; then\n\tlt_cv_ld_force_load=yes\n      else\n\tcat conftest.err >&5\n      fi\n        rm -f conftest.err libconftest.a conftest conftest.c\n        rm -rf conftest.dSYM\n     ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_ld_force_load\" >&5\nprintf \"%s\\n\" \"$lt_cv_ld_force_load\" >&6; }\n    case $host_os in\n    rhapsody* | darwin1.[012])\n      _lt_dar_allow_undefined='$wl-undefined ${wl}suppress' ;;\n    darwin1.*)\n      _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;;\n    darwin*)\n      case $MACOSX_DEPLOYMENT_TARGET,$host in\n        10.[012],*|,*powerpc*-darwin[5-8]*)\n          _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;;\n        *)\n          _lt_dar_allow_undefined='$wl-undefined ${wl}dynamic_lookup' ;;\n      esac\n    ;;\n  esac\n    if test yes = \"$lt_cv_apple_cc_single_mod\"; then\n      _lt_dar_single_mod='$single_module'\n    fi\n    if test yes = \"$lt_cv_ld_exported_symbols_list\"; then\n      _lt_dar_export_syms=' $wl-exported_symbols_list,$output_objdir/$libname-symbols.expsym'\n    else\n      _lt_dar_export_syms='~$NMEDIT -s $output_objdir/$libname-symbols.expsym $lib'\n    fi\n    if test : != \"$DSYMUTIL\" && test no = \"$lt_cv_ld_force_load\"; then\n      _lt_dsymutil='~$DSYMUTIL $lib || :'\n    else\n      _lt_dsymutil=\n    fi\n    ;;\n  esac\n\n# func_munge_path_list VARIABLE PATH\n# -----------------------------------\n# VARIABLE is name of variable containing _space_ separated list of\n# directories to be munged by the contents of PATH, which is string\n# having a format:\n# \"DIR[:DIR]:\"\n#       string \"DIR[ DIR]\" will be prepended to VARIABLE\n# \":DIR[:DIR]\"\n#       string \"DIR[ DIR]\" will be appended to VARIABLE\n# \"DIRP[:DIRP]::[DIRA:]DIRA\"\n#       string \"DIRP[ DIRP]\" will be prepended to VARIABLE and string\n#       \"DIRA[ DIRA]\" will be appended to VARIABLE\n# \"DIR[:DIR]\"\n#       VARIABLE will be replaced by \"DIR[ DIR]\"\nfunc_munge_path_list ()\n{\n    case x$2 in\n    x)\n        ;;\n    *:)\n        eval $1=\\\"`$ECHO $2 | $SED 's/:/ /g'` \\$$1\\\"\n        ;;\n    x:*)\n        eval $1=\\\"\\$$1 `$ECHO $2 | $SED 's/:/ /g'`\\\"\n        ;;\n    *::*)\n        eval $1=\\\"\\$$1\\ `$ECHO $2 | $SED -e 's/.*:://' -e 's/:/ /g'`\\\"\n        eval $1=\\\"`$ECHO $2 | $SED -e 's/::.*//' -e 's/:/ /g'`\\ \\$$1\\\"\n        ;;\n    *)\n        eval $1=\\\"`$ECHO $2 | $SED 's/:/ /g'`\\\"\n        ;;\n    esac\n}\n\nac_header= ac_cache=\nfor ac_item in $ac_header_c_list\ndo\n  if test $ac_cache; then\n    ac_fn_c_check_header_compile \"$LINENO\" $ac_header ac_cv_header_$ac_cache \"$ac_includes_default\"\n    if eval test \\\"x\\$ac_cv_header_$ac_cache\\\" = xyes; then\n      printf \"%s\\n\" \"#define $ac_item 1\" >> confdefs.h\n    fi\n    ac_header= ac_cache=\n  elif test $ac_header; then\n    ac_cache=$ac_item\n  else\n    ac_header=$ac_item\n  fi\ndone\n\n\n\n\n\n\n\n\nif test $ac_cv_header_stdlib_h = yes && test $ac_cv_header_string_h = yes\nthen :\n\nprintf \"%s\\n\" \"#define STDC_HEADERS 1\" >>confdefs.h\n\nfi\nac_fn_c_check_header_compile \"$LINENO\" \"dlfcn.h\" \"ac_cv_header_dlfcn_h\" \"$ac_includes_default\n\"\nif test \"x$ac_cv_header_dlfcn_h\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_DLFCN_H 1\" >>confdefs.h\n\nfi\n\n\n\n\nfunc_stripname_cnf ()\n{\n  case $2 in\n  .*) func_stripname_result=`$ECHO \"$3\" | $SED \"s%^$1%%; s%\\\\\\\\$2\\$%%\"`;;\n  *)  func_stripname_result=`$ECHO \"$3\" | $SED \"s%^$1%%; s%$2\\$%%\"`;;\n  esac\n} # func_stripname_cnf\n\n\n\n\n\n# Set options\nenable_win32_dll=yes\n\ncase $host in\n*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-cegcc*)\n  if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}as\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}as; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_AS+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$AS\"; then\n  ac_cv_prog_AS=\"$AS\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_AS=\"${ac_tool_prefix}as\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nAS=$ac_cv_prog_AS\nif test -n \"$AS\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $AS\" >&5\nprintf \"%s\\n\" \"$AS\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_AS\"; then\n  ac_ct_AS=$AS\n  # Extract the first word of \"as\", so it can be a program name with args.\nset dummy as; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_AS+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_AS\"; then\n  ac_cv_prog_ac_ct_AS=\"$ac_ct_AS\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_AS=\"as\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_AS=$ac_cv_prog_ac_ct_AS\nif test -n \"$ac_ct_AS\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_AS\" >&5\nprintf \"%s\\n\" \"$ac_ct_AS\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_AS\" = x; then\n    AS=\"false\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    AS=$ac_ct_AS\n  fi\nelse\n  AS=\"$ac_cv_prog_AS\"\nfi\n\n  if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}dlltool\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}dlltool; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_DLLTOOL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$DLLTOOL\"; then\n  ac_cv_prog_DLLTOOL=\"$DLLTOOL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_DLLTOOL=\"${ac_tool_prefix}dlltool\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nDLLTOOL=$ac_cv_prog_DLLTOOL\nif test -n \"$DLLTOOL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $DLLTOOL\" >&5\nprintf \"%s\\n\" \"$DLLTOOL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_DLLTOOL\"; then\n  ac_ct_DLLTOOL=$DLLTOOL\n  # Extract the first word of \"dlltool\", so it can be a program name with args.\nset dummy dlltool; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_DLLTOOL+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_DLLTOOL\"; then\n  ac_cv_prog_ac_ct_DLLTOOL=\"$ac_ct_DLLTOOL\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_DLLTOOL=\"dlltool\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_DLLTOOL=$ac_cv_prog_ac_ct_DLLTOOL\nif test -n \"$ac_ct_DLLTOOL\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_DLLTOOL\" >&5\nprintf \"%s\\n\" \"$ac_ct_DLLTOOL\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_DLLTOOL\" = x; then\n    DLLTOOL=\"false\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    DLLTOOL=$ac_ct_DLLTOOL\n  fi\nelse\n  DLLTOOL=\"$ac_cv_prog_DLLTOOL\"\nfi\n\n  if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}objdump\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}objdump; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_OBJDUMP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$OBJDUMP\"; then\n  ac_cv_prog_OBJDUMP=\"$OBJDUMP\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_OBJDUMP=\"${ac_tool_prefix}objdump\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nOBJDUMP=$ac_cv_prog_OBJDUMP\nif test -n \"$OBJDUMP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $OBJDUMP\" >&5\nprintf \"%s\\n\" \"$OBJDUMP\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nfi\nif test -z \"$ac_cv_prog_OBJDUMP\"; then\n  ac_ct_OBJDUMP=$OBJDUMP\n  # Extract the first word of \"objdump\", so it can be a program name with args.\nset dummy objdump; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_ac_ct_OBJDUMP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$ac_ct_OBJDUMP\"; then\n  ac_cv_prog_ac_ct_OBJDUMP=\"$ac_ct_OBJDUMP\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_OBJDUMP=\"objdump\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nac_ct_OBJDUMP=$ac_cv_prog_ac_ct_OBJDUMP\nif test -n \"$ac_ct_OBJDUMP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_ct_OBJDUMP\" >&5\nprintf \"%s\\n\" \"$ac_ct_OBJDUMP\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n  if test \"x$ac_ct_OBJDUMP\" = x; then\n    OBJDUMP=\"false\"\n  else\n    case $cross_compiling:$ac_tool_warned in\nyes:)\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: using cross tools not prefixed with host triplet\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: using cross tools not prefixed with host triplet\" >&2;}\nac_tool_warned=yes ;;\nesac\n    OBJDUMP=$ac_ct_OBJDUMP\n  fi\nelse\n  OBJDUMP=\"$ac_cv_prog_OBJDUMP\"\nfi\n\n  ;;\nesac\n\ntest -z \"$AS\" && AS=as\n\n\n\n\n\ntest -z \"$DLLTOOL\" && DLLTOOL=dlltool\n\n\n\n\n\ntest -z \"$OBJDUMP\" && OBJDUMP=objdump\n\n\n\n\n# Check whether --enable-shared was given.\nif test ${enable_shared+y}\nthen :\n  enableval=$enable_shared; p=${PACKAGE-default}\n    case $enableval in\n    yes) enable_shared=yes ;;\n    no) enable_shared=no ;;\n    *)\n      enable_shared=no\n      # Look at the argument we got.  We use all the common list separators.\n      lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,\n      for pkg in $enableval; do\n\tIFS=$lt_save_ifs\n\tif test \"X$pkg\" = \"X$p\"; then\n\t  enable_shared=yes\n\tfi\n      done\n      IFS=$lt_save_ifs\n      ;;\n    esac\nelse case e in #(\n  e) enable_shared=no ;;\nesac\nfi\n\n\n\n\n\n\n\n\n\n\n        enable_dlopen=no\n\n\n\n\n  # Check whether --enable-static was given.\nif test ${enable_static+y}\nthen :\n  enableval=$enable_static; p=${PACKAGE-default}\n    case $enableval in\n    yes) enable_static=yes ;;\n    no) enable_static=no ;;\n    *)\n     enable_static=no\n      # Look at the argument we got.  We use all the common list separators.\n      lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,\n      for pkg in $enableval; do\n\tIFS=$lt_save_ifs\n\tif test \"X$pkg\" = \"X$p\"; then\n\t  enable_static=yes\n\tfi\n      done\n      IFS=$lt_save_ifs\n      ;;\n    esac\nelse case e in #(\n  e) enable_static=yes ;;\nesac\nfi\n\n\n\n\n\n\n\n\n\n\n# Check whether --with-pic was given.\nif test ${with_pic+y}\nthen :\n  withval=$with_pic; lt_p=${PACKAGE-default}\n    case $withval in\n    yes|no) pic_mode=$withval ;;\n    *)\n      pic_mode=default\n      # Look at the argument we got.  We use all the common list separators.\n      lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,\n      for lt_pkg in $withval; do\n\tIFS=$lt_save_ifs\n\tif test \"X$lt_pkg\" = \"X$lt_p\"; then\n\t  pic_mode=yes\n\tfi\n      done\n      IFS=$lt_save_ifs\n      ;;\n    esac\nelse case e in #(\n  e) pic_mode=default ;;\nesac\nfi\n\n\n\n\n\n\n\n\n  # Check whether --enable-fast-install was given.\nif test ${enable_fast_install+y}\nthen :\n  enableval=$enable_fast_install; p=${PACKAGE-default}\n    case $enableval in\n    yes) enable_fast_install=yes ;;\n    no) enable_fast_install=no ;;\n    *)\n      enable_fast_install=no\n      # Look at the argument we got.  We use all the common list separators.\n      lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,\n      for pkg in $enableval; do\n\tIFS=$lt_save_ifs\n\tif test \"X$pkg\" = \"X$p\"; then\n\t  enable_fast_install=yes\n\tfi\n      done\n      IFS=$lt_save_ifs\n      ;;\n    esac\nelse case e in #(\n  e) enable_fast_install=yes ;;\nesac\nfi\n\n\n\n\n\n\n\n\n  shared_archive_member_spec=\ncase $host,$enable_shared in\npower*-*-aix[5-9]*,yes)\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking which variant of shared library versioning to provide\" >&5\nprintf %s \"checking which variant of shared library versioning to provide... \" >&6; }\n\n# Check whether --with-aix-soname was given.\nif test ${with_aix_soname+y}\nthen :\n  withval=$with_aix_soname; case $withval in\n    aix|svr4|both)\n      ;;\n    *)\n      as_fn_error $? \"Unknown argument to --with-aix-soname\" \"$LINENO\" 5\n      ;;\n    esac\n    lt_cv_with_aix_soname=$with_aix_soname\nelse case e in #(\n  e) if test ${lt_cv_with_aix_soname+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_with_aix_soname=aix ;;\nesac\nfi\n\n    with_aix_soname=$lt_cv_with_aix_soname ;;\nesac\nfi\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $with_aix_soname\" >&5\nprintf \"%s\\n\" \"$with_aix_soname\" >&6; }\n  if test aix != \"$with_aix_soname\"; then\n    # For the AIX way of multilib, we name the shared archive member\n    # based on the bitwidth used, traditionally 'shr.o' or 'shr_64.o',\n    # and 'shr.imp' or 'shr_64.imp', respectively, for the Import File.\n    # Even when GNU compilers ignore OBJECT_MODE but need '-maix64' flag,\n    # the AIX toolchain works better with OBJECT_MODE set (default 32).\n    if test 64 = \"${OBJECT_MODE-32}\"; then\n      shared_archive_member_spec=shr_64\n    else\n      shared_archive_member_spec=shr\n    fi\n  fi\n  ;;\n*)\n  with_aix_soname=aix\n  ;;\nesac\n\n\n\n\n\n\n\n\n\n\n# This can be used to rebuild libtool when needed\nLIBTOOL_DEPS=$ltmain\n\n# Always use our own libtool.\nLIBTOOL='$(SHELL) $(top_builddir)/libtool'\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\ntest -z \"$LN_S\" && LN_S=\"ln -s\"\n\n\n\n\n\n\n\n\n\n\n\n\n\n\nif test -n \"${ZSH_VERSION+set}\"; then\n   setopt NO_GLOB_SUBST\nfi\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for objdir\" >&5\nprintf %s \"checking for objdir... \" >&6; }\nif test ${lt_cv_objdir+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) rm -f .libs 2>/dev/null\nmkdir .libs 2>/dev/null\nif test -d .libs; then\n  lt_cv_objdir=.libs\nelse\n  # MS-DOS does not allow filenames that begin with a dot.\n  lt_cv_objdir=_libs\nfi\nrmdir .libs 2>/dev/null ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_objdir\" >&5\nprintf \"%s\\n\" \"$lt_cv_objdir\" >&6; }\nobjdir=$lt_cv_objdir\n\n\n\n\n\nprintf \"%s\\n\" \"#define LT_OBJDIR \\\"$lt_cv_objdir/\\\"\" >>confdefs.h\n\n\n\n\ncase $host_os in\naix3*)\n  # AIX sometimes has problems with the GCC collect2 program.  For some\n  # reason, if we set the COLLECT_NAMES environment variable, the problems\n  # vanish in a puff of smoke.\n  if test set != \"${COLLECT_NAMES+set}\"; then\n    COLLECT_NAMES=\n    export COLLECT_NAMES\n  fi\n  ;;\nesac\n\n# Global variables:\nofile=libtool\ncan_build_shared=yes\n\n# All known linkers require a '.a' archive for static linking (except MSVC and\n# ICC, which need '.lib').\nlibext=a\n\nwith_gnu_ld=$lt_cv_prog_gnu_ld\n\nold_CC=$CC\nold_CFLAGS=$CFLAGS\n\n# Set sane defaults for various variables\ntest -z \"$CC\" && CC=cc\ntest -z \"$LTCC\" && LTCC=$CC\ntest -z \"$LTCFLAGS\" && LTCFLAGS=$CFLAGS\ntest -z \"$LD\" && LD=ld\ntest -z \"$ac_objext\" && ac_objext=o\n\nfunc_cc_basename $compiler\ncc_basename=$func_cc_basename_result\n\n\n# Only perform the check for file, if the check method requires it\ntest -z \"$MAGIC_CMD\" && MAGIC_CMD=file\ncase $deplibs_check_method in\nfile_magic*)\n  if test \"$file_magic_cmd\" = '$MAGIC_CMD'; then\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for ${ac_tool_prefix}file\" >&5\nprintf %s \"checking for ${ac_tool_prefix}file... \" >&6; }\nif test ${lt_cv_path_MAGIC_CMD+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) case $MAGIC_CMD in\n[\\\\/*] |  ?:[\\\\/]*)\n  lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path.\n  ;;\n*)\n  lt_save_MAGIC_CMD=$MAGIC_CMD\n  lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR\n  ac_dummy=\"/usr/bin$PATH_SEPARATOR$PATH\"\n  for ac_dir in $ac_dummy; do\n    IFS=$lt_save_ifs\n    test -z \"$ac_dir\" && ac_dir=.\n    if test -f \"$ac_dir/${ac_tool_prefix}file\"; then\n      lt_cv_path_MAGIC_CMD=$ac_dir/\"${ac_tool_prefix}file\"\n      if test -n \"$file_magic_test_file\"; then\n\tcase $deplibs_check_method in\n\t\"file_magic \"*)\n\t  file_magic_regex=`expr \"$deplibs_check_method\" : \"file_magic \\(.*\\)\"`\n\t  MAGIC_CMD=$lt_cv_path_MAGIC_CMD\n\t  if eval $file_magic_cmd \\$file_magic_test_file 2> /dev/null |\n\t    $EGREP \"$file_magic_regex\" > /dev/null; then\n\t    :\n\t  else\n\t    cat <<_LT_EOF 1>&2\n\n*** Warning: the command libtool uses to detect shared libraries,\n*** $file_magic_cmd, produces output that libtool cannot recognize.\n*** The result is that libtool may fail to recognize shared libraries\n*** as such.  This will affect the creation of libtool libraries that\n*** depend on shared libraries, but programs linked with such libtool\n*** libraries will work regardless of this problem.  Nevertheless, you\n*** may want to report the problem to your system manager and/or to\n*** bug-libtool@gnu.org\n\n_LT_EOF\n\t  fi ;;\n\tesac\n      fi\n      break\n    fi\n  done\n  IFS=$lt_save_ifs\n  MAGIC_CMD=$lt_save_MAGIC_CMD\n  ;;\nesac ;;\nesac\nfi\n\nMAGIC_CMD=$lt_cv_path_MAGIC_CMD\nif test -n \"$MAGIC_CMD\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $MAGIC_CMD\" >&5\nprintf \"%s\\n\" \"$MAGIC_CMD\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n\n\n\nif test -z \"$lt_cv_path_MAGIC_CMD\"; then\n  if test -n \"$ac_tool_prefix\"; then\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for file\" >&5\nprintf %s \"checking for file... \" >&6; }\nif test ${lt_cv_path_MAGIC_CMD+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) case $MAGIC_CMD in\n[\\\\/*] |  ?:[\\\\/]*)\n  lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path.\n  ;;\n*)\n  lt_save_MAGIC_CMD=$MAGIC_CMD\n  lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR\n  ac_dummy=\"/usr/bin$PATH_SEPARATOR$PATH\"\n  for ac_dir in $ac_dummy; do\n    IFS=$lt_save_ifs\n    test -z \"$ac_dir\" && ac_dir=.\n    if test -f \"$ac_dir/file\"; then\n      lt_cv_path_MAGIC_CMD=$ac_dir/\"file\"\n      if test -n \"$file_magic_test_file\"; then\n\tcase $deplibs_check_method in\n\t\"file_magic \"*)\n\t  file_magic_regex=`expr \"$deplibs_check_method\" : \"file_magic \\(.*\\)\"`\n\t  MAGIC_CMD=$lt_cv_path_MAGIC_CMD\n\t  if eval $file_magic_cmd \\$file_magic_test_file 2> /dev/null |\n\t    $EGREP \"$file_magic_regex\" > /dev/null; then\n\t    :\n\t  else\n\t    cat <<_LT_EOF 1>&2\n\n*** Warning: the command libtool uses to detect shared libraries,\n*** $file_magic_cmd, produces output that libtool cannot recognize.\n*** The result is that libtool may fail to recognize shared libraries\n*** as such.  This will affect the creation of libtool libraries that\n*** depend on shared libraries, but programs linked with such libtool\n*** libraries will work regardless of this problem.  Nevertheless, you\n*** may want to report the problem to your system manager and/or to\n*** bug-libtool@gnu.org\n\n_LT_EOF\n\t  fi ;;\n\tesac\n      fi\n      break\n    fi\n  done\n  IFS=$lt_save_ifs\n  MAGIC_CMD=$lt_save_MAGIC_CMD\n  ;;\nesac ;;\nesac\nfi\n\nMAGIC_CMD=$lt_cv_path_MAGIC_CMD\nif test -n \"$MAGIC_CMD\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $MAGIC_CMD\" >&5\nprintf \"%s\\n\" \"$MAGIC_CMD\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  else\n    MAGIC_CMD=:\n  fi\nfi\n\n  fi\n  ;;\nesac\n\n# Use C for the default configuration in the libtool script\n\nlt_save_CC=$CC\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\n\n# Source file extension for C test sources.\nac_ext=c\n\n# Object file extension for compiled C test sources.\nobjext=o\nobjext=$objext\n\n# Code to be used in simple compile tests\nlt_simple_compile_test_code=\"int some_variable = 0;\"\n\n# Code to be used in simple link tests\nlt_simple_link_test_code='int main(){return(0);}'\n\n\n\n\n\n\n\n# If no C compiler was specified, use CC.\nLTCC=${LTCC-\"$CC\"}\n\n# If no C compiler flags were specified, use CFLAGS.\nLTCFLAGS=${LTCFLAGS-\"$CFLAGS\"}\n\n# Allow CC to be a program name with arguments.\ncompiler=$CC\n\n# Save the default compiler, since it gets overwritten when the other\n# tags are being tested, and _LT_TAGVAR(compiler, []) is a NOP.\ncompiler_DEFAULT=$CC\n\n# save warnings/boilerplate of simple test code\nac_outfile=conftest.$ac_objext\necho \"$lt_simple_compile_test_code\" >conftest.$ac_ext\neval \"$ac_compile\" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err\n_lt_compiler_boilerplate=`cat conftest.err`\n$RM conftest*\n\nac_outfile=conftest.$ac_objext\necho \"$lt_simple_link_test_code\" >conftest.$ac_ext\neval \"$ac_link\" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err\n_lt_linker_boilerplate=`cat conftest.err`\n$RM -r conftest*\n\n\n## CAVEAT EMPTOR:\n## There is no encapsulation within the following macros, do not change\n## the running order or otherwise move them around unless you know exactly\n## what you are doing...\nif test -n \"$compiler\"; then\n\nlt_prog_compiler_no_builtin_flag=\n\nif test yes = \"$GCC\"; then\n  case $cc_basename in\n  nvcc*)\n    lt_prog_compiler_no_builtin_flag=' -Xcompiler -fno-builtin' ;;\n  *)\n    lt_prog_compiler_no_builtin_flag=' -fno-builtin' ;;\n  esac\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler supports -fno-rtti -fno-exceptions\" >&5\nprintf %s \"checking if $compiler supports -fno-rtti -fno-exceptions... \" >&6; }\nif test ${lt_cv_prog_compiler_rtti_exceptions+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_rtti_exceptions=no\n   ac_outfile=conftest.$ac_objext\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n   lt_compiler_flag=\"-fno-rtti -fno-exceptions\"  ## exclude from sc_useless_quotes_in_assignment\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   # The option is referenced via a variable to avoid confusing sed.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [^ ]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&5)\n   (eval \"$lt_compile\" 2>conftest.err)\n   ac_status=$?\n   cat conftest.err >&5\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   if (exit $ac_status) && test -s \"$ac_outfile\"; then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings other than the usual output.\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' >conftest.exp\n     $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2\n     if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then\n       lt_cv_prog_compiler_rtti_exceptions=yes\n     fi\n   fi\n   $RM conftest*\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_rtti_exceptions\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_rtti_exceptions\" >&6; }\n\nif test yes = \"$lt_cv_prog_compiler_rtti_exceptions\"; then\n    lt_prog_compiler_no_builtin_flag=\"$lt_prog_compiler_no_builtin_flag -fno-rtti -fno-exceptions\"\nelse\n    :\nfi\n\nfi\n\n\n\n\n\n\n  lt_prog_compiler_wl=\nlt_prog_compiler_pic=\nlt_prog_compiler_static=\n\n\n  if test yes = \"$GCC\"; then\n    lt_prog_compiler_wl='-Wl,'\n    lt_prog_compiler_static='-static'\n\n    case $host_os in\n      aix*)\n      # All AIX code is PIC.\n      if test ia64 = \"$host_cpu\"; then\n\t# AIX 5 now supports IA64 processor\n\tlt_prog_compiler_static='-Bstatic'\n      fi\n      lt_prog_compiler_pic='-fPIC'\n      ;;\n\n    amigaos*)\n      case $host_cpu in\n      powerpc)\n            # see comment about AmigaOS4 .so support\n            lt_prog_compiler_pic='-fPIC'\n        ;;\n      m68k)\n            # FIXME: we need at least 68020 code to build shared libraries, but\n            # adding the '-m68020' flag to GCC prevents building anything better,\n            # like '-m68040'.\n            lt_prog_compiler_pic='-m68020 -resident32 -malways-restore-a4'\n        ;;\n      esac\n      ;;\n\n    beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*)\n      # PIC is the default for these OSes.\n      ;;\n\n    mingw* | cygwin* | pw32* | os2* | cegcc*)\n      # This hack is so that the source file can tell whether it is being\n      # built for inclusion in a dll (and should export symbols for example).\n      # Although the cygwin gcc ignores -fPIC, still need this for old-style\n      # (--disable-auto-import) libraries\n      lt_prog_compiler_pic='-DDLL_EXPORT'\n      case $host_os in\n      os2*)\n\tlt_prog_compiler_static='$wl-static'\n\t;;\n      esac\n      ;;\n\n    darwin* | rhapsody*)\n      # PIC is the default on this platform\n      # Common symbols not allowed in MH_DYLIB files\n      lt_prog_compiler_pic='-fno-common'\n      ;;\n\n    haiku*)\n      # PIC is the default for Haiku.\n      # The \"-static\" flag exists, but is broken.\n      lt_prog_compiler_static=\n      ;;\n\n    hpux*)\n      # PIC is the default for 64-bit PA HP-UX, but not for 32-bit\n      # PA HP-UX.  On IA64 HP-UX, PIC is the default but the pic flag\n      # sets the default TLS model and affects inlining.\n      case $host_cpu in\n      hppa*64*)\n\t# +Z the default\n\t;;\n      *)\n\tlt_prog_compiler_pic='-fPIC'\n\t;;\n      esac\n      ;;\n\n    interix[3-9]*)\n      # Interix 3.x gcc -fpic/-fPIC options generate broken code.\n      # Instead, we relocate shared libraries at runtime.\n      ;;\n\n    msdosdjgpp*)\n      # Just because we use GCC doesn't mean we suddenly get shared libraries\n      # on systems that don't support them.\n      lt_prog_compiler_can_build_shared=no\n      enable_shared=no\n      ;;\n\n    *nto* | *qnx*)\n      # QNX uses GNU C++, but need to define -shared option too, otherwise\n      # it will coredump.\n      lt_prog_compiler_pic='-fPIC -shared'\n      ;;\n\n    sysv4*MP*)\n      if test -d /usr/nec; then\n\tlt_prog_compiler_pic=-Kconform_pic\n      fi\n      ;;\n\n    *)\n      lt_prog_compiler_pic='-fPIC'\n      ;;\n    esac\n\n    case $cc_basename in\n    nvcc*) # Cuda Compiler Driver 2.2\n      lt_prog_compiler_wl='-Xlinker '\n      if test -n \"$lt_prog_compiler_pic\"; then\n        lt_prog_compiler_pic=\"-Xcompiler $lt_prog_compiler_pic\"\n      fi\n      ;;\n    esac\n  else\n    # PORTME Check for flag to pass linker flags through the system compiler.\n    case $host_os in\n    aix*)\n      lt_prog_compiler_wl='-Wl,'\n      if test ia64 = \"$host_cpu\"; then\n\t# AIX 5 now supports IA64 processor\n\tlt_prog_compiler_static='-Bstatic'\n      else\n\tlt_prog_compiler_static='-bnso -bI:/lib/syscalls.exp'\n      fi\n      ;;\n\n    darwin* | rhapsody*)\n      # PIC is the default on this platform\n      # Common symbols not allowed in MH_DYLIB files\n      lt_prog_compiler_pic='-fno-common'\n      case $cc_basename in\n      nagfor*)\n        # NAG Fortran compiler\n        lt_prog_compiler_wl='-Wl,-Wl,,'\n        lt_prog_compiler_pic='-PIC'\n        lt_prog_compiler_static='-Bstatic'\n        ;;\n      esac\n      ;;\n\n    mingw* | cygwin* | pw32* | os2* | cegcc*)\n      # This hack is so that the source file can tell whether it is being\n      # built for inclusion in a dll (and should export symbols for example).\n      lt_prog_compiler_pic='-DDLL_EXPORT'\n      case $host_os in\n      os2*)\n\tlt_prog_compiler_static='$wl-static'\n\t;;\n      esac\n      ;;\n\n    hpux9* | hpux10* | hpux11*)\n      lt_prog_compiler_wl='-Wl,'\n      # PIC is the default for IA64 HP-UX and 64-bit HP-UX, but\n      # not for PA HP-UX.\n      case $host_cpu in\n      hppa*64*|ia64*)\n\t# +Z the default\n\t;;\n      *)\n\tlt_prog_compiler_pic='+Z'\n\t;;\n      esac\n      # Is there a better lt_prog_compiler_static that works with the bundled CC?\n      lt_prog_compiler_static='$wl-a ${wl}archive'\n      ;;\n\n    irix5* | irix6* | nonstopux*)\n      lt_prog_compiler_wl='-Wl,'\n      # PIC (with -KPIC) is the default.\n      lt_prog_compiler_static='-non_shared'\n      ;;\n\n    linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n      case $cc_basename in\n      # old Intel for x86_64, which still supported -KPIC.\n      ecc*)\n\tlt_prog_compiler_wl='-Wl,'\n\tlt_prog_compiler_pic='-KPIC'\n\tlt_prog_compiler_static='-static'\n        ;;\n      # icc used to be incompatible with GCC.\n      # ICC 10 doesn't accept -KPIC any more.\n      icc* | ifort*)\n\tlt_prog_compiler_wl='-Wl,'\n\tlt_prog_compiler_pic='-fPIC'\n\tlt_prog_compiler_static='-static'\n        ;;\n      # Lahey Fortran 8.1.\n      lf95*)\n\tlt_prog_compiler_wl='-Wl,'\n\tlt_prog_compiler_pic='--shared'\n\tlt_prog_compiler_static='--static'\n\t;;\n      nagfor*)\n\t# NAG Fortran compiler\n\tlt_prog_compiler_wl='-Wl,-Wl,,'\n\tlt_prog_compiler_pic='-PIC'\n\tlt_prog_compiler_static='-Bstatic'\n\t;;\n      tcc*)\n\t# Fabrice Bellard et al's Tiny C Compiler\n\tlt_prog_compiler_wl='-Wl,'\n\tlt_prog_compiler_pic='-fPIC'\n\tlt_prog_compiler_static='-static'\n\t;;\n      pgcc* | pgf77* | pgf90* | pgf95* | pgfortran*)\n        # Portland Group compilers (*not* the Pentium gcc compiler,\n\t# which looks to be a dead project)\n\tlt_prog_compiler_wl='-Wl,'\n\tlt_prog_compiler_pic='-fpic'\n\tlt_prog_compiler_static='-Bstatic'\n        ;;\n      ccc*)\n        lt_prog_compiler_wl='-Wl,'\n        # All Alpha code is PIC.\n        lt_prog_compiler_static='-non_shared'\n        ;;\n      xl* | bgxl* | bgf* | mpixl*)\n\t# IBM XL C 8.0/Fortran 10.1, 11.1 on PPC and BlueGene\n\tlt_prog_compiler_wl='-Wl,'\n\tlt_prog_compiler_pic='-qpic'\n\tlt_prog_compiler_static='-qstaticlink'\n\t;;\n      *)\n\tcase `$CC -V 2>&1 | $SED 5q` in\n\t*Sun\\ Ceres\\ Fortran* | *Sun*Fortran*\\ [1-7].* | *Sun*Fortran*\\ 8.[0-3]*)\n\t  # Sun Fortran 8.3 passes all unrecognized flags to the linker\n\t  lt_prog_compiler_pic='-KPIC'\n\t  lt_prog_compiler_static='-Bstatic'\n\t  lt_prog_compiler_wl=''\n\t  ;;\n\t*Sun\\ F* | *Sun*Fortran*)\n\t  lt_prog_compiler_pic='-KPIC'\n\t  lt_prog_compiler_static='-Bstatic'\n\t  lt_prog_compiler_wl='-Qoption ld '\n\t  ;;\n\t*Sun\\ C*)\n\t  # Sun C 5.9\n\t  lt_prog_compiler_pic='-KPIC'\n\t  lt_prog_compiler_static='-Bstatic'\n\t  lt_prog_compiler_wl='-Wl,'\n\t  ;;\n        *Intel*\\ [CF]*Compiler*)\n\t  lt_prog_compiler_wl='-Wl,'\n\t  lt_prog_compiler_pic='-fPIC'\n\t  lt_prog_compiler_static='-static'\n\t  ;;\n\t*Portland\\ Group*)\n\t  lt_prog_compiler_wl='-Wl,'\n\t  lt_prog_compiler_pic='-fpic'\n\t  lt_prog_compiler_static='-Bstatic'\n\t  ;;\n\tesac\n\t;;\n      esac\n      ;;\n\n    newsos6)\n      lt_prog_compiler_pic='-KPIC'\n      lt_prog_compiler_static='-Bstatic'\n      ;;\n\n    *nto* | *qnx*)\n      # QNX uses GNU C++, but need to define -shared option too, otherwise\n      # it will coredump.\n      lt_prog_compiler_pic='-fPIC -shared'\n      ;;\n\n    osf3* | osf4* | osf5*)\n      lt_prog_compiler_wl='-Wl,'\n      # All OSF/1 code is PIC.\n      lt_prog_compiler_static='-non_shared'\n      ;;\n\n    rdos*)\n      lt_prog_compiler_static='-non_shared'\n      ;;\n\n    solaris*)\n      lt_prog_compiler_pic='-KPIC'\n      lt_prog_compiler_static='-Bstatic'\n      case $cc_basename in\n      f77* | f90* | f95* | sunf77* | sunf90* | sunf95*)\n\tlt_prog_compiler_wl='-Qoption ld ';;\n      *)\n\tlt_prog_compiler_wl='-Wl,';;\n      esac\n      ;;\n\n    sunos4*)\n      lt_prog_compiler_wl='-Qoption ld '\n      lt_prog_compiler_pic='-PIC'\n      lt_prog_compiler_static='-Bstatic'\n      ;;\n\n    sysv4 | sysv4.2uw2* | sysv4.3*)\n      lt_prog_compiler_wl='-Wl,'\n      lt_prog_compiler_pic='-KPIC'\n      lt_prog_compiler_static='-Bstatic'\n      ;;\n\n    sysv4*MP*)\n      if test -d /usr/nec; then\n\tlt_prog_compiler_pic='-Kconform_pic'\n\tlt_prog_compiler_static='-Bstatic'\n      fi\n      ;;\n\n    sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*)\n      lt_prog_compiler_wl='-Wl,'\n      lt_prog_compiler_pic='-KPIC'\n      lt_prog_compiler_static='-Bstatic'\n      ;;\n\n    unicos*)\n      lt_prog_compiler_wl='-Wl,'\n      lt_prog_compiler_can_build_shared=no\n      ;;\n\n    uts4*)\n      lt_prog_compiler_pic='-pic'\n      lt_prog_compiler_static='-Bstatic'\n      ;;\n\n    *)\n      lt_prog_compiler_can_build_shared=no\n      ;;\n    esac\n  fi\n\ncase $host_os in\n  # For platforms that do not support PIC, -DPIC is meaningless:\n  *djgpp*)\n    lt_prog_compiler_pic=\n    ;;\n  *)\n    lt_prog_compiler_pic=\"$lt_prog_compiler_pic -DPIC\"\n    ;;\nesac\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $compiler option to produce PIC\" >&5\nprintf %s \"checking for $compiler option to produce PIC... \" >&6; }\nif test ${lt_cv_prog_compiler_pic+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_pic=$lt_prog_compiler_pic ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_pic\" >&6; }\nlt_prog_compiler_pic=$lt_cv_prog_compiler_pic\n\n#\n# Check to make sure the PIC flag actually works.\n#\nif test -n \"$lt_prog_compiler_pic\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler PIC flag $lt_prog_compiler_pic works\" >&5\nprintf %s \"checking if $compiler PIC flag $lt_prog_compiler_pic works... \" >&6; }\nif test ${lt_cv_prog_compiler_pic_works+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_pic_works=no\n   ac_outfile=conftest.$ac_objext\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n   lt_compiler_flag=\"$lt_prog_compiler_pic -DPIC\"  ## exclude from sc_useless_quotes_in_assignment\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   # The option is referenced via a variable to avoid confusing sed.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [^ ]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&5)\n   (eval \"$lt_compile\" 2>conftest.err)\n   ac_status=$?\n   cat conftest.err >&5\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   if (exit $ac_status) && test -s \"$ac_outfile\"; then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings other than the usual output.\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' >conftest.exp\n     $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2\n     if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then\n       lt_cv_prog_compiler_pic_works=yes\n     fi\n   fi\n   $RM conftest*\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic_works\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_pic_works\" >&6; }\n\nif test yes = \"$lt_cv_prog_compiler_pic_works\"; then\n    case $lt_prog_compiler_pic in\n     \"\" | \" \"*) ;;\n     *) lt_prog_compiler_pic=\" $lt_prog_compiler_pic\" ;;\n     esac\nelse\n    lt_prog_compiler_pic=\n     lt_prog_compiler_can_build_shared=no\nfi\n\nfi\n\n\n\n\n\n\n\n\n\n\n\n#\n# Check to make sure the static flag actually works.\n#\nwl=$lt_prog_compiler_wl eval lt_tmp_static_flag=\\\"$lt_prog_compiler_static\\\"\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler static flag $lt_tmp_static_flag works\" >&5\nprintf %s \"checking if $compiler static flag $lt_tmp_static_flag works... \" >&6; }\nif test ${lt_cv_prog_compiler_static_works+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_static_works=no\n   save_LDFLAGS=$LDFLAGS\n   LDFLAGS=\"$LDFLAGS $lt_tmp_static_flag\"\n   echo \"$lt_simple_link_test_code\" > conftest.$ac_ext\n   if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then\n     # The linker can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     if test -s conftest.err; then\n       # Append any errors to the config.log.\n       cat conftest.err 1>&5\n       $ECHO \"$_lt_linker_boilerplate\" | $SED '/^$/d' > conftest.exp\n       $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2\n       if diff conftest.exp conftest.er2 >/dev/null; then\n         lt_cv_prog_compiler_static_works=yes\n       fi\n     else\n       lt_cv_prog_compiler_static_works=yes\n     fi\n   fi\n   $RM -r conftest*\n   LDFLAGS=$save_LDFLAGS\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_static_works\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_static_works\" >&6; }\n\nif test yes = \"$lt_cv_prog_compiler_static_works\"; then\n    :\nelse\n    lt_prog_compiler_static=\nfi\n\n\n\n\n\n\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext\" >&5\nprintf %s \"checking if $compiler supports -c -o file.$ac_objext... \" >&6; }\nif test ${lt_cv_prog_compiler_c_o+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_c_o=no\n   $RM -r conftest 2>/dev/null\n   mkdir conftest\n   cd conftest\n   mkdir out\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n\n   lt_compiler_flag=\"-o out/conftest2.$ac_objext\"\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [^ ]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&5)\n   (eval \"$lt_compile\" 2>out/conftest.err)\n   ac_status=$?\n   cat out/conftest.err >&5\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   if (exit $ac_status) && test -s out/conftest2.$ac_objext\n   then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' > out/conftest.exp\n     $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2\n     if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then\n       lt_cv_prog_compiler_c_o=yes\n     fi\n   fi\n   chmod u+w . 2>&5\n   $RM conftest*\n   # SGI C++ compiler will create directory out/ii_files/ for\n   # template instantiation\n   test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files\n   $RM out/* && rmdir out\n   cd ..\n   $RM -r conftest\n   $RM conftest*\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_c_o\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_c_o\" >&6; }\n\n\n\n\n\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext\" >&5\nprintf %s \"checking if $compiler supports -c -o file.$ac_objext... \" >&6; }\nif test ${lt_cv_prog_compiler_c_o+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_c_o=no\n   $RM -r conftest 2>/dev/null\n   mkdir conftest\n   cd conftest\n   mkdir out\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n\n   lt_compiler_flag=\"-o out/conftest2.$ac_objext\"\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [^ ]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&5)\n   (eval \"$lt_compile\" 2>out/conftest.err)\n   ac_status=$?\n   cat out/conftest.err >&5\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   if (exit $ac_status) && test -s out/conftest2.$ac_objext\n   then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' > out/conftest.exp\n     $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2\n     if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then\n       lt_cv_prog_compiler_c_o=yes\n     fi\n   fi\n   chmod u+w . 2>&5\n   $RM conftest*\n   # SGI C++ compiler will create directory out/ii_files/ for\n   # template instantiation\n   test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files\n   $RM out/* && rmdir out\n   cd ..\n   $RM -r conftest\n   $RM conftest*\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_c_o\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_c_o\" >&6; }\n\n\n\n\nhard_links=nottested\nif test no = \"$lt_cv_prog_compiler_c_o\" && test no != \"$need_locks\"; then\n  # do not overwrite the value of need_locks provided by the user\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if we can lock with hard links\" >&5\nprintf %s \"checking if we can lock with hard links... \" >&6; }\n  hard_links=yes\n  $RM conftest*\n  ln conftest.a conftest.b 2>/dev/null && hard_links=no\n  touch conftest.a\n  ln conftest.a conftest.b 2>&5 || hard_links=no\n  ln conftest.a conftest.b 2>/dev/null && hard_links=no\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $hard_links\" >&5\nprintf \"%s\\n\" \"$hard_links\" >&6; }\n  if test no = \"$hard_links\"; then\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: '$CC' does not support '-c -o', so 'make -j' may be unsafe\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: '$CC' does not support '-c -o', so 'make -j' may be unsafe\" >&2;}\n    need_locks=warn\n  fi\nelse\n  need_locks=no\nfi\n\n\n\n\n\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether the $compiler linker ($LD) supports shared libraries\" >&5\nprintf %s \"checking whether the $compiler linker ($LD) supports shared libraries... \" >&6; }\n\n  runpath_var=\n  allow_undefined_flag=\n  always_export_symbols=no\n  archive_cmds=\n  archive_expsym_cmds=\n  compiler_needs_object=no\n  enable_shared_with_static_runtimes=no\n  export_dynamic_flag_spec=\n  export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\\''s/.* //'\\'' | sort | uniq > $export_symbols'\n  hardcode_automatic=no\n  hardcode_direct=no\n  hardcode_direct_absolute=no\n  hardcode_libdir_flag_spec=\n  hardcode_libdir_separator=\n  hardcode_minus_L=no\n  hardcode_shlibpath_var=unsupported\n  inherit_rpath=no\n  link_all_deplibs=unknown\n  module_cmds=\n  module_expsym_cmds=\n  old_archive_from_new_cmds=\n  old_archive_from_expsyms_cmds=\n  thread_safe_flag_spec=\n  whole_archive_flag_spec=\n  # include_expsyms should be a list of space-separated symbols to be *always*\n  # included in the symbol list\n  include_expsyms=\n  # exclude_expsyms can be an extended regexp of symbols to exclude\n  # it will be wrapped by ' (' and ')$', so one must not match beginning or\n  # end of line.  Example: 'a|bc|.*d.*' will exclude the symbols 'a' and 'bc',\n  # as well as any symbol that contains 'd'.\n  exclude_expsyms='_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*'\n  # Although _GLOBAL_OFFSET_TABLE_ is a valid symbol C name, most a.out\n  # platforms (ab)use it in PIC code, but their linkers get confused if\n  # the symbol is explicitly referenced.  Since portable code cannot\n  # rely on this symbol name, it's probably fine to never include it in\n  # preloaded symbol tables.\n  # Exclude shared library initialization/finalization symbols.\n  extract_expsyms_cmds=\n\n  case $host_os in\n  cygwin* | mingw* | pw32* | cegcc*)\n    # FIXME: the MSVC++ and ICC port hasn't been tested in a loooong time\n    # When not using gcc, we currently assume that we are using\n    # Microsoft Visual C++ or Intel C++ Compiler.\n    if test yes != \"$GCC\"; then\n      with_gnu_ld=no\n    fi\n    ;;\n  interix*)\n    # we just hope/assume this is gcc and not c89 (= MSVC++ or ICC)\n    with_gnu_ld=yes\n    ;;\n  openbsd* | bitrig*)\n    with_gnu_ld=no\n    ;;\n  esac\n\n  ld_shlibs=yes\n\n  # On some targets, GNU ld is compatible enough with the native linker\n  # that we're better off using the native interface for both.\n  lt_use_gnu_ld_interface=no\n  if test yes = \"$with_gnu_ld\"; then\n    case $host_os in\n      aix*)\n\t# The AIX port of GNU ld has always aspired to compatibility\n\t# with the native linker.  However, as the warning in the GNU ld\n\t# block says, versions before 2.19.5* couldn't really create working\n\t# shared libraries, regardless of the interface used.\n\tcase `$LD -v 2>&1` in\n\t  *\\ \\(GNU\\ Binutils\\)\\ 2.19.5*) ;;\n\t  *\\ \\(GNU\\ Binutils\\)\\ 2.[2-9]*) ;;\n\t  *\\ \\(GNU\\ Binutils\\)\\ [3-9]*) ;;\n\t  *)\n\t    lt_use_gnu_ld_interface=yes\n\t    ;;\n\tesac\n\t;;\n      *)\n\tlt_use_gnu_ld_interface=yes\n\t;;\n    esac\n  fi\n\n  if test yes = \"$lt_use_gnu_ld_interface\"; then\n    # If archive_cmds runs LD, not CC, wlarc should be empty\n    wlarc='$wl'\n\n    # Set some defaults for GNU ld with shared library support. These\n    # are reset later if shared libraries are not supported. Putting them\n    # here allows them to be overridden if necessary.\n    runpath_var=LD_RUN_PATH\n    hardcode_libdir_flag_spec='$wl-rpath $wl$libdir'\n    export_dynamic_flag_spec='$wl--export-dynamic'\n    # ancient GNU ld didn't support --whole-archive et. al.\n    if $LD --help 2>&1 | $GREP 'no-whole-archive' > /dev/null; then\n      whole_archive_flag_spec=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive'\n    else\n      whole_archive_flag_spec=\n    fi\n    supports_anon_versioning=no\n    case `$LD -v | $SED -e 's/([^)]\\+)\\s\\+//' 2>&1` in\n      *GNU\\ gold*) supports_anon_versioning=yes ;;\n      *\\ [01].* | *\\ 2.[0-9].* | *\\ 2.10.*) ;; # catch versions < 2.11\n      *\\ 2.11.93.0.2\\ *) supports_anon_versioning=yes ;; # RH7.3 ...\n      *\\ 2.11.92.0.12\\ *) supports_anon_versioning=yes ;; # Mandrake 8.2 ...\n      *\\ 2.11.*) ;; # other 2.11 versions\n      *) supports_anon_versioning=yes ;;\n    esac\n\n    # See if GNU ld supports shared libraries.\n    case $host_os in\n    aix[3-9]*)\n      # On AIX/PPC, the GNU linker is very broken\n      if test ia64 != \"$host_cpu\"; then\n\tld_shlibs=no\n\tcat <<_LT_EOF 1>&2\n\n*** Warning: the GNU linker, at least up to release 2.19, is reported\n*** to be unable to reliably create shared libraries on AIX.\n*** Therefore, libtool is disabling shared libraries support.  If you\n*** really care for shared libraries, you may want to install binutils\n*** 2.20 or above, or modify your PATH so that a non-GNU linker is found.\n*** You will then need to restart the configuration process.\n\n_LT_EOF\n      fi\n      ;;\n\n    amigaos*)\n      case $host_cpu in\n      powerpc)\n            # see comment about AmigaOS4 .so support\n            archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n            archive_expsym_cmds=''\n        ;;\n      m68k)\n            archive_cmds='$RM $output_objdir/a2ixlibrary.data~$ECHO \"#define NAME $libname\" > $output_objdir/a2ixlibrary.data~$ECHO \"#define LIBRARY_ID 1\" >> $output_objdir/a2ixlibrary.data~$ECHO \"#define VERSION $major\" >> $output_objdir/a2ixlibrary.data~$ECHO \"#define REVISION $revision\" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)'\n            hardcode_libdir_flag_spec='-L$libdir'\n            hardcode_minus_L=yes\n        ;;\n      esac\n      ;;\n\n    beos*)\n      if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\tallow_undefined_flag=unsupported\n\t# Joseph Beckenbach <jrb3@best.com> says some releases of gcc\n\t# support --undefined.  This deserves some investigation.  FIXME\n\tarchive_cmds='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n      else\n\tld_shlibs=no\n      fi\n      ;;\n\n    cygwin* | mingw* | pw32* | cegcc*)\n      # _LT_TAGVAR(hardcode_libdir_flag_spec, ) is actually meaningless,\n      # as there is no search path for DLLs.\n      hardcode_libdir_flag_spec='-L$libdir'\n      export_dynamic_flag_spec='$wl--export-all-symbols'\n      allow_undefined_flag=unsupported\n      always_export_symbols=no\n      enable_shared_with_static_runtimes=yes\n      export_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\\''/^[BCDGRS][ ]/s/.*[ ]\\([^ ]*\\)/\\1 DATA/;s/^.*[ ]__nm__\\([^ ]*\\)[ ][^ ]*/\\1 DATA/;/^I[ ]/d;/^[AITW][ ]/s/.* //'\\'' | sort | uniq > $export_symbols'\n      exclude_expsyms='[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname'\n\n      if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then\n        archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib'\n\t# If the export-symbols file already is a .def file, use it as\n\t# is; otherwise, prepend EXPORTS...\n\tarchive_expsym_cmds='if   test DEF = \"`$SED -n     -e '\\''s/^[\t ]*//'\\''     -e '\\''/^\\(;.*\\)*$/d'\\''     -e '\\''s/^\\(EXPORTS\\|LIBRARY\\)\\([\t ].*\\)*$/DEF/p'\\''     -e q     $export_symbols`\" ; then\n          cp $export_symbols $output_objdir/$soname.def;\n        else\n          echo EXPORTS > $output_objdir/$soname.def;\n          cat $export_symbols >> $output_objdir/$soname.def;\n        fi~\n        $CC -shared $output_objdir/$soname.def $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib'\n      else\n\tld_shlibs=no\n      fi\n      ;;\n\n    haiku*)\n      archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n      link_all_deplibs=yes\n      ;;\n\n    os2*)\n      hardcode_libdir_flag_spec='-L$libdir'\n      hardcode_minus_L=yes\n      allow_undefined_flag=unsupported\n      shrext_cmds=.dll\n      archive_cmds='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t$ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t$ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t$ECHO EXPORTS >> $output_objdir/$libname.def~\n\temxexp $libobjs | $SED /\"_DLL_InitTerm\"/d >> $output_objdir/$libname.def~\n\t$CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\temximp -o $lib $output_objdir/$libname.def'\n      archive_expsym_cmds='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t$ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t$ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t$ECHO EXPORTS >> $output_objdir/$libname.def~\n\tprefix_cmds=\"$SED\"~\n\tif test EXPORTS = \"`$SED 1q $export_symbols`\"; then\n\t  prefix_cmds=\"$prefix_cmds -e 1d\";\n\tfi~\n\tprefix_cmds=\"$prefix_cmds -e \\\"s/^\\(.*\\)$/_\\1/g\\\"\"~\n\tcat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~\n\t$CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\temximp -o $lib $output_objdir/$libname.def'\n      old_archive_From_new_cmds='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def'\n      enable_shared_with_static_runtimes=yes\n      file_list_spec='@'\n      ;;\n\n    interix[3-9]*)\n      hardcode_direct=no\n      hardcode_shlibpath_var=no\n      hardcode_libdir_flag_spec='$wl-rpath,$libdir'\n      export_dynamic_flag_spec='$wl-E'\n      # Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc.\n      # Instead, shared libraries are loaded at an image base (0x10000000 by\n      # default) and relocated if they conflict, which is a slow very memory\n      # consuming and fragmenting process.  To avoid this, we pick a random,\n      # 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link\n      # time.  Moving up from 0x10000000 also allows more sbrk(2) space.\n      archive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \\* 262144 + 1342177280` -o $lib'\n      archive_expsym_cmds='$SED \"s|^|_|\" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \\* 262144 + 1342177280` -o $lib'\n      ;;\n\n    gnu* | linux* | tpf* | k*bsd*-gnu | kopensolaris*-gnu)\n      tmp_diet=no\n      if test linux-dietlibc = \"$host_os\"; then\n\tcase $cc_basename in\n\t  diet\\ *) tmp_diet=yes;;\t# linux-dietlibc with static linking (!diet-dyn)\n\tesac\n      fi\n      if $LD --help 2>&1 | $EGREP ': supported targets:.* elf' > /dev/null \\\n\t && test no = \"$tmp_diet\"\n      then\n\ttmp_addflag=' $pic_flag'\n\ttmp_sharedflag='-shared'\n\tcase $cc_basename,$host_cpu in\n        pgcc*)\t\t\t\t# Portland Group C compiler\n\t  whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t  tmp_addflag=' $pic_flag'\n\t  ;;\n\tpgf77* | pgf90* | pgf95* | pgfortran*)\n\t\t\t\t\t# Portland Group f77 and f90 compilers\n\t  whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t  tmp_addflag=' $pic_flag -Mnomain' ;;\n\tecc*,ia64* | icc*,ia64*)\t# Intel C compiler on ia64\n\t  tmp_addflag=' -i_dynamic' ;;\n\tefc*,ia64* | ifort*,ia64*)\t# Intel Fortran compiler on ia64\n\t  tmp_addflag=' -i_dynamic -nofor_main' ;;\n\tifc* | ifort*)\t\t\t# Intel Fortran compiler\n\t  tmp_addflag=' -nofor_main' ;;\n\tlf95*)\t\t\t\t# Lahey Fortran 8.1\n\t  whole_archive_flag_spec=\n\t  tmp_sharedflag='--shared' ;;\n        nagfor*)                        # NAGFOR 5.3\n          tmp_sharedflag='-Wl,-shared' ;;\n\txl[cC]* | bgxl[cC]* | mpixl[cC]*) # IBM XL C 8.0 on PPC (deal with xlf below)\n\t  tmp_sharedflag='-qmkshrobj'\n\t  tmp_addflag= ;;\n\tnvcc*)\t# Cuda Compiler Driver 2.2\n\t  whole_archive_flag_spec='$wl--whole-archive`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t  compiler_needs_object=yes\n\t  ;;\n\tesac\n\tcase `$CC -V 2>&1 | $SED 5q` in\n\t*Sun\\ C*)\t\t\t# Sun C 5.9\n\t  whole_archive_flag_spec='$wl--whole-archive`new_convenience=; for conv in $convenience\\\"\\\"; do test -z \\\"$conv\\\" || new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t  compiler_needs_object=yes\n\t  tmp_sharedflag='-G' ;;\n\t*Sun\\ F*)\t\t\t# Sun Fortran 8.3\n\t  tmp_sharedflag='-G' ;;\n\tesac\n\tarchive_cmds='$CC '\"$tmp_sharedflag\"\"$tmp_addflag\"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\n        if test yes = \"$supports_anon_versioning\"; then\n          archive_expsym_cmds='echo \"{ global:\" > $output_objdir/$libname.ver~\n            cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $output_objdir/$libname.ver~\n            echo \"local: *; };\" >> $output_objdir/$libname.ver~\n            $CC '\"$tmp_sharedflag\"\"$tmp_addflag\"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib'\n        fi\n\n\tcase $cc_basename in\n\ttcc*)\n\t  export_dynamic_flag_spec='-rdynamic'\n\t  ;;\n\txlf* | bgf* | bgxlf* | mpixlf*)\n\t  # IBM XL Fortran 10.1 on PPC cannot create shared libs itself\n\t  whole_archive_flag_spec='--whole-archive$convenience --no-whole-archive'\n\t  hardcode_libdir_flag_spec='$wl-rpath $wl$libdir'\n\t  archive_cmds='$LD -shared $libobjs $deplibs $linker_flags -soname $soname -o $lib'\n\t  if test yes = \"$supports_anon_versioning\"; then\n\t    archive_expsym_cmds='echo \"{ global:\" > $output_objdir/$libname.ver~\n              cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $output_objdir/$libname.ver~\n              echo \"local: *; };\" >> $output_objdir/$libname.ver~\n              $LD -shared $libobjs $deplibs $linker_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib'\n\t  fi\n\t  ;;\n\tesac\n      else\n        ld_shlibs=no\n      fi\n      ;;\n\n    netbsd*)\n      if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n\tarchive_cmds='$LD -Bshareable $libobjs $deplibs $linker_flags -o $lib'\n\twlarc=\n      else\n\tarchive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\tarchive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n      fi\n      ;;\n\n    solaris*)\n      if $LD -v 2>&1 | $GREP 'BFD 2\\.8' > /dev/null; then\n\tld_shlibs=no\n\tcat <<_LT_EOF 1>&2\n\n*** Warning: The releases 2.8.* of the GNU linker cannot reliably\n*** create shared libraries on Solaris systems.  Therefore, libtool\n*** is disabling shared libraries support.  We urge you to upgrade GNU\n*** binutils to release 2.9.1 or newer.  Another option is to modify\n*** your PATH or compiler configuration so that the native linker is\n*** used, and then restart.\n\n_LT_EOF\n      elif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\tarchive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\tarchive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n      else\n\tld_shlibs=no\n      fi\n      ;;\n\n    sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX*)\n      case `$LD -v 2>&1` in\n        *\\ [01].* | *\\ 2.[0-9].* | *\\ 2.1[0-5].*)\n\tld_shlibs=no\n\tcat <<_LT_EOF 1>&2\n\n*** Warning: Releases of the GNU linker prior to 2.16.91.0.3 cannot\n*** reliably create shared libraries on SCO systems.  Therefore, libtool\n*** is disabling shared libraries support.  We urge you to upgrade GNU\n*** binutils to release 2.16.91.0.3 or newer.  Another option is to modify\n*** your PATH or compiler configuration so that the native linker is\n*** used, and then restart.\n\n_LT_EOF\n\t;;\n\t*)\n\t  # For security reasons, it is highly recommended that you always\n\t  # use absolute paths for naming shared libraries, and exclude the\n\t  # DT_RUNPATH tag from executables and libraries.  But doing so\n\t  # requires that you compile everything twice, which is a pain.\n\t  if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\t    hardcode_libdir_flag_spec='$wl-rpath $wl$libdir'\n\t    archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t    archive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t  else\n\t    ld_shlibs=no\n\t  fi\n\t;;\n      esac\n      ;;\n\n    sunos4*)\n      archive_cmds='$LD -assert pure-text -Bshareable -o $lib $libobjs $deplibs $linker_flags'\n      wlarc=\n      hardcode_direct=yes\n      hardcode_shlibpath_var=no\n      ;;\n\n    *)\n      if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\tarchive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\tarchive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n      else\n\tld_shlibs=no\n      fi\n      ;;\n    esac\n\n    if test no = \"$ld_shlibs\"; then\n      runpath_var=\n      hardcode_libdir_flag_spec=\n      export_dynamic_flag_spec=\n      whole_archive_flag_spec=\n    fi\n  else\n    # PORTME fill in a description of your system's linker (not GNU ld)\n    case $host_os in\n    aix3*)\n      allow_undefined_flag=unsupported\n      always_export_symbols=yes\n      archive_expsym_cmds='$LD -o $output_objdir/$soname $libobjs $deplibs $linker_flags -bE:$export_symbols -T512 -H512 -bM:SRE~$AR $AR_FLAGS $lib $output_objdir/$soname'\n      # Note: this linker hardcodes the directories in LIBPATH if there\n      # are no directories specified by -L.\n      hardcode_minus_L=yes\n      if test yes = \"$GCC\" && test -z \"$lt_prog_compiler_static\"; then\n\t# Neither direct hardcoding nor static linking is supported with a\n\t# broken collect2.\n\thardcode_direct=unsupported\n      fi\n      ;;\n\n    aix[4-9]*)\n      if test ia64 = \"$host_cpu\"; then\n\t# On IA64, the linker does run time linking by default, so we don't\n\t# have to do anything special.\n\taix_use_runtimelinking=no\n\texp_sym_flag='-Bexport'\n\tno_entry_flag=\n      else\n\t# If we're using GNU nm, then we don't want the \"-C\" option.\n\t# -C means demangle to GNU nm, but means don't demangle to AIX nm.\n\t# Without the \"-l\" option, or with the \"-B\" option, AIX nm treats\n\t# weak defined symbols like other global defined symbols, whereas\n\t# GNU nm marks them as \"W\".\n\t# While the 'weak' keyword is ignored in the Export File, we need\n\t# it in the Import File for the 'aix-soname' feature, so we have\n\t# to replace the \"-B\" option with \"-P\" for AIX nm.\n\tif $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then\n\t  export_symbols_cmds='$NM -Bpg $libobjs $convenience | awk '\\''{ if (((\\$ 2 == \"T\") || (\\$ 2 == \"D\") || (\\$ 2 == \"B\") || (\\$ 2 == \"W\")) && (substr(\\$ 3,1,1) != \".\")) { if (\\$ 2 == \"W\") { print \\$ 3 \" weak\" } else { print \\$ 3 } } }'\\'' | sort -u > $export_symbols'\n\telse\n\t  export_symbols_cmds='`func_echo_all $NM | $SED -e '\\''s/B\\([^B]*\\)$/P\\1/'\\''` -PCpgl $libobjs $convenience | awk '\\''{ if (((\\$ 2 == \"T\") || (\\$ 2 == \"D\") || (\\$ 2 == \"B\") || (\\$ 2 == \"L\") || (\\$ 2 == \"W\") || (\\$ 2 == \"V\") || (\\$ 2 == \"Z\")) && (substr(\\$ 1,1,1) != \".\")) { if ((\\$ 2 == \"W\") || (\\$ 2 == \"V\") || (\\$ 2 == \"Z\")) { print \\$ 1 \" weak\" } else { print \\$ 1 } } }'\\'' | sort -u > $export_symbols'\n\tfi\n\taix_use_runtimelinking=no\n\n\t# Test if we are trying to use run time linking or normal\n\t# AIX style linking. If -brtl is somewhere in LDFLAGS, we\n\t# have runtime linking enabled, and use it for executables.\n\t# For shared libraries, we enable/disable runtime linking\n\t# depending on the kind of the shared library created -\n\t# when \"with_aix_soname,aix_use_runtimelinking\" is:\n\t# \"aix,no\"   lib.a(lib.so.V) shared, rtl:no,  for executables\n\t# \"aix,yes\"  lib.so          shared, rtl:yes, for executables\n\t#            lib.a           static archive\n\t# \"both,no\"  lib.so.V(shr.o) shared, rtl:yes\n\t#            lib.a(lib.so.V) shared, rtl:no,  for executables\n\t# \"both,yes\" lib.so.V(shr.o) shared, rtl:yes, for executables\n\t#            lib.a(lib.so.V) shared, rtl:no\n\t# \"svr4,*\"   lib.so.V(shr.o) shared, rtl:yes, for executables\n\t#            lib.a           static archive\n\tcase $host_os in aix4.[23]|aix4.[23].*|aix[5-9]*)\n\t  for ld_flag in $LDFLAGS; do\n\t  if (test x-brtl = \"x$ld_flag\" || test x-Wl,-brtl = \"x$ld_flag\"); then\n\t    aix_use_runtimelinking=yes\n\t    break\n\t  fi\n\t  done\n\t  if test svr4,no = \"$with_aix_soname,$aix_use_runtimelinking\"; then\n\t    # With aix-soname=svr4, we create the lib.so.V shared archives only,\n\t    # so we don't have lib.a shared libs to link our executables.\n\t    # We have to force runtime linking in this case.\n\t    aix_use_runtimelinking=yes\n\t    LDFLAGS=\"$LDFLAGS -Wl,-brtl\"\n\t  fi\n\t  ;;\n\tesac\n\n\texp_sym_flag='-bexport'\n\tno_entry_flag='-bnoentry'\n      fi\n\n      # When large executables or shared objects are built, AIX ld can\n      # have problems creating the table of contents.  If linking a library\n      # or program results in \"error TOC overflow\" add -mminimal-toc to\n      # CXXFLAGS/CFLAGS for g++/gcc.  In the cases where that is not\n      # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS.\n\n      archive_cmds=''\n      hardcode_direct=yes\n      hardcode_direct_absolute=yes\n      hardcode_libdir_separator=':'\n      link_all_deplibs=yes\n      file_list_spec='$wl-f,'\n      case $with_aix_soname,$aix_use_runtimelinking in\n      aix,*) ;; # traditional, no import file\n      svr4,* | *,yes) # use import file\n\t# The Import File defines what to hardcode.\n\thardcode_direct=no\n\thardcode_direct_absolute=no\n\t;;\n      esac\n\n      if test yes = \"$GCC\"; then\n\tcase $host_os in aix4.[012]|aix4.[012].*)\n\t# We only want to do this on AIX 4.2 and lower, the check\n\t# below for broken collect2 doesn't work under 4.3+\n\t  collect2name=`$CC -print-prog-name=collect2`\n\t  if test -f \"$collect2name\" &&\n\t   strings \"$collect2name\" | $GREP resolve_lib_name >/dev/null\n\t  then\n\t  # We have reworked collect2\n\t  :\n\t  else\n\t  # We have old collect2\n\t  hardcode_direct=unsupported\n\t  # It fails to find uninstalled libraries when the uninstalled\n\t  # path is not listed in the libpath.  Setting hardcode_minus_L\n\t  # to unsupported forces relinking\n\t  hardcode_minus_L=yes\n\t  hardcode_libdir_flag_spec='-L$libdir'\n\t  hardcode_libdir_separator=\n\t  fi\n\t  ;;\n\tesac\n\tshared_flag='-shared'\n\tif test yes = \"$aix_use_runtimelinking\"; then\n\t  shared_flag=\"$shared_flag \"'$wl-G'\n\tfi\n\t# Need to ensure runtime linking is disabled for the traditional\n\t# shared library, or the linker may eventually find shared libraries\n\t# /with/ Import File - we do not want to mix them.\n\tshared_flag_aix='-shared'\n\tshared_flag_svr4='-shared $wl-G'\n      else\n\t# not using gcc\n\tif test ia64 = \"$host_cpu\"; then\n\t# VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release\n\t# chokes on -Wl,-G. The following line is correct:\n\t  shared_flag='-G'\n\telse\n\t  if test yes = \"$aix_use_runtimelinking\"; then\n\t    shared_flag='$wl-G'\n\t  else\n\t    shared_flag='$wl-bM:SRE'\n\t  fi\n\t  shared_flag_aix='$wl-bM:SRE'\n\t  shared_flag_svr4='$wl-G'\n\tfi\n      fi\n\n      export_dynamic_flag_spec='$wl-bexpall'\n      # It seems that -bexpall does not export symbols beginning with\n      # underscore (_), so it is better to generate a list of symbols to export.\n      always_export_symbols=yes\n      if test aix,yes = \"$with_aix_soname,$aix_use_runtimelinking\"; then\n\t# Warning - without using the other runtime loading flags (-brtl),\n\t# -berok will link without error, but may produce a broken library.\n\tallow_undefined_flag='-berok'\n        # Determine the default libpath from the value encoded in an\n        # empty executable.\n        if test set = \"${lt_cv_aix_libpath+set}\"; then\n  aix_libpath=$lt_cv_aix_libpath\nelse\n  if test ${lt_cv_aix_libpath_+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n\n  lt_aix_libpath_sed='\n      /Import File Strings/,/^$/ {\n\t  /^0/ {\n\t      s/^0  *\\([^ ]*\\) *$/\\1/\n\t      p\n\t  }\n      }'\n  lt_cv_aix_libpath_=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  # Check for a 64-bit object if we didn't find anything.\n  if test -z \"$lt_cv_aix_libpath_\"; then\n    lt_cv_aix_libpath_=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  fi\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n  if test -z \"$lt_cv_aix_libpath_\"; then\n    lt_cv_aix_libpath_=/usr/lib:/lib\n  fi\n   ;;\nesac\nfi\n\n  aix_libpath=$lt_cv_aix_libpath_\nfi\n\n        hardcode_libdir_flag_spec='$wl-blibpath:$libdir:'\"$aix_libpath\"\n        archive_expsym_cmds='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n \"$allow_undefined_flag\"; then func_echo_all \"$wl$allow_undefined_flag\"; else :; fi` $wl'$exp_sym_flag:\\$export_symbols' '$shared_flag\n      else\n\tif test ia64 = \"$host_cpu\"; then\n\t  hardcode_libdir_flag_spec='$wl-R $libdir:/usr/lib:/lib'\n\t  allow_undefined_flag=\"-z nodefs\"\n\t  archive_expsym_cmds=\"\\$CC $shared_flag\"' -o $output_objdir/$soname $libobjs $deplibs '\"\\$wl$no_entry_flag\"' $compiler_flags $wl$allow_undefined_flag '\"\\$wl$exp_sym_flag:\\$export_symbols\"\n\telse\n\t # Determine the default libpath from the value encoded in an\n\t # empty executable.\n\t if test set = \"${lt_cv_aix_libpath+set}\"; then\n  aix_libpath=$lt_cv_aix_libpath\nelse\n  if test ${lt_cv_aix_libpath_+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n\n  lt_aix_libpath_sed='\n      /Import File Strings/,/^$/ {\n\t  /^0/ {\n\t      s/^0  *\\([^ ]*\\) *$/\\1/\n\t      p\n\t  }\n      }'\n  lt_cv_aix_libpath_=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  # Check for a 64-bit object if we didn't find anything.\n  if test -z \"$lt_cv_aix_libpath_\"; then\n    lt_cv_aix_libpath_=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  fi\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n  if test -z \"$lt_cv_aix_libpath_\"; then\n    lt_cv_aix_libpath_=/usr/lib:/lib\n  fi\n   ;;\nesac\nfi\n\n  aix_libpath=$lt_cv_aix_libpath_\nfi\n\n\t hardcode_libdir_flag_spec='$wl-blibpath:$libdir:'\"$aix_libpath\"\n\t  # Warning - without using the other run time loading flags,\n\t  # -berok will link without error, but may produce a broken library.\n\t  no_undefined_flag=' $wl-bernotok'\n\t  allow_undefined_flag=' $wl-berok'\n\t  if test yes = \"$with_gnu_ld\"; then\n\t    # We only use this code for GNU lds that support --whole-archive.\n\t    whole_archive_flag_spec='$wl--whole-archive$convenience $wl--no-whole-archive'\n\t  else\n\t    # Exported symbols can be pulled into shared objects from archives\n\t    whole_archive_flag_spec='$convenience'\n\t  fi\n\t  archive_cmds_need_lc=yes\n\t  archive_expsym_cmds='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d'\n\t  # -brtl affects multiple linker settings, -berok does not and is overridden later\n\t  compiler_flags_filtered='`func_echo_all \"$compiler_flags \" | $SED -e \"s%-brtl\\\\([, ]\\\\)%-berok\\\\1%g\"`'\n\t  if test svr4 != \"$with_aix_soname\"; then\n\t    # This is similar to how AIX traditionally builds its shared libraries.\n\t    archive_expsym_cmds=\"$archive_expsym_cmds\"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname'\n\t  fi\n\t  if test aix != \"$with_aix_soname\"; then\n\t    archive_expsym_cmds=\"$archive_expsym_cmds\"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all \"#! $soname($shared_archive_member_spec.o)\"; if test shr_64 = \"$shared_archive_member_spec\"; then func_echo_all \"# 64\"; else func_echo_all \"# 32\"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp'\n\t  else\n\t    # used by -dlpreopen to get the symbols\n\t    archive_expsym_cmds=\"$archive_expsym_cmds\"'~$MV  $output_objdir/$realname.d/$soname $output_objdir'\n\t  fi\n\t  archive_expsym_cmds=\"$archive_expsym_cmds\"'~$RM -r $output_objdir/$realname.d'\n\tfi\n      fi\n      ;;\n\n    amigaos*)\n      case $host_cpu in\n      powerpc)\n            # see comment about AmigaOS4 .so support\n            archive_cmds='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n            archive_expsym_cmds=''\n        ;;\n      m68k)\n            archive_cmds='$RM $output_objdir/a2ixlibrary.data~$ECHO \"#define NAME $libname\" > $output_objdir/a2ixlibrary.data~$ECHO \"#define LIBRARY_ID 1\" >> $output_objdir/a2ixlibrary.data~$ECHO \"#define VERSION $major\" >> $output_objdir/a2ixlibrary.data~$ECHO \"#define REVISION $revision\" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)'\n            hardcode_libdir_flag_spec='-L$libdir'\n            hardcode_minus_L=yes\n        ;;\n      esac\n      ;;\n\n    bsdi[45]*)\n      export_dynamic_flag_spec=-rdynamic\n      ;;\n\n    cygwin* | mingw* | pw32* | cegcc*)\n      # When not using gcc, we currently assume that we are using\n      # Microsoft Visual C++ or Intel C++ Compiler.\n      # hardcode_libdir_flag_spec is actually meaningless, as there is\n      # no search path for DLLs.\n      case $cc_basename in\n      cl* | icl*)\n\t# Native MSVC or ICC\n\thardcode_libdir_flag_spec=' '\n\tallow_undefined_flag=unsupported\n\talways_export_symbols=yes\n\tfile_list_spec='@'\n\t# Tell ltmain to make .lib files, not .a files.\n\tlibext=lib\n\t# Tell ltmain to make .dll files, not .so files.\n\tshrext_cmds=.dll\n\t# FIXME: Setting linknames here is a bad hack.\n\tarchive_cmds='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:\"$tool_output_objdir$libname.dll.lib\"~linknames='\n\tarchive_expsym_cmds='if   test DEF = \"`$SED -n     -e '\\''s/^[\t ]*//'\\''     -e '\\''/^\\(;.*\\)*$/d'\\''     -e '\\''s/^\\(EXPORTS\\|LIBRARY\\)\\([\t ].*\\)*$/DEF/p'\\''     -e q     $export_symbols`\" ; then\n            cp \"$export_symbols\" \"$output_objdir/$soname.def\";\n            echo \"$tool_output_objdir$soname.def\" > \"$output_objdir/$soname.exp\";\n          else\n            $SED -e '\\''s/^/-link -EXPORT:/'\\'' < $export_symbols > $output_objdir/$soname.exp;\n          fi~\n          $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs \"@$tool_output_objdir$soname.exp\" -Wl,-DLL,-IMPLIB:\"$tool_output_objdir$libname.dll.lib\"~\n          linknames='\n\t# The linker will not automatically build a static lib if we build a DLL.\n\t# _LT_TAGVAR(old_archive_from_new_cmds, )='true'\n\tenable_shared_with_static_runtimes=yes\n\texclude_expsyms='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*'\n\texport_symbols_cmds='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\\''/^[BCDGRS][ ]/s/.*[ ]\\([^ ]*\\)/\\1,DATA/'\\'' | $SED -e '\\''/^[AITW][ ]/s/.*[ ]//'\\'' | sort | uniq > $export_symbols'\n\t# Don't use ranlib\n\told_postinstall_cmds='chmod 644 $oldlib'\n\tpostlink_cmds='lt_outputfile=\"@OUTPUT@\"~\n          lt_tool_outputfile=\"@TOOL_OUTPUT@\"~\n          case $lt_outputfile in\n            *.exe|*.EXE) ;;\n            *)\n              lt_outputfile=$lt_outputfile.exe\n              lt_tool_outputfile=$lt_tool_outputfile.exe\n              ;;\n          esac~\n          if test : != \"$MANIFEST_TOOL\" && test -f \"$lt_outputfile.manifest\"; then\n            $MANIFEST_TOOL -manifest \"$lt_tool_outputfile.manifest\" -outputresource:\"$lt_tool_outputfile\" || exit 1;\n            $RM \"$lt_outputfile.manifest\";\n          fi'\n\t;;\n      *)\n\t# Assume MSVC and ICC wrapper\n\thardcode_libdir_flag_spec=' '\n\tallow_undefined_flag=unsupported\n\t# Tell ltmain to make .lib files, not .a files.\n\tlibext=lib\n\t# Tell ltmain to make .dll files, not .so files.\n\tshrext_cmds=.dll\n\t# FIXME: Setting linknames here is a bad hack.\n\tarchive_cmds='$CC -o $lib $libobjs $compiler_flags `func_echo_all \"$deplibs\" | $SED '\\''s/ -lc$//'\\''` -link -dll~linknames='\n\t# The linker will automatically build a .lib file if we build a DLL.\n\told_archive_from_new_cmds='true'\n\t# FIXME: Should let the user specify the lib program.\n\told_archive_cmds='lib -OUT:$oldlib$oldobjs$old_deplibs'\n\tenable_shared_with_static_runtimes=yes\n\t;;\n      esac\n      ;;\n\n    darwin* | rhapsody*)\n\n\n  archive_cmds_need_lc=no\n  hardcode_direct=no\n  hardcode_automatic=yes\n  hardcode_shlibpath_var=unsupported\n  if test yes = \"$lt_cv_ld_force_load\"; then\n    whole_archive_flag_spec='`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience $wl-force_load,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"`'\n\n  else\n    whole_archive_flag_spec=''\n  fi\n  link_all_deplibs=yes\n  allow_undefined_flag=$_lt_dar_allow_undefined\n  case $cc_basename in\n     ifort*|nagfor*) _lt_dar_can_shared=yes ;;\n     *) _lt_dar_can_shared=$GCC ;;\n  esac\n  if test yes = \"$_lt_dar_can_shared\"; then\n    output_verbose_link_cmd=func_echo_all\n    archive_cmds=\"\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$libobjs \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring $_lt_dar_single_mod$_lt_dsymutil\"\n    module_cmds=\"\\$CC \\$allow_undefined_flag -o \\$lib -bundle \\$libobjs \\$deplibs \\$compiler_flags$_lt_dsymutil\"\n    archive_expsym_cmds=\"$SED 's|^|_|' < \\$export_symbols > \\$output_objdir/\\$libname-symbols.expsym~\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$libobjs \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring $_lt_dar_single_mod$_lt_dar_export_syms$_lt_dsymutil\"\n    module_expsym_cmds=\"$SED -e 's|^|_|' < \\$export_symbols > \\$output_objdir/\\$libname-symbols.expsym~\\$CC \\$allow_undefined_flag -o \\$lib -bundle \\$libobjs \\$deplibs \\$compiler_flags$_lt_dar_export_syms$_lt_dsymutil\"\n\n  else\n  ld_shlibs=no\n  fi\n\n      ;;\n\n    dgux*)\n      archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n      hardcode_libdir_flag_spec='-L$libdir'\n      hardcode_shlibpath_var=no\n      ;;\n\n    # FreeBSD 2.2.[012] allows us to include c++rt0.o to get C++ constructor\n    # support.  Future versions do this automatically, but an explicit c++rt0.o\n    # does not break anything, and helps significantly (at the cost of a little\n    # extra space).\n    freebsd2.2*)\n      archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags /usr/lib/c++rt0.o'\n      hardcode_libdir_flag_spec='-R$libdir'\n      hardcode_direct=yes\n      hardcode_shlibpath_var=no\n      ;;\n\n    # Unfortunately, older versions of FreeBSD 2 do not have this feature.\n    freebsd2.*)\n      archive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags'\n      hardcode_direct=yes\n      hardcode_minus_L=yes\n      hardcode_shlibpath_var=no\n      ;;\n\n    # FreeBSD 3 and greater uses gcc -shared to do shared libraries.\n    freebsd* | dragonfly* | midnightbsd*)\n      archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags'\n      hardcode_libdir_flag_spec='-R$libdir'\n      hardcode_direct=yes\n      hardcode_shlibpath_var=no\n      ;;\n\n    hpux9*)\n      if test yes = \"$GCC\"; then\n\tarchive_cmds='$RM $output_objdir/$soname~$CC -shared $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test \"x$output_objdir/$soname\" = \"x$lib\" || mv $output_objdir/$soname $lib'\n      else\n\tarchive_cmds='$RM $output_objdir/$soname~$LD -b +b $install_libdir -o $output_objdir/$soname $libobjs $deplibs $linker_flags~test \"x$output_objdir/$soname\" = \"x$lib\" || mv $output_objdir/$soname $lib'\n      fi\n      hardcode_libdir_flag_spec='$wl+b $wl$libdir'\n      hardcode_libdir_separator=:\n      hardcode_direct=yes\n\n      # hardcode_minus_L: Not really in the search PATH,\n      # but as the default location of the library.\n      hardcode_minus_L=yes\n      export_dynamic_flag_spec='$wl-E'\n      ;;\n\n    hpux10*)\n      if test yes,no = \"$GCC,$with_gnu_ld\"; then\n\tarchive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'\n      else\n\tarchive_cmds='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags'\n      fi\n      if test no = \"$with_gnu_ld\"; then\n\thardcode_libdir_flag_spec='$wl+b $wl$libdir'\n\thardcode_libdir_separator=:\n\thardcode_direct=yes\n\thardcode_direct_absolute=yes\n\texport_dynamic_flag_spec='$wl-E'\n\t# hardcode_minus_L: Not really in the search PATH,\n\t# but as the default location of the library.\n\thardcode_minus_L=yes\n      fi\n      ;;\n\n    hpux11*)\n      if test yes,no = \"$GCC,$with_gnu_ld\"; then\n\tcase $host_cpu in\n\thppa*64*)\n\t  archive_cmds='$CC -shared $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\tia64*)\n\t  archive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\t*)\n\t  archive_cmds='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\tesac\n      else\n\tcase $host_cpu in\n\thppa*64*)\n\t  archive_cmds='$CC -b $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\tia64*)\n\t  archive_cmds='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\t*)\n\n\t  # Older versions of the 11.00 compiler do not understand -b yet\n\t  # (HP92453-01 A.11.01.20 doesn't, HP92453-01 B.11.X.35175-35176.GP does)\n\t  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $CC understands -b\" >&5\nprintf %s \"checking if $CC understands -b... \" >&6; }\nif test ${lt_cv_prog_compiler__b+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler__b=no\n   save_LDFLAGS=$LDFLAGS\n   LDFLAGS=\"$LDFLAGS -b\"\n   echo \"$lt_simple_link_test_code\" > conftest.$ac_ext\n   if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then\n     # The linker can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     if test -s conftest.err; then\n       # Append any errors to the config.log.\n       cat conftest.err 1>&5\n       $ECHO \"$_lt_linker_boilerplate\" | $SED '/^$/d' > conftest.exp\n       $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2\n       if diff conftest.exp conftest.er2 >/dev/null; then\n         lt_cv_prog_compiler__b=yes\n       fi\n     else\n       lt_cv_prog_compiler__b=yes\n     fi\n   fi\n   $RM -r conftest*\n   LDFLAGS=$save_LDFLAGS\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler__b\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler__b\" >&6; }\n\nif test yes = \"$lt_cv_prog_compiler__b\"; then\n    archive_cmds='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'\nelse\n    archive_cmds='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags'\nfi\n\n\t  ;;\n\tesac\n      fi\n      if test no = \"$with_gnu_ld\"; then\n\thardcode_libdir_flag_spec='$wl+b $wl$libdir'\n\thardcode_libdir_separator=:\n\n\tcase $host_cpu in\n\thppa*64*|ia64*)\n\t  hardcode_direct=no\n\t  hardcode_shlibpath_var=no\n\t  ;;\n\t*)\n\t  hardcode_direct=yes\n\t  hardcode_direct_absolute=yes\n\t  export_dynamic_flag_spec='$wl-E'\n\n\t  # hardcode_minus_L: Not really in the search PATH,\n\t  # but as the default location of the library.\n\t  hardcode_minus_L=yes\n\t  ;;\n\tesac\n      fi\n      ;;\n\n    irix5* | irix6* | nonstopux*)\n      if test yes = \"$GCC\"; then\n\tarchive_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t# Try to use the -exported_symbol ld option, if it does not\n\t# work, assume that -exports_file does not work either and\n\t# implicitly export all symbols.\n\t# This should be the same for all languages, so no per-tag cache variable.\n\t{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether the $host_os linker accepts -exported_symbol\" >&5\nprintf %s \"checking whether the $host_os linker accepts -exported_symbol... \" >&6; }\nif test ${lt_cv_irix_exported_symbol+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) save_LDFLAGS=$LDFLAGS\n\t   LDFLAGS=\"$LDFLAGS -shared $wl-exported_symbol ${wl}foo $wl-update_registry $wl/dev/null\"\n\t   cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\nint foo (void) { return 0; }\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  lt_cv_irix_exported_symbol=yes\nelse case e in #(\n  e) lt_cv_irix_exported_symbol=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n           LDFLAGS=$save_LDFLAGS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_irix_exported_symbol\" >&5\nprintf \"%s\\n\" \"$lt_cv_irix_exported_symbol\" >&6; }\n\tif test yes = \"$lt_cv_irix_exported_symbol\"; then\n          archive_expsym_cmds='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations $wl-exports_file $wl$export_symbols -o $lib'\n\tfi\n      else\n\tarchive_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\tarchive_expsym_cmds='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -exports_file $export_symbols -o $lib'\n      fi\n      archive_cmds_need_lc='no'\n      hardcode_libdir_flag_spec='$wl-rpath $wl$libdir'\n      hardcode_libdir_separator=:\n      inherit_rpath=yes\n      link_all_deplibs=yes\n      ;;\n\n    linux*)\n      case $cc_basename in\n      tcc*)\n\t# Fabrice Bellard et al's Tiny C Compiler\n\tld_shlibs=yes\n\tarchive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags'\n\t;;\n      esac\n      ;;\n\n    netbsd*)\n      if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n\tarchive_cmds='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags'  # a.out\n      else\n\tarchive_cmds='$LD -shared -o $lib $libobjs $deplibs $linker_flags'      # ELF\n      fi\n      hardcode_libdir_flag_spec='-R$libdir'\n      hardcode_direct=yes\n      hardcode_shlibpath_var=no\n      ;;\n\n    newsos6)\n      archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n      hardcode_direct=yes\n      hardcode_libdir_flag_spec='$wl-rpath $wl$libdir'\n      hardcode_libdir_separator=:\n      hardcode_shlibpath_var=no\n      ;;\n\n    *nto* | *qnx*)\n      ;;\n\n    openbsd* | bitrig*)\n      if test -f /usr/libexec/ld.so; then\n\thardcode_direct=yes\n\thardcode_shlibpath_var=no\n\thardcode_direct_absolute=yes\n\tif test -z \"`echo __ELF__ | $CC -E - | $GREP __ELF__`\"; then\n\t  archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags'\n\t  archive_expsym_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags $wl-retain-symbols-file,$export_symbols'\n\t  hardcode_libdir_flag_spec='$wl-rpath,$libdir'\n\t  export_dynamic_flag_spec='$wl-E'\n\telse\n\t  archive_cmds='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags'\n\t  hardcode_libdir_flag_spec='$wl-rpath,$libdir'\n\tfi\n      else\n\tld_shlibs=no\n      fi\n      ;;\n\n    os2*)\n      hardcode_libdir_flag_spec='-L$libdir'\n      hardcode_minus_L=yes\n      allow_undefined_flag=unsupported\n      shrext_cmds=.dll\n      archive_cmds='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t$ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t$ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t$ECHO EXPORTS >> $output_objdir/$libname.def~\n\temxexp $libobjs | $SED /\"_DLL_InitTerm\"/d >> $output_objdir/$libname.def~\n\t$CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\temximp -o $lib $output_objdir/$libname.def'\n      archive_expsym_cmds='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t$ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t$ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t$ECHO EXPORTS >> $output_objdir/$libname.def~\n\tprefix_cmds=\"$SED\"~\n\tif test EXPORTS = \"`$SED 1q $export_symbols`\"; then\n\t  prefix_cmds=\"$prefix_cmds -e 1d\";\n\tfi~\n\tprefix_cmds=\"$prefix_cmds -e \\\"s/^\\(.*\\)$/_\\1/g\\\"\"~\n\tcat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~\n\t$CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\temximp -o $lib $output_objdir/$libname.def'\n      old_archive_From_new_cmds='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def'\n      enable_shared_with_static_runtimes=yes\n      file_list_spec='@'\n      ;;\n\n    osf3*)\n      if test yes = \"$GCC\"; then\n\tallow_undefined_flag=' $wl-expect_unresolved $wl\\*'\n\tarchive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n      else\n\tallow_undefined_flag=' -expect_unresolved \\*'\n\tarchive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n      fi\n      archive_cmds_need_lc='no'\n      hardcode_libdir_flag_spec='$wl-rpath $wl$libdir'\n      hardcode_libdir_separator=:\n      ;;\n\n    osf4* | osf5*)\t# as osf3* with the addition of -msym flag\n      if test yes = \"$GCC\"; then\n\tallow_undefined_flag=' $wl-expect_unresolved $wl\\*'\n\tarchive_cmds='$CC -shared$allow_undefined_flag $pic_flag $libobjs $deplibs $compiler_flags $wl-msym $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\thardcode_libdir_flag_spec='$wl-rpath $wl$libdir'\n      else\n\tallow_undefined_flag=' -expect_unresolved \\*'\n\tarchive_cmds='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\tarchive_expsym_cmds='for i in `cat $export_symbols`; do printf \"%s %s\\\\n\" -exported_symbol \"\\$i\" >> $lib.exp; done; printf \"%s\\\\n\" \"-hidden\">> $lib.exp~\n          $CC -shared$allow_undefined_flag $wl-input $wl$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n \"$verstring\" && $ECHO \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib~$RM $lib.exp'\n\n\t# Both c and cxx compiler support -rpath directly\n\thardcode_libdir_flag_spec='-rpath $libdir'\n      fi\n      archive_cmds_need_lc='no'\n      hardcode_libdir_separator=:\n      ;;\n\n    solaris*)\n      no_undefined_flag=' -z defs'\n      if test yes = \"$GCC\"; then\n\twlarc='$wl'\n\tarchive_cmds='$CC -shared $pic_flag $wl-z ${wl}text $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags'\n\tarchive_expsym_cmds='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n          $CC -shared $pic_flag $wl-z ${wl}text $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp'\n      else\n\tcase `$CC -V 2>&1` in\n\t*\"Compilers 5.0\"*)\n\t  wlarc=''\n\t  archive_cmds='$LD -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $linker_flags'\n\t  archive_expsym_cmds='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n            $LD -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $linker_flags~$RM $lib.exp'\n\t  ;;\n\t*)\n\t  wlarc='$wl'\n\t  archive_cmds='$CC -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  archive_expsym_cmds='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n            $CC -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp'\n\t  ;;\n\tesac\n      fi\n      hardcode_libdir_flag_spec='-R$libdir'\n      hardcode_shlibpath_var=no\n      case $host_os in\n      solaris2.[0-5] | solaris2.[0-5].*) ;;\n      *)\n\t# The compiler driver will combine and reorder linker options,\n\t# but understands '-z linker_flag'.  GCC discards it without '$wl',\n\t# but is careful enough not to reorder.\n\t# Supported since Solaris 2.6 (maybe 2.5.1?)\n\tif test yes = \"$GCC\"; then\n\t  whole_archive_flag_spec='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract'\n\telse\n\t  whole_archive_flag_spec='-z allextract$convenience -z defaultextract'\n\tfi\n\t;;\n      esac\n      link_all_deplibs=yes\n      ;;\n\n    sunos4*)\n      if test sequent = \"$host_vendor\"; then\n\t# Use $CC to link under sequent, because it throws in some extra .o\n\t# files that make .init and .fini sections work.\n\tarchive_cmds='$CC -G $wl-h $soname -o $lib $libobjs $deplibs $compiler_flags'\n      else\n\tarchive_cmds='$LD -assert pure-text -Bstatic -o $lib $libobjs $deplibs $linker_flags'\n      fi\n      hardcode_libdir_flag_spec='-L$libdir'\n      hardcode_direct=yes\n      hardcode_minus_L=yes\n      hardcode_shlibpath_var=no\n      ;;\n\n    sysv4)\n      case $host_vendor in\n\tsni)\n\t  archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n\t  hardcode_direct=yes # is this really true???\n\t;;\n\tsiemens)\n\t  ## LD is ld it makes a PLAMLIB\n\t  ## CC just makes a GrossModule.\n\t  archive_cmds='$LD -G -o $lib $libobjs $deplibs $linker_flags'\n\t  reload_cmds='$CC -r -o $output$reload_objs'\n\t  hardcode_direct=no\n        ;;\n\tmotorola)\n\t  archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n\t  hardcode_direct=no #Motorola manual says yes, but my tests say they lie\n\t;;\n      esac\n      runpath_var='LD_RUN_PATH'\n      hardcode_shlibpath_var=no\n      ;;\n\n    sysv4.3*)\n      archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n      hardcode_shlibpath_var=no\n      export_dynamic_flag_spec='-Bexport'\n      ;;\n\n    sysv4*MP*)\n      if test -d /usr/nec; then\n\tarchive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n\thardcode_shlibpath_var=no\n\trunpath_var=LD_RUN_PATH\n\thardcode_runpath_var=yes\n\tld_shlibs=yes\n      fi\n      ;;\n\n    sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[01].[10]* | unixware7* | sco3.2v5.0.[024]*)\n      no_undefined_flag='$wl-z,text'\n      archive_cmds_need_lc=no\n      hardcode_shlibpath_var=no\n      runpath_var='LD_RUN_PATH'\n\n      if test yes = \"$GCC\"; then\n\tarchive_cmds='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\tarchive_expsym_cmds='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n      else\n\tarchive_cmds='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\tarchive_expsym_cmds='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n      fi\n      ;;\n\n    sysv5* | sco3.2v5* | sco5v6*)\n      # Note: We CANNOT use -z defs as we might desire, because we do not\n      # link with -lc, and that would cause any symbols used from libc to\n      # always be unresolved, which means just about no library would\n      # ever link correctly.  If we're not using GNU ld we use -z text\n      # though, which does catch some bad symbols but isn't as heavy-handed\n      # as -z defs.\n      no_undefined_flag='$wl-z,text'\n      allow_undefined_flag='$wl-z,nodefs'\n      archive_cmds_need_lc=no\n      hardcode_shlibpath_var=no\n      hardcode_libdir_flag_spec='$wl-R,$libdir'\n      hardcode_libdir_separator=':'\n      link_all_deplibs=yes\n      export_dynamic_flag_spec='$wl-Bexport'\n      runpath_var='LD_RUN_PATH'\n\n      if test yes = \"$GCC\"; then\n\tarchive_cmds='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\tarchive_expsym_cmds='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n      else\n\tarchive_cmds='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\tarchive_expsym_cmds='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n      fi\n      ;;\n\n    uts4*)\n      archive_cmds='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n      hardcode_libdir_flag_spec='-L$libdir'\n      hardcode_shlibpath_var=no\n      ;;\n\n    *)\n      ld_shlibs=no\n      ;;\n    esac\n\n    if test sni = \"$host_vendor\"; then\n      case $host in\n      sysv4 | sysv4.2uw2* | sysv4.3* | sysv5*)\n\texport_dynamic_flag_spec='$wl-Blargedynsym'\n\t;;\n      esac\n    fi\n  fi\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ld_shlibs\" >&5\nprintf \"%s\\n\" \"$ld_shlibs\" >&6; }\ntest no = \"$ld_shlibs\" && can_build_shared=no\n\nwith_gnu_ld=$with_gnu_ld\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n#\n# Do we need to explicitly link libc?\n#\ncase \"x$archive_cmds_need_lc\" in\nx|xyes)\n  # Assume -lc should be added\n  archive_cmds_need_lc=yes\n\n  if test yes,yes = \"$GCC,$enable_shared\"; then\n    case $archive_cmds in\n    *'~'*)\n      # FIXME: we may have to deal with multi-command sequences.\n      ;;\n    '$CC '*)\n      # Test whether the compiler implicitly links with -lc since on some\n      # systems, -lgcc has to come before -lc. If gcc already passes -lc\n      # to ld, don't add -lc before -lgcc.\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether -lc should be explicitly linked in\" >&5\nprintf %s \"checking whether -lc should be explicitly linked in... \" >&6; }\nif test ${lt_cv_archive_cmds_need_lc+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) $RM conftest*\n\techo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n\n\tif { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } 2>conftest.err; then\n\t  soname=conftest\n\t  lib=conftest\n\t  libobjs=conftest.$ac_objext\n\t  deplibs=\n\t  wl=$lt_prog_compiler_wl\n\t  pic_flag=$lt_prog_compiler_pic\n\t  compiler_flags=-v\n\t  linker_flags=-v\n\t  verstring=\n\t  output_objdir=.\n\t  libname=conftest\n\t  lt_save_allow_undefined_flag=$allow_undefined_flag\n\t  allow_undefined_flag=\n\t  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$archive_cmds 2\\>\\&1 \\| $GREP \\\" -lc \\\" \\>/dev/null 2\\>\\&1\\\"\"; } >&5\n  (eval $archive_cmds 2\\>\\&1 \\| $GREP \\\" -lc \\\" \\>/dev/null 2\\>\\&1) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\n\t  then\n\t    lt_cv_archive_cmds_need_lc=no\n\t  else\n\t    lt_cv_archive_cmds_need_lc=yes\n\t  fi\n\t  allow_undefined_flag=$lt_save_allow_undefined_flag\n\telse\n\t  cat conftest.err 1>&5\n\tfi\n\t$RM conftest*\n\t ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_archive_cmds_need_lc\" >&5\nprintf \"%s\\n\" \"$lt_cv_archive_cmds_need_lc\" >&6; }\n      archive_cmds_need_lc=$lt_cv_archive_cmds_need_lc\n      ;;\n    esac\n  fi\n  ;;\nesac\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking dynamic linker characteristics\" >&5\nprintf %s \"checking dynamic linker characteristics... \" >&6; }\n\nif test yes = \"$GCC\"; then\n  case $host_os in\n    darwin*) lt_awk_arg='/^libraries:/,/LR/' ;;\n    *) lt_awk_arg='/^libraries:/' ;;\n  esac\n  case $host_os in\n    mingw* | cegcc*) lt_sed_strip_eq='s|=\\([A-Za-z]:\\)|\\1|g' ;;\n    *) lt_sed_strip_eq='s|=/|/|g' ;;\n  esac\n  lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e \"s/^libraries://\" -e $lt_sed_strip_eq`\n  case $lt_search_path_spec in\n  *\\;*)\n    # if the path contains \";\" then we assume it to be the separator\n    # otherwise default to the standard path separator (i.e. \":\") - it is\n    # assumed that no part of a normal pathname contains \";\" but that should\n    # okay in the real world where \";\" in dirpaths is itself problematic.\n    lt_search_path_spec=`$ECHO \"$lt_search_path_spec\" | $SED 's/;/ /g'`\n    ;;\n  *)\n    lt_search_path_spec=`$ECHO \"$lt_search_path_spec\" | $SED \"s/$PATH_SEPARATOR/ /g\"`\n    ;;\n  esac\n  # Ok, now we have the path, separated by spaces, we can step through it\n  # and add multilib dir if necessary...\n  lt_tmp_lt_search_path_spec=\n  lt_multi_os_dir=/`$CC $CPPFLAGS $CFLAGS $LDFLAGS -print-multi-os-directory 2>/dev/null`\n  # ...but if some path component already ends with the multilib dir we assume\n  # that all is fine and trust -print-search-dirs as is (GCC 4.2? or newer).\n  case \"$lt_multi_os_dir; $lt_search_path_spec \" in\n  \"/; \"* | \"/.; \"* | \"/./; \"* | *\"$lt_multi_os_dir \"* | *\"$lt_multi_os_dir/ \"*)\n    lt_multi_os_dir=\n    ;;\n  esac\n  for lt_sys_path in $lt_search_path_spec; do\n    if test -d \"$lt_sys_path$lt_multi_os_dir\"; then\n      lt_tmp_lt_search_path_spec=\"$lt_tmp_lt_search_path_spec $lt_sys_path$lt_multi_os_dir\"\n    elif test -n \"$lt_multi_os_dir\"; then\n      test -d \"$lt_sys_path\" && \\\n\tlt_tmp_lt_search_path_spec=\"$lt_tmp_lt_search_path_spec $lt_sys_path\"\n    fi\n  done\n  lt_search_path_spec=`$ECHO \"$lt_tmp_lt_search_path_spec\" | awk '\nBEGIN {RS = \" \"; FS = \"/|\\n\";} {\n  lt_foo = \"\";\n  lt_count = 0;\n  for (lt_i = NF; lt_i > 0; lt_i--) {\n    if ($lt_i != \"\" && $lt_i != \".\") {\n      if ($lt_i == \"..\") {\n        lt_count++;\n      } else {\n        if (lt_count == 0) {\n          lt_foo = \"/\" $lt_i lt_foo;\n        } else {\n          lt_count--;\n        }\n      }\n    }\n  }\n  if (lt_foo != \"\") { lt_freq[lt_foo]++; }\n  if (lt_freq[lt_foo] == 1) { print lt_foo; }\n}'`\n  # AWK program above erroneously prepends '/' to C:/dos/paths\n  # for these hosts.\n  case $host_os in\n    mingw* | cegcc*) lt_search_path_spec=`$ECHO \"$lt_search_path_spec\" |\\\n      $SED 's|/\\([A-Za-z]:\\)|\\1|g'` ;;\n  esac\n  sys_lib_search_path_spec=`$ECHO \"$lt_search_path_spec\" | $lt_NL2SP`\nelse\n  sys_lib_search_path_spec=\"/lib /usr/lib /usr/local/lib\"\nfi\nlibrary_names_spec=\nlibname_spec='lib$name'\nsoname_spec=\nshrext_cmds=.so\npostinstall_cmds=\npostuninstall_cmds=\nfinish_cmds=\nfinish_eval=\nshlibpath_var=\nshlibpath_overrides_runpath=unknown\nversion_type=none\ndynamic_linker=\"$host_os ld.so\"\nsys_lib_dlsearch_path_spec=\"/lib /usr/lib\"\nneed_lib_prefix=unknown\nhardcode_into_libs=no\n\n# when you set need_version to no, make sure it does not cause -set_version\n# flags to be left without arguments\nneed_version=unknown\n\n\n\ncase $host_os in\naix3*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname.a'\n  shlibpath_var=LIBPATH\n\n  # AIX 3 has no versioning support, so we append a major version to the name.\n  soname_spec='$libname$release$shared_ext$major'\n  ;;\n\naix[4-9]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  hardcode_into_libs=yes\n  if test ia64 = \"$host_cpu\"; then\n    # AIX 5 supports IA64\n    library_names_spec='$libname$release$shared_ext$major $libname$release$shared_ext$versuffix $libname$shared_ext'\n    shlibpath_var=LD_LIBRARY_PATH\n  else\n    # With GCC up to 2.95.x, collect2 would create an import file\n    # for dependence libraries.  The import file would start with\n    # the line '#! .'.  This would cause the generated library to\n    # depend on '.', always an invalid library.  This was fixed in\n    # development snapshots of GCC prior to 3.0.\n    case $host_os in\n      aix4 | aix4.[01] | aix4.[01].*)\n      if { echo '#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 97)'\n\t   echo ' yes '\n\t   echo '#endif'; } | $CC -E - | $GREP yes > /dev/null; then\n\t:\n      else\n\tcan_build_shared=no\n      fi\n      ;;\n    esac\n    # Using Import Files as archive members, it is possible to support\n    # filename-based versioning of shared library archives on AIX. While\n    # this would work for both with and without runtime linking, it will\n    # prevent static linking of such archives. So we do filename-based\n    # shared library versioning with .so extension only, which is used\n    # when both runtime linking and shared linking is enabled.\n    # Unfortunately, runtime linking may impact performance, so we do\n    # not want this to be the default eventually. Also, we use the\n    # versioned .so libs for executables only if there is the -brtl\n    # linker flag in LDFLAGS as well, or --with-aix-soname=svr4 only.\n    # To allow for filename-based versioning support, we need to create\n    # libNAME.so.V as an archive file, containing:\n    # *) an Import File, referring to the versioned filename of the\n    #    archive as well as the shared archive member, telling the\n    #    bitwidth (32 or 64) of that shared object, and providing the\n    #    list of exported symbols of that shared object, eventually\n    #    decorated with the 'weak' keyword\n    # *) the shared object with the F_LOADONLY flag set, to really avoid\n    #    it being seen by the linker.\n    # At run time we better use the real file rather than another symlink,\n    # but for link time we create the symlink libNAME.so -> libNAME.so.V\n\n    case $with_aix_soname,$aix_use_runtimelinking in\n    # AIX (on Power*) has no versioning support, so currently we cannot hardcode correct\n    # soname into executable. Probably we can add versioning support to\n    # collect2, so additional links can be useful in future.\n    aix,yes) # traditional libtool\n      dynamic_linker='AIX unversionable lib.so'\n      # If using run time linking (on AIX 4.2 or later) use lib<name>.so\n      # instead of lib<name>.a to let people know that these are not\n      # typical AIX shared libraries.\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n      ;;\n    aix,no) # traditional AIX only\n      dynamic_linker='AIX lib.a(lib.so.V)'\n      # We preserve .a as extension for shared libraries through AIX4.2\n      # and later when we are not doing run time linking.\n      library_names_spec='$libname$release.a $libname.a'\n      soname_spec='$libname$release$shared_ext$major'\n      ;;\n    svr4,*) # full svr4 only\n      dynamic_linker=\"AIX lib.so.V($shared_archive_member_spec.o)\"\n      library_names_spec='$libname$release$shared_ext$major $libname$shared_ext'\n      # We do not specify a path in Import Files, so LIBPATH fires.\n      shlibpath_overrides_runpath=yes\n      ;;\n    *,yes) # both, prefer svr4\n      dynamic_linker=\"AIX lib.so.V($shared_archive_member_spec.o), lib.a(lib.so.V)\"\n      library_names_spec='$libname$release$shared_ext$major $libname$shared_ext'\n      # unpreferred sharedlib libNAME.a needs extra handling\n      postinstall_cmds='test -n \"$linkname\" || linkname=\"$realname\"~func_stripname \"\" \".so\" \"$linkname\"~$install_shared_prog \"$dir/$func_stripname_result.$libext\" \"$destdir/$func_stripname_result.$libext\"~test -z \"$tstripme\" || test -z \"$striplib\" || $striplib \"$destdir/$func_stripname_result.$libext\"'\n      postuninstall_cmds='for n in $library_names $old_library; do :; done~func_stripname \"\" \".so\" \"$n\"~test \"$func_stripname_result\" = \"$n\" || func_append rmfiles \" $odir/$func_stripname_result.$libext\"'\n      # We do not specify a path in Import Files, so LIBPATH fires.\n      shlibpath_overrides_runpath=yes\n      ;;\n    *,no) # both, prefer aix\n      dynamic_linker=\"AIX lib.a(lib.so.V), lib.so.V($shared_archive_member_spec.o)\"\n      library_names_spec='$libname$release.a $libname.a'\n      soname_spec='$libname$release$shared_ext$major'\n      # unpreferred sharedlib libNAME.so.V and symlink libNAME.so need extra handling\n      postinstall_cmds='test -z \"$dlname\" || $install_shared_prog $dir/$dlname $destdir/$dlname~test -z \"$tstripme\" || test -z \"$striplib\" || $striplib $destdir/$dlname~test -n \"$linkname\" || linkname=$realname~func_stripname \"\" \".a\" \"$linkname\"~(cd \"$destdir\" && $LN_S -f $dlname $func_stripname_result.so)'\n      postuninstall_cmds='test -z \"$dlname\" || func_append rmfiles \" $odir/$dlname\"~for n in $old_library $library_names; do :; done~func_stripname \"\" \".a\" \"$n\"~func_append rmfiles \" $odir/$func_stripname_result.so\"'\n      ;;\n    esac\n    shlibpath_var=LIBPATH\n  fi\n  ;;\n\namigaos*)\n  case $host_cpu in\n  powerpc)\n    # Since July 2007 AmigaOS4 officially supports .so libraries.\n    # When compiling the executable, add -use-dynld -Lsobjs: to the compileline.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    ;;\n  m68k)\n    library_names_spec='$libname.ixlibrary $libname.a'\n    # Create ${libname}_ixlibrary.a entries in /sys/libs.\n    finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all \"$lib\" | $SED '\\''s%^.*/\\([^/]*\\)\\.ixlibrary$%\\1%'\\''`; $RM /sys/libs/${libname}_ixlibrary.a; $show \"cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a\"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done'\n    ;;\n  esac\n  ;;\n\nbeos*)\n  library_names_spec='$libname$shared_ext'\n  dynamic_linker=\"$host_os ld.so\"\n  shlibpath_var=LIBRARY_PATH\n  ;;\n\nbsdi[45]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  sys_lib_search_path_spec=\"/shlib /usr/lib /usr/X11/lib /usr/contrib/lib /lib /usr/local/lib\"\n  sys_lib_dlsearch_path_spec=\"/shlib /usr/lib /usr/local/lib\"\n  # the default ld.so.conf also contains /usr/contrib/lib and\n  # /usr/X11R6/lib (/usr/X11 is a link to /usr/X11R6), but let us allow\n  # libtool to hard-code these into programs\n  ;;\n\ncygwin* | mingw* | pw32* | cegcc*)\n  version_type=windows\n  shrext_cmds=.dll\n  need_version=no\n  need_lib_prefix=no\n\n  case $GCC,$cc_basename in\n  yes,*)\n    # gcc\n    library_names_spec='$libname.dll.a'\n    # DLL is installed to $(libdir)/../bin by postinstall_cmds\n    postinstall_cmds='base_file=`basename \\$file`~\n      dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; echo \\$dlname'\\''`~\n      dldir=$destdir/`dirname \\$dlpath`~\n      test -d \\$dldir || mkdir -p \\$dldir~\n      $install_prog $dir/$dlname \\$dldir/$dlname~\n      chmod a+x \\$dldir/$dlname~\n      if test -n '\\''$stripme'\\'' && test -n '\\''$striplib'\\''; then\n        eval '\\''$striplib \\$dldir/$dlname'\\'' || exit \\$?;\n      fi'\n    postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; echo \\$dlname'\\''`~\n      dlpath=$dir/\\$dldll~\n       $RM \\$dlpath'\n    shlibpath_overrides_runpath=yes\n\n    case $host_os in\n    cygwin*)\n      # Cygwin DLLs use 'cyg' prefix rather than 'lib'\n      soname_spec='`echo $libname | $SED -e 's/^lib/cyg/'``echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext'\n\n      sys_lib_search_path_spec=\"$sys_lib_search_path_spec /usr/lib/w32api\"\n      ;;\n    mingw* | cegcc*)\n      # MinGW DLLs use traditional 'lib' prefix\n      soname_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext'\n      ;;\n    pw32*)\n      # pw32 DLLs use 'pw' prefix rather than 'lib'\n      library_names_spec='`echo $libname | $SED -e 's/^lib/pw/'``echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext'\n      ;;\n    esac\n    dynamic_linker='Win32 ld.exe'\n    ;;\n\n  *,cl* | *,icl*)\n    # Native MSVC or ICC\n    libname_spec='$name'\n    soname_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext'\n    library_names_spec='$libname.dll.lib'\n\n    case $build_os in\n    mingw*)\n      sys_lib_search_path_spec=\n      lt_save_ifs=$IFS\n      IFS=';'\n      for lt_path in $LIB\n      do\n        IFS=$lt_save_ifs\n        # Let DOS variable expansion print the short 8.3 style file name.\n        lt_path=`cd \"$lt_path\" 2>/dev/null && cmd //C \"for %i in (\".\") do @echo %~si\"`\n        sys_lib_search_path_spec=\"$sys_lib_search_path_spec $lt_path\"\n      done\n      IFS=$lt_save_ifs\n      # Convert to MSYS style.\n      sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e 's|\\\\\\\\|/|g' -e 's| \\\\([a-zA-Z]\\\\):| /\\\\1|g' -e 's|^ ||'`\n      ;;\n    cygwin*)\n      # Convert to unix form, then to dos form, then back to unix form\n      # but this time dos style (no spaces!) so that the unix form looks\n      # like /cygdrive/c/PROGRA~1:/cygdr...\n      sys_lib_search_path_spec=`cygpath --path --unix \"$LIB\"`\n      sys_lib_search_path_spec=`cygpath --path --dos \"$sys_lib_search_path_spec\" 2>/dev/null`\n      sys_lib_search_path_spec=`cygpath --path --unix \"$sys_lib_search_path_spec\" | $SED -e \"s/$PATH_SEPARATOR/ /g\"`\n      ;;\n    *)\n      sys_lib_search_path_spec=$LIB\n      if $ECHO \"$sys_lib_search_path_spec\" | $GREP ';[c-zC-Z]:/' >/dev/null; then\n        # It is most probably a Windows format PATH.\n        sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e 's/;/ /g'`\n      else\n        sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e \"s/$PATH_SEPARATOR/ /g\"`\n      fi\n      # FIXME: find the short name or the path components, as spaces are\n      # common. (e.g. \"Program Files\" -> \"PROGRA~1\")\n      ;;\n    esac\n\n    # DLL is installed to $(libdir)/../bin by postinstall_cmds\n    postinstall_cmds='base_file=`basename \\$file`~\n      dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; echo \\$dlname'\\''`~\n      dldir=$destdir/`dirname \\$dlpath`~\n      test -d \\$dldir || mkdir -p \\$dldir~\n      $install_prog $dir/$dlname \\$dldir/$dlname'\n    postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; echo \\$dlname'\\''`~\n      dlpath=$dir/\\$dldll~\n       $RM \\$dlpath'\n    shlibpath_overrides_runpath=yes\n    dynamic_linker='Win32 link.exe'\n    ;;\n\n  *)\n    # Assume MSVC and ICC wrapper\n    library_names_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext $libname.lib'\n    dynamic_linker='Win32 ld.exe'\n    ;;\n  esac\n  # FIXME: first we should search . and the directory the executable is in\n  shlibpath_var=PATH\n  ;;\n\ndarwin* | rhapsody*)\n  dynamic_linker=\"$host_os dyld\"\n  version_type=darwin\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$major$shared_ext $libname$shared_ext'\n  soname_spec='$libname$release$major$shared_ext'\n  shlibpath_overrides_runpath=yes\n  shlibpath_var=DYLD_LIBRARY_PATH\n  shrext_cmds='`test .$module = .yes && echo .so || echo .dylib`'\n\n  sys_lib_search_path_spec=\"$sys_lib_search_path_spec /usr/local/lib\"\n  sys_lib_dlsearch_path_spec='/usr/local/lib /lib /usr/lib'\n  ;;\n\ndgux*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  ;;\n\nfreebsd* | dragonfly* | midnightbsd*)\n  # DragonFly does not have aout.  When/if they implement a new\n  # versioning mechanism, adjust this.\n  if test -x /usr/bin/objformat; then\n    objformat=`/usr/bin/objformat`\n  else\n    case $host_os in\n    freebsd[23].*) objformat=aout ;;\n    *) objformat=elf ;;\n    esac\n  fi\n  version_type=freebsd-$objformat\n  case $version_type in\n    freebsd-elf*)\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n      soname_spec='$libname$release$shared_ext$major'\n      need_version=no\n      need_lib_prefix=no\n      ;;\n    freebsd-*)\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n      need_version=yes\n      ;;\n  esac\n  shlibpath_var=LD_LIBRARY_PATH\n  case $host_os in\n  freebsd2.*)\n    shlibpath_overrides_runpath=yes\n    ;;\n  freebsd3.[01]* | freebsdelf3.[01]*)\n    shlibpath_overrides_runpath=yes\n    hardcode_into_libs=yes\n    ;;\n  freebsd3.[2-9]* | freebsdelf3.[2-9]* | \\\n  freebsd4.[0-5] | freebsdelf4.[0-5] | freebsd4.1.1 | freebsdelf4.1.1)\n    shlibpath_overrides_runpath=no\n    hardcode_into_libs=yes\n    ;;\n  *) # from 4.6 on, and DragonFly\n    shlibpath_overrides_runpath=yes\n    hardcode_into_libs=yes\n    ;;\n  esac\n  ;;\n\nhaiku*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  dynamic_linker=\"$host_os runtime_loader\"\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib'\n  hardcode_into_libs=yes\n  ;;\n\nhpux9* | hpux10* | hpux11*)\n  # Give a soname corresponding to the major version so that dld.sl refuses to\n  # link against other versions.\n  version_type=sunos\n  need_lib_prefix=no\n  need_version=no\n  case $host_cpu in\n  ia64*)\n    shrext_cmds='.so'\n    hardcode_into_libs=yes\n    dynamic_linker=\"$host_os dld.so\"\n    shlibpath_var=LD_LIBRARY_PATH\n    shlibpath_overrides_runpath=yes # Unless +noenvvar is specified.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    if test 32 = \"$HPUX_IA64_MODE\"; then\n      sys_lib_search_path_spec=\"/usr/lib/hpux32 /usr/local/lib/hpux32 /usr/local/lib\"\n      sys_lib_dlsearch_path_spec=/usr/lib/hpux32\n    else\n      sys_lib_search_path_spec=\"/usr/lib/hpux64 /usr/local/lib/hpux64\"\n      sys_lib_dlsearch_path_spec=/usr/lib/hpux64\n    fi\n    ;;\n  hppa*64*)\n    shrext_cmds='.sl'\n    hardcode_into_libs=yes\n    dynamic_linker=\"$host_os dld.sl\"\n    shlibpath_var=LD_LIBRARY_PATH # How should we handle SHLIB_PATH\n    shlibpath_overrides_runpath=yes # Unless +noenvvar is specified.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    sys_lib_search_path_spec=\"/usr/lib/pa20_64 /usr/ccs/lib/pa20_64\"\n    sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n    ;;\n  *)\n    shrext_cmds='.sl'\n    dynamic_linker=\"$host_os dld.sl\"\n    shlibpath_var=SHLIB_PATH\n    shlibpath_overrides_runpath=no # +s is required to enable SHLIB_PATH\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    ;;\n  esac\n  # HP-UX runs *really* slowly unless shared libraries are mode 555, ...\n  postinstall_cmds='chmod 555 $lib'\n  # or fails outright, so override atomically:\n  install_override_mode=555\n  ;;\n\ninterix[3-9]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  dynamic_linker='Interix 3.x ld.so.1 (PE, like ELF)'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  ;;\n\nirix5* | irix6* | nonstopux*)\n  case $host_os in\n    nonstopux*) version_type=nonstopux ;;\n    *)\n\tif test yes = \"$lt_cv_prog_gnu_ld\"; then\n\t\tversion_type=linux # correct to gnu/linux during the next big refactor\n\telse\n\t\tversion_type=irix\n\tfi ;;\n  esac\n  need_lib_prefix=no\n  need_version=no\n  soname_spec='$libname$release$shared_ext$major'\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$release$shared_ext $libname$shared_ext'\n  case $host_os in\n  irix5* | nonstopux*)\n    libsuff= shlibsuff=\n    ;;\n  *)\n    case $LD in # libtool.m4 will add one of these switches to LD\n    *-32|*\"-32 \"|*-melf32bsmip|*\"-melf32bsmip \")\n      libsuff= shlibsuff= libmagic=32-bit;;\n    *-n32|*\"-n32 \"|*-melf32bmipn32|*\"-melf32bmipn32 \")\n      libsuff=32 shlibsuff=N32 libmagic=N32;;\n    *-64|*\"-64 \"|*-melf64bmip|*\"-melf64bmip \")\n      libsuff=64 shlibsuff=64 libmagic=64-bit;;\n    *) libsuff= shlibsuff= libmagic=never-match;;\n    esac\n    ;;\n  esac\n  shlibpath_var=LD_LIBRARY${shlibsuff}_PATH\n  shlibpath_overrides_runpath=no\n  sys_lib_search_path_spec=\"/usr/lib$libsuff /lib$libsuff /usr/local/lib$libsuff\"\n  sys_lib_dlsearch_path_spec=\"/usr/lib$libsuff /lib$libsuff\"\n  hardcode_into_libs=yes\n  ;;\n\n# No shared lib support for Linux oldld, aout, or coff.\nlinux*oldld* | linux*aout* | linux*coff*)\n  dynamic_linker=no\n  ;;\n\nlinux*android*)\n  version_type=none # Android doesn't support versioned libraries.\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext'\n  soname_spec='$libname$release$shared_ext'\n  finish_cmds=\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n\n  # This implies no fast_install, which is unacceptable.\n  # Some rework will be needed to allow for fast_install\n  # before this can be enabled.\n  hardcode_into_libs=yes\n\n  dynamic_linker='Android linker'\n  # Don't embed -rpath directories since the linker doesn't support them.\n  hardcode_libdir_flag_spec='-L$libdir'\n  ;;\n\n# This must be glibc/ELF.\nlinux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -n $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n\n  # Some binutils ld are patched to set DT_RUNPATH\n  if test ${lt_cv_shlibpath_overrides_runpath+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_shlibpath_overrides_runpath=no\n    save_LDFLAGS=$LDFLAGS\n    save_libdir=$libdir\n    eval \"libdir=/foo; wl=\\\"$lt_prog_compiler_wl\\\"; \\\n\t LDFLAGS=\\\"\\$LDFLAGS $hardcode_libdir_flag_spec\\\"\"\n    cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  if  ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep \"RUNPATH.*$libdir\" >/dev/null\nthen :\n  lt_cv_shlibpath_overrides_runpath=yes\nfi\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n    LDFLAGS=$save_LDFLAGS\n    libdir=$save_libdir\n     ;;\nesac\nfi\n\n  shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath\n\n  # This implies no fast_install, which is unacceptable.\n  # Some rework will be needed to allow for fast_install\n  # before this can be enabled.\n  hardcode_into_libs=yes\n\n  # Ideally, we could use ldconfig to report *all* directores which are\n  # searched for libraries, however this is still not possible.  Aside from not\n  # being certain /sbin/ldconfig is available, command\n  # 'ldconfig -N -X -v | grep ^/' on 64bit Fedora does not report /usr/lib64,\n  # even though it is searched at run-time.  Try to do the best guess by\n  # appending ld.so.conf contents (and includes) to the search path.\n  if test -f /etc/ld.so.conf; then\n    lt_ld_extra=`awk '/^include / { system(sprintf(\"cd /etc; cat %s 2>/dev/null\", \\$2)); skip = 1; } { if (!skip) print \\$0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[\t ]*hwcap[\t ]/d;s/[:,\t]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/\"//g;/^$/d' | tr '\\n' ' '`\n    sys_lib_dlsearch_path_spec=\"/lib /usr/lib $lt_ld_extra\"\n  fi\n\n  # We used to test for /lib/ld.so.1 and disable shared libraries on\n  # powerpc, because MkLinux only supported shared libraries with the\n  # GNU dynamic linker.  Since this was broken with cross compilers,\n  # most powerpc-linux boxes support dynamic linking these days and\n  # people can always --disable-shared, the test was removed, and we\n  # assume the GNU/Linux dynamic linker is in use.\n  dynamic_linker='GNU/Linux ld.so'\n  ;;\n\nnetbsd*)\n  version_type=sunos\n  need_lib_prefix=no\n  need_version=no\n  if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n    finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -m $libdir'\n    dynamic_linker='NetBSD (a.out) ld.so'\n  else\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    dynamic_linker='NetBSD ld.elf_so'\n  fi\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  ;;\n\nnewsos6)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  ;;\n\n*nto* | *qnx*)\n  version_type=qnx\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  dynamic_linker='ldqnx.so'\n  ;;\n\nopenbsd* | bitrig*)\n  version_type=sunos\n  sys_lib_dlsearch_path_spec=/usr/lib\n  need_lib_prefix=no\n  if test -z \"`echo __ELF__ | $CC -E - | $GREP __ELF__`\"; then\n    need_version=no\n  else\n    need_version=yes\n  fi\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -m $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  ;;\n\nos2*)\n  libname_spec='$name'\n  version_type=windows\n  shrext_cmds=.dll\n  need_version=no\n  need_lib_prefix=no\n  # OS/2 can only load a DLL with a base name of 8 characters or less.\n  soname_spec='`test -n \"$os2dllname\" && libname=\"$os2dllname\";\n    v=$($ECHO $release$versuffix | tr -d .-);\n    n=$($ECHO $libname | cut -b -$((8 - ${#v})) | tr . _);\n    $ECHO $n$v`$shared_ext'\n  library_names_spec='${libname}_dll.$libext'\n  dynamic_linker='OS/2 ld.exe'\n  shlibpath_var=BEGINLIBPATH\n  sys_lib_search_path_spec=\"/lib /usr/lib /usr/local/lib\"\n  sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n  postinstall_cmds='base_file=`basename \\$file`~\n    dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; $ECHO \\$dlname'\\''`~\n    dldir=$destdir/`dirname \\$dlpath`~\n    test -d \\$dldir || mkdir -p \\$dldir~\n    $install_prog $dir/$dlname \\$dldir/$dlname~\n    chmod a+x \\$dldir/$dlname~\n    if test -n '\\''$stripme'\\'' && test -n '\\''$striplib'\\''; then\n      eval '\\''$striplib \\$dldir/$dlname'\\'' || exit \\$?;\n    fi'\n  postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; $ECHO \\$dlname'\\''`~\n    dlpath=$dir/\\$dldll~\n    $RM \\$dlpath'\n  ;;\n\nosf3* | osf4* | osf5*)\n  version_type=osf\n  need_lib_prefix=no\n  need_version=no\n  soname_spec='$libname$release$shared_ext$major'\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  sys_lib_search_path_spec=\"/usr/shlib /usr/ccs/lib /usr/lib/cmplrs/cc /usr/lib /usr/local/lib /var/shlib\"\n  sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n  ;;\n\nrdos*)\n  dynamic_linker=no\n  ;;\n\nsolaris*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  # ldd complains unless libraries are executable\n  postinstall_cmds='chmod +x $lib'\n  ;;\n\nsunos4*)\n  version_type=sunos\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n  finish_cmds='PATH=\"\\$PATH:/usr/etc\" ldconfig $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  if test yes = \"$with_gnu_ld\"; then\n    need_lib_prefix=no\n  fi\n  need_version=yes\n  ;;\n\nsysv4 | sysv4.3*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  case $host_vendor in\n    sni)\n      shlibpath_overrides_runpath=no\n      need_lib_prefix=no\n      runpath_var=LD_RUN_PATH\n      ;;\n    siemens)\n      need_lib_prefix=no\n      ;;\n    motorola)\n      need_lib_prefix=no\n      need_version=no\n      shlibpath_overrides_runpath=no\n      sys_lib_search_path_spec='/lib /usr/lib /usr/ccs/lib'\n      ;;\n  esac\n  ;;\n\nsysv4*MP*)\n  if test -d /usr/nec; then\n    version_type=linux # correct to gnu/linux during the next big refactor\n    library_names_spec='$libname$shared_ext.$versuffix $libname$shared_ext.$major $libname$shared_ext'\n    soname_spec='$libname$shared_ext.$major'\n    shlibpath_var=LD_LIBRARY_PATH\n  fi\n  ;;\n\nsysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*)\n  version_type=sco\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  if test yes = \"$with_gnu_ld\"; then\n    sys_lib_search_path_spec='/usr/local/lib /usr/gnu/lib /usr/ccs/lib /usr/lib /lib'\n  else\n    sys_lib_search_path_spec='/usr/ccs/lib /usr/lib'\n    case $host_os in\n      sco3.2v5*)\n        sys_lib_search_path_spec=\"$sys_lib_search_path_spec /lib\"\n\t;;\n    esac\n  fi\n  sys_lib_dlsearch_path_spec='/usr/lib'\n  ;;\n\ntpf*)\n  # TPF is a cross-target only.  Preferred cross-host = GNU/Linux.\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  ;;\n\nuts4*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  ;;\n\n*)\n  dynamic_linker=no\n  ;;\nesac\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $dynamic_linker\" >&5\nprintf \"%s\\n\" \"$dynamic_linker\" >&6; }\ntest no = \"$dynamic_linker\" && can_build_shared=no\n\nvariables_saved_for_relink=\"PATH $shlibpath_var $runpath_var\"\nif test yes = \"$GCC\"; then\n  variables_saved_for_relink=\"$variables_saved_for_relink GCC_EXEC_PREFIX COMPILER_PATH LIBRARY_PATH\"\nfi\n\nif test set = \"${lt_cv_sys_lib_search_path_spec+set}\"; then\n  sys_lib_search_path_spec=$lt_cv_sys_lib_search_path_spec\nfi\n\nif test set = \"${lt_cv_sys_lib_dlsearch_path_spec+set}\"; then\n  sys_lib_dlsearch_path_spec=$lt_cv_sys_lib_dlsearch_path_spec\nfi\n\n# remember unaugmented sys_lib_dlsearch_path content for libtool script decls...\nconfigure_time_dlsearch_path=$sys_lib_dlsearch_path_spec\n\n# ... but it needs LT_SYS_LIBRARY_PATH munging for other configure-time code\nfunc_munge_path_list sys_lib_dlsearch_path_spec \"$LT_SYS_LIBRARY_PATH\"\n\n# to be used as default LT_SYS_LIBRARY_PATH value in generated libtool\nconfigure_time_lt_sys_library_path=$LT_SYS_LIBRARY_PATH\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to hardcode library paths into programs\" >&5\nprintf %s \"checking how to hardcode library paths into programs... \" >&6; }\nhardcode_action=\nif test -n \"$hardcode_libdir_flag_spec\" ||\n   test -n \"$runpath_var\" ||\n   test yes = \"$hardcode_automatic\"; then\n\n  # We can hardcode non-existent directories.\n  if test no != \"$hardcode_direct\" &&\n     # If the only mechanism to avoid hardcoding is shlibpath_var, we\n     # have to relink, otherwise we might link with an installed library\n     # when we should be linking with a yet-to-be-installed one\n     ## test no != \"$_LT_TAGVAR(hardcode_shlibpath_var, )\" &&\n     test no != \"$hardcode_minus_L\"; then\n    # Linking always hardcodes the temporary library directory.\n    hardcode_action=relink\n  else\n    # We can link without hardcoding, and we can hardcode nonexisting dirs.\n    hardcode_action=immediate\n  fi\nelse\n  # We cannot hardcode anything, or else we can only hardcode existing\n  # directories.\n  hardcode_action=unsupported\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $hardcode_action\" >&5\nprintf \"%s\\n\" \"$hardcode_action\" >&6; }\n\nif test relink = \"$hardcode_action\" ||\n   test yes = \"$inherit_rpath\"; then\n  # Fast installation is not supported\n  enable_fast_install=no\nelif test yes = \"$shlibpath_overrides_runpath\" ||\n     test no = \"$enable_shared\"; then\n  # Fast installation is not necessary\n  enable_fast_install=needless\nfi\n\n\n\n\n\n\n  if test yes != \"$enable_dlopen\"; then\n  enable_dlopen=unknown\n  enable_dlopen_self=unknown\n  enable_dlopen_self_static=unknown\nelse\n  lt_cv_dlopen=no\n  lt_cv_dlopen_libs=\n\n  case $host_os in\n  beos*)\n    lt_cv_dlopen=load_add_on\n    lt_cv_dlopen_libs=\n    lt_cv_dlopen_self=yes\n    ;;\n\n  mingw* | pw32* | cegcc*)\n    lt_cv_dlopen=LoadLibrary\n    lt_cv_dlopen_libs=\n    ;;\n\n  cygwin*)\n    lt_cv_dlopen=dlopen\n    lt_cv_dlopen_libs=\n    ;;\n\n  darwin*)\n    # if libdl is installed we need to link against it\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl\" >&5\nprintf %s \"checking for dlopen in -ldl... \" >&6; }\nif test ${ac_cv_lib_dl_dlopen+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_check_lib_save_LIBS=$LIBS\nLIBS=\"-ldl  $LIBS\"\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar dlopen (void);\nint\nmain (void)\n{\nreturn dlopen ();\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_lib_dl_dlopen=yes\nelse case e in #(\n  e) ac_cv_lib_dl_dlopen=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\nLIBS=$ac_check_lib_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen\" >&5\nprintf \"%s\\n\" \"$ac_cv_lib_dl_dlopen\" >&6; }\nif test \"x$ac_cv_lib_dl_dlopen\" = xyes\nthen :\n  lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl\nelse case e in #(\n  e)\n    lt_cv_dlopen=dyld\n    lt_cv_dlopen_libs=\n    lt_cv_dlopen_self=yes\n     ;;\nesac\nfi\n\n    ;;\n\n  tpf*)\n    # Don't try to run any link tests for TPF.  We know it's impossible\n    # because TPF is a cross-compiler, and we know how we open DSOs.\n    lt_cv_dlopen=dlopen\n    lt_cv_dlopen_libs=\n    lt_cv_dlopen_self=no\n    ;;\n\n  *)\n    ac_fn_c_check_func \"$LINENO\" \"shl_load\" \"ac_cv_func_shl_load\"\nif test \"x$ac_cv_func_shl_load\" = xyes\nthen :\n  lt_cv_dlopen=shl_load\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for shl_load in -ldld\" >&5\nprintf %s \"checking for shl_load in -ldld... \" >&6; }\nif test ${ac_cv_lib_dld_shl_load+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_check_lib_save_LIBS=$LIBS\nLIBS=\"-ldld  $LIBS\"\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar shl_load (void);\nint\nmain (void)\n{\nreturn shl_load ();\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_lib_dld_shl_load=yes\nelse case e in #(\n  e) ac_cv_lib_dld_shl_load=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\nLIBS=$ac_check_lib_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_shl_load\" >&5\nprintf \"%s\\n\" \"$ac_cv_lib_dld_shl_load\" >&6; }\nif test \"x$ac_cv_lib_dld_shl_load\" = xyes\nthen :\n  lt_cv_dlopen=shl_load lt_cv_dlopen_libs=-ldld\nelse case e in #(\n  e) ac_fn_c_check_func \"$LINENO\" \"dlopen\" \"ac_cv_func_dlopen\"\nif test \"x$ac_cv_func_dlopen\" = xyes\nthen :\n  lt_cv_dlopen=dlopen\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for dlopen in -ldl\" >&5\nprintf %s \"checking for dlopen in -ldl... \" >&6; }\nif test ${ac_cv_lib_dl_dlopen+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_check_lib_save_LIBS=$LIBS\nLIBS=\"-ldl  $LIBS\"\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar dlopen (void);\nint\nmain (void)\n{\nreturn dlopen ();\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_lib_dl_dlopen=yes\nelse case e in #(\n  e) ac_cv_lib_dl_dlopen=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\nLIBS=$ac_check_lib_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dl_dlopen\" >&5\nprintf \"%s\\n\" \"$ac_cv_lib_dl_dlopen\" >&6; }\nif test \"x$ac_cv_lib_dl_dlopen\" = xyes\nthen :\n  lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for dlopen in -lsvld\" >&5\nprintf %s \"checking for dlopen in -lsvld... \" >&6; }\nif test ${ac_cv_lib_svld_dlopen+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_check_lib_save_LIBS=$LIBS\nLIBS=\"-lsvld  $LIBS\"\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar dlopen (void);\nint\nmain (void)\n{\nreturn dlopen ();\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_lib_svld_dlopen=yes\nelse case e in #(\n  e) ac_cv_lib_svld_dlopen=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\nLIBS=$ac_check_lib_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_svld_dlopen\" >&5\nprintf \"%s\\n\" \"$ac_cv_lib_svld_dlopen\" >&6; }\nif test \"x$ac_cv_lib_svld_dlopen\" = xyes\nthen :\n  lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-lsvld\nelse case e in #(\n  e) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for dld_link in -ldld\" >&5\nprintf %s \"checking for dld_link in -ldld... \" >&6; }\nif test ${ac_cv_lib_dld_dld_link+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_check_lib_save_LIBS=$LIBS\nLIBS=\"-ldld  $LIBS\"\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar dld_link (void);\nint\nmain (void)\n{\nreturn dld_link ();\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_lib_dld_dld_link=yes\nelse case e in #(\n  e) ac_cv_lib_dld_dld_link=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\nLIBS=$ac_check_lib_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_dld_dld_link\" >&5\nprintf \"%s\\n\" \"$ac_cv_lib_dld_dld_link\" >&6; }\nif test \"x$ac_cv_lib_dld_dld_link\" = xyes\nthen :\n  lt_cv_dlopen=dld_link lt_cv_dlopen_libs=-ldld\nfi\n\n\t       ;;\nesac\nfi\n\n\t     ;;\nesac\nfi\n\n\t   ;;\nesac\nfi\n\n\t ;;\nesac\nfi\n\n       ;;\nesac\nfi\n\n    ;;\n  esac\n\n  if test no = \"$lt_cv_dlopen\"; then\n    enable_dlopen=no\n  else\n    enable_dlopen=yes\n  fi\n\n  case $lt_cv_dlopen in\n  dlopen)\n    save_CPPFLAGS=$CPPFLAGS\n    test yes = \"$ac_cv_header_dlfcn_h\" && CPPFLAGS=\"$CPPFLAGS -DHAVE_DLFCN_H\"\n\n    save_LDFLAGS=$LDFLAGS\n    wl=$lt_prog_compiler_wl eval LDFLAGS=\\\"\\$LDFLAGS $export_dynamic_flag_spec\\\"\n\n    save_LIBS=$LIBS\n    LIBS=\"$lt_cv_dlopen_libs $LIBS\"\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether a program can dlopen itself\" >&5\nprintf %s \"checking whether a program can dlopen itself... \" >&6; }\nif test ${lt_cv_dlopen_self+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) \t  if test yes = \"$cross_compiling\"; then :\n  lt_cv_dlopen_self=cross\nelse\n  lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2\n  lt_status=$lt_dlunknown\n  cat > conftest.$ac_ext <<_LT_EOF\n#line $LINENO \"configure\"\n#include \"confdefs.h\"\n\n#if HAVE_DLFCN_H\n#include <dlfcn.h>\n#endif\n\n#include <stdio.h>\n\n#ifdef RTLD_GLOBAL\n#  define LT_DLGLOBAL\t\tRTLD_GLOBAL\n#else\n#  ifdef DL_GLOBAL\n#    define LT_DLGLOBAL\t\tDL_GLOBAL\n#  else\n#    define LT_DLGLOBAL\t\t0\n#  endif\n#endif\n\n/* We may have to define LT_DLLAZY_OR_NOW in the command line if we\n   find out it does not work in some platform. */\n#ifndef LT_DLLAZY_OR_NOW\n#  ifdef RTLD_LAZY\n#    define LT_DLLAZY_OR_NOW\t\tRTLD_LAZY\n#  else\n#    ifdef DL_LAZY\n#      define LT_DLLAZY_OR_NOW\t\tDL_LAZY\n#    else\n#      ifdef RTLD_NOW\n#        define LT_DLLAZY_OR_NOW\tRTLD_NOW\n#      else\n#        ifdef DL_NOW\n#          define LT_DLLAZY_OR_NOW\tDL_NOW\n#        else\n#          define LT_DLLAZY_OR_NOW\t0\n#        endif\n#      endif\n#    endif\n#  endif\n#endif\n\n/* When -fvisibility=hidden is used, assume the code has been annotated\n   correspondingly for the symbols needed.  */\n#if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3))\nint fnord () __attribute__((visibility(\"default\")));\n#endif\n\nint fnord () { return 42; }\nint main ()\n{\n  void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW);\n  int status = $lt_dlunknown;\n\n  if (self)\n    {\n      if (dlsym (self,\"fnord\"))       status = $lt_dlno_uscore;\n      else\n        {\n\t  if (dlsym( self,\"_fnord\"))  status = $lt_dlneed_uscore;\n          else puts (dlerror ());\n\t}\n      /* dlclose (self); */\n    }\n  else\n    puts (dlerror ());\n\n  return status;\n}\n_LT_EOF\n  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_link\\\"\"; } >&5\n  (eval $ac_link) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && test -s \"conftest$ac_exeext\" 2>/dev/null; then\n    (./conftest; exit; ) >&5 2>/dev/null\n    lt_status=$?\n    case x$lt_status in\n      x$lt_dlno_uscore) lt_cv_dlopen_self=yes ;;\n      x$lt_dlneed_uscore) lt_cv_dlopen_self=yes ;;\n      x$lt_dlunknown|x*) lt_cv_dlopen_self=no ;;\n    esac\n  else :\n    # compilation failed\n    lt_cv_dlopen_self=no\n  fi\nfi\nrm -fr conftest*\n\n     ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_dlopen_self\" >&5\nprintf \"%s\\n\" \"$lt_cv_dlopen_self\" >&6; }\n\n    if test yes = \"$lt_cv_dlopen_self\"; then\n      wl=$lt_prog_compiler_wl eval LDFLAGS=\\\"\\$LDFLAGS $lt_prog_compiler_static\\\"\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether a statically linked program can dlopen itself\" >&5\nprintf %s \"checking whether a statically linked program can dlopen itself... \" >&6; }\nif test ${lt_cv_dlopen_self_static+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) \t  if test yes = \"$cross_compiling\"; then :\n  lt_cv_dlopen_self_static=cross\nelse\n  lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2\n  lt_status=$lt_dlunknown\n  cat > conftest.$ac_ext <<_LT_EOF\n#line $LINENO \"configure\"\n#include \"confdefs.h\"\n\n#if HAVE_DLFCN_H\n#include <dlfcn.h>\n#endif\n\n#include <stdio.h>\n\n#ifdef RTLD_GLOBAL\n#  define LT_DLGLOBAL\t\tRTLD_GLOBAL\n#else\n#  ifdef DL_GLOBAL\n#    define LT_DLGLOBAL\t\tDL_GLOBAL\n#  else\n#    define LT_DLGLOBAL\t\t0\n#  endif\n#endif\n\n/* We may have to define LT_DLLAZY_OR_NOW in the command line if we\n   find out it does not work in some platform. */\n#ifndef LT_DLLAZY_OR_NOW\n#  ifdef RTLD_LAZY\n#    define LT_DLLAZY_OR_NOW\t\tRTLD_LAZY\n#  else\n#    ifdef DL_LAZY\n#      define LT_DLLAZY_OR_NOW\t\tDL_LAZY\n#    else\n#      ifdef RTLD_NOW\n#        define LT_DLLAZY_OR_NOW\tRTLD_NOW\n#      else\n#        ifdef DL_NOW\n#          define LT_DLLAZY_OR_NOW\tDL_NOW\n#        else\n#          define LT_DLLAZY_OR_NOW\t0\n#        endif\n#      endif\n#    endif\n#  endif\n#endif\n\n/* When -fvisibility=hidden is used, assume the code has been annotated\n   correspondingly for the symbols needed.  */\n#if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3))\nint fnord () __attribute__((visibility(\"default\")));\n#endif\n\nint fnord () { return 42; }\nint main ()\n{\n  void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW);\n  int status = $lt_dlunknown;\n\n  if (self)\n    {\n      if (dlsym (self,\"fnord\"))       status = $lt_dlno_uscore;\n      else\n        {\n\t  if (dlsym( self,\"_fnord\"))  status = $lt_dlneed_uscore;\n          else puts (dlerror ());\n\t}\n      /* dlclose (self); */\n    }\n  else\n    puts (dlerror ());\n\n  return status;\n}\n_LT_EOF\n  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_link\\\"\"; } >&5\n  (eval $ac_link) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } && test -s \"conftest$ac_exeext\" 2>/dev/null; then\n    (./conftest; exit; ) >&5 2>/dev/null\n    lt_status=$?\n    case x$lt_status in\n      x$lt_dlno_uscore) lt_cv_dlopen_self_static=yes ;;\n      x$lt_dlneed_uscore) lt_cv_dlopen_self_static=yes ;;\n      x$lt_dlunknown|x*) lt_cv_dlopen_self_static=no ;;\n    esac\n  else :\n    # compilation failed\n    lt_cv_dlopen_self_static=no\n  fi\nfi\nrm -fr conftest*\n\n       ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_dlopen_self_static\" >&5\nprintf \"%s\\n\" \"$lt_cv_dlopen_self_static\" >&6; }\n    fi\n\n    CPPFLAGS=$save_CPPFLAGS\n    LDFLAGS=$save_LDFLAGS\n    LIBS=$save_LIBS\n    ;;\n  esac\n\n  case $lt_cv_dlopen_self in\n  yes|no) enable_dlopen_self=$lt_cv_dlopen_self ;;\n  *) enable_dlopen_self=unknown ;;\n  esac\n\n  case $lt_cv_dlopen_self_static in\n  yes|no) enable_dlopen_self_static=$lt_cv_dlopen_self_static ;;\n  *) enable_dlopen_self_static=unknown ;;\n  esac\nfi\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\nstriplib=\nold_striplib=\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether stripping libraries is possible\" >&5\nprintf %s \"checking whether stripping libraries is possible... \" >&6; }\nif test -z \"$STRIP\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nelse\n  if $STRIP -V 2>&1 | $GREP \"GNU strip\" >/dev/null; then\n    old_striplib=\"$STRIP --strip-debug\"\n    striplib=\"$STRIP --strip-unneeded\"\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; }\n  else\n    case $host_os in\n    darwin*)\n      # FIXME - insert some real tests, host_os isn't really good enough\n      striplib=\"$STRIP -x\"\n      old_striplib=\"$STRIP -S\"\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; }\n      ;;\n    freebsd*)\n      if $STRIP -V 2>&1 | $GREP \"elftoolchain\" >/dev/null; then\n        old_striplib=\"$STRIP --strip-debug\"\n        striplib=\"$STRIP --strip-unneeded\"\n        { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; }\n      else\n        { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\n      fi\n      ;;\n    *)\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\n      ;;\n    esac\n  fi\nfi\n\n\n\n\n\n\n\n\n\n\n\n\n  # Report what library types will actually be built\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if libtool supports shared libraries\" >&5\nprintf %s \"checking if libtool supports shared libraries... \" >&6; }\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $can_build_shared\" >&5\nprintf \"%s\\n\" \"$can_build_shared\" >&6; }\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether to build shared libraries\" >&5\nprintf %s \"checking whether to build shared libraries... \" >&6; }\n  test no = \"$can_build_shared\" && enable_shared=no\n\n  # On AIX, shared libraries and static libraries use the same namespace, and\n  # are all built from PIC.\n  case $host_os in\n  aix3*)\n    test yes = \"$enable_shared\" && enable_static=no\n    if test -n \"$RANLIB\"; then\n      archive_cmds=\"$archive_cmds~\\$RANLIB \\$lib\"\n      postinstall_cmds='$RANLIB $lib'\n    fi\n    ;;\n\n  aix[4-9]*)\n    if test ia64 != \"$host_cpu\"; then\n      case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in\n      yes,aix,yes) ;;\t\t\t# shared object as lib.so file only\n      yes,svr4,*) ;;\t\t\t# shared object as lib.so archive member only\n      yes,*) enable_static=no ;;\t# shared object in lib.a archive as well\n      esac\n    fi\n    ;;\n  esac\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $enable_shared\" >&5\nprintf \"%s\\n\" \"$enable_shared\" >&6; }\n\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether to build static libraries\" >&5\nprintf %s \"checking whether to build static libraries... \" >&6; }\n  # Make sure either enable_shared or enable_static is yes.\n  test yes = \"$enable_shared\" || enable_static=yes\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $enable_static\" >&5\nprintf \"%s\\n\" \"$enable_static\" >&6; }\n\n\n\n\nfi\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\nCC=$lt_save_CC\n\n      if test -n \"$CXX\" && ( test no != \"$CXX\" &&\n    ( (test g++ = \"$CXX\" && `g++ -v >/dev/null 2>&1` ) ||\n    (test g++ != \"$CXX\"))); then\n  ac_ext=cpp\nac_cpp='$CXXCPP $CPPFLAGS'\nac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_cxx_compiler_gnu\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to run the C++ preprocessor\" >&5\nprintf %s \"checking how to run the C++ preprocessor... \" >&6; }\nif test -z \"$CXXCPP\"; then\n  if test ${ac_cv_prog_CXXCPP+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e)     # Double quotes because $CXX needs to be expanded\n    for CXXCPP in \"$CXX -E\" cpp /lib/cpp\n    do\n      ac_preproc_ok=false\nfor ac_cxx_preproc_warn_flag in '' yes\ndo\n  # Use a header file that comes with gcc, so configuring glibc\n  # with a fresh cross-compiler works.\n  # On the NeXT, cc -E runs the code through the compiler's parser,\n  # not just through cpp. \"Syntax error\" is here to catch this case.\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <limits.h>\n\t\t     Syntax error\n_ACEOF\nif ac_fn_cxx_try_cpp \"$LINENO\"\nthen :\n\nelse case e in #(\n  e) # Broken: fails on valid input.\ncontinue ;;\nesac\nfi\nrm -f conftest.err conftest.i conftest.$ac_ext\n\n  # OK, works on sane cases.  Now check whether nonexistent headers\n  # can be detected and how.\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <ac_nonexistent.h>\n_ACEOF\nif ac_fn_cxx_try_cpp \"$LINENO\"\nthen :\n  # Broken: success on invalid input.\ncontinue\nelse case e in #(\n  e) # Passes both tests.\nac_preproc_ok=:\nbreak ;;\nesac\nfi\nrm -f conftest.err conftest.i conftest.$ac_ext\n\ndone\n# Because of 'break', _AC_PREPROC_IFELSE's cleaning code was skipped.\nrm -f conftest.i conftest.err conftest.$ac_ext\nif $ac_preproc_ok\nthen :\n  break\nfi\n\n    done\n    ac_cv_prog_CXXCPP=$CXXCPP\n   ;;\nesac\nfi\n  CXXCPP=$ac_cv_prog_CXXCPP\nelse\n  ac_cv_prog_CXXCPP=$CXXCPP\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $CXXCPP\" >&5\nprintf \"%s\\n\" \"$CXXCPP\" >&6; }\nac_preproc_ok=false\nfor ac_cxx_preproc_warn_flag in '' yes\ndo\n  # Use a header file that comes with gcc, so configuring glibc\n  # with a fresh cross-compiler works.\n  # On the NeXT, cc -E runs the code through the compiler's parser,\n  # not just through cpp. \"Syntax error\" is here to catch this case.\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <limits.h>\n\t\t     Syntax error\n_ACEOF\nif ac_fn_cxx_try_cpp \"$LINENO\"\nthen :\n\nelse case e in #(\n  e) # Broken: fails on valid input.\ncontinue ;;\nesac\nfi\nrm -f conftest.err conftest.i conftest.$ac_ext\n\n  # OK, works on sane cases.  Now check whether nonexistent headers\n  # can be detected and how.\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <ac_nonexistent.h>\n_ACEOF\nif ac_fn_cxx_try_cpp \"$LINENO\"\nthen :\n  # Broken: success on invalid input.\ncontinue\nelse case e in #(\n  e) # Passes both tests.\nac_preproc_ok=:\nbreak ;;\nesac\nfi\nrm -f conftest.err conftest.i conftest.$ac_ext\n\ndone\n# Because of 'break', _AC_PREPROC_IFELSE's cleaning code was skipped.\nrm -f conftest.i conftest.err conftest.$ac_ext\nif $ac_preproc_ok\nthen :\n\nelse case e in #(\n  e) { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error $? \"C++ preprocessor \\\"$CXXCPP\\\" fails sanity check\nSee 'config.log' for more details\" \"$LINENO\" 5; } ;;\nesac\nfi\n\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\nelse\n  _lt_caught_CXX_error=yes\nfi\n\nac_ext=cpp\nac_cpp='$CXXCPP $CPPFLAGS'\nac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_cxx_compiler_gnu\n\narchive_cmds_need_lc_CXX=no\nallow_undefined_flag_CXX=\nalways_export_symbols_CXX=no\narchive_expsym_cmds_CXX=\ncompiler_needs_object_CXX=no\nexport_dynamic_flag_spec_CXX=\nhardcode_direct_CXX=no\nhardcode_direct_absolute_CXX=no\nhardcode_libdir_flag_spec_CXX=\nhardcode_libdir_separator_CXX=\nhardcode_minus_L_CXX=no\nhardcode_shlibpath_var_CXX=unsupported\nhardcode_automatic_CXX=no\ninherit_rpath_CXX=no\nmodule_cmds_CXX=\nmodule_expsym_cmds_CXX=\nlink_all_deplibs_CXX=unknown\nold_archive_cmds_CXX=$old_archive_cmds\nreload_flag_CXX=$reload_flag\nreload_cmds_CXX=$reload_cmds\nno_undefined_flag_CXX=\nwhole_archive_flag_spec_CXX=\nenable_shared_with_static_runtimes_CXX=no\n\n# Source file extension for C++ test sources.\nac_ext=cpp\n\n# Object file extension for compiled C++ test sources.\nobjext=o\nobjext_CXX=$objext\n\n# No sense in running all these tests if we already determined that\n# the CXX compiler isn't working.  Some variables (like enable_shared)\n# are currently assumed to apply to all compilers on this platform,\n# and will be corrupted by setting them based on a non-working compiler.\nif test yes != \"$_lt_caught_CXX_error\"; then\n  # Code to be used in simple compile tests\n  lt_simple_compile_test_code=\"int some_variable = 0;\"\n\n  # Code to be used in simple link tests\n  lt_simple_link_test_code='int main(int, char *[]) { return(0); }'\n\n  # ltmain only uses $CC for tagged configurations so make sure $CC is set.\n\n\n\n\n\n\n# If no C compiler was specified, use CC.\nLTCC=${LTCC-\"$CC\"}\n\n# If no C compiler flags were specified, use CFLAGS.\nLTCFLAGS=${LTCFLAGS-\"$CFLAGS\"}\n\n# Allow CC to be a program name with arguments.\ncompiler=$CC\n\n\n  # save warnings/boilerplate of simple test code\n  ac_outfile=conftest.$ac_objext\necho \"$lt_simple_compile_test_code\" >conftest.$ac_ext\neval \"$ac_compile\" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err\n_lt_compiler_boilerplate=`cat conftest.err`\n$RM conftest*\n\n  ac_outfile=conftest.$ac_objext\necho \"$lt_simple_link_test_code\" >conftest.$ac_ext\neval \"$ac_link\" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err\n_lt_linker_boilerplate=`cat conftest.err`\n$RM -r conftest*\n\n\n  # Allow CC to be a program name with arguments.\n  lt_save_CC=$CC\n  lt_save_CFLAGS=$CFLAGS\n  lt_save_LD=$LD\n  lt_save_GCC=$GCC\n  GCC=$GXX\n  lt_save_with_gnu_ld=$with_gnu_ld\n  lt_save_path_LD=$lt_cv_path_LD\n  if test -n \"${lt_cv_prog_gnu_ldcxx+set}\"; then\n    lt_cv_prog_gnu_ld=$lt_cv_prog_gnu_ldcxx\n  else\n    $as_unset lt_cv_prog_gnu_ld\n  fi\n  if test -n \"${lt_cv_path_LDCXX+set}\"; then\n    lt_cv_path_LD=$lt_cv_path_LDCXX\n  else\n    $as_unset lt_cv_path_LD\n  fi\n  test -z \"${LDCXX+set}\" || LD=$LDCXX\n  CC=${CXX-\"c++\"}\n  CFLAGS=$CXXFLAGS\n  compiler=$CC\n  compiler_CXX=$CC\n  func_cc_basename $compiler\ncc_basename=$func_cc_basename_result\n\n\n  if test -n \"$compiler\"; then\n    # We don't want -fno-exception when compiling C++ code, so set the\n    # no_builtin_flag separately\n    if test yes = \"$GXX\"; then\n      lt_prog_compiler_no_builtin_flag_CXX=' -fno-builtin'\n    else\n      lt_prog_compiler_no_builtin_flag_CXX=\n    fi\n\n    if test yes = \"$GXX\"; then\n      # Set up default GNU C++ configuration\n\n\n\n# Check whether --with-gnu-ld was given.\nif test ${with_gnu_ld+y}\nthen :\n  withval=$with_gnu_ld; test no = \"$withval\" || with_gnu_ld=yes\nelse case e in #(\n  e) with_gnu_ld=no ;;\nesac\nfi\n\nac_prog=ld\nif test yes = \"$GCC\"; then\n  # Check if gcc -print-prog-name=ld gives a path.\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for ld used by $CC\" >&5\nprintf %s \"checking for ld used by $CC... \" >&6; }\n  case $host in\n  *-*-mingw*)\n    # gcc leaves a trailing carriage return, which upsets mingw\n    ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\\015'` ;;\n  *)\n    ac_prog=`($CC -print-prog-name=ld) 2>&5` ;;\n  esac\n  case $ac_prog in\n    # Accept absolute paths.\n    [\\\\/]* | ?:[\\\\/]*)\n      re_direlt='/[^/][^/]*/\\.\\./'\n      # Canonicalize the pathname of ld\n      ac_prog=`$ECHO \"$ac_prog\"| $SED 's%\\\\\\\\%/%g'`\n      while $ECHO \"$ac_prog\" | $GREP \"$re_direlt\" > /dev/null 2>&1; do\n\tac_prog=`$ECHO $ac_prog| $SED \"s%$re_direlt%/%\"`\n      done\n      test -z \"$LD\" && LD=$ac_prog\n      ;;\n  \"\")\n    # If it fails, then pretend we aren't using GCC.\n    ac_prog=ld\n    ;;\n  *)\n    # If it is relative, then search for the first ld in PATH.\n    with_gnu_ld=unknown\n    ;;\n  esac\nelif test yes = \"$with_gnu_ld\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for GNU ld\" >&5\nprintf %s \"checking for GNU ld... \" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for non-GNU ld\" >&5\nprintf %s \"checking for non-GNU ld... \" >&6; }\nfi\nif test ${lt_cv_path_LD+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -z \"$LD\"; then\n  lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR\n  for ac_dir in $PATH; do\n    IFS=$lt_save_ifs\n    test -z \"$ac_dir\" && ac_dir=.\n    if test -f \"$ac_dir/$ac_prog\" || test -f \"$ac_dir/$ac_prog$ac_exeext\"; then\n      lt_cv_path_LD=$ac_dir/$ac_prog\n      # Check to see if the program is GNU ld.  I'd rather use --version,\n      # but apparently some variants of GNU ld only accept -v.\n      # Break only if it was the GNU/non-GNU ld that we prefer.\n      case `\"$lt_cv_path_LD\" -v 2>&1 </dev/null` in\n      *GNU* | *'with BFD'*)\n\ttest no != \"$with_gnu_ld\" && break\n\t;;\n      *)\n\ttest yes != \"$with_gnu_ld\" && break\n\t;;\n      esac\n    fi\n  done\n  IFS=$lt_save_ifs\nelse\n  lt_cv_path_LD=$LD # Let the user override the test with a path.\nfi ;;\nesac\nfi\n\nLD=$lt_cv_path_LD\nif test -n \"$LD\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $LD\" >&5\nprintf \"%s\\n\" \"$LD\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\ntest -z \"$LD\" && as_fn_error $? \"no acceptable ld found in \\$PATH\" \"$LINENO\" 5\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if the linker ($LD) is GNU ld\" >&5\nprintf %s \"checking if the linker ($LD) is GNU ld... \" >&6; }\nif test ${lt_cv_prog_gnu_ld+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) # I'd rather use --version here, but apparently some GNU lds only accept -v.\ncase `$LD -v 2>&1 </dev/null` in\n*GNU* | *'with BFD'*)\n  lt_cv_prog_gnu_ld=yes\n  ;;\n*)\n  lt_cv_prog_gnu_ld=no\n  ;;\nesac ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_gnu_ld\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_gnu_ld\" >&6; }\nwith_gnu_ld=$lt_cv_prog_gnu_ld\n\n\n\n\n\n\n\n      # Check if GNU C++ uses GNU ld as the underlying linker, since the\n      # archiving commands below assume that GNU ld is being used.\n      if test yes = \"$with_gnu_ld\"; then\n        archive_cmds_CXX='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n        archive_expsym_cmds_CXX='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\n        hardcode_libdir_flag_spec_CXX='$wl-rpath $wl$libdir'\n        export_dynamic_flag_spec_CXX='$wl--export-dynamic'\n\n        # If archive_cmds runs LD, not CC, wlarc should be empty\n        # XXX I think wlarc can be eliminated in ltcf-cxx, but I need to\n        #     investigate it a little bit more. (MM)\n        wlarc='$wl'\n\n        # ancient GNU ld didn't support --whole-archive et. al.\n        if eval \"`$CC -print-prog-name=ld` --help 2>&1\" |\n\t  $GREP 'no-whole-archive' > /dev/null; then\n          whole_archive_flag_spec_CXX=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive'\n        else\n          whole_archive_flag_spec_CXX=\n        fi\n      else\n        with_gnu_ld=no\n        wlarc=\n\n        # A generic and very simple default shared library creation\n        # command for GNU C++ for the case where it uses the native\n        # linker, instead of GNU ld.  If possible, this setting should\n        # overridden to take advantage of the native linker features on\n        # the platform it is being used on.\n        archive_cmds_CXX='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $lib'\n      fi\n\n      # Commands to make compiler produce verbose output that lists\n      # what \"hidden\" libraries, object files and flags are used when\n      # linking a shared library.\n      output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v \"^Configured with:\" | $GREP \"\\-L\"'\n\n    else\n      GXX=no\n      with_gnu_ld=no\n      wlarc=\n    fi\n\n    # PORTME: fill in a description of your system's C++ link characteristics\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether the $compiler linker ($LD) supports shared libraries\" >&5\nprintf %s \"checking whether the $compiler linker ($LD) supports shared libraries... \" >&6; }\n    ld_shlibs_CXX=yes\n    case $host_os in\n      aix3*)\n        # FIXME: insert proper C++ library support\n        ld_shlibs_CXX=no\n        ;;\n      aix[4-9]*)\n        if test ia64 = \"$host_cpu\"; then\n          # On IA64, the linker does run time linking by default, so we don't\n          # have to do anything special.\n          aix_use_runtimelinking=no\n          exp_sym_flag='-Bexport'\n          no_entry_flag=\n        else\n          aix_use_runtimelinking=no\n\n          # Test if we are trying to use run time linking or normal\n          # AIX style linking. If -brtl is somewhere in LDFLAGS, we\n          # have runtime linking enabled, and use it for executables.\n          # For shared libraries, we enable/disable runtime linking\n          # depending on the kind of the shared library created -\n          # when \"with_aix_soname,aix_use_runtimelinking\" is:\n          # \"aix,no\"   lib.a(lib.so.V) shared, rtl:no,  for executables\n          # \"aix,yes\"  lib.so          shared, rtl:yes, for executables\n          #            lib.a           static archive\n          # \"both,no\"  lib.so.V(shr.o) shared, rtl:yes\n          #            lib.a(lib.so.V) shared, rtl:no,  for executables\n          # \"both,yes\" lib.so.V(shr.o) shared, rtl:yes, for executables\n          #            lib.a(lib.so.V) shared, rtl:no\n          # \"svr4,*\"   lib.so.V(shr.o) shared, rtl:yes, for executables\n          #            lib.a           static archive\n          case $host_os in aix4.[23]|aix4.[23].*|aix[5-9]*)\n\t    for ld_flag in $LDFLAGS; do\n\t      case $ld_flag in\n\t      *-brtl*)\n\t        aix_use_runtimelinking=yes\n\t        break\n\t        ;;\n\t      esac\n\t    done\n\t    if test svr4,no = \"$with_aix_soname,$aix_use_runtimelinking\"; then\n\t      # With aix-soname=svr4, we create the lib.so.V shared archives only,\n\t      # so we don't have lib.a shared libs to link our executables.\n\t      # We have to force runtime linking in this case.\n\t      aix_use_runtimelinking=yes\n\t      LDFLAGS=\"$LDFLAGS -Wl,-brtl\"\n\t    fi\n\t    ;;\n          esac\n\n          exp_sym_flag='-bexport'\n          no_entry_flag='-bnoentry'\n        fi\n\n        # When large executables or shared objects are built, AIX ld can\n        # have problems creating the table of contents.  If linking a library\n        # or program results in \"error TOC overflow\" add -mminimal-toc to\n        # CXXFLAGS/CFLAGS for g++/gcc.  In the cases where that is not\n        # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS.\n\n        archive_cmds_CXX=''\n        hardcode_direct_CXX=yes\n        hardcode_direct_absolute_CXX=yes\n        hardcode_libdir_separator_CXX=':'\n        link_all_deplibs_CXX=yes\n        file_list_spec_CXX='$wl-f,'\n        case $with_aix_soname,$aix_use_runtimelinking in\n        aix,*) ;;\t# no import file\n        svr4,* | *,yes) # use import file\n          # The Import File defines what to hardcode.\n          hardcode_direct_CXX=no\n          hardcode_direct_absolute_CXX=no\n          ;;\n        esac\n\n        if test yes = \"$GXX\"; then\n          case $host_os in aix4.[012]|aix4.[012].*)\n          # We only want to do this on AIX 4.2 and lower, the check\n          # below for broken collect2 doesn't work under 4.3+\n\t  collect2name=`$CC -print-prog-name=collect2`\n\t  if test -f \"$collect2name\" &&\n\t     strings \"$collect2name\" | $GREP resolve_lib_name >/dev/null\n\t  then\n\t    # We have reworked collect2\n\t    :\n\t  else\n\t    # We have old collect2\n\t    hardcode_direct_CXX=unsupported\n\t    # It fails to find uninstalled libraries when the uninstalled\n\t    # path is not listed in the libpath.  Setting hardcode_minus_L\n\t    # to unsupported forces relinking\n\t    hardcode_minus_L_CXX=yes\n\t    hardcode_libdir_flag_spec_CXX='-L$libdir'\n\t    hardcode_libdir_separator_CXX=\n\t  fi\n          esac\n          shared_flag='-shared'\n\t  if test yes = \"$aix_use_runtimelinking\"; then\n\t    shared_flag=$shared_flag' $wl-G'\n\t  fi\n\t  # Need to ensure runtime linking is disabled for the traditional\n\t  # shared library, or the linker may eventually find shared libraries\n\t  # /with/ Import File - we do not want to mix them.\n\t  shared_flag_aix='-shared'\n\t  shared_flag_svr4='-shared $wl-G'\n        else\n          # not using gcc\n          if test ia64 = \"$host_cpu\"; then\n\t  # VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release\n\t  # chokes on -Wl,-G. The following line is correct:\n\t  shared_flag='-G'\n          else\n\t    if test yes = \"$aix_use_runtimelinking\"; then\n\t      shared_flag='$wl-G'\n\t    else\n\t      shared_flag='$wl-bM:SRE'\n\t    fi\n\t    shared_flag_aix='$wl-bM:SRE'\n\t    shared_flag_svr4='$wl-G'\n          fi\n        fi\n\n        export_dynamic_flag_spec_CXX='$wl-bexpall'\n        # It seems that -bexpall does not export symbols beginning with\n        # underscore (_), so it is better to generate a list of symbols to\n\t# export.\n        always_export_symbols_CXX=yes\n\tif test aix,yes = \"$with_aix_soname,$aix_use_runtimelinking\"; then\n          # Warning - without using the other runtime loading flags (-brtl),\n          # -berok will link without error, but may produce a broken library.\n          # The \"-G\" linker flag allows undefined symbols.\n          no_undefined_flag_CXX='-bernotok'\n          # Determine the default libpath from the value encoded in an empty\n          # executable.\n          if test set = \"${lt_cv_aix_libpath+set}\"; then\n  aix_libpath=$lt_cv_aix_libpath\nelse\n  if test ${lt_cv_aix_libpath__CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_cxx_try_link \"$LINENO\"\nthen :\n\n  lt_aix_libpath_sed='\n      /Import File Strings/,/^$/ {\n\t  /^0/ {\n\t      s/^0  *\\([^ ]*\\) *$/\\1/\n\t      p\n\t  }\n      }'\n  lt_cv_aix_libpath__CXX=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  # Check for a 64-bit object if we didn't find anything.\n  if test -z \"$lt_cv_aix_libpath__CXX\"; then\n    lt_cv_aix_libpath__CXX=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  fi\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n  if test -z \"$lt_cv_aix_libpath__CXX\"; then\n    lt_cv_aix_libpath__CXX=/usr/lib:/lib\n  fi\n   ;;\nesac\nfi\n\n  aix_libpath=$lt_cv_aix_libpath__CXX\nfi\n\n          hardcode_libdir_flag_spec_CXX='$wl-blibpath:$libdir:'\"$aix_libpath\"\n\n          archive_expsym_cmds_CXX='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n \"$allow_undefined_flag\"; then func_echo_all \"$wl$allow_undefined_flag\"; else :; fi` $wl'$exp_sym_flag:\\$export_symbols' '$shared_flag\n        else\n          if test ia64 = \"$host_cpu\"; then\n\t    hardcode_libdir_flag_spec_CXX='$wl-R $libdir:/usr/lib:/lib'\n\t    allow_undefined_flag_CXX=\"-z nodefs\"\n\t    archive_expsym_cmds_CXX=\"\\$CC $shared_flag\"' -o $output_objdir/$soname $libobjs $deplibs '\"\\$wl$no_entry_flag\"' $compiler_flags $wl$allow_undefined_flag '\"\\$wl$exp_sym_flag:\\$export_symbols\"\n          else\n\t    # Determine the default libpath from the value encoded in an\n\t    # empty executable.\n\t    if test set = \"${lt_cv_aix_libpath+set}\"; then\n  aix_libpath=$lt_cv_aix_libpath\nelse\n  if test ${lt_cv_aix_libpath__CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_cxx_try_link \"$LINENO\"\nthen :\n\n  lt_aix_libpath_sed='\n      /Import File Strings/,/^$/ {\n\t  /^0/ {\n\t      s/^0  *\\([^ ]*\\) *$/\\1/\n\t      p\n\t  }\n      }'\n  lt_cv_aix_libpath__CXX=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  # Check for a 64-bit object if we didn't find anything.\n  if test -z \"$lt_cv_aix_libpath__CXX\"; then\n    lt_cv_aix_libpath__CXX=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  fi\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n  if test -z \"$lt_cv_aix_libpath__CXX\"; then\n    lt_cv_aix_libpath__CXX=/usr/lib:/lib\n  fi\n   ;;\nesac\nfi\n\n  aix_libpath=$lt_cv_aix_libpath__CXX\nfi\n\n\t    hardcode_libdir_flag_spec_CXX='$wl-blibpath:$libdir:'\"$aix_libpath\"\n\t    # Warning - without using the other run time loading flags,\n\t    # -berok will link without error, but may produce a broken library.\n\t    no_undefined_flag_CXX=' $wl-bernotok'\n\t    allow_undefined_flag_CXX=' $wl-berok'\n\t    if test yes = \"$with_gnu_ld\"; then\n\t      # We only use this code for GNU lds that support --whole-archive.\n\t      whole_archive_flag_spec_CXX='$wl--whole-archive$convenience $wl--no-whole-archive'\n\t    else\n\t      # Exported symbols can be pulled into shared objects from archives\n\t      whole_archive_flag_spec_CXX='$convenience'\n\t    fi\n\t    archive_cmds_need_lc_CXX=yes\n\t    archive_expsym_cmds_CXX='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d'\n\t    # -brtl affects multiple linker settings, -berok does not and is overridden later\n\t    compiler_flags_filtered='`func_echo_all \"$compiler_flags \" | $SED -e \"s%-brtl\\\\([, ]\\\\)%-berok\\\\1%g\"`'\n\t    if test svr4 != \"$with_aix_soname\"; then\n\t      # This is similar to how AIX traditionally builds its shared\n\t      # libraries. Need -bnortl late, we may have -brtl in LDFLAGS.\n\t      archive_expsym_cmds_CXX=\"$archive_expsym_cmds_CXX\"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname'\n\t    fi\n\t    if test aix != \"$with_aix_soname\"; then\n\t      archive_expsym_cmds_CXX=\"$archive_expsym_cmds_CXX\"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all \"#! $soname($shared_archive_member_spec.o)\"; if test shr_64 = \"$shared_archive_member_spec\"; then func_echo_all \"# 64\"; else func_echo_all \"# 32\"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp'\n\t    else\n\t      # used by -dlpreopen to get the symbols\n\t      archive_expsym_cmds_CXX=\"$archive_expsym_cmds_CXX\"'~$MV  $output_objdir/$realname.d/$soname $output_objdir'\n\t    fi\n\t    archive_expsym_cmds_CXX=\"$archive_expsym_cmds_CXX\"'~$RM -r $output_objdir/$realname.d'\n          fi\n        fi\n        ;;\n\n      beos*)\n\tif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\t  allow_undefined_flag_CXX=unsupported\n\t  # Joseph Beckenbach <jrb3@best.com> says some releases of gcc\n\t  # support --undefined.  This deserves some investigation.  FIXME\n\t  archive_cmds_CXX='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\telse\n\t  ld_shlibs_CXX=no\n\tfi\n\t;;\n\n      chorus*)\n        case $cc_basename in\n          *)\n\t  # FIXME: insert proper C++ library support\n\t  ld_shlibs_CXX=no\n\t  ;;\n        esac\n        ;;\n\n      cygwin* | mingw* | pw32* | cegcc*)\n\tcase $GXX,$cc_basename in\n\t,cl* | no,cl* | ,icl* | no,icl*)\n\t  # Native MSVC or ICC\n\t  # hardcode_libdir_flag_spec is actually meaningless, as there is\n\t  # no search path for DLLs.\n\t  hardcode_libdir_flag_spec_CXX=' '\n\t  allow_undefined_flag_CXX=unsupported\n\t  always_export_symbols_CXX=yes\n\t  file_list_spec_CXX='@'\n\t  # Tell ltmain to make .lib files, not .a files.\n\t  libext=lib\n\t  # Tell ltmain to make .dll files, not .so files.\n\t  shrext_cmds=.dll\n\t  # FIXME: Setting linknames here is a bad hack.\n\t  archive_cmds_CXX='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:\"$tool_output_objdir$libname.dll.lib\"~linknames='\n\t  archive_expsym_cmds_CXX='if   test DEF = \"`$SED -n     -e '\\''s/^[\t ]*//'\\''     -e '\\''/^\\(;.*\\)*$/d'\\''     -e '\\''s/^\\(EXPORTS\\|LIBRARY\\)\\([\t ].*\\)*$/DEF/p'\\''     -e q     $export_symbols`\" ; then\n              cp \"$export_symbols\" \"$output_objdir/$soname.def\";\n              echo \"$tool_output_objdir$soname.def\" > \"$output_objdir/$soname.exp\";\n            else\n              $SED -e '\\''s/^/-link -EXPORT:/'\\'' < $export_symbols > $output_objdir/$soname.exp;\n            fi~\n            $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs \"@$tool_output_objdir$soname.exp\" -Wl,-DLL,-IMPLIB:\"$tool_output_objdir$libname.dll.lib\"~\n            linknames='\n\t  # The linker will not automatically build a static lib if we build a DLL.\n\t  # _LT_TAGVAR(old_archive_from_new_cmds, CXX)='true'\n\t  enable_shared_with_static_runtimes_CXX=yes\n\t  # Don't use ranlib\n\t  old_postinstall_cmds_CXX='chmod 644 $oldlib'\n\t  postlink_cmds_CXX='lt_outputfile=\"@OUTPUT@\"~\n            lt_tool_outputfile=\"@TOOL_OUTPUT@\"~\n            case $lt_outputfile in\n              *.exe|*.EXE) ;;\n              *)\n                lt_outputfile=$lt_outputfile.exe\n                lt_tool_outputfile=$lt_tool_outputfile.exe\n                ;;\n            esac~\n            func_to_tool_file \"$lt_outputfile\"~\n            if test : != \"$MANIFEST_TOOL\" && test -f \"$lt_outputfile.manifest\"; then\n              $MANIFEST_TOOL -manifest \"$lt_tool_outputfile.manifest\" -outputresource:\"$lt_tool_outputfile\" || exit 1;\n              $RM \"$lt_outputfile.manifest\";\n            fi'\n\t  ;;\n\t*)\n\t  # g++\n\t  # _LT_TAGVAR(hardcode_libdir_flag_spec, CXX) is actually meaningless,\n\t  # as there is no search path for DLLs.\n\t  hardcode_libdir_flag_spec_CXX='-L$libdir'\n\t  export_dynamic_flag_spec_CXX='$wl--export-all-symbols'\n\t  allow_undefined_flag_CXX=unsupported\n\t  always_export_symbols_CXX=no\n\t  enable_shared_with_static_runtimes_CXX=yes\n\n\t  if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then\n\t    archive_cmds_CXX='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib'\n\t    # If the export-symbols file already is a .def file, use it as\n\t    # is; otherwise, prepend EXPORTS...\n\t    archive_expsym_cmds_CXX='if   test DEF = \"`$SED -n     -e '\\''s/^[\t ]*//'\\''     -e '\\''/^\\(;.*\\)*$/d'\\''     -e '\\''s/^\\(EXPORTS\\|LIBRARY\\)\\([\t ].*\\)*$/DEF/p'\\''     -e q     $export_symbols`\" ; then\n              cp $export_symbols $output_objdir/$soname.def;\n            else\n              echo EXPORTS > $output_objdir/$soname.def;\n              cat $export_symbols >> $output_objdir/$soname.def;\n            fi~\n            $CC -shared -nostdlib $output_objdir/$soname.def $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib'\n\t  else\n\t    ld_shlibs_CXX=no\n\t  fi\n\t  ;;\n\tesac\n\t;;\n      darwin* | rhapsody*)\n\n\n  archive_cmds_need_lc_CXX=no\n  hardcode_direct_CXX=no\n  hardcode_automatic_CXX=yes\n  hardcode_shlibpath_var_CXX=unsupported\n  if test yes = \"$lt_cv_ld_force_load\"; then\n    whole_archive_flag_spec_CXX='`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience $wl-force_load,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"`'\n\n  else\n    whole_archive_flag_spec_CXX=''\n  fi\n  link_all_deplibs_CXX=yes\n  allow_undefined_flag_CXX=$_lt_dar_allow_undefined\n  case $cc_basename in\n     ifort*|nagfor*) _lt_dar_can_shared=yes ;;\n     *) _lt_dar_can_shared=$GCC ;;\n  esac\n  if test yes = \"$_lt_dar_can_shared\"; then\n    output_verbose_link_cmd=func_echo_all\n    archive_cmds_CXX=\"\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$libobjs \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring $_lt_dar_single_mod$_lt_dsymutil\"\n    module_cmds_CXX=\"\\$CC \\$allow_undefined_flag -o \\$lib -bundle \\$libobjs \\$deplibs \\$compiler_flags$_lt_dsymutil\"\n    archive_expsym_cmds_CXX=\"$SED 's|^|_|' < \\$export_symbols > \\$output_objdir/\\$libname-symbols.expsym~\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$libobjs \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring $_lt_dar_single_mod$_lt_dar_export_syms$_lt_dsymutil\"\n    module_expsym_cmds_CXX=\"$SED -e 's|^|_|' < \\$export_symbols > \\$output_objdir/\\$libname-symbols.expsym~\\$CC \\$allow_undefined_flag -o \\$lib -bundle \\$libobjs \\$deplibs \\$compiler_flags$_lt_dar_export_syms$_lt_dsymutil\"\n       if test yes != \"$lt_cv_apple_cc_single_mod\"; then\n      archive_cmds_CXX=\"\\$CC -r -keep_private_externs -nostdlib -o \\$lib-master.o \\$libobjs~\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$lib-master.o \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring$_lt_dsymutil\"\n      archive_expsym_cmds_CXX=\"$SED 's|^|_|' < \\$export_symbols > \\$output_objdir/\\$libname-symbols.expsym~\\$CC -r -keep_private_externs -nostdlib -o \\$lib-master.o \\$libobjs~\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$lib-master.o \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring$_lt_dar_export_syms$_lt_dsymutil\"\n    fi\n\n  else\n  ld_shlibs_CXX=no\n  fi\n\n\t;;\n\n      os2*)\n\thardcode_libdir_flag_spec_CXX='-L$libdir'\n\thardcode_minus_L_CXX=yes\n\tallow_undefined_flag_CXX=unsupported\n\tshrext_cmds=.dll\n\tarchive_cmds_CXX='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t  $ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t  $ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t  $ECHO EXPORTS >> $output_objdir/$libname.def~\n\t  emxexp $libobjs | $SED /\"_DLL_InitTerm\"/d >> $output_objdir/$libname.def~\n\t  $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\t  emximp -o $lib $output_objdir/$libname.def'\n\tarchive_expsym_cmds_CXX='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t  $ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t  $ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t  $ECHO EXPORTS >> $output_objdir/$libname.def~\n\t  prefix_cmds=\"$SED\"~\n\t  if test EXPORTS = \"`$SED 1q $export_symbols`\"; then\n\t    prefix_cmds=\"$prefix_cmds -e 1d\";\n\t  fi~\n\t  prefix_cmds=\"$prefix_cmds -e \\\"s/^\\(.*\\)$/_\\1/g\\\"\"~\n\t  cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~\n\t  $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\t  emximp -o $lib $output_objdir/$libname.def'\n\told_archive_From_new_cmds_CXX='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def'\n\tenable_shared_with_static_runtimes_CXX=yes\n\tfile_list_spec_CXX='@'\n\t;;\n\n      dgux*)\n        case $cc_basename in\n          ec++*)\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n          ghcx*)\n\t    # Green Hills C++ Compiler\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n          *)\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n        esac\n        ;;\n\n      freebsd2.*)\n        # C++ shared libraries reported to be fairly broken before\n\t# switch to ELF\n        ld_shlibs_CXX=no\n        ;;\n\n      freebsd-elf*)\n        archive_cmds_need_lc_CXX=no\n        ;;\n\n      freebsd* | dragonfly* | midnightbsd*)\n        # FreeBSD 3 and later use GNU C++ and GNU ld with standard ELF\n        # conventions\n        ld_shlibs_CXX=yes\n        ;;\n\n      haiku*)\n        archive_cmds_CXX='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n        link_all_deplibs_CXX=yes\n        ;;\n\n      hpux9*)\n        hardcode_libdir_flag_spec_CXX='$wl+b $wl$libdir'\n        hardcode_libdir_separator_CXX=:\n        export_dynamic_flag_spec_CXX='$wl-E'\n        hardcode_direct_CXX=yes\n        hardcode_minus_L_CXX=yes # Not in the search PATH,\n\t\t\t\t             # but as the default\n\t\t\t\t             # location of the library.\n\n        case $cc_basename in\n          CC*)\n            # FIXME: insert proper C++ library support\n            ld_shlibs_CXX=no\n            ;;\n          aCC*)\n            archive_cmds_CXX='$RM $output_objdir/$soname~$CC -b $wl+b $wl$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test \"x$output_objdir/$soname\" = \"x$lib\" || mv $output_objdir/$soname $lib'\n            # Commands to make compiler produce verbose output that lists\n            # what \"hidden\" libraries, object files and flags are used when\n            # linking a shared library.\n            #\n            # There doesn't appear to be a way to prevent this compiler from\n            # explicitly linking system object files so we need to strip them\n            # from the output so that they don't get included in the library\n            # dependencies.\n            output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $EGREP \"\\-L\"`; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"$list\"'\n            ;;\n          *)\n            if test yes = \"$GXX\"; then\n              archive_cmds_CXX='$RM $output_objdir/$soname~$CC -shared -nostdlib $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test \"x$output_objdir/$soname\" = \"x$lib\" || mv $output_objdir/$soname $lib'\n            else\n              # FIXME: insert proper C++ library support\n              ld_shlibs_CXX=no\n            fi\n            ;;\n        esac\n        ;;\n\n      hpux10*|hpux11*)\n        if test no = \"$with_gnu_ld\"; then\n\t  hardcode_libdir_flag_spec_CXX='$wl+b $wl$libdir'\n\t  hardcode_libdir_separator_CXX=:\n\n          case $host_cpu in\n            hppa*64*|ia64*)\n              ;;\n            *)\n\t      export_dynamic_flag_spec_CXX='$wl-E'\n              ;;\n          esac\n        fi\n        case $host_cpu in\n          hppa*64*|ia64*)\n            hardcode_direct_CXX=no\n            hardcode_shlibpath_var_CXX=no\n            ;;\n          *)\n            hardcode_direct_CXX=yes\n            hardcode_direct_absolute_CXX=yes\n            hardcode_minus_L_CXX=yes # Not in the search PATH,\n\t\t\t\t\t         # but as the default\n\t\t\t\t\t         # location of the library.\n            ;;\n        esac\n\n        case $cc_basename in\n          CC*)\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n          aCC*)\n\t    case $host_cpu in\n\t      hppa*64*)\n\t        archive_cmds_CXX='$CC -b $wl+h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t        ;;\n\t      ia64*)\n\t        archive_cmds_CXX='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t        ;;\n\t      *)\n\t        archive_cmds_CXX='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t        ;;\n\t    esac\n\t    # Commands to make compiler produce verbose output that lists\n\t    # what \"hidden\" libraries, object files and flags are used when\n\t    # linking a shared library.\n\t    #\n\t    # There doesn't appear to be a way to prevent this compiler from\n\t    # explicitly linking system object files so we need to strip them\n\t    # from the output so that they don't get included in the library\n\t    # dependencies.\n\t    output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $GREP \"\\-L\"`; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"$list\"'\n\t    ;;\n          *)\n\t    if test yes = \"$GXX\"; then\n\t      if test no = \"$with_gnu_ld\"; then\n\t        case $host_cpu in\n\t          hppa*64*)\n\t            archive_cmds_CXX='$CC -shared -nostdlib -fPIC $wl+h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t            ;;\n\t          ia64*)\n\t            archive_cmds_CXX='$CC -shared -nostdlib $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t            ;;\n\t          *)\n\t            archive_cmds_CXX='$CC -shared -nostdlib $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t            ;;\n\t        esac\n\t      fi\n\t    else\n\t      # FIXME: insert proper C++ library support\n\t      ld_shlibs_CXX=no\n\t    fi\n\t    ;;\n        esac\n        ;;\n\n      interix[3-9]*)\n\thardcode_direct_CXX=no\n\thardcode_shlibpath_var_CXX=no\n\thardcode_libdir_flag_spec_CXX='$wl-rpath,$libdir'\n\texport_dynamic_flag_spec_CXX='$wl-E'\n\t# Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc.\n\t# Instead, shared libraries are loaded at an image base (0x10000000 by\n\t# default) and relocated if they conflict, which is a slow very memory\n\t# consuming and fragmenting process.  To avoid this, we pick a random,\n\t# 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link\n\t# time.  Moving up from 0x10000000 also allows more sbrk(2) space.\n\tarchive_cmds_CXX='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \\* 262144 + 1342177280` -o $lib'\n\tarchive_expsym_cmds_CXX='$SED \"s|^|_|\" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \\* 262144 + 1342177280` -o $lib'\n\t;;\n      irix5* | irix6*)\n        case $cc_basename in\n          CC*)\n\t    # SGI C++\n\t    archive_cmds_CXX='$CC -shared -all -multigot $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\n\t    # Archives containing C++ object files must be created using\n\t    # \"CC -ar\", where \"CC\" is the IRIX C++ compiler.  This is\n\t    # necessary to make sure instantiated templates are included\n\t    # in the archive.\n\t    old_archive_cmds_CXX='$CC -ar -WR,-u -o $oldlib $oldobjs'\n\t    ;;\n          *)\n\t    if test yes = \"$GXX\"; then\n\t      if test no = \"$with_gnu_ld\"; then\n\t        archive_cmds_CXX='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t      else\n\t        archive_cmds_CXX='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` -o $lib'\n\t      fi\n\t    fi\n\t    link_all_deplibs_CXX=yes\n\t    ;;\n        esac\n        hardcode_libdir_flag_spec_CXX='$wl-rpath $wl$libdir'\n        hardcode_libdir_separator_CXX=:\n        inherit_rpath_CXX=yes\n        ;;\n\n      linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n        case $cc_basename in\n          KCC*)\n\t    # Kuck and Associates, Inc. (KAI) C++ Compiler\n\n\t    # KCC will only create a shared library if the output file\n\t    # ends with \".so\" (or \".sl\" for HP-UX), so rename the library\n\t    # to its proper name (with version) after linking.\n\t    archive_cmds_CXX='tempext=`echo $shared_ext | $SED -e '\\''s/\\([^()0-9A-Za-z{}]\\)/\\\\\\\\\\1/g'\\''`; templib=`echo $lib | $SED -e \"s/\\$tempext\\..*/.so/\"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \\$templib; mv \\$templib $lib'\n\t    archive_expsym_cmds_CXX='tempext=`echo $shared_ext | $SED -e '\\''s/\\([^()0-9A-Za-z{}]\\)/\\\\\\\\\\1/g'\\''`; templib=`echo $lib | $SED -e \"s/\\$tempext\\..*/.so/\"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \\$templib $wl-retain-symbols-file,$export_symbols; mv \\$templib $lib'\n\t    # Commands to make compiler produce verbose output that lists\n\t    # what \"hidden\" libraries, object files and flags are used when\n\t    # linking a shared library.\n\t    #\n\t    # There doesn't appear to be a way to prevent this compiler from\n\t    # explicitly linking system object files so we need to strip them\n\t    # from the output so that they don't get included in the library\n\t    # dependencies.\n\t    output_verbose_link_cmd='templist=`$CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 | $GREP \"ld\"`; rm -f libconftest$shared_ext; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"$list\"'\n\n\t    hardcode_libdir_flag_spec_CXX='$wl-rpath,$libdir'\n\t    export_dynamic_flag_spec_CXX='$wl--export-dynamic'\n\n\t    # Archives containing C++ object files must be created using\n\t    # \"CC -Bstatic\", where \"CC\" is the KAI C++ compiler.\n\t    old_archive_cmds_CXX='$CC -Bstatic -o $oldlib $oldobjs'\n\t    ;;\n\t  icpc* | ecpc* )\n\t    # Intel C++\n\t    with_gnu_ld=yes\n\t    # version 8.0 and above of icpc choke on multiply defined symbols\n\t    # if we add $predep_objects and $postdep_objects, however 7.1 and\n\t    # earlier do not add the objects themselves.\n\t    case `$CC -V 2>&1` in\n\t      *\"Version 7.\"*)\n\t        archive_cmds_CXX='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n\t\tarchive_expsym_cmds_CXX='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t\t;;\n\t      *)  # Version 8.0 or newer\n\t        tmp_idyn=\n\t        case $host_cpu in\n\t\t  ia64*) tmp_idyn=' -i_dynamic';;\n\t\tesac\n\t        archive_cmds_CXX='$CC -shared'\"$tmp_idyn\"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t\tarchive_expsym_cmds_CXX='$CC -shared'\"$tmp_idyn\"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t\t;;\n\t    esac\n\t    archive_cmds_need_lc_CXX=no\n\t    hardcode_libdir_flag_spec_CXX='$wl-rpath,$libdir'\n\t    export_dynamic_flag_spec_CXX='$wl--export-dynamic'\n\t    whole_archive_flag_spec_CXX='$wl--whole-archive$convenience $wl--no-whole-archive'\n\t    ;;\n          pgCC* | pgcpp*)\n            # Portland Group C++ compiler\n\t    case `$CC -V` in\n\t    *pgCC\\ [1-5].* | *pgcpp\\ [1-5].*)\n\t      prelink_cmds_CXX='tpldir=Template.dir~\n               rm -rf $tpldir~\n               $CC --prelink_objects --instantiation_dir $tpldir $objs $libobjs $compile_deplibs~\n               compile_command=\"$compile_command `find $tpldir -name \\*.o | sort | $NL2SP`\"'\n\t      old_archive_cmds_CXX='tpldir=Template.dir~\n                rm -rf $tpldir~\n                $CC --prelink_objects --instantiation_dir $tpldir $oldobjs$old_deplibs~\n                $AR $AR_FLAGS $oldlib$oldobjs$old_deplibs `find $tpldir -name \\*.o | sort | $NL2SP`~\n                $RANLIB $oldlib'\n\t      archive_cmds_CXX='tpldir=Template.dir~\n                rm -rf $tpldir~\n                $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~\n                $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \\*.o | sort | $NL2SP` $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n\t      archive_expsym_cmds_CXX='tpldir=Template.dir~\n                rm -rf $tpldir~\n                $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~\n                $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \\*.o | sort | $NL2SP` $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t      ;;\n\t    *) # Version 6 and above use weak symbols\n\t      archive_cmds_CXX='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n\t      archive_expsym_cmds_CXX='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t      ;;\n\t    esac\n\n\t    hardcode_libdir_flag_spec_CXX='$wl--rpath $wl$libdir'\n\t    export_dynamic_flag_spec_CXX='$wl--export-dynamic'\n\t    whole_archive_flag_spec_CXX='$wl--whole-archive`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n            ;;\n\t  cxx*)\n\t    # Compaq C++\n\t    archive_cmds_CXX='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n\t    archive_expsym_cmds_CXX='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname  -o $lib $wl-retain-symbols-file $wl$export_symbols'\n\n\t    runpath_var=LD_RUN_PATH\n\t    hardcode_libdir_flag_spec_CXX='-rpath $libdir'\n\t    hardcode_libdir_separator_CXX=:\n\n\t    # Commands to make compiler produce verbose output that lists\n\t    # what \"hidden\" libraries, object files and flags are used when\n\t    # linking a shared library.\n\t    #\n\t    # There doesn't appear to be a way to prevent this compiler from\n\t    # explicitly linking system object files so we need to strip them\n\t    # from the output so that they don't get included in the library\n\t    # dependencies.\n\t    output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP \"ld\"`; templist=`func_echo_all \"$templist\" | $SED \"s/\\(^.*ld.*\\)\\( .*ld .*$\\)/\\1/\"`; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"X$list\" | $Xsed'\n\t    ;;\n\t  xl* | mpixl* | bgxl*)\n\t    # IBM XL 8.0 on PPC, with GNU ld\n\t    hardcode_libdir_flag_spec_CXX='$wl-rpath $wl$libdir'\n\t    export_dynamic_flag_spec_CXX='$wl--export-dynamic'\n\t    archive_cmds_CXX='$CC -qmkshrobj $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t    if test yes = \"$supports_anon_versioning\"; then\n\t      archive_expsym_cmds_CXX='echo \"{ global:\" > $output_objdir/$libname.ver~\n                cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $output_objdir/$libname.ver~\n                echo \"local: *; };\" >> $output_objdir/$libname.ver~\n                $CC -qmkshrobj $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib'\n\t    fi\n\t    ;;\n\t  *)\n\t    case `$CC -V 2>&1 | $SED 5q` in\n\t    *Sun\\ C*)\n\t      # Sun C++ 5.9\n\t      no_undefined_flag_CXX=' -zdefs'\n\t      archive_cmds_CXX='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t      archive_expsym_cmds_CXX='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-retain-symbols-file $wl$export_symbols'\n\t      hardcode_libdir_flag_spec_CXX='-R$libdir'\n\t      whole_archive_flag_spec_CXX='$wl--whole-archive`new_convenience=; for conv in $convenience\\\"\\\"; do test -z \\\"$conv\\\" || new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t      compiler_needs_object_CXX=yes\n\n\t      # Not sure whether something based on\n\t      # $CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1\n\t      # would be better.\n\t      output_verbose_link_cmd='func_echo_all'\n\n\t      # Archives containing C++ object files must be created using\n\t      # \"CC -xar\", where \"CC\" is the Sun C++ compiler.  This is\n\t      # necessary to make sure instantiated templates are included\n\t      # in the archive.\n\t      old_archive_cmds_CXX='$CC -xar -o $oldlib $oldobjs'\n\t      ;;\n\t    esac\n\t    ;;\n\tesac\n\t;;\n\n      lynxos*)\n        # FIXME: insert proper C++ library support\n\tld_shlibs_CXX=no\n\t;;\n\n      m88k*)\n        # FIXME: insert proper C++ library support\n        ld_shlibs_CXX=no\n\t;;\n\n      mvs*)\n        case $cc_basename in\n          cxx*)\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n\t  *)\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n\tesac\n\t;;\n\n      netbsd*)\n        if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n\t  archive_cmds_CXX='$LD -Bshareable  -o $lib $predep_objects $libobjs $deplibs $postdep_objects $linker_flags'\n\t  wlarc=\n\t  hardcode_libdir_flag_spec_CXX='-R$libdir'\n\t  hardcode_direct_CXX=yes\n\t  hardcode_shlibpath_var_CXX=no\n\tfi\n\t# Workaround some broken pre-1.5 toolchains\n\toutput_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP conftest.$objext | $SED -e \"s:-lgcc -lc -lgcc::\"'\n\t;;\n\n      *nto* | *qnx*)\n        ld_shlibs_CXX=yes\n\t;;\n\n      openbsd* | bitrig*)\n\tif test -f /usr/libexec/ld.so; then\n\t  hardcode_direct_CXX=yes\n\t  hardcode_shlibpath_var_CXX=no\n\t  hardcode_direct_absolute_CXX=yes\n\t  archive_cmds_CXX='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $lib'\n\t  hardcode_libdir_flag_spec_CXX='$wl-rpath,$libdir'\n\t  if test -z \"`echo __ELF__ | $CC -E - | grep __ELF__`\"; then\n\t    archive_expsym_cmds_CXX='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-retain-symbols-file,$export_symbols -o $lib'\n\t    export_dynamic_flag_spec_CXX='$wl-E'\n\t    whole_archive_flag_spec_CXX=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive'\n\t  fi\n\t  output_verbose_link_cmd=func_echo_all\n\telse\n\t  ld_shlibs_CXX=no\n\tfi\n\t;;\n\n      osf3* | osf4* | osf5*)\n        case $cc_basename in\n          KCC*)\n\t    # Kuck and Associates, Inc. (KAI) C++ Compiler\n\n\t    # KCC will only create a shared library if the output file\n\t    # ends with \".so\" (or \".sl\" for HP-UX), so rename the library\n\t    # to its proper name (with version) after linking.\n\t    archive_cmds_CXX='tempext=`echo $shared_ext | $SED -e '\\''s/\\([^()0-9A-Za-z{}]\\)/\\\\\\\\\\1/g'\\''`; templib=`echo \"$lib\" | $SED -e \"s/\\$tempext\\..*/.so/\"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \\$templib; mv \\$templib $lib'\n\n\t    hardcode_libdir_flag_spec_CXX='$wl-rpath,$libdir'\n\t    hardcode_libdir_separator_CXX=:\n\n\t    # Archives containing C++ object files must be created using\n\t    # the KAI C++ compiler.\n\t    case $host in\n\t      osf3*) old_archive_cmds_CXX='$CC -Bstatic -o $oldlib $oldobjs' ;;\n\t      *) old_archive_cmds_CXX='$CC -o $oldlib $oldobjs' ;;\n\t    esac\n\t    ;;\n          RCC*)\n\t    # Rational C++ 2.4.1\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n          cxx*)\n\t    case $host in\n\t      osf3*)\n\t        allow_undefined_flag_CXX=' $wl-expect_unresolved $wl\\*'\n\t        archive_cmds_CXX='$CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\t        hardcode_libdir_flag_spec_CXX='$wl-rpath $wl$libdir'\n\t\t;;\n\t      *)\n\t        allow_undefined_flag_CXX=' -expect_unresolved \\*'\n\t        archive_cmds_CXX='$CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\t        archive_expsym_cmds_CXX='for i in `cat $export_symbols`; do printf \"%s %s\\\\n\" -exported_symbol \"\\$i\" >> $lib.exp; done~\n                  echo \"-hidden\">> $lib.exp~\n                  $CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname $wl-input $wl$lib.exp  `test -n \"$verstring\" && $ECHO \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib~\n                  $RM $lib.exp'\n\t        hardcode_libdir_flag_spec_CXX='-rpath $libdir'\n\t\t;;\n\t    esac\n\n\t    hardcode_libdir_separator_CXX=:\n\n\t    # Commands to make compiler produce verbose output that lists\n\t    # what \"hidden\" libraries, object files and flags are used when\n\t    # linking a shared library.\n\t    #\n\t    # There doesn't appear to be a way to prevent this compiler from\n\t    # explicitly linking system object files so we need to strip them\n\t    # from the output so that they don't get included in the library\n\t    # dependencies.\n\t    output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP \"ld\" | $GREP -v \"ld:\"`; templist=`func_echo_all \"$templist\" | $SED \"s/\\(^.*ld.*\\)\\( .*ld.*$\\)/\\1/\"`; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"$list\"'\n\t    ;;\n\t  *)\n\t    if test yes,no = \"$GXX,$with_gnu_ld\"; then\n\t      allow_undefined_flag_CXX=' $wl-expect_unresolved $wl\\*'\n\t      case $host in\n\t        osf3*)\n\t          archive_cmds_CXX='$CC -shared -nostdlib $allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t\t  ;;\n\t        *)\n\t          archive_cmds_CXX='$CC -shared $pic_flag -nostdlib $allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-msym $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t\t  ;;\n\t      esac\n\n\t      hardcode_libdir_flag_spec_CXX='$wl-rpath $wl$libdir'\n\t      hardcode_libdir_separator_CXX=:\n\n\t      # Commands to make compiler produce verbose output that lists\n\t      # what \"hidden\" libraries, object files and flags are used when\n\t      # linking a shared library.\n\t      output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v \"^Configured with:\" | $GREP \"\\-L\"'\n\n\t    else\n\t      # FIXME: insert proper C++ library support\n\t      ld_shlibs_CXX=no\n\t    fi\n\t    ;;\n        esac\n        ;;\n\n      psos*)\n        # FIXME: insert proper C++ library support\n        ld_shlibs_CXX=no\n        ;;\n\n      sunos4*)\n        case $cc_basename in\n          CC*)\n\t    # Sun C++ 4.x\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n          lcc*)\n\t    # Lucid\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n          *)\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n        esac\n        ;;\n\n      solaris*)\n        case $cc_basename in\n          CC* | sunCC*)\n\t    # Sun C++ 4.2, 5.x and Centerline C++\n            archive_cmds_need_lc_CXX=yes\n\t    no_undefined_flag_CXX=' -zdefs'\n\t    archive_cmds_CXX='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t    archive_expsym_cmds_CXX='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n              $CC -G$allow_undefined_flag $wl-M $wl$lib.exp -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp'\n\n\t    hardcode_libdir_flag_spec_CXX='-R$libdir'\n\t    hardcode_shlibpath_var_CXX=no\n\t    case $host_os in\n\t      solaris2.[0-5] | solaris2.[0-5].*) ;;\n\t      *)\n\t\t# The compiler driver will combine and reorder linker options,\n\t\t# but understands '-z linker_flag'.\n\t        # Supported since Solaris 2.6 (maybe 2.5.1?)\n\t\twhole_archive_flag_spec_CXX='-z allextract$convenience -z defaultextract'\n\t        ;;\n\t    esac\n\t    link_all_deplibs_CXX=yes\n\n\t    output_verbose_link_cmd='func_echo_all'\n\n\t    # Archives containing C++ object files must be created using\n\t    # \"CC -xar\", where \"CC\" is the Sun C++ compiler.  This is\n\t    # necessary to make sure instantiated templates are included\n\t    # in the archive.\n\t    old_archive_cmds_CXX='$CC -xar -o $oldlib $oldobjs'\n\t    ;;\n          gcx*)\n\t    # Green Hills C++ Compiler\n\t    archive_cmds_CXX='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib'\n\n\t    # The C++ compiler must be used to create the archive.\n\t    old_archive_cmds_CXX='$CC $LDFLAGS -archive -o $oldlib $oldobjs'\n\t    ;;\n          *)\n\t    # GNU C++ compiler with Solaris linker\n\t    if test yes,no = \"$GXX,$with_gnu_ld\"; then\n\t      no_undefined_flag_CXX=' $wl-z ${wl}defs'\n\t      if $CC --version | $GREP -v '^2\\.7' > /dev/null; then\n\t        archive_cmds_CXX='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib'\n\t        archive_expsym_cmds_CXX='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n                  $CC -shared $pic_flag -nostdlib $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp'\n\n\t        # Commands to make compiler produce verbose output that lists\n\t        # what \"hidden\" libraries, object files and flags are used when\n\t        # linking a shared library.\n\t        output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v \"^Configured with:\" | $GREP \"\\-L\"'\n\t      else\n\t        # g++ 2.7 appears to require '-G' NOT '-shared' on this\n\t        # platform.\n\t        archive_cmds_CXX='$CC -G -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib'\n\t        archive_expsym_cmds_CXX='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n                  $CC -G -nostdlib $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp'\n\n\t        # Commands to make compiler produce verbose output that lists\n\t        # what \"hidden\" libraries, object files and flags are used when\n\t        # linking a shared library.\n\t        output_verbose_link_cmd='$CC -G $CFLAGS -v conftest.$objext 2>&1 | $GREP -v \"^Configured with:\" | $GREP \"\\-L\"'\n\t      fi\n\n\t      hardcode_libdir_flag_spec_CXX='$wl-R $wl$libdir'\n\t      case $host_os in\n\t\tsolaris2.[0-5] | solaris2.[0-5].*) ;;\n\t\t*)\n\t\t  whole_archive_flag_spec_CXX='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract'\n\t\t  ;;\n\t      esac\n\t    fi\n\t    ;;\n        esac\n        ;;\n\n    sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[01].[10]* | unixware7* | sco3.2v5.0.[024]*)\n      no_undefined_flag_CXX='$wl-z,text'\n      archive_cmds_need_lc_CXX=no\n      hardcode_shlibpath_var_CXX=no\n      runpath_var='LD_RUN_PATH'\n\n      case $cc_basename in\n        CC*)\n\t  archive_cmds_CXX='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  archive_expsym_cmds_CXX='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\t*)\n\t  archive_cmds_CXX='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  archive_expsym_cmds_CXX='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n      esac\n      ;;\n\n      sysv5* | sco3.2v5* | sco5v6*)\n\t# Note: We CANNOT use -z defs as we might desire, because we do not\n\t# link with -lc, and that would cause any symbols used from libc to\n\t# always be unresolved, which means just about no library would\n\t# ever link correctly.  If we're not using GNU ld we use -z text\n\t# though, which does catch some bad symbols but isn't as heavy-handed\n\t# as -z defs.\n\tno_undefined_flag_CXX='$wl-z,text'\n\tallow_undefined_flag_CXX='$wl-z,nodefs'\n\tarchive_cmds_need_lc_CXX=no\n\thardcode_shlibpath_var_CXX=no\n\thardcode_libdir_flag_spec_CXX='$wl-R,$libdir'\n\thardcode_libdir_separator_CXX=':'\n\tlink_all_deplibs_CXX=yes\n\texport_dynamic_flag_spec_CXX='$wl-Bexport'\n\trunpath_var='LD_RUN_PATH'\n\n\tcase $cc_basename in\n          CC*)\n\t    archive_cmds_CXX='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t    archive_expsym_cmds_CXX='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t    old_archive_cmds_CXX='$CC -Tprelink_objects $oldobjs~\n              '\"$old_archive_cmds_CXX\"\n\t    reload_cmds_CXX='$CC -Tprelink_objects $reload_objs~\n              '\"$reload_cmds_CXX\"\n\t    ;;\n\t  *)\n\t    archive_cmds_CXX='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t    archive_expsym_cmds_CXX='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t    ;;\n\tesac\n      ;;\n\n      tandem*)\n        case $cc_basename in\n          NCC*)\n\t    # NonStop-UX NCC 3.20\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n          *)\n\t    # FIXME: insert proper C++ library support\n\t    ld_shlibs_CXX=no\n\t    ;;\n        esac\n        ;;\n\n      vxworks*)\n        # FIXME: insert proper C++ library support\n        ld_shlibs_CXX=no\n        ;;\n\n      *)\n        # FIXME: insert proper C++ library support\n        ld_shlibs_CXX=no\n        ;;\n    esac\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ld_shlibs_CXX\" >&5\nprintf \"%s\\n\" \"$ld_shlibs_CXX\" >&6; }\n    test no = \"$ld_shlibs_CXX\" && can_build_shared=no\n\n    GCC_CXX=$GXX\n    LD_CXX=$LD\n\n    ## CAVEAT EMPTOR:\n    ## There is no encapsulation within the following macros, do not change\n    ## the running order or otherwise move them around unless you know exactly\n    ## what you are doing...\n    # Dependencies to place before and after the object being linked:\npredep_objects_CXX=\npostdep_objects_CXX=\npredeps_CXX=\npostdeps_CXX=\ncompiler_lib_search_path_CXX=\n\ncat > conftest.$ac_ext <<_LT_EOF\nclass Foo\n{\npublic:\n  Foo (void) { a = 0; }\nprivate:\n  int a;\n};\n_LT_EOF\n\n\n_lt_libdeps_save_CFLAGS=$CFLAGS\ncase \"$CC $CFLAGS \" in #(\n*\\ -flto*\\ *) CFLAGS=\"$CFLAGS -fno-lto\" ;;\n*\\ -fwhopr*\\ *) CFLAGS=\"$CFLAGS -fno-whopr\" ;;\n*\\ -fuse-linker-plugin*\\ *) CFLAGS=\"$CFLAGS -fno-use-linker-plugin\" ;;\nesac\n\nif { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }; then\n  # Parse the compiler output and extract the necessary\n  # objects, libraries and library flags.\n\n  # Sentinel used to keep track of whether or not we are before\n  # the conftest object file.\n  pre_test_object_deps_done=no\n\n  for p in `eval \"$output_verbose_link_cmd\"`; do\n    case $prev$p in\n\n    -L* | -R* | -l*)\n       # Some compilers place space between \"-{L,R}\" and the path.\n       # Remove the space.\n       if test x-L = \"$p\" ||\n          test x-R = \"$p\"; then\n\t prev=$p\n\t continue\n       fi\n\n       # Expand the sysroot to ease extracting the directories later.\n       if test -z \"$prev\"; then\n         case $p in\n         -L*) func_stripname_cnf '-L' '' \"$p\"; prev=-L; p=$func_stripname_result ;;\n         -R*) func_stripname_cnf '-R' '' \"$p\"; prev=-R; p=$func_stripname_result ;;\n         -l*) func_stripname_cnf '-l' '' \"$p\"; prev=-l; p=$func_stripname_result ;;\n         esac\n       fi\n       case $p in\n       =*) func_stripname_cnf '=' '' \"$p\"; p=$lt_sysroot$func_stripname_result ;;\n       esac\n       if test no = \"$pre_test_object_deps_done\"; then\n\t case $prev in\n\t -L | -R)\n\t   # Internal compiler library paths should come after those\n\t   # provided the user.  The postdeps already come after the\n\t   # user supplied libs so there is no need to process them.\n\t   if test -z \"$compiler_lib_search_path_CXX\"; then\n\t     compiler_lib_search_path_CXX=$prev$p\n\t   else\n\t     compiler_lib_search_path_CXX=\"${compiler_lib_search_path_CXX} $prev$p\"\n\t   fi\n\t   ;;\n\t # The \"-l\" case would never come before the object being\n\t # linked, so don't bother handling this case.\n\t esac\n       else\n\t if test -z \"$postdeps_CXX\"; then\n\t   postdeps_CXX=$prev$p\n\t else\n\t   postdeps_CXX=\"${postdeps_CXX} $prev$p\"\n\t fi\n       fi\n       prev=\n       ;;\n\n    *.lto.$objext) ;; # Ignore GCC LTO objects\n    *.$objext)\n       # This assumes that the test object file only shows up\n       # once in the compiler output.\n       if test \"$p\" = \"conftest.$objext\"; then\n\t pre_test_object_deps_done=yes\n\t continue\n       fi\n\n       if test no = \"$pre_test_object_deps_done\"; then\n\t if test -z \"$predep_objects_CXX\"; then\n\t   predep_objects_CXX=$p\n\t else\n\t   predep_objects_CXX=\"$predep_objects_CXX $p\"\n\t fi\n       else\n\t if test -z \"$postdep_objects_CXX\"; then\n\t   postdep_objects_CXX=$p\n\t else\n\t   postdep_objects_CXX=\"$postdep_objects_CXX $p\"\n\t fi\n       fi\n       ;;\n\n    *) ;; # Ignore the rest.\n\n    esac\n  done\n\n  # Clean up.\n  rm -f a.out a.exe\nelse\n  echo \"libtool.m4: error: problem compiling CXX test program\"\nfi\n\n$RM -f confest.$objext\nCFLAGS=$_lt_libdeps_save_CFLAGS\n\n# PORTME: override above test on systems where it is broken\ncase $host_os in\ninterix[3-9]*)\n  # Interix 3.5 installs completely hosed .la files for C++, so rather than\n  # hack all around it, let's just trust \"g++\" to DTRT.\n  predep_objects_CXX=\n  postdep_objects_CXX=\n  postdeps_CXX=\n  ;;\nesac\n\n\ncase \" $postdeps_CXX \" in\n*\" -lc \"*) archive_cmds_need_lc_CXX=no ;;\nesac\n compiler_lib_search_dirs_CXX=\nif test -n \"${compiler_lib_search_path_CXX}\"; then\n compiler_lib_search_dirs_CXX=`echo \" ${compiler_lib_search_path_CXX}\" | $SED -e 's! -L! !g' -e 's!^ !!'`\nfi\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n    lt_prog_compiler_wl_CXX=\nlt_prog_compiler_pic_CXX=\nlt_prog_compiler_static_CXX=\n\n\n  # C++ specific cases for pic, static, wl, etc.\n  if test yes = \"$GXX\"; then\n    lt_prog_compiler_wl_CXX='-Wl,'\n    lt_prog_compiler_static_CXX='-static'\n\n    case $host_os in\n    aix*)\n      # All AIX code is PIC.\n      if test ia64 = \"$host_cpu\"; then\n\t# AIX 5 now supports IA64 processor\n\tlt_prog_compiler_static_CXX='-Bstatic'\n      fi\n      lt_prog_compiler_pic_CXX='-fPIC'\n      ;;\n\n    amigaos*)\n      case $host_cpu in\n      powerpc)\n            # see comment about AmigaOS4 .so support\n            lt_prog_compiler_pic_CXX='-fPIC'\n        ;;\n      m68k)\n            # FIXME: we need at least 68020 code to build shared libraries, but\n            # adding the '-m68020' flag to GCC prevents building anything better,\n            # like '-m68040'.\n            lt_prog_compiler_pic_CXX='-m68020 -resident32 -malways-restore-a4'\n        ;;\n      esac\n      ;;\n\n    beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*)\n      # PIC is the default for these OSes.\n      ;;\n    mingw* | cygwin* | os2* | pw32* | cegcc*)\n      # This hack is so that the source file can tell whether it is being\n      # built for inclusion in a dll (and should export symbols for example).\n      # Although the cygwin gcc ignores -fPIC, still need this for old-style\n      # (--disable-auto-import) libraries\n      lt_prog_compiler_pic_CXX='-DDLL_EXPORT'\n      case $host_os in\n      os2*)\n\tlt_prog_compiler_static_CXX='$wl-static'\n\t;;\n      esac\n      ;;\n    darwin* | rhapsody*)\n      # PIC is the default on this platform\n      # Common symbols not allowed in MH_DYLIB files\n      lt_prog_compiler_pic_CXX='-fno-common'\n      ;;\n    *djgpp*)\n      # DJGPP does not support shared libraries at all\n      lt_prog_compiler_pic_CXX=\n      ;;\n    haiku*)\n      # PIC is the default for Haiku.\n      # The \"-static\" flag exists, but is broken.\n      lt_prog_compiler_static_CXX=\n      ;;\n    interix[3-9]*)\n      # Interix 3.x gcc -fpic/-fPIC options generate broken code.\n      # Instead, we relocate shared libraries at runtime.\n      ;;\n    sysv4*MP*)\n      if test -d /usr/nec; then\n\tlt_prog_compiler_pic_CXX=-Kconform_pic\n      fi\n      ;;\n    hpux*)\n      # PIC is the default for 64-bit PA HP-UX, but not for 32-bit\n      # PA HP-UX.  On IA64 HP-UX, PIC is the default but the pic flag\n      # sets the default TLS model and affects inlining.\n      case $host_cpu in\n      hppa*64*)\n\t;;\n      *)\n\tlt_prog_compiler_pic_CXX='-fPIC'\n\t;;\n      esac\n      ;;\n    *qnx* | *nto*)\n      # QNX uses GNU C++, but need to define -shared option too, otherwise\n      # it will coredump.\n      lt_prog_compiler_pic_CXX='-fPIC -shared'\n      ;;\n    *)\n      lt_prog_compiler_pic_CXX='-fPIC'\n      ;;\n    esac\n  else\n    case $host_os in\n      aix[4-9]*)\n\t# All AIX code is PIC.\n\tif test ia64 = \"$host_cpu\"; then\n\t  # AIX 5 now supports IA64 processor\n\t  lt_prog_compiler_static_CXX='-Bstatic'\n\telse\n\t  lt_prog_compiler_static_CXX='-bnso -bI:/lib/syscalls.exp'\n\tfi\n\t;;\n      chorus*)\n\tcase $cc_basename in\n\tcxch68*)\n\t  # Green Hills C++ Compiler\n\t  # _LT_TAGVAR(lt_prog_compiler_static, CXX)=\"--no_auto_instantiation -u __main -u __premain -u _abort -r $COOL_DIR/lib/libOrb.a $MVME_DIR/lib/CC/libC.a $MVME_DIR/lib/classix/libcx.s.a\"\n\t  ;;\n\tesac\n\t;;\n      mingw* | cygwin* | os2* | pw32* | cegcc*)\n\t# This hack is so that the source file can tell whether it is being\n\t# built for inclusion in a dll (and should export symbols for example).\n\tlt_prog_compiler_pic_CXX='-DDLL_EXPORT'\n\t;;\n      dgux*)\n\tcase $cc_basename in\n\t  ec++*)\n\t    lt_prog_compiler_pic_CXX='-KPIC'\n\t    ;;\n\t  ghcx*)\n\t    # Green Hills C++ Compiler\n\t    lt_prog_compiler_pic_CXX='-pic'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      freebsd* | dragonfly* | midnightbsd*)\n\t# FreeBSD uses GNU C++\n\t;;\n      hpux9* | hpux10* | hpux11*)\n\tcase $cc_basename in\n\t  CC*)\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    lt_prog_compiler_static_CXX='$wl-a ${wl}archive'\n\t    if test ia64 != \"$host_cpu\"; then\n\t      lt_prog_compiler_pic_CXX='+Z'\n\t    fi\n\t    ;;\n\t  aCC*)\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    lt_prog_compiler_static_CXX='$wl-a ${wl}archive'\n\t    case $host_cpu in\n\t    hppa*64*|ia64*)\n\t      # +Z the default\n\t      ;;\n\t    *)\n\t      lt_prog_compiler_pic_CXX='+Z'\n\t      ;;\n\t    esac\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      interix*)\n\t# This is c89, which is MS Visual C++ (no shared libs)\n\t# Anyone wants to do a port?\n\t;;\n      irix5* | irix6* | nonstopux*)\n\tcase $cc_basename in\n\t  CC*)\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    lt_prog_compiler_static_CXX='-non_shared'\n\t    # CC pic flag -KPIC is the default.\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n\tcase $cc_basename in\n\t  KCC*)\n\t    # KAI C++ Compiler\n\t    lt_prog_compiler_wl_CXX='--backend -Wl,'\n\t    lt_prog_compiler_pic_CXX='-fPIC'\n\t    ;;\n\t  ecpc* )\n\t    # old Intel C++ for x86_64, which still supported -KPIC.\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    lt_prog_compiler_pic_CXX='-KPIC'\n\t    lt_prog_compiler_static_CXX='-static'\n\t    ;;\n\t  icpc* )\n\t    # Intel C++, used to be incompatible with GCC.\n\t    # ICC 10 doesn't accept -KPIC any more.\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    lt_prog_compiler_pic_CXX='-fPIC'\n\t    lt_prog_compiler_static_CXX='-static'\n\t    ;;\n\t  pgCC* | pgcpp*)\n\t    # Portland Group C++ compiler\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    lt_prog_compiler_pic_CXX='-fpic'\n\t    lt_prog_compiler_static_CXX='-Bstatic'\n\t    ;;\n\t  cxx*)\n\t    # Compaq C++\n\t    # Make sure the PIC flag is empty.  It appears that all Alpha\n\t    # Linux and Compaq Tru64 Unix objects are PIC.\n\t    lt_prog_compiler_pic_CXX=\n\t    lt_prog_compiler_static_CXX='-non_shared'\n\t    ;;\n\t  xlc* | xlC* | bgxl[cC]* | mpixl[cC]*)\n\t    # IBM XL 8.0, 9.0 on PPC and BlueGene\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    lt_prog_compiler_pic_CXX='-qpic'\n\t    lt_prog_compiler_static_CXX='-qstaticlink'\n\t    ;;\n\t  *)\n\t    case `$CC -V 2>&1 | $SED 5q` in\n\t    *Sun\\ C*)\n\t      # Sun C++ 5.9\n\t      lt_prog_compiler_pic_CXX='-KPIC'\n\t      lt_prog_compiler_static_CXX='-Bstatic'\n\t      lt_prog_compiler_wl_CXX='-Qoption ld '\n\t      ;;\n\t    esac\n\t    ;;\n\tesac\n\t;;\n      lynxos*)\n\t;;\n      m88k*)\n\t;;\n      mvs*)\n\tcase $cc_basename in\n\t  cxx*)\n\t    lt_prog_compiler_pic_CXX='-W c,exportall'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      netbsd*)\n\t;;\n      *qnx* | *nto*)\n        # QNX uses GNU C++, but need to define -shared option too, otherwise\n        # it will coredump.\n        lt_prog_compiler_pic_CXX='-fPIC -shared'\n        ;;\n      osf3* | osf4* | osf5*)\n\tcase $cc_basename in\n\t  KCC*)\n\t    lt_prog_compiler_wl_CXX='--backend -Wl,'\n\t    ;;\n\t  RCC*)\n\t    # Rational C++ 2.4.1\n\t    lt_prog_compiler_pic_CXX='-pic'\n\t    ;;\n\t  cxx*)\n\t    # Digital/Compaq C++\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    # Make sure the PIC flag is empty.  It appears that all Alpha\n\t    # Linux and Compaq Tru64 Unix objects are PIC.\n\t    lt_prog_compiler_pic_CXX=\n\t    lt_prog_compiler_static_CXX='-non_shared'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      psos*)\n\t;;\n      solaris*)\n\tcase $cc_basename in\n\t  CC* | sunCC*)\n\t    # Sun C++ 4.2, 5.x and Centerline C++\n\t    lt_prog_compiler_pic_CXX='-KPIC'\n\t    lt_prog_compiler_static_CXX='-Bstatic'\n\t    lt_prog_compiler_wl_CXX='-Qoption ld '\n\t    ;;\n\t  gcx*)\n\t    # Green Hills C++ Compiler\n\t    lt_prog_compiler_pic_CXX='-PIC'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      sunos4*)\n\tcase $cc_basename in\n\t  CC*)\n\t    # Sun C++ 4.x\n\t    lt_prog_compiler_pic_CXX='-pic'\n\t    lt_prog_compiler_static_CXX='-Bstatic'\n\t    ;;\n\t  lcc*)\n\t    # Lucid\n\t    lt_prog_compiler_pic_CXX='-pic'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*)\n\tcase $cc_basename in\n\t  CC*)\n\t    lt_prog_compiler_wl_CXX='-Wl,'\n\t    lt_prog_compiler_pic_CXX='-KPIC'\n\t    lt_prog_compiler_static_CXX='-Bstatic'\n\t    ;;\n\tesac\n\t;;\n      tandem*)\n\tcase $cc_basename in\n\t  NCC*)\n\t    # NonStop-UX NCC 3.20\n\t    lt_prog_compiler_pic_CXX='-KPIC'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      vxworks*)\n\t;;\n      *)\n\tlt_prog_compiler_can_build_shared_CXX=no\n\t;;\n    esac\n  fi\n\ncase $host_os in\n  # For platforms that do not support PIC, -DPIC is meaningless:\n  *djgpp*)\n    lt_prog_compiler_pic_CXX=\n    ;;\n  *)\n    lt_prog_compiler_pic_CXX=\"$lt_prog_compiler_pic_CXX -DPIC\"\n    ;;\nesac\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $compiler option to produce PIC\" >&5\nprintf %s \"checking for $compiler option to produce PIC... \" >&6; }\nif test ${lt_cv_prog_compiler_pic_CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_pic_CXX=$lt_prog_compiler_pic_CXX ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic_CXX\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_pic_CXX\" >&6; }\nlt_prog_compiler_pic_CXX=$lt_cv_prog_compiler_pic_CXX\n\n#\n# Check to make sure the PIC flag actually works.\n#\nif test -n \"$lt_prog_compiler_pic_CXX\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler PIC flag $lt_prog_compiler_pic_CXX works\" >&5\nprintf %s \"checking if $compiler PIC flag $lt_prog_compiler_pic_CXX works... \" >&6; }\nif test ${lt_cv_prog_compiler_pic_works_CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_pic_works_CXX=no\n   ac_outfile=conftest.$ac_objext\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n   lt_compiler_flag=\"$lt_prog_compiler_pic_CXX -DPIC\"  ## exclude from sc_useless_quotes_in_assignment\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   # The option is referenced via a variable to avoid confusing sed.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [^ ]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&5)\n   (eval \"$lt_compile\" 2>conftest.err)\n   ac_status=$?\n   cat conftest.err >&5\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   if (exit $ac_status) && test -s \"$ac_outfile\"; then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings other than the usual output.\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' >conftest.exp\n     $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2\n     if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then\n       lt_cv_prog_compiler_pic_works_CXX=yes\n     fi\n   fi\n   $RM conftest*\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_pic_works_CXX\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_pic_works_CXX\" >&6; }\n\nif test yes = \"$lt_cv_prog_compiler_pic_works_CXX\"; then\n    case $lt_prog_compiler_pic_CXX in\n     \"\" | \" \"*) ;;\n     *) lt_prog_compiler_pic_CXX=\" $lt_prog_compiler_pic_CXX\" ;;\n     esac\nelse\n    lt_prog_compiler_pic_CXX=\n     lt_prog_compiler_can_build_shared_CXX=no\nfi\n\nfi\n\n\n\n\n\n#\n# Check to make sure the static flag actually works.\n#\nwl=$lt_prog_compiler_wl_CXX eval lt_tmp_static_flag=\\\"$lt_prog_compiler_static_CXX\\\"\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler static flag $lt_tmp_static_flag works\" >&5\nprintf %s \"checking if $compiler static flag $lt_tmp_static_flag works... \" >&6; }\nif test ${lt_cv_prog_compiler_static_works_CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_static_works_CXX=no\n   save_LDFLAGS=$LDFLAGS\n   LDFLAGS=\"$LDFLAGS $lt_tmp_static_flag\"\n   echo \"$lt_simple_link_test_code\" > conftest.$ac_ext\n   if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then\n     # The linker can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     if test -s conftest.err; then\n       # Append any errors to the config.log.\n       cat conftest.err 1>&5\n       $ECHO \"$_lt_linker_boilerplate\" | $SED '/^$/d' > conftest.exp\n       $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2\n       if diff conftest.exp conftest.er2 >/dev/null; then\n         lt_cv_prog_compiler_static_works_CXX=yes\n       fi\n     else\n       lt_cv_prog_compiler_static_works_CXX=yes\n     fi\n   fi\n   $RM -r conftest*\n   LDFLAGS=$save_LDFLAGS\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_static_works_CXX\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_static_works_CXX\" >&6; }\n\nif test yes = \"$lt_cv_prog_compiler_static_works_CXX\"; then\n    :\nelse\n    lt_prog_compiler_static_CXX=\nfi\n\n\n\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext\" >&5\nprintf %s \"checking if $compiler supports -c -o file.$ac_objext... \" >&6; }\nif test ${lt_cv_prog_compiler_c_o_CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_c_o_CXX=no\n   $RM -r conftest 2>/dev/null\n   mkdir conftest\n   cd conftest\n   mkdir out\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n\n   lt_compiler_flag=\"-o out/conftest2.$ac_objext\"\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [^ ]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&5)\n   (eval \"$lt_compile\" 2>out/conftest.err)\n   ac_status=$?\n   cat out/conftest.err >&5\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   if (exit $ac_status) && test -s out/conftest2.$ac_objext\n   then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' > out/conftest.exp\n     $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2\n     if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then\n       lt_cv_prog_compiler_c_o_CXX=yes\n     fi\n   fi\n   chmod u+w . 2>&5\n   $RM conftest*\n   # SGI C++ compiler will create directory out/ii_files/ for\n   # template instantiation\n   test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files\n   $RM out/* && rmdir out\n   cd ..\n   $RM -r conftest\n   $RM conftest*\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_c_o_CXX\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_c_o_CXX\" >&6; }\n\n\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if $compiler supports -c -o file.$ac_objext\" >&5\nprintf %s \"checking if $compiler supports -c -o file.$ac_objext... \" >&6; }\nif test ${lt_cv_prog_compiler_c_o_CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_prog_compiler_c_o_CXX=no\n   $RM -r conftest 2>/dev/null\n   mkdir conftest\n   cd conftest\n   mkdir out\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n\n   lt_compiler_flag=\"-o out/conftest2.$ac_objext\"\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [^ ]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&5)\n   (eval \"$lt_compile\" 2>out/conftest.err)\n   ac_status=$?\n   cat out/conftest.err >&5\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   if (exit $ac_status) && test -s out/conftest2.$ac_objext\n   then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' > out/conftest.exp\n     $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2\n     if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then\n       lt_cv_prog_compiler_c_o_CXX=yes\n     fi\n   fi\n   chmod u+w . 2>&5\n   $RM conftest*\n   # SGI C++ compiler will create directory out/ii_files/ for\n   # template instantiation\n   test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files\n   $RM out/* && rmdir out\n   cd ..\n   $RM -r conftest\n   $RM conftest*\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_prog_compiler_c_o_CXX\" >&5\nprintf \"%s\\n\" \"$lt_cv_prog_compiler_c_o_CXX\" >&6; }\n\n\n\n\nhard_links=nottested\nif test no = \"$lt_cv_prog_compiler_c_o_CXX\" && test no != \"$need_locks\"; then\n  # do not overwrite the value of need_locks provided by the user\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking if we can lock with hard links\" >&5\nprintf %s \"checking if we can lock with hard links... \" >&6; }\n  hard_links=yes\n  $RM conftest*\n  ln conftest.a conftest.b 2>/dev/null && hard_links=no\n  touch conftest.a\n  ln conftest.a conftest.b 2>&5 || hard_links=no\n  ln conftest.a conftest.b 2>/dev/null && hard_links=no\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $hard_links\" >&5\nprintf \"%s\\n\" \"$hard_links\" >&6; }\n  if test no = \"$hard_links\"; then\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: '$CC' does not support '-c -o', so 'make -j' may be unsafe\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: '$CC' does not support '-c -o', so 'make -j' may be unsafe\" >&2;}\n    need_locks=warn\n  fi\nelse\n  need_locks=no\nfi\n\n\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether the $compiler linker ($LD) supports shared libraries\" >&5\nprintf %s \"checking whether the $compiler linker ($LD) supports shared libraries... \" >&6; }\n\n  export_symbols_cmds_CXX='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\\''s/.* //'\\'' | sort | uniq > $export_symbols'\n  exclude_expsyms_CXX='_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*'\n  case $host_os in\n  aix[4-9]*)\n    # If we're using GNU nm, then we don't want the \"-C\" option.\n    # -C means demangle to GNU nm, but means don't demangle to AIX nm.\n    # Without the \"-l\" option, or with the \"-B\" option, AIX nm treats\n    # weak defined symbols like other global defined symbols, whereas\n    # GNU nm marks them as \"W\".\n    # While the 'weak' keyword is ignored in the Export File, we need\n    # it in the Import File for the 'aix-soname' feature, so we have\n    # to replace the \"-B\" option with \"-P\" for AIX nm.\n    if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then\n      export_symbols_cmds_CXX='$NM -Bpg $libobjs $convenience | awk '\\''{ if (((\\$ 2 == \"T\") || (\\$ 2 == \"D\") || (\\$ 2 == \"B\") || (\\$ 2 == \"W\")) && (substr(\\$ 3,1,1) != \".\")) { if (\\$ 2 == \"W\") { print \\$ 3 \" weak\" } else { print \\$ 3 } } }'\\'' | sort -u > $export_symbols'\n    else\n      export_symbols_cmds_CXX='`func_echo_all $NM | $SED -e '\\''s/B\\([^B]*\\)$/P\\1/'\\''` -PCpgl $libobjs $convenience | awk '\\''{ if (((\\$ 2 == \"T\") || (\\$ 2 == \"D\") || (\\$ 2 == \"B\") || (\\$ 2 == \"L\") || (\\$ 2 == \"W\") || (\\$ 2 == \"V\") || (\\$ 2 == \"Z\")) && (substr(\\$ 1,1,1) != \".\")) { if ((\\$ 2 == \"W\") || (\\$ 2 == \"V\") || (\\$ 2 == \"Z\")) { print \\$ 1 \" weak\" } else { print \\$ 1 } } }'\\'' | sort -u > $export_symbols'\n    fi\n    ;;\n  pw32*)\n    export_symbols_cmds_CXX=$ltdll_cmds\n    ;;\n  cygwin* | mingw* | cegcc*)\n    case $cc_basename in\n    cl* | icl*)\n      exclude_expsyms_CXX='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*'\n      ;;\n    *)\n      export_symbols_cmds_CXX='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\\''/^[BCDGRS][ ]/s/.*[ ]\\([^ ]*\\)/\\1 DATA/;s/^.*[ ]__nm__\\([^ ]*\\)[ ][^ ]*/\\1 DATA/;/^I[ ]/d;/^[AITW][ ]/s/.* //'\\'' | sort | uniq > $export_symbols'\n      exclude_expsyms_CXX='[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname'\n      ;;\n    esac\n    ;;\n  *)\n    export_symbols_cmds_CXX='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\\''s/.* //'\\'' | sort | uniq > $export_symbols'\n    ;;\n  esac\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ld_shlibs_CXX\" >&5\nprintf \"%s\\n\" \"$ld_shlibs_CXX\" >&6; }\ntest no = \"$ld_shlibs_CXX\" && can_build_shared=no\n\nwith_gnu_ld_CXX=$with_gnu_ld\n\n\n\n\n\n\n#\n# Do we need to explicitly link libc?\n#\ncase \"x$archive_cmds_need_lc_CXX\" in\nx|xyes)\n  # Assume -lc should be added\n  archive_cmds_need_lc_CXX=yes\n\n  if test yes,yes = \"$GCC,$enable_shared\"; then\n    case $archive_cmds_CXX in\n    *'~'*)\n      # FIXME: we may have to deal with multi-command sequences.\n      ;;\n    '$CC '*)\n      # Test whether the compiler implicitly links with -lc since on some\n      # systems, -lgcc has to come before -lc. If gcc already passes -lc\n      # to ld, don't add -lc before -lgcc.\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether -lc should be explicitly linked in\" >&5\nprintf %s \"checking whether -lc should be explicitly linked in... \" >&6; }\nif test ${lt_cv_archive_cmds_need_lc_CXX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) $RM conftest*\n\techo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n\n\tif { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$ac_compile\\\"\"; } >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; } 2>conftest.err; then\n\t  soname=conftest\n\t  lib=conftest\n\t  libobjs=conftest.$ac_objext\n\t  deplibs=\n\t  wl=$lt_prog_compiler_wl_CXX\n\t  pic_flag=$lt_prog_compiler_pic_CXX\n\t  compiler_flags=-v\n\t  linker_flags=-v\n\t  verstring=\n\t  output_objdir=.\n\t  libname=conftest\n\t  lt_save_allow_undefined_flag=$allow_undefined_flag_CXX\n\t  allow_undefined_flag_CXX=\n\t  if { { eval echo \"\\\"\\$as_me\\\":${as_lineno-$LINENO}: \\\"$archive_cmds_CXX 2\\>\\&1 \\| $GREP \\\" -lc \\\" \\>/dev/null 2\\>\\&1\\\"\"; } >&5\n  (eval $archive_cmds_CXX 2\\>\\&1 \\| $GREP \\\" -lc \\\" \\>/dev/null 2\\>\\&1) 2>&5\n  ac_status=$?\n  printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: \\$? = $ac_status\" >&5\n  test $ac_status = 0; }\n\t  then\n\t    lt_cv_archive_cmds_need_lc_CXX=no\n\t  else\n\t    lt_cv_archive_cmds_need_lc_CXX=yes\n\t  fi\n\t  allow_undefined_flag_CXX=$lt_save_allow_undefined_flag\n\telse\n\t  cat conftest.err 1>&5\n\tfi\n\t$RM conftest*\n\t ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $lt_cv_archive_cmds_need_lc_CXX\" >&5\nprintf \"%s\\n\" \"$lt_cv_archive_cmds_need_lc_CXX\" >&6; }\n      archive_cmds_need_lc_CXX=$lt_cv_archive_cmds_need_lc_CXX\n      ;;\n    esac\n  fi\n  ;;\nesac\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking dynamic linker characteristics\" >&5\nprintf %s \"checking dynamic linker characteristics... \" >&6; }\n\nlibrary_names_spec=\nlibname_spec='lib$name'\nsoname_spec=\nshrext_cmds=.so\npostinstall_cmds=\npostuninstall_cmds=\nfinish_cmds=\nfinish_eval=\nshlibpath_var=\nshlibpath_overrides_runpath=unknown\nversion_type=none\ndynamic_linker=\"$host_os ld.so\"\nsys_lib_dlsearch_path_spec=\"/lib /usr/lib\"\nneed_lib_prefix=unknown\nhardcode_into_libs=no\n\n# when you set need_version to no, make sure it does not cause -set_version\n# flags to be left without arguments\nneed_version=unknown\n\n\n\ncase $host_os in\naix3*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname.a'\n  shlibpath_var=LIBPATH\n\n  # AIX 3 has no versioning support, so we append a major version to the name.\n  soname_spec='$libname$release$shared_ext$major'\n  ;;\n\naix[4-9]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  hardcode_into_libs=yes\n  if test ia64 = \"$host_cpu\"; then\n    # AIX 5 supports IA64\n    library_names_spec='$libname$release$shared_ext$major $libname$release$shared_ext$versuffix $libname$shared_ext'\n    shlibpath_var=LD_LIBRARY_PATH\n  else\n    # With GCC up to 2.95.x, collect2 would create an import file\n    # for dependence libraries.  The import file would start with\n    # the line '#! .'.  This would cause the generated library to\n    # depend on '.', always an invalid library.  This was fixed in\n    # development snapshots of GCC prior to 3.0.\n    case $host_os in\n      aix4 | aix4.[01] | aix4.[01].*)\n      if { echo '#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 97)'\n\t   echo ' yes '\n\t   echo '#endif'; } | $CC -E - | $GREP yes > /dev/null; then\n\t:\n      else\n\tcan_build_shared=no\n      fi\n      ;;\n    esac\n    # Using Import Files as archive members, it is possible to support\n    # filename-based versioning of shared library archives on AIX. While\n    # this would work for both with and without runtime linking, it will\n    # prevent static linking of such archives. So we do filename-based\n    # shared library versioning with .so extension only, which is used\n    # when both runtime linking and shared linking is enabled.\n    # Unfortunately, runtime linking may impact performance, so we do\n    # not want this to be the default eventually. Also, we use the\n    # versioned .so libs for executables only if there is the -brtl\n    # linker flag in LDFLAGS as well, or --with-aix-soname=svr4 only.\n    # To allow for filename-based versioning support, we need to create\n    # libNAME.so.V as an archive file, containing:\n    # *) an Import File, referring to the versioned filename of the\n    #    archive as well as the shared archive member, telling the\n    #    bitwidth (32 or 64) of that shared object, and providing the\n    #    list of exported symbols of that shared object, eventually\n    #    decorated with the 'weak' keyword\n    # *) the shared object with the F_LOADONLY flag set, to really avoid\n    #    it being seen by the linker.\n    # At run time we better use the real file rather than another symlink,\n    # but for link time we create the symlink libNAME.so -> libNAME.so.V\n\n    case $with_aix_soname,$aix_use_runtimelinking in\n    # AIX (on Power*) has no versioning support, so currently we cannot hardcode correct\n    # soname into executable. Probably we can add versioning support to\n    # collect2, so additional links can be useful in future.\n    aix,yes) # traditional libtool\n      dynamic_linker='AIX unversionable lib.so'\n      # If using run time linking (on AIX 4.2 or later) use lib<name>.so\n      # instead of lib<name>.a to let people know that these are not\n      # typical AIX shared libraries.\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n      ;;\n    aix,no) # traditional AIX only\n      dynamic_linker='AIX lib.a(lib.so.V)'\n      # We preserve .a as extension for shared libraries through AIX4.2\n      # and later when we are not doing run time linking.\n      library_names_spec='$libname$release.a $libname.a'\n      soname_spec='$libname$release$shared_ext$major'\n      ;;\n    svr4,*) # full svr4 only\n      dynamic_linker=\"AIX lib.so.V($shared_archive_member_spec.o)\"\n      library_names_spec='$libname$release$shared_ext$major $libname$shared_ext'\n      # We do not specify a path in Import Files, so LIBPATH fires.\n      shlibpath_overrides_runpath=yes\n      ;;\n    *,yes) # both, prefer svr4\n      dynamic_linker=\"AIX lib.so.V($shared_archive_member_spec.o), lib.a(lib.so.V)\"\n      library_names_spec='$libname$release$shared_ext$major $libname$shared_ext'\n      # unpreferred sharedlib libNAME.a needs extra handling\n      postinstall_cmds='test -n \"$linkname\" || linkname=\"$realname\"~func_stripname \"\" \".so\" \"$linkname\"~$install_shared_prog \"$dir/$func_stripname_result.$libext\" \"$destdir/$func_stripname_result.$libext\"~test -z \"$tstripme\" || test -z \"$striplib\" || $striplib \"$destdir/$func_stripname_result.$libext\"'\n      postuninstall_cmds='for n in $library_names $old_library; do :; done~func_stripname \"\" \".so\" \"$n\"~test \"$func_stripname_result\" = \"$n\" || func_append rmfiles \" $odir/$func_stripname_result.$libext\"'\n      # We do not specify a path in Import Files, so LIBPATH fires.\n      shlibpath_overrides_runpath=yes\n      ;;\n    *,no) # both, prefer aix\n      dynamic_linker=\"AIX lib.a(lib.so.V), lib.so.V($shared_archive_member_spec.o)\"\n      library_names_spec='$libname$release.a $libname.a'\n      soname_spec='$libname$release$shared_ext$major'\n      # unpreferred sharedlib libNAME.so.V and symlink libNAME.so need extra handling\n      postinstall_cmds='test -z \"$dlname\" || $install_shared_prog $dir/$dlname $destdir/$dlname~test -z \"$tstripme\" || test -z \"$striplib\" || $striplib $destdir/$dlname~test -n \"$linkname\" || linkname=$realname~func_stripname \"\" \".a\" \"$linkname\"~(cd \"$destdir\" && $LN_S -f $dlname $func_stripname_result.so)'\n      postuninstall_cmds='test -z \"$dlname\" || func_append rmfiles \" $odir/$dlname\"~for n in $old_library $library_names; do :; done~func_stripname \"\" \".a\" \"$n\"~func_append rmfiles \" $odir/$func_stripname_result.so\"'\n      ;;\n    esac\n    shlibpath_var=LIBPATH\n  fi\n  ;;\n\namigaos*)\n  case $host_cpu in\n  powerpc)\n    # Since July 2007 AmigaOS4 officially supports .so libraries.\n    # When compiling the executable, add -use-dynld -Lsobjs: to the compileline.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    ;;\n  m68k)\n    library_names_spec='$libname.ixlibrary $libname.a'\n    # Create ${libname}_ixlibrary.a entries in /sys/libs.\n    finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all \"$lib\" | $SED '\\''s%^.*/\\([^/]*\\)\\.ixlibrary$%\\1%'\\''`; $RM /sys/libs/${libname}_ixlibrary.a; $show \"cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a\"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done'\n    ;;\n  esac\n  ;;\n\nbeos*)\n  library_names_spec='$libname$shared_ext'\n  dynamic_linker=\"$host_os ld.so\"\n  shlibpath_var=LIBRARY_PATH\n  ;;\n\nbsdi[45]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  sys_lib_search_path_spec=\"/shlib /usr/lib /usr/X11/lib /usr/contrib/lib /lib /usr/local/lib\"\n  sys_lib_dlsearch_path_spec=\"/shlib /usr/lib /usr/local/lib\"\n  # the default ld.so.conf also contains /usr/contrib/lib and\n  # /usr/X11R6/lib (/usr/X11 is a link to /usr/X11R6), but let us allow\n  # libtool to hard-code these into programs\n  ;;\n\ncygwin* | mingw* | pw32* | cegcc*)\n  version_type=windows\n  shrext_cmds=.dll\n  need_version=no\n  need_lib_prefix=no\n\n  case $GCC,$cc_basename in\n  yes,*)\n    # gcc\n    library_names_spec='$libname.dll.a'\n    # DLL is installed to $(libdir)/../bin by postinstall_cmds\n    postinstall_cmds='base_file=`basename \\$file`~\n      dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; echo \\$dlname'\\''`~\n      dldir=$destdir/`dirname \\$dlpath`~\n      test -d \\$dldir || mkdir -p \\$dldir~\n      $install_prog $dir/$dlname \\$dldir/$dlname~\n      chmod a+x \\$dldir/$dlname~\n      if test -n '\\''$stripme'\\'' && test -n '\\''$striplib'\\''; then\n        eval '\\''$striplib \\$dldir/$dlname'\\'' || exit \\$?;\n      fi'\n    postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; echo \\$dlname'\\''`~\n      dlpath=$dir/\\$dldll~\n       $RM \\$dlpath'\n    shlibpath_overrides_runpath=yes\n\n    case $host_os in\n    cygwin*)\n      # Cygwin DLLs use 'cyg' prefix rather than 'lib'\n      soname_spec='`echo $libname | $SED -e 's/^lib/cyg/'``echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext'\n\n      ;;\n    mingw* | cegcc*)\n      # MinGW DLLs use traditional 'lib' prefix\n      soname_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext'\n      ;;\n    pw32*)\n      # pw32 DLLs use 'pw' prefix rather than 'lib'\n      library_names_spec='`echo $libname | $SED -e 's/^lib/pw/'``echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext'\n      ;;\n    esac\n    dynamic_linker='Win32 ld.exe'\n    ;;\n\n  *,cl* | *,icl*)\n    # Native MSVC or ICC\n    libname_spec='$name'\n    soname_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext'\n    library_names_spec='$libname.dll.lib'\n\n    case $build_os in\n    mingw*)\n      sys_lib_search_path_spec=\n      lt_save_ifs=$IFS\n      IFS=';'\n      for lt_path in $LIB\n      do\n        IFS=$lt_save_ifs\n        # Let DOS variable expansion print the short 8.3 style file name.\n        lt_path=`cd \"$lt_path\" 2>/dev/null && cmd //C \"for %i in (\".\") do @echo %~si\"`\n        sys_lib_search_path_spec=\"$sys_lib_search_path_spec $lt_path\"\n      done\n      IFS=$lt_save_ifs\n      # Convert to MSYS style.\n      sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e 's|\\\\\\\\|/|g' -e 's| \\\\([a-zA-Z]\\\\):| /\\\\1|g' -e 's|^ ||'`\n      ;;\n    cygwin*)\n      # Convert to unix form, then to dos form, then back to unix form\n      # but this time dos style (no spaces!) so that the unix form looks\n      # like /cygdrive/c/PROGRA~1:/cygdr...\n      sys_lib_search_path_spec=`cygpath --path --unix \"$LIB\"`\n      sys_lib_search_path_spec=`cygpath --path --dos \"$sys_lib_search_path_spec\" 2>/dev/null`\n      sys_lib_search_path_spec=`cygpath --path --unix \"$sys_lib_search_path_spec\" | $SED -e \"s/$PATH_SEPARATOR/ /g\"`\n      ;;\n    *)\n      sys_lib_search_path_spec=$LIB\n      if $ECHO \"$sys_lib_search_path_spec\" | $GREP ';[c-zC-Z]:/' >/dev/null; then\n        # It is most probably a Windows format PATH.\n        sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e 's/;/ /g'`\n      else\n        sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e \"s/$PATH_SEPARATOR/ /g\"`\n      fi\n      # FIXME: find the short name or the path components, as spaces are\n      # common. (e.g. \"Program Files\" -> \"PROGRA~1\")\n      ;;\n    esac\n\n    # DLL is installed to $(libdir)/../bin by postinstall_cmds\n    postinstall_cmds='base_file=`basename \\$file`~\n      dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; echo \\$dlname'\\''`~\n      dldir=$destdir/`dirname \\$dlpath`~\n      test -d \\$dldir || mkdir -p \\$dldir~\n      $install_prog $dir/$dlname \\$dldir/$dlname'\n    postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; echo \\$dlname'\\''`~\n      dlpath=$dir/\\$dldll~\n       $RM \\$dlpath'\n    shlibpath_overrides_runpath=yes\n    dynamic_linker='Win32 link.exe'\n    ;;\n\n  *)\n    # Assume MSVC and ICC wrapper\n    library_names_spec='$libname`echo $release | $SED -e 's/[.]/-/g'`$versuffix$shared_ext $libname.lib'\n    dynamic_linker='Win32 ld.exe'\n    ;;\n  esac\n  # FIXME: first we should search . and the directory the executable is in\n  shlibpath_var=PATH\n  ;;\n\ndarwin* | rhapsody*)\n  dynamic_linker=\"$host_os dyld\"\n  version_type=darwin\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$major$shared_ext $libname$shared_ext'\n  soname_spec='$libname$release$major$shared_ext'\n  shlibpath_overrides_runpath=yes\n  shlibpath_var=DYLD_LIBRARY_PATH\n  shrext_cmds='`test .$module = .yes && echo .so || echo .dylib`'\n\n  sys_lib_dlsearch_path_spec='/usr/local/lib /lib /usr/lib'\n  ;;\n\ndgux*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  ;;\n\nfreebsd* | dragonfly* | midnightbsd*)\n  # DragonFly does not have aout.  When/if they implement a new\n  # versioning mechanism, adjust this.\n  if test -x /usr/bin/objformat; then\n    objformat=`/usr/bin/objformat`\n  else\n    case $host_os in\n    freebsd[23].*) objformat=aout ;;\n    *) objformat=elf ;;\n    esac\n  fi\n  version_type=freebsd-$objformat\n  case $version_type in\n    freebsd-elf*)\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n      soname_spec='$libname$release$shared_ext$major'\n      need_version=no\n      need_lib_prefix=no\n      ;;\n    freebsd-*)\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n      need_version=yes\n      ;;\n  esac\n  shlibpath_var=LD_LIBRARY_PATH\n  case $host_os in\n  freebsd2.*)\n    shlibpath_overrides_runpath=yes\n    ;;\n  freebsd3.[01]* | freebsdelf3.[01]*)\n    shlibpath_overrides_runpath=yes\n    hardcode_into_libs=yes\n    ;;\n  freebsd3.[2-9]* | freebsdelf3.[2-9]* | \\\n  freebsd4.[0-5] | freebsdelf4.[0-5] | freebsd4.1.1 | freebsdelf4.1.1)\n    shlibpath_overrides_runpath=no\n    hardcode_into_libs=yes\n    ;;\n  *) # from 4.6 on, and DragonFly\n    shlibpath_overrides_runpath=yes\n    hardcode_into_libs=yes\n    ;;\n  esac\n  ;;\n\nhaiku*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  dynamic_linker=\"$host_os runtime_loader\"\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib'\n  hardcode_into_libs=yes\n  ;;\n\nhpux9* | hpux10* | hpux11*)\n  # Give a soname corresponding to the major version so that dld.sl refuses to\n  # link against other versions.\n  version_type=sunos\n  need_lib_prefix=no\n  need_version=no\n  case $host_cpu in\n  ia64*)\n    shrext_cmds='.so'\n    hardcode_into_libs=yes\n    dynamic_linker=\"$host_os dld.so\"\n    shlibpath_var=LD_LIBRARY_PATH\n    shlibpath_overrides_runpath=yes # Unless +noenvvar is specified.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    if test 32 = \"$HPUX_IA64_MODE\"; then\n      sys_lib_search_path_spec=\"/usr/lib/hpux32 /usr/local/lib/hpux32 /usr/local/lib\"\n      sys_lib_dlsearch_path_spec=/usr/lib/hpux32\n    else\n      sys_lib_search_path_spec=\"/usr/lib/hpux64 /usr/local/lib/hpux64\"\n      sys_lib_dlsearch_path_spec=/usr/lib/hpux64\n    fi\n    ;;\n  hppa*64*)\n    shrext_cmds='.sl'\n    hardcode_into_libs=yes\n    dynamic_linker=\"$host_os dld.sl\"\n    shlibpath_var=LD_LIBRARY_PATH # How should we handle SHLIB_PATH\n    shlibpath_overrides_runpath=yes # Unless +noenvvar is specified.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    sys_lib_search_path_spec=\"/usr/lib/pa20_64 /usr/ccs/lib/pa20_64\"\n    sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n    ;;\n  *)\n    shrext_cmds='.sl'\n    dynamic_linker=\"$host_os dld.sl\"\n    shlibpath_var=SHLIB_PATH\n    shlibpath_overrides_runpath=no # +s is required to enable SHLIB_PATH\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    ;;\n  esac\n  # HP-UX runs *really* slowly unless shared libraries are mode 555, ...\n  postinstall_cmds='chmod 555 $lib'\n  # or fails outright, so override atomically:\n  install_override_mode=555\n  ;;\n\ninterix[3-9]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  dynamic_linker='Interix 3.x ld.so.1 (PE, like ELF)'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  ;;\n\nirix5* | irix6* | nonstopux*)\n  case $host_os in\n    nonstopux*) version_type=nonstopux ;;\n    *)\n\tif test yes = \"$lt_cv_prog_gnu_ld\"; then\n\t\tversion_type=linux # correct to gnu/linux during the next big refactor\n\telse\n\t\tversion_type=irix\n\tfi ;;\n  esac\n  need_lib_prefix=no\n  need_version=no\n  soname_spec='$libname$release$shared_ext$major'\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$release$shared_ext $libname$shared_ext'\n  case $host_os in\n  irix5* | nonstopux*)\n    libsuff= shlibsuff=\n    ;;\n  *)\n    case $LD in # libtool.m4 will add one of these switches to LD\n    *-32|*\"-32 \"|*-melf32bsmip|*\"-melf32bsmip \")\n      libsuff= shlibsuff= libmagic=32-bit;;\n    *-n32|*\"-n32 \"|*-melf32bmipn32|*\"-melf32bmipn32 \")\n      libsuff=32 shlibsuff=N32 libmagic=N32;;\n    *-64|*\"-64 \"|*-melf64bmip|*\"-melf64bmip \")\n      libsuff=64 shlibsuff=64 libmagic=64-bit;;\n    *) libsuff= shlibsuff= libmagic=never-match;;\n    esac\n    ;;\n  esac\n  shlibpath_var=LD_LIBRARY${shlibsuff}_PATH\n  shlibpath_overrides_runpath=no\n  sys_lib_search_path_spec=\"/usr/lib$libsuff /lib$libsuff /usr/local/lib$libsuff\"\n  sys_lib_dlsearch_path_spec=\"/usr/lib$libsuff /lib$libsuff\"\n  hardcode_into_libs=yes\n  ;;\n\n# No shared lib support for Linux oldld, aout, or coff.\nlinux*oldld* | linux*aout* | linux*coff*)\n  dynamic_linker=no\n  ;;\n\nlinux*android*)\n  version_type=none # Android doesn't support versioned libraries.\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext'\n  soname_spec='$libname$release$shared_ext'\n  finish_cmds=\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n\n  # This implies no fast_install, which is unacceptable.\n  # Some rework will be needed to allow for fast_install\n  # before this can be enabled.\n  hardcode_into_libs=yes\n\n  dynamic_linker='Android linker'\n  # Don't embed -rpath directories since the linker doesn't support them.\n  hardcode_libdir_flag_spec_CXX='-L$libdir'\n  ;;\n\n# This must be glibc/ELF.\nlinux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -n $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n\n  # Some binutils ld are patched to set DT_RUNPATH\n  if test ${lt_cv_shlibpath_overrides_runpath+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) lt_cv_shlibpath_overrides_runpath=no\n    save_LDFLAGS=$LDFLAGS\n    save_libdir=$libdir\n    eval \"libdir=/foo; wl=\\\"$lt_prog_compiler_wl_CXX\\\"; \\\n\t LDFLAGS=\\\"\\$LDFLAGS $hardcode_libdir_flag_spec_CXX\\\"\"\n    cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nint\nmain (void)\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_cxx_try_link \"$LINENO\"\nthen :\n  if  ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep \"RUNPATH.*$libdir\" >/dev/null\nthen :\n  lt_cv_shlibpath_overrides_runpath=yes\nfi\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\n    LDFLAGS=$save_LDFLAGS\n    libdir=$save_libdir\n     ;;\nesac\nfi\n\n  shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath\n\n  # This implies no fast_install, which is unacceptable.\n  # Some rework will be needed to allow for fast_install\n  # before this can be enabled.\n  hardcode_into_libs=yes\n\n  # Ideally, we could use ldconfig to report *all* directores which are\n  # searched for libraries, however this is still not possible.  Aside from not\n  # being certain /sbin/ldconfig is available, command\n  # 'ldconfig -N -X -v | grep ^/' on 64bit Fedora does not report /usr/lib64,\n  # even though it is searched at run-time.  Try to do the best guess by\n  # appending ld.so.conf contents (and includes) to the search path.\n  if test -f /etc/ld.so.conf; then\n    lt_ld_extra=`awk '/^include / { system(sprintf(\"cd /etc; cat %s 2>/dev/null\", \\$2)); skip = 1; } { if (!skip) print \\$0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[\t ]*hwcap[\t ]/d;s/[:,\t]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/\"//g;/^$/d' | tr '\\n' ' '`\n    sys_lib_dlsearch_path_spec=\"/lib /usr/lib $lt_ld_extra\"\n  fi\n\n  # We used to test for /lib/ld.so.1 and disable shared libraries on\n  # powerpc, because MkLinux only supported shared libraries with the\n  # GNU dynamic linker.  Since this was broken with cross compilers,\n  # most powerpc-linux boxes support dynamic linking these days and\n  # people can always --disable-shared, the test was removed, and we\n  # assume the GNU/Linux dynamic linker is in use.\n  dynamic_linker='GNU/Linux ld.so'\n  ;;\n\nnetbsd*)\n  version_type=sunos\n  need_lib_prefix=no\n  need_version=no\n  if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n    finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -m $libdir'\n    dynamic_linker='NetBSD (a.out) ld.so'\n  else\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    dynamic_linker='NetBSD ld.elf_so'\n  fi\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  ;;\n\nnewsos6)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  ;;\n\n*nto* | *qnx*)\n  version_type=qnx\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  dynamic_linker='ldqnx.so'\n  ;;\n\nopenbsd* | bitrig*)\n  version_type=sunos\n  sys_lib_dlsearch_path_spec=/usr/lib\n  need_lib_prefix=no\n  if test -z \"`echo __ELF__ | $CC -E - | $GREP __ELF__`\"; then\n    need_version=no\n  else\n    need_version=yes\n  fi\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -m $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  ;;\n\nos2*)\n  libname_spec='$name'\n  version_type=windows\n  shrext_cmds=.dll\n  need_version=no\n  need_lib_prefix=no\n  # OS/2 can only load a DLL with a base name of 8 characters or less.\n  soname_spec='`test -n \"$os2dllname\" && libname=\"$os2dllname\";\n    v=$($ECHO $release$versuffix | tr -d .-);\n    n=$($ECHO $libname | cut -b -$((8 - ${#v})) | tr . _);\n    $ECHO $n$v`$shared_ext'\n  library_names_spec='${libname}_dll.$libext'\n  dynamic_linker='OS/2 ld.exe'\n  shlibpath_var=BEGINLIBPATH\n  sys_lib_search_path_spec=\"/lib /usr/lib /usr/local/lib\"\n  sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n  postinstall_cmds='base_file=`basename \\$file`~\n    dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; $ECHO \\$dlname'\\''`~\n    dldir=$destdir/`dirname \\$dlpath`~\n    test -d \\$dldir || mkdir -p \\$dldir~\n    $install_prog $dir/$dlname \\$dldir/$dlname~\n    chmod a+x \\$dldir/$dlname~\n    if test -n '\\''$stripme'\\'' && test -n '\\''$striplib'\\''; then\n      eval '\\''$striplib \\$dldir/$dlname'\\'' || exit \\$?;\n    fi'\n  postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; $ECHO \\$dlname'\\''`~\n    dlpath=$dir/\\$dldll~\n    $RM \\$dlpath'\n  ;;\n\nosf3* | osf4* | osf5*)\n  version_type=osf\n  need_lib_prefix=no\n  need_version=no\n  soname_spec='$libname$release$shared_ext$major'\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  sys_lib_search_path_spec=\"/usr/shlib /usr/ccs/lib /usr/lib/cmplrs/cc /usr/lib /usr/local/lib /var/shlib\"\n  sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n  ;;\n\nrdos*)\n  dynamic_linker=no\n  ;;\n\nsolaris*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  # ldd complains unless libraries are executable\n  postinstall_cmds='chmod +x $lib'\n  ;;\n\nsunos4*)\n  version_type=sunos\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n  finish_cmds='PATH=\"\\$PATH:/usr/etc\" ldconfig $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  if test yes = \"$with_gnu_ld\"; then\n    need_lib_prefix=no\n  fi\n  need_version=yes\n  ;;\n\nsysv4 | sysv4.3*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  case $host_vendor in\n    sni)\n      shlibpath_overrides_runpath=no\n      need_lib_prefix=no\n      runpath_var=LD_RUN_PATH\n      ;;\n    siemens)\n      need_lib_prefix=no\n      ;;\n    motorola)\n      need_lib_prefix=no\n      need_version=no\n      shlibpath_overrides_runpath=no\n      sys_lib_search_path_spec='/lib /usr/lib /usr/ccs/lib'\n      ;;\n  esac\n  ;;\n\nsysv4*MP*)\n  if test -d /usr/nec; then\n    version_type=linux # correct to gnu/linux during the next big refactor\n    library_names_spec='$libname$shared_ext.$versuffix $libname$shared_ext.$major $libname$shared_ext'\n    soname_spec='$libname$shared_ext.$major'\n    shlibpath_var=LD_LIBRARY_PATH\n  fi\n  ;;\n\nsysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*)\n  version_type=sco\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  if test yes = \"$with_gnu_ld\"; then\n    sys_lib_search_path_spec='/usr/local/lib /usr/gnu/lib /usr/ccs/lib /usr/lib /lib'\n  else\n    sys_lib_search_path_spec='/usr/ccs/lib /usr/lib'\n    case $host_os in\n      sco3.2v5*)\n        sys_lib_search_path_spec=\"$sys_lib_search_path_spec /lib\"\n\t;;\n    esac\n  fi\n  sys_lib_dlsearch_path_spec='/usr/lib'\n  ;;\n\ntpf*)\n  # TPF is a cross-target only.  Preferred cross-host = GNU/Linux.\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  ;;\n\nuts4*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  ;;\n\n*)\n  dynamic_linker=no\n  ;;\nesac\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $dynamic_linker\" >&5\nprintf \"%s\\n\" \"$dynamic_linker\" >&6; }\ntest no = \"$dynamic_linker\" && can_build_shared=no\n\nvariables_saved_for_relink=\"PATH $shlibpath_var $runpath_var\"\nif test yes = \"$GCC\"; then\n  variables_saved_for_relink=\"$variables_saved_for_relink GCC_EXEC_PREFIX COMPILER_PATH LIBRARY_PATH\"\nfi\n\nif test set = \"${lt_cv_sys_lib_search_path_spec+set}\"; then\n  sys_lib_search_path_spec=$lt_cv_sys_lib_search_path_spec\nfi\n\nif test set = \"${lt_cv_sys_lib_dlsearch_path_spec+set}\"; then\n  sys_lib_dlsearch_path_spec=$lt_cv_sys_lib_dlsearch_path_spec\nfi\n\n# remember unaugmented sys_lib_dlsearch_path content for libtool script decls...\nconfigure_time_dlsearch_path=$sys_lib_dlsearch_path_spec\n\n# ... but it needs LT_SYS_LIBRARY_PATH munging for other configure-time code\nfunc_munge_path_list sys_lib_dlsearch_path_spec \"$LT_SYS_LIBRARY_PATH\"\n\n# to be used as default LT_SYS_LIBRARY_PATH value in generated libtool\nconfigure_time_lt_sys_library_path=$LT_SYS_LIBRARY_PATH\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking how to hardcode library paths into programs\" >&5\nprintf %s \"checking how to hardcode library paths into programs... \" >&6; }\nhardcode_action_CXX=\nif test -n \"$hardcode_libdir_flag_spec_CXX\" ||\n   test -n \"$runpath_var_CXX\" ||\n   test yes = \"$hardcode_automatic_CXX\"; then\n\n  # We can hardcode non-existent directories.\n  if test no != \"$hardcode_direct_CXX\" &&\n     # If the only mechanism to avoid hardcoding is shlibpath_var, we\n     # have to relink, otherwise we might link with an installed library\n     # when we should be linking with a yet-to-be-installed one\n     ## test no != \"$_LT_TAGVAR(hardcode_shlibpath_var, CXX)\" &&\n     test no != \"$hardcode_minus_L_CXX\"; then\n    # Linking always hardcodes the temporary library directory.\n    hardcode_action_CXX=relink\n  else\n    # We can link without hardcoding, and we can hardcode nonexisting dirs.\n    hardcode_action_CXX=immediate\n  fi\nelse\n  # We cannot hardcode anything, or else we can only hardcode existing\n  # directories.\n  hardcode_action_CXX=unsupported\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $hardcode_action_CXX\" >&5\nprintf \"%s\\n\" \"$hardcode_action_CXX\" >&6; }\n\nif test relink = \"$hardcode_action_CXX\" ||\n   test yes = \"$inherit_rpath_CXX\"; then\n  # Fast installation is not supported\n  enable_fast_install=no\nelif test yes = \"$shlibpath_overrides_runpath\" ||\n     test no = \"$enable_shared\"; then\n  # Fast installation is not necessary\n  enable_fast_install=needless\nfi\n\n\n\n\n\n\n\n  fi # test -n \"$compiler\"\n\n  CC=$lt_save_CC\n  CFLAGS=$lt_save_CFLAGS\n  LDCXX=$LD\n  LD=$lt_save_LD\n  GCC=$lt_save_GCC\n  with_gnu_ld=$lt_save_with_gnu_ld\n  lt_cv_path_LDCXX=$lt_cv_path_LD\n  lt_cv_path_LD=$lt_save_path_LD\n  lt_cv_prog_gnu_ldcxx=$lt_cv_prog_gnu_ld\n  lt_cv_prog_gnu_ld=$lt_save_with_gnu_ld\nfi # test yes != \"$_lt_caught_CXX_error\"\n\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n        ac_config_commands=\"$ac_config_commands libtool\"\n\n\n\n\n# Only expand once:\n\n\n\n\nac_config_headers=\"$ac_config_headers config.h\"\n\n\n# Checks for programs.\n { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether byte ordering is bigendian\" >&5\nprintf %s \"checking whether byte ordering is bigendian... \" >&6; }\nif test ${ac_cv_c_bigendian+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_cv_c_bigendian=unknown\n    # See if we're dealing with a universal compiler.\n    cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#ifndef __APPLE_CC__\n\t       not a universal capable compiler\n\t     #endif\n\t     typedef int dummy;\n\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n\n\t# Check for potential -arch flags.  It is not universal unless\n\t# there are at least two -arch flags with different values.\n\tac_arch=\n\tac_prev=\n\tfor ac_word in $CC $CFLAGS $CPPFLAGS $LDFLAGS; do\n\t if test -n \"$ac_prev\"; then\n\t   case $ac_word in\n\t     i?86 | x86_64 | ppc | ppc64)\n\t       if test -z \"$ac_arch\" || test \"$ac_arch\" = \"$ac_word\"; then\n\t\t ac_arch=$ac_word\n\t       else\n\t\t ac_cv_c_bigendian=universal\n\t\t break\n\t       fi\n\t       ;;\n\t   esac\n\t   ac_prev=\n\t elif test \"x$ac_word\" = \"x-arch\"; then\n\t   ac_prev=arch\n\t fi\n       done\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n    if test $ac_cv_c_bigendian = unknown; then\n      # See if sys/param.h defines the BYTE_ORDER macro.\n      cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <sys/types.h>\n\t     #include <sys/param.h>\n\nint\nmain (void)\n{\n#if ! (defined BYTE_ORDER && defined BIG_ENDIAN \\\\\n\t\t     && defined LITTLE_ENDIAN && BYTE_ORDER && BIG_ENDIAN \\\\\n\t\t     && LITTLE_ENDIAN)\n\t      bogus endian macros\n\t     #endif\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  # It does; now see whether it defined to BIG_ENDIAN or not.\n\t cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <sys/types.h>\n\t\t#include <sys/param.h>\n\nint\nmain (void)\n{\n#if BYTE_ORDER != BIG_ENDIAN\n\t\t not big endian\n\t\t#endif\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_c_bigendian=yes\nelse case e in #(\n  e) ac_cv_c_bigendian=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n    fi\n    if test $ac_cv_c_bigendian = unknown; then\n      # See if <limits.h> defines _LITTLE_ENDIAN or _BIG_ENDIAN (e.g., Solaris).\n      cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <limits.h>\n\nint\nmain (void)\n{\n#if ! (defined _LITTLE_ENDIAN || defined _BIG_ENDIAN)\n\t      bogus endian macros\n\t     #endif\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  # It does; now see whether it defined to _BIG_ENDIAN or not.\n\t cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <limits.h>\n\nint\nmain (void)\n{\n#ifndef _BIG_ENDIAN\n\t\t not big endian\n\t\t#endif\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_c_bigendian=yes\nelse case e in #(\n  e) ac_cv_c_bigendian=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n    fi\n    if test $ac_cv_c_bigendian = unknown; then\n      # Compile a test program.\n      if test \"$cross_compiling\" = yes\nthen :\n  # Try to guess by grepping values from an object file.\n\t cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\nunsigned short int ascii_mm[] =\n\t\t  { 0x4249, 0x4765, 0x6E44, 0x6961, 0x6E53, 0x7953, 0 };\n\t\tunsigned short int ascii_ii[] =\n\t\t  { 0x694C, 0x5454, 0x656C, 0x6E45, 0x6944, 0x6E61, 0 };\n\t\tint use_ascii (int i) {\n\t\t  return ascii_mm[i] + ascii_ii[i];\n\t\t}\n\t\tunsigned short int ebcdic_ii[] =\n\t\t  { 0x89D3, 0xE3E3, 0x8593, 0x95C5, 0x89C4, 0x9581, 0 };\n\t\tunsigned short int ebcdic_mm[] =\n\t\t  { 0xC2C9, 0xC785, 0x95C4, 0x8981, 0x95E2, 0xA8E2, 0 };\n\t\tint use_ebcdic (int i) {\n\t\t  return ebcdic_mm[i] + ebcdic_ii[i];\n\t\t}\n\t\tint\n\t\tmain (int argc, char **argv)\n\t\t{\n\t\t  /* Intimidate the compiler so that it does not\n\t\t     optimize the arrays away.  */\n\t\t  char *p = argv[0];\n\t\t  ascii_mm[1] = *p++; ebcdic_mm[1] = *p++;\n\t\t  ascii_ii[1] = *p++; ebcdic_ii[1] = *p++;\n\t\t  return use_ascii (argc) == use_ebcdic (*p);\n\t\t}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  if grep BIGenDianSyS conftest$ac_exeext >/dev/null; then\n\t      ac_cv_c_bigendian=yes\n\t    fi\n\t    if grep LiTTleEnDian conftest$ac_exeext >/dev/null ; then\n\t      if test \"$ac_cv_c_bigendian\" = unknown; then\n\t\tac_cv_c_bigendian=no\n\t      else\n\t\t# finding both strings is unlikely to happen, but who knows?\n\t\tac_cv_c_bigendian=unknown\n\t      fi\n\t    fi\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n$ac_includes_default\nint\nmain (void)\n{\n\n\t     /* Are we little or big endian?  From Harbison&Steele.  */\n\t     union\n\t     {\n\t       long int l;\n\t       char c[sizeof (long int)];\n\t     } u;\n\t     u.l = 1;\n\t     return u.c[sizeof (long int) - 1] == 1;\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_run \"$LINENO\"\nthen :\n  ac_cv_c_bigendian=no\nelse case e in #(\n  e) ac_cv_c_bigendian=yes ;;\nesac\nfi\nrm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \\\n  conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\n\n    fi ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_bigendian\" >&5\nprintf \"%s\\n\" \"$ac_cv_c_bigendian\" >&6; }\n case $ac_cv_c_bigendian in #(\n   yes)\n     printf \"%s\\n\" \"#define WORDS_BIGENDIAN 1\" >>confdefs.h\n;; #(\n   no)\n      ;; #(\n   universal)\n\nprintf \"%s\\n\" \"#define AC_APPLE_UNIVERSAL_BUILD 1\" >>confdefs.h\n\n     ;; #(\n   *)\n     as_fn_error $? \"unknown endianness\n presetting ac_cv_c_bigendian=no (or yes) will help\" \"$LINENO\" 5 ;;\n esac\n\n if test x$cross_compiling = xyes; then\n  CROSS_COMPILING_TRUE=\n  CROSS_COMPILING_FALSE='#'\nelse\n  CROSS_COMPILING_TRUE='#'\n  CROSS_COMPILING_FALSE=\nfi\n\n\n# Building documentation requires doxygen, pdflatex, and makeindex.\nfor ac_prog in doxygen\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_DOXYGEN+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$DOXYGEN\"; then\n  ac_cv_prog_DOXYGEN=\"$DOXYGEN\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_DOXYGEN=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nDOXYGEN=$ac_cv_prog_DOXYGEN\nif test -n \"$DOXYGEN\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $DOXYGEN\" >&5\nprintf \"%s\\n\" \"$DOXYGEN\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$DOXYGEN\" && break\ndone\n\nif test -z \"$DOXYGEN\"; then\n   { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: Doxygen not found - continuing without Doxygen support\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: Doxygen not found - continuing without Doxygen support\" >&2;}\nfi\n if test -n \"$DOXYGEN\"; then\n  HAVE_DOXYGEN_TRUE=\n  HAVE_DOXYGEN_FALSE='#'\nelse\n  HAVE_DOXYGEN_TRUE='#'\n  HAVE_DOXYGEN_FALSE=\nfi\n\nif test -z \"$HAVE_DOXYGEN_TRUE\"; then :\n  ac_config_files=\"$ac_config_files Doxyfile\"\n\nfi\n\nfor ac_prog in pdflatex\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_PDFLATEX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$PDFLATEX\"; then\n  ac_cv_prog_PDFLATEX=\"$PDFLATEX\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_PDFLATEX=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nPDFLATEX=$ac_cv_prog_PDFLATEX\nif test -n \"$PDFLATEX\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $PDFLATEX\" >&5\nprintf \"%s\\n\" \"$PDFLATEX\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$PDFLATEX\" && break\ndone\n\nif test -z \"$PDFLATEX\"; then\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: pdflatex not found - unable to compile manual to PDF\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: pdflatex not found - unable to compile manual to PDF\" >&2;}\nfi\nfor ac_prog in makeindex\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for $ac_word\" >&5\nprintf %s \"checking for $ac_word... \" >&6; }\nif test ${ac_cv_prog_MAKEINDEX+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if test -n \"$MAKEINDEX\"; then\n  ac_cv_prog_MAKEINDEX=\"$MAKEINDEX\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    for ac_exec_ext in '' $ac_executable_extensions; do\n  if as_fn_executable_p \"$as_dir$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_MAKEINDEX=\"$ac_prog\"\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: found $as_dir$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\n  done\nIFS=$as_save_IFS\n\nfi ;;\nesac\nfi\nMAKEINDEX=$ac_cv_prog_MAKEINDEX\nif test -n \"$MAKEINDEX\"; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $MAKEINDEX\" >&5\nprintf \"%s\\n\" \"$MAKEINDEX\" >&6; }\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\n  test -n \"$MAKEINDEX\" && break\ndone\n\nif test -z \"$MAKEINDEX\"; then\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: makeindex not found - unable to compile manual to PDF\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: makeindex not found - unable to compile manual to PDF\" >&2;}\nfi\n if test -n \"$PDFLATEX\" && test -n \"$MAKEINDEX\"; then\n  HAVE_PDFLATEX_TRUE=\n  HAVE_PDFLATEX_FALSE='#'\nelse\n  HAVE_PDFLATEX_TRUE='#'\n  HAVE_PDFLATEX_FALSE=\nfi\n\nif test -z \"$HAVE_PDFLATEX_TRUE\"; then :\n  ac_config_files=\"$ac_config_files doc/cudd.tex\"\n\nfi\n\n# Checks for libraries.\n#AC_CHECK_LIB([m],[pow])\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for library containing pow\" >&5\nprintf %s \"checking for library containing pow... \" >&6; }\nif test ${ac_cv_search_pow+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_func_search_save_LIBS=$LIBS\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar pow (void);\nint\nmain (void)\n{\nreturn pow ();\n  ;\n  return 0;\n}\n_ACEOF\nfor ac_lib in '' m\ndo\n  if test -z \"$ac_lib\"; then\n    ac_res=\"none required\"\n  else\n    ac_res=-l$ac_lib\n    LIBS=\"-l$ac_lib  $ac_func_search_save_LIBS\"\n  fi\n  if ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_search_pow=$ac_res\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext\n  if test ${ac_cv_search_pow+y}\nthen :\n  break\nfi\ndone\nif test ${ac_cv_search_pow+y}\nthen :\n\nelse case e in #(\n  e) ac_cv_search_pow=no ;;\nesac\nfi\nrm conftest.$ac_ext\nLIBS=$ac_func_search_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_pow\" >&5\nprintf \"%s\\n\" \"$ac_cv_search_pow\" >&6; }\nac_res=$ac_cv_search_pow\nif test \"$ac_res\" != no\nthen :\n  test \"$ac_res\" = \"none required\" || LIBS=\"$ac_res $LIBS\"\n\nfi\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for pthread_create in -lpthread\" >&5\nprintf %s \"checking for pthread_create in -lpthread... \" >&6; }\nif test ${ac_cv_lib_pthread_pthread_create+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_check_lib_save_LIBS=$LIBS\nLIBS=\"-lpthread  $LIBS\"\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar pthread_create (void);\nint\nmain (void)\n{\nreturn pthread_create ();\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_lib_pthread_pthread_create=yes\nelse case e in #(\n  e) ac_cv_lib_pthread_pthread_create=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext conftest.$ac_ext\nLIBS=$ac_check_lib_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_lib_pthread_pthread_create\" >&5\nprintf \"%s\\n\" \"$ac_cv_lib_pthread_pthread_create\" >&6; }\nif test \"x$ac_cv_lib_pthread_pthread_create\" = xyes\nthen :\n  have_pthreads=yes\nelse case e in #(\n  e) have_pthreads=no ;;\nesac\nfi\n\n if test x$have_pthreads = xyes; then\n  HAVE_PTHREADS_TRUE=\n  HAVE_PTHREADS_FALSE='#'\nelse\n  HAVE_PTHREADS_TRUE='#'\n  HAVE_PTHREADS_FALSE=\nfi\n\n# Check for Windows API functions.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for library containing WSAStartup\" >&5\nprintf %s \"checking for library containing WSAStartup... \" >&6; }\nif test ${ac_cv_search_WSAStartup+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_func_search_save_LIBS=$LIBS\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar WSAStartup (void);\nint\nmain (void)\n{\nreturn WSAStartup ();\n  ;\n  return 0;\n}\n_ACEOF\nfor ac_lib in '' ws2_32\ndo\n  if test -z \"$ac_lib\"; then\n    ac_res=\"none required\"\n  else\n    ac_res=-l$ac_lib\n    LIBS=\"-l$ac_lib  $ac_func_search_save_LIBS\"\n  fi\n  if ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_search_WSAStartup=$ac_res\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext\n  if test ${ac_cv_search_WSAStartup+y}\nthen :\n  break\nfi\ndone\nif test ${ac_cv_search_WSAStartup+y}\nthen :\n\nelse case e in #(\n  e) ac_cv_search_WSAStartup=no ;;\nesac\nfi\nrm conftest.$ac_ext\nLIBS=$ac_func_search_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_WSAStartup\" >&5\nprintf \"%s\\n\" \"$ac_cv_search_WSAStartup\" >&6; }\nac_res=$ac_cv_search_WSAStartup\nif test \"$ac_res\" != no\nthen :\n  test \"$ac_res\" = \"none required\" || LIBS=\"$ac_res $LIBS\"\n\nfi\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for library containing GetProcessMemoryInfo\" >&5\nprintf %s \"checking for library containing GetProcessMemoryInfo... \" >&6; }\nif test ${ac_cv_search_GetProcessMemoryInfo+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_func_search_save_LIBS=$LIBS\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n/* Override any GCC internal prototype to avoid an error.\n   Use char because int might match the return type of a GCC\n   builtin and then its argument prototype would still apply.\n   The 'extern \"C\"' is for builds by C++ compilers;\n   although this is not generally supported in C code supporting it here\n   has little cost and some practical benefit (sr 110532).  */\n#ifdef __cplusplus\nextern \"C\"\n#endif\nchar GetProcessMemoryInfo (void);\nint\nmain (void)\n{\nreturn GetProcessMemoryInfo ();\n  ;\n  return 0;\n}\n_ACEOF\nfor ac_lib in '' psapi\ndo\n  if test -z \"$ac_lib\"; then\n    ac_res=\"none required\"\n  else\n    ac_res=-l$ac_lib\n    LIBS=\"-l$ac_lib  $ac_func_search_save_LIBS\"\n  fi\n  if ac_fn_c_try_link \"$LINENO\"\nthen :\n  ac_cv_search_GetProcessMemoryInfo=$ac_res\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam \\\n    conftest$ac_exeext\n  if test ${ac_cv_search_GetProcessMemoryInfo+y}\nthen :\n  break\nfi\ndone\nif test ${ac_cv_search_GetProcessMemoryInfo+y}\nthen :\n\nelse case e in #(\n  e) ac_cv_search_GetProcessMemoryInfo=no ;;\nesac\nfi\nrm conftest.$ac_ext\nLIBS=$ac_func_search_save_LIBS ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_search_GetProcessMemoryInfo\" >&5\nprintf \"%s\\n\" \"$ac_cv_search_GetProcessMemoryInfo\" >&6; }\nac_res=$ac_cv_search_GetProcessMemoryInfo\nif test \"$ac_res\" != no\nthen :\n  test \"$ac_res\" = \"none required\" || LIBS=\"$ac_res $LIBS\"\n\nfi\n\n\n# Checks for header files.\n# First check for mandatory headers...\n       for ac_header in float.h inttypes.h limits.h stddef.h stdlib.h string.h assert.h math.h\ndo :\n  as_ac_Header=`printf \"%s\\n\" \"ac_cv_header_$ac_header\" | sed \"$as_sed_sh\"`\nac_fn_c_check_header_compile \"$LINENO\" \"$ac_header\" \"$as_ac_Header\" \"$ac_includes_default\"\nif eval test \\\"x\\$\"$as_ac_Header\"\\\" = x\"yes\"\nthen :\n  cat >>confdefs.h <<_ACEOF\n#define `printf \"%s\\n\" \"HAVE_$ac_header\" | sed \"$as_sed_cpp\"` 1\n_ACEOF\n\nelse case e in #(\n  e) have_mandatory_headers=no ;;\nesac\nfi\n\ndone\nif test \"x${have_mandatory_headers}\" = xno; then\n  as_fn_error $? \"One or more mandatory headers missing.  Check 'config.log'.\" \"$LINENO\" 5\nfi\n# ...then check for optional C headers.\nac_fn_c_check_header_compile \"$LINENO\" \"unistd.h\" \"ac_cv_header_unistd_h\" \"$ac_includes_default\"\nif test \"x$ac_cv_header_unistd_h\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_UNISTD_H 1\" >>confdefs.h\n\nfi\nac_fn_c_check_header_compile \"$LINENO\" \"sys/time.h\" \"ac_cv_header_sys_time_h\" \"$ac_includes_default\"\nif test \"x$ac_cv_header_sys_time_h\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_SYS_TIME_H 1\" >>confdefs.h\n\nfi\nac_fn_c_check_header_compile \"$LINENO\" \"sys/times.h\" \"ac_cv_header_sys_times_h\" \"$ac_includes_default\"\nif test \"x$ac_cv_header_sys_times_h\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_SYS_TIMES_H 1\" >>confdefs.h\n\nfi\nac_fn_c_check_header_compile \"$LINENO\" \"sys/resource.h\" \"ac_cv_header_sys_resource_h\" \"$ac_includes_default\"\nif test \"x$ac_cv_header_sys_resource_h\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_SYS_RESOURCE_H 1\" >>confdefs.h\n\nfi\nac_fn_c_check_header_compile \"$LINENO\" \"sys/wait.h\" \"ac_cv_header_sys_wait_h\" \"$ac_includes_default\"\nif test \"x$ac_cv_header_sys_wait_h\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_SYS_WAIT_H 1\" >>confdefs.h\n\nfi\n\n# Finally, check C++ optional headers.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for working C++ thread header\" >&5\nprintf %s \"checking for working C++ thread header... \" >&6; }\nac_ext=cpp\nac_cpp='$CXXCPP $CPPFLAGS'\nac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_cxx_compiler_gnu\n\ncat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <thread>\nint\nmain (void)\n{\n  std::thread([] {}).join()\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_cxx_try_compile \"$LINENO\"\nthen :\n  have_working_thread=yes\nelse case e in #(\n  e) have_working_thread=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\nif test x$have_working_thread = xyes ; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; }\n\nprintf \"%s\\n\" \"#define HAVE_WORKING_THREAD 1\" >>confdefs.h\n\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n# Checks for typedefs, structures, and compiler characteristics.\nac_fn_c_check_type \"$LINENO\" \"_Bool\" \"ac_cv_type__Bool\" \"$ac_includes_default\"\nif test \"x$ac_cv_type__Bool\" = xyes\nthen :\n\nprintf \"%s\\n\" \"#define HAVE__BOOL 1\" >>confdefs.h\n\n\nfi\n\n   { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for stdbool.h that conforms to C99 or later\" >&5\nprintf %s \"checking for stdbool.h that conforms to C99 or later... \" >&6; }\nif test ${ac_cv_header_stdbool_h+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <stdbool.h>\n\n             /* \"true\" and \"false\" should be usable in #if expressions and\n                integer constant expressions, and \"bool\" should be a valid\n                type name.\n\n                Although C99 requires bool, true, and false to be macros,\n                C23 and C++11 overrule that, so do not test for that.\n                Although C99 requires __bool_true_false_are_defined and\n                _Bool, C23 says they are obsolescent, so do not require\n                them.  */\n\n             #if !true\n               #error \"'true' is not true\"\n             #endif\n             #if true != 1\n               #error \"'true' is not equal to 1\"\n             #endif\n             char b[true == 1 ? 1 : -1];\n             char c[true];\n\n             #if false\n               #error \"'false' is not false\"\n             #endif\n             #if false != 0\n               #error \"'false' is not equal to 0\"\n             #endif\n             char d[false == 0 ? 1 : -1];\n\n             enum { e = false, f = true, g = false * true, h = true * 256 };\n\n             char i[(bool) 0.5 == true ? 1 : -1];\n             char j[(bool) 0.0 == false ? 1 : -1];\n             char k[sizeof (bool) > 0 ? 1 : -1];\n\n             struct sb { bool s: 1; bool t; } s;\n             char l[sizeof s.t > 0 ? 1 : -1];\n\n             /* The following fails for\n                HP aC++/ANSI C B3910B A.05.55 [Dec 04 2003]. */\n             bool m[h];\n             char n[sizeof m == h * sizeof m[0] ? 1 : -1];\n             char o[-1 - (bool) 0 < 0 ? 1 : -1];\n             /* Catch a bug in an HP-UX C compiler.  See\n                https://gcc.gnu.org/ml/gcc-patches/2003-12/msg02303.html\n                https://lists.gnu.org/r/bug-coreutils/2005-11/msg00161.html\n              */\n             bool p = true;\n             bool *pp = &p;\n\nint\nmain (void)\n{\n\n             bool ps = &s;\n             *pp |= p;\n             *pp |= ! p;\n\n             /* Refer to every declared value, so they cannot be\n                discarded as unused.  */\n             return (!b + !c + !d + !e + !f + !g + !h + !i + !j + !k\n                     + !l + !m + !n + !o + !p + !pp + !ps);\n\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_header_stdbool_h=yes\nelse case e in #(\n  e) ac_cv_header_stdbool_h=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_header_stdbool_h\" >&5\nprintf \"%s\\n\" \"$ac_cv_header_stdbool_h\" >&6; }\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for inline\" >&5\nprintf %s \"checking for inline... \" >&6; }\nif test ${ac_cv_c_inline+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_cv_c_inline=no\nfor ac_kw in inline __inline__ __inline; do\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#ifndef __cplusplus\ntypedef int foo_t;\nstatic $ac_kw foo_t static_foo (void) {return 0; }\n$ac_kw foo_t foo (void) {return 0; }\n#endif\n\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_c_inline=$ac_kw\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n  test \"$ac_cv_c_inline\" != no && break\ndone\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_c_inline\" >&5\nprintf \"%s\\n\" \"$ac_cv_c_inline\" >&6; }\n\ncase $ac_cv_c_inline in\n  inline | yes) ;;\n  *)\n    case $ac_cv_c_inline in\n      no) ac_val=;;\n      *) ac_val=$ac_cv_c_inline;;\n    esac\n    cat >>confdefs.h <<_ACEOF\n#ifndef __cplusplus\n#define inline $ac_val\n#endif\n_ACEOF\n    ;;\nesac\n\nac_fn_c_check_type \"$LINENO\" \"size_t\" \"ac_cv_type_size_t\" \"$ac_includes_default\"\nif test \"x$ac_cv_type_size_t\" = xyes\nthen :\n\nelse case e in #(\n  e)\nprintf \"%s\\n\" \"#define size_t unsigned int\" >>confdefs.h\n ;;\nesac\nfi\n\nac_fn_c_find_uintX_t \"$LINENO\" \"16\" \"ac_cv_c_uint16_t\"\ncase $ac_cv_c_uint16_t in #(\n  no|yes) ;; #(\n  *)\n\n\nprintf \"%s\\n\" \"#define uint16_t $ac_cv_c_uint16_t\" >>confdefs.h\n;;\n  esac\n\nac_fn_c_find_uintX_t \"$LINENO\" \"32\" \"ac_cv_c_uint32_t\"\ncase $ac_cv_c_uint32_t in #(\n  no|yes) ;; #(\n  *)\n\nprintf \"%s\\n\" \"#define _UINT32_T 1\" >>confdefs.h\n\n\nprintf \"%s\\n\" \"#define uint32_t $ac_cv_c_uint32_t\" >>confdefs.h\n;;\n  esac\n\nac_fn_c_check_type \"$LINENO\" \"ptrdiff_t\" \"ac_cv_type_ptrdiff_t\" \"$ac_includes_default\"\nif test \"x$ac_cv_type_ptrdiff_t\" = xyes\nthen :\n\nprintf \"%s\\n\" \"#define HAVE_PTRDIFF_T 1\" >>confdefs.h\n\n\nfi\n\n# The cast to long int works around a bug in the HP C Compiler\n# version HP92453-01 B.11.11.23709.GP, which incorrectly rejects\n# declarations like 'int a3[[(sizeof (unsigned char)) >= 0]];'.\n# This bug is HP SR number 8606223364.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking size of int\" >&5\nprintf %s \"checking size of int... \" >&6; }\nif test ${ac_cv_sizeof_int+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if ac_fn_c_compute_int \"$LINENO\" \"(long int) (sizeof (int))\" \"ac_cv_sizeof_int\"        \"$ac_includes_default\"\nthen :\n\nelse case e in #(\n  e) if test \"$ac_cv_type_int\" = yes; then\n     { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error 77 \"cannot compute sizeof (int)\nSee 'config.log' for more details\" \"$LINENO\" 5; }\n   else\n     ac_cv_sizeof_int=0\n   fi ;;\nesac\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_int\" >&5\nprintf \"%s\\n\" \"$ac_cv_sizeof_int\" >&6; }\n\n\n\nprintf \"%s\\n\" \"#define SIZEOF_INT $ac_cv_sizeof_int\" >>confdefs.h\n\n\n# The cast to long int works around a bug in the HP C Compiler\n# version HP92453-01 B.11.11.23709.GP, which incorrectly rejects\n# declarations like 'int a3[[(sizeof (unsigned char)) >= 0]];'.\n# This bug is HP SR number 8606223364.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking size of long\" >&5\nprintf %s \"checking size of long... \" >&6; }\nif test ${ac_cv_sizeof_long+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if ac_fn_c_compute_int \"$LINENO\" \"(long int) (sizeof (long))\" \"ac_cv_sizeof_long\"        \"$ac_includes_default\"\nthen :\n\nelse case e in #(\n  e) if test \"$ac_cv_type_long\" = yes; then\n     { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error 77 \"cannot compute sizeof (long)\nSee 'config.log' for more details\" \"$LINENO\" 5; }\n   else\n     ac_cv_sizeof_long=0\n   fi ;;\nesac\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_long\" >&5\nprintf \"%s\\n\" \"$ac_cv_sizeof_long\" >&6; }\n\n\n\nprintf \"%s\\n\" \"#define SIZEOF_LONG $ac_cv_sizeof_long\" >>confdefs.h\n\n\n# The cast to long int works around a bug in the HP C Compiler\n# version HP92453-01 B.11.11.23709.GP, which incorrectly rejects\n# declarations like 'int a3[[(sizeof (unsigned char)) >= 0]];'.\n# This bug is HP SR number 8606223364.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking size of void *\" >&5\nprintf %s \"checking size of void *... \" >&6; }\nif test ${ac_cv_sizeof_void_p+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if ac_fn_c_compute_int \"$LINENO\" \"(long int) (sizeof (void *))\" \"ac_cv_sizeof_void_p\"        \"$ac_includes_default\"\nthen :\n\nelse case e in #(\n  e) if test \"$ac_cv_type_void_p\" = yes; then\n     { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error 77 \"cannot compute sizeof (void *)\nSee 'config.log' for more details\" \"$LINENO\" 5; }\n   else\n     ac_cv_sizeof_void_p=0\n   fi ;;\nesac\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_void_p\" >&5\nprintf \"%s\\n\" \"$ac_cv_sizeof_void_p\" >&6; }\n\n\n\nprintf \"%s\\n\" \"#define SIZEOF_VOID_P $ac_cv_sizeof_void_p\" >>confdefs.h\n\n\n# The cast to long int works around a bug in the HP C Compiler\n# version HP92453-01 B.11.11.23709.GP, which incorrectly rejects\n# declarations like 'int a3[[(sizeof (unsigned char)) >= 0]];'.\n# This bug is HP SR number 8606223364.\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking size of long double\" >&5\nprintf %s \"checking size of long double... \" >&6; }\nif test ${ac_cv_sizeof_long_double+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) if ac_fn_c_compute_int \"$LINENO\" \"(long int) (sizeof (long double))\" \"ac_cv_sizeof_long_double\"        \"$ac_includes_default\"\nthen :\n\nelse case e in #(\n  e) if test \"$ac_cv_type_long_double\" = yes; then\n     { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error 77 \"cannot compute sizeof (long double)\nSee 'config.log' for more details\" \"$LINENO\" 5; }\n   else\n     ac_cv_sizeof_long_double=0\n   fi ;;\nesac\nfi\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_sizeof_long_double\" >&5\nprintf \"%s\\n\" \"$ac_cv_sizeof_long_double\" >&6; }\n\n\n\nprintf \"%s\\n\" \"#define SIZEOF_LONG_DOUBLE $ac_cv_sizeof_long_double\" >>confdefs.h\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether we are building for a Win32 host\" >&5\nprintf %s \"checking whether we are building for a Win32 host... \" >&6; }\nif test ${mingw_cv_win32_host+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n#ifdef _WIN32\n choke me\n#endif\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  mingw_cv_win32_host=no\nelse case e in #(\n  e) mingw_cv_win32_host=yes ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $mingw_cv_win32_host\" >&5\nprintf \"%s\\n\" \"$mingw_cv_win32_host\" >&6; }\n if test x$mingw_cv_win32_host = xyes; then\n  MINGW64_TRUE=\n  MINGW64_FALSE='#'\nelse\n  MINGW64_TRUE='#'\n  MINGW64_FALSE=\nfi\n\nif test x$mingw_cv_win32_host = xyes ; then\n\nprintf \"%s\\n\" \"#define __USE_MINGW_ANSI_STDIO 1\" >>confdefs.h\n\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking whether enough of C++11 is supported\" >&5\nprintf %s \"checking whether enough of C++11 is supported... \" >&6; }\nif test ${ac_cv_have_modern_cxx+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e) ac_ext=cpp\nac_cpp='$CXXCPP $CPPFLAGS'\nac_compile='$CXX -c $CXXFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CXX -o conftest$ac_exeext $CXXFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_cxx_compiler_gnu\n\n cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\nclass Myclass { explicit operator bool() const { return true; } };\nint main() {\n  void *p = nullptr;\n}\n_ACEOF\nif ac_fn_cxx_try_compile \"$LINENO\"\nthen :\n  ac_cv_have_modern_cxx=yes\nelse case e in #(\n  e) ac_cv_have_modern_cxx=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\n ac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n ;;\nesac\nfi\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: $ac_cv_have_modern_cxx\" >&5\nprintf \"%s\\n\" \"$ac_cv_have_modern_cxx\" >&6; }\nif test x$ac_cv_have_modern_cxx = xyes ; then\n\nprintf \"%s\\n\" \"#define HAVE_MODERN_CXX 1\" >>confdefs.h\n\nfi\n\n# Checks for library functions.\n# First the mandatory functions...\n\n  for ac_func in pow sqrt strchr strstr\ndo :\n  as_ac_var=`printf \"%s\\n\" \"ac_cv_func_$ac_func\" | sed \"$as_sed_sh\"`\nac_fn_c_check_func \"$LINENO\" \"$ac_func\" \"$as_ac_var\"\nif eval test \\\"x\\$\"$as_ac_var\"\\\" = x\"yes\"\nthen :\n  cat >>confdefs.h <<_ACEOF\n#define `printf \"%s\\n\" \"HAVE_$ac_func\" | sed \"$as_sed_cpp\"` 1\n_ACEOF\n\nelse case e in #(\n  e) have_mandatory_functions=no ;;\nesac\nfi\n\ndone\nif test \"x${have_mandatory_functions}\" = xno; then\n  as_fn_error $? \"One or more mandatory functions missing.  Check 'config.log'.\" \"$LINENO\" 5\nfi\n# ...then check for optional functions.\nac_fn_c_check_func \"$LINENO\" \"powl\" \"ac_cv_func_powl\"\nif test \"x$ac_cv_func_powl\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_POWL 1\" >>confdefs.h\n\nfi\nac_fn_c_check_func \"$LINENO\" \"gethostname\" \"ac_cv_func_gethostname\"\nif test \"x$ac_cv_func_gethostname\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_GETHOSTNAME 1\" >>confdefs.h\n\nfi\nac_fn_c_check_func \"$LINENO\" \"getrlimit\" \"ac_cv_func_getrlimit\"\nif test \"x$ac_cv_func_getrlimit\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_GETRLIMIT 1\" >>confdefs.h\n\nfi\nac_fn_c_check_func \"$LINENO\" \"getrusage\" \"ac_cv_func_getrusage\"\nif test \"x$ac_cv_func_getrusage\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_GETRUSAGE 1\" >>confdefs.h\n\nfi\nac_fn_c_check_func \"$LINENO\" \"sysconf\" \"ac_cv_func_sysconf\"\nif test \"x$ac_cv_func_sysconf\" = xyes\nthen :\n  printf \"%s\\n\" \"#define HAVE_SYSCONF 1\" >>confdefs.h\n\nfi\n\n\n# Check for a working implementation of IEEE 754 floating point\n# Specifically, check for correct treatment of +Infinity\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking for +Infinity (IEEE 754 floating point)\" >&5\nprintf %s \"checking for +Infinity (IEEE 754 floating point)... \" >&6; }\nif test ${ac_cv_have_ieee_754+y}\nthen :\n  printf %s \"(cached) \" >&6\nelse case e in #(\n  e)  if test \"$cross_compiling\" = yes\nthen :\n  ac_cv_have_ieee_754=maybe\nelse case e in #(\n  e) cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n\n#include <math.h>\nint main(void)\n{\n    if (HUGE_VAL != HUGE_VAL * 3 || HUGE_VAL != HUGE_VAL / 3) return 1;\n    return 0;\n}\n\n_ACEOF\nif ac_fn_c_try_run \"$LINENO\"\nthen :\n  ac_cv_have_ieee_754=yes\nelse case e in #(\n  e) ac_cv_have_ieee_754=no ;;\nesac\nfi\nrm -f core *.core core.conftest.* gmon.out bb.out conftest$ac_exeext \\\n  conftest.$ac_objext conftest.beam conftest.$ac_ext ;;\nesac\nfi\n ;;\nesac\nfi\n\nif test x$ac_cv_have_ieee_754 = xmaybe ; then\n  cat confdefs.h - <<_ACEOF >conftest.$ac_ext\n/* end confdefs.h.  */\n#include <math.h>\nint\nmain (void)\n{\n  double x = INFINITY\n  ;\n  return 0;\n}\n_ACEOF\nif ac_fn_c_try_compile \"$LINENO\"\nthen :\n  ac_cv_have_ieee_754=yes\nelse case e in #(\n  e) ac_cv_have_ieee_754=no ;;\nesac\nfi\nrm -f core conftest.err conftest.$ac_objext conftest.beam conftest.$ac_ext\nfi\nif test x$ac_cv_have_ieee_754 = xyes ; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: yes\" >&5\nprintf \"%s\\n\" \"yes\" >&6; }\n\nprintf \"%s\\n\" \"#define HAVE_IEEE_754 1\" >>confdefs.h\n\nelse\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: no\" >&5\nprintf \"%s\\n\" \"no\" >&6; }\nfi\n\n\nac_config_files=\"$ac_config_files Makefile\"\n\nac_config_files=\"$ac_config_files dddmp/exp/test1.sh\"\n\nac_config_files=\"$ac_config_files dddmp/exp/test2.sh\"\n\nac_config_files=\"$ac_config_files dddmp/exp/test3.sh\"\n\nac_config_files=\"$ac_config_files dddmp/exp/test4.sh\"\n\nac_config_files=\"$ac_config_files dddmp/exp/test5.sh\"\n\nac_config_files=\"$ac_config_files dddmp/exp/test6.sh\"\n\nac_config_files=\"$ac_config_files dddmp/exp/test7.sh\"\n\n\ncat >confcache <<\\_ACEOF\n# This file is a shell script that caches the results of configure\n# tests run on this system so they can be shared between configure\n# scripts and configure runs, see configure's option --config-cache.\n# It is not useful on other systems.  If it contains results you don't\n# want to keep, you may remove or edit it.\n#\n# config.status only pays attention to the cache file if you give it\n# the --recheck option to rerun configure.\n#\n# 'ac_cv_env_foo' variables (set or unset) will be overridden when\n# loading this file, other *unset* 'ac_cv_foo' will be assigned the\n# following values.\n\n_ACEOF\n\n# The following way of writing the cache mishandles newlines in values,\n# but we know of no workaround that is simple, portable, and efficient.\n# So, we kill variables containing newlines.\n# Ultrix sh set writes to stderr and can't be redirected directly,\n# and sets the high bit in the cache file unless we assign to the vars.\n(\n  for ac_var in `(set) 2>&1 | sed -n 's/^\\([a-zA-Z_][a-zA-Z0-9_]*\\)=.*/\\1/p'`; do\n    eval ac_val=\\$$ac_var\n    case $ac_val in #(\n    *${as_nl}*)\n      case $ac_var in #(\n      *_cv_*) { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: cache variable $ac_var contains a newline\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: cache variable $ac_var contains a newline\" >&2;} ;;\n      esac\n      case $ac_var in #(\n      _ | IFS | as_nl) ;; #(\n      BASH_ARGV | BASH_SOURCE) eval $ac_var= ;; #(\n      *) { eval $ac_var=; unset $ac_var;} ;;\n      esac ;;\n    esac\n  done\n\n  (set) 2>&1 |\n    case $as_nl`(ac_space=' '; set) 2>&1` in #(\n    *${as_nl}ac_space=\\ *)\n      # 'set' does not quote correctly, so add quotes: double-quote\n      # substitution turns \\\\\\\\ into \\\\, and sed turns \\\\ into \\.\n      sed -n \\\n\t\"s/'/'\\\\\\\\''/g;\n\t  s/^\\\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\\\)=\\\\(.*\\\\)/\\\\1='\\\\2'/p\"\n      ;; #(\n    *)\n      # 'set' quotes correctly as required by POSIX, so do not add quotes.\n      sed -n \"/^[_$as_cr_alnum]*_cv_[_$as_cr_alnum]*=/p\"\n      ;;\n    esac |\n    sort\n) |\n  sed '\n     /^ac_cv_env_/b end\n     t clear\n     :clear\n     s/^\\([^=]*\\)=\\(.*[{}].*\\)$/test ${\\1+y} || &/\n     t end\n     s/^\\([^=]*\\)=\\(.*\\)$/\\1=${\\1=\\2}/\n     :end' >>confcache\nif diff \"$cache_file\" confcache >/dev/null 2>&1; then :; else\n  if test -w \"$cache_file\"; then\n    if test \"x$cache_file\" != \"x/dev/null\"; then\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: updating cache $cache_file\" >&5\nprintf \"%s\\n\" \"$as_me: updating cache $cache_file\" >&6;}\n      if test ! -f \"$cache_file\" || test -h \"$cache_file\"; then\n\tcat confcache >\"$cache_file\"\n      else\n        case $cache_file in #(\n        */* | ?:*)\n\t  mv -f confcache \"$cache_file\"$$ &&\n\t  mv -f \"$cache_file\"$$ \"$cache_file\" ;; #(\n        *)\n\t  mv -f confcache \"$cache_file\" ;;\n\tesac\n      fi\n    fi\n  else\n    { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: not updating unwritable cache $cache_file\" >&5\nprintf \"%s\\n\" \"$as_me: not updating unwritable cache $cache_file\" >&6;}\n  fi\nfi\nrm -f confcache\n\ntest \"x$prefix\" = xNONE && prefix=$ac_default_prefix\n# Let make expand exec_prefix.\ntest \"x$exec_prefix\" = xNONE && exec_prefix='${prefix}'\n\nDEFS=-DHAVE_CONFIG_H\n\nac_libobjs=\nac_ltlibobjs=\nU=\nfor ac_i in : $LIBOBJS; do test \"x$ac_i\" = x: && continue\n  # 1. Remove the extension, and $U if already installed.\n  ac_script='s/\\$U\\././;s/\\.o$//;s/\\.obj$//'\n  ac_i=`printf \"%s\\n\" \"$ac_i\" | sed \"$ac_script\"`\n  # 2. Prepend LIBOBJDIR.  When used with automake>=1.10 LIBOBJDIR\n  #    will be set to the directory where LIBOBJS objects are built.\n  as_fn_append ac_libobjs \" \\${LIBOBJDIR}$ac_i\\$U.$ac_objext\"\n  as_fn_append ac_ltlibobjs \" \\${LIBOBJDIR}$ac_i\"'$U.lo'\ndone\nLIBOBJS=$ac_libobjs\n\nLTLIBOBJS=$ac_ltlibobjs\n\n\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: checking that generated files are newer than configure\" >&5\nprintf %s \"checking that generated files are newer than configure... \" >&6; }\n   if test -n \"$am_sleep_pid\"; then\n     # Hide warnings about reused PIDs.\n     wait $am_sleep_pid 2>/dev/null\n   fi\n   { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: result: done\" >&5\nprintf \"%s\\n\" \"done\" >&6; }\n if test -n \"$EXEEXT\"; then\n  am__EXEEXT_TRUE=\n  am__EXEEXT_FALSE='#'\nelse\n  am__EXEEXT_TRUE='#'\n  am__EXEEXT_FALSE=\nfi\n\nif test -z \"${DDDMP_TRUE}\" && test -z \"${DDDMP_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"DDDMP\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\nif test -z \"${OBJ_TRUE}\" && test -z \"${OBJ_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"OBJ\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\nif test -z \"${AMDEP_TRUE}\" && test -z \"${AMDEP_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"AMDEP\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\nif test -z \"${am__fastdepCC_TRUE}\" && test -z \"${am__fastdepCC_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"am__fastdepCC\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\nif test -z \"${am__fastdepCXX_TRUE}\" && test -z \"${am__fastdepCXX_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"am__fastdepCXX\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\n\nif test -z \"${CROSS_COMPILING_TRUE}\" && test -z \"${CROSS_COMPILING_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"CROSS_COMPILING\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\nif test -z \"${HAVE_DOXYGEN_TRUE}\" && test -z \"${HAVE_DOXYGEN_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"HAVE_DOXYGEN\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\nif test -z \"${HAVE_PDFLATEX_TRUE}\" && test -z \"${HAVE_PDFLATEX_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"HAVE_PDFLATEX\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\nif test -z \"${HAVE_PTHREADS_TRUE}\" && test -z \"${HAVE_PTHREADS_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"HAVE_PTHREADS\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\nif test -z \"${MINGW64_TRUE}\" && test -z \"${MINGW64_FALSE}\"; then\n  as_fn_error $? \"conditional \\\"MINGW64\\\" was never defined.\nUsually this means the macro was only invoked conditionally.\" \"$LINENO\" 5\nfi\n\n: \"${CONFIG_STATUS=./config.status}\"\nac_write_fail=0\nac_clean_files_save=$ac_clean_files\nac_clean_files=\"$ac_clean_files $CONFIG_STATUS\"\n{ printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: creating $CONFIG_STATUS\" >&5\nprintf \"%s\\n\" \"$as_me: creating $CONFIG_STATUS\" >&6;}\nas_write_fail=0\ncat >$CONFIG_STATUS <<_ASEOF || as_write_fail=1\n#! $SHELL\n# Generated by $as_me.\n# Run this file to recreate the current configuration.\n# Compiler output produced by configure, useful for debugging\n# configure, is in config.log if it exists.\n\ndebug=false\nac_cs_recheck=false\nac_cs_silent=false\n\nSHELL=\\${CONFIG_SHELL-$SHELL}\nexport SHELL\n_ASEOF\ncat >>$CONFIG_STATUS <<\\_ASEOF || as_write_fail=1\n## -------------------- ##\n## M4sh Initialization. ##\n## -------------------- ##\n\n# Be more Bourne compatible\nDUALCASE=1; export DUALCASE # for MKS sh\nif test ${ZSH_VERSION+y} && (emulate sh) >/dev/null 2>&1\nthen :\n  emulate sh\n  NULLCMD=:\n  # Pre-4.2 versions of Zsh do word splitting on ${1+\"$@\"}, which\n  # is contrary to our usage.  Disable this feature.\n  alias -g '${1+\"$@\"}'='\"$@\"'\n  setopt NO_GLOB_SUBST\nelse case e in #(\n  e) case `(set -o) 2>/dev/null` in #(\n  *posix*) :\n    set -o posix ;; #(\n  *) :\n     ;;\nesac ;;\nesac\nfi\n\n\n\n# Reset variables that may have inherited troublesome values from\n# the environment.\n\n# IFS needs to be set, to space, tab, and newline, in precisely that order.\n# (If _AS_PATH_WALK were called with IFS unset, it would have the\n# side effect of setting IFS to empty, thus disabling word splitting.)\n# Quoting is to prevent editors from complaining about space-tab.\nas_nl='\n'\nexport as_nl\nIFS=\" \"\"\t$as_nl\"\n\nPS1='$ '\nPS2='> '\nPS4='+ '\n\n# Ensure predictable behavior from utilities with locale-dependent output.\nLC_ALL=C\nexport LC_ALL\nLANGUAGE=C\nexport LANGUAGE\n\n# We cannot yet rely on \"unset\" to work, but we need these variables\n# to be unset--not just set to an empty or harmless value--now, to\n# avoid bugs in old shells (e.g. pre-3.0 UWIN ksh).  This construct\n# also avoids known problems related to \"unset\" and subshell syntax\n# in other old shells (e.g. bash 2.01 and pdksh 5.2.14).\nfor as_var in BASH_ENV ENV MAIL MAILPATH CDPATH\ndo eval test \\${$as_var+y} \\\n  && ( (unset $as_var) || exit 1) >/dev/null 2>&1 && unset $as_var || :\ndone\n\n# Ensure that fds 0, 1, and 2 are open.\nif (exec 3>&0) 2>/dev/null; then :; else exec 0</dev/null; fi\nif (exec 3>&1) 2>/dev/null; then :; else exec 1>/dev/null; fi\nif (exec 3>&2)            ; then :; else exec 2>/dev/null; fi\n\n# The user is always right.\nif ${PATH_SEPARATOR+false} :; then\n  PATH_SEPARATOR=:\n  (PATH='/bin;/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 && {\n    (PATH='/bin:/bin'; FPATH=$PATH; sh -c :) >/dev/null 2>&1 ||\n      PATH_SEPARATOR=';'\n  }\nfi\n\n\n# Find who we are.  Look in the path if we contain no directory separator.\nas_myself=\ncase $0 in #((\n  *[\\\\/]* ) as_myself=$0 ;;\n  *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  case $as_dir in #(((\n    '') as_dir=./ ;;\n    */) ;;\n    *) as_dir=$as_dir/ ;;\n  esac\n    test -r \"$as_dir$0\" && as_myself=$as_dir$0 && break\n  done\nIFS=$as_save_IFS\n\n     ;;\nesac\n# We did not find ourselves, most probably we were run as 'sh COMMAND'\n# in which case we are not to be found in the path.\nif test \"x$as_myself\" = x; then\n  as_myself=$0\nfi\nif test ! -f \"$as_myself\"; then\n  printf \"%s\\n\" \"$as_myself: error: cannot find myself; rerun with an absolute file name\" >&2\n  exit 1\nfi\n\n\n\n# as_fn_error STATUS ERROR [LINENO LOG_FD]\n# ----------------------------------------\n# Output \"`basename $0`: error: ERROR\" to stderr. If LINENO and LOG_FD are\n# provided, also output the error to LOG_FD, referencing LINENO. Then exit the\n# script with STATUS, using 1 if that was 0.\nas_fn_error ()\n{\n  as_status=$1; test $as_status -eq 0 && as_status=1\n  if test \"$4\"; then\n    as_lineno=${as_lineno-\"$3\"} as_lineno_stack=as_lineno_stack=$as_lineno_stack\n    printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: $2\" >&$4\n  fi\n  printf \"%s\\n\" \"$as_me: error: $2\" >&2\n  as_fn_exit $as_status\n} # as_fn_error\n\n\n# as_fn_set_status STATUS\n# -----------------------\n# Set $? to STATUS, without forking.\nas_fn_set_status ()\n{\n  return $1\n} # as_fn_set_status\n\n# as_fn_exit STATUS\n# -----------------\n# Exit the shell with STATUS, even in a \"trap 0\" or \"set -e\" context.\nas_fn_exit ()\n{\n  set +e\n  as_fn_set_status $1\n  exit $1\n} # as_fn_exit\n\n# as_fn_unset VAR\n# ---------------\n# Portably unset VAR.\nas_fn_unset ()\n{\n  { eval $1=; unset $1;}\n}\nas_unset=as_fn_unset\n\n# as_fn_append VAR VALUE\n# ----------------------\n# Append the text in VALUE to the end of the definition contained in VAR. Take\n# advantage of any shell optimizations that allow amortized linear growth over\n# repeated appends, instead of the typical quadratic growth present in naive\n# implementations.\nif (eval \"as_var=1; as_var+=2; test x\\$as_var = x12\") 2>/dev/null\nthen :\n  eval 'as_fn_append ()\n  {\n    eval $1+=\\$2\n  }'\nelse case e in #(\n  e) as_fn_append ()\n  {\n    eval $1=\\$$1\\$2\n  } ;;\nesac\nfi # as_fn_append\n\n# as_fn_arith ARG...\n# ------------------\n# Perform arithmetic evaluation on the ARGs, and store the result in the\n# global $as_val. Take advantage of shells that can avoid forks. The arguments\n# must be portable across $(()) and expr.\nif (eval \"test \\$(( 1 + 1 )) = 2\") 2>/dev/null\nthen :\n  eval 'as_fn_arith ()\n  {\n    as_val=$(( $* ))\n  }'\nelse case e in #(\n  e) as_fn_arith ()\n  {\n    as_val=`expr \"$@\" || test $? -eq 1`\n  } ;;\nesac\nfi # as_fn_arith\n\n\nif expr a : '\\(a\\)' >/dev/null 2>&1 &&\n   test \"X`expr 00001 : '.*\\(...\\)'`\" = X001; then\n  as_expr=expr\nelse\n  as_expr=false\nfi\n\nif (basename -- /) >/dev/null 2>&1 && test \"X`basename -- / 2>&1`\" = \"X/\"; then\n  as_basename=basename\nelse\n  as_basename=false\nfi\n\nif (as_dir=`dirname -- /` && test \"X$as_dir\" = X/) >/dev/null 2>&1; then\n  as_dirname=dirname\nelse\n  as_dirname=false\nfi\n\nas_me=`$as_basename -- \"$0\" ||\n$as_expr X/\"$0\" : '.*/\\([^/][^/]*\\)/*$' \\| \\\n\t X\"$0\" : 'X\\(//\\)$' \\| \\\n\t X\"$0\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X/\"$0\" |\n    sed '/^.*\\/\\([^/][^/]*\\)\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\/\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\/\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`\n\n# Avoid depending upon Character Ranges.\nas_cr_letters='abcdefghijklmnopqrstuvwxyz'\nas_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'\nas_cr_Letters=$as_cr_letters$as_cr_LETTERS\nas_cr_digits='0123456789'\nas_cr_alnum=$as_cr_Letters$as_cr_digits\n\n\n# Determine whether it's possible to make 'echo' print without a newline.\n# These variables are no longer used directly by Autoconf, but are AC_SUBSTed\n# for compatibility with existing Makefiles.\nECHO_C= ECHO_N= ECHO_T=\ncase `echo -n x` in #(((((\n-n*)\n  case `echo 'xy\\c'` in\n  *c*) ECHO_T='\t';;\t# ECHO_T is single tab character.\n  xy)  ECHO_C='\\c';;\n  *)   echo `echo ksh88 bug on AIX 6.1` > /dev/null\n       ECHO_T='\t';;\n  esac;;\n*)\n  ECHO_N='-n';;\nesac\n\n# For backward compatibility with old third-party macros, we provide\n# the shell variables $as_echo and $as_echo_n.  New code should use\n# AS_ECHO([\"message\"]) and AS_ECHO_N([\"message\"]), respectively.\nas_echo='printf %s\\n'\nas_echo_n='printf %s'\n\nrm -f conf$$ conf$$.exe conf$$.file\nif test -d conf$$.dir; then\n  rm -f conf$$.dir/conf$$.file\nelse\n  rm -f conf$$.dir\n  mkdir conf$$.dir 2>/dev/null\nfi\nif (echo >conf$$.file) 2>/dev/null; then\n  if ln -s conf$$.file conf$$ 2>/dev/null; then\n    as_ln_s='ln -s'\n    # ... but there are two gotchas:\n    # 1) On MSYS, both 'ln -s file dir' and 'ln file dir' fail.\n    # 2) DJGPP < 2.04 has no symlinks; 'ln -s' creates a wrapper executable.\n    # In both cases, we have to default to 'cp -pR'.\n    ln -s conf$$.file conf$$.dir 2>/dev/null && test ! -f conf$$.exe ||\n      as_ln_s='cp -pR'\n  elif ln conf$$.file conf$$ 2>/dev/null; then\n    as_ln_s=ln\n  else\n    as_ln_s='cp -pR'\n  fi\nelse\n  as_ln_s='cp -pR'\nfi\nrm -f conf$$ conf$$.exe conf$$.dir/conf$$.file conf$$.file\nrmdir conf$$.dir 2>/dev/null\n\n\n# as_fn_mkdir_p\n# -------------\n# Create \"$as_dir\" as a directory, including parents if necessary.\nas_fn_mkdir_p ()\n{\n\n  case $as_dir in #(\n  -*) as_dir=./$as_dir;;\n  esac\n  test -d \"$as_dir\" || eval $as_mkdir_p || {\n    as_dirs=\n    while :; do\n      case $as_dir in #(\n      *\\'*) as_qdir=`printf \"%s\\n\" \"$as_dir\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"`;; #'(\n      *) as_qdir=$as_dir;;\n      esac\n      as_dirs=\"'$as_qdir' $as_dirs\"\n      as_dir=`$as_dirname -- \"$as_dir\" ||\n$as_expr X\"$as_dir\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$as_dir\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$as_dir\" : 'X\\(//\\)$' \\| \\\n\t X\"$as_dir\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X\"$as_dir\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)[^/].*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`\n      test -d \"$as_dir\" && break\n    done\n    test -z \"$as_dirs\" || eval \"mkdir $as_dirs\"\n  } || test -d \"$as_dir\" || as_fn_error $? \"cannot create directory $as_dir\"\n\n\n} # as_fn_mkdir_p\nif mkdir -p . 2>/dev/null; then\n  as_mkdir_p='mkdir -p \"$as_dir\"'\nelse\n  test -d ./-p && rmdir ./-p\n  as_mkdir_p=false\nfi\n\n\n# as_fn_executable_p FILE\n# -----------------------\n# Test if FILE is an executable regular file.\nas_fn_executable_p ()\n{\n  test -f \"$1\" && test -x \"$1\"\n} # as_fn_executable_p\nas_test_x='test -x'\nas_executable_p=as_fn_executable_p\n\n# Sed expression to map a string onto a valid CPP name.\nas_sed_cpp=\"y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g\"\nas_tr_cpp=\"eval sed '$as_sed_cpp'\" # deprecated\n\n# Sed expression to map a string onto a valid variable name.\nas_sed_sh=\"y%*+%pp%;s%[^_$as_cr_alnum]%_%g\"\nas_tr_sh=\"eval sed '$as_sed_sh'\" # deprecated\n\n\nexec 6>&1\n## ----------------------------------- ##\n## Main body of $CONFIG_STATUS script. ##\n## ----------------------------------- ##\n_ASEOF\ntest $as_write_fail = 0 && chmod +x $CONFIG_STATUS || ac_write_fail=1\n\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\n# Save the log message, to keep $0 and so on meaningful, and to\n# report actual input values of CONFIG_FILES etc. instead of their\n# values after options handling.\nac_log=\"\nThis file was extended by cudd $as_me 3.0.0, which was\ngenerated by GNU Autoconf 2.72.  Invocation command line was\n\n  CONFIG_FILES    = $CONFIG_FILES\n  CONFIG_HEADERS  = $CONFIG_HEADERS\n  CONFIG_LINKS    = $CONFIG_LINKS\n  CONFIG_COMMANDS = $CONFIG_COMMANDS\n  $ $0 $@\n\non `(hostname || uname -n) 2>/dev/null | sed 1q`\n\"\n\n_ACEOF\n\ncase $ac_config_files in *\"\n\"*) set x $ac_config_files; shift; ac_config_files=$*;;\nesac\n\ncase $ac_config_headers in *\"\n\"*) set x $ac_config_headers; shift; ac_config_headers=$*;;\nesac\n\n\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\n# Files that config.status was made for.\nconfig_files=\"$ac_config_files\"\nconfig_headers=\"$ac_config_headers\"\nconfig_commands=\"$ac_config_commands\"\n\n_ACEOF\n\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\nac_cs_usage=\"\\\n'$as_me' instantiates files and other configuration actions\nfrom templates according to the current configuration.  Unless the files\nand actions are specified as TAGs, all are instantiated by default.\n\nUsage: $0 [OPTION]... [TAG]...\n\n  -h, --help       print this help, then exit\n  -V, --version    print version number and configuration settings, then exit\n      --config     print configuration, then exit\n  -q, --quiet, --silent\n                   do not print progress messages\n  -d, --debug      don't remove temporary files\n      --recheck    update $as_me by reconfiguring in the same conditions\n      --file=FILE[:TEMPLATE]\n                   instantiate the configuration file FILE\n      --header=FILE[:TEMPLATE]\n                   instantiate the configuration header FILE\n\nConfiguration files:\n$config_files\n\nConfiguration headers:\n$config_headers\n\nConfiguration commands:\n$config_commands\n\nReport bugs to <Fabio@Colorado.EDU>.\"\n\n_ACEOF\nac_cs_config=`printf \"%s\\n\" \"$ac_configure_args\" | sed \"$ac_safe_unquote\"`\nac_cs_config_escaped=`printf \"%s\\n\" \"$ac_cs_config\" | sed \"s/^ //; s/'/'\\\\\\\\\\\\\\\\''/g\"`\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\nac_cs_config='$ac_cs_config_escaped'\nac_cs_version=\"\\\\\ncudd config.status 3.0.0\nconfigured by $0, generated by GNU Autoconf 2.72,\n  with options \\\\\"\\$ac_cs_config\\\\\"\n\nCopyright (C) 2023 Free Software Foundation, Inc.\nThis config.status script is free software; the Free Software Foundation\ngives unlimited permission to copy, distribute and modify it.\"\n\nac_pwd='$ac_pwd'\nsrcdir='$srcdir'\nINSTALL='$INSTALL'\nMKDIR_P='$MKDIR_P'\nAWK='$AWK'\ntest -n \"\\$AWK\" || AWK=awk\n_ACEOF\n\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\n# The default lists apply if the user does not specify any file.\nac_need_defaults=:\nwhile test $# != 0\ndo\n  case $1 in\n  --*=?*)\n    ac_option=`expr \"X$1\" : 'X\\([^=]*\\)='`\n    ac_optarg=`expr \"X$1\" : 'X[^=]*=\\(.*\\)'`\n    ac_shift=:\n    ;;\n  --*=)\n    ac_option=`expr \"X$1\" : 'X\\([^=]*\\)='`\n    ac_optarg=\n    ac_shift=:\n    ;;\n  *)\n    ac_option=$1\n    ac_optarg=$2\n    ac_shift=shift\n    ;;\n  esac\n\n  case $ac_option in\n  # Handling of the options.\n  -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r)\n    ac_cs_recheck=: ;;\n  --version | --versio | --versi | --vers | --ver | --ve | --v | -V )\n    printf \"%s\\n\" \"$ac_cs_version\"; exit ;;\n  --config | --confi | --conf | --con | --co | --c )\n    printf \"%s\\n\" \"$ac_cs_config\"; exit ;;\n  --debug | --debu | --deb | --de | --d | -d )\n    debug=: ;;\n  --file | --fil | --fi | --f )\n    $ac_shift\n    case $ac_optarg in\n    *\\'*) ac_optarg=`printf \"%s\\n\" \"$ac_optarg\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"` ;;\n    '') as_fn_error $? \"missing file argument\" ;;\n    esac\n    as_fn_append CONFIG_FILES \" '$ac_optarg'\"\n    ac_need_defaults=false;;\n  --header | --heade | --head | --hea )\n    $ac_shift\n    case $ac_optarg in\n    *\\'*) ac_optarg=`printf \"%s\\n\" \"$ac_optarg\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"` ;;\n    esac\n    as_fn_append CONFIG_HEADERS \" '$ac_optarg'\"\n    ac_need_defaults=false;;\n  --he | --h)\n    # Conflict between --help and --header\n    as_fn_error $? \"ambiguous option: '$1'\nTry '$0 --help' for more information.\";;\n  --help | --hel | -h )\n    printf \"%s\\n\" \"$ac_cs_usage\"; exit ;;\n  -q | -quiet | --quiet | --quie | --qui | --qu | --q \\\n  | -silent | --silent | --silen | --sile | --sil | --si | --s)\n    ac_cs_silent=: ;;\n\n  # This is an error.\n  -*) as_fn_error $? \"unrecognized option: '$1'\nTry '$0 --help' for more information.\" ;;\n\n  *) as_fn_append ac_config_targets \" $1\"\n     ac_need_defaults=false ;;\n\n  esac\n  shift\ndone\n\nac_configure_extra_args=\n\nif $ac_cs_silent; then\n  exec 6>/dev/null\n  ac_configure_extra_args=\"$ac_configure_extra_args --silent\"\nfi\n\n_ACEOF\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\nif \\$ac_cs_recheck; then\n  set X $SHELL '$0' $ac_configure_args \\$ac_configure_extra_args --no-create --no-recursion\n  shift\n  \\printf \"%s\\n\" \"running CONFIG_SHELL=$SHELL \\$*\" >&6\n  CONFIG_SHELL='$SHELL'\n  export CONFIG_SHELL\n  exec \"\\$@\"\nfi\n\n_ACEOF\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\nexec 5>>config.log\n{\n  echo\n  sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX\n## Running $as_me. ##\n_ASBOX\n  printf \"%s\\n\" \"$ac_log\"\n} >&5\n\n_ACEOF\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\n#\n# INIT-COMMANDS\n#\nAMDEP_TRUE=\"$AMDEP_TRUE\" MAKE=\"${MAKE-make}\"\n\n\n# The HP-UX ksh and POSIX shell print the target directory to stdout\n# if CDPATH is set.\n(unset CDPATH) >/dev/null 2>&1 && unset CDPATH\n\nsed_quote_subst='$sed_quote_subst'\ndouble_quote_subst='$double_quote_subst'\ndelay_variable_subst='$delay_variable_subst'\nmacro_version='`$ECHO \"$macro_version\" | $SED \"$delay_single_quote_subst\"`'\nmacro_revision='`$ECHO \"$macro_revision\" | $SED \"$delay_single_quote_subst\"`'\nAS='`$ECHO \"$AS\" | $SED \"$delay_single_quote_subst\"`'\nDLLTOOL='`$ECHO \"$DLLTOOL\" | $SED \"$delay_single_quote_subst\"`'\nOBJDUMP='`$ECHO \"$OBJDUMP\" | $SED \"$delay_single_quote_subst\"`'\nenable_shared='`$ECHO \"$enable_shared\" | $SED \"$delay_single_quote_subst\"`'\nenable_static='`$ECHO \"$enable_static\" | $SED \"$delay_single_quote_subst\"`'\npic_mode='`$ECHO \"$pic_mode\" | $SED \"$delay_single_quote_subst\"`'\nenable_fast_install='`$ECHO \"$enable_fast_install\" | $SED \"$delay_single_quote_subst\"`'\nshared_archive_member_spec='`$ECHO \"$shared_archive_member_spec\" | $SED \"$delay_single_quote_subst\"`'\nSHELL='`$ECHO \"$SHELL\" | $SED \"$delay_single_quote_subst\"`'\nECHO='`$ECHO \"$ECHO\" | $SED \"$delay_single_quote_subst\"`'\nPATH_SEPARATOR='`$ECHO \"$PATH_SEPARATOR\" | $SED \"$delay_single_quote_subst\"`'\nhost_alias='`$ECHO \"$host_alias\" | $SED \"$delay_single_quote_subst\"`'\nhost='`$ECHO \"$host\" | $SED \"$delay_single_quote_subst\"`'\nhost_os='`$ECHO \"$host_os\" | $SED \"$delay_single_quote_subst\"`'\nbuild_alias='`$ECHO \"$build_alias\" | $SED \"$delay_single_quote_subst\"`'\nbuild='`$ECHO \"$build\" | $SED \"$delay_single_quote_subst\"`'\nbuild_os='`$ECHO \"$build_os\" | $SED \"$delay_single_quote_subst\"`'\nSED='`$ECHO \"$SED\" | $SED \"$delay_single_quote_subst\"`'\nXsed='`$ECHO \"$Xsed\" | $SED \"$delay_single_quote_subst\"`'\nGREP='`$ECHO \"$GREP\" | $SED \"$delay_single_quote_subst\"`'\nEGREP='`$ECHO \"$EGREP\" | $SED \"$delay_single_quote_subst\"`'\nFGREP='`$ECHO \"$FGREP\" | $SED \"$delay_single_quote_subst\"`'\nLD='`$ECHO \"$LD\" | $SED \"$delay_single_quote_subst\"`'\nNM='`$ECHO \"$NM\" | $SED \"$delay_single_quote_subst\"`'\nLN_S='`$ECHO \"$LN_S\" | $SED \"$delay_single_quote_subst\"`'\nmax_cmd_len='`$ECHO \"$max_cmd_len\" | $SED \"$delay_single_quote_subst\"`'\nac_objext='`$ECHO \"$ac_objext\" | $SED \"$delay_single_quote_subst\"`'\nexeext='`$ECHO \"$exeext\" | $SED \"$delay_single_quote_subst\"`'\nlt_unset='`$ECHO \"$lt_unset\" | $SED \"$delay_single_quote_subst\"`'\nlt_SP2NL='`$ECHO \"$lt_SP2NL\" | $SED \"$delay_single_quote_subst\"`'\nlt_NL2SP='`$ECHO \"$lt_NL2SP\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_to_host_file_cmd='`$ECHO \"$lt_cv_to_host_file_cmd\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_to_tool_file_cmd='`$ECHO \"$lt_cv_to_tool_file_cmd\" | $SED \"$delay_single_quote_subst\"`'\nreload_flag='`$ECHO \"$reload_flag\" | $SED \"$delay_single_quote_subst\"`'\nreload_cmds='`$ECHO \"$reload_cmds\" | $SED \"$delay_single_quote_subst\"`'\nFILECMD='`$ECHO \"$FILECMD\" | $SED \"$delay_single_quote_subst\"`'\ndeplibs_check_method='`$ECHO \"$deplibs_check_method\" | $SED \"$delay_single_quote_subst\"`'\nfile_magic_cmd='`$ECHO \"$file_magic_cmd\" | $SED \"$delay_single_quote_subst\"`'\nfile_magic_glob='`$ECHO \"$file_magic_glob\" | $SED \"$delay_single_quote_subst\"`'\nwant_nocaseglob='`$ECHO \"$want_nocaseglob\" | $SED \"$delay_single_quote_subst\"`'\nsharedlib_from_linklib_cmd='`$ECHO \"$sharedlib_from_linklib_cmd\" | $SED \"$delay_single_quote_subst\"`'\nAR='`$ECHO \"$AR\" | $SED \"$delay_single_quote_subst\"`'\nlt_ar_flags='`$ECHO \"$lt_ar_flags\" | $SED \"$delay_single_quote_subst\"`'\nAR_FLAGS='`$ECHO \"$AR_FLAGS\" | $SED \"$delay_single_quote_subst\"`'\narchiver_list_spec='`$ECHO \"$archiver_list_spec\" | $SED \"$delay_single_quote_subst\"`'\nSTRIP='`$ECHO \"$STRIP\" | $SED \"$delay_single_quote_subst\"`'\nRANLIB='`$ECHO \"$RANLIB\" | $SED \"$delay_single_quote_subst\"`'\nold_postinstall_cmds='`$ECHO \"$old_postinstall_cmds\" | $SED \"$delay_single_quote_subst\"`'\nold_postuninstall_cmds='`$ECHO \"$old_postuninstall_cmds\" | $SED \"$delay_single_quote_subst\"`'\nold_archive_cmds='`$ECHO \"$old_archive_cmds\" | $SED \"$delay_single_quote_subst\"`'\nlock_old_archive_extraction='`$ECHO \"$lock_old_archive_extraction\" | $SED \"$delay_single_quote_subst\"`'\nCC='`$ECHO \"$CC\" | $SED \"$delay_single_quote_subst\"`'\nCFLAGS='`$ECHO \"$CFLAGS\" | $SED \"$delay_single_quote_subst\"`'\ncompiler='`$ECHO \"$compiler\" | $SED \"$delay_single_quote_subst\"`'\nGCC='`$ECHO \"$GCC\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_sys_global_symbol_pipe='`$ECHO \"$lt_cv_sys_global_symbol_pipe\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_sys_global_symbol_to_cdecl='`$ECHO \"$lt_cv_sys_global_symbol_to_cdecl\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_sys_global_symbol_to_import='`$ECHO \"$lt_cv_sys_global_symbol_to_import\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_sys_global_symbol_to_c_name_address='`$ECHO \"$lt_cv_sys_global_symbol_to_c_name_address\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_sys_global_symbol_to_c_name_address_lib_prefix='`$ECHO \"$lt_cv_sys_global_symbol_to_c_name_address_lib_prefix\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_nm_interface='`$ECHO \"$lt_cv_nm_interface\" | $SED \"$delay_single_quote_subst\"`'\nnm_file_list_spec='`$ECHO \"$nm_file_list_spec\" | $SED \"$delay_single_quote_subst\"`'\nlt_sysroot='`$ECHO \"$lt_sysroot\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_truncate_bin='`$ECHO \"$lt_cv_truncate_bin\" | $SED \"$delay_single_quote_subst\"`'\nobjdir='`$ECHO \"$objdir\" | $SED \"$delay_single_quote_subst\"`'\nMAGIC_CMD='`$ECHO \"$MAGIC_CMD\" | $SED \"$delay_single_quote_subst\"`'\nlt_prog_compiler_no_builtin_flag='`$ECHO \"$lt_prog_compiler_no_builtin_flag\" | $SED \"$delay_single_quote_subst\"`'\nlt_prog_compiler_pic='`$ECHO \"$lt_prog_compiler_pic\" | $SED \"$delay_single_quote_subst\"`'\nlt_prog_compiler_wl='`$ECHO \"$lt_prog_compiler_wl\" | $SED \"$delay_single_quote_subst\"`'\nlt_prog_compiler_static='`$ECHO \"$lt_prog_compiler_static\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_prog_compiler_c_o='`$ECHO \"$lt_cv_prog_compiler_c_o\" | $SED \"$delay_single_quote_subst\"`'\nneed_locks='`$ECHO \"$need_locks\" | $SED \"$delay_single_quote_subst\"`'\nMANIFEST_TOOL='`$ECHO \"$MANIFEST_TOOL\" | $SED \"$delay_single_quote_subst\"`'\nDSYMUTIL='`$ECHO \"$DSYMUTIL\" | $SED \"$delay_single_quote_subst\"`'\nNMEDIT='`$ECHO \"$NMEDIT\" | $SED \"$delay_single_quote_subst\"`'\nLIPO='`$ECHO \"$LIPO\" | $SED \"$delay_single_quote_subst\"`'\nOTOOL='`$ECHO \"$OTOOL\" | $SED \"$delay_single_quote_subst\"`'\nOTOOL64='`$ECHO \"$OTOOL64\" | $SED \"$delay_single_quote_subst\"`'\nlibext='`$ECHO \"$libext\" | $SED \"$delay_single_quote_subst\"`'\nshrext_cmds='`$ECHO \"$shrext_cmds\" | $SED \"$delay_single_quote_subst\"`'\nextract_expsyms_cmds='`$ECHO \"$extract_expsyms_cmds\" | $SED \"$delay_single_quote_subst\"`'\narchive_cmds_need_lc='`$ECHO \"$archive_cmds_need_lc\" | $SED \"$delay_single_quote_subst\"`'\nenable_shared_with_static_runtimes='`$ECHO \"$enable_shared_with_static_runtimes\" | $SED \"$delay_single_quote_subst\"`'\nexport_dynamic_flag_spec='`$ECHO \"$export_dynamic_flag_spec\" | $SED \"$delay_single_quote_subst\"`'\nwhole_archive_flag_spec='`$ECHO \"$whole_archive_flag_spec\" | $SED \"$delay_single_quote_subst\"`'\ncompiler_needs_object='`$ECHO \"$compiler_needs_object\" | $SED \"$delay_single_quote_subst\"`'\nold_archive_from_new_cmds='`$ECHO \"$old_archive_from_new_cmds\" | $SED \"$delay_single_quote_subst\"`'\nold_archive_from_expsyms_cmds='`$ECHO \"$old_archive_from_expsyms_cmds\" | $SED \"$delay_single_quote_subst\"`'\narchive_cmds='`$ECHO \"$archive_cmds\" | $SED \"$delay_single_quote_subst\"`'\narchive_expsym_cmds='`$ECHO \"$archive_expsym_cmds\" | $SED \"$delay_single_quote_subst\"`'\nmodule_cmds='`$ECHO \"$module_cmds\" | $SED \"$delay_single_quote_subst\"`'\nmodule_expsym_cmds='`$ECHO \"$module_expsym_cmds\" | $SED \"$delay_single_quote_subst\"`'\nwith_gnu_ld='`$ECHO \"$with_gnu_ld\" | $SED \"$delay_single_quote_subst\"`'\nallow_undefined_flag='`$ECHO \"$allow_undefined_flag\" | $SED \"$delay_single_quote_subst\"`'\nno_undefined_flag='`$ECHO \"$no_undefined_flag\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_libdir_flag_spec='`$ECHO \"$hardcode_libdir_flag_spec\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_libdir_separator='`$ECHO \"$hardcode_libdir_separator\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_direct='`$ECHO \"$hardcode_direct\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_direct_absolute='`$ECHO \"$hardcode_direct_absolute\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_minus_L='`$ECHO \"$hardcode_minus_L\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_shlibpath_var='`$ECHO \"$hardcode_shlibpath_var\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_automatic='`$ECHO \"$hardcode_automatic\" | $SED \"$delay_single_quote_subst\"`'\ninherit_rpath='`$ECHO \"$inherit_rpath\" | $SED \"$delay_single_quote_subst\"`'\nlink_all_deplibs='`$ECHO \"$link_all_deplibs\" | $SED \"$delay_single_quote_subst\"`'\nalways_export_symbols='`$ECHO \"$always_export_symbols\" | $SED \"$delay_single_quote_subst\"`'\nexport_symbols_cmds='`$ECHO \"$export_symbols_cmds\" | $SED \"$delay_single_quote_subst\"`'\nexclude_expsyms='`$ECHO \"$exclude_expsyms\" | $SED \"$delay_single_quote_subst\"`'\ninclude_expsyms='`$ECHO \"$include_expsyms\" | $SED \"$delay_single_quote_subst\"`'\nprelink_cmds='`$ECHO \"$prelink_cmds\" | $SED \"$delay_single_quote_subst\"`'\npostlink_cmds='`$ECHO \"$postlink_cmds\" | $SED \"$delay_single_quote_subst\"`'\nfile_list_spec='`$ECHO \"$file_list_spec\" | $SED \"$delay_single_quote_subst\"`'\nvariables_saved_for_relink='`$ECHO \"$variables_saved_for_relink\" | $SED \"$delay_single_quote_subst\"`'\nneed_lib_prefix='`$ECHO \"$need_lib_prefix\" | $SED \"$delay_single_quote_subst\"`'\nneed_version='`$ECHO \"$need_version\" | $SED \"$delay_single_quote_subst\"`'\nversion_type='`$ECHO \"$version_type\" | $SED \"$delay_single_quote_subst\"`'\nrunpath_var='`$ECHO \"$runpath_var\" | $SED \"$delay_single_quote_subst\"`'\nshlibpath_var='`$ECHO \"$shlibpath_var\" | $SED \"$delay_single_quote_subst\"`'\nshlibpath_overrides_runpath='`$ECHO \"$shlibpath_overrides_runpath\" | $SED \"$delay_single_quote_subst\"`'\nlibname_spec='`$ECHO \"$libname_spec\" | $SED \"$delay_single_quote_subst\"`'\nlibrary_names_spec='`$ECHO \"$library_names_spec\" | $SED \"$delay_single_quote_subst\"`'\nsoname_spec='`$ECHO \"$soname_spec\" | $SED \"$delay_single_quote_subst\"`'\ninstall_override_mode='`$ECHO \"$install_override_mode\" | $SED \"$delay_single_quote_subst\"`'\npostinstall_cmds='`$ECHO \"$postinstall_cmds\" | $SED \"$delay_single_quote_subst\"`'\npostuninstall_cmds='`$ECHO \"$postuninstall_cmds\" | $SED \"$delay_single_quote_subst\"`'\nfinish_cmds='`$ECHO \"$finish_cmds\" | $SED \"$delay_single_quote_subst\"`'\nfinish_eval='`$ECHO \"$finish_eval\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_into_libs='`$ECHO \"$hardcode_into_libs\" | $SED \"$delay_single_quote_subst\"`'\nsys_lib_search_path_spec='`$ECHO \"$sys_lib_search_path_spec\" | $SED \"$delay_single_quote_subst\"`'\nconfigure_time_dlsearch_path='`$ECHO \"$configure_time_dlsearch_path\" | $SED \"$delay_single_quote_subst\"`'\nconfigure_time_lt_sys_library_path='`$ECHO \"$configure_time_lt_sys_library_path\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_action='`$ECHO \"$hardcode_action\" | $SED \"$delay_single_quote_subst\"`'\nenable_dlopen='`$ECHO \"$enable_dlopen\" | $SED \"$delay_single_quote_subst\"`'\nenable_dlopen_self='`$ECHO \"$enable_dlopen_self\" | $SED \"$delay_single_quote_subst\"`'\nenable_dlopen_self_static='`$ECHO \"$enable_dlopen_self_static\" | $SED \"$delay_single_quote_subst\"`'\nold_striplib='`$ECHO \"$old_striplib\" | $SED \"$delay_single_quote_subst\"`'\nstriplib='`$ECHO \"$striplib\" | $SED \"$delay_single_quote_subst\"`'\ncompiler_lib_search_dirs='`$ECHO \"$compiler_lib_search_dirs\" | $SED \"$delay_single_quote_subst\"`'\npredep_objects='`$ECHO \"$predep_objects\" | $SED \"$delay_single_quote_subst\"`'\npostdep_objects='`$ECHO \"$postdep_objects\" | $SED \"$delay_single_quote_subst\"`'\npredeps='`$ECHO \"$predeps\" | $SED \"$delay_single_quote_subst\"`'\npostdeps='`$ECHO \"$postdeps\" | $SED \"$delay_single_quote_subst\"`'\ncompiler_lib_search_path='`$ECHO \"$compiler_lib_search_path\" | $SED \"$delay_single_quote_subst\"`'\nLD_CXX='`$ECHO \"$LD_CXX\" | $SED \"$delay_single_quote_subst\"`'\nreload_flag_CXX='`$ECHO \"$reload_flag_CXX\" | $SED \"$delay_single_quote_subst\"`'\nreload_cmds_CXX='`$ECHO \"$reload_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\nold_archive_cmds_CXX='`$ECHO \"$old_archive_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\ncompiler_CXX='`$ECHO \"$compiler_CXX\" | $SED \"$delay_single_quote_subst\"`'\nGCC_CXX='`$ECHO \"$GCC_CXX\" | $SED \"$delay_single_quote_subst\"`'\nlt_prog_compiler_no_builtin_flag_CXX='`$ECHO \"$lt_prog_compiler_no_builtin_flag_CXX\" | $SED \"$delay_single_quote_subst\"`'\nlt_prog_compiler_pic_CXX='`$ECHO \"$lt_prog_compiler_pic_CXX\" | $SED \"$delay_single_quote_subst\"`'\nlt_prog_compiler_wl_CXX='`$ECHO \"$lt_prog_compiler_wl_CXX\" | $SED \"$delay_single_quote_subst\"`'\nlt_prog_compiler_static_CXX='`$ECHO \"$lt_prog_compiler_static_CXX\" | $SED \"$delay_single_quote_subst\"`'\nlt_cv_prog_compiler_c_o_CXX='`$ECHO \"$lt_cv_prog_compiler_c_o_CXX\" | $SED \"$delay_single_quote_subst\"`'\narchive_cmds_need_lc_CXX='`$ECHO \"$archive_cmds_need_lc_CXX\" | $SED \"$delay_single_quote_subst\"`'\nenable_shared_with_static_runtimes_CXX='`$ECHO \"$enable_shared_with_static_runtimes_CXX\" | $SED \"$delay_single_quote_subst\"`'\nexport_dynamic_flag_spec_CXX='`$ECHO \"$export_dynamic_flag_spec_CXX\" | $SED \"$delay_single_quote_subst\"`'\nwhole_archive_flag_spec_CXX='`$ECHO \"$whole_archive_flag_spec_CXX\" | $SED \"$delay_single_quote_subst\"`'\ncompiler_needs_object_CXX='`$ECHO \"$compiler_needs_object_CXX\" | $SED \"$delay_single_quote_subst\"`'\nold_archive_from_new_cmds_CXX='`$ECHO \"$old_archive_from_new_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\nold_archive_from_expsyms_cmds_CXX='`$ECHO \"$old_archive_from_expsyms_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\narchive_cmds_CXX='`$ECHO \"$archive_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\narchive_expsym_cmds_CXX='`$ECHO \"$archive_expsym_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\nmodule_cmds_CXX='`$ECHO \"$module_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\nmodule_expsym_cmds_CXX='`$ECHO \"$module_expsym_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\nwith_gnu_ld_CXX='`$ECHO \"$with_gnu_ld_CXX\" | $SED \"$delay_single_quote_subst\"`'\nallow_undefined_flag_CXX='`$ECHO \"$allow_undefined_flag_CXX\" | $SED \"$delay_single_quote_subst\"`'\nno_undefined_flag_CXX='`$ECHO \"$no_undefined_flag_CXX\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_libdir_flag_spec_CXX='`$ECHO \"$hardcode_libdir_flag_spec_CXX\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_libdir_separator_CXX='`$ECHO \"$hardcode_libdir_separator_CXX\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_direct_CXX='`$ECHO \"$hardcode_direct_CXX\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_direct_absolute_CXX='`$ECHO \"$hardcode_direct_absolute_CXX\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_minus_L_CXX='`$ECHO \"$hardcode_minus_L_CXX\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_shlibpath_var_CXX='`$ECHO \"$hardcode_shlibpath_var_CXX\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_automatic_CXX='`$ECHO \"$hardcode_automatic_CXX\" | $SED \"$delay_single_quote_subst\"`'\ninherit_rpath_CXX='`$ECHO \"$inherit_rpath_CXX\" | $SED \"$delay_single_quote_subst\"`'\nlink_all_deplibs_CXX='`$ECHO \"$link_all_deplibs_CXX\" | $SED \"$delay_single_quote_subst\"`'\nalways_export_symbols_CXX='`$ECHO \"$always_export_symbols_CXX\" | $SED \"$delay_single_quote_subst\"`'\nexport_symbols_cmds_CXX='`$ECHO \"$export_symbols_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\nexclude_expsyms_CXX='`$ECHO \"$exclude_expsyms_CXX\" | $SED \"$delay_single_quote_subst\"`'\ninclude_expsyms_CXX='`$ECHO \"$include_expsyms_CXX\" | $SED \"$delay_single_quote_subst\"`'\nprelink_cmds_CXX='`$ECHO \"$prelink_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\npostlink_cmds_CXX='`$ECHO \"$postlink_cmds_CXX\" | $SED \"$delay_single_quote_subst\"`'\nfile_list_spec_CXX='`$ECHO \"$file_list_spec_CXX\" | $SED \"$delay_single_quote_subst\"`'\nhardcode_action_CXX='`$ECHO \"$hardcode_action_CXX\" | $SED \"$delay_single_quote_subst\"`'\ncompiler_lib_search_dirs_CXX='`$ECHO \"$compiler_lib_search_dirs_CXX\" | $SED \"$delay_single_quote_subst\"`'\npredep_objects_CXX='`$ECHO \"$predep_objects_CXX\" | $SED \"$delay_single_quote_subst\"`'\npostdep_objects_CXX='`$ECHO \"$postdep_objects_CXX\" | $SED \"$delay_single_quote_subst\"`'\npredeps_CXX='`$ECHO \"$predeps_CXX\" | $SED \"$delay_single_quote_subst\"`'\npostdeps_CXX='`$ECHO \"$postdeps_CXX\" | $SED \"$delay_single_quote_subst\"`'\ncompiler_lib_search_path_CXX='`$ECHO \"$compiler_lib_search_path_CXX\" | $SED \"$delay_single_quote_subst\"`'\n\nLTCC='$LTCC'\nLTCFLAGS='$LTCFLAGS'\ncompiler='$compiler_DEFAULT'\n\n# A function that is used when there is no print builtin or printf.\nfunc_fallback_echo ()\n{\n  eval 'cat <<_LTECHO_EOF\n\\$1\n_LTECHO_EOF'\n}\n\n# Quote evaled strings.\nfor var in AS \\\nDLLTOOL \\\nOBJDUMP \\\nSHELL \\\nECHO \\\nPATH_SEPARATOR \\\nSED \\\nGREP \\\nEGREP \\\nFGREP \\\nLD \\\nNM \\\nLN_S \\\nlt_SP2NL \\\nlt_NL2SP \\\nreload_flag \\\nFILECMD \\\ndeplibs_check_method \\\nfile_magic_cmd \\\nfile_magic_glob \\\nwant_nocaseglob \\\nsharedlib_from_linklib_cmd \\\nAR \\\narchiver_list_spec \\\nSTRIP \\\nRANLIB \\\nCC \\\nCFLAGS \\\ncompiler \\\nlt_cv_sys_global_symbol_pipe \\\nlt_cv_sys_global_symbol_to_cdecl \\\nlt_cv_sys_global_symbol_to_import \\\nlt_cv_sys_global_symbol_to_c_name_address \\\nlt_cv_sys_global_symbol_to_c_name_address_lib_prefix \\\nlt_cv_nm_interface \\\nnm_file_list_spec \\\nlt_cv_truncate_bin \\\nlt_prog_compiler_no_builtin_flag \\\nlt_prog_compiler_pic \\\nlt_prog_compiler_wl \\\nlt_prog_compiler_static \\\nlt_cv_prog_compiler_c_o \\\nneed_locks \\\nMANIFEST_TOOL \\\nDSYMUTIL \\\nNMEDIT \\\nLIPO \\\nOTOOL \\\nOTOOL64 \\\nshrext_cmds \\\nexport_dynamic_flag_spec \\\nwhole_archive_flag_spec \\\ncompiler_needs_object \\\nwith_gnu_ld \\\nallow_undefined_flag \\\nno_undefined_flag \\\nhardcode_libdir_flag_spec \\\nhardcode_libdir_separator \\\nexclude_expsyms \\\ninclude_expsyms \\\nfile_list_spec \\\nvariables_saved_for_relink \\\nlibname_spec \\\nlibrary_names_spec \\\nsoname_spec \\\ninstall_override_mode \\\nfinish_eval \\\nold_striplib \\\nstriplib \\\ncompiler_lib_search_dirs \\\npredep_objects \\\npostdep_objects \\\npredeps \\\npostdeps \\\ncompiler_lib_search_path \\\nLD_CXX \\\nreload_flag_CXX \\\ncompiler_CXX \\\nlt_prog_compiler_no_builtin_flag_CXX \\\nlt_prog_compiler_pic_CXX \\\nlt_prog_compiler_wl_CXX \\\nlt_prog_compiler_static_CXX \\\nlt_cv_prog_compiler_c_o_CXX \\\nexport_dynamic_flag_spec_CXX \\\nwhole_archive_flag_spec_CXX \\\ncompiler_needs_object_CXX \\\nwith_gnu_ld_CXX \\\nallow_undefined_flag_CXX \\\nno_undefined_flag_CXX \\\nhardcode_libdir_flag_spec_CXX \\\nhardcode_libdir_separator_CXX \\\nexclude_expsyms_CXX \\\ninclude_expsyms_CXX \\\nfile_list_spec_CXX \\\ncompiler_lib_search_dirs_CXX \\\npredep_objects_CXX \\\npostdep_objects_CXX \\\npredeps_CXX \\\npostdeps_CXX \\\ncompiler_lib_search_path_CXX; do\n    case \\`eval \\\\\\\\\\$ECHO \\\\\\\\\"\"\\\\\\\\\\$\\$var\"\\\\\\\\\"\\` in\n    *[\\\\\\\\\\\\\\`\\\\\"\\\\\\$]*)\n      eval \"lt_\\$var=\\\\\\\\\\\\\"\\\\\\`\\\\\\$ECHO \\\\\"\\\\\\$\\$var\\\\\" | \\\\\\$SED \\\\\"\\\\\\$sed_quote_subst\\\\\"\\\\\\`\\\\\\\\\\\\\"\" ## exclude from sc_prohibit_nested_quotes\n      ;;\n    *)\n      eval \"lt_\\$var=\\\\\\\\\\\\\"\\\\\\$\\$var\\\\\\\\\\\\\"\"\n      ;;\n    esac\ndone\n\n# Double-quote double-evaled strings.\nfor var in reload_cmds \\\nold_postinstall_cmds \\\nold_postuninstall_cmds \\\nold_archive_cmds \\\nextract_expsyms_cmds \\\nold_archive_from_new_cmds \\\nold_archive_from_expsyms_cmds \\\narchive_cmds \\\narchive_expsym_cmds \\\nmodule_cmds \\\nmodule_expsym_cmds \\\nexport_symbols_cmds \\\nprelink_cmds \\\npostlink_cmds \\\npostinstall_cmds \\\npostuninstall_cmds \\\nfinish_cmds \\\nsys_lib_search_path_spec \\\nconfigure_time_dlsearch_path \\\nconfigure_time_lt_sys_library_path \\\nreload_cmds_CXX \\\nold_archive_cmds_CXX \\\nold_archive_from_new_cmds_CXX \\\nold_archive_from_expsyms_cmds_CXX \\\narchive_cmds_CXX \\\narchive_expsym_cmds_CXX \\\nmodule_cmds_CXX \\\nmodule_expsym_cmds_CXX \\\nexport_symbols_cmds_CXX \\\nprelink_cmds_CXX \\\npostlink_cmds_CXX; do\n    case \\`eval \\\\\\\\\\$ECHO \\\\\\\\\"\"\\\\\\\\\\$\\$var\"\\\\\\\\\"\\` in\n    *[\\\\\\\\\\\\\\`\\\\\"\\\\\\$]*)\n      eval \"lt_\\$var=\\\\\\\\\\\\\"\\\\\\`\\\\\\$ECHO \\\\\"\\\\\\$\\$var\\\\\" | \\\\\\$SED -e \\\\\"\\\\\\$double_quote_subst\\\\\" -e \\\\\"\\\\\\$sed_quote_subst\\\\\" -e \\\\\"\\\\\\$delay_variable_subst\\\\\"\\\\\\`\\\\\\\\\\\\\"\" ## exclude from sc_prohibit_nested_quotes\n      ;;\n    *)\n      eval \"lt_\\$var=\\\\\\\\\\\\\"\\\\\\$\\$var\\\\\\\\\\\\\"\"\n      ;;\n    esac\ndone\n\nac_aux_dir='$ac_aux_dir'\n\n# See if we are running on zsh, and set the options that allow our\n# commands through without removal of \\ escapes INIT.\nif test -n \"\\${ZSH_VERSION+set}\"; then\n   setopt NO_GLOB_SUBST\nfi\n\n\n    PACKAGE='$PACKAGE'\n    VERSION='$VERSION'\n    RM='$RM'\n    ofile='$ofile'\n\n\n\n\n\n\n_ACEOF\n\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\n\n# Handling of arguments.\nfor ac_config_target in $ac_config_targets\ndo\n  case $ac_config_target in\n    \"depfiles\") CONFIG_COMMANDS=\"$CONFIG_COMMANDS depfiles\" ;;\n    \"libtool\") CONFIG_COMMANDS=\"$CONFIG_COMMANDS libtool\" ;;\n    \"config.h\") CONFIG_HEADERS=\"$CONFIG_HEADERS config.h\" ;;\n    \"Doxyfile\") CONFIG_FILES=\"$CONFIG_FILES Doxyfile\" ;;\n    \"doc/cudd.tex\") CONFIG_FILES=\"$CONFIG_FILES doc/cudd.tex\" ;;\n    \"Makefile\") CONFIG_FILES=\"$CONFIG_FILES Makefile\" ;;\n    \"dddmp/exp/test1.sh\") CONFIG_FILES=\"$CONFIG_FILES dddmp/exp/test1.sh\" ;;\n    \"dddmp/exp/test2.sh\") CONFIG_FILES=\"$CONFIG_FILES dddmp/exp/test2.sh\" ;;\n    \"dddmp/exp/test3.sh\") CONFIG_FILES=\"$CONFIG_FILES dddmp/exp/test3.sh\" ;;\n    \"dddmp/exp/test4.sh\") CONFIG_FILES=\"$CONFIG_FILES dddmp/exp/test4.sh\" ;;\n    \"dddmp/exp/test5.sh\") CONFIG_FILES=\"$CONFIG_FILES dddmp/exp/test5.sh\" ;;\n    \"dddmp/exp/test6.sh\") CONFIG_FILES=\"$CONFIG_FILES dddmp/exp/test6.sh\" ;;\n    \"dddmp/exp/test7.sh\") CONFIG_FILES=\"$CONFIG_FILES dddmp/exp/test7.sh\" ;;\n\n  *) as_fn_error $? \"invalid argument: '$ac_config_target'\" \"$LINENO\" 5;;\n  esac\ndone\n\n\n# If the user did not use the arguments to specify the items to instantiate,\n# then the envvar interface is used.  Set only those that are not.\n# We use the long form for the default assignment because of an extremely\n# bizarre bug on SunOS 4.1.3.\nif $ac_need_defaults; then\n  test ${CONFIG_FILES+y} || CONFIG_FILES=$config_files\n  test ${CONFIG_HEADERS+y} || CONFIG_HEADERS=$config_headers\n  test ${CONFIG_COMMANDS+y} || CONFIG_COMMANDS=$config_commands\nfi\n\n# Have a temporary directory for convenience.  Make it in the build tree\n# simply because there is no reason against having it here, and in addition,\n# creating and moving files from /tmp can sometimes cause problems.\n# Hook for its removal unless debugging.\n# Note that there is a small window in which the directory will not be cleaned:\n# after its creation but before its name has been assigned to '$tmp'.\n$debug ||\n{\n  tmp= ac_tmp=\n  trap 'exit_status=$?\n  : \"${ac_tmp:=$tmp}\"\n  { test ! -d \"$ac_tmp\" || rm -fr \"$ac_tmp\"; } && exit $exit_status\n' 0\n  trap 'as_fn_exit 1' 1 2 13 15\n}\n# Create a (secure) tmp directory for tmp files.\n\n{\n  tmp=`(umask 077 && mktemp -d \"./confXXXXXX\") 2>/dev/null` &&\n  test -d \"$tmp\"\n}  ||\n{\n  tmp=./conf$$-$RANDOM\n  (umask 077 && mkdir \"$tmp\")\n} || as_fn_error $? \"cannot create a temporary directory in .\" \"$LINENO\" 5\nac_tmp=$tmp\n\n# Set up the scripts for CONFIG_FILES section.\n# No need to generate them if there are no CONFIG_FILES.\n# This happens for instance with './config.status config.h'.\nif test -n \"$CONFIG_FILES\"; then\n\n\nac_cr=`echo X | tr X '\\015'`\n# On cygwin, bash can eat \\r inside `` if the user requested igncr.\n# But we know of no other shell where ac_cr would be empty at this\n# point, so we can use a bashism as a fallback.\nif test \"x$ac_cr\" = x; then\n  eval ac_cr=\\$\\'\\\\r\\'\nfi\nac_cs_awk_cr=`$AWK 'BEGIN { print \"a\\rb\" }' </dev/null 2>/dev/null`\nif test \"$ac_cs_awk_cr\" = \"a${ac_cr}b\"; then\n  ac_cs_awk_cr='\\\\r'\nelse\n  ac_cs_awk_cr=$ac_cr\nfi\n\necho 'BEGIN {' >\"$ac_tmp/subs1.awk\" &&\n_ACEOF\n\n\n{\n  echo \"cat >conf$$subs.awk <<_ACEOF\" &&\n  echo \"$ac_subst_vars\" | sed 's/.*/&!$&$ac_delim/' &&\n  echo \"_ACEOF\"\n} >conf$$subs.sh ||\n  as_fn_error $? \"could not make $CONFIG_STATUS\" \"$LINENO\" 5\nac_delim_num=`echo \"$ac_subst_vars\" | grep -c '^'`\nac_delim='%!_!# '\nfor ac_last_try in false false false false false :; do\n  . ./conf$$subs.sh ||\n    as_fn_error $? \"could not make $CONFIG_STATUS\" \"$LINENO\" 5\n\n  ac_delim_n=`sed -n \"s/.*$ac_delim\\$/X/p\" conf$$subs.awk | grep -c X`\n  if test $ac_delim_n = $ac_delim_num; then\n    break\n  elif $ac_last_try; then\n    as_fn_error $? \"could not make $CONFIG_STATUS\" \"$LINENO\" 5\n  else\n    ac_delim=\"$ac_delim!$ac_delim _$ac_delim!! \"\n  fi\ndone\nrm -f conf$$subs.sh\n\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\ncat >>\"\\$ac_tmp/subs1.awk\" <<\\\\_ACAWK &&\n_ACEOF\nsed -n '\nh\ns/^/S[\"/; s/!.*/\"]=/\np\ng\ns/^[^!]*!//\n:repl\nt repl\ns/'\"$ac_delim\"'$//\nt delim\n:nl\nh\ns/\\(.\\{148\\}\\)..*/\\1/\nt more1\ns/[\"\\\\]/\\\\&/g; s/^/\"/; s/$/\\\\n\"\\\\/\np\nn\nb repl\n:more1\ns/[\"\\\\]/\\\\&/g; s/^/\"/; s/$/\"\\\\/\np\ng\ns/.\\{148\\}//\nt nl\n:delim\nh\ns/\\(.\\{148\\}\\)..*/\\1/\nt more2\ns/[\"\\\\]/\\\\&/g; s/^/\"/; s/$/\"/\np\nb\n:more2\ns/[\"\\\\]/\\\\&/g; s/^/\"/; s/$/\"\\\\/\np\ng\ns/.\\{148\\}//\nt delim\n' <conf$$subs.awk | sed '\n/^[^\"\"]/{\n  N\n  s/\\n//\n}\n' >>$CONFIG_STATUS || ac_write_fail=1\nrm -f conf$$subs.awk\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\n_ACAWK\ncat >>\"\\$ac_tmp/subs1.awk\" <<_ACAWK &&\n  for (key in S) S_is_set[key] = 1\n  FS = \"\u0007\"\n\n}\n{\n  line = $ 0\n  nfields = split(line, field, \"@\")\n  substed = 0\n  len = length(field[1])\n  for (i = 2; i < nfields; i++) {\n    key = field[i]\n    keylen = length(key)\n    if (S_is_set[key]) {\n      value = S[key]\n      line = substr(line, 1, len) \"\" value \"\" substr(line, len + keylen + 3)\n      len += length(value) + length(field[++i])\n      substed = 1\n    } else\n      len += 1 + keylen\n  }\n\n  print line\n}\n\n_ACAWK\n_ACEOF\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\nif sed \"s/$ac_cr//\" < /dev/null > /dev/null 2>&1; then\n  sed \"s/$ac_cr\\$//; s/$ac_cr/$ac_cs_awk_cr/g\"\nelse\n  cat\nfi < \"$ac_tmp/subs1.awk\" > \"$ac_tmp/subs.awk\" \\\n  || as_fn_error $? \"could not setup config files machinery\" \"$LINENO\" 5\n_ACEOF\n\n# VPATH may cause trouble with some makes, so we remove sole $(srcdir),\n# ${srcdir} and @srcdir@ entries from VPATH if srcdir is \".\", strip leading and\n# trailing colons and then remove the whole line if VPATH becomes empty\n# (actually we leave an empty line to preserve line numbers).\nif test \"x$srcdir\" = x.; then\n  ac_vpsub='/^[\t ]*VPATH[\t ]*=[\t ]*/{\nh\ns///\ns/^/:/\ns/[\t ]*$/:/\ns/:\\$(srcdir):/:/g\ns/:\\${srcdir}:/:/g\ns/:@srcdir@:/:/g\ns/^:*//\ns/:*$//\nx\ns/\\(=[\t ]*\\).*/\\1/\nG\ns/\\n//\ns/^[^=]*=[\t ]*$//\n}'\nfi\n\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\nfi # test -n \"$CONFIG_FILES\"\n\n# Set up the scripts for CONFIG_HEADERS section.\n# No need to generate them if there are no CONFIG_HEADERS.\n# This happens for instance with './config.status Makefile'.\nif test -n \"$CONFIG_HEADERS\"; then\ncat >\"$ac_tmp/defines.awk\" <<\\_ACAWK ||\nBEGIN {\n_ACEOF\n\n# Transform confdefs.h into an awk script 'defines.awk', embedded as\n# here-document in config.status, that substitutes the proper values into\n# config.h.in to produce config.h.\n\n# Create a delimiter string that does not exist in confdefs.h, to ease\n# handling of long lines.\nac_delim='%!_!# '\nfor ac_last_try in false false :; do\n  ac_tt=`sed -n \"/$ac_delim/p\" confdefs.h`\n  if test -z \"$ac_tt\"; then\n    break\n  elif $ac_last_try; then\n    as_fn_error $? \"could not make $CONFIG_HEADERS\" \"$LINENO\" 5\n  else\n    ac_delim=\"$ac_delim!$ac_delim _$ac_delim!! \"\n  fi\ndone\n\n# For the awk script, D is an array of macro values keyed by name,\n# likewise P contains macro parameters if any.  Preserve backslash\n# newline sequences.\n\nac_word_re=[_$as_cr_Letters][_$as_cr_alnum]*\nsed -n '\ns/.\\{148\\}/&'\"$ac_delim\"'/g\nt rset\n:rset\ns/^[\t ]*#[\t ]*define[\t ][\t ]*/ /\nt def\nd\n:def\ns/\\\\$//\nt bsnl\ns/[\"\\\\]/\\\\&/g\ns/^ \\('\"$ac_word_re\"'\\)\\(([^()]*)\\)[\t ]*\\(.*\\)/P[\"\\1\"]=\"\\2\"\\\nD[\"\\1\"]=\" \\3\"/p\ns/^ \\('\"$ac_word_re\"'\\)[\t ]*\\(.*\\)/D[\"\\1\"]=\" \\2\"/p\nd\n:bsnl\ns/[\"\\\\]/\\\\&/g\ns/^ \\('\"$ac_word_re\"'\\)\\(([^()]*)\\)[\t ]*\\(.*\\)/P[\"\\1\"]=\"\\2\"\\\nD[\"\\1\"]=\" \\3\\\\\\\\\\\\n\"\\\\/p\nt cont\ns/^ \\('\"$ac_word_re\"'\\)[\t ]*\\(.*\\)/D[\"\\1\"]=\" \\2\\\\\\\\\\\\n\"\\\\/p\nt cont\nd\n:cont\nn\ns/.\\{148\\}/&'\"$ac_delim\"'/g\nt clear\n:clear\ns/\\\\$//\nt bsnlc\ns/[\"\\\\]/\\\\&/g; s/^/\"/; s/$/\"/p\nd\n:bsnlc\ns/[\"\\\\]/\\\\&/g; s/^/\"/; s/$/\\\\\\\\\\\\n\"\\\\/p\nb cont\n' <confdefs.h | sed '\ns/'\"$ac_delim\"'/\"\\\\\\\n\"/g' >>$CONFIG_STATUS || ac_write_fail=1\n\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\n  for (key in D) D_is_set[key] = 1\n  FS = \"\u0007\"\n}\n/^[\\t ]*#[\\t ]*(define|undef)[\\t ]+$ac_word_re([\\t (]|\\$)/ {\n  line = \\$ 0\n  split(line, arg, \" \")\n  if (arg[1] == \"#\") {\n    defundef = arg[2]\n    mac1 = arg[3]\n  } else {\n    defundef = substr(arg[1], 2)\n    mac1 = arg[2]\n  }\n  split(mac1, mac2, \"(\") #)\n  macro = mac2[1]\n  prefix = substr(line, 1, index(line, defundef) - 1)\n  if (D_is_set[macro]) {\n    # Preserve the white space surrounding the \"#\".\n    print prefix \"define\", macro P[macro] D[macro]\n    next\n  } else {\n    # Replace #undef with comments.  This is necessary, for example,\n    # in the case of _POSIX_SOURCE, which is predefined and required\n    # on some systems where configure will not decide to define it.\n    if (defundef == \"undef\") {\n      print \"/*\", prefix defundef, macro, \"*/\"\n      next\n    }\n  }\n}\n{ print }\n_ACAWK\n_ACEOF\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\n  as_fn_error $? \"could not setup config headers machinery\" \"$LINENO\" 5\nfi # test -n \"$CONFIG_HEADERS\"\n\n\neval set X \"  :F $CONFIG_FILES  :H $CONFIG_HEADERS    :C $CONFIG_COMMANDS\"\nshift\nfor ac_tag\ndo\n  case $ac_tag in\n  :[FHLC]) ac_mode=$ac_tag; continue;;\n  esac\n  case $ac_mode$ac_tag in\n  :[FHL]*:*);;\n  :L* | :C*:*) as_fn_error $? \"invalid tag '$ac_tag'\" \"$LINENO\" 5;;\n  :[FH]-) ac_tag=-:-;;\n  :[FH]*) ac_tag=$ac_tag:$ac_tag.in;;\n  esac\n  ac_save_IFS=$IFS\n  IFS=:\n  set x $ac_tag\n  IFS=$ac_save_IFS\n  shift\n  ac_file=$1\n  shift\n\n  case $ac_mode in\n  :L) ac_source=$1;;\n  :[FH])\n    ac_file_inputs=\n    for ac_f\n    do\n      case $ac_f in\n      -) ac_f=\"$ac_tmp/stdin\";;\n      *) # Look for the file first in the build tree, then in the source tree\n\t # (if the path is not absolute).  The absolute path cannot be DOS-style,\n\t # because $ac_f cannot contain ':'.\n\t test -f \"$ac_f\" ||\n\t   case $ac_f in\n\t   [\\\\/$]*) false;;\n\t   *) test -f \"$srcdir/$ac_f\" && ac_f=\"$srcdir/$ac_f\";;\n\t   esac ||\n\t   as_fn_error 1 \"cannot find input file: '$ac_f'\" \"$LINENO\" 5;;\n      esac\n      case $ac_f in *\\'*) ac_f=`printf \"%s\\n\" \"$ac_f\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"`;; esac\n      as_fn_append ac_file_inputs \" '$ac_f'\"\n    done\n\n    # Let's still pretend it is 'configure' which instantiates (i.e., don't\n    # use $as_me), people would be surprised to read:\n    #    /* config.h.  Generated by config.status.  */\n    configure_input='Generated from '`\n\t  printf \"%s\\n\" \"$*\" | sed 's|^[^:]*/||;s|:[^:]*/|, |g'\n\t`' by configure.'\n    if test x\"$ac_file\" != x-; then\n      configure_input=\"$ac_file.  $configure_input\"\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: creating $ac_file\" >&5\nprintf \"%s\\n\" \"$as_me: creating $ac_file\" >&6;}\n    fi\n    # Neutralize special characters interpreted by sed in replacement strings.\n    case $configure_input in #(\n    *\\&* | *\\|* | *\\\\* )\n       ac_sed_conf_input=`printf \"%s\\n\" \"$configure_input\" |\n       sed 's/[\\\\\\\\&|]/\\\\\\\\&/g'`;; #(\n    *) ac_sed_conf_input=$configure_input;;\n    esac\n\n    case $ac_tag in\n    *:-:* | *:-) cat >\"$ac_tmp/stdin\" \\\n      || as_fn_error $? \"could not create $ac_file\" \"$LINENO\" 5 ;;\n    esac\n    ;;\n  esac\n\n  ac_dir=`$as_dirname -- \"$ac_file\" ||\n$as_expr X\"$ac_file\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$ac_file\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$ac_file\" : 'X\\(//\\)$' \\| \\\n\t X\"$ac_file\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X\"$ac_file\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)[^/].*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`\n  as_dir=\"$ac_dir\"; as_fn_mkdir_p\n  ac_builddir=.\n\ncase \"$ac_dir\" in\n.) ac_dir_suffix= ac_top_builddir_sub=. ac_top_build_prefix= ;;\n*)\n  ac_dir_suffix=/`printf \"%s\\n\" \"$ac_dir\" | sed 's|^\\.[\\\\/]||'`\n  # A \"..\" for each directory in $ac_dir_suffix.\n  ac_top_builddir_sub=`printf \"%s\\n\" \"$ac_dir_suffix\" | sed 's|/[^\\\\/]*|/..|g;s|/||'`\n  case $ac_top_builddir_sub in\n  \"\") ac_top_builddir_sub=. ac_top_build_prefix= ;;\n  *)  ac_top_build_prefix=$ac_top_builddir_sub/ ;;\n  esac ;;\nesac\nac_abs_top_builddir=$ac_pwd\nac_abs_builddir=$ac_pwd$ac_dir_suffix\n# for backward compatibility:\nac_top_builddir=$ac_top_build_prefix\n\ncase $srcdir in\n  .)  # We are building in place.\n    ac_srcdir=.\n    ac_top_srcdir=$ac_top_builddir_sub\n    ac_abs_top_srcdir=$ac_pwd ;;\n  [\\\\/]* | ?:[\\\\/]* )  # Absolute name.\n    ac_srcdir=$srcdir$ac_dir_suffix;\n    ac_top_srcdir=$srcdir\n    ac_abs_top_srcdir=$srcdir ;;\n  *) # Relative name.\n    ac_srcdir=$ac_top_build_prefix$srcdir$ac_dir_suffix\n    ac_top_srcdir=$ac_top_build_prefix$srcdir\n    ac_abs_top_srcdir=$ac_pwd/$srcdir ;;\nesac\nac_abs_srcdir=$ac_abs_top_srcdir$ac_dir_suffix\n\n\n  case $ac_mode in\n  :F)\n  #\n  # CONFIG_FILE\n  #\n\n  case $INSTALL in\n  [\\\\/$]* | ?:[\\\\/]* ) ac_INSTALL=$INSTALL ;;\n  *) ac_INSTALL=$ac_top_build_prefix$INSTALL ;;\n  esac\n  ac_MKDIR_P=$MKDIR_P\n  case $MKDIR_P in\n  [\\\\/$]* | ?:[\\\\/]* ) ;;\n  */*) ac_MKDIR_P=$ac_top_build_prefix$MKDIR_P ;;\n  esac\n_ACEOF\n\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\n# If the template does not know about datarootdir, expand it.\n# FIXME: This hack should be removed a few years after 2.60.\nac_datarootdir_hack=; ac_datarootdir_seen=\nac_sed_dataroot='\n/datarootdir/ {\n  p\n  q\n}\n/@datadir@/p\n/@docdir@/p\n/@infodir@/p\n/@localedir@/p\n/@mandir@/p'\ncase `eval \"sed -n \\\"\\$ac_sed_dataroot\\\" $ac_file_inputs\"` in\n*datarootdir*) ac_datarootdir_seen=yes;;\n*@datadir@*|*@docdir@*|*@infodir@*|*@localedir@*|*@mandir@*)\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: $ac_file_inputs seems to ignore the --datarootdir setting\" >&2;}\n_ACEOF\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\n  ac_datarootdir_hack='\n  s&@datadir@&$datadir&g\n  s&@docdir@&$docdir&g\n  s&@infodir@&$infodir&g\n  s&@localedir@&$localedir&g\n  s&@mandir@&$mandir&g\n  s&\\\\\\${datarootdir}&$datarootdir&g' ;;\nesac\n_ACEOF\n\n# Neutralize VPATH when '$srcdir' = '.'.\n# Shell code in configure.ac might set extrasub.\n# FIXME: do we really want to maintain this feature?\ncat >>$CONFIG_STATUS <<_ACEOF || ac_write_fail=1\nac_sed_extra=\"$ac_vpsub\n$extrasub\n_ACEOF\ncat >>$CONFIG_STATUS <<\\_ACEOF || ac_write_fail=1\n:t\n/@[a-zA-Z_][a-zA-Z_0-9]*@/!b\ns|@configure_input@|$ac_sed_conf_input|;t t\ns&@top_builddir@&$ac_top_builddir_sub&;t t\ns&@top_build_prefix@&$ac_top_build_prefix&;t t\ns&@srcdir@&$ac_srcdir&;t t\ns&@abs_srcdir@&$ac_abs_srcdir&;t t\ns&@top_srcdir@&$ac_top_srcdir&;t t\ns&@abs_top_srcdir@&$ac_abs_top_srcdir&;t t\ns&@builddir@&$ac_builddir&;t t\ns&@abs_builddir@&$ac_abs_builddir&;t t\ns&@abs_top_builddir@&$ac_abs_top_builddir&;t t\ns&@INSTALL@&$ac_INSTALL&;t t\ns&@MKDIR_P@&$ac_MKDIR_P&;t t\n$ac_datarootdir_hack\n\"\neval sed \\\"\\$ac_sed_extra\\\" \"$ac_file_inputs\" | $AWK -f \"$ac_tmp/subs.awk\" \\\n  >$ac_tmp/out || as_fn_error $? \"could not create $ac_file\" \"$LINENO\" 5\n\ntest -z \"$ac_datarootdir_hack$ac_datarootdir_seen\" &&\n  { ac_out=`sed -n '/\\${datarootdir}/p' \"$ac_tmp/out\"`; test -n \"$ac_out\"; } &&\n  { ac_out=`sed -n '/^[\t ]*datarootdir[\t ]*:*=/p' \\\n      \"$ac_tmp/out\"`; test -z \"$ac_out\"; } &&\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: $ac_file contains a reference to the variable 'datarootdir'\nwhich seems to be undefined.  Please make sure it is defined\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: $ac_file contains a reference to the variable 'datarootdir'\nwhich seems to be undefined.  Please make sure it is defined\" >&2;}\n\n  rm -f \"$ac_tmp/stdin\"\n  case $ac_file in\n  -) cat \"$ac_tmp/out\" && rm -f \"$ac_tmp/out\";;\n  *) rm -f \"$ac_file\" && mv \"$ac_tmp/out\" \"$ac_file\";;\n  esac \\\n  || as_fn_error $? \"could not create $ac_file\" \"$LINENO\" 5\n ;;\n  :H)\n  #\n  # CONFIG_HEADER\n  #\n  if test x\"$ac_file\" != x-; then\n    {\n      printf \"%s\\n\" \"/* $configure_input  */\" >&1 \\\n      && eval '$AWK -f \"$ac_tmp/defines.awk\"' \"$ac_file_inputs\"\n    } >\"$ac_tmp/config.h\" \\\n      || as_fn_error $? \"could not create $ac_file\" \"$LINENO\" 5\n    if diff \"$ac_file\" \"$ac_tmp/config.h\" >/dev/null 2>&1; then\n      { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: $ac_file is unchanged\" >&5\nprintf \"%s\\n\" \"$as_me: $ac_file is unchanged\" >&6;}\n    else\n      rm -f \"$ac_file\"\n      mv \"$ac_tmp/config.h\" \"$ac_file\" \\\n\t|| as_fn_error $? \"could not create $ac_file\" \"$LINENO\" 5\n    fi\n  else\n    printf \"%s\\n\" \"/* $configure_input  */\" >&1 \\\n      && eval '$AWK -f \"$ac_tmp/defines.awk\"' \"$ac_file_inputs\" \\\n      || as_fn_error $? \"could not create -\" \"$LINENO\" 5\n  fi\n# Compute \"$ac_file\"'s index in $config_headers.\n_am_arg=\"$ac_file\"\n_am_stamp_count=1\nfor _am_header in $config_headers :; do\n  case $_am_header in\n    $_am_arg | $_am_arg:* )\n      break ;;\n    * )\n      _am_stamp_count=`expr $_am_stamp_count + 1` ;;\n  esac\ndone\necho \"timestamp for $_am_arg\" >`$as_dirname -- \"$_am_arg\" ||\n$as_expr X\"$_am_arg\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$_am_arg\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$_am_arg\" : 'X\\(//\\)$' \\| \\\n\t X\"$_am_arg\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X\"$_am_arg\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)[^/].*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`/stamp-h$_am_stamp_count\n ;;\n\n  :C)  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: executing $ac_file commands\" >&5\nprintf \"%s\\n\" \"$as_me: executing $ac_file commands\" >&6;}\n ;;\n  esac\n\n\n  case $ac_file$ac_mode in\n    \"depfiles\":C) test x\"$AMDEP_TRUE\" != x\"\" || {\n  # Older Autoconf quotes --file arguments for eval, but not when files\n  # are listed without --file.  Let's play safe and only enable the eval\n  # if we detect the quoting.\n  # TODO: see whether this extra hack can be removed once we start\n  # requiring Autoconf 2.70 or later.\n  case $CONFIG_FILES in #(\n  *\\'*) :\n    eval set x \"$CONFIG_FILES\" ;; #(\n  *) :\n    set x $CONFIG_FILES ;; #(\n  *) :\n     ;;\nesac\n  shift\n  # Used to flag and report bootstrapping failures.\n  am_rc=0\n  for am_mf\n  do\n    # Strip MF so we end up with the name of the file.\n    am_mf=`printf \"%s\\n\" \"$am_mf\" | sed -e 's/:.*$//'`\n    # Check whether this is an Automake generated Makefile which includes\n    # dependency-tracking related rules and includes.\n    # Grep'ing the whole file directly is not great: AIX grep has a line\n    # limit of 2048, but all sed's we know have understand at least 4000.\n    sed -n 's,^am--depfiles:.*,X,p' \"$am_mf\" | grep X >/dev/null 2>&1 \\\n      || continue\n    am_dirpart=`$as_dirname -- \"$am_mf\" ||\n$as_expr X\"$am_mf\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$am_mf\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$am_mf\" : 'X\\(//\\)$' \\| \\\n\t X\"$am_mf\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X\"$am_mf\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)[^/].*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`\n    am_filepart=`$as_basename -- \"$am_mf\" ||\n$as_expr X/\"$am_mf\" : '.*/\\([^/][^/]*\\)/*$' \\| \\\n\t X\"$am_mf\" : 'X\\(//\\)$' \\| \\\n\t X\"$am_mf\" : 'X\\(/\\)' \\| . 2>/dev/null ||\nprintf \"%s\\n\" X/\"$am_mf\" |\n    sed '/^.*\\/\\([^/][^/]*\\)\\/*$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\/\\(\\/\\/\\)$/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  /^X\\/\\(\\/\\).*/{\n\t    s//\\1/\n\t    q\n\t  }\n\t  s/.*/./; q'`\n    { echo \"$as_me:$LINENO: cd \"$am_dirpart\" \\\n      && sed -e '/# am--include-marker/d' \"$am_filepart\" \\\n        | $MAKE -f - am--depfiles\" >&5\n   (cd \"$am_dirpart\" \\\n      && sed -e '/# am--include-marker/d' \"$am_filepart\" \\\n        | $MAKE -f - am--depfiles) >&5 2>&5\n   ac_status=$?\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n   (exit $ac_status); } || am_rc=$?\n  done\n  if test $am_rc -ne 0; then\n    { { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: error: in '$ac_pwd':\" >&5\nprintf \"%s\\n\" \"$as_me: error: in '$ac_pwd':\" >&2;}\nas_fn_error $? \"Something went wrong bootstrapping makefile fragments\n    for automatic dependency tracking.  If GNU make was not used, consider\n    re-running the configure script with MAKE=\\\"gmake\\\" (or whatever is\n    necessary).  You can also try re-running configure with the\n    '--disable-dependency-tracking' option to at least be able to build\n    the package (albeit without support for automatic dependency tracking).\nSee 'config.log' for more details\" \"$LINENO\" 5; }\n  fi\n  { am_dirpart=; unset am_dirpart;}\n  { am_filepart=; unset am_filepart;}\n  { am_mf=; unset am_mf;}\n  { am_rc=; unset am_rc;}\n  rm -f conftest-deps.mk\n}\n ;;\n    \"libtool\":C)\n\n    # See if we are running on zsh, and set the options that allow our\n    # commands through without removal of \\ escapes.\n    if test -n \"${ZSH_VERSION+set}\"; then\n      setopt NO_GLOB_SUBST\n    fi\n\n    cfgfile=${ofile}T\n    trap \"$RM \\\"$cfgfile\\\"; exit 1\" 1 2 15\n    $RM \"$cfgfile\"\n\n    cat <<_LT_EOF >> \"$cfgfile\"\n#! $SHELL\n# Generated automatically by $as_me ($PACKAGE) $VERSION\n# Libtool was configured on host `(hostname || uname -n) 2>/dev/null | sed 1q`:\n# NOTE: Changes made to this file will be lost: look at ltmain.sh.\n\n# Provide generalized library-building support services.\n# Written by Gordon Matzigkeit, 1996\n\n# Copyright (C) 2014 Free Software Foundation, Inc.\n# This is free software; see the source for copying conditions.  There is NO\n# warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\n# GNU Libtool is free software; you can redistribute it and/or modify\n# it under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 2 of of the License, or\n# (at your option) any later version.\n#\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program or library that is built\n# using GNU Libtool, you may include this file under the  same\n# distribution terms that you use for the rest of that program.\n#\n# GNU Libtool is distributed in the hope that it will be useful, but\n# WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n# GNU General Public License for more details.\n#\n# You should have received a copy of the GNU General Public License\n# along with this program.  If not, see <http://www.gnu.org/licenses/>.\n\n\n# The names of the tagged configurations supported by this script.\navailable_tags='CXX '\n\n# Configured defaults for sys_lib_dlsearch_path munging.\n: \\${LT_SYS_LIBRARY_PATH=\"$configure_time_lt_sys_library_path\"}\n\n# ### BEGIN LIBTOOL CONFIG\n\n# Which release of libtool.m4 was used?\nmacro_version=$macro_version\nmacro_revision=$macro_revision\n\n# Assembler program.\nAS=$lt_AS\n\n# DLL creation program.\nDLLTOOL=$lt_DLLTOOL\n\n# Object dumper program.\nOBJDUMP=$lt_OBJDUMP\n\n# Whether or not to build shared libraries.\nbuild_libtool_libs=$enable_shared\n\n# Whether or not to build static libraries.\nbuild_old_libs=$enable_static\n\n# What type of objects to build.\npic_mode=$pic_mode\n\n# Whether or not to optimize for fast installation.\nfast_install=$enable_fast_install\n\n# Shared archive member basename,for filename based shared library versioning on AIX.\nshared_archive_member_spec=$shared_archive_member_spec\n\n# Shell to use when invoking shell scripts.\nSHELL=$lt_SHELL\n\n# An echo program that protects backslashes.\nECHO=$lt_ECHO\n\n# The PATH separator for the build system.\nPATH_SEPARATOR=$lt_PATH_SEPARATOR\n\n# The host system.\nhost_alias=$host_alias\nhost=$host\nhost_os=$host_os\n\n# The build system.\nbuild_alias=$build_alias\nbuild=$build\nbuild_os=$build_os\n\n# A sed program that does not truncate output.\nSED=$lt_SED\n\n# Sed that helps us avoid accidentally triggering echo(1) options like -n.\nXsed=\"\\$SED -e 1s/^X//\"\n\n# A grep program that handles long lines.\nGREP=$lt_GREP\n\n# An ERE matcher.\nEGREP=$lt_EGREP\n\n# A literal string matcher.\nFGREP=$lt_FGREP\n\n# A BSD- or MS-compatible name lister.\nNM=$lt_NM\n\n# Whether we need soft or hard links.\nLN_S=$lt_LN_S\n\n# What is the maximum length of a command?\nmax_cmd_len=$max_cmd_len\n\n# Object file suffix (normally \"o\").\nobjext=$ac_objext\n\n# Executable file suffix (normally \"\").\nexeext=$exeext\n\n# whether the shell understands \"unset\".\nlt_unset=$lt_unset\n\n# turn spaces into newlines.\nSP2NL=$lt_lt_SP2NL\n\n# turn newlines into spaces.\nNL2SP=$lt_lt_NL2SP\n\n# convert \\$build file names to \\$host format.\nto_host_file_cmd=$lt_cv_to_host_file_cmd\n\n# convert \\$build files to toolchain format.\nto_tool_file_cmd=$lt_cv_to_tool_file_cmd\n\n# A file(cmd) program that detects file types.\nFILECMD=$lt_FILECMD\n\n# Method to check whether dependent libraries are shared objects.\ndeplibs_check_method=$lt_deplibs_check_method\n\n# Command to use when deplibs_check_method = \"file_magic\".\nfile_magic_cmd=$lt_file_magic_cmd\n\n# How to find potential files when deplibs_check_method = \"file_magic\".\nfile_magic_glob=$lt_file_magic_glob\n\n# Find potential files using nocaseglob when deplibs_check_method = \"file_magic\".\nwant_nocaseglob=$lt_want_nocaseglob\n\n# Command to associate shared and link libraries.\nsharedlib_from_linklib_cmd=$lt_sharedlib_from_linklib_cmd\n\n# The archiver.\nAR=$lt_AR\n\n# Flags to create an archive (by configure).\nlt_ar_flags=$lt_ar_flags\n\n# Flags to create an archive.\nAR_FLAGS=\\${ARFLAGS-\"\\$lt_ar_flags\"}\n\n# How to feed a file listing to the archiver.\narchiver_list_spec=$lt_archiver_list_spec\n\n# A symbol stripping program.\nSTRIP=$lt_STRIP\n\n# Commands used to install an old-style archive.\nRANLIB=$lt_RANLIB\nold_postinstall_cmds=$lt_old_postinstall_cmds\nold_postuninstall_cmds=$lt_old_postuninstall_cmds\n\n# Whether to use a lock for old archive extraction.\nlock_old_archive_extraction=$lock_old_archive_extraction\n\n# A C compiler.\nLTCC=$lt_CC\n\n# LTCC compiler flags.\nLTCFLAGS=$lt_CFLAGS\n\n# Take the output of nm and produce a listing of raw symbols and C names.\nglobal_symbol_pipe=$lt_lt_cv_sys_global_symbol_pipe\n\n# Transform the output of nm in a proper C declaration.\nglobal_symbol_to_cdecl=$lt_lt_cv_sys_global_symbol_to_cdecl\n\n# Transform the output of nm into a list of symbols to manually relocate.\nglobal_symbol_to_import=$lt_lt_cv_sys_global_symbol_to_import\n\n# Transform the output of nm in a C name address pair.\nglobal_symbol_to_c_name_address=$lt_lt_cv_sys_global_symbol_to_c_name_address\n\n# Transform the output of nm in a C name address pair when lib prefix is needed.\nglobal_symbol_to_c_name_address_lib_prefix=$lt_lt_cv_sys_global_symbol_to_c_name_address_lib_prefix\n\n# The name lister interface.\nnm_interface=$lt_lt_cv_nm_interface\n\n# Specify filename containing input files for \\$NM.\nnm_file_list_spec=$lt_nm_file_list_spec\n\n# The root where to search for dependent libraries,and where our libraries should be installed.\nlt_sysroot=$lt_sysroot\n\n# Command to truncate a binary pipe.\nlt_truncate_bin=$lt_lt_cv_truncate_bin\n\n# The name of the directory that contains temporary libtool files.\nobjdir=$objdir\n\n# Used to examine libraries when file_magic_cmd begins with \"file\".\nMAGIC_CMD=$MAGIC_CMD\n\n# Must we lock files when doing compilation?\nneed_locks=$lt_need_locks\n\n# Manifest tool.\nMANIFEST_TOOL=$lt_MANIFEST_TOOL\n\n# Tool to manipulate archived DWARF debug symbol files on Mac OS X.\nDSYMUTIL=$lt_DSYMUTIL\n\n# Tool to change global to local symbols on Mac OS X.\nNMEDIT=$lt_NMEDIT\n\n# Tool to manipulate fat objects and archives on Mac OS X.\nLIPO=$lt_LIPO\n\n# ldd/readelf like tool for Mach-O binaries on Mac OS X.\nOTOOL=$lt_OTOOL\n\n# ldd/readelf like tool for 64 bit Mach-O binaries on Mac OS X 10.4.\nOTOOL64=$lt_OTOOL64\n\n# Old archive suffix (normally \"a\").\nlibext=$libext\n\n# Shared library suffix (normally \".so\").\nshrext_cmds=$lt_shrext_cmds\n\n# The commands to extract the exported symbol list from a shared archive.\nextract_expsyms_cmds=$lt_extract_expsyms_cmds\n\n# Variables whose values should be saved in libtool wrapper scripts and\n# restored at link time.\nvariables_saved_for_relink=$lt_variables_saved_for_relink\n\n# Do we need the \"lib\" prefix for modules?\nneed_lib_prefix=$need_lib_prefix\n\n# Do we need a version for libraries?\nneed_version=$need_version\n\n# Library versioning type.\nversion_type=$version_type\n\n# Shared library runtime path variable.\nrunpath_var=$runpath_var\n\n# Shared library path variable.\nshlibpath_var=$shlibpath_var\n\n# Is shlibpath searched before the hard-coded library search path?\nshlibpath_overrides_runpath=$shlibpath_overrides_runpath\n\n# Format of library name prefix.\nlibname_spec=$lt_libname_spec\n\n# List of archive names.  First name is the real one, the rest are links.\n# The last name is the one that the linker finds with -lNAME\nlibrary_names_spec=$lt_library_names_spec\n\n# The coded name of the library, if different from the real name.\nsoname_spec=$lt_soname_spec\n\n# Permission mode override for installation of shared libraries.\ninstall_override_mode=$lt_install_override_mode\n\n# Command to use after installation of a shared archive.\npostinstall_cmds=$lt_postinstall_cmds\n\n# Command to use after uninstallation of a shared archive.\npostuninstall_cmds=$lt_postuninstall_cmds\n\n# Commands used to finish a libtool library installation in a directory.\nfinish_cmds=$lt_finish_cmds\n\n# As \"finish_cmds\", except a single script fragment to be evaled but\n# not shown.\nfinish_eval=$lt_finish_eval\n\n# Whether we should hardcode library paths into libraries.\nhardcode_into_libs=$hardcode_into_libs\n\n# Compile-time system search path for libraries.\nsys_lib_search_path_spec=$lt_sys_lib_search_path_spec\n\n# Detected run-time system search path for libraries.\nsys_lib_dlsearch_path_spec=$lt_configure_time_dlsearch_path\n\n# Explicit LT_SYS_LIBRARY_PATH set during ./configure time.\nconfigure_time_lt_sys_library_path=$lt_configure_time_lt_sys_library_path\n\n# Whether dlopen is supported.\ndlopen_support=$enable_dlopen\n\n# Whether dlopen of programs is supported.\ndlopen_self=$enable_dlopen_self\n\n# Whether dlopen of statically linked programs is supported.\ndlopen_self_static=$enable_dlopen_self_static\n\n# Commands to strip libraries.\nold_striplib=$lt_old_striplib\nstriplib=$lt_striplib\n\n\n# The linker used to build libraries.\nLD=$lt_LD\n\n# How to create reloadable object files.\nreload_flag=$lt_reload_flag\nreload_cmds=$lt_reload_cmds\n\n# Commands used to build an old-style archive.\nold_archive_cmds=$lt_old_archive_cmds\n\n# A language specific compiler.\nCC=$lt_compiler\n\n# Is the compiler the GNU compiler?\nwith_gcc=$GCC\n\n# Compiler flag to turn off builtin functions.\nno_builtin_flag=$lt_lt_prog_compiler_no_builtin_flag\n\n# Additional compiler flags for building library objects.\npic_flag=$lt_lt_prog_compiler_pic\n\n# How to pass a linker flag through the compiler.\nwl=$lt_lt_prog_compiler_wl\n\n# Compiler flag to prevent dynamic linking.\nlink_static_flag=$lt_lt_prog_compiler_static\n\n# Does compiler simultaneously support -c and -o options?\ncompiler_c_o=$lt_lt_cv_prog_compiler_c_o\n\n# Whether or not to add -lc for building shared libraries.\nbuild_libtool_need_lc=$archive_cmds_need_lc\n\n# Whether or not to disallow shared libs when runtime libs are static.\nallow_libtool_libs_with_static_runtimes=$enable_shared_with_static_runtimes\n\n# Compiler flag to allow reflexive dlopens.\nexport_dynamic_flag_spec=$lt_export_dynamic_flag_spec\n\n# Compiler flag to generate shared objects directly from archives.\nwhole_archive_flag_spec=$lt_whole_archive_flag_spec\n\n# Whether the compiler copes with passing no objects directly.\ncompiler_needs_object=$lt_compiler_needs_object\n\n# Create an old-style archive from a shared archive.\nold_archive_from_new_cmds=$lt_old_archive_from_new_cmds\n\n# Create a temporary old-style archive to link instead of a shared archive.\nold_archive_from_expsyms_cmds=$lt_old_archive_from_expsyms_cmds\n\n# Commands used to build a shared archive.\narchive_cmds=$lt_archive_cmds\narchive_expsym_cmds=$lt_archive_expsym_cmds\n\n# Commands used to build a loadable module if different from building\n# a shared archive.\nmodule_cmds=$lt_module_cmds\nmodule_expsym_cmds=$lt_module_expsym_cmds\n\n# Whether we are building with GNU ld or not.\nwith_gnu_ld=$lt_with_gnu_ld\n\n# Flag that allows shared libraries with undefined symbols to be built.\nallow_undefined_flag=$lt_allow_undefined_flag\n\n# Flag that enforces no undefined symbols.\nno_undefined_flag=$lt_no_undefined_flag\n\n# Flag to hardcode \\$libdir into a binary during linking.\n# This must work even if \\$libdir does not exist\nhardcode_libdir_flag_spec=$lt_hardcode_libdir_flag_spec\n\n# Whether we need a single \"-rpath\" flag with a separated argument.\nhardcode_libdir_separator=$lt_hardcode_libdir_separator\n\n# Set to \"yes\" if using DIR/libNAME\\$shared_ext during linking hardcodes\n# DIR into the resulting binary.\nhardcode_direct=$hardcode_direct\n\n# Set to \"yes\" if using DIR/libNAME\\$shared_ext during linking hardcodes\n# DIR into the resulting binary and the resulting library dependency is\n# \"absolute\",i.e impossible to change by setting \\$shlibpath_var if the\n# library is relocated.\nhardcode_direct_absolute=$hardcode_direct_absolute\n\n# Set to \"yes\" if using the -LDIR flag during linking hardcodes DIR\n# into the resulting binary.\nhardcode_minus_L=$hardcode_minus_L\n\n# Set to \"yes\" if using SHLIBPATH_VAR=DIR during linking hardcodes DIR\n# into the resulting binary.\nhardcode_shlibpath_var=$hardcode_shlibpath_var\n\n# Set to \"yes\" if building a shared library automatically hardcodes DIR\n# into the library and all subsequent libraries and executables linked\n# against it.\nhardcode_automatic=$hardcode_automatic\n\n# Set to yes if linker adds runtime paths of dependent libraries\n# to runtime path list.\ninherit_rpath=$inherit_rpath\n\n# Whether libtool must link a program against all its dependency libraries.\nlink_all_deplibs=$link_all_deplibs\n\n# Set to \"yes\" if exported symbols are required.\nalways_export_symbols=$always_export_symbols\n\n# The commands to list exported symbols.\nexport_symbols_cmds=$lt_export_symbols_cmds\n\n# Symbols that should not be listed in the preloaded symbols.\nexclude_expsyms=$lt_exclude_expsyms\n\n# Symbols that must always be exported.\ninclude_expsyms=$lt_include_expsyms\n\n# Commands necessary for linking programs (against libraries) with templates.\nprelink_cmds=$lt_prelink_cmds\n\n# Commands necessary for finishing linking programs.\npostlink_cmds=$lt_postlink_cmds\n\n# Specify filename containing input files.\nfile_list_spec=$lt_file_list_spec\n\n# How to hardcode a shared library path into an executable.\nhardcode_action=$hardcode_action\n\n# The directories searched by this compiler when creating a shared library.\ncompiler_lib_search_dirs=$lt_compiler_lib_search_dirs\n\n# Dependencies to place before and after the objects being linked to\n# create a shared library.\npredep_objects=$lt_predep_objects\npostdep_objects=$lt_postdep_objects\npredeps=$lt_predeps\npostdeps=$lt_postdeps\n\n# The library search path used internally by the compiler when linking\n# a shared library.\ncompiler_lib_search_path=$lt_compiler_lib_search_path\n\n# ### END LIBTOOL CONFIG\n\n_LT_EOF\n\n    cat <<'_LT_EOF' >> \"$cfgfile\"\n\n# ### BEGIN FUNCTIONS SHARED WITH CONFIGURE\n\n# func_munge_path_list VARIABLE PATH\n# -----------------------------------\n# VARIABLE is name of variable containing _space_ separated list of\n# directories to be munged by the contents of PATH, which is string\n# having a format:\n# \"DIR[:DIR]:\"\n#       string \"DIR[ DIR]\" will be prepended to VARIABLE\n# \":DIR[:DIR]\"\n#       string \"DIR[ DIR]\" will be appended to VARIABLE\n# \"DIRP[:DIRP]::[DIRA:]DIRA\"\n#       string \"DIRP[ DIRP]\" will be prepended to VARIABLE and string\n#       \"DIRA[ DIRA]\" will be appended to VARIABLE\n# \"DIR[:DIR]\"\n#       VARIABLE will be replaced by \"DIR[ DIR]\"\nfunc_munge_path_list ()\n{\n    case x$2 in\n    x)\n        ;;\n    *:)\n        eval $1=\\\"`$ECHO $2 | $SED 's/:/ /g'` \\$$1\\\"\n        ;;\n    x:*)\n        eval $1=\\\"\\$$1 `$ECHO $2 | $SED 's/:/ /g'`\\\"\n        ;;\n    *::*)\n        eval $1=\\\"\\$$1\\ `$ECHO $2 | $SED -e 's/.*:://' -e 's/:/ /g'`\\\"\n        eval $1=\\\"`$ECHO $2 | $SED -e 's/::.*//' -e 's/:/ /g'`\\ \\$$1\\\"\n        ;;\n    *)\n        eval $1=\\\"`$ECHO $2 | $SED 's/:/ /g'`\\\"\n        ;;\n    esac\n}\n\n\n# Calculate cc_basename.  Skip known compiler wrappers and cross-prefix.\nfunc_cc_basename ()\n{\n    for cc_temp in $*\"\"; do\n      case $cc_temp in\n        compile | *[\\\\/]compile | ccache | *[\\\\/]ccache ) ;;\n        distcc | *[\\\\/]distcc | purify | *[\\\\/]purify ) ;;\n        \\-*) ;;\n        *) break;;\n      esac\n    done\n    func_cc_basename_result=`$ECHO \"$cc_temp\" | $SED \"s%.*/%%; s%^$host_alias-%%\"`\n}\n\n\n# ### END FUNCTIONS SHARED WITH CONFIGURE\n\n_LT_EOF\n\n  case $host_os in\n  aix3*)\n    cat <<\\_LT_EOF >> \"$cfgfile\"\n# AIX sometimes has problems with the GCC collect2 program.  For some\n# reason, if we set the COLLECT_NAMES environment variable, the problems\n# vanish in a puff of smoke.\nif test set != \"${COLLECT_NAMES+set}\"; then\n  COLLECT_NAMES=\n  export COLLECT_NAMES\nfi\n_LT_EOF\n    ;;\n  esac\n\n\n\nltmain=$ac_aux_dir/ltmain.sh\n\n\n  # We use sed instead of cat because bash on DJGPP gets confused if\n  # if finds mixed CR/LF and LF-only lines.  Since sed operates in\n  # text mode, it properly converts lines to CR/LF.  This bash problem\n  # is reportedly fixed, but why not run on old versions too?\n  $SED '$q' \"$ltmain\" >> \"$cfgfile\" \\\n     || (rm -f \"$cfgfile\"; exit 1)\n\n   mv -f \"$cfgfile\" \"$ofile\" ||\n    (rm -f \"$ofile\" && cp \"$cfgfile\" \"$ofile\" && rm -f \"$cfgfile\")\n  chmod +x \"$ofile\"\n\n\n    cat <<_LT_EOF >> \"$ofile\"\n\n# ### BEGIN LIBTOOL TAG CONFIG: CXX\n\n# The linker used to build libraries.\nLD=$lt_LD_CXX\n\n# How to create reloadable object files.\nreload_flag=$lt_reload_flag_CXX\nreload_cmds=$lt_reload_cmds_CXX\n\n# Commands used to build an old-style archive.\nold_archive_cmds=$lt_old_archive_cmds_CXX\n\n# A language specific compiler.\nCC=$lt_compiler_CXX\n\n# Is the compiler the GNU compiler?\nwith_gcc=$GCC_CXX\n\n# Compiler flag to turn off builtin functions.\nno_builtin_flag=$lt_lt_prog_compiler_no_builtin_flag_CXX\n\n# Additional compiler flags for building library objects.\npic_flag=$lt_lt_prog_compiler_pic_CXX\n\n# How to pass a linker flag through the compiler.\nwl=$lt_lt_prog_compiler_wl_CXX\n\n# Compiler flag to prevent dynamic linking.\nlink_static_flag=$lt_lt_prog_compiler_static_CXX\n\n# Does compiler simultaneously support -c and -o options?\ncompiler_c_o=$lt_lt_cv_prog_compiler_c_o_CXX\n\n# Whether or not to add -lc for building shared libraries.\nbuild_libtool_need_lc=$archive_cmds_need_lc_CXX\n\n# Whether or not to disallow shared libs when runtime libs are static.\nallow_libtool_libs_with_static_runtimes=$enable_shared_with_static_runtimes_CXX\n\n# Compiler flag to allow reflexive dlopens.\nexport_dynamic_flag_spec=$lt_export_dynamic_flag_spec_CXX\n\n# Compiler flag to generate shared objects directly from archives.\nwhole_archive_flag_spec=$lt_whole_archive_flag_spec_CXX\n\n# Whether the compiler copes with passing no objects directly.\ncompiler_needs_object=$lt_compiler_needs_object_CXX\n\n# Create an old-style archive from a shared archive.\nold_archive_from_new_cmds=$lt_old_archive_from_new_cmds_CXX\n\n# Create a temporary old-style archive to link instead of a shared archive.\nold_archive_from_expsyms_cmds=$lt_old_archive_from_expsyms_cmds_CXX\n\n# Commands used to build a shared archive.\narchive_cmds=$lt_archive_cmds_CXX\narchive_expsym_cmds=$lt_archive_expsym_cmds_CXX\n\n# Commands used to build a loadable module if different from building\n# a shared archive.\nmodule_cmds=$lt_module_cmds_CXX\nmodule_expsym_cmds=$lt_module_expsym_cmds_CXX\n\n# Whether we are building with GNU ld or not.\nwith_gnu_ld=$lt_with_gnu_ld_CXX\n\n# Flag that allows shared libraries with undefined symbols to be built.\nallow_undefined_flag=$lt_allow_undefined_flag_CXX\n\n# Flag that enforces no undefined symbols.\nno_undefined_flag=$lt_no_undefined_flag_CXX\n\n# Flag to hardcode \\$libdir into a binary during linking.\n# This must work even if \\$libdir does not exist\nhardcode_libdir_flag_spec=$lt_hardcode_libdir_flag_spec_CXX\n\n# Whether we need a single \"-rpath\" flag with a separated argument.\nhardcode_libdir_separator=$lt_hardcode_libdir_separator_CXX\n\n# Set to \"yes\" if using DIR/libNAME\\$shared_ext during linking hardcodes\n# DIR into the resulting binary.\nhardcode_direct=$hardcode_direct_CXX\n\n# Set to \"yes\" if using DIR/libNAME\\$shared_ext during linking hardcodes\n# DIR into the resulting binary and the resulting library dependency is\n# \"absolute\",i.e impossible to change by setting \\$shlibpath_var if the\n# library is relocated.\nhardcode_direct_absolute=$hardcode_direct_absolute_CXX\n\n# Set to \"yes\" if using the -LDIR flag during linking hardcodes DIR\n# into the resulting binary.\nhardcode_minus_L=$hardcode_minus_L_CXX\n\n# Set to \"yes\" if using SHLIBPATH_VAR=DIR during linking hardcodes DIR\n# into the resulting binary.\nhardcode_shlibpath_var=$hardcode_shlibpath_var_CXX\n\n# Set to \"yes\" if building a shared library automatically hardcodes DIR\n# into the library and all subsequent libraries and executables linked\n# against it.\nhardcode_automatic=$hardcode_automatic_CXX\n\n# Set to yes if linker adds runtime paths of dependent libraries\n# to runtime path list.\ninherit_rpath=$inherit_rpath_CXX\n\n# Whether libtool must link a program against all its dependency libraries.\nlink_all_deplibs=$link_all_deplibs_CXX\n\n# Set to \"yes\" if exported symbols are required.\nalways_export_symbols=$always_export_symbols_CXX\n\n# The commands to list exported symbols.\nexport_symbols_cmds=$lt_export_symbols_cmds_CXX\n\n# Symbols that should not be listed in the preloaded symbols.\nexclude_expsyms=$lt_exclude_expsyms_CXX\n\n# Symbols that must always be exported.\ninclude_expsyms=$lt_include_expsyms_CXX\n\n# Commands necessary for linking programs (against libraries) with templates.\nprelink_cmds=$lt_prelink_cmds_CXX\n\n# Commands necessary for finishing linking programs.\npostlink_cmds=$lt_postlink_cmds_CXX\n\n# Specify filename containing input files.\nfile_list_spec=$lt_file_list_spec_CXX\n\n# How to hardcode a shared library path into an executable.\nhardcode_action=$hardcode_action_CXX\n\n# The directories searched by this compiler when creating a shared library.\ncompiler_lib_search_dirs=$lt_compiler_lib_search_dirs_CXX\n\n# Dependencies to place before and after the objects being linked to\n# create a shared library.\npredep_objects=$lt_predep_objects_CXX\npostdep_objects=$lt_postdep_objects_CXX\npredeps=$lt_predeps_CXX\npostdeps=$lt_postdeps_CXX\n\n# The library search path used internally by the compiler when linking\n# a shared library.\ncompiler_lib_search_path=$lt_compiler_lib_search_path_CXX\n\n# ### END LIBTOOL TAG CONFIG: CXX\n_LT_EOF\n\n ;;\n    \"dddmp/exp/test1.sh\":F) chmod +x dddmp/exp/test1.sh ;;\n    \"dddmp/exp/test2.sh\":F) chmod +x dddmp/exp/test2.sh ;;\n    \"dddmp/exp/test3.sh\":F) chmod +x dddmp/exp/test3.sh ;;\n    \"dddmp/exp/test4.sh\":F) chmod +x dddmp/exp/test4.sh ;;\n    \"dddmp/exp/test5.sh\":F) chmod +x dddmp/exp/test5.sh ;;\n    \"dddmp/exp/test6.sh\":F) chmod +x dddmp/exp/test6.sh ;;\n    \"dddmp/exp/test7.sh\":F) chmod +x dddmp/exp/test7.sh ;;\n\n  esac\ndone # for ac_tag\n\n\nas_fn_exit 0\n_ACEOF\nac_clean_files=$ac_clean_files_save\n\ntest $ac_write_fail = 0 ||\n  as_fn_error $? \"write failure creating $CONFIG_STATUS\" \"$LINENO\" 5\n\n\n# configure is writing to config.log, and then calls config.status.\n# config.status does its own redirection, appending to config.log.\n# Unfortunately, on DOS this fails, as config.log is still kept open\n# by configure, so config.status won't be able to write to it; its\n# output is simply discarded.  So we exec the FD to /dev/null,\n# effectively closing config.log, so it can be properly (re)opened and\n# appended to by config.status.  When coming back to configure, we\n# need to make the FD available again.\nif test \"$no_create\" != yes; then\n  ac_cs_success=:\n  ac_config_status_args=\n  test \"$silent\" = yes &&\n    ac_config_status_args=\"$ac_config_status_args --quiet\"\n  exec 5>/dev/null\n  $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false\n  exec 5>>config.log\n  # Use ||, not &&, to avoid exiting from the if with $? = 1, which\n  # would make configure fail if this is the last instruction.\n  $ac_cs_success || as_fn_exit 1\nfi\nif test -n \"$ac_unrecognized_opts\" && test \"$enable_option_checking\" != no; then\n  { printf \"%s\\n\" \"$as_me:${as_lineno-$LINENO}: WARNING: unrecognized options: $ac_unrecognized_opts\" >&5\nprintf \"%s\\n\" \"$as_me: WARNING: unrecognized options: $ac_unrecognized_opts\" >&2;}\nfi\n\n\necho \\\n\"--------------------------------------------------\nConfiguration summary for ${PACKAGE_NAME} ${PACKAGE_VERSION}\n\nBuild system   : ${build}\nHost system    : ${host}\nPrefix         : '${prefix}'\nCompilers      : '${CC} ${AM_CPPFLAGS} ${CPPFLAGS} ${AM_CFLAGS} ${CFLAGS}'\n               : '${CXX} ${AM_CPPFLAGS} ${CPPFLAGS} ${AM_CXXFLAGS} ${CXXFLAGS}'\nShared library : ${enable_shared}\n dddmp enabled : ${enable_dddmp:-no}\n obj enabled   : ${enable_obj:-no}\n--------------------------------------------------\"\n\n"
  },
  {
    "path": "cudd/configure.ac",
    "content": "#                                               -*- Autoconf -*-\n# Process this file with autoconf to produce a configure script.\n\nAC_PREREQ([2.69])\nAC_INIT([cudd], [3.0.0], [Fabio@Colorado.EDU])\nAC_CONFIG_AUX_DIR([build-aux])\nAC_CONFIG_MACRO_DIR([m4])\nAC_CANONICAL_HOST\nAM_INIT_AUTOMAKE(\n  [1.14 -Wall -Werror foreign subdir-objects color-tests silent-rules]\n)\nAC_REQUIRE_AUX_FILE([tap-driver.sh])\n\nAC_ARG_ENABLE([dddmp],\n  [AS_HELP_STRING([--enable-dddmp],[include libdddmp in libcudd])])\nAM_CONDITIONAL([DDDMP], [test x$enable_dddmp = xyes])\n\nAC_ARG_ENABLE([obj],\n  [AS_HELP_STRING([--enable-obj],[include libobj in libcudd])])\nAM_CONDITIONAL([OBJ], [test x$enable_obj = xyes])\n\nAC_ARG_WITH([system-qsort],\n  [AS_HELP_STRING([--with-system-qsort],\n                  [use system qsort instead of portable one])],\n  [],[with_system_qsort=no])\nif test x$with_system_qsort != xno ; then\n  AC_DEFINE([USE_SYSTEM_QSORT], [1], [Define to 1 to use system qsort])\nfi\n\n# Set our own default (instead of \"-g -O2\") unless CFLAGS is already defined.\n: ${CFLAGS=\"-Wall -Wextra -g -O3\"}\n: ${CXXFLAGS=\"-Wall -Wextra -std=c++0x -g -O3\"}\n\nAC_PROG_CC\nAC_PROG_CXX\nAM_PROG_AR\nLT_PREREQ([2.4])\nLT_INIT([win32-dll disable-shared])\n\nAC_CONFIG_SRCDIR([st/st.c])\nAC_CONFIG_HEADERS([config.h])\n\n# Checks for programs.\nAC_C_BIGENDIAN\nAM_CONDITIONAL([CROSS_COMPILING],[test x$cross_compiling = xyes])\n\n# Building documentation requires doxygen, pdflatex, and makeindex.\nAC_CHECK_PROGS([DOXYGEN], [doxygen])\nif test -z \"$DOXYGEN\"; then\n   AC_MSG_WARN([Doxygen not found - continuing without Doxygen support])\nfi\nAM_CONDITIONAL([HAVE_DOXYGEN],[test -n \"$DOXYGEN\"])\nAM_COND_IF([HAVE_DOXYGEN], [AC_CONFIG_FILES([Doxyfile])])\n\nAC_CHECK_PROGS([PDFLATEX], [pdflatex])\nif test -z \"$PDFLATEX\"; then\n    AC_MSG_WARN([pdflatex not found - unable to compile manual to PDF])\nfi\nAC_CHECK_PROGS([MAKEINDEX], [makeindex])\nif test -z \"$MAKEINDEX\"; then\n    AC_MSG_WARN([makeindex not found - unable to compile manual to PDF])\nfi\nAM_CONDITIONAL([HAVE_PDFLATEX],[test -n \"$PDFLATEX\" && test -n \"$MAKEINDEX\"])\nAM_COND_IF([HAVE_PDFLATEX], [AC_CONFIG_FILES([doc/cudd.tex])])\n\n# Checks for libraries.\n#AC_CHECK_LIB([m],[pow])\nAC_SEARCH_LIBS([pow],[m])\nAC_CHECK_LIB([pthread],[pthread_create],[have_pthreads=yes],[have_pthreads=no])\nAM_CONDITIONAL([HAVE_PTHREADS],[test x$have_pthreads = xyes])\n# Check for Windows API functions.\nAC_SEARCH_LIBS([WSAStartup],[ws2_32])\nAC_SEARCH_LIBS([GetProcessMemoryInfo],[psapi])\n\n# Checks for header files.\n# First check for mandatory headers...\nAC_CHECK_HEADERS([float.h inttypes.h limits.h stddef.h stdlib.h string.h assert.h math.h], [], [have_mandatory_headers=no])\nif test \"x${have_mandatory_headers}\" = xno; then\n  AC_MSG_ERROR([One or more mandatory headers missing.  Check 'config.log'.])\nfi\n# ...then check for optional C headers.\nAC_CHECK_HEADERS([unistd.h sys/time.h sys/times.h sys/resource.h sys/wait.h])\n# Finally, check C++ optional headers.\nAC_MSG_CHECKING([for working C++ thread header])\nAC_LANG_PUSH([C++])\nAC_COMPILE_IFELSE(\n  [AC_LANG_PROGRAM([#include <thread>], [[  std::thread([] {}).join()]])],\n  [have_working_thread=yes],[have_working_thread=no])\nAC_LANG_POP([C++])\nif test x$have_working_thread = xyes ; then\n  AC_MSG_RESULT(yes)\n  AC_DEFINE([HAVE_WORKING_THREAD], [1], [Define to 1 if C++ thread header is usable])\nelse\n  AC_MSG_RESULT(no)\nfi\n\n# Checks for typedefs, structures, and compiler characteristics.\nAC_CHECK_HEADER_STDBOOL\nAC_C_INLINE\nAC_TYPE_SIZE_T\nAC_TYPE_UINT16_T\nAC_TYPE_UINT32_T\nAC_CHECK_TYPES([ptrdiff_t])\nAC_CHECK_SIZEOF([int])\nAC_CHECK_SIZEOF([long])\nAC_CHECK_SIZEOF([void *])\nAC_CHECK_SIZEOF([long double])\nMINGW_AC_WIN32_NATIVE_HOST\nAM_CONDITIONAL([MINGW64], [test x$mingw_cv_win32_host = xyes])\nif test x$mingw_cv_win32_host = xyes ; then\n  AC_DEFINE([__USE_MINGW_ANSI_STDIO], [1], [Define to 1 to enable C99-compliant printf on MinGW-w64])\nfi\nMODERN_CXX\nif test x$ac_cv_have_modern_cxx = xyes ; then\n  AC_DEFINE([HAVE_MODERN_CXX], [1], [Define to 1 if your compiler supports enough C++11])\nfi\n\n# Checks for library functions.\n# First the mandatory functions...\nAC_CHECK_FUNCS([pow sqrt strchr strstr],\n  [], [have_mandatory_functions=no])\nif test \"x${have_mandatory_functions}\" = xno; then\n  AC_MSG_ERROR([One or more mandatory functions missing.  Check 'config.log'.])\nfi\n# ...then check for optional functions.   \nAC_CHECK_FUNCS([powl gethostname getrlimit getrusage sysconf])\n\n# Check for a working implementation of IEEE 754 floating point\n# Specifically, check for correct treatment of +Infinity\nAC_MSG_CHECKING([for +Infinity (IEEE 754 floating point)])\nAC_CACHE_VAL(ac_cv_have_ieee_754,\n[ AC_TRY_RUN([\n#include <math.h>\nint main(void)\n{\n    if (HUGE_VAL != HUGE_VAL * 3 || HUGE_VAL != HUGE_VAL / 3) return 1;\n    return 0;\n}\n],ac_cv_have_ieee_754=yes,ac_cv_have_ieee_754=no,ac_cv_have_ieee_754=maybe)])\nif test x$ac_cv_have_ieee_754 = xmaybe ; then\n  AC_COMPILE_IFELSE(\n  [AC_LANG_PROGRAM([#include <math.h>], [  double x = INFINITY])],\n  [ac_cv_have_ieee_754=yes],[ac_cv_have_ieee_754=no])\nfi\nif test x$ac_cv_have_ieee_754 = xyes ; then\n  AC_MSG_RESULT(yes)\n  AC_DEFINE([HAVE_IEEE_754], [1], [Define to 1 if you have working floating-point infinities])\nelse\n  AC_MSG_RESULT(no)\nfi\n\n\nAC_CONFIG_FILES([Makefile])\nAC_CONFIG_FILES([dddmp/exp/test1.sh], [chmod +x dddmp/exp/test1.sh])\nAC_CONFIG_FILES([dddmp/exp/test2.sh], [chmod +x dddmp/exp/test2.sh])\nAC_CONFIG_FILES([dddmp/exp/test3.sh], [chmod +x dddmp/exp/test3.sh])\nAC_CONFIG_FILES([dddmp/exp/test4.sh], [chmod +x dddmp/exp/test4.sh])\nAC_CONFIG_FILES([dddmp/exp/test5.sh], [chmod +x dddmp/exp/test5.sh])\nAC_CONFIG_FILES([dddmp/exp/test6.sh], [chmod +x dddmp/exp/test6.sh])\nAC_CONFIG_FILES([dddmp/exp/test7.sh], [chmod +x dddmp/exp/test7.sh])\n\nAC_OUTPUT\n\necho \\\n\"--------------------------------------------------\nConfiguration summary for ${PACKAGE_NAME} ${PACKAGE_VERSION}\n\nBuild system   : ${build}\nHost system    : ${host}\nPrefix         : '${prefix}'\nCompilers      : '${CC} ${AM_CPPFLAGS} ${CPPFLAGS} ${AM_CFLAGS} ${CFLAGS}'\n               : '${CXX} ${AM_CPPFLAGS} ${CPPFLAGS} ${AM_CXXFLAGS} ${CXXFLAGS}'\nShared library : ${enable_shared}\n dddmp enabled : ${enable_dddmp:-no}\n obj enabled   : ${enable_obj:-no}\n--------------------------------------------------\"\n"
  },
  {
    "path": "cudd/cplusplus/Included.am",
    "content": "cplusplus_sources = cplusplus/cuddObj.hh cplusplus/cuddObj.cc\n\nif OBJ\ncudd_libcudd_la_SOURCES += $(cplusplus_sources)\nelse\nnoinst_LTLIBRARIES += cplusplus/libobj.la\ncplusplus_libobj_la_SOURCES = $(cplusplus_sources)\ncplusplus_libobj_la_CPPFLAGS = -I$(top_srcdir)/cudd -I$(top_srcdir)/mtr \\\n  -I$(top_srcdir)/epd -I$(top_srcdir)/st\nendif !OBJ\n\ncheck_PROGRAMS += cplusplus/testobj cplusplus/testmulti\n\ncplusplus_testobj_SOURCES = cplusplus/testobj.cc\nif OBJ\ncplusplus_testobj_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\ncplusplus_testobj_LDADD =\nelse\ncplusplus_testobj_CPPFLAGS = $(cplusplus_libobj_la_CPPFLAGS)\ncplusplus_testobj_LDADD = cplusplus/libobj.la\nendif !OBJ\ncplusplus_testobj_LDADD +=  cudd/libcudd.la\n\ncplusplus_testmulti_SOURCES = cplusplus/testmulti.cc\nif OBJ\ncplusplus_testmulti_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\ncplusplus_testmulti_LDADD =\nelse\ncplusplus_testmulti_CPPFLAGS = $(cplusplus_libobj_la_CPPFLAGS)\ncplusplus_testmulti_LDADD = cplusplus/libobj.la\nendif !OBJ\ncplusplus_testmulti_LDADD += cudd/libcudd.la\nif HAVE_PTHREADS\ncplusplus_testmulti_LDFLAGS = -pthread\nendif HAVE_PTHREADS\n\ncheck_SCRIPTS += cplusplus/test_obj.test\ndist_check_DATA += cplusplus/test.out cplusplus/multi.out\nEXTRA_DIST += cplusplus/test_obj.test.in\nif !CROSS_COMPILING\nTESTS += cplusplus/test_obj.test\nendif !CROSS_COMPILING\n\ncplusplus/test_obj.test: cplusplus/test_obj.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\nCLEANFILES += cplusplus/test.tst cplusplus/multi.tst\n"
  },
  {
    "path": "cudd/cplusplus/cuddObj.cc",
    "content": "/**\n  @file\n\n  @ingroup cplusplus\n\n  @brief Functions for the C++ object-oriented encapsulation of CUDD.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n#include <iostream>\n#include <sstream>\n#include <cassert>\n#include <cstdlib>\n#include <cstring>\n#include <algorithm>\n#include <stdexcept>\n#include \"epdInt.h\"\n#include \"cuddInt.h\"\n#include \"cuddObj.hh\"\n\nusing std::cout;\nusing std::cerr;\nusing std::ostream;\nusing std::endl;\nusing std::hex;\nusing std::dec;\nusing std::string;\nusing std::vector;\nusing std::sort;\n\n// ---------------------------------------------------------------------------\n// Variable declarations\n// ---------------------------------------------------------------------------\n\n// ---------------------------------------------------------------------------\n// Members of class Capsule\n// ---------------------------------------------------------------------------\n\n/**\n  @brief Class for reference counting of CUDD managers.\n\n  @see Cudd DD ABDD ADD BDD ZDD\n\n*/\nclass Capsule {\npublic:\n    Capsule(unsigned int numVars, unsigned int numVarsZ,\n            unsigned int numSlots, unsigned int cacheSize,\n            unsigned long maxMemory, PFC defaultHandler);\n    ~Capsule();\n#if HAVE_MODERN_CXX == 1\n    Capsule(Capsule const &) = delete;\n    Capsule & operator=(Capsule const &) = delete;\n#else\nprivate:\n    Capsule(Capsule const &); // not defined\n    Capsule & operator=(Capsule const &); // not defined\npublic:\n#endif\n    DdManager *manager;\n    PFC errorHandler;\n    PFC timeoutHandler;\n    PFC terminationHandler;\n    std::vector<char *> varnames;\n    int ref;\n    bool verbose;\n};\n\n\nCapsule::Capsule(\n  unsigned int numVars,\n  unsigned int numVarsZ,\n  unsigned int numSlots,\n  unsigned int cacheSize,\n  unsigned long maxMemory,\n  PFC defaultHandler)\n{\n    errorHandler = defaultHandler;\n    timeoutHandler = defaultHandler;\n    terminationHandler = defaultHandler;\n    manager = Cudd_Init(numVars, numVarsZ, numSlots, cacheSize, maxMemory);\n    if (!manager)\n        errorHandler(\"Out of memory\");\n    verbose = 0; // initially terse\n    ref = 1;\n\n} // Capsule::Capsule\n\n\nCapsule::~Capsule()\n{\n#ifdef DD_DEBUG\n    if (manager) {\n        int retval = Cudd_CheckZeroRef(manager);\n        if (retval != 0) {\n            cerr << retval << \" unexpected non-zero reference counts\" << endl;\n        } else if (verbose) {\n            cerr << \"All went well\" << endl;\n        }\n    }\n#endif\n    for (vector<char *>::iterator it = varnames.begin();\n         it != varnames.end(); ++it) {\n        delete [] *it;\n    }   \n    Cudd_Quit(manager);\n\n} // Capsule::~Capsule\n\n\n// ---------------------------------------------------------------------------\n// Members of class DD\n// ---------------------------------------------------------------------------\n\n\nDD::DD() : p(0), node(0) {}\n\n\nDD::DD(Capsule *cap, DdNode *ddNode) : p(cap), node(ddNode) {\n    if (node) Cudd_Ref(node);\n    if (p->verbose) {\n\tcout << \"Standard DD constructor for node \" << hex << node << dec <<\n\t    \" ref = \" << Cudd_Regular(node)->ref << \"\\n\";\n    }\n\n} // DD::DD\n\n\nDD::DD(Cudd const & manager, DdNode *ddNode) : p(manager.p), node(ddNode) {\n    checkReturnValue(ddNode);\n    if (node) Cudd_Ref(node);\n    if (p->verbose) {\n\tcout << \"Standard DD constructor for node \" << hex << node << dec <<\n\t    \" ref = \" << Cudd_Regular(node)->ref << \"\\n\";\n    }\n\n} // DD::DD\n\n\nDD::DD(const DD &from) {\n    p = from.p;\n    node = from.node;\n    if (node) {\n\tCudd_Ref(node);\n\tif (p->verbose) {\n\t    cout << \"Copy DD constructor for node \" << hex << node << dec <<\n\t\t\" ref = \" << Cudd_Regular(node)->ref << \"\\n\";\n\t}\n    }\n\n} // DD::DD\n\n\nDD::~DD() {}\n\n\ninline DdManager *\nDD::checkSameManager(\n  const DD &other) const\n{\n    DdManager *mgr = p->manager;\n    if (mgr != other.p->manager) {\n\tp->errorHandler(\"Operands come from different manager.\");\n    }\n    return mgr;\n\n} // DD::checkSameManager\n\n\ninline void\nDD::checkReturnValue(\n  const void *result) const\n{\n    if (result == 0) {\n\tDdManager *mgr = p->manager;\n\tCudd_ErrorType errType = Cudd_ReadErrorCode(mgr);\n\tswitch (errType) {\n\tcase CUDD_MEMORY_OUT:\n\t    p->errorHandler(\"Out of memory.\");\n\t    break;\n\tcase CUDD_TOO_MANY_NODES:\n\t    break;\n\tcase CUDD_MAX_MEM_EXCEEDED:\n\t    p->errorHandler(\"Maximum memory exceeded.\");\n\t    break;\n        case CUDD_TIMEOUT_EXPIRED: \n            {\n                std::ostringstream msg;\n                unsigned long lag = \n                    Cudd_ReadElapsedTime(mgr) - Cudd_ReadTimeLimit(mgr);\n                msg << \"Timeout expired.  Lag = \" << lag << \" ms.\";\n                p->timeoutHandler(msg.str());\n            }\n\t    break;\n        case CUDD_TERMINATION:\n            {\n                std::ostringstream msg;\n                msg << \"Terminated.\\n\";\n                p->terminationHandler(msg.str());\n            }\n            break;\n\tcase CUDD_INVALID_ARG:\n\t    p->errorHandler(\"Invalid argument.\");\n\t    break;\n\tcase CUDD_INTERNAL_ERROR:\n\t    p->errorHandler(\"Internal error.\");\n\t    break;\n\tcase CUDD_NO_ERROR:\n\t    p->errorHandler(\"Unexpected error.\");\n\t    break;\n\t}\n    }\n\n} // DD::checkReturnValue\n\n\ninline void\nDD::checkReturnValue(\n  int result,\n  int expected) const\n{\n    if (result != expected) {\n\tDdManager *mgr = p->manager;\n\tCudd_ErrorType errType = Cudd_ReadErrorCode(mgr);\n\tswitch (errType) {\n\tcase CUDD_MEMORY_OUT:\n\t    p->errorHandler(\"Out of memory.\");\n\t    break;\n\tcase CUDD_TOO_MANY_NODES:\n\t    break;\n\tcase CUDD_MAX_MEM_EXCEEDED:\n\t    p->errorHandler(\"Maximum memory exceeded.\");\n\t    break;\n        case CUDD_TIMEOUT_EXPIRED:\n            {\n                std::ostringstream msg;\n                unsigned long lag = \n                    Cudd_ReadElapsedTime(mgr) - Cudd_ReadTimeLimit(mgr);\n                msg << \"Timeout expired.  Lag = \" << lag << \" ms.\\n\";\n                p->timeoutHandler(msg.str());\n            }\n\t    break;\n        case CUDD_TERMINATION:\n            {\n                std::ostringstream msg;\n                msg << \"Terminated.\\n\";\n                p->terminationHandler(msg.str());\n            }\n            break;\n\tcase CUDD_INVALID_ARG:\n\t    p->errorHandler(\"Invalid argument.\");\n\t    break;\n\tcase CUDD_INTERNAL_ERROR:\n\t    p->errorHandler(\"Internal error.\");\n\t    break;\n\tcase CUDD_NO_ERROR:\n\t    p->errorHandler(\"Unexpected error.\");\n\t    break;\n\t}\n    }\n\n} // DD::checkReturnValue\n\n\nDdManager *\nDD::manager() const\n{\n    return p->manager;\n\n} // DD::manager\n\n\nDdNode *\nDD::getNode() const\n{\n    return node;\n\n} // DD::getNode\n\n\nDdNode *\nDD::getRegularNode() const\n{\n    return Cudd_Regular(node);\n\n} // DD::getRegularNode\n\n\nint\nDD::nodeCount() const\n{\n    return Cudd_DagSize(node);\n\n} // DD::nodeCount\n\n\nunsigned int\nDD::NodeReadIndex() const\n{\n    return Cudd_NodeReadIndex(node);\n\n} // DD::NodeReadIndex\n\n\n// ---------------------------------------------------------------------------\n// Members of class ABDD\n// ---------------------------------------------------------------------------\n\n\nABDD::ABDD() : DD() {}\nABDD::ABDD(Capsule *cap, DdNode *bddNode) : DD(cap,bddNode) {}\nABDD::ABDD(Cudd const & manager, DdNode *bddNode) : DD(manager,bddNode) {}\nABDD::ABDD(const ABDD &from) : DD(from) {}\n\n\nABDD::~ABDD() {\n    if (node) {\n\tCudd_RecursiveDeref(p->manager,node);\n\tif (p->verbose) {\n\t    cout << \"ADD/BDD destructor called for node \" << hex << dec <<\n\t\tnode << \" ref = \" << Cudd_Regular(node)->ref << \"\\n\";\n\t}\n    }\n\n} // ABDD::~ABDD\n\n\nbool\nABDD::operator==(\n  const ABDD& other) const\n{\n    checkSameManager(other);\n    return node == other.node;\n\n} // ABDD::operator==\n\n\nbool\nABDD::operator!=(\n  const ABDD& other) const\n{\n    checkSameManager(other);\n    return node != other.node;\n\n} // ABDD::operator!=\n\n\nbool\nABDD::IsOne() const\n{\n    return node == Cudd_ReadOne(p->manager);\n\n} // ABDD::IsOne\n\n\nvoid\nABDD::print(\n  int nvars,\n  int verbosity) const\n{\n    cout.flush();\n    if (!node) defaultError(\"empty DD.\");\n    int retval = Cudd_PrintDebug(p->manager,node,nvars,verbosity);\n    fflush(Cudd_ReadStdout(p->manager));\n    checkReturnValue(retval);\n    //if (retval == 0) p->errorHandler(\"print failed\");\n\n} // ABDD::print\n\nvoid\nABDD::summary(\n  int nvars,\n  int mode) const\n{\n    cout.flush();\n    if (!node) defaultError(\"empty DD.\");\n    int retval = Cudd_PrintSummary(p->manager,node,nvars,mode);\n    fflush(Cudd_ReadStdout(p->manager));\n    checkReturnValue(retval);\n\n} // ABDD::summary\n\n// ---------------------------------------------------------------------------\n// Members of class BDD\n// ---------------------------------------------------------------------------\n\nBDD::BDD() : ABDD() {}\nBDD::BDD(Capsule *cap, DdNode *bddNode) : ABDD(cap,bddNode) {}\nBDD::BDD(Cudd const & manager, DdNode *bddNode) : ABDD(manager,bddNode) {}\nBDD::BDD(const BDD &from) : ABDD(from) {}\n\n\nBDD\nBDD::operator=(\n  const BDD& right)\n{\n    if (this == &right) return *this;\n    if (right.node) Cudd_Ref(right.node);\n    if (node) {\n\tCudd_RecursiveDeref(p->manager,node);\n\tif (p->verbose) {\n\t    cout << \"BDD dereferencing for node \" << hex << node << dec <<\n\t\t\" ref = \" << Cudd_Regular(node)->ref << \"\\n\";\n\t}\n    }\n    node = right.node;\n    p = right.p;\n    if (node && p->verbose) {\n\tcout << \"BDD assignment for node \" << hex << node << dec <<\n\t    \" ref = \" << Cudd_Regular(node)->ref << \"\\n\";\n    }\n    return *this;\n\n} // BDD::operator=\n\n\nbool\nBDD::operator<=(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return Cudd_bddLeq(mgr,node,other.node);\n\n} // BDD::operator<=\n\n\nbool\nBDD::operator>=(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return Cudd_bddLeq(mgr,other.node,node);\n\n} // BDD::operator>=\n\n\nbool\nBDD::operator<(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return node != other.node && Cudd_bddLeq(mgr,node,other.node);\n\n} // BDD::operator<\n\n\nbool\nBDD::operator>(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return node != other.node && Cudd_bddLeq(mgr,other.node,node);\n\n} // BDD::operator>\n\n\nBDD\nBDD::operator!() const\n{\n    return BDD(p, Cudd_Not(node));\n\n} // BDD::operator!\n\n\nBDD\nBDD::operator~() const\n{\n    return BDD(p, Cudd_Not(node));\n\n} // BDD::operator~\n\n\nBDD\nBDD::operator*(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddAnd(mgr,node,other.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::operator*\n\n\nBDD\nBDD::operator*=(\n  const BDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddAnd(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // BDD::operator*=\n\n\nBDD\nBDD::operator&(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddAnd(mgr,node,other.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::operator&\n\n\nBDD\nBDD::operator&=(\n  const BDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddAnd(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // BDD::operator&=\n\n\nBDD\nBDD::operator+(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddOr(mgr,node,other.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::operator+\n\n\nBDD\nBDD::operator+=(\n  const BDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddOr(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // BDD::operator+=\n\n\nBDD\nBDD::operator|(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddOr(mgr,node,other.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::operator|\n\n\nBDD\nBDD::operator|=(\n  const BDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddOr(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // BDD::operator|=\n\n\nBDD\nBDD::operator^(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddXor(mgr,node,other.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::operator^\n\n\nBDD\nBDD::operator^=(\n  const BDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddXor(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // BDD::operator^=\n\n\nBDD\nBDD::operator-(\n  const BDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddAnd(mgr,node,Cudd_Not(other.node));\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::operator-\n\n\nBDD\nBDD::operator-=(\n  const BDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_bddAnd(mgr,node,Cudd_Not(other.node));\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // BDD::operator-=\n\n\nostream & operator<<(ostream & os, BDD const & f)\n{\n    if (!f.node) defaultError(\"empty DD.\");\n    DdManager *mgr = f.p->manager;\n    vector<char *> const & vn = f.p->varnames;\n    char const * const *inames = vn.size() == (size_t) Cudd_ReadSize(mgr) ?\n        &vn[0] : 0;\n    char * str = Cudd_FactoredFormString(mgr, f.node, inames);\n    f.checkReturnValue(str);\n    os << string(str);\n    free(str);\n    return os;\n\n} // operator<<\n\n\nbool\nBDD::IsZero() const\n{\n    return node == Cudd_ReadLogicZero(p->manager);\n\n} // BDD::IsZero\n\n\nbool\nBDD::IsVar() const\n{\n    return Cudd_bddIsVar(p->manager, node);\n\n} // BDD::IsVar\n\n\n// ---------------------------------------------------------------------------\n// Members of class ADD\n// ---------------------------------------------------------------------------\n\n\nADD::ADD() : ABDD() {}\nADD::ADD(Capsule *cap, DdNode *bddNode) : ABDD(cap,bddNode) {}\nADD::ADD(Cudd const & manager, DdNode *bddNode) : ABDD(manager,bddNode) {}\nADD::ADD(const ADD &from) : ABDD(from) {}\n\n\nADD\nADD::operator=(\n  const ADD& right)\n{\n    if (this == &right) return *this;\n    if (right.node) Cudd_Ref(right.node);\n    if (node) {\n\tCudd_RecursiveDeref(p->manager,node);\n    }\n    node = right.node;\n    p = right.p;\n    return *this;\n\n} // ADD::operator=\n\n\nbool\nADD::operator<=(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return Cudd_addLeq(mgr,node,other.node);\n\n} // ADD::operator<=\n\n\nbool\nADD::operator>=(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return Cudd_addLeq(mgr,other.node,node);\n\n} // ADD::operator>=\n\n\nbool\nADD::operator<(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return node != other.node && Cudd_addLeq(mgr,node,other.node);\n\n} // ADD::operator<\n\n\nbool\nADD::operator>(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return node != other.node && Cudd_addLeq(mgr,other.node,node);\n\n} // ADD::operator>\n\n\nADD\nADD::operator-() const\n{\n    return ADD(p, Cudd_addNegate(p->manager,node));\n\n} // ADD::operator-\n\n\nADD\nADD::operator*(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addTimes,node,other.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::operator*\n\n\nADD\nADD::operator*=(\n  const ADD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addTimes,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // ADD::operator*=\n\n\nADD\nADD::operator+(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addPlus,node,other.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::operator+\n\n\nADD\nADD::operator+=(\n  const ADD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addPlus,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // ADD::operator+=\n\n\nADD\nADD::operator-(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addMinus,node,other.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::operator-\n\n\nADD\nADD::operator-=(\n  const ADD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addMinus,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // ADD::operator-=\n\n\nADD\nADD::operator~() const\n{\n    return ADD(p, Cudd_addCmpl(p->manager,node));\n\n} // ADD::operator~\n\n\nADD\nADD::operator&(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addTimes,node,other.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::operator&\n\n\nADD\nADD::operator&=(\n  const ADD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addTimes,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // ADD::operator&=\n\n\nADD\nADD::operator|(\n  const ADD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addOr,node,other.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::operator|\n\n\nADD\nADD::operator|=(\n  const ADD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_addApply(mgr,Cudd_addOr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDeref(mgr,node);\n    node = result;\n    return *this;\n\n} // ADD::operator|=\n\n\nbool\nADD::IsZero() const\n{\n    return node == Cudd_ReadZero(p->manager);\n\n} // ADD::IsZero\n\n\n// ---------------------------------------------------------------------------\n// Members of class ZDD\n// ---------------------------------------------------------------------------\n\n\nZDD::ZDD(Capsule *cap, DdNode *bddNode) : DD(cap,bddNode) {}\nZDD::ZDD() : DD() {}\nZDD::ZDD(const ZDD &from) : DD(from) {}\n\n\nZDD::~ZDD() {\n    if (node) {\n\tCudd_RecursiveDerefZdd(p->manager,node);\n\tif (p->verbose) {\n\t    cout << \"ZDD destructor called for node \" << hex << node << dec <<\n\t\t\" ref = \" << Cudd_Regular(node)->ref << \"\\n\";\n\t}\n    }\n\n} // ZDD::~ZDD\n\n\nZDD\nZDD::operator=(\n  const ZDD& right)\n{\n    if (this == &right) return *this;\n    if (right.node) Cudd_Ref(right.node);\n    if (node) {\n\tCudd_RecursiveDerefZdd(p->manager,node);\n\tif (p->verbose) {\n\t    cout << \"ZDD dereferencing for node \" << hex << node << dec <<\n\t\t\" ref = \" << node->ref << \"\\n\";\n\t}\n    }\n    node = right.node;\n    p = right.p;\n    if (node && p->verbose) {\n\tcout << \"ZDD assignment for node \" << hex << node << dec <<\n\t    \" ref = \" << node->ref << \"\\n\";\n    }\n    return *this;\n\n} // ZDD::operator=\n\n\nbool\nZDD::operator==(\n  const ZDD& other) const\n{\n    checkSameManager(other);\n    return node == other.node;\n\n} // ZDD::operator==\n\n\nbool\nZDD::operator!=(\n  const ZDD& other) const\n{\n    checkSameManager(other);\n    return node != other.node;\n\n} // ZDD::operator!=\n\n\nbool\nZDD::operator<=(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return Cudd_zddDiffConst(mgr,node,other.node) == Cudd_ReadZero(mgr);\n\n} // ZDD::operator<=\n\n\nbool\nZDD::operator>=(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return Cudd_zddDiffConst(mgr,other.node,node) == Cudd_ReadZero(mgr);\n\n} // ZDD::operator>=\n\n\nbool\nZDD::operator<(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return node != other.node &&\n\tCudd_zddDiffConst(mgr,node,other.node) == Cudd_ReadZero(mgr);\n\n} // ZDD::operator<\n\n\nbool\nZDD::operator>(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    return node != other.node &&\n\tCudd_zddDiffConst(mgr,other.node,node) == Cudd_ReadZero(mgr);\n\n} // ZDD::operator>\n\n\nvoid\nZDD::print(\n  int nvars,\n  int verbosity) const\n{\n    cout.flush();\n    int retval = Cudd_zddPrintDebug(p->manager,node,nvars,verbosity);\n    fflush(Cudd_ReadStdout(p->manager));\n    if (retval == 0) p->errorHandler(\"print failed\");\n\n} // ZDD::print\n\n\nZDD\nZDD::operator*(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddIntersect(mgr,node,other.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::operator*\n\n\nZDD\nZDD::operator*=(\n  const ZDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddIntersect(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDerefZdd(mgr,node);\n    node = result;\n    return *this;\n\n} // ZDD::operator*=\n\n\nZDD\nZDD::operator&(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddIntersect(mgr,node,other.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::operator&\n\n\nZDD\nZDD::operator&=(\n  const ZDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddIntersect(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDerefZdd(mgr,node);\n    node = result;\n    return *this;\n\n} // ZDD::operator&=\n\n\nZDD\nZDD::operator+(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddUnion(mgr,node,other.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::operator+\n\n\nZDD\nZDD::operator+=(\n  const ZDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddUnion(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDerefZdd(mgr,node);\n    node = result;\n    return *this;\n\n} // ZDD::operator+=\n\n\nZDD\nZDD::operator|(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddUnion(mgr,node,other.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::operator|\n\n\nZDD\nZDD::operator|=(\n  const ZDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddUnion(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDerefZdd(mgr,node);\n    node = result;\n    return *this;\n\n} // ZDD::operator|=\n\n\nZDD\nZDD::operator-(\n  const ZDD& other) const\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddDiff(mgr,node,other.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::operator-\n\n\nZDD\nZDD::operator-=(\n  const ZDD& other)\n{\n    DdManager *mgr = checkSameManager(other);\n    DdNode *result = Cudd_zddDiff(mgr,node,other.node);\n    checkReturnValue(result);\n    Cudd_Ref(result);\n    Cudd_RecursiveDerefZdd(mgr,node);\n    node = result;\n    return *this;\n\n} // ZDD::operator-=\n\n\n// ---------------------------------------------------------------------------\n// Members of class Cudd\n// ---------------------------------------------------------------------------\n\n\nCudd::Cudd(\n  unsigned int numVars,\n  unsigned int numVarsZ,\n  unsigned int numSlots,\n  unsigned int cacheSize,\n  unsigned long maxMemory,\n  PFC defaultHandler)\n{\n    p = new Capsule(numVars,numVarsZ,numSlots,cacheSize,maxMemory,defaultHandler);\n\n} // Cudd::Cudd\n\n\nCudd::Cudd(\n  const Cudd& x)\n{\n    p = x.p;\n    x.p->ref++;\n    if (p->verbose)\n        cout << \"Cudd Copy Constructor\" << endl;\n\n} // Cudd::Cudd\n\n\nCudd::~Cudd()\n{\n    if (--p->ref == 0) {\n\tdelete p;\n    }\n\n} // Cudd::~Cudd\n\n\nDdManager *\nCudd::getManager(void) const\n{\n    return p->manager;\n\n} // Cudd::getManager\n\n\nvoid\nCudd::makeVerbose(void) const\n{\n    p->verbose = 1;\n\n} // Cudd::makeVerbose\n\n\nvoid\nCudd::makeTerse(void) const\n{\n    p->verbose = 0;\n\n} // Cudd::makeTerse\n\n\nbool\nCudd::isVerbose(void) const\n{\n    return p->verbose;\n\n} // Cudd::isVerbose\n\n\nCudd&\nCudd::operator=(\n  const Cudd& right)\n{\n    right.p->ref++;\n    if (--p->ref == 0) {\t// disconnect self\n\tdelete p;\n    }\n    p = right.p;\n    return *this;\n\n} // Cudd::operator=\n\n\nPFC\nCudd::setHandler(\n  PFC newHandler) const\n{\n    PFC oldHandler = p->errorHandler;\n    p->errorHandler = newHandler;\n    return oldHandler;\n\n} // Cudd::setHandler\n\n\nPFC\nCudd::getHandler() const\n{\n    return p->errorHandler;\n\n} // Cudd::getHandler\n\n\nPFC\nCudd::setTimeoutHandler(\n  PFC newHandler) const\n{\n    PFC oldHandler = p->timeoutHandler;\n    p->timeoutHandler = newHandler;\n    return oldHandler;\n\n} // Cudd::setTimeoutHandler\n\n\nPFC\nCudd::getTimeoutHandler() const\n{\n    return p->timeoutHandler;\n\n} // Cudd::getTimeourHandler\n\n\nPFC\nCudd::setTerminationHandler(\n  PFC newHandler) const\n{\n    PFC oldHandler = p->terminationHandler;\n    p->terminationHandler = newHandler;\n    return oldHandler;\n\n} // Cudd::setTerminationHandler\n\n\nPFC\nCudd::getTerminationHandler() const\n{\n    return p->terminationHandler;\n\n} // Cudd::getTerminationHandler\n\n\nvoid\nCudd::pushVariableName(std::string s) const\n{\n    char * cstr = new char[s.length() + 1];\n    strcpy(cstr, s.c_str());\n    p->varnames.push_back(cstr);\n}\n\n\nvoid\nCudd::clearVariableNames(void) const\n{\n    for (vector<char *>::iterator it = p->varnames.begin();\n         it != p->varnames.end(); ++it) {\n        delete [] *it;\n    }\n    p->varnames.clear();\n}\n\n\nstd::string\nCudd::getVariableName(size_t i) const\n{\n    return std::string(p->varnames.at(i));\n}\n\n\ninline void\nCudd::checkReturnValue(\n  const void *result) const\n{\n    if (result == 0) {\n\tif (Cudd_ReadErrorCode(p->manager) == CUDD_MEMORY_OUT) {\n\t    p->errorHandler(\"Out of memory.\");\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_TOO_MANY_NODES) {\n            p->errorHandler(\"Too many nodes.\");\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_MAX_MEM_EXCEEDED) {\n            p->errorHandler(\"Maximum memory exceeded.\");\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_TIMEOUT_EXPIRED) {\n            std::ostringstream msg;\n            DdManager *mgr = p->manager;\n            unsigned long lag = \n                Cudd_ReadElapsedTime(mgr) - Cudd_ReadTimeLimit(mgr);\n            msg << \"Timeout expired.  Lag = \" << lag << \" ms.\\n\";\n            p->timeoutHandler(msg.str());\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_TERMINATION) {\n            std::ostringstream msg;\n            msg << \"Terminated.\\n\";\n            p->terminationHandler(msg.str());\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_INVALID_ARG) {\n            p->errorHandler(\"Invalid argument.\");\n\t} else if (Cudd_ReadErrorCode(p->manager) == CUDD_INTERNAL_ERROR) {\n\t    p->errorHandler(\"Internal error.\");\n\t} else {\n            p->errorHandler(\"Unexpected error.\");\n        }\n    }\n\n} // Cudd::checkReturnValue\n\n\ninline void\nCudd::checkReturnValue(\n  const int result) const\n{\n    if (result == 0) {\n\tif (Cudd_ReadErrorCode(p->manager) == CUDD_MEMORY_OUT) {\n\t    p->errorHandler(\"Out of memory.\");\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_TOO_MANY_NODES) {\n            p->errorHandler(\"Too many nodes.\");\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_MAX_MEM_EXCEEDED) {\n            p->errorHandler(\"Maximum memory exceeded.\");\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_TIMEOUT_EXPIRED) {\n            std::ostringstream msg;\n            DdManager *mgr = p->manager;\n            unsigned long lag = \n                Cudd_ReadElapsedTime(mgr) - Cudd_ReadTimeLimit(mgr);\n            msg << \"Timeout expired.  Lag = \" << lag << \" ms.\\n\";\n            p->timeoutHandler(msg.str());\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_TERMINATION) {\n            std::ostringstream msg;\n            msg << \"Terminated.\\n\";\n            p->terminationHandler(msg.str());\n        } else if (Cudd_ReadErrorCode(p->manager) == CUDD_INVALID_ARG) {\n            p->errorHandler(\"Invalid argument.\");\n\t} else if (Cudd_ReadErrorCode(p->manager) == CUDD_INTERNAL_ERROR) {\n\t    p->errorHandler(\"Internal error.\");\n\t} else {\n\t    p->errorHandler(\"Unexpected error.\");\n\t}\n    }\n\n} // Cudd::checkReturnValue\n\n\nvoid\nCudd::info() const\n{\n    cout.flush();\n    int retval = Cudd_PrintInfo(p->manager,stdout);\n    checkReturnValue(retval);\n\n} // Cudd::info\n\n\nBDD\nCudd::bddVar() const\n{\n    DdNode *result = Cudd_bddNewVar(p->manager);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::bddVar\n\n\nBDD\nCudd::bddVar(\n  int index) const\n{\n    DdNode *result = Cudd_bddIthVar(p->manager,index);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::bddVar\n\n\nBDD\nCudd::bddOne() const\n{\n    DdNode *result = Cudd_ReadOne(p->manager);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::bddOne\n\n\nBDD\nCudd::bddZero() const\n{\n    DdNode *result = Cudd_ReadLogicZero(p->manager);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::bddZero\n\n\nADD\nCudd::addVar() const\n{\n    DdNode *result = Cudd_addNewVar(p->manager);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::addVar\n\n\nADD\nCudd::addVar(\n  int index) const\n{\n    DdNode *result = Cudd_addIthVar(p->manager,index);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::addVar\n\n\nADD\nCudd::addOne() const\n{\n    DdNode *result = Cudd_ReadOne(p->manager);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::addOne\n\n\nADD\nCudd::addZero() const\n{\n    DdNode *result = Cudd_ReadZero(p->manager);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::addZero\n\n\nADD\nCudd::constant(\n  CUDD_VALUE_TYPE c) const\n{\n    DdNode *result = Cudd_addConst(p->manager, c);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::constant\n\n\nADD\nCudd::plusInfinity() const\n{\n    DdNode *result = Cudd_ReadPlusInfinity(p->manager);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::plusInfinity\n\n\nADD\nCudd::minusInfinity() const\n{\n    DdNode *result = Cudd_ReadMinusInfinity(p->manager);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::minusInfinity\n\n\nZDD\nCudd::zddVar(\n  int index) const\n{\n    DdNode *result = Cudd_zddIthVar(p->manager,index);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // Cudd::zddVar\n\n\nZDD\nCudd::zddOne(\n  int i) const\n{\n    DdNode *result = Cudd_ReadZddOne(p->manager,i);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // Cudd::zddOne\n\n\nZDD\nCudd::zddZero() const\n{\n    DdNode *result = Cudd_ReadZero(p->manager);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // Cudd::zddZero\n\n\nvoid\ndefaultError(\n  string message)\n{\n    throw std::logic_error(message);\n\n} // defaultError\n\n\n// ---------------------------------------------------------------------------\n// All the rest\n// ---------------------------------------------------------------------------\n\n\nADD\nCudd::addNewVarAtLevel(\n  int level) const\n{\n    DdNode *result = Cudd_addNewVarAtLevel(p->manager, level);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::addNewVarAtLevel\n\n\nBDD\nCudd::bddNewVarAtLevel(\n  int level) const\n{\n    DdNode *result = Cudd_bddNewVarAtLevel(p->manager, level);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::bddNewVarAtLevel\n\n\nvoid\nCudd::zddVarsFromBddVars(\n  int multiplicity) const\n{\n    int result = Cudd_zddVarsFromBddVars(p->manager, multiplicity);\n    checkReturnValue(result);\n\n} // Cudd::zddVarsFromBddVars\n\n\nunsigned long\nCudd::ReadStartTime() const\n{\n    return Cudd_ReadStartTime(p->manager);\n\n} // Cudd::ReadStartTime\n\n\nunsigned long\nCudd::ReadElapsedTime() const\n{\n    return Cudd_ReadElapsedTime(p->manager);\n\n} // Cudd::ReadElapsedTime\n\n\nvoid \nCudd::SetStartTime(\n  unsigned long st) const\n{\n    Cudd_SetStartTime(p->manager, st);\n\n} // Cudd::SetStartTime\n\n\nvoid \nCudd::ResetStartTime() const\n{\n    Cudd_ResetStartTime(p->manager);\n\n} // Cudd::ResetStartTime\n\n\nunsigned long\nCudd::ReadTimeLimit() const\n{\n    return Cudd_ReadTimeLimit(p->manager);\n\n} // Cudd::ReadTimeLimit\n\n\nunsigned long\nCudd::SetTimeLimit(\n  unsigned long tl) const\n{\n    return Cudd_SetTimeLimit(p->manager, tl);\n\n} // Cudd::SetTimeLimit\n\n\nvoid\nCudd::UpdateTimeLimit() const\n{\n    Cudd_UpdateTimeLimit(p->manager);\n\n} // Cudd::UpdateTimeLimit\n\n\nvoid\nCudd::IncreaseTimeLimit(\n  unsigned long increase) const\n{\n    Cudd_IncreaseTimeLimit(p->manager, increase);\n\n} // Cudd::IncreaseTimeLimit\n\n\nvoid \nCudd::UnsetTimeLimit() const\n{\n    Cudd_UnsetTimeLimit(p->manager);\n\n} // Cudd::UnsetTimeLimit\n\n\nbool\nCudd::TimeLimited() const\n{\n    return Cudd_TimeLimited(p->manager);\n\n} // Cudd::TimeLimited\n\n\nvoid\nCudd::RegisterTerminationCallback(\n  DD_THFP callback,\n  void * callback_arg) const\n{\n    Cudd_RegisterTerminationCallback(p->manager, callback, callback_arg);\n\n} // Cudd::RegisterTerminationCallback\n\n\nvoid\nCudd::UnregisterTerminationCallback() const\n{\n    Cudd_UnregisterTerminationCallback(p->manager);\n\n} // Cudd::UnregisterTerminationCallback\n\n\nDD_OOMFP\nCudd::RegisterOutOfMemoryCallback(\n  DD_OOMFP callback) const\n{\n    return Cudd_RegisterOutOfMemoryCallback(p->manager, callback);\n\n} // Cudd::RegisterOutOfMemoryCallback\n\n\nvoid\nCudd::UnregisterOutOfMemoryCallback() const\n{\n    Cudd_UnregisterOutOfMemoryCallback(p->manager);\n\n} // Cudd::UnregisterOutOfMemoryCallback\n\n\nvoid\nCudd::AutodynEnable(\n  Cudd_ReorderingType method) const\n{\n    Cudd_AutodynEnable(p->manager, method);\n\n} // Cudd::AutodynEnable\n\n\nvoid\nCudd::AutodynDisable() const\n{\n    Cudd_AutodynDisable(p->manager);\n\n} // Cudd::AutodynDisable\n\n\nbool\nCudd::ReorderingStatus(\n  Cudd_ReorderingType * method) const\n{\n    return Cudd_ReorderingStatus(p->manager, method);\n\n} // Cudd::ReorderingStatus\n\n\nvoid\nCudd::AutodynEnableZdd(\n  Cudd_ReorderingType method) const\n{\n    Cudd_AutodynEnableZdd(p->manager, method);\n\n} // Cudd::AutodynEnableZdd\n\n\nvoid\nCudd::AutodynDisableZdd() const\n{\n    Cudd_AutodynDisableZdd(p->manager);\n\n} // Cudd::AutodynDisableZdd\n\n\nbool\nCudd::ReorderingStatusZdd(\n  Cudd_ReorderingType * method) const\n{\n    return Cudd_ReorderingStatusZdd(p->manager, method);\n\n} // Cudd::ReorderingStatusZdd\n\n\nbool\nCudd::zddRealignmentEnabled() const\n{\n    return Cudd_zddRealignmentEnabled(p->manager);\n\n} // Cudd::zddRealignmentEnabled\n\n\nvoid\nCudd::zddRealignEnable() const\n{\n    Cudd_zddRealignEnable(p->manager);\n\n} // Cudd::zddRealignEnable\n\n\nvoid\nCudd::zddRealignDisable() const\n{\n    Cudd_zddRealignDisable(p->manager);\n\n} // Cudd::zddRealignDisable\n\n\nbool\nCudd::bddRealignmentEnabled() const\n{\n    return Cudd_bddRealignmentEnabled(p->manager);\n\n} // Cudd::bddRealignmentEnabled\n\n\nvoid\nCudd::bddRealignEnable() const\n{\n    Cudd_bddRealignEnable(p->manager);\n\n} // Cudd::bddRealignEnable\n\n\nvoid\nCudd::bddRealignDisable() const\n{\n    Cudd_bddRealignDisable(p->manager);\n\n} // Cudd::bddRealignDisable\n\n\nADD\nCudd::background() const\n{\n    DdNode *result = Cudd_ReadBackground(p->manager);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::background\n\n\nvoid\nCudd::SetBackground(\n  ADD bg) const\n{\n    DdManager *mgr = p->manager;\n    if (mgr != bg.manager()) {\n\tp->errorHandler(\"Background comes from different manager.\");\n    }\n    Cudd_SetBackground(mgr, bg.getNode());\n\n} // Cudd::SetBackground\n\n\nunsigned int\nCudd::ReadCacheSlots() const\n{\n    return Cudd_ReadCacheSlots(p->manager);\n\n} // Cudd::ReadCacheSlots\n\n\ndouble\nCudd::ReadCacheLookUps() const\n{\n    return Cudd_ReadCacheLookUps(p->manager);\n\n} // Cudd::ReadCacheLookUps\n\n\ndouble\nCudd::ReadCacheUsedSlots() const\n{\n    return Cudd_ReadCacheUsedSlots(p->manager);\n\n} // Cudd::ReadCacheUsedSlots\n\n\ndouble\nCudd::ReadCacheHits() const\n{\n    return Cudd_ReadCacheHits(p->manager);\n\n} // Cudd::ReadCacheHits\n\n\nunsigned int\nCudd::ReadMinHit() const\n{\n    return Cudd_ReadMinHit(p->manager);\n\n} // Cudd::ReadMinHit\n\n\nvoid\nCudd::SetMinHit(\n  unsigned int hr) const\n{\n    Cudd_SetMinHit(p->manager, hr);\n\n} // Cudd::SetMinHit\n\n\nunsigned int\nCudd::ReadLooseUpTo() const\n{\n    return Cudd_ReadLooseUpTo(p->manager);\n\n} // Cudd::ReadLooseUpTo\n\n\nvoid\nCudd::SetLooseUpTo(\n  unsigned int lut) const\n{\n    Cudd_SetLooseUpTo(p->manager, lut);\n\n} // Cudd::SetLooseUpTo\n\n\nunsigned int\nCudd::ReadMaxCache() const\n{\n    return Cudd_ReadMaxCache(p->manager);\n\n} // Cudd::ReadMaxCache\n\n\nunsigned int\nCudd::ReadMaxCacheHard() const\n{\n    return Cudd_ReadMaxCacheHard(p->manager);\n\n} // Cudd::ReadMaxCacheHard\n\n\nvoid\nCudd::SetMaxCacheHard(\n  unsigned int mc) const\n{\n    Cudd_SetMaxCacheHard(p->manager, mc);\n\n} // Cudd::SetMaxCacheHard\n\n\nint\nCudd::ReadSize() const\n{\n    return Cudd_ReadSize(p->manager);\n\n} // Cudd::ReadSize\n\n\nint\nCudd::ReadZddSize() const\n{\n    return Cudd_ReadZddSize(p->manager);\n\n} // Cudd::ReadZddSize\n\n\nunsigned int\nCudd::ReadSlots() const\n{\n    return Cudd_ReadSlots(p->manager);\n\n} // Cudd::ReadSlots\n\n\nunsigned int\nCudd::ReadKeys() const\n{\n    return Cudd_ReadKeys(p->manager);\n\n} // Cudd::ReadKeys\n\n\nunsigned int\nCudd::ReadDead() const\n{\n    return Cudd_ReadDead(p->manager);\n\n} // Cudd::ReadDead\n\n\nunsigned int\nCudd::ReadMinDead() const\n{\n    return Cudd_ReadMinDead(p->manager);\n\n} // Cudd::ReadMinDead\n\n\nunsigned int\nCudd::ReadReorderings() const\n{\n    return Cudd_ReadReorderings(p->manager);\n\n} // Cudd::ReadReorderings\n\n\nunsigned int\nCudd::ReadMaxReorderings() const\n{\n    return Cudd_ReadMaxReorderings(p->manager);\n\n} // Cudd::ReadMaxReorderings\n\nvoid\nCudd::SetMaxReorderings(\n  unsigned int mr) const\n{\n    Cudd_SetMaxReorderings(p->manager, mr);\n\n} // Cudd::SetMaxReorderings\n\nlong\nCudd::ReadReorderingTime() const\n{\n    return Cudd_ReadReorderingTime(p->manager);\n\n} // Cudd::ReadReorderingTime\n\n\nint\nCudd::ReadGarbageCollections() const\n{\n    return Cudd_ReadGarbageCollections(p->manager);\n\n} // Cudd::ReadGarbageCollections\n\n\nlong\nCudd::ReadGarbageCollectionTime() const\n{\n    return Cudd_ReadGarbageCollectionTime(p->manager);\n\n} // Cudd::ReadGarbageCollectionTime\n\n\nint\nCudd::ReadSiftMaxVar() const\n{\n    return Cudd_ReadSiftMaxVar(p->manager);\n\n} // Cudd::ReadSiftMaxVar\n\n\nvoid\nCudd::SetSiftMaxVar(\n  int smv) const\n{\n    Cudd_SetSiftMaxVar(p->manager, smv);\n\n} // Cudd::SetSiftMaxVar\n\n\nint\nCudd::ReadSiftMaxSwap() const\n{\n    return Cudd_ReadSiftMaxSwap(p->manager);\n\n} // Cudd::ReadSiftMaxSwap\n\n\nvoid\nCudd::SetSiftMaxSwap(\n  int sms) const\n{\n    Cudd_SetSiftMaxSwap(p->manager, sms);\n\n} // Cudd::SetSiftMaxSwap\n\n\ndouble\nCudd::ReadMaxGrowth() const\n{\n    return Cudd_ReadMaxGrowth(p->manager);\n\n} // Cudd::ReadMaxGrowth\n\n\nvoid\nCudd::SetMaxGrowth(\n  double mg) const\n{\n    Cudd_SetMaxGrowth(p->manager, mg);\n\n} // Cudd::SetMaxGrowth\n\n\nMtrNode *\nCudd::ReadTree() const\n{\n    return Cudd_ReadTree(p->manager);\n\n} // Cudd::ReadTree\n\n\nvoid\nCudd::SetTree(\n  MtrNode * tree) const\n{\n    Cudd_SetTree(p->manager, tree);\n\n} // Cudd::SetTree\n\n\nvoid\nCudd::FreeTree() const\n{\n    Cudd_FreeTree(p->manager);\n\n} // Cudd::FreeTree\n\n\nMtrNode *\nCudd::ReadZddTree() const\n{\n    return Cudd_ReadZddTree(p->manager);\n\n} // Cudd::ReadZddTree\n\n\nvoid\nCudd::SetZddTree(\n  MtrNode * tree) const\n{\n    Cudd_SetZddTree(p->manager, tree);\n\n} // Cudd::SetZddTree\n\n\nvoid\nCudd::FreeZddTree() const\n{\n    Cudd_FreeZddTree(p->manager);\n\n} // Cudd::FreeZddTree\n\n\nint\nCudd::ReadPerm(\n  int i) const\n{\n    return Cudd_ReadPerm(p->manager, i);\n\n} // Cudd::ReadPerm\n\n\nint\nCudd::ReadPermZdd(\n  int i) const\n{\n    return Cudd_ReadPermZdd(p->manager, i);\n\n} // Cudd::ReadPermZdd\n\n\nint\nCudd::ReadInvPerm(\n  int i) const\n{\n    return Cudd_ReadInvPerm(p->manager, i);\n\n} // Cudd::ReadInvPerm\n\n\nint\nCudd::ReadInvPermZdd(\n  int i) const\n{\n    return Cudd_ReadInvPermZdd(p->manager, i);\n\n} // Cudd::ReadInvPermZdd\n\n\nBDD\nCudd::ReadVars(\n  int i) const\n{\n    DdNode *result = Cudd_ReadVars(p->manager, i);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::ReadVars\n\n\nCUDD_VALUE_TYPE\nCudd::ReadEpsilon() const\n{\n    return Cudd_ReadEpsilon(p->manager);\n\n} // Cudd::ReadEpsilon\n\n\nvoid\nCudd::SetEpsilon(\n  CUDD_VALUE_TYPE ep) const\n{\n    Cudd_SetEpsilon(p->manager, ep);\n\n} // Cudd::SetEpsilon\n\n\nCudd_AggregationType\nCudd::ReadGroupcheck() const\n{\n    return Cudd_ReadGroupcheck(p->manager);\n\n} // Cudd::ReadGroupcheck\n\n\nvoid\nCudd::SetGroupcheck(\n  Cudd_AggregationType gc) const\n{\n    Cudd_SetGroupcheck(p->manager, gc);\n\n} // Cudd::SetGroupcheck\n\n\nbool\nCudd::GarbageCollectionEnabled() const\n{\n    return Cudd_GarbageCollectionEnabled(p->manager);\n\n} // Cudd::GarbageCollectionEnabled\n\n\nvoid\nCudd::EnableGarbageCollection() const\n{\n    Cudd_EnableGarbageCollection(p->manager);\n\n} // Cudd::EnableGarbageCollection\n\n\nvoid\nCudd::DisableGarbageCollection() const\n{\n    Cudd_DisableGarbageCollection(p->manager);\n\n} // Cudd::DisableGarbageCollection\n\n\nbool\nCudd::DeadAreCounted() const\n{\n    return Cudd_DeadAreCounted(p->manager);\n\n} // Cudd::DeadAreCounted\n\n\nvoid\nCudd::TurnOnCountDead() const\n{\n    Cudd_TurnOnCountDead(p->manager);\n\n} // Cudd::TurnOnCountDead\n\n\nvoid\nCudd::TurnOffCountDead() const\n{\n    Cudd_TurnOffCountDead(p->manager);\n\n} // Cudd::TurnOffCountDead\n\n\nint\nCudd::ReadRecomb() const\n{\n    return Cudd_ReadRecomb(p->manager);\n\n} // Cudd::ReadRecomb\n\n\nvoid\nCudd::SetRecomb(\n  int recomb) const\n{\n    Cudd_SetRecomb(p->manager, recomb);\n\n} // Cudd::SetRecomb\n\n\nint\nCudd::ReadSymmviolation() const\n{\n    return Cudd_ReadSymmviolation(p->manager);\n\n} // Cudd::ReadSymmviolation\n\n\nvoid\nCudd::SetSymmviolation(\n  int symmviolation) const\n{\n    Cudd_SetSymmviolation(p->manager, symmviolation);\n\n} // Cudd::SetSymmviolation\n\n\nint\nCudd::ReadArcviolation() const\n{\n    return Cudd_ReadArcviolation(p->manager);\n\n} // Cudd::ReadArcviolation\n\n\nvoid\nCudd::SetArcviolation(\n  int arcviolation) const\n{\n    Cudd_SetArcviolation(p->manager, arcviolation);\n\n} // Cudd::SetArcviolation\n\n\nint\nCudd::ReadPopulationSize() const\n{\n    return Cudd_ReadPopulationSize(p->manager);\n\n} // Cudd::ReadPopulationSize\n\n\nvoid\nCudd::SetPopulationSize(\n  int populationSize) const\n{\n    Cudd_SetPopulationSize(p->manager, populationSize);\n\n} // Cudd::SetPopulationSize\n\n\nint\nCudd::ReadNumberXovers() const\n{\n    return Cudd_ReadNumberXovers(p->manager);\n\n} // Cudd::ReadNumberXovers\n\n\nvoid\nCudd::SetNumberXovers(\n  int numberXovers) const\n{\n    Cudd_SetNumberXovers(p->manager, numberXovers);\n\n} // Cudd::SetNumberXovers\n\n\nunsigned int \nCudd::ReadOrderRandomization() const\n{\n    return Cudd_ReadOrderRandomization(p->manager);\n\n} // Cudd::ReadOrderRandomization\n\n\nvoid \nCudd::SetOrderRandomization(\n  unsigned int factor) const\n{\n    Cudd_SetOrderRandomization(p->manager, factor);\n\n} // Cudd::SetOrderRandomization\n\n\nunsigned long\nCudd::ReadMemoryInUse() const\n{\n    return Cudd_ReadMemoryInUse(p->manager);\n\n} // Cudd::ReadMemoryInUse\n\n\nlong\nCudd::ReadPeakNodeCount() const\n{\n    return Cudd_ReadPeakNodeCount(p->manager);\n\n} // Cudd::ReadPeakNodeCount\n\n\nlong\nCudd::ReadNodeCount() const\n{\n    return Cudd_ReadNodeCount(p->manager);\n\n} // Cudd::ReadNodeCount\n\n\nlong\nCudd::zddReadNodeCount() const\n{\n    return Cudd_zddReadNodeCount(p->manager);\n\n} // Cudd::zddReadNodeCount\n\n\nvoid\nCudd::AddHook(\n  DD_HFP f,\n  Cudd_HookType where) const\n{\n    int result = Cudd_AddHook(p->manager, f, where);\n    checkReturnValue(result);\n\n} // Cudd::AddHook\n\n\nvoid\nCudd::RemoveHook(\n  DD_HFP f,\n  Cudd_HookType where) const\n{\n    int result = Cudd_RemoveHook(p->manager, f, where);\n    checkReturnValue(result);\n\n} // Cudd::RemoveHook\n\n\nbool\nCudd::IsInHook(\n  DD_HFP f,\n  Cudd_HookType where) const\n{\n    return Cudd_IsInHook(p->manager, f, where);\n\n} // Cudd::IsInHook\n\n\nvoid\nCudd::EnableReorderingReporting() const\n{\n    int result = Cudd_EnableReorderingReporting(p->manager);\n    checkReturnValue(result);\n\n} // Cudd::EnableReorderingReporting\n\n\nvoid\nCudd::DisableReorderingReporting() const\n{\n    int result = Cudd_DisableReorderingReporting(p->manager);\n    checkReturnValue(result);\n\n} // Cudd::DisableReorderingReporting\n\n\nbool\nCudd::ReorderingReporting() const\n{\n    return Cudd_ReorderingReporting(p->manager);\n\n} // Cudd::ReorderingReporting\n\n\nint\nCudd::ReadErrorCode() const\n{\n    return Cudd_ReadErrorCode(p->manager);\n\n} // Cudd::ReadErrorCode\n\n\nvoid\nCudd::ClearErrorCode() const\n{\n    Cudd_ClearErrorCode(p->manager);\n\n} // Cudd::ClearErrorCode\n\n\nDD_OOMFP Cudd::InstallOutOfMemoryHandler(DD_OOMFP newHandler) const\n{\n    return Cudd_InstallOutOfMemoryHandler(newHandler);\n\n} // Cudd::InstallOutOfMemoryHandler\n\n\nFILE *\nCudd::ReadStdout() const\n{\n    return Cudd_ReadStdout(p->manager);\n\n} // Cudd::ReadStdout\n\n\nvoid\nCudd::SetStdout(FILE *fp) const\n{\n    Cudd_SetStdout(p->manager, fp);\n\n} // Cudd::SetStdout\n\n\nFILE *\nCudd::ReadStderr() const\n{\n    return Cudd_ReadStderr(p->manager);\n\n} // Cudd::ReadStderr\n\n\nvoid\nCudd::SetStderr(FILE *fp) const\n{\n    Cudd_SetStderr(p->manager, fp);\n\n} // Cudd::SetStderr\n\n\nunsigned int\nCudd::ReadNextReordering() const\n{\n    return Cudd_ReadNextReordering(p->manager);\n\n} // Cudd::ReadNextReordering\n\n\nvoid\nCudd::SetNextReordering(\n  unsigned int next) const\n{\n    Cudd_SetNextReordering(p->manager, next);\n\n} // Cudd::SetNextReordering\n\n\ndouble\nCudd::ReadSwapSteps() const\n{\n    return Cudd_ReadSwapSteps(p->manager);\n\n} // Cudd::ReadSwapSteps\n\n\nunsigned int\nCudd::ReadMaxLive() const\n{\n    return Cudd_ReadMaxLive(p->manager);\n\n} // Cudd::ReadMaxLive\n\n\nvoid\nCudd::SetMaxLive(unsigned int maxLive) const\n{\n    Cudd_SetMaxLive(p->manager, maxLive);\n\n} // Cudd::SetMaxLive\n\n\nsize_t\nCudd::ReadMaxMemory() const\n{\n    return Cudd_ReadMaxMemory(p->manager);\n\n} // Cudd::ReadMaxMemory\n\n\nsize_t\nCudd::SetMaxMemory(size_t maxMem) const\n{\n    return Cudd_SetMaxMemory(p->manager, maxMem);\n\n} // Cudd::SetMaxMemory\n\n\nint\nCudd::bddBindVar(int index) const\n{\n    return Cudd_bddBindVar(p->manager, index);\n\n} // Cudd::bddBindVar\n\n\nint\nCudd::bddUnbindVar(int index) const\n{\n    return Cudd_bddUnbindVar(p->manager, index);\n\n} // Cudd::bddUnbindVar\n\n\nbool\nCudd::bddVarIsBound(int index) const\n{\n    return Cudd_bddVarIsBound(p->manager, index);\n\n} // Cudd::bddVarIsBound\n\n\nADD\nADD::ExistAbstract(\n  const ADD& cube) const\n{\n    DdManager *mgr = checkSameManager(cube);\n    DdNode *result = Cudd_addExistAbstract(mgr, node, cube.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::ExistAbstract\n\n\nADD\nADD::UnivAbstract(\n  const ADD& cube) const\n{\n    DdManager *mgr = checkSameManager(cube);\n    DdNode *result = Cudd_addUnivAbstract(mgr, node, cube.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::UnivAbstract\n\n\nADD\nADD::OrAbstract(\n  const ADD& cube) const\n{\n    DdManager *mgr = checkSameManager(cube);\n    DdNode *result = Cudd_addOrAbstract(mgr, node, cube.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::OrAbstract\n\n\nADD\nADD::Plus(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addPlus, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Plus\n\n\nADD\nADD::Times(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addTimes, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Times\n\n\nADD\nADD::Threshold(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addThreshold, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Threshold\n\n\nADD\nADD::SetNZ(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addSetNZ, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::SetNZ\n\n\nADD\nADD::Divide(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addDivide, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Divide\n\n\nADD\nADD::Minus(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addMinus, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Minus\n\n\nADD\nADD::Minimum(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addMinimum, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Minimum\n\n\nADD\nADD::Maximum(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addMaximum, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Maximum\n\n\nADD\nADD::OneZeroMaximum(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addOneZeroMaximum, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::OneZeroMaximum\n\n\nADD\nADD::Diff(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addDiff, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Diff\n\n\nADD\nADD::Agreement(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addAgreement, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Agreement\n\n\nADD\nADD::Or(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addOr, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Or\n\n\nADD\nADD::Nand(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addNand, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Nand\n\n\nADD\nADD::Nor(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addNor, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Nor\n\n\nADD\nADD::Xor(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addXor, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Xor\n\n\nADD\nADD::Xnor(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addApply(mgr, Cudd_addXnor, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Xnor\n\n\nADD\nADD::Log() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addMonadicApply(mgr, Cudd_addLog, node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Log\n\n\nADD\nADD::FindMax() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addFindMax(mgr, node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::FindMax\n\n\nADD\nADD::FindMin() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addFindMin(mgr, node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::FindMin\n\n\nADD\nADD::IthBit(\n  int bit) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addIthBit(mgr, node, bit);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::IthBit\n\n\nADD\nADD::ScalarInverse(\n  const ADD& epsilon) const\n{\n    DdManager *mgr = checkSameManager(epsilon);\n    DdNode *result = Cudd_addScalarInverse(mgr, node, epsilon.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::ScalarInverse\n\n\nADD\nADD::Ite(\n  const ADD& g,\n  const ADD& h) const\n{\n    DdManager *mgr = checkSameManager(g);\n    checkSameManager(h);\n    DdNode *result = Cudd_addIte(mgr, node, g.node, h.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Ite\n\n\nADD\nADD::IteConstant(\n  const ADD& g,\n  const ADD& h) const\n{\n    DdManager *mgr = checkSameManager(g);\n    checkSameManager(h);\n    DdNode *result = Cudd_addIteConstant(mgr, node, g.node, h.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::IteConstant\n\n\nADD\nADD::EvalConst(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addEvalConst(mgr, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::EvalConst\n\n\nbool\nADD::Leq(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    return Cudd_addLeq(mgr, node, g.node);\n\n} // ADD::Leq\n\n\nADD\nADD::Cmpl() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addCmpl(mgr, node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Cmpl\n\n\nADD\nADD::Negate() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addNegate(mgr, node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Negate\n\n\nADD\nADD::RoundOff(\n  int N) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addRoundOff(mgr, node, N);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::RoundOff\n\n\nADD\nCudd::Walsh(\n  std::vector<ADD> x,\n  std::vector<ADD> y) const\n{\n    size_t n = x.size();\n    DdNode **X = new DdNode *[n];\n    DdNode **Y = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tX[i] = x[i].getNode();\n\tY[i] = y[i].getNode();\n    }\n    DdNode *result = Cudd_addWalsh(p->manager, X, Y, (int) n);\n    delete [] X;\n    delete [] Y;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Walsh\n\n\nADD\nCudd::addResidue(\n  int n,\n  int m,\n  int options,\n  int top) const\n{\n    DdNode *result = Cudd_addResidue(p->manager, n, m, options, top);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::addResidue\n\n\nBDD\nBDD::AndAbstract(\n  const BDD& g,\n  const BDD& cube,\n  unsigned int limit) const\n{\n    DdManager *mgr = checkSameManager(g);\n    checkSameManager(cube);\n    DdNode *result;\n    if (limit == 0)\n\tresult = Cudd_bddAndAbstract(mgr, node, g.node, cube.node);\n    else\n\tresult = Cudd_bddAndAbstractLimit(mgr, node, g.node,\n\t\t\t\t\t  cube.node, limit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::AndAbstract\n\n\nint\nCudd::ApaNumberOfDigits(\n  int binaryDigits) const\n{\n    return Cudd_ApaNumberOfDigits(binaryDigits);\n\n} // Cudd::ApaNumberOfDigits\n\n\nDdApaNumber\nCudd::NewApaNumber(\n  int digits) const\n{\n    return Cudd_NewApaNumber(digits);\n\n} // Cudd::NewApaNumber\n\n\nvoid\nCudd::ApaCopy(\n  int digits,\n  DdApaNumber source,\n  DdApaNumber dest) const\n{\n    Cudd_ApaCopy(digits, source, dest);\n\n} // Cudd::ApaCopy\n\n\nDdApaDigit\nCudd::ApaAdd(\n  int digits,\n  DdApaNumber a,\n  DdApaNumber b,\n  DdApaNumber sum) const\n{\n    return Cudd_ApaAdd(digits, a, b, sum);\n\n} // Cudd::ApaAdd\n\n\nDdApaDigit\nCudd::ApaSubtract(\n  int digits,\n  DdApaNumber a,\n  DdApaNumber b,\n  DdApaNumber diff) const\n{\n    return Cudd_ApaSubtract(digits, a, b, diff);\n\n} // Cudd::ApaSubtract\n\n\nDdApaDigit\nCudd::ApaShortDivision(\n  int digits,\n  DdApaNumber dividend,\n  DdApaDigit divisor,\n  DdApaNumber quotient) const\n{\n    return Cudd_ApaShortDivision(digits, dividend, divisor, quotient);\n\n} // Cudd::ApaShortDivision\n\n\nvoid\nCudd::ApaShiftRight(\n  int digits,\n  DdApaDigit in,\n  DdApaNumber a,\n  DdApaNumber b) const\n{\n    Cudd_ApaShiftRight(digits, in, a, b);\n\n} // Cudd::ApaShiftRight\n\n\nvoid\nCudd::ApaSetToLiteral(\n  int digits,\n  DdApaNumber number,\n  DdApaDigit literal) const\n{\n    Cudd_ApaSetToLiteral(digits, number, literal);\n\n} // Cudd::ApaSetToLiteral\n\n\nvoid\nCudd::ApaPowerOfTwo(\n  int digits,\n  DdApaNumber number,\n  int power) const\n{\n    Cudd_ApaPowerOfTwo(digits, number, power);\n\n} // Cudd::ApaPowerOfTwo\n\n\nvoid\nCudd::ApaPrintHex(\n  int digits,\n  DdApaNumber number,\n  FILE * fp) const\n{\n    cout.flush();\n    int result = Cudd_ApaPrintHex(fp, digits, number);\n    checkReturnValue(result);\n\n} // Cudd::ApaPrintHex\n\n\nvoid\nCudd::ApaPrintDecimal(\n  int digits,\n  DdApaNumber number,\n  FILE * fp) const\n{\n    cout.flush();\n    int result = Cudd_ApaPrintDecimal(fp, digits, number);\n    checkReturnValue(result);\n\n} // Cudd::ApaPrintDecimal\n\n\nstd::string\nCudd::ApaStringDecimal(\n  int digits,\n  DdApaNumber number) const\n{\n    char * result = Cudd_ApaStringDecimal(digits, number);\n    checkReturnValue(result);\n    std::string ret = std::string(result);\n    free(result);\n    return ret;\n\n} // Cudd::ApaStringDecimal\n\n\nvoid\nCudd::ApaPrintExponential(\n  int digits,\n  DdApaNumber number,\n  int precision,\n  FILE * fp) const\n{\n    cout.flush();\n    int result = Cudd_ApaPrintExponential(fp, digits, number, precision);\n    checkReturnValue(result);\n\n} // Cudd::ApaPrintExponential\n\n\nDdApaNumber\nABDD::ApaCountMinterm(\n  int nvars,\n  int * digits) const\n{\n    DdManager *mgr = p->manager;\n    return Cudd_ApaCountMinterm(mgr, node, nvars, digits);\n\n} // ABDD::ApaCountMinterm\n\n\nvoid\nABDD::ApaPrintMinterm(\n  int nvars,\n  FILE * fp) const\n{\n    cout.flush();\n    DdManager *mgr = p->manager;\n    int result = Cudd_ApaPrintMinterm(fp, mgr, node, nvars);\n    checkReturnValue(result);\n\n} // ABDD::ApaPrintMinterm\n\n\nvoid\nABDD::ApaPrintMintermExp(\n  int nvars,\n  int precision,\n  FILE * fp) const\n{\n    cout.flush();\n    DdManager *mgr = p->manager;\n    int result = Cudd_ApaPrintMintermExp(fp, mgr, node, nvars, precision);\n    checkReturnValue(result);\n\n} // ABDD::ApaPrintMintermExp\n\n\nvoid\nABDD::EpdPrintMinterm(\n  int nvars,\n  FILE * fp) const\n{\n    EpDouble count;\n    char str[24];\n    cout.flush();\n    DdManager *mgr = p->manager;\n    int result = Cudd_EpdCountMinterm(mgr, node, nvars, &count);\n    checkReturnValue(result,0);\n    EpdGetString(&count, str);\n    fprintf(fp, \"%s\", str);\n\n} // ABDD::EpdPrintMinterm\n\n\nlong double\nABDD::LdblCountMinterm(\n  int nvars) const\n{\n    cout.flush();\n    DdManager *mgr = p->manager;\n    long double result = Cudd_LdblCountMinterm(mgr, node, nvars);\n    checkReturnValue(result != (long double) CUDD_OUT_OF_MEM);\n    return result;\n\n} // ABDD::LdblCountMinterm\n\n\nBDD\nBDD::UnderApprox(\n  int numVars,\n  int threshold,\n  bool safe,\n  double quality) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_UnderApprox(mgr, node, numVars, threshold, safe, quality);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::UnderApprox\n\n\nBDD\nBDD::OverApprox(\n  int numVars,\n  int threshold,\n  bool safe,\n  double quality) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_OverApprox(mgr, node, numVars, threshold, safe, quality);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::OverApprox\n\n\nBDD\nBDD::RemapUnderApprox(\n  int numVars,\n  int threshold,\n  double quality) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_RemapUnderApprox(mgr, node, numVars, threshold, quality);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::RemapUnderApprox\n\n\nBDD\nBDD::RemapOverApprox(\n  int numVars,\n  int threshold,\n  double quality) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_RemapOverApprox(mgr, node, numVars, threshold, quality);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::RemapOverApprox\n\n\nBDD\nBDD::BiasedUnderApprox(\n  const BDD& bias,\n  int numVars,\n  int threshold,\n  double quality1,\n  double quality0) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_BiasedUnderApprox(mgr, node, bias.node, numVars, \n                                            threshold, quality1, quality0);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::BiasedUnderApprox\n\n\nBDD\nBDD::BiasedOverApprox(\n  const BDD& bias,\n  int numVars,\n  int threshold,\n  double quality1,\n  double quality0) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_BiasedOverApprox(mgr, node, bias.node, numVars, \n                                           threshold, quality1, quality0);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::BiasedOverApprox\n\n\nBDD\nBDD::ExistAbstract(\n  const BDD& cube,\n  unsigned int limit) const\n{\n    DdManager *mgr = checkSameManager(cube);\n    DdNode *result;\n    if (limit == 0)\n        result = Cudd_bddExistAbstract(mgr, node, cube.node);\n    else\n        result = Cudd_bddExistAbstractLimit(mgr, node, cube.node, limit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::ExistAbstract\n\n\nBDD\nBDD::XorExistAbstract(\n  const BDD& g,\n  const BDD& cube) const\n{\n    DdManager *mgr = checkSameManager(g);\n    checkSameManager(cube);\n    DdNode *result = Cudd_bddXorExistAbstract(mgr, node, g.node, cube.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::XorExistAbstract\n\n\nBDD\nBDD::UnivAbstract(\n  const BDD& cube) const\n{\n    DdManager *mgr = checkSameManager(cube);\n    DdNode *result = Cudd_bddUnivAbstract(mgr, node, cube.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::UnivAbstract\n\n\nBDD\nBDD::BooleanDiff(\n  int x) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_bddBooleanDiff(mgr, node, x);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::BooleanDiff\n\n\nbool\nBDD::VarIsDependent(\n  const BDD& var) const\n{\n    DdManager *mgr = p->manager;\n    return Cudd_bddVarIsDependent(mgr, node, var.node);\n\n} // BDD::VarIsDependent\n\n\ndouble\nBDD::Correlation(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    return Cudd_bddCorrelation(mgr, node, g.node);\n\n} // BDD::Correlation\n\n\ndouble\nBDD::CorrelationWeights(\n  const BDD& g,\n  double * prob) const\n{\n    DdManager *mgr = checkSameManager(g);\n    return Cudd_bddCorrelationWeights(mgr, node, g.node, prob);\n\n} // BDD::CorrelationWeights\n\n\nBDD\nBDD::Ite(\n  const BDD& g,\n  const BDD& h,\n  unsigned int limit) const\n{\n    DdManager *mgr = checkSameManager(g);\n    checkSameManager(h);\n    DdNode *result;\n    if (limit == 0)\n\tresult = Cudd_bddIte(mgr, node, g.node, h.node);\n    else\n\tresult = Cudd_bddIteLimit(mgr, node, g.node, h.node, limit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Ite\n\n\nBDD\nBDD::IteConstant(\n  const BDD& g,\n  const BDD& h) const\n{\n    DdManager *mgr = checkSameManager(g);\n    checkSameManager(h);\n    DdNode *result = Cudd_bddIteConstant(mgr, node, g.node, h.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::IteConstant\n\n\nBDD\nBDD::Intersect(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_bddIntersect(mgr, node, g.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Intersect\n\n\nBDD\nBDD::And(\n  const BDD& g,\n  unsigned int limit) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result;\n    if (limit == 0)\n\tresult = Cudd_bddAnd(mgr, node, g.node);\n    else\n\tresult = Cudd_bddAndLimit(mgr, node, g.node, limit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::And\n\n\nBDD\nBDD::Or(\n  const BDD& g,\n  unsigned int limit) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result;\n    if (limit == 0)\n\tresult = Cudd_bddOr(mgr, node, g.node);\n    else\n\tresult = Cudd_bddOrLimit(mgr, node, g.node, limit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Or\n\n\nBDD\nBDD::Nand(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_bddNand(mgr, node, g.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Nand\n\n\nBDD\nBDD::Nor(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_bddNor(mgr, node, g.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Nor\n\n\nBDD\nBDD::Xor(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_bddXor(mgr, node, g.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Xor\n\n\nBDD\nBDD::Xnor(\n  const BDD& g,\n  unsigned int limit) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result;\n    if (limit == 0)\n\tresult = Cudd_bddXnor(mgr, node, g.node);\n    else\n\tresult = Cudd_bddXnorLimit(mgr, node, g.node, limit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Xnor\n\n\nbool\nBDD::Leq(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    return Cudd_bddLeq(mgr, node, g.node);\n\n} // BDD::Leq\n\n\nBDD\nADD::BddThreshold(\n  CUDD_VALUE_TYPE value) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addBddThreshold(mgr, node, value);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ADD::BddThreshold\n\n\nBDD\nADD::BddStrictThreshold(\n  CUDD_VALUE_TYPE value) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addBddStrictThreshold(mgr, node, value);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ADD::BddStrictThreshold\n\n\nBDD\nADD::BddInterval(\n  CUDD_VALUE_TYPE lower,\n  CUDD_VALUE_TYPE upper) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addBddInterval(mgr, node, lower, upper);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ADD::BddInterval\n\n\nBDD\nADD::BddIthBit(\n  int bit) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addBddIthBit(mgr, node, bit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ADD::BddIthBit\n\n\nADD\nBDD::Add() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_BddToAdd(mgr, node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // BDD::Add\n\n\nBDD\nADD::BddPattern() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addBddPattern(mgr, node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ADD::BddPattern\n\n\nBDD\nBDD::Transfer(\n  Cudd& destination) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_bddTransfer(mgr, destination.p->manager, node);\n    checkReturnValue(result);\n    return BDD(destination.p, result);\n\n} // BDD::Transfer\n\n\nvoid\nCudd::DebugCheck() const\n{\n    int result = Cudd_DebugCheck(p->manager);\n    checkReturnValue(result == 0);\n\n} // Cudd::DebugCheck\n\n\nvoid\nCudd::CheckKeys() const\n{\n    int result = Cudd_CheckKeys(p->manager);\n    checkReturnValue(result == 0);\n\n} // Cudd::CheckKeys\n\n\nBDD\nBDD::ClippingAnd(\n  const BDD& g,\n  int maxDepth,\n  int direction) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_bddClippingAnd(mgr, node, g.node, maxDepth,\n\t\t\t\t\t direction);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::ClippingAnd\n\n\nBDD\nBDD::ClippingAndAbstract(\n  const BDD& g,\n  const BDD& cube,\n  int maxDepth,\n  int direction) const\n{\n    DdManager *mgr = checkSameManager(g);\n    checkSameManager(cube);\n    DdNode *result = Cudd_bddClippingAndAbstract(mgr, node, g.node, cube.node,\n\t\t\t\t\t\t maxDepth, direction);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::ClippingAndAbstract\n\n\nADD\nADD::Cofactor(\n  const ADD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_Cofactor(mgr, node, g.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Cofactor\n\n\nBDD\nBDD::Cofactor(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_Cofactor(mgr, node, g.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Cofactor\n\n\nbool\nBDD::VarAreSymmetric(int index1, int index2) const\n{\n    return Cudd_VarsAreSymmetric(p->manager, node, index1, index2);\n\n} // BDD::VarAreSymmetric\n\nBDD\nBDD::Compose(\n  const BDD& g,\n  int v) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_bddCompose(mgr, node, g.node, v);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Compose\n\n\nADD\nADD::Compose(\n  const ADD& g,\n  int v) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_addCompose(mgr, node, g.node, v);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Compose\n\n\nADD\nADD::Permute(\n  int * permut) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_addPermute(mgr, node, permut);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Permute\n\n\nADD\nADD::SwapVariables(\n  std::vector<ADD> x,\n  std::vector<ADD> y) const\n{\n    size_t n = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[n];\n    DdNode **Y = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tX[i] = x[i].node;\n\tY[i] = y[i].node;\n    }\n    DdNode *result = Cudd_addSwapVariables(mgr, node, X, Y, (int) n);\n    delete [] X;\n    delete [] Y;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::SwapVariables\n\n\nBDD\nBDD::Permute(\n  int * permut) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_bddPermute(mgr, node, permut);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Permute\n\n\nBDD\nBDD::SwapVariables(\n  std::vector<BDD> x,\n  std::vector<BDD> y) const\n{\n    size_t n = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[n];\n    DdNode **Y = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n        X[i] = x[i].node;\n        Y[i] = y[i].node;\n    }\n    DdNode *result = Cudd_bddSwapVariables(mgr, node, X, Y, (int) n);\n    delete [] X;\n    delete [] Y;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::SwapVariables\n\n\nBDD\nBDD::AdjPermuteX(\n  std::vector<BDD> x) const\n{\n    size_t n = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tX[i] = x[i].node;\n    }\n    DdNode *result = Cudd_bddAdjPermuteX(mgr, node, X, (int) n);\n    delete [] X;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::AdjPermuteX\n\n\nADD\nADD::VectorCompose(\n  std::vector<ADD> vect) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = (size_t) Cudd_ReadSize(mgr);\n    DdNode **X = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tX[i] = vect[i].node;\n    }\n    DdNode *result = Cudd_addVectorCompose(mgr, node, X);\n    delete [] X;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::VectorCompose\n\n\nADD\nADD::NonSimCompose(\n  std::vector<ADD> vect) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = (size_t) Cudd_ReadSize(mgr);\n    DdNode **X = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tX[i] = vect[i].node;\n    }\n    DdNode *result = Cudd_addNonSimCompose(mgr, node, X);\n    delete [] X;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::NonSimCompose\n\n\nBDD\nBDD::VectorCompose(\n  std::vector<BDD> vect) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = (size_t) Cudd_ReadSize(mgr);\n    DdNode **X = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tX[i] = vect[i].node;\n    }\n    DdNode *result = Cudd_bddVectorCompose(mgr, node, X);\n    delete [] X;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::VectorCompose\n\n\nvoid\nBDD::ApproxConjDecomp(\n  BDD* g,\n  BDD* h) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **pieces;\n    int result = Cudd_bddApproxConjDecomp(mgr, node, &pieces);\n    checkReturnValue(result == 2);\n    *g = BDD(p, pieces[0]);\n    *h = BDD(p, pieces[1]);\n    Cudd_RecursiveDeref(mgr,pieces[0]);\n    Cudd_RecursiveDeref(mgr,pieces[1]);\n    free(pieces);\n\n} // BDD::ApproxConjDecomp\n\n\nvoid\nBDD::ApproxDisjDecomp(\n  BDD* g,\n  BDD* h) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **pieces;\n    int result = Cudd_bddApproxDisjDecomp(mgr, node, &pieces);\n    checkReturnValue(result == 2);\n    *g = BDD(p, pieces[0]);\n    *h = BDD(p, pieces[1]);\n    Cudd_RecursiveDeref(mgr,pieces[0]);\n    Cudd_RecursiveDeref(mgr,pieces[1]);\n    free(pieces);\n\n} // BDD::ApproxDisjDecomp\n\n\nvoid\nBDD::IterConjDecomp(\n  BDD* g,\n  BDD* h) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **pieces;\n    int result = Cudd_bddIterConjDecomp(mgr, node, &pieces);\n    checkReturnValue(result == 2);\n    *g = BDD(p, pieces[0]);\n    *h = BDD(p, pieces[1]);\n    Cudd_RecursiveDeref(mgr,pieces[0]);\n    Cudd_RecursiveDeref(mgr,pieces[1]);\n    free(pieces);\n\n} // BDD::IterConjDecomp\n\n\nvoid\nBDD::IterDisjDecomp(\n  BDD* g,\n  BDD* h) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **pieces;\n    int result = Cudd_bddIterDisjDecomp(mgr, node, &pieces);\n    checkReturnValue(result == 2);\n    *g = BDD(p, pieces[0]);\n    *h = BDD(p, pieces[1]);\n    Cudd_RecursiveDeref(mgr,pieces[0]);\n    Cudd_RecursiveDeref(mgr,pieces[1]);\n    free(pieces);\n\n} // BDD::IterDisjDecomp\n\n\nvoid\nBDD::GenConjDecomp(\n  BDD* g,\n  BDD* h) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **pieces;\n    int result = Cudd_bddGenConjDecomp(mgr, node, &pieces);\n    checkReturnValue(result == 2);\n    *g = BDD(p, pieces[0]);\n    *h = BDD(p, pieces[1]);\n    Cudd_RecursiveDeref(mgr,pieces[0]);\n    Cudd_RecursiveDeref(mgr,pieces[1]);\n    free(pieces);\n\n} // BDD::GenConjDecomp\n\n\nvoid\nBDD::GenDisjDecomp(\n  BDD* g,\n  BDD* h) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **pieces;\n    int result = Cudd_bddGenDisjDecomp(mgr, node, &pieces);\n    checkReturnValue(result == 2);\n    *g = BDD(p, pieces[0]);\n    *h = BDD(p, pieces[1]);\n    Cudd_RecursiveDeref(mgr,pieces[0]);\n    Cudd_RecursiveDeref(mgr,pieces[1]);\n    free(pieces);\n\n} // BDD::GenDisjDecomp\n\n\nvoid\nBDD::VarConjDecomp(\n  BDD* g,\n  BDD* h) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **pieces;\n    int result = Cudd_bddVarConjDecomp(mgr, node, &pieces);\n    checkReturnValue(result == 2);\n    *g = BDD(p, pieces[0]);\n    *h = BDD(p, pieces[1]);\n    Cudd_RecursiveDeref(mgr,pieces[0]);\n    Cudd_RecursiveDeref(mgr,pieces[1]);\n    free(pieces);\n\n} // BDD::VarConjDecomp\n\n\nvoid\nBDD::VarDisjDecomp(\n  BDD* g,\n  BDD* h) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **pieces;\n    int result = Cudd_bddVarDisjDecomp(mgr, node, &pieces);\n    checkReturnValue(result == 2);\n    *g = BDD(p, pieces[0]);\n    *h = BDD(p, pieces[1]);\n    Cudd_RecursiveDeref(mgr,pieces[0]);\n    Cudd_RecursiveDeref(mgr,pieces[1]);\n    free(pieces);\n\n} // BDD::VarDisjDecomp\n\n\nbool\nABDD::IsCube() const\n{\n    DdManager *mgr = p->manager;\n    return Cudd_CheckCube(mgr, node);\n\n} // ABDD::IsCube\n\n\nBDD\nABDD::FindEssential() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_FindEssential(mgr, node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ABDD::FindEssential\n\n\nbool\nBDD::IsVarEssential(\n  int id,\n  int phase) const\n{\n    DdManager *mgr = p->manager;\n    return Cudd_bddIsVarEssential(mgr, node, id, phase);\n\n} // BDD::IsVarEssential\n\n\nvoid\nABDD::PrintTwoLiteralClauses(\n  char **names,\n  FILE *fp) const\n{\n    DdManager *mgr = p->manager;\n    int result = Cudd_PrintTwoLiteralClauses(mgr, node, names, fp);\n    checkReturnValue(result);\n\n} // ABDD::PrintTwoLiteralClauses\n\n\nvoid\nCudd::DumpBlif(\n  const std::vector<BDD>& nodes,\n  char const * const * inames,\n  char const * const * onames,\n  char * mname,\n  FILE * fp,\n  int mv) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = nodes.size();\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i ++) {\n\tF[i] = nodes[i].getNode();\n    }\n    int result = Cudd_DumpBlif(mgr, (int) n, F, inames, onames, mname, fp, mv);\n    delete [] F;\n    checkReturnValue(result);\n\n} // Cudd::DumpBlif\n\n\nvoid\nCudd::DumpDot(\n  const std::vector<BDD>& nodes,\n  char const * const * inames,\n  char const * const * onames,\n  FILE * fp) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = nodes.size();\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i ++) {\n\tF[i] = nodes[i].getNode();\n    }\n    int result = Cudd_DumpDot(mgr, (int) n, F, inames, onames, fp);\n    delete [] F;\n    checkReturnValue(result);\n\n} // Cudd::DumpDot\n\n\nvoid\nCudd::DumpDot(\n  const std::vector<ADD>& nodes,\n  char const * const * inames,\n  char const * const * onames,\n  FILE * fp) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = nodes.size();\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i ++) {\n\tF[i] = nodes[i].getNode();\n    }\n    int result = Cudd_DumpDot(mgr, (int) n, F, inames, onames, fp);\n    delete [] F;\n    checkReturnValue(result);\n\n} // Cudd::DumpDot\n\n\nvoid\nCudd::DumpDaVinci(\n  const std::vector<BDD>& nodes,\n  char const * const * inames,\n  char const * const * onames,\n  FILE * fp) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = nodes.size();\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i ++) {\n\tF[i] = nodes[i].getNode();\n    }\n    int result = Cudd_DumpDaVinci(mgr, (int) n, F, inames, onames, fp);\n    delete [] F;\n    checkReturnValue(result);\n\n} // Cudd::DumpDaVinci\n\n\nvoid\nCudd::DumpDaVinci(\n  const std::vector<ADD>& nodes,\n  char const * const * inames,\n  char const * const * onames,\n  FILE * fp) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = nodes.size();\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i ++) {\n\tF[i] = nodes[i].getNode();\n    }\n    int result = Cudd_DumpDaVinci(mgr, (int) n, F, inames, onames, fp);\n    delete [] F;\n    checkReturnValue(result);\n\n} // Cudd::DumpDaVinci\n\n\nvoid\nCudd::DumpDDcal(\n  const std::vector<BDD>& nodes,\n  char const * const * inames,\n  char const * const * onames,\n  FILE * fp) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = nodes.size();\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i ++) {\n\tF[i] = nodes[i].getNode();\n    }\n    int result = Cudd_DumpDDcal(mgr, (int) n, F, inames, onames, fp);\n    delete [] F;\n    checkReturnValue(result);\n\n} // Cudd::DumpDDcal\n\n\nvoid\nCudd::DumpFactoredForm(\n  const std::vector<BDD>& nodes,\n  char const * const * inames,\n  char const * const * onames,\n  FILE * fp) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = nodes.size();\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i ++) {\n\tF[i] = nodes[i].getNode();\n    }\n    int result = Cudd_DumpFactoredForm(mgr, (int) n, F, inames, onames, fp);\n    delete [] F;\n    checkReturnValue(result);\n\n} // Cudd::DumpFactoredForm\n\n\nvoid\nBDD::PrintFactoredForm(\n  char const * const * inames,\n  FILE * fp) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *f = node;\n    int result = Cudd_DumpFactoredForm(mgr, 0, &f, inames, 0, fp);\n    checkReturnValue(result);\n\n} // BDD::PrintFactoredForm\n\n\nstring\nBDD::FactoredFormString(char const * const * inames) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *f = node;\n    char *cstr = Cudd_FactoredFormString(mgr, f, inames);\n    checkReturnValue(cstr);\n    string str(cstr);\n    free(cstr);\n    return str;\n\n} // BDD::FactoredFormString\n\n\nBDD\nBDD::Constrain(\n  const BDD& c) const\n{\n    DdManager *mgr = checkSameManager(c);\n    DdNode *result = Cudd_bddConstrain(mgr, node, c.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Constrain\n\n\nBDD\nBDD::Restrict(\n  const BDD& c) const\n{\n    DdManager *mgr = checkSameManager(c);\n    DdNode *result = Cudd_bddRestrict(mgr, node, c.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Restrict\n\n\nBDD\nBDD::NPAnd(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_bddNPAnd(mgr, node, g.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::NPAnd\n\n\nADD\nADD::Constrain(\n  const ADD& c) const\n{\n    DdManager *mgr = checkSameManager(c);\n    DdNode *result = Cudd_addConstrain(mgr, node, c.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Constrain\n\n\nstd::vector<BDD>\nBDD::ConstrainDecomp() const\n{\n    DdManager *mgr = p->manager;\n    DdNode **result = Cudd_bddConstrainDecomp(mgr, node);\n    checkReturnValue(result);\n    int size = Cudd_ReadSize(mgr);\n    vector<BDD> vect;\n    for (int i = 0; i < size; i++) {\n\tCudd_Deref(result[i]);\n\tvect.push_back(BDD(p, result[i]));\n    }\n    free(result);\n    return vect;\n\n} // BDD::ConstrainDecomp\n\n\nADD\nADD::Restrict(\n  const ADD& c) const\n{\n    DdManager *mgr = checkSameManager(c);\n    DdNode *result = Cudd_addRestrict(mgr, node, c.node);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Restrict\n\n\nstd::vector<BDD>\nBDD::CharToVect() const\n{\n    DdManager *mgr = p->manager;\n    DdNode **result = Cudd_bddCharToVect(mgr, node);\n    checkReturnValue(result);\n    int size = Cudd_ReadSize(mgr);\n    vector<BDD> vect;\n    for (int i = 0; i < size; i++) {\n\tCudd_Deref(result[i]);\n\tvect.push_back(BDD(p, result[i]));\n    }\n    free(result);\n    return vect;\n\n} // BDD::CharToVect\n\n\nBDD\nBDD::LICompaction(\n  const BDD& c) const\n{\n    DdManager *mgr = checkSameManager(c);\n    DdNode *result = Cudd_bddLICompaction(mgr, node, c.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::LICompaction\n\n\nBDD\nBDD::Squeeze(\n  const BDD& u) const\n{\n    DdManager *mgr = checkSameManager(u);\n    DdNode *result = Cudd_bddSqueeze(mgr, node, u.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Squeeze\n\n\nBDD\nBDD::Interpolate(\n  const BDD& u) const\n{\n    DdManager *mgr = checkSameManager(u);\n    DdNode *result = Cudd_bddInterpolate(mgr, node, u.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Interpolate\n\n\nBDD\nBDD::Minimize(\n  const BDD& c) const\n{\n    DdManager *mgr = checkSameManager(c);\n    DdNode *result = Cudd_bddMinimize(mgr, node, c.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Minimize\n\n\nBDD\nBDD::SubsetCompress(\n  int nvars,\n  int threshold) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_SubsetCompress(mgr, node, nvars, threshold);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::SubsetCompress\n\n\nBDD\nBDD::SupersetCompress(\n  int nvars,\n  int threshold) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_SupersetCompress(mgr, node, nvars, threshold);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::SupersetCompress\n\n\nMtrNode *\nCudd::MakeTreeNode(\n  unsigned int low,\n  unsigned int size,\n  unsigned int type) const\n{\n    return Cudd_MakeTreeNode(p->manager, low, size, type);\n\n} // Cudd::MakeTreeNode\n\n\nADD\nCudd::Harwell(\n  FILE * fp,\n  std::vector<ADD>& x,\n  std::vector<ADD>& y,\n  std::vector<ADD>& xn,\n  std::vector<ADD>& yn_,\n  int * m,\n  int * n,\n  int bx,\n  int sx,\n  int by,\n  int sy,\n  int pr) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *E;\n    DdNode **xa = 0, **ya = 0, **xna = 0, **yna = 0;\n    int nx = x.size(), ny = y.size();\n    if (nx > 0) {\n        xa = (DdNode **) malloc(nx * sizeof(DdNode *));\n        if (!xa) {\n            p->errorHandler(\"Out of memory.\");\n        }\n        xna = (DdNode **) malloc(nx * sizeof(DdNode *));\n        if (!xna) {\n            free(xa);\n            p->errorHandler(\"Out of memory.\");\n        }\n        for (int i = 0; i < nx; ++i) {\n            xa[i] = x.at(i).node;\n            xna[i] = xn.at(i).node;\n        }\n    }\n    if (ny > 0) {\n        ya = (DdNode **) malloc(ny * sizeof(DdNode *));\n        if (!ya) {\n            free(xa);\n            free(xna);\n            p->errorHandler(\"Out of memory.\");\n        }\n        yna = (DdNode **) malloc(ny * sizeof(DdNode *));\n        if (!yna) {\n            free(xa);\n            free(xna);\n            free(ya);\n            p->errorHandler(\"Out of memory.\");\n        }\n        for (int j = 0; j < ny; ++j) {\n            ya[j] = y.at(j).node;\n            yna[j] = yn_.at(j).node;\n        }\n    }\n    int result = Cudd_addHarwell(fp, mgr, &E, &xa, &ya, &xna, &yna, &nx, &ny,\n                                 m, n, bx, sx, by, sy, pr);\n    checkReturnValue(result);\n    for (int i = x.size(); i < nx; ++i) {\n        x.push_back(ADD(p, xa[i]));\n        xn.push_back(ADD(p, xna[i]));\n    }\n    free(xa);\n    free(xna);\n    for (int j = y.size(); j < ny; ++j) {\n        y.push_back(ADD(p, ya[j]));\n        yn_.push_back(ADD(p, yna[j]));\n    }\n    free(ya);\n    free(yna);\n    Cudd_Deref(E);\n    return ADD(p, E);\n\n} // Cudd::Harwell\n\n\nvoid\nCudd::PrintLinear(void) const\n{\n    cout.flush();\n    int result = Cudd_PrintLinear(p->manager);\n    checkReturnValue(result);\n\n} // Cudd::PrintLinear\n\n\nint\nCudd::ReadLinear(\n  int x,\n  int y) const\n{\n    return Cudd_ReadLinear(p->manager, x, y);\n\n} // Cudd::ReadLinear\n\n\nBDD\nBDD::LiteralSetIntersection(\n  const BDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_bddLiteralSetIntersection(mgr, node, g.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::LiteralSetIntersection\n\n\nADD\nADD::MatrixMultiply(\n  const ADD& B,\n  std::vector<ADD> z) const\n{\n    size_t nz = z.size();\n    DdManager *mgr = checkSameManager(B);\n    DdNode **Z = new DdNode *[nz];\n    for (size_t i = 0; i < nz; i++) {\n\tZ[i] = z[i].node;\n    }\n    DdNode *result = Cudd_addMatrixMultiply(mgr, node, B.node, Z, (int) nz);\n    delete [] Z;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::MatrixMultiply\n\n\nADD\nADD::TimesPlus(\n  const ADD& B,\n  std::vector<ADD> z) const\n{\n    size_t nz = z.size();\n    DdManager *mgr = checkSameManager(B);\n    DdNode **Z = new DdNode *[nz];\n    for (size_t i = 0; i < nz; i++) {\n\tZ[i] = z[i].node;\n    }\n    DdNode *result = Cudd_addTimesPlus(mgr, node, B.node, Z, (int) nz);\n    delete [] Z;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::TimesPlus\n\n\nADD\nADD::Triangle(\n  const ADD& g,\n  std::vector<ADD> z) const\n{\n    size_t nz = z.size();\n    DdManager *mgr = checkSameManager(g);\n    DdNode **Z = new DdNode *[nz];\n    for (size_t i = 0; i < nz; i++) {\n\tZ[i] = z[i].node;\n    }\n    DdNode *result = Cudd_addTriangle(mgr, node, g.node, Z, (int) nz);\n    delete [] Z;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Triangle\n\n\nBDD\nBDD::PrioritySelect(\n  std::vector<BDD> x,\n  std::vector<BDD> y,\n  std::vector<BDD> z,\n  const BDD& Pi,\n  DD_PRFP Pifunc) const\n{\n    size_t n = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[n];\n    DdNode **Y = new DdNode *[n];\n    DdNode **Z = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tX[i] = x[i].node;\n\tY[i] = y[i].node;\n\tZ[i] = z[i].node;\n    }\n    DdNode *result = Cudd_PrioritySelect(mgr, node, X, Y, Z, Pi.node,\n                                         (int) n, Pifunc);\n    delete [] X;\n    delete [] Y;\n    delete [] Z;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::PrioritySelect\n\n\nBDD\nCudd::Xgty(\n  std::vector<BDD> z,\n  std::vector<BDD> x,\n  std::vector<BDD> y) const\n{\n    size_t N = z.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[N];\n    DdNode **Y = new DdNode *[N];\n    DdNode **Z = new DdNode *[N];\n    for (size_t i = 0; i < N; i++) {\n\tX[i] = x[i].getNode();\n\tY[i] = y[i].getNode();\n\tZ[i] = z[i].getNode();\n    }\n    DdNode *result = Cudd_Xgty(mgr, (int) N, Z, X, Y);\n    delete [] X;\n    delete [] Y;\n    delete [] Z;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::Xgty\n\n\nBDD\nCudd::Xeqy(\n  std::vector<BDD> x,\n  std::vector<BDD> y) const\n{\n    size_t N = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[N];\n    DdNode **Y = new DdNode *[N];\n    for (size_t i = 0; i < N; i++) {\n\tX[i] = x[i].getNode();\n\tY[i] = y[i].getNode();\n    }\n    DdNode *result = Cudd_Xeqy(mgr, (int) N, X, Y);\n    delete [] X;\n    delete [] Y;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Xeqy\n\n\nADD\nCudd::Xeqy(\n  std::vector<ADD> x,\n  std::vector<ADD> y) const\n{\n    size_t N = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[N];\n    DdNode **Y = new DdNode *[N];\n    for (size_t i = 0; i < N; i++) {\n\tX[i] = x[i].getNode();\n\tY[i] = y[i].getNode();\n    }\n    DdNode *result = Cudd_addXeqy(mgr, (int) N, X, X);\n    delete [] X;\n    delete [] Y;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Xeqy\n\n\nBDD\nCudd::Dxygtdxz(\n  std::vector<BDD> x,\n  std::vector<BDD> y,\n  std::vector<BDD> z) const\n{\n    size_t N = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[N];\n    DdNode **Y = new DdNode *[N];\n    DdNode **Z = new DdNode *[N];\n    for (size_t i = 0; i < N; i++) {\n\tX[i] = x[i].getNode();\n\tY[i] = y[i].getNode();\n\tZ[i] = z[i].getNode();\n    }\n    DdNode *result = Cudd_Dxygtdxz(mgr, (int) N, X, Y, Z);\n    delete [] X;\n    delete [] Y;\n    delete [] Z;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::Dxygtdxz\n\n\nBDD\nCudd::Dxygtdyz(\n  std::vector<BDD> x,\n  std::vector<BDD> y,\n  std::vector<BDD> z) const\n{\n    size_t N = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[N];\n    DdNode **Y = new DdNode *[N];\n    DdNode **Z = new DdNode *[N];\n    for (size_t i = 0; i < N; i++) {\n\tX[i] = x[i].getNode();\n\tY[i] = y[i].getNode();\n\tZ[i] = z[i].getNode();\n    }\n    DdNode *result = Cudd_Dxygtdyz(mgr, (int) N, X, Y, Z);\n    delete [] X;\n    delete [] Y;\n    delete [] Z;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::Dxygtdyz\n\n\nBDD\nCudd::Inequality(\n  int c,\n  std::vector<BDD> x,\n  std::vector<BDD> y) const\n{\n    size_t N = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[N];\n    DdNode **Y = new DdNode *[N];\n    for (size_t i = 0; i < N; i++) {\n\tX[i] = x[i].getNode();\n\tY[i] = y[i].getNode();\n    }\n    DdNode *result = Cudd_Inequality(mgr, (int) N, c, X, Y);\n    delete [] X;\n    delete [] Y;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::Inequality\n\n\nBDD\nCudd::Disequality(\n  int c,\n  std::vector<BDD> x,\n  std::vector<BDD> y) const\n{\n    size_t N = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[N];\n    DdNode **Y = new DdNode *[N];\n    for (size_t i = 0; i < N; i++) {\n\tX[i] = x[i].getNode();\n\tY[i] = y[i].getNode();\n    }\n    DdNode *result = Cudd_Disequality(mgr, (int) N, c, X, Y);\n    delete [] X;\n    delete [] Y;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::Disequality\n\n\nBDD\nCudd::Interval(\n  std::vector<BDD> x,\n  unsigned int lowerB,\n  unsigned int upperB) const\n{\n    size_t N = x.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[N];\n    for (size_t i = 0; i < N; i++) {\n\tX[i] = x[i].getNode();\n    }\n    DdNode *result = Cudd_bddInterval(mgr, (int) N, X, lowerB, upperB);\n    delete [] X;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::Interval\n\n\nBDD\nBDD::CProjection(\n  const BDD& Y) const\n{\n    DdManager *mgr = checkSameManager(Y);\n    DdNode *result = Cudd_CProjection(mgr, node, Y.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::CProjection\n\n\nint\nBDD::MinHammingDist(\n  int *minterm,\n  int upperBound) const\n{\n    DdManager *mgr = p->manager;\n    int result = Cudd_MinHammingDist(mgr, node, minterm, upperBound);\n    return result;\n\n} // BDD::MinHammingDist\n\n\nADD\nCudd::Hamming(\n  std::vector<ADD> xVars,\n  std::vector<ADD> yVars) const\n{\n    size_t nVars = xVars.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[nVars];\n    DdNode **Y = new DdNode *[nVars];\n    for (size_t i = 0; i < nVars; i++) {\n\tX[i] = xVars[i].getNode();\n\tY[i] = yVars[i].getNode();\n    }\n    DdNode *result = Cudd_addHamming(mgr, X, Y, (int) nVars);\n    delete [] X;\n    delete [] Y;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::Hamming\n\n\nADD\nCudd::Read(\n  FILE * fp,\n  std::vector<ADD>& x,\n  std::vector<ADD>& y,\n  std::vector<ADD>& xn,\n  std::vector<ADD>& yn_,\n  int * m,\n  int * n,\n  int bx,\n  int sx,\n  int by,\n  int sy) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *E;\n    DdNode **xa = 0, **ya = 0, **xna = 0, **yna = 0;\n    int nx = x.size(), ny = y.size();\n    if (nx > 0) {\n        xa = (DdNode **) malloc(nx * sizeof(DdNode *));\n        if (!xa) {\n            p->errorHandler(\"Out of memory.\");\n        }\n        xna = (DdNode **) malloc(nx * sizeof(DdNode *));\n        if (!xna) {\n            free(xa);\n            p->errorHandler(\"Out of memory.\");\n        }\n        for (int i = 0; i < nx; ++i) {\n            xa[i] = x.at(i).node;\n            xna[i] = xn.at(i).node;\n        }\n    }\n    if (ny > 0) {\n        ya = (DdNode **) malloc(ny * sizeof(DdNode *));\n        if (!ya) {\n            free(xa);\n            free(xna);\n            p->errorHandler(\"Out of memory.\");\n        }\n        yna = (DdNode **) malloc(ny * sizeof(DdNode *));\n        if (!yna) {\n            free(xa);\n            free(xna);\n            free(ya);\n            p->errorHandler(\"Out of memory.\");\n        }\n        for (int j = 0; j < ny; ++j) {\n            ya[j] = y.at(j).node;\n            yna[j] = yn_.at(j).node;\n        }\n    }\n    int result = Cudd_addRead(fp, mgr, &E, &xa, &ya, &xna, &yna, &nx, &ny,\n                              m, n, bx, sx, by, sy);\n    checkReturnValue(result);\n    for (int i = x.size(); i < nx; ++i) {\n        x.push_back(ADD(p, xa[i]));\n        xn.push_back(ADD(p, xna[i]));\n    }\n    free(xa);\n    free(xna);\n    for (int j = y.size(); j < ny; ++j) {\n        y.push_back(ADD(p, ya[j]));\n        yn_.push_back(ADD(p, yna[j]));\n    }\n    free(ya);\n    free(yna);\n    Cudd_Deref(E);\n    return ADD(p, E);\n\n} // Cudd::Read\n\n\nBDD\nCudd::Read(\n  FILE * fp,\n  std::vector<BDD>& x,\n  std::vector<BDD>& y,\n  int * m,\n  int * n,\n  int bx,\n  int sx,\n  int by,\n  int sy) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *E;\n    DdNode **xa = 0, **ya = 0;\n    int nx = x.size(), ny = y.size();\n    if (nx > 0) {\n        xa = (DdNode **) malloc(nx * sizeof(DdNode *));\n        if (!xa) {\n            p->errorHandler(\"Out of memory.\");\n        }\n        for (int i = 0; i < nx; ++i) {\n            xa[i] = x.at(i).node;\n        }\n    }\n    if (ny > 0) {\n        ya = (DdNode **) malloc(ny * sizeof(DdNode *));\n        if (!ya) {\n            free(xa);\n            p->errorHandler(\"Out of memory.\");\n        }\n        for (int j = 0; j < nx; ++j) {\n            ya[j] = y.at(j).node;\n        }\n    }\n    int result = Cudd_bddRead(fp, mgr, &E, &xa, &ya, &nx, &ny,\n                              m, n, bx, sx, by, sy);\n    checkReturnValue(result);\n    for (int i = x.size(); i < nx; ++i) {\n        x.push_back(BDD(p, xa[i]));\n    }\n    free(xa);\n    for (int j = y.size(); j < ny; ++j) {\n        y.push_back(BDD(p, ya[j]));\n    }\n    free(ya);\n    Cudd_Deref(E);\n    return BDD(p, E);\n\n} // Cudd::Read\n\n\nvoid\nCudd::ReduceHeap(\n  Cudd_ReorderingType heuristic,\n  int minsize) const\n{\n    int result = Cudd_ReduceHeap(p->manager, heuristic, minsize);\n    checkReturnValue(result);\n\n} // Cudd::ReduceHeap\n\n\nvoid\nCudd::ShuffleHeap(\n  int * permutation) const\n{\n    int result = Cudd_ShuffleHeap(p->manager, permutation);\n    checkReturnValue(result);\n\n} // Cudd::ShuffleHeap\n\n\nADD\nADD::Eval(\n  int * inputs) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_Eval(mgr, node, inputs);\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // ADD::Eval\n\n\nBDD\nBDD::Eval(\n  int * inputs) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_Eval(mgr, node, inputs);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Eval\n\n\nBDD\nABDD::ShortestPath(\n  int * weight,\n  int * support,\n  int * length) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_ShortestPath(mgr, node, weight, support, length);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ABDD::ShortestPath\n\n\nBDD\nABDD::LargestCube(\n  int * length) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_LargestCube(mgr, node, length);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ABDD::LargestCube\n\n\nint\nABDD::ShortestLength(\n  int * weight) const\n{\n    DdManager *mgr = p->manager;\n    int result = Cudd_ShortestLength(mgr, node, weight);\n    checkReturnValue(result != CUDD_OUT_OF_MEM);\n    return result;\n\n} // ABDD::ShortestLength\n\n\nBDD\nBDD::Decreasing(\n  int i) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_Decreasing(mgr, node, i);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Decreasing\n\n\nBDD\nBDD::Increasing(\n  int i) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_Increasing(mgr, node, i);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Increasing\n\n\nbool\nABDD::EquivDC(\n  const ABDD& G,\n  const ABDD& D) const\n{\n    DdManager *mgr = checkSameManager(G);\n    checkSameManager(D);\n    return Cudd_EquivDC(mgr, node, G.node, D.node);\n\n} // ABDD::EquivDC\n\nbool\nBDD::LeqUnless(\n  const BDD& G,\n  const BDD& D) const\n{\n    DdManager *mgr = checkSameManager(G);\n    checkSameManager(D);\n    int res = Cudd_bddLeqUnless(mgr, node, G.node, D.node);\n    return res;\n\n} // BDD::LeqUnless\n\n\nbool\nADD::EqualSupNorm(\n  const ADD& g,\n  CUDD_VALUE_TYPE tolerance,\n  int pr) const\n{\n    DdManager *mgr = checkSameManager(g);\n    return Cudd_EqualSupNorm(mgr, node, g.node, tolerance, pr);\n\n} // ADD::EqualSupNorm\n\n\nBDD\nBDD::MakePrime(\n  const BDD& F) const\n{\n    DdManager *mgr = checkSameManager(F);\n    if (!Cudd_CheckCube(mgr, node)) {\n        p->errorHandler(\"Invalid argument.\");\n    }\n    DdNode *result = Cudd_bddMakePrime(mgr, node, F.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD:MakePrime\n\n\nBDD\nBDD::MaximallyExpand(\n  const BDD& ub,\n  const BDD& f)\n{\n    DdManager *mgr = checkSameManager(ub);\n    checkSameManager(f);\n    DdNode *result = Cudd_bddMaximallyExpand(mgr, node, ub.node, f.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::MaximallyExpand\n\n\nBDD\nBDD::LargestPrimeUnate(\n  const BDD& phases)\n{\n    DdManager *mgr = checkSameManager(phases);\n    DdNode *result = Cudd_bddLargestPrimeUnate(mgr, node, phases.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::LargestPrimeUnate\n\n\ndouble *\nABDD::CofMinterm() const\n{\n    DdManager *mgr = p->manager;\n    double *result = Cudd_CofMinterm(mgr, node);\n    checkReturnValue(result);\n    return result;\n\n} // ABDD::CofMinterm\n\n\nBDD\nBDD::SolveEqn(\n  const BDD& Y,\n  std::vector<BDD> & G,\n  int ** yIndex,\n  int n) const\n{\n    DdManager *mgr = checkSameManager(Y);\n    DdNode **g = new DdNode *[n];\n    DdNode *result = Cudd_SolveEqn(mgr, node, Y.node, g, yIndex, n);\n    checkReturnValue(result);\n    for (int i = 0; i < n; i++) {\n        G.push_back(BDD(p, g[i]));\n\tCudd_RecursiveDeref(mgr,g[i]);\n    }\n    delete [] g;\n    return BDD(p, result);\n\n} // BDD::SolveEqn\n\n\nBDD\nBDD::VerifySol(\n  std::vector<BDD> const & G,\n  int * yIndex) const\n{\n    size_t n = G.size();\n    DdManager *mgr = p->manager;\n    DdNode **g = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tg[i] = G[i].node;\n    }\n    DdNode *result = Cudd_VerifySol(mgr, node, g, yIndex, (int) n);\n    delete [] g;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::VerifySol\n\n\nBDD\nBDD::SplitSet(\n  std::vector<BDD> xVars,\n  double m) const\n{\n    size_t n = xVars.size();\n    DdManager *mgr = p->manager;\n    DdNode **X = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tX[i] = xVars[i].node;\n    }\n    DdNode *result = Cudd_SplitSet(mgr, node, X, (int) n, m);\n    delete [] X;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::SplitSet\n\n\nBDD\nBDD::SubsetHeavyBranch(\n  int numVars,\n  int threshold) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_SubsetHeavyBranch(mgr, node, numVars, threshold);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::SubsetHeavyBranch\n\n\nBDD\nBDD::SupersetHeavyBranch(\n  int numVars,\n  int threshold) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_SupersetHeavyBranch(mgr, node, numVars, threshold);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::SupersetHeavyBranch\n\n\nBDD\nBDD::SubsetShortPaths(\n  int numVars,\n  int threshold,\n  bool hardlimit) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_SubsetShortPaths(mgr, node, numVars, threshold, hardlimit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::SubsetShortPaths\n\n\nBDD\nBDD::SupersetShortPaths(\n  int numVars,\n  int threshold,\n  bool hardlimit) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_SupersetShortPaths(mgr, node, numVars, threshold, hardlimit);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::SupersetShortPaths\n\n\nvoid\nCudd::SymmProfile(\n  int lower,\n  int upper) const\n{\n    Cudd_SymmProfile(p->manager, lower, upper);\n\n} // Cudd::SymmProfile\n\n\nunsigned int\nCudd::Prime(\n  unsigned int pr) const\n{\n    return Cudd_Prime(pr);\n\n} // Cudd::Prime\n\n\nvoid\nCudd::Reserve(\n  int amount) const\n{\n    int result = Cudd_Reserve(p->manager, amount);\n    checkReturnValue(result);\n\n} // Cudd::Reserve\n\n\nvoid\nABDD::PrintMinterm() const\n{\n    cout.flush();\n    DdManager *mgr = p->manager;\n    int result = Cudd_PrintMinterm(mgr, node);\n    checkReturnValue(result);\n\n} // ABDD::PrintMinterm\n\n\nvoid\nBDD::PrintCover() const\n{\n    cout.flush();\n    DdManager *mgr = p->manager;\n    int result = Cudd_bddPrintCover(mgr, node, node);\n    checkReturnValue(result);\n\n} // BDD::PrintCover\n\n\nvoid\nBDD::PrintCover(\n  const BDD& u) const\n{\n    checkSameManager(u);\n    cout.flush();\n    DdManager *mgr = p->manager;\n    int result = Cudd_bddPrintCover(mgr, node, u.node);\n    checkReturnValue(result);\n\n} // BDD::PrintCover\n\n\nint\nBDD::EstimateCofactor(\n  int i,\n  int phase) const\n{\n    DdManager *mgr = p->manager;\n    int result = Cudd_EstimateCofactor(mgr, node, i, phase);\n    checkReturnValue(result != CUDD_OUT_OF_MEM);\n    return result;\n\n} // BDD::EstimateCofactor\n\n\nint\nBDD::EstimateCofactorSimple(\n  int i) const\n{\n    int result = Cudd_EstimateCofactorSimple(node, i);\n    return result;\n\n} // BDD::EstimateCofactorSimple\n\n\nint\nCudd::SharingSize(\n  DD* nodes,\n  int n) const\n{\n    DdNode **nodeArray = new DdNode *[n];\n    for (int i = 0; i < n; i++) {\n\tnodeArray[i] = nodes[i].getNode();\n    }\n    int result = Cudd_SharingSize(nodeArray, n);\n    delete [] nodeArray;\n    checkReturnValue(n == 0 || result > 0);\n    return result;\n\n} // Cudd::SharingSize\n\n\nint\nCudd::SharingSize(\n  const std::vector<BDD>& v) const\n{\n    vector<BDD>::size_type n = v.size();\n    DdNode **nodeArray = new DdNode *[n];\n    for (vector<BDD>::size_type i = 0; i != n; ++i) {\n\tnodeArray[i] = v[i].getNode();\n    }\n    int result = Cudd_SharingSize(nodeArray, (int) n);\n    delete [] nodeArray;\n    checkReturnValue(n == 0 || result > 0);\n    return result;\n\n} // Cudd::SharingSize\n\n\ndouble\nABDD::CountMinterm(\n  int nvars) const\n{\n    DdManager *mgr = p->manager;\n    double result = Cudd_CountMinterm(mgr, node, nvars);\n    checkReturnValue(result != (double) CUDD_OUT_OF_MEM);\n    return result;\n\n} // ABDD::CountMinterm\n\n\ndouble\nABDD::CountPath() const\n{\n    double result = Cudd_CountPath(node);\n    checkReturnValue(result != (double) CUDD_OUT_OF_MEM);\n    return result;\n\n} // ABDD::CountPath\n\n\nBDD\nABDD::Support() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_Support(mgr, node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ABDD::Support\n\n\nint\nABDD::SupportSize() const\n{\n    DdManager *mgr = p->manager;\n    int result = Cudd_SupportSize(mgr, node);\n    checkReturnValue(result != CUDD_OUT_OF_MEM);\n    return result;\n\n} // ABDD::SupportSize\n\n\nBDD\nCudd::VectorSupport(const std::vector<BDD>& roots) const\n{\n    size_t n = roots.size();\n    DdManager *mgr = p->manager;\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tF[i] = roots[i].getNode();\n    }\n    DdNode *result = Cudd_VectorSupport(mgr, F, (int) n);\n    delete [] F;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::VectorSupport\n\n\nstd::vector<unsigned int>\nABDD::SupportIndices() const\n{\n    unsigned int *support;\n    DdManager *mgr = p->manager;\n    int size = Cudd_SupportIndices(mgr, node, (int **)&support);\n    checkReturnValue(size >= 0);\n    // size could be 0, in which case support is 0 too!\n    vector<unsigned int> indices(support, support+size);\n    if (support) free(support);\n    return indices;\n\n} // ABDD::SupportIndices\n\n\nstd::vector<unsigned int>\nCudd::SupportIndices(const std::vector<BDD>& roots) const\n{\n    unsigned int *support;\n    size_t n = roots.size();\n    DdManager *mgr = p->manager;\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tF[i] = roots[i].getNode();\n    }\n    int size = Cudd_VectorSupportIndices(mgr, F, (int) n, (int **)&support);\n    delete [] F;\n    checkReturnValue(size >= 0);\n    // size could be 0, in which case support is 0 too!\n    vector<unsigned int> indices(support, support+size);\n    if (support) free(support);\n    return indices;\n\n} // Cudd::SupportIndices\n\n\nstd::vector<unsigned int>\nCudd::SupportIndices(const std::vector<ADD>& roots) const\n{\n    unsigned int *support;\n    size_t n = roots.size();\n    DdManager *mgr = p->manager;\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tF[i] = roots[i].getNode();\n    }\n    int size = Cudd_VectorSupportIndices(mgr, F, (int) n, (int **)&support);\n    delete [] F;\n    checkReturnValue(size >= 0);\n    // size could be 0, in which case support is 0 too!\n    vector<unsigned int> indices(support, support+size);\n    if (support) free(support);\n    return indices;\n\n} // Cudd::SupportIndices\n\n\nint\nCudd::nodeCount(const std::vector<BDD>& roots) const\n{\n    size_t n = roots.size();\n    DdNode **nodeArray = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tnodeArray[i] = roots[i].getNode();\n    }\n    int result = Cudd_SharingSize(nodeArray, (int) n);\n    delete [] nodeArray;\n    checkReturnValue(result > 0);\n    return result;\n\n} // Cudd::nodeCount\n\n\nBDD\nCudd::VectorSupport(const std::vector<ADD>& roots) const\n{\n    size_t n = roots.size();\n    DdManager *mgr = p->manager;\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tF[i] = roots[i].getNode();\n    }\n    DdNode *result = Cudd_VectorSupport(mgr, F, (int) n);\n    delete [] F;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::VectorSupport\n\n\nint\nCudd::VectorSupportSize(const std::vector<BDD>& roots) const\n{\n    size_t n = roots.size();\n    DdManager *mgr = p->manager;\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tF[i] = roots[i].getNode();\n    }\n    int result = Cudd_VectorSupportSize(mgr, F, (int) n);\n    delete [] F;\n    checkReturnValue(result != CUDD_OUT_OF_MEM);\n    return result;\n\n} // Cudd::VectorSupportSize\n\n\nint\nCudd::VectorSupportSize(const std::vector<ADD>& roots) const\n{\n    size_t n = roots.size();\n    DdManager *mgr = p->manager;\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tF[i] = roots[i].getNode();\n    }\n    int result = Cudd_VectorSupportSize(mgr, F, (int) n);\n    delete [] F;\n    checkReturnValue(result != CUDD_OUT_OF_MEM);\n    return result;\n\n} // Cudd::VectorSupportSize\n\n\nvoid\nABDD::ClassifySupport(\n  const ABDD& g,\n  BDD* common,\n  BDD* onlyF,\n  BDD* onlyG) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *C, *F, *G;\n    int result = Cudd_ClassifySupport(mgr, node, g.node, &C, &F, &G);\n    checkReturnValue(result);\n    *common = BDD(p, C);\n    *onlyF = BDD(p, F);\n    *onlyG = BDD(p, G);\n\n} // ABDD::ClassifySupport\n\n\nint\nABDD::CountLeaves() const\n{\n    return Cudd_CountLeaves(node);\n\n} // ABDD::CountLeaves\n\n\nvoid\nBDD::PickOneCube(\n  char * string) const\n{\n    DdManager *mgr = p->manager;\n    int result = Cudd_bddPickOneCube(mgr, node, string);\n    checkReturnValue(result);\n\n} // BDD::PickOneCube\n\n\nBDD\nBDD::PickOneMinterm(\n  std::vector<BDD> vars) const\n{\n    size_t n = vars.size();\n    DdManager *mgr = p->manager;\n    DdNode **V = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tV[i] = vars[i].node;\n    }\n    DdNode *result = Cudd_bddPickOneMinterm(mgr, node, V, (int) n);\n    delete [] V;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::PickOneMinterm\n\n\nBDD\nCudd::bddComputeCube(\n  BDD * vars,\n  int * phase,\n  int n) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **V = new DdNode *[n];\n    for (int i = 0; i < n; i++) {\n\tV[i] = vars[i].getNode();\n    }\n    DdNode *result = Cudd_bddComputeCube(mgr, V, phase, n);\n    delete [] V;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::bddComputeCube\n\n\nBDD\nCudd::computeCube(\n  std::vector<BDD> const & vars) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = vars.size();\n    DdNode **V = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tV[i] = vars[i].getNode();\n    }\n    DdNode *result = Cudd_bddComputeCube(mgr, V, 0, n);\n    delete [] V;\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::computeCube\n\n\nADD\nCudd::addComputeCube(\n  ADD * vars,\n  int * phase,\n  int n) const\n{\n    DdManager *mgr = p->manager;\n    DdNode **V = new DdNode *[n];\n    for (int i = 0; i < n; i++) {\n\tV[i] = vars[i].getNode();\n    }\n    DdNode *result = Cudd_addComputeCube(mgr, V, phase, n);\n    delete [] V;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::addComputeCube\n\n\nADD\nCudd::computeCube(\n  std::vector<ADD> const & vars) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = vars.size();\n    DdNode **V = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tV[i] = vars[i].getNode();\n    }\n    DdNode *result = Cudd_addComputeCube(mgr, V, 0, n);\n    delete [] V;\n    checkReturnValue(result);\n    return ADD(p, result);\n\n} // Cudd::computeCube\n\n\nBDD\nCudd::IndicesToCube(\n  int * array,\n  int n) const\n{\n    DdNode *result = Cudd_IndicesToCube(p->manager, array, n);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // Cudd::IndicesToCube\n\n\nvoid\nCudd::PrintVersion(\n  FILE * fp) const\n{\n    cout.flush();\n    Cudd_PrintVersion(fp);\n\n} // Cudd::PrintVersion\n\n\ndouble\nCudd::AverageDistance() const\n{\n    return Cudd_AverageDistance(p->manager);\n\n} // Cudd::AverageDistance\n\n\nint32_t\nCudd::Random() const\n{\n    return Cudd_Random(p->manager);\n\n} // Cudd::Random\n\n\nvoid\nCudd::Srandom(\n  int32_t seed) const\n{\n    Cudd_Srandom(p->manager,seed);\n\n} // Cudd::Srandom\n\n\ndouble\nABDD::Density(\n  int nvars) const\n{\n    DdManager *mgr = p->manager;\n    double result = Cudd_Density(mgr, node, nvars);\n    checkReturnValue(result != (double) CUDD_OUT_OF_MEM);\n    return result;\n\n} // ABDD::Density\n\n\nint\nZDD::Count() const\n{\n    DdManager *mgr = p->manager;\n    int result = Cudd_zddCount(mgr, node);\n    checkReturnValue(result != CUDD_OUT_OF_MEM);\n    return result;\n\n} // ZDD::Count\n\n\ndouble\nZDD::CountDouble() const\n{\n    DdManager *mgr = p->manager;\n    double result = Cudd_zddCountDouble(mgr, node);\n    checkReturnValue(result != (double) CUDD_OUT_OF_MEM);\n    return result;\n\n} // ZDD::CountDouble\n\n\nZDD\nZDD::Product(\n  const ZDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_zddProduct(mgr, node, g.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Product\n\n\nZDD\nZDD::UnateProduct(\n  const ZDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_zddUnateProduct(mgr, node, g.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::UnateProduct\n\n\nZDD\nZDD::WeakDiv(\n  const ZDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_zddWeakDiv(mgr, node, g.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::WeakDiv\n\n\nZDD\nZDD::Divide(\n  const ZDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_zddDivide(mgr, node, g.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Divide\n\n\nZDD\nZDD::WeakDivF(\n  const ZDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_zddWeakDivF(mgr, node, g.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::WeakDivF\n\n\nZDD\nZDD::DivideF(\n  const ZDD& g) const\n{\n    DdManager *mgr = checkSameManager(g);\n    DdNode *result = Cudd_zddDivideF(mgr, node, g.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::DivideF\n\n\nMtrNode *\nCudd::MakeZddTreeNode(\n  unsigned int low,\n  unsigned int size,\n  unsigned int type) const\n{\n    return Cudd_MakeZddTreeNode(p->manager, low, size, type);\n\n} // Cudd::MakeZddTreeNode\n\n\nBDD\nBDD::zddIsop(\n  const BDD& U,\n  ZDD* zdd_I) const\n{\n    DdManager *mgr = checkSameManager(U);\n    DdNode *Z;\n    DdNode *result = Cudd_zddIsop(mgr, node, U.node, &Z);\n    checkReturnValue(result);\n    *zdd_I = ZDD(p, Z);\n    return BDD(p, result);\n\n} // BDD::Isop\n\n\nBDD\nBDD::Isop(\n  const BDD& U) const\n{\n    DdManager *mgr = checkSameManager(U);\n    DdNode *result = Cudd_bddIsop(mgr, node, U.node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // BDD::Isop\n\n\ndouble\nZDD::CountMinterm(\n  int path) const\n{\n    DdManager *mgr = p->manager;\n    double result = Cudd_zddCountMinterm(mgr, node, path);\n    checkReturnValue(result != (double) CUDD_OUT_OF_MEM);\n    return result;\n\n} // ZDD::CountMinterm\n\n\nvoid\nCudd::zddPrintSubtable() const\n{\n    cout.flush();\n    Cudd_zddPrintSubtable(p->manager);\n\n} // Cudd::zddPrintSubtable\n\n\nZDD\nBDD::PortToZdd() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_zddPortFromBdd(mgr, node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // BDD::PortToZdd\n\n\nBDD\nZDD::PortToBdd() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_zddPortToBdd(mgr, node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ZDD::PortToBdd\n\n\nvoid\nCudd::zddReduceHeap(\n  Cudd_ReorderingType heuristic,\n  int minsize) const\n{\n    int result = Cudd_zddReduceHeap(p->manager, heuristic, minsize);\n    checkReturnValue(result);\n\n} // Cudd::zddReduceHeap\n\n\nvoid\nCudd::zddShuffleHeap(\n  int * permutation) const\n{\n    int result = Cudd_zddShuffleHeap(p->manager, permutation);\n    checkReturnValue(result);\n\n} // Cudd::zddShuffleHeap\n\n\nZDD\nZDD::Ite(\n  const ZDD& g,\n  const ZDD& h) const\n{\n    DdManager *mgr = checkSameManager(g);\n    checkSameManager(h);\n    DdNode *result = Cudd_zddIte(mgr, node, g.node, h.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Ite\n\n\nZDD\nZDD::Union(\n  const ZDD& Q) const\n{\n    DdManager *mgr = checkSameManager(Q);\n    DdNode *result = Cudd_zddUnion(mgr, node, Q.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Union\n\n\nZDD\nZDD::Intersect(\n  const ZDD& Q) const\n{\n    DdManager *mgr = checkSameManager(Q);\n    DdNode *result = Cudd_zddIntersect(mgr, node, Q.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Intersect\n\n\nZDD\nZDD::Diff(\n  const ZDD& Q) const\n{\n    DdManager *mgr = checkSameManager(Q);\n    DdNode *result = Cudd_zddDiff(mgr, node, Q.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Diff\n\n\nZDD\nZDD::DiffConst(\n  const ZDD& Q) const\n{\n    DdManager *mgr = checkSameManager(Q);\n    DdNode *result = Cudd_zddDiffConst(mgr, node, Q.node);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::DiffConst\n\n\nZDD\nZDD::Subset1(\n  int var) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_zddSubset1(mgr, node, var);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Subset1\n\n\nZDD\nZDD::Subset0(\n  int var) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_zddSubset0(mgr, node, var);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Subset0\n\n\nZDD\nZDD::Change(\n  int var) const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_zddChange(mgr, node, var);\n    checkReturnValue(result);\n    return ZDD(p, result);\n\n} // ZDD::Change\n\n\nvoid\nCudd::zddSymmProfile(\n  int lower,\n  int upper) const\n{\n    Cudd_zddSymmProfile(p->manager, lower, upper);\n\n} // Cudd::zddSymmProfile\n\n\nvoid\nZDD::PrintMinterm() const\n{\n    cout.flush();\n    DdManager *mgr = p->manager;\n    int result = Cudd_zddPrintMinterm(mgr, node);\n    checkReturnValue(result);\n\n} // ZDD::PrintMinterm\n\n\nvoid\nZDD::PrintCover() const\n{\n    cout.flush();\n    DdManager *mgr = p->manager;\n    int result = Cudd_zddPrintCover(mgr, node);\n    checkReturnValue(result);\n\n} // ZDD::PrintCover\n\n\nBDD\nZDD::Support() const\n{\n    DdManager *mgr = p->manager;\n    DdNode *result = Cudd_zddSupport(mgr, node);\n    checkReturnValue(result);\n    return BDD(p, result);\n\n} // ZDD::Support\n\n\nvoid\nCudd::DumpDot(\n  const std::vector<ZDD>& nodes,\n  char const * const * inames,\n  char const * const * onames,\n  FILE * fp) const\n{\n    DdManager *mgr = p->manager;\n    size_t n = nodes.size();\n    DdNode **F = new DdNode *[n];\n    for (size_t i = 0; i < n; i++) {\n\tF[i] = nodes[i].getNode();\n    }\n    int result = Cudd_zddDumpDot(mgr, (int) n, F, inames, onames, fp);\n    delete [] F;\n    checkReturnValue(result);\n\n} // vector<ZDD>::DumpDot\n\n\nstd::string\nCudd::OrderString(void) const\n{\n    DdManager * mgr = p->manager;\n    int nvars = Cudd_ReadSize(mgr);\n    bool hasNames = p->varnames.size() == (size_t) nvars;\n    std::ostringstream oss;\n    std::string separ = \"\";\n    for (int level = 0; level != nvars; ++level) {\n        oss << separ;\n        separ = \" \";\n        int index = Cudd_ReadInvPerm(mgr, level);\n        if (hasNames) {\n            oss << p->varnames.at(index);\n        } else {\n            oss << \"x\" << index;\n        }\n    }\n    return oss.str();\n\n} // Cudd::OrderString\n"
  },
  {
    "path": "cudd/cplusplus/cuddObj.hh",
    "content": "/**\n  @file\n\n  @ingroup cplusplus\n\n  @brief Class definitions for C++ object-oriented encapsulation of\n  CUDD.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef CUDD_OBJ_H_\n#define CUDD_OBJ_H_\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n\n#include <cstdio>\n#include <string>\n#include <vector>\n#include \"cudd.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Type definitions                                                          */\n/*---------------------------------------------------------------------------*/\nclass BDD;\nclass ADD;\nclass ZDD;\nclass Cudd;\n\ntypedef void (*PFC)(std::string);\t// handler function type\n\n/*---------------------------------------------------------------------------*/\n/* Class definitions                                                         */\n/*---------------------------------------------------------------------------*/\n\nclass Capsule;\n\n\n/**\n  @brief Base class for all decision diagrams in CUDD.\n\n  @see Cudd ABDD ADD BDD ZDD\n\n*/\nclass DD {\nprotected:\n    Capsule *p;\n    DdNode *node;\n    inline DdManager * checkSameManager(const DD &other) const;\n    inline void checkReturnValue(const void *result) const;\n    inline void checkReturnValue(int result, int expected = 1)\n\tconst;\n    DD();\n    DD(Capsule *cap, DdNode *ddNode);\n    DD(Cudd const & manager, DdNode *ddNode);\n    DD(const DD &from);\n    ~DD();\npublic:\n    // This operator should be declared explicit, but there are still too many\n    // compilers out there that do not support this C++11 feature.\n    operator bool() const { return node; }\n    DdManager * manager() const;\n    DdNode * getNode() const;\n    DdNode * getRegularNode() const;\n    int nodeCount() const;\n    unsigned int NodeReadIndex() const;\n\n}; // DD\n\n\n/**\n  @brief Class for ADDs and BDDs.\n\n  @see Cudd ADD BDD\n\n*/\nclass ABDD : public DD {\n    friend class Cudd;\nprotected:\n    ABDD();\n    ABDD(Capsule *cap, DdNode *bddNode);\n    ABDD(Cudd const & manager, DdNode *ddNode);\n    ABDD(const ABDD &from);\n    ~ABDD();\npublic:\n    bool operator==(const ABDD &other) const;\n    bool operator!=(const ABDD &other) const;\n    void print(int nvars, int verbosity = 1) const;\n    void summary(int nvars, int mode = 0) const;\n    DdApaNumber ApaCountMinterm(int nvars, int * digits) const;\n    void ApaPrintMinterm(int nvars, FILE * fp = stdout) const;\n    void ApaPrintMintermExp(int nvars, int precision = 6, FILE * fp = stdout) const;\n    void EpdPrintMinterm(int nvars, FILE * fp = stdout) const;\n    long double LdblCountMinterm(int nvars) const;\n    bool IsOne() const;\n    bool IsCube() const;\n    BDD FindEssential() const;\n    void PrintTwoLiteralClauses(char ** names = 0, FILE * fp = stdout) const;\n    BDD ShortestPath(int * weight, int * support, int * length) const;\n    BDD LargestCube(int * length = 0) const;\n    int ShortestLength(int * weight = 0) const;\n    bool EquivDC(const ABDD& G, const ABDD& D) const;\n    double * CofMinterm() const;\n    void PrintMinterm() const;\n    double CountMinterm(int nvars) const;\n    double CountPath() const;\n    BDD Support() const;\n    int SupportSize() const;\n    std::vector<unsigned int> SupportIndices() const;\n    void ClassifySupport(const ABDD& g, BDD* common, BDD* onlyF, BDD* onlyG)\n\tconst;\n    int CountLeaves() const;\n    double Density(int nvars) const;\n\n}; // ABDD\n\n\n/**\n  @brief Class for BDDs.\n\n  @see Cudd\n\n*/\nclass BDD : public ABDD {\n    friend class Cudd;\npublic:\n    BDD();\n    BDD(Capsule *cap, DdNode *bddNode);\n    BDD(Cudd const & manager, DdNode *ddNode);\n    BDD(const BDD &from);\n    BDD operator=(const BDD& right);\n    bool operator<=(const BDD& other) const;\n    bool operator>=(const BDD& other) const;\n    bool operator<(const BDD& other) const;\n    bool operator>(const BDD& other) const;\n    BDD operator!() const;\n    BDD operator~() const;\n    BDD operator*(const BDD& other) const;\n    BDD operator*=(const BDD& other);\n    BDD operator&(const BDD& other) const;\n    BDD operator&=(const BDD& other);\n    BDD operator+(const BDD& other) const;\n    BDD operator+=(const BDD& other);\n    BDD operator|(const BDD& other) const;\n    BDD operator|=(const BDD& other);\n    BDD operator^(const BDD& other) const;\n    BDD operator^=(const BDD& other);\n    BDD operator-(const BDD& other) const;\n    BDD operator-=(const BDD& other);\n    friend std::ostream & operator<<(std::ostream & os, BDD const & f);\n    bool IsZero() const;\n    bool IsVar() const;\n    BDD AndAbstract(const BDD& g, const BDD& cube, unsigned int limit = 0)\n\tconst;\n    BDD UnderApprox(\n      int numVars,\n      int threshold = 0,\n      bool safe = false,\n      double quality = 1.0) const;\n    BDD OverApprox(\n      int numVars,\n      int threshold = 0,\n      bool safe = false,\n      double quality = 1.0) const;\n    BDD RemapUnderApprox(int numVars, int threshold = 0, double quality = 1.0)\n\tconst;\n    BDD RemapOverApprox(int numVars, int threshold = 0, double quality = 1.0)\n\tconst;\n    BDD BiasedUnderApprox(const BDD& bias, int numVars, int threshold = 0, \n                          double quality1 = 1.0, double quality0 = 1.0) const;\n    BDD BiasedOverApprox(const BDD& bias, int numVars, int threshold = 0, \n                         double quality1 = 1.0, double quality0 = 1.0) const;\n    BDD ExistAbstract(const BDD& cube, unsigned int limit = 0) const;\n    BDD XorExistAbstract(const BDD& g, const BDD& cube) const;\n    BDD UnivAbstract(const BDD& cube) const;\n    BDD BooleanDiff(int x) const;\n    bool VarIsDependent(const BDD& var) const;\n    double Correlation(const BDD& g) const;\n    double CorrelationWeights(const BDD& g, double * prob) const;\n    BDD Ite(const BDD& g, const BDD& h, unsigned int limit = 0) const;\n    BDD IteConstant(const BDD& g, const BDD& h) const;\n    BDD Intersect(const BDD& g) const;\n    BDD And(const BDD& g, unsigned int limit = 0) const;\n    BDD Or(const BDD& g, unsigned int limit = 0) const;\n    BDD Nand(const BDD& g) const;\n    BDD Nor(const BDD& g) const;\n    BDD Xor(const BDD& g) const;\n    BDD Xnor(const BDD& g, unsigned int limit = 0) const;\n    bool Leq(const BDD& g) const;\n    ADD Add() const;\n    BDD Transfer(Cudd& destination) const;\n    BDD ClippingAnd(const BDD& g, int maxDepth, int direction = 0) const;\n    BDD ClippingAndAbstract(const BDD& g, const BDD& cube, int maxDepth,\n\t\t\t    int direction = 0) const;\n    BDD Cofactor(const BDD& g) const;\n    bool VarAreSymmetric(int index1, int index2) const;\n    BDD Compose(const BDD& g, int v) const;\n    BDD Permute(int * permut) const;\n    BDD SwapVariables(std::vector<BDD> x, std::vector<BDD> y) const;\n    BDD AdjPermuteX(std::vector<BDD> x) const;\n    BDD VectorCompose(std::vector<BDD> vector) const;\n    void ApproxConjDecomp(BDD* g, BDD* h) const;\n    void ApproxDisjDecomp(BDD* g, BDD* h) const;\n    void IterConjDecomp(BDD* g, BDD* h) const;\n    void IterDisjDecomp(BDD* g, BDD* h) const;\n    void GenConjDecomp(BDD* g, BDD* h) const;\n    void GenDisjDecomp(BDD* g, BDD* h) const;\n    void VarConjDecomp(BDD* g, BDD* h) const;\n    void VarDisjDecomp(BDD* g, BDD* h) const;\n    bool IsVarEssential(int id, int phase) const;\n    BDD Constrain(const BDD& c) const;\n    BDD Restrict(const BDD& c) const;\n    BDD NPAnd(const BDD& g) const;\n    std::vector<BDD> ConstrainDecomp() const;\n    std::vector<BDD> CharToVect() const;\n    BDD LICompaction(const BDD& c) const;\n    BDD Squeeze(const BDD& u) const;\n    BDD Interpolate(const BDD& u) const;\n    BDD Minimize(const BDD& c) const;\n    BDD SubsetCompress(int nvars, int threshold) const;\n    BDD SupersetCompress(int nvars, int threshold) const;\n    BDD LiteralSetIntersection(const BDD& g) const;\n    BDD PrioritySelect(std::vector<BDD> x, std::vector<BDD> y,\n\t\t       std::vector<BDD> z, const BDD& Pi, DD_PRFP Pifunc) const;\n    BDD CProjection(const BDD& Y) const;\n    int MinHammingDist(int *minterm, int upperBound) const;\n    BDD Eval(int * inputs) const;\n    BDD Decreasing(int i) const;\n    BDD Increasing(int i) const;\n    bool LeqUnless(const BDD& G, const BDD& D) const;\n    BDD MakePrime(const BDD& F) const;\n    BDD MaximallyExpand(const BDD& ub, const BDD& f);\n    BDD LargestPrimeUnate(const BDD& phases);\n    BDD SolveEqn(const BDD& Y, std::vector<BDD> & G, int ** yIndex, int n) const;\n    BDD VerifySol(std::vector<BDD> const & G, int * yIndex) const;\n    BDD SplitSet(std::vector<BDD> xVars, double m) const;\n    BDD SubsetHeavyBranch(int numVars, int threshold) const;\n    BDD SupersetHeavyBranch(int numVars, int threshold) const;\n    BDD SubsetShortPaths(int numVars, int threshold, bool hardlimit = false) const;\n    BDD SupersetShortPaths(int numVars, int threshold, bool hardlimit = false) const;\n    void PrintCover() const;\n    void PrintCover(const BDD& u) const;\n    int EstimateCofactor(int i, int phase) const;\n    int EstimateCofactorSimple(int i) const;\n    void PickOneCube(char * string) const;\n    BDD PickOneMinterm(std::vector<BDD> vars) const;\n    BDD zddIsop(const BDD& U, ZDD* zdd_I) const;\n    BDD Isop(const BDD& U) const;\n    ZDD PortToZdd() const;\n    void PrintFactoredForm(char const * const * inames = 0, FILE * fp = stdout) const;\n    std::string FactoredFormString(char const * const * inames = 0) const;\n\n}; // BDD\n\n\n/**\n  @brief Class for ADDs.\n\n  @see Cudd\n\n*/\nclass ADD : public ABDD {\n    friend class Cudd;\npublic:\n    ADD();\n    ADD(Capsule *cap, DdNode *bddNode);\n    ADD(Cudd const & manager, DdNode *ddNode);\n    ADD(const ADD &from);\n    ADD operator=(const ADD& right);\n    // Relational operators\n    bool operator<=(const ADD& other) const;\n    bool operator>=(const ADD& other) const;\n    bool operator<(const ADD& other) const;\n    bool operator>(const ADD& other) const;\n    // Arithmetic operators\n    ADD operator-() const;\n    ADD operator*(const ADD& other) const;\n    ADD operator*=(const ADD& other);\n    ADD operator+(const ADD& other) const;\n    ADD operator+=(const ADD& other);\n    ADD operator-(const ADD& other) const;\n    ADD operator-=(const ADD& other);\n    // Logical operators\n    ADD operator~() const;\n    ADD operator&(const ADD& other) const;\n    ADD operator&=(const ADD& other);\n    ADD operator|(const ADD& other) const;\n    ADD operator|=(const ADD& other);\n    bool IsZero() const;\n    ADD ExistAbstract(const ADD& cube) const;\n    ADD UnivAbstract(const ADD& cube) const;\n    ADD OrAbstract(const ADD& cube) const;\n    ADD Plus(const ADD& g) const;\n    ADD Times(const ADD& g) const;\n    ADD Threshold(const ADD& g) const;\n    ADD SetNZ(const ADD& g) const;\n    ADD Divide(const ADD& g) const;\n    ADD Minus(const ADD& g) const;\n    ADD Minimum(const ADD& g) const;\n    ADD Maximum(const ADD& g) const;\n    ADD OneZeroMaximum(const ADD& g) const;\n    ADD Diff(const ADD& g) const;\n    ADD Agreement(const ADD& g) const;\n    ADD Or(const ADD& g) const;\n    ADD Nand(const ADD& g) const;\n    ADD Nor(const ADD& g) const;\n    ADD Xor(const ADD& g) const;\n    ADD Xnor(const ADD& g) const;\n    ADD Log() const;\n    ADD FindMax() const;\n    ADD FindMin() const;\n    ADD IthBit(int bit) const;\n    ADD ScalarInverse(const ADD& epsilon) const;\n    ADD Ite(const ADD& g, const ADD& h) const;\n    ADD IteConstant(const ADD& g, const ADD& h) const;\n    ADD EvalConst(const ADD& g) const;\n    bool Leq(const ADD& g) const;\n    ADD Cmpl() const;\n    ADD Negate() const;\n    ADD RoundOff(int N) const;\n    BDD BddThreshold(CUDD_VALUE_TYPE value) const;\n    BDD BddStrictThreshold(CUDD_VALUE_TYPE value) const;\n    BDD BddInterval(CUDD_VALUE_TYPE lower, CUDD_VALUE_TYPE upper) const;\n    BDD BddIthBit(int bit) const;\n    BDD BddPattern() const;\n    ADD Cofactor(const ADD& g) const;\n    ADD Compose(const ADD& g, int v) const;\n    ADD Permute(int * permut) const;\n    ADD SwapVariables(std::vector<ADD> x, std::vector<ADD> y) const;\n    ADD VectorCompose(std::vector<ADD> vector) const;\n    ADD NonSimCompose(std::vector<ADD> vector) const;\n    ADD Constrain(const ADD& c) const;\n    ADD Restrict(const ADD& c) const;\n    ADD MatrixMultiply(const ADD& B, std::vector<ADD> z) const;\n    ADD TimesPlus(const ADD& B, std::vector<ADD> z) const;\n    ADD Triangle(const ADD& g, std::vector<ADD> z) const;\n    ADD Eval(int * inputs) const;\n    bool EqualSupNorm(const ADD& g, CUDD_VALUE_TYPE tolerance, int pr) const;\n\n}; // ADD\n\n\n/**\n  @brief Class for ZDDs.\n\n  @see Cudd\n\n*/\nclass ZDD : public DD {\n    friend class Cudd;\npublic:\n    ZDD(Capsule *cap, DdNode *bddNode);\n    ZDD();\n    ZDD(const ZDD &from);\n    ~ZDD();\n    ZDD operator=(const ZDD& right);\n    bool operator==(const ZDD& other) const;\n    bool operator!=(const ZDD& other) const;\n    bool operator<=(const ZDD& other) const;\n    bool operator>=(const ZDD& other) const;\n    bool operator<(const ZDD& other) const;\n    bool operator>(const ZDD& other) const;\n    void print(int nvars, int verbosity = 1) const;\n    ZDD operator*(const ZDD& other) const;\n    ZDD operator*=(const ZDD& other);\n    ZDD operator&(const ZDD& other) const;\n    ZDD operator&=(const ZDD& other);\n    ZDD operator+(const ZDD& other) const;\n    ZDD operator+=(const ZDD& other);\n    ZDD operator|(const ZDD& other) const;\n    ZDD operator|=(const ZDD& other);\n    ZDD operator-(const ZDD& other) const;\n    ZDD operator-=(const ZDD& other);\n    int Count() const;\n    double CountDouble() const;\n    ZDD Product(const ZDD& g) const;\n    ZDD UnateProduct(const ZDD& g) const;\n    ZDD WeakDiv(const ZDD& g) const;\n    ZDD Divide(const ZDD& g) const;\n    ZDD WeakDivF(const ZDD& g) const;\n    ZDD DivideF(const ZDD& g) const;\n    double CountMinterm(int path) const;\n    BDD PortToBdd() const;\n    ZDD Ite(const ZDD& g, const ZDD& h) const;\n    ZDD Union(const ZDD& Q) const;\n    ZDD Intersect(const ZDD& Q) const;\n    ZDD Diff(const ZDD& Q) const;\n    ZDD DiffConst(const ZDD& Q) const;\n    ZDD Subset1(int var) const;\n    ZDD Subset0(int var) const;\n    ZDD Change(int var) const;\n    void PrintMinterm() const;\n    void PrintCover() const;\n    BDD Support() const;\n\n}; // ZDD\n\n\n/**\n   @brief Default error handler.\n*/\nextern void defaultError(std::string message);\n\n\n/**\n  @brief Class for CUDD managers.\n\n  @see DD\n\n*/\nclass Cudd {\n    friend class DD;\n    friend class ABDD;\n    friend class BDD;\n    friend class ADD;\n    friend class ZDD;\n    friend std::ostream & operator<<(std::ostream & os, BDD const & f);\nprivate:\n    Capsule *p;\npublic:\n    Cudd(\n      unsigned int numVars = 0,\n      unsigned int numVarsZ = 0,\n      unsigned int numSlots = CUDD_UNIQUE_SLOTS,\n      unsigned int cacheSize = CUDD_CACHE_SLOTS,\n      unsigned long maxMemory = 0,\n      PFC defaultHandler = defaultError);\n    Cudd(const Cudd& x);\n    ~Cudd(void);\n    PFC setHandler(PFC newHandler) const;\n    PFC getHandler(void) const;\n    PFC setTimeoutHandler(PFC newHandler) const;\n    PFC getTimeoutHandler(void) const;\n    PFC setTerminationHandler(PFC newHandler) const;\n    PFC getTerminationHandler(void) const;\n    void pushVariableName(std::string s) const;\n    void clearVariableNames(void) const;\n    std::string getVariableName(size_t i) const;\n    DdManager *getManager(void) const;\n    void makeVerbose(void) const;\n    void makeTerse(void) const;\n    bool isVerbose(void) const;\n    void checkReturnValue(const void *result) const;\n    void checkReturnValue(const int result) const;\n    Cudd& operator=(const Cudd& right);\n    void info(void) const;\n    BDD bddVar(void) const;\n    BDD bddVar(int index) const;\n    BDD bddOne(void) const;\n    BDD bddZero(void) const;\n    ADD addVar(void) const;\n    ADD addVar(int index) const;\n    ADD addOne(void) const;\n    ADD addZero(void) const;\n    ADD constant(CUDD_VALUE_TYPE c) const;\n    ADD plusInfinity(void) const;\n    ADD minusInfinity(void) const;\n    ZDD zddVar(int index) const;\n    ZDD zddOne(int i) const;\n    ZDD zddZero(void) const;\n    ADD addNewVarAtLevel(int level) const;\n    BDD bddNewVarAtLevel(int level) const;\n    void zddVarsFromBddVars(int multiplicity) const;\n    unsigned long ReadStartTime(void) const;\n    unsigned long ReadElapsedTime(void) const;\n    void SetStartTime(unsigned long st) const;\n    void ResetStartTime(void) const;\n    unsigned long ReadTimeLimit(void) const;\n    unsigned long SetTimeLimit(unsigned long tl) const;\n    void UpdateTimeLimit(void) const;\n    void IncreaseTimeLimit(unsigned long increase) const;\n    void UnsetTimeLimit(void) const;\n    bool TimeLimited(void) const;\n    void RegisterTerminationCallback(DD_THFP callback,\n                                     void * callback_arg) const;\n    void UnregisterTerminationCallback(void) const;\n    DD_OOMFP RegisterOutOfMemoryCallback(DD_OOMFP callback) const;\n    void UnregisterOutOfMemoryCallback(void) const;\n    void AutodynEnable(Cudd_ReorderingType method = CUDD_REORDER_SIFT) const;\n    void AutodynDisable(void) const;\n    bool ReorderingStatus(Cudd_ReorderingType * method) const;\n    void AutodynEnableZdd(Cudd_ReorderingType method = CUDD_REORDER_SIFT) const;\n    void AutodynDisableZdd(void) const;\n    bool ReorderingStatusZdd(Cudd_ReorderingType * method) const;\n    bool zddRealignmentEnabled(void) const;\n    void zddRealignEnable(void) const;\n    void zddRealignDisable(void) const;\n    bool bddRealignmentEnabled(void) const;\n    void bddRealignEnable(void) const;\n    void bddRealignDisable(void) const;\n    ADD background(void) const;\n    void SetBackground(ADD bg) const;\n    unsigned int ReadCacheSlots(void) const;\n    double ReadCacheUsedSlots(void) const;\n    double ReadCacheLookUps(void) const;\n    double ReadCacheHits(void) const;\n    unsigned int ReadMinHit(void) const;\n    void SetMinHit(unsigned int hr) const;\n    unsigned int ReadLooseUpTo(void) const;\n    void SetLooseUpTo(unsigned int lut) const;\n    unsigned int ReadMaxCache(void) const;\n    unsigned int ReadMaxCacheHard(void) const;\n    void SetMaxCacheHard(unsigned int mc) const;\n    int ReadSize(void) const;\n    int ReadZddSize(void) const;\n    unsigned int ReadSlots(void) const;\n    unsigned int ReadKeys(void) const;\n    unsigned int ReadDead(void) const;\n    unsigned int ReadMinDead(void) const;\n    unsigned int ReadReorderings(void) const;\n    unsigned int ReadMaxReorderings(void) const;\n    void SetMaxReorderings(unsigned int mr) const;\n    long ReadReorderingTime(void) const;\n    int ReadGarbageCollections(void) const;\n    long ReadGarbageCollectionTime(void) const;\n    int ReadSiftMaxVar(void) const;\n    void SetSiftMaxVar(int smv) const;\n    int ReadSiftMaxSwap(void) const;\n    void SetSiftMaxSwap(int sms) const;\n    double ReadMaxGrowth(void) const;\n    void SetMaxGrowth(double mg) const;\n#ifdef MTR_H_\n    MtrNode * ReadTree(void) const;\n    void SetTree(MtrNode * tree) const;\n    void FreeTree(void) const;\n    MtrNode * ReadZddTree(void) const;\n    void SetZddTree(MtrNode * tree) const;\n    void FreeZddTree(void) const;\n    MtrNode * MakeTreeNode(unsigned int low, unsigned int size,\n                           unsigned int type) const;\n    MtrNode * MakeZddTreeNode(unsigned int low, unsigned int size,\n                              unsigned int type) const;\n#endif\n    int ReadPerm(int i) const;\n    int ReadPermZdd(int i) const;\n    int ReadInvPerm(int i) const;\n    int ReadInvPermZdd(int i) const;\n    BDD ReadVars(int i) const;\n    CUDD_VALUE_TYPE ReadEpsilon(void) const;\n    void SetEpsilon(CUDD_VALUE_TYPE ep) const;\n    Cudd_AggregationType ReadGroupcheck(void) const;\n    void SetGroupcheck(Cudd_AggregationType gc) const;\n    bool GarbageCollectionEnabled(void) const;\n    void EnableGarbageCollection(void) const;\n    void DisableGarbageCollection(void) const;\n    bool DeadAreCounted(void) const;\n    void TurnOnCountDead(void) const;\n    void TurnOffCountDead(void) const;\n    int ReadRecomb(void) const;\n    void SetRecomb(int recomb) const;\n    int ReadSymmviolation(void) const;\n    void SetSymmviolation(int symmviolation) const;\n    int ReadArcviolation(void) const;\n    void SetArcviolation(int arcviolation) const;\n    int ReadPopulationSize(void) const;\n    void SetPopulationSize(int populationSize) const;\n    int ReadNumberXovers(void) const;\n    void SetNumberXovers(int numberXovers) const;\n    unsigned int ReadOrderRandomization(void) const;\n    void SetOrderRandomization(unsigned int factor) const;\n    unsigned long ReadMemoryInUse(void) const;\n    long ReadPeakNodeCount(void) const;\n    long ReadNodeCount(void) const;\n    long zddReadNodeCount(void) const;\n    void AddHook(DD_HFP f, Cudd_HookType where) const;\n    void RemoveHook(DD_HFP f, Cudd_HookType where) const;\n    bool IsInHook(DD_HFP f, Cudd_HookType where) const;\n    void EnableReorderingReporting(void) const;\n    void DisableReorderingReporting(void) const;\n    bool ReorderingReporting(void) const;\n    int ReadErrorCode(void) const;\n    DD_OOMFP InstallOutOfMemoryHandler(DD_OOMFP newHandler) const;\n    void ClearErrorCode(void) const;\n    FILE *ReadStdout(void) const;\n    void SetStdout(FILE * fp) const;\n    FILE *ReadStderr(void) const;\n    void SetStderr(FILE * fp) const;\n    unsigned int ReadNextReordering(void) const;\n    void SetNextReordering(unsigned int) const;\n    double ReadSwapSteps(void) const;\n    unsigned int ReadMaxLive(void) const;\n    void SetMaxLive(unsigned int) const;\n    size_t ReadMaxMemory(void) const;\n    size_t SetMaxMemory(size_t) const;\n    int bddBindVar(int) const;\n    int bddUnbindVar(int) const;\n    bool bddVarIsBound(int) const;\n    ADD Walsh(std::vector<ADD> x, std::vector<ADD> y) const;\n    ADD addResidue(int n, int m, int options, int top) const;\n    int ApaNumberOfDigits(int binaryDigits) const;\n    DdApaNumber NewApaNumber(int digits) const;\n    void ApaCopy(int digits, DdApaNumber source, DdApaNumber dest) const;\n    DdApaDigit ApaAdd(int digits, DdApaNumber a, DdApaNumber b, DdApaNumber\n\t\t      sum) const;\n    DdApaDigit ApaSubtract(int digits, DdApaNumber a, DdApaNumber b,\n\t\t\t   DdApaNumber diff) const;\n    DdApaDigit ApaShortDivision(int digits, DdApaNumber dividend, DdApaDigit\n\t\t\t\tdivisor, DdApaNumber quotient) const;\n    void ApaShiftRight(int digits, DdApaDigit in, DdApaNumber a, DdApaNumber\n\t\t       b) const;\n    void ApaSetToLiteral(int digits, DdApaNumber number, DdApaDigit literal)\n      const;\n    void ApaPowerOfTwo(int digits, DdApaNumber number, int power) const;\n    void ApaPrintHex(int digits, DdApaNumber number, FILE * fp = stdout) const;\n    void ApaPrintDecimal(int digits, DdApaNumber number, FILE * fp = stdout) const;\n    std::string ApaStringDecimal(int digits, DdApaNumber number) const;\n    void ApaPrintExponential(int digits, DdApaNumber number,\n                             int precision = 6, FILE * fp = stdout) const;\n    void DebugCheck(void) const;\n    void CheckKeys(void) const;\n    ADD Harwell(FILE * fp, std::vector<ADD>& x, std::vector<ADD>& y,\n                std::vector<ADD>& xn, std::vector<ADD>& yn_,\n                int * m, int * n, int bx = 0, int sx = 2, int by = 1,\n                int sy = 2, int pr = 0) const;\n    void PrintLinear(void) const;\n    int ReadLinear(int x, int y) const;\n    BDD Xgty(std::vector<BDD> z, std::vector<BDD> x, std::vector<BDD> y) const;\n    BDD Xeqy(std::vector<BDD> x, std::vector<BDD> y) const;\n    ADD Xeqy(std::vector<ADD> x, std::vector<ADD> y) const;\n    BDD Dxygtdxz(std::vector<BDD> x, std::vector<BDD> y,\n                 std::vector<BDD> z) const;\n    BDD Dxygtdyz(std::vector<BDD> x, std::vector<BDD> y,\n                 std::vector<BDD> z) const;\n    BDD Inequality(int c, std::vector<BDD> x, std::vector<BDD> y) const;\n    BDD Disequality(int c, std::vector<BDD> x, std::vector<BDD> y) const;\n    BDD Interval(std::vector<BDD> x, unsigned int lowerB,\n                 unsigned int upperB) const;\n    ADD Hamming(std::vector<ADD> xVars, std::vector<ADD> yVars) const;\n    ADD Read(FILE * fp, std::vector<ADD>& x, std::vector<ADD>& y, std::vector<ADD>& xn,\n             std::vector<ADD>& yn_, int * m, int * n, int bx = 0, int sx = 2,\n             int by = 1, int sy = 2) const;\n    BDD Read(FILE * fp, std::vector<BDD>& x, std::vector<BDD>& y,\n             int * m, int * n, int bx = 0, int sx = 2, int by = 1,\n             int sy = 2) const;\n    void ReduceHeap(Cudd_ReorderingType heuristic = CUDD_REORDER_SIFT,\n                    int minsize = 0) const;\n    void ShuffleHeap(int * permutation) const;\n    void SymmProfile(int lower, int upper) const;\n    unsigned int Prime(unsigned int pr) const;\n    void Reserve(int amount) const;\n    int SharingSize(DD* nodes, int n) const;\n    int SharingSize(const std::vector<BDD>& v) const;\n    BDD bddComputeCube(BDD * vars, int * phase, int n) const;\n    BDD computeCube(std::vector<BDD> const & vars) const;\n    ADD addComputeCube(ADD * vars, int * phase, int n) const;\n    ADD computeCube(std::vector<ADD> const & vars) const;\n    BDD IndicesToCube(int * array, int n) const;\n    void PrintVersion(FILE * fp) const;\n    double AverageDistance(void) const;\n    int32_t Random(void) const;\n    void Srandom(int32_t seed) const;\n    void zddPrintSubtable() const;\n    void zddReduceHeap(Cudd_ReorderingType heuristic = CUDD_REORDER_SIFT,\n                       int minsize = 0) const;\n    void zddShuffleHeap(int * permutation) const;\n    void zddSymmProfile(int lower, int upper) const;\n    void DumpDot(\n      const std::vector<BDD>& nodes, \n      char const * const * inames = 0, \n      char const * const * onames = 0, \n      FILE * fp = stdout) const;\n    void DumpDaVinci(\n      const std::vector<BDD>& nodes, \n      char const * const * inames = 0,\n      char const * const * onames = 0,\n      FILE * fp = stdout) const;\n    void DumpBlif(\n      const std::vector<BDD>& nodes, \n      char const * const * inames = 0,\n      char const * const * onames = 0,\n      char * mname = 0,\n      FILE * fp = stdout,\n      int mv = 0) const;\n    void DumpDDcal(\n      const std::vector<BDD>& nodes, \n      char const * const * inames = 0, \n      char const * const * onames = 0, \n      FILE * fp = stdout) const;\n    void DumpFactoredForm(\n      const std::vector<BDD>& nodes, \n      char const * const * inames = 0,\n      char const * const * onames = 0,\n      FILE * fp = stdout) const;\n    BDD VectorSupport(const std::vector<BDD>& roots) const;\n    std::vector<unsigned int> \n    SupportIndices(const std::vector<BDD>& roots) const;\n    std::vector<unsigned int> \n    SupportIndices(const std::vector<ADD>& roots) const;\n    int nodeCount(const std::vector<BDD>& roots) const;\n    int VectorSupportSize(const std::vector<BDD>& roots) const;\n    void DumpDot(\n      const std::vector<ADD>& nodes,\n      char const * const * inames = 0, \n      char const * const * onames = 0, \n      FILE * fp = stdout) const;\n    void DumpDaVinci(\n      const std::vector<ADD>& nodes,\n      char const * const * inames = 0,\n      char const * const * onames = 0,\n      FILE * fp = stdout) const;\n    BDD VectorSupport(const std::vector<ADD>& roots) const;\n    int VectorSupportSize(const std::vector<ADD>& roots) const;\n    void DumpDot(\n      const std::vector<ZDD>& nodes,\n      char const * const * inames = 0,\n      char const * const * onames = 0,\n      FILE * fp = stdout) const;\n    std::string OrderString(void) const;\n\n}; // Cudd\n\n\n#endif\n"
  },
  {
    "path": "cudd/cplusplus/multi.out",
    "content": "Report from thread 0 with 32 variables: 7598 nodes and 2147483648 minterms\nVariable order: x30 x0 x31 x29 x1 x28 x2 x27 x3 x26 x4 x25 x5 x6 x24 x23 x9 x21 x10 x22 x14 x15 x20 x19 x18 x17 x16 x13 x12 x11 x7 x8\nA random number from our generator: 751438031\nReport from thread 1 with 33 variables: 8333 nodes and 4294967296 minterms\nVariable order: x32 x0 x31 x1 x30 x2 x29 x3 x28 x4 x27 x5 x26 x6 x25 x7 x24 x23 x8 x9 x21 x15 x22 x10 x20 x11 x19 x18 x17 x16 x14 x13 x12\nA random number from our generator: 1059943320\nReport from thread 2 with 34 variables: 10253 nodes and 8589934592 minterms\nVariable order: x32 x0 x33 x31 x1 x30 x2 x29 x3 x28 x4 x27 x5 x26 x6 x25 x7 x8 x24 x23 x12 x16 x17 x15 x22 x21 x20 x19 x18 x14 x13 x11 x10 x9\nA random number from our generator: 1374140202\nReport from thread 3 with 35 variables: 12330 nodes and 17179869184 minterms\nVariable order: x33 x0 x34 x1 x32 x31 x2 x30 x3 x4 x29 x28 x5 x6 x27 x26 x7 x25 x8 x23 x12 x24 x16 x17 x13 x22 x21 x20 x19 x18 x15 x14 x11 x10 x9\nA random number from our generator: 1150759539\n"
  },
  {
    "path": "cudd/cplusplus/test.out",
    "content": "Entering testBdd\nf: 3 nodes 1 leaves 1 minterms\n11  1\n\ng: 3 nodes 1 leaves 3 minterms\n0-  1\n11  1\n\nf and g are not complementary\nf is less than or equal to g\ng: 2 nodes 1 leaves 2 minterms\n1-  1\n\nh: 2 nodes 1 leaves 2 minterms\n-1  1\n\nx + h has 3 nodes\nh: 3 nodes 1 leaves 3 minterms\n01  1\n1-  1\n\nEntering testAdd\nr: 6 nodes 3 leaves 3 minterms\n01  1\n10  1\n11  2\n\ns: 4 nodes 2 leaves 1 minterms\n11  3\n\ns: 1 nodes 1 leaves 4 minterms\n--  inf\n\np is less than or equal to r\nr: 4 nodes 2 leaves 3 minterms\n01  1\n1-  1\n\nEntering testAdd2\nf: 7 nodes 4 leaves 4 minterms\n00  0.1\n01  0.2\n10  0.3\n11  0.4\n\nl: 7 nodes 4 leaves 4 minterms\n00 -2.30259\n01 -1.60944\n10 -1.20397\n11 -0.916291\n\nr: 7 nodes 4 leaves 4 minterms\n00 -0.230259\n01 -0.321888\n10 -0.361192\n11 -0.366516\n\ne: 1 nodes 1 leaves 4 minterms\n--  1.84644\n\nEntering testZdd\ns: 3 nodes 3 minterms\n1- 1\n01 1\n\nv is less than s\ns: 1 nodes 1 minterms\n01 1\n\nEntering testBdd2\nf: 7 nodes 1 leaves 7 minterms\n01-1  1\n101-  1\n1101  1\n111-  1\n\nIrredundant cover of f:\n1-1- 1\n-1-1 1\n\nNumber of minterms (arbitrary precision): 7\nNumber of minterms (extended precision):  7.000000e+00\nTwo-literal clauses of f:\n x2 |  x3\n x1 |  x2\n x0 |  x3\n x0 |  x1\n\nvect[0]\n1--- 1\n\nvect[1]\n0--- 1\n-1-- 1\n\nvect[2]\n10-- 1\n--1- 1\n\nvect[3]\n0--- 1\n-10- 1\n---1 1\n\ndigraph \"DD\" {\nsize = \"7.5,10\"\ncenter = true;\nedge [dir = none];\n{ node [shape = plaintext];\n  edge [style = invis];\n  \"CONST NODES\" [style = invis];\n\" x0 \" -> \" x1 \" -> \" x2 \" -> \" x3 \" -> \"CONST NODES\"; \n}\n{ rank = same; node [shape = box]; edge [style = invis];\n\"  v0  \" -> \"  v1  \" -> \"  v2  \" -> \"  v3  \"; }\n{ rank = same; \" x0 \";\n\"0x1d\";\n\"0x5d\";\n\"0x5a\";\n\"0x19\";\n}\n{ rank = same; \" x1 \";\n\"0x59\";\n\"0x5c\";\n\"0x1a\";\n}\n{ rank = same; \" x2 \";\n\"0x4a\";\n\"0x5b\";\n}\n{ rank = same; \" x3 \";\n\"0x4b\";\n}\n{ rank = same; \"CONST NODES\";\n{ node [shape = box]; \"0x13\";\n}\n}\n\"  v0  \" -> \"0x19\" [style = solid];\n\"  v1  \" -> \"0x1d\" [style = solid];\n\"  v2  \" -> \"0x5a\" [style = solid];\n\"  v3  \" -> \"0x5d\" [style = solid];\n\"0x1d\" -> \"0x1a\";\n\"0x1d\" -> \"0x13\" [style = dashed];\n\"0x5d\" -> \"0x5c\";\n\"0x5d\" -> \"0x13\" [style = dashed];\n\"0x5a\" -> \"0x59\";\n\"0x5a\" -> \"0x4a\" [style = dashed];\n\"0x19\" -> \"0x13\";\n\"0x19\" -> \"0x13\" [style = dotted];\n\"0x59\" -> \"0x4a\";\n\"0x59\" -> \"0x13\" [style = dashed];\n\"0x5c\" -> \"0x5b\";\n\"0x5c\" -> \"0x4b\" [style = dashed];\n\"0x1a\" -> \"0x13\";\n\"0x1a\" -> \"0x13\" [style = dotted];\n\"0x4a\" -> \"0x13\";\n\"0x4a\" -> \"0x13\" [style = dotted];\n\"0x5b\" -> \"0x4b\";\n\"0x5b\" -> \"0x13\" [style = dashed];\n\"0x4b\" -> \"0x13\";\n\"0x4b\" -> \"0x13\" [style = dotted];\n\"0x13\" [label = \"1\"];\n}\nEntering testBdd3\nf: 10 nodes 1 leaves 50 minterms\n0-0-0-  1\n0-0-10  1\n0-100-  1\n0-1010  1\n0-11--  1\n10-00-  1\n10-010  1\n10-1--  1\n11000-  1\n110010  1\n1101--  1\n1110-1  1\n111101  1\n\nf1: 5 nodes 1 leaves 36 minterms\n0---0-  1\n0---10  1\n10--0-  1\n10--10  1\n\nf1 is less than or equal to f\ng: 6 nodes 1 leaves 62 minterms\n0-----  1\n10----  1\n110---  1\n1110--  1\n11110-  1\n\nh: 8 nodes 1 leaves 51 minterms\n0-0-0-  1\n0-0-10  1\n0-100-  1\n0-1010  1\n0-11--  1\n10-00-  1\n10-010  1\n10-1--  1\n11000-  1\n110010  1\n1101--  1\n111--1  1\n\ng * h == f\nEntering testZdd2\np[0]: 3 nodes 1 leaves 64 minterms\n----0-0  1\n----1-1  1\n\np[1]: 5 nodes 1 leaves 64 minterms\n--0-0-0  1\n--0-10-  1\n--1-0-1  1\n--1-11-  1\n\np[2]: 7 nodes 1 leaves 64 minterms\n0-0-0-0  1\n0-0-10-  1\n0-10---  1\n1-0-0-1  1\n1-0-11-  1\n1-11---  1\n\np[3]: 8 nodes 1 leaves 64 minterms\n0-0-0-1  1\n0-0-11-  1\n0-11---  1\n11-----  1\n\ndigraph \"DD\" {\nsize = \"7.5,10\"\ncenter = true;\nedge [dir = none];\n{ node [shape = plaintext];\n  edge [style = invis];\n  \"CONST NODES\" [style = invis];\n\" a2 \" -> \" b2 \" -> \" a1 \" -> \" b1 \" -> \" a0 \" -> \" b0 \" -> \" c0 \" -> \"CONST NODES\"; \n}\n{ rank = same; node [shape = box]; edge [style = invis];\n\"  s0  \" -> \"  s1  \" -> \"  s2  \" -> \"  c3  \"; }\n{ rank = same; \" a2 \";\n\"0x494\";\n\"0x493\";\n}\n{ rank = same; \" b2 \";\n\"0x41a\";\n}\n{ rank = same; \" a1 \";\n\"0x491\";\n\"0x492\";\n}\n{ rank = same; \" b1 \";\n\"0x44b\";\n}\n{ rank = same; \" a0 \";\n\"0x490\";\n\"0x48f\";\n}\n{ rank = same; \" b0 \";\n\"0x46a\";\n}\n{ rank = same; \" c0 \";\n\"0x48e\";\n}\n{ rank = same; \"CONST NODES\";\n{ node [shape = box]; \"0x413\";\n}\n}\n\"  s0  \" -> \"0x48f\" [style = solid];\n\"  s1  \" -> \"0x491\" [style = solid];\n\"  s2  \" -> \"0x493\" [style = solid];\n\"  c3  \" -> \"0x494\" [style = solid];\n\"0x494\" -> \"0x41a\";\n\"0x494\" -> \"0x492\" [style = dashed];\n\"0x493\" -> \"0x492\";\n\"0x493\" -> \"0x492\" [style = dotted];\n\"0x41a\" -> \"0x413\";\n\"0x41a\" -> \"0x413\" [style = dotted];\n\"0x491\" -> \"0x490\";\n\"0x491\" -> \"0x490\" [style = dotted];\n\"0x492\" -> \"0x44b\";\n\"0x492\" -> \"0x490\" [style = dashed];\n\"0x44b\" -> \"0x413\";\n\"0x44b\" -> \"0x413\" [style = dotted];\n\"0x490\" -> \"0x46a\";\n\"0x490\" -> \"0x48e\" [style = dashed];\n\"0x48f\" -> \"0x48e\";\n\"0x48f\" -> \"0x48e\" [style = dotted];\n\"0x46a\" -> \"0x413\";\n\"0x46a\" -> \"0x413\" [style = dotted];\n\"0x48e\" -> \"0x413\";\n\"0x48e\" -> \"0x413\" [style = dotted];\n\"0x413\" [label = \"1\"];\n}\nz[0]: 4 nodes 2 minterms\n00000000100010 1\n00000000010001 1\n\nz[1]: 10 nodes 4 minterms\n00001000101000 1\n00001000010010 1\n00000100100100 1\n00000100010001 1\n\nz[2]: 16 nodes 6 minterms\n10001010000000 1\n10000100101000 1\n10000100010010 1\n01001001000000 1\n01000100100100 1\n01000100010001 1\n\nz[3]: 10 nodes 4 minterms\n10100000000000 1\n01001010000000 1\n01000100101000 1\n01000100010010 1\n\nz[0]\n----1-1 1\n----0-0 1\nz[0]\n----0-0 1\n----1-1 1\nz[1]\n--1-11- 1\n--1-0-1 1\n--0-10- 1\n--0-0-0 1\nz[1]\n--0-0-0 1\n--0-10- 1\n--1-0-1 1\n--1-11- 1\nz[2]\n1-11--- 1\n1-0-11- 1\n1-0-0-1 1\n0-10--- 1\n0-0-10- 1\n0-0-0-0 1\nz[2]\n0-0-0-0 1\n0-0-10- 1\n0-10--- 1\n1-0-0-1 1\n1-0-11- 1\n1-11--- 1\nz[3]\n11----- 1\n0-11--- 1\n0-0-11- 1\n0-0-0-1 1\nz[3]\n0-0-0-1 1\n0-0-11- 1\n0-11--- 1\n11----- 1\ndigraph \"ZDD\" {\nsize = \"7.5,10\"\ncenter = true;\nedge [dir = none];\n{ node [shape = plaintext];\n  edge [style = invis];\n  \"CONST NODES\" [style = invis];\n\" a2+ \" -> \" a2- \" -> \" b2+ \" -> \" a1+ \" -> \" a1- \" -> \" b1+ \" -> \" b1- \" -> \" a0+ \" -> \" a0- \" -> \" b0+ \" -> \" b0- \" -> \" c0+ \" -> \" c0- \" -> \"CONST NODES\"; \n}\n{ rank = same; node [shape = box]; edge [style = invis];\n\"  s0  \" -> \"  s1  \" -> \"  s2  \" -> \"  c3  \"; }\n{ rank = same; \" a2+ \";\n\"0x56\";\n\"0x4d\";\n}\n{ rank = same; \" a2- \";\n\"0x54\";\n\"0x49\";\n}\n{ rank = same; \" b2+ \";\n\"0x50\";\n}\n{ rank = same; \" a1+ \";\n\"0x44\";\n\"0x36\";\n\"0x3d\";\n}\n{ rank = same; \" a1- \";\n\"0x34\";\n\"0x42\";\n}\n{ rank = same; \" b1+ \";\n\"0x3e\";\n}\n{ rank = same; \" b1- \";\n\"0x39\";\n}\n{ rank = same; \" a0+ \";\n\"0x2f\";\n\"0x21\";\n\"0x28\";\n}\n{ rank = same; \" a0- \";\n\"0x2d\";\n\"0x1f\";\n}\n{ rank = same; \" b0+ \";\n\"0x29\";\n}\n{ rank = same; \" b0- \";\n\"0x24\";\n}\n{ rank = same; \" c0+ \";\n\"0x18\";\n}\n{ rank = same; \" c0- \";\n\"0x17\";\n}\n{ rank = same; \"CONST NODES\";\n{ node [shape = box]; \"0x14\";\n\"0x13\";\n}\n}\n\"  s0  \" -> \"0x21\" [style = solid];\n\"  s1  \" -> \"0x36\" [style = solid];\n\"  s2  \" -> \"0x4d\" [style = solid];\n\"  c3  \" -> \"0x56\" [style = solid];\n\"0x56\" -> \"0x50\";\n\"0x56\" -> \"0x54\" [style = dashed];\n\"0x4d\" -> \"0x44\";\n\"0x4d\" -> \"0x49\" [style = dashed];\n\"0x54\" -> \"0x44\";\n\"0x54\" -> \"0x14\" [style = dashed];\n\"0x49\" -> \"0x3d\";\n\"0x49\" -> \"0x14\" [style = dashed];\n\"0x50\" -> \"0x13\";\n\"0x50\" -> \"0x14\" [style = dashed];\n\"0x44\" -> \"0x3e\";\n\"0x44\" -> \"0x42\" [style = dashed];\n\"0x36\" -> \"0x2f\";\n\"0x36\" -> \"0x34\" [style = dashed];\n\"0x3d\" -> \"0x39\";\n\"0x3d\" -> \"0x34\" [style = dashed];\n\"0x34\" -> \"0x28\";\n\"0x34\" -> \"0x14\" [style = dashed];\n\"0x42\" -> \"0x2f\";\n\"0x42\" -> \"0x14\" [style = dashed];\n\"0x3e\" -> \"0x13\";\n\"0x3e\" -> \"0x14\" [style = dashed];\n\"0x39\" -> \"0x13\";\n\"0x39\" -> \"0x14\" [style = dashed];\n\"0x2f\" -> \"0x29\";\n\"0x2f\" -> \"0x2d\" [style = dashed];\n\"0x21\" -> \"0x18\";\n\"0x21\" -> \"0x1f\" [style = dashed];\n\"0x28\" -> \"0x24\";\n\"0x28\" -> \"0x1f\" [style = dashed];\n\"0x2d\" -> \"0x18\";\n\"0x2d\" -> \"0x14\" [style = dashed];\n\"0x1f\" -> \"0x17\";\n\"0x1f\" -> \"0x14\" [style = dashed];\n\"0x29\" -> \"0x13\";\n\"0x29\" -> \"0x14\" [style = dashed];\n\"0x24\" -> \"0x13\";\n\"0x24\" -> \"0x14\" [style = dashed];\n\"0x18\" -> \"0x13\";\n\"0x18\" -> \"0x14\" [style = dashed];\n\"0x17\" -> \"0x13\";\n\"0x17\" -> \"0x14\" [style = dashed];\n\"0x14\" [label = \"0\"];\n\"0x13\" [label = \"1\"];\n}\nEntering testBdd4\nf: 5 nodes 1 leaves 3 minterms\n000-----------  1\n11------------  1\n\ng: 5 nodes 1 leaves 3 minterms\n000  1\n11-  1\n\nf and h are identical\nEntering testBdd5\ndigraph \"DD\" {\nsize = \"7.5,10\"\ncenter = true;\nedge [dir = none];\n{ node [shape = plaintext];\n  edge [style = invis];\n  \"CONST NODES\" [style = invis];\n\" a \" -> \" b \" -> \" c \" -> \" d \" -> \"CONST NODES\"; \n}\n{ rank = same; node [shape = box]; edge [style = invis];\n\"  lb  \" -> \"  ub  \" -> \"  f  \" -> \"  primes  \" -> \"  lprime  \"; }\n{ rank = same; \" a \";\n\"0x487\";\n}\n{ rank = same; \" b \";\n\"0x484\";\n\"0x486\";\n\"0x483\";\n\"0x488\";\n}\n{ rank = same; \" c \";\n\"0x481\";\n\"0x43b\";\n}\n{ rank = same; \" d \";\n\"0x44b\";\n}\n{ rank = same; \"CONST NODES\";\n{ node [shape = box]; \"0x413\";\n}\n}\n\"  lb  \" -> \"0x488\" [style = dotted];\n\"  ub  \" -> \"0x44b\" [style = solid];\n\"  f  \" -> \"0x487\" [style = solid];\n\"  primes  \" -> \"0x483\" [style = solid];\n\"  lprime  \" -> \"0x483\" [style = solid];\n\"0x487\" -> \"0x484\";\n\"0x487\" -> \"0x486\" [style = dashed];\n\"0x484\" -> \"0x44b\";\n\"0x484\" -> \"0x481\" [style = dotted];\n\"0x486\" -> \"0x43b\";\n\"0x486\" -> \"0x413\" [style = dotted];\n\"0x483\" -> \"0x44b\";\n\"0x483\" -> \"0x413\" [style = dotted];\n\"0x488\" -> \"0x481\";\n\"0x488\" -> \"0x413\" [style = dashed];\n\"0x481\" -> \"0x413\";\n\"0x481\" -> \"0x44b\" [style = dotted];\n\"0x43b\" -> \"0x44b\";\n\"0x43b\" -> \"0x413\" [style = dashed];\n\"0x44b\" -> \"0x413\";\n\"0x44b\" -> \"0x413\" [style = dotted];\n\"0x413\" [label = \"1\"];\n}\nprimes(1): 3 nodes 1 leaves 4 minterms\n-1-1----------  1\n\nprimes(2): is the zero DD\nprimes(3): 4 nodes 1 leaves 2 minterms\n1-01----------  1\n\nprimes(4): 6 nodes 1 leaves 5 minterms\n-1-1---------- 1\n010----------- 1\n\nprimes(5): 4 nodes 1 leaves 2 minterms\n01-1----------  1\n\nl1: 7 nodes 1 leaves 3 minterms\n0111----------  1\n111-----------  1\n\nu1: 4 nodes 1 leaves 8 minterms\n000-----------  1\n011-----------  1\n1-1-----------  1\n\ninterpolant1: 4 nodes 1 leaves 6 minterms\n011-----------  1\n1-1-----------  1\n\nl2: 7 nodes 1 leaves 5 minterms\n001-----------  1\n0110----------  1\n101-----------  1\n\nu2: 5 nodes 1 leaves 8 minterms\n-000----------  1\n-01-----------  1\n-110----------  1\n\ninterpolant2: 5 nodes 1 leaves 6 minterms\n-01-----------  1\n-110----------  1\n\nl3: 4 nodes 1 leaves 2 minterms\n00-1----------  1\n\nu3: 3 nodes 1 leaves 4 minterms\n-0-1----------  1\n\ninterpolant3: 3 nodes 1 leaves 4 minterms\n-0-1----------  1\n\nEntering testErrorHandling\nOops! Caught: empty DD.\nCaught: Invalid argument.\nf = var[1] | (var[2] & var[3])\nvar[0] | var[1] is not a cube\nCudd_Cofactor: Invalid restriction 2\nCaught: Invalid argument.\nf : 511 nodes 1 leaves 115422332637413376 minterms\ng : 511 nodes 1 leaves 115422332637413376 minterms\nh Caught: empty DD.\nf : 88 nodes 1 leaves 226007109 minterms\ng : 91 nodes 1 leaves 3143500301 minterms\nh : 142 nodes 1 leaves 2917493192 minterms\nCaught: Maximum memory exceeded.\nCaught: Timeout expired.  Lag = 29 ms.\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 0\nArc violation threshold: 0\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 4004\n**** CUDD non-modifiable parameters ****\nMemory in use: 146651968\nPeak number of nodes: 2044\nPeak number of live nodes: 2030\nNumber of BDD variables: 60\nNumber of ZDD variables: 14\nNumber of cache entries: 524288\nNumber of cache look-ups: 5326\nNumber of cache hits: 1226\nNumber of cache insertions: 4217\nNumber of cache collisions: 16\nNumber of cache deletions: 2300\nCache used slots = 0.39% (expected 0.39%)\nSoft limit for cache size: 76800\nNumber of buckets in unique table: 19200\nUsed buckets in unique table: 9.11% (expected 8.95%)\nNumber of BDD and ADD nodes: 3789\nNumber of ZDD nodes: 14\nNumber of dead BDD and ADD nodes: 3725\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 6011\nTotal number of nodes reclaimed: 154\nGarbage collections so far: 3\nTime for garbage collection: 0.00 sec\nReorderings so far: 0\nTime for reordering: 0.00 sec\n"
  },
  {
    "path": "cudd/cplusplus/test_obj.test.in",
    "content": "#! /bin/sh\n\nEXE=@EXEEXT@\nsrcdir=@srcdir@\n\nfile=test\nmfile=multi\nverbosity=2\nnthreads=4\n\nsed_command='-r:-e:s/0x[0-9a-f][0-9a-f]*//g:-e:s/dashed//:-e:s/dotted//:-e:s/[0-9][0-9]*.bytes//:-e:/[0-9][0-9]* ms//:-e:/modifiable/,$d'\n\necho TAP version 13\necho 1..2\nexitstatus=0\n# Create empty file.\n: > ./cplusplus/differences\n\ncplusplus/testobj$EXE $verbosity > ./cplusplus/${file}.tst 2>&1\nfailed=`expr $? != 0`\nif test x$failed = x0; then\n    echo \"# comparing ./cplusplus/${file}.tst to ${srcdir}/cplusplus/${file}.out\"\n    mkfifo ./cplusplus/tst_fifo ./cplusplus/out_fifo\n    OIFS=$IFS\n    IFS=:\n    `sed ${sed_command} ./cplusplus/${file}.tst > ./cplusplus/tst_fifo &\\\n     sed ${sed_command} ${srcdir}/cplusplus/${file}.out > ./cplusplus/out_fifo &\\\n     diff -b ./cplusplus/tst_fifo ./cplusplus/out_fifo >> ./cplusplus/differences`\n    failed=`expr $? != 0`\n    rm ./cplusplus/tst_fifo ./cplusplus/out_fifo\n    IFS=$OIFS\nfi\nif test x$failed = x0 ; then\n    echo \"ok 1 BDD ADD ZDD basic test\"\nelse\n    echo \"not ok 1 base\"\nfi\nexitstatus=`expr $exitstatus + $failed`\n\ncplusplus/testmulti$EXE $nthreads > ./cplusplus/${mfile}.tst 2>&1\nretval=$?\nfailed=`expr $retval != 0`\nif test x$failed = x0; then\n    echo \"# comparing ./cplusplus/${mfile}.tst to ${srcdir}/cplusplus/${mfile}.out\"\n    mkfifo ./cplusplus/tst_fifo ./cplusplus/out_fifo\n    OIFS=$IFS\n    IFS=:\n    `sed ${sed_command} ./cplusplus/${mfile}.tst > ./cplusplus/tst_fifo &\\\n     sed ${sed_command} ${srcdir}/cplusplus/${mfile}.out > ./cplusplus/out_fifo &\\\n     diff -b ./cplusplus/tst_fifo ./cplusplus/out_fifo >> ./cplusplus/differences`\n    failed=`expr $? != 0`\n    rm ./cplusplus/tst_fifo ./cplusplus/out_fifo\n    IFS=$OIFS\nfi\nif test x$failed = x0 ; then\n    echo \"ok 2 multi-threaded multiple managers\"\nelif test x$retval = x77 ; then\n    failed=0\n    echo \"ok 2 multiple managers #SKIP thread header broken\" \nelse\n    echo \"not ok $count 2 multiple managers\"\nfi\nexitstatus=`expr $exitstatus + $failed`\n\nif test x$exitstatus = x0; then\n    rm -rf ./cplusplus/differences\nelse\n    echo '# Check file \"./cplusplus/differences\"'\nfi\n\nexit 0\n"
  },
  {
    "path": "cudd/cplusplus/testmulti.cc",
    "content": "/**\n  @file\n\n  @ingroup cplusplus\n\n  @brief Test program for multiple managers (one per thread).\n\n  @details This program tests the ability to run different CUDD managers\n  in different threads.  Each thread builds the hidden weight bit function\n  for a certain number of variables and then reorders the variables.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"config.h\"\n#include \"cuddObj.hh\"\n#include <cstdlib>\n#include <iostream>\n#include <sstream>\n#if HAVE_WORKING_THREAD == 1\n#include <thread>\n\n/**\n * @brief Taks performed by each thread.\n */\nclass Task {\npublic:\n    /** Constructor. */\n    Task(int n, std::ostringstream & os) : n(n), os(os) {}\n    /** Builds the hidden weight bit function and reorders the variables. */\n    void operator()(void) {\n        Cudd mgr;\n        mgr.AutodynEnable();\n        int nvars = n + 32;\n        std::vector<BDD> vars;\n        for (int i = 0; i != nvars; ++i) {\n            vars.push_back(mgr.bddVar());\n        }\n        os << \"Report from thread \" << n << \" with \" << nvars << \" variables: \";\n        // The hidden weight bit function is built from a tally circuit and\n        // a multiplexer.  First the tally circuit...\n        std::vector<BDD> oldt;\n        oldt.push_back(mgr.bddOne());\n        std::vector<BDD> t;\n        for (int i = 1; i != nvars + 1; ++i) {\n            t.clear();\n            t.push_back(oldt.at(0) & !vars.at(i-1));\n            for (int j = 1; j != i; ++j) {\n                t.push_back(vars.at(i-1).Ite(oldt.at(j-1), oldt.at(j)));\n            }\n            t.push_back(oldt.at(i-1) & vars.at(i-1));\n            oldt = t;\n        }\n#if 0\n        // Diagnostic print.\n        for (int i = 0;  i != nvars + 1; ++i) {\n            os << \"t(\" << i << \") = \" << t.at(i).FactoredFormString()\n               << std::endl;\n        }\n#endif\n        // ...then the multiplexer.\n        BDD hwb = mgr.bddZero();\n        for (int i = 0; i != nvars; ++i) {\n            hwb |= t.at(i+1) & vars.at(i);\n        }\n        mgr.ReduceHeap(CUDD_REORDER_SIFT_CONVERGE);\n        \n        int nodes = hwb.nodeCount();\n        os << nodes << \" nodes and \";\n        int digits;\n        DdApaNumber apa_minterms = hwb.ApaCountMinterm(nvars, &digits);\n        os << mgr.ApaStringDecimal(digits, apa_minterms) << \" minterms\\n\";\n        free(apa_minterms);\n        os << \"Variable order: \" << mgr.OrderString() << \"\\n\";\n        mgr.Srandom(n+11);\n        os << \"A random number from our generator: \" << mgr.Random() << \"\\n\";\n#if 0\n        // Diagnostic prints.\n        hwb.summary(nvars);\n        os << hwb.FactoredFormString() << std::endl;\n#endif\n    }\nprivate:\n    int n;\n    std::ostringstream & os;\n};\n\n\n/**\n * @brief Class to join threads in RAII fashion.\n */\nclass joinThreads {\npublic:\n    explicit joinThreads(std::vector<std::thread>& t) : threads_(t) {}\n    /** It completes once all threads have been joined. */\n    ~joinThreads() {\n        for (std::vector<std::thread>::iterator it = threads_.begin();\n             it != threads_.end(); ++it)\n            if (it->joinable())\n                it->join();\n    }\n    joinThreads(joinThreads const &) = delete;\n    joinThreads& operator=(joinThreads const &) = delete;\nprivate:\n    std::vector<std::thread>& threads_; /**< vector of threads to be joined. */\n};\n#endif\n\n/**\n  @brief Main program for testmulti.\n*/\nint main(int argc, char **argv)\n{\n    int nthreads = 4; // default value\n\n    // If there's an argument, it's the number of threads.\n    if (argc == 2) {\n        int nread;\n        int retval = sscanf(argv[1], \"%d%n\", &nthreads, &nread);\n        if (retval != 1 || argv[1][nread]) {\n            std::cerr << \"The argument should be an integer.\" << std::endl;\n            return 1;\n        }\n    } else if (argc != 1) {\n        std::cerr << \"Either no arguments or one argument.\" << std::endl;\n        return 1;\n    }\n\n#if HAVE_WORKING_THREAD == 1\n    // Each thread has its own output stream, so that main can print thread\n    // reports without interleaving.  We can't use an std::vector here because\n    // old versions of g++ don't support move semantics (and streams can't\n    // be copied).  We can't use a variable-length array either because it's\n    // a g++ extension and clang++ rejects it.  Hence we use new/delete.\n    std::ostringstream *oss = new std::ostringstream[nthreads];\n\n    // Multi-threaded code in this block.\n    {\n        std::vector<std::thread> t;\n        joinThreads joiner(t); // threads are joined by its destructor\n        for (int n = 0; n != nthreads; ++n) {\n            t.push_back(std::thread(Task(n, oss[n])));\n        }\n    }\n\n    // Print the reports.\n    for (int n = 0; n != nthreads; ++n) {\n        std::cout << oss[n].str();\n    }\n\n    delete [] oss;\n\n    return 0;\n#else\n    return 77; // test skipped\n#endif\n}\n"
  },
  {
    "path": "cudd/cplusplus/testobj.cc",
    "content": "/**\n  @file\n\n  @ingroup cplusplus\n\n  @brief Test program for the C++ object-oriented encapsulation of CUDD.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"cuddObj.hh\"\n#include <math.h>\n#include <iostream>\n#include <sstream>\n#include <cassert>\n#include <stdexcept>\n\nusing namespace std;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void testBdd(Cudd& mgr, int verbosity);\nstatic void testAdd(Cudd& mgr, int verbosity);\nstatic void testAdd2(Cudd& mgr, int verbosity);\nstatic void testZdd(Cudd& mgr, int verbosity);\nstatic void testBdd2(Cudd& mgr, int verbosity);\nstatic void testBdd3(Cudd& mgr, int verbosity);\nstatic void testZdd2(Cudd& mgr, int verbosity);\nstatic void testBdd4(Cudd& mgr, int verbosity);\nstatic void testBdd5(Cudd& mgr, int verbosity);\nstatic void testInterpolation(Cudd& mgr, int verbosity);\nstatic void testErrorHandling(Cudd& mgr, int verbosity);\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Main program for testobj.\n*/\nint\nmain(int argc, char **argv)\n{\n    int verbosity = 0;\n\n    if (argc == 2) {\n        int cnt;\n        int retval = sscanf(argv[1], \"%d %n\", &verbosity, &cnt);\n        if (retval != 1 || argv[1][cnt])\n            return 1;\n    } else if (argc != 1) {\n        return 1;\n    }\n\n    Cudd mgr(0,2);\n    if (verbosity > 2) mgr.makeVerbose(); // trace constructors and destructors\n    testBdd(mgr,verbosity);\n    testAdd(mgr,verbosity);\n    testAdd2(mgr,verbosity);\n    testZdd(mgr,verbosity);\n    testBdd2(mgr,verbosity);\n    testBdd3(mgr,verbosity);\n    testZdd2(mgr,verbosity);\n    testBdd4(mgr,verbosity);\n    testBdd5(mgr,verbosity);\n    testInterpolation(mgr,verbosity);\n    testErrorHandling(mgr,verbosity);\n    if (verbosity) mgr.info();\n    return 0;\n\n} // main\n\n\n/**\n  @brief Test basic operators on BDDs.\n\n  @details The function returns void\n  because it relies on the error handling done by the interface. The\n  default error handler causes program termination.\n\n  @sideeffect Creates BDD variables in the manager.\n\n  @see testBdd2 testBdd3 testBdd4 testBdd5\n\n*/\nstatic void\ntestBdd(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testBdd\\n\";\n    // Create two new variables in the manager. If testBdd is called before\n    // any variable is created in mgr, then x gets index 0 and y gets index 1.\n    BDD x = mgr.bddVar();\n    BDD y = mgr.bddVar();\n\n    BDD f = x * y;\n    if (verbosity) cout << \"f\"; f.print(2,verbosity);\n\n    BDD g = y + !x;\n    if (verbosity) cout << \"g\"; g.print(2,verbosity);\n\n    if (verbosity) \n        cout << \"f and g are\" << (f == !g ? \"\" : \" not\") << \" complementary\\n\";\n    if (verbosity) \n        cout << \"f is\" << (f <= g ? \"\" : \" not\") << \" less than or equal to g\\n\";\n\n    g = f | ~g;\n    if (verbosity) cout << \"g\"; g.print(2,verbosity);\n\n    BDD h = f = y;\n    if (verbosity) cout << \"h\"; h.print(2,verbosity);\n\n    if (verbosity) cout << \"x + h has \" << (x+h).nodeCount() << \" nodes\\n\";\n\n    h += x;\n    if (verbosity) cout << \"h\"; h.print(2,verbosity);\n\n} // testBdd\n\n\n/**\n  @brief Test basic operators on ADDs.\n\n  @details The function returns void because it relies on the error\n  handling done by the interface. The default error handler causes\n  program termination.\n\n  @sideeffect May create ADD variables in the manager.\n\n  @see testAdd2\n\n*/\nstatic void\ntestAdd(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testAdd\\n\";\n    // Create two ADD variables. If we called method addVar without an\n    // argument, we would get two new indices. If testAdd is indeed called\n    // after testBdd, then those indices would be 2 and 3. By specifying the\n    // arguments, on the other hand, we avoid creating new unnecessary BDD\n    // variables.\n    ADD p = mgr.addVar(0);\n    ADD q = mgr.addVar(1);\n\n    // Test arithmetic operators.\n    ADD r = p + q;\n    if (verbosity) cout << \"r\"; r.print(2,verbosity);\n\n    // CUDD_VALUE_TYPE is double.\n    ADD s = mgr.constant(3.0);\n    s *= p * q;\n    if (verbosity) cout << \"s\"; s.print(2,verbosity);\n\n    s += mgr.plusInfinity();\n    if (verbosity) cout << \"s\"; s.print(2,verbosity);\n\n    // Test relational operators.\n    if (verbosity) \n        cout << \"p is\" << (p <= r ? \"\" : \" not\") << \" less than or equal to r\\n\";\n\n    // Test logical operators.\n    r = p | q;\n    if (verbosity) cout << \"r\"; r.print(2,verbosity);\n\n} // testAdd\n\n\n/**\n  @brief Test some more operators on ADDs.\n\n  @details The function returns void because it relies on the error\n  handling done by the interface. The default error handler causes\n  program termination.\n\n  @sideeffect May create ADD variables in the manager.\n\n  @see testAdd\n\n*/\nstatic void\ntestAdd2(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testAdd2\\n\";\n    // Create two ADD variables. If we called method addVar without an\n    // argument, we would get two new indices.\n    vector<ADD> x(2);\n    for (size_t i = 0; i < 2; ++i) {\n      x[i] = mgr.addVar((int) i);\n    }\n\n    // Build a probability density function: [0.1, 0.2, 0.3, 0.4].\n    ADD f0 = x[1].Ite(mgr.constant(0.2), mgr.constant(0.1));\n    ADD f1 = x[1].Ite(mgr.constant(0.4), mgr.constant(0.3));\n    ADD f  = x[0].Ite(f1, f0);\n    if (verbosity) cout << \"f\"; f.print(2,verbosity);\n\n    // Compute the entropy.\n    ADD l = f.Log();\n    if (verbosity) cout << \"l\"; l.print(2,verbosity);\n    ADD r = f * l;\n    if (verbosity) cout << \"r\"; r.print(2,verbosity);\n\n    ADD e = r.MatrixMultiply(mgr.constant(-1.0/log(2.0)),x);\n    if (verbosity) cout << \"e\"; e.print(2,verbosity);\n\n} // testAdd2\n\n\n/**\n  @brief Test basic operators on ZDDs.\n\n  @details The function returns void because it relies on the error\n  handling done by the interface. The default error handler causes\n  program termination.\n\n  @sideeffect May create ZDD variables in the manager.\n\n  @see testZdd2\n\n*/\nstatic void\ntestZdd(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testZdd\\n\";\n    ZDD v = mgr.zddVar(0);\n    ZDD w = mgr.zddVar(1);\n\n    ZDD s = v + w;\n    if (verbosity) cout << \"s\"; s.print(2,verbosity);\n\n    if (verbosity) cout << \"v is\" << (v < s ? \"\" : \" not\") << \" less than s\\n\";\n\n    s -= v;\n    if (verbosity) cout << \"s\"; s.print(2,verbosity);\n\n} // testZdd\n\n\n/**\n  @brief Test vector operators on BDDs.\n\n  @details The function returns void because it relies on the error\n  handling done by the interface. The default error handler causes\n  program termination.\n\n  @sideeffect May create BDD variables in the manager.\n\n  @see testBdd testBdd3 testBdd4 testBdd5\n\n*/\nstatic void\ntestBdd2(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testBdd2\\n\";\n    vector<BDD> x(4);\n    for (size_t i = 0; i < 4; ++i) {\n      x[i] = mgr.bddVar((int) i);\n    }\n\n    // Create the BDD for the Achilles' Heel function.\n    BDD p1 = x[0] * x[2];\n    BDD p2 = x[1] * x[3];\n    BDD f = p1 + p2;\n    const char* inames[] = {\"x0\", \"x1\", \"x2\", \"x3\"};\n    if (verbosity) {\n        cout << \"f\"; f.print(4,verbosity);\n        cout << \"Irredundant cover of f:\" << endl; f.PrintCover();\n        cout << \"Number of minterms (arbitrary precision): \"; f.ApaPrintMinterm(4);\n        cout << \"Number of minterms (extended precision):  \"; f.EpdPrintMinterm(4);\n        cout << \"Two-literal clauses of f:\" << endl;\n        f.PrintTwoLiteralClauses((char **)inames); cout << endl;\n    }\n\n    vector<BDD> vect = f.CharToVect();\n    if (verbosity) {\n        for (size_t i = 0; i < vect.size(); i++) {\n            cout << \"vect[\" << i << \"]\" << endl; vect[i].PrintCover();\n        }\n    }\n\n    // v0,...,v3 suffice if testBdd2 is called before testBdd3.\n    if (verbosity) {\n        const char* onames[] = {\"v0\", \"v1\", \"v2\", \"v3\", \"v4\", \"v5\"};\n        mgr.DumpDot(vect, (char **)inames,(char **)onames);\n    }\n\n} // testBdd2\n\n\n/**\n  @brief Test additional operators on BDDs.\n\n  @details The function returns void because it relies on the error\n  handling done by the interface. The default error handler causes\n  program termination.\n\n  @sideeffect May create BDD variables in the manager.\n\n  @see testBdd testBdd2 testBdd4 testBdd5\n\n*/\nstatic void\ntestBdd3(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testBdd3\\n\";\n    vector<BDD> x(6);\n    for (size_t i = 0; i < 6; ++i) {\n      x[i] = mgr.bddVar((int) i);\n    }\n\n    BDD G = x[4] + !x[5];\n    BDD H = x[4] * x[5];\n    BDD E = x[3].Ite(G,!x[5]);\n    BDD F = x[3] + !H;\n    BDD D = x[2].Ite(F,!H);\n    BDD C = x[2].Ite(E,!F);\n    BDD B = x[1].Ite(C,!F);\n    BDD A = x[0].Ite(B,!D);\n    BDD f = !A;\n    if (verbosity) cout << \"f\"; f.print(6,verbosity);\n\n    BDD f1 = f.RemapUnderApprox(6);\n    if (verbosity) cout << \"f1\"; f1.print(6,verbosity);\n    if (verbosity) \n        cout << \"f1 is\" << (f1 <= f ? \"\" : \" not\") << \" less than or equal to f\\n\";\n\n    BDD g;\n    BDD h;\n    f.GenConjDecomp(&g,&h);\n    if (verbosity) {\n        cout << \"g\"; g.print(6,verbosity);\n        cout << \"h\"; h.print(6,verbosity);\n        cout << \"g * h \" << (g * h == f ? \"==\" : \"!=\") << \" f\\n\";\n    }\n\n} // testBdd3\n\n\n/**\n  @brief Test cover manipulation with BDDs and ZDDs.\n\n  @details The function returns void because it relies on the error\n  handling done by the interface.  The default error handler causes\n  program termination.  This function builds the BDDs for a\n  transformed adder: one in which the inputs are transformations of\n  the original inputs. It then creates ZDDs for the covers from the\n  BDDs.\n\n  @sideeffect May create BDD and ZDD variables in the manager.\n\n  @see testZdd\n\n*/\nstatic void\ntestZdd2(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testZdd2\\n\";\n    size_t N = 3;\t\t\t// number of bits\n    // Create variables.\n    vector<BDD> a(N);\n    vector<BDD> b(N);\n    vector<BDD> c(N+1);\n    for (size_t i = 0; i < N; ++i) {\n      a[N-1-i] = mgr.bddVar(2*(int)i);\n      b[N-1-i] = mgr.bddVar(2*(int)i+1);\n    }\n    c[0] = mgr.bddVar(2*(int)N);\n    // Build functions.\n    vector<BDD> s(N);\n    for (size_t i = 0; i < N; ++i) {\n\ts[i] = a[i].Xnor(c[i]);\n\tc[i+1] = a[i].Ite(b[i],c[i]);\n    }\n\n    // Create array of outputs and print it.\n    vector<BDD> p(N+1);\n    for (size_t i = 0; i < N; ++i) {\n\tp[i] = s[i];\n    }\n    p[N] = c[N];\n    if (verbosity) {\n        for (size_t i = 0; i < p.size(); ++i) {\n          cout << \"p[\" << i << \"]\"; p[i].print(2*(int)N+1,verbosity);\n        }\n    }\n    const char* onames[] = {\"s0\", \"s1\", \"s2\", \"c3\"};\n    if (verbosity) {\n        const char* inames[] = {\"a2\", \"b2\", \"a1\", \"b1\", \"a0\", \"b0\", \"c0\"};\n        mgr.DumpDot(p, (char **)inames,(char **)onames);\n    }\n\n    // Create ZDD variables and build ZDD covers from BDDs.\n    mgr.zddVarsFromBddVars(2);\n    vector<ZDD> z(N+1);\n    for (size_t i = 0; i < N+1; ++i) {\n\tZDD temp;\n\tBDD dummy = p[i].zddIsop(p[i],&temp);\n\tz[i] = temp;\n    }\n\n    // Print out covers.\n    if (verbosity) {\n        DdGen *gen;\n        int *path;\n        for (size_t i = 0; i < z.size(); i++) {\n          cout << \"z[\" << i << \"]\"; z[i].print(4*(int)N+2,verbosity);\n        }\n        // Print cover in two different ways: with PrintCover and with\n        // enumeration over the paths.  The only difference should be\n        // a reversal in the order of the cubes.\n        for (size_t i = 0; i < z.size(); i++) {\n            cout << \"z[\" << i << \"]\\n\"; z[i].PrintCover();\n            cout << \"z[\" << i << \"]\\n\";\n            DdNode *f = Cudd_Not(z[i].getNode());\n            Cudd_zddForeachPath(z[i].manager(), f, gen, path) {\n                for (size_t q = 0; q < 4*N+2; q += 2) {\n                    int v = path[q] * 4 + path[q+1];\n                    switch (v) {\n                    case 0:\n                    case 2:\n                    case 8:\n                    case 10:\n                        cout << \"-\";\n                        break;\n                    case 1:\n                    case 9:\n                        cout << \"0\";\n                        break;\n                    case 6:\n                        cout << \"1\";\n                        break;\n                    default:\n                        cout << \"?\";\n                    }\n                }\n                cout << \" 1\\n\";\n            }\n        }\n        const char* znames[] = {\"a2+\", \"a2-\", \"b2+\", \"b2-\", \"a1+\", \"a1-\", \"b1+\",\n                                \"b1-\", \"a0+\", \"a0-\", \"b0+\", \"b0-\", \"c0+\", \"c0-\"};\n        mgr.DumpDot(z, (char **)znames,(char **)onames);\n    }\n\n} // testZdd2\n\n\n/**\n  @brief Test transfer between BDD managers.\n\n  @details The function returns void because it relies on the error\n  handling done by the interface.  The default error handler causes\n  program termination.\n\n  @sideeffect May create BDD variables in the manager.\n\n  @see testBdd testBdd2 testBdd3 testBdd5\n\n*/\nstatic void\ntestBdd4(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testBdd4\\n\";\n    BDD x = mgr.bddVar(0);\n    BDD y = mgr.bddVar(1);\n    BDD z = mgr.bddVar(2);\n\n    BDD f = (~x & ~y & ~z) | (x & y);\n    if (verbosity) cout << \"f\"; f.print(3,verbosity);\n\n    Cudd otherMgr(0,0);\n    BDD g = f.Transfer(otherMgr);\n    if (verbosity) cout << \"g\"; g.print(3,verbosity);\n\n    BDD h = g.Transfer(mgr);\n    if (verbosity) \n        cout << \"f and h are\" << (f == h ? \"\" : \" not\") << \" identical\\n\";\n\n} // testBdd4\n\n\n/**\n  @brief Test maximal expansion of cubes.\n\n  @details The function returns void because it relies on the error\n  handling done by the interface.  The default error handler causes\n  program termination.\n\n  @sideeffect May create BDD variables in the manager.\n\n  @see testBdd testBdd2 testBdd3 testBdd4\n\n*/\nstatic void\ntestBdd5(\n  Cudd& mgr,\n  int verbosity)\n{\n    if (verbosity) cout << \"Entering testBdd5\\n\";\n    vector<BDD> x;\n    x.reserve(4);\n    for (int i = 0; i < 4; i++) {\n\tx.push_back(mgr.bddVar(i));\n    }\n    const char* inames[] = {\"a\", \"b\", \"c\", \"d\"};\n    BDD f = (x[1] & x[3]) | (x[0] & ~x[2] & x[3]) | (~x[0] & x[1] & ~x[2]);\n    BDD lb = x[1] & ~x[2] & x[3];\n    BDD ub = x[3];\n    BDD primes = lb.MaximallyExpand(ub,f);\n    assert(primes == (x[1] & x[3]));\n    BDD lprime = primes.LargestPrimeUnate(lb);\n    assert(lprime == primes);\n    if (verbosity) {\n      const char * onames[] = {\"lb\", \"ub\", \"f\", \"primes\", \"lprime\"};\n        vector<BDD> z;\n        z.reserve(5);\n        z.push_back(lb);\n        z.push_back(ub);\n        z.push_back(f);\n        z.push_back(primes);\n        z.push_back(lprime);\n        mgr.DumpDot(z, (char **)inames, (char **)onames);\n        cout << \"primes(1)\"; primes.print(4,verbosity);\n    }\n\n    lb = ~x[0] & x[2] & x[3];\n    primes = lb.MaximallyExpand(ub,f);\n    assert(primes == mgr.bddZero());\n    if (verbosity) {\n        cout << \"primes(2)\"; primes.print(4,verbosity);\n    }\n\n    lb = x[0] & ~x[2] & x[3];\n    primes = lb.MaximallyExpand(ub,f);\n    assert(primes == lb);\n    lprime = primes.LargestPrimeUnate(lb);\n    assert(lprime == primes);\n    if (verbosity) {\n        cout << \"primes(3)\"; primes.print(4,verbosity);\n    }\n\n    lb = ~x[0] & x[1] & ~x[2] & x[3];\n    ub = mgr.bddOne();\n    primes = lb.MaximallyExpand(ub,f);\n    assert(primes == ((x[1] & x[3]) | (~x[0] & x[1] & ~x[2])));\n    lprime = primes.LargestPrimeUnate(lb);\n    assert(lprime == (x[1] & x[3]));\n    if (verbosity) {\n        cout << \"primes(4)\"; primes.print(4,1); primes.PrintCover();\n    }\n\n    ub = ~x[0] & x[3];\n    primes = lb.MaximallyExpand(ub,f);\n    assert(primes == (~x[0] & x[1] & x[3]));\n    lprime = primes.LargestPrimeUnate(lb);\n    assert(lprime == primes);\n    if (verbosity) {\n        cout << \"primes(5)\"; primes.print(4,verbosity);\n    }\n\n} // testBdd5\n\n\n/**\n  @brief Test BDD interpolation.\n*/\nstatic void\ntestInterpolation(\n  Cudd& mgr,\n  int verbosity)\n{\n    BDD a = mgr.bddVar(0);\n    BDD b = mgr.bddVar(1);\n    BDD c = mgr.bddVar(2);\n    BDD d = mgr.bddVar(3);\n\n    BDD l1 = (a | d) & b & c;\n    BDD u1 = (~a & ~b & ~c) | ((a | b) & c);\n    BDD ip1 = l1.Interpolate(u1);\n    if (verbosity) {\n        cout << \"l1\"; l1.print(4,verbosity);\n        cout << \"u1\"; u1.print(4,verbosity);\n        cout << \"interpolant1\"; ip1.print(4,verbosity);\n    }\n\n    BDD l2 = (~a | ~b) & (a | c) & (b | c) & (a | ~b | ~d);\n    BDD u2 = (~b & ~d) | (~b & c & d) | (b & c & ~d);\n    BDD ip2 = l2.Interpolate(u2);\n    if (verbosity) {\n        cout << \"l2\"; l2.print(4,verbosity);\n        cout << \"u2\"; u2.print(4,verbosity);\n        cout << \"interpolant2\"; ip2.print(4,verbosity);\n    }\n\n    BDD l3 = ~a & ~b & d;\n    BDD u3 = ~b & d;\n    BDD ip3 = l3.Interpolate(u3);\n    if (verbosity) {\n        cout << \"l3\"; l3.print(4,verbosity);\n        cout << \"u3\"; u3.print(4,verbosity);\n        cout << \"interpolant3\"; ip3.print(4,verbosity);\n    }\n\n} // testInterpolation\n\n\n/**\n  @brief Basic test of error handling.\n\n  @details This function also illustrates the use of the overloading of the\n  stream insertion operator (operator<<) for BDDs.\n*/\nstatic void\ntestErrorHandling(\n  Cudd& mgr,\n  int verbosity)\n{\n    // Setup.\n\n    if (verbosity) cout << \"Entering testErrorHandling\\n\";\n\n    FILE *savefp = 0;\n    if (verbosity == 0) {\n        // Suppress error messages coming from CUDD.\n        savefp = mgr.ReadStderr();\n#ifndef _WIN32\n        FILE * devnull = fopen(\"/dev/null\", \"w\");\n#else\n        FILE * devnull = fopen(\"NUL\", \"w\");\n#endif\n        if (devnull)\n            mgr.SetStderr(devnull);\n    }\n\n    size_t const N = 60;\n    vector<BDD> vars;\n    vars.reserve(N);\n    for (size_t i = 0; i < N; ++i) {\n        vars.push_back(mgr.bddVar((int) i));\n    }\n\n    // It is necessary to give names to all the BDD variables in the manager\n    // for the names to be used by operator<<.\n    for (int i = 0; i < mgr.ReadSize(); ++i) {\n        ostringstream os;\n        os << \"var[\" << i << \"]\";\n        mgr.pushVariableName(os.str());\n    }\n\n    // Tests.\n\n    // Trying to print the expression of an empty BDD.\n    try {\n        BDD empty;\n        if (verbosity > 0)\n            cout << \"Oops! \";\n        cout << empty << endl;\n    } catch (logic_error const & e) {\n        if (verbosity > 0)\n            cerr << \"Caught: \" << e.what() << endl;\n    }\n\n    // Trying to extract a minterm from the zero BDD.\n    try {\n        BDD zero = mgr.bddZero();\n        BDD minterm = zero.PickOneMinterm(vars);\n    } catch (logic_error const & e) {\n        if (verbosity > 0)\n            cerr << \"Caught: \" << e.what() << endl;\n        mgr.ClearErrorCode();\n    }\n\n    // Passing a non-cube second argument to Cofactor.\n    try {\n        BDD f = vars.at(1) | (vars.at(2) & vars.at(3));\n        if (verbosity > 0)\n            cout << \"f = \" << f << endl;\n        BDD notAcube = vars.at(0) | vars.at(1);\n        if (verbosity > 0)\n            cout << notAcube << \" is not a cube\" << endl;\n        BDD fc = f.Cofactor(notAcube);\n        if (verbosity > 0) {\n            cout << \"The cofactor is: \"; fc.summary(3);\n        }\n    } catch (logic_error const & e) {\n        if (verbosity > 0)\n            cerr << \"Caught: \" << e.what() << endl;\n        mgr.ClearErrorCode();\n    }\n\n#if 0\n    // This attempt to allocate over 100 GB may succeed on machines with\n    // enough memory; hence we exclude it from \"make check.\"\n    // Failing malloc.\n    // Don't let the memory manager kill the program if malloc fails.\n    DD_OOMFP saveHandler = mgr.InstallOutOfMemoryHandler(Cudd_OutOfMemSilent);\n    try {\n        mgr.Reserve(2000000000);\n    } catch (logic_error const & e) {\n        if (verbosity > 0)\n            cerr << \"Caught: \" << e.what() << endl;\n        mgr.ClearErrorCode();\n    }\n    (void) mgr.InstallOutOfMemoryHandler(saveHandler);\n#endif\n\n    // Forgetting to check for empty result when setting a limit on\n    // the number of new nodes.\n    try {\n        BDD f = mgr.bddOne();\n        BDD g = f;\n        for (size_t i = 0; i < N/2; i += 4) {\n            f &= vars.at(i) | vars.at(i+N/2);\n            g &= vars.at(i+1) | vars.at(i+N/2+1);\n        }\n        if (verbosity > 0) {\n            cout << \"f \"; f.summary(N);\n            cout << \"g \"; g.summary(N);\n        }\n        BDD h = f.And(g, /* max new nodes */ 1);\n        if (verbosity > 0) {\n            cout << \"h \"; h.summary(N);\n        }\n    } catch (logic_error const & e) {\n        if (verbosity > 0)\n            cerr << \"Caught: \" << e.what() << endl;\n        mgr.ClearErrorCode();\n    }\n\n    // Using more memory than the set limit.\n    size_t saveLimit = mgr.SetMaxMemory((size_t) 1);\n    try {\n        // The limit is ridiculously low (1 byte), but CUDD is resourceful.\n        // Therefore we can still create a few BDDs.\n        BDD f = mgr.Interval(vars, 122346345U, 348353453U);\n        if (verbosity > 0) {\n            cout << \"f \"; f.summary(N);\n        }\n        BDD g = mgr.Interval(vars, 34234U, 3143534534U);\n        if (verbosity > 0) {\n            cout << \"g \"; g.summary(N);\n        }\n        BDD h = f ^ g;\n        if (verbosity > 0) {\n            cout << \"h \"; h.summary(N);\n        }\n        // But if we really insist...\n        BDD extra = mgr.bddVar(60000);\n        // Here we would have to fix the variable names.\n    } catch (logic_error const & e) {\n        if (verbosity > 0)\n            cerr << \"Caught: \" << e.what() << endl;\n        mgr.ClearErrorCode();\n    }\n    (void) mgr.SetMaxMemory(saveLimit);\n\n    // Timing out.\n    unsigned long saveTl = mgr.SetTimeLimit(1UL); // 1 ms\n    try {\n        BDD f = mgr.bddOne();\n        for (size_t i = 0; i < N/2; ++i) {\n            f &= vars.at(i) | vars.at(i+N/2);\n        }\n    } catch (logic_error const & e) {\n        if (verbosity > 0)\n            cerr << \"Caught: \" << e.what() << endl;\n        mgr.ClearErrorCode();\n    }\n    (void) mgr.SetTimeLimit(saveTl);\n\n    // Let's clean up after ourselves.\n    mgr.clearVariableNames();\n    if (verbosity == 0) {\n        mgr.SetStderr(savefp);\n    }\n\n} // testErrorHandling\n"
  },
  {
    "path": "cudd/cudd/Included.am",
    "content": "lib_LTLIBRARIES = cudd/libcudd.la\ncudd_libcudd_la_SOURCES = cudd/cudd.h cudd/cuddInt.h \\\n  cudd/cuddAddAbs.c cudd/cuddAddApply.c cudd/cuddAddFind.c cudd/cuddAddInv.c \\\n  cudd/cuddAddIte.c cudd/cuddAddNeg.c cudd/cuddAddWalsh.c cudd/cuddAndAbs.c \\\n  cudd/cuddAnneal.c cudd/cuddApa.c cudd/cuddAPI.c cudd/cuddApprox.c \\\n  cudd/cuddBddAbs.c cudd/cuddBddCorr.c cudd/cuddBddIte.c cudd/cuddBridge.c \\\n  cudd/cuddCache.c cudd/cuddCheck.c cudd/cuddClip.c cudd/cuddCof.c \\\n  cudd/cuddCompose.c cudd/cuddDecomp.c cudd/cuddEssent.c cudd/cuddExact.c \\\n  cudd/cuddExport.c cudd/cuddGenCof.c cudd/cuddGenetic.c cudd/cuddGroup.c \\\n  cudd/cuddHarwell.c cudd/cuddInit.c cudd/cuddInteract.c cudd/cuddLCache.c \\\n  cudd/cuddLevelQ.c cudd/cuddLinear.c cudd/cuddLiteral.c cudd/cuddMatMult.c \\\n  cudd/cuddPriority.c cudd/cuddRead.c cudd/cuddRef.c cudd/cuddReorder.c \\\n  cudd/cuddSat.c cudd/cuddSign.c cudd/cuddSolve.c cudd/cuddSplit.c \\\n  cudd/cuddSubsetHB.c cudd/cuddSubsetSP.c cudd/cuddSymmetry.c cudd/cuddTable.c \\\n  cudd/cuddUtil.c cudd/cuddWindow.c cudd/cuddZddCount.c cudd/cuddZddFuncs.c \\\n  cudd/cuddZddGroup.c cudd/cuddZddIsop.c cudd/cuddZddLin.c cudd/cuddZddMisc.c \\\n  cudd/cuddZddPort.c cudd/cuddZddReord.c cudd/cuddZddSetop.c \\\n  cudd/cuddZddSymm.c cudd/cuddZddUtil.c\ncudd_libcudd_la_CPPFLAGS = -I$(top_srcdir)/cudd -I$(top_srcdir)/st \\\n  -I$(top_srcdir)/epd -I$(top_srcdir)/mtr -I$(top_srcdir)/util\nif OBJ\ncudd_libcudd_la_LIBTOOLFLAGS=--tag=CXX\nendif OBJ\ncudd_libcudd_la_LDFLAGS = -release @PACKAGE_VERSION@ -version-info 0:0:0 \\\n  -no-undefined\n\ncheck_PROGRAMS += cudd/testcudd cudd/testextra\ncudd_testcudd_SOURCES = cudd/testcudd.c\ncudd_testcudd_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\ncudd_testcudd_LDADD = cudd/libcudd.la\ncudd_testextra_SOURCES = cudd/testextra.c\ncudd_testextra_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\ncudd_testextra_LDADD = cudd/libcudd.la\n\ncheck_SCRIPTS += cudd/test_cudd.test\nEXTRA_DIST += cudd/test_cudd.test.in\ndist_check_DATA += cudd/r7x8.1.mat cudd/r7x8.1.out cudd/extra.out\nif !CROSS_COMPILING\nTESTS += cudd/test_cudd.test\nendif !CROSS_COMPILING\n\ncudd/test_cudd.test: cudd/test_cudd.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\nCLEANFILES += cudd/r7x8.1.tst cudd/extra.tst\n"
  },
  {
    "path": "cudd/cudd/cudd.h",
    "content": "/**\n  @file \n\n  @ingroup cudd\n\n  @brief The University of Colorado decision diagram package.\n\n  @details External functions and data strucures of the CUDD package.\n  <ul>\n  <li> To turn on the gathering of statistics, define DD_STATS.\n  <li> To turn on additional debugging code, define DD_DEBUG.\n  </ul>\n\n  @author Fabio Somenzi\n  @author Modified by Abelardo Pardo to interface it to VIS\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef CUDD_H_\n#define CUDD_H_\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n\n#include <inttypes.h>\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define CUDD_TRUE 1 /**< readable true */\n#define CUDD_FALSE 0 /**< readable false */\n\n/**\n * @brief Value returned my many functions when memory is exhausted.\n */\n#define CUDD_OUT_OF_MEM\t\t-1\n/* The sizes of the subtables and the cache must be powers of two. */\n#define CUDD_UNIQUE_SLOTS\t256\t/**< Initial size of subtables */\n#define CUDD_CACHE_SLOTS\t262144\t/**< Default size of the cache */\n\n/* Constants for residue functions. */\n#define CUDD_RESIDUE_DEFAULT\t0\n#define CUDD_RESIDUE_MSB\t1\n#define CUDD_RESIDUE_TC\t\t2\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Type of reordering algorithm.\n*/\ntypedef enum {\n    CUDD_REORDER_SAME,\n    CUDD_REORDER_NONE,\n    CUDD_REORDER_RANDOM,\n    CUDD_REORDER_RANDOM_PIVOT,\n    CUDD_REORDER_SIFT,\n    CUDD_REORDER_SIFT_CONVERGE,\n    CUDD_REORDER_SYMM_SIFT,\n    CUDD_REORDER_SYMM_SIFT_CONV,\n    CUDD_REORDER_WINDOW2,\n    CUDD_REORDER_WINDOW3,\n    CUDD_REORDER_WINDOW4,\n    CUDD_REORDER_WINDOW2_CONV,\n    CUDD_REORDER_WINDOW3_CONV,\n    CUDD_REORDER_WINDOW4_CONV,\n    CUDD_REORDER_GROUP_SIFT,\n    CUDD_REORDER_GROUP_SIFT_CONV,\n    CUDD_REORDER_ANNEALING,\n    CUDD_REORDER_GENETIC,\n    CUDD_REORDER_LINEAR,\n    CUDD_REORDER_LINEAR_CONVERGE,\n    CUDD_REORDER_LAZY_SIFT,\n    CUDD_REORDER_EXACT\n} Cudd_ReorderingType;\n\n\n/**\n  @brief Type of aggregation methods.\n*/\ntypedef enum {\n    CUDD_NO_CHECK,\n    CUDD_GROUP_CHECK,\n    CUDD_GROUP_CHECK2,\n    CUDD_GROUP_CHECK3,\n    CUDD_GROUP_CHECK4,\n    CUDD_GROUP_CHECK5,\n    CUDD_GROUP_CHECK6,\n    CUDD_GROUP_CHECK7,\n    CUDD_GROUP_CHECK8,\n    CUDD_GROUP_CHECK9\n} Cudd_AggregationType;\n\n\n/**\n  @brief Type of hooks.\n*/\ntypedef enum {\n    CUDD_PRE_GC_HOOK,\n    CUDD_POST_GC_HOOK,\n    CUDD_PRE_REORDERING_HOOK,\n    CUDD_POST_REORDERING_HOOK\n} Cudd_HookType;\n\n\n/**\n  @brief Type of error codes.\n*/\ntypedef enum {\n    CUDD_NO_ERROR,\n    CUDD_MEMORY_OUT,\n    CUDD_TOO_MANY_NODES,\n    CUDD_MAX_MEM_EXCEEDED,\n    CUDD_TIMEOUT_EXPIRED,\n    CUDD_TERMINATION,\n    CUDD_INVALID_ARG,\n    CUDD_INTERNAL_ERROR\n} Cudd_ErrorType;\n\n\n/**\n  @brief Group type for lazy sifting.\n*/\ntypedef enum {\n    CUDD_LAZY_NONE,\n    CUDD_LAZY_SOFT_GROUP,\n    CUDD_LAZY_HARD_GROUP,\n    CUDD_LAZY_UNGROUP\n} Cudd_LazyGroupType;\n\n\n/**\n  @brief Variable type.\n\n  @details Used only in lazy sifting.\n\n*/\ntypedef enum {\n    CUDD_VAR_PRIMARY_INPUT,\n    CUDD_VAR_PRESENT_STATE,\n    CUDD_VAR_NEXT_STATE\n} Cudd_VariableType;\n\n/**\n   @brief Type of the value of a terminal node.\n*/\ntypedef double CUDD_VALUE_TYPE;\n\n/**\n   @brief Type of the decision diagram node.\n*/\ntypedef struct DdNode DdNode;\n\n/**\n   @brief Type of a pointer to a decision diagram node.\n*/\ntypedef DdNode *DdNodePtr;\n\n/**\n   @brief CUDD manager.\n*/\ntypedef struct DdManager DdManager;\n\n/**\n   @brief CUDD generator.\n*/\ntypedef struct DdGen DdGen;\n\n/**\n   @brief Type of an arbitrary precision integer \"digit.\"\n*/\ntypedef uint32_t DdApaDigit;\n\n/**\n   @brief Type of an arbitrary precision intger, which is an array of digits.\n*/\ntypedef DdApaDigit * DdApaNumber;\n\n/**\n   @brief Type of a const-qualified arbitrary precision integer.\n*/\ntypedef DdApaDigit const * DdConstApaNumber;\n\n/**\n   @brief Return type for function computing two-literal clauses.\n*/\ntypedef struct DdTlcInfo DdTlcInfo;\n\n/**\n   @brief Type of hook function.\n*/\ntypedef int (*DD_HFP)(DdManager *, const char *, void *);\n/**\n   @brief Type of priority function\n*/\ntypedef DdNode * (*DD_PRFP)(DdManager * , int, DdNode **, DdNode **, DdNode **);\n/**\n   @brief Type of apply operator.\n*/\ntypedef DdNode * (*DD_AOP)(DdManager *, DdNode **, DdNode **);\n/**\n   @brief Type of monadic apply operator.\n*/\ntypedef DdNode * (*DD_MAOP)(DdManager *, DdNode *);\n/**\n   @brief Type of two-operand cache tag functions.\n*/\ntypedef DdNode * (*DD_CTFP)(DdManager *, DdNode *, DdNode *);\n/**\n   @brief Type of one-operand cache tag functions.\n*/\ntypedef DdNode * (*DD_CTFP1)(DdManager *, DdNode *);\n/**\n   @brief Type of memory-out function.\n*/\ntypedef void (*DD_OOMFP)(size_t);\n/**\n   @brief Type of comparison function for qsort.\n*/\ntypedef int (*DD_QSFP)(const void *, const void *);\n/**\n   @brief Type of termination handler.\n*/\ntypedef int (*DD_THFP)(const void *);\n/**\n   @brief Type of timeout handler.\n*/\ntypedef void (*DD_TOHFP)(DdManager *, void *);\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Complements a %DD.\n\n  @details Complements a %DD by flipping the complement attribute of\n  the pointer (the least significant bit).\n\n  @sideeffect none\n\n  @see Cudd_NotCond\n\n*/\n#define Cudd_Not(node) ((DdNode *)((uintptr_t)(node) ^ (uintptr_t) 01))\n\n\n/**\n  @brief Complements a %DD if a condition is true.\n\n  @details Complements a %DD if condition c is true; c should be\n  either 0 or 1, because it is used directly (for efficiency). If in\n  doubt on the values c may take, use \"(c) ? Cudd_Not(node) : node\".\n\n  @sideeffect none\n\n  @see Cudd_Not\n\n*/\n#define Cudd_NotCond(node,c) ((DdNode *)((uintptr_t)(node) ^ (uintptr_t) (c)))\n\n\n/**\n  @brief Returns the regular version of a pointer.\n\n  @details \n\n  @sideeffect none\n\n  @see Cudd_Complement Cudd_IsComplement\n\n*/\n#define Cudd_Regular(node) ((DdNode *)((uintptr_t)(node) & ~(uintptr_t) 01))\n\n\n/**\n  @brief Returns the complemented version of a pointer.\n\n  @details \n\n  @sideeffect none\n\n  @see Cudd_Regular Cudd_IsComplement\n\n*/\n#define Cudd_Complement(node) ((DdNode *)((uintptr_t)(node) | (uintptr_t) 01))\n\n\n/**\n  @brief Returns 1 if a pointer is complemented.\n\n  @details \n\n  @sideeffect none\n\n  @see Cudd_Regular Cudd_Complement\n\n*/\n#define Cudd_IsComplement(node) ((int) ((uintptr_t) (node) & (uintptr_t) 01))\n\n\n/**\n  @brief Returns the current position in the order of variable\n  index.\n\n  @details Returns the current position in the order of variable\n  index. This macro is obsolete and is kept for compatibility. New\n  applications should use Cudd_ReadPerm instead.\n\n  @sideeffect none\n\n  @see Cudd_ReadPerm\n\n*/\n#define Cudd_ReadIndex(dd,index) (Cudd_ReadPerm(dd,index))\n\n\n/**\n  @brief Iterates over the cubes of a decision diagram.\n\n  @details Iterates over the cubes of a decision diagram f.\n  <ul>\n  <li> DdManager *manager;\n  <li> DdNode *f;\n  <li> DdGen *gen;\n  <li> int *cube;\n  <li> CUDD_VALUE_TYPE value;\n  </ul>\n  Cudd_ForeachCube allocates and frees the generator. Therefore the\n  application should not try to do that. Also, the cube is freed at the\n  end of Cudd_ForeachCube and hence is not available outside of the loop.<p>\n  CAUTION: It is assumed that dynamic reordering will not occur while\n  there are open generators. It is the user's responsibility to make sure\n  that dynamic reordering does not occur. As long as new nodes are not created\n  during generation, and dynamic reordering is not called explicitly,\n  dynamic reordering will not occur. Alternatively, it is sufficient to\n  disable dynamic reordering. It is a mistake to dispose of a diagram\n  on which generation is ongoing.\n\n  @sideeffect none\n\n  @see Cudd_ForeachNode Cudd_FirstCube Cudd_NextCube Cudd_GenFree\n  Cudd_IsGenEmpty Cudd_AutodynDisable\n\n*/\n#define Cudd_ForeachCube(manager, f, gen, cube, value)\\\n    for((gen) = Cudd_FirstCube(manager, f, &cube, &value);\\\n\tCudd_IsGenEmpty(gen) ? Cudd_GenFree(gen) : CUDD_TRUE;\\\n\t(void) Cudd_NextCube(gen, &cube, &value))\n\n\n/**\n  @brief Iterates over the primes of a Boolean function.\n\n  @details Iterates over the primes of a Boolean function producing\n  a prime, but not necessarily irredundant, cover.\n  <ul>\n  <li> DdManager *manager;\n  <li> DdNode *l;\n  <li> DdNode *u;\n  <li> DdGen *gen;\n  <li> int *cube;\n  </ul>\n  The Boolean function is described by an upper bound and a lower bound.  If\n  the function is completely specified, the two bounds coincide.\n  Cudd_ForeachPrime allocates and frees the generator.  Therefore the\n  application should not try to do that.  Also, the cube is freed at the\n  end of Cudd_ForeachPrime and hence is not available outside of the loop.<p>\n  CAUTION: It is a mistake to change a diagram on which generation is ongoing.\n\n  @sideeffect none\n\n  @see Cudd_ForeachCube Cudd_FirstPrime Cudd_NextPrime Cudd_GenFree\n  Cudd_IsGenEmpty\n\n*/\n#define Cudd_ForeachPrime(manager, l, u, gen, cube)\\\n    for((gen) = Cudd_FirstPrime(manager, l, u, &cube);\\\n\tCudd_IsGenEmpty(gen) ? Cudd_GenFree(gen) : CUDD_TRUE;\\\n\t(void) Cudd_NextPrime(gen, &cube))\n\n\n/**\n  @brief Iterates over the nodes of a decision diagram.\n\n  @details Iterates over the nodes of a decision diagram f.\n  <ul>\n  <li> DdManager *manager;\n  <li> DdNode *f;\n  <li> DdGen *gen;\n  <li> DdNode *node;\n  </ul>\n  The nodes are returned in a seemingly random order.\n  Cudd_ForeachNode allocates and frees the generator. Therefore the\n  application should not try to do that.<p>\n  CAUTION: It is assumed that dynamic reordering will not occur while\n  there are open generators. It is the user's responsibility to make sure\n  that dynamic reordering does not occur. As long as new nodes are not created\n  during generation, and dynamic reordering is not called explicitly,\n  dynamic reordering will not occur. Alternatively, it is sufficient to\n  disable dynamic reordering. It is a mistake to dispose of a diagram\n  on which generation is ongoing.\n\n  @sideeffect none\n\n  @see Cudd_ForeachCube Cudd_FirstNode Cudd_NextNode Cudd_GenFree\n  Cudd_IsGenEmpty Cudd_AutodynDisable\n\n*/\n#define Cudd_ForeachNode(manager, f, gen, node)\\\n    for((gen) = Cudd_FirstNode(manager, f, &node);\\\n\tCudd_IsGenEmpty(gen) ? Cudd_GenFree(gen) : CUDD_TRUE;\\\n\t(void) Cudd_NextNode(gen, &node))\n\n\n/**\n  @brief Iterates over the paths of a %ZDD.\n\n  @details Iterates over the paths of a %ZDD f.\n  <ul>\n  <li> DdManager *manager;\n  <li> DdNode *f;\n  <li> DdGen *gen;\n  <li> int *path;\n  </ul>\n  Cudd_zddForeachPath allocates and frees the generator. Therefore the\n  application should not try to do that. Also, the path is freed at the\n  end of Cudd_zddForeachPath and hence is not available outside of the loop.<p>\n  CAUTION: It is assumed that dynamic reordering will not occur while\n  there are open generators.  It is the user's responsibility to make sure\n  that dynamic reordering does not occur.  As long as new nodes are not created\n  during generation, and dynamic reordering is not called explicitly,\n  dynamic reordering will not occur.  Alternatively, it is sufficient to\n  disable dynamic reordering.  It is a mistake to dispose of a diagram\n  on which generation is ongoing.\n\n  @sideeffect none\n\n  @see Cudd_zddFirstPath Cudd_zddNextPath Cudd_GenFree\n  Cudd_IsGenEmpty Cudd_AutodynDisable\n\n*/\n#define Cudd_zddForeachPath(manager, f, gen, path)\\\n    for((gen) = Cudd_zddFirstPath(manager, f, &path);\\\n\tCudd_IsGenEmpty(gen) ? Cudd_GenFree(gen) : CUDD_TRUE;\\\n\t(void) Cudd_zddNextPath(gen, &path))\n\n\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nextern DdNode * Cudd_addNewVar(DdManager *dd);\nextern DdNode * Cudd_addNewVarAtLevel(DdManager *dd, int level);\nextern DdNode * Cudd_bddNewVar(DdManager *dd);\nextern DdNode * Cudd_bddNewVarAtLevel(DdManager *dd, int level);\nextern int Cudd_bddIsVar(DdManager * dd, DdNode * f);\nextern DdNode * Cudd_addIthVar(DdManager *dd, int i);\nextern DdNode * Cudd_bddIthVar(DdManager *dd, int i);\nextern DdNode * Cudd_zddIthVar(DdManager *dd, int i);\nextern int Cudd_zddVarsFromBddVars(DdManager *dd, int multiplicity);\nextern unsigned int Cudd_ReadMaxIndex(void);\nextern DdNode * Cudd_addConst(DdManager *dd, CUDD_VALUE_TYPE c);\nextern int Cudd_IsConstant(DdNode *node);\nextern int Cudd_IsNonConstant(DdNode *f);\nextern DdNode * Cudd_T(DdNode *node);\nextern DdNode * Cudd_E(DdNode *node);\nextern CUDD_VALUE_TYPE Cudd_V(DdNode *node);\nextern unsigned long Cudd_ReadStartTime(DdManager *unique);\nextern unsigned long Cudd_ReadElapsedTime(DdManager *unique);\nextern void Cudd_SetStartTime(DdManager *unique, unsigned long st);\nextern void Cudd_ResetStartTime(DdManager *unique);\nextern unsigned long Cudd_ReadTimeLimit(DdManager *unique);\nextern unsigned long Cudd_SetTimeLimit(DdManager *unique, unsigned long tl);\nextern void Cudd_UpdateTimeLimit(DdManager * unique);\nextern void Cudd_IncreaseTimeLimit(DdManager * unique, unsigned long increase);\nextern void Cudd_UnsetTimeLimit(DdManager *unique);\nextern int Cudd_TimeLimited(DdManager *unique);\nextern void Cudd_RegisterTerminationCallback(DdManager *unique, DD_THFP callback, void * callback_arg);\nextern void Cudd_UnregisterTerminationCallback(DdManager *unique);\nextern DD_OOMFP Cudd_RegisterOutOfMemoryCallback(DdManager *unique, DD_OOMFP callback);\nextern void Cudd_UnregisterOutOfMemoryCallback(DdManager *unique);\nextern void Cudd_RegisterTimeoutHandler(DdManager *unique, DD_TOHFP handler, void *arg);\nextern DD_TOHFP Cudd_ReadTimeoutHandler(DdManager *unique, void **argp);\nextern void Cudd_AutodynEnable(DdManager *unique, Cudd_ReorderingType method);\nextern void Cudd_AutodynDisable(DdManager *unique);\nextern int Cudd_ReorderingStatus(DdManager *unique, Cudd_ReorderingType *method);\nextern void Cudd_AutodynEnableZdd(DdManager *unique, Cudd_ReorderingType method);\nextern void Cudd_AutodynDisableZdd(DdManager *unique);\nextern int Cudd_ReorderingStatusZdd(DdManager *unique, Cudd_ReorderingType *method);\nextern int Cudd_zddRealignmentEnabled(DdManager *unique);\nextern void Cudd_zddRealignEnable(DdManager *unique);\nextern void Cudd_zddRealignDisable(DdManager *unique);\nextern int Cudd_bddRealignmentEnabled(DdManager *unique);\nextern void Cudd_bddRealignEnable(DdManager *unique);\nextern void Cudd_bddRealignDisable(DdManager *unique);\nextern DdNode * Cudd_ReadOne(DdManager *dd);\nextern DdNode * Cudd_ReadZddOne(DdManager *dd, int i);\nextern DdNode * Cudd_ReadZero(DdManager *dd);\nextern DdNode * Cudd_ReadLogicZero(DdManager *dd);\nextern DdNode * Cudd_ReadPlusInfinity(DdManager *dd);\nextern DdNode * Cudd_ReadMinusInfinity(DdManager *dd);\nextern DdNode * Cudd_ReadBackground(DdManager *dd);\nextern void Cudd_SetBackground(DdManager *dd, DdNode *bck);\nextern unsigned int Cudd_ReadCacheSlots(DdManager *dd);\nextern double Cudd_ReadCacheUsedSlots(DdManager * dd);\nextern double Cudd_ReadCacheLookUps(DdManager *dd);\nextern double Cudd_ReadCacheHits(DdManager *dd);\nextern double Cudd_ReadRecursiveCalls(DdManager * dd);\nextern unsigned int Cudd_ReadMinHit(DdManager *dd);\nextern void Cudd_SetMinHit(DdManager *dd, unsigned int hr);\nextern unsigned int Cudd_ReadLooseUpTo(DdManager *dd);\nextern void Cudd_SetLooseUpTo(DdManager *dd, unsigned int lut);\nextern unsigned int Cudd_ReadMaxCache(DdManager *dd);\nextern unsigned int Cudd_ReadMaxCacheHard(DdManager *dd);\nextern void Cudd_SetMaxCacheHard(DdManager *dd, unsigned int mc);\nextern int Cudd_ReadSize(DdManager *dd);\nextern int Cudd_ReadZddSize(DdManager *dd);\nextern unsigned int Cudd_ReadSlots(DdManager *dd);\nextern double Cudd_ReadUsedSlots(DdManager * dd);\nextern double Cudd_ExpectedUsedSlots(DdManager * dd);\nextern unsigned int Cudd_ReadKeys(DdManager *dd);\nextern unsigned int Cudd_ReadDead(DdManager *dd);\nextern unsigned int Cudd_ReadMinDead(DdManager *dd);\nextern unsigned int Cudd_ReadReorderings(DdManager *dd);\nextern unsigned int Cudd_ReadMaxReorderings(DdManager *dd);\nextern void Cudd_SetMaxReorderings(DdManager *dd, unsigned int mr);\nextern long Cudd_ReadReorderingTime(DdManager * dd);\nextern int Cudd_ReadGarbageCollections(DdManager * dd);\nextern long Cudd_ReadGarbageCollectionTime(DdManager * dd);\nextern double Cudd_ReadNodesFreed(DdManager * dd);\nextern double Cudd_ReadNodesDropped(DdManager * dd);\nextern double Cudd_ReadUniqueLookUps(DdManager * dd);\nextern double Cudd_ReadUniqueLinks(DdManager * dd);\nextern int Cudd_ReadSiftMaxVar(DdManager *dd);\nextern void Cudd_SetSiftMaxVar(DdManager *dd, int smv);\nextern int Cudd_ReadSiftMaxSwap(DdManager *dd);\nextern void Cudd_SetSiftMaxSwap(DdManager *dd, int sms);\nextern double Cudd_ReadMaxGrowth(DdManager *dd);\nextern void Cudd_SetMaxGrowth(DdManager *dd, double mg);\nextern double Cudd_ReadMaxGrowthAlternate(DdManager * dd);\nextern void Cudd_SetMaxGrowthAlternate(DdManager * dd, double mg);\nextern int Cudd_ReadReorderingCycle(DdManager * dd);\nextern void Cudd_SetReorderingCycle(DdManager * dd, int cycle);\nextern unsigned int Cudd_NodeReadIndex(DdNode *node);\nextern int Cudd_ReadPerm(DdManager *dd, int i);\nextern int Cudd_ReadPermZdd(DdManager *dd, int i);\nextern int Cudd_ReadInvPerm(DdManager *dd, int i);\nextern int Cudd_ReadInvPermZdd(DdManager *dd, int i);\nextern DdNode * Cudd_ReadVars(DdManager *dd, int i);\nextern CUDD_VALUE_TYPE Cudd_ReadEpsilon(DdManager *dd);\nextern void Cudd_SetEpsilon(DdManager *dd, CUDD_VALUE_TYPE ep);\nextern Cudd_AggregationType Cudd_ReadGroupcheck(DdManager *dd);\nextern void Cudd_SetGroupcheck(DdManager *dd, Cudd_AggregationType gc);\nextern int Cudd_GarbageCollectionEnabled(DdManager *dd);\nextern void Cudd_EnableGarbageCollection(DdManager *dd);\nextern void Cudd_DisableGarbageCollection(DdManager *dd);\nextern int Cudd_DeadAreCounted(DdManager *dd);\nextern void Cudd_TurnOnCountDead(DdManager *dd);\nextern void Cudd_TurnOffCountDead(DdManager *dd);\nextern int Cudd_ReadRecomb(DdManager *dd);\nextern void Cudd_SetRecomb(DdManager *dd, int recomb);\nextern int Cudd_ReadSymmviolation(DdManager *dd);\nextern void Cudd_SetSymmviolation(DdManager *dd, int symmviolation);\nextern int Cudd_ReadArcviolation(DdManager *dd);\nextern void Cudd_SetArcviolation(DdManager *dd, int arcviolation);\nextern int Cudd_ReadPopulationSize(DdManager *dd);\nextern void Cudd_SetPopulationSize(DdManager *dd, int populationSize);\nextern int Cudd_ReadNumberXovers(DdManager *dd);\nextern void Cudd_SetNumberXovers(DdManager *dd, int numberXovers);\nextern unsigned int Cudd_ReadOrderRandomization(DdManager * dd);\nextern void Cudd_SetOrderRandomization(DdManager * dd, unsigned int factor);\nextern size_t Cudd_ReadMemoryInUse(DdManager *dd);\nextern int Cudd_PrintInfo(DdManager *dd, FILE *fp);\nextern long Cudd_ReadPeakNodeCount(DdManager *dd);\nextern int Cudd_ReadPeakLiveNodeCount(DdManager * dd);\nextern long Cudd_ReadNodeCount(DdManager *dd);\nextern long Cudd_zddReadNodeCount(DdManager *dd);\nextern int Cudd_AddHook(DdManager *dd, DD_HFP f, Cudd_HookType where);\nextern int Cudd_RemoveHook(DdManager *dd, DD_HFP f, Cudd_HookType where);\nextern int Cudd_IsInHook(DdManager * dd, DD_HFP f, Cudd_HookType where);\nextern int Cudd_StdPreReordHook(DdManager *dd, const char *str, void *data);\nextern int Cudd_StdPostReordHook(DdManager *dd, const char *str, void *data);\nextern int Cudd_EnableReorderingReporting(DdManager *dd);\nextern int Cudd_DisableReorderingReporting(DdManager *dd);\nextern int Cudd_ReorderingReporting(DdManager *dd);\nextern int Cudd_PrintGroupedOrder(DdManager * dd, const char *str, void *data);\nextern int Cudd_EnableOrderingMonitoring(DdManager *dd);\nextern int Cudd_DisableOrderingMonitoring(DdManager *dd);\nextern int Cudd_OrderingMonitoring(DdManager *dd);\nextern void Cudd_SetApplicationHook(DdManager *dd, void * value);\nextern void * Cudd_ReadApplicationHook(DdManager *dd);\nextern Cudd_ErrorType Cudd_ReadErrorCode(DdManager *dd);\nextern void Cudd_ClearErrorCode(DdManager *dd);\nextern DD_OOMFP Cudd_InstallOutOfMemoryHandler(DD_OOMFP newHandler);\nextern FILE * Cudd_ReadStdout(DdManager *dd);\nextern void Cudd_SetStdout(DdManager *dd, FILE *fp);\nextern FILE * Cudd_ReadStderr(DdManager *dd);\nextern void Cudd_SetStderr(DdManager *dd, FILE *fp);\nextern unsigned int Cudd_ReadNextReordering(DdManager *dd);\nextern void Cudd_SetNextReordering(DdManager *dd, unsigned int next);\nextern double Cudd_ReadSwapSteps(DdManager *dd);\nextern unsigned int Cudd_ReadMaxLive(DdManager *dd);\nextern void Cudd_SetMaxLive(DdManager *dd, unsigned int maxLive);\nextern size_t Cudd_ReadMaxMemory(DdManager *dd);\nextern size_t Cudd_SetMaxMemory(DdManager *dd, size_t maxMemory);\nextern int Cudd_bddBindVar(DdManager *dd, int index);\nextern int Cudd_bddUnbindVar(DdManager *dd, int index);\nextern int Cudd_bddVarIsBound(DdManager *dd, int index);\nextern DdNode * Cudd_addExistAbstract(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * Cudd_addUnivAbstract(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * Cudd_addOrAbstract(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * Cudd_addMinAbstract(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * Cudd_addMaxAbstract(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * Cudd_addFirstFilter(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * Cudd_addApply(DdManager *dd, DD_AOP op, DdNode *f, DdNode *g);\nextern DdNode * Cudd_addPlus(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addTimes(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addThreshold(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addSetNZ(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addDivide(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addMinus(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addMinimum(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addMaximum(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addOneZeroMaximum(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addDiff(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addAgreement(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addOr(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addNand(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addNor(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addXor(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addXnor(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addEquals(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addNotEquals(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addGreaterThan(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addGreaterThanEquals(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addLessThan(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addLessThanEquals(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addPow(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addMod(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addLogXY(DdManager *dd, DdNode **f, DdNode **g);\nextern DdNode * Cudd_addMonadicApply(DdManager * dd, DD_MAOP op, DdNode * f);\nextern DdNode * Cudd_addLog(DdManager * dd, DdNode * f);\nextern DdNode * Cudd_addFloor(DdManager * dd, DdNode * f);\nextern DdNode * Cudd_addCeil(DdManager * dd, DdNode * f);\nextern DdNode * Cudd_addFindMax(DdManager *dd, DdNode *f);\nextern DdNode * Cudd_addFindMin(DdManager *dd, DdNode *f);\nextern DdNode * Cudd_addIthBit(DdManager *dd, DdNode *f, int bit);\nextern DdNode * Cudd_addScalarInverse(DdManager *dd, DdNode *f, DdNode *epsilon);\nextern DdNode * Cudd_addIte(DdManager *dd, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * Cudd_addIteConstant(DdManager *dd, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * Cudd_addEvalConst(DdManager *dd, DdNode *f, DdNode *g);\nextern int Cudd_addLeq(DdManager * dd, DdNode * f, DdNode * g);\nextern DdNode * Cudd_addCmpl(DdManager *dd, DdNode *f);\nextern DdNode * Cudd_addNegate(DdManager *dd, DdNode *f);\nextern DdNode * Cudd_addRoundOff(DdManager *dd, DdNode *f, int N);\nextern DdNode * Cudd_addWalsh(DdManager *dd, DdNode **x, DdNode **y, int n);\nextern DdNode * Cudd_addResidue(DdManager *dd, int n, int m, int options, int top);\nextern DdNode * Cudd_bddAndAbstract(DdManager *manager, DdNode *f, DdNode *g, DdNode *cube);\nextern DdNode * Cudd_bddAndAbstractLimit(DdManager *manager, DdNode *f, DdNode *g, DdNode *cube, unsigned int limit);\nextern int Cudd_ApaNumberOfDigits(int binaryDigits);\nextern DdApaNumber Cudd_NewApaNumber(int digits);\nextern void Cudd_FreeApaNumber(DdApaNumber number);\nextern void Cudd_ApaCopy(int digits, DdConstApaNumber source, DdApaNumber dest);\nextern DdApaDigit Cudd_ApaAdd(int digits, DdConstApaNumber a, DdConstApaNumber b, DdApaNumber sum);\nextern DdApaDigit Cudd_ApaSubtract(int digits, DdConstApaNumber a, DdConstApaNumber b, DdApaNumber diff);\nextern DdApaDigit Cudd_ApaShortDivision(int digits, DdConstApaNumber dividend, DdApaDigit divisor, DdApaNumber quotient);\nextern unsigned int Cudd_ApaIntDivision(int  digits, DdConstApaNumber dividend, unsigned int  divisor, DdApaNumber  quotient);\nextern void Cudd_ApaShiftRight(int digits, DdApaDigit in, DdConstApaNumber a, DdApaNumber b);\nextern void Cudd_ApaSetToLiteral(int digits, DdApaNumber number, DdApaDigit literal);\nextern void Cudd_ApaPowerOfTwo(int digits, DdApaNumber number, int power);\nextern int Cudd_ApaCompare(int digitsFirst, DdConstApaNumber first, int digitsSecond, DdConstApaNumber second);\nextern int Cudd_ApaCompareRatios(int digitsFirst, DdConstApaNumber firstNum, unsigned int firstDen, int digitsSecond, DdConstApaNumber secondNum, unsigned int secondDen);\nextern int Cudd_ApaPrintHex(FILE *fp, int digits, DdConstApaNumber number);\nextern int Cudd_ApaPrintDecimal(FILE *fp, int digits, DdConstApaNumber number);\nextern char * Cudd_ApaStringDecimal(int digits, DdConstApaNumber number);\nextern int Cudd_ApaPrintExponential(FILE * fp, int  digits, DdConstApaNumber number, int precision);\nextern DdApaNumber Cudd_ApaCountMinterm(DdManager const *manager, DdNode *node, int nvars, int *digits);\nextern int Cudd_ApaPrintMinterm(FILE *fp, DdManager const *dd, DdNode *node, int nvars);\nextern int Cudd_ApaPrintMintermExp(FILE * fp, DdManager const * dd, DdNode *node, int  nvars, int precision);\nextern int Cudd_ApaPrintDensity(FILE * fp, DdManager * dd, DdNode * node, int  nvars);\nextern DdNode * Cudd_UnderApprox(DdManager *dd, DdNode *f, int numVars, int threshold, int safe, double quality);\nextern DdNode * Cudd_OverApprox(DdManager *dd, DdNode *f, int numVars, int threshold, int safe, double quality);\nextern DdNode * Cudd_RemapUnderApprox(DdManager *dd, DdNode *f, int numVars, int threshold, double quality);\nextern DdNode * Cudd_RemapOverApprox(DdManager *dd, DdNode *f, int numVars, int threshold, double quality);\nextern DdNode * Cudd_BiasedUnderApprox(DdManager *dd, DdNode *f, DdNode *b, int numVars, int threshold, double quality1, double quality0);\nextern DdNode * Cudd_BiasedOverApprox(DdManager *dd, DdNode *f, DdNode *b, int numVars, int threshold, double quality1, double quality0);\nextern DdNode * Cudd_bddExistAbstract(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * Cudd_bddExistAbstractLimit(DdManager * manager, DdNode * f, DdNode * cube, unsigned int limit);\nextern DdNode * Cudd_bddXorExistAbstract(DdManager *manager, DdNode *f, DdNode *g, DdNode *cube);\nextern DdNode * Cudd_bddUnivAbstract(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * Cudd_bddBooleanDiff(DdManager *manager, DdNode *f, int x);\nextern int Cudd_bddVarIsDependent(DdManager *dd, DdNode *f, DdNode *var);\nextern double Cudd_bddCorrelation(DdManager *manager, DdNode *f, DdNode *g);\nextern double Cudd_bddCorrelationWeights(DdManager *manager, DdNode *f, DdNode *g, double *prob);\nextern DdNode * Cudd_bddIte(DdManager *dd, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * Cudd_bddIteLimit(DdManager *dd, DdNode *f, DdNode *g, DdNode *h, unsigned int limit);\nextern DdNode * Cudd_bddIteConstant(DdManager *dd, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * Cudd_bddIntersect(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_bddAnd(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_bddAndLimit(DdManager *dd, DdNode *f, DdNode *g, unsigned int limit);\nextern DdNode * Cudd_bddOr(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_bddOrLimit(DdManager *dd, DdNode *f, DdNode *g, unsigned int limit);\nextern DdNode * Cudd_bddNand(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_bddNor(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_bddXor(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_bddXnor(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_bddXnorLimit(DdManager *dd, DdNode *f, DdNode *g, unsigned int limit);\nextern int Cudd_bddLeq(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_addBddThreshold(DdManager *dd, DdNode *f, CUDD_VALUE_TYPE value);\nextern DdNode * Cudd_addBddStrictThreshold(DdManager *dd, DdNode *f, CUDD_VALUE_TYPE value);\nextern DdNode * Cudd_addBddInterval(DdManager *dd, DdNode *f, CUDD_VALUE_TYPE lower, CUDD_VALUE_TYPE upper);\nextern DdNode * Cudd_addBddIthBit(DdManager *dd, DdNode *f, int bit);\nextern DdNode * Cudd_BddToAdd(DdManager *dd, DdNode *B);\nextern DdNode * Cudd_addBddPattern(DdManager *dd, DdNode *f);\nextern DdNode * Cudd_bddTransfer(DdManager *ddSource, DdManager *ddDestination, DdNode *f);\nextern int Cudd_DebugCheck(DdManager *table);\nextern int Cudd_CheckKeys(DdManager *table);\nextern DdNode * Cudd_bddClippingAnd(DdManager *dd, DdNode *f, DdNode *g, int maxDepth, int direction);\nextern DdNode * Cudd_bddClippingAndAbstract(DdManager *dd, DdNode *f, DdNode *g, DdNode *cube, int maxDepth, int direction);\nextern DdNode * Cudd_Cofactor(DdManager *dd, DdNode *f, DdNode *g);\nextern int Cudd_CheckCube(DdManager *dd, DdNode *g);\nextern int Cudd_VarsAreSymmetric(DdManager * dd, DdNode * f, int index1, int index2);\nextern DdNode * Cudd_bddCompose(DdManager *dd, DdNode *f, DdNode *g, int v);\nextern DdNode * Cudd_addCompose(DdManager *dd, DdNode *f, DdNode *g, int v);\nextern DdNode * Cudd_addPermute(DdManager *manager, DdNode *node, int *permut);\nextern DdNode * Cudd_addSwapVariables(DdManager *dd, DdNode *f, DdNode **x, DdNode **y, int n);\nextern DdNode * Cudd_bddPermute(DdManager *manager, DdNode *node, int *permut);\nextern DdNode * Cudd_bddVarMap(DdManager *manager, DdNode *f);\nextern int Cudd_SetVarMap(DdManager *manager, DdNode **x, DdNode **y, int n);\nextern DdNode * Cudd_bddSwapVariables(DdManager *dd, DdNode *f, DdNode **x, DdNode **y, int n);\nextern DdNode * Cudd_bddAdjPermuteX(DdManager *dd, DdNode *B, DdNode **x, int n);\nextern DdNode * Cudd_addVectorCompose(DdManager *dd, DdNode *f, DdNode **vector);\nextern DdNode * Cudd_addGeneralVectorCompose(DdManager *dd, DdNode *f, DdNode **vectorOn, DdNode **vectorOff);\nextern DdNode * Cudd_addNonSimCompose(DdManager *dd, DdNode *f, DdNode **vector);\nextern DdNode * Cudd_bddVectorCompose(DdManager *dd, DdNode *f, DdNode **vector);\nextern int Cudd_bddApproxConjDecomp(DdManager *dd, DdNode *f, DdNode ***conjuncts);\nextern int Cudd_bddApproxDisjDecomp(DdManager *dd, DdNode *f, DdNode ***disjuncts);\nextern int Cudd_bddIterConjDecomp(DdManager *dd, DdNode *f, DdNode ***conjuncts);\nextern int Cudd_bddIterDisjDecomp(DdManager *dd, DdNode *f, DdNode ***disjuncts);\nextern int Cudd_bddGenConjDecomp(DdManager *dd, DdNode *f, DdNode ***conjuncts);\nextern int Cudd_bddGenDisjDecomp(DdManager *dd, DdNode *f, DdNode ***disjuncts);\nextern int Cudd_bddVarConjDecomp(DdManager *dd, DdNode * f, DdNode ***conjuncts);\nextern int Cudd_bddVarDisjDecomp(DdManager *dd, DdNode * f, DdNode ***disjuncts);\nextern DdNode * Cudd_FindEssential(DdManager *dd, DdNode *f);\nextern int Cudd_bddIsVarEssential(DdManager *manager, DdNode *f, int id, int phase);\nextern DdTlcInfo * Cudd_FindTwoLiteralClauses(DdManager * dd, DdNode * f);\nextern int Cudd_PrintTwoLiteralClauses(DdManager * dd, DdNode * f, char **names, FILE *fp);\nextern int Cudd_ReadIthClause(DdTlcInfo * tlc, int i, unsigned *var1, unsigned *var2, int *phase1, int *phase2);\nextern void Cudd_tlcInfoFree(DdTlcInfo * t);\nextern int Cudd_DumpBlif(DdManager *dd, int n, DdNode **f, char const * const *inames, char const * const *onames, char *mname, FILE *fp, int mv);\nextern int Cudd_DumpBlifBody(DdManager *dd, int n, DdNode **f, char const * const *inames, char const * const *onames, FILE *fp, int mv);\nextern int Cudd_DumpDot(DdManager *dd, int n, DdNode **f, char const * const *inames, char const * const *onames, FILE *fp);\nextern int Cudd_DumpDaVinci(DdManager *dd, int n, DdNode **f, char const * const *inames, char const * const *onames, FILE *fp);\nextern int Cudd_DumpDDcal(DdManager *dd, int n, DdNode **f, char const * const *inames, char const * const *onames, FILE *fp);\nextern int Cudd_DumpFactoredForm(DdManager *dd, int n, DdNode **f, char const * const *inames, char const * const *onames, FILE *fp);\nextern char * Cudd_FactoredFormString(DdManager *dd, DdNode *f, char const * const * inames);\nextern DdNode * Cudd_bddConstrain(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * Cudd_bddRestrict(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * Cudd_bddNPAnd(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * Cudd_addConstrain(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode ** Cudd_bddConstrainDecomp(DdManager *dd, DdNode *f);\nextern DdNode * Cudd_addRestrict(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode ** Cudd_bddCharToVect(DdManager *dd, DdNode *f);\nextern DdNode * Cudd_bddLICompaction(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * Cudd_bddSqueeze(DdManager *dd, DdNode *l, DdNode *u);\nextern DdNode * Cudd_bddInterpolate(DdManager * dd, DdNode * l, DdNode * u);\nextern DdNode * Cudd_bddMinimize(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * Cudd_SubsetCompress(DdManager *dd, DdNode *f, int nvars, int threshold);\nextern DdNode * Cudd_SupersetCompress(DdManager *dd, DdNode *f, int nvars, int threshold);\nextern int Cudd_addHarwell(FILE *fp, DdManager *dd, DdNode **E, DdNode ***x, DdNode ***y, DdNode ***xn, DdNode ***yn_, int *nx, int *ny, int *m, int *n, int bx, int sx, int by, int sy, int pr);\nextern DdManager * Cudd_Init(unsigned int numVars, unsigned int numVarsZ, unsigned int numSlots, unsigned int cacheSize, size_t maxMemory);\nextern void Cudd_Quit(DdManager *unique);\nextern int Cudd_PrintLinear(DdManager *table);\nextern int Cudd_ReadLinear(DdManager *table, int x, int y);\nextern DdNode * Cudd_bddLiteralSetIntersection(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_addMatrixMultiply(DdManager *dd, DdNode *A, DdNode *B, DdNode **z, int nz);\nextern DdNode * Cudd_addTimesPlus(DdManager *dd, DdNode *A, DdNode *B, DdNode **z, int nz);\nextern DdNode * Cudd_addTriangle(DdManager *dd, DdNode *f, DdNode *g, DdNode **z, int nz);\nextern DdNode * Cudd_addOuterSum(DdManager *dd, DdNode *M, DdNode *r, DdNode *c);\nextern DdNode * Cudd_PrioritySelect(DdManager *dd, DdNode *R, DdNode **x, DdNode **y, DdNode **z, DdNode *Pi, int n, DD_PRFP PiFunc);\nextern DdNode * Cudd_Xgty(DdManager *dd, int N, DdNode **z, DdNode **x, DdNode **y);\nextern DdNode * Cudd_Xeqy(DdManager *dd, int N, DdNode **x, DdNode **y);\nextern DdNode * Cudd_addXeqy(DdManager *dd, int N, DdNode **x, DdNode **y);\nextern DdNode * Cudd_Dxygtdxz(DdManager *dd, int N, DdNode **x, DdNode **y, DdNode **z);\nextern DdNode * Cudd_Dxygtdyz(DdManager *dd, int N, DdNode **x, DdNode **y, DdNode **z);\nextern DdNode * Cudd_Inequality(DdManager * dd, int  N, int c, DdNode ** x, DdNode ** y);\nextern DdNode * Cudd_Disequality(DdManager * dd, int  N, int c, DdNode ** x, DdNode ** y);\nextern DdNode * Cudd_bddInterval(DdManager * dd, int  N, DdNode ** x, unsigned int lowerB, unsigned int upperB);\nextern DdNode * Cudd_CProjection(DdManager *dd, DdNode *R, DdNode *Y);\nextern DdNode * Cudd_addHamming(DdManager *dd, DdNode **xVars, DdNode **yVars, int nVars);\nextern int Cudd_MinHammingDist(DdManager *dd, DdNode *f, int *minterm, int upperBound);\nextern DdNode * Cudd_bddClosestCube(DdManager *dd, DdNode * f, DdNode *g, int *distance);\nextern int Cudd_addRead(FILE *fp, DdManager *dd, DdNode **E, DdNode ***x, DdNode ***y, DdNode ***xn, DdNode ***yn_, int *nx, int *ny, int *m, int *n, int bx, int sx, int by, int sy);\nextern int Cudd_bddRead(FILE *fp, DdManager *dd, DdNode **E, DdNode ***x, DdNode ***y, int *nx, int *ny, int *m, int *n, int bx, int sx, int by, int sy);\nextern void Cudd_Ref(DdNode *n);\nextern void Cudd_RecursiveDeref(DdManager *table, DdNode *n);\nextern void Cudd_IterDerefBdd(DdManager *table, DdNode *n);\nextern void Cudd_DelayedDerefBdd(DdManager * table, DdNode * n);\nextern void Cudd_RecursiveDerefZdd(DdManager *table, DdNode *n);\nextern void Cudd_Deref(DdNode *node);\nextern int Cudd_CheckZeroRef(DdManager *manager);\nextern int Cudd_ReduceHeap(DdManager *table, Cudd_ReorderingType heuristic, int minsize);\nextern int Cudd_ShuffleHeap(DdManager *table, int *permutation);\nextern DdNode * Cudd_Eval(DdManager *dd, DdNode *f, int *inputs);\nextern DdNode * Cudd_ShortestPath(DdManager *manager, DdNode *f, int *weight, int *support, int *length);\nextern DdNode * Cudd_LargestCube(DdManager *manager, DdNode *f, int *length);\nextern int Cudd_ShortestLength(DdManager *manager, DdNode *f, int *weight);\nextern DdNode * Cudd_Decreasing(DdManager *dd, DdNode *f, int i);\nextern DdNode * Cudd_Increasing(DdManager *dd, DdNode *f, int i);\nextern int Cudd_EquivDC(DdManager *dd, DdNode *F, DdNode *G, DdNode *D);\nextern int Cudd_bddLeqUnless(DdManager *dd, DdNode *f, DdNode *g, DdNode *D);\nextern int Cudd_EqualSupNorm(DdManager *dd, DdNode *f, DdNode *g, CUDD_VALUE_TYPE tolerance, int pr);\nextern int Cudd_EqualSupNormRel(DdManager *dd, DdNode *f, DdNode *g, CUDD_VALUE_TYPE tolerance, int pr);\nextern DdNode * Cudd_bddMakePrime(DdManager *dd, DdNode *cube, DdNode *f);\nextern DdNode * Cudd_bddMaximallyExpand(DdManager *dd, DdNode *lb, DdNode *ub, DdNode *f);\nextern DdNode * Cudd_bddLargestPrimeUnate(DdManager *dd , DdNode *f, DdNode *phaseBdd);\nextern double * Cudd_CofMinterm(DdManager *dd, DdNode *node);\nextern DdNode * Cudd_SolveEqn(DdManager * bdd, DdNode *F, DdNode *Y, DdNode **G, int **yIndex, int n);\nextern DdNode * Cudd_VerifySol(DdManager * bdd, DdNode *F, DdNode **G, int *yIndex, int n);\nextern DdNode * Cudd_SplitSet(DdManager *manager, DdNode *S, DdNode **xVars, int n, double m);\nextern DdNode * Cudd_SubsetHeavyBranch(DdManager *dd, DdNode *f, int numVars, int threshold);\nextern DdNode * Cudd_SupersetHeavyBranch(DdManager *dd, DdNode *f, int numVars, int threshold);\nextern DdNode * Cudd_SubsetShortPaths(DdManager *dd, DdNode *f, int numVars, int threshold, int hardlimit);\nextern DdNode * Cudd_SupersetShortPaths(DdManager *dd, DdNode *f, int numVars, int threshold, int hardlimit);\nextern void Cudd_SymmProfile(DdManager *table, int lower, int upper);\nextern unsigned int Cudd_Prime(unsigned int p);\nextern int Cudd_Reserve(DdManager *manager, int amount);\nextern int Cudd_PrintMinterm(DdManager *manager, DdNode *node);\nextern int Cudd_bddPrintCover(DdManager *dd, DdNode *l, DdNode *u);\nextern int Cudd_PrintDebug(DdManager *dd, DdNode *f, int n, int pr);\nextern int Cudd_PrintSummary(DdManager * dd, DdNode * f, int n, int mode);\nextern int Cudd_DagSize(DdNode *node);\nextern int Cudd_EstimateCofactor(DdManager *dd, DdNode * node, int i, int phase);\nextern int Cudd_EstimateCofactorSimple(DdNode * node, int i);\nextern int Cudd_SharingSize(DdNode **nodeArray, int n);\nextern double Cudd_CountMinterm(DdManager *manager, DdNode *node, int nvars);\n#ifdef EPD_H_\nextern int Cudd_EpdCountMinterm(DdManager const *manager, DdNode *node, int nvars, EpDouble *epd);\n#endif\nextern long double Cudd_LdblCountMinterm(DdManager const *manager, DdNode *node, int nvars);\nextern int Cudd_EpdPrintMinterm(DdManager const * dd, DdNode * node, int nvars);\nextern double Cudd_CountPath(DdNode *node);\nextern double Cudd_CountPathsToNonZero(DdNode *node);\nextern int Cudd_SupportIndices(DdManager * dd, DdNode * f, int **indices);\nextern DdNode * Cudd_Support(DdManager *dd, DdNode *f);\nextern int * Cudd_SupportIndex(DdManager *dd, DdNode *f);\nextern int Cudd_SupportSize(DdManager *dd, DdNode *f);\nextern int Cudd_VectorSupportIndices(DdManager * dd, DdNode ** F, int n, int **indices);\nextern DdNode * Cudd_VectorSupport(DdManager *dd, DdNode **F, int n);\nextern int * Cudd_VectorSupportIndex(DdManager *dd, DdNode **F, int n);\nextern int Cudd_VectorSupportSize(DdManager *dd, DdNode **F, int n);\nextern int Cudd_ClassifySupport(DdManager *dd, DdNode *f, DdNode *g, DdNode **common, DdNode **onlyF, DdNode **onlyG);\nextern int Cudd_CountLeaves(DdNode *node);\nextern int Cudd_bddPickOneCube(DdManager *ddm, DdNode *node, char *string);\nextern DdNode * Cudd_bddPickOneMinterm(DdManager *dd, DdNode *f, DdNode **vars, int n);\nextern DdNode ** Cudd_bddPickArbitraryMinterms(DdManager *dd, DdNode *f, DdNode **vars, int n, int k);\nextern DdNode * Cudd_SubsetWithMaskVars(DdManager *dd, DdNode *f, DdNode **vars, int nvars, DdNode **maskVars, int mvars);\nextern DdGen * Cudd_FirstCube(DdManager *dd, DdNode *f, int **cube, CUDD_VALUE_TYPE *value);\nextern int Cudd_NextCube(DdGen *gen, int **cube, CUDD_VALUE_TYPE *value);\nextern DdGen * Cudd_FirstPrime(DdManager *dd, DdNode *l, DdNode *u, int **cube);\nextern int Cudd_NextPrime(DdGen *gen, int **cube);\nextern DdNode * Cudd_bddComputeCube(DdManager *dd, DdNode **vars, int *phase, int n);\nextern DdNode * Cudd_addComputeCube(DdManager *dd, DdNode **vars, int *phase, int n);\nextern DdNode * Cudd_CubeArrayToBdd(DdManager *dd, int *array);\nextern int Cudd_BddToCubeArray(DdManager *dd, DdNode *cube, int *array);\nextern DdGen * Cudd_FirstNode(DdManager *dd, DdNode *f, DdNode **node);\nextern int Cudd_NextNode(DdGen *gen, DdNode **node);\nextern int Cudd_GenFree(DdGen *gen);\nextern int Cudd_IsGenEmpty(DdGen *gen);\nextern DdNode * Cudd_IndicesToCube(DdManager *dd, int *array, int n);\nextern void Cudd_PrintVersion(FILE *fp);\nextern double Cudd_AverageDistance(DdManager *dd);\nextern int32_t Cudd_Random(DdManager * dd);\nextern void Cudd_Srandom(DdManager * dd, int32_t seed);\nextern double Cudd_Density(DdManager *dd, DdNode *f, int nvars);\nextern void Cudd_OutOfMem(size_t size);\nextern void Cudd_OutOfMemSilent(size_t size);\nextern int Cudd_zddCount(DdManager *zdd, DdNode *P);\nextern double Cudd_zddCountDouble(DdManager *zdd, DdNode *P);\nextern DdNode * Cudd_zddProduct(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_zddUnateProduct(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_zddWeakDiv(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_zddDivide(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_zddWeakDivF(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_zddDivideF(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * Cudd_zddComplement(DdManager *dd, DdNode *node);\nextern DdNode * Cudd_zddIsop(DdManager *dd, DdNode *L, DdNode *U, DdNode **zdd_I);\nextern DdNode * Cudd_bddIsop(DdManager *dd, DdNode *L, DdNode *U);\nextern DdNode * Cudd_MakeBddFromZddCover(DdManager *dd, DdNode *node);\nextern int Cudd_zddDagSize(DdNode *p_node);\nextern double Cudd_zddCountMinterm(DdManager *zdd, DdNode *node, int path);\nextern void Cudd_zddPrintSubtable(DdManager *table);\nextern DdNode * Cudd_zddPortFromBdd(DdManager *dd, DdNode *B);\nextern DdNode * Cudd_zddPortToBdd(DdManager *dd, DdNode *f);\nextern int Cudd_zddReduceHeap(DdManager *table, Cudd_ReorderingType heuristic, int minsize);\nextern int Cudd_zddShuffleHeap(DdManager *table, int *permutation);\nextern DdNode * Cudd_zddIte(DdManager *dd, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * Cudd_zddUnion(DdManager *dd, DdNode *P, DdNode *Q);\nextern DdNode * Cudd_zddIntersect(DdManager *dd, DdNode *P, DdNode *Q);\nextern DdNode * Cudd_zddDiff(DdManager *dd, DdNode *P, DdNode *Q);\nextern DdNode * Cudd_zddDiffConst(DdManager *zdd, DdNode *P, DdNode *Q);\nextern DdNode * Cudd_zddSubset1(DdManager *dd, DdNode *P, int var);\nextern DdNode * Cudd_zddSubset0(DdManager *dd, DdNode *P, int var);\nextern DdNode * Cudd_zddChange(DdManager *dd, DdNode *P, int var);\nextern void Cudd_zddSymmProfile(DdManager *table, int lower, int upper);\nextern int Cudd_zddPrintMinterm(DdManager *zdd, DdNode *node);\nextern int Cudd_zddPrintCover(DdManager *zdd, DdNode *node);\nextern int Cudd_zddPrintDebug(DdManager *zdd, DdNode *f, int n, int pr);\nextern DdGen * Cudd_zddFirstPath(DdManager *zdd, DdNode *f, int **path);\nextern int Cudd_zddNextPath(DdGen *gen, int **path);\nextern char * Cudd_zddCoverPathToString(DdManager *zdd, int *path, char *str);\nextern DdNode * Cudd_zddSupport(DdManager * dd, DdNode * f);\nextern int Cudd_zddDumpDot(DdManager *dd, int n, DdNode **f, char const * const *inames, char const * const *onames, FILE *fp);\nextern int Cudd_bddSetPiVar(DdManager *dd, int index);\nextern int Cudd_bddSetPsVar(DdManager *dd, int index);\nextern int Cudd_bddSetNsVar(DdManager *dd, int index);\nextern int Cudd_bddIsPiVar(DdManager *dd, int index);\nextern int Cudd_bddIsPsVar(DdManager *dd, int index);\nextern int Cudd_bddIsNsVar(DdManager *dd, int index);\nextern int Cudd_bddSetPairIndex(DdManager *dd, int index, int pairIndex);\nextern int Cudd_bddReadPairIndex(DdManager *dd, int index);\nextern int Cudd_bddSetVarToBeGrouped(DdManager *dd, int index);\nextern int Cudd_bddSetVarHardGroup(DdManager *dd, int index);\nextern int Cudd_bddResetVarToBeGrouped(DdManager *dd, int index);\nextern int Cudd_bddIsVarToBeGrouped(DdManager *dd, int index);\nextern int Cudd_bddSetVarToBeUngrouped(DdManager *dd, int index);\nextern int Cudd_bddIsVarToBeUngrouped(DdManager *dd, int index);\nextern int Cudd_bddIsVarHardGroup(DdManager *dd, int index);\n#ifdef MTR_H_\nextern MtrNode * Cudd_ReadTree(DdManager *dd);\nextern void Cudd_SetTree(DdManager *dd, MtrNode *tree);\nextern void Cudd_FreeTree(DdManager *dd);\nextern MtrNode * Cudd_ReadZddTree(DdManager *dd);\nextern void Cudd_SetZddTree(DdManager *dd, MtrNode *tree);\nextern void Cudd_FreeZddTree(DdManager *dd);\nextern MtrNode * Cudd_MakeTreeNode(DdManager *dd, unsigned int low, unsigned int size, unsigned int type);\nextern MtrNode * Cudd_MakeZddTreeNode(DdManager *dd, unsigned int low, unsigned int size, unsigned int type);\n#endif\n\n#ifdef __cplusplus\n} /* end of extern \"C\" */\n#endif\n\n#endif /* CUDD_H_ */\n"
  },
  {
    "path": "cudd/cudd/cuddAPI.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Application interface functions.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void fixVarTree (MtrNode *treenode, int *perm, int size);\nstatic int addMultiplicityGroups (DdManager *dd, MtrNode *treenode, int multiplicity, char *vmask, char *lmask);\n\n/** \\endcond */\n\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Returns a new %ADD variable.\n\n  @details The new variable has an index equal to the largest previous\n  index plus 1.  An %ADD variable differs from a %BDD variable because\n  it points to the arithmetic zero, instead of having a complement\n  pointer to 1.\n\n  @return a pointer to the new variable if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddNewVar Cudd_addIthVar Cudd_addConst\n  Cudd_addNewVarAtLevel\n\n*/\nDdNode *\nCudd_addNewVar(\n  DdManager * dd)\n{\n    DdNode *res;\n\n    if ((unsigned int) dd->size >= CUDD_MAXINDEX - 1) {\n        dd->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n    do {\n\tdd->reordered = 0;\n\tres = cuddUniqueInter(dd,dd->size,DD_ONE(dd),DD_ZERO(dd));\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_addNewVar */\n\n\n/**\n  @brief Returns a new %ADD variable at a specified level.\n\n  @details The new variable has an index equal to the largest previous\n  index plus 1 and is positioned at the specified level in the order.\n\n  @return a pointer to the new variable if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addNewVar Cudd_addIthVar Cudd_bddNewVarAtLevel\n\n*/\nDdNode *\nCudd_addNewVarAtLevel(\n  DdManager * dd,\n  int  level)\n{\n    DdNode *res;\n\n    if ((unsigned int) dd->size >= CUDD_MAXINDEX - 1) {\n        dd->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n    if (level >= dd->size) return(Cudd_addIthVar(dd,level));\n    if (!cuddInsertSubtables(dd,1,level)) return(NULL);\n    do {\n\tdd->reordered = 0;\n\tres = cuddUniqueInter(dd,dd->size - 1,DD_ONE(dd),DD_ZERO(dd));\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_addNewVarAtLevel */\n\n\n/**\n  @brief Returns a new %BDD variable.\n\n  @details The new variable has an index equal to the largest previous\n  index plus 1.\n\n  @return a pointer to the new variable if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addNewVar Cudd_bddIthVar Cudd_bddNewVarAtLevel\n\n*/\nDdNode *\nCudd_bddNewVar(\n  DdManager * dd)\n{\n    DdNode *res;\n\n    if ((unsigned int) dd->size >= CUDD_MAXINDEX - 1) {\n        dd->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n    res = cuddUniqueInter(dd,dd->size,dd->one,Cudd_Not(dd->one));\n\n    return(res);\n\n} /* end of Cudd_bddNewVar */\n\n\n/**\n  @brief Returns a new %BDD variable at a specified level.\n\n  @details The new variable has an index equal to the largest previous\n  index plus 1 and is positioned at the specified level in the order.\n\n  @return a pointer to the new variable if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddNewVar Cudd_bddIthVar Cudd_addNewVarAtLevel\n\n*/\nDdNode *\nCudd_bddNewVarAtLevel(\n  DdManager * dd,\n  int  level)\n{\n    DdNode *res;\n\n    if ((unsigned int) dd->size >= CUDD_MAXINDEX - 1) {\n        dd->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n    if (level >= dd->size) return(Cudd_bddIthVar(dd,level));\n    if (!cuddInsertSubtables(dd,1,level)) return(NULL);\n    res = dd->vars[dd->size - 1];\n\n    return(res);\n\n} /* end of Cudd_bddNewVarAtLevel */\n\n\n/**\n  @brief Returns 1 if the given node is a %BDD variable; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nCudd_bddIsVar(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *one = DD_ONE(dd);\n    return(f != 0 && cuddT(f) == one && cuddE(f) == Cudd_Not(one));\n\n} /* end of Cudd_bddIsVar */\n\n\n/**\n  @brief Returns the %ADD variable with index i.\n\n  @details Retrieves the %ADD variable with index i if it already\n  exists, or creates a new %ADD variable.  An %ADD variable differs from\n  a %BDD variable because it points to the arithmetic zero, instead of\n  having a complement pointer to 1.\n\n  @return a pointer to the variable if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addNewVar Cudd_bddIthVar Cudd_addConst\n  Cudd_addNewVarAtLevel\n\n*/\nDdNode *\nCudd_addIthVar(\n  DdManager * dd,\n  int  i)\n{\n    DdNode *res;\n\n    if ((unsigned int) i >= CUDD_MAXINDEX - 1) {\n        dd->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n    do {\n\tdd->reordered = 0;\n\tres = cuddUniqueInter(dd,i,DD_ONE(dd),DD_ZERO(dd));\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_addIthVar */\n\n\n/**\n  @brief Returns the %BDD variable with index i.\n\n  @details Retrieves the %BDD variable with index i if it already\n  exists, or creates a new %BDD variable.\n\n  @return a pointer to the variable if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddNewVar Cudd_addIthVar Cudd_bddNewVarAtLevel\n  Cudd_ReadVars\n\n*/\nDdNode *\nCudd_bddIthVar(\n  DdManager * dd,\n  int  i)\n{\n    DdNode *res;\n\n    if ((unsigned int) i >= CUDD_MAXINDEX - 1) {\n        dd->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n    if (i < dd->size) {\n\tres = dd->vars[i];\n    } else {\n\tres = cuddUniqueInter(dd,i,dd->one,Cudd_Not(dd->one));\n    }\n\n    return(res);\n\n} /* end of Cudd_bddIthVar */\n\n\n/**\n  @brief Returns the %ZDD variable with index i.\n\n  @details Retrieves the %ZDD variable with index i if it already\n  exists, or creates a new %ZDD variable.\n\n  @return a pointer to the variable if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddIthVar Cudd_addIthVar\n\n*/\nDdNode *\nCudd_zddIthVar(\n  DdManager * dd,\n  int  i)\n{\n    DdNode *res;\n    DdNode *zvar;\n    DdNode *lower;\n    int j;\n\n    if ((unsigned int) i >= CUDD_MAXINDEX - 1) {\n        dd->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n    /* The i-th variable function has the following structure:\n    ** at the level corresponding to index i there is a node whose \"then\"\n    ** child points to the universe, and whose \"else\" child points to zero.\n    ** Above that level there are nodes with identical children.\n    */\n\n    /* First we build the node at the level of index i. */\n    lower = (i < dd->sizeZ - 1) ? dd->univ[dd->permZ[i]+1] : DD_ONE(dd);\n    do {\n\tdd->reordered = 0;\n\tzvar = cuddUniqueInterZdd(dd, i, lower, DD_ZERO(dd));\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    if (zvar == NULL)\n\treturn(NULL);\n    cuddRef(zvar);\n\n    /* Now we add the \"filler\" nodes above the level of index i. */\n    for (j = dd->permZ[i] - 1; j >= 0; j--) {\n\tdo {\n\t    dd->reordered = 0;\n\t    res = cuddUniqueInterZdd(dd, dd->invpermZ[j], zvar, zvar);\n\t} while (dd->reordered == 1);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd,zvar);\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDerefZdd(dd,zvar);\n\tzvar = res;\n    }\n    cuddDeref(zvar);\n    return(zvar);\n\n} /* end of Cudd_zddIthVar */\n\n\n/**\n  @brief Creates one or more %ZDD variables for each %BDD variable.\n\n  @details If some %ZDD variables already exist, only the missing\n  variables are created.  Parameter multiplicity allows the caller to\n  control how many variables are created for each %BDD variable in\n  existence. For instance, if ZDDs are used to represent covers, two\n  %ZDD variables are required for each %BDD variable.  The order of the\n  %BDD variables is transferred to the %ZDD variables. If a variable\n  group tree exists for the %BDD variables, a corresponding %ZDD\n  variable group tree is created by expanding the %BDD variable\n  tree. In any case, the %ZDD variables derived from the same %BDD\n  variable are merged in a %ZDD variable group. If a %ZDD variable group\n  tree exists, it is freed.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddNewVar Cudd_bddIthVar Cudd_bddNewVarAtLevel\n\n*/\nint\nCudd_zddVarsFromBddVars(\n  DdManager * dd /**< %DD manager */,\n  int multiplicity /**< how many %ZDD variables are created for each %BDD variable */)\n{\n    int res;\n    int i, j;\n    int allnew;\n    int *permutation;\n\n    if (multiplicity < 1) {\n        dd->errorCode = CUDD_INVALID_ARG;\n        return(0);\n    }\n    allnew = dd->sizeZ == 0;\n    if (dd->size * multiplicity > dd->sizeZ) {\n\tres = cuddResizeTableZdd(dd,dd->size * multiplicity - 1);\n\tif (res == 0) return(0);\n    }\n    /* Impose the order of the BDD variables to the ZDD variables. */\n    if (allnew) {\n\tfor (i = 0; i < dd->size; i++) {\n\t    for (j = 0; j < multiplicity; j++) {\n\t\tdd->permZ[i * multiplicity + j] =\n\t\t    dd->perm[i] * multiplicity + j;\n\t\tdd->invpermZ[dd->permZ[i * multiplicity + j]] =\n\t\t    i * multiplicity + j;\n\t    }\n\t}\n\tfor (i = 0; i < dd->sizeZ; i++) {\n\t    dd->univ[i]->index = dd->invpermZ[i];\n\t}\n    } else {\n\tpermutation = ALLOC(int,dd->sizeZ);\n\tif (permutation == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tfor (i = 0; i < dd->size; i++) {\n\t    for (j = 0; j < multiplicity; j++) {\n\t\tpermutation[i * multiplicity + j] =\n\t\t    dd->invperm[i] * multiplicity + j;\n\t    }\n\t}\n\tfor (i = dd->size * multiplicity; i < dd->sizeZ; i++) {\n\t    permutation[i] = i;\n\t}\n\tres = Cudd_zddShuffleHeap(dd, permutation);\n\tFREE(permutation);\n\tif (res == 0) return(0);\n    }\n    /* Copy and expand the variable group tree if it exists. */\n    if (dd->treeZ != NULL) {\n\tCudd_FreeZddTree(dd);\n    }\n    if (dd->tree != NULL) {\n\tdd->treeZ = Mtr_CopyTree(dd->tree, multiplicity);\n\tif (dd->treeZ == NULL) return(0);\n    } else if (multiplicity > 1) {\n\tdd->treeZ = Mtr_InitGroupTree(0, dd->sizeZ);\n\tif (dd->treeZ == NULL) return(0);\n\tdd->treeZ->index = dd->invpermZ[0];\n    }\n    /* Create groups for the ZDD variables derived from the same BDD variable.\n    */\n    if (multiplicity > 1) {\n\tchar *vmask, *lmask;\n\n\tvmask = ALLOC(char, dd->size);\n\tif (vmask == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tlmask =  ALLOC(char, dd->size);\n\tif (lmask == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tfor (i = 0; i < dd->size; i++) {\n\t    vmask[i] = lmask[i] = 0;\n\t}\n\tres = addMultiplicityGroups(dd,dd->treeZ,multiplicity,vmask,lmask);\n\tFREE(vmask);\n\tFREE(lmask);\n\tif (res == 0) return(0);\n    }\n    return(1);\n\n} /* end of Cudd_zddVarsFromBddVars */\n\n\n/**\n  @brief Returns the maximum possible index for a variable.\n\n  @sideeffect None\n*/\nunsigned int\nCudd_ReadMaxIndex(void)\n{\n    return(CUDD_MAXINDEX);\n\n} /* end of Cudd_ReadMaxIndex */\n\n\n/**\n  @brief Returns the %ADD for constant c.\n\n  @details Retrieves the %ADD for constant c if it already\n  exists, or creates a new %ADD.\n\n  @return a pointer to the %ADD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addNewVar Cudd_addIthVar\n\n*/\nDdNode *\nCudd_addConst(\n  DdManager * dd,\n  CUDD_VALUE_TYPE  c)\n{\n    return(cuddUniqueConst(dd,c));\n\n} /* end of Cudd_addConst */\n\n\n/**\n  @brief Returns 1 if the node is a constant node.\n\n  @details A constant node is not an internal node.  The pointer\n  passed to Cudd_IsConstant may be either regular or complemented.\n\n  @sideeffect none\n\n*/\nint Cudd_IsConstant(DdNode *node)\n{\n    return Cudd_Regular(node)->index == CUDD_CONST_INDEX;\n\n} /* end of Cudd_IsConstant */\n\n\n/**\n  @brief Returns 1 if a %DD node is not constant.\n\n  @details This function is useful to test the results of\n  Cudd_bddIteConstant, Cudd_addIteConstant, Cudd_addEvalConst. These\n  results may be a special value signifying non-constant. In the other\n  cases Cudd_IsConstant can be used.\n\n  @sideeffect None\n\n  @see Cudd_IsConstant Cudd_bddIteConstant Cudd_addIteConstant\n  Cudd_addEvalConst\n\n*/\nint\nCudd_IsNonConstant(\n  DdNode *f)\n{\n    return(f == DD_NON_CONSTANT || !Cudd_IsConstantInt(f));\n\n} /* end of Cudd_IsNonConstant */\n\n\n/**\n  @brief Returns the then child of an internal node.\n\n  @details If <code>node</code> is a constant node, the result is\n  unpredictable.\n\n  @sideeffect none\n\n  @see Cudd_E Cudd_V\n\n*/\nDdNode *\nCudd_T(DdNode *node)\n{\n    return Cudd_Regular(node)->type.kids.T;\n\n} /* end of Cudd_T */\n\n\n/**\n  @brief Returns the else child of an internal node.\n\n  @details If <code>node</code> is a constant node, the result is\n  unpredictable.\n\n  @sideeffect none\n\n  @see Cudd_T Cudd_V\n\n*/\nDdNode *\nCudd_E(DdNode *node)\n{\n    return Cudd_Regular(node)->type.kids.E;\n\n} /* end of Cudd_E */\n\n\n/**\n  @brief Returns the value of a constant node.\n\n  @details If <code>node</code> is an internal node, the result is\n  unpredictable.\n\n  @sideeffect none\n\n  @see Cudd_T Cudd_E\n\n*/\nCUDD_VALUE_TYPE\nCudd_V(DdNode *node)\n{\n    return Cudd_Regular(node)->type.value;\n\n} /* end of Cudd_V */\n\n\n/**\n  @brief Returns the start time of the manager.\n\n  @details This is initially set to the number of milliseconds since\n  the program started, but may be reset by the application.\n\n  @sideeffect None\n\n  @see Cudd_SetStartTime Cudd_ResetStartTime Cudd_ReadTimeLimit\n\n*/\nunsigned long\nCudd_ReadStartTime(\n  DdManager * unique)\n{\n    return unique->startTime;\n\n} /* end of Cudd_ReadStartTime */\n\n\n/**\n  @brief Returns the time elapsed since the start time of the manager.\n\n  @details The time is expressed in milliseconds.\n\n  @sideeffect None\n\n  @see Cudd_ReadStartTime Cudd_SetStartTime\n\n*/\nunsigned long\nCudd_ReadElapsedTime(\n  DdManager * unique)\n{\n  return util_cpu_time() - unique->startTime;\n\n} /* end of Cudd_ReadElapsedTime */\n\n\n/**\n  @brief Sets the start time of the manager.\n\n  @details The time must be expressed in milliseconds.\n\n  @sideeffect None\n\n  @see Cudd_ReadStartTime Cudd_ResetStartTime Cudd_ReadElapsedTime\n  Cudd_SetTimeLimit\n\n*/\nvoid\nCudd_SetStartTime(\n  DdManager * unique,\n  unsigned long st)\n{\n    unique->startTime = st;\n\n} /* end of Cudd_SetStartTime */\n\n\n/**\n  @brief Resets the start time of the manager.\n\n  @sideeffect None\n\n  @see Cudd_ReadStartTime Cudd_SetStartTime Cudd_SetTimeLimit\n\n*/\nvoid\nCudd_ResetStartTime(\n  DdManager * unique)\n{\n    unique->startTime = util_cpu_time();\n\n} /* end of Cudd_ResetStartTime */\n\n\n/**\n  @brief Returns the time limit for the manager.\n\n  @details This is initially set to a very large number, but may be\n  reset by the application.  The time is expressed in milliseconds.\n\n  @sideeffect None\n\n  @see Cudd_SetTimeLimit Cudd_UpdateTimeLimit Cudd_UnsetTimeLimit\n  Cudd_IncreaseTimeLimit Cudd_TimeLimited Cudd_ReadStartTime\n\n*/\nunsigned long\nCudd_ReadTimeLimit(\n  DdManager * unique)\n{\n    return unique->timeLimit;\n\n} /* end of Cudd_ReadTimeLimit */\n\n\n/**\n  @brief Sets the time limit for the manager.\n\n  @details The time must be expressed in milliseconds.\n\n  @return the old time limit.\n\n  @sideeffect None\n\n  @see Cudd_ReadTimeLimit Cudd_UnsetTimeLimit Cudd_UpdateTimeLimit\n  Cudd_IncreaseTimeLimit Cudd_TimeLimited Cudd_SetStartTime\n\n*/\nunsigned long\nCudd_SetTimeLimit(\n  DdManager * unique,\n  unsigned long tl)\n{\n    unsigned long ret = unique->timeLimit;\n    unique->timeLimit = tl;\n    return(ret);\n\n} /* end of Cudd_SetTimeLimit */\n\n\n/**\n  @brief Updates the time limit for the manager.\n\n  @details Updates the time limit for the manager by subtracting the\n  elapsed time from it.\n\n  @sideeffect None\n\n  @see Cudd_ReadTimeLimit Cudd_SetTimeLimit Cudd_UnsetTimeLimit\n  Cudd_IncreaseTimeLimit Cudd_TimeLimited Cudd_SetStartTime\n\n*/\nvoid\nCudd_UpdateTimeLimit(\n  DdManager * unique)\n{\n    unsigned long elapsed;\n    if (unique->timeLimit == ~0UL)\n        return;\n    elapsed = util_cpu_time() - unique->startTime;\n    if (unique->timeLimit >= elapsed) {\n        unique->timeLimit -= elapsed;\n    } else {\n        unique->timeLimit = 0;\n    }\n\n} /* end of Cudd_UpdateTimeLimit */\n\n\n/**\n  @brief Increases the time limit for the manager.\n\n  @details The time increase must be expressed in milliseconds.\n\n  @sideeffect None\n\n  @see Cudd_ReadTimeLimit Cudd_SetTimeLimit Cudd_UnsetTimeLimit\n  Cudd_UpdateTimeLimit Cudd_TimeLimited Cudd_SetStartTime\n\n*/\nvoid\nCudd_IncreaseTimeLimit(\n  DdManager * unique,\n  unsigned long increase)\n{\n    if (unique->timeLimit == ~0UL)\n        unique->timeLimit = increase;\n    else\n        unique->timeLimit += increase;\n\n} /* end of Cudd_IncreaseTimeLimit */\n\n\n/**\n  @brief Unsets the time limit for the manager.\n\n  @details Actually, sets it to a very large value.\n\n  @sideeffect None\n\n  @see Cudd_ReadTimeLimit Cudd_SetTimeLimit Cudd_UpdateTimeLimit\n  Cudd_IncreaseTimeLimit Cudd_TimeLimited Cudd_SetStartTime\n\n*/\nvoid\nCudd_UnsetTimeLimit(\n  DdManager * unique)\n{\n    unique->timeLimit = ~0UL;\n\n} /* end of Cudd_UnsetTimeLimit */\n\n\n/**\n  @brief Returns true if the time limit for the manager is set.\n\n  @sideeffect None\n\n  @see Cudd_ReadTimeLimit Cudd_SetTimeLimit Cudd_UpdateTimeLimit\n  Cudd_UnsetTimeLimit Cudd_IncreaseTimeLimit\n\n*/\nint\nCudd_TimeLimited(\n  DdManager * unique)\n{\n    return unique->timeLimit != ~0UL;\n\n} /* end of Cudd_TimeLimited */\n\n\n/**\n  @brief Installs a termination callback.\n\n  @details Registers a callback function that is called from time\n  to time to decide whether computation should be abandoned.\n\n  @sideeffect None\n\n  @see Cudd_UnregisterTerminationCallback\n\n*/\nvoid\nCudd_RegisterTerminationCallback(\n  DdManager *unique,\n  DD_THFP callback,\n  void * callback_arg)\n{\n    unique->terminationCallback = callback;\n    unique->tcbArg = callback_arg;\n\n} /* end of Cudd_RegisterTerminationCallback */\n\n\n/**\n  @brief Unregisters a termination callback.\n\n  @sideeffect None\n\n  @see Cudd_RegisterTerminationCallback\n\n*/\nvoid\nCudd_UnregisterTerminationCallback(\n  DdManager *unique)\n{\n    unique->terminationCallback = NULL;\n    unique->tcbArg = NULL;\n\n}  /* end of Cudd_UnregisterTerminationCallback */\n\n\n/**\n  @brief Installs an out-of-memory callback.\n\n  @details Registers a callback function that is called when\n  a discretionary memory allocation fails.\n\n  @return the old callback function.\n\n  @sideeffect None\n\n  @see Cudd_UnregisterOutOfMemoryCallback Cudd_OutOfMem Cudd_OutOfMemSilent\n\n*/\nDD_OOMFP\nCudd_RegisterOutOfMemoryCallback(\n  DdManager *unique,\n  DD_OOMFP callback)\n{\n  DD_OOMFP ret = unique->outOfMemCallback;\n  unique->outOfMemCallback = callback;\n  return(ret);\n\n} /* end of Cudd_RegisterOutOfMemoryCallback */\n\n\n/**\n  @brief Unregister an out-of-memory callback.\n\n  @sideeffect None\n\n  @see Cudd_RegisterOutOfMemoryCallback Cudd_OutOfMem Cudd_OutOfMemSilent\n\n*/\nvoid\nCudd_UnregisterOutOfMemoryCallback(\n  DdManager *unique)\n{\n  unique->outOfMemCallback = Cudd_OutOfMemSilent;\n\n} /* end of Cudd_UnregisterOutOfMemoryCallback */\n\n\n/**\n  @brief Register a timeout handler function.\n\n  @details To unregister a handler, register a NULL pointer.\n\n  @sideeffect None\n\n  @see Cudd_ReadTimeoutHandler\n*/\nvoid\nCudd_RegisterTimeoutHandler(\n  DdManager *unique,\n  DD_TOHFP handler,\n  void *arg)\n{\n    unique->timeoutHandler = handler;\n    unique->tohArg = arg;\n\n} /* end of Cudd_RegisterTimeoutHandler */\n\n\n/**\n  @brief Read the current timeout handler function.\n\n  @sideeffect If argp is non-null, the second argument to\n  the handler is written to the location it points to.\n\n  @see Cudd_RegisterTimeoutHandler\n*/\nDD_TOHFP\nCudd_ReadTimeoutHandler(\n  DdManager *unique,\n  void **argp)\n{\n    if (argp != NULL)\n        *argp = unique->tohArg;\n    return unique->timeoutHandler;\n\n} /* end of Cudd_ReadTimeoutHandler */\n\n\n/**\n  @brief Enables automatic dynamic reordering of BDDs and ADDs.\n\n  @details Parameter method is used to determine the method used for\n  reordering. If CUDD_REORDER_SAME is passed, the method is unchanged.\n\n  @sideeffect None\n\n  @see Cudd_AutodynDisable Cudd_ReorderingStatus\n  Cudd_AutodynEnableZdd\n\n*/\nvoid\nCudd_AutodynEnable(\n  DdManager * unique,\n  Cudd_ReorderingType  method)\n{\n    unique->autoDyn = 1;\n    if (method != CUDD_REORDER_SAME) {\n\tunique->autoMethod = method;\n    }\n#ifndef DD_NO_DEATH_ROW\n    /* If reordering is enabled, using the death row causes too many\n    ** invocations. Hence, we shrink the death row to just one entry.\n    */\n    cuddClearDeathRow(unique);\n    unique->deathRowDepth = 1;\n    unique->deadMask = unique->deathRowDepth - 1;\n    if ((unsigned) unique->nextDead > unique->deadMask) {\n\tunique->nextDead = 0;\n    }\n    unique->deathRow = REALLOC(DdNodePtr, unique->deathRow,\n\tunique->deathRowDepth);\n#endif\n    return;\n\n} /* end of Cudd_AutodynEnable */\n\n\n/**\n  @brief Disables automatic dynamic reordering.\n\n  @sideeffect None\n\n  @see Cudd_AutodynEnable Cudd_ReorderingStatus\n  Cudd_AutodynDisableZdd\n\n*/\nvoid\nCudd_AutodynDisable(\n  DdManager * unique)\n{\n    unique->autoDyn = 0;\n    return;\n\n} /* end of Cudd_AutodynDisable */\n\n\n/**\n  @brief Reports the status of automatic dynamic reordering of BDDs\n  and ADDs.\n\n  @details The location pointed by parameter method is set to\n  the reordering method currently selected if method is non-null.\n\n  @return 1 if automatic reordering is enabled; 0 otherwise.\n\n  @sideeffect The location pointed by parameter method is set to the\n  reordering method currently selected if method is non-null.\n\n  @see Cudd_AutodynEnable Cudd_AutodynDisable\n  Cudd_ReorderingStatusZdd\n\n*/\nint\nCudd_ReorderingStatus(\n  DdManager * unique,\n  Cudd_ReorderingType * method)\n{\n    if (method)\n\t*method = unique->autoMethod;\n    return(unique->autoDyn);\n\n} /* end of Cudd_ReorderingStatus */\n\n\n/**\n  @brief Enables automatic dynamic reordering of ZDDs.\n\n  @details Parameter method is used to determine the method used for\n  reordering ZDDs.  If CUDD_REORDER_SAME is passed, the method is\n  unchanged.\n\n  @sideeffect None\n\n  @see Cudd_AutodynDisableZdd Cudd_ReorderingStatusZdd\n  Cudd_AutodynEnable\n\n*/\nvoid\nCudd_AutodynEnableZdd(\n  DdManager * unique,\n  Cudd_ReorderingType method)\n{\n    unique->autoDynZ = 1;\n    if (method != CUDD_REORDER_SAME) {\n\tunique->autoMethodZ = method;\n    }\n    return;\n\n} /* end of Cudd_AutodynEnableZdd */\n\n\n/**\n  @brief Disables automatic dynamic reordering of ZDDs.\n\n  @sideeffect None\n\n  @see Cudd_AutodynEnableZdd Cudd_ReorderingStatusZdd\n  Cudd_AutodynDisable\n\n*/\nvoid\nCudd_AutodynDisableZdd(\n  DdManager * unique)\n{\n    unique->autoDynZ = 0;\n    return;\n\n} /* end of Cudd_AutodynDisableZdd */\n\n\n/**\n  @brief Reports the status of automatic dynamic reordering of ZDDs.\n\n  @details Parameter method is set to the %ZDD reordering method currently\n  selected.\n\n  @return 1 if automatic reordering is enabled; 0 otherwise.\n\n  @sideeffect Parameter method is set to the %ZDD reordering method currently\n  selected.\n\n  @see Cudd_AutodynEnableZdd Cudd_AutodynDisableZdd\n  Cudd_ReorderingStatus\n\n*/\nint\nCudd_ReorderingStatusZdd(\n  DdManager * unique,\n  Cudd_ReorderingType * method)\n{\n    *method = unique->autoMethodZ;\n    return(unique->autoDynZ);\n\n} /* end of Cudd_ReorderingStatusZdd */\n\n\n/**\n  @brief Tells whether the realignment of %ZDD order to %BDD order is\n  enabled.\n\n  @return 1 if the realignment of %ZDD order to %BDD order is enabled; 0\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddRealignEnable Cudd_zddRealignDisable\n  Cudd_bddRealignEnable Cudd_bddRealignDisable\n\n*/\nint\nCudd_zddRealignmentEnabled(\n  DdManager * unique)\n{\n    return(unique->realign);\n\n} /* end of Cudd_zddRealignmentEnabled */\n\n\n/**\n  @brief Enables realignment of %ZDD order to %BDD order.\n\n  @details Enables realignment of the %ZDD variable order to the\n  %BDD variable order after the BDDs and ADDs have been reordered.  The\n  number of %ZDD variables must be a multiple of the number of %BDD\n  variables for realignment to make sense. If this condition is not met,\n  Cudd_ReduceHeap will return 0. Let <code>M</code> be the\n  ratio of the two numbers. For the purpose of realignment, the %ZDD\n  variables from <code>M*i</code> to <code>(M+1)*i-1</code> are\n  reagarded as corresponding to %BDD variable <code>i</code>. Realignment\n  is initially disabled.\n\n  @sideeffect None\n\n  @see Cudd_ReduceHeap Cudd_zddRealignDisable\n  Cudd_zddRealignmentEnabled Cudd_bddRealignDisable\n  Cudd_bddRealignmentEnabled\n\n*/\nvoid\nCudd_zddRealignEnable(\n  DdManager * unique)\n{\n    unique->realign = 1;\n    return;\n\n} /* end of Cudd_zddRealignEnable */\n\n\n/**\n  @brief Disables realignment of %ZDD order to %BDD order.\n\n  @sideeffect None\n\n  @see Cudd_zddRealignEnable Cudd_zddRealignmentEnabled\n  Cudd_bddRealignEnable Cudd_bddRealignmentEnabled\n\n*/\nvoid\nCudd_zddRealignDisable(\n  DdManager * unique)\n{\n    unique->realign = 0;\n    return;\n\n} /* end of Cudd_zddRealignDisable */\n\n\n/**\n  @brief Tells whether the realignment of %BDD order to %ZDD order is\n  enabled.\n\n  @return 1 if the realignment of %BDD order to %ZDD order is enabled; 0\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddRealignEnable Cudd_bddRealignDisable\n  Cudd_zddRealignEnable Cudd_zddRealignDisable\n\n*/\nint\nCudd_bddRealignmentEnabled(\n  DdManager * unique)\n{\n    return(unique->realignZ);\n\n} /* end of Cudd_bddRealignmentEnabled */\n\n\n/**\n  @brief Enables realignment of %BDD order to %ZDD order.\n\n  @details Enables realignment of the %BDD variable order to the\n  %ZDD variable order after the ZDDs have been reordered.  The\n  number of %ZDD variables must be a multiple of the number of %BDD\n  variables for realignment to make sense. If this condition is not met,\n  Cudd_zddReduceHeap will return 0. Let <code>M</code> be the\n  ratio of the two numbers. For the purpose of realignment, the %ZDD\n  variables from <code>M*i</code> to <code>(M+1)*i-1</code> are\n  reagarded as corresponding to %BDD variable <code>i</code>. Realignment\n  is initially disabled.\n\n  @sideeffect None\n\n  @see Cudd_zddReduceHeap Cudd_bddRealignDisable\n  Cudd_bddRealignmentEnabled Cudd_zddRealignDisable\n  Cudd_zddRealignmentEnabled\n\n*/\nvoid\nCudd_bddRealignEnable(\n  DdManager * unique)\n{\n    unique->realignZ = 1;\n    return;\n\n} /* end of Cudd_bddRealignEnable */\n\n\n/**\n  @brief Disables realignment of %ZDD order to %BDD order.\n\n  @sideeffect None\n\n  @see Cudd_bddRealignEnable Cudd_bddRealignmentEnabled\n  Cudd_zddRealignEnable Cudd_zddRealignmentEnabled\n\n*/\nvoid\nCudd_bddRealignDisable(\n  DdManager * unique)\n{\n    unique->realignZ = 0;\n    return;\n\n} /* end of Cudd_bddRealignDisable */\n\n\n/**\n  @brief Returns the one constant of the manager.\n\n  @details The one constant is common to ADDs and BDDs.\n\n  @sideeffect None\n\n  @see Cudd_ReadZero Cudd_ReadLogicZero Cudd_ReadZddOne\n\n*/\nDdNode *\nCudd_ReadOne(\n  DdManager * dd)\n{\n    return(dd->one);\n\n} /* end of Cudd_ReadOne */\n\n\n/**\n  @brief Returns the %ZDD for the constant 1 function.\n\n  @details The representation of the constant 1 function as a %ZDD\n  depends on how many variables it (nominally) depends on. The index\n  of the topmost variable in the support is given as argument\n  <code>i</code>.\n\n  @sideeffect None\n\n  @see Cudd_ReadOne\n\n*/\nDdNode *\nCudd_ReadZddOne(\n  DdManager * dd,\n  int  i)\n{\n    if (i < 0)\n\treturn(NULL);\n    return(i < dd->sizeZ ? dd->univ[i] : DD_ONE(dd));\n\n} /* end of Cudd_ReadZddOne */\n\n\n\n/**\n  @brief Returns the zero constant of the manager.\n\n  @details The zero constant is the arithmetic zero, rather than the\n  logic zero. The latter is the complement of the one constant.\n\n  @sideeffect None\n\n  @see Cudd_ReadOne Cudd_ReadLogicZero\n\n*/\nDdNode *\nCudd_ReadZero(\n  DdManager * dd)\n{\n    return(DD_ZERO(dd));\n\n} /* end of Cudd_ReadZero */\n\n\n/**\n  @brief Returns the logic zero constant of the manager.\n\n  @details The logic zero constant is the complement of the one\n  constant, and is distinct from the arithmetic zero.\n\n  @sideeffect None\n\n  @see Cudd_ReadOne Cudd_ReadZero\n\n*/\nDdNode *\nCudd_ReadLogicZero(\n  DdManager * dd)\n{\n    return(Cudd_Not(DD_ONE(dd)));\n\n} /* end of Cudd_ReadLogicZero */\n\n\n/**\n  @brief Reads the plus-infinity constant from the manager.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_ReadPlusInfinity(\n  DdManager * dd)\n{\n    return(dd->plusinfinity);\n\n} /* end of Cudd_ReadPlusInfinity */\n\n\n/**\n  @brief Reads the minus-infinity constant from the manager.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_ReadMinusInfinity(\n  DdManager * dd)\n{\n    return(dd->minusinfinity);\n\n} /* end of Cudd_ReadMinusInfinity */\n\n\n/**\n  @brief Reads the background constant of the manager.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_ReadBackground(\n  DdManager * dd)\n{\n    return(dd->background);\n\n} /* end of Cudd_ReadBackground */\n\n\n/**\n  @brief Sets the background constant of the manager.\n\n  @details It assumes that the DdNode pointer bck is already\n  referenced.\n\n  @sideeffect None\n\n*/\nvoid\nCudd_SetBackground(\n  DdManager * dd,\n  DdNode * bck)\n{\n    dd->background = bck;\n\n} /* end of Cudd_SetBackground */\n\n\n/**\n  @brief Reads the number of slots in the cache.\n\n  @sideeffect None\n\n  @see Cudd_ReadCacheUsedSlots\n\n*/\nunsigned int\nCudd_ReadCacheSlots(\n  DdManager * dd)\n{\n    return(dd->cacheSlots);\n\n} /* end of Cudd_ReadCacheSlots */\n\n\n/**\n  @brief Reads the fraction of used slots in the cache.\n\n  @details The unused slots are those in which no valid data is\n  stored. Garbage collection, variable reordering, and cache resizing\n  may cause used slots to become unused.\n\n  @sideeffect None\n\n  @see Cudd_ReadCacheSlots\n\n*/\ndouble\nCudd_ReadCacheUsedSlots(\n  DdManager * dd)\n{\n    size_t used = 0;\n    int slots = dd->cacheSlots;\n    DdCache *cache = dd->cache;\n    int i;\n\n    for (i = 0; i < slots; i++) {\n\tused += cache[i].h != 0;\n    }\n\n    return((double)used / (double) dd->cacheSlots);\n\n} /* end of Cudd_ReadCacheUsedSlots */\n\n\n/**\n  @brief Returns the number of cache look-ups.\n\n  @sideeffect None\n\n  @see Cudd_ReadCacheHits\n\n*/\ndouble\nCudd_ReadCacheLookUps(\n  DdManager * dd)\n{\n    return(dd->cacheHits + dd->cacheMisses +\n\t   dd->totCachehits + dd->totCacheMisses);\n\n} /* end of Cudd_ReadCacheLookUps */\n\n\n/**\n  @brief Returns the number of cache hits.\n\n  @sideeffect None\n\n  @see Cudd_ReadCacheLookUps\n\n*/\ndouble\nCudd_ReadCacheHits(\n  DdManager * dd)\n{\n    return(dd->cacheHits + dd->totCachehits);\n\n} /* end of Cudd_ReadCacheHits */\n\n\n/**\n  @brief Returns the number of recursive calls.\n\n  @details Returns the number of recursive calls if the package is\n  compiled with DD_COUNT defined.\n\n  @sideeffect None\n\n*/\ndouble\nCudd_ReadRecursiveCalls(\n  DdManager * dd)\n{\n#ifdef DD_COUNT\n    return(dd->recursiveCalls);\n#else\n    (void) dd; /* avoid warning */\n    return(-1.0);\n#endif\n\n} /* end of Cudd_ReadRecursiveCalls */\n\n\n\n/**\n  @brief Reads the hit rate that causes resizinig of the computed\n  table.\n\n  @sideeffect None\n\n  @see Cudd_SetMinHit\n\n*/\nunsigned int\nCudd_ReadMinHit(\n  DdManager * dd)\n{\n    /* Internally, the package manipulates the ratio of hits to\n    ** misses instead of the ratio of hits to accesses. */\n    return((unsigned int) (0.5 + 100 * dd->minHit / (1 + dd->minHit)));\n\n} /* end of Cudd_ReadMinHit */\n\n\n/**\n  @brief Sets the hit rate that causes resizinig of the computed\n  table.\n\n  @details Sets the minHit parameter of the manager. This\n  parameter controls the resizing of the computed table. If the hit\n  rate is larger than the specified value, and the cache is not\n  already too large, then its size is doubled.\n\n  @sideeffect None\n\n  @see Cudd_ReadMinHit\n\n*/\nvoid\nCudd_SetMinHit(\n  DdManager * dd,\n  unsigned int hr)\n{\n    /* Internally, the package manipulates the ratio of hits to\n    ** misses instead of the ratio of hits to accesses. */\n    dd->minHit = (double) hr / (100.0 - (double) hr);\n\n} /* end of Cudd_SetMinHit */\n\n\n/**\n  @brief Reads the looseUpTo parameter of the manager.\n\n  @sideeffect None\n\n  @see Cudd_SetLooseUpTo Cudd_ReadMinHit Cudd_ReadMinDead\n\n*/\nunsigned int\nCudd_ReadLooseUpTo(\n  DdManager * dd)\n{\n    return(dd->looseUpTo);\n\n} /* end of Cudd_ReadLooseUpTo */\n\n\n/**\n  @brief Sets the looseUpTo parameter of the manager.\n\n  @details This parameter of the manager controls the threshold beyond\n  which no fast growth of the unique table is allowed. The threshold\n  is given as a number of slots. If the value passed to this function\n  is 0, the function determines a suitable value based on the\n  available memory.\n\n  @sideeffect None\n\n  @see Cudd_ReadLooseUpTo Cudd_SetMinHit\n\n*/\nvoid\nCudd_SetLooseUpTo(\n  DdManager * dd,\n  unsigned int lut)\n{\n    if (lut == 0) {\n\tunsigned long datalimit = getSoftDataLimit();\n\tlut = (unsigned int) (datalimit / (sizeof(DdNode) *\n\t\t\t\t\t   DD_MAX_LOOSE_FRACTION));\n    }\n    dd->looseUpTo = lut;\n\n} /* end of Cudd_SetLooseUpTo */\n\n\n/**\n  @brief Returns the soft limit for the cache size.\n\n  @sideeffect None\n\n  @see Cudd_ReadMaxCacheHard\n\n*/\nunsigned int\nCudd_ReadMaxCache(\n  DdManager * dd)\n{\n    return(2 * dd->cacheSlots + dd->cacheSlack);\n\n} /* end of Cudd_ReadMaxCache */\n\n\n/**\n  @brief Reads the maxCacheHard parameter of the manager.\n\n  @sideeffect None\n\n  @see Cudd_SetMaxCacheHard Cudd_ReadMaxCache\n\n*/\nunsigned int\nCudd_ReadMaxCacheHard(\n  DdManager * dd)\n{\n    return(dd->maxCacheHard);\n\n} /* end of Cudd_ReadMaxCache */\n\n\n/**\n  @brief Sets the maxCacheHard parameter of the manager.\n\n  @details The cache cannot grow larger than maxCacheHard\n  entries. This parameter allows an application to control the\n  trade-off of memory versus speed. If the value passed to this\n  function is 0, the function determines a suitable maximum cache size\n  based on the available memory.\n\n  @sideeffect None\n\n  @see Cudd_ReadMaxCacheHard Cudd_SetMaxCache\n\n*/\nvoid\nCudd_SetMaxCacheHard(\n  DdManager * dd,\n  unsigned int mc)\n{\n    if (mc == 0) {\n\tunsigned long datalimit = getSoftDataLimit();\n\tmc = (unsigned int) (datalimit / (sizeof(DdCache) *\n\t\t\t\t\t  DD_MAX_CACHE_FRACTION));\n    }\n    dd->maxCacheHard = mc;\n\n} /* end of Cudd_SetMaxCacheHard */\n\n\n/**\n  @brief Returns the number of %BDD variables in existance.\n\n  @sideeffect None\n\n  @see Cudd_ReadZddSize\n\n*/\nint\nCudd_ReadSize(\n  DdManager * dd)\n{\n    return(dd->size);\n\n} /* end of Cudd_ReadSize */\n\n\n/**\n  @brief Returns the number of %ZDD variables in existance.\n\n  @sideeffect None\n\n  @see Cudd_ReadSize\n\n*/\nint\nCudd_ReadZddSize(\n  DdManager * dd)\n{\n    return(dd->sizeZ);\n\n} /* end of Cudd_ReadZddSize */\n\n\n/**\n  @brief Returns the total number of slots of the unique table.\n\n  @details This number is mainly for diagnostic purposes.\n\n  @sideeffect None\n\n*/\nunsigned int\nCudd_ReadSlots(\n  DdManager * dd)\n{\n    return(dd->slots);\n\n} /* end of Cudd_ReadSlots */\n\n\n/**\n  @brief Reads the fraction of used slots in the unique table.\n\n  @details The unused slots are those in which no valid data is\n  stored. Garbage collection, variable reordering, and subtable\n  resizing may cause used slots to become unused.\n\n  @sideeffect None\n\n  @see Cudd_ReadSlots\n\n*/\ndouble\nCudd_ReadUsedSlots(\n  DdManager * dd)\n{\n    size_t used = 0;\n    int i, j;\n    int size = dd->size;\n    DdNodePtr *nodelist;\n    DdSubtable *subtable;\n    DdNode *node;\n    DdNode *sentinel = &(dd->sentinel);\n\n    /* Scan each BDD/ADD subtable. */\n    for (i = 0; i < size; i++) {\n\tsubtable = &(dd->subtables[i]);\n\tnodelist = subtable->nodelist;\n\tfor (j = 0; (unsigned) j < subtable->slots; j++) {\n\t    node = nodelist[j];\n\t    if (node != sentinel) {\n\t\tused++;\n\t    }\n\t}\n    }\n\n    /* Scan the ZDD subtables. */\n    size = dd->sizeZ;\n\n    for (i = 0; i < size; i++) {\n\tsubtable = &(dd->subtableZ[i]);\n\tnodelist = subtable->nodelist;\n\tfor (j = 0; (unsigned) j < subtable->slots; j++) {\n\t    node = nodelist[j];\n\t    if (node != NULL) {\n\t\tused++;\n\t    }\n\t}\n    }\n\n    /* Constant table. */\n    subtable = &(dd->constants);\n    nodelist = subtable->nodelist;\n    for (j = 0; (unsigned) j < subtable->slots; j++) {\n\tnode = nodelist[j];\n\tif (node != NULL) {\n\t    used++;\n\t}\n    }\n\n    return((double)used / (double) dd->slots);\n\n} /* end of Cudd_ReadUsedSlots */\n\n\n/**\n  @brief Computes the expected fraction of used slots in the unique\n  table.\n\n  @details This expected value is based on the assumption that the\n  hash function distributes the keys randomly; it can be compared with\n  the result of Cudd_ReadUsedSlots to monitor the performance of the\n  unique table hash function.\n\n  @sideeffect None\n\n  @see Cudd_ReadSlots Cudd_ReadUsedSlots\n\n*/\ndouble\nCudd_ExpectedUsedSlots(\n  DdManager * dd)\n{\n    int i;\n    int size = dd->size;\n    DdSubtable *subtable;\n    double empty = 0.0;\n\n    /* To each subtable we apply the corollary to Theorem 8.5 (occupancy\n    ** distribution) from Sedgewick and Flajolet's Analysis of Algorithms.\n    ** The corollary says that for a table with M buckets and a load ratio\n    ** of r, the expected number of empty buckets is asymptotically given\n    ** by M * exp(-r).\n    */\n\n    /* Scan each BDD/ADD subtable. */\n    for (i = 0; i < size; i++) {\n\tsubtable = &(dd->subtables[i]);\n\tempty += (double) subtable->slots *\n\t    exp(-(double) subtable->keys / (double) subtable->slots);\n    }\n\n    /* Scan the ZDD subtables. */\n    size = dd->sizeZ;\n\n    for (i = 0; i < size; i++) {\n\tsubtable = &(dd->subtableZ[i]);\n\tempty += (double) subtable->slots *\n\t    exp(-(double) subtable->keys / (double) subtable->slots);\n    }\n\n    /* Constant table. */\n    subtable = &(dd->constants);\n    empty += (double) subtable->slots *\n\texp(-(double) subtable->keys / (double) subtable->slots);\n\n    return(1.0 - empty / (double) dd->slots);\n\n} /* end of Cudd_ExpectedUsedSlots */\n\n\n/**\n  @brief Returns the number of nodes in the unique table.\n\n  @details Returns the total number of nodes currently in the unique\n  table, including the dead nodes.\n\n  @sideeffect None\n\n  @see Cudd_ReadDead\n\n*/\nunsigned int\nCudd_ReadKeys(\n  DdManager * dd)\n{\n    return(dd->keys);\n\n} /* end of Cudd_ReadKeys */\n\n\n/**\n  @brief Returns the number of dead nodes in the unique table.\n\n  @sideeffect None\n\n  @see Cudd_ReadKeys\n\n*/\nunsigned int\nCudd_ReadDead(\n  DdManager * dd)\n{\n    return(dd->dead);\n\n} /* end of Cudd_ReadDead */\n\n\n/**\n  @brief Reads the minDead parameter of the manager.\n\n  @details The minDead parameter is used by the package to decide\n  whether to collect garbage or resize a subtable of the unique table\n  when the subtable becomes too full. The application can indirectly\n  control the value of minDead by setting the looseUpTo parameter.\n\n  @sideeffect None\n\n  @see Cudd_ReadDead Cudd_ReadLooseUpTo Cudd_SetLooseUpTo\n\n*/\nunsigned int\nCudd_ReadMinDead(\n  DdManager * dd)\n{\n    return(dd->minDead);\n\n} /* end of Cudd_ReadMinDead */\n\n\n/**\n  @brief Returns the number of times reordering has occurred.\n\n  @details The number includes both the calls to Cudd_ReduceHeap from\n  the application program and those automatically performed by the\n  package. However, calls that do not even initiate reordering are not\n  counted. A call may not initiate reordering if there are fewer than\n  minsize live nodes in the manager, or if CUDD_REORDER_NONE is specified\n  as reordering method. The calls to Cudd_ShuffleHeap are not counted.\n\n  @sideeffect None\n\n  @see Cudd_ReduceHeap Cudd_ReadReorderingTime\n\n*/\nunsigned int\nCudd_ReadReorderings(\n  DdManager * dd)\n{\n    return(dd->reorderings);\n\n} /* end of Cudd_ReadReorderings */\n\n\n/**\n  @brief Returns the maximum number of times reordering may be invoked.\n\n  @sideeffect None\n\n  @see Cudd_ReadReorderings Cudd_SetMaxReorderings Cudd_ReduceHeap\n\n*/\nunsigned int\nCudd_ReadMaxReorderings(\n  DdManager * dd)\n{\n    return(dd->maxReorderings);\n\n} /* end of Cudd_ReadMaxReorderings */\n\n\n/**\n  @brief Sets the maximum number of times reordering may be invoked.\n\n  @details The default value is (practically) infinite.\n\n  @sideeffect None\n\n  @see Cudd_ReadReorderings Cudd_ReadMaxReorderings Cudd_ReduceHeap\n\n*/\nvoid\nCudd_SetMaxReorderings(\n  DdManager * dd, unsigned int mr)\n{\n    dd->maxReorderings = mr;\n\n} /* end of Cudd_SetMaxReorderings */\n\n\n/**\n  @brief Returns the time spent in reordering.\n\n  @details Returns the number of milliseconds spent reordering\n  variables since the manager was initialized. The time spent in collecting\n  garbage before reordering is included.\n\n  @sideeffect None\n\n  @see Cudd_ReadReorderings\n\n*/\nlong\nCudd_ReadReorderingTime(\n  DdManager * dd)\n{\n    return(dd->reordTime);\n\n} /* end of Cudd_ReadReorderingTime */\n\n\n/**\n  @brief Returns the number of times garbage collection has occurred.\n\n  @details The number includes both the calls from reordering\n  procedures and those caused by requests to create new nodes.\n\n  @sideeffect None\n\n  @see Cudd_ReadGarbageCollectionTime\n\n*/\nint\nCudd_ReadGarbageCollections(\n  DdManager * dd)\n{\n    return(dd->garbageCollections);\n\n} /* end of Cudd_ReadGarbageCollections */\n\n\n/**\n  @brief Returns the time spent in garbage collection.\n\n  @details Returns the number of milliseconds spent doing garbage\n  collection since the manager was initialized.\n\n  @sideeffect None\n\n  @see Cudd_ReadGarbageCollections\n\n*/\nlong\nCudd_ReadGarbageCollectionTime(\n  DdManager * dd)\n{\n    return(dd->GCTime);\n\n} /* end of Cudd_ReadGarbageCollectionTime */\n\n\n/**\n  @brief Returns the number of nodes freed.\n\n  @details Returns the number of nodes returned to the free list if the\n  keeping of this statistic is enabled; -1 otherwise. This statistic is\n  enabled only if the package is compiled with DD_STATS defined.\n\n  @sideeffect None\n\n  @see Cudd_ReadNodesDropped\n\n*/\ndouble\nCudd_ReadNodesFreed(\n  DdManager * dd)\n{\n#ifdef DD_STATS\n    return(dd->nodesFreed);\n#else\n    (void) dd; /* avoid warning */\n    return(-1.0);\n#endif\n\n} /* end of Cudd_ReadNodesFreed */\n\n\n/**\n  @brief Returns the number of nodes dropped.\n\n  @details Returns the number of nodes killed by dereferencing if the\n  keeping of this statistic is enabled; -1 otherwise. This statistic is\n  enabled only if the package is compiled with DD_STATS defined.\n\n  @sideeffect None\n\n  @see Cudd_ReadNodesFreed\n\n*/\ndouble\nCudd_ReadNodesDropped(\n  DdManager * dd)\n{\n#ifdef DD_STATS\n    return(dd->nodesDropped);\n#else\n    (void) dd; /* avoid warning */\n    return(-1.0);\n#endif\n\n} /* end of Cudd_ReadNodesDropped */\n\n\n/**\n  @brief Returns the number of look-ups in the unique table.\n\n  @details Returns the number of look-ups in the unique table if the\n  keeping of this statistic is enabled; -1 otherwise. This statistic is\n  enabled only if the package is compiled with DD_UNIQUE_PROFILE defined.\n\n  @sideeffect None\n\n  @see Cudd_ReadUniqueLinks\n\n*/\ndouble\nCudd_ReadUniqueLookUps(\n  DdManager * dd)\n{\n#ifdef DD_UNIQUE_PROFILE\n    return(dd->uniqueLookUps);\n#else\n    (void) dd; /* avoid warning */\n    return(-1.0);\n#endif\n\n} /* end of Cudd_ReadUniqueLookUps */\n\n\n/**\n  @brief Returns the number of links followed in the unique table.\n\n  @details Returns the number of links followed during look-ups in the\n  unique table if the keeping of this statistic is enabled; -1 otherwise.\n  If an item is found in the first position of its collision list, the\n  number of links followed is taken to be 0. If it is in second position,\n  the number of links is 1, and so on. This statistic is enabled only if\n  the package is compiled with DD_UNIQUE_PROFILE defined.\n\n  @sideeffect None\n\n  @see Cudd_ReadUniqueLookUps\n\n*/\ndouble\nCudd_ReadUniqueLinks(\n  DdManager * dd)\n{\n#ifdef DD_UNIQUE_PROFILE\n    return(dd->uniqueLinks);\n#else\n    (void) dd; /* avoid warning */\n    return(-1.0);\n#endif\n\n} /* end of Cudd_ReadUniqueLinks */\n\n\n/**\n  @brief Reads the siftMaxVar parameter of the manager.\n\n  @details This parameter gives the maximum number of variables that\n  will be sifted for each invocation of sifting.\n\n  @sideeffect None\n\n  @see Cudd_ReadSiftMaxSwap Cudd_SetSiftMaxVar\n\n*/\nint\nCudd_ReadSiftMaxVar(\n  DdManager * dd)\n{\n    return(dd->siftMaxVar);\n\n} /* end of Cudd_ReadSiftMaxVar */\n\n\n/**\n  @brief Sets the siftMaxVar parameter of the manager.\n\n  @details This parameter gives the maximum number of variables that\n  will be sifted for each invocation of sifting.\n\n  @sideeffect None\n\n  @see Cudd_SetSiftMaxSwap Cudd_ReadSiftMaxVar\n\n*/\nvoid\nCudd_SetSiftMaxVar(\n  DdManager * dd,\n  int  smv)\n{\n    dd->siftMaxVar = smv;\n\n} /* end of Cudd_SetSiftMaxVar */\n\n\n/**\n  @brief Reads the siftMaxSwap parameter of the manager.\n\n  @details This parameter gives the maximum number of swaps that will\n  be attempted for each invocation of sifting. The real number of\n  swaps may exceed the set limit because the package will always\n  complete the sifting of the variable that causes the limit to be\n  reached.\n\n  @sideeffect None\n\n  @see Cudd_ReadSiftMaxVar Cudd_SetSiftMaxSwap\n\n*/\nint\nCudd_ReadSiftMaxSwap(\n  DdManager * dd)\n{\n    return(dd->siftMaxSwap);\n\n} /* end of Cudd_ReadSiftMaxSwap */\n\n\n/**\n  @brief Sets the siftMaxSwap parameter of the manager.\n\n  @details This parameter gives the maximum number of swaps that will\n  be attempted for each invocation of sifting. The real number of\n  swaps may exceed the set limit because the package will always\n  complete the sifting of the variable that causes the limit to be\n  reached.\n\n  @sideeffect None\n\n  @see Cudd_SetSiftMaxVar Cudd_ReadSiftMaxSwap\n\n*/\nvoid\nCudd_SetSiftMaxSwap(\n  DdManager * dd,\n  int  sms)\n{\n    dd->siftMaxSwap = sms;\n\n} /* end of Cudd_SetSiftMaxSwap */\n\n\n/**\n  @brief Reads the maxGrowth parameter of the manager.\n\n  @details This parameter determines how much the number of nodes can\n  grow during sifting of a variable.  Overall, sifting never increases\n  the size of the decision diagrams.  This parameter only refers to\n  intermediate results.  A lower value will speed up sifting, possibly\n  at the expense of quality.\n\n  @sideeffect None\n\n  @see Cudd_SetMaxGrowth Cudd_ReadMaxGrowthAlternate\n\n*/\ndouble\nCudd_ReadMaxGrowth(\n  DdManager * dd)\n{\n    return(dd->maxGrowth);\n\n} /* end of Cudd_ReadMaxGrowth */\n\n\n/**\n  @brief Sets the maxGrowth parameter of the manager.\n\n  @details This parameter determines how much the number of nodes can\n  grow during sifting of a variable.  Overall, sifting never increases\n  the size of the decision diagrams.  This parameter only refers to\n  intermediate results.  A lower value will speed up sifting, possibly\n  at the expense of quality.\n\n  @sideeffect None\n\n  @see Cudd_ReadMaxGrowth Cudd_SetMaxGrowthAlternate\n\n*/\nvoid\nCudd_SetMaxGrowth(\n  DdManager * dd,\n  double mg)\n{\n    dd->maxGrowth = mg;\n\n} /* end of Cudd_SetMaxGrowth */\n\n\n/**\n  @brief Reads the maxGrowthAlt parameter of the manager.\n\n  @details This parameter is analogous to the maxGrowth paramter, and\n  is used every given number of reorderings instead of maxGrowth.  The\n  number of reorderings is set with Cudd_SetReorderingCycle.  If the\n  number of reorderings is 0 (default) maxGrowthAlt is never used.\n\n  @sideeffect None\n\n  @see Cudd_ReadMaxGrowth Cudd_SetMaxGrowthAlternate\n  Cudd_SetReorderingCycle Cudd_ReadReorderingCycle\n\n*/\ndouble\nCudd_ReadMaxGrowthAlternate(\n  DdManager * dd)\n{\n    return(dd->maxGrowthAlt);\n\n} /* end of Cudd_ReadMaxGrowthAlternate */\n\n\n/**\n  @brief Sets the maxGrowthAlt parameter of the manager.\n\n  @details This parameter is analogous to the maxGrowth paramter, and\n  is used every given number of reorderings instead of maxGrowth.  The\n  number of reorderings is set with Cudd_SetReorderingCycle.  If the\n  number of reorderings is 0 (default) maxGrowthAlt is never used.\n\n  @sideeffect None\n\n  @see Cudd_ReadMaxGrowthAlternate Cudd_SetMaxGrowth\n  Cudd_SetReorderingCycle Cudd_ReadReorderingCycle\n\n*/\nvoid\nCudd_SetMaxGrowthAlternate(\n  DdManager * dd,\n  double mg)\n{\n    dd->maxGrowthAlt = mg;\n\n} /* end of Cudd_SetMaxGrowthAlternate */\n\n\n/**\n  @brief Reads the reordCycle parameter of the manager.\n\n  @details This parameter determines how often the alternate threshold\n  on maximum growth is used in reordering.\n\n  @sideeffect None\n\n  @see Cudd_ReadMaxGrowthAlternate Cudd_SetMaxGrowthAlternate\n  Cudd_SetReorderingCycle\n\n*/\nint\nCudd_ReadReorderingCycle(\n  DdManager * dd)\n{\n    return(dd->reordCycle);\n\n} /* end of Cudd_ReadReorderingCycle */\n\n\n/**\n  @brief Sets the reordCycle parameter of the manager.\n\n  @details This parameter determines how often the alternate threshold\n  on maximum growth is used in reordering.\n\n  @sideeffect None\n\n  @see Cudd_ReadMaxGrowthAlternate Cudd_SetMaxGrowthAlternate\n  Cudd_ReadReorderingCycle\n\n*/\nvoid\nCudd_SetReorderingCycle(\n  DdManager * dd,\n  int cycle)\n{\n    dd->reordCycle = cycle;\n\n} /* end of Cudd_SetReorderingCycle */\n\n\n/**\n  @brief Returns the variable group tree of the manager.\n\n  @sideeffect None\n\n  @see Cudd_SetTree Cudd_FreeTree Cudd_ReadZddTree\n\n*/\nMtrNode *\nCudd_ReadTree(\n  DdManager * dd)\n{\n    return(dd->tree);\n\n} /* end of Cudd_ReadTree */\n\n\n/**\n  @brief Sets the variable group tree of the manager.\n\n  @sideeffect None\n\n  @see Cudd_FreeTree Cudd_ReadTree Cudd_SetZddTree\n\n*/\nvoid\nCudd_SetTree(\n  DdManager * dd,\n  MtrNode * tree)\n{\n    if (dd->tree != NULL) {\n\tMtr_FreeTree(dd->tree);\n    }\n    dd->tree = tree;\n    if (tree == NULL) return;\n\n    fixVarTree(tree, dd->perm, dd->size);\n    return;\n\n} /* end of Cudd_SetTree */\n\n\n/**\n  @brief Frees the variable group tree of the manager.\n\n  @sideeffect None\n\n  @see Cudd_SetTree Cudd_ReadTree Cudd_FreeZddTree\n\n*/\nvoid\nCudd_FreeTree(\n  DdManager * dd)\n{\n    if (dd->tree != NULL) {\n\tMtr_FreeTree(dd->tree);\n\tdd->tree = NULL;\n    }\n    return;\n\n} /* end of Cudd_FreeTree */\n\n\n/**\n  @brief Returns the variable group tree of the manager.\n\n  @sideeffect None\n\n  @see Cudd_SetZddTree Cudd_FreeZddTree Cudd_ReadTree\n\n*/\nMtrNode *\nCudd_ReadZddTree(\n  DdManager * dd)\n{\n    return(dd->treeZ);\n\n} /* end of Cudd_ReadZddTree */\n\n\n/**\n  @brief Sets the %ZDD variable group tree of the manager.\n\n  @sideeffect None\n\n  @see Cudd_FreeZddTree Cudd_ReadZddTree Cudd_SetTree\n\n*/\nvoid\nCudd_SetZddTree(\n  DdManager * dd,\n  MtrNode * tree)\n{\n    if (dd->treeZ != NULL) {\n\tMtr_FreeTree(dd->treeZ);\n    }\n    dd->treeZ = tree;\n    if (tree == NULL) return;\n\n    fixVarTree(tree, dd->permZ, dd->sizeZ);\n    return;\n\n} /* end of Cudd_SetZddTree */\n\n\n/**\n  @brief Frees the variable group tree of the manager.\n\n  @sideeffect None\n\n  @see Cudd_SetZddTree Cudd_ReadZddTree Cudd_FreeTree\n\n*/\nvoid\nCudd_FreeZddTree(\n  DdManager * dd)\n{\n    if (dd->treeZ != NULL) {\n\tMtr_FreeTree(dd->treeZ);\n\tdd->treeZ = NULL;\n    }\n    return;\n\n} /* end of Cudd_FreeZddTree */\n\n\n/**\n  @brief Returns the index of the node.\n\n  @details The node pointer can be either regular or complemented.\n\n  @sideeffect None\n\n  @see Cudd_ReadIndex\n\n*/\nunsigned int\nCudd_NodeReadIndex(\n  DdNode * node)\n{\n    return((unsigned int) Cudd_Regular(node)->index);\n\n} /* end of Cudd_NodeReadIndex */\n\n\n/**\n  @brief Returns the current position of the i-th variable in the\n  order.\n\n  @details If the index is CUDD_CONST_INDEX, returns CUDD_CONST_INDEX;\n  otherwise, if the index is out of bounds returns -1.\n\n  @sideeffect None\n\n  @see Cudd_ReadInvPerm Cudd_ReadPermZdd\n\n*/\nint\nCudd_ReadPerm(\n  DdManager * dd,\n  int  i)\n{\n    if (i == CUDD_CONST_INDEX) return(CUDD_CONST_INDEX);\n    if (i < 0 || i >= dd->size) return(-1);\n    return(dd->perm[i]);\n\n} /* end of Cudd_ReadPerm */\n\n\n/**\n  @brief Returns the current position of the i-th %ZDD variable in the\n  order.\n\n  @details If the index is CUDD_CONST_INDEX, returns CUDD_CONST_INDEX;\n  otherwise, if the index is out of bounds returns -1.\n\n  @sideeffect None\n\n  @see Cudd_ReadInvPermZdd Cudd_ReadPerm\n\n*/\nint\nCudd_ReadPermZdd(\n  DdManager * dd,\n  int  i)\n{\n    if (i == CUDD_CONST_INDEX) return(CUDD_CONST_INDEX);\n    if (i < 0 || i >= dd->sizeZ) return(-1);\n    return(dd->permZ[i]);\n\n} /* end of Cudd_ReadPermZdd */\n\n\n/**\n  @brief Returns the index of the variable currently in the i-th\n  position of the order.\n\n  @details If the index is CUDD_CONST_INDEX, returns CUDD_CONST_INDEX;\n  otherwise, if the index is out of bounds returns -1.\n\n  @sideeffect None\n\n  @see Cudd_ReadPerm Cudd_ReadInvPermZdd\n\n*/\nint\nCudd_ReadInvPerm(\n  DdManager * dd,\n  int  i)\n{\n    if (i == CUDD_CONST_INDEX) return(CUDD_CONST_INDEX);\n    if (i < 0 || i >= dd->size) return(-1);\n    return(dd->invperm[i]);\n\n} /* end of Cudd_ReadInvPerm */\n\n\n/**\n  @brief Returns the index of the %ZDD variable currently in the i-th\n  position of the order.\n\n  @details If the index is CUDD_CONST_INDEX, returns CUDD_CONST_INDEX;\n  otherwise, if the index is out of bounds returns -1.\n\n  @sideeffect None\n\n  @see Cudd_ReadPerm Cudd_ReadInvPermZdd\n\n*/\nint\nCudd_ReadInvPermZdd(\n  DdManager * dd,\n  int  i)\n{\n    if (i == CUDD_CONST_INDEX) return(CUDD_CONST_INDEX);\n    if (i < 0 || i >= dd->sizeZ) return(-1);\n    return(dd->invpermZ[i]);\n\n} /* end of Cudd_ReadInvPermZdd */\n\n\n/**\n  @brief Returns the i-th element of the vars array.\n\n  @details Returns the i-th element of the vars array if it falls\n  within the array bounds; NULL otherwise. If i is the index of an\n  existing variable, this function produces the same result as\n  Cudd_bddIthVar. However, if the i-th var does not exist yet,\n  Cudd_bddIthVar will create it, whereas Cudd_ReadVars will not.\n\n  @sideeffect None\n\n  @see Cudd_bddIthVar\n\n*/\nDdNode *\nCudd_ReadVars(\n  DdManager * dd,\n  int  i)\n{\n    if (i < 0 || i > dd->size) return(NULL);\n    return(dd->vars[i]);\n\n} /* end of Cudd_ReadVars */\n\n\n/**\n  @brief Reads the epsilon parameter of the manager.\n\n  @details The epsilon parameter control the comparison between\n  floating point numbers.\n\n  @sideeffect None\n\n  @see Cudd_SetEpsilon\n\n*/\nCUDD_VALUE_TYPE\nCudd_ReadEpsilon(\n  DdManager * dd)\n{\n    return(dd->epsilon);\n\n} /* end of Cudd_ReadEpsilon */\n\n\n/**\n  @brief Sets the epsilon parameter of the manager to ep.\n\n  @details The epsilon parameter control the comparison between\n  floating point numbers.\n\n  @sideeffect None\n\n  @see Cudd_ReadEpsilon\n\n*/\nvoid\nCudd_SetEpsilon(\n  DdManager * dd,\n  CUDD_VALUE_TYPE  ep)\n{\n    dd->epsilon = ep;\n\n} /* end of Cudd_SetEpsilon */\n\n\n/**\n  @brief Reads the groupcheck parameter of the manager.\n\n  @details The groupcheck parameter determines the aggregation\n  criterion in group sifting.\n\n  @sideeffect None\n\n  @see Cudd_SetGroupcheck\n\n*/\nCudd_AggregationType\nCudd_ReadGroupcheck(\n  DdManager * dd)\n{\n    return(dd->groupcheck);\n\n} /* end of Cudd_ReadGroupCheck */\n\n\n/**\n  @brief Sets the parameter groupcheck of the manager to gc.\n\n  @details The groupcheck parameter determines the aggregation\n  criterion in group sifting.\n\n  @sideeffect None\n\n  @see Cudd_ReadGroupCheck\n\n*/\nvoid\nCudd_SetGroupcheck(\n  DdManager * dd,\n  Cudd_AggregationType gc)\n{\n    dd->groupcheck = gc;\n\n} /* end of Cudd_SetGroupcheck */\n\n\n/**\n  @brief Tells whether garbage collection is enabled.\n\n  @return 1 if garbage collection is enabled; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_EnableGarbageCollection Cudd_DisableGarbageCollection\n\n*/\nint\nCudd_GarbageCollectionEnabled(\n  DdManager * dd)\n{\n    return(dd->gcEnabled);\n\n} /* end of Cudd_GarbageCollectionEnabled */\n\n\n/**\n  @brief Enables garbage collection.\n\n  @details Garbage collection is initially enabled. Therefore it is\n  necessary to call this function only if garbage collection has been\n  explicitly disabled.\n\n  @sideeffect None\n\n  @see Cudd_DisableGarbageCollection Cudd_GarbageCollectionEnabled\n\n*/\nvoid\nCudd_EnableGarbageCollection(\n  DdManager * dd)\n{\n    dd->gcEnabled = 1;\n\n} /* end of Cudd_EnableGarbageCollection */\n\n\n/**\n  @brief Disables garbage collection.\n\n  @details Garbage collection is initially enabled. This function may\n  be called to disable it.  However, garbage collection will still\n  occur when a new node must be created and no memory is left, or when\n  garbage collection is required for correctness. (E.g., before\n  reordering.)\n\n  @sideeffect None\n\n  @see Cudd_EnableGarbageCollection Cudd_GarbageCollectionEnabled\n\n*/\nvoid\nCudd_DisableGarbageCollection(\n  DdManager * dd)\n{\n    dd->gcEnabled = 0;\n\n} /* end of Cudd_DisableGarbageCollection */\n\n\n/**\n  @brief Tells whether dead nodes are counted towards triggering\n  reordering.\n\n  @return 1 if dead nodes are counted; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_TurnOnCountDead Cudd_TurnOffCountDead\n\n*/\nint\nCudd_DeadAreCounted(\n  DdManager * dd)\n{\n    return(dd->countDead == 0 ? 1 : 0);\n\n} /* end of Cudd_DeadAreCounted */\n\n\n/**\n  @brief Causes the dead nodes to be counted towards triggering\n  reordering.\n\n  @details This causes more frequent reorderings. By default dead\n  nodes are not counted.\n\n  @sideeffect Changes the manager.\n\n  @see Cudd_TurnOffCountDead Cudd_DeadAreCounted\n\n*/\nvoid\nCudd_TurnOnCountDead(\n  DdManager * dd)\n{\n    dd->countDead = 0;\n\n} /* end of Cudd_TurnOnCountDead */\n\n\n/**\n  @brief Causes the dead nodes not to be counted towards triggering\n  reordering.\n\n  @details This causes less frequent reorderings. By default dead\n  nodes are not counted. Therefore there is no need to call this\n  function unless Cudd_TurnOnCountDead has been previously called.\n\n  @sideeffect Changes the manager.\n\n  @see Cudd_TurnOnCountDead Cudd_DeadAreCounted\n\n*/\nvoid\nCudd_TurnOffCountDead(\n  DdManager * dd)\n{\n    dd->countDead = ~0U;\n\n} /* end of Cudd_TurnOffCountDead */\n\n\n/**\n  @brief Returns the current value of the recombination parameter used\n  in group sifting.\n\n  @details A larger (positive) value makes the aggregation of\n  variables due to the second difference criterion more likely. A\n  smaller (negative) value makes aggregation less likely.\n\n  @sideeffect None\n\n  @see Cudd_SetRecomb\n\n*/\nint\nCudd_ReadRecomb(\n  DdManager * dd)\n{\n    return(dd->recomb);\n\n} /* end of Cudd_ReadRecomb */\n\n\n/**\n  @brief Sets the value of the recombination parameter used in group\n  sifting.\n\n  @details A larger (positive) value makes the aggregation of\n  variables due to the second difference criterion more likely. A\n  smaller (negative) value makes aggregation less likely. The default\n  value is 0.\n\n  @sideeffect Changes the manager.\n\n  @see Cudd_ReadRecomb\n\n*/\nvoid\nCudd_SetRecomb(\n  DdManager * dd,\n  int  recomb)\n{\n    dd->recomb = recomb;\n\n} /* end of Cudd_SetRecomb */\n\n\n/**\n  @brief Returns the current value of the symmviolation parameter used\n  in group sifting.\n\n  @details This parameter is used in group sifting to decide how many\n  violations to the symmetry conditions <code>f10 = f01</code> or\n  <code>f11 = f00</code> are tolerable when checking for aggregation\n  due to extended symmetry. The value should be between 0 and 100. A\n  small value causes fewer variables to be aggregated. The default\n  value is 0.\n\n  @sideeffect None\n\n  @see Cudd_SetSymmviolation\n\n*/\nint\nCudd_ReadSymmviolation(\n  DdManager * dd)\n{\n    return(dd->symmviolation);\n\n} /* end of Cudd_ReadSymmviolation */\n\n\n/**\n  @brief Sets the value of the symmviolation parameter used\n  in group sifting.\n\n  @details This parameter is used in group sifting to decide how many\n  violations to the symmetry conditions <code>f10 = f01</code> or\n  <code>f11 = f00</code> are tolerable when checking for aggregation\n  due to extended symmetry. The value should be between 0 and 100. A\n  small value causes fewer variables to be aggregated. The default\n  value is 0.\n\n  @sideeffect Changes the manager.\n\n  @see Cudd_ReadSymmviolation\n\n*/\nvoid\nCudd_SetSymmviolation(\n  DdManager * dd,\n  int  symmviolation)\n{\n    dd->symmviolation = symmviolation;\n\n} /* end of Cudd_SetSymmviolation */\n\n\n/**\n  @brief Returns the current value of the arcviolation parameter used\n  in group sifting.\n\n  @details This parameter is used to decide how many arcs into\n  <code>y</code> not coming from <code>x</code> are tolerable when\n  checking for aggregation due to extended symmetry. The value should\n  be between 0 and 100. A small value causes fewer variables to be\n  aggregated. The default value is 0.\n\n  @sideeffect None\n\n  @see Cudd_SetArcviolation\n\n*/\nint\nCudd_ReadArcviolation(\n  DdManager * dd)\n{\n    return(dd->arcviolation);\n\n} /* end of Cudd_ReadArcviolation */\n\n\n/**\n  @brief Sets the value of the arcviolation parameter used\n  in group sifting.\n\n  @details This parameter is used to decide how many arcs into\n  <code>y</code> not coming from <code>x</code> are tolerable when\n  checking for aggregation due to extended symmetry. The value should\n  be between 0 and 100. A small value causes fewer variables to be\n  aggregated. The default value is 0.\n\n  @sideeffect None\n\n  @see Cudd_ReadArcviolation\n\n*/\nvoid\nCudd_SetArcviolation(\n  DdManager * dd,\n  int  arcviolation)\n{\n    dd->arcviolation = arcviolation;\n\n} /* end of Cudd_SetArcviolation */\n\n\n/**\n  @brief Reads the current size of the population used by the\n  genetic algorithm for variable reordering.\n\n  @details A larger population size will cause the genetic algorithm\n  to take more time, but will generally produce better results. The\n  default value is 0, in which case the package uses three times the\n  number of variables as population size, with a maximum of 120.\n\n  @sideeffect None\n\n  @see Cudd_SetPopulationSize\n\n*/\nint\nCudd_ReadPopulationSize(\n  DdManager * dd)\n{\n    return(dd->populationSize);\n\n} /* end of Cudd_ReadPopulationSize */\n\n\n/**\n  @brief Sets the size of the population used by the\n  genetic algorithm for variable reordering.\n\n  @details A larger population size will cause the genetic algorithm\n  to take more time, but will generally produce better results. The\n  default value is 0, in which case the package uses three times the\n  number of variables as population size, with a maximum of 120.\n\n  @sideeffect Changes the manager.\n\n  @see Cudd_ReadPopulationSize\n\n*/\nvoid\nCudd_SetPopulationSize(\n  DdManager * dd,\n  int  populationSize)\n{\n    dd->populationSize = populationSize;\n\n} /* end of Cudd_SetPopulationSize */\n\n\n/**\n  @brief Reads the current number of crossovers used by the\n  genetic algorithm for variable reordering.\n\n  @details A larger number of crossovers will cause the genetic\n  algorithm to take more time, but will generally produce better\n  results. The default value is 0, in which case the package uses\n  three times the number of variables as number of crossovers, with a\n  maximum of 60.\n\n  @sideeffect None\n\n  @see Cudd_SetNumberXovers\n\n*/\nint\nCudd_ReadNumberXovers(\n  DdManager * dd)\n{\n    return(dd->numberXovers);\n\n} /* end of Cudd_ReadNumberXovers */\n\n\n/**\n  @brief Sets the number of crossovers used by the\n  genetic algorithm for variable reordering.\n\n  @details A larger number of crossovers will cause the genetic\n  algorithm to take more time, but will generally produce better\n  results. The default value is 0, in which case the package uses\n  three times the number of variables as number of crossovers, with a\n  maximum of 60.\n\n  @sideeffect None\n\n  @see Cudd_ReadNumberXovers\n\n*/\nvoid\nCudd_SetNumberXovers(\n  DdManager * dd,\n  int  numberXovers)\n{\n    dd->numberXovers = numberXovers;\n\n} /* end of Cudd_SetNumberXovers */\n\n\n/**\n  @brief Returns the order randomization factor.\n\n  @details If non-zero this factor is used to determine a perturbation\n  of the next reordering threshold.  Larger factors cause larger\n  perturbations.\n\n  @sideeffect None\n\n  @see Cudd_SetOrderRandomization\n\n*/\nunsigned int\nCudd_ReadOrderRandomization(\n  DdManager * dd)\n{\n    return(dd->randomizeOrder);\n\n} /* end of Cudd_ReadOrderRandomization */\n\n\n/**\n  @brief Sets the order randomization factor.\n\n  @sideeffect None\n\n  @see Cudd_ReadOrderRandomization\n\n*/\nvoid\nCudd_SetOrderRandomization(\n  DdManager * dd,\n  unsigned int factor)\n{\n    dd->randomizeOrder = factor;\n\n} /* end of Cudd_SetOrderRandomization */\n\n\n/**\n  @brief Returns the memory in use by the manager measured in bytes.\n\n  @sideeffect None\n\n*/\nsize_t\nCudd_ReadMemoryInUse(\n  DdManager * dd)\n{\n    return(dd->memused);\n\n} /* end of Cudd_ReadMemoryInUse */\n\n\n/**\n  @brief Prints out statistics and settings for a CUDD manager.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nCudd_PrintInfo(\n  DdManager * dd,\n  FILE * fp)\n{\n    int retval;\n    Cudd_ReorderingType autoMethod, autoMethodZ;\n\n    /* Modifiable parameters. */\n    retval = fprintf(fp,\"**** CUDD modifiable parameters ****\\n\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Hard limit for cache size: %u\\n\",\n\t\t     Cudd_ReadMaxCacheHard(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Cache hit threshold for resizing: %u%%\\n\",\n\t\t     Cudd_ReadMinHit(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Garbage collection enabled: %s\\n\",\n\t\t     Cudd_GarbageCollectionEnabled(dd) ? \"yes\" : \"no\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Limit for fast unique table growth: %u\\n\",\n\t\t     Cudd_ReadLooseUpTo(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\n\t\t     \"Maximum number of variables sifted per reordering: %d\\n\",\n\t\t     Cudd_ReadSiftMaxVar(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\n\t\t     \"Maximum number of variable swaps per reordering: %d\\n\",\n\t\t     Cudd_ReadSiftMaxSwap(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Maximum growth while sifting a variable: %g\\n\",\n\t\t     Cudd_ReadMaxGrowth(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Dynamic reordering of BDDs enabled: %s\\n\",\n\t\t     Cudd_ReorderingStatus(dd,&autoMethod) ? \"yes\" : \"no\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Default BDD reordering method: %d\\n\",\n\t\t     (int) autoMethod);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Dynamic reordering of ZDDs enabled: %s\\n\",\n\t\t     Cudd_ReorderingStatusZdd(dd,&autoMethodZ) ? \"yes\" : \"no\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Default ZDD reordering method: %d\\n\",\n\t\t     (int) autoMethodZ);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Realignment of ZDDs to BDDs enabled: %s\\n\",\n\t\t     Cudd_zddRealignmentEnabled(dd) ? \"yes\" : \"no\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Realignment of BDDs to ZDDs enabled: %s\\n\",\n\t\t     Cudd_bddRealignmentEnabled(dd) ? \"yes\" : \"no\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Dead nodes counted in triggering reordering: %s\\n\",\n\t\t     Cudd_DeadAreCounted(dd) ? \"yes\" : \"no\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Group checking criterion: %u\\n\",\n\t\t     (unsigned int) Cudd_ReadGroupcheck(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Recombination threshold: %d\\n\", Cudd_ReadRecomb(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Symmetry violation threshold: %d\\n\",\n\t\t     Cudd_ReadSymmviolation(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Arc violation threshold: %d\\n\",\n\t\t     Cudd_ReadArcviolation(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"GA population size: %d\\n\",\n\t\t     Cudd_ReadPopulationSize(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of crossovers for GA: %d\\n\",\n\t\t     Cudd_ReadNumberXovers(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Next reordering threshold: %u\\n\",\n\t\t     Cudd_ReadNextReordering(dd));\n    if (retval == EOF) return(0);\n\n    /* Non-modifiable parameters. */\n    retval = fprintf(fp,\"**** CUDD non-modifiable parameters ****\\n\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Memory in use: %\" PRIszt \"\\n\",\n                     Cudd_ReadMemoryInUse(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Peak number of nodes: %ld\\n\",\n\t\t     Cudd_ReadPeakNodeCount(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Peak number of live nodes: %d\\n\",\n\t\t     Cudd_ReadPeakLiveNodeCount(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of BDD variables: %d\\n\", dd->size);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of ZDD variables: %d\\n\", dd->sizeZ);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of cache entries: %u\\n\", dd->cacheSlots);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of cache look-ups: %.0f\\n\",\n\t\t     Cudd_ReadCacheLookUps(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of cache hits: %.0f\\n\",\n\t\t     Cudd_ReadCacheHits(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of cache insertions: %.0f\\n\",\n\t\t     dd->cacheinserts);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of cache collisions: %.0f\\n\",\n\t\t     dd->cachecollisions);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of cache deletions: %.0f\\n\",\n\t\t     dd->cachedeletions);\n    if (retval == EOF) return(0);\n    retval = cuddCacheProfile(dd,fp);\n    if (retval == 0) return(0);\n    retval = fprintf(fp,\"Soft limit for cache size: %u\\n\",\n\t\t     Cudd_ReadMaxCache(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of buckets in unique table: %u\\n\", dd->slots);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Used buckets in unique table: %.2f%% (expected %.2f%%)\\n\",\n\t\t     100.0 * Cudd_ReadUsedSlots(dd),\n\t\t     100.0 * Cudd_ExpectedUsedSlots(dd));\n    if (retval == EOF) return(0);\n#ifdef DD_UNIQUE_PROFILE\n    retval = fprintf(fp,\"Unique lookups: %.0f\\n\", dd->uniqueLookUps);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Unique links: %.0f (%g per lookup)\\n\",\n\t    dd->uniqueLinks, dd->uniqueLinks / dd->uniqueLookUps);\n    if (retval == EOF) return(0);\n#endif\n    retval = fprintf(fp,\"Number of BDD and ADD nodes: %u\\n\", dd->keys);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of ZDD nodes: %u\\n\", dd->keysZ);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of dead BDD and ADD nodes: %u\\n\", dd->dead);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Number of dead ZDD nodes: %u\\n\", dd->deadZ);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Total number of nodes allocated: %.0f\\n\",\n\t\t     dd->allocated);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Total number of nodes reclaimed: %.0f\\n\",\n\t\t     dd->reclaimed);\n    if (retval == EOF) return(0);\n#ifdef DD_STATS\n    retval = fprintf(fp,\"Nodes freed: %.0f\\n\", dd->nodesFreed);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Nodes dropped: %.0f\\n\", dd->nodesDropped);\n    if (retval == EOF) return(0);\n#endif\n#ifdef DD_COUNT\n    retval = fprintf(fp,\"Number of recursive calls: %.0f\\n\",\n\t\t     Cudd_ReadRecursiveCalls(dd));\n    if (retval == EOF) return(0);\n#endif\n    retval = fprintf(fp,\"Garbage collections so far: %d\\n\",\n\t\t     Cudd_ReadGarbageCollections(dd));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Time for garbage collection: %.2f sec\\n\",\n\t\t     ((double)Cudd_ReadGarbageCollectionTime(dd)/1000.0));\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Reorderings so far: %d\\n\", dd->reorderings);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Time for reordering: %.2f sec\\n\",\n\t\t     ((double)Cudd_ReadReorderingTime(dd)/1000.0));\n    if (retval == EOF) return(0);\n#ifdef DD_COUNT\n    retval = fprintf(fp,\"Node swaps in reordering: %.0f\\n\",\n\tCudd_ReadSwapSteps(dd));\n    if (retval == EOF) return(0);\n#endif\n\n    return(1);\n\n} /* end of Cudd_PrintInfo */\n\n\n/**\n  @brief Reports the peak number of nodes.\n\n  @details This number includes node on the free list. At the peak,\n  the number of nodes on the free list is guaranteed to be less than\n  DD_MEM_CHUNK.\n\n  @sideeffect None\n\n  @see Cudd_ReadNodeCount Cudd_PrintInfo\n\n*/\nlong\nCudd_ReadPeakNodeCount(\n  DdManager * dd)\n{\n    long count = 0;\n    DdNodePtr *scan = dd->memoryList;\n\n    while (scan != NULL) {\n\tcount += DD_MEM_CHUNK;\n\tscan = (DdNodePtr *) *scan;\n    }\n    return(count);\n\n} /* end of Cudd_ReadPeakNodeCount */\n\n\n/**\n  @brief Reports the peak number of live nodes.\n\n  @sideeffect None\n\n  @see Cudd_ReadNodeCount Cudd_PrintInfo Cudd_ReadPeakNodeCount\n\n*/\nint\nCudd_ReadPeakLiveNodeCount(\n  DdManager * dd)\n{\n    unsigned int live = dd->keys - dd->dead;\n\n    if (live > dd->peakLiveNodes) {\n\tdd->peakLiveNodes = live;\n    }\n    return((int)dd->peakLiveNodes);\n\n} /* end of Cudd_ReadPeakLiveNodeCount */\n\n\n/**\n  @brief Reports the number of nodes in BDDs and ADDs.\n\n  @details This number does not include the isolated projection\n  functions and the unused constants. These nodes that are not counted\n  are not part of the DDs manipulated by the application.\n\n  @sideeffect None\n\n  @see Cudd_ReadPeakNodeCount Cudd_zddReadNodeCount\n\n*/\nlong\nCudd_ReadNodeCount(\n  DdManager * dd)\n{\n    long count;\n    int i;\n\n#ifndef DD_NO_DEATH_ROW\n    cuddClearDeathRow(dd);\n#endif\n\n    count = (long) (dd->keys - dd->dead);\n\n    /* Count isolated projection functions. Their number is subtracted\n    ** from the node count because they are not part of the BDDs.\n    */\n    for (i=0; i < dd->size; i++) {\n\tif (dd->vars[i]->ref == 1) count--;\n    }\n    /* Subtract from the count the unused constants. */\n    if (DD_ZERO(dd)->ref == 1) count--;\n    if (DD_PLUS_INFINITY(dd)->ref == 1) count--;\n    if (DD_MINUS_INFINITY(dd)->ref == 1) count--;\n\n    return(count);\n\n} /* end of Cudd_ReadNodeCount */\n\n\n\n/**\n  @brief Reports the number of nodes in ZDDs.\n\n  @details This number always includes the two constants 1 and 0.\n\n  @sideeffect None\n\n  @see Cudd_ReadPeakNodeCount Cudd_ReadNodeCount\n\n*/\nlong\nCudd_zddReadNodeCount(\n  DdManager * dd)\n{\n    return((long)(dd->keysZ - dd->deadZ + 2));\n\n} /* end of Cudd_zddReadNodeCount */\n\n\n/**\n  @brief Adds a function to a hook.\n\n  @details A hook is a list of\n  application-provided functions called on certain occasions by the\n  package.\n\n  @return 1 if the function is successfully added; 2 if the function\n  was already in the list; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_RemoveHook\n\n*/\nint\nCudd_AddHook(\n  DdManager * dd,\n  DD_HFP f,\n  Cudd_HookType where)\n{\n    DdHook **hook, *nextHook, *newHook;\n\n    switch (where) {\n    case CUDD_PRE_GC_HOOK:\n\thook = &(dd->preGCHook);\n\tbreak;\n    case CUDD_POST_GC_HOOK:\n\thook = &(dd->postGCHook);\n\tbreak;\n    case CUDD_PRE_REORDERING_HOOK:\n\thook = &(dd->preReorderingHook);\n\tbreak;\n    case CUDD_POST_REORDERING_HOOK:\n\thook = &(dd->postReorderingHook);\n\tbreak;\n    default:\n        return(0);\n    }\n    /* Scan the list and find whether the function is already there.\n    ** If so, just return. */\n    nextHook = *hook;\n    while (nextHook != NULL) {\n\tif (nextHook->f == f) {\n\t    return(2);\n\t}\n\thook = &(nextHook->next);\n\tnextHook = nextHook->next;\n    }\n    /* The function was not in the list. Create a new item and append it\n    ** to the end of the list. */\n    newHook = ALLOC(DdHook,1);\n    if (newHook == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    newHook->next = NULL;\n    newHook->f = f;\n    *hook = newHook;\n    return(1);\n\n} /* end of Cudd_AddHook */\n\n\n/**\n  @brief Removes a function from a hook.\n\n  @details A hook is a list of application-provided functions called\n  on certain occasions by the package.\n\n  @return 1 if successful; 0 the function was not in the list.\n\n  @sideeffect None\n\n  @see Cudd_AddHook\n\n*/\nint\nCudd_RemoveHook(\n  DdManager * dd,\n  DD_HFP f,\n  Cudd_HookType where)\n{\n    DdHook **hook, *nextHook;\n\n    switch (where) {\n    case CUDD_PRE_GC_HOOK:\n\thook = &(dd->preGCHook);\n\tbreak;\n    case CUDD_POST_GC_HOOK:\n\thook = &(dd->postGCHook);\n\tbreak;\n    case CUDD_PRE_REORDERING_HOOK:\n\thook = &(dd->preReorderingHook);\n\tbreak;\n    case CUDD_POST_REORDERING_HOOK:\n\thook = &(dd->postReorderingHook);\n\tbreak;\n    default:\n        return(0);\n    }\n    nextHook = *hook;\n    while (nextHook != NULL) {\n\tif (nextHook->f == f) {\n\t    *hook = nextHook->next;\n\t    FREE(nextHook);\n\t    return(1);\n\t}\n\thook = &(nextHook->next);\n\tnextHook = nextHook->next;\n    }\n\n    return(0);\n\n} /* end of Cudd_RemoveHook */\n\n\n/**\n  @brief Checks whether a function is in a hook.\n\n  @details A hook is a list of application-provided functions called\n  on certain occasions by the package.\n\n  @return 1 if the function is found; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_AddHook Cudd_RemoveHook\n\n*/\nint\nCudd_IsInHook(\n  DdManager * dd,\n  DD_HFP f,\n  Cudd_HookType where)\n{\n    DdHook *hook;\n\n    switch (where) {\n    case CUDD_PRE_GC_HOOK:\n\thook = dd->preGCHook;\n\tbreak;\n    case CUDD_POST_GC_HOOK:\n\thook = dd->postGCHook;\n\tbreak;\n    case CUDD_PRE_REORDERING_HOOK:\n\thook = dd->preReorderingHook;\n\tbreak;\n    case CUDD_POST_REORDERING_HOOK:\n\thook = dd->postReorderingHook;\n\tbreak;\n    default:\n        return(0);\n    }\n    /* Scan the list and find whether the function is already there. */\n    while (hook != NULL) {\n\tif (hook->f == f) {\n\t    return(1);\n\t}\n\thook = hook->next;\n    }\n    return(0);\n\n} /* end of Cudd_IsInHook */\n\n\n/**\n  @brief Sample hook function to call before reordering.\n\n  @details Prints on the manager's stdout reordering method and initial size.\n  \n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_StdPostReordHook\n\n*/\nint\nCudd_StdPreReordHook(\n  DdManager *dd,\n  const char *str,\n  void *data)\n{\n    Cudd_ReorderingType method = (Cudd_ReorderingType) (ptruint) data;\n    int retval;\n\n    retval = fprintf(dd->out,\"%s reordering with \", str);\n    if (retval == EOF) return(0);\n    switch (method) {\n    case CUDD_REORDER_SIFT_CONVERGE:\n    case CUDD_REORDER_SYMM_SIFT_CONV:\n    case CUDD_REORDER_GROUP_SIFT_CONV:\n    case CUDD_REORDER_WINDOW2_CONV:\n    case CUDD_REORDER_WINDOW3_CONV:\n    case CUDD_REORDER_WINDOW4_CONV:\n    case CUDD_REORDER_LINEAR_CONVERGE:\n\tretval = fprintf(dd->out,\"converging \");\n\tif (retval == EOF) return(0);\n\tbreak;\n    default:\n\tbreak;\n    }\n    switch (method) {\n    case CUDD_REORDER_RANDOM:\n    case CUDD_REORDER_RANDOM_PIVOT:\n\tretval = fprintf(dd->out,\"random\");\n\tbreak;\n    case CUDD_REORDER_SIFT:\n    case CUDD_REORDER_SIFT_CONVERGE:\n\tretval = fprintf(dd->out,\"sifting\");\n\tbreak;\n    case CUDD_REORDER_SYMM_SIFT:\n    case CUDD_REORDER_SYMM_SIFT_CONV:\n\tretval = fprintf(dd->out,\"symmetric sifting\");\n\tbreak;\n    case CUDD_REORDER_LAZY_SIFT:\n\tretval = fprintf(dd->out,\"lazy sifting\");\n\tbreak;\n    case CUDD_REORDER_GROUP_SIFT:\n    case CUDD_REORDER_GROUP_SIFT_CONV:\n\tretval = fprintf(dd->out,\"group sifting\");\n\tbreak;\n    case CUDD_REORDER_WINDOW2:\n    case CUDD_REORDER_WINDOW3:\n    case CUDD_REORDER_WINDOW4:\n    case CUDD_REORDER_WINDOW2_CONV:\n    case CUDD_REORDER_WINDOW3_CONV:\n    case CUDD_REORDER_WINDOW4_CONV:\n\tretval = fprintf(dd->out,\"window\");\n\tbreak;\n    case CUDD_REORDER_ANNEALING:\n\tretval = fprintf(dd->out,\"annealing\");\n\tbreak;\n    case CUDD_REORDER_GENETIC:\n\tretval = fprintf(dd->out,\"genetic\");\n\tbreak;\n    case CUDD_REORDER_LINEAR:\n    case CUDD_REORDER_LINEAR_CONVERGE:\n\tretval = fprintf(dd->out,\"linear sifting\");\n\tbreak;\n    case CUDD_REORDER_EXACT:\n\tretval = fprintf(dd->out,\"exact\");\n\tbreak;\n    default:\n\treturn(0);\n    }\n    if (retval == EOF) return(0);\n\n    retval = fprintf(dd->out,\": from %ld to ... \", strcmp(str, \"BDD\") == 0 ?\n\t\t     Cudd_ReadNodeCount(dd) : Cudd_zddReadNodeCount(dd));\n    if (retval == EOF) return(0);\n    fflush(dd->out);\n    return(1);\n\n} /* end of Cudd_StdPreReordHook */\n\n\n/**\n  @brief Sample hook function to call after reordering.\n\n  @details Prints on the manager's stdout final size and reordering time.\n  \n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_StdPreReordHook\n\n*/\nint\nCudd_StdPostReordHook(\n  DdManager *dd,\n  const char *str,\n  void *data)\n{\n    unsigned long initialTime = (unsigned long) (ptruint) data;\n    int retval;\n    unsigned long finalTime = util_cpu_time();\n    double totalTimeSec = (double)(finalTime - initialTime) / 1000.0;\n\n    retval = fprintf(dd->out,\"%ld nodes in %g sec\\n\", strcmp(str, \"BDD\") == 0 ?\n\t\t     Cudd_ReadNodeCount(dd) : Cudd_zddReadNodeCount(dd),\n\t\t     totalTimeSec);\n    if (retval == EOF) return(0);\n    retval = fflush(dd->out);\n    if (retval == EOF) return(0);\n    return(1);\n\n} /* end of Cudd_StdPostReordHook */\n\n\n/**\n  @brief Enables reporting of reordering stats.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Installs functions in the pre-reordering and post-reordering\n  hooks.\n\n  @see Cudd_DisableReorderingReporting Cudd_ReorderingReporting\n\n*/\nint\nCudd_EnableReorderingReporting(\n  DdManager *dd)\n{\n    if (!Cudd_AddHook(dd, Cudd_StdPreReordHook, CUDD_PRE_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    if (!Cudd_AddHook(dd, Cudd_StdPostReordHook, CUDD_POST_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    return(1);\n\n} /* end of Cudd_EnableReorderingReporting */\n\n\n/**\n  @brief Disables reporting of reordering stats.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Removes functions from the pre-reordering and post-reordering\n  hooks.\n\n  @see Cudd_EnableReorderingReporting Cudd_ReorderingReporting\n\n*/\nint\nCudd_DisableReorderingReporting(\n  DdManager *dd)\n{\n    if (!Cudd_RemoveHook(dd, Cudd_StdPreReordHook, CUDD_PRE_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    if (!Cudd_RemoveHook(dd, Cudd_StdPostReordHook, CUDD_POST_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    return(1);\n\n} /* end of Cudd_DisableReorderingReporting */\n\n\n/**\n  @brief Returns 1 if reporting of reordering stats is enabled; 0\n  otherwise.\n\n  @sideeffect none\n\n  @see Cudd_EnableReorderingReporting Cudd_DisableReorderingReporting\n\n*/\nint\nCudd_ReorderingReporting(\n  DdManager *dd)\n{\n    return(Cudd_IsInHook(dd, Cudd_StdPreReordHook, CUDD_PRE_REORDERING_HOOK));\n\n} /* end of Cudd_ReorderingReporting */\n\n\n/**\n  @brief Hook function to print the current variable order.\n\n  @details It may be called before or after reordering. Prints on the\n  manager's stdout a parenthesized list that describes the variable\n  groups.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_StdPreReordHook\n\n*/\nint\nCudd_PrintGroupedOrder(\n  DdManager * dd,\n  const char *str,\n  void *data)\n{\n    (void) data; /* avoid warning */\n    int isBdd = strcmp(str, \"ZDD\");\n    MtrNode *tree = isBdd ? dd->tree : dd->treeZ;\n    int *invperm = isBdd ? dd->invperm : dd->invpermZ;\n    int size = isBdd ? dd->size : dd->sizeZ;\n    if (tree == NULL) {\n        int i, retval;\n        for (i=0; i < size; i++) {\n            retval = fprintf(dd->out, \"%c%d\", i==0 ? '(' : ',', invperm[i]);\n            if (retval == EOF) return(0);\n        }\n        retval = fprintf(dd->out,\")\\n\");\n        return (retval != EOF);\n    } else {\n        return Mtr_PrintGroupedOrder(tree,invperm,dd->out);\n    }\n        \n} /* end of Cudd_PrintGroupedOrder */\n\n\n/**\n  @brief Enables monitoring of ordering.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Installs functions in the pre-reordering and post-reordering\n  hooks.\n\n  @see Cudd_EnableReorderingReporting\n\n*/\nint\nCudd_EnableOrderingMonitoring(\n  DdManager *dd)\n{\n    if (!Cudd_AddHook(dd, Cudd_PrintGroupedOrder, CUDD_PRE_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    if (!Cudd_AddHook(dd, Cudd_StdPreReordHook, CUDD_PRE_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    if (!Cudd_AddHook(dd, Cudd_StdPostReordHook, CUDD_POST_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    if (!Cudd_AddHook(dd, Cudd_PrintGroupedOrder, CUDD_POST_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    return(1);\n\n} /* end of Cudd_EnableOrderingMonitoring */\n\n\n/**\n  @brief Disables monitoring of ordering.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Removes functions from the pre-reordering and post-reordering\n  hooks.\n\n  @see Cudd_EnableOrderingMonitoring\n\n*/\nint\nCudd_DisableOrderingMonitoring(\n  DdManager *dd)\n{\n    if (!Cudd_RemoveHook(dd, Cudd_StdPreReordHook, CUDD_PRE_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    if (!Cudd_RemoveHook(dd, Cudd_PrintGroupedOrder, CUDD_PRE_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    if (!Cudd_RemoveHook(dd, Cudd_PrintGroupedOrder, CUDD_POST_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    if (!Cudd_RemoveHook(dd, Cudd_StdPostReordHook, CUDD_POST_REORDERING_HOOK)) {\n\treturn(0);\n    }\n    return(1);\n\n} /* end of Cudd_DisableOrderingMonitoring */\n\n\n/**\n  @brief Returns 1 if monitoring of ordering is enabled; 0 otherwise.\n\n  @sideeffect none\n\n  @see Cudd_EnableOrderingMonitoring Cudd_DisableOrderingMonitoring\n\n*/\nint\nCudd_OrderingMonitoring(\n  DdManager *dd)\n{\n    return(Cudd_IsInHook(dd, Cudd_PrintGroupedOrder, CUDD_PRE_REORDERING_HOOK));\n\n} /* end of Cudd_OrderingMonitoring */\n\n\n/**\n  @brief Sets the application hook.\n\n  @sideeffect None\n\n  @see Cudd_ReadApplicationHook\n\n*/\nvoid\nCudd_SetApplicationHook(\n  DdManager *dd,\n  void * value)\n{\n    dd->hooks = value;  \n\n} /* end of Cudd_SetApplicationHook */\n\n\n/**\n  @brief Reads the application hook.\n\n  @sideeffect None\n\n  @see Cudd_SetApplicationHook\n\n*/\nvoid *\nCudd_ReadApplicationHook(\n  DdManager *dd)\n{\n    return(dd->hooks);  \n\n} /* end of Cudd_ReadApplicationHook */\n\n\n/**\n  @brief Returns the code of the last error.\n\n  @details The error codes are defined in cudd.h.\n\n  @sideeffect None\n\n  @see Cudd_ClearErrorCode\n\n*/\nCudd_ErrorType\nCudd_ReadErrorCode(\n  DdManager *dd)\n{\n    return(dd->errorCode);\n\n} /* end of Cudd_ReadErrorCode */\n\n\n/**\n  @brief Clear the error code of a manager.\n\n  @sideeffect None\n\n  @see Cudd_ReadErrorCode\n\n*/\nvoid\nCudd_ClearErrorCode(\n  DdManager *dd)\n{\n    dd->errorCode = CUDD_NO_ERROR;\n\n} /* end of Cudd_ClearErrorCode */\n\n\n/**\n  @brief Installs a handler for failed memory allocations.\n\n  @details Changing the handler only has an effect if the wrappers\n  in safe_mem.c are in use.\n\n  @return the current handler.\n*/\nDD_OOMFP\nCudd_InstallOutOfMemoryHandler(\n  DD_OOMFP newHandler)\n{\n    DD_OOMFP oldHandler = MMoutOfMemory;\n    MMoutOfMemory = newHandler;\n    return oldHandler;\n\n} /* end of Cudd_InstallOutOfMemoryHandler */\n\n\n/**\n  @brief Reads the stdout of a manager.\n\n  @details This is the file pointer to which messages normally going\n  to stdout are written. It is initialized to stdout. Cudd_SetStdout\n  allows the application to redirect it.\n\n  @sideeffect None\n\n  @see Cudd_SetStdout Cudd_ReadStderr\n\n*/\nFILE *\nCudd_ReadStdout(\n  DdManager *dd)\n{\n    return(dd->out);\n\n} /* end of Cudd_ReadStdout */\n\n\n/**\n  @brief Sets the stdout of a manager.\n\n  @sideeffect None\n\n  @see Cudd_ReadStdout Cudd_SetStderr\n\n*/\nvoid\nCudd_SetStdout(\n  DdManager *dd,\n  FILE *fp)\n{\n    dd->out = fp;\n\n} /* end of Cudd_SetStdout */\n\n\n/**\n  @brief Reads the stderr of a manager.\n\n  @details This is the file pointer to which messages normally going\n  to stderr are written. It is initialized to stderr. Cudd_SetStderr\n  allows the application to redirect it.\n\n  @sideeffect None\n\n  @see Cudd_SetStderr Cudd_ReadStdout\n\n*/\nFILE *\nCudd_ReadStderr(\n  DdManager *dd)\n{\n    return(dd->err);\n\n} /* end of Cudd_ReadStderr */\n\n\n/**\n  @brief Sets the stderr of a manager.\n\n  @sideeffect None\n\n  @see Cudd_ReadStderr Cudd_SetStdout\n\n*/\nvoid\nCudd_SetStderr(\n  DdManager *dd,\n  FILE *fp)\n{\n    dd->err = fp;\n\n} /* end of Cudd_SetStderr */\n\n\n/**\n  @brief Returns the threshold for the next dynamic reordering.\n\n  @details The threshold is in terms of number of nodes and is in\n  effect only if reordering is enabled. The count does not include the\n  dead nodes, unless the countDead parameter of the manager has been\n  changed from its default setting.\n\n  @sideeffect None\n\n  @see Cudd_SetNextReordering\n\n*/\nunsigned int\nCudd_ReadNextReordering(\n  DdManager *dd)\n{\n    return(dd->nextDyn);\n\n} /* end of Cudd_ReadNextReordering */\n\n\n/**\n  @brief Sets the threshold for the next dynamic reordering.\n\n  @details The threshold is in terms of number of nodes and is in\n  effect only if reordering is enabled. The count does not include the\n  dead nodes, unless the countDead parameter of the manager has been\n  changed from its default setting.\n\n  @sideeffect None\n\n  @see Cudd_ReadNextReordering\n\n*/\nvoid\nCudd_SetNextReordering(\n  DdManager *dd,\n  unsigned int next)\n{\n    dd->nextDyn = next;\n\n} /* end of Cudd_SetNextReordering */\n\n\n/**\n  @brief Reads the number of elementary reordering steps.\n\n  @sideeffect none\n\n*/\ndouble\nCudd_ReadSwapSteps(\n  DdManager *dd)\n{\n#ifdef DD_COUNT\n    return(dd->swapSteps);\n#else\n    (void) dd; /* avoid warning */\n    return(-1);\n#endif\n\n} /* end of Cudd_ReadSwapSteps */\n\n\n/**\n  @brief Reads the maximum allowed number of live nodes.\n\n  @details When this number is exceeded, the package returns NULL.\n\n  @sideeffect none\n\n  @see Cudd_SetMaxLive\n\n*/\nunsigned int\nCudd_ReadMaxLive(\n  DdManager *dd)\n{\n    return(dd->maxLive);\n\n} /* end of Cudd_ReadMaxLive */\n\n\n/**\n  @brief Sets the maximum allowed number of live nodes.\n\n  @details When this number is exceeded, the package returns NULL.\n\n  @sideeffect none\n\n  @see Cudd_ReadMaxLive\n\n*/\nvoid\nCudd_SetMaxLive(\n  DdManager *dd,\n  unsigned int maxLive)\n{\n    dd->maxLive = maxLive;\n\n} /* end of Cudd_SetMaxLive */\n\n\n/**\n  @brief Reads the maximum allowed memory.\n\n  @details When this number is exceeded, the package returns NULL.\n\n  @sideeffect none\n\n  @see Cudd_SetMaxMemory\n\n*/\nsize_t\nCudd_ReadMaxMemory(\n  DdManager *dd)\n{\n    return(dd->maxmemhard);\n\n} /* end of Cudd_ReadMaxMemory */\n\n\n/**\n  @brief Sets the maximum allowed memory.\n\n  @details When this number is exceeded, the package returns NULL.\n\n  @return the previous limit.\n\n  @sideeffect none\n\n  @see Cudd_ReadMaxMemory\n\n*/\nsize_t\nCudd_SetMaxMemory(\n  DdManager *dd,\n  size_t maxMemory)\n{\n    size_t oldLimit = dd->maxmemhard;\n    dd->maxmemhard = maxMemory;\n    return oldLimit;\n\n} /* end of Cudd_SetMaxMemory */\n\n\n/**\n  @brief Prevents sifting of a variable.\n\n  @details This function sets a flag to prevent sifting of a\n  variable.\n\n  @return 1 if successful; 0 otherwise (i.e., invalid variable index).\n\n  @sideeffect Changes the \"bindVar\" flag in DdSubtable.\n\n  @see Cudd_bddUnbindVar\n\n*/\nint\nCudd_bddBindVar(\n  DdManager *dd /**< manager */,\n  int index /**< variable index */)\n{\n    if (index >= dd->size || index < 0) return(0);\n    dd->subtables[dd->perm[index]].bindVar = 1;\n    return(1);\n\n} /* end of Cudd_bddBindVar */\n\n\n/**\n  @brief Allows the sifting of a variable.\n\n  @details This function resets the flag that prevents the sifting\n  of a variable. In successive variable reorderings, the variable will\n  NOT be skipped, that is, sifted.  Initially all variables can be\n  sifted. It is necessary to call this function only to re-enable\n  sifting after a call to Cudd_bddBindVar.\n\n  @return 1 if successful; 0 otherwise (i.e., invalid variable index).\n\n  @sideeffect Changes the \"bindVar\" flag in DdSubtable.\n\n  @see Cudd_bddBindVar\n\n*/\nint\nCudd_bddUnbindVar(\n  DdManager *dd /**< manager */,\n  int index /**< variable index */)\n{\n    if (index >= dd->size || index < 0) return(0);\n    dd->subtables[dd->perm[index]].bindVar = 0;\n    return(1);\n\n} /* end of Cudd_bddUnbindVar */\n\n\n/**\n  @brief Tells whether a variable can be sifted.\n\n  @details This function returns 1 if a variable is enabled for\n  sifting.  Initially all variables can be sifted. This function\n  returns 0 if there has been a previous call to Cudd_bddBindVar for\n  that variable not followed by a call to Cudd_bddUnbindVar. The\n  function returns 0 also in the case in which the index of the\n  variable is out of bounds.\n\n  @sideeffect none\n\n  @see Cudd_bddBindVar Cudd_bddUnbindVar\n\n*/\nint\nCudd_bddVarIsBound(\n  DdManager *dd /**< manager */,\n  int index /**< variable index */)\n{\n    if (index >= dd->size || index < 0) return(0);\n    return(dd->subtables[dd->perm[index]].bindVar);\n\n} /* end of Cudd_bddVarIsBound */\n\n\n/**\n  @brief Sets a variable type to primary input.\n\n  @details The variable type is used by lazy sifting.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddSetPsVar Cudd_bddSetNsVar Cudd_bddIsPiVar\n\n*/\nint\nCudd_bddSetPiVar(\n  DdManager *dd /**< manager */,\n  int index /**< variable index */)\n{\n    if (index >= dd->size || index < 0) return (0);\n    dd->subtables[dd->perm[index]].varType = CUDD_VAR_PRIMARY_INPUT;\n    return(1);\n\n} /* end of Cudd_bddSetPiVar */\n\n\n/**\n  @brief Sets a variable type to present state.\n\n  @details The variable type is used by lazy sifting.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddSetPiVar Cudd_bddSetNsVar Cudd_bddIsPsVar\n\n*/\nint\nCudd_bddSetPsVar(\n  DdManager *dd /**< manager */,\n  int index /**< variable index */)\n{\n    if (index >= dd->size || index < 0) return (0);\n    dd->subtables[dd->perm[index]].varType = CUDD_VAR_PRESENT_STATE;\n    return(1);\n\n} /* end of Cudd_bddSetPsVar */\n\n\n/**\n  @brief Sets a variable type to next state.\n\n  @details The variable type is used by lazy sifting.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddSetPiVar Cudd_bddSetPsVar Cudd_bddIsNsVar\n\n*/\nint\nCudd_bddSetNsVar(\n  DdManager *dd /**< manager */,\n  int index /**< variable index */)\n{\n    if (index >= dd->size || index < 0) return (0);\n    dd->subtables[dd->perm[index]].varType = CUDD_VAR_NEXT_STATE;\n    return(1);\n\n} /* end of Cudd_bddSetNsVar */\n\n\n/**\n  @brief Checks whether a variable is primary input.\n\n  @return 1 if the variable's type is primary input; 0 if the variable\n  exists but is not a primary input; -1 if the variable does not\n  exist.\n\n  @sideeffect none\n\n  @see Cudd_bddSetPiVar Cudd_bddIsPsVar Cudd_bddIsNsVar\n\n*/\nint\nCudd_bddIsPiVar(\n  DdManager *dd /**< manager */,\n  int index /**< variable index */)\n{\n    if (index >= dd->size || index < 0) return -1;\n    return (dd->subtables[dd->perm[index]].varType == CUDD_VAR_PRIMARY_INPUT);\n\n} /* end of Cudd_bddIsPiVar */\n\n\n/**\n  @brief Checks whether a variable is present state.\n\n  @return 1 if the variable's type is present state; 0 if the variable\n  exists but is not a present state; -1 if the variable does not\n  exist.\n\n  @sideeffect none\n\n  @see Cudd_bddSetPsVar Cudd_bddIsPiVar Cudd_bddIsNsVar\n\n*/\nint\nCudd_bddIsPsVar(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return -1;\n    return (dd->subtables[dd->perm[index]].varType == CUDD_VAR_PRESENT_STATE);\n\n} /* end of Cudd_bddIsPsVar */\n\n\n/**\n  @brief Checks whether a variable is next state.\n\n  @return 1 if the variable's type is present state; 0 if the variable\n  exists but is not a present state; -1 if the variable does not\n  exist.\n\n  @sideeffect none\n\n  @see Cudd_bddSetNsVar Cudd_bddIsPiVar Cudd_bddIsPsVar\n\n*/\nint\nCudd_bddIsNsVar(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return -1;\n    return (dd->subtables[dd->perm[index]].varType == CUDD_VAR_NEXT_STATE);\n\n} /* end of Cudd_bddIsNsVar */\n\n\n/**\n  @brief Sets a corresponding pair index for a given index.\n\n  @details These pair indices are present and next state variable.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddReadPairIndex\n\n*/\nint\nCudd_bddSetPairIndex(\n  DdManager *dd /**< manager */,\n  int index /**< variable index */,\n  int pairIndex /**< corresponding variable index */)\n{\n    if (index >= dd->size || index < 0) return(0);\n    dd->subtables[dd->perm[index]].pairIndex = pairIndex;\n    return(1);\n\n} /* end of Cudd_bddSetPairIndex */\n\n\n/**\n  @brief Reads a corresponding pair index for a given index.\n\n  @details These pair indices are present and next state variable.\n\n  @return the corresponding variable index if the variable exists; -1\n  otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddSetPairIndex\n\n*/\nint\nCudd_bddReadPairIndex(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return -1;\n    return dd->subtables[dd->perm[index]].pairIndex;\n\n} /* end of Cudd_bddReadPairIndex */\n\n\n/**\n  @brief Sets a variable to be grouped.\n\n  @details This function is used for lazy sifting.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddSetVarHardGroup Cudd_bddResetVarToBeGrouped\n\n*/\nint\nCudd_bddSetVarToBeGrouped(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(0);\n    if (dd->subtables[dd->perm[index]].varToBeGrouped <= CUDD_LAZY_SOFT_GROUP) {\n\tdd->subtables[dd->perm[index]].varToBeGrouped = CUDD_LAZY_SOFT_GROUP;\n    }\n    return(1);\n\n} /* end of Cudd_bddSetVarToBeGrouped */\n\n\n/**\n  @brief Sets a variable to be a hard group.\n\n  @details This function is used for lazy sifting.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddSetVarToBeGrouped Cudd_bddResetVarToBeGrouped\n  Cudd_bddIsVarHardGroup\n\n*/\nint\nCudd_bddSetVarHardGroup(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(0);\n    dd->subtables[dd->perm[index]].varToBeGrouped = CUDD_LAZY_HARD_GROUP;\n    return(1);\n\n} /* end of Cudd_bddSetVarHardGrouped */\n\n\n/**\n  @brief Resets a variable not to be grouped.\n\n  @details This function is used for lazy sifting.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddSetVarToBeGrouped Cudd_bddSetVarHardGroup\n\n*/\nint\nCudd_bddResetVarToBeGrouped(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(0);\n    if (dd->subtables[dd->perm[index]].varToBeGrouped <=\n\tCUDD_LAZY_SOFT_GROUP) {\n\tdd->subtables[dd->perm[index]].varToBeGrouped = CUDD_LAZY_NONE;\n    }\n    return(1);\n\n} /* end of Cudd_bddResetVarToBeGrouped */\n\n\n/**\n  @brief Checks whether a variable is set to be grouped.\n\n  @details This function is used for lazy sifting.\n\n  @sideeffect none\n\n*/\nint\nCudd_bddIsVarToBeGrouped(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(-1);\n    if (dd->subtables[dd->perm[index]].varToBeGrouped == CUDD_LAZY_UNGROUP)\n\treturn(0);\n    else\n\treturn(dd->subtables[dd->perm[index]].varToBeGrouped);\n\n} /* end of Cudd_bddIsVarToBeGrouped */\n\n\n/**\n  @brief Sets a variable to be ungrouped.\n\n  @details This function is used for lazy sifting.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect modifies the manager\n\n  @see Cudd_bddIsVarToBeUngrouped\n\n*/\nint\nCudd_bddSetVarToBeUngrouped(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(0);\n    dd->subtables[dd->perm[index]].varToBeGrouped = CUDD_LAZY_UNGROUP;\n    return(1);\n\n} /* end of Cudd_bddSetVarToBeGrouped */\n\n\n/**\n  @brief Checks whether a variable is set to be ungrouped.\n\n  @details This function is used for lazy sifting.\n\n  @return 1 if the variable is marked to be ungrouped; 0 if the\n  variable exists, but it is not marked to be ungrouped; -1 if the\n  variable does not exist.\n\n  @sideeffect none\n\n  @see Cudd_bddSetVarToBeUngrouped\n\n*/\nint\nCudd_bddIsVarToBeUngrouped(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(-1);\n    return dd->subtables[dd->perm[index]].varToBeGrouped == CUDD_LAZY_UNGROUP;\n\n} /* end of Cudd_bddIsVarToBeGrouped */\n\n\n/**\n  @brief Checks whether a variable is set to be in a hard group.\n\n  @details This function is used for lazy sifting.\n\n  @return 1 if the variable is marked to be in a hard group; 0 if the\n  variable exists, but it is not marked to be in a hard group; -1 if\n  the variable does not exist.\n\n  @sideeffect none\n\n  @see Cudd_bddSetVarHardGroup\n\n*/\nint\nCudd_bddIsVarHardGroup(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(-1);\n    if (dd->subtables[dd->perm[index]].varToBeGrouped == CUDD_LAZY_HARD_GROUP)\n\treturn(1);\n    return(0);\n\n} /* end of Cudd_bddIsVarToBeGrouped */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Fixes a variable group tree.\n\n  @sideeffect Changes the variable group tree.\n\n*/\nstatic void\nfixVarTree(\n  MtrNode * treenode,\n  int * perm,\n  int  size)\n{\n    treenode->index = treenode->low;\n    treenode->low = ((int) treenode->index < size) ?\n\t(MtrHalfWord) perm[treenode->index] : treenode->index;\n    if (treenode->child != NULL)\n\tfixVarTree(treenode->child, perm, size);\n    if (treenode->younger != NULL)\n\tfixVarTree(treenode->younger, perm, size);\n    return;\n\n} /* end of fixVarTree */\n\n\n/**\n  @brief Adds multiplicity groups to a %ZDD variable group tree.\n\n  @details This function creates the groups for set of %ZDD variables\n  (whose cardinality is given by parameter multiplicity) that are\n  created for each %BDD variable in Cudd_zddVarsFromBddVars. The crux\n  of the matter is to determine the index each new group. (The index\n  of the first variable in the group.)  We first build all the groups\n  for the children of a node, and then deal with the %ZDD variables\n  that are directly attached to the node. The problem for these is\n  that the tree itself does not provide information on their position\n  inside the group. While we deal with the children of the node,\n  therefore, we keep track of all the positions they occupy. The\n  remaining positions in the tree can be freely used. Also, we keep\n  track of all the variables placed in the children. All the remaining\n  variables are directly attached to the group. We can then place any\n  pair of variables not yet grouped in any pair of available positions\n  in the node.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Changes the variable group tree.\n\n  @see Cudd_zddVarsFromBddVars\n\n*/\nstatic int\naddMultiplicityGroups(\n  DdManager *dd /**< manager */,\n  MtrNode *treenode /**< current tree node */,\n  int multiplicity /**< how many %ZDD vars per %BDD var */,\n  char *vmask /**< variable pairs for which a group has been already built */,\n  char *lmask /**< levels for which a group has already been built*/)\n{\n    int startV, stopV, startL;\n    int i, j;\n    MtrNode *auxnode = treenode;\n\n    while (auxnode != NULL) {\n\tif (auxnode->child != NULL) {\n\t    addMultiplicityGroups(dd,auxnode->child,multiplicity,vmask,lmask);\n\t}\n\t/* Build remaining groups. */\n\tstartV = dd->permZ[auxnode->index] / multiplicity;\n\tstartL = auxnode->low / multiplicity;\n\tstopV = startV + auxnode->size / multiplicity;\n\t/* Walk down vmask starting at startV and build missing groups. */\n\tfor (i = startV, j = startL; i < stopV; i++) {\n\t    if (vmask[i] == 0) {\n\t\tMtrNode *node;\n\t\twhile (lmask[j] == 1) j++;\n\t\tnode = Mtr_MakeGroup(auxnode, j * multiplicity, multiplicity,\n\t\t\t\t     MTR_FIXED);\n\t\tif (node == NULL) {\n\t\t    return(0);\n\t\t}\n\t\tnode->index = dd->invpermZ[i * multiplicity];\n\t\tvmask[i] = 1;\n\t\tlmask[j] = 1;\n\t    }\n\t}\n\tauxnode = auxnode->younger;\n    }\n    return(1);\n\n} /* end of addMultiplicityGroups */\n"
  },
  {
    "path": "cudd/cudd/cuddAddAbs.c",
    "content": "/**\n  @file \n\n  @ingroup cudd\n\n  @brief Quantification functions for ADDs.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int addCheckPositiveCube (DdManager *manager, DdNode *cube);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Existentially Abstracts all the variables in cube from f.\n\n  @details Abstracts all the variables in cube from f by summing\n  over all possible values taken by the variables.\n\n  @return the abstracted %ADD.\n\n  @sideeffect None\n\n  @see Cudd_addUnivAbstract Cudd_bddExistAbstract\n  Cudd_addOrAbstract\n\n*/\nDdNode *\nCudd_addExistAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode *res;\n\n    if (addCheckPositiveCube(manager, cube) == 0) {\n        (void) fprintf(manager->err,\"Error: Can only abstract cubes\");\n        return(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddAddExistAbstractRecur(manager, f, cube);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_addExistAbstract */\n\n\n/**\n  @brief Universally Abstracts all the variables in cube from f.\n\n  @details Abstracts all the variables in cube from f by taking\n  the product over all possible values taken by the variable.\n\n  @return the abstracted %ADD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addExistAbstract Cudd_bddUnivAbstract\n  Cudd_addOrAbstract\n\n*/\nDdNode *\nCudd_addUnivAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode\t\t*res;\n\n    if (addCheckPositiveCube(manager, cube) == 0) {\n\t(void) fprintf(manager->err,\"Error:  Can only abstract cubes\");\n\treturn(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddAddUnivAbstractRecur(manager, f, cube);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_addUnivAbstract */\n\n\n/**\n  @brief Disjunctively abstracts all the variables in cube from the\n  0-1 %ADD f.\n\n  @details Abstracts all the variables in cube from the 0-1 %ADD f\n  by taking the disjunction over all possible values taken by the\n  variables.\n\n  @return the abstracted %ADD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addUnivAbstract Cudd_addExistAbstract\n\n*/\nDdNode *\nCudd_addOrAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode *res;\n\n    if (addCheckPositiveCube(manager, cube) == 0) {\n        (void) fprintf(manager->err,\"Error: Can only abstract cubes\");\n        return(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddAddOrAbstractRecur(manager, f, cube);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addOrAbstract */\n\n\n/**\n\n  @brief Abstracts all the variables in cube from the\n  ADD f by taking the minimum.\n\n  @details Abstracts all the variables in cube from the ADD f\n  by taking the minimum over all possible values taken by the\n  variables.\n  \n  @return the abstracted ADD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addUnivAbstract Cudd_addExistAbstract\n  \n*/\nDdNode *\nCudd_addMinAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode *res;\n\n    if (addCheckPositiveCube(manager, cube) == 0) {\n        (void) fprintf(manager->err,\"Error: Can only abstract cubes\");\n        return(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddAddMinAbstractRecur(manager, f, cube);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addMinAbstract */\n\n\n/**\n\n  @brief Abstracts all the variables in cube from the\n  ADD f by taking the maximum.\n\n  @details Abstracts all the variables in cube from the ADD f\n  by taking the maximum over all possible values taken by the\n  variables.\n  \n  @return the abstracted ADD if successful; NULL otherwise.\n  \n  @sideeffect None\n\n  @see Cudd_addUnivAbstract Cudd_addExistAbstract\n  \n*/\nDdNode *\nCudd_addMaxAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode *res;\n\n    if (addCheckPositiveCube(manager, cube) == 0) {\n        (void) fprintf(manager->err,\"Error: Can only abstract cubes\");\n        return(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddAddMaxAbstractRecur(manager, f, cube);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addMaxAbstract */\n\n\n/**\n\n  @brief Filters over all the variables in cube from the\n  ADD f by taking the first element.\n\n  @details Filters over all the variables in cube from the ADD f\n  by taking the first of all possible values taken by the\n  variables.\n  \n  @return the filtered ADD if successful; NULL otherwise.\n  \n  @sideeffect None\n\n  @see Cudd_addUnivAbstract Cudd_addExistAbstract\n  \n*/\nDdNode *\nCudd_addFirstFilter(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode *res;\n\n    if (addCheckPositiveCube(manager, cube) == 0) {\n        (void) fprintf(manager->err,\"Error: Can only abstract cubes\");\n        return(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddAddFirstFilterRecur(manager, f, cube);\n    } while (manager->reordered == 1);\n    return(res);\n\n} /* end of Cudd_addFirstFilter */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_addExistAbstract.\n\n  @details Returns the %ADD obtained by abstracting the variables of\n  cube from f, if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddExistAbstractRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode\t*T, *E, *res, *res1, *res2, *zero;\n\n    statLine(manager);\n    zero = DD_ZERO(manager);\n\n    /* Cube is guaranteed to be a cube at this point. */\t\n    if (f == zero || cuddIsConstant(cube)) {  \n        return(f);\n    }\n\n    /* Abstract a variable that does not appear in f => multiply by 2. */\n    if (cuddI(manager,f->index) > cuddI(manager,cube->index)) {\n\tres1 = cuddAddExistAbstractRecur(manager, f, cuddT(cube));\n\tif (res1 == NULL) return(NULL);\n\tcuddRef(res1);\n\t/* Use the \"internal\" procedure to be alerted in case of\n\t** dynamic reordering. If dynamic reordering occurs, we\n\t** have to abort the entire abstraction.\n\t*/\n\tres = cuddAddApplyRecur(manager,Cudd_addPlus,res1,res1);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDeref(manager,res1);\n\tcuddDeref(res);\n        return(res);\n    }\n\n    if ((res = cuddCacheLookup2(manager, Cudd_addExistAbstract, f, cube)) != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    T = cuddT(f);\n    E = cuddE(f);\n\n    /* If the two indices are the same, so are their levels. */\n    if (f->index == cube->index) {\n\tres1 = cuddAddExistAbstractRecur(manager, T, cuddT(cube));\n\tif (res1 == NULL) return(NULL);\n        cuddRef(res1);\n\tres2 = cuddAddExistAbstractRecur(manager, E, cuddT(cube));\n\tif (res2 == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    return(NULL);\n\t}\n        cuddRef(res2);\n\tres = cuddAddApplyRecur(manager, Cudd_addPlus, res1, res2);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    Cudd_RecursiveDeref(manager,res2);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDeref(manager,res1);\n\tCudd_RecursiveDeref(manager,res2);\n\tcuddCacheInsert2(manager, Cudd_addExistAbstract, f, cube, res);\n\tcuddDeref(res);\n        return(res);\n    } else { /* if (cuddI(manager,f->index) < cuddI(manager,cube->index)) */\n\tres1 = cuddAddExistAbstractRecur(manager, T, cube);\n\tif (res1 == NULL) return(NULL);\n        cuddRef(res1);\n\tres2 = cuddAddExistAbstractRecur(manager, E, cube);\n\tif (res2 == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    return(NULL);\n\t}\n        cuddRef(res2);\n\tres = (res1 == res2) ? res1 :\n\t    cuddUniqueInter(manager, (int) f->index, res1, res2);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    Cudd_RecursiveDeref(manager,res2);\n\t    return(NULL);\n\t}\n\tcuddDeref(res1);\n\tcuddDeref(res2);\n\tcuddCacheInsert2(manager, Cudd_addExistAbstract, f, cube, res);\n        return(res);\n    }\t    \n\n} /* end of cuddAddExistAbstractRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addUnivAbstract.\n\n  @return the %ADD obtained by abstracting the variables of cube from\n  f, if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddUnivAbstractRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode\t*T, *E, *res, *res1, *res2, *one, *zero;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n    zero = DD_ZERO(manager);\n\n    /* Cube is guaranteed to be a cube at this point.\n    ** zero and one are the only constatnts c such that c*c=c.\n    */\n    if (f == zero || f == one || cube == one) {  \n\treturn(f);\n    }\n\n    /* Abstract a variable that does not appear in f. */\n    if (cuddI(manager,f->index) > cuddI(manager,cube->index)) {\n\tres1 = cuddAddUnivAbstractRecur(manager, f, cuddT(cube));\n\tif (res1 == NULL) return(NULL);\n\tcuddRef(res1);\n\t/* Use the \"internal\" procedure to be alerted in case of\n\t** dynamic reordering. If dynamic reordering occurs, we\n\t** have to abort the entire abstraction.\n\t*/\n\tres = cuddAddApplyRecur(manager, Cudd_addTimes, res1, res1);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDeref(manager,res1);\n\tcuddDeref(res);\n\treturn(res);\n    }\n\n    if ((res = cuddCacheLookup2(manager, Cudd_addUnivAbstract, f, cube)) != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    T = cuddT(f);\n    E = cuddE(f);\n\n    /* If the two indices are the same, so are their levels. */\n    if (f->index == cube->index) {\n\tres1 = cuddAddUnivAbstractRecur(manager, T, cuddT(cube));\n\tif (res1 == NULL) return(NULL);\n        cuddRef(res1);\n\tres2 = cuddAddUnivAbstractRecur(manager, E, cuddT(cube));\n\tif (res2 == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    return(NULL);\n\t}\n        cuddRef(res2);\n\tres = cuddAddApplyRecur(manager, Cudd_addTimes, res1, res2);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    Cudd_RecursiveDeref(manager,res2);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDeref(manager,res1);\n\tCudd_RecursiveDeref(manager,res2);\n\tcuddCacheInsert2(manager, Cudd_addUnivAbstract, f, cube, res);\n\tcuddDeref(res);\n        return(res);\n    } else { /* if (cuddI(manager,f->index) < cuddI(manager,cube->index)) */\n\tres1 = cuddAddUnivAbstractRecur(manager, T, cube);\n\tif (res1 == NULL) return(NULL);\n        cuddRef(res1);\n\tres2 = cuddAddUnivAbstractRecur(manager, E, cube);\n\tif (res2 == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    return(NULL);\n\t}\n        cuddRef(res2);\n\tres = (res1 == res2) ? res1 :\n\t    cuddUniqueInter(manager, (int) f->index, res1, res2);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    Cudd_RecursiveDeref(manager,res2);\n\t    return(NULL);\n\t}\n\tcuddDeref(res1);\n\tcuddDeref(res2);\n\tcuddCacheInsert2(manager, Cudd_addUnivAbstract, f, cube, res);\n        return(res);\n    }\n\n} /* end of cuddAddUnivAbstractRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addOrAbstract.\n\n  @return the %ADD obtained by abstracting the variables of cube from\n  f, if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddOrAbstractRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode\t*T, *E, *res, *res1, *res2, *one;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n\n    /* Cube is guaranteed to be a cube at this point. */\n    if (cuddIsConstant(f) || cube == one) {  \n\treturn(f);\n    }\n\n    /* Abstract a variable that does not appear in f. */\n    if (cuddI(manager,f->index) > cuddI(manager,cube->index)) {\n\tres = cuddAddOrAbstractRecur(manager, f, cuddT(cube));\n\treturn(res);\n    }\n\n    if ((res = cuddCacheLookup2(manager, Cudd_addOrAbstract, f, cube)) != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    T = cuddT(f);\n    E = cuddE(f);\n\n    /* If the two indices are the same, so are their levels. */\n    if (f->index == cube->index) {\n\tres1 = cuddAddOrAbstractRecur(manager, T, cuddT(cube));\n\tif (res1 == NULL) return(NULL);\n        cuddRef(res1);\n\tif (res1 != one) {\n\t    res2 = cuddAddOrAbstractRecur(manager, E, cuddT(cube));\n\t    if (res2 == NULL) {\n\t\tCudd_RecursiveDeref(manager,res1);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(res2);\n\t    res = cuddAddApplyRecur(manager, Cudd_addOr, res1, res2);\n\t    if (res == NULL) {\n\t\tCudd_RecursiveDeref(manager,res1);\n\t\tCudd_RecursiveDeref(manager,res2);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(res);\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    Cudd_RecursiveDeref(manager,res2);\n\t} else {\n\t    res = res1;\n\t}\n\tcuddCacheInsert2(manager, Cudd_addOrAbstract, f, cube, res);\n\tcuddDeref(res);\n        return(res);\n    } else { /* if (cuddI(manager,f->index) < cuddI(manager,cube->index)) */\n\tres1 = cuddAddOrAbstractRecur(manager, T, cube);\n\tif (res1 == NULL) return(NULL);\n        cuddRef(res1);\n\tres2 = cuddAddOrAbstractRecur(manager, E, cube);\n\tif (res2 == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    return(NULL);\n\t}\n        cuddRef(res2);\n\tres = (res1 == res2) ? res1 :\n\t    cuddUniqueInter(manager, (int) f->index, res1, res2);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(manager,res1);\n\t    Cudd_RecursiveDeref(manager,res2);\n\t    return(NULL);\n\t}\n\tcuddDeref(res1);\n\tcuddDeref(res2);\n\tcuddCacheInsert2(manager, Cudd_addOrAbstract, f, cube, res);\n        return(res);\n    }\n\n} /* end of cuddAddOrAbstractRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addMinAbstract.\n\n  @return the %ADD obtained by abstracting the variables of cube from\n  f, if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddMinAbstractRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n\tDdNode\t*T, *E, *res, *res1, *res2, *zero;\n\n\tzero = DD_ZERO(manager);\n\n\t/* Cube is guaranteed to be a cube at this point. */\t\n\tif (f == zero || cuddIsConstant(cube)) {  \n\t\treturn(f);\n\t}\n\n    /* Abstract a variable that does not appear in f. */\n\tif (cuddI(manager,f->index) > cuddI(manager,cube->index)) {\n\t\tres = cuddAddMinAbstractRecur(manager, f, cuddT(cube));\n       \treturn(res);\n\t}\n\n\tif ((res = cuddCacheLookup2(manager, Cudd_addMinAbstract, f, cube)) != NULL) {\n\t\treturn(res);\n\t}\n\n    checkWhetherToGiveUp(manager);\n\n\tT = cuddT(f);\n\tE = cuddE(f);\n\n\t/* If the two indices are the same, so are their levels. */\n\tif (f->index == cube->index) {\n\t\tres1 = cuddAddMinAbstractRecur(manager, T, cuddT(cube));\n\t\tif (res1 == NULL) return(NULL);\n        \tcuddRef(res1);\n\t\tres2 = cuddAddMinAbstractRecur(manager, E, cuddT(cube));\n\t\tif (res2 == NULL) {\n\t    \t\tCudd_RecursiveDeref(manager,res1);\n\t    \t\treturn(NULL);\n\t\t}\n\t\tcuddRef(res2);\n\t\tres = cuddAddApplyRecur(manager, Cudd_addMinimum, res1, res2);\n\t\tif (res == NULL) {\n\t  \t\t  Cudd_RecursiveDeref(manager,res1);\n\t   \t\t Cudd_RecursiveDeref(manager,res2);\n\t  \t\t  return(NULL);\n\t\t}\n\t\tcuddRef(res);\n\t\tCudd_RecursiveDeref(manager,res1);\n\t\tCudd_RecursiveDeref(manager,res2);\n\t\tcuddCacheInsert2(manager, Cudd_addMinAbstract, f, cube, res);\n\t\tcuddDeref(res);\n        \treturn(res);\n    \t}\n\telse { /* if (cuddI(manager,f->index) < cuddI(manager,cube->index)) */\n\t\tres1 = cuddAddMinAbstractRecur(manager, T, cube);\n\t\tif (res1 == NULL) return(NULL);\n        \tcuddRef(res1);\n\t\tres2 = cuddAddMinAbstractRecur(manager, E, cube);\n\t\tif (res2 == NULL) {\n\t\t\tCudd_RecursiveDeref(manager,res1);\n\t\t\treturn(NULL);\n\t\t}\n        \tcuddRef(res2);\n\t\tres = (res1 == res2) ? res1 :\n\t\t    cuddUniqueInter(manager, (int) f->index, res1, res2);\n\t\tif (res == NULL) {\n\t   \t\t Cudd_RecursiveDeref(manager,res1);\n\t    \t\tCudd_RecursiveDeref(manager,res2);\n\t    \t\treturn(NULL);\n\t\t}\n\t\tcuddDeref(res1);\n\t\tcuddDeref(res2);\n\t\tcuddCacheInsert2(manager, Cudd_addMinAbstract, f, cube, res);\n        \treturn(res);\n\t}\n\t    \n} /* end of cuddAddMinAbstractRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addMaxAbstract.\n\n  @return the %ADD obtained by abstracting the variables of cube from\n  f, if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddMaxAbstractRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n\tDdNode\t*T, *E, *res, *res1, *res2, *zero;\n\n\tzero = DD_ZERO(manager);\n\n\t/* Cube is guaranteed to be a cube at this point. */\t\n\tif (f == zero || cuddIsConstant(cube)) {  \n\t\treturn(f);\n\t}\n\n    /* Abstract a variable that does not appear in f. */\n\tif (cuddI(manager,f->index) > cuddI(manager,cube->index)) {\n\t\tres = cuddAddMaxAbstractRecur(manager, f, cuddT(cube));\n       \treturn(res);\n\t}\n\n\tif ((res = cuddCacheLookup2(manager, Cudd_addMaxAbstract, f, cube)) != NULL) {\n\t\treturn(res);\n\t}\n\n    checkWhetherToGiveUp(manager);\n\n\tT = cuddT(f);\n\tE = cuddE(f);\n\n\t/* If the two indices are the same, so are their levels. */\n\tif (f->index == cube->index) {\n\t\tres1 = cuddAddMaxAbstractRecur(manager, T, cuddT(cube));\n\t\tif (res1 == NULL) return(NULL);\n        \tcuddRef(res1);\n\t\tres2 = cuddAddMaxAbstractRecur(manager, E, cuddT(cube));\n\t\tif (res2 == NULL) {\n\t    \t\tCudd_RecursiveDeref(manager,res1);\n\t    \t\treturn(NULL);\n\t\t}\n\t\tcuddRef(res2);\n\t\tres = cuddAddApplyRecur(manager, Cudd_addMaximum, res1, res2);\n\t\tif (res == NULL) {\n\t  \t\t  Cudd_RecursiveDeref(manager,res1);\n\t   \t\t Cudd_RecursiveDeref(manager,res2);\n\t  \t\t  return(NULL);\n\t\t}\n\t\tcuddRef(res);\n\t\tCudd_RecursiveDeref(manager,res1);\n\t\tCudd_RecursiveDeref(manager,res2);\n\t\tcuddCacheInsert2(manager, Cudd_addMaxAbstract, f, cube, res);\n\t\tcuddDeref(res);\n        \treturn(res);\n    \t}\n\telse { /* if (cuddI(manager,f->index) < cuddI(manager,cube->index)) */\n\t\tres1 = cuddAddMaxAbstractRecur(manager, T, cube);\n\t\tif (res1 == NULL) return(NULL);\n        \tcuddRef(res1);\n\t\tres2 = cuddAddMaxAbstractRecur(manager, E, cube);\n\t\tif (res2 == NULL) {\n\t\t\tCudd_RecursiveDeref(manager,res1);\n\t\t\treturn(NULL);\n\t\t}\n        \tcuddRef(res2);\n\t\tres = (res1 == res2) ? res1 :\n\t\t    cuddUniqueInter(manager, (int) f->index, res1, res2);\n\t\tif (res == NULL) {\n\t   \t\t Cudd_RecursiveDeref(manager,res1);\n\t    \t\tCudd_RecursiveDeref(manager,res2);\n\t    \t\treturn(NULL);\n\t\t}\n\t\tcuddDeref(res1);\n\t\tcuddDeref(res2);\n\t\tcuddCacheInsert2(manager, Cudd_addMaxAbstract, f, cube, res);\n        \treturn(res);\n\t}\t    \n\n} /* end of cuddAddMaxAbstractRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addFirstFilterRecur.\n\n  @return the %ADD obtained by filtering the variables of cube from\n  f, if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddFirstFilterRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n\tDdNode\t*T, *E, *res, *res1, *res2, *zero;\n\n\tzero = DD_ZERO(manager);\n\n\t/* Cube is guaranteed to be a cube at this point. */\t\n\tif (f == zero || cuddIsConstant(cube)) { \n\t\treturn(f);\n\t}\n\n\tif ((res = cuddCacheLookup2(manager, Cudd_addFirstFilter, f, cube)) != NULL) {\n\t\treturn(res);\n\t}\n\n    checkWhetherToGiveUp(manager);\n\n\tT = cuddT(f);\n\tE = cuddE(f);\n\n    /* Case where a variable that does not appear in f. */\n\tif (cuddI(manager,f->index) > cuddI(manager,cube->index)) {\n\t\tres1 = zero;\n\t\tres2 = cuddAddFirstFilterRecur(manager, f, cuddT(cube));\n\t\tres = (res1 == res2) ? res1 :\n\t\t    cuddUniqueInter(manager, (int) cube->index, res1, res2);\n\t\tif (res == NULL) {\n\t   \t\tCudd_RecursiveDeref(manager,res1);\n\t    \tCudd_RecursiveDeref(manager,res2);\n\t    \treturn(NULL);\n\t\t}\n\t\tcuddCacheInsert2(manager, Cudd_addFirstFilter, f, cube, res);\n        return(res);\n\t}\n\n\t/* If the two indices are the same, so are their levels. */\n\tif (f->index == cube->index) {\n\t\tres2 = cuddAddFirstFilterRecur(manager, E, cuddT(cube));\n\t\tif (res2 == NULL) return(NULL);\n        cuddRef(res2);\n\t\tif (res2 != zero) {\n\t\t\tres1 = zero;\n\t\t} else {\n\t\t\tres1 = cuddAddFirstFilterRecur(manager, T, cuddT(cube));\n\t\t\tif (res1 == NULL) {\n\t\t\t\t\tCudd_RecursiveDeref(manager, res2);\n\t\t\t\t\treturn(NULL);\n\t\t\t}\n\t\t\tcuddRef(res1);\n\t\t}\n\t\tres = (res1 == res2) ? res1 :\n\t\t    cuddUniqueInter(manager, (int) cube->index, res1, res2);\n\t\tif (res == NULL) {\n\t   \t\tCudd_RecursiveDeref(manager, res1);\n\t    \tCudd_RecursiveDeref(manager, res2);\n\t    \treturn(NULL);\n\t\t}\n\t\tcuddCacheInsert2(manager, Cudd_addFirstFilter, f, cube, res);\n        return(res);\n    }\n\telse { /* if (cuddI(manager,f->index) < cuddI(manager,cube->index)) */\n\t\tres1 = cuddAddFirstFilterRecur(manager, T, cube);\n\t\tif (res1 == NULL) return(NULL);\n        \tcuddRef(res1);\n\t\tres2 = cuddAddFirstFilterRecur(manager, E, cube);\n\t\tif (res2 == NULL) {\n\t\t\tCudd_RecursiveDeref(manager,res1);\n\t\t\treturn(NULL);\n\t\t}\n        \tcuddRef(res2);\n\t\tres = (res1 == res2) ? res1 :\n\t\t    cuddUniqueInter(manager, (int) f->index, res1, res2);\n\t\tif (res == NULL) {\n\t   \t\t Cudd_RecursiveDeref(manager,res1);\n\t    \t\tCudd_RecursiveDeref(manager,res2);\n\t    \t\treturn(NULL);\n\t\t}\n\t\tcuddDeref(res1);\n\t\tcuddDeref(res2);\n\t\tcuddCacheInsert2(manager, Cudd_addFirstFilter, f, cube, res);\n        \treturn(res);\n\t}\t    \n\n} /* end of cuddAddFirstFilterRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Checks whether cube is an %ADD representing the product\n  of positive literals.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\naddCheckPositiveCube(\n  DdManager * manager,\n  DdNode * cube)\n{\n    if (Cudd_IsComplement(cube)) return(0);\n    if (cube == DD_ONE(manager)) return(1);\n    if (cuddIsConstant(cube)) return(0);\n    if (cuddE(cube) == DD_ZERO(manager)) {\n        return(addCheckPositiveCube(manager, cuddT(cube)));\n    }\n    return(0);\n\n} /* end of addCheckPositiveCube */\n"
  },
  {
    "path": "cudd/cudd/cuddAddApply.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Apply functions for ADDs and their operators.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Applies op to the corresponding discriminants of f and g.\n\n  @return a pointer to the result if succssful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addMonadicApply Cudd_addPlus Cudd_addTimes\n  Cudd_addThreshold Cudd_addSetNZ Cudd_addDivide Cudd_addMinus Cudd_addMinimum\n  Cudd_addMaximum Cudd_addOneZeroMaximum Cudd_addDiff Cudd_addAgreement\n  Cudd_addOr Cudd_addNand Cudd_addNor Cudd_addXor Cudd_addXnor\n\n*/\nDdNode *\nCudd_addApply(\n  DdManager * dd /**< manager */,\n  DD_AOP op /**< operator */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddApplyRecur(dd,op,f,g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_addApply */\n\n\n/**\n  @brief Integer and floating point addition.\n\n  @return NULL if not a terminal case; f+g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addPlus(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *res;\n    DdNode *F, *G;\n    CUDD_VALUE_TYPE value;\n\n    F = *f; G = *g;\n    if (F == DD_ZERO(dd)) return(G);\n    if (G == DD_ZERO(dd)) return(F);\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tvalue = cuddV(F)+cuddV(G);\n\tres = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addPlus */\n\n\n/**\n  @brief Integer and floating point multiplication.\n\n  @details This function can be used also to take the AND of two 0-1\n  ADDs.\n\n  @return NULL if not a terminal case; f * g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addTimes(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *res;\n    DdNode *F, *G;\n    CUDD_VALUE_TYPE value;\n\n    F = *f; G = *g;\n    if (F == DD_ZERO(dd) || G == DD_ZERO(dd)) return(DD_ZERO(dd));\n    if (F == DD_ONE(dd)) return(G);\n    if (G == DD_ONE(dd)) return(F);\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tvalue = cuddV(F)*cuddV(G);\n\tres = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addTimes */\n\n\n/**\n  @brief f if f&ge;g; 0 if f&lt;g.\n\n  @details Threshold operator for Apply (f if f &ge;g; 0 if f&lt;g).\n\n  @return NULL if not a terminal case; f op g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addThreshold(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G || F == DD_PLUS_INFINITY(dd)) return(F);\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tif (cuddV(F) >= cuddV(G)) {\n\t    return(F);\n\t} else {\n\t    return(DD_ZERO(dd));\n\t}\n    }\n    return(NULL);\n\n} /* end of Cudd_addThreshold */\n\n\n/**\n  @brief This operator sets f to the value of g wherever g != 0.\n\n  @return NULL if not a terminal case; f op g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addSetNZ(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(F);\n    if (F == DD_ZERO(dd)) return(G);\n    if (G == DD_ZERO(dd)) return(F);\n    if (cuddIsConstant(G)) return(G);\n    return(NULL);\n\n} /* end of Cudd_addSetNZ */\n\n\n/**\n  @brief Integer and floating point division.\n\n  @return NULL if not a terminal case; f / g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addDivide(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *res;\n    DdNode *F, *G;\n    CUDD_VALUE_TYPE value;\n\n    F = *f; G = *g;\n    /* We would like to use F == G -> F/G == 1, but F and G may\n    ** contain zeroes. */\n    if (F == DD_ZERO(dd)) return(DD_ZERO(dd));\n    if (G == DD_ONE(dd)) return(F);\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tvalue = cuddV(F)/cuddV(G);\n\tres = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    return(NULL);\n\n} /* end of Cudd_addDivide */\n\n\n/**\n  @brief Integer and floating point subtraction.\n\n  @return NULL if not a terminal case; f - g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addMinus(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *res;\n    DdNode *F, *G;\n    CUDD_VALUE_TYPE value;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ZERO(dd));\n    if (F == DD_ZERO(dd)) return(cuddAddNegateRecur(dd,G));\n    if (G == DD_ZERO(dd)) return(F);\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tvalue = cuddV(F)-cuddV(G);\n\tres = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    return(NULL);\n\n} /* end of Cudd_addMinus */\n\n\n/**\n  @brief Integer and floating point min.\n\n  @details Integer and floating point min for Cudd_addApply.\n  \n  @return NULL if not a terminal case; min(f,g) otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addMinimum(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == DD_PLUS_INFINITY(dd)) return(G);\n    if (G == DD_PLUS_INFINITY(dd)) return(F);\n    if (F == G) return(F);\n#if 0\n    /* These special cases probably do not pay off. */\n    if (F == DD_MINUS_INFINITY(dd)) return(F);\n    if (G == DD_MINUS_INFINITY(dd)) return(G);\n#endif\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tif (cuddV(F) <= cuddV(G)) {\n\t    return(F);\n\t} else {\n\t    return(G);\n\t}\n    }\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addMinimum */\n\n\n/**\n  @brief Integer and floating point max.\n\n  @details Integer and floating point max for Cudd_addApply.\n\n  @return NULL if not a terminal case; max(f,g) otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addMaximum(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(F);\n    if (F == DD_MINUS_INFINITY(dd)) return(G);\n    if (G == DD_MINUS_INFINITY(dd)) return(F);\n#if 0\n    /* These special cases probably do not pay off. */\n    if (F == DD_PLUS_INFINITY(dd)) return(F);\n    if (G == DD_PLUS_INFINITY(dd)) return(G);\n#endif\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tif (cuddV(F) >= cuddV(G)) {\n\t    return(F);\n\t} else {\n\t    return(G);\n\t}\n    }\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addMaximum */\n\n\n/**\n  @brief Returns 1 if f &gt; g and 0 otherwise.\n\n  @details Used in conjunction with Cudd_addApply.\n\n  @return NULL if not a terminal case.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addOneZeroMaximum(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n\n    if (*f == *g) return(DD_ZERO(dd));\n    if (*g == DD_PLUS_INFINITY(dd))\n\treturn DD_ZERO(dd);\n    if (cuddIsConstant(*f) && cuddIsConstant(*g)) {\n\tif (cuddV(*f) > cuddV(*g)) {\n\t    return(DD_ONE(dd));\n\t} else {\n\t    return(DD_ZERO(dd));\n\t}\n    }\n\n    return(NULL);\n\n} /* end of Cudd_addOneZeroMaximum */\n\n\n/**\n  @brief Returns plusinfinity if f=g; returns min(f,g) if f!=g.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g\n  is plusinfinity if f=g; min(f,g) if f!=g.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addDiff(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_PLUS_INFINITY(dd));\n    if (F == DD_PLUS_INFINITY(dd)) return(G);\n    if (G == DD_PLUS_INFINITY(dd)) return(F);\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tif (cuddV(F) != cuddV(G)) {\n\t    if (cuddV(F) < cuddV(G)) {\n\t\treturn(F);\n\t    } else {\n\t\treturn(G);\n\t    }\n\t} else {\n\t    return(DD_PLUS_INFINITY(dd));\n\t}\n    }\n    return(NULL);\n\n} /* end of Cudd_addDiff */\n\n\n/**\n  @brief f if f==g; background if f!=g.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g\n  is f if f==g; background if f!=g.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addAgreement(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(F);\n    if (F == dd->background) return(F);\n    if (G == dd->background) return(G);\n    if (cuddIsConstant(F) && cuddIsConstant(G)) return(dd->background);\n    return(NULL);\n\n} /* end of Cudd_addAgreement */\n\n\n/**\n  @brief Disjunction of two 0-1 ADDs.\n\n  @return NULL if not a terminal case; f OR g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addOr(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == DD_ONE(dd) || G == DD_ONE(dd)) return(DD_ONE(dd));\n    if (cuddIsConstant(F)) return(G);\n    if (cuddIsConstant(G)) return(F);\n    if (F == G) return(F);\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addOr */\n\n\n/**\n  @brief NAND of two 0-1 ADDs.\n\n  @return NULL if not a terminal case; f NAND g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addNand(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == DD_ZERO(dd) || G == DD_ZERO(dd)) return(DD_ONE(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) return(DD_ZERO(dd));\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addNand */\n\n\n/**\n  @brief NOR of two 0-1 ADDs.\n\n  @return NULL if not a terminal case; f NOR g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addNor(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == DD_ONE(dd) || G == DD_ONE(dd)) return(DD_ZERO(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) return(DD_ONE(dd));\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addNor */\n\n\n/**\n  @brief XOR of two 0-1 ADDs.\n\n  @return NULL if not a terminal case; f XOR g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addXor(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ZERO(dd));\n    if (F == DD_ONE(dd) && G == DD_ZERO(dd)) return(DD_ONE(dd));\n    if (G == DD_ONE(dd) && F == DD_ZERO(dd)) return(DD_ONE(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) return(DD_ZERO(dd));\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addXor */\n\n\n/**\n  @brief XNOR of two 0-1 ADDs.\n\n  @return NULL if not a terminal case; f XNOR g otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addXnor(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ONE(dd));\n    if (F == DD_ONE(dd) && G == DD_ONE(dd)) return(DD_ONE(dd));\n    if (G == DD_ZERO(dd) && F == DD_ZERO(dd)) return(DD_ONE(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) return(DD_ZERO(dd));\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addXnor */\n\n\n/**\n  @brief Applies op to the discriminants of f.\n\n  @return a pointer to the result if succssful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply Cudd_addLog\n\n*/\nDdNode *\nCudd_addMonadicApply(\n  DdManager * dd,\n  DD_MAOP op,\n  DdNode * f)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddMonadicApplyRecur(dd,op,f);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_addMonadicApply */\n\n\n/**\n  @brief Natural logarithm of an %ADD.\n\n  @details The discriminants of f must be positive double's.\n\n  @return NULL if not a terminal case; log(f) otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addMonadicApply\n\n*/\nDdNode *\nCudd_addLog(\n  DdManager * dd,\n  DdNode * f)\n{\n    if (cuddIsConstant(f)) {\n\tCUDD_VALUE_TYPE value = log(cuddV(f));\n\tDdNode *res = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    return(NULL);\n\n} /* end of Cudd_addLog */\n\n\n/**\n  @brief Floor of an ADD.\n\n  @return NULL if not a terminal case; floor(f) otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addMonadicApply\n\n*/\nDdNode *\nCudd_addFloor(\n  DdManager * dd,\n  DdNode * f)\n{\n    if (cuddIsConstant(f)) {\n\tCUDD_VALUE_TYPE value = floor(cuddV(f));\n\tDdNode *res = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    return(NULL);\n\n} /* end of Cudd_addFloor */\n\n\n/**\n  @brief Ceiling of an ADD.\n\n  @return NULL if not a terminal case; ceil(f) otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addMonadicApply\n\n*/\nDdNode *\nCudd_addCeil(\n  DdManager * dd,\n  DdNode * f)\n{\n    if (cuddIsConstant(f)) {\n\tCUDD_VALUE_TYPE value = ceil(cuddV(f));\n\tDdNode *res = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    return(NULL);\n\n} /* end of Cudd_addCeiling */\n\n\n/**\n  @brief 1 if f==g; 0 otherwise.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is 1 if f==g; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addEquals(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ONE(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) return(DD_ZERO(dd));\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addEquals */\n\n\n/**\n  @brief 1 if f!=g; 0 otherwise.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is 1 if f!=g; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addNotEquals(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ZERO(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) return(DD_ONE(dd));\n    if (F > G) { /* swap f and g */\n\t*f = G;\n\t*g = F;\n    }\n    return(NULL);\n\n} /* end of Cudd_addNotEquals */\n\n\n/**\n  @brief 1 if f>g; 0 otherwise.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is 1 if f>g; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addGreaterThan(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ZERO(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\t\tif (cuddV(F)>cuddV(G)) return (DD_ONE(dd)); else return (DD_ZERO(dd));\n    }\n    return(NULL);\n\n} /* end of Cudd_addGreaterThan */\n\n\n/**\n  @brief 1 if f>=g; 0 otherwise.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is 1 if f>=g; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addGreaterThanEquals(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ONE(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\t\tif (cuddV(F)>=cuddV(G)) return (DD_ONE(dd)); else return (DD_ZERO(dd));\n    }\n    return(NULL);\n\n} /* end of Cudd_addGreaterThanEquals */\n\n\n/**\n  @brief 1 if f<g; 0 otherwise.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is 1 if f<g; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addLessThan(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ZERO(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\t\tif (cuddV(F)<cuddV(G)) return (DD_ONE(dd)); else return (DD_ZERO(dd));\n    }\n    return(NULL);\n\n} /* end of Cudd_addLessThan */\n\n\n/**\n  @brief 1 if f<=g; 0 otherwise.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is 1 if f<=g; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addLessThanEquals(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *F, *G;\n\n    F = *f; G = *g;\n    if (F == G) return(DD_ONE(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\t\tif (cuddV(F)<=cuddV(G)) return (DD_ONE(dd)); else return (DD_ZERO(dd));\n    }\n    return(NULL);\n\n} /* end of Cudd_addLessThanEquals */\n\n\n/**\n  @brief f to the power of g.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is f to the power of g.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addPow(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *res;\n    DdNode *F, *G;\n    CUDD_VALUE_TYPE value;\n\n    F = *f; G = *g;\n    if (G == DD_ZERO(dd)) return(DD_ONE(dd));\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\tvalue = pow(cuddV(F), cuddV(G));\n\tres = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    return(NULL);\n\n} /* end of Cudd_addPow */\n\n\n/**\n  @brief f modulo g.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is f modulo g.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addMod(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n    DdNode *res;\n    DdNode *F, *G;\n    int rem;\n    CUDD_VALUE_TYPE value;\n\n    F = *f; G = *g;\n    if (cuddIsConstant(F) && cuddIsConstant(G)) {\n\t// If g is <=0, then result is NaN\n\tif (cuddV(G) <= 0) value = (0.0/0.0);\n\t// Take care of negative case (% is remainder, not modulo)\n\telse {\n\t\trem = ((int)cuddV(F) % (int)cuddV(G));\n\t\tif (rem < 0) rem += (int)cuddV(G);\n\t\tvalue = rem;\n\t}\n\t// Create/return result\n\tres = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n    return(NULL);\n\n} /* end of Cudd_addMod */\n\n\n/**\n  @brief log f base g.\n\n  @return NULL if not a terminal case; f op g otherwise, where f op g is log f base g.\n\n  @sideeffect None\n\n  @see Cudd_addApply\n\n*/\nDdNode *\nCudd_addLogXY(\n  DdManager * dd,\n  DdNode ** f,\n  DdNode ** g)\n{\n\tDdNode *res;\n\tDdNode *F, *G;\n\tCUDD_VALUE_TYPE value;\n\n\tF = *f; G = *g;\n\tif (cuddIsConstant(F) && cuddIsConstant(G)) {\n\t// If base is <=0 or ==1 (or +Inf/NaN), then result is NaN\n\tif (cuddV(G) <= 0 || cuddV(G) == 1.0 || G==DD_PLUS_INFINITY(dd) || cuddV(G) != cuddV(G)) value = (0.0/0.0);\n\t// If arg is <0 or NaN, then result is NaN\n\telse if (cuddV(F) < 0 || cuddV(F) != cuddV(F)) value = (0.0/0.0);\n\t// If arg is +Inf, then result is +Inf\n\telse if (F==DD_PLUS_INFINITY(dd)) return DD_PLUS_INFINITY(dd);\n\t// If arg is (positive/negative) 0, then result is -Inf\n\telse if (cuddV(F) == 0.0 || cuddV(F) == -0.0) return DD_MINUS_INFINITY(dd);\n\t// Default case: normal log\n\telse value = log(cuddV(F)) / log(cuddV(G));\n\t// Create/return result\n\tres = cuddUniqueConst(dd,value);\n\treturn(res);\n\t}\n\treturn(NULL);\n\n} /* end of Cudd_addLogXY */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_addApply.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddAddMonadicApplyRecur\n\n*/\nDdNode *\ncuddAddApplyRecur(\n  DdManager * dd,\n  DD_AOP op,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *res,\n\t   *fv, *fvn, *gv, *gvn,\n\t   *T, *E;\n    int ford, gord;\n    unsigned int index;\n    DD_CTFP cacheOp;\n\n    /* Check terminal cases. Op may swap f and g to increase the\n     * cache hit rate.\n     */\n    statLine(dd);\n    res = (*op)(dd,&f,&g);\n    if (res != NULL) return(res);\n\n    /* Check cache. */\n    cacheOp = (DD_CTFP) op;\n    res = cuddCacheLookup2(dd,cacheOp,f,g);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    ford = cuddI(dd,f->index);\n    gord = cuddI(dd,g->index);\n    if (ford <= gord) {\n\tindex = f->index;\n\tfv = cuddT(f);\n\tfvn = cuddE(f);\n    } else {\n\tindex = g->index;\n\tfv = fvn = f;\n    }\n    if (gord <= ford) {\n\tgv = cuddT(g);\n\tgvn = cuddE(g);\n    } else {\n\tgv = gvn = g;\n    }\n\n    T = cuddAddApplyRecur(dd,op,fv,gv);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = cuddAddApplyRecur(dd,op,fvn,gvn);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd,T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    res = (T == E) ? T : cuddUniqueInter(dd,(int)index,T,E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\tCudd_RecursiveDeref(dd, E);\n\treturn(NULL);\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert2(dd,cacheOp,f,g,res);\n\n    return(res);\n\n} /* end of cuddAddApplyRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addMonadicApply.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddAddApplyRecur\n\n*/\nDdNode *\ncuddAddMonadicApplyRecur(\n  DdManager * dd,\n  DD_MAOP op,\n  DdNode * f)\n{\n    DdNode *res, *ft, *fe, *T, *E;\n    unsigned int index;\n\n    /* Check terminal cases. */\n    statLine(dd);\n    res = (*op)(dd,f);\n    if (res != NULL) return(res);\n\n    /* Check cache. */\n    res = cuddCacheLookup1(dd,op,f);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    index = f->index;\n    ft = cuddT(f);\n    fe = cuddE(f);\n\n    T = cuddAddMonadicApplyRecur(dd,op,ft);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = cuddAddMonadicApplyRecur(dd,op,fe);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd,T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    res = (T == E) ? T : cuddUniqueInter(dd,(int)index,T,E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\tCudd_RecursiveDeref(dd, E);\n\treturn(NULL);\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert1(dd,op,f,res);\n\n    return(res);\n\n} /* end of cuddAddMonadicApplyRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n"
  },
  {
    "path": "cudd/cudd/cuddAddFind.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions to find maximum and minimum in an %ADD and to\n  extract the i-th bit.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * addDoIthBit (DdManager *dd, DdNode *f, DdNode *index);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Finds the maximum discriminant of f.\n\n  @return a pointer to a constant %ADD.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_addFindMax(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *t, *e, *res;\n\n    statLine(dd);\n    if (cuddIsConstant(f)) {\n\treturn(f);\n    }\n\n    res = cuddCacheLookup1(dd,Cudd_addFindMax,f);\n    if (res != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    t  = Cudd_addFindMax(dd,cuddT(f));\n    if (t == DD_PLUS_INFINITY(dd)) return(t);\n\n    e  = Cudd_addFindMax(dd,cuddE(f));\n\n    res = (cuddV(t) >= cuddV(e)) ? t : e;\n\n    cuddCacheInsert1(dd,Cudd_addFindMax,f,res);\n\n    return(res);\n\n} /* end of Cudd_addFindMax */\n\n\n/**\n  @brief Finds the minimum discriminant of f.\n\n  @return a pointer to a constant %ADD.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_addFindMin(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *t, *e, *res;\n\n    statLine(dd);\n    if (cuddIsConstant(f)) {\n\treturn(f);\n    }\n\n    res = cuddCacheLookup1(dd,Cudd_addFindMin,f);\n    if (res != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    t  = Cudd_addFindMin(dd,cuddT(f));\n    if (t == DD_MINUS_INFINITY(dd)) return(t);\n\n    e  = Cudd_addFindMin(dd,cuddE(f));\n\n    res = (cuddV(t) <= cuddV(e)) ? t : e;\n\n    cuddCacheInsert1(dd,Cudd_addFindMin,f,res);\n\n    return(res);\n\n} /* end of Cudd_addFindMin */\n\n\n/**\n  @brief Extracts the i-th bit from an %ADD.\n\n  @details Produces an %ADD from another %ADD by replacing all\n  discriminants whose i-th bit is equal to 1 with 1, and all other\n  discriminants with 0. The i-th bit refers to the integer\n  representation of the leaf value. If the value has a fractional\n  part, it is ignored. Repeated calls to this procedure allow one to\n  transform an integer-valued %ADD into an array of ADDs, one for each\n  bit of the leaf values.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addBddIthBit\n\n*/\nDdNode *\nCudd_addIthBit(\n  DdManager * dd,\n  DdNode * f,\n  int  bit)\n{\n    DdNode *res;\n    DdNode *index;\n    \n    /* Use a constant node to remember the bit, so that we can use the\n    ** global cache.\n    */\n    index = cuddUniqueConst(dd,(CUDD_VALUE_TYPE) bit);\n    if (index == NULL) return(NULL);\n    cuddRef(index);\n\n    do {\n\tdd->reordered = 0;\n\tres = addDoIthBit(dd, f, index);\n    } while (dd->reordered == 1);\n\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, index);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd, index);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_addIthBit */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step for Cudd_addIthBit.\n\n  @return a pointer to the %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\naddDoIthBit(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * index)\n{\n    DdNode *res, *T, *E;\n    DdNode *fv, *fvn;\n    unsigned int mask, value;\n    DdHalfWord v;\n\n    statLine(dd);\n    /* Check terminal case. */\n    if (cuddIsConstant(f)) {\n\tmask = 1U << ((unsigned int) cuddV(index));\n\tvalue = (unsigned) (int) cuddV(f);\n\treturn((value & mask) == 0 ? DD_ZERO(dd) : DD_ONE(dd));\n    }\n\n    /* Check cache. */\n    res = cuddCacheLookup2(dd,addDoIthBit,f,index);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    v = f->index;\n    fv = cuddT(f); fvn = cuddE(f);\n\n    T = addDoIthBit(dd,fv,index);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = addDoIthBit(dd,fvn,index);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    res = (T == E) ? T : cuddUniqueInter(dd,v,T,E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\tCudd_RecursiveDeref(dd, E);\n\treturn(NULL);\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert2(dd,addDoIthBit,f,index,res);\n\n    return(res);\n\n} /* end of addDoIthBit */\n\n"
  },
  {
    "path": "cudd/cudd/cuddAddInv.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Function to compute the scalar inverse of an %ADD.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Computes the scalar inverse of an %ADD.\n  \n  @details Computes an n %ADD where the discriminants are the\n  multiplicative inverses of the corresponding discriminants of the\n  argument %ADD.\n\n  @return a pointer to the resulting %ADD in case of success. Returns\n  NULL if any discriminants smaller than epsilon is encountered.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_addScalarInverse(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * epsilon)\n{\n    DdNode *res;\n\n    if (!cuddIsConstant(epsilon)) {\n\t(void) fprintf(dd->err,\"Invalid epsilon\\n\");\n\treturn(NULL);\n    }\n    do {\n\tdd->reordered = 0;\n\tres  = cuddAddScalarInverseRecur(dd,f,epsilon);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addScalarInverse */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of addScalarInverse.\n\n  @return a pointer to the resulting %ADD in case of success. Returns\n  NULL if any discriminants smaller than epsilon is encountered.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddScalarInverseRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * epsilon)\n{\n    DdNode *t, *e, *res;\n    CUDD_VALUE_TYPE value;\n\n    statLine(dd);\n    if (cuddIsConstant(f)) {\n\tif (ddAbs(cuddV(f)) < cuddV(epsilon)) return(NULL);\n\tvalue = 1.0 / cuddV(f);\n\tres = cuddUniqueConst(dd,value);\n\treturn(res);\n    }\n\n    res = cuddCacheLookup2(dd,Cudd_addScalarInverse,f,epsilon);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    t = cuddAddScalarInverseRecur(dd,cuddT(f),epsilon);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n\n    e = cuddAddScalarInverseRecur(dd,cuddE(f),epsilon);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(dd, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    res = (t == e) ? t : cuddUniqueInter(dd,(int)f->index,t,e);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, t);\n\tCudd_RecursiveDeref(dd, e);\n\treturn(NULL);\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    cuddCacheInsert2(dd,Cudd_addScalarInverse,f,epsilon,res);\n\n    return(res);\n\n} /* end of cuddAddScalarInverseRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n"
  },
  {
    "path": "cudd/cudd/cuddAddIte.c",
    "content": "/**\n  @file \n\n  @ingroup cudd\n\n  @brief %ADD ITE function and satellites.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void addVarToConst (DdNode *f, DdNode **gp, DdNode **hp, DdNode *one, DdNode *zero);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements ITE(f,g,h).\n\n  @details This procedure assumes that f is a 0-1 %ADD.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddIte Cudd_addIteConstant Cudd_addApply\n\n*/\nDdNode *\nCudd_addIte(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddIteRecur(dd,f,g,h);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addIte */\n\n\n/**\n  @brief Implements ITEconstant for %ADDs.\n\n  @details f must be a 0-1 %ADD.  No new nodes are created. This\n  function can be used, for instance, to check that g has a constant\n  value (specified by h) whenever f is 1. If the constant value is\n  unknown, then one should use Cudd_addEvalConst.\n\n  @return a pointer to the resulting %ADD (which may or may not be\n  constant) or DD_NON_CONSTANT.\n\n  @sideeffect None\n\n  @see Cudd_addIte Cudd_addEvalConst Cudd_bddIteConstant\n\n*/\nDdNode *\nCudd_addIteConstant(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    DdNode *one,*zero;\n    DdNode *Fv,*Fnv,*Gv,*Gnv,*Hv,*Hnv,*r,*t,*e;\n    int topf,topg,toph,v;\n\n    statLine(dd);\n    /* Trivial cases. */\n    if (f == (one = DD_ONE(dd))) {\t/* ITE(1,G,H) = G */\n        return(g);\n    }\n    if (f == (zero = DD_ZERO(dd))) {\t/* ITE(0,G,H) = H */\n        return(h);\n    }\n\n    /* From now on, f is known not to be a constant. */\n    addVarToConst(f,&g,&h,one,zero);\n\n    /* Check remaining one variable cases. */\n    if (g == h) { \t\t\t/* ITE(F,G,G) = G */\n        return(g);\n    }\n    if (cuddIsConstant(g) && cuddIsConstant(h)) {\n        return(DD_NON_CONSTANT);\n    }\n\n    topf = cuddI(dd,f->index);\n    topg = cuddI(dd,g->index);\n    toph = cuddI(dd,h->index);\n    v = ddMin(topg,toph);\n\n    /* ITE(F,G,H) = (x,G,H) (non constant) if F = (x,1,0), x < top(G,H). */\n    if (topf < v && cuddIsConstant(cuddT(f)) && cuddIsConstant(cuddE(f))) {\n\treturn(DD_NON_CONSTANT);\n    }\n\n    /* Check cache. */\n    r = cuddConstantLookup(dd,DD_ADD_ITE_CONSTANT_TAG,f,g,h);\n    if (r != NULL) {\n        return(r);\n    }\n\n    /* Compute cofactors. */\n    if (topf <= v) {\n\tv = ddMin(topf,v);\t/* v = top_var(F,G,H) */\n        Fv = cuddT(f); Fnv = cuddE(f);\n    } else {\n        Fv = Fnv = f;\n    }\n    if (topg == v) {\n        Gv = cuddT(g); Gnv = cuddE(g);\n    } else {\n        Gv = Gnv = g;\n    }\n    if (toph == v) {\n        Hv = cuddT(h); Hnv = cuddE(h);\n    } else {\n        Hv = Hnv = h;\n    }\n    \n    /* Recursive step. */\n    t = Cudd_addIteConstant(dd,Fv,Gv,Hv);\n    if (t == DD_NON_CONSTANT || !cuddIsConstant(t)) {\n\tcuddCacheInsert(dd, DD_ADD_ITE_CONSTANT_TAG, f, g, h, DD_NON_CONSTANT);\n\treturn(DD_NON_CONSTANT);\n    }\n    e = Cudd_addIteConstant(dd,Fnv,Gnv,Hnv);\n    if (e == DD_NON_CONSTANT || !cuddIsConstant(e) || t != e) {\n\tcuddCacheInsert(dd, DD_ADD_ITE_CONSTANT_TAG, f, g, h, DD_NON_CONSTANT);\n\treturn(DD_NON_CONSTANT);\n    }\n    cuddCacheInsert(dd, DD_ADD_ITE_CONSTANT_TAG, f, g, h, t);\n    return(t);\n\n} /* end of Cudd_addIteConstant */\n\n\n/**\n  @brief Checks whether %ADD g is constant whenever %ADD f is 1.\n\n  @details f must be a 0-1 %ADD.  If f is identically 0, the check is\n  assumed to be successful, and the background value is returned.  No\n  new nodes are created.\n\n  @return a pointer to the resulting %ADD (which may or may not be\n  constant) or DD_NON_CONSTANT.\n\n  @sideeffect None\n\n  @see Cudd_addIteConstant Cudd_addLeq\n\n*/\nDdNode *\nCudd_addEvalConst(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *zero;\n    DdNode *Fv,*Fnv,*Gv,*Gnv,*r,*t,*e;\n    int topf,topg;\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsComplement(f));\n#endif\n\n    statLine(dd);\n    /* Terminal cases. */\n    if (f == DD_ONE(dd) || cuddIsConstant(g)) {\n        return(g);\n    }\n    if (f == (zero = DD_ZERO(dd))) {\n        return(dd->background);\n    }\n\n#ifdef DD_DEBUG\n    assert(!cuddIsConstant(f));\n#endif\n    /* From now on, f and g are known not to be constants. */\n\n    topf = cuddI(dd,f->index);\n    topg = cuddI(dd,g->index);\n\n    /* Check cache. */\n    r = cuddConstantLookup(dd,DD_ADD_EVAL_CONST_TAG,f,g,g);\n    if (r != NULL) {\n        return(r);\n    }\n\n    /* Compute cofactors. */\n    if (topf <= topg) {\n        Fv = cuddT(f); Fnv = cuddE(f);\n    } else {\n        Fv = Fnv = f;\n    }\n    if (topg <= topf) {\n        Gv = cuddT(g); Gnv = cuddE(g);\n    } else {\n        Gv = Gnv = g;\n    }\n    \n    /* Recursive step. */\n    if (Fv != zero) {\n\tt = Cudd_addEvalConst(dd,Fv,Gv);\n\tif (t == DD_NON_CONSTANT || !cuddIsConstant(t)) {\n\t    cuddCacheInsert2(dd, Cudd_addEvalConst, f, g, DD_NON_CONSTANT);\n\t    return(DD_NON_CONSTANT);\n\t}\n\tif (Fnv != zero) {\n\t    e = Cudd_addEvalConst(dd,Fnv,Gnv);\n\t    if (e == DD_NON_CONSTANT || !cuddIsConstant(e) || t != e) {\n\t\tcuddCacheInsert2(dd, Cudd_addEvalConst, f, g, DD_NON_CONSTANT);\n\t\treturn(DD_NON_CONSTANT);\n\t    }\n\t}\n\tcuddCacheInsert2(dd,Cudd_addEvalConst,f,g,t);\n\treturn(t);\n    } else { /* Fnv must be != zero */\n\te = Cudd_addEvalConst(dd,Fnv,Gnv);\n\tcuddCacheInsert2(dd, Cudd_addEvalConst, f, g, e);\n\treturn(e);\n    }\n\n} /* end of Cudd_addEvalConst */\n\n\n/**\n  @brief Computes the complement of an %ADD a la C language.\n\n  @details The complement of 0 is 1 and the complement of everything\n  else is 0.\n\n  @return a pointer to the resulting %ADD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addNegate\n\n*/\nDdNode *\nCudd_addCmpl(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddCmplRecur(dd,f);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addCmpl */\n\n\n/**\n  @brief Determines whether f is less than or equal to g.\n\n  @details No new nodes are created. This procedure works for arbitrary ADDs.\n  For 0-1 ADDs Cudd_addEvalConst is more efficient.\n\n  @return 1 if f is less than or equal to g; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addIteConstant Cudd_addEvalConst Cudd_bddLeq\n\n*/\nint\nCudd_addLeq(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *tmp, *fv, *fvn, *gv, *gvn;\n    int topf, topg, res;\n\n    /* Terminal cases. */\n    if (f == g) return(1);\n\n    statLine(dd);\n    if (cuddIsConstant(f)) {\n\tif (cuddIsConstant(g)) return(cuddV(f) <= cuddV(g));\n\tif (f == DD_MINUS_INFINITY(dd)) return(1);\n\tif (f == DD_PLUS_INFINITY(dd)) return(0); /* since f != g */\n    }\n    if (g == DD_PLUS_INFINITY(dd)) return(1);\n    if (g == DD_MINUS_INFINITY(dd)) return(0); /* since f != g */\n\n    /* Check cache. */\n    tmp = cuddCacheLookup2(dd,(DD_CTFP)Cudd_addLeq,f,g);\n    if (tmp != NULL) {\n\treturn(tmp == DD_ONE(dd));\n    }\n\n    /* Compute cofactors. One of f and g is not constant. */\n    topf = cuddI(dd,f->index);\n    topg = cuddI(dd,g->index);\n    if (topf <= topg) {\n\tfv = cuddT(f); fvn = cuddE(f);\n    } else {\n\tfv = fvn = f;\n    }\n    if (topg <= topf) {\n\tgv = cuddT(g); gvn = cuddE(g);\n    } else {\n\tgv = gvn = g;\n    }\n\n    res = Cudd_addLeq(dd,fvn,gvn) && Cudd_addLeq(dd,fv,gv);\n\n    /* Store result in cache and return. */\n    cuddCacheInsert2(dd,(DD_CTFP) Cudd_addLeq,f,g,\n\t\t     Cudd_NotCond(DD_ONE(dd),res==0));\n    return(res);\n\n} /* end of Cudd_addLeq */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the recursive step of Cudd_addIte(f,g,h).\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addIte\n\n*/\nDdNode *\ncuddAddIteRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    DdNode *one,*zero;\n    DdNode *r,*Fv,*Fnv,*Gv,*Gnv,*Hv,*Hnv,*t,*e;\n    int topf,topg,toph,v;\n    unsigned int index;\n\n    statLine(dd);\n    /* Trivial cases. */\n\n    /* One variable cases. */\n    if (f == (one = DD_ONE(dd))) {\t/* ITE(1,G,H) = G */\n        return(g);\n    }\n    if (f == (zero = DD_ZERO(dd))) {\t/* ITE(0,G,H) = H */\n        return(h);\n    }\n\n    /* From now on, f is known to not be a constant. */\n    addVarToConst(f,&g,&h,one,zero);\n\n    /* Check remaining one variable cases. */\n    if (g == h) {\t\t\t/* ITE(F,G,G) = G */\n        return(g);\n    }\n\n    if (g == one) {\t\t\t/* ITE(F,1,0) = F */\n        if (h == zero) return(f);\n    }\n\n    topf = cuddI(dd,f->index);\n    topg = cuddI(dd,g->index);\n    toph = cuddI(dd,h->index);\n    v = ddMin(topg,toph);\n\n    /* A shortcut: ITE(F,G,H) = (x,G,H) if F=(x,1,0), x < top(G,H). */\n    if (topf < v && cuddT(f) == one && cuddE(f) == zero) {\n\tr = cuddUniqueInter(dd,(int)f->index,g,h);\n\treturn(r);\n    }\n    if (topf < v && cuddT(f) == zero && cuddE(f) == one) {\n\tr = cuddUniqueInter(dd,(int)f->index,h,g);\n\treturn(r);\n    }\n\n    /* Check cache. */\n    r = cuddCacheLookup(dd,DD_ADD_ITE_TAG,f,g,h);\n    if (r != NULL) {\n        return(r);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Compute cofactors. */\n    index = f->index;\n    if (topf <= v) {\n\tv = ddMin(topf,v);\t/* v = top_var(F,G,H) */\n        Fv = cuddT(f); Fnv = cuddE(f);\n    } else {\n        Fv = Fnv = f;\n    }\n    if (topg == v) {\n\tindex = g->index;\n        Gv = cuddT(g); Gnv = cuddE(g);\n    } else {\n        Gv = Gnv = g;\n    }\n    if (toph == v) {\n\tindex = h->index;\n        Hv = cuddT(h); Hnv = cuddE(h);\n    } else {\n        Hv = Hnv = h;\n    }\n    \n    /* Recursive step. */\n    t = cuddAddIteRecur(dd,Fv,Gv,Hv);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n\n    e = cuddAddIteRecur(dd,Fnv,Gnv,Hnv);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(dd,t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    r = (t == e) ? t : cuddUniqueInter(dd,index,t,e);\n    if (r == NULL) {\n\tCudd_RecursiveDeref(dd,t);\n\tCudd_RecursiveDeref(dd,e);\n\treturn(NULL);\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    cuddCacheInsert(dd,DD_ADD_ITE_TAG,f,g,h,r);\n\n    return(r);\n\n} /* end of cuddAddIteRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addCmpl.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addCmpl\n\n*/\nDdNode *\ncuddAddCmplRecur(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *one,*zero;\n    DdNode *r,*Fv,*Fnv,*t,*e;\n\n    statLine(dd);\n    one = DD_ONE(dd);\n    zero = DD_ZERO(dd); \n\n    if (cuddIsConstant(f)) {\n        if (f == zero) {\n\t    return(one);\n\t} else {\n\t    return(zero);\n\t}\n    }\n    r = cuddCacheLookup1(dd,Cudd_addCmpl,f);\n    if (r != NULL) {\n\treturn(r);\n    }\n    checkWhetherToGiveUp(dd);\n    Fv = cuddT(f);\n    Fnv = cuddE(f);\n    t = cuddAddCmplRecur(dd,Fv);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n    e = cuddAddCmplRecur(dd,Fnv);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(dd,t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n    r = (t == e) ? t : cuddUniqueInter(dd,(int)f->index,t,e);\n    if (r == NULL) {\n\tCudd_RecursiveDeref(dd, t);\n\tCudd_RecursiveDeref(dd, e);\n\treturn(NULL);\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n    cuddCacheInsert1(dd,Cudd_addCmpl,f,r);\n    return(r);\n\n} /* end of cuddAddCmplRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Replaces variables with constants if possible (part of\n  canonical form).\n\n  @sideeffect None\n\n*/\nstatic void\naddVarToConst(\n  DdNode * f,\n  DdNode ** gp,\n  DdNode ** hp,\n  DdNode * one,\n  DdNode * zero)\n{\n    DdNode *g = *gp;\n    DdNode *h = *hp;\n\n    if (f == g) { /* ITE(F,F,H) = ITE(F,1,H) = F + H */\n\t*gp = one;\n    }\n\n    if (f == h) { /* ITE(F,G,F) = ITE(F,G,0) = F * G */\n\t*hp = zero;\n    }\n\n} /* end of addVarToConst */\n"
  },
  {
    "path": "cudd/cudd/cuddAddNeg.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Function to compute the negation of an %ADD.\n\n  @author Fabio Somenzi, Balakrishna Kumthekar\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Computes the additive inverse of an %ADD.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addCmpl\n\n*/\nDdNode *\nCudd_addNegate(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddNegateRecur(dd,f);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addNegate */\n\n\n/**\n  @brief Rounds off the discriminants of an %ADD.\n\n  @details The discriminants are rounded off to N digits after the\n  decimal.\n\n  @return a pointer to the result %ADD if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_addRoundOff(\n  DdManager * dd,\n  DdNode * f,\n  int  N)\n{\n    DdNode *res;\n    double trunc = pow(10.0,(double)N);\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddRoundOffRecur(dd,f,trunc);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addRoundOff */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the recursive step of Cudd_addNegate.\n\n  @return a pointer to the result.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddNegateRecur(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *res,\n\t    *fv, *fvn,\n\t    *T, *E;\n\n    statLine(dd);\n    /* Check terminal cases. */\n    if (cuddIsConstant(f)) {\n\tres = cuddUniqueConst(dd,-cuddV(f));\n\treturn(res);\n    }\n\n    /* Check cache */\n    res = cuddCacheLookup1(dd,Cudd_addNegate,f);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive Step */\n    fv = cuddT(f);\n    fvn = cuddE(f);\n    T = cuddAddNegateRecur(dd,fv);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = cuddAddNegateRecur(dd,fvn);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd,T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    res = (T == E) ? T : cuddUniqueInter(dd,(int)f->index,T,E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\tCudd_RecursiveDeref(dd, E);\n\treturn(NULL);\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert1(dd,Cudd_addNegate,f,res);\n\n    return(res);\n\n} /* end of cuddAddNegateRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_addRoundOff.\n\n  @return a pointer to the result.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddRoundOffRecur(\n  DdManager * dd,\n  DdNode * f,\n  double  trunc)\n{\n\n    DdNode *res, *fv, *fvn, *T, *E;\n    double m, n;\n    DD_CTFP1 cacheOp;\n\n    statLine(dd);\n    if (cuddIsConstant(f)) {\n        m = cuddV(f)*trunc;\n        n = floor(m);\n\tif (m-n >= 0.5) \n\t    n = n + 1;\n        n = n / trunc;\n\tres = cuddUniqueConst(dd,n);\n\treturn(res);\n    }\n    cacheOp = (DD_CTFP1) Cudd_addRoundOff;\n    res = cuddCacheLookup1(dd,cacheOp,f);\n    if (res != NULL) {\n\treturn(res);\n    }\n    checkWhetherToGiveUp(dd);\n    /* Recursive Step */\n    fv = cuddT(f);\n    fvn = cuddE(f);\n    T = cuddAddRoundOffRecur(dd,fv,trunc);\n    if (T == NULL) {\n       return(NULL);\n    }\n    cuddRef(T);\n    E = cuddAddRoundOffRecur(dd,fvn,trunc);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd,T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    res = (T == E) ? T : cuddUniqueInter(dd,(int)f->index,T,E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd,T);\n\tCudd_RecursiveDeref(dd,E);\n\treturn(NULL);\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert1(dd,cacheOp,f,res);\n    return(res);\n\n} /* end of cuddAddRoundOffRecur */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n"
  },
  {
    "path": "cudd/cudd/cuddAddWalsh.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions that generate Walsh matrices and residue\n  functions in %ADD form.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * addWalshInt (DdManager *dd, DdNode **x, DdNode **y, int n);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Generates a Walsh matrix in %ADD form.\n\n  @return a pointer to the matrixi if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_addWalsh(\n  DdManager * dd,\n  DdNode ** x,\n  DdNode ** y,\n  int  n)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = addWalshInt(dd, x, y, n);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addWalsh */\n\n\n/**\n  @brief Builds an %ADD for the residue modulo m of an n-bit\n  number.\n\n  @details The modulus must be at least 2, and the number of bits at\n  least 1. Parameter options specifies whether the MSB should be on top\n  or the LSB; and whther the number whose residue is computed is in\n  two's complement notation or not. The macro CUDD_RESIDUE_DEFAULT\n  specifies LSB on top and unsigned number. The macro CUDD_RESIDUE_MSB\n  specifies MSB on top, and the macro CUDD_RESIDUE_TC specifies two's\n  complement residue. To request MSB on top and two's complement residue\n  simultaneously, one can OR the two macros:\n  CUDD_RESIDUE_MSB | CUDD_RESIDUE_TC.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_addResidue(\n  DdManager * dd /**< manager */,\n  int  n /**< number of bits */,\n  int  m /**< modulus */,\n  int  options /**< options */,\n  int  top /**< index of top variable */)\n{\n    int msbLsb;\t/* MSB on top (1) or LSB on top (0) */\n    int tc;\t/* two's complement (1) or unsigned (0) */\n    int i, j, k, t, residue, thisOne, previous, index;\n    DdNode **array[2], *var, *tmp, *res;\n\n    /* Sanity check. */\n    if (n < 1 && m < 2) return(NULL);\n\n    msbLsb = options & CUDD_RESIDUE_MSB;\n    tc = options & CUDD_RESIDUE_TC;\n\n    /* Allocate and initialize working arrays. */\n    array[0] = ALLOC(DdNode *,m);\n    if (array[0] == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    array[1] = ALLOC(DdNode *,m);\n    if (array[1] == NULL) {\n\tFREE(array[0]);\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < m; i++) {\n\tarray[0][i] = array[1][i] = NULL;\n    }\n\n    /* Initialize residues. */\n    for (i = 0; i < m; i++) {\n\ttmp = cuddUniqueConst(dd,(CUDD_VALUE_TYPE) i);\n\tif (tmp == NULL) {\n\t    for (j = 0; j < i; j++) {\n\t\tCudd_RecursiveDeref(dd,array[1][j]);\n\t    }\n\t    FREE(array[0]);\n\t    FREE(array[1]);\n\t    return(NULL);\n\t}\n\tcuddRef(tmp);\n\tarray[1][i] = tmp;\n    }\n\n    /* Main iteration. */\n    residue = 1;\t/* residue of 2**0 */\n    for (k = 0; k < n; k++) {\n\t/* Choose current and previous arrays. */\n\tthisOne = k & 1;\n\tprevious = thisOne ^ 1;\n\t/* Build an ADD projection function. */\n\tif (msbLsb) {\n\t    index = top+n-k-1;\n\t} else {\n\t    index = top+k;\n\t}\n\tvar = cuddUniqueInter(dd,index,DD_ONE(dd),DD_ZERO(dd));\n\tif (var == NULL) {\n\t    for (j = 0; j < m; j++) {\n\t\tCudd_RecursiveDeref(dd,array[previous][j]);\n\t    }\n\t    FREE(array[0]);\n\t    FREE(array[1]);\n\t    return(NULL);\n\t}\n\tcuddRef(var);\n\tfor (i = 0; i < m; i ++) {\n\t    t = (i + residue) % m;\n\t    tmp = Cudd_addIte(dd,var,array[previous][t],array[previous][i]);\n\t    if (tmp == NULL) {\n\t\tfor (j = 0; j < i; j++) {\n\t\t    Cudd_RecursiveDeref(dd,array[thisOne][j]);\n\t\t}\n\t\tfor (j = 0; j < m; j++) {\n\t\t    Cudd_RecursiveDeref(dd,array[previous][j]);\n\t\t}\n\t\tFREE(array[0]);\n\t\tFREE(array[1]);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(tmp);\n\t    array[thisOne][i] = tmp;\n\t}\n\t/* One layer completed. Free the other array for the next iteration. */\n\tfor (i = 0; i < m; i++) {\n\t    Cudd_RecursiveDeref(dd,array[previous][i]);\n\t}\n\tCudd_RecursiveDeref(dd,var);\n\t/* Update residue of 2**k. */\n\tresidue = (2 * residue) % m;\n\t/* Adjust residue for MSB, if this is a two's complement number. */\n\tif (tc && (k == n - 1)) {\n\t    residue = (m - residue) % m;\n\t}\n    }\n\n    /* We are only interested in the 0-residue node of the top layer. */\n    for (i = 1; i < m; i++) {\n\tCudd_RecursiveDeref(dd,array[(n - 1) & 1][i]);\n    }\n    res = array[(n - 1) & 1][0];\n\n    FREE(array[0]);\n    FREE(array[1]);\n\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_addResidue */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the recursive step of Cudd_addWalsh.\n\n  @return a pointer to the matrixi if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addWalsh\n\n*/\nstatic DdNode *\naddWalshInt(\n  DdManager * dd,\n  DdNode ** x,\n  DdNode ** y,\n  int  n)\n{\n    DdNode *one, *minusone;\n    DdNode *t = NULL, *u, *t1, *u1, *v, *w;\n    int     i;\n\n    one = DD_ONE(dd);\n    if (n == 0) return(one);\n\n    /* Build bottom part of ADD outside loop */\n    minusone = cuddUniqueConst(dd,(CUDD_VALUE_TYPE) -1);\n    if (minusone == NULL) return(NULL);\n    cuddRef(minusone);\n    v = Cudd_addIte(dd, y[n-1], minusone, one);\n    if (v == NULL) {\n\tCudd_RecursiveDeref(dd, minusone);\n\treturn(NULL);\n    }\n    cuddRef(v);\n    u = Cudd_addIte(dd, x[n-1], v, one);\n    if (u == NULL) {\n\tCudd_RecursiveDeref(dd, minusone);\n\tCudd_RecursiveDeref(dd, v);\n\treturn(NULL);\n    }\n    cuddRef(u);\n    Cudd_RecursiveDeref(dd, v);\n    if (n>1) {\n\tw = Cudd_addIte(dd, y[n-1], one, minusone);\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd, minusone);\n\t    Cudd_RecursiveDeref(dd, u);\n\t    return(NULL);\n\t}\n\tcuddRef(w);\n\tt = Cudd_addIte(dd, x[n-1], w, minusone);\n\tif (t == NULL) {\n\t    Cudd_RecursiveDeref(dd, minusone);\n\t    Cudd_RecursiveDeref(dd, u);\n\t    Cudd_RecursiveDeref(dd, w);\n\t    return(NULL);\n\t}\n\tcuddRef(t);\n\tCudd_RecursiveDeref(dd, w);\n    }\n    cuddDeref(minusone); /* minusone is in the result; it won't die */\n\n    /* Loop to build the rest of the ADD */\n    for (i=n-2; i>=0; i--) {\n\tt1 = t; u1 = u;\n\tv = Cudd_addIte(dd, y[i], t1, u1);\n\tif (v == NULL) {\n\t    Cudd_RecursiveDeref(dd, u1);\n\t    Cudd_RecursiveDeref(dd, t1);\n\t    return(NULL);\n\t}\n\tcuddRef(v);\n\tu = Cudd_addIte(dd, x[i], v, u1);\n\tif (u == NULL) {\n\t    Cudd_RecursiveDeref(dd, u1);\n\t    Cudd_RecursiveDeref(dd, t1);\n\t    Cudd_RecursiveDeref(dd, v);\n\t    return(NULL);\n\t}\n\tcuddRef(u);\n\tCudd_RecursiveDeref(dd, v);\n\tif (i>0) {\n\t    w = Cudd_addIte(dd, y[i], u1, t1);\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, u1);\n\t\tCudd_RecursiveDeref(dd, t1);\n\t\tCudd_RecursiveDeref(dd, u);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(w);\n\t    t = Cudd_addIte(dd, x[i], w, t1);\n\t    if (u == NULL) {\n\t\tCudd_RecursiveDeref(dd, u1);\n\t\tCudd_RecursiveDeref(dd, t1);\n\t\tCudd_RecursiveDeref(dd, u);\n\t\tCudd_RecursiveDeref(dd, w);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(t);\n\t    Cudd_RecursiveDeref(dd, w);\n\t}\n\tCudd_RecursiveDeref(dd, u1);\n\tCudd_RecursiveDeref(dd, t1);\n    }\n\n    cuddDeref(u);\n    return(u);\n\n} /* end of addWalshInt */\n"
  },
  {
    "path": "cudd/cudd/cuddAndAbs.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Combined AND and existential abstraction for BDDs\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Takes the AND of two BDDs and simultaneously abstracts the\n  variables in cube.\n\n  @details The variables are existentially abstracted.\n  Cudd_bddAndAbstract implements the semiring matrix multiplication\n  algorithm for the boolean semiring.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addMatrixMultiply Cudd_addTriangle Cudd_bddAnd\n\n*/\nDdNode *\nCudd_bddAndAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g,\n  DdNode * cube)\n{\n    DdNode *res;\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddBddAndAbstractRecur(manager, f, g, cube);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddAndAbstract */\n\n\n/**\n  @brief Takes the AND of two BDDs and simultaneously abstracts\n  variables unless too many nodes are needed.\n\n  @details The variables in cube are existentially abstracted.\n\n  @return a pointer to the result is successful; NULL otherwise.\n  In particular, if the number of new nodes created exceeds\n  <code>limit</code>, this function returns NULL.\n\n  @sideeffect None\n\n  @see Cudd_bddAndAbstract\n\n*/\nDdNode *\nCudd_bddAndAbstractLimit(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g,\n  DdNode * cube,\n  unsigned int limit)\n{\n    DdNode *res;\n    unsigned int saveLimit = manager->maxLive;\n\n    manager->maxLive = (manager->keys - manager->dead) +\n      (manager->keysZ - manager->deadZ) + limit;\n    do {\n\tmanager->reordered = 0;\n\tres = cuddBddAndAbstractRecur(manager, f, g, cube);\n    } while (manager->reordered == 1);\n    manager->maxLive = saveLimit;\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddAndAbstractLimit */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Takes the AND of two BDDs and simultaneously abstracts the\n  variables in cube.\n\n  @details The variables are existentially abstracted.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddAndAbstract\n\n*/\nDdNode *\ncuddBddAndAbstractRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g,\n  DdNode * cube)\n{\n    DdNode *F, *ft, *fe, *G, *gt, *ge;\n    DdNode *one, *zero, *r, *t, *e;\n    int topf, topg, top, topcube;\n    unsigned int index;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    /* Terminal cases. */\n    if (f == zero || g == zero || f == Cudd_Not(g)) return(zero);\n    if (f == one && g == one)\treturn(one);\n\n    if (cube == one) {\n\treturn(cuddBddAndRecur(manager, f, g));\n    }\n    if (f == one || f == g) {\n\treturn(cuddBddExistAbstractRecur(manager, g, cube));\n    }\n    if (g == one) {\n\treturn(cuddBddExistAbstractRecur(manager, f, cube));\n    }\n    /* At this point f, g, and cube are not constant. */\n\n    if (f > g) { /* Try to increase cache efficiency. */\n\tDdNode *tmp = f;\n\tf = g;\n\tg = tmp;\n    }\n\n    /* Here we can skip the use of cuddI, because the operands are known\n    ** to be non-constant.\n    */\n    F = Cudd_Regular(f);\n    G = Cudd_Regular(g);\n    topf = manager->perm[F->index];\n    topg = manager->perm[G->index];\n    top = ddMin(topf, topg);\n    topcube = manager->perm[cube->index];\n\n    while (topcube < top) {\n\tcube = cuddT(cube);\n\tif (cube == one) {\n\t    return(cuddBddAndRecur(manager, f, g));\n\t}\n\ttopcube = manager->perm[cube->index];\n    }\n    /* Now, topcube >= top. */\n\n    /* Check cache. */\n    if (F->ref != 1 || G->ref != 1) {\n\tr = cuddCacheLookup(manager, DD_BDD_AND_ABSTRACT_TAG, f, g, cube);\n\tif (r != NULL) {\n\t    return(r);\n\t}\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    if (topf == top) {\n\tindex = F->index;\n\tft = cuddT(F);\n\tfe = cuddE(F);\n\tif (Cudd_IsComplement(f)) {\n\t    ft = Cudd_Not(ft);\n\t    fe = Cudd_Not(fe);\n\t}\n    } else {\n\tindex = G->index;\n\tft = fe = f;\n    }\n\n    if (topg == top) {\n\tgt = cuddT(G);\n\tge = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gt = Cudd_Not(gt);\n\t    ge = Cudd_Not(ge);\n\t}\n    } else {\n\tgt = ge = g;\n    }\n\n    if (topcube == top) {\t/* quantify */\n\tDdNode *Cube = cuddT(cube);\n\tt = cuddBddAndAbstractRecur(manager, ft, gt, Cube);\n\tif (t == NULL) return(NULL);\n\t/* Special case: 1 OR anything = 1. Hence, no need to compute\n\t** the else branch if t is 1. Likewise t + t * anything == t.\n\t** Notice that t == fe implies that fe does not depend on the\n\t** variables in Cube. Likewise for t == ge.\n\t*/\n\tif (t == one || t == fe || t == ge) {\n\t    if (F->ref != 1 || G->ref != 1)\n\t\tcuddCacheInsert(manager, DD_BDD_AND_ABSTRACT_TAG,\n\t\t\t\tf, g, cube, t);\n\t    return(t);\n\t}\n\tcuddRef(t);\n\t/* Special case: t + !t * anything == t + anything. */\n\tif (t == Cudd_Not(fe)) {\n\t    e = cuddBddExistAbstractRecur(manager, ge, Cube);\n\t} else if (t == Cudd_Not(ge)) {\n\t    e = cuddBddExistAbstractRecur(manager, fe, Cube);\n\t} else {\n\t    e = cuddBddAndAbstractRecur(manager, fe, ge, Cube);\n\t}\n\tif (e == NULL) {\n\t    Cudd_IterDerefBdd(manager, t);\n\t    return(NULL);\n\t}\n\tif (t == e) {\n\t    r = t;\n\t    cuddDeref(t);\n\t} else {\n\t    cuddRef(e);\n\t    r = cuddBddAndRecur(manager, Cudd_Not(t), Cudd_Not(e));\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t    cuddRef(r);\n\t    Cudd_DelayedDerefBdd(manager, t);\n\t    Cudd_DelayedDerefBdd(manager, e);\n\t    cuddDeref(r);\n\t}\n    } else {\n\tt = cuddBddAndAbstractRecur(manager, ft, gt, cube);\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n\te = cuddBddAndAbstractRecur(manager, fe, ge, cube);\n\tif (e == NULL) {\n\t    Cudd_IterDerefBdd(manager, t);\n\t    return(NULL);\n\t}\n\tif (t == e) {\n\t    r = t;\n\t    cuddDeref(t);\n\t} else {\n\t    cuddRef(e);\n\t    if (Cudd_IsComplement(t)) {\n\t\tr = cuddUniqueInter(manager, (int) index,\n\t\t\t\t    Cudd_Not(t), Cudd_Not(e));\n\t\tif (r == NULL) {\n\t\t    Cudd_IterDerefBdd(manager, t);\n\t\t    Cudd_IterDerefBdd(manager, e);\n\t\t    return(NULL);\n\t\t}\n\t\tr = Cudd_Not(r);\n\t    } else {\n\t\tr = cuddUniqueInter(manager,(int)index,t,e);\n\t\tif (r == NULL) {\n\t\t    Cudd_IterDerefBdd(manager, t);\n\t\t    Cudd_IterDerefBdd(manager, e);\n\t\t    return(NULL);\n\t\t}\n\t    }\n\t    cuddDeref(e);\n\t    cuddDeref(t);\n\t}\n    }\n\n    if (F->ref != 1 || G->ref != 1)\n\tcuddCacheInsert(manager, DD_BDD_AND_ABSTRACT_TAG, f, g, cube, r);\n    return (r);\n\n} /* end of cuddBddAndAbstractRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n"
  },
  {
    "path": "cudd/cudd/cuddAnneal.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Reordering of DDs based on simulated annealing\n\n  @author Jae-Young Jang, Jorgen Sivesind\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* Annealing parameters */\n#define BETA 0.6 \n#define ALPHA 0.90\n#define EXC_PROB 0.4 \n#define JUMP_UP_PROB 0.36\n#define MAXGEN_RATIO 15.0\n#define STOP_TEMP 1.0\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int stopping_criterion (int c1, int c2, int c3, int c4, double temp);\nstatic double random_generator (DdManager *dd);\nstatic int ddExchange (DdManager *table, int x, int y, double temp);\nstatic int ddJumpingAux (DdManager *table, int x, int x_low, int x_high, double temp);\nstatic Move * ddJumpingUp (DdManager *table, int x, int x_low, int initial_size);\nstatic Move * ddJumpingDown (DdManager *table, int x, int x_high, int initial_size);\nstatic int siftBackwardProb (DdManager *table, Move *moves, int size, double temp);\nstatic void copyOrder (DdManager *table, int *array, int lower, int upper);\nstatic int restoreOrder (DdManager *table, int *array, int lower, int upper);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Get new variable-order by simulated annealing algorithm.\n\n  @details Get x, y by random selection. Choose either\n  exchange or jump randomly. In case of jump, choose between jump_up\n  and jump_down randomly. Do exchange or jump and get optimal case.\n  Loop until there is no improvement or temperature reaches\n  minimum.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddAnnealing(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int         nvars;\n    int         size;\n    int         x,y;\n    int         result;\n    int\t\tc1, c2, c3, c4;\n    int\t\tBestCost;\n    int\t\t*BestOrder;\n    double\tNewTemp, temp;\n    double\trand1;\n    int         innerloop, maxGen;\n    int         ecount, ucount, dcount;\n   \n    nvars = upper - lower + 1;\n\n    result = cuddSifting(table,lower,upper);\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n\");\n#endif\n    if (result == 0) return(0);\n\n    size = (int) (table->keys - table->isolated);\n\n    /* Keep track of the best order. */\n    BestCost = size;\n    BestOrder = ALLOC(int,nvars);\n    if (BestOrder == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    copyOrder(table,BestOrder,lower,upper);\n\n    temp = BETA * size;\n    maxGen = (int) (MAXGEN_RATIO * nvars);\n\n    c1 = size + 10;\n    c2 = c1 + 10;\n    c3 = size;\n    c4 = c2 + 10;\n    ecount = ucount = dcount = 0;\n \n    while (!stopping_criterion(c1, c2, c3, c4, temp)) {\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\"temp=%f\\tsize=%d\\tgen=%d\\t\",\n\t\t       temp,size,maxGen);\n\ttable->tosses = table->acceptances = 0;\n#endif\n\tfor (innerloop = 0; innerloop < maxGen; innerloop++) {\n\t    /* Choose x, y  randomly. */\n\t    x = (int) Cudd_Random(table) % nvars;\n\t    do {\n\t\ty = (int) Cudd_Random(table) % nvars;\n\t    } while (x == y);\n\t    x += lower;\n\t    y += lower;\n\t    if (x > y) {\n\t\tint tmp = x;\n\t\tx = y;\n\t\ty = tmp;\n\t    }\n\n\t    /* Choose move with roulette wheel. */\n\t    rand1 = random_generator(table);\n\t    if (rand1 < EXC_PROB) {\n\t\tresult = ddExchange(table,x,y,temp);       /* exchange */\n\t\tecount++;\n#if 0\n\t\t(void) fprintf(table->out,\n\t\t\t       \"Exchange of %d and %d: size = %d\\n\",\n\t\t\t       x,y,table->keys - table->isolated);\n#endif\n\t    } else if (rand1 < EXC_PROB + JUMP_UP_PROB) {\n\t\tresult = ddJumpingAux(table,y,x,y,temp); /* jumping_up */\n\t\tucount++;\n#if 0\n\t\t(void) fprintf(table->out,\n\t\t\t       \"Jump up of %d to %d: size = %d\\n\",\n\t\t\t       y,x,table->keys - table->isolated);\n#endif\n\t    } else {\n\t\tresult = ddJumpingAux(table,x,x,y,temp); /* jumping_down */\n\t\tdcount++;\n#if 0\n\t\t(void) fprintf(table->out,\n\t\t\t       \"Jump down of %d to %d: size = %d\\n\",\n\t\t\t       x,y,table->keys - table->isolated);\n#endif\n\t    }\n\n\t    if (!result) {\n\t\tFREE(BestOrder);\n\t\treturn(0);\n\t    }\n\n\t    size = (int) (table->keys - table->isolated); /* keep current size */\n\t    if (size < BestCost) {\t\t\t/* update best order */\n\t\tBestCost = size;\n\t\tcopyOrder(table,BestOrder,lower,upper);\n\t    }\n\t}\n\tc1 = c2;\n\tc2 = c3;\n\tc3 = c4;\n\tc4 = size;\n\tNewTemp = ALPHA * temp;\n\tif (NewTemp >= 1.0) {\n\t    maxGen = (int)(log(NewTemp) / log(temp) * maxGen);\n\t}\n\ttemp = NewTemp;\t                /* control variable */\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\"uphill = %d\\taccepted = %d\\n\",\n\t\t       table->tosses,table->acceptances);\n\tfflush(table->out);\n#endif\n    }\n\n    result = restoreOrder(table,BestOrder,lower,upper);\n    FREE(BestOrder);\n    if (!result) return(0);\n#ifdef DD_STATS\n    fprintf(table->out,\"#:N_EXCHANGE %8d : total exchanges\\n\",ecount);\n    fprintf(table->out,\"#:N_JUMPUP   %8d : total jumps up\\n\",ucount);\n    fprintf(table->out,\"#:N_JUMPDOWN %8d : total jumps down\",dcount);\n#endif\n    return(1);\n\n} /* end of cuddAnnealing */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Checks termination condition.\n\n  @details If temperature is STOP_TEMP or there is no improvement\n  then terminates.\n\n  @return 1 if the termination criterion is met; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nstopping_criterion(\n  int  c1,\n  int  c2,\n  int  c3,\n  int  c4,\n  double  temp)\n{\n    if (STOP_TEMP < temp) {\n\treturn(0);\n    } else if ((c1 == c2) && (c1 == c3) && (c1 == c4)) {\n\treturn(1);\n    } else {\n\treturn(0);\n    }\n\n} /* end of stopping_criterion */\n\n\n/**\n  @brief Random number generator.\n\n  @return a double precision value between 0.0 and 1.0.\n\n  @sideeffect None\n\n*/\nstatic double\nrandom_generator(DdManager * dd)\n{\n    return((double)(Cudd_Random(dd) / 2147483561.0));\n\n} /* end of random_generator */\n\n\n/**\n  @brief Exchanges two variables, x and y.\n\n  @details This is the same funcion as ddSwapping except for the\n  comparison expression.  Use probability function, exp(-size_change/temp).\n\n  @sideeffect None\n\n*/\nstatic int\nddExchange(\n  DdManager * table,\n  int  x,\n  int  y,\n  double  temp)\n{\n    Move       *move,*moves;\n    int        tmp;\n    int        x_ref,y_ref;\n    int        x_next,y_next;\n    int        size, result;\n    int        initial_size, limit_size;\n\n    x_ref = x;\n    y_ref = y;\n\n    x_next = cuddNextHigh(table,x);\n    y_next = cuddNextLow(table,y);\n    moves = NULL;\n    initial_size = limit_size = (int) (table->keys - table->isolated);\n\n    for (;;) {\n\tif (x_next == y_next) {\n\t    size = cuddSwapInPlace(table,x,x_next);\n\t    if (size == 0) goto ddExchangeOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddExchangeOutOfMem;\n\t    move->x = x;\n\t    move->y = x_next;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    size = cuddSwapInPlace(table,y_next,y);\n\t    if (size == 0) goto ddExchangeOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddExchangeOutOfMem;\n\t    move->x = y_next;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    size = cuddSwapInPlace(table,x,x_next);\n\t    if (size == 0) goto ddExchangeOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddExchangeOutOfMem;\n\t    move->x = x;\n\t    move->y = x_next;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    tmp = x;\n\t    x = y;\n\t    y = tmp;\n\t} else if (x == y_next) {\n\t    size = cuddSwapInPlace(table,x,x_next);\n\t    if (size == 0) goto ddExchangeOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddExchangeOutOfMem;\n\t    move->x = x;\n\t    move->y = x_next;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    tmp = x;\n\t    x = y;\n\t    y = tmp;\n\t} else {\n\t    size = cuddSwapInPlace(table,x,x_next);\n\t    if (size == 0) goto ddExchangeOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddExchangeOutOfMem;\n\t    move->x = x;\n\t    move->y = x_next;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    size = cuddSwapInPlace(table,y_next,y);\n\t    if (size == 0) goto ddExchangeOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddExchangeOutOfMem;\n\t    move->x = y_next;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    x = x_next;\n\t    y = y_next;\n\t}\n\n\tx_next = cuddNextHigh(table,x);\n\ty_next = cuddNextLow(table,y);\n\tif (x_next > y_ref) break;\n\n\tif ((double) size > DD_MAX_REORDER_GROWTH * (double) limit_size) {\n\t    break;\n\t} else if (size < limit_size) {\n\t    limit_size = size;\n\t}\n    }\n\n    if (y_next>=x_ref) {\n        size = cuddSwapInPlace(table,y_next,y);\n        if (size == 0) goto ddExchangeOutOfMem;\n        move = (Move *)cuddDynamicAllocNode(table);\n        if (move == NULL) goto ddExchangeOutOfMem;\n        move->x = y_next;\n        move->y = y;\n        move->size = size;\n        move->next = moves;\n        moves = move;\n    }\n\n    /* move backward and stop at best position or accept uphill move */\n    result = siftBackwardProb(table,moves,initial_size,temp);\n    if (!result) goto ddExchangeOutOfMem;\n\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(1);\n\nddExchangeOutOfMem:\n    while (moves != NULL) {\n        move = moves->next;\n        cuddDeallocMove(table, moves);\n        moves = move;\n    }\n    return(0);\n\n} /* end of ddExchange */\n\n\n/**\n  @brief Moves a variable to a specified position.\n\n  @details If x==x_low, it executes jumping_down. If x==x_high, it\n  executes jumping_up. This funcion is similar to ddSiftingAux.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddJumpingAux(\n  DdManager * table,\n  int  x,\n  int  x_low,\n  int  x_high,\n  double  temp)\n{\n    Move       *move;\n    Move       *moves;        /* list of moves */\n    int        initial_size;\n    int        result;\n\n    initial_size = (int) (table->keys - table->isolated);\n\n#ifdef DD_DEBUG\n    assert(table->subtables[x].keys > 0);\n#endif\n\n    moves = NULL;\n\n    if (cuddNextLow(table,x) < x_low) {\n\tif (cuddNextHigh(table,x) > x_high) return(1);\n\tmoves = ddJumpingDown(table,x,x_high,initial_size);\n\t/* after that point x --> x_high unless early termination */\n\tif (moves == NULL) goto ddJumpingAuxOutOfMem;\n\t/* move backward and stop at best position or accept uphill move */\n\tresult = siftBackwardProb(table,moves,initial_size,temp);\n\tif (!result) goto ddJumpingAuxOutOfMem;\n    } else if (cuddNextHigh(table,x) > x_high) {\n\tmoves = ddJumpingUp(table,x,x_low,initial_size);\n\t/* after that point x --> x_low unless early termination */\n\tif (moves == NULL) goto ddJumpingAuxOutOfMem;\n\t/* move backward and stop at best position or accept uphill move */\n\tresult = siftBackwardProb(table,moves,initial_size,temp);\n\tif (!result) goto ddJumpingAuxOutOfMem;\n    } else {\n\t(void) fprintf(table->err,\"Unexpected condition in ddJumping\\n\");\n\tgoto ddJumpingAuxOutOfMem;\n    }\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(1);\n\nddJumpingAuxOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(0);\n\n} /* end of ddJumpingAux */\n\n\n/**\n  @brief This function is for jumping up.\n\n  @details This is a simplified version of ddSiftingUp. It does not\n  use lower bounding.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddJumpingUp(\n  DdManager * table,\n  int  x,\n  int  x_low,\n  int  initial_size)\n{\n    Move       *moves;\n    Move       *move;\n    int        y;\n    int        size;\n    int        limit_size = initial_size;\n\n    moves = NULL;\n    y = cuddNextLow(table,x);\n    while (y >= x_low) {\n\tsize = cuddSwapInPlace(table,y,x);\n\tif (size == 0) goto ddJumpingUpOutOfMem;\n\tmove = (Move *)cuddDynamicAllocNode(table);\n\tif (move == NULL) goto ddJumpingUpOutOfMem;\n\tmove->x = y;\n\tmove->y = x;\n\tmove->size = size;\n\tmove->next = moves;\n\tmoves = move;\n\tif ((double) size > table->maxGrowth * (double) limit_size) {\n\t    break;\n\t} else if (size < limit_size) {\n\t    limit_size = size;\n\t}\n\tx = y;\n\ty = cuddNextLow(table,x);\n    }\n    return(moves);\n\nddJumpingUpOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(NULL);\n\n} /* end of ddJumpingUp */\n\n\n/**\n  @brief This function is for jumping down.\n\n  @details This is a simplified version of ddSiftingDown. It does not\n  use lower bounding.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddJumpingDown(\n  DdManager * table,\n  int  x,\n  int  x_high,\n  int  initial_size)\n{\n    Move       *moves;\n    Move       *move;\n    int        y;\n    int        size;\n    int        limit_size = initial_size;\n\n    moves = NULL;\n    y = cuddNextHigh(table,x);\n    while (y <= x_high) {\n\tsize = cuddSwapInPlace(table,x,y);\n\tif (size == 0) goto ddJumpingDownOutOfMem;\n\tmove = (Move *)cuddDynamicAllocNode(table);\n\tif (move == NULL) goto ddJumpingDownOutOfMem;\n\tmove->x = x;\n\tmove->y = y;\n\tmove->size = size;\n\tmove->next = moves;\n\tmoves = move;\n\tif ((double) size > table->maxGrowth * (double) limit_size) {\n\t    break;\n\t} else if (size < limit_size) {\n\t    limit_size = size;\n\t}\n\tx = y;\n\ty = cuddNextHigh(table,x);\n    }\n    return(moves);\n\nddJumpingDownOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(NULL);\n\n} /* end of ddJumpingDown */\n\n\n/**\n  @brief Returns the %DD to the best position encountered during\n  sifting if there was improvement.\n\n  @details Otherwise, \"tosses a coin\" to decide whether to keep\n  the current configuration or return the %DD to the original\n  one.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nsiftBackwardProb(\n  DdManager * table,\n  Move * moves,\n  int  size,\n  double  temp)\n{\n    Move   *move;\n    int    res;\n    int    best_size = size;\n    double coin, threshold;\n\n    /* Look for best size during the last sifting */\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size < best_size) {\n\t    best_size = move->size;\n\t}\n    }\n    \n    /* If best_size equals size, the last sifting did not produce any\n    ** improvement. We now toss a coin to decide whether to retain\n    ** this change or not.\n    */\n    if (best_size == size) {\n\tcoin = random_generator(table);\n#ifdef DD_STATS\n\ttable->tosses++;\n#endif\n\tthreshold = exp(-((double)(table->keys - table->isolated -\n                                   (unsigned int) size))/temp);\n\tif (coin < threshold) {\n#ifdef DD_STATS\n\t    table->acceptances++;\n#endif\n\t    return(1);\n\t}\n    }\n\n    /* Either there was improvement, or we have decided not to\n    ** accept the uphill move. Go to best position.\n    */\n    res = (int) (table->keys - table->isolated);\n    for (move = moves; move != NULL; move = move->next) {\n\tif (res == best_size) return(1);\n\tres = cuddSwapInPlace(table,(int)move->x,(int)move->y);\n\tif (!res) return(0);\n    }\n\n    return(1);\n\n} /* end of sift_backward_prob */\n\n\n/**\n  @brief Copies the current variable order to array.\n\n  @details At the same time inverts the permutation.\n\n  @sideeffect None\n\n*/\nstatic void\ncopyOrder(\n  DdManager * table,\n  int * array,\n  int  lower,\n  int  upper)\n{\n    int i;\n    int nvars;\n\n    nvars = upper - lower + 1;\n    for (i = 0; i < nvars; i++) {\n\tarray[i] = table->invperm[i+lower];\n    }\n\n} /* end of copyOrder */\n\n\n/**\n  @brief Restores the variable order in array by a series of sifts up.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nrestoreOrder(\n  DdManager * table,\n  int * array,\n  int  lower,\n  int  upper)\n{\n    int i, x, y, size;\n    int nvars = upper - lower + 1;\n\n    for (i = 0; i < nvars; i++) {\n\tx = table->perm[array[i]];\n#ifdef DD_DEBUG\n    assert(x >= lower && x <= upper);\n#endif\n\ty = cuddNextLow(table,x);\n\twhile (y >= i + lower) {\n\t    size = cuddSwapInPlace(table,y,x);\n\t    if (size == 0) return(0);\n\t    x = y;\n\t    y = cuddNextLow(table,x);\n\t}\n    }\n\n    return(1);\n\n} /* end of restoreOrder */\n\n"
  },
  {
    "path": "cudd/cudd/cuddApa.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Arbitrary precision arithmetic functions.\n\n  @details This file provides just enough functionality as needed\n  by CUDD to compute the number of minterms of functions with many\n  variables.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* These constants define the digits used in the representation of\n** arbitrary precision integers.\n*/\n#define DD_APA_BITS\t((int) sizeof(DdApaDigit) * 8)\n#define DD_APA_BASE\t((DdApaDoubleDigit) 1 << DD_APA_BITS)\n#define DD_APA_MASK\t(DD_APA_BASE - 1)\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n   @brief Type used for intermediate results.\n*/\ntypedef uint64_t DdApaDoubleDigit;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Extract the least significant digit of a double digit.\n\n  @sideeffect None\n\n  @see DD_MSDIGIT\n\n*/\n#define DD_LSDIGIT(x)\t((x) & DD_APA_MASK)\n\n\n/**\n  @brief Extract the most significant digit of a double digit.\n\n  @sideeffect None\n\n  @see DD_LSDIGIT\n\n*/\n#define DD_MSDIGIT(x)\t((x) >> DD_APA_BITS)\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdApaNumber cuddApaCountMintermAux (DdManager const * manager, DdNode * node, int digits, DdApaNumber mmax, DdApaNumber mmin, st_table * table);\nstatic enum st_retval cuddApaStCountfree (void * key, void * value, void * arg);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Returns the number of digits for an arbitrary precision\n  integer.\n\n  @details Finds the number of digits for an arbitrary precision\n  integer given the maximum number of binary digits.  The number of\n  binary digits should be positive.\n\n  @sideeffect None\n\n*/\nint\nCudd_ApaNumberOfDigits(\n  int binaryDigits)\n{\n    int digits;\n\n    digits = binaryDigits / DD_APA_BITS;\n    if ((digits * DD_APA_BITS) != binaryDigits)\n\tdigits++;\n    return(digits);\n\n} /* end of Cudd_ApaNumberOfDigits */\n\n\n/**\n  @brief Allocates memory for an arbitrary precision integer.\n\n  @return a pointer to the allocated memory if successful;\n  NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_FreeApaNumber\n*/\nDdApaNumber\nCudd_NewApaNumber(\n  int digits)\n{\n    return(ALLOC(DdApaDigit, digits));\n\n} /* end of Cudd_NewApaNumber */\n\n\n/**\n  @brief Frees an arbitrary precision integer.\n\n  @sideeffect None\n\n  @see Cudd_NewApaNumber\n*/\nvoid\nCudd_FreeApaNumber(\n  DdApaNumber number)\n{\n    FREE(number);\n\n} /* end of Cudd_FreeApaNumber */\n\n\n/**\n  @brief Makes a copy of an arbitrary precision integer.\n\n  @sideeffect Changes parameter <code>dest</code>.\n\n*/\nvoid\nCudd_ApaCopy(\n  int digits,\n  DdConstApaNumber source,\n  DdApaNumber dest)\n{\n    int i;\n\n    for (i = 0; i < digits; i++) {\n\tdest[i] = source[i];\n    }\n\n} /* end of Cudd_ApaCopy */\n\n\n/**\n  @brief Adds two arbitrary precision integers.\n\n  @return the carry out of the most significant digit.\n\n  @sideeffect The result of the sum is stored in parameter <code>sum</code>.\n\n*/\nDdApaDigit\nCudd_ApaAdd(\n  int  digits,\n  DdConstApaNumber a,\n  DdConstApaNumber b,\n  DdApaNumber sum)\n{\n    int i;\n    DdApaDoubleDigit partial = 0;\n\n    for (i = digits - 1; i >= 0; i--) {\n\tpartial = DD_MSDIGIT(partial) + a[i] + b[i];\n\tsum[i] = (DdApaDigit) DD_LSDIGIT(partial);\n    }\n    return((DdApaDigit) DD_MSDIGIT(partial));\n\n} /* end of Cudd_ApaAdd */\n\n\n/**\n  @brief Subtracts two arbitrary precision integers.\n\n  @return the borrow out of the most significant digit.\n\n  @sideeffect The result of the subtraction is stored in parameter\n  <code>diff</code>.\n\n*/\nDdApaDigit\nCudd_ApaSubtract(\n  int  digits,\n  DdConstApaNumber a,\n  DdConstApaNumber b,\n  DdApaNumber diff)\n{\n    int i;\n    DdApaDoubleDigit partial = DD_APA_BASE;\n\n    for (i = digits - 1; i >= 0; i--) {\n        partial = DD_MSDIGIT(partial) + DD_APA_MASK + a[i] - b[i];\n\tdiff[i] = (DdApaDigit) DD_LSDIGIT(partial);\n    }\n    return((DdApaDigit) DD_MSDIGIT(partial) - 1);\n\n} /* end of Cudd_ApaSubtract */\n\n\n/**\n  @brief Divides an arbitrary precision integer by a digit.\n\n  @return the remainder digit.\n\n  @sideeffect The quotient is returned in parameter <code>quotient</code>.\n\n*/\nDdApaDigit\nCudd_ApaShortDivision(\n  int  digits,\n  DdConstApaNumber dividend,\n  DdApaDigit divisor,\n  DdApaNumber quotient)\n{\n    int i;\n    DdApaDigit remainder;\n    DdApaDoubleDigit partial;\n\n    remainder = 0;\n    for (i = 0; i < digits; i++) {\n\tpartial = remainder * DD_APA_BASE + dividend[i];\n\tquotient[i] = (DdApaDigit) (partial/(DdApaDoubleDigit)divisor);\n\tremainder = (DdApaDigit) (partial % divisor);\n    }\n\n    return(remainder);\n\n} /* end of Cudd_ApaShortDivision */\n\n\n/**\n  @brief Divides an arbitrary precision integer by an integer.\n\n  @details Divides an arbitrary precision integer by a 32-bit unsigned\n  integer. This procedure relies on the assumption that the number of\n  bits of a DdApaDigit plus the number of bits of an unsigned int is\n  less the number of bits of the mantissa of a double. This guarantees\n  that the product of a DdApaDigit and an unsigned int can be\n  represented without loss of precision by a double. On machines where\n  this assumption is not satisfied, this procedure will malfunction.\n\n  @return the remainder.\n\n  @sideeffect The quotient is returned in parameter <code>quotient</code>.\n\n  @deprecated The assumption on which the correctness of this function rests\n  is not satisfied by modern-day 64-bit CPUs.\n\n  @see Cudd_ApaShortDivision\n\n*/\nunsigned int\nCudd_ApaIntDivision(\n  int  digits,\n  DdConstApaNumber dividend,\n  unsigned int divisor,\n  DdApaNumber quotient)\n{\n    int i;\n    double partial;\n    unsigned int remainder = 0;\n    double ddiv = (double) divisor;\n\n    for (i = 0; i < digits; i++) {\n\tpartial = (double) remainder * DD_APA_BASE + dividend[i];\n\tquotient[i] = (DdApaDigit) (partial / ddiv);\n\tremainder = (unsigned int) (partial - ((double)quotient[i] * ddiv));\n    }\n\n    return(remainder);\n\n} /* end of Cudd_ApaIntDivision */\n\n\n/**\n  @brief Shifts right an arbitrary precision integer by one binary\n  place.\n\n  @details The most significant binary digit of the result is taken\n  from parameter <code>in</code>.\n\n  @sideeffect The result is returned in parameter <code>b</code>.\n\n*/\nvoid\nCudd_ApaShiftRight(\n  int digits,\n  DdApaDigit in,\n  DdConstApaNumber a,\n  DdApaNumber b)\n{\n    int i;\n\n    for (i = digits - 1; i > 0; i--) {\n\tb[i] = (a[i] >> 1) | ((a[i-1] & 1) << (DD_APA_BITS - 1));\n    }\n    b[0] = (a[0] >> 1) | (in << (DD_APA_BITS - 1));\n\n} /* end of Cudd_ApaShiftRight */\n\n\n/**\n  @brief Sets an arbitrary precision integer to a one-digit literal.\n\n  @sideeffect The result is returned in parameter <code>number</code>.\n\n*/\nvoid\nCudd_ApaSetToLiteral(\n  int digits,\n  DdApaNumber number,\n  DdApaDigit literal)\n{\n    int i;\n\n    for (i = 0; i < digits - 1; i++)\n\tnumber[i] = 0;\n    number[digits - 1] = literal;\n\n} /* end of Cudd_ApaSetToLiteral */\n\n\n/**\n  @brief Sets an arbitrary precision integer to a power of two.\n\n  @details If the power of two is too large to be represented, the number\n  is set to 0.\n\n  @sideeffect The result is returned in parameter <code>number</code>.\n\n*/\nvoid\nCudd_ApaPowerOfTwo(\n  int digits,\n  DdApaNumber number,\n  int power)\n{\n    int i;\n    int index;\n\n    for (i = 0; i < digits; i++)\n\tnumber[i] = 0;\n    i = digits - 1 - power / DD_APA_BITS;\n    if (i < 0) return;\n    index = power & (DD_APA_BITS - 1);\n    number[i] = (DdApaDigit) 1 << index;\n\n} /* end of Cudd_ApaPowerOfTwo */\n\n\n/**\n  @brief Compares two arbitrary precision integers.\n\n  @return 1 if the first number is larger; 0 if they are equal; -1 if\n  the second number is larger.\n\n  @sideeffect None\n\n*/\nint\nCudd_ApaCompare(\n  int digitsFirst,\n  DdConstApaNumber first,\n  int digitsSecond,\n  DdConstApaNumber second)\n{\n    int i;\n    int firstNZ, secondNZ;\n\n    /* Find first non-zero in both numbers. */\n    for (firstNZ = 0; firstNZ < digitsFirst; firstNZ++)\n\tif (first[firstNZ] != 0) break;\n    for (secondNZ = 0; secondNZ < digitsSecond; secondNZ++)\n\tif (second[secondNZ] != 0) break;\n    if (digitsFirst - firstNZ > digitsSecond - secondNZ) return(1);\n    else if (digitsFirst - firstNZ < digitsSecond - secondNZ) return(-1);\n    for (i = 0; i < digitsFirst - firstNZ; i++) {\n\tif (first[firstNZ + i] > second[secondNZ + i]) return(1);\n\telse if (first[firstNZ + i] < second[secondNZ + i]) return(-1);\n    }\n    return(0);\n\n} /* end of Cudd_ApaCompare */\n\n\n/**\n  @brief Compares the ratios of two arbitrary precision integers to two\n  unsigned ints.\n\n  @return 1 if the first number is larger; 0 if they are equal; -1 if\n  the second number is larger.\n\n  @sideeffect None\n\n*/\nint\nCudd_ApaCompareRatios(\n  int digitsFirst,\n  DdConstApaNumber firstNum,\n  unsigned int firstDen,\n  int digitsSecond,\n  DdConstApaNumber secondNum,\n  unsigned int secondDen)\n{\n    int result;\n    DdApaNumber first, second;\n    unsigned int firstRem, secondRem;\n\n    first = Cudd_NewApaNumber(digitsFirst);\n    firstRem = Cudd_ApaIntDivision(digitsFirst,firstNum,firstDen,first);\n    second = Cudd_NewApaNumber(digitsSecond);\n    secondRem = Cudd_ApaIntDivision(digitsSecond,secondNum,secondDen,second);\n    result = Cudd_ApaCompare(digitsFirst,first,digitsSecond,second);\n    FREE(first);\n    FREE(second);\n    if (result == 0) {\n\tif ((double)firstRem/firstDen > (double)secondRem/secondDen)\n\t    return(1);\n\telse if ((double)firstRem/firstDen < (double)secondRem/secondDen)\n\t    return(-1);\n    }\n    return(result);\n\n} /* end of Cudd_ApaCompareRatios */\n\n\n/**\n  @brief Prints an arbitrary precision integer in hexadecimal format.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_ApaPrintDecimal Cudd_ApaPrintExponential\n\n*/\nint\nCudd_ApaPrintHex(\n  FILE * fp,\n  int digits,\n  DdConstApaNumber number)\n{\n    int i, result;\n\n    for (i = 0; i < digits; i++) {\n        result = fprintf(fp, \"%0*x\", (int) sizeof(DdApaDigit) * 2, number[i]);\n\tif (result == EOF)\n\t    return(0);\n    }\n    return(1);\n\n} /* end of Cudd_ApaPrintHex */\n\n\n/**\n  @brief Prints an arbitrary precision integer in decimal format.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_ApaPrintHex Cudd_ApaPrintExponential\n\n*/\nint\nCudd_ApaPrintDecimal(\n  FILE * fp,\n  int digits,\n  DdConstApaNumber number)\n{\n    int i, result;\n    DdApaDigit remainder;\n    DdApaNumber work;\n    unsigned char *decimal;\n    int leadingzero;\n    int decimalDigits = (int) (digits * log10((double) DD_APA_BASE)) + 1;\n\n    work = Cudd_NewApaNumber(digits);\n    if (work == NULL)\n\treturn(0);\n    decimal = ALLOC(unsigned char, decimalDigits);\n    if (decimal == NULL) {\n\tFREE(work);\n\treturn(0);\n    }\n    Cudd_ApaCopy(digits,number,work);\n    for (i = decimalDigits - 1; i >= 0; i--) {\n\tremainder = Cudd_ApaShortDivision(digits,work,(DdApaDigit) 10,work);\n\tdecimal[i] = (unsigned char) remainder;\n    }\n    FREE(work);\n\n    leadingzero = 1;\n    for (i = 0; i < decimalDigits; i++) {\n\tleadingzero = leadingzero && (decimal[i] == 0);\n\tif ((!leadingzero) || (i == (decimalDigits - 1))) {\n\t    result = fprintf(fp,\"%1d\",decimal[i]);\n\t    if (result == EOF) {\n\t\tFREE(decimal);\n\t\treturn(0);\n\t    }\n\t}\n    }\n    FREE(decimal);\n    return(1);\n\n} /* end of Cudd_ApaPrintDecimal */\n\n\n/**\n  @brief converts an arbitrary precision integer to a string in decimal format.\n\n  @return the string if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_ApaPrintDecimal\n\n*/\nchar *\nCudd_ApaStringDecimal(\n  int digits,\n  DdConstApaNumber number)\n{\n    int i, fsd;\n    DdApaDigit remainder;\n    DdApaNumber work;\n    char *decimal, *ret;\n    int decimalDigits = (int) (digits * log10((double) DD_APA_BASE)) + 1;\n\n    work = Cudd_NewApaNumber(digits);\n    if (work == NULL) {\n\treturn(0);\n    }\n    decimal = ALLOC(char, decimalDigits);\n    if (decimal == NULL) {\n\tFREE(work);\n\treturn(0);\n    }\n    Cudd_ApaCopy(digits,number,work);\n    for (i = decimalDigits - 1; i >= 0; i--) {\n\tremainder = Cudd_ApaShortDivision(digits,work,(DdApaDigit) 10,work);\n\tdecimal[i] = (char) remainder;\n    }\n    FREE(work);\n\n    /* Find first significant digit. */\n    for (fsd = 0; fsd < decimalDigits-1; fsd++) {\n        if (decimal[fsd] != 0)\n            break;\n    }\n    ret = ALLOC(char, decimalDigits - fsd + 1);\n    if (ret == NULL) {\n        FREE(decimal);\n        return(NULL);\n    }\n    for (i = fsd; i < decimalDigits; i++) {\n        ret[i-fsd] = decimal[i] + '0';\n    }\n    ret[decimalDigits-fsd] = '\\0';\n    FREE(decimal);\n    return(ret);\n\n} /* end of Cudd_ApaStringDecimal */\n\n\n/**\n  @brief Prints an arbitrary precision integer in exponential format.\n\n  @details Prints as an integer if precision is at least the number of\n  digits to be printed.  If precision does not allow printing of all\n  digits, rounds to nearest breaking ties so that the last printed\n  digit is even.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_ApaPrintHex Cudd_ApaPrintDecimal\n\n*/\nint\nCudd_ApaPrintExponential(\n  FILE * fp,\n  int digits,\n  DdConstApaNumber number,\n  int precision)\n{\n    int i, first, last, result;\n    DdApaDigit remainder;\n    DdApaNumber work;\n    unsigned char *decimal, carry;\n    /* We add an extra digit to have room for rounding up. */\n    int decimalDigits = (int) (digits * log10((double) DD_APA_BASE)) + 2;\n\n    /* Convert to decimal. */\n    work = Cudd_NewApaNumber(digits);\n    if (work == NULL)\n\treturn(0);\n    decimal = ALLOC(unsigned char, decimalDigits);\n    if (decimal == NULL) {\n\tFREE(work);\n\treturn(0);\n    }\n    Cudd_ApaCopy(digits,number,work);\n    first = decimalDigits - 1;\n    for (i = decimalDigits - 1; i >= 0; i--) {\n\tremainder = Cudd_ApaShortDivision(digits,work,(DdApaDigit) 10,work);\n\tdecimal[i] = (unsigned char) remainder;\n\tif (remainder != 0) first = i; /* keep track of MS non-zero */\n    }\n    FREE(work);\n    last = ddMin(first + precision, decimalDigits);\n\n    /* See if we can print as integer. */\n    if (decimalDigits - first <= precision) {\n        for (i = first; i < last; i++) {\n            result = fprintf(fp,\"%1d\", decimal[i]);\n            if (result == EOF) {\n                FREE(decimal);\n                return(0);\n            }\n        }\n        FREE(decimal);\n        return(1);\n    }\n\n    /* If we get here we need to print an exponent.  Take care of rounding. */\n    if (last == decimalDigits) {\n        carry = 0;\n    } else if (decimal[last] < 5) {\n        carry = 0;\n    } else if (decimal[last] == 5) {\n        int nonZero = CUDD_FALSE;\n        for (i = last + 1; i < decimalDigits; i++) {\n            if (decimal[i] > 0) {\n                nonZero = CUDD_TRUE;\n                break;\n            }\n        }\n        if (nonZero) {\n            carry = 1;\n        } else if (decimal[last - 1] & 1) { /* odd */\n            carry = 1;\n        } else {\n            carry = 0;\n        }\n    } else {\n        carry = 1;\n    }\n\n    /* Add carry. */\n    for (i = last - 1; i >= 0; i--) {\n        unsigned char tmp = decimal[i] + carry;\n        if (tmp < 10) {\n            decimal[i] = tmp;\n            break;\n        } else {\n            decimal[i] = tmp - 10;\n        }\n    }\n\n    /* Don't print trailing zeros. */\n    while (last > first && decimal[last - 1] == 0)\n        last--;\n\n    /* Print. */\n    for (i = first; i < last; i++) {\n\tresult = fprintf(fp,\"%s%1d\",i == first+1 ? \".\" : \"\", decimal[i]);\n\tif (result == EOF) {\n\t    FREE(decimal);\n\t    return(0);\n\t}\n    }\n    FREE(decimal);\n    result = fprintf(fp,\"e+%02d\",decimalDigits - first - 1);\n    if (result == EOF) {\n\treturn(0);\n    }\n    return(1);\n\n} /* end of Cudd_ApaPrintExponential */\n\n\n/**\n  @brief Counts the number of minterms of a %DD.\n\n  @details The function is assumed to depend on nvars variables. The\n  minterm count is represented as an arbitrary precision unsigned\n  integer, to allow for any number of variables CUDD supports.\n\n  @return a pointer to the array representing the number of minterms\n  of the function rooted at node if successful; NULL otherwise.\n\n  @sideeffect The number of digits of the result is returned in\n  parameter <code>digits</code>.\n\n  @see Cudd_CountMinterm\n\n*/\nDdApaNumber\nCudd_ApaCountMinterm(\n  DdManager const * manager,\n  DdNode * node,\n  int  nvars,\n  int * digits)\n{\n    DdApaNumber\tmmax, mmin;\n    st_table\t*table;\n    DdApaNumber\ti,count;\n\n    *digits = Cudd_ApaNumberOfDigits(nvars+1);\n    mmax = Cudd_NewApaNumber(*digits);\n    if (mmax == NULL) {\n\treturn(NULL);\n    }\n    Cudd_ApaPowerOfTwo(*digits,mmax,nvars);\n    mmin = Cudd_NewApaNumber(*digits);\n    if (mmin == NULL) {\n\tFREE(mmax);\n\treturn(NULL);\n    }\n    Cudd_ApaSetToLiteral(*digits,mmin,0);\n    table = st_init_table(st_ptrcmp,st_ptrhash);\n    if (table == NULL) {\n\tFREE(mmax);\n\tFREE(mmin);\n\treturn(NULL);\n    }\n    i = cuddApaCountMintermAux(manager, Cudd_Regular(node),*digits,mmax,mmin,table);\n    if (i == NULL) {\n\tFREE(mmax);\n\tFREE(mmin);\n\tst_foreach(table, cuddApaStCountfree, NULL);\n\tst_free_table(table);\n\treturn(NULL);\n    }\n    count = Cudd_NewApaNumber(*digits);\n    if (count == NULL) {\n\tFREE(mmax);\n\tFREE(mmin);\n\tst_foreach(table, cuddApaStCountfree, NULL);\n\tst_free_table(table);\n\tif (Cudd_Regular(node)->ref == 1) FREE(i);\n\treturn(NULL);\n    }\n    if (Cudd_IsComplement(node)) {\n\t(void) Cudd_ApaSubtract(*digits,mmax,i,count);\n    } else {\n\tCudd_ApaCopy(*digits,i,count);\n    }\n    FREE(mmax);\n    FREE(mmin);\n    st_foreach(table, cuddApaStCountfree, NULL);\n    st_free_table(table);\n    if (Cudd_Regular(node)->ref == 1) FREE(i);\n    return(count);\n\n} /* end of Cudd_ApaCountMinterm */\n\n\n/**\n  @brief Prints the number of minterms of a %BDD or %ADD using arbitrary\n  precision arithmetic.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_ApaPrintMintermExp\n\n*/\nint\nCudd_ApaPrintMinterm(\n  FILE * fp,\n  DdManager const * dd,\n  DdNode * node,\n  int  nvars)\n{\n    int digits;\n    int result;\n    DdApaNumber count;\n\n    count = Cudd_ApaCountMinterm(dd,node,nvars,&digits);\n    if (count == NULL)\n\treturn(0);\n    result = Cudd_ApaPrintDecimal(fp,digits,count);\n    FREE(count);\n    if (fprintf(fp,\"\\n\") == EOF) {\n\treturn(0);\n    }\n    return(result);\n\n} /* end of Cudd_ApaPrintMinterm */\n\n\n/**\n  @brief Prints the number of minterms of a %BDD or %ADD in\n  exponential format using arbitrary precision arithmetic.\n\n  @details Parameter precision controls the number of signficant\n  digits printed.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_ApaPrintMinterm\n\n*/\nint\nCudd_ApaPrintMintermExp(\n  FILE * fp,\n  DdManager const * dd,\n  DdNode * node,\n  int nvars,\n  int precision)\n{\n    int digits;\n    int result;\n    DdApaNumber count;\n\n    count = Cudd_ApaCountMinterm(dd,node,nvars,&digits);\n    if (count == NULL)\n\treturn(0);\n    result = Cudd_ApaPrintExponential(fp,digits,count,precision);\n    FREE(count);\n    if (fprintf(fp,\"\\n\") == EOF) {\n\treturn(0);\n    }\n    return(result);\n\n} /* end of Cudd_ApaPrintMintermExp */\n\n\n/**\n  @brief Prints the density of a %BDD or %ADD using arbitrary\n  precision arithmetic.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nCudd_ApaPrintDensity(\n  FILE * fp,\n  DdManager * dd,\n  DdNode * node,\n  int nvars)\n{\n    int digits;\n    int result;\n    DdApaNumber count,density;\n    unsigned int size, remainder, fractional;\n\n    count = Cudd_ApaCountMinterm(dd,node,nvars,&digits);\n    if (count == NULL)\n\treturn(0);\n    size = (unsigned int) Cudd_DagSize(node);\n    density = Cudd_NewApaNumber(digits);\n    remainder = Cudd_ApaIntDivision(digits,count,size,density);\n    result = Cudd_ApaPrintDecimal(fp,digits,density);\n    FREE(count);\n    FREE(density);\n    fractional = (unsigned int)((double)remainder / size * 1000000);\n    if (fprintf(fp,\".%u\\n\", fractional) == EOF) {\n\treturn(0);\n    }\n    return(result);\n\n} /* end of Cudd_ApaPrintDensity */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_ApaCountMinterm.\n\n  @details It is based on the following identity. Let <code>|f|</code> be the\n  number of minterms of <code>f</code>. Then:\n\n      |f| = (|f0|+|f1|)/2\n\n  where f0 and f1 are the two cofactors of f.\n  Uses the identity <code>|f'| = mmax - |f|</code>.\n  The procedure expects the argument \"node\" to be a regular pointer, and\n  guarantees this condition is met in the recursive calls.\n  For efficiency, the result of a call is cached only if the node has\n  a reference count greater than 1.\n\n  @return the number of minterms of the function rooted at node.\n\n  @sideeffect None\n\n*/\nstatic DdApaNumber\ncuddApaCountMintermAux(\n  DdManager const * manager,\n  DdNode * node,\n  int digits,\n  DdApaNumber mmax,\n  DdApaNumber mmin,\n  st_table * table)\n{\n    DdNode      *Nt, *Ne;\n    DdApaNumber\tmint, mint1, mint2;\n    DdApaDigit\tcarryout;\n\n    if (cuddIsConstant(node)) {\n        int singleRef = Cudd_Regular(node)->ref == 1;\n        if (node == manager->background || node == Cudd_Not(manager->one)) {\n            if (singleRef) {\n                mint = Cudd_NewApaNumber(digits);\n                if (mint == NULL) {\n                    return(NULL);\n                }\n                Cudd_ApaCopy(digits, mmin, mint);\n                return(mint);\n            } else {\n                return(mmin);\n            }\n\t} else {\n            if (singleRef) {\n                mint = Cudd_NewApaNumber(digits);\n                if (mint == NULL) {\n                    return(NULL);\n                }\n                Cudd_ApaCopy(digits, mmax, mint);\n                return(mint);\n            } else {\n                return(mmax);\n            }\n\t}\n    }\n    if (node->ref > 1 && st_lookup(table, node, (void **) &mint)) {\n\treturn(mint);\n    }\n\n    Nt = cuddT(node); Ne = cuddE(node);\n\n    mint1 = cuddApaCountMintermAux(manager, Nt,  digits, mmax, mmin, table);\n    if (mint1 == NULL) return(NULL);\n    mint2 = cuddApaCountMintermAux(manager, Cudd_Regular(Ne), digits, mmax, mmin, table);\n    if (mint2 == NULL) {\n\tif (Nt->ref == 1) FREE(mint1);\n\treturn(NULL);\n    }\n    mint = Cudd_NewApaNumber(digits);\n    if (mint == NULL) {\n\tif (Nt->ref == 1) FREE(mint1);\n\tif (Cudd_Regular(Ne)->ref == 1) FREE(mint2);\n\treturn(NULL);\n    }\n    if (Cudd_IsComplement(Ne)) {\n\t(void) Cudd_ApaSubtract(digits,mmax,mint2,mint);\n\tcarryout = Cudd_ApaAdd(digits,mint1,mint,mint);\n    } else {\n\tcarryout = Cudd_ApaAdd(digits,mint1,mint2,mint);\n    }\n    Cudd_ApaShiftRight(digits,carryout,mint,mint);\n    /* If the refernce count of a child is 1, its minterm count\n    ** hasn't been stored in table.  Therefore, it must be explicitly\n    ** freed here. */\n    if (Nt->ref == 1) FREE(mint1);\n    if (Cudd_Regular(Ne)->ref == 1) FREE(mint2);\n\n    if (node->ref > 1) {\n\tif (st_insert(table, node, mint) == ST_OUT_OF_MEM) {\n\t    FREE(mint);\n\t    return(NULL);\n\t}\n    }\n    return(mint);\n\n} /* end of cuddApaCountMintermAux */\n\n\n/**\n  @brief Frees the memory used to store the minterm counts recorded\n  in the visited table.\n\n  @return ST_CONTINUE.\n\n  @sideeffect None\n\n*/\nstatic enum st_retval\ncuddApaStCountfree(\n  void * key,\n  void * value,\n  void * arg)\n{\n    DdApaNumber\td;\n\n    (void) key; /* avoid warning */\n    (void) arg; /* avoid warning */\n    d = (DdApaNumber) value;\n    FREE(d);\n    return(ST_CONTINUE);\n\n} /* end of cuddApaStCountfree */\n"
  },
  {
    "path": "cudd/cudd/cuddApprox.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Procedures to approximate a given %BDD.\n\n  @see cuddSubsetHB.c cuddSubsetSP.c cuddGenCof.c\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifdef __STDC__\n#include <float.h>\n#else\n#define DBL_MAX_EXP 1024\n#endif\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define NOTHING\t\t0\n#define REPLACE_T\t1\n#define REPLACE_E\t2\n#define REPLACE_N\t3\n#define REPLACE_TT\t4\n#define REPLACE_TE\t5\n\n#define DONT_CARE\t0\n#define CARE\t\t1\n#define TOTAL_CARE\t2\n#define CARE_ERROR\t3\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n ** @brief Data structure to store the information on each node.\n **\n ** @details It keeps the number of minterms of the function rooted at\n ** this node in terms of the number of variables specified by the\n ** user; the number of minterms of the complement; the impact of the\n ** number of minterms of this function on the number of minterms of\n ** the root function; the reference count of the node from within the\n ** root function; the flag that says whether the node intersects the\n ** care set; the flag that says whether the node should be replaced\n ** and how; the results of subsetting in both phases.\n */\ntypedef struct NodeData {\n    double mintermsP;\t\t/**< minterms for the regular node */\n    double mintermsN;\t\t/**< minterms for the complemented node */\n    int functionRef;\t\t/**< references from within this function */\n    char care;\t\t\t/**< node intersects care set */\n    char replace;\t\t/**< replacement decision */\n    short int parity;\t\t/**< 1: even; 2: odd; 3: both */\n    DdNode *resultP;\t\t/**< result for even parity */\n    DdNode *resultN;\t\t/**< result for odd parity */\n} NodeData;\n\n/**\n **  @brief Main bookkeeping data structure for approximation algorithms.\n */\ntypedef struct ApproxInfo {\n    DdNode *one;\t\t/**< one constant */\n    DdNode *zero;\t\t/**< %BDD zero constant */\n    NodeData *page;\t\t/**< per-node information */\n    DdHashTable *table;\t\t/**< hash table to access the per-node info */\n    int index;\t\t\t/**< index of the current node */\n    double max;\t\t\t/**< max number of minterms */\n    int size;\t\t\t/**< how many nodes are left */\n    double minterms;\t\t/**< how many minterms are left */\n} ApproxInfo;\n\n/**\n ** @brief Item of the queue used in the levelized traversal of the %BDD.\n */\ntypedef struct GlobalQueueItem {\n    struct GlobalQueueItem *next;\n    struct GlobalQueueItem *cnext;\n    DdNode *node;\n    double impactP;\n    double impactN;\n} GlobalQueueItem;\n\n/**\n ** @brief Type of the item of the local queue.\n */\ntypedef struct LocalQueueItem {\n    struct LocalQueueItem *next;\n    struct LocalQueueItem *cnext;\n    DdNode *node;\n    int localRef;\n} LocalQueueItem;\n\n    \n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void updateParity (DdNode *node, ApproxInfo *info, int newparity);\nstatic NodeData * gatherInfoAux (DdNode *node, ApproxInfo *info, int parity);\nstatic ApproxInfo * gatherInfo (DdManager *dd, DdNode *node, int numVars, int parity);\nstatic int computeSavings (DdManager *dd, DdNode *f, DdNode *skip, ApproxInfo *info, DdLevelQueue *queue);\nstatic int updateRefs (DdManager *dd, DdNode *f, DdNode *skip, ApproxInfo *info, DdLevelQueue *queue);\nstatic int UAmarkNodes (DdManager *dd, DdNode *f, ApproxInfo *info, int threshold, int safe, double quality);\nstatic DdNode * UAbuildSubset (DdManager *dd, DdNode *node, ApproxInfo *info);\nstatic int RAmarkNodes (DdManager *dd, DdNode *f, ApproxInfo *info, int threshold, double quality);\nstatic int BAmarkNodes (DdManager *dd, DdNode *f, ApproxInfo *info, int threshold, double quality1, double quality0);\nstatic DdNode * RAbuildSubset (DdManager *dd, DdNode *node, ApproxInfo *info);\nstatic int BAapplyBias (DdManager *dd, DdNode *f, DdNode *b, ApproxInfo *info, DdHashTable *cache);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Extracts a dense subset from a %BDD with Shiple's\n  underapproximation method.\n\n  @details This procedure uses a variant of Tom Shiple's\n  underapproximation method. The main difference from the original\n  method is that density is used as cost function.  The parameter\n  numVars is the maximum number of variables to be used in minterm\n  calculation.  The optimal number should be as close as possible to\n  the size of the support of f.  However, it is safe to pass the value\n  returned by Cudd_ReadSize for numVars when the number of variables\n  is under 1023.  If numVars is larger than 1023, it will cause\n  overflow. If a 0 parameter is passed then the procedure will compute\n  a value which will avoid overflow but will cause underflow with 2046\n  variables or more.\n\n  @return a pointer to the %BDD of the subset if successful; NULL if\n  the procedure runs out of memory.\n\n  @sideeffect None\n\n  @see Cudd_SubsetShortPaths Cudd_SubsetHeavyBranch Cudd_ReadSize\n\n*/\nDdNode *\nCudd_UnderApprox(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be subset */,\n  int  numVars /**< number of variables in the support of f */,\n  int  threshold /**< when to stop approximation */,\n  int  safe /**< enforce safe approximation */,\n  double  quality /**< minimum improvement for accepted changes */)\n{\n    DdNode *subset;\n\n    do {\n\tdd->reordered = 0;\n\tsubset = cuddUnderApprox(dd, f, numVars, threshold, safe, quality);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(subset);\n\n} /* end of Cudd_UnderApprox */\n\n\n/**\n  @brief Extracts a dense superset from a %BDD with Shiple's\n  underapproximation method.\n\n  @details The procedure is identical to the underapproximation\n  procedure except for the fact that it works on the complement of the\n  given function. Extracting the subset of the complement function is\n  equivalent to extracting the superset of the function.  The\n  parameter numVars is the maximum number of variables to be used in\n  minterm calculation.  The optimal number should be as close as\n  possible to the size of the support of f.  However, it is safe to\n  pass the value returned by Cudd_ReadSize for numVars when the number\n  of variables is under 1023.  If numVars is larger than 1023, it will\n  overflow. If a 0 parameter is passed then the procedure will compute\n  a value which will avoid overflow but will cause underflow with 2046\n  variables or more.\n  \n  @return a pointer to the %BDD of the superset if successful. NULL if\n  intermediate result causes the procedure to run out of memory.\n\n  @sideeffect None\n\n  @see Cudd_SupersetHeavyBranch Cudd_SupersetShortPaths Cudd_ReadSize\n\n*/\nDdNode *\nCudd_OverApprox(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be superset */,\n  int  numVars /**< number of variables in the support of f */,\n  int  threshold /**< when to stop approximation */,\n  int  safe /**< enforce safe approximation */,\n  double  quality /**< minimum improvement for accepted changes */)\n{\n    DdNode *subset, *g;\n\n    g = Cudd_Not(f);    \n    do {\n\tdd->reordered = 0;\n\tsubset = cuddUnderApprox(dd, g, numVars, threshold, safe, quality);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(Cudd_NotCond(subset, (subset != NULL)));\n    \n} /* end of Cudd_OverApprox */\n\n\n/**\n  @brief Extracts a dense subset from a %BDD with the remapping\n  underapproximation method.\n\n  @details This procedure uses a remapping technique and density as\n  the cost function.  The parameter numVars is the maximum number of\n  variables to be used in minterm calculation.  The optimal number\n  should be as close as possible to the size of the support of f.\n  However, it is safe to pass the value returned by Cudd_ReadSize for\n  numVars when the number of variables is under 1023.  If numVars is\n  larger than 1023, it will cause overflow. If a 0 parameter is passed\n  then the procedure will compute a value which will avoid overflow\n  but will cause underflow with 2046 variables or more.\n\n  @return a pointer to the %BDD of the subset if successful. NULL if\n  the procedure runs out of memory.\n  \n  @sideeffect None\n\n  @see Cudd_SubsetShortPaths Cudd_SubsetHeavyBranch Cudd_UnderApprox Cudd_ReadSize\n\n*/\nDdNode *\nCudd_RemapUnderApprox(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be subset */,\n  int  numVars /**< number of variables in the support of f */,\n  int  threshold /**< when to stop approximation */,\n  double  quality /**< minimum improvement for accepted changes */)\n{\n    DdNode *subset;\n\n    do {\n\tdd->reordered = 0;\n\tsubset = cuddRemapUnderApprox(dd, f, numVars, threshold, quality);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(subset);\n\n} /* end of Cudd_RemapUnderApprox */\n\n\n/**\n  @brief Extracts a dense superset from a %BDD with the remapping\n  underapproximation method.\n\n  @details The procedure is identical to the underapproximation\n  procedure except for the fact that it works on the complement of the\n  given function. Extracting the subset of the complement function is\n  equivalent to extracting the superset of the function. The parameter\n  numVars is the maximum number of variables to be used in minterm\n  calculation.  The optimal number should be as close as possible to\n  the size of the support of f.  However, it is safe to pass the value\n  returned by Cudd_ReadSize for numVars when the number of variables\n  is under 1023.  If numVars is larger than 1023, it will overflow. If\n  a 0 parameter is passed then the procedure will compute a value\n  which will avoid overflow but will cause underflow with 2046\n  variables or more.\n\n  @return a pointer to the %BDD of the superset if successful. NULL if\n  intermediate result causes the procedure to run out of memory.\n  \n  @sideeffect None\n\n  @see Cudd_SupersetHeavyBranch Cudd_SupersetShortPaths Cudd_ReadSize\n\n*/\nDdNode *\nCudd_RemapOverApprox(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be superset */,\n  int  numVars /**< number of variables in the support of f */,\n  int  threshold /**< when to stop approximation */,\n  double  quality /**< minimum improvement for accepted changes */)\n{\n    DdNode *subset, *g;\n\n    g = Cudd_Not(f);    \n    do {\n\tdd->reordered = 0;\n\tsubset = cuddRemapUnderApprox(dd, g, numVars, threshold, quality);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(Cudd_NotCond(subset, (subset != NULL)));\n    \n} /* end of Cudd_RemapOverApprox */\n\n\n/**\n  @brief Extracts a dense subset from a %BDD with the biased\n  underapproximation method.\n\n  @details This procedure uses a biased remapping technique and\n  density as the cost function. The bias is a function. This procedure\n  tries to approximate where the bias is 0 and preserve the given\n  function where the bias is 1.  The parameter numVars is the maximum\n  number of variables to be used in minterm calculation.  The optimal\n  number should be as close as possible to the size of the support of\n  f.  However, it is safe to pass the value returned by Cudd_ReadSize\n  for numVars when the number of variables is under 1023.  If numVars\n  is larger than 1023, it will cause overflow. If a 0 parameter is\n  passed then the procedure will compute a value which will avoid\n  overflow but will cause underflow with 2046 variables or more.\n\n  @return a pointer to the %BDD of the subset if successful. NULL if\n  the procedure runs out of memory.\n  \n  @sideeffect None\n\n  @see Cudd_SubsetShortPaths Cudd_SubsetHeavyBranch Cudd_UnderApprox\n  Cudd_RemapUnderApprox Cudd_ReadSize\n\n*/\nDdNode *\nCudd_BiasedUnderApprox(\n  DdManager *dd /**< manager */,\n  DdNode *f /**< function to be subset */,\n  DdNode *b /**< bias function */,\n  int numVars /**< number of variables in the support of f */,\n  int threshold /**< when to stop approximation */,\n  double quality1 /**< minimum improvement for accepted changes when b=1 */,\n  double quality0 /**< minimum improvement for accepted changes when b=0 */)\n{\n    DdNode *subset;\n\n    do {\n\tdd->reordered = 0;\n\tsubset = cuddBiasedUnderApprox(dd, f, b, numVars, threshold, quality1,\n\t\t\t\t       quality0);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(subset);\n\n} /* end of Cudd_BiasedUnderApprox */\n\n\n/**\n  @brief Extracts a dense superset from a %BDD with the biased\n  underapproximation method.\n\n  @details The procedure is identical to the underapproximation\n  procedure except for the fact that it works on the complement of the\n  given function. Extracting the subset of the complement function is\n  equivalent to extracting the superset of the function.  The\n  parameter numVars is the maximum number of variables to be used in\n  minterm calculation.  The optimal number should be as close as\n  possible to the size of the support of f.  However, it is safe to\n  pass the value returned by Cudd_ReadSize for numVars when the number\n  of variables is under 1023.  If numVars is larger than 1023, it will\n  overflow. If a 0 parameter is passed then the procedure will compute\n  a value which will avoid overflow but will cause underflow with 2046\n  variables or more.\n\n  @return a pointer to the %BDD of the superset if successful. NULL if\n  intermediate result causes the procedure to run out of memory.\n  \n  @sideeffect None\n\n  @see Cudd_SupersetHeavyBranch Cudd_SupersetShortPaths\n  Cudd_RemapOverApprox Cudd_BiasedUnderApprox Cudd_ReadSize\n\n*/\nDdNode *\nCudd_BiasedOverApprox(\n  DdManager *dd /**< manager */,\n  DdNode *f /**< function to be superset */,\n  DdNode *b /**< bias function */,\n  int numVars /**< number of variables in the support of f */,\n  int threshold /**< when to stop approximation */,\n  double quality1 /**< minimum improvement for accepted changes when b=1*/,\n  double quality0 /**< minimum improvement for accepted changes when b=0 */)\n{\n    DdNode *subset, *g;\n\n    g = Cudd_Not(f);    \n    do {\n\tdd->reordered = 0;\n\tsubset = cuddBiasedUnderApprox(dd, g, b, numVars, threshold, quality1,\n\t\t\t\t      quality0);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(Cudd_NotCond(subset, (subset != NULL)));\n    \n} /* end of Cudd_BiasedOverApprox */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Applies Tom Shiple's underappoximation algorithm.\n\n  @details Proceeds in three phases:\n  <ul>\n  <li> collect information on each node in the %BDD; this is done via DFS.\n  <li> traverse the %BDD in top-down fashion and compute for each node\n  whether its elimination increases density.\n  <li> traverse the %BDD via DFS and actually perform the elimination.\n  </ul>\n\n  @return the approximated %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_UnderApprox\n\n*/\nDdNode *\ncuddUnderApprox(\n  DdManager * dd /**< %DD manager */,\n  DdNode * f /**< current %DD */,\n  int  numVars /**< maximum number of variables */,\n  int  threshold /**< threshold under which approximation stops */,\n  int  safe /**< enforce safe approximation */,\n  double  quality /**< minimum improvement for accepted changes */)\n{\n    ApproxInfo *info;\n    DdNode *subset;\n    int result;\n\n    if (f == NULL) {\n\tfprintf(dd->err, \"Cannot subset, nil object\\n\");\n\treturn(NULL);\n    }\n\n    if (Cudd_IsConstantInt(f)) {\n\treturn(f);\n    }\n\n    /* Create table where node data are accessible via a hash table. */\n    info = gatherInfo(dd, f, numVars, safe);\n    if (info == NULL) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    /* Mark nodes that should be replaced by zero. */\n    result = UAmarkNodes(dd, f, info, threshold, safe, quality);\n    if (result == 0) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tFREE(info->page);\n\tcuddHashTableGenericQuit(info->table);\n\tFREE(info);\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    /* Build the result. */\n    subset = UAbuildSubset(dd, f, info);\n#if 1\n    if (subset && info->size < Cudd_DagSize(subset))\n\t(void) fprintf(dd->err, \"Wrong prediction: %d versus actual %d\\n\",\n\t\t       info->size, Cudd_DagSize(subset));\n#endif\n    FREE(info->page);\n    cuddHashTableGenericQuit(info->table);\n    FREE(info);\n\n#ifdef DD_DEBUG\n    if (subset != NULL) {\n\tcuddRef(subset);\n#if 0\n\t(void) Cudd_DebugCheck(dd);\n\t(void) Cudd_CheckKeys(dd);\n#endif\n\tif (!Cudd_bddLeq(dd, subset, f)) {\n\t    (void) fprintf(dd->err, \"Wrong subset\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t}\n\tcuddDeref(subset);\n    }\n#endif\n    return(subset);\n\n} /* end of cuddUnderApprox */\n\n\n/**\n  @brief Applies the remapping underappoximation algorithm.\n\n  @details Proceeds in three phases:\n  <ul>\n  <li> collect information on each node in the %BDD; this is done via DFS.\n  <li> traverse the %BDD in top-down fashion and compute for each node\n  whether remapping increases density.\n  <li> traverse the %BDD via DFS and actually perform the elimination.\n  </ul>\n\n  @return the approximated %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_RemapUnderApprox\n\n*/\nDdNode *\ncuddRemapUnderApprox(\n  DdManager * dd /**< %DD manager */,\n  DdNode * f /**< current %DD */,\n  int  numVars /**< maximum number of variables */,\n  int  threshold /**< threshold under which approximation stops */,\n  double  quality /**< minimum improvement for accepted changes */)\n{\n    ApproxInfo *info;\n    DdNode *subset;\n    int result;\n\n    if (f == NULL) {\n\tfprintf(dd->err, \"Cannot subset, nil object\\n\");\n\tdd->errorCode = CUDD_INVALID_ARG;\n\treturn(NULL);\n    }\n\n    if (Cudd_IsConstantInt(f)) {\n\treturn(f);\n    }\n\n    /* Create table where node data are accessible via a hash table. */\n    info = gatherInfo(dd, f, numVars, CUDD_TRUE);\n    if (info == NULL) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    /* Mark nodes that should be replaced by zero. */\n    result = RAmarkNodes(dd, f, info, threshold, quality);\n    if (result == 0) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tFREE(info->page);\n\tcuddHashTableGenericQuit(info->table);\n\tFREE(info);\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    /* Build the result. */\n    subset = RAbuildSubset(dd, f, info);\n#if 1\n    if (subset && info->size < Cudd_DagSize(subset))\n\t(void) fprintf(dd->err, \"Wrong prediction: %d versus actual %d\\n\",\n\t\t       info->size, Cudd_DagSize(subset));\n#endif\n    FREE(info->page);\n    cuddHashTableGenericQuit(info->table);\n    FREE(info);\n\n#ifdef DD_DEBUG\n    if (subset != NULL) {\n\tcuddRef(subset);\n#if 0\n\t(void) Cudd_DebugCheck(dd);\n\t(void) Cudd_CheckKeys(dd);\n#endif\n\tif (!Cudd_bddLeq(dd, subset, f)) {\n\t    (void) fprintf(dd->err, \"Wrong subset\\n\");\n\t}\n\tcuddDeref(subset);\n\tdd->errorCode = CUDD_INTERNAL_ERROR;\n    }\n#endif\n    return(subset);\n\n} /* end of cuddRemapUnderApprox */\n\n\n/**\n  @brief Applies the biased remapping underappoximation algorithm.\n\n  @details Proceeds in three phases:\n  <ul>\n  <li> collect information on each node in the %BDD; this is done via DFS.\n  <li> traverse the %BDD in top-down fashion and compute for each node\n  whether remapping increases density.\n  <li> traverse the %BDD via DFS and actually perform the elimination.\n  </ul>\n\n  @return the approximated %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_BiasedUnderApprox\n\n*/\nDdNode *\ncuddBiasedUnderApprox(\n  DdManager *dd /**< %DD manager */,\n  DdNode *f /**< current %DD */,\n  DdNode *b /**< bias function */,\n  int numVars /**< maximum number of variables */,\n  int threshold /**< threshold under which approximation stops */,\n  double quality1 /**< minimum improvement for accepted changes when b=1 */,\n  double quality0 /**< minimum improvement for accepted changes when b=0 */)\n{\n    ApproxInfo *info;\n    DdNode *subset;\n    int result;\n    DdHashTable\t*cache;\n\n    if (f == NULL) {\n\tfprintf(dd->err, \"Cannot subset, nil object\\n\");\n\tdd->errorCode = CUDD_INVALID_ARG;\n\treturn(NULL);\n    }\n\n    if (Cudd_IsConstantInt(f)) {\n\treturn(f);\n    }\n\n    /* Create table where node data are accessible via a hash table. */\n    info = gatherInfo(dd, f, numVars, CUDD_TRUE);\n    if (info == NULL) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    cache = cuddHashTableInit(dd,2,2);\n    result = BAapplyBias(dd, Cudd_Regular(f), b, info, cache);\n    if (result == CARE_ERROR) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tcuddHashTableQuit(cache);\n\tFREE(info->page);\n\tcuddHashTableGenericQuit(info->table);\n\tFREE(info);\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    cuddHashTableQuit(cache);\n\n    /* Mark nodes that should be replaced by zero. */\n    result = BAmarkNodes(dd, f, info, threshold, quality1, quality0);\n    if (result == 0) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tFREE(info->page);\n\tcuddHashTableGenericQuit(info->table);\n\tFREE(info);\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    /* Build the result. */\n    subset = RAbuildSubset(dd, f, info);\n#if 1\n    if (subset && info->size < Cudd_DagSize(subset))\n\t(void) fprintf(dd->err, \"Wrong prediction: %d versus actual %d\\n\",\n\t\t       info->size, Cudd_DagSize(subset));\n#endif\n    FREE(info->page);\n    cuddHashTableGenericQuit(info->table);\n    FREE(info);\n\n#ifdef DD_DEBUG\n    if (subset != NULL) {\n\tcuddRef(subset);\n#if 0\n\t(void) Cudd_DebugCheck(dd);\n\t(void) Cudd_CheckKeys(dd);\n#endif\n\tif (!Cudd_bddLeq(dd, subset, f)) {\n\t    (void) fprintf(dd->err, \"Wrong subset\\n\");\n\t}\n\tcuddDeref(subset);\n\tdd->errorCode = CUDD_INTERNAL_ERROR;\n    }\n#endif\n    return(subset);\n\n} /* end of cuddBiasedUnderApprox */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Recursively update the parity of the paths reaching a node.\n\n  @details Assumes that node is regular and propagates the invariant.\n\n  @sideeffect None\n\n  @see gatherInfoAux\n\n*/\nstatic void\nupdateParity(\n  DdNode * node /**< function to analyze */,\n  ApproxInfo * info /**< info on %BDD */,\n  int newparity /**< new parity for node */)\n{\n    NodeData *infoN;\n    DdNode *E;\n\n    if ((infoN = (NodeData *) cuddHashTableGenericLookup(info->table, node)) == NULL)\n        return;\n    if ((infoN->parity & newparity) != 0) return;\n    infoN->parity |= (short) newparity;\n    if (Cudd_IsConstantInt(node)) return;\n    updateParity(cuddT(node),info,newparity);\n    E = cuddE(node);\n    if (Cudd_IsComplement(E)) {\n\tupdateParity(Cudd_Not(E),info,3-newparity);\n    } else {\n\tupdateParity(E,info,newparity);\n    }\n    return;\n\n} /* end of updateParity */\n\n\n/**\n  @brief Recursively counts minterms and computes reference counts\n  of each node in the %BDD.\n\n  @details Similar to the cuddCountMintermAux which recursively counts\n  the number of minterms for the dag rooted at each node in terms of\n  the total number of variables (max). It assumes that the node\n  pointer passed to it is regular and it maintains the invariant.\n\n  @sideeffect None\n\n  @see gatherInfo\n\n*/\nstatic NodeData *\ngatherInfoAux(\n  DdNode * node /**< function to analyze */,\n  ApproxInfo * info /**< info on %BDD */,\n  int parity /**< gather parity information */)\n{\n    DdNode\t*N, *Nt, *Ne;\n    NodeData\t*infoN, *infoT, *infoE;\n\n    N = Cudd_Regular(node);\n\n    /* Check whether entry for this node exists. */\n    if ((infoN = (NodeData *) cuddHashTableGenericLookup(info->table, N)) != NULL) {\n\tif (parity) {\n\t    /* Update parity and propagate. */\n\t    updateParity(N, info, 1 +  (int) Cudd_IsComplement(node));\n\t}\n\treturn(infoN);\n    }\n\n    /* Compute the cofactors. */\n    Nt = Cudd_NotCond(cuddT(N), N != node);\n    Ne = Cudd_NotCond(cuddE(N), N != node);\n\n    infoT = gatherInfoAux(Nt, info, parity);\n    if (infoT == NULL) return(NULL);\n    infoE = gatherInfoAux(Ne, info, parity);\n    if (infoE == NULL) return(NULL);\n\n    infoT->functionRef++;\n    infoE->functionRef++;\n\n    /* Point to the correct location in the page. */\n    infoN = &(info->page[info->index++]);\n    infoN->parity |= (short) (1 + Cudd_IsComplement(node));\n\n    infoN->mintermsP = infoT->mintermsP/2;\n    infoN->mintermsN = infoT->mintermsN/2;\n    if (Cudd_IsComplement(Ne) ^ Cudd_IsComplement(node)) {\n\tinfoN->mintermsP += infoE->mintermsN/2;\n\tinfoN->mintermsN += infoE->mintermsP/2;\n    } else {\n\tinfoN->mintermsP += infoE->mintermsP/2;\n\tinfoN->mintermsN += infoE->mintermsN/2;\n    }\n\n    /* Insert entry for the node in the table. */\n    if (cuddHashTableGenericInsert(info->table, N, infoN) == 0) {\n\treturn(NULL);\n    }\n    return(infoN);\n\n} /* end of gatherInfoAux */\n\n\n/**\n  @brief Gathers information about each node.\n\n  @details Counts minterms and computes reference counts of each\n  node in the %BDD. The minterm count is separately computed for the\n  node and its complement. This is to avoid cancellation\n  errors.\n\n  @return a pointer to the data structure holding the information\n  gathered if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddUnderApprox gatherInfoAux\n\n*/\nstatic ApproxInfo *\ngatherInfo(\n  DdManager * dd /* manager */,\n  DdNode * node /* function to be analyzed */,\n  int numVars /* number of variables node depends on */,\n  int parity /* gather parity information */)\n{\n    ApproxInfo * info;\n    NodeData * infoTop;\n\n    /* If user did not give numVars value, set it to the maximum\n    ** exponent that the pow function can take. The -1 is due to the\n    ** discrepancy in the value that pow takes and the value that\n    ** log gives.\n    */\n    if (numVars == 0) {\n\tnumVars = DBL_MAX_EXP - 1;\n    }\n\n    info = ALLOC(ApproxInfo,1);\n    if (info == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    info->max = pow(2.0,(double) numVars);\n    info->one = DD_ONE(dd);\n    info->zero = Cudd_Not(info->one);\n    info->size = Cudd_DagSize(node);\n    /* All the information gathered will be stored in a contiguous\n    ** piece of memory, which is allocated here. This can be done\n    ** efficiently because we have counted the number of nodes of the\n    ** BDD. info->index points to the next available entry in the array\n    ** that stores the per-node information. */\n    info->page = ALLOC(NodeData,info->size);\n    if (info->page == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(info);\n\treturn(NULL);\n    }\n    memset(info->page, 0, info->size * sizeof(NodeData)); /* clear all page */\n    info->table = cuddHashTableInit(dd,1,info->size);\n    if (info->table == NULL) {\n\tFREE(info->page);\n\tFREE(info);\n\treturn(NULL);\n    }\n    /* We visit the DAG in post-order DFS. Hence, the constant node is\n    ** in first position, and the root of the DAG is in last position. */\n\n    /* Info for the constant node: Initialize only fields different from 0. */\n    if (cuddHashTableGenericInsert(info->table, info->one, info->page) == 0) {\n\tFREE(info->page);\n\tcuddHashTableGenericQuit(info->table);\n\tFREE(info);\n\treturn(NULL);\n    }\n    info->page[0].mintermsP = info->max;\n    info->index = 1;\n\n    infoTop = gatherInfoAux(node,info,parity);\n    if (infoTop == NULL) {\n\tFREE(info->page);\n\tcuddHashTableGenericQuit(info->table);\n\tFREE(info);\n\treturn(NULL);\n    }\n    if (Cudd_IsComplement(node)) {\n\tinfo->minterms = infoTop->mintermsN;\n    } else {\n\tinfo->minterms = infoTop->mintermsP;\n    }\n\n    infoTop->functionRef = 1;\n    return(info);\n\n} /* end of gatherInfo */\n\n\n/**\n  @brief Counts the nodes that would be eliminated if a given node\n  were replaced by zero.\n\n  @details This procedure uses a queue passed by the caller for\n  efficiency: since the queue is left empty at the endof the search,\n  it can be reused as is by the next search.\n\n  @return the count (always striclty positive) if successful; 0\n  otherwise.\n\n  @sideeffect None\n\n  @see UAmarkNodes RAmarkNodes BAmarkNodes\n\n*/\nstatic int\ncomputeSavings(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * skip,\n  ApproxInfo * info,\n  DdLevelQueue * queue)\n{\n    NodeData *infoN;\n    LocalQueueItem *item;\n    DdNode *node;\n    int savings = 0;\n\n    node = Cudd_Regular(f);\n    if (node == NULL) return(0);\n    skip = Cudd_Regular(skip);\n    /* Insert the given node in the level queue. Its local reference\n    ** count is set equal to the function reference count so that the\n    ** search will continue from it when it is retrieved. */\n    item = (LocalQueueItem *)\n\tcuddLevelQueueFirst(queue,node,cuddI(dd,node->index));\n    if (item == NULL)\n\treturn(0);\n    infoN = (NodeData *) cuddHashTableGenericLookup(info->table, node);\n    item->localRef = infoN->functionRef;\n\n    /* Process the queue. */\n    while ((item = (LocalQueueItem *) queue->first) != NULL) {\n\tnode = item->node;\n\tif (node != skip) {\n            infoN = (NodeData *) cuddHashTableGenericLookup(info->table,node);\n            if (item->localRef == infoN->functionRef) {\n                /* This node is not shared. */\n                DdNode *nodeT, *nodeE;\n                savings++;\n                nodeT = cuddT(node);\n                if (!cuddIsConstant(nodeT)) {\n                    item = (LocalQueueItem *)\n                        cuddLevelQueueEnqueue(queue,nodeT,cuddI(dd,nodeT->index));\n                    if (item == NULL) return(0);\n                    item->localRef++;\n                }\n                nodeE = Cudd_Regular(cuddE(node));\n                if (!cuddIsConstant(nodeE)) {\n                    item = (LocalQueueItem *)\n                        cuddLevelQueueEnqueue(queue,nodeE,cuddI(dd,nodeE->index));\n                    if (item == NULL) return(0);\n                    item->localRef++;\n                }\n            }\n        }\n\tcuddLevelQueueDequeue(queue,cuddI(dd,node->index));\n    }\n\n#ifdef DD_DEBUG\n    /* At the end of a local search the queue should be empty. */\n    assert(queue->size == 0);\n#endif\n    return(savings);\n\n} /* end of computeSavings */\n\n\n/**\n  @brief Update function reference counts to account for replacement.\n\n  @return the number of nodes saved if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see UAmarkNodes RAmarkNodes BAmarkNodes\n\n*/\nstatic int\nupdateRefs(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * skip,\n  ApproxInfo * info,\n  DdLevelQueue * queue)\n{\n    NodeData *infoN;\n    LocalQueueItem *item;\n    DdNode *node;\n    int savings = 0;\n\n    node = Cudd_Regular(f);\n    /* Insert the given node in the level queue. Its function reference\n    ** count is set equal to 0 so that the search will continue from it\n    ** when it is retrieved. */\n    item = (LocalQueueItem *) cuddLevelQueueFirst(queue,node,cuddI(dd,node->index));\n    if (item == NULL)\n\treturn(0);\n    infoN = (NodeData *) cuddHashTableGenericLookup(info->table, node);\n    infoN->functionRef = 0;\n\n    if (skip != NULL) {\n\t/* Increase the function reference count of the node to be skipped\n\t** by 1 to account for the node pointing to it that will be created. */\n\tskip = Cudd_Regular(skip);\n\tinfoN = (NodeData *) cuddHashTableGenericLookup(info->table, skip);\n\tinfoN->functionRef++;\n    }\n\n    /* Process the queue. */\n    while ((item = (LocalQueueItem *) queue->first) != NULL) {\n\tnode = item->node;\n\tinfoN = (NodeData *) cuddHashTableGenericLookup(info->table,node);\n\tif (infoN->functionRef == 0) {\n\t    /* This node is not shared or to be be skipped. */\n            DdNode *nodeT, *nodeE;\n            savings++;\n            nodeT = cuddT(node);\n            if (!cuddIsConstant(nodeT)) {\n                item = (LocalQueueItem *)\n                    cuddLevelQueueEnqueue(queue,nodeT,cuddI(dd,nodeT->index));\n                if (item == NULL) return(0);\n                infoN = (NodeData *) cuddHashTableGenericLookup(info->table,nodeT);\n                infoN->functionRef--;\n            }\n            nodeE = Cudd_Regular(cuddE(node));\n            if (!cuddIsConstant(nodeE)) {\n                item = (LocalQueueItem *)\n                    cuddLevelQueueEnqueue(queue,nodeE,cuddI(dd,nodeE->index));\n                if (item == NULL) return(0);\n                infoN = (NodeData *) cuddHashTableGenericLookup(info->table,nodeE);\n                infoN->functionRef--;\n            }\n\t}\n\tcuddLevelQueueDequeue(queue,cuddI(dd,node->index));\n    }\n\n#ifdef DD_DEBUG\n    /* At the end of a local search the queue should be empty. */\n    assert(queue->size == 0);\n#endif\n    return(savings);\n\n} /* end of updateRefs */\n\n\n/**\n  @brief Marks nodes for replacement by zero.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddUnderApprox\n\n*/\nstatic int\nUAmarkNodes(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be analyzed */,\n  ApproxInfo * info /**< info on %BDD */,\n  int  threshold /**< when to stop approximating */,\n  int  safe /**< enforce safe approximation */,\n  double  quality /**< minimum improvement for accepted changes */)\n{\n    DdLevelQueue *queue;\n    DdLevelQueue *localQueue;\n    NodeData *infoN;\n    GlobalQueueItem *item;\n    DdNode *node;\n    double numOnset;\n    double impactP, impactN;\n    int savings;\n\n#if 0\n    (void) printf(\"initial size = %d initial minterms = %g\\n\",\n\t\t  info->size, info->minterms);\n#endif\n    queue = cuddLevelQueueInit(dd->size,sizeof(GlobalQueueItem),info->size,dd);\n    if (queue == NULL) {\n\treturn(0);\n    }\n    localQueue = cuddLevelQueueInit(dd->size,sizeof(LocalQueueItem),\n\t\t\t\t    dd->initSlots,dd);\n    if (localQueue == NULL) {\n\tcuddLevelQueueQuit(queue);\n\treturn(0);\n    }\n    node = Cudd_Regular(f);\n    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,node,cuddI(dd,node->index));\n    if (item == NULL) {\n\tcuddLevelQueueQuit(queue);\n\tcuddLevelQueueQuit(localQueue);\n\treturn(0);\n    }\n    if (Cudd_IsComplement(f)) {\n\titem->impactP = 0.0;\n\titem->impactN = 1.0;\n    } else {\n\titem->impactP = 1.0;\n\titem->impactN = 0.0;\n    }\n    while (queue->first != NULL) {\n\t/* If the size of the subset is below the threshold, quit. */\n\tif (info->size <= threshold)\n\t    break;\n\titem = (GlobalQueueItem *) queue->first;\n\tnode = item->node;\n\tnode = Cudd_Regular(node);\n\tinfoN = (NodeData *) cuddHashTableGenericLookup(info->table, node);\n\tif (safe && infoN->parity == 3) {\n\t    cuddLevelQueueDequeue(queue,cuddI(dd,node->index));\n\t    continue;\n\t}\n\timpactP = item->impactP;\n\timpactN = item->impactN;\n\tnumOnset = infoN->mintermsP * impactP + infoN->mintermsN * impactN;\n\tsavings = computeSavings(dd,node,NULL,info,localQueue);\n\tif (savings == 0) {\n\t    cuddLevelQueueQuit(queue);\n\t    cuddLevelQueueQuit(localQueue);\n\t    return(0);\n\t}\n\tcuddLevelQueueDequeue(queue,cuddI(dd,node->index));\n#if 0\n\t(void) printf(\"node %p: impact = %g/%g numOnset = %g savings %d\\n\",\n\t\t      node, impactP, impactN, numOnset, savings);\n#endif\n\tif ((1 - numOnset / info->minterms) >\n\t    quality * (1 - (double) savings / info->size)) {\n\t    infoN->replace = CUDD_TRUE;\n\t    info->size -= savings;\n\t    info->minterms -=numOnset;\n#if 0\n\t    (void) printf(\"replace: new size = %d new minterms = %g\\n\",\n\t\t\t  info->size, info->minterms);\n#endif\n\t    savings -= updateRefs(dd,node,NULL,info,localQueue);\n\t    assert(savings == 0);\n\t    continue;\n\t}\n\tif (!cuddIsConstant(cuddT(node))) {\n\t    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,cuddT(node),\n\t\t\t\t\t cuddI(dd,cuddT(node)->index));\n\t    item->impactP += impactP/2.0;\n\t    item->impactN += impactN/2.0;\n\t}\n\tif (!Cudd_IsConstantInt(cuddE(node))) {\n\t    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,Cudd_Regular(cuddE(node)),\n\t\t\t\t\t cuddI(dd,Cudd_Regular(cuddE(node))->index));\n\t    if (Cudd_IsComplement(cuddE(node))) {\n\t\titem->impactP += impactN/2.0;\n\t\titem->impactN += impactP/2.0;\n\t    } else {\n\t\titem->impactP += impactP/2.0;\n\t\titem->impactN += impactN/2.0;\n\t    }\n\t}\n    }\n\n    cuddLevelQueueQuit(queue);\n    cuddLevelQueueQuit(localQueue);\n    return(1);\n\n} /* end of UAmarkNodes */\n\n\n/**\n  @brief Builds the subset %BDD. \n\n  @details Based on the info table, replaces selected nodes by zero.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddUnderApprox\n\n*/\nstatic DdNode *\nUAbuildSubset(\n  DdManager * dd /**< %DD manager */,\n  DdNode * node /**< current node */,\n  ApproxInfo * info /**< node info */)\n{\n\n    DdNode *Nt, *Ne, *N, *t, *e, *r;\n    NodeData *infoN;\n\n    if (Cudd_IsConstantInt(node))\n\treturn(node);\n\n    N = Cudd_Regular(node);\n\n    if ((infoN = (NodeData *) cuddHashTableGenericLookup(info->table, N)) != NULL) {\n\tif (infoN->replace == CUDD_TRUE) {\n\t    return(info->zero);\n\t}\n\tif (N == node ) {\n\t    if (infoN->resultP != NULL) {\n\t\treturn(infoN->resultP);\n\t    }\n\t} else {\n\t    if (infoN->resultN != NULL) {\n\t\treturn(infoN->resultN);\n\t    }\n\t}\n    } else {\n\t(void) fprintf(dd->err,\n\t\t       \"Something is wrong, ought to be in info table\\n\");\n\tdd->errorCode = CUDD_INTERNAL_ERROR;\n\treturn(NULL);\n    }\n\n    Nt = Cudd_NotCond(cuddT(N), Cudd_IsComplement(node));\n    Ne = Cudd_NotCond(cuddE(N), Cudd_IsComplement(node));\n\n    t = UAbuildSubset(dd, Nt, info);\n    if (t == NULL) {\n\treturn(NULL);\n    }\n    cuddRef(t);\n\n    e = UAbuildSubset(dd, Ne, info);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(dd,t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (Cudd_IsComplement(t)) {\n\tt = Cudd_Not(t);\n\te = Cudd_Not(e);\n\tr = (t == e) ? t : cuddUniqueInter(dd, N->index, t, e);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(dd, e);\n\t    Cudd_RecursiveDeref(dd, t);\n\t    return(NULL);\n\t}\n\tr = Cudd_Not(r);\n    } else {\n\tr = (t == e) ? t : cuddUniqueInter(dd, N->index, t, e);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(dd, e);\n\t    Cudd_RecursiveDeref(dd, t);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    if (N == node) {\n\tinfoN->resultP = r;\n    } else {\n\tinfoN->resultN = r;\n    }\n\n    return(r);\n\n} /* end of UAbuildSubset */\n\n\n/**\n  @brief Marks nodes for remapping.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddRemapUnderApprox\n\n*/\nstatic int\nRAmarkNodes(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be analyzed */,\n  ApproxInfo * info /**< info on %BDD */,\n  int threshold /**< when to stop approximating */,\n  double quality /**< minimum improvement for accepted changes */)\n{\n    DdLevelQueue *queue;\n    DdLevelQueue *localQueue;\n    NodeData *infoN, *infoT, *infoE;\n    GlobalQueueItem *item;\n    DdNode *node, *T, *E;\n    DdNode *shared; /* grandchild shared by the two children of node */\n    double numOnset;\n    double impact, impactP, impactN;\n    double minterms;\n    int savings;\n    int replace;\n\n#if 0\n    (void) fprintf(dd->out,\"initial size = %d initial minterms = %g\\n\",\n\t\t  info->size, info->minterms);\n#endif\n    queue = cuddLevelQueueInit(dd->size,sizeof(GlobalQueueItem),info->size,dd);\n    if (queue == NULL) {\n\treturn(0);\n    }\n    localQueue = cuddLevelQueueInit(dd->size,sizeof(LocalQueueItem),\n\t\t\t\t    dd->initSlots,dd);\n    if (localQueue == NULL) {\n\tcuddLevelQueueQuit(queue);\n\treturn(0);\n    }\n    /* Enqueue regular pointer to root and initialize impact. */\n    node = Cudd_Regular(f);\n    item = (GlobalQueueItem *)\n\tcuddLevelQueueEnqueue(queue,node,cuddI(dd,node->index));\n    if (item == NULL) {\n\tcuddLevelQueueQuit(queue);\n\tcuddLevelQueueQuit(localQueue);\n\treturn(0);\n    }\n    if (Cudd_IsComplement(f)) {\n\titem->impactP = 0.0;\n\titem->impactN = 1.0;\n    } else {\n\titem->impactP = 1.0;\n\titem->impactN = 0.0;\n    }\n    /* The nodes retrieved here are guaranteed to be non-terminal.\n    ** The initial node is not terminal because constant nodes are\n    ** dealt with in the calling procedure. Subsequent nodes are inserted\n    ** only if they are not terminal. */\n    while ((item = (GlobalQueueItem *) queue->first) != NULL) {\n\t/* If the size of the subset is below the threshold, quit. */\n\tif (info->size <= threshold)\n\t    break;\n\tnode = item->node;\n#ifdef DD_DEBUG\n\tassert(item->impactP >= 0 && item->impactP <= 1.0);\n\tassert(item->impactN >= 0 && item->impactN <= 1.0);\n\tassert(!Cudd_IsComplement(node));\n\tassert(!Cudd_IsConstantInt(node));\n#endif\n\tif ((infoN = (NodeData *) cuddHashTableGenericLookup(info->table, node)) == NULL) {\n\t    cuddLevelQueueQuit(queue);\n\t    cuddLevelQueueQuit(localQueue);\n\t    return(0);\n\t}\n#ifdef DD_DEBUG\n\tassert(infoN->parity >= 1 && infoN->parity <= 3);\n#endif\n\tif (infoN->parity == 3) {\n\t    /* This node can be reached through paths of different parity.\n\t    ** It is not safe to replace it, because remapping will give\n\t    ** an incorrect result, while replacement by 0 may cause node\n\t    ** splitting. */\n\t    cuddLevelQueueDequeue(queue,cuddI(dd,node->index));\n\t    continue;\n\t}\n\tT = cuddT(node);\n\tE = cuddE(node);\n\tshared = NULL;\n\timpactP = item->impactP;\n\timpactN = item->impactN;\n\tif (Cudd_bddLeq(dd,T,E)) {\n\t    /* Here we know that E is regular. */\n#ifdef DD_DEBUG\n\t    assert(!Cudd_IsComplement(E));\n#endif\n\t    infoT = (NodeData *) cuddHashTableGenericLookup(info->table, T);\n\t    infoE = (NodeData *) cuddHashTableGenericLookup(info->table, E);\n\t    if (infoN->parity == 1) {\n\t\timpact = impactP;\n\t\tminterms = infoE->mintermsP/2.0 - infoT->mintermsP/2.0;\n\t\tif (infoE->functionRef == 1 && !cuddIsConstant(E)) {\n\t\t    savings = 1 + computeSavings(dd,E,NULL,info,localQueue);\n\t\t    if (savings == 1) {\n\t\t\tcuddLevelQueueQuit(queue);\n\t\t\tcuddLevelQueueQuit(localQueue);\n\t\t\treturn(0);\n\t\t    }\n\t\t} else {\n\t\t    savings = 1;\n\t\t}\n\t\treplace = REPLACE_E;\n\t    } else {\n#ifdef DD_DEBUG\n\t\tassert(infoN->parity == 2);\n#endif\n\t\timpact = impactN;\n\t\tminterms = infoT->mintermsN/2.0 - infoE->mintermsN/2.0;\n\t\tif (infoT->functionRef == 1 && !cuddIsConstant(T)) {\n\t\t    savings = 1 + computeSavings(dd,T,NULL,info,localQueue);\n\t\t    if (savings == 1) {\n\t\t\tcuddLevelQueueQuit(queue);\n\t\t\tcuddLevelQueueQuit(localQueue);\n\t\t\treturn(0);\n\t\t    }\n\t\t} else {\n\t\t    savings = 1;\n\t\t}\n\t\treplace = REPLACE_T;\n\t    }\n\t    numOnset = impact * minterms;\n\t} else if (Cudd_bddLeq(dd,E,T)) {\n\t    /* Here E may be complemented. */\n\t    DdNode *Ereg = Cudd_Regular(E);\n\t    infoT = (NodeData *) cuddHashTableGenericLookup(info->table, T);\n\t    infoE = (NodeData *) cuddHashTableGenericLookup(info->table, Ereg);\n\t    if (infoN->parity == 1) {\n\t\timpact = impactP;\n\t\tminterms = infoT->mintermsP/2.0 -\n\t\t    ((E == Ereg) ? infoE->mintermsP : infoE->mintermsN)/2.0;\n\t\tif (infoT->functionRef == 1 && !cuddIsConstant(T)) {\n\t\t    savings = 1 + computeSavings(dd,T,NULL,info,localQueue);\n\t\t    if (savings == 1) {\n\t\t\tcuddLevelQueueQuit(queue);\n\t\t\tcuddLevelQueueQuit(localQueue);\n\t\t\treturn(0);\n\t\t    }\n\t\t} else {\n\t\t    savings = 1;\n\t\t}\n\t\treplace = REPLACE_T;\n\t    } else {\n#ifdef DD_DEBUG\n\t\tassert(infoN->parity == 2);\n#endif\n\t\timpact = impactN;\n\t\tminterms = ((E == Ereg) ? infoE->mintermsN :\n\t\t\t    infoE->mintermsP)/2.0 - infoT->mintermsN/2.0;\n\t\tif (infoE->functionRef == 1 && !cuddIsConstant(Ereg)) {\n\t\t    savings = 1 + computeSavings(dd,E,NULL,info,localQueue);\n\t\t    if (savings == 1) {\n\t\t\tcuddLevelQueueQuit(queue);\n\t\t\tcuddLevelQueueQuit(localQueue);\n\t\t\treturn(0);\n\t\t    }\n\t\t} else {\n\t\t    savings = 1;\n\t\t}\n\t\treplace = REPLACE_E;\n\t    }\n\t    numOnset = impact * minterms;\n\t} else {\n\t    DdNode *Ereg = Cudd_Regular(E);\n\t    DdNode *TT = cuddT(T);\n\t    DdNode *ET = Cudd_NotCond(cuddT(Ereg), Cudd_IsComplement(E));\n\t    if (T->index == Ereg->index && TT == ET) {\n\t\tshared = TT;\n\t\treplace = REPLACE_TT;\n\t    } else {\n\t\tDdNode *TE = cuddE(T);\n\t\tDdNode *EE = Cudd_NotCond(cuddE(Ereg), Cudd_IsComplement(E));\n\t\tif (T->index == Ereg->index && TE == EE) {\n\t\t    shared = TE;\n\t\t    replace = REPLACE_TE;\n\t\t} else {\n\t\t    replace = REPLACE_N;\n\t\t}\n\t    }\n\t    numOnset = infoN->mintermsP * impactP + infoN->mintermsN * impactN;\n\t    savings = computeSavings(dd,node,shared,info,localQueue);\n\t    if (shared != NULL) {\n\t\tNodeData *infoS;\n\t\tinfoS = (NodeData *) cuddHashTableGenericLookup(info->table, Cudd_Regular(shared));\n\t\tif (Cudd_IsComplement(shared)) {\n\t\t    numOnset -= (infoS->mintermsN * impactP +\n\t\t\tinfoS->mintermsP * impactN)/2.0;\n\t\t} else {\n\t\t    numOnset -= (infoS->mintermsP * impactP +\n\t\t\tinfoS->mintermsN * impactN)/2.0;\n\t\t}\n\t\tsavings--;\n\t    }\n\t}\n\n\tcuddLevelQueueDequeue(queue,cuddI(dd,node->index));\n#if 0\n\tif (replace == REPLACE_T || replace == REPLACE_E)\n\t    (void) printf(\"node %p: impact = %g numOnset = %g savings %d\\n\",\n\t\t\t  node, impact, numOnset, savings);\n\telse\n\t    (void) printf(\"node %p: impact = %g/%g numOnset = %g savings %d\\n\",\n\t\t\t  node, impactP, impactN, numOnset, savings);\n#endif\n\tif ((1 - numOnset / info->minterms) >\n\t    quality * (1 - (double) savings / info->size)) {\n\t    infoN->replace = (char) replace;\n\t    info->size -= savings;\n\t    info->minterms -=numOnset;\n#if 0\n\t    (void) printf(\"remap(%d): new size = %d new minterms = %g\\n\",\n\t\t\t  replace, info->size, info->minterms);\n#endif\n\t    if (replace == REPLACE_N) {\n\t\tsavings -= updateRefs(dd,node,NULL,info,localQueue);\n\t    } else if (replace == REPLACE_T) {\n\t\tsavings -= updateRefs(dd,node,E,info,localQueue);\n\t    } else if (replace == REPLACE_E) {\n\t\tsavings -= updateRefs(dd,node,T,info,localQueue);\n\t    } else {\n#ifdef DD_DEBUG\n\t\tassert(replace == REPLACE_TT || replace == REPLACE_TE);\n#endif\n\t\tsavings -= updateRefs(dd,node,shared,info,localQueue) - 1;\n\t    }\n\t    assert(savings == 0);\n\t} else {\n\t    replace = NOTHING;\n\t}\n\tif (replace == REPLACE_N) continue;\n\tif ((replace == REPLACE_E || replace == NOTHING) &&\n\t    !cuddIsConstant(cuddT(node))) {\n\t    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,cuddT(node),\n\t\t\t\t\t cuddI(dd,cuddT(node)->index));\n\t    if (replace == REPLACE_E) {\n\t\titem->impactP += impactP;\n\t\titem->impactN += impactN;\n\t    } else {\n\t\titem->impactP += impactP/2.0;\n\t\titem->impactN += impactN/2.0;\n\t    }\n\t}\n\tif ((replace == REPLACE_T || replace == NOTHING) &&\n\t    !Cudd_IsConstantInt(cuddE(node))) {\n\t    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,Cudd_Regular(cuddE(node)),\n\t\t\t\t\t cuddI(dd,Cudd_Regular(cuddE(node))->index));\n\t    if (Cudd_IsComplement(cuddE(node))) {\n\t\tif (replace == REPLACE_T) {\n\t\t    item->impactP += impactN;\n\t\t    item->impactN += impactP;\n\t\t} else {\n\t\t    item->impactP += impactN/2.0;\n\t\t    item->impactN += impactP/2.0;\n\t\t}\n\t    } else {\n\t\tif (replace == REPLACE_T) {\n\t\t    item->impactP += impactP;\n\t\t    item->impactN += impactN;\n\t\t} else {\n\t\t    item->impactP += impactP/2.0;\n\t\t    item->impactN += impactN/2.0;\n\t\t}\n\t    }\n\t}\n\tif ((replace == REPLACE_TT || replace == REPLACE_TE) &&\n\t    !Cudd_IsConstantInt(shared)) {\n\t    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,Cudd_Regular(shared),\n\t\t\t\t\t cuddI(dd,Cudd_Regular(shared)->index));\n\t    if (Cudd_IsComplement(shared)) {\n\t        item->impactP += impactN;\n\t\titem->impactN += impactP;\n\t    } else {\n\t        item->impactP += impactP;\n\t\titem->impactN += impactN;\n\t    }\n\t}\n    }\n\n    cuddLevelQueueQuit(queue);\n    cuddLevelQueueQuit(localQueue);\n    return(1);\n\n} /* end of RAmarkNodes */\n\n\n/**\n  @brief Marks nodes for remapping.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddBiasedUnderApprox\n\n*/\nstatic int\nBAmarkNodes(\n  DdManager *dd /**< manager */,\n  DdNode *f /**< function to be analyzed */,\n  ApproxInfo *info /**< info on %BDD */,\n  int threshold /**< when to stop approximating */,\n  double quality1 /**< minimum improvement for accepted changes when b=1 */,\n  double quality0 /**< minimum improvement for accepted changes when b=0 */)\n{\n    DdLevelQueue *queue;\n    DdLevelQueue *localQueue;\n    NodeData *infoN, *infoT, *infoE;\n    GlobalQueueItem *item;\n    DdNode *node, *T, *E;\n    DdNode *shared; /* grandchild shared by the two children of node */\n    double numOnset;\n    double impact, impactP, impactN;\n    double minterms;\n    double quality;\n    int savings;\n    int replace;\n\n#if 0\n    (void) fprintf(dd->out,\"initial size = %d initial minterms = %g\\n\",\n\t\t  info->size, info->minterms);\n#endif\n    queue = cuddLevelQueueInit(dd->size,sizeof(GlobalQueueItem),info->size,dd);\n    if (queue == NULL) {\n\treturn(0);\n    }\n    localQueue = cuddLevelQueueInit(dd->size,sizeof(LocalQueueItem),\n\t\t\t\t    dd->initSlots,dd);\n    if (localQueue == NULL) {\n\tcuddLevelQueueQuit(queue);\n\treturn(0);\n    }\n    /* Enqueue regular pointer to root and initialize impact. */\n    node = Cudd_Regular(f);\n    item = (GlobalQueueItem *)\n\tcuddLevelQueueEnqueue(queue,node,cuddI(dd,node->index));\n    if (item == NULL) {\n\tcuddLevelQueueQuit(queue);\n\tcuddLevelQueueQuit(localQueue);\n\treturn(0);\n    }\n    if (Cudd_IsComplement(f)) {\n\titem->impactP = 0.0;\n\titem->impactN = 1.0;\n    } else {\n\titem->impactP = 1.0;\n\titem->impactN = 0.0;\n    }\n    /* The nodes retrieved here are guaranteed to be non-terminal.\n    ** The initial node is not terminal because constant nodes are\n    ** dealt with in the calling procedure. Subsequent nodes are inserted\n    ** only if they are not terminal. */\n    while (queue->first != NULL) {\n\t/* If the size of the subset is below the threshold, quit. */\n\tif (info->size <= threshold)\n\t    break;\n\titem = (GlobalQueueItem *) queue->first;\n\tnode = item->node;\n#ifdef DD_DEBUG\n\tassert(item->impactP >= 0 && item->impactP <= 1.0);\n\tassert(item->impactN >= 0 && item->impactN <= 1.0);\n\tassert(!Cudd_IsComplement(node));\n\tassert(!Cudd_IsConstantInt(node));\n#endif\n\tif ((infoN = (NodeData *) cuddHashTableGenericLookup(info->table, node)) == NULL) {\n\t    cuddLevelQueueQuit(queue);\n\t    cuddLevelQueueQuit(localQueue);\n\t    return(0);\n\t}\n\tquality = infoN->care ? quality1 : quality0;\n#ifdef DD_DEBUG\n\tassert(infoN->parity >= 1 && infoN->parity <= 3);\n#endif\n\tif (infoN->parity == 3) {\n\t    /* This node can be reached through paths of different parity.\n\t    ** It is not safe to replace it, because remapping will give\n\t    ** an incorrect result, while replacement by 0 may cause node\n\t    ** splitting. */\n\t    cuddLevelQueueDequeue(queue,cuddI(dd,node->index));\n\t    continue;\n\t}\n\tT = cuddT(node);\n\tE = cuddE(node);\n\tshared = NULL;\n\timpactP = item->impactP;\n\timpactN = item->impactN;\n\tif (Cudd_bddLeq(dd,T,E)) {\n\t    /* Here we know that E is regular. */\n#ifdef DD_DEBUG\n\t    assert(!Cudd_IsComplement(E));\n#endif\n\t    infoT = (NodeData *) cuddHashTableGenericLookup(info->table, T);\n\t    infoE = (NodeData *) cuddHashTableGenericLookup(info->table, E);\n\t    if (infoN->parity == 1) {\n\t\timpact = impactP;\n\t\tminterms = infoE->mintermsP/2.0 - infoT->mintermsP/2.0;\n\t\tif (infoE->functionRef == 1 && !Cudd_IsConstantInt(E)) {\n\t\t    savings = 1 + computeSavings(dd,E,NULL,info,localQueue);\n\t\t    if (savings == 1) {\n\t\t\tcuddLevelQueueQuit(queue);\n\t\t\tcuddLevelQueueQuit(localQueue);\n\t\t\treturn(0);\n\t\t    }\n\t\t} else {\n\t\t    savings = 1;\n\t\t}\n\t\treplace = REPLACE_E;\n\t    } else {\n#ifdef DD_DEBUG\n\t\tassert(infoN->parity == 2);\n#endif\n\t\timpact = impactN;\n\t\tminterms = infoT->mintermsN/2.0 - infoE->mintermsN/2.0;\n\t\tif (infoT->functionRef == 1 && !Cudd_IsConstantInt(T)) {\n\t\t    savings = 1 + computeSavings(dd,T,NULL,info,localQueue);\n\t\t    if (savings == 1) {\n\t\t\tcuddLevelQueueQuit(queue);\n\t\t\tcuddLevelQueueQuit(localQueue);\n\t\t\treturn(0);\n\t\t    }\n\t\t} else {\n\t\t    savings = 1;\n\t\t}\n\t\treplace = REPLACE_T;\n\t    }\n\t    numOnset = impact * minterms;\n\t} else if (Cudd_bddLeq(dd,E,T)) {\n\t    /* Here E may be complemented. */\n\t    DdNode *Ereg = Cudd_Regular(E);\n\t    infoT = (NodeData *) cuddHashTableGenericLookup(info->table, T);\n\t    infoE = (NodeData *) cuddHashTableGenericLookup(info->table, Ereg);\n\t    if (infoN->parity == 1) {\n\t\timpact = impactP;\n\t\tminterms = infoT->mintermsP/2.0 -\n\t\t    ((E == Ereg) ? infoE->mintermsP : infoE->mintermsN)/2.0;\n\t\tif (infoT->functionRef == 1 && !Cudd_IsConstantInt(T)) {\n\t\t    savings = 1 + computeSavings(dd,T,NULL,info,localQueue);\n\t\t    if (savings == 1) {\n\t\t\tcuddLevelQueueQuit(queue);\n\t\t\tcuddLevelQueueQuit(localQueue);\n\t\t\treturn(0);\n\t\t    }\n\t\t} else {\n\t\t    savings = 1;\n\t\t}\n\t\treplace = REPLACE_T;\n\t    } else {\n#ifdef DD_DEBUG\n\t\tassert(infoN->parity == 2);\n#endif\n\t\timpact = impactN;\n\t\tminterms = ((E == Ereg) ? infoE->mintermsN :\n\t\t\t    infoE->mintermsP)/2.0 - infoT->mintermsN/2.0;\n\t\tif (infoE->functionRef == 1 && !Cudd_IsConstantInt(E)) {\n\t\t    savings = 1 + computeSavings(dd,E,NULL,info,localQueue);\n\t\t    if (savings == 1) {\n\t\t\tcuddLevelQueueQuit(queue);\n\t\t\tcuddLevelQueueQuit(localQueue);\n\t\t\treturn(0);\n\t\t    }\n\t\t} else {\n\t\t    savings = 1;\n\t\t}\n\t\treplace = REPLACE_E;\n\t    }\n\t    numOnset = impact * minterms;\n\t} else {\n\t    DdNode *Ereg = Cudd_Regular(E);\n\t    DdNode *TT = cuddT(T);\n\t    DdNode *ET = Cudd_NotCond(cuddT(Ereg), Cudd_IsComplement(E));\n\t    if (T->index == Ereg->index && TT == ET) {\n\t\tshared = TT;\n\t\treplace = REPLACE_TT;\n\t    } else {\n\t\tDdNode *TE = cuddE(T);\n\t\tDdNode *EE = Cudd_NotCond(cuddE(Ereg), Cudd_IsComplement(E));\n\t\tif (T->index == Ereg->index && TE == EE) {\n\t\t    shared = TE;\n\t\t    replace = REPLACE_TE;\n\t\t} else {\n\t\t    replace = REPLACE_N;\n\t\t}\n\t    }\n\t    numOnset = infoN->mintermsP * impactP + infoN->mintermsN * impactN;\n\t    savings = computeSavings(dd,node,shared,info,localQueue);\n\t    if (shared != NULL) {\n\t\tNodeData *infoS;\n\t\tinfoS = (NodeData *) cuddHashTableGenericLookup(info->table, Cudd_Regular(shared));\n\t\tif (Cudd_IsComplement(shared)) {\n\t\t    numOnset -= (infoS->mintermsN * impactP +\n\t\t\tinfoS->mintermsP * impactN)/2.0;\n\t\t} else {\n\t\t    numOnset -= (infoS->mintermsP * impactP +\n\t\t\tinfoS->mintermsN * impactN)/2.0;\n\t\t}\n\t\tsavings--;\n\t    }\n\t}\n\n\tcuddLevelQueueDequeue(queue,cuddI(dd,node->index));\n#if 0\n\tif (replace == REPLACE_T || replace == REPLACE_E)\n\t    (void) printf(\"node %p: impact = %g numOnset = %g savings %d\\n\",\n\t\t\t  node, impact, numOnset, savings);\n\telse\n\t    (void) printf(\"node %p: impact = %g/%g numOnset = %g savings %d\\n\",\n\t\t\t  node, impactP, impactN, numOnset, savings);\n#endif\n\tif ((1 - numOnset / info->minterms) >\n\t    quality * (1 - (double) savings / info->size)) {\n\t    infoN->replace = (char) replace;\n\t    info->size -= savings;\n\t    info->minterms -=numOnset;\n#if 0\n\t    (void) printf(\"remap(%d): new size = %d new minterms = %g\\n\",\n\t\t\t  replace, info->size, info->minterms);\n#endif\n\t    if (replace == REPLACE_N) {\n\t\tsavings -= updateRefs(dd,node,NULL,info,localQueue);\n\t    } else if (replace == REPLACE_T) {\n\t\tsavings -= updateRefs(dd,node,E,info,localQueue);\n\t    } else if (replace == REPLACE_E) {\n\t\tsavings -= updateRefs(dd,node,T,info,localQueue);\n\t    } else {\n#ifdef DD_DEBUG\n\t\tassert(replace == REPLACE_TT || replace == REPLACE_TE);\n#endif\n\t\tsavings -= updateRefs(dd,node,shared,info,localQueue) - 1;\n\t    }\n\t    assert(savings == 0);\n\t} else {\n\t    replace = NOTHING;\n\t}\n\tif (replace == REPLACE_N) continue;\n\tif ((replace == REPLACE_E || replace == NOTHING) &&\n\t    !cuddIsConstant(cuddT(node))) {\n\t    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,cuddT(node),\n\t\t\t\t\t cuddI(dd,cuddT(node)->index));\n\t    if (replace == REPLACE_E) {\n\t\titem->impactP += impactP;\n\t\titem->impactN += impactN;\n\t    } else {\n\t\titem->impactP += impactP/2.0;\n\t\titem->impactN += impactN/2.0;\n\t    }\n\t}\n\tif ((replace == REPLACE_T || replace == NOTHING) &&\n\t    !Cudd_IsConstantInt(cuddE(node))) {\n\t    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,Cudd_Regular(cuddE(node)),\n\t\t\t\t\t cuddI(dd,Cudd_Regular(cuddE(node))->index));\n\t    if (Cudd_IsComplement(cuddE(node))) {\n\t\tif (replace == REPLACE_T) {\n\t\t    item->impactP += impactN;\n\t\t    item->impactN += impactP;\n\t\t} else {\n\t\t    item->impactP += impactN/2.0;\n\t\t    item->impactN += impactP/2.0;\n\t\t}\n\t    } else {\n\t\tif (replace == REPLACE_T) {\n\t\t    item->impactP += impactP;\n\t\t    item->impactN += impactN;\n\t\t} else {\n\t\t    item->impactP += impactP/2.0;\n\t\t    item->impactN += impactN/2.0;\n\t\t}\n\t    }\n\t}\n\tif ((replace == REPLACE_TT || replace == REPLACE_TE) &&\n\t    !Cudd_IsConstantInt(shared)) {\n\t    item = (GlobalQueueItem *) cuddLevelQueueEnqueue(queue,Cudd_Regular(shared),\n\t\t\t\t\t cuddI(dd,Cudd_Regular(shared)->index));\n\t    if (Cudd_IsComplement(shared)) {\n\t\tif (replace == REPLACE_T) {\n\t\t    item->impactP += impactN;\n\t\t    item->impactN += impactP;\n\t\t} else {\n\t\t    item->impactP += impactN/2.0;\n\t\t    item->impactN += impactP/2.0;\n\t\t}\n\t    } else {\n\t\tif (replace == REPLACE_T) {\n\t\t    item->impactP += impactP;\n\t\t    item->impactN += impactN;\n\t\t} else {\n\t\t    item->impactP += impactP/2.0;\n\t\t    item->impactN += impactN/2.0;\n\t\t}\n\t    }\n\t}\n    }\n\n    cuddLevelQueueQuit(queue);\n    cuddLevelQueueQuit(localQueue);\n    return(1);\n\n} /* end of BAmarkNodes */\n\n\n/**\n  @brief Builds the subset %BDD for cuddRemapUnderApprox.\n\n  @details Based on the info table, performs remapping or replacement\n  at selected nodes.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddRemapUnderApprox\n\n*/\nstatic DdNode *\nRAbuildSubset(\n  DdManager * dd /**< %DD manager */,\n  DdNode * node /**< current node */,\n  ApproxInfo * info /**< node info */)\n{\n    DdNode *Nt, *Ne, *N, *t, *e, *r;\n    NodeData *infoN;\n\n    if (Cudd_IsConstantInt(node))\n\treturn(node);\n\n    N = Cudd_Regular(node);\n\n    Nt = Cudd_NotCond(cuddT(N), Cudd_IsComplement(node));\n    Ne = Cudd_NotCond(cuddE(N), Cudd_IsComplement(node));\n\n    if ((infoN = (NodeData *) cuddHashTableGenericLookup(info->table, N)) != NULL) {\n\tif (N == node ) {\n\t    if (infoN->resultP != NULL) {\n\t\treturn(infoN->resultP);\n\t    }\n\t} else {\n\t    if (infoN->resultN != NULL) {\n\t\treturn(infoN->resultN);\n\t    }\n\t}\n\tif (infoN->replace == REPLACE_T) {\n\t    r = RAbuildSubset(dd, Ne, info);\n\t    return(r);\n\t} else if (infoN->replace == REPLACE_E) {\n\t    r = RAbuildSubset(dd, Nt, info);\n\t    return(r);\n\t} else if (infoN->replace == REPLACE_N) {\n\t    return(info->zero);\n\t} else if (infoN->replace == REPLACE_TT) {\n\t    DdNode *Ntt = Cudd_NotCond(cuddT(cuddT(N)),\n\t\t\t\t       Cudd_IsComplement(node));\n\t    int index = cuddT(N)->index;\n\t    e = info->zero;\n\t    t = RAbuildSubset(dd, Ntt, info);\n\t    if (t == NULL) {\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(t);\n\t    if (Cudd_IsComplement(t)) {\n\t\tt = Cudd_Not(t);\n\t\te = Cudd_Not(e);\n\t\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\t\tif (r == NULL) {\n\t\t    Cudd_RecursiveDeref(dd, t);\n\t\t    return(NULL);\n\t\t}\n\t\tr = Cudd_Not(r);\n\t    } else {\n\t\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\t\tif (r == NULL) {\n\t\t    Cudd_RecursiveDeref(dd, t);\n\t\t    return(NULL);\n\t\t}\n\t    }\n\t    cuddDeref(t);\n\t    return(r);\n\t} else if (infoN->replace == REPLACE_TE) {\n\t    DdNode *Nte = Cudd_NotCond(cuddE(cuddT(N)),\n\t\t\t\t       Cudd_IsComplement(node));\n\t    unsigned int index = cuddT(N)->index;\n\t    t = info->one;\n\t    e = RAbuildSubset(dd, Nte, info);\n\t    if (e == NULL) {\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(e);\n\t    e = Cudd_Not(e);\n\t    r = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\t    if (r == NULL) {\n\t\tCudd_RecursiveDeref(dd, e);\n\t\treturn(NULL);\n\t    }\n\t    r =Cudd_Not(r);\n\t    cuddDeref(e);\n\t    return(r);\n\t}\n    } else {\n\t(void) fprintf(dd->err,\n\t\t       \"Something is wrong, ought to be in info table\\n\");\n\tdd->errorCode = CUDD_INTERNAL_ERROR;\n\treturn(NULL);\n    }\n\n    t = RAbuildSubset(dd, Nt, info);\n    if (t == NULL) {\n\treturn(NULL);\n    }\n    cuddRef(t);\n\n    e = RAbuildSubset(dd, Ne, info);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(dd,t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (Cudd_IsComplement(t)) {\n\tt = Cudd_Not(t);\n\te = Cudd_Not(e);\n\tr = (t == e) ? t : cuddUniqueInter(dd, N->index, t, e);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(dd, e);\n\t    Cudd_RecursiveDeref(dd, t);\n\t    return(NULL);\n\t}\n\tr = Cudd_Not(r);\n    } else {\n\tr = (t == e) ? t : cuddUniqueInter(dd, N->index, t, e);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(dd, e);\n\t    Cudd_RecursiveDeref(dd, t);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    if (N == node) {\n\tinfoN->resultP = r;\n    } else {\n\tinfoN->resultN = r;\n    }\n\n    return(r);\n\n} /* end of RAbuildSubset */\n\n\n/**\n  @brief Finds don't care nodes by traversing f and b in parallel.\n\n  @return the care status of the visited f node if successful;\n  CARE_ERROR otherwise.\n\n  @sideeffect None\n\n  @see cuddBiasedUnderApprox\n\n*/\nstatic int\nBAapplyBias(\n  DdManager *dd,\n  DdNode *f,\n  DdNode *b,\n  ApproxInfo *info,\n  DdHashTable *cache)\n{\n    DdNode *one, *zero, *res;\n    DdNode *Ft, *Fe, *B, *Bt, *Be;\n    int topf, topb;\n    NodeData *infoF;\n    int careT, careE;\n\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    if ((infoF = (NodeData *) cuddHashTableGenericLookup(info->table, f)) == NULL)\n\treturn(CARE_ERROR);\n    if (f == one) return(TOTAL_CARE);\n    if (b == zero) return(infoF->care);\n    if (infoF->care == TOTAL_CARE) return(TOTAL_CARE);\n\n    if ((f->ref != 1 || Cudd_Regular(b)->ref != 1) &&\n\t(res = cuddHashTableLookup2(cache,f,b)) != NULL) {\n\tif (res->ref == 0) {\n\t    cache->manager->dead++;\n\t    cache->manager->constants.dead++;\n\t}\n\treturn(infoF->care);\n    }\n\n    topf = dd->perm[f->index];\n    B = Cudd_Regular(b);\n    topb = cuddI(dd,B->index);\n    if (topf <= topb) {\n\tFt = cuddT(f); Fe = cuddE(f);\n    } else {\n\tFt = Fe = f;\n    }\n    if (topb <= topf) {\n\t/* We know that b is not constant because f is not. */\n\tBt = cuddT(B); Be = cuddE(B);\n\tif (Cudd_IsComplement(b)) {\n\t    Bt = Cudd_Not(Bt);\n\t    Be = Cudd_Not(Be);\n\t}\n    } else {\n\tBt = Be = b;\n    }\n\n    careT = BAapplyBias(dd, Ft, Bt, info, cache);\n    if (careT == CARE_ERROR)\n\treturn(CARE_ERROR);\n    careE = BAapplyBias(dd, Cudd_Regular(Fe), Be, info, cache);\n    if (careE == CARE_ERROR)\n\treturn(CARE_ERROR);\n    if (careT == TOTAL_CARE && careE == TOTAL_CARE) {\n\tinfoF->care = TOTAL_CARE;\n    } else {\n\tinfoF->care = CARE;\n    }\n\n    if (f->ref != 1 || Cudd_Regular(b)->ref != 1) {\n\tptrint fanout = (ptrint) f->ref * Cudd_Regular(b)->ref;\n\tcuddSatDec(fanout);\n\tif (!cuddHashTableInsert2(cache,f,b,one,fanout)) {\n\t    return(CARE_ERROR);\n\t}\n    }\n    return(infoF->care);\n\n} /* end of BAapplyBias */\n"
  },
  {
    "path": "cudd/cudd/cuddBddAbs.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Quantification functions for BDDs.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int bddCheckPositiveCube (DdManager *manager, DdNode *cube);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Existentially abstracts all the variables in cube from f.\n\n  @return the abstracted %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddUnivAbstract Cudd_addExistAbstract\n\n*/\nDdNode *\nCudd_bddExistAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode *res;\n\n    if (bddCheckPositiveCube(manager, cube) == 0) {\n        (void) fprintf(manager->err,\n\t\t       \"Error: Can only abstract positive cubes\\n\");\n\tmanager->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddBddExistAbstractRecur(manager, f, cube);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_bddExistAbstract */\n\n\n/**\n  @brief Existentially abstracts all the variables in cube from f.\n\n  @return the abstracted %BDD if successful; NULL if the intermediate\n  result blows up or more new nodes than <code>limit</code> are\n  required.\n\n  @sideeffect None\n\n  @see Cudd_bddExistAbstract\n\n*/\nDdNode *\nCudd_bddExistAbstractLimit(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube,\n  unsigned int limit)\n{\n    DdNode *res;\n    unsigned int saveLimit = manager->maxLive;\n\n    if (bddCheckPositiveCube(manager, cube) == 0) {\n        (void) fprintf(manager->err,\n\t\t       \"Error: Can only abstract positive cubes\\n\");\n\tmanager->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n\n    manager->maxLive = (manager->keys - manager->dead) + \n        (manager->keysZ - manager->deadZ) + limit;\n    do {\n\tmanager->reordered = 0;\n\tres = cuddBddExistAbstractRecur(manager, f, cube);\n    } while (manager->reordered == 1);\n    manager->maxLive = saveLimit;\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_bddExistAbstractLimit */\n\n\n/**\n  @brief Takes the exclusive OR of two BDDs and simultaneously abstracts the\n  variables in cube.\n\n  @details The variables are existentially abstracted.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddUnivAbstract Cudd_bddExistAbstract Cudd_bddAndAbstract\n\n*/\nDdNode *\nCudd_bddXorExistAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g,\n  DdNode * cube)\n{\n    DdNode *res;\n\n    if (bddCheckPositiveCube(manager, cube) == 0) {\n        (void) fprintf(manager->err,\n\t\t       \"Error: Can only abstract positive cubes\\n\");\n\tmanager->errorCode = CUDD_INVALID_ARG;\n        return(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddBddXorExistAbstractRecur(manager, f, g, cube);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_bddXorExistAbstract */\n\n\n/**\n  @brief Universally abstracts all the variables in cube from f.\n\n  @return the abstracted %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddExistAbstract Cudd_addUnivAbstract\n\n*/\nDdNode *\nCudd_bddUnivAbstract(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode\t*res;\n\n    if (bddCheckPositiveCube(manager, cube) == 0) {\n\t(void) fprintf(manager->err,\n\t\t       \"Error: Can only abstract positive cubes\\n\");\n\tmanager->errorCode = CUDD_INVALID_ARG;\n\treturn(NULL);\n    }\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddBddExistAbstractRecur(manager, Cudd_Not(f), cube);\n    } while (manager->reordered == 1);\n    if (res != NULL) res = Cudd_Not(res);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_bddUnivAbstract */\n\n\n/**\n  @brief Computes the boolean difference of f with respect to x.\n\n  @details Computes the boolean difference of f with respect to the\n  variable with index x.\n\n  @return the %BDD of the boolean difference if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_bddBooleanDiff(\n  DdManager * manager,\n  DdNode * f,\n  int  x)\n{\n    DdNode *res, *var;\n\n    /* If the variable is not currently in the manager, f cannot\n    ** depend on it.\n    */\n    if (x >= manager->size) return(Cudd_Not(DD_ONE(manager)));\n    var = manager->vars[x];\n\n    do {\n\tmanager->reordered = 0;\n\tres = cuddBddBooleanDiffRecur(manager, Cudd_Regular(f), var);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_bddBooleanDiff */\n\n\n/**\n  @brief Checks whether a variable is dependent on others in a\n  function.\n\n  @details No new nodes are created.\n\n  @return 1 if the variable is dependent; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nCudd_bddVarIsDependent(\n  DdManager *dd,\t\t/**< manager */\n  DdNode *f,\t\t\t/**< function */\n  DdNode *var\t\t\t/**< variable */)\n{\n    DdNode *F, *res, *zero, *ft, *fe;\n    unsigned topf, level;\n    DD_CTFP cacheOp;\n    int retval;\n\n    zero = Cudd_Not(DD_ONE(dd));\n    F = Cudd_Regular(f);\n    if (cuddIsConstant(F)) return(f == zero);\n\n    /* From now on f is not constant. */\n    topf = (unsigned) dd->perm[F->index];\n    level = (unsigned) dd->perm[var->index];\n\n    /* Check terminal case. If topf > index of var, f does not depend on var.\n    ** Therefore, var is not dependent in f. */\n    if (topf > level) {\n\treturn(0);\n    }\n\n    cacheOp = (DD_CTFP) Cudd_bddVarIsDependent;\n    res = cuddCacheLookup2(dd,cacheOp,f,var);\n    if (res != NULL) {\n\treturn(res != zero);\n    }\n\n    /* Compute cofactors. */\n    ft = Cudd_NotCond(cuddT(F), f != F);\n    fe = Cudd_NotCond(cuddE(F), f != F);\n\n    if (topf == level) {\n\tretval = Cudd_bddLeq(dd,ft,Cudd_Not(fe));\n    } else {\n\tretval = Cudd_bddVarIsDependent(dd,ft,var) &&\n\t    Cudd_bddVarIsDependent(dd,fe,var);\n    }\n\n    cuddCacheInsert2(dd,cacheOp,f,var,Cudd_NotCond(zero,retval));\n\n    return(retval);\n\n} /* Cudd_bddVarIsDependent */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive steps of Cudd_bddExistAbstract.\n\n  @details It is also used by Cudd_bddUnivAbstract.\n\n  @return the %BDD obtained by abstracting the variables of cube from f\n  if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddExistAbstract Cudd_bddUnivAbstract\n\n*/\nDdNode *\ncuddBddExistAbstractRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * cube)\n{\n    DdNode\t*F, *T, *E, *res, *res1, *res2, *one;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n    F = Cudd_Regular(f);\n\n    /* Cube is guaranteed to be a cube at this point. */\t\n    if (cube == one || F == one) {  \n        return(f);\n    }\n    /* From now on, f and cube are non-constant. */\n\n    /* Abstract a variable that does not appear in f. */\n    while (manager->perm[F->index] > manager->perm[cube->index]) {\n\tcube = cuddT(cube);\n\tif (cube == one) return(f);\n    }\n\n    /* Check the cache. */\n    if (F->ref != 1 && (res = cuddCacheLookup2(manager, Cudd_bddExistAbstract, f, cube)) != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    /* Compute the cofactors of f. */\n    T = cuddT(F); E = cuddE(F);\n    if (f != F) {\n\tT = Cudd_Not(T); E = Cudd_Not(E);\n    }\n\n    /* If the two indices are the same, so are their levels. */\n    if (F->index == cube->index) {\n\tif (T == one || E == one || T == Cudd_Not(E)) {\n\t    return(one);\n\t}\n\tres1 = cuddBddExistAbstractRecur(manager, T, cuddT(cube));\n\tif (res1 == NULL) return(NULL);\n\tif (res1 == one) {\n\t    if (F->ref != 1)\n\t\tcuddCacheInsert2(manager, Cudd_bddExistAbstract, f, cube, one);\n\t    return(one);\n\t}\n        cuddRef(res1);\n\tres2 = cuddBddExistAbstractRecur(manager, E, cuddT(cube));\n\tif (res2 == NULL) {\n\t    Cudd_IterDerefBdd(manager,res1);\n\t    return(NULL);\n\t}\n        cuddRef(res2);\n\tres = cuddBddAndRecur(manager, Cudd_Not(res1), Cudd_Not(res2));\n\tif (res == NULL) {\n\t    Cudd_IterDerefBdd(manager, res1);\n\t    Cudd_IterDerefBdd(manager, res2);\n\t    return(NULL);\n\t}\n\tres = Cudd_Not(res);\n\tcuddRef(res);\n\tCudd_IterDerefBdd(manager, res1);\n\tCudd_IterDerefBdd(manager, res2);\n\tif (F->ref != 1)\n\t    cuddCacheInsert2(manager, Cudd_bddExistAbstract, f, cube, res);\n\tcuddDeref(res);\n        return(res);\n    } else { /* if (cuddI(manager,F->index) < cuddI(manager,cube->index)) */\n\tres1 = cuddBddExistAbstractRecur(manager, T, cube);\n\tif (res1 == NULL) return(NULL);\n        cuddRef(res1);\n\tres2 = cuddBddExistAbstractRecur(manager, E, cube);\n\tif (res2 == NULL) {\n\t    Cudd_IterDerefBdd(manager, res1);\n\t    return(NULL);\n\t}\n        cuddRef(res2);\n\t/* ITE takes care of possible complementation of res1 and of the\n        ** case in which res1 == res2. */\n\tres = cuddBddIteRecur(manager, manager->vars[F->index], res1, res2);\n\tif (res == NULL) {\n\t    Cudd_IterDerefBdd(manager, res1);\n\t    Cudd_IterDerefBdd(manager, res2);\n\t    return(NULL);\n\t}\n\tcuddDeref(res1);\n\tcuddDeref(res2);\n\tif (F->ref != 1)\n\t    cuddCacheInsert2(manager, Cudd_bddExistAbstract, f, cube, res);\n        return(res);\n    }\t    \n\n} /* end of cuddBddExistAbstractRecur */\n\n\n/**\n  @brief Takes the exclusive OR of two BDDs and simultaneously abstracts the\n  variables in cube.\n\n  @details The variables are existentially abstracted.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddAndAbstract\n\n*/\nDdNode *\ncuddBddXorExistAbstractRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g,\n  DdNode * cube)\n{\n    DdNode *F, *fv, *fnv, *G, *gv, *gnv;\n    DdNode *one, *zero, *r, *t, *e, *Cube;\n    int topf, topg, topcube, top;\n    unsigned int index;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    /* Terminal cases. */\n    if (f == g) {\n\treturn(zero);\n    }\n    if (f == Cudd_Not(g)) {\n\treturn(one);\n    }\n    if (cube == one) {\n\treturn(cuddBddXorRecur(manager, f, g));\n    }\n    if (f == one) {\n\treturn(cuddBddExistAbstractRecur(manager, Cudd_Not(g), cube));\n    }\n    if (g == one) {\n\treturn(cuddBddExistAbstractRecur(manager, Cudd_Not(f), cube));\n    }\n    if (f == zero) {\n\treturn(cuddBddExistAbstractRecur(manager, g, cube));\n    }\n    if (g == zero) {\n\treturn(cuddBddExistAbstractRecur(manager, f, cube));\n    }\n\n    /* At this point f, g, and cube are not constant. */\n\n    if (f > g) { /* Try to increase cache efficiency. */\n\tDdNode *tmp = f;\n\tf = g;\n\tg = tmp;\n    }\n\n    /* Check cache. */\n    r = cuddCacheLookup(manager, DD_BDD_XOR_EXIST_ABSTRACT_TAG, f, g, cube);\n    if (r != NULL) {\n\treturn(r);\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    /* Here we can skip the use of cuddI, because the operands are known\n    ** to be non-constant.\n    */\n    F = Cudd_Regular(f);\n    topf = manager->perm[F->index];\n    G = Cudd_Regular(g);\n    topg = manager->perm[G->index];\n    top = ddMin(topf, topg);\n    topcube = manager->perm[cube->index];\n\n    if (topcube < top) {\n\treturn(cuddBddXorExistAbstractRecur(manager, f, g, cuddT(cube)));\n    }\n    /* Now, topcube >= top. */\n\n    if (topf == top) {\n\tindex = F->index;\n\tfv = cuddT(F);\n\tfnv = cuddE(F);\n\tif (Cudd_IsComplement(f)) {\n\t    fv = Cudd_Not(fv);\n\t    fnv = Cudd_Not(fnv);\n\t}\n    } else {\n\tindex = G->index;\n\tfv = fnv = f;\n    }\n\n    if (topg == top) {\n\tgv = cuddT(G);\n\tgnv = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gv = Cudd_Not(gv);\n\t    gnv = Cudd_Not(gnv);\n\t}\n    } else {\n\tgv = gnv = g;\n    }\n\n    if (topcube == top) {\n\tCube = cuddT(cube);\n    } else {\n\tCube = cube;\n    }\n\n    t = cuddBddXorExistAbstractRecur(manager, fv, gv, Cube);\n    if (t == NULL) return(NULL);\n\n    /* Special case: 1 OR anything = 1. Hence, no need to compute\n    ** the else branch if t is 1.\n    */\n    if (t == one && topcube == top) {\n\tcuddCacheInsert(manager, DD_BDD_XOR_EXIST_ABSTRACT_TAG, f, g, cube, one);\n\treturn(one);\n    }\n    cuddRef(t);\n\n    e = cuddBddXorExistAbstractRecur(manager, fnv, gnv, Cube);\n    if (e == NULL) {\n\tCudd_IterDerefBdd(manager, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (topcube == top) {\t/* abstract */\n\tr = cuddBddAndRecur(manager, Cudd_Not(t), Cudd_Not(e));\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(manager, t);\n\t    Cudd_IterDerefBdd(manager, e);\n\t    return(NULL);\n\t}\n\tr = Cudd_Not(r);\n\tcuddRef(r);\n\tCudd_IterDerefBdd(manager, t);\n\tCudd_IterDerefBdd(manager, e);\n\tcuddDeref(r);\n    } else if (t == e) {\n\tr = t;\n\tcuddDeref(t);\n\tcuddDeref(e);\n    } else {\n\tif (Cudd_IsComplement(t)) {\n\t    r = cuddUniqueInter(manager,(int)index,Cudd_Not(t),Cudd_Not(e));\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t} else {\n\t    r = cuddUniqueInter(manager,(int)index,t,e);\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t}\n\tcuddDeref(e);\n\tcuddDeref(t);\n    }\n    cuddCacheInsert(manager, DD_BDD_XOR_EXIST_ABSTRACT_TAG, f, g, cube, r);\n    return (r);\n\n} /* end of cuddBddXorExistAbstractRecur */\n\n\n/**\n  @brief Performs the recursive steps of Cudd_bddBoleanDiff.\n\n  @details Exploits the fact that dF/dx = dF'/dx.\n\n  @return the %BDD obtained by XORing the cofactors of f with respect\n  to var if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddBddBooleanDiffRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * var)\n{\n    DdNode *T, *E, *res, *res1, *res2;\n\n    statLine(manager);\n    if (cuddI(manager,f->index) > manager->perm[var->index]) {\n\t/* f does not depend on var. */\n\treturn(Cudd_Not(DD_ONE(manager)));\n    }\n\n    /* From now on, f is non-constant. */\n\n    /* If the two indices are the same, so are their levels. */\n    if (f->index == var->index) {\n\tres = cuddBddXorRecur(manager, cuddT(f), cuddE(f));\n        return(res);\n    }\n\n    /* From now on, cuddI(manager,f->index) < cuddI(manager,cube->index). */\n\n    /* Check the cache. */\n    res = cuddCacheLookup2(manager, cuddBddBooleanDiffRecur, f, var);\n    if (res != NULL) {\n\treturn(res);\n    }\n\n    /* Compute the cofactors of f. */\n    T = cuddT(f); E = cuddE(f);\n\n    res1 = cuddBddBooleanDiffRecur(manager, T, var);\n    if (res1 == NULL) return(NULL);\n    cuddRef(res1);\n    res2 = cuddBddBooleanDiffRecur(manager, Cudd_Regular(E), var);\n    if (res2 == NULL) {\n\tCudd_IterDerefBdd(manager, res1);\n\treturn(NULL);\n    }\n    cuddRef(res2);\n    /* ITE takes care of possible complementation of res1 and of the\n    ** case in which res1 == res2. */\n    res = cuddBddIteRecur(manager, manager->vars[f->index], res1, res2);\n    if (res == NULL) {\n\tCudd_IterDerefBdd(manager, res1);\n\tCudd_IterDerefBdd(manager, res2);\n\treturn(NULL);\n    }\n    cuddDeref(res1);\n    cuddDeref(res2);\n    cuddCacheInsert2(manager, cuddBddBooleanDiffRecur, f, var, res);\n    return(res);\n\n} /* end of cuddBddBooleanDiffRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Checks whether cube is a %BDD representing the product of\n  positive literals.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nbddCheckPositiveCube(\n  DdManager * manager,\n  DdNode * cube)\n{\n    if (Cudd_IsComplement(cube)) return(0);\n    if (cube == DD_ONE(manager)) return(1);\n    if (cuddIsConstant(cube)) return(0);\n    if (cuddE(cube) == Cudd_Not(DD_ONE(manager))) {\n        return(bddCheckPositiveCube(manager, cuddT(cube)));\n    }\n    return(0);\n\n} /* end of bddCheckPositiveCube */\n\n"
  },
  {
    "path": "cudd/cudd/cuddBddCorr.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Correlation between BDDs.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/** Type of hash-table key. */\ntypedef struct hashEntry {\n    DdNode *f;\n    DdNode *g;\n} HashEntry;\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#ifdef CORREL_STATS\nstatic\tint\tnum_calls;\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic double bddCorrelationAux (DdManager *dd, DdNode *f, DdNode *g, st_table *table);\nstatic double bddCorrelationWeightsAux (DdManager *dd, DdNode *f, DdNode *g, double *prob, st_table *table);\nstatic int CorrelCompare (const void *key1, const void *key2);\nstatic int CorrelHash (void const *key, int modulus);\nstatic enum st_retval CorrelCleanUp (void *key, void *value, void *arg);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Computes the correlation of f and g.\n\n  @details If f == g, their correlation is 1. If f == g', their\n  correlation is 0.\n\n  @return the fraction of minterms in the ON-set of the EXNOR of f and\n  g.  If it runs out of memory, returns (double)CUDD_OUT_OF_MEM.\n\n  @sideeffect None\n\n  @see Cudd_bddCorrelationWeights\n\n*/\ndouble\nCudd_bddCorrelation(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g)\n{\n    st_table\t*table;\n    double\tcorrelation;\n\n#ifdef CORREL_STATS\n    num_calls = 0;\n#endif\n\n    table = st_init_table(CorrelCompare,CorrelHash);\n    if (table == NULL) return((double)CUDD_OUT_OF_MEM);\n    correlation = bddCorrelationAux(manager,f,g,table);\n    st_foreach(table, CorrelCleanUp, NIL(void));\n    st_free_table(table);\n    return(correlation);\n\n} /* end of Cudd_bddCorrelation */\n\n\n/**\n  @brief Computes the correlation of f and g for given input\n  probabilities.\n\n  @details On input, prob\\[i\\] is supposed to contain the probability\n  of the i-th input variable to be 1.  If f == g, their correlation is\n  1. If f == g', their correlation is 0.  The correlation of f and the\n  constant one gives the probability of f.\n\n  @return the probability that f and g have the same value. If it runs\n  out of memory, returns (double)CUDD_OUT_OF_MEM.\n\n  @sideeffect None\n\n  @see Cudd_bddCorrelation\n\n*/\ndouble\nCudd_bddCorrelationWeights(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g,\n  double * prob)\n{\n    st_table\t*table;\n    double\tcorrelation;\n\n#ifdef CORREL_STATS\n    num_calls = 0;\n#endif\n\n    table = st_init_table(CorrelCompare,CorrelHash);\n    if (table == NULL) return((double)CUDD_OUT_OF_MEM);\n    correlation = bddCorrelationWeightsAux(manager,f,g,prob,table);\n    st_foreach(table, CorrelCleanUp, NIL(void));\n    st_free_table(table);\n    return(correlation);\n\n} /* end of Cudd_bddCorrelationWeights */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddCorrelation.\n\n  @return the fraction of minterms in the ON-set of the EXNOR of f and\n  g.\n\n  @sideeffect None\n\n  @see bddCorrelationWeightsAux\n\n*/\nstatic double\nbddCorrelationAux(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  st_table * table)\n{\n    DdNode\t*Fv, *Fnv, *G, *Gv, *Gnv;\n    double\tmin, *pmin, min1, min2;\n    void        *dummy;\n    HashEntry\t*entry;\n    int topF, topG;\n\n    statLine(dd);\n#ifdef CORREL_STATS\n    num_calls++;\n#endif\n\n    /* Terminal cases: only work for BDDs. */\n    if (f == g) return(1.0);\n    if (f == Cudd_Not(g)) return(0.0);\n\n    /* Standardize call using the following properties:\n    **     (f EXNOR g)   = (g EXNOR f)\n    **     (f' EXNOR g') = (f EXNOR g).\n    */\n    if (f > g) {\n\tDdNode *tmp = f;\n\tf = g; g = tmp;\n    }\n    if (Cudd_IsComplement(f)) {\n\tf = Cudd_Not(f);\n\tg = Cudd_Not(g);\n    }\n    /* From now on, f is regular. */\n    \n    entry = ALLOC(HashEntry,1);\n    if (entry == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    entry->f = f; entry->g = g;\n\n    /* We do not use the fact that\n    ** correlation(f,g') = 1 - correlation(f,g)\n    ** to minimize the risk of cancellation.\n    */\n    if (st_lookup(table, entry, &dummy)) {\n        min = *(double *) dummy;\n\tFREE(entry);\n\treturn(min);\n    }\n\n    G = Cudd_Regular(g);\n    topF = cuddI(dd,f->index); topG = cuddI(dd,G->index);\n    if (topF <= topG) { Fv = cuddT(f); Fnv = cuddE(f); } else { Fv = Fnv = f; }\n    if (topG <= topF) { Gv = cuddT(G); Gnv = cuddE(G); } else { Gv = Gnv = G; }\n\n    if (g != G) {\n\tGv = Cudd_Not(Gv);\n\tGnv = Cudd_Not(Gnv);\n    }\n\n    min1 = bddCorrelationAux(dd, Fv, Gv, table) / 2.0;\n    if (min1 == (double)CUDD_OUT_OF_MEM) {\n\tFREE(entry);\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    min2 = bddCorrelationAux(dd, Fnv, Gnv, table) / 2.0; \n    if (min2 == (double)CUDD_OUT_OF_MEM) {\n\tFREE(entry);\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    min = (min1+min2);\n    \n    pmin = ALLOC(double,1);\n    if (pmin == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    *pmin = min;\n\n    if (st_insert(table, entry, pmin) == ST_OUT_OF_MEM) {\n\tFREE(entry);\n\tFREE(pmin);\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    return(min);\n\n} /* end of bddCorrelationAux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddCorrelationWeigths.\n\n  @sideeffect None\n\n  @see bddCorrelationAux\n\n*/\nstatic double\nbddCorrelationWeightsAux(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  double * prob,\n  st_table * table)\n{\n    DdNode\t*Fv, *Fnv, *G, *Gv, *Gnv;\n    double\tmin, *pmin, min1, min2;\n    void        *dummy;\n    HashEntry\t*entry;\n    int\t\ttopF, topG;\n    unsigned\tindex;\n\n    statLine(dd);\n#ifdef CORREL_STATS\n    num_calls++;\n#endif\n\n    /* Terminal cases: only work for BDDs. */\n    if (f == g) return(1.0);\n    if (f == Cudd_Not(g)) return(0.0);\n\n    /* Standardize call using the following properties:\n    **     (f EXNOR g)   = (g EXNOR f)\n    **     (f' EXNOR g') = (f EXNOR g).\n    */\n    if (f > g) {\n\tDdNode *tmp = f;\n\tf = g; g = tmp;\n    }\n    if (Cudd_IsComplement(f)) {\n\tf = Cudd_Not(f);\n\tg = Cudd_Not(g);\n    }\n    /* From now on, f is regular. */\n    \n    entry = ALLOC(HashEntry,1);\n    if (entry == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    entry->f = f; entry->g = g;\n\n    /* We do not use the fact that\n    ** correlation(f,g') = 1 - correlation(f,g)\n    ** to minimize the risk of cancellation.\n    */\n    if (st_lookup(table, entry, &dummy)) {\n\tmin = *(double *) dummy;\n\tFREE(entry);\n\treturn(min);\n    }\n\n    G = Cudd_Regular(g);\n    topF = cuddI(dd,f->index); topG = cuddI(dd,G->index);\n    if (topF <= topG) {\n\tFv = cuddT(f); Fnv = cuddE(f);\n\tindex = f->index;\n    } else {\n\tFv = Fnv = f;\n\tindex = G->index;\n    }\n    if (topG <= topF) { Gv = cuddT(G); Gnv = cuddE(G); } else { Gv = Gnv = G; }\n\n    if (g != G) {\n\tGv = Cudd_Not(Gv);\n\tGnv = Cudd_Not(Gnv);\n    }\n\n    min1 = bddCorrelationWeightsAux(dd, Fv, Gv, prob, table) * prob[index];\n    if (min1 == (double)CUDD_OUT_OF_MEM) {\n\tFREE(entry);\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    min2 = bddCorrelationWeightsAux(dd, Fnv, Gnv, prob, table) * (1.0 - prob[index]); \n    if (min2 == (double)CUDD_OUT_OF_MEM) {\n\tFREE(entry);\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    min = (min1+min2);\n    \n    pmin = ALLOC(double,1);\n    if (pmin == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    *pmin = min;\n\n    if (st_insert(table, entry, pmin) == ST_OUT_OF_MEM) {\n\tFREE(entry);\n\tFREE(pmin);\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    return(min);\n\n} /* end of bddCorrelationWeightsAux */\n\n\n/**\n  @brief Compares two hash table entries.\n\n  @return 0 if they are identical; 1 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nCorrelCompare(\n  void const * key1,\n  void const * key2)\n{\n    HashEntry const *entry1 = (HashEntry const *) key1;\n    HashEntry const *entry2 = (HashEntry const *) key2;\n    if (entry1->f != entry2->f || entry1->g != entry2->g) return(1);\n\n    return(0);\n\n} /* end of CorrelCompare */\n\n\n/**\n  @brief Hashes a hash table entry.\n\n  @details It is patterned after st_strhash.\n\n  @return a value between 0 and modulus.\n\n  @sideeffect None\n\n*/\nstatic int\nCorrelHash(\n  void const * key,\n  int  modulus)\n{\n    HashEntry const *entry = (HashEntry const *) key;\n    int val = 0;\n\n    val = (int) (((ptrint)entry->f)*997 + ((ptrint)entry->g));\n\n    return ((val < 0) ? -val : val) % modulus;\n\n} /* end of CorrelHash */\n\n\n/**\n  @brief Frees memory associated with hash table.\n\n  @return ST_CONTINUE.\n\n  @sideeffect None\n\n*/\nstatic enum st_retval\nCorrelCleanUp(\n  void * key,\n  void * value,\n  void * arg)\n{\n    double\t  *d = (double *) value;\n    HashEntry *entry = (HashEntry *) key;\n\n    (void) arg; /* avoid warning */\n    FREE(entry);\n    FREE(d);\n    return ST_CONTINUE;\n\n} /* end of CorrelCleanUp */\n"
  },
  {
    "path": "cudd/cudd/cuddBddIte.c",
    "content": "/**\n  @file \n\n  @ingroup cudd\n\n  @brief %BDD ITE function and satellites.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void bddVarToConst (DdNode *f, DdNode **gp, DdNode **hp, DdNode *one);\nstatic int bddVarToCanonical (DdManager *dd, DdNode **fp, DdNode **gp, DdNode **hp, int *topfp, int *topgp, int *tophp);\nstatic int bddVarToCanonicalSimple (DdManager *dd, DdNode **fp, DdNode **gp, DdNode **hp, int *topfp, int *topgp, int *tophp);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements ITE(f,g,h).\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_addIte Cudd_bddIteConstant Cudd_bddIntersect\n\n*/\nDdNode *\nCudd_bddIte(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */,\n  DdNode * h /**< third operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddIteRecur(dd,f,g,h);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddIte */\n\n\n/**\n  @brief Implements ITE(f,g,h) unless too many nodes are required.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up or more new nodes than `limit` are\n  required.\n\n  @sideeffect None\n\n  @see Cudd_bddIte\n\n*/\nDdNode *\nCudd_bddIteLimit(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */,\n  DdNode * h /**< third operand */,\n  unsigned int limit /**< maximum number of new nodes */)\n{\n    DdNode *res;\n    unsigned int saveLimit = dd->maxLive;\n\n    dd->maxLive = (dd->keys - dd->dead) + (dd->keysZ - dd->deadZ) + limit;\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddIteRecur(dd,f,g,h);\n    } while (dd->reordered == 1);\n    dd->maxLive = saveLimit;\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddIteLimit */\n\n\n/**\n  @brief Implements ITEconstant(f,g,h).\n\n  @return a pointer to the resulting %BDD (which may or may not be\n  constant) or DD_NON_CONSTANT.\n\n  @details No new nodes are created.\n\n  @sideeffect None\n\n  @see Cudd_bddIte Cudd_bddIntersect Cudd_bddLeq Cudd_addIteConstant\n\n*/\nDdNode *\nCudd_bddIteConstant(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */,\n  DdNode * h /**< thord operand */)\n{\n    DdNode\t *r, *Fv, *Fnv, *Gv, *Gnv, *H, *Hv, *Hnv, *t, *e;\n    DdNode\t *one = DD_ONE(dd);\n    DdNode\t *zero = Cudd_Not(one);\n    int\t\t comple;\n    int\t\t topf, topg, toph, v;\n\n    statLine(dd);\n    /* Trivial cases. */\n    if (f == one) \t\t\t/* ITE(1,G,H) => G */\n\treturn(g);\n    \n    if (f == zero)\t\t\t/* ITE(0,G,H) => H */\n\treturn(h);\n    \n    /* f now not a constant. */\n    bddVarToConst(f, &g, &h, one);\t/* possibly convert g or h */\n\t\t\t\t\t/* to constants */\n\n    if (g == h) \t\t\t/* ITE(F,G,G) => G */\n\treturn(g);\n\n    if (Cudd_IsConstantInt(g) && Cudd_IsConstantInt(h)) \n\treturn(DD_NON_CONSTANT);\t/* ITE(F,1,0) or ITE(F,0,1) */\n\t\t\t\t\t/* => DD_NON_CONSTANT */\n    \n    if (g == Cudd_Not(h))\n\treturn(DD_NON_CONSTANT);\t/* ITE(F,G,G') => DD_NON_CONSTANT */\n\t\t\t\t\t/* if F != G and F != G' */\n    \n    comple = bddVarToCanonical(dd, &f, &g, &h, &topf, &topg, &toph);\n\n    /* Cache lookup. */\n    r = cuddConstantLookup(dd, DD_BDD_ITE_CONSTANT_TAG, f, g, h);\n    if (r != NULL) {\n\treturn(Cudd_NotCond(r,comple && r != DD_NON_CONSTANT));\n    }\n\n    v = ddMin(topg, toph);\n\n    /* ITE(F,G,H) = (v,G,H) (non constant) if F = (v,1,0), v < top(G,H). */\n    if (topf < v && cuddT(f) == one && cuddE(f) == zero) {\n\treturn(DD_NON_CONSTANT);\n    }\n\n    /* Compute cofactors. */\n    if (topf <= v) {\n\tv = ddMin(topf, v);\t\t/* v = top_var(F,G,H) */\n\tFv = cuddT(f); Fnv = cuddE(f);\n    } else {\n\tFv = Fnv = f;\n    }\n\n    if (topg == v) {\n\tGv = cuddT(g); Gnv = cuddE(g);\n    } else {\n\tGv = Gnv = g;\n    }\n\n    if (toph == v) {\n\tH = Cudd_Regular(h);\n\tHv = cuddT(H); Hnv = cuddE(H);\n\tif (Cudd_IsComplement(h)) {\n\t    Hv = Cudd_Not(Hv);\n\t    Hnv = Cudd_Not(Hnv);\n\t}\n    } else {\n\tHv = Hnv = h;\n    }\n\n    /* Recursion. */\n    t = Cudd_bddIteConstant(dd, Fv, Gv, Hv);\n    if (t == DD_NON_CONSTANT || !Cudd_IsConstantInt(t)) {\n\tcuddCacheInsert(dd, DD_BDD_ITE_CONSTANT_TAG, f, g, h, DD_NON_CONSTANT);\n\treturn(DD_NON_CONSTANT);\n    }\n    e = Cudd_bddIteConstant(dd, Fnv, Gnv, Hnv);\n    if (e == DD_NON_CONSTANT || !Cudd_IsConstantInt(e) || t != e) {\n\tcuddCacheInsert(dd, DD_BDD_ITE_CONSTANT_TAG, f, g, h, DD_NON_CONSTANT);\n\treturn(DD_NON_CONSTANT);\n    }\n    cuddCacheInsert(dd, DD_BDD_ITE_CONSTANT_TAG, f, g, h, t);\n    return(Cudd_NotCond(t,comple));\n\n} /* end of Cudd_bddIteConstant */\n\n\n/**\n  @brief Returns a function included in the intersection of f and g.\n\n  @details The function computed (if not zero) is a witness that the\n  intersection is not empty.  Cudd_bddIntersect tries to build as few\n  new nodes as possible. If the only result of interest is whether f\n  and g intersect, Cudd_bddLeq should be used instead.\n\n  @sideeffect None\n\n  @see Cudd_bddLeq Cudd_bddIteConstant\n\n*/\nDdNode *\nCudd_bddIntersect(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddIntersectRecur(dd,f,g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_bddIntersect */\n\n\n/**\n  @brief Computes the conjunction of two BDDs f and g.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddIte Cudd_addApply Cudd_bddAndAbstract Cudd_bddIntersect\n  Cudd_bddOr Cudd_bddNand Cudd_bddNor Cudd_bddXor Cudd_bddXnor\n\n*/\nDdNode *\nCudd_bddAnd(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddAndRecur(dd,f,g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddAnd */\n\n\n/**\n  @brief Computes the conjunction of two BDDs f and g unless too many\n  nodes are required.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up or more new nodes than `limit` are\n  required.\n\n  @sideeffect None\n\n  @see Cudd_bddAnd\n\n*/\nDdNode *\nCudd_bddAndLimit(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */,\n  unsigned int limit /**< maximum number of new nodes */)\n{\n    DdNode *res;\n    unsigned int saveLimit = dd->maxLive;\n\n    dd->maxLive = (dd->keys - dd->dead) + (dd->keysZ - dd->deadZ) + limit;\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddAndRecur(dd,f,g);\n    } while (dd->reordered == 1);\n    dd->maxLive = saveLimit;\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddAndLimit */\n\n\n/**\n  @brief Computes the disjunction of two BDDs f and g.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddIte Cudd_addApply Cudd_bddAnd Cudd_bddNand Cudd_bddNor\n  Cudd_bddXor Cudd_bddXnor\n\n*/\nDdNode *\nCudd_bddOr(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddAndRecur(dd,Cudd_Not(f),Cudd_Not(g));\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    res = Cudd_NotCond(res,res != NULL);\n    return(res);\n\n} /* end of Cudd_bddOr */\n\n\n/**\n  @brief Computes the disjunction of two BDDs f and g unless too many\n  nodes are required.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up or more new nodes than `limit` are\n  required.\n\n  @sideeffect None\n\n  @see Cudd_bddOr\n\n*/\nDdNode *\nCudd_bddOrLimit(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */,\n  unsigned int limit /**< maximum number of new nodes */)\n{\n    DdNode *res;\n    unsigned int saveLimit = dd->maxLive;\n\n    dd->maxLive = (dd->keys - dd->dead) + (dd->keysZ - dd->deadZ) + limit;\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddAndRecur(dd,Cudd_Not(f),Cudd_Not(g));\n    } while (dd->reordered == 1);\n    dd->maxLive = saveLimit;\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    res = Cudd_NotCond(res,res != NULL);\n    return(res);\n\n} /* end of Cudd_bddOrLimit */\n\n\n/**\n  @brief Computes the NAND of two BDDs f and g.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddIte Cudd_addApply Cudd_bddAnd Cudd_bddOr Cudd_bddNor\n  Cudd_bddXor Cudd_bddXnor\n\n*/\nDdNode *\nCudd_bddNand(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /** second operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddAndRecur(dd,f,g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    res = Cudd_NotCond(res,res != NULL);\n    return(res);\n\n} /* end of Cudd_bddNand */\n\n\n/**\n  @brief Computes the NOR of two BDDs f and g.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddIte Cudd_addApply Cudd_bddAnd Cudd_bddOr Cudd_bddNand\n  Cudd_bddXor Cudd_bddXnor\n\n*/\nDdNode *\nCudd_bddNor(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddAndRecur(dd,Cudd_Not(f),Cudd_Not(g));\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddNor */\n\n\n/**\n  @brief Computes the exclusive OR of two BDDs f and g.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddIte Cudd_addApply Cudd_bddAnd Cudd_bddOr\n  Cudd_bddNand Cudd_bddNor Cudd_bddXnor\n\n*/\nDdNode *\nCudd_bddXor(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddXorRecur(dd,f,g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddXor */\n\n\n/**\n  @brief Computes the exclusive NOR of two BDDs f and g.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddIte Cudd_addApply Cudd_bddAnd Cudd_bddOr\n  Cudd_bddNand Cudd_bddNor Cudd_bddXor\n\n*/\nDdNode *\nCudd_bddXnor(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddXorRecur(dd,f,Cudd_Not(g));\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddXnor */\n\n\n/**\n  @brief Computes the exclusive NOR of two BDDs f and g unless too\n  many nodes are required.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up or more new nodes than `limit` are\n  required.\n\n  @sideeffect None\n\n  @see Cudd_bddXnor\n\n*/\nDdNode *\nCudd_bddXnorLimit(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */,\n  unsigned int limit /**< maximum number of new nodes */)\n{\n    DdNode *res;\n    unsigned int saveLimit = dd->maxLive;\n\n    dd->maxLive = (dd->keys - dd->dead) + (dd->keysZ - dd->deadZ) + limit;\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddXorRecur(dd,f,Cudd_Not(g));\n    } while (dd->reordered == 1);\n    dd->maxLive = saveLimit;\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddXnorLimit */\n\n\n/**\n  @brief Checks whether f is less than or equal to g.\n\n  @return 1 if f is less than or equal to g; 0 otherwise.\n\n  @details No new nodes are created.\n\n  @sideeffect None\n\n  @see Cudd_bddIteConstant Cudd_addEvalConst\n\n*/\nint\nCudd_bddLeq(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first operand */,\n  DdNode * g /**< second operand */)\n{\n    DdNode *one, *zero, *tmp, *F, *fv, *fvn, *gv, *gvn;\n    int topf, topg, res;\n\n    statLine(dd);\n    /* Terminal cases and normalization. */\n    if (f == g) return(1);\n\n    if (Cudd_IsComplement(g)) {\n\t/* Special case: if f is regular and g is complemented,\n\t** f(1,...,1) = 1 > 0 = g(1,...,1).\n\t*/\n\tif (!Cudd_IsComplement(f)) return(0);\n\t/* Both are complemented: Swap and complement because\n\t** f <= g <=> g' <= f' and we want the second argument to be regular.\n\t*/\n\ttmp = g;\n\tg = Cudd_Not(f);\n\tf = Cudd_Not(tmp);\n    } else if (Cudd_IsComplement(f) && g < f) {\n\ttmp = g;\n\tg = Cudd_Not(f);\n\tf = Cudd_Not(tmp);\n    }\n\n    /* Now g is regular. */\n    one = DD_ONE(dd);\n    if (g == one) return(1);\t/* no need to test against zero */\n    if (f == one) return(0);\t/* since at this point g != one */\n    if (Cudd_Not(f) == g) return(0); /* because neither is constant */\n    zero = Cudd_Not(one);\n    if (f == zero) return(1);\n\n    /* Here neither f nor g is constant. */\n\n    /* Check cache. */\n    F = Cudd_Regular(f);\n    if (F->ref != 1 || g->ref != 1) {\n        tmp = cuddCacheLookup2(dd,(DD_CTFP)Cudd_bddLeq,f,g);\n        if (tmp != NULL) {\n            return(tmp == one);\n        }\n    }\n\n    /* Compute cofactors. */\n    topf = dd->perm[F->index];\n    topg = dd->perm[g->index];\n    if (topf <= topg) {\n\tfv = cuddT(F); fvn = cuddE(F);\n\tif (f != F) {\n\t    fv = Cudd_Not(fv);\n\t    fvn = Cudd_Not(fvn);\n\t}\n    } else {\n\tfv = fvn = f;\n    }\n    if (topg <= topf) {\n\tgv = cuddT(g); gvn = cuddE(g);\n    } else {\n\tgv = gvn = g;\n    }\n\n    /* Recursive calls. Since we want to maximize the probability of\n    ** the special case f(1,...,1) > g(1,...,1), we consider the negative\n    ** cofactors first. Indeed, the complementation parity of the positive\n    ** cofactors is the same as the one of the parent functions.\n    */\n    res = Cudd_bddLeq(dd,fvn,gvn) && Cudd_bddLeq(dd,fv,gv);\n\n    /* Store result in cache and return. */\n    if (F->ref !=1 || g->ref != 1)\n        cuddCacheInsert2(dd,(DD_CTFP)Cudd_bddLeq,f,g,(res ? one : zero));\n    return(res);\n\n} /* end of Cudd_bddLeq */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the recursive step of Cudd_bddIte.\n\n  @return a pointer to the resulting %BDD. NULL if the intermediate\n  result blows up or if reordering occurs.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddBddIteRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    DdNode\t *one, *zero, *res;\n    DdNode\t *r, *Fv, *Fnv, *Gv, *Gnv, *H, *Hv, *Hnv, *t, *e;\n    int\t\t topf, topg, toph, v;\n    unsigned int index;\n    int\t\t comple;\n\n    statLine(dd);\n    /* Terminal cases. */\n\n    /* One variable cases. */\n    if (f == (one = DD_ONE(dd))) \t/* ITE(1,G,H) = G */\n\treturn(g);\n    \n    if (f == (zero = Cudd_Not(one))) \t/* ITE(0,G,H) = H */\n\treturn(h);\n    \n    /* From now on, f is known not to be a constant. */\n    if (g == one || f == g) {\t/* ITE(F,F,H) = ITE(F,1,H) = F + H */\n\tif (h == zero) {\t/* ITE(F,1,0) = F */\n\t    return(f);\n\t} else {\n\t    res = cuddBddAndRecur(dd,Cudd_Not(f),Cudd_Not(h));\n\t    return(Cudd_NotCond(res,res != NULL));\n\t}\n    } else if (g == zero || f == Cudd_Not(g)) { /* ITE(F,!F,H) = ITE(F,0,H) = !F * H */\n\tif (h == one) {\t\t/* ITE(F,0,1) = !F */\n\t    return(Cudd_Not(f));\n\t} else {\n\t    res = cuddBddAndRecur(dd,Cudd_Not(f),h);\n\t    return(res);\n\t}\n    }\n    if (h == zero || f == h) {    /* ITE(F,G,F) = ITE(F,G,0) = F * G */\n\tres = cuddBddAndRecur(dd,f,g);\n\treturn(res);\n    } else if (h == one || f == Cudd_Not(h)) { /* ITE(F,G,!F) = ITE(F,G,1) = !F + G */\n\tres = cuddBddAndRecur(dd,f,Cudd_Not(g));\n\treturn(Cudd_NotCond(res,res != NULL));\n    }\n\n    /* Check remaining one variable case. */\n    if (g == h) { \t\t/* ITE(F,G,G) = G */\n\treturn(g);\n    } else if (g == Cudd_Not(h)) { /* ITE(F,G,!G) = F <-> G */\n\tres = cuddBddXorRecur(dd,f,h);\n\treturn(res);\n    }\n    \n    /* From here, there are no constants. */\n    comple = bddVarToCanonicalSimple(dd, &f, &g, &h, &topf, &topg, &toph);\n\n    /* f & g are now regular pointers */\n\n    v = ddMin(topg, toph);\n\n    /* A shortcut: ITE(F,G,H) = (v,G,H) if F = (v,1,0), v < top(G,H). */\n    if (topf < v && cuddT(f) == one && cuddE(f) == zero) {\n\tr = cuddUniqueInter(dd, (int) f->index, g, h);\n\treturn(Cudd_NotCond(r,comple && r != NULL));\n    }\n\n    /* Check cache. */\n    r = cuddCacheLookup(dd, DD_BDD_ITE_TAG, f, g, h);\n    if (r != NULL) {\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Compute cofactors. */\n    index = f->index;\n    if (topf <= v) {\n\tv = ddMin(topf, v);\t/* v = top_var(F,G,H) */\n\tFv = cuddT(f); Fnv = cuddE(f);\n    } else {\n\tFv = Fnv = f;\n    }\n    if (topg == v) {\n\tindex = g->index;\n\tGv = cuddT(g); Gnv = cuddE(g);\n    } else {\n\tGv = Gnv = g;\n    }\n    if (toph == v) {\n\tH = Cudd_Regular(h);\n\tindex = H->index;\n\tHv = cuddT(H); Hnv = cuddE(H);\n\tif (Cudd_IsComplement(h)) {\n\t    Hv = Cudd_Not(Hv);\n\t    Hnv = Cudd_Not(Hnv);\n\t}\n    } else {\n\tHv = Hnv = h;\n    }\n\n    /* Recursive step. */\n    t = cuddBddIteRecur(dd,Fv,Gv,Hv);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n\n    e = cuddBddIteRecur(dd,Fnv,Gnv,Hnv);\n    if (e == NULL) {\n\tCudd_IterDerefBdd(dd,t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    r = (t == e) ? t : cuddUniqueInter(dd,index,t,e);\n    if (r == NULL) {\n\tCudd_IterDerefBdd(dd,t);\n\tCudd_IterDerefBdd(dd,e);\n\treturn(NULL);\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    cuddCacheInsert(dd, DD_BDD_ITE_TAG, f, g, h, r);\n    return(Cudd_NotCond(r,comple));\n\n} /* end of cuddBddIteRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_bddIntersect.\n\n  @sideeffect None\n\n  @see Cudd_bddIntersect\n\n*/\nDdNode *\ncuddBddIntersectRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *res;\n    DdNode *F, *G, *t, *e;\n    DdNode *fv, *fnv, *gv, *gnv;\n    DdNode *one, *zero;\n    unsigned int index;\n    int topf, topg;\n\n    statLine(dd);\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    /* Terminal cases. */\n    if (f == zero || g == zero || f == Cudd_Not(g)) return(zero);\n    if (f == g || g == one) return(f);\n    if (f == one) return(g);\n\n    /* At this point f and g are not constant. */\n    if (f > g) { DdNode *tmp = f; f = g; g = tmp; }\n    res = cuddCacheLookup2(dd,Cudd_bddIntersect,f,g);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Find splitting variable. Here we can skip the use of cuddI,\n    ** because the operands are known to be non-constant.\n    */\n    F = Cudd_Regular(f);\n    topf = dd->perm[F->index];\n    G = Cudd_Regular(g);\n    topg = dd->perm[G->index];\n\n    /* Compute cofactors. */\n    if (topf <= topg) {\n\tindex = F->index;\n\tfv = cuddT(F);\n\tfnv = cuddE(F);\n\tif (Cudd_IsComplement(f)) {\n\t    fv = Cudd_Not(fv);\n\t    fnv = Cudd_Not(fnv);\n\t}\n    } else {\n\tindex = G->index;\n\tfv = fnv = f;\n    }\n\n    if (topg <= topf) {\n\tgv = cuddT(G);\n\tgnv = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gv = Cudd_Not(gv);\n\t    gnv = Cudd_Not(gnv);\n\t}\n    } else {\n\tgv = gnv = g;\n    }\n\n    /* Compute partial results. */\n    t = cuddBddIntersectRecur(dd,fv,gv);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n    if (t != zero) {\n\te = zero;\n    } else {\n\te = cuddBddIntersectRecur(dd,fnv,gnv);\n\tif (e == NULL) {\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n    }\n    cuddRef(e);\n\n    if (t == e) { /* both equal zero */\n\tres = t;\n    } else if (Cudd_IsComplement(t)) {\n\tres = cuddUniqueInter(dd,(int)index,Cudd_Not(t),Cudd_Not(e));\n\tif (res == NULL) {\n\t    Cudd_IterDerefBdd(dd, t);\n\t    Cudd_IterDerefBdd(dd, e);\n\t    return(NULL);\n\t}\n\tres = Cudd_Not(res);\n    } else {\n\tres = cuddUniqueInter(dd,(int)index,t,e);\n\tif (res == NULL) {\n\t    Cudd_IterDerefBdd(dd, t);\n\t    Cudd_IterDerefBdd(dd, e);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(e);\n    cuddDeref(t);\n\n    cuddCacheInsert2(dd,Cudd_bddIntersect,f,g,res);\n\n    return(res);\n\n} /* end of cuddBddIntersectRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_bddAnd.\n\n  @details Takes the conjunction of two BDDs.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddAnd\n\n*/\nDdNode *\ncuddBddAndRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *F, *fv, *fnv, *G, *gv, *gnv;\n    DdNode *one, *r, *t, *e;\n    int topf, topg;\n    unsigned int index;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n\n    /* Terminal cases. */\n    F = Cudd_Regular(f);\n    G = Cudd_Regular(g);\n    if (F == G) {\n\tif (f == g) return(f);\n\telse return(Cudd_Not(one));\n    }\n    if (F == one) {\n\tif (f == one) return(g);\n\telse return(f);\n    }\n    if (G == one) {\n\tif (g == one) return(f);\n\telse return(g);\n    }\n\n    /* At this point f and g are not constant. */\n    if (f > g) { /* Try to increase cache efficiency. */\n\tDdNode *tmp = f;\n\tf = g;\n\tg = tmp;\n\tF = Cudd_Regular(f);\n\tG = Cudd_Regular(g);\n    }\n\n    /* Check cache. */\n    if (F->ref != 1 || G->ref != 1) {\n\tr = cuddCacheLookup2(manager, Cudd_bddAnd, f, g);\n\tif (r != NULL) return(r);\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    /* Here we can skip the use of cuddI, because the operands are known\n    ** to be non-constant.\n    */\n    topf = manager->perm[F->index];\n    topg = manager->perm[G->index];\n\n    /* Compute cofactors. */\n    if (topf <= topg) {\n\tindex = F->index;\n\tfv = cuddT(F);\n\tfnv = cuddE(F);\n\tif (Cudd_IsComplement(f)) {\n\t    fv = Cudd_Not(fv);\n\t    fnv = Cudd_Not(fnv);\n\t}\n    } else {\n\tindex = G->index;\n\tfv = fnv = f;\n    }\n\n    if (topg <= topf) {\n\tgv = cuddT(G);\n\tgnv = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gv = Cudd_Not(gv);\n\t    gnv = Cudd_Not(gnv);\n\t}\n    } else {\n\tgv = gnv = g;\n    }\n\n    t = cuddBddAndRecur(manager, fv, gv);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n\n    e = cuddBddAndRecur(manager, fnv, gnv);\n    if (e == NULL) {\n\tCudd_IterDerefBdd(manager, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (t == e) {\n\tr = t;\n    } else {\n\tif (Cudd_IsComplement(t)) {\n\t    r = cuddUniqueInter(manager,(int)index,Cudd_Not(t),Cudd_Not(e));\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t} else {\n\t    r = cuddUniqueInter(manager,(int)index,t,e);\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t}\n    }\n    cuddDeref(e);\n    cuddDeref(t);\n    if (F->ref != 1 || G->ref != 1)\n\tcuddCacheInsert2(manager, Cudd_bddAnd, f, g, r);\n    return(r);\n\n} /* end of cuddBddAndRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_bddXor.\n\n  @details Takes the exclusive OR of two BDDs.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddXor\n\n*/\nDdNode *\ncuddBddXorRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *fv, *fnv, *G, *gv, *gnv;\n    DdNode *one, *zero, *r, *t, *e;\n    int topf, topg;\n    unsigned int index;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    /* Terminal cases. */\n    if (f == g) return(zero);\n    if (f == Cudd_Not(g)) return(one);\n    if (f > g) { /* Try to increase cache efficiency and simplify tests. */\n\tDdNode *tmp = f;\n\tf = g;\n\tg = tmp;\n    }\n    if (g == zero) return(f);\n    if (g == one) return(Cudd_Not(f));\n    if (Cudd_IsComplement(f)) {\n\tf = Cudd_Not(f);\n\tg = Cudd_Not(g);\n    }\n    /* Now the first argument is regular. */\n    if (f == one) return(Cudd_Not(g));\n\n    /* At this point f and g are not constant. */\n\n    /* Check cache. */\n    r = cuddCacheLookup2(manager, Cudd_bddXor, f, g);\n    if (r != NULL) return(r);\n\n    checkWhetherToGiveUp(manager);\n\n    /* Here we can skip the use of cuddI, because the operands are known\n    ** to be non-constant.\n    */\n    topf = manager->perm[f->index];\n    G = Cudd_Regular(g);\n    topg = manager->perm[G->index];\n\n    /* Compute cofactors. */\n    if (topf <= topg) {\n\tindex = f->index;\n\tfv = cuddT(f);\n\tfnv = cuddE(f);\n    } else {\n\tindex = G->index;\n\tfv = fnv = f;\n    }\n\n    if (topg <= topf) {\n\tgv = cuddT(G);\n\tgnv = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gv = Cudd_Not(gv);\n\t    gnv = Cudd_Not(gnv);\n\t}\n    } else {\n\tgv = gnv = g;\n    }\n\n    t = cuddBddXorRecur(manager, fv, gv);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n\n    e = cuddBddXorRecur(manager, fnv, gnv);\n    if (e == NULL) {\n\tCudd_IterDerefBdd(manager, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (t == e) {\n\tr = t;\n    } else {\n\tif (Cudd_IsComplement(t)) {\n\t    r = cuddUniqueInter(manager,(int)index,Cudd_Not(t),Cudd_Not(e));\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t} else {\n\t    r = cuddUniqueInter(manager,(int)index,t,e);\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t}\n    }\n    cuddDeref(e);\n    cuddDeref(t);\n    cuddCacheInsert2(manager, Cudd_bddXor, f, g, r);\n    return(r);\n\n} /* end of cuddBddXorRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Replaces variables with constants if possible.\n\n  @details This function performs part of the transformation to\n  standard form by replacing variables with constants if possible.\n\n  @sideeffect None\n\n  @see bddVarToCanonical bddVarToCanonicalSimple\n\n*/\nstatic void\nbddVarToConst(\n  DdNode * f,\n  DdNode ** gp,\n  DdNode ** hp,\n  DdNode * one)\n{\n    DdNode *g = *gp;\n    DdNode *h = *hp;\n\n    if (f == g) {    /* ITE(F,F,H) = ITE(F,1,H) = F + H */\n\t*gp = one;\n    } else if (f == Cudd_Not(g)) {    /* ITE(F,!F,H) = ITE(F,0,H) = !F * H */\n\t*gp = Cudd_Not(one);\n    }\n    if (f == h) {    /* ITE(F,G,F) = ITE(F,G,0) = F * G */\n\t*hp = Cudd_Not(one);\n    } else if (f == Cudd_Not(h)) {    /* ITE(F,G,!F) = ITE(F,G,1) = !F + G */\n\t*hp = one;\n    }\n\n} /* end of bddVarToConst */\n\n\n/**\n  @brief Picks unique member from equiv expressions.\n\n  @details Reduces 2 variable expressions to canonical form.\n\n  @sideeffect None\n\n  @see bddVarToConst bddVarToCanonicalSimple\n\n*/\nstatic int\nbddVarToCanonical(\n  DdManager * dd,\n  DdNode ** fp,\n  DdNode ** gp,\n  DdNode ** hp,\n  int * topfp,\n  int * topgp,\n  int * tophp)\n{\n    DdNode\t*F, *G, *H, *r, *f, *g, *h;\n    DdNode\t*one = dd->one;\n    int\t\ttopf, topg, toph;\n    int\t\tcomple, change;\n\n    f = *fp;\n    g = *gp;\n    h = *hp;\n    F = Cudd_Regular(f);\n    G = Cudd_Regular(g);\n    H = Cudd_Regular(h);\n    topf = cuddI(dd,F->index);\n    topg = cuddI(dd,G->index);\n    toph = cuddI(dd,H->index);\n\n    change = 0;\n\n    if (G == one) {\t\t\t/* ITE(F,c,H) */\n\tif ((topf > toph) || (topf == toph && f > h)) {\n\t    r = h;\n\t    h = f;\n\t    f = r;\t\t\t/* ITE(F,1,H) = ITE(H,1,F) */\n\t    if (g != one) {\t/* g == zero */\n\t\tf = Cudd_Not(f);\t\t/* ITE(F,0,H) = ITE(!H,0,!F) */\n\t\th = Cudd_Not(h);\n\t    }\n\t    change = 1;\n\t}\n    } else if (H == one) {\t\t/* ITE(F,G,c) */\n\tif ((topf > topg) || (topf == topg && f > g)) {\n\t    r = g;\n\t    g = f;\n\t    f = r;\t\t\t/* ITE(F,G,0) = ITE(G,F,0) */\n\t    if (h == one) {\n\t\tf = Cudd_Not(f);\t\t/* ITE(F,G,1) = ITE(!G,!F,1) */\n\t\tg = Cudd_Not(g);\n\t    }\n\t    change = 1;\n\t}\n    } else if (g == Cudd_Not(h)) {\t/* ITE(F,G,!G) = ITE(G,F,!F) */\n\tif ((topf > topg) || (topf == topg && f > g)) {\n\t    r = f;\n\t    f = g;\n\t    g = r;\n\t    h = Cudd_Not(r);\n\t    change = 1;\n\t}\n    }\n    /* adjust pointers so that the first 2 arguments to ITE are regular */\n    if (Cudd_IsComplement(f) != 0) {\t/* ITE(!F,G,H) = ITE(F,H,G) */\n\tf = Cudd_Not(f);\n\tr = g;\n\tg = h;\n\th = r;\n\tchange = 1;\n    }\n    comple = 0;\n    if (Cudd_IsComplement(g) != 0) {\t/* ITE(F,!G,H) = !ITE(F,G,!H) */\n\tg = Cudd_Not(g);\n\th = Cudd_Not(h);\n\tchange = 1;\n\tcomple = 1;\n    }\n    if (change != 0) {\n\t*fp = f;\n\t*gp = g;\n\t*hp = h;\n    }\n    *topfp = cuddI(dd,f->index);\n    *topgp = cuddI(dd,g->index);\n    *tophp = cuddI(dd,Cudd_Regular(h)->index);\n\n    return(comple);\n\n} /* end of bddVarToCanonical */\n\n\n/**\n  @brief Picks unique member from equiv expressions.\n\n  @details Makes sure the first two pointers are regular.  This\n  mat require the complementation of the result, which is signaled by\n  returning 1 instead of 0.  This function is simpler than the general\n  case because it assumes that no two arguments are the same or\n  complementary, and no argument is constant.\n\n  @sideeffect None\n\n  @see bddVarToConst bddVarToCanonical\n\n*/\nstatic int\nbddVarToCanonicalSimple(\n  DdManager * dd,\n  DdNode ** fp,\n  DdNode ** gp,\n  DdNode ** hp,\n  int * topfp,\n  int * topgp,\n  int * tophp)\n{\n    DdNode\t*r, *f, *g, *h;\n    int\t\tcomple, change;\n\n    f = *fp;\n    g = *gp;\n    h = *hp;\n\n    change = 0;\n\n    /* adjust pointers so that the first 2 arguments to ITE are regular */\n    if (Cudd_IsComplement(f)) {\t/* ITE(!F,G,H) = ITE(F,H,G) */\n\tf = Cudd_Not(f);\n\tr = g;\n\tg = h;\n\th = r;\n\tchange = 1;\n    }\n    comple = 0;\n    if (Cudd_IsComplement(g)) {\t/* ITE(F,!G,H) = !ITE(F,G,!H) */\n\tg = Cudd_Not(g);\n\th = Cudd_Not(h);\n\tchange = 1;\n\tcomple = 1;\n    }\n    if (change) {\n\t*fp = f;\n\t*gp = g;\n\t*hp = h;\n    }\n\n    /* Here we can skip the use of cuddI, because the operands are known\n    ** to be non-constant.\n    */\n    *topfp = dd->perm[f->index];\n    *topgp = dd->perm[g->index];\n    *tophp = dd->perm[Cudd_Regular(h)->index];\n\n    return(comple);\n\n} /* end of bddVarToCanonicalSimple */\n"
  },
  {
    "path": "cudd/cudd/cuddBridge.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Translation from %BDD to %ADD and vice versa and transfer\n  between different managers.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * addBddDoThreshold (DdManager *dd, DdNode *f, DdNode *val);\nstatic DdNode * addBddDoStrictThreshold (DdManager *dd, DdNode *f, DdNode *val);\nstatic DdNode * addBddDoInterval (DdManager *dd, DdNode *f, DdNode *l, DdNode *u);\nstatic DdNode * addBddDoIthBit (DdManager *dd, DdNode *f, DdNode *index);\nstatic DdNode * ddBddToAddRecur (DdManager *dd, DdNode *B);\nstatic DdNode * cuddBddTransferRecur (DdManager *ddS, DdManager *ddD, DdNode *f, st_table *table);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Converts an %ADD to a %BDD.\n\n  @details Replaces all discriminants greater than or equal to value\n  with 1, and all other discriminants with 0.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addBddInterval Cudd_addBddPattern Cudd_BddToAdd\n  Cudd_addBddStrictThreshold\n\n*/\nDdNode *\nCudd_addBddThreshold(\n  DdManager * dd,\n  DdNode * f,\n  CUDD_VALUE_TYPE  value)\n{\n    DdNode *res;\n    DdNode *val;\n    \n    val = cuddUniqueConst(dd,value);\n    if (val == NULL) return(NULL);\n    cuddRef(val);\n\n    do {\n\tdd->reordered = 0;\n\tres = addBddDoThreshold(dd, f, val);\n    } while (dd->reordered == 1);\n\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, val);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd, val);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_addBddThreshold */\n\n\n/**\n  @brief Converts an %ADD to a %BDD.\n\n  @details Replaces all discriminants STRICTLY greater than value with\n  1, and all other discriminants with 0.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addBddInterval Cudd_addBddPattern Cudd_BddToAdd \n  Cudd_addBddThreshold\n\n*/\nDdNode *\nCudd_addBddStrictThreshold(\n  DdManager * dd,\n  DdNode * f,\n  CUDD_VALUE_TYPE  value)\n{\n    DdNode *res;\n    DdNode *val;\n    \n    val = cuddUniqueConst(dd,value);\n    if (val == NULL) return(NULL);\n    cuddRef(val);\n\n    do {\n\tdd->reordered = 0;\n\tres = addBddDoStrictThreshold(dd, f, val);\n    } while (dd->reordered == 1);\n\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, val);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd, val);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_addBddStrictThreshold */\n\n\n/**\n  @brief Converts an %ADD to a %BDD.\n\n  @details Replaces all discriminants greater than or equal to lower\n  and less than or equal to upper with 1, and all other discriminants\n  with 0.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addBddThreshold Cudd_addBddStrictThreshold \n  Cudd_addBddPattern Cudd_BddToAdd\n\n*/\nDdNode *\nCudd_addBddInterval(\n  DdManager * dd,\n  DdNode * f,\n  CUDD_VALUE_TYPE  lower,\n  CUDD_VALUE_TYPE  upper)\n{\n    DdNode *res;\n    DdNode *l;\n    DdNode *u;\n    \n    /* Create constant nodes for the interval bounds, so that we can use\n    ** the global cache.\n    */\n    l = cuddUniqueConst(dd,lower);\n    if (l == NULL) return(NULL);\n    cuddRef(l);\n    u = cuddUniqueConst(dd,upper);\n    if (u == NULL) {\n\tCudd_RecursiveDeref(dd,l);\n\treturn(NULL);\n    }\n    cuddRef(u);\n\n    do {\n\tdd->reordered = 0;\n\tres = addBddDoInterval(dd, f, l, u);\n    } while (dd->reordered == 1);\n\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, l);\n\tCudd_RecursiveDeref(dd, u);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd, l);\n    Cudd_RecursiveDeref(dd, u);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_addBddInterval */\n\n\n/**\n  @brief Converts an %ADD to a %BDD by extracting the i-th bit from\n  the leaves.\n\n  @details Converts an %ADD to a %BDD by replacing all\n  discriminants whose i-th bit is equal to 1 with 1, and all other\n  discriminants with 0.  The i-th bit refers to the integer\n  representation of the leaf value.  If the value has a fractional\n  part, it is ignored.  Repeated calls to this procedure allow one to\n  transform an integer-valued %ADD into an array of BDDs, one for each\n  bit of the leaf values.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addBddInterval Cudd_addBddPattern Cudd_BddToAdd\n\n*/\nDdNode *\nCudd_addBddIthBit(\n  DdManager * dd,\n  DdNode * f,\n  int  bit)\n{\n    DdNode *res;\n    DdNode *index;\n    \n    index = cuddUniqueConst(dd,(CUDD_VALUE_TYPE) bit);\n    if (index == NULL) return(NULL);\n    cuddRef(index);\n\n    do {\n\tdd->reordered = 0;\n\tres = addBddDoIthBit(dd, f, index);\n    } while (dd->reordered == 1);\n\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, index);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd, index);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_addBddIthBit */\n\n\n/**\n  @brief Converts a %BDD to a 0-1 %ADD.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addBddPattern Cudd_addBddThreshold Cudd_addBddInterval\n  Cudd_addBddStrictThreshold\n\n*/\nDdNode *\nCudd_BddToAdd(\n  DdManager * dd,\n  DdNode * B)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = ddBddToAddRecur(dd, B);\n    } while (dd->reordered ==1);\n    return(res);\n\n} /* end of Cudd_BddToAdd */\n\n\n/**\n  @brief Converts an %ADD to a %BDD.\n\n  @details Replaces all discriminants different from 0 with 1.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_BddToAdd Cudd_addBddThreshold Cudd_addBddInterval\n  Cudd_addBddStrictThreshold\n\n*/\nDdNode *\nCudd_addBddPattern(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *res;\n    \n    do {\n\tdd->reordered = 0;\n\tres = cuddAddBddDoPattern(dd, f);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addBddPattern */\n\n\n/**\n  @brief Convert a %BDD from a manager to another one.\n\n  @details The orders of the variables in the two managers may be\n  different.\n\n  @return a pointer to the %BDD in the destination manager if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_bddTransfer(\n  DdManager * ddSource,\n  DdManager * ddDestination,\n  DdNode * f)\n{\n    DdNode *res;\n    do {\n\tddDestination->reordered = 0;\n\tres = cuddBddTransfer(ddSource, ddDestination, f);\n    } while (ddDestination->reordered == 1);\n    if (ddDestination->errorCode == CUDD_TIMEOUT_EXPIRED &&\n        ddDestination->timeoutHandler) {\n        ddDestination->timeoutHandler(ddDestination, ddDestination->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddTransfer */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Convert a %BDD from a manager to another one.\n\n  @return a pointer to the %BDD in the destination manager if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddTransfer\n\n*/\nDdNode *\ncuddBddTransfer(\n  DdManager * ddS,\n  DdManager * ddD,\n  DdNode * f)\n{\n    DdNode *res;\n    st_table *table = NULL;\n    st_generator *gen = NULL;\n    DdNode *key, *value;\n\n    table = st_init_table(st_ptrcmp,st_ptrhash);\n    if (table == NULL) goto failure;\n    res = cuddBddTransferRecur(ddS, ddD, f, table);\n    if (res != NULL) cuddRef(res);\n\n    /* Dereference all elements in the table and dispose of the table.\n    ** This must be done also if res is NULL to avoid leaks in case of\n    ** reordering. */\n    gen = st_init_gen(table);\n    if (gen == NULL) goto failure;\n    while (st_gen(gen, (void **) &key, (void **) &value)) {\n\tCudd_RecursiveDeref(ddD, value);\n    }\n    st_free_gen(gen); gen = NULL;\n    st_free_table(table); table = NULL;\n\n    if (res != NULL) cuddDeref(res);\n    return(res);\n\nfailure:\n    /* No need to free gen because it is always NULL here. */\n    if (table != NULL) st_free_table(table);\n    return(NULL);\n\n} /* end of cuddBddTransfer */\n\n\n/**\n  @brief Performs the recursive step for Cudd_addBddPattern.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddAddBddDoPattern(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *res, *T, *E;\n    DdNode *fv, *fvn;\n    unsigned int v;\n\n    statLine(dd);\n    /* Check terminal case. */\n    if (cuddIsConstant(f)) {\n\treturn(Cudd_NotCond(DD_ONE(dd),f == DD_ZERO(dd)));\n    }\n\n    /* Check cache. */\n    res = cuddCacheLookup1(dd,Cudd_addBddPattern,f);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    v = f->index;\n    fv = cuddT(f); fvn = cuddE(f);\n\n    T = cuddAddBddDoPattern(dd,fv);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = cuddAddBddDoPattern(dd,fvn);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    if (Cudd_IsComplement(T)) {\n\tres = (T == E) ? Cudd_Not(T) : cuddUniqueInter(dd,v,Cudd_Not(T),Cudd_Not(E));\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n\tres = Cudd_Not(res);\n    } else {\n\tres = (T == E) ? T : cuddUniqueInter(dd,v,T,E);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert1(dd,Cudd_addBddPattern,f,res);\n\n    return(res);\n\n} /* end of cuddAddBddDoPattern */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step for Cudd_addBddThreshold.\n\n  @return a pointer to the %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see addBddDoStrictThreshold\n\n*/\nstatic DdNode *\naddBddDoThreshold(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * val)\n{\n    DdNode *res, *T, *E;\n    DdNode *fv, *fvn;\n    unsigned int v;\n\n    statLine(dd);\n    /* Check terminal case. */\n    if (cuddIsConstant(f)) {\n\treturn(Cudd_NotCond(DD_ONE(dd),cuddV(f) < cuddV(val)));\n    }\n\n    /* Check cache. */\n    res = cuddCacheLookup2(dd,addBddDoThreshold,f,val);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    v = f->index;\n    fv = cuddT(f); fvn = cuddE(f);\n\n    T = addBddDoThreshold(dd,fv,val);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = addBddDoThreshold(dd,fvn,val);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    if (Cudd_IsComplement(T)) {\n\tres = (T == E) ? Cudd_Not(T) : cuddUniqueInter(dd,v,Cudd_Not(T),Cudd_Not(E));\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n\tres = Cudd_Not(res);\n    } else {\n\tres = (T == E) ? T : cuddUniqueInter(dd,v,T,E);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert2(dd,addBddDoThreshold,f,val,res);\n\n    return(res);\n\n} /* end of addBddDoThreshold */\n\n\n/**\n  @brief Performs the recursive step for Cudd_addBddStrictThreshold.\n\n  @return a pointer to the %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see addBddDoThreshold\n\n*/\nstatic DdNode *\naddBddDoStrictThreshold(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * val)\n{\n    DdNode *res, *T, *E;\n    DdNode *fv, *fvn;\n    unsigned int v;\n\n    statLine(dd);\n    /* Check terminal case. */\n    if (cuddIsConstant(f)) {\n\treturn(Cudd_NotCond(DD_ONE(dd),cuddV(f) <= cuddV(val)));\n    }\n\n    /* Check cache. */\n    res = cuddCacheLookup2(dd,addBddDoStrictThreshold,f,val);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    v = f->index;\n    fv = cuddT(f); fvn = cuddE(f);\n\n    T = addBddDoStrictThreshold(dd,fv,val);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = addBddDoStrictThreshold(dd,fvn,val);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    if (Cudd_IsComplement(T)) {\n\tres = (T == E) ? Cudd_Not(T) : cuddUniqueInter(dd,v,Cudd_Not(T),Cudd_Not(E));\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n\tres = Cudd_Not(res);\n    } else {\n\tres = (T == E) ? T : cuddUniqueInter(dd,v,T,E);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert2(dd,addBddDoStrictThreshold,f,val,res);\n\n    return(res);\n\n} /* end of addBddDoStrictThreshold */\n\n\n/**\n  @brief Performs the recursive step for Cudd_addBddInterval.\n\n  @return a pointer to the %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see addBddDoThreshold addBddDoStrictThreshold\n\n*/\nstatic DdNode *\naddBddDoInterval(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * l,\n  DdNode * u)\n{\n    DdNode *res, *T, *E;\n    DdNode *fv, *fvn;\n    unsigned int v;\n\n    statLine(dd);\n    /* Check terminal case. */\n    if (cuddIsConstant(f)) {\n\t// note: do check via !( f>=l && f<=u ) to correctly handle case of f being NaN (is always outside the interval)\n\treturn(Cudd_NotCond(DD_ONE(dd), !(cuddV(f) >= cuddV(l) && cuddV(f) <= cuddV(u))));\n    }\n\n    /* Check cache. */\n    res = cuddCacheLookup(dd,DD_ADD_BDD_DO_INTERVAL_TAG,f,l,u);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    v = f->index;\n    fv = cuddT(f); fvn = cuddE(f);\n\n    T = addBddDoInterval(dd,fv,l,u);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = addBddDoInterval(dd,fvn,l,u);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    if (Cudd_IsComplement(T)) {\n\tres = (T == E) ? Cudd_Not(T) : cuddUniqueInter(dd,v,Cudd_Not(T),Cudd_Not(E));\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n\tres = Cudd_Not(res);\n    } else {\n\tres = (T == E) ? T : cuddUniqueInter(dd,v,T,E);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert(dd,DD_ADD_BDD_DO_INTERVAL_TAG,f,l,u,res);\n\n    return(res);\n\n} /* end of addBddDoInterval */\n\n\n/**\n  @brief Performs the recursive step for Cudd_addBddIthBit.\n\n  @return a pointer to the %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\naddBddDoIthBit(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * index)\n{\n    DdNode *res, *T, *E;\n    DdNode *fv, *fvn;\n    int mask, value;\n    unsigned int v;\n\n    statLine(dd);\n    /* Check terminal case. */\n    if (cuddIsConstant(f)) {\n\tmask = 1 << ((int) cuddV(index));\n\tvalue = (int) cuddV(f);\n\treturn(Cudd_NotCond(DD_ONE(dd),(value & mask) == 0));\n    }\n\n    /* Check cache. */\n    res = cuddCacheLookup2(dd,addBddDoIthBit,f,index);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    v = f->index;\n    fv = cuddT(f); fvn = cuddE(f);\n\n    T = addBddDoIthBit(dd,fv,index);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = addBddDoIthBit(dd,fvn,index);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    if (Cudd_IsComplement(T)) {\n\tres = (T == E) ? Cudd_Not(T) : cuddUniqueInter(dd,v,Cudd_Not(T),Cudd_Not(E));\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n\tres = Cudd_Not(res);\n    } else {\n\tres = (T == E) ? T : cuddUniqueInter(dd,v,T,E);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    /* Store result. */\n    cuddCacheInsert2(dd,addBddDoIthBit,f,index,res);\n\n    return(res);\n\n} /* end of addBddDoIthBit */\n\n\n/**\n  @brief Performs the recursive step for Cudd_BddToAdd.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nddBddToAddRecur(\n  DdManager * dd,\n  DdNode * B)\n{\n    DdNode *one;\n    DdNode *res, *res1, *T, *E, *Bt, *Be;\n    int complement = 0;\n\n    statLine(dd);\n    one = DD_ONE(dd);\n\n    if (Cudd_IsConstantInt(B)) {\n\tif (B == one) {\n\t    res = one;\n\t} else {\n\t    res = DD_ZERO(dd);\n\t}\n\treturn(res);\n    }\n    /* Check visited table */\n    res = cuddCacheLookup1(dd,ddBddToAddRecur,B);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    if (Cudd_IsComplement(B)) {\n\tcomplement = 1;\n\tBt = cuddT(Cudd_Regular(B));\n\tBe = cuddE(Cudd_Regular(B));\n    } else {\n\tBt = cuddT(B);\n\tBe = cuddE(B);\n    }\n\n    T = ddBddToAddRecur(dd, Bt);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n\n    E = ddBddToAddRecur(dd, Be);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    /* No need to check for T == E, because it is guaranteed not to happen. */\n    res = cuddUniqueInter(dd, (int) Cudd_Regular(B)->index, T, E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd ,T);\n\tCudd_RecursiveDeref(dd ,E);\n\treturn(NULL);\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n\n    if (complement) {\n\tcuddRef(res);\n\tres1 = cuddAddCmplRecur(dd, res);\n\tif (res1 == NULL) {\n\t    Cudd_RecursiveDeref(dd, res);\n\t    return(NULL);\n\t}\n\tcuddRef(res1);\n\tCudd_RecursiveDeref(dd, res);\n\tres = res1;\n\tcuddDeref(res);\n    }\n\n    /* Store result. */\n    cuddCacheInsert1(dd,ddBddToAddRecur,B,res);\n\n    return(res);\n\n} /* end of ddBddToAddRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddTransfer.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddBddTransfer\n\n*/\nstatic DdNode *\ncuddBddTransferRecur(\n  DdManager * ddS,\n  DdManager * ddD,\n  DdNode * f,\n  st_table * table)\n{\n    DdNode *ft, *fe, *t, *e, *var, *res;\n    DdNode *one, *zero;\n    unsigned int index;\n    int comple = 0;\n\n    statLine(ddD);\n    one = DD_ONE(ddD);\n    comple = Cudd_IsComplement(f);\n\n    /* Trivial cases. */\n    if (Cudd_IsConstantInt(f)) return(Cudd_NotCond(one, comple));\n\n    /* Make canonical to increase the utilization of the cache. */\n    f = Cudd_NotCond(f,comple);\n    /* Now f is a regular pointer to a non-constant node. */\n\n    /* Check the cache. */\n    if (st_lookup(table, f, (void **) &res))\n\treturn(Cudd_NotCond(res,comple));\n    \n    /* Recursive step. */\n    index = f->index;\n    ft = cuddT(f); fe = cuddE(f);\n\n    t = cuddBddTransferRecur(ddS, ddD, ft, table);\n    if (t == NULL) {\n    \treturn(NULL);\n    }\n    cuddRef(t);\n\n    e = cuddBddTransferRecur(ddS, ddD, fe, table);\n    if (e == NULL) {\n    \tCudd_RecursiveDeref(ddD, t);\n    \treturn(NULL);\n    }\n    cuddRef(e);\n\n    zero = Cudd_Not(one);\n    var = cuddUniqueInter(ddD,index,one,zero);\n    if (var == NULL) {\n\tCudd_RecursiveDeref(ddD, t);\n\tCudd_RecursiveDeref(ddD, e);\n    \treturn(NULL);\n    }\n    res = cuddBddIteRecur(ddD,var,t,e);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(ddD, t);\n\tCudd_RecursiveDeref(ddD, e);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(ddD, t);\n    Cudd_RecursiveDeref(ddD, e);\n\n    if (st_add_direct(table, f, res) == ST_OUT_OF_MEM) {\n\tCudd_RecursiveDeref(ddD, res);\n\treturn(NULL);\n    }\n    return(Cudd_NotCond(res,comple));\n\n} /* end of cuddBddTransferRecur */\n\n"
  },
  {
    "path": "cudd/cudd/cuddCache.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for cache insertion and lookup.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#ifdef DD_CACHE_PROFILE\n#define DD_HYSTO_BINS 8\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Initializes the computed table.\n\n  @details It is called by Cudd_Init.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Init\n\n*/\nint\ncuddInitCache(\n  DdManager * unique /**< unique table */,\n  unsigned int cacheSize /**< initial size of the cache */,\n  unsigned int maxCacheSize /**< cache size beyond which no resizing occurs */)\n{\n    int i;\n    unsigned int logSize;\n#ifndef DD_CACHE_PROFILE\n    DdNodePtr *mem;\n    ptruint offset;\n#endif\n\n    /* Round cacheSize to largest power of 2 not greater than the requested\n    ** initial cache size. */\n    logSize = cuddComputeFloorLog2(ddMax(cacheSize,unique->slots/2));\n    cacheSize = 1U << logSize;\n    unique->acache = ALLOC(DdCache,cacheSize+1);\n    if (unique->acache == NULL) {\n\tunique->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    /* If the size of the cache entry is a power of 2, we want to\n    ** enforce alignment to that power of two. This happens when\n    ** DD_CACHE_PROFILE is not defined. */\n#ifdef DD_CACHE_PROFILE\n    unique->cache = unique->acache;\n    unique->memused += (cacheSize) * sizeof(DdCache);\n#else\n    mem = (DdNodePtr *) unique->acache;\n    offset = (ptruint) mem & (sizeof(DdCache) - 1);\n    mem += (sizeof(DdCache) - offset) / sizeof(DdNodePtr);\n    unique->cache = (DdCache *) mem;\n    assert(((ptruint) unique->cache & (sizeof(DdCache) - 1)) == 0);\n    unique->memused += (cacheSize+1) * sizeof(DdCache);\n#endif\n    unique->cacheSlots = cacheSize;\n    unique->cacheShift = sizeof(int) * 8 - logSize;\n    unique->maxCacheHard = maxCacheSize;\n    /* If cacheSlack is non-negative, we can resize. */\n    unique->cacheSlack = (int) ddMin(maxCacheSize,\n\tDD_MAX_CACHE_TO_SLOTS_RATIO*unique->slots) -\n\t2 * (int) cacheSize;\n    Cudd_SetMinHit(unique,DD_MIN_HIT);\n    /* Initialize to avoid division by 0 and immediate resizing. */\n    unique->cacheMisses = (double) (int) (cacheSize * unique->minHit + 1);\n    unique->cacheHits = 0;\n    unique->totCachehits = 0;\n    /* The sum of cacheMisses and totCacheMisses is always correct,\n    ** even though cacheMisses is larger than it should for the reasons\n    ** explained above. */\n    unique->totCacheMisses = -unique->cacheMisses;\n    unique->cachecollisions = 0;\n    unique->cacheinserts = 0;\n    unique->cacheLastInserts = 0;\n    unique->cachedeletions = 0;\n\n    /* Initialize the cache */\n    for (i = 0; (unsigned) i < cacheSize; i++) {\n\tunique->cache[i].h = 0; /* unused slots */\n\tunique->cache[i].data = NULL; /* invalid entry */\n#ifdef DD_CACHE_PROFILE\n\tunique->cache[i].count = 0;\n#endif\n    }\n\n    return(1);\n\n} /* end of cuddInitCache */\n\n\n/**\n  @brief Inserts a result in the cache for a function with three\n  operands.\n\n  @details The operator tag (see cuddInt.h for details) is split and\n  stored into unused bits of the first two pointers.\n\n  @sideeffect None\n\n  @see cuddCacheInsert2 cuddCacheInsert1\n\n*/\nvoid\ncuddCacheInsert(\n  DdManager * table,\n  ptruint op,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h,\n  DdNode * data)\n{\n    int posn;\n    DdCache *entry;\n    ptruint uf, ug, uh;\n\n    uf = (ptruint) f | (op & 0xe);\n    ug = (ptruint) g | (op >> 4);\n    uh = (ptruint) h;\n\n    posn = ddCHash2(uh,uf,ug,table->cacheShift);\n    entry = &table->cache[posn];\n\n    table->cachecollisions += entry->data != NULL;\n    table->cacheinserts++;\n\n    entry->f    = (DdNode *) uf;\n    entry->g    = (DdNode *) ug;\n    entry->h    = uh;\n    entry->data = data;\n#ifdef DD_CACHE_PROFILE\n    entry->count++;\n#endif\n\n} /* end of cuddCacheInsert */\n\n\n/**\n  @brief Inserts a result in the cache for a function with two\n  operands.\n\n  @sideeffect None\n\n  @see cuddCacheInsert cuddCacheInsert1\n\n*/\nvoid\ncuddCacheInsert2(\n  DdManager * table,\n  DD_CTFP op,\n  DdNode * f,\n  DdNode * g,\n  DdNode * data)\n{\n    int posn;\n    DdCache *entry;\n\n    posn = ddCHash2(op,f,g,table->cacheShift);\n    entry = &table->cache[posn];\n\n    if (entry->data != NULL) {\n\ttable->cachecollisions++;\n    }\n    table->cacheinserts++;\n\n    entry->f = f;\n    entry->g = g;\n    entry->h = (ptruint) op;\n    entry->data = data;\n#ifdef DD_CACHE_PROFILE\n    entry->count++;\n#endif\n\n} /* end of cuddCacheInsert2 */\n\n\n/**\n  @brief Inserts a result in the cache for a function with two\n  operands.\n\n  @sideeffect None\n\n  @see cuddCacheInsert cuddCacheInsert2\n\n*/\nvoid\ncuddCacheInsert1(\n  DdManager * table,\n  DD_CTFP1 op,\n  DdNode * f,\n  DdNode * data)\n{\n    int posn;\n    DdCache *entry;\n\n    posn = ddCHash2(op,f,f,table->cacheShift);\n    entry = &table->cache[posn];\n\n    if (entry->data != NULL) {\n\ttable->cachecollisions++;\n    }\n    table->cacheinserts++;\n\n    entry->f = f;\n    entry->g = f;\n    entry->h = (ptruint) op;\n    entry->data = data;\n#ifdef DD_CACHE_PROFILE\n    entry->count++;\n#endif\n\n} /* end of cuddCacheInsert1 */\n\n\n/**\n  @brief Looks up in the cache for the result of op applied to f,\n  g, and h.\n\n  @return the result if found; it returns NULL if no result is found.\n\n  @sideeffect None\n\n  @see cuddCacheLookup2 cuddCacheLookup1\n\n*/\nDdNode *\ncuddCacheLookup(\n  DdManager * table,\n  ptruint op,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    int posn;\n    DdCache *en,*cache;\n    DdNode *data;\n    ptruint uf, ug, uh;\n\n    uf = (ptruint) f | (op & 0xe);\n    ug = (ptruint) g | (op >> 4);\n    uh = (ptruint) h;\n\n    cache = table->cache;\n#ifdef DD_DEBUG\n    if (cache == NULL) {\n\treturn(NULL);\n    }\n#endif\n\n    posn = ddCHash2(uh,uf,ug,table->cacheShift);\n    en = &cache[posn];\n    if (en->data != NULL && en->f==(DdNodePtr)uf && en->g==(DdNodePtr)ug &&\n\ten->h==uh) {\n\tdata = Cudd_Regular(en->data);\n\ttable->cacheHits++;\n\tif (data->ref == 0) {\n\t    cuddReclaim(table,data);\n\t}\n\treturn(en->data);\n    }\n\n    /* Cache miss: decide whether to resize. */\n    table->cacheMisses++;\n\n    if (table->cacheSlack >= 0 &&\n\ttable->cacheHits > table->cacheMisses * table->minHit) {\n\tcuddCacheResize(table);\n    }\n\n    return(NULL);\n\n} /* end of cuddCacheLookup */\n\n\n/**\n  @brief Looks up in the cache for the result of op applied to f,\n  g, and h.\n\n  @return the result if found; it returns NULL if no result is found.\n\n  @sideeffect None\n\n  @see cuddCacheLookup2Zdd cuddCacheLookup1Zdd\n\n*/\nDdNode *\ncuddCacheLookupZdd(\n  DdManager * table,\n  ptruint op,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    int posn;\n    DdCache *en,*cache;\n    DdNode *data;\n    ptruint uf, ug, uh;\n\n    uf = (ptruint) f | (op & 0xe);\n    ug = (ptruint) g | (op >> 4);\n    uh = (ptruint) h;\n\n    cache = table->cache;\n#ifdef DD_DEBUG\n    if (cache == NULL) {\n\treturn(NULL);\n    }\n#endif\n\n    posn = ddCHash2(uh,uf,ug,table->cacheShift);\n    en = &cache[posn];\n    if (en->data != NULL && en->f==(DdNodePtr)uf && en->g==(DdNodePtr)ug &&\n\ten->h==uh) {\n\tdata = Cudd_Regular(en->data);\n\ttable->cacheHits++;\n\tif (data->ref == 0) {\n\t    cuddReclaimZdd(table,data);\n\t}\n\treturn(en->data);\n    }\n\n    /* Cache miss: decide whether to resize. */\n    table->cacheMisses++;\n\n    if (table->cacheSlack >= 0 &&\n\ttable->cacheHits > table->cacheMisses * table->minHit) {\n\tcuddCacheResize(table);\n    }\n\n    return(NULL);\n\n} /* end of cuddCacheLookupZdd */\n\n\n/**\n  @brief Looks up in the cache for the result of op applied to f\n  and g.\n\n  @return the result if found; it returns NULL if no result is found.\n\n  @sideeffect None\n\n  @see cuddCacheLookup cuddCacheLookup1\n\n*/\nDdNode *\ncuddCacheLookup2(\n  DdManager * table,\n  DD_CTFP op,\n  DdNode * f,\n  DdNode * g)\n{\n    int posn;\n    DdCache *en,*cache;\n    DdNode *data;\n\n    cache = table->cache;\n#ifdef DD_DEBUG\n    if (cache == NULL) {\n\treturn(NULL);\n    }\n#endif\n\n    posn = ddCHash2(op,f,g,table->cacheShift);\n    en = &cache[posn];\n    if (en->data != NULL && en->f==f && en->g==g && en->h==(ptruint)op) {\n\tdata = Cudd_Regular(en->data);\n\ttable->cacheHits++;\n\tif (data->ref == 0) {\n\t    cuddReclaim(table,data);\n\t}\n\treturn(en->data);\n    }\n\n    /* Cache miss: decide whether to resize. */\n    table->cacheMisses++;\n\n    if (table->cacheSlack >= 0 &&\n\ttable->cacheHits > table->cacheMisses * table->minHit) {\n\tcuddCacheResize(table);\n    }\n\n    return(NULL);\n\n} /* end of cuddCacheLookup2 */\n\n\n/**\n  @brief Looks up in the cache for the result of op applied to f.\n\n  @return the result if found; it returns NULL if no result is found.\n\n  @sideeffect None\n\n  @see cuddCacheLookup cuddCacheLookup2\n\n*/\nDdNode *\ncuddCacheLookup1(\n  DdManager * table,\n  DD_CTFP1 op,\n  DdNode * f)\n{\n    int posn;\n    DdCache *en,*cache;\n    DdNode *data;\n\n    cache = table->cache;\n#ifdef DD_DEBUG\n    if (cache == NULL) {\n\treturn(NULL);\n    }\n#endif\n\n    posn = ddCHash2(op,f,f,table->cacheShift);\n    en = &cache[posn];\n    if (en->data != NULL && en->f==f && en->h==(ptruint)op) {\n\tdata = Cudd_Regular(en->data);\n\ttable->cacheHits++;\n\tif (data->ref == 0) {\n\t    cuddReclaim(table,data);\n\t}\n\treturn(en->data);\n    }\n\n    /* Cache miss: decide whether to resize. */\n    table->cacheMisses++;\n\n    if (table->cacheSlack >= 0 &&\n\ttable->cacheHits > table->cacheMisses * table->minHit) {\n\tcuddCacheResize(table);\n    }\n\n    return(NULL);\n\n} /* end of cuddCacheLookup1 */\n\n\n/**\n  @brief Looks up in the cache for the result of op applied to f\n  and g.\n\n  @return the result if found; it returns NULL if no result is found.\n\n  @sideeffect None\n\n  @see cuddCacheLookupZdd cuddCacheLookup1Zdd\n\n*/\nDdNode *\ncuddCacheLookup2Zdd(\n  DdManager * table,\n  DD_CTFP op,\n  DdNode * f,\n  DdNode * g)\n{\n    int posn;\n    DdCache *en,*cache;\n    DdNode *data;\n\n    cache = table->cache;\n#ifdef DD_DEBUG\n    if (cache == NULL) {\n\treturn(NULL);\n    }\n#endif\n\n    posn = ddCHash2(op,f,g,table->cacheShift);\n    en = &cache[posn];\n    if (en->data != NULL && en->f==f && en->g==g && en->h==(ptruint)op) {\n\tdata = Cudd_Regular(en->data);\n\ttable->cacheHits++;\n\tif (data->ref == 0) {\n\t    cuddReclaimZdd(table,data);\n\t}\n\treturn(en->data);\n    }\n\n    /* Cache miss: decide whether to resize. */\n    table->cacheMisses++;\n\n    if (table->cacheSlack >= 0 &&\n\ttable->cacheHits > table->cacheMisses * table->minHit) {\n\tcuddCacheResize(table);\n    }\n\n    return(NULL);\n\n} /* end of cuddCacheLookup2Zdd */\n\n\n/**\n  @brief Looks up in the cache for the result of op applied to f.\n\n  @return the result if found; it returns NULL if no result is found.\n\n  @sideeffect None\n\n  @see cuddCacheLookupZdd cuddCacheLookup2Zdd\n\n*/\nDdNode *\ncuddCacheLookup1Zdd(\n  DdManager * table,\n  DD_CTFP1 op,\n  DdNode * f)\n{\n    int posn;\n    DdCache *en,*cache;\n    DdNode *data;\n\n    cache = table->cache;\n#ifdef DD_DEBUG\n    if (cache == NULL) {\n\treturn(NULL);\n    }\n#endif\n\n    posn = ddCHash2(op,f,f,table->cacheShift);\n    en = &cache[posn];\n    if (en->data != NULL && en->f==f && en->h==(ptruint)op) {\n\tdata = Cudd_Regular(en->data);\n\ttable->cacheHits++;\n\tif (data->ref == 0) {\n\t    cuddReclaimZdd(table,data);\n\t}\n\treturn(en->data);\n    }\n\n    /* Cache miss: decide whether to resize. */\n    table->cacheMisses++;\n\n    if (table->cacheSlack >= 0  &&\n\ttable->cacheHits > table->cacheMisses * table->minHit) {\n\tcuddCacheResize(table);\n    }\n\n    return(NULL);\n\n} /* end of cuddCacheLookup1Zdd */\n\n\n/**\n  @brief Looks up in the cache for the result of op applied to f,\n  g, and h.\n\n  @details Assumes that the calling procedure (e.g.,\n  Cudd_bddIteConstant) is only interested in whether the result is\n  constant or not.\n\n  @return the result if found (possibly DD_NON_CONSTANT); otherwise it\n  returns NULL.\n\n  @sideeffect None\n\n  @see cuddCacheLookup\n\n*/\nDdNode *\ncuddConstantLookup(\n  DdManager * table,\n  ptruint op,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    int posn;\n    DdCache *en,*cache;\n    ptruint uf, ug, uh;\n\n    uf = (ptruint) f | (op & 0xe);\n    ug = (ptruint) g | (op >> 4);\n    uh = (ptruint) h;\n\n    cache = table->cache;\n#ifdef DD_DEBUG\n    if (cache == NULL) {\n\treturn(NULL);\n    }\n#endif\n    posn = ddCHash2(uh,uf,ug,table->cacheShift);\n    en = &cache[posn];\n\n    /* We do not reclaim here because the result should not be\n     * referenced, but only tested for being a constant.\n     */\n    if (en->data != NULL &&\n\ten->f == (DdNodePtr)uf && en->g == (DdNodePtr)ug && en->h == uh) {\n\ttable->cacheHits++;\n\treturn(en->data);\n    }\n\n    /* Cache miss: decide whether to resize. */\n    table->cacheMisses++;\n\n    if (table->cacheSlack >= 0 &&\n\ttable->cacheHits > table->cacheMisses * table->minHit) {\n\tcuddCacheResize(table);\n    }\n\n    return(NULL);\n\n} /* end of cuddConstantLookup */\n\n\n/**\n  @brief Computes and prints a profile of the cache usage.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddCacheProfile(\n  DdManager * table,\n  FILE * fp)\n{\n    DdCache *cache = table->cache;\n    int slots = table->cacheSlots;\n    int nzeroes = 0;\n    int i, retval;\n    double exUsed;\n\n#ifdef DD_CACHE_PROFILE\n    double count, mean, meansq, stddev, expected;\n    long max, min;\n    int imax, imin;\n    double *hystogramQ, *hystogramR; /* histograms by quotient and remainder */\n    int nbins = DD_HYSTO_BINS;\n    int bin;\n    long thiscount;\n    double totalcount, exStddev;\n\n    meansq = mean = expected = 0.0;\n    max = min = (long) cache[0].count;\n    imax = imin = 0;\n    totalcount = 0.0;\n\n    hystogramQ = ALLOC(double, nbins);\n    if (hystogramQ == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    hystogramR = ALLOC(double, nbins);\n    if (hystogramR == NULL) {\n\tFREE(hystogramQ);\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (i = 0; i < nbins; i++) {\n\thystogramQ[i] = 0;\n\thystogramR[i] = 0;\n    }\n\n    for (i = 0; i < slots; i++) {\n\tthiscount = (long) cache[i].count;\n\tif (thiscount > max) {\n\t    max = thiscount;\n\t    imax = i;\n\t}\n\tif (thiscount < min) {\n\t    min = thiscount;\n\t    imin = i;\n\t}\n\tif (thiscount == 0) {\n\t    nzeroes++;\n\t}\n\tcount = (double) thiscount;\n\tmean += count;\n\tmeansq += count * count;\n\ttotalcount += count;\n\texpected += count * (double) i;\n\tbin = (i * nbins) / slots;\n\thystogramQ[bin] += (double) thiscount;\n\tbin = i % nbins;\n\thystogramR[bin] += (double) thiscount;\n    }\n    mean /= (double) slots;\n    meansq /= (double) slots;\n\n    /* Compute the standard deviation from both the data and the\n    ** theoretical model for a random distribution. */\n    stddev = sqrt(meansq - mean*mean);\n    exStddev = sqrt((1 - 1/(double) slots) * totalcount / (double) slots);\n\n    retval = fprintf(fp,\"Cache average accesses = %g\\n\",  mean);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Cache access standard deviation = %g \", stddev);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"(expected = %g)\\n\", exStddev);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Cache max accesses = %ld for slot %d\\n\", max, imax);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Cache min accesses = %ld for slot %d\\n\", min, imin);\n    if (retval == EOF) return(0);\n    exUsed = 100.0 * (1.0 - exp(-totalcount / (double) slots));\n    retval = fprintf(fp,\"Cache used slots = %.2f%% (expected %.2f%%)\\n\",\n\t\t     100.0 - (double) nzeroes * 100.0 / (double) slots,\n\t\t     exUsed);\n    if (retval == EOF) return(0);\n\n    if (totalcount > 0) {\n\texpected /= totalcount;\n\tretval = fprintf(fp,\"Cache access hystogram for %d bins\", nbins);\n\tif (retval == EOF) return(0);\n\tretval = fprintf(fp,\" (expected bin value = %g)\\nBy quotient:\",\n\t\t\t expected);\n\tif (retval == EOF) return(0);\n\tfor (i = nbins - 1; i>=0; i--) {\n\t    retval = fprintf(fp,\" %.0f\", hystogramQ[i]);\n\t    if (retval == EOF) return(0);\n\t}\n\tretval = fprintf(fp,\"\\nBy residue: \");\n\tif (retval == EOF) return(0);\n\tfor (i = nbins - 1; i>=0; i--) {\n\t    retval = fprintf(fp,\" %.0f\", hystogramR[i]);\n\t    if (retval == EOF) return(0);\n\t}\n\tretval = fprintf(fp,\"\\n\");\n\tif (retval == EOF) return(0);\n    }\n\n    FREE(hystogramQ);\n    FREE(hystogramR);\n#else\n    for (i = 0; i < slots; i++) {\n\tnzeroes += cache[i].h == 0;\n    }\n    exUsed = 100.0 *\n\t(1.0 - exp(-(table->cacheinserts - table->cacheLastInserts) /\n\t\t   (double) slots));\n    retval = fprintf(fp,\"Cache used slots = %.2f%% (expected %.2f%%)\\n\",\n\t\t     100.0 - (double) nzeroes * 100.0 / (double) slots,\n\t\t     exUsed);\n    if (retval == EOF) return(0);\n#endif\n    return(1);\n\n} /* end of cuddCacheProfile */\n\n\n/**\n  @brief Resizes the cache.\n\n  @sideeffect None\n\n*/\nvoid\ncuddCacheResize(\n  DdManager * table)\n{\n    DdCache *cache, *oldcache, *oldacache, *entry, *old;\n    int i;\n    int posn, shift;\n    unsigned int slots, oldslots;\n    double offset;\n    int moved = 0;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n#ifndef DD_CACHE_PROFILE\n    ptruint misalignment;\n    DdNodePtr *mem;\n#endif\n\n    oldcache = table->cache;\n    oldacache = table->acache;\n    oldslots = table->cacheSlots;\n    slots = table->cacheSlots = oldslots << 1;\n\n#ifdef DD_VERBOSE\n    (void) fprintf(table->err,\"Resizing the cache from %d to %d entries\\n\",\n\t\t   oldslots, slots);\n    (void) fprintf(table->err,\n\t\t   \"\\thits = %g\\tmisses = %g\\thit ratio = %5.3f\\n\",\n\t\t   table->cacheHits, table->cacheMisses,\n\t\t   table->cacheHits / (table->cacheHits + table->cacheMisses));\n#endif\n\n    saveHandler = MMoutOfMemory;\n    MMoutOfMemory = table->outOfMemCallback;\n    table->acache = cache = ALLOC(DdCache,slots+1);\n    MMoutOfMemory = saveHandler;\n    /* If we fail to allocate the new table we just give up. */\n    if (cache == NULL) {\n#ifdef DD_VERBOSE\n\t(void) fprintf(table->err,\"Resizing failed. Giving up.\\n\");\n#endif\n\ttable->cacheSlots = oldslots;\n\ttable->acache = oldacache;\n\t/* Do not try to resize again. */\n\ttable->maxCacheHard = oldslots - 1;\n\ttable->cacheSlack = - (int) (oldslots + 1);\n\treturn;\n    }\n    /* If the size of the cache entry is a power of 2, we want to\n    ** enforce alignment to that power of two. This happens when\n    ** DD_CACHE_PROFILE is not defined. */\n#ifdef DD_CACHE_PROFILE\n    table->cache = cache;\n#else\n    mem = (DdNodePtr *) cache;\n    misalignment = (ptruint) mem & (sizeof(DdCache) - 1);\n    mem += (sizeof(DdCache) - misalignment) / sizeof(DdNodePtr);\n    table->cache = cache = (DdCache *) mem;\n    assert(((ptruint) table->cache & (sizeof(DdCache) - 1)) == 0);\n#endif\n    shift = --(table->cacheShift);\n    table->memused += (slots - oldslots) * sizeof(DdCache);\n    table->cacheSlack -= slots; /* need these many slots to double again */\n\n    /* Clear new cache. */\n    for (i = 0; (unsigned) i < slots; i++) {\n\tcache[i].data = NULL;\n\tcache[i].h = 0;\n#ifdef DD_CACHE_PROFILE\n\tcache[i].count = 0;\n#endif\n    }\n\n    /* Copy from old cache to new one. */\n    for (i = 0; (unsigned) i < oldslots; i++) {\n\told = &oldcache[i];\n\tif (old->data != NULL) {\n\t    posn = ddCHash2(old->h,old->f,old->g,shift);\n\t    entry = &cache[posn];\n\t    entry->f = old->f;\n\t    entry->g = old->g;\n\t    entry->h = old->h;\n\t    entry->data = old->data;\n#ifdef DD_CACHE_PROFILE\n\t    entry->count = 1;\n#endif\n\t    moved++;\n\t}\n    }\n\n    FREE(oldacache);\n\n    /* Reinitialize measurements so as to avoid division by 0 and\n    ** immediate resizing.\n    */\n    offset = (double) (int) (slots * table->minHit + 1);\n    table->totCacheMisses += table->cacheMisses - offset;\n    table->cacheMisses = offset;\n    table->totCachehits += table->cacheHits;\n    table->cacheHits = 0;\n    table->cacheLastInserts = table->cacheinserts - (double) moved;\n\n} /* end of cuddCacheResize */\n\n\n/**\n  @brief Flushes the cache.\n\n  @sideeffect None\n\n*/\nvoid\ncuddCacheFlush(\n  DdManager * table)\n{\n    int i, slots;\n    DdCache *cache;\n\n    slots = table->cacheSlots;\n    cache = table->cache;\n    for (i = 0; i < slots; i++) {\n\ttable->cachedeletions += cache[i].data != NULL;\n\tcache[i].data = NULL;\n    }\n    table->cacheLastInserts = table->cacheinserts;\n\n    return;\n\n} /* end of cuddCacheFlush */\n\n\n/**\n  @brief Returns the floor of the logarithm to the base 2.\n\n  @details The input value is assumed to be greater than 0.\n\n  @sideeffect None\n\n*/\nint\ncuddComputeFloorLog2(\n  unsigned int value)\n{\n    int floorLog = 0;\n#ifdef DD_DEBUG\n    assert(value > 0);\n#endif\n    while (value > 1) {\n\tfloorLog++;\n\tvalue >>= 1;\n    }\n    return(floorLog);\n\n} /* end of cuddComputeFloorLog2 */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n"
  },
  {
    "path": "cudd/cudd/cuddCheck.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions to check consistency of data structures.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void debugFindParent (DdManager *table, DdNode *node);\n#if 0\nstatic void debugCheckParent (DdManager *table, DdNode *node);\n#endif\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Checks for inconsistencies in the %DD heap.\n\n  @details The following inconsistencies are checked:\n  <ul>\n  <li> node has illegal index\n  <li> live node has dead children\n  <li> node has illegal Then or Else pointers\n  <li> %BDD/%ADD node has identical children\n  <li> %ZDD node has zero then child\n  <li> wrong number of total nodes\n  <li> wrong number of dead nodes\n  <li> ref count error at node\n  </ul>\n  \n  @return 0 if no inconsistencies are found; DD_OUT_OF_MEM if there is\n  not enough memory; 1 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_CheckKeys\n\n*/\nint\nCudd_DebugCheck(\n  DdManager * table)\n{\n    unsigned int i;\n    int\t\tj,count;\n    int\t\tslots;\n    DdNodePtr\t*nodelist;\n    DdNode\t*f;\n    DdNode\t*sentinel = &(table->sentinel);\n    st_table\t*edgeTable;\t/* stores internal ref count for each node */\n    st_generator\t*gen;\n    int\t\tflag = 0;\n    int\t\ttotalNode;\n    int\t\tdeadNode;\n    int\t\tindex;\n    int         shift;\n\n    edgeTable = st_init_table(st_ptrcmp,st_ptrhash);\n    if (edgeTable == NULL) return(CUDD_OUT_OF_MEM);\n\n    /* Check the BDD/ADD subtables. */\n    for (i = 0; i < (unsigned) table->size; i++) {\n\tindex = table->invperm[i];\n\tif (i != (unsigned) table->perm[index]) {\n\t    (void) fprintf(table->err,\n\t\t\t   \"Permutation corrupted: invperm[%u] = %d\\t perm[%d] = %d\\n\",\n\t\t\t   i, index, index, table->perm[index]);\n\t}\n\tnodelist = table->subtables[i].nodelist;\n\tslots = table->subtables[i].slots;\n\tshift = table->subtables[i].shift;\n\n\ttotalNode = 0;\n\tdeadNode = 0;\n\tfor (j = 0; j < slots; j++) {\t/* for each subtable slot */\n\t    f = nodelist[j];\n\t    while (f != sentinel) {\n\t\ttotalNode++;\n\t\tif (cuddT(f) != NULL && cuddE(f) != NULL && f->ref != 0) {\n\t\t    if ((int) f->index != index) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: node has illegal index\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag = 1;\n\t\t    }\n\t\t    if ((unsigned) cuddI(table,cuddT(f)->index) <= i ||\n\t\t\t(unsigned) cuddI(table,Cudd_Regular(cuddE(f))->index)\n\t\t\t<= i) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: node has illegal children\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag = 1;\n\t\t    }\n\t\t    if (Cudd_Regular(cuddT(f)) != cuddT(f)) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: node has illegal form\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag = 1;\n\t\t    }\n\t\t    if (cuddT(f) == cuddE(f)) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: node has identical children\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag = 1;\n\t\t    }\n\t\t    if (cuddT(f)->ref == 0 || Cudd_Regular(cuddE(f))->ref == 0) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: live node has dead children\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag =1;\n\t\t    }\n                    if (ddHash(cuddT(f),cuddE(f),shift) != (unsigned) j) {\n                        (void) fprintf(table->err, \"Error: misplaced node\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag =1;\n                    }\n\t\t    /* Increment the internal reference count for the\n\t\t    ** then child of the current node.\n\t\t    */\n\t\t    if (st_lookup_int(edgeTable,cuddT(f),&count)) {\n\t\t\tcount++;\n\t\t    } else {\n\t\t\tcount = 1;\n\t\t    }\n\t\t    if (st_insert(edgeTable,cuddT(f),\n\t\t    (void *)(ptruint)count) == ST_OUT_OF_MEM) {\n\t\t\tst_free_table(edgeTable);\n\t\t\treturn(CUDD_OUT_OF_MEM);\n\t\t    }\n\n\t\t    /* Increment the internal reference count for the\n\t\t    ** else child of the current node.\n\t\t    */\n\t\t    if (st_lookup_int(edgeTable,Cudd_Regular(cuddE(f)),\n\t\t\t\t      &count)) {\n\t\t\tcount++;\n\t\t    } else {\n\t\t\tcount = 1;\n\t\t    }\n\t\t    if (st_insert(edgeTable,Cudd_Regular(cuddE(f)),\n\t\t    (void *)(ptruint)count) == ST_OUT_OF_MEM) {\n\t\t\tst_free_table(edgeTable);\n\t\t\treturn(CUDD_OUT_OF_MEM);\n\t\t    }\n\t\t} else if (cuddT(f) != NULL && cuddE(f) != NULL && f->ref == 0) {\n\t\t    deadNode++;\n#if 0\n\t\t    debugCheckParent(table,f);\n#endif\n\t\t} else {\n\t\t    fprintf(table->err,\n\t\t\t    \"Error: node has illegal Then or Else pointers\\n\");\n\t\t    cuddPrintNode(f,table->err);\n\t\t    flag = 1;\n\t\t}\n\n\t\tf = f->next;\n\t    }\t/* for each element of the collision list */\n\t}\t/* for each subtable slot */\n\n\tif ((unsigned) totalNode != table->subtables[i].keys) {\n\t    fprintf(table->err,\"Error: wrong number of total nodes\\n\");\n\t    flag = 1;\n\t}\n\tif ((unsigned) deadNode != table->subtables[i].dead) {\n\t    fprintf(table->err,\"Error: wrong number of dead nodes\\n\");\n\t    flag = 1;\n\t}\n    }\t/* for each BDD/ADD subtable */\n\n    /* Check the ZDD subtables. */\n    for (i = 0; i < (unsigned) table->sizeZ; i++) {\n\tindex = table->invpermZ[i];\n\tif (i != (unsigned) table->permZ[index]) {\n\t    (void) fprintf(table->err,\n\t\t\t   \"Permutation corrupted: invpermZ[%u] = %d\\t permZ[%d] = %d in ZDD\\n\",\n\t\t\t   i, index, index, table->permZ[index]);\n\t}\n\tnodelist = table->subtableZ[i].nodelist;\n\tslots = table->subtableZ[i].slots;\n\n\ttotalNode = 0;\n\tdeadNode = 0;\n\tfor (j = 0; j < slots; j++) {\t/* for each subtable slot */\n\t    f = nodelist[j];\n\t    while (f != NULL) {\n\t\ttotalNode++;\n\t\tif (cuddT(f) != NULL && cuddE(f) != NULL && f->ref != 0) {\n\t\t    if ((int) f->index != index) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: ZDD node has illegal index\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag = 1;\n\t\t    }\n\t\t    if (Cudd_IsComplement(cuddT(f)) ||\n\t\t\tCudd_IsComplement(cuddE(f))) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: ZDD node has complemented children\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag = 1;\n\t\t    }\n\t\t    if ((unsigned) cuddIZ(table,cuddT(f)->index) <= i ||\n\t\t    (unsigned) cuddIZ(table,cuddE(f)->index) <= i) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: ZDD node has illegal children\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tcuddPrintNode(cuddT(f),table->err);\n\t\t\tcuddPrintNode(cuddE(f),table->err);\n\t\t\tflag = 1;\n\t\t    }\n\t\t    if (cuddT(f) == DD_ZERO(table)) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: ZDD node has zero then child\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag = 1;\n\t\t    }\n\t\t    if (cuddT(f)->ref == 0 || cuddE(f)->ref == 0) {\n\t\t\t(void) fprintf(table->err,\n\t\t\t\t       \"Error: ZDD live node has dead children\\n\");\n\t\t\tcuddPrintNode(f,table->err);\n\t\t\tflag =1;\n\t\t    }\n\t\t    /* Increment the internal reference count for the\n\t\t    ** then child of the current node.\n\t\t    */\n\t\t    if (st_lookup_int(edgeTable,cuddT(f),&count)) {\n\t\t\tcount++;\n\t\t    } else {\n\t\t\tcount = 1;\n\t\t    }\n\t\t    if (st_insert(edgeTable,cuddT(f),\n\t\t    (void *)(ptruint)count) == ST_OUT_OF_MEM) {\n\t\t\tst_free_table(edgeTable);\n\t\t\treturn(CUDD_OUT_OF_MEM);\n\t\t    }\n\n\t\t    /* Increment the internal reference count for the\n\t\t    ** else child of the current node.\n\t\t    */\n\t\t    if (st_lookup_int(edgeTable,cuddE(f),&count)) {\n\t\t\tcount++;\n\t\t    } else {\n\t\t\tcount = 1;\n\t\t    }\n\t\t    if (st_insert(edgeTable,cuddE(f),\n\t\t    (void *)(ptruint)count) == ST_OUT_OF_MEM) {\n\t\t\tst_free_table(edgeTable);\n\t\t\ttable->errorCode = CUDD_MEMORY_OUT;\n\t\t\treturn(CUDD_OUT_OF_MEM);\n\t\t    }\n\t\t} else if (cuddT(f) != NULL && cuddE(f) != NULL && f->ref == 0) {\n\t\t    deadNode++;\n#if 0\n\t\t    debugCheckParent(table,f);\n#endif\n\t\t} else {\n\t\t    fprintf(table->err,\n\t\t\t    \"Error: ZDD node has illegal Then or Else pointers\\n\");\n\t\t    cuddPrintNode(f,table->err);\n\t\t    flag = 1;\n\t\t}\n\n\t\tf = f->next;\n\t    }\t/* for each element of the collision list */\n\t}\t/* for each subtable slot */\n\n\tif ((unsigned) totalNode != table->subtableZ[i].keys) {\n\t    fprintf(table->err,\n\t\t    \"Error: wrong number of total nodes in ZDD\\n\");\n\t    flag = 1;\n\t}\n\tif ((unsigned) deadNode != table->subtableZ[i].dead) {\n\t    fprintf(table->err,\n\t\t    \"Error: wrong number of dead nodes in ZDD\\n\");\n\t    flag = 1;\n\t}\n    }\t/* for each ZDD subtable */\n\n    /* Check the constant table. */\n    nodelist = table->constants.nodelist;\n    slots = table->constants.slots;\n\n    totalNode = 0;\n    deadNode = 0;\n    for (j = 0; j < slots; j++) {\n\tf = nodelist[j];\n\twhile (f != NULL) {\n\t    totalNode++;\n\t    if (f->ref != 0) {\n\t\tif (f->index != CUDD_CONST_INDEX) {\n\t\t    fprintf(table->err,\"Error: node has illegal index\\n\");\n\t\t    fprintf(table->err,\n\t\t\t    \"       node 0x%\" PRIxPTR \", id = %u, ref = %u, value = %g\\n\",\n\t\t\t    (ptruint)f,f->index,f->ref,cuddV(f));\n\t\t    flag = 1;\n\t\t}\n\t    } else {\n\t\tdeadNode++;\n\t    }\n\t    f = f->next;\n\t}\n    }\n    if ((unsigned) totalNode != table->constants.keys) {\n\t(void) fprintf(table->err,\n\t\t       \"Error: wrong number of total nodes in constants\\n\");\n\tflag = 1;\n    }\n    if ((unsigned) deadNode != table->constants.dead) {\n\t(void) fprintf(table->err,\n\t\t       \"Error: wrong number of dead nodes in constants\\n\");\n\tflag = 1;\n    }\n    gen = st_init_gen(edgeTable);\n    while (st_gen_int(gen, (void **) &f, &count)) {\n\tif (count > (int)(f->ref) && f->ref != DD_MAXREF) {\n\t    fprintf(table->err,\"ref count error at node 0x%\" PRIxPTR \", count = %d, id = %u, ref = %u, then = 0x%\" PRIxPTR \", else = 0x%\" PRIxPTR \"\\n\",\n                (ptruint)f,count,f->index,f->ref,(ptruint)cuddT(f),(ptruint)cuddE(f));\n\t    debugFindParent(table,f);\n\t    flag = 1;\n\t}\n    }\n    st_free_gen(gen);\n    st_free_table(edgeTable);\n\n    return (flag);\n\n} /* end of Cudd_DebugCheck */\n\n\n/**\n  @brief Checks for several conditions that should not occur.\n\n  @details Checks for the following conditions:\n  <ul>\n  <li>Wrong sizes of subtables.\n  <li>Wrong number of keys found in unique subtable.\n  <li>Wrong number of dead found in unique subtable.\n  <li>Wrong number of keys found in the constant table\n  <li>Wrong number of dead found in the constant table\n  <li>Wrong number of total slots found\n  <li>Wrong number of maximum keys found\n  <li>Wrong number of total dead found\n  </ul>\n  Reports the average length of non-empty lists.\n\n  @return the number of subtables for which the number of keys is\n  wrong.\n\n  @sideeffect None\n\n  @see Cudd_DebugCheck\n\n*/\nint\nCudd_CheckKeys(\n  DdManager * table)\n{\n    int size;\n    int i,j;\n    DdNodePtr *nodelist;\n    DdNode *node;\n    DdNode *sentinel = &(table->sentinel);\n    DdSubtable *subtable;\n    int keys;\n    int dead;\n    int count = 0;\n    int totalKeys = 0;\n    int totalSlots = 0;\n    int totalDead = 0;\n    int nonEmpty = 0;\n    unsigned int slots;\n    int logSlots;\n    int shift;\n\n    size = table->size;\n\n    for (i = 0; i < size; i++) {\n\tsubtable = &(table->subtables[i]);\n\tnodelist = subtable->nodelist;\n\tkeys = subtable->keys;\n\tdead = subtable->dead;\n\ttotalKeys += keys;\n\tslots = subtable->slots;\n\tshift = subtable->shift;\n\tlogSlots = sizeof(int) * 8 - shift;\n\tif (((slots >> logSlots) << logSlots) != slots) {\n\t    (void) fprintf(table->err,\n\t\t\t   \"Unique table %d is not the right power of 2\\n\", i);\n\t    (void) fprintf(table->err,\n\t\t\t   \"    slots = %u shift = %d\\n\", slots, shift);\n\t}\n\ttotalSlots += slots;\n\ttotalDead += dead;\n\tfor (j = 0; (unsigned) j < slots; j++) {\n\t    node = nodelist[j];\n\t    if (node != sentinel) {\n\t\tnonEmpty++;\n\t    }\n\t    while (node != sentinel) {\n\t\tkeys--;\n\t\tif (node->ref == 0) {\n\t\t    dead--;\n\t\t}\n\t\tnode = node->next;\n\t    }\n\t}\n\tif (keys != 0) {\n\t    (void) fprintf(table->err, \"Wrong number of keys found \\\nin unique table %d (difference=%d)\\n\", i, keys);\n\t    count++;\n\t}\n\tif (dead != 0) {\n\t    (void) fprintf(table->err, \"Wrong number of dead found \\\nin unique table no. %d (difference=%d)\\n\", i, dead);\n\t}\n    }\t/* for each BDD/ADD subtable */\n\n    /* Check the ZDD subtables. */\n    size = table->sizeZ;\n\n    for (i = 0; i < size; i++) {\n\tsubtable = &(table->subtableZ[i]);\n\tnodelist = subtable->nodelist;\n\tkeys = subtable->keys;\n\tdead = subtable->dead;\n\ttotalKeys += keys;\n\ttotalSlots += subtable->slots;\n\ttotalDead += dead;\n\tfor (j = 0; (unsigned) j < subtable->slots; j++) {\n\t    node = nodelist[j];\n\t    if (node != NULL) {\n\t\tnonEmpty++;\n\t    }\n\t    while (node != NULL) {\n\t\tkeys--;\n\t\tif (node->ref == 0) {\n\t\t    dead--;\n\t\t}\n\t\tnode = node->next;\n\t    }\n\t}\n\tif (keys != 0) {\n\t    (void) fprintf(table->err, \"Wrong number of keys found \\\nin ZDD unique table no. %d (difference=%d)\\n\", i, keys);\n\t    count++;\n\t}\n\tif (dead != 0) {\n\t    (void) fprintf(table->err, \"Wrong number of dead found \\\nin ZDD unique table no. %d (difference=%d)\\n\", i, dead);\n\t}\n    }\t/* for each ZDD subtable */\n\n    /* Check the constant table. */\n    subtable = &(table->constants);\n    nodelist = subtable->nodelist;\n    keys = subtable->keys;\n    dead = subtable->dead;\n    totalKeys += keys;\n    totalSlots += subtable->slots;\n    totalDead += dead;\n    for (j = 0; (unsigned) j < subtable->slots; j++) {\n\tnode = nodelist[j];\n\tif (node != NULL) {\n\t    nonEmpty++;\n\t}\n\twhile (node != NULL) {\n\t    keys--;\n\t    if (node->ref == 0) {\n\t\tdead--;\n\t    }\n\t    node = node->next;\n\t}\n    }\n    if (keys != 0) {\n\t(void) fprintf(table->err, \"Wrong number of keys found \\\nin the constant table (difference=%d)\\n\", keys);\n\tcount++;\n    }\n    if (dead != 0) {\n\t(void) fprintf(table->err, \"Wrong number of dead found \\\nin the constant table (difference=%d)\\n\", dead);\n    }\n    if ((unsigned) totalKeys != table->keys + table->keysZ) {\n\t(void) fprintf(table->err, \"Wrong number of total keys found \\\n(difference=%d)\\n\", (int) (totalKeys-table->keys));\n    }\n    if ((unsigned) totalSlots != table->slots) {\n\t(void) fprintf(table->err, \"Wrong number of total slots found \\\n(difference=%d)\\n\", (int) (totalSlots-table->slots));\n    }\n    if (table->minDead != (unsigned) (table->gcFrac * table->slots)) {\n\t(void) fprintf(table->err, \"Wrong number of minimum dead found \\\n(%u vs. %u)\\n\", table->minDead,\n\t(unsigned) (table->gcFrac * (double) table->slots));\n    }\n    if ((unsigned) totalDead != table->dead + table->deadZ) {\n\t(void) fprintf(table->err, \"Wrong number of total dead found \\\n(difference=%d)\\n\", (int) (totalDead-table->dead));\n    }\n    (void) fprintf(table->out,\"Average length of non-empty lists = %g\\n\",\n                   (double) table->keys / (double) nonEmpty);\n\n    return(count);\n\n} /* end of Cudd_CheckKeys */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints information about the heap.\n\n  @details Prints to the manager's stdout the number of live nodes for each\n  level of the %DD heap that contains at least one live node.  It also\n  prints a summary containing:\n  <ul>\n  <li> total number of tables;\n  <li> number of tables with live nodes;\n  <li> table with the largest number of live nodes;\n  <li> number of nodes in that table.\n  </ul>\n  If more than one table contains the maximum number of live nodes,\n  only the one of lowest index is reported.\n\n  @return 1 in case of success and 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddHeapProfile(\n  DdManager * dd)\n{\n    int ntables = dd->size;\n    DdSubtable *subtables = dd->subtables;\n    int i,\t\t/* loop index */\n\tnodes,\t\t/* live nodes in i-th layer */\n\tretval,\t\t/* return value of fprintf */\n\tlargest = -1,\t/* index of the table with most live nodes */\n\tmaxnodes = -1,\t/* maximum number of live nodes in a table */\n\tnonempty = 0;\t/* number of tables with live nodes */\n\n    /* Print header. */\n    retval = fprintf(dd->out,\"*** DD heap profile for 0x%\" PRIxPTR \" ***\\n\",\n\t\t     (ptruint) dd);\n    if (retval == EOF) return 0;\n\n    /* Print number of live nodes for each nonempty table. */\n    for (i=0; i<ntables; i++) {\n\tnodes = subtables[i].keys - subtables[i].dead;\n\tif (nodes) {\n\t    nonempty++;\n\t    retval = fprintf(dd->out,\"%5d: %5d nodes\\n\", i, nodes);\n\t    if (retval == EOF) return 0;\n\t    if (nodes > maxnodes) {\n\t\tmaxnodes = nodes;\n\t\tlargest = i;\n\t    }\n\t}\n    }\n\n    nodes = dd->constants.keys - dd->constants.dead;\n    if (nodes) {\n\tnonempty++;\n\tretval = fprintf(dd->out,\"const: %5d nodes\\n\", nodes);\n\tif (retval == EOF) return 0;\n\tif (nodes > maxnodes) {\n\t    maxnodes = nodes;\n\t    largest = CUDD_CONST_INDEX;\n\t}\n    }\n\n    /* Print summary. */\n    retval = fprintf(dd->out,\"Summary: %d tables, %d non-empty, largest: %d \",\n\t  ntables+1, nonempty, largest);\n    if (retval == EOF) return 0;\n    retval = fprintf(dd->out,\"(with %d nodes)\\n\", maxnodes);\n    if (retval == EOF) return 0;\n\n    return(1);\n\n} /* end of cuddHeapProfile */\n\n\n/**\n  @brief Prints out information on a node.\n\n  @sideeffect None\n\n*/\nvoid\ncuddPrintNode(\n  DdNode * f,\n  FILE *fp)\n{\n    f = Cudd_Regular(f);\n    (void) fprintf(fp,\"       node 0x%\" PRIxPTR \", id = %u, ref = %u, then = 0x%\" PRIxPTR \", else = 0x%\" PRIxPTR \"\\n\",\n        (ptruint)f,f->index,f->ref,(ptruint)cuddT(f),(ptruint)cuddE(f));\n\n} /* end of cuddPrintNode */\n\n\n/**\n  @brief Prints the variable groups as a parenthesized list.\n\n  @details   For each group the level range that it represents is printed.\n  After each group, the group's flags are printed, preceded by a `|'.  For\n  each flag (except MTR_TERMINAL) a character is printed.\n  <ul>\n  <li>F: MTR_FIXED\n  <li>N: MTR_NEWNODE\n  <li>S: MTR_SOFT\n  </ul>\n  The second argument, silent, if different from 0, causes\n  Cudd_PrintVarGroups to only check the syntax of the group tree.\n\n  @sideeffect None\n\n*/\nvoid\ncuddPrintVarGroups(\n  DdManager * dd /**< manager */,\n  MtrNode * root /**< root of the group tree */,\n  int zdd /**< 0: %BDD; 1: %ZDD */,\n  int silent /**< flag to check tree syntax only */)\n{\n    MtrNode *node;\n    int level;\n\n    assert(root != NULL);\n    assert(root->younger == NULL || root->younger->elder == root);\n    assert(root->elder == NULL || root->elder->younger == root);\n    if (zdd) {\n\tlevel = dd->permZ[root->index];\n    } else {\n\tlevel = dd->perm[root->index];\n    }\n    if (!silent) (void) printf(\"(%d\",level);\n    if (MTR_TEST(root,MTR_TERMINAL) || root->child == NULL) {\n\tif (!silent) (void) printf(\",\");\n    } else {\n\tnode = root->child;\n\twhile (node != NULL) {\n\t    assert(node->low >= root->low && (int) (node->low + node->size) <= (int) (root->low + root->size));\n\t    assert(node->parent == root);\n\t    cuddPrintVarGroups(dd,node,zdd,silent);\n\t    node = node->younger;\n\t}\n    }\n    if (!silent) {\n\t(void) printf(\"%d\", (int) (level + root->size - 1));\n\tif (root->flags != MTR_DEFAULT) {\n\t    (void) printf(\"|\");\n\t    if (MTR_TEST(root,MTR_FIXED)) (void) printf(\"F\");\n\t    if (MTR_TEST(root,MTR_NEWNODE)) (void) printf(\"N\");\n\t    if (MTR_TEST(root,MTR_SOFT)) (void) printf(\"S\");\n\t}\n\t(void) printf(\")\");\n\tif (root->parent == NULL) (void) printf(\"\\n\");\n    }\n    assert((root->flags &~(MTR_TERMINAL | MTR_SOFT | MTR_FIXED | MTR_NEWNODE)) == 0);\n    return;\n\n} /* end of cuddPrintVarGroups */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Searches the subtables above node for its parents.\n\n  @sideeffect None\n\n*/\nstatic void\ndebugFindParent(\n  DdManager * table,\n  DdNode * node)\n{\n    int         i,j;\n    int\t\tslots;\n    DdNodePtr\t*nodelist;\n    DdNode\t*f;\n\n    for (i = 0; i < cuddI(table,node->index); i++) {\n\tnodelist = table->subtables[i].nodelist;\n\tslots = table->subtables[i].slots;\n\n\tfor (j=0;j<slots;j++) {\n\t    f = nodelist[j];\n\t    while (f != NULL) {\n\t\tif (cuddT(f) == node || Cudd_Regular(cuddE(f)) == node) {\n\t\t    (void) fprintf(table->out,\"parent is at 0x%\" PRIxPTR \", id = %u, ref = %u, then = 0x%\" PRIxPTR \", else = 0x%\" PRIxPTR \"\\n\",\n\t\t\t(ptruint)f,f->index,f->ref,(ptruint)cuddT(f),(ptruint)cuddE(f));\n\t\t}\n\t\tf = f->next;\n\t    }\n\t}\n    }\n\n} /* end of debugFindParent */\n\n\n#if 0\n/**\n  @brief Reports an error if a (dead) node has a non-dead parent.\n\n  @details Searches all the subtables above node. Very expensive.\n  The same check is now implemented more efficiently in ddDebugCheck.\n\n  @sideeffect None\n\n  @see debugFindParent\n\n*/\nstatic void\ndebugCheckParent(\n  DdManager * table,\n  DdNode * node)\n{\n    int         i,j;\n    int\t\tslots;\n    DdNode\t**nodelist,*f;\n\n    for (i = 0; i < cuddI(table,node->index); i++) {\n\tnodelist = table->subtables[i].nodelist;\n\tslots = table->subtables[i].slots;\n\n\tfor (j=0;j<slots;j++) {\n\t    f = nodelist[j];\n\t    while (f != NULL) {\n\t\tif ((Cudd_Regular(cuddE(f)) == node || cuddT(f) == node) && f->ref != 0) {\n\t\t    (void) fprintf(table->err,\n\t\t\t\t   \"error with zero ref count\\n\");\n\t\t    (void) fprintf(table->err,\"parent is 0x%x, id = %u, ref = %u, then = 0x%x, else = 0x%x\\n\",f,f->index,f->ref,cuddT(f),cuddE(f));\n\t\t    (void) fprintf(table->err,\"child  is 0x%x, id = %u, ref = %u, then = 0x%x, else = 0x%x\\n\",node,node->index,node->ref,cuddT(node),cuddE(node));\n\t\t}\n\t\tf = f->next;\n\t    }\n\t}\n    }\n}\n#endif\n"
  },
  {
    "path": "cudd/cudd/cuddClip.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Clipping functions.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * cuddBddClippingAndRecur (DdManager *manager, DdNode *f, DdNode *g, int distance, int direction);\nstatic DdNode * cuddBddClipAndAbsRecur (DdManager *manager, DdNode *f, DdNode *g, DdNode *cube, int distance, int direction);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Approximates the conjunction of two BDDs f and g.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddAnd\n\n*/\nDdNode *\nCudd_bddClippingAnd(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first conjunct */,\n  DdNode * g /**< second conjunct */,\n  int  maxDepth /**< maximum recursion depth */,\n  int  direction /**< under (0) or over (1) approximation */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddClippingAnd(dd,f,g,maxDepth,direction);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddClippingAnd */\n\n\n/**\n  @brief Approximates the conjunction of two BDDs f and g and\n  simultaneously abstracts the variables in cube.\n\n  @details The variables are existentially abstracted.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddAndAbstract Cudd_bddClippingAnd\n\n*/\nDdNode *\nCudd_bddClippingAndAbstract(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first conjunct */,\n  DdNode * g /**< second conjunct */,\n  DdNode * cube /**< cube of variables to be abstracted */,\n  int  maxDepth /**< maximum recursion depth */,\n  int  direction /**< under (0) or over (1) approximation */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddClippingAndAbstract(dd,f,g,cube,maxDepth,direction);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddClippingAndAbstract */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Approximates the conjunction of two BDDs f and g.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddClippingAnd\n\n*/\nDdNode *\ncuddBddClippingAnd(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first conjunct */,\n  DdNode * g /**< second conjunct */,\n  int  maxDepth /**< maximum recursion depth */,\n  int  direction /**< under (0) or over (1) approximation */)\n{\n    DdNode *res;\n\n    res = cuddBddClippingAndRecur(dd,f,g,maxDepth,direction);\n\n    return(res);\n\n} /* end of cuddBddClippingAnd */\n\n\n/**\n  @brief Approximates the conjunction of two BDDs f and g and\n  simultaneously abstracts the variables in cube.\n\n  @return a pointer to the resulting %BDD if successful; NULL if the\n  intermediate result blows up.\n\n  @sideeffect None\n\n  @see Cudd_bddClippingAndAbstract\n\n*/\nDdNode *\ncuddBddClippingAndAbstract(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first conjunct */,\n  DdNode * g /**< second conjunct */,\n  DdNode * cube /**< cube of variables to be abstracted */,\n  int  maxDepth /**< maximum recursion depth */,\n  int  direction /**< under (0) or over (1) approximation */)\n{\n    DdNode *res;\n\n    res = cuddBddClipAndAbsRecur(dd,f,g,cube,maxDepth,direction);\n\n    return(res);\n\n} /* end of cuddBddClippingAndAbstract */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the recursive step of Cudd_bddClippingAnd.\n\n  @details Takes the conjunction of two BDDs.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddBddClippingAnd\n\n*/\nstatic DdNode *\ncuddBddClippingAndRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g,\n  int  distance,\n  int  direction)\n{\n    DdNode *F, *ft, *fe, *G, *gt, *ge;\n    DdNode *one, *zero, *r, *t, *e;\n    int topf, topg;\n    unsigned int index;\n    DD_CTFP cacheOp;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    /* Terminal cases. */\n    if (f == zero || g == zero || f == Cudd_Not(g)) return(zero);\n    if (f == g || g == one) return(f);\n    if (f == one) return(g);\n    if (distance == 0) {\n\t/* One last attempt at returning the right result. We sort of\n\t** cheat by calling Cudd_bddLeq. */\n\tif (Cudd_bddLeq(manager,f,g)) return(f);\n\tif (Cudd_bddLeq(manager,g,f)) return(g);\n\tif (direction == 1) {\n\t    if (Cudd_bddLeq(manager,f,Cudd_Not(g)) ||\n\t\tCudd_bddLeq(manager,g,Cudd_Not(f))) return(zero);\n\t}\n\treturn(Cudd_NotCond(one,(direction == 0)));\n    }\n\n    /* At this point f and g are not constant. */\n    distance--;\n\n    /* Check cache. Try to increase cache efficiency by sorting the\n    ** pointers. */\n    if (f > g) {\n\tDdNode *tmp = f;\n\tf = g; g = tmp;\n    }\n    F = Cudd_Regular(f);\n    G = Cudd_Regular(g);\n    cacheOp = (DD_CTFP)\n\t(direction ? Cudd_bddClippingAnd : cuddBddClippingAnd);\n    if (F->ref != 1 || G->ref != 1) {\n\tr = cuddCacheLookup2(manager, cacheOp, f, g);\n\tif (r != NULL) return(r);\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    /* Here we can skip the use of cuddI, because the operands are known\n    ** to be non-constant.\n    */\n    topf = manager->perm[F->index];\n    topg = manager->perm[G->index];\n\n    /* Compute cofactors. */\n    if (topf <= topg) {\n\tindex = F->index;\n\tft = cuddT(F);\n\tfe = cuddE(F);\n\tif (Cudd_IsComplement(f)) {\n\t    ft = Cudd_Not(ft);\n\t    fe = Cudd_Not(fe);\n\t}\n    } else {\n\tindex = G->index;\n\tft = fe = f;\n    }\n\n    if (topg <= topf) {\n\tgt = cuddT(G);\n\tge = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gt = Cudd_Not(gt);\n\t    ge = Cudd_Not(ge);\n\t}\n    } else {\n\tgt = ge = g;\n    }\n\n    t = cuddBddClippingAndRecur(manager, ft, gt, distance, direction);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n    e = cuddBddClippingAndRecur(manager, fe, ge, distance, direction);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(manager, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (t == e) {\n\tr = t;\n    } else {\n\tif (Cudd_IsComplement(t)) {\n\t    r = cuddUniqueInter(manager,(int)index,Cudd_Not(t),Cudd_Not(e));\n\t    if (r == NULL) {\n\t\tCudd_RecursiveDeref(manager, t);\n\t\tCudd_RecursiveDeref(manager, e);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t} else {\n\t    r = cuddUniqueInter(manager,(int)index,t,e);\n\t    if (r == NULL) {\n\t\tCudd_RecursiveDeref(manager, t);\n\t\tCudd_RecursiveDeref(manager, e);\n\t\treturn(NULL);\n\t    }\n\t}\n    }\n    cuddDeref(e);\n    cuddDeref(t);\n    if (F->ref != 1 || G->ref != 1)\n\tcuddCacheInsert2(manager, cacheOp, f, g, r);\n    return(r);\n\n} /* end of cuddBddClippingAndRecur */\n\n\n/**\n  @brief Approximates the AND of two BDDs and simultaneously abstracts the\n  variables in cube.\n\n  @details The variables are existentially abstracted.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddClippingAndAbstract\n\n*/\nstatic DdNode *\ncuddBddClipAndAbsRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g,\n  DdNode * cube,\n  int  distance,\n  int  direction)\n{\n    DdNode *F, *ft, *fe, *G, *gt, *ge;\n    DdNode *one, *zero, *r, *t, *e, *Cube;\n    int topf, topg, topcube, top;\n    unsigned int index;\n    ptruint cacheTag;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    /* Terminal cases. */\n    if (f == zero || g == zero || f == Cudd_Not(g)) return(zero);\n    if (f == one && g == one)\treturn(one);\n    if (cube == one) {\n\treturn(cuddBddClippingAndRecur(manager, f, g, distance, direction));\n    }\n    if (f == one || f == g) {\n\treturn (cuddBddExistAbstractRecur(manager, g, cube));\n    }\n    if (g == one) {\n\treturn (cuddBddExistAbstractRecur(manager, f, cube));\n    }\n    if (distance == 0) return(Cudd_NotCond(one,(direction == 0)));\n\n    /* At this point f, g, and cube are not constant. */\n    distance--;\n\n    /* Check cache. */\n    if (f > g) { /* Try to increase cache efficiency. */\n\tDdNode *tmp = f;\n\tf = g; g = tmp;\n    }\n    F = Cudd_Regular(f);\n    G = Cudd_Regular(g);\n    cacheTag = direction ? DD_BDD_CLIPPING_AND_ABSTRACT_UP_TAG :\n\tDD_BDD_CLIPPING_AND_ABSTRACT_DOWN_TAG;\n    if (F->ref != 1 || G->ref != 1) {\n\tr = cuddCacheLookup(manager, cacheTag,\n\t\t\t    f, g, cube);\n\tif (r != NULL) {\n\t    return(r);\n\t}\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    /* Here we can skip the use of cuddI, because the operands are known\n    ** to be non-constant.\n    */\n    topf = manager->perm[F->index];\n    topg = manager->perm[G->index];\n    top = ddMin(topf, topg);\n    topcube = manager->perm[cube->index];\n\n    if (topcube < top) {\n\treturn(cuddBddClipAndAbsRecur(manager, f, g, cuddT(cube),\n\t\t\t\t      distance, direction));\n    }\n    /* Now, topcube >= top. */\n\n    if (topf == top) {\n\tindex = F->index;\n\tft = cuddT(F);\n\tfe = cuddE(F);\n\tif (Cudd_IsComplement(f)) {\n\t    ft = Cudd_Not(ft);\n\t    fe = Cudd_Not(fe);\n\t}\n    } else {\n\tindex = G->index;\n\tft = fe = f;\n    }\n\n    if (topg == top) {\n\tgt = cuddT(G);\n\tge = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gt = Cudd_Not(gt);\n\t    ge = Cudd_Not(ge);\n\t}\n    } else {\n\tgt = ge = g;\n    }\n\n    if (topcube == top) {\n\tCube = cuddT(cube);\n    } else {\n\tCube = cube;\n    }\n\n    t = cuddBddClipAndAbsRecur(manager, ft, gt, Cube, distance, direction);\n    if (t == NULL) return(NULL);\n\n    /* Special case: 1 OR anything = 1. Hence, no need to compute\n    ** the else branch if t is 1.\n    */\n    if (t == one && topcube == top) {\n\tif (F->ref != 1 || G->ref != 1)\n\t    cuddCacheInsert(manager, cacheTag, f, g, cube, one);\n\treturn(one);\n    }\n    cuddRef(t);\n\n    e = cuddBddClipAndAbsRecur(manager, fe, ge, Cube, distance, direction);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(manager, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (topcube == top) {\t/* abstract */\n\tr = cuddBddClippingAndRecur(manager, Cudd_Not(t), Cudd_Not(e),\n\t\t\t\t    distance, (direction == 0));\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(manager, t);\n\t    Cudd_RecursiveDeref(manager, e);\n\t    return(NULL);\n\t}\n\tr = Cudd_Not(r);\n\tcuddRef(r);\n\tCudd_RecursiveDeref(manager, t);\n\tCudd_RecursiveDeref(manager, e);\n\tcuddDeref(r);\n    } else if (t == e) {\n\tr = t;\n\tcuddDeref(t);\n\tcuddDeref(e);\n    } else {\n\tif (Cudd_IsComplement(t)) {\n\t    r = cuddUniqueInter(manager,(int)index,Cudd_Not(t),Cudd_Not(e));\n\t    if (r == NULL) {\n\t\tCudd_RecursiveDeref(manager, t);\n\t\tCudd_RecursiveDeref(manager, e);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t} else {\n\t    r = cuddUniqueInter(manager,(int)index,t,e);\n\t    if (r == NULL) {\n\t\tCudd_RecursiveDeref(manager, t);\n\t\tCudd_RecursiveDeref(manager, e);\n\t\treturn(NULL);\n\t    }\n\t}\n\tcuddDeref(e);\n\tcuddDeref(t);\n    }\n    if (F->ref != 1 || G->ref != 1)\n\tcuddCacheInsert(manager, cacheTag, f, g, cube, r);\n    return (r);\n\n} /* end of cuddBddClipAndAbsRecur */\n\n"
  },
  {
    "path": "cudd/cudd/cuddCof.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Cofactoring functions.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int ddVarsAreSymmetricBefore(DdManager * dd, DdNode * f, DdNode * var1, DdNode * var2);\nstatic int ddVarsAreSymmetricBetween(DdManager * dd, DdNode * f1, DdNode * f0, DdNode * var2);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Computes the cofactor of f with respect to g.\n\n  @details g must be the %BDD or the %ADD of a cube.\n\n  @return a pointer to the cofactor if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddConstrain Cudd_bddRestrict\n\n*/\nDdNode *\nCudd_Cofactor(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *res,*zero;\n\n    zero = Cudd_Not(DD_ONE(dd));\n    if (g == zero || g == DD_ZERO(dd)) {\n\t(void) fprintf(dd->err,\"Cudd_Cofactor: Invalid restriction 1\\n\");\n\tdd->errorCode = CUDD_INVALID_ARG;\n\treturn(NULL);\n    }\n    do {\n\tdd->reordered = 0;\n\tres = cuddCofactorRecur(dd,f,g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_Cofactor */\n\n\n/**\n  @brief Checks whether g is the %BDD of a cube.\n\n  @details The constant 1 is a valid cube, but all other constant\n  functions cause cuddCheckCube to return 0.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nCudd_CheckCube(\n  DdManager * dd,\n  DdNode * g)\n{\n    DdNode *g1,*g0,*one,*zero;\n    \n    one = DD_ONE(dd);\n    if (g == one) return(1);\n    if (Cudd_Not(g) == one) return(0);\n\n    zero = Cudd_Not(one);\n    cuddGetBranches(g,&g1,&g0);\n\n    if (g0 == zero) {\n        return(Cudd_CheckCube(dd, g1));\n    }\n    if (g1 == zero) {\n        return(Cudd_CheckCube(dd, g0));\n    }\n    return(0);\n\n} /* end of Cudd_CheckCube */\n\n\n/**\n   @brief Checks whether two variables are symmetric in a BDD.\n\n   @return 1 if the variables are symmetric; 0 if they are not.\n\n   @details No nodes are built during the check.\n\n   @sideeffect None\n*/\nint\nCudd_VarsAreSymmetric(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< BDD whose variables are tested */,\n  int index1 /**< index of first variable */,\n  int index2 /**< index of second variable */)\n{\n    DdNode *var1, *var2;\n\n    if (index1 == index2) /* trivial case: symmetry is reflexive */\n        return(1);\n\n    if (index1 >= dd->size) {\n        if (index2 >= dd->size) {\n            return(1); /* f depends on neither variable */\n        } else {\n            /* f does not depend on var1; check whether it depends on var2 */\n            var2 = dd->vars[index2];\n            return ddVarsAreSymmetricBetween(dd, f, f, var2);\n        }\n    } else if (index2 >= dd->size) {\n        /* f does not depend on var2; check whether it depends on var1 */\n        var1 = dd->vars[index1];\n        return  ddVarsAreSymmetricBetween(dd, f, f, var1);\n    }\n\n    /* Make sure index1 denotes the variable currently closer to the root. */\n    if (dd->perm[index1] < dd->perm[index2]) {\n        var1 = dd->vars[index1];\n        var2 = dd->vars[index2];\n    } else {\n        var1 = dd->vars[index2];\n        var2 = dd->vars[index1];\n    }\n\n    return ddVarsAreSymmetricBefore(dd, f, var1, var2);\n\n} /* end of Cudd_VarsAreSymmetric */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Computes the children of g.\n\n  @sideeffect None\n\n*/\nvoid\ncuddGetBranches(\n  DdNode * g,\n  DdNode ** g1,\n  DdNode ** g0)\n{\n    DdNode\t*G = Cudd_Regular(g);\n\n    *g1 = cuddT(G);\n    *g0 = cuddE(G);\n    if (Cudd_IsComplement(g)) {\n\t*g1 = Cudd_Not(*g1);\n\t*g0 = Cudd_Not(*g0);\n    }\n\n} /* end of cuddGetBranches */\n\n\n/**\n  @brief Performs the recursive step of Cudd_Cofactor.\n\n  @return a pointer to the cofactor if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Cofactor\n\n*/\nDdNode *\ncuddCofactorRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *one,*zero,*F,*G,*g1,*g0,*f1,*f0,*t,*e,*r;\n    int topf,topg;\n    int comple;\n\n    statLine(dd);\n    F = Cudd_Regular(f);\n    if (cuddIsConstant(F)) return(f);\n\n    one = DD_ONE(dd);\n\n    /* The invariant g != 0 is true on entry to this procedure and is\n    ** recursively maintained by it. Therefore it suffices to test g\n    ** against one to make sure it is not constant.\n    */\n    if (g == one) return(f);\n    /* From now on, f and g are known not to be constants. */\n\n    comple = f != F;\n    r = cuddCacheLookup2(dd,Cudd_Cofactor,F,g);\n    if (r != NULL) {\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    topf = dd->perm[F->index];\n    G = Cudd_Regular(g);\n    topg = dd->perm[G->index];\n\n    /* We take the cofactors of F because we are going to rely on\n    ** the fact that the cofactors of the complement are the complements\n    ** of the cofactors to better utilize the cache. Variable comple\n    ** remembers whether we have to complement the result or not.\n    */\n    if (topf <= topg) {\n\tf1 = cuddT(F); f0 = cuddE(F);\n    } else {\n\tf1 = f0 = F;\n    }\n    if (topg <= topf) {\n\tg1 = cuddT(G); g0 = cuddE(G);\n\tif (g != G) { g1 = Cudd_Not(g1); g0 = Cudd_Not(g0); }\n    } else {\n\tg1 = g0 = g;\n    }\n\n    zero = Cudd_Not(one);\n    if (topf >= topg) {\n\tif (g0 == zero || g0 == DD_ZERO(dd)) {\n\t    r = cuddCofactorRecur(dd, f1, g1);\n\t} else if (g1 == zero || g1 == DD_ZERO(dd)) {\n\t    r = cuddCofactorRecur(dd, f0, g0);\n\t} else {\n\t    (void) fprintf(dd->err,\n\t\t\t   \"Cudd_Cofactor: Invalid restriction 2\\n\");\n\t    dd->errorCode = CUDD_INVALID_ARG;\n\t    return(NULL);\n\t}\n\tif (r == NULL) return(NULL);\n    } else /* if (topf < topg) */ {\n\tt = cuddCofactorRecur(dd, f1, g);\n\tif (t == NULL) return(NULL);\n    \tcuddRef(t);\n    \te = cuddCofactorRecur(dd, f0, g);\n\tif (e == NULL) {\n\t    Cudd_RecursiveDeref(dd, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n\n\tif (t == e) {\n\t    r = t;\n\t} else if (Cudd_IsComplement(t)) {\n\t    r = cuddUniqueInter(dd,(int)F->index,Cudd_Not(t),Cudd_Not(e));\n\t    if (r != NULL)\n\t\tr = Cudd_Not(r);\n\t} else {\n\t    r = cuddUniqueInter(dd,(int)F->index,t,e);\n\t}\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(dd ,e);\n\t    Cudd_RecursiveDeref(dd ,t);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert2(dd,Cudd_Cofactor,F,g,r);\n\n    return(Cudd_NotCond(r,comple));\n\n} /* end of cuddCofactorRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n   @brief Implements the upper recursive step of Cudd_VarsAreSymmetric().\n\n   @details The assumption is made that the level of index1 is less\n   than the level of index2.\n\n   @return 1 if the variables are symmetric for the given function;\n   0 if they are not.\n\n   @see Cudd_VarsAreSymmetric ddVarsAreSymmetricBetween\n\n*/\nstatic int\nddVarsAreSymmetricBefore(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * var1,\n  DdNode * var2)\n{\n    DdNode *F, *ft, *fe, *r;\n    int top, res, level1;\n\n    statLine(dd);\n    F = Cudd_Regular(f);\n    if (cuddIsConstant(F)) /* f depends on neither variable */\n        return(1);\n    top = dd->perm[F->index];\n    if (top > dd->perm[var2->index])\n        return(1); /* f depends on neither variable */\n    /* Cache lookup.  We take advantage of the observation that\n     * var1 and var2 are symmetric in f iff they are symmetric in\n     * the complement of f. */\n    r = cuddCacheLookup(dd, DD_VARS_SYMM_BEFORE_TAG, F, var1, var2);\n    if (r != NULL) {\n        return(r == DD_ONE(dd) ? 1 : 0);\n    }\n    level1 = dd->perm[var1->index];\n    if (top > level1)\n        /* Check whether f1 depends on the variable currently at level2. */\n        return ddVarsAreSymmetricBetween(dd, f, f, var2);\n    ft = cuddT(F);\n    fe = cuddE(F);\n    if (F != f) {\n        ft = Cudd_Not(ft);\n        fe = Cudd_Not(fe);\n    }\n    if (top < level1) {\n        res = ddVarsAreSymmetricBefore(dd, ft, var1, var2);\n        if (res)\n            res = ddVarsAreSymmetricBefore(dd, fe, var1, var2);\n    } else {\n        res = ddVarsAreSymmetricBetween(dd, ft, fe, var2);\n    }\n    /* Cache insertion. */\n    cuddCacheInsert(dd, DD_VARS_SYMM_BEFORE_TAG, F, var1, var2,\n                    res ? DD_ONE(dd) : Cudd_Not(DD_ONE(dd)));\n    return(res);\n\n} /* end of ddVarsAreSymmetricBefore */\n\n\n/**\n   @brief Implements the lower recursive step of Cudd_VarsAreSymmetric().\n\n   @return 1 if the negative cofactor of the first argument w.r.t. the variable\n   currently at level2 is the same as the positive cofactor of the second\n   argument; 0 if the two cofactors are not the same.\n\n   @see Cudd_VarsAreSymmetric ddVarsAreSymmetricBefore\n\n*/\nstatic int\nddVarsAreSymmetricBetween(\n  DdManager * dd,\n  DdNode * f1,\n  DdNode * f0,\n  DdNode * var2)\n{\n    DdNode *F1, *F0, *f1t, *f1e, *f0t, *f0e, *r;\n    int topf1, topf0, top, res;\n    int level2 = dd->perm[var2->index];\n\n    statLine(dd);\n    F1 = Cudd_Regular(f1);\n    F0 = Cudd_Regular(f0);\n    if (cuddIsConstant(F1) && cuddIsConstant(F0))\n        return f1 == f0;\n    /* Here we know that one of f1 and f0 is not constant.  Hence the\n     * least index is that of a variable. */\n    if (cuddIsConstant(F1))\n        topf1 = CUDD_CONST_INDEX;\n    else\n        topf1 = dd->perm[F1->index];\n    if (cuddIsConstant(F0))\n        topf0 = CUDD_CONST_INDEX;\n    else\n        topf0 = dd->perm[F0->index];\n    if (topf0 > level2 && topf1 > level2)\n        return(f1 == f0);\n    /* Cache lookup. */\n    r = cuddCacheLookup(dd, DD_VARS_SYMM_BETWEEN_TAG, f1, f0, var2);\n    if (r != NULL) {\n        return(r == DD_ONE(dd) ? 1 : 0);\n    }\n    /* Compute cofactors and find top level. */\n    if (topf1 <= topf0) {\n        top = topf1;\n        f1t = cuddT(F1);\n        f1e = cuddE(F1);\n        if (F1 != f1) {\n            f1t = Cudd_Not(f1t);\n            f1e = Cudd_Not(f1e);\n        }\n    } else {\n        top = topf0;\n        f1t = f1e = f1;\n    }\n    if (topf0 <= topf1) {\n        f0t = cuddT(F0);\n        f0e = cuddE(F0);\n        if (F0 != f0) {\n            f0t = Cudd_Not(f0t);\n            f0e = Cudd_Not(f0e);\n        }\n    } else {\n        f0t = f0e = f0;\n    }\n    if (top < level2) {\n        res = ddVarsAreSymmetricBetween(dd, f1t, f0t, var2);\n        if (res)\n            res = ddVarsAreSymmetricBetween(dd, f1e, f0e, var2);\n    } else {\n        assert(top == level2);\n        res = f1e == f0t;\n    }\n    /* Cache insertion. */\n    cuddCacheInsert(dd, DD_VARS_SYMM_BETWEEN_TAG, f1, f0, var2,\n                    res ? DD_ONE(dd) : Cudd_Not(DD_ONE(dd)));\n    return(res);\n\n} /* end of ddVarsAreSymmetricBetween */\n"
  },
  {
    "path": "cudd/cudd/cuddCompose.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functional composition and variable permutation of DDs.\n\n  @details The permutation functions use a local cache because the\n  results to be remembered depend on the permutation being applied.\n  Since the permutation is just an array, it cannot be stored in the\n  global cache. There are different procedured for BDDs and ADDs. This\n  is because bddPermuteRecur uses cuddBddIteRecur. If this were\n  changed, the procedures could be merged.\n\n  @author Fabio Somenzi and Kavita Ravi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * cuddAddPermuteRecur (DdManager *manager, DdHashTable *table, DdNode *node, int *permut);\nstatic DdNode * cuddBddPermuteRecur (DdManager *manager, DdHashTable *table, DdNode *node, int *permut);\nstatic DdNode * cuddBddVarMapRecur (DdManager *manager, DdNode *f);\nstatic DdNode * cuddAddVectorComposeRecur (DdManager *dd, DdHashTable *table, DdNode *f, DdNode **vector, int deepest);\nstatic DdNode * cuddAddNonSimComposeRecur (DdManager *dd, DdNode *f, DdNode **vector, DdNode *key, DdNode *cube, int lastsub);\nstatic DdNode * cuddBddVectorComposeRecur (DdManager *dd, DdHashTable *table, DdNode *f, DdNode **vector, int deepest);\nstatic int ddIsIthAddVar (DdManager *dd, DdNode *f, unsigned int i);\n\nstatic DdNode * cuddAddGeneralVectorComposeRecur (DdManager *dd, DdHashTable *table, DdNode *f, DdNode **vectorOn, DdNode **vectorOff, int deepest);\nstatic int ddIsIthAddVarPair (DdManager *dd, DdNode *f, DdNode *g, unsigned int i);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Substitutes g for x_v in the %BDD for f.\n\n  @details v is the index of the variable to be substituted.\n  Cudd_bddCompose passes the corresponding projection function to the\n  recursive procedure, so that the cache may be used.\n\n  @return the composed %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addCompose\n\n*/\nDdNode *\nCudd_bddCompose(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  int  v)\n{\n    DdNode *proj, *res;\n\n    /* Sanity check. */\n    if (v < 0 || v >= dd->size) return(NULL);\n\n    proj =  dd->vars[v];\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddComposeRecur(dd,f,g,proj);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddCompose */\n\n\n/**\n  @brief Substitutes g for x_v in the %ADD for f.\n\n  @details v is the index of the variable to be substituted. g must be\n  a 0-1 %ADD. Cudd_bddCompose passes the corresponding projection\n  function to the recursive procedure, so that the cache may be used.\n\n  @return the composed %ADD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddCompose\n\n*/\nDdNode *\nCudd_addCompose(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  int  v)\n{\n    DdNode *proj, *res;\n\n    /* Sanity check. */\n    if (v < 0 || v >= dd->size) return(NULL);\n\n    proj =  dd->vars[v];\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddComposeRecur(dd,f,g,proj);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addCompose */\n\n\n/**\n  @brief Permutes the variables of an %ADD.\n\n  @details Given a permutation in array permut, creates a new %ADD\n  with permuted variables. There should be an entry in array permut\n  for each variable in the manager. The i-th entry of permut holds the\n  index of the variable that is to substitute the i-th\n  variable.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddPermute Cudd_addSwapVariables\n\n*/\nDdNode *\nCudd_addPermute(\n  DdManager * manager,\n  DdNode * node,\n  int * permut)\n{\n    DdHashTable\t\t*table;\n    DdNode\t\t*res;\n\n    do {\n\tmanager->reordered = 0;\n\ttable = cuddHashTableInit(manager,1,2);\n\tif (table == NULL) return(NULL);\n\t/* Recursively solve the problem. */\n\tres = cuddAddPermuteRecur(manager,table,node,permut);\n\tif (res != NULL) cuddRef(res);\n\t/* Dispose of local cache. */\n\tcuddHashTableQuit(table);\n    } while (manager->reordered == 1);\n\n    if (res != NULL) cuddDeref(res);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addPermute */\n\n\n/**\n  @brief Swaps two sets of variables of the same size (x and y) in\n  the %ADD f.\n\n  @details The size is given by n. The two sets of variables are\n  assumed to be disjoint.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addPermute Cudd_bddSwapVariables\n\n*/\nDdNode *\nCudd_addSwapVariables(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** x,\n  DdNode ** y,\n  int  n)\n{\n    DdNode *swapped;\n    int\t i, j, k;\n    int\t *permut;\n\n    permut = ALLOC(int,dd->size);\n    if (permut == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < dd->size; i++) permut[i] = i;\n    for (i = 0; i < n; i++) {\n\tj = x[i]->index;\n\tk = y[i]->index;\n\tpermut[j] = k;\n\tpermut[k] = j;\n    }\n\n    swapped = Cudd_addPermute(dd,f,permut);\n    FREE(permut);\n\n    return(swapped);\n\n} /* end of Cudd_addSwapVariables */\n\n\n/**\n  @brief Permutes the variables of a %BDD.\n\n  @details Given a permutation in array permut, creates a new %BDD\n  with permuted variables. There should be an entry in array permut\n  for each variable in the manager. The i-th entry of permut holds the\n  index of the variable that is to substitute the i-th variable.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addPermute Cudd_bddSwapVariables\n\n*/\nDdNode *\nCudd_bddPermute(\n  DdManager * manager,\n  DdNode * node,\n  int * permut)\n{\n    DdHashTable\t\t*table;\n    DdNode\t\t*res;\n\n    do {\n\tmanager->reordered = 0;\n\ttable = cuddHashTableInit(manager,1,2);\n\tif (table == NULL) return(NULL);\n\tres = cuddBddPermuteRecur(manager,table,node,permut);\n\tif (res != NULL) cuddRef(res);\n\t/* Dispose of local cache. */\n\tcuddHashTableQuit(table);\n\n    } while (manager->reordered == 1);\n\n    if (res != NULL) cuddDeref(res);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddPermute */\n\n\n/**\n  @brief Remaps the variables of a %BDD using the default variable map.\n\n  @details A typical use of this function is to swap two sets of\n  variables.  The variable map must be registered with Cudd_SetVarMap.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddPermute Cudd_bddSwapVariables Cudd_SetVarMap\n\n*/\nDdNode *\nCudd_bddVarMap(\n  DdManager * manager /**< %DD manager */,\n  DdNode * f /**< function in which to remap variables */)\n{\n    DdNode *res;\n\n    if (manager->map == NULL) return(NULL);\n    do {\n\tmanager->reordered = 0;\n\tres = cuddBddVarMapRecur(manager, f);\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_bddVarMap */\n\n\n/**\n  @brief Registers a variable mapping with the manager.\n\n  @details Registers with the manager a variable mapping described\n  by two sets of variables.  This variable mapping is then used by\n  functions like Cudd_bddVarMap.  This function is convenient for\n  those applications that perform the same mapping several times.\n  However, if several different permutations are used, it may be more\n  efficient not to rely on the registered mapping, because changing\n  mapping causes the cache to be cleared.  (The initial setting,\n  however, does not clear the cache.) The two sets of variables (x and\n  y) must have the same size (x and y).  The size is given by n. The\n  two sets of variables are normally disjoint, but this restriction is\n  not imposeded by the function. When new variables are created, the\n  map is automatically extended (each new variable maps to\n  itself). The typical use, however, is to wait until all variables\n  are created, and then create the map.\n\n  @return 1 if the mapping is successfully registered with the\n  manager; 0 otherwise.\n\n  @sideeffect Modifies the manager. May clear the cache.\n\n  @see Cudd_bddVarMap Cudd_bddPermute Cudd_bddSwapVariables\n\n*/\nint\nCudd_SetVarMap (\n  DdManager *manager /**< %DD manager */,\n  DdNode **x /**< first array of variables */,\n  DdNode **y /**< second array of variables */,\n  int n /**< length of both arrays */)\n{\n    int i;\n\n    if (manager->map != NULL) {\n\tcuddCacheFlush(manager);\n    } else {\n\tmanager->map = ALLOC(int,manager->maxSize);\n\tif (manager->map == NULL) {\n\t    manager->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tmanager->memused += sizeof(int) * manager->maxSize;\n    }\n    /* Initialize the map to the identity. */\n    for (i = 0; i < manager->size; i++) {\n\tmanager->map[i] = i;\n    }\n    /* Create the map. */\n    for (i = 0; i < n; i++) {\n\tmanager->map[x[i]->index] = y[i]->index;\n\tmanager->map[y[i]->index] = x[i]->index;\n    }\n    return(1);\n\n} /* end of Cudd_SetVarMap */\n\n\n/**\n  @brief Swaps two sets of variables of the same size (x and y) in\n  the %BDD f.\n\n  @details The size is given by n. The two sets of variables are\n  assumed to be disjoint.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddPermute Cudd_addSwapVariables\n\n*/\nDdNode *\nCudd_bddSwapVariables(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** x,\n  DdNode ** y,\n  int  n)\n{\n    DdNode *swapped;\n    int\t i, j, k;\n    int\t *permut;\n\n    permut = ALLOC(int,dd->size);\n    if (permut == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < dd->size; i++) permut[i] = i;\n    for (i = 0; i < n; i++) {\n\tj = x[i]->index;\n\tk = y[i]->index;\n\tpermut[j] = k;\n\tpermut[k] = j;\n    }\n\n    swapped = Cudd_bddPermute(dd,f,permut);\n    FREE(permut);\n\n    return(swapped);\n\n} /* end of Cudd_bddSwapVariables */\n\n\n/**\n  @brief Rearranges a set of variables in the %BDD B.\n\n  @details The size of the set is given by n. This procedure is\n  intended for the `randomization' of the priority functions.\n\n  @return a pointer to the %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddPermute Cudd_bddSwapVariables\n  Cudd_Dxygtdxz Cudd_Dxygtdyz Cudd_PrioritySelect\n\n*/\nDdNode *\nCudd_bddAdjPermuteX(\n  DdManager * dd,\n  DdNode * B,\n  DdNode ** x,\n  int  n)\n{\n    DdNode *swapped;\n    int\t i, j, k;\n    int\t *permut;\n\n    permut = ALLOC(int,dd->size);\n    if (permut == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < dd->size; i++) permut[i] = i;\n    for (i = 0; i < n-2; i += 3) {\n\tj = x[i]->index;\n\tk = x[i+1]->index;\n\tpermut[j] = k;\n\tpermut[k] = j;\n    }\n\n    swapped = Cudd_bddPermute(dd,B,permut);\n    FREE(permut);\n\n    return(swapped);\n\n} /* end of Cudd_bddAdjPermuteX */\n\n\n/**\n  @brief Composes an %ADD with a vector of 0-1 ADDs.\n\n  @details Given a vector of 0-1 ADDs, creates a new %ADD by\n  substituting the 0-1 ADDs for the variables of the %ADD f.  There\n  should be an entry in vector for each variable in the manager.\n  If no substitution is sought for a given variable, the corresponding\n  projection function should be specified in the vector.\n  This function implements simultaneous composition.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addNonSimCompose Cudd_addPermute Cudd_addCompose\n  Cudd_bddVectorCompose\n\n*/\nDdNode *\nCudd_addVectorCompose(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** vector)\n{\n    DdHashTable\t\t*table;\n    DdNode\t\t*res;\n    int\t\t\tdeepest;\n    int                 i;\n\n    do {\n\tdd->reordered = 0;\n\t/* Initialize local cache. */\n\ttable = cuddHashTableInit(dd,1,2);\n\tif (table == NULL) return(NULL);\n\n\t/* Find deepest real substitution. */\n\tfor (deepest = dd->size - 1; deepest >= 0; deepest--) {\n\t    i = dd->invperm[deepest];\n\t    if (!ddIsIthAddVar(dd,vector[i],i)) {\n\t\tbreak;\n\t    }\n\t}\n\n\t/* Recursively solve the problem. */\n\tres = cuddAddVectorComposeRecur(dd,table,f,vector,deepest);\n\tif (res != NULL) cuddRef(res);\n\n\t/* Dispose of local cache. */\n\tcuddHashTableQuit(table);\n    } while (dd->reordered == 1);\n\n    if (res != NULL) cuddDeref(res);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addVectorCompose */\n\n\n/**\n  @brief Composes an %ADD with a vector of ADDs.\n\n  @details Given a vector of ADDs, creates a new %ADD by substituting the\n  ADDs for the variables of the %ADD f. vectorOn contains ADDs to be substituted\n  for the x_v and vectorOff the ADDs to be substituted for x_v'. There should\n  be an entry in vector for each variable in the manager.  If no substitution\n  is sought for a given variable, the corresponding projection function should\n  be specified in the vector.  This function implements simultaneous\n  composition.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addVectorCompose Cudd_addNonSimCompose Cudd_addPermute\n  Cudd_addCompose Cudd_bddVectorCompose\n\n*/\nDdNode *\nCudd_addGeneralVectorCompose(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** vectorOn,\n  DdNode ** vectorOff)\n{\n    DdHashTable\t\t*table;\n    DdNode\t\t*res;\n    int\t\t\tdeepest;\n    int                 i;\n\n    do {\n\tdd->reordered = 0;\n\t/* Initialize local cache. */\n\ttable = cuddHashTableInit(dd,1,2);\n\tif (table == NULL) return(NULL);\n\n\t/* Find deepest real substitution. */\n\tfor (deepest = dd->size - 1; deepest >= 0; deepest--) {\n\t    i = dd->invperm[deepest];\n\t    if (!ddIsIthAddVarPair(dd,vectorOn[i],vectorOff[i],i)) {\n\t\tbreak;\n\t    }\n\t}\n\n\t/* Recursively solve the problem. */\n\tres = cuddAddGeneralVectorComposeRecur(dd,table,f,vectorOn,\n\t\t\t\t\t       vectorOff,deepest);\n\tif (res != NULL) cuddRef(res);\n\n\t/* Dispose of local cache. */\n\tcuddHashTableQuit(table);\n    } while (dd->reordered == 1);\n\n    if (res != NULL) cuddDeref(res);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addGeneralVectorCompose */\n\n\n/**\n  @brief Composes an %ADD with a vector of 0-1 ADDs.\n\n  @details Given a vector of 0-1 ADDs, creates a new %ADD by\n  substituting the 0-1 ADDs for the variables of the %ADD f.  There\n  should be an entry in vector for each variable in the manager.\n  This function implements non-simultaneous composition. If any of the\n  functions being composed depends on any of the variables being\n  substituted, then the result depends on the order of composition,\n  which in turn depends on the variable order: The variables farther from\n  the roots in the order are substituted first.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addVectorCompose Cudd_addPermute Cudd_addCompose\n\n*/\nDdNode *\nCudd_addNonSimCompose(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** vector)\n{\n    DdNode\t\t*cube, *key, *var, *tmp, *piece;\n    DdNode\t\t*res;\n    int\t\t\ti, lastsub;\n\n    /* The cache entry for this function is composed of three parts:\n    ** f itself, the replacement relation, and the cube of the\n    ** variables being substituted.\n    ** The replacement relation is the product of the terms (yi EXNOR gi).\n    ** This apporach allows us to use the global cache for this function,\n    ** with great savings in memory with respect to using arrays for the\n    ** cache entries.\n    ** First we build replacement relation and cube of substituted\n    ** variables from the vector specifying the desired composition.\n    */\n    key = DD_ONE(dd);\n    cuddRef(key);\n    cube = DD_ONE(dd);\n    cuddRef(cube);\n    for (i = (int) dd->size - 1; i >= 0; i--) {\n\tif (ddIsIthAddVar(dd,vector[i],(unsigned int)i)) {\n\t    continue;\n\t}\n\tvar = Cudd_addIthVar(dd,i);\n\tif (var == NULL) {\n\t    Cudd_RecursiveDeref(dd,key);\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    return(NULL);\n\t}\n\tcuddRef(var);\n\t/* Update cube. */\n\ttmp = Cudd_addApply(dd,Cudd_addTimes,var,cube);\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDeref(dd,key);\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    Cudd_RecursiveDeref(dd,var);\n\t    return(NULL);\n\t}\n\tcuddRef(tmp);\n\tCudd_RecursiveDeref(dd,cube);\n\tcube = tmp;\n\t/* Update replacement relation. */\n\tpiece = Cudd_addApply(dd,Cudd_addXnor,var,vector[i]);\n\tif (piece == NULL) {\n\t    Cudd_RecursiveDeref(dd,key);\n\t    Cudd_RecursiveDeref(dd,var);\n\t    return(NULL);\n\t}\n\tcuddRef(piece);\n\tCudd_RecursiveDeref(dd,var);\n\ttmp = Cudd_addApply(dd,Cudd_addTimes,key,piece);\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDeref(dd,key);\n\t    Cudd_RecursiveDeref(dd,piece);\n\t    return(NULL);\n\t}\n\tcuddRef(tmp);\n\tCudd_RecursiveDeref(dd,key);\n\tCudd_RecursiveDeref(dd,piece);\n\tkey = tmp;\n    }\n\n    /* Now try composition, until no reordering occurs. */\n    do {\n\t/* Find real substitution with largest index. */\n\tfor (lastsub = dd->size - 1; lastsub >= 0; lastsub--) {\n\t    if (!ddIsIthAddVar(dd,vector[lastsub],(unsigned int)lastsub)) {\n\t\tbreak;\n\t    }\n\t}\n\n\t/* Recursively solve the problem. */\n\tdd->reordered = 0;\n\tres = cuddAddNonSimComposeRecur(dd,f,vector,key,cube,lastsub+1);\n\tif (res != NULL) cuddRef(res);\n\n    } while (dd->reordered == 1);\n\n    Cudd_RecursiveDeref(dd,key);\n    Cudd_RecursiveDeref(dd,cube);\n    if (res != NULL) cuddDeref(res);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addNonSimCompose */\n\n\n/**\n  @brief Composes a %BDD with a vector of BDDs.\n\n  @details Given a vector of BDDs, creates a new %BDD by\n  substituting the BDDs for the variables of the %BDD f.  There\n  should be an entry in vector for each variable in the manager.\n  If no substitution is sought for a given variable, the corresponding\n  projection function should be specified in the vector.\n  This function implements simultaneous composition.\n\n  @return a pointer to the resulting %BDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddPermute Cudd_bddCompose Cudd_addVectorCompose\n\n*/\nDdNode *\nCudd_bddVectorCompose(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** vector)\n{\n    DdHashTable\t\t*table;\n    DdNode\t\t*res;\n    int\t\t\tdeepest;\n    int                 i;\n\n    do {\n\tdd->reordered = 0;\n\t/* Initialize local cache. */\n\ttable = cuddHashTableInit(dd,1,2);\n\tif (table == NULL) return(NULL);\n\n\t/* Find deepest real substitution. */\n\tfor (deepest = dd->size - 1; deepest >= 0; deepest--) {\n\t    i = dd->invperm[deepest];\n\t    if (vector[i] != dd->vars[i]) {\n\t\tbreak;\n\t    }\n\t}\n\n\t/* Recursively solve the problem. */\n\tres = cuddBddVectorComposeRecur(dd,table,f,vector, deepest);\n\tif (res != NULL) cuddRef(res);\n\n\t/* Dispose of local cache. */\n\tcuddHashTableQuit(table);\n    } while (dd->reordered == 1);\n\n    if (res != NULL) cuddDeref(res);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddVectorCompose */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddCompose.\n\n  @details Exploits the fact that the composition of f' with g\n  produces the complement of the composition of f with g to better\n  utilize the cache.\n\n  @return the composed %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddCompose\n\n*/\nDdNode *\ncuddBddComposeRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode * proj)\n{\n    DdNode\t *F, *G, *f1, *f0, *g1, *g0, *r, *t, *e;\n    unsigned int topindex;\n    int\t\t topf, topg, v;\n    int\t\t comple;\n\n    statLine(dd);\n    v = dd->perm[proj->index];\n    F = Cudd_Regular(f);\n    topf = cuddI(dd,F->index);\n\n    /* Terminal case. Subsumes the test for constant f. */\n    if (topf > v) return(f);\n\n    /* We solve the problem for a regular pointer, and then complement\n    ** the result if the pointer was originally complemented.\n    */\n    comple = Cudd_IsComplement(f);\n\n    /* Check cache. */\n    r = cuddCacheLookup(dd,DD_BDD_COMPOSE_RECUR_TAG,F,g,proj);\n    if (r != NULL) {\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    if (topf == v) {\n\t/* Compose. */\n\tf1 = cuddT(F);\n\tf0 = cuddE(F);\n\tr = cuddBddIteRecur(dd, g, f1, f0);\n\tif (r == NULL) return(NULL);\n    } else {\n\t/* Compute cofactors of f and g. Remember the index of the top\n\t** variable.\n\t*/\n\tG = Cudd_Regular(g);\n\ttopg = cuddI(dd,G->index);\n\tif (topf > topg) {\n\t    topindex = G->index;\n\t    f1 = f0 = F;\n\t} else {\n\t    topindex = F->index;\n\t    f1 = cuddT(F);\n\t    f0 = cuddE(F);\n\t}\n\tif (topg > topf) {\n\t    g1 = g0 = g;\n\t} else {\n\t    g1 = cuddT(G);\n\t    g0 = cuddE(G);\n\t    if (g != G) {\n\t\tg1 = Cudd_Not(g1);\n\t\tg0 = Cudd_Not(g0);\n\t    }\n\t}\n\t/* Recursive step. */\n\tt = cuddBddComposeRecur(dd, f1, g1, proj);\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n\te = cuddBddComposeRecur(dd, f0, g0, proj);\n\tif (e == NULL) {\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n\n\tr = cuddBddIteRecur(dd, dd->vars[topindex], t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, t);\n\t    Cudd_IterDerefBdd(dd, e);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_IterDerefBdd(dd, t); /* t & e not necessarily part of r */\n\tCudd_IterDerefBdd(dd, e);\n\tcuddDeref(r);\n    }\n\n    cuddCacheInsert(dd,DD_BDD_COMPOSE_RECUR_TAG,F,g,proj,r);\n\n    return(Cudd_NotCond(r,comple));\n\n} /* end of cuddBddComposeRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addCompose.\n\n  @return the composed %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addCompose\n\n*/\nDdNode *\ncuddAddComposeRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode * proj)\n{\n    DdNode *f1, *f0, *g1, *g0, *r, *t, *e;\n    int v;\n    int topf, topg;\n    unsigned int topindex;\n\n    statLine(dd);\n    v = dd->perm[proj->index];\n    topf = cuddI(dd,f->index);\n\n    /* Terminal case. Subsumes the test for constant f. */\n    if (topf > v) return(f);\n\n    /* Check cache. */\n    r = cuddCacheLookup(dd,DD_ADD_COMPOSE_RECUR_TAG,f,g,proj);\n    if (r != NULL) {\n\treturn(r);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    if (topf == v) {\n\t/* Compose. */\n\tf1 = cuddT(f);\n\tf0 = cuddE(f);\n\tr = cuddAddIteRecur(dd, g, f1, f0);\n\tif (r == NULL) return(NULL);\n    } else {\n\t/* Compute cofactors of f and g. Remember the index of the top\n\t** variable.\n\t*/\n\ttopg = cuddI(dd,g->index);\n\tif (topf > topg) {\n\t    topindex = g->index;\n\t    f1 = f0 = f;\n\t} else {\n\t    topindex = f->index;\n\t    f1 = cuddT(f);\n\t    f0 = cuddE(f);\n\t}\n\tif (topg > topf) {\n\t    g1 = g0 = g;\n\t} else {\n\t    g1 = cuddT(g);\n\t    g0 = cuddE(g);\n\t}\n\t/* Recursive step. */\n\tt = cuddAddComposeRecur(dd, f1, g1, proj);\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n\te = cuddAddComposeRecur(dd, f0, g0, proj);\n\tif (e == NULL) {\n\t    Cudd_RecursiveDeref(dd, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n\n\tif (t == e) {\n\t    r = t;\n\t} else {\n\t    r = cuddUniqueInter(dd, (int) topindex, t, e);\n\t    if (r == NULL) {\n\t\tCudd_RecursiveDeref(dd, t);\n\t\tCudd_RecursiveDeref(dd, e);\n\t\treturn(NULL);\n\t    }\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert(dd,DD_ADD_COMPOSE_RECUR_TAG,f,g,proj,r);\n\n    return(r);\n\n} /* end of cuddAddComposeRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the recursive step of Cudd_addPermute.\n\n  @details Recursively puts the %ADD in the order given in the\n  array permut. Checks for trivial cases to terminate recursion, then\n  splits on the children of this node.  Once the solutions for the\n  children are obtained, it puts into the current position the node\n  from the rest of the %ADD that should be here. Then returns this %ADD.\n  The key here is that the node being visited is NOT put in its proper\n  place by this instance, but rather is switched when its proper\n  position is reached in the recursion tree.<p>\n  The DdNode * that is returned is the same %ADD as passed in as node,\n  but in the new order.\n\n  @sideeffect None\n\n  @see Cudd_addPermute cuddBddPermuteRecur\n\n*/\nstatic DdNode *\ncuddAddPermuteRecur(\n  DdManager * manager /**< %DD manager */,\n  DdHashTable * table /**< computed table */,\n  DdNode * node /**< %ADD to be reordered */,\n  int * permut /**< permutation array */)\n{\n    DdNode\t*T,*E;\n    DdNode\t*res,*var;\n    int\t\tindex;\n    \n    statLine(manager);\n    /* Check for terminal case of constant node. */\n    if (cuddIsConstant(node)) {\n\treturn(node);\n    }\n\n    /* If problem already solved, look up answer and return. */\n    if (node->ref != 1 && (res = cuddHashTableLookup1(table,node)) != NULL) {\n#ifdef DD_DEBUG\n\tmanager->addPermuteRecurHits++;\n#endif\n\treturn(res);\n    }\n\n    /* Split and recur on children of this node. */\n    T = cuddAddPermuteRecur(manager,table,cuddT(node),permut);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n    E = cuddAddPermuteRecur(manager,table,cuddE(node),permut);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(manager, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    /* Move variable that should be in this position to this position\n    ** by creating a single var ADD for that variable, and calling\n    ** cuddAddIteRecur with the T and E we just created.\n    */\n    index = permut[node->index];\n    var = cuddUniqueInter(manager,index,DD_ONE(manager),DD_ZERO(manager));\n    if (var == NULL) return(NULL);\n    cuddRef(var);\n    res = cuddAddIteRecur(manager,var,T,E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(manager,var);\n\tCudd_RecursiveDeref(manager, T);\n\tCudd_RecursiveDeref(manager, E);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(manager,var);\n    Cudd_RecursiveDeref(manager, T);\n    Cudd_RecursiveDeref(manager, E);\n\n    /* Do not keep the result if the reference count is only 1, since\n    ** it will not be visited again.\n    */\n    if (node->ref != 1) {\n\tptrint fanout = (ptrint) node->ref;\n\tcuddSatDec(fanout);\n\tif (!cuddHashTableInsert1(table,node,res,fanout)) {\n\t    Cudd_RecursiveDeref(manager, res);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(res);\n    return(res);\n\n} /* end of cuddAddPermuteRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_bddPermute.\n\n  @details Recursively puts the %BDD in the order given in the array permut.\n  Checks for trivial cases to terminate recursion, then splits on the\n  children of this node.  Once the solutions for the children are\n  obtained, it puts into the current position the node from the rest of\n  the %BDD that should be here. Then returns this %BDD.\n  The key here is that the node being visited is NOT put in its proper\n  place by this instance, but rather is switched when its proper position\n  is reached in the recursion tree.<p>\n  The DdNode * that is returned is the same %BDD as passed in as node,\n  but in the new order.\n\n  @sideeffect None\n\n  @see Cudd_bddPermute cuddAddPermuteRecur\n\n*/\nstatic DdNode *\ncuddBddPermuteRecur(\n  DdManager * manager /**< %DD manager */,\n  DdHashTable * table /**< computed table */,\n  DdNode * node /**< %BDD to be reordered */,\n  int * permut /**< permutation array */)\n{\n    DdNode\t*N,*T,*E;\n    DdNode\t*res;\n    int\t\tindex;\n\n    statLine(manager);\n    N = Cudd_Regular(node);\n\n    /* Check for terminal case of constant node. */\n    if (cuddIsConstant(N)) {\n\treturn(node);\n    }\n\n    /* If problem already solved, look up answer and return. */\n    if (N->ref != 1 && (res = cuddHashTableLookup1(table,N)) != NULL) {\n#ifdef DD_DEBUG\n\tmanager->bddPermuteRecurHits++;\n#endif\n\treturn(Cudd_NotCond(res,N != node));\n    }\n\n    /* Split and recur on children of this node. */\n    T = cuddBddPermuteRecur(manager,table,cuddT(N),permut);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n    E = cuddBddPermuteRecur(manager,table,cuddE(N),permut);\n    if (E == NULL) {\n\tCudd_IterDerefBdd(manager, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    /* Move variable that should be in this position to this position\n    ** by retrieving the single var BDD for that variable, and calling\n    ** cuddBddIteRecur with the T and E we just created.\n    */\n    index = permut[N->index];\n    res = cuddBddIteRecur(manager,manager->vars[index],T,E);\n    if (res == NULL) {\n\tCudd_IterDerefBdd(manager, T);\n\tCudd_IterDerefBdd(manager, E);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_IterDerefBdd(manager, T);\n    Cudd_IterDerefBdd(manager, E);\n\n    /* Do not keep the result if the reference count is only 1, since\n    ** it will not be visited again.\n    */\n    if (N->ref != 1) {\n\tptrint fanout = (ptrint) N->ref;\n\tcuddSatDec(fanout);\n\tif (!cuddHashTableInsert1(table,N,res,fanout)) {\n\t    Cudd_IterDerefBdd(manager, res);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(res);\n    return(Cudd_NotCond(res,N != node));\n\n} /* end of cuddBddPermuteRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_bddVarMap.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddVarMap\n\n*/\nstatic DdNode *\ncuddBddVarMapRecur(\n  DdManager *manager /**< %DD manager */,\n  DdNode *f /**< %BDD to be remapped */)\n{\n    DdNode\t*F, *T, *E;\n    DdNode\t*res;\n    int\t\tindex;\n\n    statLine(manager);\n    F = Cudd_Regular(f);\n\n    /* Check for terminal case of constant node. */\n    if (cuddIsConstant(F)) {\n\treturn(f);\n    }\n\n    /* If problem already solved, look up answer and return. */\n    if (F->ref != 1 &&\n\t(res = cuddCacheLookup1(manager,Cudd_bddVarMap,F)) != NULL) {\n\treturn(Cudd_NotCond(res,F != f));\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    /* Split and recur on children of this node. */\n    T = cuddBddVarMapRecur(manager,cuddT(F));\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n    E = cuddBddVarMapRecur(manager,cuddE(F));\n    if (E == NULL) {\n\tCudd_IterDerefBdd(manager, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    /* Move variable that should be in this position to this position\n    ** by retrieving the single var BDD for that variable, and calling\n    ** cuddBddIteRecur with the T and E we just created.\n    */\n    index = manager->map[F->index];\n    res = cuddBddIteRecur(manager,manager->vars[index],T,E);\n    if (res == NULL) {\n\tCudd_IterDerefBdd(manager, T);\n\tCudd_IterDerefBdd(manager, E);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_IterDerefBdd(manager, T);\n    Cudd_IterDerefBdd(manager, E);\n\n    /* Do not keep the result if the reference count is only 1, since\n    ** it will not be visited again.\n    */\n    if (F->ref != 1) {\n\tcuddCacheInsert1(manager,Cudd_bddVarMap,F,res);\n    }\n    cuddDeref(res);\n    return(Cudd_NotCond(res,F != f));\n\n} /* end of cuddBddVarMapRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addVectorCompose.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\ncuddAddVectorComposeRecur(\n  DdManager * dd /**< %DD manager */,\n  DdHashTable * table /**< computed table */,\n  DdNode * f /**< %ADD in which to compose */,\n  DdNode ** vector /**< functions to substitute */,\n  int  deepest /**< depth of deepest substitution */)\n{\n    DdNode\t*T,*E;\n    DdNode\t*res;\n\n    statLine(dd);\n    /* If we are past the deepest substitution, return f. */\n    if (cuddI(dd,f->index) > deepest) {\n\treturn(f);\n    }\n\n    if ((res = cuddHashTableLookup1(table,f)) != NULL) {\n#ifdef DD_DEBUG\n\tdd->addVectorComposeHits++;\n#endif\n\treturn(res);\n    }\n\n    /* Split and recur on children of this node. */\n    T = cuddAddVectorComposeRecur(dd,table,cuddT(f),vector,deepest);\n    if (T == NULL)  return(NULL);\n    cuddRef(T);\n    E = cuddAddVectorComposeRecur(dd,table,cuddE(f),vector,deepest);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    /* Retrieve the 0-1 ADD for the current top variable and call\n    ** cuddAddIteRecur with the T and E we just created.\n    */\n    res = cuddAddIteRecur(dd,vector[f->index],T,E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\tCudd_RecursiveDeref(dd, E);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd, T);\n    Cudd_RecursiveDeref(dd, E);\n\n    /* Do not keep the result if the reference count is only 1, since\n    ** it will not be visited again\n    */\n    if (f->ref != 1) {\n\tptrint fanout = (ptrint) f->ref;\n\tcuddSatDec(fanout);\n\tif (!cuddHashTableInsert1(table,f,res,fanout)) {\n\t    Cudd_RecursiveDeref(dd, res);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(res);\n    return(res);\n\n} /* end of cuddAddVectorComposeRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addGeneralVectorCompose.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\ncuddAddGeneralVectorComposeRecur(\n  DdManager * dd /**< %DD manager */,\n  DdHashTable * table /**< computed table */,\n  DdNode * f /**< %ADD in which to compose */,\n  DdNode ** vectorOn /**< functions to substitute for x_i */,\n  DdNode ** vectorOff /**< functions to substitute for x_i' */,\n  int  deepest /**< depth of deepest substitution */)\n{\n    DdNode\t*T,*E,*t,*e;\n    DdNode\t*res;\n\n    /* If we are past the deepest substitution, return f. */\n    if (cuddI(dd,f->index) > deepest) {\n\treturn(f);\n    }\n\n    if ((res = cuddHashTableLookup1(table,f)) != NULL) {\n#ifdef DD_DEBUG\n\tdd->addGeneralVectorComposeHits++;\n#endif\n\treturn(res);\n    }\n\n    /* Split and recur on children of this node. */\n    T = cuddAddGeneralVectorComposeRecur(dd,table,cuddT(f),\n\t\t\t\t\t vectorOn,vectorOff,deepest);\n    if (T == NULL)  return(NULL);\n    cuddRef(T);\n    E = cuddAddGeneralVectorComposeRecur(dd,table,cuddE(f),\n\t\t\t\t\t vectorOn,vectorOff,deepest);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    /* Retrieve the compose ADDs for the current top variable and call\n    ** cuddAddApplyRecur with the T and E we just created.\n    */\n    t = cuddAddApplyRecur(dd,Cudd_addTimes,vectorOn[f->index],T);\n    if (t == NULL) {\n      Cudd_RecursiveDeref(dd,T);\n      Cudd_RecursiveDeref(dd,E);\n      return(NULL);\n    }\n    cuddRef(t);\n    e = cuddAddApplyRecur(dd,Cudd_addTimes,vectorOff[f->index],E);\n    if (e == NULL) {\n      Cudd_RecursiveDeref(dd,T);\n      Cudd_RecursiveDeref(dd,E);\n      Cudd_RecursiveDeref(dd,t);\n      return(NULL);\n    }\n    cuddRef(e);\n    res = cuddAddApplyRecur(dd,Cudd_addPlus,t,e);\n    if (res == NULL) {\n      Cudd_RecursiveDeref(dd,T);\n      Cudd_RecursiveDeref(dd,E);\n      Cudd_RecursiveDeref(dd,t);\n      Cudd_RecursiveDeref(dd,e);\n      return(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd,T);\n    Cudd_RecursiveDeref(dd,E);\n    Cudd_RecursiveDeref(dd,t);\n    Cudd_RecursiveDeref(dd,e);\n\n    /* Do not keep the result if the reference count is only 1, since\n    ** it will not be visited again\n    */\n    if (f->ref != 1) {\n\tptrint fanout = (ptrint) f->ref;\n\tcuddSatDec(fanout);\n\tif (!cuddHashTableInsert1(table,f,res,fanout)) {\n\t    Cudd_RecursiveDeref(dd, res);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(res);\n    return(res);\n\n} /* end of cuddAddGeneralVectorComposeRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addNonSimCompose.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\ncuddAddNonSimComposeRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** vector,\n  DdNode * key,\n  DdNode * cube,\n  int  lastsub)\n{\n    DdNode *f1, *f0, *key1, *key0, *cube1, *var;\n    DdNode *T,*E;\n    DdNode *r;\n    int top, topf, topk, topc;\n    unsigned int index;\n    int i;\n    DdNode **vect1;\n    DdNode **vect0;\n\n    statLine(dd);\n    /* If we are past the deepest substitution, return f. */\n    if (cube == DD_ONE(dd) || cuddIsConstant(f)) {\n\treturn(f);\n    }\n\n    /* If problem already solved, look up answer and return. */\n    r = cuddCacheLookup(dd,DD_ADD_NON_SIM_COMPOSE_TAG,f,key,cube);\n    if (r != NULL) {\n\treturn(r);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Find top variable. we just need to look at f, key, and cube,\n    ** because all the varibles in the gi are in key.\n    */\n    topf = cuddI(dd,f->index);\n    topk = cuddI(dd,key->index);\n    top = ddMin(topf,topk);\n    topc = cuddI(dd,cube->index);\n    top = ddMin(top,topc);\n    index = dd->invperm[top];\n\n    /* Compute the cofactors. */\n    if (topf == top) {\n\tf1 = cuddT(f);\n\tf0 = cuddE(f);\n    } else {\n\tf1 = f0 = f;\n    }\n    if (topc == top) {\n\tcube1 = cuddT(cube);\n\t/* We want to eliminate vector[index] from key. Otherwise\n\t** cache performance is severely affected. Hence we\n\t** existentially quantify the variable with index \"index\" from key.\n\t*/\n\tvar = Cudd_addIthVar(dd, (int) index);\n\tif (var == NULL) {\n\t    return(NULL);\n\t}\n\tcuddRef(var);\n\tkey1 = cuddAddExistAbstractRecur(dd, key, var);\n\tif (key1 == NULL) {\n\t    Cudd_RecursiveDeref(dd,var);\n\t    return(NULL);\n\t}\n\tcuddRef(key1);\n\tCudd_RecursiveDeref(dd,var);\n\tkey0 = key1;\n    } else {\n\tcube1 = cube;\n\tif (topk == top) {\n\t    key1 = cuddT(key);\n\t    key0 = cuddE(key);\n\t} else {\n\t    key1 = key0 = key;\n\t}\n\tcuddRef(key1);\n    }\n\n    /* Allocate two new vectors for the cofactors of vector. */\n    vect1 = ALLOC(DdNode *,lastsub);\n    if (vect1 == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tCudd_RecursiveDeref(dd,key1);\n\treturn(NULL);\n    }\n    vect0 = ALLOC(DdNode *,lastsub);\n    if (vect0 == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tCudd_RecursiveDeref(dd,key1);\n\tFREE(vect1);\n\treturn(NULL);\n    }\n\n    /* Cofactor the gi. Eliminate vect1[index] and vect0[index], because\n    ** we do not need them.\n    */\n    for (i = 0; i < lastsub; i++) {\n\tDdNode *gi = vector[i];\n\tif (gi == NULL) {\n\t    vect1[i] = vect0[i] = NULL;\n\t} else if (gi->index == index) {\n\t    vect1[i] = cuddT(gi);\n\t    vect0[i] = cuddE(gi);\n\t} else {\n\t    vect1[i] = vect0[i] = gi;\n\t}\n    }\n    vect1[index] = vect0[index] = NULL;\n\n    /* Recur on children. */\n    T = cuddAddNonSimComposeRecur(dd,f1,vect1,key1,cube1,lastsub);\n    FREE(vect1);\n    if (T == NULL) {\n\tCudd_RecursiveDeref(dd,key1);\n\tFREE(vect0);\n\treturn(NULL);\n    }\n    cuddRef(T);\n    E = cuddAddNonSimComposeRecur(dd,f0,vect0,key0,cube1,lastsub);\n    FREE(vect0);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd,key1);\n\tCudd_RecursiveDeref(dd,T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    Cudd_RecursiveDeref(dd,key1);\n\n    /* Retrieve the 0-1 ADD for the current top variable from vector,\n    ** and call cuddAddIteRecur with the T and E we just created.\n    */\n    r = cuddAddIteRecur(dd,vector[index],T,E);\n    if (r == NULL) {\n\tCudd_RecursiveDeref(dd,T);\n\tCudd_RecursiveDeref(dd,E);\n\treturn(NULL);\n    }\n    cuddRef(r);\n    Cudd_RecursiveDeref(dd,T);\n    Cudd_RecursiveDeref(dd,E);\n    cuddDeref(r);\n\n    /* Store answer to trim recursion. */\n    cuddCacheInsert(dd,DD_ADD_NON_SIM_COMPOSE_TAG,f,key,cube,r);\n\n    return(r);\n\n} /* end of cuddAddNonSimComposeRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddVectorCompose.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\ncuddBddVectorComposeRecur(\n  DdManager * dd /**< %DD manager */,\n  DdHashTable * table /**< computed table */,\n  DdNode * f /**< %BDD in which to compose */,\n  DdNode ** vector /**< functions to be composed */,\n  int deepest /**< depth of the deepest substitution */)\n{\n    DdNode\t*F,*T,*E;\n    DdNode\t*res;\n\n    statLine(dd);\n    F = Cudd_Regular(f);\n\n    /* If we are past the deepest substitution, return f. */\n    if (cuddI(dd,F->index) > deepest) {\n\treturn(f);\n    }\n\n    /* If problem already solved, look up answer and return. */\n    if ((res = cuddHashTableLookup1(table,F)) != NULL) {\n#ifdef DD_DEBUG\n\tdd->bddVectorComposeHits++;\n#endif\n\treturn(Cudd_NotCond(res,F != f));\n    }\n\n    /* Split and recur on children of this node. */\n    T = cuddBddVectorComposeRecur(dd,table,cuddT(F),vector, deepest);\n    if (T == NULL) return(NULL);\n    cuddRef(T);\n    E = cuddBddVectorComposeRecur(dd,table,cuddE(F),vector, deepest);\n    if (E == NULL) {\n\tCudd_IterDerefBdd(dd, T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    /* Call cuddBddIteRecur with the BDD that replaces the current top\n    ** variable and the T and E we just created.\n    */\n    res = cuddBddIteRecur(dd,vector[F->index],T,E);\n    if (res == NULL) {\n\tCudd_IterDerefBdd(dd, T);\n\tCudd_IterDerefBdd(dd, E);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_IterDerefBdd(dd, T);\n    Cudd_IterDerefBdd(dd, E);\t\n\n    /* Do not keep the result if the reference count is only 1, since\n    ** it will not be visited again.\n    */\n    if (F->ref != 1) {\n\tptrint fanout = (ptrint) F->ref;\n\tcuddSatDec(fanout);\n\tif (!cuddHashTableInsert1(table,F,res,fanout)) {\n\t    Cudd_IterDerefBdd(dd, res);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(res);\n    return(Cudd_NotCond(res,F != f));\n\n} /* end of cuddBddVectorComposeRecur */\n\n\n/**\n  @brief Comparison of a function to the i-th %ADD variable.\n\n  @return 1 if the function is the i-th %ADD variable; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddIsIthAddVar(\n  DdManager * dd,\n  DdNode * f,\n  unsigned int  i)\n{\n    return(f->index == i && cuddT(f) == DD_ONE(dd) && cuddE(f) == DD_ZERO(dd));\n\n} /* end of ddIsIthAddVar */\n\n\n/**\n  @brief Comparison of a pair of functions to the i-th %ADD variable.\n\n  @return 1 if the functions are the i-th %ADD variable and its\n  complement; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddIsIthAddVarPair(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  unsigned int  i)\n{\n    return(f->index == i && g->index == i && \n\t   cuddT(f) == DD_ONE(dd) && cuddE(f) == DD_ZERO(dd) &&\n\t   cuddT(g) == DD_ZERO(dd) && cuddE(g) == DD_ONE(dd));\n\n} /* end of ddIsIthAddVarPair */\n"
  },
  {
    "path": "cudd/cudd/cuddDecomp.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for %BDD decomposition.\n\n  @author Kavita Ravi, Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n#define DEPTH 5\n#define THRESHOLD 10\n#define NONE 0\n#define PAIR_ST 1\n#define PAIR_CR 2\n#define G_ST 3\n#define G_CR 4\n#define H_ST 5\n#define H_CR 6\n#define BOTH_G 7\n#define BOTH_H 8\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n/**\n * @brief Type of a pair of conjoined BDDs.\n */\ntypedef struct Conjuncts {\n    DdNode *g;\n    DdNode *h;\n} Conjuncts;\n\n/**\n   @brief Stats for one node.\n*/\ntypedef struct  NodeStat {\n    int distance;\n    int localRef;\n} NodeStat;\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n\n#define FactorsNotStored(factors)  ((int)((ptrint)(factors) & 01))\n\n#define FactorsComplement(factors) ((Conjuncts *)((ptrint)(factors) | 01))\n\n#define FactorsUncomplement(factors) ((Conjuncts *)((ptrint)(factors) ^ 01))\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic NodeStat * CreateBotDist (DdNode * node, st_table * distanceTable);\nstatic double CountMinterms (DdManager * dd, DdNode * node, double max, st_table * mintermTable, FILE *fp);\nstatic void ConjunctsFree (DdManager * dd, Conjuncts * factors);\nstatic int PairInTables (DdNode * g, DdNode * h, st_table * ghTable);\nstatic Conjuncts * CheckTablesCacheAndReturn (DdManager *manager, DdNode * node, DdNode * g, DdNode * h, st_table * ghTable, st_table * cacheTable);\nstatic Conjuncts * PickOnePair (DdManager * manager, DdNode * node, DdNode * g1, DdNode * h1, DdNode * g2, DdNode * h2, st_table * ghTable, st_table * cacheTable);\nstatic Conjuncts * CheckInTables (DdManager * manager, DdNode * node, DdNode * g1, DdNode * h1, DdNode * g2, DdNode * h2, st_table * ghTable, st_table * cacheTable, int * outOfMem);\nstatic Conjuncts * ZeroCase (DdManager * dd, DdNode * node, Conjuncts * factorsNv, st_table * ghTable, st_table * cacheTable, int switched);\nstatic Conjuncts * BuildConjuncts (DdManager * dd, DdNode * node, st_table * distanceTable, st_table * cacheTable, int approxDistance, int maxLocalRef, st_table * ghTable, st_table * mintermTable, int32_t *lastTimeG);\nstatic int cuddConjunctsAux (DdManager * dd, DdNode * f, DdNode ** c1, DdNode ** c2);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs two-way conjunctive decomposition of a %BDD.\n\n  @details This procedure owes its name to the use of supersetting to\n  obtain an initial factor of the given function.  The conjuncts\n  produced by this procedure tend to be imbalanced.\n\n  @return the number of conjuncts produced, that is, 2 if successful;\n  1 if no meaningful decomposition was found; 0 otherwise.\n\n  @sideeffect The factors are returned in an array as side effects.\n  The array is allocated by this function. It is the caller's responsibility\n  to free it. On successful completion, the conjuncts are already\n  referenced. If the function returns 0, the array for the conjuncts is\n  not allocated. If the function returns 1, the only factor equals the\n  function to be decomposed.\n\n  @see Cudd_bddApproxDisjDecomp Cudd_bddIterConjDecomp\n  Cudd_bddGenConjDecomp Cudd_bddVarConjDecomp Cudd_RemapOverApprox\n  Cudd_bddSqueeze Cudd_bddLICompaction\n\n*/\nint\nCudd_bddApproxConjDecomp(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be decomposed */,\n  DdNode *** conjuncts /**< address of the first factor */)\n{\n    DdNode *superset1, *superset2, *glocal, *hlocal;\n    int nvars = Cudd_SupportSize(dd,f);\n\n    /* Find a tentative first factor by overapproximation and minimization. */\n    superset1 = Cudd_RemapOverApprox(dd,f,nvars,0,1.0);\n    if (superset1 == NULL) return(0);\n    cuddRef(superset1);\n    superset2 = Cudd_bddSqueeze(dd,f,superset1);\n    if (superset2 == NULL) {\n\tCudd_RecursiveDeref(dd,superset1);\n\treturn(0);\n    }\n    cuddRef(superset2);\n    Cudd_RecursiveDeref(dd,superset1);\n\n    /* Compute the second factor by minimization. */\n    hlocal = Cudd_bddLICompaction(dd,f,superset2);\n    if (hlocal == NULL) {\n\tCudd_RecursiveDeref(dd,superset2);\n\treturn(0);\n    }\n    cuddRef(hlocal);\n\n    /* Refine the first factor by minimization. If h turns out to be f, this\n    ** step guarantees that g will be 1. */\n    glocal = Cudd_bddLICompaction(dd,superset2,hlocal);\n    if (glocal == NULL) {\n\tCudd_RecursiveDeref(dd,superset2);\n\tCudd_RecursiveDeref(dd,hlocal);\n\treturn(0);\n    }\n    cuddRef(glocal);\n    Cudd_RecursiveDeref(dd,superset2);\n\n    if (glocal != DD_ONE(dd)) {\n\tif (hlocal != DD_ONE(dd)) {\n\t    *conjuncts = ALLOC(DdNode *,2);\n\t    if (*conjuncts == NULL) {\n\t\tCudd_RecursiveDeref(dd,glocal);\n\t\tCudd_RecursiveDeref(dd,hlocal);\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    (*conjuncts)[0] = glocal;\n\t    (*conjuncts)[1] = hlocal;\n\t    return(2);\n\t} else {\n\t    Cudd_RecursiveDeref(dd,hlocal);\n\t    *conjuncts = ALLOC(DdNode *,1);\n\t    if (*conjuncts == NULL) {\n\t\tCudd_RecursiveDeref(dd,glocal);\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    (*conjuncts)[0] = glocal;\n\t    return(1);\n\t}\n    } else {\n\tCudd_RecursiveDeref(dd,glocal);\n\t*conjuncts = ALLOC(DdNode *,1);\n\tif (*conjuncts == NULL) {\n\t    Cudd_RecursiveDeref(dd,hlocal);\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t(*conjuncts)[0] = hlocal;\n\treturn(1);\n    }\n\n} /* end of Cudd_bddApproxConjDecomp */\n\n\n/**\n  @brief Performs two-way disjunctive decomposition of a %BDD.\n\n  @details The disjuncts produced by this procedure tend to be\n  imbalanced.\n\n  @return the number of disjuncts produced, that is, 2 if successful;\n  1 if no meaningful decomposition was found; 0 otherwise.\n\n  @sideeffect The two disjuncts are returned in an array as side effects.\n  The array is allocated by this function. It is the caller's responsibility\n  to free it. On successful completion, the disjuncts are already\n  referenced. If the function returns 0, the array for the disjuncts is\n  not allocated. If the function returns 1, the only factor equals the\n  function to be decomposed.\n\n  @see Cudd_bddApproxConjDecomp Cudd_bddIterDisjDecomp\n  Cudd_bddGenDisjDecomp Cudd_bddVarDisjDecomp\n\n*/\nint\nCudd_bddApproxDisjDecomp(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be decomposed */,\n  DdNode *** disjuncts /**< address of the array of the disjuncts */)\n{\n    int result, i;\n\n    result = Cudd_bddApproxConjDecomp(dd,Cudd_Not(f),disjuncts);\n    for (i = 0; i < result; i++) {\n\t(*disjuncts)[i] = Cudd_Not((*disjuncts)[i]);\n    }\n    return(result);\n\n} /* end of Cudd_bddApproxDisjDecomp */\n\n\n/**\n  @brief Performs two-way conjunctive decomposition of a %BDD.\n\n  @details This procedure owes its name to the iterated use of\n  supersetting to obtain a factor of the given function.  The\n  conjuncts produced by this procedure tend to be imbalanced.\n\n  @return the number of conjuncts produced, that is, 2 if successful;\n  1 if no meaningful decomposition was found; 0 otherwise.\n\n  @sideeffect The factors are returned in an array as side effects.\n  The array is allocated by this function. It is the caller's responsibility\n  to free it. On successful completion, the conjuncts are already\n  referenced. If the function returns 0, the array for the conjuncts is\n  not allocated. If the function returns 1, the only factor equals the\n  function to be decomposed.\n\n  @see Cudd_bddIterDisjDecomp Cudd_bddApproxConjDecomp\n  Cudd_bddGenConjDecomp Cudd_bddVarConjDecomp Cudd_RemapOverApprox\n  Cudd_bddSqueeze Cudd_bddLICompaction\n\n*/\nint\nCudd_bddIterConjDecomp(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be decomposed */,\n  DdNode *** conjuncts /**< address of the array of conjuncts */)\n{\n    DdNode *superset1, *superset2, *old[2], *res[2];\n    int sizeOld, sizeNew;\n    int nvars = Cudd_SupportSize(dd,f);\n\n    old[0] = DD_ONE(dd);\n    cuddRef(old[0]);\n    old[1] = f;\n    cuddRef(old[1]);\n    sizeOld = Cudd_SharingSize(old,2);\n\n    do {\n\t/* Find a tentative first factor by overapproximation and\n\t** minimization. */\n\tsuperset1 = Cudd_RemapOverApprox(dd,old[1],nvars,0,1.0);\n\tif (superset1 == NULL) {\n\t    Cudd_RecursiveDeref(dd,old[0]);\n\t    Cudd_RecursiveDeref(dd,old[1]);\n\t    return(0);\n\t}\n\tcuddRef(superset1);\n\tsuperset2 = Cudd_bddSqueeze(dd,old[1],superset1);\n\tif (superset2 == NULL) {\n\t    Cudd_RecursiveDeref(dd,old[0]);\n\t    Cudd_RecursiveDeref(dd,old[1]);\n\t    Cudd_RecursiveDeref(dd,superset1);\n\t    return(0);\n\t}\n\tcuddRef(superset2);\n\tCudd_RecursiveDeref(dd,superset1);\n\tres[0] = Cudd_bddAnd(dd,old[0],superset2);\n\tif (res[0] == NULL) {\n\t    Cudd_RecursiveDeref(dd,superset2);\n\t    Cudd_RecursiveDeref(dd,old[0]);\n\t    Cudd_RecursiveDeref(dd,old[1]);\n\t    return(0);\n\t}\n\tcuddRef(res[0]);\n\tCudd_RecursiveDeref(dd,superset2);\n\tif (res[0] == old[0]) {\n\t    Cudd_RecursiveDeref(dd,res[0]);\n\t    break;\t/* avoid infinite loop */\n\t}\n\n\t/* Compute the second factor by minimization. */\n\tres[1] = Cudd_bddLICompaction(dd,old[1],res[0]);\n\tif (res[1] == NULL) {\n\t    Cudd_RecursiveDeref(dd,old[0]);\n\t    Cudd_RecursiveDeref(dd,old[1]);\n\t    return(0);\n\t}\n\tcuddRef(res[1]);\n\n\tsizeNew = Cudd_SharingSize(res,2);\n\tif (sizeNew <= sizeOld) {\n\t    Cudd_RecursiveDeref(dd,old[0]);\n\t    old[0] = res[0];\n\t    Cudd_RecursiveDeref(dd,old[1]);\n\t    old[1] = res[1];\n\t    sizeOld = sizeNew;\n\t} else {\n\t    Cudd_RecursiveDeref(dd,res[0]);\n\t    Cudd_RecursiveDeref(dd,res[1]);\n\t    break;\n\t}\n\n    } while (1);\n\n    /* Refine the first factor by minimization. If h turns out to\n    ** be f, this step guarantees that g will be 1. */\n    superset1 = Cudd_bddLICompaction(dd,old[0],old[1]);\n    if (superset1 == NULL) {\n\tCudd_RecursiveDeref(dd,old[0]);\n\tCudd_RecursiveDeref(dd,old[1]);\n\treturn(0);\n    }\n    cuddRef(superset1);\n    Cudd_RecursiveDeref(dd,old[0]);\n    old[0] = superset1;\n\n    if (old[0] != DD_ONE(dd)) {\n\tif (old[1] != DD_ONE(dd)) {\n\t    *conjuncts = ALLOC(DdNode *,2);\n\t    if (*conjuncts == NULL) {\n\t\tCudd_RecursiveDeref(dd,old[0]);\n\t\tCudd_RecursiveDeref(dd,old[1]);\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    (*conjuncts)[0] = old[0];\n\t    (*conjuncts)[1] = old[1];\n\t    return(2);\n\t} else {\n\t    Cudd_RecursiveDeref(dd,old[1]);\n\t    *conjuncts = ALLOC(DdNode *,1);\n\t    if (*conjuncts == NULL) {\n\t\tCudd_RecursiveDeref(dd,old[0]);\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    (*conjuncts)[0] = old[0];\n\t    return(1);\n\t}\n    } else {\n\tCudd_RecursiveDeref(dd,old[0]);\n\t*conjuncts = ALLOC(DdNode *,1);\n\tif (*conjuncts == NULL) {\n\t    Cudd_RecursiveDeref(dd,old[1]);\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t(*conjuncts)[0] = old[1];\n\treturn(1);\n    }\n\n} /* end of Cudd_bddIterConjDecomp */\n\n\n/**\n  @brief Performs two-way disjunctive decomposition of a %BDD.\n\n  @details The disjuncts produced by this procedure tend to be\n  imbalanced.\n\n  @return the number of disjuncts produced, that is, 2 if successful;\n  1 if no meaningful decomposition was found; 0 otherwise.\n\n  @sideeffect The two disjuncts are returned in an array as side effects.\n  The array is allocated by this function. It is the caller's responsibility\n  to free it. On successful completion, the disjuncts are already\n  referenced. If the function returns 0, the array for the disjuncts is\n  not allocated. If the function returns 1, the only factor equals the\n  function to be decomposed.\n\n  @see Cudd_bddIterConjDecomp Cudd_bddApproxDisjDecomp\n  Cudd_bddGenDisjDecomp Cudd_bddVarDisjDecomp\n\n*/\nint\nCudd_bddIterDisjDecomp(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be decomposed */,\n  DdNode *** disjuncts /**< address of the array of the disjuncts */)\n{\n    int result, i;\n\n    result = Cudd_bddIterConjDecomp(dd,Cudd_Not(f),disjuncts);\n    for (i = 0; i < result; i++) {\n\t(*disjuncts)[i] = Cudd_Not((*disjuncts)[i]);\n    }\n    return(result);\n\n} /* end of Cudd_bddIterDisjDecomp */\n\n\n/**\n  @brief Performs two-way conjunctive decomposition of a %BDD.\n\n  @details This procedure owes its name to the fact tht it generalizes\n  the decomposition based on the cofactors with respect to one\n  variable.  The conjuncts produced by this procedure tend to be\n  balanced.\n\n  @return the number of conjuncts produced, that is, 2 if successful;\n  1 if no meaningful decomposition was found; 0 otherwise.\n\n  @sideeffect The two factors are returned in an array as side effects.\n  The array is allocated by this function. It is the caller's responsibility\n  to free it. On successful completion, the conjuncts are already\n  referenced. If the function returns 0, the array for the conjuncts is\n  not allocated. If the function returns 1, the only factor equals the\n  function to be decomposed.\n\n  @see Cudd_bddGenDisjDecomp Cudd_bddApproxConjDecomp\n  Cudd_bddIterConjDecomp Cudd_bddVarConjDecomp\n\n*/\nint\nCudd_bddGenConjDecomp(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be decomposed */,\n  DdNode *** conjuncts /**< address of the array of conjuncts */)\n{\n    int result;\n    DdNode *glocal, *hlocal;\n\n    do {\n\tdd->reordered = 0;\n\tresult = cuddConjunctsAux(dd, f, &glocal, &hlocal);\n    } while (dd->reordered == 1);\n\n    if (result == 0) {\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(0);\n    }\n\n    if (glocal != DD_ONE(dd)) {\n\tif (hlocal != DD_ONE(dd)) {\n\t    *conjuncts = ALLOC(DdNode *,2);\n\t    if (*conjuncts == NULL) {\n\t\tCudd_RecursiveDeref(dd,glocal);\n\t\tCudd_RecursiveDeref(dd,hlocal);\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    (*conjuncts)[0] = glocal;\n\t    (*conjuncts)[1] = hlocal;\n\t    return(2);\n\t} else {\n\t    Cudd_RecursiveDeref(dd,hlocal);\n\t    *conjuncts = ALLOC(DdNode *,1);\n\t    if (*conjuncts == NULL) {\n\t\tCudd_RecursiveDeref(dd,glocal);\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    (*conjuncts)[0] = glocal;\n\t    return(1);\n\t}\n    } else {\n\tCudd_RecursiveDeref(dd,glocal);\n\t*conjuncts = ALLOC(DdNode *,1);\n\tif (*conjuncts == NULL) {\n\t    Cudd_RecursiveDeref(dd,hlocal);\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t(*conjuncts)[0] = hlocal;\n\treturn(1);\n    }\n\n} /* end of Cudd_bddGenConjDecomp */\n\n\n/**\n  @brief Performs two-way disjunctive decomposition of a %BDD.\n\n  @details The disjuncts produced by this procedure tend to be\n  balanced.\n\n  @return the number of disjuncts produced, that is, 2 if successful;\n  1 if no meaningful decomposition was found; 0 otherwise.\n\n  @sideeffect The two disjuncts are returned in an array as side effects.\n  The array is allocated by this function. It is the caller's responsibility\n  to free it. On successful completion, the disjuncts are already\n  referenced. If the function returns 0, the array for the disjuncts is\n  not allocated. If the function returns 1, the only factor equals the\n  function to be decomposed.\n\n  @see Cudd_bddGenConjDecomp Cudd_bddApproxDisjDecomp\n  Cudd_bddIterDisjDecomp Cudd_bddVarDisjDecomp\n\n*/\nint\nCudd_bddGenDisjDecomp(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be decomposed */,\n  DdNode *** disjuncts /**< address of the array of the disjuncts */)\n{\n    int result, i;\n\n    result = Cudd_bddGenConjDecomp(dd,Cudd_Not(f),disjuncts);\n    for (i = 0; i < result; i++) {\n\t(*disjuncts)[i] = Cudd_Not((*disjuncts)[i]);\n    }\n    return(result);\n\n} /* end of Cudd_bddGenDisjDecomp */\n\n\n/**\n  @brief Performs two-way conjunctive decomposition of a %BDD.\n\n  @details Conjunctively decomposes one %BDD according to a\n  variable.  If <code>f</code> is the function of the %BDD and\n  <code>x</code> is the variable, the decomposition is\n  <code>(f+x)(f+x')</code>.  The variable is chosen so as to balance\n  the sizes of the two conjuncts and to keep them small.\n\n  @return the number of conjuncts produced, that is, 2 if successful;\n  1 if no meaningful decomposition was found; 0 otherwise.\n\n  @sideeffect The two factors are returned in an array as side effects.\n  The array is allocated by this function. It is the caller's responsibility\n  to free it. On successful completion, the conjuncts are already\n  referenced. If the function returns 0, the array for the conjuncts is\n  not allocated. If the function returns 1, the only factor equals the\n  function to be decomposed.\n\n  @see Cudd_bddVarDisjDecomp Cudd_bddGenConjDecomp\n  Cudd_bddApproxConjDecomp Cudd_bddIterConjDecomp\n\n*/\nint\nCudd_bddVarConjDecomp(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be decomposed */,\n  DdNode *** conjuncts /**< address of the array of conjuncts */)\n{\n    int best;\n    int min;\n    DdNode *support, *scan, *var, *glocal, *hlocal;\n\n    /* Find best cofactoring variable. */\n    support = Cudd_Support(dd,f);\n    if (support == NULL) return(0);\n    if (Cudd_IsConstantInt(support)) {\n\t*conjuncts = ALLOC(DdNode *,1);\n\tif (*conjuncts == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t(*conjuncts)[0] = f;\n\tcuddRef((*conjuncts)[0]);\n\treturn(1);\n    }\n    cuddRef(support);\n    min = 1000000000;\n    best = -1;\n    scan = support;\n    while (!Cudd_IsConstantInt(scan)) {\n        int i, est1, est0, est;\n\ti = scan->index;\n\test1 = Cudd_EstimateCofactor(dd,f,i,1);\n        if (est1 == CUDD_OUT_OF_MEM) return(0);\n\test0 = Cudd_EstimateCofactor(dd,f,i,0);\n        if (est0 == CUDD_OUT_OF_MEM) return(0);\n\t/* Minimize the size of the larger of the two cofactors. */\n\test = (est1 > est0) ? est1 : est0;\n\tif (est < min) {\n\t    min = est;\n\t    best = i;\n\t}\n\tscan = cuddT(scan);\n    }\n#ifdef DD_DEBUG\n    assert(best >= 0 && best < dd->size);\n#endif\n    Cudd_RecursiveDeref(dd,support);\n\n    var = Cudd_bddIthVar(dd,best);\n    glocal = Cudd_bddOr(dd,f,var);\n    if (glocal == NULL) {\n\treturn(0);\n    }\n    cuddRef(glocal);\n    hlocal = Cudd_bddOr(dd,f,Cudd_Not(var));\n    if (hlocal == NULL) {\n\tCudd_RecursiveDeref(dd,glocal);\n\treturn(0);\n    }\n    cuddRef(hlocal);\n\n    if (glocal != DD_ONE(dd)) {\n\tif (hlocal != DD_ONE(dd)) {\n\t    *conjuncts = ALLOC(DdNode *,2);\n\t    if (*conjuncts == NULL) {\n\t\tCudd_RecursiveDeref(dd,glocal);\n\t\tCudd_RecursiveDeref(dd,hlocal);\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    (*conjuncts)[0] = glocal;\n\t    (*conjuncts)[1] = hlocal;\n\t    return(2);\n\t} else {\n\t    Cudd_RecursiveDeref(dd,hlocal);\n\t    *conjuncts = ALLOC(DdNode *,1);\n\t    if (*conjuncts == NULL) {\n\t\tCudd_RecursiveDeref(dd,glocal);\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    (*conjuncts)[0] = glocal;\n\t    return(1);\n\t}\n    } else {\n\tCudd_RecursiveDeref(dd,glocal);\n\t*conjuncts = ALLOC(DdNode *,1);\n\tif (*conjuncts == NULL) {\n\t    Cudd_RecursiveDeref(dd,hlocal);\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t(*conjuncts)[0] = hlocal;\n\treturn(1);\n    }\n\n} /* end of Cudd_bddVarConjDecomp */\n\n\n/**\n  @brief Performs two-way disjunctive decomposition of a %BDD.\n\n  @details Performs two-way disjunctive decomposition of a %BDD\n  according to a variable. If <code>f</code> is the function of the\n  %BDD and <code>x</code> is the variable, the decomposition is\n  <code>f*x + f*x'</code>.  The variable is chosen so as to balance\n  the sizes of the two disjuncts and to keep them small.\n\n  @return the number of disjuncts produced, that is, 2 if successful;\n  1 if no meaningful decomposition was found; 0 otherwise.\n\n  @sideeffect The two disjuncts are returned in an array as side effects.\n  The array is allocated by this function. It is the caller's responsibility\n  to free it. On successful completion, the disjuncts are already\n  referenced. If the function returns 0, the array for the disjuncts is\n  not allocated. If the function returns 1, the only factor equals the\n  function to be decomposed.\n\n  @see Cudd_bddVarConjDecomp Cudd_bddApproxDisjDecomp\n  Cudd_bddIterDisjDecomp Cudd_bddGenDisjDecomp\n\n*/\nint\nCudd_bddVarDisjDecomp(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be decomposed */,\n  DdNode *** disjuncts /**< address of the array of the disjuncts */)\n{\n    int result, i;\n\n    result = Cudd_bddVarConjDecomp(dd,Cudd_Not(f),disjuncts);\n    for (i = 0; i < result; i++) {\n\t(*disjuncts)[i] = Cudd_Not((*disjuncts)[i]);\n    }\n    return(result);\n\n} /* end of Cudd_bddVarDisjDecomp */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Get longest distance of node from constant.\n\n  @return the distance of the root from the constant if successful;\n  CUDD_OUT_OF_MEM otherwise.\n\n  @sideeffect None\n\n*/\nstatic NodeStat *\nCreateBotDist(\n  DdNode * node,\n  st_table * distanceTable)\n{\n    DdNode *N, *Nv, *Nnv;\n    int distance, distanceNv, distanceNnv;\n    NodeStat *nodeStat, *nodeStatNv, *nodeStatNnv;\n\n#if 0\n    if (Cudd_IsConstantInt(node)) {\n\treturn(0);\n    }\n#endif\n    \n    /* Return the entry in the table if found. */\n    N = Cudd_Regular(node);\n    if (st_lookup(distanceTable, N, (void **) &nodeStat)) {\n\tnodeStat->localRef++;\n\treturn(nodeStat);\n    }\n\n    Nv = cuddT(N);\n    Nnv = cuddE(N);\n    Nv = Cudd_NotCond(Nv, Cudd_IsComplement(node));\n    Nnv = Cudd_NotCond(Nnv, Cudd_IsComplement(node));\n\n    /* Recur on the children. */\n    nodeStatNv = CreateBotDist(Nv, distanceTable);\n    if (nodeStatNv == NULL) return(NULL);\n    distanceNv = nodeStatNv->distance;\n\n    nodeStatNnv = CreateBotDist(Nnv, distanceTable);\n    if (nodeStatNnv == NULL) return(NULL);\n    distanceNnv = nodeStatNnv->distance;\n    /* Store max distance from constant; note sometimes this distance\n    ** may be to 0.\n    */\n    distance = (distanceNv > distanceNnv) ? (distanceNv+1) : (distanceNnv + 1);\n\n    nodeStat = ALLOC(NodeStat, 1);\n    if (nodeStat == NULL) {\n\treturn(0);\n    }\n    nodeStat->distance = distance;\n    nodeStat->localRef = 1;\n    \n    if (st_insert(distanceTable, N, nodeStat) ==\n\tST_OUT_OF_MEM) {\n\treturn(0);\n\n    }\n    return(nodeStat);\n\n} /* end of CreateBotDist */\n\n\n/**\n  @brief Count the number of minterms of each node ina a %BDD and\n  store it in a hash table.\n\n  @sideeffect None\n\n*/\nstatic double\nCountMinterms(\n  DdManager * dd,\n  DdNode * node,\n  double  max,\n  st_table * mintermTable,\n  FILE *fp)\n{\n    DdNode *N, *Nv, *Nnv;\n    double min, minNv, minNnv;\n    double *dummy;\n\n    N = Cudd_Regular(node);\n\n    if (cuddIsConstant(N)) {\n        if (node == Cudd_Not(DD_ONE(dd))) {\n\t    return(0);\n\t} else {\n\t    return(max);\n\t}\n    }\n\n    /* Return the entry in the table if found. */\n    if (st_lookup(mintermTable, node, (void **) &dummy)) {\n        min = *dummy;\n\treturn(min);\n    }\n\n    Nv = cuddT(N);\n    Nnv = cuddE(N);\n    Nv = Cudd_NotCond(Nv, Cudd_IsComplement(node));\n    Nnv = Cudd_NotCond(Nnv, Cudd_IsComplement(node));\n\n    /* Recur on the children. */\n    minNv = CountMinterms(dd, Nv, max, mintermTable, fp);\n    if (minNv == -1.0) return(-1.0);\n    minNnv = CountMinterms(dd, Nnv, max, mintermTable, fp);\n    if (minNnv == -1.0) return(-1.0);\n    min = minNv / 2.0 + minNnv / 2.0;\n    /* store \n     */\n\n    dummy = ALLOC(double, 1);\n    if (dummy == NULL) return(-1.0);\n    *dummy = min;\n    if (st_insert(mintermTable, node, dummy) == ST_OUT_OF_MEM) {\n\t(void) fprintf(fp, \"st table insert failed\\n\");\n    }\n    return(min);\n\n} /* end of CountMinterms */\n\n\n/**\n  @brief Free factors structure\n\n  @sideeffect None\n\n*/\nstatic void\nConjunctsFree(\n  DdManager * dd,\n  Conjuncts * factors)\n{\n    Cudd_RecursiveDeref(dd, factors->g);\n    Cudd_RecursiveDeref(dd, factors->h);\n    FREE(factors);\n    return;\n\n} /* end of ConjunctsFree */\n\n\n/**\n  @brief Check whether the given pair is in the tables.\n\n  @details gTable and hTable are combined.\n  absence in both is indicated by 0,\n  presence in gTable is indicated by 1,\n  presence in hTable by 2 and\n  presence in both by 3.\n  The values returned by this function are PAIR_ST,\n  PAIR_CR, G_ST, G_CR, H_ST, H_CR, BOTH_G, BOTH_H, NONE.\n  PAIR_ST implies g in gTable and h in hTable\n  PAIR_CR implies g in hTable and h in gTable\n  G_ST implies g in gTable and h not in any table\n  G_CR implies g in hTable and h not in any table\n  H_ST implies h in hTable and g not in any table\n  H_CR implies h in gTable and g not in any table\n  BOTH_G implies both in gTable\n  BOTH_H implies both in hTable\n  NONE implies none in table; \n\n  @see CheckTablesCacheAndReturn CheckInTables\n\n*/\nstatic int\nPairInTables(\n  DdNode * g,\n  DdNode * h,\n  st_table * ghTable)\n{\n    int valueG, valueH, gPresent, hPresent;\n\n    valueG = valueH = gPresent = hPresent = 0;\n    \n    gPresent = st_lookup_int(ghTable, Cudd_Regular(g), &valueG);\n    hPresent = st_lookup_int(ghTable, Cudd_Regular(h), &valueH);\n\n    if (!gPresent && !hPresent) return(NONE);\n\n    if (!hPresent) {\n\tif (valueG & 1) return(G_ST);\n\tif (valueG & 2) return(G_CR);\n    }\n    if (!gPresent) {\n\tif (valueH & 1) return(H_CR);\n\tif (valueH & 2) return(H_ST);\n    }\n    /* both in tables */\n    if ((valueG & 1) && (valueH & 2)) return(PAIR_ST);\n    if ((valueG & 2) && (valueH & 1)) return(PAIR_CR);\n    \n    if (valueG & 1) {\n\treturn(BOTH_G);\n    } else {\n\treturn(BOTH_H);\n    }\n    \n} /* end of PairInTables */\n\n\n/**\n  @brief Check the tables for the existence of pair and return one\n  combination, cache the result.\n\n  @details The assumption is that one of the conjuncts is already in\n  the tables.\n\n  @sideeffect g and h referenced for the cache\n\n  @see ZeroCase\n\n*/\nstatic Conjuncts *\nCheckTablesCacheAndReturn(\n  DdManager * manager,\n  DdNode * node,\n  DdNode * g,\n  DdNode * h,\n  st_table * ghTable,\n  st_table * cacheTable)\n{\n    int pairValue;\n    int value;\n    Conjuncts *factors;\n    \n    value = 0;\n    /* check tables */\n    pairValue = PairInTables(g, h, ghTable);\n    assert(pairValue != NONE);\n    /* if both dont exist in table, we know one exists(either g or h).\n     * Therefore store the other and proceed\n     */\n    factors = ALLOC(Conjuncts, 1);\n    if (factors == NULL) return(NULL);\n    if ((pairValue == BOTH_H) || (pairValue == H_ST)) {\n\tif (g != DD_ONE(manager)) {\n\t    value = 0;\n\t    if (st_lookup_int(ghTable, Cudd_Regular(g), &value)) {\n\t\tvalue |= 1;\n\t    } else {\n\t\tvalue = 1;\n\t    }\n\t    if (st_insert(ghTable, Cudd_Regular(g),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\treturn(NULL);\n\t    }\n\t}\n\tfactors->g = g;\n\tfactors->h = h;\n    } else  if ((pairValue == BOTH_G) || (pairValue == G_ST)) {\n\tif (h != DD_ONE(manager)) {\n\t    value = 0;\n\t    if (st_lookup_int(ghTable, Cudd_Regular(h), &value)) {\n\t\tvalue |= 2;\n\t    } else {\n\t\tvalue = 2;\n\t    }\n\t    if (st_insert(ghTable, Cudd_Regular(h),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\treturn(NULL);\n\t    }\n\t}\n\tfactors->g = g;\n\tfactors->h = h;\n    } else if (pairValue == H_CR) {\n\tif (g != DD_ONE(manager)) {\n\t    value = 2;\n\t    if (st_insert(ghTable, Cudd_Regular(g),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\treturn(NULL);\n\t    }\n\t}\n\tfactors->g = h;\n\tfactors->h = g;\n    } else if (pairValue == G_CR) {\n\tif (h != DD_ONE(manager)) {\n\t    value = 1;\n\t    if (st_insert(ghTable, Cudd_Regular(h),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\treturn(NULL);\n\t    }\n\t}\n\tfactors->g = h;\n\tfactors->h = g;\n    } else if (pairValue == PAIR_CR) {\n    /* pair exists in table */\n\tfactors->g = h;\n\tfactors->h = g;\n    } else if (pairValue == PAIR_ST) {\n\tfactors->g = g;\n\tfactors->h = h;\n    }\n\t    \n    /* cache the result for this node */\n    if (st_insert(cacheTable, node, factors) == ST_OUT_OF_MEM) {\n\tFREE(factors);\n\treturn(NULL);\n    }\n\n    return(factors);\n\n} /* end of CheckTablesCacheAndReturn */\n\t\n/**\n  @brief Check the tables for the existence of pair and return one\n  combination, store in cache.\n\n  @details The pair that has more pointers to it is picked. An\n  approximation of the number of local pointers is made by taking the\n  reference count of the pairs sent.\n\n  @see ZeroCase BuildConjuncts\n\n*/\nstatic Conjuncts *\nPickOnePair(\n  DdManager * manager,\n  DdNode * node,\n  DdNode * g1,\n  DdNode * h1,\n  DdNode * g2,\n  DdNode * h2,\n  st_table * ghTable,\n  st_table * cacheTable)\n{\n    int value;\n    Conjuncts *factors;\n    int oneRef, twoRef;\n    \n    factors = ALLOC(Conjuncts, 1);\n    if (factors == NULL) return(NULL);\n\n    /* count the number of pointers to pair 2 */\n    if (h2 == DD_ONE(manager)) {\n\ttwoRef = (Cudd_Regular(g2))->ref;\n    } else if (g2 == DD_ONE(manager)) {\n\ttwoRef = (Cudd_Regular(h2))->ref;\n    } else {\n\ttwoRef = ((Cudd_Regular(g2))->ref + (Cudd_Regular(h2))->ref)/2;\n    }\n\n    /* count the number of pointers to pair 1 */\n    if (h1 == DD_ONE(manager)) {\n\toneRef  = (Cudd_Regular(g1))->ref;\n    } else if (g1 == DD_ONE(manager)) {\n\toneRef  = (Cudd_Regular(h1))->ref;\n    } else {\n\toneRef = ((Cudd_Regular(g1))->ref + (Cudd_Regular(h1))->ref)/2;\n    }\n\n    /* pick the pair with higher reference count */\n    if (oneRef >= twoRef) {\n\tfactors->g = g1;\n\tfactors->h = h1;\n    } else {\n\tfactors->g = g2;\n\tfactors->h = h2;\n    }\n    \n    /*\n     * Store computed factors in respective tables to encourage\n     * recombination.\n     */\n    if (factors->g != DD_ONE(manager)) {\n\t/* insert g in htable */\n\tvalue = 0;\n\tif (st_lookup_int(ghTable, Cudd_Regular(factors->g), &value)) {\n\t    if (value == 2) {\n\t\tvalue |= 1;\n\t\tif (st_insert(ghTable, Cudd_Regular(factors->g),\n\t\t\t      (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t    FREE(factors);\n\t\t    return(NULL);\n\t\t}\n\t    }\n\t} else {\n\t    value = 1;\n\t    if (st_insert(ghTable, Cudd_Regular(factors->g),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    }\n\n    if (factors->h != DD_ONE(manager)) {\n\t/* insert h in htable */\n\tvalue = 0;\n\tif (st_lookup_int(ghTable, Cudd_Regular(factors->h), &value)) {\n\t    if (value == 1) {\n\t\tvalue |= 2;\n\t\tif (st_insert(ghTable, Cudd_Regular(factors->h),\n\t\t\t      (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t    FREE(factors);\n\t\t    return(NULL);\n\t\t}\n\t    }\t    \n\t} else {\n\t    value = 2;\n\t    if (st_insert(ghTable, Cudd_Regular(factors->h),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    }\n    \n    /* Store factors in cache table for later use. */\n    if (st_insert(cacheTable, node, factors) ==\n\t    ST_OUT_OF_MEM) {\n\tFREE(factors);\n\treturn(NULL);\n    }\n\n    return(factors);\n\n} /* end of PickOnePair */\n\n\n/**\n  @brief Check if the two pairs exist in the table.\n\n  @details If any of the conjuncts do exist, store in the cache and\n  return the corresponding pair.\n\n  @see ZeroCase BuildConjuncts\n\n*/\nstatic Conjuncts *\nCheckInTables(\n  DdManager * manager,\n  DdNode * node,\n  DdNode * g1,\n  DdNode * h1,\n  DdNode * g2,\n  DdNode * h2,\n  st_table * ghTable,\n  st_table * cacheTable,\n  int * outOfMem)\n{\n    int pairValue1,  pairValue2;\n    Conjuncts *factors;\n    int value;\n    \n    *outOfMem = 0;\n\n    /* check existence of pair in table */\n    pairValue1 = PairInTables(g1, h1, ghTable);\n    pairValue2 = PairInTables(g2, h2, ghTable);\n\n    /* if none of the 4 exist in the gh tables, return NULL */\n    if ((pairValue1 == NONE) && (pairValue2 == NONE)) {\n\treturn NULL;\n    }\n    \n    factors = ALLOC(Conjuncts, 1);\n    if (factors == NULL) {\n\t*outOfMem = 1;\n\treturn NULL;\n    }\n\n    /* pairs that already exist in the table get preference. */\n    if (pairValue1 == PAIR_ST) {\n\tfactors->g = g1;\n\tfactors->h = h1;\n    } else if (pairValue2 == PAIR_ST) {\n\tfactors->g = g2;\n\tfactors->h = h2;\n    } else if (pairValue1 == PAIR_CR) {\n\tfactors->g = h1;\n\tfactors->h = g1;\n    } else if (pairValue2 == PAIR_CR) {\n\tfactors->g = h2;\n\tfactors->h = g2;\n    } else if (pairValue1 == G_ST) {\n\t/* g exists in the table, h is not found in either table */\n\tfactors->g = g1;\n\tfactors->h = h1;\n\tif (h1 != DD_ONE(manager)) {\n\t    value = 2;\n\t    if (st_insert(ghTable, Cudd_Regular(h1),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue1 == BOTH_G) {\n\t/* g and h are  found in the g table */\n\tfactors->g = g1;\n\tfactors->h = h1;\n\tif (h1 != DD_ONE(manager)) {\n\t    value = 3;\n\t    if (st_insert(ghTable, Cudd_Regular(h1),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue1 == H_ST) {\n\t/* h exists in the table, g is not found in either table */\n\tfactors->g = g1;\n\tfactors->h = h1;\n\tif (g1 != DD_ONE(manager)) {\n\t    value = 1;\n\t    if (st_insert(ghTable, Cudd_Regular(g1),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue1 == BOTH_H) {\n\t/* g and h are  found in the h table */\n\tfactors->g = g1;\n\tfactors->h = h1;\n\tif (g1 != DD_ONE(manager)) {\n\t    value = 3;\n\t    if (st_insert(ghTable, Cudd_Regular(g1),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue2 == G_ST) {\n\t/* g exists in the table, h is not found in either table */\n\tfactors->g = g2;\n\tfactors->h = h2;\n\tif (h2 != DD_ONE(manager)) {\n\t    value = 2;\n\t    if (st_insert(ghTable, Cudd_Regular(h2),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if  (pairValue2 == BOTH_G) {\n\t/* g and h are  found in the g table */\n\tfactors->g = g2;\n\tfactors->h = h2;\n\tif (h2 != DD_ONE(manager)) {\n\t    value = 3;\n\t    if (st_insert(ghTable, Cudd_Regular(h2),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue2 == H_ST) { \n\t/* h exists in the table, g is not found in either table */\n\tfactors->g = g2;\n\tfactors->h = h2;\n\tif (g2 != DD_ONE(manager)) {\n\t    value = 1;\n\t    if (st_insert(ghTable, Cudd_Regular(g2),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue2 == BOTH_H) {\n\t/* g and h are  found in the h table */\n\tfactors->g = g2;\n\tfactors->h = h2;\n\tif (g2 != DD_ONE(manager)) {\n\t    value = 3;\n\t    if (st_insert(ghTable, Cudd_Regular(g2),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue1 == G_CR) {\n\t/* g found in h table and h in none */\n\tfactors->g = h1;\n\tfactors->h = g1;\n\tif (h1 != DD_ONE(manager)) {\n\t    value = 1;\n\t    if (st_insert(ghTable, Cudd_Regular(h1),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue1 == H_CR) {\n\t/* h found in g table and g in none */\n\tfactors->g = h1;\n\tfactors->h = g1;\n\tif (g1 != DD_ONE(manager)) {\n\t    value = 2;\n\t    if (st_insert(ghTable, Cudd_Regular(g1),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue2 == G_CR) {\n\t/* g found in h table and h in none */\n\tfactors->g = h2;\n\tfactors->h = g2;\n\tif (h2 != DD_ONE(manager)) {\n\t    value = 1;\n\t    if (st_insert(ghTable, Cudd_Regular(h2),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    } else if (pairValue2 == H_CR) {\n\t/* h found in g table and g in none */\n\tfactors->g = h2;\n\tfactors->h = g2;\n\tif (g2 != DD_ONE(manager)) {\n\t    value = 2;\n\t    if (st_insert(ghTable, Cudd_Regular(g2),\n\t\t\t  (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\t*outOfMem = 1;\n\t\tFREE(factors);\n\t\treturn(NULL);\n\t    }\n\t}\n    }\n    \n    /* Store factors in cache table for later use. */\n    if (st_insert(cacheTable, node, factors) ==\n\t    ST_OUT_OF_MEM) {\n\t*outOfMem = 1;\n\tFREE(factors);\n\treturn(NULL);\n    }\n    return factors;\n} /* end of CheckInTables */\n\n\n\n/**\n  @brief If one child is zero, do explicitly what Restrict does or better\n\n  @details First separate a variable and its child in the base\n  case. In case of a cube times a function, separate the cube and\n  function. As a last resort, look in tables.\n\n  @sideeffect Frees the BDDs in factorsNv. factorsNv itself is not freed\n  because it is freed above.\n\n  @see BuildConjuncts\n\n*/\nstatic Conjuncts *\nZeroCase(\n  DdManager * dd,\n  DdNode * node,\n  Conjuncts * factorsNv,\n  st_table * ghTable,\n  st_table * cacheTable,\n  int switched)\n{\n    int topid;\n    DdNode *g, *h, *g1, *g2, *h1, *h2, *x, *N, *G, *H, *Gv, *Gnv;\n    DdNode *Hv, *Hnv;\n    int value;\n    int outOfMem;\n    Conjuncts *factors;\n    \n    /* get var at this node */\n    N = Cudd_Regular(node);\n    topid = N->index;\n    x = dd->vars[topid];\n    x = (switched) ? Cudd_Not(x): x;\n    cuddRef(x);\n\n    /* Seprate variable and child */\n    if (factorsNv->g == DD_ONE(dd)) {\n\tCudd_RecursiveDeref(dd, factorsNv->g);\n\tfactors = ALLOC(Conjuncts, 1);\n\tif (factors == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    Cudd_RecursiveDeref(dd, factorsNv->h);\n\t    Cudd_RecursiveDeref(dd, x);\n\t    return(NULL);\n\t}\n\tfactors->g = x;\n\tfactors->h = factorsNv->h;\n\t/* cache the result*/\n\tif (st_insert(cacheTable, node, factors) == ST_OUT_OF_MEM) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    Cudd_RecursiveDeref(dd, factorsNv->h); \n\t    Cudd_RecursiveDeref(dd, x);\n\t    FREE(factors);\n\t    return NULL;\n\t}\n\t\n\t/* store  x in g table, the other node is already in the table */\n\tif (st_lookup_int(ghTable, Cudd_Regular(x), &value)) {\n\t    value |= 1;\n\t} else {\n\t    value = 1;\n\t}\n\tif (st_insert(ghTable, Cudd_Regular(x), (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return NULL;\n\t}\n\treturn(factors);\n    }\n    \n    /* Seprate variable and child */\n    if (factorsNv->h == DD_ONE(dd)) {\n\tCudd_RecursiveDeref(dd, factorsNv->h);\n\tfactors = ALLOC(Conjuncts, 1);\n\tif (factors == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    Cudd_RecursiveDeref(dd, factorsNv->g);\n\t    Cudd_RecursiveDeref(dd, x);\n\t    return(NULL);\n\t}\n\tfactors->g = factorsNv->g;\n\tfactors->h = x;\n\t/* cache the result. */\n \tif (st_insert(cacheTable, node, factors) == ST_OUT_OF_MEM) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    Cudd_RecursiveDeref(dd, factorsNv->g);\n\t    Cudd_RecursiveDeref(dd, x);\n\t    FREE(factors);\n\t    return(NULL);\n\t}\n\t/* store x in h table,  the other node is already in the table */\n\tif (st_lookup_int(ghTable, Cudd_Regular(x), &value)) {\n\t    value |= 2;\n\t} else {\n\t    value = 2;\n\t}\n\tif (st_insert(ghTable, Cudd_Regular(x), (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return NULL;\n\t}\n\treturn(factors);\n    }\n\n    G = Cudd_Regular(factorsNv->g);\n    Gv = cuddT(G);\n    Gnv = cuddE(G);\n    Gv = Cudd_NotCond(Gv, Cudd_IsComplement(node));\n    Gnv = Cudd_NotCond(Gnv, Cudd_IsComplement(node));\n    /* if the child below is a variable */\n    if ((Gv == Cudd_Not(DD_ONE(dd))) || (Gnv == Cudd_Not(DD_ONE(dd)))) {\n\th = factorsNv->h;\n\tg = cuddBddAndRecur(dd, x, factorsNv->g);\n\tif (g != NULL) \tcuddRef(g);\n\tCudd_RecursiveDeref(dd, factorsNv->g); \n\tCudd_RecursiveDeref(dd, x);\n\tif (g == NULL) {\n\t    Cudd_RecursiveDeref(dd, factorsNv->h); \n\t    return NULL;\n\t}\n\t/* CheckTablesCacheAndReturn responsible for allocating\n\t * factors structure., g,h referenced for cache store  the\n\t */\n\tfactors = CheckTablesCacheAndReturn(dd,\n\t\t\t\t\t    node,\n\t\t\t\t\t    g,\n\t\t\t\t\t    h,\n\t\t\t\t\t    ghTable,\n\t\t\t\t\t    cacheTable);\n\tif (factors == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    Cudd_RecursiveDeref(dd, g);\n\t    Cudd_RecursiveDeref(dd, h);\n\t}\n\treturn(factors); \n    }\n\n    H = Cudd_Regular(factorsNv->h);\n    Hv = cuddT(H);\n    Hnv = cuddE(H);\n    Hv = Cudd_NotCond(Hv, Cudd_IsComplement(node));\n    Hnv = Cudd_NotCond(Hnv, Cudd_IsComplement(node));\n    /* if the child below is a variable */\n    if ((Hv == Cudd_Not(DD_ONE(dd))) || (Hnv == Cudd_Not(DD_ONE(dd)))) {\n\tg = factorsNv->g;\n\th = cuddBddAndRecur(dd, x, factorsNv->h);\n\tif (h!= NULL) cuddRef(h);\n\tCudd_RecursiveDeref(dd, factorsNv->h);\n\tCudd_RecursiveDeref(dd, x);\n\tif (h == NULL) {\n\t    Cudd_RecursiveDeref(dd, factorsNv->g);\n\t    return NULL;\n\t}\n\t/* CheckTablesCacheAndReturn responsible for allocating\n\t * factors structure.g,h referenced for table store \n\t */\n\tfactors = CheckTablesCacheAndReturn(dd,\n\t\t\t\t\t    node,\n\t\t\t\t\t    g,\n\t\t\t\t\t    h,\n\t\t\t\t\t    ghTable,\n\t\t\t\t\t    cacheTable);\n\tif (factors == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    Cudd_RecursiveDeref(dd, g);\n\t    Cudd_RecursiveDeref(dd, h);\n\t}\n\treturn(factors); \n    }\n\n    /* build g1 = x*g; h1 = h */\n    /* build g2 = g; h2 = x*h */\n    Cudd_RecursiveDeref(dd, x);\n    h1 = factorsNv->h;\n    g1 = cuddBddAndRecur(dd, x, factorsNv->g);\n    if (g1 != NULL) cuddRef(g1);\n    if (g1 == NULL) {\n\tCudd_RecursiveDeref(dd, factorsNv->g); \n\tCudd_RecursiveDeref(dd, factorsNv->h);\n\treturn NULL;\n    }\n    \n    g2 = factorsNv->g;\n    h2 = cuddBddAndRecur(dd, x, factorsNv->h);\n    if (h2 != NULL) cuddRef(h2);\n    if (h2 == NULL) {\n\tCudd_RecursiveDeref(dd, factorsNv->h);\n\tCudd_RecursiveDeref(dd, factorsNv->g);\n\treturn NULL;\n    }\n\n    /* check whether any pair is in tables */\n    factors = CheckInTables(dd, node, g1, h1, g2, h2, ghTable, cacheTable, &outOfMem);\n    if (outOfMem) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tCudd_RecursiveDeref(dd, g1);\n\tCudd_RecursiveDeref(dd, h1);\n\tCudd_RecursiveDeref(dd, g2);\n\tCudd_RecursiveDeref(dd, h2);\n\treturn NULL;\n    }\n    if (factors != NULL) {\n\tif ((factors->g == g1) || (factors->g == h1)) {\n\t    Cudd_RecursiveDeref(dd, g2);\n\t    Cudd_RecursiveDeref(dd, h2);\n\t} else {\n\t    Cudd_RecursiveDeref(dd, g1);\n\t    Cudd_RecursiveDeref(dd, h1);\n\t}\n\treturn factors;\n    }\n\n    /* check for each pair in tables and choose one */\n    factors = PickOnePair(dd, node,g1, h1, g2, h2, ghTable, cacheTable);\n    if (factors == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tCudd_RecursiveDeref(dd, g1);\n\tCudd_RecursiveDeref(dd, h1);\n\tCudd_RecursiveDeref(dd, g2);\n\tCudd_RecursiveDeref(dd, h2);\n    } else {\n\t/* now free what was created and not used */\n\tif ((factors->g == g1) || (factors->g == h1)) {\n\t    Cudd_RecursiveDeref(dd, g2);\n\t    Cudd_RecursiveDeref(dd, h2);\n\t} else {\n\t    Cudd_RecursiveDeref(dd, g1);\n\t    Cudd_RecursiveDeref(dd, h1);\n\t}\n    }\n\t\n    return(factors);\n} /* end of ZeroCase */\n\n\n/**\n  @brief Builds the conjuncts recursively, bottom up.\n\n  @details Constants are returned as (f, f). The cache is checked for\n  previously computed result. The decomposition points are determined\n  by the local reference count of this node and the longest distance\n  from the constant. At the decomposition point, the factors returned\n  are (f, 1). Recur on the two children. The order is determined by\n  the heavier branch. Combine the factors of the two children and pick\n  the one that already occurs in the gh table. Occurence in g is\n  indicated by value 1, occurence in h by 2, occurence in both by 3.\n\n  @see cuddConjunctsAux\n\n*/\nstatic Conjuncts *\nBuildConjuncts(\n  DdManager * dd,\n  DdNode * node,\n  st_table * distanceTable,\n  st_table * cacheTable,\n  int approxDistance,\n  int maxLocalRef,\n  st_table * ghTable,\n  st_table * mintermTable,\n  int32_t *lastTimeG)\n{\n    int topid, distance;\n    Conjuncts *factorsNv = NULL, *factorsNnv = NULL, *factors;\n    void *dummy;\n    DdNode *N, *Nv, *Nnv, *temp, *g1, *g2, *h1, *h2, *topv;\n    double minNv = 0.0, minNnv = 0.0;\n    double *doubleDummy;\n    int switched =0;\n    int outOfMem;\n    int freeNv = 0, freeNnv = 0, freeTemp;\n    NodeStat *nodeStat;\n    int value;\n    DdNode * const one = DD_ONE(dd);\n    DdNode * const zero = Cudd_Not(one);\n\n    /* if f is constant, return (f,f) */\n    if (Cudd_IsConstantInt(node)) {\n\tfactors = ALLOC(Conjuncts, 1);\n\tif (factors == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(NULL);\n\t}\n\tfactors->g = node;\n\tfactors->h = node;\n\treturn(FactorsComplement(factors));\n    }\n\n    /* If result (a pair of conjuncts) in cache, return the factors. */\n    if (st_lookup(cacheTable, node, &dummy)) {\n        factors = (Conjuncts *) dummy;\n\treturn(factors);\n    }\n\n    /* check distance and local reference count of this node */\n    N = Cudd_Regular(node);\n    if (!st_lookup(distanceTable, N, (void **) &nodeStat)) {\n\t(void) fprintf(dd->err, \"Not in table, Something wrong\\n\");\n\tdd->errorCode = CUDD_INTERNAL_ERROR;\n\treturn(NULL);\n    }\n    distance = nodeStat->distance;\n\n    /* at or below decomposition point, return (f, 1) */\n    if (((nodeStat->localRef > maxLocalRef*2/3) &&\n\t (distance < approxDistance*2/3)) ||\n\t    (distance <= approxDistance/4)) {\n\tfactors = ALLOC(Conjuncts, 1);\n\tif (factors == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(NULL);\n\t}\n\t/* alternate assigning (f,1) */\n\tvalue = 0;\n\tif (st_lookup_int(ghTable, Cudd_Regular(node), &value)) {\n\t    if (value == 3) {\n\t\tif (!*lastTimeG) {\n\t\t    factors->g = node;\n\t\t    factors->h = one;\n\t\t    *lastTimeG = 1;\n\t\t} else {\n\t\t    factors->g = one;\n\t\t    factors->h = node;\n\t\t    *lastTimeG = 0; \n\t\t}\n\t    } else if (value == 1) {\n\t\tfactors->g = node;\n\t\tfactors->h = one;\n\t    } else {\n\t\tfactors->g = one;\n\t\tfactors->h = node;\n\t    }\n\t} else if (!*lastTimeG) {\n\t    factors->g = node;\n\t    factors->h = one;\n\t    *lastTimeG = 1;\n\t    value = 1;\n\t    if (st_insert(ghTable, Cudd_Regular(node), (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\tFREE(factors);\n\t\treturn NULL;\n\t    }\n\t} else {\n\t    factors->g = one;\n\t    factors->h = node;\n\t    *lastTimeG = 0;\n\t    value = 2;\n\t    if (st_insert(ghTable, Cudd_Regular(node), (void *)(ptruint)value) == ST_OUT_OF_MEM) {\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\tFREE(factors);\n\t\treturn NULL;\n\t    }\n\t}\n\treturn(FactorsComplement(factors));\n    }\n\n    /* get the children and recur */\n    Nv = cuddT(N);\n    Nnv = cuddE(N);\n    Nv = Cudd_NotCond(Nv, Cudd_IsComplement(node));\n    Nnv = Cudd_NotCond(Nnv, Cudd_IsComplement(node));\n\n    /* Choose which subproblem to solve first based on the number of\n     * minterms. We go first where there are more minterms.\n     */\n    if (!Cudd_IsConstantInt(Nv)) {\n\tif (!st_lookup(mintermTable, Nv, (void **) &doubleDummy)) {\n\t    (void) fprintf(dd->err, \"Not in table: Something wrong\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t    return(NULL);\n\t}\n\tminNv = *doubleDummy;\n    }\n\n    if (!Cudd_IsConstantInt(Nnv)) {\n\tif (!st_lookup(mintermTable, Nnv, (void **) &doubleDummy)) {\n\t    (void) fprintf(dd->err, \"Not in table: Something wrong\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t    return(NULL);\n\t}\n\tminNnv = *doubleDummy;\n    }\n\n    if (minNv < minNnv) {\n\ttemp = Nv;\n\tNv = Nnv;\n\tNnv = temp;\n\tswitched = 1;\n    }\n\n    /* build gt, ht recursively */\n    if (Nv != zero) {\n\tfactorsNv = BuildConjuncts(dd, Nv, distanceTable,\n\t\t\t\t   cacheTable, approxDistance, maxLocalRef, \n\t\t\t\t   ghTable, mintermTable, lastTimeG);\n\tif (factorsNv == NULL) return(NULL);\n\tfreeNv = FactorsNotStored(factorsNv);\n\tfactorsNv = (freeNv) ? FactorsUncomplement(factorsNv) : factorsNv;\n\tcuddRef(factorsNv->g);\n\tcuddRef(factorsNv->h);\n\n\t/* Deal with the zero case */\n\tif (Nnv == zero) {\n\t    /* is responsible for freeing factorsNv */\n\t    factors = ZeroCase(dd, node, factorsNv, ghTable,\n\t\t\t       cacheTable, switched);\n\t    if (freeNv) FREE(factorsNv);\n\t    return(factors);\n\t}\n    }\n\n    /* build ge, he recursively */\n    if (Nnv != zero) {\n\tfactorsNnv = BuildConjuncts(dd, Nnv, distanceTable,\n\t\t\t\t    cacheTable, approxDistance, maxLocalRef,\n\t\t\t\t    ghTable, mintermTable, lastTimeG);\n\tif (factorsNnv == NULL) {\n            if (factorsNv != NULL) {\n                Cudd_RecursiveDeref(dd, factorsNv->g);\n                Cudd_RecursiveDeref(dd, factorsNv->h);\n                if (freeNv) FREE(factorsNv);\n            }\n\t    return(NULL);\n\t}\n\tfreeNnv = FactorsNotStored(factorsNnv);\n\tfactorsNnv = (freeNnv) ? FactorsUncomplement(factorsNnv) : factorsNnv;\n\tcuddRef(factorsNnv->g);\n\tcuddRef(factorsNnv->h);\n\t\n\t/* Deal with the zero case */\n\tif (Nv == zero) {\n\t    /* is responsible for freeing factorsNv */\n\t    factors = ZeroCase(dd, node, factorsNnv, ghTable,\n\t\t\t       cacheTable, switched);\n\t    if (freeNnv) FREE(factorsNnv);\n\t    return(factors);\n\t}\n    }\n\n    /* construct the 2 pairs */\n    /* g1 = x*gt + x'*ge; h1 = x*ht + x'*he; */\n    /* g2 = x*gt + x'*he; h2 = x*ht + x'*ge */\n    if (switched) {\n\tfactors = factorsNnv;\n\tfactorsNnv = factorsNv;\n\tfactorsNv = factors;\n\tfreeTemp = freeNv;\n\tfreeNv = freeNnv;\n\tfreeNnv = freeTemp;\n    }\n\n    /* Build the factors for this node. */\n    topid = N->index;\n    topv = dd->vars[topid];\n\n    g1 = cuddBddIteRecur(dd, topv, factorsNv->g, factorsNnv->g);\n    if (g1 == NULL) {\n\tCudd_RecursiveDeref(dd, factorsNv->g);\n\tCudd_RecursiveDeref(dd, factorsNv->h);\n\tCudd_RecursiveDeref(dd, factorsNnv->g);\n\tCudd_RecursiveDeref(dd, factorsNnv->h);\n\tif (freeNv) FREE(factorsNv);\n\tif (freeNnv) FREE(factorsNnv);\n\treturn(NULL);\n    }\n\n    cuddRef(g1);\n\n    h1 = cuddBddIteRecur(dd, topv, factorsNv->h, factorsNnv->h);\n    if (h1 == NULL) {\n\tCudd_RecursiveDeref(dd, factorsNv->g);\n\tCudd_RecursiveDeref(dd, factorsNv->h);\n\tCudd_RecursiveDeref(dd, factorsNnv->g);\n\tCudd_RecursiveDeref(dd, factorsNnv->h);\n\tCudd_RecursiveDeref(dd, g1);\n\tif (freeNv) FREE(factorsNv);\n\tif (freeNnv) FREE(factorsNnv);\n\treturn(NULL);\n    }\n\n    cuddRef(h1);\n\n    g2 = cuddBddIteRecur(dd, topv, factorsNv->g, factorsNnv->h);\n    if (g2 == NULL) {\n\tCudd_RecursiveDeref(dd, factorsNv->h);\n\tCudd_RecursiveDeref(dd, factorsNv->g);\n\tCudd_RecursiveDeref(dd, factorsNnv->g);\n\tCudd_RecursiveDeref(dd, factorsNnv->h);\n\tCudd_RecursiveDeref(dd, g1);\n\tCudd_RecursiveDeref(dd, h1);\n\tif (freeNv) FREE(factorsNv);\n\tif (freeNnv) FREE(factorsNnv);\n\treturn(NULL);\n    }\n    cuddRef(g2);\n    Cudd_RecursiveDeref(dd, factorsNv->g);\n    Cudd_RecursiveDeref(dd, factorsNnv->h);\n\n    h2 = cuddBddIteRecur(dd, topv, factorsNv->h, factorsNnv->g);\n    if (h2 == NULL) {\n\tCudd_RecursiveDeref(dd, factorsNv->g);\n\tCudd_RecursiveDeref(dd, factorsNv->h);\n\tCudd_RecursiveDeref(dd, factorsNnv->g);\n\tCudd_RecursiveDeref(dd, factorsNnv->h);\n\tCudd_RecursiveDeref(dd, g1);\n\tCudd_RecursiveDeref(dd, h1);\n\tCudd_RecursiveDeref(dd, g2);\n\tif (freeNv) FREE(factorsNv);\n\tif (freeNnv) FREE(factorsNnv);\n\treturn(NULL);\n    }\n    cuddRef(h2);\n    Cudd_RecursiveDeref(dd, factorsNv->h);\n    Cudd_RecursiveDeref(dd, factorsNnv->g);\n    if (freeNv) FREE(factorsNv);\n    if (freeNnv) FREE(factorsNnv);\n\n    /* check for each pair in tables and choose one */\n    factors = CheckInTables(dd, node, g1, h1, g2, h2, ghTable, cacheTable, &outOfMem);\n    if (outOfMem) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tCudd_RecursiveDeref(dd, g1);\n\tCudd_RecursiveDeref(dd, h1);\n\tCudd_RecursiveDeref(dd, g2);\n\tCudd_RecursiveDeref(dd, h2);\n\treturn(NULL);\n    }\n    if (factors != NULL) {\n\tif ((factors->g == g1) || (factors->g == h1)) {\n\t    Cudd_RecursiveDeref(dd, g2);\n\t    Cudd_RecursiveDeref(dd, h2);\n\t} else {\n\t    Cudd_RecursiveDeref(dd, g1);\n\t    Cudd_RecursiveDeref(dd, h1);\n\t}\n\treturn(factors);\n    }\n\n    /* if not in tables, pick one pair */\n    factors = PickOnePair(dd, node, g1, h1, g2, h2, ghTable, cacheTable);\n    if (factors == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tCudd_RecursiveDeref(dd, g1);\n\tCudd_RecursiveDeref(dd, h1);\n\tCudd_RecursiveDeref(dd, g2);\n\tCudd_RecursiveDeref(dd, h2);\n    } else {\n\t/* now free what was created and not used */\n\tif ((factors->g == g1) || (factors->g == h1)) {\n\t    Cudd_RecursiveDeref(dd, g2);\n\t    Cudd_RecursiveDeref(dd, h2);\n\t} else {\n\t    Cudd_RecursiveDeref(dd, g1);\n\t    Cudd_RecursiveDeref(dd, h1);\n\t}\n    }\n\n    return(factors);\n\n} /* end of BuildConjuncts */\n\n\n/**\n  @brief Computes two conjunctive factors of f and places them in *c1 and *c2.\n\n  @details Sets up the required data - table of distances from the\n  constant and local reference count. Also minterm table.\n\n*/\nstatic int\ncuddConjunctsAux(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** c1,\n  DdNode ** c2)\n{\n    st_table *distanceTable = NULL;\n    st_table *cacheTable = NULL;\n    st_table *mintermTable = NULL;\n    st_table *ghTable = NULL;\n    st_generator *stGen;\n    char *key, *value;\n    Conjuncts *factors;\n    int distance, approxDistance;\n    double max, minterms;\n    int freeFactors;\n    NodeStat *nodeStat;\n    int maxLocalRef;\n    int32_t lastTimeG;\n\n    /* initialize */\n    *c1 = NULL;\n    *c2 = NULL;\n\n    /* initialize distances table */\n    distanceTable = st_init_table(st_ptrcmp,st_ptrhash);\n    if (distanceTable == NULL) goto outOfMem;\n    \n    /* make the entry for the constant */\n    nodeStat = ALLOC(NodeStat, 1);\n    if (nodeStat == NULL) goto outOfMem;\n    nodeStat->distance = 0;\n    nodeStat->localRef = 1;\n    if (st_insert(distanceTable, DD_ONE(dd), nodeStat) == ST_OUT_OF_MEM) {\n\tgoto outOfMem;\n    }\n\n    /* Count node distances from constant. */\n    nodeStat = CreateBotDist(f, distanceTable);\n    if (nodeStat == NULL) goto outOfMem;\n\n    /* set the distance for the decomposition points */\n    approxDistance = (DEPTH < nodeStat->distance) ? nodeStat->distance : DEPTH;\n    distance = nodeStat->distance;\n\n    if (distance < approxDistance) {\n\t/* Too small to bother. */\n\t*c1 = f;\n\t*c2 = DD_ONE(dd);\n\tcuddRef(*c1); cuddRef(*c2);\n\tstGen = st_init_gen(distanceTable);\n\tif (stGen == NULL) goto outOfMem;\n\twhile(st_gen(stGen, (void **)&key, (void **)&value)) {\n\t    FREE(value);\n\t}\n\tst_free_gen(stGen); stGen = NULL;\n\tst_free_table(distanceTable);\n\treturn(1);\n    }\n\n    /* record the maximum local reference count */\n    maxLocalRef = 0;\n    stGen = st_init_gen(distanceTable);\n    if (stGen == NULL) goto outOfMem;\n    while(st_gen(stGen, (void **)&key, (void **)&value)) {\n\tnodeStat = (NodeStat *)value;\n\tmaxLocalRef = (nodeStat->localRef > maxLocalRef) ?\n\t    nodeStat->localRef : maxLocalRef;\n    }\n    st_free_gen(stGen); stGen = NULL;\n\n\n    /* Count minterms for each node. */\n    max = pow(2.0, (double)Cudd_SupportSize(dd,f)); /* potential overflow */\n    mintermTable = st_init_table(st_ptrcmp,st_ptrhash);\n    if (mintermTable == NULL) goto outOfMem;\n    minterms = CountMinterms(dd, f, max, mintermTable, dd->err);\n    if (minterms == -1.0) goto outOfMem;\n    \n    lastTimeG = Cudd_Random(dd) & 1;\n    cacheTable = st_init_table(st_ptrcmp, st_ptrhash);\n    if (cacheTable == NULL) goto outOfMem;\n    ghTable = st_init_table(st_ptrcmp, st_ptrhash);\n    if (ghTable == NULL) goto outOfMem;\n\n    /* Build conjuncts. */\n    factors = BuildConjuncts(dd, f, distanceTable, cacheTable,\n\t\t\t     approxDistance, maxLocalRef, ghTable,\n                             mintermTable, &lastTimeG);\n    if (factors == NULL) goto outOfMem;\n\n    /* free up tables */\n    stGen = st_init_gen(distanceTable);\n    if (stGen == NULL) goto outOfMem;\n    while(st_gen(stGen, (void **)&key, (void **)&value)) {\n\tFREE(value);\n    }\n    st_free_gen(stGen); stGen = NULL;\n    st_free_table(distanceTable); distanceTable = NULL;\n    st_free_table(ghTable); ghTable = NULL;\n    \n    stGen = st_init_gen(mintermTable);\n    if (stGen == NULL) goto outOfMem;\n    while(st_gen(stGen, (void **)&key, (void **)&value)) {\n\tFREE(value);\n    }\n    st_free_gen(stGen); stGen = NULL;\n    st_free_table(mintermTable); mintermTable = NULL;\n\n    freeFactors = FactorsNotStored(factors);\n    factors = (freeFactors) ? FactorsUncomplement(factors) : factors;\n    if (factors != NULL) {\n\t*c1 = factors->g;\n\t*c2 = factors->h;\n\tcuddRef(*c1);\n\tcuddRef(*c2);\n\tif (freeFactors) FREE(factors);\n\t\n#if 0    \n\tif ((*c1 == f) && (!Cudd_IsConstantInt(f))) {\n\t    assert(*c2 == DD_ONE(manager));\n\t}\n\tif ((*c2 == f) && (!Cudd_IsConstantInt(f))) {\n\t    assert(*c1 == DD_ONE(manager));\n\t}\n\t\n\tif ((*c1 != DD_ONE(manager)) && (!Cudd_IsConstantInt(f))) {\n\t    assert(!Cudd_bddLeq(dd, *c2, *c1));\n\t}\n\tif ((*c2 != DD_ONE(manager)) && (!Cudd_IsConstantInt(f))) {\n\t    assert(!Cudd_bddLeq(dd, *c1, *c2));\n\t}\n#endif\n    }\n\n    stGen = st_init_gen(cacheTable);\n    if (stGen == NULL) goto outOfMem;\n    while(st_gen(stGen, (void **)&key, (void **)&value)) {\n\tConjunctsFree(dd, (Conjuncts *)value);\n    }\n    st_free_gen(stGen); stGen = NULL;\n\n    st_free_table(cacheTable); cacheTable = NULL;\n\n    return(1);\n\noutOfMem:\n    if (distanceTable != NULL) {\n\tstGen = st_init_gen(distanceTable);\n\tif (stGen == NULL) goto outOfMem;\n\twhile(st_gen(stGen, (void **)&key, (void **)&value)) {\n\t    FREE(value);\n\t}\n\tst_free_gen(stGen); stGen = NULL;\n\tst_free_table(distanceTable); distanceTable = NULL;\n    }\n    if (mintermTable != NULL) {\n\tstGen = st_init_gen(mintermTable);\n\tif (stGen == NULL) goto outOfMem;\n\twhile(st_gen(stGen, (void **)&key, (void **)&value)) {\n\t    FREE(value);\n\t}\n\tst_free_gen(stGen); stGen = NULL;\n\tst_free_table(mintermTable); mintermTable = NULL;\n    }\n    if (ghTable != NULL) st_free_table(ghTable);\n    if (cacheTable != NULL) {\n\tstGen = st_init_gen(cacheTable);\n\tif (stGen == NULL) goto outOfMem;\n\twhile(st_gen(stGen, (void **)&key, (void **)&value)) {\n\t    ConjunctsFree(dd, (Conjuncts *)value);\n\t}\n\tst_free_gen(stGen); stGen = NULL;\n\tst_free_table(cacheTable); cacheTable = NULL;\n    }\n    dd->errorCode = CUDD_MEMORY_OUT;\n    return(0);\n\n} /* end of cuddConjunctsAux */\n"
  },
  {
    "path": "cudd/cudd/cuddEssent.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for the detection of essential variables.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* These definitions are for the bit vectors. */\n#if SIZEOF_VOID_P == 8\n#define BPL 64\n#define LOGBPL 6\n#else\n#define BPL 32\n#define LOGBPL 5\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n** @brief This structure holds the set of clauses for a node.\n** @details Each clause consists of two literals.\n** For one-literal clauses, the second literal is FALSE.\n** Each literal is composed of a variable and a phase.  A variable is a node\n** index, and requires sizeof(DdHalfWord) bytes.  The constant literals use\n** CUDD_MAXINDEX as variable indicator.  Each phase is a bit: 0 for positive\n** phase, and 1 for negative phase.\n** Variables and phases are stored separately for the sake of compactness.\n** The variables are stored in an array of DdHalfWord's terminated by a\n** sentinel (a pair of zeroes).  The phases are stored in a bit vector.\n** The cnt field holds, at the end, the number of clauses.\n** The clauses of the set are kept sorted.  For each clause, the first literal\n** is the one of least index.  So, the clause with literals +2 and -4 is stored\n** as (+2,-4).  A one-literal clause with literal +3 is stored as\n** (+3,-CUDD_MAXINDEX).  Clauses are sorted in decreasing order as follows:\n** <ul>\n** <li> (+5,-7)\n** <li> (+5,+6)\n** <li> (-5,+7)\n** <li> (-4,FALSE)\n** <li> (-4,+8)\n** <li> ...\n** </ul>\n** That is, one first looks at the variable of the first literal, then at the\n** phase of the first literal, then at the variable of the second literal,\n** and finally at the phase of the second literal.\n*/\nstruct DdTlcInfo {\n    DdHalfWord *vars;\n    ptruint *phases;\n    DdHalfWord cnt;\n};\n\n/**\n** @brief This structure is for temporary representation of sets of clauses.\n** @details It is meant to be used in linked lists, when the number of clauses\n** is not yet known.  The encoding of a clause is the same as in DdTlcInfo,\n** though the phase information is not stored in a bit array.\n*/\nstruct TlClause {\n    DdHalfWord v1, v2;\n    short p1, p2;\n    struct TlClause *next;\n};\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\ntypedef ptruint BitVector;\ntypedef struct TlClause TlClause;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * ddFindEssentialRecur (DdManager *dd, DdNode *f);\nstatic DdTlcInfo * ddFindTwoLiteralClausesRecur (DdManager * dd, DdNode * f, st_table *table, BitVector *Tolv, BitVector *Tolp, BitVector *Eolv, BitVector *Eolp);\nstatic DdTlcInfo * computeClauses (DdTlcInfo *Tres, DdTlcInfo *Eres, DdHalfWord label, int size, BitVector *Tolv, BitVector *Tolp, BitVector *Eolv, BitVector *Eolp);\nstatic DdTlcInfo * computeClausesWithUniverse (DdTlcInfo *Cres, DdHalfWord label, short phase);\nstatic DdTlcInfo * emptyClauseSet (void);\nstatic int sentinelp (DdHalfWord var1, DdHalfWord var2);\nstatic int equalp (DdHalfWord var1a, short phase1a, DdHalfWord var1b, short phase1b, DdHalfWord var2a, short phase2a, DdHalfWord var2b, short phase2b);\nstatic int beforep (DdHalfWord var1a, short phase1a, DdHalfWord var1b, short phase1b, DdHalfWord var2a, short phase2a, DdHalfWord var2b, short phase2b);\nstatic int oneliteralp (DdHalfWord var);\nstatic int impliedp (DdHalfWord var1, short phase1, DdHalfWord var2, short phase2, BitVector *olv, BitVector *olp);\nstatic BitVector * bitVectorAlloc (int size);\nstatic void bitVectorClear (BitVector *vector, int size);\nstatic void bitVectorFree (BitVector *vector);\nstatic short bitVectorRead (BitVector *vector, int i);\nstatic void bitVectorSet (BitVector * vector, int i, short val);\nstatic DdTlcInfo * tlcInfoAlloc (void);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Finds the essential variables of a %DD.\n\n  @details Returns the cube of the essential variables. A positive\n  literal means that the variable must be set to 1 for the function to be\n  1. A negative literal means that the variable must be set to 0 for the\n  function to be 1.\n\n  @return a pointer to the cube %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddIsVarEssential\n\n*/\nDdNode *\nCudd_FindEssential(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = ddFindEssentialRecur(dd,f);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_FindEssential */\n\n\n/**\n  @brief Determines whether a given variable is essential with a\n  given phase in a %BDD.\n\n  @details Uses Cudd_bddIteConstant. Returns 1 if phase == 1 and\n  f-->x_id, or if phase == 0 and f-->x_id'.\n\n  @sideeffect None\n\n  @see Cudd_FindEssential\n\n*/\nint\nCudd_bddIsVarEssential(\n  DdManager * manager,\n  DdNode * f,\n  int  id,\n  int  phase)\n{\n    DdNode\t*var;\n    int\t\tres;\n\n    var = Cudd_bddIthVar(manager, id);\n\n    var = Cudd_NotCond(var,phase == 0);\n\n    res = Cudd_bddLeq(manager, f, var);\n\n    return(res);\n\n} /* end of Cudd_bddIsVarEssential */\n\n\n/**\n  @brief Finds the two literal clauses of a %DD.\n\n  @details Returns the one- and two-literal clauses of a %DD.  For a\n  constant %DD, the empty set of clauses is returned.  This is\n  obviously correct for a non-zero constant.  For the constant zero,\n  it is based on the assumption that only those clauses containing\n  variables in the support of the function are considered.  Since the\n  support of a constant function is empty, no clauses are returned.\n\n  @return a pointer to the structure holding the clauses if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_FindEssential\n\n*/\nDdTlcInfo *\nCudd_FindTwoLiteralClauses(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdTlcInfo *res;\n    st_table *table;\n    st_generator *gen;\n    DdTlcInfo *tlc;\n    DdNode *node;\n    int size = dd->size;\n    BitVector *Tolv, *Tolp, *Eolv, *Eolp;\n\n    if (Cudd_IsConstantInt(f)) {\n\tres = emptyClauseSet();\n\treturn(res);\n    }\n    table = st_init_table(st_ptrcmp,st_ptrhash);\n    if (table == NULL) return(NULL);\n    Tolv = bitVectorAlloc(size);\n    if (Tolv == NULL) {\n\tst_free_table(table);\n\treturn(NULL);\n    }\n    Tolp = bitVectorAlloc(size);\n    if (Tolp == NULL) {\n\tst_free_table(table);\n\tbitVectorFree(Tolv);\n\treturn(NULL);\n    }\n    Eolv = bitVectorAlloc(size);\n    if (Eolv == NULL) {\n\tst_free_table(table);\n\tbitVectorFree(Tolv);\n\tbitVectorFree(Tolp);\n\treturn(NULL);\n    }\n    Eolp = bitVectorAlloc(size);\n    if (Eolp == NULL) {\n\tst_free_table(table);\n\tbitVectorFree(Tolv);\n\tbitVectorFree(Tolp);\n\tbitVectorFree(Eolv);\n\treturn(NULL);\n    }\n\n    res = ddFindTwoLiteralClausesRecur(dd,f,table,Tolv,Tolp,Eolv,Eolp);\n    /* Dispose of table contents and free table. */\n    st_foreach_item(table, gen, (void **) &node, (void **) &tlc) {\n\tif (node != f) {\n\t    Cudd_tlcInfoFree(tlc);\n\t}\n    }\n    st_free_table(table);\n    bitVectorFree(Tolv);\n    bitVectorFree(Tolp);\n    bitVectorFree(Eolv);\n    bitVectorFree(Eolp);\n\n    if (res != NULL) {\n\tint i;\n\tfor (i = 0; !sentinelp(res->vars[i], res->vars[i+1]); i += 2);\n\tres->cnt = i >> 1;\n    }\n\n    return(res);\n\n} /* end of Cudd_FindTwoLiteralClauses */\n\n\n/**\n  @brief Accesses the i-th clause of a %DD.\n\n  @details Accesses the i-th clause of a %DD given the clause set which\n  must be already computed.\n\n  @return 1 if successful; 0 if i is out of range, or in case of\n  error.\n\n  @sideeffect the four components of a clause are returned as side effects.\n\n  @see Cudd_FindTwoLiteralClauses\n\n*/\nint\nCudd_ReadIthClause(\n  DdTlcInfo * tlc,\n  int i,\n  unsigned *var1,\n  unsigned *var2,\n  int *phase1,\n  int *phase2)\n{\n    if (tlc == NULL) return(0);\n    if (tlc->vars == NULL || tlc->phases == NULL) return(0);\n    if (i < 0 || (unsigned) i >= tlc->cnt) return(0);\n    *var1 = (unsigned) tlc->vars[2*i];\n    *var2 = (unsigned) tlc->vars[2*i+1];\n    *phase1 = (int) bitVectorRead(tlc->phases, 2*i);\n    *phase2 = (int) bitVectorRead(tlc->phases, 2*i+1);\n    return(1);\n\n} /* end of Cudd_ReadIthClause */\n\n\n/**\n  @brief Prints the one- and two-literal clauses of a %DD.\n\n  @details The argument \"names\" can be NULL, in which case the\n  variable indices are printed.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_FindTwoLiteralClauses\n\n*/\nint\nCudd_PrintTwoLiteralClauses(\n  DdManager * dd,\n  DdNode * f,\n  char **names,\n  FILE *fp)\n{\n    DdHalfWord *vars;\n    BitVector *phases;\n    int i;\n    DdTlcInfo *res = Cudd_FindTwoLiteralClauses(dd, f);\n    FILE *ifp = fp == NULL ? dd->out : fp;\n\n    if (res == NULL) return(0);\n    vars = res->vars;\n    phases = res->phases;\n    for (i = 0; !sentinelp(vars[i], vars[i+1]); i += 2) {\n\tif (names != NULL) {\n\t    if (vars[i+1] == CUDD_MAXINDEX) {\n\t\t(void) fprintf(ifp, \"%s%s\\n\",\n\t\t\t       bitVectorRead(phases, i) ? \"~\" : \" \",\n\t\t\t       names[vars[i]]);\n\t    } else {\n\t\t(void) fprintf(ifp, \"%s%s | %s%s\\n\",\n\t\t\t       bitVectorRead(phases, i) ? \"~\" : \" \",\n\t\t\t       names[vars[i]],\n\t\t\t       bitVectorRead(phases, i+1) ? \"~\" : \" \",\n\t\t\t       names[vars[i+1]]);\n\t    }\n\t} else {\n\t    if (vars[i+1] == CUDD_MAXINDEX) {\n\t\t(void) fprintf(ifp, \"%s%d\\n\",\n\t\t\t       bitVectorRead(phases, i) ? \"~\" : \" \",\n\t\t\t       (int) vars[i]);\n\t    } else {\n\t\t(void) fprintf(ifp, \"%s%d | %s%d\\n\",\n\t\t\t       bitVectorRead(phases, i) ? \"~\" : \" \",\n\t\t\t       (int) vars[i],\n\t\t\t       bitVectorRead(phases, i+1) ? \"~\" : \" \",\n\t\t\t       (int) vars[i+1]);\n\t    }\n\t}\n    }\n    Cudd_tlcInfoFree(res);\n\n    return(1);\n\n} /* end of Cudd_PrintTwoLiteralClauses */\n\n\n/**\n  @brief Frees a DdTlcInfo Structure.\n\n  @details Also frees the memory pointed by it.\n\n  @sideeffect None\n\n*/\nvoid\nCudd_tlcInfoFree(\n  DdTlcInfo * t)\n{\n    if (t->vars != NULL) FREE(t->vars);\n    if (t->phases != NULL) FREE(t->phases);\n    FREE(t);\n\n} /* end of Cudd_tlcInfoFree */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the recursive step of Cudd_FindEssential.\n\n  @return a pointer to the cube %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nddFindEssentialRecur(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode\t*T, *E, *F;\n    DdNode\t*essT, *essE, *res;\n    unsigned\tindex;\n    DdNode\t*one, *lzero, *azero;\n\n    one = DD_ONE(dd);\n    F = Cudd_Regular(f);\n    /* If f is constant the set of essential variables is empty. */\n    if (cuddIsConstant(F)) return(one);\n\n    res = cuddCacheLookup1(dd,Cudd_FindEssential,f);\n    if (res != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    lzero = Cudd_Not(one);\n    azero = DD_ZERO(dd);\n    /* Find cofactors: here f is non-constant. */\n    T = cuddT(F);\n    E = cuddE(F);\n    if (Cudd_IsComplement(f)) {\n\tT = Cudd_Not(T); E = Cudd_Not(E);\n    }\n\n    index = F->index;\n    if (Cudd_IsConstantInt(T) && T != lzero && T != azero) {\n\t/* if E is zero, index is essential, otherwise there are no\n\t** essentials, because index is not essential and no other variable\n\t** can be, since setting index = 1 makes the function constant and\n\t** different from 0.\n\t*/\n\tif (E == lzero || E == azero) {\n\t    res = dd->vars[index];\n\t} else {\n\t    res = one;\n\t}\n    } else if (T == lzero || T == azero) {\n\tif (Cudd_IsConstantInt(E)) { /* E cannot be zero here */\n\t    res = Cudd_Not(dd->vars[index]);\n\t} else { /* E == non-constant */\n\t    /* find essentials in the else branch */\n\t    essE = ddFindEssentialRecur(dd,E);\n\t    if (essE == NULL) {\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(essE);\n\n\t    /* add index to the set with negative phase */\n\t    res = cuddUniqueInter(dd,index,one,Cudd_Not(essE));\n\t    if (res == NULL) {\n\t\tCudd_RecursiveDeref(dd,essE);\n\t\treturn(NULL);\n\t    }\n\t    res = Cudd_Not(res);\n\t    cuddDeref(essE);\n\t}\n    } else { /* T == non-const */\n\tif (E == lzero || E == azero) {\n\t    /* find essentials in the then branch */\n\t    essT = ddFindEssentialRecur(dd,T);\n\t    if (essT == NULL) {\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(essT);\n\n\t    /* add index to the set with positive phase */\n\t    /* use And because essT may be complemented */\n\t    res = cuddBddAndRecur(dd,dd->vars[index],essT);\n\t    if (res == NULL) {\n\t\tCudd_RecursiveDeref(dd,essT);\n\t\treturn(NULL);\n\t    }\n\t    cuddDeref(essT);\n\t} else if (!Cudd_IsConstantInt(E)) {\n\t    /* if E is a non-zero constant there are no essentials\n\t    ** because T is non-constant.\n\t    */\n\t    essT = ddFindEssentialRecur(dd,T);\n\t    if (essT == NULL) {\n\t\treturn(NULL);\n\t    }\n\t    if (essT == one) {\n\t\tres = one;\n\t    } else {\n\t\tcuddRef(essT);\n\t\tessE = ddFindEssentialRecur(dd,E);\n\t\tif (essE == NULL) {\n\t\t    Cudd_RecursiveDeref(dd,essT);\n\t\t    return(NULL);\n\t\t}\n\t\tcuddRef(essE);\n\n\t\t/* res = intersection(essT, essE) */\n\t\tres = cuddBddLiteralSetIntersectionRecur(dd,essT,essE);\n\t\tif (res == NULL) {\n\t\t    Cudd_RecursiveDeref(dd,essT);\n\t\t    Cudd_RecursiveDeref(dd,essE);\n\t\t    return(NULL);\n\t\t}\n\t\tcuddRef(res);\n\t\tCudd_RecursiveDeref(dd,essT);\n\t\tCudd_RecursiveDeref(dd,essE);\n\t\tcuddDeref(res);\n\t    }\n\t} else {\t/* E is a non-zero constant */\n\t    res = one;\n\t}\n    }\n\n    cuddCacheInsert1(dd,Cudd_FindEssential, f, res);\n    return(res);\n\n} /* end of ddFindEssentialRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_FindTwoLiteralClauses.\n\n  @details The %DD node is assumed to be not constant.\n\n  @return a pointer to a set of clauses if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_FindTwoLiteralClauses\n\n*/\nstatic DdTlcInfo *\nddFindTwoLiteralClausesRecur(\n  DdManager * dd,\n  DdNode * f,\n  st_table *table,\n  BitVector *Tolv,\n  BitVector *Tolp,\n  BitVector *Eolv,\n  BitVector *Eolp)\n{\n    DdNode *T, *E, *F;\n    DdNode *one, *lzero, *azero;\n    DdTlcInfo *res, *Tres, *Eres;\n    DdHalfWord index;\n\n    F = Cudd_Regular(f);\n\n    assert(!cuddIsConstant(F));\n\n    /* Check computed table.  Separate entries are necessary for\n    ** a node and its complement.  We should update the counter here. */\n    if (st_lookup(table, f, (void **) &res)) {\n\treturn(res);\n    }\n\n    /* Easy access to the constants for BDDs and ADDs. */\n    one = DD_ONE(dd);\n    lzero = Cudd_Not(one);\n    azero = DD_ZERO(dd);\n\n    /* Find cofactors and variable labeling the top node. */\n    T = cuddT(F); E = cuddE(F);\n    if (Cudd_IsComplement(f)) {\n\tT = Cudd_Not(T); E = Cudd_Not(E);\n    }\n    index = F->index;\n\n    if (Cudd_IsConstantInt(T) && T != lzero && T != azero) {\n\t/* T is a non-zero constant.  If E is zero, then this node's index\n\t** is a one-literal clause.  Otherwise, if E is a non-zero\n\t** constant, there are no clauses for this node.  Finally,\n\t** if E is not constant, we recursively compute its clauses, and then\n\t** merge using the empty set for T. */\n\tif (E == lzero || E == azero) {\n\t    /* Create the clause (index + 0). */\n\t    res = tlcInfoAlloc();\n\t    if (res == NULL) return(NULL);\n\t    res->vars = ALLOC(DdHalfWord,4);\n\t    if (res->vars == NULL) {\n\t\tFREE(res);\n\t\treturn(NULL);\n\t    }\n\t    res->phases = bitVectorAlloc(2);\n\t    if (res->phases == NULL) {\n\t\tFREE(res->vars);\n\t\tFREE(res);\n\t\treturn(NULL);\n\t    }\n\t    res->vars[0] = index;\n\t    res->vars[1] = CUDD_MAXINDEX;\n\t    res->vars[2] = 0;\n\t    res->vars[3] = 0;\n\t    bitVectorSet(res->phases, 0, 0); /* positive phase */\n\t    bitVectorSet(res->phases, 1, 1); /* negative phase */\n\t} else if (Cudd_IsConstantInt(E)) {\n\t    /* If E is a non-zero constant, no clauses. */\n\t    res = emptyClauseSet();\n\t} else {\n\t    /* E is non-constant */\n\t    Tres = emptyClauseSet();\n\t    if (Tres == NULL) return(NULL);\n\t    Eres = ddFindTwoLiteralClausesRecur(dd, E, table,\n                                                Tolv, Tolp, Eolv, Eolp);\n\t    if (Eres == NULL) {\n\t\tCudd_tlcInfoFree(Tres);\n\t\treturn(NULL);\n\t    }\n\t    res = computeClauses(Tres, Eres, index, dd->size,\n                                 Tolv, Tolp, Eolv, Eolp);\n\t    Cudd_tlcInfoFree(Tres);\n\t}\n    } else if (T == lzero || T == azero) {\n\t/* T is zero.  If E is a non-zero constant, then the\n\t** complement of this node's index is a one-literal clause.\n\t** Otherwise, if E is not constant, we recursively compute its\n\t** clauses, and then merge using the universal set for T. */\n\tif (Cudd_IsConstantInt(E)) { /* E cannot be zero here */\n\t    /* Create the clause (!index + 0). */\n\t    res = tlcInfoAlloc();\n\t    if (res == NULL) return(NULL);\n\t    res->vars = ALLOC(DdHalfWord,4);\n\t    if (res->vars == NULL) {\n\t\tFREE(res);\n\t\treturn(NULL);\n\t    }\n\t    res->phases = bitVectorAlloc(2);\n\t    if (res->phases == NULL) {\n\t\tFREE(res->vars);\n\t\tFREE(res);\n\t\treturn(NULL);\n\t    }\n\t    res->vars[0] = index;\n\t    res->vars[1] = CUDD_MAXINDEX;\n\t    res->vars[2] = 0;\n\t    res->vars[3] = 0;\n\t    bitVectorSet(res->phases, 0, 1); /* negative phase */\n\t    bitVectorSet(res->phases, 1, 1); /* negative phase */\n\t} else { /* E == non-constant */\n\t    Eres = ddFindTwoLiteralClausesRecur(dd, E, table,\n                                                Tolv, Tolp, Eolv, Eolp);\n\t    if (Eres == NULL) return(NULL);\n\t    res = computeClausesWithUniverse(Eres, index, 1);\n\t}\n    } else { /* T == non-const */\n\tTres = ddFindTwoLiteralClausesRecur(dd, T, table,\n                                            Tolv, Tolp, Eolv, Eolp);\n\tif (Tres == NULL) return(NULL);\n\tif (Cudd_IsConstantInt(E)) {\n\t    if (E == lzero || E == azero) {\n\t\tres = computeClausesWithUniverse(Tres, index, 0);\n\t    } else {\n\t\tEres = emptyClauseSet();\n\t\tif (Eres == NULL) return(NULL);\n\t\tres = computeClauses(Tres, Eres, index, dd->size,\n                                     Tolv, Tolp, Eolv, Eolp);\n\t\tCudd_tlcInfoFree(Eres);\n\t    }\n\t} else {\n\t    Eres = ddFindTwoLiteralClausesRecur(dd, E, table,\n                                                Tolv, Tolp, Eolv, Eolp);\n\t    if (Eres == NULL) return(NULL);\n\t    res = computeClauses(Tres, Eres, index, dd->size,\n                                 Tolv, Tolp, Eolv, Eolp);\n\t}\n    }\n\n    /* Cache results. */\n    if (st_add_direct(table, f, res) == ST_OUT_OF_MEM) {\n\tFREE(res);\n\treturn(NULL);\n    }\n    return(res);\n\n} /* end of ddFindTwoLiteralClausesRecur */\n\n\n/**\n  @brief Computes the two-literal clauses for a node.\n\n  @details Computes the two-literal clauses for a node given the\n  clauses for its children and the label of the node.\n\n  @return a pointer to a TclInfo structure if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see computeClausesWithUniverse\n\n*/\nstatic DdTlcInfo *\ncomputeClauses(\n  DdTlcInfo *Tres /**< list of clauses for T child */,\n  DdTlcInfo *Eres /**< list of clauses for E child */,\n  DdHalfWord label /**< variable labeling the current node */,\n  int size /**< number of variables in the manager */,\n  BitVector *Tolv /**< variable bit vector for T child */,\n  BitVector *Tolp /**< phase bit vector for T child */,\n  BitVector *Eolv /**< variable bit vector for E child */,\n  BitVector *Eolp /**< phase bit vector for E child */)\n{\n    DdHalfWord *Tcv = Tres->vars; /* variables of clauses for the T child */\n    BitVector *Tcp = Tres->phases; /* phases of clauses for the T child */\n    DdHalfWord *Ecv = Eres->vars; /* variables of clauses for the E child */\n    BitVector *Ecp = Eres->phases; /* phases of clauses for the E child */\n    DdHalfWord *Vcv = NULL; /* pointer to variables of the clauses for v */\n    BitVector *Vcp = NULL; /* pointer to phases of the clauses for v */\n    DdTlcInfo *res = NULL; /* the set of clauses to be returned */\n    int pt = 0; /* index in the list of clauses of T */\n    int pe = 0; /* index in the list of clauses of E */\n    int cv = 0; /* counter of the clauses for this node */\n    TlClause *iclauses = NULL; /* list of inherited clauses */\n    TlClause *tclauses = NULL; /* list of 1-literal clauses of T */\n    TlClause *eclauses = NULL; /* list of 1-literal clauses of E */\n    TlClause *nclauses = NULL; /* list of new (non-inherited) clauses */\n    TlClause *lnclause = NULL; /* pointer to last new clause */\n    TlClause *newclause; /* temporary pointer to new clauses */\n\n    /* Initialize sets of one-literal clauses.  The one-literal clauses\n    ** are stored redundantly.  These sets allow constant-time lookup, which\n    ** we need when we check for implication of a two-literal clause by a\n    ** one-literal clause.  The linked lists allow fast sequential\n    ** processing. */\n    bitVectorClear(Tolv, size);\n    bitVectorClear(Tolp, size);\n    bitVectorClear(Eolv, size);\n    bitVectorClear(Eolp, size);\n\n    /* Initialize result structure. */\n    res = tlcInfoAlloc();\n    if (res == NULL) goto cleanup;\n\n    /* Scan the two input list.  Extract inherited two-literal clauses\n    ** and set aside one-literal clauses from each list.  The incoming lists\n    ** are sorted in the order defined by beforep.  The three linked list\n    ** produced by this loop are sorted in the reverse order because we\n    ** always append to the front of the lists.\n    ** The inherited clauses are those clauses (both one- and two-literal)\n    ** that are common to both children; and the two-literal clauses of\n    ** one child that are implied by a one-literal clause of the other\n    ** child. */\n    while (!sentinelp(Tcv[pt], Tcv[pt+1]) || !sentinelp(Ecv[pe], Ecv[pe+1])) {\n\tif (equalp(Tcv[pt], bitVectorRead(Tcp, pt),\n\t\t   Tcv[pt+1], bitVectorRead(Tcp, pt+1),\n\t\t   Ecv[pe], bitVectorRead(Ecp, pe),\n\t\t   Ecv[pe+1], bitVectorRead(Ecp, pe+1))) {\n\t    /* Add clause to inherited list. */\n\t    newclause = ALLOC(TlClause,1);\n\t    if (newclause == NULL) goto cleanup;\n\t    newclause->v1 = Tcv[pt];\n\t    newclause->v2 = Tcv[pt+1];\n\t    newclause->p1 = bitVectorRead(Tcp, pt);\n\t    newclause->p2 = bitVectorRead(Tcp, pt+1);\n\t    newclause->next = iclauses;\n\t    iclauses = newclause;\n\t    pt += 2; pe += 2; cv++;\n\t} else if (beforep(Tcv[pt], bitVectorRead(Tcp, pt),\n\t\t   Tcv[pt+1], bitVectorRead(Tcp, pt+1),\n\t\t   Ecv[pe], bitVectorRead(Ecp, pe),\n\t\t   Ecv[pe+1], bitVectorRead(Ecp, pe+1))) {\n\t    if (oneliteralp(Tcv[pt+1])) {\n\t\t/* Add this one-literal clause to the T set. */\n\t\tnewclause = ALLOC(TlClause,1);\n\t\tif (newclause == NULL) goto cleanup;\n\t\tnewclause->v1 = Tcv[pt];\n\t\tnewclause->v2 = CUDD_MAXINDEX;\n\t\tnewclause->p1 = bitVectorRead(Tcp, pt);\n\t\tnewclause->p2 = 1;\n\t\tnewclause->next = tclauses;\n\t\ttclauses = newclause;\n\t\tbitVectorSet(Tolv, Tcv[pt], 1);\n\t\tbitVectorSet(Tolp, Tcv[pt], bitVectorRead(Tcp, pt));\n\t    } else {\n\t\tif (impliedp(Tcv[pt], bitVectorRead(Tcp, pt),\n\t\t\t     Tcv[pt+1], bitVectorRead(Tcp, pt+1),\n\t\t\t     Eolv, Eolp)) {\n\t\t    /* Add clause to inherited list. */\n\t\t    newclause = ALLOC(TlClause,1);\n\t\t    if (newclause == NULL) goto cleanup;\n\t\t    newclause->v1 = Tcv[pt];\n\t\t    newclause->v2 = Tcv[pt+1];\n\t\t    newclause->p1 = bitVectorRead(Tcp, pt);\n\t\t    newclause->p2 = bitVectorRead(Tcp, pt+1);\n\t\t    newclause->next = iclauses;\n\t\t    iclauses = newclause;\n\t\t    cv++;\n\t\t}\n\t    }\n\t    pt += 2;\n\t} else { /* !beforep() */\n\t    if (oneliteralp(Ecv[pe+1])) {\n\t\t/* Add this one-literal clause to the E set. */\n\t\tnewclause = ALLOC(TlClause,1);\n\t\tif (newclause == NULL) goto cleanup;\n\t\tnewclause->v1 = Ecv[pe];\n\t\tnewclause->v2 = CUDD_MAXINDEX;\n\t\tnewclause->p1 = bitVectorRead(Ecp, pe);\n\t\tnewclause->p2 = 1;\n\t\tnewclause->next = eclauses;\n\t\teclauses = newclause;\n\t\tbitVectorSet(Eolv, Ecv[pe], 1);\n\t\tbitVectorSet(Eolp, Ecv[pe], bitVectorRead(Ecp, pe));\n\t    } else {\n\t\tif (impliedp(Ecv[pe], bitVectorRead(Ecp, pe),\n\t\t\t     Ecv[pe+1], bitVectorRead(Ecp, pe+1),\n\t\t\t     Tolv, Tolp)) {\n\t\t    /* Add clause to inherited list. */\n\t\t    newclause = ALLOC(TlClause,1);\n\t\t    if (newclause == NULL) goto cleanup;\n\t\t    newclause->v1 = Ecv[pe];\n\t\t    newclause->v2 = Ecv[pe+1];\n\t\t    newclause->p1 = bitVectorRead(Ecp, pe);\n\t\t    newclause->p2 = bitVectorRead(Ecp, pe+1);\n\t\t    newclause->next = iclauses;\n\t\t    iclauses = newclause;\n\t\t    cv++;\n\t\t}\n\t    }\n\t    pe += 2;\n\t}\n    }\n\n    /* Add one-literal clauses for the label variable to the front of\n    ** the two lists. */\n    newclause = ALLOC(TlClause,1);\n    if (newclause == NULL) goto cleanup;\n    newclause->v1 = label;\n    newclause->v2 = CUDD_MAXINDEX;\n    newclause->p1 = 0;\n    newclause->p2 = 1;\n    newclause->next = tclauses;\n    tclauses = newclause;\n    newclause = ALLOC(TlClause,1);\n    if (newclause == NULL) goto cleanup;\n    newclause->v1 = label;\n    newclause->v2 = CUDD_MAXINDEX;\n    newclause->p1 = 1;\n    newclause->p2 = 1;\n    newclause->next = eclauses;\n    eclauses = newclause;\n\n    /* Produce the non-inherited clauses.  We preserve the \"reverse\"\n    ** order of the two input lists by appending to the end of the\n    ** list.  In this way, iclauses and nclauses are consistent. */\n    while (tclauses != NULL && eclauses != NULL) {\n\tif (beforep(eclauses->v1, eclauses->p1, eclauses->v2, eclauses->p2,\n\t\t    tclauses->v1, tclauses->p1, tclauses->v2, tclauses->p2)) {\n\t    TlClause *nextclause = tclauses->next;\n\t    TlClause *otherclauses = eclauses;\n\t    while (otherclauses != NULL) {\n\t\tif (tclauses->v1 != otherclauses->v1) {\n\t\t    newclause = ALLOC(TlClause,1);\n\t\t    if (newclause == NULL) goto cleanup;\n\t\t    newclause->v1 = tclauses->v1;\n\t\t    newclause->v2 = otherclauses->v1;\n\t\t    newclause->p1 = tclauses->p1;\n\t\t    newclause->p2 = otherclauses->p1;\n\t\t    newclause->next = NULL;\n\t\t    if (nclauses == NULL) {\n\t\t\tnclauses = newclause;\n\t\t\tlnclause = newclause;\n\t\t    } else {\n\t\t\tlnclause->next = newclause;\n\t\t\tlnclause = newclause;\n\t\t    }\n\t\t    cv++;\n\t\t}\n\t\totherclauses = otherclauses->next;\n\t    }\n\t    FREE(tclauses);\n\t    tclauses = nextclause;\n\t} else {\n\t    TlClause *nextclause = eclauses->next;\n\t    TlClause *otherclauses = tclauses;\n\t    while (otherclauses != NULL) {\n\t\tif (eclauses->v1 != otherclauses->v1) {\n\t\t    newclause = ALLOC(TlClause,1);\n\t\t    if (newclause == NULL) goto cleanup;\n\t\t    newclause->v1 = eclauses->v1;\n\t\t    newclause->v2 = otherclauses->v1;\n\t\t    newclause->p1 = eclauses->p1;\n\t\t    newclause->p2 = otherclauses->p1;\n\t\t    newclause->next = NULL;\n\t\t    if (nclauses == NULL) {\n\t\t\tnclauses = newclause;\n\t\t\tlnclause = newclause;\n\t\t    } else {\n\t\t\tlnclause->next = newclause;\n\t\t\tlnclause = newclause;\n\t\t    }\n\t\t    cv++;\n\t\t}\n\t\totherclauses = otherclauses->next;\n\t    }\n\t    FREE(eclauses);\n\t    eclauses = nextclause;\n\t}\n    }\n    while (tclauses != NULL) {\n\tTlClause *nextclause = tclauses->next;\n\tFREE(tclauses);\n\ttclauses = nextclause;\n    }\n    while (eclauses != NULL) {\n\tTlClause *nextclause = eclauses->next;\n\tFREE(eclauses);\n\teclauses = nextclause;\n    }\n\n    /* Merge inherited and non-inherited clauses.  Now that we know the\n    ** total number, we allocate the arrays, and we fill them bottom-up\n    ** to restore the proper ordering. */\n    Vcv = ALLOC(DdHalfWord, 2*(cv+1));\n    if (Vcv == NULL) goto cleanup;\n    if (cv > 0) {\n\tVcp = bitVectorAlloc(2*cv);\n\tif (Vcp == NULL) goto cleanup;\n    } else {\n\tVcp = NULL;\n    }\n    res->vars = Vcv;\n    res->phases = Vcp;\n    /* Add sentinel. */\n    Vcv[2*cv] = 0;\n    Vcv[2*cv+1] = 0;\n    while (iclauses != NULL || nclauses != NULL) {\n\tTlClause *nextclause;\n\tcv--;\n\tif (nclauses == NULL || (iclauses != NULL &&\n\t    beforep(nclauses->v1, nclauses->p1, nclauses->v2, nclauses->p2,\n\t\t    iclauses->v1, iclauses->p1, iclauses->v2, iclauses->p2))) {\n\t    Vcv[2*cv] = iclauses->v1;\n\t    Vcv[2*cv+1] = iclauses->v2;\n\t    bitVectorSet(Vcp, 2*cv, iclauses->p1);\n\t    bitVectorSet(Vcp, 2*cv+1, iclauses->p2);\n\t    nextclause = iclauses->next;\n\t    FREE(iclauses);\n\t    iclauses = nextclause;\n\t} else {\n\t    Vcv[2*cv] = nclauses->v1;\n\t    Vcv[2*cv+1] = nclauses->v2;\n\t    bitVectorSet(Vcp, 2*cv, nclauses->p1);\n\t    bitVectorSet(Vcp, 2*cv+1, nclauses->p2);\n\t    nextclause = nclauses->next;\n\t    FREE(nclauses);\n\t    nclauses = nextclause;\n\t}\n    }\n    assert(cv == 0);\n\n    return(res);\n\n cleanup:\n    if (res != NULL) Cudd_tlcInfoFree(res);\n    while (iclauses != NULL) {\n\tTlClause *nextclause = iclauses->next;\n\tFREE(iclauses);\n\ticlauses = nextclause;\n    }\n    while (nclauses != NULL) {\n\tTlClause *nextclause = nclauses->next;\n\tFREE(nclauses);\n\tnclauses = nextclause;\n    }\n    while (tclauses != NULL) {\n\tTlClause *nextclause = tclauses->next;\n\tFREE(tclauses);\n\ttclauses = nextclause;\n    }\n    while (eclauses != NULL) {\n\tTlClause *nextclause = eclauses->next;\n\tFREE(eclauses);\n\teclauses = nextclause;\n    }\n\n    return(NULL);\n\n} /* end of computeClauses */\n\n\n/**\n  @brief Computes the two-literal clauses for a node.\n\n  @details Computes the two-literal clauses for a node with a zero\n  child, given the clauses for its other child and the label of the\n  node.\n\n  @return a pointer to a TclInfo structure if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see computeClauses\n\n*/\nstatic DdTlcInfo *\ncomputeClausesWithUniverse(\n  DdTlcInfo *Cres /* list of clauses for child */,\n  DdHalfWord label /* variable labeling the current node */,\n  short phase /* 0 if E child is zero; 1 if T child is zero */)\n{\n    DdHalfWord *Ccv = Cres->vars; /* variables of clauses for child */\n    BitVector *Ccp = Cres->phases; /* phases of clauses for child */\n    DdHalfWord *Vcv = NULL; /* pointer to the variables of the clauses for v */\n    BitVector *Vcp = NULL; /* pointer to the phases of the clauses for v */\n    DdTlcInfo *res = NULL; /* the set of clauses to be returned */\n    int i;\n\n    /* Initialize result. */\n    res = tlcInfoAlloc();\n    if (res == NULL) goto cleanup;\n    /* Count entries for new list and allocate accordingly. */\n    for (i = 0; !sentinelp(Ccv[i], Ccv[i+1]); i += 2);\n    /* At this point, i is twice the number of clauses in the child's\n    ** list.  We need four more entries for this node: 2 for the one-literal\n    ** clause for the label, and 2 for the sentinel. */\n    Vcv = ALLOC(DdHalfWord,i+4);\n    if (Vcv == NULL) goto cleanup;\n    Vcp = bitVectorAlloc(i+4);\n    if (Vcp == NULL) goto cleanup;\n    res->vars = Vcv;\n    res->phases = Vcp;\n    /* Copy old list into new. */\n    for (i = 0; !sentinelp(Ccv[i], Ccv[i+1]); i += 2) {\n\tVcv[i] = Ccv[i];\n\tVcv[i+1] = Ccv[i+1];\n\tbitVectorSet(Vcp, i, bitVectorRead(Ccp, i));\n\tbitVectorSet(Vcp, i+1, bitVectorRead(Ccp, i+1));\n    }\n    /* Add clause corresponding to label. */\n    Vcv[i] = label;\n    bitVectorSet(Vcp, i, phase);\n    i++;\n    Vcv[i] = CUDD_MAXINDEX;\n    bitVectorSet(Vcp, i, 1);\n    i++;\n    /* Add sentinel. */\n    Vcv[i] = 0;\n    Vcv[i+1] = 0;\n    bitVectorSet(Vcp, i, 0);\n    bitVectorSet(Vcp, i+1, 0);\n\n    return(res);\n\n cleanup:\n    /* Vcp is guaranteed to be NULL here.  Hence, we do not try to free it. */\n    if (Vcv != NULL) FREE(Vcv);\n    if (res != NULL) Cudd_tlcInfoFree(res);\n\n    return(NULL);\n\n} /* end of computeClausesWithUniverse */\n\n\n/**\n  @brief Returns an enpty set of clauses.\n\n  @details No bit vector for the phases is allocated.\n\n  @return a pointer to an empty set of clauses if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdTlcInfo *\nemptyClauseSet(void)\n{\n    DdTlcInfo *eset;\n\n    eset = ALLOC(DdTlcInfo,1);\n    if (eset == NULL) return(NULL);\n    eset->vars = ALLOC(DdHalfWord,2);\n    if (eset->vars == NULL) {\n\tFREE(eset);\n\treturn(NULL);\n    }\n    /* Sentinel */\n    eset->vars[0] = 0;\n    eset->vars[1] = 0;\n    eset->phases = NULL; /* does not matter */\n    eset->cnt = 0;\n    return(eset);\n\n} /* end of emptyClauseSet */\n\n\n/**\n  @brief Returns true iff the argument is the sentinel clause.\n\n  @details A sentinel clause has both variables equal to 0.\n\n  @sideeffect None\n\n*/\nstatic int\nsentinelp(\n  DdHalfWord var1,\n  DdHalfWord var2)\n{\n    return(var1 == 0 && var2 == 0);\n\n} /* end of sentinelp */\n\n\n/**\n  @brief Returns true iff the two arguments are identical clauses.\n\n  @details Since literals are sorted, we only need to compare literals\n  in the same position.\n\n  @sideeffect None\n\n  @see beforep\n\n*/\nstatic int\nequalp(\n  DdHalfWord var1a,\n  short phase1a,\n  DdHalfWord var1b,\n  short phase1b,\n  DdHalfWord var2a,\n  short phase2a,\n  DdHalfWord var2b,\n  short phase2b)\n{\n    return(var1a == var2a && phase1a == phase2a &&\n\t   var1b == var2b && phase1b == phase2b);\n\n} /* end of equalp */\n\n\n/**\n  @brief Returns true iff the first argument precedes the second in\n  the clause order.\n\n  @details A clause precedes another if its first lieral\n  precedes the first literal of the other, or if the first literals\n  are the same, and its second literal precedes the second literal of\n  the other clause.  A literal precedes another if it has a higher\n  index, of if it has the same index, but it has lower phase.  Phase 0\n  is the positive phase, and it is lower than Phase 1 (negative\n  phase).\n\n  @sideeffect None\n\n  @see equalp\n\n*/\nstatic int\nbeforep(\n  DdHalfWord var1a,\n  short phase1a,\n  DdHalfWord var1b,\n  short phase1b,\n  DdHalfWord var2a,\n  short phase2a,\n  DdHalfWord var2b,\n  short phase2b)\n{\n    return(var1a > var2a || (var1a == var2a &&\n\t   (phase1a < phase2a || (phase1a == phase2a &&\n\t    (var1b > var2b || (var1b == var2b && phase1b < phase2b))))));\n\n} /* end of beforep */\n\n\n/**\n  @brief Returns true iff the argument is a one-literal clause.\n\n  @details A one-litaral clause has the constant FALSE as second\n  literal.  Since the constant TRUE is never used, it is sufficient to\n  test for a constant.\n\n  @sideeffect None\n\n*/\nstatic int\noneliteralp(\n  DdHalfWord var)\n{\n    return(var == CUDD_MAXINDEX);\n\n} /* end of oneliteralp */\n\n\n/**\n  @brief Returns true iff either literal of a clause is in a set of\n  literals.\n\n  @details The first four arguments specify the clause.  The remaining\n  two arguments specify the literal set.\n\n  @sideeffect None\n\n*/\nstatic int\nimpliedp(\n  DdHalfWord var1,\n  short phase1,\n  DdHalfWord var2,\n  short phase2,\n  BitVector *olv,\n  BitVector *olp)\n{\n    return((bitVectorRead(olv, var1) &&\n\t    bitVectorRead(olp, var1) == phase1) ||\n\t   (bitVectorRead(olv, var2) &&\n\t    bitVectorRead(olp, var2) == phase2));\n\n} /* end of impliedp */\n\n\n/**\n  @brief Allocates a bit vector.\n\n  @details The parameter size gives the number of bits.  This\n  procedure allocates enough words to hold the specified number of\n  bits.\n\n  @return a pointer to the allocated vector if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see bitVectorClear bitVectorFree\n\n*/\nstatic BitVector *\nbitVectorAlloc(\n  int size)\n{\n    int allocSize;\n    BitVector *vector;\n\n    /* Find out how many words we need.\n    ** There are sizeof(ptruint) * 8 bits in a ptruint.\n    ** The ceiling of the ratio of two integers m and n is given\n    ** by ((n-1)/m)+1.  Putting all this together, we get... */\n    allocSize = ((size - 1) / (sizeof(BitVector) * 8)) + 1;\n    vector = ALLOC(BitVector, allocSize);\n    if (vector == NULL) return(NULL);\n    /* Clear the whole array. */\n    (void) memset(vector, 0, allocSize * sizeof(BitVector));\n    return(vector);\n\n} /* end of bitVectorAlloc */\n\n\n/**\n  @brief Clears a bit vector.\n\n  @details The parameter size gives the number of bits.\n\n  @sideeffect None\n\n  @see bitVectorAlloc\n\n*/\nstatic void\nbitVectorClear(\n  BitVector *vector,\n  int size)\n{\n    int allocSize;\n\n    /* Find out how many words we need.\n    ** There are sizeof(ptruint) * 8 bits in a ptruint.\n    ** The ceiling of the ratio of two integers m and n is given\n    ** by ((n-1)/m)+1.  Putting all this together, we get... */\n    allocSize = ((size - 1) / (sizeof(BitVector) * 8)) + 1;\n    /* Clear the whole array. */\n    (void) memset(vector, 0, allocSize * sizeof(BitVector));\n    return;\n\n} /* end of bitVectorClear */\n\n\n/**\n  @brief Frees a bit vector.\n\n  @sideeffect None\n\n  @see bitVectorAlloc\n\n*/\nstatic void\nbitVectorFree(\n  BitVector *vector)\n{\n    FREE(vector);\n\n} /* end of bitVectorFree */\n\n\n/**\n  @brief Returns the i-th entry of a bit vector.\n\n  @sideeffect None\n\n  @see bitVectorSet\n\n*/\nstatic short\nbitVectorRead(\n  BitVector *vector,\n  int i)\n{\n    int word, bit;\n    short result;\n\n    if (vector == NULL) return((short) 0);\n\n    word = i >> LOGBPL;\n    bit = i & (BPL - 1);\n    result = (short) ((vector[word] >> bit) & (ptruint) 1);\n    return(result);\n\n} /* end of bitVectorRead */\n\n\n/**\n  @brief Sets the i-th entry of a bit vector to a value.\n\n  @sideeffect None\n\n  @see bitVectorRead\n\n*/\nstatic void\nbitVectorSet(\n  BitVector * vector,\n  int i,\n  short val)\n{\n    int word, bit;\n\n    word = i >> LOGBPL;\n    bit = i & (BPL - 1);\n    vector[word] &= ~((ptruint) 1 << bit);\n    vector[word] |= (((ptruint) val) << bit);\n\n} /* end of bitVectorSet */\n\n\n/**\n  @brief Allocates a DdTlcInfo Structure.\n\n  @return a pointer to a DdTlcInfo Structure if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_tlcInfoFree\n\n*/\nstatic DdTlcInfo *\ntlcInfoAlloc(void)\n{\n    DdTlcInfo *res = ALLOC(DdTlcInfo,1);\n    if (res == NULL) return(NULL);\n    res->vars = NULL;\n    res->phases = NULL;\n    res->cnt = 0;\n    return(res);\n\n} /* end of tlcInfoAlloc */\n"
  },
  {
    "path": "cudd/cudd/cuddExact.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for exact variable reordering.\n\n  @author Cheng Hua, Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int getMaxBinomial (int n);\nstatic DdHalfWord ** getMatrix (int rows, int cols);\nstatic void freeMatrix (DdHalfWord **matrix);\nstatic int getLevelKeys (DdManager *table, int l);\nstatic int ddShuffle (DdManager *table, DdHalfWord *permutation, int lower, int upper);\nstatic int ddSiftUp (DdManager *table, int x, int xLow);\nstatic int updateUB (DdManager *table, int oldBound, DdHalfWord *bestOrder, int lower, int upper);\nstatic int ddCountRoots (DdManager *table, int lower, int upper);\nstatic void ddClearGlobal (DdManager *table, int lower, int maxlevel);\nstatic int computeLB (DdManager *table, DdHalfWord *order, int roots, int cost, int lower, int upper, int level);\nstatic int updateEntry (DdManager *table, DdHalfWord *order, int level, int cost, DdHalfWord **orders, int *costs, int subsets, char *mask, int lower, int upper);\nstatic void pushDown (DdHalfWord *order, int j, int level);\nstatic DdHalfWord * initSymmInfo (DdManager *table, int lower, int upper);\nstatic int checkSymmInfo (DdManager *table, DdHalfWord *symmInfo, int index, int level);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Exact variable ordering algorithm.\n\n  @details Finds an optimum order for the variables between lower and\n  upper.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddExact(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int k, i, j;\n    int maxBinomial, oldSubsets, newSubsets;\n    int subsetCost;\n    int size;\t\t\t/* number of variables to be reordered */\n    int unused, nvars, level, result;\n    int upperBound, lowerBound, cost;\n    int roots;\n    char *mask = NULL;\n    DdHalfWord  *symmInfo = NULL;\n    DdHalfWord **newOrder = NULL;\n    DdHalfWord **oldOrder = NULL;\n    int *newCost = NULL;\n    int *oldCost = NULL;\n    DdHalfWord **tmpOrder;\n    int *tmpCost;\n    DdHalfWord *bestOrder = NULL;\n    DdHalfWord *order;\n#ifdef DD_STATS\n    int  ddTotalSubsets;\n#endif\n\n    /* Restrict the range to be reordered by excluding unused variables\n    ** at the two ends. */\n    while (table->subtables[lower].keys == 1 &&\n\t   table->vars[table->invperm[lower]]->ref == 1 &&\n\t   lower < upper)\n\tlower++;\n    while (table->subtables[upper].keys == 1 &&\n\t   table->vars[table->invperm[upper]]->ref == 1 &&\n\t   lower < upper)\n\tupper--;\n    if (lower == upper) return(1); /* trivial problem */\n\n    /* Apply symmetric sifting to get a good upper bound and to extract\n    ** symmetry information. */\n    result = cuddSymmSiftingConv(table,lower,upper);\n    if (result == 0) goto cuddExactOutOfMem;\n\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n\");\n    table->totalShuffles = 0;\n    ddTotalSubsets = 0;\n#endif\n\n    /* Initialization. */\n    nvars = table->size;\n    size = upper - lower + 1;\n    /* Count unused variable among those to be reordered.  This is only\n    ** used to compute maxBinomial. */\n    unused = 0;\n    for (i = lower + 1; i < upper; i++) {\n\tif (table->subtables[i].keys == 1 &&\n\t    table->vars[table->invperm[i]]->ref == 1)\n\t    unused++;\n    }\n\n    /* Find the maximum number of subsets we may have to store. */\n    maxBinomial = getMaxBinomial(size - unused);\n    if (maxBinomial == -1) goto cuddExactOutOfMem;\n\n    newOrder = getMatrix(maxBinomial, size);\n    if (newOrder == NULL) goto cuddExactOutOfMem;\n\n    newCost = ALLOC(int, maxBinomial);\n    if (newCost == NULL) goto cuddExactOutOfMem;\n\n    oldOrder = getMatrix(maxBinomial, size);\n    if (oldOrder == NULL) goto cuddExactOutOfMem;\n\n    oldCost = ALLOC(int, maxBinomial);\n    if (oldCost == NULL) goto cuddExactOutOfMem;\n\n    bestOrder = ALLOC(DdHalfWord, size);\n    if (bestOrder == NULL) goto cuddExactOutOfMem;\n\n    mask = ALLOC(char, nvars);\n    if (mask == NULL) goto cuddExactOutOfMem;\n\n    symmInfo = initSymmInfo(table, lower, upper);\n    if (symmInfo == NULL) goto cuddExactOutOfMem;\n\n    roots = ddCountRoots(table, lower, upper);\n\n    /* Initialize the old order matrix for the empty subset and the best\n    ** order to the current order. The cost for the empty subset includes\n    ** the cost of the levels between upper and the constants. These levels\n    ** are not going to change. Hence, we count them only once.\n    */\n    oldSubsets = 1;\n    for (i = 0; i < size; i++) {\n\toldOrder[0][i] = bestOrder[i] = (DdHalfWord) table->invperm[i+lower];\n    }\n    subsetCost = (int) table->constants.keys;\n    for (i = upper + 1; i < nvars; i++)\n\tsubsetCost += getLevelKeys(table,i);\n    oldCost[0] = subsetCost;\n    /* The upper bound is initialized to the current size of the BDDs. */\n    upperBound = (int) (table->keys - table->isolated);\n\n    /* Now consider subsets of increasing size. */\n    for (k = 1; k <= size; k++) {\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\"Processing subsets of size %d\\n\", k);\n\tfflush(table->out);\n#endif\n\tnewSubsets = 0;\n\tlevel = size - k;\t\t/* offset of first bottom variable */\n\n\tfor (i = 0; i < oldSubsets; i++) { /* for each subset of size k-1 */\n\t    order = oldOrder[i];\n\t    cost = oldCost[i];\n\t    lowerBound = computeLB(table, order, roots, cost, lower, upper,\n\t\t\t\t   level);\n\t    if (lowerBound >= upperBound)\n\t\tcontinue;\n\t    /* Impose new order. */\n\t    result = ddShuffle(table, order, lower, upper);\n\t    if (result == 0) goto cuddExactOutOfMem;\n\t    upperBound = updateUB(table,upperBound,bestOrder,lower,upper);\n\t    /* For each top bottom variable. */\n\t    for (j = level; j >= 0; j--) {\n\t\t/* Skip unused variables. */\n\t\tif (table->subtables[j+lower-1].keys == 1 &&\n\t\t    table->vars[table->invperm[j+lower-1]]->ref == 1) continue;\n\t\t/* Find cost under this order. */\n\t\tsubsetCost = cost + getLevelKeys(table, lower + level);\n\t\tnewSubsets = updateEntry(table, order, level, subsetCost,\n\t\t\t\t\t newOrder, newCost, newSubsets, mask,\n\t\t\t\t\t lower, upper);\n\t\tif (j == 0)\n\t\t    break;\n\t\tif (checkSymmInfo(table, symmInfo, (int) order[j-1], level) == 0)\n\t\t    continue;\n\t\tpushDown(order,j-1,level);\n\t\t/* Impose new order. */\n\t\tresult = ddShuffle(table, order, lower, upper);\n\t\tif (result == 0) goto cuddExactOutOfMem;\n\t\tupperBound = updateUB(table,upperBound,bestOrder,lower,upper);\n\t    } /* for each bottom variable */\n\t} /* for each subset of size k */\n\n\t/* New orders become old orders in preparation for next iteration. */\n\ttmpOrder = oldOrder; tmpCost = oldCost;\n\toldOrder = newOrder; oldCost = newCost;\n\tnewOrder = tmpOrder; newCost = tmpCost;\n#ifdef DD_STATS\n\tddTotalSubsets += newSubsets;\n#endif\n\toldSubsets = newSubsets;\n    }\n    result = ddShuffle(table, bestOrder, lower, upper);\n    if (result == 0) goto cuddExactOutOfMem;\n#ifdef DD_STATS\n#ifdef DD_VERBOSE\n    (void) fprintf(table->out,\"\\n\");\n#endif\n    (void) fprintf(table->out,\"#:S_EXACT   %8d: total subsets\\n\",\n\t\t   ddTotalSubsets);\n    (void) fprintf(table->out,\"#:H_EXACT   %8d: total shuffles\",\n\t\t   table->totalShuffles);\n#endif\n\n    freeMatrix(newOrder);\n    freeMatrix(oldOrder);\n    FREE(bestOrder);\n    FREE(oldCost);\n    FREE(newCost);\n    FREE(symmInfo);\n    FREE(mask);\n    return(1);\n\ncuddExactOutOfMem:\n\n    if (newOrder != NULL) freeMatrix(newOrder);\n    if (oldOrder != NULL) freeMatrix(oldOrder);\n    if (bestOrder != NULL) FREE(bestOrder);\n    if (oldCost != NULL) FREE(oldCost);\n    if (newCost != NULL) FREE(newCost);\n    if (symmInfo != NULL) FREE(symmInfo);\n    if (mask != NULL) FREE(mask);\n    table->errorCode = CUDD_MEMORY_OUT;\n    return(0);\n\n} /* end of cuddExact */\n\n\n/**\n  @brief Returns the maximum value of `(n choose k)` for a given `n`.\n\n  @details Computes the maximum value of `(n choose k)` for a given\n  `n`.  The maximum value occurs for `k = n/2` when `n` is even, or `k =\n  (n-1)/2` when `n` is odd.  The algorithm used in this procedure avoids\n  intermediate overflow problems.  It is based on the identity\n\n      binomial(n,k) = n/k * binomial(n-1,k-1).\n\n  @return the computed value if successful; -1 if out of range.\n\n  @sideeffect None\n\n*/\nstatic int\ngetMaxBinomial(\n  int n)\n{\n    double i, j, result;\n\n    if (n < 0 || n > 33) return(-1); /* error */\n    if (n < 2) return(1);\n\n    for (result = (double)((n+3)/2), i = result+1, j=2; i <= n; i++, j++) {\n\tresult *= i;\n\tresult /= j;\n    }\n\n    return((int)result);\n\n} /* end of getMaxBinomial */\n\n\n#if 0\n/**\n  @brief Returns the gcd of two integers.\n\n  @details Uses the binary GCD algorithm described in Cormen,\n  Leiserson, and Rivest.\n\n  @sideeffect None\n\n*/\nstatic int\ngcd(\n  int  x,\n  int  y)\n{\n    int a;\n    int b;\n    int lsbMask;\n\n    /* GCD(n,0) = n. */\n    if (x == 0) return(y);\n    if (y == 0) return(x);\n\n    a = x; b = y; lsbMask = 1;\n\n    /* Here both a and b are != 0. The iteration maintains this invariant.\n    ** Hence, we only need to check for when they become equal.\n    */\n    while (a != b) {\n\tif (a & lsbMask) {\n\t    if (b & lsbMask) {\t/* both odd */\n\t\tif (a < b) {\n\t\t    b = (b - a) >> 1;\n\t\t} else {\n\t\t    a = (a - b) >> 1;\n\t\t}\n\t    } else {\t\t/* a odd, b even */\n\t\tb >>= 1;\n\t    }\n\t} else {\n\t    if (b & lsbMask) {\t/* a even, b odd */\n\t\ta >>= 1;\n\t    } else {\t\t/* both even */\n\t\tlsbMask <<= 1;\n\t    }\n\t}\n    }\n\n    return(a);\n\n} /* end of gcd */\n#endif\n\n\n/**\n  @brief Allocates a two-dimensional matrix of ints.\n\n  @return the pointer to the matrix if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see freeMatrix\n\n*/\nstatic DdHalfWord **\ngetMatrix(\n  int  rows /* number of rows */,\n  int  cols /* number of columns */)\n{\n    DdHalfWord **matrix;\n    int i;\n\n    if (cols*rows == 0) return(NULL);\n    matrix = ALLOC(DdHalfWord *, rows);\n    if (matrix == NULL) return(NULL);\n    matrix[0] = ALLOC(DdHalfWord, cols*rows);\n    if (matrix[0] == NULL) {\n\tFREE(matrix);\n\treturn(NULL);\n    }\n    for (i = 1; i < rows; i++) {\n\tmatrix[i] = matrix[i-1] + cols;\n    }\n    return(matrix);\n\n} /* end of getMatrix */\n\n\n/**\n  @brief Frees a two-dimensional matrix allocated by getMatrix.\n\n  @sideeffect None\n\n  @see getMatrix\n\n*/\nstatic void\nfreeMatrix(\n  DdHalfWord ** matrix)\n{\n    FREE(matrix[0]);\n    FREE(matrix);\n    return;\n\n} /* end of freeMatrix */\n\n\n/**\n  @brief Returns the number of nodes at one level of a unique table.\n\n  @details The projection function, if isolated, is not counted.\n\n  @sideeffect None\n\n*/\nstatic int\ngetLevelKeys(\n  DdManager * table,\n  int  l)\n{\n    int isolated;\n    int x;        /* x is an index */\n\n    x = table->invperm[l];\n    isolated = table->vars[x]->ref == 1;\n\n    return((int) table->subtables[l].keys - isolated);\n\n} /* end of getLevelKeys */\n\n\n/**\n  @brief Reorders variables according to a given permutation.\n\n  @details The i-th permutation array contains the index of the\n  variable that should be brought to the i-th level. ddShuffle assumes\n  that no dead nodes are present and that the interaction matrix is\n  properly initialized.  The reordering is achieved by a series of\n  upward sifts.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddShuffle(\n  DdManager * table,\n  DdHalfWord * permutation,\n  int  lower,\n  int  upper)\n{\n    DdHalfWord\tindex;\n    int\t\tlevel;\n    int\t\tposition;\n#if 0\n    int\t\tnumvars;\n#endif\n    int\t\tresult;\n#if defined(DD_STATS) && defined(DD_VERBOSE)\n    int\t\tinitialSize;\n    int\t\tfinalSize;\n#endif\n\n#if defined(DD_STATS) && defined(DD_VERBOSE)\n    initialSize = (int) (table->keys - table->isolated);\n#endif\n\n#if 0\n    numvars = table->size;\n\n    (void) fprintf(table->out,\"%d:\", table->totalShuffles);\n    for (level = 0; level < numvars; level++) {\n\t(void) fprintf(table->out,\" %d\", table->invperm[level]);\n    }\n    (void) fprintf(table->out,\"\\n\");\n#endif\n\n    for (level = 0; level <= upper - lower; level++) {\n\tindex = permutation[level];\n\tposition = table->perm[index];\n\tresult = ddSiftUp(table,position,level+lower);\n\tif (!result) return(0);\n    }\n\n#ifdef DD_STATS\n    table->totalShuffles++;\n#ifdef DD_VERBOSE\n    finalSize = (int) (table->keys - table->isolated);\n    if (finalSize < initialSize) {\n\t(void) fprintf(table->out,\"-\");\n    } else if (finalSize > initialSize) {\n\t(void) fprintf(table->out,\"+\");\n    } else {\n\t(void) fprintf(table->out,\"=\");\n    }\n    if ((table->totalShuffles & 63) == 0) (void) fprintf(table->out,\"\\n\");\n    fflush(table->out);\n#endif\n#endif\n\n    return(1);\n\n} /* end of ddShuffle */\n\n\n/**\n  @brief Moves one variable up.\n\n  @details Takes a variable from position x and sifts it up to\n  position xLow;  xLow should be less than or equal to x.\n\n  @return 1 if successful; 0 otherwise\n\n  @sideeffect None\n\n*/\nstatic int\nddSiftUp(\n  DdManager * table,\n  int  x,\n  int  xLow)\n{\n    int        y;\n    int        size;\n\n    y = cuddNextLow(table,x);\n    while (y >= xLow) {\n\tsize = cuddSwapInPlace(table,y,x);\n\tif (size == 0) {\n\t    return(0);\n\t}\n\tx = y;\n\ty = cuddNextLow(table,x);\n    }\n    return(1);\n\n} /* end of ddSiftUp */\n\n\n/**\n  @brief Updates the upper bound and saves the best order seen so far.\n\n  @return the current value of the upper bound.\n\n  @sideeffect None\n\n*/\nstatic int\nupdateUB(\n  DdManager * table,\n  int  oldBound,\n  DdHalfWord * bestOrder,\n  int  lower,\n  int  upper)\n{\n    int i;\n    int newBound = (int) (table->keys - table->isolated);\n\n    if (newBound < oldBound) {\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\"New upper bound = %d\\n\", newBound);\n\tfflush(table->out);\n#endif\n\tfor (i = lower; i <= upper; i++)\n\t    bestOrder[i-lower] = (DdHalfWord) table->invperm[i];\n\treturn(newBound);\n    } else {\n\treturn(oldBound);\n    }\n\n} /* end of updateUB */\n\n\n/**\n  @brief Counts the number of roots.\n\n  @details Counts the number of roots at the levels between lower and\n  upper.  The computation is based on breadth-first search.  A node is\n  a root if it is not reachable from any previously visited node.\n  (All the nodes at level lower are therefore considered roots.)  The\n  roots that are constant nodes are always ignored.  The visited flag\n  uses the LSB of the next pointer.\n\n  @return the root count.\n\n  @sideeffect None\n\n  @see ddClearGlobal\n\n*/\nstatic int\nddCountRoots(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int i,j;\n    DdNode *f;\n    DdNodePtr *nodelist;\n    DdNode *sentinel = &(table->sentinel);\n    int slots;\n    int roots = 0;\n    int maxlevel = lower;\n\n    for (i = lower; i <= upper; i++) {\n\tnodelist = table->subtables[i].nodelist;\n\tslots = (int) table->subtables[i].slots;\n\tfor (j = 0; j < slots; j++) {\n\t    f = nodelist[j];\n\t    while (f != sentinel) {\n\t\t/* A node is a root of the DAG if it cannot be\n\t\t** reached by nodes above it. If a node was never\n\t\t** reached during the previous depth-first searches,\n\t\t** then it is a root, and we start a new depth-first\n\t\t** search from it.\n\t\t*/\n\t\tif (!Cudd_IsComplement(f->next)) {\n\t\t    if (f != table->vars[f->index]) {\n\t\t\troots++;\n\t\t    }\n\t\t}\n\t\tif (!cuddIsConstant(cuddT(f))) {\n\t\t    cuddT(f)->next = Cudd_Complement(cuddT(f)->next);\n\t\t    if (table->perm[cuddT(f)->index] > maxlevel)\n\t\t\tmaxlevel = table->perm[cuddT(f)->index];\n\t\t}\n\t\tif (!Cudd_IsConstantInt(cuddE(f))) {\n\t\t    Cudd_Regular(cuddE(f))->next =\n\t\t\tCudd_Complement(Cudd_Regular(cuddE(f))->next);\n\t\t    if (table->perm[Cudd_Regular(cuddE(f))->index] > maxlevel)\n\t\t\tmaxlevel = table->perm[Cudd_Regular(cuddE(f))->index];\n\t\t}\n\t\tf = Cudd_Regular(f->next);\n\t    }\n\t}\n    }\n    ddClearGlobal(table, lower, maxlevel);\n\n    return(roots);\n\n} /* end of ddCountRoots */\n\n\n/**\n  @brief Scans the %DD and clears the LSB of the next pointers.\n\n  @details The LSB of the next pointers are used as markers to tell\n  whether a node was reached. Once the roots are counted, these flags\n  are reset.\n\n  @sideeffect None\n\n  @see ddCountRoots\n\n*/\nstatic void\nddClearGlobal(\n  DdManager * table,\n  int  lower,\n  int  maxlevel)\n{\n    int i,j;\n    DdNode *f;\n    DdNodePtr *nodelist;\n    DdNode *sentinel = &(table->sentinel);\n    int slots;\n\n    for (i = lower; i <= maxlevel; i++) {\n\tnodelist = table->subtables[i].nodelist;\n\tslots = (int) table->subtables[i].slots;\n\tfor (j = 0; j < slots; j++) {\n\t    f = nodelist[j];\n\t    while (f != sentinel) {\n\t\tf->next = Cudd_Regular(f->next);\n\t\tf = f->next;\n\t    }\n\t}\n    }\n\n} /* end of ddClearGlobal */\n\n\n/**\n  @brief Computes a lower bound on the size of a %BDD.\n\n  @details The lower bound depends on the following factors:\n  <ul>\n  <li> size of the lower part of it;\n  <li> size of the part of the upper part not subjected to reordering;\n  <li> number of roots in the part of the %BDD subjected to reordering;\n  <li> variable in the support of the roots in the upper part of the\n       %BDD subjected to reordering.\n  </ul>\n\n  @sideeffect None\n\n*/\nstatic int\ncomputeLB(\n  DdManager * table\t\t/**< manager */,\n  DdHalfWord * order\t\t/**< optimal order for the subset */,\n  int  roots\t\t\t/**< roots between lower and upper */,\n  int  cost\t\t\t/**< minimum cost for the subset */,\n  int  lower\t\t\t/**< lower level to be reordered */,\n  int  upper\t\t\t/**< upper level to be reordered */,\n  int  level\t\t\t/**< offset for the current top bottom var */\n  )\n{\n    int i;\n    int lb = cost;\n    int lb1 = 0;\n    int lb2;\n    int support;\n    DdHalfWord ref;\n\n    /* The levels not involved in reordering are not going to change.\n    ** Add their sizes to the lower bound.\n    */\n    for (i = 0; i < lower; i++) {\n\tlb += getLevelKeys(table,i);\n    }\n    /* If a variable is in the support, then there is going\n    ** to be at least one node labeled by that variable.\n    */\n    for (i = lower; i <= lower+level; i++) {\n\tsupport = table->subtables[i].keys > 1 ||\n\t    table->vars[order[i-lower]]->ref > 1;\n\tlb1 += support;\n    }\n\n    /* Estimate the number of nodes required to connect the roots to\n    ** the nodes in the bottom part. */\n    if (lower+level+1 < table->size) {\n\tif (lower+level < upper)\n\t    ref = table->vars[order[level+1]]->ref;\n\telse\n\t    ref = table->vars[table->invperm[upper+1]]->ref;\n\tlb2 = (int) table->subtables[lower+level+1].keys -\n            (ref > (DdHalfWord) 1) - roots;\n    } else {\n\tlb2 = 0;\n    }\n\n    lb += lb1 > lb2 ? lb1 : lb2;\n\n    return(lb);\n\n} /* end of computeLB */\n\n\n/**\n  @brief Updates entry for a subset.\n\n  @details Finds the subset, if it exists.  If the new order for the\n  subset has lower cost, or if the subset did not exist, it stores the\n  new order and cost.\n\n  @return the number of subsets currently in the table.\n\n  @sideeffect None\n\n*/\nstatic int\nupdateEntry(\n  DdManager * table,\n  DdHalfWord * order,\n  int  level,\n  int  cost,\n  DdHalfWord ** orders,\n  int * costs,\n  int  subsets,\n  char * mask,\n  int  lower,\n  int  upper)\n{\n    int i, j;\n    int size = upper - lower + 1;\n\n    /* Build a mask that says what variables are in this subset. */\n    for (i = lower; i <= upper; i++)\n\tmask[table->invperm[i]] = 0;\n    for (i = level; i < size; i++)\n\tmask[order[i]] = 1;\n\n    /* Check each subset until a match is found or all subsets are examined. */\n    for (i = 0; i < subsets; i++) {\n\tDdHalfWord *subset = orders[i];\n\tfor (j = level; j < size; j++) {\n\t    if (mask[subset[j]] == 0)\n\t\tbreak;\n\t}\n\tif (j == size)\t\t/* no mismatches: success */\n\t    break;\n    }\n    if (i == subsets || cost < costs[i]) {\t\t/* add or replace */\n\tfor (j = 0; j < size; j++)\n\t    orders[i][j] = order[j];\n\tcosts[i] = cost;\n\tsubsets += (i == subsets);\n    }\n    return(subsets);\n\n} /* end of updateEntry */\n\n\n/**\n  @brief Pushes a variable in the order down to position \"level.\"\n\n  @sideeffect None\n\n*/\nstatic void\npushDown(\n  DdHalfWord * order,\n  int  j,\n  int  level)\n{\n    int i;\n    DdHalfWord tmp;\n\n    tmp = order[j];\n    for (i = j; i < level; i++) {\n\torder[i] = order[i+1];\n    }\n    order[level] = tmp;\n    return;\n\n} /* end of pushDown */\n\n\n/**\n  @brief Gathers symmetry information.\n\n  @details Translates the symmetry information stored in the next\n  field of each subtable from level to indices. This procedure is called\n  immediately after symmetric sifting, so that the next fields are correct.\n  By translating this informaton in terms of indices, we make it independent\n  of subsequent reorderings. The format used is that of the next fields:\n  a circular list where each variable points to the next variable in the\n  same symmetry group. Only the entries between lower and upper are\n  considered.  The procedure returns a pointer to an array\n  holding the symmetry information if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see checkSymmInfo\n\n*/\nstatic DdHalfWord *\ninitSymmInfo(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int level, index, next, nextindex;\n    DdHalfWord *symmInfo;\n\n    symmInfo =  ALLOC(DdHalfWord, table->size);\n    if (symmInfo == NULL) return(NULL);\n\n    for (level = lower; level <= upper; level++) {\n\tindex = table->invperm[level];\n\tnext =  (int) table->subtables[level].next;\n\tnextindex = table->invperm[next];\n\tsymmInfo[index] = (DdHalfWord) nextindex;\n    }\n    return(symmInfo);\n\n} /* end of initSymmInfo */\n\n\n/**\n  @brief Check symmetry condition.\n\n  @details Returns 1 if a variable is the one with the highest index\n  among those belonging to a symmetry group that are in the top part of\n  the %BDD.  The top part is given by level.\n\n  @sideeffect None\n\n  @see initSymmInfo\n\n*/\nstatic int\ncheckSymmInfo(\n  DdManager * table,\n  DdHalfWord * symmInfo,\n  int  index,\n  int  level)\n{\n    int i;\n\n    i = (int) symmInfo[index];\n    while (i != index) {\n\tif (index < i && table->perm[i] <= level)\n\t    return(0);\n\ti = (int) symmInfo[i];\n    }\n    return(1);\n\n} /* end of checkSymmInfo */\n"
  },
  {
    "path": "cudd/cudd/cuddExport.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Export functions.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cstringstream.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int ddDoDumpBlif (DdManager *dd, DdNode *f, FILE *fp, st_table *visited, char const * const *names, int mv);\nstatic int ddDoDumpDaVinci (DdManager *dd, DdNode *f, FILE *fp, st_table *visited, char const * const *names, ptruint mask);\nstatic int ddDoDumpDDcal (DdManager *dd, DdNode *f, FILE *fp, st_table *visited, char const * const *names, ptruint mask);\nstatic int ddDoDumpFactoredForm (DdManager *dd, DdNode *f, FILE *fp, char const * const *names);\nstatic int ddDoFactoredFormString(DdManager * dd, DdNode *f, cstringstream stream, char const * const * names);\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Writes a blif file representing the argument BDDs.\n\n  @details Each %BDD is written as a network of multiplexers.\n  Cudd_DumpBlif does not close the file: This is the caller\n  responsibility. Cudd_DumpBlif uses a minimal unique subset of the\n  hexadecimal address of a node as name for it.  If the argument\n  inames is non-null, it is assumed to hold the pointers to the names\n  of the inputs. Similarly for onames.\n\n  @return 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n  system full, or an %ADD with constants different from 0 and 1).\n\n  @sideeffect None\n\n  @see Cudd_DumpBlifBody Cudd_DumpDot Cudd_PrintDebug Cudd_DumpDDcal\n  Cudd_DumpDaVinci Cudd_DumpFactoredForm\n\n*/\nint\nCudd_DumpBlif(\n  DdManager * dd /**< manager */,\n  int  n /**< number of output nodes to be dumped */,\n  DdNode ** f /**< array of output nodes to be dumped */,\n  char const * const * inames /**< array of input names (or NULL) */,\n  char const * const * onames /**< array of output names (or NULL) */,\n  char * mname /**< model name (or NULL) */,\n  FILE * fp /**< pointer to the dump file */,\n  int mv /**< 0: blif, 1: blif-MV */)\n{\n    DdNode\t*support = NULL;\n    DdNode\t*scan;\n    int\t\t*sorted = NULL;\n    int\t\tnvars = dd->size;\n    int\t\tretval;\n    int\t\ti;\n\n    /* Build a bit array with the support of f. */\n    sorted = ALLOC(int,nvars);\n    if (sorted == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tgoto failure;\n    }\n    for (i = 0; i < nvars; i++) sorted[i] = 0;\n\n    /* Take the union of the supports of each output function. */\n    support = Cudd_VectorSupport(dd,f,n);\n    if (support == NULL) goto failure;\n    cuddRef(support);\n    scan = support;\n    while (!cuddIsConstant(scan)) {\n\tsorted[scan->index] = 1;\n\tscan = cuddT(scan);\n    }\n    Cudd_RecursiveDeref(dd,support);\n    support = NULL; /* so that we do not try to free it in case of failure */\n\n    /* Write the header (.model .inputs .outputs). */\n    if (mname == NULL) {\n\tretval = fprintf(fp,\".model DD\\n.inputs\");\n    } else {\n\tretval = fprintf(fp,\".model %s\\n.inputs\",mname);\n    }\n    if (retval == EOF) {\n\tFREE(sorted);\n\treturn(0);\n    }\n\n    /* Write the input list by scanning the support array. */\n    for (i = 0; i < nvars; i++) {\n\tif (sorted[i]) {\n\t    if (inames == NULL) {\n\t\tretval = fprintf(fp,\" %d\", i);\n\t    } else {\n\t\tretval = fprintf(fp,\" %s\", inames[i]);\n\t    }\n\t    if (retval == EOF) goto failure;\n\t}\n    }\n    FREE(sorted);\n    sorted = NULL;\n\n    /* Write the .output line. */\n    retval = fprintf(fp,\"\\n.outputs\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < n; i++) {\n\tif (onames == NULL) {\n\t    retval = fprintf(fp,\" f%d\", i);\n\t} else {\n\t    retval = fprintf(fp,\" %s\", onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n    }\n    retval = fprintf(fp,\"\\n\");\n    if (retval == EOF) goto failure;\n\n    retval = Cudd_DumpBlifBody(dd, n, f, inames, onames, fp, mv);\n    if (retval == 0) goto failure;\n\n    /* Write trailer and return. */\n    retval = fprintf(fp,\".end\\n\");\n    if (retval == EOF) goto failure;\n\n    return(1);\n\n failure:\n    if (sorted != NULL) FREE(sorted);\n    if (support != NULL) Cudd_RecursiveDeref(dd,support);\n    return(0);\n\n} /* end of Cudd_DumpBlif */\n\n\n/**\n  @brief Writes a blif body representing the argument BDDs.\n\n  @details Each %BDD is written as a network of multiplexers.  No\n  header (.model, .inputs, and .outputs) and footer (.end) are\n  produced by this function.  One multiplexer is written for each %BDD\n  node.  Cudd_DumpBlifBody does not close the file: This is the caller\n  responsibility. Cudd_DumpBlifBody uses a minimal unique subset of\n  the hexadecimal address of a node as name for it.  If the argument\n  inames is non-null, it is assumed to hold the pointers to the names\n  of the inputs. Similarly for onames. This function prints out only\n  .names part.\n\n  @return 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n  system full, or an %ADD with constants different from 0 and 1).\n\n  @sideeffect None\n\n  @see Cudd_DumpBlif Cudd_DumpDot Cudd_PrintDebug Cudd_DumpDDcal\n  Cudd_DumpDaVinci Cudd_DumpFactoredForm\n\n*/\nint\nCudd_DumpBlifBody(\n  DdManager * dd /**< manager */,\n  int  n /**< number of output nodes to be dumped */,\n  DdNode ** f /**< array of output nodes to be dumped */,\n  char const * const * inames /**< array of input names (or NULL) */,\n  char const * const * onames /**< array of output names (or NULL) */,\n  FILE * fp /**< pointer to the dump file */,\n  int mv /**< 0: blif, 1: blif-MV */)\n{\n    st_table\t*visited = NULL;\n    int\t\tretval;\n    int\t\ti;\n\n    /* Initialize symbol table for visited nodes. */\n    visited = st_init_table(st_ptrcmp, st_ptrhash);\n    if (visited == NULL) goto failure;\n\n    /* Call the function that really gets the job done. */\n    for (i = 0; i < n; i++) {\n\tretval = ddDoDumpBlif(dd,Cudd_Regular(f[i]),fp,visited,inames,mv);\n\tif (retval == 0) goto failure;\n    }\n\n    /* To account for the possible complement on the root,\n    ** we put either a buffer or an inverter at the output of\n    ** the multiplexer representing the top node.\n    */\n    for (i = 0; i < n; i++) {\n\tif (onames == NULL) {\n\t    retval = fprintf(fp, \".names %\" PRIxPTR \" f%d\\n\",\n                (ptruint) f[i] / (ptruint) sizeof(DdNode), i);\n\t} else {\n\t    retval = fprintf(fp, \".names %\" PRIxPTR \" %s\\n\",\n                (ptruint) f[i] / (ptruint) sizeof(DdNode), onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n\tif (Cudd_IsComplement(f[i])) {\n\t    retval = fprintf(fp,\"%s0 1\\n\", mv ? \".def 0\\n\" : \"\");\n\t} else {\n\t    retval = fprintf(fp,\"%s1 1\\n\", mv ? \".def 0\\n\" : \"\");\n\t}\n\tif (retval == EOF) goto failure;\n    }\n\n    st_free_table(visited);\n    return(1);\n\n failure:\n    if (visited != NULL) st_free_table(visited);\n    return(0);\n\n} /* end of Cudd_DumpBlifBody */\n\n\n/**\n  @brief Writes a dot file representing the argument DDs.\n\n  @details Writes a file representing the argument DDs in a format\n  suitable for the graph drawing program dot.\n  Cudd_DumpDot does not close the file: This is the caller\n  responsibility. Cudd_DumpDot uses a minimal unique subset of the\n  hexadecimal address of a node as name for it.\n  If the argument inames is non-null, it is assumed to hold the pointers\n  to the names of the inputs. Similarly for onames.\n  Cudd_DumpDot uses the following convention to draw arcs:\n    <ul>\n    <li> solid line: THEN arcs;\n    <li> dotted line: complement arcs;\n    <li> dashed line: regular ELSE arcs.\n    </ul>\n  The dot options are chosen so that the drawing fits on a letter-size\n  sheet.\n\n  @return 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n  system full).\n\n  @sideeffect None\n\n  @see Cudd_DumpBlif Cudd_PrintDebug Cudd_DumpDDcal\n  Cudd_DumpDaVinci Cudd_DumpFactoredForm\n\n*/\nint\nCudd_DumpDot(\n  DdManager * dd /**< manager */,\n  int  n /**< number of output nodes to be dumped */,\n  DdNode ** f /**< array of output nodes to be dumped */,\n  char const * const * inames /**< array of input names (or NULL) */,\n  char const * const * onames /**< array of output names (or NULL) */,\n  FILE * fp /**< pointer to the dump file */)\n{\n    DdNode\t*support = NULL;\n    DdNode\t*scan;\n    int\t\t*sorted = NULL;\n    int\t\tnvars = dd->size;\n    st_table\t*visited = NULL;\n    st_generator *gen = NULL;\n    int\t\tretval;\n    int\t\ti, j;\n    int\t\tslots;\n    DdNodePtr\t*nodelist;\n    ptruint\trefAddr, diff, mask = 0;\n\n    /* Build a bit array with the support of f. */\n    sorted = ALLOC(int,nvars);\n    if (sorted == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tgoto failure;\n    }\n    for (i = 0; i < nvars; i++) sorted[i] = 0;\n\n    /* Take the union of the supports of each output function. */\n    support = Cudd_VectorSupport(dd,f,n);\n    if (support == NULL) goto failure;\n    cuddRef(support);\n    scan = support;\n    while (!cuddIsConstant(scan)) {\n\tsorted[scan->index] = 1;\n\tscan = cuddT(scan);\n    }\n    Cudd_RecursiveDeref(dd,support);\n    support = NULL; /* so that we do not try to free it in case of failure */\n\n    /* Initialize symbol table for visited nodes. */\n    visited = st_init_table(st_ptrcmp, st_ptrhash);\n    if (visited == NULL) goto failure;\n\n    /* Collect all the nodes of this DD in the symbol table. */\n    for (i = 0; i < n; i++) {\n\tretval = cuddCollectNodes(Cudd_Regular(f[i]),visited);\n\tif (retval == 0) goto failure;\n    }\n\n    /* Find how many most significant hex digits are identical\n    ** in the addresses of all the nodes. Build a mask based\n    ** on this knowledge, so that digits that carry no information\n    ** will not be printed. This is done in two steps.\n    **  1. We scan the symbol table to find the bits that differ\n    **     in at least 2 addresses.\n    **  2. We choose one of the possible masks. There are 8 possible\n    **     masks for 32-bit integer, and 16 possible masks for 64-bit\n    **     integers.\n    */\n\n    /* Find the bits that are different. */\n    refAddr = (ptruint) Cudd_Regular(f[0]);\n    diff = 0;\n    gen = st_init_gen(visited);\n    if (gen == NULL) goto failure;\n    while (st_gen(gen, (void **) &scan, NULL)) {\n\tdiff |= refAddr ^ (ptruint) scan;\n    }\n    st_free_gen(gen); gen = NULL;\n\n    /* Choose the mask. */\n    for (i = 0; (unsigned) i < 8 * sizeof(ptruint); i += 4) {\n        mask = ((ptruint) 1 << i) - 1;\n\tif (diff <= mask) break;\n    }\n\n    /* Write the header and the global attributes. */\n    retval = fprintf(fp,\"digraph \\\"DD\\\" {\\n\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\n\t\"size = \\\"7.5,10\\\"\\ncenter = true;\\nedge [dir = none];\\n\");\n    if (retval == EOF) return(0);\n\n    /* Write the input name subgraph by scanning the support array. */\n    retval = fprintf(fp,\"{ node [shape = plaintext];\\n\");\n    if (retval == EOF) goto failure;\n    retval = fprintf(fp,\"  edge [style = invis];\\n\");\n    if (retval == EOF) goto failure;\n    /* We use a name (\"CONST NODES\") with an embedded blank, because\n    ** it is unlikely to appear as an input name.\n    */\n    retval = fprintf(fp,\"  \\\"CONST NODES\\\" [style = invis];\\n\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < nvars; i++) {\n\tif (sorted[dd->invperm[i]]) {\n\t    if (inames == NULL || inames[dd->invperm[i]] == NULL) {\n\t\tretval = fprintf(fp,\"\\\" %d \\\" -> \", dd->invperm[i]);\n\t    } else {\n\t\tretval = fprintf(fp,\"\\\" %s \\\" -> \", inames[dd->invperm[i]]);\n\t    }\n\t    if (retval == EOF) goto failure;\n\t}\n    }\n    retval = fprintf(fp,\"\\\"CONST NODES\\\"; \\n}\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Write the output node subgraph. */\n    retval = fprintf(fp,\"{ rank = same; node [shape = box]; edge [style = invis];\\n\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < n; i++) {\n\tif (onames == NULL) {\n\t    retval = fprintf(fp,\"\\\"F%d\\\"\", i);\n\t} else {\n\t    retval = fprintf(fp,\"\\\"  %s  \\\"\", onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n\tif (i == n - 1) {\n\t    retval = fprintf(fp,\"; }\\n\");\n\t} else {\n\t    retval = fprintf(fp,\" -> \");\n\t}\n\tif (retval == EOF) goto failure;\n    }\n\n    /* Write rank info: All nodes with the same index have the same rank. */\n    for (i = 0; i < nvars; i++) {\n\tif (sorted[dd->invperm[i]]) {\n\t    retval = fprintf(fp,\"{ rank = same; \");\n\t    if (retval == EOF) goto failure;\n\t    if (inames == NULL || inames[dd->invperm[i]] == NULL) {\n\t\tretval = fprintf(fp,\"\\\" %d \\\";\\n\", dd->invperm[i]);\n\t    } else {\n\t\tretval = fprintf(fp,\"\\\" %s \\\";\\n\", inames[dd->invperm[i]]);\n\t    }\n\t    if (retval == EOF) goto failure;\n\t    nodelist = dd->subtables[i].nodelist;\n\t    slots = dd->subtables[i].slots;\n\t    for (j = 0; j < slots; j++) {\n\t\tscan = nodelist[j];\n\t\twhile (scan != NULL) {\n\t\t    if (st_is_member(visited,scan)) {\n\t\t\tretval = fprintf(fp,\"\\\"%#\" PRIxPTR \"\\\";\\n\",\n\t\t\t    ((mask & (ptruint) scan) / sizeof(DdNode)));\n\t\t\tif (retval == EOF) goto failure;\n\t\t    }\n\t\t    scan = scan->next;\n\t\t}\n\t    }\n\t    retval = fprintf(fp,\"}\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n    }\n\n    /* All constants have the same rank. */\n    retval = fprintf(fp,\n\t\"{ rank = same; \\\"CONST NODES\\\";\\n{ node [shape = box]; \");\n    if (retval == EOF) goto failure;\n    nodelist = dd->constants.nodelist;\n    slots = dd->constants.slots;\n    for (j = 0; j < slots; j++) {\n\tscan = nodelist[j];\n\twhile (scan != NULL) {\n\t    if (st_is_member(visited,scan)) {\n\t\tif (scan != Cudd_ReadZero(dd)) {\n\t\tretval = fprintf(fp,\"\\\"%#\" PRIxPTR \"\\\";\\n\",\n\t\t    ((mask & (ptruint) scan) / sizeof(DdNode)));\n\t\tif (retval == EOF) goto failure;\n\t\t}\n\t    }\n\t    scan = scan->next;\n\t}\n    }\n    retval = fprintf(fp,\"}\\n}\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Write edge info. */\n    /* Edges from the output nodes. */\n    for (i = 0; i < n; i++) {\n\tif (onames == NULL) {\n\t    retval = fprintf(fp,\"\\\"F%d\\\"\", i);\n\t} else {\n\t    retval = fprintf(fp,\"\\\"  %s  \\\"\", onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n\t/* Account for the possible complement on the root. */\n\tif (Cudd_IsComplement(f[i])) {\n\t    retval = fprintf(fp,\" -> \\\"%#\" PRIxPTR \"\\\" [style = dashed];\\n\",\n\t\t((mask & (ptruint) f[i]) / sizeof(DdNode)));\n\t} else {\n\t    retval = fprintf(fp,\" -> \\\"%#\" PRIxPTR \"\\\" [style = solid];\\n\",\n\t\t((mask & (ptruint) f[i]) / sizeof(DdNode)));\n\t}\n\tif (retval == EOF) goto failure;\n    }\n\n    /* Edges from internal nodes. */\n    for (i = 0; i < nvars; i++) {\n\tif (sorted[dd->invperm[i]]) {\n\t    nodelist = dd->subtables[i].nodelist;\n\t    slots = dd->subtables[i].slots;\n\t    for (j = 0; j < slots; j++) {\n\t\tscan = nodelist[j];\n\t\twhile (scan != NULL) {\n\t\t    if (st_is_member(visited,scan)) {\n\t\t\t/* print label (blank) */\n\t\t\tretval = fprintf(fp,\n\t\t\t    \"\\\"%#\" PRIxPTR \"\\\" [label = \\\"\\\"];\\n\",\n\t\t\t    ((mask & (ptruint) scan) / sizeof(DdNode)));\n\t\t\tif (retval == EOF) goto failure;\n\t\t\tif (cuddT(scan) != Cudd_ReadZero(dd)) {\n\t\t\tretval = fprintf(fp,\n\t\t\t    \"\\\"%#\" PRIxPTR \"\\\" -> \\\"%#\" PRIxPTR \"\\\";\\n\",\n\t\t\t    ((mask & (ptruint) scan) / sizeof(DdNode)),\n\t\t\t    ((mask & (ptruint) cuddT(scan)) / sizeof(DdNode)));\n\t\t\tif (retval == EOF) goto failure;\n\t\t\t}\n\t\t\tif (cuddE(scan) != Cudd_ReadZero(dd)) {\n\t\t\tif (Cudd_IsComplement(cuddE(scan))) {\n\t\t\t    retval = fprintf(fp,\n\t\t\t\t\"\\\"%#\" PRIxPTR \"\\\" -> \\\"%#\" PRIxPTR\n                                             \"\\\" [style = dashed];\\n\",\n\t\t\t\t((mask & (ptruint) scan) / sizeof(DdNode)),\n\t\t\t\t((mask & (ptruint) cuddE(scan)) /\n\t\t\t\tsizeof(DdNode)));\n\t\t\t} else {\n\t\t\t    retval = fprintf(fp,\n\t\t\t\t\"\\\"%#\" PRIxPTR \"\\\" -> \\\"%#\" PRIxPTR\n                                             \"\\\" [style = dotted];\\n\",\n\t\t\t\t((mask & (ptruint) scan) / sizeof(DdNode)),\n\t\t\t\t((mask & (ptruint) cuddE(scan)) /\n\t\t\t\tsizeof(DdNode)));\n\t\t\t}\n\t\t\tif (retval == EOF) goto failure;\n\t\t\t}\n\t\t    }\n\t\t    scan = scan->next;\n\t\t}\n\t    }\n\t}\n    }\n\n    /* Write constant labels. */\n    nodelist = dd->constants.nodelist;\n    slots = dd->constants.slots;\n    for (j = 0; j < slots; j++) {\n\tscan = nodelist[j];\n\twhile (scan != NULL) {\n\t    if (st_is_member(visited,scan)) {\n\t\tif (scan != Cudd_ReadZero(dd)) {\n\t\tretval = fprintf(fp,\"\\\"%#\" PRIxPTR \"\\\" [label = \\\"%g\\\"];\\n\",\n\t\t    ((mask & (ptruint) scan) / sizeof(DdNode)), cuddV(scan));\n\t\tif (retval == EOF) goto failure;\n\t\t}\n\t    }\n\t    scan = scan->next;\n\t}\n    }\n\n    /* Write trailer and return. */\n    retval = fprintf(fp,\"}\\n\");\n    if (retval == EOF) goto failure;\n\n    st_free_table(visited);\n    FREE(sorted);\n    return(1);\n\n failure:\n    if (sorted != NULL) FREE(sorted);\n    if (support != NULL) Cudd_RecursiveDeref(dd,support);\n    if (visited != NULL) st_free_table(visited);\n    return(0);\n\n} /* end of Cudd_DumpDot */\n\n\n/**\n  @brief Writes a daVinci file representing the argument BDDs.\n\n  @details Writes a daVinci file representing the argument BDDs.\n  Cudd_DumpDaVinci does not close the file: This is the caller\n  responsibility. Cudd_DumpDaVinci uses a minimal unique subset of the\n  hexadecimal address of a node as name for it.  If the argument\n  inames is non-null, it is assumed to hold the pointers to the names\n  of the inputs. Similarly for onames.\n\n  @return 1 in case of success; 0 otherwise (e.g., out-of-memory or\n  file system full).\n\n  @sideeffect None\n\n  @see Cudd_DumpDot Cudd_PrintDebug Cudd_DumpBlif Cudd_DumpDDcal\n  Cudd_DumpFactoredForm\n\n*/\nint\nCudd_DumpDaVinci(\n  DdManager * dd /**< manager */,\n  int  n /**< number of output nodes to be dumped */,\n  DdNode ** f /**< array of output nodes to be dumped */,\n  char const * const * inames /**< array of input names (or NULL) */,\n  char const * const * onames /**< array of output names (or NULL) */,\n  FILE * fp /**< pointer to the dump file */)\n{\n    DdNode\t  *support = NULL;\n    DdNode\t  *scan;\n    st_table\t  *visited = NULL;\n    int\t\t  retval;\n    int\t\t  i;\n    st_generator  *gen;\n    ptruint       refAddr, diff, mask = 0;\n\n    /* Initialize symbol table for visited nodes. */\n    visited = st_init_table(st_ptrcmp, st_ptrhash);\n    if (visited == NULL) goto failure;\n\n    /* Collect all the nodes of this DD in the symbol table. */\n    for (i = 0; i < n; i++) {\n\tretval = cuddCollectNodes(Cudd_Regular(f[i]),visited);\n\tif (retval == 0) goto failure;\n    }\n\n    /* Find how many most significant hex digits are identical\n    ** in the addresses of all the nodes. Build a mask based\n    ** on this knowledge, so that digits that carry no information\n    ** will not be printed. This is done in two steps.\n    **  1. We scan the symbol table to find the bits that differ\n    **     in at least 2 addresses.\n    **  2. We choose one of the possible masks. There are 8 possible\n    **     masks for 32-bit integer, and 16 possible masks for 64-bit\n    **     integers.\n    */\n\n    /* Find the bits that are different. */\n    refAddr = (ptruint) Cudd_Regular(f[0]);\n    diff = 0;\n    gen = st_init_gen(visited);\n    while (st_gen(gen, (void **) &scan, NULL)) {\n\tdiff |= refAddr ^ (ptruint) scan;\n    }\n    st_free_gen(gen);\n\n    /* Choose the mask. */\n    for (i = 0; (unsigned) i < 8 * sizeof(ptruint); i += 4) {\n\tmask = ((ptruint) 1 << i) - 1;\n\tif (diff <= mask) break;\n    }\n    st_free_table(visited);\n\n    /* Initialize symbol table for visited nodes. */\n    visited = st_init_table(st_ptrcmp, st_ptrhash);\n    if (visited == NULL) goto failure;\n\n    retval = fprintf(fp, \"[\");\n    if (retval == EOF) goto failure;\n    /* Call the function that really gets the job done. */\n    for (i = 0; i < n; i++) {\n\tif (onames == NULL) {\n\t    retval = fprintf(fp,\n\t\t\t     \"l(\\\"f%d\\\",n(\\\"root\\\",[a(\\\"OBJECT\\\",\\\"f%d\\\")],\",\n\t\t\t     i,i);\n\t} else {\n\t    retval = fprintf(fp,\n\t\t\t     \"l(\\\"%s\\\",n(\\\"root\\\",[a(\\\"OBJECT\\\",\\\"%s\\\")],\",\n\t\t\t     onames[i], onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n\tretval = fprintf(fp, \"[e(\\\"edge\\\",[a(\\\"EDGECOLOR\\\",\\\"%s\\\"),a(\\\"_DIR\\\",\\\"none\\\")],\",\n\t\t\t Cudd_IsComplement(f[i]) ? \"red\" : \"blue\");\n\tif (retval == EOF) goto failure;\n\tretval = ddDoDumpDaVinci(dd,Cudd_Regular(f[i]),fp,visited,inames,mask);\n\tif (retval == 0) goto failure;\n\tretval = fprintf(fp, \")]))%s\", i == n-1 ? \"\" : \",\");\n\tif (retval == EOF) goto failure;\n    }\n\n    /* Write trailer and return. */\n    retval = fprintf(fp, \"]\\n\");\n    if (retval == EOF) goto failure;\n\n    st_free_table(visited);\n    return(1);\n\nfailure:\n    if (support != NULL) Cudd_RecursiveDeref(dd,support);\n    if (visited != NULL) st_free_table(visited);\n    return(0);\n\n} /* end of Cudd_DumpDaVinci */\n\n\n/**\n  @brief Writes a DDcal file representing the argument BDDs.\n\n  @details Writes a DDcal file representing the argument BDDs.\n  Cudd_DumpDDcal does not close the file: This is the caller\n  responsibility. Cudd_DumpDDcal uses a minimal unique subset of the\n  hexadecimal address of a node as name for it.  If the argument\n  inames is non-null, it is assumed to hold the pointers to the names\n  of the inputs. Similarly for onames.\n\n  @return 1 in case of success; 0 otherwise (e.g., out-of-memory or\n  file system full).\n\n  @sideeffect None\n\n  @see Cudd_DumpDot Cudd_PrintDebug Cudd_DumpBlif Cudd_DumpDaVinci\n  Cudd_DumpFactoredForm\n\n*/\nint\nCudd_DumpDDcal(\n  DdManager * dd /**< manager */,\n  int  n /**< number of output nodes to be dumped */,\n  DdNode ** f /**< array of output nodes to be dumped */,\n  char const * const * inames /**< array of input names (or NULL) */,\n  char const * const * onames /**< array of output names (or NULL) */,\n  FILE * fp /**< pointer to the dump file */)\n{\n    DdNode\t  *support = NULL;\n    DdNode\t  *scan;\n    int\t\t  *sorted = NULL;\n    int\t\t  nvars = dd->size;\n    st_table\t  *visited = NULL;\n    int\t\t  retval;\n    int\t\t  i;\n    st_generator  *gen;\n    ptruint       refAddr, diff, mask = 0;\n\n    /* Initialize symbol table for visited nodes. */\n    visited = st_init_table(st_ptrcmp, st_ptrhash);\n    if (visited == NULL) goto failure;\n\n    /* Collect all the nodes of this DD in the symbol table. */\n    for (i = 0; i < n; i++) {\n\tretval = cuddCollectNodes(Cudd_Regular(f[i]),visited);\n\tif (retval == 0) goto failure;\n    }\n\n    /* Find how many most significant hex digits are identical\n    ** in the addresses of all the nodes. Build a mask based\n    ** on this knowledge, so that digits that carry no information\n    ** will not be printed. This is done in two steps.\n    **  1. We scan the symbol table to find the bits that differ\n    **     in at least 2 addresses.\n    **  2. We choose one of the possible masks. There are 8 possible\n    **     masks for 32-bit integer, and 16 possible masks for 64-bit\n    **     integers.\n    */\n\n    /* Find the bits that are different. */\n    refAddr = (ptruint) Cudd_Regular(f[0]);\n    diff = 0;\n    gen = st_init_gen(visited);\n    while (st_gen(gen, (void **) &scan, NULL)) {\n\tdiff |= refAddr ^ (ptruint) scan;\n    }\n    st_free_gen(gen);\n\n    /* Choose the mask. */\n    for (i = 0; (unsigned) i < 8 * sizeof(ptruint); i += 4) {\n\tmask = ((ptruint) 1 << i) - 1;\n\tif (diff <= mask) break;\n    }\n    st_free_table(visited);\n\n    /* Build a bit array with the support of f. */\n    sorted = ALLOC(int,nvars);\n    if (sorted == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tgoto failure;\n    }\n    for (i = 0; i < nvars; i++) sorted[i] = 0;\n\n    /* Take the union of the supports of each output function. */\n    support = Cudd_VectorSupport(dd,f,n);\n    if (support == NULL) goto failure;\n    cuddRef(support);\n    scan = support;\n    while (!cuddIsConstant(scan)) {\n\tsorted[scan->index] = 1;\n\tscan = cuddT(scan);\n    }\n    Cudd_RecursiveDeref(dd,support);\n    support = NULL; /* so that we do not try to free it in case of failure */\n    for (i = 0; i < nvars; i++) {\n\tif (sorted[dd->invperm[i]]) {\n\t    if (inames == NULL || inames[dd->invperm[i]] == NULL) {\n\t\tretval = fprintf(fp,\"v%d\", dd->invperm[i]);\n\t    } else {\n\t\tretval = fprintf(fp,\"%s\", inames[dd->invperm[i]]);\n\t    }\n\t    if (retval == EOF) goto failure;\n\t}\n\tretval = fprintf(fp,\"%s\", i == nvars - 1 ? \"\\n\" : \" * \");\n\tif (retval == EOF) goto failure;\n    }\n    FREE(sorted);\n    sorted = NULL;\n\n    /* Initialize symbol table for visited nodes. */\n    visited = st_init_table(st_ptrcmp, st_ptrhash);\n    if (visited == NULL) goto failure;\n\n    /* Call the function that really gets the job done. */\n    for (i = 0; i < n; i++) {\n\tretval = ddDoDumpDDcal(dd,Cudd_Regular(f[i]),fp,visited,inames,mask);\n\tif (retval == 0) goto failure;\n\tif (onames == NULL) {\n\t    retval = fprintf(fp, \"f%d = \", i);\n\t} else {\n\t    retval = fprintf(fp, \"%s = \", onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n\tretval = fprintf(fp, \"n%#\" PRIxPTR \"%s\\n\",\n\t\t\t (((ptruint) f[i] & mask) / sizeof(DdNode)),\n\t\t\t Cudd_IsComplement(f[i]) ? \"'\" : \"\");\n\tif (retval == EOF) goto failure;\n    }\n\n    /* Write trailer and return. */\n    retval = fprintf(fp, \"[\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < n; i++) {\n\tif (onames == NULL) {\n\t    retval = fprintf(fp, \"f%d\", i);\n\t} else {\n\t    retval = fprintf(fp, \"%s\", onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n\tretval = fprintf(fp, \"%s\", i == n-1 ? \"\" : \" \");\n\tif (retval == EOF) goto failure;\n    }\n    retval = fprintf(fp, \"]\\n\");\n    if (retval == EOF) goto failure;\n\n    st_free_table(visited);\n    return(1);\n\nfailure:\n    if (sorted != NULL) FREE(sorted);\n    if (support != NULL) Cudd_RecursiveDeref(dd,support);\n    if (visited != NULL) st_free_table(visited);\n    return(0);\n\n} /* end of Cudd_DumpDDcal */\n\n\n/**\n  @brief Writes factored forms representing the argument BDDs.\n\n  @details Writes factored forms representing the argument BDDs.  The\n  format of the factored form is the one used in the genlib files for\n  technology mapping in sis.  Cudd_DumpFactoredForm does not close the\n  file: This is the caller responsibility. Caution must be exercised\n  because a factored form may be exponentially larger than the\n  argument %BDD.  If the argument inames is non-null, it is assumed to\n  hold the pointers to the names of the inputs. Similarly for onames.\n  If the number of output nodes is 0, it is interpreted as 1, but no\n  output name followed by equal sign is printed before the factored\n  form.\n\n  @return 1 in case of success; 0 otherwise (e.g., file system full).\n\n  @sideeffect None\n\n  @see Cudd_DumpDot Cudd_PrintDebug Cudd_DumpBlif Cudd_DumpDaVinci\n  Cudd_DumpDDcal\n\n*/\nint\nCudd_DumpFactoredForm(\n  DdManager * dd /**< manager */,\n  int  n /**< number of output nodes to be dumped */,\n  DdNode ** f /**< array of output nodes to be dumped */,\n  char const * const * inames /**< array of input names (or NULL) */,\n  char const * const * onames /**< array of output names (or NULL) */,\n  FILE * fp /**< pointer to the dump file */)\n{\n    int\t\tretval = 0;\n    int\t\ti;\n    int\t\tprintName = n != 0;\n\n    if (!printName) n = 1;\n\n    /* Call the function that really gets the job done. */\n    for (i = 0; i < n; i++) {\n        if (printName) {\n            if (onames == NULL) {\n\t\tretval = fprintf(fp, \"f%d = \", i);\n            } else {\n\t\tretval = fprintf(fp, \"%s = \", onames[i]);\n            }\n        }\n\tif (retval == EOF) return(0);\n\tif (f[i] == DD_ONE(dd)) {\n\t    retval = fprintf(fp, \"CONST1\");\n\t    if (retval == EOF) return(0);\n\t} else if (f[i] == Cudd_Not(DD_ONE(dd)) || f[i] == DD_ZERO(dd)) {\n\t    retval = fprintf(fp, \"CONST0\");\n\t    if (retval == EOF) return(0);\n\t} else {\n\t    retval = fprintf(fp, \"%s\", Cudd_IsComplement(f[i]) ? (Cudd_bddIsVar(dd, Cudd_Regular(f[i])) ? \"!\" : \"!(\") : \"\");\n\t    if (retval == EOF) return(0);\n\t    retval = ddDoDumpFactoredForm(dd,Cudd_Regular(f[i]),fp,inames);\n\t    if (retval == 0) return(0);\n\t    retval = fprintf(fp, \"%s\", Cudd_IsComplement(f[i]) && !Cudd_bddIsVar(dd, Cudd_Regular(f[i])) ? \")\" : \"\");\n\t    if (retval == EOF) return(0);\n\t}\n\tretval = fprintf(fp, \"%s\", i == n-1 ? \"\" : \"\\n\");\n\tif (retval == EOF) return(0);\n    }\n\n    return(1);\n\n} /* end of Cudd_DumpFactoredForm */\n\n\n/**\n  @brief Returns a string with the factored form of the argument BDDs\n\n  @details The factored form uses & for conjunction, | for disjunction\n  and ! for negation.  Caution must be exercised because a factored\n  form may be exponentially larger than the argument %BDD.  If the\n  argument inames is non-null, it is assumed to hold the pointers to\n  the names of the inputs.\n\n  @return a string in case of success; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_DumpDot Cudd_PrintDebug Cudd_DumpBlif Cudd_DumpDaVinci\n  Cudd_DumpDDcal Cudd_DumpFactoredForm\n\n*/\nchar *\nCudd_FactoredFormString(\n  DdManager *dd,\n  DdNode *f,\n  char const * const * inames)\n{\n    cstringstream stream = newStringStream();\n    int err, retval;\n    char * str;\n\n    if (!stream) {\n        return(0);\n    }\n    /* Call the function that really gets the job done. */\n    if (f == DD_ONE(dd)) {\n        err = appendStringStringStream(stream, \"true\");\n        if (err) {\n            deleteStringStream(stream);\n            return(0);\n        }\n    } else if (f == Cudd_Not(DD_ONE(dd)) || f == DD_ZERO(dd)) {\n        err = appendStringStringStream(stream, \"false\");\n        if (err) {\n            deleteStringStream(stream);\n            return(0);\n        }\n    } else {\n        err = appendStringStringStream(\n          stream, Cudd_IsComplement(f) ?\n          (Cudd_bddIsVar(dd, Cudd_Regular(f)) ? \"!\" : \"!(\") : \"\");\n        if (err) {\n            deleteStringStream(stream);\n            return(0);\n        }\n        retval = ddDoFactoredFormString(dd,Cudd_Regular(f),stream,inames);\n        if (retval == 0) {\n            deleteStringStream(stream);\n            return(0);\n        }\n        err = appendStringStringStream(\n          stream, Cudd_IsComplement(f) &&\n          !Cudd_bddIsVar(dd, Cudd_Regular(f)) ? \")\" : \"\");\n        if (err) {\n            deleteStringStream(stream);\n            return(0);\n        }\n    }\n    str = stringFromStringStream(stream);\n    deleteStringStream(stream);\n    return(str);\n\n} /* end of Cudd_FactoredFormString */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_DumpBlif.\n\n  @details Traverses the %BDD f and writes a multiplexer-network\n  description to the file pointed by fp in blif format. f is assumed\n  to be a regular pointer and ddDoDumpBlif guarantees this assumption\n  in the recursive calls.\n\n  @sideeffect None\n\n*/\nstatic int\nddDoDumpBlif(\n  DdManager * dd,\n  DdNode * f,\n  FILE * fp,\n  st_table * visited,\n  char const * const * names,\n  int mv)\n{\n    DdNode\t*T, *E;\n    int\t\tretval;\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsComplement(f));\n#endif\n\n    /* If already visited, nothing to do. */\n    if (st_is_member(visited, f) == 1)\n\treturn(1);\n\n    /* Check for abnormal condition that should never happen. */\n    if (f == NULL)\n\treturn(0);\n\n    /* Mark node as visited. */\n    if (st_insert(visited, f, NULL) == ST_OUT_OF_MEM)\n\treturn(0);\n\n    /* Check for special case: If constant node, generate constant 1. */\n    if (f == DD_ONE(dd)) {\n\tretval = fprintf(fp, \".names %\" PRIxPTR \"\\n1\\n\",(ptruint) f / (ptruint) sizeof(DdNode));\n\tif (retval == EOF) {\n\t    return(0);\n\t} else {\n\t    return(1);\n\t}\n    }\n\n    /* Check whether this is an ADD. We deal with 0-1 ADDs, but not\n    ** with the general case.\n    */\n    if (f == DD_ZERO(dd)) {\n\tretval = fprintf(fp, \".names %\" PRIxPTR \"\\n%s\",\n\t\t\t (ptruint) f / (ptruint) sizeof(DdNode),\n\t\t\t mv ? \"0\\n\" : \"\");\n\tif (retval == EOF) {\n\t    return(0);\n\t} else {\n\t    return(1);\n\t}\n    }\n    if (cuddIsConstant(f))\n\treturn(0);\n\n    /* Recursive calls. */\n    T = cuddT(f);\n    retval = ddDoDumpBlif(dd,T,fp,visited,names,mv);\n    if (retval != 1) return(retval);\n    E = Cudd_Regular(cuddE(f));\n    retval = ddDoDumpBlif(dd,E,fp,visited,names,mv);\n    if (retval != 1) return(retval);\n\n    /* Write multiplexer taking complement arc into account. */\n    if (names != NULL) {\n\tretval = fprintf(fp,\".names %s\", names[f->index]);\n    } else {\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n\tretval = fprintf(fp,\".names %u\", f->index);\n#else\n\tretval = fprintf(fp,\".names %hu\", f->index);\n#endif\n    }\n    if (retval == EOF)\n\treturn(0);\n\n    if (mv) {\n\tif (Cudd_IsComplement(cuddE(f))) {\n\t    retval = fprintf(fp,\" %\" PRIxPTR \" %\" PRIxPTR \" %\" PRIxPTR \"\\n.def 0\\n1 1 - 1\\n0 - 0 1\\n\",\n\t\t(ptruint) T / (ptruint) sizeof(DdNode),\n\t\t(ptruint) E / (ptruint) sizeof(DdNode),\n\t\t(ptruint) f / (ptruint) sizeof(DdNode));\n\t} else {\n\t    retval = fprintf(fp,\" %\" PRIxPTR \" %\" PRIxPTR \" %\" PRIxPTR \"\\n.def 0\\n1 1 - 1\\n0 - 1 1\\n\",\n\t\t(ptruint) T / (ptruint) sizeof(DdNode),\n\t\t(ptruint) E / (ptruint) sizeof(DdNode),\n\t\t(ptruint) f / (ptruint) sizeof(DdNode));\n\t}\n    } else {\n\tif (Cudd_IsComplement(cuddE(f))) {\n\t    retval = fprintf(fp,\" %\" PRIxPTR \" %\" PRIxPTR \" %\" PRIxPTR \"\\n11- 1\\n0-0 1\\n\",\n\t\t(ptruint) T / (ptruint) sizeof(DdNode),\n\t\t(ptruint) E / (ptruint) sizeof(DdNode),\n\t\t(ptruint) f / (ptruint) sizeof(DdNode));\n\t} else {\n\t    retval = fprintf(fp,\" %\" PRIxPTR \" %\" PRIxPTR \" %\" PRIxPTR \"\\n11- 1\\n0-1 1\\n\",\n\t\t(ptruint) T / (ptruint) sizeof(DdNode),\n\t\t(ptruint) E / (ptruint) sizeof(DdNode),\n\t\t(ptruint) f / (ptruint) sizeof(DdNode));\n\t}\n    }\n    if (retval == EOF) {\n\treturn(0);\n    } else {\n\treturn(1);\n    }\n\n} /* end of ddDoDumpBlif */\n\n\n/**\n  @brief Performs the recursive step of Cudd_DumpDaVinci.\n\n  @details Traverses the %BDD f and writes a term expression to the\n  file pointed by fp in daVinci format. f is assumed to be a regular\n  pointer and ddDoDumpDaVinci guarantees this assumption in the\n  recursive calls.\n\n  @sideeffect None\n\n*/\nstatic int\nddDoDumpDaVinci(\n  DdManager * dd,\n  DdNode * f,\n  FILE * fp,\n  st_table * visited,\n  char const * const * names,\n  ptruint mask)\n{\n    DdNode  *T, *E;\n    int\t    retval;\n    ptruint id;\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsComplement(f));\n#endif\n\n    id = ((ptruint) f & mask) / sizeof(DdNode);\n\n    /* If already visited, insert a reference. */\n    if (st_is_member(visited, f) == 1) {\n\tretval = fprintf(fp,\"r(\\\"%#\" PRIxPTR \"\\\")\", id);\n\tif (retval == EOF) {\n\t    return(0);\n\t} else {\n\t    return(1);\n\t}\n    }\n\n    /* Check for abnormal condition that should never happen. */\n    if (f == NULL)\n\treturn(0);\n\n    /* Mark node as visited. */\n    if (st_insert(visited, f, NULL) == ST_OUT_OF_MEM)\n\treturn(0);\n\n    /* Check for special case: If constant node, generate constant 1. */\n    if (Cudd_IsConstantInt(f)) {\n\tretval = fprintf(fp,\n\t\t\t \"l(\\\"%#\" PRIxPTR\n                         \"\\\",n(\\\"constant\\\",[a(\\\"OBJECT\\\",\\\"%g\\\")],[]))\",\n\t\t\t id, cuddV(f));\n\tif (retval == EOF) {\n\t    return(0);\n\t} else {\n\t    return(1);\n\t}\n    }\n\n    /* Recursive calls. */\n    if (names != NULL) {\n\tretval = fprintf(fp, \"l(\\\"%#\" PRIxPTR\n                         \"\\\",n(\\\"internal\\\",[a(\\\"OBJECT\\\",\\\"%s\\\"),\",\n\t\t\t id, names[f->index]);\n    } else {\n#if SIZEOF_VOID_P == 8\n\tretval = fprintf(fp, \"l(\\\"%#\" PRIxPTR\n                         \"\\\",n(\\\"internal\\\",[a(\\\"OBJECT\\\",\\\"%u\\\"),\",\n\t\t\t id, f->index);\n#else\n\tretval = fprintf(fp, \"l(\\\"%#\"PRIxPTR\n                         \"\\\",n(\\\"internal\\\",[a(\\\"OBJECT\\\",\\\"%hu\\\"),\",\n\t\t\t id, f->index);\n#endif\n    }\n    if (retval == EOF) return(0);\n    retval = fprintf(fp, \"a(\\\"_GO\\\",\\\"ellipse\\\")],[e(\\\"then\\\",[a(\\\"EDGECOLOR\\\",\\\"blue\\\"),a(\\\"_DIR\\\",\\\"none\\\")],\");\n    if (retval == EOF) return(0);\n    T = cuddT(f);\n    retval = ddDoDumpDaVinci(dd,T,fp,visited,names,mask);\n    if (retval != 1) return(retval);\n    retval = fprintf(fp, \"),e(\\\"else\\\",[a(\\\"EDGECOLOR\\\",\\\"%s\\\"),a(\\\"_DIR\\\",\\\"none\\\")],\",\n\t\t     Cudd_IsComplement(cuddE(f)) ? \"red\" : \"green\");\n    if (retval == EOF) return(0);\n    E = Cudd_Regular(cuddE(f));\n    retval = ddDoDumpDaVinci(dd,E,fp,visited,names,mask);\n    if (retval != 1) return(retval);\n\n    retval = fprintf(fp,\")]))\");\n    if (retval == EOF) {\n\treturn(0);\n    } else {\n\treturn(1);\n    }\n\n} /* end of ddDoDumpDaVinci */\n\n\n/**\n  @brief Performs the recursive step of Cudd_DumpDDcal.\n\n  @details Traverses the %BDD f and writes a line for each node to the\n  file pointed by fp in DDcal format. f is assumed to be a regular\n  pointer and ddDoDumpDDcal guarantees this assumption in the\n  recursive calls.\n\n  @sideeffect None\n\n*/\nstatic int\nddDoDumpDDcal(\n  DdManager * dd,\n  DdNode * f,\n  FILE * fp,\n  st_table * visited,\n  char const * const * names,\n  ptruint mask)\n{\n    DdNode  *T, *E;\n    int\t    retval;\n    ptruint id, idT, idE;\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsComplement(f));\n#endif\n\n    id = ((ptruint) f & mask) / sizeof(DdNode);\n\n    /* If already visited, do nothing. */\n    if (st_is_member(visited, f) == 1) {\n\treturn(1);\n    }\n\n    /* Check for abnormal condition that should never happen. */\n    if (f == NULL)\n\treturn(0);\n\n    /* Mark node as visited. */\n    if (st_insert(visited, f, NULL) == ST_OUT_OF_MEM)\n\treturn(0);\n\n    /* Check for special case: If constant node, assign constant. */\n    if (Cudd_IsConstantInt(f)) {\n\tif (f != DD_ONE(dd) && f != DD_ZERO(dd))\n\t    return(0);\n\tretval = fprintf(fp, \"n%#\" PRIxPTR\" = %g\\n\", id, cuddV(f));\n\tif (retval == EOF) {\n\t    return(0);\n\t} else {\n\t    return(1);\n\t}\n    }\n\n    /* Recursive calls. */\n    T = cuddT(f);\n    retval = ddDoDumpDDcal(dd,T,fp,visited,names,mask);\n    if (retval != 1) return(retval);\n    E = Cudd_Regular(cuddE(f));\n    retval = ddDoDumpDDcal(dd,E,fp,visited,names,mask);\n    if (retval != 1) return(retval);\n    idT = ((ptruint) T & mask) / sizeof(DdNode);\n    idE = ((ptruint) E & mask) / sizeof(DdNode);\n    if (names != NULL) {\n\tretval = fprintf(fp, \"n%#\" PRIxPTR \" = %s * n%#\" PRIxPTR\n                         \" + %s' * n%#\" PRIxPTR \"%s\\n\",\n\t\t\t id, names[f->index], idT, names[f->index],\n\t\t\t idE, Cudd_IsComplement(cuddE(f)) ? \"'\" : \"\");\n    } else {\n#if SIZEOF_VOID_P == 8\n\tretval = fprintf(fp, \"n%#\" PRIxPTR \" = v%u * n%#\" PRIxPTR\n                         \" + v%u' * n%#\" PRIxPTR \"%s\\n\",\n\t\t\t id, f->index, idT, f->index,\n\t\t\t idE, Cudd_IsComplement(cuddE(f)) ? \"'\" : \"\");\n#else\n\tretval = fprintf(fp, \"n%#\"PRIxPTR\" = v%hu * n%#\"PRIxPTR\n                         \" + v%hu' * n%#\"PRIxPTR\"%s\\n\",\n\t\t\t id, f->index, idT, f->index,\n\t\t\t idE, Cudd_IsComplement(cuddE(f)) ? \"'\" : \"\");\n#endif\n    }\n    if (retval == EOF) {\n\treturn(0);\n    } else {\n\treturn(1);\n    }\n\n} /* end of ddDoDumpDDcal */\n\n\n/**\n  @brief Performs the recursive step of Cudd_DumpFactoredForm.\n\n  @details Traverses the %BDD f and writes a factored form for each\n  node to the file pointed by fp in terms of the factored forms of the\n  children. Constants are propagated, and absorption is applied.  f is\n  assumed to be a regular pointer and ddDoDumpFActoredForm guarantees\n  this assumption in the recursive calls.\n\n  @sideeffect None\n\n  @see Cudd_DumpFactoredForm\n\n*/\nstatic int\nddDoDumpFactoredForm(\n  DdManager * dd,\n  DdNode * f,\n  FILE * fp,\n  char const * const * names)\n{\n    DdNode\t*T, *E;\n    int\t\tretval;\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsComplement(f));\n    assert(!cuddIsConstant(f));\n#endif\n\n    /* Check for abnormal condition that should never happen. */\n    if (f == NULL)\n\treturn(0);\n\n    /* Recursive calls. */\n    T = cuddT(f);\n    E = cuddE(f);\n    if (T != DD_ZERO(dd)) {\n\tif (E != DD_ONE(dd)) {\n\t    if (names != NULL) {\n\t\tretval = fprintf(fp, \"%s\", names[f->index]);\n\t    } else {\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n\t\tretval = fprintf(fp, \"x%u\", f->index);\n#else\n\t\tretval = fprintf(fp, \"x%hu\", f->index);\n#endif\n\t    }\n\t    if (retval == EOF) return(0);\n\t}\n\tif (T != DD_ONE(dd)) {\n            //\t    retval = fprintf(fp, \"%s(\", E != DD_ONE(dd) ? \" * \" : \"\");\n            retval = fprintf(fp, \"%s%s\", E != DD_ONE(dd) ? \" * \" : \"\", Cudd_bddIsVar(dd, T) ? \"\" : \"(\");\n\t    if (retval == EOF) return(0);\n\t    retval = ddDoDumpFactoredForm(dd,T,fp,names);\n\t    if (retval != 1) return(retval);\n\t    retval = fprintf(fp, \"%s\", Cudd_bddIsVar(dd, T) ? \"\" : \")\");\n\t    if (retval == EOF) return(0);\n\t}\n\tif (E == Cudd_Not(DD_ONE(dd)) || E == DD_ZERO(dd)) return(1);\n\tretval = fprintf(fp, \" + \");\n\tif (retval == EOF) return(0);\n    }\n    E = Cudd_Regular(E);\n    if (T != DD_ONE(dd)) {\n\tif (names != NULL) {\n\t    retval = fprintf(fp, \"!%s\", names[f->index]);\n\t} else {\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n\t    retval = fprintf(fp, \"!x%u\", f->index);\n#else\n\t    retval = fprintf(fp, \"!x%hu\", f->index);\n#endif\n\t}\n\tif (retval == EOF) return(0);\n    }\n    if (E != DD_ONE(dd)) {\n\tretval = fprintf(fp, \"%s%s%s\", T != DD_ONE(dd) ? \" * \" : \"\",\n\t\t\t E != cuddE(f) ? \"!\" : \"\", Cudd_bddIsVar(dd, E) ? \"\" : \"(\");\n\tif (retval == EOF) return(0);\n\tretval = ddDoDumpFactoredForm(dd,E,fp,names);\n\tif (retval != 1) return(retval);\n\tretval = fprintf(fp, \"%s\", Cudd_bddIsVar(dd, E) ? \"\" : \"(\");\n\tif (retval == EOF) return(0);\n    }\n    return(1);\n\n} /* end of ddDoDumpFactoredForm */\n\n\n/**\n  @brief Performs the recursive step of Cudd_DumpFactoredForm.\n\n  @details Traverses the %BDD f and writes a factored form for each\n  node to the file pointed by fp in terms of the factored forms of the\n  children. Constants are propagated, and absorption is applied.  f is\n  assumed to be a regular pointer and ddDoDumpFActoredForm guarantees\n  this assumption in the recursive calls.\n\n  @sideeffect None\n\n  @see Cudd_DumpFactoredForm\n\n*/\nstatic int\nddDoFactoredFormString(\n  DdManager * dd,\n  DdNode * f,\n  cstringstream stream,\n  char const * const * names)\n{\n    DdNode\t*T, *E;\n    int\t\tretval, err;\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsComplement(f));\n    assert(!cuddIsConstant(f));\n#endif\n\n    /* Check for abnormal condition that should never happen. */\n    if (f == NULL)\n\treturn(0);\n\n    /* Recursive calls. */\n    T = cuddT(f);\n    E = cuddE(f);\n    if (T != DD_ZERO(dd)) {\n\tif (E != DD_ONE(dd)) {\n\t    if (names != NULL) {\n                err = appendStringStringStream(stream, names[f->index]);\n\t    } else {\n                err = appendCharStringStream(stream, 'x');\n                if (err) return(0);\n                err = appendUnsignedStringStream(stream, (unsigned) f->index);\n\t    }\n\t    if (err) return(0);\n\t}\n\tif (T != DD_ONE(dd)) {\n            err = appendStringStringStream(stream, E != DD_ONE(dd) ? \" & \" : \"\");\n            if (err) return(0);\n            err = appendStringStringStream(stream, Cudd_bddIsVar(dd, T) ? \"\" : \"(\");\n\t    if (err) return(0);\n\t    retval = ddDoFactoredFormString(dd,T,stream,names);\n\t    if (retval != 1) return(retval);\n            err = appendStringStringStream(stream, Cudd_bddIsVar(dd, T) ? \"\" : \")\");\n\t    if (err) return(0);\n\t}\n\tif (E == Cudd_Not(DD_ONE(dd)) || E == DD_ZERO(dd)) return(1);\n        err = appendStringStringStream(stream,  \" | \");\n\tif (err) return(0);\n    }\n    E = Cudd_Regular(E);\n    if (T != DD_ONE(dd)) {\n        err = appendCharStringStream(stream, '!');\n        if (err) return(0);\n\tif (names != NULL) {\n            err = appendStringStringStream(stream, names[f->index]);\n\t} else {\n            err = appendCharStringStream(stream, 'x');\n            if (err) return(0);\n            err = appendUnsignedStringStream(stream, (unsigned) f->index);\n\t}\n\tif (err) return(0);\n    }\n    if (E != DD_ONE(dd)) {\n        err = appendStringStringStream(stream, T != DD_ONE(dd) ? \" & \" : \"\");\n        if (err) return(0);\n        err = appendStringStringStream(stream, E != cuddE(f) ? \"!\" : \"\");\n        if (err) return(0);\n        err = appendStringStringStream(stream, Cudd_bddIsVar(dd, E) ? \"\" : \"(\");\n        if (err) return(0);\n\tretval = ddDoFactoredFormString(dd,E,stream,names);\n\tif (retval != 1) return(retval);\n        err = appendStringStringStream(stream, Cudd_bddIsVar(dd, E) ? \"\" : \")\");\n\tif (err) return(0);\n    }\n    return(1);\n\n} /* end of ddDoFactoredFormString */\n"
  },
  {
    "path": "cudd/cudd/cuddGenCof.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Generalized cofactors for BDDs and ADDs.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* Codes for edge markings in Cudd_bddLICompaction.  The codes are defined\n** so that they can be bitwise ORed to implement the code priority scheme.\n*/\n#define DD_LIC_DC 0\n#define DD_LIC_1  1\n#define DD_LIC_0  2\n#define DD_LIC_NL 3\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/** Key for the cache used in the edge marking phase. */\ntypedef struct MarkCacheKey {\n    DdNode *f;\n    DdNode *c;\n} MarkCacheKey;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int cuddBddConstrainDecomp (DdManager *dd, DdNode *f, DdNode **decomp);\nstatic DdNode * cuddBddCharToVect (DdManager *dd, DdNode *f, DdNode *x);\nstatic int cuddBddLICMarkEdges (DdManager *dd, DdNode *f, DdNode *c, st_table *table, st_table *cache);\nstatic DdNode * cuddBddLICBuildResult (DdManager *dd, DdNode *f, st_table *cache, st_table *table);\nstatic int MarkCacheHash (void const *ptr, int modulus);\nstatic int MarkCacheCompare (const void *ptr1, const void *ptr2);\nstatic enum st_retval MarkCacheCleanUp (void *key, void *value, void *arg);\nstatic DdNode * cuddBddSqueeze (DdManager *dd, DdNode *l, DdNode *u);\nstatic DdNode * cuddBddInterpolate (DdManager * dd, DdNode * l, DdNode * u);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Computes f constrain c.\n\n  @details Computes f constrain c (f @ c).\n  Uses a canonical form: (f' @ c) = (f @ c)'.  (Note: this is not true\n  for c.)  List of special cases:\n    <ul>\n    <li> f @ 0 = 0\n    <li> f @ 1 = f\n    <li> 0 @ c = 0\n    <li> 1 @ c = 1\n    <li> f @ f = 1\n    <li> f @ f'= 0\n    </ul>\n  Note that if F=(f1,...,fn) and reordering takes place while computing F @ c,\n  then the image restriction property (Img(F,c) = Img(F @ c)) is lost.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddRestrict Cudd_addConstrain\n\n*/\nDdNode *\nCudd_bddConstrain(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddConstrainRecur(dd,f,c);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddConstrain */\n\n\n/**\n  @brief %BDD restrict according to Coudert and Madre's algorithm\n  (ICCAD90).\n\n  @details If application of restrict results in a %BDD larger than the\n  input %BDD, the input %BDD is returned.\n\n  @return the restricted %BDD if successful; otherwise NULL.\n\n  @sideeffect None\n\n  @see Cudd_bddConstrain Cudd_addRestrict\n\n*/\nDdNode *\nCudd_bddRestrict(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode *suppF, *suppC, *commonSupport;\n    DdNode *cplus, *res;\n    int retval;\n    int sizeF, sizeRes;\n\n    /* Check terminal cases here to avoid computing supports in trivial cases.\n    ** This also allows us notto check later for the case c == 0, in which\n    ** there is no common support. */\n    if (c == Cudd_Not(DD_ONE(dd))) return(Cudd_Not(DD_ONE(dd)));\n    if (Cudd_IsConstantInt(f)) return(f);\n    if (f == c) return(DD_ONE(dd));\n    if (f == Cudd_Not(c)) return(Cudd_Not(DD_ONE(dd)));\n\n    /* Check if supports intersect. */\n    retval = Cudd_ClassifySupport(dd,f,c,&commonSupport,&suppF,&suppC);\n    if (retval == 0) {\n\treturn(NULL);\n    }\n    cuddRef(commonSupport); cuddRef(suppF); cuddRef(suppC);\n    Cudd_IterDerefBdd(dd,suppF);\n\n    if (commonSupport == DD_ONE(dd)) {\n\tCudd_IterDerefBdd(dd,commonSupport);\n\tCudd_IterDerefBdd(dd,suppC);\n\treturn(f);\n    }\n    Cudd_IterDerefBdd(dd,commonSupport);\n\n    /* Abstract from c the variables that do not appear in f. */\n    cplus = Cudd_bddExistAbstract(dd, c, suppC);\n    if (cplus == NULL) {\n\tCudd_IterDerefBdd(dd,suppC);\n\treturn(NULL);\n    }\n    cuddRef(cplus);\n    Cudd_IterDerefBdd(dd,suppC);\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddRestrictRecur(dd, f, cplus);\n    } while (dd->reordered == 1);\n    if (res == NULL) {\n\tCudd_IterDerefBdd(dd,cplus);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n          dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_IterDerefBdd(dd,cplus);\n    /* Make restric safe by returning the smaller of the input and the\n    ** result. */\n    sizeF = Cudd_DagSize(f);\n    sizeRes = Cudd_DagSize(res);\n    if (sizeF <= sizeRes) {\n\tCudd_IterDerefBdd(dd, res);\n\treturn(f);\n    } else {\n\tcuddDeref(res);\n\treturn(res);\n    }\n\n} /* end of Cudd_bddRestrict */\n\n\n/**\n  @brief Computes f non-polluting-and g.\n\n  @details The non-polluting AND of f and g is a hybrid of AND and\n  Restrict.  From Restrict, this operation takes the idea of\n  existentially quantifying the top variable of the second operand if\n  it does not appear in the first.  Therefore, the variables that\n  appear in the result also appear in f.  For the rest, the function\n  behaves like AND.  Since the two operands play different roles,\n  non-polluting AND is not commutative.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddConstrain Cudd_bddRestrict\n\n*/\nDdNode *\nCudd_bddNPAnd(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddNPAndRecur(dd,f,g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddNPAnd */\n\n\n/**\n  @brief Computes f constrain c for ADDs.\n\n  @details Computes f constrain c (f @ c), for f an %ADD and c a 0-1\n  %ADD.  List of special cases:\n  <ul>\n  <li> F @ 0 = 0\n  <li> F @ 1 = F\n  <li> 0 @ c = 0\n  <li> 1 @ c = 1\n  <li> F @ F = 1\n  </ul>\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddConstrain\n\n*/\nDdNode *\nCudd_addConstrain(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddConstrainRecur(dd,f,c);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addConstrain */\n\n\n/**\n  @brief %BDD conjunctive decomposition as in McMillan's CAV96 paper.\n\n  @details The decomposition is canonical only for a given variable\n  order. If canonicity is required, variable ordering must be disabled\n  after the decomposition has been computed.  The components of the\n  solution have their reference counts already incremented (unlike the\n  results of most other functions in the package).\n\n  @return an array with one entry for each %BDD variable in the manager\n  if successful; otherwise NULL.\n\n  @sideeffect None\n\n  @see Cudd_bddConstrain Cudd_bddExistAbstract\n\n*/\nDdNode **\nCudd_bddConstrainDecomp(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode **decomp;\n    int res;\n    int i;\n\n    /* Create an initialize decomposition array. */\n    decomp = ALLOC(DdNode *,dd->size);\n    if (decomp == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < dd->size; i++) {\n\tdecomp[i] = NULL;\n    }\n    do {\n\tdd->reordered = 0;\n\t/* Clean up the decomposition array in case reordering took place. */\n\tfor (i = 0; i < dd->size; i++) {\n\t    if (decomp[i] != NULL) {\n\t\tCudd_IterDerefBdd(dd, decomp[i]);\n\t\tdecomp[i] = NULL;\n\t    }\n\t}\n\tres = cuddBddConstrainDecomp(dd,f,decomp);\n    } while (dd->reordered == 1);\n    if (res == 0) {\n\tFREE(decomp);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n          dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    /* Missing components are constant ones. */\n    for (i = 0; i < dd->size; i++) {\n\tif (decomp[i] == NULL) {\n\t    decomp[i] = DD_ONE(dd);\n\t    cuddRef(decomp[i]);\n\t}\n    }\n    return(decomp);\n\n} /* end of Cudd_bddConstrainDecomp */\n\n\n/**\n  @brief %ADD restrict according to Coudert and Madre's algorithm\n  (ICCAD90).\n\n  @details If application of restrict results in an %ADD larger than\n  the input %ADD, the input %ADD is returned.\n\n  @return the restricted %ADD if successful; otherwise NULL.\n\n  @sideeffect None\n\n  @see Cudd_addConstrain Cudd_bddRestrict\n\n*/\nDdNode *\nCudd_addRestrict(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode *supp_f, *supp_c;\n    DdNode *res, *commonSupport;\n    int intersection;\n    int sizeF, sizeRes;\n\n    /* Check if supports intersect. */\n    supp_f = Cudd_Support(dd, f);\n    if (supp_f == NULL) {\n\treturn(NULL);\n    }\n    cuddRef(supp_f);\n    supp_c = Cudd_Support(dd, c);\n    if (supp_c == NULL) {\n\tCudd_RecursiveDeref(dd,supp_f);\n\treturn(NULL);\n    }\n    cuddRef(supp_c);\n    commonSupport = Cudd_bddLiteralSetIntersection(dd, supp_f, supp_c);\n    if (commonSupport == NULL) {\n\tCudd_RecursiveDeref(dd,supp_f);\n\tCudd_RecursiveDeref(dd,supp_c);\n\treturn(NULL);\n    }\n    cuddRef(commonSupport);\n    Cudd_RecursiveDeref(dd,supp_f);\n    Cudd_RecursiveDeref(dd,supp_c);\n    intersection = commonSupport != DD_ONE(dd);\n    Cudd_RecursiveDeref(dd,commonSupport);\n\n    if (intersection) {\n\tdo {\n\t    dd->reordered = 0;\n\t    res = cuddAddRestrictRecur(dd, f, c);\n\t} while (dd->reordered == 1);\n        if (res == 0) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(f);\n        }\n\tsizeF = Cudd_DagSize(f);\n\tsizeRes = Cudd_DagSize(res);\n\tif (sizeF <= sizeRes) {\n\t    cuddRef(res);\n\t    Cudd_RecursiveDeref(dd, res);\n\t    return(f);\n\t} else {\n\t    return(res);\n\t}\n    } else {\n\treturn(f);\n    }\n\n} /* end of Cudd_addRestrict */\n\n\n/**\n  @brief Computes a vector of BDDs whose image equals a non-zero function.\n\n  @details \n  The result depends on the variable order. The i-th component of the vector\n  depends only on the first i variables in the order.  Each %BDD in the vector\n  is not larger than the %BDD of the given characteristic function.  This\n  function is based on the description of char-to-vect in \"Verification of\n  Sequential Machines Using Boolean Functional Vectors\" by O. Coudert, C.\n  Berthet and J. C. Madre.\n\n  @return a pointer to an array containing the result if successful;\n  NULL otherwise.  The size of the array equals the number of\n  variables in the manager. The components of the solution have their\n  reference counts already incremented (unlike the results of most\n  other functions in the package).\n\n  @sideeffect None\n\n  @see Cudd_bddConstrain\n\n*/\nDdNode **\nCudd_bddCharToVect(\n  DdManager * dd,\n  DdNode * f)\n{\n    int i, j;\n    DdNode **vect;\n    DdNode *res = NULL;\n\n    if (f == Cudd_Not(DD_ONE(dd))) return(NULL);\n\n    vect = ALLOC(DdNode *, dd->size);\n    if (vect == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    do {\n\tdd->reordered = 0;\n\tfor (i = 0; i < dd->size; i++) {\n\t    res = cuddBddCharToVect(dd,f,dd->vars[dd->invperm[i]]);\n\t    if (res == NULL) {\n\t\t/* Clean up the vector array in case reordering took place. */\n\t\tfor (j = 0; j < i; j++) {\n\t\t    Cudd_IterDerefBdd(dd, vect[dd->invperm[j]]);\n\t\t}\n\t\tbreak;\n\t    }\n\t    cuddRef(res);\n\t    vect[dd->invperm[i]] = res;\n\t}\n    } while (dd->reordered == 1);\n    if (res == NULL) {\n\tFREE(vect);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    return(vect);\n\n} /* end of Cudd_bddCharToVect */\n\n\n/**\n  @brief Performs safe minimization of a %BDD.\n\n  @details Given the %BDD `f` of a function to be minimized and a %BDD\n  `c` representing the care set, Cudd_bddLICompaction produces the\n  %BDD of a function that agrees with `f` wherever `c` is 1.  Safe\n  minimization means that the size of the result is guaranteed not to\n  exceed the size of `f`. This function is based on the DAC97 paper by\n  Hong et al..\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddRestrict\n\n*/\nDdNode *\nCudd_bddLICompaction(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be minimized */,\n  DdNode * c /**< constraint (care set) */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddLICompaction(dd,f,c);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddLICompaction */\n\n\n/**\n  @brief Finds a small %BDD in a function interval.\n\n  @details Given BDDs `l` and `u`, representing the lower bound and\n  upper bound of a function interval, Cudd_bddSqueeze produces the\n  %BDD of a function within the interval with a small %BDD.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddRestrict Cudd_bddLICompaction\n\n*/\nDdNode *\nCudd_bddSqueeze(\n  DdManager * dd /**< manager */,\n  DdNode * l /**< lower bound */,\n  DdNode * u /**< upper bound */)\n{\n    DdNode *res;\n    int sizeRes, sizeL, sizeU;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddSqueeze(dd,l,u);\n    } while (dd->reordered == 1);\n    if (res == NULL) {\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n        return(NULL);\n    }\n    /* We now compare the result with the bounds and return the smallest.\n    ** We first compare to u, so that in case l == 0 and u == 1, we return\n    ** 0 as in other minimization algorithms. */\n    sizeRes = Cudd_DagSize(res);\n    sizeU = Cudd_DagSize(u);\n    if (sizeU <= sizeRes) {\n\tcuddRef(res);\n\tCudd_IterDerefBdd(dd,res);\n\tres = u;\n\tsizeRes = sizeU;\n    }\n    sizeL = Cudd_DagSize(l);\n    if (sizeL <= sizeRes) {\n\tcuddRef(res);\n\tCudd_IterDerefBdd(dd,res);\n\tres = l;\n    }\n    return(res);\n\n} /* end of Cudd_bddSqueeze */\n\n\n/**\n  @brief Finds an interpolant of two functions.\n\n  @details Given BDDs `l` and `u`, representing the lower bound and\n  upper bound of a function interval, Cudd_bddInterpolate produces the\n  %BDD of a function within the interval that only depends on the\n  variables common to `l` and `u`.\n\n  The approach is based on quantification as in Cudd_bddRestrict().\n  The function assumes that `l` implies `u`, but does not check whether\n  that's true.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddRestrict Cudd_bddSqueeze\n\n*/\nDdNode *\nCudd_bddInterpolate(\n  DdManager * dd /**< manager */,\n  DdNode * l /**< lower bound */,\n  DdNode * u /**< upper bound */)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddInterpolate(dd,l,u);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddInterpolate */\n\n\n/**\n  @brief Finds a small %BDD that agrees with `f` over `c`.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddRestrict Cudd_bddLICompaction Cudd_bddSqueeze\n\n*/\nDdNode *\nCudd_bddMinimize(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode *cplus, *res;\n\n    if (c == Cudd_Not(DD_ONE(dd))) return(c);\n    if (Cudd_IsConstantInt(f)) return(f);\n    if (f == c) return(DD_ONE(dd));\n    if (f == Cudd_Not(c)) return(Cudd_Not(DD_ONE(dd)));\n\n    cplus = Cudd_RemapOverApprox(dd,c,0,0,1.0);\n    if (cplus == NULL) return(NULL);\n    cuddRef(cplus);\n    res = Cudd_bddLICompaction(dd,f,cplus);\n    if (res == NULL) {\n\tCudd_IterDerefBdd(dd,cplus);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_IterDerefBdd(dd,cplus);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_bddMinimize */\n\n\n/**\n  @brief Find a dense subset of %BDD `f`.\n\n  @details Density is the ratio of number of minterms to number of\n  nodes.  Uses several techniques in series. It is more expensive than\n  other subsetting procedures, but often produces better results. See\n  Cudd_SubsetShortPaths for a description of the threshold and nvars\n  parameters.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_RemapUnderApprox Cudd_SubsetShortPaths\n  Cudd_SubsetHeavyBranch Cudd_bddSqueeze\n\n*/\nDdNode *\nCudd_SubsetCompress(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< %BDD whose subset is sought */,\n  int  nvars /**< number of variables in the support of f */,\n  int  threshold /**< maximum number of nodes in the subset */)\n{\n    DdNode *res, *tmp1, *tmp2;\n\n    tmp1 = Cudd_SubsetShortPaths(dd, f, nvars, threshold, 0);\n    if (tmp1 == NULL) return(NULL);\n    cuddRef(tmp1);\n    tmp2 = Cudd_RemapUnderApprox(dd,tmp1,nvars,0,0.95);\n    if (tmp2 == NULL) {\n\tCudd_IterDerefBdd(dd,tmp1);\n\treturn(NULL);\n    }\n    cuddRef(tmp2);\n    Cudd_IterDerefBdd(dd,tmp1);\n    res = Cudd_bddSqueeze(dd,tmp2,f);\n    if (res == NULL) {\n\tCudd_IterDerefBdd(dd,tmp2);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_IterDerefBdd(dd,tmp2);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_SubsetCompress */\n\n\n/**\n  @brief Find a dense superset of %BDD `f`.\n\n  @details Density is the ratio of number of minterms to number of\n  nodes.  Uses several techniques in series. It is more expensive than\n  other supersetting procedures, but often produces better\n  results. See Cudd_SupersetShortPaths for a description of the\n  threshold and nvars parameters.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_SubsetCompress Cudd_SupersetRemap Cudd_SupersetShortPaths\n  Cudd_SupersetHeavyBranch Cudd_bddSqueeze\n\n*/\nDdNode *\nCudd_SupersetCompress(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< %BDD whose superset is sought */,\n  int  nvars /**< number of variables in the support of f */,\n  int  threshold /**< maximum number of nodes in the superset */)\n{\n    DdNode *subset;\n\n    subset = Cudd_SubsetCompress(dd, Cudd_Not(f),nvars,threshold);\n\n    return(Cudd_NotCond(subset, (subset != NULL)));\n\n} /* end of Cudd_SupersetCompress */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddConstrain.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddConstrain\n\n*/\nDdNode *\ncuddBddConstrainRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode       *Fv, *Fnv, *Cv, *Cnv, *t, *e, *r;\n    DdNode\t *one, *zero;\n    int\t\t topf, topc;\n    unsigned int index;\n    int          comple = 0;\n\n    statLine(dd);\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    /* Trivial cases. */\n    if (c == one)\t\treturn(f);\n    if (c == zero)\t\treturn(zero);\n    if (Cudd_IsConstantInt(f))\treturn(f);\n    if (f == c)\t\t\treturn(one);\n    if (f == Cudd_Not(c))\treturn(zero);\n\n    /* Make canonical to increase the utilization of the cache. */\n    if (Cudd_IsComplement(f)) {\n\tf = Cudd_Not(f);\n\tcomple = 1;\n    }\n    /* Now f is a regular pointer to a non-constant node; c is also\n    ** non-constant, but may be complemented.\n    */\n\n    /* Check the cache. */\n    r = cuddCacheLookup2(dd, Cudd_bddConstrain, f, c);\n    if (r != NULL) {\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    checkWhetherToGiveUp(dd);\n    \n    /* Recursive step. */\n    topf = dd->perm[f->index];\n    topc = dd->perm[Cudd_Regular(c)->index];\n    if (topf <= topc) {\n\tindex = f->index;\n\tFv = cuddT(f); Fnv = cuddE(f);\n    } else {\n\tindex = Cudd_Regular(c)->index;\n\tFv = Fnv = f;\n    }\n    if (topc <= topf) {\n\tCv = cuddT(Cudd_Regular(c)); Cnv = cuddE(Cudd_Regular(c));\n\tif (Cudd_IsComplement(c)) {\n\t    Cv = Cudd_Not(Cv);\n\t    Cnv = Cudd_Not(Cnv);\n\t}\n    } else {\n\tCv = Cnv = c;\n    }\n\n    if (!Cudd_IsConstantInt(Cv)) {\n\tt = cuddBddConstrainRecur(dd, Fv, Cv);\n\tif (t == NULL)\n\t    return(NULL);\n    } else if (Cv == one) {\n\tt = Fv;\n    } else {\t\t/* Cv == zero: return Fnv @ Cnv */\n\tif (Cnv == one) {\n\t    r = Fnv;\n\t} else {\n\t    r = cuddBddConstrainRecur(dd, Fnv, Cnv);\n\t    if (r == NULL)\n\t\treturn(NULL);\n\t}\n\treturn(Cudd_NotCond(r,comple));\n    }\n    cuddRef(t);\n\n    if (!Cudd_IsConstantInt(Cnv)) {\n\te = cuddBddConstrainRecur(dd, Fnv, Cnv);\n\tif (e == NULL) {\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n    } else if (Cnv == one) {\n\te = Fnv;\n    } else {\t\t/* Cnv == zero: return Fv @ Cv previously computed */\n\tcuddDeref(t);\n\treturn(Cudd_NotCond(t,comple));\n    }\n    cuddRef(e);\n\n    if (Cudd_IsComplement(t)) {\n\tt = Cudd_Not(t);\n\te = Cudd_Not(e);\n\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, e);\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n\tr = Cudd_Not(r);\n    } else {\n\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, e);\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    cuddCacheInsert2(dd, Cudd_bddConstrain, f, c, r);\n    return(Cudd_NotCond(r,comple));\n\n} /* end of cuddBddConstrainRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddRestrict.\n\n  @return the restricted %BDD if successful; otherwise NULL.\n\n  @sideeffect None\n\n  @see Cudd_bddRestrict\n\n*/\nDdNode *\ncuddBddRestrictRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode\t *Fv, *Fnv, *Cv, *Cnv, *t, *e, *r, *one, *zero;\n    int\t\t topf, topc;\n    unsigned int index;\n    int\t\t comple = 0;\n\n    statLine(dd);\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    /* Trivial cases */\n    if (c == one)\t\treturn(f);\n    if (c == zero)\t\treturn(zero);\n    if (Cudd_IsConstantInt(f))\treturn(f);\n    if (f == c)\t\t\treturn(one);\n    if (f == Cudd_Not(c))\treturn(zero);\n\n    /* Make canonical to increase the utilization of the cache. */\n    if (Cudd_IsComplement(f)) {\n\tf = Cudd_Not(f);\n\tcomple = 1;\n    }\n    /* Now f is a regular pointer to a non-constant node; c is also\n    ** non-constant, but may be complemented.\n    */\n\n    /* Check the cache. */\n    r = cuddCacheLookup2(dd, Cudd_bddRestrict, f, c);\n    if (r != NULL) {\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    topf = dd->perm[f->index];\n    topc = dd->perm[Cudd_Regular(c)->index];\n\n    if (topc < topf) {\t/* abstract top variable from c */\n\tDdNode *d, *s1, *s2;\n\n\t/* Find complements of cofactors of c. */\n\tif (Cudd_IsComplement(c)) {\n\t    s1 = cuddT(Cudd_Regular(c));\n\t    s2 = cuddE(Cudd_Regular(c));\n\t} else {\n\t    s1 = Cudd_Not(cuddT(c));\n\t    s2 = Cudd_Not(cuddE(c));\n\t}\n\t/* Take the OR by applying DeMorgan. */\n\td = cuddBddAndRecur(dd, s1, s2);\n\tif (d == NULL) return(NULL);\n\td = Cudd_Not(d);\n\tcuddRef(d);\n\tr = cuddBddRestrictRecur(dd, f, d);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, d);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_IterDerefBdd(dd, d);\n\tcuddCacheInsert2(dd, Cudd_bddRestrict, f, c, r);\n\tcuddDeref(r);\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    /* Recursive step. Here topf <= topc. */\n    index = f->index;\n    Fv = cuddT(f); Fnv = cuddE(f);\n    if (topc == topf) {\n\tCv = cuddT(Cudd_Regular(c)); Cnv = cuddE(Cudd_Regular(c));\n\tif (Cudd_IsComplement(c)) {\n\t    Cv = Cudd_Not(Cv);\n\t    Cnv = Cudd_Not(Cnv);\n\t}\n    } else {\n\tCv = Cnv = c;\n    }\n\n    if (!Cudd_IsConstantInt(Cv)) {\n\tt = cuddBddRestrictRecur(dd, Fv, Cv);\n\tif (t == NULL) return(NULL);\n    } else if (Cv == one) {\n\tt = Fv;\n    } else {\t\t/* Cv == zero: return(Fnv @ Cnv) */\n\tif (Cnv == one) {\n\t    r = Fnv;\n\t} else {\n\t    r = cuddBddRestrictRecur(dd, Fnv, Cnv);\n\t    if (r == NULL) return(NULL);\n\t}\n\treturn(Cudd_NotCond(r,comple));\n    }\n    cuddRef(t);\n\n    if (!Cudd_IsConstantInt(Cnv)) {\n\te = cuddBddRestrictRecur(dd, Fnv, Cnv);\n\tif (e == NULL) {\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n    } else if (Cnv == one) {\n\te = Fnv;\n    } else {\t\t/* Cnv == zero: return (Fv @ Cv) previously computed */\n\tcuddDeref(t);\n\treturn(Cudd_NotCond(t,comple));\n    }\n    cuddRef(e);\n\n    if (Cudd_IsComplement(t)) {\n\tt = Cudd_Not(t);\n\te = Cudd_Not(e);\n\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, e);\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n\tr = Cudd_Not(r);\n    } else {\n\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, e);\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    cuddCacheInsert2(dd, Cudd_bddRestrict, f, c, r);\n    return(Cudd_NotCond(r,comple));\n\n} /* end of cuddBddRestrictRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_bddAnd.\n\n  @return a pointer to the result is successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddNPAnd\n\n*/\nDdNode *\ncuddBddNPAndRecur(\n  DdManager * manager,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *F, *ft, *fe, *G, *gt, *ge;\n    DdNode *one, *r, *t, *e;\n    int topf, topg;\n    unsigned int index;\n\n    statLine(manager);\n    one = DD_ONE(manager);\n\n    /* Terminal cases. */\n    F = Cudd_Regular(f);\n    G = Cudd_Regular(g);\n    if (F == G) {\n\tif (f == g) return(one);\n\telse return(Cudd_Not(one));\n    }\n    if (G == one) {\n\tif (g == one) return(f);\n\telse return(g);\n    }\n    if (F == one) {\n\treturn(f);\n    }\n\n    /* At this point f and g are not constant. */\n    /* Check cache. */\n    if (F->ref != 1 || G->ref != 1) {\n\tr = cuddCacheLookup2(manager, Cudd_bddNPAnd, f, g);\n\tif (r != NULL) return(r);\n    }\n\n    checkWhetherToGiveUp(manager);\n\n    /* Here we can skip the use of cuddI, because the operands are known\n    ** to be non-constant.\n    */\n    topf = manager->perm[F->index];\n    topg = manager->perm[G->index];\n\n    if (topg < topf) {\t/* abstract top variable from g */\n\tDdNode *d;\n\n\t/* Find complements of cofactors of g. */\n\tif (Cudd_IsComplement(g)) {\n\t    gt = cuddT(G);\n\t    ge = cuddE(G);\n\t} else {\n\t    gt = Cudd_Not(cuddT(g));\n\t    ge = Cudd_Not(cuddE(g));\n\t}\n\t/* Take the OR by applying DeMorgan. */\n\td = cuddBddAndRecur(manager, gt, ge);\n\tif (d == NULL) return(NULL);\n\td = Cudd_Not(d);\n\tcuddRef(d);\n\tr = cuddBddNPAndRecur(manager, f, d);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(manager, d);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_IterDerefBdd(manager, d);\n\tcuddCacheInsert2(manager, Cudd_bddNPAnd, f, g, r);\n\tcuddDeref(r);\n\treturn(r);\n    }\n\n    /* Compute cofactors. */\n    index = F->index;\n    ft = cuddT(F);\n    fe = cuddE(F);\n    if (Cudd_IsComplement(f)) {\n      ft = Cudd_Not(ft);\n      fe = Cudd_Not(fe);\n    }\n\n    if (topg == topf) {\n\tgt = cuddT(G);\n\tge = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gt = Cudd_Not(gt);\n\t    ge = Cudd_Not(ge);\n\t}\n    } else {\n\tgt = ge = g;\n    }\n\n    t = cuddBddAndRecur(manager, ft, gt);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n\n    e = cuddBddAndRecur(manager, fe, ge);\n    if (e == NULL) {\n\tCudd_IterDerefBdd(manager, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (t == e) {\n\tr = t;\n    } else {\n\tif (Cudd_IsComplement(t)) {\n\t    r = cuddUniqueInter(manager,(int)index,Cudd_Not(t),Cudd_Not(e));\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t} else {\n\t    r = cuddUniqueInter(manager,(int)index,t,e);\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(manager, t);\n\t\tCudd_IterDerefBdd(manager, e);\n\t\treturn(NULL);\n\t    }\n\t}\n    }\n    cuddDeref(e);\n    cuddDeref(t);\n    if (F->ref != 1 || G->ref != 1)\n\tcuddCacheInsert2(manager, Cudd_bddNPAnd, f, g, r);\n    return(r);\n\n} /* end of cuddBddNPAndRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addConstrain.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addConstrain\n\n*/\nDdNode *\ncuddAddConstrainRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode       *Fv, *Fnv, *Cv, *Cnv, *t, *e, *r;\n    DdNode\t *one, *zero;\n    int\t\t topf, topc;\n    unsigned int index;\n\n    statLine(dd);\n    one = DD_ONE(dd);\n    zero = DD_ZERO(dd);\n\n    /* Trivial cases. */\n    if (c == one)\t\treturn(f);\n    if (c == zero)\t\treturn(zero);\n    if (cuddIsConstant(f))\treturn(f);\n    if (f == c)\t\t\treturn(one);\n\n    /* Now f and c are non-constant. */\n\n    /* Check the cache. */\n    r = cuddCacheLookup2(dd, Cudd_addConstrain, f, c);\n    if (r != NULL) {\n\treturn(r);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    topf = dd->perm[f->index];\n    topc = dd->perm[c->index];\n    if (topf <= topc) {\n\tindex = f->index;\n\tFv = cuddT(f); Fnv = cuddE(f);\n    } else {\n\tindex = c->index;\n\tFv = Fnv = f;\n    }\n    if (topc <= topf) {\n\tCv = cuddT(c); Cnv = cuddE(c);\n    } else {\n\tCv = Cnv = c;\n    }\n\n    if (!cuddIsConstant(Cv)) {\n\tt = cuddAddConstrainRecur(dd, Fv, Cv);\n\tif (t == NULL)\n\t    return(NULL);\n    } else if (Cv == one) {\n\tt = Fv;\n    } else {\t\t/* Cv == zero: return Fnv @ Cnv */\n\tif (Cnv == one) {\n\t    r = Fnv;\n\t} else {\n\t    r = cuddAddConstrainRecur(dd, Fnv, Cnv);\n\t    if (r == NULL)\n\t\treturn(NULL);\n\t}\n\treturn(r);\n    }\n    cuddRef(t);\n\n    if (!cuddIsConstant(Cnv)) {\n\te = cuddAddConstrainRecur(dd, Fnv, Cnv);\n\tif (e == NULL) {\n\t    Cudd_RecursiveDeref(dd, t);\n\t    return(NULL);\n\t}\n    } else if (Cnv == one) {\n\te = Fnv;\n    } else {\t\t/* Cnv == zero: return Fv @ Cv previously computed */\n\tcuddDeref(t);\n\treturn(t);\n    }\n    cuddRef(e);\n\n    r = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n    if (r == NULL) {\n\tCudd_RecursiveDeref(dd, e);\n\tCudd_RecursiveDeref(dd, t);\n\treturn(NULL);\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    cuddCacheInsert2(dd, Cudd_addConstrain, f, c, r);\n    return(r);\n\n} /* end of cuddAddConstrainRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addRestrict.\n\n  @return the restricted %ADD if successful; otherwise NULL.\n\n  @sideeffect None\n\n  @see Cudd_addRestrict\n\n*/\nDdNode *\ncuddAddRestrictRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c)\n{\n    DdNode\t *Fv, *Fnv, *Cv, *Cnv, *t, *e, *r, *one, *zero;\n    int\t\t topf, topc;\n    unsigned int index;\n\n    statLine(dd);\n    one = DD_ONE(dd);\n    zero = DD_ZERO(dd);\n\n    /* Trivial cases */\n    if (c == one)\t\treturn(f);\n    if (c == zero)\t\treturn(zero);\n    if (cuddIsConstant(f))\treturn(f);\n    if (f == c)\t\t\treturn(one);\n\n    /* Now f and c are non-constant. */\n\n    /* Check the cache. */\n    r = cuddCacheLookup2(dd, Cudd_addRestrict, f, c);\n    if (r != NULL) {\n\treturn(r);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    topf = dd->perm[f->index];\n    topc = dd->perm[c->index];\n\n    if (topc < topf) {\t/* abstract top variable from c */\n\tDdNode *d, *s1, *s2;\n\n\t/* Find cofactors of c. */\n\ts1 = cuddT(c);\n\ts2 = cuddE(c);\n\t/* Take the OR by applying DeMorgan. */\n\td = cuddAddApplyRecur(dd, Cudd_addOr, s1, s2);\n\tif (d == NULL) return(NULL);\n\tcuddRef(d);\n\tr = cuddAddRestrictRecur(dd, f, d);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(dd, d);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_RecursiveDeref(dd, d);\n\tcuddCacheInsert2(dd, Cudd_addRestrict, f, c, r);\n\tcuddDeref(r);\n\treturn(r);\n    }\n\n    /* Recursive step. Here topf <= topc. */\n    index = f->index;\n    Fv = cuddT(f); Fnv = cuddE(f);\n    if (topc == topf) {\n\tCv = cuddT(c); Cnv = cuddE(c);\n    } else {\n\tCv = Cnv = c;\n    }\n\n    if (!Cudd_IsConstantInt(Cv)) {\n\tt = cuddAddRestrictRecur(dd, Fv, Cv);\n\tif (t == NULL) return(NULL);\n    } else if (Cv == one) {\n\tt = Fv;\n    } else {\t\t/* Cv == zero: return(Fnv @ Cnv) */\n\tif (Cnv == one) {\n\t    r = Fnv;\n\t} else {\n\t    r = cuddAddRestrictRecur(dd, Fnv, Cnv);\n\t    if (r == NULL) return(NULL);\n\t}\n\treturn(r);\n    }\n    cuddRef(t);\n\n    if (!cuddIsConstant(Cnv)) {\n\te = cuddAddRestrictRecur(dd, Fnv, Cnv);\n\tif (e == NULL) {\n\t    Cudd_RecursiveDeref(dd, t);\n\t    return(NULL);\n\t}\n    } else if (Cnv == one) {\n\te = Fnv;\n    } else {\t\t/* Cnv == zero: return (Fv @ Cv) previously computed */\n\tcuddDeref(t);\n\treturn(t);\n    }\n    cuddRef(e);\n\n    r = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n    if (r == NULL) {\n\tCudd_RecursiveDeref(dd, e);\n\tCudd_RecursiveDeref(dd, t);\n\treturn(NULL);\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    cuddCacheInsert2(dd, Cudd_addRestrict, f, c, r);\n    return(r);\n\n} /* end of cuddAddRestrictRecur */\n\n\n\n/**\n  @brief Performs safe minimization of a %BDD.\n\n  @details Given the %BDD `f` of a function to be minimized and a %BDD\n  `c` representing the care set, Cudd_bddLICompaction produces the\n  %BDD of a function that agrees with `f` wherever `c` is 1.  Safe\n  minimization means that the size of the result is guaranteed not to\n  exceed the size of `f`. This function is based on the DAC97 paper by\n  Hong et al..\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddLICompaction\n\n*/\nDdNode *\ncuddBddLICompaction(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be minimized */,\n  DdNode * c /**< constraint (care set) */)\n{\n    st_table *marktable, *markcache, *buildcache;\n    DdNode *res, *zero;\n\n    zero = Cudd_Not(DD_ONE(dd));\n    if (c == zero) return(zero);\n\n    /* We need to use local caches for both steps of this operation.\n    ** The results of the edge marking step are only valid as long as the\n    ** edge markings themselves are available. However, the edge markings\n    ** are lost at the end of one invocation of Cudd_bddLICompaction.\n    ** Hence, the cache entries for the edge marking step must be\n    ** invalidated at the end of this function.\n    ** For the result of the building step we argue as follows. The result\n    ** for a node and a given constrain depends on the BDD in which the node\n    ** appears. Hence, the same node and constrain may give different results\n    ** in successive invocations.\n    */\n    marktable = st_init_table(st_ptrcmp,st_ptrhash);\n    if (marktable == NULL) {\n\treturn(NULL);\n    }\n    markcache = st_init_table(MarkCacheCompare,MarkCacheHash);\n    if (markcache == NULL) {\n\tst_free_table(marktable);\n\treturn(NULL);\n    }\n    if (cuddBddLICMarkEdges(dd,f,c,marktable,markcache) == CUDD_OUT_OF_MEM) {\n\tst_foreach(markcache, MarkCacheCleanUp, NULL);\n\tst_free_table(marktable);\n\tst_free_table(markcache);\n\treturn(NULL);\n    }\n    st_foreach(markcache, MarkCacheCleanUp, NULL);\n    st_free_table(markcache);\n    buildcache = st_init_table(st_ptrcmp,st_ptrhash);\n    if (buildcache == NULL) {\n\tst_free_table(marktable);\n\treturn(NULL);\n    }\n    res = cuddBddLICBuildResult(dd,f,buildcache,marktable);\n    st_free_table(buildcache);\n    st_free_table(marktable);\n    return(res);\n\n} /* end of cuddBddLICompaction */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddConstrainDecomp.\n\n  @return f super (i) if successful; otherwise NULL.\n\n  @sideeffect None\n\n  @see Cudd_bddConstrainDecomp\n\n*/\nstatic int\ncuddBddConstrainDecomp(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** decomp)\n{\n    DdNode *F, *fv, *fvn;\n    DdNode *fAbs;\n    DdNode *result;\n    int ok;\n\n    if (Cudd_IsConstantInt(f)) return(1);\n    /* Compute complements of cofactors. */\n    F = Cudd_Regular(f);\n    fv = cuddT(F);\n    fvn = cuddE(F);\n    if (F == f) {\n\tfv = Cudd_Not(fv);\n\tfvn = Cudd_Not(fvn);\n    }\n    /* Compute abstraction of top variable. */\n    fAbs = cuddBddAndRecur(dd, fv, fvn);\n    if (fAbs == NULL) {\n\treturn(0);\n    }\n    cuddRef(fAbs);\n    fAbs = Cudd_Not(fAbs);\n    /* Recursively find the next abstraction and the components of the\n    ** decomposition. */\n    ok = cuddBddConstrainDecomp(dd, fAbs, decomp);\n    if (ok == 0) {\n\tCudd_IterDerefBdd(dd,fAbs);\n\treturn(0);\n    }\n    /* Compute the component of the decomposition corresponding to the\n    ** top variable and store it in the decomposition array. */\n    result = cuddBddConstrainRecur(dd, f, fAbs);\n    if (result == NULL) {\n\tCudd_IterDerefBdd(dd,fAbs);\n\treturn(0);\n    }\n    cuddRef(result);\n    decomp[F->index] = result;\n    Cudd_IterDerefBdd(dd, fAbs);\n    return(1);\n\n} /* end of cuddBddConstrainDecomp */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddCharToVect.\n\n  @details This function maintains the invariant that f is non-zero.\n\n  @return the i-th component of the vector if successful; otherwise NULL.\n\n  @sideeffect None\n\n  @see Cudd_bddCharToVect\n\n*/\nstatic DdNode *\ncuddBddCharToVect(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * x)\n{\n    int topf;\n    int level;\n    int comple;\n\n    DdNode *one, *zero, *res, *F, *fT, *fE, *T, *E;\n\n    statLine(dd);\n    /* Check the cache. */\n    res = cuddCacheLookup2(dd, cuddBddCharToVect, f, x);\n    if (res != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    F = Cudd_Regular(f);\n\n    topf = cuddI(dd,F->index);\n    level = dd->perm[x->index];\n\n    if (topf > level) return(x);\n\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    comple = F != f;\n    fT = Cudd_NotCond(cuddT(F),comple);\n    fE = Cudd_NotCond(cuddE(F),comple);\n\n    if (topf == level) {\n\tif (fT == zero) return(zero);\n\tif (fE == zero) return(one);\n\treturn(x);\n    }\n\n    /* Here topf < level. */\n    if (fT == zero) return(cuddBddCharToVect(dd, fE, x));\n    if (fE == zero) return(cuddBddCharToVect(dd, fT, x));\n\n    T = cuddBddCharToVect(dd, fT, x);\n    if (T == NULL) {\n\treturn(NULL);\n    }\n    cuddRef(T);\n    E = cuddBddCharToVect(dd, fE, x);\n    if (E == NULL) {\n\tCudd_IterDerefBdd(dd,T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n    res = cuddBddIteRecur(dd, dd->vars[F->index], T, E);\n    if (res == NULL) {\n\tCudd_IterDerefBdd(dd,T);\n\tCudd_IterDerefBdd(dd,E);\n\treturn(NULL);\n    }\n    cuddDeref(T);\n    cuddDeref(E);\n    cuddCacheInsert2(dd, cuddBddCharToVect, f, x, res);\n    return(res);\n\n} /* end of cuddBddCharToVect */\n\n\n/**\n  @brief Performs the edge marking step of Cudd_bddLICompaction.\n\n  @return the LUB of the markings of the two outgoing edges of\n  <code>f</code> if successful; otherwise CUDD_OUT_OF_MEM.\n\n  @sideeffect None\n\n  @see Cudd_bddLICompaction cuddBddLICBuildResult\n\n*/\nstatic int\ncuddBddLICMarkEdges(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * c,\n  st_table * table,\n  st_table * cache)\n{\n    DdNode *Fv, *Fnv, *Cv, *Cnv;\n    DdNode *one, *zero;\n    int topf, topc;\n    int comple;\n    int resT, resE, res, retval;\n    void **slot;\n    MarkCacheKey *key;\n\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    /* Terminal cases. */\n    if (c == zero) return(DD_LIC_DC);\n    if (f == one)  return(DD_LIC_1);\n    if (f == zero) return(DD_LIC_0);\n\n    /* Make canonical to increase the utilization of the cache. */\n    comple = Cudd_IsComplement(f);\n    f = Cudd_Regular(f);\n    /* Now f is a regular pointer to a non-constant node; c may be\n    ** constant, or it may be complemented.\n    */\n\n    /* Check the cache. */\n    key = ALLOC(MarkCacheKey, 1);\n    if (key == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    key->f = f; key->c = c;\n    if (st_lookup_int(cache, key, &res)) {\n\tFREE(key);\n\tif (comple) {\n\t    if (res == DD_LIC_0) res = DD_LIC_1;\n\t    else if (res == DD_LIC_1) res = DD_LIC_0;\n\t}\n\treturn(res);\n    }\n\n    /* Recursive step. */\n    topf = dd->perm[f->index];\n    topc = cuddI(dd,Cudd_Regular(c)->index);\n    if (topf <= topc) {\n\tFv = cuddT(f); Fnv = cuddE(f);\n    } else {\n\tFv = Fnv = f;\n    }\n    if (topc <= topf) {\n\t/* We know that c is not constant because f is not. */\n\tCv = cuddT(Cudd_Regular(c)); Cnv = cuddE(Cudd_Regular(c));\n\tif (Cudd_IsComplement(c)) {\n\t    Cv = Cudd_Not(Cv);\n\t    Cnv = Cudd_Not(Cnv);\n\t}\n    } else {\n\tCv = Cnv = c;\n    }\n\n    resT = cuddBddLICMarkEdges(dd, Fv, Cv, table, cache);\n    if (resT == CUDD_OUT_OF_MEM) {\n\tFREE(key);\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    resE = cuddBddLICMarkEdges(dd, Fnv, Cnv, table, cache);\n    if (resE == CUDD_OUT_OF_MEM) {\n\tFREE(key);\n\treturn(CUDD_OUT_OF_MEM);\n    }\n\n    /* Update edge markings. */\n    if (topf <= topc) {\n\tretval = st_find_or_add(table, f, &slot);\n\tif (retval == 0) {\n\t    *slot = (void **) (ptrint)((resT << 2) | resE);\n\t} else if (retval == 1) {\n\t    *slot = (void **) (ptrint)((int)((ptrint) *slot) | (resT << 2) | resE);\n\t} else {\n\t    FREE(key);\n\t    return(CUDD_OUT_OF_MEM);\n\t}\n    }\n\n    /* Cache result. */\n    res = resT | resE;\n    if (st_insert(cache, key, (void *)(ptrint)res) == ST_OUT_OF_MEM) {\n\tFREE(key);\n\treturn(CUDD_OUT_OF_MEM);\n    }\n\n    /* Take into account possible complementation. */\n    if (comple) {\n\tif (res == DD_LIC_0) res = DD_LIC_1;\n\telse if (res == DD_LIC_1) res = DD_LIC_0;\n    }\n    return(res);\n\n} /* end of cuddBddLICMarkEdges */\n\n\n/**\n  @brief Builds the result of Cudd_bddLICompaction.\n\n  @return a pointer to the minimized %BDD if successful; otherwise NULL.\n\n  @sideeffect None\n\n  @see Cudd_bddLICompaction cuddBddLICMarkEdges\n\n*/\nstatic DdNode *\ncuddBddLICBuildResult(\n  DdManager * dd,\n  DdNode * f,\n  st_table * cache,\n  st_table * table)\n{\n    DdNode *Fv, *Fnv, *r, *t, *e;\n    DdNode *one, *zero;\n    unsigned int index;\n    int comple;\n    int markT, markE, markings;\n\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    if (Cudd_IsConstantInt(f)) return(f);\n    /* Make canonical to increase the utilization of the cache. */\n    comple = Cudd_IsComplement(f);\n    f = Cudd_Regular(f);\n\n    /* Check the cache. */\n    if (st_lookup(cache, f, (void **) &r)) {\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    /* Retrieve the edge markings. */\n    if (st_lookup_int(table, f, &markings) == 0)\n\treturn(NULL);\n    markT = markings >> 2;\n    markE = markings & 3;\n\n    index = f->index;\n    Fv = cuddT(f); Fnv = cuddE(f);\n\n    if (markT == DD_LIC_NL) {\n\tt = cuddBddLICBuildResult(dd,Fv,cache,table);\n\tif (t == NULL) {\n\t    return(NULL);\n\t}\n    } else if (markT == DD_LIC_1) {\n\tt = one;\n    } else {\n\tt = zero;\n    }\n    cuddRef(t);\n    if (markE == DD_LIC_NL) {\n\te = cuddBddLICBuildResult(dd,Fnv,cache,table);\n\tif (e == NULL) {\n\t    Cudd_IterDerefBdd(dd,t);\n\t    return(NULL);\n\t}\n    } else if (markE == DD_LIC_1) {\n\te = one;\n    } else {\n\te = zero;\n    }\n    cuddRef(e);\n\n    if (markT == DD_LIC_DC && markE != DD_LIC_DC) {\n\tr = e;\n    } else if (markT != DD_LIC_DC && markE == DD_LIC_DC) {\n\tr = t;\n    } else {\n\tif (Cudd_IsComplement(t)) {\n\t    t = Cudd_Not(t);\n\t    e = Cudd_Not(e);\n\t    r = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(dd, e);\n\t\tCudd_IterDerefBdd(dd, t);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t} else {\n\t    r = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(dd, e);\n\t\tCudd_IterDerefBdd(dd, t);\n\t\treturn(NULL);\n\t    }\n\t}\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    if (st_insert(cache, f, r) == ST_OUT_OF_MEM) {\n\tcuddRef(r);\n\tCudd_IterDerefBdd(dd,r);\n\treturn(NULL);\n    }\n\n    return(Cudd_NotCond(r,comple));\n\n} /* end of cuddBddLICBuildResult */\n\n\n/**\n  @brief Hash function for the computed table of cuddBddLICMarkEdges.\n\n  @return the bucket number.\n\n  @sideeffect None\n\n  @see Cudd_bddLICompaction\n\n*/\nstatic int\nMarkCacheHash(\n  void const * ptr,\n  int  modulus)\n{\n    int val = 0;\n    MarkCacheKey const *entry = (MarkCacheKey const *) ptr;\n\n    val = (int) (ptrint) entry->f;\n    val = val * 997 + (int) (ptrint) entry->c;\n\n    return ((val < 0) ? -val : val) % modulus;\n\n} /* end of MarkCacheHash */\n\n\n/**\n  @brief Comparison function for the computed table of\n  cuddBddLICMarkEdges.\n\n  @return 0 if the two nodes of the key are equal; 1 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddLICompaction\n\n*/\nstatic int\nMarkCacheCompare(\n  const void * ptr1,\n  const void * ptr2)\n{\n    MarkCacheKey const *entry1 = (MarkCacheKey const *) ptr1;\n    MarkCacheKey const *entry2 = (MarkCacheKey const *) ptr2;\n    \n    return((entry1->f != entry2->f) || (entry1->c != entry2->c));\n\n} /* end of MarkCacheCompare */\n\n\n/**\n  @brief Frees memory associated with computed table of\n  cuddBddLICMarkEdges.\n\n  @return ST_CONTINUE.\n\n  @sideeffect None\n\n  @see Cudd_bddLICompaction\n\n*/\nstatic enum st_retval\nMarkCacheCleanUp(\n  void * key,\n  void * value,\n  void * arg)\n{\n    MarkCacheKey *entry = (MarkCacheKey *) key;\n\n    (void) value; /* avoid warning */\n    (void) arg;   /* avoid warning */\n    FREE(entry);\n    return ST_CONTINUE;\n\n} /* end of MarkCacheCleanUp */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddSqueeze.\n\n  @details This procedure exploits the fact that if we complement and\n  swap the bounds of the interval we obtain a valid solution by taking\n  the complement of the solution to the original problem. Therefore,\n  we can enforce the condition that the upper bound is always regular.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddSqueeze\n\n*/\nstatic DdNode *\ncuddBddSqueeze(\n  DdManager * dd,\n  DdNode * l,\n  DdNode * u)\n{\n    DdNode *one, *zero, *r, *lt, *le, *ut, *ue, *t, *e;\n#if 0\n    DdNode *ar;\n#endif\n    int comple = 0;\n    int topu, topl;\n    unsigned int index;\n\n    statLine(dd);\n    if (l == u) {\n\treturn(l);\n    }\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n    /* The only case when l == zero && u == one is at the top level,\n    ** where returning either one or zero is OK. In all other cases\n    ** the procedure will detect such a case and will perform\n    ** remapping. Therefore the order in which we test l and u at this\n    ** point is immaterial. */\n    if (l == zero) return(l);\n    if (u == one)  return(u);\n\n    /* Make canonical to increase the utilization of the cache. */\n    if (Cudd_IsComplement(u)) {\n\tDdNode *temp;\n\ttemp = Cudd_Not(l);\n\tl = Cudd_Not(u);\n\tu = temp;\n\tcomple = 1;\n    }\n    /* At this point u is regular and non-constant; l is non-constant, but\n    ** may be complemented. */\n\n    /* Here we could check the relative sizes. */\n\n    /* Check the cache. */\n    r = cuddCacheLookup2(dd, Cudd_bddSqueeze, l, u);\n    if (r != NULL) {\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    topu = dd->perm[u->index];\n    topl = dd->perm[Cudd_Regular(l)->index];\n    if (topu <= topl) {\n\tindex = u->index;\n\tut = cuddT(u); ue = cuddE(u);\n    } else {\n\tindex = Cudd_Regular(l)->index;\n\tut = ue = u;\n    }\n    if (topl <= topu) {\n\tlt = cuddT(Cudd_Regular(l)); le = cuddE(Cudd_Regular(l));\n\tif (Cudd_IsComplement(l)) {\n\t    lt = Cudd_Not(lt);\n\t    le = Cudd_Not(le);\n\t}\n    } else {\n\tlt = le = l;\n    }\n\n    /* If one interval is contained in the other, use the smaller\n    ** interval. This corresponds to one-sided matching. */\n    if ((lt == zero || Cudd_bddLeq(dd,lt,le)) &&\n\t(ut == one  || Cudd_bddLeq(dd,ue,ut))) { /* remap */\n\tr = cuddBddSqueeze(dd, le, ue);\n\tif (r == NULL)\n\t    return(NULL);\n\treturn(Cudd_NotCond(r,comple));\n    } else if ((le == zero || Cudd_bddLeq(dd,le,lt)) &&\n\t       (ue == one  || Cudd_bddLeq(dd,ut,ue))) { /* remap */\n\tr = cuddBddSqueeze(dd, lt, ut);\n\tif (r == NULL)\n\t    return(NULL);\n\treturn(Cudd_NotCond(r,comple));\n    } else if ((le == zero || Cudd_bddLeq(dd,le,Cudd_Not(ut))) &&\n\t       (ue == one  || Cudd_bddLeq(dd,Cudd_Not(lt),ue))) { /* c-remap */\n\tt = cuddBddSqueeze(dd, lt, ut);\n\tcuddRef(t);\n\tif (Cudd_IsComplement(t)) {\n\t    r = cuddUniqueInter(dd, index, Cudd_Not(t), t);\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(dd, t);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t} else {\n\t    r = cuddUniqueInter(dd, index, t, Cudd_Not(t));\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(dd, t);\n\t\treturn(NULL);\n\t    }\n\t}\n\tcuddDeref(t);\n\tif (r == NULL)\n\t    return(NULL);\n\tcuddCacheInsert2(dd, Cudd_bddSqueeze, l, u, r);\n\treturn(Cudd_NotCond(r,comple));\n    } else if ((lt == zero || Cudd_bddLeq(dd,lt,Cudd_Not(ue))) &&\n\t       (ut == one  || Cudd_bddLeq(dd,Cudd_Not(le),ut))) { /* c-remap */\n\te = cuddBddSqueeze(dd, le, ue);\n\tcuddRef(e);\n\tif (Cudd_IsComplement(e)) {\n\t    r = cuddUniqueInter(dd, index, Cudd_Not(e), e);\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(dd, e);\n\t\treturn(NULL);\n\t    }\n\t} else {\n\t    r = cuddUniqueInter(dd, index, e, Cudd_Not(e));\n\t    if (r == NULL) {\n\t\tCudd_IterDerefBdd(dd, e);\n\t\treturn(NULL);\n\t    }\n\t    r = Cudd_Not(r);\n\t}\n\tcuddDeref(e);\n\tif (r == NULL)\n\t    return(NULL);\n\tcuddCacheInsert2(dd, Cudd_bddSqueeze, l, u, r);\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n#if 0\n    /* If the two intervals intersect, take a solution from\n    ** the intersection of the intervals. This guarantees that the\n    ** splitting variable will not appear in the result.\n    ** This approach corresponds to two-sided matching, and is very\n    ** expensive. */\n    if (Cudd_bddLeq(dd,lt,ue) && Cudd_bddLeq(dd,le,ut)) {\n\tDdNode *au, *al;\n\tau = cuddBddAndRecur(dd,ut,ue);\n\tif (au == NULL)\n\t    return(NULL);\n\tcuddRef(au);\n\tal = cuddBddAndRecur(dd,Cudd_Not(lt),Cudd_Not(le));\n\tif (al == NULL) {\n\t    Cudd_IterDerefBdd(dd,au);\n\t    return(NULL);\n\t}\n\tcuddRef(al);\n\tal = Cudd_Not(al);\n\tar = cuddBddSqueeze(dd, al, au);\n\tif (ar == NULL) {\n\t    Cudd_IterDerefBdd(dd,au);\n\t    Cudd_IterDerefBdd(dd,al);\n\t    return(NULL);\n\t}\n\tcuddRef(ar);\n\tCudd_IterDerefBdd(dd,au);\n\tCudd_IterDerefBdd(dd,al);\n    } else {\n\tar = NULL;\n    }\n#endif\n\n    t = cuddBddSqueeze(dd, lt, ut);\n    if (t == NULL) {\n\treturn(NULL);\n    }\n    cuddRef(t);\n    e = cuddBddSqueeze(dd, le, ue);\n    if (e == NULL) {\n\tCudd_IterDerefBdd(dd,t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (Cudd_IsComplement(t)) {\n\tt = Cudd_Not(t);\n\te = Cudd_Not(e);\n\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, e);\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n\tr = Cudd_Not(r);\n    } else {\n\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, e);\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n#if 0\n    /* Check whether there is a result obtained by abstraction and whether\n    ** it is better than the one obtained by recursion. */\n    cuddRef(r);\n    if (ar != NULL) {\n\tif (Cudd_DagSize(ar) <= Cudd_DagSize(r)) {\n\t    Cudd_IterDerefBdd(dd, r);\n\t    r = ar;\n\t} else {\n\t    Cudd_IterDerefBdd(dd, ar);\n\t}\n    }\n    cuddDeref(r);\n#endif\n\n    cuddCacheInsert2(dd, Cudd_bddSqueeze, l, u, r);\n    return(Cudd_NotCond(r,comple));\n\n} /* end of cuddBddSqueeze */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddInterpolate.\n\n  @details This procedure exploits the fact that if we complement and\n  swap the bounds of the interval we obtain a valid solution by taking\n  the complement of the solution to the original problem. Therefore,\n  we can enforce the condition that the upper bound is always regular.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddInterpolate\n\n*/\nstatic DdNode *\ncuddBddInterpolate(\n  DdManager * dd,\n  DdNode * l,\n  DdNode * u)\n{\n    DdNode *one, *zero, *r, *lt, *le, *ut, *ue, *t, *e;\n#if 0\n    DdNode *ar;\n#endif\n    int comple = 0;\n    int topu, topl;\n    unsigned int index;\n\n    statLine(dd);\n    if (l == u) {\n\treturn(l);\n    }\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n    if (l == zero) return(l);\n    if (u == one)  return(u);\n\n    /* Make canonical to increase the utilization of the cache. */\n    if (Cudd_IsComplement(u)) {\n\tDdNode *temp;\n\ttemp = Cudd_Not(l);\n\tl = Cudd_Not(u);\n\tu = temp;\n\tcomple = 1;\n    }\n    /* At this point u is regular and non-constant; l is non-constant, but\n    ** may be complemented. */\n\n    /* Check the cache. */\n    r = cuddCacheLookup2(dd, Cudd_bddInterpolate, l, u);\n    if (r != NULL) {\n\treturn(Cudd_NotCond(r,comple));\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Recursive step. */\n    topu = dd->perm[u->index];\n    topl = dd->perm[Cudd_Regular(l)->index];\n    if (topu < topl) {\n        /* Universally quantify top variable from upper bound. */\n        DdNode *qu;\n\tut = cuddT(u); ue = cuddE(u);\n        qu = cuddBddAndRecur(dd, ut, ue);\n        if (qu == NULL) return(NULL);\n        cuddRef(qu);\n        r = cuddBddInterpolate(dd, l, qu);\n        if (r == NULL) {\n            Cudd_IterDerefBdd(dd, qu);\n            return(NULL);\n        }\n        cuddRef(r);\n        Cudd_IterDerefBdd(dd, qu);\n        cuddCacheInsert2(dd, Cudd_bddInterpolate, l, u, r);\n        cuddDeref(r);\n        return(Cudd_NotCond(r, comple));\n    } else if (topl < topu) {\n        /* Existentially quantify top variable from lower bound. */\n        DdNode *ql;\n        /* Find complements of cofactors of c. */\n        if (Cudd_IsComplement(l)) {\n            lt = cuddT(Cudd_Regular(l));\n            le = cuddE(Cudd_Regular(l));\n        } else {\n            lt = Cudd_Not(cuddT(l));\n            le = Cudd_Not(cuddE(l));\n        }\n        /* Disjoin cofactors by applying DeMorgan. */\n        ql = cuddBddAndRecur(dd, lt, le);\n        if (ql == NULL) return (NULL);\n        cuddRef(ql);\n        ql = Cudd_Not(ql);\n        r = cuddBddInterpolate(dd, ql, u);\n        if (r == NULL) {\n            Cudd_IterDerefBdd(dd, ql);\n            return(NULL);\n        }\n        cuddRef(r);\n        Cudd_IterDerefBdd(dd, ql);\n        cuddCacheInsert2(dd, Cudd_bddInterpolate, l, u, r);\n        cuddDeref(r);\n        return(Cudd_NotCond(r, comple));\n    }\n\n    /* Both bounds depend on the top variable: split and recur. */\n    index = u->index;\n    ut = cuddT(u); ue = cuddE(u);\n    lt = cuddT(Cudd_Regular(l)); le = cuddE(Cudd_Regular(l));\n    if (Cudd_IsComplement(l)) {\n        lt = Cudd_Not(lt);\n        le = Cudd_Not(le);\n    }\n\n    t = cuddBddInterpolate(dd, lt, ut);\n    if (t == NULL) {\n\treturn(NULL);\n    }\n    cuddRef(t);\n    e = cuddBddInterpolate(dd, le, ue);\n    if (e == NULL) {\n\tCudd_IterDerefBdd(dd,t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    if (Cudd_IsComplement(t)) {\n\tt = Cudd_Not(t);\n\te = Cudd_Not(e);\n\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, e);\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n\tr = Cudd_Not(r);\n    } else {\n\tr = (t == e) ? t : cuddUniqueInter(dd, index, t, e);\n\tif (r == NULL) {\n\t    Cudd_IterDerefBdd(dd, e);\n\t    Cudd_IterDerefBdd(dd, t);\n\t    return(NULL);\n\t}\n    }\n    cuddDeref(t);\n    cuddDeref(e);\n\n    cuddCacheInsert2(dd, Cudd_bddInterpolate, l, u, r);\n    return(Cudd_NotCond(r,comple));\n\n} /* end of cuddBddInterpolate */\n"
  },
  {
    "path": "cudd/cudd/cuddGenetic.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Genetic algorithm for variable reordering.\n\n  @details The genetic algorithm implemented here is as follows.  We\n  start with the current %DD order.  We sift this order and use this as\n  the reference %DD.  We only keep 1 %DD around for the entire process\n  and simply rearrange the order of this %DD, storing the various\n  orders and their corresponding %DD sizes.  We generate more random\n  orders to build an initial population. This initial population is 3\n  times the number of variables, with a maximum of 120. Each random\n  order is built (from the reference %DD) and its size stored.  Each\n  random order is also sifted to keep the %DD sizes fairly small.  Then\n  a crossover is performed between two orders (picked randomly) and\n  the two resulting DDs are built and sifted.  For each new order, if\n  its size is smaller than any %DD in the population, it is inserted\n  into the population and the %DD with the largest number of nodes is\n  thrown out. The crossover process happens up to 50 times, and at\n  this point the %DD in the population with the smallest size is chosen\n  as the result.  This %DD must then be built from the reference %DD.\n\n  @author Curt Musfeldt, Alan Shuler, Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\ntypedef struct GeneticInfo GeneticInfo_t;\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Miscellaneous information.\n */\nstruct GeneticInfo {\n    int popsize;\t/**< the size of the population */\n    int numvars;\t/**< the number of variables to be ordered. */\n/**\n ** @brief storedd stores the population orders and sizes.\n **\n ** @details This table has two extra rows and one extras column. The\n ** two extra rows are used for the offspring produced by a\n ** crossover. Each row stores one order and its size. The order is\n ** stored by storing the indices of variables in the order in which\n ** they appear in the order. The table is in reality a\n ** one-dimensional array which is accessed via a macro to give the\n ** illusion it is a two-dimensional structure.\n */\n    int *storedd;\n    st_table *computed;\t/**< hash table to identify existing orders */\n    int *repeat;\t/**< how many times an order is present */\n    int large;\t\t/**< stores the index of the population with\n                         ** the largest number of nodes in the %DD */\n    int result;\t\t/**< result */\n    int cross;\t\t/**< the number of crossovers to perform */\n};\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**\n ** @brief Used to access the population table as if it were a\n ** two-dimensional structure.\n */\n#define STOREDD(info,i,j)\t(info)->storedd[(i)*((info)->numvars+1)+(j)]\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int make_random (DdManager *table, int lower, GeneticInfo_t * info);\nstatic int sift_up (DdManager *table, int x, int x_low);\nstatic int build_dd (DdManager *table, int num, int lower, int upper, GeneticInfo_t * info);\nstatic int largest (GeneticInfo_t * info);\nstatic int rand_int (DdManager * dd, int a);\nstatic int array_hash (void const *array, int modulus, void const * arg);\nstatic int array_compare (const void *array1, const void *array2, void const * arg);\nstatic int find_best (GeneticInfo_t * info);\n#ifdef DD_STATS\nstatic double find_average_fitness (GeneticInfo_t * info);\n#endif\nstatic int PMX (DdManager * dd, int maxvar, GeneticInfo_t * info);\nstatic int roulette (DdManager *dd, int *p1, int *p2, GeneticInfo_t * info);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Genetic algorithm for %DD reordering.\n\n  @details The two children of a crossover will be stored in\n  storedd[popsize] and storedd[popsize+1] --- the last two slots in the\n  storedd array.  (This will make comparisons and replacement easy.)\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddGa(\n  DdManager * table /**< manager */,\n  int  lower /**< lowest level to be reordered */,\n  int  upper /**< highest level to be reorderded */)\n{\n    int \ti,n,m;\t\t/* dummy/loop vars */\n    int\t\tindex;\n#ifdef DD_STATS\n    double\taverage_fitness;\n#endif\n    int\t\tsmall;\t\t/* index of smallest DD in population */\n    GeneticInfo_t info;\n\n    /* Do an initial sifting to produce at least one reasonable individual. */\n    if (!cuddSifting(table,lower,upper)) return(0);\n\n    /* Get the initial values. */\n    info.numvars = upper - lower + 1; /* number of variables to be reordered */\n    if (table->populationSize == 0) {\n\tinfo.popsize = 3 * info.numvars;  /* population size is 3 times # of vars */\n\tif (info.popsize > 120) {\n\t    info.popsize = 120;\t/* Maximum population size is 120 */\n\t}\n    } else {\n\tinfo.popsize = table->populationSize;  /* user specified value */\n    }\n    if (info.popsize < 4) info.popsize = 4;\t/* enforce minimum population size */\n\n    /* Allocate population table. */\n    info.storedd = ALLOC(int,(info.popsize+2)*(info.numvars+1));\n    if (info.storedd == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n\n    /* Initialize the computed table. This table is made up of two data\n    ** structures: A hash table with the key given by the order, which says\n    ** if a given order is present in the population; and the repeat\n    ** vector, which says how many copies of a given order are stored in\n    ** the population table. If there are multiple copies of an order, only\n    ** one has a repeat count greater than 1. This copy is the one pointed\n    ** by the computed table.\n    */\n    info.repeat = ALLOC(int,info.popsize);\n    if (info.repeat == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tFREE(info.storedd);\n\treturn(0);\n    }\n    for (i = 0; i < info.popsize; i++) {\n\tinfo.repeat[i] = 0;\n    }\n    info.computed = st_init_table_with_arg(array_compare,array_hash,\n                                           (void *)(ptrint) info.numvars);\n    if (info.computed == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tFREE(info.storedd);\n\tFREE(info.repeat);\n\treturn(0);\n    }\n\n    /* Copy the current DD and its size to the population table. */\n    for (i = 0; i < info.numvars; i++) {\n\tSTOREDD(&info,0,i) = table->invperm[i+lower]; /* order of initial DD */\n    }\n    STOREDD(&info,0,info.numvars) =\n        (int) (table->keys - table->isolated); /* size of initial DD */\n\n    /* Store the initial order in the computed table. */\n    if (st_insert(info.computed,info.storedd,(void *) 0) == ST_OUT_OF_MEM) {\n\tFREE(info.storedd);\n\tFREE(info.repeat);\n\tst_free_table(info.computed);\n\treturn(0);\n    }\n    info.repeat[0]++;\n\n    /* Insert the reverse order as second element of the population. */\n    for (i = 0; i < info.numvars; i++) {\n\tSTOREDD(&info,1,info.numvars-1-i) = table->invperm[i+lower]; /* reverse order */\n    }\n\n    /* Now create the random orders. make_random fills the population\n    ** table with random permutations. The successive loop builds and sifts\n    ** the DDs for the reverse order and each random permutation, and stores\n    ** the results in the computed table.\n    */\n    if (!make_random(table,lower,&info)) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tFREE(info.storedd);\n\tFREE(info.repeat);\n\tst_free_table(info.computed);\n\treturn(0);\n    }\n    for (i = 1; i < info.popsize; i++) {\n\tinfo.result = build_dd(table,i,lower,upper,&info);\t/* build and sift order */\n\tif (!info.result) {\n\t    FREE(info.storedd);\n\t    FREE(info.repeat);\n\t    st_free_table(info.computed);\n\t    return(0);\n\t}\n\tif (st_lookup_int(info.computed,&STOREDD(&info,i,0),&index)) {\n\t    info.repeat[index]++;\n\t} else {\n\t    if (st_insert(info.computed,&STOREDD(&info,i,0),(void *)(ptruint)i) ==\n\t    ST_OUT_OF_MEM) {\n\t\tFREE(info.storedd);\n\t\tFREE(info.repeat);\n\t\tst_free_table(info.computed);\n\t\treturn(0);\n\t    }\n\t    info.repeat[i]++;\n\t}\n    }\n\n#if 0\n#ifdef DD_STATS\n    /* Print the initial population. */\n    (void) fprintf(table->out,\"Initial population after sifting\\n\");\n    for (m = 0; m < info.popsize; m++) {\n\tfor (i = 0; i < info.numvars; i++) {\n\t    (void) fprintf(table->out,\" %2d\",STOREDD(&info,m,i));\n\t}\n\t(void) fprintf(table->out,\" : %3d (%d)\\n\",\n\t\t       STOREDD(&info,m,numvars),info.repeat[m]);\n    }\n#endif\n#endif\n\n#ifdef DD_STATS\n    small = find_best(&info);\n    average_fitness = find_average_fitness(&info);\n    (void) fprintf(table->out,\"\\nInitial population: best fitness = %d, average fitness %8.3f\",STOREDD(&info,small,info.numvars),average_fitness);\n#endif\n\n    /* Decide how many crossovers should be tried. */\n    if (table->numberXovers == 0) {\n\tinfo.cross = 3*info.numvars;\n\tif (info.cross > 60) {\t/* do a maximum of 50 crossovers */\n\t    info.cross = 60;\n\t}\n    } else {\n\tinfo.cross = table->numberXovers;      /* use user specified value */\n    }\n    if (info.cross >= info.popsize) {\n\tinfo.cross = info.popsize;\n    }\n\n    /* Perform the crossovers to get the best order. */\n    for (m = 0; m < info.cross; m++) {\n\tif (!PMX(table, table->size, &info)) {\t/* perform one crossover */\n\t    table->errorCode = CUDD_MEMORY_OUT;\n\t    FREE(info.storedd);\n\t    FREE(info.repeat);\n\t    st_free_table(info.computed);\n\t    return(0);\n\t}\n\t/* The offsprings are left in the last two entries of the\n\t** population table. These are now considered in turn.\n\t*/\n\tfor (i = info.popsize; i <= info.popsize+1; i++) {\n\t    info.result = build_dd(table,i,lower,upper,&info); /* build and sift child */\n\t    if (!info.result) {\n\t\tFREE(info.storedd);\n\t\tFREE(info.repeat);\n\t\tst_free_table(info.computed);\n\t\treturn(0);\n\t    }\n\t    info.large = largest(&info); /* find the largest DD in population */\n\n\t    /* If the new child is smaller than the largest DD in the current\n\t    ** population, enter it into the population in place of the\n\t    ** largest DD.\n\t    */\n\t    if (STOREDD(&info,i,info.numvars) <\n                STOREDD(&info,info.large,info.numvars)) {\n\t\t/* Look up the largest DD in the computed table.\n\t\t** Decrease its repetition count. If the repetition count\n\t\t** goes to 0, remove the largest DD from the computed table.\n\t\t*/\n\t\tinfo.result = st_lookup_int(info.computed,&STOREDD(&info,info.large,0),&index);\n\t\tif (!info.result) {\n\t\t    FREE(info.storedd);\n\t\t    FREE(info.repeat);\n\t\t    st_free_table(info.computed);\n\t\t    return(0);\n\t\t}\n\t\tinfo.repeat[index]--;\n\t\tif (info.repeat[index] == 0) {\n\t\t    int *pointer = &STOREDD(&info,index,0);\n\t\t    info.result = st_delete(info.computed, (void **) &pointer, NULL);\n\t\t    if (!info.result) {\n\t\t\tFREE(info.storedd);\n\t\t\tFREE(info.repeat);\n\t\t\tst_free_table(info.computed);\n\t\t\treturn(0);\n\t\t    }\n\t\t}\n\t\t/* Copy the new individual to the entry of the\n\t\t** population table just made available and update the\n\t\t** computed table.\n\t\t*/\n\t\tfor (n = 0; n <= info.numvars; n++) {\n\t\t    STOREDD(&info,info.large,n) = STOREDD(&info,i,n);\n\t\t}\n\t\tif (st_lookup_int(info.computed,&STOREDD(&info,info.large,0),&index)) {\n\t\t    info.repeat[index]++;\n\t\t} else {\n\t\t    if (st_insert(info.computed,&STOREDD(&info,info.large,0),\n\t\t    (void *)(ptruint)info.large) == ST_OUT_OF_MEM) {\n\t\t\tFREE(info.storedd);\n\t\t\tFREE(info.repeat);\n\t\t\tst_free_table(info.computed);\n\t\t\treturn(0);\n\t\t    }\n\t\t    info.repeat[info.large]++;\n\t\t}\n\t    }\n\t}\n    }\n\n    /* Find the smallest DD in the population and build it;\n    ** that will be the result.\n    */\n    small = find_best(&info);\n\n    /* Print stats on the final population. */\n#ifdef DD_STATS\n    average_fitness = find_average_fitness(&info);\n    (void) fprintf(table->out,\"\\nFinal population: best fitness = %d, average fitness %8.3f\",STOREDD(&info,small,info.numvars),average_fitness);\n#endif\n\n    /* Clean up, build the result DD, and return. */\n    st_free_table(info.computed);\n    info.computed = NULL;\n    info.result = build_dd(table,small,lower,upper,&info);\n    FREE(info.storedd);\n    FREE(info.repeat);\n    return(info.result);\n\n} /* end of cuddGa */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Generates the random sequences for the initial population.\n\n  @details The sequences are permutations of the indices between lower\n  and upper in the current order.\n\n  @sideeffect None\n\n*/\nstatic int\nmake_random(\n  DdManager * table,\n  int  lower,\n  GeneticInfo_t * info)\n{\n    int i,j;\t\t/* loop variables */\n    int\t*used;\t\t/* is a number already in a permutation */\n    int\tnext;\t\t/* next random number without repetitions */\n\n    used = ALLOC(int,info->numvars);\n    if (used == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n#if 0\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"Initial population before sifting\\n\");\n    for (i = 0; i < 2; i++) {\n\tfor (j = 0; j < numvars; j++) {\n\t    (void) fprintf(table->out,\" %2d\",STOREDD(i,j));\n\t}\n\t(void) fprintf(table->out,\"\\n\");\n    }\n#endif\n#endif\n    for (i = 2; i < info->popsize; i++) {\n       \tfor (j = 0; j < info->numvars; j++) {\n\t    used[j] = 0;\n\t}\n\t/* Generate a permutation of {0...numvars-1} and use it to\n\t** permute the variables in the layesr from lower to upper.\n\t*/\n       \tfor (j = 0; j < info->numvars; j++) {\n\t    do {\n\t\tnext = rand_int(table,info->numvars-1);\n\t    } while (used[next] != 0);\n\t    used[next] = 1;\n\t    STOREDD(info,i,j) = table->invperm[next+lower];\n       \t}\n#if 0\n#ifdef DD_STATS\n\t/* Print the order just generated. */\n\tfor (j = 0; j < numvars; j++) {\n\t    (void) fprintf(table->out,\" %2d\",STOREDD(i,j));\n\t}\n\t(void) fprintf(table->out,\"\\n\");\n#endif\n#endif\n    }\n    FREE(used);\n    return(1);\n\n} /* end of make_random */\n\n\n/**\n  @brief Moves one variable up.\n\n  @details Takes a variable from position x and sifts it up to\n  position x_low;  x_low should be less than x.\n\n  @return 1 if successful; 0 otherwise\n\n  @sideeffect None\n\n*/\nstatic int\nsift_up(\n  DdManager * table,\n  int  x,\n  int  x_low)\n{\n    int        y;\n    int        size;\n\n    y = cuddNextLow(table,x);\n    while (y >= x_low) {\n\tsize = cuddSwapInPlace(table,y,x);\n\tif (size == 0) {\n\t    return(0);\n\t}\n\tx = y;\n\ty = cuddNextLow(table,x);\n    }\n    return(1);\n\n} /* end of sift_up */\n\n\n/**\n  @brief Builds a %DD from a given order.\n\n  @details This procedure also sifts the final order and inserts into\n  the array the size in nodes of the result.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nbuild_dd(\n  DdManager * table,\n  int  num /* the index of the individual to be built */,\n  int  lower,\n  int  upper,\n  GeneticInfo_t * info)\n{\n    int \ti,j;\t\t/* loop vars */\n    int \tposition;\n    int\t\tindex;\n    int\t\tlimit;\t\t/* how large the DD for this order can grow */\n    int\t\tsize;\n\n    /* Check the computed table. If the order already exists, it\n    ** suffices to copy the size from the existing entry.\n    */\n    if (info->computed &&\n        st_lookup_int(info->computed,&STOREDD(info,num,0),&index)) {\n\tSTOREDD(info,num,info->numvars) = STOREDD(info,index,info->numvars);\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\"\\nCache hit for index %d\", index);\n#endif\n\treturn(1);\n    }\n\n    /* Stop if the DD grows 20 times larges than the reference size. */\n    limit = 20 * STOREDD(info,0,info->numvars);\n\n    /* Sift up the variables so as to build the desired permutation.\n    ** First the variable that has to be on top is sifted to the top.\n    ** Then the variable that has to occupy the secon position is sifted\n    ** up to the second position, and so on.\n    */\n    for (j = 0; j < info->numvars; j++) {\n\ti = STOREDD(info,num,j);\n\tposition = table->perm[i];\n\tinfo->result = sift_up(table,position,j+lower);\n\tif (!info->result) return(0);\n\tsize = (int) (table->keys - table->isolated);\n\tif (size > limit) break;\n    }\n\n    /* Sift the DD just built. */\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n\");\n#endif\n    info->result = cuddSifting(table,lower,upper);\n    if (!info->result) return(0);\n\n    /* Copy order and size to table. */\n    for (j = 0; j < info->numvars; j++) {\n\tSTOREDD(info,num,j) = table->invperm[lower+j];\n    }\n    STOREDD(info,num,info->numvars) = (int) (table->keys - table->isolated); /* size of new DD */\n    return(1);\n\n} /* end of build_dd */\n\n\n/**\n  @brief Finds the largest %DD in the population.\n\n  @details If an order is repeated, it avoids choosing the copy that\n  is in the computed table (it has repeat[i > 1).]\n\n  @sideeffect None\n\n*/\nstatic int\nlargest(GeneticInfo_t * info)\n{\n    int i;\t/* loop var */\n    int big;\t/* temporary holder to return result */\n\n    big = 0;\n    while (info->repeat[big] > 1) big++;\n    for (i = big + 1; i < info->popsize; i++) {\n\tif (STOREDD(info,i,info->numvars) >=\n            STOREDD(info,big,info->numvars) && info->repeat[i] <= 1) {\n\t    big = i;\n\t}\n    }\n    return(big);\n\n} /* end of largest */\n\n\n/**\n  @brief Generates a random number between 0 and the integer a.\n\n  @sideeffect None\n\n*/\nstatic int\nrand_int(\n  DdManager *dd,\n  int  a)\n{\n    return(Cudd_Random(dd) % (a+1));\n\n} /* end of rand_int */\n\n\n/**\n  @brief Hash function for the computed table.\n\n  @return the bucket number.\n\n  @sideeffect None\n\n*/\nstatic int\narray_hash(\n  void const * array,\n  int modulus,\n  void const * arg)\n{\n    int val = 0;\n    int i;\n    int const *intarray = (int const *) array;\n    int const numvars = (int const)(ptrint const) arg;\n\n    for (i = 0; i < numvars; i++) {\n\tval = val * 997 + intarray[i];\n    }\n\n    return(((val < 0) ? -val : val) % modulus);\n\n} /* end of array_hash */\n\n\n/**\n  @brief Comparison function for the computed table.\n\n  @return 0 if the two arrays are equal; 1 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\narray_compare(\n  void const * array1,\n  void const * array2,\n  void const * arg)\n{\n    int i;\n    int const *intarray1 = (int const *) array1;\n    int const *intarray2 = (int const *) array2;\n    int const numvars = (int const)(ptrint const) arg;\n\n    for (i = 0; i < numvars; i++) {\n\tif (intarray1[i] != intarray2[i]) return(1);\n    }\n    return(0);\n\n} /* end of array_compare */\n\n\n/**\n  @brief Returns the index of the fittest individual.\n\n  @sideeffect None\n\n*/\nstatic int\nfind_best(GeneticInfo_t * info)\n{\n    int i,small;\n\n    small = 0;\n    for (i = 1; i < info->popsize; i++) {\n\tif (STOREDD(info,i,info->numvars) < STOREDD(info,small,info->numvars)) {\n\t    small = i;\n\t}\n    }\n    return(small);\n\n} /* end of find_best */\n\n\n/**\n  @brief Returns the average fitness of the population.\n\n  @sideeffect None\n\n*/\n#ifdef DD_STATS\nstatic double\nfind_average_fitness(GeneticInfo_t * info)\n{\n    int i;\n    int total_fitness = 0;\n    double average_fitness;\n\n    for (i = 0; i < info->popsize; i++) {\n\ttotal_fitness += STOREDD(info,i,info->numvars);\n    }\n    average_fitness = (double) total_fitness / (double) info->popsize;\n    return(average_fitness);\n\n} /* end of find_average_fitness */\n#endif\n\n\n/**\n  @brief Performs the crossover between two parents.\n\n  @details Performs the crossover between two randomly chosen\n  parents, and creates two children, x1 and x2. Uses the Partially\n  Matched Crossover operator.\n\n  @sideeffect None\n\n*/\nstatic int\nPMX(\n  DdManager * dd,\n  int  maxvar,\n  GeneticInfo_t * info)\n{\n    int \tcut1,cut2;\t/* the two cut positions (random) */\n    int \tmom,dad;\t/* the two randomly chosen parents */\n    int\t\t*inv1;\t\t/* inverse permutations for repair algo */\n    int\t\t*inv2;\n    int \ti;\t\t/* loop vars */\n    int\t\tu,v;\t\t/* aux vars */\n\n    inv1 = ALLOC(int,maxvar);\n    if (inv1 == NULL) {\n\treturn(0);\n    }\n    inv2 = ALLOC(int,maxvar);\n    if (inv2 == NULL) {\n\tFREE(inv1);\n\treturn(0);\n    }\n\n    /* Choose two orders from the population using roulette wheel. */\n    if (!roulette(dd,&mom,&dad,info)) {\n\tFREE(inv1);\n\tFREE(inv2);\n\treturn(0);\n    }\n\n    /* Choose two random cut positions. A cut in position i means that\n    ** the cut immediately precedes position i.  If cut1 < cut2, we\n    ** exchange the middle of the two orderings; otherwise, we\n    ** exchange the beginnings and the ends.\n    */\n    cut1 = rand_int(dd,info->numvars-1);\n    do {\n\tcut2 = rand_int(dd,info->numvars-1);\n    } while (cut1 == cut2);\n\n#if 0\n    /* Print out the parents. */\n    (void) fprintf(dd->out,\n\t\t   \"Crossover of %d (mom) and %d (dad) between %d and %d\\n\",\n\t\t   mom,dad,cut1,cut2);\n    for (i = 0; i < info->numvars; i++) {\n\tif (i == cut1 || i == cut2) (void) fprintf(dd->out,\"|\");\n\t(void) fprintf(dd->out,\"%2d \",STOREDD(info,mom,i));\n    }\n    (void) fprintf(dd->out,\"\\n\");\n    for (i = 0; i < info->numvars; i++) {\n\tif (i == cut1 || i == cut2) (void) fprintf(dd->out,\"|\");\n\t(void) fprintf(dd->out,\"%2d \",STOREDD(info,dad,i));\n    }\n    (void) fprintf(dd->out,\"\\n\");\n#endif\n\n    /* Initialize the inverse permutations: -1 means yet undetermined. */\n    for (i = 0; i < maxvar; i++) {\n\tinv1[i] = -1;\n\tinv2[i] = -1;\n    }\n\n    /* Copy the portions whithin the cuts. */\n    for (i = cut1; i != cut2; i = (i == info->numvars-1) ? 0 : i+1) {\n\tSTOREDD(info,info->popsize,i) = STOREDD(info,dad,i);\n\tinv1[STOREDD(info,info->popsize,i)] = i;\n\tSTOREDD(info,info->popsize+1,i) = STOREDD(info,mom,i);\n\tinv2[STOREDD(info,info->popsize+1,i)] = i;\n    }\n\n    /* Now apply the repair algorithm outside the cuts. */\n    for (i = cut2; i != cut1; i = (i == info->numvars-1 ) ? 0 : i+1) {\n\tv = i;\n\tdo {\n\t    u = STOREDD(info,mom,v);\n\t    v = inv1[u];\n\t} while (v != -1);\n\tSTOREDD(info,info->popsize,i) = u;\n\tinv1[u] = i;\n\tv = i;\n\tdo {\n\t    u = STOREDD(info,dad,v);\n\t    v = inv2[u];\n\t} while (v != -1);\n\tSTOREDD(info,info->popsize+1,i) = u;\n\tinv2[u] = i;\n    }\n\n#if 0\n    /* Print the results of crossover. */\n    for (i = 0; i < info->numvars; i++) {\n\tif (i == cut1 || i == cut2) (void) fprintf(table->out,\"|\");\n\t(void) fprintf(table->out,\"%2d \",STOREDD(info,info->popsize,i));\n    }\n    (void) fprintf(table->out,\"\\n\");\n    for (i = 0; i < info->numvars; i++) {\n\tif (i == cut1 || i == cut2) (void) fprintf(table->out,\"|\");\n\t(void) fprintf(table->out,\"%2d \",STOREDD(info,info->popsize+1,i));\n    }\n    (void) fprintf(table->out,\"\\n\");\n#endif\n\n    FREE(inv1);\n    FREE(inv2);\n    return(1);\n\n} /* end of PMX */\n\n\n/**\n  @brief Selects two distinct parents with the roulette wheel method.\n\n  @sideeffect The indices of the selected parents are returned as side\n  effects.\n\n*/\nstatic int\nroulette(\n  DdManager * dd,\n  int * p1,\n  int * p2,\n  GeneticInfo_t * info)\n{\n    double *wheel;\n    double spin;\n    int i;\n\n    wheel = ALLOC(double,info->popsize);\n    if (wheel == NULL) {\n\treturn(0);\n    }\n\n    /* The fitness of an individual is the reciprocal of its size. */\n    wheel[0] = 1.0 / (double) STOREDD(info,0,info->numvars);\n\n    for (i = 1; i < info->popsize; i++) {\n\twheel[i] = wheel[i-1] + 1.0 / (double) STOREDD(info,i,info->numvars);\n    }\n\n    /* Get a random number between 0 and wheel[popsize-1] (that is,\n    ** the sum of all fitness values. 2147483561 is the largest number\n    ** returned by Cudd_Random.\n    */\n    spin = wheel[info->numvars-1] * (double) Cudd_Random(dd) / 2147483561.0;\n\n    /* Find the lucky element by scanning the wheel. */\n    for (i = 0; i < info->popsize; i++) {\n\tif (spin <= wheel[i]) break;\n    }\n    *p1 = i;\n\n    /* Repeat the process for the second parent, making sure it is\n    ** distinct from the first.\n    */\n    do {\n\tspin = wheel[info->popsize-1] * (double) Cudd_Random(dd) / 2147483561.0;\n\tfor (i = 0; i < info->popsize; i++) {\n\t    if (spin <= wheel[i]) break;\n\t}\n    } while (i == *p1);\n    *p2 = i;\n\n    FREE(wheel);\n    return(1);\n\n} /* end of roulette */\n"
  },
  {
    "path": "cudd/cudd/cuddGroup.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for group sifting.\n\n  @author Shipra Panda, Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* Constants for lazy sifting */\n#define\tDD_NORMAL_SIFT\t0\n#define\tDD_LAZY_SIFT\t1\n\n/* Constants for sifting up and down */\n#define\tDD_SIFT_DOWN\t0\n#define\tDD_SIFT_UP\t1\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\ntypedef int (*DD_CHKFP)(DdManager *, int, int);\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int ddTreeSiftingAux (DdManager *table, MtrNode *treenode, Cudd_ReorderingType method);\n#ifdef DD_STATS\nstatic int ddCountInternalMtrNodes (DdManager *table, MtrNode *treenode);\n#endif\nstatic int ddReorderChildren (DdManager *table, MtrNode *treenode, Cudd_ReorderingType method);\nstatic void ddFindNodeHiLo (DdManager *table, MtrNode *treenode, int *lower, int *upper);\nstatic int ddUniqueCompareGroup (void const *ptrX, void const *ptrY);\nstatic int ddGroupSifting (DdManager *table, int lower, int upper, DD_CHKFP checkFunction, int lazyFlag);\nstatic void ddCreateGroup (DdManager *table, int x, int y);\nstatic int ddGroupSiftingAux (DdManager *table, int x, int xLow, int xHigh, DD_CHKFP checkFunction, int lazyFlag);\nstatic int ddGroupSiftingUp (DdManager *table, int y, int xLow, DD_CHKFP checkFunction, Move **moves);\nstatic int ddGroupSiftingDown (DdManager *table, int x, int xHigh, DD_CHKFP checkFunction, Move **moves);\nstatic int ddGroupMove (DdManager *table, int x, int y, Move **moves);\nstatic int ddGroupMoveBackward (DdManager *table, int x, int y);\nstatic int ddGroupSiftingBackward (DdManager *table, Move *moves, int size, int upFlag, int lazyFlag);\nstatic void ddMergeGroups (DdManager *table, MtrNode *treenode, int low, int high);\nstatic void ddDissolveGroup (DdManager *table, int x, int y);\nstatic int ddNoCheck (DdManager *table, int x, int y);\nstatic int ddSecDiffCheck (DdManager *table, int x, int y);\nstatic int ddExtSymmCheck (DdManager *table, int x, int y);\nstatic int ddVarGroupCheck (DdManager * table, int x, int y);\nstatic int ddSetVarHandled (DdManager *dd, int index);\nstatic int ddResetVarHandled (DdManager *dd, int index);\nstatic int ddIsVarHandled (DdManager *dd, int index);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Creates a new variable group.\n\n  @details The group starts at variable low and contains size\n  variables. The parameter low is the index of the first variable. If\n  the variable already exists, its current position in the order is\n  known to the manager. If the variable does not exist yet, the\n  position is assumed to be the same as the index.  The group tree is\n  created if it does not exist yet.\n\n  @return a pointer to the group if successful; NULL otherwise.\n\n  @sideeffect The variable tree is changed.\n\n  @see Cudd_MakeZddTreeNode\n\n*/\nMtrNode *\nCudd_MakeTreeNode(\n  DdManager * dd /**< manager */,\n  unsigned int  low /**< index of the first group variable */,\n  unsigned int  size /**< number of variables in the group */,\n  unsigned int  type /**< MTR_DEFAULT or MTR_FIXED */)\n{\n    MtrNode *group;\n    MtrNode *tree;\n    unsigned int level;\n\n    /* If the variable does not exist yet, the position is assumed to be\n    ** the same as the index. Therefore, applications that rely on\n    ** Cudd_bddNewVarAtLevel or Cudd_addNewVarAtLevel to create new\n    ** variables have to create the variables before they group them.\n    */\n    level = (low < (unsigned int) dd->size) ? (unsigned int) dd->perm[low] : low;\n\n    if (level + size - 1> (int) MTR_MAXHIGH)\n\treturn(NULL);\n\n    /* If the tree does not exist yet, create it. */\n    tree = dd->tree;\n    if (tree == NULL) {\n\tdd->tree = tree = Mtr_InitGroupTree(0, dd->size);\n\tif (tree == NULL)\n\t    return(NULL);\n\ttree->index = dd->size == 0 ? 0 : dd->invperm[0];\n    }\n\n    /* Extend the upper bound of the tree if necessary. This allows the\n    ** application to create groups even before the variables are created.\n    */\n    tree->size = ddMax(tree->size, ddMax(level + size, (unsigned) dd->size));\n\n    /* Create the group. */\n    group = Mtr_MakeGroup(tree, level, size, type);\n    if (group == NULL)\n\treturn(NULL);\n\n    /* Initialize the index field to the index of the variable currently\n    ** in position low. This field will be updated by the reordering\n    ** procedure to provide a handle to the group once it has been moved.\n    */\n    group->index = (MtrHalfWord) low;\n\n    return(group);\n\n} /* end of Cudd_MakeTreeNode */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Tree sifting algorithm.\n\n  @details Assumes that a tree representing a group hierarchy is\n  passed as a parameter.  It then reorders each group in postorder\n  fashion by calling ddTreeSiftingAux.  Assumes that no dead nodes are\n  present.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddTreeSifting(\n  DdManager * table /**< %DD table */,\n  Cudd_ReorderingType method /**< reordering method for the groups of leaves */)\n{\n    int i;\n    int nvars;\n    int result;\n    int tempTree;\n\n    /* If no tree is provided we create a temporary one in which all\n    ** variables are in a single group. After reordering this tree is\n    ** destroyed.\n    */\n    tempTree = table->tree == NULL;\n    if (tempTree) {\n\ttable->tree = Mtr_InitGroupTree(0,table->size);\n\ttable->tree->index = table->invperm[0];\n    }\n    nvars = table->size;\n\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0 && !tempTree)\n        (void) fprintf(table->out,\"cuddTreeSifting:\");\n    Mtr_PrintGroups(table->tree,table->enableExtraDebug <= 0);\n#endif\n\n#ifdef DD_STATS\n    table->extsymmcalls = 0;\n    table->extsymm = 0;\n    table->secdiffcalls = 0;\n    table->secdiff = 0;\n    table->secdiffmisfire = 0;\n\n    (void) fprintf(table->out,\"\\n\");\n    if (!tempTree)\n\t(void) fprintf(table->out,\"#:IM_NODES  %8d: group tree nodes\\n\",\n\t\t       ddCountInternalMtrNodes(table,table->tree));\n#endif\n\n    /* Initialize the group of each subtable to itself. Initially\n    ** there are no groups. Groups are created according to the tree\n    ** structure in postorder fashion.\n    */\n    for (i = 0; i < nvars; i++)\n\ttable->subtables[i].next = i;\n\n\n    /* Reorder. */\n    result = ddTreeSiftingAux(table, table->tree, method);\n\n#ifdef DD_STATS\t\t/* print stats */\n    if (!tempTree && method == CUDD_REORDER_GROUP_SIFT &&\n\t(table->groupcheck == CUDD_GROUP_CHECK7 ||\n\t table->groupcheck == CUDD_GROUP_CHECK5)) {\n\t(void) fprintf(table->out,\"\\nextsymmcalls = %d\\n\",table->extsymmcalls);\n\t(void) fprintf(table->out,\"extsymm = %d\",table->extsymm);\n    }\n    if (!tempTree && method == CUDD_REORDER_GROUP_SIFT &&\n\ttable->groupcheck == CUDD_GROUP_CHECK7) {\n\t(void) fprintf(table->out,\"\\nsecdiffcalls = %d\\n\",table->secdiffcalls);\n\t(void) fprintf(table->out,\"secdiff = %d\\n\",table->secdiff);\n\t(void) fprintf(table->out,\"secdiffmisfire = %d\",table->secdiffmisfire);\n    }\n#endif\n\n    if (tempTree)\n\tCudd_FreeTree(table);\n    else\n      Mtr_ReorderGroups(table->tree, table->perm);\n\n    return(result);\n\n} /* end of cuddTreeSifting */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Visits the group tree and reorders each group.\n\n  @details Recursively visits the group tree and reorders each\n  group in postorder fashion.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddTreeSiftingAux(\n  DdManager * table,\n  MtrNode * treenode,\n  Cudd_ReorderingType method)\n{\n    MtrNode  *auxnode;\n    int res;\n    Cudd_AggregationType saveCheck;\n\n#ifdef DD_DEBUG\n    Mtr_PrintGroups(treenode,1);\n#endif\n\n    auxnode = treenode;\n    while (auxnode != NULL) {\n\tif (auxnode->child != NULL) {\n\t    if (!ddTreeSiftingAux(table, auxnode->child, method))\n\t\treturn(0);\n\t    saveCheck = table->groupcheck;\n\t    table->groupcheck = CUDD_NO_CHECK;\n\t    if (method != CUDD_REORDER_LAZY_SIFT)\n\t      res = ddReorderChildren(table, auxnode, CUDD_REORDER_GROUP_SIFT);\n\t    else\n\t      res = ddReorderChildren(table, auxnode, CUDD_REORDER_LAZY_SIFT);\n\t    table->groupcheck = saveCheck;\n\n\t    if (res == 0)\n\t\treturn(0);\n\t} else if (auxnode->size > 1) {\n\t    if (!ddReorderChildren(table, auxnode, method))\n\t\treturn(0);\n\t}\n\tauxnode = auxnode->younger;\n    }\n\n    return(1);\n\n} /* end of ddTreeSiftingAux */\n\n\n#ifdef DD_STATS\n/**\n  @brief Counts the number of internal nodes of the group tree.\n\n  @return the count.\n\n  @sideeffect None\n\n*/\nstatic int\nddCountInternalMtrNodes(\n  DdManager * table,\n  MtrNode * treenode)\n{\n    MtrNode *auxnode;\n    int     count,nodeCount;\n\n\n    nodeCount = 0;\n    auxnode = treenode;\n    while (auxnode != NULL) {\n\tif (!(MTR_TEST(auxnode,MTR_TERMINAL))) {\n\t    nodeCount++;\n\t    count = ddCountInternalMtrNodes(table,auxnode->child);\n\t    nodeCount += count;\n\t}\n\tauxnode = auxnode->younger;\n    }\n\n    return(nodeCount);\n\n} /* end of ddCountInternalMtrNodes */\n#endif\n\n\n/**\n  @brief Reorders the children of a group tree node according to\n  the options.\n\n  @details After reordering puts all the variables in the group and/or\n  its descendents in a single group. This allows hierarchical\n  reordering.  If the variables in the group do not exist yet, simply\n  does nothing.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddReorderChildren(\n  DdManager * table,\n  MtrNode * treenode,\n  Cudd_ReorderingType method)\n{\n    int lower;\n    int upper = 0;\n    int result;\n    unsigned int initialSize;\n\n    ddFindNodeHiLo(table,treenode,&lower,&upper);\n    /* If upper == -1 these variables do not exist yet. */\n    if (upper == -1)\n\treturn(1);\n\n    if (treenode->flags == MTR_FIXED) {\n\tresult = 1;\n    } else {\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\" \");\n#endif\n\tswitch (method) {\n\tcase CUDD_REORDER_RANDOM:\n\tcase CUDD_REORDER_RANDOM_PIVOT:\n\t    result = cuddSwapping(table,lower,upper,method);\n\t    break;\n\tcase CUDD_REORDER_SIFT:\n\t    result = cuddSifting(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_SIFT_CONVERGE:\n\t    do {\n\t\tinitialSize = table->keys - table->isolated;\n\t\tresult = cuddSifting(table,lower,upper);\n\t\tif (initialSize <= table->keys - table->isolated)\n\t\t    break;\n#ifdef DD_STATS\n\t\telse\n\t\t    (void) fprintf(table->out,\"\\n\");\n#endif\n\t    } while (result != 0);\n\t    break;\n\tcase CUDD_REORDER_SYMM_SIFT:\n\t    result = cuddSymmSifting(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_SYMM_SIFT_CONV:\n\t    result = cuddSymmSiftingConv(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_GROUP_SIFT:\n\t    if (table->groupcheck == CUDD_NO_CHECK) {\n\t\tresult = ddGroupSifting(table,lower,upper,ddNoCheck,\n\t\t\t\t\tDD_NORMAL_SIFT);\n\t    } else if (table->groupcheck == CUDD_GROUP_CHECK5) {\n\t\tresult = ddGroupSifting(table,lower,upper,ddExtSymmCheck,\n\t\t\t\t\tDD_NORMAL_SIFT);\n\t    } else if (table->groupcheck == CUDD_GROUP_CHECK7) {\n\t\tresult = ddGroupSifting(table,lower,upper,ddExtSymmCheck,\n\t\t\t\t\tDD_NORMAL_SIFT);\n\t    } else {\n\t\t(void) fprintf(table->err,\n\t\t\t       \"Unknown group ckecking method\\n\");\n\t\tresult = 0;\n\t    }\n\t    break;\n\tcase CUDD_REORDER_GROUP_SIFT_CONV:\n\t    do {\n\t\tinitialSize = table->keys - table->isolated;\n\t\tif (table->groupcheck == CUDD_NO_CHECK) {\n\t\t    (void) ddGroupSifting(table,lower,upper,ddNoCheck,\n                                          DD_NORMAL_SIFT);\n\t\t} else if (table->groupcheck == CUDD_GROUP_CHECK5) {\n\t\t    (void) ddGroupSifting(table,lower,upper,ddExtSymmCheck,\n                                          DD_NORMAL_SIFT);\n\t\t} else if (table->groupcheck == CUDD_GROUP_CHECK7) {\n\t\t    (void) ddGroupSifting(table,lower,upper,ddExtSymmCheck,\n                                          DD_NORMAL_SIFT);\n\t\t} else {\n\t\t    (void) fprintf(table->err,\n\t\t\t\t   \"Unknown group ckecking method\\n\");\n\t\t}\n#ifdef DD_STATS\n\t\t(void) fprintf(table->out,\"\\n\");\n#endif\n\t\tresult = cuddWindowReorder(table,lower,upper,\n\t\t\t\t\t   CUDD_REORDER_WINDOW4);\n\t\tif (initialSize <= table->keys - table->isolated)\n\t\t    break;\n#ifdef DD_STATS\n\t\telse\n\t\t    (void) fprintf(table->out,\"\\n\");\n#endif\n\t    } while (result != 0);\n\t    break;\n\tcase CUDD_REORDER_WINDOW2:\n\tcase CUDD_REORDER_WINDOW3:\n\tcase CUDD_REORDER_WINDOW4:\n\tcase CUDD_REORDER_WINDOW2_CONV:\n\tcase CUDD_REORDER_WINDOW3_CONV:\n\tcase CUDD_REORDER_WINDOW4_CONV:\n\t    result = cuddWindowReorder(table,lower,upper,method);\n\t    break;\n\tcase CUDD_REORDER_ANNEALING:\n\t    result = cuddAnnealing(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_GENETIC:\n\t    result = cuddGa(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_LINEAR:\n\t    result = cuddLinearAndSifting(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_LINEAR_CONVERGE:\n\t    do {\n\t\tinitialSize = table->keys - table->isolated;\n\t\tresult = cuddLinearAndSifting(table,lower,upper);\n\t\tif (initialSize <= table->keys - table->isolated)\n\t\t    break;\n#ifdef DD_STATS\n\t\telse\n\t\t    (void) fprintf(table->out,\"\\n\");\n#endif\n\t    } while (result != 0);\n\t    break;\n\tcase CUDD_REORDER_EXACT:\n\t    result = cuddExact(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_LAZY_SIFT:\n\t    result = ddGroupSifting(table,lower,upper,ddVarGroupCheck,\n\t\t\t\t    DD_LAZY_SIFT);\n\t    break;\n\tdefault:\n\t    return(0);\n\t}\n    }\n\n    /* Create a single group for all the variables that were sifted,\n    ** so that they will be treated as a single block by successive\n    ** invocations of ddGroupSifting.\n    */\n    ddMergeGroups(table,treenode,lower,upper);\n\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0)\n        (void) fprintf(table->out,\"ddReorderChildren:\");\n#endif\n\n    return(result);\n\n} /* end of ddReorderChildren */\n\n\n/**\n  @brief Finds the lower and upper bounds of the group represented\n  by treenode.\n\n  @details From the index and size fields we need to derive the\n  current positions, and find maximum and minimum.\n\n  @sideeffect The bounds are returned as side effects.\n\n*/\nstatic void\nddFindNodeHiLo(\n  DdManager * table,\n  MtrNode * treenode,\n  int * lower,\n  int * upper)\n{\n    int low;\n    int high;\n\n    /* Check whether no variables in this group already exist.\n    ** If so, return immediately. The calling procedure will know from\n    ** the values of upper that no reordering is needed.\n    */\n    if ((int) treenode->low >= table->size) {\n\t*lower = table->size;\n\t*upper = -1;\n\treturn;\n    }\n\n    *lower = low = (unsigned int) table->perm[treenode->index];\n    high = (int) (low + treenode->size - 1);\n\n    if (high >= table->size) {\n\t/* This is the case of a partially existing group. The aim is to\n\t** reorder as many variables as safely possible.  If the tree\n\t** node is terminal, we just reorder the subset of the group\n\t** that is currently in existence.  If the group has\n\t** subgroups, then we only reorder those subgroups that are\n\t** fully instantiated.  This way we avoid breaking up a group.\n\t*/\n\tMtrNode *auxnode = treenode->child;\n\tif (auxnode == NULL) {\n\t    *upper = (unsigned int) table->size - 1;\n\t} else {\n\t    /* Search the subgroup that strands the table->size line.\n\t    ** If the first group starts at 0 and goes past table->size\n\t    ** upper will get -1, thus correctly signaling that no reordering\n\t    ** should take place.\n\t    */\n\t    while (auxnode != NULL) {\n\t\tint thisLower = table->perm[auxnode->low];\n\t\tint thisUpper = thisLower + auxnode->size - 1;\n\t\tif (thisUpper >= table->size && thisLower < table->size)\n\t\t    *upper = (unsigned int) thisLower - 1;\n\t\tauxnode = auxnode->younger;\n\t    }\n\t}\n    } else {\n\t/* Normal case: All the variables of the group exist. */\n\t*upper = (unsigned int) high;\n    }\n\n#ifdef DD_DEBUG\n    /* Make sure that all variables in group are contiguous. */\n    assert(treenode->size >= (MtrHalfWord) (*upper - *lower + 1));\n#endif\n\n    return;\n\n} /* end of ddFindNodeHiLo */\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Comparison function used by qsort to order the variables\n  according to the number of keys in the subtables.\n\n  @return the difference in number of keys between the two variables\n  being compared.\n\n  @sideeffect None\n\n*/\nstatic int\nddUniqueCompareGroup(\n  void const * ptrX,\n  void const * ptrY)\n{\n    IndexKey const * pX = (IndexKey const *) ptrX;\n    IndexKey const * pY = (IndexKey const *) ptrY;\n#if 0\n    if (pY->keys == pX->keys) {\n\treturn(pX->index - pY->index);\n    }\n#endif\n    return(pY->keys - pX->keys);\n\n} /* end of ddUniqueCompareGroup */\n\n\n/**\n  @brief Sifts from treenode->low to treenode->high.\n\n  @details If croupcheck == CUDD_GROUP_CHECK7, it checks for group\n  creation at the end of the initial sifting. If a group is created,\n  it is then sifted again. After sifting one variable, the group that\n  contains it is dissolved.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddGroupSifting(\n  DdManager * table,\n  int  lower,\n  int  upper,\n  DD_CHKFP checkFunction,\n  int lazyFlag)\n{\n    IndexKey\t*var;\n    int\t\ti,j,x,xInit;\n    int\t\tnvars;\n    int\t\tclasses;\n    int\t\tresult;\n    int\t\t*sifted;\n    int\t\tmerged;\n    int\t\tdissolve;\n#ifdef DD_STATS\n    unsigned\tpreviousSize;\n#endif\n    int\t\txindex;\n\n    nvars = table->size;\n\n    /* Order variables to sift. */\n    sifted = NULL;\n    var = ALLOC(IndexKey,nvars);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto ddGroupSiftingOutOfMem;\n    }\n    sifted = ALLOC(int,nvars);\n    if (sifted == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto ddGroupSiftingOutOfMem;\n    }\n\n    /* Here we consider only one representative for each group. */\n    for (i = 0, classes = 0; i < nvars; i++) {\n\tsifted[i] = 0;\n\tx = table->perm[i];\n\tif ((unsigned) x >= table->subtables[x].next) {\n\t    var[classes].index = i;\n\t    var[classes].keys = table->subtables[x].keys;\n\t    classes++;\n\t}\n    }\n\n    util_qsort(var, classes, sizeof(IndexKey), ddUniqueCompareGroup);\n\n    if (lazyFlag) {\n\tfor (i = 0; i < nvars; i ++) {\n\t    ddResetVarHandled(table, i);\n\t}\n    }\n\n    /* Now sift. */\n    for (i = 0; i < ddMin(table->siftMaxVar,classes); i++) {\n\tif (table->ddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime + table->reordTime\n            > table->timeLimit) {\n            table->autoDyn = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDyn = 0; /* prevent further reordering */\n            break;\n        }\n\txindex = var[i].index;\n\tif (sifted[xindex] == 1) /* variable already sifted as part of group */\n\t    continue;\n\tx = table->perm[xindex]; /* find current level of this variable */\n\n\tif (x < lower || x > upper || table->subtables[x].bindVar == 1)\n\t    continue;\n#ifdef DD_STATS\n\tpreviousSize = table->keys - table->isolated;\n#endif\n#ifdef DD_DEBUG\n\t/* x is bottom of group */\n\tassert((unsigned) x >= table->subtables[x].next);\n#endif\n\tif ((unsigned) x == table->subtables[x].next) {\n\t    dissolve = 1;\n\t    result = ddGroupSiftingAux(table,x,lower,upper,checkFunction,\n\t\t\t\t\tlazyFlag);\n\t} else {\n\t    dissolve = 0;\n\t    result = ddGroupSiftingAux(table,x,lower,upper,ddNoCheck,lazyFlag);\n\t}\n\tif (!result) goto ddGroupSiftingOutOfMem;\n\n\t/* check for aggregation */\n\tmerged = 0;\n\tif (lazyFlag == 0 && table->groupcheck == CUDD_GROUP_CHECK7) {\n\t    x = table->perm[xindex]; /* find current level */\n\t    if ((unsigned) x == table->subtables[x].next) { /* not part of a group */\n\t\tif (x != upper && sifted[table->invperm[x+1]] == 0 &&\n\t\t(unsigned) x+1 == table->subtables[x+1].next) {\n\t\t    if (ddSecDiffCheck(table,x,x+1)) {\n\t\t\tmerged =1;\n\t\t\tddCreateGroup(table,x,x+1);\n\t\t    }\n\t\t}\n\t\tif (x != lower && sifted[table->invperm[x-1]] == 0 &&\n\t\t(unsigned) x-1 == table->subtables[x-1].next) {\n\t\t    if (ddSecDiffCheck(table,x-1,x)) {\n\t\t\tmerged =1;\n\t\t\tddCreateGroup(table,x-1,x);\n\t\t    }\n\t\t}\n\t    }\n\t}\n\n\tif (merged) { /* a group was created */\n\t    /* move x to bottom of group */\n\t    while ((unsigned) x < table->subtables[x].next)\n\t\tx = table->subtables[x].next;\n\t    /* sift */\n\t    result = ddGroupSiftingAux(table,x,lower,upper,ddNoCheck,lazyFlag);\n\t    if (!result) goto ddGroupSiftingOutOfMem;\n#ifdef DD_STATS\n\t    if (table->keys < previousSize + table->isolated) {\n\t\t(void) fprintf(table->out,\"_\");\n\t    } else if (table->keys > previousSize + table->isolated) {\n\t\t(void) fprintf(table->out,\"^\");\n\t    } else {\n\t\t(void) fprintf(table->out,\"*\");\n\t    }\n\t    fflush(table->out);\n\t} else {\n\t    if (table->keys < previousSize + table->isolated) {\n\t\t(void) fprintf(table->out,\"-\");\n\t    } else if (table->keys > previousSize + table->isolated) {\n\t\t(void) fprintf(table->out,\"+\");\n\t    } else {\n\t\t(void) fprintf(table->out,\"=\");\n\t    }\n\t    fflush(table->out);\n#endif\n\t}\n\n\t/* Mark variables in the group just sifted. */\n\tx = table->perm[xindex];\n\tif ((unsigned) x != table->subtables[x].next) {\n\t    xInit = x;\n\t    do {\n\t\tj = table->invperm[x];\n\t\tsifted[j] = 1;\n\t\tx = table->subtables[x].next;\n\t    } while (x != xInit);\n\n\t    /* Dissolve the group if it was created. */\n\t    if (lazyFlag == 0 && dissolve) {\n\t\tdo {\n\t\t    j = table->subtables[x].next;\n\t\t    table->subtables[x].next = x;\n\t\t    x = j;\n\t\t} while (x != xInit);\n\t    }\n\t}\n\n#ifdef DD_DEBUG\n\tif (table->enableExtraDebug > 0)\n            (void) fprintf(table->out,\"ddGroupSifting:\");\n#endif\n\n        if (lazyFlag) ddSetVarHandled(table, xindex);\n    } /* for */\n\n    FREE(sifted);\n    FREE(var);\n\n    return(1);\n\nddGroupSiftingOutOfMem:\n    if (var != NULL)\tFREE(var);\n    if (sifted != NULL)\tFREE(sifted);\n\n    return(0);\n\n} /* end of ddGroupSifting */\n\n\n/**\n  @brief Creates a group encompassing variables from x to y in the\n  %DD table.\n\n  @details In the current implementation it must be y == x+1.\n\n  @sideeffect None\n\n*/\nstatic void\nddCreateGroup(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    int  gybot;\n\n#ifdef DD_DEBUG\n    assert(y == x+1);\n#endif\n\n    /* Find bottom of second group. */\n    gybot = y;\n    while ((unsigned) gybot < table->subtables[gybot].next)\n\tgybot = table->subtables[gybot].next;\n\n    /* Link groups. */\n    table->subtables[x].next = y;\n    table->subtables[gybot].next = x;\n\n    return;\n\n} /* ddCreateGroup */\n\n\n/**\n  @brief Sifts one variable up and down until it has taken all\n  positions. Checks for aggregation.\n\n  @details There may be at most two sweeps, even if the group grows.\n  Assumes that x is either an isolated variable, or it is the bottom\n  of a group. All groups may not have been found. The variable being\n  moved is returned to the best position seen during sifting.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddGroupSiftingAux(\n  DdManager * table,\n  int  x,\n  int  xLow,\n  int  xHigh,\n  DD_CHKFP checkFunction,\n  int lazyFlag)\n{\n    Move *move;\n    Move *moves;\t/* list of moves */\n    int  initialSize;\n    int  result;\n    int  y;\n    int  topbot;\n\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0)\n        (void) fprintf(table->out,\n                       \"ddGroupSiftingAux from %d to %d\\n\",xLow,xHigh);\n    assert((unsigned) x >= table->subtables[x].next); /* x is bottom of group */\n#endif\n\n    table->originalSize = (table->keys - table->isolated);\n    initialSize = (int) table->originalSize;\n    moves = NULL;\n\n    /* If we have a singleton, we check for aggregation in both\n    ** directions before we sift.\n    */\n    if ((unsigned) x == table->subtables[x].next) {\n\t/* Will go down first, unless x == xHigh:\n\t** Look for aggregation above x.\n\t*/\n\tfor (y = x; y > xLow; y--) {\n\t    if (!checkFunction(table,y-1,y))\n\t\tbreak;\n\t    topbot = table->subtables[y-1].next; /* find top of y-1's group */\n\t    table->subtables[y-1].next = y;\n\t    table->subtables[x].next = topbot; /* x is bottom of group so its */\n\t\t\t\t\t       /* next is top of y-1's group */\n\t    y = topbot + 1; /* add 1 for y--; new y is top of group */\n\t}\n\t/* Will go up first unless x == xlow:\n\t** Look for aggregation below x.\n\t*/\n\tfor (y = x; y < xHigh; y++) {\n\t    if (!checkFunction(table,y,y+1))\n\t\tbreak;\n\t    /* find bottom of y+1's group */\n\t    topbot = y + 1;\n\t    while ((unsigned) topbot < table->subtables[topbot].next) {\n\t\ttopbot = table->subtables[topbot].next;\n\t    }\n\t    table->subtables[topbot].next = table->subtables[y].next;\n\t    table->subtables[y].next = y + 1;\n\t    y = topbot - 1; /* subtract 1 for y++; new y is bottom of group */\n\t}\n    }\n\n    /* Now x may be in the middle of a group.\n    ** Find bottom of x's group.\n    */\n    while ((unsigned) x < table->subtables[x].next)\n\tx = table->subtables[x].next;\n\n    if (x == xLow) { /* Sift down */\n#ifdef DD_DEBUG\n\t/* x must be a singleton */\n\tassert((unsigned) x == table->subtables[x].next);\n#endif\n\tif (x == xHigh) return(1);\t/* just one variable */\n\n\tif (!ddGroupSiftingDown(table,x,xHigh,checkFunction,&moves))\n\t    goto ddGroupSiftingAuxOutOfMem;\n\t/* at this point x == xHigh, unless early term */\n\n\t/* move backward and stop at best position */\n\tresult = ddGroupSiftingBackward(table,moves,initialSize,\n\t\t\t\t\tDD_SIFT_DOWN,lazyFlag);\n#ifdef DD_DEBUG\n\tassert(table->keys - table->isolated <= (unsigned) initialSize);\n#endif\n\tif (!result) goto ddGroupSiftingAuxOutOfMem;\n\n    } else if (cuddNextHigh(table,x) > xHigh) { /* Sift up */\n#ifdef DD_DEBUG\n\t/* x is bottom of group */\n\tassert((unsigned) x >= table->subtables[x].next);\n#endif\n\t/* Find top of x's group */\n\tx = table->subtables[x].next;\n\n\tif (!ddGroupSiftingUp(table,x,xLow,checkFunction,&moves))\n\t    goto ddGroupSiftingAuxOutOfMem;\n\t/* at this point x == xLow, unless early term */\n\n\t/* move backward and stop at best position */\n\tresult = ddGroupSiftingBackward(table,moves,initialSize,\n\t\t\t\t\tDD_SIFT_UP,lazyFlag);\n#ifdef DD_DEBUG\n\tassert(table->keys - table->isolated <= (unsigned) initialSize);\n#endif\n\tif (!result) goto ddGroupSiftingAuxOutOfMem;\n\n    } else if (x - xLow > xHigh - x) { /* must go down first: shorter */\n\tif (!ddGroupSiftingDown(table,x,xHigh,checkFunction,&moves))\n\t    goto ddGroupSiftingAuxOutOfMem;\n\t/* at this point x == xHigh, unless early term */\n\n\t/* Find top of group */\n\tif (moves) {\n\t    x = moves->y;\n\t}\n\twhile ((unsigned) x < table->subtables[x].next)\n\t    x = table->subtables[x].next;\n\tx = table->subtables[x].next;\n#ifdef DD_DEBUG\n\t/* x should be the top of a group */\n\tassert((unsigned) x <= table->subtables[x].next);\n#endif\n\n\tif (!ddGroupSiftingUp(table,x,xLow,checkFunction,&moves))\n\t    goto ddGroupSiftingAuxOutOfMem;\n\n\t/* move backward and stop at best position */\n\tresult = ddGroupSiftingBackward(table,moves,initialSize,\n\t\t\t\t\tDD_SIFT_UP,lazyFlag);\n#ifdef DD_DEBUG\n\tassert(table->keys - table->isolated <= (unsigned) initialSize);\n#endif\n\tif (!result) goto ddGroupSiftingAuxOutOfMem;\n\n    } else { /* moving up first: shorter */\n\t/* Find top of x's group */\n\tx = table->subtables[x].next;\n\n\tif (!ddGroupSiftingUp(table,x,xLow,checkFunction,&moves))\n\t    goto ddGroupSiftingAuxOutOfMem;\n\t/* at this point x == xHigh, unless early term */\n\n\tif (moves) {\n\t    x = moves->x;\n\t}\n\twhile ((unsigned) x < table->subtables[x].next)\n\t    x = table->subtables[x].next;\n#ifdef DD_DEBUG\n\t/* x is bottom of a group */\n\tassert((unsigned) x >= table->subtables[x].next);\n#endif\n\n\tif (!ddGroupSiftingDown(table,x,xHigh,checkFunction,&moves))\n\t    goto ddGroupSiftingAuxOutOfMem;\n\n\t/* move backward and stop at best position */\n\tresult = ddGroupSiftingBackward(table,moves,initialSize,\n\t\t\t\t\tDD_SIFT_DOWN,lazyFlag);\n#ifdef DD_DEBUG\n\tassert(table->keys - table->isolated <= (unsigned) initialSize);\n#endif\n\tif (!result) goto ddGroupSiftingAuxOutOfMem;\n    }\n\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n\n    return(1);\n\nddGroupSiftingAuxOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n\n    return(0);\n\n} /* end of ddGroupSiftingAux */\n\n\n/**\n  @brief Sifts up a variable until either it reaches position xLow\n  or the size of the %DD heap increases too much.\n\n  @details Assumes that y is the top of a group (or a singleton).\n  Checks y for aggregation to the adjacent variables. Records all the\n  moves that are appended to the list of moves received as input and\n  returned as a side effect.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddGroupSiftingUp(\n  DdManager * table,\n  int  y,\n  int  xLow,\n  DD_CHKFP checkFunction,\n  Move ** moves)\n{\n    Move *move;\n    int  x;\n    int  size;\n    int  i;\n    int  gxtop,gybot;\n    int  limitSize;\n    int  xindex, yindex;\n    int  zindex;\n    int  z;\n    unsigned int isolated;\n    int  L;\t/* lower bound on DD size */\n#ifdef DD_DEBUG\n    int  checkL;\n#endif\n\n    yindex = table->invperm[y];\n\n    /* Initialize the lower bound.\n    ** The part of the DD below the bottom of y's group will not change.\n    ** The part of the DD above y that does not interact with any\n    ** variable of y's group will not change.\n    ** The rest may vanish in the best case, except for\n    ** the nodes at level xLow, which will not vanish, regardless.\n    ** What we use here is not really a lower bound, because we ignore\n    ** the interactions with all variables except y.\n    */\n    limitSize = L = (int) (table->keys - table->isolated);\n    gybot = y;\n    while ((unsigned) gybot < table->subtables[gybot].next)\n\tgybot = table->subtables[gybot].next;\n    for (z = xLow + 1; z <= gybot; z++) {\n\tzindex = table->invperm[z];\n\tif (zindex == yindex || cuddTestInteract(table,zindex,yindex)) {\n\t    isolated = table->vars[zindex]->ref == 1;\n\t    L -= table->subtables[z].keys - isolated;\n\t}\n    }\n\n    x = cuddNextLow(table,y);\n    while (x >= xLow && L <= limitSize) {\n#ifdef DD_DEBUG\n\tgybot = y;\n\twhile ((unsigned) gybot < table->subtables[gybot].next)\n\t    gybot = table->subtables[gybot].next;\n\tcheckL = table->keys - table->isolated;\n\tfor (z = xLow + 1; z <= gybot; z++) {\n\t    zindex = table->invperm[z];\n\t    if (zindex == yindex || cuddTestInteract(table,zindex,yindex)) {\n\t\tisolated = table->vars[zindex]->ref == 1;\n\t\tcheckL -= table->subtables[z].keys - isolated;\n\t    }\n\t}\n\tif (table->enableExtraDebug > 0 && L != checkL) {\n\t    (void) fprintf(table->out,\n\t\t\t   \"Inaccurate lower bound: L = %d checkL = %d\\n\",\n\t\t\t   L, checkL);\n\t}\n#endif\n\tgxtop = table->subtables[x].next;\n\tif (checkFunction(table,x,y)) {\n\t    /* Group found, attach groups */\n\t    table->subtables[x].next = y;\n\t    i = table->subtables[y].next;\n\t    while (table->subtables[i].next != (unsigned) y)\n\t\ti = table->subtables[i].next;\n\t    table->subtables[i].next = gxtop;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddGroupSiftingUpOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->flags = MTR_NEWNODE;\n\t    move->size = (int) (table->keys - table->isolated);\n\t    move->next = *moves;\n\t    *moves = move;\n\t} else if (table->subtables[x].next == (unsigned) x &&\n\t\t   table->subtables[y].next == (unsigned) y) {\n\t    /* x and y are self groups */\n\t    xindex = table->invperm[x];\n\t    size = cuddSwapInPlace(table,x,y);\n#ifdef DD_DEBUG\n\t    assert(table->subtables[x].next == (unsigned) x);\n\t    assert(table->subtables[y].next == (unsigned) y);\n#endif\n\t    if (size == 0) goto ddGroupSiftingUpOutOfMem;\n\t    /* Update the lower bound. */\n\t    if (cuddTestInteract(table,xindex,yindex)) {\n\t\tisolated = table->vars[xindex]->ref == 1;\n\t\tL += table->subtables[y].keys - isolated;\n\t    }\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddGroupSiftingUpOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->flags = MTR_DEFAULT;\n\t    move->size = size;\n\t    move->next = *moves;\n\t    *moves = move;\n\n#ifdef DD_DEBUG\n\t    if (table->enableExtraDebug > 0)\n                (void) fprintf(table->out,\n                               \"ddGroupSiftingUp (2 single groups):\\n\");\n#endif\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(1);\n\t    if (size < limitSize) limitSize = size;\n\t} else { /* Group move */\n\t    size = ddGroupMove(table,x,y,moves);\n\t    if (size == 0) goto ddGroupSiftingUpOutOfMem;\n\t    /* Update the lower bound. */\n\t    z = (*moves)->y;\n\t    do {\n\t\tzindex = table->invperm[z];\n\t\tif (cuddTestInteract(table,zindex,yindex)) {\n\t\t    isolated = table->vars[zindex]->ref == 1;\n\t\t    L += table->subtables[z].keys - isolated;\n\t\t}\n\t\tz = table->subtables[z].next;\n\t    } while (z != (int) (*moves)->y);\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(1);\n\t    if (size < limitSize) limitSize = size;\n\t}\n\ty = gxtop;\n\tx = cuddNextLow(table,y);\n    }\n\n    return(1);\n\nddGroupSiftingUpOutOfMem:\n    while (*moves != NULL) {\n\tmove = (*moves)->next;\n\tcuddDeallocMove(table, *moves);\n\t*moves = move;\n    }\n    return(0);\n\n} /* end of ddGroupSiftingUp */\n\n\n/**\n  @brief Sifts down a variable until it reaches position xHigh.\n\n  @details Assumes that x is the bottom of a group (or a singleton).\n  Records all the moves.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddGroupSiftingDown(\n  DdManager * table,\n  int  x,\n  int  xHigh,\n  DD_CHKFP checkFunction,\n  Move ** moves)\n{\n    Move *move;\n    int  y;\n    int  size;\n    int  limitSize;\n    int  gxtop,gybot;\n    int  R;\t/* upper bound on node decrease */\n    int  xindex, yindex;\n    unsigned isolated;\n    int  allVars;\n    int  z;\n    int  zindex;\n#ifdef DD_DEBUG\n    int  checkR;\n#endif\n\n    /* If the group consists of simple variables, there is no point in\n    ** sifting it down. This check is redundant if the projection functions\n    ** do not have external references, because the computation of the\n    ** lower bound takes care of the problem.  It is necessary otherwise to\n    ** prevent the sifting down of simple variables. */\n    y = x;\n    allVars = 1;\n    do {\n\tif (table->subtables[y].keys != 1) {\n\t    allVars = 0;\n\t    break;\n\t}\n\ty = table->subtables[y].next;\n    } while (table->subtables[y].next != (unsigned) x);\n    if (allVars)\n\treturn(1);\n\n    /* Initialize R. */\n    xindex = table->invperm[x];\n    gxtop = table->subtables[x].next;\n    limitSize = size = (int) (table->keys - table->isolated);\n    R = 0;\n    for (z = xHigh; z > gxtop; z--) {\n\tzindex = table->invperm[z];\n\tif (zindex == xindex || cuddTestInteract(table,xindex,zindex)) {\n\t    isolated = table->vars[zindex]->ref == 1;\n\t    R += table->subtables[z].keys - isolated;\n\t}\n    }\n\n    y = cuddNextHigh(table,x);\n    while (y <= xHigh && size - R < limitSize) {\n#ifdef DD_DEBUG\n\tgxtop = table->subtables[x].next;\n\tcheckR = 0;\n\tfor (z = xHigh; z > gxtop; z--) {\n\t    zindex = table->invperm[z];\n\t    if (zindex == xindex || cuddTestInteract(table,xindex,zindex)) {\n\t\tisolated = table->vars[zindex]->ref == 1;\n\t\tcheckR += table->subtables[z].keys - isolated;\n\t    }\n\t}\n\tassert(R >= checkR);\n#endif\n\t/* Find bottom of y group. */\n\tgybot = table->subtables[y].next;\n\twhile (table->subtables[gybot].next != (unsigned) y)\n\t    gybot = table->subtables[gybot].next;\n\n\tif (checkFunction(table,x,y)) {\n\t    /* Group found: attach groups and record move. */\n\t    gxtop = table->subtables[x].next;\n\t    table->subtables[x].next = y;\n\t    table->subtables[gybot].next = gxtop;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddGroupSiftingDownOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->flags = MTR_NEWNODE;\n\t    move->size = (int) (table->keys - table->isolated);\n\t    move->next = *moves;\n\t    *moves = move;\n\t} else if (table->subtables[x].next == (unsigned) x &&\n\t\t   table->subtables[y].next == (unsigned) y) {\n\t    /* x and y are self groups */\n\t    /* Update upper bound on node decrease. */\n\t    yindex = table->invperm[y];\n\t    if (cuddTestInteract(table,xindex,yindex)) {\n\t\tisolated = table->vars[yindex]->ref == 1;\n\t\tR -= table->subtables[y].keys - isolated;\n\t    }\n\t    size = cuddSwapInPlace(table,x,y);\n#ifdef DD_DEBUG\n\t    assert(table->subtables[x].next == (unsigned) x);\n\t    assert(table->subtables[y].next == (unsigned) y);\n#endif\n\t    if (size == 0) goto ddGroupSiftingDownOutOfMem;\n\n\t    /* Record move. */\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddGroupSiftingDownOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->flags = MTR_DEFAULT;\n\t    move->size = size;\n\t    move->next = *moves;\n\t    *moves = move;\n\n#ifdef DD_DEBUG\n\t    if (table->enableExtraDebug > 0)\n                (void) fprintf(table->out,\n                               \"ddGroupSiftingDown (2 single groups):\\n\");\n#endif\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(1);\n\t    if (size < limitSize) limitSize = size;\n\n\t} else { /* Group move */\n\t    /* Update upper bound on node decrease: first phase. */\n\t    gxtop = table->subtables[x].next;\n\t    z = gxtop + 1;\n\t    do {\n\t\tzindex = table->invperm[z];\n\t\tif (zindex == xindex || cuddTestInteract(table,xindex,zindex)) {\n\t\t    isolated = table->vars[zindex]->ref == 1;\n\t\t    R -= table->subtables[z].keys - isolated;\n\t\t}\n\t\tz++;\n\t    } while (z <= gybot);\n\t    size = ddGroupMove(table,x,y,moves);\n\t    if (size == 0) goto ddGroupSiftingDownOutOfMem;\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(1);\n\t    if (size < limitSize) limitSize = size;\n\n\t    /* Update upper bound on node decrease: second phase. */\n\t    gxtop = table->subtables[gybot].next;\n\t    for (z = gxtop + 1; z <= gybot; z++) {\n\t\tzindex = table->invperm[z];\n\t\tif (zindex == xindex || cuddTestInteract(table,xindex,zindex)) {\n\t\t    isolated = table->vars[zindex]->ref == 1;\n\t\t    R += table->subtables[z].keys - isolated;\n\t\t}\n\t    }\n\t}\n\tx = gybot;\n\ty = cuddNextHigh(table,x);\n    }\n\n    return(1);\n\nddGroupSiftingDownOutOfMem:\n    while (*moves != NULL) {\n\tmove = (*moves)->next;\n\tcuddDeallocMove(table, *moves);\n\t*moves = move;\n    }\n\n    return(0);\n\n} /* end of ddGroupSiftingDown */\n\n\n/**\n  @brief Swaps two groups and records the move.\n\n  @return the number of keys in the %DD table in case of success; 0\n  otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddGroupMove(\n  DdManager * table,\n  int  x,\n  int  y,\n  Move ** moves)\n{\n    Move *move;\n    int  size;\n    int  i,j,xtop,xbot,xsize,ytop,ybot,ysize,newxtop;\n    int  swapx = 0, swapy = 0;\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    int  initialSize,bestSize;\n#endif\n\n#ifdef DD_DEBUG\n    /* We assume that x < y */\n    assert(x < y);\n#endif\n    /* Find top, bottom, and size for the two groups. */\n    xbot = x;\n    xtop = table->subtables[x].next;\n    xsize = xbot - xtop + 1;\n    ybot = y;\n    while ((unsigned) ybot < table->subtables[ybot].next)\n\tybot = table->subtables[ybot].next;\n    ytop = y;\n    ysize = ybot - ytop + 1;\n\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    initialSize = bestSize = table->keys - table->isolated;\n#endif\n    /* Sift the variables of the second group up through the first group */\n    for (i = 1; i <= ysize; i++) {\n\tfor (j = 1; j <= xsize; j++) {\n\t    size = cuddSwapInPlace(table,x,y);\n\t    if (size == 0) goto ddGroupMoveOutOfMem;\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n\t    if (size < bestSize)\n\t\tbestSize = size;\n#endif\n\t    swapx = x; swapy = y;\n\t    y = x;\n\t    x = cuddNextLow(table,y);\n\t}\n\ty = ytop + i;\n\tx = cuddNextLow(table,y);\n    }\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    if ((bestSize < initialSize) && (bestSize < size))\n\t(void) fprintf(table->out,\"Missed local minimum: initialSize:%d  bestSize:%d  finalSize:%d\\n\",initialSize,bestSize,size);\n#endif\n\n    /* fix groups */\n    y = xtop; /* ytop is now where xtop used to be */\n    for (i = 0; i < ysize - 1; i++) {\n\ttable->subtables[y].next = cuddNextHigh(table,y);\n\ty = cuddNextHigh(table,y);\n    }\n    table->subtables[y].next = xtop; /* y is bottom of its group, join */\n\t\t\t\t    /* it to top of its group */\n    x = cuddNextHigh(table,y);\n    newxtop = x;\n    for (i = 0; i < xsize - 1; i++) {\n\ttable->subtables[x].next = cuddNextHigh(table,x);\n\tx = cuddNextHigh(table,x);\n    }\n    table->subtables[x].next = newxtop; /* x is bottom of its group, join */\n\t\t\t\t    /* it to top of its group */\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0)\n        (void) fprintf(table->out,\"ddGroupMove:\\n\");\n#endif\n\n    /* Store group move */\n    move = (Move *) cuddDynamicAllocNode(table);\n    if (move == NULL) goto ddGroupMoveOutOfMem;\n    move->x = swapx;\n    move->y = swapy;\n    move->flags = MTR_DEFAULT;\n    move->size = (int) (table->keys - table->isolated);\n    move->next = *moves;\n    *moves = move;\n\n    return((int)(table->keys - table->isolated));\n\nddGroupMoveOutOfMem:\n    while (*moves != NULL) {\n\tmove = (*moves)->next;\n\tcuddDeallocMove(table, *moves);\n\t*moves = move;\n    }\n    return(0);\n\n} /* end of ddGroupMove */\n\n\n/**\n  @brief Undoes the swap two groups.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddGroupMoveBackward(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    int size;\n    int i,j,xtop,xbot,xsize,ytop,ybot,ysize,newxtop;\n\n\n#ifdef DD_DEBUG\n    /* We assume that x < y */\n    assert(x < y);\n#endif\n\n    /* Find top, bottom, and size for the two groups. */\n    xbot = x;\n    xtop = table->subtables[x].next;\n    xsize = xbot - xtop + 1;\n    ybot = y;\n    while ((unsigned) ybot < table->subtables[ybot].next)\n\tybot = table->subtables[ybot].next;\n    ytop = y;\n    ysize = ybot - ytop + 1;\n\n    /* Sift the variables of the second group up through the first group */\n    for (i = 1; i <= ysize; i++) {\n\tfor (j = 1; j <= xsize; j++) {\n\t    size = cuddSwapInPlace(table,x,y);\n\t    if (size == 0)\n\t\treturn(0);\n\t    y = x;\n\t    x = cuddNextLow(table,y);\n\t}\n\ty = ytop + i;\n\tx = cuddNextLow(table,y);\n    }\n\n    /* fix groups */\n    y = xtop;\n    for (i = 0; i < ysize - 1; i++) {\n\ttable->subtables[y].next = cuddNextHigh(table,y);\n\ty = cuddNextHigh(table,y);\n    }\n    table->subtables[y].next = xtop; /* y is bottom of its group, join */\n\t\t\t\t    /* to its top */\n    x = cuddNextHigh(table,y);\n    newxtop = x;\n    for (i = 0; i < xsize - 1; i++) {\n\ttable->subtables[x].next = cuddNextHigh(table,x);\n\tx = cuddNextHigh(table,x);\n    }\n    table->subtables[x].next = newxtop; /* x is bottom of its group, join */\n\t\t\t\t    /* to its top */\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0)\n        (void) fprintf(table->out,\"ddGroupMoveBackward:\\n\");\n#endif\n\n    return(1);\n\n} /* end of ddGroupMoveBackward */\n\n\n/**\n  @brief Determines the best position for a variables and returns\n  it there.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddGroupSiftingBackward(\n  DdManager * table,\n  Move * moves,\n  int  size,\n  int  upFlag,\n  int  lazyFlag)\n{\n    Move *move;\n    int  res;\n    Move *end_move = NULL;\n    int diff, tmp_diff;\n    int index;\n    unsigned int pairlev;\n\n    if (lazyFlag) {\n\tend_move = NULL;\n\n\t/* Find the minimum size, and the earliest position at which it\n\t** was achieved. */\n\tfor (move = moves; move != NULL; move = move->next) {\n\t    if (move->size < size) {\n\t\tsize = move->size;\n\t\tend_move = move;\n\t    } else if (move->size == size) {\n\t\tif (end_move == NULL) end_move = move;\n\t    }\n\t}\n\n\t/* Find among the moves that give minimum size the one that\n\t** minimizes the distance from the corresponding variable. */\n\tif (moves != NULL) {\n\t    diff = Cudd_ReadSize(table) + 1;\n\t    index = (upFlag == 1) ?\n\t\t    table->invperm[moves->x] : table->invperm[moves->y];\n\t    pairlev =\n\t\t(unsigned) table->perm[Cudd_bddReadPairIndex(table, index)];\n\n\t    for (move = moves; move != NULL; move = move->next) {\n\t\tif (move->size == size) {\n\t\t    if (upFlag == 1) {\n\t\t\ttmp_diff = (move->x > pairlev) ?\n\t\t\t\t    move->x - pairlev : pairlev - move->x;\n\t\t    } else {\n\t\t\ttmp_diff = (move->y > pairlev) ?\n\t\t\t\t    move->y - pairlev : pairlev - move->y;\n\t\t    }\n\t\t    if (tmp_diff < diff) {\n\t\t\tdiff = tmp_diff;\n\t\t\tend_move = move;\n\t\t    }\n\t\t}\n\t    }\n\t}\n    } else {\n\t/* Find the minimum size. */\n\tfor (move = moves; move != NULL; move = move->next) {\n\t    if (move->size < size) {\n\t\tsize = move->size;\n\t    }\n\t}\n    }\n\n    /* In case of lazy sifting, end_move identifies the position at\n    ** which we want to stop.  Otherwise, we stop as soon as we meet\n    ** the minimum size. */\n    for (move = moves; move != NULL; move = move->next) {\n\tif (lazyFlag) {\n\t    if (move == end_move) return(1);\n\t} else {\n\t    if (move->size == size) return(1);\n\t}\n\tif ((table->subtables[move->x].next == move->x) &&\n\t(table->subtables[move->y].next == move->y)) {\n\t    res = cuddSwapInPlace(table,(int)move->x,(int)move->y);\n\t    if (!res) return(0);\n#ifdef DD_DEBUG\n\t    if (table->enableExtraDebug > 0)\n                (void) fprintf(table->out,\"ddGroupSiftingBackward:\\n\");\n\t    assert(table->subtables[move->x].next == move->x);\n\t    assert(table->subtables[move->y].next == move->y);\n#endif\n\t} else { /* Group move necessary */\n\t    if (move->flags == MTR_NEWNODE) {\n\t\tddDissolveGroup(table,(int)move->x,(int)move->y);\n\t    } else {\n\t\tres = ddGroupMoveBackward(table,(int)move->x,(int)move->y);\n\t\tif (!res) return(0);\n\t    }\n\t}\n\n    }\n\n    return(1);\n\n} /* end of ddGroupSiftingBackward */\n\n\n/**\n  @brief Merges groups in the %DD table.\n\n  @details Creates a single group from low to high and adjusts the\n  index field of the tree node.\n\n  @sideeffect None\n\n*/\nstatic void\nddMergeGroups(\n  DdManager * table,\n  MtrNode * treenode,\n  int  low,\n  int  high)\n{\n    int i;\n    MtrNode *auxnode;\n    int saveindex;\n    int newindex;\n\n    /* Merge all variables from low to high in one group, unless\n    ** this is the topmost group. In such a case we do not merge lest\n    ** we lose the symmetry information. */\n    if (treenode != table->tree) {\n\tfor (i = low; i < high; i++)\n\t    table->subtables[i].next = i+1;\n\ttable->subtables[high].next = low;\n    }\n\n    /* Adjust the index fields of the tree nodes. If a node is the\n    ** first child of its parent, then the parent may also need adjustment. */\n    saveindex = treenode->index;\n    newindex = table->invperm[low];\n    auxnode = treenode;\n    do {\n\tauxnode->index = newindex;\n\tif (auxnode->parent == NULL ||\n\t\t(int) auxnode->parent->index != saveindex)\n\t    break;\n\tauxnode = auxnode->parent;\n    } while (1);\n    return;\n\n} /* end of ddMergeGroups */\n\n\n/**\n  @brief Dissolves a group in the %DD table.\n\n  @details x and y are variables in a group to be cut in two. The cut\n  is to pass between x and y.\n\n  @sideeffect None\n\n*/\nstatic void\nddDissolveGroup(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    int topx;\n    int boty;\n\n    /* find top and bottom of the two groups */\n    boty = y;\n    while ((unsigned) boty < table->subtables[boty].next)\n\tboty = table->subtables[boty].next;\n\n    topx = table->subtables[boty].next;\n\n    table->subtables[boty].next = y;\n    table->subtables[x].next = topx;\n\n    return;\n\n} /* end of ddDissolveGroup */\n\n\n/**\n  @brief Pretends to check two variables for aggregation.\n\n  @return always 0.\n\n  @sideeffect None\n\n*/\nstatic int\nddNoCheck(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    (void) table; /* avoid warning */\n    (void) x;     /* avoid warning */\n    (void) y;     /* avoid warning */\n    return(0);\n\n} /* end of ddNoCheck */\n\n\n/**\n  @brief Checks two variables for aggregation.\n\n  @details The check is based on the second difference of the number\n  of nodes as a function of the layer. If the second difference is\n  lower than a given threshold (typically negative) then the two\n  variables should be aggregated.\n\n  @return 1 if the two variables pass the test; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddSecDiffCheck(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    double Nx,Nx_1;\n    double Sx;\n    double threshold;\n    int    xindex,yindex;\n\n    if (x==0) return(0);\n\n#ifdef DD_STATS\n    table->secdiffcalls++;\n#endif\n    Nx = (double) table->subtables[x].keys;\n    Nx_1 = (double) table->subtables[x-1].keys;\n    Sx = (table->subtables[y].keys/Nx) - (Nx/Nx_1);\n\n    threshold = table->recomb / 100.0;\n    if (Sx < threshold) {\n\txindex = table->invperm[x];\n\tyindex = table->invperm[y];\n\tif (cuddTestInteract(table,xindex,yindex)) {\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n\t    (void) fprintf(table->out,\n\t\t\t   \"Second difference for %d = %g Pos(%d)\\n\",\n\t\t\t   table->invperm[x],Sx,x);\n#endif\n#ifdef DD_STATS\n\t    table->secdiff++;\n#endif\n\t    return(1);\n\t} else {\n#ifdef DD_STATS\n\t    table->secdiffmisfire++;\n#endif\n\t    return(0);\n\t}\n\n    }\n    return(0);\n\n} /* end of ddSecDiffCheck */\n\n\n/**\n  @brief Checks for extended symmetry of x and y.\n\n  @return 1 in case of extended symmetry; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddExtSymmCheck(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    DdNode *f,*f0,*f1,*f01,*f00,*f11,*f10;\n    DdNode *one;\n    int comple;\t\t/* f0 is complemented */\n    int notproj;\t/* f is not a projection function */\n    int arccount;\t/* number of arcs from layer x to layer y */\n    int TotalRefCount;\t/* total reference count of layer y minus 1 */\n    int counter;\t/* number of nodes of layer x that are allowed */\n\t\t\t/* to violate extended symmetry conditions */\n    int arccounter;\t/* number of arcs into layer y that are allowed */\n\t\t\t/* to come from layers other than x */\n    int i;\n    int xindex;\n    int yindex;\n    int res;\n    int slots;\n    DdNodePtr *list;\n    DdNode *sentinel = &(table->sentinel);\n\n    xindex = table->invperm[x];\n    yindex = table->invperm[y];\n\n    /* If the two variables do not interact, we do not want to merge them. */\n    if (!cuddTestInteract(table,xindex,yindex))\n\treturn(0);\n\n#ifdef DD_DEBUG\n    /* Checks that x and y do not contain just the projection functions.\n    ** With the test on interaction, these test become redundant,\n    ** because an isolated projection function does not interact with\n    ** any other variable.\n    */\n    if (table->subtables[x].keys == 1) {\n\tassert(table->vars[xindex]->ref != 1);\n    }\n    if (table->subtables[y].keys == 1) {\n\tassert(table->vars[yindex]->ref != 1);\n    }\n#endif\n\n#ifdef DD_STATS\n    table->extsymmcalls++;\n#endif\n\n    arccount = 0;\n    counter = (int) (table->subtables[x].keys *\n\t      (table->symmviolation/100.0) + 0.5);\n    one = DD_ONE(table);\n\n    slots = table->subtables[x].slots;\n    list = table->subtables[x].nodelist;\n    for (i = 0; i < slots; i++) {\n\tf = list[i];\n\twhile (f != sentinel) {\n\t    /* Find f1, f0, f11, f10, f01, f00. */\n\t    f1 = cuddT(f);\n\t    f0 = Cudd_Regular(cuddE(f));\n\t    comple = Cudd_IsComplement(cuddE(f));\n\t    notproj = f1 != one || f0 != one || f->ref != (DdHalfWord) 1;\n\t    if (f1->index == (unsigned) yindex) {\n\t\tarccount++;\n\t\tf11 = cuddT(f1); f10 = cuddE(f1);\n\t    } else {\n\t\tif ((int) f0->index != yindex) {\n\t\t    /* If f is an isolated projection function it is\n\t\t    ** allowed to bypass layer y.\n\t\t    */\n\t\t    if (notproj) {\n\t\t\tif (counter == 0)\n\t\t\t    return(0);\n\t\t\tcounter--; /* f bypasses layer y */\n\t\t    }\n\t\t}\n\t\tf11 = f10 = f1;\n\t    }\n\t    if ((int) f0->index == yindex) {\n\t\tarccount++;\n\t\tf01 = cuddT(f0); f00 = cuddE(f0);\n\t    } else {\n\t\tf01 = f00 = f0;\n\t    }\n\t    if (comple) {\n\t\tf01 = Cudd_Not(f01);\n\t\tf00 = Cudd_Not(f00);\n\t    }\n\n\t    /* Unless we are looking at a projection function\n\t    ** without external references except the one from the\n\t    ** table, we insist that f01 == f10 or f11 == f00\n\t    */\n\t    if (notproj) {\n\t\tif (f01 != f10 && f11 != f00) {\n\t\t    if (counter == 0)\n\t\t\treturn(0);\n\t\t    counter--;\n\t\t}\n\t    }\n\n\t    f = f->next;\n\t} /* while */\n    } /* for */\n\n    /* Calculate the total reference counts of y */\n    TotalRefCount = -1;\t/* -1 for projection function */\n    slots = table->subtables[y].slots;\n    list = table->subtables[y].nodelist;\n    for (i = 0; i < slots; i++) {\n\tf = list[i];\n\twhile (f != sentinel) {\n\t    TotalRefCount += f->ref;\n\t    f = f->next;\n\t}\n    }\n\n    arccounter = (int) (table->subtables[y].keys *\n\t\t (table->arcviolation/100.0) + 0.5);\n    res = arccount >= TotalRefCount - arccounter;\n\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    if (res) {\n\t(void) fprintf(table->out,\n\t\t       \"Found extended symmetry! x = %d\\ty = %d\\tPos(%d,%d)\\n\",\n\t\t       xindex,yindex,x,y);\n    }\n#endif\n\n#ifdef DD_STATS\n    if (res)\n\ttable->extsymm++;\n#endif\n    return(res);\n\n} /* end ddExtSymmCheck */\n\n\n/**\n  @brief Checks for grouping of x and y.\n\n  @details This function is used for lazy sifting.\n\n  @return 1 in case of grouping; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddVarGroupCheck(\n  DdManager * table,\n  int x,\n  int y)\n{\n    int xindex = table->invperm[x];\n    int yindex = table->invperm[y];\n\n    if (Cudd_bddIsVarToBeUngrouped(table, xindex)) return(0);\n\n    if (Cudd_bddReadPairIndex(table, xindex) == yindex) {\n\tif (ddIsVarHandled(table, xindex) ||\n\t    ddIsVarHandled(table, yindex)) {\n\t    if (Cudd_bddIsVarToBeGrouped(table, xindex) ||\n\t\tCudd_bddIsVarToBeGrouped(table, yindex) ) {\n\t\tif (table->keys - table->isolated <= table->originalSize) {\n\t\t    return(1);\n\t\t}\n\t    }\n\t}\n    }\n\n    return(0);\n\n} /* end of ddVarGroupCheck */\n\n\n/**\n  @brief Sets a variable to already handled.\n\n  @details This function is used for lazy sifting.\n\n  @sideeffect none\n\n*/\nstatic int\nddSetVarHandled(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(0);\n    dd->subtables[dd->perm[index]].varHandled = 1;\n    return(1);\n\n} /* end of ddSetVarHandled */\n\n\n/**\n  @brief Resets a variable to be processed.\n\n  @details This function is used for lazy sifting.\n\n  @sideeffect none\n\n*/\nstatic int\nddResetVarHandled(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(0);\n    dd->subtables[dd->perm[index]].varHandled = 0;\n    return(1);\n\n} /* end of ddResetVarHandled */\n\n\n/**\n  @brief Checks whether a variables is already handled.\n\n  @details This function is used for lazy sifting.\n\n  @sideeffect none\n\n*/\nstatic int\nddIsVarHandled(\n  DdManager *dd,\n  int index)\n{\n    if (index >= dd->size || index < 0) return(-1);\n    return dd->subtables[dd->perm[index]].varHandled;\n\n} /* end of ddIsVarHandled */\n"
  },
  {
    "path": "cudd/cudd/cuddHarwell.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Function to read a matrix in Harwell format.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Reads in a matrix in the format of the Harwell-Boeing\n  benchmark suite.\n\n  @details The variables are ordered as follows:\n  <blockquote>\n  x\\[0\\] y\\[0\\] x\\[1\\] y\\[1\\] ...\n  </blockquote>\n  0 is the most significant bit.  On input, nx and ny hold the numbers\n  of row and column variables already in existence.\n\n  @return 1 on success; 0 otherwise.\n\n  @sideeffect On output, nx and ny hold the numbers of row and column\n  variables actually used by the matrix.  m and n are set to the\n  numbers of rows and columns of the matrix.  Their values on input\n  are immaterial.  The %ADD for the sparse matrix is returned in E, and\n  its reference count is > 0.\n\n  @see Cudd_addRead Cudd_bddRead\n\n*/\nint\nCudd_addHarwell(\n  FILE * fp /**< pointer to the input file */,\n  DdManager * dd /**< %DD manager */,\n  DdNode ** E /**< characteristic function of the graph */,\n  DdNode *** x /**< array of row variables */,\n  DdNode *** y /**< array of column variables */,\n  DdNode *** xn /**< array of complemented row variables */,\n  DdNode *** yn_ /**< array of complemented column variables */,\n  int * nx /**< number or row variables */,\n  int * ny /**< number or column variables */,\n  int * m /**< number of rows */,\n  int * n /**< number of columns */,\n  int  bx /**< first index of row variables */,\n  int  sx /**< step of row variables */,\n  int  by /**< first index of column variables */,\n  int  sy /**< step of column variables */,\n  int  pr /**< verbosity level */)\n{\n    DdNode *one, *zero;\n    DdNode *w;\n    DdNode *cubex, *cubey, *minterm1;\n    int u, v, err, i, j, nv;\n    double val;\n    /* local copies of x, y, xn, yn_ */\n    DdNode **lx = NULL, **ly = NULL, **lxn = NULL, **lyn = NULL;\n    int lnx, lny;\t\t\t/* local copies of nx and ny */\n    char title[73], key[9], mxtype[4], rhstyp[4];\n    int totcrd, ptrcrd, indcrd, valcrd, rhscrd,\n        nrow, ncol, nnzero, neltvl,\n\tnrhs, nrhsix;\n    int *colptr, *rowind;\n#if 0\n    int nguess, nexact;\n    int\t*rhsptr, *rhsind;\n#endif\n\n    if (*nx < 0 || *ny < 0) return(0);\n\n    one = DD_ONE(dd);\n    zero = DD_ZERO(dd);\n\n    /* Read the header */\n    err = fscanf(fp, \"%72c %8c\", title, key);\n    if (err == EOF) {\n\treturn(0);\n    } else if (err != 2) {\n        return(0);\n    }\n    title[72] = (char) 0;\n    key[8] = (char) 0;\n\n    err = fscanf(fp, \"%d %d %d %d %d\", &totcrd, &ptrcrd, &indcrd,\n    &valcrd, &rhscrd);\n    if (err == EOF) {\n\treturn(0);\n    } else if (err != 5) {\n        return(0);\n    }\n\n    err = fscanf(fp, \"%3s %d %d %d %d\", mxtype, &nrow, &ncol,\n    &nnzero, &neltvl);\n    if (err == EOF) {\n\treturn(0);\n    } else if (err != 5) {\n        return(0);\n    }\n\n    /* Skip FORTRAN formats */\n    if (rhscrd == 0) {\n\terr = fscanf(fp, \"%*s %*s %*s \\n\");\n    } else {\n\terr = fscanf(fp, \"%*s %*s %*s %*s \\n\");\n    }\n    if (err == EOF) {\n\treturn(0);\n    } else if (err != 0) {\n        return(0);\n    }\n\n    /* Print out some stuff if requested to be verbose */\n    if (pr>0) {\n\t(void) fprintf(dd->out,\"%s: type %s, %d rows, %d columns, %d entries\\n\", key,\n\tmxtype, nrow, ncol, nnzero);\n\tif (pr>1) (void) fprintf(dd->out,\"%s\\n\", title);\n    }\n\n    /* Check matrix type */\n    if (mxtype[0] != 'R' || mxtype[1] != 'U' || mxtype[2] != 'A') {\n\t(void) fprintf(dd->err,\"%s: Illegal matrix type: %s\\n\",\n\t\t       key, mxtype);\n\treturn(0);\n    }\n    if (neltvl != 0) return(0);\n\n    /* Read optional 5-th line */\n    if (rhscrd != 0) {\n\terr = fscanf(fp, \"%3c %d %d\", rhstyp, &nrhs, &nrhsix);\n\tif (err == EOF) {\n\t    return(0);\n\t} else if (err != 3) {\n\t    return(0);\n\t}\n\trhstyp[3] = (char) 0;\n\tif (rhstyp[0] != 'F') {\n\t    (void) fprintf(dd->err,\n\t    \"%s: Sparse right-hand side not yet supported\\n\", key);\n\t    return(0);\n\t}\n\tif (pr>0) (void) fprintf(dd->out,\"%d right-hand side(s)\\n\", nrhs);\n    } else {\n\tnrhs = 0;\n    }\n\n    /* Compute the number of variables */\n\n    /* row and column numbers start from 0 */\n    u = nrow - 1;\n    for (i=0; u > 0; i++) {\n\tu >>= 1;\n    }\n    lnx = i;\n    if (nrhs == 0) {\n\tv = ncol - 1;\n    } else {\n\tv = 2* (ddMax(ncol, nrhs) - 1);\n    }\n    for (i=0; v > 0; i++) {\n\tv >>= 1;\n    }\n    lny = i;\n\n    /* Allocate or reallocate arrays for variables as needed */\n    if (*nx == 0) {\n\tif (lnx > 0) {\n\t    *x = lx = ALLOC(DdNode *,lnx);\n\t    if (lx == NULL) {\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    *xn = lxn =  ALLOC(DdNode *,lnx);\n\t    if (lxn == NULL) {\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t} else {\n\t    *x = *xn = NULL;\n\t}\n    } else if (lnx > *nx) {\n\t*x = lx = REALLOC(DdNode *, *x, lnx);\n\tif (lx == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t*xn = lxn =  REALLOC(DdNode *, *xn, lnx);\n\tif (lxn == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n    } else {\n\tlx = *x;\n\tlxn = *xn;\n    }\n    if (*ny == 0) {\n\tif (lny >0) {\n\t    *y = ly = ALLOC(DdNode *,lny);\n\t    if (ly == NULL) {\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    *yn_ = lyn = ALLOC(DdNode *,lny);\n\t    if (lyn == NULL) {\n\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t} else {\n\t    *y = *yn_ = NULL;\n\t}\n    } else if (lny > *ny) {\n\t*y = ly = REALLOC(DdNode *, *y, lny);\n\tif (ly == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t*yn_ = lyn = REALLOC(DdNode *, *yn_, lny);\n\tif (lyn == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n    } else {\n\tly = *y;\n\tlyn = *yn_;\n    }\n\n    /* Create new variables as needed */\n    for (i= *nx,nv=bx+(*nx)*sx; i < lnx; i++,nv+=sx) {\n\tdo {\n\t    dd->reordered = 0;\n\t    lx[i] = cuddUniqueInter(dd, nv, one, zero);\n\t} while (dd->reordered == 1);\n\tif (lx[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n        cuddRef(lx[i]);\n\tdo {\n\t    dd->reordered = 0;\n\t    lxn[i] = cuddUniqueInter(dd, nv, zero, one);\n\t} while (dd->reordered == 1);\n\tif (lxn[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n        cuddRef(lxn[i]);\n    }\n    for (i= *ny,nv=by+(*ny)*sy; i < lny; i++,nv+=sy) {\n\tdo {\n\t    dd->reordered = 0;\n\t    ly[i] = cuddUniqueInter(dd, nv, one, zero);\n\t} while (dd->reordered == 1);\n\tif (ly[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n\tcuddRef(ly[i]);\n\tdo {\n\t    dd->reordered = 0;\n\t    lyn[i] = cuddUniqueInter(dd, nv, zero, one);\n\t} while (dd->reordered == 1);\n\tif (lyn[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n\tcuddRef(lyn[i]);\n    }\n\n    /* Update matrix parameters */\n    *nx = lnx;\n    *ny = lny;\n    *m = nrow;\n    if (nrhs == 0) {\n\t*n = ncol;\n    } else {\n\t*n = (1 << (lny - 1)) + nrhs;\n    }\n    \n    /* Read structure data */\n    colptr = ALLOC(int, ncol+1);\n    if (colptr == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    rowind = ALLOC(int, nnzero);\n    if (rowind == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n\n    for (i=0; i<ncol+1; i++) {\n\terr = fscanf(fp, \" %d \", &u);\n\tif (err == EOF){ \n\t    FREE(colptr);\n\t    FREE(rowind);\n\t    return(0);\n\t} else if (err != 1) {\n\t    FREE(colptr);\n\t    FREE(rowind);\n\t    return(0);\n\t}\n\tcolptr[i] = u - 1;\n    }\n    if (colptr[0] != 0) {\n\t(void) fprintf(dd->err,\"%s: Unexpected colptr[0] (%d)\\n\",\n\t\t       key,colptr[0]);\n\tFREE(colptr);\n\tFREE(rowind);\n\treturn(0);\n    }\n    for (i=0; i<nnzero; i++) {\n\terr = fscanf(fp, \" %d \", &u);\n\tif (err == EOF){ \n\t    FREE(colptr);\n\t    FREE(rowind);\n\t    return(0);\n\t} else if (err != 1) {\n\t    FREE(colptr);\n\t    FREE(rowind);\n\t    return(0);\n\t}\n\trowind[i] = u - 1;\n    }\n\n    *E = zero; cuddRef(*E);\n\n    for (j=0; j<ncol; j++) {\n\tv = j;\n\tcubey = one; cuddRef(cubey);\n\tfor (nv = lny - 1; nv>=0; nv--) {\n\t    if (v & 1) {\n\t\tw = Cudd_addApply(dd, Cudd_addTimes, cubey, ly[nv]);\n\t    } else {\n\t\tw = Cudd_addApply(dd, Cudd_addTimes, cubey, lyn[nv]);\n\t    }\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\tFREE(colptr);\n\t\tFREE(rowind);\n\t\treturn(0);\n\t    }\n\t    cuddRef(w);\n\t    Cudd_RecursiveDeref(dd, cubey);\n\t    cubey = w;\n\t    v >>= 1;\n\t}\n\tfor (i=colptr[j]; i<colptr[j+1]; i++) {\n\t    u = rowind[i];\n\t    err = fscanf(fp, \" %lf \", &val);\n\t    if (err == EOF || err != 1){ \n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\tFREE(colptr);\n\t\tFREE(rowind);\n\t\treturn(0);\n\t    }\n\t    /* Create new Constant node if necessary */\n\t    cubex = cuddUniqueConst(dd, (CUDD_VALUE_TYPE) val);\n\t    if (cubex == NULL) {\n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\tFREE(colptr);\n\t\tFREE(rowind);\n\t\treturn(0);\n\t    }\n\t    cuddRef(cubex);\n\n\t    for (nv = lnx - 1; nv>=0; nv--) {\n\t\tif (u & 1) {\n\t\t    w = Cudd_addApply(dd, Cudd_addTimes, cubex, lx[nv]);\n\t\t} else { \n\t\t    w = Cudd_addApply(dd, Cudd_addTimes, cubex, lxn[nv]);\n\t\t}\n\t\tif (w == NULL) {\n\t\t    Cudd_RecursiveDeref(dd, cubey);\n\t\t    Cudd_RecursiveDeref(dd, cubex);\n\t\t    FREE(colptr);\n\t\t    FREE(rowind);\n\t\t    return(0);\n\t\t}\n\t\tcuddRef(w);\n\t\tCudd_RecursiveDeref(dd, cubex);\n\t\tcubex = w;\n\t\tu >>= 1;\n\t    }\n\t    minterm1 = Cudd_addApply(dd, Cudd_addTimes, cubey, cubex);\n\t    if (minterm1 == NULL) {\n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\tCudd_RecursiveDeref(dd, cubex);\n\t\tFREE(colptr);\n\t\tFREE(rowind);\n\t\treturn(0);\n\t    }\n\t    cuddRef(minterm1);\n\t    Cudd_RecursiveDeref(dd, cubex);\n\t    w = Cudd_addApply(dd, Cudd_addPlus, *E, minterm1);\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\tFREE(colptr);\n\t\tFREE(rowind);\n\t\treturn(0);\n\t    }\n\t    cuddRef(w);\n\t    Cudd_RecursiveDeref(dd, minterm1);\n\t    Cudd_RecursiveDeref(dd, *E);\n\t    *E = w;\n\t}\n\tCudd_RecursiveDeref(dd, cubey);\n    }\n    FREE(colptr);\n    FREE(rowind);\n\n    /* Read right-hand sides */\n    for (j=0; j<nrhs; j++) {\n\tv = j + (1<< (lny-1));\n\tcubey = one; cuddRef(cubey);\n\tfor (nv = lny - 1; nv>=0; nv--) {\n\t    if (v & 1) {\n\t\tw = Cudd_addApply(dd, Cudd_addTimes, cubey, ly[nv]);\n\t    } else {\n\t\tw = Cudd_addApply(dd, Cudd_addTimes, cubey, lyn[nv]);\n\t    }\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\treturn(0);\n\t    }\n\t    cuddRef(w);\n\t    Cudd_RecursiveDeref(dd, cubey);\n\t    cubey = w;\n\t    v >>= 1;\n\t}\n\tfor (i=0; i<nrow; i++) {\n\t    u = i;\n\t    err = fscanf(fp, \" %lf \", &val);\n\t    if (err == EOF || err != 1){ \n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\treturn(0);\n\t    }\n\t    /* Create new Constant node if necessary */\n\t    if (val == (double) 0.0) continue;\n\t    cubex = cuddUniqueConst(dd, (CUDD_VALUE_TYPE) val);\n\t    if (cubex == NULL) {\n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\treturn(0);\n\t    }\n\t    cuddRef(cubex);\n\n\t    for (nv = lnx - 1; nv>=0; nv--) {\n\t\tif (u & 1) {\n\t\t   w = Cudd_addApply(dd, Cudd_addTimes, cubex, lx[nv]);\n\t\t} else { \n\t\t    w = Cudd_addApply(dd, Cudd_addTimes, cubex, lxn[nv]);\n\t\t}\n\t\tif (w == NULL) {\n\t\t    Cudd_RecursiveDeref(dd, cubey);\n\t\t    Cudd_RecursiveDeref(dd, cubex);\n\t\t    return(0);\n\t\t}\n\t\tcuddRef(w);\n\t\tCudd_RecursiveDeref(dd, cubex);\n\t\tcubex = w;\n\t\tu >>= 1;\n\t    }\n\t    minterm1 = Cudd_addApply(dd, Cudd_addTimes, cubey, cubex);\n\t    if (minterm1 == NULL) {\n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\tCudd_RecursiveDeref(dd, cubex);\n\t\treturn(0);\n\t    }\n\t    cuddRef(minterm1);\n\t    Cudd_RecursiveDeref(dd, cubex);\n\t    w = Cudd_addApply(dd, Cudd_addPlus, *E, minterm1);\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, cubey);\n\t\treturn(0);\n\t    }\n\t    cuddRef(w);\n\t    Cudd_RecursiveDeref(dd, minterm1);\n\t    Cudd_RecursiveDeref(dd, *E);\n\t    *E = w;\n\t}\n\tCudd_RecursiveDeref(dd, cubey);\n    }\n\n    return(1);\n\n} /* end of Cudd_addHarwell */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n"
  },
  {
    "path": "cudd/cudd/cuddInit.c",
    "content": "/**\n  @file \n\n  @ingroup cudd\n\n  @brief Functions to initialize and shut down the %DD manager.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Creates a new DD manager.\n\n  @details Initializes the table, the basic constants and the\n  projection functions. If maxMemory is 0, Cudd_Init decides suitable\n  values for the maximum size of the cache and for the limit for fast\n  unique table growth based on the available memory.\n\n  @return a pointer to the manager if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Quit\n\n*/\nDdManager *\nCudd_Init(\n  unsigned int numVars /**< initial number of %BDD variables (i.e., subtables) */,\n  unsigned int numVarsZ /**< initial number of %ZDD variables (i.e., subtables) */,\n  unsigned int numSlots /**< initial size of the unique tables */,\n  unsigned int cacheSize /**< initial size of the cache */,\n  size_t maxMemory /**< target maximum memory occupation */)\n{\n    DdManager *unique;\n    int i,result;\n    DdNode *one, *zero;\n    unsigned int maxCacheSize;\n    unsigned int looseUpTo;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    if (maxMemory == 0) {\n\tmaxMemory = getSoftDataLimit();\n    }\n    looseUpTo = (unsigned int) ((maxMemory / sizeof(DdNode)) /\n\t\t\t\tDD_MAX_LOOSE_FRACTION);\n    unique = cuddInitTable(numVars,numVarsZ,numSlots,looseUpTo);\n    if (unique == NULL) return(NULL);\n    unique->maxmem = (size_t) maxMemory / 10 * 9;\n    maxCacheSize = (unsigned int) ((maxMemory / sizeof(DdCache)) /\n\t\t\t\t   DD_MAX_CACHE_FRACTION);\n    result = cuddInitCache(unique,cacheSize,maxCacheSize);\n    if (result == 0) return(NULL);\n\n    saveHandler = MMoutOfMemory;\n    MMoutOfMemory = unique->outOfMemCallback;\n    unique->stash = ALLOC(char,(maxMemory / DD_STASH_FRACTION) + 4);\n    MMoutOfMemory = saveHandler;\n    if (unique->stash == NULL) {\n\t(void) fprintf(unique->err,\"Unable to set aside memory\\n\");\n    }\n\n    /* Initialize constants. */\n    unique->one = cuddUniqueConst(unique,1.0);\n    if (unique->one == NULL) return(0);\n    cuddRef(unique->one);\n    unique->zero = NULL;\n    unique->zero = cuddUniqueConst(unique,0.0);\n    if (unique->zero == NULL) return(0);\n    cuddRef(unique->zero);\n#ifdef HAVE_IEEE_754\n    if (DD_PLUS_INF_VAL != DD_PLUS_INF_VAL * 3 ||\n\tDD_PLUS_INF_VAL != DD_PLUS_INF_VAL / 3) {\n\t(void) fprintf(unique->err,\"Warning: Crippled infinite values\\n\");\n\t(void) fprintf(unique->err,\"Recompile without -DHAVE_IEEE_754\\n\");\n    }\n#endif\n    unique->plusinfinity = cuddUniqueConst(unique,DD_PLUS_INF_VAL);\n    if (unique->plusinfinity == NULL) return(0);\n    cuddRef(unique->plusinfinity);\n    unique->minusinfinity = cuddUniqueConst(unique,DD_MINUS_INF_VAL);\n    if (unique->minusinfinity == NULL) return(0);\n    cuddRef(unique->minusinfinity);\n    unique->background = unique->zero;\n\n    /* The logical zero is different from the CUDD_VALUE_TYPE zero! */\n    one = unique->one;\n    zero = Cudd_Not(one);\n    /* Create the projection functions. */\n    unique->vars = ALLOC(DdNodePtr,unique->maxSize);\n    if (unique->vars == NULL) {\n\tunique->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < unique->size; i++) {\n\tunique->vars[i] = cuddUniqueInter(unique,i,one,zero);\n\tif (unique->vars[i] == NULL) return(0);\n\tcuddRef(unique->vars[i]);\n    }\n\n    if (unique->sizeZ)\n\tcuddZddInitUniv(unique);\n\n    unique->memused += sizeof(DdNode *) * unique->maxSize;\n\n    return(unique);\n\n} /* end of Cudd_Init */\n\n\n/**\n  @brief Deletes resources associated with a %DD manager.\n\n  @details Calling Cudd_Quit with a null pointer has no effect.\n\n  @sideeffect None\n\n  @see Cudd_Init\n\n*/\nvoid\nCudd_Quit(\n  DdManager * unique /**< pointer to manager */)\n{\n    if (unique)\n        cuddFreeTable(unique);\n\n} /* end of Cudd_Quit */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Initializes the %ZDD universe.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddZddFreeUniv\n\n*/\nint\ncuddZddInitUniv(\n  DdManager * zdd)\n{\n    DdNode\t*p, *res;\n    int\t\ti;\n\n    zdd->univ = ALLOC(DdNodePtr, zdd->sizeZ);\n    if (zdd->univ == NULL) {\n\tzdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n\n    res = DD_ONE(zdd);\n    cuddRef(res);\n    for (i = zdd->sizeZ - 1; i >= 0; i--) {\n\tunsigned int index = zdd->invpermZ[i];\n\tp = res;\n\tres = cuddUniqueInterZdd(zdd, index, p, p);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(zdd,p);\n\t    FREE(zdd->univ);\n\t    return(0);\n\t}\n\tcuddRef(res);\n\tcuddDeref(p);\n\tzdd->univ[i] = res;\n    }\n\n#ifdef DD_VERBOSE\n    cuddZddP(zdd, zdd->univ[0]);\n#endif\n\n    return(1);\n\n} /* end of cuddZddInitUniv */\n\n\n/**\n  @brief Frees the %ZDD universe.\n\n  @sideeffect None\n\n  @see cuddZddInitUniv\n\n*/\nvoid\ncuddZddFreeUniv(\n  DdManager * zdd)\n{\n    if (zdd->univ) {\n\tCudd_RecursiveDerefZdd(zdd, zdd->univ[0]);\n\tFREE(zdd->univ);\n    }\n\n} /* end of cuddZddFreeUniv */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n"
  },
  {
    "path": "cudd/cudd/cuddInt.h",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Internal data structures of the CUDD package.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef CUDD_INT_H_\n#define CUDD_INT_H_\n\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n\n#include <math.h>\n#include \"config.h\"\n#include \"st.h\"\n#include \"mtr.h\"\n#include \"epd.h\"\n#include \"cudd.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define CUDD_VERSION\t\tPACKAGE_VERSION\n\n#define DD_MAXREF\t\t((DdHalfWord) ~0)\n\n#define DD_DEFAULT_RESIZE\t10\t/* how many extra variables */\n\t\t\t\t\t/* should be added when resizing */\n#define DD_MEM_CHUNK\t\t1022\n\n/* These definitions work for CUDD_VALUE_TYPE == double */\n#define DD_ONE_VAL\t\t(1.0)\n#define DD_ZERO_VAL\t\t(0.0)\n#define DD_EPSILON\t\t(1.0e-12)\n\n/* The definitions of +/- infinity in terms of HUGE_VAL work on\n** the DECstations and on many other combinations of OS/compiler.\n*/\n#ifdef HAVE_IEEE_754\n#  define DD_PLUS_INF_VAL\t(HUGE_VAL)\n#else\n#  define DD_PLUS_INF_VAL\t(10e301)\n#  define DD_CRI_HI_MARK\t(10e150)\n#  define DD_CRI_LO_MARK\t(-(DD_CRI_HI_MARK))\n#endif\n#define DD_MINUS_INF_VAL\t(-(DD_PLUS_INF_VAL))\n\n#define DD_NON_CONSTANT\t\t((DdNode *) 1)\t/* for Cudd_bddIteConstant */\n\n/* Unique table and cache management constants. */\n#define DD_MAX_SUBTABLE_DENSITY 4\t/* tells when to resize a subtable */\n/* gc when this percent are dead (measured w.r.t. slots, not keys)\n** The first limit (LO) applies normally. The second limit applies when\n** the package believes more space for the unique table (i.e., more dead\n** nodes) would improve performance, and the unique table is not already\n** too large. The third limit applies when memory is low.\n*/\n#define DD_GC_FRAC_LO\t\tDD_MAX_SUBTABLE_DENSITY * 0.25\n#define DD_GC_FRAC_HI\t\tDD_MAX_SUBTABLE_DENSITY * 1.0\n#define DD_GC_FRAC_MIN\t\t0.2\n#define DD_MIN_HIT\t\t30\t/* resize cache when hit ratio\n\t\t\t\t\t   above this percentage (default) */\n#define DD_MAX_LOOSE_FRACTION\t5 /* 1 / (max fraction of memory used for\n\t\t\t\t     unique table in fast growth mode) */\n#define DD_MAX_CACHE_FRACTION\t3 /* 1 / (max fraction of memory used for\n\t\t\t\t     computed table if resizing enabled) */\n#define DD_STASH_FRACTION\t64 /* 1 / (fraction of memory set\n\t\t\t\t      aside for emergencies) */\n#define DD_MAX_CACHE_TO_SLOTS_RATIO 4 /* used to limit the cache size */\n\n/* Variable ordering default parameter values. */\n#define DD_SIFT_MAX_VAR\t\t1000\n#define DD_SIFT_MAX_SWAPS\t2000000\n#define DD_DEFAULT_RECOMB\t0\n#define DD_MAX_REORDER_GROWTH\t1.2\n#define DD_FIRST_REORDER\t4004\t/* 4 for the constants */\n#define DD_DYN_RATIO\t\t2\t/* when to dynamically reorder */\n\n/* Primes for cache hash functions. */\n#define DD_P1\t\t\t12582917\n#define DD_P2\t\t\t4256249\n#define DD_P3\t\t\t741457\n#define DD_P4\t\t\t1618033999\n\n/* Cache tags for 3-operand operators.  These tags are stored in the\n** least significant bits of the cache operand pointers according to\n** the following scheme.  The tag consists of two hex digits.  Both digits\n** must be even, so that they do not interfere with complementation bits.\n** The least significant one is stored in Bits 3:1 of the f operand in the\n** cache entry.  Bit 1 is always 1, so that we can differentiate\n** three-operand operations from one- and two-operand operations.\n** Therefore, the least significant digit is one of {2,6,a,e}.  The most\n** significant digit occupies Bits 3:1 of the g operand in the cache\n** entry.  It can by any even digit between 0 and e.  This gives a total\n** of 5 bits for the tag proper, which means a maximum of 32 three-operand\n** operations. */\n#define DD_ADD_ITE_TAG\t\t\t\t0x02\n#define DD_BDD_AND_ABSTRACT_TAG\t\t\t0x06\n#define DD_BDD_XOR_EXIST_ABSTRACT_TAG\t\t0x0a\n#define DD_BDD_ITE_TAG\t\t\t\t0x0e\n#define DD_ADD_BDD_DO_INTERVAL_TAG\t\t0x22\n#define DD_BDD_CLIPPING_AND_ABSTRACT_UP_TAG\t0x26\n#define DD_BDD_CLIPPING_AND_ABSTRACT_DOWN_TAG\t0x2a\n#define DD_BDD_COMPOSE_RECUR_TAG\t\t0x2e\n#define DD_ADD_COMPOSE_RECUR_TAG\t\t0x42\n#define DD_ADD_NON_SIM_COMPOSE_TAG\t\t0x46\n#define DD_EQUIV_DC_TAG\t\t\t\t0x4a\n#define DD_ZDD_ITE_TAG\t\t\t\t0x4e\n#define DD_ADD_ITE_CONSTANT_TAG\t\t\t0x62\n#define DD_ADD_EVAL_CONST_TAG\t\t\t0x66\n#define DD_BDD_ITE_CONSTANT_TAG\t\t\t0x6a\n#define DD_ADD_OUT_SUM_TAG\t\t\t0x6e\n#define DD_BDD_LEQ_UNLESS_TAG\t\t\t0x82\n#define DD_ADD_TRIANGLE_TAG\t\t\t0x86\n#define DD_BDD_MAX_EXP_TAG\t\t\t0x8a\n#define DD_VARS_SYMM_BEFORE_TAG\t\t\t0x8e\n#define DD_VARS_SYMM_BETWEEN_TAG\t\t0xa2\n\n/* Generator constants. */\n#define CUDD_GEN_CUBES 0\n#define CUDD_GEN_PRIMES 1\n#define CUDD_GEN_NODES 2\n#define CUDD_GEN_ZDD_PATHS 3\n#define CUDD_GEN_EMPTY 0\n#define CUDD_GEN_NONEMPTY 1\n\n/**\n ** @brief Maximum variable index.\n **\n ** @details CUDD_MAXINDEX is defined in such a way that on 32-bit and\n ** 64-bit machines one can cast an index to (int) without generating\n ** a negative number.\n */\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define CUDD_MAXINDEX\t\t(((DdHalfWord) ~0) >> 1)\n#else\n#define CUDD_MAXINDEX\t\t((DdHalfWord) ~0)\n#endif\n\n/**\n ** @brief The index of constant nodes.\n **\n ** @details This is a synonim for CUDD_MAXINDEX.\n */\n#define CUDD_CONST_INDEX\tCUDD_MAXINDEX\n\n/**\n ** @brief Size of the random number generator shuffle table.\n */\n#define STAB_SIZE 64\n\n/**\n ** @brief Mask for periodic check of termination and timeout.\n **\n ** @see checkWhetherToGiveUp\n */\n#define CUDD_CHECK_MASK 0x7ff\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n   @brief Type that is half the size of a pointer.\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\ntypedef uint32_t DdHalfWord;\n#else\ntypedef uint16_t DdHalfWord;\n#endif\n\n/**\n * @brief Signed integer that is the size of a pointer.\n *\n * @details The only platforms on which CUDD has been tested define\n * intptr_t and uintptr_t in inttypes.h and satisfy the condition\n *\n *     sizeof(intptr_t) == sizeof(uintptr_t) == sizeof(void *)\n *\n * Neither of these is guaranteed by the C standard.\n */\ntypedef intptr_t ptrint;\n\n/**\n * @brief Unsigned integer that is the size of a pointer.\n *\n * @see ptrint\n */\ntypedef uintptr_t ptruint;\n\ntypedef struct DdChildren DdChildren;\ntypedef struct DdHook DdHook;\ntypedef struct DdSubtable DdSubtable;\ntypedef struct DdCache DdCache;\ntypedef struct DdLocalCacheItem DdLocalCacheItem;\ntypedef struct DdLocalCache DdLocalCache;\ntypedef struct DdHashItem DdHashItem;\ntypedef struct DdHashTable DdHashTable;\ntypedef struct Move Move;\ntypedef struct IndexKey IndexKey;\ntypedef struct DdQueueItem DdQueueItem;\ntypedef struct DdLevelQueue DdLevelQueue;\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief The two children of a non-terminal node.\n */\nstruct DdChildren {\n    struct DdNode *T;\t/**< then (true) child */\n    struct DdNode *E;\t/**< else (false) child */\n};\n\n/**\n * @brief Decision diagram node.\n */\nstruct DdNode {\n    DdHalfWord index;\t\t/**< variable index */\n    DdHalfWord ref;\t\t/**< reference count */\n    DdNode *next;\t\t/**< next pointer for unique table */\n    union {\n\tCUDD_VALUE_TYPE value;\t/**< for constant (terminal) nodes */\n\tDdChildren kids;\t/**< for internal nodes */\n    } type;\t\t\t/**< terminal or internal */\n};\n\n/**\n * @brief CUDD generator.\n */\nstruct DdGen {\n    DdManager\t*manager;\n    int\t\ttype;\n    int\t\tstatus;\n    union {\n\tstruct {\n\t    int\t\t\t*cube;\n\t    CUDD_VALUE_TYPE\tvalue;\n\t} cubes;\n\tstruct {\n\t    int\t\t\t*cube;\n\t    DdNode\t\t*ub;\n\t} primes;\n\tstruct {\n\t    int                 size;\n\t} nodes;\n    } gen;\n    struct {\n\tint\tsp;\n\tDdNode\t**stack;\n    } stack;\n    DdNode\t*node;\n};\n\n/**\n ** @brief CUDD hook\n **\n ** Hooks in CUDD are functions that the application registers with the\n ** manager so that they are called at appropriate times. The functions\n ** are passed the manager as argument; they should return 1 if\n ** successful and 0 otherwise.\n */\nstruct DdHook {\n    DD_HFP f;\t\t\t/**< function to be called */\n    struct DdHook *next;\t/**< next element in the list */\n};\n\n/**\n *  @brief Generic local cache item.\n */\nstruct DdLocalCacheItem {\n    DdNode *value;\n#ifdef DD_CACHE_PROFILE\n    ptrint count;\n#endif\n    DdNode *key[1];\n};\n\n/**\n *  @brief Local cache.\n */\nstruct DdLocalCache {\n    DdLocalCacheItem *item;\n    unsigned int itemsize;\n    unsigned int keysize;\n    unsigned int slots;\n    int shift;\n    double lookUps;\n    double minHit;\n    double hits;\n    unsigned int maxslots;\n    DdManager *manager;\n    struct DdLocalCache *next;\n};\n\n/**\n *  @brief Local hash table item.\n */\nstruct DdHashItem {\n    struct DdHashItem *next;\t/**< collision list link */\n    ptrint count;\t\t/**< reference count of item */\n    DdNode *value;\t\t/**< value %DD */\n    DdNode *key[1];\t\t/**< key pointers */\n};\n\n/**\n * @brief Local hash table.\n */\nstruct DdHashTable {\n    unsigned int keysize;\t/**< number of pointers in the key */\n    unsigned int itemsize;\t/**< size of hash table item in bytes */\n    DdHashItem **bucket;\t/**< array of buckets */\n    DdHashItem *nextFree;\t/**< item free list */\n    DdHashItem **memoryList;\t/**< list of memory blocks for items */\n    unsigned int numBuckets;\t/**< number of buckets in array */\n    int shift;\t\t\t/**< shift used in hash function */\n    unsigned int size;\t\t/**< number of items stored in table */\n    unsigned int maxsize;\t/**< threshold for table resizing */\n    DdManager *manager;\t\t/**< %DD manager */\n};\n\n/**\n *  @brief Computed table.\n */\nstruct DdCache {\n    DdNode *f,*g;\t\t/**< DDs */\n    ptruint h;\t\t\t/**< either operator or %DD */\n    DdNode *data;\t\t/**< already constructed %DD */\n#ifdef DD_CACHE_PROFILE\n    ptrint count;\t\t/**< statistical counter */\n#endif\n};\n\n/**\n *  @brief Subtable for one index.\n */\nstruct DdSubtable {\n    DdNode **nodelist;\t\t/**< hash table */\n    int shift;\t\t\t/**< shift for hash function */\n    unsigned int slots;\t\t/**< size of the hash table */\n    unsigned int keys;\t\t/**< number of nodes stored in this table */\n    unsigned int maxKeys;\t/**< slots * DD_MAX_SUBTABLE_DENSITY */\n    unsigned int dead;\t\t/**< number of dead nodes in this table */\n    unsigned int next;\t\t/**< index of next variable in group */\n    int bindVar;\t\t/**< flag to bind this variable to its level */\n    /* Fields for lazy sifting. */\n    Cudd_VariableType varType;  /**< variable type (ps, ns, pi) */\n    int pairIndex;              /**< corresponding variable index (ps <-> ns) */\n    int varHandled;\t\t/**< flag: 1 means variable is already handled */\n    Cudd_LazyGroupType varToBeGrouped; /**< tells what grouping to apply */\n};\n\n/**\n *  @brief Specialized %DD symbol table.\n */\nstruct DdManager {\n    /* Constants */\n    DdNode sentinel;\t\t/**< for collision lists */\n    DdNode *one;\t\t/**< constant 1 */\n    DdNode *zero;\t\t/**< constant 0 */\n    DdNode *plusinfinity;\t/**< plus infinity */\n    DdNode *minusinfinity;\t/**< minus infinity */\n    DdNode *background;\t\t/**< background value */\n    /* Computed Table */\n    DdCache *acache;\t\t/**< address of allocated memory for cache */\n    DdCache *cache;\t\t/**< the cache-based computed table */\n    unsigned int cacheSlots;\t/**< total number of cache entries */\n    int cacheShift;\t\t/**< shift value for cache hash function */\n    double cacheMisses;\t\t/**< number of cache misses (since resizing) */\n    double cacheHits;\t\t/**< number of cache hits (since resizing) */\n    double minHit;\t\t/**< hit percentage above which to resize */\n    int cacheSlack;\t\t/**< slots still available for resizing */\n    unsigned int maxCacheHard;\t/**< hard limit for cache size */\n    /* Unique Table */\n    int size;\t\t\t/**< number of unique subtables */\n    int sizeZ;\t\t\t/**< for %ZDD */\n    int maxSize;\t\t/**< max number of subtables before resizing */\n    int maxSizeZ;\t\t/**< for %ZDD */\n    DdSubtable *subtables;\t/**< array of unique subtables */\n    DdSubtable *subtableZ;\t/**< for %ZDD */\n    DdSubtable constants;\t/**< unique subtable for the constants */\n    unsigned int slots;\t\t/**< total number of hash buckets */\n    unsigned int keys;\t\t/**< total number of %BDD and %ADD nodes */\n    unsigned int keysZ;\t\t/**< total number of %ZDD nodes */\n    unsigned int dead;\t\t/**< total number of dead %BDD and %ADD nodes */\n    unsigned int deadZ;\t\t/**< total number of dead %ZDD nodes */\n    unsigned int maxLive;\t/**< maximum number of live nodes */\n    unsigned int minDead;\t/**< do not GC if fewer than these dead */\n    int gcEnabled;\t\t/**< gc is enabled */\n    double gcFrac;\t\t/**< gc when this fraction is dead */\n    unsigned int looseUpTo;\t/**< slow growth beyond this limit */\n\t\t\t\t/**< (measured w.r.t. slots, not keys) */\n    unsigned int initSlots;\t/**< initial size of a subtable */\n    DdNode **stack;\t\t/**< stack for iterative procedures */\n    double allocated;\t\t/**< number of nodes allocated */\n\t\t\t\t/**< (not during reordering) */\n    double reclaimed;\t\t/**< number of nodes brought back from the dead */\n    int *perm;\t\t\t/**< current variable perm. (index to level) */\n    int *permZ;\t\t\t/**< for %ZDD */\n    int *invperm;\t\t/**< current inv. var. perm. (level to index) */\n    int *invpermZ;\t\t/**< for %ZDD */\n    DdNode **vars;\t\t/**< projection functions */\n    int *map;\t\t\t/**< variable map for fast swap */\n    DdNode **univ;\t\t/**< %ZDD 1 for each variable */\n    unsigned int isolated;\t/**< isolated projection functions */\n    unsigned int originalSize;\t/**< used by lazy sifting */\n    int linearSize;\t\t/**< number of rows and columns of linear */\n    ptruint *interact;\t\t/**< interacting variable matrix */\n    ptruint *linear;\t\t/**< linear transform matrix */\n    /* Memory Management */\n    DdNode **memoryList;\t/**< memory manager for symbol table */\n    DdNode *nextFree;\t\t/**< list of free nodes */\n    char *stash;\t\t/**< memory reserve */\n#ifndef DD_NO_DEATH_ROW\n    DdNode **deathRow;\t\t/**< queue for dereferencing */\n    int deathRowDepth;\t\t/**< number of slots in the queue */\n    int nextDead;\t\t/**< index in the queue */\n    unsigned deadMask;\t\t/**< mask for circular index update */\n#endif\n    /* General Parameters */\n    CUDD_VALUE_TYPE epsilon;\t/**< tolerance on comparisons */\n    /* Dynamic Reordering Parameters */\n    int reordered;\t\t/**< flag set at the end of reordering */\n    unsigned int reorderings;\t/**< number of calls to Cudd_ReduceHeap */\n    unsigned int maxReorderings;/**< maximum number of calls to Cudd_ReduceHeap */\n    int siftMaxVar;\t\t/**< maximum number of vars sifted */\n    int siftMaxSwap;\t\t/**< maximum number of swaps per sifting */\n    int ddTotalNumberSwapping;  /**< number of %BDD/%ADD swaps completed */\n    int zddTotalNumberSwapping; /**< number of %ZDD swaps completed */\n    int reordCycle;\t\t/**< how often to apply alternate threshold */\n    double maxGrowth;\t\t/**< maximum growth during reordering */\n    double maxGrowthAlt;\t/**< alternate maximum growth for reordering */\n    int autoDyn;\t\t/**< automatic dynamic reordering flag (BDD) */\n    int autoDynZ;\t\t/**< automatic dynamic reordering flag (ZDD) */\n    Cudd_ReorderingType autoMethod;  /**< default reordering method */\n    Cudd_ReorderingType autoMethodZ; /**< default reordering method (ZDD) */\n    int realign;\t\t/**< realign %ZDD order after %BDD reordering */\n    int realignZ;\t\t/**< realign %BDD order after %ZDD reordering */\n    unsigned int nextDyn;\t/**< reorder if this size is reached */\n    unsigned int countDead;\t/**< if 0, count deads to trigger reordering */\n    MtrNode *tree;\t\t/**< variable group tree (BDD) */\n    MtrNode *treeZ;\t\t/**< variable group tree (ZDD) */\n    Cudd_AggregationType groupcheck; /**< used during group sifting */\n    int recomb;\t\t\t/**< used during group sifting */\n    int symmviolation;\t\t/**< used during group sifting */\n    int arcviolation;\t\t/**< used during group sifting */\n    int populationSize;\t\t/**< population size for GA */\n    int\tnumberXovers;\t\t/**< number of crossovers for GA */\n    unsigned int randomizeOrder; /**< perturb the next reordering threshold */\n    DdLocalCache *localCaches;\t/**< local caches currently in existence */\n    void *hooks;\t\t/**< application-specific field (used by vis) */\n    DdHook *preGCHook;\t\t/**< hooks to be called before GC */\n    DdHook *postGCHook;\t\t/**< hooks to be called after GC */\n    DdHook *preReorderingHook;\t/**< hooks to be called before reordering */\n    DdHook *postReorderingHook;\t/**< hooks to be called after reordering */\n    FILE *out;\t\t\t/**< stdout for this manager */\n    FILE *err;\t\t\t/**< stderr for this manager */\n    Cudd_ErrorType errorCode;\t/**< info on last error */\n    unsigned long startTime;\t/**< start time in milliseconds */\n    unsigned long timeLimit;\t/**< CPU time limit */\n    DD_THFP terminationCallback; /**< termination callback */\n    void * tcbArg;\t\t/**< second argument passed to termination handler */\n    DD_OOMFP outOfMemCallback;\t/**< out-of-memory callback */\n    DD_TOHFP timeoutHandler;\t/**< timeout handler */\n    void * tohArg;\t\t/**< second argument passed to timeout handler */\n    /* Statistical counters. */\n    size_t memused;\t\t/**< total memory allocated for the manager */\n    size_t maxmem;\t\t/**< target maximum memory */\n    size_t maxmemhard;\t\t/**< hard limit for maximum memory */\n    int garbageCollections;\t/**< number of garbage collections */\n    unsigned long GCTime;\t/**< total time spent in garbage collection */\n    unsigned long reordTime;\t/**< total time spent in reordering */\n    double totCachehits;\t/**< total number of cache hits */\n    double totCacheMisses;\t/**< total number of cache misses */\n    double cachecollisions;\t/**< number of cache collisions */\n    double cacheinserts;\t/**< number of cache insertions */\n    double cacheLastInserts;\t/**< insertions at the last cache resizing */\n    double cachedeletions;\t/**< number of deletions during garbage coll. */\n    unsigned int peakLiveNodes;\t/**< maximum number of live nodes */\n    /* Random number generator. */\n    int32_t cuddRand;\t\t/**< state of the random number generator */\n    int32_t cuddRand2;\t\t/**< state of the random number generator */\n    int32_t shuffleSelect;\t/**< state of the random number generator */\n    int32_t shuffleTable[STAB_SIZE]; /**< state of the random number generator */\n#ifdef DD_STATS\n    double nodesFreed;\t\t/**< number of nodes returned to the free list */\n    double nodesDropped;\t/**< number of nodes killed by dereferencing */\n    int\ttotalNISwaps;\t\t/**< number of non-interacting (cheap) swaps */\n    int extsymmcalls;\t\t/**< number of calls to symmetry check fn */\n    int extsymm;\t\t/**< number of successful symmetry checks */\n    int secdiffcalls;\t\t/**< number of calls to second difference fn */\n    int secdiff;\t\t/**< number of successful second diff. checks */\n    int secdiffmisfire;\t\t/**< number of misfired second diff. checks */\n    int tosses;\t\t\t/**< number of coin tosses in annealing */\n    int acceptances;\t\t/**< number of acceptances in annealing */\n    int totalShuffles;\t\t/**< number of shuffles in exact reordering */\n    int totalNumberLinearTr;\t/**< number of linear transformations */\n    int num_calls;\t\t/**< should equal 2n-1 (n is the # of nodes) */\n#endif\n#ifdef DD_UNIQUE_PROFILE\n    double uniqueLookUps;\t/**< number of unique table lookups */\n    double uniqueLinks;\t\t/**< total distance traveled in coll. chains */\n#endif\n#ifdef DD_COUNT\n    double recursiveCalls;\t/**< number of recursive calls */\n#ifdef DD_STATS\n    double nextSample;\t\t/**< when to write next line of stats */\n#endif\n    double swapSteps;\t\t/**< number of elementary reordering steps */\n#endif\n#ifdef DD_DEBUG\n    int addPermuteRecurHits;\t/**< debug variable for variable permutation */\n    int bddPermuteRecurHits;\t/**< debug variable for variable permutation */\n    int bddVectorComposeHits;\t/**< debug variable for vector composition */\n    int addVectorComposeHits;\t/**< debug variable for vector composition */\n    int addGeneralVectorComposeHits; /**< debug var. for vector composition */\n    int enableExtraDebug;\t/**< deposit a 1 here to enable more debugging */\n#endif\n};\n\n/**\n *  @brief Reordering move record.\n */\nstruct Move {\n    DdHalfWord x;\n    DdHalfWord y;\n    unsigned int flags;\n    int size;\n    struct Move *next;\n};\n\n/**\n *  @brief Used to sort variables for reordering.\n */\nstruct IndexKey {\n    int index;\n    int keys;\n};\n\n/**\n *  @brief Generic level queue item.\n */\nstruct DdQueueItem {\n    struct DdQueueItem *next;\n    struct DdQueueItem *cnext;\n    void *key;\n};\n\n/**\n *  @brief Level queue.\n */\nstruct DdLevelQueue {\n    void *first;\n    DdQueueItem **last;\n    DdQueueItem *freelist;\n    DdQueueItem **buckets;\n    int levels;\n    int itemsize;\n    int size;\n    int maxsize;\n    int numBuckets;\n    int shift;\n    DdManager *manager;\n};\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Adds node to the head of the free list.\n\n  @details Does not deallocate memory chunks that become free.  This\n  function is also used by the dynamic reordering functions.\n\n  @sideeffect None\n\n  @see cuddAllocNode cuddDynamicAllocNode cuddDeallocMove\n\n*/\n#define cuddDeallocNode(unique,node) \\\n    (node)->next = (unique)->nextFree; \\\n    (unique)->nextFree = node;\n\n/**\n  @brief Adds node to the head of the free list.\n\n  @details Does not deallocate memory chunks that become free.  This\n  function is also used by the dynamic reordering functions.\n\n  @sideeffect None\n\n  @see cuddDeallocNode cuddDynamicAllocNode\n\n*/\n#define cuddDeallocMove(unique,node) \\\n    ((DdNode *)(node))->ref = 0; \\\n    ((DdNode *)(node))->next = (unique)->nextFree; \\\n    (unique)->nextFree = (DdNode *)(node);\n\n\n/**\n  @brief Increases the reference count of a node, if it is not\n  saturated.\n\n  @details This being a macro, it is faster than Cudd_Ref, but it\n  cannot be used in constructs like cuddRef(a = b()).\n\n  @sideeffect none\n\n  @see Cudd_Ref\n\n*/\n#define cuddRef(n) cuddSatInc(Cudd_Regular(n)->ref)\n\n\n/**\n  @brief Decreases the reference count of a node, if it is not\n  saturated.\n\n  @details It is primarily used in recursive procedures to decrease\n  the ref count of a result node before returning it. This\n  accomplishes the goal of removing the protection applied by a\n  previous cuddRef. This being a macro, it is faster than Cudd_Deref,\n  but it cannot be used in constructs like cuddDeref(a = b()).\n\n  @sideeffect none\n\n  @see Cudd_Deref\n\n*/\n#define cuddDeref(n) cuddSatDec(Cudd_Regular(n)->ref)\n\n\n/**\n  @brief Returns 1 if the node is a constant node.\n\n  @details Returns 1 if the node is a constant node (rather than an\n  internal node). All constant nodes have the same index\n  (CUDD_CONST_INDEX). The pointer passed to Cudd_IsConstantInt may be either\n  regular or complemented.\n\n  @sideeffect none\n\n  @see cuddIsConstant Cudd_IsConstant\n\n*/\n#define Cudd_IsConstantInt(node) ((Cudd_Regular(node))->index == CUDD_CONST_INDEX)\n\n\n/**\n  @brief Returns 1 if the node is a constant node.\n\n  @details Returns 1 if the node is a constant node (rather than an\n  internal node). All constant nodes have the same index\n  (CUDD_CONST_INDEX). The pointer passed to cuddIsConstant must be regular.\n\n  @sideeffect none\n\n  @see Cudd_IsConstant Cudd_IsConstantInt\n\n*/\n#define cuddIsConstant(node) ((node)->index == CUDD_CONST_INDEX)\n\n\n/**\n  @brief Returns the then child of an internal node.\n\n  @details If <code>node</code> is a constant node, the result is\n  unpredictable.  The pointer passed to cuddT must be regular.\n\n  @sideeffect none\n\n  @see Cudd_T\n\n*/\n#define cuddT(node) ((node)->type.kids.T)\n\n\n/**\n  @brief Returns the else child of an internal node.\n\n  @details If <code>node</code> is a constant node, the result is\n  unpredictable.  The pointer passed to cuddE must be regular.\n\n  @sideeffect none\n\n  @see Cudd_E\n\n*/\n#define cuddE(node) ((node)->type.kids.E)\n\n\n/**\n  @brief Returns the value of a constant node.\n\n  @details If <code>node</code> is an internal node, the result is\n  unpredictable.  The pointer passed to cuddV must be regular.\n\n  @sideeffect none\n\n  @see Cudd_V\n\n*/\n#define cuddV(node) ((node)->type.value)\n\n\n/**\n  @brief Finds the current position of variable index in the\n  order.\n\n  @details This macro duplicates the functionality of Cudd_ReadPerm,\n  but it does not check for out-of-bounds indices and it is more\n  efficient.\n\n  @sideeffect none\n\n  @see Cudd_ReadPerm\n\n*/\n#define cuddI(dd,index) (((index)==CUDD_CONST_INDEX)?(int)(index):(dd)->perm[(index)])\n\n\n/**\n  @brief Finds the current position of %ZDD variable index in the\n  order.\n\n  @details This macro duplicates the functionality of\n  Cudd_ReadPermZdd, but it does not check for out-of-bounds indices\n  and it is more efficient.\n\n  @sideeffect none\n\n  @see Cudd_ReadPermZdd\n\n*/\n#define cuddIZ(dd,index) (((index)==CUDD_CONST_INDEX)?(int)(index):(dd)->permZ[(index)])\n\n\n/**\n  @brief Hash function for the unique table.\n\n  @details \n\n  @sideeffect none\n\n  @see ddCHash ddCHash2\n\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define ddHash(f,g,s) \\\n((((unsigned)(ptruint)(f) * DD_P1 + \\\n   (unsigned)(ptruint)(g)) * DD_P2) >> (s))\n#else\n#define ddHash(f,g,s) \\\n((((unsigned)(f) * DD_P1 + (unsigned)(g)) * DD_P2) >> (s))\n#endif\n\n\n/**\n  @brief Hash function for the cache.\n\n  @sideeffect none\n\n  @see ddHash ddCHash2\n\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define ddCHash(o,f,g,h,s) \\\n((((((unsigned)(ptruint)(f) + (unsigned)(ptruint)(o)) * DD_P1 + \\\n    (unsigned)(ptruint)(g)) * DD_P2 + \\\n   (unsigned)(ptruint)(h)) * DD_P3) >> (s))\n#else\n#define ddCHash(o,f,g,h,s) \\\n((((((unsigned)(f) + (unsigned)(o)) * DD_P1 + (unsigned)(g)) * DD_P2 + \\\n   (unsigned)(h)) * DD_P3) >> (s))\n#endif\n\n\n/**\n  @brief Hash function for the cache for functions with two operands.\n\n  @sideeffect none\n\n  @see ddHash ddCHash\n\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define ddCHash2(o,f,g,s) \\\n(((((unsigned)(ptruint)(f) + (unsigned)(ptruint)(o)) * DD_P1 + \\\n   (unsigned)(ptruint)(g)) * DD_P2) >> (s))\n#else\n#define ddCHash2(o,f,g,s) \\\n(((((unsigned)(f) + (unsigned)(o)) * DD_P1 + (unsigned)(g)) * DD_P2) >> (s))\n#endif\n\n\n/**\n  @brief Clears the 4 least significant bits of a pointer.\n\n  @sideeffect none\n\n*/\n#define cuddClean(p) ((DdNode *)((ptruint)(p) & ~ (ptruint) 0xf))\n\n\n/**\n  @brief Computes the minimum of two numbers.\n\n  @sideeffect none\n\n  @see ddMax\n\n*/\n#define ddMin(x,y) (((y) < (x)) ? (y) : (x))\n\n\n/**\n  @brief Computes the maximum of two numbers.\n\n  @sideeffect none\n\n  @see ddMin\n\n*/\n#define ddMax(x,y) (((y) > (x)) ? (y) : (x))\n\n\n/**\n  @brief Computes the absolute value of a number.\n\n  @sideeffect none\n\n*/\n#define ddAbs(x) (((x)<0) ? -(x) : (x))\n\n\n/**\n  @brief Returns 1 if the absolute value of the difference of the two\n  arguments x and y is less than e.\n\n  @sideeffect none\n\n*/\n#define ddEqualVal(x,y,e) (ddAbs((x)-(y))<(e))\n\n\n/**\n  @brief Saturating increment operator.\n\n  @details Saturation is only necessary on 32-bit machines, where the\n  reference count is only 16-bit wide.\n\n  @sideeffect none\n\n  @see cuddSatDec\n\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define cuddSatInc(x) ((x)++)\n#else\n#define cuddSatInc(x) ((x) += (x) != (DdHalfWord)DD_MAXREF)\n#endif\n\n\n/**\n  @brief Saturating decrement operator.\n\n  @details Saturation is only necessary on 32-bit machines, where the\n  reference count is only 16-bit wide.\n\n  @sideeffect none\n\n  @see cuddSatInc\n\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define cuddSatDec(x) ((x)--)\n#else\n#define cuddSatDec(x) ((x) -= (x) != (DdHalfWord)DD_MAXREF)\n#endif\n\n\n/**\n  @brief Returns the constant 1 node.\n\n  @sideeffect none\n\n  @see DD_ZERO DD_PLUS_INFINITY DD_MINUS_INFINITY\n\n*/\n#define DD_ONE(dd)\t\t((dd)->one)\n\n\n/**\n  @brief Returns the arithmetic 0 constant node.\n\n  @details This is different from the logical zero. The latter is\n  obtained by Cudd_Not(DD_ONE(dd)).\n\n  @sideeffect none\n\n  @see DD_ONE Cudd_Not DD_PLUS_INFINITY DD_MINUS_INFINITY\n\n*/\n#define DD_ZERO(dd) ((dd)->zero)\n\n\n/**\n  @brief Returns the plus infinity constant node.\n\n  @sideeffect none\n\n  @see DD_ONE DD_ZERO DD_MINUS_INFINITY\n\n*/\n#define DD_PLUS_INFINITY(dd) ((dd)->plusinfinity)\n\n\n/**\n  @brief Returns the minus infinity constant node.\n\n  @sideeffect none\n\n  @see DD_ONE DD_ZERO DD_PLUS_INFINITY\n\n*/\n#define DD_MINUS_INFINITY(dd) ((dd)->minusinfinity)\n\n\n/**\n  @brief Enforces DD_MINUS_INF_VAL <= x <= DD_PLUS_INF_VAL.\n\n  @details Furthermore, if x <= DD_MINUS_INF_VAL/2, x is set to\n  DD_MINUS_INF_VAL. Similarly, if DD_PLUS_INF_VAL/2 <= x, x is set to\n  DD_PLUS_INF_VAL.  Normally this macro is a NOOP. However, if\n  HAVE_IEEE_754 is not defined, it makes sure that a value does not\n  get larger than infinity in absolute value, and once it gets to\n  infinity, stays there.  If the value overflows before this macro is\n  applied, no recovery is possible.\n\n  @sideeffect none\n\n*/\n#ifdef HAVE_IEEE_754\n#define cuddAdjust(x)\n#else\n#define cuddAdjust(x)\t\t((x) = ((x) >= DD_CRI_HI_MARK) ? DD_PLUS_INF_VAL : (((x) <= DD_CRI_LO_MARK) ? DD_MINUS_INF_VAL : (x)))\n#endif\n\n\n/**\n  @brief Outputs a line of stats.\n\n  @details Outputs a line of stats if DD_COUNT and DD_STATS are\n  defined. Increments the number of recursive calls if DD_COUNT is\n  defined.\n\n  @sideeffect None\n\n*/\n#ifdef DD_COUNT\n#ifdef DD_STATS\n#define statLine(dd)                                                    \\\n    do {                                                                \\\n        (dd)->recursiveCalls++;                                         \\\n        if ((dd)->recursiveCalls == (dd)->nextSample) {                 \\\n            (void) fprintf((dd)->err,                                   \\\n                           \"@%.0f: %u nodes %u live %.0f dropped\"       \\\n                           \" %.0f reclaimed\\n\",                         \\\n                           (dd)->recursiveCalls, (dd)->keys,            \\\n                           (dd)->keys - (dd)->dead,                     \\\n                           (dd)->nodesDropped, (dd)->reclaimed);        \\\n            (dd)->nextSample += 250000;}                                \\\n    } while (0)\n#else\n#define statLine(dd) (dd)->recursiveCalls++\n#endif\n#else\n#define statLine(dd)\n#endif\n\n\n/**\n  @brief Checks for termination or timeout.\n*/\n#define checkWhetherToGiveUp(dd)                                        \\\n    do {                                                                \\\n        if (((int64_t) CUDD_CHECK_MASK & (int64_t) (dd)->cacheMisses) == 0) { \\\n            if ((dd)->terminationCallback != NULL &&                    \\\n                (dd)->terminationCallback((dd)->tcbArg)) {              \\\n                (dd)->errorCode = CUDD_TERMINATION;                     \\\n                return(NULL);                                           \\\n            }                                                           \\\n            if (util_cpu_time() - (dd)->startTime > (dd)->timeLimit) {  \\\n                (dd)->errorCode = CUDD_TIMEOUT_EXPIRED;                 \\\n                return(NULL);                                           \\\n            }                                                           \\\n        }                                                               \\\n    } while (0)\n\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nextern DdNode * cuddAddExistAbstractRecur(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * cuddAddUnivAbstractRecur(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * cuddAddOrAbstractRecur(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * cuddAddMinAbstractRecur(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * cuddAddMaxAbstractRecur(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * cuddAddFirstFilterRecur(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * cuddAddApplyRecur(DdManager *dd, DdNode * (*)(DdManager *, DdNode **, DdNode **), DdNode *f, DdNode *g);\nextern DdNode * cuddAddMonadicApplyRecur(DdManager * dd, DdNode * (*op)(DdManager *, DdNode *), DdNode * f);\nextern DdNode * cuddAddScalarInverseRecur(DdManager *dd, DdNode *f, DdNode *epsilon);\nextern DdNode * cuddAddIteRecur(DdManager *dd, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * cuddAddCmplRecur(DdManager *dd, DdNode *f);\nextern DdNode * cuddAddNegateRecur(DdManager *dd, DdNode *f);\nextern DdNode * cuddAddRoundOffRecur(DdManager *dd, DdNode *f, double trunc);\nextern DdNode * cuddUnderApprox(DdManager *dd, DdNode *f, int numVars, int threshold, int safe, double quality);\nextern DdNode * cuddRemapUnderApprox(DdManager *dd, DdNode *f, int numVars, int threshold, double quality);\nextern DdNode * cuddBiasedUnderApprox(DdManager *dd, DdNode *f, DdNode *b, int numVars, int threshold, double quality1, double quality0);\nextern DdNode * cuddBddAndAbstractRecur(DdManager *manager, DdNode *f, DdNode *g, DdNode *cube);\nextern int cuddAnnealing(DdManager *table, int lower, int upper);\nextern DdNode * cuddBddExistAbstractRecur(DdManager *manager, DdNode *f, DdNode *cube);\nextern DdNode * cuddBddXorExistAbstractRecur(DdManager *manager, DdNode *f, DdNode *g, DdNode *cube);\nextern DdNode * cuddBddBooleanDiffRecur(DdManager *manager, DdNode *f, DdNode *var);\nextern DdNode * cuddBddIteRecur(DdManager *dd, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * cuddBddIntersectRecur(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * cuddBddAndRecur(DdManager *manager, DdNode *f, DdNode *g);\nextern DdNode * cuddBddXorRecur(DdManager *manager, DdNode *f, DdNode *g);\nextern DdNode * cuddBddTransfer(DdManager *ddS, DdManager *ddD, DdNode *f);\nextern DdNode * cuddAddBddDoPattern(DdManager *dd, DdNode *f);\nextern int cuddInitCache(DdManager *unique, unsigned int cacheSize, unsigned int maxCacheSize);\nextern void cuddCacheInsert(DdManager *table, ptruint op, DdNode *f, DdNode *g, DdNode *h, DdNode *data);\nextern void cuddCacheInsert2(DdManager *table, DdNode * (*)(DdManager *, DdNode *, DdNode *), DdNode *f, DdNode *g, DdNode *data);\nextern void cuddCacheInsert1(DdManager *table, DdNode * (*)(DdManager *, DdNode *), DdNode *f, DdNode *data);\nextern DdNode * cuddCacheLookup(DdManager *table, ptruint op, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * cuddCacheLookupZdd(DdManager *table, ptruint op, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * cuddCacheLookup2(DdManager *table, DdNode * (*)(DdManager *, DdNode *, DdNode *), DdNode *f, DdNode *g);\nextern DdNode * cuddCacheLookup1(DdManager *table, DdNode * (*)(DdManager *, DdNode *), DdNode *f);\nextern DdNode * cuddCacheLookup2Zdd(DdManager *table, DdNode * (*)(DdManager *, DdNode *, DdNode *), DdNode *f, DdNode *g);\nextern DdNode * cuddCacheLookup1Zdd(DdManager *table, DdNode * (*)(DdManager *, DdNode *), DdNode *f);\nextern DdNode * cuddConstantLookup(DdManager *table, ptruint op, DdNode *f, DdNode *g, DdNode *h);\nextern int cuddCacheProfile(DdManager *table, FILE *fp);\nextern void cuddCacheResize(DdManager *table);\nextern void cuddCacheFlush(DdManager *table);\nextern int cuddComputeFloorLog2(unsigned int value);\nextern int cuddHeapProfile(DdManager *dd);\nextern void cuddPrintNode(DdNode *f, FILE *fp);\nextern void cuddPrintVarGroups(DdManager * dd, MtrNode * root, int zdd, int silent);\nextern DdNode * cuddBddClippingAnd(DdManager *dd, DdNode *f, DdNode *g, int maxDepth, int direction);\nextern DdNode * cuddBddClippingAndAbstract(DdManager *dd, DdNode *f, DdNode *g, DdNode *cube, int maxDepth, int direction);\nextern void cuddGetBranches(DdNode *g, DdNode **g1, DdNode **g0);\nextern DdNode * cuddCofactorRecur(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * cuddBddComposeRecur(DdManager *dd, DdNode *f, DdNode *g, DdNode *proj);\nextern DdNode * cuddAddComposeRecur(DdManager *dd, DdNode *f, DdNode *g, DdNode *proj);\nextern int cuddExact(DdManager *table, int lower, int upper);\nextern DdNode * cuddBddConstrainRecur(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * cuddBddRestrictRecur(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * cuddBddNPAndRecur(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * cuddAddConstrainRecur(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * cuddAddRestrictRecur(DdManager *dd, DdNode *f, DdNode *c);\nextern DdNode * cuddBddLICompaction(DdManager *dd, DdNode *f, DdNode *c);\nextern int cuddGa(DdManager *table, int lower, int upper);\nextern int cuddTreeSifting(DdManager *table, Cudd_ReorderingType method);\nextern int cuddZddInitUniv(DdManager *zdd);\nextern void cuddZddFreeUniv(DdManager *zdd);\nextern void cuddSetInteract(DdManager *table, int x, int y);\nextern int cuddTestInteract(DdManager *table, int x, int y);\nextern int cuddInitInteract(DdManager *table);\nextern DdLocalCache * cuddLocalCacheInit(DdManager *manager, unsigned int keySize, unsigned int cacheSize, unsigned int maxCacheSize);\nextern void cuddLocalCacheQuit(DdLocalCache *cache);\nextern void cuddLocalCacheInsert(DdLocalCache *cache, DdNodePtr *key, DdNode *value);\nextern DdNode * cuddLocalCacheLookup(DdLocalCache *cache, DdNodePtr *key);\nextern void cuddLocalCacheClearDead(DdManager *manager);\nextern int cuddIsInDeathRow(DdManager *dd, DdNode *f);\nextern int cuddTimesInDeathRow(DdManager *dd, DdNode *f);\nextern void cuddLocalCacheClearAll(DdManager *manager);\n#ifdef DD_CACHE_PROFILE\nextern int cuddLocalCacheProfile(DdLocalCache *cache);\n#endif\nextern DdHashTable * cuddHashTableInit(DdManager *manager, unsigned int keySize, unsigned int initSize);\nextern void cuddHashTableQuit(DdHashTable *hash);\nextern void cuddHashTableGenericQuit(DdHashTable *hash);\nextern int cuddHashTableInsert(DdHashTable *hash, DdNodePtr *key, DdNode *value, ptrint count);\nextern DdNode * cuddHashTableLookup(DdHashTable *hash, DdNodePtr *key);\nextern int cuddHashTableInsert1(DdHashTable *hash, DdNode *f, DdNode *value, ptrint count);\nextern DdNode * cuddHashTableLookup1(DdHashTable *hash, DdNode *f);\nextern int cuddHashTableInsert2(DdHashTable *hash, DdNode *f, DdNode *g, DdNode *value, ptrint count);\nextern DdNode * cuddHashTableLookup2(DdHashTable *hash, DdNode *f, DdNode *g);\nextern int cuddHashTableInsert3(DdHashTable *hash, DdNode *f, DdNode *g, DdNode *h, DdNode *value, ptrint count);\nextern DdNode * cuddHashTableLookup3(DdHashTable *hash, DdNode *f, DdNode *g, DdNode *h);\nextern int cuddHashTableGenericInsert(DdHashTable * hash, DdNode * f, void * value);\nextern void * cuddHashTableGenericLookup(DdHashTable * hash, DdNode * f);\nextern DdLevelQueue * cuddLevelQueueInit(int levels, int itemSize, int numBuckets, DdManager * manager);\nextern void cuddLevelQueueQuit(DdLevelQueue *queue);\nextern void * cuddLevelQueueFirst(DdLevelQueue * queue, void * key, int  level);\nextern void * cuddLevelQueueEnqueue(DdLevelQueue *queue, void *key, int level);\nextern void cuddLevelQueueDequeue(DdLevelQueue *queue, int level);\nextern int cuddLinearAndSifting(DdManager *table, int lower, int upper);\nextern int cuddLinearInPlace(DdManager * table, int  x, int  y);\nextern void cuddUpdateInteractionMatrix(DdManager * table, int  xindex, int  yindex);\nextern int cuddInitLinear(DdManager *table);\nextern int cuddResizeLinear(DdManager *table);\nextern DdNode * cuddBddLiteralSetIntersectionRecur(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * cuddCProjectionRecur(DdManager *dd, DdNode *R, DdNode *Y, DdNode *Ysupp);\nextern DdNode * cuddBddClosestCube(DdManager *dd, DdNode *f, DdNode *g, CUDD_VALUE_TYPE bound);\nextern void cuddReclaim(DdManager *table, DdNode *n);\nextern void cuddReclaimZdd(DdManager *table, DdNode *n);\nextern void cuddClearDeathRow(DdManager *table);\nextern void cuddShrinkDeathRow(DdManager *table);\nextern DdNode * cuddDynamicAllocNode(DdManager *table);\nextern int cuddSifting(DdManager *table, int lower, int upper);\nextern int cuddSwapping(DdManager *table, int lower, int upper, Cudd_ReorderingType heuristic);\nextern int cuddNextHigh(DdManager *table, int x);\nextern int cuddNextLow(DdManager *table, int x);\nextern int cuddSwapInPlace(DdManager *table, int x, int y);\nextern int cuddBddAlignToZdd(DdManager *table);\nextern DdNode * cuddBddMakePrime(DdManager *dd, DdNode *cube, DdNode *f);\nextern DdNode * cuddSolveEqnRecur(DdManager *bdd, DdNode *F, DdNode *Y, DdNode **G, int n, int *yIndex, int i);\nextern DdNode * cuddVerifySol(DdManager *bdd, DdNode *F, DdNode **G, int *yIndex, int n);\n#ifdef ST_H_\nextern DdNode* cuddSplitSetRecur(DdManager *manager, st_table *mtable, int *varSeen, DdNode *p, double n, double max, int index);\n#endif\nextern DdNode * cuddSubsetHeavyBranch(DdManager *dd, DdNode *f, int numVars, int threshold);\nextern DdNode * cuddSubsetShortPaths(DdManager *dd, DdNode *f, int numVars, int threshold, int hardlimit);\nextern int cuddSymmCheck(DdManager *table, int x, int y);\nextern int cuddSymmSifting(DdManager *table, int lower, int upper);\nextern int cuddSymmSiftingConv(DdManager *table, int lower, int upper);\nextern DdNode * cuddAllocNode(DdManager *unique);\nextern DdManager * cuddInitTable(unsigned int numVars, unsigned int numVarsZ, unsigned int numSlots, unsigned int looseUpTo);\nextern void cuddFreeTable(DdManager *unique);\nextern int cuddGarbageCollect(DdManager *unique, int clearCache);\nextern DdNode * cuddZddGetNode(DdManager *zdd, int id, DdNode *T, DdNode *E);\nextern DdNode * cuddZddGetNodeIVO(DdManager *dd, int index, DdNode *g, DdNode *h);\nextern DdNode * cuddUniqueInter(DdManager *unique, int index, DdNode *T, DdNode *E);\nextern DdNode * cuddUniqueInterIVO(DdManager *unique, int index, DdNode *T, DdNode *E);\nextern DdNode * cuddUniqueInterZdd(DdManager *unique, int index, DdNode *T, DdNode *E);\nextern DdNode * cuddUniqueConst(DdManager *unique, CUDD_VALUE_TYPE value);\nextern void cuddRehash(DdManager *unique, int i);\nextern void cuddShrinkSubtable(DdManager *unique, int i);\nextern int cuddInsertSubtables(DdManager *unique, int n, int level);\nextern int cuddDestroySubtables(DdManager *unique, int n);\nextern int cuddResizeTableZdd(DdManager *unique, int index);\nextern void cuddSlowTableGrowth(DdManager *unique);\nextern int cuddP(DdManager *dd, DdNode *f);\n#ifdef ST_H_\nextern enum st_retval cuddStCountfree(void *key, void *value, void *arg);\nextern int cuddCollectNodes(DdNode *f, st_table *visited);\n#endif\nextern DdNodePtr * cuddNodeArray(DdNode *f, int *n);\nextern int cuddWindowReorder(DdManager *table, int low, int high, Cudd_ReorderingType submethod);\nextern DdNode * cuddZddProduct(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * cuddZddUnateProduct(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * cuddZddWeakDiv(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * cuddZddWeakDivF(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * cuddZddDivide(DdManager *dd, DdNode *f, DdNode *g);\nextern DdNode * cuddZddDivideF(DdManager *dd, DdNode *f, DdNode *g);\nextern int cuddZddGetCofactors3(DdManager *dd, DdNode *f, int v, DdNode **f1, DdNode **f0, DdNode **fd);\nextern int cuddZddGetCofactors2(DdManager *dd, DdNode *f, int v, DdNode **f1, DdNode **f0);\nextern DdNode * cuddZddComplement(DdManager *dd, DdNode *node);\nextern int cuddZddGetPosVarIndex(DdManager * dd, int index);\nextern int cuddZddGetNegVarIndex(DdManager * dd, int index);\nextern int cuddZddGetPosVarLevel(DdManager * dd, int index);\nextern int cuddZddGetNegVarLevel(DdManager * dd, int index);\nextern int cuddZddTreeSifting(DdManager *table, Cudd_ReorderingType method);\nextern DdNode * cuddZddIsop(DdManager *dd, DdNode *L, DdNode *U, DdNode **zdd_I);\nextern DdNode * cuddBddIsop(DdManager *dd, DdNode *L, DdNode *U);\nextern DdNode * cuddMakeBddFromZddCover(DdManager *dd, DdNode *node);\nextern int cuddZddLinearSifting(DdManager *table, int lower, int upper);\nextern int cuddZddAlignToBdd(DdManager *table);\nextern int cuddZddNextHigh(DdManager *table, int x);\nextern int cuddZddNextLow(DdManager *table, int x);\nextern int cuddZddUniqueCompare(void const *ptr_x, void const *ptr_y);\nextern int cuddZddSwapInPlace(DdManager *table, int x, int y);\nextern int cuddZddSwapping(DdManager *table, int lower, int upper, Cudd_ReorderingType heuristic);\nextern int cuddZddSifting(DdManager *table, int lower, int upper);\nextern DdNode * cuddZddIte(DdManager *dd, DdNode *f, DdNode *g, DdNode *h);\nextern DdNode * cuddZddUnion(DdManager *zdd, DdNode *P, DdNode *Q);\nextern DdNode * cuddZddIntersect(DdManager *zdd, DdNode *P, DdNode *Q);\nextern DdNode * cuddZddDiff(DdManager *zdd, DdNode *P, DdNode *Q);\nextern DdNode * cuddZddChangeAux(DdManager *zdd, DdNode *P, DdNode *zvar);\nextern DdNode * cuddZddSubset1(DdManager *dd, DdNode *P, int var);\nextern DdNode * cuddZddSubset0(DdManager *dd, DdNode *P, int var);\nextern DdNode * cuddZddChange(DdManager *dd, DdNode *P, int var);\nextern int cuddZddSymmCheck(DdManager *table, int x, int y);\nextern int cuddZddSymmSifting(DdManager *table, int lower, int upper);\nextern int cuddZddSymmSiftingConv(DdManager *table, int lower, int upper);\nextern int cuddZddP(DdManager *zdd, DdNode *f);\n\n#ifdef __cplusplus\n} /* end of extern \"C\" */\n#endif\n\n/** \\endcond */\n\n#endif /* CUDD_INT_H_ */\n"
  },
  {
    "path": "cudd/cudd/cuddInteract.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions to manipulate the variable interaction matrix.\n\n  @details The interaction matrix tells whether two variables are both\n  in the support of some function of the %DD. The main use of the\n  interaction matrix is in the in-place swapping. Indeed, if two\n  variables do not interact, there is no arc connecting the two\n  layers; therefore, the swap can be performed in constant time,\n  without scanning the subtables. Another use of the interaction\n  matrix is in the computation of the lower bounds for\n  sifting. Finally, the interaction matrix can be used to speed up\n  aggregation checks in symmetric and group sifting.<p>\n  The computation of the interaction matrix is done with a series of\n  depth-first searches. The searches start from those nodes that have\n  only external references. The matrix is stored as a packed array of\n  bits; since it is symmetric, only the upper triangle is kept in\n  memory.  As a final remark, we note that there may be variables that\n  do interact, but that for a given variable order have no arc\n  connecting their layers when they are adjacent.  For instance, in\n  ite(a,b,c) with the order a<b<c, b and c interact, but are not\n  connected.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#if SIZEOF_VOID_P == 8\n#define BPL 64\n#define LOGBPL 6\n#else\n#define BPL 32\n#define LOGBPL 5\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void ddSuppInteract (DdNode *f, char *support);\nstatic void ddClearLocal (DdNode *f);\nstatic void ddUpdateInteract (DdManager *table, char *support);\nstatic void ddClearGlobal (DdManager *table);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Set interaction matrix entries.\n\n  @details Given a pair of variables 0 <= x < y < table->size,\n  sets the corresponding bit of the interaction matrix to 1.\n\n  @sideeffect None\n\n*/\nvoid\ncuddSetInteract(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    ptruint posn, word, bit;\n\n#ifdef DD_DEBUG\n    assert(x < y);\n    assert(y < table->size);\n    assert(x >= 0);\n#endif\n\n    posn = (((((ptruint)table->size << 1) - x - 3) * x) >> 1) + y - 1;\n    word = posn >> LOGBPL;\n    bit = posn & (BPL-1);\n    table->interact[word] |= ((ptruint) 1) << bit;\n\n} /* end of cuddSetInteract */\n\n\n/**\n  @brief Test interaction matrix entries.\n\n  @details Given a pair of variables 0 <= x < y < table->size,\n  tests whether the corresponding bit of the interaction matrix is 1.\n  Returns the value of the bit.\n\n  @sideeffect None\n\n*/\nint\ncuddTestInteract(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n  ptruint posn, word, bit;\n  int result;\n\n    if (x > y) {\n\tint tmp = x;\n\tx = y;\n\ty = tmp;\n    }\n#ifdef DD_DEBUG\n    assert(x < y);\n    assert(y < table->size);\n    assert(x >= 0);\n#endif\n\n    posn = (((((ptruint)table->size << 1) - x - 3) * x) >> 1) + y - 1;\n    word = posn >> LOGBPL;\n    bit = posn & (BPL-1);\n    result = (table->interact[word] >> bit) & (ptruint) 1;\n    return(result);\n\n} /* end of cuddTestInteract */\n\n\n/**\n  @brief Initializes the interaction matrix.\n\n  @details The interaction matrix is implemented as a bit vector\n  storing the upper triangle of the symmetric interaction matrix. The\n  bit vector is kept in an array of ptruints. The computation is based\n  on a series of depth-first searches, one for each root of the\n  DAG. Two flags are needed: The local visited flag uses the LSB of\n  the then pointer. The global visited flag uses the LSB of the next\n  pointer.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddInitInteract(\n  DdManager * table)\n{\n    unsigned int i;\n    int j;\n    ptruint words;\n    ptruint *interact;\n    char *support;\n    DdNode *f;\n    DdNode *sentinel = &(table->sentinel);\n    DdNodePtr *nodelist;\n    int slots;\n    ptruint n = (ptruint) table->size;\n\n    words = ((n * (n-1)) >> (1 + LOGBPL)) + 1;\n    table->interact = interact = ALLOC(ptruint,words);\n    if (interact == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (i = 0; i < words; i++) {\n\tinteract[i] = 0;\n    }\n\n    support = ALLOC(char,n);\n    if (support == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tFREE(interact);\n\treturn(0);\n    }\n    for (i = 0; i < n; i++) {\n        support[i] = 0;\n    }\n\n    for (i = 0; i < n; i++) {\n\tnodelist = table->subtables[i].nodelist;\n\tslots = table->subtables[i].slots;\n\tfor (j = 0; j < slots; j++) {\n\t    f = nodelist[j];\n\t    while (f != sentinel) {\n\t\t/* A node is a root of the DAG if it cannot be\n\t\t** reached by nodes above it. If a node was never\n\t\t** reached during the previous depth-first searches,\n\t\t** then it is a root, and we start a new depth-first\n\t\t** search from it.\n\t\t*/\n\t\tif (!Cudd_IsComplement(f->next)) {\n\t\t    ddSuppInteract(f,support);\n\t\t    ddClearLocal(f);\n\t\t    ddUpdateInteract(table,support);\n\t\t}\n\t\tf = Cudd_Regular(f->next);\n\t    }\n\t}\n    }\n    ddClearGlobal(table);\n\n    FREE(support);\n    return(1);\n\n} /* end of cuddInitInteract */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Find the support of f.\n\n  @details Performs a DFS from f. Uses the LSB of the then pointer\n  as visited flag.\n\n  @sideeffect Accumulates in support the variables on which f depends.\n\n*/\nstatic void\nddSuppInteract(\n  DdNode * f,\n  char * support)\n{\n    if (cuddIsConstant(f) || Cudd_IsComplement(cuddT(f))) {\n\treturn;\n    }\n\n    support[f->index] = 1;\n    ddSuppInteract(cuddT(f),support);\n    ddSuppInteract(Cudd_Regular(cuddE(f)),support);\n    /* mark as visited */\n    cuddT(f) = Cudd_Complement(cuddT(f));\n    f->next = Cudd_Complement(f->next);\n    return;\n\n} /* end of ddSuppInteract */\n\n\n/**\n  @brief Performs a DFS from f, clearing the LSB of the then pointers.\n\n  @sideeffect None\n\n*/\nstatic void\nddClearLocal(\n  DdNode * f)\n{\n    if (cuddIsConstant(f) || !Cudd_IsComplement(cuddT(f))) {\n\treturn;\n    }\n    /* clear visited flag */\n    cuddT(f) = Cudd_Regular(cuddT(f));\n    ddClearLocal(cuddT(f));\n    ddClearLocal(Cudd_Regular(cuddE(f)));\n    return;\n\n} /* end of ddClearLocal */\n\n\n/**\n  @brief Marks as interacting all pairs of variables that appear in\n  support.\n\n  @details If support[i == support[j] == 1, sets the (i,j) entry\n  of the interaction matrix to 1.]\n\n  @sideeffect Clears support.\n\n*/\nstatic void\nddUpdateInteract(\n  DdManager * table,\n  char * support)\n{\n    int i,j;\n    int n = table->size;\n\n    for (i = 0; i < n-1; i++) {\n\tif (support[i] == 1) {\n            support[i] = 0;\n\t    for (j = i+1; j < n; j++) {\n\t\tif (support[j] == 1) {\n\t\t    cuddSetInteract(table,i,j);\n\t\t}\n\t    }\n\t}\n    }\n    support[n-1] = 0;\n\n} /* end of ddUpdateInteract */\n\n\n/**\n  @brief Scans the %DD and clears the LSB of the next pointers.\n\n  @details The LSB of the next pointers are used as markers to tell\n  whether a node was reached by at least one DFS. Once the interaction\n  matrix is built, these flags are reset.\n\n  @sideeffect None\n\n*/\nstatic void\nddClearGlobal(\n  DdManager * table)\n{\n    int i,j;\n    DdNode *f;\n    DdNode *sentinel = &(table->sentinel);\n    DdNodePtr *nodelist;\n    int slots;\n\n    for (i = 0; i < table->size; i++) {\n\tnodelist = table->subtables[i].nodelist;\n\tslots = table->subtables[i].slots;\n\tfor (j = 0; j < slots; j++) {\n\t    f = nodelist[j];\n\t    while (f != sentinel) {\n\t\tf->next = Cudd_Regular(f->next);\n\t\tf = f->next;\n\t    }\n\t}\n    }\n\n} /* end of ddClearGlobal */\n\n"
  },
  {
    "path": "cudd/cudd/cuddLCache.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for local caches.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define DD_MAX_HASHTABLE_DENSITY 2\t/* tells when to resize a table */\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Computes hash function for keys of one operand.\n\n  @sideeffect None\n\n  @see ddLCHash3 ddLCHash\n\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define ddLCHash1(f,shift) \\\n(((unsigned)(ptruint)(f) * DD_P1) >> (shift))\n#else\n#define ddLCHash1(f,shift) \\\n(((unsigned)(f) * DD_P1) >> (shift))\n#endif\n\n\n/**\n  @brief Computes hash function for keys of two operands.\n\n  @sideeffect None\n\n  @see ddLCHash3 ddLCHash\n\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define ddLCHash2(f,g,shift) \\\n((((unsigned)(ptruint)(f) * DD_P1 + \\\n   (unsigned)(ptruint)(g)) * DD_P2) >> (shift))\n#else\n#define ddLCHash2(f,g,shift) \\\n((((unsigned)(f) * DD_P1 + (unsigned)(g)) * DD_P2) >> (shift))\n#endif\n\n\n/**\n  @brief Computes hash function for keys of three operands.\n\n  @sideeffect None\n\n  @see ddLCHash2 ddLCHash\n\n*/\n#define ddLCHash3(f,g,h,shift) ddCHash2(f,g,h,shift)\n\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void cuddLocalCacheResize (DdLocalCache *cache);\nstatic unsigned int ddLCHash (DdNodePtr *key, unsigned int keysize, int shift);\nstatic void cuddLocalCacheAddToList (DdLocalCache *cache);\nstatic void cuddLocalCacheRemoveFromList (DdLocalCache *cache);\nstatic int cuddHashTableResize (DdHashTable *hash);\nstatic DdHashItem * cuddHashTableAlloc (DdHashTable *hash);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Initializes a local computed table.\n\n  @return a pointer the the new local cache in case of success; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see cuddInitCache\n\n*/\nDdLocalCache *\ncuddLocalCacheInit(\n  DdManager * manager /**< manager */,\n  unsigned int  keySize /**< size of the key (number of operands) */,\n  unsigned int  cacheSize /**< Initial size of the cache */,\n  unsigned int  maxCacheSize /**< Size of the cache beyond which no resizing occurs */)\n{\n    DdLocalCache *cache;\n    int logSize;\n\n    cache = ALLOC(DdLocalCache,1);\n    if (cache == NULL) {\n\tmanager->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    cache->manager = manager;\n    cache->keysize = keySize;\n    cache->itemsize = (keySize + 1) * sizeof(DdNode *);\n#ifdef DD_CACHE_PROFILE\n    cache->itemsize += sizeof(ptrint);\n#endif\n    logSize = cuddComputeFloorLog2(ddMax(cacheSize,manager->slots/2));\n    cacheSize = 1U << logSize;\n    cache->item = (DdLocalCacheItem *)\n\tALLOC(char, cacheSize * cache->itemsize);\n    if (cache->item == NULL) {\n\tmanager->errorCode = CUDD_MEMORY_OUT;\n\tFREE(cache);\n\treturn(NULL);\n    }\n    cache->slots = cacheSize;\n    cache->shift = sizeof(int) * 8 - logSize;\n    cache->maxslots = ddMin(maxCacheSize,manager->slots);\n    cache->minHit = manager->minHit;\n    /* Initialize to avoid division by 0 and immediate resizing. */\n    cache->lookUps = (double) (int) (cacheSize * cache->minHit + 1);\n    cache->hits = 0;\n    manager->memused += cacheSize * cache->itemsize + sizeof(DdLocalCache);\n\n    /* Initialize the cache. */\n    memset(cache->item, 0, cacheSize * cache->itemsize);\n\n    /* Add to manager's list of local caches for GC. */\n    cuddLocalCacheAddToList(cache);\n\n    return(cache);\n\n} /* end of cuddLocalCacheInit */\n\n\n/**\n  @brief Shuts down a local computed table.\n\n  @sideeffect None\n\n  @see cuddLocalCacheInit\n\n*/\nvoid\ncuddLocalCacheQuit(\n  DdLocalCache * cache /**< cache to be shut down */)\n{\n    cache->manager->memused -=\n\tcache->slots * cache->itemsize + sizeof(DdLocalCache);\n    cuddLocalCacheRemoveFromList(cache);\n    FREE(cache->item);\n    FREE(cache);\n\n    return;\n\n} /* end of cuddLocalCacheQuit */\n\n\n/**\n  @brief Inserts a result in a local cache.\n\n  @sideeffect None\n\n*/\nvoid\ncuddLocalCacheInsert(\n  DdLocalCache * cache,\n  DdNodePtr * key,\n  DdNode * value)\n{\n    unsigned int posn;\n    DdLocalCacheItem *entry;\n\n    posn = ddLCHash(key,cache->keysize,cache->shift);\n    entry = (DdLocalCacheItem *) ((char *) cache->item +\n\t\t\t\t  posn * cache->itemsize);\n    memcpy(entry->key,key,cache->keysize * sizeof(DdNode *));\n    entry->value = value;\n#ifdef DD_CACHE_PROFILE\n    entry->count++;\n#endif\n\n} /* end of cuddLocalCacheInsert */\n\n\n/**\n  @brief Looks up in a local cache.\n\n  @return the result if found; it returns NULL if no result is found.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddLocalCacheLookup(\n  DdLocalCache * cache,\n  DdNodePtr * key)\n{\n    unsigned int posn;\n    DdLocalCacheItem *entry;\n    DdNode *value;\n\n    cache->lookUps++;\n    posn = ddLCHash(key,cache->keysize,cache->shift);\n    entry = (DdLocalCacheItem *) ((char *) cache->item +\n\t\t\t\t  posn * cache->itemsize);\n    if (entry->value != NULL &&\n\tmemcmp(key,entry->key,cache->keysize*sizeof(DdNode *)) == 0) {\n\tcache->hits++;\n\tvalue = Cudd_Regular(entry->value);\n\tif (value->ref == 0) {\n\t    cuddReclaim(cache->manager,value);\n\t}\n\treturn(entry->value);\n    }\n\n    /* Cache miss: decide whether to resize */\n\n    if (cache->slots < cache->maxslots &&\n\tcache->hits > cache->lookUps * cache->minHit) {\n\tcuddLocalCacheResize(cache);\n    }\n\n    return(NULL);\n\n} /* end of cuddLocalCacheLookup */\n\n\n/**\n  @brief Clears the dead entries of the local caches of a manager.\n\n  @details Used during garbage collection.\n\n  @sideeffect None\n\n*/\nvoid\ncuddLocalCacheClearDead(\n  DdManager * manager)\n{\n    DdLocalCache *cache = manager->localCaches;\n    unsigned int keysize;\n    unsigned int itemsize;\n    unsigned int slots;\n    DdLocalCacheItem *item;\n    DdNodePtr *key;\n    unsigned int i, j;\n\n    while (cache != NULL) {\n\tkeysize = cache->keysize;\n\titemsize = cache->itemsize;\n\tslots = cache->slots;\n\titem = cache->item;\n\tfor (i = 0; i < slots; i++) {\n\t    if (item->value != NULL) {\n\t\tif (Cudd_Regular(item->value)->ref == 0) {\n\t\t    item->value = NULL;\n\t\t} else {\n\t\t    key = item->key;\n\t\t    for (j = 0; j < keysize; j++) {\n\t\t\tif (Cudd_Regular(key[j])->ref == 0) {\n\t\t\t    item->value = NULL;\n\t\t\t    break;\n\t\t\t}\n\t\t    }\n\t\t}\n\t    }\n\t    item = (DdLocalCacheItem *) ((char *) item + itemsize);\n\t}\n\tcache = cache->next;\n    }\n    return;\n\n} /* end of cuddLocalCacheClearDead */\n\n\n/**\n  @brief Clears the local caches of a manager.\n\n  @details Used before reordering.\n\n  @sideeffect None\n\n*/\nvoid\ncuddLocalCacheClearAll(\n  DdManager * manager)\n{\n    DdLocalCache *cache = manager->localCaches;\n\n    while (cache != NULL) {\n\tmemset(cache->item, 0, cache->slots * cache->itemsize);\n\tcache = cache->next;\n    }\n    return;\n\n} /* end of cuddLocalCacheClearAll */\n\n\n#ifdef DD_CACHE_PROFILE\n\n#define DD_HYSTO_BINS 8\n\n/**\n  @brief Computes and prints a profile of a local cache usage.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddLocalCacheProfile(\n  DdLocalCache * cache)\n{\n    double count, mean, meansq, stddev, expected;\n    long max, min;\n    int imax, imin;\n    int i, retval, slots;\n    long *hystogram;\n    int nbins = DD_HYSTO_BINS;\n    int bin;\n    long thiscount;\n    double totalcount;\n    int nzeroes;\n    DdLocalCacheItem *entry;\n    FILE *fp = cache->manager->out;\n\n    slots = cache->slots;\n\n    meansq = mean = expected = 0.0;\n    max = min = (long) cache->item[0].count;\n    imax = imin = nzeroes = 0;\n    totalcount = 0.0;\n\n    hystogram = ALLOC(long, nbins);\n    if (hystogram == NULL) {\n\treturn(0);\n    }\n    for (i = 0; i < nbins; i++) {\n\thystogram[i] = 0;\n    }\n\n    for (i = 0; i < slots; i++) {\n\tentry = (DdLocalCacheItem *) ((char *) cache->item +\n\t\t\t\t      i * cache->itemsize);\n\tthiscount = (long) entry->count;\n\tif (thiscount > max) {\n\t    max = thiscount;\n\t    imax = i;\n\t}\n\tif (thiscount < min) {\n\t    min = thiscount;\n\t    imin = i;\n\t}\n\tif (thiscount == 0) {\n\t    nzeroes++;\n\t}\n\tcount = (double) thiscount;\n\tmean += count;\n\tmeansq += count * count;\n\ttotalcount += count;\n\texpected += count * (double) i;\n\tbin = (i * nbins) / slots;\n\thystogram[bin] += thiscount;\n    }\n    mean /= (double) slots;\n    meansq /= (double) slots;\n    stddev = sqrt(meansq - mean*mean);\n\n    retval = fprintf(fp,\"Cache stats: slots = %d average = %g \", slots, mean);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"standard deviation = %g\\n\", stddev);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Cache max accesses = %ld for slot %d\\n\", max, imax);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Cache min accesses = %ld for slot %d\\n\", min, imin);\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\"Cache unused slots = %d\\n\", nzeroes);\n    if (retval == EOF) return(0);\n\n    if (totalcount) {\n\texpected /= totalcount;\n\tretval = fprintf(fp,\"Cache access hystogram for %d bins\", nbins);\n\tif (retval == EOF) return(0);\n\tretval = fprintf(fp,\" (expected bin value = %g)\\n# \", expected);\n\tif (retval == EOF) return(0);\n\tfor (i = nbins - 1; i>=0; i--) {\n\t    retval = fprintf(fp,\"%ld \", hystogram[i]);\n\t    if (retval == EOF) return(0);\n\t}\n\tretval = fprintf(fp,\"\\n\");\n\tif (retval == EOF) return(0);\n    }\n\n    FREE(hystogram);\n    return(1);\n\n} /* end of cuddLocalCacheProfile */\n#endif\n\n\n/**\n  @brief Initializes a hash table.\n\n  @details The table associates tuples of DdNode pointers to one DdNode pointer.\n  This type of table is used for functions that cannot (or prefer not to) use\n  the main computed table.  The package also provides functions that allow the\n  caller to store arbitrary pointers in the table.\n\n  @return a pointer to the new table if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableQuit cuddHashTableGenericQuit\n\n*/\nDdHashTable *\ncuddHashTableInit(\n  DdManager * manager /**< %DD manager */,\n  unsigned int keySize /**< number of pointers in the key */,\n  unsigned int initSize /**< initial size of the table */)\n{\n    DdHashTable *hash;\n    int logSize;\n\n    hash = ALLOC(DdHashTable, 1);\n    if (hash == NULL) {\n\tmanager->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    hash->keysize = keySize;\n    hash->manager = manager;\n    hash->memoryList = NULL;\n    hash->nextFree = NULL;\n    hash->itemsize = (keySize + 1) * sizeof(DdNode *) +\n\tsizeof(ptrint) + sizeof(DdHashItem *);\n    /* We have to guarantee that the shift be < 32. */\n    if (initSize < 2) initSize = 2;\n    logSize = cuddComputeFloorLog2(initSize);\n    hash->numBuckets = 1U << logSize;\n    hash->shift = sizeof(int) * 8 - logSize;\n    hash->bucket = ALLOC(DdHashItem *, hash->numBuckets);\n    if (hash->bucket == NULL) {\n\tmanager->errorCode = CUDD_MEMORY_OUT;\n\tFREE(hash);\n\treturn(NULL);\n    }\n    memset(hash->bucket, 0, hash->numBuckets * sizeof(DdHashItem *));\n    hash->size = 0;\n    hash->maxsize = hash->numBuckets * DD_MAX_HASHTABLE_DENSITY;\n    return(hash);\n\n} /* end of cuddHashTableInit */\n\n\n/**\n  @brief Shuts down a hash table.\n\n  @details Dereferences all the values.\n\n  @sideeffect None\n\n  @see cuddHashTableInit\n\n*/\nvoid\ncuddHashTableQuit(\n  DdHashTable * hash)\n{\n    unsigned int i;\n    DdManager *dd = hash->manager;\n    DdHashItem *bucket;\n    DdHashItem **memlist, **nextmem;\n    unsigned int numBuckets = hash->numBuckets;\n\n    for (i = 0; i < numBuckets; i++) {\n\tbucket = hash->bucket[i];\n\twhile (bucket != NULL) {\n\t    Cudd_RecursiveDeref(dd, bucket->value);\n\t    bucket = bucket->next;\n\t}\n    }\n\n    memlist = hash->memoryList;\n    while (memlist != NULL) {\n\tnextmem = (DdHashItem **) memlist[0];\n\tFREE(memlist);\n\tmemlist = nextmem;\n    }\n\n    FREE(hash->bucket);\n    FREE(hash);\n\n    return;\n\n} /* end of cuddHashTableQuit */\n\n\n/**\n  @brief Shuts down a hash table.\n\n  @details Shuts down a hash table, when the values are not DdNode\n  pointers.\n\n  @sideeffect None\n\n  @see cuddHashTableInit\n\n*/\nvoid\ncuddHashTableGenericQuit(\n  DdHashTable * hash)\n{\n    DdHashItem **memlist, **nextmem;\n\n    memlist = hash->memoryList;\n    while (memlist != NULL) {\n\tnextmem = (DdHashItem **) memlist[0];\n\tFREE(memlist);\n\tmemlist = nextmem;\n    }\n\n    FREE(hash->bucket);\n    FREE(hash);\n\n    return;\n\n} /* end of cuddHashTableGenericQuit */\n\n\n/**\n  @brief Inserts an item in a hash table.\n\n  @details Inserts an item in a hash table when the key has more than\n  three pointers.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see [cuddHashTableInsert1 cuddHashTableInsert2 cuddHashTableInsert3\n  cuddHashTableLookup\n\n*/\nint\ncuddHashTableInsert(\n  DdHashTable * hash,\n  DdNodePtr * key,\n  DdNode * value,\n  ptrint count)\n{\n    int result;\n    unsigned int posn;\n    DdHashItem *item;\n    unsigned int i;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize > 3);\n#endif\n\n    if (hash->size > hash->maxsize) {\n\tresult = cuddHashTableResize(hash);\n\tif (result == 0) return(0);\n    }\n    item = cuddHashTableAlloc(hash);\n    if (item == NULL) return(0);\n    hash->size++;\n    item->value = value;\n    cuddRef(value);\n    item->count = count;\n    for (i = 0; i < hash->keysize; i++) {\n\titem->key[i] = key[i];\n    }\n    posn = ddLCHash(key,hash->keysize,hash->shift);\n    item->next = hash->bucket[posn];\n    hash->bucket[posn] = item;\n\n    return(1);\n\n} /* end of cuddHashTableInsert */\n\n\n/**\n  @brief Looks up a key in a hash table.\n\n  @details Looks up a key consisting of more than three pointers in a\n  hash table.  If the entry is present, its reference counter is\n  decremented if not saturated. If the counter reaches 0, the value of\n  the entry is dereferenced, and the entry is returned to the free\n  list.\n\n  @return the value associated to the key if there is an entry for the\n  given key in the table; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableLookup1 cuddHashTableLookup2 cuddHashTableLookup3\n  cuddHashTableInsert\n\n*/\nDdNode *\ncuddHashTableLookup(\n  DdHashTable * hash,\n  DdNodePtr * key)\n{\n    unsigned int posn;\n    DdHashItem *item, *prev;\n    unsigned int i, keysize;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize > 3);\n#endif\n\n    posn = ddLCHash(key,hash->keysize,hash->shift);\n    item = hash->bucket[posn];\n    prev = NULL;\n\n    keysize = hash->keysize;\n    while (item != NULL) {\n\tDdNodePtr *key2 = item->key;\n\tint equal = 1;\n\tfor (i = 0; i < keysize; i++) {\n\t    if (key[i] != key2[i]) {\n\t\tequal = 0;\n\t\tbreak;\n\t    }\n\t}\n\tif (equal) {\n\t    DdNode *value = item->value;\n\t    cuddSatDec(item->count);\n\t    if (item->count == 0) {\n\t\tcuddDeref(value);\n\t\tif (prev == NULL) {\n\t\t    hash->bucket[posn] = item->next;\n\t\t} else {\n\t\t    prev->next = item->next;\n\t\t}\n\t\titem->next = hash->nextFree;\n\t\thash->nextFree = item;\n\t\thash->size--;\n\t    }\n\t    return(value);\n\t}\n\tprev = item;\n\titem = item->next;\n    }\n    return(NULL);\n\n} /* end of cuddHashTableLookup */\n\n\n/**\n  @brief Inserts an item in a hash table.\n\n  @details Inserts an item in a hash table when the key is one pointer.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableInsert cuddHashTableInsert2 cuddHashTableInsert3\n  cuddHashTableLookup1\n\n*/\nint\ncuddHashTableInsert1(\n  DdHashTable * hash,\n  DdNode * f,\n  DdNode * value,\n  ptrint count)\n{\n    int result;\n    unsigned int posn;\n    DdHashItem *item;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize == 1);\n#endif\n\n    if (hash->size > hash->maxsize) {\n\tresult = cuddHashTableResize(hash);\n\tif (result == 0) return(0);\n    }\n    item = cuddHashTableAlloc(hash);\n    if (item == NULL) return(0);\n    hash->size++;\n    item->value = value;\n    cuddRef(value);\n    item->count = count;\n    item->key[0] = f;\n    posn = ddLCHash1(f,hash->shift);\n    item->next = hash->bucket[posn];\n    hash->bucket[posn] = item;\n\n    return(1);\n\n} /* end of cuddHashTableInsert1 */\n\n\n/**\n  @brief Looks up a key consisting of one pointer in a hash table.\n\n  @details If the entry is present, its reference count is\n  decremented if not saturated. If the counter reaches 0, the value of\n  the entry is dereferenced, and the entry is returned to the free\n  list.\n\n  @return the value associated to the key if there is an entry for the\n  given key in the table; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableLookup cuddHashTableLookup2 cuddHashTableLookup3\n  cuddHashTableInsert1\n\n*/\nDdNode *\ncuddHashTableLookup1(\n  DdHashTable * hash,\n  DdNode * f)\n{\n    unsigned int posn;\n    DdHashItem *item, *prev;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize == 1);\n#endif\n\n    posn = ddLCHash1(f,hash->shift);\n    item = hash->bucket[posn];\n    prev = NULL;\n\n    while (item != NULL) {\n\tDdNodePtr *key = item->key;\n\tif (f == key[0]) {\n\t    DdNode *value = item->value;\n\t    cuddSatDec(item->count);\n\t    if (item->count == 0) {\n\t\tcuddDeref(value);\n\t\tif (prev == NULL) {\n\t\t    hash->bucket[posn] = item->next;\n\t\t} else {\n\t\t    prev->next = item->next;\n\t\t}\n\t\titem->next = hash->nextFree;\n\t\thash->nextFree = item;\n\t\thash->size--;\n\t    }\n\t    return(value);\n\t}\n\tprev = item;\n\titem = item->next;\n    }\n    return(NULL);\n\n} /* end of cuddHashTableLookup1 */\n\n\n/**\n  @brief Inserts a generic item in a hash table.\n\n  @details Inserts an item in a hash table when the key is one\n  pointer and the value is not a DdNode pointer.  The main difference w.r.t.\n  cuddHashTableInsert1 is that the reference count of the value is not\n  incremented.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableInsert1 cuddHashTableGenericLookup\n\n*/\nint\ncuddHashTableGenericInsert(\n  DdHashTable * hash,\n  DdNode * f,\n  void * value)\n{\n    int result;\n    unsigned int posn;\n    DdHashItem *item;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize == 1);\n#endif\n\n    if (hash->size > hash->maxsize) {\n\tresult = cuddHashTableResize(hash);\n\tif (result == 0) return(0);\n    }\n    item = cuddHashTableAlloc(hash);\n    if (item == NULL) return(0);\n    hash->size++;\n    item->value = (DdNode *) value;\n    item->count = 0;\n    item->key[0] = f;\n    posn = ddLCHash1(f,hash->shift);\n    item->next = hash->bucket[posn];\n    hash->bucket[posn] = item;\n\n    return(1);\n\n} /* end of cuddHashTableGenericInsert */\n\n\n/**\n  @brief Looks up a key consisting of one pointer in a hash table.\n\n  @details Looks up a key consisting of one pointer in a hash\n  table when the value is not a DdNode pointer.\n\n  @return the value associated to the key if there is an entry for the\n  given key in the table; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableLookup1 cuddHashTableGenericInsert\n\n*/\nvoid *\ncuddHashTableGenericLookup(\n  DdHashTable * hash,\n  DdNode * f)\n{\n    unsigned int posn;\n    DdHashItem *item;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize == 1);\n#endif\n\n    posn = ddLCHash1(f,hash->shift);\n    item = hash->bucket[posn];\n\n    while (item != NULL) {\n\tif (f == item->key[0]) {\n            return ((void *) item->value);\n\t}\n\titem = item->next;\n    }\n    return(NULL);\n\n} /* end of cuddHashTableGenericLookup */\n\n\n/**\n  @brief Inserts an item in a hash table.\n\n  @details Inserts an item in a hash table when the key is\n  composed of two pointers.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableInsert cuddHashTableInsert1 cuddHashTableInsert3\n  cuddHashTableLookup2\n\n*/\nint\ncuddHashTableInsert2(\n  DdHashTable * hash,\n  DdNode * f,\n  DdNode * g,\n  DdNode * value,\n  ptrint count)\n{\n    int result;\n    unsigned int posn;\n    DdHashItem *item;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize == 2);\n#endif\n\n    if (hash->size > hash->maxsize) {\n\tresult = cuddHashTableResize(hash);\n\tif (result == 0) return(0);\n    }\n    item = cuddHashTableAlloc(hash);\n    if (item == NULL) return(0);\n    hash->size++;\n    item->value = value;\n    cuddRef(value);\n    item->count = count;\n    item->key[0] = f;\n    item->key[1] = g;\n    posn = ddLCHash2(f,g,hash->shift);\n    item->next = hash->bucket[posn];\n    hash->bucket[posn] = item;\n\n    return(1);\n\n} /* end of cuddHashTableInsert2 */\n\n\n/**\n  @brief Looks up a key consisting of two pointers in a hash table.\n\n  @details If the entry is present, its reference counter is\n  decremented if not saturated. If the counter reaches 0, the value of\n  the entry is dereferenced, and the entry is returned to the free\n  list.\n\n  @return the value associated to the key if there is an entry for the\n  given key in the table; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableLookup cuddHashTableLookup1 cuddHashTableLookup3\n  cuddHashTableInsert2\n\n*/\nDdNode *\ncuddHashTableLookup2(\n  DdHashTable * hash,\n  DdNode * f,\n  DdNode * g)\n{\n    unsigned int posn;\n    DdHashItem *item, *prev;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize == 2);\n#endif\n\n    posn = ddLCHash2(f,g,hash->shift);\n    item = hash->bucket[posn];\n    prev = NULL;\n\n    while (item != NULL) {\n\tDdNodePtr *key = item->key;\n\tif ((f == key[0]) && (g == key[1])) {\n\t    DdNode *value = item->value;\n\t    cuddSatDec(item->count);\n\t    if (item->count == 0) {\n\t\tcuddDeref(value);\n\t\tif (prev == NULL) {\n\t\t    hash->bucket[posn] = item->next;\n\t\t} else {\n\t\t    prev->next = item->next;\n\t\t}\n\t\titem->next = hash->nextFree;\n\t\thash->nextFree = item;\n\t\thash->size--;\n\t    }\n\t    return(value);\n\t}\n\tprev = item;\n\titem = item->next;\n    }\n    return(NULL);\n\n} /* end of cuddHashTableLookup2 */\n\n\n/**\n  @brief Inserts an item in a hash table.\n\n  @details Inserts an item in a hash table when the key is\n  composed of three pointers.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableInsert cuddHashTableInsert1 cuddHashTableInsert2\n  cuddHashTableLookup3\n\n*/\nint\ncuddHashTableInsert3(\n  DdHashTable * hash,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h,\n  DdNode * value,\n  ptrint count)\n{\n    int result;\n    unsigned int posn;\n    DdHashItem *item;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize == 3);\n#endif\n\n    if (hash->size > hash->maxsize) {\n\tresult = cuddHashTableResize(hash);\n\tif (result == 0) return(0);\n    }\n    item = cuddHashTableAlloc(hash);\n    if (item == NULL) return(0);\n    hash->size++;\n    item->value = value;\n    cuddRef(value);\n    item->count = count;\n    item->key[0] = f;\n    item->key[1] = g;\n    item->key[2] = h;\n    posn = ddLCHash3(f,g,h,hash->shift);\n    item->next = hash->bucket[posn];\n    hash->bucket[posn] = item;\n\n    return(1);\n\n} /* end of cuddHashTableInsert3 */\n\n\n/**\n  @brief Looks up a key consisting of three pointers in a hash table.\n\n  @details If the entry is present, its reference counter is\n  decremented if not saturated. If the counter reaches 0, the value of\n  the entry is dereferenced, and the entry is returned to the free\n  list.\n\n  @return the value associated to the key if there is an entry for the\n  given key in the table; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableLookup cuddHashTableLookup1 cuddHashTableLookup2\n  cuddHashTableInsert3\n\n*/\nDdNode *\ncuddHashTableLookup3(\n  DdHashTable * hash,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    unsigned int posn;\n    DdHashItem *item, *prev;\n\n#ifdef DD_DEBUG\n    assert(hash->keysize == 3);\n#endif\n\n    posn = ddLCHash3(f,g,h,hash->shift);\n    item = hash->bucket[posn];\n    prev = NULL;\n\n    while (item != NULL) {\n\tDdNodePtr *key = item->key;\n\tif ((f == key[0]) && (g == key[1]) && (h == key[2])) {\n\t    DdNode *value = item->value;\n\t    cuddSatDec(item->count);\n\t    if (item->count == 0) {\n\t\tcuddDeref(value);\n\t\tif (prev == NULL) {\n\t\t    hash->bucket[posn] = item->next;\n\t\t} else {\n\t\t    prev->next = item->next;\n\t\t}\n\t\titem->next = hash->nextFree;\n\t\thash->nextFree = item;\n\t\thash->size--;\n\t    }\n\t    return(value);\n\t}\n\tprev = item;\n\titem = item->next;\n    }\n    return(NULL);\n\n} /* end of cuddHashTableLookup3 */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Resizes a local cache.\n\n  @sideeffect None\n\n*/\nstatic void\ncuddLocalCacheResize(\n  DdLocalCache * cache)\n{\n    DdLocalCacheItem *item, *olditem, *entry, *old;\n    int i, shift;\n    unsigned int posn;\n    unsigned int slots, oldslots;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    olditem = cache->item;\n    oldslots = cache->slots;\n    slots = cache->slots = oldslots << 1;\n\n#ifdef DD_VERBOSE\n    (void) fprintf(cache->manager->err,\n\t\t   \"Resizing local cache from %d to %d entries\\n\",\n\t\t   oldslots, slots);\n    (void) fprintf(cache->manager->err,\n\t\t   \"\\thits = %.0f\\tlookups = %.0f\\thit ratio = %5.3f\\n\",\n\t\t   cache->hits, cache->lookUps, cache->hits / cache->lookUps);\n#endif\n\n    saveHandler = MMoutOfMemory;\n    MMoutOfMemory = cache->manager->outOfMemCallback;\n    cache->item = item =\n\t(DdLocalCacheItem *) ALLOC(char, slots * cache->itemsize);\n    MMoutOfMemory = saveHandler;\n    /* If we fail to allocate the new table we just give up. */\n    if (item == NULL) {\n#ifdef DD_VERBOSE\n\t(void) fprintf(cache->manager->err,\"Resizing failed. Giving up.\\n\");\n#endif\n\tcache->slots = oldslots;\n\tcache->item = olditem;\n\t/* Do not try to resize again. */\n\tcache->maxslots = oldslots - 1;\n\treturn;\n    }\n    shift = --(cache->shift);\n    cache->manager->memused += (slots - oldslots) * cache->itemsize;\n\n    /* Clear new cache. */\n    memset(item, 0, slots * cache->itemsize);\n\n    /* Copy from old cache to new one. */\n    for (i = 0; (unsigned) i < oldslots; i++) {\n\told = (DdLocalCacheItem *) ((char *) olditem + i * cache->itemsize);\n\tif (old->value != NULL) {\n\t    posn = ddLCHash(old->key,cache->keysize,shift);\n\t    entry = (DdLocalCacheItem *) ((char *) item +\n\t\t\t\t\t  posn * cache->itemsize);\n\t    memcpy(entry->key,old->key,cache->keysize*sizeof(DdNode *));\n\t    entry->value = old->value;\n\t}\n    }\n\n    FREE(olditem);\n\n    /* Reinitialize measurements so as to avoid division by 0 and\n    ** immediate resizing.\n    */\n    cache->lookUps = (double) (int) (slots * cache->minHit + 1);\n    cache->hits = 0;\n\n} /* end of cuddLocalCacheResize */\n\n\n/**\n  @brief Computes the hash value for a local cache.\n\n  @return the bucket index.\n\n  @sideeffect None\n\n*/\nstatic unsigned int\nddLCHash(\n  DdNodePtr * key,\n  unsigned int keysize,\n  int shift)\n{\n    unsigned int val = (unsigned int) (ptrint) key[0] * DD_P2;\n    unsigned int i;\n\n    for (i = 1; i < keysize; i++) {\n\tval = val * DD_P1 + (int) (ptrint) key[i];\n    }\n\n    return(val >> shift);\n\n} /* end of ddLCHash */\n\n\n/**\n  @brief Inserts a local cache in the manager list.\n\n  @sideeffect None\n\n*/\nstatic void\ncuddLocalCacheAddToList(\n  DdLocalCache * cache)\n{\n    DdManager *manager = cache->manager;\n\n    cache->next = manager->localCaches;\n    manager->localCaches = cache;\n    return;\n\n} /* end of cuddLocalCacheAddToList */\n\n\n/**\n  @brief Removes a local cache from the manager list.\n\n  @sideeffect None\n\n*/\nstatic void\ncuddLocalCacheRemoveFromList(\n  DdLocalCache * cache)\n{\n    DdManager *manager = cache->manager;\n    DdLocalCache **prevCache, *nextCache;\n\n    prevCache = &(manager->localCaches);\n    nextCache = manager->localCaches;\n\n    while (nextCache != NULL) {\n\tif (nextCache == cache) {\n\t    *prevCache = nextCache->next;\n\t    return;\n\t}\n\tprevCache = &(nextCache->next);\n\tnextCache = nextCache->next;\n    }\n    return;\t\t\t/* should never get here */\n\n} /* end of cuddLocalCacheRemoveFromList */\n\n\n/**\n  @brief Resizes a hash table.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddHashTableInsert\n\n*/\nstatic int\ncuddHashTableResize(\n  DdHashTable * hash)\n{\n    int j;\n    unsigned int posn;\n    DdHashItem *item;\n    DdHashItem *next;\n    DdNode **key;\n    int numBuckets;\n    DdHashItem **buckets;\n    DdHashItem **oldBuckets = hash->bucket;\n    int shift;\n    int oldNumBuckets = hash->numBuckets;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    /* Compute the new size of the table. */\n    numBuckets = oldNumBuckets << 1;\n    saveHandler = MMoutOfMemory;\n    MMoutOfMemory = hash->manager->outOfMemCallback;\n    buckets = ALLOC(DdHashItem *, numBuckets);\n    MMoutOfMemory = saveHandler;\n    if (buckets == NULL) {\n\thash->maxsize <<= 1;\n\treturn(1);\n    }\n\n    hash->bucket = buckets;\n    hash->numBuckets = numBuckets;\n    shift = --(hash->shift);\n    hash->maxsize <<= 1;\n    memset(buckets, 0, numBuckets * sizeof(DdHashItem *));\n    if (hash->keysize == 1) {\n\tfor (j = 0; j < oldNumBuckets; j++) {\n\t    item = oldBuckets[j];\n\t    while (item != NULL) {\n\t\tnext = item->next;\n\t\tkey = item->key;\n\t\tposn = ddLCHash2(key[0], key[0], shift);\n\t\titem->next = buckets[posn];\n\t\tbuckets[posn] = item;\n\t\titem = next;\n\t    }\n\t}\n    } else if (hash->keysize == 2) {\n\tfor (j = 0; j < oldNumBuckets; j++) {\n\t    item = oldBuckets[j];\n\t    while (item != NULL) {\n\t\tnext = item->next;\n\t\tkey = item->key;\n\t\tposn = ddLCHash2(key[0], key[1], shift);\n\t\titem->next = buckets[posn];\n\t\tbuckets[posn] = item;\n\t\titem = next;\n\t    }\n\t}\n    } else if (hash->keysize == 3) {\n\tfor (j = 0; j < oldNumBuckets; j++) {\n\t    item = oldBuckets[j];\n\t    while (item != NULL) {\n\t\tnext = item->next;\n\t\tkey = item->key;\n\t\tposn = ddLCHash3(key[0], key[1], key[2], shift);\n\t\titem->next = buckets[posn];\n\t\tbuckets[posn] = item;\n\t\titem = next;\n\t    }\n\t}\n    } else {\n\tfor (j = 0; j < oldNumBuckets; j++) {\n\t    item = oldBuckets[j];\n\t    while (item != NULL) {\n\t\tnext = item->next;\n\t\tposn = ddLCHash(item->key, hash->keysize, shift);\n\t\titem->next = buckets[posn];\n\t\tbuckets[posn] = item;\n\t\titem = next;\n\t    }\n\t}\n    }\n    FREE(oldBuckets);\n    return(1);\n\n} /* end of cuddHashTableResize */\n\n\n/**\n  @brief Fast storage allocation for items in a hash table.\n\n  @details The first sizeof(void *) bytes of a chunk contain a pointer to the\n  next block; the rest contains DD_MEM_CHUNK spaces for hash items.\n\n  @return a pointer to a new item if successful; NULL is memory is full.\n\n  @sideeffect None\n\n  @see cuddAllocNode cuddDynamicAllocNode\n\n*/\nstatic DdHashItem *\ncuddHashTableAlloc(\n  DdHashTable * hash)\n{\n    int i;\n    unsigned int itemsize = hash->itemsize;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n    DdHashItem **mem, *thisOne, *next, *item;\n\n    if (hash->nextFree == NULL) {\n\tsaveHandler = MMoutOfMemory;\n\tMMoutOfMemory = hash->manager->outOfMemCallback;\n\tmem = (DdHashItem **) ALLOC(char,(DD_MEM_CHUNK+1) * itemsize);\n\tMMoutOfMemory = saveHandler;\n\tif (mem == NULL) {\n\t    if (hash->manager->stash != NULL) {\n\t\tFREE(hash->manager->stash);\n\t\thash->manager->stash = NULL;\n\t\t/* Inhibit resizing of tables. */\n\t\thash->manager->maxCacheHard = hash->manager->cacheSlots - 1;\n\t\thash->manager->cacheSlack = - (int) (hash->manager->cacheSlots + 1);\n\t\tfor (i = 0; i < hash->manager->size; i++) {\n\t\t    hash->manager->subtables[i].maxKeys <<= 2;\n\t\t}\n\t\thash->manager->gcFrac = 0.2;\n\t\thash->manager->minDead =\n\t\t    (unsigned) (0.2 * (double) hash->manager->slots);\n\t\tmem = (DdHashItem **) ALLOC(char,(DD_MEM_CHUNK+1) * itemsize);\n\t    }\n\t    if (mem == NULL) {\n\t\t(*MMoutOfMemory)((size_t)((DD_MEM_CHUNK + 1) * itemsize));\n\t\thash->manager->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(NULL);\n\t    }\n\t}\n\n\tmem[0] = (DdHashItem *) hash->memoryList;\n\thash->memoryList = mem;\n\n\tthisOne = (DdHashItem *) ((char *) mem + itemsize);\n\thash->nextFree = thisOne;\n\tfor (i = 1; i < DD_MEM_CHUNK; i++) {\n\t    next = (DdHashItem *) ((char *) thisOne + itemsize);\n\t    thisOne->next = next;\n\t    thisOne = next;\n\t}\n\n\tthisOne->next = NULL;\n\n    }\n    item = hash->nextFree;\n    hash->nextFree = item->next;\n    return(item);\n\n} /* end of cuddHashTableAlloc */\n"
  },
  {
    "path": "cudd/cudd/cuddLevelQ.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Procedure to manage level queues.\n\n  @details The functions in this file allow an application to easily\n  manipulate a queue where nodes are prioritized by level. The\n  emphasis is on efficiency. Therefore, the queue items can have\n  variable size.  If the application does not need to attach\n  information to the nodes, it can declare the queue items to be of\n  type DdQueueItem. Otherwise, it can declare them to be of a\n  structure type such that the first three fields are data\n  pointers. The third pointer points to the node.  The first two\n  pointers are used by the level queue functions. The remaining fields\n  are initialized to 0 when a new item is created, and are then left\n  to the exclusive use of the application. On the DEC Alphas the three\n  pointers must be 32-bit pointers when CUDD is compiled with 32-bit\n  pointers.  The level queue functions make sure that each node\n  appears at most once in the queue. They do so by keeping a hash\n  table where the node is used as key.  Queue items are recycled via a\n  free list for efficiency.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Hash function for the table of a level queue.\n\n  @sideeffect None\n\n  @see hashInsert hashLookup hashDelete\n\n*/\n#if SIZEOF_VOID_P == 8 && SIZEOF_INT == 4\n#define lqHash(key,shift) \\\n(((unsigned)(ptruint)(key) * DD_P1) >> (shift))\n#else\n#define lqHash(key,shift) \\\n(((unsigned)(key) * DD_P1) >> (shift))\n#endif\n\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdQueueItem * hashLookup(DdLevelQueue *queue, void *key);\nstatic int hashInsert(DdLevelQueue *queue, DdQueueItem *item);\nstatic void hashDelete(DdLevelQueue *queue, DdQueueItem *item);\nstatic int hashResize(DdLevelQueue *queue);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Initializes a level queue.\n\n  @details A level queue is a queue where inserts are based on the\n  levels of the nodes. Within each level the policy is FIFO. Level\n  queues are useful in traversing a %BDD top-down. Queue items are kept\n  in a free list when dequeued for efficiency.\n\n  @return a pointer to the new queue if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddLevelQueueQuit cuddLevelQueueEnqueue cuddLevelQueueDequeue\n\n*/\nDdLevelQueue *\ncuddLevelQueueInit(\n  int  levels /**< number of levels */,\n  int  itemSize /**< size of the item */,\n  int  numBuckets /**< initial number of hash buckets */,\n  DdManager * manager /*<< DD manager */)\n{\n    DdLevelQueue *queue;\n    int logSize;\n\n    queue = ALLOC(DdLevelQueue,1);\n    if (queue == NULL)\n\treturn(NULL);\n    /* Keep pointers to the insertion points for all levels. */\n    queue->last = ALLOC(DdQueueItem *, levels);\n    if (queue->last == NULL) {\n\tFREE(queue);\n\treturn(NULL);\n    }\n    /* Use a hash table to test for uniqueness. */\n    if (numBuckets < 2) numBuckets = 2;\n    logSize = cuddComputeFloorLog2(numBuckets);\n    queue->numBuckets = 1U << logSize;\n    queue->shift = sizeof(int) * 8 - logSize;\n    queue->buckets = ALLOC(DdQueueItem *, queue->numBuckets);\n    if (queue->buckets == NULL) {\n\tFREE(queue->last);\n\tFREE(queue);\n\treturn(NULL);\n    }\n    memset(queue->last, 0, levels * sizeof(DdQueueItem *));\n    memset(queue->buckets, 0, queue->numBuckets * sizeof(DdQueueItem *));\n    queue->first = NULL;\n    queue->freelist = NULL;\n    queue->levels = levels;\n    queue->itemsize = itemSize;\n    queue->size = 0;\n    queue->maxsize = queue->numBuckets * DD_MAX_SUBTABLE_DENSITY;\n    queue->manager = manager;\n    return(queue);\n\n} /* end of cuddLevelQueueInit */\n\n\n/**\n  @brief Shuts down a level queue.\n\n  @details Releases all the associated memory.\n\n  @sideeffect None\n\n  @see cuddLevelQueueInit\n\n*/\nvoid\ncuddLevelQueueQuit(\n  DdLevelQueue * queue)\n{\n    DdQueueItem *item;\n\n    while (queue->freelist != NULL) {\n\titem = queue->freelist;\n\tqueue->freelist = item->next;\n\tFREE(item);\n    }\n    while (queue->first != NULL) {\n\titem = (DdQueueItem *) queue->first;\n\tqueue->first = item->next;\n\tFREE(item);\n    }\n    FREE(queue->buckets);\n    FREE(queue->last);\n    FREE(queue);\n    return;\n\n} /* end of cuddLevelQueueQuit */\n\n\n/**\n  @brief Inserts a new key in a level queue.\n\n  @details A new entry is created in the queue only if the node is not\n  already enqueued.\n\n  @return a pointer to the queue item if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddLevelQueueInit cuddLevelQueueDequeue\n\n*/\nvoid *\ncuddLevelQueueEnqueue(\n  DdLevelQueue * queue /**< level queue */,\n  void * key /**< key to be enqueued */,\n  int  level /**< level at which to insert */)\n{\n    DdQueueItem *item;\n\n#ifdef DD_DEBUG\n    assert(level < queue->levels);\n#endif\n    /* Check whether entry for this node exists. */\n    item = hashLookup(queue,key);\n    if (item != NULL) return(item);\n\n    /* Get a free item from either the free list or the memory manager. */\n    if (queue->freelist == NULL) {\n\titem = (DdQueueItem *) ALLOC(char, queue->itemsize);\n\tif (item == NULL)\n\t    return(NULL);\n    } else {\n\titem = queue->freelist;\n\tqueue->freelist = item->next;\n    }\n    /* Initialize. */\n    memset(item, 0, queue->itemsize);\n    item->key = key;\n    /* Update stats. */\n    queue->size++;\n\n    if (queue->last[level]) {\n\t/* There are already items for this level in the queue. */\n\titem->next = queue->last[level]->next;\n\tqueue->last[level]->next = item;\n    } else {\n\t/* There are no items at the current level.  Look for the first\n\t** non-empty level preceeding this one. */\n        int plevel = level;\n\twhile (plevel != 0 && queue->last[plevel] == NULL)\n\t    plevel--;\n\tif (queue->last[plevel] == NULL) {\n\t    /* No element precedes this one in the queue. */\n\t    item->next = (DdQueueItem *) queue->first;\n\t    queue->first = item;\n\t} else {\n\t    item->next = queue->last[plevel]->next;\n\t    queue->last[plevel]->next = item;\n\t}\n    }\n    queue->last[level] = item;\n\n    /* Insert entry for the key in the hash table. */\n    if (hashInsert(queue,item) == 0) {\n\treturn(NULL);\n    }\n    return(item);\n\n} /* end of cuddLevelQueueEnqueue */\n\n\n/**\n  @brief Inserts the first key in a level queue.\n\n  @return a pointer to the queue item if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddLevelQueueEnqueue\n\n*/\nvoid *\ncuddLevelQueueFirst(\n  DdLevelQueue * queue /**< level queue */,\n  void * key /**< key to be enqueued */,\n  int  level /**< level at which to insert */)\n{\n    DdQueueItem *item;\n\n#ifdef DD_DEBUG\n    assert(level < queue->levels);\n    /* Check whether entry for this node exists. */\n    item = hashLookup(queue,key);\n    assert(item == NULL);\n#endif\n\n    /* Get a free item from either the free list or the memory manager. */\n    if (queue->freelist == NULL) {\n\titem = (DdQueueItem *) ALLOC(char, queue->itemsize);\n\tif (item == NULL)\n\t    return(NULL);\n    } else {\n\titem = queue->freelist;\n\tqueue->freelist = item->next;\n    }\n    /* Initialize. */\n    memset(item, 0, queue->itemsize);\n    item->key = key;\n    /* Update stats. */\n    queue->size = 1;\n\n    /* No element precedes this one in the queue. */\n    queue->first = item;\n    queue->last[level] = item;\n\n    /* Insert entry for the key in the hash table. */\n    if (hashInsert(queue,item) == 0) {\n\treturn(NULL);\n    }\n    return(item);\n\n} /* end of cuddLevelQueueFirst */\n\n\n/**\n  @brief Remove an item from the front of a level queue.\n\n  @sideeffect None\n\n  @see cuddLevelQueueEnqueue\n\n*/\nvoid\ncuddLevelQueueDequeue(\n  DdLevelQueue * queue,\n  int  level)\n{\n    DdQueueItem *item = (DdQueueItem *) queue->first;\n\n    /* Delete from the hash table. */\n    hashDelete(queue,item);\n\n    /* Since we delete from the front, if this is the last item for\n    ** its level, there are no other items for the same level. */\n    if (queue->last[level] == item) {\n\tqueue->last[level] = NULL;\n    }\n\n    queue->first = item->next;\n    /* Put item on the free list. */\n    item->next = queue->freelist;\n    queue->freelist = item;\n    /* Update stats. */\n    queue->size--;\n    return;\n\n} /* end of cuddLevelQueueDequeue */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Looks up a key in the hash table of a level queue.\n\n  @return a pointer to the item with the given key if the key is\n  found; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddLevelQueueEnqueue hashInsert\n\n*/\nstatic DdQueueItem *\nhashLookup(\n  DdLevelQueue * queue,\n  void * key)\n{\n    int posn;\n    DdQueueItem *item;\n\n    posn = lqHash(key,queue->shift);\n    item = queue->buckets[posn];\n\n    while (item != NULL) {\n\tif (item->key == key) {\n\t    return(item);\n\t}\n\titem = item->cnext;\n    }\n    return(NULL);\n\n} /* end of hashLookup */\n\n\n/**\n  @brief Inserts an item in the hash table of a level queue.\n\n  @details No check is performed to see if an item with the same key\n  is already in the hash table.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddLevelQueueEnqueue\n\n*/\nstatic int\nhashInsert(\n  DdLevelQueue * queue,\n  DdQueueItem * item)\n{\n    int result;\n    int posn;\n\n    if (queue->size > queue->maxsize) {\n\tresult = hashResize(queue);\n\tif (result == 0) return(0);\n    }\n\n    posn = lqHash(item->key,queue->shift);\n    item->cnext = queue->buckets[posn];\n    queue->buckets[posn] = item;\n\n    return(1);\n    \n} /* end of hashInsert */\n\n\n/**\n  @brief Removes an item from the hash table of a level queue.\n\n  @details Nothing is done if the item is not in the table.\n\n  @sideeffect None\n\n  @see cuddLevelQueueDequeue hashInsert\n\n*/\nstatic void\nhashDelete(\n  DdLevelQueue * queue,\n  DdQueueItem * item)\n{\n    int posn;\n    DdQueueItem *prevItem;\n\n    posn = lqHash(item->key,queue->shift);\n    prevItem = queue->buckets[posn];\n\n    if (prevItem == NULL) return;\n    if (prevItem == item) {\n\tqueue->buckets[posn] = prevItem->cnext;\n\treturn;\n    }\n\n    while (prevItem->cnext != NULL) {\n\tif (prevItem->cnext == item) {\n\t    prevItem->cnext = item->cnext;\n\t    return;\n\t}\n\tprevItem = prevItem->cnext;\n    }\n    return;\n\n} /* end of hashDelete */\n\n\n/**\n  @brief Resizes the hash table of a level queue.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see hashInsert\n\n*/\nstatic int\nhashResize(\n  DdLevelQueue * queue)\n{\n    int j;\n    int posn;\n    DdQueueItem *item;\n    DdQueueItem *next;\n    int numBuckets;\n    DdQueueItem **buckets;\n    DdQueueItem **oldBuckets = queue->buckets;\n    int shift;\n    int oldNumBuckets = queue->numBuckets;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    /* Compute the new size of the subtable. */\n    numBuckets = oldNumBuckets << 1;\n    saveHandler = MMoutOfMemory;\n    MMoutOfMemory = queue->manager->outOfMemCallback;\n    buckets = queue->buckets = ALLOC(DdQueueItem *, numBuckets);\n    MMoutOfMemory = saveHandler;\n    if (buckets == NULL) {\n\tqueue->maxsize <<= 1;\n\treturn(1);\n    }\n\n    queue->numBuckets = numBuckets;\n    shift = --(queue->shift);\n    queue->maxsize <<= 1;\n    memset(buckets, 0, numBuckets * sizeof(DdQueueItem *));\n    for (j = 0; j < oldNumBuckets; j++) {\n\titem = oldBuckets[j];\n\twhile (item != NULL) {\n\t    next = item->cnext;\n\t    posn = lqHash(item->key, shift);\n\t    item->cnext = buckets[posn];\n\t    buckets[posn] = item;\n\t    item = next;\n\t}\n    }\n    FREE(oldBuckets);\n    return(1);\n\n} /* end of hashResize */\n"
  },
  {
    "path": "cudd/cudd/cuddLinear.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for %BDD and %ADD reduction by linear\n  transformations.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define CUDD_SWAP_MOVE 0\n#define CUDD_LINEAR_TRANSFORM_MOVE 1\n#define CUDD_INVERSE_TRANSFORM_MOVE 2\n#if SIZEOF_VOID_P == 8\n#define BPL 64\n#define LOGBPL 6\n#else\n#define BPL 32\n#define LOGBPL 5\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int ddLinearUniqueCompare (void const *ptrX, void const *ptrY);\nstatic int ddLinearAndSiftingAux (DdManager *table, int x, int xLow, int xHigh);\nstatic Move * ddLinearAndSiftingUp (DdManager *table, int y, int xLow, Move *prevMoves);\nstatic Move * ddLinearAndSiftingDown (DdManager *table, int x, int xHigh, Move *prevMoves);\nstatic int ddLinearAndSiftingBackward (DdManager *table, int size, Move *moves);\nstatic Move* ddUndoMoves (DdManager *table, Move *moves);\nstatic void cuddXorLinear (DdManager *table, int x, int y);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints the linear transform matrix.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect none\n\n*/\nint\nCudd_PrintLinear(\n  DdManager * table)\n{\n    int i,j,k;\n    int retval;\n    int nvars = table->linearSize;\n    int wordsPerRow = ((nvars - 1) >> LOGBPL) + 1;\n    ptruint word;\n\n    for (i = 0; i < nvars; i++) {\n\tfor (j = 0; j < wordsPerRow; j++) {\n\t    word = table->linear[i*wordsPerRow + j];\n\t    for (k = 0; k < BPL; k++) {\n              retval = fprintf(table->out,\"%\" PRIuPTR,word & (ptruint) 1);\n\t\tif (retval == 0) return(0);\n\t\tword >>= 1;\n\t    }\n\t}\n\tretval = fprintf(table->out,\"\\n\");\n\tif (retval == 0) return(0);\n    }\n    return(1);\n\n} /* end of Cudd_PrintLinear */\n\n\n/**\n  @brief Reads an entry of the linear transform matrix.\n\n  @sideeffect none\n\n*/\nint\nCudd_ReadLinear(\n  DdManager * table /**< CUDD manager */,\n  int  x /**< row index */,\n  int  y /**< column index */)\n{\n    int nvars = table->size;\n    ptruint wordsPerRow = ((ptruint)(nvars - 1) >> LOGBPL) + 1;\n    ptruint word;\n    int bit;\n    int result;\n\n    assert(table->size == table->linearSize);\n\n    word = wordsPerRow * (ptruint) x + ((ptruint) y >> LOGBPL);\n    bit  = y & (BPL-1);\n    result = (int) ((table->linear[word] >> bit) & (ptruint) 1);\n    return(result);\n\n} /* end of Cudd_ReadLinear */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief %BDD reduction based on combination of sifting and linear\n  transformations.\n\n  @details Assumes that no dead nodes are present.\n    <ol>\n    <li> Order all the variables according to the number of entries\n    in each unique table.\n    <li> Sift the variable up and down, remembering each time the\n    total size of the %DD heap. At each position, linear transformation\n    of the two adjacent variables is tried and is accepted if it reduces\n    the size of the %DD.\n    <li> Select the best permutation.\n    <li> Repeat 3 and 4 for all variables.\n    </ol>\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddLinearAndSifting(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\t\ti;\n    IndexKey\t*var;\n    int\t\tsize;\n    int\t\tx;\n    int\t\tresult;\n#ifdef DD_STATS\n    int\t\tpreviousSize;\n#endif\n\n#ifdef DD_STATS\n    table->totalNumberLinearTr = 0;\n#endif\n\n    size = table->size;\n\n    var = NULL;\n    if (table->linear == NULL) {\n\tresult = cuddInitLinear(table);\n\tif (result == 0) goto cuddLinearAndSiftingOutOfMem;\n#if 0\n\t(void) fprintf(table->out,\"\\n\");\n\tresult = Cudd_PrintLinear(table);\n\tif (result == 0) goto cuddLinearAndSiftingOutOfMem;\n#endif\n    } else if (table->size != table->linearSize) {\n\tresult = cuddResizeLinear(table);\n\tif (result == 0) goto cuddLinearAndSiftingOutOfMem;\n#if 0\n\t(void) fprintf(table->out,\"\\n\");\n\tresult = Cudd_PrintLinear(table);\n\tif (result == 0) goto cuddLinearAndSiftingOutOfMem;\n#endif\n    }\n\n    /* Find order in which to sift variables. */\n    var = ALLOC(IndexKey,size);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto cuddLinearAndSiftingOutOfMem;\n    }\n\n    for (i = 0; i < size; i++) {\n\tx = table->perm[i];\n\tvar[i].index = i;\n\tvar[i].keys = table->subtables[x].keys;\n    }\n\n    util_qsort(var,size,sizeof(IndexKey),ddLinearUniqueCompare);\n\n    /* Now sift. */\n    for (i = 0; i < ddMin(table->siftMaxVar,size); i++) {\n\tx = table->perm[var[i].index];\n\tif (x < lower || x > upper) continue;\n#ifdef DD_STATS\n\tpreviousSize = (int) (table->keys - table->isolated);\n#endif\n\tresult = ddLinearAndSiftingAux(table,x,lower,upper);\n\tif (!result) goto cuddLinearAndSiftingOutOfMem;\n#ifdef DD_STATS\n\tif (table->keys < (unsigned) previousSize + table->isolated) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keys > (unsigned) previousSize + table->isolated) {\n\t    (void) fprintf(table->out,\"+\");\t/* should never happen */\n\t    (void) fprintf(table->out,\"\\nSize increased from %d to %u while sifting variable %d\\n\", previousSize, table->keys - table->isolated, var[i].index);\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n#ifdef DD_DEBUG\n\t(void) Cudd_DebugCheck(table);\n#endif\n    }\n\n    FREE(var);\n\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n#:L_LINSIFT %8d: linear trans.\",\n\t\t   table->totalNumberLinearTr);\n#endif\n\n    return(1);\n\ncuddLinearAndSiftingOutOfMem:\n\n    if (var != NULL) FREE(var);\n\n    return(0);\n\n} /* end of cuddLinearAndSifting */\n\n\n/**\n  @brief Linearly combines two adjacent variables.\n\n  @details Specifically, replaces the top variable with the exclusive\n  nor of the two variables.  It assumes that no dead nodes are present\n  on entry to this procedure.  The procedure then guarantees that no\n  dead nodes will be present when it terminates.  cuddLinearInPlace\n  assumes that x &lt; y.\n\n  @return the number of keys in the table if successful; 0 otherwise.\n\n  @sideeffect The two subtables corrresponding to variables x and y are\n  modified. The global counters of the unique table are also affected.\n\n  @see cuddSwapInPlace\n\n*/\nint\ncuddLinearInPlace(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    DdNodePtr *xlist, *ylist;\n    int    xindex, yindex;\n    int    xslots, yslots;\n    int    xshift, yshift;\n#if defined(DD_COUNT) || defined(DD_DEBUG)\n    int    oldxkeys;\n#endif\n    int oldykeys;\n    int    newxkeys, newykeys;\n    int    comple, newcomplement;\n    int    i;\n    int    posn;\n    int    isolated;\n    DdNode *f,*f0,*f1,*f01,*f00,*f11,*f10,*newf1,*newf0;\n    DdNode *g,*next,*last=NULL;\n    DdNodePtr *previousP;\n    DdNode *tmp;\n    DdNode *sentinel = &(table->sentinel);\n#ifdef DD_DEBUG\n    int    count, idcheck;\n#endif\n\n#ifdef DD_DEBUG\n    assert(x < y);\n    assert(cuddNextHigh(table,x) == y);\n    assert(table->subtables[x].keys != 0);\n    assert(table->subtables[y].keys != 0);\n    assert(table->subtables[x].dead == 0);\n    assert(table->subtables[y].dead == 0);\n#endif\n\n    xindex = table->invperm[x];\n    yindex = table->invperm[y];\n\n    if (cuddTestInteract(table,xindex,yindex)) {\n#ifdef DD_STATS\n\ttable->totalNumberLinearTr++;\n#endif\n\t/* Get parameters of x subtable. */\n\txlist = table->subtables[x].nodelist;\n#if defined(DD_COUNT) || defined(DD_DEBUG)\n\toldxkeys = table->subtables[x].keys;\n#endif\n\txslots = table->subtables[x].slots;\n\txshift = table->subtables[x].shift;\n\n\t/* Get parameters of y subtable. */\n\tylist = table->subtables[y].nodelist;\n\toldykeys = table->subtables[y].keys;\n\tyslots = table->subtables[y].slots;\n\tyshift = table->subtables[y].shift;\n\n\tnewxkeys = 0;\n\tnewykeys = oldykeys;\n\n\t/* Check whether the two projection functions involved in this\n\t** swap are isolated. At the end, we'll be able to tell how many\n\t** isolated projection functions are there by checking only these\n\t** two functions again. This is done to eliminate the isolated\n\t** projection functions from the node count.\n\t*/\n\tisolated = - ((table->vars[xindex]->ref == 1) +\n\t\t     (table->vars[yindex]->ref == 1));\n\n\t/* The nodes in the x layer are put in a chain.\n\t** The chain is handled as a FIFO; g points to the beginning and\n\t** last points to the end.\n\t*/\n\tg = NULL;\n#ifdef DD_DEBUG\n\tlast = NULL;\n#endif\n\tfor (i = 0; i < xslots; i++) {\n\t    f = xlist[i];\n\t    if (f == sentinel) continue;\n\t    xlist[i] = sentinel;\n\t    if (g == NULL) {\n\t\tg = f;\n\t    } else {\n\t\tlast->next = f;\n\t    }\n\t    while ((next = f->next) != sentinel) {\n\t\tf = next;\n\t    } /* while there are elements in the collision chain */\n\t    last = f;\n\t} /* for each slot of the x subtable */\n#ifdef DD_DEBUG\n\t/* last is always assigned in the for loop because there is at\n\t** least one key */\n\tassert(last != NULL);\n#endif\n\tlast->next = NULL;\n\n#ifdef DD_COUNT\n\ttable->swapSteps += oldxkeys;\n#endif\n\t/* Take care of the x nodes that must be re-expressed.\n\t** They form a linked list pointed by g.\n\t*/\n\tf = g;\n\twhile (f != NULL) {\n\t    next = f->next;\n\t    /* Find f1, f0, f11, f10, f01, f00. */\n\t    f1 = cuddT(f);\n#ifdef DD_DEBUG\n\t    assert(!(Cudd_IsComplement(f1)));\n#endif\n\t    if ((int) f1->index == yindex) {\n\t\tf11 = cuddT(f1); f10 = cuddE(f1);\n\t    } else {\n\t\tf11 = f10 = f1;\n\t    }\n#ifdef DD_DEBUG\n\t    assert(!(Cudd_IsComplement(f11)));\n#endif\n\t    f0 = cuddE(f);\n\t    comple = Cudd_IsComplement(f0);\n\t    f0 = Cudd_Regular(f0);\n\t    if ((int) f0->index == yindex) {\n\t\tf01 = cuddT(f0); f00 = cuddE(f0);\n\t    } else {\n\t\tf01 = f00 = f0;\n\t    }\n\t    if (comple) {\n\t\tf01 = Cudd_Not(f01);\n\t\tf00 = Cudd_Not(f00);\n\t    }\n\t    /* Decrease ref count of f1. */\n\t    cuddSatDec(f1->ref);\n\t    /* Create the new T child. */\n\t    if (f11 == f00) {\n\t\tnewf1 = f11;\n\t\tcuddSatInc(newf1->ref);\n\t    } else {\n\t\t/* Check ylist for triple (yindex,f11,f00). */\n\t\tposn = ddHash(f11, f00, yshift);\n\t\t/* For each element newf1 in collision list ylist[posn]. */\n\t\tpreviousP = &(ylist[posn]);\n\t\tnewf1 = *previousP;\n\t\twhile (f11 < cuddT(newf1)) {\n\t\t    previousP = &(newf1->next);\n\t\t    newf1 = *previousP;\n\t\t}\n\t\twhile (f11 == cuddT(newf1) && f00 < cuddE(newf1)) {\n\t\t    previousP = &(newf1->next);\n\t\t    newf1 = *previousP;\n\t\t}\n\t\tif (cuddT(newf1) == f11 && cuddE(newf1) == f00) {\n\t\t    cuddSatInc(newf1->ref);\n\t\t} else { /* no match */\n\t\t    newf1 = cuddDynamicAllocNode(table);\n\t\t    if (newf1 == NULL)\n\t\t\tgoto cuddLinearOutOfMem;\n\t\t    newf1->index = yindex; newf1->ref = 1;\n\t\t    cuddT(newf1) = f11;\n\t\t    cuddE(newf1) = f00;\n\t\t    /* Insert newf1 in the collision list ylist[posn];\n\t\t    ** increase the ref counts of f11 and f00.\n\t\t    */\n\t\t    newykeys++;\n\t\t    newf1->next = *previousP;\n\t\t    *previousP = newf1;\n\t\t    cuddSatInc(f11->ref);\n\t\t    tmp = Cudd_Regular(f00);\n\t\t    cuddSatInc(tmp->ref);\n\t\t}\n\t    }\n\t    cuddT(f) = newf1;\n#ifdef DD_DEBUG\n\t    assert(!(Cudd_IsComplement(newf1)));\n#endif\n\n\t    /* Do the same for f0, keeping complement dots into account. */\n\t    /* decrease ref count of f0 */\n\t    tmp = Cudd_Regular(f0);\n\t    cuddSatDec(tmp->ref);\n\t    /* create the new E child */\n\t    if (f01 == f10) {\n\t\tnewf0 = f01;\n\t\ttmp = Cudd_Regular(newf0);\n\t\tcuddSatInc(tmp->ref);\n\t    } else {\n\t\t/* make sure f01 is regular */\n\t\tnewcomplement = Cudd_IsComplement(f01);\n\t\tif (newcomplement) {\n\t\t    f01 = Cudd_Not(f01);\n\t\t    f10 = Cudd_Not(f10);\n\t\t}\n\t\t/* Check ylist for triple (yindex,f01,f10). */\n\t\tposn = ddHash(f01, f10, yshift);\n\t\t/* For each element newf0 in collision list ylist[posn]. */\n\t\tpreviousP = &(ylist[posn]);\n\t\tnewf0 = *previousP;\n\t\twhile (f01 < cuddT(newf0)) {\n\t\t    previousP = &(newf0->next);\n\t\t    newf0 = *previousP;\n\t\t}\n\t\twhile (f01 == cuddT(newf0) && f10 < cuddE(newf0)) {\n\t\t    previousP = &(newf0->next);\n\t\t    newf0 = *previousP;\n\t\t}\n\t\tif (cuddT(newf0) == f01 && cuddE(newf0) == f10) {\n\t\t    cuddSatInc(newf0->ref);\n\t\t} else { /* no match */\n\t\t    newf0 = cuddDynamicAllocNode(table);\n\t\t    if (newf0 == NULL)\n\t\t\tgoto cuddLinearOutOfMem;\n\t\t    newf0->index = yindex; newf0->ref = 1;\n\t\t    cuddT(newf0) = f01;\n\t\t    cuddE(newf0) = f10;\n\t\t    /* Insert newf0 in the collision list ylist[posn];\n\t\t    ** increase the ref counts of f01 and f10.\n\t\t    */\n\t\t    newykeys++;\n\t\t    newf0->next = *previousP;\n\t\t    *previousP = newf0;\n\t\t    cuddSatInc(f01->ref);\n\t\t    tmp = Cudd_Regular(f10);\n\t\t    cuddSatInc(tmp->ref);\n\t\t}\n\t\tif (newcomplement) {\n\t\t    newf0 = Cudd_Not(newf0);\n\t\t}\n\t    }\n\t    cuddE(f) = newf0;\n\n\t    /* Re-insert the modified f in xlist.\n\t    ** The modified f does not already exists in xlist.\n\t    ** (Because of the uniqueness of the cofactors.)\n\t    */\n\t    posn = ddHash(newf1, newf0, xshift);\n\t    newxkeys++;\n\t    previousP = &(xlist[posn]);\n\t    tmp = *previousP;\n\t    while (newf1 < cuddT(tmp)) {\n\t\tpreviousP = &(tmp->next);\n\t\ttmp = *previousP;\n\t    }\n\t    while (newf1 == cuddT(tmp) && newf0 < cuddE(tmp)) {\n\t\tpreviousP = &(tmp->next);\n\t\ttmp = *previousP;\n\t    }\n\t    f->next = *previousP;\n\t    *previousP = f;\n\t    f = next;\n\t} /* while f != NULL */\n\n\t/* GC the y layer. */\n\n\t/* For each node f in ylist. */\n\tfor (i = 0; i < yslots; i++) {\n\t    previousP = &(ylist[i]);\n\t    f = *previousP;\n\t    while (f != sentinel) {\n\t\tnext = f->next;\n\t\tif (f->ref == 0) {\n\t\t    tmp = cuddT(f);\n\t\t    cuddSatDec(tmp->ref);\n\t\t    tmp = Cudd_Regular(cuddE(f));\n\t\t    cuddSatDec(tmp->ref);\n\t\t    cuddDeallocNode(table,f);\n\t\t    newykeys--;\n\t\t} else {\n\t\t    *previousP = f;\n\t\t    previousP = &(f->next);\n\t\t}\n\t\tf = next;\n\t    } /* while f */\n\t    *previousP = sentinel;\n\t} /* for every collision list */\n\n#ifdef DD_DEBUG\n#if 0\n\t(void) fprintf(table->out,\"Linearly combining %d and %d\\n\",x,y);\n#endif\n\tcount = 0;\n\tidcheck = 0;\n\tfor (i = 0; i < yslots; i++) {\n\t    f = ylist[i];\n\t    while (f != sentinel) {\n\t\tcount++;\n\t\tif (f->index != (DdHalfWord) yindex)\n\t\t    idcheck++;\n\t\tf = f->next;\n\t    }\n\t}\n\tif (count != newykeys) {\n\t    fprintf(table->err,\"Error in finding newykeys\\toldykeys = %d\\tnewykeys = %d\\tactual = %d\\n\",oldykeys,newykeys,count);\n\t}\n\tif (idcheck != 0)\n\t    fprintf(table->err,\"Error in id's of ylist\\twrong id's = %d\\n\",idcheck);\n\tcount = 0;\n\tidcheck = 0;\n\tfor (i = 0; i < xslots; i++) {\n\t    f = xlist[i];\n\t    while (f != sentinel) {\n\t\tcount++;\n\t\tif (f->index != (DdHalfWord) xindex)\n\t\t    idcheck++;\n\t\tf = f->next;\n\t    }\n\t}\n\tif (count != newxkeys || newxkeys != oldxkeys) {\n\t    fprintf(table->err,\"Error in finding newxkeys\\toldxkeys = %d \\tnewxkeys = %d \\tactual = %d\\n\",oldxkeys,newxkeys,count);\n\t}\n\tif (idcheck != 0)\n\t    fprintf(table->err,\"Error in id's of xlist\\twrong id's = %d\\n\",idcheck);\n#endif\n\n\tisolated += (table->vars[xindex]->ref == 1) +\n\t\t    (table->vars[yindex]->ref == 1);\n\ttable->isolated += (unsigned int) isolated;\n\n\t/* Set the appropriate fields in table. */\n\ttable->subtables[y].keys = newykeys;\n\n\t/* Here we should update the linear combination table\n\t** to record that x <- x EXNOR y. This is done by complementing\n\t** the (x,y) entry of the table.\n\t*/\n\n\ttable->keys += newykeys - oldykeys;\n\n\tcuddXorLinear(table,xindex,yindex);\n    }\n\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug) {\n\t(void) Cudd_DebugCheck(table);\n    }\n#endif\n\n    return((int) (table->keys - table->isolated));\n\ncuddLinearOutOfMem:\n    (void) fprintf(table->err,\"Error: cuddLinearInPlace out of memory\\n\");\n\n    return (0);\n\n} /* end of cuddLinearInPlace */\n\n\n/**\n  @brief Updates the interaction matrix.\n\n  @sideeffect none\n\n*/\nvoid\ncuddUpdateInteractionMatrix(\n  DdManager * table,\n  int  xindex,\n  int  yindex)\n{\n    int i;\n    for (i = 0; i < yindex; i++) {\n\tif (i != xindex && cuddTestInteract(table,i,yindex)) {\n\t    if (i < xindex) {\n\t\tcuddSetInteract(table,i,xindex);\n\t    } else {\n\t\tcuddSetInteract(table,xindex,i);\n\t    }\n\t}\n    }\n    for (i = yindex+1; i < table->size; i++) {\n\tif (i != xindex && cuddTestInteract(table,yindex,i)) {\n\t    if (i < xindex) {\n\t\tcuddSetInteract(table,i,xindex);\n\t    } else {\n\t\tcuddSetInteract(table,xindex,i);\n\t    }\n\t}\n    }\n\n} /* end of cuddUpdateInteractionMatrix */\n\n\n/**\n  @brief Initializes the linear transform matrix.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect none\n\n*/\nint\ncuddInitLinear(\n  DdManager * table)\n{\n    int words;\n    int wordsPerRow;\n    int nvars;\n    int word;\n    int bit;\n    int i;\n    ptruint *linear;\n\n    nvars = table->size;\n    wordsPerRow = ((nvars - 1) >> LOGBPL) + 1;\n    words = wordsPerRow * nvars;\n    table->linear = linear = ALLOC(ptruint,words);\n    if (linear == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    table->memused += words * sizeof(ptruint);\n    table->linearSize = nvars;\n    for (i = 0; i < words; i++) linear[i] = 0;\n    for (i = 0; i < nvars; i++) {\n\tword = wordsPerRow * i + (i >> LOGBPL);\n\tbit  = i & (BPL-1);\n\tlinear[word] = (ptruint) 1 << bit;\n    }\n    return(1);\n\n} /* end of cuddInitLinear */\n\n\n/**\n  @brief Resizes the linear transform matrix.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect none\n\n*/\nint\ncuddResizeLinear(\n  DdManager * table)\n{\n    int words,oldWords;\n    int wordsPerRow,oldWordsPerRow;\n    int nvars,oldNvars;\n    int word,oldWord;\n    int bit;\n    int i,j;\n    ptruint *linear,*oldLinear;\n\n    oldNvars = table->linearSize;\n    oldWordsPerRow = ((oldNvars - 1) >> LOGBPL) + 1;\n    oldWords = oldWordsPerRow * oldNvars;\n    oldLinear = table->linear;\n\n    nvars = table->size;\n    wordsPerRow = ((nvars - 1) >> LOGBPL) + 1;\n    words = wordsPerRow * nvars;\n    table->linear = linear = ALLOC(ptruint,words);\n    if (linear == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    table->memused += (words - oldWords) * sizeof(ptruint);\n    for (i = 0; i < words; i++) linear[i] = 0;\n\n    /* Copy old matrix. */\n    for (i = 0; i < oldNvars; i++) {\n\tfor (j = 0; j < oldWordsPerRow; j++) {\n\t    oldWord = oldWordsPerRow * i + j;\n\t    word = wordsPerRow * i + j;\n\t    linear[word] = oldLinear[oldWord];\n\t}\n    }\n    FREE(oldLinear);\n\n    /* Add elements to the diagonal. */\n    for (i = oldNvars; i < nvars; i++) {\n\tword = wordsPerRow * i + (i >> LOGBPL);\n\tbit  = i & (BPL-1);\n\tlinear[word] = (ptruint) 1 << bit;\n    }\n    table->linearSize = nvars;\n\n    return(1);\n\n} /* end of cuddResizeLinear */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Comparison function used by qsort to order the\n  variables according to the number of keys in the subtables.\n\n  @return the difference in number of keys between the two variables\n  being compared.\n\n  @sideeffect None\n\n*/\nstatic int\nddLinearUniqueCompare(\n  void const * ptrX,\n  void const * ptrY)\n{\n    IndexKey const * pX = (IndexKey const *) ptrX;\n    IndexKey const * pY = (IndexKey const *) ptrY;\n#if 0\n    if (pY->keys == pX->keys) {\n\treturn(pX->index - pY->index);\n    }\n#endif\n    return(pY->keys - pX->keys);\n\n} /* end of ddLinearUniqueCompare */\n\n\n/**\n  @brief Given xLow <= x <= xHigh moves x up and down between the\n  boundaries.\n\n  @details At each step a linear transformation is tried, and, if it\n  decreases the size of the %DD, it is accepted. Finds the best position\n  and does the required changes.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddLinearAndSiftingAux(\n  DdManager * table,\n  int  x,\n  int  xLow,\n  int  xHigh)\n{\n\n    Move\t*move;\n    Move\t*moveUp;\t\t/* list of up moves */\n    Move\t*moveDown;\t\t/* list of down moves */\n    int\t\tinitialSize;\n    int\t\tresult;\n\n    initialSize = (int) (table->keys - table->isolated);\n\n    moveDown = NULL;\n    moveUp = NULL;\n\n    if (x == xLow) {\n\tmoveDown = ddLinearAndSiftingDown(table,x,xHigh,NULL);\n\t/* At this point x --> xHigh unless bounding occurred. */\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM) goto ddLinearAndSiftingAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = ddLinearAndSiftingBackward(table,initialSize,moveDown);\n\tif (!result) goto ddLinearAndSiftingAuxOutOfMem;\n\n    } else if (x == xHigh) {\n\tmoveUp = ddLinearAndSiftingUp(table,x,xLow,NULL);\n\t/* At this point x --> xLow unless bounding occurred. */\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM) goto ddLinearAndSiftingAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = ddLinearAndSiftingBackward(table,initialSize,moveUp);\n\tif (!result) goto ddLinearAndSiftingAuxOutOfMem;\n\n    } else if ((x - xLow) > (xHigh - x)) { /* must go down first: shorter */\n\tmoveDown = ddLinearAndSiftingDown(table,x,xHigh,NULL);\n\t/* At this point x --> xHigh unless bounding occurred. */\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM) goto ddLinearAndSiftingAuxOutOfMem;\n\tmoveUp = ddUndoMoves(table,moveDown);\n#ifdef DD_DEBUG\n\tassert(moveUp == NULL || moveUp->x == (DdHalfWord) x);\n#endif\n\tmoveUp = ddLinearAndSiftingUp(table,x,xLow,moveUp);\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM) goto ddLinearAndSiftingAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = ddLinearAndSiftingBackward(table,initialSize,moveUp);\n\tif (!result) goto ddLinearAndSiftingAuxOutOfMem;\n\n    } else { /* must go up first: shorter */\n\tmoveUp = ddLinearAndSiftingUp(table,x,xLow,NULL);\n\t/* At this point x --> xLow unless bounding occurred. */\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM) goto ddLinearAndSiftingAuxOutOfMem;\n\tmoveDown = ddUndoMoves(table,moveUp);\n#ifdef DD_DEBUG\n\tassert(moveDown == NULL || moveDown->y == (DdHalfWord) x);\n#endif\n\tmoveDown = ddLinearAndSiftingDown(table,x,xHigh,moveDown);\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM) goto ddLinearAndSiftingAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = ddLinearAndSiftingBackward(table,initialSize,moveDown);\n\tif (!result) goto ddLinearAndSiftingAuxOutOfMem;\n    }\n\n    while (moveDown != NULL) {\n\tmove = moveDown->next;\n\tcuddDeallocMove(table, moveDown);\n\tmoveDown = move;\n    }\n    while (moveUp != NULL) {\n\tmove = moveUp->next;\n\tcuddDeallocMove(table, moveUp);\n\tmoveUp = move;\n    }\n\n    return(1);\n\nddLinearAndSiftingAuxOutOfMem:\n    while (moveDown != NULL) {\n\tmove = moveDown->next;\n\tcuddDeallocMove(table, moveDown);\n\tmoveDown = move;\n    }\n    while (moveUp != NULL) {\n\tmove = moveUp->next;\n\tcuddDeallocMove(table, moveUp);\n\tmoveUp = move;\n    }\n\n    return(0);\n\n} /* end of ddLinearAndSiftingAux */\n\n\n/**\n  @brief Sifts a variable up and applies linear transformations.\n\n  @details Moves y up until either it reaches the bound (xLow) or the\n  size of the %DD heap increases too much.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddLinearAndSiftingUp(\n  DdManager * table,\n  int  y,\n  int  xLow,\n  Move * prevMoves)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\tx;\n    int\t\tsize, newsize;\n    int\t\tlimitSize;\n    int\t\txindex, yindex;\n    int\t\tisolated;\n    int\t\tL;\t/* lower bound on DD size */\n#ifdef DD_DEBUG\n    int checkL;\n    int z;\n    int zindex;\n#endif\n\n    moves = prevMoves;\n    yindex = table->invperm[y];\n\n    /* Initialize the lower bound.\n    ** The part of the DD below y will not change.\n    ** The part of the DD above y that does not interact with y will not\n    ** change. The rest may vanish in the best case, except for\n    ** the nodes at level xLow, which will not vanish, regardless.\n    */\n    limitSize = L = (int) (table->keys - table->isolated);\n    for (x = xLow + 1; x < y; x++) {\n\txindex = table->invperm[x];\n\tif (cuddTestInteract(table,xindex,yindex)) {\n\t    isolated = table->vars[xindex]->ref == 1;\n\t    L -= (int) table->subtables[x].keys - isolated;\n\t}\n    }\n    isolated = table->vars[yindex]->ref == 1;\n    L -= (int) table->subtables[y].keys - isolated;\n\n    x = cuddNextLow(table,y);\n    while (x >= xLow && L <= limitSize) {\n\txindex = table->invperm[x];\n#ifdef DD_DEBUG\n\tcheckL = table->keys - table->isolated;\n\tfor (z = xLow + 1; z < y; z++) {\n\t    zindex = table->invperm[z];\n\t    if (cuddTestInteract(table,zindex,yindex)) {\n\t\tisolated = table->vars[zindex]->ref == 1;\n\t\tcheckL -= table->subtables[z].keys - isolated;\n\t    }\n\t}\n\tisolated = table->vars[yindex]->ref == 1;\n\tcheckL -= table->subtables[y].keys - isolated;\n\tif (L != checkL) {\n\t    (void) fprintf(table->out, \"checkL(%d) != L(%d)\\n\",checkL,L);\n\t}\n#endif\n\tsize = cuddSwapInPlace(table,x,y);\n\tif (size == 0) goto ddLinearAndSiftingUpOutOfMem;\n\tnewsize = cuddLinearInPlace(table,x,y);\n\tif (newsize == 0) goto ddLinearAndSiftingUpOutOfMem;\n\tmove = (Move *) cuddDynamicAllocNode(table);\n\tif (move == NULL) goto ddLinearAndSiftingUpOutOfMem;\n\tmove->x = x;\n\tmove->y = y;\n\tmove->next = moves;\n\tmoves = move;\n\tmove->flags = CUDD_SWAP_MOVE;\n\tif (newsize >= size) {\n\t    /* Undo transformation. The transformation we apply is\n\t    ** its own inverse. Hence, we just apply the transformation\n\t    ** again.\n\t    */\n\t    newsize = cuddLinearInPlace(table,x,y);\n\t    if (newsize == 0) goto ddLinearAndSiftingUpOutOfMem;\n#ifdef DD_DEBUG\n\t    if (newsize != size) {\n\t\t(void) fprintf(table->out,\"Change in size after identity transformation! From %d to %d\\n\",size,newsize);\n\t    }\n#endif\n\t} else if (cuddTestInteract(table,xindex,yindex)) {\n\t    size = newsize;\n\t    move->flags = CUDD_LINEAR_TRANSFORM_MOVE;\n\t    cuddUpdateInteractionMatrix(table,xindex,yindex);\n\t}\n\tmove->size = size;\n\t/* Update the lower bound. */\n\tif (cuddTestInteract(table,xindex,yindex)) {\n\t    isolated = table->vars[xindex]->ref == 1;\n\t    L += (int) table->subtables[y].keys - isolated;\n\t}\n\tif ((double) size > (double) limitSize * table->maxGrowth) break;\n\tif (size < limitSize) limitSize = size;\n\ty = x;\n\tx = cuddNextLow(table,y);\n    }\n    return(moves);\n\nddLinearAndSiftingUpOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return((Move *) CUDD_OUT_OF_MEM);\n\n} /* end of ddLinearAndSiftingUp */\n\n\n/**\n  @brief Sifts a variable down and applies linear transformations.\n\n  @details Moves x down until either it reaches the bound (xHigh) or\n  the size of the %DD heap increases too much.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddLinearAndSiftingDown(\n  DdManager * table,\n  int  x,\n  int  xHigh,\n  Move * prevMoves)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\ty;\n    int\t\tsize, newsize;\n    int\t\tR;\t/* upper bound on node decrease */\n    int\t\tlimitSize;\n    int\t\txindex, yindex;\n    int\t\tisolated;\n#ifdef DD_DEBUG\n    int\t\tcheckR;\n    int\t\tz;\n    int\t\tzindex;\n#endif\n\n    moves = prevMoves;\n    /* Initialize R */\n    xindex = table->invperm[x];\n    limitSize = size = table->keys - table->isolated;\n    R = 0;\n    for (y = xHigh; y > x; y--) {\n\tyindex = table->invperm[y];\n\tif (cuddTestInteract(table,xindex,yindex)) {\n\t    isolated = table->vars[yindex]->ref == 1;\n\t    R += table->subtables[y].keys - isolated;\n\t}\n    }\n\n    y = cuddNextHigh(table,x);\n    while (y <= xHigh && size - R < limitSize) {\n#ifdef DD_DEBUG\n\tcheckR = 0;\n\tfor (z = xHigh; z > x; z--) {\n\t    zindex = table->invperm[z];\n\t    if (cuddTestInteract(table,xindex,zindex)) {\n\t\tisolated = table->vars[zindex]->ref == 1;\n\t\tcheckR += (int) table->subtables[z].keys - isolated;\n\t    }\n\t}\n\tif (R != checkR) {\n\t    (void) fprintf(table->out, \"checkR(%d) != R(%d)\\n\",checkR,R);\n\t}\n#endif\n\t/* Update upper bound on node decrease. */\n\tyindex = table->invperm[y];\n\tif (cuddTestInteract(table,xindex,yindex)) {\n\t    isolated = table->vars[yindex]->ref == 1;\n\t    R -= (int) table->subtables[y].keys - isolated;\n\t}\n\tsize = cuddSwapInPlace(table,x,y);\n\tif (size == 0) goto ddLinearAndSiftingDownOutOfMem;\n\tnewsize = cuddLinearInPlace(table,x,y);\n\tif (newsize == 0) goto ddLinearAndSiftingDownOutOfMem;\n\tmove = (Move *) cuddDynamicAllocNode(table);\n\tif (move == NULL) goto ddLinearAndSiftingDownOutOfMem;\n\tmove->x = x;\n\tmove->y = y;\n\tmove->next = moves;\n\tmoves = move;\n\tmove->flags = CUDD_SWAP_MOVE;\n\tif (newsize >= size) {\n\t    /* Undo transformation. The transformation we apply is\n\t    ** its own inverse. Hence, we just apply the transformation\n\t    ** again.\n\t    */\n\t    newsize = cuddLinearInPlace(table,x,y);\n\t    if (newsize == 0) goto ddLinearAndSiftingDownOutOfMem;\n\t    if (newsize != size) {\n\t\t(void) fprintf(table->out,\"Change in size after identity transformation! From %d to %d\\n\",size,newsize);\n\t    }\n\t} else if (cuddTestInteract(table,xindex,yindex)) {\n\t    size = newsize;\n\t    move->flags = CUDD_LINEAR_TRANSFORM_MOVE;\n\t    cuddUpdateInteractionMatrix(table,xindex,yindex);\n\t}\n\tmove->size = size;\n\tif ((double) size > (double) limitSize * table->maxGrowth) break;\n\tif (size < limitSize) limitSize = size;\n\tx = y;\n\ty = cuddNextHigh(table,x);\n    }\n    return(moves);\n\nddLinearAndSiftingDownOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return((Move *) CUDD_OUT_OF_MEM);\n\n} /* end of ddLinearAndSiftingDown */\n\n\n/**\n  @brief Given a set of moves, returns the %DD heap to the order\n  giving the minimum size.\n\n  @details In case of ties, returns to the closest position giving the\n  minimum size.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddLinearAndSiftingBackward(\n  DdManager * table,\n  int  size,\n  Move * moves)\n{\n    Move *move;\n    int\tres;\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size < size) {\n\t    size = move->size;\n\t}\n    }\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size == size) return(1);\n\tif (move->flags == CUDD_LINEAR_TRANSFORM_MOVE) {\n\t    res = cuddLinearInPlace(table,(int)move->x,(int)move->y);\n\t    if (!res) return(0);\n\t}\n\tres = cuddSwapInPlace(table,(int)move->x,(int)move->y);\n\tif (!res) return(0);\n\tif (move->flags == CUDD_INVERSE_TRANSFORM_MOVE) {\n\t    res = cuddLinearInPlace(table,(int)move->x,(int)move->y);\n\t    if (!res) return(0);\n\t}\n    }\n\n    return(1);\n\n} /* end of ddLinearAndSiftingBackward */\n\n\n/**\n  @brief Given a set of moves, returns the %DD heap to the order\n  in effect before the moves.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic Move*\nddUndoMoves(\n  DdManager * table,\n  Move * moves)\n{\n    Move *invmoves = NULL;\n    Move *move;\n    Move *invmove;\n    int\tsize;\n\n    for (move = moves; move != NULL; move = move->next) {\n\tinvmove = (Move *) cuddDynamicAllocNode(table);\n\tif (invmove == NULL) goto ddUndoMovesOutOfMem;\n\tinvmove->x = move->x;\n\tinvmove->y = move->y;\n\tinvmove->next = invmoves;\n\tinvmoves = invmove;\n\tif (move->flags == CUDD_SWAP_MOVE) {\n\t    invmove->flags = CUDD_SWAP_MOVE;\n\t    size = cuddSwapInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto ddUndoMovesOutOfMem;\n\t} else if (move->flags == CUDD_LINEAR_TRANSFORM_MOVE) {\n\t    invmove->flags = CUDD_INVERSE_TRANSFORM_MOVE;\n\t    size = cuddLinearInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto ddUndoMovesOutOfMem;\n\t    size = cuddSwapInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto ddUndoMovesOutOfMem;\n\t} else { /* must be CUDD_INVERSE_TRANSFORM_MOVE */\n#ifdef DD_DEBUG\n\t    (void) fprintf(table->err,\"Unforseen event in ddUndoMoves!\\n\");\n#endif\n\t    invmove->flags = CUDD_LINEAR_TRANSFORM_MOVE;\n\t    size = cuddSwapInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto ddUndoMovesOutOfMem;\n\t    size = cuddLinearInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto ddUndoMovesOutOfMem;\n\t}\n\tinvmove->size = size;\n    }\n\n    return(invmoves);\n\nddUndoMovesOutOfMem:\n    while (invmoves != NULL) {\n\tmove = invmoves->next;\n\tcuddDeallocMove(table, invmoves);\n\tinvmoves = move;\n    }\n    return((Move *) CUDD_OUT_OF_MEM);\n\n} /* end of ddUndoMoves */\n\n\n/**\n  @brief XORs two rows of the linear transform matrix.\n\n  @details Replaces the first row with the result.\n\n  @sideeffect none\n\n*/\nstatic void\ncuddXorLinear(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    int i;\n    int nvars = table->size;\n    int wordsPerRow = ((nvars - 1) >> LOGBPL) + 1;\n    int xstart = wordsPerRow * x;\n    int ystart = wordsPerRow * y;\n    ptruint *linear = table->linear;\n\n    for (i = 0; i < wordsPerRow; i++) {\n\tlinear[xstart+i] ^= linear[ystart+i];\n    }\n\n} /* end of cuddXorLinear */\n"
  },
  {
    "path": "cudd/cudd/cuddLiteral.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for manipulation of literal sets represented by BDDs.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Computes the intesection of two sets of literals\n  represented as BDDs.\n\n  @details Each set is represented as a cube of the literals in the\n  set. The empty set is represented by the constant 1.  No variable\n  can be simultaneously present in both phases in a set.\n\n  @return a pointer to the %BDD representing the intersected sets, if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_bddLiteralSetIntersection(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddLiteralSetIntersectionRecur(dd,f,g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddLiteralSetIntersection */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of\n  Cudd_bddLiteralSetIntersection.\n\n  @details Scans the cubes for common variables, and checks whether\n  they agree in phase.\n\n  @return a pointer to the resulting cube if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddBddLiteralSetIntersectionRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode *res, *tmp;\n    DdNode *F, *G;\n    DdNode *fc, *gc;\n    DdNode *one;\n    DdNode *zero;\n    int topf, topg, comple;\n    int phasef, phaseg;\n\n    statLine(dd);\n    if (f == g) return(f);\n\n    F = Cudd_Regular(f);\n    G = Cudd_Regular(g);\n    one = DD_ONE(dd);\n\n    /* Here f != g. If F == G, then f and g are complementary.\n    ** Since they are two cubes, this case only occurs when f == v,\n    ** g == v', and v is a variable or its complement.\n    */\n    if (F == G) return(one);\n\n    zero = Cudd_Not(one);\n    topf = cuddI(dd,F->index);\n    topg = cuddI(dd,G->index);\n    /* Look for a variable common to both cubes. If there are none, this\n    ** loop will stop when the constant node is reached in both cubes.\n    */\n    while (topf != topg) {\n\tif (topf < topg) {\t/* move down on f */\n\t    comple = f != F;\n\t    f = cuddT(F);\n\t    if (comple) f = Cudd_Not(f);\n\t    if (f == zero) {\n\t\tf = cuddE(F);\n\t\tif (comple) f = Cudd_Not(f);\n\t    }\n\t    F = Cudd_Regular(f);\n\t    topf = cuddI(dd,F->index);\n\t} else if (topg < topf) {\n\t    comple = g != G;\n\t    g = cuddT(G);\n\t    if (comple) g = Cudd_Not(g);\n\t    if (g == zero) {\n\t\tg = cuddE(G);\n\t\tif (comple) g = Cudd_Not(g);\n\t    }\n\t    G = Cudd_Regular(g);\n\t    topg = cuddI(dd,G->index);\n\t}\n    }\n\n    /* At this point, f == one <=> g == 1. It suffices to test one of them. */\n    if (f == one) return(one);\n\n    res = cuddCacheLookup2(dd,Cudd_bddLiteralSetIntersection,f,g);\n    if (res != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Here f and g are both non constant and have the same top variable. */\n    comple = f != F;\n    fc = cuddT(F);\n    phasef = 1;\n    if (comple) fc = Cudd_Not(fc);\n    if (fc == zero) {\n\tfc = cuddE(F);\n\tphasef = 0;\n\tif (comple) fc = Cudd_Not(fc);\n    }\n    comple = g != G;\n    gc = cuddT(G);\n    phaseg = 1;\n    if (comple) gc = Cudd_Not(gc);\n    if (gc == zero) {\n\tgc = cuddE(G);\n\tphaseg = 0;\n\tif (comple) gc = Cudd_Not(gc);\n    }\n\n    tmp = cuddBddLiteralSetIntersectionRecur(dd,fc,gc);\n    if (tmp == NULL) {\n\treturn(NULL);\n    }\n\n    if (phasef != phaseg) {\n\tres = tmp;\n    } else {\n\tcuddRef(tmp);\n\tif (phasef == 0) {\n\t    res = cuddBddAndRecur(dd,Cudd_Not(dd->vars[F->index]),tmp);\n\t} else {\n\t    res = cuddBddAndRecur(dd,dd->vars[F->index],tmp);\n\t}\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd,tmp);\n\t    return(NULL);\n\t}\n\tcuddDeref(tmp); /* Just cuddDeref, because it is included in result */\n    }\n\n    cuddCacheInsert2(dd,Cudd_bddLiteralSetIntersection,f,g,res);\n\n    return(res);\n\n} /* end of cuddBddLiteralSetIntersectionRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n"
  },
  {
    "path": "cudd/cudd/cuddMatMult.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Matrix multiplication functions.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * addMMRecur (DdManager *dd, DdNode *A, DdNode *B, int topP, int *vars);\nstatic DdNode * addTriangleRecur (DdManager *dd, DdNode *f, DdNode *g, int *vars, DdNode *cube);\nstatic DdNode * cuddAddOuterSumRecur (DdManager *dd, DdNode *M, DdNode *r, DdNode *c);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Calculates the product of two matrices represented as\n  ADDs.\n\n  @details This procedure implements the quasiring multiplication\n  algorithm.  A is assumed to depend on variables x (rows) and z\n  (columns).  B is assumed to depend on variables z (rows) and y\n  (columns).  The product of A and B then depends on x (rows) and y\n  (columns).  Only the z variables have to be explicitly identified;\n  they are the \"summation\" variables.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addTimesPlus Cudd_addTriangle Cudd_bddAndAbstract\n\n*/\nDdNode *\nCudd_addMatrixMultiply(\n  DdManager * dd,\n  DdNode * A,\n  DdNode * B,\n  DdNode ** z,\n  int  nz)\n{\n    int i, nvars, *vars;\n    DdNode *res; \n\n    /* Array vars says what variables are \"summation\" variables. */\n    nvars = dd->size;\n    vars = ALLOC(int,nvars);\n    if (vars == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < nvars; i++) {\n        vars[i] = 0;\n    }\n    for (i = 0; i < nz; i++) {\n        vars[z[i]->index] = 1;\n    }\n\n    do {\n\tdd->reordered = 0;\n\tres = addMMRecur(dd,A,B,-1,vars);\n    } while (dd->reordered == 1);\n    FREE(vars);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addMatrixMultiply */\n\n\n/**\n  @brief Calculates the product of two matrices represented as\n  ADDs.\n\n  @details Calculates the product of two matrices, A and B,\n  represented as ADDs, using the CMU matrix by matrix multiplication\n  procedure by Clarke et al..  Matrix A has x's as row variables and\n  z's as column variables, while matrix B has z's as row variables and\n  y's as column variables.  The resulting matrix has x's as row\n  variables and y's as column variables.\n\n  @return the pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addMatrixMultiply\n\n*/\nDdNode *\nCudd_addTimesPlus(\n  DdManager * dd,\n  DdNode * A,\n  DdNode * B,\n  DdNode ** z,\n  int  nz)\n{\n    DdNode *w, *cube, *tmp, *res; \n    int i;\n    tmp = Cudd_addApply(dd,Cudd_addTimes,A,B);\n    if (tmp == NULL) return(NULL);\n    Cudd_Ref(tmp);\n    Cudd_Ref(cube = DD_ONE(dd));\n    for (i = nz-1; i >= 0; i--) {\n\t w = Cudd_addIte(dd,z[i],cube,DD_ZERO(dd));\n\t if (w == NULL) {\n\t    Cudd_RecursiveDeref(dd,tmp);\n\t    return(NULL);\n\t }\n\t Cudd_Ref(w);\n\t Cudd_RecursiveDeref(dd,cube);\n\t cube = w;\n    }\n    res = Cudd_addExistAbstract(dd,tmp,cube);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd,tmp);\n\tCudd_RecursiveDeref(dd,cube);\n\treturn(NULL);\n    }\n    Cudd_Ref(res);\n    Cudd_RecursiveDeref(dd,cube);\n    Cudd_RecursiveDeref(dd,tmp);\n    Cudd_Deref(res);\n    return(res);\n\n} /* end of Cudd_addTimesPlus */\n\n\n/**\n  @brief Performs the triangulation step for the shortest path\n  computation.\n\n  @details Implements the semiring multiplication algorithm used in\n  the triangulation step for the shortest path computation.  f\n  is assumed to depend on variables x (rows) and z (columns).  g is\n  assumed to depend on variables z (rows) and y (columns).  The product\n  of f and g then depends on x (rows) and y (columns).  Only the z\n  variables have to be explicitly identified; they are the\n  \"abstraction\" variables.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addMatrixMultiply Cudd_bddAndAbstract\n\n*/\nDdNode *\nCudd_addTriangle(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode ** z,\n  int  nz)\n{\n    int    i, nvars, *vars;\n    DdNode *res, *cube;\n\n    nvars = dd->size;\n    vars = ALLOC(int, nvars);\n    if (vars == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < nvars; i++) vars[i] = -1;\n    for (i = 0; i < nz; i++) vars[z[i]->index] = i;\n    cube = Cudd_addComputeCube(dd, z, NULL, nz);\n    if (cube == NULL) {\n\tFREE(vars);\n\treturn(NULL);\n    }\n    cuddRef(cube);\n\n    do {\n\tdd->reordered = 0;\n\tres = addTriangleRecur(dd, f, g, vars, cube);\n    } while (dd->reordered == 1);\n    if (res != NULL) cuddRef(res);\n    Cudd_RecursiveDeref(dd,cube);\n    if (res != NULL) cuddDeref(res);\n    FREE(vars);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addTriangle */\n\n\n/**\n  @brief Takes the minimum of a matrix and the outer sum of two vectors.\n\n  @details Takes the pointwise minimum of a matrix and the outer\n  sum of two vectors.  This procedure is used in the Floyd-Warshall\n  all-pair shortest path algorithm.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_addOuterSum(\n  DdManager *dd,\n  DdNode *M,\n  DdNode *r,\n  DdNode *c)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddOuterSumRecur(dd, M, r, c);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_addOuterSum */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Performs the recursive step of Cudd_addMatrixMultiply.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\naddMMRecur(\n  DdManager * dd,\n  DdNode * A,\n  DdNode * B,\n  int  topP,\n  int * vars)\n{\n    DdNode *zero,\n           *At,\t\t/* positive cofactor of first operand */\n\t   *Ae,\t\t/* negative cofactor of first operand */\n\t   *Bt,\t\t/* positive cofactor of second operand */\n\t   *Be,\t\t/* negative cofactor of second operand */\n\t   *t,\t\t/* positive cofactor of result */\n\t   *e,\t\t/* negative cofactor of result */\n\t   *scaled,\t/* scaled result */\n\t   *add_scale,\t/* ADD representing the scaling factor */\n\t   *res;\n    int\ti;\t\t/* loop index */\n    double scale;\t/* scaling factor */\n    int index;\t\t/* index of the top variable */\n    CUDD_VALUE_TYPE value;\n    int topA, topB, topV;\n    DD_CTFP cacheOp;\n\n    statLine(dd);\n    zero = DD_ZERO(dd);\n\n    if (A == zero || B == zero) {\n        return(zero);\n    }\n\n    if (cuddIsConstant(A) && cuddIsConstant(B)) {\n\t/* Compute the scaling factor. It is 2^k, where k is the\n\t** number of summation variables below the current variable.\n\t** Indeed, these constants represent blocks of 2^k identical\n\t** constant values in both A and B.\n\t*/\n\tvalue = cuddV(A) * cuddV(B);\n\tfor (i = 0; i < dd->size; i++) {\n\t    if (vars[i]) {\n\t\tif (dd->perm[i] > topP) {\n\t\t    value *= (CUDD_VALUE_TYPE) 2;\n\t\t}\n\t    }\n\t}\n\tres = cuddUniqueConst(dd, value);\n\treturn(res);\n    }\n\n    /* Standardize to increase cache efficiency. Clearly, A*B != B*A\n    ** in matrix multiplication. However, which matrix is which is\n    ** determined by the variables appearing in the ADDs and not by\n    ** which one is passed as first argument.\n    */\n    if (A > B) {\n\tDdNode *tmp = A;\n\tA = B;\n\tB = tmp;\n    }\n\n    topA = cuddI(dd,A->index); topB = cuddI(dd,B->index);\n    topV = ddMin(topA,topB);\n\n    cacheOp = (DD_CTFP) addMMRecur;\n    res = cuddCacheLookup2(dd,cacheOp,A,B);\n    if (res != NULL) {\n\t/* If the result is 0, there is no need to normalize.\n\t** Otherwise we count the number of z variables between\n\t** the current depth and the top of the ADDs. These are\n\t** the missing variables that determine the size of the\n\t** constant blocks.\n\t*/\n\tif (res == zero) return(res);\n\tscale = 1.0;\n\tfor (i = 0; i < dd->size; i++) {\n\t    if (vars[i]) {\n\t\tif (dd->perm[i] > topP && dd->perm[i] < topV) {\n\t\t    scale *= 2;\n\t\t}\n\t    }\n\t}\n\tif (scale > 1.0) {\n\t    cuddRef(res);\n\t    add_scale = cuddUniqueConst(dd,(CUDD_VALUE_TYPE)scale);\n\t    if (add_scale == NULL) {\n\t\tCudd_RecursiveDeref(dd, res);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(add_scale);\n\t    scaled = cuddAddApplyRecur(dd,Cudd_addTimes,res,add_scale);\n\t    if (scaled == NULL) {\n\t\tCudd_RecursiveDeref(dd, add_scale);\n\t\tCudd_RecursiveDeref(dd, res);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(scaled);\n\t    Cudd_RecursiveDeref(dd, add_scale);\n\t    Cudd_RecursiveDeref(dd, res);\n\t    res = scaled;\n\t    cuddDeref(res);\n\t}\n        return(res);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* compute the cofactors */\n    if (topV == topA) {\n\tAt = cuddT(A);\n\tAe = cuddE(A);\n    } else {\n\tAt = Ae = A;\n    }\n    if (topV == topB) {\n\tBt = cuddT(B);\n\tBe = cuddE(B);\n    } else {\n\tBt = Be = B;\n    }\n\n    t = addMMRecur(dd, At, Bt, (int)topV, vars);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n    e = addMMRecur(dd, Ae, Be, (int)topV, vars);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(dd, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    index = dd->invperm[topV];\n    if (vars[index] == 0) {\n\t/* We have split on either the rows of A or the columns\n\t** of B. We just need to connect the two subresults,\n\t** which correspond to two submatrices of the result.\n\t*/\n\tres = (t == e) ? t : cuddUniqueInter(dd,index,t,e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, t);\n\t    Cudd_RecursiveDeref(dd, e);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tcuddDeref(t);\n\tcuddDeref(e);\n    } else {\n\t/* we have simultaneously split on the columns of A and\n\t** the rows of B. The two subresults must be added.\n\t*/\n\tres = cuddAddApplyRecur(dd,Cudd_addPlus,t,e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, t);\n\t    Cudd_RecursiveDeref(dd, e);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDeref(dd, t);\n\tCudd_RecursiveDeref(dd, e);\n    }\n\n    cuddCacheInsert2(dd,cacheOp,A,B,res);\n\n    /* We have computed (and stored in the computed table) a minimal\n    ** result; that is, a result that assumes no summation variables\n    ** between the current depth of the recursion and its top\n    ** variable. We now take into account the z variables by properly\n    ** scaling the result.\n    */\n    if (res != zero) {\n\tscale = 1.0;\n\tfor (i = 0; i < dd->size; i++) {\n\t    if (vars[i]) {\n\t\tif (dd->perm[i] > topP && dd->perm[i] < topV) {\n\t\t    scale *= 2;\n\t\t}\n\t    }\n\t}\n\tif (scale > 1.0) {\n\t    add_scale = cuddUniqueConst(dd,(CUDD_VALUE_TYPE)scale);\n\t    if (add_scale == NULL) {\n\t\tCudd_RecursiveDeref(dd, res);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(add_scale);\n\t    scaled = cuddAddApplyRecur(dd,Cudd_addTimes,res,add_scale);\n\t    if (scaled == NULL) {\n\t\tCudd_RecursiveDeref(dd, res);\n\t\tCudd_RecursiveDeref(dd, add_scale);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(scaled);\n\t    Cudd_RecursiveDeref(dd, add_scale);\n\t    Cudd_RecursiveDeref(dd, res);\n\t    res = scaled;\n\t}\n    }\n    cuddDeref(res);\n    return(res);\n\n} /* end of addMMRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addTriangle.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\naddTriangleRecur(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  int * vars,\n  DdNode *cube)\n{\n    DdNode *fv, *fvn, *gv, *gvn, *t, *e, *res;\n    CUDD_VALUE_TYPE value;\n    int top, topf, topg, index;\n\n    statLine(dd);\n    if (f == DD_PLUS_INFINITY(dd) || g == DD_PLUS_INFINITY(dd)) {\n\treturn(DD_PLUS_INFINITY(dd));\n    }\n\n    if (cuddIsConstant(f) && cuddIsConstant(g)) {\n\tvalue = cuddV(f) + cuddV(g);\n\tres = cuddUniqueConst(dd, value);\n\treturn(res);\n    }\n    if (f < g) {\n\tDdNode *tmp = f;\n\tf = g;\n\tg = tmp;\n    }\n\n    if (f->ref != 1 || g->ref != 1) {\n\tres = cuddCacheLookup(dd, DD_ADD_TRIANGLE_TAG, f, g, cube);\n\tif (res != NULL) {\n\t    return(res);\n\t}\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    topf = cuddI(dd,f->index); topg = cuddI(dd,g->index);\n    top = ddMin(topf,topg);\n\n    if (top == topf) {fv = cuddT(f); fvn = cuddE(f);} else {fv = fvn = f;}\n    if (top == topg) {gv = cuddT(g); gvn = cuddE(g);} else {gv = gvn = g;}\n\n    t = addTriangleRecur(dd, fv, gv, vars, cube);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n    e = addTriangleRecur(dd, fvn, gvn, vars, cube);\n    if (e == NULL) {\n\tCudd_RecursiveDeref(dd, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n\n    index = dd->invperm[top];\n    if (vars[index] < 0) {\n\tres = (t == e) ? t : cuddUniqueInter(dd,index,t,e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, t);\n\t    Cudd_RecursiveDeref(dd, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    } else {\n\tres = cuddAddApplyRecur(dd,Cudd_addMinimum,t,e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd, t);\n\t    Cudd_RecursiveDeref(dd, e);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDeref(dd, t);\n\tCudd_RecursiveDeref(dd, e);\n\tcuddDeref(res);\n    }\n\n    if (f->ref != 1 || g->ref != 1) {\n\tcuddCacheInsert(dd, DD_ADD_TRIANGLE_TAG, f, g, cube, res);\n    }\n\n    return(res);\n\n} /* end of addTriangleRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_addOuterSum.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\ncuddAddOuterSumRecur(\n  DdManager *dd,\n  DdNode *M,\n  DdNode *r,\n  DdNode *c)\n{\n    DdNode *P, *R, *Mt, *Me, *rt, *re, *ct, *ce, *Rt, *Re;\n    int topM, topc, topr;\n    int v, index;\n\n    statLine(dd);\n    /* Check special cases. */\n    if (r == DD_PLUS_INFINITY(dd) || c == DD_PLUS_INFINITY(dd)) return(M); \n\n    if (cuddIsConstant(c) && cuddIsConstant(r)) {\n\tR = cuddUniqueConst(dd,Cudd_V(c)+Cudd_V(r));\n\tcuddRef(R);\n\tif (cuddIsConstant(M)) {\n\t    if (cuddV(R) <= cuddV(M)) {\n\t\tcuddDeref(R);\n\t        return(R);\n\t    } else {\n\t        Cudd_RecursiveDeref(dd,R);       \n\t\treturn(M);\n\t    }\n\t} else {\n\t    P = Cudd_addApply(dd,Cudd_addMinimum,R,M);\n\t    cuddRef(P);\n\t    Cudd_RecursiveDeref(dd,R);\n\t    cuddDeref(P);\n\t    return(P);\n\t}\n    }\n\n    /* Check the cache. */\n    R = cuddCacheLookup(dd,DD_ADD_OUT_SUM_TAG,M,r,c);\n    if (R != NULL) return(R);\n\n    checkWhetherToGiveUp(dd);\n\n    topM = cuddI(dd,M->index); topr = cuddI(dd,r->index);\n    topc = cuddI(dd,c->index);\n    v = ddMin(topM,ddMin(topr,topc));\n\n    /* Compute cofactors. */\n    if (topM == v) { Mt = cuddT(M); Me = cuddE(M); } else { Mt = Me = M; }\n    if (topr == v) { rt = cuddT(r); re = cuddE(r); } else { rt = re = r; }\n    if (topc == v) { ct = cuddT(c); ce = cuddE(c); } else { ct = ce = c; }\n\n    /* Recursively solve. */\n    Rt = cuddAddOuterSumRecur(dd,Mt,rt,ct);\n    if (Rt == NULL) return(NULL);\n    cuddRef(Rt);\n    Re = cuddAddOuterSumRecur(dd,Me,re,ce);\n    if (Re == NULL) {\n\tCudd_RecursiveDeref(dd, Rt);\n\treturn(NULL);\n    }\n    cuddRef(Re);\n    index = dd->invperm[v];\n    R = (Rt == Re) ? Rt : cuddUniqueInter(dd,index,Rt,Re);\n    if (R == NULL) {\n\tCudd_RecursiveDeref(dd, Rt);\n\tCudd_RecursiveDeref(dd, Re);\n\treturn(NULL);\n    }\n    cuddDeref(Rt);\n    cuddDeref(Re);\n\n    /* Store the result in the cache. */\n    cuddCacheInsert(dd,DD_ADD_OUT_SUM_TAG,M,r,c,R);\n\n    return(R);\n\n} /* end of cuddAddOuterSumRecur */\n"
  },
  {
    "path": "cudd/cudd/cuddPriority.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Priority functions.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\nstatic int cuddMinHammingDistRecur (DdNode * f, int *minterm, DdHashTable * table, int upperBound);\nstatic DdNode * separateCube (DdManager *dd, DdNode *f, CUDD_VALUE_TYPE *distance);\nstatic DdNode * createResult (DdManager *dd, unsigned int index, unsigned int phase, DdNode *cube, CUDD_VALUE_TYPE distance);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Selects pairs from R using a priority function.\n\n  @details Selects pairs from a relation R(x,y) (given as a %BDD)\n  in such a way that a given x appears in one pair only. Uses a\n  priority function to determine which y should be paired to a given x.\n  Three of the arguments--x, y, and z--are vectors of %BDD variables.\n  The first two are the variables on which R depends. The third vector\n  is a vector of auxiliary variables, used during the computation. This\n  vector is optional. If a NULL value is passed instead,\n  Cudd_PrioritySelect will create the working variables on the fly.\n  The sizes of x and y (and z if it is not NULL) should equal n.\n  The priority function Pi can be passed as a %BDD, or can be built by\n  Cudd_PrioritySelect. If NULL is passed instead of a DdNode *,\n  parameter Pifunc is used by Cudd_PrioritySelect to build a %BDD for the\n  priority function. (Pifunc is a pointer to a C function.) If Pi is not\n  NULL, then Pifunc is ignored. Pifunc should have the same interface as\n  the standard priority functions (e.g., Cudd_Dxygtdxz).\n  Cudd_PrioritySelect and Cudd_CProjection can sometimes be used\n  interchangeably. Specifically, calling Cudd_PrioritySelect with\n  Cudd_Xgty as Pifunc produces the same result as calling\n  Cudd_CProjection with the all-zero minterm as reference minterm.\n  However, depending on the application, one or the other may be\n  preferable:\n  <ul>\n  <li> When extracting representatives from an equivalence relation,\n  Cudd_CProjection has the advantage of nor requiring the auxiliary\n  variables.\n  <li> When computing matchings in general bipartite graphs,\n  Cudd_PrioritySelect normally obtains better results because it can use\n  more powerful matching schemes (e.g., Cudd_Dxygtdxz).\n  </ul>\n\n  @return a pointer to the selected function if successful; NULL\n  otherwise.\n\n  @sideeffect If called with z == NULL, will create new variables in\n  the manager.\n\n  @see Cudd_Dxygtdxz Cudd_Dxygtdyz Cudd_Xgty\n  Cudd_bddAdjPermuteX Cudd_CProjection\n\n*/\nDdNode *\nCudd_PrioritySelect(\n  DdManager * dd /**< manager */,\n  DdNode * R /**< %BDD of the relation */,\n  DdNode ** x /**< array of x variables */,\n  DdNode ** y /**< array of y variables */,\n  DdNode ** z /**< array of z variables (optional: may be NULL) */,\n  DdNode * Pi /**< %BDD of the priority function (optional: may be NULL) */,\n  int  n /**< size of x, y, and z */,\n  DD_PRFP Pifunc /**< function used to build Pi if it is NULL */)\n{\n    DdNode *res = NULL;\n    DdNode *zcube = NULL;\n    DdNode *Rxz, *Q;\n    int createdZ = 0;\n    int createdPi = 0;\n    int i;\n\n    /* Create z variables if needed. */\n    if (z == NULL) {\n\tif (Pi != NULL) return(NULL);\n\tz = ALLOC(DdNode *,n);\n\tif (z == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(NULL);\n\t}\n\tcreatedZ = 1;\n\tfor (i = 0; i < n; i++) {\n\t    if (dd->size >= (int) CUDD_MAXINDEX - 1) goto endgame;\n\t    z[i] = cuddUniqueInter(dd,dd->size,dd->one,Cudd_Not(dd->one));\n\t    if (z[i] == NULL) goto endgame;\n\t}\n    }\n\n    /* Create priority function BDD if needed. */\n    if (Pi == NULL) {\n\tPi = Pifunc(dd,n,x,y,z);\n\tif (Pi == NULL) goto endgame;\n\tcreatedPi = 1;\n\tcuddRef(Pi);\n    }\n\n    /* Initialize abstraction cube. */\n    zcube = DD_ONE(dd);\n    cuddRef(zcube);\n    for (i = n - 1; i >= 0; i--) {\n\tDdNode *tmpp;\n\ttmpp = Cudd_bddAnd(dd,z[i],zcube);\n\tif (tmpp == NULL) goto endgame;\n\tcuddRef(tmpp);\n\tCudd_RecursiveDeref(dd,zcube);\n\tzcube = tmpp;\n    }\n\n    /* Compute subset of (x,y) pairs. */\n    Rxz = Cudd_bddSwapVariables(dd,R,y,z,n);\n    if (Rxz == NULL) goto endgame;\n    cuddRef(Rxz);\n    Q = Cudd_bddAndAbstract(dd,Rxz,Pi,zcube);\n    if (Q == NULL) {\n\tCudd_RecursiveDeref(dd,Rxz);\n\tgoto endgame;\n    }\n    cuddRef(Q);\n    Cudd_RecursiveDeref(dd,Rxz);\n    res = Cudd_bddAnd(dd,R,Cudd_Not(Q));\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd,Q);\n\tgoto endgame;\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd,Q);\n\nendgame:\n    if (zcube != NULL) Cudd_RecursiveDeref(dd,zcube);\n    if (createdZ) {\n\tFREE(z);\n    }\n    if (createdPi) {\n\tCudd_RecursiveDeref(dd,Pi);\n    }\n    if (res != NULL) cuddDeref(res);\n    return(res);\n\n} /* Cudd_PrioritySelect */\n\n\n/**\n  @brief Generates a %BDD for the function x &gt; y.\n\n  @details This function generates a %BDD for the function x &gt; y.\n  Both x and y are N-bit numbers, x\\[0\\] x\\[1\\] ... x\\[N-1\\] and\n  y\\[0\\] y\\[1\\] ...  y\\[N-1\\], with 0 the most significant bit.\n  The %BDD is built bottom-up.\n  It has 3*N-1 internal nodes, if the variables are ordered as follows:\n  x\\[0\\] y\\[0\\] x\\[1\\] y\\[1\\] ... x\\[N-1\\] y\\[N-1\\].\n  Argument z is not used by Cudd_Xgty: it is included to make it\n  call-compatible to Cudd_Dxygtdxz and Cudd_Dxygtdyz.\n\n  @sideeffect None\n\n  @see Cudd_PrioritySelect Cudd_Dxygtdxz Cudd_Dxygtdyz\n\n*/\nDdNode *\nCudd_Xgty(\n  DdManager * dd /**< %DD manager */,\n  int  N /**< number of x and y variables */,\n  DdNode ** z /**< array of z variables: unused */,\n  DdNode ** x /**< array of x variables */,\n  DdNode ** y /**< array of y variables */)\n{\n    DdNode *u, *v, *w;\n    int     i;\n\n    (void) z; /* avoid warning */\n    /* Build bottom part of BDD outside loop. */\n    u = Cudd_bddAnd(dd, x[N-1], Cudd_Not(y[N-1]));\n    if (u == NULL) return(NULL);\n    cuddRef(u);\n\n    /* Loop to build the rest of the BDD. */\n    for (i = N-2; i >= 0; i--) {\n\tv = Cudd_bddAnd(dd, y[i], Cudd_Not(u));\n\tif (v == NULL) {\n\t    Cudd_RecursiveDeref(dd, u);\n\t    return(NULL);\n\t}\n\tcuddRef(v);\n\tw = Cudd_bddAnd(dd, Cudd_Not(y[i]), u);\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd, u);\n\t    Cudd_RecursiveDeref(dd, v);\n\t    return(NULL);\n\t}\n\tcuddRef(w);\n\tCudd_RecursiveDeref(dd, u);\n\tu = Cudd_bddIte(dd, x[i], Cudd_Not(v), w);\n\tif (u == NULL) {\n\t    Cudd_RecursiveDeref(dd, v);\n\t    Cudd_RecursiveDeref(dd, w);\n\t    return(NULL);\n\t}\n\tcuddRef(u);\n\tCudd_RecursiveDeref(dd, v);\n\tCudd_RecursiveDeref(dd, w);\n\n    }\n    cuddDeref(u);\n    return(u);\n\n} /* end of Cudd_Xgty */\n\n\n/**\n  @brief Generates a %BDD for the function x==y.\n\n  @details This function generates a %BDD for the function x==y.\n  Both x and y are N-bit numbers, x\\[0\\] x\\[1\\] ... x\\[N-1\\] and\n  y\\[0\\] y\\[1\\] ...  y\\[N-1\\].  The %BDD is built bottom-up.\n  It has 3*N-1 internal nodes, if the variables are ordered as follows:\n  x\\[0\\] y\\[0\\] x\\[1\\] y\\[1\\] ... x\\[N-1\\] y\\[N-1\\].\n\n  @sideeffect None\n\n  @see Cudd_addXeqy\n\n*/\nDdNode *\nCudd_Xeqy(\n  DdManager * dd /**< %DD manager */,\n  int  N /**< number of x and y variables */,\n  DdNode ** x /**< array of x variables */,\n  DdNode ** y /**< array of y variables */)\n{\n    DdNode *u, *v, *w;\n    int     i;\n\n    /* Build bottom part of BDD outside loop. */\n    u = Cudd_bddIte(dd, x[N-1], y[N-1], Cudd_Not(y[N-1]));\n    if (u == NULL) return(NULL);\n    cuddRef(u);\n\n    /* Loop to build the rest of the BDD. */\n    for (i = N-2; i >= 0; i--) {\n\tv = Cudd_bddAnd(dd, y[i], u);\n\tif (v == NULL) {\n\t    Cudd_RecursiveDeref(dd, u);\n\t    return(NULL);\n\t}\n\tcuddRef(v);\n\tw = Cudd_bddAnd(dd, Cudd_Not(y[i]), u);\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd, u);\n\t    Cudd_RecursiveDeref(dd, v);\n\t    return(NULL);\n\t}\n\tcuddRef(w);\n\tCudd_RecursiveDeref(dd, u);\n\tu = Cudd_bddIte(dd, x[i], v, w);\n\tif (u == NULL) {\n\t    Cudd_RecursiveDeref(dd, v);\n\t    Cudd_RecursiveDeref(dd, w);\n\t    return(NULL);\n\t}\n\tcuddRef(u);\n\tCudd_RecursiveDeref(dd, v);\n\tCudd_RecursiveDeref(dd, w);\n    }\n    cuddDeref(u);\n    return(u);\n\n} /* end of Cudd_Xeqy */\n\n\n/**\n  @brief Generates an %ADD for the function x==y.\n\n  @details This function generates an %ADD for the function x==y.\n  Both x and y are N-bit numbers, x\\[0\\] x\\[1\\] ... x\\[N-1\\] and\n  y\\[0\\] y\\[1\\] ...  y\\[N-1\\].  The %ADD is built bottom-up.\n  It has 3*N-1 internal nodes, if the variables are ordered as follows:\n  x\\[0\\] y\\[0\\] x\\[1\\] y\\[1\\] ... x\\[N-1\\] y\\[N-1\\].\n\n  @sideeffect None\n\n  @see Cudd_Xeqy\n\n*/\nDdNode *\nCudd_addXeqy(\n  DdManager * dd /**< %DD manager */,\n  int  N /**< number of x and y variables */,\n  DdNode ** x /**< array of x variables */,\n  DdNode ** y /**< array of y variables */)\n{\n    DdNode *one, *zero;\n    DdNode *u, *v, *w;\n    int     i;\n\n    one = DD_ONE(dd);\n    zero = DD_ZERO(dd);\n\n    /* Build bottom part of ADD outside loop. */\n    v = Cudd_addIte(dd, y[N-1], one, zero);\n    if (v == NULL) return(NULL);\n    cuddRef(v);\n    w = Cudd_addIte(dd, y[N-1], zero, one);\n    if (w == NULL) {\n\tCudd_RecursiveDeref(dd, v);\n\treturn(NULL);\n    }\n    cuddRef(w);\n    u = Cudd_addIte(dd, x[N-1], v, w);\n    if (u == NULL) {\n\tCudd_RecursiveDeref(dd, v);\n\tCudd_RecursiveDeref(dd, w);\n\treturn(NULL);\n    }\n    cuddRef(u);\n    Cudd_RecursiveDeref(dd, v);\n    Cudd_RecursiveDeref(dd, w);\n\n    /* Loop to build the rest of the ADD. */\n    for (i = N-2; i >= 0; i--) {\n\tv = Cudd_addIte(dd, y[i], u, zero);\n\tif (v == NULL) {\n\t    Cudd_RecursiveDeref(dd, u);\n\t    return(NULL);\n\t}\n\tcuddRef(v);\n\tw = Cudd_addIte(dd, y[i], zero, u);\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd, u);\n\t    Cudd_RecursiveDeref(dd, v);\n\t    return(NULL);\n\t}\n\tcuddRef(w);\n\tCudd_RecursiveDeref(dd, u);\n\tu = Cudd_addIte(dd, x[i], v, w);\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd, v);\n\t    Cudd_RecursiveDeref(dd, w);\n\t    return(NULL);\n\t}\n\tcuddRef(u);\n\tCudd_RecursiveDeref(dd, v);\n\tCudd_RecursiveDeref(dd, w);\n    }\n    cuddDeref(u);\n    return(u);\n\n} /* end of Cudd_addXeqy */\n\n\n/**\n  @brief Generates a %BDD for the function d(x,y) &gt; d(x,z).\n\n  @details This function generates a %BDD for the function d(x,y)\n  &gt; d(x,z);\n  x, y, and z are N-bit numbers, x\\[0\\] x\\[1\\] ... x\\[N-1\\],\n  y\\[0\\] y\\[1\\] ...  y\\[N-1\\], and z\\[0\\] z\\[1\\] ...  z\\[N-1\\],\n  with 0 the most significant bit.\n  The distance d(x,y) is defined as:\n\t\\f$\\sum_{i=0}^{N-1}(|x_i - y_i| \\cdot 2^{N-i-1})\\f$.\n  The %BDD is built bottom-up.\n  It has 7*N-3 internal nodes, if the variables are ordered as follows:\n  x\\[0\\] y\\[0\\] z\\[0\\] x\\[1\\] y\\[1\\] z\\[1\\] ... x\\[N-1\\] y\\[N-1\\] z\\[N-1\\].\n\n  @sideeffect None\n\n  @see Cudd_PrioritySelect Cudd_Dxygtdyz Cudd_Xgty Cudd_bddAdjPermuteX\n\n*/\nDdNode *\nCudd_Dxygtdxz(\n  DdManager * dd /**< %DD manager */,\n  int  N /**< number of x, y, and z variables */,\n  DdNode ** x /**< array of x variables */,\n  DdNode ** y /**< array of y variables */,\n  DdNode ** z /**< array of z variables */)\n{\n    DdNode *one, *zero;\n    DdNode *z1, *z2, *z3, *z4, *y1_, *y2, *x1;\n    int     i;\n\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    /* Build bottom part of BDD outside loop. */\n    y1_ = Cudd_bddIte(dd, y[N-1], one, Cudd_Not(z[N-1]));\n    if (y1_ == NULL) return(NULL);\n    cuddRef(y1_);\n    y2 = Cudd_bddIte(dd, y[N-1], z[N-1], one);\n    if (y2 == NULL) {\n\tCudd_RecursiveDeref(dd, y1_);\n\treturn(NULL);\n    }\n    cuddRef(y2);\n    x1 = Cudd_bddIte(dd, x[N-1], y1_, y2);\n    if (x1 == NULL) {\n\tCudd_RecursiveDeref(dd, y1_);\n\tCudd_RecursiveDeref(dd, y2);\n\treturn(NULL);\n    }\n    cuddRef(x1);\n    Cudd_RecursiveDeref(dd, y1_);\n    Cudd_RecursiveDeref(dd, y2);\n\n    /* Loop to build the rest of the BDD. */\n    for (i = N-2; i >= 0; i--) {\n\tz1 = Cudd_bddIte(dd, z[i], one, Cudd_Not(x1));\n\tif (z1 == NULL) {\n\t    Cudd_RecursiveDeref(dd, x1);\n\t    return(NULL);\n\t}\n\tcuddRef(z1);\n\tz2 = Cudd_bddIte(dd, z[i], x1, one);\n\tif (z2 == NULL) {\n\t    Cudd_RecursiveDeref(dd, x1);\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    return(NULL);\n\t}\n\tcuddRef(z2);\n\tz3 = Cudd_bddIte(dd, z[i], one, x1);\n\tif (z3 == NULL) {\n\t    Cudd_RecursiveDeref(dd, x1);\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    Cudd_RecursiveDeref(dd, z2);\n\t    return(NULL);\n\t}\n\tcuddRef(z3);\n\tz4 = Cudd_bddIte(dd, z[i], x1, zero);\n\tif (z4 == NULL) {\n\t    Cudd_RecursiveDeref(dd, x1);\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    Cudd_RecursiveDeref(dd, z2);\n\t    Cudd_RecursiveDeref(dd, z3);\n\t    return(NULL);\n\t}\n\tcuddRef(z4);\n\tCudd_RecursiveDeref(dd, x1);\n\ty1_ = Cudd_bddIte(dd, y[i], z2, Cudd_Not(z1));\n\tif (y1_ == NULL) {\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    Cudd_RecursiveDeref(dd, z2);\n\t    Cudd_RecursiveDeref(dd, z3);\n\t    Cudd_RecursiveDeref(dd, z4);\n\t    return(NULL);\n\t}\n\tcuddRef(y1_);\n\ty2 = Cudd_bddIte(dd, y[i], z4, z3);\n\tif (y2 == NULL) {\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    Cudd_RecursiveDeref(dd, z2);\n\t    Cudd_RecursiveDeref(dd, z3);\n\t    Cudd_RecursiveDeref(dd, z4);\n\t    Cudd_RecursiveDeref(dd, y1_);\n\t    return(NULL);\n\t}\n\tcuddRef(y2);\n\tCudd_RecursiveDeref(dd, z1);\n\tCudd_RecursiveDeref(dd, z2);\n\tCudd_RecursiveDeref(dd, z3);\n\tCudd_RecursiveDeref(dd, z4);\n\tx1 = Cudd_bddIte(dd, x[i], y1_, y2);\n\tif (x1 == NULL) {\n\t    Cudd_RecursiveDeref(dd, y1_);\n\t    Cudd_RecursiveDeref(dd, y2);\n\t    return(NULL);\n\t}\n\tcuddRef(x1);\n\tCudd_RecursiveDeref(dd, y1_);\n\tCudd_RecursiveDeref(dd, y2);\n    }\n    cuddDeref(x1);\n    return(Cudd_Not(x1));\n\n} /* end of Cudd_Dxygtdxz */\n\n\n/**\n  @brief Generates a %BDD for the function d(x,y) &gt; d(y,z).\n\n  @details This function generates a %BDD for the function d(x,y)\n  &gt; d(y,z);\n  x, y, and z are N-bit numbers, x\\[0\\] x\\[1\\] ... x\\[N-1\\],\n  y\\[0\\] y\\[1\\] ...  y\\[N-1\\], and z\\[0\\] z\\[1\\] ...  z\\[N-1\\],\n  with 0 the most significant bit.\n  The distance d(x,y) is defined as:\n\t\\f$\\sum_{i=0}^{N-1}(|x_i - y_i| \\cdot 2^{N-i-1})\\f$.\n  The %BDD is built bottom-up.\n  It has 7*N-3 internal nodes, if the variables are ordered as follows:\n  x\\[0\\] y\\[0\\] z\\[0\\] x\\[1\\] y\\[1\\] z\\[1\\] ... x\\[N-1\\] y\\[N-1\\] z\\[N-1\\].\n\n  @sideeffect None\n\n  @see Cudd_PrioritySelect Cudd_Dxygtdxz Cudd_Xgty Cudd_bddAdjPermuteX\n\n*/\nDdNode *\nCudd_Dxygtdyz(\n  DdManager * dd /**< %DD manager */,\n  int  N /**< number of x, y, and z variables */,\n  DdNode ** x /**< array of x variables */,\n  DdNode ** y /**< array of y variables */,\n  DdNode ** z /**< array of z variables */)\n{\n    DdNode *one, *zero;\n    DdNode *z1, *z2, *z3, *z4, *y1_, *y2, *x1;\n    int     i;\n\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    /* Build bottom part of BDD outside loop. */\n    y1_ = Cudd_bddIte(dd, y[N-1], one, z[N-1]);\n    if (y1_ == NULL) return(NULL);\n    cuddRef(y1_);\n    y2 = Cudd_bddIte(dd, y[N-1], z[N-1], zero);\n    if (y2 == NULL) {\n\tCudd_RecursiveDeref(dd, y1_);\n\treturn(NULL);\n    }\n    cuddRef(y2);\n    x1 = Cudd_bddIte(dd, x[N-1], y1_, Cudd_Not(y2));\n    if (x1 == NULL) {\n\tCudd_RecursiveDeref(dd, y1_);\n\tCudd_RecursiveDeref(dd, y2);\n\treturn(NULL);\n    }\n    cuddRef(x1);\n    Cudd_RecursiveDeref(dd, y1_);\n    Cudd_RecursiveDeref(dd, y2);\n\n    /* Loop to build the rest of the BDD. */\n    for (i = N-2; i >= 0; i--) {\n\tz1 = Cudd_bddIte(dd, z[i], x1, zero);\n\tif (z1 == NULL) {\n\t    Cudd_RecursiveDeref(dd, x1);\n\t    return(NULL);\n\t}\n\tcuddRef(z1);\n\tz2 = Cudd_bddIte(dd, z[i], x1, one);\n\tif (z2 == NULL) {\n\t    Cudd_RecursiveDeref(dd, x1);\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    return(NULL);\n\t}\n\tcuddRef(z2);\n\tz3 = Cudd_bddIte(dd, z[i], one, x1);\n\tif (z3 == NULL) {\n\t    Cudd_RecursiveDeref(dd, x1);\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    Cudd_RecursiveDeref(dd, z2);\n\t    return(NULL);\n\t}\n\tcuddRef(z3);\n\tz4 = Cudd_bddIte(dd, z[i], one, Cudd_Not(x1));\n\tif (z4 == NULL) {\n\t    Cudd_RecursiveDeref(dd, x1);\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    Cudd_RecursiveDeref(dd, z2);\n\t    Cudd_RecursiveDeref(dd, z3);\n\t    return(NULL);\n\t}\n\tcuddRef(z4);\n\tCudd_RecursiveDeref(dd, x1);\n\ty1_ = Cudd_bddIte(dd, y[i], z2, z1);\n\tif (y1_ == NULL) {\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    Cudd_RecursiveDeref(dd, z2);\n\t    Cudd_RecursiveDeref(dd, z3);\n\t    Cudd_RecursiveDeref(dd, z4);\n\t    return(NULL);\n\t}\n\tcuddRef(y1_);\n\ty2 = Cudd_bddIte(dd, y[i], z4, Cudd_Not(z3));\n\tif (y2 == NULL) {\n\t    Cudd_RecursiveDeref(dd, z1);\n\t    Cudd_RecursiveDeref(dd, z2);\n\t    Cudd_RecursiveDeref(dd, z3);\n\t    Cudd_RecursiveDeref(dd, z4);\n\t    Cudd_RecursiveDeref(dd, y1_);\n\t    return(NULL);\n\t}\n\tcuddRef(y2);\n\tCudd_RecursiveDeref(dd, z1);\n\tCudd_RecursiveDeref(dd, z2);\n\tCudd_RecursiveDeref(dd, z3);\n\tCudd_RecursiveDeref(dd, z4);\n\tx1 = Cudd_bddIte(dd, x[i], y1_, Cudd_Not(y2));\n\tif (x1 == NULL) {\n\t    Cudd_RecursiveDeref(dd, y1_);\n\t    Cudd_RecursiveDeref(dd, y2);\n\t    return(NULL);\n\t}\n\tcuddRef(x1);\n\tCudd_RecursiveDeref(dd, y1_);\n\tCudd_RecursiveDeref(dd, y2);\n    }\n    cuddDeref(x1);\n    return(Cudd_Not(x1));\n\n} /* end of Cudd_Dxygtdyz */\n\n\n/**\n  @brief Generates a %BDD for the function x - y &ge; c.\n\n  @details This function generates a %BDD for the function x -y &ge; c.\n  Both x and y are N-bit numbers, x\\[0\\] x\\[1\\] ... x\\[N-1\\] and\n  y\\[0\\] y\\[1\\] ...  y\\[N-1\\], with 0 the most significant bit.\n  The %BDD is built bottom-up.\n  It has a linear number of nodes if the variables are ordered as follows:\n  x\\[0\\] y\\[0\\] x\\[1\\] y\\[1\\] ... x\\[N-1\\] y\\[N-1\\].\n\n  @sideeffect None\n\n  @see Cudd_Xgty\n\n*/\nDdNode *\nCudd_Inequality(\n  DdManager * dd /**< %DD manager */,\n  int  N /**< number of x and y variables */,\n  int c /**< right-hand side constant */,\n  DdNode ** x /**< array of x variables */,\n  DdNode ** y /**< array of y variables */)\n{\n    /* The nodes at level i represent values of the difference that are\n    ** multiples of 2^i.  We use variables with names starting with k\n    ** to denote the multipliers of 2^i in such multiples. */\n    int kTrue = c;\n    int kFalse = c - 1;\n    /* Mask used to compute the ceiling function.  Since we divide by 2^i,\n    ** we want to know whether the dividend is a multiple of 2^i.  If it is,\n    ** then ceiling and floor coincide; otherwise, they differ by one. */\n    int mask = 1;\n    int i;\n\n    DdNode *f = NULL;\t\t/* the eventual result */\n    DdNode *one = DD_ONE(dd);\n    DdNode *zero = Cudd_Not(one);\n\n    /* Two x-labeled nodes are created at most at each iteration.  They are\n    ** stored, along with their k values, in these variables.  At each level,\n    ** the old nodes are freed and the new nodes are copied into the old map.\n    */\n    DdNode *map[2] = {NULL, NULL};\n    int invalidIndex = 1 << (N-1);\n    int index[2] = {invalidIndex, invalidIndex};\n\n    /* This should never happen. */\n    if (N < 0) return(NULL);\n\n    /* If there are no bits, both operands are 0.  The result depends on c. */\n    if (N == 0) {\n\tif (c >= 0) return(one);\n\telse return(zero);\n    }\n\n    /* The maximum or the minimum difference comparing to c can generate the terminal case */\n    if ((1 << N) - 1 < c) return(zero);\n    else if ((-(1 << N) + 1) >= c) return(one);\n\n    /* Build the result bottom up. */\n    for (i = 1; i <= N; i++) {\n\tint kTrueLower, kFalseLower;\n\tint leftChild, middleChild, rightChild;\n\tDdNode *g0, *g1, *fplus, *fequal, *fminus;\n\tint j;\n\tDdNode *newMap[2] = {NULL, NULL};\n\tint newIndex[2];\n\n\tkTrueLower = kTrue;\n\tkFalseLower = kFalse;\n\t/* kTrue = ceiling((c-1)/2^i) + 1 */\n\tkTrue = ((c-1) >> i) + ((c & mask) != 1) + 1;\n\tmask = (mask << 1) | 1;\n\t/* kFalse = floor(c/2^i) - 1 */\n\tkFalse = (c >> i) - 1;\n\tnewIndex[0] = invalidIndex;\n\tnewIndex[1] = invalidIndex;\n\n\tfor (j = kFalse + 1; j < kTrue; j++) {\n\t    /* Skip if node is not reachable from top of BDD. */\n\t    if ((j >= (1 << (N - i))) || (j <= -(1 << (N -i)))) continue;\n\n\t    /* Find f- */\n\t    leftChild = (j << 1) - 1;\n\t    if (leftChild >= kTrueLower) {\n\t\tfminus = one;\n\t    } else if (leftChild <= kFalseLower) {\n\t\tfminus = zero;\n\t    } else {\n\t\tassert(leftChild == index[0] || leftChild == index[1]);\n\t\tif (leftChild == index[0]) {\n\t\t    fminus = map[0];\n\t\t} else {\n\t\t    fminus = map[1];\n\t\t}\n\t    }\n\n\t    /* Find f= */\n\t    middleChild = j << 1;\n\t    if (middleChild >= kTrueLower) {\n\t\tfequal = one;\n\t    } else if (middleChild <= kFalseLower) {\n\t\tfequal = zero;\n\t    } else {\n\t\tassert(middleChild == index[0] || middleChild == index[1]);\n\t\tif (middleChild == index[0]) {\n\t\t    fequal = map[0];\n\t\t} else {\n\t\t    fequal = map[1];\n\t\t}\n\t    }\n\n\t    /* Find f+ */\n\t    rightChild = (j << 1) + 1;\n\t    if (rightChild >= kTrueLower) {\n\t\tfplus = one;\n\t    } else if (rightChild <= kFalseLower) {\n\t\tfplus = zero;\n\t    } else {\n\t\tassert(rightChild == index[0] || rightChild == index[1]);\n\t\tif (rightChild == index[0]) {\n\t\t    fplus = map[0];\n\t\t} else {\n\t\t    fplus = map[1];\n\t\t}\n\t    }\n\n\t    /* Build new nodes. */\n\t    g1 = Cudd_bddIte(dd, y[N - i], fequal, fplus);\n\t    if (g1 == NULL) {\n\t\tif (index[0] != invalidIndex) Cudd_IterDerefBdd(dd, map[0]);\n\t\tif (index[1] != invalidIndex) Cudd_IterDerefBdd(dd, map[1]);\n\t\tif (newIndex[0] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[0]);\n\t\tif (newIndex[1] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[1]);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(g1);\n\t    g0 = Cudd_bddIte(dd, y[N - i], fminus, fequal);\n\t    if (g0 == NULL) {\n\t\tCudd_IterDerefBdd(dd, g1);\n\t\tif (index[0] != invalidIndex) Cudd_IterDerefBdd(dd, map[0]);\n\t\tif (index[1] != invalidIndex) Cudd_IterDerefBdd(dd, map[1]);\n\t\tif (newIndex[0] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[0]);\n\t\tif (newIndex[1] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[1]);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(g0);\n\t    f = Cudd_bddIte(dd, x[N - i], g1, g0);\n\t    if (f == NULL) {\n\t\tCudd_IterDerefBdd(dd, g1);\n\t\tCudd_IterDerefBdd(dd, g0);\n\t\tif (index[0] != invalidIndex) Cudd_IterDerefBdd(dd, map[0]);\n\t\tif (index[1] != invalidIndex) Cudd_IterDerefBdd(dd, map[1]);\n\t\tif (newIndex[0] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[0]);\n\t\tif (newIndex[1] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[1]);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(f);\n\t    Cudd_IterDerefBdd(dd, g1);\n\t    Cudd_IterDerefBdd(dd, g0);\n\n\t    /* Save newly computed node in map. */\n\t    assert(newIndex[0] == invalidIndex || newIndex[1] == invalidIndex);\n\t    if (newIndex[0] == invalidIndex) {\n\t\tnewIndex[0] = j;\n\t\tnewMap[0] = f;\n\t    } else {\n\t\tnewIndex[1] = j;\n\t\tnewMap[1] = f;\n\t    }\n\t}\n\n\t/* Copy new map to map. */\n\tif (index[0] != invalidIndex) Cudd_IterDerefBdd(dd, map[0]);\n\tif (index[1] != invalidIndex) Cudd_IterDerefBdd(dd, map[1]);\n\tmap[0] = newMap[0];\n\tmap[1] = newMap[1];\n\tindex[0] = newIndex[0];\n\tindex[1] = newIndex[1];\n    }\n\n    cuddDeref(f);\n    return(f);\n\n} /* end of Cudd_Inequality */\n\n\n/**\n  @brief Generates a %BDD for the function x - y != c.\n\n  @details This function generates a %BDD for the function x -y != c.\n  Both x and y are N-bit numbers, x\\[0\\] x\\[1\\] ... x\\[N-1\\] and\n  y\\[0\\] y\\[1\\] ...  y\\[N-1\\], with 0 the most significant bit.\n  The %BDD is built bottom-up.\n  It has a linear number of nodes if the variables are ordered as follows:\n  x\\[0\\] y\\[0\\] x\\[1\\] y\\[1\\] ... x\\[N-1\\] y\\[N-1\\].\n\n  @sideeffect None\n\n  @see Cudd_Xgty\n\n*/\nDdNode *\nCudd_Disequality(\n  DdManager * dd /**< %DD manager */,\n  int  N /**< number of x and y variables */,\n  int c /**< right-hand side constant */,\n  DdNode ** x /**< array of x variables */,\n  DdNode ** y /**< array of y variables */)\n{\n    /* The nodes at level i represent values of the difference that are\n    ** multiples of 2^i.  We use variables with names starting with k\n    ** to denote the multipliers of 2^i in such multiples. */\n    int kTrueLb = c + 1;\n    int kTrueUb = c - 1;\n    int kFalse = c;\n    /* Mask used to compute the ceiling function.  Since we divide by 2^i,\n    ** we want to know whether the dividend is a multiple of 2^i.  If it is,\n    ** then ceiling and floor coincide; otherwise, they differ by one. */\n    int mask = 1;\n    int i;\n\n    DdNode *f = NULL;\t\t/* the eventual result */\n    DdNode *one = DD_ONE(dd);\n    DdNode *zero = Cudd_Not(one);\n\n    /* Two x-labeled nodes are created at most at each iteration.  They are\n    ** stored, along with their k values, in these variables.  At each level,\n    ** the old nodes are freed and the new nodes are copied into the old map.\n    */\n    DdNode *map[2] = {NULL, NULL};\n    int invalidIndex = 1 << (N-1);\n    int index[2] = {invalidIndex, invalidIndex};\n\n    /* This should never happen. */\n    if (N < 0) return(NULL);\n\n    /* If there are no bits, both operands are 0.  The result depends on c. */\n    if (N == 0) {\n\tif (c != 0) return(one);\n\telse return(zero);\n    }\n\n    /* The maximum or the minimum difference comparing to c can generate the terminal case */\n    if ((1 << N) - 1 < c || (-(1 << N) + 1) > c) return(one);\n\n    /* Build the result bottom up. */\n    for (i = 1; i <= N; i++) {\n\tint kTrueLbLower, kTrueUbLower;\n\tint leftChild, middleChild, rightChild;\n\tDdNode *g0, *g1, *fplus, *fequal, *fminus;\n\tint j;\n\tDdNode *newMap[2] = {NULL, NULL};\n\tint newIndex[2];\n\n\tkTrueLbLower = kTrueLb;\n\tkTrueUbLower = kTrueUb;\n\t/* kTrueLb = floor((c-1)/2^i) + 2 */\n\tkTrueLb = ((c-1) >> i) + 2;\n\t/* kTrueUb = ceiling((c+1)/2^i) - 2 */\n\tkTrueUb = ((c+1) >> i) + (((c+2) & mask) != 1) - 2;\n\tmask = (mask << 1) | 1;\n\tnewIndex[0] = invalidIndex;\n\tnewIndex[1] = invalidIndex;\n\n\tfor (j = kTrueUb + 1; j < kTrueLb; j++) {\n\t    /* Skip if node is not reachable from top of BDD. */\n\t    if ((j >= (1 << (N - i))) || (j <= -(1 << (N -i)))) continue;\n\n\t    /* Find f- */\n\t    leftChild = (j << 1) - 1;\n\t    if (leftChild >= kTrueLbLower || leftChild <= kTrueUbLower) {\n\t\tfminus = one;\n\t    } else if (i == 1 && leftChild == kFalse) {\n\t\tfminus = zero;\n\t    } else {\n\t\tassert(leftChild == index[0] || leftChild == index[1]);\n\t\tif (leftChild == index[0]) {\n\t\t    fminus = map[0];\n\t\t} else {\n\t\t    fminus = map[1];\n\t\t}\n\t    }\n\n\t    /* Find f= */\n\t    middleChild = j << 1;\n\t    if (middleChild >= kTrueLbLower || middleChild <= kTrueUbLower) {\n\t\tfequal = one;\n\t    } else if (i == 1 && middleChild == kFalse) {\n\t\tfequal = zero;\n\t    } else {\n\t\tassert(middleChild == index[0] || middleChild == index[1]);\n\t\tif (middleChild == index[0]) {\n\t\t    fequal = map[0];\n\t\t} else {\n\t\t    fequal = map[1];\n\t\t}\n\t    }\n\n\t    /* Find f+ */\n\t    rightChild = (j << 1) + 1;\n\t    if (rightChild >= kTrueLbLower || rightChild <= kTrueUbLower) {\n\t\tfplus = one;\n\t    } else if (i == 1 && rightChild == kFalse) {\n\t\tfplus = zero;\n\t    } else {\n\t\tassert(rightChild == index[0] || rightChild == index[1]);\n\t\tif (rightChild == index[0]) {\n\t\t    fplus = map[0];\n\t\t} else {\n\t\t    fplus = map[1];\n\t\t}\n\t    }\n\n\t    /* Build new nodes. */\n\t    g1 = Cudd_bddIte(dd, y[N - i], fequal, fplus);\n\t    if (g1 == NULL) {\n\t\tif (index[0] != invalidIndex) Cudd_IterDerefBdd(dd, map[0]);\n\t\tif (index[1] != invalidIndex) Cudd_IterDerefBdd(dd, map[1]);\n\t\tif (newIndex[0] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[0]);\n\t\tif (newIndex[1] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[1]);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(g1);\n\t    g0 = Cudd_bddIte(dd, y[N - i], fminus, fequal);\n\t    if (g0 == NULL) {\n\t\tCudd_IterDerefBdd(dd, g1);\n\t\tif (index[0] != invalidIndex) Cudd_IterDerefBdd(dd, map[0]);\n\t\tif (index[1] != invalidIndex) Cudd_IterDerefBdd(dd, map[1]);\n\t\tif (newIndex[0] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[0]);\n\t\tif (newIndex[1] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[1]);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(g0);\n\t    f = Cudd_bddIte(dd, x[N - i], g1, g0);\n\t    if (f == NULL) {\n\t\tCudd_IterDerefBdd(dd, g1);\n\t\tCudd_IterDerefBdd(dd, g0);\n\t\tif (index[0] != invalidIndex) Cudd_IterDerefBdd(dd, map[0]);\n\t\tif (index[1] != invalidIndex) Cudd_IterDerefBdd(dd, map[1]);\n\t\tif (newIndex[0] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[0]);\n\t\tif (newIndex[1] != invalidIndex) Cudd_IterDerefBdd(dd, newMap[1]);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(f);\n\t    Cudd_IterDerefBdd(dd, g1);\n\t    Cudd_IterDerefBdd(dd, g0);\n\n\t    /* Save newly computed node in map. */\n\t    assert(newIndex[0] == invalidIndex || newIndex[1] == invalidIndex);\n\t    if (newIndex[0] == invalidIndex) {\n\t\tnewIndex[0] = j;\n\t\tnewMap[0] = f;\n\t    } else {\n\t\tnewIndex[1] = j;\n\t\tnewMap[1] = f;\n\t    }\n\t}\n\n\t/* Copy new map to map. */\n\tif (index[0] != invalidIndex) Cudd_IterDerefBdd(dd, map[0]);\n\tif (index[1] != invalidIndex) Cudd_IterDerefBdd(dd, map[1]);\n\tmap[0] = newMap[0];\n\tmap[1] = newMap[1];\n\tindex[0] = newIndex[0];\n\tindex[1] = newIndex[1];\n    }\n\n    cuddDeref(f);\n    return(f);\n\n} /* end of Cudd_Disequality */\n\n\n/**\n  @brief Generates a %BDD for the function lowerB &le; x &le; upperB.\n\n  @details This function generates a %BDD for the function\n  lowerB &le; x &le; upperB, where x is an N-bit number,\n  x\\[0\\] x\\[1\\] ... x\\[N-1\\], with 0 the most significant bit (important!).\n  The number of variables N should be sufficient to represent the bounds;\n  otherwise, the bounds are truncated to their N least significant bits.\n  Two BDDs are built bottom-up for lowerB &le; x and x &le; upperB, and they\n  are finally conjoined.\n\n  @sideeffect None\n\n  @see Cudd_Xgty\n\n*/\nDdNode *\nCudd_bddInterval(\n  DdManager * dd /**< %DD manager */,\n  int  N /**< number of x variables */,\n  DdNode ** x /**< array of x variables */,\n  unsigned int lowerB /**< lower bound */,\n  unsigned int upperB /**< upper bound */)\n{\n    DdNode *one, *zero;\n    DdNode *r, *rl, *ru;\n    int     i;\n\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    rl = one;\n    cuddRef(rl);\n    ru = one;\n    cuddRef(ru);\n\n    /* Loop to build the rest of the BDDs. */\n    for (i = N-1; i >= 0; i--) {\n\tDdNode *vl, *vu;\n\tvl = Cudd_bddIte(dd, x[i],\n\t\t\t lowerB&1 ? rl : one,\n\t\t\t lowerB&1 ? zero : rl);\n\tif (vl == NULL) {\n\t    Cudd_IterDerefBdd(dd, rl);\n\t    Cudd_IterDerefBdd(dd, ru);\n\t    return(NULL);\n\t}\n\tcuddRef(vl);\n\tCudd_IterDerefBdd(dd, rl);\n\trl = vl;\n\tlowerB >>= 1;\n\tvu = Cudd_bddIte(dd, x[i],\n\t\t\t upperB&1 ? ru : zero,\n\t\t\t upperB&1 ? one : ru);\n\tif (vu == NULL) {\n\t    Cudd_IterDerefBdd(dd, rl);\n\t    Cudd_IterDerefBdd(dd, ru);\n\t    return(NULL);\n\t}\n\tcuddRef(vu);\n\tCudd_IterDerefBdd(dd, ru);\n\tru = vu;\n\tupperB >>= 1;\n    }\n\n    /* Conjoin the two bounds. */\n    r = Cudd_bddAnd(dd, rl, ru);\n    if (r == NULL) {\n\tCudd_IterDerefBdd(dd, rl);\n\tCudd_IterDerefBdd(dd, ru);\n\treturn(NULL);\n    }\n    cuddRef(r);\n    Cudd_IterDerefBdd(dd, rl);\n    Cudd_IterDerefBdd(dd, ru);\n    cuddDeref(r);\n    return(r);\n\n} /* end of Cudd_bddInterval */\n\n\n/**\n  @brief Computes the compatible projection of R w.r.t. cube Y.\n\n  @details Computes the compatible projection of relation R with\n  respect to cube Y.  For a comparison between Cudd_CProjection and\n  Cudd_PrioritySelect, see the documentation of the latter.\n\n  @return a pointer to the c-projection if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_PrioritySelect\n\n*/\nDdNode *\nCudd_CProjection(\n  DdManager * dd,\n  DdNode * R,\n  DdNode * Y)\n{\n    DdNode *res;\n    DdNode *support;\n\n    if (Cudd_CheckCube(dd,Y) == 0) {\n\t(void) fprintf(dd->err,\n\t\"Error: The third argument of Cudd_CProjection should be a cube\\n\");\n\tdd->errorCode = CUDD_INVALID_ARG;\n\treturn(NULL);\n    }\n\n    /* Compute the support of Y, which is used by the abstraction step\n    ** in cuddCProjectionRecur.\n    */\n    support = Cudd_Support(dd,Y);\n    if (support == NULL) return(NULL);\n    cuddRef(support);\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddCProjectionRecur(dd,R,Y,support);\n    } while (dd->reordered == 1);\n\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd,support);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n          dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd,support);\n    cuddDeref(res);\n\n    return(res);\n\n} /* end of Cudd_CProjection */\n\n\n/**\n  @brief Computes the Hamming distance %ADD.\n\n  @details The two vectors xVars and yVars identify the variables that\n  form the two arguments.\n\n  @return an %ADD that gives the Hamming distance between its two\n  arguments if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_addHamming(\n  DdManager * dd,\n  DdNode ** xVars,\n  DdNode ** yVars,\n  int  nVars)\n{\n    DdNode  *result,*tempBdd;\n    DdNode  *tempAdd,*temp;\n    int     i;\n\n    result = DD_ZERO(dd);\n    cuddRef(result);\n\n    for (i = 0; i < nVars; i++) {\n\ttempBdd = Cudd_bddIte(dd,xVars[i],Cudd_Not(yVars[i]),yVars[i]);\n\tif (tempBdd == NULL) {\n\t    Cudd_RecursiveDeref(dd,result);\n\t    return(NULL);\n\t}\n\tcuddRef(tempBdd);\n\ttempAdd = Cudd_BddToAdd(dd,tempBdd);\n\tif (tempAdd == NULL) {\n\t    Cudd_RecursiveDeref(dd,tempBdd);\n\t    Cudd_RecursiveDeref(dd,result);\n\t    return(NULL);\n\t}\n\tcuddRef(tempAdd);\n\tCudd_RecursiveDeref(dd,tempBdd);\n\ttemp = Cudd_addApply(dd,Cudd_addPlus,tempAdd,result);\n\tif (temp == NULL) {\n\t    Cudd_RecursiveDeref(dd,tempAdd);\n\t    Cudd_RecursiveDeref(dd,result);\n\t    return(NULL);\n\t}\n\tcuddRef(temp);\n\tCudd_RecursiveDeref(dd,tempAdd);\n\tCudd_RecursiveDeref(dd,result);\n\tresult = temp;\n    }\n\n    cuddDeref(result);\n    return(result);\n\n} /* end of Cudd_addHamming */\n\n\n/**\n  @brief Returns the minimum Hamming distance between f and minterm.\n\n  @details Returns the minimum Hamming distance between the\n  minterms of a function f and a reference minterm. The function is\n  given as a %BDD; the minterm is given as an array of integers, one\n  for each variable in the manager.\n\n  @return the minimum distance if it is less than the upper bound; the\n  upper bound if the minimum distance is at least as large;\n  CUDD_OUT_OF_MEM in case of failure.\n\n  @sideeffect None\n\n  @see Cudd_addHamming Cudd_bddClosestCube\n\n*/\nint\nCudd_MinHammingDist(\n  DdManager *dd /**< %DD manager */,\n  DdNode *f /**< function to examine */,\n  int *minterm /**< reference minterm */,\n  int upperBound /**< distance above which an approximate answer is OK */)\n{\n    DdHashTable *table;\n    CUDD_VALUE_TYPE epsilon;\n    int res;\n\n    table = cuddHashTableInit(dd,1,2);\n    if (table == NULL) {\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    epsilon = Cudd_ReadEpsilon(dd);\n    Cudd_SetEpsilon(dd,(CUDD_VALUE_TYPE)0.0);\n    res = cuddMinHammingDistRecur(f,minterm,table,upperBound);\n    cuddHashTableQuit(table);\n    Cudd_SetEpsilon(dd,epsilon);\n\n    return(res);\n\n} /* end of Cudd_MinHammingDist */\n\n\n/**\n  @brief Finds a cube of f at minimum Hamming distance from the minterms of g.\n\n  @details All the minterms of the cube are at the minimum distance.\n  If the distance is 0, the cube belongs to the intersection of f and\n  g.\n\n  @return the cube if successful; NULL otherwise.\n\n  @sideeffect The distance is returned as a side effect.\n\n  @see Cudd_MinHammingDist\n\n*/\nDdNode *\nCudd_bddClosestCube(\n  DdManager *dd,\n  DdNode * f,\n  DdNode *g,\n  int *distance)\n{\n    DdNode *res, *acube;\n    CUDD_VALUE_TYPE rdist;\n\n    /* Compute the cube and distance as a single ADD. */\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddClosestCube(dd,f,g,CUDD_CONST_INDEX + 1.0);\n    } while (dd->reordered == 1);\n    if (res == NULL) {\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n        return(NULL);\n    }\n    cuddRef(res);\n\n    /* Unpack distance and cube. */\n    do {\n\tdd->reordered = 0;\n\tacube = separateCube(dd, res, &rdist);\n    } while (dd->reordered == 1);\n    if (acube == NULL) {\n\tCudd_RecursiveDeref(dd, res);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(acube);\n    Cudd_RecursiveDeref(dd, res);\n\n    /* Convert cube from ADD to BDD. */\n    do {\n\tdd->reordered = 0;\n\tres = cuddAddBddDoPattern(dd, acube);\n    } while (dd->reordered == 1);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, acube);\n        if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n            dd->timeoutHandler(dd, dd->tohArg);\n        }\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd, acube);\n\n    *distance = (int) rdist;\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_bddClosestCube */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_CProjection.\n\n  @return the projection if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_CProjection\n\n*/\nDdNode *\ncuddCProjectionRecur(\n  DdManager * dd,\n  DdNode * R,\n  DdNode * Y,\n  DdNode * Ysupp)\n{\n    DdNode *res, *res1, *res2, *resA;\n    DdNode *r, *y, *RT, *RE, *YT, *YE, *Yrest, *Ra, *Ran, *Gamma, *Alpha;\n    int topR, topY, top;\n    unsigned int index;\n    DdNode *one = DD_ONE(dd);\n\n    statLine(dd);\n    if (Y == one) return(R);\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsConstantInt(Y));\n#endif\n\n    if (R == Cudd_Not(one)) return(R);\n\n    res = cuddCacheLookup2(dd, Cudd_CProjection, R, Y);\n    if (res != NULL) return(res);\n\n    checkWhetherToGiveUp(dd);\n\n    r = Cudd_Regular(R);\n    topR = cuddI(dd,r->index);\n    y = Cudd_Regular(Y);\n    topY = cuddI(dd,y->index);\n\n    top = ddMin(topR, topY);\n\n    /* Compute the cofactors of R */\n    index = r->index;\n    if (topR == top) {\n\tRT = cuddT(r);\n\tRE = cuddE(r);\n\tif (r != R) {\n\t    RT = Cudd_Not(RT); RE = Cudd_Not(RE);\n\t}\n    } else {\n\tRT = RE = R;\n    }\n\n    if (topY > top) {\n\t/* Y does not depend on the current top variable.\n\t** We just need to compute the results on the two cofactors of R\n\t** and make them the children of a node labeled r->index.\n\t*/\n\tres1 = cuddCProjectionRecur(dd,RT,Y,Ysupp);\n\tif (res1 == NULL) return(NULL);\n\tcuddRef(res1);\n\tres2 = cuddCProjectionRecur(dd,RE,Y,Ysupp);\n\tif (res2 == NULL) {\n\t    Cudd_RecursiveDeref(dd,res1);\n\t    return(NULL);\n\t}\n\tcuddRef(res2);\n\tres = cuddBddIteRecur(dd, dd->vars[index], res1, res2);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd,res1);\n\t    Cudd_RecursiveDeref(dd,res2);\n\t    return(NULL);\n\t}\n\t/* If we have reached this point, res1 and res2 are now\n\t** incorporated in res. cuddDeref is therefore sufficient.\n\t*/\n\tcuddDeref(res1);\n\tcuddDeref(res2);\n    } else {\n\t/* Compute the cofactors of Y */\n\tindex = y->index;\n\tYT = cuddT(y);\n\tYE = cuddE(y);\n\tif (y != Y) {\n\t    YT = Cudd_Not(YT); YE = Cudd_Not(YE);\n\t}\n\tif (YT == Cudd_Not(one)) {\n\t    Alpha  = Cudd_Not(dd->vars[index]);\n\t    Yrest = YE;\n\t    Ra = RE;\n\t    Ran = RT;\n\t} else {\n\t    Alpha = dd->vars[index];\n\t    Yrest = YT;\n\t    Ra = RT;\n\t    Ran = RE;\n\t}\n\tGamma = cuddBddExistAbstractRecur(dd,Ra,cuddT(Ysupp));\n\tif (Gamma == NULL) return(NULL);\n\tif (Gamma == one) {\n\t    res1 = cuddCProjectionRecur(dd,Ra,Yrest,cuddT(Ysupp));\n\t    if (res1 == NULL) return(NULL);\n\t    cuddRef(res1);\n\t    res = cuddBddAndRecur(dd, Alpha, res1);\n\t    if (res == NULL) {\n\t\tCudd_RecursiveDeref(dd,res1);\n\t\treturn(NULL);\n\t    }\n\t    cuddDeref(res1);\n\t} else if (Gamma == Cudd_Not(one)) {\n\t    res1 = cuddCProjectionRecur(dd,Ran,Yrest,cuddT(Ysupp));\n\t    if (res1 == NULL) return(NULL);\n\t    cuddRef(res1);\n\t    res = cuddBddAndRecur(dd, Cudd_Not(Alpha), res1);\n\t    if (res == NULL) {\n\t\tCudd_RecursiveDeref(dd,res1);\n\t\treturn(NULL);\n\t    }\n\t    cuddDeref(res1);\n\t} else {\n\t    cuddRef(Gamma);\n\t    resA = cuddCProjectionRecur(dd,Ran,Yrest,cuddT(Ysupp));\n\t    if (resA == NULL) {\n\t\tCudd_RecursiveDeref(dd,Gamma);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(resA);\n\t    res2 = cuddBddAndRecur(dd, Cudd_Not(Gamma), resA);\n\t    if (res2 == NULL) {\n\t\tCudd_RecursiveDeref(dd,Gamma);\n\t\tCudd_RecursiveDeref(dd,resA);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(res2);\n\t    Cudd_RecursiveDeref(dd,Gamma);\n\t    Cudd_RecursiveDeref(dd,resA);\n\t    res1 = cuddCProjectionRecur(dd,Ra,Yrest,cuddT(Ysupp));\n\t    if (res1 == NULL) {\n\t\tCudd_RecursiveDeref(dd,res2);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(res1);\n\t    res = cuddBddIteRecur(dd, Alpha, res1, res2);\n\t    if (res == NULL) {\n\t\tCudd_RecursiveDeref(dd,res1);\n\t\tCudd_RecursiveDeref(dd,res2);\n\t\treturn(NULL);\n\t    }\n\t    cuddDeref(res1);\n\t    cuddDeref(res2);\n\t}\n    }\n\n    cuddCacheInsert2(dd,Cudd_CProjection,R,Y,res);\n\n    return(res);\n\n} /* end of cuddCProjectionRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddClosestCube.\n\n  @details@parblock\n  The procedure uses a four-way recursion to examine all four combinations\n  of cofactors of <code>f</code> and <code>g</code> according to the\n  following formula.\n\n      H(f,g) = min(H(ft,gt), H(fe,ge), H(ft,ge)+1, H(fe,gt)+1)\n\n  Bounding is based on the following observations.\n  <ul>\n  <li> If we already found two points at distance 0, there is no point in\n       continuing.  Furthermore,\n  <li> If F == not(G) then the best we can hope for is a minimum distance\n       of 1.  If we have already found two points at distance 1, there is\n       no point in continuing.  (Indeed, H(F,G) == 1 in this case.  We\n       have to continue, though, to find the cube.)\n  </ul>\n  The variable <code>bound</code> is set at the largest value of the distance\n  that we are still interested in.  Therefore, we desist when\n\n      (bound == -1) and (F != not(G)) or (bound == 0) and (F == not(G)).\n\n  If we were maximally aggressive in using the bound, we would always\n  set the bound to the minimum distance seen thus far minus one.  That\n  is, we would maintain the invariant\n\n      bound < minD,\n\n  except at the very beginning, when we have no value for\n  <code>minD</code>.\n\n  However, we do not use <code>bound < minD</code> when examining the\n  two negative cofactors, because we try to find a large cube at\n  minimum distance.  To do so, we try to find a cube in the negative\n  cofactors at the same or smaller distance from the cube found in the\n  positive cofactors.\n\n  When we compute <code>H(ft,ge)</code> and <code>H(fe,gt)</code> we\n  know that we are going to add 1 to the result of the recursive call\n  to account for the difference in the splitting variable.  Therefore,\n  we decrease the bound correspondingly.\n\n  Another important observation concerns the need of examining all\n  four pairs of cofators only when both <code>f</code> and\n  <code>g</code> depend on the top variable.\n\n  Suppose <code>gt == ge == g</code>.  (That is, <code>g</code> does\n  not depend on the top variable.)  Then\n\n      H(f,g) = min(H(ft,g), H(fe,g), H(ft,g)+1, H(fe,g)+1)\n             = min(H(ft,g), H(fe,g)) .\n\n  Therefore, under these circumstances, we skip the two \"cross\" cases.\n\n  An interesting feature of this function is the scheme used for\n  caching the results in the global computed table.  Since we have a\n  cube and a distance, we combine them to form an %ADD.  The\n  combination replaces the zero child of the top node of the cube with\n  the negative of the distance.  (The use of the negative is to avoid\n  ambiguity with 1.)  The degenerate cases (zero and one) are treated\n  specially because the distance is known (0 for one, and infinity for\n  zero).\n  @endparblock\n\n  @return the cube if succesful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddClosestCube\n\n*/\nDdNode *\ncuddBddClosestCube(\n  DdManager *dd,\n  DdNode *f,\n  DdNode *g,\n  CUDD_VALUE_TYPE bound)\n{\n    DdNode *res, *F, *G, *ft, *fe, *gt, *ge, *tt, *ee;\n    DdNode *ctt, *cee, *cte, *cet;\n    CUDD_VALUE_TYPE minD, dtt, dee, dte, det;\n    DdNode *one = DD_ONE(dd);\n    DdNode *lzero = Cudd_Not(one);\n    DdNode *azero = DD_ZERO(dd);\n    int topf, topg;\n    unsigned int index;\n\n    statLine(dd);\n    if (bound < (f == Cudd_Not(g))) return(azero);\n    /* Terminal cases. */\n    if (g == lzero || f == lzero) return(azero);\n    if (f == one && g == one) return(one);\n\n    /* Check cache. */\n    F = Cudd_Regular(f);\n    G = Cudd_Regular(g);\n    if (F->ref != 1 || G->ref != 1) {\n\tres = cuddCacheLookup2(dd,(DD_CTFP) Cudd_bddClosestCube, f, g);\n\tif (res != NULL) return(res);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    topf = cuddI(dd,F->index);\n    topg = cuddI(dd,G->index);\n\n    /* Compute cofactors. */\n    if (topf <= topg) {\n\tindex = F->index;\n\tft = cuddT(F);\n\tfe = cuddE(F);\n\tif (Cudd_IsComplement(f)) {\n\t    ft = Cudd_Not(ft);\n\t    fe = Cudd_Not(fe);\n\t}\n    } else {\n\tindex = G->index;\n\tft = fe = f;\n    }\n\n    if (topg <= topf) {\n\tgt = cuddT(G);\n\tge = cuddE(G);\n\tif (Cudd_IsComplement(g)) {\n\t    gt = Cudd_Not(gt);\n\t    ge = Cudd_Not(ge);\n\t}\n    } else {\n\tgt = ge = g;\n    }\n\n    tt = cuddBddClosestCube(dd,ft,gt,bound);\n    if (tt == NULL) return(NULL);\n    cuddRef(tt);\n    ctt = separateCube(dd,tt,&dtt);\n    if (ctt == NULL) {\n\tCudd_RecursiveDeref(dd, tt);\n\treturn(NULL);\n    }\n    cuddRef(ctt);\n    Cudd_RecursiveDeref(dd, tt);\n    minD = dtt;\n    bound = ddMin(bound,minD);\n\n    ee = cuddBddClosestCube(dd,fe,ge,bound);\n    if (ee == NULL) {\n\tCudd_RecursiveDeref(dd, ctt);\n\treturn(NULL);\n    }\n    cuddRef(ee);\n    cee = separateCube(dd,ee,&dee);\n    if (cee == NULL) {\n\tCudd_RecursiveDeref(dd, ctt);\n\tCudd_RecursiveDeref(dd, ee);\n\treturn(NULL);\n    }\n    cuddRef(cee);\n    Cudd_RecursiveDeref(dd, ee);\n    minD = ddMin(dtt, dee);\n    if (minD <= CUDD_CONST_INDEX) bound = ddMin(bound,minD-1);\n\n    if (minD > 0 && topf == topg) {\n\tDdNode *te = cuddBddClosestCube(dd,ft,ge,bound-1);\n\tif (te == NULL) {\n\t    Cudd_RecursiveDeref(dd, ctt);\n\t    Cudd_RecursiveDeref(dd, cee);\n\t    return(NULL);\n\t}\n\tcuddRef(te);\n\tcte = separateCube(dd,te,&dte);\n\tif (cte == NULL) {\n\t    Cudd_RecursiveDeref(dd, ctt);\n\t    Cudd_RecursiveDeref(dd, cee);\n\t    Cudd_RecursiveDeref(dd, te);\n\t    return(NULL);\n\t}\n\tcuddRef(cte);\n\tCudd_RecursiveDeref(dd, te);\n\tdte += 1.0;\n\tminD = ddMin(minD, dte);\n    } else {\n\tcte = azero;\n\tcuddRef(cte);\n\tdte = CUDD_CONST_INDEX + 1.0;\n    }\n    if (minD <= CUDD_CONST_INDEX) bound = ddMin(bound,minD-1);\n\n    if (minD > 0 && topf == topg) {\n\tDdNode *et = cuddBddClosestCube(dd,fe,gt,bound-1);\n\tif (et == NULL) {\n\t    Cudd_RecursiveDeref(dd, ctt);\n\t    Cudd_RecursiveDeref(dd, cee);\n\t    Cudd_RecursiveDeref(dd, cte);\n\t    return(NULL);\n\t}\n\tcuddRef(et);\n\tcet = separateCube(dd,et,&det);\n\tif (cet == NULL) {\n\t    Cudd_RecursiveDeref(dd, ctt);\n\t    Cudd_RecursiveDeref(dd, cee);\n\t    Cudd_RecursiveDeref(dd, cte);\n\t    Cudd_RecursiveDeref(dd, et);\n\t    return(NULL);\n\t}\n\tcuddRef(cet);\n\tCudd_RecursiveDeref(dd, et);\n\tdet += 1.0;\n\tminD = ddMin(minD, det);\n    } else {\n\tcet = azero;\n\tcuddRef(cet);\n\tdet = CUDD_CONST_INDEX + 1.0;\n    }\n\n    if (minD == dtt) {\n\tif (dtt == dee && ctt == cee) {\n\t    res = createResult(dd,CUDD_CONST_INDEX,1,ctt,dtt);\n\t} else {\n\t    res = createResult(dd,index,1,ctt,dtt);\n\t}\n    } else if (minD == dee) {\n\tres = createResult(dd,index,0,cee,dee);\n    } else if (minD == dte) {\n#ifdef DD_DEBUG\n\tassert(topf == topg);\n#endif\n\tres = createResult(dd,index,1,cte,dte);\n    } else {\n#ifdef DD_DEBUG\n\tassert(topf == topg);\n#endif\n\tres = createResult(dd,index,0,cet,det);\n    }\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, ctt);\n\tCudd_RecursiveDeref(dd, cee);\n\tCudd_RecursiveDeref(dd, cte);\n\tCudd_RecursiveDeref(dd, cet);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd, ctt);\n    Cudd_RecursiveDeref(dd, cee);\n    Cudd_RecursiveDeref(dd, cte);\n    Cudd_RecursiveDeref(dd, cet);\n\n    /* Only cache results that are different from azero to avoid\n    ** storing results that depend on the value of the bound. */\n    if ((F->ref != 1 || G->ref != 1) && res != azero)\n\tcuddCacheInsert2(dd,(DD_CTFP) Cudd_bddClosestCube, f, g, res);\n\n    cuddDeref(res);\n    return(res);\n\n} /* end of cuddBddClosestCube */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_MinHammingDist.\n\n  @details It is based on the following identity. Let H(f) be the\n  minimum Hamming distance of the minterms of f from the reference\n  minterm. Then:\n\n      H(f) = min(H(f0)+h0,H(f1)+h1)\n\n  where f0 and f1 are the two cofactors of f with respect to its top\n  variable; h0 is 1 if the minterm assigns 1 to the top variable of f;\n  h1 is 1 if the minterm assigns 0 to the top variable of f.\n  The upper bound on the distance is used to bound the depth of the\n  recursion.\n\n  @return the minimum distance unless it exceeds the upper bound or\n  computation fails.\n\n  @sideeffect None\n\n  @see Cudd_MinHammingDist\n\n*/\nstatic int\ncuddMinHammingDistRecur(\n  DdNode * f,\n  int *minterm,\n  DdHashTable * table,\n  int upperBound)\n{\n    DdNode\t*F, *Ft, *Fe;\n    double\th, hT, hE;\n    DdNode\t*zero, *res;\n    DdManager\t*dd = table->manager;\n\n    statLine(dd);\n    if (upperBound == 0) return(0);\n\n    F = Cudd_Regular(f);\n\n    if (cuddIsConstant(F)) {\n\tzero = Cudd_Not(DD_ONE(dd));\n\tif (f == dd->background || f == zero) {\n\t    return(upperBound);\n\t} else {\n\t    return(0);\n\t}\n    }\n    if ((res = cuddHashTableLookup1(table,f)) != NULL) {\n\th = cuddV(res);\n\tif (res->ref == 0) {\n\t    dd->dead++;\n\t    dd->constants.dead++;\n\t}\n\treturn((int) h);\n    }\n\n    Ft = cuddT(F); Fe = cuddE(F);\n    if (Cudd_IsComplement(f)) {\n\tFt = Cudd_Not(Ft); Fe = Cudd_Not(Fe);\n    }\n    if (minterm[F->index] == 0) {\n\tDdNode *temp = Ft;\n\tFt = Fe; Fe = temp;\n    }\n\n    hT = cuddMinHammingDistRecur(Ft,minterm,table,upperBound);\n    if (hT == CUDD_OUT_OF_MEM) return(CUDD_OUT_OF_MEM);\n    if (hT == 0) {\n\thE = upperBound;\n    } else {\n\thE = cuddMinHammingDistRecur(Fe,minterm,table,upperBound - 1);\n\tif (hE == CUDD_OUT_OF_MEM) return(CUDD_OUT_OF_MEM);\n    }\n    h = ddMin(hT, hE + 1);\n\n    if (F->ref != 1) {\n\tptrint fanout = (ptrint) F->ref;\n\tcuddSatDec(fanout);\n\tres = cuddUniqueConst(dd, (CUDD_VALUE_TYPE) h);\n\tif (!cuddHashTableInsert1(table,f,res,fanout)) {\n\t    cuddRef(res); Cudd_RecursiveDeref(dd, res);\n\t    return(CUDD_OUT_OF_MEM);\n\t}\n    }\n\n    return((int) h);\n\n} /* end of cuddMinHammingDistRecur */\n\n\n/**\n  @brief Separates cube from distance.\n\n  @return the cube if successful; NULL otherwise.\n\n  @sideeffect The distance is returned as a side effect.\n\n  @see cuddBddClosestCube createResult\n\n*/\nstatic DdNode *\nseparateCube(\n  DdManager *dd,\n  DdNode *f,\n  CUDD_VALUE_TYPE *distance)\n{\n    DdNode *cube, *t;\n\n    /* One and zero are special cases because the distance is implied. */\n    if (Cudd_IsConstantInt(f)) {\n\t*distance = (f == DD_ONE(dd)) ? 0.0 :\n\t    (1.0 + (CUDD_VALUE_TYPE) CUDD_CONST_INDEX);\n\treturn(f);\n    }\n\n    /* Find out which branch points to the distance and replace the top\n    ** node with one pointing to zero instead. */\n    t = cuddT(f);\n    if (Cudd_IsConstantInt(t) && cuddV(t) <= 0) {\n#ifdef DD_DEBUG\n\tassert(!Cudd_IsConstantInt(cuddE(f)) || cuddE(f) == DD_ONE(dd));\n#endif\n\t*distance = -cuddV(t);\n\tcube = cuddUniqueInter(dd, f->index, DD_ZERO(dd), cuddE(f));\n    } else {\n#ifdef DD_DEBUG\n\tassert(!Cudd_IsConstantInt(t) || t == DD_ONE(dd));\n#endif\n\t*distance = -cuddV(cuddE(f));\n\tcube = cuddUniqueInter(dd, f->index, t, DD_ZERO(dd));\n    }\n\n    return(cube);\n\n} /* end of separateCube */\n\n\n/**\n  @brief Builds a result for cache storage.\n\n  @return a pointer to the resulting %ADD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see cuddBddClosestCube separateCube\n\n*/\nstatic DdNode *\ncreateResult(\n  DdManager *dd,\n  unsigned int index,\n  unsigned int phase,\n  DdNode *cube,\n  CUDD_VALUE_TYPE distance)\n{\n    DdNode *res, *constant;\n\n    /* Special case.  The cube is either one or zero, and we do not\n    ** add any variables.  Hence, the result is also one or zero,\n    ** and the distance remains implied by the value of the constant. */\n    if (index == CUDD_CONST_INDEX && Cudd_IsConstantInt(cube)) return(cube);\n\n    constant = cuddUniqueConst(dd,-distance);\n    if (constant == NULL) return(NULL);\n    cuddRef(constant);\n\n    if (index == CUDD_CONST_INDEX) {\n\t/* Replace the top node. */\n\tif (cuddT(cube) == DD_ZERO(dd)) {\n\t    res = cuddUniqueInter(dd,cube->index,constant,cuddE(cube));\n\t} else {\n\t    res = cuddUniqueInter(dd,cube->index,cuddT(cube),constant);\n\t}\n    } else {\n\t/* Add a new top node. */\n#ifdef DD_DEBUG\n\tassert(cuddI(dd,index) < cuddI(dd,cube->index));\n#endif\n\tif (phase) {\n\t    res = cuddUniqueInter(dd,index,cube,constant);\n\t} else {\n\t    res = cuddUniqueInter(dd,index,constant,cube);\n\t}\n    }\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd, constant);\n\treturn(NULL);\n    }\n    cuddDeref(constant); /* safe because constant is part of res */\n\n    return(res);\n\n} /* end of createResult */\n"
  },
  {
    "path": "cudd/cudd/cuddRead.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions to read in a matrix\n\n  @see cudd_addHarwell.c\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Reads in a sparse matrix.\n\n  @details Reads in a sparse matrix specified in a simple format.\n  The first line of the input contains the numbers of rows and columns.\n  The remaining lines contain the elements of the matrix, one per line.\n  Given a background value\n  (specified by the background field of the manager), only the values\n  different from it are explicitly listed.  Each foreground element is\n  described by two integers, i.e., the row and column number, and a\n  real number, i.e., the value.<p>\n  Cudd_addRead produces an %ADD that depends on two sets of variables: x\n  and y.  The x variables (x\\[0\\] ... x\\[nx-1\\]) encode the row index and\n  the y variables (y\\[0\\] ... y\\[ny-1\\]) encode the column index.\n  x\\[0\\] and y\\[0\\] are the most significant bits in the indices.\n  The variables may already exist or may be created by the function.\n  The index of x\\[i\\] is bx+i*sx, and the index of y\\[i\\] is by+i*sy.<p>\n  On input, nx and ny hold the numbers\n  of row and column variables already in existence. On output, they\n  hold the numbers of row and column variables actually used by the\n  matrix. When Cudd_addRead creates the variable arrays,\n  the index of x\\[i\\] is bx+i*sx, and the index of y\\[i\\] is by+i*sy.\n  When some variables already exist Cudd_addRead expects the indices\n  of the existing x variables to be bx+i*sx, and the indices of the\n  existing y variables to be by+i*sy.<p>\n  m and n are set to the numbers of rows and columns of the\n  matrix.  Their values on input are immaterial.\n  The %ADD for the sparse matrix is returned in E, and its reference\n  count is > 0.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect nx and ny are set to the numbers of row and column\n  variables. m and n are set to the numbers of rows and columns. x and y\n  are possibly extended to represent the array of row and column\n  variables. Similarly for xn and yn_, which hold on return from\n  Cudd_addRead the complements of the row and column variables.\n\n  @see Cudd_addHarwell Cudd_bddRead\n\n*/\nint\nCudd_addRead(\n  FILE * fp /**< input file pointer */,\n  DdManager * dd /**< %DD manager */,\n  DdNode ** E /**< characteristic function of the graph */,\n  DdNode *** x /**< array of row variables */,\n  DdNode *** y /**< array of column variables */,\n  DdNode *** xn /**< array of complemented row variables */,\n  DdNode *** yn_ /**< array of complemented column variables */,\n  int * nx /**< number or row variables */,\n  int * ny /**< number or column variables */,\n  int * m /**< number of rows */,\n  int * n /**< number of columns */,\n  int  bx /**< first index of row variables */,\n  int  sx /**< step of row variables */,\n  int  by /**< first index of column variables */,\n  int  sy /**< step of column variables */)\n{\n    DdNode *one, *zero;\n    DdNode *w, *neW;\n    DdNode *minterm1;\n    int u, v, err, i, nv;\n    int lnx, lny;\n    CUDD_VALUE_TYPE val;\n    DdNode **lx, **ly, **lxn, **lyn;\n\n    one = DD_ONE(dd);\n    zero = DD_ZERO(dd);\n\n    err = fscanf(fp, \"%d %d\", &u, &v);\n    if (err == EOF) {\n\treturn(0);\n    } else if (err != 2) {\n\treturn(0);\n    }\n\n    *m = u;\n    /* Compute the number of x variables. */\n    lx = *x; lxn = *xn;\n    u--; \t/* row and column numbers start from 0 */\n    for (lnx=0; u > 0; lnx++) {\n\tu >>= 1;\n    }\n    /* Here we rely on the fact that REALLOC of a null pointer is\n    ** translates to an ALLOC.\n    */\n    if (lnx > *nx) {\n\t*x = lx = REALLOC(DdNode *, *x, lnx);\n\tif (lx == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t*xn = lxn =  REALLOC(DdNode *, *xn, lnx);\n\tif (lxn == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n    }\n\n    *n = v;\n    /* Compute the number of y variables. */\n    ly = *y; lyn = *yn_;\n    v--; \t/* row and column numbers start from 0 */\n    for (lny=0; v > 0; lny++) {\n\tv >>= 1;\n    }\n    /* Here we rely on the fact that REALLOC of a null pointer is\n    ** translates to an ALLOC.\n    */\n    if (lny > *ny) {\n\t*y = ly = REALLOC(DdNode *, *y, lny);\n\tif (ly == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\t*yn_ = lyn =  REALLOC(DdNode *, *yn_, lny);\n\tif (lyn == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n    }\n\n    /* Create all new variables. */\n    for (i = *nx, nv = bx + (*nx) * sx; i < lnx; i++, nv += sx) {\n\tdo {\n\t    dd->reordered = 0;\n\t    lx[i] = cuddUniqueInter(dd, nv, one, zero);\n\t} while (dd->reordered == 1);\n\tif (lx[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n        cuddRef(lx[i]);\n\tdo {\n\t    dd->reordered = 0;\n\t    lxn[i] = cuddUniqueInter(dd, nv, zero, one);\n\t} while (dd->reordered == 1);\n\tif (lxn[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n        cuddRef(lxn[i]);\n    }\n    for (i = *ny, nv = by + (*ny) * sy; i < lny; i++, nv += sy) {\n\tdo {\n\t    dd->reordered = 0;\n\t    ly[i] = cuddUniqueInter(dd, nv, one, zero);\n\t} while (dd->reordered == 1);\n\tif (ly[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n\tcuddRef(ly[i]);\n\tdo {\n\t    dd->reordered = 0;\n\t    lyn[i] = cuddUniqueInter(dd, nv, zero, one);\n\t} while (dd->reordered == 1);\n\tif (lyn[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n\tcuddRef(lyn[i]);\n    }\n    *nx = lnx;\n    *ny = lny;\n\n    *E = dd->background; /* this call will never cause reordering */\n    cuddRef(*E);\n\n    while (! feof(fp)) {\n\terr = fscanf(fp, \"%d %d %lf\", &u, &v, &val);\n\tif (err == EOF) {\n\t    break;\n\t} else if (err != 3) {\n\t    return(0);\n\t} else if (u >= *m || v >= *n || u < 0 || v < 0) {\n\t    return(0);\n\t}\n \n\tminterm1 = one; cuddRef(minterm1);\n\n\t/* Build minterm1 corresponding to this arc */\n\tfor (i = lnx - 1; i>=0; i--) {\n\t    if (u & 1) {\n\t\tw = Cudd_addApply(dd, Cudd_addTimes, minterm1, lx[i]);\n\t    } else {\n\t\tw = Cudd_addApply(dd, Cudd_addTimes, minterm1, lxn[i]);\n\t    }\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, minterm1);\n\t\treturn(0);\n\t    }\n\t    cuddRef(w);\n\t    Cudd_RecursiveDeref(dd, minterm1);\n\t    minterm1 = w;\n\t    u >>= 1;\n\t}\n\tfor (i = lny - 1; i>=0; i--) {\n\t    if (v & 1) {\n\t\tw = Cudd_addApply(dd, Cudd_addTimes, minterm1, ly[i]);\n\t    } else {\n\t\tw = Cudd_addApply(dd, Cudd_addTimes, minterm1, lyn[i]);\n\t    }\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, minterm1);\n\t\treturn(0);\n\t    }\n\t    cuddRef(w);\n\t    Cudd_RecursiveDeref(dd, minterm1);\n\t    minterm1 = w;\n\t    v >>= 1;\n\t}\n\t/* Create new constant node if necessary.\n\t** This call will never cause reordering.\n\t*/\n\tneW = cuddUniqueConst(dd, val);\n\tif (neW == NULL) {\n\t    Cudd_RecursiveDeref(dd, minterm1);\n\t    return(0);\n\t}\n    \tcuddRef(neW);\n\n\tw = Cudd_addIte(dd, minterm1, neW, *E);\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd, minterm1);\n\t    Cudd_RecursiveDeref(dd, neW);\n\t    return(0);\n\t}\n\tcuddRef(w);\n\tCudd_RecursiveDeref(dd, minterm1);\n\tCudd_RecursiveDeref(dd, neW);\n\tCudd_RecursiveDeref(dd, *E);\n\t*E = w;\n    }\n    return(1);\n\n} /* end of Cudd_addRead */\n\n\n/**\n  @brief Reads in a graph (without labels) given as a list of arcs.\n\n  @details Reads in a graph (without labels) given as an adjacency\n  matrix.  The first line of the input contains the numbers of rows and\n  columns of the adjacency matrix. The remaining lines contain the arcs\n  of the graph, one per line. Each arc is described by two integers,\n  i.e., the row and column number, or the indices of the two endpoints.\n  Cudd_bddRead produces a %BDD that depends on two sets of variables: x\n  and y.  The x variables (x\\[0\\] ... x\\[nx-1\\]) encode\n  the row index and the y variables (y\\[0\\] ... y\\[ny-1\\]) encode the\n  column index. x\\[0\\] and y\\[0\\] are the most significant bits in the\n  indices.\n  The variables may already exist or may be created by the function.\n  The index of x\\[i\\] is bx+i*sx, and the index of y\\[i\\] is by+i*sy.<p>\n  On input, nx and ny hold the numbers of row and column variables already\n  in existence. On output, they hold the numbers of row and column\n  variables actually used by the matrix. When Cudd_bddRead creates the\n  variable arrays, the index of x\\[i\\] is bx+i*sx, and the index of\n  y\\[i\\] is by+i*sy. When some variables already exist, Cudd_bddRead\n  expects the indices of the existing x variables to be bx+i*sx, and the\n  indices of the existing y variables to be by+i*sy.<p>\n  m and n are set to the numbers of rows and columns of the\n  matrix.  Their values on input are immaterial.  The %BDD for the graph\n  is returned in E, and its reference count is > 0.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect nx and ny are set to the numbers of row and column\n  variables. m and n are set to the numbers of rows and columns. x and y\n  are possibly extended to represent the array of row and column\n  variables.\n\n  @see Cudd_addHarwell Cudd_addRead\n\n*/\nint\nCudd_bddRead(\n  FILE * fp /**< input file pointer */,\n  DdManager * dd /**< DD manager */,\n  DdNode ** E /**< characteristic function of the graph */,\n  DdNode *** x /**< array of row variables */,\n  DdNode *** y /**< array of column variables */,\n  int * nx /**< number or row variables */,\n  int * ny /**< number or column variables */,\n  int * m /**< number of rows */,\n  int * n /**< number of columns */,\n  int  bx /**< first index of row variables */,\n  int  sx /**< step of row variables */,\n  int  by /**< first index of column variables */,\n  int  sy /**< step of column variables */)\n{\n    DdNode *one, *zero;\n    DdNode *w;\n    DdNode *minterm1;\n    int u, v, err, i, nv;\n    int lnx, lny;\n    DdNode **lx, **ly;\n\n    one = DD_ONE(dd);\n    zero = Cudd_Not(one);\n\n    err = fscanf(fp, \"%d %d\", &u, &v);\n    if (err == EOF) {\n\treturn(0);\n    } else if (err != 2) {\n\treturn(0);\n    }\n\n    *m = u;\n    /* Compute the number of x variables. */\n    lx = *x;\n    u--; \t/* row and column numbers start from 0 */\n    for (lnx=0; u > 0; lnx++) {\n\tu >>= 1;\n    }\n    if (lnx > *nx) {\n\t*x = lx = REALLOC(DdNode *, *x, lnx);\n\tif (lx == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n    }\n\n    *n = v;\n    /* Compute the number of y variables. */\n    ly = *y;\n    v--; \t/* row and column numbers start from 0 */\n    for (lny=0; v > 0; lny++) {\n\tv >>= 1;\n    }\n    if (lny > *ny) {\n\t*y = ly = REALLOC(DdNode *, *y, lny);\n\tif (ly == NULL) {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n    }\n\n    /* Create all new variables. */\n    for (i = *nx, nv = bx + (*nx) * sx; i < lnx; i++, nv += sx) {\n\tdo {\n\t    dd->reordered = 0;\n\t    lx[i] = cuddUniqueInter(dd, nv, one, zero);\n\t} while (dd->reordered == 1);\n\tif (lx[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n        cuddRef(lx[i]);\n    }\n    for (i = *ny, nv = by + (*ny) * sy; i < lny; i++, nv += sy) {\n\tdo {\n\t    dd->reordered = 0;\n\t    ly[i] = cuddUniqueInter(dd, nv, one, zero);\n\t} while (dd->reordered == 1);\n\tif (ly[i] == NULL) {\n            if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n                dd->timeoutHandler(dd, dd->tohArg);\n            }\n            return(0);\n        }\n\tcuddRef(ly[i]);\n    }\n    *nx = lnx;\n    *ny = lny;\n\n    *E = zero; /* this call will never cause reordering */\n    cuddRef(*E);\n\n    while (! feof(fp)) {\n\terr = fscanf(fp, \"%d %d\", &u, &v);\n\tif (err == EOF) {\n\t    break;\n\t} else if (err != 2) {\n\t    return(0);\n\t} else if (u >= *m || v >= *n || u < 0 || v < 0) {\n\t    return(0);\n\t}\n \n\tminterm1 = one; cuddRef(minterm1);\n\n\t/* Build minterm1 corresponding to this arc. */\n\tfor (i = lnx - 1; i>=0; i--) {\n\t    if (u & 1) {\n\t\tw = Cudd_bddAnd(dd, minterm1, lx[i]);\n\t    } else {\n\t\tw = Cudd_bddAnd(dd, minterm1, Cudd_Not(lx[i]));\n\t    }\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, minterm1);\n\t\treturn(0);\n\t    }\n\t    cuddRef(w);\n\t    Cudd_RecursiveDeref(dd,minterm1);\n\t    minterm1 = w;\n\t    u >>= 1;\n\t}\n\tfor (i = lny - 1; i>=0; i--) {\n\t    if (v & 1) {\n\t\tw = Cudd_bddAnd(dd, minterm1, ly[i]);\n\t    } else {\n\t\tw = Cudd_bddAnd(dd, minterm1, Cudd_Not(ly[i]));\n\t    }\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd, minterm1);\n\t\treturn(0);\n\t    }\n\t    cuddRef(w);\n\t    Cudd_RecursiveDeref(dd, minterm1);\n\t    minterm1 = w;\n\t    v >>= 1;\n\t}\n\n\tw = Cudd_bddAnd(dd, Cudd_Not(minterm1), Cudd_Not(*E));\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd, minterm1);\n\t    return(0);\n\t}\n\tw = Cudd_Not(w);\n\tcuddRef(w);\n\tCudd_RecursiveDeref(dd, minterm1);\n\tCudd_RecursiveDeref(dd, *E);\n\t*E = w;\n    }\n    return(1);\n\n} /* end of Cudd_bddRead */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n"
  },
  {
    "path": "cudd/cudd/cuddRef.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions that manipulate the reference counts.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Increases the reference count of a node, if it is not\n  saturated.\n\n  @sideeffect None\n\n  @see Cudd_RecursiveDeref Cudd_Deref\n\n*/\nvoid\nCudd_Ref(\n  DdNode * n)\n{\n\n    n = Cudd_Regular(n);\n\n    cuddSatInc(n->ref);\n\n} /* end of Cudd_Ref */\n\n\n/**\n  @brief Decreases the reference count of node n.\n\n  @details If n dies, recursively decreases the reference counts of\n  its children.  It is used to dispose of a DD that is no longer\n  needed.\n\n  @sideeffect None\n\n  @see Cudd_Deref Cudd_Ref Cudd_RecursiveDerefZdd\n\n*/\nvoid\nCudd_RecursiveDeref(\n  DdManager * table,\n  DdNode * n)\n{\n    DdNode *N;\n    int ord;\n    DdNodePtr *stack = table->stack;\n    int SP = 1;\n\n    unsigned int live = table->keys - table->dead;\n    if (live > table->peakLiveNodes) {\n\ttable->peakLiveNodes = live;\n    }\n\n    N = Cudd_Regular(n);\n\n    do {\n#ifdef DD_DEBUG\n\tassert(N->ref != 0);\n#endif\n\n\tif (N->ref == 1) {\n\t    N->ref = 0;\n\t    table->dead++;\n#ifdef DD_STATS\n\t    table->nodesDropped++;\n#endif\n\t    if (cuddIsConstant(N)) {\n\t\ttable->constants.dead++;\n\t\tN = stack[--SP];\n\t    } else {\n\t\tord = table->perm[N->index];\n\t\tstack[SP++] = Cudd_Regular(cuddE(N));\n\t\ttable->subtables[ord].dead++;\n\t\tN = cuddT(N);\n\t    }\n\t} else {\n\t    cuddSatDec(N->ref);\n\t    N = stack[--SP];\n\t}\n    } while (SP != 0);\n\n} /* end of Cudd_RecursiveDeref */\n\n\n/**\n  @brief Decreases the reference count of %BDD node n.\n\n  @details If n dies, recursively decreases the reference counts of\n  its children.  It is used to dispose of a %BDD that is no longer\n  needed. It is more efficient than Cudd_RecursiveDeref, but it cannot\n  be used on ADDs. The greater efficiency comes from being able to\n  assume that no constant node will ever die as a result of a call to\n  this procedure.\n\n  @sideeffect None\n\n  @see Cudd_RecursiveDeref Cudd_DelayedDerefBdd\n\n*/\nvoid\nCudd_IterDerefBdd(\n  DdManager * table,\n  DdNode * n)\n{\n    DdNode *N;\n    int ord;\n    DdNodePtr *stack = table->stack;\n    int SP = 1;\n\n    unsigned int live = table->keys - table->dead;\n    if (live > table->peakLiveNodes) {\n\ttable->peakLiveNodes = live;\n    }\n\n    N = Cudd_Regular(n);\n\n    do {\n#ifdef DD_DEBUG\n\tassert(N->ref != 0);\n#endif\n\n\tif (N->ref == 1) {\n\t    N->ref = 0;\n\t    table->dead++;\n#ifdef DD_STATS\n\t    table->nodesDropped++;\n#endif\n\t    ord = table->perm[N->index];\n\t    stack[SP++] = Cudd_Regular(cuddE(N));\n\t    table->subtables[ord].dead++;\n\t    N = cuddT(N);\n\t} else {\n\t    cuddSatDec(N->ref);\n\t    N = stack[--SP];\n\t}\n    } while (SP != 0);\n\n} /* end of Cudd_IterDerefBdd */\n\n\n/**\n  @brief Decreases the reference count of %BDD node n.\n\n  @details Enqueues node n for later dereferencing. If the queue\n  is full decreases the reference count of the oldest node N to make\n  room for n. If N dies, recursively decreases the reference counts of\n  its children.  It is used to dispose of a %BDD that is currently not\n  needed, but may be useful again in the near future. The dereferencing\n  proper is done as in Cudd_IterDerefBdd.\n\n  @sideeffect None\n\n  @see Cudd_RecursiveDeref Cudd_IterDerefBdd\n\n*/\nvoid\nCudd_DelayedDerefBdd(\n  DdManager * table,\n  DdNode * n)\n{\n    DdNode *N;\n    int ord;\n    DdNodePtr *stack;\n    int SP;\n\n    unsigned int live = table->keys - table->dead;\n    if (live > table->peakLiveNodes) {\n\ttable->peakLiveNodes = live;\n    }\n\n    n = Cudd_Regular(n);\n#ifdef DD_DEBUG\n    assert(n->ref != 0);\n#endif\n\n#ifdef DD_NO_DEATH_ROW\n    N = n;\n#else\n    if (cuddIsConstant(n) || n->ref > 1) {\n#ifdef DD_DEBUG\n\tassert(n->ref != 1 && (!cuddIsConstant(n) || n == DD_ONE(table)));\n#endif\n\tcuddSatDec(n->ref);\n\treturn;\n    }\n\n    N = table->deathRow[table->nextDead];\n\n    if (N != NULL) {\n#endif\n#ifdef DD_DEBUG\n\tassert(!Cudd_IsComplement(N));\n#endif\n\tstack = table->stack;\n\tSP = 1;\n\tdo {\n#ifdef DD_DEBUG\n\t    assert(N->ref != 0);\n#endif\n\t    if (N->ref == 1) {\n\t\tN->ref = 0;\n\t\ttable->dead++;\n#ifdef DD_STATS\n\t\ttable->nodesDropped++;\n#endif\n\t\tord = table->perm[N->index];\n\t\tstack[SP++] = Cudd_Regular(cuddE(N));\n\t\ttable->subtables[ord].dead++;\n\t\tN = cuddT(N);\n\t    } else {\n\t\tcuddSatDec(N->ref);\n\t\tN = stack[--SP];\n\t    }\n\t} while (SP != 0);\n#ifndef DD_NO_DEATH_ROW\n    }\n    table->deathRow[table->nextDead] = n;\n\n    /* Udate insertion point. */\n    table->nextDead++;\n    table->nextDead &= table->deadMask;\n#if 0\n    if (table->nextDead == table->deathRowDepth) {\n\tif (table->deathRowDepth < table->looseUpTo / 2) {\n\t    extern void (*MMoutOfMemory)(size_t);\n\t    void (*saveHandler)(size_t) = MMoutOfMemory;\n\t    DdNodePtr *newRow;\n\t    MMoutOfMemory = table->outOfMemCallback;\n\t    newRow = REALLOC(DdNodePtr,table->deathRow,2*table->deathRowDepth);\n\t    MMoutOfMemory = saveHandler;\n\t    if (newRow == NULL) {\n\t\ttable->nextDead = 0;\n\t    } else {\n\t\tint i;\n\t\ttable->memused += table->deathRowDepth;\n\t\ti = table->deathRowDepth;\n\t\ttable->deathRowDepth <<= 1;\n\t\tfor (; i < table->deathRowDepth; i++) {\n\t\t    newRow[i] = NULL;\n\t\t}\n\t\ttable->deadMask = table->deathRowDepth - 1;\n\t\ttable->deathRow = newRow;\n\t    }\n\t} else {\n\t    table->nextDead = 0;\n\t}\n    }\n#endif\n#endif\n\n} /* end of Cudd_DelayedDerefBdd */\n\n\n/**\n  @brief Decreases the reference count of %ZDD node n.\n\n  @details If n dies, recursively decreases the reference counts of\n  its children.  It is used to dispose of a %ZDD that is no longer\n  needed.\n\n  @sideeffect None\n\n  @see Cudd_Deref Cudd_Ref Cudd_RecursiveDeref\n\n*/\nvoid\nCudd_RecursiveDerefZdd(\n  DdManager * table,\n  DdNode * n)\n{\n    DdNode *N;\n    int ord;\n    DdNodePtr *stack = table->stack;\n    int SP = 1;\n\n    N = n;\n\n    do {\n#ifdef DD_DEBUG\n\tassert(N->ref != 0);\n#endif\n\n\tcuddSatDec(N->ref);\n    \n\tif (N->ref == 0) {\n\t    table->deadZ++;\n#ifdef DD_STATS\n\t    table->nodesDropped++;\n#endif\n#ifdef DD_DEBUG\n\t    assert(!cuddIsConstant(N));\n#endif\n\t    ord = table->permZ[N->index];\n\t    stack[SP++] = cuddE(N);\n\t    table->subtableZ[ord].dead++;\n\t    N = cuddT(N);\n\t} else {\n\t    N = stack[--SP];\n\t}\n    } while (SP != 0);\n\n} /* end of Cudd_RecursiveDerefZdd */\n\n\n/**\n  @brief Decreases the reference count of node.\n\n  @details It is primarily used in recursive procedures to decrease\n  the ref count of a result node before returning it. This\n  accomplishes the goal of removing the protection applied by a\n  previous Cudd_Ref.\n\n  @sideeffect None\n\n  @see Cudd_RecursiveDeref Cudd_RecursiveDerefZdd Cudd_Ref\n\n*/\nvoid\nCudd_Deref(\n  DdNode * node)\n{\n    node = Cudd_Regular(node);\n    cuddSatDec(node->ref);\n\n} /* end of Cudd_Deref */\n\n\n/**\n  @brief Checks the unique table for nodes with non-zero reference\n  counts.\n\n  @details It is normally called before Cudd_Quit to make sure that\n  there are no memory leaks due to missing Cudd_RecursiveDeref's.\n  Takes into account that reference counts may saturate and that the\n  basic constants and the projection functions are referenced by the\n  manager.\n\n  @return the number of nodes with non-zero reference count.\n  (Except for the cases mentioned above.)\n\n  @sideeffect None\n\n*/\nint\nCudd_CheckZeroRef(\n  DdManager * manager)\n{\n    int size;\n    int i, j;\n    int remain;\t/* the expected number of remaining references to one */\n    DdNodePtr *nodelist;\n    DdNode *node;\n    DdNode *sentinel = &(manager->sentinel);\n    DdSubtable *subtable;\n    int count = 0;\n    int index;\n\n#ifndef DD_NO_DEATH_ROW\n    cuddClearDeathRow(manager);\n#endif\n\n    /* First look at the BDD/ADD subtables. */\n    remain = 1; /* reference from the manager */\n    size = manager->size;\n    remain += 2 * size;\t/* reference from the BDD projection functions */\n\n    for (i = 0; i < size; i++) {\n\tsubtable = &(manager->subtables[i]);\n\tnodelist = subtable->nodelist;\n\tfor (j = 0; (unsigned) j < subtable->slots; j++) {\n\t    node = nodelist[j];\n\t    while (node != sentinel) {\n\t\tif (node->ref != 0 && node->ref != DD_MAXREF) {\n\t\t    index = (int) node->index;\n\t\t    if (node != manager->vars[index]) {\n\t\t\tcount++;\n\t\t    } else {\n\t\t\tif (node->ref != 1) {\n\t\t\t    count++;\n\t\t\t}\n\t\t    }\n\t\t}\n\t\tnode = node->next;\n\t    }\n\t}\n    }\n\n    /* Then look at the ZDD subtables. */\n    size = manager->sizeZ;\n    if (size) /* references from ZDD universe */\n\tremain += 2;\n\n    for (i = 0; i < size; i++) {\n\tsubtable = &(manager->subtableZ[i]);\n\tnodelist = subtable->nodelist;\n\tfor (j = 0; (unsigned) j < subtable->slots; j++) {\n\t    node = nodelist[j];\n\t    while (node != NULL) {\n\t\tif (node->ref != 0 && node->ref != DD_MAXREF) {\n\t\t    index = (int) node->index;\n\t\t    if (node == manager->univ[manager->permZ[index]]) {\n\t\t\tif (node->ref > 2) {\n\t\t\t    count++;\n\t\t\t}\n\t\t    } else {\n\t\t\tcount++;\n\t\t    }\n\t\t}\n\t\tnode = node->next;\n\t    }\n\t}\n    }\n\n    /* Now examine the constant table. Plusinfinity, minusinfinity, and\n    ** zero are referenced by the manager. One is referenced by the\n    ** manager, by the ZDD universe, and by all projection functions.\n    ** All other nodes should have no references.\n    */\n    nodelist = manager->constants.nodelist;\n    for (j = 0; (unsigned) j < manager->constants.slots; j++) {\n\tnode = nodelist[j];\n\twhile (node != NULL) {\n\t    if (node->ref != 0 && node->ref != DD_MAXREF) {\n\t\tif (node == manager->one) {\n\t\t    if ((int) node->ref != remain) {\n\t\t\tcount++;\n\t\t    }\n\t\t} else if (node == manager->zero ||\n\t\tnode == manager->plusinfinity ||\n\t\tnode == manager->minusinfinity) {\n\t\t    if (node->ref != 1) {\n\t\t\tcount++;\n\t\t    }\n\t\t} else {\n\t\t    count++;\n\t\t}\n\t    }\n\t    node = node->next;\n\t}\n    }\n    return(count);\n\n} /* end of Cudd_CheckZeroRef */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Brings children of a dead node back.\n\n  @sideeffect None\n\n  @see cuddReclaimZdd\n\n*/\nvoid\ncuddReclaim(\n  DdManager * table,\n  DdNode * n)\n{\n    DdNode *N;\n    int ord;\n    DdNodePtr *stack = table->stack;\n    int SP = 1;\n    double initialDead = table->dead;\n\n    N = Cudd_Regular(n);\n\n#ifdef DD_DEBUG\n    assert(N->ref == 0);\n#endif\n\n    do {\n\tif (N->ref == 0) {\n\t    N->ref = 1;\n\t    table->dead--;\n\t    if (cuddIsConstant(N)) {\n\t\ttable->constants.dead--;\n\t\tN = stack[--SP];\n\t    } else {\n\t\tord = table->perm[N->index];\n\t\tstack[SP++] = Cudd_Regular(cuddE(N));\n\t\ttable->subtables[ord].dead--;\n\t\tN = cuddT(N);\n\t    }\n\t} else {\n\t    cuddSatInc(N->ref);\n\t    N = stack[--SP];\n\t}\n    } while (SP != 0);\n\n    N = Cudd_Regular(n);\n    cuddSatDec(N->ref);\n    table->reclaimed += initialDead - table->dead;\n\n} /* end of cuddReclaim */\n\n\n/**\n  @brief Brings children of a dead %ZDD node back.\n\n  @sideeffect None\n\n  @see cuddReclaim\n\n*/\nvoid\ncuddReclaimZdd(\n  DdManager * table,\n  DdNode * n)\n{\n    DdNode *N;\n    int ord;\n    DdNodePtr *stack = table->stack;\n    int SP = 1;\n\n    N = n;\n\n#ifdef DD_DEBUG\n    assert(N->ref == 0);\n#endif\n\n    do {\n\tcuddSatInc(N->ref);\n\n\tif (N->ref == 1) {\n\t    table->deadZ--;\n\t    table->reclaimed++;\n#ifdef DD_DEBUG\n\t    assert(!cuddIsConstant(N));\n#endif\n\t    ord = table->permZ[N->index];\n\t    stack[SP++] = cuddE(N);\n\t    table->subtableZ[ord].dead--;\n\t    N = cuddT(N);\n\t} else {\n\t    N = stack[--SP];\n\t}\n    } while (SP != 0);\n\n    cuddSatDec(n->ref);\n\n} /* end of cuddReclaimZdd */\n\n\n/**\n  @brief Shrinks the death row.\n\n  @details Shrinks the death row by a factor of four.\n\n  @sideeffect None\n\n  @see cuddClearDeathRow\n\n*/\nvoid\ncuddShrinkDeathRow(\n  DdManager *table)\n{\n#ifndef DD_NO_DEATH_ROW\n    int i;\n\n    if (table->deathRowDepth > 3) {\n\tfor (i = table->deathRowDepth/4; i < table->deathRowDepth; i++) {\n\t    if (table->deathRow[i] == NULL) break;\n\t    Cudd_IterDerefBdd(table,table->deathRow[i]);\n\t    table->deathRow[i] = NULL;\n\t}\n\ttable->deathRowDepth /= 4;\n\ttable->deadMask = table->deathRowDepth - 1;\n\tif ((unsigned) table->nextDead > table->deadMask) {\n\t    table->nextDead = 0;\n\t}\n\ttable->deathRow = REALLOC(DdNodePtr, table->deathRow,\n\t\t\t\t   table->deathRowDepth);\n    }\n#endif\n\n} /* end of cuddShrinkDeathRow */\n\n\n/**\n  @brief Clears the death row.\n\n  @sideeffect None\n\n  @see Cudd_DelayedDerefBdd Cudd_IterDerefBdd Cudd_CheckZeroRef\n  cuddGarbageCollect\n\n*/\nvoid\ncuddClearDeathRow(\n  DdManager *table)\n{\n#ifndef DD_NO_DEATH_ROW\n    int i;\n\n    for (i = 0; i < table->deathRowDepth; i++) {\n\tif (table->deathRow[i] == NULL) break;\n\tCudd_IterDerefBdd(table,table->deathRow[i]);\n\ttable->deathRow[i] = NULL;\n    }\n#ifdef DD_DEBUG\n    for (; i < table->deathRowDepth; i++) {\n\tassert(table->deathRow[i] == NULL);\n    }\n#endif\n    table->nextDead = 0;\n#endif\n\n} /* end of cuddClearDeathRow */\n\n\n/**\n  @brief Checks whether a node is in the death row.\n\n  @return the position of the first occurrence if the node is present;\n  -1 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_DelayedDerefBdd cuddClearDeathRow\n\n*/\nint\ncuddIsInDeathRow(\n  DdManager *dd,\n  DdNode *f)\n{\n#ifndef DD_NO_DEATH_ROW\n    int i;\n\n    for (i = 0; i < dd->deathRowDepth; i++) {\n\tif (f == dd->deathRow[i]) {\n\t    return(i);\n\t}\n    }\n#endif\n\n    return(-1);\n\n} /* end of cuddIsInDeathRow */\n\n\n/**\n  @brief Counts how many times a node is in the death row.\n\n  @sideeffect None\n\n  @see Cudd_DelayedDerefBdd cuddClearDeathRow cuddIsInDeathRow\n\n*/\nint\ncuddTimesInDeathRow(\n  DdManager *dd,\n  DdNode *f)\n{\n    int count = 0;\n#ifndef DD_NO_DEATH_ROW\n    int i;\n\n    for (i = 0; i < dd->deathRowDepth; i++) {\n\tcount += f == dd->deathRow[i];\n    }\n#endif\n\n    return(count);\n\n} /* end of cuddTimesInDeathRow */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n"
  },
  {
    "path": "cudd/cudd/cuddReorder.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for dynamic variable reordering.\n\n  @author Shipra Panda, Bernard Plessier, Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int ddUniqueCompare (void const *ptrX, void const *ptrY);\nstatic Move * ddSwapAny (DdManager *table, int x, int y);\nstatic int ddSiftingAux (DdManager *table, int x, int xLow, int xHigh);\nstatic Move * ddSiftingUp (DdManager *table, int y, int xLow);\nstatic Move * ddSiftingDown (DdManager *table, int x, int xHigh);\nstatic int ddSiftingBackward (DdManager *table, int size, Move *moves);\nstatic int ddReorderPreprocess (DdManager *table);\nstatic int ddReorderPostprocess (DdManager *table);\nstatic int ddShuffle (DdManager *table, int *permutation);\nstatic int ddSiftUp (DdManager *table, int x, int xLow);\nstatic void bddFixTree (DdManager *table, MtrNode *treenode);\nstatic int ddUpdateMtrTree (DdManager *table, MtrNode *treenode, int *perm, int *invperm);\nstatic int ddCheckPermuation (DdManager *table, MtrNode *treenode, int *perm, int *invperm);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Main dynamic reordering routine.\n\n  @details Calls one of the possible reordering procedures:\n  <ul>\n  <li>Swapping\n  <li>Sifting\n  <li>Symmetric Sifting\n  <li>Group Sifting\n  <li>Window Permutation\n  <li>Simulated Annealing\n  <li>Genetic Algorithm\n  <li>Dynamic Programming (exact)\n  </ul>\n  For sifting, symmetric sifting, group sifting, and window\n  permutation it is possible to request reordering to convergence.<p>\n  The core of all methods is the reordering procedure\n  cuddSwapInPlace() which swaps two adjacent variables and is based\n  on Rudell's paper.\n\n  @return 1 in case of success; 0 otherwise. In the case of symmetric\n  sifting (with and without convergence) returns 1 plus the number of\n  symmetric variables, in case of success.\n\n  @sideeffect Changes the variable order for all diagrams and clears\n  the cache.\n\n*/\nint\nCudd_ReduceHeap(\n  DdManager * table /**< %DD manager */,\n  Cudd_ReorderingType heuristic /**< method used for reordering */,\n  int  minsize /**< bound below which no reordering occurs */)\n{\n    DdHook *hook;\n    int\tresult;\n    unsigned int nextDyn;\n#ifdef DD_STATS\n    unsigned int initialSize;\n    unsigned int finalSize;\n#endif\n    unsigned long localTime;\n\n    /* Don't reorder if there are too many dead nodes. */\n    if (table->keys - table->dead < (unsigned) minsize)\n\treturn(1);\n\n    if (heuristic == CUDD_REORDER_SAME) {\n\theuristic = table->autoMethod;\n    }\n    if (heuristic == CUDD_REORDER_NONE) {\n\treturn(1);\n    }\n\n    /* This call to Cudd_ReduceHeap does initiate reordering. Therefore\n    ** we count it.\n    */\n    table->reorderings++;\n\n    localTime = util_cpu_time();\n\n    /* Run the hook functions. */\n    hook = table->preReorderingHook;\n    while (hook != NULL) {\n\tint res = (hook->f)(table, \"BDD\", (void *)heuristic);\n\tif (res == 0) return(0);\n\thook = hook->next;\n    }\n\n    if (!ddReorderPreprocess(table)) return(0);\n    table->ddTotalNumberSwapping = 0;\n\n    if (table->keys > table->peakLiveNodes) {\n\ttable->peakLiveNodes = table->keys;\n    }\n#ifdef DD_STATS\n    initialSize = (int) (table->keys - table->isolated);\n    table->totalNISwaps = 0;\n\n    switch(heuristic) {\n    case CUDD_REORDER_RANDOM:\n    case CUDD_REORDER_RANDOM_PIVOT:\n\t(void) fprintf(table->out,\"#:I_RANDOM  \");\n\tbreak;\n    case CUDD_REORDER_SIFT:\n    case CUDD_REORDER_SIFT_CONVERGE:\n    case CUDD_REORDER_SYMM_SIFT:\n    case CUDD_REORDER_SYMM_SIFT_CONV:\n    case CUDD_REORDER_GROUP_SIFT:\n    case CUDD_REORDER_GROUP_SIFT_CONV:\n\t(void) fprintf(table->out,\"#:I_SIFTING \");\n\tbreak;\n    case CUDD_REORDER_WINDOW2:\n    case CUDD_REORDER_WINDOW3:\n    case CUDD_REORDER_WINDOW4:\n    case CUDD_REORDER_WINDOW2_CONV:\n    case CUDD_REORDER_WINDOW3_CONV:\n    case CUDD_REORDER_WINDOW4_CONV:\n\t(void) fprintf(table->out,\"#:I_WINDOW  \");\n\tbreak;\n    case CUDD_REORDER_ANNEALING:\n\t(void) fprintf(table->out,\"#:I_ANNEAL  \");\n\tbreak;\n    case CUDD_REORDER_GENETIC:\n\t(void) fprintf(table->out,\"#:I_GENETIC \");\n\tbreak;\n    case CUDD_REORDER_LINEAR:\n    case CUDD_REORDER_LINEAR_CONVERGE:\n\t(void) fprintf(table->out,\"#:I_LINSIFT \");\n\tbreak;\n    case CUDD_REORDER_EXACT:\n\t(void) fprintf(table->out,\"#:I_EXACT   \");\n\tbreak;\n    default:\n\treturn(0);\n    }\n    (void) fprintf(table->out,\"%8d: initial size\",initialSize);\n#endif\n\n    /* See if we should use alternate threshold for maximum growth. */\n    if (table->reordCycle && table->reorderings % table->reordCycle == 0) {\n\tdouble saveGrowth = table->maxGrowth;\n\ttable->maxGrowth = table->maxGrowthAlt;\n\tresult = cuddTreeSifting(table,heuristic);\n\ttable->maxGrowth = saveGrowth;\n    } else {\n\tresult = cuddTreeSifting(table,heuristic);\n    }\n\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n\");\n    finalSize = (int) (table->keys - table->isolated);\n    (void) fprintf(table->out,\"#:F_REORDER %8d: final size\\n\",finalSize);\n    (void) fprintf(table->out,\"#:T_REORDER %8g: total time (sec)\\n\",\n\t\t   ((double)(util_cpu_time() - localTime)/1000.0));\n    (void) fprintf(table->out,\"#:N_REORDER %8d: total swaps\\n\",\n\t\t   table->ddTotalNumberSwapping);\n    (void) fprintf(table->out,\"#:M_REORDER %8d: NI swaps\\n\",\n                   table->totalNISwaps);\n#endif\n\n    if (result == 0)\n\treturn(0);\n\n    if (!ddReorderPostprocess(table))\n\treturn(0);\n\n    if (table->realign) {\n\tif (!cuddZddAlignToBdd(table))\n\t    return(0);\n    }\n\n    nextDyn = (table->keys - table->constants.keys + 1) *\n\t      DD_DYN_RATIO + table->constants.keys;\n    if (table->reorderings < 20 || nextDyn > table->nextDyn)\n\ttable->nextDyn = nextDyn;\n    else\n\ttable->nextDyn += 20;\n    if (table->randomizeOrder != 0) {\n        table->nextDyn += Cudd_Random(table) & table->randomizeOrder;\n    }\n    table->reordered = 1;\n\n    /* Run hook functions. */\n    hook = table->postReorderingHook;\n    while (hook != NULL) {\n\tint res = (hook->f)(table, \"BDD\", (void *)(ptruint)localTime);\n\tif (res == 0) return(0);\n\thook = hook->next;\n    }\n    /* Update cumulative reordering time. */\n    table->reordTime += util_cpu_time() - localTime;\n\n    return(result);\n\n} /* end of Cudd_ReduceHeap */\n\n\n/**\n  @brief Reorders variables according to given permutation.\n\n  @details The i-th entry of the permutation array contains the index\n  of the variable that should be brought to the i-th level.  The size\n  of the array should be equal or greater to the number of variables\n  currently in use.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect Changes the variable order for all diagrams and clears\n  the cache.\n\n  @see Cudd_ReduceHeap\n\n*/\nint\nCudd_ShuffleHeap(\n  DdManager * table /**< %DD manager */,\n  int * permutation /**< required variable permutation */)\n{\n\n    int\tresult;\n    int i;\n    int identity = 1;\n    int *perm;\n\n    /* Don't waste time in case of identity permutation. */\n    for (i = 0; i < table->size; i++) {\n\tif (permutation[i] != table->invperm[i]) {\n\t    identity = 0;\n\t    break;\n\t}\n    }\n    if (identity == 1) {\n\treturn(1);\n    }\n    if (!ddReorderPreprocess(table)) return(0);\n    if (table->keys > table->peakLiveNodes) {\n\ttable->peakLiveNodes = table->keys;\n    }\n\n    perm = ALLOC(int, table->size);\n    for (i = 0; i < table->size; i++)\n\tperm[permutation[i]] = i;\n    if (!ddCheckPermuation(table,table->tree,perm,permutation)) {\n\tFREE(perm);\n\treturn(0);\n    }\n    if (!ddUpdateMtrTree(table,table->tree,perm,permutation)) {\n\tFREE(perm);\n\treturn(0);\n    }\n    FREE(perm);\n\n    result = ddShuffle(table,permutation);\n\n    if (!ddReorderPostprocess(table)) return(0);\n\n    return(result);\n\n} /* end of Cudd_ShuffleHeap */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Dynamically allocates a Node.\n\n  @details This procedure is similar to cuddAllocNode in Cudd_Table.c,\n  but it does not attempt garbage collection, because during\n  reordering there are no dead nodes.\n\n  @return a pointer to a new node if successful; NULL is memory is\n  full.\n\n  @sideeffect None\n\n  @see cuddAllocNode\n\n*/\nDdNode *\ncuddDynamicAllocNode(\n  DdManager * table)\n{\n    int     i;\n    DdNodePtr *mem;\n    DdNode *list, *node;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    if (table->nextFree == NULL) {        /* free list is empty */\n\t/* Try to allocate a new block. */\n\tsaveHandler = MMoutOfMemory;\n\tMMoutOfMemory = table->outOfMemCallback;\n\tmem = (DdNodePtr *) ALLOC(DdNode, DD_MEM_CHUNK + 1);\n\tMMoutOfMemory = saveHandler;\n\tif (mem == NULL && table->stash != NULL) {\n\t    FREE(table->stash);\n\t    table->stash = NULL;\n\t    /* Inhibit resizing of tables. */\n\t    table->maxCacheHard = table->cacheSlots - 1;\n\t    table->cacheSlack = - (int) (table->cacheSlots + 1);\n\t    for (i = 0; i < table->size; i++) {\n\t\ttable->subtables[i].maxKeys <<= 2;\n\t    }\n\t    mem = (DdNodePtr *) ALLOC(DdNode,DD_MEM_CHUNK + 1);\n\t}\n\tif (mem == NULL) {\n\t    /* Out of luck. Call the default handler to do\n\t    ** whatever it specifies for a failed malloc.  If this\n\t    ** handler returns, then set error code, print\n\t    ** warning, and return. */\n\t    (*MMoutOfMemory)(sizeof(DdNode)*(DD_MEM_CHUNK + 1));\n\t    table->errorCode = CUDD_MEMORY_OUT;\n#ifdef DD_VERBOSE\n\t    (void) fprintf(table->err,\n\t\t\t   \"cuddDynamicAllocNode: out of memory\");\n\t    (void) fprintf(table->err,\"Memory in use = %lu\\n\",\n\t\t\t   table->memused);\n#endif\n\t    return(NULL);\n\t} else {\t/* successful allocation; slice memory */\n\t    size_t offset;\n\t    table->memused += (DD_MEM_CHUNK + 1) * sizeof(DdNode);\n\t    mem[0] = (DdNode *) table->memoryList;\n\t    table->memoryList = mem;\n\n\t    /* Here we rely on the fact that the size of a DdNode is a\n\t    ** power of 2 and a multiple of the size of a pointer.\n\t    ** If we align one node, all the others will be aligned\n\t    ** as well. */\n\t    offset = (size_t) mem & (sizeof(DdNode) - 1);\n\t    mem += (sizeof(DdNode) - offset) / sizeof(DdNodePtr);\n#ifdef DD_DEBUG\n\t    assert(((size_t) mem & (sizeof(DdNode) - 1)) == 0);\n#endif\n\t    list = (DdNode *) mem;\n\n\t    i = 1;\n\t    do {\n\t\tlist[i - 1].ref = 0;\n\t\tlist[i - 1].next = &list[i];\n\t    } while (++i < DD_MEM_CHUNK);\n\n\t    list[DD_MEM_CHUNK-1].ref = 0;\n\t    list[DD_MEM_CHUNK - 1].next = NULL;\n\n\t    table->nextFree = &list[0];\n\t}\n    } /* if free list empty */\n\n    node = table->nextFree;\n    table->nextFree = node->next;\n    return (node);\n\n} /* end of cuddDynamicAllocNode */\n\n\n/**\n  @brief Implementation of Rudell's sifting algorithm.\n\n  @details Assumes that no dead nodes are present.\n    <ol>\n    <li> Order all the variables according to the number of entries\n    in each unique table.\n    <li> Sift the variable up and down, remembering each time the\n    total size of the %DD heap.\n    <li> Select the best permutation.\n    <li> Repeat 3 and 4 for all variables.\n    </ol>\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddSifting(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\ti;\n    IndexKey *var;\n    int\tsize;\n    int\tx;\n    int\tresult;\n#ifdef DD_STATS\n    int\tpreviousSize;\n#endif\n\n    size = table->size;\n\n    /* Find order in which to sift variables. */\n    var = ALLOC(IndexKey,size);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto cuddSiftingOutOfMem;\n    }\n\n    for (i = 0; i < size; i++) {\n\tx = table->perm[i];\n\tvar[i].index = i;\n\tvar[i].keys = table->subtables[x].keys;\n    }\n\n    util_qsort(var,size,sizeof(IndexKey),ddUniqueCompare);\n\n    /* Now sift. */\n    for (i = 0; i < ddMin(table->siftMaxVar,size); i++) {\n\tif (table->ddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime + table->reordTime\n            > table->timeLimit) {\n            table->autoDyn = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDyn = 0; /* prevent further reordering */\n            break;\n        }\n\tx = table->perm[var[i].index];\n\n\tif (x < lower || x > upper || table->subtables[x].bindVar == 1)\n\t    continue;\n#ifdef DD_STATS\n\tpreviousSize = (int) (table->keys - table->isolated);\n#endif\n\tresult = ddSiftingAux(table, x, lower, upper);\n\tif (!result) goto cuddSiftingOutOfMem;\n#ifdef DD_STATS\n\tif (table->keys < (unsigned) previousSize + table->isolated) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keys > (unsigned) previousSize + table->isolated) {\n\t    (void) fprintf(table->out,\"+\");\t/* should never happen */\n\t    (void) fprintf(table->err,\"\\nSize increased from %d to %u while sifting variable %d\\n\", previousSize, table->keys - table->isolated, var[i].index);\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n    FREE(var);\n\n    return(1);\n\ncuddSiftingOutOfMem:\n\n    if (var != NULL) FREE(var);\n\n    return(0);\n\n} /* end of cuddSifting */\n\n\n/**\n  @brief Reorders variables by a sequence of (non-adjacent) swaps.\n\n  @details Implementation of Plessier's algorithm that reorders\n  variables by a sequence of (non-adjacent) swaps.\n    <ol>\n    <li> Select two variables (RANDOM or HEURISTIC).\n    <li> Permute these variables.\n    <li> If the nodes have decreased accept the permutation.\n    <li> Otherwise reconstruct the original heap.\n    <li> Loop.\n    </ol>\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddSwapping(\n  DdManager * table,\n  int lower,\n  int upper,\n  Cudd_ReorderingType heuristic)\n{\n    int\ti, j;\n    int\tmax, keys;\n    int\tnvars;\n    int\tx, y;\n    int\titerate;\n    int previousSize;\n    Move *moves, *move;\n    int\tpivot = 0;\n    int\tmodulo;\n    int result;\n\n#ifdef DD_DEBUG\n    /* Sanity check */\n    assert(lower >= 0 && upper < table->size && lower <= upper);\n#endif\n\n    nvars = upper - lower + 1;\n    iterate = nvars;\n\n    for (i = 0; i < iterate; i++) {\n\tif (table->ddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n\tif (heuristic == CUDD_REORDER_RANDOM_PIVOT) {\n\t    max = -1;\n\t    for (j = lower; j <= upper; j++) {\n\t\tif ((keys = table->subtables[j].keys) > max) {\n\t\t    max = keys;\n\t\t    pivot = j;\n\t\t}\n\t    }\n\n\t    modulo = upper - pivot;\n\t    if (modulo == 0) {\n\t\ty = pivot;\n\t    } else{\n\t\ty = pivot + 1 + ((int) Cudd_Random(table) % modulo);\n\t    }\n\n\t    modulo = pivot - lower - 1;\n\t    if (modulo < 1) {\n\t\tx = lower;\n\t    } else{\n\t\tdo {\n\t\t    x = (int) Cudd_Random(table) % modulo;\n\t\t} while (x == y);\n\t    }\n\t} else {\n\t    x = ((int) Cudd_Random(table) % nvars) + lower;\n\t    do {\n\t\ty = ((int) Cudd_Random(table) % nvars) + lower;\n\t    } while (x == y);\n\t}\n\tpreviousSize = (int) (table->keys - table->isolated);\n\tmoves = ddSwapAny(table,x,y);\n\tif (moves == NULL) goto cuddSwappingOutOfMem;\n\tresult = ddSiftingBackward(table,previousSize,moves);\n\tif (!result) goto cuddSwappingOutOfMem;\n\twhile (moves != NULL) {\n\t    move = moves->next;\n\t    cuddDeallocMove(table, moves);\n\t    moves = move;\n\t}\n#ifdef DD_STATS\n\tif (table->keys < (unsigned) previousSize + table->isolated) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keys > (unsigned) previousSize + table->isolated) {\n\t    (void) fprintf(table->out,\"+\");\t/* should never happen */\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n#if 0\n\t(void) fprintf(table->out,\"#:t_SWAPPING %8d: tmp size\\n\",\n\t\t       table->keys - table->isolated);\n#endif\n    }\n\n    return(1);\n\ncuddSwappingOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n\n    return(0);\n\n} /* end of cuddSwapping */\n\n\n/**\n  @brief Finds the next subtable with a larger index.\n\n  @return the index.\n\n  @sideeffect None\n\n  @see cuddNextLow\n\n*/\nint\ncuddNextHigh(\n  DdManager * table,\n  int  x)\n{\n    (void) table; /* avoid warning */\n    return(x+1);\n\n} /* end of cuddNextHigh */\n\n\n/**\n  @brief Finds the next subtable with a smaller index.\n\n  @return the index.\n\n  @sideeffect None\n\n  @see cuddNextHigh\n\n*/\nint\ncuddNextLow(\n  DdManager * table,\n  int  x)\n{\n    (void) table; /* avoid warning */\n    return(x-1);\n\n} /* end of cuddNextLow */\n\n\n/**\n  @brief Swaps two adjacent variables.\n\n  @details It assumes that no dead nodes are present on entry to this\n  procedure.  The procedure then guarantees that no dead nodes will be\n  present when it terminates.  cuddSwapInPlace assumes that x &lt; y.\n\n  @return the number of keys in the table if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddSwapInPlace(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    DdNodePtr *xlist, *ylist;\n    int    xindex, yindex;\n    int    xslots, yslots;\n    int    xshift, yshift;\n    int    oldxkeys, oldykeys;\n    int    newxkeys, newykeys;\n    int    comple, newcomplement;\n    int    i;\n    Cudd_VariableType varType;\n    Cudd_LazyGroupType groupType;\n    int    posn;\n    int    isolated;\n    DdNode *f,*f0,*f1,*f01,*f00,*f11,*f10,*newf1,*newf0;\n    DdNode *g,*next;\n    DdNodePtr *previousP;\n    DdNode *tmp;\n    DdNode *sentinel = &(table->sentinel);\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n#ifdef DD_DEBUG\n    int    count,idcheck;\n#endif\n\n#ifdef DD_DEBUG\n    assert(x < y);\n    assert(cuddNextHigh(table,x) == y);\n    assert(table->subtables[x].keys != 0);\n    assert(table->subtables[y].keys != 0);\n    assert(table->subtables[x].dead == 0);\n    assert(table->subtables[y].dead == 0);\n#endif\n\n    table->ddTotalNumberSwapping++;\n\n    /* Get parameters of x subtable. */\n    xindex = table->invperm[x];\n    xlist = table->subtables[x].nodelist;\n    oldxkeys = table->subtables[x].keys;\n    xslots = table->subtables[x].slots;\n    xshift = table->subtables[x].shift;\n\n    /* Get parameters of y subtable. */\n    yindex = table->invperm[y];\n    ylist = table->subtables[y].nodelist;\n    oldykeys = table->subtables[y].keys;\n    yslots = table->subtables[y].slots;\n    yshift = table->subtables[y].shift;\n\n    if (!cuddTestInteract(table,xindex,yindex)) {\n#ifdef DD_STATS\n\ttable->totalNISwaps++;\n#endif\n\tnewxkeys = oldxkeys;\n\tnewykeys = oldykeys;\n    } else {\n\tnewxkeys = 0;\n\tnewykeys = oldykeys;\n\n\t/* Check whether the two projection functions involved in this\n\t** swap are isolated. At the end, we'll be able to tell how many\n\t** isolated projection functions are there by checking only these\n\t** two functions again. This is done to eliminate the isolated\n\t** projection functions from the node count.\n\t*/\n\tisolated = - ((table->vars[xindex]->ref == 1) +\n\t\t     (table->vars[yindex]->ref == 1));\n\n\t/* The nodes in the x layer that do not depend on\n\t** y will stay there; the others are put in a chain.\n\t** The chain is handled as a LIFO; g points to the beginning.\n\t*/\n\tg = NULL;\n\tif ((oldxkeys >= xslots || (unsigned) xslots == table->initSlots) &&\n\t    oldxkeys <= DD_MAX_SUBTABLE_DENSITY * xslots) {\n\t    for (i = 0; i < xslots; i++) {\n\t\tpreviousP = &(xlist[i]);\n\t\tf = *previousP;\n\t\twhile (f != sentinel) {\n\t\t    next = f->next;\n\t\t    f1 = cuddT(f); f0 = cuddE(f);\n\t\t    if (f1->index != (DdHalfWord) yindex &&\n\t\t\tCudd_Regular(f0)->index != (DdHalfWord) yindex) {\n\t\t\t/* stays */\n\t\t\tnewxkeys++;\n\t\t\t*previousP = f;\n\t\t\tpreviousP = &(f->next);\n\t\t    } else {\n\t\t\tf->index = yindex;\n\t\t\tf->next = g;\n\t\t\tg = f;\n\t\t    }\n\t\t    f = next;\n\t\t} /* while there are elements in the collision chain */\n\t\t*previousP = sentinel;\n\t    } /* for each slot of the x subtable */\n\t} else {\t\t/* resize xlist */\n\t    DdNode *h = NULL;\n\t    DdNodePtr *newxlist;\n\t    unsigned int newxslots;\n\t    int newxshift;\n\t    /* Empty current xlist. Nodes that stay go to list h;\n\t    ** nodes that move go to list g. */\n\t    for (i = 0; i < xslots; i++) {\n\t\tf = xlist[i];\n\t\twhile (f != sentinel) {\n\t\t    next = f->next;\n\t\t    f1 = cuddT(f); f0 = cuddE(f);\n\t\t    if (f1->index != (DdHalfWord) yindex &&\n\t\t\tCudd_Regular(f0)->index != (DdHalfWord) yindex) {\n\t\t\t/* stays */\n\t\t\tf->next = h;\n\t\t\th = f;\n\t\t\tnewxkeys++;\n\t\t    } else {\n\t\t\tf->index = yindex;\n\t\t\tf->next = g;\n\t\t\tg = f;\n\t\t    }\n\t\t    f = next;\n\t\t} /* while there are elements in the collision chain */\n\t    } /* for each slot of the x subtable */\n\t    /* Decide size of new subtable. */\n\t    newxshift = xshift;\n\t    newxslots = xslots;\n\t    while ((unsigned) oldxkeys > DD_MAX_SUBTABLE_DENSITY * newxslots) {\n\t\tnewxshift--;\n\t\tnewxslots <<= 1;\n\t    }\n\t    while ((unsigned) oldxkeys < newxslots &&\n\t\t   newxslots > table->initSlots) {\n\t\tnewxshift++;\n\t\tnewxslots >>= 1;\n\t    }\n\t    /* Try to allocate new table. Be ready to back off. */\n\t    saveHandler = MMoutOfMemory;\n\t    MMoutOfMemory = table->outOfMemCallback;\n\t    newxlist = ALLOC(DdNodePtr, newxslots);\n\t    MMoutOfMemory = saveHandler;\n\t    if (newxlist == NULL) {\n\t\t(void) fprintf(table->err, \"Unable to resize subtable %d for lack of memory\\n\", i);\n\t    } else {\n\t\ttable->slots += ((int) newxslots - xslots);\n\t\ttable->minDead = (unsigned)\n\t\t    (table->gcFrac * (double) table->slots);\n\t\ttable->cacheSlack = (int)\n\t\t    ddMin(table->maxCacheHard, DD_MAX_CACHE_TO_SLOTS_RATIO\n\t\t\t  * table->slots) - 2 * (int) table->cacheSlots;\n\t\ttable->memused +=\n\t\t    ((int) newxslots - xslots) * sizeof(DdNodePtr);\n\t\tFREE(xlist);\n\t\txslots =  newxslots;\n\t\txshift = newxshift;\n\t\txlist = newxlist;\n\t    }\n\t    /* Initialize new subtable. */\n\t    for (i = 0; i < xslots; i++) {\n\t\txlist[i] = sentinel;\n\t    }\n\t    /* Move nodes that were parked in list h to their new home. */\n\t    f = h;\n\t    while (f != NULL) {\n\t\tnext = f->next;\n\t\tf1 = cuddT(f);\n\t\tf0 = cuddE(f);\n\t\t/* Check xlist for pair (f11,f01). */\n\t\tposn = ddHash(f1, f0, xshift);\n\t\t/* For each element tmp in collision list xlist[posn]. */\n\t\tpreviousP = &(xlist[posn]);\n\t\ttmp = *previousP;\n\t\twhile (f1 < cuddT(tmp)) {\n\t\t    previousP = &(tmp->next);\n\t\t    tmp = *previousP;\n\t\t}\n\t\twhile (f1 == cuddT(tmp) && f0 < cuddE(tmp)) {\n\t\t    previousP = &(tmp->next);\n\t\t    tmp = *previousP;\n\t\t}\n\t\tf->next = *previousP;\n\t\t*previousP = f;\n\t\tf = next;\n\t    }\n\t}\n\n#ifdef DD_COUNT\n\ttable->swapSteps += oldxkeys - newxkeys;\n#endif\n\t/* Take care of the x nodes that must be re-expressed.\n\t** They form a linked list pointed by g. Their index has been\n\t** already changed to yindex.\n\t*/\n\tf = g;\n\twhile (f != NULL) {\n\t    next = f->next;\n\t    /* Find f1, f0, f11, f10, f01, f00. */\n\t    f1 = cuddT(f);\n#ifdef DD_DEBUG\n\t    assert(!(Cudd_IsComplement(f1)));\n#endif\n\t    if ((int) f1->index == yindex) {\n\t\tf11 = cuddT(f1); f10 = cuddE(f1);\n\t    } else {\n\t\tf11 = f10 = f1;\n\t    }\n#ifdef DD_DEBUG\n\t    assert(!(Cudd_IsComplement(f11)));\n#endif\n\t    f0 = cuddE(f);\n\t    comple = Cudd_IsComplement(f0);\n\t    f0 = Cudd_Regular(f0);\n\t    if ((int) f0->index == yindex) {\n\t\tf01 = cuddT(f0); f00 = cuddE(f0);\n\t    } else {\n\t\tf01 = f00 = f0;\n\t    }\n\t    if (comple) {\n\t\tf01 = Cudd_Not(f01);\n\t\tf00 = Cudd_Not(f00);\n\t    }\n\t    /* Decrease ref count of f1. */\n\t    cuddSatDec(f1->ref);\n\t    /* Create the new T child. */\n\t    if (f11 == f01) {\n\t\tnewf1 = f11;\n\t\tcuddSatInc(newf1->ref);\n\t    } else {\n\t\t/* Check xlist for triple (xindex,f11,f01). */\n\t\tposn = ddHash(f11, f01, xshift);\n\t\t/* For each element newf1 in collision list xlist[posn]. */\n\t\tpreviousP = &(xlist[posn]);\n\t\tnewf1 = *previousP;\n\t\twhile (f11 < cuddT(newf1)) {\n\t\t    previousP = &(newf1->next);\n\t\t    newf1 = *previousP;\n\t\t}\n\t\twhile (f11 == cuddT(newf1) && f01 < cuddE(newf1)) {\n\t\t    previousP = &(newf1->next);\n\t\t    newf1 = *previousP;\n\t\t}\n\t\tif (cuddT(newf1) == f11 && cuddE(newf1) == f01) {\n\t\t    cuddSatInc(newf1->ref);\n\t\t} else { /* no match */\n\t\t    newf1 = cuddDynamicAllocNode(table);\n\t\t    if (newf1 == NULL)\n\t\t\tgoto cuddSwapOutOfMem;\n\t\t    newf1->index = xindex; newf1->ref = 1;\n\t\t    cuddT(newf1) = f11;\n\t\t    cuddE(newf1) = f01;\n\t\t    /* Insert newf1 in the collision list xlist[posn];\n\t\t    ** increase the ref counts of f11 and f01.\n\t\t    */\n\t\t    newxkeys++;\n\t\t    newf1->next = *previousP;\n\t\t    *previousP = newf1;\n\t\t    cuddSatInc(f11->ref);\n\t\t    tmp = Cudd_Regular(f01);\n\t\t    cuddSatInc(tmp->ref);\n\t\t}\n\t    }\n\t    cuddT(f) = newf1;\n#ifdef DD_DEBUG\n\t    assert(!(Cudd_IsComplement(newf1)));\n#endif\n\n\t    /* Do the same for f0, keeping complement dots into account. */\n\t    /* Decrease ref count of f0. */\n\t    tmp = Cudd_Regular(f0);\n\t    cuddSatDec(tmp->ref);\n\t    /* Create the new E child. */\n\t    if (f10 == f00) {\n\t\tnewf0 = f00;\n\t\ttmp = Cudd_Regular(newf0);\n\t\tcuddSatInc(tmp->ref);\n\t    } else {\n\t\t/* make sure f10 is regular */\n\t\tnewcomplement = Cudd_IsComplement(f10);\n\t\tif (newcomplement) {\n\t\t    f10 = Cudd_Not(f10);\n\t\t    f00 = Cudd_Not(f00);\n\t\t}\n\t\t/* Check xlist for triple (xindex,f10,f00). */\n\t\tposn = ddHash(f10, f00, xshift);\n\t\t/* For each element newf0 in collision list xlist[posn]. */\n\t\tpreviousP = &(xlist[posn]);\n\t\tnewf0 = *previousP;\n\t\twhile (f10 < cuddT(newf0)) {\n\t\t    previousP = &(newf0->next);\n\t\t    newf0 = *previousP;\n\t\t}\n\t\twhile (f10 == cuddT(newf0) && f00 < cuddE(newf0)) {\n\t\t    previousP = &(newf0->next);\n\t\t    newf0 = *previousP;\n\t\t}\n\t\tif (cuddT(newf0) == f10 && cuddE(newf0) == f00) {\n\t\t    cuddSatInc(newf0->ref);\n\t\t} else { /* no match */\n\t\t    newf0 = cuddDynamicAllocNode(table);\n\t\t    if (newf0 == NULL)\n\t\t\tgoto cuddSwapOutOfMem;\n\t\t    newf0->index = xindex; newf0->ref = 1;\n\t\t    cuddT(newf0) = f10;\n\t\t    cuddE(newf0) = f00;\n\t\t    /* Insert newf0 in the collision list xlist[posn];\n\t\t    ** increase the ref counts of f10 and f00.\n\t\t    */\n\t\t    newxkeys++;\n\t\t    newf0->next = *previousP;\n\t\t    *previousP = newf0;\n\t\t    cuddSatInc(f10->ref);\n\t\t    tmp = Cudd_Regular(f00);\n\t\t    cuddSatInc(tmp->ref);\n\t\t}\n\t\tif (newcomplement) {\n\t\t    newf0 = Cudd_Not(newf0);\n\t\t}\n\t    }\n\t    cuddE(f) = newf0;\n\n\t    /* Insert the modified f in ylist.\n\t    ** The modified f does not already exists in ylist.\n\t    ** (Because of the uniqueness of the cofactors.)\n\t    */\n\t    posn = ddHash(newf1, newf0, yshift);\n\t    newykeys++;\n\t    previousP = &(ylist[posn]);\n\t    tmp = *previousP;\n\t    while (newf1 < cuddT(tmp)) {\n\t\tpreviousP = &(tmp->next);\n\t\ttmp = *previousP;\n\t    }\n\t    while (newf1 == cuddT(tmp) && newf0 < cuddE(tmp)) {\n\t\tpreviousP = &(tmp->next);\n\t\ttmp = *previousP;\n\t    }\n\t    f->next = *previousP;\n\t    *previousP = f;\n\t    f = next;\n\t} /* while f != NULL */\n\n\t/* GC the y layer. */\n\n\t/* For each node f in ylist. */\n\tfor (i = 0; i < yslots; i++) {\n\t    previousP = &(ylist[i]);\n\t    f = *previousP;\n\t    while (f != sentinel) {\n\t\tnext = f->next;\n\t\tif (f->ref == 0) {\n\t\t    tmp = cuddT(f);\n\t\t    cuddSatDec(tmp->ref);\n\t\t    tmp = Cudd_Regular(cuddE(f));\n\t\t    cuddSatDec(tmp->ref);\n\t\t    cuddDeallocNode(table,f);\n\t\t    newykeys--;\n\t\t} else {\n\t\t    *previousP = f;\n\t\t    previousP = &(f->next);\n\t\t}\n\t\tf = next;\n\t    } /* while f */\n\t    *previousP = sentinel;\n\t} /* for i */\n\n#ifdef DD_DEBUG\n#if 0\n\t(void) fprintf(table->out,\"Swapping %d and %d\\n\",x,y);\n#endif\n\tcount = 0;\n\tidcheck = 0;\n\tfor (i = 0; i < yslots; i++) {\n\t    f = ylist[i];\n\t    while (f != sentinel) {\n\t\tcount++;\n\t\tif (f->index != (DdHalfWord) yindex)\n\t\t    idcheck++;\n\t\tf = f->next;\n\t    }\n\t}\n\tif (count != newykeys) {\n\t    (void) fprintf(table->out,\n\t\t\t   \"Error in finding newykeys\\toldykeys = %d\\tnewykeys = %d\\tactual = %d\\n\",\n\t\t\t   oldykeys,newykeys,count);\n\t}\n\tif (idcheck != 0)\n\t    (void) fprintf(table->out,\n\t\t\t   \"Error in id's of ylist\\twrong id's = %d\\n\",\n\t\t\t   idcheck);\n\tcount = 0;\n\tidcheck = 0;\n\tfor (i = 0; i < xslots; i++) {\n\t    f = xlist[i];\n\t    while (f != sentinel) {\n\t\tcount++;\n\t\tif (f->index != (DdHalfWord) xindex)\n\t\t    idcheck++;\n\t\tf = f->next;\n\t    }\n\t}\n\tif (count != newxkeys) {\n\t    (void) fprintf(table->out,\n\t\t\t   \"Error in finding newxkeys\\toldxkeys = %d \\tnewxkeys = %d \\tactual = %d\\n\",\n\t\t\t   oldxkeys,newxkeys,count);\n\t}\n\tif (idcheck != 0)\n\t    (void) fprintf(table->out,\n\t\t\t   \"Error in id's of xlist\\twrong id's = %d\\n\",\n\t\t\t   idcheck);\n#endif\n\n\tisolated += (table->vars[xindex]->ref == 1) +\n\t\t    (table->vars[yindex]->ref == 1);\n\ttable->isolated += (unsigned int) isolated;\n    }\n\n    /* Set the appropriate fields in table. */\n    table->subtables[x].nodelist = ylist;\n    table->subtables[x].slots = yslots;\n    table->subtables[x].shift = yshift;\n    table->subtables[x].keys = newykeys;\n    table->subtables[x].maxKeys = yslots * DD_MAX_SUBTABLE_DENSITY;\n    i = table->subtables[x].bindVar;\n    table->subtables[x].bindVar = table->subtables[y].bindVar;\n    table->subtables[y].bindVar = i;\n    /* Adjust fields for lazy sifting. */\n    varType = table->subtables[x].varType;\n    table->subtables[x].varType = table->subtables[y].varType;\n    table->subtables[y].varType = varType;\n    i = table->subtables[x].pairIndex;\n    table->subtables[x].pairIndex = table->subtables[y].pairIndex;\n    table->subtables[y].pairIndex = i;\n    i = table->subtables[x].varHandled;\n    table->subtables[x].varHandled = table->subtables[y].varHandled;\n    table->subtables[y].varHandled = i;\n    groupType = table->subtables[x].varToBeGrouped;\n    table->subtables[x].varToBeGrouped = table->subtables[y].varToBeGrouped;\n    table->subtables[y].varToBeGrouped = groupType;\n\n    table->subtables[y].nodelist = xlist;\n    table->subtables[y].slots = xslots;\n    table->subtables[y].shift = xshift;\n    table->subtables[y].keys = newxkeys;\n    table->subtables[y].maxKeys = xslots * DD_MAX_SUBTABLE_DENSITY;\n\n    table->perm[xindex] = y; table->perm[yindex] = x;\n    table->invperm[x] = yindex; table->invperm[y] = xindex;\n\n    table->keys += newxkeys + newykeys - oldxkeys - oldykeys;\n\n    return((int)(table->keys - table->isolated));\n\ncuddSwapOutOfMem:\n    (void) fprintf(table->err,\"Error: cuddSwapInPlace out of memory\\n\");\n\n    return (0);\n\n} /* end of cuddSwapInPlace */\n\n\n/**\n  @brief Reorders %BDD variables according to the order of the %ZDD\n  variables.\n\n  @details This function can be called at the end of %ZDD\n  reordering to insure that the order of the %BDD variables is\n  consistent with the order of the %ZDD variables. The number of %ZDD\n  variables must be a multiple of the number of %BDD variables. Let\n  <code>M</code> be the ratio of the two numbers. cuddBddAlignToZdd\n  then considers the %ZDD variables from <code>M*i</code> to\n  <code>(M+1)*i-1</code> as corresponding to %BDD variable\n  <code>i</code>.  This function should be normally called from\n  Cudd_zddReduceHeap, which clears the cache.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect Changes the %BDD variable order for all diagrams and performs\n  garbage collection of the %BDD unique table.\n\n  @see Cudd_ShuffleHeap Cudd_zddReduceHeap\n\n*/\nint\ncuddBddAlignToZdd(\n  DdManager * table /**< %DD manager */)\n{\n    int *invperm;\t\t/* permutation array */\n    int M;\t\t\t/* ratio of ZDD variables to BDD variables */\n    int i;\t\t\t/* loop index */\n    int result;\t\t\t/* return value */\n\n    /* We assume that a ratio of 0 is OK. */\n    if (table->size == 0)\n\treturn(1);\n\n    M = table->sizeZ / table->size;\n    /* Check whether the number of ZDD variables is a multiple of the\n    ** number of BDD variables.\n    */\n    if (M * table->size != table->sizeZ)\n\treturn(0);\n    /* Create and initialize the inverse permutation array. */\n    invperm = ALLOC(int,table->size);\n    if (invperm == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (i = 0; i < table->sizeZ; i += M) {\n\tint indexZ = table->invpermZ[i];\n\tint index  = indexZ / M;\n\tinvperm[i / M] = index;\n    }\n    /* Eliminate dead nodes. Do not scan the cache again, because we\n    ** assume that Cudd_zddReduceHeap has already cleared it.\n    */\n    cuddGarbageCollect(table,0);\n\n    /* Initialize number of isolated projection functions. */\n    table->isolated = 0;\n    for (i = 0; i < table->size; i++) {\n\tif (table->vars[i]->ref == 1) table->isolated++;\n    }\n\n    /* Initialize the interaction matrix. */\n    result = cuddInitInteract(table);\n    if (result == 0) return(0);\n\n    result = ddShuffle(table, invperm);\n    FREE(invperm);\n    /* Free interaction matrix. */\n    FREE(table->interact);\n    /* Fix the BDD variable group tree. */\n    bddFixTree(table,table->tree);\n    return(result);\n\n} /* end of cuddBddAlignToZdd */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Used to order the variables according to the number of keys\n  in the subtables.\n\n  @return the difference in number of keys between the two variables\n  being compared.\n\n  @sideeffect None\n\n*/\nstatic int\nddUniqueCompare(\n  void const * ptrX,\n  void const * ptrY)\n{\n    IndexKey const * pX = (IndexKey const *) ptrX;\n    IndexKey const * pY = (IndexKey const *) ptrY;\n#if 0\n    /* This would make the order stable, which would be good because of\n     * it would platform-independent, but instability often produces\n     * smaller BDDs.\n     */\n    if (pY->keys == pX->keys) {\n\treturn(pX->index - pY->index);\n    }\n#endif\n    return(pY->keys - pX->keys);\n\n} /* end of ddUniqueCompare */\n\n\n/**\n  @brief Swaps any two variables.\n\n  @return the set of moves.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddSwapAny(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    Move\t*move, *moves;\n    int\t\txRef,yRef;\n    int\t\txNext,yNext;\n    int\t\tsize;\n    int\t\tlimitSize;\n    int\t\ttmp;\n\n    if (x >y) {\n\ttmp = x; x = y; y = tmp;\n    }\n\n    xRef = x; yRef = y;\n\n    xNext = cuddNextHigh(table,x);\n    yNext = cuddNextLow(table,y);\n    moves = NULL;\n    limitSize = (int) (table->keys - table->isolated);\n\n    for (;;) {\n\tif ( xNext == yNext) {\n\t    size = cuddSwapInPlace(table,x,xNext);\n\t    if (size == 0) goto ddSwapAnyOutOfMem;\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddSwapAnyOutOfMem;\n\t    move->x = x;\n\t    move->y = xNext;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    size = cuddSwapInPlace(table,yNext,y);\n\t    if (size == 0) goto ddSwapAnyOutOfMem;\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddSwapAnyOutOfMem;\n\t    move->x = yNext;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    size = cuddSwapInPlace(table,x,xNext);\n\t    if (size == 0) goto ddSwapAnyOutOfMem;\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddSwapAnyOutOfMem;\n\t    move->x = x;\n\t    move->y = xNext;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    tmp = x; x = y; y = tmp;\n\n\t} else if (x == yNext) {\n\n\t    size = cuddSwapInPlace(table,x,xNext);\n\t    if (size == 0) goto ddSwapAnyOutOfMem;\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddSwapAnyOutOfMem;\n\t    move->x = x;\n\t    move->y = xNext;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    tmp = x; x = y; y = tmp;\n\n\t} else {\n\t    size = cuddSwapInPlace(table,x,xNext);\n\t    if (size == 0) goto ddSwapAnyOutOfMem;\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddSwapAnyOutOfMem;\n\t    move->x = x;\n\t    move->y = xNext;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    size = cuddSwapInPlace(table,yNext,y);\n\t    if (size == 0) goto ddSwapAnyOutOfMem;\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddSwapAnyOutOfMem;\n\t    move->x = yNext;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    x = xNext;\n\t    y = yNext;\n\t}\n\n\txNext = cuddNextHigh(table,x);\n\tyNext = cuddNextLow(table,y);\n\tif (xNext > yRef) break;\n\n\tif ((double) size > table->maxGrowth * (double) limitSize) break;\n\tif (size < limitSize) limitSize = size;\n    }\n    if (yNext>=xRef) {\n\tsize = cuddSwapInPlace(table,yNext,y);\n\tif (size == 0) goto ddSwapAnyOutOfMem;\n\tmove = (Move *) cuddDynamicAllocNode(table);\n\tif (move == NULL) goto ddSwapAnyOutOfMem;\n\tmove->x = yNext;\n\tmove->y = y;\n\tmove->size = size;\n\tmove->next = moves;\n\tmoves = move;\n    }\n\n    return(moves);\n\nddSwapAnyOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(NULL);\n\n} /* end of ddSwapAny */\n\n\n/**\n  @brief Given xLow <= x <= xHigh moves x up and down between the\n  boundaries.\n\n  @details Finds the best position and does the required changes.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddSiftingAux(\n  DdManager * table,\n  int  x,\n  int  xLow,\n  int  xHigh)\n{\n\n    Move\t*move;\n    Move\t*moveUp;\t\t/* list of up moves */\n    Move\t*moveDown;\t\t/* list of down moves */\n    int\t\tinitialSize;\n    int\t\tresult;\n\n    initialSize = (int) (table->keys - table->isolated);\n\n    moveDown = NULL;\n    moveUp = NULL;\n\n    if (x == xLow) {\n\tmoveDown = ddSiftingDown(table,x,xHigh);\n\t/* At this point x --> xHigh unless bounding occurred. */\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM) goto ddSiftingAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = ddSiftingBackward(table,initialSize,moveDown);\n\tif (!result) goto ddSiftingAuxOutOfMem;\n\n    } else if (x == xHigh) {\n\tmoveUp = ddSiftingUp(table,x,xLow);\n\t/* At this point x --> xLow unless bounding occurred. */\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM) goto ddSiftingAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = ddSiftingBackward(table,initialSize,moveUp);\n\tif (!result) goto ddSiftingAuxOutOfMem;\n\n    } else if ((x - xLow) > (xHigh - x)) { /* must go down first: shorter */\n\tmoveDown = ddSiftingDown(table,x,xHigh);\n\t/* At this point x --> xHigh unless bounding occurred. */\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM) goto ddSiftingAuxOutOfMem;\n\tif (moveDown != NULL) {\n\t    x = moveDown->y;\n\t}\n\tmoveUp = ddSiftingUp(table,x,xLow);\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM) goto ddSiftingAuxOutOfMem;\n\t/* Move backward and stop at best position */\n\tresult = ddSiftingBackward(table,initialSize,moveUp);\n\tif (!result) goto ddSiftingAuxOutOfMem;\n\n    } else { /* must go up first: shorter */\n\tmoveUp = ddSiftingUp(table,x,xLow);\n\t/* At this point x --> xLow unless bounding occurred. */\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM) goto ddSiftingAuxOutOfMem;\n\tif (moveUp != NULL) {\n\t    x = moveUp->x;\n\t}\n\tmoveDown = ddSiftingDown(table,x,xHigh);\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM) goto ddSiftingAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = ddSiftingBackward(table,initialSize,moveDown);\n\tif (!result) goto ddSiftingAuxOutOfMem;\n    }\n\n    while (moveDown != NULL) {\n\tmove = moveDown->next;\n\tcuddDeallocMove(table, moveDown);\n\tmoveDown = move;\n    }\n    while (moveUp != NULL) {\n\tmove = moveUp->next;\n\tcuddDeallocMove(table, moveUp);\n\tmoveUp = move;\n    }\n\n    return(1);\n\nddSiftingAuxOutOfMem:\n    if (moveDown != (Move *) CUDD_OUT_OF_MEM) {\n\twhile (moveDown != NULL) {\n\t    move = moveDown->next;\n\t    cuddDeallocMove(table, moveDown);\n\t    moveDown = move;\n\t}\n    }\n    if (moveUp != (Move *) CUDD_OUT_OF_MEM) {\n\twhile (moveUp != NULL) {\n\t    move = moveUp->next;\n\t    cuddDeallocMove(table, moveUp);\n\t    moveUp = move;\n\t}\n    }\n\n    return(0);\n\n} /* end of ddSiftingAux */\n\n\n/**\n  @brief Sifts a variable up.\n\n  @details Moves y up until either it reaches the bound (xLow) or the\n  size of the %DD heap increases too much.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddSiftingUp(\n  DdManager * table,\n  int  y,\n  int  xLow)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\tx;\n    int\t\tsize;\n    int\t\tlimitSize;\n    int\t\txindex, yindex;\n    int\t\tisolated;\n    int\t\tL;\t/* lower bound on DD size */\n#ifdef DD_DEBUG\n    int checkL;\n    int z;\n    int zindex;\n#endif\n\n    moves = NULL;\n    yindex = table->invperm[y];\n\n    /* Initialize the lower bound.\n    ** The part of the DD below y will not change.\n    ** The part of the DD above y that does not interact with y will not\n    ** change. The rest may vanish in the best case, except for\n    ** the nodes at level xLow, which will not vanish, regardless.\n    */\n    limitSize = L = (int) (table->keys - table->isolated);\n    for (x = xLow + 1; x < y; x++) {\n\txindex = table->invperm[x];\n\tif (cuddTestInteract(table,xindex,yindex)) {\n\t    isolated = table->vars[xindex]->ref == 1;\n\t    L -= table->subtables[x].keys - isolated;\n\t}\n    }\n    isolated = table->vars[yindex]->ref == 1;\n    L -= (int) table->subtables[y].keys - isolated;\n\n    x = cuddNextLow(table,y);\n    while (x >= xLow && L <= limitSize) {\n\txindex = table->invperm[x];\n#ifdef DD_DEBUG\n\tcheckL = (int) (table->keys - table->isolated);\n\tfor (z = xLow + 1; z < y; z++) {\n\t    zindex = table->invperm[z];\n\t    if (cuddTestInteract(table,zindex,yindex)) {\n\t\tisolated = table->vars[zindex]->ref == 1;\n\t\tcheckL -= (int) table->subtables[z].keys - isolated;\n\t    }\n\t}\n\tisolated = table->vars[yindex]->ref == 1;\n\tcheckL -= (int) table->subtables[y].keys - isolated;\n\tassert(L == checkL);\n#endif\n\tsize = cuddSwapInPlace(table,x,y);\n\tif (size == 0) goto ddSiftingUpOutOfMem;\n\t/* Update the lower bound. */\n\tif (cuddTestInteract(table,xindex,yindex)) {\n\t    isolated = table->vars[xindex]->ref == 1;\n\t    L += (int) table->subtables[y].keys - isolated;\n\t}\n\tmove = (Move *) cuddDynamicAllocNode(table);\n\tif (move == NULL) goto ddSiftingUpOutOfMem;\n\tmove->x = x;\n\tmove->y = y;\n\tmove->size = size;\n\tmove->next = moves;\n\tmoves = move;\n\tif ((double) size > (double) limitSize * table->maxGrowth) break;\n\tif (size < limitSize) limitSize = size;\n\ty = x;\n\tx = cuddNextLow(table,y);\n    }\n    return(moves);\n\nddSiftingUpOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return((Move *) CUDD_OUT_OF_MEM);\n\n} /* end of ddSiftingUp */\n\n\n/**\n  @brief Sifts a variable down.\n\n  @details Moves x down until either it reaches the bound (xHigh) or\n  the size of the %DD heap increases too much.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddSiftingDown(\n  DdManager * table,\n  int  x,\n  int  xHigh)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\ty;\n    int\t\tsize;\n    int\t\tR;\t/* upper bound on node decrease */\n    int\t\tlimitSize;\n    int\t\txindex, yindex;\n    int\t\tisolated;\n#ifdef DD_DEBUG\n    int\t\tcheckR;\n    int\t\tz;\n    int\t\tzindex;\n#endif\n\n    moves = NULL;\n    /* Initialize R */\n    xindex = table->invperm[x];\n    limitSize = size = (int) (table->keys - table->isolated);\n    R = 0;\n    for (y = xHigh; y > x; y--) {\n\tyindex = table->invperm[y];\n\tif (cuddTestInteract(table,xindex,yindex)) {\n\t    isolated = table->vars[yindex]->ref == 1;\n\t    R += (int) table->subtables[y].keys - isolated;\n\t}\n    }\n\n    y = cuddNextHigh(table,x);\n    while (y <= xHigh && size - R < limitSize) {\n#ifdef DD_DEBUG\n\tcheckR = 0;\n\tfor (z = xHigh; z > x; z--) {\n\t    zindex = table->invperm[z];\n\t    if (cuddTestInteract(table,xindex,zindex)) {\n\t\tisolated = table->vars[zindex]->ref == 1;\n\t\tcheckR += (int) table->subtables[z].keys - isolated;\n\t    }\n\t}\n\tassert(R == checkR);\n#endif\n\t/* Update upper bound on node decrease. */\n\tyindex = table->invperm[y];\n\tif (cuddTestInteract(table,xindex,yindex)) {\n\t    isolated = table->vars[yindex]->ref == 1;\n\t    R -= (int) table->subtables[y].keys - isolated;\n\t}\n\tsize = cuddSwapInPlace(table,x,y);\n\tif (size == 0) goto ddSiftingDownOutOfMem;\n\tmove = (Move *) cuddDynamicAllocNode(table);\n\tif (move == NULL) goto ddSiftingDownOutOfMem;\n\tmove->x = x;\n\tmove->y = y;\n\tmove->size = size;\n\tmove->next = moves;\n\tmoves = move;\n\tif ((double) size > (double) limitSize * table->maxGrowth) break;\n\tif (size < limitSize) limitSize = size;\n\tx = y;\n\ty = cuddNextHigh(table,x);\n    }\n    return(moves);\n\nddSiftingDownOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return((Move *) CUDD_OUT_OF_MEM);\n\n} /* end of ddSiftingDown */\n\n\n/**\n  @brief Given a set of moves, returns the %DD heap to the position\n  giving the minimum size.\n\n  @details In case of ties, returns to the closest position giving the\n  minimum size.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddSiftingBackward(\n  DdManager * table,\n  int  size,\n  Move * moves)\n{\n    Move *move;\n    int\tres;\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size < size) {\n\t    size = move->size;\n\t}\n    }\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size == size) return(1);\n\tres = cuddSwapInPlace(table,(int)move->x,(int)move->y);\n\tif (!res) return(0);\n    }\n\n    return(1);\n\n} /* end of ddSiftingBackward */\n\n\n/**\n  @brief Prepares the %DD heap for dynamic reordering.\n\n  @details Does garbage collection, to guarantee that there are no\n  dead nodes; clears the cache, which is invalidated by dynamic\n  reordering; initializes the number of isolated projection functions;\n  and initializes the interaction matrix.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddReorderPreprocess(\n  DdManager * table)\n{\n    int i;\n    int res;\n\n    /* Clear the cache. */\n    cuddCacheFlush(table);\n    cuddLocalCacheClearAll(table);\n\n    /* Eliminate dead nodes. Do not scan the cache again. */\n    cuddGarbageCollect(table,0);\n\n    /* Initialize number of isolated projection functions. */\n    table->isolated = 0;\n    for (i = 0; i < table->size; i++) {\n\tif (table->vars[i]->ref == 1) table->isolated++;\n    }\n\n    /* Initialize the interaction matrix. */\n    res = cuddInitInteract(table);\n    if (res == 0) return(0);\n\n    return(1);\n\n} /* end of ddReorderPreprocess */\n\n\n/**\n  @brief Cleans up at the end of reordering.\n\n  @sideeffect None\n\n*/\nstatic int\nddReorderPostprocess(\n  DdManager * table)\n{\n\n#ifdef DD_VERBOSE\n    (void) fflush(table->out);\n#endif\n\n    /* Free interaction matrix. */\n    FREE(table->interact);\n\n    return(1);\n\n} /* end of ddReorderPostprocess */\n\n\n/**\n  @brief Reorders variables according to a given permutation.\n\n  @details The i-th permutation array contains the index of the\n  variable that should be brought to the i-th level. ddShuffle assumes\n  that no dead nodes are present and that the interaction matrix is\n  properly initialized.  The reordering is achieved by a series of\n  upward sifts.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddShuffle(\n  DdManager * table,\n  int * permutation)\n{\n    int\t\tindex;\n    int\t\tlevel;\n    int\t\tposition;\n    int\t\tnumvars;\n    int\t\tresult;\n#ifdef DD_STATS\n    unsigned long localTime;\n    int\t\tinitialSize;\n    int\t\tfinalSize;\n    int\t\tpreviousSize;\n#endif\n\n    table->ddTotalNumberSwapping = 0;\n#ifdef DD_STATS\n    localTime = util_cpu_time();\n    initialSize = table->keys - table->isolated;\n    (void) fprintf(table->out,\"#:I_SHUFFLE %8d: initial size\\n\",\n\t\t   initialSize);\n    table->totalNISwaps = 0;\n#endif\n\n    numvars = table->size;\n\n    for (level = 0; level < numvars; level++) {\n\tindex = permutation[level];\n\tposition = table->perm[index];\n#ifdef DD_STATS\n\tpreviousSize = table->keys - table->isolated;\n#endif\n\tresult = ddSiftUp(table,position,level);\n\tif (!result) return(0);\n#ifdef DD_STATS\n\tif (table->keys < (unsigned) previousSize + table->isolated) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keys > (unsigned) previousSize + table->isolated) {\n\t    (void) fprintf(table->out,\"+\");\t/* should never happen */\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n\");\n    finalSize = table->keys - table->isolated;\n    (void) fprintf(table->out,\"#:F_SHUFFLE %8d: final size\\n\",finalSize);\n    (void) fprintf(table->out,\"#:T_SHUFFLE %8g: total time (sec)\\n\",\n\t((double)(util_cpu_time() - localTime)/1000.0));\n    (void) fprintf(table->out,\"#:N_SHUFFLE %8d: total swaps\\n\",\n\t\t   table->ddTotalNumberSwapping);\n    (void) fprintf(table->out,\"#:M_SHUFFLE %8d: NI swaps\\n\",\n                   table->totalNISwaps);\n#endif\n\n    return(1);\n\n} /* end of ddShuffle */\n\n\n/**\n  @brief Moves one variable up.\n\n  @details Takes a variable from position x and sifts it up to\n  position xLow;  xLow should be less than or equal to x.\n\n  @return 1 if successful; 0 otherwise\n\n  @sideeffect None\n\n*/\nstatic int\nddSiftUp(\n  DdManager * table,\n  int  x,\n  int  xLow)\n{\n    int        y;\n    int        size;\n\n    y = cuddNextLow(table,x);\n    while (y >= xLow) {\n\tsize = cuddSwapInPlace(table,y,x);\n\tif (size == 0) {\n\t    return(0);\n\t}\n\tx = y;\n\ty = cuddNextLow(table,x);\n    }\n    return(1);\n\n} /* end of ddSiftUp */\n\n\n/**\n  @brief Fixes the %BDD variable group tree after a shuffle.\n\n  @details Assumes that the order of the variables in a terminal node\n  has not been changed.\n\n  @sideeffect Changes the %BDD variable group tree.\n\n*/\nstatic void\nbddFixTree(\n  DdManager * table,\n  MtrNode * treenode)\n{\n    if (treenode == NULL) return;\n    treenode->low = ((int) treenode->index < table->size) ?\n\t(MtrHalfWord) table->perm[treenode->index] : treenode->index;\n    if (treenode->child != NULL) {\n\tbddFixTree(table, treenode->child);\n    }\n    if (treenode->younger != NULL)\n\tbddFixTree(table, treenode->younger);\n    if (treenode->parent != NULL && treenode->low < treenode->parent->low) {\n\ttreenode->parent->low = treenode->low;\n\ttreenode->parent->index = treenode->index;\n    }\n    return;\n\n} /* end of bddFixTree */\n\n\n/**\n  @brief Updates the %BDD variable group tree before a shuffle.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Changes the %BDD variable group tree.\n\n*/\nstatic int\nddUpdateMtrTree(\n  DdManager * table,\n  MtrNode * treenode,\n  int * perm,\n  int * invperm)\n{\n    unsigned int i, size;\n    int index, level, minLevel, maxLevel, minIndex;\n\n    if (treenode == NULL) return(1);\n\n    minLevel = CUDD_MAXINDEX;\n    maxLevel = 0;\n    minIndex = -1;\n    /* i : level */\n    for (i = treenode->low; i < treenode->low + treenode->size; i++) {\n\tindex = table->invperm[i];\n\tlevel = perm[index];\n\tif (level < minLevel) {\n\t    minLevel = level;\n\t    minIndex = index;\n\t}\n\tif (level > maxLevel)\n\t    maxLevel = level;\n    }\n    size = maxLevel - minLevel + 1;\n    if (minIndex == -1) return(0);\n    if (size == treenode->size) {\n\ttreenode->low = minLevel;\n\ttreenode->index = minIndex;\n    } else {\n\treturn(0);\n    }\n\n    if (treenode->child != NULL) {\n\tif (!ddUpdateMtrTree(table, treenode->child, perm, invperm))\n\t    return(0);\n    }\n    if (treenode->younger != NULL) {\n\tif (!ddUpdateMtrTree(table, treenode->younger, perm, invperm))\n\t    return(0);\n    }\n    return(1);\n}\n\n\n/**\n  @brief Checks the %BDD variable group tree before a shuffle.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Changes the %BDD variable group tree.\n\n*/\nstatic int\nddCheckPermuation(\n  DdManager * table,\n  MtrNode * treenode,\n  int * perm,\n  int * invperm)\n{\n    unsigned int i, size;\n    int index, level, minLevel, maxLevel;\n\n    if (treenode == NULL) return(1);\n\n    minLevel = table->size;\n    maxLevel = 0;\n    /* i : level */\n    for (i = treenode->low; i < treenode->low + treenode->size; i++) {\n\tindex = table->invperm[i];\n\tlevel = perm[index];\n\tif (level < minLevel)\n\t    minLevel = level;\n\tif (level > maxLevel)\n\t    maxLevel = level;\n    }\n    size = maxLevel - minLevel + 1;\n    if (size != treenode->size)\n\treturn(0);\n\n    if (treenode->child != NULL) {\n\tif (!ddCheckPermuation(table, treenode->child, perm, invperm))\n\t    return(0);\n    }\n    if (treenode->younger != NULL) {\n\tif (!ddCheckPermuation(table, treenode->younger, perm, invperm))\n\t    return(0);\n    }\n    return(1);\n}\n"
  },
  {
    "path": "cudd/cudd/cuddSat.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for the solution of satisfiability related problems.\n\n  @author Seh-Woong Jeong, Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define\tDD_BIGGY\t100000000\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n   @brief Type of item stored in memoization table.\n*/\ntypedef struct cuddPathPair {\n    int\tpos;\n    int\tneg;\n} cuddPathPair;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#define WEIGHT(weight, col)\t((weight) == NULL ? 1 : weight[col])\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic enum st_retval freePathPair (void *key, void *value, void *arg);\nstatic cuddPathPair getShortest (DdManager *dd, DdNode *root, int *cost, int *support, st_table *visited);\nstatic DdNode * getPath (DdManager *manager, st_table *visited, DdNode *f, int *weight, int cost);\nstatic cuddPathPair getLargest (DdManager *dd, DdNode *root, st_table *visited);\nstatic DdNode * getCube (DdManager *manager, st_table *visited, DdNode *f, int cost);\nstatic DdNode * ddBddMaximallyExpand(DdManager *dd, DdNode *lb, DdNode *ub, DdNode *f);\nstatic int ddBddShortestPathUnate(DdManager *dd, DdNode *f, int *phases, st_table *table);\nstatic DdNode * ddGetLargestCubeUnate(DdManager *dd, DdNode *f, int *phases, st_table *table);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Returns the value of a %DD for a given variable assignment.\n\n  @details The variable assignment is passed in an array of int's,\n  that should specify a zero or a one for each variable in the support\n  of the function.\n\n  @return a pointer to a constant node. No new nodes are produced.\n\n  @sideeffect None\n\n  @see Cudd_bddLeq Cudd_addEvalConst\n\n*/\nDdNode *\nCudd_Eval(\n  DdManager * dd,\n  DdNode * f,\n  int * inputs)\n{\n    int comple;\n    DdNode *ptr;\n\n    (void) dd; /* avoid warning */\n    comple = Cudd_IsComplement(f);\n    ptr = Cudd_Regular(f);\n\n    while (!cuddIsConstant(ptr)) {\n\tif (inputs[ptr->index] == 1) {\n\t    ptr = cuddT(ptr);\n\t} else {\n\t    comple ^= Cudd_IsComplement(cuddE(ptr));\n\t    ptr = Cudd_Regular(cuddE(ptr));\n\t}\n    }\n    return(Cudd_NotCond(ptr,comple));\n\n} /* end of Cudd_Eval */\n\n\n/**\n  @brief Finds a shortest path in a %DD.\n\n  @details f is the %DD we want to get the shortest path for;\n  weight\\[i\\] is the weight of the THEN arc coming from the node whose\n  index is i. If weight is NULL, then unit weights are assumed for all\n  THEN arcs. All ELSE arcs have 0 weight.  If non-NULL, both weight\n  and support should point to arrays with at least as many entries as\n  there are variables in the manager.\n\n  @return the shortest path as the %BDD of a cube.\n\n  @sideeffect support contains on return the true support of f.\n  If support is NULL on entry, then Cudd_ShortestPath does not compute\n  the true support info. length contains the length of the path.\n\n  @see Cudd_ShortestLength Cudd_LargestCube\n\n*/\nDdNode *\nCudd_ShortestPath(\n  DdManager * manager,\n  DdNode * f,\n  int * weight,\n  int * support,\n  int * length)\n{\n    DdNode\t*F;\n    st_table\t*visited;\n    DdNode\t*sol;\n    cuddPathPair *rootPair;\n    int\t\tcomplement, cost;\n    int\t\ti;\n\n    DdNode *one = DD_ONE(manager);\n    DdNode *zero = DD_ZERO(manager);\n\n    /* Initialize support. Support does not depend on variable order.\n    ** Hence, it does not need to be reinitialized if reordering occurs.\n    */\n    if (support) {\n      for (i = 0; i < manager->size; i++) {\n\tsupport[i] = 0;\n      }\n    }\n\n    if (f == Cudd_Not(one) || f == zero) {\n      *length = DD_BIGGY;\n      return(Cudd_Not(one));\n    }\n    /* From this point on, a path exists. */\n\n    do {\n\tmanager->reordered = 0;\n\n\t/* Initialize visited table. */\n\tvisited = st_init_table(st_ptrcmp, st_ptrhash);\n\n\t/* Now get the length of the shortest path(s) from f to 1. */\n\t(void) getShortest(manager, f, weight, support, visited);\n\n\tcomplement = Cudd_IsComplement(f);\n\n\tF = Cudd_Regular(f);\n\n\tif (!st_lookup(visited, F, (void **) &rootPair)) return(NULL);\n\n\tif (complement) {\n\t  cost = rootPair->neg;\n\t} else {\n\t  cost = rootPair->pos;\n\t}\n\n\t/* Recover an actual shortest path. */\n\tsol = getPath(manager,visited,f,weight,cost);\n\n\tst_foreach(visited, freePathPair, NULL);\n\tst_free_table(visited);\n\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    *length = cost;\n    return(sol);\n\n} /* end of Cudd_ShortestPath */\n\n\n/**\n  @brief Finds a largest cube in a %DD.\n\n  @details f is the %DD we want to get the largest cube for. The\n  problem is translated into the one of finding a shortest path in f,\n  when both THEN and ELSE arcs are assumed to have unit length. This\n  yields a largest cube in the disjoint cover corresponding to the\n  %DD. Therefore, it is not necessarily the largest implicant of f.\n\n  @return the largest cube as a %BDD.\n\n  @sideeffect The number of literals of the cube is returned in the location\n  pointed by length if it is non-null.\n\n  @see Cudd_ShortestPath\n\n*/\nDdNode *\nCudd_LargestCube(\n  DdManager * manager,\n  DdNode * f,\n  int * length)\n{\n    DdNode\t*F;\n    st_table\t*visited;\n    DdNode\t*sol;\n    cuddPathPair *rootPair;\n    int\t\tcomplement, cost;\n\n    DdNode *one = DD_ONE(manager);\n    DdNode *zero = DD_ZERO(manager);\n\n    if (f == Cudd_Not(one) || f == zero) {\n\tif (length != NULL) {\n            *length = DD_BIGGY;\n        }\n\treturn(Cudd_Not(one));\n    }\n    /* From this point on, a path exists. */\n\n    do {\n\tmanager->reordered = 0;\n\n\t/* Initialize visited table. */\n\tvisited = st_init_table(st_ptrcmp, st_ptrhash);\n\n\t/* Now get the length of the shortest path(s) from f to 1. */\n\t(void) getLargest(manager, f, visited);\n\n\tcomplement = Cudd_IsComplement(f);\n\n\tF = Cudd_Regular(f);\n\n\tif (!st_lookup(visited, F, (void **) &rootPair)) return(NULL);\n\n\tif (complement) {\n\t  cost = rootPair->neg;\n\t} else {\n\t  cost = rootPair->pos;\n\t}\n\n\t/* Recover an actual shortest path. */\n\tsol = getCube(manager,visited,f,cost);\n\n\tst_foreach(visited, freePathPair, NULL);\n\tst_free_table(visited);\n\n    } while (manager->reordered == 1);\n\n    if (length != NULL) {\n        *length = cost;\n    }\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n    return(sol);\n\n} /* end of Cudd_LargestCube */\n\n\n/**\n  @brief Find the length of the shortest path(s) in a %DD.\n\n  @details f is the %DD we want to get the shortest path for;\n  weight\\[i\\] is the weight of the THEN edge coming from the node\n  whose index is i. All ELSE edges have 0 weight.\n\n  @return the length of the shortest path(s) if such a path is found;\n  a large number if the function is identically 0, and CUDD_OUT_OF_MEM\n  in case of failure.\n\n  @sideeffect None\n\n  @see Cudd_ShortestPath\n\n*/\nint\nCudd_ShortestLength(\n  DdManager * manager,\n  DdNode * f,\n  int * weight)\n{\n    DdNode\t*F;\n    st_table\t*visited;\n    cuddPathPair *my_pair;\n    int\t\tcomplement, cost;\n\n    DdNode *one = DD_ONE(manager);\n    DdNode *zero = DD_ZERO(manager);\n\n    if (f == Cudd_Not(one) || f == zero) {\n\treturn(DD_BIGGY);\n    }\n\n    /* From this point on, a path exists. */\n    /* Initialize visited table and support. */\n    visited = st_init_table(st_ptrcmp, st_ptrhash);\n\n    /* Now get the length of the shortest path(s) from f to 1. */\n    (void) getShortest(manager, f, weight, NULL, visited);\n\n    complement = Cudd_IsComplement(f);\n\n    F = Cudd_Regular(f);\n\n    if (!st_lookup(visited, F, (void **) &my_pair)) return(CUDD_OUT_OF_MEM);\n    \n    if (complement) {\n\tcost = my_pair->neg;\n    } else {\n\tcost = my_pair->pos;\n    }\n\n    st_foreach(visited, freePathPair, NULL);\n    st_free_table(visited);\n\n    return(cost);\n\n} /* end of Cudd_ShortestLength */\n\n\n/**\n  @brief Checks whether a %BDD is negative unate in a\n  variable.\n\n  @details Determines whether the function represented by %BDD f is\n  negative unate (monotonic decreasing) in variable i.  This function\n  does not generate any new nodes.\n\n  @return the constant one is f is unate and the (logical) constant\n  zero if it is not.\n\n  @sideeffect None\n\n  @see Cudd_Increasing\n\n*/\nDdNode *\nCudd_Decreasing(\n  DdManager * dd,\n  DdNode * f,\n  int  i)\n{\n    int topf, level;\n    DdNode *F, *fv, *fvn, *res;\n    DD_CTFP cacheOp;\n\n    statLine(dd);\n#ifdef DD_DEBUG\n    assert(0 <= i && i < dd->size);\n#endif\n\n    F = Cudd_Regular(f);\n    topf = cuddI(dd,F->index);\n\n    /* Check terminal case. If topf > i, f does not depend on var.\n    ** Therefore, f is unate in i.\n    */\n    level = (unsigned) dd->perm[i];\n    if (topf > level) {\n\treturn(DD_ONE(dd));\n    }\n\n    /* From now on, f is not constant. */\n\n    /* Check cache. */\n    cacheOp = (DD_CTFP) Cudd_Decreasing;\n    res = cuddCacheLookup2(dd,cacheOp,f,dd->vars[i]);\n    if (res != NULL) {\n\treturn(res);\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Compute cofactors. */\n    fv = cuddT(F); fvn = cuddE(F);\n    if (F != f) {\n\tfv = Cudd_Not(fv);\n\tfvn = Cudd_Not(fvn);\n    }\n\n    if (topf == level) {\n\t/* Special case: if fv is regular, fv(1,...,1) = 1;\n\t** If in addition fvn is complemented, fvn(1,...,1) = 0.\n\t** But then f(1,1,...,1) > f(0,1,...,1). Hence f is not\n\t** monotonic decreasing in i.\n\t*/\n\tif (!Cudd_IsComplement(fv) && Cudd_IsComplement(fvn)) {\n\t    return(Cudd_Not(DD_ONE(dd)));\n\t}\n\tres = Cudd_bddLeq(dd,fv,fvn) ? DD_ONE(dd) : Cudd_Not(DD_ONE(dd));\n    } else {\n\tres = Cudd_Decreasing(dd,fv,i);\n\tif (res == DD_ONE(dd)) {\n\t    res = Cudd_Decreasing(dd,fvn,i);\n\t}\n    }\n\n    cuddCacheInsert2(dd,cacheOp,f,dd->vars[i],res);\n    return(res);\n\n} /* end of Cudd_Decreasing */\n\n\n/**\n  @brief Checks whether a %BDD is positive unate in a variable.\n\n  @details Determines whether the function represented by %BDD f is\n  positive unate (monotonic increasing) in variable i. It is based on\n  Cudd_Decreasing and the fact that f is monotonic increasing in i if\n  and only if its complement is monotonic decreasing in i.\n\n  @sideeffect None\n\n  @see Cudd_Decreasing\n\n*/\nDdNode *\nCudd_Increasing(\n  DdManager * dd,\n  DdNode * f,\n  int  i)\n{\n    return(Cudd_Decreasing(dd,Cudd_Not(f),i));\n\n} /* end of Cudd_Increasing */\n\n\n/**\n  @brief Tells whether F and G are identical wherever D is 0.\n\n  @details F and G are either two ADDs or two BDDs.  D is either a 0-1\n  %ADD or a %BDD.  No new nodes are created.\n\n  @return 1 if F and G are equivalent, and 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddLeqUnless\n\n*/\nint\nCudd_EquivDC(\n  DdManager * dd,\n  DdNode * F,\n  DdNode * G,\n  DdNode * D)\n{\n    DdNode *tmp, *One, *Gr, *Dr;\n    DdNode *Fv, *Fvn, *Gv, *Gvn, *Dv, *Dvn;\n    int res;\n    int flevel, glevel, dlevel, top;\n\n    One = DD_ONE(dd);\n\n    statLine(dd);\n    /* Check terminal cases. */\n    if (D == One || F == G) return(1);\n    if (D == Cudd_Not(One) || D == DD_ZERO(dd) || F == Cudd_Not(G)) return(0);\n\n    /* From now on, D is non-constant. */\n\n    /* Normalize call to increase cache efficiency. */\n    if (F > G) {\n\ttmp = F;\n\tF = G;\n\tG = tmp;\n    }\n    if (Cudd_IsComplement(F)) {\n\tF = Cudd_Not(F);\n\tG = Cudd_Not(G);\n    }\n\n    /* From now on, F is regular. */\n\n    /* Check cache. */\n    tmp = cuddCacheLookup(dd,DD_EQUIV_DC_TAG,F,G,D);\n    if (tmp != NULL) return(tmp == One);\n\n    /* Find splitting variable. */\n    flevel = cuddI(dd,F->index);\n    Gr = Cudd_Regular(G);\n    glevel = cuddI(dd,Gr->index);\n    top = ddMin(flevel,glevel);\n    Dr = Cudd_Regular(D);\n    dlevel = dd->perm[Dr->index];\n    top = ddMin(top,dlevel);\n\n    /* Compute cofactors. */\n    if (top == flevel) {\n\tFv = cuddT(F);\n\tFvn = cuddE(F);\n    } else {\n\tFv = Fvn = F;\n    }\n    if (top == glevel) {\n\tGv = cuddT(Gr);\n\tGvn = cuddE(Gr);\n\tif (G != Gr) {\n\t    Gv = Cudd_Not(Gv);\n\t    Gvn = Cudd_Not(Gvn);\n\t}\n    } else {\n\tGv = Gvn = G;\n    }\n    if (top == dlevel) {\n\tDv = cuddT(Dr);\n\tDvn = cuddE(Dr);\n\tif (D != Dr) {\n\t    Dv = Cudd_Not(Dv);\n\t    Dvn = Cudd_Not(Dvn);\n\t}\n    } else {\n\tDv = Dvn = D;\n    }\n\n    /* Solve recursively. */\n    res = Cudd_EquivDC(dd,Fv,Gv,Dv);\n    if (res != 0) {\n\tres = Cudd_EquivDC(dd,Fvn,Gvn,Dvn);\n    }\n    cuddCacheInsert(dd,DD_EQUIV_DC_TAG,F,G,D,(res) ? One : Cudd_Not(One));\n\n    return(res);\n\n} /* end of Cudd_EquivDC */\n\n\n/**\n  @brief Tells whether f is less than of equal to G unless D is 1.\n\n  @details f, g, and D are BDDs.  No new nodes are created.\n\n  @return 1 if f is less than of equal to G, and 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_EquivDC Cudd_bddLeq Cudd_bddIteConstant\n\n*/\nint\nCudd_bddLeqUnless(\n  DdManager *dd,\n  DdNode *f,\n  DdNode *g,\n  DdNode *D)\n{\n    DdNode *tmp, *One, *F, *G;\n    DdNode *Ft, *Fe, *Gt, *Ge, *Dt, *De;\n    int res;\n    int flevel, glevel, dlevel, top;\n\n    statLine(dd);\n\n    One = DD_ONE(dd);\n\n    /* Check terminal cases. */\n    if (f == g || g == One || f == Cudd_Not(One) || D == One ||\n\tD == f || D == Cudd_Not(g)) return(1);\n    /* Check for two-operand cases. */\n    if (D == Cudd_Not(One) || D == g || D == Cudd_Not(f))\n\treturn(Cudd_bddLeq(dd,f,g));\n    if (g == Cudd_Not(One) || g == Cudd_Not(f)) return(Cudd_bddLeq(dd,f,D));\n    if (f == One) return(Cudd_bddLeq(dd,Cudd_Not(g),D));\n\n    /* From now on, f, g, and D are non-constant, distinct, and\n    ** non-complementary. */\n\n    /* Normalize call to increase cache efficiency.  We rely on the\n    ** fact that f <= g unless D is equivalent to not(g) <= not(f)\n    ** unless D and to f <= D unless g.  We make sure that D is\n    ** regular, and that at most one of f and g is complemented.  We also\n    ** ensure that when two operands can be swapped, the one with the\n    ** lowest address comes first. */\n\n    if (Cudd_IsComplement(D)) {\n\tif (Cudd_IsComplement(g)) {\n\t    /* Special case: if f is regular and g is complemented,\n\t    ** f(1,...,1) = 1 > 0 = g(1,...,1).  If D(1,...,1) = 0, return 0.\n\t    */\n\t    if (!Cudd_IsComplement(f)) return(0);\n\t    /* !g <= D unless !f  or  !D <= g unless !f */\n\t    tmp = D;\n\t    D = Cudd_Not(f);\n\t    if (g < tmp) {\n\t\tf = Cudd_Not(g);\n\t\tg = tmp;\n\t    } else {\n\t\tf = Cudd_Not(tmp);\n\t    }\n\t} else {\n\t    if (Cudd_IsComplement(f)) {\n\t\t/* !D <= !f unless g  or  !D <= g unless !f */\n\t\ttmp = f;\n\t\tf = Cudd_Not(D);\n\t\tif (tmp < g) {\n\t\t    D = g;\n\t\t    g = Cudd_Not(tmp);\n\t\t} else {\n\t\t    D = Cudd_Not(tmp);\n\t\t}\n\t    } else {\n\t\t/* f <= D unless g  or  !D <= !f unless g */\n\t\ttmp = D;\n\t\tD = g;\n\t\tif (tmp < f) {\n\t\t    g = Cudd_Not(f);\n\t\t    f = Cudd_Not(tmp);\n\t\t} else {\n\t\t    g = tmp;\n\t\t}\n\t    }\n\t}\n    } else {\n\tif (Cudd_IsComplement(g)) {\n\t    if (Cudd_IsComplement(f)) {\n\t\t/* !g <= !f unless D  or  !g <= D unless !f */\n\t\ttmp = f;\n\t\tf = Cudd_Not(g);\n\t\tif (D < tmp) {\n\t\t    g = D;\n\t\t    D = Cudd_Not(tmp);\n\t\t} else {\n\t\t    g = Cudd_Not(tmp);\n\t\t}\n\t    } else {\n\t\t/* f <= g unless D  or  !g <= !f unless D */\n\t\tif (g < f) {\n\t\t    tmp = g;\n\t\t    g = Cudd_Not(f);\n\t\t    f = Cudd_Not(tmp);\n\t\t}\n\t    }\n\t} else {\n\t    /* f <= g unless D  or  f <= D unless g */\n\t    if (D < g) {\n\t\ttmp = D;\n\t\tD = g;\n\t\tg = tmp;\n\t    }\n\t}\n    }\n\n    /* From now on, D is regular. */\n\n    /* Check cache. */\n    tmp = cuddCacheLookup(dd,DD_BDD_LEQ_UNLESS_TAG,f,g,D);\n    if (tmp != NULL) return(tmp == One);\n\n    /* Find splitting variable. */\n    F = Cudd_Regular(f);\n    flevel = dd->perm[F->index];\n    G = Cudd_Regular(g);\n    glevel = dd->perm[G->index];\n    top = ddMin(flevel,glevel);\n    dlevel = dd->perm[D->index];\n    top = ddMin(top,dlevel);\n\n    /* Compute cofactors. */\n    if (top == flevel) {\n\tFt = cuddT(F);\n\tFe = cuddE(F);\n\tif (F != f) {\n\t    Ft = Cudd_Not(Ft);\n\t    Fe = Cudd_Not(Fe);\n\t}\n    } else {\n\tFt = Fe = f;\n    }\n    if (top == glevel) {\n\tGt = cuddT(G);\n\tGe = cuddE(G);\n\tif (G != g) {\n\t    Gt = Cudd_Not(Gt);\n\t    Ge = Cudd_Not(Ge);\n\t}\n    } else {\n\tGt = Ge = g;\n    }\n    if (top == dlevel) {\n\tDt = cuddT(D);\n\tDe = cuddE(D);\n    } else {\n\tDt = De = D;\n    }\n\n    /* Solve recursively. */\n    res = Cudd_bddLeqUnless(dd,Ft,Gt,Dt);\n    if (res != 0) {\n\tres = Cudd_bddLeqUnless(dd,Fe,Ge,De);\n    }\n    cuddCacheInsert(dd,DD_BDD_LEQ_UNLESS_TAG,f,g,D,Cudd_NotCond(One,!res));\n\n    return(res);\n\n} /* end of Cudd_bddLeqUnless */\n\n\n/**\n  @brief Compares two ADDs for equality within tolerance.\n\n  @details Two ADDs are reported to be equal if the maximum difference\n  between them (the sup norm of their difference) is less than or\n  equal to the tolerance parameter.  If parameter <code>pr</code> is\n  positive the first failure is reported to the standard output.\n\n  @return 1 if the two ADDs are equal (within tolerance); 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nCudd_EqualSupNorm(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first %ADD */,\n  DdNode * g /**< second %ADD */,\n  CUDD_VALUE_TYPE  tolerance /**< maximum allowed difference */,\n  int  pr /**< verbosity level */)\n{\n    DdNode *fv, *fvn, *gv, *gvn, *r;\n    int topf, topg;\n\n    statLine(dd);\n    /* Check terminal cases. */\n    if (f == g) return(1);\n    if (cuddIsConstant(f) && cuddIsConstant(g)) {\n\tif (ddEqualVal(cuddV(f),cuddV(g),tolerance)) {\n\t    return(1);\n\t} else {\n\t    if (pr>0) {\n\t\t(void) fprintf(dd->out,\"Offending nodes:\\n\");\n\t\t(void) fprintf(dd->out,\n\t\t\t       \"f: address = %p\\t value = %40.30f\\n\",\n\t\t\t       (void *) f, cuddV(f));\n\t\t(void) fprintf(dd->out,\n\t\t\t       \"g: address = %p\\t value = %40.30f\\n\",\n\t\t\t       (void *) g, cuddV(g));\n\t    }\n\t    return(0);\n\t}\n    }\n\n    /* We only insert the result in the cache if the comparison is\n    ** successful. Therefore, if we hit we return 1. */\n    r = cuddCacheLookup2(dd,(DD_CTFP)Cudd_EqualSupNorm,f,g);\n    if (r != NULL) {\n\treturn(1);\n    }\n\n    /* Compute the cofactors and solve the recursive subproblems. */\n    topf = cuddI(dd,f->index);\n    topg = cuddI(dd,g->index);\n\n    if (topf <= topg) {fv = cuddT(f); fvn = cuddE(f);} else {fv = fvn = f;}\n    if (topg <= topf) {gv = cuddT(g); gvn = cuddE(g);} else {gv = gvn = g;}\n\n    if (!Cudd_EqualSupNorm(dd,fv,gv,tolerance,pr)) return(0);\n    if (!Cudd_EqualSupNorm(dd,fvn,gvn,tolerance,pr)) return(0);\n\n    cuddCacheInsert2(dd,(DD_CTFP)Cudd_EqualSupNorm,f,g,DD_ONE(dd));\n\n    return(1);\n\n} /* end of Cudd_EqualSupNorm */\n\n\n/**\n  @brief Compares two ADDs for equality within relative tolerance.\n\n  @details Same as Cudd_EqualSupNorm but tests for max _relative_\n  difference, i.e., (f-g/f)<e instead of (f-g)<e.\n  \n  @return 1 if the two ADDs are equal (within tolerance); 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nCudd_EqualSupNormRel(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first %ADD */,\n  DdNode * g /**< second %ADD */,\n  CUDD_VALUE_TYPE  tolerance /**< maximum allowed difference */,\n  int  pr /**< verbosity level */)\n{\n    DdNode *fv, *fvn, *gv, *gvn, *r;\n    int topf, topg;\n\n    statLine(dd);\n    /* Check terminal cases. */\n    if (f == g) return(1);\n    if (cuddIsConstant(f) && cuddIsConstant(g)) {\n\tif (ddAbs((cuddV(f) - cuddV(g))/cuddV(f)) < tolerance) {\n\t    return(1);\n\t} else {\n\t    if (pr>0) {\n\t\t(void) fprintf(dd->out,\"Offending nodes:\\n\");\n\t\t(void) fprintf(dd->out,\n\t\t\t       \"f: address = %p\\t value = %40.30f\\n\",\n\t\t\t       (void *) f, cuddV(f));\n\t\t(void) fprintf(dd->out,\n\t\t\t       \"g: address = %p\\t value = %40.30f\\n\",\n\t\t\t       (void *) g, cuddV(g));\n\t    }\n\t    return(0);\n\t}\n    }\n\n    /* We only insert the result in the cache if the comparison is\n    ** successful. Therefore, if we hit we return 1. */\n    r = cuddCacheLookup2(dd,(DD_CTFP)Cudd_EqualSupNormRel,f,g);\n    if (r != NULL) {\n\treturn(1);\n    }\n\n    /* Compute the cofactors and solve the recursive subproblems. */\n    topf = cuddI(dd,f->index);\n    topg = cuddI(dd,g->index);\n\n    if (topf <= topg) {fv = cuddT(f); fvn = cuddE(f);} else {fv = fvn = f;}\n    if (topg <= topf) {gv = cuddT(g); gvn = cuddE(g);} else {gv = gvn = g;}\n\n    if (!Cudd_EqualSupNormRel(dd,fv,gv,tolerance,pr)) return(0);\n    if (!Cudd_EqualSupNormRel(dd,fvn,gvn,tolerance,pr)) return(0);\n\n    cuddCacheInsert2(dd,(DD_CTFP)Cudd_EqualSupNormRel,f,g,DD_ONE(dd));\n\n    return(1);\n\n} /* end of Cudd_EqualSupNormRel */\n\n\n/**\n  @brief Expands cube to a prime implicant of f.\n\n  @return the prime if successful; NULL otherwise.  In particular,\n  NULL is returned if cube is not a real cube or is not an implicant\n  of f.\n\n  @sideeffect None\n\n  @see Cudd_bddMaximallyExpand\n\n*/\nDdNode *\nCudd_bddMakePrime(\n  DdManager *dd /**< manager */,\n  DdNode *cube /**< cube to be expanded */,\n  DdNode *f /**< function of which the cube is to be made a prime */)\n{\n    DdNode *res;\n\n    if (!Cudd_bddLeq(dd,cube,f)) return(NULL);\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddMakePrime(dd,cube,f);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddMakePrime */\n\n\n/**\n  @brief Expands lb to prime implicants of (f and ub).\n\n  @details Expands lb to all prime implicants of (f and ub) that\n  contain lb.  Assumes that lb is contained in ub.\n\n  @return the disjunction of the primes if lb is contained in f;\n  returns the zero %BDD if lb is not contained in f; returns NULL in\n  case of failure.  In particular, NULL is returned if cube is not a\n  real cube or is not an implicant of f.  Returning the disjunction of\n  all prime implicants works because the resulting function is unate.\n\n  @sideeffect None\n\n  @see Cudd_bddMakePrime\n\n*/\nDdNode *\nCudd_bddMaximallyExpand(\n  DdManager *dd /**< manager */,\n  DdNode *lb /**< cube to be expanded */,\n  DdNode *ub /**< upper bound cube */,\n  DdNode *f /**< function against which to expand */)\n{\n    DdNode *res;\n\n    if (!Cudd_bddLeq(dd,lb,ub)) return(NULL);\n\n    do {\n\tdd->reordered = 0;\n\tres = ddBddMaximallyExpand(dd,lb,ub,f);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddMaximallyExpand */\n\n\n/**\n  @brief Find a largest prime implicant of a unate function.\n\n  @details The behavior is undefined if f is not unate.  The third\n  argument is used to determine whether f is unate positive\n  (increasing) or negative (decreasing) in each of the variables in\n  its support.\n\n  @return the %BDD for the prime if succesful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddMaximallyExpand\n\n*/\nDdNode *\nCudd_bddLargestPrimeUnate(\n  DdManager *dd /**< manager */,\n  DdNode *f /**< unate function */,\n  DdNode *phaseBdd /**< cube of the phases */)\n{\n    DdNode *res;\n    int *phases;\n    int retval;\n    st_table *table;\n\n    /* Extract phase vector for quick access. */\n    phases = ALLOC(int, dd->size);\n    if (phases == NULL) return(NULL);\n    retval = Cudd_BddToCubeArray(dd, phaseBdd, phases);\n    if (retval == 0) {\n        FREE(phases);\n        return(NULL);\n    }\n    do {\n        dd->reordered = 0;\n        table = st_init_table(st_ptrcmp,st_ptrhash);\n        if (table == NULL) {\n            FREE(phases);\n            return(NULL);\n        }\n\t(void) ddBddShortestPathUnate(dd, f, phases, table);\n        res = ddGetLargestCubeUnate(dd, f, phases, table);\n        st_free_table(table);\n    } while (dd->reordered == 1);\n\n    FREE(phases);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddLargestPrimeUnate */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddMakePrime.\n\n  @return the prime if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddBddMakePrime(\n  DdManager *dd /**< manager */,\n  DdNode *cube /**< cube to be expanded */,\n  DdNode *f /**< function of which the cube is to be made a prime */)\n{\n    DdNode *scan;\n    DdNode *t, *e;\n    DdNode *res = cube;\n    DdNode *lzero = Cudd_Not(DD_ONE(dd));\n\n    Cudd_Ref(res);\n    scan = cube;\n    while (!Cudd_IsConstantInt(scan)) {\n\tDdNode *reg = Cudd_Regular(scan);\n\tDdNode *var = dd->vars[reg->index];\n\tDdNode *expanded = Cudd_bddExistAbstract(dd,res,var);\n\tif (expanded == NULL) {\n            Cudd_RecursiveDeref(dd,res);\n\t    return(NULL);\n\t}\n\tCudd_Ref(expanded);\n\tif (Cudd_bddLeq(dd,expanded,f)) {\n\t    Cudd_RecursiveDeref(dd,res);\n\t    res = expanded;\n\t} else {\n\t    Cudd_RecursiveDeref(dd,expanded);\n\t}\n\tcuddGetBranches(scan,&t,&e);\n\tif (t == lzero) {\n\t    scan = e;\n\t} else if (e == lzero) {\n\t    scan = t;\n\t} else {\n\t    Cudd_RecursiveDeref(dd,res);\n\t    return(NULL);\t/* cube is not a cube */\n\t}\n    }\n\n    if (scan == DD_ONE(dd)) {\n\tCudd_Deref(res);\n\treturn(res);\n    } else {\n\tCudd_RecursiveDeref(dd,res);\n\treturn(NULL);\n    }\n\n} /* end of cuddBddMakePrime */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Frees the entries of the visited symbol table.\n\n  @return ST_CONTINUE.\n\n  @sideeffect None\n\n*/\nstatic enum st_retval\nfreePathPair(\n  void * key,\n  void * value,\n  void * arg)\n{\n    cuddPathPair *pair = (cuddPathPair *) value;\n\n    (void) key; /* avoid warning */\n    (void) arg; /* avoid warning */\n    FREE(pair);\n    return(ST_CONTINUE);\n\n} /* end of freePathPair */\n\n\n/**\n  @brief Finds the length of the shortest path(s) in a %DD.\n\n  @details Uses a local symbol table to store the lengths for each\n  node. Only the lengths for the regular nodes are entered in the\n  table, because those for the complement nodes are simply obtained by\n  swapping the two lenghts.\n\n  @return a pair of lengths: the length of the shortest path to 1; and\n  the length of the shortest path to 0. This is done so as to take\n  complement arcs into account.\n\n  @sideeffect Accumulates the support of the %DD in support.\n\n*/\nstatic cuddPathPair\ngetShortest(\n  DdManager * dd,\n  DdNode * root,\n  int * cost,\n  int * support,\n  st_table * visited)\n{\n    cuddPathPair *my_pair, res_pair, pair_T, pair_E;\n    DdNode\t*my_root, *T, *E;\n    int\t\tweight;\n    DdNode\t*zero = DD_ZERO(dd);\n\n    my_root = Cudd_Regular(root);\n\n    if (st_lookup(visited, my_root, (void **) &my_pair)) {\n\tif (Cudd_IsComplement(root)) {\n\t    res_pair.pos = my_pair->neg;\n\t    res_pair.neg = my_pair->pos;\n\t} else {\n\t    res_pair.pos = my_pair->pos;\n\t    res_pair.neg = my_pair->neg;\n\t}\n\treturn(res_pair);\n    }\n\n    /* In the case of a BDD the following test is equivalent to\n    ** testing whether the BDD is the constant 1. This formulation,\n    ** however, works for ADDs as well, by assuming the usual\n    ** dichotomy of 0 and != 0.\n    */\n    if (cuddIsConstant(my_root)) {\n\tif (my_root != zero) {\n\t    res_pair.pos = 0;\n\t    res_pair.neg = DD_BIGGY;\n\t} else {\n\t    res_pair.pos = DD_BIGGY;\n\t    res_pair.neg = 0;\n\t}\n    } else {\n\tT = cuddT(my_root);\n\tE = cuddE(my_root);\n\n\tpair_T = getShortest(dd, T, cost, support, visited);\n\tpair_E = getShortest(dd, E, cost, support, visited);\n\tweight = WEIGHT(cost, my_root->index);\n\tres_pair.pos = ddMin(pair_T.pos+weight, pair_E.pos);\n\tres_pair.neg = ddMin(pair_T.neg+weight, pair_E.neg);\n\n\t/* Update support. */\n\tif (support != NULL) {\n\t    support[my_root->index] = 1;\n\t}\n    }\n\n    my_pair = ALLOC(cuddPathPair, 1);\n    if (my_pair == NULL) {\n\tif (Cudd_IsComplement(root)) {\n\t    int tmp = res_pair.pos;\n\t    res_pair.pos = res_pair.neg;\n\t    res_pair.neg = tmp;\n\t}\n\treturn(res_pair);\n    }\n    my_pair->pos = res_pair.pos;\n    my_pair->neg = res_pair.neg;\n\n    st_insert(visited, my_root, my_pair);\n    if (Cudd_IsComplement(root)) {\n\tres_pair.pos = my_pair->neg;\n\tres_pair.neg = my_pair->pos;\n    } else {\n\tres_pair.pos = my_pair->pos;\n\tres_pair.neg = my_pair->neg;\n    }\n    return(res_pair);\n\n} /* end of getShortest */\n\n\n/**\n  @brief Build a %BDD for a shortest path of f.\n\n  @details Given the minimum length from the root, and the minimum\n  lengths for each node (in visited), apply triangulation at each\n  node.  Of the two children of each node on a shortest path, at least\n  one is on a shortest path. In case of ties the procedure chooses the\n  THEN children.\n\n  @return a pointer to the cube %BDD representing the path if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\ngetPath(\n  DdManager * manager,\n  st_table * visited,\n  DdNode * f,\n  int * weight,\n  int  cost)\n{\n    DdNode\t*sol, *tmp;\n    DdNode\t*my_dd, *T, *E;\n    cuddPathPair *T_pair, *E_pair;\n    int\t\tTcost, Ecost;\n    int\t\tcomplement;\n\n    my_dd = Cudd_Regular(f);\n    complement = Cudd_IsComplement(f);\n\n    sol = DD_ONE(manager);\n    cuddRef(sol);\n\n    while (!cuddIsConstant(my_dd)) {\n\tTcost = cost - WEIGHT(weight, my_dd->index);\n\tEcost = cost;\n\n\tT = cuddT(my_dd);\n\tE = cuddE(my_dd);\n\n\tif (complement) {T = Cudd_Not(T); E = Cudd_Not(E);}\n\n\tst_lookup(visited, Cudd_Regular(T), (void **) &T_pair);\n\tif ((Cudd_IsComplement(T) && T_pair->neg == Tcost) ||\n\t(!Cudd_IsComplement(T) && T_pair->pos == Tcost)) {\n\t    tmp = cuddBddAndRecur(manager,manager->vars[my_dd->index],sol);\n\t    if (tmp == NULL) {\n\t\tCudd_RecursiveDeref(manager,sol);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(tmp);\n\t    Cudd_RecursiveDeref(manager,sol);\n\t    sol = tmp;\n\n\t    complement =  Cudd_IsComplement(T);\n\t    my_dd = Cudd_Regular(T);\n\t    cost = Tcost;\n\t    continue;\n\t}\n\tst_lookup(visited, Cudd_Regular(E), (void **) &E_pair);\n\tif ((Cudd_IsComplement(E) && E_pair->neg == Ecost) ||\n\t(!Cudd_IsComplement(E) && E_pair->pos == Ecost)) {\n\t    tmp = cuddBddAndRecur(manager,Cudd_Not(manager->vars[my_dd->index]),sol);\n\t    if (tmp == NULL) {\n\t\tCudd_RecursiveDeref(manager,sol);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(tmp);\n\t    Cudd_RecursiveDeref(manager,sol);\n\t    sol = tmp;\n\t    complement = Cudd_IsComplement(E);\n\t    my_dd = Cudd_Regular(E);\n\t    cost = Ecost;\n\t    continue;\n\t}\n\t(void) fprintf(manager->err,\"We shouldn't be here!!\\n\");\n\tmanager->errorCode = CUDD_INTERNAL_ERROR;\n\treturn(NULL);\n    }\n\n    cuddDeref(sol);\n    return(sol);\n\n} /* end of getPath */\n\n\n/**\n  @brief Finds the size of the largest cube(s) in a %DD.\n\n  @details This problem is translated into finding the shortest paths\n  from a node when both THEN and ELSE arcs have unit lengths.  Uses a\n  local symbol table to store the lengths for each node. Only the\n  lengths for the regular nodes are entered in the table, because\n  those for the complement nodes are simply obtained by swapping the\n  two lenghts.\n\n  @return a pair of lengths: the length of the shortest path to 1; and\n  the length of the shortest path to 0. This is done so as to take\n  complement arcs into account.\n\n  @sideeffect none\n\n*/\nstatic cuddPathPair\ngetLargest(\n  DdManager * dd,\n  DdNode * root,\n  st_table * visited)\n{\n    cuddPathPair *my_pair, res_pair, pair_T, pair_E;\n    DdNode\t*my_root, *T, *E;\n    DdNode\t*zero = DD_ZERO(dd);\n\n    my_root = Cudd_Regular(root);\n\n    if (st_lookup(visited, my_root, (void **) &my_pair)) {\n\tif (Cudd_IsComplement(root)) {\n\t    res_pair.pos = my_pair->neg;\n\t    res_pair.neg = my_pair->pos;\n\t} else {\n\t    res_pair.pos = my_pair->pos;\n\t    res_pair.neg = my_pair->neg;\n\t}\n\treturn(res_pair);\n    }\n\n    /* In the case of a BDD the following test is equivalent to\n    ** testing whether the BDD is the constant 1. This formulation,\n    ** however, works for ADDs as well, by assuming the usual\n    ** dichotomy of 0 and != 0.\n    */\n    if (cuddIsConstant(my_root)) {\n\tif (my_root != zero) {\n\t    res_pair.pos = 0;\n\t    res_pair.neg = DD_BIGGY;\n\t} else {\n\t    res_pair.pos = DD_BIGGY;\n\t    res_pair.neg = 0;\n\t}\n    } else {\n\tT = cuddT(my_root);\n\tE = cuddE(my_root);\n\n\tpair_T = getLargest(dd, T, visited);\n\tpair_E = getLargest(dd, E, visited);\n\tres_pair.pos = ddMin(pair_T.pos, pair_E.pos) + 1;\n\tres_pair.neg = ddMin(pair_T.neg, pair_E.neg) + 1;\n    }\n\n    my_pair = ALLOC(cuddPathPair, 1);\n    if (my_pair == NULL) {\t/* simply do not cache this result */\n\tif (Cudd_IsComplement(root)) {\n\t    int tmp = res_pair.pos;\n\t    res_pair.pos = res_pair.neg;\n\t    res_pair.neg = tmp;\n\t}\n\treturn(res_pair);\n    }\n    my_pair->pos = res_pair.pos;\n    my_pair->neg = res_pair.neg;\n\n    /* Caching may fail without affecting correctness. */\n    st_insert(visited, my_root, my_pair);\n    if (Cudd_IsComplement(root)) {\n\tres_pair.pos = my_pair->neg;\n\tres_pair.neg = my_pair->pos;\n    } else {\n\tres_pair.pos = my_pair->pos;\n\tres_pair.neg = my_pair->neg;\n    }\n    return(res_pair);\n\n} /* end of getLargest */\n\n\n/**\n  @brief Build a %BDD for a largest cube of f.\n\n  @details Given the minimum length from the root, and the minimum\n  lengths for each node (in visited), apply triangulation at each\n  node.  Of the two children of each node on a shortest path, at least\n  one is on a shortest path. In case of ties the procedure chooses the\n  THEN children.\n\n  @return a pointer to the cube %BDD representing the path if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\ngetCube(\n  DdManager * manager,\n  st_table * visited,\n  DdNode * f,\n  int  cost)\n{\n    DdNode\t*sol, *tmp;\n    DdNode\t*my_dd, *T, *E;\n    cuddPathPair *T_pair, *E_pair;\n    int\t\tTcost, Ecost;\n    int\t\tcomplement;\n\n    my_dd = Cudd_Regular(f);\n    complement = Cudd_IsComplement(f);\n\n    sol = DD_ONE(manager);\n    cuddRef(sol);\n\n    while (!cuddIsConstant(my_dd)) {\n\tTcost = cost - 1;\n\tEcost = cost - 1;\n\n\tT = cuddT(my_dd);\n\tE = cuddE(my_dd);\n\n\tif (complement) {T = Cudd_Not(T); E = Cudd_Not(E);}\n\n\tif (!st_lookup(visited, Cudd_Regular(T), (void **)&T_pair)) return(NULL);\n\tif ((Cudd_IsComplement(T) && T_pair->neg == Tcost) ||\n\t(!Cudd_IsComplement(T) && T_pair->pos == Tcost)) {\n\t    tmp = cuddBddAndRecur(manager,manager->vars[my_dd->index],sol);\n\t    if (tmp == NULL) {\n\t\tCudd_RecursiveDeref(manager,sol);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(tmp);\n\t    Cudd_RecursiveDeref(manager,sol);\n\t    sol = tmp;\n\n\t    complement =  Cudd_IsComplement(T);\n\t    my_dd = Cudd_Regular(T);\n\t    cost = Tcost;\n\t    continue;\n\t}\n\tif (!st_lookup(visited, Cudd_Regular(E), (void **)&E_pair)) return(NULL);\n\tif ((Cudd_IsComplement(E) && E_pair->neg == Ecost) ||\n\t(!Cudd_IsComplement(E) && E_pair->pos == Ecost)) {\n\t    tmp = cuddBddAndRecur(manager,Cudd_Not(manager->vars[my_dd->index]),sol);\n\t    if (tmp == NULL) {\n\t\tCudd_RecursiveDeref(manager,sol);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(tmp);\n\t    Cudd_RecursiveDeref(manager,sol);\n\t    sol = tmp;\n\t    complement = Cudd_IsComplement(E);\n\t    my_dd = Cudd_Regular(E);\n\t    cost = Ecost;\n\t    continue;\n\t}\n\t(void) fprintf(manager->err,\"We shouldn't be here!\\n\");\n\tmanager->errorCode = CUDD_INTERNAL_ERROR;\n\treturn(NULL);\n    }\n\n    cuddDeref(sol);\n    return(sol);\n\n} /* end of getCube */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddMaximallyExpand.\n\n  @details On entry to this function, ub and lb should be different\n  from the zero %BDD.  The function then maintains this invariant.\n\n  @return set of primes or zero %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nddBddMaximallyExpand(\n  DdManager *dd /**< manager */,\n  DdNode *lb /**< cube to be expanded */,\n  DdNode *ub /**< upper bound cube */,\n  DdNode *f /**< function against which to expand */)\n{\n    DdNode *lone, *lzero, *lbv, *lbvn, *lbnx, *ubv, *ubvn, *fv, *fvn, *res;\n    DdNode *F, *UB, *LB, *t, *e;\n    int top, toplb, topub, topf;\n    unsigned int index;\n\n    statLine(dd);\n    /* Terminal cases. */\n    lone = DD_ONE(dd);\n    lzero = Cudd_Not(lone);\n    assert(ub != lzero && lb != lzero);\n    /** There are three major terminal cases in theory:\n     **   ub -> f     : return ub\n     **   lb == f     : return lb\n     **   not(lb -> f): return zero\n     ** Only the second case can be checked exactly in constant time.\n     ** For the others, we check for sufficient conditions.\n     */\n    if (ub == f || f == lone) return(ub);\n    if (lb == f) return(lb);\n    if (f == lzero || ub == Cudd_Not(f) || lb == lone || lb == Cudd_Not(f))\n        return(lzero);\n    if (!Cudd_IsComplement(lb) && Cudd_IsComplement(f)) return(lzero);\n\n    /* Here lb and f are not constant. */\n\n    /* Check cache.  Since lb and ub are cubes, their local reference counts\n    ** are always 1.  Hence, we only check the reference count of f.\n    */\n    F = Cudd_Regular(f);\n    if (F->ref != 1) {\n        DdNode *tmp = cuddCacheLookup(dd, DD_BDD_MAX_EXP_TAG, lb, ub, f);\n        if (tmp != NULL) {\n            return(tmp);\n        }\n    }\n\n    checkWhetherToGiveUp(dd);\n\n    /* Compute cofactors.  For lb we use the non-zero one in\n    ** both branches of the recursion.\n    */\n    LB = Cudd_Regular(lb);\n    UB = Cudd_Regular(ub);\n    topf = dd->perm[F->index];\n    toplb = dd->perm[LB->index];\n    topub = (ub == lone) ? CUDD_CONST_INDEX : (unsigned int) dd->perm[UB->index];\n    assert(toplb <= topub);\n    top = ddMin(topf,toplb);\n    if (toplb == top) {\n\tindex = LB->index;\n        lbv = cuddT(LB);\n        lbvn = cuddE(LB);\n        if (lb != LB) {\n            lbv = Cudd_Not(lbv);\n            lbvn = Cudd_Not(lbvn);\n        }\n        if (lbv == lzero) {\n            lbnx = lbvn;\n        } else {\n            lbnx = lbv;\n        }\n    } else {\n\tindex = F->index;\n        lbnx = lbv = lbvn = lb;\n    }\n    if (topub == top) {\n        ubv = cuddT(UB);\n        ubvn = cuddE(UB);\n        if (ub != UB) {\n            ubv = Cudd_Not(ubv);\n            ubvn = Cudd_Not(ubvn);\n        }\n    } else {\n        ubv = ubvn = ub;\n    }\n    if (topf == top) {\n        fv = cuddT(F);\n        fvn = cuddE(F);\n        if (f != F) {\n            fv = Cudd_Not(fv);\n            fvn = Cudd_Not(fvn);\n        }\n    } else {\n        fv = fvn = f;\n    }\n\n    /* Recursive calls. */\n    if (ubv != lzero) {\n        t = ddBddMaximallyExpand(dd, lbnx, ubv, fv);\n        if (t == NULL) return(NULL);\n    } else {\n        assert(topub == toplb && topub == top && lbv == lzero);\n        t = lzero;\n    }\n    cuddRef(t);\n\n    /* If the top variable appears only in lb, the positive and negative\n    ** cofactors of each operand are the same.  We want to avoid a\n    ** needless recursive call, which would force us to give up the\n    ** cache optimization trick based on reference counts.\n    */\n    if (ubv == ubvn && fv == fvn) {\n        res = t;\n    } else {\n        if (ubvn != lzero) {\n            e = ddBddMaximallyExpand(dd, lbnx, ubvn, fvn);\n            if (e == NULL) {\n                Cudd_IterDerefBdd(dd,t);\n                return(NULL);\n            }\n        } else {\n            assert(topub == toplb && topub == top && lbvn == lzero);\n            e = lzero;\n        }\n\n        if (t == e) {\n            res = t;\n        } else {\n            cuddRef(e);\n\n            if (toplb == top) {\n                if (lbv == lzero) {\n                    /* Top variable appears in negative phase. */\n                    if (t != lone) {\n                        DdNode *newT;\n                        if (Cudd_IsComplement(t)) {\n                            newT = cuddUniqueInter(dd, index, Cudd_Not(t), lzero);\n                            if (newT == NULL) {\n                                Cudd_IterDerefBdd(dd,t);\n                                Cudd_IterDerefBdd(dd,e);\n                                return(NULL);\n                            }\n                            newT = Cudd_Not(newT);\n                        } else {\n                            newT = cuddUniqueInter(dd, index, t, lone);\n                            if (newT == NULL) {\n                                Cudd_IterDerefBdd(dd,t);\n                                Cudd_IterDerefBdd(dd,e);\n                                return(NULL);\n                            }\n                        }\n                        cuddRef(newT);\n                        cuddDeref(t);\n                        t = newT;\n                    }\n                } else if (lbvn == lzero) {\n                    /* Top variable appears in positive phase. */\n                    if (e != lone) {\n                        DdNode *newE;\n                        newE = cuddUniqueInter(dd, index, lone, e);\n                        if (newE == NULL) {\n                            Cudd_IterDerefBdd(dd,t);\n                            Cudd_IterDerefBdd(dd,e);\n                            return(NULL);\n                        }\n                        cuddRef(newE);\n                        cuddDeref(e);\n                        e = newE;\n                    }\n                } else {\n                    /* Not a cube. */\n                    Cudd_IterDerefBdd(dd,t);\n                    Cudd_IterDerefBdd(dd,e);\n                    return(NULL);\n                }\n            }\n\n            /* Combine results. */\n            res = cuddBddAndRecur(dd, t, e);\n            if (res == NULL) {\n                Cudd_IterDerefBdd(dd,t);\n                Cudd_IterDerefBdd(dd,e);\n                return(NULL);\n            }\n            cuddRef(res);\n            Cudd_IterDerefBdd(dd,t);\n            Cudd_IterDerefBdd(dd,e);\n        }\n    }\n\n    /* Cache result and return. */\n    if (F->ref != 1) {\n        cuddCacheInsert(dd, DD_BDD_MAX_EXP_TAG, lb, ub, f, res);\n    }\n    cuddDeref(res);\n    return(res);\n\n} /* end of ddBddMaximallyExpand */\n\n\n/**\n  @brief Performs shortest path computation on a unate function.\n\n  @details This function is based on the observation that in the %BDD\n  of a unate function no node except the constant is reachable from\n  the root via paths of different parity.\n\n  @return the length of the shortest path to one if successful;\n  CUDD_OUT_OF_MEM otherwise.\n\n  @sideeffect None\n\n  @see getShortest\n\n*/\nstatic int\nddBddShortestPathUnate(\n  DdManager *dd,\n  DdNode *f,\n  int *phases,\n  st_table *table)\n{\n    int positive, l, lT, lE;\n    DdNode *lone = DD_ONE(dd);\n    DdNode *lzero = Cudd_Not(lone);\n    DdNode *F, *fv, *fvn;\n\n    if (st_lookup_int(table, f, &l)) {\n        return(l);\n    }\n    if (f == lone) {\n        l = 0;\n    } else if (f == lzero) {\n        l = DD_BIGGY;\n    } else {\n        F = Cudd_Regular(f);\n        fv = cuddT(F);\n        fvn = cuddE(F);\n        if (f != F) {\n            fv = Cudd_Not(fv);\n            fvn = Cudd_Not(fvn);\n        }\n        lT = ddBddShortestPathUnate(dd, fv, phases, table);\n        lE = ddBddShortestPathUnate(dd, fvn, phases, table);\n        positive = phases[F->index];\n        l = positive ? ddMin(lT+1, lE) : ddMin(lT, lE+1);\n    }\n    if (st_insert(table, f, (void *)(ptrint) l) == ST_OUT_OF_MEM) {\n        return(CUDD_OUT_OF_MEM);\n    }\n    return(l);\n\n} /* end of ddShortestPathUnate */\n\n\n/**\n  @brief Extracts largest prime of a unate function.\n\n  @return the %BDD of the prime if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see getPath\n\n*/\nstatic DdNode *\nddGetLargestCubeUnate(\n  DdManager *dd,\n  DdNode *f,\n  int *phases,\n  st_table *table)\n{\n    DdNode *res, *scan;\n    int cost;\n\n    res = DD_ONE(dd);\n    cuddRef(res);\n    scan = f;\n    st_lookup_int(table, scan, &cost);\n\n    while (!Cudd_IsConstantInt(scan)) {\n        int Pcost, Ncost, Tcost;\n        DdNode *tmp, *T, *E;\n        DdNode *rscan = Cudd_Regular(scan);\n        unsigned int index = rscan->index;\n        assert(phases[index] == 0 || phases[index] == 1);\n        int positive = phases[index] == 1;\n        Pcost = positive ? cost - 1 : cost;\n        Ncost = positive ? cost : cost - 1;\n        T = cuddT(rscan);\n        E = cuddE(rscan);\n        if (rscan != scan) {\n            T = Cudd_Not(T);\n            E = Cudd_Not(E);\n        }\n        tmp = res;\n        st_lookup_int(table, T, &Tcost);\n        if (Tcost == Pcost) {\n            cost = Pcost;\n            scan = T;\n            if (positive) {\n                tmp = cuddBddAndRecur(dd, dd->vars[index], res);\n            }\n        } else {\n            cost = Ncost;\n            scan = E;\n            if (!positive) {\n                tmp = cuddBddAndRecur(dd, Cudd_Not(dd->vars[index]), res);\n            }\n        }\n        if (tmp == NULL) {\n            Cudd_IterDerefBdd(dd, res);\n            return(NULL);\n        }\n        cuddRef(tmp);\n        Cudd_IterDerefBdd(dd, res);\n        res = tmp;\n    }\n\n    cuddDeref(res);\n    return(res);\n\n} /* end of ddGetLargestCubeUnate */\n"
  },
  {
    "path": "cudd/cudd/cuddSign.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Computation of signatures.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic double * ddCofMintermAux (DdManager *dd, DdNode *node, st_table *table);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Computes the fraction of minterms in the on-set of all the\n  positive cofactors of a %BDD or %ADD.\n\n  @details The array has as many positions as there are %BDD variables\n  in the manager plus one. The last position of the array contains the\n  fraction of the minterms in the ON-set of the function represented\n  by the %BDD or %ADD. The other positions of the array hold the\n  variable signatures.\n\n  @return the pointer to an array of doubles if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\ndouble *\nCudd_CofMinterm(\n  DdManager * dd,\n  DdNode * node)\n{\n    st_table\t*table;\n    double\t*values;\n    double\t*result = NULL;\n    int\t\ti, firstLevel;\n    int\t\tsize;\n\n#ifdef DD_STATS\n    unsigned long startTime;\n    startTime = util_cpu_time();\n    dd->num_calls = 0;\n#endif\n\n    table = st_init_table(st_ptrcmp, st_ptrhash);\n    if (table == NULL) {\n\t(void) fprintf(dd->err,\n\t\t       \"out-of-memory, couldn't measure DD cofactors.\\n\");\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    size = dd->size;\n    values = ddCofMintermAux(dd, node, table);\n    if (values != NULL) {\n\tresult = ALLOC(double,size + 1);\n\tif (result != NULL) {\n\t    if (Cudd_IsConstantInt(node))\n\t\tfirstLevel = 1;\n\t    else\n\t\tfirstLevel = cuddI(dd,Cudd_Regular(node)->index);\n\t    for (i = 0; i < size; i++) {\n\t\tif (i >= cuddI(dd,Cudd_Regular(node)->index)) {\n\t\t    result[dd->invperm[i]] = values[i - firstLevel];\n\t\t} else {\n\t\t    result[dd->invperm[i]] = values[size - firstLevel];\n\t\t}\n\t    }\n\t    result[size] = values[size - firstLevel];\n\t} else {\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t}\n    }\n\n    if (Cudd_Regular(node)->ref == 1) FREE(values);\n    st_foreach(table, cuddStCountfree, NULL);\n    st_free_table(table);\n#ifdef DD_STATS\n    (void) fprintf(dd->out,\"Number of calls: %d\\n\", dd->num_calls);\n    (void) fprintf(dd->out,\"Time to compute measures: %s\\n\",\n\t\t  util_print_time(util_cpu_time() - startTime));\n#endif\n    if (result == NULL) {\n\t(void) fprintf(dd->out,\n\t\t       \"out-of-memory, couldn't measure DD cofactors.\\n\");\n\tdd->errorCode = CUDD_MEMORY_OUT;\n    }\n    return(result);\n\n} /* end of Cudd_CofMinterm */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Recursive Step for Cudd_CofMinterm function.\n\n  @details Traverses the %DD node and computes the fraction of minterms\n  in the on-set of all positive cofactors simultaneously.  It\n  allocates an array with two more entries than there are variables\n  below the one labeling the node.  One extra entry (the first in the\n  array) is for the variable labeling the node. The other entry (the\n  last one in the array) holds the fraction of minterms of the\n  function rooted at node.  Each other entry holds the value for one\n  cofactor. The array is put in a symbol table, to avoid repeated\n  computation, and its address is returned by the procedure, for use\n  by the caller.\n\n  @return a pointer to the array of cofactor measures.\n\n  @sideeffect None\n\n*/\nstatic double *\nddCofMintermAux(\n  DdManager * dd,\n  DdNode * node,\n  st_table * table)\n{\n    DdNode\t*N;\t\t/* regular version of node */\n    DdNode\t*Nv, *Nnv;\n    double\t*values;\n    double\t*valuesT, *valuesE;\n    int\t\ti;\n    int\t\tlocalSize, localSizeT, localSizeE;\n    double\tvT, vE;\n    int\t\tsize = dd->size;\n\n    statLine(dd);\n#ifdef DD_STATS\n    dd->num_calls++;\n#endif\n\n    if (st_lookup(table, node, (void **) &values)) {\n\treturn(values);\n    }\n\n    N = Cudd_Regular(node);\n    if (cuddIsConstant(N)) {\n\tlocalSize = 1;\n    } else {\n\tlocalSize = size - cuddI(dd,N->index) + 1;\n    }\n    values = ALLOC(double, localSize);\n    if (values == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    if (cuddIsConstant(N)) {\n\tif (node == DD_ZERO(dd) || node == Cudd_Not(DD_ONE(dd))) {\n\t    values[0] = 0.0;\n\t} else {\n\t    values[0] = 1.0;\n\t}\n    } else {\n\tNv = Cudd_NotCond(cuddT(N),N!=node);\n\tNnv = Cudd_NotCond(cuddE(N),N!=node);\n\n\tvaluesT = ddCofMintermAux(dd, Nv, table);\n\tif (valuesT == NULL) return(NULL);\n\tvaluesE = ddCofMintermAux(dd, Nnv, table);\n\tif (valuesE == NULL) return(NULL);\n\n\tif (Cudd_IsConstantInt(Nv)) {\n\t    localSizeT = 1;\n\t} else {\n\t    localSizeT = size - cuddI(dd,Cudd_Regular(Nv)->index) + 1;\n\t}\n\tif (Cudd_IsConstantInt(Nnv)) {\n\t    localSizeE = 1;\n\t} else {\n\t    localSizeE = size - cuddI(dd,Cudd_Regular(Nnv)->index) + 1;\n\t}\n\tvalues[0] = valuesT[localSizeT - 1];\n\tfor (i = 1; i < localSize; i++) {\n\t    if (i >= cuddI(dd,Cudd_Regular(Nv)->index) - cuddI(dd,N->index)) {\n\t\tvT = valuesT[i - cuddI(dd,Cudd_Regular(Nv)->index) +\n\t\t\t    cuddI(dd,N->index)];\n\t    } else {\n\t\tvT = valuesT[localSizeT - 1];\n\t    }\n\t    if (i >= cuddI(dd,Cudd_Regular(Nnv)->index) - cuddI(dd,N->index)) {\n\t\tvE = valuesE[i - cuddI(dd,Cudd_Regular(Nnv)->index) +\n\t\t\t    cuddI(dd,N->index)];\n\t    } else {\n\t\tvE = valuesE[localSizeE - 1];\n\t    }\n\t    values[i] = (vT + vE) / 2.0;\n\t}\n\tif (Cudd_Regular(Nv)->ref == 1) FREE(valuesT);\n\tif (Cudd_Regular(Nnv)->ref == 1) FREE(valuesE);\n    }\n\n    if (N->ref > 1) {\n\tif (st_add_direct(table, node, values) == ST_OUT_OF_MEM) {\n\t    FREE(values);\n\t    return(NULL);\n\t}\n    }\n    return(values);\n\n} /* end of ddCofMintermAux */\n"
  },
  {
    "path": "cudd/cudd/cuddSolve.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Boolean equation solver and related functions.\n\n  @author Balakrishna Kumthekar\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Structure declarations                                                    */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the solution of F(x,y) = 0.\n\n  @details The return value is the consistency condition. The y\n  variables are the unknowns and the remaining variables are the\n  parameters.  Cudd_SolveEqn allocates an array and fills it with the\n  indices of the unknowns. This array is used by Cudd_VerifySol.\n\n  @return the consistency condition if successful; NULL otherwise.\n\n  @sideeffect The solution is returned in G; the indices of the y\n  variables are returned in yIndex.\n\n  @see Cudd_VerifySol\n\n*/\nDdNode *\nCudd_SolveEqn(\n  DdManager *  bdd /**< CUDD manager */,\n  DdNode * F /**< the left-hand side of the equation */,\n  DdNode * Y /**< the cube of the y variables */,\n  DdNode ** G /**< the array of solutions (return parameter) */,\n  int ** yIndex /**< index of y variables */,\n  int  n /**< numbers of unknowns */)\n{\n    DdNode *res;\n    int *temp;\n\n    *yIndex = temp = ALLOC(int, n);\n    if (temp == NULL) {\n\tbdd->errorCode = CUDD_MEMORY_OUT;\n\t(void) fprintf(bdd->out,\n\t\t       \"Cudd_SolveEqn: Out of memory for yIndex\\n\");\n\treturn(NULL);\n    }\n\n    do {\n\tbdd->reordered = 0;\n\tres = cuddSolveEqnRecur(bdd, F, Y, G, n, temp, 0);\n    } while (bdd->reordered == 1);\n    if (bdd->errorCode == CUDD_TIMEOUT_EXPIRED && bdd->timeoutHandler) {\n        bdd->timeoutHandler(bdd, bdd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_SolveEqn */\n\n\n/**\n  @brief Checks the solution of F(x,y) = 0.\n\n  @details This procedure substitutes the solution components for the\n  unknowns of F and returns the resulting %BDD for F.\n\n  @sideeffect Frees the memory pointed by yIndex.\n\n  @see Cudd_SolveEqn\n\n*/\nDdNode *\nCudd_VerifySol(\n  DdManager *  bdd /**< CUDD manager */,\n  DdNode * F /**< the left-hand side of the equation */,\n  DdNode ** G /**< the array of solutions */,\n  int * yIndex /**< index of y variables */,\n  int  n /**< numbers of unknowns */)\n{\n    DdNode *res;\n\n    do {\n\tbdd->reordered = 0;\n\tres = cuddVerifySol(bdd, F, G, yIndex, n);\n    } while (bdd->reordered == 1);\n\n    FREE(yIndex);\n    if (bdd->errorCode == CUDD_TIMEOUT_EXPIRED && bdd->timeoutHandler) {\n        bdd->timeoutHandler(bdd, bdd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_VerifySol */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Implements the recursive step of Cudd_SolveEqn.\n\n  @return NULL if the intermediate solution blows up or reordering\n  occurs.\n\n  @sideeffect The parametric solutions are stored in the array G.\n\n  @see Cudd_SolveEqn, Cudd_VerifySol\n\n*/\nDdNode *\ncuddSolveEqnRecur(\n  DdManager * bdd /**< CUDD manager */,\n  DdNode * F /**< the left-hand side of the equation */,\n  DdNode * Y /**< the cube of remaining y variables */,\n  DdNode ** G /**< the array of solutions */,\n  int  n /**< number of unknowns */,\n  int * yIndex /**< array holding the y variable indices */,\n  int  i /**< level of recursion */)\n{\n    DdNode *Fn, *Fm1, *Fv, *Fvbar, *T, *w, *nextY, *one;\n    DdNodePtr *variables;\n\n    int j;\n\n    statLine(bdd);\n    variables = bdd->vars;\n    one = DD_ONE(bdd);\n\n    /* Base condition. */\n    if (Y == one) {\n\treturn F;\n    }\n\n    /* Cofactor of Y. */\n    yIndex[i] = Y->index;\n    nextY = Cudd_T(Y);\n\n    /* Universal abstraction of F with respect to the top variable index. */\n    Fm1 = cuddBddExistAbstractRecur(bdd, Cudd_Not(F), variables[yIndex[i]]);\n    if (Fm1) {\n\tFm1 = Cudd_Not(Fm1);\n\tcuddRef(Fm1);\n    } else {\n\treturn(NULL);\n    }\n\n    Fn = cuddSolveEqnRecur(bdd, Fm1, nextY, G, n, yIndex, i+1);\n    if (Fn) {\n\tcuddRef(Fn);\n    } else {\n\tCudd_RecursiveDeref(bdd, Fm1);\n\treturn(NULL);\n    }\n\n    Fv = cuddCofactorRecur(bdd, F, variables[yIndex[i]]);\n    if (Fv) {\n\tcuddRef(Fv);\n    } else {\n\tCudd_RecursiveDeref(bdd, Fm1);\n\tCudd_RecursiveDeref(bdd, Fn);\n\treturn(NULL);\n    }\n\n    Fvbar = cuddCofactorRecur(bdd, F, Cudd_Not(variables[yIndex[i]]));\n    if (Fvbar) {\n\tcuddRef(Fvbar);\n    } else {\n\tCudd_RecursiveDeref(bdd, Fm1);\n\tCudd_RecursiveDeref(bdd, Fn);\n\tCudd_RecursiveDeref(bdd, Fv);\n\treturn(NULL);\n    }\n\n    /* Build i-th component of the solution. */\n    w = cuddBddIteRecur(bdd, variables[yIndex[i]], Cudd_Not(Fv), Fvbar);\n    if (w) {\n\tcuddRef(w);\n    } else {\n\tCudd_RecursiveDeref(bdd, Fm1);\n\tCudd_RecursiveDeref(bdd, Fn);\n\tCudd_RecursiveDeref(bdd, Fv);\n\tCudd_RecursiveDeref(bdd, Fvbar);\n\treturn(NULL);\n    }\n\n    T = cuddBddRestrictRecur(bdd, w, Cudd_Not(Fm1));\n    if(T) {\n\tcuddRef(T);\n    } else {\n\tCudd_RecursiveDeref(bdd, Fm1);\n\tCudd_RecursiveDeref(bdd, Fn);\n\tCudd_RecursiveDeref(bdd, Fv);\n\tCudd_RecursiveDeref(bdd, Fvbar);\n\tCudd_RecursiveDeref(bdd, w);\n\treturn(NULL);\n    }\n\n    Cudd_RecursiveDeref(bdd,Fm1);\n    Cudd_RecursiveDeref(bdd,w);\n    Cudd_RecursiveDeref(bdd,Fv);\n    Cudd_RecursiveDeref(bdd,Fvbar);\n\n    /* Substitute components of solution already found into solution. */\n    for (j = n-1; j > i; j--) {\n\tw = cuddBddComposeRecur(bdd,T, G[j], variables[yIndex[j]]);\n\tif(w) {\n\t    cuddRef(w);\n\t} else {\n\t    Cudd_RecursiveDeref(bdd, Fn);\n\t    Cudd_RecursiveDeref(bdd, T);\n\t    return(NULL);\n\t}\n\tCudd_RecursiveDeref(bdd,T);\n\tT = w;\n    }\n    G[i] = T;\n\n    Cudd_Deref(Fn);\n\n    return(Fn);\n\n} /* end of cuddSolveEqnRecur */\n\n\n/**\n  @brief Implements the recursive step of Cudd_VerifySol. \n\n  @sideeffect none\n\n  @see Cudd_VerifySol\n\n*/\nDdNode *\ncuddVerifySol(\n  DdManager * bdd /**< CUDD manager */,\n  DdNode * F /**< the left-hand side of the equation */,\n  DdNode ** G /**< the array of solutions */,\n  int * yIndex /**< array holding the y variable indices */,\n  int  n /**< number of unknowns */)\n{\n    DdNode *w, *R;\n\n    int j;\n\n    R = F;\n    cuddRef(R);\n    for(j = n - 1; j >= 0; j--) {\n\t w = Cudd_bddCompose(bdd, R, G[j], yIndex[j]);\n\tif (w) {\n\t    cuddRef(w);\n\t} else {\n\t    return(NULL); \n\t}\n\tCudd_RecursiveDeref(bdd,R);\n\tR = w;\n    }\n\n    cuddDeref(R);\n\n    return(R);\n\n} /* end of cuddVerifySol */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n"
  },
  {
    "path": "cudd/cudd/cuddSplit.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Returns a subset of minterms from a boolean function.\n\n  @author Balakrishna Kumthekar\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Structure declarations                                                    */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * selectMintermsFromUniverse (DdManager *manager, int *varSeen, double n);\nstatic DdNode * mintermsFromUniverse (DdManager *manager, DdNode **vars, int numVars, double n, int index);\nstatic double bddAnnotateMintermCount (DdManager *manager, DdNode *node, double max, st_table *table);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Returns m minterms from a %BDD.\n\n  @details Returns <code>m</code> minterms from a %BDD whose\n  support has <code>n</code> variables at most.  The procedure tries\n  to create as few extra nodes as possible. The function represented\n  by <code>S</code> depends on at most <code>n</code> of the variables\n  in <code>xVars</code>.\n\n  @return a %BDD with <code>m</code> minterms of the on-set of S if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_SplitSet(\n  DdManager * manager,\n  DdNode * S,\n  DdNode ** xVars,\n  int  n,\n  double  m)\n{\n    DdNode *result;\n    DdNode *zero, *one;\n    double  max, num;\n    st_table *mtable;\n    int *varSeen;\n    int i,index, size;\n\n    size = manager->size;\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    /* Trivial cases. */\n    if (m == 0.0) {\n\treturn(zero);\n    }\n    if (S == zero) {\n\treturn(NULL);\n    }\n\n    max = pow(2.0,(double)n);\n    if (m > max)\n\treturn(NULL);\n\n    do {\n\tmanager->reordered = 0;\n\t/* varSeen is used to mark the variables that are encountered\n\t** while traversing the BDD S.\n\t*/\n\tvarSeen = ALLOC(int, size);\n\tif (varSeen == NULL) {\n\t    manager->errorCode = CUDD_MEMORY_OUT;\n\t    return(NULL);\n\t}\n\tfor (i = 0; i < size; i++) {\n\t    varSeen[i] = -1;\n\t}\n\tfor (i = 0; i < n; i++) {\n\t    index = (xVars[i])->index;\n\t    varSeen[manager->invperm[index]] = 0;\n\t}\n\n\tif (S == one) {\n\t    if (m == max) {\n\t\tFREE(varSeen);\n\t\treturn(S);\n\t    }\n\t    result = selectMintermsFromUniverse(manager,varSeen,m);\n\t    if (result)\n\t\tcuddRef(result);\n\t    FREE(varSeen);\n\t} else {\n\t    mtable = st_init_table(st_ptrcmp,st_ptrhash);\n\t    if (mtable == NULL) {\n\t\t(void) fprintf(manager->out,\n\t\t\t       \"Cudd_SplitSet: out-of-memory.\\n\");\n\t\tFREE(varSeen);\n\t\tmanager->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(NULL);\n\t    }\n\t    /* The nodes of BDD S are annotated by the number of minterms\n\t    ** in their onset. The node and the number of minterms in its\n\t    ** onset are stored in mtable.\n\t    */\n\t    num = bddAnnotateMintermCount(manager,S,max,mtable);\n\t    if (m == num) {\n\t\tst_foreach(mtable,cuddStCountfree,NIL(void));\n\t\tst_free_table(mtable);\n\t\tFREE(varSeen);\n\t\treturn(S);\n\t    }\n\t    \n\t    result = cuddSplitSetRecur(manager,mtable,varSeen,S,m,max,0);\n\t    if (result)\n\t\tcuddRef(result);\n\t    st_foreach(mtable,cuddStCountfree,NULL);\n\t    st_free_table(mtable);\n\t    FREE(varSeen);\n\t}\n    } while (manager->reordered == 1);\n    if (manager->errorCode == CUDD_TIMEOUT_EXPIRED && manager->timeoutHandler) {\n        manager->timeoutHandler(manager, manager->tohArg);\n    }\n\n    cuddDeref(result);\n    return(result);\n\n} /* end of Cudd_SplitSet */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Implements the recursive step of Cudd_SplitSet.\n\n  @details The procedure recursively traverses the %BDD and checks to\n  see if any node satisfies the minterm requirements as specified by\n  'n'. At any node X, n is compared to the number of minterms in the\n  onset of X's children. If either of the child nodes have exactly n\n  minterms, then that node is returned; else, if n is greater than the\n  onset of one of the child nodes, that node is retained and the\n  difference in the number of minterms is extracted from the other\n  child. In case n minterms can be extracted from constant 1, the\n  algorithm returns the result with at most log(n) nodes.\n\n  @sideeffect The array 'varSeen' is updated at every recursive call\n  to set the variables traversed by the procedure.\n\n*/\nDdNode*\ncuddSplitSetRecur(\n  DdManager * manager,\n  st_table * mtable,\n  int * varSeen,\n  DdNode * p,\n  double  n,\n  double  max,\n  int  index)\n{\n    DdNode *one, *zero, *N, *Nv;\n    DdNode *Nnv, *q, *r, *v;\n    DdNode *result;\n    double *dummy, numT, numE;\n    int variable, positive;\n  \n    statLine(manager);\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    /* If p is constant, extract n minterms from constant 1.  The procedure by\n    ** construction guarantees that minterms will not be extracted from\n    ** constant 0.\n    */\n    if (Cudd_IsConstantInt(p)) {\n\tq = selectMintermsFromUniverse(manager,varSeen,n);\n\treturn(q);\n    }\n\n    N = Cudd_Regular(p);\n\n    /* Set variable as seen. */\n    variable = N->index;\n    varSeen[manager->invperm[variable]] = -1;\n\n    Nv = cuddT(N);\n    Nnv = cuddE(N);\n    if (Cudd_IsComplement(p)) {\n\tNv = Cudd_Not(Nv);\n\tNnv = Cudd_Not(Nnv);\n    }\n\n    /* If both the children of 'p' are constants, extract n minterms from a\n    ** constant node.\n    */\n    if (Cudd_IsConstantInt(Nv) && Cudd_IsConstantInt(Nnv)) {\n\tq = selectMintermsFromUniverse(manager,varSeen,n);\n\tif (q == NULL) {\n\t    return(NULL);\n\t}\n\tcuddRef(q);\n\tr = cuddBddAndRecur(manager,p,q);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(manager,q);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_RecursiveDeref(manager,q);\n\tcuddDeref(r);\n\treturn(r);\n    }\n  \n    /* Lookup the # of minterms in the onset of the node from the table. */\n    if (!Cudd_IsConstantInt(Nv)) {\n      if (!st_lookup(mtable, Nv, (void **) &dummy)) return(NULL);\n\tnumT = *dummy/(2*(1U<<index));\n    } else if (Nv == one) {\n\tnumT = max/(2*(1U<<index));\n    } else {\n\tnumT = 0;\n    }\n  \n    if (!Cudd_IsConstantInt(Nnv)) {\n      if (!st_lookup(mtable, Nnv, (void **) &dummy)) return(NULL);\n\tnumE = *dummy/(2*(1U<<index));\n    } else if (Nnv == one) {\n\tnumE = max/(2*(1U<<index));\n    } else {\n\tnumE = 0;\n    }\n\n    v = cuddUniqueInter(manager,variable,one,zero);\n    cuddRef(v);\n\n    /* If perfect match. */\n    if (numT == n) {\n\tq = cuddBddAndRecur(manager,v,Nv);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(q);\n\tCudd_RecursiveDeref(manager,v);\n\tcuddDeref(q);\n\treturn(q);\n    }\n    if (numE == n) {\n\tq = cuddBddAndRecur(manager,Cudd_Not(v),Nnv);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(q);\n\tCudd_RecursiveDeref(manager,v);\n\tcuddDeref(q);\n\treturn(q);\n    }\n    /* If n is greater than numT, extract the difference from the ELSE child\n    ** and retain the function represented by the THEN branch.\n    */\n    if (numT < n) {\n\tq = cuddSplitSetRecur(manager,mtable,varSeen,\n\t\t\t      Nnv,(n-numT),max,index+1);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(q);\n\tr = cuddBddIteRecur(manager,v,Nv,q);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(manager,q);\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_RecursiveDeref(manager,q);\n\tCudd_RecursiveDeref(manager,v);\n\tcuddDeref(r);\n\treturn(r);\n    }\n    /* If n is greater than numE, extract the difference from the THEN child\n    ** and retain the function represented by the ELSE branch.\n    */\n    if (numE < n) {\n\tq = cuddSplitSetRecur(manager,mtable,varSeen,\n\t\t\t      Nv, (n-numE),max,index+1);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(q);\n\tr = cuddBddIteRecur(manager,v,q,Nnv);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDeref(manager,q);\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_RecursiveDeref(manager,q);\n\tCudd_RecursiveDeref(manager,v);\n\tcuddDeref(r);    \n\treturn(r);\n    }\n\n    /* None of the above cases; (n < numT and n < numE) and either of\n    ** the Nv, Nnv or both are not constants. If possible extract the\n    ** required minterms the constant branch.\n    */\n    if (Cudd_IsConstantInt(Nv) && !Cudd_IsConstantInt(Nnv)) {\n\tq = selectMintermsFromUniverse(manager,varSeen,n);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(q);\n\tresult = cuddBddAndRecur(manager,v,q);\n\tif (result == NULL) {\n\t    Cudd_RecursiveDeref(manager,q);\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(result);\n\tCudd_RecursiveDeref(manager,q);\n\tCudd_RecursiveDeref(manager,v);\n\tcuddDeref(result);\n\treturn(result);\n    } else if (!Cudd_IsConstantInt(Nv) && Cudd_IsConstantInt(Nnv)) {\n\tq = selectMintermsFromUniverse(manager,varSeen,n);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(q);\n\tresult = cuddBddAndRecur(manager,Cudd_Not(v),q);\n\tif (result == NULL) {\n\t    Cudd_RecursiveDeref(manager,q);\n\t    Cudd_RecursiveDeref(manager,v);\n\t    return(NULL);\n\t}\n\tcuddRef(result);\n\tCudd_RecursiveDeref(manager,q);\n\tCudd_RecursiveDeref(manager,v);\n\tcuddDeref(result);\n\treturn(result);\n    }\n\n    /* Both Nv and Nnv are not constants. So choose the one which\n    ** has fewer minterms in its onset.\n    */\n    positive = 0;\n    if (numT < numE) {\n\tq = cuddSplitSetRecur(manager,mtable,varSeen,\n\t\t\t      Nv,n,max,index+1);\n\tpositive = 1;\n    } else {\n\tq = cuddSplitSetRecur(manager,mtable,varSeen,\n\t\t\t      Nnv,n,max,index+1);\n    }\n\n    if (q == NULL) {\n\tCudd_RecursiveDeref(manager,v);\n\treturn(NULL);\n    }\n    cuddRef(q);\n\n    if (positive) {\n\tresult = cuddBddAndRecur(manager,v,q);\n    } else {\n\tresult = cuddBddAndRecur(manager,Cudd_Not(v),q);\n    }\n    if (result == NULL) {\n\tCudd_RecursiveDeref(manager,q);\n\tCudd_RecursiveDeref(manager,v);\n\treturn(NULL);\n    }\n    cuddRef(result);\n    Cudd_RecursiveDeref(manager,q);\n    Cudd_RecursiveDeref(manager,v);\n    cuddDeref(result);\n\n    return(result);\n\n} /* end of cuddSplitSetRecur */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief This function prepares an array of variables which have not been\n  encountered so far when traversing the procedure cuddSplitSetRecur.\n\n  @details This array is then used to extract the required number of\n  minterms from a constant 1.  The algorithm guarantees that the size\n  of %BDD will be at most log(n).\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nselectMintermsFromUniverse(\n  DdManager * manager,\n  int * varSeen,\n  double  n)\n{\n    int numVars;\n    int i, size, j;\n     DdNode *one, *zero, *result;\n    DdNode **vars;\n\n    numVars = 0;\n    size = manager->size;\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    /* Count the number of variables not encountered so far in procedure\n    ** cuddSplitSetRecur.\n    */\n    for (i = size-1; i >= 0; i--) {\n\tif(varSeen[i] == 0)\n\t    numVars++;\n    }\n    vars = ALLOC(DdNode *, numVars);\n    if (!vars) {\n\tmanager->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    j = 0;\n    for (i = size-1; i >= 0; i--) {\n\tif(varSeen[i] == 0) {\n\t    vars[j] = cuddUniqueInter(manager,manager->perm[i],one,zero);\n\t    cuddRef(vars[j]);\n\t    j++;\n\t}\n    }\n\n    /* Compute a function which has n minterms and depends on at most\n    ** numVars variables.\n    */\n    result = mintermsFromUniverse(manager,vars,numVars,n, 0);\n    if (result) \n\tcuddRef(result);\n\n    for (i = 0; i < numVars; i++)\n\tCudd_RecursiveDeref(manager,vars[i]);\n    FREE(vars);\n\n    return(result);\n\n} /* end of selectMintermsFromUniverse */\n\n\n/**\n  @brief Recursive procedure to extract n mintems from constant 1.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nmintermsFromUniverse(\n  DdManager * manager,\n  DdNode ** vars,\n  int  numVars,\n  double  n,\n  int  index)\n{\n    DdNode *one, *zero;\n    DdNode *q, *result;\n    double max, max2;\n    \n    statLine(manager);\n    one = DD_ONE(manager);\n    zero = Cudd_Not(one);\n\n    max = pow(2.0, (double)numVars);\n    max2 = max / 2.0;\n\n    if (n == max)\n\treturn(one);\n    if (n == 0.0)\n\treturn(zero);\n    /* if n == 2^(numVars-1), return a single variable */\n    if (n == max2)\n\treturn vars[index];\n    else if (n > max2) {\n\t/* When n > 2^(numVars-1), a single variable vars[index]\n\t** contains 2^(numVars-1) minterms. The rest are extracted\n\t** from a constant with 1 less variable.\n\t*/\n\tq = mintermsFromUniverse(manager,vars,numVars-1,(n-max2),index+1);\n\tif (q == NULL)\n\t    return(NULL);\n\tcuddRef(q);\n\tresult = cuddBddIteRecur(manager,vars[index],one,q);\n    } else {\n\t/* When n < 2^(numVars-1), a literal of variable vars[index]\n\t** is selected. The required n minterms are extracted from a\n\t** constant with 1 less variable.\n\t*/\n\tq = mintermsFromUniverse(manager,vars,numVars-1,n,index+1);\n\tif (q == NULL)\n\t    return(NULL);\n\tcuddRef(q);\n\tresult = cuddBddAndRecur(manager,vars[index],q);\n    }\n    \n    if (result == NULL) {\n\tCudd_RecursiveDeref(manager,q);\n\treturn(NULL);\n    }\n    cuddRef(result);\n    Cudd_RecursiveDeref(manager,q);\n    cuddDeref(result);\n    return(result);\n\n} /* end of mintermsFromUniverse */\n\n\n/**\n  @brief Annotates every node in the %BDD node with its minterm count.\n\n  @details In this function, every node and the minterm count\n  represented by it are stored in a hash table.\n\n  @sideeffect Fills up 'table' with the pair <node,minterm_count>.\n\n*/\nstatic double\nbddAnnotateMintermCount(\n  DdManager * manager,\n  DdNode * node,\n  double  max,\n  st_table * table)\n{\n\n    DdNode *N,*Nv,*Nnv;\n    double min_v,min_nv;\n    double min_N;\n    double *pmin;\n    double *dummy;\n\n    statLine(manager);\n    N = Cudd_Regular(node);\n    if (cuddIsConstant(N)) {\n\tif (node == DD_ONE(manager)) {\n\t    return(max);\n\t} else {\n\t    return(0.0);\n\t}\n    }\n\n    if (st_lookup(table, node, (void **) &dummy)) {\n\treturn(*dummy);\n    }\t\n  \n    Nv = cuddT(N);\n    Nnv = cuddE(N);\n    if (N != node) {\n\tNv = Cudd_Not(Nv);\n\tNnv = Cudd_Not(Nnv);\n    }\n\n    /* Recur on the two branches. */\n    min_v  = bddAnnotateMintermCount(manager,Nv,max,table) / 2.0;\n    if (min_v == (double)CUDD_OUT_OF_MEM)\n\treturn ((double)CUDD_OUT_OF_MEM);\n    min_nv = bddAnnotateMintermCount(manager,Nnv,max,table) / 2.0;\n    if (min_nv == (double)CUDD_OUT_OF_MEM)\n\treturn ((double)CUDD_OUT_OF_MEM);\n    min_N  = min_v + min_nv;\n\n    pmin = ALLOC(double,1);\n    if (pmin == NULL) {\n\tmanager->errorCode = CUDD_MEMORY_OUT;\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    *pmin = min_N;\n\n    if (st_insert(table, node, pmin) == ST_OUT_OF_MEM) {\n\tFREE(pmin);\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    \n    return(min_N);\n\n} /* end of bddAnnotateMintermCount */\n"
  },
  {
    "path": "cudd/cudd/cuddSubsetHB.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Procedure to subset the given %BDD by choosing the heavier\n  branches.\n\n  @see cuddSubsetSP.c\n\n  @author Kavita Ravi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifdef __STDC__\n#include <float.h>\n#else\n#define DBL_MAX_EXP 1024\n#endif\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define\tDEFAULT_PAGE_SIZE 2048\n#define\tDEFAULT_NODE_DATA_PAGE_SIZE 1024\n#define INITIAL_PAGES 128\n\n#undef max\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\ntypedef struct NodeData NodeData_t;\n\ntypedef struct SubsetInfo SubsetInfo_t;\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Data structure to store the information on each node.\n\n * @details It keeps the number of minterms represented by the DAG\n * rooted at this node in terms of the number of variables specified\n * by the user, number of nodes in this DAG and the number of nodes of\n * its child with lesser number of minterms that are not shared by the\n * child with more minterms.\n */\nstruct NodeData {\n    double *mintermPointer;\n    int *nodesPointer;\n    int *lightChildNodesPointer;\n};\n\n/**\n * @brief Miscellaneous info.\n */\nstruct SubsetInfo {\n    DdNode\t*zero, *one; /**< constant functions */\n    double\t**mintermPages;\t/**< pointers to the pages */\n    int\t\t**nodePages; /**< pointers to the pages */\n    int\t\t**lightNodePages; /**< pointers to the pages */\n    double\t*currentMintermPage; /**< pointer to the current page */\n    double\tmax; /**< to store the 2^n value of the number of variables */\n    int\t\t*currentNodePage; /**< pointer to the current page */\n    int\t\t*currentLightNodePage; /**< pointer to the current page */\n    int\t\tpageIndex; /**< index to next element */\n    int\t\tpage; /**< index to current page */\n    int\t\tpageSize; /**< page size */\n    int         maxPages; /**< number of page pointers */\n    NodeData_t\t*currentNodeDataPage; /**< pointer to the current page */\n    int\t\tnodeDataPage; /**< index to next element */\n    int\t\tnodeDataPageIndex; /**< index to next element */\n    NodeData_t\t**nodeDataPages; /**< index to current page */\n    int\t\tnodeDataPageSize; /**< page size */\n    int         maxNodeDataPages; /**< number of page pointers */\n    int memOut;\n#ifdef DEBUG\n    int\t\tnum_calls;\n#endif\n};\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void ResizeNodeDataPages (SubsetInfo_t * info);\nstatic void ResizeCountMintermPages (SubsetInfo_t * info);\nstatic void ResizeCountNodePages (SubsetInfo_t * info);\nstatic double SubsetCountMintermAux (DdNode *node, double max, st_table *table, SubsetInfo_t * info);\nstatic st_table * SubsetCountMinterm (DdNode *node, int nvars, SubsetInfo_t * info);\nstatic int SubsetCountNodesAux (DdNode *node, st_table *table, double max, SubsetInfo_t * info);\nstatic int SubsetCountNodes (DdNode *node, st_table *table, int nvars, SubsetInfo_t * info);\nstatic void StoreNodes (st_table *storeTable, DdManager *dd, DdNode *node);\nstatic DdNode * BuildSubsetBdd (DdManager *dd, DdNode *node, int *size, st_table *visitedTable, int threshold, st_table *storeTable, st_table *approxTable, SubsetInfo_t * info);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Extracts a dense subset from a %BDD with the heavy branch\n  heuristic.\n\n  @details This procedure builds a subset by throwing away one of the\n  children of each node, starting from the root, until the result is\n  small enough. The child that is eliminated from the result is the\n  one that contributes the fewer minterms.  The parameter numVars is\n  the maximum number of variables to be used in minterm calculation\n  and node count calculation.  The optimal number should be as close\n  as possible to the size of the support of f.  However, it is safe to\n  pass the value returned by Cudd_ReadSize for numVars when the number\n  of variables is under 1023.  If numVars is larger than 1023, it will\n  overflow. If a 0 parameter is passed then the procedure will compute\n  a value which will avoid overflow but will cause underflow with 2046\n  variables or more.\n\n  @return a pointer to the %BDD of the subset if successful. NULL if\n  the procedure runs out of memory.\n\n  @sideeffect None\n\n  @see Cudd_SubsetShortPaths Cudd_SupersetHeavyBranch Cudd_ReadSize\n\n*/\nDdNode *\nCudd_SubsetHeavyBranch(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be subset */,\n  int  numVars /**< number of variables in the support of f */,\n  int  threshold /**< maximum number of nodes in the subset */)\n{\n    DdNode *subset;\n\n    do {\n\tdd->reordered = 0;\n\tsubset = cuddSubsetHeavyBranch(dd, f, numVars, threshold);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(subset);\n\n} /* end of Cudd_SubsetHeavyBranch */\n\n\n/**\n  @brief Extracts a dense superset from a %BDD with the heavy branch\n  heuristic.\n\n  @details The procedure is identical to the subset procedure except\n  for the fact that it receives the complement of the given\n  function. Extracting the subset of the complement function is\n  equivalent to extracting the superset of the function. This\n  procedure builds a superset by throwing away one of the children of\n  each node starting from the root of the complement function, until\n  the result is small enough. The child that is eliminated from the\n  result is the one that contributes the fewer minterms.  The\n  parameter numVars is the maximum number of variables to be used in\n  minterm calculation and node count calculation.  The optimal number\n  should be as close as possible to the size of the support of f.\n  However, it is safe to pass the value returned by Cudd_ReadSize for\n  numVars when the number of variables is under 1023.  If numVars is\n  larger than 1023, it will overflow. If a 0 parameter is passed then\n  the procedure will compute a value which will avoid overflow but\n  will cause underflow with 2046 variables or more.\n\n  @return a pointer to the %BDD of the superset if successful. NULL if\n  intermediate result causes the procedure to run out of memory.\n\n  @sideeffect None\n\n  @see Cudd_SubsetHeavyBranch Cudd_SupersetShortPaths Cudd_ReadSize\n\n*/\nDdNode *\nCudd_SupersetHeavyBranch(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be superset */,\n  int  numVars /**< number of variables in the support of f */,\n  int  threshold /**< maximum number of nodes in the superset */)\n{\n    DdNode *subset, *g;\n\n    g = Cudd_Not(f);\n    do {\n\tdd->reordered = 0;\n\tsubset = cuddSubsetHeavyBranch(dd, g, numVars, threshold);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(Cudd_NotCond(subset, (subset != NULL)));\n\n} /* end of Cudd_SupersetHeavyBranch */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief The main procedure that returns a subset by choosing the heavier\n  branch in the %BDD.\n\n  @details Here a subset %BDD is built by throwing away one of the\n  children. Starting at root, annotate each node with the number of\n  minterms (in terms of the total number of variables specified -\n  numVars), number of nodes taken by the DAG rooted at this node and\n  number of additional nodes taken by the child that has the lesser\n  minterms. The child with the lower number of minterms is thrown away\n  and a dyanmic count of the nodes of the subset is kept. Once the\n  threshold is reached the subset is returned to the calling\n  procedure.\n\n  @sideeffect None\n\n  @see Cudd_SubsetHeavyBranch\n\n*/\nDdNode *\ncuddSubsetHeavyBranch(\n  DdManager * dd /**< %DD manager */,\n  DdNode * f /**< current %DD */,\n  int  numVars /**< maximum number of variables */,\n  int  threshold /**< threshold size for the subset */)\n{\n\n    int i, *size;\n    st_table *visitedTable;\n    int numNodes;\n    NodeData_t *currNodeQual;\n    DdNode *subset;\n    st_table *storeTable, *approxTable;\n    DdNode *key, *value;\n    st_generator *stGen;\n    SubsetInfo_t info;\n\n    if (f == NULL) {\n\tfprintf(dd->err, \"Cannot subset, nil object\\n\");\n\tdd->errorCode = CUDD_INVALID_ARG;\n\treturn(NULL);\n    }\n\n    /* If user does not know numVars value, set it to the maximum\n     * exponent that the pow function can take. The -1 is due to the\n     * discrepancy in the value that pow takes and the value that\n     * log gives.\n     */\n    if (numVars == 0) {\n\t/* set default value */\n\tnumVars = DBL_MAX_EXP - 1;\n    }\n\n    if (Cudd_IsConstantInt(f)) {\n\treturn(f);\n    }\n\n    info.one  = Cudd_ReadOne(dd);\n    info.zero = Cudd_Not(info.one);\n    info.mintermPages = NULL;\n    info.nodePages = info.lightNodePages = NULL;\n    info.currentMintermPage = NULL;\n    info.max = pow(2.0, (double)numVars);\n    info.currentNodePage = info.currentLightNodePage = NULL;\n    info.pageIndex = info.page = 0;\n    info.pageSize = DEFAULT_PAGE_SIZE;\n    info.maxPages = 0;\n    info.currentNodeDataPage = NULL;\n    info.nodeDataPage = info.nodeDataPageIndex = 0;\n    info.nodeDataPages = NULL;\n    info.nodeDataPageSize = DEFAULT_NODE_DATA_PAGE_SIZE;\n    info.maxNodeDataPages = 0;\n    info.memOut = 0;\n#ifdef DEBUG\n    info.num_calls = 0;\n#endif\n\n    /* Create visited table where structures for node data are allocated and\n       stored in a st_table */\n    visitedTable = SubsetCountMinterm(f, numVars, &info);\n    if ((visitedTable == NULL) || info.memOut) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    numNodes = SubsetCountNodes(f, visitedTable, numVars, &info);\n    if (info.memOut) {\n\t(void) fprintf(dd->err, \"Out-of-memory; Cannot subset\\n\");\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n\n    if (st_lookup(visitedTable, f, (void **) &currNodeQual) == 0) {\n\tfprintf(dd->err,\n\t\t\"Something is wrong, ought to be node quality table\\n\");\n\tdd->errorCode = CUDD_INTERNAL_ERROR;\n    }\n\n    size = ALLOC(int, 1);\n    if (size == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    *size = numNodes;\n\n    /* table to store nodes being created. */\n    storeTable = st_init_table(st_ptrcmp, st_ptrhash);\n    /* insert the constant */\n    cuddRef(info.one);\n    if (st_insert(storeTable, Cudd_ReadOne(dd), NULL) ==\n\tST_OUT_OF_MEM) {\n\tfprintf(dd->out, \"Something wrong, st_table insert failed\\n\");\n    }\n    /* table to store approximations of nodes */\n    approxTable = st_init_table(st_ptrcmp, st_ptrhash);\n    subset = (DdNode *)BuildSubsetBdd(dd, f, size, visitedTable, threshold,\n\t\t\t\t      storeTable, approxTable, &info);\n    if (subset != NULL) {\n\tcuddRef(subset);\n    }\n\n    if (info.memOut) {\n        dd->errorCode = CUDD_MEMORY_OUT;\n        dd->reordered = 0;\n    }\n\n    stGen = st_init_gen(approxTable);\n    if (stGen == NULL) {\n\tst_free_table(approxTable);\n\treturn(NULL);\n    }\n    while(st_gen(stGen, (void **) &key, (void **) &value)) {\n\tCudd_RecursiveDeref(dd, value);\n    }\n    st_free_gen(stGen); stGen = NULL;\n    st_free_table(approxTable);\n\n    stGen = st_init_gen(storeTable);\n    if (stGen == NULL) {\n\tst_free_table(storeTable);\n\treturn(NULL);\n    }\n    while(st_gen(stGen, (void **) &key, (void **) &value)) {\n\tCudd_RecursiveDeref(dd, key);\n    }\n    st_free_gen(stGen); stGen = NULL;\n    st_free_table(storeTable);\n\n    for (i = 0; i <= info.page; i++) {\n\tFREE(info.mintermPages[i]);\n    }\n    FREE(info.mintermPages);\n    for (i = 0; i <= info.page; i++) {\n\tFREE(info.nodePages[i]);\n    }\n    FREE(info.nodePages);\n    for (i = 0; i <= info.page; i++) {\n\tFREE(info.lightNodePages[i]);\n    }\n    FREE(info.lightNodePages);\n    for (i = 0; i <= info.nodeDataPage; i++) {\n\tFREE(info.nodeDataPages[i]);\n    }\n    FREE(info.nodeDataPages);\n    st_free_table(visitedTable);\n    FREE(size);\n#if 0\n    (void) Cudd_DebugCheck(dd);\n    (void) Cudd_CheckKeys(dd);\n#endif\n\n    if (subset != NULL) {\n#ifdef DD_DEBUG\n      if (!Cudd_bddLeq(dd, subset, f)) {\n\t    fprintf(dd->err, \"Wrong subset\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t    return(NULL);\n      }\n#endif\n\tcuddDeref(subset);\n    }\n    return(subset);\n\n} /* end of cuddSubsetHeavyBranch */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Resize the number of pages allocated to store the node data.\n\n  @details The procedure moves the counter to the next page when the\n  end of the page is reached and allocates new pages when necessary.\n\n  @sideeffect Changes the size of pages, page, page index, maximum\n  number of pages freeing stuff in case of memory out. \n\n*/\nstatic void\nResizeNodeDataPages(SubsetInfo_t * info)\n{\n    int i;\n    NodeData_t **newNodeDataPages;\n\n    info->nodeDataPage++;\n    /* If the current page index is larger than the number of pages\n     * allocated, allocate a new page array. Page numbers are incremented by\n     * INITIAL_PAGES\n     */\n    if (info->nodeDataPage == info->maxNodeDataPages) {\n\tnewNodeDataPages = ALLOC(NodeData_t *, info->maxNodeDataPages + INITIAL_PAGES);\n\tif (newNodeDataPages == NULL) {\n\t    for (i = 0; i < info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\t    FREE(info->nodeDataPages);\n\t    info->memOut = 1;\n\t    return;\n\t} else {\n\t    for (i = 0; i < info->maxNodeDataPages; i++) {\n\t\tnewNodeDataPages[i] = info->nodeDataPages[i];\n\t    }\n\t    /* Increase total page count */\n\t    info->maxNodeDataPages += INITIAL_PAGES;\n\t    FREE(info->nodeDataPages);\n\t    info->nodeDataPages = newNodeDataPages;\n\t}\n    }\n    /* Allocate a new page */\n    info->currentNodeDataPage = info->nodeDataPages[info->nodeDataPage] =\n\tALLOC(NodeData_t ,info->nodeDataPageSize);\n    if (info->currentNodeDataPage == NULL) {\n\tfor (i = 0; i < info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\tFREE(info->nodeDataPages);\n\tinfo->memOut = 1;\n\treturn;\n    }\n    /* reset page index */\n    info->nodeDataPageIndex = 0;\n    return;\n\n} /* end of ResizeNodeDataPages */\n\n\n/**\n  @brief Resize the number of pages allocated to store the minterm\n  counts. \n\n  @details The procedure  moves the counter to the next page when the\n  end of the page is reached and allocates new pages when necessary.\n\n  @sideeffect Changes the size of minterm pages, page, page index, maximum\n  number of pages freeing stuff in case of memory out. \n\n*/\nstatic void\nResizeCountMintermPages(SubsetInfo_t * info)\n{\n    int i;\n    double **newMintermPages;\n\n    info->page++;\n    /* If the current page index is larger than the number of pages\n     * allocated, allocate a new page array. Page numbers are incremented by\n     * INITIAL_PAGES\n     */\n    if (info->page == info->maxPages) {\n\tnewMintermPages = ALLOC(double *, info->maxPages + INITIAL_PAGES);\n\tif (newMintermPages == NULL) {\n\t    for (i = 0; i < info->page; i++) FREE(info->mintermPages[i]);\n\t    FREE(info->mintermPages);\n\t    info->memOut = 1;\n\t    return;\n\t} else {\n\t    for (i = 0; i < info->maxPages; i++) {\n\t\tnewMintermPages[i] = info->mintermPages[i];\n\t    }\n\t    /* Increase total page count */\n\t    info->maxPages += INITIAL_PAGES;\n\t    FREE(info->mintermPages);\n\t    info->mintermPages = newMintermPages;\n\t}\n    }\n    /* Allocate a new page */\n    info->currentMintermPage = info->mintermPages[info->page] = ALLOC(double,info->pageSize);\n    if (info->currentMintermPage == NULL) {\n\tfor (i = 0; i < info->page; i++) FREE(info->mintermPages[i]);\n\tFREE(info->mintermPages);\n\tinfo->memOut = 1;\n\treturn;\n    }\n    /* reset page index */\n    info->pageIndex = 0;\n    return;\n\n} /* end of ResizeCountMintermPages */\n\n\n/**\n  @brief Resize the number of pages allocated to store the node counts.\n\n  @details The procedure moves the counter to the next page when the\n  end of the page is reached and allocates new pages when necessary.\n\n  @sideeffect Changes the size of pages, page, page index, maximum\n  number of pages freeing stuff in case of memory out.\n\n*/\nstatic void\nResizeCountNodePages(SubsetInfo_t * info)\n{\n    int i;\n    int **newNodePages;\n\n    info->page++;\n\n    /* If the current page index is larger than the number of pages\n     * allocated, allocate a new page array. The number of pages is incremented\n     * by INITIAL_PAGES.\n     */\n    if (info->page == info->maxPages) {\n\tnewNodePages = ALLOC(int *, info->maxPages + INITIAL_PAGES);\n\tif (newNodePages == NULL) {\n\t    for (i = 0; i < info->page; i++) FREE(info->nodePages[i]);\n\t    FREE(info->nodePages);\n\t    for (i = 0; i < info->page; i++) FREE(info->lightNodePages[i]);\n\t    FREE(info->lightNodePages);\n\t    info->memOut = 1;\n\t    return;\n\t} else {\n\t    for (i = 0; i < info->maxPages; i++) {\n\t\tnewNodePages[i] = info->nodePages[i];\n\t    }\n\t    FREE(info->nodePages);\n\t    info->nodePages = newNodePages;\n\t}\n\n\tnewNodePages = ALLOC(int *, info->maxPages + INITIAL_PAGES);\n\tif (newNodePages == NULL) {\n\t    for (i = 0; i < info->page; i++) FREE(info->nodePages[i]);\n\t    FREE(info->nodePages);\n\t    for (i = 0; i < info->page; i++) FREE(info->lightNodePages[i]);\n\t    FREE(info->lightNodePages);\n\t    info->memOut = 1;\n\t    return;\n\t} else {\n\t    for (i = 0; i < info->maxPages; i++) {\n\t\tnewNodePages[i] = info->lightNodePages[i];\n\t    }\n\t    FREE(info->lightNodePages);\n\t    info->lightNodePages = newNodePages;\n\t}\n\t/* Increase total page count */\n\tinfo->maxPages += INITIAL_PAGES;\n    }\n    /* Allocate a new page */\n    info->currentNodePage = info->nodePages[info->page] = ALLOC(int,info->pageSize);\n    if (info->currentNodePage == NULL) {\n\tfor (i = 0; i < info->page; i++) FREE(info->nodePages[i]);\n\tFREE(info->nodePages);\n\tfor (i = 0; i < info->page; i++) FREE(info->lightNodePages[i]);\n\tFREE(info->lightNodePages);\n\tinfo->memOut = 1;\n\treturn;\n    }\n    /* Allocate a new page */\n    info->currentLightNodePage = info->lightNodePages[info->page]\n        = ALLOC(int,info->pageSize);\n    if (info->currentLightNodePage == NULL) {\n\tfor (i = 0; i <= info->page; i++) FREE(info->nodePages[i]);\n\tFREE(info->nodePages);\n\tfor (i = 0; i < info->page; i++) FREE(info->lightNodePages[i]);\n\tFREE(info->lightNodePages);\n\tinfo->memOut = 1;\n\treturn;\n    }\n    /* reset page index */\n    info->pageIndex = 0;\n    return;\n\n} /* end of ResizeCountNodePages */\n\n\n/**\n  @brief Recursively counts minterms of each node in the DAG.\n\n  @details Similar to the cuddCountMintermAux which recursively counts\n  the number of minterms for the dag rooted at each node in terms of\n  the total number of variables (max). This procedure creates the node\n  data structure and stores the minterm count as part of the node data\n  structure.\n\n  @sideeffect Creates structures of type node quality and fills the st_table\n\n  @see SubsetCountMinterm\n\n*/\nstatic double\nSubsetCountMintermAux(\n  DdNode * node /**< function to analyze */,\n  double  max /**< number of minterms of constant 1 */,\n  st_table * table /**< visitedTable table */,\n  SubsetInfo_t * info /**< miscellaneous info */)\n{\n\n    DdNode\t*N,*Nv,*Nnv; /* nodes to store cofactors  */\n    double\tmin,*pmin; /* minterm count */\n    double\tmin1, min2; /* minterm count */\n    NodeData_t *dummy;\n    NodeData_t *newEntry;\n    int i;\n\n#ifdef DEBUG\n    info->num_calls++;\n#endif\n\n    /* Constant case */\n    if (Cudd_IsConstantInt(node)) {\n\tif (node == info->zero) {\n\t    return(0.0);\n\t} else {\n\t    return(max);\n\t}\n    } else {\n\n\t/* check if entry for this node exists */\n        if (st_lookup(table, node, (void **) &dummy)) {\n\t    min = *(dummy->mintermPointer);\n\t    return(min);\n\t}\n\n\t/* Make the node regular to extract cofactors */\n\tN = Cudd_Regular(node);\n\n\t/* store the cofactors */\n\tNv = Cudd_T(N);\n\tNnv = Cudd_E(N);\n\n\tNv = Cudd_NotCond(Nv, Cudd_IsComplement(node));\n\tNnv = Cudd_NotCond(Nnv, Cudd_IsComplement(node));\n\n\tmin1 =  SubsetCountMintermAux(Nv, max,table,info)/2.0;\n\tif (info->memOut) return(0.0);\n\tmin2 =  SubsetCountMintermAux(Nnv,max,table,info)/2.0;\n\tif (info->memOut) return(0.0);\n\tmin = (min1+min2);\n\n\t/* if page index is at the bottom, then create a new page */\n\tif (info->pageIndex == info->pageSize) ResizeCountMintermPages(info);\n\tif (info->memOut) {\n\t    for (i = 0; i <= info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\t    FREE(info->nodeDataPages);\n\t    st_free_table(table);\n\t    return(0.0);\n\t}\n\n\t/* point to the correct location in the page */\n\tpmin = info->currentMintermPage + info->pageIndex;\n\tinfo->pageIndex++;\n\n\t/* store the minterm count of this node in the page */\n\t*pmin = min;\n\n\t/* Note I allocate the struct here. Freeing taken care of later */\n\tif (info->nodeDataPageIndex == info->nodeDataPageSize)\n            ResizeNodeDataPages(info);\n\tif (info->memOut) {\n\t    for (i = 0; i <= info->page; i++) FREE(info->mintermPages[i]);\n\t    FREE(info->mintermPages);\n\t    st_free_table(table);\n\t    return(0.0);\n\t}\n\n\tnewEntry = info->currentNodeDataPage + info->nodeDataPageIndex;\n\tinfo->nodeDataPageIndex++;\n\n\t/* points to the correct location in the page */\n\tnewEntry->mintermPointer = pmin;\n\t/* initialize this field of the Node Quality structure */\n\tnewEntry->nodesPointer = NULL;\n\n\t/* insert entry for the node in the table */\n\tif (st_insert(table,node, newEntry) == ST_OUT_OF_MEM) {\n\t    info->memOut = 1;\n\t    for (i = 0; i <= info->page; i++) FREE(info->mintermPages[i]);\n\t    FREE(info->mintermPages);\n\t    for (i = 0; i <= info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\t    FREE(info->nodeDataPages);\n\t    st_free_table(table);\n\t    return(0.0);\n\t}\n\treturn(min);\n    }\n\n} /* end of SubsetCountMintermAux */\n\n\n/**\n  @brief Counts minterms of each node in the DAG\n\n  @details Similar to the Cudd_CountMinterm procedure except this\n  returns the minterm count for all the nodes in the bdd in an\n  st_table.\n\n  @sideeffect none\n\n  @see SubsetCountMintermAux\n\n*/\nstatic st_table *\nSubsetCountMinterm(\n  DdNode * node /**< function to be analyzed */,\n  int nvars /**< number of variables node depends on */,\n  SubsetInfo_t * info /**< miscellaneous info */)\n{\n    st_table\t*table;\n    int i;\n\n\n#ifdef DEBUG\n    info->num_calls = 0;\n#endif\n\n    info->max = pow(2.0,(double) nvars);\n    table = st_init_table(st_ptrcmp,st_ptrhash);\n    if (table == NULL) goto OUT_OF_MEM;\n    info->maxPages = INITIAL_PAGES;\n    info->mintermPages = ALLOC(double *,info->maxPages);\n    if (info->mintermPages == NULL) {\n\tst_free_table(table);\n\tgoto OUT_OF_MEM;\n    }\n    info->page = 0;\n    info->currentMintermPage = ALLOC(double,info->pageSize);\n    info->mintermPages[info->page] = info->currentMintermPage;\n    if (info->currentMintermPage == NULL) {\n\tFREE(info->mintermPages);\n\tst_free_table(table);\n\tgoto OUT_OF_MEM;\n    }\n    info->pageIndex = 0;\n    info->maxNodeDataPages = INITIAL_PAGES;\n    info->nodeDataPages = ALLOC(NodeData_t *, info->maxNodeDataPages);\n    if (info->nodeDataPages == NULL) {\n\tfor (i = 0; i <= info->page ; i++) FREE(info->mintermPages[i]);\n\tFREE(info->mintermPages);\n\tst_free_table(table);\n\tgoto OUT_OF_MEM;\n    }\n    info->nodeDataPage = 0;\n    info->currentNodeDataPage = ALLOC(NodeData_t ,info->nodeDataPageSize);\n    info->nodeDataPages[info->nodeDataPage] = info->currentNodeDataPage;\n    if (info->currentNodeDataPage == NULL) {\n\tfor (i = 0; i <= info->page ; i++) FREE(info->mintermPages[i]);\n\tFREE(info->mintermPages);\n\tFREE(info->nodeDataPages);\n\tst_free_table(table);\n\tgoto OUT_OF_MEM;\n    }\n    info->nodeDataPageIndex = 0;\n\n    (void) SubsetCountMintermAux(node,info->max,table,info);\n    if (info->memOut) goto OUT_OF_MEM;\n    return(table);\n\nOUT_OF_MEM:\n    info->memOut = 1;\n    return(NULL);\n\n} /* end of SubsetCountMinterm */\n\n\n/**\n  @brief Recursively counts the number of nodes under the dag.\n  Also counts the number of nodes under the lighter child of\n  this node.\n\n  @details Note that the same dag may be the lighter child of two\n  different nodes and have different counts. As with the minterm\n  counts, the node counts are stored in pages to be space efficient\n  and the address for these node counts are stored in an st_table\n  associated to each node.\n\n  @sideeffect Updates the node data table with node counts\n\n  @see SubsetCountNodes\n\n*/\nstatic int\nSubsetCountNodesAux(\n  DdNode * node /**< current node */,\n  st_table * table /**< table to update node count, also serves as visited table. */,\n  double  max /**< maximum number of variables */,\n  SubsetInfo_t * info)\n{\n    int tval, eval, i;\n    DdNode *N, *Nv, *Nnv;\n    double minNv, minNnv;\n    NodeData_t *dummyN, *dummyNv, *dummyNnv, *dummyNBar;\n    int *pmin, *pminBar, *val;\n\n    if ((node == NULL) || Cudd_IsConstantInt(node))\n\treturn(0);\n\n    /* if this node has been processed do nothing */\n    if (st_lookup(table, node, (void **) &dummyN) == 1) {\n\tval = dummyN->nodesPointer;\n\tif (val != NULL)\n\t    return(0);\n    } else {\n\treturn(0);\n    }\n\n    N  = Cudd_Regular(node);\n    Nv = Cudd_T(N);\n    Nnv = Cudd_E(N);\n\n    Nv = Cudd_NotCond(Nv, Cudd_IsComplement(node));\n    Nnv = Cudd_NotCond(Nnv, Cudd_IsComplement(node));\n\n    /* find the minterm counts for the THEN and ELSE branches */\n    if (Cudd_IsConstantInt(Nv)) {\n\tif (Nv == info->zero) {\n\t    minNv = 0.0;\n\t} else {\n\t    minNv = max;\n\t}\n    } else {\n\tif (st_lookup(table, Nv, (void **) &dummyNv) == 1)\n\t    minNv = *(dummyNv->mintermPointer);\n\telse {\n\t    return(0);\n\t}\n    }\n    if (Cudd_IsConstantInt(Nnv)) {\n\tif (Nnv == info->zero) {\n\t    minNnv = 0.0;\n\t} else {\n\t    minNnv = max;\n\t}\n    } else {\n\tif (st_lookup(table, Nnv, (void **) &dummyNnv) == 1) {\n\t    minNnv = *(dummyNnv->mintermPointer);\n\t}\n\telse {\n\t    return(0);\n\t}\n    }\n\n\n    /* recur based on which has larger minterm, */\n    if (minNv >= minNnv) {\n\ttval = SubsetCountNodesAux(Nv, table, max, info);\n\tif (info->memOut) return(0);\n\teval = SubsetCountNodesAux(Nnv, table, max, info);\n\tif (info->memOut) return(0);\n\n\t/* store the node count of the lighter child. */\n\tif (info->pageIndex == info->pageSize) ResizeCountNodePages(info);\n\tif (info->memOut) {\n\t    for (i = 0; i <= info->page; i++) FREE(info->mintermPages[i]);\n\t    FREE(info->mintermPages);\n\t    for (i = 0; i <= info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\t    FREE(info->nodeDataPages);\n\t    st_free_table(table);\n\t    return(0);\n\t}\n\tpmin = info->currentLightNodePage + info->pageIndex;\n\t*pmin = eval; /* Here the ELSE child is lighter */\n\tdummyN->lightChildNodesPointer = pmin;\n\n    } else {\n\teval = SubsetCountNodesAux(Nnv, table, max, info);\n\tif (info->memOut) return(0);\n\ttval = SubsetCountNodesAux(Nv, table, max, info);\n\tif (info->memOut) return(0);\n\n\t/* store the node count of the lighter child. */\n\tif (info->pageIndex == info->pageSize) ResizeCountNodePages(info);\n\tif (info->memOut) {\n\t    for (i = 0; i <= info->page; i++) FREE(info->mintermPages[i]);\n\t    FREE(info->mintermPages);\n\t    for (i = 0; i <= info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\t    FREE(info->nodeDataPages);\n\t    st_free_table(table);\n\t    return(0);\n\t}\n\tpmin = info->currentLightNodePage + info->pageIndex;\n\t*pmin = tval; /* Here the THEN child is lighter */\n\tdummyN->lightChildNodesPointer = pmin;\n\n    }\n    /* updating the page index for node count storage. */\n    pmin = info->currentNodePage + info->pageIndex;\n    *pmin = tval + eval + 1;\n    dummyN->nodesPointer = pmin;\n\n    /* pageIndex is parallel page index for count_nodes and count_lightNodes */\n    info->pageIndex++;\n\n    /* if this node has been reached first, it belongs to a heavier\n       branch. Its complement will be reached later on a lighter branch.\n       Hence the complement has zero node count. */\n\n    if (st_lookup(table, Cudd_Not(node), (void **) &dummyNBar) == 1)  {\n\tif (info->pageIndex == info->pageSize) ResizeCountNodePages(info);\n\tif (info->memOut) {\n\t    for (i = 0; i < info->page; i++) FREE(info->mintermPages[i]);\n\t    FREE(info->mintermPages);\n\t    for (i = 0; i < info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\t    FREE(info->nodeDataPages);\n\t    st_free_table(table);\n\t    return(0);\n\t}\n\tpminBar = info->currentLightNodePage + info->pageIndex;\n\t*pminBar = 0;\n\tdummyNBar->lightChildNodesPointer = pminBar;\n\t/* The lighter child has less nodes than the parent.\n\t * So if parent 0 then lighter child zero\n\t */\n\tif (info->pageIndex == info->pageSize) ResizeCountNodePages(info);\n\tif (info->memOut) {\n\t    for (i = 0; i < info->page; i++) FREE(info->mintermPages[i]);\n\t    FREE(info->mintermPages);\n\t    for (i = 0; i < info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\t    FREE(info->nodeDataPages);\n\t    st_free_table(table);\n\t    return(0);\n\t}\n\tpminBar = info->currentNodePage + info->pageIndex;\n\t*pminBar = 0;\n\tdummyNBar->nodesPointer = pminBar ; /* maybe should point to zero */\n\n\tinfo->pageIndex++;\n    }\n    return(*pmin);\n} /*end of SubsetCountNodesAux */\n\n\n/**\n  @brief Counts the nodes under the current node and its lighter child.\n\n  @details Calls a recursive procedure to count the number of nodes of\n  a DAG rooted at a particular node and the number of nodes taken by\n  its lighter child.\n\n  @sideeffect None\n\n  @see SubsetCountNodesAux\n\n*/\nstatic int\nSubsetCountNodes(\n  DdNode * node /**< function to be analyzed */,\n  st_table * table /**< node quality table */,\n  int  nvars /**< number of variables node depends on */,\n  SubsetInfo_t * info /**< miscellaneous info */)\n{\n    int\tnum;\n    int i;\n\n#ifdef DEBUG\n    info->num_calls = 0;\n#endif\n\n    info->max = pow(2.0,(double) nvars);\n    info->maxPages = INITIAL_PAGES;\n    info->nodePages = ALLOC(int *, info->maxPages);\n    if (info->nodePages == NULL)  {\n\tgoto OUT_OF_MEM;\n    }\n\n    info->lightNodePages = ALLOC(int *, info->maxPages);\n    if (info->lightNodePages == NULL) {\n\tfor (i = 0; i <= info->page; i++) FREE(info->mintermPages[i]);\n\tFREE(info->mintermPages);\n\tfor (i = 0; i <= info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\tFREE(info->nodeDataPages);\n\tFREE(info->nodePages);\n\tgoto OUT_OF_MEM;\n    }\n\n    info->page = 0;\n    info->currentNodePage = info->nodePages[info->page] =\n        ALLOC(int,info->pageSize);\n    if (info->currentNodePage == NULL) {\n\tfor (i = 0; i <= info->page; i++) FREE(info->mintermPages[i]);\n\tFREE(info->mintermPages);\n\tfor (i = 0; i <= info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\tFREE(info->nodeDataPages);\n\tFREE(info->lightNodePages);\n\tFREE(info->nodePages);\n\tgoto OUT_OF_MEM;\n    }\n\n    info->currentLightNodePage = info->lightNodePages[info->page] =\n        ALLOC(int,info->pageSize);\n    if (info->currentLightNodePage == NULL) {\n\tfor (i = 0; i <= info->page; i++) FREE(info->mintermPages[i]);\n\tFREE(info->mintermPages);\n\tfor (i = 0; i <= info->nodeDataPage; i++) FREE(info->nodeDataPages[i]);\n\tFREE(info->nodeDataPages);\n\tFREE(info->currentNodePage);\n\tFREE(info->lightNodePages);\n\tFREE(info->nodePages);\n\tgoto OUT_OF_MEM;\n    }\n\n    info->pageIndex = 0;\n    num = SubsetCountNodesAux(node,table,info->max,info);\n    if (info->memOut) goto OUT_OF_MEM;\n    return(num);\n\nOUT_OF_MEM:\n    info->memOut = 1;\n    return(0);\n\n} /* end of SubsetCountNodes */\n\n\n/**\n  @brief Procedure to recursively store nodes that are retained in the subset.\n\n  @sideeffect None\n\n  @see StoreNodes\n\n*/\nstatic void\nStoreNodes(\n  st_table * storeTable,\n  DdManager * dd,\n  DdNode * node)\n{\n    DdNode *N, *Nt, *Ne;\n    if (Cudd_IsConstantInt(dd)) {\n\treturn;\n    }\n    N = Cudd_Regular(node);\n    if (st_is_member(storeTable, N)) {\n\treturn;\n    }\n    cuddRef(N);\n    if (st_insert(storeTable, N, NULL) == ST_OUT_OF_MEM) {\n\tfprintf(dd->err,\"Something wrong, st_table insert failed\\n\");\n    }\n\n    Nt = Cudd_T(N);\n    Ne = Cudd_E(N);\n\n    StoreNodes(storeTable, dd, Nt);\n    StoreNodes(storeTable, dd, Ne);\n    return;\n\n}\n\n\n/**\n  @brief Builds the subset %BDD using the heavy branch method.\n\n  @details The procedure carries out the building of the subset %BDD\n  starting at the root. Using the three different counts labelling each node,\n  the procedure chooses the heavier branch starting from the root and keeps\n  track of the number of nodes it discards at each step, thus keeping count\n  of the size of the subset %BDD dynamically. Once the threshold is satisfied,\n  the procedure then calls ITE to build the %BDD.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nBuildSubsetBdd(\n  DdManager * dd /**< %DD manager */,\n  DdNode * node /**< current node */,\n  int * size /**< current size of the subset */,\n  st_table * visitedTable /**< visited table storing all node data */,\n  int threshold /**< subsetting threshold */,\n  st_table * storeTable /**< store table */,\n  st_table * approxTable /**< approximation table */,\n  SubsetInfo_t * info /**< miscellaneous info */)\n{\n\n    DdNode *Nv, *Nnv, *N, *topv, *neW;\n    double minNv, minNnv;\n    NodeData_t *currNodeQual;\n    NodeData_t *currNodeQualT;\n    NodeData_t *currNodeQualE;\n    DdNode *ThenBranch, *ElseBranch;\n    int topid;\n    void *dummy;\n\n#ifdef DEBUG\n    info->num_calls++;\n#endif\n    /*If the size of the subset is below the threshold, dont do\n      anything. */\n    if ((*size) <= threshold) {\n      /* store nodes below this, so we can recombine if possible */\n      StoreNodes(storeTable, dd, node);\n      return(node);\n    }\n\n    if (Cudd_IsConstantInt(node))\n\treturn(node);\n\n    /* Look up minterm count for this node. */\n    if (!st_lookup(visitedTable, node, (void **) &currNodeQual)) {\n\tfprintf(dd->err,\n\t\t\"Something is wrong, ought to be in node quality table\\n\");\n    }\n\n    /* Get children. */\n    N = Cudd_Regular(node);\n    Nv = Cudd_T(N);\n    Nnv = Cudd_E(N);\n\n    /* complement if necessary */\n    Nv = Cudd_NotCond(Nv, Cudd_IsComplement(node));\n    Nnv = Cudd_NotCond(Nnv, Cudd_IsComplement(node));\n\n    if (!Cudd_IsConstantInt(Nv)) {\n\t/* find out minterms and nodes contributed by then child */\n\tif (!st_lookup(visitedTable, Nv, (void **) &currNodeQualT)) {\n\t\tfprintf(dd->out,\"Something wrong, couldnt find nodes in node quality table\\n\");\n\t\tdd->errorCode = CUDD_INTERNAL_ERROR;\n\t\treturn(NULL);\n\t    }\n\telse {\n\t    minNv = *(((NodeData_t *)currNodeQualT)->mintermPointer);\n\t}\n    } else {\n\tif (Nv == info->zero) {\n\t    minNv = 0;\n\t} else  {\n\t    minNv = info->max;\n\t}\n    }\n    if (!Cudd_IsConstantInt(Nnv)) {\n\t/* find out minterms and nodes contributed by else child */\n\tif (!st_lookup(visitedTable, Nnv, (void **) &currNodeQualE)) {\n\t    fprintf(dd->out,\"Something wrong, couldnt find nodes in node quality table\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t    return(NULL);\n\t} else {\n\t    minNnv = *(((NodeData_t *)currNodeQualE)->mintermPointer);\n\t}\n    } else {\n\tif (Nnv == info->zero) {\n\t    minNnv = 0;\n\t} else {\n\t    minNnv = info->max;\n\t}\n    }\n\n    /* keep track of size of subset by subtracting the number of\n     * differential nodes contributed by lighter child\n     */\n    *size = (*(size)) - (int)*(currNodeQual->lightChildNodesPointer);\n    if (minNv >= minNnv) { /*SubsetCountNodesAux procedure takes\n\t\t\t     the Then branch in case of a tie */\n\n\t/* recur with the Then branch */\n\tThenBranch = (DdNode *)BuildSubsetBdd(dd, Nv, size, visitedTable,\n                                              threshold, storeTable,\n                                              approxTable, info);\n\tif (ThenBranch == NULL) {\n\t    return(NULL);\n\t}\n\tcuddRef(ThenBranch);\n\t/* The Else branch is either a node that already exists in the\n\t * subset, or one whose approximation has been computed, or\n\t * Zero.\n\t */\n\tif (st_lookup(storeTable, Cudd_Regular(Nnv), &dummy)) {\n            ElseBranch = Nnv;\n            cuddRef(ElseBranch);\n\t} else {\n            if (st_lookup(approxTable, Nnv, &dummy)) {\n                ElseBranch = (DdNode *)dummy;\n                cuddRef(ElseBranch);\n            } else {\n                ElseBranch = info->zero;\n                cuddRef(ElseBranch);\n            }\n\t}\n\n    }\n    else {\n\t/* recur with the Else branch */\n\tElseBranch = (DdNode *)BuildSubsetBdd(dd, Nnv, size, visitedTable,\n                                              threshold, storeTable,\n                                              approxTable, info);\n\tif (ElseBranch == NULL) {\n\t    return(NULL);\n\t}\n\tcuddRef(ElseBranch);\n\t/* The Then branch is either a node that already exists in the\n\t * subset, or one whose approximation has been computed, or\n\t * Zero.\n\t */\n\tif (st_lookup(storeTable, Cudd_Regular(Nv), &dummy)) {\n            ThenBranch = Nv;\n            cuddRef(ThenBranch);\n\t} else {\n            if (st_lookup(approxTable, Nv, &dummy)) {\n                ThenBranch = (DdNode *)dummy;\n                cuddRef(ThenBranch);\n            } else {\n                ThenBranch = info->zero;\n                cuddRef(ThenBranch);\n            }\n\t}\n    }\n\n    /* construct the Bdd with the top variable and the two children */\n    topid = Cudd_NodeReadIndex(N);\n    topv = Cudd_ReadVars(dd, topid);\n    cuddRef(topv);\n    neW =  cuddBddIteRecur(dd, topv, ThenBranch, ElseBranch);\n    if (neW != NULL) {\n      cuddRef(neW);\n    }\n    Cudd_RecursiveDeref(dd, topv);\n    Cudd_RecursiveDeref(dd, ThenBranch);\n    Cudd_RecursiveDeref(dd, ElseBranch);\n\n\n    if (neW == NULL)\n\treturn(NULL);\n    else {\n\t/* store this node in the store table */\n\tif (!st_lookup(storeTable, Cudd_Regular(neW), &dummy)) {\n            cuddRef(neW);\n            if (st_insert(storeTable, Cudd_Regular(neW), NULL) ==\n                ST_OUT_OF_MEM)\n                return (NULL);\n\t}\n\t/* store the approximation for this node */\n\tif (N !=  Cudd_Regular(neW)) {\n\t    if (st_lookup(approxTable, node, &dummy)) {\n\t\tfprintf(dd->err, \"This node should not be in the approximated table\\n\");\n\t    } else {\n\t\tcuddRef(neW);\n\t\tif (st_insert(approxTable, node, neW) ==\n                    ST_OUT_OF_MEM)\n\t\t    return(NULL);\n\t    }\n\t}\n\tcuddDeref(neW);\n\treturn(neW);\n    }\n} /* end of BuildSubsetBdd */\n"
  },
  {
    "path": "cudd/cudd/cuddSubsetSP.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Procedure to subset the given %BDD choosing the shortest paths\n  (largest cubes) in the %BDD.\n\n  @see cuddSubsetHB.c\n\n  @author Kavita Ravi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define DEFAULT_PAGE_SIZE 2048 /* page size to store the BFS queue element type */\n#define DEFAULT_NODE_DIST_PAGE_SIZE 2048 /*  page size to store NodeDist_t type */\n#define MAXSHORTINT\t((DdHalfWord) ~0) /* constant defined to store\n\t\t\t\t\t   * maximum distance of a node\n\t\t\t\t\t   * from the root or the constant\n\t\t\t\t\t   */\n#define INITIAL_PAGES 128 /* number of initial pages for the\n\t\t\t   * queue/NodeDist_t type */\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief structure created to store subset results for each node and\n * distances with odd and even parity of the node from the root and\n * sink.\n *\n * Main data structure in this procedure.\n */\nstruct NodeDist {\n    DdHalfWord oddTopDist;\n    DdHalfWord evenTopDist;\n    DdHalfWord oddBotDist;\n    DdHalfWord evenBotDist;\n    DdNode *regResult;\n    DdNode *compResult;\n};\n\n/**\n   @brief assorted information needed by the BuildSubsetBdd procedure.\n*/\nstruct AssortedInfo {\n    unsigned int maxpath;\n    int findShortestPath;\n    int thresholdReached;\n    st_table *maxpathTable;\n    int threshold;\n};\n\n/**\n * @brief Bookkeeping data structure for subsetting algorithm.\n */\nstruct GlobalInfo {\n    struct NodeDist **nodeDistPages; /**< pointers to the pages */\n    int\t\tnodeDistPageIndex; /**< index to next element */\n    int\t\tnodeDistPage; /**< index to current page */\n    int\t\tnodeDistPageSize; /**< page size */\n    int\t\tmaxNodeDistPages; /**< number of page pointers */\n    struct NodeDist *currentNodeDistPage; /**< current page */\n    DdNode      ***queuePages; /**< pointers to the pages */\n    int\t\tqueuePageIndex;\t/**< index to next element */\n    int\t\tqueuePage; /**< index to current page */\n    int\t\tqueuePageSize; /**< page size */\n    int\t\tmaxQueuePages; /**< number of page pointers */\n    DdNode      **currentQueuePage; /**< current page */\n#ifdef DD_DEBUG\n    int         numCalls;\n    int         hits;\n    int         thishit;\n#endif\n};\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\ntypedef struct NodeDist NodeDist_t;\ntypedef struct GlobalInfo GlobalInfo_t;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void ResizeNodeDistPages (DdManager *dd, GlobalInfo_t *gInfo);\nstatic void ResizeQueuePages (DdManager *dd, GlobalInfo_t *gInfo);\nstatic void CreateTopDist (DdManager *dd, GlobalInfo_t *gInfo, st_table *pathTable, int parentPage, int parentQueueIndex, int topLen, DdNode **childPage, int childQueueIndex, int numParents, FILE *fp);\nstatic int CreateBotDist (DdNode *node, st_table *pathTable, unsigned int *pathLengthArray, FILE *fp);\nstatic st_table * CreatePathTable (DdManager *dd, GlobalInfo_t *gInfo, DdNode *node, unsigned int *pathLengthArray, FILE *fp);\nstatic unsigned int AssessPathLength (unsigned int *pathLengthArray, int threshold, int numVars, unsigned int *excess, FILE *fp);\nstatic DdNode * BuildSubsetBdd (DdManager *dd, GlobalInfo_t *gInfo, st_table *pathTable, DdNode *node, struct AssortedInfo *info, st_table *subsetNodeTable);\nstatic enum st_retval stPathTableDdFree (void *key, void *value, void *arg);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of Exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Extracts a dense subset from a %BDD with the shortest paths\n  heuristic.\n\n  @details This procedure tries to preserve the shortest paths of the\n  input %BDD, because they give many minterms and contribute few nodes.\n  This procedure may increase the number of nodes in trying to create\n  the subset or reduce the number of nodes due to recombination as\n  compared to the original %BDD. Hence the threshold may not be\n  strictly adhered to. In practice, recombination overshadows the\n  increase in the number of nodes and results in small BDDs as\n  compared to the threshold. The hardlimit specifies whether threshold\n  needs to be strictly adhered to. If it is set to 1, the procedure\n  ensures that result is never larger than the specified limit but may\n  be considerably less than the threshold.  The value for numVars\n  should be as close as possible to the size of the support of f for\n  better efficiency. However, it is safe to pass the value returned by\n  Cudd_ReadSize for numVars. If 0 is passed, then the value returned\n  by Cudd_ReadSize is used.\n\n  @return a pointer to the %BDD for the subset if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_SupersetShortPaths Cudd_SubsetHeavyBranch Cudd_ReadSize\n\n*/\nDdNode *\nCudd_SubsetShortPaths(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be subset */,\n  int  numVars /**< number of variables in the support of f */,\n  int  threshold /**< maximum number of nodes in the subset */,\n  int  hardlimit /**< flag: 1 if threshold is a hard limit */)\n{\n    DdNode *subset;\n\n    do {\n\tdd->reordered = 0;\n\tsubset = cuddSubsetShortPaths(dd, f, numVars, threshold, hardlimit);\n    } while(dd->reordered == 1);\n\n    return(subset);\n\n} /* end of Cudd_SubsetShortPaths */\n\n\n/**\n  @brief Extracts a dense superset from a %BDD with the shortest paths\n  heuristic.\n\n  @details The procedure is identical to the subset procedure except\n  for the fact that it receives the complement of the given\n  function. Extracting the subset of the complement function is\n  equivalent to extracting the superset of the function.  This\n  procedure tries to preserve the shortest paths of the complement\n  %BDD, because they give many minterms and contribute few nodes.  This\n  procedure may increase the number of nodes in trying to create the\n  superset or reduce the number of nodes due to recombination as\n  compared to the original %BDD. Hence the threshold may not be\n  strictly adhered to. In practice, recombination overshadows the\n  increase in the number of nodes and results in small BDDs as\n  compared to the threshold.  The hardlimit specifies whether\n  threshold needs to be strictly adhered to. If it is set to 1, the\n  procedure ensures that result is never larger than the specified\n  limit but may be considerably less than the threshold.  The value\n  for numVars should be as close as possible to the size of the\n  support of f for better efficiency.  However, it is safe to pass the\n  value returned by Cudd_ReadSize for numVar.  If 0 is passed, then\n  the value returned by Cudd_ReadSize is used.\n\n  @return a pointer to the %BDD for the superset if successful; NULL\n  otherwise.\n  \n  @sideeffect None\n\n  @see Cudd_SubsetShortPaths Cudd_SupersetHeavyBranch Cudd_ReadSize\n\n*/\nDdNode *\nCudd_SupersetShortPaths(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function to be superset */,\n  int  numVars /**< number of variables in the support of f */,\n  int  threshold /**< maximum number of nodes in the subset */,\n  int  hardlimit /**< flag: 1 if threshold is a hard limit */)\n{\n    DdNode *subset, *g;\n\n    g = Cudd_Not(f);\n    do {\n\tdd->reordered = 0;\n\tsubset = cuddSubsetShortPaths(dd, g, numVars, threshold, hardlimit);\n    } while(dd->reordered == 1);\n\n    return(Cudd_NotCond(subset, (subset != NULL)));\n\n} /* end of Cudd_SupersetShortPaths */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief The outermost procedure to return a subset of the given %BDD\n  with the shortest path lengths.\n\n  @details The path lengths are calculated, the maximum allowable path\n  length is determined and the number of nodes of this path length\n  that can be used to build a subset. If the threshold is larger than\n  the size of the original %BDD, the original %BDD is returned.\n\n  @sideeffect None\n\n  @see Cudd_SubsetShortPaths\n\n*/\nDdNode *\ncuddSubsetShortPaths(\n  DdManager * dd /**< %DD manager */,\n  DdNode * f /**< function to be subset */,\n  int  numVars /**< total number of variables in consideration */,\n  int  threshold /**< maximum number of nodes allowed in the subset */,\n  int  hardlimit /**< flag determining whether threshold should be respected strictly */)\n{\n    GlobalInfo_t gInfo;\n    st_table *pathTable;\n    DdNode *N, *subset;\n\n    unsigned int  *pathLengthArray;\n    unsigned int maxpath, oddLen, evenLen, pathLength, *excess;\n    int i;\n    NodeDist_t\t*nodeStat;\n    struct AssortedInfo *info;\n    st_table *subsetNodeTable;\n\n    gInfo.nodeDistPageSize = DEFAULT_NODE_DIST_PAGE_SIZE;\n    gInfo.queuePageSize = DEFAULT_PAGE_SIZE;\n\n    if (numVars == 0) {\n      /* set default value */\n      numVars = Cudd_ReadSize(dd);\n    }\n\n    if (threshold > numVars) {\n\tthreshold = threshold - numVars;\n    }\n    if (f == NULL) {\n\tfprintf(dd->err, \"Cannot partition, nil object\\n\");\n\tdd->errorCode = CUDD_INVALID_ARG;\n\treturn(NULL);\n    }\n    if (Cudd_IsConstantInt(f))\n\treturn (f);\n\n    pathLengthArray = ALLOC(unsigned int, numVars+1);\n    for (i = 0; i < numVars+1; i++) pathLengthArray[i] = 0;\n\n\n#ifdef DD_DEBUG\n    gInfo.numCalls = 0;\n#endif\n\n    pathTable = CreatePathTable(dd, &gInfo, f, pathLengthArray, dd->err);\n\n    if ((pathTable == NULL) || (dd->errorCode == CUDD_MEMORY_OUT)) {\n\tif (pathTable != NULL)\n\t    st_free_table(pathTable);\n\tFREE(pathLengthArray);\n\treturn (NIL(DdNode));\n    }\n\n    excess = ALLOC(unsigned int, 1);\n    *excess = 0;\n    maxpath = AssessPathLength(pathLengthArray, threshold, numVars, excess,\n\t\t\t       dd->err);\n\n    if (maxpath != (unsigned) (numVars + 1)) {\n\n\tinfo = ALLOC(struct AssortedInfo, 1);\n\tinfo->maxpath = maxpath;\n\tinfo->findShortestPath = 0;\n\tinfo->thresholdReached = *excess;\n\tinfo->maxpathTable = st_init_table(st_ptrcmp, st_ptrhash);\n\tinfo->threshold = threshold;\n\n#ifdef DD_DEBUG\n\t(void) fprintf(dd->out, \"Path length array\\n\");\n\tfor (i = 0; i < (numVars+1); i++) {\n\t    if (pathLengthArray[i])\n\t\t(void) fprintf(dd->out, \"%d \",i);\n\t}\n\t(void) fprintf(dd->out, \"\\n\");\n\tfor (i = 0; i < (numVars+1); i++) {\n\t    if (pathLengthArray[i])\n\t\t(void) fprintf(dd->out, \"%d \",pathLengthArray[i]);\n\t}\n\t(void) fprintf(dd->out, \"\\n\");\n\t(void) fprintf(dd->out, \"Maxpath  = %d, Thresholdreached = %d\\n\",\n\t\t       maxpath, info->thresholdReached);\n#endif\n\n\tN = Cudd_Regular(f);\n\tif (!st_lookup(pathTable, N, (void **) &nodeStat)) {\n\t    fprintf(dd->err, \"Something wrong, root node must be in table\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t    FREE(excess);\n\t    FREE(info);\n\t    return(NULL);\n\t} else {\n\t    if ((nodeStat->oddTopDist != MAXSHORTINT) &&\n\t\t(nodeStat->oddBotDist != MAXSHORTINT))\n\t\toddLen = (nodeStat->oddTopDist + nodeStat->oddBotDist);\n\t    else\n\t\toddLen = MAXSHORTINT;\n\n\t    if ((nodeStat->evenTopDist != MAXSHORTINT) &&\n\t\t(nodeStat->evenBotDist != MAXSHORTINT))\n\t\tevenLen = (nodeStat->evenTopDist +nodeStat->evenBotDist);\n\t    else\n\t\tevenLen = MAXSHORTINT;\n\n\t    pathLength = (oddLen <= evenLen) ? oddLen : evenLen;\n\t    if (pathLength > maxpath) {\n\t\t(void) fprintf(dd->err, \"All computations are bogus, since root has path length greater than max path length within threshold %u, %u\\n\", maxpath, pathLength);\n\t\tdd->errorCode = CUDD_INTERNAL_ERROR;\n\t\treturn(NULL);\n\t    }\n\t}\n\n#ifdef DD_DEBUG\n\tgInfo.numCalls = 0;\n\tgInfo.hits = 0;\n\tgInfo.thishit = 0;\n#endif\n\t/* initialize a table to store computed nodes */\n\tif (hardlimit) {\n\t    subsetNodeTable = st_init_table(st_ptrcmp, st_ptrhash);\n\t} else {\n\t    subsetNodeTable = NIL(st_table);\n\t}\n\tsubset = BuildSubsetBdd(dd, &gInfo, pathTable, f, info, subsetNodeTable);\n\tif (subset != NULL) {\n\t    cuddRef(subset);\n\t}\n\t/* record the number of times a computed result for a node is hit */\n\n#ifdef DD_DEBUG\n\t(void) fprintf(dd->out, \"Hits = %d, New==Node = %d, NumCalls = %d\\n\",\n\t\tgInfo.hits, gInfo.thishit, gInfo.numCalls);\n#endif\n\n\tif (subsetNodeTable != NIL(st_table)) {\n\t    st_free_table(subsetNodeTable);\n\t}\n\tst_free_table(info->maxpathTable);\n\tst_foreach(pathTable, stPathTableDdFree, (void *)dd);\n\n\tFREE(info);\n\n    } else {/* if threshold larger than size of dd */\n\tsubset = f;\n\tcuddRef(subset);\n    }\n    FREE(excess);\n    st_free_table(pathTable);\n    FREE(pathLengthArray);\n    for (i = 0; i <= gInfo.nodeDistPage; i++) FREE(gInfo.nodeDistPages[i]);\n    FREE(gInfo.nodeDistPages);\n\n#ifdef DD_DEBUG\n    /* check containment of subset in f */\n    if (subset != NULL) {\n\tif (!Cudd_bddLeq(dd, subset, f)) {\n\t    (void) fprintf(dd->err, \"Wrong partition\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t    return(NULL);\n\t}\n    }\n#endif\n\n    if (subset != NULL) {\n\tcuddDeref(subset);\n\treturn(subset);\n    } else {\n\treturn(NULL);\n    }\n\n} /* end of cuddSubsetShortPaths */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Resize the number of pages allocated to store the distances\n  related to each node.\n\n  @details The procedure moves the counter to the next page when the\n  end of the page is reached and allocates new pages when necessary.\n\n  @sideeffect Changes the size of  pages, page, page index, maximum\n  number of pages freeing stuff in case of memory out. \n\n*/\nstatic void\nResizeNodeDistPages(\n  DdManager *dd /**< %DD manager */,\n  GlobalInfo_t *gInfo /**< global information */)\n{\n    int i;\n    NodeDist_t **newNodeDistPages;\n\n    /* move to next page */\n    gInfo->nodeDistPage++;\n\n    /* If the current page index is larger than the number of pages\n     * allocated, allocate a new page array. Page numbers are incremented by\n     * INITIAL_PAGES\n     */\n    if (gInfo->nodeDistPage == gInfo->maxNodeDistPages) {\n\tnewNodeDistPages = ALLOC(NodeDist_t *,gInfo->maxNodeDistPages + INITIAL_PAGES);\n\tif (newNodeDistPages == NULL) {\n\t    for (i = 0; i < gInfo->nodeDistPage; i++) FREE(gInfo->nodeDistPages[i]);\n\t    FREE(gInfo->nodeDistPages);\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return;\n\t} else {\n\t    for (i = 0; i < gInfo->maxNodeDistPages; i++) {\n\t\tnewNodeDistPages[i] = gInfo->nodeDistPages[i];\n\t    }\n\t    /* Increase total page count */\n\t    gInfo->maxNodeDistPages += INITIAL_PAGES;\n\t    FREE(gInfo->nodeDistPages);\n\t    gInfo->nodeDistPages = newNodeDistPages;\n\t}\n    }\n    /* Allocate a new page */\n    gInfo->currentNodeDistPage = gInfo->nodeDistPages[gInfo->nodeDistPage] =\n        ALLOC(NodeDist_t, gInfo->nodeDistPageSize);\n    if (gInfo->currentNodeDistPage == NULL) {\n\tfor (i = 0; i < gInfo->nodeDistPage; i++) FREE(gInfo->nodeDistPages[i]);\n\tFREE(gInfo->nodeDistPages);\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn;\n    }\n    /* reset page index */\n    gInfo->nodeDistPageIndex = 0;\n    return;\n\n} /* end of ResizeNodeDistPages */\n\n\n/**\n  @brief Resize the number of pages allocated to store nodes in the BFS\n  traversal of the %BDD.\n\n  @details The procedure moves the counter to the next page when the\n  end of the page is reached and allocates new pages when necessary.\n\n  @sideeffect Changes the size of pages, page, page index, maximum\n  number of pages freeing stuff in case of memory out. \n\n*/\nstatic void\nResizeQueuePages(\n  DdManager *dd /**< %DD manager */,\n  GlobalInfo_t *gInfo /**< global information */)\n{\n    int i;\n    DdNode ***newQueuePages;\n\n    gInfo->queuePage++;\n    /* If the current page index is larger than the number of pages\n     * allocated, allocate a new page array. Page numbers are incremented by\n     * INITIAL_PAGES\n     */\n    if (gInfo->queuePage == gInfo->maxQueuePages) {\n\tnewQueuePages = ALLOC(DdNode **,gInfo->maxQueuePages + INITIAL_PAGES);\n\tif (newQueuePages == NULL) {\n\t    for (i = 0; i < gInfo->queuePage; i++) FREE(gInfo->queuePages[i]);\n\t    FREE(gInfo->queuePages);\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return;\n\t} else {\n\t    for (i = 0; i < gInfo->maxQueuePages; i++) {\n\t\tnewQueuePages[i] = gInfo->queuePages[i];\n\t    }\n\t    /* Increase total page count */\n\t    gInfo->maxQueuePages += INITIAL_PAGES;\n\t    FREE(gInfo->queuePages);\n\t    gInfo->queuePages = newQueuePages;\n\t}\n    }\n    /* Allocate a new page */\n    gInfo->currentQueuePage = gInfo->queuePages[gInfo->queuePage] =\n        ALLOC(DdNode *,gInfo->queuePageSize);\n    if (gInfo->currentQueuePage == NULL) {\n\tfor (i = 0; i < gInfo->queuePage; i++) FREE(gInfo->queuePages[i]);\n\tFREE(gInfo->queuePages);\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn;\n    }\n    /* reset page index */\n    gInfo->queuePageIndex = 0;\n    return;\n\n} /* end of ResizeQueuePages */\n\n\n/**\n  @brief Labels each node with its shortest distance from the root.\n\n  @details This is done in a BFS search of the %BDD. The nodes are\n  processed in a queue implemented as pages(array) to reduce memory\n  fragmentation.  An entry is created for each node visited. The\n  distance from the root to the node with the corresponding parity is\n  updated. The procedure is called recursively each recusion level\n  handling nodes at a given level from the root.\n\n  @sideeffect Creates entries in the pathTable\n\n  @see CreatePathTable CreateBotDist\n\n*/\nstatic void\nCreateTopDist(\n  DdManager *dd /**< %DD manager */,\n  GlobalInfo_t *gInfo /**< global information */,\n  st_table * pathTable /**< hash table to store path lengths */,\n  int  parentPage /**< the pointer to the page on which the first parent in the queue is to be found. */,\n  int  parentQueueIndex /**< pointer to the first parent on the page */,\n  int  topLen /**< current distance from the root */,\n  DdNode ** childPage /**< pointer to the page on which the first child is to be added. */,\n  int  childQueueIndex /**< pointer to the first child */,\n  int  numParents /**< number of parents to process in this recursive call */,\n  FILE *fp /**< where to write messages */)\n{\n    NodeDist_t *nodeStat;\n    DdNode *N, *Nv, *Nnv, *node, *child, *regChild;\n    int  i;\n    int processingDone, childrenCount;\n\n#ifdef DD_DEBUG\n    gInfo->numCalls++;\n\n    /* assume this procedure comes in with only the root node*/\n    /* set queue index to the next available entry for addition */\n    /* set queue page to page of addition */\n    if ((gInfo->queuePages[parentPage] == childPage) && (parentQueueIndex ==\n\t\t\t\t\t\t  childQueueIndex)) {\n\tfprintf(fp, \"Should not happen that they are equal\\n\");\n    }\n    assert(gInfo->queuePageIndex == childQueueIndex);\n    assert(gInfo->currentQueuePage == childPage);\n#endif\n    /* number children added to queue is initialized , needed for\n     * numParents in the next call\n     */\n    childrenCount = 0;\n    /* process all the nodes in this level */\n    while (numParents) {\n\tnumParents--;\n\tif (parentQueueIndex == gInfo->queuePageSize) {\n\t    parentPage++;\n\t    parentQueueIndex = 0;\n\t}\n\t/* a parent to process */\n\tnode = *(gInfo->queuePages[parentPage] + parentQueueIndex);\n\tparentQueueIndex++;\n\t/* get its children */\n\tN = Cudd_Regular(node);\n\tNv = Cudd_T(N);\n\tNnv = Cudd_E(N);\n\n\tNv = Cudd_NotCond(Nv, Cudd_IsComplement(node));\n\tNnv = Cudd_NotCond(Nnv, Cudd_IsComplement(node));\n\n\tprocessingDone = 2;\n\twhile (processingDone) {\n\t    /* processing the THEN and the ELSE children, the THEN\n\t     * child first\n\t     */\n\t    if (processingDone == 2) {\n\t\tchild = Nv;\n\t    } else {\n\t\tchild = Nnv;\n\t    }\n\n\t    regChild = Cudd_Regular(child);\n\t    /* dont process if the child is a constant */\n\t    if (!Cudd_IsConstantInt(child)) {\n\t\t/* check is already visited, if not add a new entry in\n\t\t * the path Table\n\t\t */\n                if (!st_lookup(pathTable, regChild, (void **) &nodeStat)) {\n\t\t    /* if not in table, has never been visited */\n\t\t    /* create entry for table */\n\t\t    if (gInfo->nodeDistPageIndex == gInfo->nodeDistPageSize)\n\t\t\tResizeNodeDistPages(dd, gInfo);\n\t\t    if (dd->errorCode == CUDD_MEMORY_OUT) {\n\t\t\tfor (i = 0; i <= gInfo->queuePage; i++) FREE(gInfo->queuePages[i]);\n\t\t\tFREE(gInfo->queuePages);\n\t\t\tst_free_table(pathTable);\n\t\t\treturn;\n\t\t    }\n\t\t    /* New entry for child in path Table is created here */\n\t\t    nodeStat = gInfo->currentNodeDistPage + gInfo->nodeDistPageIndex;\n\t\t    gInfo->nodeDistPageIndex++;\n\n\t\t    /* Initialize fields of the node data */\n\t\t    nodeStat->oddTopDist = MAXSHORTINT;\n\t\t    nodeStat->evenTopDist = MAXSHORTINT;\n\t\t    nodeStat->evenBotDist = MAXSHORTINT;\n\t\t    nodeStat->oddBotDist = MAXSHORTINT;\n\t\t    nodeStat->regResult = NULL;\n\t\t    nodeStat->compResult = NULL;\n\t\t    /* update the table entry element, the distance keeps\n\t\t     * track of the parity of the path from the root\n\t\t     */\n\t\t    if (Cudd_IsComplement(child)) {\n\t\t\tnodeStat->oddTopDist = (DdHalfWord) topLen + 1;\n\t\t    } else {\n\t\t\tnodeStat->evenTopDist = (DdHalfWord) topLen + 1;\n\t\t    }\n\n\t\t    /* insert entry element for child in the table */\n\t\t    if (st_insert(pathTable, regChild,\n\t\t\t\t  nodeStat) == ST_OUT_OF_MEM) {\n\t\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\t\tfor (i = 0; i <= gInfo->nodeDistPage; i++)\n\t\t\t    FREE(gInfo->nodeDistPages[i]);\n\t\t\tFREE(gInfo->nodeDistPages);\n\t\t\tfor (i = 0; i <= gInfo->queuePage; i++) FREE(gInfo->queuePages[i]);\n\t\t\tFREE(gInfo->queuePages);\n\t\t\tst_free_table(pathTable);\n\t\t\treturn;\n\t\t    }\n\n\t\t    /* Create list element for this child to process its children.\n\t\t     * If this node has been processed already, then it appears\n\t\t     * in the path table and hence is never added to the list\n\t\t     * again.\n\t\t     */\n\n\t\t    if (gInfo->queuePageIndex == gInfo->queuePageSize) ResizeQueuePages(dd, gInfo);\n\t\t    if (dd->errorCode == CUDD_MEMORY_OUT) {\n\t\t\tfor (i = 0; i <= gInfo->nodeDistPage; i++)\n\t\t\t    FREE(gInfo->nodeDistPages[i]);\n\t\t\tFREE(gInfo->nodeDistPages);\n\t\t\tst_free_table(pathTable);\n\t\t\treturn;\n\t\t    }\n\t\t    *(gInfo->currentQueuePage + gInfo->queuePageIndex) = child;\n\t\t    gInfo->queuePageIndex++;\n\n\t\t    childrenCount++;\n\t\t} else {\n\t\t    /* if not been met in a path with this parity before */\n\t\t    /* put in list */\n\t\t    if (((Cudd_IsComplement(child)) && (nodeStat->oddTopDist ==\n\t\t\t  MAXSHORTINT)) || ((!Cudd_IsComplement(child)) &&\n\t\t\t\t  (nodeStat->evenTopDist == MAXSHORTINT))) {\n\n\t\t\tif (gInfo->queuePageIndex == gInfo->queuePageSize) ResizeQueuePages(dd, gInfo);\n\t\t\tif (dd->errorCode == CUDD_MEMORY_OUT) {\n\t\t\t    for (i = 0; i <= gInfo->nodeDistPage; i++)\n\t\t\t\tFREE(gInfo->nodeDistPages[i]);\n\t\t\t    FREE(gInfo->nodeDistPages);\n\t\t\t    st_free_table(pathTable);\n\t\t\t    return;\n\n\t\t\t}\n\t\t\t*(gInfo->currentQueuePage + gInfo->queuePageIndex) = child;\n\t\t\tgInfo->queuePageIndex++;\n\n\t\t\t/* update the distance with the appropriate parity */\n\t\t\tif (Cudd_IsComplement(child)) {\n\t\t\t    nodeStat->oddTopDist = (DdHalfWord) topLen + 1;\n\t\t\t} else {\n\t\t\t    nodeStat->evenTopDist = (DdHalfWord) topLen + 1;\n\t\t\t}\n\t\t\tchildrenCount++;\n\t\t    }\n\n\t\t} /* end of else (not found in st_table) */\n\t    } /*end of if Not constant child */\n\t    processingDone--;\n\t} /*end of while processing Nv, Nnv */\n    }  /*end of while numParents */\n\n#ifdef DD_DEBUG\n    assert(gInfo->queuePages[parentPage] == childPage);\n    assert(parentQueueIndex == childQueueIndex);\n#endif\n\n    if (childrenCount != 0) {\n\ttopLen++;\n\tchildPage = gInfo->currentQueuePage;\n\tchildQueueIndex = gInfo->queuePageIndex;\n\tCreateTopDist(dd, gInfo, pathTable, parentPage, parentQueueIndex, topLen,\n\t\t      childPage, childQueueIndex, childrenCount, fp);\n    }\n\n    return;\n\n} /* end of CreateTopDist */\n\n\n/**\n  @brief Labels each node with the shortest distance from the constant.\n\n  @details This is done in a DFS search of the %BDD. Each node has an\n  odd and even parity distance from the sink (since there exists paths\n  to both zero and one) which is less than MAXSHORTINT. At each node\n  these distances are updated using the minimum distance of its\n  children from the constant.  SInce now both the length from the root\n  and child is known, the minimum path length(length of the shortest\n  path between the root and the constant that this node lies on) of\n  this node can be calculated and used to update the pathLengthArray.\n\n  @sideeffect Updates Path Table and path length array\n\n  @see CreatePathTable CreateTopDist AssessPathLength\n\n*/\nstatic int\nCreateBotDist(\n  DdNode * node /* current node */,\n  st_table * pathTable /* path table with path lengths */,\n  unsigned int * pathLengthArray /* array that stores number of nodes belonging to a particular path length. */,\n  FILE *fp /* where to write messages */)\n{\n    DdNode *N, *Nv, *Nnv;\n    DdNode *realChild;\n    DdNode *child, *regChild;\n    NodeDist_t *nodeStat, *nodeStatChild;\n    unsigned int  oddLen, evenLen, pathLength;\n    DdHalfWord botDist;\n    int processingDone;\n\n    if (Cudd_IsConstantInt(node))\n\treturn(1);\n    N = Cudd_Regular(node);\n    /* each node has one table entry */\n    /* update as you go down the min dist of each node from\n       the root in each (odd and even) parity */\n    if (!st_lookup(pathTable, N, (void **) &nodeStat)) {\n\tfprintf(fp, \"Something wrong, the entry doesn't exist\\n\");\n\treturn(0);\n    }\n\n    /* compute length of odd parity distances */\n    if ((nodeStat->oddTopDist != MAXSHORTINT) &&\n\t(nodeStat->oddBotDist != MAXSHORTINT))\n\toddLen = (nodeStat->oddTopDist + nodeStat->oddBotDist);\n    else\n\toddLen = MAXSHORTINT;\n\n    /* compute length of even parity distances */\n    if (!((nodeStat->evenTopDist == MAXSHORTINT) ||\n\t  (nodeStat->evenBotDist == MAXSHORTINT)))\n\tevenLen = (nodeStat->evenTopDist +nodeStat->evenBotDist);\n    else\n\tevenLen = MAXSHORTINT;\n\n    /* assign pathlength to minimum of the two */\n    pathLength = (oddLen <= evenLen) ? oddLen : evenLen;\n\n    Nv = Cudd_T(N);\n    Nnv = Cudd_E(N);\n\n    /* process each child */\n    processingDone = 0;\n    while (processingDone != 2) {\n\tif (!processingDone) {\n\t    child = Nv;\n\t} else {\n\t    child = Nnv;\n\t}\n\n\trealChild = Cudd_NotCond(child, Cudd_IsComplement(node));\n\tregChild = Cudd_Regular(child);\n\tif (Cudd_IsConstantInt(realChild)) {\n\t    /* Found a minterm; count parity and shortest distance\n\t    ** from the constant.\n\t    */\n\t    if (Cudd_IsComplement(child))\n\t\tnodeStat->oddBotDist = 1;\n\t    else\n\t\tnodeStat->evenBotDist = 1;\n\t} else {\n\t    /* If node not in table, recur. */\n            if (!st_lookup(pathTable, regChild, (void **) &nodeStatChild)) {\n\t\tfprintf(fp, \"Something wrong, node in table should have been created in top dist proc.\\n\");\n\t\treturn(0);\n\t    }\n\n\t    if (nodeStatChild->oddBotDist == MAXSHORTINT) {\n\t\tif (nodeStatChild->evenBotDist == MAXSHORTINT) {\n\t\t    if (!CreateBotDist(realChild, pathTable, pathLengthArray, fp))\n\t\t\treturn(0);\n\t\t} else {\n\t\t    fprintf(fp, \"Something wrong, both bot nodeStats should be there\\n\");\n\t\t    return(0);\n\t\t}\n\t    }\n\n\t    /* Update shortest distance from the constant depending on\n\t    **  parity. */\n\n\t    if (Cudd_IsComplement(child)) {\n\t\t/* If parity on the edge then add 1 to even distance\n\t\t** of child to get odd parity distance and add 1 to\n\t\t** odd distance of child to get even parity\n\t\t** distance. Change distance of current node only if\n\t\t** the calculated distance is less than existing\n\t\t** distance. */\n\t\tif (nodeStatChild->oddBotDist != MAXSHORTINT)\n\t\t    botDist = nodeStatChild->oddBotDist + 1;\n\t\telse\n\t\t    botDist = MAXSHORTINT;\n\t\tif (nodeStat->evenBotDist > botDist )\n\t\t    nodeStat->evenBotDist = botDist;\n\n\t\tif (nodeStatChild->evenBotDist != MAXSHORTINT)\n\t\t    botDist = nodeStatChild->evenBotDist + 1;\n\t\telse\n\t\t    botDist = MAXSHORTINT;\n\t\tif (nodeStat->oddBotDist > botDist)\n\t\t    nodeStat->oddBotDist = botDist;\n\n\t    } else {\n\t\t/* If parity on the edge then add 1 to even distance\n\t\t** of child to get even parity distance and add 1 to\n\t\t** odd distance of child to get odd parity distance.\n\t\t** Change distance of current node only if the\n\t\t** calculated distance is lesser than existing\n\t\t** distance. */\n\t\tif (nodeStatChild->evenBotDist != MAXSHORTINT)\n\t\t    botDist = nodeStatChild->evenBotDist + 1;\n\t\telse\n\t\t    botDist = MAXSHORTINT;\n\t\tif (nodeStat->evenBotDist > botDist)\n\t\t    nodeStat->evenBotDist = botDist;\n\n\t\tif (nodeStatChild->oddBotDist != MAXSHORTINT)\n\t\t    botDist = nodeStatChild->oddBotDist + 1;\n\t\telse\n\t\t    botDist = MAXSHORTINT;\n\t\tif (nodeStat->oddBotDist > botDist)\n\t\t    nodeStat->oddBotDist = botDist;\n\t    }\n\t} /* end of else (if not constant child ) */\n\tprocessingDone++;\n    } /* end of while processing Nv, Nnv */\n\n    /* Compute shortest path length on the fly. */\n    if ((nodeStat->oddTopDist != MAXSHORTINT) &&\n\t(nodeStat->oddBotDist != MAXSHORTINT))\n\toddLen = (nodeStat->oddTopDist + nodeStat->oddBotDist);\n    else\n\toddLen = MAXSHORTINT;\n\n    if ((nodeStat->evenTopDist != MAXSHORTINT) &&\n\t(nodeStat->evenBotDist != MAXSHORTINT))\n\tevenLen = (nodeStat->evenTopDist +nodeStat->evenBotDist);\n    else\n\tevenLen = MAXSHORTINT;\n\n    /* Update path length array that has number of nodes of a particular\n    ** path length. */\n    if (oddLen < pathLength ) {\n\tif (pathLength != MAXSHORTINT)\n\t    pathLengthArray[pathLength]--;\n\tif (oddLen != MAXSHORTINT)\n\t    pathLengthArray[oddLen]++;\n\tpathLength = oddLen;\n    }\n    if (evenLen < pathLength ) {\n\tif (pathLength != MAXSHORTINT)\n\t    pathLengthArray[pathLength]--;\n\tif (evenLen != MAXSHORTINT)\n\t    pathLengthArray[evenLen]++;\n    }\n\n    return(1);\n\n} /*end of CreateBotDist */\n\n\n/**\n  @brief The outer procedure to label each node with its shortest\n  distance from the root and constant\n\n  @details Calls CreateTopDist and CreateBotDist.  The basis for\n  computing the distance between root and constant is that the\n  distance may be the sum of even distances from the node to the root\n  and constant or the sum of odd distances from the node to the root\n  and constant.  Both CreateTopDist and CreateBotDist create the odd\n  and even parity distances from the root and constant respectively.\n\n  @sideeffect None\n\n  @see CreateTopDist CreateBotDist\n\n*/\nstatic st_table *\nCreatePathTable(\n  DdManager *dd /**< %DD manager */,\n  GlobalInfo_t *gInfo /**< global information */,\n  DdNode * node /**< root of function */,\n  unsigned int * pathLengthArray /**< array of path lengths to store nodes labeled with the various path lengths */,\n  FILE *fp /**< where to write messages */)\n{\n    st_table *pathTable;\n    NodeDist_t *nodeStat;\n    DdHalfWord topLen;\n    DdNode *N;\n    int i, numParents;\n    int insertValue;\n    DdNode **childPage;\n    int parentPage;\n    int childQueueIndex, parentQueueIndex;\n\n    /* Creating path table for storing data about nodes */\n    pathTable = st_init_table(st_ptrcmp,st_ptrhash);\n\n    /* Initializing pages for info about each node */\n    gInfo->maxNodeDistPages = INITIAL_PAGES;\n    gInfo->nodeDistPages = ALLOC(NodeDist_t *, gInfo->maxNodeDistPages);\n    if (gInfo->nodeDistPages == NULL) {\n\tgoto OUT_OF_MEM;\n    }\n    assert(gInfo->nodeDistPageSize > 0);\n    gInfo->nodeDistPage = 0;\n    gInfo->currentNodeDistPage = gInfo->nodeDistPages[gInfo->nodeDistPage] =\n\tALLOC(NodeDist_t, gInfo->nodeDistPageSize);\n    if (gInfo->currentNodeDistPage == NULL) {\n\tfor (i = 0; i <= gInfo->nodeDistPage; i++) FREE(gInfo->nodeDistPages[i]);\n\tFREE(gInfo->nodeDistPages);\n\tgoto OUT_OF_MEM;\n    }\n    gInfo->nodeDistPageIndex = 0;\n\n    /* Initializing pages for the BFS search queue, implemented as an array. */\n    gInfo->maxQueuePages = INITIAL_PAGES;\n    gInfo->queuePages = ALLOC(DdNode **, gInfo->maxQueuePages);\n    if (gInfo->queuePages == NULL) {\n\tgoto OUT_OF_MEM;\n    }\n    assert(gInfo->queuePageSize > 0);\n    gInfo->queuePage = 0;\n    gInfo->currentQueuePage  = gInfo->queuePages[gInfo->queuePage] =\n        ALLOC(DdNode *, gInfo->queuePageSize);\n    if (gInfo->currentQueuePage == NULL) {\n\tfor (i = 0; i <= gInfo->queuePage; i++) FREE(gInfo->queuePages[i]);\n\tFREE(gInfo->queuePages);\n\tgoto OUT_OF_MEM;\n    }\n    gInfo->queuePageIndex = 0;\n\n    /* Enter the root node into the queue to start with. */\n    parentPage = gInfo->queuePage;\n    parentQueueIndex = gInfo->queuePageIndex;\n    topLen = 0;\n    *(gInfo->currentQueuePage + gInfo->queuePageIndex) = node;\n    gInfo->queuePageIndex++;\n    childPage = gInfo->currentQueuePage;\n    childQueueIndex = gInfo->queuePageIndex;\n\n    N = Cudd_Regular(node);\n\n    if (gInfo->nodeDistPageIndex == gInfo->nodeDistPageSize)\n        ResizeNodeDistPages(dd, gInfo);\n    if (dd->errorCode == CUDD_MEMORY_OUT) {\n        if (gInfo->nodeDistPages != NULL) {\n            for (i = 0; i <= gInfo->nodeDistPage; i++)\n                FREE(gInfo->nodeDistPages[i]);\n            FREE(gInfo->nodeDistPages);\n        }\n\tfor (i = 0; i <= gInfo->queuePage; i++) FREE(gInfo->queuePages[i]);\n\tFREE(gInfo->queuePages);\n\tst_free_table(pathTable);\n\tgoto OUT_OF_MEM;\n    }\n\n    nodeStat = gInfo->currentNodeDistPage + gInfo->nodeDistPageIndex;\n    gInfo->nodeDistPageIndex++;\n\n    nodeStat->oddTopDist = MAXSHORTINT;\n    nodeStat->evenTopDist = MAXSHORTINT;\n    nodeStat->evenBotDist = MAXSHORTINT;\n    nodeStat->oddBotDist = MAXSHORTINT;\n    nodeStat->regResult = NULL;\n    nodeStat->compResult = NULL;\n\n    insertValue = st_insert(pathTable, N, nodeStat);\n    if (insertValue == ST_OUT_OF_MEM) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tfor (i = 0; i <= gInfo->nodeDistPage; i++) FREE(gInfo->nodeDistPages[i]);\n\tFREE(gInfo->nodeDistPages);\n\tfor (i = 0; i <= gInfo->queuePage; i++) FREE(gInfo->queuePages[i]);\n\tFREE(gInfo->queuePages);\n\tst_free_table(pathTable);\n\tgoto OUT_OF_MEM;\n    } else if (insertValue == 1) {\n\tfprintf(fp, \"Something wrong, the entry exists but didnt show up in st_lookup\\n\");\n\treturn(NULL);\n    }\n\n    if (Cudd_IsComplement(node)) {\n\tnodeStat->oddTopDist = 0;\n    } else {\n\tnodeStat->evenTopDist = 0;\n    }\n    numParents = 1;\n    /* call the function that counts the distance of each node from the\n     * root\n     */\n#ifdef DD_DEBUG\n    gInfo->numCalls = 0;\n#endif\n    CreateTopDist(dd, gInfo, pathTable, parentPage, parentQueueIndex, (int) topLen,\n\t\t  childPage, childQueueIndex, numParents, fp);\n    if (dd->errorCode == CUDD_MEMORY_OUT) {\n\tfprintf(fp, \"Out of Memory and cant count path lengths\\n\");\n\tgoto OUT_OF_MEM;\n    }\n\n#ifdef DD_DEBUG\n    gInfo->numCalls = 0;\n#endif\n    /* call the function that counts the distance of each node from the\n     * constant\n     */\n    if (!CreateBotDist(node, pathTable, pathLengthArray, fp)) return(NULL);\n\n    /* free BFS queue pages as no longer required */\n    for (i = 0; i <= gInfo->queuePage; i++) FREE(gInfo->queuePages[i]);\n    FREE(gInfo->queuePages);\n    return(pathTable);\n\nOUT_OF_MEM:\n    (void) fprintf(fp, \"Out of Memory, cannot allocate pages\\n\");\n    dd->errorCode = CUDD_MEMORY_OUT;\n    return(NULL);\n\n} /*end of CreatePathTable */\n\n\n/**\n  @brief Chooses the maximum allowable path length of nodes under the\n  threshold.\n\n  @details The corner cases are when the threshold is larger than the\n  number of nodes in the %BDD iself, in which case 'numVars + 1' is\n  returned.  If all nodes of a particular path length are needed, then\n  the maxpath returned is the next one with excess nodes = 0.\n\n  @sideeffect None\n\n*/\nstatic unsigned int\nAssessPathLength(\n  unsigned int * pathLengthArray /* array determining number of nodes belonging to the different path lengths */,\n  int  threshold /* threshold to determine maximum allowable nodes in the subset */,\n  int  numVars /* maximum number of variables */,\n  unsigned int * excess /* number of nodes labeled maxpath required in the subset */,\n  FILE *fp /* where to write messages */)\n{\n    unsigned int i, maxpath;\n    int temp;\n\n    temp = threshold;\n    i = 0;\n    maxpath = 0;\n    /* quit loop if i reaches max number of variables or if temp reaches\n     * below zero\n     */\n    while ((i < (unsigned) numVars+1) && (temp > 0)) {\n\tif (pathLengthArray[i] > 0) {\n\t    maxpath = i;\n\t    temp = temp - pathLengthArray[i];\n\t}\n\ti++;\n    }\n    /* if all nodes of max path are needed */\n    if (temp >= 0) {\n\tmaxpath++; /* now maxpath  becomes the next maxppath or max number\n\t\t      of variables */\n\t*excess = 0;\n    } else { /* normal case when subset required is less than size of\n\t\toriginal BDD */\n\t*excess = temp + pathLengthArray[maxpath];\n    }\n\n    if (maxpath == 0) {\n\tfprintf(fp, \"Path Length array seems to be all zeroes, check\\n\");\n    }\n    return(maxpath);\n\n} /* end of AssessPathLength */\n\n\n/**\n  @brief Builds the %BDD with nodes labeled with path length less than\n  or equal to maxpath.\n\n  @details Builds the %BDD with nodes labeled with path length\n  under maxpath and as many nodes labeled maxpath as determined by the\n  threshold. The procedure uses the path table to determine which nodes\n  in the original bdd need to be retained. This procedure picks a\n  shortest path (tie break decided by taking the child with the shortest\n  distance to the constant) and recurs down the path till it reaches the\n  constant. the procedure then starts building the subset upward from\n  the constant. All nodes labeled by path lengths less than the given\n  maxpath are used to build the subset.  However, in the case of nodes\n  that have label equal to maxpath, as many are chosen as required by\n  the threshold. This number is stored in the info structure in the\n  field thresholdReached. This field is decremented whenever a node\n  labeled maxpath is encountered and the nodes labeled maxpath are\n  aggregated in a maxpath table. As soon as the thresholdReached count\n  goes to 0, the shortest path from this node to the constant is found.\n  The extraction of nodes with the above labeling is based on the fact\n  that each node, labeled with a path length, P, has at least one child\n  labeled P or less. So extracting all nodes labeled a given path length\n  P ensures complete paths between the root and the constant. Extraction\n  of a partial number of nodes with a given path length may result in\n  incomplete paths and hence the additional number of nodes are grabbed\n  to complete the path. Since the Bdd is built bottom-up, other nodes\n  labeled maxpath do lie on complete paths.  The procedure may cause the\n  subset to have a larger or smaller number of nodes than the specified\n  threshold. The increase in the number of nodes is caused by the\n  building of a subset and the reduction by recombination. However in\n  most cases, the recombination overshadows the increase and the\n  procedure returns a result with lower number of nodes than specified.\n  The subsetNodeTable is NIL when there is no hard limit on the number\n  of nodes. Further efforts towards keeping the subset closer to the\n  threshold number were abandoned in favour of keeping the procedure\n  simple and fast.\n\n  @sideeffect SubsetNodeTable is changed if it is not NIL.\n\n*/\nstatic DdNode *\nBuildSubsetBdd(\n  DdManager * dd /**< %DD manager */,\n  GlobalInfo_t *gInfo /**< global information */,\n  st_table * pathTable /**< path table with path lengths and computed results */,\n  DdNode * node /**< current node */,\n  struct AssortedInfo * info /**< assorted information structure */,\n  st_table * subsetNodeTable /**< table storing computed results */)\n{\n    DdNode *N, *Nv, *Nnv;\n    DdNode *ThenBranch, *ElseBranch, *childBranch;\n    DdNode *child = NULL, *regChild = NULL, *regNnv = NULL, *regNv = NULL;\n    NodeDist_t *nodeStatNv, *nodeStat, *nodeStatNnv;\n    DdNode *neW, *topv, *regNew;\n    char *entry;\n    int topid;\n    unsigned int childPathLength, oddLen, evenLen;\n    unsigned int NnvPathLength = 0, NvPathLength = 0;\n    unsigned int NvBotDist, NnvBotDist;\n    int tiebreakChild;\n    int  processingDone, thenDone;\n\n    DdNode *zero = Cudd_Not(DD_ONE(dd));\n#ifdef DD_DEBUG\n    gInfo->numCalls++;\n#endif\n    if (Cudd_IsConstantInt(node))\n\treturn(node);\n\n    N = Cudd_Regular(node);\n    /* Find node in table. */\n    if (!st_lookup(pathTable, N, (void **) &nodeStat)) {\n\t(void) fprintf(dd->err, \"Something wrong, node must be in table \\n\");\n\tdd->errorCode = CUDD_INTERNAL_ERROR;\n\treturn(NULL);\n    }\n    /* If the node in the table has been visited, then return the corresponding\n    ** Dd. Since a node can become a subset of itself, its\n    ** complement (that is te same node reached by a different parity) will\n    ** become a superset of the original node and result in some minterms\n    ** that were not in the original set. Hence two different results are\n    ** maintained, corresponding to the odd and even parities.\n    */\n\n    /* If this node is reached with an odd parity, get odd parity results. */\n    if (Cudd_IsComplement(node)) {\n\tif  (nodeStat->compResult != NULL) {\n#ifdef DD_DEBUG\n\t    gInfo->hits++;\n#endif\n\t    return(nodeStat->compResult);\n\t}\n    } else {\n\t/* if this node is reached with an even parity, get even parity\n\t * results\n\t */\n\tif (nodeStat->regResult != NULL) {\n#ifdef DD_DEBUG\n\t    gInfo->hits++;\n#endif\n\t    return(nodeStat->regResult);\n\t}\n    }\n\n\n    /* get children */\n    Nv = Cudd_T(N);\n    Nnv = Cudd_E(N);\n\n    Nv = Cudd_NotCond(Nv, Cudd_IsComplement(node));\n    Nnv = Cudd_NotCond(Nnv, Cudd_IsComplement(node));\n\n    /* no child processed */\n    processingDone = 0;\n    /* then child not processed */\n    thenDone = 0;\n    ThenBranch = NULL;\n    /* else child not processed */\n    ElseBranch = NULL;\n    /* if then child constant, branch is the child */\n    if (Cudd_IsConstantInt(Nv)) {\n\t/*shortest path found */\n\tif ((Nv == DD_ONE(dd)) && (info->findShortestPath)) {\n\t    info->findShortestPath = 0;\n\t}\n\n\tThenBranch = Nv;\n\tcuddRef(ThenBranch);\n\tif (ThenBranch == NULL) {\n\t    return(NULL);\n\t}\n\n\tthenDone++;\n\tprocessingDone++;\n\tNvBotDist = MAXSHORTINT;\n    } else {\n\t/* Derive regular child for table lookup. */\n\tregNv = Cudd_Regular(Nv);\n\t/* Get node data for shortest path length. */\n\tif (!st_lookup(pathTable, regNv, (void **) &nodeStatNv) ) {\n\t    (void) fprintf(dd->err, \"Something wrong, node must be in table\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t    return(NULL);\n\t}\n\t/* Derive shortest path length for child. */\n\tif ((nodeStatNv->oddTopDist != MAXSHORTINT) &&\n\t    (nodeStatNv->oddBotDist != MAXSHORTINT)) {\n\t    oddLen = (nodeStatNv->oddTopDist + nodeStatNv->oddBotDist);\n\t} else {\n\t    oddLen = MAXSHORTINT;\n\t}\n\n\tif ((nodeStatNv->evenTopDist != MAXSHORTINT) &&\n\t    (nodeStatNv->evenBotDist != MAXSHORTINT)) {\n\t    evenLen = (nodeStatNv->evenTopDist +nodeStatNv->evenBotDist);\n\t} else {\n\t    evenLen = MAXSHORTINT;\n\t}\n\n\tNvPathLength = (oddLen <= evenLen) ? oddLen : evenLen;\n\tNvBotDist = (oddLen <= evenLen) ? nodeStatNv->oddBotDist:\n\t\t\t\t\t\t   nodeStatNv->evenBotDist;\n    }\n    /* if else child constant, branch is the child */\n    if (Cudd_IsConstantInt(Nnv)) {\n\t/*shortest path found */\n\tif ((Nnv == DD_ONE(dd)) && (info->findShortestPath)) {\n\t    info->findShortestPath = 0;\n\t}\n\n\tElseBranch = Nnv;\n\tcuddRef(ElseBranch);\n\tif (ElseBranch == NULL) {\n\t    return(NULL);\n\t}\n\n\tprocessingDone++;\n\tNnvBotDist = MAXSHORTINT;\n    } else {\n\t/* Derive regular child for table lookup. */\n\tregNnv = Cudd_Regular(Nnv);\n\t/* Get node data for shortest path length. */\n\tif (!st_lookup(pathTable, regNnv, (void **) &nodeStatNnv) ) {\n\t    (void) fprintf(dd->err, \"Something wrong, node must be in table\\n\");\n\t    dd->errorCode = CUDD_INTERNAL_ERROR;\n\t    return(NULL);\n\t}\n\t/* Derive shortest path length for child. */\n\tif ((nodeStatNnv->oddTopDist != MAXSHORTINT) &&\n\t    (nodeStatNnv->oddBotDist != MAXSHORTINT)) {\n\t    oddLen = (nodeStatNnv->oddTopDist + nodeStatNnv->oddBotDist);\n\t} else {\n\t    oddLen = MAXSHORTINT;\n\t}\n\n\tif ((nodeStatNnv->evenTopDist != MAXSHORTINT) &&\n\t    (nodeStatNnv->evenBotDist != MAXSHORTINT)) {\n\t    evenLen = (nodeStatNnv->evenTopDist +nodeStatNnv->evenBotDist);\n\t} else {\n\t    evenLen = MAXSHORTINT;\n\t}\n\n\tNnvPathLength = (oddLen <= evenLen) ? oddLen : evenLen;\n\tNnvBotDist = (oddLen <= evenLen) ? nodeStatNnv->oddBotDist :\n\t\t\t\t\t\t   nodeStatNnv->evenBotDist;\n    }\n\n    tiebreakChild = (NvBotDist <= NnvBotDist) ? 1 : 0;\n    /* while both children not processed */\n    while (processingDone != 2) {\n\tif (!processingDone) {\n\t    /* if no child processed */\n\t    /* pick the child with shortest path length and record which one\n\t     * picked\n\t     */\n\t    if ((NvPathLength < NnvPathLength) ||\n\t\t((NvPathLength == NnvPathLength) && (tiebreakChild == 1))) {\n\t\tchild = Nv;\n\t\tregChild = regNv;\n\t\tthenDone = 1;\n\t\tchildPathLength = NvPathLength;\n\t    } else {\n\t\tchild = Nnv;\n\t\tregChild = regNnv;\n\t\tchildPathLength = NnvPathLength;\n\t    } /* then path length less than else path length */\n\t} else {\n\t    /* if one child processed, process the other */\n\t    if (thenDone) {\n\t\tchild = Nnv;\n\t\tregChild = regNnv;\n\t\tchildPathLength = NnvPathLength;\n\t    } else {\n\t\tchild = Nv;\n\t\tregChild = regNv;\n\t\tthenDone = 1;\n\t\tchildPathLength = NvPathLength;\n\t    } /* end of else pick the Then child if ELSE child processed */\n\t} /* end of else one child has been processed */\n\n\t/* ignore (replace with constant 0) all nodes which lie on paths larger\n\t * than the maximum length of the path required\n\t */\n\tif (childPathLength > info->maxpath) {\n\t    /* record nodes visited */\n\t    childBranch = zero;\n\t} else {\n\t    if (childPathLength < info->maxpath) {\n\t\tif (info->findShortestPath) {\n\t\t    info->findShortestPath = 0;\n\t\t}\n\t\tchildBranch = BuildSubsetBdd(dd, gInfo, pathTable, child, info,\n\t\t\t\t\t     subsetNodeTable);\n\n\t    } else { /* Case: path length of node = maxpath */\n\t\t/* If the node labeled with maxpath is found in the\n\t\t** maxpathTable, use it to build the subset BDD.  */\n\t\tif (st_lookup(info->maxpathTable, regChild, (void **) &entry)) {\n\t\t    /* When a node that is already been chosen is hit,\n\t\t    ** the quest for a complete path is over.  */\n\t\t    if (info->findShortestPath) {\n\t\t\tinfo->findShortestPath = 0;\n\t\t    }\n\t\t    childBranch = BuildSubsetBdd(dd, gInfo, pathTable, child, info,\n\t\t\t\t\t\t subsetNodeTable);\n\t\t} else {\n\t\t    /* If node is not found in the maxpathTable and\n\t\t    ** the threshold has been reached, then if the\n\t\t    ** path needs to be completed, continue. Else\n\t\t    ** replace the node with a zero.  */\n\t\t    if (info->thresholdReached <= 0) {\n\t\t\tif (info->findShortestPath) {\n\t\t\t    if (st_insert(info->maxpathTable, regChild,\n\t\t\t\t\t  NULL) == ST_OUT_OF_MEM) {\n\t\t\t\tdd->errorCode = CUDD_MEMORY_OUT;\n\t\t\t\t(void) fprintf(dd->err, \"OUT of memory\\n\");\n\t\t\t\tinfo->thresholdReached = 0;\n\t\t\t\tchildBranch = zero;\n\t\t\t    } else {\n\t\t\t\tinfo->thresholdReached--;\n\t\t\t\tchildBranch = BuildSubsetBdd(dd, gInfo, pathTable,\n\t\t\t\t\t\t    child, info,subsetNodeTable);\n\t\t\t    }\n\t\t\t} else { /* not find shortest path, we dont need this\n\t\t\t\t    node */\n\t\t\t    childBranch = zero;\n\t\t\t}\n\t\t    } else { /* Threshold hasn't been reached,\n\t\t\t     ** need the node. */\n\t\t\tif (st_insert(info->maxpathTable, regChild,\n\t\t\t\t      NULL) == ST_OUT_OF_MEM) {\n\t\t\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t\t\t    (void) fprintf(dd->err, \"OUT of memory\\n\");\n\t\t\t    info->thresholdReached = 0;\n\t\t\t    childBranch = zero;\n\t\t\t} else {\n\t\t\t    info->thresholdReached--;\n\t\t\t    if (info->thresholdReached <= 0) {\n\t\t\t\tinfo->findShortestPath = 1;\n\t\t\t    }\n\t\t\t    childBranch = BuildSubsetBdd(dd, gInfo, pathTable,\n\t\t\t\t\t\t child, info, subsetNodeTable);\n\n\t\t\t} /* end of st_insert successful */\n\t\t    } /* end of threshold hasnt been reached yet */\n\t\t} /* end of else node not found in maxpath table */\n\t    } /* end of if (path length of node = maxpath) */\n\t} /* end if !(childPathLength > maxpath) */\n\tif (childBranch == NULL) {\n\t    /* deref other stuff incase reordering has taken place */\n\t    if (ThenBranch != NULL) {\n\t\tCudd_RecursiveDeref(dd, ThenBranch);\n\t\tThenBranch = NULL;\n\t    }\n\t    if (ElseBranch != NULL) {\n\t\tCudd_RecursiveDeref(dd, ElseBranch);\n\t\tElseBranch = NULL;\n\t    }\n\t    return(NULL);\n\t}\n\n\tcuddRef(childBranch);\n\n\tif (child == Nv) {\n\t    ThenBranch = childBranch;\n\t} else {\n\t    ElseBranch = childBranch;\n\t}\n\tprocessingDone++;\n\n    } /*end of while processing Nv, Nnv */\n\n    info->findShortestPath = 0;\n    topid = Cudd_NodeReadIndex(N);\n    topv = Cudd_ReadVars(dd, topid);\n    cuddRef(topv);\n    neW = cuddBddIteRecur(dd, topv, ThenBranch, ElseBranch);\n    if (neW != NULL) {\n\tcuddRef(neW);\n    }\n    Cudd_RecursiveDeref(dd, topv);\n    Cudd_RecursiveDeref(dd, ThenBranch);\n    Cudd_RecursiveDeref(dd, ElseBranch);\n\n\n    if (neW == NULL) {\n\treturn(NULL);\n    } else {\n\n        /* Hard Limit of threshold has been imposed */\n        if (subsetNodeTable != NIL(st_table)) {\n            /* check if a new node is created */\n            regNew = Cudd_Regular(neW);\n            /* subset node table keeps all new nodes that have been created to\n             * keep a running count of how many nodes have been built in the\n             * subset.\n             */\n            if (!st_lookup(subsetNodeTable, regNew, (void **) &entry)) {\n                if (!Cudd_IsConstantInt(regNew)) {\n                    if (st_insert(subsetNodeTable, regNew,\n                                  NULL) == ST_OUT_OF_MEM) {\n                        (void) fprintf(dd->err, \"Out of memory\\n\");\n                        return (NULL);\n                    }\n                    if (st_count(subsetNodeTable) > info->threshold) {\n                        info->thresholdReached = 0;\n                    }\n                }\n            }\n        }\n\n\t/*store computed result in regular form*/\n\tif (Cudd_IsComplement(node)) {\n\t    nodeStat->compResult = neW;\n\t    cuddRef(nodeStat->compResult);\n\t    /* if the new node is the same as the corresponding node in the\n\t     * original bdd then its complement need not be computed as it\n\t     * cannot be larger than the node itself\n\t     */\n\t    if (neW == node) {\n#ifdef DD_DEBUG\n\t\tgInfo->thishit++;\n#endif\n\t\t/* if a result for the node has already been computed, then\n\t\t * it can only be smaller than teh node itself. hence store\n\t\t * the node result in order not to break recombination\n\t\t */\n\t\tif (nodeStat->regResult != NULL) {\n\t\t    Cudd_RecursiveDeref(dd, nodeStat->regResult);\n\t\t}\n\t\tnodeStat->regResult = Cudd_Not(neW);\n\t\tcuddRef(nodeStat->regResult);\n\t    }\n\n\t} else {\n\t    nodeStat->regResult = neW;\n\t    cuddRef(nodeStat->regResult);\n\t    if (neW == node) {\n#ifdef DD_DEBUG\n\t\tgInfo->thishit++;\n#endif\n\t\tif (nodeStat->compResult != NULL) {\n\t\t    Cudd_RecursiveDeref(dd, nodeStat->compResult);\n\t\t}\n\t\tnodeStat->compResult = Cudd_Not(neW);\n\t\tcuddRef(nodeStat->compResult);\n\t    }\n\t}\n\n\tcuddDeref(neW);\n\treturn(neW);\n    } /* end of else i.e. Subset != NULL */\n} /* end of BuildSubsetBdd */\n\n\n/**\n  @brief Procedure to free the result dds stored in the NodeDist pages.\n\n  @sideeffect None\n\n*/\nstatic enum st_retval\nstPathTableDdFree(\n  void * key,\n  void * value,\n  void * arg)\n{\n    NodeDist_t *nodeStat = (NodeDist_t *) value;\n    DdManager *dd = (DdManager *) arg;\n\n    (void) key; /* avoid warning */\n    if (nodeStat->regResult != NULL) {\n\tCudd_RecursiveDeref(dd, nodeStat->regResult);\n    }\n    if (nodeStat->compResult != NULL) {\n\tCudd_RecursiveDeref(dd, nodeStat->compResult);\n    }\n    return(ST_CONTINUE);\n\n} /* end of stPathTableFree */\n"
  },
  {
    "path": "cudd/cudd/cuddSymmetry.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for symmetry-based variable reordering.\n\n  @author Shipra Panda, Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define MV_OOM (Move *)1\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int ddSymmUniqueCompare (void const *ptrX, void const *ptrY);\nstatic int ddSymmSiftingAux (DdManager *table, int x, int xLow, int xHigh);\nstatic int ddSymmSiftingConvAux (DdManager *table, int x, int xLow, int xHigh);\nstatic Move * ddSymmSiftingUp (DdManager *table, int y, int xLow);\nstatic Move * ddSymmSiftingDown (DdManager *table, int x, int xHigh);\nstatic int ddSymmGroupMove (DdManager *table, int x, int y, Move **moves);\nstatic int ddSymmGroupMoveBackward (DdManager *table, int x, int y);\nstatic int ddSymmSiftingBackward (DdManager *table, Move *moves, int size);\nstatic void ddSymmSummary (DdManager *table, int lower, int upper, int *symvars, int *symgroups);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints statistics on symmetric variables.\n\n  @details The information is accurate only if this function is called\n  right after reordering with methods CUDD_REORDER_SYMM_SIFT or\n  CUDD_REORDER_SYMM_SIFT_CONV.\n\n  @sideeffect None\n\n*/\nvoid\nCudd_SymmProfile(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int i,x,gbot;\n    int TotalSymm = 0;\n    int TotalSymmGroups = 0;\n\n    for (i = lower; i <= upper; i++) {\n\tif (table->subtables[i].next != (unsigned) i) {\n\t    x = i;\n\t    (void) fprintf(table->out,\"Group:\");\n\t    do {\n\t\t(void) fprintf(table->out,\"  %d\",table->invperm[x]);\n\t\tTotalSymm++;\n\t\tgbot = x;\n\t\tx = table->subtables[x].next;\n\t    } while (x != i);\n\t    TotalSymmGroups++;\n#ifdef DD_DEBUG\n\t    assert(table->subtables[gbot].next == (unsigned) i);\n#endif\n\t    i = gbot;\n\t    (void) fprintf(table->out,\"\\n\");\n\t}\n    }\n    (void) fprintf(table->out,\"Total Symmetric = %d\\n\",TotalSymm);\n    (void) fprintf(table->out,\"Total Groups = %d\\n\",TotalSymmGroups);\n\n} /* end of Cudd_SymmProfile */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Checks for symmetry of x and y.\n\n  @details Ignores projection functions, unless they are isolated.\n\n  @return 1 in case of symmetry; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddSymmCheck(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    DdNode *f,*f0,*f1,*f01,*f00,*f11,*f10;\n    int comple;\t\t/* f0 is complemented */\n    int xsymmy;\t\t/* x and y may be positively symmetric */\n    int xsymmyp;\t/* x and y may be negatively symmetric */\n    int arccount;\t/* number of arcs from layer x to layer y */\n    int TotalRefCount;\t/* total reference count of layer y minus 1 */\n    int yindex;\n    int i;\n    DdNodePtr *list;\n    int slots;\n    DdNode *sentinel = &(table->sentinel);\n#ifdef DD_DEBUG\n    int xindex;\n#endif\n\n    /* Checks that x and y are not the projection functions.\n    ** For x it is sufficient to check whether there is only one\n    ** node; indeed, if there is one node, it is the projection function\n    ** and it cannot point to y. Hence, if y isn't just the projection\n    ** function, it has one arc coming from a layer different from x.\n    */\n    if (table->subtables[x].keys == 1) {\n\treturn(0);\n    }\n    yindex = table->invperm[y];\n    if (table->subtables[y].keys == 1) {\n\tif (table->vars[yindex]->ref == 1)\n\t    return(0);\n    }\n\n    xsymmy = xsymmyp = 1;\n    arccount = 0;\n    slots = table->subtables[x].slots;\n    list = table->subtables[x].nodelist;\n    for (i = 0; i < slots; i++) {\n\tf = list[i];\n\twhile (f != sentinel) {\n\t    /* Find f1, f0, f11, f10, f01, f00. */\n\t    f1 = cuddT(f);\n\t    f0 = Cudd_Regular(cuddE(f));\n\t    comple = Cudd_IsComplement(cuddE(f));\n\t    if ((int) f1->index == yindex) {\n\t\tarccount++;\n\t\tf11 = cuddT(f1); f10 = cuddE(f1);\n\t    } else {\n\t\tif ((int) f0->index != yindex) {\n\t\t    /* If f is an isolated projection function it is\n\t\t    ** allowed to bypass layer y.\n\t\t    */\n\t\t    if (f1 != DD_ONE(table) || f0 != DD_ONE(table) || f->ref != 1)\n\t\t\treturn(0); /* f bypasses layer y */\n\t\t}\n\t\tf11 = f10 = f1;\n\t    }\n\t    if ((int) f0->index == yindex) {\n\t\tarccount++;\n\t\tf01 = cuddT(f0); f00 = cuddE(f0);\n\t    } else {\n\t\tf01 = f00 = f0;\n\t    }\n\t    if (comple) {\n\t\tf01 = Cudd_Not(f01);\n\t\tf00 = Cudd_Not(f00);\n\t    }\n\n\t    if (f1 != DD_ONE(table) || f0 != DD_ONE(table) || f->ref != 1) {\n\t\txsymmy &= f01 == f10;\n\t\txsymmyp &= f11 == f00;\n\t\tif ((xsymmy == 0) && (xsymmyp == 0))\n\t\t    return(0);\n\t    }\n\n\t    f = f->next;\n\t} /* while */\n    } /* for */\n\n    /* Calculate the total reference counts of y */\n    TotalRefCount = -1; /* -1 for projection function */\n    slots = table->subtables[y].slots;\n    list = table->subtables[y].nodelist;\n    for (i = 0; i < slots; i++) {\n\tf = list[i];\n\twhile (f != sentinel) {\n\t    TotalRefCount += f->ref;\n\t    f = f->next;\n\t}\n    }\n\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    if (arccount == TotalRefCount) {\n\txindex = table->invperm[x];\n\t(void) fprintf(table->out,\n\t\t       \"Found symmetry! x =%d\\ty = %d\\tPos(%d,%d)\\n\",\n\t\t       xindex,yindex,x,y);\n    }\n#endif\n\n    return(arccount == TotalRefCount);\n\n} /* end of cuddSymmCheck */\n\n\n/**\n  @brief Symmetric sifting algorithm.\n\n  @details Assumes that no dead nodes are present.\n    <ol>\n    <li> Order all the variables according to the number of entries in\n    each unique subtable.\n    <li> Sift the variable up and down, remembering each time the total\n    size of the DD heap and grouping variables that are symmetric.\n    <li> Select the best permutation.\n    <li> Repeat 3 and 4 for all variables.\n    </ol>\n\n  @return 1 plus the number of symmetric variables if successful; 0\n  otherwise.\n\n  @sideeffect None\n\n  @see cuddSymmSiftingConv\n\n*/\nint\ncuddSymmSifting(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\t\ti;\n    IndexKey\t*var;\n    int\t\tsize;\n    int\t\tx;\n    int\t\tresult;\n    int\t\tsymvars;\n    int\t\tsymgroups;\n#ifdef DD_STATS\n    int\t\tpreviousSize;\n#endif\n\n    size = table->size;\n\n    /* Find order in which to sift variables. */\n    var = ALLOC(IndexKey,size);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto ddSymmSiftingOutOfMem;\n    }\n\n    for (i = 0; i < size; i++) {\n\tx = table->perm[i];\n\tvar[i].index = i;\n\tvar[i].keys = table->subtables[x].keys;\n    }\n\n    util_qsort(var,size,sizeof(IndexKey),ddSymmUniqueCompare);\n\n    /* Initialize the symmetry of each subtable to itself. */\n    for (i = lower; i <= upper; i++) {\n\ttable->subtables[i].next = i;\n    }\n\n    for (i = 0; i < ddMin(table->siftMaxVar,size); i++) {\n\tif (table->ddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime > table->timeLimit) {\n            table->autoDyn = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDyn = 0; /* prevent further reordering */\n            break;\n        }\n\tx = table->perm[var[i].index];\n#ifdef DD_STATS\n\tpreviousSize = (int) (table->keys - table->isolated);\n#endif\n\tif (x < lower || x > upper) continue;\n\tif (table->subtables[x].next == (unsigned) x) {\n\t    result = ddSymmSiftingAux(table,x,lower,upper);\n\t    if (!result) goto ddSymmSiftingOutOfMem;\n#ifdef DD_STATS\n\t    if (table->keys < (unsigned) previousSize + table->isolated) {\n\t\t(void) fprintf(table->out,\"-\");\n\t    } else if (table->keys > (unsigned) previousSize +\n\t\t       table->isolated) {\n\t\t(void) fprintf(table->out,\"+\"); /* should never happen */\n\t    } else {\n\t\t(void) fprintf(table->out,\"=\");\n\t    }\n\t    fflush(table->out);\n#endif\n\t}\n    }\n\n    FREE(var);\n\n    ddSymmSummary(table, lower, upper, &symvars, &symgroups);\n\n#ifdef DD_STATS\n    (void) fprintf(table->out, \"\\n#:S_SIFTING %8d: symmetric variables\\n\",\n\t\t   symvars);\n    (void) fprintf(table->out, \"#:G_SIFTING %8d: symmetric groups\",\n\t\t   symgroups);\n#endif\n\n    return(1+symvars);\n\nddSymmSiftingOutOfMem:\n\n    if (var != NULL) FREE(var);\n\n    return(0);\n\n} /* end of cuddSymmSifting */\n\n\n/**\n  @brief Symmetric sifting to convergence algorithm.\n\n  @details Assumes that no dead nodes are present.\n    <ol>\n    <li> Order all the variables according to the number of entries in\n    each unique subtable.\n    <li> Sift the variable up and down, remembering each time the total\n    size of the %DD heap and grouping variables that are symmetric.\n    <li> Select the best permutation.\n    <li> Repeat 3 and 4 for all variables.\n    <li> Repeat 1-4 until no further improvement.\n    </ol>\n\n  @return 1 plus the number of symmetric variables if successful; 0\n  otherwise.\n\n  @sideeffect None\n\n  @see cuddSymmSifting\n\n*/\nint\ncuddSymmSiftingConv(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\t\ti;\n    IndexKey\t*var;\n    int\t\tsize;\n    int\t\tx;\n    int\t\tresult;\n    int\t\tsymvars;\n    int\t\tsymgroups;\n    int\t\tclasses;\n    int\t\tinitialSize;\n#ifdef DD_STATS\n    int\t\tpreviousSize;\n#endif\n\n    initialSize = (int) (table->keys - table->isolated);\n\n    size = table->size;\n\n    /* Find order in which to sift variables. */\n    var = ALLOC(IndexKey,size);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto ddSymmSiftingConvOutOfMem;\n    }\n\n    for (i = 0; i < size; i++) {\n\tx = table->perm[i];\n\tvar[i].index = i;\n\tvar[i].keys = table->subtables[x].keys;\n    }\n\n    util_qsort(var,size,sizeof(IndexKey),ddSymmUniqueCompare);\n\n    /* Initialize the symmetry of each subtable to itself\n    ** for first pass of converging symmetric sifting.\n    */\n    for (i = lower; i <= upper; i++) {\n\ttable->subtables[i].next = i;\n    }\n\n    for (i = 0; i < ddMin(table->siftMaxVar, table->size); i++) {\n\tif (table->ddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime > table->timeLimit) {\n            table->autoDyn = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDyn = 0; /* prevent further reordering */\n            break;\n        }\n\tx = table->perm[var[i].index];\n\tif (x < lower || x > upper) continue;\n\t/* Only sift if not in symmetry group already. */\n\tif (table->subtables[x].next == (unsigned) x) {\n#ifdef DD_STATS\n          previousSize = (int) (table->keys - table->isolated);\n#endif\n\t    result = ddSymmSiftingAux(table,x,lower,upper);\n\t    if (!result) goto ddSymmSiftingConvOutOfMem;\n#ifdef DD_STATS\n\t    if (table->keys < (unsigned) previousSize + table->isolated) {\n\t\t(void) fprintf(table->out,\"-\");\n\t    } else if (table->keys > (unsigned) previousSize +\n\t\t       table->isolated) {\n\t\t(void) fprintf(table->out,\"+\");\n\t    } else {\n\t\t(void) fprintf(table->out,\"=\");\n\t    }\n\t    fflush(table->out);\n#endif\n\t}\n    }\n\n    /* Sifting now until convergence. */\n    while ((unsigned) initialSize > table->keys - table->isolated) {\n      initialSize = (int) (table->keys - table->isolated);\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\"\\n\");\n#endif\n\t/* Here we consider only one representative for each symmetry class. */\n\tfor (x = lower, classes = 0; x <= upper; x++, classes++) {\n\t    while ((unsigned) x < table->subtables[x].next) {\n\t\tx = table->subtables[x].next;\n\t    }\n\t    /* Here x is the largest index in a group.\n\t    ** Groups consist of adjacent variables.\n\t    ** Hence, the next increment of x will move it to a new group.\n\t    */\n\t    i = table->invperm[x];\n\t    var[classes].keys = table->subtables[x].keys;\n\t    var[classes].index = i;\n\t}\n\n\tutil_qsort(var,classes,sizeof(IndexKey),ddSymmUniqueCompare);\n\n\t/* Now sift. */\n\tfor (i = 0; i < ddMin(table->siftMaxVar,classes); i++) {\n\t    if (table->ddTotalNumberSwapping >= table->siftMaxSwap)\n\t\tbreak;\n            if (util_cpu_time() - table->startTime > table->timeLimit) {\n              table->autoDyn = 0; /* prevent further reordering */\n              break;\n            }\n            if (table->terminationCallback != NULL &&\n                table->terminationCallback(table->tcbArg)) {\n                table->autoDyn = 0; /* prevent further reordering */\n                break;\n            }\n\t    x = table->perm[var[i].index];\n\t    if ((unsigned) x >= table->subtables[x].next) {\n#ifdef DD_STATS\n              previousSize = (int) (table->keys - table->isolated);\n#endif\n\t\tresult = ddSymmSiftingConvAux(table,x,lower,upper);\n\t\tif (!result ) goto ddSymmSiftingConvOutOfMem;\n#ifdef DD_STATS\n\t\tif (table->keys < (unsigned) previousSize + table->isolated) {\n\t\t    (void) fprintf(table->out,\"-\");\n\t\t} else if (table->keys > (unsigned) previousSize +\n\t\t\t   table->isolated) {\n\t\t    (void) fprintf(table->out,\"+\");\n\t\t} else {\n\t\t    (void) fprintf(table->out,\"=\");\n\t\t}\n\t\tfflush(table->out);\n#endif\n\t    }\n\t} /* for */\n    }\n\n    ddSymmSummary(table, lower, upper, &symvars, &symgroups);\n\n#ifdef DD_STATS\n    (void) fprintf(table->out, \"\\n#:S_SIFTING %8d: symmetric variables\\n\",\n\t\t   symvars);\n    (void) fprintf(table->out, \"#:G_SIFTING %8d: symmetric groups\",\n\t\t   symgroups);\n#endif\n\n    FREE(var);\n\n    return(1+symvars);\n\nddSymmSiftingConvOutOfMem:\n\n    if (var != NULL) FREE(var);\n\n    return(0);\n\n} /* end of cuddSymmSiftingConv */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Used to order the variables according to the number of keys\n  in the subtables.\n\n  @return the difference in number of keys between the two variables\n  being compared.\n\n  @sideeffect None\n\n*/\nstatic int\nddSymmUniqueCompare(\n  void const * ptrX,\n  void const * ptrY)\n{\n    IndexKey const * pX = (IndexKey const *) ptrX;\n    IndexKey const * pY = (IndexKey const *) ptrY;\n#if 0\n    if (pY->keys == pX->keys) {\n\treturn(pX->index - pY->index);\n    }\n#endif\n    return(pY->keys - pX->keys);\n\n} /* end of ddSymmUniqueCompare */\n\n\n/**\n  @brief Given xLow <= x <= xHigh moves x up and down between the\n  boundaries.\n\n  @details Finds the best position and does the required changes.\n  Assumes that x is not part of a symmetry group.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddSymmSiftingAux(\n  DdManager * table,\n  int  x,\n  int  xLow,\n  int  xHigh)\n{\n    Move *move;\n    Move *moveUp;\t/* list of up moves */\n    Move *moveDown;\t/* list of down moves */\n    int\t initialSize;\n    int\t result;\n    int  i;\n    int  topbot;\t/* index to either top or bottom of symmetry group */\n    int  initGroupSize, finalGroupSize;\n\n\n#ifdef DD_DEBUG\n    /* check for previously detected symmetry */\n    assert(table->subtables[x].next == (unsigned) x);\n#endif\n\n    initialSize = (int) (table->keys - table->isolated);\n\n    moveDown = NULL;\n    moveUp = NULL;\n\n    if ((x - xLow) > (xHigh - x)) {\n\t/* Will go down first, unless x == xHigh:\n\t** Look for consecutive symmetries above x.\n\t*/\n\tfor (i = x; i > xLow; i--) {\n\t    if (!cuddSymmCheck(table,i-1,i))\n\t\tbreak;\n\t    topbot = table->subtables[i-1].next; /* find top of i-1's group */\n\t    table->subtables[i-1].next = i;\n\t    table->subtables[x].next = topbot; /* x is bottom of group so its */\n\t\t\t\t\t       /* next is top of i-1's group */\n\t    i = topbot + 1; /* add 1 for i--; new i is top of symm group */\n\t}\n    } else {\n\t/* Will go up first unless x == xlow:\n\t** Look for consecutive symmetries below x.\n\t*/\n\tfor (i = x; i < xHigh; i++) {\n\t    if (!cuddSymmCheck(table,i,i+1))\n\t\tbreak;\n\t    /* find bottom of i+1's symm group */\n\t    topbot = i + 1;\n\t    while ((unsigned) topbot < table->subtables[topbot].next) {\n\t\ttopbot = table->subtables[topbot].next;\n\t    }\n\t    table->subtables[topbot].next = table->subtables[i].next;\n\t    table->subtables[i].next = i + 1;\n\t    i = topbot - 1; /* subtract 1 for i++; new i is bottom of group */\n\t}\n    }\n\n    /* Now x may be in the middle of a symmetry group.\n    ** Find bottom of x's symm group.\n    */\n    while ((unsigned) x < table->subtables[x].next)\n\tx = table->subtables[x].next;\n\n    if (x == xLow) { /* Sift down */\n\n#ifdef DD_DEBUG\n\t/* x must be a singleton */\n\tassert((unsigned) x == table->subtables[x].next);\n#endif\n\tif (x == xHigh) return(1);\t/* just one variable */\n\n\tinitGroupSize = 1;\n\n\tmoveDown = ddSymmSiftingDown(table,x,xHigh);\n\t    /* after this point x --> xHigh, unless early term */\n\tif (moveDown == MV_OOM) goto ddSymmSiftingAuxOutOfMem;\n\tif (moveDown == NULL) return(1);\n\n\tx = moveDown->y;\n\t/* Find bottom of x's group */\n\ti = x;\n\twhile ((unsigned) i < table->subtables[i].next) {\n\t    i = table->subtables[i].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x should be the top of the symmetry group and i the bottom */\n\tassert((unsigned) i >= table->subtables[i].next);\n\tassert((unsigned) x == table->subtables[i].next);\n#endif\n\tfinalGroupSize = i - x + 1;\n\n\tif (initGroupSize == finalGroupSize) {\n\t    /* No new symmetry groups detected, return to best position */\n\t    result = ddSymmSiftingBackward(table,moveDown,initialSize);\n\t} else {\n          initialSize = (int) (table->keys - table->isolated);\n\t    moveUp = ddSymmSiftingUp(table,x,xLow);\n\t    result = ddSymmSiftingBackward(table,moveUp,initialSize);\n\t}\n\tif (!result) goto ddSymmSiftingAuxOutOfMem;\n\n    } else if (cuddNextHigh(table,x) > xHigh) { /* Sift up */\n\t/* Find top of x's symm group */\n\ti = x;\t\t\t\t/* bottom */\n\tx = table->subtables[x].next;\t/* top */\n\n\tif (x == xLow) return(1); /* just one big group */\n\n\tinitGroupSize = i - x + 1;\n\n\tmoveUp = ddSymmSiftingUp(table,x,xLow);\n\t    /* after this point x --> xLow, unless early term */\n\tif (moveUp == MV_OOM) goto ddSymmSiftingAuxOutOfMem;\n\tif (moveUp == NULL) return(1);\n\n\tx = moveUp->x;\n\t/* Find top of x's group */\n\ti = table->subtables[x].next;\n#ifdef DD_DEBUG\n\t/* x should be the bottom of the symmetry group and i the top */\n\tassert((unsigned) x >= table->subtables[x].next);\n\tassert((unsigned) i == table->subtables[x].next);\n#endif\n\tfinalGroupSize = x - i + 1;\n\n\tif (initGroupSize == finalGroupSize) {\n\t    /* No new symmetry groups detected, return to best position */\n\t    result = ddSymmSiftingBackward(table,moveUp,initialSize);\n\t} else {\n          initialSize = (int) (table->keys - table->isolated);\n\t    moveDown = ddSymmSiftingDown(table,x,xHigh);\n\t    result = ddSymmSiftingBackward(table,moveDown,initialSize);\n\t}\n\tif (!result) goto ddSymmSiftingAuxOutOfMem;\n\n    } else if ((x - xLow) > (xHigh - x)) { /* must go down first: shorter */\n\n\tmoveDown = ddSymmSiftingDown(table,x,xHigh);\n\t/* at this point x == xHigh, unless early term */\n\tif (moveDown == MV_OOM) goto ddSymmSiftingAuxOutOfMem;\n\n\tif (moveDown != NULL) {\n\t    x = moveDown->y;\t/* x is top here */\n\t    i = x;\n\t    while ((unsigned) i < table->subtables[i].next) {\n\t\ti = table->subtables[i].next;\n\t    }\n\t} else {\n\t    i = x;\n\t    while ((unsigned) i < table->subtables[i].next) {\n\t\ti = table->subtables[i].next;\n\t    }\n\t    x = table->subtables[i].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x should be the top of the symmetry group and i the bottom */\n\tassert((unsigned) i >= table->subtables[i].next);\n\tassert((unsigned) x == table->subtables[i].next);\n#endif\n\tinitGroupSize = i - x + 1;\n\n\tmoveUp = ddSymmSiftingUp(table,x,xLow);\n\tif (moveUp == MV_OOM) goto ddSymmSiftingAuxOutOfMem;\n\n\tif (moveUp != NULL) {\n\t    x = moveUp->x;\n\t    i = table->subtables[x].next;\n\t} else {\n\t    i = x;\n\t    while ((unsigned) x < table->subtables[x].next)\n\t\tx = table->subtables[x].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x should be the bottom of the symmetry group and i the top */\n\tassert((unsigned) x >= table->subtables[x].next);\n\tassert((unsigned) i == table->subtables[x].next);\n#endif\n\tfinalGroupSize = x - i + 1;\n\n\tif (initGroupSize == finalGroupSize) {\n\t    /* No new symmetry groups detected, return to best position */\n\t    result = ddSymmSiftingBackward(table,moveUp,initialSize);\n\t} else {\n\t    while (moveDown != NULL) {\n\t\tmove = moveDown->next;\n\t\tcuddDeallocMove(table, moveDown);\n\t\tmoveDown = move;\n\t    }\n\t    initialSize = (int) (table->keys - table->isolated);\n\t    moveDown = ddSymmSiftingDown(table,x,xHigh);\n\t    result = ddSymmSiftingBackward(table,moveDown,initialSize);\n\t}\n\tif (!result) goto ddSymmSiftingAuxOutOfMem;\n\n    } else { /* moving up first: shorter */\n\t/* Find top of x's symmetry group */\n\tx = table->subtables[x].next;\n\n\tmoveUp = ddSymmSiftingUp(table,x,xLow);\n\t/* at this point x == xHigh, unless early term */\n\tif (moveUp == MV_OOM) goto ddSymmSiftingAuxOutOfMem;\n\n\tif (moveUp != NULL) {\n\t    x = moveUp->x;\n\t    i = table->subtables[x].next;\n\t} else {\n\t    while ((unsigned) x < table->subtables[x].next)\n\t\tx = table->subtables[x].next;\n\t    i = table->subtables[x].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x is bottom of the symmetry group and i is top */\n\tassert((unsigned) x >= table->subtables[x].next);\n\tassert((unsigned) i == table->subtables[x].next);\n#endif\n\tinitGroupSize = x - i + 1;\n\n\tmoveDown = ddSymmSiftingDown(table,x,xHigh);\n\tif (moveDown == MV_OOM) goto ddSymmSiftingAuxOutOfMem;\n\n\tif (moveDown != NULL) {\n\t    x = moveDown->y;\n\t    i = x;\n\t    while ((unsigned) i < table->subtables[i].next) {\n\t\ti = table->subtables[i].next;\n\t    }\n\t} else {\n\t    i = x;\n\t    x = table->subtables[x].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x should be the top of the symmetry group and i the bottom */\n\tassert((unsigned) i >= table->subtables[i].next);\n\tassert((unsigned) x == table->subtables[i].next);\n#endif\n\tfinalGroupSize = i - x + 1;\n\n\tif (initGroupSize == finalGroupSize) {\n\t    /* No new symmetries detected, go back to best position */\n\t    result = ddSymmSiftingBackward(table,moveDown,initialSize);\n\t} else {\n\t    while (moveUp != NULL) {\n\t\tmove = moveUp->next;\n\t\tcuddDeallocMove(table, moveUp);\n\t\tmoveUp = move;\n\t    }\n\t    initialSize = (int) (table->keys - table->isolated);\n\t    moveUp = ddSymmSiftingUp(table,x,xLow);\n\t    result = ddSymmSiftingBackward(table,moveUp,initialSize);\n\t}\n\tif (!result) goto ddSymmSiftingAuxOutOfMem;\n    }\n\n    while (moveDown != NULL) {\n\tmove = moveDown->next;\n\tcuddDeallocMove(table, moveDown);\n\tmoveDown = move;\n    }\n    while (moveUp != NULL) {\n\tmove = moveUp->next;\n\tcuddDeallocMove(table, moveUp);\n\tmoveUp = move;\n    }\n\n    return(1);\n\nddSymmSiftingAuxOutOfMem:\n    if (moveDown != MV_OOM) {\n\twhile (moveDown != NULL) {\n\t    move = moveDown->next;\n\t    cuddDeallocMove(table, moveDown);\n\t    moveDown = move;\n\t}\n    }\n    if (moveUp != MV_OOM) {\n\twhile (moveUp != NULL) {\n\t    move = moveUp->next;\n\t    cuddDeallocMove(table, moveUp);\n\t    moveUp = move;\n\t}\n    }\n\n    return(0);\n\n} /* end of ddSymmSiftingAux */\n\n\n/**\n  @brief Given xLow <= x <= xHigh moves x up and down between the\n  boundaries.\n\n  @details Finds the best position and does the required changes.\n  Assumes that x is either an isolated variable, or it is the bottom of\n  a symmetry group. All symmetries may not have been found, because of\n  exceeded growth limit.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddSymmSiftingConvAux(\n  DdManager * table,\n  int  x,\n  int  xLow,\n  int  xHigh)\n{\n    Move *move;\n    Move *moveUp;\t/* list of up moves */\n    Move *moveDown;\t/* list of down moves */\n    int\t initialSize;\n    int\t result;\n    int  i;\n    int  initGroupSize, finalGroupSize;\n\n\n    initialSize = (int) (table->keys - table->isolated);\n\n    moveDown = NULL;\n    moveUp = NULL;\n\n    if (x == xLow) { /* Sift down */\n#ifdef DD_DEBUG\n\t/* x is bottom of symmetry group */\n\tassert((unsigned) x >= table->subtables[x].next);\n#endif\n\ti = table->subtables[x].next;\n\tinitGroupSize = x - i + 1;\n\n\tmoveDown = ddSymmSiftingDown(table,x,xHigh);\n\t/* at this point x == xHigh, unless early term */\n\tif (moveDown == MV_OOM) goto ddSymmSiftingConvAuxOutOfMem;\n\tif (moveDown == NULL) return(1);\n\n\tx = moveDown->y;\n\ti = x;\n\twhile ((unsigned) i < table->subtables[i].next) {\n\t    i = table->subtables[i].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x should be the top of the symmetric group and i the bottom */\n\tassert((unsigned) i >= table->subtables[i].next);\n\tassert((unsigned) x == table->subtables[i].next);\n#endif\n\tfinalGroupSize = i - x + 1;\n\n\tif (initGroupSize == finalGroupSize) {\n\t    /* No new symmetries detected, go back to best position */\n\t    result = ddSymmSiftingBackward(table,moveDown,initialSize);\n\t} else {\n          initialSize = (int) (table->keys - table->isolated);\n\t    moveUp = ddSymmSiftingUp(table,x,xLow);\n\t    result = ddSymmSiftingBackward(table,moveUp,initialSize);\n\t}\n\tif (!result) goto ddSymmSiftingConvAuxOutOfMem;\n\n    } else if (cuddNextHigh(table,x) > xHigh) { /* Sift up */\n\t/* Find top of x's symm group */\n\twhile ((unsigned) x < table->subtables[x].next)\n\t    x = table->subtables[x].next;\n\ti = x;\t\t\t\t/* bottom */\n\tx = table->subtables[x].next;\t/* top */\n\n\tif (x == xLow) return(1);\n\n\tinitGroupSize = i - x + 1;\n\n\tmoveUp = ddSymmSiftingUp(table,x,xLow);\n\t    /* at this point x == xLow, unless early term */\n\tif (moveUp == MV_OOM) goto ddSymmSiftingConvAuxOutOfMem;\n\tif (moveUp == NULL) return(1);\n\n\tx = moveUp->x;\n\ti = table->subtables[x].next;\n#ifdef DD_DEBUG\n\t/* x should be the bottom of the symmetry group and i the top */\n\tassert((unsigned) x >= table->subtables[x].next);\n\tassert((unsigned) i == table->subtables[x].next);\n#endif\n\tfinalGroupSize = x - i + 1;\n\n\tif (initGroupSize == finalGroupSize) {\n\t    /* No new symmetry groups detected, return to best position */\n\t    result = ddSymmSiftingBackward(table,moveUp,initialSize);\n\t} else {\n          initialSize = (int) (table->keys - table->isolated);\n\t    moveDown = ddSymmSiftingDown(table,x,xHigh);\n\t    result = ddSymmSiftingBackward(table,moveDown,initialSize);\n\t}\n\tif (!result)\n\t    goto ddSymmSiftingConvAuxOutOfMem;\n\n    } else if ((x - xLow) > (xHigh - x)) { /* must go down first: shorter */\n\tmoveDown = ddSymmSiftingDown(table,x,xHigh);\n\t    /* at this point x == xHigh, unless early term */\n\tif (moveDown == MV_OOM) goto ddSymmSiftingConvAuxOutOfMem;\n\n\tif (moveDown != NULL) {\n\t    x = moveDown->y;\n\t    i = x;\n\t    while ((unsigned) i < table->subtables[i].next) {\n\t\ti = table->subtables[i].next;\n\t    }\n\t} else {\n\t    while ((unsigned) x < table->subtables[x].next)\n\t\tx = table->subtables[x].next;\n\t    i = x;\n\t    x = table->subtables[x].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x should be the top of the symmetry group and i the bottom */\n\tassert((unsigned) i >= table->subtables[i].next);\n\tassert((unsigned) x == table->subtables[i].next);\n#endif\n\tinitGroupSize = i - x + 1;\n\n\tmoveUp = ddSymmSiftingUp(table,x,xLow);\n\tif (moveUp == MV_OOM) goto ddSymmSiftingConvAuxOutOfMem;\n\n\tif (moveUp != NULL) {\n\t    x = moveUp->x;\n\t    i = table->subtables[x].next;\n\t} else {\n\t    i = x;\n\t    while ((unsigned) x < table->subtables[x].next)\n\t\tx = table->subtables[x].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x should be the bottom of the symmetry group and i the top */\n\tassert((unsigned) x >= table->subtables[x].next);\n\tassert((unsigned) i == table->subtables[x].next);\n#endif\n\tfinalGroupSize = x - i + 1;\n\n\tif (initGroupSize == finalGroupSize) {\n\t    /* No new symmetry groups detected, return to best position */\n\t    result = ddSymmSiftingBackward(table,moveUp,initialSize);\n\t} else {\n\t    while (moveDown != NULL) {\n\t\tmove = moveDown->next;\n\t\tcuddDeallocMove(table, moveDown);\n\t\tmoveDown = move;\n\t    }\n\t    initialSize = (int) (table->keys - table->isolated);\n\t    moveDown = ddSymmSiftingDown(table,x,xHigh);\n\t    result = ddSymmSiftingBackward(table,moveDown,initialSize);\n\t}\n\tif (!result) goto ddSymmSiftingConvAuxOutOfMem;\n\n    } else { /* moving up first: shorter */\n\t/* Find top of x's symmetry group */\n\tx = table->subtables[x].next;\n\n\tmoveUp = ddSymmSiftingUp(table,x,xLow);\n\t/* at this point x == xHigh, unless early term */\n\tif (moveUp == MV_OOM) goto ddSymmSiftingConvAuxOutOfMem;\n\n\tif (moveUp != NULL) {\n\t    x = moveUp->x;\n\t    i = table->subtables[x].next;\n\t} else {\n\t    i = x;\n\t    while ((unsigned) x < table->subtables[x].next)\n\t\tx = table->subtables[x].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x is bottom of the symmetry group and i is top */\n\tassert((unsigned) x >= table->subtables[x].next);\n\tassert((unsigned) i == table->subtables[x].next);\n#endif\n\tinitGroupSize = x - i + 1;\n\n\tmoveDown = ddSymmSiftingDown(table,x,xHigh);\n\tif (moveDown == MV_OOM) goto ddSymmSiftingConvAuxOutOfMem;\n\n\tif (moveDown != NULL) {\n\t    x = moveDown->y;\n\t    i = x;\n\t    while ((unsigned) i < table->subtables[i].next) {\n\t\ti = table->subtables[i].next;\n\t    }\n\t} else {\n\t    i = x;\n\t    x = table->subtables[x].next;\n\t}\n#ifdef DD_DEBUG\n\t/* x should be the top of the symmetry group and i the bottom */\n\tassert((unsigned) i >= table->subtables[i].next);\n\tassert((unsigned) x == table->subtables[i].next);\n#endif\n\tfinalGroupSize = i - x + 1;\n\n\tif (initGroupSize == finalGroupSize) {\n\t    /* No new symmetries detected, go back to best position */\n\t    result = ddSymmSiftingBackward(table,moveDown,initialSize);\n\t} else {\n\t    while (moveUp != NULL) {\n\t\tmove = moveUp->next;\n\t\tcuddDeallocMove(table, moveUp);\n\t\tmoveUp = move;\n\t    }\n\t    initialSize = (int) (table->keys - table->isolated);\n\t    moveUp = ddSymmSiftingUp(table,x,xLow);\n\t    result = ddSymmSiftingBackward(table,moveUp,initialSize);\n\t}\n\tif (!result) goto ddSymmSiftingConvAuxOutOfMem;\n    }\n\n    while (moveDown != NULL) {\n\tmove = moveDown->next;\n\tcuddDeallocMove(table, moveDown);\n\tmoveDown = move;\n    }\n    while (moveUp != NULL) {\n\tmove = moveUp->next;\n\tcuddDeallocMove(table, moveUp);\n\tmoveUp = move;\n    }\n\n    return(1);\n\nddSymmSiftingConvAuxOutOfMem:\n    if (moveDown != MV_OOM) {\n\twhile (moveDown != NULL) {\n\t    move = moveDown->next;\n\t    cuddDeallocMove(table, moveDown);\n\t    moveDown = move;\n\t}\n    }\n    if (moveUp != MV_OOM) {\n\twhile (moveUp != NULL) {\n\t    move = moveUp->next;\n\t    cuddDeallocMove(table, moveUp);\n\t    moveUp = move;\n\t}\n    }\n\n    return(0);\n\n} /* end of ddSymmSiftingConvAux */\n\n\n/**\n  @brief Moves x up until either it reaches the bound (xLow) or\n  the size of the %DD heap increases too much.\n\n  @details Assumes that x is the top of a symmetry group.  Checks x\n  for symmetry to the adjacent variables. If symmetry is found, the\n  symmetry group of x is merged with the symmetry group of the other\n  variable.\n\n  @return the set of moves in case of success; MV_OOM if memory is\n  full.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddSymmSiftingUp(\n  DdManager * table,\n  int  y,\n  int  xLow)\n{\n    Move *moves;\n    Move *move;\n    int\t x;\n    int\t size;\n    int  i;\n    int  gxtop,gybot;\n    int  limitSize;\n    int  xindex, yindex;\n    int  zindex;\n    int  z;\n    int  isolated;\n    int  L;\t/* lower bound on DD size */\n#ifdef DD_DEBUG\n    int  checkL;\n#endif\n\n\n    moves = NULL;\n    yindex = table->invperm[y];\n\n    /* Initialize the lower bound.\n    ** The part of the DD below the bottom of y' group will not change.\n    ** The part of the DD above y that does not interact with y will not\n    ** change. The rest may vanish in the best case, except for\n    ** the nodes at level xLow, which will not vanish, regardless.\n    */\n    limitSize = L = (int) (table->keys - table->isolated);\n    gybot = y;\n    while ((unsigned) gybot < table->subtables[gybot].next)\n\tgybot = table->subtables[gybot].next;\n    for (z = xLow + 1; z <= gybot; z++) {\n\tzindex = table->invperm[z];\n\tif (zindex == yindex || cuddTestInteract(table,zindex,yindex)) {\n\t    isolated = table->vars[zindex]->ref == 1;\n\t    L -= (int) table->subtables[z].keys - isolated;\n\t}\n    }\n\n    x = cuddNextLow(table,y);\n    while (x >= xLow && L <= limitSize) {\n#ifdef DD_DEBUG\n\tgybot = y;\n\twhile ((unsigned) gybot < table->subtables[gybot].next)\n\t    gybot = table->subtables[gybot].next;\n\tcheckL = (int) (table->keys - table->isolated);\n\tfor (z = xLow + 1; z <= gybot; z++) {\n\t    zindex = table->invperm[z];\n\t    if (zindex == yindex || cuddTestInteract(table,zindex,yindex)) {\n\t\tisolated = table->vars[zindex]->ref == 1;\n\t\tcheckL -= (int) table->subtables[z].keys - isolated;\n\t    }\n\t}\n\tassert(L == checkL);\n#endif\n\tgxtop = table->subtables[x].next;\n\tif (cuddSymmCheck(table,x,y)) {\n\t    /* Symmetry found, attach symm groups */\n\t    table->subtables[x].next = y;\n\t    i = table->subtables[y].next;\n\t    while (table->subtables[i].next != (unsigned) y)\n\t\ti = table->subtables[i].next;\n\t    table->subtables[i].next = gxtop;\n\t} else if (table->subtables[x].next == (unsigned) x &&\n\t\t   table->subtables[y].next == (unsigned) y) {\n\t    /* x and y have self symmetry */\n\t    xindex = table->invperm[x];\n\t    size = cuddSwapInPlace(table,x,y);\n#ifdef DD_DEBUG\n\t    assert(table->subtables[x].next == (unsigned) x);\n\t    assert(table->subtables[y].next == (unsigned) y);\n#endif\n\t    if (size == 0) goto ddSymmSiftingUpOutOfMem;\n\t    /* Update the lower bound. */\n\t    if (cuddTestInteract(table,xindex,yindex)) {\n\t\tisolated = table->vars[xindex]->ref == 1;\n\t\tL += (int) table->subtables[y].keys - isolated;\n\t    }\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddSymmSiftingUpOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(moves);\n\t    if (size < limitSize) limitSize = size;\n\t} else { /* Group move */\n\t    size = ddSymmGroupMove(table,x,y,&moves);\n\t    if (size == 0) goto ddSymmSiftingUpOutOfMem;\n\t    /* Update the lower bound. */\n\t    z = moves->y;\n\t    do {\n\t\tzindex = table->invperm[z];\n\t\tif (cuddTestInteract(table,zindex,yindex)) {\n\t\t    isolated = table->vars[zindex]->ref == 1;\n\t\t    L += (int) table->subtables[z].keys - isolated;\n\t\t}\n\t\tz = table->subtables[z].next;\n\t    } while (z != (int) moves->y);\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(moves);\n\t    if (size < limitSize) limitSize = size;\n\t}\n\ty = gxtop;\n\tx = cuddNextLow(table,y);\n    }\n\n    return(moves);\n\nddSymmSiftingUpOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(MV_OOM);\n\n} /* end of ddSymmSiftingUp */\n\n\n/**\n  @brief Moves x down until either it reaches the bound (xHigh) or\n  the size of the %DD heap increases too much.\n\n  @details Assumes that x is the bottom of a symmetry group. Checks x\n  for symmetry to the adjacent variables. If symmetry is found, the\n  symmetry group of x is merged with the symmetry group of the other\n  variable.\n\n  @return the set of moves in case of success; MV_OOM if memory is\n  full.\n\n  @sideeffect None\n\n*/\nstatic Move *\nddSymmSiftingDown(\n  DdManager * table,\n  int  x,\n  int  xHigh)\n{\n    Move *moves;\n    Move *move;\n    int\t y;\n    int\t size;\n    int  limitSize;\n    int  gxtop,gybot;\n    int  R;\t/* upper bound on node decrease */\n    int  xindex, yindex;\n    int  isolated;\n    int  z;\n    int  zindex;\n#ifdef DD_DEBUG\n    int  checkR;\n#endif\n\n    moves = NULL;\n    /* Initialize R */\n    xindex = table->invperm[x];\n    gxtop = table->subtables[x].next;\n    limitSize = size = (int) (table->keys - table->isolated);\n    R = 0;\n    for (z = xHigh; z > gxtop; z--) {\n\tzindex = table->invperm[z];\n\tif (zindex == xindex || cuddTestInteract(table,xindex,zindex)) {\n\t    isolated = table->vars[zindex]->ref == 1;\n\t    R += (int) table->subtables[z].keys - isolated;\n\t}\n    }\n\n    y = cuddNextHigh(table,x);\n    while (y <= xHigh && size - R < limitSize) {\n#ifdef DD_DEBUG\n\tgxtop = table->subtables[x].next;\n\tcheckR = 0;\n\tfor (z = xHigh; z > gxtop; z--) {\n\t    zindex = table->invperm[z];\n\t    if (zindex == xindex || cuddTestInteract(table,xindex,zindex)) {\n\t\tisolated = table->vars[zindex]->ref == 1;\n\t\tcheckR += (int) table->subtables[z].keys - isolated;\n\t    }\n\t}\n\tassert(R == checkR);\n#endif\n\tgybot = table->subtables[y].next;\n\twhile (table->subtables[gybot].next != (unsigned) y)\n\t    gybot = table->subtables[gybot].next;\n\tif (cuddSymmCheck(table,x,y)) {\n\t    /* Symmetry found, attach symm groups */\n\t    gxtop = table->subtables[x].next;\n\t    table->subtables[x].next = y;\n\t    table->subtables[gybot].next = gxtop;\n\t} else if (table->subtables[x].next == (unsigned) x &&\n\t\t   table->subtables[y].next == (unsigned) y) {\n\t    /* x and y have self symmetry */\n\t    /* Update upper bound on node decrease. */\n\t    yindex = table->invperm[y];\n\t    if (cuddTestInteract(table,xindex,yindex)) {\n\t\tisolated = table->vars[yindex]->ref == 1;\n\t\tR -= (int) table->subtables[y].keys - isolated;\n\t    }\n\t    size = cuddSwapInPlace(table,x,y);\n#ifdef DD_DEBUG\n\t    assert(table->subtables[x].next == (unsigned) x);\n\t    assert(table->subtables[y].next == (unsigned) y);\n#endif\n\t    if (size == 0) goto ddSymmSiftingDownOutOfMem;\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto ddSymmSiftingDownOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(moves);\n\t    if (size < limitSize) limitSize = size;\n\t} else { /* Group move */\n\t    /* Update upper bound on node decrease: first phase. */\n\t    gxtop = table->subtables[x].next;\n\t    z = gxtop + 1;\n\t    do {\n\t\tzindex = table->invperm[z];\n\t\tif (zindex == xindex || cuddTestInteract(table,xindex,zindex)) {\n\t\t    isolated = table->vars[zindex]->ref == 1;\n\t\t    R -= (int) table->subtables[z].keys - isolated;\n\t\t}\n\t\tz++;\n\t    } while (z <= gybot);\n\t    size = ddSymmGroupMove(table,x,y,&moves);\n\t    if (size == 0) goto ddSymmSiftingDownOutOfMem;\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(moves);\n\t    if (size < limitSize) limitSize = size;\n\t    /* Update upper bound on node decrease: second phase. */\n\t    gxtop = table->subtables[gybot].next;\n\t    for (z = gxtop + 1; z <= gybot; z++) {\n\t\tzindex = table->invperm[z];\n\t\tif (zindex == xindex || cuddTestInteract(table,xindex,zindex)) {\n\t\t    isolated = table->vars[zindex]->ref == 1;\n\t\t    R += (int) table->subtables[z].keys - isolated;\n\t\t}\n\t    }\n\t}\n\tx = gybot;\n\ty = cuddNextHigh(table,x);\n    }\n\n    return(moves);\n\nddSymmSiftingDownOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(MV_OOM);\n\n} /* end of ddSymmSiftingDown */\n\n\n/**\n  @brief Swaps two groups.\n\n  @details x is assumed to be the bottom variable of the first\n  group. y is assumed to be the top variable of the second group.\n  Updates the list of moves.\n\n  @return the number of keys in the table if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddSymmGroupMove(\n  DdManager * table,\n  int  x,\n  int  y,\n  Move ** moves)\n{\n    Move *move;\n    int\t size = 0;\n    int  i,j;\n    int  xtop,xbot,xsize,ytop,ybot,ysize,newxtop;\n    int  swapx = 0, swapy = 0;\n\n#ifdef DD_DEBUG\n    assert(x < y);\t/* we assume that x < y */\n#endif\n    /* Find top, bottom, and size for the two groups. */\n    xbot = x;\n    xtop = table->subtables[x].next;\n    xsize = xbot - xtop + 1;\n    ybot = y;\n    while ((unsigned) ybot < table->subtables[ybot].next)\n\tybot = table->subtables[ybot].next;\n    ytop = y;\n    ysize = ybot - ytop + 1;\n\n    /* Sift the variables of the second group up through the first group. */\n    for (i = 1; i <= ysize; i++) {\n\tfor (j = 1; j <= xsize; j++) {\n\t    size = cuddSwapInPlace(table,x,y);\n\t    if (size == 0) return(0);\n\t    swapx = x; swapy = y;\n\t    y = x;\n\t    x = y - 1;\n\t}\n\ty = ytop + i;\n\tx = y - 1;\n    }\n\n    /* fix symmetries */\n    y = xtop; /* ytop is now where xtop used to be */\n    for (i = 0; i < ysize-1 ; i++) {\n\ttable->subtables[y].next = y + 1;\n\ty = y + 1;\n    }\n    table->subtables[y].next = xtop; /* y is bottom of its group, join */\n\t\t\t\t     /* its symmetry to top of its group */\n    x = y + 1;\n    newxtop = x;\n    for (i = 0; i < xsize - 1 ; i++) {\n\ttable->subtables[x].next = x + 1;\n\tx = x + 1;\n    }\n    table->subtables[x].next = newxtop; /* x is bottom of its group, join */\n\t\t\t\t\t/* its symmetry to top of its group */\n    /* Store group move */\n    move = (Move *) cuddDynamicAllocNode(table);\n    if (move == NULL) return(0);\n    move->x = swapx;\n    move->y = swapy;\n    move->size = size;\n    move->next = *moves;\n    *moves = move;\n\n    return(size);\n\n} /* end of ddSymmGroupMove */\n\n\n/**\n  @brief Undoes the swap of two groups.\n\n  @details x is assumed to be the bottom variable of the first\n  group. y is assumed to be the top variable of the second group.\n\n  @return the number of keys in the table if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddSymmGroupMoveBackward(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n  int\tsize = (int) (table->keys - table->isolated);\n    int i,j;\n    int\txtop,xbot,xsize,ytop,ybot,ysize,newxtop;\n\n#ifdef DD_DEBUG\n    assert(x < y); /* We assume that x < y */\n#endif\n\n    /* Find top, bottom, and size for the two groups. */\n    xbot = x;\n    xtop = table->subtables[x].next;\n    xsize = xbot - xtop + 1;\n    ybot = y;\n    while ((unsigned) ybot < table->subtables[ybot].next)\n\tybot = table->subtables[ybot].next;\n    ytop = y;\n    ysize = ybot - ytop + 1;\n#ifdef DD_DEBUG\n    assert(xsize > 0);\n    assert(ysize > 0);\n#endif\n\n    /* Sift the variables of the second group up through the first group. */\n    for (i = 1; i <= ysize; i++) {\n\tfor (j = 1; j <= xsize; j++) {\n\t    size = cuddSwapInPlace(table,x,y);\n\t    if (size == 0) return(0);\n\t    y = x;\n\t    x = cuddNextLow(table,y);\n\t}\n\ty = ytop + i;\n\tx = y - 1;\n    }\n\n    /* Fix symmetries. */\n    y = xtop;\n    for (i = 0; i < ysize-1 ; i++) {\n\ttable->subtables[y].next = y + 1;\n\ty = y + 1;\n    }\n    table->subtables[y].next = xtop; /* y is bottom of its group, join */\n\t\t\t\t     /* its symmetry to top of its group */\n    x = y + 1;\n    newxtop = x;\n    for (i = 0; i < xsize-1 ; i++) {\n\ttable->subtables[x].next = x + 1;\n\tx = x + 1;\n    }\n    table->subtables[x].next = newxtop; /* x is bottom of its group, join */\n\t\t\t\t\t/* its symmetry to top of its group */\n\n    return(size);\n\n} /* end of ddSymmGroupMoveBackward */\n\n\n/**\n  @brief Given a set of moves, returns the %DD heap to the position\n  giving the minimum size.\n\n  @details In case of ties, returns to the closest position giving the\n  minimum size.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddSymmSiftingBackward(\n  DdManager * table,\n  Move * moves,\n  int  size)\n{\n    Move *move;\n    int  res;\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size < size) {\n\t    size = move->size;\n\t}\n    }\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size == size) return(1);\n\tif (table->subtables[move->x].next == move->x && table->subtables[move->y].next == move->y) {\n\t    res = cuddSwapInPlace(table,(int)move->x,(int)move->y);\n#ifdef DD_DEBUG\n\t    assert(table->subtables[move->x].next == move->x);\n\t    assert(table->subtables[move->y].next == move->y);\n#endif\n\t} else { /* Group move necessary */\n\t    res = ddSymmGroupMoveBackward(table,(int)move->x,(int)move->y);\n\t}\n\tif (!res) return(0);\n    }\n\n    return(1);\n\n} /* end of ddSymmSiftingBackward */\n\n\n/**\n  @brief Counts numbers of symmetric variables and symmetry groups.\n\n  @sideeffect None\n\n*/\nstatic void\nddSymmSummary(\n  DdManager * table,\n  int  lower,\n  int  upper,\n  int * symvars,\n  int * symgroups)\n{\n    int i,x,gbot;\n    int TotalSymm = 0;\n    int TotalSymmGroups = 0;\n\n    for (i = lower; i <= upper; i++) {\n\tif (table->subtables[i].next != (unsigned) i) {\n\t    TotalSymmGroups++;\n\t    x = i;\n\t    do {\n\t\tTotalSymm++;\n\t\tgbot = x;\n\t\tx = table->subtables[x].next;\n\t    } while (x != i);\n#ifdef DD_DEBUG\n\t    assert(table->subtables[gbot].next == (unsigned) i);\n#endif\n\t    i = gbot;\n\t}\n    }\n    *symvars = TotalSymm;\n    *symgroups = TotalSymmGroups;\n\n    return;\n\n} /* end of ddSymmSummary */\n"
  },
  {
    "path": "cudd/cudd/cuddTable.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Unique table management functions.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n/* Constants for red/black trees. */\n#define DD_STACK_SIZE 128\n#define DD_RED   0\n#define DD_BLACK 1\n#define DD_PAGE_SIZE 8192\n#define DD_PAGE_MASK ~(DD_PAGE_SIZE - 1)\n#endif\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief This is a hack for when CUDD_VALUE_TYPE is double\n */\ntypedef union hack {\n    CUDD_VALUE_TYPE value;\n    unsigned int bits[2];\n} hack;\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n/* Macros for red/black trees. */\n#define DD_INSERT_COMPARE(x,y) \\\n\t(((ptruint) (x) & DD_PAGE_MASK) - ((ptruint) (y) & DD_PAGE_MASK))\n#define DD_COLOR(p)  ((p)->index)\n#define DD_IS_BLACK(p) ((p)->index == DD_BLACK)\n#define DD_IS_RED(p) ((p)->index == DD_RED)\n#define DD_LEFT(p) cuddT(p)\n#define DD_RIGHT(p) cuddE(p)\n#define DD_NEXT(p) ((p)->next)\n#endif\n#endif\n\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void ddRehashZdd (DdManager *unique, int i);\nstatic int ddResizeTable (DdManager *unique, int index, int amount);\nstatic int cuddFindParent (DdManager *table, DdNode *node);\nstatic void ddFixLimits (DdManager *unique);\n#ifdef DD_RED_BLACK_FREE_LIST\nstatic void cuddOrderedInsert (DdNodePtr *root, DdNodePtr node);\nstatic DdNode * cuddOrderedThread (DdNode *root, DdNode *list);\nstatic void cuddRotateLeft (DdNodePtr *nodeP);\nstatic void cuddRotateRight (DdNodePtr *nodeP);\nstatic void cuddDoRebalance (DdNodePtr **stack, int stackN);\n#endif\nstatic void ddPatchTree (DdManager *dd, MtrNode *treenode);\n#ifdef DD_DEBUG\nstatic int cuddCheckCollisionOrdering (DdManager *unique, int i, int j);\n#endif\nstatic void ddReportRefMess (DdManager *unique, int i, const char *caller);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Returns the next prime &ge; p.\n\n  @sideeffect None\n\n*/\nunsigned int\nCudd_Prime(\n  unsigned int  p)\n{\n    unsigned int i, pn;\n\n    p--;\n    do {\n\tp++;\n\tif (p&1) {\n\t    pn = 1;\n\t    i = 3;\n\t    while ((unsigned) (i * i) <= p) {\n\t\tif (p % i == 0) {\n\t\t    pn = 0;\n\t\t    break;\n\t\t}\n\t\ti += 2;\n\t    }\n\t} else {\n\t    pn = 0;\n\t}\n    } while (!pn);\n    return(p);\n\n} /* end of Cudd_Prime */\n\n\n/**\n  @brief Expand manager without creating variables.\n\n  @details Expand a manager by a specified number of subtables without\n  actually creating new variables.  This function can be used to reduce the\n  frequency of resizing when an estimate of the number of variables is\n  available.  One would call this function instead of passing the number\n  of variables to Cudd_Init if variables should not be created right away\n  of if the estimate on their number became available only after the manager\n  has been created.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Init\n\n*/\nint\nCudd_Reserve(\n  DdManager *manager,\n  int amount)\n{\n    int currentSize = manager->size;\n    if (amount < 0)\n        return(0);\n    if (currentSize + amount < currentSize) /* overflow */\n        return(0);\n    if (amount <= manager->maxSize - manager->size)\n        return(1);\n    return ddResizeTable(manager, -1, amount);\n\n} /* end of Cudd_Reserve */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Fast storage allocation for DdNodes in the table.\n\n  @details The first 4 bytes of a chunk contain a pointer to the next\n  block; the rest contains DD_MEM_CHUNK spaces for DdNodes.\n\n  @return a pointer to a new node if successful; NULL is memory is\n  full.\n\n  @sideeffect None\n\n  @see cuddDynamicAllocNode\n\n*/\nDdNode *\ncuddAllocNode(\n  DdManager * unique)\n{\n    int i;\n    DdNodePtr *mem;\n    DdNode *list, *node;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    if (unique->nextFree == NULL) {\t/* free list is empty */\n\t/* Check for exceeded limits. */\n        if (unique->terminationCallback != NULL &&\n            unique->terminationCallback(unique->tcbArg)) {\n            unique->errorCode = CUDD_TERMINATION;\n            return(NULL);\n        }\n        if (util_cpu_time() - unique->startTime > unique->timeLimit) {\n            unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n            return(NULL);\n        }\n\tif ((unique->keys - unique->dead) + (unique->keysZ - unique->deadZ) >\n\t    unique->maxLive) {\n\t    unique->errorCode = CUDD_TOO_MANY_NODES;\n\t    return(NULL);\n\t}\n\tif (unique->stash == NULL || unique->memused > unique->maxmemhard) {\n\t    (void) cuddGarbageCollect(unique,1);\n\t    mem = NULL;\n\t}\n\tif (unique->nextFree == NULL) {\n\t    if (unique->memused > unique->maxmemhard) {\n\t\tunique->errorCode = CUDD_MAX_MEM_EXCEEDED;\n\t\treturn(NULL);\n\t    }\n\t    /* Try to allocate a new block. */\n\t    saveHandler = MMoutOfMemory;\n\t    MMoutOfMemory = unique->outOfMemCallback;\n\t    mem = (DdNodePtr *) ALLOC(DdNode,DD_MEM_CHUNK + 1);\n\t    MMoutOfMemory = saveHandler;\n\t    if (mem == NULL) {\n\t\t/* No more memory: Try collecting garbage. If this succeeds,\n\t\t** we end up with mem still NULL, but unique->nextFree !=\n\t\t** NULL. */\n\t\tif (cuddGarbageCollect(unique,1) == 0) {\n\t\t    /* Last resort: Free the memory stashed away, if there\n\t\t    ** any. If this succeeeds, mem != NULL and\n\t\t    ** unique->nextFree still NULL. */\n\t\t    if (unique->stash != NULL) {\n\t\t\tFREE(unique->stash);\n\t\t\tunique->stash = NULL;\n\t\t\t/* Inhibit resizing of tables. */\n\t\t\tcuddSlowTableGrowth(unique);\n\t\t\t/* Now try again. */\n\t\t\tmem = (DdNodePtr *) ALLOC(DdNode,DD_MEM_CHUNK + 1);\n\t\t    }\n\t\t    if (mem == NULL) {\n\t\t\t/* Out of luck. Call the default handler to do\n\t\t\t** whatever it specifies for a failed malloc.\n\t\t\t** If this handler returns, then set error code,\n\t\t\t** print warning, and return. */\n\t\t\t(*MMoutOfMemory)(sizeof(DdNode)*(DD_MEM_CHUNK + 1));\n\t\t\tunique->errorCode = CUDD_MEMORY_OUT;\n#ifdef DD_VERBOSE\n\t\t\t(void) fprintf(unique->err,\n\t\t\t\t       \"cuddAllocNode: out of memory\");\n\t\t\t(void) fprintf(unique->err, \"Memory in use = %lu\\n\",\n\t\t\t\t       unique->memused);\n#endif\n\t\t\treturn(NULL);\n\t\t    }\n\t\t}\n\t    }\n\t    if (mem != NULL) {\t/* successful allocation; slice memory */\n\t\tptruint offset;\n\t\tunique->memused += (DD_MEM_CHUNK + 1) * sizeof(DdNode);\n\t\tmem[0] = (DdNodePtr) unique->memoryList;\n\t\tunique->memoryList = mem;\n\n\t\t/* Here we rely on the fact that a DdNode is as large\n\t\t** as 4 pointers.  */\n\t\toffset = (ptruint) mem & (sizeof(DdNode) - 1);\n\t\tmem += (sizeof(DdNode) - offset) / sizeof(DdNodePtr);\n\t\tassert(((ptruint) mem & (sizeof(DdNode) - 1)) == 0);\n\t\tlist = (DdNode *) mem;\n\n\t\ti = 1;\n\t\tdo {\n\t\t    list[i - 1].ref = 0;\n\t\t    list[i - 1].next = &list[i];\n\t\t} while (++i < DD_MEM_CHUNK);\n\n\t\tlist[DD_MEM_CHUNK-1].ref = 0;\n\t\tlist[DD_MEM_CHUNK-1].next = NULL;\n\n\t\tunique->nextFree = &list[0];\n\t    }\n\t}\n    }\n    unique->allocated++;\n    node = unique->nextFree;\n    unique->nextFree = node->next;\n    return(node);\n\n} /* end of cuddAllocNode */\n\n\n/**\n  @brief Creates and initializes the unique table.\n\n  @return a pointer to the table if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Init cuddFreeTable\n\n*/\nDdManager *\ncuddInitTable(\n  unsigned int numVars  /**< Initial number of %BDD variables (and subtables) */,\n  unsigned int numVarsZ /**< Initial number of %ZDD variables (and subtables) */,\n  unsigned int numSlots /**< Initial size of the %BDD subtables */,\n  unsigned int looseUpTo /**< Limit for fast table growth */)\n{\n    DdManager\t*unique = ALLOC(DdManager,1);\n    int\t\ti, j;\n    DdNodePtr\t*nodelist;\n    DdNode\t*sentinel;\n    unsigned int slots;\n    int shift;\n\n    if (unique == NULL) {\n\treturn(NULL);\n    }\n    sentinel = &(unique->sentinel);\n    sentinel->ref = 0;\n    sentinel->index = 0;\n    cuddT(sentinel) = NULL;\n    cuddE(sentinel) = NULL;\n    sentinel->next = NULL;\n    unique->epsilon = DD_EPSILON;\n    unique->size = numVars;\n    unique->sizeZ = numVarsZ;\n    unique->maxSize = ddMax(DD_DEFAULT_RESIZE, numVars);\n    unique->maxSizeZ = ddMax(DD_DEFAULT_RESIZE, numVarsZ);\n\n    /* Adjust the requested number of slots to a power of 2. */\n    slots = 8;\n    while (slots < numSlots) {\n\tslots <<= 1;\n    }\n    unique->initSlots = slots;\n    shift = sizeof(int) * 8 - cuddComputeFloorLog2(slots);\n\n    unique->slots = (numVars + numVarsZ + 1) * slots;\n    unique->keys = 0;\n    unique->maxLive = ~0;\t/* very large number */\n    unique->keysZ = 0;\n    unique->dead = 0;\n    unique->deadZ = 0;\n    unique->gcFrac = DD_GC_FRAC_HI;\n    unique->minDead = (unsigned) (DD_GC_FRAC_HI * (double) unique->slots);\n    unique->looseUpTo = looseUpTo;\n    unique->gcEnabled = 1;\n    unique->allocated = 0;\n    unique->reclaimed = 0;\n    unique->subtables = ALLOC(DdSubtable,unique->maxSize);\n    if (unique->subtables == NULL) {\n\tFREE(unique);\n\treturn(NULL);\n    }\n    unique->subtableZ = ALLOC(DdSubtable,unique->maxSizeZ);\n    if (unique->subtableZ == NULL) {\n\tFREE(unique->subtables);\n\tFREE(unique);\n\treturn(NULL);\n    }\n    unique->perm = ALLOC(int,unique->maxSize);\n    if (unique->perm == NULL) {\n\tFREE(unique->subtables);\n\tFREE(unique->subtableZ);\n\tFREE(unique);\n\treturn(NULL);\n    }\n    unique->invperm = ALLOC(int,unique->maxSize);\n    if (unique->invperm == NULL) {\n\tFREE(unique->subtables);\n\tFREE(unique->subtableZ);\n\tFREE(unique->perm);\n\tFREE(unique);\n\treturn(NULL);\n    }\n    unique->permZ = ALLOC(int,unique->maxSizeZ);\n    if (unique->permZ == NULL) {\n\tFREE(unique->subtables);\n\tFREE(unique->subtableZ);\n\tFREE(unique->perm);\n\tFREE(unique->invperm);\n\tFREE(unique);\n\treturn(NULL);\n    }\n    unique->invpermZ = ALLOC(int,unique->maxSizeZ);\n    if (unique->invpermZ == NULL) {\n\tFREE(unique->subtables);\n\tFREE(unique->subtableZ);\n\tFREE(unique->perm);\n\tFREE(unique->invperm);\n\tFREE(unique->permZ);\n\tFREE(unique);\n\treturn(NULL);\n    }\n    unique->map = NULL;\n    unique->stack = ALLOC(DdNodePtr,ddMax(unique->maxSize,unique->maxSizeZ)+1);\n    if (unique->stack == NULL) {\n\tFREE(unique->subtables);\n\tFREE(unique->subtableZ);\n\tFREE(unique->perm);\n\tFREE(unique->invperm);\n\tFREE(unique->permZ);\n\tFREE(unique->invpermZ);\n\tFREE(unique);\n\treturn(NULL);\n    }\n    unique->stack[0] = NULL; /* to suppress harmless UMR */\n\n#ifndef DD_NO_DEATH_ROW\n    unique->deathRowDepth = 1U << cuddComputeFloorLog2(unique->looseUpTo >> 2);\n    unique->deathRow = ALLOC(DdNodePtr,unique->deathRowDepth);\n    if (unique->deathRow == NULL) {\n\tFREE(unique->subtables);\n\tFREE(unique->subtableZ);\n\tFREE(unique->perm);\n\tFREE(unique->invperm);\n\tFREE(unique->permZ);\n\tFREE(unique->invpermZ);\n\tFREE(unique->stack);\n\tFREE(unique);\n\treturn(NULL);\n    }\n    for (i = 0; i < unique->deathRowDepth; i++) {\n\tunique->deathRow[i] = NULL;\n    }\n    unique->nextDead = 0;\n    unique->deadMask = unique->deathRowDepth - 1;\n#endif\n\n    for (i = 0; (unsigned) i < numVars; i++) {\n\tunique->subtables[i].slots = slots;\n\tunique->subtables[i].shift = shift;\n\tunique->subtables[i].keys = 0;\n\tunique->subtables[i].dead = 0;\n        unique->subtables[i].next = i;\n\tunique->subtables[i].maxKeys = slots * DD_MAX_SUBTABLE_DENSITY;\n\tunique->subtables[i].bindVar = 0;\n\tunique->subtables[i].varType = CUDD_VAR_PRIMARY_INPUT;\n\tunique->subtables[i].pairIndex = 0;\n\tunique->subtables[i].varHandled = 0;\n\tunique->subtables[i].varToBeGrouped = CUDD_LAZY_NONE;\n\n\tnodelist = unique->subtables[i].nodelist = ALLOC(DdNodePtr,slots);\n\tif (nodelist == NULL) {\n\t    for (j = 0; j < i; j++) {\n\t\tFREE(unique->subtables[j].nodelist);\n\t    }\n\t    FREE(unique->subtables);\n\t    FREE(unique->subtableZ);\n\t    FREE(unique->perm);\n\t    FREE(unique->invperm);\n\t    FREE(unique->permZ);\n\t    FREE(unique->invpermZ);\n\t    FREE(unique->stack);\n\t    FREE(unique);\n\t    return(NULL);\n\t}\n\tfor (j = 0; (unsigned) j < slots; j++) {\n\t    nodelist[j] = sentinel;\n\t}\n\tunique->perm[i] = i;\n\tunique->invperm[i] = i;\n    }\n    for (i = 0; (unsigned) i < numVarsZ; i++) {\n\tunique->subtableZ[i].slots = slots;\n\tunique->subtableZ[i].shift = shift;\n\tunique->subtableZ[i].keys = 0;\n\tunique->subtableZ[i].dead = 0;\n        unique->subtableZ[i].next = i;\n\tunique->subtableZ[i].maxKeys = slots * DD_MAX_SUBTABLE_DENSITY;\n\tnodelist = unique->subtableZ[i].nodelist = ALLOC(DdNodePtr,slots);\n\tif (nodelist == NULL) {\n\t    for (j = 0; (unsigned) j < numVars; j++) {\n\t\tFREE(unique->subtables[j].nodelist);\n\t    }\n\t    FREE(unique->subtables);\n\t    for (j = 0; j < i; j++) {\n\t\tFREE(unique->subtableZ[j].nodelist);\n\t    }\n\t    FREE(unique->subtableZ);\n\t    FREE(unique->perm);\n\t    FREE(unique->invperm);\n\t    FREE(unique->permZ);\n\t    FREE(unique->invpermZ);\n\t    FREE(unique->stack);\n\t    FREE(unique);\n\t    return(NULL);\n\t}\n\tfor (j = 0; (unsigned) j < slots; j++) {\n\t    nodelist[j] = NULL;\n\t}\n\tunique->permZ[i] = i;\n\tunique->invpermZ[i] = i;\n    }\n    unique->constants.slots = slots;\n    unique->constants.shift = shift;\n    unique->constants.keys = 0;\n    unique->constants.dead = 0;\n    unique->constants.next = 0;\n    unique->constants.bindVar = 0;\n    unique->constants.varType = CUDD_VAR_PRIMARY_INPUT;\n    unique->constants.pairIndex = 0;\n    unique->constants.varHandled = 0;\n    unique->constants.varToBeGrouped = CUDD_LAZY_NONE;\n    unique->constants.maxKeys = slots * DD_MAX_SUBTABLE_DENSITY;\n    nodelist = unique->constants.nodelist = ALLOC(DdNodePtr,slots);\n    if (nodelist == NULL) {\n\tfor (j = 0; (unsigned) j < numVars; j++) {\n\t    FREE(unique->subtables[j].nodelist);\n\t}\n\tFREE(unique->subtables);\n\tfor (j = 0; (unsigned) j < numVarsZ; j++) {\n\t    FREE(unique->subtableZ[j].nodelist);\n\t}\n\tFREE(unique->subtableZ);\n\tFREE(unique->perm);\n\tFREE(unique->invperm);\n\tFREE(unique->permZ);\n\tFREE(unique->invpermZ);\n\tFREE(unique->stack);\n\tFREE(unique);\n\treturn(NULL);\n    }\n    for (j = 0; (unsigned) j < slots; j++) {\n\tnodelist[j] = NULL;\n    }\n\n    unique->memoryList = NULL;\n    unique->nextFree = NULL;\n\n    unique->memused = sizeof(DdManager) + (unique->maxSize + unique->maxSizeZ)\n\t* (sizeof(DdSubtable) + 2 * sizeof(int)) + (numVars + 1) *\n\tslots * sizeof(DdNodePtr) +\n\t(ddMax(unique->maxSize,unique->maxSizeZ) + 1) * sizeof(DdNodePtr);\n#ifndef DD_NO_DEATH_ROW\n    unique->memused += unique->deathRowDepth * sizeof(DdNodePtr);\n#endif\n\n    /* Initialize fields concerned with automatic dynamic reordering. */\n    unique->reordered = 0;\n    unique->reorderings = 0;\n    unique->maxReorderings = ~0;\n    unique->siftMaxVar = DD_SIFT_MAX_VAR;\n    unique->siftMaxSwap = DD_SIFT_MAX_SWAPS;\n    unique->maxGrowth = DD_MAX_REORDER_GROWTH;\n    unique->maxGrowthAlt = 2.0 * DD_MAX_REORDER_GROWTH;\n    unique->reordCycle = 0;\t/* do not use alternate threshold */\n    unique->autoDyn = 0;\t/* initially disabled */\n    unique->autoDynZ = 0;\t/* initially disabled */\n    unique->autoMethod = CUDD_REORDER_SIFT;\n    unique->autoMethodZ = CUDD_REORDER_SIFT;\n    unique->realign = 0;\t/* initially disabled */\n    unique->realignZ = 0;\t/* initially disabled */\n    unique->nextDyn = DD_FIRST_REORDER;\n    unique->countDead = ~0;\n    unique->tree = NULL;\n    unique->treeZ = NULL;\n    unique->groupcheck = CUDD_GROUP_CHECK7;\n    unique->recomb = DD_DEFAULT_RECOMB;\n    unique->symmviolation = 0;\n    unique->arcviolation = 0;\n    unique->populationSize = 0;\n    unique->numberXovers = 0;\n    unique->randomizeOrder = 0;\n    unique->linear = NULL;\n    unique->originalSize = 0;\n    unique->linearSize = 0;\n\n    /* Initialize ZDD universe. */\n    unique->univ = (DdNodePtr *)NULL;\n\n    /* Initialize auxiliary fields. */\n    unique->localCaches = NULL;\n    unique->preGCHook = NULL;\n    unique->postGCHook = NULL;\n    unique->preReorderingHook = NULL;\n    unique->postReorderingHook = NULL;\n    unique->out = stdout;\n    unique->err = stderr;\n    unique->errorCode = CUDD_NO_ERROR;\n    unique->startTime = util_cpu_time();\n    unique->timeLimit = ~0UL;\n    unique->terminationCallback = NULL;\n    unique->tcbArg = NULL;\n    unique->outOfMemCallback = Cudd_OutOfMem;\n    unique->timeoutHandler = NULL;\n\n    /* Initialize statistical counters. */\n    unique->maxmemhard = ~ (size_t) 0;\n    unique->garbageCollections = 0;\n    unique->GCTime = 0;\n    unique->reordTime = 0;\n    unique->peakLiveNodes = 0;\n    unique->cuddRand = 0;\n#ifdef DD_STATS\n    unique->nodesDropped = 0;\n    unique->nodesFreed = 0;\n#endif\n#ifdef DD_UNIQUE_PROFILE\n    unique->uniqueLookUps = 0;\n    unique->uniqueLinks = 0;\n#endif\n#ifdef DD_COUNT\n    unique->recursiveCalls = 0;\n    unique->swapSteps = 0;\n#ifdef DD_STATS\n    unique->nextSample = 250000;\n#endif\n#endif\n#ifdef DD_DEBUG\n    unique->enableExtraDebug = 0;\n#endif\n\n    return(unique);\n\n} /* end of cuddInitTable */\n\n\n/**\n  @brief Frees the resources associated to a unique table.\n\n  @sideeffect None\n\n  @see cuddInitTable\n\n*/\nvoid\ncuddFreeTable(\n  DdManager * unique)\n{\n    DdNodePtr *next;\n    DdNodePtr *memlist = unique->memoryList;\n    int i;\n\n    if (unique->stash != NULL) FREE(unique->stash);\n    if (unique->univ != NULL) cuddZddFreeUniv(unique);\n    while (memlist != NULL) {\n\tnext = (DdNodePtr *) memlist[0];\t/* link to next block */\n\tFREE(memlist);\n\tmemlist = next;\n    }\n    unique->nextFree = NULL;\n    unique->memoryList = NULL;\n\n    for (i = 0; i < unique->size; i++) {\n\tFREE(unique->subtables[i].nodelist);\n    }\n    for (i = 0; i < unique->sizeZ; i++) {\n\tFREE(unique->subtableZ[i].nodelist);\n    }\n    FREE(unique->constants.nodelist);\n    FREE(unique->subtables);\n    FREE(unique->subtableZ);\n    FREE(unique->acache);\n    FREE(unique->perm);\n    FREE(unique->permZ);\n    FREE(unique->invperm);\n    FREE(unique->invpermZ);\n    FREE(unique->vars);\n    if (unique->map != NULL) FREE(unique->map);\n    FREE(unique->stack);\n#ifndef DD_NO_DEATH_ROW\n    FREE(unique->deathRow);\n#endif\n    if (unique->tree != NULL) Mtr_FreeTree(unique->tree);\n    if (unique->treeZ != NULL) Mtr_FreeTree(unique->treeZ);\n    if (unique->linear != NULL) FREE(unique->linear);\n    while (unique->preGCHook != NULL)\n\tCudd_RemoveHook(unique,unique->preGCHook->f,CUDD_PRE_GC_HOOK);\n    while (unique->postGCHook != NULL)\n\tCudd_RemoveHook(unique,unique->postGCHook->f,CUDD_POST_GC_HOOK);\n    while (unique->preReorderingHook != NULL)\n\tCudd_RemoveHook(unique,unique->preReorderingHook->f,\n\t\t\tCUDD_PRE_REORDERING_HOOK);\n    while (unique->postReorderingHook != NULL)\n\tCudd_RemoveHook(unique,unique->postReorderingHook->f,\n\t\t\tCUDD_POST_REORDERING_HOOK);\n    FREE(unique);\n\n} /* end of cuddFreeTable */\n\n\n/**\n  @brief Performs garbage collection on the %BDD and %ZDD unique tables.\n\n  @details If clearCache is 0, the cache is not cleared. This should\n  only be specified if the cache has been cleared right before calling\n  cuddGarbageCollect. (As in the case of dynamic reordering.)\n\n  @return the total number of deleted nodes.\n\n  @sideeffect None\n\n*/\nint\ncuddGarbageCollect(\n  DdManager * unique,\n  int clearCache)\n{\n    DdHook\t*hook;\n    DdCache\t*cache = unique->cache;\n    DdNode\t*sentinel = &(unique->sentinel);\n    DdNodePtr\t*nodelist;\n    int\t\ti, j, deleted, totalDeleted, totalDeletedZ;\n    DdCache\t*c;\n    DdNode\t*node,*next;\n    DdNodePtr\t*lastP;\n    int\t\tslots;\n    unsigned long localTime;\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n    DdNodePtr\ttree;\n#else\n    DdNodePtr *memListTrav, *nxtNode;\n    DdNode *downTrav, *sentry;\n    int k;\n#endif\n#endif\n\n    if (util_cpu_time() - unique->startTime > unique->timeLimit) {\n        unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n        return(0);\n    }\n\n#ifndef DD_NO_DEATH_ROW\n    cuddClearDeathRow(unique);\n#endif\n\n    hook = unique->preGCHook;\n    while (hook != NULL) {\n\tint res = (hook->f)(unique,\"DD\",NULL);\n\tif (res == 0) return(0);\n\thook = hook->next;\n    }\n\n    if (unique->dead + unique->deadZ == 0) {\n\thook = unique->postGCHook;\n\twhile (hook != NULL) {\n\t    int res = (hook->f)(unique,\"DD\",NULL);\n\t    if (res == 0) return(0);\n\t    hook = hook->next;\n\t}\n\treturn(0);\n    }\n\n    /* If many nodes are being reclaimed, we want to resize the tables\n    ** more aggressively, to reduce the frequency of garbage collection.\n    */\n    if (clearCache && unique->gcFrac == DD_GC_FRAC_LO &&\n\tunique->slots <= unique->looseUpTo && unique->stash != NULL) {\n\tunique->minDead = (unsigned) (DD_GC_FRAC_HI * (double) unique->slots);\n#ifdef DD_VERBOSE\n\t(void) fprintf(unique->err,\"GC fraction = %.2f\\t\", DD_GC_FRAC_HI);\n\t(void) fprintf(unique->err,\"minDead = %d\\n\", unique->minDead);\n#endif\n\tunique->gcFrac = DD_GC_FRAC_HI;\n\treturn(0);\n    }\n\n    localTime = util_cpu_time();\n\n    unique->garbageCollections++;\n#ifdef DD_VERBOSE\n    (void) fprintf(unique->err,\n\t\t   \"garbage collecting (%d dead BDD nodes out of %d, min %d)...\",\n\t\t   unique->dead, unique->keys, unique->minDead);\n    (void) fprintf(unique->err,\n\t\t   \"                   (%d dead ZDD nodes out of %d)...\",\n\t\t   unique->deadZ, unique->keysZ);\n#endif\n\n    /* Remove references to garbage collected nodes from the cache. */\n    if (clearCache) {\n\tslots = unique->cacheSlots;\n\tfor (i = 0; i < slots; i++) {\n\t    c = &cache[i];\n\t    if (c->data != NULL) {\n\t\tif (cuddClean(c->f)->ref == 0 ||\n\t\tcuddClean(c->g)->ref == 0 ||\n\t\t(((ptruint)c->f & 0x2) && Cudd_Regular(c->h)->ref == 0) ||\n\t\t(c->data != DD_NON_CONSTANT &&\n\t\tCudd_Regular(c->data)->ref == 0)) {\n\t\t    c->data = NULL;\n\t\t    unique->cachedeletions++;\n\t\t}\n\t    }\n\t}\n\tcuddLocalCacheClearDead(unique);\n    }\n\n    /* Now return dead nodes to free list. Count them for sanity check. */\n    totalDeleted = 0;\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n    tree = NULL;\n#endif\n#endif\n\n    for (i = 0; i < unique->size; i++) {\n\tif (unique->subtables[i].dead == 0) continue;\n\tnodelist = unique->subtables[i].nodelist;\n\n\tdeleted = 0;\n\tslots = unique->subtables[i].slots;\n\tfor (j = 0; j < slots; j++) {\n\t    lastP = &(nodelist[j]);\n\t    node = *lastP;\n\t    while (node != sentinel) {\n\t\tnext = node->next;\n\t\tif (node->ref == 0) {\n\t\t    deleted++;\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n\t\t    cuddOrderedInsert(&tree,node);\n#endif\n#else\n\t\t    cuddDeallocNode(unique,node);\n#endif\n\t\t} else {\n\t\t    *lastP = node;\n\t\t    lastP = &(node->next);\n\t\t}\n\t\tnode = next;\n\t    }\n\t    *lastP = sentinel;\n\t}\n\tif ((unsigned) deleted != unique->subtables[i].dead) {\n\t    ddReportRefMess(unique, i, \"cuddGarbageCollect\");\n\t}\n\ttotalDeleted += deleted;\n\tunique->subtables[i].keys -= deleted;\n\tunique->subtables[i].dead = 0;\n    }\n    if (unique->constants.dead != 0) {\n\tnodelist = unique->constants.nodelist;\n\tdeleted = 0;\n\tslots = unique->constants.slots;\n\tfor (j = 0; j < slots; j++) {\n\t    lastP = &(nodelist[j]);\n\t    node = *lastP;\n\t    while (node != NULL) {\n\t\tnext = node->next;\n\t\tif (node->ref == 0) {\n\t\t    deleted++;\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n\t\t    cuddOrderedInsert(&tree,node);\n#endif\n#else\n\t\t    cuddDeallocNode(unique,node);\n#endif\n\t\t} else {\n\t\t    *lastP = node;\n\t\t    lastP = &(node->next);\n\t\t}\n\t\tnode = next;\n\t    }\n\t    *lastP = NULL;\n\t}\n\tif ((unsigned) deleted != unique->constants.dead) {\n\t    ddReportRefMess(unique, CUDD_CONST_INDEX, \"cuddGarbageCollect\");\n\t}\n\ttotalDeleted += deleted;\n\tunique->constants.keys -= deleted;\n\tunique->constants.dead = 0;\n    }\n    if ((unsigned) totalDeleted != unique->dead) {\n\tddReportRefMess(unique, -1, \"cuddGarbageCollect\");\n    }\n    unique->keys -= totalDeleted;\n    unique->dead = 0;\n#ifdef DD_STATS\n    unique->nodesFreed += (double) totalDeleted;\n#endif\n\n    totalDeletedZ = 0;\n\n    for (i = 0; i < unique->sizeZ; i++) {\n\tif (unique->subtableZ[i].dead == 0) continue;\n\tnodelist = unique->subtableZ[i].nodelist;\n\n\tdeleted = 0;\n\tslots = unique->subtableZ[i].slots;\n\tfor (j = 0; j < slots; j++) {\n\t    lastP = &(nodelist[j]);\n\t    node = *lastP;\n\t    while (node != NULL) {\n\t\tnext = node->next;\n\t\tif (node->ref == 0) {\n\t\t    deleted++;\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n\t\t    cuddOrderedInsert(&tree,node);\n#endif\n#else\n\t\t    cuddDeallocNode(unique,node);\n#endif\n\t\t} else {\n\t\t    *lastP = node;\n\t\t    lastP = &(node->next);\n\t\t}\n\t\tnode = next;\n\t    }\n\t    *lastP = NULL;\n\t}\n\tif ((unsigned) deleted != unique->subtableZ[i].dead) {\n\t    ddReportRefMess(unique, i, \"cuddGarbageCollect\");\n\t}\n\ttotalDeletedZ += deleted;\n\tunique->subtableZ[i].keys -= deleted;\n\tunique->subtableZ[i].dead = 0;\n    }\n\n    /* No need to examine the constant table for ZDDs.\n    ** If we did we should be careful not to count whatever dead\n    ** nodes we found there among the dead ZDD nodes. */\n    if ((unsigned) totalDeletedZ != unique->deadZ) {\n\tddReportRefMess(unique, -1, \"cuddGarbageCollect\");\n    }\n    unique->keysZ -= totalDeletedZ;\n    unique->deadZ = 0;\n#ifdef DD_STATS\n    unique->nodesFreed += (double) totalDeletedZ;\n#endif\n\n\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n    unique->nextFree = cuddOrderedThread(tree,unique->nextFree);\n#else\n    memListTrav = unique->memoryList;\n    sentry = NULL;\n    while (memListTrav != NULL) {\n\tptruint offset;\n\tnxtNode = (DdNodePtr *)memListTrav[0];\n\toffset = (ptruint) memListTrav & (sizeof(DdNode) - 1);\n\tmemListTrav += (sizeof(DdNode) - offset) / sizeof(DdNodePtr);\n\tdownTrav = (DdNode *)memListTrav;\n\tk = 0;\n\tdo {\n\t    if (downTrav[k].ref == 0) {\n\t\tif (sentry == NULL) {\n\t\t    unique->nextFree = sentry = &downTrav[k];\n\t\t} else {\n\t\t    /* First hook sentry->next to the dead node and then\n\t\t    ** reassign sentry to the dead node. */\n\t\t    sentry = (sentry->next = &downTrav[k]);\n\t\t}\n\t    }\n\t} while (++k < DD_MEM_CHUNK);\n\tmemListTrav = nxtNode;\n    }\n    sentry->next = NULL;\n#endif\n#endif\n\n    unique->GCTime += util_cpu_time() - localTime;\n\n    hook = unique->postGCHook;\n    while (hook != NULL) {\n\tint res = (hook->f)(unique,\"DD\",NULL);\n\tif (res == 0) return(0);\n\thook = hook->next;\n    }\n\n#ifdef DD_VERBOSE\n    (void) fprintf(unique->err,\" done\\n\");\n#endif\n\n    return(totalDeleted+totalDeletedZ);\n\n} /* end of cuddGarbageCollect */\n\n\n/**\n  @brief Wrapper for cuddUniqueInterZdd.\n\n  @details It applies the %ZDD reduction rule.\n\n  @return a pointer to the result node under normal conditions; NULL\n  if reordering occurred or memory was exhausted.\n\n  @sideeffect None\n\n  @see cuddUniqueInterZdd\n\n*/\nDdNode *\ncuddZddGetNode(\n  DdManager * zdd,\n  int  id,\n  DdNode * T,\n  DdNode * E)\n{\n    DdNode\t*node;\n\n    if (T == DD_ZERO(zdd))\n\treturn(E);\n    node = cuddUniqueInterZdd(zdd, id, T, E);\n    return(node);\n\n} /* end of cuddZddGetNode */\n\n\n/**\n  @brief Wrapper for cuddUniqueInterZdd that is independent of variable\n  ordering.\n\n  @details Wrapper for cuddUniqueInterZdd that is independent of\n  variable ordering (IVO). This function does not require parameter\n  index to precede the indices of the top nodes of g and h in the\n  variable order.\n\n  @return a pointer to the result node under normal conditions; NULL\n  if reordering occurred or memory was exhausted.\n\n  @sideeffect None\n\n  @see cuddZddGetNode cuddZddIsop\n\n*/\nDdNode *\ncuddZddGetNodeIVO(\n  DdManager * dd,\n  int  index,\n  DdNode * g,\n  DdNode * h)\n{\n    DdNode\t*f, *r, *t;\n    DdNode\t*zdd_one = DD_ONE(dd);\n    DdNode\t*zdd_zero = DD_ZERO(dd);\n\n    f = cuddUniqueInterZdd(dd, index, zdd_one, zdd_zero);\n    if (f == NULL) {\n\treturn(NULL);\n    }\n    cuddRef(f);\n    t = cuddZddProduct(dd, f, g);\n    if (t == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f);\n\treturn(NULL);\n    }\n    cuddRef(t);\n    Cudd_RecursiveDerefZdd(dd, f);\n    r = cuddZddUnion(dd, t, h);\n    if (r == NULL) {\n\tCudd_RecursiveDerefZdd(dd, t);\n\treturn(NULL);\n    }\n    cuddRef(r);\n    Cudd_RecursiveDerefZdd(dd, t);\n\n    cuddDeref(r);\n    return(r);\n\n} /* end of cuddZddGetNodeIVO */\n\n\n/**\n  @brief Checks the unique table for the existence of an internal node.\n\n  @details If it does not exist, it creates a new one.  Does not\n  modify the reference count of whatever is returned.  A newly created\n  internal node comes back with a reference count 0.  For a newly\n  created node, increments the reference counts of what T and E point\n  to.\n\n  @return a pointer to the new node if successful; NULL if memory is\n  exhausted, if a termination request was detected, if a timeout expired,\n  or if reordering took place.\n\n  @sideeffect None\n\n  @see cuddUniqueInterZdd\n\n*/\nDdNode *\ncuddUniqueInter(\n  DdManager * unique,\n  int  index,\n  DdNode * T,\n  DdNode * E)\n{\n    int pos;\n    unsigned int level;\n    int retval;\n    DdNodePtr *nodelist;\n    DdNode *looking;\n    DdNodePtr *previousP;\n    DdSubtable *subtable;\n    int gcNumber;\n\n#ifdef DD_UNIQUE_PROFILE\n    unique->uniqueLookUps++;\n#endif\n\n    if (((int64_t) 0x1ffff & (int64_t) unique->cacheMisses) == 0) {\n        if (unique->terminationCallback != NULL &&\n            unique->terminationCallback(unique->tcbArg)) {\n            unique->errorCode = CUDD_TERMINATION;\n            return(NULL);\n        }\n        if (util_cpu_time() - unique->startTime > unique->timeLimit) {\n            unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n            return(NULL);\n        }\n    }\n    if (index >= unique->size) {\n        int amount = ddMax(DD_DEFAULT_RESIZE,unique->size/20);\n        if (!ddResizeTable(unique,index,amount)) return(NULL);\n    }\n\n    level = unique->perm[index];\n    subtable = &(unique->subtables[level]);\n\n#ifdef DD_DEBUG\n    assert(level < (unsigned) cuddI(unique,T->index));\n    assert(level < (unsigned) cuddI(unique,Cudd_Regular(E)->index));\n#endif\n\n    pos = ddHash(T, E, subtable->shift);\n    nodelist = subtable->nodelist;\n    previousP = &(nodelist[pos]);\n    looking = *previousP;\n\n    while (T < cuddT(looking)) {\n\tpreviousP = &(looking->next);\n\tlooking = *previousP;\n#ifdef DD_UNIQUE_PROFILE\n\tunique->uniqueLinks++;\n#endif\n    }\n    while (T == cuddT(looking) && E < cuddE(looking)) {\n\tpreviousP = &(looking->next);\n\tlooking = *previousP;\n#ifdef DD_UNIQUE_PROFILE\n\tunique->uniqueLinks++;\n#endif\n    }\n    if (T == cuddT(looking) && E == cuddE(looking)) {\n\tif (looking->ref == 0) {\n\t    cuddReclaim(unique,looking);\n\t}\n\treturn(looking);\n    }\n\n    /* countDead is 0 if deads should be counted and ~0 if they should not. */\n    if (unique->autoDyn &&\n        unique->keys - (unique->dead & unique->countDead) >= unique->nextDyn &&\n        unique->maxReorderings > 0) {\n        unsigned long cpuTime;\n#ifdef DD_DEBUG\n\tretval = Cudd_DebugCheck(unique);\n\tif (retval != 0) return(NULL);\n\tretval = Cudd_CheckKeys(unique);\n\tif (retval != 0) return(NULL);\n#endif\n\tretval = Cudd_ReduceHeap(unique,unique->autoMethod,10); /* 10 = whatever */\n        unique->maxReorderings--;\n\tif (retval == 0) {\n            unique->reordered = 2;\n        } else if (unique->terminationCallback != NULL &&\n            unique->terminationCallback(unique->tcbArg)) {\n            unique->errorCode = CUDD_TERMINATION;\n            unique->reordered = 0;\n        } else if ((cpuTime = util_cpu_time()) - unique->startTime >\n                   unique->timeLimit) {\n            unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n            unique->reordered = 0;\n        } else if (unique->timeLimit - (cpuTime - unique->startTime)\n                   < unique->reordTime) {\n            /* No risk of overflow because here unique->timeLimit is known\n             * to be greater than or equal to (cpuTime - unique->startTime).\n             * If the remaining time is less than the time spent on\n             * reordering so far, we disable reordering.  */\n            unique->autoDyn = 0;\n        }\n#ifdef DD_DEBUG\n\tretval = Cudd_DebugCheck(unique);\n\tif (retval != 0) unique->reordered = 2;\n\tretval = Cudd_CheckKeys(unique);\n\tif (retval != 0) unique->reordered = 2;\n#endif\n\treturn(NULL);\n    }\n\n    if (subtable->keys > subtable->maxKeys) {\n\tif (unique->gcEnabled &&\n\t    ((unique->dead > unique->minDead) ||\n\t    ((unique->dead > unique->minDead / 2) &&\n\t    (subtable->dead > subtable->keys * 0.95)))) { /* too many dead */\n            if (unique->terminationCallback != NULL &&\n                unique->terminationCallback(unique->tcbArg)) {\n                unique->errorCode = CUDD_TERMINATION;\n                return(NULL);\n            }\n            if (util_cpu_time() - unique->startTime > unique->timeLimit) {\n                unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n                return(NULL);\n            }\n\t    (void) cuddGarbageCollect(unique,1);\n\t} else {\n\t    cuddRehash(unique,(int)level);\n\t}\n\t/* Update pointer to insertion point. In the case of rehashing,\n\t** the slot may have changed. In the case of garbage collection,\n\t** the predecessor may have been dead. */\n\tpos = ddHash(T, E, subtable->shift);\n\tnodelist = subtable->nodelist;\n\tpreviousP = &(nodelist[pos]);\n\tlooking = *previousP;\n\n\twhile (T < cuddT(looking)) {\n\t    previousP = &(looking->next);\n\t    looking = *previousP;\n#ifdef DD_UNIQUE_PROFILE\n\t    unique->uniqueLinks++;\n#endif\n\t}\n\twhile (T == cuddT(looking) && E < cuddE(looking)) {\n\t    previousP = &(looking->next);\n\t    looking = *previousP;\n#ifdef DD_UNIQUE_PROFILE\n\t    unique->uniqueLinks++;\n#endif\n\t}\n    }\n\n    gcNumber = unique->garbageCollections;\n    looking = cuddAllocNode(unique);\n    if (looking == NULL) {\n\treturn(NULL);\n    }\n    unique->keys++;\n    subtable->keys++;\n\n    if (gcNumber != unique->garbageCollections) {\n\tDdNode *looking2;\n\tpos = ddHash(T, E, subtable->shift);\n\tnodelist = subtable->nodelist;\n\tpreviousP = &(nodelist[pos]);\n\tlooking2 = *previousP;\n\n\twhile (T < cuddT(looking2)) {\n\t    previousP = &(looking2->next);\n\t    looking2 = *previousP;\n#ifdef DD_UNIQUE_PROFILE\n\t    unique->uniqueLinks++;\n#endif\n\t}\n\twhile (T == cuddT(looking2) && E < cuddE(looking2)) {\n\t    previousP = &(looking2->next);\n\t    looking2 = *previousP;\n#ifdef DD_UNIQUE_PROFILE\n\t    unique->uniqueLinks++;\n#endif\n\t}\n    }\n    looking->index = index;\n    cuddT(looking) = T;\n    cuddE(looking) = E;\n    looking->next = *previousP;\n    *previousP = looking;\n    cuddSatInc(T->ref);\t\t/* we know T is a regular pointer */\n    cuddRef(E);\n\n#ifdef DD_DEBUG\n    cuddCheckCollisionOrdering(unique,level,pos);\n#endif\n\n    return(looking);\n\n} /* end of cuddUniqueInter */\n\n\n/**\n  @brief Wrapper for cuddUniqueInter that is independent of variable\n  ordering.\n\n  @details Wrapper for cuddUniqueInter that is independent of\n  variable ordering (IVO). This function does not require parameter\n  index to precede the indices of the top nodes of T and E in the\n  variable order.\n\n  @return a pointer to the result node under normal conditions; NULL\n  if reordering occurred or memory was exhausted.\n\n  @sideeffect None\n\n  @see cuddUniqueInter Cudd_MakeBddFromZddCover\n\n*/\nDdNode *\ncuddUniqueInterIVO(\n  DdManager * unique,\n  int  index,\n  DdNode * T,\n  DdNode * E)\n{\n    DdNode *result;\n    DdNode *v;\n\n    v = cuddUniqueInter(unique, index, DD_ONE(unique),\n\t\t\tCudd_Not(DD_ONE(unique)));\n    if (v == NULL)\n\treturn(NULL);\n    /* Since v is a projection function, we can skip the call to cuddRef. */\n    result = cuddBddIteRecur(unique, v, T, E);\n    return(result);\n\n} /* end of cuddUniqueInterIVO */\n\n\n/**\n  @brief Checks the unique table for the existence of an internal\n  %ZDD node.\n\n  @details If it does not exist, it creates a new one.  Does not\n  modify the reference count of whatever is returned.  A newly created\n  internal node comes back with a reference count 0.  For a newly\n  created node, increments the reference counts of what T and E point\n  to.\n\n  @return a pointer to the new node if successful; NULL if memory is\n  exhausted, if a termination request was detected, if a timeout expired,\n  or if reordering took place.\n\n  @sideeffect None\n\n  @see cuddUniqueInter\n\n*/\nDdNode *\ncuddUniqueInterZdd(\n  DdManager * unique,\n  int  index,\n  DdNode * T,\n  DdNode * E)\n{\n    int pos;\n    unsigned int level;\n    int retval;\n    DdNodePtr *nodelist;\n    DdNode *looking;\n    DdSubtable *subtable;\n\n#ifdef DD_UNIQUE_PROFILE\n    unique->uniqueLookUps++;\n#endif\n\n    if (((int64_t) 0x1ffff & (int64_t) unique->cacheMisses) == 0) {\n        if (unique->terminationCallback != NULL &&\n            unique->terminationCallback(unique->tcbArg)) {\n            unique->errorCode = CUDD_TERMINATION;\n            return(NULL);\n        }\n        if (util_cpu_time() - unique->startTime > unique->timeLimit) {\n            unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n            return(NULL);\n        }\n    }\n    if (index >= unique->sizeZ) {\n\tif (!cuddResizeTableZdd(unique,index)) return(NULL);\n    }\n\n    level = unique->permZ[index];\n    subtable = &(unique->subtableZ[level]);\n\n#ifdef DD_DEBUG\n    assert(level < (unsigned) cuddIZ(unique,T->index));\n    assert(level < (unsigned) cuddIZ(unique,Cudd_Regular(E)->index));\n#endif\n\n    if (subtable->keys > subtable->maxKeys) {\n\tif (unique->gcEnabled && ((unique->deadZ > unique->minDead) ||\n\t(10 * subtable->dead > 9 * subtable->keys))) {\t/* too many dead */\n            if (unique->terminationCallback != NULL &&\n                unique->terminationCallback(unique->tcbArg)) {\n                unique->errorCode = CUDD_TERMINATION;\n                return(NULL);\n            }\n            if (util_cpu_time() - unique->startTime > unique->timeLimit) {\n                unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n                return(NULL);\n            }\n\t    (void) cuddGarbageCollect(unique,1);\n\t} else {\n\t    ddRehashZdd(unique,(int)level);\n\t}\n    }\n\n    pos = ddHash(T, E, subtable->shift);\n    nodelist = subtable->nodelist;\n    looking = nodelist[pos];\n\n    while (looking != NULL) {\n\tif (cuddT(looking) == T && cuddE(looking) == E) {\n\t    if (looking->ref == 0) {\n\t\tcuddReclaimZdd(unique,looking);\n\t    }\n\t    return(looking);\n\t}\n\tlooking = looking->next;\n#ifdef DD_UNIQUE_PROFILE\n\tunique->uniqueLinks++;\n#endif\n    }\n\n    /* countDead is 0 if deads should be counted and ~0 if they should not. */\n    if (unique->autoDynZ &&\n        unique->keysZ - (unique->deadZ & unique->countDead) >= unique->nextDyn) {\n#ifdef DD_DEBUG\n\tretval = Cudd_DebugCheck(unique);\n\tif (retval != 0) return(NULL);\n\tretval = Cudd_CheckKeys(unique);\n\tif (retval != 0) return(NULL);\n#endif\n\tretval = Cudd_zddReduceHeap(unique,unique->autoMethodZ,10); /* 10 = whatever */\n\tif (retval == 0) {\n            unique->reordered = 2;\n        } else if (unique->terminationCallback != NULL &&\n            unique->terminationCallback(unique->tcbArg)) {\n            unique->errorCode = CUDD_TERMINATION;\n            unique->reordered = 0;\n        } else if (util_cpu_time() - unique->startTime > unique->timeLimit) {\n            unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n            unique->reordered = 0;\n        }\n#ifdef DD_DEBUG\n\tretval = Cudd_DebugCheck(unique);\n\tif (retval != 0) unique->reordered = 2;\n\tretval = Cudd_CheckKeys(unique);\n\tif (retval != 0) unique->reordered = 2;\n#endif\n\treturn(NULL);\n    }\n\n    unique->keysZ++;\n    subtable->keys++;\n\n    looking = cuddAllocNode(unique);\n    if (looking == NULL) return(NULL);\n    looking->index = index;\n    cuddT(looking) = T;\n    cuddE(looking) = E;\n    looking->next = nodelist[pos];\n    nodelist[pos] = looking;\n    cuddRef(T);\n    cuddRef(E);\n\n    return(looking);\n\n} /* end of cuddUniqueInterZdd */\n\n\n/**\n * Helper function: Truncate a double value to approximately\n * 10^-10 precision (with rounding).\n *\n * This is used in cuddUnqiueConstant and cuddRehash to generate a\n * canonical double value for the hash lookup, ensuring that values that\n * are close will be hashed to the same bucket.\n */\nstatic double truncateDoubleConstant(double value)\n{\n\tdouble trunc, m, n;\n\n\t// (round off before doing hash function to ensure\n\t//  close valued constants are in the same table)\n\tif (isfinite(value)) {\n\t\ttrunc = 10000000000.0; // 10^10\n\t\tm = value * trunc;\n\t\tn = floor(m);\n\t\tif (m-n >= 0.5)\n\t\t\tn = n + 1;\n\t\tn = n / trunc;\n\t\treturn n;\n\t} else {\n\t\treturn value;\n\t}\n}\n\n\n/**\n  @brief Checks the unique table for the existence of a constant node.\n\n  @details If it does not exist, it creates a new one.  Does not\n  modify the reference count of whatever is returned.  A newly created\n  internal node comes back with a reference count 0.\n\n  @return a pointer to the new node.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddUniqueConst(\n  DdManager * unique,\n  CUDD_VALUE_TYPE  value)\n{\n    int pos;\n    DdNodePtr *nodelist;\n    DdNode *looking;\n    hack split;\n\n#ifdef DD_UNIQUE_PROFILE\n    unique->uniqueLookUps++;\n#endif\n\n    if (unique->constants.keys > unique->constants.maxKeys) {\n\tif (unique->gcEnabled && ((unique->dead > unique->minDead) ||\n\t(10 * unique->constants.dead > 9 * unique->constants.keys))) {\t/* too many dead */\n            if (unique->terminationCallback != NULL &&\n                unique->terminationCallback(unique->tcbArg)) {\n                unique->errorCode = CUDD_TERMINATION;\n                return(NULL);\n            }\n            if (util_cpu_time() - unique->startTime > unique->timeLimit) {\n                unique->errorCode = CUDD_TIMEOUT_EXPIRED;\n                return(NULL);\n            }\n\t    (void) cuddGarbageCollect(unique,1);\n\t} else {\n\t    cuddRehash(unique,CUDD_CONST_INDEX);\n\t}\n    }\n\n    cuddAdjust(value); /* for the case of crippled infinities */\n\n    if (ddAbs(value) < unique->epsilon) {\n\tvalue = 0.0;\n    }\n\n    /* PRISM-specific behaviour:\n     * To keep the number of distinct constants with very close double value low,\n     * we would like to identify constants where\n     *   ddEqualVal(value, existing_constant, unique->epsilon)\n     * is true, i.e., where the values differ by less than the CUDD epsilon parameter.\n     *\n     * However, as the lookup in the unique table is performed via a hashtable, we have\n     * to ensure that all constants that are close are hashed into the same bucket\n     * in the hash table.\n     *\n     * This is achieved by performing the hashtable lookup not on the value itself, but\n     * on a truncated/rounded version, i.e., where the precision has been reduced such\n     * that it is ensured that all constants within the epsilon range are hashed to\n     * the same value.\n     *\n     * The procedure is then:\n     *  1) Lookup the bucket (pos) using the truncated value (split.value)\n     *  2) In the linked list of the bucket, search for an exact match\n     *     or a close match\n     *  3) If there is no match, insert the value.\n     *\n     * To ensure that the uniqueness for the constants is not violated, during\n     * rehashing of the unique table for the constants, the truncation has to be\n     * applied as well (see cuddRehash, case for i == CUDD_CONST_INDEX).\n     *\n     * In addition, we catch the special case of constant zero, since some operations\n     * (e.g., for counting minterms) result in the addition of constants below epsilon.\n     */\n\n    // this is the original, CUDD version (without truncation):\n    // split.value = value;\n\n    // PRISM version:\n    // first, deal with zero separately\n\tif (value == 0.0 && unique->epsilon > 0.0 && DD_ZERO(unique) != NULL) {\n\t\treturn DD_ZERO(unique);\n\t}\n    // use truncated value for hash lookup\n    split.value = truncateDoubleConstant(value);\n\n    pos = ddHash(split.bits[0], split.bits[1], unique->constants.shift);\n    nodelist = unique->constants.nodelist;\n    looking = nodelist[pos];\n\n    /* Here we compare values both for equality and for difference less\n     * than epsilon. The first comparison is required when values are\n     * infinite, since Infinity - Infinity is NaN and NaN < X is 0 for\n     * every X.\n     */\n    // PRISM: check explicitly for not-a-number (NaN), as NaN != NaN\n    while (looking != NULL) {\n        if (looking->type.value == value ||\n            (isnan(value) && isnan(looking->type.value)) ||\n            ddEqualVal(looking->type.value,value,unique->epsilon)) {\n            if (looking->ref == 0) {\n                cuddReclaim(unique,looking);\n            }\n            return(looking);\n        }\n\tlooking = looking->next;\n#ifdef DD_UNIQUE_PROFILE\n\tunique->uniqueLinks++;\n#endif\n    }\n\n    unique->keys++;\n    unique->constants.keys++;\n\n    looking = cuddAllocNode(unique);\n    if (looking == NULL) return(NULL);\n    looking->index = CUDD_CONST_INDEX;\n    looking->type.value = value;\n    looking->next = nodelist[pos];\n    nodelist[pos] = looking;\n\n    return(looking);\n\n} /* end of cuddUniqueConst */\n\n\n/**\n  @brief Rehashes a unique subtable.\n\n  @details Doubles the size of a unique subtable and rehashes its\n  contents.\n\n  @sideeffect None\n\n*/\nvoid\ncuddRehash(\n  DdManager * unique,\n  int i)\n{\n    unsigned int slots, oldslots;\n    int shift, oldshift;\n    int j, pos;\n    DdNodePtr *nodelist, *oldnodelist;\n    DdNode *node, *next;\n    DdNode *sentinel = &(unique->sentinel);\n    hack split;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    if (unique->gcFrac == DD_GC_FRAC_HI && unique->slots > unique->looseUpTo) {\n\tunique->gcFrac = DD_GC_FRAC_LO;\n\tunique->minDead = (unsigned) (DD_GC_FRAC_LO * (double) unique->slots);\n#ifdef DD_VERBOSE\n\t(void) fprintf(unique->err,\"GC fraction = %.2f\\t\", DD_GC_FRAC_LO);\n\t(void) fprintf(unique->err,\"minDead = %d\\n\", unique->minDead);\n#endif\n    }\n\n    if (unique->gcFrac != DD_GC_FRAC_MIN && unique->memused > unique->maxmem) {\n\tunique->gcFrac = DD_GC_FRAC_MIN;\n\tunique->minDead = (unsigned) (DD_GC_FRAC_MIN * (double) unique->slots);\n#ifdef DD_VERBOSE\n\t(void) fprintf(unique->err,\"GC fraction = %.2f\\t\", DD_GC_FRAC_MIN);\n\t(void) fprintf(unique->err,\"minDead = %d\\n\", unique->minDead);\n#endif\n\tcuddShrinkDeathRow(unique);\n\tif (cuddGarbageCollect(unique,1) > 0) return;\n    }\n\n    if (i != CUDD_CONST_INDEX) {\n\toldslots = unique->subtables[i].slots;\n\toldshift = unique->subtables[i].shift;\n\toldnodelist = unique->subtables[i].nodelist;\n\n\t/* Compute the new size of the subtable. */\n\tslots = oldslots << 1;\n\tshift = oldshift - 1;\n\n\tsaveHandler = MMoutOfMemory;\n\tMMoutOfMemory = unique->outOfMemCallback;\n\tnodelist = ALLOC(DdNodePtr, slots);\n\tMMoutOfMemory = saveHandler;\n\tif (nodelist == NULL) {\n\t    (void) fprintf(unique->err,\n\t\t\t   \"Unable to resize subtable %d for lack of memory\\n\",\n\t\t\t   i);\n\t    /* Prevent frequent resizing attempts. */\n\t    (void) cuddGarbageCollect(unique,1);\n\t    if (unique->stash != NULL) {\n\t\tFREE(unique->stash);\n\t\tunique->stash = NULL;\n\t\t/* Inhibit resizing of tables. */\n\t\tcuddSlowTableGrowth(unique);\n\t    }\n\t    return;\n\t}\n\tunique->subtables[i].nodelist = nodelist;\n\tunique->subtables[i].slots = slots;\n\tunique->subtables[i].shift = shift;\n\tunique->subtables[i].maxKeys = slots * DD_MAX_SUBTABLE_DENSITY;\n\n\t/* Move the nodes from the old table to the new table.\n\t** This code depends on the type of hash function.\n\t** It assumes that the effect of doubling the size of the table\n\t** is to retain one more bit of the 32-bit hash value.\n\t** The additional bit is the LSB. */\n\tfor (j = 0; (unsigned) j < oldslots; j++) {\n\t    DdNodePtr *evenP, *oddP;\n\t    node = oldnodelist[j];\n\t    evenP = &(nodelist[j<<1]);\n\t    oddP = &(nodelist[(j<<1)+1]);\n\t    while (node != sentinel) {\n\t\tnext = node->next;\n\t\tpos = ddHash(cuddT(node), cuddE(node), shift);\n\t\tif (pos & 1) {\n\t\t    *oddP = node;\n\t\t    oddP = &(node->next);\n\t\t} else {\n\t\t    *evenP = node;\n\t\t    evenP = &(node->next);\n\t\t}\n\t\tnode = next;\n\t    }\n\t    *evenP = *oddP = sentinel;\n\t}\n\tFREE(oldnodelist);\n\n#ifdef DD_VERBOSE\n\t(void) fprintf(unique->err,\n\t\t       \"rehashing layer %d: keys %d dead %d new size %d\\n\",\n\t\t       i, unique->subtables[i].keys,\n\t\t       unique->subtables[i].dead, slots);\n#endif\n    } else {\n\toldslots = unique->constants.slots;\n\toldshift = unique->constants.shift;\n\toldnodelist = unique->constants.nodelist;\n\n\t/* The constant subtable is never subjected to reordering.\n\t** Therefore, when it is resized, it is because it has just\n\t** reached the maximum load. We can safely just double the size,\n\t** with no need for the loop we use for the other tables.\n\t*/\n\tslots = oldslots << 1;\n\tshift = oldshift - 1;\n\tsaveHandler = MMoutOfMemory;\n\tMMoutOfMemory = unique->outOfMemCallback;\n\tnodelist = ALLOC(DdNodePtr, slots);\n\tMMoutOfMemory = saveHandler;\n\tif (nodelist == NULL) {\n\t    (void) fprintf(unique->err,\n\t\t\t   \"Unable to resize constant subtable for lack of memory\\n\");\n\t    (void) cuddGarbageCollect(unique,1);\n\t    for (j = 0; j < unique->size; j++) {\n\t\tunique->subtables[j].maxKeys <<= 1;\n\t    }\n\t    unique->constants.maxKeys <<= 1;\n\t    return;\n\t}\n\tunique->constants.slots = slots;\n\tunique->constants.shift = shift;\n\tunique->constants.maxKeys = slots * DD_MAX_SUBTABLE_DENSITY;\n\tunique->constants.nodelist = nodelist;\n\tfor (j = 0; (unsigned) j < slots; j++) {\n\t    nodelist[j] = NULL;\n\t}\n\tfor (j = 0; (unsigned) j < oldslots; j++) {\n\t    node = oldnodelist[j];\n\t    while (node != NULL) {\n\t\tnext = node->next;\n\n\t\t// original CUDD version:\n\t\t// split.value = cuddV(node);\n\n\t\t// PRISM version: we have to truncate the value for the hash lookup\n\t\t// (see corresponding comment in cuddUniqueConstant)\n\t\tsplit.value = truncateDoubleConstant(cuddV(node));\n\n\t\tpos = ddHash(split.bits[0], split.bits[1], shift);\n\t\tnode->next = nodelist[pos];\n\t\tnodelist[pos] = node;\n\t\tnode = next;\n\t    }\n\t}\n\tFREE(oldnodelist);\n\n#ifdef DD_VERBOSE\n\t(void) fprintf(unique->err,\n\t\t       \"rehashing constants: keys %d dead %d new size %d\\n\",\n\t\t       unique->constants.keys,unique->constants.dead,slots);\n#endif\n    }\n\n    /* Update global data */\n\n    unique->memused += (slots - oldslots) * sizeof(DdNodePtr);\n    unique->slots += (slots - oldslots);\n    ddFixLimits(unique);\n\n} /* end of cuddRehash */\n\n\n/**\n  @brief Shrinks a subtable.\n\n  @sideeffect None\n\n  @see cuddRehash\n\n*/\nvoid\ncuddShrinkSubtable(\n  DdManager *unique,\n  int i)\n{\n    int j;\n    int shift, posn;\n    DdNodePtr *nodelist, *oldnodelist;\n    DdNode *node, *next;\n    DdNode *sentinel = &(unique->sentinel);\n    unsigned int slots, oldslots;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    oldnodelist = unique->subtables[i].nodelist;\n    oldslots = unique->subtables[i].slots;\n    slots = oldslots >> 1;\n    saveHandler = MMoutOfMemory;\n    MMoutOfMemory = unique->outOfMemCallback;\n    nodelist = ALLOC(DdNodePtr, slots);\n    MMoutOfMemory = saveHandler;\n    if (nodelist == NULL) {\n\treturn;\n    }\n    unique->subtables[i].nodelist = nodelist;\n    unique->subtables[i].slots = slots;\n    unique->subtables[i].shift++;\n    unique->subtables[i].maxKeys = slots * DD_MAX_SUBTABLE_DENSITY;\n#ifdef DD_VERBOSE\n    (void) fprintf(unique->err,\n\t\t   \"shrunk layer %d (%d keys) from %d to %d slots\\n\",\n\t\t   i, unique->subtables[i].keys, oldslots, slots);\n#endif\n\n    for (j = 0; (unsigned) j < slots; j++) {\n\tnodelist[j] = sentinel;\n    }\n    shift = unique->subtables[i].shift;\n    for (j = 0; (unsigned) j < oldslots; j++) {\n\tnode = oldnodelist[j];\n\twhile (node != sentinel) {\n\t    DdNode *looking, *T, *E;\n\t    DdNodePtr *previousP;\n\t    next = node->next;\n\t    posn = ddHash(cuddT(node), cuddE(node), shift);\n\t    previousP = &(nodelist[posn]);\n\t    looking = *previousP;\n\t    T = cuddT(node);\n\t    E = cuddE(node);\n\t    while (T < cuddT(looking)) {\n\t\tpreviousP = &(looking->next);\n\t\tlooking = *previousP;\n#ifdef DD_UNIQUE_PROFILE\n\t\tunique->uniqueLinks++;\n#endif\n\t    }\n\t    while (T == cuddT(looking) && E < cuddE(looking)) {\n\t\tpreviousP = &(looking->next);\n\t\tlooking = *previousP;\n#ifdef DD_UNIQUE_PROFILE\n\t\tunique->uniqueLinks++;\n#endif\n\t    }\n\t    node->next = *previousP;\n\t    *previousP = node;\n\t    node = next;\n\t}\n    }\n    FREE(oldnodelist);\n\n    unique->memused += ((long) slots - (long) oldslots) * sizeof(DdNode *);\n    unique->slots += slots - oldslots;\n    unique->minDead = (unsigned) (unique->gcFrac * (double) unique->slots);\n    unique->cacheSlack = (int)\n\tddMin(unique->maxCacheHard,DD_MAX_CACHE_TO_SLOTS_RATIO * unique->slots)\n\t- 2 * (int) unique->cacheSlots;\n\n} /* end of cuddShrinkSubtable */\n\n\n/**\n  @brief Inserts n new subtables in a unique table at level.\n\n  @details The number n should be positive, and level should be an\n  existing level.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddDestroySubtables\n\n*/\nint\ncuddInsertSubtables(\n  DdManager * unique,\n  int  n,\n  int  level)\n{\n    DdSubtable *newsubtables;\n    DdNodePtr *newnodelist;\n    DdNodePtr *newvars;\n    DdNode *sentinel = &(unique->sentinel);\n    int oldsize,newsize;\n    int i,j,index,reorderSave;\n    unsigned int numSlots = unique->initSlots;\n    int *newperm, *newinvperm, *newmap = NULL;\n    DdNode *one, *zero;\n\n#ifdef DD_DEBUG\n    assert(n > 0 && level < unique->size);\n#endif\n\n    oldsize = unique->size;\n    /* Easy case: there is still room in the current table. */\n    if (oldsize + n <= unique->maxSize) {\n\t/* Shift the tables at and below level. */\n\tfor (i = oldsize - 1; i >= level; i--) {\n\t    unique->subtables[i+n].slots    = unique->subtables[i].slots;\n\t    unique->subtables[i+n].shift    = unique->subtables[i].shift;\n\t    unique->subtables[i+n].keys     = unique->subtables[i].keys;\n\t    unique->subtables[i+n].maxKeys  = unique->subtables[i].maxKeys;\n\t    unique->subtables[i+n].dead     = unique->subtables[i].dead;\n            unique->subtables[i+n].next     = i+n;\n\t    unique->subtables[i+n].nodelist = unique->subtables[i].nodelist;\n\t    unique->subtables[i+n].bindVar  = unique->subtables[i].bindVar;\n\t    unique->subtables[i+n].varType  = unique->subtables[i].varType;\n\t    unique->subtables[i+n].pairIndex  = unique->subtables[i].pairIndex;\n\t    unique->subtables[i+n].varHandled = unique->subtables[i].varHandled;\n\t    unique->subtables[i+n].varToBeGrouped =\n\t\tunique->subtables[i].varToBeGrouped;\n\n\t    index                           = unique->invperm[i];\n\t    unique->invperm[i+n]            = index;\n\t    unique->perm[index]            += n;\n\t}\n\t/* Create new subtables. */\n\tfor (i = 0; i < n; i++) {\n\t    unique->subtables[level+i].slots = numSlots;\n\t    unique->subtables[level+i].shift = sizeof(int) * 8 -\n\t\tcuddComputeFloorLog2(numSlots);\n\t    unique->subtables[level+i].keys = 0;\n\t    unique->subtables[level+i].maxKeys = numSlots * DD_MAX_SUBTABLE_DENSITY;\n\t    unique->subtables[level+i].dead = 0;\n            unique->subtables[level+i].next = level+i;\n\t    unique->subtables[level+i].bindVar = 0;\n\t    unique->subtables[level+i].varType = CUDD_VAR_PRIMARY_INPUT;\n\t    unique->subtables[level+i].pairIndex = 0;\n\t    unique->subtables[level+i].varHandled = 0;\n\t    unique->subtables[level+i].varToBeGrouped = CUDD_LAZY_NONE;\n\n\t    unique->perm[oldsize+i] = level + i;\n\t    unique->invperm[level+i] = oldsize + i;\n\t    newnodelist = unique->subtables[level+i].nodelist =\n\t\tALLOC(DdNodePtr, numSlots);\n\t    if (newnodelist == NULL) {\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    for (j = 0; (unsigned) j < numSlots; j++) {\n\t\tnewnodelist[j] = sentinel;\n\t    }\n\t}\n\tif (unique->map != NULL) {\n\t    for (i = 0; i < n; i++) {\n\t\tunique->map[oldsize+i] = oldsize + i;\n\t    }\n\t}\n    } else {\n\t/* The current table is too small: we need to allocate a new,\n\t** larger one; move all old subtables, and initialize the new\n\t** subtables.\n\t*/\n\tnewsize = oldsize + n + DD_DEFAULT_RESIZE;\n#ifdef DD_VERBOSE\n\t(void) fprintf(unique->err,\n\t\t       \"Increasing the table size from %d to %d\\n\",\n\t    unique->maxSize, newsize);\n#endif\n\t/* Allocate memory for new arrays (except nodelists). */\n\tnewsubtables = ALLOC(DdSubtable,newsize);\n\tif (newsubtables == NULL) {\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tnewvars = ALLOC(DdNodePtr,newsize);\n\tif (newvars == NULL) {\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    FREE(newsubtables);\n\t    return(0);\n\t}\n\tnewperm = ALLOC(int,newsize);\n\tif (newperm == NULL) {\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    FREE(newsubtables);\n\t    FREE(newvars);\n\t    return(0);\n\t}\n\tnewinvperm = ALLOC(int,newsize);\n\tif (newinvperm == NULL) {\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    FREE(newsubtables);\n\t    FREE(newvars);\n\t    FREE(newperm);\n\t    return(0);\n\t}\n\tif (unique->map != NULL) {\n\t    newmap = ALLOC(int,newsize);\n\t    if (newmap == NULL) {\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\tFREE(newsubtables);\n\t\tFREE(newvars);\n\t\tFREE(newperm);\n\t\tFREE(newinvperm);\n\t\treturn(0);\n\t    }\n\t    unique->memused += (newsize - unique->maxSize) * sizeof(int);\n\t}\n\tunique->memused += (newsize - unique->maxSize) * ((numSlots+1) *\n\t    sizeof(DdNode *) + 2 * sizeof(int) + sizeof(DdSubtable));\n\t/* Copy levels before insertion points from old tables. */\n\tfor (i = 0; i < level; i++) {\n\t    newsubtables[i].slots = unique->subtables[i].slots;\n\t    newsubtables[i].shift = unique->subtables[i].shift;\n\t    newsubtables[i].keys = unique->subtables[i].keys;\n\t    newsubtables[i].maxKeys = unique->subtables[i].maxKeys;\n\t    newsubtables[i].dead = unique->subtables[i].dead;\n            newsubtables[i].next = i;\n\t    newsubtables[i].nodelist = unique->subtables[i].nodelist;\n\t    newsubtables[i].bindVar = unique->subtables[i].bindVar;\n\t    newsubtables[i].varType = unique->subtables[i].varType;\n\t    newsubtables[i].pairIndex = unique->subtables[i].pairIndex;\n\t    newsubtables[i].varHandled = unique->subtables[i].varHandled;\n\t    newsubtables[i].varToBeGrouped = unique->subtables[i].varToBeGrouped;\n\n\t    newvars[i] = unique->vars[i];\n\t    newperm[i] = unique->perm[i];\n\t    newinvperm[i] = unique->invperm[i];\n\t}\n\t/* Finish initializing permutation for new table to old one. */\n\tfor (i = level; i < oldsize; i++) {\n\t    newperm[i] = unique->perm[i];\n\t}\n\t/* Initialize new levels. */\n\tfor (i = level; i < level + n; i++) {\n\t    newsubtables[i].slots = numSlots;\n\t    newsubtables[i].shift = sizeof(int) * 8 -\n\t\tcuddComputeFloorLog2(numSlots);\n\t    newsubtables[i].keys = 0;\n\t    newsubtables[i].maxKeys = numSlots * DD_MAX_SUBTABLE_DENSITY;\n\t    newsubtables[i].dead = 0;\n            newsubtables[i].next = i;\n\t    newsubtables[i].bindVar = 0;\n\t    newsubtables[i].varType = CUDD_VAR_PRIMARY_INPUT;\n\t    newsubtables[i].pairIndex = 0;\n\t    newsubtables[i].varHandled = 0;\n\t    newsubtables[i].varToBeGrouped = CUDD_LAZY_NONE;\n\n\t    newperm[oldsize + i - level] = i;\n\t    newinvperm[i] = oldsize + i - level;\n\t    newnodelist = newsubtables[i].nodelist = ALLOC(DdNodePtr, numSlots);\n\t    if (newnodelist == NULL) {\n\t\t/* We are going to leak some memory.  We should clean up. */\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    for (j = 0; (unsigned) j < numSlots; j++) {\n\t\tnewnodelist[j] = sentinel;\n\t    }\n\t}\n\t/* Copy the old tables for levels past the insertion point. */\n\tfor (i = level; i < oldsize; i++) {\n\t    newsubtables[i+n].slots    = unique->subtables[i].slots;\n\t    newsubtables[i+n].shift    = unique->subtables[i].shift;\n\t    newsubtables[i+n].keys     = unique->subtables[i].keys;\n\t    newsubtables[i+n].maxKeys  = unique->subtables[i].maxKeys;\n\t    newsubtables[i+n].dead     = unique->subtables[i].dead;\n            newsubtables[i+n].next     = i+n;\n\t    newsubtables[i+n].nodelist = unique->subtables[i].nodelist;\n\t    newsubtables[i+n].bindVar  = unique->subtables[i].bindVar;\n\t    newsubtables[i+n].varType  = unique->subtables[i].varType;\n\t    newsubtables[i+n].pairIndex  = unique->subtables[i].pairIndex;\n\t    newsubtables[i+n].varHandled  = unique->subtables[i].varHandled;\n\t    newsubtables[i+n].varToBeGrouped  =\n\t\tunique->subtables[i].varToBeGrouped;\n\n\t    newvars[i]                 = unique->vars[i];\n\t    index                      = unique->invperm[i];\n\t    newinvperm[i+n]            = index;\n\t    newperm[index]            += n;\n\t}\n\t/* Update the map. */\n\tif (unique->map != NULL) {\n\t    for (i = 0; i < oldsize; i++) {\n\t\tnewmap[i] = unique->map[i];\n\t    }\n\t    for (i = oldsize; i < oldsize + n; i++) {\n\t\tnewmap[i] = i;\n\t    }\n\t    FREE(unique->map);\n\t    unique->map = newmap;\n\t}\n\t/* Install the new tables and free the old ones. */\n\tFREE(unique->subtables);\n\tunique->subtables = newsubtables;\n\tunique->maxSize = newsize;\n\tFREE(unique->vars);\n\tunique->vars = newvars;\n\tFREE(unique->perm);\n\tunique->perm = newperm;\n\tFREE(unique->invperm);\n\tunique->invperm = newinvperm;\n\t/* Update the stack for iterative procedures. */\n\tif (newsize > unique->maxSizeZ) {\n\t    FREE(unique->stack);\n\t    unique->stack = ALLOC(DdNodePtr,newsize + 1);\n\t    if (unique->stack == NULL) {\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    unique->stack[0] = NULL; /* to suppress harmless UMR */\n\t    unique->memused +=\n\t\t(newsize - ddMax(unique->maxSize,unique->maxSizeZ))\n\t\t* sizeof(DdNode *);\n\t}\n    }\n    /* Update manager parameters to account for the new subtables. */\n    unique->slots += n * numSlots;\n    ddFixLimits(unique);\n    unique->size += n;\n\n    /* Now that the table is in a coherent state, create the new\n    ** projection functions. We need to temporarily disable reordering,\n    ** because we cannot reorder without projection functions in place.\n    **/\n    one = unique->one;\n    zero = Cudd_Not(one);\n\n    reorderSave = unique->autoDyn;\n    unique->autoDyn = 0;\n    for (i = oldsize; i < oldsize + n; i++) {\n\tunique->vars[i] = cuddUniqueInter(unique,i,one,zero);\n\tif (unique->vars[i] == NULL) {\n\t    unique->autoDyn = reorderSave;\n\t    /* Shift everything back so table remains coherent. */\n\t    for (j = oldsize; j < i; j++) {\n\t\tCudd_IterDerefBdd(unique,unique->vars[j]);\n\t\tcuddDeallocNode(unique,unique->vars[j]);\n\t\tunique->vars[j] = NULL;\n\t    }\n\t    for (j = level; j < oldsize; j++) {\n\t\tunique->subtables[j].slots    = unique->subtables[j+n].slots;\n\t\tunique->subtables[j].slots    = unique->subtables[j+n].slots;\n\t\tunique->subtables[j].shift    = unique->subtables[j+n].shift;\n\t\tunique->subtables[j].keys     = unique->subtables[j+n].keys;\n\t\tunique->subtables[j].maxKeys  =\n\t\t    unique->subtables[j+n].maxKeys;\n\t\tunique->subtables[j].dead     = unique->subtables[j+n].dead;\n                unique->subtables[j].next     = j;\n\t\tFREE(unique->subtables[j].nodelist);\n\t\tunique->subtables[j].nodelist =\n\t\t    unique->subtables[j+n].nodelist;\n\t\tunique->subtables[j+n].nodelist = NULL;\n\t\tunique->subtables[j].bindVar  =\n\t\t    unique->subtables[j+n].bindVar;\n\t\tunique->subtables[j].varType  =\n\t\t    unique->subtables[j+n].varType;\n\t\tunique->subtables[j].pairIndex =\n\t\t    unique->subtables[j+n].pairIndex;\n\t\tunique->subtables[j].varHandled =\n\t\t    unique->subtables[j+n].varHandled;\n\t\tunique->subtables[j].varToBeGrouped =\n\t\t    unique->subtables[j+n].varToBeGrouped;\n\t\tindex                         = unique->invperm[j+n];\n\t\tunique->invperm[j]            = index;\n\t\tunique->perm[index]          -= n;\n\t    }\n\t    unique->size = oldsize;\n\t    unique->slots -= n * numSlots;\n\t    ddFixLimits(unique);\n\t    (void) Cudd_DebugCheck(unique);\n\t    return(0);\n\t}\n\tcuddRef(unique->vars[i]);\n    }\n    if (unique->tree != NULL) {\n\tunique->tree->size += n;\n\tunique->tree->index = unique->invperm[0];\n\tddPatchTree(unique,unique->tree);\n    }\n    unique->autoDyn = reorderSave;\n\n    return(1);\n\n} /* end of cuddInsertSubtables */\n\n\n/**\n  @brief Destroys the n most recently created subtables in a unique table.\n\n  @details n should be positive. The subtables should not contain any live\n  nodes, except the (isolated) projection function. The projection\n  functions are freed.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect The variable map used for fast variable substitution is\n  destroyed if it exists. In this case the cache is also cleared.\n\n  @see cuddInsertSubtables Cudd_SetVarMap\n\n*/\nint\ncuddDestroySubtables(\n  DdManager * unique,\n  int  n)\n{\n    DdSubtable *subtables;\n    DdNodePtr *nodelist;\n    DdNodePtr *vars;\n    int firstIndex, lastIndex;\n    int index, level, newlevel;\n    int lowestLevel;\n    int shift;\n    int found;\n\n    /* Sanity check and set up. */\n    if (n <= 0) return(0);\n    if (n > unique->size) n = unique->size;\n\n    subtables = unique->subtables;\n    vars = unique->vars;\n    firstIndex = unique->size - n;\n    lastIndex  = unique->size;\n\n    /* Check for nodes labeled by the variables being destroyed\n    ** that may still be in use.  It is allowed to destroy a variable\n    ** only if there are no such nodes. Also, find the lowest level\n    ** among the variables being destroyed. This will make further\n    ** processing more efficient.\n    */\n    lowestLevel = unique->size;\n    for (index = firstIndex; index < lastIndex; index++) {\n\tlevel = unique->perm[index];\n\tif (level < lowestLevel) lowestLevel = level;\n\tif (subtables[level].keys - subtables[level].dead != 1) return(0);\n\t/* The projection function should be isolated. If the ref count\n\t** is 1, everything is OK. If the ref count is saturated, then\n\t** we need to make sure that there are no nodes pointing to it.\n\t** As for the external references, we assume the application is\n\t** responsible for them.\n\t*/\n\tif (vars[index]->ref != 1) {\n\t    if (vars[index]->ref != DD_MAXREF) return(0);\n\t    found = cuddFindParent(unique,vars[index]);\n\t    if (found) {\n\t\treturn(0);\n\t    } else {\n\t\tvars[index]->ref = 1;\n\t    }\n\t}\n\tCudd_RecursiveDeref(unique,vars[index]);\n    }\n\n    /* Collect garbage, because we cannot afford having dead nodes pointing\n    ** to the dead nodes in the subtables being destroyed.\n    */\n    (void) cuddGarbageCollect(unique,1);\n\n    /* Here we know we can destroy our subtables. */\n    for (index = firstIndex; index < lastIndex; index++) {\n\tlevel = unique->perm[index];\n\tnodelist = subtables[level].nodelist;\n#ifdef DD_DEBUG\n\tassert(subtables[level].keys == 0);\n#endif\n\tFREE(nodelist);\n\tunique->memused -= sizeof(DdNodePtr) * subtables[level].slots;\n\tunique->slots -= subtables[level].slots;\n\tunique->dead -= subtables[level].dead;\n    }\n\n    /* Here all subtables to be destroyed have their keys field == 0 and\n    ** their hash tables have been freed.\n    ** We now scan the subtables from level lowestLevel + 1 to level size - 1,\n    ** shifting the subtables as required. We keep a running count of\n    ** how many subtables have been moved, so that we know by how many\n    ** positions each subtable should be shifted.\n    */\n    shift = 1;\n    for (level = lowestLevel + 1; level < unique->size; level++) {\n\tif (subtables[level].keys == 0) {\n\t    shift++;\n\t    continue;\n\t}\n\tnewlevel = level - shift;\n\tsubtables[newlevel].slots = subtables[level].slots;\n\tsubtables[newlevel].shift = subtables[level].shift;\n\tsubtables[newlevel].keys = subtables[level].keys;\n\tsubtables[newlevel].maxKeys = subtables[level].maxKeys;\n\tsubtables[newlevel].dead = subtables[level].dead;\n        subtables[newlevel].next = newlevel;\n\tsubtables[newlevel].nodelist = subtables[level].nodelist;\n\tindex = unique->invperm[level];\n\tunique->perm[index] = newlevel;\n\tunique->invperm[newlevel]  = index;\n\tsubtables[newlevel].bindVar = subtables[level].bindVar;\n\tsubtables[newlevel].varType = subtables[level].varType;\n\tsubtables[newlevel].pairIndex = subtables[level].pairIndex;\n\tsubtables[newlevel].varHandled = subtables[level].varHandled;\n\tsubtables[newlevel].varToBeGrouped = subtables[level].varToBeGrouped;\n    }\n    /* Destroy the map. If a surviving variable is\n    ** mapped to a dying variable, and the map were used again,\n    ** an out-of-bounds access to unique->vars would result. */\n    if (unique->map != NULL) {\n\tcuddCacheFlush(unique);\n\tFREE(unique->map);\n\tunique->map = NULL;\n    }\n\n    unique->minDead = (unsigned) (unique->gcFrac * (double) unique->slots);\n    unique->size -= n;\n\n    return(1);\n\n} /* end of cuddDestroySubtables */\n\n\n/**\n  @brief Increases the number of %ZDD subtables in a unique table so\n  that it meets or exceeds index.\n\n  @details When new %ZDD variables are created, it is possible to\n  preserve the functions unchanged, or it is possible to preserve the\n  covers unchanged, but not both. cuddResizeTableZdd preserves the\n  covers.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see ddResizeTable\n\n*/\nint\ncuddResizeTableZdd(\n  DdManager * unique,\n  int  index)\n{\n    DdSubtable *newsubtables;\n    DdNodePtr *newnodelist;\n    int oldsize,newsize;\n    int i,j,reorderSave;\n    unsigned int numSlots = unique->initSlots;\n    int *newperm, *newinvperm;\n\n    oldsize = unique->sizeZ;\n    /* Easy case: there is still room in the current table. */\n    if (index < unique->maxSizeZ) {\n\tfor (i = oldsize; i <= index; i++) {\n\t    unique->subtableZ[i].slots = numSlots;\n\t    unique->subtableZ[i].shift = sizeof(int) * 8 -\n\t\tcuddComputeFloorLog2(numSlots);\n\t    unique->subtableZ[i].keys = 0;\n\t    unique->subtableZ[i].maxKeys = numSlots * DD_MAX_SUBTABLE_DENSITY;\n\t    unique->subtableZ[i].dead = 0;\n            unique->subtableZ[i].next = i;\n\t    unique->permZ[i] = i;\n\t    unique->invpermZ[i] = i;\n\t    newnodelist = unique->subtableZ[i].nodelist =\n\t\tALLOC(DdNodePtr, numSlots);\n\t    if (newnodelist == NULL) {\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    for (j = 0; (unsigned) j < numSlots; j++) {\n\t\tnewnodelist[j] = NULL;\n\t    }\n\t}\n    } else {\n\t/* The current table is too small: we need to allocate a new,\n\t** larger one; move all old subtables, and initialize the new\n\t** subtables up to index included.\n\t*/\n\tnewsize = index + DD_DEFAULT_RESIZE;\n#ifdef DD_VERBOSE\n\t(void) fprintf(unique->err,\n\t\t       \"Increasing the ZDD table size from %d to %d\\n\",\n\t    unique->maxSizeZ, newsize);\n#endif\n\tnewsubtables = ALLOC(DdSubtable,newsize);\n\tif (newsubtables == NULL) {\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tnewperm = ALLOC(int,newsize);\n\tif (newperm == NULL) {\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tnewinvperm = ALLOC(int,newsize);\n\tif (newinvperm == NULL) {\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tunique->memused += (newsize - unique->maxSizeZ) * ((numSlots+1) *\n\t    sizeof(DdNode *) + 2 * sizeof(int) + sizeof(DdSubtable));\n\tif (newsize > unique->maxSize) {\n\t    FREE(unique->stack);\n\t    unique->stack = ALLOC(DdNodePtr,newsize + 1);\n\t    if (unique->stack == NULL) {\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    unique->stack[0] = NULL; /* to suppress harmless UMR */\n\t    unique->memused +=\n\t\t(newsize - ddMax(unique->maxSize,unique->maxSizeZ))\n\t\t* sizeof(DdNode *);\n\t}\n\tfor (i = 0; i < oldsize; i++) {\n\t    newsubtables[i].slots = unique->subtableZ[i].slots;\n\t    newsubtables[i].shift = unique->subtableZ[i].shift;\n\t    newsubtables[i].keys = unique->subtableZ[i].keys;\n\t    newsubtables[i].maxKeys = unique->subtableZ[i].maxKeys;\n\t    newsubtables[i].dead = unique->subtableZ[i].dead;\n            newsubtables[i].next = i;\n\t    newsubtables[i].nodelist = unique->subtableZ[i].nodelist;\n\t    newperm[i] = unique->permZ[i];\n\t    newinvperm[i] = unique->invpermZ[i];\n\t}\n\tfor (i = oldsize; i <= index; i++) {\n\t    newsubtables[i].slots = numSlots;\n\t    newsubtables[i].shift = sizeof(int) * 8 -\n\t\tcuddComputeFloorLog2(numSlots);\n\t    newsubtables[i].keys = 0;\n\t    newsubtables[i].maxKeys = numSlots * DD_MAX_SUBTABLE_DENSITY;\n\t    newsubtables[i].dead = 0;\n            newsubtables[i].next = i;\n\t    newperm[i] = i;\n\t    newinvperm[i] = i;\n\t    newnodelist = newsubtables[i].nodelist = ALLOC(DdNodePtr, numSlots);\n\t    if (newnodelist == NULL) {\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    for (j = 0; (unsigned) j < numSlots; j++) {\n\t\tnewnodelist[j] = NULL;\n\t    }\n\t}\n\tFREE(unique->subtableZ);\n\tunique->subtableZ = newsubtables;\n\tunique->maxSizeZ = newsize;\n\tFREE(unique->permZ);\n\tunique->permZ = newperm;\n\tFREE(unique->invpermZ);\n\tunique->invpermZ = newinvperm;\n    }\n    unique->slots += (index + 1 - unique->sizeZ) * numSlots;\n    ddFixLimits(unique);\n    unique->sizeZ = index + 1;\n\n    /* Now that the table is in a coherent state, update the ZDD\n    ** universe. We need to temporarily disable reordering,\n    ** because we cannot reorder without universe in place.\n    */\n\n    reorderSave = unique->autoDynZ;\n    unique->autoDynZ = 0;\n    cuddZddFreeUniv(unique);\n    if (!cuddZddInitUniv(unique)) {\n\tunique->autoDynZ = reorderSave;\n\treturn(0);\n    }\n    unique->autoDynZ = reorderSave;\n\n    return(1);\n\n} /* end of cuddResizeTableZdd */\n\n\n/**\n  @brief Adjusts parameters of a table to slow down its growth.\n\n  @sideeffect None\n\n*/\nvoid\ncuddSlowTableGrowth(\n  DdManager *unique)\n{\n    int i;\n\n    unique->maxCacheHard = unique->cacheSlots - 1;\n    unique->cacheSlack = - (int) (unique->cacheSlots + 1);\n    for (i = 0; i < unique->size; i++) {\n\tunique->subtables[i].maxKeys <<= 2;\n    }\n    unique->gcFrac = DD_GC_FRAC_MIN;\n    unique->minDead = (unsigned) (DD_GC_FRAC_MIN * (double) unique->slots);\n    cuddShrinkDeathRow(unique);\n#ifdef DD_VERBOSE\n    (void) fprintf(unique->err,\"CUDD: slowing down table growth: \");\n    (void) fprintf(unique->err,\"GC fraction = %.2f\\t\", unique->gcFrac);\n    (void) fprintf(unique->err,\"minDead = %u\\n\", unique->minDead);\n#endif\n\n} /* end of cuddSlowTableGrowth */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Rehashes a %ZDD unique subtable.\n\n  @sideeffect None\n\n  @see cuddRehash\n\n*/\nstatic void\nddRehashZdd(\n  DdManager * unique,\n  int  i)\n{\n    unsigned int slots, oldslots;\n    int shift, oldshift;\n    int j, pos;\n    DdNodePtr *nodelist, *oldnodelist;\n    DdNode *node, *next;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n    if (unique->slots > unique->looseUpTo) {\n\tunique->minDead = (unsigned) (DD_GC_FRAC_LO * (double) unique->slots);\n#ifdef DD_VERBOSE\n\tif (unique->gcFrac == DD_GC_FRAC_HI) {\n\t    (void) fprintf(unique->err,\"GC fraction = %.2f\\t\",\n\t\t\t   DD_GC_FRAC_LO);\n\t    (void) fprintf(unique->err,\"minDead = %d\\n\", unique->minDead);\n\t}\n#endif\n\tunique->gcFrac = DD_GC_FRAC_LO;\n    }\n\n    assert(i != CUDD_MAXINDEX);\n    oldslots = unique->subtableZ[i].slots;\n    oldshift = unique->subtableZ[i].shift;\n    oldnodelist = unique->subtableZ[i].nodelist;\n\n    /* Compute the new size of the subtable. Normally, we just\n    ** double.  However, after reordering, a table may be severely\n    ** overloaded. Therefore, we iterate. */\n    slots = oldslots;\n    shift = oldshift;\n    do {\n\tslots <<= 1;\n\tshift--;\n    } while (slots * DD_MAX_SUBTABLE_DENSITY < unique->subtableZ[i].keys);\n\n    saveHandler = MMoutOfMemory;\n    MMoutOfMemory = unique->outOfMemCallback;\n    nodelist = ALLOC(DdNodePtr, slots);\n    MMoutOfMemory = saveHandler;\n    if (nodelist == NULL) {\n\t(void) fprintf(unique->err,\n\t\t       \"Unable to resize ZDD subtable %d for lack of memory.\\n\",\n\t\t       i);\n\t(void) cuddGarbageCollect(unique,1);\n\tfor (j = 0; j < unique->sizeZ; j++) {\n\t    unique->subtableZ[j].maxKeys <<= 1;\n\t}\n\treturn;\n    }\n    unique->subtableZ[i].nodelist = nodelist;\n    unique->subtableZ[i].slots = slots;\n    unique->subtableZ[i].shift = shift;\n    unique->subtableZ[i].maxKeys = slots * DD_MAX_SUBTABLE_DENSITY;\n    for (j = 0; (unsigned) j < slots; j++) {\n\tnodelist[j] = NULL;\n    }\n    for (j = 0; (unsigned) j < oldslots; j++) {\n\tnode = oldnodelist[j];\n\twhile (node != NULL) {\n\t    next = node->next;\n\t    pos = ddHash(cuddT(node), cuddE(node), shift);\n\t    node->next = nodelist[pos];\n\t    nodelist[pos] = node;\n\t    node = next;\n\t}\n    }\n    FREE(oldnodelist);\n\n#ifdef DD_VERBOSE\n    (void) fprintf(unique->err,\n\t\t   \"rehashing layer %d: keys %d dead %d new size %d\\n\",\n\t\t   i, unique->subtableZ[i].keys,\n\t\t   unique->subtableZ[i].dead, slots);\n#endif\n\n    /* Update global data. */\n    unique->memused += (slots - oldslots) * sizeof(DdNode *);\n    unique->slots += (slots - oldslots);\n    ddFixLimits(unique);\n\n} /* end of ddRehashZdd */\n\n\n/**\n  @brief Increases the number of subtables in a unique table so\n  that it meets or exceeds index.\n\n  @details The parameter amount determines how much spare space is\n  allocated to prevent too frequent resizing.  If index is negative,\n  the table is resized, but no new variables are created.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Reserve cuddResizeTableZdd\n\n*/\nstatic int\nddResizeTable(\n  DdManager * unique,\n  int index,\n  int amount)\n{\n    DdSubtable *newsubtables;\n    DdNodePtr *newnodelist;\n    DdNodePtr *newvars;\n    DdNode *sentinel = &(unique->sentinel);\n    int oldsize,newsize;\n    int i,j,reorderSave;\n    int numSlots = unique->initSlots;\n    int *newperm, *newinvperm, *newmap = NULL;\n    DdNode *one, *zero;\n\n    oldsize = unique->size;\n    /* Easy case: there is still room in the current table. */\n    if (index >= 0 && index < unique->maxSize) {\n\tfor (i = oldsize; i <= index; i++) {\n\t    unique->subtables[i].slots = numSlots;\n\t    unique->subtables[i].shift = sizeof(int) * 8 -\n\t\tcuddComputeFloorLog2(numSlots);\n\t    unique->subtables[i].keys = 0;\n\t    unique->subtables[i].maxKeys = numSlots * DD_MAX_SUBTABLE_DENSITY;\n\t    unique->subtables[i].dead = 0;\n            unique->subtables[i].next = i;\n\t    unique->subtables[i].bindVar = 0;\n\t    unique->subtables[i].varType = CUDD_VAR_PRIMARY_INPUT;\n\t    unique->subtables[i].pairIndex = 0;\n\t    unique->subtables[i].varHandled = 0;\n\t    unique->subtables[i].varToBeGrouped = CUDD_LAZY_NONE;\n\n\t    unique->perm[i] = i;\n\t    unique->invperm[i] = i;\n\t    newnodelist = unique->subtables[i].nodelist =\n\t\tALLOC(DdNodePtr, numSlots);\n\t    if (newnodelist == NULL) {\n\t\tfor (j = oldsize; j < i; j++) {\n\t\t    FREE(unique->subtables[j].nodelist);\n\t\t}\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    for (j = 0; j < numSlots; j++) {\n\t\tnewnodelist[j] = sentinel;\n\t    }\n\t}\n\tif (unique->map != NULL) {\n\t    for (i = oldsize; i <= index; i++) {\n\t\tunique->map[i] = i;\n\t    }\n\t}\n    } else {\n\t/* The current table is too small: we need to allocate a new,\n\t** larger one; move all old subtables, and initialize the new\n\t** subtables up to index included.\n\t*/\n\tnewsize = (index < 0) ? amount + oldsize : index + amount;\n#ifdef DD_VERBOSE\n\t(void) fprintf(unique->err,\n\t\t       \"Increasing the table size from %d to %d\\n\",\n\t\t       unique->maxSize, newsize);\n#endif\n\tnewsubtables = ALLOC(DdSubtable,newsize);\n\tif (newsubtables == NULL) {\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tnewvars = ALLOC(DdNodePtr,newsize);\n\tif (newvars == NULL) {\n\t    FREE(newsubtables);\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tnewperm = ALLOC(int,newsize);\n\tif (newperm == NULL) {\n\t    FREE(newsubtables);\n\t    FREE(newvars);\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tnewinvperm = ALLOC(int,newsize);\n\tif (newinvperm == NULL) {\n\t    FREE(newsubtables);\n\t    FREE(newvars);\n\t    FREE(newperm);\n\t    unique->errorCode = CUDD_MEMORY_OUT;\n\t    return(0);\n\t}\n\tif (unique->map != NULL) {\n\t    newmap = ALLOC(int,newsize);\n\t    if (newmap == NULL) {\n\t\tFREE(newsubtables);\n\t\tFREE(newvars);\n\t\tFREE(newperm);\n\t\tFREE(newinvperm);\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    unique->memused += (newsize - unique->maxSize) * sizeof(int);\n\t}\n\tunique->memused += (newsize - unique->maxSize) * ((numSlots+1) *\n\t    sizeof(DdNode *) + 2 * sizeof(int) + sizeof(DdSubtable));\n\tif (newsize > unique->maxSizeZ) {\n\t    FREE(unique->stack);\n\t    unique->stack = ALLOC(DdNodePtr,newsize + 1);\n\t    if (unique->stack == NULL) {\n\t\tFREE(newsubtables);\n\t\tFREE(newvars);\n\t\tFREE(newperm);\n\t\tFREE(newinvperm);\n\t\tif (unique->map != NULL) {\n\t\t    FREE(newmap);\n\t\t}\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    unique->stack[0] = NULL; /* to suppress harmless UMR */\n\t    unique->memused +=\n\t\t(newsize - ddMax(unique->maxSize,unique->maxSizeZ))\n\t\t* sizeof(DdNode *);\n\t}\n\tfor (i = 0; i < oldsize; i++) {\n\t    newsubtables[i].slots = unique->subtables[i].slots;\n\t    newsubtables[i].shift = unique->subtables[i].shift;\n\t    newsubtables[i].keys = unique->subtables[i].keys;\n\t    newsubtables[i].maxKeys = unique->subtables[i].maxKeys;\n\t    newsubtables[i].dead = unique->subtables[i].dead;\n            newsubtables[i].next = i;\n\t    newsubtables[i].nodelist = unique->subtables[i].nodelist;\n\t    newsubtables[i].bindVar = unique->subtables[i].bindVar;\n\t    newsubtables[i].varType = unique->subtables[i].varType;\n\t    newsubtables[i].pairIndex = unique->subtables[i].pairIndex;\n\t    newsubtables[i].varHandled = unique->subtables[i].varHandled;\n\t    newsubtables[i].varToBeGrouped = unique->subtables[i].varToBeGrouped;\n\n\t    newvars[i] = unique->vars[i];\n\t    newperm[i] = unique->perm[i];\n\t    newinvperm[i] = unique->invperm[i];\n\t}\n\tfor (i = oldsize; i <= index; i++) {\n\t    newsubtables[i].slots = numSlots;\n\t    newsubtables[i].shift = sizeof(int) * 8 -\n\t\tcuddComputeFloorLog2(numSlots);\n\t    newsubtables[i].keys = 0;\n\t    newsubtables[i].maxKeys = numSlots * DD_MAX_SUBTABLE_DENSITY;\n\t    newsubtables[i].dead = 0;\n            newsubtables[i].next = i;\n\t    newsubtables[i].bindVar = 0;\n\t    newsubtables[i].varType = CUDD_VAR_PRIMARY_INPUT;\n\t    newsubtables[i].pairIndex = 0;\n\t    newsubtables[i].varHandled = 0;\n\t    newsubtables[i].varToBeGrouped = CUDD_LAZY_NONE;\n\n\t    newperm[i] = i;\n\t    newinvperm[i] = i;\n\t    newnodelist = newsubtables[i].nodelist = ALLOC(DdNodePtr, numSlots);\n\t    if (newnodelist == NULL) {\n\t\tunique->errorCode = CUDD_MEMORY_OUT;\n\t\treturn(0);\n\t    }\n\t    for (j = 0; j < numSlots; j++) {\n\t\tnewnodelist[j] = sentinel;\n\t    }\n\t}\n\tif (unique->map != NULL) {\n\t    for (i = 0; i < oldsize; i++) {\n\t\tnewmap[i] = unique->map[i];\n\t    }\n\t    for (i = oldsize; i <= index; i++) {\n\t\tnewmap[i] = i;\n\t    }\n\t    FREE(unique->map);\n\t    unique->map = newmap;\n\t}\n\tFREE(unique->subtables);\n\tunique->subtables = newsubtables;\n\tunique->maxSize = newsize;\n\tFREE(unique->vars);\n\tunique->vars = newvars;\n\tFREE(unique->perm);\n\tunique->perm = newperm;\n\tFREE(unique->invperm);\n\tunique->invperm = newinvperm;\n    }\n\n    /* Now that the table is in a coherent state, create the new\n    ** projection functions. We need to temporarily disable reordering,\n    ** because we cannot reorder without projection functions in place.\n    **/\n    if (index >= 0) {\n        one = unique->one;\n        zero = Cudd_Not(one);\n\n        unique->size = index + 1;\n        if (unique->tree != NULL) {\n\t    unique->tree->size = ddMax(unique->tree->size, (MtrHalfWord) unique->size);\n        }\n        unique->slots += (index + 1 - oldsize) * numSlots;\n        ddFixLimits(unique);\n\n        reorderSave = unique->autoDyn;\n        unique->autoDyn = 0;\n        for (i = oldsize; i <= index; i++) {\n            unique->vars[i] = cuddUniqueInter(unique,i,one,zero);\n            if (unique->vars[i] == NULL) {\n                unique->autoDyn = reorderSave;\n                for (j = oldsize; j < i; j++) {\n                    Cudd_IterDerefBdd(unique,unique->vars[j]);\n                    cuddDeallocNode(unique,unique->vars[j]);\n                    unique->vars[j] = NULL;\n                }\n                for (j = oldsize; j <= index; j++) {\n                    FREE(unique->subtables[j].nodelist);\n                    unique->subtables[j].nodelist = NULL;\n                }\n                unique->size = oldsize;\n                unique->slots -= (index + 1 - oldsize) * numSlots;\n                ddFixLimits(unique);\n                return(0);\n            }\n            cuddRef(unique->vars[i]);\n        }\n        unique->autoDyn = reorderSave;\n    }\n\n    return(1);\n\n} /* end of ddResizeTable */\n\n\n/**\n  @brief Searches the subtables above node for a parent.\n\n  @details Returns 1 as soon as one parent is found. Returns 0 is the\n  search is fruitless.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddFindParent(\n  DdManager * table,\n  DdNode * node)\n{\n    int         i,j;\n    int\t\tslots;\n    DdNodePtr\t*nodelist;\n    DdNode\t*f;\n\n    for (i = cuddI(table,node->index) - 1; i >= 0; i--) {\n\tnodelist = table->subtables[i].nodelist;\n\tslots = table->subtables[i].slots;\n\n\tfor (j = 0; j < slots; j++) {\n\t    f = nodelist[j];\n\t    while (cuddT(f) > node) {\n\t\tf = f->next;\n\t    }\n\t    while (cuddT(f) == node && Cudd_Regular(cuddE(f)) > node) {\n\t\tf = f->next;\n\t    }\n\t    if (cuddT(f) == node && Cudd_Regular(cuddE(f)) == node) {\n\t\treturn(1);\n\t    }\n\t}\n    }\n\n    return(0);\n\n} /* end of cuddFindParent */\n\n\n/**\n  @brief Adjusts the values of table limits.\n\n  @details Adjusts the values of table fields controlling the sizes of\n  subtables and computed table. If the computed table is too small\n  according to the new values, it is resized.\n\n  @sideeffect Modifies manager fields. May resize computed table.\n\n*/\nstatic void\nddFixLimits(\n  DdManager *unique)\n{\n    unique->minDead = (unsigned) (unique->gcFrac * (double) unique->slots);\n    unique->cacheSlack = (int) ddMin(unique->maxCacheHard,\n\tDD_MAX_CACHE_TO_SLOTS_RATIO * unique->slots) -\n\t2 * (int) unique->cacheSlots;\n    if (unique->cacheSlots < unique->slots/2 && unique->cacheSlack >= 0)\n\tcuddCacheResize(unique);\n    return;\n\n} /* end of ddFixLimits */\n\n\n#ifndef DD_UNSORTED_FREE_LIST\n#ifdef DD_RED_BLACK_FREE_LIST\n/**\n  @brief Inserts a DdNode in a red/black search tree.\n\n  @details Nodes from the same \"page\" (defined by DD_PAGE_MASK) are\n  linked in a LIFO list.\n\n  @sideeffect None\n\n  @see cuddOrderedThread\n\n*/\nstatic void\ncuddOrderedInsert(\n  DdNodePtr * root,\n  DdNodePtr node)\n{\n    DdNode *scan;\n    DdNodePtr *scanP;\n    DdNodePtr *stack[DD_STACK_SIZE];\n    int stackN = 0;\n\n    scanP = root;\n    while ((scan = *scanP) != NULL) {\n\tstack[stackN++] = scanP;\n\tif (DD_INSERT_COMPARE(node, scan) == 0) { /* add to page list */\n\t    DD_NEXT(node) = DD_NEXT(scan);\n\t    DD_NEXT(scan) = node;\n\t    return;\n\t}\n\tscanP = (node < scan) ? &DD_LEFT(scan) : &DD_RIGHT(scan);\n    }\n    DD_RIGHT(node) = DD_LEFT(node) = DD_NEXT(node) = NULL;\n    DD_COLOR(node) = DD_RED;\n    *scanP = node;\n    stack[stackN] = &node;\n    cuddDoRebalance(stack,stackN);\n\n} /* end of cuddOrderedInsert */\n\n\n/**\n  @brief Threads all the nodes of a search tree into a linear list.\n\n  @details For each node of the search tree, the \"left\" child, if\n  non-null, has a lower address than its parent, and the \"right\"\n  child, if non-null, has a higher address than its parent.  The list\n  is sorted in order of increasing addresses. The search tree is\n  destroyed as a result of this operation. The last element of the\n  linear list is made to point to the address passed in list. Each\n  node if the search tree is a linearly-linked list of nodes from the\n  same memory page (as defined in DD_PAGE_MASK). When a node is added\n  to the linear list, all the elements of the linked list are added.\n\n  @sideeffect The search tree is destroyed as a result of this operation.\n\n  @see cuddOrderedInsert\n\n*/\nstatic DdNode *\ncuddOrderedThread(\n  DdNode * root,\n  DdNode * list)\n{\n    DdNode *current, *next, *prev, *end;\n\n    current = root;\n    /* The first word in the node is used to implement a stack that holds\n    ** the nodes from the root of the tree to the current node. Here we\n    ** put the root of the tree at the bottom of the stack.\n    */\n    *((DdNodePtr *) current) = NULL;\n\n    while (current != NULL) {\n\tif (DD_RIGHT(current) != NULL) {\n\t    /* If possible, we follow the \"right\" link. Eventually we'll\n\t    ** find the node with the largest address in the current tree.\n\t    ** In this phase we use the first word of a node to implemen\n\t    ** a stack of the nodes on the path from the root to \"current\".\n\t    ** Also, we disconnect the \"right\" pointers to indicate that\n\t    ** we have already followed them.\n\t    */\n\t    next = DD_RIGHT(current);\n\t    DD_RIGHT(current) = NULL;\n\t    *((DdNodePtr *)next) = current;\n\t    current = next;\n\t} else {\n\t    /* We can't proceed along the \"right\" links any further.\n\t    ** Hence \"current\" is the largest element in the current tree.\n\t    ** We make this node the new head of \"list\". (Repeating this\n\t    ** operation until the tree is empty yields the desired linear\n\t    ** threading of all nodes.)\n\t    */\n\t    prev = *((DdNodePtr *) current); /* save prev node on stack in prev */\n\t    /* Traverse the linked list of current until the end. */\n\t    for (end = current; DD_NEXT(end) != NULL; end = DD_NEXT(end));\n\t    DD_NEXT(end) = list; /* attach \"list\" at end and make */\n\t    list = current;   /* \"current\" the new head of \"list\" */\n\t    /* Now, if current has a \"left\" child, we push it on the stack.\n\t    ** Otherwise, we just continue with the parent of \"current\".\n\t    */\n\t    if (DD_LEFT(current) != NULL) {\n\t\tnext = DD_LEFT(current);\n\t\t*((DdNodePtr *) next) = prev;\n\t\tcurrent = next;\n\t    } else {\n\t\tcurrent = prev;\n\t    }\n\t}\n    }\n\n    return(list);\n\n} /* end of cuddOrderedThread */\n\n\n/**\n  @brief Performs the left rotation for red/black trees.\n\n  @sideeffect None\n\n  @see cuddRotateRight\n\n*/\nstatic void\ncuddRotateLeft(\n  DdNodePtr * nodeP)\n{\n    DdNode *newRoot;\n    DdNode *oldRoot = *nodeP;\n\n    *nodeP = newRoot = DD_RIGHT(oldRoot);\n    DD_RIGHT(oldRoot) = DD_LEFT(newRoot);\n    DD_LEFT(newRoot) = oldRoot;\n\n} /* end of cuddRotateLeft */\n\n\n/**\n  @brief Performs the right rotation for red/black trees.\n\n  @sideeffect None\n\n  @see cuddRotateLeft\n\n*/\nstatic void\ncuddRotateRight(\n  DdNodePtr * nodeP)\n{\n    DdNode *newRoot;\n    DdNode *oldRoot = *nodeP;\n\n    *nodeP = newRoot = DD_LEFT(oldRoot);\n    DD_LEFT(oldRoot) = DD_RIGHT(newRoot);\n    DD_RIGHT(newRoot) = oldRoot;\n\n} /* end of cuddRotateRight */\n\n\n/**\n  @brief Rebalances a red/black tree.\n\n  @sideeffect None\n\n*/\nstatic void\ncuddDoRebalance(\n  DdNodePtr ** stack,\n  int  stackN)\n{\n    DdNodePtr *xP, *parentP, *grandpaP;\n    DdNode *x, *y, *parent, *grandpa;\n\n    xP = stack[stackN];\n    x = *xP;\n    /* Work our way back up, re-balancing the tree. */\n    while (--stackN >= 0) {\n\tparentP = stack[stackN];\n\tparent = *parentP;\n\tif (DD_IS_BLACK(parent)) break;\n\t/* Since the root is black, here a non-null grandparent exists. */\n\tgrandpaP = stack[stackN-1];\n\tgrandpa = *grandpaP;\n\tif (parent == DD_LEFT(grandpa)) {\n\t    y = DD_RIGHT(grandpa);\n\t    if (y != NULL && DD_IS_RED(y)) {\n\t\tDD_COLOR(parent) = DD_BLACK;\n\t\tDD_COLOR(y) = DD_BLACK;\n\t\tDD_COLOR(grandpa) = DD_RED;\n\t\tx = grandpa;\n\t\tstackN--;\n\t    } else {\n\t\tif (x == DD_RIGHT(parent)) {\n\t\t    cuddRotateLeft(parentP);\n\t\t    DD_COLOR(x) = DD_BLACK;\n\t\t} else {\n\t\t    DD_COLOR(parent) = DD_BLACK;\n\t\t}\n\t\tDD_COLOR(grandpa) = DD_RED;\n\t\tcuddRotateRight(grandpaP);\n\t\tbreak;\n\t    }\n\t} else {\n\t    y = DD_LEFT(grandpa);\n\t    if (y != NULL && DD_IS_RED(y)) {\n\t\tDD_COLOR(parent) = DD_BLACK;\n\t\tDD_COLOR(y) = DD_BLACK;\n\t\tDD_COLOR(grandpa) = DD_RED;\n\t\tx = grandpa;\n\t\tstackN--;\n\t    } else {\n\t\tif (x == DD_LEFT(parent)) {\n\t\t    cuddRotateRight(parentP);\n\t\t    DD_COLOR(x) = DD_BLACK;\n\t\t} else {\n\t\t    DD_COLOR(parent) = DD_BLACK;\n\t\t}\n\t\tDD_COLOR(grandpa) = DD_RED;\n\t\tcuddRotateLeft(grandpaP);\n\t    }\n\t}\n    }\n    DD_COLOR(*(stack[0])) = DD_BLACK;\n\n} /* end of cuddDoRebalance */\n#endif\n#endif\n\n\n/**\n  @brief Fixes a variable tree after the insertion of new subtables.\n\n  @details After such an insertion, the low fields of the tree below\n  the insertion point are inconsistent.\n\n  @sideeffect None\n\n*/\nstatic void\nddPatchTree(\n  DdManager *dd,\n  MtrNode *treenode)\n{\n    MtrNode *auxnode = treenode;\n\n    while (auxnode != NULL) {\n\tauxnode->low = dd->perm[auxnode->index];\n\tif (auxnode->child != NULL) {\n\t    ddPatchTree(dd, auxnode->child);\n\t}\n\tauxnode = auxnode->younger;\n    }\n\n    return;\n\n} /* end of ddPatchTree */\n\n\n#ifdef DD_DEBUG\n/**\n  @brief Checks whether a collision list is ordered.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddCheckCollisionOrdering(\n  DdManager *unique,\n  int i,\n  int j)\n{\n    DdNode *node, *next;\n    DdNodePtr *nodelist;\n    DdNode *sentinel = &(unique->sentinel);\n\n    nodelist = unique->subtables[i].nodelist;\n    node = nodelist[j];\n    if (node == sentinel) return(1);\n    next = node->next;\n    while (next != sentinel) {\n\tif (cuddT(node) < cuddT(next) ||\n\t    (cuddT(node) == cuddT(next) && cuddE(node) < cuddE(next))) {\n\t    (void) fprintf(unique->err,\n\t\t\t   \"Unordered list: index %u, position %d\\n\", i, j);\n\t    return(0);\n\t}\n\tnode = next;\n\tnext = node->next;\n    }\n    return(1);\n\n} /* end of cuddCheckCollisionOrdering */\n#endif\n\n\n\n\n/**\n  @brief Reports problem in garbage collection.\n\n  @sideeffect None\n\n  @see cuddGarbageCollect cuddGarbageCollectZdd\n\n*/\nstatic void\nddReportRefMess(\n  DdManager *unique /**< manager */,\n  int i /**< table in which the problem occurred */,\n  const char *caller /**< procedure that detected the problem */)\n{\n    if (i == CUDD_CONST_INDEX) {\n\t(void) fprintf(unique->err,\n\t\t\t   \"%s: problem in constants\\n\", caller);\n    } else if (i != -1) {\n\t(void) fprintf(unique->err,\n\t\t\t   \"%s: problem in table %d\\n\", caller, i);\n    }\n    (void) fprintf(unique->err, \"  dead count != deleted\\n\");\n    (void) fprintf(unique->err, \"  This problem is often due to a missing \\\ncall to Cudd_Ref\\n  or to an extra call to Cudd_RecursiveDeref.\\n  \\\nSee the CUDD Programmer's Guide for additional details.\");\n    abort();\n\n} /* end of ddReportRefMess */\n"
  },
  {
    "path": "cudd/cudd/cuddUtil.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Utility functions.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include <stddef.h>\n#include <float.h>\n#include \"util.h\"\n#include \"epdInt.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* Random generator constants. */\n#define MODULUS1 2147483563\n#define LEQA1 40014\n#define LEQQ1 53668\n#define LEQR1 12211\n#define MODULUS2 2147483399\n#define LEQA2 40692\n#define LEQQ2 52774\n#define LEQR2 3791\n#define STAB_DIV (1 + (MODULUS1 - 1) / STAB_SIZE)\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#define bang(f)\t((Cudd_IsComplement(f)) ? '!' : ' ')\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int dp2 (DdManager *dd, DdNode *f, st_table *t);\nstatic void ddPrintMintermAux (DdManager *dd, DdNode *node, int *list);\nstatic int ddDagInt (DdNode *n);\nstatic int cuddNodeArrayRecur (DdNode *f, DdNodePtr *table, int index);\nstatic int cuddEstimateCofactor (DdManager *dd, st_table *table, DdNode * node, int i, int phase, DdNode ** ptr);\nstatic DdNode * cuddUniqueLookup (DdManager * unique, int  index, DdNode * T, DdNode * E);\nstatic int cuddEstimateCofactorSimple (DdNode * node, int i);\nstatic double ddCountMintermAux (DdManager *dd, DdNode *node, double max, DdHashTable *table);\nstatic int ddEpdCountMintermAux (DdManager const *dd, DdNode *node, EpDouble *max, EpDouble *epd, st_table *table);\nstatic long double ddLdblCountMintermAux(DdManager const *manager, DdNode *node, long double max, st_table *table);\nstatic double ddCountPathAux (DdNode *node, st_table *table);\nstatic double ddCountPathsToNonZero (DdNode * N, st_table * table);\nstatic void ddSupportStep (DdNode *f, int *support);\nstatic void ddClearFlag (DdNode *f);\nstatic int ddLeavesInt (DdNode *n);\nstatic int ddPickArbitraryMinterms (DdManager *dd, DdNode *node, int nvars, int nminterms, char **string);\nstatic int ddPickRepresentativeCube (DdManager *dd, DdNode *node, double *weight, char *string);\nstatic enum st_retval ddEpdFree (void * key, void * value, void * arg);\nstatic void ddFindSupport(DdManager *dd, DdNode *f, int *SP);\nstatic void ddClearVars(DdManager *dd, int SP);\nstatic int indexCompare(const void *a, const void *b);\nstatic enum st_retval ddLdblFree(void * key, void * value, void * arg);\n#if HAVE_POWL != 1\nstatic long double powl(long double base, long double exponent);\n#endif\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints a disjoint sum of products.\n\n  @details Prints a disjoint sum of product cover for the function\n  rooted at node. Each product corresponds to a path from node to a\n  leaf node different from the logical zero, and different from the\n  background value. Uses the package default output file.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_PrintDebug Cudd_bddPrintCover\n\n*/\nint\nCudd_PrintMinterm(\n  DdManager * manager,\n  DdNode * node)\n{\n    int\t\ti, *list;\n\n    list = ALLOC(int,manager->size);\n    if (list == NULL) {\n\tmanager->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (i = 0; i < manager->size; i++) list[i] = 2;\n    ddPrintMintermAux(manager,node,list);\n    FREE(list);\n    return(1);\n\n} /* end of Cudd_PrintMinterm */\n\n\n/**\n  @brief Prints a sum of prime implicants of a %BDD.\n\n  @details Prints a sum of product cover for an incompletely\n  specified function given by a lower bound and an upper bound.  Each\n  product is a prime implicant obtained by expanding the product\n  corresponding to a path from node to the constant one.  Uses the\n  package default output file.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_PrintMinterm\n\n*/\nint\nCudd_bddPrintCover(\n  DdManager *dd,\n  DdNode *l,\n  DdNode *u)\n{\n    int *array;\n    int q, result;\n    DdNode *lb;\n#ifdef DD_DEBUG\n    DdNode *cover;\n#endif\n\n    array = ALLOC(int, Cudd_ReadSize(dd));\n    if (array == NULL) return(0);\n    lb = l;\n    cuddRef(lb);\n#ifdef DD_DEBUG\n    cover = Cudd_ReadLogicZero(dd);\n    cuddRef(cover);\n#endif\n    while (lb != Cudd_ReadLogicZero(dd)) {\n\tDdNode *implicant, *prime, *tmp;\n\tint length;\n\timplicant = Cudd_LargestCube(dd,lb,&length);\n\tif (implicant == NULL) {\n\t    Cudd_RecursiveDeref(dd,lb);\n\t    FREE(array);\n\t    return(0);\n\t}\n\tcuddRef(implicant);\n\tprime = Cudd_bddMakePrime(dd,implicant,u);\n\tif (prime == NULL) {\n\t    Cudd_RecursiveDeref(dd,lb);\n\t    Cudd_RecursiveDeref(dd,implicant);\n\t    FREE(array);\n\t    return(0);\n\t}\n\tcuddRef(prime);\n\tCudd_RecursiveDeref(dd,implicant);\n\ttmp = Cudd_bddAnd(dd,lb,Cudd_Not(prime));\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDeref(dd,lb);\n\t    Cudd_RecursiveDeref(dd,prime);\n\t    FREE(array);\n\t    return(0);\n\t}\n\tcuddRef(tmp);\n\tCudd_RecursiveDeref(dd,lb);\n\tlb = tmp;\n\tresult = Cudd_BddToCubeArray(dd,prime,array);\n\tif (result == 0) {\n\t    Cudd_RecursiveDeref(dd,lb);\n\t    Cudd_RecursiveDeref(dd,prime);\n\t    FREE(array);\n\t    return(0);\n\t}\n\tfor (q = 0; q < dd->size; q++) {\n\t    switch (array[q]) {\n\t    case 0:\n\t\t(void) fprintf(dd->out, \"0\");\n\t\tbreak;\n\t    case 1:\n\t\t(void) fprintf(dd->out, \"1\");\n\t\tbreak;\n\t    case 2:\n\t\t(void) fprintf(dd->out, \"-\");\n\t\tbreak;\n\t    default:\n\t\t(void) fprintf(dd->out, \"?\");\n\t    }\n\t}\n\t(void) fprintf(dd->out, \" 1\\n\");\n#ifdef DD_DEBUG\n\ttmp = Cudd_bddOr(dd,prime,cover);\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDeref(dd,cover);\n\t    Cudd_RecursiveDeref(dd,lb);\n\t    Cudd_RecursiveDeref(dd,prime);\n\t    FREE(array);\n\t    return(0);\n\t}\n\tcuddRef(tmp);\n\tCudd_RecursiveDeref(dd,cover);\n\tcover = tmp;\n#endif\n\tCudd_RecursiveDeref(dd,prime);\n    }\n    (void) fprintf(dd->out, \"\\n\");\n    Cudd_RecursiveDeref(dd,lb);\n    FREE(array);\n#ifdef DD_DEBUG\n    if (!Cudd_bddLeq(dd,cover,u) || !Cudd_bddLeq(dd,l,cover)) {\n\tCudd_RecursiveDeref(dd,cover);\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,cover);\n#endif\n    return(1);\n\n} /* end of Cudd_bddPrintCover */\n\n\n/**\n  @brief Prints to the manager standard output a %DD and its statistics.\n\n  @details The statistics include the number of nodes, the number of leaves,\n  and the number of minterms. (The number of minterms is the number of\n  assignments to the variables that cause the function to be different\n  from the logical zero (for BDDs) and from the background value (for\n  ADDs.) The statistics are printed if pr &gt; 0. Specifically:\n  <ul>\n  <li> pr = 0 : prints nothing\n  <li> pr = 1 : prints counts of nodes and minterms\n  <li> pr = 2 : prints counts + disjoint sum of product\n  <li> pr = 3 : prints counts + list of nodes\n  <li> pr &gt; 3 : prints counts + disjoint sum of product + list of nodes\n  </ul>\n  For the purpose of counting the number of minterms, the function is\n  supposed to depend on n variables.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_DagSize Cudd_CountLeaves Cudd_CountMinterm\n  Cudd_PrintMinterm\n\n*/\nint\nCudd_PrintDebug(\n  DdManager * dd,\n  DdNode * f,\n  int  n,\n  int  pr)\n{\n    DdNode *azero, *bzero;\n    int\t   nodes;\n    int\t   leaves;\n    double minterms;\n    int    retval = 1;\n\n    if (dd == NULL) {\n\treturn(0);\n    }\n    if (f == NULL) {\n\t(void) fprintf(dd->out,\": is the NULL DD\\n\");\n\t(void) fflush(dd->out);\n        dd->errorCode = CUDD_INVALID_ARG;\n\treturn(0);\n    }\n    azero = DD_ZERO(dd);\n    bzero = Cudd_Not(DD_ONE(dd));\n    if ((f == azero || f == bzero) && pr > 0){\n       (void) fprintf(dd->out,\": is the zero DD\\n\");\n       (void) fflush(dd->out);\n       return(1);\n    }\n    if (pr > 0) {\n\tnodes = Cudd_DagSize(f);\n\tif (nodes == CUDD_OUT_OF_MEM) retval = 0;\n\tleaves = Cudd_CountLeaves(f);\n\tif (leaves == CUDD_OUT_OF_MEM) retval = 0;\n\tminterms = Cudd_CountMinterm(dd, f, n);\n\tif (minterms == (double)CUDD_OUT_OF_MEM) {\n            retval = 0;\n            (void) fprintf(dd->out,\": %d nodes %d leaves unknown minterms\\n\",\n                           nodes, leaves);\n        } else {\n            (void) fprintf(dd->out,\": %d nodes %d leaves %g minterms\\n\",\n                           nodes, leaves, minterms);\n        }\n\tif (pr > 2) {\n\t    if (!cuddP(dd, f)) retval = 0;\n\t}\n\tif (pr == 2 || pr > 3) {\n\t    if (!Cudd_PrintMinterm(dd,f)) retval = 0;\n\t    (void) fprintf(dd->out,\"\\n\");\n\t}\n\t(void) fflush(dd->out);\n    }\n    return(retval);\n\n} /* end of Cudd_PrintDebug */\n\n\n/**\n  @brief Prints a one-line summary of an %ADD or %BDD to the manager stdout.\n\n  @details The summary includes the number of nodes, the number of leaves,\n  and the number of minterms.  The number of minterms is computed with\n  arbitrary precision unlike Cudd_PrintDebug().  For the purpose of counting\n  minterms, the function `f` is supposed to depend on `n` variables.\n\n  @return 1 if successful; 0 otherwise.\n\n  @see Cudd_PrintDebug Cudd_ApaPrintMinterm Cudd_ApaPrintMintermExp\n*/\nint\nCudd_PrintSummary(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< %DD to be summarized */,\n  int n /**< number of variables for minterm computation */,\n  int mode /**< integer (0) or exponential (1) format */)\n{\n    DdNode *azero, *bzero;\n    int\tnodes, leaves, digits;\n    int retval = 1;\n    DdApaNumber count;\n\n    if (dd == NULL) {\n        return(0);\n    }\n    if (f == NULL) {\n\t(void) fprintf(dd->out,\": is the NULL DD\\n\");\n\t(void) fflush(dd->out);\n        dd->errorCode = CUDD_INVALID_ARG;\n\treturn(0);\n    }\n    azero = DD_ZERO(dd);\n    bzero = Cudd_Not(DD_ONE(dd));\n    if (f == azero || f == bzero){\n        (void) fprintf(dd->out,\": is the zero DD\\n\");\n        (void) fflush(dd->out);\n        return(1);\n    }\n    nodes = Cudd_DagSize(f);\n    if (nodes == CUDD_OUT_OF_MEM) retval = 0;\n    leaves = Cudd_CountLeaves(f);\n    if (leaves == CUDD_OUT_OF_MEM) retval = 0;\n    (void) fprintf(dd->out,\": %d nodes %d leaves \", nodes, leaves);\n    count = Cudd_ApaCountMinterm(dd, f, n, &digits);\n    if (count == NULL) {\n\tretval = 0;\n    } else if (mode) {\n        if (!Cudd_ApaPrintExponential(dd->out, digits, count, 6))\n            retval = 0;\n    } else {\n        if (!Cudd_ApaPrintDecimal(dd->out, digits, count))\n            retval = 0;\n    }\n    FREE(count);\n    (void) fprintf(dd->out, \" minterms\\n\");\n    (void) fflush(dd->out);\n    return(retval);\n\n} /* end of Cudd_PrintSummary */\n  \n\n/**\n  @brief Counts the number of nodes in a %DD.\n\n  @return the number of nodes in the graph rooted at node.\n\n  @sideeffect None\n\n  @see Cudd_SharingSize Cudd_PrintDebug\n\n*/\nint\nCudd_DagSize(\n  DdNode * node)\n{\n    int\ti;\n\n    i = ddDagInt(Cudd_Regular(node));\n    ddClearFlag(Cudd_Regular(node));\n\n    return(i);\n\n} /* end of Cudd_DagSize */\n\n\n/**\n  @brief Estimates the number of nodes in a cofactor of a %DD.\n\n  @details This function uses a refinement of the algorithm of Cabodi\n  et al.  (ICCAD96). The refinement allows the procedure to account\n  for part of the recombination that may occur in the part of the\n  cofactor above the cofactoring variable. This procedure does not\n  create any new node.  It does keep a small table of results;\n  therefore it may run out of memory.  If this is a concern, one\n  should use Cudd_EstimateCofactorSimple, which is faster, does not\n  allocate any memory, but is less accurate.\n\n  @return an estimate of the number of nodes in a cofactor of the\n  graph rooted at node with respect to the variable whose index is i.\n  In case of failure, returns CUDD_OUT_OF_MEM.\n\n  @sideeffect None\n\n  @see Cudd_DagSize Cudd_EstimateCofactorSimple\n\n*/\nint\nCudd_EstimateCofactor(\n  DdManager *dd /**< manager */,\n  DdNode * f\t/**< function */,\n  int i\t\t/**< index of variable */,\n  int phase\t/**< 1: positive; 0: negative */\n  )\n{\n    int\tval;\n    DdNode *ptr;\n    st_table *table;\n\n    table = st_init_table(st_ptrcmp,st_ptrhash);\n    if (table == NULL) {\n        dd->errorCode = CUDD_MEMORY_OUT;\n        return(CUDD_OUT_OF_MEM);\n    }\n    val = cuddEstimateCofactor(dd,table,Cudd_Regular(f),i,phase,&ptr);\n    ddClearFlag(Cudd_Regular(f));\n    st_free_table(table);\n    if (val == CUDD_OUT_OF_MEM)\n        dd->errorCode = CUDD_MEMORY_OUT;\n    \n    return(val);\n\n} /* end of Cudd_EstimateCofactor */\n\n\n/**\n  @brief Estimates the number of nodes in a cofactor of a %DD.\n\n  @details Returns an estimate of the number of nodes in the positive\n  cofactor of the graph rooted at node with respect to the variable\n  whose index is i.  This procedure implements with minor changes the\n  algorithm of Cabodi et al.  (ICCAD96). It does not allocate any\n  memory, it does not change the state of the manager, and it is\n  fast. However, it has been observed to overestimate the size of the\n  cofactor by as much as a factor of 2.\n\n  @sideeffect None\n\n  @see Cudd_DagSize\n\n*/\nint\nCudd_EstimateCofactorSimple(\n  DdNode * node,\n  int i)\n{\n    int\tval;\n\n    val = cuddEstimateCofactorSimple(Cudd_Regular(node),i);\n    ddClearFlag(Cudd_Regular(node));\n\n    return(val);\n\n} /* end of Cudd_EstimateCofactorSimple */\n\n\n/**\n  @brief Counts the number of nodes in an array of DDs.\n\n  @details Shared nodes are counted only once.\n\n  @return the total number of nodes.\n\n  @sideeffect None\n\n  @see Cudd_DagSize\n\n*/\nint\nCudd_SharingSize(\n  DdNode ** nodeArray,\n  int  n)\n{\n    int\ti,j;\n\n    i = 0;\n    for (j = 0; j < n; j++) {\n\ti += ddDagInt(Cudd_Regular(nodeArray[j]));\n    }\n    for (j = 0; j < n; j++) {\n\tddClearFlag(Cudd_Regular(nodeArray[j]));\n    }\n    return(i);\n\n} /* end of Cudd_SharingSize */\n\n\n/**\n  @brief Counts the minterms of an %ADD or %BDD.\n\n  @details The function is assumed to depend on `nvars` variables. The\n  minterm count is represented as a double; hence overflow is\n  possible.  For functions with many variables (more than 1023 if\n  floating point conforms to IEEE 754), one should consider\n  Cudd_ApaCountMinterm() or Cudd_EpdCountMinterm().\n\n  @return the number of minterms of the function rooted at node if\n  successful; +infinity if the number of minterms is known to be larger\n  than the maximum value representable as a double; `(double) CUDD_OUT_OF_MEM`\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_ApaCountMinterm Cudd_EpdCountMinterm Cudd_LdblCountMinterm\n  Cudd_PrintDebug Cudd_CountPath\n\n*/\ndouble\nCudd_CountMinterm(\n  DdManager * manager,\n  DdNode * node,\n  int  nvars)\n{\n    double\tmax;\n    DdHashTable\t*table;\n    double\tres;\n    CUDD_VALUE_TYPE epsilon;\n\n    /* PRISM modification:\n     * Revert to CUDD 2.5.1 behaviour (unscaled max).\n     * To enable CUDD 3.0.0 behaviour, define CUDD_COUNT_MINTERM_3_0_0\n     */\n\n#ifdef CUDD_COUNT_MINTERM_3_0_0\n    /* Scale the maximum number of minterm.  This is done in an attempt\n     * to deal with functions that depend on more than 1023, but less\n     * than 2044 variables and don't have too many minterms.\n     */\n    max = pow(2.0,(double)(nvars + DBL_MIN_EXP));\n#else  // !CUDD_COUNT_MINTERM_3_0_0\n    max = pow(2.0,(double)nvars);\n#endif\n    if (max >= DD_PLUS_INF_VAL) {\n        return((double)CUDD_OUT_OF_MEM);\n    }\n    table = cuddHashTableInit(manager,1,2);\n    if (table == NULL) {\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    /* Temporarily set epsilon to 0 to avoid rounding errors. */\n    epsilon = Cudd_ReadEpsilon(manager);\n    Cudd_SetEpsilon(manager,(CUDD_VALUE_TYPE)0.0);\n    res = ddCountMintermAux(manager,node,max,table);\n    cuddHashTableQuit(table);\n    Cudd_SetEpsilon(manager,epsilon);\n#ifdef CUDD_COUNT_MINTERM_3_0_0\n    if (res == (double)CUDD_OUT_OF_MEM) {\n        return((double)CUDD_OUT_OF_MEM);\n    } else if (res >= pow(2.0,(double)(DBL_MAX_EXP + DBL_MIN_EXP))) {\n        /* Minterm count is too large to be scaled back. */\n        return(DD_PLUS_INF_VAL);\n    } else {\n        /* Undo the scaling. */\n        res *= pow(2.0,(double)-DBL_MIN_EXP);\n        return(res);\n    }\n#else  // !CUDD_COUNT_MINTERM_3_0_0\n    if (res == (double)CUDD_OUT_OF_MEM) {\n        return((double)CUDD_OUT_OF_MEM);\n    } else {\n        return(res);\n    }\n#endif\n\n} /* end of Cudd_CountMinterm */\n\n\n/**\n  @brief Counts the paths of a %DD.\n\n  @details Paths to all terminal nodes are counted. The path count is\n  represented as a double; hence overflow is possible.\n\n  @return the number of paths of the function rooted at node if\n  successful; `(double) CUDD_OUT_OF_MEM` otherwise.\n\n  @sideeffect None\n\n  @see Cudd_CountMinterm\n\n*/\ndouble\nCudd_CountPath(\n  DdNode * node)\n{\n\n    st_table\t*table;\n    double\ti;\n\n    table = st_init_table(st_ptrcmp,st_ptrhash);\n    if (table == NULL) {\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    i = ddCountPathAux(Cudd_Regular(node),table);\n    st_foreach(table, cuddStCountfree, NULL);\n    st_free_table(table);\n    return(i);\n\n} /* end of Cudd_CountPath */\n\n\n/**\n  @brief Counts the minterms of an %ADD or %BDD with extended range.\n\n  @details The function is assumed to depend on `nvars` variables. The\n  minterm count is represented as an `EpDouble`, to allow for any\n  number of variables.\n\n  @return 0 if successful; `CUDD_OUT_OF_MEM` otherwise.\n\n  @sideeffect None\n\n  @see Cudd_CountMinterm Cudd_LdblCountMinterm Cudd_ApaCountMinterm\n  Cudd_PrintDebug Cudd_CountPath\n\n*/\nint\nCudd_EpdCountMinterm(\n  DdManager const * manager,\n  DdNode * node,\n  int  nvars,\n  EpDouble * epd)\n{\n    EpDouble\tmax, tmp;\n    st_table\t*table;\n    int\t\tstatus;\n\n    EpdPow2(nvars, &max);\n    table = st_init_table(st_ptrcmp, st_ptrhash);\n    if (table == NULL) {\n\tEpdMakeZero(epd, 0);\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    status = ddEpdCountMintermAux(manager,Cudd_Regular(node),&max,epd,table);\n    st_foreach(table, ddEpdFree, NULL);\n    st_free_table(table);\n    if (status == CUDD_OUT_OF_MEM) {\n\tEpdMakeZero(epd, 0);\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    if (Cudd_IsComplement(node)) {\n\tEpdSubtract3(&max, epd, &tmp);\n\tEpdCopy(&tmp, epd);\n    }\n    return(0);\n\n} /* end of Cudd_EpdCountMinterm */\n\n\n/**\n  @brief Returns the number of minterms of aa %ADD or %BDD as a long double.\n\n  @details On systems where double and long double are the same type,\n  Cudd_CountMinterm() is preferable.  On systems where long double values\n  have 15-bit exponents, this function avoids overflow for up to 16383\n  variables.  It applies scaling to try to avoid overflow when the number of\n  variables is larger than 16383, but smaller than 32764.\n\n  @return The nimterm count if successful; +infinity if the number is known to\n  be too large for representation as a long double;\n  `(long double)CUDD_OUT_OF_MEM` otherwise. \n\n  @see Cudd_CountMinterm Cudd_EpdCountMinterm Cudd_ApaCountMinterm\n*/\nlong double\nCudd_LdblCountMinterm(\n  DdManager const *manager,\n  DdNode *node,\n  int nvars)\n{\n    long double max, count;\n    st_table *table;\n\n    max = powl(2.0L, (long double) (nvars+LDBL_MIN_EXP));\n    if (max == HUGE_VALL) {\n        return((long double)CUDD_OUT_OF_MEM);\n    }\n    table = st_init_table(st_ptrcmp, st_ptrhash);\n    if (table == NULL) {\n        return((long double)CUDD_OUT_OF_MEM);\n    }\n    count = ddLdblCountMintermAux(manager, Cudd_Regular(node), max, table);\n    st_foreach(table, ddLdblFree, NULL);\n    st_free_table(table);\n    if (count == (long double)CUDD_OUT_OF_MEM) {\n        return((long double)CUDD_OUT_OF_MEM);\n    }\n    if (Cudd_IsComplement(node)) {\n        count = max - count;\n    }\n    if (count >= powl(2.0L, (long double)(LDBL_MAX_EXP + LDBL_MIN_EXP))) {\n        /* Minterm count is too large to be scaled back. */\n        return(HUGE_VALL);\n    } else {\n        /* Undo the scaling. */\n        count *= powl(2.0L,(long double)-LDBL_MIN_EXP);\n        return(count);\n    }\n\n} /* end of Cudd_LdlbCountMinterm */\n\n\n/**\n  @brief Prints the number of minterms of an %ADD or %BDD with extended range.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_EpdCountMinterm Cudd_ApaPrintMintermExp\n\n*/\nint\nCudd_EpdPrintMinterm(\n  DdManager const * dd,\n  DdNode * node,\n  int nvars)\n{\n    EpDouble epd;\n    int ret;\n    char pstring[128];\n\n    ret = Cudd_EpdCountMinterm(dd, node, nvars, &epd);\n    if (ret !=0) return(0);\n    EpdGetString(&epd, pstring);\n    fprintf(dd->out, \"%s\", pstring);\n    return(1);\n\n} /* end of Cudd_EpdPrintMinterm */\n\n\n/**\n  @brief Counts the paths to a non-zero terminal of a %DD.\n\n  @details The path count is represented as a double; hence overflow is\n  possible.\n\n  @return the number of paths of the function rooted at node.\n\n  @sideeffect None\n\n  @see Cudd_CountMinterm Cudd_CountPath\n\n*/\ndouble\nCudd_CountPathsToNonZero(\n  DdNode * node)\n{\n\n    st_table\t*table;\n    double\ti;\n\n    table = st_init_table(st_ptrcmp,st_ptrhash);\n    if (table == NULL) {\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    i = ddCountPathsToNonZero(node,table);\n    st_foreach(table, cuddStCountfree, NULL);\n    st_free_table(table);\n    return(i);\n\n} /* end of Cudd_CountPathsToNonZero */\n\n\n/**\n  @brief Finds the variables on which a %DD depends.\n\n  @return the number of variables if successful; CUDD_OUT_OF_MEM\n  otherwise.\n\n  @sideeffect The indices of the support variables are returned as\n  side effects.  If the function is constant, no array is allocated.\n\n  @see Cudd_Support Cudd_SupportIndex Cudd_VectorSupportIndices\n\n*/\nint\nCudd_SupportIndices(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< %DD whose support is sought */,\n  int **indices /**< array containing (on return) the indices */)\n{\n    int SP = 0;\n\n    ddFindSupport(dd, Cudd_Regular(f), &SP);\n    ddClearFlag(Cudd_Regular(f));\n    ddClearVars(dd, SP);\n    if (SP > 0) {\n        int i;\n        *indices = ALLOC(int, SP);\n        if (*indices == NULL) {\n            dd->errorCode = CUDD_MEMORY_OUT;\n            return(CUDD_OUT_OF_MEM);\n        }\n\n        for (i = 0; i < SP; i++)\n            (*indices)[i] = (int) (ptrint) dd->stack[i];\n\n        util_qsort(*indices, SP, sizeof(int), indexCompare);\n    } else {\n        *indices = NULL;\n    }\n\n    return(SP);\n\n} /* end of Cudd_SupportIndices */\n\n\n/**\n  @brief Finds the variables on which a %DD depends.\n\n  @return a %BDD consisting of the product of the variables if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_VectorSupport Cudd_ClassifySupport\n\n*/\nDdNode *\nCudd_Support(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< %DD whose support is sought */)\n{\n    int\t*support;\n    DdNode *res;\n    int j;\n\n    int size = Cudd_SupportIndices(dd, f, &support);\n    if (size == CUDD_OUT_OF_MEM)\n        return(NULL);\n\n    /* Transform support from array of indices to cube. */\n    res = DD_ONE(dd);\n    cuddRef(res);\n    \n    for (j = size - 1; j >= 0; j--) { /* for each index bottom-up (almost) */\n        int index = support[j];\n        DdNode *var = dd->vars[index];\n        DdNode *tmp = Cudd_bddAnd(dd,res,var);\n        if (tmp == NULL) {\n            Cudd_RecursiveDeref(dd,res);\n            FREE(support);\n            return(NULL);\n        }\n        cuddRef(tmp);\n        Cudd_RecursiveDeref(dd,res);\n        res = tmp;\n    }\n\n    FREE(support);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_Support */\n\n\n/**\n  @brief Finds the variables on which a %DD depends.\n\n  @return an index array of the variables if successful; NULL\n  otherwise.  The size of the array equals the number of variables in\n  the manager.  Each entry of the array is 1 if the corresponding\n  variable is in the support of the %DD and 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Support Cudd_SupportIndices Cudd_ClassifySupport\n\n*/\nint *\nCudd_SupportIndex(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< %DD whose support is sought */)\n{\n    int\t*support;\n    int\ti;\n    int size;\n\n    /* Allocate and initialize support array for ddSupportStep. */\n    size = ddMax(dd->size, dd->sizeZ);\n    support = ALLOC(int,size);\n    if (support == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < size; i++) {\n\tsupport[i] = 0;\n    }\n\n    /* Compute support and clean up markers. */\n    ddSupportStep(Cudd_Regular(f),support);\n    ddClearFlag(Cudd_Regular(f));\n\n    return(support);\n\n} /* end of Cudd_SupportIndex */\n\n\n/**\n  @brief Counts the variables on which a %DD depends.\n\n  @return the variables on which a %DD depends.\n\n  @sideeffect None\n\n  @see Cudd_Support Cudd_SupportIndices\n\n*/\nint\nCudd_SupportSize(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< %DD whose support size is sought */)\n{\n    int SP = 0;\n\n    ddFindSupport(dd, Cudd_Regular(f), &SP);\n    ddClearFlag(Cudd_Regular(f));\n    ddClearVars(dd, SP);\n\n    return(SP);\n\n} /* end of Cudd_SupportSize */\n\n\n/**\n  @brief Finds the variables on which a set of DDs depends.\n\n  @details The set must contain either BDDs and ADDs, or ZDDs.\n\n  @return the number of variables if successful; CUDD_OUT_OF_MEM\n  otherwise.\n\n  @sideeffect The indices of the support variables are returned as\n  side effects.  If the function is constant, no array is allocated.\n\n  @see Cudd_Support Cudd_SupportIndex Cudd_VectorSupportIndices\n\n*/\nint\nCudd_VectorSupportIndices(\n  DdManager * dd /**< manager */,\n  DdNode ** F /**< %DD whose support is sought */,\n  int  n /**< size of the array */,\n  int **indices /**< array containing (on return) the indices */)\n{\n    int i;\n    int SP = 0;\n\n    /* Compute support and clean up markers. */\n    for (i = 0; i < n; i++) {\n\tddFindSupport(dd, Cudd_Regular(F[i]), &SP);\n    }\n    for (i = 0; i < n; i++) {\n\tddClearFlag(Cudd_Regular(F[i]));\n    }\n    ddClearVars(dd, SP);\n\n    if (SP > 0) {\n        *indices = ALLOC(int, SP);\n        if (*indices == NULL) {\n            dd->errorCode = CUDD_MEMORY_OUT;\n            return(CUDD_OUT_OF_MEM);\n        }\n\n        for (i = 0; i < SP; i++)\n            (*indices)[i] = (int) (ptrint) dd->stack[i];\n\n        util_qsort(*indices, SP, sizeof(int), indexCompare);\n    } else {\n        *indices = NULL;\n    }\n\n    return(SP);\n\n} /* end of Cudd_VectorSupportIndices */\n\n\n/**\n  @brief Finds the variables on which a set of DDs depends.\n\n  @details The set must contain either BDDs and ADDs, or ZDDs.\n\n  @return a %BDD consisting of the product of the variables if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Support Cudd_ClassifySupport\n\n*/\nDdNode *\nCudd_VectorSupport(\n  DdManager * dd /**< manager */,\n  DdNode ** F /**< array of DDs whose support is sought */,\n  int  n /**< size of the array */)\n{\n    int\t*support;\n    DdNode *res;\n    int\tj;\n    int size = Cudd_VectorSupportIndices(dd, F, n, &support);\n    if (size == CUDD_OUT_OF_MEM)\n        return(NULL);\n\n    /* Transform support from array of indices to cube. */\n    res = DD_ONE(dd);\n    cuddRef(res);\n    \n    for (j = size - 1; j >= 0; j--) { /* for each index bottom-up (almost) */\n        int index = support[j];\n        DdNode *var = dd->vars[index];\n        DdNode *tmp = Cudd_bddAnd(dd,res,var);\n        if (tmp == NULL) {\n            Cudd_RecursiveDeref(dd,res);\n            FREE(support);\n            return(NULL);\n        }\n        cuddRef(tmp);\n        Cudd_RecursiveDeref(dd,res);\n        res = tmp;\n    }\n\n    FREE(support);\n    cuddDeref(res);\n    return(res);\n\n} /* end of Cudd_VectorSupport */\n\n\n/**\n  @brief Finds the variables on which a set of DDs depends.\n\n  @details The set must contain either BDDs and ADDs, or ZDDs.\n\n  @return an index array of the variables if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_SupportIndex Cudd_VectorSupport Cudd_VectorSupportIndices\n\n*/\nint *\nCudd_VectorSupportIndex(\n  DdManager * dd /**< manager */,\n  DdNode ** F /**< array of DDs whose support is sought */,\n  int  n /**< size of the array */)\n{\n    int\t*support;\n    int\ti;\n    int size;\n\n    /* Allocate and initialize support array for ddSupportStep. */\n    size = ddMax(dd->size, dd->sizeZ);\n    support = ALLOC(int,size);\n    if (support == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < size; i++) {\n\tsupport[i] = 0;\n    }\n\n    /* Compute support and clean up markers. */\n    for (i = 0; i < n; i++) {\n\tddSupportStep(Cudd_Regular(F[i]),support);\n    }\n    for (i = 0; i < n; i++) {\n\tddClearFlag(Cudd_Regular(F[i]));\n    }\n\n    return(support);\n\n} /* end of Cudd_VectorSupportIndex */\n\n\n/**\n  @brief Counts the variables on which a set of DDs depends.\n\n  @details The set must contain either BDDs and ADDs, or ZDDs.\n\n  @return the number of variables on which a set of DDs depends.\n\n  @sideeffect None\n\n  @see Cudd_VectorSupport Cudd_SupportSize\n\n*/\nint\nCudd_VectorSupportSize(\n  DdManager * dd /**< manager */,\n  DdNode ** F /**< array of DDs whose support is sought */,\n  int  n /**< size of the array */)\n{\n    int i;\n    int SP = 0;\n\n    /* Compute support and clean up markers. */\n    for (i = 0; i < n; i++) {\n\tddFindSupport(dd, Cudd_Regular(F[i]), &SP);\n    }\n    for (i = 0; i < n; i++) {\n\tddClearFlag(Cudd_Regular(F[i]));\n    }\n    ddClearVars(dd, SP);\n\n    return(SP);\n\n} /* end of Cudd_VectorSupportSize */\n\n\n/**\n  @brief Classifies the variables in the support of two DDs.\n\n  @details Classifies the variables in the support of two DDs\n  <code>f</code> and <code>g</code>, depending on whether they appear\n  in both DDs, only in <code>f</code>, or only in <code>g</code>.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect The cubes of the three classes of variables are\n  returned as side effects.\n\n  @see Cudd_Support Cudd_VectorSupport\n\n*/\nint\nCudd_ClassifySupport(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< first %DD */,\n  DdNode * g /**< second %DD */,\n  DdNode ** common /**< cube of shared variables */,\n  DdNode ** onlyF /**< cube of variables only in f */,\n  DdNode ** onlyG /**< cube of variables only in g */)\n{\n    int\t*supportF, *supportG;\n    int\tfi, gi;\n    int sizeF, sizeG;\n\n    sizeF = Cudd_SupportIndices(dd, f, &supportF);\n    if (sizeF == CUDD_OUT_OF_MEM)\n        return(0);\n\n    sizeG = Cudd_SupportIndices(dd, g, &supportG);\n    if (sizeG == CUDD_OUT_OF_MEM) {\n        FREE(supportF);\n        return(0);\n    }\n\n    /* Classify variables and create cubes. This part of the procedure\n    ** relies on the sorting of the indices in the two support arrays.\n    */\n    *common = *onlyF = *onlyG = DD_ONE(dd);\n    cuddRef(*common); cuddRef(*onlyF); cuddRef(*onlyG);\n    fi = sizeF - 1;\n    gi = sizeG - 1;\n    while (fi >= 0 || gi >= 0) {\n        int indexF = fi >= 0 ? supportF[fi] : -1;\n        int indexG = gi >= 0 ? supportG[gi] : -1;\n        int index = ddMax(indexF, indexG);\n        DdNode *var = dd->vars[index];\n#ifdef DD_DEBUG\n        assert(index >= 0);\n#endif\n        if (indexF == indexG) {\n            DdNode *tmp = Cudd_bddAnd(dd,*common,var);\n\t    if (tmp == NULL) {\n\t\tCudd_RecursiveDeref(dd,*common);\n\t\tCudd_RecursiveDeref(dd,*onlyF);\n\t\tCudd_RecursiveDeref(dd,*onlyG);\n\t\tFREE(supportF); FREE(supportG);\n\t\treturn(0);\n\t    }\n\t    cuddRef(tmp);\n\t    Cudd_RecursiveDeref(dd,*common);\n\t    *common = tmp;\n            fi--;\n            gi--;\n        } else if (index == indexF) {\n\t    DdNode *tmp = Cudd_bddAnd(dd,*onlyF,var);\n\t    if (tmp == NULL) {\n\t\tCudd_RecursiveDeref(dd,*common);\n\t\tCudd_RecursiveDeref(dd,*onlyF);\n\t\tCudd_RecursiveDeref(dd,*onlyG);\n\t\tFREE(supportF); FREE(supportG);\n\t\treturn(0);\n\t    }\n\t    cuddRef(tmp);\n\t    Cudd_RecursiveDeref(dd,*onlyF);\n\t    *onlyF = tmp;\n            fi--;\n        } else { /* index == indexG */\n\t    DdNode *tmp = Cudd_bddAnd(dd,*onlyG,var);\n\t    if (tmp == NULL) {\n\t\tCudd_RecursiveDeref(dd,*common);\n\t\tCudd_RecursiveDeref(dd,*onlyF);\n\t\tCudd_RecursiveDeref(dd,*onlyG);\n\t\tFREE(supportF); FREE(supportG);\n\t\treturn(0);\n\t    }\n\t    cuddRef(tmp);\n\t    Cudd_RecursiveDeref(dd,*onlyG);\n\t    *onlyG = tmp;\n            gi--;\n        }\n    }\n\n    FREE(supportF); FREE(supportG);\n    cuddDeref(*common); cuddDeref(*onlyF); cuddDeref(*onlyG);\n    return(1);\n\n} /* end of Cudd_ClassifySupport */\n\n\n/**\n  @brief Counts the number of leaves in a %DD.\n\n  @return the number of leaves in the %DD rooted at node if successful;\n  CUDD_OUT_OF_MEM otherwise.\n\n  @sideeffect None\n\n  @see Cudd_PrintDebug\n\n*/\nint\nCudd_CountLeaves(\n  DdNode * node)\n{\n    int\ti;\n\n    i = ddLeavesInt(Cudd_Regular(node));\n    ddClearFlag(Cudd_Regular(node));\n    return(i);\n\n} /* end of Cudd_CountLeaves */\n\n\n/**\n  @brief Picks one on-set cube randomly from the given %DD.\n\n  @details The cube is written into an array of characters.  The array\n  must have at least as many entries as there are variables.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddPickOneMinterm\n\n*/\nint\nCudd_bddPickOneCube(\n  DdManager * ddm,\n  DdNode * node,\n  char * string)\n{\n    DdNode *N, *T, *E;\n    DdNode *one, *bzero;\n    char   dir;\n    int    i;\n\n    if (string == NULL || node == NULL) return(0);\n\n    /* The constant 0 function has no on-set cubes. */\n    one = DD_ONE(ddm);\n    bzero = Cudd_Not(one);\n    if (node == bzero) {\n        ddm->errorCode = CUDD_INVALID_ARG;\n        return(0);\n    }\n\n    for (i = 0; i < ddm->size; i++) string[i] = 2;\n\n    for (;;) {\n\n\tif (node == one) break;\n\n\tN = Cudd_Regular(node);\n\n\tT = cuddT(N); E = cuddE(N);\n\tif (Cudd_IsComplement(node)) {\n\t    T = Cudd_Not(T); E = Cudd_Not(E);\n\t}\n\tif (T == bzero) {\n\t    string[N->index] = 0;\n\t    node = E;\n\t} else if (E == bzero) {\n\t    string[N->index] = 1;\n\t    node = T;\n\t} else {\n\t    dir = (char) ((Cudd_Random(ddm) & 0x2000) >> 13);\n\t    string[N->index] = dir;\n\t    node = dir ? T : E;\n\t}\n    }\n    return(1);\n\n} /* end of Cudd_bddPickOneCube */\n\n\n/**\n  @brief Picks one on-set minterm randomly from the given %DD.\n\n  @details The minterm is in terms of <code>vars</code>. The array\n  <code>vars</code> should contain at least all variables in the\n  support of <code>f</code>; if this condition is not met the minterm\n  built by this procedure may not be contained in <code>f</code>.\n\n  @return a pointer to the %BDD for the minterm if successful; NULL otherwise.\n  There are three reasons why the procedure may fail:\n  <ul>\n  <li> It may run out of memory;\n  <li> the function <code>f</code> may be the constant 0;\n  <li> the minterm may not be contained in <code>f</code>.\n  </ul>\n\n  @sideeffect None\n\n  @see Cudd_bddPickOneCube\n\n*/\nDdNode *\nCudd_bddPickOneMinterm(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function from which to pick one minterm */,\n  DdNode ** vars /**< array of variables */,\n  int  n /**< size of <code>vars</code> */)\n{\n    char *string;\n    int i, size;\n    int *indices;\n    int result;\n    DdNode *old, *neW;\n\n    size = dd->size;\n    string = ALLOC(char, size);\n    if (string == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    indices = ALLOC(int,n);\n    if (indices == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(string);\n\treturn(NULL);\n    }\n\n    for (i = 0; i < n; i++) {\n\tindices[i] = vars[i]->index;\n    }\n\n    result = Cudd_bddPickOneCube(dd,f,string);\n    if (result == 0) {\n\tFREE(string);\n\tFREE(indices);\n\treturn(NULL);\n    }\n\n    /* Randomize choice for don't cares. */\n    for (i = 0; i < n; i++) {\n\tif (string[indices[i]] == 2)\n\t    string[indices[i]] = (char) ((Cudd_Random(dd) & 0x20) >> 5);\n    }\n\n    /* Build result BDD. */\n    old = Cudd_ReadOne(dd);\n    cuddRef(old);\n\n    for (i = n-1; i >= 0; i--) {\n\tneW = Cudd_bddAnd(dd,old,Cudd_NotCond(vars[i],string[indices[i]]==0));\n\tif (neW == NULL) {\n\t    FREE(string);\n\t    FREE(indices);\n\t    Cudd_RecursiveDeref(dd,old);\n\t    return(NULL);\n\t}\n\tcuddRef(neW);\n\tCudd_RecursiveDeref(dd,old);\n\told = neW;\n    }\n\n#ifdef DD_DEBUG\n    /* Test. */\n    if (Cudd_bddLeq(dd,old,f)) {\n\tcuddDeref(old);\n    } else {\n\tCudd_RecursiveDeref(dd,old);\n\told = NULL;\n    }\n#else\n    cuddDeref(old);\n#endif\n\n    FREE(string);\n    FREE(indices);\n    return(old);\n\n}  /* end of Cudd_bddPickOneMinterm */\n\n\n/**\n  @brief Picks k on-set minterms evenly distributed from given %DD.\n\n  @details The minterms are in terms of <code>vars</code>. The array\n  <code>vars</code> should contain at least all variables in the\n  support of <code>f</code>; if this condition is not met the minterms\n  built by this procedure may not be contained in <code>f</code>.\n\n  @return an array of BDDs for the minterms if successful; NULL otherwise.\n  There are three reasons why the procedure may fail:\n  <ul>\n  <li> It may run out of memory;\n  <li> the function <code>f</code> may be the constant 0;\n  <li> the minterms may not be contained in <code>f</code>.\n  </ul>\n\n  @sideeffect None\n\n  @see Cudd_bddPickOneMinterm Cudd_bddPickOneCube\n\n*/\nDdNode **\nCudd_bddPickArbitraryMinterms(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function from which to pick k minterms */,\n  DdNode ** vars /**< array of variables */,\n  int  n /**< size of <code>vars</code> */,\n  int  k /**< number of minterms to find */)\n{\n    char **string;\n    int i, j, l, size;\n    int *indices;\n    int result;\n    DdNode **old, *neW;\n    double minterms;\n    char *saveString;\n    int saveFlag, savePoint = 0, isSame;\n\n    minterms = Cudd_CountMinterm(dd,f,n);\n    if ((double)k > minterms) {\n\treturn(NULL);\n    }\n\n    size = dd->size;\n    string = ALLOC(char *, k);\n    if (string == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < k; i++) {\n\tstring[i] = ALLOC(char, size + 1);\n\tif (string[i] == NULL) {\n\t    for (j = 0; j < i; j++)\n\t\tFREE(string[i]);\n\t    FREE(string);\n\t    dd->errorCode = CUDD_MEMORY_OUT;\n\t    return(NULL);\n\t}\n\tfor (j = 0; j < size; j++) string[i][j] = '2';\n\tstring[i][size] = '\\0';\n    }\n    indices = ALLOC(int,n);\n    if (indices == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tfor (i = 0; i < k; i++)\n\t    FREE(string[i]);\n\tFREE(string);\n\treturn(NULL);\n    }\n\n    for (i = 0; i < n; i++) {\n\tindices[i] = vars[i]->index;\n    }\n\n    result = ddPickArbitraryMinterms(dd,f,n,k,string);\n    if (result == 0) {\n\tfor (i = 0; i < k; i++)\n\t    FREE(string[i]);\n\tFREE(string);\n\tFREE(indices);\n\treturn(NULL);\n    }\n\n    old = ALLOC(DdNode *, k);\n    if (old == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tfor (i = 0; i < k; i++)\n\t    FREE(string[i]);\n\tFREE(string);\n\tFREE(indices);\n\treturn(NULL);\n    }\n    saveString = ALLOC(char, size + 1);\n    if (saveString == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tfor (i = 0; i < k; i++)\n\t    FREE(string[i]);\n\tFREE(string);\n\tFREE(indices);\n\tFREE(old);\n\treturn(NULL);\n    }\n    saveFlag = 0;\n\n    /* Build result BDD array. */\n    for (i = 0; i < k; i++) {\n\tisSame = 0;\n\tif (!saveFlag) {\n\t    for (j = i + 1; j < k; j++) {\n\t\tif (strcmp(string[i], string[j]) == 0) {\n\t\t    savePoint = i;\n\t\t    strcpy(saveString, string[i]);\n\t\t    saveFlag = 1;\n\t\t    break;\n\t\t}\n\t    }\n\t} else {\n\t    if (strcmp(string[i], saveString) == 0) {\n\t\tisSame = 1;\n\t    } else {\n\t\tsaveFlag = 0;\n\t\tfor (j = i + 1; j < k; j++) {\n\t\t    if (strcmp(string[i], string[j]) == 0) {\n\t\t\tsavePoint = i;\n\t\t\tstrcpy(saveString, string[i]);\n\t\t\tsaveFlag = 1;\n\t\t\tbreak;\n\t\t    }\n\t\t}\n\t    }\n\t}\n\t/* Randomize choice for don't cares. */\n\tfor (j = 0; j < n; j++) {\n\t    if (string[i][indices[j]] == '2')\n\t\tstring[i][indices[j]] =\n\t\t  (char) ((Cudd_Random(dd) & 0x20) ? '1' : '0');\n\t}\n\n\twhile (isSame) {\n\t    isSame = 0;\n\t    for (j = savePoint; j < i; j++) {\n\t\tif (strcmp(string[i], string[j]) == 0) {\n\t\t    isSame = 1;\n\t\t    break;\n\t\t}\n\t    }\n\t    if (isSame) {\n\t\tstrcpy(string[i], saveString);\n\t\t/* Randomize choice for don't cares. */\n\t\tfor (j = 0; j < n; j++) {\n\t\t    if (string[i][indices[j]] == '2')\n\t\t\tstring[i][indices[j]] =\n\t\t\t  (char) ((Cudd_Random(dd) & 0x20) ? '1' : '0');\n\t\t}\n\t    }\n\t}\n\n\told[i] = Cudd_ReadOne(dd);\n\tcuddRef(old[i]);\n\n\tfor (j = 0; j < n; j++) {\n\t    if (string[i][indices[j]] == '0') {\n\t\tneW = Cudd_bddAnd(dd,old[i],Cudd_Not(vars[j]));\n\t    } else {\n\t\tneW = Cudd_bddAnd(dd,old[i],vars[j]);\n\t    }\n\t    if (neW == NULL) {\n\t\tFREE(saveString);\n\t\tfor (l = 0; l < k; l++)\n\t\t    FREE(string[l]);\n\t\tFREE(string);\n\t\tFREE(indices);\n\t\tfor (l = 0; l <= i; l++)\n\t\t    Cudd_RecursiveDeref(dd,old[l]);\n\t\tFREE(old);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(neW);\n\t    Cudd_RecursiveDeref(dd,old[i]);\n\t    old[i] = neW;\n\t}\n\n\t/* Test. */\n\tif (!Cudd_bddLeq(dd,old[i],f)) {\n\t    FREE(saveString);\n\t    for (l = 0; l < k; l++)\n\t\tFREE(string[l]);\n\t    FREE(string);\n\t    FREE(indices);\n\t    for (l = 0; l <= i; l++)\n\t\tCudd_RecursiveDeref(dd,old[l]);\n\t    FREE(old);\n\t    return(NULL);\n\t}\n    }\n\n    FREE(saveString);\n    for (i = 0; i < k; i++) {\n\tcuddDeref(old[i]);\n\tFREE(string[i]);\n    }\n    FREE(string);\n    FREE(indices);\n    return(old);\n\n}  /* end of Cudd_bddPickArbitraryMinterms */\n\n\n/**\n  @brief Extracts a subset from a %BDD.\n\n  @details Extracts a subset from a %BDD in the following procedure.\n  1. Compute the weight for each mask variable by counting the number of\n     minterms for both positive and negative cofactors of the %BDD with\n     respect to each mask variable. (weight = # positive - # negative)\n  2. Find a representative cube of the %BDD by using the weight. From the\n     top variable of the %BDD, for each variable, if the weight is greater\n     than 0.0, choose THEN branch, othereise ELSE branch, until meeting\n     the constant 1.\n  3. Quantify out the variables not in maskVars from the representative\n     cube and if a variable in maskVars is don't care, replace the\n     variable with a constant(1 or 0) depending on the weight.\n  4. Make a subset of the %BDD by multiplying with the modified cube.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_SubsetWithMaskVars(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function from which to pick a cube */,\n  DdNode ** vars /**< array of variables */,\n  int  nvars /**< size of <code>vars</code> */,\n  DdNode ** maskVars /**< array of variables */,\n  int  mvars /**< size of <code>maskVars</code> */)\n{\n    double\t*weight;\n    char\t*string;\n    int\t\ti, size;\n    int\t\t*indices, *mask;\n    int\t\tresult;\n    DdNode\t*cube, *newCube, *subset;\n    DdNode\t*cof;\n    DdNode\t*support;\n    DdNode\t*zero;\n\n    support = Cudd_Support(dd,f);\n    cuddRef(support);\n    Cudd_RecursiveDeref(dd,support);\n\n    size = dd->size;\n\n    weight = ALLOC(double,size);\n    if (weight == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    for (i = 0; i < size; i++) {\n\tweight[i] = 0.0;\n    }\n    for (i = 0; i < mvars; i++) {\n\tcof = Cudd_Cofactor(dd, f, maskVars[i]);\n\tcuddRef(cof);\n\tweight[i] = Cudd_CountMinterm(dd, cof, nvars);\n\tCudd_RecursiveDeref(dd,cof);\n\n\tcof = Cudd_Cofactor(dd, f, Cudd_Not(maskVars[i]));\n\tcuddRef(cof);\n\tweight[i] -= Cudd_CountMinterm(dd, cof, nvars);\n\tCudd_RecursiveDeref(dd,cof);\n    }\n\n    string = ALLOC(char, size + 1);\n    if (string == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(weight);\n\treturn(NULL);\n    }\n    mask = ALLOC(int, size);\n    if (mask == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(weight);\n\tFREE(string);\n\treturn(NULL);\n    }\n    for (i = 0; i < size; i++) {\n\tstring[i] = '2';\n\tmask[i] = 0;\n    }\n    string[size] = '\\0';\n    indices = ALLOC(int,nvars);\n    if (indices == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(weight);\n\tFREE(string);\n\tFREE(mask);\n\treturn(NULL);\n    }\n    for (i = 0; i < nvars; i++) {\n\tindices[i] = vars[i]->index;\n    }\n\n    result = ddPickRepresentativeCube(dd,f,weight,string);\n    if (result == 0) {\n\tFREE(weight);\n\tFREE(string);\n\tFREE(mask);\n\tFREE(indices);\n\treturn(NULL);\n    }\n\n    cube = Cudd_ReadOne(dd);\n    cuddRef(cube);\n    zero = Cudd_Not(Cudd_ReadOne(dd));\n    for (i = 0; i < nvars; i++) {\n\tif (string[indices[i]] == '0') {\n\t    newCube = Cudd_bddIte(dd,cube,Cudd_Not(vars[i]),zero);\n\t} else if (string[indices[i]] == '1') {\n\t    newCube = Cudd_bddIte(dd,cube,vars[i],zero);\n\t} else\n\t    continue;\n\tif (newCube == NULL) {\n\t    FREE(weight);\n\t    FREE(string);\n\t    FREE(mask);\n\t    FREE(indices);\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    return(NULL);\n\t}\n\tcuddRef(newCube);\n\tCudd_RecursiveDeref(dd,cube);\n\tcube = newCube;\n    }\n    Cudd_RecursiveDeref(dd,cube);\n\n    for (i = 0; i < mvars; i++) {\n\tmask[maskVars[i]->index] = 1;\n    }\n    for (i = 0; i < nvars; i++) {\n\tif (mask[indices[i]]) {\n\t    if (string[indices[i]] == '2') {\n\t\tif (weight[indices[i]] >= 0.0)\n\t\t    string[indices[i]] = '1';\n\t\telse\n\t\t    string[indices[i]] = '0';\n\t    }\n\t} else {\n\t    string[indices[i]] = '2';\n\t}\n    }\n\n    cube = Cudd_ReadOne(dd);\n    cuddRef(cube);\n    zero = Cudd_Not(Cudd_ReadOne(dd));\n\n    /* Build result BDD. */\n    for (i = 0; i < nvars; i++) {\n\tif (string[indices[i]] == '0') {\n\t    newCube = Cudd_bddIte(dd,cube,Cudd_Not(vars[i]),zero);\n\t} else if (string[indices[i]] == '1') {\n\t    newCube = Cudd_bddIte(dd,cube,vars[i],zero);\n\t} else\n\t    continue;\n\tif (newCube == NULL) {\n\t    FREE(weight);\n\t    FREE(string);\n\t    FREE(mask);\n\t    FREE(indices);\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    return(NULL);\n\t}\n\tcuddRef(newCube);\n\tCudd_RecursiveDeref(dd,cube);\n\tcube = newCube;\n    }\n\n    subset = Cudd_bddAnd(dd,f,cube);\n    cuddRef(subset);\n    Cudd_RecursiveDeref(dd,cube);\n\n    /* Test. */\n    if (Cudd_bddLeq(dd,subset,f)) {\n\tcuddDeref(subset);\n    } else {\n\tCudd_RecursiveDeref(dd,subset);\n\tsubset = NULL;\n    }\n\n    FREE(weight);\n    FREE(string);\n    FREE(mask);\n    FREE(indices);\n    return(subset);\n\n} /* end of Cudd_SubsetWithMaskVars */\n\n\n/**\n  @brief Finds the first cube of a decision diagram.\n\n  @details Defines an iterator on the onset of a decision diagram\n  and finds its first cube.<p>\n  A cube is represented as an array of literals, which are integers in\n  {0, 1, 2}; 0 represents a complemented literal, 1 represents an\n  uncomplemented literal, and 2 stands for don't care. The enumeration\n  produces a disjoint cover of the function associated with the diagram.\n  The size of the array equals the number of variables in the manager at\n  the time Cudd_FirstCube is called.<p>\n  For each cube, a value is also returned. This value is always 1 for a\n  %BDD, while it may be different from 1 for an %ADD.\n  For BDDs, the offset is the set of cubes whose value is the logical zero.\n  For ADDs, the offset is the set of cubes whose value is the\n  background value. The cubes of the offset are not enumerated.\n\n  @return a generator that contains the information necessary to\n  continue the enumeration if successful; NULL otherwise.\n\n  @sideeffect The first cube and its value are returned as side effects.\n\n  @see Cudd_ForeachCube Cudd_NextCube Cudd_GenFree Cudd_IsGenEmpty\n  Cudd_FirstNode\n\n*/\nDdGen *\nCudd_FirstCube(\n  DdManager * dd,\n  DdNode * f,\n  int ** cube,\n  CUDD_VALUE_TYPE * value)\n{\n    DdGen *gen;\n    DdNode *top, *treg, *next, *nreg, *prev, *preg;\n    int i;\n    int nvars;\n\n    /* Sanity Check. */\n    if (dd == NULL || f == NULL) return(NULL);\n\n    /* Allocate generator an initialize it. */\n    gen = ALLOC(DdGen,1);\n    if (gen == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    gen->manager = dd;\n    gen->type = CUDD_GEN_CUBES;\n    gen->status = CUDD_GEN_EMPTY;\n    gen->gen.cubes.cube = NULL;\n    gen->gen.cubes.value = DD_ZERO_VAL;\n    gen->stack.sp = 0;\n    gen->stack.stack = NULL;\n    gen->node = NULL;\n\n    nvars = dd->size;\n    gen->gen.cubes.cube = ALLOC(int,nvars);\n    if (gen->gen.cubes.cube == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(gen);\n\treturn(NULL);\n    }\n    for (i = 0; i < nvars; i++) gen->gen.cubes.cube[i] = 2;\n\n    /* The maximum stack depth is one plus the number of variables.\n    ** because a path may have nodes at all levels, including the\n    ** constant level.\n    */\n    gen->stack.stack = ALLOC(DdNodePtr, nvars+1);\n    if (gen->stack.stack == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(gen->gen.cubes.cube);\n\tFREE(gen);\n\treturn(NULL);\n    }\n    for (i = 0; i <= nvars; i++) gen->stack.stack[i] = NULL;\n\n    /* Find the first cube of the onset. */\n    gen->stack.stack[gen->stack.sp] = f; gen->stack.sp++;\n\n    while (1) {\n\ttop = gen->stack.stack[gen->stack.sp-1];\n\ttreg = Cudd_Regular(top);\n\tif (!cuddIsConstant(treg)) {\n\t    /* Take the else branch first. */\n\t    gen->gen.cubes.cube[treg->index] = 0;\n\t    next = cuddE(treg);\n\t    if (top != treg) next = Cudd_Not(next);\n\t    gen->stack.stack[gen->stack.sp] = next; gen->stack.sp++;\n\t} else if (top == Cudd_Not(DD_ONE(dd)) || top == dd->background) {\n\t    /* Backtrack */\n\t    while (1) {\n\t\tif (gen->stack.sp == 1) {\n\t\t    /* The current node has no predecessor. */\n\t\t    gen->status = CUDD_GEN_EMPTY;\n\t\t    gen->stack.sp--;\n\t\t    goto done;\n\t\t}\n\t\tprev = gen->stack.stack[gen->stack.sp-2];\n\t\tpreg = Cudd_Regular(prev);\n\t\tnreg = cuddT(preg);\n\t\tif (prev != preg) {next = Cudd_Not(nreg);} else {next = nreg;}\n\t\tif (next != top) { /* follow the then branch next */\n\t\t    gen->gen.cubes.cube[preg->index] = 1;\n\t\t    gen->stack.stack[gen->stack.sp-1] = next;\n\t\t    break;\n\t\t}\n\t\t/* Pop the stack and try again. */\n\t\tgen->gen.cubes.cube[preg->index] = 2;\n\t\tgen->stack.sp--;\n\t\ttop = gen->stack.stack[gen->stack.sp-1];\n\t    }\n\t} else {\n\t    gen->status = CUDD_GEN_NONEMPTY;\n\t    gen->gen.cubes.value = cuddV(top);\n\t    goto done;\n\t}\n    }\n\ndone:\n    *cube = gen->gen.cubes.cube;\n    *value = gen->gen.cubes.value;\n    return(gen);\n\n} /* end of Cudd_FirstCube */\n\n\n/**\n  @brief Generates the next cube of a decision diagram onset.\n\n  @return 0 if the enumeration is completed; 1 otherwise.\n\n  @sideeffect The cube and its value are returned as side effects. The\n  generator is modified.\n\n  @see Cudd_ForeachCube Cudd_FirstCube Cudd_GenFree Cudd_IsGenEmpty\n  Cudd_NextNode\n\n*/\nint\nCudd_NextCube(\n  DdGen * gen,\n  int ** cube,\n  CUDD_VALUE_TYPE * value)\n{\n    DdNode *top, *treg, *next, *nreg, *prev, *preg;\n    DdManager *dd = gen->manager;\n\n    /* Backtrack from previously reached terminal node. */\n    while (1) {\n\tif (gen->stack.sp == 1) {\n\t    /* The current node has no predecessor. */\n\t    gen->status = CUDD_GEN_EMPTY;\n\t    gen->stack.sp--;\n\t    goto done;\n\t}\n\ttop = gen->stack.stack[gen->stack.sp-1];\n\tprev = gen->stack.stack[gen->stack.sp-2];\n\tpreg = Cudd_Regular(prev);\n\tnreg = cuddT(preg);\n\tif (prev != preg) {next = Cudd_Not(nreg);} else {next = nreg;}\n\tif (next != top) { /* follow the then branch next */\n\t    gen->gen.cubes.cube[preg->index] = 1;\n\t    gen->stack.stack[gen->stack.sp-1] = next;\n\t    break;\n\t}\n\t/* Pop the stack and try again. */\n\tgen->gen.cubes.cube[preg->index] = 2;\n\tgen->stack.sp--;\n    }\n\n    while (1) {\n\ttop = gen->stack.stack[gen->stack.sp-1];\n\ttreg = Cudd_Regular(top);\n\tif (!cuddIsConstant(treg)) {\n\t    /* Take the else branch first. */\n\t    gen->gen.cubes.cube[treg->index] = 0;\n\t    next = cuddE(treg);\n\t    if (top != treg) next = Cudd_Not(next);\n\t    gen->stack.stack[gen->stack.sp] = next; gen->stack.sp++;\n\t} else if (top == Cudd_Not(DD_ONE(dd)) || top == dd->background) {\n\t    /* Backtrack */\n\t    while (1) {\n\t\tif (gen->stack.sp == 1) {\n\t\t    /* The current node has no predecessor. */\n\t\t    gen->status = CUDD_GEN_EMPTY;\n\t\t    gen->stack.sp--;\n\t\t    goto done;\n\t\t}\n\t\tprev = gen->stack.stack[gen->stack.sp-2];\n\t\tpreg = Cudd_Regular(prev);\n\t\tnreg = cuddT(preg);\n\t\tif (prev != preg) {next = Cudd_Not(nreg);} else {next = nreg;}\n\t\tif (next != top) { /* follow the then branch next */\n\t\t    gen->gen.cubes.cube[preg->index] = 1;\n\t\t    gen->stack.stack[gen->stack.sp-1] = next;\n\t\t    break;\n\t\t}\n\t\t/* Pop the stack and try again. */\n\t\tgen->gen.cubes.cube[preg->index] = 2;\n\t\tgen->stack.sp--;\n\t\ttop = gen->stack.stack[gen->stack.sp-1];\n\t    }\n\t} else {\n\t    gen->status = CUDD_GEN_NONEMPTY;\n\t    gen->gen.cubes.value = cuddV(top);\n\t    goto done;\n\t}\n    }\n\ndone:\n    if (gen->status == CUDD_GEN_EMPTY) return(0);\n    *cube = gen->gen.cubes.cube;\n    *value = gen->gen.cubes.value;\n    return(1);\n\n} /* end of Cudd_NextCube */\n\n\n/**\n  @brief Finds the first prime of a Boolean function.\n\n  @details@parblock\n  Defines an iterator on a pair of BDDs describing a\n  (possibly incompletely specified) Boolean functions and finds the\n  first cube of a cover of the function.\n\n  The two argument BDDs are the lower and upper bounds of an interval.\n  It is a mistake to call this function with a lower bound that is not\n  less than or equal to the upper bound.\n\n  A cube is represented as an array of literals, which are integers in\n  {0, 1, 2}; 0 represents a complemented literal, 1 represents an\n  uncomplemented literal, and 2 stands for don't care. The enumeration\n  produces a prime and irredundant cover of the function associated\n  with the two BDDs.  The size of the array equals the number of\n  variables in the manager at the time Cudd_FirstCube is called.\n\n  This iterator can only be used on BDDs.\n  @endparblock\n\n  @return a generator that contains the information necessary to\n  continue the enumeration if successful; NULL otherwise.\n\n  @sideeffect The first cube is returned as side effect.\n\n  @see Cudd_ForeachPrime Cudd_NextPrime Cudd_GenFree Cudd_IsGenEmpty\n  Cudd_FirstCube Cudd_FirstNode\n\n*/\nDdGen *\nCudd_FirstPrime(\n  DdManager *dd,\n  DdNode *l,\n  DdNode *u,\n  int **cube)\n{\n    DdGen *gen;\n    DdNode *implicant, *prime, *tmp;\n    int length, result;\n\n    /* Sanity Check. */\n    if (dd == NULL || l == NULL || u == NULL) return(NULL);\n\n    /* Allocate generator an initialize it. */\n    gen = ALLOC(DdGen,1);\n    if (gen == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    gen->manager = dd;\n    gen->type = CUDD_GEN_PRIMES;\n    gen->status = CUDD_GEN_EMPTY;\n    gen->gen.primes.cube = NULL;\n    gen->gen.primes.ub = u;\n    gen->stack.sp = 0;\n    gen->stack.stack = NULL;\n    gen->node = l;\n    cuddRef(l);\n\n    gen->gen.primes.cube = ALLOC(int,dd->size);\n    if (gen->gen.primes.cube == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(gen);\n\treturn(NULL);\n    }\n\n    if (gen->node == Cudd_ReadLogicZero(dd)) {\n\tgen->status = CUDD_GEN_EMPTY;\n    } else {\n\timplicant = Cudd_LargestCube(dd,gen->node,&length);\n\tif (implicant == NULL) {\n\t    Cudd_RecursiveDeref(dd,gen->node);\n\t    FREE(gen->gen.primes.cube);\n\t    FREE(gen);\n\t    return(NULL);\n\t}\n\tcuddRef(implicant);\n\tprime = Cudd_bddMakePrime(dd,implicant,gen->gen.primes.ub);\n\tif (prime == NULL) {\n\t    Cudd_RecursiveDeref(dd,gen->node);\n\t    Cudd_RecursiveDeref(dd,implicant);\n\t    FREE(gen->gen.primes.cube);\n\t    FREE(gen);\n\t    return(NULL);\n\t}\n\tcuddRef(prime);\n\tCudd_RecursiveDeref(dd,implicant);\n\ttmp = Cudd_bddAnd(dd,gen->node,Cudd_Not(prime));\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDeref(dd,gen->node);\n\t    Cudd_RecursiveDeref(dd,prime);\n\t    FREE(gen->gen.primes.cube);\n\t    FREE(gen);\n\t    return(NULL);\n\t}\n\tcuddRef(tmp);\n\tCudd_RecursiveDeref(dd,gen->node);\n\tgen->node = tmp;\n\tresult = Cudd_BddToCubeArray(dd,prime,gen->gen.primes.cube);\n\tif (result == 0) {\n\t    Cudd_RecursiveDeref(dd,gen->node);\n\t    Cudd_RecursiveDeref(dd,prime);\n\t    FREE(gen->gen.primes.cube);\n\t    FREE(gen);\n\t    return(NULL);\n\t}\n\tCudd_RecursiveDeref(dd,prime);\n\tgen->status = CUDD_GEN_NONEMPTY;\n    }\n    *cube = gen->gen.primes.cube;\n    return(gen);\n\n} /* end of Cudd_FirstPrime */\n\n\n/**\n  @brief Generates the next prime of a Boolean function.\n\n  @return 0 if the enumeration is completed; 1 otherwise.\n\n  @sideeffect The cube and is returned as side effects. The\n  generator is modified.\n\n  @see Cudd_ForeachPrime Cudd_FirstPrime Cudd_GenFree Cudd_IsGenEmpty\n  Cudd_NextCube Cudd_NextNode\n\n*/\nint\nCudd_NextPrime(\n  DdGen *gen,\n  int **cube)\n{\n    DdNode *implicant, *prime, *tmp;\n    DdManager *dd = gen->manager;\n    int length, result;\n\n    if (gen->node == Cudd_ReadLogicZero(dd)) {\n\tgen->status = CUDD_GEN_EMPTY;\n    } else {\n\timplicant = Cudd_LargestCube(dd,gen->node,&length);\n\tif (implicant == NULL) {\n\t    gen->status = CUDD_GEN_EMPTY;\n\t    return(0);\n\t}\n\tcuddRef(implicant);\n\tprime = Cudd_bddMakePrime(dd,implicant,gen->gen.primes.ub);\n\tif (prime == NULL) {\n\t    Cudd_RecursiveDeref(dd,implicant);\n\t    gen->status = CUDD_GEN_EMPTY;\n\t    return(0);\n\t}\n\tcuddRef(prime);\n\tCudd_RecursiveDeref(dd,implicant);\n\ttmp = Cudd_bddAnd(dd,gen->node,Cudd_Not(prime));\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDeref(dd,prime);\n\t    gen->status = CUDD_GEN_EMPTY;\n\t    return(0);\n\t}\n\tcuddRef(tmp);\n\tCudd_RecursiveDeref(dd,gen->node);\n\tgen->node = tmp;\n\tresult = Cudd_BddToCubeArray(dd,prime,gen->gen.primes.cube);\n\tif (result == 0) {\n\t    Cudd_RecursiveDeref(dd,prime);\n\t    gen->status = CUDD_GEN_EMPTY;\n\t    return(0);\n\t}\n\tCudd_RecursiveDeref(dd,prime);\n\tgen->status = CUDD_GEN_NONEMPTY;\n    }\n    if (gen->status == CUDD_GEN_EMPTY) return(0);\n    *cube = gen->gen.primes.cube;\n    return(1);\n\n} /* end of Cudd_NextPrime */\n\n\n/**\n  @brief Computes the cube of an array of %BDD variables.\n\n  @details If non-null, the phase argument indicates which literal of\n  each variable should appear in the cube. If phase\\[i\\] is nonzero,\n  then the positive literal is used. If phase is NULL, the cube is\n  positive unate.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_addComputeCube Cudd_IndicesToCube Cudd_CubeArrayToBdd\n\n*/\nDdNode *\nCudd_bddComputeCube(\n  DdManager * dd,\n  DdNode ** vars,\n  int * phase,\n  int  n)\n{\n    DdNode\t*cube;\n    DdNode\t*fn;\n    int         i;\n\n    cube = DD_ONE(dd);\n    cuddRef(cube);\n\n    for (i = n - 1; i >= 0; i--) {\n\tif (phase == NULL || phase[i] != 0) {\n\t    fn = Cudd_bddAnd(dd,vars[i],cube);\n\t} else {\n\t    fn = Cudd_bddAnd(dd,Cudd_Not(vars[i]),cube);\n\t}\n\tif (fn == NULL) {\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    return(NULL);\n\t}\n\tcuddRef(fn);\n\tCudd_RecursiveDeref(dd,cube);\n\tcube = fn;\n    }\n    cuddDeref(cube);\n\n    return(cube);\n\n}  /* end of Cudd_bddComputeCube */\n\n\n/**\n  @brief Computes the cube of an array of %ADD variables.\n\n  @details If non-null, the phase argument indicates which literal of\n  each variable should appear in the cube. If phase\\[i\\] is nonzero,\n  then the positive literal is used. If phase is NULL, the cube is\n  positive unate.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect none\n\n  @see Cudd_bddComputeCube\n\n*/\nDdNode *\nCudd_addComputeCube(\n  DdManager * dd,\n  DdNode ** vars,\n  int * phase,\n  int  n)\n{\n    DdNode\t*cube, *azero;\n    DdNode\t*fn;\n    int         i;\n\n    cube = DD_ONE(dd);\n    cuddRef(cube);\n    azero = DD_ZERO(dd);\n\n    for (i = n - 1; i >= 0; i--) {\n\tif (phase == NULL || phase[i] != 0) {\n\t    fn = Cudd_addIte(dd,vars[i],cube,azero);\n\t} else {\n\t    fn = Cudd_addIte(dd,vars[i],azero,cube);\n\t}\n\tif (fn == NULL) {\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    return(NULL);\n\t}\n\tcuddRef(fn);\n\tCudd_RecursiveDeref(dd,cube);\n\tcube = fn;\n    }\n    cuddDeref(cube);\n\n    return(cube);\n\n} /* end of Cudd_addComputeCube */\n\n\n/**\n  @brief Builds the %BDD of a cube from a positional array.\n\n  @details The array must have one integer entry for each %BDD\n  variable.  If the i-th entry is 1, the variable of index i appears\n  in true form in the cube; If the i-th entry is 0, the variable of\n  index i appears complemented in the cube; otherwise the variable\n  does not appear in the cube.\n\n  @return a pointer to the %BDD for the cube if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddComputeCube Cudd_IndicesToCube Cudd_BddToCubeArray\n\n*/\nDdNode *\nCudd_CubeArrayToBdd(\n  DdManager *dd,\n  int *array)\n{\n    DdNode *cube, *var, *tmp;\n    int i;\n    int size = Cudd_ReadSize(dd);\n\n    cube = DD_ONE(dd);\n    cuddRef(cube);\n    for (i = size - 1; i >= 0; i--) {\n\tif ((array[i] & ~1) == 0) {\n\t    var = Cudd_bddIthVar(dd,i);\n\t    tmp = Cudd_bddAnd(dd,cube,Cudd_NotCond(var,array[i]==0));\n\t    if (tmp == NULL) {\n\t\tCudd_RecursiveDeref(dd,cube);\n\t\treturn(NULL);\n\t    }\n\t    cuddRef(tmp);\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    cube = tmp;\n\t}\n    }\n    cuddDeref(cube);\n    return(cube);\n\n} /* end of Cudd_CubeArrayToBdd */\n\n\n/**\n  @brief Builds a positional array from the %BDD of a cube.\n\n  @details Array must have one entry for each %BDD variable.  The\n  positional array has 1 in i-th position if the variable of index i\n  appears in true form in the cube; it has 0 in i-th position if the\n  variable of index i appears in complemented form in the cube;\n  finally, it has 2 in i-th position if the variable of index i does\n  not appear in the cube.\n\n  @return 1 if successful (the %BDD is indeed a cube); 0 otherwise.\n\n  @sideeffect The result is in the array passed by reference.\n\n  @see Cudd_CubeArrayToBdd\n\n*/\nint\nCudd_BddToCubeArray(\n  DdManager *dd,\n  DdNode *cube,\n  int *array)\n{\n    DdNode *scan, *t, *e;\n    int i;\n    int size = Cudd_ReadSize(dd);\n    DdNode *lzero = Cudd_Not(DD_ONE(dd));\n\n    for (i = size-1; i >= 0; i--) {\n\tarray[i] = 2;\n    }\n    scan = cube;\n    while (!Cudd_IsConstantInt(scan)) {\n\tunsigned int index = Cudd_Regular(scan)->index;\n\tcuddGetBranches(scan,&t,&e);\n\tif (t == lzero) {\n\t    array[index] = 0;\n\t    scan = e;\n\t} else if (e == lzero) {\n\t    array[index] = 1;\n\t    scan = t;\n\t} else {\n\t    return(0);\t/* cube is not a cube */\n\t}\n    }\n    if (scan == lzero) {\n\treturn(0);\n    } else {\n\treturn(1);\n    }\n\n} /* end of Cudd_BddToCubeArray */\n\n\n/**\n  @brief Finds the first node of a decision diagram.\n\n  @details Defines an iterator on the nodes of a decision diagram and\n  finds its first node.  The nodes are enumerated in a reverse\n  topological order, so that a node is always preceded in the\n  enumeration by its descendants.\n\n  @return a generator that contains the information necessary to\n  continue the enumeration if successful; NULL otherwise.\n\n  @sideeffect The first node is returned as a side effect.\n\n  @see Cudd_ForeachNode Cudd_NextNode Cudd_GenFree Cudd_IsGenEmpty\n  Cudd_FirstCube\n\n*/\nDdGen *\nCudd_FirstNode(\n  DdManager * dd,\n  DdNode * f,\n  DdNode ** node)\n{\n    DdGen *gen;\n    int size;\n\n    /* Sanity Check. */\n    if (dd == NULL || f == NULL) return(NULL);\n\n    /* Allocate generator an initialize it. */\n    gen = ALLOC(DdGen,1);\n    if (gen == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    gen->manager = dd;\n    gen->type = CUDD_GEN_NODES;\n    gen->status = CUDD_GEN_EMPTY;\n    gen->stack.sp = 0;\n    gen->node = NULL;\n\n    /* Collect all the nodes on the generator stack for later perusal. */\n    gen->stack.stack = cuddNodeArray(Cudd_Regular(f), &size);\n    if (gen->stack.stack == NULL) {\n\tFREE(gen);\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n    gen->gen.nodes.size = size;\n\n    /* Find the first node. */\n    if (gen->stack.sp < gen->gen.nodes.size) {\n\tgen->status = CUDD_GEN_NONEMPTY;\n\tgen->node = gen->stack.stack[gen->stack.sp];\n\t*node = gen->node;\n    }\n\n    return(gen);\n\n} /* end of Cudd_FirstNode */\n\n\n/**\n  @brief Finds the next node of a decision diagram.\n\n  @return 0 if the enumeration is completed; 1 otherwise.\n\n  @sideeffect The next node is returned as a side effect.\n\n  @see Cudd_ForeachNode Cudd_FirstNode Cudd_GenFree Cudd_IsGenEmpty\n  Cudd_NextCube\n\n*/\nint\nCudd_NextNode(\n  DdGen * gen,\n  DdNode ** node)\n{\n    /* Find the next node. */\n    gen->stack.sp++;\n    if (gen->stack.sp < gen->gen.nodes.size) {\n\tgen->node = gen->stack.stack[gen->stack.sp];\n\t*node = gen->node;\n\treturn(1);\n    } else {\n\tgen->status = CUDD_GEN_EMPTY;\n\treturn(0);\n    }\n\n} /* end of Cudd_NextNode */\n\n\n/**\n  @brief Frees a CUDD generator.\n\n  @return always 0.\n\n  @sideeffect None\n\n  @see Cudd_ForeachCube Cudd_ForeachNode Cudd_FirstCube Cudd_NextCube\n  Cudd_FirstNode Cudd_NextNode Cudd_IsGenEmpty\n\n*/\nint\nCudd_GenFree(\n  DdGen * gen)\n{\n    if (gen == NULL) return(0);\n    switch (gen->type) {\n    case CUDD_GEN_CUBES:\n    case CUDD_GEN_ZDD_PATHS:\n\tFREE(gen->gen.cubes.cube);\n\tFREE(gen->stack.stack);\n\tbreak;\n    case CUDD_GEN_PRIMES:\n\tFREE(gen->gen.primes.cube);\n\tCudd_RecursiveDeref(gen->manager,gen->node);\n\tbreak;\n    case CUDD_GEN_NODES:\n\tFREE(gen->stack.stack);\n\tbreak;\n    default:\n\treturn(0);\n    }\n    FREE(gen);\n    return(0);\n\n} /* end of Cudd_GenFree */\n\n\n/**\n  @brief Queries the status of a generator.\n\n  @return 1 if the generator is empty or NULL; 0 otherswise.\n\n  @sideeffect None\n\n  @see Cudd_ForeachCube Cudd_ForeachNode Cudd_FirstCube Cudd_NextCube\n  Cudd_FirstNode Cudd_NextNode Cudd_GenFree\n\n*/\nint\nCudd_IsGenEmpty(\n  DdGen * gen)\n{\n    if (gen == NULL) return(1);\n    return(gen->status == CUDD_GEN_EMPTY);\n\n} /* end of Cudd_IsGenEmpty */\n\n\n/**\n  @brief Builds a cube of %BDD variables from an array of indices.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_bddComputeCube Cudd_CubeArrayToBdd\n\n*/\nDdNode *\nCudd_IndicesToCube(\n  DdManager * dd,\n  int * array,\n  int  n)\n{\n    DdNode *cube, *tmp;\n    int i;\n\n    cube = DD_ONE(dd);\n    cuddRef(cube);\n    for (i = n - 1; i >= 0; i--) {\n\ttmp = Cudd_bddAnd(dd,Cudd_bddIthVar(dd,array[i]),cube);\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    return(NULL);\n\t}\n\tcuddRef(tmp);\n\tCudd_RecursiveDeref(dd,cube);\n\tcube = tmp;\n    }\n\n    cuddDeref(cube);\n    return(cube);\n\n} /* end of Cudd_IndicesToCube */\n\n\n/**\n  @brief Prints the package version number.\n\n  @sideeffect None\n\n*/\nvoid\nCudd_PrintVersion(\n  FILE * fp)\n{\n    (void) fprintf(fp, \"%s\\n\", CUDD_VERSION);\n\n} /* end of Cudd_PrintVersion */\n\n\n/**\n  @brief Computes the average distance between adjacent nodes in the manager.\n\n  @details Adjacent nodes are node pairs such that the second node\n  is the then child, else child, or next node in the collision list.\n\n  @sideeffect None\n\n*/\ndouble\nCudd_AverageDistance(\n  DdManager * dd)\n{\n    double tetotal, nexttotal;\n    double tesubtotal, nextsubtotal;\n    double temeasured, nextmeasured;\n    int i, j;\n    int slots, nvars;\n    ptrdiff_t diff;\n    DdNode *scan;\n    DdNodePtr *nodelist;\n    DdNode *sentinel = &(dd->sentinel);\n\n    nvars = dd->size;\n    if (nvars == 0) return(0.0);\n\n    /* Initialize totals. */\n    tetotal = 0.0;\n    nexttotal = 0.0;\n    temeasured = 0.0;\n    nextmeasured = 0.0;\n\n    /* Scan the variable subtables. */\n    for (i = 0; i < nvars; i++) {\n\tnodelist = dd->subtables[i].nodelist;\n\ttesubtotal = 0.0;\n\tnextsubtotal = 0.0;\n\tslots = dd->subtables[i].slots;\n\tfor (j = 0; j < slots; j++) {\n\t    scan = nodelist[j];\n\t    while (scan != sentinel) {\n\t\tdiff = (ptrint) scan - (ptrint) cuddT(scan);\n\t\ttesubtotal += (double) ddAbs(diff);\n\t\tdiff = (ptrint) scan - (ptrint) Cudd_Regular(cuddE(scan));\n\t\ttesubtotal += (double) ddAbs(diff);\n\t\ttemeasured += 2.0;\n\t\tif (scan->next != sentinel) {\n\t\t    diff = (ptrint) scan - (ptrint) scan->next;\n\t\t    nextsubtotal += (double) ddAbs(diff);\n\t\t    nextmeasured += 1.0;\n\t\t}\n\t\tscan = scan->next;\n\t    }\n\t}\n\ttetotal += tesubtotal;\n\tnexttotal += nextsubtotal;\n    }\n\n    /* Scan the constant table. */\n    nodelist = dd->constants.nodelist;\n    nextsubtotal = 0.0;\n    slots = dd->constants.slots;\n    for (j = 0; j < slots; j++) {\n\tscan = nodelist[j];\n\twhile (scan != NULL) {\n\t    if (scan->next != NULL) {\n\t\tdiff = (ptrint) scan - (ptrint) scan->next;\n\t\tnextsubtotal += (double) ddAbs(diff);\n\t\tnextmeasured += 1.0;\n\t    }\n\t    scan = scan->next;\n\t}\n    }\n    nexttotal += nextsubtotal;\n\n    return((tetotal + nexttotal) / (temeasured + nextmeasured));\n\n} /* end of Cudd_AverageDistance */\n\n\n/**\n  @brief Portable random number generator.\n\n  @details Based on ran2 from \"Numerical Recipes in C.\" It is a long\n  period (> 2 * 10^18) random number generator of L'Ecuyer with\n  Bays-Durham shuffle.  The random generator can be explicitly\n  initialized by calling Cudd_Srandom. If no explicit initialization\n  is performed, then the seed 1 is assumed.\n\n  @return a long integer uniformly distributed between 0 and\n  2147483561 (inclusive of the endpoint values).\n\n  @sideeffect None\n\n  @see Cudd_Srandom\n\n*/\nint32_t\nCudd_Random(DdManager *dd)\n{\n    int i;\t/* index in the shuffle table */\n    int32_t w;\t/* work variable */\n\n    /* dd->cuddRand == 0 if the geneartor has not been initialized yet. */\n    if (dd->cuddRand == 0) Cudd_Srandom(dd,1);\n\n    /* Compute cuddRand = (cuddRand * LEQA1) % MODULUS1 avoiding\n    ** overflows by Schrage's method.\n    */\n    w          = dd->cuddRand / LEQQ1;\n    dd->cuddRand   = LEQA1 * (dd->cuddRand - w * LEQQ1) - w * LEQR1;\n    dd->cuddRand  += (dd->cuddRand < 0) * MODULUS1;\n\n    /* Compute dd->cuddRand2 = (dd->cuddRand2 * LEQA2) % MODULUS2 avoiding\n    ** overflows by Schrage's method.\n    */\n    w          = dd->cuddRand2 / LEQQ2;\n    dd->cuddRand2  = LEQA2 * (dd->cuddRand2 - w * LEQQ2) - w * LEQR2;\n    dd->cuddRand2 += (dd->cuddRand2 < 0) * MODULUS2;\n\n    /* dd->cuddRand is shuffled with the Bays-Durham algorithm.\n    ** dd->shuffleSelect and cuddRand2 are combined to generate the output.\n    */\n\n    /* Pick one element from the shuffle table; \"i\" will be in the range\n    ** from 0 to STAB_SIZE-1.\n    */\n    i = (int) (dd->shuffleSelect / STAB_DIV);\n    /* Mix the element of the shuffle table with the current iterate of\n    ** the second sub-generator, and replace the chosen element of the\n    ** shuffle table with the current iterate of the first sub-generator.\n    */\n    dd->shuffleSelect   = dd->shuffleTable[i] - dd->cuddRand2;\n    dd->shuffleTable[i] = dd->cuddRand;\n    dd->shuffleSelect  += (dd->shuffleSelect < 1) * (MODULUS1 - 1);\n    /* Since dd->shuffleSelect != 0, and we want to be able to return 0,\n    ** here we subtract 1 before returning.\n    */\n    return(dd->shuffleSelect - 1);\n\n} /* end of Cudd_Random */\n\n\n/**\n  @brief Initializer for the portable random number generator.\n\n  @details Based on ran2 in \"Numerical Recipes in C.\" The input is the\n  seed for the generator. If it is negative, its absolute value is\n  taken as seed.  If it is 0, then 1 is taken as seed. The initialized\n  sets up the two recurrences used to generate a long-period stream,\n  and sets up the shuffle table.\n\n  @sideeffect None\n\n  @see Cudd_Random\n\n*/\nvoid\nCudd_Srandom(\n  DdManager *dd,\n  int32_t  seed)\n{\n    int32_t i;\n\n    if (seed < 0)       dd->cuddRand = -seed;\n    else if (seed == 0) dd->cuddRand = 1;\n    else                dd->cuddRand = seed;\n    dd->cuddRand2 = dd->cuddRand;\n    /* Load the shuffle table (after 11 warm-ups). */\n    for (i = 0; i < STAB_SIZE + 11; i++) {\n\tint32_t w;\n\tw = dd->cuddRand / LEQQ1;\n\tdd->cuddRand = LEQA1 * (dd->cuddRand - w * LEQQ1) - w * LEQR1;\n\tdd->cuddRand += (dd->cuddRand < 0) * MODULUS1;\n\tdd->shuffleTable[i % STAB_SIZE] = dd->cuddRand;\n    }\n    dd->shuffleSelect = dd->shuffleTable[1 % STAB_SIZE];\n\n} /* end of Cudd_Srandom */\n\n\n/**\n  @brief Computes the density of a %BDD or %ADD.\n\n  @details The density is the ratio of the number of minterms to the\n  number of nodes. If 0 is passed as number of variables, the number\n  of variables existing in the manager is used.\n\n  @return the density if successful; (double) CUDD_OUT_OF_MEM\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_CountMinterm Cudd_DagSize\n\n*/\ndouble\nCudd_Density(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< function whose density is sought */,\n  int  nvars /**< size of the support of f */)\n{\n    double minterms;\n    int nodes;\n    double density;\n\n    if (nvars == 0) nvars = dd->size;\n    minterms = Cudd_CountMinterm(dd,f,nvars);\n    if (minterms == (double) CUDD_OUT_OF_MEM) return(minterms);\n    nodes = Cudd_DagSize(f);\n    density = minterms / (double) nodes;\n    return(density);\n\n} /* end of Cudd_Density */\n\n\n/**\n  @brief Warns that a memory allocation failed.\n\n  @details This function can be used as replacement of MMout_of_memory\n  to prevent the safe_mem functions of the util package from exiting\n  when malloc returns NULL.  One possible use is in case of\n  discretionary allocations; for instance, an allocation of memory to\n  enlarge the computed table.\n\n  @sideeffect None\n\n  @see Cudd_OutOfMemSilent Cudd_RegisterOutOfMemoryCallback\n\n*/\nvoid\nCudd_OutOfMem(\n  size_t size /**< size of the allocation that failed */)\n{\n    (void) fflush(stdout);\n    (void) fprintf(stderr, \"\\nCUDD: unable to allocate %\" PRIszt \" bytes\\n\",\n                   size);\n\n} /* end of Cudd_OutOfMem */\n\n\n/**\n  @brief Doesn not warn that a memory allocation failed.\n\n  @details This function can be used as replacement of MMout_of_memory\n  to prevent the safe_mem functions of the util package from exiting\n  when malloc returns NULL.  One possible use is in case of\n  discretionary allocations; for instance, an allocation of memory to\n  enlarge the computed table.\n\n  @sideeffect None\n\n  @see Cudd_OutOfMem Cudd_RegisterOutOfMemoryCallback\n\n*/\nvoid\nCudd_OutOfMemSilent(\n  size_t size /**< size of the allocation that failed */)\n{\n    (void) size; /* suppress warning */\n\n} /* end of Cudd_OutOfMem */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints a %DD to the standard output. One line per node is\n  printed.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_PrintDebug\n\n*/\nint\ncuddP(\n  DdManager * dd,\n  DdNode * f)\n{\n    int retval;\n    st_table *table = st_init_table(st_ptrcmp,st_ptrhash);\n\n    if (table == NULL) return(0);\n\n    retval = dp2(dd,f,table);\n    st_free_table(table);\n    (void) fputc('\\n',dd->out);\n    return(retval);\n\n} /* end of cuddP */\n\n\n/**\n  @brief Frees the memory used to store the minterm counts recorded\n  in the visited table.\n\n  @return ST_CONTINUE.\n\n  @sideeffect None\n\n*/\nenum st_retval\ncuddStCountfree(\n  void * key,\n  void * value,\n  void * arg)\n{\n    double *d = (double *)value;\n\n    (void) key; /* avoid warning */\n    (void) arg; /* avoid warning */\n    FREE(d);\n    return(ST_CONTINUE);\n\n} /* end of cuddStCountfree */\n\n\n/**\n  @brief Recursively collects all the nodes of a %DD in a symbol\n  table.\n\n  @details Traverses the %DD f and collects all its nodes in a\n  symbol table.  f is assumed to be a regular pointer and\n  cuddCollectNodes guarantees this assumption in the recursive calls.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddCollectNodes(\n  DdNode * f,\n  st_table * visited)\n{\n    DdNode\t*T, *E;\n    int\t\tretval;\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsComplement(f));\n#endif\n\n    /* If already visited, nothing to do. */\n    if (st_is_member(visited, f) == 1)\n\treturn(1);\n\n    /* Check for abnormal condition that should never happen. */\n    if (f == NULL)\n\treturn(0);\n\n    /* Mark node as visited. */\n    if (st_add_direct(visited, f, NULL) == ST_OUT_OF_MEM)\n\treturn(0);\n\n    /* Check terminal case. */\n    if (cuddIsConstant(f))\n\treturn(1);\n\n    /* Recursive calls. */\n    T = cuddT(f);\n    retval = cuddCollectNodes(T,visited);\n    if (retval != 1) return(retval);\n    E = Cudd_Regular(cuddE(f));\n    retval = cuddCollectNodes(E,visited);\n    return(retval);\n\n} /* end of cuddCollectNodes */\n\n\n/**\n  @brief Recursively collects all the nodes of a %DD in an array.\n\n  @details Traverses the %DD f and collects all its nodes in an array.\n  The caller should free the array returned by cuddNodeArray.  The\n  nodes are collected in reverse topological order, so that a node is\n  always preceded in the array by all its descendants.\n\n  @return a pointer to the array of nodes in case of success; NULL\n  otherwise.\n\n  @sideeffect The number of nodes is returned as a side effect.\n\n  @see Cudd_FirstNode\n\n*/\nDdNodePtr *\ncuddNodeArray(\n  DdNode *f,\n  int *n)\n{\n    DdNodePtr *table;\n    int size, retval;\n\n    size = ddDagInt(Cudd_Regular(f));\n    table = ALLOC(DdNodePtr, size);\n    if (table == NULL) {\n\tddClearFlag(Cudd_Regular(f));\n\treturn(NULL);\n    }\n\n    retval = cuddNodeArrayRecur(f, table, 0);\n    assert(retval == size);\n\n    *n = size;\n    return(table);\n\n} /* cuddNodeArray */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of cuddP.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ndp2(\n  DdManager *dd,\n  DdNode * f,\n  st_table * t)\n{\n    DdNode *g, *n, *N;\n    int T,E;\n\n    if (f == NULL) {\n\treturn(0);\n    }\n    g = Cudd_Regular(f);\n    if (cuddIsConstant(g)) {\n\t(void) fprintf(dd->out,\"ID = %c0x%\" PRIxPTR \"\\tvalue = %-9g\\n\", bang(f),\n\t\t(ptruint) g / (ptruint) sizeof(DdNode),cuddV(g));\n\treturn(1);\n    }\n    if (st_is_member(t,g) == 1) {\n\treturn(1);\n    }\n    if (st_add_direct(t,g,NULL) == ST_OUT_OF_MEM)\n\treturn(0);\n#ifdef DD_STATS\n    (void) fprintf(dd->out,\"ID = %c0x%\"PRIxPTR\"\\tindex = %d\\tr = %d\\t\", bang(f),\n\t\t(ptruint) g / (ptruint) sizeof(DdNode), g->index, g->ref);\n#else\n    (void) fprintf(dd->out,\"ID = %c0x%\" PRIxPTR \"\\tindex = %u\\t\", bang(f),\n\t\t(ptruint) g / (ptruint) sizeof(DdNode),g->index);\n#endif\n    n = cuddT(g);\n    if (cuddIsConstant(n)) {\n\t(void) fprintf(dd->out,\"T = %-9g\\t\",cuddV(n));\n\tT = 1;\n    } else {\n\t(void) fprintf(dd->out,\"T = 0x%\" PRIxPTR \"\\t\",\n                       (ptruint) n / (ptruint) sizeof(DdNode));\n\tT = 0;\n    }\n\n    n = cuddE(g);\n    N = Cudd_Regular(n);\n    if (cuddIsConstant(N)) {\n\t(void) fprintf(dd->out,\"E = %c%-9g\\n\",bang(n),cuddV(N));\n\tE = 1;\n    } else {\n\t(void) fprintf(dd->out,\"E = %c0x%\" PRIxPTR \"\\n\",\n                       bang(n), (ptruint) N/(ptruint) sizeof(DdNode));\n\tE = 0;\n    }\n    if (E == 0) {\n\tif (dp2(dd,N,t) == 0)\n\t    return(0);\n    }\n    if (T == 0) {\n\tif (dp2(dd,cuddT(g),t) == 0)\n\t    return(0);\n    }\n    return(1);\n\n} /* end of dp2 */\n\n\n/**\n  @brief Performs the recursive step of Cudd_PrintMinterm.\n\n  @sideeffect None\n\n*/\nstatic void\nddPrintMintermAux(\n  DdManager * dd /**< manager */,\n  DdNode * node /**< current node */,\n  int * list /**< current recursion path */)\n{\n    DdNode\t *N,*Nv,*Nnv;\n    int\t\t i,v;\n    unsigned int index;\n\n    N = Cudd_Regular(node);\n\n    if (cuddIsConstant(N)) {\n\t/* Terminal case: Print one cube based on the current recursion\n\t** path, unless we have reached the background value (ADDs) or\n\t** the logical zero (BDDs).\n\t*/\n\tif (node != dd->background && node != Cudd_Not(dd->one)) {\n\t    for (i = 0; i < dd->size; i++) {\n\t\tv = list[i];\n\t\tif (v == 0) (void) fprintf(dd->out,\"0\");\n\t\telse if (v == 1) (void) fprintf(dd->out,\"1\");\n\t\telse (void) fprintf(dd->out,\"-\");\n\t    }\n\t    (void) fprintf(dd->out,\" % g\\n\", cuddV(node));\n\t}\n    } else {\n\tNv  = cuddT(N);\n\tNnv = cuddE(N);\n\tif (Cudd_IsComplement(node)) {\n\t    Nv  = Cudd_Not(Nv);\n\t    Nnv = Cudd_Not(Nnv);\n\t}\n\tindex = N->index;\n\tlist[index] = 0;\n\tddPrintMintermAux(dd,Nnv,list);\n\tlist[index] = 1;\n\tddPrintMintermAux(dd,Nv,list);\n\tlist[index] = 2;\n    }\n    return;\n\n} /* end of ddPrintMintermAux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_DagSize.\n\n  @return the number of nodes in the graph rooted at n.\n\n  @sideeffect None\n\n*/\nstatic int\nddDagInt(\n  DdNode * n)\n{\n    int tval, eval;\n\n    if (Cudd_IsComplement(n->next)) {\n\treturn(0);\n    }\n    n->next = Cudd_Not(n->next);\n    if (cuddIsConstant(n)) {\n\treturn(1);\n    }\n    tval = ddDagInt(cuddT(n));\n    eval = ddDagInt(Cudd_Regular(cuddE(n)));\n    return(1 + tval + eval);\n\n} /* end of ddDagInt */\n\n\n/**\n  @brief Performs the recursive step of cuddNodeArray.\n\n  @details node is supposed to be regular; the invariant is maintained\n  by this procedure.\n\n  @return an the number of nodes in the %DD.\n\n  @sideeffect Clears the least significant bit of the next field that\n  was used as visited flag by cuddNodeArrayRecur when counting the\n  nodes.\n\n*/\nstatic int\ncuddNodeArrayRecur(\n  DdNode *f,\n  DdNodePtr *table,\n  int index)\n{\n    int tindex, eindex;\n\n    if (!Cudd_IsComplement(f->next)) {\n\treturn(index);\n    }\n    /* Clear visited flag. */\n    f->next = Cudd_Regular(f->next);\n    if (cuddIsConstant(f)) {\n\ttable[index] = f;\n\treturn(index + 1);\n    }\n    tindex = cuddNodeArrayRecur(cuddT(f), table, index);\n    eindex = cuddNodeArrayRecur(Cudd_Regular(cuddE(f)), table, tindex);\n    table[eindex] = f;\n    return(eindex + 1);\n\n} /* end of cuddNodeArrayRecur */\n\n\n/**\n  @brief Performs the recursive step of Cudd_CofactorEstimate.\n\n  @details Uses the least significant bit of the next field as visited\n  flag. node is supposed to be regular; the invariant is maintained by\n  this procedure.\n\n  @return an estimate of the number of nodes in the %DD of a cofactor\n  of node.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddEstimateCofactor(\n  DdManager *dd,\n  st_table *table,\n  DdNode * node,\n  int i,\n  int phase,\n  DdNode ** ptr)\n{\n    int tval, eval, val;\n    DdNode *ptrT, *ptrE;\n\n#ifdef DD_DEBUG\n    assert(!Cudd_IsComplement(node));\n#endif\n    if (Cudd_IsComplement(node->next)) {\n\tif (!st_lookup(table, node, (void **)ptr)) {\n\t    if (st_add_direct(table, node, node) == ST_OUT_OF_MEM)\n\t\treturn(CUDD_OUT_OF_MEM);\n\t    *ptr = node;\n\t}\n\treturn(0);\n    }\n    node->next = Cudd_Not(node->next);\n    if (cuddIsConstant(node)) {\n\t*ptr = node;\n\tif (st_add_direct(table, node, node) == ST_OUT_OF_MEM)\n\t    return(CUDD_OUT_OF_MEM);\n\treturn(1);\n    }\n    if ((int) node->index == i) {\n\tif (phase == 1) {\n\t    *ptr = cuddT(node);\n\t    val = ddDagInt(cuddT(node));\n\t} else {\n\t    *ptr = cuddE(node);\n\t    val = ddDagInt(Cudd_Regular(cuddE(node)));\n\t}\n\tif (node->ref > 1) {\n\t    if (st_add_direct(table,node,*ptr) == ST_OUT_OF_MEM)\n\t\treturn(CUDD_OUT_OF_MEM);\n\t}\n\treturn(val);\n    }\n    if (dd->perm[node->index] > dd->perm[i]) {\n\t*ptr = node;\n\tif (node->ref > 1) {\n\t    if (st_add_direct(table,node,node) == ST_OUT_OF_MEM)\n\t\treturn(CUDD_OUT_OF_MEM);\n\t}\n\tval = 1 + ddDagInt(cuddT(node)) + ddDagInt(Cudd_Regular(cuddE(node)));\n\treturn(val);\n    }\n    tval = cuddEstimateCofactor(dd,table,cuddT(node),i,phase,&ptrT);\n    if (tval == CUDD_OUT_OF_MEM) return(CUDD_OUT_OF_MEM);\n    eval = cuddEstimateCofactor(dd,table,Cudd_Regular(cuddE(node)),i,\n\t\t\t\tphase,&ptrE);\n    if (eval == CUDD_OUT_OF_MEM) return(CUDD_OUT_OF_MEM);\n    ptrE = Cudd_NotCond(ptrE,Cudd_IsComplement(cuddE(node)));\n    if (ptrT == ptrE) {\t\t/* recombination */\n\t*ptr = ptrT;\n\tval = tval;\n\tif (node->ref > 1) {\n\t    if (st_add_direct(table,node,*ptr) == ST_OUT_OF_MEM)\n\t\treturn(CUDD_OUT_OF_MEM);\n\t}\n    } else {\n        int complement = Cudd_IsComplement(ptrT);\n        if (complement) {\n            ptrT = Cudd_Regular(ptrT);\n            ptrE = Cudd_Complement(ptrE);\n        }\n        if ((ptrT != cuddT(node) || ptrE != cuddE(node)) &&\n            (*ptr = cuddUniqueLookup(dd,node->index,ptrT,ptrE)) != NULL) {\n            if (Cudd_IsComplement((*ptr)->next)) {\n                val = 0;\n            } else {\n                val = 1 + tval + eval;\n            }\n            if (node->ref > 1) {\n                if (st_add_direct(table,node,*ptr) == ST_OUT_OF_MEM)\n                    return(CUDD_OUT_OF_MEM);\n            }\n            if (complement) {\n                *ptr = Cudd_Complement(*ptr);\n            }\n        } else {\n            *ptr = node;\n            val = 1 + tval + eval;\n        }\n    }\n    return(val);\n\n} /* end of cuddEstimateCofactor */\n\n\n/**\n  @brief Checks the unique table for the existence of an internal node.\n\n  @return a pointer to the node if it is in the table; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddUniqueInter\n\n*/\nstatic DdNode *\ncuddUniqueLookup(\n  DdManager * unique,\n  int  index,\n  DdNode * T,\n  DdNode * E)\n{\n    unsigned int posn;\n    int level;\n    DdNodePtr *nodelist;\n    DdNode *looking;\n    DdSubtable *subtable;\n\n    if (index >= unique->size) {\n\treturn(NULL);\n    }\n\n    level = unique->perm[index];\n    subtable = &(unique->subtables[level]);\n\n#ifdef DD_DEBUG\n    assert(level < cuddI(unique,T->index));\n    assert(level < cuddI(unique,Cudd_Regular(E)->index));\n#endif\n\n    posn = ddHash(T, E, subtable->shift);\n    nodelist = subtable->nodelist;\n    looking = nodelist[posn];\n\n    while (T < cuddT(looking)) {\n\tlooking = Cudd_Regular(looking->next);\n    }\n    while (T == cuddT(looking) && E < cuddE(looking)) {\n\tlooking = Cudd_Regular(looking->next);\n    }\n    if (cuddT(looking) == T && cuddE(looking) == E) {\n\treturn(looking);\n    }\n\n    return(NULL);\n\n} /* end of cuddUniqueLookup */\n\n\n/**\n  @brief Performs the recursive step of Cudd_CofactorEstimateSimple.\n\n  @details Uses the least significant bit of the next field as visited\n  flag. node is supposed to be regular; the invariant is maintained by\n  this procedure.\n\n  @return an estimate of the number of nodes in the %DD of the positive\n  cofactor of node.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddEstimateCofactorSimple(\n  DdNode * node,\n  int i)\n{\n    int tval, eval;\n\n    if (Cudd_IsComplement(node->next)) {\n\treturn(0);\n    }\n    node->next = Cudd_Not(node->next);\n    if (cuddIsConstant(node)) {\n\treturn(1);\n    }\n    tval = cuddEstimateCofactorSimple(cuddT(node),i);\n    if ((int) node->index == i) return(tval);\n    eval = cuddEstimateCofactorSimple(Cudd_Regular(cuddE(node)),i);\n    return(1 + tval + eval);\n\n} /* end of cuddEstimateCofactorSimple */\n\n\n/**\n  @brief Performs the recursive step of Cudd_CountMinterm.\n\n  @details It is based on the following identity. Let |f| be the\n  number of minterms of f. Then:\n\n      |f| = (|f0|+|f1|)/2\n\n  where f0 and f1 are the two cofactors of f.  Does not use the\n  identity |f'| = max - |f|, to minimize loss of accuracy due to\n  roundoff.\n\n  @return the number of minterms of the function rooted at node.\n\n  @sideeffect None\n\n*/\nstatic double\nddCountMintermAux(\n  DdManager * dd,\n  DdNode * node,\n  double  max,\n  DdHashTable * table)\n{\n    DdNode\t*N, *Nt, *Ne;\n    double\tmin, minT, minE;\n    DdNode\t*res;\n\n    N = Cudd_Regular(node);\n\n    if (cuddIsConstant(N)) {\n\tif (node == dd->background || node == Cudd_Not(dd->one)) {\n\t    return(0.0);\n\t} else {\n\t    return(max);\n\t}\n    }\n    if (N->ref != 1 && (res = cuddHashTableLookup1(table,node)) != NULL) {\n\tmin = cuddV(res);\n\tif (res->ref == 0) {\n\t    table->manager->dead++;\n\t    table->manager->constants.dead++;\n\t}\n\treturn(min);\n    }\n\n    Nt = cuddT(N); Ne = cuddE(N);\n    if (Cudd_IsComplement(node)) {\n\tNt = Cudd_Not(Nt); Ne = Cudd_Not(Ne);\n    }\n\n    minT = ddCountMintermAux(dd,Nt,max,table);\n    if (minT == (double)CUDD_OUT_OF_MEM) return((double)CUDD_OUT_OF_MEM);\n    minT *= 0.5;\n    minE = ddCountMintermAux(dd,Ne,max,table);\n    if (minE == (double)CUDD_OUT_OF_MEM) return((double)CUDD_OUT_OF_MEM);\n    minE *= 0.5;\n    min = minT + minE;\n\n    if (N->ref != 1) {\n\tptrint fanout = (ptrint) N->ref;\n\tcuddSatDec(fanout);\n\tres = cuddUniqueConst(table->manager,min);\n\tif (!res) {\n\t    return((double)CUDD_OUT_OF_MEM);\n\t}\n\tif (!cuddHashTableInsert1(table,node,res,fanout)) {\n\t    cuddRef(res); Cudd_RecursiveDeref(table->manager, res);\n\t    return((double)CUDD_OUT_OF_MEM);\n\t}\n    }\n\n    return(min);\n\n} /* end of ddCountMintermAux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_CountPath.\n\n  @details It is based on the following identity. Let |f| be the\n  number of paths of f. Then:\n\n      |f| = |f0|+|f1|\n\n  where f0 and f1 are the two cofactors of f.  Uses the\n  identity |f'| = |f|, to improve the utilization of the (local) cache.\n\n  @return the number of paths of the function rooted at node.\n\n  @sideeffect None\n\n*/\nstatic double\nddCountPathAux(\n  DdNode * node,\n  st_table * table)\n{\n\n    DdNode\t*Nv, *Nnv;\n    double\tpaths, *ppaths, paths1, paths2;\n    void\t*dummy;\n\n\n    if (cuddIsConstant(node)) {\n\treturn(1.0);\n    }\n    if (st_lookup(table, node, &dummy)) {\n\tpaths = *(double *) dummy;\n\treturn(paths);\n    }\n\n    Nv = cuddT(node); Nnv = cuddE(node);\n\n    paths1 = ddCountPathAux(Nv,table);\n    if (paths1 == (double)CUDD_OUT_OF_MEM) return((double)CUDD_OUT_OF_MEM);\n    paths2 = ddCountPathAux(Cudd_Regular(Nnv),table);\n    if (paths2 == (double)CUDD_OUT_OF_MEM) return((double)CUDD_OUT_OF_MEM);\n    paths = paths1 + paths2;\n\n    ppaths = ALLOC(double,1);\n    if (ppaths == NULL) {\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n\n    *ppaths = paths;\n\n    if (st_add_direct(table, node, ppaths) == ST_OUT_OF_MEM) {\n\tFREE(ppaths);\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    return(paths);\n\n} /* end of ddCountPathAux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_EpdCountMinterm.\n\n  @details It is based on the following identity. Let |f| be the\n  number of minterms of f. Then:\n\n      |f| = (|f0|+|f1|)/2\n\n  where f0 and f1 are the two cofactors of f.  Does not use the\n  identity |f'| = max - |f|, to minimize loss of accuracy due to\n  roundoff.\n\n  @return the number of minterms of the function rooted at node.\n\n  @sideeffect None\n\n*/\nstatic int\nddEpdCountMintermAux(\n  DdManager const * dd,\n  DdNode * node,\n  EpDouble * max,\n  EpDouble * epd,\n  st_table * table)\n{\n    DdNode\t*Nt, *Ne;\n    EpDouble\t*min, minT, minE;\n    EpDouble\t*res;\n    int\t\tstatus;\n\n    /* node is assumed to be regular */\n    if (cuddIsConstant(node)) {\n\tif (node == dd->background) {\n\t    EpdMakeZero(epd, 0);\n\t} else {\n\t    EpdCopy(max, epd);\n\t}\n\treturn(0);\n    }\n    if (node->ref != 1 && st_lookup(table, node, (void **) &res)) {\n\tEpdCopy(res, epd);\n\treturn(0);\n    }\n\n    Nt = cuddT(node); Ne = cuddE(node);\n\n    status = ddEpdCountMintermAux(dd,Nt,max,&minT,table);\n    if (status == CUDD_OUT_OF_MEM) return(CUDD_OUT_OF_MEM);\n    EpdMultiply(&minT, (double)0.5);\n    status = ddEpdCountMintermAux(dd,Cudd_Regular(Ne),max,&minE,table);\n    if (status == CUDD_OUT_OF_MEM) return(CUDD_OUT_OF_MEM);\n    if (Cudd_IsComplement(Ne)) {\n\tEpdSubtract3(max, &minE, epd);\n\tEpdCopy(epd, &minE);\n    }\n    EpdMultiply(&minE, (double)0.5);\n    EpdAdd3(&minT, &minE, epd);\n\n    if (node->ref > 1) {\n\tmin = EpdAlloc();\n\tif (!min)\n\t    return(CUDD_OUT_OF_MEM);\n\tEpdCopy(epd, min);\n\tif (st_insert(table, node, min) == ST_OUT_OF_MEM) {\n\t    EpdFree(min);\n\t    return(CUDD_OUT_OF_MEM);\n\t}\n    }\n\n    return(0);\n\n} /* end of ddEpdCountMintermAux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_LdblCountMinterm.\n\n  @details It is based on the following identity. Let |f| be the\n  number of minterms of f. Then:\n\n      |f| = (|f0|+|f1|)/2\n\n  where f0 and f1 are the two cofactors of f.  Does not use the\n  identity |f'| = max - |f|, to minimize loss of accuracy due to\n  roundoff.\n\n  @return the number of minterms of the function rooted at node.\n\n  @sideeffect None\n\n*/\nstatic long double\nddLdblCountMintermAux(\n  DdManager const *manager,\n  DdNode *node,\n  long double max,\n  st_table *table)\n{\n    DdNode *t, *e;\n    long double min, minT, minE;\n    long double *res;\n    if (cuddIsConstant(node)) {\n        if (node == manager->background) {\n            return 0.0L;\n        } else {\n            return max;\n        }\n    }\n    if (node->ref != 1 && st_lookup(table, node, (void **) &res)) {\n        return *res;\n    }\n\n    t = cuddT(node); e = cuddE(node);\n\n    minT = ddLdblCountMintermAux(manager, t, max, table);\n    if (minT == (long double) CUDD_OUT_OF_MEM)\n        return((long double) CUDD_OUT_OF_MEM);\n    minT *= 0.5L;\n    minE = ddLdblCountMintermAux(manager, Cudd_Regular(e), max, table);\n    if (minE == (long double) CUDD_OUT_OF_MEM)\n        return((long double) CUDD_OUT_OF_MEM);\n    if (Cudd_IsComplement(e)) {\n        minE = max - minE;\n    }\n    minE *= 0.5L;\n    min = minT + minE;\n    if (node->ref != 1) {\n        res = ALLOC(long double, 1);\n        if (res == NULL)\n            return((long double) CUDD_OUT_OF_MEM);\n        *res = min;\n        if (st_insert(table, node, res) == ST_OUT_OF_MEM) {\n            FREE(res);\n            return((long double) CUDD_OUT_OF_MEM);\n        }\n    }\n    return(min);\n\n} /* end of ddLdblCountMintermAux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_CountPathsToNonZero.\n\n  @details It is based on the following identity. Let |f| be the\n  number of paths of f. Then:\n\n      |f| = |f0|+|f1|\n\n  where f0 and f1 are the two cofactors of f.\n\n  @return the number of paths of the function rooted at node.\n\n  @sideeffect None\n\n*/\nstatic double\nddCountPathsToNonZero(\n  DdNode * N,\n  st_table * table)\n{\n\n    DdNode\t*node, *Nt, *Ne;\n    double\tpaths, *ppaths, paths1, paths2;\n    void\t*dummy;\n\n    node = Cudd_Regular(N);\n    if (cuddIsConstant(node)) {\n\treturn((double) !(Cudd_IsComplement(N) || cuddV(node)==DD_ZERO_VAL));\n    }\n    if (st_lookup(table, N, &dummy)) {\n\tpaths = *(double *) dummy;\n\treturn(paths);\n    }\n\n    Nt = cuddT(node); Ne = cuddE(node);\n    if (node != N) {\n\tNt = Cudd_Not(Nt); Ne = Cudd_Not(Ne);\n    }\n\n    paths1 = ddCountPathsToNonZero(Nt,table);\n    if (paths1 == (double)CUDD_OUT_OF_MEM) return((double)CUDD_OUT_OF_MEM);\n    paths2 = ddCountPathsToNonZero(Ne,table);\n    if (paths2 == (double)CUDD_OUT_OF_MEM) return((double)CUDD_OUT_OF_MEM);\n    paths = paths1 + paths2;\n\n    ppaths = ALLOC(double,1);\n    if (ppaths == NULL) {\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n\n    *ppaths = paths;\n\n    if (st_add_direct(table, N, ppaths) == ST_OUT_OF_MEM) {\n\tFREE(ppaths);\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    return(paths);\n\n} /* end of ddCountPathsToNonZero */\n\n\n/**\n  @brief Performs the recursive step of Cudd_Support.\n\n  @details Performs a DFS from f. The support is accumulated in supp\n  as a side effect. Uses the LSB of the then pointer as visited flag.\n\n  @sideeffect None\n\n  @see ddClearFlag\n\n*/\nstatic void\nddSupportStep(\n  DdNode * f,\n  int * support)\n{\n    if (cuddIsConstant(f) || Cudd_IsComplement(f->next))\n\treturn;\n\n    support[f->index] = 1;\n    ddSupportStep(cuddT(f),support);\n    ddSupportStep(Cudd_Regular(cuddE(f)),support);\n    /* Mark as visited. */\n    f->next = Cudd_Complement(f->next);\n\n} /* end of ddSupportStep */\n\n\n/**\n  @brief Performs a DFS from f, clearing the LSB of the next pointers.\n\n  @sideeffect None\n\n  @see ddSupportStep ddFindSupport ddLeavesInt ddDagInt\n\n*/\nstatic void\nddClearFlag(\n  DdNode * f)\n{\n    if (!Cudd_IsComplement(f->next)) {\n\treturn;\n    }\n    /* Clear visited flag. */\n    f->next = Cudd_Regular(f->next);\n    if (cuddIsConstant(f)) {\n\treturn;\n    }\n    ddClearFlag(cuddT(f));\n    ddClearFlag(Cudd_Regular(cuddE(f)));\n    return;\n\n} /* end of ddClearFlag */\n\n\n/**\n  @brief Performs the recursive step of Cudd_CountLeaves.\n\n  @return the number of leaves in the %DD rooted at n.\n\n  @sideeffect None\n\n  @see Cudd_CountLeaves\n\n*/\nstatic int\nddLeavesInt(\n  DdNode * n)\n{\n    int tval, eval;\n\n    if (Cudd_IsComplement(n->next)) {\n\treturn(0);\n    }\n    n->next = Cudd_Not(n->next);\n    if (cuddIsConstant(n)) {\n\treturn(1);\n    }\n    tval = ddLeavesInt(cuddT(n));\n    eval = ddLeavesInt(Cudd_Regular(cuddE(n)));\n    return(tval + eval);\n\n} /* end of ddLeavesInt */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddPickArbitraryMinterms.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect none\n\n  @see Cudd_bddPickArbitraryMinterms\n\n*/\nstatic int\nddPickArbitraryMinterms(\n  DdManager *dd,\n  DdNode *node,\n  int nvars,\n  int nminterms,\n  char **string)\n{\n    DdNode *N, *T, *E;\n    DdNode *one, *bzero;\n    int    i, t, result;\n    double min1, min2;\n\n    if (string == NULL || node == NULL) return(0);\n\n    /* The constant 0 function has no on-set cubes. */\n    one = DD_ONE(dd);\n    bzero = Cudd_Not(one);\n    if (nminterms == 0 || node == bzero) return(1);\n    if (node == one) {\n\treturn(1);\n    }\n\n    N = Cudd_Regular(node);\n    T = cuddT(N); E = cuddE(N);\n    if (Cudd_IsComplement(node)) {\n\tT = Cudd_Not(T); E = Cudd_Not(E);\n    }\n\n    min1 = Cudd_CountMinterm(dd, T, nvars) / 2.0;\n    if (min1 == (double)CUDD_OUT_OF_MEM) return(0);\n    min2 = Cudd_CountMinterm(dd, E, nvars) / 2.0;\n    if (min2 == (double)CUDD_OUT_OF_MEM) return(0);\n\n    t = (int)((double)nminterms * min1 / (min1 + min2) + 0.5);\n    for (i = 0; i < t; i++)\n\tstring[i][N->index] = '1';\n    for (i = t; i < nminterms; i++)\n\tstring[i][N->index] = '0';\n\n    result = ddPickArbitraryMinterms(dd,T,nvars,t,&string[0]);\n    if (result == 0)\n\treturn(0);\n    result = ddPickArbitraryMinterms(dd,E,nvars,nminterms-t,&string[t]);\n    return(result);\n\n} /* end of ddPickArbitraryMinterms */\n\n\n/**\n  @brief Finds a representative cube of a %BDD.\n\n  @details Finds a representative cube of a %BDD with the weight of\n  each variable. From the top variable, if the weight is greater than or\n  equal to 0.0, choose THEN branch unless the child is the constant 0.\n  Otherwise, choose ELSE branch unless the child is the constant 0.\n\n  @sideeffect Cudd_SubsetWithMaskVars Cudd_bddPickOneCube\n\n*/\nstatic int\nddPickRepresentativeCube(\n  DdManager *dd,\n  DdNode *node,\n  double *weight,\n  char *string)\n{\n    DdNode *N, *T, *E;\n    DdNode *one, *bzero;\n\n    if (string == NULL || node == NULL) return(0);\n\n    /* The constant 0 function has no on-set cubes. */\n    one = DD_ONE(dd);\n    bzero = Cudd_Not(one);\n    if (node == bzero) return(0);\n\n    if (node == DD_ONE(dd)) return(1);\n\n    for (;;) {\n\tN = Cudd_Regular(node);\n\tif (N == one)\n\t    break;\n\tT = cuddT(N);\n\tE = cuddE(N);\n\tif (Cudd_IsComplement(node)) {\n\t    T = Cudd_Not(T);\n\t    E = Cudd_Not(E);\n\t}\n\tif (weight[N->index] >= 0.0) {\n\t    if (T == bzero) {\n\t\tnode = E;\n\t\tstring[N->index] = '0';\n\t    } else {\n\t\tnode = T;\n\t\tstring[N->index] = '1';\n\t    }\n\t} else {\n\t    if (E == bzero) {\n\t\tnode = T;\n\t\tstring[N->index] = '1';\n\t    } else {\n\t\tnode = E;\n\t\tstring[N->index] = '0';\n\t    }\n\t}\n    }\n    return(1);\n\n} /* end of ddPickRepresentativeCube */\n\n\n/**\n  @brief Frees the memory used to store the minterm counts recorded\n  in the visited table.\n\n  @return ST_CONTINUE.\n\n  @sideeffect None\n\n*/\nstatic enum st_retval\nddEpdFree(\n  void * key,\n  void * value,\n  void * arg)\n{\n    EpDouble *epd = (EpDouble *) value;\n\n    (void) key; /* avoid warning */\n    (void) arg; /* avoid warning */\n    EpdFree(epd);\n    return(ST_CONTINUE);\n\n} /* end of ddEpdFree */\n\n\n/**\n  @brief Recursively find the support of f.\n\n  @details This function uses the LSB of the next field of the nodes\n  of f as visited flag.  It also uses the LSB of the next field of the\n  variables as flag to remember whether a certain index has already\n  been seen.  Finally, it uses the manager stack to record all seen\n  indices.\n\n  @sideeffect The stack pointer SP is modified by side-effect.  The next\n  fields are changed and need to be reset.\n\n*/\nstatic void\nddFindSupport(\n  DdManager *dd,\n  DdNode *f,\n  int *SP)\n{\n    unsigned int index;\n    DdNode *var;\n\n    if (cuddIsConstant(f) || Cudd_IsComplement(f->next)) {\n\treturn;\n    }\n\n    index = f->index;\n    var = dd->vars[index];\n    /* It is possible that var is embedded in f.  That causes no problem,\n    ** though, because if we see it after encountering another node with\n    ** the same index, nothing is supposed to happen.\n    */\n    if (!Cudd_IsComplement(var->next)) {\n        var->next = Cudd_Complement(var->next);\n        dd->stack[*SP] = (DdNode *)(ptruint) index;\n        (*SP)++;\n    }\n    ddFindSupport(dd, cuddT(f), SP);\n    ddFindSupport(dd, Cudd_Regular(cuddE(f)), SP);\n    /* Mark as visited. */\n    f->next = Cudd_Complement(f->next);\n\n} /* end of ddFindSupport */\n\n\n/**\n  @brief Clears visited flags for variables.\n\n  @sideeffect None\n\n*/\nstatic void\nddClearVars(\n  DdManager *dd,\n  int SP)\n{\n    int i;\n\n    for (i = 0; i < SP; i++) {\n        int index = (int) (ptrint) dd->stack[i];\n        DdNode *var = dd->vars[index];\n        var->next = Cudd_Regular(var->next);\n    }\n    \n} /* end of ddClearVars */\n\n\n/**\n  @brief Compares indices for qsort.\n\n  @details Subtracting these integers cannot produce overflow, because\n  they are non-negative.\n\n  @sideeffect None\n\n*/\nstatic int\nindexCompare(\n  const void *a,\n  const void *b)\n{\n    int ia = *(int const *) a;\n    int ib = *(int const *) b;\n    return(ia - ib);\n\n} /* end of indexCompare */\n\n\n/**\n  @brief Frees the memory used to store the minterm counts recorded in the\n  visited table by Cudd_LdblCountMinterm.\n\n  @returns ST_CONTINUE.\n\n  @sideeffect None\n*/\nstatic enum st_retval\nddLdblFree(\n  void * key,\n  void * value,\n  void * arg)\n{\n    long double * ld = (long double *) value;\n\n    (void) key; /* avoid warning */\n    (void) arg; /* avoid warning */\n    FREE(ld);\n    return(ST_CONTINUE);\n\n} /* end of ddLdblFree */\n\n\n#if HAVE_POWL != 1\n/**\n  @brief Replacement for standard library powl.\n\n  @details Some systems' C libraries, notably Cygwin as of 2015,\n  lack an implementation of powl.  This simple-minded replacement\n  works for integral powers.  It is based on iterative squaring.\n\n  @return base raised to the exponent.\n*/\nstatic long double\npowl(\n  long double base,\n  long double exponent)\n{\n    long exp;\n    long double power = 1.0L, square = base;\n    if (exponent < 0.0L) {\n        exp = (long) -exponent;\n    } else {\n        exp = (long) exponent;\n    }\n    /* Compute base^exponent by iterative squaring.\n     * The loop invariant is power * square^exp = base^exponent.\n     */\n    while (exp > 0) {\n        if (exp & 1L)\n            power *= square;\n        square *= square;\n        exp >>= 1L;\n    }\n    if (exponent < 0.0L) {\n        power = 1.0L / power;\n    }\n    return(power);\n\n} /* end of powl */\n#endif\n"
  },
  {
    "path": "cudd/cudd/cuddWindow.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for variable reordering by window permutation.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int ddWindow2 (DdManager *table, int low, int high);\nstatic int ddWindowConv2 (DdManager *table, int low, int high);\nstatic int ddPermuteWindow3 (DdManager *table, int x);\nstatic int ddWindow3 (DdManager *table, int low, int high);\nstatic int ddWindowConv3 (DdManager *table, int low, int high);\nstatic int ddPermuteWindow4 (DdManager *table, int w);\nstatic int ddWindow4 (DdManager *table, int low, int high);\nstatic int ddWindowConv4 (DdManager *table, int low, int high);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Reorders by applying the method of the sliding window.\n\n  @details Tries all possible permutations to the variables in a\n  window that slides from low to high. The size of the window is\n  determined by submethod.  Assumes that no dead nodes are present.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddWindowReorder(\n  DdManager * table /**< %DD table */,\n  int low /**< lowest index to reorder */,\n  int high /**< highest index to reorder */,\n  Cudd_ReorderingType submethod /**< window reordering option */)\n{\n\n    int res;\n#ifdef DD_DEBUG\n    int supposedOpt;\n#endif\n\n    switch (submethod) {\n    case CUDD_REORDER_WINDOW2:\n\tres = ddWindow2(table,low,high);\n\tbreak;\n    case CUDD_REORDER_WINDOW3:\n\tres = ddWindow3(table,low,high);\n\tbreak;\n    case CUDD_REORDER_WINDOW4:\n\tres = ddWindow4(table,low,high);\n\tbreak;\n    case CUDD_REORDER_WINDOW2_CONV:\n\tres = ddWindowConv2(table,low,high);\n\tbreak;\n    case CUDD_REORDER_WINDOW3_CONV:\n\tres = ddWindowConv3(table,low,high);\n#ifdef DD_DEBUG\n\tsupposedOpt = (int) (table->keys - table->isolated);\n\tres = ddWindow3(table,low,high);\n\tif (table->keys - table->isolated != (unsigned) supposedOpt) {\n\t    (void) fprintf(table->err, \"Convergence failed! (%d != %d)\\n\",\n\t\t\t   table->keys - table->isolated, supposedOpt);\n\t}\n#endif\n\tbreak;\n    case CUDD_REORDER_WINDOW4_CONV:\n\tres = ddWindowConv4(table,low,high);\n#ifdef DD_DEBUG\n\tsupposedOpt = (int) (table->keys - table->isolated);\n\tres = ddWindow4(table,low,high);\n\tif (table->keys - table->isolated != (unsigned) supposedOpt) {\n\t    (void) fprintf(table->err,\"Convergence failed! (%d != %d)\\n\",\n\t\t\t   table->keys - table->isolated, supposedOpt);\n\t}\n#endif\n\tbreak;\n    default: return(0);\n    }\n\n    return(res);\n\n} /* end of cuddWindowReorder */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Reorders by applying a sliding window of width 2.\n\n  @details Tries both permutations of the variables in a window that\n  slides from low to high.  Assumes that no dead nodes are present.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddWindow2(\n  DdManager * table,\n  int  low,\n  int  high)\n{\n\n    int x;\n    int res;\n    int size;\n\n#ifdef DD_DEBUG\n    assert(low >= 0 && high < table->size);\n#endif\n\n    if (high-low < 1) return(0);\n\n    res = (int) (table->keys - table->isolated);\n    for (x = low; x < high; x++) {\n\tsize = res;\n\tres = cuddSwapInPlace(table,x,x+1);\n\tif (res == 0) return(0);\n\tif (res >= size) { /* no improvement: undo permutation */\n\t    res = cuddSwapInPlace(table,x,x+1);\n\t    if (res == 0) return(0);\n\t}\n#ifdef DD_STATS\n\tif (res < size) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n    return(1);\n\n} /* end of ddWindow2 */\n\n\n/**\n  @brief Reorders by repeatedly applying a sliding window of width 2.\n\n  @details Tries both permutations of the variables in a window that\n  slides from low to high.  Assumes that no dead nodes are present.\n  Uses an event-driven approach to determine convergence.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddWindowConv2(\n  DdManager * table,\n  int  low,\n  int  high)\n{\n    int x;\n    int res;\n    int nwin;\n    int newevent;\n    int *events;\n    int size;\n\n#ifdef DD_DEBUG\n    assert(low >= 0 && high < table->size);\n#endif\n\n    if (high-low < 1) return(ddWindowConv2(table,low,high));\n\n    nwin = high-low;\n    events = ALLOC(int,nwin);\n    if (events == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (x=0; x<nwin; x++) {\n\tevents[x] = 1;\n    }\n\n    res = (int) (table->keys - table->isolated);\n    do {\n\tnewevent = 0;\n\tfor (x=0; x<nwin; x++) {\n\t    if (events[x]) {\n\t\tsize = res;\n\t\tres = cuddSwapInPlace(table,x+low,x+low+1);\n\t\tif (res == 0) {\n\t\t    FREE(events);\n\t\t    return(0);\n\t\t}\n\t\tif (res >= size) { /* no improvement: undo permutation */\n\t\t    res = cuddSwapInPlace(table,x+low,x+low+1);\n\t\t    if (res == 0) {\n\t\t\tFREE(events);\n\t\t\treturn(0);\n\t\t    }\n\t\t}\n\t\tif (res < size) {\n\t\t    if (x < nwin-1)\tevents[x+1] = 1;\n\t\t    if (x > 0)\t\tevents[x-1] = 1;\n\t\t    newevent = 1;\n\t\t}\n\t\tevents[x] = 0;\n#ifdef DD_STATS\n\t\tif (res < size) {\n\t\t    (void) fprintf(table->out,\"-\");\n\t\t} else {\n\t\t    (void) fprintf(table->out,\"=\");\n\t\t}\n\t\tfflush(table->out);\n#endif\n\t    }\n\t}\n#ifdef DD_STATS\n\tif (newevent) {\n\t    (void) fprintf(table->out,\"|\");\n\t    fflush(table->out);\n\t}\n#endif\n    } while (newevent);\n\n    FREE(events);\n\n    return(1);\n\n} /* end of ddWindowConv3 */\n\n\n/**\n  @brief Tries all the permutations of the three variables between\n  x and x+2 and retains the best.\n\n  @details Assumes that no dead nodes are present.\n\n  @return the index of the best permutation (1-6) in case of success;\n  0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddPermuteWindow3(\n  DdManager * table,\n  int  x)\n{\n    int y,z;\n    int\tsize,sizeNew;\n    int\tbest;\n\n#ifdef DD_DEBUG\n    assert(table->dead == 0);\n    assert(x+2 < table->size);\n#endif\n\n    size = (int) (table->keys - table->isolated);\n    y = x+1; z = y+1;\n\n    /* The permutation pattern is:\n    ** (x,y)(y,z)\n    ** repeated three times to get all 3! = 6 permutations.\n    */\n#define ABC 1\n    best = ABC;\n\n#define\tBAC 2\n    sizeNew = cuddSwapInPlace(table,x,y);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = BAC;\n\tsize = sizeNew;\n    }\n#define BCA 3\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = BCA;\n\tsize = sizeNew;\n    }\n#define CBA 4\n    sizeNew = cuddSwapInPlace(table,x,y);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = CBA;\n\tsize = sizeNew;\n    }\n#define CAB 5\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = CAB;\n\tsize = sizeNew;\n    }\n#define ACB 6\n    sizeNew = cuddSwapInPlace(table,x,y);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = ACB;\n\tsize = sizeNew;\n    }\n\n    /* Now take the shortest route to the best permuytation.\n    ** The initial permutation is ACB.\n    */\n    switch(best) {\n    case BCA: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case CBA: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case ABC: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case ACB: break;\n    case BAC: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case CAB: if (!cuddSwapInPlace(table,x,y)) return(0);\n\t       break;\n    default: return(0);\n    }\n\n#ifdef DD_DEBUG\n    assert(table->keys - table->isolated == (unsigned) size);\n#endif\n\n    return(best);\n\n} /* end of ddPermuteWindow3 */\n\n\n/**\n  @brief Reorders by applying a sliding window of width 3.\n\n  @details Tries all possible permutations to the variables in a\n  window that slides from low to high.  Assumes that no dead nodes are\n  present.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddWindow3(\n  DdManager * table,\n  int  low,\n  int  high)\n{\n\n    int x;\n    int res;\n\n#ifdef DD_DEBUG\n    assert(low >= 0 && high < table->size);\n#endif\n\n    if (high-low < 2) return(ddWindow2(table,low,high));\n\n    for (x = low; x+1 < high; x++) {\n\tres = ddPermuteWindow3(table,x);\n\tif (res == 0) return(0);\n#ifdef DD_STATS\n\tif (res == ABC) {\n\t    (void) fprintf(table->out,\"=\");\n\t} else {\n\t    (void) fprintf(table->out,\"-\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n    return(1);\n\n} /* end of ddWindow3 */\n\n\n/**\n  @brief Reorders by repeatedly applying a sliding window of width 3.\n\n  @details Tries all possible permutations to the variables in a\n  window that slides from low to high.  Assumes that no dead nodes are\n  present.  Uses an event-driven approach to determine convergence.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddWindowConv3(\n  DdManager * table,\n  int  low,\n  int  high)\n{\n    int x;\n    int res;\n    int nwin;\n    int newevent;\n    int *events;\n\n#ifdef DD_DEBUG\n    assert(low >= 0 && high < table->size);\n#endif\n\n    if (high-low < 2) return(ddWindowConv2(table,low,high));\n\n    nwin = high-low-1;\n    events = ALLOC(int,nwin);\n    if (events == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (x=0; x<nwin; x++) {\n\tevents[x] = 1;\n    }\n\n    do {\n\tnewevent = 0;\n\tfor (x=0; x<nwin; x++) {\n\t    if (events[x]) {\n\t\tres = ddPermuteWindow3(table,x+low);\n\t\tswitch (res) {\n\t\tcase ABC:\n\t\t    break;\n\t\tcase BAC:\n\t\t    if (x < nwin-1)\tevents[x+1] = 1;\n\t\t    if (x > 1)\t\tevents[x-2] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tcase BCA:\n\t\tcase CBA:\n\t\tcase CAB:\n\t\t    if (x < nwin-2)\tevents[x+2] = 1;\n\t\t    if (x < nwin-1)\tevents[x+1] = 1;\n\t\t    if (x > 0)\t\tevents[x-1] = 1;\n\t\t    if (x > 1)\t\tevents[x-2] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tcase ACB:\n\t\t    if (x < nwin-2)\tevents[x+2] = 1;\n\t\t    if (x > 0)\t\tevents[x-1] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tdefault:\n\t\t    FREE(events);\n\t\t    return(0);\n\t\t}\n\t\tevents[x] = 0;\n#ifdef DD_STATS\n\t\tif (res == ABC) {\n\t\t    (void) fprintf(table->out,\"=\");\n\t\t} else {\n\t\t    (void) fprintf(table->out,\"-\");\n\t\t}\n\t\tfflush(table->out);\n#endif\n\t    }\n\t}\n#ifdef DD_STATS\n\tif (newevent) {\n\t    (void) fprintf(table->out,\"|\");\n\t    fflush(table->out);\n\t}\n#endif\n    } while (newevent);\n\n    FREE(events);\n\n    return(1);\n\n} /* end of ddWindowConv3 */\n\n\n/**\n  @brief Tries all the permutations of the four variables between w\n  and w+3 and retains the best.\n\n  @details Assumes that no dead nodes are present.\n\n  @return the index of the best permutation (1-24) in case of success;\n  0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddPermuteWindow4(\n  DdManager * table,\n  int  w)\n{\n    int x,y,z;\n    int\tsize,sizeNew;\n    int\tbest;\n\n#ifdef DD_DEBUG\n    assert(table->dead == 0);\n    assert(w+3 < table->size);\n#endif\n\n    size = (int) (table->keys - table->isolated);\n    x = w+1; y = x+1; z = y+1;\n\n    /* The permutation pattern is:\n     * (w,x)(y,z)(w,x)(x,y)\n     * (y,z)(w,x)(y,z)(x,y)\n     * repeated three times to get all 4! = 24 permutations.\n     * This gives a hamiltonian circuit of Cayley's graph.\n     * The codes to the permutation are assigned in topological order.\n     * The permutations at lower distance from the final permutation are\n     * assigned lower codes. This way we can choose, between\n     * permutations that give the same size, one that requires the minimum\n     * number of swaps from the final permutation of the hamiltonian circuit.\n     * There is an exception to this rule: ABCD is given Code 1, to\n     * avoid oscillation when convergence is sought.\n     */\n#define ABCD 1\n    best = ABCD;\n\n#define\tBACD 7\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = BACD;\n\tsize = sizeNew;\n    }\n#define BADC 13\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = BADC;\n\tsize = sizeNew;\n    }\n#define ABDC 8\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size || (sizeNew == size && ABDC < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = ABDC;\n\tsize = sizeNew;\n    }\n#define ADBC 14\n    sizeNew = cuddSwapInPlace(table,x,y);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = ADBC;\n\tsize = sizeNew;\n    }\n#define ADCB 9\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size || (sizeNew == size && ADCB < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = ADCB;\n\tsize = sizeNew;\n    }\n#define DACB 15\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = DACB;\n\tsize = sizeNew;\n    }\n#define DABC 20\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = DABC;\n\tsize = sizeNew;\n    }\n#define DBAC 23\n    sizeNew = cuddSwapInPlace(table,x,y);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = DBAC;\n\tsize = sizeNew;\n    }\n#define BDAC 19\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size || (sizeNew == size && BDAC < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = BDAC;\n\tsize = sizeNew;\n    }\n#define BDCA 21\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size || (sizeNew == size && BDCA < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = BDCA;\n\tsize = sizeNew;\n    }\n#define DBCA 24\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size) {\n\tif (sizeNew == 0) return(0);\n\tbest = DBCA;\n\tsize = sizeNew;\n    }\n#define DCBA 22\n    sizeNew = cuddSwapInPlace(table,x,y);\n    if (sizeNew < size || (sizeNew == size && DCBA < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = DCBA;\n\tsize = sizeNew;\n    }\n#define DCAB 18\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size || (sizeNew == size && DCAB < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = DCAB;\n\tsize = sizeNew;\n    }\n#define CDAB 12\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size || (sizeNew == size && CDAB < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = CDAB;\n\tsize = sizeNew;\n    }\n#define CDBA 17\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size || (sizeNew == size && CDBA < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = CDBA;\n\tsize = sizeNew;\n    }\n#define CBDA 11\n    sizeNew = cuddSwapInPlace(table,x,y);\n    if (sizeNew < size || (sizeNew == size && CBDA < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = CBDA;\n\tsize = sizeNew;\n    }\n#define BCDA 16\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size || (sizeNew == size && BCDA < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = BCDA;\n\tsize = sizeNew;\n    }\n#define BCAD 10\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size || (sizeNew == size && BCAD < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = BCAD;\n\tsize = sizeNew;\n    }\n#define CBAD 5\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size || (sizeNew == size && CBAD < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = CBAD;\n\tsize = sizeNew;\n    }\n#define CABD 3\n    sizeNew = cuddSwapInPlace(table,x,y);\n    if (sizeNew < size || (sizeNew == size && CABD < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = CABD;\n\tsize = sizeNew;\n    }\n#define CADB 6\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size || (sizeNew == size && CADB < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = CADB;\n\tsize = sizeNew;\n    }\n#define ACDB 4\n    sizeNew = cuddSwapInPlace(table,w,x);\n    if (sizeNew < size || (sizeNew == size && ACDB < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = ACDB;\n\tsize = sizeNew;\n    }\n#define ACBD 2\n    sizeNew = cuddSwapInPlace(table,y,z);\n    if (sizeNew < size || (sizeNew == size && ACBD < best)) {\n\tif (sizeNew == 0) return(0);\n\tbest = ACBD;\n\tsize = sizeNew;\n    }\n\n    /* Now take the shortest route to the best permutation.\n    ** The initial permutation is ACBD.\n    */\n    switch(best) {\n    case DBCA: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case BDCA: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case CDBA: if (!cuddSwapInPlace(table,w,x)) return(0);\n    case ADBC: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case ABDC: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case ACDB: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case ACBD: break;\n    case DCBA: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case BCDA: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case CBDA: if (!cuddSwapInPlace(table,w,x)) return(0);\n\t       if (!cuddSwapInPlace(table,x,y)) return(0);\n\t       if (!cuddSwapInPlace(table,y,z)) return(0);\n\t       break;\n    case DBAC: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case DCAB: if (!cuddSwapInPlace(table,w,x)) return(0);\n    case DACB: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case BACD: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case CABD: if (!cuddSwapInPlace(table,w,x)) return(0);\n\t       break;\n    case DABC: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case BADC: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case CADB: if (!cuddSwapInPlace(table,w,x)) return(0);\n\t       if (!cuddSwapInPlace(table,y,z)) return(0);\n\t       break;\n    case BDAC: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case CDAB: if (!cuddSwapInPlace(table,w,x)) return(0);\n    case ADCB: if (!cuddSwapInPlace(table,y,z)) return(0);\n    case ABCD: if (!cuddSwapInPlace(table,x,y)) return(0);\n\t       break;\n    case BCAD: if (!cuddSwapInPlace(table,x,y)) return(0);\n    case CBAD: if (!cuddSwapInPlace(table,w,x)) return(0);\n\t       if (!cuddSwapInPlace(table,x,y)) return(0);\n\t       break;\n    default: return(0);\n    }\n\n#ifdef DD_DEBUG\n    assert(table->keys - table->isolated == (unsigned) size);\n#endif\n\n    return(best);\n\n} /* end of ddPermuteWindow4 */\n\n\n/**\n  @brief Reorders by applying a sliding window of width 4.\n\n  @details Tries all possible permutations to the variables in a\n  window that slides from low to high.  Assumes that no dead nodes are\n  present.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddWindow4(\n  DdManager * table,\n  int  low,\n  int  high)\n{\n\n    int w;\n    int res;\n\n#ifdef DD_DEBUG\n    assert(low >= 0 && high < table->size);\n#endif\n\n    if (high-low < 3) return(ddWindow3(table,low,high));\n\n    for (w = low; w+2 < high; w++) {\n\tres = ddPermuteWindow4(table,w);\n\tif (res == 0) return(0);\n#ifdef DD_STATS\n\tif (res == ABCD) {\n\t    (void) fprintf(table->out,\"=\");\n\t} else {\n\t    (void) fprintf(table->out,\"-\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n    return(1);\n\n} /* end of ddWindow4 */\n\n\n/**\n  @brief Reorders by repeatedly applying a sliding window of width 4.\n\n  @details Tries all possible permutations to the variables in a\n  window that slides from low to high.  Assumes that no dead nodes are\n  present.  Uses an event-driven approach to determine convergence.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nddWindowConv4(\n  DdManager * table,\n  int  low,\n  int  high)\n{\n    int x;\n    int res;\n    int nwin;\n    int newevent;\n    int *events;\n\n#ifdef DD_DEBUG\n    assert(low >= 0 && high < table->size);\n#endif\n\n    if (high-low < 3) return(ddWindowConv3(table,low,high));\n\n    nwin = high-low-2;\n    events = ALLOC(int,nwin);\n    if (events == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (x=0; x<nwin; x++) {\n\tevents[x] = 1;\n    }\n\n    do {\n\tnewevent = 0;\n\tfor (x=0; x<nwin; x++) {\n\t    if (events[x]) {\n\t\tres = ddPermuteWindow4(table,x+low);\n\t\tswitch (res) {\n\t\tcase ABCD:\n\t\t    break;\n\t\tcase BACD:\n\t\t    if (x < nwin-1)\tevents[x+1] = 1;\n\t\t    if (x > 2)\t\tevents[x-3] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tcase BADC:\n\t\t    if (x < nwin-3)\tevents[x+3] = 1;\n\t\t    if (x < nwin-1)\tevents[x+1] = 1;\n\t\t    if (x > 0)\t\tevents[x-1] = 1;\n\t\t    if (x > 2)\t\tevents[x-3] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tcase ABDC:\n\t\t    if (x < nwin-3)\tevents[x+3] = 1;\n\t\t    if (x > 0)\t\tevents[x-1] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tcase ADBC:\n\t\tcase ADCB:\n\t\tcase ACDB:\n\t\t    if (x < nwin-3)\tevents[x+3] = 1;\n\t\t    if (x < nwin-2)\tevents[x+2] = 1;\n\t\t    if (x > 0)\t\tevents[x-1] = 1;\n\t\t    if (x > 1)\t\tevents[x-2] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tcase DACB:\n\t\tcase DABC:\n\t\tcase DBAC:\n\t\tcase BDAC:\n\t\tcase BDCA:\n\t\tcase DBCA:\n\t\tcase DCBA:\n\t\tcase DCAB:\n\t\tcase CDAB:\n\t\tcase CDBA:\n\t\tcase CBDA:\n\t\tcase BCDA:\n\t\tcase CADB:\n\t\t    if (x < nwin-3)\tevents[x+3] = 1;\n\t\t    if (x < nwin-2)\tevents[x+2] = 1;\n\t\t    if (x < nwin-1)\tevents[x+1] = 1;\n\t\t    if (x > 0)\t\tevents[x-1] = 1;\n\t\t    if (x > 1)\t\tevents[x-2] = 1;\n\t\t    if (x > 2)\t\tevents[x-3] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tcase BCAD:\n\t\tcase CBAD:\n\t\tcase CABD:\n\t\t    if (x < nwin-2)\tevents[x+2] = 1;\n\t\t    if (x < nwin-1)\tevents[x+1] = 1;\n\t\t    if (x > 1)\t\tevents[x-2] = 1;\n\t\t    if (x > 2)\t\tevents[x-3] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tcase ACBD:\n\t\t    if (x < nwin-2)\tevents[x+2] = 1;\n\t\t    if (x > 1)\t\tevents[x-2] = 1;\n\t\t    newevent = 1;\n\t\t    break;\n\t\tdefault:\n\t\t    FREE(events);\n\t\t    return(0);\n\t\t}\n\t\tevents[x] = 0;\n#ifdef DD_STATS\n\t\tif (res == ABCD) {\n\t\t    (void) fprintf(table->out,\"=\");\n\t\t} else {\n\t\t    (void) fprintf(table->out,\"-\");\n\t\t}\n\t\tfflush(table->out);\n#endif\n\t    }\n\t}\n#ifdef DD_STATS\n\tif (newevent) {\n\t    (void) fprintf(table->out,\"|\");\n\t    fflush(table->out);\n\t}\n#endif\n    } while (newevent);\n\n    FREE(events);\n\n    return(1);\n\n} /* end of ddWindowConv4 */\n"
  },
  {
    "path": "cudd/cudd/cuddZddCount.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Procedures to count the number of minterms of a %ZDD.\n\n  @author Hyong-Kyoon Shin, In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int cuddZddCountStep (DdNode *P, st_table *table, DdNode *base, DdNode *empty);\nstatic double cuddZddCountDoubleStep (DdNode *P, st_table *table, DdNode *base, DdNode *empty);\nstatic enum st_retval st_zdd_countfree (void *key, void *value, void *arg);\nstatic enum st_retval st_zdd_count_dbl_free (void *key, void *value, void *arg);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Counts the number of minterms in a %ZDD.\n\n  @details Returns an integer representing the number of minterms\n  in a %ZDD.\n\n  @sideeffect None\n\n  @see Cudd_zddCountDouble\n\n*/\nint\nCudd_zddCount(\n  DdManager * zdd,\n  DdNode * P)\n{\n    st_table\t*table;\n    int\t\tres;\n    DdNode\t*base, *empty;\n\n    base  = DD_ONE(zdd);\n    empty = DD_ZERO(zdd);\n    table = st_init_table(st_ptrcmp, st_ptrhash);\n    if (table == NULL) return(CUDD_OUT_OF_MEM);\n    res = cuddZddCountStep(P, table, base, empty);\n    if (res == CUDD_OUT_OF_MEM) {\n\tzdd->errorCode = CUDD_MEMORY_OUT;\n    }\n    st_foreach(table, st_zdd_countfree, NIL(void));\n    st_free_table(table);\n\n    return(res);\n\n} /* end of Cudd_zddCount */\n\n\n/**\n  @brief Counts the number of minterms of a %ZDD.\n\n  @details This procedure is used in Cudd_zddCountMinterm.\n\n  @result the count.  If the procedure runs out of memory, it returns\n  (double) CUDD_OUT_OF_MEM.\n\n  @sideeffect None\n\n  @see Cudd_zddCountMinterm Cudd_zddCount\n\n*/\ndouble\nCudd_zddCountDouble(\n  DdManager * zdd,\n  DdNode * P)\n{\n    st_table\t*table;\n    double\tres;\n    DdNode\t*base, *empty;\n\n    base  = DD_ONE(zdd);\n    empty = DD_ZERO(zdd);\n    table = st_init_table(st_ptrcmp, st_ptrhash);\n    if (table == NULL) return((double)CUDD_OUT_OF_MEM);\n    res = cuddZddCountDoubleStep(P, table, base, empty);\n    if (res == (double)CUDD_OUT_OF_MEM) {\n\tzdd->errorCode = CUDD_MEMORY_OUT;\n    }\n    st_foreach(table, st_zdd_count_dbl_free, NIL(void));\n    st_free_table(table);\n\n    return(res);\n\n} /* end of Cudd_zddCountDouble */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddCount.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddCountStep(\n  DdNode * P,\n  st_table * table,\n  DdNode * base,\n  DdNode * empty)\n{\n    int\t\tres;\n    int\t\t*dummy;\n\n    if (P == empty)\n\treturn(0);\n    if (P == base)\n\treturn(1);\n\n    /* Check cache. */\n    if (st_lookup(table, P, (void **) &dummy)) {\n\tres = *dummy;\n\treturn(res);\n    }\n\n    res = cuddZddCountStep(cuddE(P), table, base, empty) +\n\tcuddZddCountStep(cuddT(P), table, base, empty);\n\n    dummy = ALLOC(int, 1);\n    if (dummy == NULL) {\n\treturn(CUDD_OUT_OF_MEM);\n    }\n    *dummy = res;\n    if (st_insert(table, P, dummy) == ST_OUT_OF_MEM) {\n\tFREE(dummy);\n\treturn(CUDD_OUT_OF_MEM);\n    }\n\n    return(res);\n\n} /* end of cuddZddCountStep */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddCountDouble.\n\n  @sideeffect None\n\n*/\nstatic double\ncuddZddCountDoubleStep(\n  DdNode * P,\n  st_table * table,\n  DdNode * base,\n  DdNode * empty)\n{\n    double\tres;\n    double\t*dummy;\n\n    if (P == empty)\n\treturn((double)0.0);\n    if (P == base)\n\treturn((double)1.0);\n\n    /* Check cache */\n    if (st_lookup(table, P, (void **) &dummy)) {\n\tres = *dummy;\n\treturn(res);\n    }\n\n    res = cuddZddCountDoubleStep(cuddE(P), table, base, empty) +\n\tcuddZddCountDoubleStep(cuddT(P), table, base, empty);\n\n    dummy = ALLOC(double, 1);\n    if (dummy == NULL) {\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n    *dummy = res;\n    if (st_insert(table, P, dummy) == ST_OUT_OF_MEM) {\n\tFREE(dummy);\n\treturn((double)CUDD_OUT_OF_MEM);\n    }\n\n    return(res);\n\n} /* end of cuddZddCountDoubleStep */\n\n\n/**\n  @brief Frees the memory associated with the computed table of\n  Cudd_zddCount.\n\n  @sideeffect None\n\n*/\nstatic enum st_retval\nst_zdd_countfree(\n  void * key,\n  void * value,\n  void * arg)\n{\n    int\t*d = (int *) value;\n\n    (void) key; /* avoid warning */\n    (void) arg; /* avoid warning */\n    FREE(d);\n    return(ST_CONTINUE);\n\n} /* end of st_zdd_countfree */\n\n\n/**\n  @brief Frees the memory associated with the computed table of\n  Cudd_zddCountDouble.\n\n  @sideeffect None\n\n*/\nstatic enum st_retval\nst_zdd_count_dbl_free(\n  void * key,\n  void * value,\n  void * arg)\n{\n    double *d = (double *) value;\n\n    (void) key; /* avoid warning */\n    (void) arg; /* avoid warning */\n    FREE(d);\n    return(ST_CONTINUE);\n\n} /* end of st_zdd_count_dbl_free */\n"
  },
  {
    "path": "cudd/cudd/cuddZddFuncs.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions to manipulate covers represented as ZDDs.\n\n  @author In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Computes the product of two covers represented by ZDDs.\n\n  @details The result is also a %ZDD.  The covers on which\n  Cudd_zddProduct operates use two %ZDD variables for each function\n  variable (one %ZDD variable for each literal of the variable). Those\n  two %ZDD variables should be adjacent in the order.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddUnateProduct\n\n*/\nDdNode\t*\nCudd_zddProduct(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode\t*res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddProduct(dd, f, g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddProduct */\n\n\n/**\n  @brief Computes the product of two unate covers represented as ZDDs.\n\n  @details Unate covers use one %ZDD variable for each %BDD\n  variable.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddProduct\n\n*/\nDdNode\t*\nCudd_zddUnateProduct(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode\t*res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddUnateProduct(dd, f, g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddUnateProduct */\n\n\n/**\n  @brief Applies weak division to two covers.\n\n  @details Applies weak division to two ZDDs representing two covers.\n  The result of weak division depends on the variable order. The\n  covers on which Cudd_zddWeakDiv operates use two %ZDD variables for\n  each function variable (one %ZDD variable for each literal of the\n  variable). Those two %ZDD variables should be adjacent in the order.\n\n  @return a pointer to the %ZDD representing the result if successful;\n  NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddDivide\n\n*/\nDdNode\t*\nCudd_zddWeakDiv(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode\t*res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddWeakDiv(dd, f, g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddWeakDiv */\n\n\n/**\n  @brief Computes the quotient of two unate covers.\n\n  @details Computes the quotient of two unate covers represented by\n  ZDDs.  Unate covers use one %ZDD variable for each %BDD variable.\n\n  @return a pointer to the resulting %ZDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddWeakDiv\n\n*/\nDdNode\t*\nCudd_zddDivide(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode\t*res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddDivide(dd, f, g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddDivide */\n\n\n/**\n  @brief Modified version of Cudd_zddWeakDiv.\n\n  @details This function may disappear in future releases.\n\n  @sideeffect None\n\n  @see Cudd_zddWeakDiv\n\n*/\nDdNode\t*\nCudd_zddWeakDivF(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode\t*res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddWeakDivF(dd, f, g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddWeakDivF */\n\n\n/**\n  @brief Modified version of Cudd_zddDivide.\n\n  @details This function may disappear in future releases.\n\n  @sideeffect None\n\n*/\nDdNode\t*\nCudd_zddDivideF(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    DdNode\t*res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddDivideF(dd, f, g);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddDivideF */\n\n\n/**\n  @brief Computes a complement cover for a %ZDD node.\n\n  @details For lack of a better method, we first extract the function\n  %BDD from the %ZDD cover, then make the complement of the %ZDD cover\n  from the complement of the %BDD node by using ISOP.  The result\n  depends on current variable order.\n\n  @return a pointer to the resulting cover if successful; NULL\n  otherwise.\n\n  @sideeffect The result depends on current variable order.\n\n*/\nDdNode\t*\nCudd_zddComplement(\n  DdManager *dd,\n  DdNode *node)\n{\n    DdNode\t*b, *isop, *zdd_I;\n\n    /* Check cache */\n    zdd_I = cuddCacheLookup1Zdd(dd, cuddZddComplement, node);\n    if (zdd_I)\n\treturn(zdd_I);\n\n    b = Cudd_MakeBddFromZddCover(dd, node);\n    if (!b)\n\treturn(NULL);\n    Cudd_Ref(b);\n    isop = Cudd_zddIsop(dd, Cudd_Not(b), Cudd_Not(b), &zdd_I);\n    if (!isop) {\n\tCudd_RecursiveDeref(dd, b);\n\treturn(NULL);\n    }\n    Cudd_Ref(isop);\n    Cudd_Ref(zdd_I);\n    Cudd_RecursiveDeref(dd, b);\n    Cudd_RecursiveDeref(dd, isop);\n\n    cuddCacheInsert1(dd, cuddZddComplement, node, zdd_I);\n    Cudd_Deref(zdd_I);\n    return(zdd_I);\n} /* end of Cudd_zddComplement */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddProduct.\n\n  @sideeffect None\n\n  @see Cudd_zddProduct\n\n*/\nDdNode\t*\ncuddZddProduct(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    int\t\tv;\n    int\t\ttop_f, top_g;\n    DdNode\t*tmp, *term1, *term2, *term3;\n    DdNode\t*f0, *f1, *fd, *g0, *g1, *gd;\n    DdNode\t*R0, *R1, *Rd, *N0, *N1;\n    DdNode\t*r;\n    DdNode\t*one = DD_ONE(dd);\n    DdNode\t*zero = DD_ZERO(dd);\n    int\t\tflag;\n    int\t\tpv, nv;\n\n    statLine(dd);\n    if (f == zero || g == zero)\n        return(zero);\n    if (f == one)\n        return(g);\n    if (g == one)\n        return(f);\n\n    top_f = dd->permZ[f->index];\n    top_g = dd->permZ[g->index];\n\n    if (top_f > top_g)\n\treturn(cuddZddProduct(dd, g, f));\n\n    /* Check cache */\n    r = cuddCacheLookup2Zdd(dd, cuddZddProduct, f, g);\n    if (r)\n\treturn(r);\n\n    v = (int) f->index;\t/* either yi or zi */\n    flag = cuddZddGetCofactors3(dd, f, v, &f1, &f0, &fd);\n    if (flag == 1)\n\treturn(NULL);\n    Cudd_Ref(f1);\n    Cudd_Ref(f0);\n    Cudd_Ref(fd);\n    flag = cuddZddGetCofactors3(dd, g, v, &g1, &g0, &gd);\n    if (flag == 1) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\treturn(NULL);\n    }\n    Cudd_Ref(g1);\n    Cudd_Ref(g0);\n    Cudd_Ref(gd);\n    pv = cuddZddGetPosVarIndex(dd, v);\n    nv = cuddZddGetNegVarIndex(dd, v);\n\n    Rd = cuddZddProduct(dd, fd, gd);\n    if (Rd == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\treturn(NULL);\n    }\n    Cudd_Ref(Rd);\n\n    term1 = cuddZddProduct(dd, f0, g0);\n    if (term1 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, Rd);\n\treturn(NULL);\n    }\n    Cudd_Ref(term1);\n    term2 = cuddZddProduct(dd, f0, gd);\n    if (term2 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, Rd);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\treturn(NULL);\n    }\n    Cudd_Ref(term2);\n    term3 = cuddZddProduct(dd, fd, g0);\n    if (term3 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, Rd);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\tCudd_RecursiveDerefZdd(dd, term2);\n\treturn(NULL);\n    }\n    Cudd_Ref(term3);\n    Cudd_RecursiveDerefZdd(dd, f0);\n    Cudd_RecursiveDerefZdd(dd, g0);\n    tmp = cuddZddUnion(dd, term1, term2);\n    if (tmp == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, Rd);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\tCudd_RecursiveDerefZdd(dd, term2);\n\tCudd_RecursiveDerefZdd(dd, term3);\n\treturn(NULL);\n    }\n    Cudd_Ref(tmp);\n    Cudd_RecursiveDerefZdd(dd, term1);\n    Cudd_RecursiveDerefZdd(dd, term2);\n    R0 = cuddZddUnion(dd, tmp, term3);\n    if (R0 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, Rd);\n\tCudd_RecursiveDerefZdd(dd, term3);\n\tCudd_RecursiveDerefZdd(dd, tmp);\n\treturn(NULL);\n    }\n    Cudd_Ref(R0);\n    Cudd_RecursiveDerefZdd(dd, tmp);\n    Cudd_RecursiveDerefZdd(dd, term3);\n    N0 = cuddZddGetNode(dd, nv, R0, Rd); /* nv = zi */\n    if (N0 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, Rd);\n\tCudd_RecursiveDerefZdd(dd, R0);\n\treturn(NULL);\n    }\n    Cudd_Ref(N0);\n    Cudd_RecursiveDerefZdd(dd, R0);\n    Cudd_RecursiveDerefZdd(dd, Rd);\n\n    term1 = cuddZddProduct(dd, f1, g1);\n    if (term1 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, N0);\n\treturn(NULL);\n    }\n    Cudd_Ref(term1);\n    term2 = cuddZddProduct(dd, f1, gd);\n    if (term2 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, N0);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\treturn(NULL);\n    }\n    Cudd_Ref(term2);\n    term3 = cuddZddProduct(dd, fd, g1);\n    if (term3 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tCudd_RecursiveDerefZdd(dd, N0);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\tCudd_RecursiveDerefZdd(dd, term2);\n\treturn(NULL);\n    }\n    Cudd_Ref(term3);\n    Cudd_RecursiveDerefZdd(dd, f1);\n    Cudd_RecursiveDerefZdd(dd, g1);\n    Cudd_RecursiveDerefZdd(dd, fd);\n    Cudd_RecursiveDerefZdd(dd, gd);\n    tmp = cuddZddUnion(dd, term1, term2);\n    if (tmp == NULL) {\n\tCudd_RecursiveDerefZdd(dd, N0);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\tCudd_RecursiveDerefZdd(dd, term2);\n\tCudd_RecursiveDerefZdd(dd, term3);\n\treturn(NULL);\n    }\n    Cudd_Ref(tmp);\n    Cudd_RecursiveDerefZdd(dd, term1);\n    Cudd_RecursiveDerefZdd(dd, term2);\n    R1 = cuddZddUnion(dd, tmp, term3);\n    if (R1 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, N0);\n\tCudd_RecursiveDerefZdd(dd, term3);\n\tCudd_RecursiveDerefZdd(dd, tmp);\n\treturn(NULL);\n    }\n    Cudd_Ref(R1);\n    Cudd_RecursiveDerefZdd(dd, tmp);\n    Cudd_RecursiveDerefZdd(dd, term3);\n    N1 = cuddZddGetNode(dd, pv, R1, N0); /* pv = yi */\n    if (N1 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, N0);\n\tCudd_RecursiveDerefZdd(dd, R1);\n\treturn(NULL);\n    }\n    Cudd_Ref(N1);\n    Cudd_RecursiveDerefZdd(dd, R1);\n    Cudd_RecursiveDerefZdd(dd, N0);\n\n    cuddCacheInsert2(dd, cuddZddProduct, f, g, N1);\n    Cudd_Deref(N1);\n    return(N1);\n\n} /* end of cuddZddProduct */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddUnateProduct.\n\n  @sideeffect None\n\n  @see Cudd_zddUnateProduct\n\n*/\nDdNode\t*\ncuddZddUnateProduct(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    int\t\tv;\n    int\t\ttop_f, top_g;\n    DdNode\t*term1, *term2, *term3, *term4;\n    DdNode\t*sum1, *sum2;\n    DdNode\t*f0, *f1, *g0, *g1;\n    DdNode\t*r;\n    DdNode\t*one = DD_ONE(dd);\n    DdNode\t*zero = DD_ZERO(dd);\n    int\t\tflag;\n\n    statLine(dd);\n    if (f == zero || g == zero)\n        return(zero);\n    if (f == one)\n        return(g);\n    if (g == one)\n        return(f);\n\n    top_f = dd->permZ[f->index];\n    top_g = dd->permZ[g->index];\n\n    if (top_f > top_g)\n\treturn(cuddZddUnateProduct(dd, g, f));\n\n    /* Check cache */\n    r = cuddCacheLookup2Zdd(dd, cuddZddUnateProduct, f, g);\n    if (r)\n\treturn(r);\n\n    v = (int) f->index;\t/* either yi or zi */\n    flag = cuddZddGetCofactors2(dd, f, v, &f1, &f0);\n    if (flag == 1)\n\treturn(NULL);\n    Cudd_Ref(f1);\n    Cudd_Ref(f0);\n    flag = cuddZddGetCofactors2(dd, g, v, &g1, &g0);\n    if (flag == 1) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\treturn(NULL);\n    }\n    Cudd_Ref(g1);\n    Cudd_Ref(g0);\n\n    term1 = cuddZddUnateProduct(dd, f1, g1);\n    if (term1 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\treturn(NULL);\n    }\n    Cudd_Ref(term1);\n    term2 = cuddZddUnateProduct(dd, f1, g0);\n    if (term2 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\treturn(NULL);\n    }\n    Cudd_Ref(term2);\n    term3 = cuddZddUnateProduct(dd, f0, g1);\n    if (term3 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\tCudd_RecursiveDerefZdd(dd, term2);\n\treturn(NULL);\n    }\n    Cudd_Ref(term3);\n    term4 = cuddZddUnateProduct(dd, f0, g0);\n    if (term4 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\tCudd_RecursiveDerefZdd(dd, term2);\n\tCudd_RecursiveDerefZdd(dd, term3);\n\treturn(NULL);\n    }\n    Cudd_Ref(term4);\n    Cudd_RecursiveDerefZdd(dd, f1);\n    Cudd_RecursiveDerefZdd(dd, f0);\n    Cudd_RecursiveDerefZdd(dd, g1);\n    Cudd_RecursiveDerefZdd(dd, g0);\n    sum1 = cuddZddUnion(dd, term1, term2);\n    if (sum1 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, term1);\n\tCudd_RecursiveDerefZdd(dd, term2);\n\tCudd_RecursiveDerefZdd(dd, term3);\n\tCudd_RecursiveDerefZdd(dd, term4);\n\treturn(NULL);\n    }\n    Cudd_Ref(sum1);\n    Cudd_RecursiveDerefZdd(dd, term1);\n    Cudd_RecursiveDerefZdd(dd, term2);\n    sum2 = cuddZddUnion(dd, sum1, term3);\n    if (sum2 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, term3);\n\tCudd_RecursiveDerefZdd(dd, term4);\n\tCudd_RecursiveDerefZdd(dd, sum1);\n\treturn(NULL);\n    }\n    Cudd_Ref(sum2);\n    Cudd_RecursiveDerefZdd(dd, sum1);\n    Cudd_RecursiveDerefZdd(dd, term3);\n    r = cuddZddGetNode(dd, v, sum2, term4);\n    if (r == NULL) {\n\tCudd_RecursiveDerefZdd(dd, term4);\n\tCudd_RecursiveDerefZdd(dd, sum2);\n\treturn(NULL);\n    }\n    Cudd_Ref(r);\n    Cudd_RecursiveDerefZdd(dd, sum2);\n    Cudd_RecursiveDerefZdd(dd, term4);\n\n    cuddCacheInsert2(dd, cuddZddUnateProduct, f, g, r);\n    Cudd_Deref(r);\n    return(r);\n\n} /* end of cuddZddUnateProduct */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddWeakDiv.\n\n  @sideeffect None\n\n  @see Cudd_zddWeakDiv\n\n*/\nDdNode\t*\ncuddZddWeakDiv(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    int\t\tv;\n    DdNode\t*one = DD_ONE(dd);\n    DdNode\t*zero = DD_ZERO(dd);\n    DdNode\t*f0, *f1, *fd, *g0, *g1, *gd;\n    DdNode\t*q, *tmp;\n    DdNode\t*r;\n    int\t\tflag;\n\n    statLine(dd);\n    if (g == one)\n\treturn(f);\n    if (f == zero || f == one)\n\treturn(zero);\n    if (f == g)\n\treturn(one);\n\n    /* Check cache. */\n    r = cuddCacheLookup2Zdd(dd, cuddZddWeakDiv, f, g);\n    if (r)\n\treturn(r);\n\n    v = (int) g->index;\n\n    flag = cuddZddGetCofactors3(dd, f, v, &f1, &f0, &fd);\n    if (flag == 1)\n\treturn(NULL);\n    Cudd_Ref(f1);\n    Cudd_Ref(f0);\n    Cudd_Ref(fd);\n    flag = cuddZddGetCofactors3(dd, g, v, &g1, &g0, &gd);\n    if (flag == 1) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\treturn(NULL);\n    }\n    Cudd_Ref(g1);\n    Cudd_Ref(g0);\n    Cudd_Ref(gd);\n\n    q = g;\n\n    if (g0 != zero) {\n\tq = cuddZddWeakDiv(dd, f0, g0);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, f0);\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDerefZdd(dd, g1);\n\t    Cudd_RecursiveDerefZdd(dd, g0);\n\t    Cudd_RecursiveDerefZdd(dd, gd);\n\t    return(NULL);\n\t}\n\tCudd_Ref(q);\n    }\n    else\n\tCudd_Ref(q);\n    Cudd_RecursiveDerefZdd(dd, f0);\n    Cudd_RecursiveDerefZdd(dd, g0);\n\n    if (q == zero) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tcuddCacheInsert2(dd, cuddZddWeakDiv, f, g, zero);\n\tCudd_Deref(q);\n\treturn(zero);\n    }\n\n    if (g1 != zero) {\n\tCudd_RecursiveDerefZdd(dd, q);\n\ttmp = cuddZddWeakDiv(dd, f1, g1);\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, g1);\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDerefZdd(dd, gd);\n\t    return(NULL);\n\t}\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tif (q == g)\n\t    q = tmp;\n\telse {\n\t    q = cuddZddIntersect(dd, q, tmp);\n\t    if (q == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, fd);\n\t\tCudd_RecursiveDerefZdd(dd, gd);\n\t\treturn(NULL);\n\t    }\n\t    Cudd_Ref(q);\n\t    Cudd_RecursiveDerefZdd(dd, tmp);\n\t}\n    }\n    else {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, g1);\n    }\n\n    if (q == zero) {\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tcuddCacheInsert2(dd, cuddZddWeakDiv, f, g, zero);\n\tCudd_Deref(q);\n\treturn(zero);\n    }\n\n    if (gd != zero) {\n\tCudd_RecursiveDerefZdd(dd, q);\n\ttmp = cuddZddWeakDiv(dd, fd, gd);\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDerefZdd(dd, gd);\n\t    return(NULL);\n\t}\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tif (q == g)\n\t    q = tmp;\n\telse {\n\t    q = cuddZddIntersect(dd, q, tmp);\n\t    if (q == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, tmp);\n\t\treturn(NULL);\n\t    }\n\t    Cudd_Ref(q);\n\t    Cudd_RecursiveDerefZdd(dd, tmp);\n\t}\n    }\n    else {\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, gd);\n    }\n\n    cuddCacheInsert2(dd, cuddZddWeakDiv, f, g, q);\n    Cudd_Deref(q);\n    return(q);\n\n} /* end of cuddZddWeakDiv */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddWeakDivF.\n\n  @sideeffect None\n\n  @see Cudd_zddWeakDivF\n\n*/\nDdNode\t*\ncuddZddWeakDivF(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    int\t\tv;\n    int\t\ttop_f, top_g, vf, vg;\n    DdNode\t*one = DD_ONE(dd);\n    DdNode\t*zero = DD_ZERO(dd);\n    DdNode\t*f0, *f1, *fd, *g0, *g1, *gd;\n    DdNode\t*q, *tmp;\n    DdNode\t*r;\n    DdNode\t*term1, *term0, *termd;\n    int\t\tflag;\n    int\t\tpv, nv;\n\n    statLine(dd);\n    if (g == one)\n\treturn(f);\n    if (f == zero || f == one)\n\treturn(zero);\n    if (f == g)\n\treturn(one);\n\n    /* Check cache. */\n    r = cuddCacheLookup2Zdd(dd, cuddZddWeakDivF, f, g);\n    if (r)\n\treturn(r);\n\n    top_f = dd->permZ[f->index];\n    top_g = dd->permZ[g->index];\n    vf = top_f >> 1;\n    vg = top_g >> 1;\n    v = ddMin(top_f, top_g);\n\n    if (v == top_f && vf < vg) {\n\tv = (int) f->index;\n\tflag = cuddZddGetCofactors3(dd, f, v, &f1, &f0, &fd);\n\tif (flag == 1)\n\t    return(NULL);\n\tCudd_Ref(f1);\n\tCudd_Ref(f0);\n\tCudd_Ref(fd);\n\n\tpv = cuddZddGetPosVarIndex(dd, v);\n\tnv = cuddZddGetNegVarIndex(dd, v);\n\n\tterm1 = cuddZddWeakDivF(dd, f1, g);\n\tif (term1 == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, f0);\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    return(NULL);\n\t}\n\tCudd_Ref(term1);\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tterm0 = cuddZddWeakDivF(dd, f0, g);\n\tif (term0 == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f0);\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDerefZdd(dd, term1);\n\t    return(NULL);\n\t}\n\tCudd_Ref(term0);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\ttermd = cuddZddWeakDivF(dd, fd, g);\n\tif (termd == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDerefZdd(dd, term1);\n\t    Cudd_RecursiveDerefZdd(dd, term0);\n\t    return(NULL);\n\t}\n\tCudd_Ref(termd);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\n\ttmp = cuddZddGetNode(dd, nv, term0, termd); /* nv = zi */\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, term1);\n\t    Cudd_RecursiveDerefZdd(dd, term0);\n\t    Cudd_RecursiveDerefZdd(dd, termd);\n\t    return(NULL);\n\t}\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDerefZdd(dd, term0);\n\tCudd_RecursiveDerefZdd(dd, termd);\n\tq = cuddZddGetNode(dd, pv, term1, tmp); /* pv = yi */\n\tif (q == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, term1);\n\t    Cudd_RecursiveDerefZdd(dd, tmp);\n\t    return(NULL);\n\t}\n\tCudd_Ref(q);\n\tCudd_RecursiveDerefZdd(dd, term1);\n\tCudd_RecursiveDerefZdd(dd, tmp);\n\n\tcuddCacheInsert2(dd, cuddZddWeakDivF, f, g, q);\n\tCudd_Deref(q);\n\treturn(q);\n    }\n\n    if (v == top_f)\n\tv = (int) f->index;\n    else\n\tv = (int) g->index;\n\n    flag = cuddZddGetCofactors3(dd, f, v, &f1, &f0, &fd);\n    if (flag == 1)\n\treturn(NULL);\n    Cudd_Ref(f1);\n    Cudd_Ref(f0);\n    Cudd_Ref(fd);\n    flag = cuddZddGetCofactors3(dd, g, v, &g1, &g0, &gd);\n    if (flag == 1) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\treturn(NULL);\n    }\n    Cudd_Ref(g1);\n    Cudd_Ref(g0);\n    Cudd_Ref(gd);\n\n    q = g;\n\n    if (g0 != zero) {\n\tq = cuddZddWeakDivF(dd, f0, g0);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, f0);\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDerefZdd(dd, g1);\n\t    Cudd_RecursiveDerefZdd(dd, g0);\n\t    Cudd_RecursiveDerefZdd(dd, gd);\n\t    return(NULL);\n\t}\n\tCudd_Ref(q);\n    }\n    else\n\tCudd_Ref(q);\n    Cudd_RecursiveDerefZdd(dd, f0);\n    Cudd_RecursiveDerefZdd(dd, g0);\n\n    if (q == zero) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tcuddCacheInsert2(dd, cuddZddWeakDivF, f, g, zero);\n\tCudd_Deref(q);\n\treturn(zero);\n    }\n\n    if (g1 != zero) {\n\tCudd_RecursiveDerefZdd(dd, q);\n\ttmp = cuddZddWeakDivF(dd, f1, g1);\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, g1);\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDerefZdd(dd, gd);\n\t    return(NULL);\n\t}\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tif (q == g)\n\t    q = tmp;\n\telse {\n\t    q = cuddZddIntersect(dd, q, tmp);\n\t    if (q == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, fd);\n\t\tCudd_RecursiveDerefZdd(dd, gd);\n\t\treturn(NULL);\n\t    }\n\t    Cudd_Ref(q);\n\t    Cudd_RecursiveDerefZdd(dd, tmp);\n\t}\n    }\n    else {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, g1);\n    }\n\n    if (q == zero) {\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tcuddCacheInsert2(dd, cuddZddWeakDivF, f, g, zero);\n\tCudd_Deref(q);\n\treturn(zero);\n    }\n\n    if (gd != zero) {\n\tCudd_RecursiveDerefZdd(dd, q);\n\ttmp = cuddZddWeakDivF(dd, fd, gd);\n\tif (tmp == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDerefZdd(dd, gd);\n\t    return(NULL);\n\t}\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, gd);\n\tif (q == g)\n\t    q = tmp;\n\telse {\n\t    q = cuddZddIntersect(dd, q, tmp);\n\t    if (q == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, tmp);\n\t\treturn(NULL);\n\t    }\n\t    Cudd_Ref(q);\n\t    Cudd_RecursiveDerefZdd(dd, tmp);\n\t}\n    }\n    else {\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDerefZdd(dd, gd);\n    }\n\n    cuddCacheInsert2(dd, cuddZddWeakDivF, f, g, q);\n    Cudd_Deref(q);\n    return(q);\n\n} /* end of cuddZddWeakDivF */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddDivide.\n\n  @sideeffect None\n\n  @see Cudd_zddDivide\n\n*/\nDdNode\t*\ncuddZddDivide(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    int\t\tv;\n    DdNode\t*one = DD_ONE(dd);\n    DdNode\t*zero = DD_ZERO(dd);\n    DdNode\t*f0, *f1, *g0, *g1;\n    DdNode\t*q, *r, *tmp;\n    int\t\tflag;\n\n    statLine(dd);\n    if (g == one)\n\treturn(f);\n    if (f == zero || f == one)\n\treturn(zero);\n    if (f == g)\n\treturn(one);\n\n    /* Check cache. */\n    r = cuddCacheLookup2Zdd(dd, cuddZddDivide, f, g);\n    if (r)\n\treturn(r);\n\n    v = (int) g->index;\n\n    flag = cuddZddGetCofactors2(dd, f, v, &f1, &f0);\n    if (flag == 1)\n\treturn(NULL);\n    Cudd_Ref(f1);\n    Cudd_Ref(f0);\n    flag = cuddZddGetCofactors2(dd, g, v, &g1, &g0);\t/* g1 != zero */\n    if (flag == 1) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\treturn(NULL);\n    }\n    Cudd_Ref(g1);\n    Cudd_Ref(g0);\n\n    r = cuddZddDivide(dd, f1, g1);\n    if (r == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\treturn(NULL);\n    }\n    Cudd_Ref(r);\n\n    if (r != zero && g0 != zero) {\n\ttmp = r;\n\tq = cuddZddDivide(dd, f0, g0);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, f0);\n\t    Cudd_RecursiveDerefZdd(dd, g1);\n\t    Cudd_RecursiveDerefZdd(dd, g0);\n\t    return(NULL);\n\t}\n\tCudd_Ref(q);\n\tr = cuddZddIntersect(dd, r, q);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, f0);\n\t    Cudd_RecursiveDerefZdd(dd, g1);\n\t    Cudd_RecursiveDerefZdd(dd, g0);\n\t    Cudd_RecursiveDerefZdd(dd, q);\n\t    return(NULL);\n\t}\n\tCudd_Ref(r);\n\tCudd_RecursiveDerefZdd(dd, q);\n\tCudd_RecursiveDerefZdd(dd, tmp);\n    }\n\n    Cudd_RecursiveDerefZdd(dd, f1);\n    Cudd_RecursiveDerefZdd(dd, f0);\n    Cudd_RecursiveDerefZdd(dd, g1);\n    Cudd_RecursiveDerefZdd(dd, g0);\n    \n    cuddCacheInsert2(dd, cuddZddDivide, f, g, r);\n    Cudd_Deref(r);\n    return(r);\n\n} /* end of cuddZddDivide */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddDivideF.\n\n  @sideeffect None\n\n  @see Cudd_zddDivideF\n\n*/\nDdNode\t*\ncuddZddDivideF(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g)\n{\n    int\t\tv;\n    DdNode\t*one = DD_ONE(dd);\n    DdNode\t*zero = DD_ZERO(dd);\n    DdNode\t*f0, *f1, *g0, *g1;\n    DdNode\t*q, *r, *tmp;\n    int\t\tflag;\n\n    statLine(dd);\n    if (g == one)\n\treturn(f);\n    if (f == zero || f == one)\n\treturn(zero);\n    if (f == g)\n\treturn(one);\n\n    /* Check cache. */\n    r = cuddCacheLookup2Zdd(dd, cuddZddDivideF, f, g);\n    if (r)\n\treturn(r);\n\n    v = (int) g->index;\n\n    flag = cuddZddGetCofactors2(dd, f, v, &f1, &f0);\n    if (flag == 1)\n\treturn(NULL);\n    Cudd_Ref(f1);\n    Cudd_Ref(f0);\n    flag = cuddZddGetCofactors2(dd, g, v, &g1, &g0);\t/* g1 != zero */\n    if (flag == 1) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\treturn(NULL);\n    }\n    Cudd_Ref(g1);\n    Cudd_Ref(g0);\n\n    r = cuddZddDivideF(dd, f1, g1);\n    if (r == NULL) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, g1);\n\tCudd_RecursiveDerefZdd(dd, g0);\n\treturn(NULL);\n    }\n    Cudd_Ref(r);\n\n    if (r != zero && g0 != zero) {\n\ttmp = r;\n\tq = cuddZddDivideF(dd, f0, g0);\n\tif (q == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, f0);\n\t    Cudd_RecursiveDerefZdd(dd, g1);\n\t    Cudd_RecursiveDerefZdd(dd, g0);\n\t    return(NULL);\n\t}\n\tCudd_Ref(q);\n\tr = cuddZddIntersect(dd, r, q);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, f1);\n\t    Cudd_RecursiveDerefZdd(dd, f0);\n\t    Cudd_RecursiveDerefZdd(dd, g1);\n\t    Cudd_RecursiveDerefZdd(dd, g0);\n\t    Cudd_RecursiveDerefZdd(dd, q);\n\t    return(NULL);\n\t}\n\tCudd_Ref(r);\n\tCudd_RecursiveDerefZdd(dd, q);\n\tCudd_RecursiveDerefZdd(dd, tmp);\n    }\n\n    Cudd_RecursiveDerefZdd(dd, f1);\n    Cudd_RecursiveDerefZdd(dd, f0);\n    Cudd_RecursiveDerefZdd(dd, g1);\n    Cudd_RecursiveDerefZdd(dd, g0);\n    \n    cuddCacheInsert2(dd, cuddZddDivideF, f, g, r);\n    Cudd_Deref(r);\n    return(r);\n\n} /* end of cuddZddDivideF */\n\n\n/**\n  @brief Computes the three-way decomposition of f w.r.t. v.\n\n  @details Computes the three-way decomposition of function f\n  (represented by a %ZDD) with respect to variable v.\n\n  @return 0 if successful; 1 otherwise.\n\n  @sideeffect The results are returned in f1, f0, and fd.\n\n  @see cuddZddGetCofactors2\n\n*/\nint\ncuddZddGetCofactors3(\n  DdManager * dd,\n  DdNode * f,\n  int  v,\n  DdNode ** f1,\n  DdNode ** f0,\n  DdNode ** fd)\n{\n    DdNode\t*pc, *nc;\n    DdNode\t*zero = DD_ZERO(dd);\n    int\t\ttop, hv, ht, pv, nv;\n    int\t\tlevel;\n\n    top = dd->permZ[f->index];\n    level = dd->permZ[v];\n    hv = level >> 1;\n    ht = top >> 1;\n\n    if (hv < ht) {\n\t*f1 = zero;\n\t*f0 = zero;\n\t*fd = f;\n    }\n    else {\n\tpv = cuddZddGetPosVarIndex(dd, v);\n\tnv = cuddZddGetNegVarIndex(dd, v);\n\n\t/* not to create intermediate ZDD node */\n\tif (cuddZddGetPosVarLevel(dd, v) < cuddZddGetNegVarLevel(dd, v)) {\n\t    pc = cuddZddSubset1(dd, f, pv);\n\t    if (pc == NULL)\n\t\treturn(1);\n\t    Cudd_Ref(pc);\n\t    nc = cuddZddSubset0(dd, f, pv);\n\t    if (nc == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, pc);\n\t\treturn(1);\n\t    }\n\t    Cudd_Ref(nc);\n\n\t    *f1 = cuddZddSubset0(dd, pc, nv);\n\t    if (*f1 == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, pc);\n\t\tCudd_RecursiveDerefZdd(dd, nc);\n\t\treturn(1);\n\t    }\n\t    Cudd_Ref(*f1);\n\t    *f0 = cuddZddSubset1(dd, nc, nv);\n\t    if (*f0 == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, pc);\n\t\tCudd_RecursiveDerefZdd(dd, nc);\n\t\tCudd_RecursiveDerefZdd(dd, *f1);\n\t\treturn(1);\n\t    }\n\t    Cudd_Ref(*f0);\n\n\t    *fd = cuddZddSubset0(dd, nc, nv);\n\t    if (*fd == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, pc);\n\t\tCudd_RecursiveDerefZdd(dd, nc);\n\t\tCudd_RecursiveDerefZdd(dd, *f1);\n\t\tCudd_RecursiveDerefZdd(dd, *f0);\n\t\treturn(1);\n\t    }\n\t    Cudd_Ref(*fd);\n\t} else {\n\t    pc = cuddZddSubset1(dd, f, nv);\n\t    if (pc == NULL)\n\t\treturn(1);\n\t    Cudd_Ref(pc);\n\t    nc = cuddZddSubset0(dd, f, nv);\n\t    if (nc == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, pc);\n\t\treturn(1);\n\t    }\n\t    Cudd_Ref(nc);\n\n\t    *f0 = cuddZddSubset0(dd, pc, pv);\n\t    if (*f0 == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, pc);\n\t\tCudd_RecursiveDerefZdd(dd, nc);\n\t\treturn(1);\n\t    }\n\t    Cudd_Ref(*f0);\n\t    *f1 = cuddZddSubset1(dd, nc, pv);\n\t    if (*f1 == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, pc);\n\t\tCudd_RecursiveDerefZdd(dd, nc);\n\t\tCudd_RecursiveDerefZdd(dd, *f0);\n\t\treturn(1);\n\t    }\n\t    Cudd_Ref(*f1);\n\n\t    *fd = cuddZddSubset0(dd, nc, pv);\n\t    if (*fd == NULL) {\n\t\tCudd_RecursiveDerefZdd(dd, pc);\n\t\tCudd_RecursiveDerefZdd(dd, nc);\n\t\tCudd_RecursiveDerefZdd(dd, *f1);\n\t\tCudd_RecursiveDerefZdd(dd, *f0);\n\t\treturn(1);\n\t    }\n\t    Cudd_Ref(*fd);\n\t}\n\n\tCudd_RecursiveDerefZdd(dd, pc);\n\tCudd_RecursiveDerefZdd(dd, nc);\n\tCudd_Deref(*f1);\n\tCudd_Deref(*f0);\n\tCudd_Deref(*fd);\n    }\n    return(0);\n\n} /* end of cuddZddGetCofactors3 */\n\n\n/**\n  @brief Computes the two-way decomposition of f w.r.t. v.\n\n  @sideeffect The results are returned in f1 and f0.\n\n  @see cuddZddGetCofactors3\n\n*/\nint\ncuddZddGetCofactors2(\n  DdManager * dd,\n  DdNode * f,\n  int  v,\n  DdNode ** f1,\n  DdNode ** f0)\n{\n    *f1 = cuddZddSubset1(dd, f, v);\n    if (*f1 == NULL)\n\treturn(1);\n    *f0 = cuddZddSubset0(dd, f, v);\n    if (*f0 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, *f1);\n\treturn(1);\n    }\n    return(0);\n\n} /* end of cuddZddGetCofactors2 */\n\n\n/**\n  @brief Computes a complement of a %ZDD node.\n\n  @details So far, since we couldn't find a direct way to get the\n  complement of a %ZDD cover, we first convert a %ZDD cover to a %BDD,\n  then make the complement of the %ZDD cover from the complement of the\n  %BDD node by using ISOP.  The result depends on current variable order.\n\n*/\nDdNode\t*\ncuddZddComplement(\n  DdManager * dd,\n  DdNode *node)\n{\n    DdNode\t*b, *isop, *zdd_I;\n\n    /* Check cache */\n    zdd_I = cuddCacheLookup1Zdd(dd, cuddZddComplement, node);\n    if (zdd_I)\n\treturn(zdd_I);\n\n    b = cuddMakeBddFromZddCover(dd, node);\n    if (!b)\n\treturn(NULL);\n    cuddRef(b);\n    isop = cuddZddIsop(dd, Cudd_Not(b), Cudd_Not(b), &zdd_I);\n    if (!isop) {\n\tCudd_RecursiveDeref(dd, b);\n\treturn(NULL);\n    }\n    cuddRef(isop);\n    cuddRef(zdd_I);\n    Cudd_RecursiveDeref(dd, b);\n    Cudd_RecursiveDeref(dd, isop);\n\n    cuddCacheInsert1(dd, cuddZddComplement, node, zdd_I);\n    cuddDeref(zdd_I);\n    return(zdd_I);\n} /* end of cuddZddComplement */\n\n\n/**\n  @brief Returns the index of positive %ZDD variable.\n*/\nint\ncuddZddGetPosVarIndex(\n  DdManager * dd,\n  int index)\n{\n    (void) dd; /* avoid warning */\n    int\tpv = index & ~0x1;\n    return(pv);\n} /* end of cuddZddGetPosVarIndex */\n\n\n/**\n  @brief Returns the index of negative %ZDD variable.\n*/\nint\ncuddZddGetNegVarIndex(\n  DdManager * dd,\n  int index)\n{\n    (void) dd; /* avoid warning */\n    int\tnv = index | 0x1;\n    return(nv);\n} /* end of cuddZddGetPosVarIndex */\n\n\n/**\n  @brief Returns the level of positive %ZDD variable.\n*/\nint\ncuddZddGetPosVarLevel(\n  DdManager * dd,\n  int index)\n{\n    int\tpv = cuddZddGetPosVarIndex(dd, index);\n    return(dd->permZ[pv]);\n} /* end of cuddZddGetPosVarLevel */\n\n\n/**\n  @brief Returns the level of negative %ZDD variable.\n*/\nint\ncuddZddGetNegVarLevel(\n  DdManager * dd,\n  int index)\n{\n    int\tnv = cuddZddGetNegVarIndex(dd, index);\n    return(dd->permZ[nv]);\n} /* end of cuddZddGetNegVarLevel */\n"
  },
  {
    "path": "cudd/cudd/cuddZddGroup.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for %ZDD group sifting.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int zddTreeSiftingAux (DdManager *table, MtrNode *treenode, Cudd_ReorderingType method);\n#ifdef DD_STATS\nstatic int zddCountInternalMtrNodes (DdManager *table, MtrNode *treenode);\n#endif\nstatic int zddReorderChildren (DdManager *table, MtrNode *treenode, Cudd_ReorderingType method);\nstatic void zddFindNodeHiLo (DdManager *table, MtrNode *treenode, int *lower, int *upper);\nstatic int zddUniqueCompareGroup (void const *ptrX, void const *ptrY);\nstatic int zddGroupSifting (DdManager *table, int lower, int upper);\nstatic int zddGroupSiftingAux (DdManager *table, int x, int xLow, int xHigh);\nstatic int zddGroupSiftingUp (DdManager *table, int y, int xLow, Move **moves);\nstatic int zddGroupSiftingDown (DdManager *table, int x, int xHigh, Move **moves);\nstatic int zddGroupMove (DdManager *table, int x, int y, Move **moves);\nstatic int zddGroupMoveBackward (DdManager *table, int x, int y);\nstatic int zddGroupSiftingBackward (DdManager *table, Move *moves, int size);\nstatic void zddMergeGroups (DdManager *table, MtrNode *treenode, int low, int high);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Creates a new %ZDD variable group.\n\n  @details The group starts at variable and contains size\n  variables. The parameter low is the index of the first variable. If\n  the variable already exists, its current position in the order is\n  known to the manager. If the variable does not exist yet, the\n  position is assumed to be the same as the index.  The group tree is\n  created if it does not exist yet.\n\n  @return a pointer to the group if successful; NULL otherwise.\n\n  @sideeffect The %ZDD variable tree is changed.\n\n  @see Cudd_MakeTreeNode\n\n*/\nMtrNode *\nCudd_MakeZddTreeNode(\n  DdManager * dd /**< manager */,\n  unsigned int  low /**< index of the first group variable */,\n  unsigned int  size /**< number of variables in the group */,\n  unsigned int  type /**< MTR_DEFAULT or MTR_FIXED */)\n{\n    MtrNode *group;\n    MtrNode *tree;\n    unsigned int level;\n\n    /* If the variable does not exist yet, the position is assumed to be\n    ** the same as the index. Therefore, applications that rely on\n    ** Cudd_bddNewVarAtLevel or Cudd_addNewVarAtLevel to create new\n    ** variables have to create the variables before they group them.\n    */\n    level = (low < (unsigned int) dd->sizeZ) ? (unsigned int) dd->permZ[low] : low;\n\n    if (level + size - 1> (int) MTR_MAXHIGH)\n\treturn(NULL);\n\n    /* If the tree does not exist yet, create it. */\n    tree = dd->treeZ;\n    if (tree == NULL) {\n\tdd->treeZ = tree = Mtr_InitGroupTree(0, dd->sizeZ);\n\tif (tree == NULL)\n\t    return(NULL);\n\ttree->index = dd->invpermZ[0];\n    }\n\n    /* Extend the upper bound of the tree if necessary. This allows the\n    ** application to create groups even before the variables are created.\n    */\n    tree->size = ddMax(tree->size, level + size);\n\n    /* Create the group. */\n    group = Mtr_MakeGroup(tree, level, size, type);\n    if (group == NULL)\n\treturn(NULL);\n\n    /* Initialize the index field to the index of the variable currently\n    ** in position low. This field will be updated by the reordering\n    ** procedure to provide a handle to the group once it has been moved.\n    */\n    group->index = (MtrHalfWord) low;\n\n    return(group);\n\n} /* end of Cudd_MakeZddTreeNode */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Tree sifting algorithm for %ZDDs.\n\n  @details Assumes that a tree representing a group hierarchy is\n  passed as a parameter. It then reorders each group in postorder\n  fashion by calling zddTreeSiftingAux.  Assumes that no dead nodes\n  are present.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddZddTreeSifting(\n  DdManager * table /**< %DD table */,\n  Cudd_ReorderingType method /**< reordering method for the groups of leaves */)\n{\n    int i;\n    int nvars;\n    int result;\n    int tempTree;\n\n    /* If no tree is provided we create a temporary one in which all\n    ** variables are in a single group. After reordering this tree is\n    ** destroyed.\n    */\n    tempTree = table->treeZ == NULL;\n    if (tempTree) {\n\ttable->treeZ = Mtr_InitGroupTree(0,table->sizeZ);\n\ttable->treeZ->index = table->invpermZ[0];\n    }\n    nvars = table->sizeZ;\n\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0 && !tempTree)\n\t(void) fprintf(table->out,\"cuddZddTreeSifting:\");\n    Mtr_PrintGroups(table->treeZ,table->enableExtraDebug <= 0);\n#endif\n#if 0\n    /* Debugging code. */\n    if (table->tree && table->treeZ) {\n\t(void) fprintf(table->out,\"\\n\");\n\tMtr_PrintGroups(table->tree, 0);\n\tcuddPrintVarGroups(table,table->tree,0,0);\n\tfor (i = 0; i < table->size; i++) {\n\t    (void) fprintf(table->out,\"%s%d\",\n\t\t\t   (i == 0) ? \"\" : \",\", table->invperm[i]);\n\t}\n\t(void) fprintf(table->out,\"\\n\");\n\tfor (i = 0; i < table->size; i++) {\n\t    (void) fprintf(table->out,\"%s%d\",\n\t\t\t   (i == 0) ? \"\" : \",\", table->perm[i]);\n\t}\n\t(void) fprintf(table->out,\"\\n\\n\");\n\tMtr_PrintGroups(table->treeZ,0);\n\tcuddPrintVarGroups(table,table->treeZ,1,0);\n\tfor (i = 0; i < table->sizeZ; i++) {\n\t    (void) fprintf(table->out,\"%s%d\",\n\t\t\t   (i == 0) ? \"\" : \",\", table->invpermZ[i]);\n\t}\n\t(void) fprintf(table->out,\"\\n\");\n\tfor (i = 0; i < table->sizeZ; i++) {\n\t    (void) fprintf(table->out,\"%s%d\",\n\t\t\t   (i == 0) ? \"\" : \",\", table->permZ[i]);\n\t}\n\t(void) fprintf(table->out,\"\\n\");\n    }\n    /* End of debugging code. */\n#endif\n#ifdef DD_STATS\n    table->extsymmcalls = 0;\n    table->extsymm = 0;\n    table->secdiffcalls = 0;\n    table->secdiff = 0;\n    table->secdiffmisfire = 0;\n\n    (void) fprintf(table->out,\"\\n\");\n    if (!tempTree)\n\t(void) fprintf(table->out,\"#:IM_NODES  %8d: group tree nodes\\n\",\n\t\t       zddCountInternalMtrNodes(table,table->treeZ));\n#endif\n\n    /* Initialize the group of each subtable to itself. Initially\n    ** there are no groups. Groups are created according to the tree\n    ** structure in postorder fashion.\n    */\n    for (i = 0; i < nvars; i++)\n\ttable->subtableZ[i].next = i;\n\n    /* Reorder. */\n    result = zddTreeSiftingAux(table, table->treeZ, method);\n\n#ifdef DD_STATS\t\t/* print stats */\n    if (!tempTree && method == CUDD_REORDER_GROUP_SIFT &&\n\t(table->groupcheck == CUDD_GROUP_CHECK7 ||\n\t table->groupcheck == CUDD_GROUP_CHECK5)) {\n\t(void) fprintf(table->out,\"\\nextsymmcalls = %d\\n\",table->extsymmcalls);\n\t(void) fprintf(table->out,\"extsymm = %d\",table->extsymm);\n    }\n    if (!tempTree && method == CUDD_REORDER_GROUP_SIFT &&\n\ttable->groupcheck == CUDD_GROUP_CHECK7) {\n\t(void) fprintf(table->out,\"\\nsecdiffcalls = %d\\n\",table->secdiffcalls);\n\t(void) fprintf(table->out,\"secdiff = %d\\n\",table->secdiff);\n\t(void) fprintf(table->out,\"secdiffmisfire = %d\",table->secdiffmisfire);\n    }\n#endif\n\n    if (tempTree)\n\tCudd_FreeZddTree(table);\n    return(result);\n\n} /* end of cuddZddTreeSifting */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Visits the group tree and reorders each group.\n\n  @details Recursively visits the group tree and reorders each group\n  in postorder fashion.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddTreeSiftingAux(\n  DdManager * table,\n  MtrNode * treenode,\n  Cudd_ReorderingType method)\n{\n    MtrNode  *auxnode;\n    int res;\n\n#ifdef DD_DEBUG\n    Mtr_PrintGroups(treenode,1);\n#endif\n\n    auxnode = treenode;\n    while (auxnode != NULL) {\n\tif (auxnode->child != NULL) {\n\t    if (!zddTreeSiftingAux(table, auxnode->child, method))\n\t\treturn(0);\n\t    res = zddReorderChildren(table, auxnode, CUDD_REORDER_GROUP_SIFT);\n\t    if (res == 0)\n\t\treturn(0);\n\t} else if (auxnode->size > 1) {\n\t    if (!zddReorderChildren(table, auxnode, method))\n\t\treturn(0);\n\t}\n\tauxnode = auxnode->younger;\n    }\n\n    return(1);\n\n} /* end of zddTreeSiftingAux */\n\n\n#ifdef DD_STATS\n/**\n  @brief Counts the number of internal nodes of the group tree.\n\n  @return the count.\n\n  @sideeffect None\n\n*/\nstatic int\nzddCountInternalMtrNodes(\n  DdManager * table,\n  MtrNode * treenode)\n{\n    MtrNode *auxnode;\n    int     count,nodeCount;\n\n\n    nodeCount = 0;\n    auxnode = treenode;\n    while (auxnode != NULL) {\n\tif (!(MTR_TEST(auxnode,MTR_TERMINAL))) {\n\t    nodeCount++;\n\t    count = zddCountInternalMtrNodes(table,auxnode->child);\n\t    nodeCount += count;\n\t}\n\tauxnode = auxnode->younger;\n    }\n\n    return(nodeCount);\n\n} /* end of zddCountInternalMtrNodes */\n#endif\n\n\n/**\n  @brief Reorders the children of a group tree node according to\n  the options.\n\n  @details After reordering puts all the variables in the group and/or\n  its descendents in a single group. This allows hierarchical\n  reordering.  If the variables in the group do not exist yet, simply\n  does nothing.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddReorderChildren(\n  DdManager * table,\n  MtrNode * treenode,\n  Cudd_ReorderingType method)\n{\n    int lower;\n    int upper = 0;\n    int result;\n    unsigned int initialSize;\n\n    zddFindNodeHiLo(table,treenode,&lower,&upper);\n    /* If upper == -1 these variables do not exist yet. */\n    if (upper == -1)\n\treturn(1);\n\n    if (treenode->flags == MTR_FIXED) {\n\tresult = 1;\n    } else {\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\" \");\n#endif\n\tswitch (method) {\n\tcase CUDD_REORDER_RANDOM:\n\tcase CUDD_REORDER_RANDOM_PIVOT:\n\t    result = cuddZddSwapping(table,lower,upper,method);\n\t    break;\n\tcase CUDD_REORDER_SIFT:\n\t    result = cuddZddSifting(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_SIFT_CONVERGE:\n\t    do {\n\t\tinitialSize = table->keysZ;\n\t\tresult = cuddZddSifting(table,lower,upper);\n\t\tif (initialSize <= table->keysZ)\n\t\t    break;\n#ifdef DD_STATS\n\t\telse\n\t\t    (void) fprintf(table->out,\"\\n\");\n#endif\n\t    } while (result != 0);\n\t    break;\n\tcase CUDD_REORDER_SYMM_SIFT:\n\t    result = cuddZddSymmSifting(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_SYMM_SIFT_CONV:\n\t    result = cuddZddSymmSiftingConv(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_GROUP_SIFT:\n\t    result = zddGroupSifting(table,lower,upper);\n\t    break;\n        case CUDD_REORDER_GROUP_SIFT_CONV:\n            do {\n                initialSize = table->keysZ;\n                result = zddGroupSifting(table,lower,upper);\n                if (initialSize <= table->keysZ)\n                    break;\n            } while (result != 0);\n            break;\n\tcase CUDD_REORDER_LINEAR:\n\t    result = cuddZddLinearSifting(table,lower,upper);\n\t    break;\n\tcase CUDD_REORDER_LINEAR_CONVERGE:\n\t    do {\n\t\tinitialSize = table->keysZ;\n\t\tresult = cuddZddLinearSifting(table,lower,upper);\n\t\tif (initialSize <= table->keysZ)\n\t\t    break;\n#ifdef DD_STATS\n\t\telse\n\t\t    (void) fprintf(table->out,\"\\n\");\n#endif\n\t    } while (result != 0);\n\t    break;\n\tdefault:\n\t    return(0);\n\t}\n    }\n\n    /* Create a single group for all the variables that were sifted,\n    ** so that they will be treated as a single block by successive\n    ** invocations of zddGroupSifting.\n    */\n    zddMergeGroups(table,treenode,lower,upper);\n\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0)\n        (void) fprintf(table->out,\"zddReorderChildren:\");\n#endif\n\n    return(result);\n\n} /* end of zddReorderChildren */\n\n\n/**\n  @brief Finds the lower and upper bounds of the group represented\n  by treenode.\n\n  @details The high and low fields of treenode are indices.  From\n  those we need to derive the current positions, and find maximum and\n  minimum.\n\n  @sideeffect The bounds are returned as side effects.\n\n*/\nstatic void\nzddFindNodeHiLo(\n  DdManager * table,\n  MtrNode * treenode,\n  int * lower,\n  int * upper)\n{\n    int low;\n    int high;\n\n    /* Check whether no variables in this group already exist.\n    ** If so, return immediately. The calling procedure will know from\n    ** the values of upper that no reordering is needed.\n    */\n    if ((int) treenode->low >= table->sizeZ) {\n\t*lower = table->sizeZ;\n\t*upper = -1;\n\treturn;\n    }\n\n    *lower = low = (unsigned int) table->permZ[treenode->index];\n    high = (int) (low + treenode->size - 1);\n\n    if (high >= table->sizeZ) {\n\t/* This is the case of a partially existing group. The aim is to\n\t** reorder as many variables as safely possible.  If the tree\n\t** node is terminal, we just reorder the subset of the group\n\t** that is currently in existence.  If the group has\n\t** subgroups, then we only reorder those subgroups that are\n\t** fully instantiated.  This way we avoid breaking up a group.\n\t*/\n\tMtrNode *auxnode = treenode->child;\n\tif (auxnode == NULL) {\n\t    *upper = (unsigned int) table->sizeZ - 1;\n\t} else {\n\t    /* Search the subgroup that strands the table->sizeZ line.\n\t    ** If the first group starts at 0 and goes past table->sizeZ\n\t    ** upper will get -1, thus correctly signaling that no reordering\n\t    ** should take place.\n\t    */\n\t    while (auxnode != NULL) {\n\t\tint thisLower = table->permZ[auxnode->low];\n\t\tint thisUpper = thisLower + auxnode->size - 1;\n\t\tif (thisUpper >= table->sizeZ && thisLower < table->sizeZ)\n\t\t    *upper = (unsigned int) thisLower - 1;\n\t\tauxnode = auxnode->younger;\n\t    }\n\t}\n    } else {\n\t/* Normal case: All the variables of the group exist. */\n\t*upper = (unsigned int) high;\n    }\n\n#ifdef DD_DEBUG\n    /* Make sure that all variables in group are contiguous. */\n    assert(treenode->size >= (MtrHalfWord) (*upper - *lower + 1));\n#endif\n\n    return;\n\n} /* end of zddFindNodeHiLo */\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Comparison function used by qsort to order the variables\n  according to the number of keys in the subtables.\n\n  @return the difference in number of keys between the two variables\n  being compared.\n\n  @sideeffect None\n\n*/\nstatic int\nzddUniqueCompareGroup(\n  void const * ptrX,\n  void const * ptrY)\n{\n    IndexKey const * pX = (IndexKey const *) ptrX;\n    IndexKey const * pY = (IndexKey const *) ptrY;\n#if 0\n    if (pY->keys == pX->keys) {\n\treturn(pX->index - pY->index);\n    }\n#endif\n    return(pY->keys - pX->keys);\n\n} /* end of zddUniqueCompareGroup */\n\n\n/**\n  @brief Sifts from treenode->low to treenode->high.\n\n  @details If croupcheck == CUDD_GROUP_CHECK7, it checks for group\n  creation at the end of the initial sifting. If a group is created,\n  it is then sifted again. After sifting one variable, the group that\n  contains it is dissolved.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddGroupSifting(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    IndexKey\t*var;\n    int\t\ti,j,x,xInit;\n    int\t\tnvars;\n    int\t\tclasses;\n    int\t\tresult;\n    int\t\t*sifted;\n#ifdef DD_STATS\n    unsigned\tpreviousSize;\n#endif\n    int\t\txindex;\n\n    nvars = table->sizeZ;\n\n    /* Order variables to sift. */\n    sifted = NULL;\n    var = ALLOC(IndexKey,nvars);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto zddGroupSiftingOutOfMem;\n    }\n    sifted = ALLOC(int,nvars);\n    if (sifted == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto zddGroupSiftingOutOfMem;\n    }\n\n    /* Here we consider only one representative for each group. */\n    for (i = 0, classes = 0; i < nvars; i++) {\n\tsifted[i] = 0;\n\tx = table->permZ[i];\n\tif ((unsigned) x >= table->subtableZ[x].next) {\n\t    var[classes].index = i;\n\t    var[classes].keys = table->subtableZ[x].keys;\n\t    classes++;\n\t}\n    }\n\n    util_qsort(var,classes,sizeof(IndexKey),zddUniqueCompareGroup);\n\n    /* Now sift. */\n    for (i = 0; i < ddMin(table->siftMaxVar,classes); i++) {\n\tif (table->zddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime > table->timeLimit) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n\txindex = var[i].index;\n\tif (sifted[xindex] == 1) /* variable already sifted as part of group */\n\t    continue;\n\tx = table->permZ[xindex]; /* find current level of this variable */\n\tif (x < lower || x > upper)\n\t    continue;\n#ifdef DD_STATS\n\tpreviousSize = table->keysZ;\n#endif\n#ifdef DD_DEBUG\n\t/* x is bottom of group */\n\tassert((unsigned) x >= table->subtableZ[x].next);\n#endif\n\tresult = zddGroupSiftingAux(table,x,lower,upper);\n\tif (!result) goto zddGroupSiftingOutOfMem;\n\n#ifdef DD_STATS\n\tif (table->keysZ < previousSize) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keysZ > previousSize) {\n\t    (void) fprintf(table->out,\"+\");\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n\n\t/* Mark variables in the group just sifted. */\n\tx = table->permZ[xindex];\n\tif ((unsigned) x != table->subtableZ[x].next) {\n\t    xInit = x;\n\t    do {\n\t\tj = table->invpermZ[x];\n\t\tsifted[j] = 1;\n\t\tx = table->subtableZ[x].next;\n\t    } while (x != xInit);\n\t}\n\n#ifdef DD_DEBUG\n\tif (table->enableExtraDebug > 0)\n            (void) fprintf(table->out,\"zddGroupSifting:\");\n#endif\n    } /* for */\n\n    FREE(sifted);\n    FREE(var);\n\n    return(1);\n\nzddGroupSiftingOutOfMem:\n    if (var != NULL)\tFREE(var);\n    if (sifted != NULL)\tFREE(sifted);\n\n    return(0);\n\n} /* end of zddGroupSifting */\n\n\n/**\n  @brief Sifts one variable up and down until it has taken all\n  positions. Checks for aggregation.\n\n  @details There may be at most two sweeps, even if the group grows.\n  Assumes that x is either an isolated variable, or it is the bottom\n  of a group. All groups may not have been found. The variable being\n  moved is returned to the best position seen during sifting.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddGroupSiftingAux(\n  DdManager * table,\n  int  x,\n  int  xLow,\n  int  xHigh)\n{\n    Move *move;\n    Move *moves;\t/* list of moves */\n    int  initialSize;\n    int  result;\n\n\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0)\n        (void) fprintf(table->out,\n                       \"zddGroupSiftingAux from %d to %d\\n\",xLow,xHigh);\n    assert((unsigned) x >= table->subtableZ[x].next); /* x is bottom of group */\n#endif\n\n    initialSize = table->keysZ;\n    moves = NULL;\n\n    if (x == xLow) { /* Sift down */\n#ifdef DD_DEBUG\n\t/* x must be a singleton */\n\tassert((unsigned) x == table->subtableZ[x].next);\n#endif\n\tif (x == xHigh) return(1);\t/* just one variable */\n\n\tif (!zddGroupSiftingDown(table,x,xHigh,&moves))\n\t    goto zddGroupSiftingAuxOutOfMem;\n\t/* at this point x == xHigh, unless early term */\n\n\t/* move backward and stop at best position */\n\tresult = zddGroupSiftingBackward(table,moves,initialSize);\n#ifdef DD_DEBUG\n\tassert(table->keysZ <= (unsigned) initialSize);\n#endif\n\tif (!result) goto zddGroupSiftingAuxOutOfMem;\n\n    } else if (cuddZddNextHigh(table,x) > xHigh) { /* Sift up */\n#ifdef DD_DEBUG\n\t/* x is bottom of group */\n\tassert((unsigned) x >= table->subtableZ[x].next);\n#endif\n\t/* Find top of x's group */\n\tx = table->subtableZ[x].next;\n\n\tif (!zddGroupSiftingUp(table,x,xLow,&moves))\n\t    goto zddGroupSiftingAuxOutOfMem;\n\t/* at this point x == xLow, unless early term */\n\n\t/* move backward and stop at best position */\n\tresult = zddGroupSiftingBackward(table,moves,initialSize);\n#ifdef DD_DEBUG\n\tassert(table->keysZ <= (unsigned) initialSize);\n#endif\n\tif (!result) goto zddGroupSiftingAuxOutOfMem;\n\n    } else if (x - xLow > xHigh - x) { /* must go down first: shorter */\n\tif (!zddGroupSiftingDown(table,x,xHigh,&moves))\n\t    goto zddGroupSiftingAuxOutOfMem;\n\t/* at this point x == xHigh, unless early term */\n\n\t/* Find top of group */\n\tif (moves) {\n\t    x = moves->y;\n\t}\n\twhile ((unsigned) x < table->subtableZ[x].next)\n\t    x = table->subtableZ[x].next;\n\tx = table->subtableZ[x].next;\n#ifdef DD_DEBUG\n\t/* x should be the top of a group */\n\tassert((unsigned) x <= table->subtableZ[x].next);\n#endif\n\n\tif (!zddGroupSiftingUp(table,x,xLow,&moves))\n\t    goto zddGroupSiftingAuxOutOfMem;\n\n\t/* move backward and stop at best position */\n\tresult = zddGroupSiftingBackward(table,moves,initialSize);\n#ifdef DD_DEBUG\n\tassert(table->keysZ <= (unsigned) initialSize);\n#endif\n\tif (!result) goto zddGroupSiftingAuxOutOfMem;\n\n    } else { /* moving up first: shorter */\n\t/* Find top of x's group */\n\tx = table->subtableZ[x].next;\n\n\tif (!zddGroupSiftingUp(table,x,xLow,&moves))\n\t    goto zddGroupSiftingAuxOutOfMem;\n\t/* at this point x == xHigh, unless early term */\n\n\tif (moves) {\n\t    x = moves->x;\n\t}\n\twhile ((unsigned) x < table->subtableZ[x].next)\n\t    x = table->subtableZ[x].next;\n#ifdef DD_DEBUG\n\t/* x is bottom of a group */\n\tassert((unsigned) x >= table->subtableZ[x].next);\n#endif\n\n\tif (!zddGroupSiftingDown(table,x,xHigh,&moves))\n\t    goto zddGroupSiftingAuxOutOfMem;\n\n\t/* move backward and stop at best position */\n\tresult = zddGroupSiftingBackward(table,moves,initialSize);\n#ifdef DD_DEBUG\n\tassert(table->keysZ <= (unsigned) initialSize);\n#endif\n\tif (!result) goto zddGroupSiftingAuxOutOfMem;\n    }\n\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n\n    return(1);\n\nzddGroupSiftingAuxOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n\n    return(0);\n\n} /* end of zddGroupSiftingAux */\n\n\n/**\n  @brief Sifts up a variable until either it reaches position xLow\n  or the size of the %DD heap increases too much.\n\n  @details Assumes that y is the top of a group (or a singleton).\n  Checks y for aggregation to the adjacent variables. Records all the\n  moves that are appended to the list of moves received as input and\n  returned as a side effect.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddGroupSiftingUp(\n  DdManager * table,\n  int  y,\n  int  xLow,\n  Move ** moves)\n{\n    Move *move;\n    int  x;\n    int  size;\n    int  gxtop;\n    int  limitSize;\n\n    limitSize = table->keysZ;\n\n    x = cuddZddNextLow(table,y);\n    while (x >= xLow) {\n\tgxtop = table->subtableZ[x].next;\n\tif (table->subtableZ[x].next == (unsigned) x &&\n\t    table->subtableZ[y].next == (unsigned) y) {\n\t    /* x and y are self groups */\n\t    size = cuddZddSwapInPlace(table,x,y);\n#ifdef DD_DEBUG\n\t    assert(table->subtableZ[x].next == (unsigned) x);\n\t    assert(table->subtableZ[y].next == (unsigned) y);\n#endif\n\t    if (size == 0) goto zddGroupSiftingUpOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto zddGroupSiftingUpOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->flags = MTR_DEFAULT;\n\t    move->size = size;\n\t    move->next = *moves;\n\t    *moves = move;\n\n#ifdef DD_DEBUG\n\t    if (table->enableExtraDebug > 0)\n                (void) fprintf(table->out,\n                               \"zddGroupSiftingUp (2 single groups):\\n\");\n#endif\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(1);\n\t    if (size < limitSize) limitSize = size;\n\t} else { /* group move */\n\t    size = zddGroupMove(table,x,y,moves);\n\t    if (size == 0) goto zddGroupSiftingUpOutOfMem;\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(1);\n\t    if (size < limitSize) limitSize = size;\n\t}\n\ty = gxtop;\n\tx = cuddZddNextLow(table,y);\n    }\n\n    return(1);\n\nzddGroupSiftingUpOutOfMem:\n    while (*moves != NULL) {\n\tmove = (*moves)->next;\n\tcuddDeallocMove(table, *moves);\n\t*moves = move;\n    }\n    return(0);\n\n} /* end of zddGroupSiftingUp */\n\n\n/**\n  @brief Sifts down a variable until it reaches position xHigh.\n\n  @details Assumes that x is the bottom of a group (or a singleton).\n  Records all the moves.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddGroupSiftingDown(\n  DdManager * table,\n  int  x,\n  int  xHigh,\n  Move ** moves)\n{\n    Move *move;\n    int  y;\n    int  size;\n    int  limitSize;\n    int  gybot;\n\n\n    /* Initialize R */\n    limitSize = size = table->keysZ;\n    y = cuddZddNextHigh(table,x);\n    while (y <= xHigh) {\n\t/* Find bottom of y group. */\n\tgybot = table->subtableZ[y].next;\n\twhile (table->subtableZ[gybot].next != (unsigned) y)\n\t    gybot = table->subtableZ[gybot].next;\n\n\tif (table->subtableZ[x].next == (unsigned) x &&\n\t    table->subtableZ[y].next == (unsigned) y) {\n\t    /* x and y are self groups */\n\t    size = cuddZddSwapInPlace(table,x,y);\n#ifdef DD_DEBUG\n\t    assert(table->subtableZ[x].next == (unsigned) x);\n\t    assert(table->subtableZ[y].next == (unsigned) y);\n#endif\n\t    if (size == 0) goto zddGroupSiftingDownOutOfMem;\n\n\t    /* Record move. */\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL) goto zddGroupSiftingDownOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->flags = MTR_DEFAULT;\n\t    move->size = size;\n\t    move->next = *moves;\n\t    *moves = move;\n\n#ifdef DD_DEBUG\n\t    if (table->enableExtraDebug > 0)\n                (void) fprintf(table->out,\n                               \"zddGroupSiftingDown (2 single groups):\\n\");\n#endif\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(1);\n\t    if (size < limitSize) limitSize = size;\n\t} else { /* Group move */\n\t    size = zddGroupMove(table,x,y,moves);\n\t    if (size == 0) goto zddGroupSiftingDownOutOfMem;\n\t    if ((double) size > (double) limitSize * table->maxGrowth)\n\t\treturn(1);\n\t    if (size < limitSize) limitSize = size;\n\t}\n\tx = gybot;\n\ty = cuddZddNextHigh(table,x);\n    }\n\n    return(1);\n\nzddGroupSiftingDownOutOfMem:\n    while (*moves != NULL) {\n\tmove = (*moves)->next;\n\tcuddDeallocMove(table, *moves);\n\t*moves = move;\n    }\n\n    return(0);\n\n} /* end of zddGroupSiftingDown */\n\n\n/**\n  @brief Swaps two groups and records the move.\n\n  @return the number of keys in the %DD table in case of success; 0\n  otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddGroupMove(\n  DdManager * table,\n  int  x,\n  int  y,\n  Move ** moves)\n{\n    Move *move;\n    int  size;\n    int  i,j,xtop,xbot,xsize,ytop,ybot,ysize,newxtop;\n    int  swapx = 0, swapy = 0;\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    int  initialSize,bestSize;\n#endif\n\n#ifdef DD_DEBUG\n    /* We assume that x < y */\n    assert(x < y);\n#endif\n    /* Find top, bottom, and size for the two groups. */\n    xbot = x;\n    xtop = table->subtableZ[x].next;\n    xsize = xbot - xtop + 1;\n    ybot = y;\n    while ((unsigned) ybot < table->subtableZ[ybot].next)\n\tybot = table->subtableZ[ybot].next;\n    ytop = y;\n    ysize = ybot - ytop + 1;\n\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    initialSize = bestSize = table->keysZ;\n#endif\n    /* Sift the variables of the second group up through the first group */\n    for (i = 1; i <= ysize; i++) {\n\tfor (j = 1; j <= xsize; j++) {\n\t    size = cuddZddSwapInPlace(table,x,y);\n\t    if (size == 0) goto zddGroupMoveOutOfMem;\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n\t    if (size < bestSize)\n\t\tbestSize = size;\n#endif\n\t    swapx = x; swapy = y;\n\t    y = x;\n\t    x = cuddZddNextLow(table,y);\n\t}\n\ty = ytop + i;\n\tx = cuddZddNextLow(table,y);\n    }\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    if ((bestSize < initialSize) && (bestSize < size))\n\t(void) fprintf(table->out,\"Missed local minimum: initialSize:%d  bestSize:%d  finalSize:%d\\n\",initialSize,bestSize,size);\n#endif\n\n    /* fix groups */\n    y = xtop; /* ytop is now where xtop used to be */\n    for (i = 0; i < ysize - 1; i++) {\n\ttable->subtableZ[y].next = cuddZddNextHigh(table,y);\n\ty = cuddZddNextHigh(table,y);\n    }\n    table->subtableZ[y].next = xtop; /* y is bottom of its group, join */\n\t\t\t\t    /* it to top of its group */\n    x = cuddZddNextHigh(table,y);\n    newxtop = x;\n    for (i = 0; i < xsize - 1; i++) {\n\ttable->subtableZ[x].next = cuddZddNextHigh(table,x);\n\tx = cuddZddNextHigh(table,x);\n    }\n    table->subtableZ[x].next = newxtop; /* x is bottom of its group, join */\n\t\t\t\t    /* it to top of its group */\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0)\n        (void) fprintf(table->out,\"zddGroupMove:\\n\");\n#endif\n\n    /* Store group move */\n    move = (Move *) cuddDynamicAllocNode(table);\n    if (move == NULL) goto zddGroupMoveOutOfMem;\n    move->x = swapx;\n    move->y = swapy;\n    move->flags = MTR_DEFAULT;\n    move->size = table->keysZ;\n    move->next = *moves;\n    *moves = move;\n\n    return(table->keysZ);\n\nzddGroupMoveOutOfMem:\n    while (*moves != NULL) {\n\tmove = (*moves)->next;\n\tcuddDeallocMove(table, *moves);\n\t*moves = move;\n    }\n    return(0);\n\n} /* end of zddGroupMove */\n\n\n/**\n  @brief Undoes the swap two groups.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddGroupMoveBackward(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    int size;\n    int i,j,xtop,xbot,xsize,ytop,ybot,ysize,newxtop;\n\n\n#ifdef DD_DEBUG\n    /* We assume that x < y */\n    assert(x < y);\n#endif\n\n    /* Find top, bottom, and size for the two groups. */\n    xbot = x;\n    xtop = table->subtableZ[x].next;\n    xsize = xbot - xtop + 1;\n    ybot = y;\n    while ((unsigned) ybot < table->subtableZ[ybot].next)\n\tybot = table->subtableZ[ybot].next;\n    ytop = y;\n    ysize = ybot - ytop + 1;\n\n    /* Sift the variables of the second group up through the first group */\n    for (i = 1; i <= ysize; i++) {\n\tfor (j = 1; j <= xsize; j++) {\n\t    size = cuddZddSwapInPlace(table,x,y);\n\t    if (size == 0)\n\t\treturn(0);\n\t    y = x;\n\t    x = cuddZddNextLow(table,y);\n\t}\n\ty = ytop + i;\n\tx = cuddZddNextLow(table,y);\n    }\n\n    /* fix groups */\n    y = xtop;\n    for (i = 0; i < ysize - 1; i++) {\n\ttable->subtableZ[y].next = cuddZddNextHigh(table,y);\n\ty = cuddZddNextHigh(table,y);\n    }\n    table->subtableZ[y].next = xtop; /* y is bottom of its group, join */\n\t\t\t\t    /* to its top */\n    x = cuddZddNextHigh(table,y);\n    newxtop = x;\n    for (i = 0; i < xsize - 1; i++) {\n\ttable->subtableZ[x].next = cuddZddNextHigh(table,x);\n\tx = cuddZddNextHigh(table,x);\n    }\n    table->subtableZ[x].next = newxtop; /* x is bottom of its group, join */\n\t\t\t\t    /* to its top */\n#ifdef DD_DEBUG\n    if (table->enableExtraDebug > 0)\n        (void) fprintf(table->out,\"zddGroupMoveBackward:\\n\");\n#endif\n\n    return(1);\n\n} /* end of zddGroupMoveBackward */\n\n\n/**\n  @brief Determines the best position for a variables and returns\n  it there.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddGroupSiftingBackward(\n  DdManager * table,\n  Move * moves,\n  int  size)\n{\n    Move *move;\n    int  res;\n\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size < size) {\n\t    size = move->size;\n\t}\n    }\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size == size) return(1);\n\tif ((table->subtableZ[move->x].next == move->x) &&\n\t(table->subtableZ[move->y].next == move->y)) {\n\t    res = cuddZddSwapInPlace(table,(int)move->x,(int)move->y);\n\t    if (!res) return(0);\n#ifdef DD_DEBUG\n\t    if (table->enableExtraDebug > 0)\n                (void) fprintf(table->out,\"zddGroupSiftingBackward:\\n\");\n\t    assert(table->subtableZ[move->x].next == move->x);\n\t    assert(table->subtableZ[move->y].next == move->y);\n#endif\n\t} else { /* Group move necessary */\n\t    res = zddGroupMoveBackward(table,(int)move->x,(int)move->y);\n\t    if (!res) return(0);\n\t}\n    }\n\n    return(1);\n\n} /* end of zddGroupSiftingBackward */\n\n\n/**\n  @brief Merges groups in the %DD table.\n\n  @details Creates a single group from low to high and adjusts the\n  idex field of the tree node.\n\n  @sideeffect None\n\n*/\nstatic void\nzddMergeGroups(\n  DdManager * table,\n  MtrNode * treenode,\n  int  low,\n  int  high)\n{\n    int i;\n    MtrNode *auxnode;\n    int saveindex;\n    int newindex;\n\n    /* Merge all variables from low to high in one group, unless\n    ** this is the topmost group. In such a case we do not merge lest\n    ** we lose the symmetry information. */\n    if (treenode != table->treeZ) {\n\tfor (i = low; i < high; i++)\n\t    table->subtableZ[i].next = i+1;\n\ttable->subtableZ[high].next = low;\n    }\n\n    /* Adjust the index fields of the tree nodes. If a node is the\n    ** first child of its parent, then the parent may also need adjustment. */\n    saveindex = treenode->index;\n    newindex = table->invpermZ[low];\n    auxnode = treenode;\n    do {\n\tauxnode->index = newindex;\n\tif (auxnode->parent == NULL ||\n\t\t(int) auxnode->parent->index != saveindex)\n\t    break;\n\tauxnode = auxnode->parent;\n    } while (1);\n    return;\n\n} /* end of zddMergeGroups */\n"
  },
  {
    "path": "cudd/cudd/cuddZddIsop.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions to find irredundant SOP covers as ZDDs from BDDs.\n\n  @author In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Computes an ISOP in %ZDD form from BDDs.\n\n  @details Computes an irredundant sum of products (ISOP) in %ZDD\n  form from BDDs. The two BDDs L and U represent the lower bound and\n  the upper bound, respectively, of the function. The ISOP uses two\n  %ZDD variables for each %BDD variable: One for the positive literal,\n  and one for the negative literal. These two variables should be\n  adjacent in the %ZDD order. The two %ZDD variables corresponding to\n  %BDD variable <code>i</code> should have indices <code>2i</code> and\n  <code>2i+1</code>.  The result of this procedure depends on the\n  variable order. If successful, Cudd_zddIsop returns the %BDD for\n  the function chosen from the interval. The %ZDD representing the\n  irredundant cover is returned as a side effect in zdd_I. In case of\n  failure, NULL is returned.\n\n  @return the %BDD for the chosen function if successful; NULL otherwise.\n\n  @sideeffect zdd_I holds the pointer to the %ZDD for the ISOP on\n  successful return.\n\n  @see Cudd_bddIsop Cudd_zddVarsFromBddVars\n\n*/\nDdNode\t*\nCudd_zddIsop(\n  DdManager * dd,\n  DdNode * L,\n  DdNode * U,\n  DdNode ** zdd_I)\n{\n    DdNode\t*res;\n    int\t\tautoDynZ;\n\n    autoDynZ = dd->autoDynZ;\n    dd->autoDynZ = 0;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddIsop(dd, L, U, zdd_I);\n    } while (dd->reordered == 1);\n    dd->autoDynZ = autoDynZ;\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddIsop */\n\n\n/**\n  @brief Computes a %BDD in the interval between L and U with a\n  simple sum-of-product cover.\n\n  @details This procedure is similar to Cudd_zddIsop, but it does not\n  return the %ZDD for the cover.\n\n  @return a pointer to the %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddIsop\n\n*/\nDdNode\t*\nCudd_bddIsop(\n  DdManager * dd,\n  DdNode * L,\n  DdNode * U)\n{\n    DdNode\t*res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddBddIsop(dd, L, U);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_bddIsop */\n\n\n/**\n  @brief Converts a %ZDD cover to a %BDD.\n\n  @details Converts a %ZDD cover to a %BDD for the function represented\n  by the cover.\n\n  @return a %BDD node if successful; otherwise it returns NULL.\n\n  @see Cudd_zddIsop\n\n*/\nDdNode\t*\nCudd_MakeBddFromZddCover(\n  DdManager * dd,\n  DdNode * node)\n{\n    DdNode\t*res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddMakeBddFromZddCover(dd, node);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_MakeBddFromZddCover */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddIsop.\n\n  @sideeffect None\n\n  @see Cudd_zddIsop\n\n*/\nDdNode\t*\ncuddZddIsop(\n  DdManager * dd,\n  DdNode * L,\n  DdNode * U,\n  DdNode ** zdd_I)\n{\n    DdNode\t*one = DD_ONE(dd);\n    DdNode\t*zero = Cudd_Not(one);\n    DdNode\t*zdd_one = DD_ONE(dd);\n    DdNode\t*zdd_zero = DD_ZERO(dd);\n    int\t\tv, top_l, top_u;\n    DdNode\t*Lsub0, *Usub0, *Lsub1, *Usub1, *Ld, *Ud;\n    DdNode\t*Lsuper0, *Usuper0, *Lsuper1, *Usuper1;\n    DdNode\t*Isub0, *Isub1, *Id;\n    DdNode\t*zdd_Isub0, *zdd_Isub1, *zdd_Id;\n    DdNode\t*x;\n    DdNode\t*term0, *term1, *sum;\n    DdNode\t*Lv, *Uv, *Lnv, *Unv;\n    DdNode\t*r, *y, *z;\n    unsigned\tindex;\n    DD_CTFP\tcacheOp;\n\n    statLine(dd);\n    if (L == zero) {\n\t*zdd_I = zdd_zero;\n\treturn(zero);\n    }\n    if (U == one) {\n\t*zdd_I = zdd_one;\n\treturn(one);\n    }\n\n    if (U == zero || L == one) {\n\tprintf(\"*** ERROR : illegal condition for ISOP (U < L).\\n\");\n\texit(1);\n    }\n\n    /* Check the cache. We store two results for each recursive call.\n    ** One is the BDD, and the other is the ZDD. Both are needed.\n    ** Hence we need a double hit in the cache to terminate the\n    ** recursion. Clearly, collisions may evict only one of the two\n    ** results. */\n    cacheOp = (DD_CTFP) cuddZddIsop;\n    r = cuddCacheLookup2(dd, cuddBddIsop, L, U);\n    if (r) {\n\t*zdd_I = cuddCacheLookup2Zdd(dd, cacheOp, L, U);\n\tif (*zdd_I)\n\t    return(r);\n\telse {\n\t    /* The BDD result may have been dead. In that case\n\t    ** cuddCacheLookup2 would have called cuddReclaim,\n\t    ** whose effects we now have to undo. */\n\t    cuddRef(r);\n\t    Cudd_RecursiveDeref(dd, r);\n\t}\n    }\n\n    top_l = dd->perm[Cudd_Regular(L)->index];\n    top_u = dd->perm[Cudd_Regular(U)->index];\n    v = ddMin(top_l, top_u);\n\n    /* Compute cofactors. */\n    if (top_l == v) {\n\tindex = Cudd_Regular(L)->index;\n\tLv = Cudd_T(L);\n\tLnv = Cudd_E(L);\n\tif (Cudd_IsComplement(L)) {\n\t    Lv = Cudd_Not(Lv);\n\t    Lnv = Cudd_Not(Lnv);\n\t}\n    }\n    else {\n\tindex = Cudd_Regular(U)->index;\n\tLv = Lnv = L;\n    }\n\n    if (top_u == v) {\n\tUv = Cudd_T(U);\n\tUnv = Cudd_E(U);\n\tif (Cudd_IsComplement(U)) {\n\t    Uv = Cudd_Not(Uv);\n\t    Unv = Cudd_Not(Unv);\n\t}\n    }\n    else {\n\tUv = Unv = U;\n    }\n\n    Lsub0 = cuddBddAndRecur(dd, Lnv, Cudd_Not(Uv));\n    if (Lsub0 == NULL)\n\treturn(NULL);\n    Cudd_Ref(Lsub0);\n    Usub0 = Unv;\n    Lsub1 = cuddBddAndRecur(dd, Lv, Cudd_Not(Unv));\n    if (Lsub1 == NULL) {\n\tCudd_RecursiveDeref(dd, Lsub0);\n\treturn(NULL);\n    }\n    Cudd_Ref(Lsub1);\n    Usub1 = Uv;\n\n    Isub0 = cuddZddIsop(dd, Lsub0, Usub0, &zdd_Isub0);\n    if (Isub0 == NULL) {\n\tCudd_RecursiveDeref(dd, Lsub0);\n\tCudd_RecursiveDeref(dd, Lsub1);\n\treturn(NULL);\n    }\n    /*\n    if ((!cuddIsConstant(Cudd_Regular(Isub0))) &&\n\t(Cudd_Regular(Isub0)->index != zdd_Isub0->index / 2 ||\n\tdd->permZ[index * 2] > dd->permZ[zdd_Isub0->index])) {\n\tprintf(\"*** ERROR : illegal permutation in ZDD. ***\\n\");\n    }\n    */\n    Cudd_Ref(Isub0);\n    Cudd_Ref(zdd_Isub0);\n    Isub1 = cuddZddIsop(dd, Lsub1, Usub1, &zdd_Isub1);\n    if (Isub1 == NULL) {\n\tCudd_RecursiveDeref(dd, Lsub0);\n\tCudd_RecursiveDeref(dd, Lsub1);\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\treturn(NULL);\n    }\n    /*\n    if ((!cuddIsConstant(Cudd_Regular(Isub1))) &&\n\t(Cudd_Regular(Isub1)->index != zdd_Isub1->index / 2 ||\n\tdd->permZ[index * 2] > dd->permZ[zdd_Isub1->index])) {\n\tprintf(\"*** ERROR : illegal permutation in ZDD. ***\\n\");\n    }\n    */\n    Cudd_Ref(Isub1);\n    Cudd_Ref(zdd_Isub1);\n    Cudd_RecursiveDeref(dd, Lsub0);\n    Cudd_RecursiveDeref(dd, Lsub1);\n\n    Lsuper0 = cuddBddAndRecur(dd, Lnv, Cudd_Not(Isub0));\n    if (Lsuper0 == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\treturn(NULL);\n    }\n    Cudd_Ref(Lsuper0);\n    Lsuper1 = cuddBddAndRecur(dd, Lv, Cudd_Not(Isub1));\n    if (Lsuper1 == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Lsuper0);\n\treturn(NULL);\n    }\n    Cudd_Ref(Lsuper1);\n    Usuper0 = Unv;\n    Usuper1 = Uv;\n\n    /* Ld = Lsuper0 + Lsuper1 */\n    Ld = cuddBddAndRecur(dd, Cudd_Not(Lsuper0), Cudd_Not(Lsuper1));\n    if (Ld == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Lsuper0);\n\tCudd_RecursiveDeref(dd, Lsuper1);\n\treturn(NULL);\n    }\n    Ld = Cudd_Not(Ld);\n    Cudd_Ref(Ld);\n    /* Ud = Usuper0 * Usuper1 */\n    Ud = cuddBddAndRecur(dd, Usuper0, Usuper1);\n    if (Ud == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Lsuper0);\n\tCudd_RecursiveDeref(dd, Lsuper1);\n\tCudd_RecursiveDeref(dd, Ld);\n\treturn(NULL);\n    }\n    Cudd_Ref(Ud);\n    Cudd_RecursiveDeref(dd, Lsuper0);\n    Cudd_RecursiveDeref(dd, Lsuper1);\n\n    Id = cuddZddIsop(dd, Ld, Ud, &zdd_Id);\n    if (Id == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Ld);\n\tCudd_RecursiveDeref(dd, Ud);\n\treturn(NULL);\n    }\n    /*\n    if ((!cuddIsConstant(Cudd_Regular(Id))) &&\n\t(Cudd_Regular(Id)->index != zdd_Id->index / 2 ||\n\tdd->permZ[index * 2] > dd->permZ[zdd_Id->index])) {\n\tprintf(\"*** ERROR : illegal permutation in ZDD. ***\\n\");\n    }\n    */\n    Cudd_Ref(Id);\n    Cudd_Ref(zdd_Id);\n    Cudd_RecursiveDeref(dd, Ld);\n    Cudd_RecursiveDeref(dd, Ud);\n\n    x = cuddUniqueInter(dd, index, one, zero);\n    if (x == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDerefZdd(dd, zdd_Id);\n\treturn(NULL);\n    }\n    Cudd_Ref(x);\n    /* term0 = x * Isub0 */\n    term0 = cuddBddAndRecur(dd, Cudd_Not(x), Isub0);\n    if (term0 == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDerefZdd(dd, zdd_Id);\n\tCudd_RecursiveDeref(dd, x);\n\treturn(NULL);\n    }\n    Cudd_Ref(term0);\n    Cudd_RecursiveDeref(dd, Isub0);\n    /* term1 = x * Isub1 */\n    term1 = cuddBddAndRecur(dd, x, Isub1);\n    if (term1 == NULL) {\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDerefZdd(dd, zdd_Id);\n\tCudd_RecursiveDeref(dd, x);\n\tCudd_RecursiveDeref(dd, term0);\n\treturn(NULL);\n    }\n    Cudd_Ref(term1);\n    Cudd_RecursiveDeref(dd, x);\n    Cudd_RecursiveDeref(dd, Isub1);\n    /* sum = term0 + term1 */\n    sum = cuddBddAndRecur(dd, Cudd_Not(term0), Cudd_Not(term1));\n    if (sum == NULL) {\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDerefZdd(dd, zdd_Id);\n\tCudd_RecursiveDeref(dd, term0);\n\tCudd_RecursiveDeref(dd, term1);\n\treturn(NULL);\n    }\n    sum = Cudd_Not(sum);\n    Cudd_Ref(sum);\n    Cudd_RecursiveDeref(dd, term0);\n    Cudd_RecursiveDeref(dd, term1);\n    /* r = sum + Id */\n    r = cuddBddAndRecur(dd, Cudd_Not(sum), Cudd_Not(Id));\n    r = Cudd_NotCond(r, r != NULL);\n    if (r == NULL) {\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\tCudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDerefZdd(dd, zdd_Id);\n\tCudd_RecursiveDeref(dd, sum);\n\treturn(NULL);\n    }\n    Cudd_Ref(r);\n    Cudd_RecursiveDeref(dd, sum);\n    Cudd_RecursiveDeref(dd, Id);\n\n    if (zdd_Isub0 != zdd_zero) {\n\tz = cuddZddGetNodeIVO(dd, index * 2 + 1, zdd_Isub0, zdd_Id);\n\tif (z == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\t    Cudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\t    Cudd_RecursiveDerefZdd(dd, zdd_Id);\n\t    Cudd_RecursiveDeref(dd, r);\n\t    return(NULL);\n\t}\n    }\n    else {\n\tz = zdd_Id;\n    }\n    Cudd_Ref(z);\n    if (zdd_Isub1 != zdd_zero) {\n\ty = cuddZddGetNodeIVO(dd, index * 2, zdd_Isub1, z);\n\tif (y == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, zdd_Isub0);\n\t    Cudd_RecursiveDerefZdd(dd, zdd_Isub1);\n\t    Cudd_RecursiveDerefZdd(dd, zdd_Id);\n\t    Cudd_RecursiveDeref(dd, r);\n\t    Cudd_RecursiveDerefZdd(dd, z);\n\t    return(NULL);\n\t}\n    }\n    else\n\ty = z;\n    Cudd_Ref(y);\n\n    Cudd_RecursiveDerefZdd(dd, zdd_Isub0);\n    Cudd_RecursiveDerefZdd(dd, zdd_Isub1);\n    Cudd_RecursiveDerefZdd(dd, zdd_Id);\n    Cudd_RecursiveDerefZdd(dd, z);\n\n    cuddCacheInsert2(dd, cuddBddIsop, L, U, r);\n    cuddCacheInsert2(dd, cacheOp, L, U, y);\n\n    Cudd_Deref(r);\n    Cudd_Deref(y);\n    *zdd_I = y;\n    /*\n    if (Cudd_Regular(r)->index != y->index / 2) {\n\tprintf(\"*** ERROR : mismatch in indices between BDD and ZDD. ***\\n\");\n    }\n    */\n    return(r);\n\n} /* end of cuddZddIsop */\n\n\n/**\n  @brief Performs the recursive step of Cudd_bddIsop.\n\n  @sideeffect None\n\n  @see Cudd_bddIsop\n\n*/\nDdNode\t*\ncuddBddIsop(\n  DdManager * dd,\n  DdNode * L,\n  DdNode * U)\n{\n    DdNode\t*one = DD_ONE(dd);\n    DdNode\t*zero = Cudd_Not(one);\n    int\t\tv, top_l, top_u;\n    DdNode\t*Lsub0, *Usub0, *Lsub1, *Usub1, *Ld, *Ud;\n    DdNode\t*Lsuper0, *Usuper0, *Lsuper1, *Usuper1;\n    DdNode\t*Isub0, *Isub1, *Id;\n    DdNode\t*x;\n    DdNode\t*term0, *term1, *sum;\n    DdNode\t*Lv, *Uv, *Lnv, *Unv;\n    DdNode\t*r;\n    unsigned\tindex;\n\n    statLine(dd);\n    if (L == zero)\n\treturn(zero);\n    if (U == one)\n\treturn(one);\n\n    /* Check cache */\n    r = cuddCacheLookup2(dd, cuddBddIsop, L, U);\n    if (r)\n\treturn(r);\n\n    top_l = dd->perm[Cudd_Regular(L)->index];\n    top_u = dd->perm[Cudd_Regular(U)->index];\n    v = ddMin(top_l, top_u);\n\n    /* Compute cofactors */\n    if (top_l == v) {\n\tindex = Cudd_Regular(L)->index;\n\tLv = Cudd_T(L);\n\tLnv = Cudd_E(L);\n\tif (Cudd_IsComplement(L)) {\n\t    Lv = Cudd_Not(Lv);\n\t    Lnv = Cudd_Not(Lnv);\n\t}\n    }\n    else {\n\tindex = Cudd_Regular(U)->index;\n\tLv = Lnv = L;\n    }\n\n    if (top_u == v) {\n\tUv = Cudd_T(U);\n\tUnv = Cudd_E(U);\n\tif (Cudd_IsComplement(U)) {\n\t    Uv = Cudd_Not(Uv);\n\t    Unv = Cudd_Not(Unv);\n\t}\n    }\n    else {\n\tUv = Unv = U;\n    }\n\n    Lsub0 = cuddBddAndRecur(dd, Lnv, Cudd_Not(Uv));\n    if (Lsub0 == NULL)\n\treturn(NULL);\n    Cudd_Ref(Lsub0);\n    Usub0 = Unv;\n    Lsub1 = cuddBddAndRecur(dd, Lv, Cudd_Not(Unv));\n    if (Lsub1 == NULL) {\n\tCudd_RecursiveDeref(dd, Lsub0);\n\treturn(NULL);\n    }\n    Cudd_Ref(Lsub1);\n    Usub1 = Uv;\n\n    Isub0 = cuddBddIsop(dd, Lsub0, Usub0);\n    if (Isub0 == NULL) {\n\tCudd_RecursiveDeref(dd, Lsub0);\n\tCudd_RecursiveDeref(dd, Lsub1);\n\treturn(NULL);\n    }\n    Cudd_Ref(Isub0);\n    Isub1 = cuddBddIsop(dd, Lsub1, Usub1);\n    if (Isub1 == NULL) {\n\tCudd_RecursiveDeref(dd, Lsub0);\n\tCudd_RecursiveDeref(dd, Lsub1);\n\tCudd_RecursiveDeref(dd, Isub0);\n\treturn(NULL);\n    }\n    Cudd_Ref(Isub1);\n    Cudd_RecursiveDeref(dd, Lsub0);\n    Cudd_RecursiveDeref(dd, Lsub1);\n\n    Lsuper0 = cuddBddAndRecur(dd, Lnv, Cudd_Not(Isub0));\n    if (Lsuper0 == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\treturn(NULL);\n    }\n    Cudd_Ref(Lsuper0);\n    Lsuper1 = cuddBddAndRecur(dd, Lv, Cudd_Not(Isub1));\n    if (Lsuper1 == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDeref(dd, Lsuper0);\n\treturn(NULL);\n    }\n    Cudd_Ref(Lsuper1);\n    Usuper0 = Unv;\n    Usuper1 = Uv;\n\n    /* Ld = Lsuper0 + Lsuper1 */\n    Ld = cuddBddAndRecur(dd, Cudd_Not(Lsuper0), Cudd_Not(Lsuper1));\n    Ld = Cudd_NotCond(Ld, Ld != NULL);\n    if (Ld == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDeref(dd, Lsuper0);\n\tCudd_RecursiveDeref(dd, Lsuper1);\n\treturn(NULL);\n    }\n    Cudd_Ref(Ld);\n    Ud = cuddBddAndRecur(dd, Usuper0, Usuper1);\n    if (Ud == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDeref(dd, Lsuper0);\n\tCudd_RecursiveDeref(dd, Lsuper1);\n\tCudd_RecursiveDeref(dd, Ld);\n\treturn(NULL);\n    }\n    Cudd_Ref(Ud);\n    Cudd_RecursiveDeref(dd, Lsuper0);\n    Cudd_RecursiveDeref(dd, Lsuper1);\n\n    Id = cuddBddIsop(dd, Ld, Ud);\n    if (Id == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDeref(dd, Ld);\n\tCudd_RecursiveDeref(dd, Ud);\n\treturn(NULL);\n    }\n    Cudd_Ref(Id);\n    Cudd_RecursiveDeref(dd, Ld);\n    Cudd_RecursiveDeref(dd, Ud);\n\n    x = cuddUniqueInter(dd, index, one, zero);\n    if (x == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDeref(dd, Id);\n\treturn(NULL);\n    }\n    Cudd_Ref(x);\n    term0 = cuddBddAndRecur(dd, Cudd_Not(x), Isub0);\n    if (term0 == NULL) {\n\tCudd_RecursiveDeref(dd, Isub0);\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDeref(dd, x);\n\treturn(NULL);\n    }\n    Cudd_Ref(term0);\n    Cudd_RecursiveDeref(dd, Isub0);\n    term1 = cuddBddAndRecur(dd, x, Isub1);\n    if (term1 == NULL) {\n\tCudd_RecursiveDeref(dd, Isub1);\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDeref(dd, x);\n\tCudd_RecursiveDeref(dd, term0);\n\treturn(NULL);\n    }\n    Cudd_Ref(term1);\n    Cudd_RecursiveDeref(dd, x);\n    Cudd_RecursiveDeref(dd, Isub1);\n    /* sum = term0 + term1 */\n    sum = cuddBddAndRecur(dd, Cudd_Not(term0), Cudd_Not(term1));\n    sum = Cudd_NotCond(sum, sum != NULL);\n    if (sum == NULL) {\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDeref(dd, term0);\n\tCudd_RecursiveDeref(dd, term1);\n\treturn(NULL);\n    }\n    Cudd_Ref(sum);\n    Cudd_RecursiveDeref(dd, term0);\n    Cudd_RecursiveDeref(dd, term1);\n    /* r = sum + Id */\n    r = cuddBddAndRecur(dd, Cudd_Not(sum), Cudd_Not(Id));\n    r = Cudd_NotCond(r, r != NULL);\n    if (r == NULL) {\n\tCudd_RecursiveDeref(dd, Id);\n\tCudd_RecursiveDeref(dd, sum);\n\treturn(NULL);\n    }\n    Cudd_Ref(r);\n    Cudd_RecursiveDeref(dd, sum);\n    Cudd_RecursiveDeref(dd, Id);\n\n    cuddCacheInsert2(dd, cuddBddIsop, L, U, r);\n\n    Cudd_Deref(r);\n    return(r);\n\n} /* end of cuddBddIsop */\n\n\n/**\n  @brief Converts a %ZDD cover to a %BDD.\n\n  @details It is a recursive algorithm that works as follows. First it\n  computes 3 cofactors of a %ZDD cover: f1, f0 and fd. Second, it\n  compute BDDs (b1, b0 and bd) of f1, f0 and fd.  Third, it computes\n  T=b1+bd and E=b0+bd. Fourth, it computes ITE(v,T,E) where v is the\n  variable which has the index of the top node of the %ZDD cover.  In\n  this case, since the index of v can be larger than either the one of\n  T or the one of E, cuddUniqueInterIVO is called, where IVO stands\n  for independent from variable ordering.\n\n  @return a %BDD node if successful; otherwise it returns NULL.\n\n  @see Cudd_MakeBddFromZddCover\n\n*/\nDdNode\t*\ncuddMakeBddFromZddCover(\n  DdManager * dd,\n  DdNode * node)\n{\n    DdNode\t*neW;\n    unsigned\tv;\n    DdNode\t*f1, *f0, *fd;\n    DdNode\t*b1, *b0, *bd;\n    DdNode\t*T, *E;\n\n    statLine(dd);\n    if (node == dd->one)\n\treturn(dd->one);\n    if (node == dd->zero)\n\treturn(Cudd_Not(dd->one));\n\n    /* Check cache */\n    neW = cuddCacheLookup1(dd, cuddMakeBddFromZddCover, node);\n    if (neW)\n\treturn(neW);\n\n    v = Cudd_Regular(node)->index;\t/* either yi or zi */\n    if (cuddZddGetCofactors3(dd, node, v, &f1, &f0, &fd)) return(NULL);\n    Cudd_Ref(f1);\n    Cudd_Ref(f0);\n    Cudd_Ref(fd);\n\n    b1 = cuddMakeBddFromZddCover(dd, f1);\n    if (!b1) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\treturn(NULL);\n    }\n    Cudd_Ref(b1);\n    b0 = cuddMakeBddFromZddCover(dd, f0);\n    if (!b0) {\n\tCudd_RecursiveDerefZdd(dd, f1);\n\tCudd_RecursiveDerefZdd(dd, f0);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tCudd_RecursiveDeref(dd, b1);\n\treturn(NULL);\n    }\n    Cudd_Ref(b0);\n    Cudd_RecursiveDerefZdd(dd, f1);\n    Cudd_RecursiveDerefZdd(dd, f0);\n    if (fd != dd->zero) {\n\tbd = cuddMakeBddFromZddCover(dd, fd);\n\tif (!bd) {\n\t    Cudd_RecursiveDerefZdd(dd, fd);\n\t    Cudd_RecursiveDeref(dd, b1);\n\t    Cudd_RecursiveDeref(dd, b0);\n\t    return(NULL);\n\t}\n\tCudd_Ref(bd);\n\tCudd_RecursiveDerefZdd(dd, fd);\n\n\tT = cuddBddAndRecur(dd, Cudd_Not(b1), Cudd_Not(bd));\n\tif (!T) {\n\t    Cudd_RecursiveDeref(dd, b1);\n\t    Cudd_RecursiveDeref(dd, b0);\n\t    Cudd_RecursiveDeref(dd, bd);\n\t    return(NULL);\n\t}\n\tT = Cudd_NotCond(T, T != NULL);\n\tCudd_Ref(T);\n\tCudd_RecursiveDeref(dd, b1);\n\tE = cuddBddAndRecur(dd, Cudd_Not(b0), Cudd_Not(bd));\n\tif (!E) {\n\t    Cudd_RecursiveDeref(dd, b0);\n\t    Cudd_RecursiveDeref(dd, bd);\n\t    Cudd_RecursiveDeref(dd, T);\n\t    return(NULL);\n\t}\n\tE = Cudd_NotCond(E, E != NULL);\n\tCudd_Ref(E);\n\tCudd_RecursiveDeref(dd, b0);\n\tCudd_RecursiveDeref(dd, bd);\n    }\n    else {\n\tCudd_RecursiveDerefZdd(dd, fd);\n\tT = b1;\n\tE = b0;\n    }\n\n    if (Cudd_IsComplement(T)) {\n\tneW = cuddUniqueInterIVO(dd, v / 2, Cudd_Not(T), Cudd_Not(E));\n\tif (!neW) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n\tneW = Cudd_Not(neW);\n    }\n    else {\n\tneW = cuddUniqueInterIVO(dd, v / 2, T, E);\n\tif (!neW) {\n\t    Cudd_RecursiveDeref(dd, T);\n\t    Cudd_RecursiveDeref(dd, E);\n\t    return(NULL);\n\t}\n    }\n    Cudd_Ref(neW);\n    Cudd_RecursiveDeref(dd, T);\n    Cudd_RecursiveDeref(dd, E);\n\n    cuddCacheInsert1(dd, cuddMakeBddFromZddCover, node, neW);\n    Cudd_Deref(neW);\n    return(neW);\n\n} /* end of cuddMakeBddFromZddCover */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n"
  },
  {
    "path": "cudd/cudd/cuddZddLin.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Procedures for dynamic variable ordering of ZDDs.\n\n  @see cuddLinear.c cuddZddReord.c\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define CUDD_SWAP_MOVE 0\n#define CUDD_LINEAR_TRANSFORM_MOVE 1\n#define CUDD_INVERSE_TRANSFORM_MOVE 2\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int cuddZddLinearInPlace (DdManager * table, int x, int y);\nstatic int cuddZddLinearAux (DdManager *table, int x, int xLow, int xHigh);\nstatic Move * cuddZddLinearUp (DdManager *table, int y, int xLow, Move *prevMoves);\nstatic Move * cuddZddLinearDown (DdManager *table, int x, int xHigh, Move *prevMoves);\nstatic int cuddZddLinearBackward (DdManager *table, int size, Move *moves);\nstatic Move* cuddZddUndoMoves (DdManager *table, Move *moves);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n\n\n/**\n  @brief Implementation of the linear sifting algorithm for ZDDs.\n\n  @details Assumes that no dead nodes are present.\n    <ol>\n    <li> Order all the variables according to the number of entries\n    in each unique table.\n    <li> Sift the variable up and down and applies the XOR transformation,\n    remembering each time the total size of the %DD heap.\n    <li> Select the best permutation.\n    <li> Repeat 3 and 4 for all variables.\n    </ol>\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddZddLinearSifting(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\ti;\n    IndexKey *var;\n    int\tsize;\n    int\tx;\n    int\tresult;\n#ifdef DD_STATS\n    int\tpreviousSize;\n#endif\n\n    size = table->sizeZ;\n\n    /* Find order in which to sift variables. */\n    var = ALLOC(IndexKey, size);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto cuddZddSiftingOutOfMem;\n    }\n\n    for (i = 0; i < size; i++) {\n\tx = table->permZ[i];\n\tvar[i].index = i;\n\tvar[i].keys = table->subtableZ[x].keys;\n    }\n\n    util_qsort(var, size, sizeof(IndexKey), cuddZddUniqueCompare);\n\n    /* Now sift. */\n    for (i = 0; i < ddMin(table->siftMaxVar, size); i++) {\n\tif (table->zddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime > table->timeLimit) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n\tx = table->permZ[var[i].index];\n\tif (x < lower || x > upper) continue;\n#ifdef DD_STATS\n\tpreviousSize = table->keysZ;\n#endif\n\tresult = cuddZddLinearAux(table, x, lower, upper);\n\tif (!result)\n\t    goto cuddZddSiftingOutOfMem;\n#ifdef DD_STATS\n\tif (table->keysZ < (unsigned) previousSize) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keysZ > (unsigned) previousSize) {\n\t    (void) fprintf(table->out,\"+\");\t/* should never happen */\n\t    (void) fprintf(table->out,\"\\nSize increased from %d to %d while sifting variable %d\\n\", previousSize, table->keysZ , var[i].index);\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n    FREE(var);\n\n    return(1);\n\ncuddZddSiftingOutOfMem:\n\n    if (var != NULL) FREE(var);\n\n    return(0);\n\n} /* end of cuddZddLinearSifting */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Linearly combines two adjacent variables.\n\n  @details It assumes that no dead nodes are present on entry to this\n  procedure.  The procedure then guarantees that no dead nodes will be\n  present when it terminates.  cuddZddLinearInPlace assumes that x\n  &lt; y.\n\n  @return the number of keys in the table if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see cuddZddSwapInPlace cuddLinearInPlace\n\n*/\nstatic int\ncuddZddLinearInPlace(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    DdNodePtr *xlist, *ylist;\n    int\t\txindex, yindex;\n    int\t\txslots, yslots;\n    int\t\txshift, yshift;\n    int         oldxkeys, oldykeys;\n    int         newxkeys, newykeys;\n    int\t\ti;\n    int\t\tposn;\n    DdNode\t*f, *f1, *f0, *f11, *f10, *f01, *f00;\n    DdNode\t*newf1, *newf0, *g, *next, *previous;\n    DdNode\t*special;\n    DdNode\t*empty = table->zero;\n\n#ifdef DD_DEBUG\n    assert(x < y);\n    assert(cuddZddNextHigh(table,x) == y);\n    assert(table->subtableZ[x].keys != 0);\n    assert(table->subtableZ[y].keys != 0);\n    assert(table->subtableZ[x].dead == 0);\n    assert(table->subtableZ[y].dead == 0);\n#endif\n\n    /* Get parameters of x subtable. */\n    xindex   = table->invpermZ[x];\n    xlist    = table->subtableZ[x].nodelist;\n    oldxkeys = table->subtableZ[x].keys;\n    xslots   = table->subtableZ[x].slots;\n    xshift   = table->subtableZ[x].shift;\n    newxkeys = 0;\n\n    /* Get parameters of y subtable. */\n    yindex   = table->invpermZ[y];\n    ylist    = table->subtableZ[y].nodelist;\n    oldykeys = table->subtableZ[y].keys;\n    yslots   = table->subtableZ[y].slots;\n    yshift   = table->subtableZ[y].shift;\n    newykeys = oldykeys;\n\n    /* The nodes in the x layer are put in two chains.  The chain\n    ** pointed by g holds the normal nodes. When re-expressed they stay\n    ** in the x list. The chain pointed by special holds the elements\n    ** that will move to the y list.\n    */\n    g = special = NULL;\n    for (i = 0; i < xslots; i++) {\n\tf = xlist[i];\n\tif (f == NULL) continue;\n\txlist[i] = NULL;\n\twhile (f != NULL) {\n\t    next = f->next;\n\t    f1 = cuddT(f);\n\t    /* if (f1->index == yindex) */ cuddSatDec(f1->ref);\n\t    f0 = cuddE(f);\n\t    /* if (f0->index == yindex) */ cuddSatDec(f0->ref);\n\t    if ((int) f1->index == yindex && cuddE(f1) == empty &&\n\t\t(int) f0->index != yindex) {\n\t\tf->next = special;\n\t\tspecial = f;\n\t    } else {\n\t\tf->next = g;\n\t\tg = f;\n\t    }\n\t    f = next;\n\t} /* while there are elements in the collision chain */\n    } /* for each slot of the x subtable */\n\n    /* Mark y nodes with pointers from above x. We mark them by\n    **  changing their index to x.\n    */\n    for (i = 0; i < yslots; i++) {\n\tf = ylist[i];\n\twhile (f != NULL) {\n\t    if (f->ref != 0) {\n\t\tf->index = xindex;\n\t    }\n\t    f = f->next;\n\t} /* while there are elements in the collision chain */\n    } /* for each slot of the y subtable */\n\n    /* Move special nodes to the y list. */\n    f = special;\n    while (f != NULL) {\n\tnext = f->next;\n\tf1 = cuddT(f);\n\tf11 = cuddT(f1);\n\tcuddT(f) = f11;\n\tcuddSatInc(f11->ref);\n\tf0 = cuddE(f);\n\tcuddSatInc(f0->ref);\n\tf->index = yindex;\n\t/* Insert at the beginning of the list so that it will be\n\t** found first if there is a duplicate. The duplicate will\n\t** eventually be moved or garbage collected. No node\n\t** re-expression will add a pointer to it.\n\t*/\n\tposn = ddHash(f11, f0, yshift);\n\tf->next = ylist[posn];\n\tylist[posn] = f;\n\tnewykeys++;\n\tf = next;\n    }\n\n    /* Take care of the remaining x nodes that must be re-expressed.\n    ** They form a linked list pointed by g.\n    */\n    f = g;\n    while (f != NULL) {\n#ifdef DD_COUNT\n\ttable->swapSteps++;\n#endif\n\tnext = f->next;\n\t/* Find f1, f0, f11, f10, f01, f00. */\n\tf1 = cuddT(f);\n\tif ((int) f1->index == yindex || (int) f1->index == xindex) {\n\t    f11 = cuddT(f1); f10 = cuddE(f1);\n\t} else {\n\t    f11 = empty; f10 = f1;\n\t}\n\tf0 = cuddE(f);\n\tif ((int) f0->index == yindex || (int) f0->index == xindex) {\n\t    f01 = cuddT(f0); f00 = cuddE(f0);\n\t} else {\n\t    f01 = empty; f00 = f0;\n\t}\n\t/* Create the new T child. */\n\tif (f01 == empty) {\n\t    newf1 = f10;\n\t    cuddSatInc(newf1->ref);\n\t} else {\n\t    /* Check ylist for triple (yindex, f01, f10). */\n\t    posn = ddHash(f01, f10, yshift);\n\t    /* For each element newf1 in collision list ylist[posn]. */\n\t    newf1 = ylist[posn];\n\t    /* Search the collision chain skipping the marked nodes. */\n\t    while (newf1 != NULL) {\n\t\tif (cuddT(newf1) == f01 && cuddE(newf1) == f10 &&\n\t\t    (int) newf1->index == yindex) {\n\t\t    cuddSatInc(newf1->ref);\n\t\t    break; /* match */\n\t\t}\n\t\tnewf1 = newf1->next;\n\t    } /* while newf1 */\n\t    if (newf1 == NULL) {\t/* no match */\n\t\tnewf1 = cuddDynamicAllocNode(table);\n\t\tif (newf1 == NULL)\n\t\t    goto zddSwapOutOfMem;\n\t\tnewf1->index = yindex; newf1->ref = 1;\n\t\tcuddT(newf1) = f01;\n\t\tcuddE(newf1) = f10;\n\t\t/* Insert newf1 in the collision list ylist[pos];\n\t\t** increase the ref counts of f01 and f10\n\t\t*/\n\t\tnewykeys++;\n\t\tnewf1->next = ylist[posn];\n\t\tylist[posn] = newf1;\n\t\tcuddSatInc(f01->ref);\n\t\tcuddSatInc(f10->ref);\n\t    }\n\t}\n\tcuddT(f) = newf1;\n\n\t/* Do the same for f0. */\n\t/* Create the new E child. */\n\tif (f11 == empty) {\n\t    newf0 = f00;\n\t    cuddSatInc(newf0->ref);\n\t} else {\n\t    /* Check ylist for triple (yindex, f11, f00). */\n\t    posn = ddHash(f11, f00, yshift);\n\t    /* For each element newf0 in collision list ylist[posn]. */\n\t    newf0 = ylist[posn];\n\t    while (newf0 != NULL) {\n\t\tif (cuddT(newf0) == f11 && cuddE(newf0) == f00 &&\n\t\t    (int) newf0->index == yindex) {\n\t\t    cuddSatInc(newf0->ref);\n\t\t    break; /* match */\n\t\t}\n\t\tnewf0 = newf0->next;\n\t    } /* while newf0 */\n\t    if (newf0 == NULL) {\t/* no match */\n\t\tnewf0 = cuddDynamicAllocNode(table);\n\t\tif (newf0 == NULL)\n\t\t    goto zddSwapOutOfMem;\n\t\tnewf0->index = yindex; newf0->ref = 1;\n\t\tcuddT(newf0) = f11; cuddE(newf0) = f00;\n\t\t/* Insert newf0 in the collision list ylist[posn];\n\t\t** increase the ref counts of f11 and f00.\n\t\t*/\n\t\tnewykeys++;\n\t\tnewf0->next = ylist[posn];\n\t\tylist[posn] = newf0;\n\t\tcuddSatInc(f11->ref);\n\t\tcuddSatInc(f00->ref);\n\t    }\n\t}\n\tcuddE(f) = newf0;\n\n\t/* Re-insert the modified f in xlist.\n\t** The modified f does not already exists in xlist.\n\t** (Because of the uniqueness of the cofactors.)\n\t*/\n\tposn = ddHash(newf1, newf0, xshift);\n\tnewxkeys++;\n\tf->next = xlist[posn];\n\txlist[posn] = f;\n\tf = next;\n    } /* while f != NULL */\n\n    /* GC the y layer and move the marked nodes to the x list. */\n\n    /* For each node f in ylist. */\n    for (i = 0; i < yslots; i++) {\n\tprevious = NULL;\n\tf = ylist[i];\n\twhile (f != NULL) {\n\t    next = f->next;\n\t    if (f->ref == 0) {\n\t\tcuddSatDec(cuddT(f)->ref);\n\t\tcuddSatDec(cuddE(f)->ref);\n\t\tcuddDeallocNode(table, f);\n\t\tnewykeys--;\n\t\tif (previous == NULL)\n\t\t    ylist[i] = next;\n\t\telse\n\t\t    previous->next = next;\n\t    } else if ((int) f->index == xindex) { /* move marked node */\n\t\tif (previous == NULL)\n\t\t    ylist[i] = next;\n\t\telse\n\t\t    previous->next = next;\n\t\tf1 = cuddT(f);\n\t\tcuddSatDec(f1->ref);\n\t\t/* Check ylist for triple (yindex, f1, empty). */\n\t\tposn = ddHash(f1, empty, yshift);\n\t\t/* For each element newf1 in collision list ylist[posn]. */\n\t\tnewf1 = ylist[posn];\n\t\twhile (newf1 != NULL) {\n\t\t    if (cuddT(newf1) == f1 && cuddE(newf1) == empty &&\n\t\t\t(int) newf1->index == yindex) {\n\t\t\tcuddSatInc(newf1->ref);\n\t\t\tbreak; /* match */\n\t\t    }\n\t\t    newf1 = newf1->next;\n\t\t} /* while newf1 */\n\t\tif (newf1 == NULL) {\t/* no match */\n\t\t    newf1 = cuddDynamicAllocNode(table);\n\t\t    if (newf1 == NULL)\n\t\t\tgoto zddSwapOutOfMem;\n\t\t    newf1->index = yindex; newf1->ref = 1;\n\t\t    cuddT(newf1) = f1; cuddE(newf1) = empty;\n\t\t    /* Insert newf1 in the collision list ylist[posn];\n\t\t    ** increase the ref counts of f1 and empty.\n\t\t    */\n\t\t    newykeys++;\n\t\t    newf1->next = ylist[posn];\n\t\t    ylist[posn] = newf1;\n\t\t    if (posn == i && previous == NULL)\n\t\t\tprevious = newf1;\n\t\t    cuddSatInc(f1->ref);\n\t\t    cuddSatInc(empty->ref);\n\t\t}\n\t\tcuddT(f) = newf1;\n\t\tf0 = cuddE(f);\n\t\t/* Insert f in x list. */\n\t\tposn = ddHash(newf1, f0, xshift);\n\t\tnewxkeys++;\n\t\tnewykeys--;\n\t\tf->next = xlist[posn];\n\t\txlist[posn] = f;\n\t    } else {\n\t\tprevious = f;\n\t    }\n\t    f = next;\n\t} /* while f */\n    } /* for i */\n\n    /* Set the appropriate fields in table. */\n    table->subtableZ[x].keys     = newxkeys;\n    table->subtableZ[y].keys     = newykeys;\n\n    table->keysZ += newxkeys + newykeys - oldxkeys - oldykeys;\n\n    /* Update univ section; univ[x] remains the same. */\n    table->univ[y] = cuddT(table->univ[x]);\n\n#if 0\n    (void) fprintf(table->out,\"x = %d  y = %d\\n\", x, y);\n    (void) Cudd_DebugCheck(table);\n    (void) Cudd_CheckKeys(table);\n#endif\n\n    return (table->keysZ);\n\nzddSwapOutOfMem:\n    (void) fprintf(table->err, \"Error: cuddZddSwapInPlace out of memory\\n\");\n\n    return (0);\n\n} /* end of cuddZddLinearInPlace */\n\n\n/**\n  @brief Given xLow <= x <= xHigh moves x up and down between the\n  boundaries.\n\n  @details Finds the best position and does the required changes.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddLinearAux(\n  DdManager * table,\n  int  x,\n  int  xLow,\n  int  xHigh)\n{\n    Move\t*move;\n    Move\t*moveUp;\t/* list of up move */\n    Move\t*moveDown;\t/* list of down move */\n\n    int\t\tinitial_size;\n    int\t\tresult;\n\n    initial_size = table->keysZ;\n\n#ifdef DD_DEBUG\n    assert(table->subtableZ[x].keys > 0);\n#endif\n\n    moveDown = NULL;\n    moveUp = NULL;\n\n    if (x == xLow) {\n\tmoveDown = cuddZddLinearDown(table, x, xHigh, NULL);\n\t/* At this point x --> xHigh. */\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM)\n\t    goto cuddZddLinearAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = cuddZddLinearBackward(table, initial_size, moveDown);\n\tif (!result)\n\t    goto cuddZddLinearAuxOutOfMem;\n\n    } else if (x == xHigh) {\n\tmoveUp = cuddZddLinearUp(table, x, xLow, NULL);\n\t/* At this point x --> xLow. */\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM)\n\t    goto cuddZddLinearAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = cuddZddLinearBackward(table, initial_size, moveUp);\n\tif (!result)\n\t    goto cuddZddLinearAuxOutOfMem;\n\n    } else if ((x - xLow) > (xHigh - x)) { /* must go down first: shorter */\n\tmoveDown = cuddZddLinearDown(table, x, xHigh, NULL);\n\t/* At this point x --> xHigh. */\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM)\n\t    goto cuddZddLinearAuxOutOfMem;\n\tmoveUp = cuddZddUndoMoves(table,moveDown);\n#ifdef DD_DEBUG\n\tassert(moveUp == NULL || moveUp->x == (DdHalfWord) x);\n#endif\n\tmoveUp = cuddZddLinearUp(table, x, xLow, moveUp);\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM)\n\t    goto cuddZddLinearAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = cuddZddLinearBackward(table, initial_size, moveUp);\n\tif (!result)\n\t    goto cuddZddLinearAuxOutOfMem;\n\n    } else {\n\tmoveUp = cuddZddLinearUp(table, x, xLow, NULL);\n\t/* At this point x --> xHigh. */\n\tif (moveUp == (Move *) CUDD_OUT_OF_MEM)\n\t    goto cuddZddLinearAuxOutOfMem;\n\t/* Then move up. */\n\tmoveDown = cuddZddUndoMoves(table,moveUp);\n#ifdef DD_DEBUG\n\tassert(moveDown == NULL || moveDown->y == (DdHalfWord) x);\n#endif\n\tmoveDown = cuddZddLinearDown(table, x, xHigh, moveDown);\n\tif (moveDown == (Move *) CUDD_OUT_OF_MEM)\n\t    goto cuddZddLinearAuxOutOfMem;\n\t/* Move backward and stop at best position. */\n\tresult = cuddZddLinearBackward(table, initial_size, moveDown);\n\tif (!result)\n\t    goto cuddZddLinearAuxOutOfMem;\n    }\n\n    while (moveDown != NULL) {\n\tmove = moveDown->next;\n\tcuddDeallocMove(table, moveDown);\n\tmoveDown = move;\n    }\n    while (moveUp != NULL) {\n\tmove = moveUp->next;\n\tcuddDeallocMove(table, moveUp);\n\tmoveUp = move;\n    }\n\n    return(1);\n\ncuddZddLinearAuxOutOfMem:\n    if (moveDown != (Move *) CUDD_OUT_OF_MEM) {\n\twhile (moveDown != NULL) {\n\t    move = moveDown->next;\n\t    cuddDeallocMove(table, moveDown);\n\t    moveDown = move;\n\t}\n    }\n    if (moveUp != (Move *) CUDD_OUT_OF_MEM) {\n\twhile (moveUp != NULL) {\n\t    move = moveUp->next;\n\t    cuddDeallocMove(table, moveUp);\n\t    moveUp = move;\n\t}\n    }\n\n    return(0);\n\n} /* end of cuddZddLinearAux */\n\n\n/**\n  @brief Sifts a variable up applying the XOR transformation.\n\n  @details Moves y up until either it reaches the bound (xLow) or the\n  size of the %ZDD heap increases too much.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\ncuddZddLinearUp(\n  DdManager * table,\n  int  y,\n  int  xLow,\n  Move * prevMoves)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\tx;\n    int\t\tsize, newsize;\n    int\t\tlimitSize;\n\n    moves = prevMoves;\n    limitSize = table->keysZ;\n\n    x = cuddZddNextLow(table, y);\n    while (x >= xLow) {\n\tsize = cuddZddSwapInPlace(table, x, y);\n\tif (size == 0)\n\t    goto cuddZddLinearUpOutOfMem;\n\tnewsize = cuddZddLinearInPlace(table, x, y);\n\tif (newsize == 0)\n\t    goto cuddZddLinearUpOutOfMem;\n\tmove = (Move *) cuddDynamicAllocNode(table);\n\tif (move == NULL)\n\t    goto cuddZddLinearUpOutOfMem;\n\tmove->x = x;\n\tmove->y = y;\n\tmove->next = moves;\n\tmoves = move;\n\tmove->flags = CUDD_SWAP_MOVE;\n\tif (newsize > size) {\n\t    /* Undo transformation. The transformation we apply is\n\t    ** its own inverse. Hence, we just apply the transformation\n\t    ** again.\n\t    */\n\t    newsize = cuddZddLinearInPlace(table,x,y);\n\t    if (newsize == 0) goto cuddZddLinearUpOutOfMem;\n#ifdef DD_DEBUG\n\t    if (newsize != size) {\n\t\t(void) fprintf(table->err,\"Change in size after identity transformation! From %d to %d\\n\",size,newsize);\n\t    }\n#endif\n\t} else {\n\t    size = newsize;\n\t    move->flags = CUDD_LINEAR_TRANSFORM_MOVE;\n\t}\n\tmove->size = size;\n\n\tif ((double)size > (double)limitSize * table->maxGrowth)\n\t    break;\n        if (size < limitSize)\n\t    limitSize = size;\n\n\ty = x;\n\tx = cuddZddNextLow(table, y);\n    }\n    return(moves);\n\ncuddZddLinearUpOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return((Move *) CUDD_OUT_OF_MEM);\n\n} /* end of cuddZddLinearUp */\n\n\n/**\n  @brief Sifts a variable down and applies the XOR transformation.\n\n  @details Sifts a variable down. Moves x down until either it\n  reaches the bound (xHigh) or the size of the %ZDD heap increases too\n  much.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\ncuddZddLinearDown(\n  DdManager * table,\n  int  x,\n  int  xHigh,\n  Move * prevMoves)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\ty;\n    int\t\tsize, newsize;\n    int\t\tlimitSize;\n\n    moves = prevMoves;\n    limitSize = table->keysZ;\n\n    y = cuddZddNextHigh(table, x);\n    while (y <= xHigh) {\n\tsize = cuddZddSwapInPlace(table, x, y);\n\tif (size == 0)\n\t    goto cuddZddLinearDownOutOfMem;\n\tnewsize = cuddZddLinearInPlace(table, x, y);\n\tif (newsize == 0)\n\t    goto cuddZddLinearDownOutOfMem;\n\tmove = (Move *) cuddDynamicAllocNode(table);\n\tif (move == NULL)\n\t    goto cuddZddLinearDownOutOfMem;\n\tmove->x = x;\n\tmove->y = y;\n\tmove->next = moves;\n\tmoves = move;\n\tmove->flags = CUDD_SWAP_MOVE;\n\tif (newsize > size) {\n\t    /* Undo transformation. The transformation we apply is\n\t    ** its own inverse. Hence, we just apply the transformation\n\t    ** again.\n\t    */\n\t    newsize = cuddZddLinearInPlace(table,x,y);\n\t    if (newsize == 0) goto cuddZddLinearDownOutOfMem;\n\t    if (newsize != size) {\n\t\t(void) fprintf(table->err,\"Change in size after identity transformation! From %d to %d\\n\",size,newsize);\n\t    }\n\t} else {\n\t    size = newsize;\n\t    move->flags = CUDD_LINEAR_TRANSFORM_MOVE;\n\t}\n\tmove->size = size;\n\n\tif ((double)size > (double)limitSize * table->maxGrowth)\n\t    break;\n        if (size < limitSize)\n\t    limitSize = size;\n\n\tx = y;\n\ty = cuddZddNextHigh(table, x);\n    }\n    return(moves);\n\ncuddZddLinearDownOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return((Move *) CUDD_OUT_OF_MEM);\n\n} /* end of cuddZddLinearDown */\n\n\n/**\n  @brief Given a set of moves, returns the %ZDD heap to the position\n  giving the minimum size.\n\n  @details In case of ties, returns to the closest position giving the\n  minimum size.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddLinearBackward(\n  DdManager * table,\n  int  size,\n  Move * moves)\n{\n    Move\t*move;\n    int\t\tres;\n\n    /* Find the minimum size among moves. */\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size < size) {\n\t    size = move->size;\n\t}\n    }\n\n    for (move = moves; move != NULL; move = move->next) {\n\tif (move->size == size) return(1);\n\tif (move->flags == CUDD_LINEAR_TRANSFORM_MOVE) {\n\t    res = cuddZddLinearInPlace(table,(int)move->x,(int)move->y);\n\t    if (!res) return(0);\n\t}\n\tres = cuddZddSwapInPlace(table, move->x, move->y);\n\tif (!res)\n\t    return(0);\n\tif (move->flags == CUDD_INVERSE_TRANSFORM_MOVE) {\n\t    res = cuddZddLinearInPlace(table,(int)move->x,(int)move->y);\n\t    if (!res) return(0);\n\t}\n    }\n\n    return(1);\n\n} /* end of cuddZddLinearBackward */\n\n\n/**\n  @brief Given a set of moves, returns the %ZDD heap to the order\n  in effect before the moves.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic Move*\ncuddZddUndoMoves(\n  DdManager * table,\n  Move * moves)\n{\n    Move *invmoves = NULL;\n    Move *move;\n    Move *invmove;\n    int\tsize;\n\n    for (move = moves; move != NULL; move = move->next) {\n\tinvmove = (Move *) cuddDynamicAllocNode(table);\n\tif (invmove == NULL) goto cuddZddUndoMovesOutOfMem;\n\tinvmove->x = move->x;\n\tinvmove->y = move->y;\n\tinvmove->next = invmoves;\n\tinvmoves = invmove;\n\tif (move->flags == CUDD_SWAP_MOVE) {\n\t    invmove->flags = CUDD_SWAP_MOVE;\n\t    size = cuddZddSwapInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto cuddZddUndoMovesOutOfMem;\n\t} else if (move->flags == CUDD_LINEAR_TRANSFORM_MOVE) {\n\t    invmove->flags = CUDD_INVERSE_TRANSFORM_MOVE;\n\t    size = cuddZddLinearInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto cuddZddUndoMovesOutOfMem;\n\t    size = cuddZddSwapInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto cuddZddUndoMovesOutOfMem;\n\t} else { /* must be CUDD_INVERSE_TRANSFORM_MOVE */\n#ifdef DD_DEBUG\n\t    (void) fprintf(table->err,\"Unforseen event in ddUndoMoves!\\n\");\n#endif\n\t    invmove->flags = CUDD_LINEAR_TRANSFORM_MOVE;\n\t    size = cuddZddSwapInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto cuddZddUndoMovesOutOfMem;\n\t    size = cuddZddLinearInPlace(table,(int)move->x,(int)move->y);\n\t    if (!size) goto cuddZddUndoMovesOutOfMem;\n\t}\n\tinvmove->size = size;\n    }\n\n    return(invmoves);\n\ncuddZddUndoMovesOutOfMem:\n    while (invmoves != NULL) {\n\tmove = invmoves->next;\n\tcuddDeallocMove(table, invmoves);\n\tinvmoves = move;\n    }\n    return((Move *) CUDD_OUT_OF_MEM);\n\n} /* end of cuddZddUndoMoves */\n\n"
  },
  {
    "path": "cudd/cudd/cuddZddMisc.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Miscellaneous utility functions for ZDDs.\n\n  @author Hyong-Kyoon Shin, In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include <math.h>\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int cuddZddDagInt (DdNode *n, st_table *tab);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Counts the number of nodes in a %ZDD.\n\n  @deprecated This function duplicates Cudd_DagSize and is only\n  retained for compatibility.\n\n  @sideeffect None\n\n  @see Cudd_DagSize\n\n*/\nint\nCudd_zddDagSize(\n  DdNode * p_node)\n{\n\n    int\t\ti;\n    st_table\t*table;\n\n    table = st_init_table(st_ptrcmp, st_ptrhash);\n    i = cuddZddDagInt(p_node, table);\n    st_free_table(table);\n    return(i);\n\n} /* end of Cudd_zddDagSize */\n\n\n/**\n  @brief Counts the number of minterms of a %ZDD.\n\n  @details Counts the number of minterms of the %ZDD rooted at\n  <code>node</code>.  This procedure takes a parameter\n  <code>path</code> that specifies how many variables are in the\n  support of the function.\n\n  @return the count.  If the procedure runs out of memory, it returns\n  (double) CUDD_OUT_OF_MEM.\n\n  @sideeffect None\n\n  @see Cudd_zddCountDouble\n\n*/\ndouble\nCudd_zddCountMinterm(\n  DdManager * zdd,\n  DdNode * node,\n  int  path)\n{\n    double\tdc_var, minterms;\n\n    dc_var = (double)((double)(zdd->sizeZ) - (double)path);\n    minterms = Cudd_zddCountDouble(zdd, node) / pow(2.0, dc_var);\n    return(minterms);\n\n} /* end of Cudd_zddCountMinterm */\n\n\n/**\n  @brief Prints the %ZDD table for debugging purposes.\n\n  @sideeffect None\n\n*/\nvoid\nCudd_zddPrintSubtable(\n  DdManager * table)\n{\n    int\t\ti, j;\n    DdNode\t*z1, *z1_next, *base;\n    DdSubtable\t*ZSubTable;\n\n    base = table->one;\n    for (i = table->sizeZ - 1; i >= 0; i--) {\n\tZSubTable = &(table->subtableZ[i]);\n\tprintf(\"subtable[%d]:\\n\", i);\n\tfor (j = ZSubTable->slots - 1; j >= 0; j--) {\n\t    z1 = ZSubTable->nodelist[j];\n\t    while (z1 != NIL(DdNode)) {\n\t\t(void) fprintf(table->out,\n\t\t    \"ID = 0x%\" PRIxPTR \"\\tindex = %u\\tr = %u\\t\",\n\t\t    (ptruint) z1 / (ptruint) sizeof(DdNode),\n\t\t    z1->index, z1->ref);\n\t\tz1_next = cuddT(z1);\n\t\tif (Cudd_IsConstantInt(z1_next)) {\n\t\t    (void) fprintf(table->out, \"T = %d\\t\\t\",\n\t\t\t(z1_next == base));\n\t\t}\n\t\telse {\n\t\t    (void) fprintf(table->out, \"T = 0x%\" PRIxPTR \"\\t\",\n\t\t\t(ptruint) z1_next / (ptruint) sizeof(DdNode));\n\t\t}\n\t\tz1_next = cuddE(z1);\n\t\tif (Cudd_IsConstantInt(z1_next)) {\n\t\t    (void) fprintf(table->out, \"E = %d\\n\",\n\t\t\t(z1_next == base));\n\t\t}\n\t\telse {\n\t\t    (void) fprintf(table->out, \"E = 0x%\" PRIxPTR \"\\n\",\n\t\t\t(ptruint) z1_next / (ptruint) sizeof(DdNode));\n\t\t}\n\n\t\tz1_next = z1->next;\n\t\tz1 = z1_next;\n\t    }\n\t}\n    }\n    putchar('\\n');\n\n} /* Cudd_zddPrintSubtable */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddDagSize.\n\n  @details Does not check for out-of-memory conditions.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddDagInt(\n  DdNode * n,\n  st_table * tab)\n{\n    if (n == NIL(DdNode))\n\treturn(0);\n\n    if (st_is_member(tab, n) == 1)\n\treturn(0);\n\n    if (Cudd_IsConstantInt(n))\n\treturn(0);\n\n    (void)st_insert(tab, n, NIL(void));\n    return(1 + cuddZddDagInt(cuddT(n), tab) +\n\tcuddZddDagInt(cuddE(n), tab));\n\n} /* cuddZddDagInt */\n"
  },
  {
    "path": "cudd/cudd/cuddZddPort.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions that translate BDDs to ZDDs.\n\n  @author Hyong-kyoon Shin, In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * zddPortFromBddStep (DdManager *dd, DdNode *B, int expected);\nstatic DdNode * zddPortToBddStep (DdManager *dd, DdNode *f, int depth);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Converts a %BDD into a %ZDD.\n\n  @details This function assumes that there is a one-to-one\n  correspondence between the %BDD variables and the %ZDD variables, and\n  that the variable order is the same for both types of\n  variables. These conditions are established if the %ZDD variables are\n  created by one call to Cudd_zddVarsFromBddVars with multiplicity = 1.\n\n  @return a pointer to the resulting %ZDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddVarsFromBddVars\n\n*/\nDdNode *\nCudd_zddPortFromBdd(\n  DdManager * dd,\n  DdNode * B)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = zddPortFromBddStep(dd,B,0);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_zddPortFromBdd */\n\n\n/**\n  @brief Converts a %ZDD into a %BDD.\n\n  @return a pointer to the resulting %ZDD if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddPortFromBdd\n\n*/\nDdNode *\nCudd_zddPortToBdd(\n  DdManager * dd,\n  DdNode * f)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = zddPortToBddStep(dd,f,0);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(res);\n\n} /* end of Cudd_zddPortToBdd */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddPortFromBdd.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nzddPortFromBddStep(\n  DdManager * dd,\n  DdNode * B,\n  int  expected)\n{\n    DdNode\t*res, *prevZdd, *t, *e;\n    DdNode\t*Breg, *Bt, *Be;\n    int\t\tid;\n    int\t\tlevel;\n\n    statLine(dd);\n    /* Terminal cases. */\n    if (B == Cudd_Not(DD_ONE(dd)))\n\treturn(DD_ZERO(dd));\n    if (B == DD_ONE(dd)) {\n\tif (expected >= dd->sizeZ) {\n\t    return(DD_ONE(dd));\n\t} else {\n\t    return(dd->univ[expected]);\n\t}\n    }\n\n    Breg = Cudd_Regular(B);\n\n    /* Computed table look-up. */\n    res = cuddCacheLookup1Zdd(dd,Cudd_zddPortFromBdd,B);\n    if (res != NULL) {\n\tlevel = cuddI(dd,Breg->index);\n\t/* Adding DC vars. */\n\tif (expected < level) {\n\t    /* Add suppressed variables. */\n\t    cuddRef(res);\n\t    for (level--; level >= expected; level--) {\n\t\tprevZdd = res;\n\t\tid = dd->invperm[level];\n\t\tres = cuddZddGetNode(dd, id, prevZdd, prevZdd);\n\t\tif (res == NULL) {\n\t\t    Cudd_RecursiveDerefZdd(dd, prevZdd);\n\t\t    return(NULL);\n\t\t}\n\t\tcuddRef(res);\n\t\tCudd_RecursiveDerefZdd(dd, prevZdd);\n\t    }\n\t    cuddDeref(res);\n\t}\n\treturn(res);\n    }\t/* end of cache look-up */\n\n    if (Cudd_IsComplement(B)) {\n\tBt = Cudd_Not(cuddT(Breg));\n\tBe = Cudd_Not(cuddE(Breg));\n    } else {\n\tBt = cuddT(Breg);\n\tBe = cuddE(Breg);\n    }\n\n    id = (int) Breg->index;\n    level = cuddI(dd,id);\n    t = zddPortFromBddStep(dd, Bt, level+1);\n    if (t == NULL) return(NULL);\n    cuddRef(t);\n    e = zddPortFromBddStep(dd, Be, level+1);\n    if (e == NULL) {\n\tCudd_RecursiveDerefZdd(dd, t);\n\treturn(NULL);\n    }\n    cuddRef(e);\n    res = cuddZddGetNode(dd, id, t, e);\n    if (res == NULL) {\n\tCudd_RecursiveDerefZdd(dd, t);\n\tCudd_RecursiveDerefZdd(dd, e);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDerefZdd(dd, t);\n    Cudd_RecursiveDerefZdd(dd, e);\n\n    cuddCacheInsert1(dd,Cudd_zddPortFromBdd,B,res);\n\n    for (level--; level >= expected; level--) {\n\tprevZdd = res;\n\tid = dd->invperm[level];\n\tres = cuddZddGetNode(dd, id, prevZdd, prevZdd);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, prevZdd);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDerefZdd(dd, prevZdd);\n    }\n\n    cuddDeref(res);\n    return(res);\n\n} /* end of zddPortFromBddStep */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddPortToBdd.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nzddPortToBddStep(\n  DdManager * dd /* manager */,\n  DdNode * f /* %ZDD to be converted */,\n  int  depth /* recursion depth */)\n{\n    DdNode *one, *zero, *T, *E, *res, *var;\n    int index;\n    int level;\n\n    statLine(dd);\n    one = DD_ONE(dd);\n    zero = DD_ZERO(dd);\n    if (f == zero) return(Cudd_Not(one));\n\n    if (depth == dd->sizeZ) return(one);\n\n    index = dd->invpermZ[depth];\n    level = cuddIZ(dd,f->index);\n    var = cuddUniqueInter(dd,index,one,Cudd_Not(one));\n    if (var == NULL) return(NULL);\n    cuddRef(var);\n\n    if (level > depth) {\n\tE = zddPortToBddStep(dd,f,depth+1);\n\tif (E == NULL) {\n\t    Cudd_RecursiveDeref(dd,var);\n\t    return(NULL);\n\t}\n\tcuddRef(E);\n\tres = cuddBddIteRecur(dd,var,Cudd_Not(one),E);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDeref(dd,var);\n\t    Cudd_RecursiveDeref(dd,E);\n\t    return(NULL);\n\t}\n\tcuddRef(res);\n\tCudd_RecursiveDeref(dd,var);\n\tCudd_RecursiveDeref(dd,E);\n\tcuddDeref(res);\n\treturn(res);\n    }\n\n    res = cuddCacheLookup1(dd,Cudd_zddPortToBdd,f);\n    if (res != NULL) {\n\tCudd_RecursiveDeref(dd,var);\n\treturn(res);\n    }\n\n    T = zddPortToBddStep(dd,cuddT(f),depth+1);\n    if (T == NULL) {\n\tCudd_RecursiveDeref(dd,var);\n\treturn(NULL);\n    }\n    cuddRef(T);\n    E = zddPortToBddStep(dd,cuddE(f),depth+1);\n    if (E == NULL) {\n\tCudd_RecursiveDeref(dd,var);\n\tCudd_RecursiveDeref(dd,T);\n\treturn(NULL);\n    }\n    cuddRef(E);\n\n    res = cuddBddIteRecur(dd,var,T,E);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd,var);\n\tCudd_RecursiveDeref(dd,T);\n\tCudd_RecursiveDeref(dd,E);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDeref(dd,var);\n    Cudd_RecursiveDeref(dd,T);\n    Cudd_RecursiveDeref(dd,E);\n    cuddDeref(res);\n\n    cuddCacheInsert1(dd,Cudd_zddPortToBdd,f,res);\n\n    return(res);\n\n} /* end of zddPortToBddStep */\n\n"
  },
  {
    "path": "cudd/cudd/cuddZddReord.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Procedures for dynamic variable ordering of ZDDs.\n\n  @author Hyong-Kyoon Shin, In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define DD_MAX_SUBTABLE_SPARSITY 8\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic Move * zddSwapAny (DdManager *table, int x, int y);\nstatic int cuddZddSiftingAux (DdManager *table, int x, int x_low, int x_high);\nstatic Move * cuddZddSiftingUp (DdManager *table, int x, int x_low, int initial_size);\nstatic Move * cuddZddSiftingDown (DdManager *table, int x, int x_high, int initial_size);\nstatic int cuddZddSiftingBackward (DdManager *table, Move *moves, int size);\nstatic void zddReorderPreprocess (DdManager *table);\nstatic int zddReorderPostprocess (DdManager *table);\nstatic int zddShuffle (DdManager *table, int *permutation);\nstatic int zddSiftUp (DdManager *table, int x, int xLow);\nstatic void zddFixTree (DdManager *table, MtrNode *treenode);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Main dynamic reordering routine for ZDDs.\n\n  @details@parblock\n  Calls one of the possible reordering procedures:\n  <ul>\n  <li>Swapping\n  <li>Sifting\n  <li>Symmetric Sifting\n  </ul>\n\n  For sifting and symmetric sifting it is possible to request reordering\n  to convergence.\n\n  The core of all methods is the reordering procedure\n  cuddZddSwapInPlace() which swaps two adjacent variables.\n  @endparblock\n\n  @return 1 in case of success; 0 otherwise. In the case of symmetric\n  sifting (with and without convergence) returns 1 plus the number of\n  symmetric variables, in case of success.\n\n  @sideeffect Changes the variable order for all ZDDs and clears\n  the cache.\n\n*/\nint\nCudd_zddReduceHeap(\n  DdManager * table /**< DD manager */,\n  Cudd_ReorderingType heuristic /**< method used for reordering */,\n  int minsize /**< bound below which no reordering occurs */)\n{\n    DdHook\t *hook;\n    int\t\t result;\n    unsigned int nextDyn;\n#ifdef DD_STATS\n    unsigned int initialSize;\n    unsigned int finalSize;\n#endif\n    unsigned long localTime;\n\n    /* Don't reorder if there are too many dead nodes. */\n    if (table->keysZ - table->deadZ < (unsigned) minsize)\n\treturn(1);\n\n    if (heuristic == CUDD_REORDER_SAME) {\n\theuristic = table->autoMethodZ;\n    }\n    if (heuristic == CUDD_REORDER_NONE) {\n\treturn(1);\n    }\n\n    /* This call to Cudd_zddReduceHeap does initiate reordering. Therefore\n    ** we count it.\n    */\n    table->reorderings++;\n\n    localTime = util_cpu_time();\n\n    /* Run the hook functions. */\n    hook = table->preReorderingHook;\n    while (hook != NULL) {\n\tint res = (hook->f)(table, \"ZDD\", (void *)heuristic);\n\tif (res == 0) return(0);\n\thook = hook->next;\n    }\n\n    /* Clear the cache and collect garbage. */\n    zddReorderPreprocess(table);\n    table->zddTotalNumberSwapping = 0;\n\n#ifdef DD_STATS\n    initialSize = table->keysZ;\n\n    switch(heuristic) {\n    case CUDD_REORDER_RANDOM:\n    case CUDD_REORDER_RANDOM_PIVOT:\n\t(void) fprintf(table->out,\"#:I_RANDOM  \");\n\tbreak;\n    case CUDD_REORDER_SIFT:\n    case CUDD_REORDER_SIFT_CONVERGE:\n    case CUDD_REORDER_SYMM_SIFT:\n    case CUDD_REORDER_SYMM_SIFT_CONV:\n\t(void) fprintf(table->out,\"#:I_SIFTING \");\n\tbreak;\n    case CUDD_REORDER_LINEAR:\n    case CUDD_REORDER_LINEAR_CONVERGE:\n\t(void) fprintf(table->out,\"#:I_LINSIFT \");\n\tbreak;\n    default:\n\t(void) fprintf(table->err,\"Unsupported ZDD reordering method\\n\");\n\treturn(0);\n    }\n    (void) fprintf(table->out,\"%8d: initial size\",initialSize); \n#endif\n\n    result = cuddZddTreeSifting(table,heuristic);\n\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n\");\n    finalSize = table->keysZ;\n    (void) fprintf(table->out,\"#:F_REORDER %8d: final size\\n\",finalSize); \n    (void) fprintf(table->out,\"#:T_REORDER %8g: total time (sec)\\n\",\n\t\t   ((double)(util_cpu_time() - localTime)/1000.0)); \n    (void) fprintf(table->out,\"#:N_REORDER %8d: total swaps\\n\",\n\t\t   table->zddTotalNumberSwapping);\n#endif\n\n    if (result == 0)\n\treturn(0);\n\n    if (!zddReorderPostprocess(table))\n\treturn(0);\n\n    if (table->realignZ) {\n\tif (!cuddBddAlignToZdd(table))\n\t    return(0);\n    }\n\n    nextDyn = table->keysZ * DD_DYN_RATIO;\n    if (table->reorderings < 20 || nextDyn > table->nextDyn)\n\ttable->nextDyn = nextDyn;\n    else\n\ttable->nextDyn += 20;\n\n    table->reordered = 1;\n\n    /* Run hook functions. */\n    hook = table->postReorderingHook;\n    while (hook != NULL) {\n      int res = (hook->f)(table, \"ZDD\", (void *)(ptruint)localTime);\n\tif (res == 0) return(0);\n\thook = hook->next;\n    }\n    /* Update cumulative reordering time. */\n    table->reordTime += util_cpu_time() - localTime;\n\n    return(result);\n\n} /* end of Cudd_zddReduceHeap */\n\n\n/**\n  @brief Reorders %ZDD variables according to given permutation.\n\n  @details The i-th entry of the permutation array contains the index\n  of the variable that should be brought to the i-th level.  The size\n  of the array should be equal or greater to the number of variables\n  currently in use.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect Changes the %ZDD variable order for all diagrams and clears\n  the cache.\n\n  @see Cudd_zddReduceHeap\n\n*/\nint\nCudd_zddShuffleHeap(\n  DdManager * table /**< DD manager */,\n  int * permutation /**< required variable permutation */)\n{\n\n    int\tresult;\n\n    zddReorderPreprocess(table);\n\n    result = zddShuffle(table,permutation);\n\n    if (!zddReorderPostprocess(table)) return(0);\n\n    return(result);\n\n} /* end of Cudd_zddShuffleHeap */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Reorders %ZDD variables according to the order of the %BDD\n  variables.\n\n  @details This function can be called at the end of %BDD reordering to\n  insure that the order of the %ZDD variables is consistent with the\n  order of the %BDD variables. The number of %ZDD variables must be a\n  multiple of the number of %BDD variables. Let <code>M</code> be the\n  ratio of the two numbers. cuddZddAlignToBdd then considers the %ZDD\n  variables from <code>M*i</code> to <code>(M+1)*i-1</code> as\n  corresponding to %BDD variable <code>i</code>.  This function should\n  be normally called from Cudd_ReduceHeap, which clears the cache.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect Changes the %ZDD variable order for all diagrams and performs\n  garbage collection of the %ZDD unique table.\n\n  @see Cudd_zddShuffleHeap Cudd_ReduceHeap\n\n*/\nint\ncuddZddAlignToBdd(\n  DdManager * table /**< %DD manager */)\n{\n    int *invpermZ;\t\t/* permutation array */\n    int M;\t\t\t/* ratio of ZDD variables to BDD variables */\n    int i,j;\t\t\t/* loop indices */\n    int result;\t\t\t/* return value */\n\n    /* We assume that a ratio of 0 is OK. */\n    if (table->sizeZ == 0)\n\treturn(1);\n\n    M = table->sizeZ / table->size;\n    /* Check whether the number of ZDD variables is a multiple of the\n    ** number of BDD variables.\n    */\n    if (M * table->size != table->sizeZ)\n\treturn(0);\n    /* Create and initialize the inverse permutation array. */\n    invpermZ = ALLOC(int,table->sizeZ);\n    if (invpermZ == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (i = 0; i < table->size; i++) {\n\tint index = table->invperm[i];\n\tint indexZ = index * M;\n\tint levelZ = table->permZ[indexZ];\n\tlevelZ = (levelZ / M) * M;\n\tfor (j = 0; j < M; j++) {\n\t    invpermZ[M * i + j] = table->invpermZ[levelZ + j];\n\t}\n    }\n    /* Eliminate dead nodes. Do not scan the cache again, because we\n    ** assume that Cudd_ReduceHeap has already cleared it.\n    */\n    cuddGarbageCollect(table,0);\n\n    result = zddShuffle(table, invpermZ);\n    FREE(invpermZ);\n    /* Fix the ZDD variable group tree. */\n    zddFixTree(table,table->treeZ);\n    return(result);\n    \n} /* end of cuddZddAlignToBdd */\n\n\n/**\n  @brief Finds the next subtable with a larger index.\n\n  @return the index.\n\n  @sideeffect None\n\n*/\nint\ncuddZddNextHigh(\n  DdManager * table,\n  int  x)\n{\n    (void) table; /* avoid warning */\n    return(x + 1);\n\n} /* end of cuddZddNextHigh */\n\n\n/**\n  @brief Finds the next subtable with a smaller index.\n\n  @return the index.\n\n  @sideeffect None\n\n*/\nint\ncuddZddNextLow(\n  DdManager * table,\n  int  x)\n{\n    (void) table; /* avoid warning */\n    return(x - 1);\n\n} /* end of cuddZddNextLow */\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Comparison function used by qsort to order the variables\n  according to the number of keys in the subtables.\n\n  @return the difference in number of keys between the two variables\n  being compared.\n\n  @sideeffect None\n\n*/\nint\ncuddZddUniqueCompare(\n  void const * ptr_x,\n  void const * ptr_y)\n{\n    IndexKey const * pX = (IndexKey const *) ptr_x;\n    IndexKey const * pY = (IndexKey const *) ptr_y;\n    return(pY->keys - pX->keys);\n\n} /* end of cuddZddUniqueCompare */\n\n\n/**\n  @brief Swaps two adjacent variables.\n\n  @details It assumes that no dead nodes are present on entry to this\n  procedure.  The procedure then guarantees that no dead nodes will be\n  present when it terminates.  cuddZddSwapInPlace assumes that x &lt; y.\n\n  @return the number of keys in the table if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddZddSwapInPlace(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    DdNodePtr\t*xlist, *ylist;\n    int\t\txindex, yindex;\n    int\t\txslots, yslots;\n    int\t\txshift, yshift;\n    int         oldxkeys, oldykeys;\n    int         newxkeys, newykeys;\n    int\t\ti;\n    int\t\tposn;\n    DdNode\t*f, *f1, *f0, *f11, *f10, *f01, *f00;\n    DdNode\t*newf1 = NULL, *newf0 = NULL, *next;\n    DdNodePtr\tg, *lastP, *previousP;\n    DdNode\t*empty = table->zero;\n\n#ifdef DD_DEBUG\n    assert(x < y);\n    assert(cuddZddNextHigh(table,x) == y);\n    assert(table->subtableZ[x].keys != 0);\n    assert(table->subtableZ[y].keys != 0);\n    assert(table->subtableZ[x].dead == 0);\n    assert(table->subtableZ[y].dead == 0);\n#endif\n\n    table->zddTotalNumberSwapping++;\n\n    /* Get parameters of x subtable. */\n    xindex   = table->invpermZ[x];\n    xlist    = table->subtableZ[x].nodelist;\n    oldxkeys = table->subtableZ[x].keys;\n    xslots   = table->subtableZ[x].slots;\n    xshift   = table->subtableZ[x].shift;\n    newxkeys = 0;\n\n    yindex   = table->invpermZ[y];\n    ylist    = table->subtableZ[y].nodelist;\n    oldykeys = table->subtableZ[y].keys;\n    yslots   = table->subtableZ[y].slots;\n    yshift   = table->subtableZ[y].shift;\n    newykeys = oldykeys;\n\n    /* The nodes in the x layer that don't depend on y directly\n    ** will stay there; the others are put in a chain.\n    ** The chain is handled as a FIFO; g points to the beginning and\n    ** last points to the end.\n    */\n\n    g = NULL;\n    lastP = &g;\n    for (i = 0; i < xslots; i++) {\n\tpreviousP = &(xlist[i]);\n\tf = *previousP;\n\twhile (f != NULL) {\n\t    next = f->next;\n\t    f1 = cuddT(f); f0 = cuddE(f);\n\t    if ((f1->index != (DdHalfWord) yindex) &&\n\t\t(f0->index != (DdHalfWord) yindex)) { /* stays */\n\t        newxkeys++;\n\t\t*previousP = f;\n\t\tpreviousP = &(f->next);\n\t    } else {\n\t\tf->index = yindex;\n\t\t*lastP = f;\n\t\tlastP = &(f->next);\n\t    }\n\t    f = next;\n\t} /* while there are elements in the collision chain */\n\t*previousP = NULL;\n    } /* for each slot of the x subtable */\n    *lastP = NULL;\n\n\n#ifdef DD_COUNT\n    table->swapSteps += oldxkeys - newxkeys;\n#endif\n    /* Take care of the x nodes that must be re-expressed.\n    ** They form a linked list pointed by g. Their index has been\n    ** changed to yindex already.\n    */\n    f = g;\n    while (f != NULL) {\n\tnext = f->next;\n\t/* Find f1, f0, f11, f10, f01, f00. */\n\tf1 = cuddT(f);\n\tif ((int) f1->index == yindex) {\n\t    f11 = cuddT(f1); f10 = cuddE(f1);\n\t} else {\n\t    f11 = empty; f10 = f1;\n\t}\n\tf0 = cuddE(f);\n\tif ((int) f0->index == yindex) {\n\t    f01 = cuddT(f0); f00 = cuddE(f0);\n\t} else {\n\t    f01 = empty; f00 = f0;\n\t}\n\n\t/* Decrease ref count of f1. */\n\tcuddSatDec(f1->ref);\n\t/* Create the new T child. */\n\tif (f11 == empty) {\n\t    if (f01 != empty) {\n\t\tnewf1 = f01;\n\t\tcuddSatInc(newf1->ref);\n\t    }\n\t    /* else case was already handled when finding nodes\n\t    ** with both children below level y\n\t    */\n\t} else {\n\t    /* Check xlist for triple (xindex, f11, f01). */\n\t    posn = ddHash(f11, f01, xshift);\n\t    /* For each element newf1 in collision list xlist[posn]. */\n\t    newf1 = xlist[posn];\n\t    while (newf1 != NULL) {\n\t\tif (cuddT(newf1) == f11 && cuddE(newf1) == f01) {\n\t\t    cuddSatInc(newf1->ref);\n\t\t    break; /* match */\n\t\t}\n\t\tnewf1 = newf1->next;\n\t    } /* while newf1 */\n\t    if (newf1 == NULL) {\t/* no match */\n\t\tnewf1 = cuddDynamicAllocNode(table);\n\t\tif (newf1 == NULL)\n\t\t    goto zddSwapOutOfMem;\n\t\tnewf1->index = xindex; newf1->ref = 1;\n\t\tcuddT(newf1) = f11;\n\t\tcuddE(newf1) = f01;\n\t\t/* Insert newf1 in the collision list xlist[pos];\n\t\t** increase the ref counts of f11 and f01\n\t\t*/\n\t\tnewxkeys++;\n\t\tnewf1->next = xlist[posn];\n\t\txlist[posn] = newf1;\n\t\tcuddSatInc(f11->ref);\n\t\tcuddSatInc(f01->ref);\n\t    }\n\t}\n\tcuddT(f) = newf1;\n\n\t/* Do the same for f0. */\n\t/* Decrease ref count of f0. */\n\tcuddSatDec(f0->ref);\n\t/* Create the new E child. */\n\tif (f10 == empty) {\n\t    newf0 = f00;\n\t    cuddSatInc(newf0->ref);\n\t} else {\n\t    /* Check xlist for triple (xindex, f10, f00). */\n\t    posn = ddHash(f10, f00, xshift);\n\t    /* For each element newf0 in collision list xlist[posn]. */\n\t    newf0 = xlist[posn];\n\t    while (newf0 != NULL) {\n\t\tif (cuddT(newf0) == f10 && cuddE(newf0) == f00) {\n\t\t    cuddSatInc(newf0->ref);\n\t\t    break; /* match */\n\t\t}\n\t\tnewf0 = newf0->next;\n\t    } /* while newf0 */\n\t    if (newf0 == NULL) {\t/* no match */\n\t\tnewf0 = cuddDynamicAllocNode(table);\n\t\tif (newf0 == NULL)\n\t\t    goto zddSwapOutOfMem;\n\t\tnewf0->index = xindex; newf0->ref = 1;\n\t\tcuddT(newf0) = f10; cuddE(newf0) = f00;\n\t\t/* Insert newf0 in the collision list xlist[posn];\n\t\t** increase the ref counts of f10 and f00.\n\t\t*/\n\t\tnewxkeys++;\n\t\tnewf0->next = xlist[posn];\n\t\txlist[posn] = newf0;\n\t\tcuddSatInc(f10->ref);\n\t\tcuddSatInc(f00->ref);\n\t    }\n\t}\n\tcuddE(f) = newf0;\n\n\t/* Insert the modified f in ylist.\n\t** The modified f does not already exists in ylist.\n\t** (Because of the uniqueness of the cofactors.)\n\t*/\n\tposn = ddHash(newf1, newf0, yshift);\n\tnewykeys++;\n\tf->next = ylist[posn];\n\tylist[posn] = f;\n\tf = next;\n    } /* while f != NULL */\n\n    /* GC the y layer. */\n\n    /* For each node f in ylist. */\n    for (i = 0; i < yslots; i++) {\n\tpreviousP = &(ylist[i]);\n\tf = *previousP;\n\twhile (f != NULL) {\n\t    next = f->next;\n\t    if (f->ref == 0) {\n\t\tcuddSatDec(cuddT(f)->ref);\n\t\tcuddSatDec(cuddE(f)->ref);\n\t\tcuddDeallocNode(table, f);\n\t\tnewykeys--;\n\t    } else {\n\t\t*previousP = f;\n\t\tpreviousP = &(f->next);\n\t    }\n\t    f = next;\n\t} /* while f */\n\t*previousP = NULL;\n    } /* for i */\n\n    /* Set the appropriate fields in table. */\n    table->subtableZ[x].nodelist = ylist;\n    table->subtableZ[x].slots    = yslots;\n    table->subtableZ[x].shift    = yshift;\n    table->subtableZ[x].keys     = newykeys;\n    table->subtableZ[x].maxKeys  = yslots * DD_MAX_SUBTABLE_DENSITY;\n\n    table->subtableZ[y].nodelist = xlist;\n    table->subtableZ[y].slots    = xslots;\n    table->subtableZ[y].shift    = xshift;\n    table->subtableZ[y].keys     = newxkeys;\n    table->subtableZ[y].maxKeys  = xslots * DD_MAX_SUBTABLE_DENSITY;\n\n    table->permZ[xindex] = y; table->permZ[yindex] = x;\n    table->invpermZ[x] = yindex; table->invpermZ[y] = xindex;\n\n    table->keysZ += newxkeys + newykeys - oldxkeys - oldykeys;\n\n    /* Update univ section; univ[x] remains the same. */\n    table->univ[y] = cuddT(table->univ[x]);\n\n    return (table->keysZ);\n\nzddSwapOutOfMem:\n    (void) fprintf(table->err, \"Error: cuddZddSwapInPlace out of memory\\n\");\n\n    return (0);\n\n} /* end of cuddZddSwapInPlace */\n\n\n/**\n  @brief Reorders variables by a sequence of (non-adjacent) swaps.\n\n  @details Implementation of Plessier's algorithm that reorders\n  variables by a sequence of (non-adjacent) swaps.\n    <ol>\n    <li> Select two variables (RANDOM or HEURISTIC).\n    <li> Permute these variables.\n    <li> If the nodes have decreased accept the permutation.\n    <li> Otherwise reconstruct the original heap.\n    <li> Loop.\n    </ol>\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddZddSwapping(\n  DdManager * table,\n  int lower,\n  int upper,\n  Cudd_ReorderingType heuristic)\n{\n    int\ti, j;\n    int max, keys;\n    int nvars;\n    int\tx, y;\n    int iterate;\n    int previousSize;\n    Move *moves, *move;\n    int\tpivot = 0;\n    int modulo;\n    int result;\n\n#ifdef DD_DEBUG\n    /* Sanity check */\n    assert(lower >= 0 && upper < table->sizeZ && lower <= upper);\n#endif\n\n    nvars = upper - lower + 1;\n    iterate = nvars;\n\n    for (i = 0; i < iterate; i++) {\n\tif (heuristic == CUDD_REORDER_RANDOM_PIVOT) {\n\t    /* Find pivot <= id with maximum keys. */\n\t    for (max = -1, j = lower; j <= upper; j++) {\n\t\tif ((keys = table->subtableZ[j].keys) > max) {\n\t\t    max = keys;\n\t\t    pivot = j;\n\t\t}\n\t    }\n\n\t    modulo = upper - pivot;\n\t    if (modulo == 0) {\n\t\ty = pivot;\t/* y = nvars-1 */\n\t    } else {\n\t\t/* y = random # from {pivot+1 .. nvars-1} */\n\t\ty = pivot + 1 + (int) (Cudd_Random(table) % modulo);\n\t    }\n\n\t    modulo = pivot - lower - 1;\n\t    if (modulo < 1) {\t/* if pivot = 1 or 0 */\n\t\tx = lower;\n\t    } else {\n\t\tdo { /* x = random # from {0 .. pivot-2} */\n\t\t    x = (int) Cudd_Random(table) % modulo;\n\t\t} while (x == y);\n\t\t  /* Is this condition really needed, since x and y\n\t\t     are in regions separated by pivot? */\n\t    }\n\t} else {\n\t    x = (int) (Cudd_Random(table) % nvars) + lower;\n\t    do {\n\t\ty = (int) (Cudd_Random(table) % nvars) + lower;\n\t    } while (x == y);\n\t}\n\n\tpreviousSize = table->keysZ;\n\tmoves = zddSwapAny(table, x, y);\n\tif (moves == NULL)\n\t    goto cuddZddSwappingOutOfMem;\n\n\tresult = cuddZddSiftingBackward(table, moves, previousSize);\n\tif (!result)\n\t    goto cuddZddSwappingOutOfMem;\n\n\twhile (moves != NULL) {\n\t    move = moves->next;\n\t    cuddDeallocMove(table, moves);\n\t    moves = move;\n\t}\n#ifdef DD_STATS\n\tif (table->keysZ < (unsigned) previousSize) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keysZ > (unsigned) previousSize) {\n\t    (void) fprintf(table->out,\"+\");\t/* should never happen */\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n    return(1);\n\ncuddZddSwappingOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(0);\n\n} /* end of cuddZddSwapping */\n\n\n/**\n  @brief Implementation of Rudell's sifting algorithm.\n\n  @details Assumes that no dead nodes are present.\n    <ol>\n    <li> Order all the variables according to the number of entries\n    in each unique table.\n    <li> Sift the variable up and down, remembering each time the\n    total size of the %DD heap.\n    <li> Select the best permutation.\n    <li> Repeat 3 and 4 for all variables.\n    </ol>\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddZddSifting(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\ti;\n    IndexKey *var;\n    int\tsize;\n    int\tx;\n    int\tresult;\n#ifdef DD_STATS\n    int\tpreviousSize;\n#endif\n\n    size = table->sizeZ;\n\n    /* Find order in which to sift variables. */\n    var = ALLOC(IndexKey, size);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto cuddZddSiftingOutOfMem;\n    }\n\n    for (i = 0; i < size; i++) {\n\tx = table->permZ[i];\n\tvar[i].index = i;\n\tvar[i].keys = table->subtableZ[x].keys;\n    }\n\n    util_qsort(var, size, sizeof(IndexKey), cuddZddUniqueCompare);\n\n    /* Now sift. */\n    for (i = 0; i < ddMin(table->siftMaxVar, size); i++) {\n\tif (table->zddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime > table->timeLimit) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n\tx = table->permZ[var[i].index];\n\tif (x < lower || x > upper) continue;\n#ifdef DD_STATS\n\tpreviousSize = table->keysZ;\n#endif\n\tresult = cuddZddSiftingAux(table, x, lower, upper);\n\tif (!result)\n\t    goto cuddZddSiftingOutOfMem;\n#ifdef DD_STATS\n\tif (table->keysZ < (unsigned) previousSize) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keysZ > (unsigned) previousSize) {\n\t    (void) fprintf(table->out,\"+\");\t/* should never happen */\n\t    (void) fprintf(table->out,\"\\nSize increased from %d to %d while sifting variable %d\\n\", previousSize, table->keysZ , var[i].index);\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n    FREE(var);\n\n    return(1);\n\ncuddZddSiftingOutOfMem:\n\n    if (var != NULL) FREE(var);\n\n    return(0);\n\n} /* end of cuddZddSifting */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Swaps any two variables.\n\n  @return the set of moves.\n\n  @sideeffect None\n\n*/\nstatic Move *\nzddSwapAny(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    Move\t*move, *moves;\n    int\t\ttmp, size;\n    int\t\tx_ref, y_ref;\n    int\t\tx_next, y_next;\n    int\t\tlimit_size;\n\n    if (x > y) {\t/* make x precede y */\n\ttmp = x; x = y;\ty = tmp;\n    }\n\n    x_ref = x; y_ref = y;\n\n    x_next = cuddZddNextHigh(table, x);\n    y_next = cuddZddNextLow(table, y);\n    moves = NULL;\n    limit_size = table->keysZ;\n\n    for (;;) {\n\tif (x_next == y_next) {\t/* x < x_next = y_next < y */\n\t    size = cuddZddSwapInPlace(table, x, x_next);\n\t    if (size == 0)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move = (Move *) cuddDynamicAllocNode(table);\n\t    if (move == NULL)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move->x = x;\n\t    move->y = x_next;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    size = cuddZddSwapInPlace(table, y_next, y);\n\t    if (size == 0)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move->x = y_next;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    size = cuddZddSwapInPlace(table, x, x_next);\n\t    if (size == 0)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move->x = x;\n\t    move->y = x_next;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    tmp = x; x = y; y = tmp;\n\n\t} else if (x == y_next) { /* x = y_next < y = x_next */\n\t    size = cuddZddSwapInPlace(table, x, x_next);\n\t    if (size == 0)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move->x = x;\n\t    move->y = x_next;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    tmp = x; x = y;  y = tmp;\n\t} else {\n\t    size = cuddZddSwapInPlace(table, x, x_next);\n\t    if (size == 0)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move->x = x;\n\t    move->y = x_next;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    size = cuddZddSwapInPlace(table, y_next, y);\n\t    if (size == 0)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL)\n\t\tgoto zddSwapAnyOutOfMem;\n\t    move->x = y_next;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\n\t    x = x_next; y = y_next;\n\t}\n\n\tx_next = cuddZddNextHigh(table, x);\n\ty_next = cuddZddNextLow(table, y);\n\tif (x_next > y_ref)\n\t    break;\t/* if x == y_ref */\n\n\tif ((double) size > table->maxGrowth * (double) limit_size)\n\t    break;\n\tif (size < limit_size)\n\t    limit_size = size;\n    }\n    if (y_next >= x_ref) {\n\tsize = cuddZddSwapInPlace(table, y_next, y);\n\tif (size == 0)\n\t    goto zddSwapAnyOutOfMem;\n\tmove = (Move *)cuddDynamicAllocNode(table);\n\tif (move == NULL)\n\t    goto zddSwapAnyOutOfMem;\n\tmove->x = y_next;\n\tmove->y = y;\n\tmove->size = size;\n\tmove->next = moves;\n\tmoves = move;\n    }\n\n    return(moves);\n\nzddSwapAnyOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(NULL);\n\n} /* end of zddSwapAny */\n\n\n/**\n  @brief Given xLow <= x <= xHigh moves x up and down between the\n  boundaries.\n\n  @details Finds the best position and does the required changes.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddSiftingAux(\n  DdManager * table,\n  int  x,\n  int  x_low,\n  int  x_high)\n{\n    Move\t*move;\n    Move\t*moveUp;\t/* list of up move */\n    Move\t*moveDown;\t/* list of down move */\n\n    int\t\tinitial_size;\n    int\t\tresult;\n\n    initial_size = table->keysZ;\n\n#ifdef DD_DEBUG\n    assert(table->subtableZ[x].keys > 0);\n#endif\n\n    moveDown = NULL;\n    moveUp = NULL;\n\n    if (x == x_low) {\n\tmoveDown = cuddZddSiftingDown(table, x, x_high, initial_size);\n\t/* after that point x --> x_high */\n\tif (moveDown == NULL)\n\t    goto cuddZddSiftingAuxOutOfMem;\n\tresult = cuddZddSiftingBackward(table, moveDown,\n\t    initial_size);\n\t/* move backward and stop at best position */\n\tif (!result)\n\t    goto cuddZddSiftingAuxOutOfMem;\n\n    }\n    else if (x == x_high) {\n\tmoveUp = cuddZddSiftingUp(table, x, x_low, initial_size);\n\t/* after that point x --> x_low */\n\tif (moveUp == NULL)\n\t    goto cuddZddSiftingAuxOutOfMem;\n\tresult = cuddZddSiftingBackward(table, moveUp, initial_size);\n\t/* move backward and stop at best position */\n\tif (!result)\n\t    goto cuddZddSiftingAuxOutOfMem;\n    }\n    else if ((x - x_low) > (x_high - x)) {\n\t/* must go down first:shorter */\n\tmoveDown = cuddZddSiftingDown(table, x, x_high, initial_size);\n\t/* after that point x --> x_high */\n\tif (moveDown == NULL)\n\t    goto cuddZddSiftingAuxOutOfMem;\n\tmoveUp = cuddZddSiftingUp(table, moveDown->y, x_low,\n\t    initial_size);\n\tif (moveUp == NULL)\n\t    goto cuddZddSiftingAuxOutOfMem;\n\tresult = cuddZddSiftingBackward(table, moveUp, initial_size);\n\t/* move backward and stop at best position */\n\tif (!result)\n\t    goto cuddZddSiftingAuxOutOfMem;\n    }\n    else {\n\tmoveUp = cuddZddSiftingUp(table, x, x_low, initial_size);\n\t/* after that point x --> x_high */\n\tif (moveUp == NULL)\n\t    goto cuddZddSiftingAuxOutOfMem;\n\tmoveDown = cuddZddSiftingDown(table, moveUp->x, x_high,\n\t    initial_size);\n\t/* then move up */\n\tif (moveDown == NULL)\n\t    goto cuddZddSiftingAuxOutOfMem;\n\tresult = cuddZddSiftingBackward(table, moveDown,\n\t    initial_size);\n\t/* move backward and stop at best position */\n\tif (!result)\n\t    goto cuddZddSiftingAuxOutOfMem;\n    }\n\n    while (moveDown != NULL) {\n\tmove = moveDown->next;\n\tcuddDeallocMove(table, moveDown);\n\tmoveDown = move;\n    }\n    while (moveUp != NULL) {\n\tmove = moveUp->next;\n\tcuddDeallocMove(table, moveUp);\n\tmoveUp = move;\n    }\n\n    return(1);\n\ncuddZddSiftingAuxOutOfMem:\n    while (moveDown != NULL) {\n\tmove = moveDown->next;\n\tcuddDeallocMove(table, moveDown);\n\tmoveDown = move;\n    }\n    while (moveUp != NULL) {\n\tmove = moveUp->next;\n\tcuddDeallocMove(table, moveUp);\n\tmoveUp = move;\n    }\n\n    return(0);\n\n} /* end of cuddZddSiftingAux */\n\n\n/**\n  @brief Sifts a variable up.\n\n  @details Moves y up until either it reaches the bound (x_low) or the\n  size of the %ZDD heap increases too much.\n\n  @return the set of moves in case of success; NULL if memory is full.\n\n  @sideeffect None\n\n*/\nstatic Move *\ncuddZddSiftingUp(\n  DdManager * table,\n  int  x,\n  int  x_low,\n  int  initial_size)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\ty;\n    int\t\tsize;\n    int\t\tlimit_size = initial_size;\n\n    moves = NULL;\n    y = cuddZddNextLow(table, x);\n    while (y >= x_low) {\n\tsize = cuddZddSwapInPlace(table, y, x);\n\tif (size == 0)\n\t    goto cuddZddSiftingUpOutOfMem;\n\tmove = (Move *)cuddDynamicAllocNode(table);\n\tif (move == NULL)\n\t    goto cuddZddSiftingUpOutOfMem;\n\tmove->x = y;\n\tmove->y = x;\n\tmove->size = size;\n\tmove->next = moves;\n\tmoves = move;\n\n\tif ((double)size > (double)limit_size * table->maxGrowth)\n\t    break;\n        if (size < limit_size)\n\t    limit_size = size;\n\n\tx = y;\n\ty = cuddZddNextLow(table, x);\n    }\n    return(moves);\n\ncuddZddSiftingUpOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(NULL);\n\n} /* end of cuddZddSiftingUp */\n\n\n/**\n  @brief Sifts a variable down.\n\n  @details Moves x down until either it reaches the bound (x_high) or\n  the size of the %ZDD heap increases too much.\n\n  @return the set of moves in case of success; NULL if memory is\n  full.\n\n  @sideeffect None\n\n*/\nstatic Move *\ncuddZddSiftingDown(\n  DdManager * table,\n  int  x,\n  int  x_high,\n  int  initial_size)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\ty;\n    int\t\tsize;\n    int\t\tlimit_size = initial_size;\n\n    moves = NULL;\n    y = cuddZddNextHigh(table, x);\n    while (y <= x_high) {\n\tsize = cuddZddSwapInPlace(table, x, y);\n\tif (size == 0)\n\t    goto cuddZddSiftingDownOutOfMem;\n\tmove = (Move *)cuddDynamicAllocNode(table);\n\tif (move == NULL)\n\t    goto cuddZddSiftingDownOutOfMem;\n\tmove->x = x;\n\tmove->y = y;\n\tmove->size = size;\n\tmove->next = moves;\n\tmoves = move;\n\n\tif ((double)size > (double)limit_size * table->maxGrowth)\n\t    break;\n        if (size < limit_size)\n\t    limit_size = size;\n\n\tx = y;\n\ty = cuddZddNextHigh(table, x);\n    }\n    return(moves);\n\ncuddZddSiftingDownOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(NULL);\n\n} /* end of cuddZddSiftingDown */\n\n\n/**\n  @brief Given a set of moves, returns the %ZDD heap to the position\n  giving the minimum size.\n\n  @details In case of ties, returns to the closest position giving the\n  minimum size.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddSiftingBackward(\n  DdManager * table,\n  Move * moves,\n  int  size)\n{\n    int\t    \ti;\n    int\t\ti_best;\n    Move\t*move;\n    int\t\tres;\n\n    /* Find the minimum size among moves. */\n    i_best = -1;\n    for (move = moves, i = 0; move != NULL; move = move->next, i++) {\n\tif (move->size < size) {\n\t    i_best = i;\n\t    size = move->size;\n\t}\n    }\n\n    for (move = moves, i = 0; move != NULL; move = move->next, i++) {\n\tif (i == i_best)\n\t    break;\n\tres = cuddZddSwapInPlace(table, move->x, move->y);\n\tif (!res)\n\t    return(0);\n\tif (i_best == -1 && res == size)\n\t    break;\n    }\n\n    return(1);\n\n} /* end of cuddZddSiftingBackward */\n\n\n/**\n  @brief Prepares the %ZDD heap for dynamic reordering.\n\n  @details Does garbage collection, to guarantee that there are no\n  dead nodes; and clears the cache, which is invalidated by dynamic\n  reordering.\n\n  @sideeffect None\n\n*/\nstatic void\nzddReorderPreprocess(\n  DdManager * table)\n{\n\n    /* Clear the cache. */\n    cuddCacheFlush(table);\n\n    /* Eliminate dead nodes. Do not scan the cache again. */\n    cuddGarbageCollect(table,0);\n\n    return;\n\n} /* end of ddReorderPreprocess */\n\n\n/**\n  @brief Shrinks almost empty %ZDD subtables at the end of reordering\n  to guarantee that they have a reasonable load factor.\n\n  @details However, if there many nodes are being reclaimed, then no\n  resizing occurs.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddReorderPostprocess(\n  DdManager * table)\n{\n    int i, j, posn;\n    DdNodePtr *nodelist, *oldnodelist;\n    DdNode *node, *next;\n    unsigned int slots, oldslots;\n    extern DD_OOMFP MMoutOfMemory;\n    DD_OOMFP saveHandler;\n\n#ifdef DD_VERBOSE\n    (void) fflush(table->out);\n#endif\n\n    /* If we have very many reclaimed nodes, we do not want to shrink\n    ** the subtables, because this will lead to more garbage\n    ** collections. More garbage collections mean shorter mean life for\n    ** nodes with zero reference count; hence lower probability of finding\n    ** a result in the cache.\n    */\n    if (table->reclaimed > table->allocated * 0.5) return(1);\n\n    /* Resize subtables. */\n    for (i = 0; i < table->sizeZ; i++) {\n\tint shift;\n\toldslots = table->subtableZ[i].slots;\n\tif (oldslots < table->subtableZ[i].keys * DD_MAX_SUBTABLE_SPARSITY ||\n\t    oldslots <= table->initSlots) continue;\n\toldnodelist = table->subtableZ[i].nodelist;\n\tslots = oldslots >> 1;\n\tsaveHandler = MMoutOfMemory;\n\tMMoutOfMemory = table->outOfMemCallback;\n\tnodelist = ALLOC(DdNodePtr, slots);\n\tMMoutOfMemory = saveHandler;\n\tif (nodelist == NULL) {\n\t    return(1);\n\t}\n\ttable->subtableZ[i].nodelist = nodelist;\n\ttable->subtableZ[i].slots = slots;\n\ttable->subtableZ[i].shift++;\n\ttable->subtableZ[i].maxKeys = slots * DD_MAX_SUBTABLE_DENSITY;\n#ifdef DD_VERBOSE\n\t(void) fprintf(table->err,\n\t\t       \"shrunk layer %d (%d keys) from %d to %d slots\\n\",\n\t\t       i, table->subtableZ[i].keys, oldslots, slots);\n#endif\n\n\tfor (j = 0; (unsigned) j < slots; j++) {\n\t    nodelist[j] = NULL;\n\t}\n\tshift = table->subtableZ[i].shift;\n\tfor (j = 0; (unsigned) j < oldslots; j++) {\n\t    node = oldnodelist[j];\n\t    while (node != NULL) {\n\t\tnext = node->next;\n\t\tposn = ddHash(cuddT(node), cuddE(node), shift);\n\t\tnode->next = nodelist[posn];\n\t\tnodelist[posn] = node;\n\t\tnode = next;\n\t    }\n\t}\n\tFREE(oldnodelist);\n\n\ttable->memused += (slots - oldslots) * sizeof(DdNode *);\n\ttable->slots += slots - oldslots;\n\ttable->minDead = (unsigned) (table->gcFrac * (double) table->slots);\n\ttable->cacheSlack = (int) ddMin(table->maxCacheHard,\n\t    DD_MAX_CACHE_TO_SLOTS_RATIO*table->slots) -\n\t    2 * (int) table->cacheSlots;\n    }\n    /* We don't look at the constant subtable, because it is not\n    ** affected by reordering.\n    */\n\n    return(1);\n\n} /* end of zddReorderPostprocess */\n\n\n/**\n  @brief Reorders %ZDD variables according to a given permutation.\n\n  @details The i-th permutation array contains the index of the\n  variable that should be brought to the i-th level. zddShuffle\n  assumes that no dead nodes are present.  The reordering is achieved\n  by a series of upward sifts.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzddShuffle(\n  DdManager * table,\n  int * permutation)\n{\n    int\t\tindex;\n    int\t\tlevel;\n    int\t\tposition;\n    int\t\tnumvars;\n    int\t\tresult;\n#ifdef DD_STATS\n    unsigned long localTime;\n    int\t\tinitialSize;\n    int\t\tfinalSize;\n    int\t\tpreviousSize;\n#endif\n\n    table->zddTotalNumberSwapping = 0;\n#ifdef DD_STATS\n    localTime = util_cpu_time();\n    initialSize = table->keysZ;\n    (void) fprintf(table->out,\"#:I_SHUFFLE %8d: initial size\\n\",\n\t\t   initialSize); \n#endif\n\n    numvars = table->sizeZ;\n\n    for (level = 0; level < numvars; level++) {\n\tindex = permutation[level];\n\tposition = table->permZ[index];\n#ifdef DD_STATS\n\tpreviousSize = table->keysZ;\n#endif\n\tresult = zddSiftUp(table,position,level);\n\tif (!result) return(0);\n#ifdef DD_STATS\n\tif (table->keysZ < (unsigned) previousSize) {\n\t    (void) fprintf(table->out,\"-\");\n\t} else if (table->keysZ > (unsigned) previousSize) {\n\t    (void) fprintf(table->out,\"+\");\t/* should never happen */\n\t} else {\n\t    (void) fprintf(table->out,\"=\");\n\t}\n\tfflush(table->out);\n#endif\n    }\n\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n\");\n    finalSize = table->keysZ;\n    (void) fprintf(table->out,\"#:F_SHUFFLE %8d: final size\\n\",finalSize); \n    (void) fprintf(table->out,\"#:T_SHUFFLE %8g: total time (sec)\\n\",\n\t((double)(util_cpu_time() - localTime)/1000.0)); \n    (void) fprintf(table->out,\"#:N_SHUFFLE %8d: total swaps\\n\",\n\t\t   table->zddTotalNumberSwapping);\n#endif\n\n    return(1);\n\n} /* end of zddShuffle */\n\n\n/**\n  @brief Moves one %ZDD variable up.\n\n  @details Takes a %ZDD variable from position x and sifts it up to\n  position xLow;  xLow should be less than or equal to x.\n\n  @return 1 if successful; 0 otherwise\n\n  @sideeffect None\n\n*/\nstatic int\nzddSiftUp(\n  DdManager * table,\n  int  x,\n  int  xLow)\n{\n    int        y;\n    int        size;\n\n    y = cuddZddNextLow(table,x);\n    while (y >= xLow) {\n\tsize = cuddZddSwapInPlace(table,y,x);\n\tif (size == 0) {\n\t    return(0);\n\t}\n\tx = y;\n\ty = cuddZddNextLow(table,x);\n    }\n    return(1);\n\n} /* end of zddSiftUp */\n\n\n/**\n  @brief Fixes the %ZDD variable group tree after a shuffle.\n\n  @details Assumes that the order of the variables in a terminal node\n  has not been changed.\n\n  @sideeffect Changes the %ZDD variable group tree.\n\n*/\nstatic void\nzddFixTree(\n  DdManager * table,\n  MtrNode * treenode)\n{\n    if (treenode == NULL) return;\n    treenode->low = ((int) treenode->index < table->sizeZ) ?\n\t(MtrHalfWord) table->permZ[treenode->index] : treenode->index;\n    if (treenode->child != NULL) {\n\tzddFixTree(table, treenode->child);\n    }\n    if (treenode->younger != NULL)\n\tzddFixTree(table, treenode->younger);\n    if (treenode->parent != NULL && treenode->low < treenode->parent->low) {\n\ttreenode->parent->low = treenode->low;\n\ttreenode->parent->index = treenode->index;\n    }\n    return;\n\n} /* end of zddFixTree */\n\n"
  },
  {
    "path": "cudd/cudd/cuddZddSetop.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Set operations on ZDDs.\n\n  @author Hyong-Kyoon Shin, In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * zdd_subset1_aux (DdManager *zdd, DdNode *P, DdNode *zvar);\nstatic DdNode * zdd_subset0_aux (DdManager *zdd, DdNode *P, DdNode *zvar);\nstatic void zddVarToConst (DdNode *f, DdNode **gp, DdNode **hp, DdNode *base, DdNode *empty);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Computes the ITE of three ZDDs.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_zddIte(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddIte(dd, f, g, h);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddIte */\n\n\n/**\n  @brief Computes the union of two ZDDs.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_zddUnion(\n  DdManager * dd,\n  DdNode * P,\n  DdNode * Q)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddUnion(dd, P, Q);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddUnion */\n\n\n/**\n  @brief Computes the intersection of two ZDDs.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_zddIntersect(\n  DdManager * dd,\n  DdNode * P,\n  DdNode * Q)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddIntersect(dd, P, Q);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddIntersect */\n\n\n/**\n  @brief Computes the difference of two ZDDs.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_zddDiff(\n  DdManager * dd,\n  DdNode * P,\n  DdNode * Q)\n{\n    DdNode *res;\n\n    do {\n\tdd->reordered = 0;\n\tres = cuddZddDiff(dd, P, Q);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddDiff */\n\n\n/**\n  @brief Performs the inclusion test for ZDDs (P implies Q).\n\n  @details No new nodes are generated by this procedure.\n\n  @return empty if true; a valid pointer different from empty or\n  DD_NON_CONSTANT otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddDiff\n\n*/\nDdNode *\nCudd_zddDiffConst(\n  DdManager * zdd,\n  DdNode * P,\n  DdNode * Q)\n{\n    int\t\tp_top, q_top;\n    DdNode\t*empty = DD_ZERO(zdd), *t, *res;\n    DdManager\t*table = zdd;\n\n    statLine(zdd);\n    if (P == empty)\n\treturn(empty);\n    if (Q == empty)\n\treturn(P);\n    if (P == Q)\n\treturn(empty);\n\n    /* Check cache.  The cache is shared by cuddZddDiff(). */\n    res = cuddCacheLookup2Zdd(table, cuddZddDiff, P, Q);\n    if (res != NULL)\n\treturn(res);\n\n    if (cuddIsConstant(P))\n\tp_top = P->index;\n    else\n\tp_top = zdd->permZ[P->index];\n    if (cuddIsConstant(Q))\n\tq_top = Q->index;\n    else\n\tq_top = zdd->permZ[Q->index];\n    if (p_top < q_top) {\n\tres = DD_NON_CONSTANT;\n    } else if (p_top > q_top) {\n\tres = Cudd_zddDiffConst(zdd, P, cuddE(Q));\n    } else {\n\tt = Cudd_zddDiffConst(zdd, cuddT(P), cuddT(Q));\n\tif (t != empty)\n\t    res = DD_NON_CONSTANT;\n\telse\n\t    res = Cudd_zddDiffConst(zdd, cuddE(P), cuddE(Q));\n    }\n\n    cuddCacheInsert2(table, cuddZddDiff, P, Q, res);\n\n    return(res);\n\n} /* end of Cudd_zddDiffConst */\n\n\n/**\n  @brief Computes the positive cofactor of a %ZDD w.r.t. a variable.\n\n  @details In terms of combinations, the result is the set of all\n  combinations in which the variable is asserted.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddSubset0\n\n*/\nDdNode *\nCudd_zddSubset1(\n  DdManager * dd,\n  DdNode * P,\n  int  var)\n{\n    DdNode\t*r;\n\n    do {\n\tdd->reordered = 0;\n\tr = cuddZddSubset1(dd, P, var);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(r);\n\n} /* end of Cudd_zddSubset1 */\n\n\n/**\n  @brief Computes the negative cofactor of a %ZDD w.r.t. a variable.\n\n  @details In terms of combinations, the result is the set of all\n  combinations in which the variable is negated.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddSubset1\n\n*/\nDdNode *\nCudd_zddSubset0(\n  DdManager * dd,\n  DdNode * P,\n  int  var)\n{\n    DdNode\t*r;\n\n    do {\n\tdd->reordered = 0;\n\tr = cuddZddSubset0(dd, P, var);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n\n    return(r);\n\n} /* end of Cudd_zddSubset0 */\n\n\n/**\n  @brief Substitutes a variable with its complement in a %ZDD.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nCudd_zddChange(\n  DdManager * dd,\n  DdNode * P,\n  int  var)\n{\n    DdNode\t*res;\n\n    if ((unsigned int) var >= CUDD_MAXINDEX - 1) return(NULL);\n    \n    do {\n\tdd->reordered = 0;\n\tres = cuddZddChange(dd, P, var);\n    } while (dd->reordered == 1);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddChange */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddIte.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddZddIte(\n  DdManager * dd,\n  DdNode * f,\n  DdNode * g,\n  DdNode * h)\n{\n    DdNode *tautology, *empty;\n    DdNode *r,*Gv,*Gvn,*Hv,*Hvn,*t,*e;\n    int topf,topg,toph,v,top;\n    unsigned int index;\n\n    statLine(dd);\n    /* Trivial cases. */\n    /* One variable cases. */\n    if (f == (empty = DD_ZERO(dd))) {\t/* ITE(0,G,H) = H */\n\treturn(h);\n    }\n    topf = cuddIZ(dd,f->index);\n    topg = cuddIZ(dd,g->index);\n    toph = cuddIZ(dd,h->index);\n    v = ddMin(topg,toph);\n    top  = ddMin(topf,v);\n\n    tautology = (top == CUDD_MAXINDEX) ? DD_ONE(dd) : dd->univ[top];\n    if (f == tautology) {\t\t\t/* ITE(1,G,H) = G */\n    \treturn(g);\n    }\n\n    /* From now on, f is known to not be a constant. */\n    zddVarToConst(f,&g,&h,tautology,empty);\n\n    /* Check remaining one variable cases. */\n    if (g == h) {\t\t\t/* ITE(F,G,G) = G */\n\treturn(g);\n    }\n\n    if (g == tautology) {\t\t\t/* ITE(F,1,0) = F */\n\tif (h == empty) return(f);\n    }\n\n    /* Check cache. */\n    r = cuddCacheLookupZdd(dd,DD_ZDD_ITE_TAG,f,g,h);\n    if (r != NULL) {\n\treturn(r);\n    }\n\n    /* Recompute these because they may have changed in zddVarToConst. */\n    topg = cuddIZ(dd,g->index);\n    toph = cuddIZ(dd,h->index);\n    v = ddMin(topg,toph);\n\n    if (topf < v) {\n\tr = cuddZddIte(dd,cuddE(f),g,h);\n\tif (r == NULL) return(NULL);\n    } else if (topf > v) {\n\tif (topg > v) {\n\t    Gvn = g;\n\t    index = h->index;\n\t} else {\n\t    Gvn = cuddE(g);\n\t    index = g->index;\n\t}\n\tif (toph > v) {\n\t    Hv = empty; Hvn = h;\n\t} else {\n\t    Hv = cuddT(h); Hvn = cuddE(h);\n\t}\n\te = cuddZddIte(dd,f,Gvn,Hvn);\n\tif (e == NULL) return(NULL);\n\tcuddRef(e);\n\tr = cuddZddGetNode(dd,index,Hv,e);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd,e);\n\t    return(NULL);\n\t}\n\tcuddDeref(e);\n    } else {\n\tindex = f->index;\n\tif (topg > v) {\n\t    Gv = empty; Gvn = g;\n\t} else {\n\t    Gv = cuddT(g); Gvn = cuddE(g);\n\t}\n\tif (toph > v) {\n\t    Hv = empty; Hvn = h;\n\t} else {\n\t    Hv = cuddT(h); Hvn = cuddE(h);\n\t}\n\te = cuddZddIte(dd,cuddE(f),Gvn,Hvn);\n\tif (e == NULL) return(NULL);\n\tcuddRef(e);\n\tt = cuddZddIte(dd,cuddT(f),Gv,Hv);\n\tif (t == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd,e);\n\t    return(NULL);\n\t}\n\tcuddRef(t);\n\tr = cuddZddGetNode(dd,index,t,e);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd,e);\n\t    Cudd_RecursiveDerefZdd(dd,t);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert(dd,DD_ZDD_ITE_TAG,f,g,h,r);\n\n    return(r);\n\n} /* end of cuddZddIte */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddUnion.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddZddUnion(\n  DdManager * zdd,\n  DdNode * P,\n  DdNode * Q)\n{\n    int\t\tp_top, q_top;\n    DdNode\t*empty = DD_ZERO(zdd), *t, *e, *res;\n    DdManager\t*table = zdd;\n\n    statLine(zdd);\n    if (P == empty)\n\treturn(Q);\n    if (Q == empty)\n\treturn(P);\n    if (P == Q)\n\treturn(P);\n\n    /* Check cache */\n    res = cuddCacheLookup2Zdd(table, cuddZddUnion, P, Q);\n    if (res != NULL)\n\treturn(res);\n\n    if (cuddIsConstant(P))\n\tp_top = P->index;\n    else\n\tp_top = zdd->permZ[P->index];\n    if (cuddIsConstant(Q))\n\tq_top = Q->index;\n    else\n\tq_top = zdd->permZ[Q->index];\n    if (p_top < q_top) {\n\te = cuddZddUnion(zdd, cuddE(P), Q);\n\tif (e == NULL) return (NULL);\n\tcuddRef(e);\n\tres = cuddZddGetNode(zdd, P->index, cuddT(P), e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(e);\n    } else if (p_top > q_top) {\n\te = cuddZddUnion(zdd, P, cuddE(Q));\n\tif (e == NULL) return(NULL);\n\tcuddRef(e);\n\tres = cuddZddGetNode(zdd, Q->index, cuddT(Q), e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(e);\n    } else {\n\tt = cuddZddUnion(zdd, cuddT(P), cuddT(Q));\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n\te = cuddZddUnion(zdd, cuddE(P), cuddE(Q));\n\tif (e == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n\tres = cuddZddGetNode(zdd, P->index, t, e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, t);\n\t    Cudd_RecursiveDerefZdd(table, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert2(table, cuddZddUnion, P, Q, res);\n\n    return(res);\n\n} /* end of cuddZddUnion */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddIntersect.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddZddIntersect(\n  DdManager * zdd,\n  DdNode * P,\n  DdNode * Q)\n{\n    int\t\tp_top, q_top;\n    DdNode\t*empty = DD_ZERO(zdd), *t, *e, *res;\n    DdManager\t*table = zdd;\n\n    statLine(zdd);\n    if (P == empty)\n\treturn(empty);\n    if (Q == empty)\n\treturn(empty);\n    if (P == Q)\n\treturn(P);\n\n    /* Check cache. */\n    res = cuddCacheLookup2Zdd(table, cuddZddIntersect, P, Q);\n    if (res != NULL)\n\treturn(res);\n\n    if (cuddIsConstant(P))\n\tp_top = P->index;\n    else\n\tp_top = zdd->permZ[P->index];\n    if (cuddIsConstant(Q))\n\tq_top = Q->index;\n    else\n\tq_top = zdd->permZ[Q->index];\n    if (p_top < q_top) {\n\tres = cuddZddIntersect(zdd, cuddE(P), Q);\n\tif (res == NULL) return(NULL);\n    } else if (p_top > q_top) {\n\tres = cuddZddIntersect(zdd, P, cuddE(Q));\n\tif (res == NULL) return(NULL);\n    } else {\n\tt = cuddZddIntersect(zdd, cuddT(P), cuddT(Q));\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n\te = cuddZddIntersect(zdd, cuddE(P), cuddE(Q));\n\tif (e == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n\tres = cuddZddGetNode(zdd, P->index, t, e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, t);\n\t    Cudd_RecursiveDerefZdd(table, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert2(table, cuddZddIntersect, P, Q, res);\n\n    return(res);\n\n} /* end of cuddZddIntersect */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddDiff.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddZddDiff(\n  DdManager * zdd,\n  DdNode * P,\n  DdNode * Q)\n{\n    int\t\tp_top, q_top;\n    DdNode\t*empty = DD_ZERO(zdd), *t, *e, *res;\n    DdManager\t*table = zdd;\n\n    statLine(zdd);\n    if (P == empty)\n\treturn(empty);\n    if (Q == empty)\n\treturn(P);\n    if (P == Q)\n\treturn(empty);\n\n    /* Check cache.  The cache is shared by Cudd_zddDiffConst(). */\n    res = cuddCacheLookup2Zdd(table, cuddZddDiff, P, Q);\n    if (res != NULL && res != DD_NON_CONSTANT)\n\treturn(res);\n\n    if (cuddIsConstant(P))\n\tp_top = P->index;\n    else\n\tp_top = zdd->permZ[P->index];\n    if (cuddIsConstant(Q))\n\tq_top = Q->index;\n    else\n\tq_top = zdd->permZ[Q->index];\n    if (p_top < q_top) {\n\te = cuddZddDiff(zdd, cuddE(P), Q);\n\tif (e == NULL) return(NULL);\n\tcuddRef(e);\n\tres = cuddZddGetNode(zdd, P->index, cuddT(P), e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(e);\n    } else if (p_top > q_top) {\n\tres = cuddZddDiff(zdd, P, cuddE(Q));\n\tif (res == NULL) return(NULL);\n    } else {\n\tt = cuddZddDiff(zdd, cuddT(P), cuddT(Q));\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n\te = cuddZddDiff(zdd, cuddE(P), cuddE(Q));\n\tif (e == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n\tres = cuddZddGetNode(zdd, P->index, t, e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(table, t);\n\t    Cudd_RecursiveDerefZdd(table, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert2(table, cuddZddDiff, P, Q, res);\n\n    return(res);\n\n} /* end of cuddZddDiff */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddChange.\n\n  @sideeffect None\n\n*/\nDdNode *\ncuddZddChangeAux(\n  DdManager * zdd,\n  DdNode * P,\n  DdNode * zvar)\n{\n    int\t\ttop_var, level;\n    DdNode\t*res, *t, *e;\n    DdNode\t*base = DD_ONE(zdd);\n    DdNode\t*empty = DD_ZERO(zdd);\n\n    statLine(zdd);\n    if (P == empty)\n\treturn(empty);\n    if (P == base)\n\treturn(zvar);\n\n    /* Check cache. */\n    res = cuddCacheLookup2Zdd(zdd, cuddZddChangeAux, P, zvar);\n    if (res != NULL)\n\treturn(res);\n\n    top_var = zdd->permZ[P->index];\n    level = zdd->permZ[zvar->index];\n\n    if (top_var > level) {\n\tres = cuddZddGetNode(zdd, zvar->index, P, DD_ZERO(zdd));\n\tif (res == NULL) return(NULL);\n    } else if (top_var == level) {\n\tres = cuddZddGetNode(zdd, zvar->index, cuddE(P), cuddT(P));\n\tif (res == NULL) return(NULL);\n    } else {\n\tt = cuddZddChangeAux(zdd, cuddT(P), zvar);\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n\te = cuddZddChangeAux(zdd, cuddE(P), zvar);\n\tif (e == NULL) {\n\t    Cudd_RecursiveDerefZdd(zdd, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n\tres = cuddZddGetNode(zdd, P->index, t, e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(zdd, t);\n\t    Cudd_RecursiveDerefZdd(zdd, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert2(zdd, cuddZddChangeAux, P, zvar, res);\n\n    return(res);\n\n} /* end of cuddZddChangeAux */\n\n\n/**\n  @brief Computes the positive cofactor of a %ZDD w.r.t. a variable.\n\n  @details In terms of combinations, the result is the set of all\n  combinations in which the variable is asserted.  cuddZddSubset1\n  performs the same function as Cudd_zddSubset1, but does not restart\n  if reordering has taken place. Therefore it can be called from\n  within a recursive procedure.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddZddSubset0 Cudd_zddSubset1\n\n*/\nDdNode *\ncuddZddSubset1(\n  DdManager * dd,\n  DdNode * P,\n  int  var)\n{\n    DdNode\t*zvar, *r;\n    DdNode\t*base, *empty;\n\n    base = DD_ONE(dd);\n    empty = DD_ZERO(dd);\n\n    zvar = cuddUniqueInterZdd(dd, var, base, empty);\n    if (zvar == NULL) {\n\treturn(NULL);\n    } else {\n\tcuddRef(zvar);\n\tr = zdd_subset1_aux(dd, P, zvar);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, zvar);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_RecursiveDerefZdd(dd, zvar);\n    }\n\n    cuddDeref(r);\n    return(r);\n\n} /* end of cuddZddSubset1 */\n\n\n/**\n  @brief Computes the negative cofactor of a %ZDD w.r.t. a variable.\n\n  @details In terms of combinations, the result is the set of all\n  combinations in which the variable is negated.  cuddZddSubset0\n  performs the same function as Cudd_zddSubset0, but does not restart\n  if reordering has taken place. Therefore it can be called from\n  within a recursive procedure.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see cuddZddSubset1 Cudd_zddSubset0\n\n*/\nDdNode *\ncuddZddSubset0(\n  DdManager * dd,\n  DdNode * P,\n  int  var)\n{\n    DdNode\t*zvar, *r;\n    DdNode\t*base, *empty;\n\n    base = DD_ONE(dd);\n    empty = DD_ZERO(dd);\n\n    zvar = cuddUniqueInterZdd(dd, var, base, empty);\n    if (zvar == NULL) {\n\treturn(NULL);\n    } else {\n\tcuddRef(zvar);\n\tr = zdd_subset0_aux(dd, P, zvar);\n\tif (r == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd, zvar);\n\t    return(NULL);\n\t}\n\tcuddRef(r);\n\tCudd_RecursiveDerefZdd(dd, zvar);\n    }\n\n    cuddDeref(r);\n    return(r);\n\n} /* end of cuddZddSubset0 */\n\n\n/**\n  @brief Substitutes a variable with its complement in a %ZDD.\n\n  @details cuddZddChange performs the same function as Cudd_zddChange,\n  but does not restart if reordering has taken place. Therefore it can\n  be called from within a recursive procedure.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddChange\n\n*/\nDdNode *\ncuddZddChange(\n  DdManager * dd,\n  DdNode * P,\n  int  var)\n{\n    DdNode\t*zvar, *res;\n\n    zvar = cuddUniqueInterZdd(dd, var, DD_ONE(dd), DD_ZERO(dd));\n    if (zvar == NULL) return(NULL);\n    cuddRef(zvar);\n\n    res = cuddZddChangeAux(dd, P, zvar);\n    if (res == NULL) {\n\tCudd_RecursiveDerefZdd(dd,zvar);\n\treturn(NULL);\n    }\n    cuddRef(res);\n    Cudd_RecursiveDerefZdd(dd,zvar);\n    cuddDeref(res);\n    return(res);\n\n} /* end of cuddZddChange */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddSubset1.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nzdd_subset1_aux(\n  DdManager * zdd,\n  DdNode * P,\n  DdNode * zvar)\n{\n    int\t\ttop_var, level;\n    DdNode\t*res, *t, *e;\n    DdNode\t*empty;\n\n    statLine(zdd);\n    empty = DD_ZERO(zdd);\n\n    /* Check cache. */\n    res = cuddCacheLookup2Zdd(zdd, zdd_subset1_aux, P, zvar);\n    if (res != NULL)\n\treturn(res);\n\n    if (cuddIsConstant(P)) {\n\tres = empty;\n\tcuddCacheInsert2(zdd, zdd_subset1_aux, P, zvar, res);\n\treturn(res);\n    }\n\n    top_var = zdd->permZ[P->index];\n    level = zdd->permZ[zvar->index];\n\n    if (top_var > level) {\n        res = empty;\n    } else if (top_var == level) {\n\tres = cuddT(P);\n    } else {\n        t = zdd_subset1_aux(zdd, cuddT(P), zvar);\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n        e = zdd_subset1_aux(zdd, cuddE(P), zvar);\n\tif (e == NULL) {\n\t    Cudd_RecursiveDerefZdd(zdd, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n        res = cuddZddGetNode(zdd, P->index, t, e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(zdd, t);\n\t    Cudd_RecursiveDerefZdd(zdd, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert2(zdd, zdd_subset1_aux, P, zvar, res);\n\n    return(res);\n\n} /* end of zdd_subset1_aux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddSubset0.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nzdd_subset0_aux(\n  DdManager * zdd,\n  DdNode * P,\n  DdNode * zvar)\n{\n    int\t\ttop_var, level;\n    DdNode\t*res, *t, *e;\n\n    statLine(zdd);\n\n    /* Check cache. */\n    res = cuddCacheLookup2Zdd(zdd, zdd_subset0_aux, P, zvar);\n    if (res != NULL)\n\treturn(res);\n\n    if (cuddIsConstant(P)) {\n\tres = P;\n\tcuddCacheInsert2(zdd, zdd_subset0_aux, P, zvar, res);\n\treturn(res);\n    }\n\n    top_var = zdd->permZ[P->index];\n    level = zdd->permZ[zvar->index];\n\n    if (top_var > level) {\n        res = P;\n    }\n    else if (top_var == level) {\n        res = cuddE(P);\n    }\n    else {\n        t = zdd_subset0_aux(zdd, cuddT(P), zvar);\n\tif (t == NULL) return(NULL);\n\tcuddRef(t);\n        e = zdd_subset0_aux(zdd, cuddE(P), zvar);\n\tif (e == NULL) {\n\t    Cudd_RecursiveDerefZdd(zdd, t);\n\t    return(NULL);\n\t}\n\tcuddRef(e);\n        res = cuddZddGetNode(zdd, P->index, t, e);\n\tif (res == NULL) {\n\t    Cudd_RecursiveDerefZdd(zdd, t);\n\t    Cudd_RecursiveDerefZdd(zdd, e);\n\t    return(NULL);\n\t}\n\tcuddDeref(t);\n\tcuddDeref(e);\n    }\n\n    cuddCacheInsert2(zdd, zdd_subset0_aux, P, zvar, res);\n\n    return(res);\n\n} /* end of zdd_subset0_aux */\n\n\n/**\n  @brief Replaces variables with constants if possible (part of\n  canonical form).\n\n  @sideeffect None\n\n*/\nstatic void\nzddVarToConst(\n  DdNode * f,\n  DdNode ** gp,\n  DdNode ** hp,\n  DdNode * base,\n  DdNode * empty)\n{\n    DdNode *g = *gp;\n    DdNode *h = *hp;\n\n    if (f == g) { /* ITE(F,F,H) = ITE(F,1,H) = F + H */\n\t*gp = base;\n    }\n\n    if (f == h) { /* ITE(F,G,F) = ITE(F,G,0) = F * G */\n\t*hp = empty;\n    }\n\n} /* end of zddVarToConst */\n\n"
  },
  {
    "path": "cudd/cudd/cuddZddSymm.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Functions for symmetry-based %ZDD variable reordering.\n\n  @see cuddSymmetry.c\n\n  @author Hyong-Kyoon Shin, In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define ZDD_MV_OOM (Move *)1\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int cuddZddSymmSiftingAux (DdManager *table, int x, int x_low, int x_high);\nstatic int cuddZddSymmSiftingConvAux (DdManager *table, int x, int x_low, int x_high);\nstatic Move * cuddZddSymmSifting_up (DdManager *table, int x, int x_low, int initial_size);\nstatic Move * cuddZddSymmSifting_down (DdManager *table, int x, int x_high, int initial_size);\nstatic int cuddZddSymmSiftingBackward (DdManager *table, Move *moves, int size);\nstatic int zdd_group_move (DdManager *table, int x, int y, Move **moves);\nstatic int zdd_group_move_backward (DdManager *table, int x, int y);\nstatic void cuddZddSymmSummary (DdManager *table, int lower, int upper, int *symvars, int *symgroups);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints statistics on symmetric %ZDD variables.\n\n  @sideeffect None\n\n*/\nvoid\nCudd_zddSymmProfile(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\t\ti, x, gbot;\n    int\t\tTotalSymm = 0;\n    int \tTotalSymmGroups = 0;\n\n    for (i = lower; i < upper; i++) {\n\tif (table->subtableZ[i].next != (unsigned) i) {\n\t    x = i;\n\t    (void) fprintf(table->out,\"Group:\");\n\t    do {\n\t\t(void) fprintf(table->out,\"  %d\", table->invpermZ[x]);\n\t\tTotalSymm++;\n\t\tgbot = x;\n\t\tx = table->subtableZ[x].next;\n\t    } while (x != i);\n\t    TotalSymmGroups++;\n#ifdef DD_DEBUG\n\t    assert(table->subtableZ[gbot].next == (unsigned) i);\n#endif\n\t    i = gbot;\n\t    (void) fprintf(table->out,\"\\n\");\n\t}\n    }\n    (void) fprintf(table->out,\"Total Symmetric = %d\\n\", TotalSymm);\n    (void) fprintf(table->out,\"Total Groups = %d\\n\", TotalSymmGroups);\n\n} /* end of Cudd_zddSymmProfile */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Checks for symmetry of x and y.\n\n  @details Ignores projection functions, unless they are isolated.\n\n  @return 1 in case of symmetry; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\ncuddZddSymmCheck(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    int\t\ti;\n    DdNode\t*f, *f0, *f1, *f01, *f00, *f11, *f10;\n    int\t\tyindex;\n    int \txsymmy = 1;\n    int\t\txsymmyp = 1;\n    int \tarccount = 0;\n    int \tTotalRefCount = 0;\n    int \tsymm_found;\n    DdNode\t*empty = table->zero;\n\n    yindex = table->invpermZ[y];\n    for (i = table->subtableZ[x].slots - 1; i >= 0; i--) {\n\tf = table->subtableZ[x].nodelist[i];\n\twhile (f != NULL) {\n\t    /* Find f1, f0, f11, f10, f01, f00 */\n\t    f1 = cuddT(f);\n\t    f0 = cuddE(f);\n\t    if ((int) f1->index == yindex) {\n\t\tf11 = cuddT(f1);\n\t\tf10 = cuddE(f1);\n\t\tif (f10 != empty)\n\t\t    arccount++;\n\t    } else {\n\t\tif ((int) f0->index != yindex) {\n\t\t    return(0); /* f bypasses layer y */\n\t\t}\n\t\tf11 = empty;\n\t\tf10 = f1;\n\t    }\n\t    if ((int) f0->index == yindex) {\n\t\tf01 = cuddT(f0);\n\t\tf00 = cuddE(f0);\n\t\tif (f00 != empty)\n\t\t    arccount++;\n\t    } else {\n\t\tf01 = empty;\n\t\tf00 = f0;\n\t    }\n\t    if (f01 != f10)\n\t\txsymmy = 0;\n\t    if (f11 != f00)\n\t\txsymmyp = 0;\n\t    if ((xsymmy == 0) && (xsymmyp == 0))\n\t\treturn(0);\n\n\t    f = f->next;\n\t} /* for each element of the collision list */\n    } /* for each slot of the subtable */\n\n    /* Calculate the total reference counts of y\n    ** whose else arc is not empty.\n    */\n    for (i = table->subtableZ[y].slots - 1; i >= 0; i--) {\n\tf = table->subtableZ[y].nodelist[i];\n\twhile (f != NIL(DdNode)) {\n\t    if (cuddE(f) != empty)\n\t\tTotalRefCount += f->ref;\n\t    f = f->next;\n\t}\n    }\n\n    symm_found = (arccount == TotalRefCount);\n#if defined(DD_DEBUG) && defined(DD_VERBOSE)\n    if (symm_found) {\n\tint xindex = table->invpermZ[x];\n\t(void) fprintf(table->out,\n\t\t       \"Found symmetry! x =%d\\ty = %d\\tPos(%d,%d)\\n\",\n\t\t       xindex,yindex,x,y);\n    }\n#endif\n\n    return(symm_found);\n\n} /* end cuddZddSymmCheck */\n\n\n/**\n  @brief Symmetric sifting algorithm for ZDDs.\n\n  @details Assumes that no dead nodes are present.\n    <ol>\n    <li> Order all the variables according to the number of entries in\n    each unique subtable.\n    <li> Sift the variable up and down, remembering each time the total\n    size of the %ZDD heap and grouping variables that are symmetric.\n    <li> Select the best permutation.\n    <li> Repeat 3 and 4 for all variables.\n    </ol>\n\n  @return 1 plus the number of symmetric variables if successful; 0\n  otherwise.\n\n  @sideeffect None\n\n  @see cuddZddSymmSiftingConv\n\n*/\nint\ncuddZddSymmSifting(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\t\ti;\n    IndexKey\t*var;\n    int\t\tnvars;\n    int\t\tx;\n    int\t\tresult;\n    int\t\tsymvars;\n    int\t\tsymgroups;\n    int\t\titeration;\n#ifdef DD_STATS\n    int\t\tpreviousSize;\n#endif\n\n    nvars = table->sizeZ;\n\n    /* Find order in which to sift variables. */\n    var = ALLOC(IndexKey, nvars);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto cuddZddSymmSiftingOutOfMem;\n    }\n\n    for (i = 0; i < nvars; i++) {\n\tx = table->permZ[i];\n\tvar[i].index = i;\n\tvar[i].keys = table->subtableZ[x].keys;\n    }\n\n    util_qsort(var, nvars, sizeof(IndexKey), cuddZddUniqueCompare);\n\n    /* Initialize the symmetry of each subtable to itself. */\n    for (i = lower; i <= upper; i++)\n\ttable->subtableZ[i].next = i;\n\n    iteration = ddMin(table->siftMaxVar, nvars);\n    for (i = 0; i < iteration; i++) {\n\tif (table->zddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime > table->timeLimit) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n\tx = table->permZ[var[i].index];\n#ifdef DD_STATS\n\tpreviousSize = table->keysZ;\n#endif\n\tif (x < lower || x > upper) continue;\n\tif (table->subtableZ[x].next == (unsigned) x) {\n\t    result = cuddZddSymmSiftingAux(table, x, lower, upper);\n\t    if (!result)\n\t\tgoto cuddZddSymmSiftingOutOfMem;\n#ifdef DD_STATS\n\t    if (table->keysZ < (unsigned) previousSize) {\n\t\t(void) fprintf(table->out,\"-\");\n\t    } else if (table->keysZ > (unsigned) previousSize) {\n\t\t(void) fprintf(table->out,\"+\");\n#ifdef DD_VERBOSE\n\t\t(void) fprintf(table->out,\"\\nSize increased from %d to %d while sifting variable %d\\n\", previousSize, table->keysZ, var[i].index);\n#endif\n\t    } else {\n\t\t(void) fprintf(table->out,\"=\");\n\t    }\n\t    fflush(table->out);\n#endif\n\t}\n    }\n\n    FREE(var);\n\n    cuddZddSymmSummary(table, lower, upper, &symvars, &symgroups);\n\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n#:S_SIFTING %8d: symmetric variables\\n\",symvars);\n    (void) fprintf(table->out,\"#:G_SIFTING %8d: symmetric groups\\n\",symgroups);\n#endif\n\n    return(1+symvars);\n\ncuddZddSymmSiftingOutOfMem:\n\n    if (var != NULL)\n\tFREE(var);\n\n    return(0);\n\n} /* end of cuddZddSymmSifting */\n\n\n/**\n  @brief Symmetric sifting to convergence algorithm for ZDDs.\n\n  @details Assumes that no dead nodes are present.\n    <ol>\n    <li> Order all the variables according to the number of entries in\n    each unique subtable.\n    <li> Sift the variable up and down, remembering each time the total\n    size of the %ZDD heap and grouping variables that are symmetric.\n    <li> Select the best permutation.\n    <li> Repeat 3 and 4 for all variables.\n    <li> Repeat 1-4 until no further improvement.\n    </ol>\n\n  @return 1 plus the number of symmetric variables if successful; 0\n  otherwise.\n\n  @sideeffect None\n\n  @see cuddZddSymmSifting\n\n*/\nint\ncuddZddSymmSiftingConv(\n  DdManager * table,\n  int  lower,\n  int  upper)\n{\n    int\t\ti;\n    IndexKey\t*var;\n    int\t\tnvars;\n    int\t\tinitialSize;\n    int\t\tx;\n    int\t\tresult;\n    int\t\tsymvars;\n    int\t\tsymgroups;\n    int\t\tclasses;\n    int\t\titeration;\n#ifdef DD_STATS\n    int         previousSize;\n#endif\n\n    initialSize = table->keysZ;\n\n    nvars = table->sizeZ;\n\n    /* Find order in which to sift variables. */\n    var = ALLOC(IndexKey, nvars);\n    if (var == NULL) {\n\ttable->errorCode = CUDD_MEMORY_OUT;\n\tgoto cuddZddSymmSiftingConvOutOfMem;\n    }\n\n    for (i = 0; i < nvars; i++) {\n\tx = table->permZ[i];\n\tvar[i].index = i;\n\tvar[i].keys = table->subtableZ[x].keys;\n    }\n\n    util_qsort(var, nvars, sizeof(IndexKey), cuddZddUniqueCompare);\n\n    /* Initialize the symmetry of each subtable to itself\n    ** for first pass of converging symmetric sifting.\n    */\n    for (i = lower; i <= upper; i++)\n\ttable->subtableZ[i].next = i;\n\n    iteration = ddMin(table->siftMaxVar, table->sizeZ);\n    for (i = 0; i < iteration; i++) {\n\tif (table->zddTotalNumberSwapping >= table->siftMaxSwap)\n\t    break;\n        if (util_cpu_time() - table->startTime > table->timeLimit) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n        if (table->terminationCallback != NULL &&\n            table->terminationCallback(table->tcbArg)) {\n            table->autoDynZ = 0; /* prevent further reordering */\n            break;\n        }\n\tx = table->permZ[var[i].index];\n\tif (x < lower || x > upper) continue;\n\t/* Only sift if not in symmetry group already. */\n\tif (table->subtableZ[x].next == (unsigned) x) {\n#ifdef DD_STATS\n\t    previousSize = table->keysZ;\n#endif\n\t    result = cuddZddSymmSiftingAux(table, x, lower, upper);\n\t    if (!result)\n\t\tgoto cuddZddSymmSiftingConvOutOfMem;\n#ifdef DD_STATS\n\t    if (table->keysZ < (unsigned) previousSize) {\n\t\t(void) fprintf(table->out,\"-\");\n\t    } else if (table->keysZ > (unsigned) previousSize) {\n\t\t(void) fprintf(table->out,\"+\");\n#ifdef DD_VERBOSE\n\t\t(void) fprintf(table->out,\"\\nSize increased from %d to %d while sifting variable %d\\n\", previousSize, table->keysZ, var[i].index);\n#endif\n\t    } else {\n\t\t(void) fprintf(table->out,\"=\");\n\t    }\n\t    fflush(table->out);\n#endif\n\t}\n    }\n\n    /* Sifting now until convergence. */\n    while ((unsigned) initialSize > table->keysZ) {\n\tinitialSize = table->keysZ;\n#ifdef DD_STATS\n\t(void) fprintf(table->out,\"\\n\");\n#endif\n\t/* Here we consider only one representative for each symmetry class. */\n\tfor (x = lower, classes = 0; x <= upper; x++, classes++) {\n\t    while ((unsigned) x < table->subtableZ[x].next)\n\t\tx = table->subtableZ[x].next;\n\t    /* Here x is the largest index in a group.\n\t    ** Groups consists of adjacent variables.\n\t    ** Hence, the next increment of x will move it to a new group.\n\t    */\n\t    i = table->invpermZ[x];\n\t    var[classes].index = i;\n\t    var[classes].keys = table->subtableZ[x].keys;\n\t}\n\n\tutil_qsort(var,classes,sizeof(IndexKey),cuddZddUniqueCompare);\n\n\t/* Now sift. */\n\titeration = ddMin(table->siftMaxVar, nvars);\n\tfor (i = 0; i < iteration; i++) {\n\t    if (table->zddTotalNumberSwapping >= table->siftMaxSwap)\n\t\tbreak;\n            if (util_cpu_time() - table->startTime > table->timeLimit) {\n              table->autoDynZ = 0; /* prevent further reordering */\n              break;\n            }\n            if (table->terminationCallback != NULL &&\n                table->terminationCallback(table->tcbArg)) {\n                table->autoDynZ = 0; /* prevent further reordering */\n                break;\n            }\n\t    x = table->permZ[var[i].index];\n\t    if ((unsigned) x >= table->subtableZ[x].next) {\n#ifdef DD_STATS\n\t\tpreviousSize = table->keysZ;\n#endif\n\t\tresult = cuddZddSymmSiftingConvAux(table, x, lower, upper);\n\t\tif (!result)\n\t\t    goto cuddZddSymmSiftingConvOutOfMem;\n#ifdef DD_STATS\n\t\tif (table->keysZ < (unsigned) previousSize) {\n\t\t    (void) fprintf(table->out,\"-\");\n\t\t} else if (table->keysZ > (unsigned) previousSize) {\n\t\t    (void) fprintf(table->out,\"+\");\n#ifdef DD_VERBOSE\n\t\t(void) fprintf(table->out,\"\\nSize increased from %d to %d while sifting variable %d\\n\", previousSize, table->keysZ, var[i].index);\n#endif\n\t\t} else {\n\t\t    (void) fprintf(table->out,\"=\");\n\t\t}\n\t\tfflush(table->out);\n#endif\n\t    }\n\t} /* for */\n    }\n\n    cuddZddSymmSummary(table, lower, upper, &symvars, &symgroups);\n\n#ifdef DD_STATS\n    (void) fprintf(table->out,\"\\n#:S_SIFTING %8d: symmetric variables\\n\",\n\t\t   symvars);\n    (void) fprintf(table->out,\"#:G_SIFTING %8d: symmetric groups\\n\",\n\t\t   symgroups);\n#endif\n\n    FREE(var);\n\n    return(1+symvars);\n\ncuddZddSymmSiftingConvOutOfMem:\n\n    if (var != NULL)\n\tFREE(var);\n\n    return(0);\n\n} /* end of cuddZddSymmSiftingConv */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Given x_low <= x <= x_high moves x up and down between the\n  boundaries.\n\n  @details Finds the best position and does the required changes.\n  Assumes that x is not part of a symmetry group.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddSymmSiftingAux(\n  DdManager * table,\n  int  x,\n  int  x_low,\n  int  x_high)\n{\n    Move *move;\n    Move *move_up;\t/* list of up move */\n    Move *move_down;\t/* list of down move */\n    int\t initial_size;\n    int\t result;\n    int\t i;\n    int  topbot;\t/* index to either top or bottom of symmetry group */\n    int\t init_group_size, final_group_size;\n\n    initial_size = table->keysZ;\n\n    move_down = NULL;\n    move_up = NULL;\n\n    /* Look for consecutive symmetries above x. */\n    for (i = x; i > x_low; i--) {\n\tif (!cuddZddSymmCheck(table, i - 1, i))\n            break;\n\t/* find top of i-1's symmetry */\n\ttopbot = table->subtableZ[i - 1].next;\n\ttable->subtableZ[i - 1].next = i;\n\ttable->subtableZ[x].next = topbot;\n\t/* x is bottom of group so its symmetry is top of i-1's\n\t   group */\n\ti = topbot + 1; /* add 1 for i--, new i is top of symm group */\n    }\n    /* Look for consecutive symmetries below x. */\n    for (i = x; i < x_high; i++) {\n\tif (!cuddZddSymmCheck(table, i, i + 1))\n            break;\n\t/* find bottom of i+1's symm group */\n\ttopbot = i + 1;\n\twhile ((unsigned) topbot < table->subtableZ[topbot].next)\n\t    topbot = table->subtableZ[topbot].next;\n\n\ttable->subtableZ[topbot].next = table->subtableZ[i].next;\n\ttable->subtableZ[i].next = i + 1;\n\ti = topbot - 1; /* add 1 for i++,\n\t\t\t   new i is bottom of symm group */\n    }\n\n    /* Now x maybe in the middle of a symmetry group. */\n    if (x == x_low) { /* Sift down */\n\t/* Find bottom of x's symm group */\n\twhile ((unsigned) x < table->subtableZ[x].next)\n\t    x = table->subtableZ[x].next;\n\n\ti = table->subtableZ[x].next;\n\tinit_group_size = x - i + 1;\n\n\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t    initial_size);\n\t/* after that point x --> x_high, unless early term */\n\tif (move_down == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n\n\tif (move_down == NULL ||\n\t    table->subtableZ[move_down->y].next != move_down->y) {\n\t    /* symmetry detected may have to make another complete\n\t       pass */\n            if (move_down != NULL)\n\t\tx = move_down->y;\n\t    else\n\t\tx = table->subtableZ[x].next;\n\t    i = x;\n\t    while ((unsigned) i < table->subtableZ[i].next) {\n\t\ti = table->subtableZ[i].next;\n\t    }\n\t    final_group_size = i - x + 1;\n\n\t    if (init_group_size == final_group_size) {\n\t\t/* No new symmetry groups detected,\n\t\t   return to best position */\n\t\tresult = cuddZddSymmSiftingBackward(table,\n\t\t    move_down, initial_size);\n\t    }\n\t    else {\n\t\tinitial_size = table->keysZ;\n\t\tmove_up = cuddZddSymmSifting_up(table, x, x_low,\n\t\t    initial_size);\n\t\tresult = cuddZddSymmSiftingBackward(table, move_up,\n\t\t    initial_size);\n\t    }\n\t}\n\telse {\n\t    result = cuddZddSymmSiftingBackward(table, move_down,\n\t\tinitial_size);\n\t    /* move backward and stop at best position */\n\t}\n\tif (!result)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n    }\n    else if (x == x_high) { /* Sift up */\n\t/* Find top of x's symm group */\n\twhile ((unsigned) x < table->subtableZ[x].next)\n\t    x = table->subtableZ[x].next;\n\tx = table->subtableZ[x].next;\n\n\ti = x;\n\twhile ((unsigned) i < table->subtableZ[i].next) {\n\t    i = table->subtableZ[i].next;\n\t}\n\tinit_group_size = i - x + 1;\n\n\tmove_up = cuddZddSymmSifting_up(table, x, x_low, initial_size);\n\t/* after that point x --> x_low, unless early term */\n\tif (move_up == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n\n\tif (move_up == NULL ||\n\t    table->subtableZ[move_up->x].next != move_up->x) {\n\t    /* symmetry detected may have to make another complete\n\t\tpass */\n            if (move_up != NULL)\n\t\tx = move_up->x;\n\t    else {\n\t\twhile ((unsigned) x < table->subtableZ[x].next)\n\t\t    x = table->subtableZ[x].next;\n\t    }\n\t    i = table->subtableZ[x].next;\n\t    final_group_size = x - i + 1;\n\n\t    if (init_group_size == final_group_size) {\n\t\t/* No new symmetry groups detected,\n\t\t   return to best position */\n\t\tresult = cuddZddSymmSiftingBackward(table, move_up,\n\t\t    initial_size);\n\t    }\n\t    else {\n\t\tinitial_size = table->keysZ;\n\t\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t\t    initial_size);\n\t\tresult = cuddZddSymmSiftingBackward(table, move_down,\n\t\t    initial_size);\n\t    }\n\t}\n\telse {\n\t    result = cuddZddSymmSiftingBackward(table, move_up,\n\t\tinitial_size);\n\t    /* move backward and stop at best position */\n\t}\n\tif (!result)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n    }\n    else if ((x - x_low) > (x_high - x)) { /* must go down first:\n\t\t\t\t\t\tshorter */\n\t/* Find bottom of x's symm group */\n\twhile ((unsigned) x < table->subtableZ[x].next)\n\t    x = table->subtableZ[x].next;\n\n\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t    initial_size);\n\t/* after that point x --> x_high, unless early term */\n\tif (move_down == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n\n\tif (move_down != NULL) {\n\t    x = move_down->y;\n\t}\n\telse {\n\t    x = table->subtableZ[x].next;\n\t}\n\ti = x;\n\twhile ((unsigned) i < table->subtableZ[i].next) {\n\t    i = table->subtableZ[i].next;\n\t}\n\tinit_group_size = i - x + 1;\n\n\tmove_up = cuddZddSymmSifting_up(table, x, x_low, initial_size);\n\tif (move_up == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n\n\tif (move_up == NULL ||\n\t    table->subtableZ[move_up->x].next != move_up->x) {\n\t    /* symmetry detected may have to make another complete\n\t       pass */\n\t    if (move_up != NULL) {\n\t\tx = move_up->x;\n\t    }\n\t    else {\n\t\twhile ((unsigned) x < table->subtableZ[x].next)\n\t\t    x = table->subtableZ[x].next;\n\t    }\n\t    i = table->subtableZ[x].next;\n\t    final_group_size = x - i + 1;\n\n\t    if (init_group_size == final_group_size) {\n\t\t/* No new symmetry groups detected,\n\t\t   return to best position */\n\t\tresult = cuddZddSymmSiftingBackward(table, move_up,\n\t\t    initial_size);\n\t    }\n\t    else {\n\t\twhile (move_down != NULL) {\n\t\t    move = move_down->next;\n\t\t    cuddDeallocMove(table, move_down);\n\t\t    move_down = move;\n\t\t}\n\t\tinitial_size = table->keysZ;\n\t\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t\t    initial_size);\n\t\tresult = cuddZddSymmSiftingBackward(table, move_down,\n\t\t    initial_size);\n\t    }\n\t}\n\telse {\n\t    result = cuddZddSymmSiftingBackward(table, move_up,\n\t\tinitial_size);\n\t    /* move backward and stop at best position */\n\t}\n\tif (!result)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n    }\n    else { /* moving up first:shorter */\n        /* Find top of x's symmetry group */\n\twhile ((unsigned) x < table->subtableZ[x].next)\n\t    x = table->subtableZ[x].next;\n\tx = table->subtableZ[x].next;\n\n\tmove_up = cuddZddSymmSifting_up(table, x, x_low, initial_size);\n\t/* after that point x --> x_high, unless early term */\n\tif (move_up == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n\n\tif (move_up != NULL) {\n\t    x = move_up->x;\n\t}\n\telse {\n\t    while ((unsigned) x < table->subtableZ[x].next)\n\t\tx = table->subtableZ[x].next;\n\t}\n\ti = table->subtableZ[x].next;\n\tinit_group_size = x - i + 1;\n\n\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t    initial_size);\n\tif (move_down == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n\n\tif (move_down == NULL ||\n\t    table->subtableZ[move_down->y].next != move_down->y) {\n\t    /* symmetry detected may have to make another complete\n\t       pass */\n            if (move_down != NULL) {\n\t\tx = move_down->y;\n\t    }\n\t    else {\n\t\tx = table->subtableZ[x].next;\n\t    }\n\t    i = x;\n\t    while ((unsigned) i < table->subtableZ[i].next) {\n\t\ti = table->subtableZ[i].next;\n\t    }\n\t    final_group_size = i - x + 1;\n\n\t    if (init_group_size == final_group_size) {\n\t\t/* No new symmetries detected,\n\t\t   go back to best position */\n\t\tresult = cuddZddSymmSiftingBackward(table, move_down,\n\t\t    initial_size);\n\t    }\n\t    else {\n\t\twhile (move_up != NULL) {\n\t\t    move = move_up->next;\n\t\t    cuddDeallocMove(table, move_up);\n\t\t    move_up = move;\n\t\t}\n\t\tinitial_size = table->keysZ;\n\t\tmove_up = cuddZddSymmSifting_up(table, x, x_low,\n\t\t    initial_size);\n\t\tresult = cuddZddSymmSiftingBackward(table, move_up,\n\t\t    initial_size);\n\t    }\n\t}\n\telse {\n\t    result = cuddZddSymmSiftingBackward(table, move_down,\n\t\tinitial_size);\n\t    /* move backward and stop at best position */\n\t}\n\tif (!result)\n\t    goto cuddZddSymmSiftingAuxOutOfMem;\n    }\n\n    while (move_down != NULL) {\n\tmove = move_down->next;\n\tcuddDeallocMove(table, move_down);\n\tmove_down = move;\n    }\n    while (move_up != NULL) {\n\tmove = move_up->next;\n\tcuddDeallocMove(table, move_up);\n\tmove_up = move;\n    }\n\n    return(1);\n\ncuddZddSymmSiftingAuxOutOfMem:\n    if (move_down != ZDD_MV_OOM) {\n\twhile (move_down != NULL) {\n\t    move = move_down->next;\n\t    cuddDeallocMove(table, move_down);\n\t    move_down = move;\n\t}\n    }\n    if (move_up != ZDD_MV_OOM) {\n\twhile (move_up != NULL) {\n\t    move = move_up->next;\n\t    cuddDeallocMove(table, move_up);\n\t    move_up = move;\n\t}\n    }\n\n    return(0);\n\n} /* end of cuddZddSymmSiftingAux */\n\n\n/**\n  @brief Given x_low <= x <= x_high moves x up and down between the\n  boundaries.\n\n  @details Finds the best position and does the required changes.\n  Assumes that x is either an isolated variable, or it is the bottom of\n  a symmetry group. All symmetries may not have been found, because of\n  exceeded growth limit.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddSymmSiftingConvAux(\n  DdManager * table,\n  int  x,\n  int  x_low,\n  int  x_high)\n{\n    Move\t*move;\n    Move\t*move_up;\t/* list of up move */\n    Move\t*move_down;\t/* list of down move */\n    int\t\tinitial_size;\n    int\t\tresult;\n    int\t\ti;\n    int\t\tinit_group_size, final_group_size;\n\n    initial_size = table->keysZ;\n\n    move_down = NULL;\n    move_up = NULL;\n\n    if (x == x_low) { /* Sift down */\n        i = table->subtableZ[x].next;\n\tinit_group_size = x - i + 1;\n\n\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t    initial_size);\n\t/* after that point x --> x_high, unless early term */\n\tif (move_down == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n\n\tif (move_down == NULL ||\n\t    table->subtableZ[move_down->y].next != move_down->y) {\n\t    /* symmetry detected may have to make another complete\n\t\tpass */\n            if (move_down != NULL)\n\t\tx = move_down->y;\n\t    else {\n\t\twhile ((unsigned) x < table->subtableZ[x].next)\n\t\t    x = table->subtableZ[x].next;\n\t\tx = table->subtableZ[x].next;\n\t    }\n\t    i = x;\n\t    while ((unsigned) i < table->subtableZ[i].next) {\n\t\ti = table->subtableZ[i].next;\n\t    }\n\t    final_group_size = i - x + 1;\n\n\t    if (init_group_size == final_group_size) {\n\t\t/* No new symmetries detected,\n\t\t   go back to best position */\n\t\tresult = cuddZddSymmSiftingBackward(table, move_down,\n\t\t    initial_size);\n\t    }\n\t    else {\n\t\tinitial_size = table->keysZ;\n\t\tmove_up = cuddZddSymmSifting_up(table, x, x_low,\n\t\t    initial_size);\n\t\tresult = cuddZddSymmSiftingBackward(table, move_up,\n\t\t    initial_size);\n\t    }\n\t}\n\telse {\n\t    result = cuddZddSymmSiftingBackward(table, move_down,\n\t\tinitial_size);\n\t    /* move backward and stop at best position */\n\t}\n\tif (!result)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n    }\n    else if (x == x_high) { /* Sift up */\n\t/* Find top of x's symm group */\n\twhile ((unsigned) x < table->subtableZ[x].next)\n\t    x = table->subtableZ[x].next;\n\tx = table->subtableZ[x].next;\n\n\ti = x;\n\twhile ((unsigned) i < table->subtableZ[i].next) {\n\t    i = table->subtableZ[i].next;\n\t}\n\tinit_group_size = i - x + 1;\n\n\tmove_up = cuddZddSymmSifting_up(table, x, x_low, initial_size);\n\t/* after that point x --> x_low, unless early term */\n\tif (move_up == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n\n\tif (move_up == NULL ||\n\t    table->subtableZ[move_up->x].next != move_up->x) {\n\t    /* symmetry detected may have to make another complete\n\t       pass */\n            if (move_up != NULL)\n\t\tx = move_up->x;\n\t    else {\n\t\twhile ((unsigned) x < table->subtableZ[x].next)\n\t\t    x = table->subtableZ[x].next;\n\t    }\n\t    i = table->subtableZ[x].next;\n\t    final_group_size = x - i + 1;\n\n\t    if (init_group_size == final_group_size) {\n\t\t/* No new symmetry groups detected,\n\t\t   return to best position */\n\t\tresult = cuddZddSymmSiftingBackward(table, move_up,\n\t\t    initial_size);\n\t    }\n\t    else {\n\t\tinitial_size = table->keysZ;\n\t\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t\t    initial_size);\n\t\tresult = cuddZddSymmSiftingBackward(table, move_down,\n\t\t    initial_size);\n\t    }\n\t}\n\telse {\n\t    result = cuddZddSymmSiftingBackward(table, move_up,\n\t\tinitial_size);\n\t    /* move backward and stop at best position */\n\t}\n\tif (!result)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n    }\n    else if ((x - x_low) > (x_high - x)) { /* must go down first:\n\t\t\t\t\t\tshorter */\n\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t    initial_size);\n\t/* after that point x --> x_high */\n\tif (move_down == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n\n\tif (move_down != NULL) {\n\t    x = move_down->y;\n\t}\n\telse {\n\t    while ((unsigned) x < table->subtableZ[x].next)\n\t\tx = table->subtableZ[x].next;\n\t    x = table->subtableZ[x].next;\n\t}\n\ti = x;\n\twhile ((unsigned) i < table->subtableZ[i].next) {\n\t    i = table->subtableZ[i].next;\n\t}\n\tinit_group_size = i - x + 1;\n\n\tmove_up = cuddZddSymmSifting_up(table, x, x_low, initial_size);\n\tif (move_up == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n\n\tif (move_up == NULL ||\n\t    table->subtableZ[move_up->x].next != move_up->x) {\n\t    /* symmetry detected may have to make another complete\n\t       pass */\n\t    if (move_up != NULL) {\n\t\tx = move_up->x;\n\t    }\n\t    else {\n\t\twhile ((unsigned) x < table->subtableZ[x].next)\n\t\t    x = table->subtableZ[x].next;\n\t    }\n            i = table->subtableZ[x].next;\n            final_group_size = x - i + 1;\n\n            if (init_group_size == final_group_size) {\n\t\t/* No new symmetry groups detected,\n\t\t   return to best position */\n                result = cuddZddSymmSiftingBackward(table, move_up,\n\t\t    initial_size);\n            }\n\t    else {\n\t\twhile (move_down != NULL) {\n\t\t    move = move_down->next;\n\t\t    cuddDeallocMove(table, move_down);\n\t\t    move_down = move;\n\t\t}\n\t\tinitial_size = table->keysZ;\n\t\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t\t    initial_size);\n\t\tresult = cuddZddSymmSiftingBackward(table, move_down,\n\t\t    initial_size);\n\t    }\n\t}\n\telse {\n\t    result = cuddZddSymmSiftingBackward(table, move_up,\n\t\tinitial_size);\n\t    /* move backward and stop at best position */\n\t}\n\tif (!result)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n    }\n    else { /* moving up first:shorter */\n\t/* Find top of x's symmetry group */\n\tx = table->subtableZ[x].next;\n\n\tmove_up = cuddZddSymmSifting_up(table, x, x_low, initial_size);\n\t/* after that point x --> x_high, unless early term */\n\tif (move_up == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n\n\tif (move_up != NULL) {\n\t    x = move_up->x;\n\t}\n\telse {\n\t    while ((unsigned) x < table->subtableZ[x].next)\n\t\tx = table->subtableZ[x].next;\n\t}\n        i = table->subtableZ[x].next;\n        init_group_size = x - i + 1;\n\n\tmove_down = cuddZddSymmSifting_down(table, x, x_high,\n\t    initial_size);\n\tif (move_down == ZDD_MV_OOM)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n\n\tif (move_down == NULL ||\n\t    table->subtableZ[move_down->y].next != move_down->y) {\n\t    /* symmetry detected may have to make another complete\n\t       pass */\n            if (move_down != NULL) {\n\t\tx = move_down->y;\n\t    }\n\t    else {\n\t\twhile ((unsigned) x < table->subtableZ[x].next)\n\t\t    x = table->subtableZ[x].next;\n\t\tx = table->subtableZ[x].next;\n\t    }\n            i = x;\n            while ((unsigned) i < table->subtableZ[i].next) {\n                i = table->subtableZ[i].next;\n            }\n\t    final_group_size = i - x + 1;\n\n            if (init_group_size == final_group_size) {\n\t\t/* No new symmetries detected,\n\t\t   go back to best position */\n                result = cuddZddSymmSiftingBackward(table, move_down,\n\t\t    initial_size);\n            }\n\t    else {\n\t\twhile (move_up != NULL) {\n\t\t    move = move_up->next;\n\t\t    cuddDeallocMove(table, move_up);\n\t\t    move_up = move;\n\t\t}\n\t\tinitial_size = table->keysZ;\n\t\tmove_up = cuddZddSymmSifting_up(table, x, x_low,\n\t\t    initial_size);\n\t\tresult = cuddZddSymmSiftingBackward(table, move_up,\n\t\t    initial_size);\n\t    }\n\t}\n\telse {\n\t    result = cuddZddSymmSiftingBackward(table, move_down,\n\t\tinitial_size);\n\t    /* move backward and stop at best position */\n\t}\n\tif (!result)\n\t    goto cuddZddSymmSiftingConvAuxOutOfMem;\n    }\n\n    while (move_down != NULL) {\n\tmove = move_down->next;\n\tcuddDeallocMove(table, move_down);\n\tmove_down = move;\n    }\n    while (move_up != NULL) {\n\tmove = move_up->next;\n\tcuddDeallocMove(table, move_up);\n\tmove_up = move;\n    }\n\n    return(1);\n\ncuddZddSymmSiftingConvAuxOutOfMem:\n    if (move_down != ZDD_MV_OOM) {\n\twhile (move_down != NULL) {\n\t    move = move_down->next;\n\t    cuddDeallocMove(table, move_down);\n\t    move_down = move;\n\t}\n    }\n    if (move_up != ZDD_MV_OOM) {\n\twhile (move_up != NULL) {\n\t    move = move_up->next;\n\t    cuddDeallocMove(table, move_up);\n\t    move_up = move;\n\t}\n    }\n\n    return(0);\n\n} /* end of cuddZddSymmSiftingConvAux */\n\n\n/**\n  @brief Moves x up until either it reaches the bound (x_low) or\n  the size of the %ZDD heap increases too much.\n\n  @details Assumes that x is the top of a symmetry group.  Checks x\n  for symmetry to the adjacent variables. If symmetry is found, the\n  symmetry group of x is merged with the symmetry group of the other\n  variable.\n\n  @return the set of moves in case of success; ZDD_MV_OOM if memory is\n  full.\n\n  @sideeffect None\n\n*/\nstatic Move *\ncuddZddSymmSifting_up(\n  DdManager * table,\n  int  x,\n  int  x_low,\n  int  initial_size)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\ty;\n    int\t\tsize;\n    int\t\tlimit_size = initial_size;\n    int\t\ti, gytop;\n\n    moves = NULL;\n    y = cuddZddNextLow(table, x);\n    while (y >= x_low) {\n\tgytop = table->subtableZ[y].next;\n\tif (cuddZddSymmCheck(table, y, x)) {\n\t    /* Symmetry found, attach symm groups */\n\t    table->subtableZ[y].next = x;\n\t    i = table->subtableZ[x].next;\n\t    while (table->subtableZ[i].next != (unsigned) x)\n\t\ti = table->subtableZ[i].next;\n\t    table->subtableZ[i].next = gytop;\n\t}\n\telse if ((table->subtableZ[x].next == (unsigned) x) &&\n\t    (table->subtableZ[y].next == (unsigned) y)) {\n\t    /* x and y have self symmetry */\n\t    size = cuddZddSwapInPlace(table, y, x);\n\t    if (size == 0)\n\t\tgoto cuddZddSymmSifting_upOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL)\n\t\tgoto cuddZddSymmSifting_upOutOfMem;\n\t    move->x = y;\n\t    move->y = x;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    if ((double)size >\n\t\t(double)limit_size * table->maxGrowth)\n\t\treturn(moves);\n\t    if (size < limit_size)\n\t\tlimit_size = size;\n\t}\n\telse { /* Group move */\n\t    size = zdd_group_move(table, y, x, &moves);\n\t    if ((double)size >\n\t\t(double)limit_size * table->maxGrowth)\n\t\treturn(moves);\n\t    if (size < limit_size)\n\t\tlimit_size = size;\n\t}\n\tx = gytop;\n\ty = cuddZddNextLow(table, x);\n    }\n\n    return(moves);\n\ncuddZddSymmSifting_upOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(ZDD_MV_OOM);\n\n} /* end of cuddZddSymmSifting_up */\n\n\n/**\n  @brief Moves x down until either it reaches the bound (x_high) or\n  the size of the %ZDD heap increases too much.\n\n  @details Assumes that x is the bottom of a symmetry group. Checks x\n  for symmetry to the adjacent variables. If symmetry is found, the\n  symmetry group of x is merged with the symmetry group of the other\n  variable.\n\n  @return the set of moves in case of success; ZDD_MV_OOM if memory is\n  full.\n\n  @sideeffect None\n\n*/\nstatic Move *\ncuddZddSymmSifting_down(\n  DdManager * table,\n  int  x,\n  int  x_high,\n  int  initial_size)\n{\n    Move\t*moves;\n    Move\t*move;\n    int\t\ty;\n    int\t\tsize;\n    int\t\tlimit_size = initial_size;\n    int\t\ti, gxtop, gybot;\n\n    moves = NULL;\n    y = cuddZddNextHigh(table, x);\n    while (y <= x_high) {\n\tgybot = table->subtableZ[y].next;\n\twhile (table->subtableZ[gybot].next != (unsigned) y)\n\t    gybot = table->subtableZ[gybot].next;\n\tif (cuddZddSymmCheck(table, x, y)) {\n\t    /* Symmetry found, attach symm groups */\n\t    gxtop = table->subtableZ[x].next;\n\t    table->subtableZ[x].next = y;\n\t    i = table->subtableZ[y].next;\n\t    while (table->subtableZ[i].next != (unsigned) y)\n\t\ti = table->subtableZ[i].next;\n\t    table->subtableZ[i].next = gxtop;\n\t}\n\telse if ((table->subtableZ[x].next == (unsigned) x) &&\n\t    (table->subtableZ[y].next == (unsigned) y)) {\n\t    /* x and y have self symmetry */\n\t    size = cuddZddSwapInPlace(table, x, y);\n\t    if (size == 0)\n\t\tgoto cuddZddSymmSifting_downOutOfMem;\n\t    move = (Move *)cuddDynamicAllocNode(table);\n\t    if (move == NULL)\n\t\tgoto cuddZddSymmSifting_downOutOfMem;\n\t    move->x = x;\n\t    move->y = y;\n\t    move->size = size;\n\t    move->next = moves;\n\t    moves = move;\n\t    if ((double)size >\n\t\t(double)limit_size * table->maxGrowth)\n\t\treturn(moves);\n\t    if (size < limit_size)\n\t\tlimit_size = size;\n\t}\n\telse { /* Group move */\n\t    size = zdd_group_move(table, x, y, &moves);\n\t    if ((double)size >\n\t\t(double)limit_size * table->maxGrowth)\n\t\treturn(moves);\n\t    if (size < limit_size)\n\t\tlimit_size = size;\n\t}\n\tx = gybot;\n\ty = cuddZddNextHigh(table, x);\n    }\n\n    return(moves);\n\ncuddZddSymmSifting_downOutOfMem:\n    while (moves != NULL) {\n\tmove = moves->next;\n\tcuddDeallocMove(table, moves);\n\tmoves = move;\n    }\n    return(ZDD_MV_OOM);\n\n} /* end of cuddZddSymmSifting_down */\n\n\n/**\n  @brief Given a set of moves, returns the %ZDD heap to the position\n  giving the minimum size.\n\n  @details In case of ties, returns to the closest position giving the\n  minimum size.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ncuddZddSymmSiftingBackward(\n  DdManager * table,\n  Move * moves,\n  int  size)\n{\n    int\t\ti;\n    int\t\ti_best;\n    Move\t*move;\n    int\t\tres;\n\n    i_best = -1;\n    for (move = moves, i = 0; move != NULL; move = move->next, i++) {\n\tif (move->size < size) {\n\t    i_best = i;\n\t    size = move->size;\n\t}\n    }\n\n    for (move = moves, i = 0; move != NULL; move = move->next, i++) {\n\tif (i == i_best) break;\n\tif ((table->subtableZ[move->x].next == move->x) &&\n\t    (table->subtableZ[move->y].next == move->y)) {\n\t    res = cuddZddSwapInPlace(table, move->x, move->y);\n\t    if (!res) return(0);\n\t}\n\telse { /* Group move necessary */\n\t    res = zdd_group_move_backward(table, move->x, move->y);\n\t}\n\tif (i_best == -1 && res == size)\n\t    break;\n    }\n\n    return(1);\n\n} /* end of cuddZddSymmSiftingBackward */\n\n\n/**\n  @brief Swaps two groups.\n\n  @details x is assumed to be the bottom variable of the first\n  group. y is assumed to be the top variable of the second group.\n  Updates the list of moves.\n\n  @return the number of keys in the table if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzdd_group_move(\n  DdManager * table,\n  int  x,\n  int  y,\n  Move ** moves)\n{\n    Move\t*move;\n    int\t\tsize;\n    int\t\ti, temp, gxtop, gxbot, gybot, yprev;\n    int\t\tswapx = 0, swapy = 0;\n\n#ifdef DD_DEBUG\n    assert(x < y);\t/* we assume that x < y */\n#endif\n    /* Find top and bottom for the two groups. */\n    gxtop = table->subtableZ[x].next;\n    gxbot = x;\n    gybot = table->subtableZ[y].next;\n    while (table->subtableZ[gybot].next != (unsigned) y)\n\tgybot = table->subtableZ[gybot].next;\n    yprev = gybot;\n\n    while (x <= y) {\n\twhile (y > gxtop) {\n\t    /* Set correct symmetries. */\n\t    temp = table->subtableZ[x].next;\n\t    if (temp == x)\n\t\ttemp = y;\n\t    i = gxtop;\n\t    for (;;) {\n\t\tif (table->subtableZ[i].next == (unsigned) x) {\n\t\t    table->subtableZ[i].next = y;\n\t\t    break;\n\t\t} else {\n\t\t    i = table->subtableZ[i].next;\n\t\t}\n\t    }\n\t    if (table->subtableZ[y].next != (unsigned) y) {\n\t\ttable->subtableZ[x].next = table->subtableZ[y].next;\n\t    } else {\n\t\ttable->subtableZ[x].next = x;\n\t    }\n\n\t    if (yprev != y) {\n\t\ttable->subtableZ[yprev].next = x;\n\t    } else {\n\t\typrev = x;\n\t    }\n\t    table->subtableZ[y].next = temp;\n\n\t    size = cuddZddSwapInPlace(table, x, y);\n\t    if (size == 0)\n\t\tgoto zdd_group_moveOutOfMem;\n            swapx = x;\n\t    swapy = y;\n\t    y = x;\n\t    x--;\n\t} /* while y > gxtop */\n\n\t/* Trying to find the next y. */\n\tif (table->subtableZ[y].next > (unsigned) y) {\n\t    y = table->subtableZ[y].next;\n\t}\n\n\typrev = gxtop;\n\tgxtop++;\n\tgxbot++;\n\tx = gxbot;\n    } /* while x <= y, end of group movement */\n    move = (Move *)cuddDynamicAllocNode(table);\n    if (move == NULL)\n\tgoto zdd_group_moveOutOfMem;\n    move->x = swapx;\n    move->y = swapy;\n    move->size = table->keysZ;\n    move->next = *moves;\n    *moves = move;\n\n    return(table->keysZ);\n\nzdd_group_moveOutOfMem:\n    while (*moves != NULL) {\n\tmove = (*moves)->next;\n\tcuddDeallocMove(table, *moves);\n\t*moves = move;\n    }\n    return(0);\n\n} /* end of zdd_group_move */\n\n\n/**\n  @brief Undoes the swap of two groups.\n\n  @details x is assumed to be the bottom variable of the first\n  group. y is assumed to be the top variable of the second group.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzdd_group_move_backward(\n  DdManager * table,\n  int  x,\n  int  y)\n{\n    int\t       size = table->keysZ;\n    int        i, temp, gxtop, gxbot, gybot, yprev;\n\n#ifdef DD_DEBUG\n    assert(x < y);\t/* we assume that x < y */\n#endif\n    /* Find top and bottom of the two groups. */\n    gxtop = table->subtableZ[x].next;\n    gxbot = x;\n    gybot = table->subtableZ[y].next;\n    while (table->subtableZ[gybot].next != (unsigned) y)\n\tgybot = table->subtableZ[gybot].next;\n    yprev = gybot;\n\n    while (x <= y) {\n\twhile (y > gxtop) {\n\t    /* Set correct symmetries. */\n\t    temp = table->subtableZ[x].next;\n\t    if (temp == x)\n\t\ttemp = y;\n\t    i = gxtop;\n\t    for (;;) {\n\t\tif (table->subtableZ[i].next == (unsigned) x) {\n\t\t    table->subtableZ[i].next = y;\n\t\t    break;\n\t\t} else {\n\t\t    i = table->subtableZ[i].next;\n\t\t}\n\t    }\n\t    if (table->subtableZ[y].next != (unsigned) y) {\n\t\ttable->subtableZ[x].next = table->subtableZ[y].next;\n\t    } else {\n\t\ttable->subtableZ[x].next = x;\n\t    }\n\n\t    if (yprev != y) {\n\t\ttable->subtableZ[yprev].next = x;\n\t    } else {\n\t\typrev = x;\n\t    }\n\t    table->subtableZ[y].next = temp;\n\n\t    size = cuddZddSwapInPlace(table, x, y);\n\t    if (size == 0)\n\t\treturn(0);\n\t    y = x;\n\t    x--;\n\t} /* while y > gxtop */\n\n\t/* Trying to find the next y. */\n\tif (table->subtableZ[y].next > (unsigned) y) {\n\t    y = table->subtableZ[y].next;\n\t}\n\n\typrev = gxtop;\n\tgxtop++;\n\tgxbot++;\n\tx = gxbot;\n    } /* while x <= y, end of group movement backward */\n\n    return(size);\n\n} /* end of zdd_group_move_backward */\n\n\n/**\n  @brief Counts numbers of symmetric variables and symmetry groups.\n\n  @sideeffect None\n\n*/\nstatic void\ncuddZddSymmSummary(\n  DdManager * table,\n  int  lower,\n  int  upper,\n  int * symvars,\n  int * symgroups)\n{\n    int i,x,gbot;\n    int TotalSymm = 0;\n    int TotalSymmGroups = 0;\n\n    for (i = lower; i <= upper; i++) {\n\tif (table->subtableZ[i].next != (unsigned) i) {\n\t    TotalSymmGroups++;\n\t    x = i;\n\t    do {\n\t\tTotalSymm++;\n\t\tgbot = x;\n\t\tx = table->subtableZ[x].next;\n\t    } while (x != i);\n#ifdef DD_DEBUG\n\t    assert(table->subtableZ[gbot].next == (unsigned) i);\n#endif\n\t    i = gbot;\n\t}\n    }\n    *symvars = TotalSymm;\n    *symgroups = TotalSymmGroups;\n\n    return;\n\n} /* end of cuddZddSymmSummary */\n\n"
  },
  {
    "path": "cudd/cudd/cuddZddUtil.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief Utility functions for ZDDs.\n\n  @author Hyong-Kyoon Shin, In-Ho Moon, Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int zp2 (DdManager *zdd, DdNode *f, st_table *t);\nstatic void zdd_print_minterm_aux (DdManager *zdd, DdNode *node, int level, int *list);\nstatic void zddPrintCoverAux (DdManager *zdd, DdNode *node, int level, int *list);\nstatic void zddSupportStep(DdNode * f, int * support);\nstatic void zddClearFlag(DdNode * f);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints a disjoint sum of product form for a %ZDD.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddPrintDebug Cudd_zddPrintCover\n\n*/\nint\nCudd_zddPrintMinterm(\n  DdManager * zdd,\n  DdNode * node)\n{\n    int\t\ti, size;\n    int\t\t*list;\n\n    size = (int)zdd->sizeZ;\n    list = ALLOC(int, size);\n    if (list == NULL) {\n\tzdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (i = 0; i < size; i++) list[i] = 3; /* bogus value should disappear */\n    zdd_print_minterm_aux(zdd, node, 0, list);\n    FREE(list);\n    return(1);\n\n} /* end of Cudd_zddPrintMinterm */\n\n\n/**\n  @brief Prints a sum of products from a %ZDD representing a cover.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddPrintMinterm\n\n*/\nint\nCudd_zddPrintCover(\n  DdManager * zdd,\n  DdNode * node)\n{\n    int\t\ti, size;\n    int\t\t*list;\n\n    size = (int)zdd->sizeZ;\n    if (size % 2 != 0) return(0); /* number of variables should be even */\n    list = ALLOC(int, size);\n    if (list == NULL) {\n\tzdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(0);\n    }\n    for (i = 0; i < size; i++) list[i] = 3; /* bogus value should disappear */\n    zddPrintCoverAux(zdd, node, 0, list);\n    FREE(list);\n    return(1);\n\n} /* end of Cudd_zddPrintCover */\n\n\n/**\n  @brief Prints to the standard output a %ZDD and its statistics.\n\n  @details The statistics include the number of nodes and the number of\n  minterms.  (The number of minterms is also the number of combinations\n  in the set.)  The statistics are printed if pr &gt; 0.  Specifically:\n  <ul>\n  <li> pr = 0 : prints nothing\n  <li> pr = 1 : prints counts of nodes and minterms\n  <li> pr = 2 : prints counts + disjoint sum of products\n  <li> pr = 3 : prints counts + list of nodes\n  <li> pr &gt; 3 : prints counts + disjoint sum of products + list of nodes\n  </ul>\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nCudd_zddPrintDebug(\n  DdManager * zdd,\n  DdNode * f,\n  int  n,\n  int  pr)\n{\n    DdNode\t*empty = DD_ZERO(zdd);\n    int\t\tnodes;\n    double\tminterms;\n    int\t\tretval = 1;\n\n    if (f == empty && pr > 0) {\n\t(void) fprintf(zdd->out,\": is the empty ZDD\\n\");\n\t(void) fflush(zdd->out);\n\treturn(1);\n    }\n\n    if (pr > 0) {\n\tnodes = Cudd_zddDagSize(f);\n\tif (nodes == CUDD_OUT_OF_MEM) retval = 0;\n\tminterms = Cudd_zddCountMinterm(zdd, f, n);\n\tif (minterms == (double)CUDD_OUT_OF_MEM) retval = 0;\n\t(void) fprintf(zdd->out,\": %d nodes %g minterms\\n\",\n\t\t       nodes, minterms);\n\tif (pr > 2)\n\t    if (!cuddZddP(zdd, f)) retval = 0;\n\tif (pr == 2 || pr > 3) {\n\t    if (!Cudd_zddPrintMinterm(zdd, f)) retval = 0;\n\t    (void) fprintf(zdd->out,\"\\n\");\n\t}\n\t(void) fflush(zdd->out);\n    }\n    return(retval);\n\n} /* end of Cudd_zddPrintDebug */\n\n\n\n/**\n  @brief Finds the first path of a %ZDD.\n\n  @details Defines an iterator on the paths of a %ZDD and finds its first\n  path.<p>\n  A path is represented as an array of literals, which are integers in\n  {0, 1, 2}; 0 represents an else arc out of a node, 1 represents a then arc\n  out of a node, and 2 stands for the absence of a node.\n  The size of the array equals the number of variables in the manager at\n  the time Cudd_zddFirstCube is called.<p>\n  The paths that end in the empty terminal are not enumerated.\n\n  @return a generator that contains the information necessary to\n  continue the enumeration if successful; NULL otherwise.\n\n  @sideeffect The first path is returned as a side effect.\n\n  @see Cudd_zddForeachPath Cudd_zddNextPath Cudd_GenFree\n  Cudd_IsGenEmpty\n\n*/\nDdGen *\nCudd_zddFirstPath(\n  DdManager * zdd,\n  DdNode * f,\n  int ** path)\n{\n    DdGen *gen;\n    DdNode *top, *next, *prev;\n    int i;\n    int nvars;\n\n    /* Sanity Check. */\n    if (zdd == NULL || f == NULL) return(NULL);\n\n    /* Allocate generator an initialize it. */\n    gen = ALLOC(DdGen,1);\n    if (gen == NULL) {\n\tzdd->errorCode = CUDD_MEMORY_OUT;\n\treturn(NULL);\n    }\n\n    gen->manager = zdd;\n    gen->type = CUDD_GEN_ZDD_PATHS;\n    gen->status = CUDD_GEN_EMPTY;\n    gen->gen.cubes.cube = NULL;\n    gen->gen.cubes.value = DD_ZERO_VAL;\n    gen->stack.sp = 0;\n    gen->stack.stack = NULL;\n    gen->node = NULL;\n\n    nvars = zdd->sizeZ;\n    gen->gen.cubes.cube = ALLOC(int,nvars);\n    if (gen->gen.cubes.cube == NULL) {\n\tzdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(gen);\n\treturn(NULL);\n    }\n    for (i = 0; i < nvars; i++) gen->gen.cubes.cube[i] = 2;\n\n    /* The maximum stack depth is one plus the number of variables.\n    ** because a path may have nodes at all levels, including the\n    ** constant level.\n    */\n    gen->stack.stack = ALLOC(DdNodePtr, nvars+1);\n    if (gen->stack.stack == NULL) {\n\tzdd->errorCode = CUDD_MEMORY_OUT;\n\tFREE(gen->gen.cubes.cube);\n\tFREE(gen);\n\treturn(NULL);\n    }\n    for (i = 0; i <= nvars; i++) gen->stack.stack[i] = NULL;\n\n    /* Find the first path of the ZDD. */\n    gen->stack.stack[gen->stack.sp] = f; gen->stack.sp++;\n\n    while (1) {\n\ttop = gen->stack.stack[gen->stack.sp-1];\n\tif (!cuddIsConstant(Cudd_Regular(top))) {\n\t    /* Take the else branch first. */\n\t    gen->gen.cubes.cube[Cudd_Regular(top)->index] = 0;\n\t    next = cuddE(Cudd_Regular(top));\n\t    gen->stack.stack[gen->stack.sp] = Cudd_Not(next); gen->stack.sp++;\n\t} else if (Cudd_Regular(top) == DD_ZERO(zdd)) {\n\t    /* Backtrack. */\n\t    while (1) {\n\t\tif (gen->stack.sp == 1) {\n\t\t    /* The current node has no predecessor. */\n\t\t    gen->status = CUDD_GEN_EMPTY;\n\t\t    gen->stack.sp--;\n\t\t    goto done;\n\t\t}\n\t\tprev = Cudd_Regular(gen->stack.stack[gen->stack.sp-2]);\n\t\tnext = cuddT(prev);\n\t\tif (next != top) { /* follow the then branch next */\n\t\t    gen->gen.cubes.cube[prev->index] = 1;\n\t\t    gen->stack.stack[gen->stack.sp-1] = next;\n\t\t    break;\n\t\t}\n\t\t/* Pop the stack and try again. */\n\t\tgen->gen.cubes.cube[prev->index] = 2;\n\t\tgen->stack.sp--;\n\t\ttop = gen->stack.stack[gen->stack.sp-1];\n\t    }\n\t} else {\n\t    gen->status = CUDD_GEN_NONEMPTY;\n\t    gen->gen.cubes.value = cuddV(Cudd_Regular(top));\n\t    goto done;\n\t}\n    }\n\ndone:\n    *path = gen->gen.cubes.cube;\n    return(gen);\n\n} /* end of Cudd_zddFirstPath */\n\n\n/**\n  @brief Generates the next path of a %ZDD.\n\n  @details Generates the next path of a %ZDD onset, using generator\n  gen.\n\n  @return 0 if the enumeration is completed; 1 otherwise.\n\n  @sideeffect The path is returned as a side effect. The generator is\n  modified.\n\n  @see Cudd_zddForeachPath Cudd_zddFirstPath Cudd_GenFree\n  Cudd_IsGenEmpty\n\n*/\nint\nCudd_zddNextPath(\n  DdGen * gen,\n  int ** path)\n{\n    DdNode *top, *next, *prev;\n    DdManager *zdd = gen->manager;\n\n    /* Backtrack from previously reached terminal node. */\n    while (1) {\n\tif (gen->stack.sp == 1) {\n\t    /* The current node has no predecessor. */\n\t    gen->status = CUDD_GEN_EMPTY;\n\t    gen->stack.sp--;\n\t    goto done;\n\t}\n\ttop = gen->stack.stack[gen->stack.sp-1];\n\tprev = Cudd_Regular(gen->stack.stack[gen->stack.sp-2]);\n\tnext = cuddT(prev);\n\tif (next != top) { /* follow the then branch next */\n\t    gen->gen.cubes.cube[prev->index] = 1;\n\t    gen->stack.stack[gen->stack.sp-1] = next;\n\t    break;\n\t}\n\t/* Pop the stack and try again. */\n\tgen->gen.cubes.cube[prev->index] = 2;\n\tgen->stack.sp--;\n    }\n\n    while (1) {\n\ttop = gen->stack.stack[gen->stack.sp-1];\n\tif (!cuddIsConstant(Cudd_Regular(top))) {\n\t    /* Take the else branch first. */\n\t    gen->gen.cubes.cube[Cudd_Regular(top)->index] = 0;\n\t    next = cuddE(Cudd_Regular(top));\n\t    gen->stack.stack[gen->stack.sp] = Cudd_Not(next); gen->stack.sp++;\n\t} else if (Cudd_Regular(top) == DD_ZERO(zdd)) {\n\t    /* Backtrack. */\n\t    while (1) {\n\t\tif (gen->stack.sp == 1) {\n\t\t    /* The current node has no predecessor. */\n\t\t    gen->status = CUDD_GEN_EMPTY;\n\t\t    gen->stack.sp--;\n\t\t    goto done;\n\t\t}\n\t\tprev = Cudd_Regular(gen->stack.stack[gen->stack.sp-2]);\n\t\tnext = cuddT(prev);\n\t\tif (next != top) { /* follow the then branch next */\n\t\t    gen->gen.cubes.cube[prev->index] = 1;\n\t\t    gen->stack.stack[gen->stack.sp-1] = next;\n\t\t    break;\n\t\t}\n\t\t/* Pop the stack and try again. */\n\t\tgen->gen.cubes.cube[prev->index] = 2;\n\t\tgen->stack.sp--;\n\t\ttop = gen->stack.stack[gen->stack.sp-1];\n\t    }\n\t} else {\n\t    gen->status = CUDD_GEN_NONEMPTY;\n\t    gen->gen.cubes.value = cuddV(Cudd_Regular(top));\n\t    goto done;\n\t}\n    }\n\ndone:\n    if (gen->status == CUDD_GEN_EMPTY) return(0);\n    *path = gen->gen.cubes.cube;\n    return(1);\n\n} /* end of Cudd_zddNextPath */\n\n\n/**\n  @brief Converts a path of a %ZDD representing a cover to a string.\n\n  @details The string represents an implicant of the cover.  The path\n  is typically produced by Cudd_zddForeachPath.  If the str input is\n  NULL, it allocates a new string.  The string passed to this function\n  must have enough room for all variables and for the terminator.\n\n  @return a pointer to the string if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddForeachPath\n\n*/\nchar *\nCudd_zddCoverPathToString(\n  DdManager *zdd\t\t/**< %DD manager */,\n  int *path\t\t\t/**< path of %ZDD representing a cover */,\n  char *str\t\t\t/**< pointer to string to use if != NULL */\n  )\n{\n    int nvars = zdd->sizeZ;\n    int i;\n    char *res;\n\n    if (nvars & 1) return(NULL);\n    nvars >>= 1;\n    if (str == NULL) {\n\tres = ALLOC(char, nvars+1);\n\tif (res == NULL) return(NULL);\n    } else {\n\tres = str;\n    }\n    for (i = 0; i < nvars; i++) {\n\tint v = (path[2*i] << 2) | path[2*i+1];\n\tswitch (v) {\n\tcase 0:\n\tcase 2:\n\tcase 8:\n\tcase 10:\n\t    res[i] = '-';\n\t    break;\n\tcase 1:\n\tcase 9:\n\t    res[i] = '0';\n\t    break;\n\tcase 4:\n\tcase 6:\n\t    res[i] = '1';\n\t    break;\n\tdefault:\n\t    res[i] = '?';\n\t}\n    }\n    res[nvars] = 0;\n\n    return(res);\n\n} /* end of Cudd_zddCoverPathToString */\n\n\n/**\n  @brief Finds the variables on which a %ZDD depends.\n\n  @return a %BDD consisting of the product of the variables if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Cudd_Support\n\n*/\nDdNode *\nCudd_zddSupport(\n  DdManager * dd /**< manager */,\n  DdNode * f /**< %ZDD whose support is sought */)\n{\n    int *support;\n    DdNode *res, *tmp, *var;\n    int i,j;\n    int size;\n\n    /* Allocate and initialize support array for ddSupportStep. */\n    size = ddMax(dd->size, dd->sizeZ);\n    support = ALLOC(int,size);\n    if (support == NULL) {\n        dd->errorCode = CUDD_MEMORY_OUT;\n        return(NULL);\n    }\n    for (i = 0; i < size; i++) {\n        support[i] = 0;\n    }\n\n    /* Compute support and clean up markers. */\n    zddSupportStep(Cudd_Regular(f),support);\n    zddClearFlag(Cudd_Regular(f));\n\n    /* Transform support from array to cube. */\n    do {\n        dd->reordered = 0;\n        res = DD_ONE(dd);\n        cuddRef(res);\n        for (j = size - 1; j >= 0; j--) { /* for each level bottom-up */\n            i = (j >= dd->size) ? j : dd->invperm[j];\n            if (support[i] == 1) {\n                /* The following call to cuddUniqueInter is guaranteed\n                ** not to trigger reordering because the node we look up\n                ** already exists. */\n                var = cuddUniqueInter(dd,i,dd->one,Cudd_Not(dd->one));\n                cuddRef(var);\n                tmp = cuddBddAndRecur(dd,res,var);\n                if (tmp == NULL) {\n                    Cudd_RecursiveDeref(dd,res);\n                    Cudd_RecursiveDeref(dd,var);\n                    res = NULL;\n                    break;\n                }\n                cuddRef(tmp);\n                Cudd_RecursiveDeref(dd,res);\n                Cudd_RecursiveDeref(dd,var);\n                res = tmp;\n            }\n        }\n    } while (dd->reordered == 1);\n\n    FREE(support);\n    if (res != NULL) cuddDeref(res);\n    if (dd->errorCode == CUDD_TIMEOUT_EXPIRED && dd->timeoutHandler) {\n        dd->timeoutHandler(dd, dd->tohArg);\n    }\n    return(res);\n\n} /* end of Cudd_zddSupport */\n\n\n/**\n  @brief Writes a dot file representing the argument ZDDs.\n\n  @details Writes a file representing the argument ZDDs in a format\n  suitable for the graph drawing program dot.\n  Cudd_zddDumpDot does not close the file: This is the caller\n  responsibility. Cudd_zddDumpDot uses a minimal unique subset of the\n  hexadecimal address of a node as name for it.\n  If the argument inames is non-null, it is assumed to hold the pointers\n  to the names of the inputs. Similarly for onames.\n  Cudd_zddDumpDot uses the following convention to draw arcs:\n    <ul>\n    <li> solid line: THEN arcs;\n    <li> dashed line: ELSE arcs.\n    </ul>\n  The dot options are chosen so that the drawing fits on a letter-size\n  sheet.\n  \n  @return 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n  system full).\n\n  @sideeffect None\n\n  @see Cudd_DumpDot Cudd_zddPrintDebug\n\n*/\nint\nCudd_zddDumpDot(\n  DdManager * dd /**< manager */,\n  int  n /**< number of output nodes to be dumped */,\n  DdNode ** f /**< array of output nodes to be dumped */,\n  char const * const * inames /**< array of input names (or NULL) */,\n  char const * const * onames /**< array of output names (or NULL) */,\n  FILE * fp /**< pointer to the dump file */)\n{\n    DdNode\t*support = NULL;\n    DdNode\t*scan;\n    int\t\t*sorted = NULL;\n    int\t\tnvars = dd->sizeZ;\n    st_table\t*visited = NULL;\n    st_generator *gen;\n    int\t\tretval;\n    int\t\ti, j;\n    int\t\tslots;\n    DdNodePtr\t*nodelist;\n    ptruint\trefAddr, diff, mask = 0;\n\n    /* Build a bit array with the support of f. */\n    sorted = ALLOC(int,nvars);\n    if (sorted == NULL) {\n\tdd->errorCode = CUDD_MEMORY_OUT;\n\tgoto failure;\n    }\n    for (i = 0; i < nvars; i++) sorted[i] = 0;\n\n    /* Take the union of the supports of each output function. */\n    for (i = 0; i < n; i++) {\n\tsupport = Cudd_zddSupport(dd,f[i]);\n\tif (support == NULL) goto failure;\n\tcuddRef(support);\n\tscan = support;\n\twhile (!cuddIsConstant(scan)) {\n\t    sorted[scan->index] = 1;\n\t    scan = cuddT(scan);\n\t}\n\tCudd_RecursiveDeref(dd,support);\n    }\n    support = NULL; /* so that we do not try to free it in case of failure */\n\n    /* Initialize symbol table for visited nodes. */\n    visited = st_init_table(st_ptrcmp, st_ptrhash);\n    if (visited == NULL) goto failure;\n\n    /* Collect all the nodes of this DD in the symbol table. */\n    for (i = 0; i < n; i++) {\n\tretval = cuddCollectNodes(f[i],visited);\n\tif (retval == 0) goto failure;\n    }\n\n    /* Find how many most significant hex digits are identical\n    ** in the addresses of all the nodes. Build a mask based\n    ** on this knowledge, so that digits that carry no information\n    ** will not be printed. This is done in two steps.\n    **  1. We scan the symbol table to find the bits that differ\n    **     in at least 2 addresses.\n    **  2. We choose one of the possible masks. There are 8 possible\n    **     masks for 32-bit integer, and 16 possible masks for 64-bit\n    **     integers.\n    */\n\n    /* Find the bits that are different. */\n    refAddr = (ptruint) f[0];\n    diff = 0;\n    gen = st_init_gen(visited);\n    while (st_gen(gen, (void **) &scan, NULL)) {\n\tdiff |= refAddr ^ (ptruint) scan;\n    }\n    st_free_gen(gen);\n\n    /* Choose the mask. */\n    for (i = 0; (unsigned) i < 8 * sizeof(ptruint); i += 4) {\n        mask = ((ptruint) 1 << i) - 1;\n\tif (diff <= mask) break;\n    }\n\n    /* Write the header and the global attributes. */\n    retval = fprintf(fp,\"digraph \\\"ZDD\\\" {\\n\");\n    if (retval == EOF) return(0);\n    retval = fprintf(fp,\n\t\"size = \\\"7.5,10\\\"\\ncenter = true;\\nedge [dir = none];\\n\");\n    if (retval == EOF) return(0);\n\n    /* Write the input name subgraph by scanning the support array. */\n    retval = fprintf(fp,\"{ node [shape = plaintext];\\n\");\n    if (retval == EOF) goto failure;\n    retval = fprintf(fp,\"  edge [style = invis];\\n\");\n    if (retval == EOF) goto failure;\n    /* We use a name (\"CONST NODES\") with an embedded blank, because\n    ** it is unlikely to appear as an input name.\n    */\n    retval = fprintf(fp,\"  \\\"CONST NODES\\\" [style = invis];\\n\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < nvars; i++) {\n\tif (sorted[dd->invpermZ[i]]) {\n\t    if (inames == NULL) {\n\t\tretval = fprintf(fp,\"\\\" %d \\\" -> \", dd->invpermZ[i]);\n\t    } else {\n\t\tretval = fprintf(fp,\"\\\" %s \\\" -> \", inames[dd->invpermZ[i]]);\n\t    }\n\t    if (retval == EOF) goto failure;\n\t}\n    }\n    retval = fprintf(fp,\"\\\"CONST NODES\\\"; \\n}\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Write the output node subgraph. */\n    retval = fprintf(fp,\"{ rank = same; node [shape = box]; edge [style = invis];\\n\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < n; i++) {\n\tif (onames == NULL) {\n\t    retval = fprintf(fp,\"\\\"F%d\\\"\", i);\n\t} else {\n\t    retval = fprintf(fp,\"\\\"  %s  \\\"\", onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n\tif (i == n - 1) {\n\t    retval = fprintf(fp,\"; }\\n\");\n\t} else {\n\t    retval = fprintf(fp,\" -> \");\n\t}\n\tif (retval == EOF) goto failure;\n    }\n\n    /* Write rank info: All nodes with the same index have the same rank. */\n    for (i = 0; i < nvars; i++) {\n\tif (sorted[dd->invpermZ[i]]) {\n\t    retval = fprintf(fp,\"{ rank = same; \");\n\t    if (retval == EOF) goto failure;\n\t    if (inames == NULL) {\n\t\tretval = fprintf(fp,\"\\\" %d \\\";\\n\", dd->invpermZ[i]);\n\t    } else {\n\t\tretval = fprintf(fp,\"\\\" %s \\\";\\n\", inames[dd->invpermZ[i]]);\n\t    }\n\t    if (retval == EOF) goto failure;\n\t    nodelist = dd->subtableZ[i].nodelist;\n\t    slots = dd->subtableZ[i].slots;\n\t    for (j = 0; j < slots; j++) {\n\t\tscan = nodelist[j];\n\t\twhile (scan != NULL) {\n\t\t    if (st_is_member(visited,scan)) {\n\t\t\tretval = fprintf(fp,\"\\\"%#\" PRIxPTR \"\\\";\\n\",\n\t\t\t\t\t ((mask & (ptruint) scan) /\n\t\t\t\t\t  sizeof(DdNode)));\n\t\t\tif (retval == EOF) goto failure;\n\t\t    }\n\t\t    scan = scan->next;\n\t\t}\n\t    }\n\t    retval = fprintf(fp,\"}\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n    }\n\n    /* All constants have the same rank. */\n    retval = fprintf(fp,\n\t\"{ rank = same; \\\"CONST NODES\\\";\\n{ node [shape = box]; \");\n    if (retval == EOF) goto failure;\n    nodelist = dd->constants.nodelist;\n    slots = dd->constants.slots;\n    for (j = 0; j < slots; j++) {\n\tscan = nodelist[j];\n\twhile (scan != NULL) {\n\t    if (st_is_member(visited,scan)) {\n\t\tretval = fprintf(fp,\"\\\"%#\" PRIxPTR \"\\\";\\n\",\n\t\t\t\t ((mask & (ptruint) scan) / sizeof(DdNode)));\n\t\tif (retval == EOF) goto failure;\n\t    }\n\t    scan = scan->next;\n\t}\n    }\n    retval = fprintf(fp,\"}\\n}\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Write edge info. */\n    /* Edges from the output nodes. */\n    for (i = 0; i < n; i++) {\n\tif (onames == NULL) {\n\t    retval = fprintf(fp,\"\\\"F%d\\\"\", i);\n\t} else {\n\t    retval = fprintf(fp,\"\\\"  %s  \\\"\", onames[i]);\n\t}\n\tif (retval == EOF) goto failure;\n\tretval = fprintf(fp,\" -> \\\"%#\" PRIxPTR \"\\\" [style = solid];\\n\",\n\t\t\t ((mask & (ptruint) f[i]) / sizeof(DdNode)));\n\tif (retval == EOF) goto failure;\n    }\n\n    /* Edges from internal nodes. */\n    for (i = 0; i < nvars; i++) {\n\tif (sorted[dd->invpermZ[i]]) {\n\t    nodelist = dd->subtableZ[i].nodelist;\n\t    slots = dd->subtableZ[i].slots;\n\t    for (j = 0; j < slots; j++) {\n\t\tscan = nodelist[j];\n\t\twhile (scan != NULL) {\n\t\t    if (st_is_member(visited,scan)) {\n\t\t\tretval = fprintf(fp,\n\t\t\t    \"\\\"%#\" PRIxPTR \"\\\" -> \\\"%#\" PRIxPTR \"\\\";\\n\",\n\t\t\t    ((mask & (ptruint) scan) / sizeof(DdNode)),\n\t\t\t    ((mask & (ptruint) cuddT(scan)) / sizeof(DdNode)));\n\t\t\tif (retval == EOF) goto failure;\n\t\t\tretval = fprintf(fp,\n\t\t\t\t\t \"\\\"%#\" PRIxPTR \"\\\" -> \\\"%#\" PRIxPTR\n                                         \"\\\" [style = dashed];\\n\",\n\t\t\t\t\t ((mask & (ptruint) scan) /\n                                          sizeof(DdNode)),\n\t\t\t\t\t ((mask & (ptruint) cuddE(scan)) /\n                                          sizeof(DdNode)));\n\t\t\tif (retval == EOF) goto failure;\n\t\t    }\n\t\t    scan = scan->next;\n\t\t}\n\t    }\n\t}\n    }\n\n    /* Write constant labels. */\n    nodelist = dd->constants.nodelist;\n    slots = dd->constants.slots;\n    for (j = 0; j < slots; j++) {\n\tscan = nodelist[j];\n\twhile (scan != NULL) {\n\t    if (st_is_member(visited,scan)) {\n\t\tretval = fprintf(fp,\"\\\"%#\" PRIxPTR \"\\\" [label = \\\"%g\\\"];\\n\",\n\t\t\t\t ((mask & (ptruint) scan) / sizeof(DdNode)),\n\t\t\t\t cuddV(scan));\n\t\tif (retval == EOF) goto failure;\n\t    }\n\t    scan = scan->next;\n\t}\n    }\n\n    /* Write trailer and return. */\n    retval = fprintf(fp,\"}\\n\");\n    if (retval == EOF) goto failure;\n\n    st_free_table(visited);\n    FREE(sorted);\n    return(1);\n\nfailure:\n    if (sorted != NULL) FREE(sorted);\n    if (visited != NULL) st_free_table(visited);\n    return(0);\n\n} /* end of Cudd_zddDumpBlif */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints a %ZDD to the standard output. One line per node is\n  printed.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Cudd_zddPrintDebug\n\n*/\nint\ncuddZddP(\n  DdManager * zdd,\n  DdNode * f)\n{\n    int retval;\n    st_table *table = st_init_table(st_ptrcmp, st_ptrhash);\n\n    if (table == NULL) return(0);\n\n    retval = zp2(zdd, f, table);\n    st_free_table(table);\n    (void) fputc('\\n', zdd->out);\n    return(retval);\n\n} /* end of cuddZddP */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Performs the recursive step of cuddZddP.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nzp2(\n  DdManager * zdd,\n  DdNode * f,\n  st_table * t)\n{\n    DdNode\t*n;\n    int\t\tT, E;\n    DdNode\t*base = DD_ONE(zdd);\n\n    if (f == NULL)\n\treturn(0);\n\n    if (Cudd_IsConstantInt(f)) {\n\t(void)fprintf(zdd->out, \"ID = %d\\n\", (f == base));\n\treturn(1);\n    }\n    if (st_is_member(t, f) == 1)\n\treturn(1);\n\n    if (st_insert(t, f, NULL) == ST_OUT_OF_MEM)\n\treturn(0);\n\n    (void) fprintf(zdd->out, \"ID = 0x%\" PRIxPTR \"\\tindex = %u\\tr = %u\\t\",\n\t(ptruint)f / (ptruint) sizeof(DdNode), f->index, f->ref);\n\n    n = cuddT(f);\n    if (Cudd_IsConstantInt(n)) {\n\t(void) fprintf(zdd->out, \"T = %d\\t\\t\", (n == base));\n\tT = 1;\n    } else {\n\t(void) fprintf(zdd->out, \"T = 0x%\" PRIxPTR \"\\t\", (ptruint) n /\n\t\t       (ptruint) sizeof(DdNode));\n\tT = 0;\n    }\n\n    n = cuddE(f);\n    if (Cudd_IsConstantInt(n)) {\n\t(void) fprintf(zdd->out, \"E = %d\\n\", (n == base));\n\tE = 1;\n    } else {\n\t(void) fprintf(zdd->out, \"E = 0x%\" PRIxPTR \"\\n\", (ptruint) n /\n\t\t      (ptruint) sizeof(DdNode));\n\tE = 0;\n    }\n\n    if (E == 0)\n\tif (zp2(zdd, cuddE(f), t) == 0) return(0);\n    if (T == 0)\n\tif (zp2(zdd, cuddT(f), t) == 0) return(0);\n    return(1);\n\n} /* end of zp2 */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddPrintMinterm.\n\n  @sideeffect None\n\n*/\nstatic void\nzdd_print_minterm_aux(\n  DdManager * zdd /* manager */,\n  DdNode * node /* current node */,\n  int  level /* depth in the recursion */,\n  int * list /* current recursion path */)\n{\n    DdNode\t*Nv, *Nnv;\n    int\t\ti, v;\n    DdNode\t*base = DD_ONE(zdd);\n\n    if (Cudd_IsConstantInt(node)) {\n\tif (node == base) {\n\t    /* Check for missing variable. */\n\t    if (level != zdd->sizeZ) {\n\t\tlist[zdd->invpermZ[level]] = 0;\n\t\tzdd_print_minterm_aux(zdd, node, level + 1, list);\n\t\treturn;\n\t    }\n\t    /* Terminal case: Print one cube based on the current recursion\n\t    ** path.\n\t    */\n\t    for (i = 0; i < zdd->sizeZ; i++) {\n\t\tv = list[i];\n\t\tif (v == 0)\n\t\t    (void) fprintf(zdd->out,\"0\");\n\t\telse if (v == 1)\n\t\t    (void) fprintf(zdd->out,\"1\");\n\t\telse if (v == 3)\n\t\t    (void) fprintf(zdd->out,\"@\");\t/* should never happen */\n\t\telse\n\t\t    (void) fprintf(zdd->out,\"-\");\n\t    }\n\t    (void) fprintf(zdd->out,\" 1\\n\");\n\t}\n    } else {\n\t/* Check for missing variable. */\n\tif (level != cuddIZ(zdd,node->index)) {\n\t    list[zdd->invpermZ[level]] = 0;\n\t    zdd_print_minterm_aux(zdd, node, level + 1, list);\n\t    return;\n\t}\n\n\tNnv = cuddE(node);\n\tNv = cuddT(node);\n\tif (Nv == Nnv) {\n\t    list[node->index] = 2;\n\t    zdd_print_minterm_aux(zdd, Nnv, level + 1, list);\n\t    return;\n\t}\n\n\tlist[node->index] = 1;\n\tzdd_print_minterm_aux(zdd, Nv, level + 1, list);\n\tlist[node->index] = 0;\n\tzdd_print_minterm_aux(zdd, Nnv, level + 1, list);\n    }\n    return;\n\n} /* end of zdd_print_minterm_aux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddPrintCover.\n\n  @sideeffect None\n\n*/\nstatic void\nzddPrintCoverAux(\n  DdManager * zdd /* manager */,\n  DdNode * node /* current node */,\n  int  level /* depth in the recursion */,\n  int * list /* current recursion path */)\n{\n    DdNode\t*Nv, *Nnv;\n    int\t\ti, v;\n    DdNode\t*base = DD_ONE(zdd);\n\n    if (Cudd_IsConstantInt(node)) {\n\tif (node == base) {\n\t    /* Check for missing variable. */\n\t    if (level != zdd->sizeZ) {\n\t\tlist[zdd->invpermZ[level]] = 0;\n\t\tzddPrintCoverAux(zdd, node, level + 1, list);\n\t\treturn;\n\t    }\n\t    /* Terminal case: Print one cube based on the current recursion\n\t    ** path.\n\t    */\n\t    for (i = 0; i < zdd->sizeZ; i += 2) {\n\t\tv = list[i] * 4 + list[i+1];\n\t\tif (v == 0)\n\t\t    (void) putc('-',zdd->out);\n\t\telse if (v == 4)\n\t\t    (void) putc('1',zdd->out);\n\t\telse if (v == 1)\n\t\t    (void) putc('0',zdd->out);\n\t\telse\n\t\t    (void) putc('@',zdd->out); /* should never happen */\n\t    }\n\t    (void) fprintf(zdd->out,\" 1\\n\");\n\t}\n    } else {\n\t/* Check for missing variable. */\n\tif (level != cuddIZ(zdd,node->index)) {\n\t    list[zdd->invpermZ[level]] = 0;\n\t    zddPrintCoverAux(zdd, node, level + 1, list);\n\t    return;\n\t}\n\n\tNnv = cuddE(node);\n\tNv = cuddT(node);\n\tif (Nv == Nnv) {\n\t    list[node->index] = 2;\n\t    zddPrintCoverAux(zdd, Nnv, level + 1, list);\n\t    return;\n\t}\n\n\tlist[node->index] = 1;\n\tzddPrintCoverAux(zdd, Nv, level + 1, list);\n\tlist[node->index] = 0;\n\tzddPrintCoverAux(zdd, Nnv, level + 1, list);\n    }\n    return;\n\n} /* end of zddPrintCoverAux */\n\n\n/**\n  @brief Performs the recursive step of Cudd_zddSupport.\n\n  @details Performs a DFS from f. The support is accumulated in supp\n  as a side effect. Uses the LSB of the then pointer as visited flag.\n\n  @sideeffect None\n\n  @see zddClearFlag\n\n*/\nstatic void\nzddSupportStep(\n  DdNode * f,\n  int * support)\n{\n    if (cuddIsConstant(f) || Cudd_IsComplement(f->next)) {\n        return;\n    }\n\n    support[f->index] = 1;\n    zddSupportStep(cuddT(f),support);\n    zddSupportStep(Cudd_Regular(cuddE(f)),support);\n    /* Mark as visited. */\n    f->next = Cudd_Not(f->next);\n    return;\n\n} /* end of zddSupportStep */\n\n\n/**\n  @brief Performs a DFS from f, clearing the LSB of the next\n  pointers.\n\n  @sideeffect None\n\n  @see zddSupportStep\n\n*/\nstatic void\nzddClearFlag(\n  DdNode * f)\n{\n    if (!Cudd_IsComplement(f->next)) {\n        return;\n    }\n    /* Clear visited flag. */\n    f->next = Cudd_Regular(f->next);\n    if (cuddIsConstant(f)) {\n        return;\n    }\n    zddClearFlag(cuddT(f));\n    zddClearFlag(Cudd_Regular(cuddE(f)));\n    return;\n\n} /* end of zddClearFlag */\n\n"
  },
  {
    "path": "cudd/cudd/extra.out",
    "content": "Started CUDD version 3.0.0\n0000 1\n\nPlus infinity is inf\n1111  5\n\nbackground (0) minterms : 0\n1110 1\n110- 1\n10-- 1\n0--- 1\n\nDD_APA_BITS = 32\n000000000000000000001f4a\n1283805 -> 1.2838e+06\n1283815 -> 1.28382e+06\n15983557 -> 1.59836e+07\n1598354 -> 1.59835e+06\n15999999 -> 1.6e+07\nh (dbl) : 1023 nodes 1 leaves 4.49423e+307 minterms\nh (apa) : 1023 nodes 1 leaves 4.49423e+307 minterms\none[2044] (dbl) : 1 nodes 1 leaves inf minterms\none[2044] (apa) : 1 nodes 1 leaves 2.01981e+615 minterms\none[2045] (dbl) : 1 nodes 1 leaves unknown minterms\none[2045] (apa) : 1 nodes 1 leaves 4.03963e+615 minterms\nf: 8191 nodes 1 leaves 531441 minterms\nf has 531441 minterms\nEPD count for f = 5.314410e+05\ng: 8191 nodes 1 leaves 531441 minterms\ng has 531441 minterms\nEPD count for g = 5.314410e+05\ncaught timeout\nso far: 131071 nodes 1 leaves 11019960576 minterms\nf implies 0 clauses\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 0\nArc violation threshold: 0\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 4004\n**** CUDD non-modifiable parameters ****\nMemory in use: 21161448\nPeak number of nodes: 305578\nPeak number of live nodes: 239037\nNumber of BDD variables: 37\nNumber of ZDD variables: 0\nNumber of cache entries: 262144\nNumber of cache look-ups: 466112\nNumber of cache hits: 101229\nNumber of cache insertions: 365030\nNumber of cache collisions: 255308\nNumber of cache deletions: 0\nCache used slots = 41.86% (expected 75.15%)\nSoft limit for cache size: 448512\nNumber of buckets in unique table: 112128\nUsed buckets in unique table: 90.30% (expected 89.69%)\nNumber of BDD and ADD nodes: 304566\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 304525\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 304566\nTotal number of nodes reclaimed: 0\nGarbage collections so far: 0\nTime for garbage collection: 0.00 sec\nReorderings so far: 0\nTime for reordering: 0.00 sec\n"
  },
  {
    "path": "cudd/cudd/r7x8.1.mat",
    "content": "7 9\n0 0 1\n0 1 1\n0 2 1\n0 3 4\n0 4 3\n0 5 3\n0 6 3\n0 8 3\n1 0 4\n1 1 3\n1 2 2\n1 3 4\n1 4 1\n1 5 2\n1 6 4\n1 8 3\n2 0 1\n2 1 1\n2 2 4\n2 4 2\n2 5 3\n2 6 3\n2 8 3\n3 0 2\n3 1 1\n3 3 4\n3 4 4\n3 5 1\n3 8 1\n4 0 2\n4 1 3\n4 2 2\n4 3 4\n4 4 1\n4 5 1\n4 6 2\n4 8 2\n5 0 3\n5 1 3\n5 2 4\n5 3 4\n5 4 1\n5 5 3\n5 6 3\n5 8 4\n6 1 1\n6 2 1\n6 3 4\n6 4 2\n6 5 4\n6 6 4\n6 8 2\n"
  },
  {
    "path": "cudd/cudd/r7x8.1.out",
    "content": "# TestCudd Version #1.0, Release date 3/17/01\n# cudd/testcudd -p 2 ./cudd/r7x8.1.mat\n:name: ./cudd/r7x8.1.mat: 7 rows 9 columns\n:1: M: 63 nodes 5 leaves 52 minterms\n000000--  1\n000001-0  1\n000001-1  4\n000010-0  4\n000010-1  3\n000011-0  2\n000011-1  4\n000100--  3\n000101-0  3\n000110-0  1\n000110-1  2\n000111-0  4\n001000--  1\n001001-0  4\n001010-0  2\n001010-1  1\n001011-1  4\n001100-0  2\n001100-1  3\n001101-0  3\n001110-0  4\n001110-1  1\n0100-0-0  3\n011000-0  3\n011010-0  1\n100000-0  2\n100000-1  3\n100001-0  2\n100001-1  4\n100010--  3\n100011--  4\n100100--  1\n100101-0  2\n100110-0  1\n100110-1  3\n100111-0  3\n101000-1  1\n101001-0  1\n101001-1  4\n101100-0  2\n101100-1  4\n101101-0  4\n110000-0  2\n110010-0  4\n111000-0  2\n\n:2: time to read the matrix = 0.00 sec\n:3: C: 22 nodes 1 leaves 52 minterms\n0000----  1\n0001-0--  1\n0001-1-0  1\n001000--  1\n001001-0  1\n001010--  1\n001011-1  1\n001100--  1\n001101-0  1\n001110--  1\n01-0-0-0  1\n1000----  1\n1001-0--  1\n1001-1-0  1\n101000-1  1\n101001--  1\n101100--  1\n101101-0  1\n1100-0-0  1\n111000-0  1\n\nTesting iterator on cubes:\n000000-- 1\n000001-0 1\n000001-1 4\n000010-0 4\n000010-1 3\n000011-0 2\n000011-1 4\n000100-- 3\n000101-0 3\n000110-0 1\n000110-1 2\n000111-0 4\n001000-- 1\n001001-0 4\n001010-0 2\n001010-1 1\n001011-1 4\n001100-0 2\n001100-1 3\n001101-0 3\n001110-0 4\n001110-1 1\n0100-0-0 3\n011000-0 3\n011010-0 1\n100000-0 2\n100000-1 3\n100001-0 2\n100001-1 4\n100010-- 3\n100011-- 4\n100100-- 1\n100101-0 2\n100110-0 1\n100110-1 3\n100111-0 3\n101000-1 1\n101001-0 1\n101001-1 4\n101100-0 2\n101100-1 4\n101101-0 4\n110000-0 2\n110010-0 4\n111000-0 2\n\nTesting prime expansion of cubes:\n-000---- 1\n-00--0-- 1\n0--0-0-0 1\n--00-0-0 1\n-0-100-- 1\n10-001-- 1\n-00----0 1\n00---0-- 1\n-1-000-0 1\n-0--01-0 1\n-0--00-1 1\n00-01--1 1\n\nTesting iterator on primes (CNF):\n-0-0---- 1\n-0---0-- 1\n0-0-0--- 1\n-0-----0 1\n---0-0-0 1\n0101-1-1 1\n--0-00-1 1\n1-0-10-0 1\n\nCache used slots = 58.40% (expected 58.68%)\nxor1: 14 nodes 1 leaves 28 minterms\n000--1-1  1\n001-11-1  1\n01---0-0  1\n100--1-1  1\n101-00-0  1\n101-01-1  1\n110--0-0  1\n111-00-0  1\n\nChosen minterm for Hamming distance test: : 9 nodes 1 leaves 1 minterms\n11110010  1\n\nMinimum Hamming distance = 1\nycube: 5 nodes 1 leaves 8 minterms\n-0-0-0-0  1\n\nCP: 11 nodes 1 leaves 7 minterms\n00-0-0-0  1\n1000-0-0  1\n101000-1  1\n\n:4: ineq: 10 nodes 1 leaves 42 minterms\n001000--  1\n00101---  1\n1000----  1\n100100--  1\n10011---  1\n101-----  1\n111000--  1\n11101---  1\n\n10------ 1\n-01----- 1\n1-1----- 1\n-0-0---- 1\n1--0---- 1\n-0--10-- 1\n--1010-- 1\n1---10-- 1\n\n:4: ess: 1 nodes 1 leaves 128 minterms\n--------  1\n\n:5: shortP: 7 nodes 1 leaves 2 minterms\n000000--  1\n\n:5b: largest: 4 nodes 1 leaves 16 minterms\n01-1----  1\n\nThe value of M along the chosen shortest path is 1\n:6: shortP: 5 nodes 1 leaves 8 minterms\n0000----  1\n\nSupport of f: : 8 nodes 1 leaves 2 minterms\n111111-1  1\n\nSize of the support of f: 7\nSize of the support of f: 7\nSupport of f and g: : 8 nodes 1 leaves 2 minterms\n111111-1  1\n\nSize of the support of f and g: 7\nSize of the support of f and g: 7\nSupport common to f and g: : 5 nodes 1 leaves 16 minterms\n-1-1-1-1  1\n\nSupport private to f: : 4 nodes 1 leaves 32 minterms\n1-1-1---  1\n\nSupport private to g: : 1 nodes 1 leaves 256 minterms\n--------  1\n\nAverage distance: 8304.73\nNumber of variables =      8\tNumber of slots     =   2304\nNumber of keys      =    999\tNumber of min dead  =   9216\nwalsh1: 16 nodes 2 leaves 256 minterms\n-0--0--0--0-  1\n-0--0--0--10  1\n-0--0--0--11 -1\n-0--0--10-0-  1\n-0--0--10-10  1\n-0--0--10-11 -1\n-0--0--11-0- -1\n-0--0--11-10 -1\n-0--0--11-11  1\n-0--10-0--0-  1\n-0--10-0--10  1\n-0--10-0--11 -1\n-0--10-10-0-  1\n-0--10-10-10  1\n-0--10-10-11 -1\n-0--10-11-0- -1\n-0--10-11-10 -1\n-0--10-11-11  1\n-0--11-0--0- -1\n-0--11-0--10 -1\n-0--11-0--11  1\n-0--11-10-0- -1\n-0--11-10-10 -1\n-0--11-10-11  1\n-0--11-11-0-  1\n-0--11-11-10  1\n-0--11-11-11 -1\n-10-0--0--0-  1\n-10-0--0--10  1\n-10-0--0--11 -1\n-10-0--10-0-  1\n-10-0--10-10  1\n-10-0--10-11 -1\n-10-0--11-0- -1\n-10-0--11-10 -1\n-10-0--11-11  1\n-10-10-0--0-  1\n-10-10-0--10  1\n-10-10-0--11 -1\n-10-10-10-0-  1\n-10-10-10-10  1\n-10-10-10-11 -1\n-10-10-11-0- -1\n-10-10-11-10 -1\n-10-10-11-11  1\n-10-11-0--0- -1\n-10-11-0--10 -1\n-10-11-0--11  1\n-10-11-10-0- -1\n-10-11-10-10 -1\n-10-11-10-11  1\n-10-11-11-0-  1\n-10-11-11-10  1\n-10-11-11-11 -1\n-11-0--0--0- -1\n-11-0--0--10 -1\n-11-0--0--11  1\n-11-0--10-0- -1\n-11-0--10-10 -1\n-11-0--10-11  1\n-11-0--11-0-  1\n-11-0--11-10  1\n-11-0--11-11 -1\n-11-10-0--0- -1\n-11-10-0--10 -1\n-11-10-0--11  1\n-11-10-10-0- -1\n-11-10-10-10 -1\n-11-10-10-11  1\n-11-10-11-0-  1\n-11-10-11-10  1\n-11-10-11-11 -1\n-11-11-0--0-  1\n-11-11-0--10  1\n-11-11-0--11 -1\n-11-11-10-0-  1\n-11-11-10-10  1\n-11-11-10-11 -1\n-11-11-11-0- -1\n-11-11-11-10 -1\n-11-11-11-11  1\n\nwtw: 14 nodes 2 leaves 16 minterms\n0-00-00-00-0  16\n0-00-00-01-1  16\n0-00-01-10-0  16\n0-00-01-11-1  16\n0-01-10-00-0  16\n0-01-10-01-1  16\n0-01-11-10-0  16\n0-01-11-11-1  16\n1-10-00-00-0  16\n1-10-00-01-1  16\n1-10-01-10-0  16\n1-10-01-11-1  16\n1-11-10-00-0  16\n1-11-10-01-1  16\n1-11-11-10-0  16\n1-11-11-11-1  16\n\nAverage length of non-empty lists = 1\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 0\nArc violation threshold: 0\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 4004\n**** CUDD non-modifiable parameters ****\nMemory in use: 2255792\nPeak number of nodes: 2044\nPeak number of live nodes: 119\nNumber of BDD variables: 9\nNumber of ZDD variables: 0\nNumber of cache entries: 2048\nNumber of cache look-ups: 2844\nNumber of cache hits: 730\nNumber of cache insertions: 2282\nNumber of cache collisions: 926\nNumber of cache deletions: 1352\nCache used slots = 66.21% (expected 67.18%)\nSoft limit for cache size: 13312\nNumber of buckets in unique table: 2560\nUsed buckets in unique table: 0.51% (expected 0.51%)\nNumber of BDD and ADD nodes: 13\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 0\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 1095\nTotal number of nodes reclaimed: 967\nGarbage collections so far: 1\nTime for garbage collection: 0.00 sec\nReorderings so far: 0\nTime for reordering: 0.00 sec\ntotal time = 0.00 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  5048K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 658\nSwaps = 0\nInput blocks = 0\nOutput blocks = 16\nContext switch (voluntary) = 0\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/cudd/test_cudd.test.in",
    "content": "#! /bin/sh\n\nEXE=@EXEEXT@\nsrcdir=@srcdir@\nfile=r7x8.1\nverbosity=2\n\nsed_command='-r:-e:2,3d:-e:/Cache used slots/d:-e:/Average distance/d:-e:/modifiable/,$d:-e:s/[0-9][0-9]*\\.?[0-9]* sec//:-e:/so far/d'\n\necho TAP version 13\necho 1..2\nexitstatus=0\n# Create empty file.\n: > ./cudd/differences\n\ncudd/testcudd$EXE -p $verbosity ${srcdir}/cudd/${file}.mat > ./cudd/${file}.tst 2>&1\nfailed=`expr $? != 0`\nif test x$failed = x0 ; then\n    echo \"# comparing ./cudd/${file}.tst to ${srcdir}/cudd/${file}.out\"\n    mkfifo ./cudd/tst_fifo ./cudd/out_fifo\n    OIFS=$IFS\n    IFS=:\n    `sed ${sed_command} ./cudd/${file}.tst > ./cudd/tst_fifo &\\\n     sed ${sed_command} ${srcdir}/cudd/${file}.out > ./cudd/out_fifo &\\\n     diff -b ./cudd/tst_fifo ./cudd/out_fifo >> ./cudd/differences`\n    failed=`expr $? != 0`\n    rm ./cudd/tst_fifo ./cudd/out_fifo\n    IFS=$OIFS\nfi\nif test x$failed = x0 ; then\n    echo ok 1 cudd basic\nelse\n    echo not ok 1 cudd basic\nfi\nexitstatus=`expr $exitstatus + $failed`\n\ncudd/testextra$EXE $verbosity > ./cudd/extra.tst 2>&1\nfailed=`expr $? != 0`\nif test x$failed = x0 ; then\n    echo \"# comparing ./cudd/extra.tst to ${srcdir}/cudd/extra.out\"\n    mkfifo ./cudd/tst_fifo ./cudd/out_fifo\n    OIFS=$IFS\n    IFS=:\n    `sed ${sed_command} ./cudd/extra.tst > ./cudd/tst_fifo &\\\n     sed ${sed_command} ${srcdir}/cudd/extra.out > ./cudd/out_fifo &\\\n     diff -b ./cudd/tst_fifo ./cudd/out_fifo >> ./cudd/differences`\n    failed=`expr $? != 0`\n    rm ./cudd/tst_fifo ./cudd/out_fifo\n    IFS=$OIFS\nfi\nif test x$failed = x0 ; then\n    echo ok 2 cudd extra\nelse\n    echo not ok 2 cudd extra\nfi\nexitstatus=`expr $exitstatus + $failed`\n\nif test x$exitstatus = x0; then\n    rm -rf ./cudd/differences\nelse\n    echo '# Check file \"./cudd/differences\"'\nfi\n\nexit 0\n"
  },
  {
    "path": "cudd/cudd/testcudd.c",
    "content": "/**\n  @file \n\n  @ingroup cudd\n\n  @brief Sanity check tests for some CUDD functions.\n\n  @details testcudd reads a matrix with real coefficients and\n  transforms it into an %ADD. It then performs various operations on\n  the %ADD and on the %BDD corresponding to the ADD pattern. Finally,\n  testcudd tests functions relate to Walsh matrices and matrix\n  multiplication.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define TESTCUDD_VERSION\t\"TestCudd Version #1.0, Release date 3/17/01\"\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\nstatic const char *onames[] = { \"C\", \"M\" }; /* names of functions to be dumped */\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void usage (char * prog);\nstatic FILE *open_file (char *filename, const char *mode);\nstatic int testIterators (DdManager *dd, DdNode *M, DdNode *C, int pr);\nstatic int testXor (DdManager *dd, DdNode *f, int pr, int nvars);\nstatic int testHamming (DdManager *dd, DdNode *f, int pr);\nstatic int testWalsh (DdManager *dd, int N, int cmu, int approach, int pr);\nstatic int testSupport(DdManager *dd, DdNode *f, DdNode *g, int pr);\n\n/** \\endcond */\n\n\n\n/**\n  @brief Main function for testcudd.\n\n  @sideeffect None\n\n*/\nint\nmain(int argc, char * const *argv)\n{\n    FILE *fp;           /* pointer to input file */\n    char *file = (char *) \"\";\t/* input file name */\n    FILE *dfp = NULL;\t/* pointer to dump file */\n    FILE *savefp = NULL;/* pointer to save current manager's stdout setting */\n    char *dfile;\t/* file for DD dump */\n    DdNode *dfunc[2];\t/* addresses of the functions to be dumped */\n    DdManager *dd;\t/* pointer to DD manager */\n    DdNode *one;\t/* fast access to constant function */\n    DdNode *M;\n    DdNode **x;\t\t/* pointers to variables */\n    DdNode **y;\t\t/* pointers to variables */\n    DdNode **xn;\t/* complements of row variables */\n    DdNode **yn_;\t/* complements of column variables */\n    DdNode **xvars;\n    DdNode **yvars;\n    DdNode *C;\t\t/* result of converting from ADD to BDD */\n    DdNode *ess;\t/* cube of essential variables */\n    DdNode *shortP;\t/* BDD cube of shortest path */\n    DdNode *largest;\t/* BDD of largest cube */\n    DdNode *shortA;\t/* ADD cube of shortest path */\n    DdNode *constN;\t/* value returned by evaluation of ADD */\n    DdNode *ycube;\t/* cube of the negated y vars for c-proj */\n    DdNode *CP;\t\t/* C-Projection of C */\n    DdNode *CPr;\t/* C-Selection of C */\n    int    length;\t/* length of the shortest path */\n    int    nx;\t\t\t/* number of variables */\n    int    ny;\n    int    maxnx;\n    int    maxny;\n    int    m;\n    int    n;\n    int    N;\n    int    cmu;\t\t\t/* use CMU multiplication */\n    int    pr;\t\t\t/* verbose printout level */\n    int    harwell;\n    int    multiple;\t\t/* read multiple matrices */\n    int    ok;\n    int    approach;\t\t/* reordering approach */\n    int    autodyn;\t\t/* automatic reordering */\n    int    groupcheck;\t\t/* option for group sifting */\n    int    profile;\t\t/* print heap and cache profile if != 0 */\n    int    keepperm;\t\t/* keep track of permutation */\n    int    clearcache;\t\t/* clear the cache after each matrix */\n    int    blifOrDot;\t\t/* dump format: 0 -> dot, 1 -> blif, ... */\n    int    retval;\t\t/* return value */\n    int    i;\t\t\t/* loop index */\n    unsigned long startTime;\t/* initial time */\n    unsigned long lapTime = 0;\n    int    size;\n    unsigned int cacheSize, maxMemory;\n    unsigned int nvars,nslots;\n    int optidx;\n\n    startTime = util_cpu_time();\n\n    approach = CUDD_REORDER_NONE;\n    autodyn = 0;\n    pr = 0;\n    harwell = 0;\n    multiple = 0;\n    profile = 0;\n    keepperm = 0;\n    cmu = 0;\n    N = 4;\n    nvars = 4;\n    cacheSize = 2048;\n    maxMemory = 0;\n    nslots = CUDD_UNIQUE_SLOTS;\n    clearcache = 0;\n    groupcheck = CUDD_GROUP_CHECK7;\n    dfile = NULL;\n    blifOrDot = 0; /* dot format */\n\n    /* Parse command line. */\n    for (optidx = 1; optidx < argc; optidx++) {\n        if (argv[optidx][0] == '-') {\n            switch(argv[optidx][1]) {\n            case 'C':\n                cmu = 1;\n                break;\n            case 'D':\n                autodyn = 1;\n                break;\n            case 'H':\n                harwell = 1;\n                break;\n            case 'M':\n                /* NOOP: retained for backward compatibility. */\n                break;\n            case 'P':\n                profile = 1;\n                break;\n            case 'S':\n                if (++optidx == argc) usage(argv[0]);\n                nslots = atoi(argv[optidx]);\n                break;\n            case 'X':\n                if (++optidx == argc) usage(argv[0]);\n                maxMemory = atoi(argv[optidx]);\n                break;\n            case 'a':\n                if (++optidx == argc) usage(argv[0]);\n                approach = atoi(argv[optidx]);\n                break;\n            case 'b':\n                blifOrDot = 1; /* blif format */\n                break;\n            case 'c':\n                clearcache = 1;\n                break;\n            case 'd':\n                if (++optidx == argc) usage(argv[0]);\n                dfile = argv[optidx];\n                break;\n            case 'g':\n                if (++optidx == argc) usage(argv[0]);\n                groupcheck = atoi(argv[optidx]);\n                break;\n            case 'k':\n                keepperm = 1;\n                break;\n            case 'm':\n                multiple = 1;\n                break;\n            case 'n':\n                if (++optidx == argc) usage(argv[0]);\n                N = atoi(argv[optidx]);\n                break;\n            case 'p':\n                if (++optidx == argc) usage(argv[0]);\n                pr = atoi(argv[optidx]);\n                break;\n            case 'v':\n                if (++optidx == argc) usage(argv[0]);\n                nvars = atoi(argv[optidx]);\n                break;\n            case 'x':\n                if (++optidx == argc) usage(argv[0]);\n                cacheSize = atoi(argv[optidx]);\n                break;\n            case 'h':\n            default:\n                usage(argv[0]);\n                break;\n            }\n        } else if (argc - optidx == 1) {\n            file = argv[optidx];\n        } else {\n            usage(argv[0]);\n        }\n    }\n\n    if ((approach<0) || (approach>17)) {\n\t(void) fprintf(stderr,\"Invalid approach: %d \\n\",approach);\n\tusage(argv[0]);\n    }\n\n    if (pr > 0) {\n\t(void) printf(\"# %s\\n\", TESTCUDD_VERSION);\n\t/* Echo command line and arguments. */\n\t(void) printf(\"#\");\n\tfor (i = 0; i < argc; i++) {\n\t    (void) printf(\" %s\", argv[i]);\n\t}\n\t(void) printf(\"\\n\");\n\t(void) fflush(stdout);\n    }\n\n    /* Initialize manager and provide easy reference to terminals. */\n    dd = Cudd_Init(nvars,0,nslots,cacheSize,maxMemory);\n    one = DD_ONE(dd);\n    dd->groupcheck = (Cudd_AggregationType) groupcheck;\n    if (autodyn) Cudd_AutodynEnable(dd,CUDD_REORDER_SAME);\n\n    /* Open input file. */\n    fp = open_file(file, \"r\");\n\n    /* Open dump file if requested */\n    if (dfile != NULL) {\n\tdfp = open_file(dfile, \"w\");\n    }\n\n    x = y = xn = yn_ = NULL;\n    do {\n\t/* We want to start anew for every matrix. */\n\tmaxnx = maxny = 0;\n\tnx = maxnx; ny = maxny;\n\tif (pr>0) lapTime = util_cpu_time();\n\tif (harwell) {\n\t    if (pr > 0) (void) printf(\":name: \");\n\t    ok = Cudd_addHarwell(fp, dd, &M, &x, &y, &xn, &yn_, &nx, &ny,\n\t    &m, &n, 0, 2, 1, 2, pr);\n\t} else {\n\t    ok = Cudd_addRead(fp, dd, &M, &x, &y, &xn, &yn_, &nx, &ny,\n\t    &m, &n, 0, 2, 1, 2);\n\t    if (pr > 0)\n\t\t(void) printf(\":name: %s: %d rows %d columns\\n\", file, m, n);\n\t}\n\tif (!ok) {\n\t    (void) fprintf(stderr, \"Error reading matrix\\n\");\n\t    return(1);\n\t}\n\n\tif (nx > maxnx) maxnx = nx;\n\tif (ny > maxny) maxny = ny;\n\n\t/* Build cube of negated y's. */\n\tycube = DD_ONE(dd);\n\tCudd_Ref(ycube);\n\tfor (i = maxny - 1; i >= 0; i--) {\n\t    DdNode *tmpp;\n\t    tmpp = Cudd_bddAnd(dd,Cudd_Not(dd->vars[y[i]->index]),ycube);\n\t    if (tmpp == NULL) return(2);\n\t    Cudd_Ref(tmpp);\n\t    Cudd_RecursiveDeref(dd,ycube);\n\t    ycube = tmpp;\n\t}\n\t/* Initialize vectors of BDD variables used by priority func. */\n\txvars = ALLOC(DdNode *, nx);\n\tif (xvars == NULL) return(2);\n\tfor (i = 0; i < nx; i++) {\n\t    xvars[i] = dd->vars[x[i]->index];\n\t}\n\tyvars = ALLOC(DdNode *, ny);\n\tif (yvars == NULL) return(2);\n\tfor (i = 0; i < ny; i++) {\n\t    yvars[i] = dd->vars[y[i]->index];\n\t}\n\n\t/* Clean up */\n\tfor (i=0; i < maxnx; i++) {\n\t    Cudd_RecursiveDeref(dd, x[i]);\n\t    Cudd_RecursiveDeref(dd, xn[i]);\n\t}\n\tFREE(x);\n\tFREE(xn);\n\tfor (i=0; i < maxny; i++) {\n\t    Cudd_RecursiveDeref(dd, y[i]);\n\t    Cudd_RecursiveDeref(dd, yn_[i]);\n\t}\n\tFREE(y);\n\tFREE(yn_);\n\n\tif (pr>0) {(void) printf(\":1: M\"); Cudd_PrintDebug(dd,M,nx+ny,pr);}\n\n\tif (pr>0) (void) printf(\":2: time to read the matrix = %s\\n\",\n\t\t    util_print_time(util_cpu_time() - lapTime));\n\n\tC = Cudd_addBddPattern(dd, M);\n\tif (C == 0) return(2);\n\tCudd_Ref(C);\n\tif (pr>0) {(void) printf(\":3: C\"); Cudd_PrintDebug(dd,C,nx+ny,pr);}\n\n\t/* Test iterators. */\n\tretval = testIterators(dd,M,C,pr);\n\tif (retval == 0) return(2);\n\n        if (profile != 0 && pr > 0)\n            cuddCacheProfile(dd,stdout);\n\n\t/* Test XOR */\n\tretval = testXor(dd,C,pr,nx+ny);\n\tif (retval == 0) return(2);\n\n\t/* Test Hamming distance functions. */\n\tretval = testHamming(dd,C,pr);\n\tif (retval == 0) return(2);\n\n\t/* Test selection functions. */\n\tCP = Cudd_CProjection(dd,C,ycube);\n\tif (CP == NULL) return(2);\n\tCudd_Ref(CP);\n\tif (pr>0) {(void) printf(\"ycube\"); Cudd_PrintDebug(dd,ycube,nx+ny,pr);}\n\tif (pr>0) {(void) printf(\"CP\"); Cudd_PrintDebug(dd,CP,nx+ny,pr);}\n\n\tif (nx == ny) {\n\t    CPr = Cudd_PrioritySelect(dd,C,xvars,yvars,(DdNode **)NULL,\n\t\t(DdNode *)NULL,ny,Cudd_Xgty);\n\t    if (CPr == NULL) return(2);\n\t    Cudd_Ref(CPr);\n\t    if (pr>0) {(void) printf(\":4: CPr\"); Cudd_PrintDebug(dd,CPr,nx+ny,pr);}\n\t    if (CP != CPr) {\n\t\t(void) printf(\"CP != CPr!\\n\");\n\t    }\n\t    Cudd_RecursiveDeref(dd, CPr);\n\t}\n\n\t/* Test inequality generator. */\n\t{\n\t    int Nmin = ddMin(nx,ny);\n\t    int q;\n\t    DdGen *gen;\n\t    int *cube;\n\t    DdNode *f = Cudd_Inequality(dd,Nmin,2,xvars,yvars);\n\t    if (f == NULL) return(2);\n\t    Cudd_Ref(f);\n\t    if (pr>0) {\n\t\t(void) printf(\":4: ineq\");\n\t\tCudd_PrintDebug(dd,f,nx+ny,pr);\n\t\tif (pr>1) {\n\t\t    Cudd_ForeachPrime(dd,Cudd_Not(f),Cudd_Not(f),gen,cube) {\n\t\t\tfor (q = 0; q < dd->size; q++) {\n\t\t\t    switch (cube[q]) {\n\t\t\t    case 0:\n\t\t\t\t(void) printf(\"1\");\n\t\t\t\tbreak;\n\t\t\t    case 1:\n\t\t\t\t(void) printf(\"0\");\n\t\t\t\tbreak;\n\t\t\t    case 2:\n\t\t\t\t(void) printf(\"-\");\n\t\t\t\tbreak;\n\t\t\t    default:\n\t\t\t\t(void) printf(\"?\");\n\t\t\t    }\n\t\t\t}\n\t\t\t(void) printf(\" 1\\n\");\n\t\t    }\n\t\t    (void) printf(\"\\n\");\n\t\t}\n\t    }\n\t    Cudd_IterDerefBdd(dd, f);\n\t}\n\tFREE(xvars); FREE(yvars);\n\n\tCudd_RecursiveDeref(dd, CP);\n\n\t/* Test functions for essential variables. */\n\tess = Cudd_FindEssential(dd,C);\n\tif (ess == NULL) return(2);\n\tCudd_Ref(ess);\n\tif (pr>0) {(void) printf(\":4: ess\"); Cudd_PrintDebug(dd,ess,nx+ny,pr);}\n\tCudd_RecursiveDeref(dd, ess);\n\n\t/* Test functions for shortest paths. */\n\tshortP = Cudd_ShortestPath(dd, M, NULL, NULL, &length);\n\tif (shortP == NULL) return(2);\n\tCudd_Ref(shortP);\n\tif (pr>0) {\n\t    (void) printf(\":5: shortP\"); Cudd_PrintDebug(dd,shortP,nx+ny,pr);\n\t}\n\t/* Test functions for largest cubes. */\n\tlargest = Cudd_LargestCube(dd, Cudd_Not(C), &length);\n\tif (largest == NULL) return(2);\n\tCudd_Ref(largest);\n\tif (pr>0) {\n\t    (void) printf(\":5b: largest\");\n\t    Cudd_PrintDebug(dd,largest,nx+ny,pr);\n\t}\n\tCudd_RecursiveDeref(dd, largest);\n\n\t/* Test Cudd_addEvalConst and Cudd_addIteConstant. */\n\tshortA = Cudd_BddToAdd(dd,shortP);\n\tif (shortA == NULL) return(2);\n\tCudd_Ref(shortA);\n\tCudd_RecursiveDeref(dd, shortP);\n\tconstN = Cudd_addEvalConst(dd,shortA,M);\n\tif (constN == DD_NON_CONSTANT) return(2);\n\tif (Cudd_addIteConstant(dd,shortA,M,constN) != constN) return(2);\n\tif (pr>0) {(void) printf(\"The value of M along the chosen shortest path is %g\\n\", cuddV(constN));}\n\tCudd_RecursiveDeref(dd, shortA);\n\n\tshortP = Cudd_ShortestPath(dd, C, NULL, NULL, &length);\n\tif (shortP == NULL) return(2);\n\tCudd_Ref(shortP);\n\tif (pr>0) {\n\t    (void) printf(\":6: shortP\"); Cudd_PrintDebug(dd,shortP,nx+ny,pr);\n\t}\n\n\t/* Test Cudd_bddIteConstant and Cudd_bddLeq. */\n\tif (!Cudd_bddLeq(dd,shortP,C)) return(2);\n\tif (Cudd_bddIteConstant(dd,Cudd_Not(shortP),one,C) != one) return(2);\n\tCudd_RecursiveDeref(dd, shortP);\n\n        /* Experiment with support functions. */\n        if (!testSupport(dd,M,ycube,pr)) {\n            return(2);\n        }\n\tCudd_RecursiveDeref(dd, ycube);\n\n\tif (profile) {\n\t    retval = cuddHeapProfile(dd);\n            if (retval == 0) {\n                (void) fprintf(stderr,\"Error reported by cuddHeapProfile\\n\");\n                return(2);\n            }\n\t}\n\n\tsize = dd->size;\n\n\tif (pr>0) {\n\t    (void) printf(\"Average distance: %g\\n\", Cudd_AverageDistance(dd));\n\t}\n\n\t/* Reorder if so requested. */\n\tif (approach != CUDD_REORDER_NONE) {\n#ifndef DD_STATS\n\t    retval = Cudd_EnableReorderingReporting(dd);\n\t    if (retval == 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_EnableReorderingReporting\\n\");\n\t\treturn(3);\n\t    }\n#endif\n#ifdef DD_DEBUG\n\t    retval = Cudd_DebugCheck(dd);\n\t    if (retval != 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_DebugCheck\\n\");\n\t\treturn(3);\n\t    }\n\t    retval = Cudd_CheckKeys(dd);\n\t    if (retval != 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_CheckKeys\\n\");\n\t\treturn(3);\n\t    }\n#endif\n\t    retval = Cudd_ReduceHeap(dd,(Cudd_ReorderingType)approach,5);\n\t    if (retval == 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_ReduceHeap\\n\");\n\t\treturn(3);\n\t    }\n#ifndef DD_STATS\n\t    retval = Cudd_DisableReorderingReporting(dd);\n\t    if (retval == 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_DisableReorderingReporting\\n\");\n\t\treturn(3);\n\t    }\n#endif\n#ifdef DD_DEBUG\n\t    retval = Cudd_DebugCheck(dd);\n\t    if (retval != 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_DebugCheck\\n\");\n\t\treturn(3);\n\t    }\n\t    retval = Cudd_CheckKeys(dd);\n\t    if (retval != 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_CheckKeys\\n\");\n\t\treturn(3);\n\t    }\n#endif\n\t    if (approach == CUDD_REORDER_SYMM_SIFT ||\n\t    approach == CUDD_REORDER_SYMM_SIFT_CONV) {\n\t\tCudd_SymmProfile(dd,0,dd->size-1);\n\t    }\n\n\t    if (pr>0) {\n\t\t(void) printf(\"Average distance: %g\\n\", Cudd_AverageDistance(dd));\n\t    }\n\n\t    if (keepperm) {\n\t\t/* Print variable permutation. */\n\t\t(void) printf(\"Variable Permutation:\");\n\t\tfor (i=0; i<size; i++) {\n\t\t    if (i%20 == 0) (void) printf(\"\\n\");\n\t\t    (void) printf(\"%d \", dd->invperm[i]);\n\t\t}\n\t\t(void) printf(\"\\n\");\n\t\t(void) printf(\"Inverse Permutation:\");\n\t\tfor (i=0; i<size; i++) {\n\t\t    if (i%20 == 0) (void) printf(\"\\n\");\n\t\t    (void) printf(\"%d \", dd->perm[i]);\n\t\t}\n\t\t(void) printf(\"\\n\");\n\t    }\n\n\t    if (pr>0) {(void) printf(\"M\"); Cudd_PrintDebug(dd,M,nx+ny,pr);}\n\n\t    if (profile) {\n\t\tretval = cuddHeapProfile(dd);\n                if (retval == 0) {\n                    (void) fprintf(stderr,\"Error reported by cuddHeapProfile\\n\");\n                    return(2);\n                }\n\t    }\n\n\t}\n\n\t/* Dump DDs of C and M if so requested. */\n\tif (dfile != NULL) {\n\t    dfunc[0] = C;\n\t    dfunc[1] = M;\n\t    if (blifOrDot == 1) {\n\t\t/* Only dump C because blif cannot handle ADDs */\n\t\tretval = Cudd_DumpBlif(dd,1,dfunc,NULL,\n                                       (char const * const *)onames,NULL,dfp,0);\n\t    } else {\n\t\tretval = Cudd_DumpDot(dd,2,dfunc,NULL,\n                                      (char const * const *)onames,dfp);\n\t    }\n\t    if (retval != 1) {\n\t\t(void) fprintf(stderr,\"abnormal termination\\n\");\n\t\treturn(2);\n\t    }\n\t}\n\n\tCudd_RecursiveDeref(dd, C);\n\tCudd_RecursiveDeref(dd, M);\n\n\tif (clearcache) {\n\t    if (pr>0) {(void) printf(\"Clearing the cache... \");}\n\t    for (i = dd->cacheSlots - 1; i>=0; i--) {\n\t\tdd->cache[i].data = NULL;\n\t    }\n\t    if (pr>0) {(void) printf(\"done\\n\");}\n\t}\n\tif (pr>0) {\n\t    (void) printf(\"Number of variables = %6d\\t\",dd->size);\n\t    (void) printf(\"Number of slots     = %6u\\n\",dd->slots);\n\t    (void) printf(\"Number of keys      = %6u\\t\",dd->keys);\n\t    (void) printf(\"Number of min dead  = %6u\\n\",dd->minDead);\n\t}\n\n    } while (multiple && !feof(fp));\n\n    fclose(fp);\n    if (dfile != NULL) {\n\tfclose(dfp);\n    }\n\n    /* Second phase: experiment with Walsh matrices. */\n    if (!testWalsh(dd,N,cmu,approach,pr)) {\n\treturn(2);\n    }\n\n    /* Check variable destruction. */\n    assert(cuddDestroySubtables(dd,3));\n    if (pr == 0) {\n        savefp = Cudd_ReadStdout(dd);\n        Cudd_SetStdout(dd,fopen(\"/dev/null\",\"a\"));\n    }\n    assert(Cudd_DebugCheck(dd) == 0);\n    assert(Cudd_CheckKeys(dd) == 0);\n    if (pr == 0) {\n        fclose(Cudd_ReadStdout(dd));\n        Cudd_SetStdout(dd,savefp);\n    }\n\n    retval = Cudd_CheckZeroRef(dd);\n    ok = retval != 0;  /* ok == 0 means O.K. */\n    if (retval != 0) {\n\t(void) fprintf(stderr,\n\t    \"%d non-zero DD reference counts after dereferencing\\n\", retval);\n    }\n\n    if (pr > 0) {\n\t(void) Cudd_PrintInfo(dd,stdout);\n    }\n\n    Cudd_Quit(dd);\n\n    if (pr>0) (void) printf(\"total time = %s\\n\",\n\t\tutil_print_time(util_cpu_time() - startTime));\n\n    if (pr > 0) util_print_cpu_stats(stdout);\n    return ok;\n\n} /* end of main */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Prints usage info for testcudd.\n\n  @sideeffect None\n\n*/\nstatic void\nusage(char *prog)\n{\n    (void) fprintf(stderr, \"usage: %s [options] [file]\\n\", prog);\n    (void) fprintf(stderr, \"   -C\\t\\tuse CMU multiplication algorithm\\n\");\n    (void) fprintf(stderr, \"   -D\\t\\tenable automatic dynamic reordering\\n\");\n    (void) fprintf(stderr, \"   -H\\t\\tread matrix in Harwell format\\n\");\n    (void) fprintf(stderr, \"   -P\\t\\tprint BDD heap and cache profile\\n\");\n    (void) fprintf(stderr, \"   -S n\\t\\tnumber of slots for each subtable\\n\");\n    (void) fprintf(stderr, \"   -X n\\t\\ttarget maximum memory in bytes\\n\");\n    (void) fprintf(stderr, \"   -a n\\t\\tchoose reordering approach (0-13)\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t0: same as autoMethod\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t1: no reordering (default)\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t2: random\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t3: pivot\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t4: sifting\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t5: sifting to convergence\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t6: symmetric sifting\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t7: symmetric sifting to convergence\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t8-10: window of size 2-4\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t11-13: window of size 2-4 to conv.\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t14: group sifting\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t15: group sifting to convergence\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t16: simulated annealing\\n\");\n    (void) fprintf(stderr, \"   \\t\\t\\t17: genetic algorithm\\n\");\n    (void) fprintf(stderr, \"   -b\\t\\tuse blif as format for dumps\\n\");\n    (void) fprintf(stderr, \"   -c\\t\\tclear the cache after each matrix\\n\");\n    (void) fprintf(stderr, \"   -d file\\tdump DDs to file\\n\");\n    (void) fprintf(stderr, \"   -g\\t\\tselect aggregation criterion (0,5,7)\\n\");\n    (void) fprintf(stderr, \"   -h\\t\\tprints this message\\n\");\n    (void) fprintf(stderr, \"   -k\\t\\tprint the variable permutation\\n\");\n    (void) fprintf(stderr, \"   -m\\t\\tread multiple matrices (only with -H)\\n\");\n    (void) fprintf(stderr, \"   -n n\\t\\tnumber of variables\\n\");\n    (void) fprintf(stderr, \"   -p n\\t\\tcontrol verbosity\\n\");\n    (void) fprintf(stderr, \"   -v n\\t\\tinitial variables in the unique table\\n\");\n    (void) fprintf(stderr, \"   -x n\\t\\tinitial size of the cache\\n\");\n    exit(2);\n} /* end of usage */\n\n\n/**\n  @brief Opens a file.\n\n  @details Opens a file, or fails with an error message and exits.\n  Allows '-' as a synonym for standard input.\n\n  @sideeffect None\n\n*/\nstatic FILE *\nopen_file(char *filename, const char *mode)\n{\n    FILE *fp;\n\n    if (strcmp(filename, \"-\") == 0) {\n\treturn mode[0] == 'r' ? stdin : stdout;\n    } else if ((fp = fopen(filename, mode)) == NULL) {\n\tperror(filename);\n\texit(1);\n    }\n    return fp;\n\n} /* end of open_file */\n\n\n/**\n  @brief Tests Walsh matrix multiplication.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect May create new variables in the manager.\n\n*/\nstatic int\ntestWalsh(\n  DdManager *dd /* manager */,\n  int N /* number of variables */,\n  int cmu /* use CMU approach to matrix multiplication */,\n  int approach /* reordering approach */,\n  int pr /* verbosity level */)\n{\n    DdNode *walsh1, *walsh2, *wtw;\n    DdNode **x, **v, **z;\n    int i, retval;\n    DdNode *one = DD_ONE(dd);\n    DdNode *zero = DD_ZERO(dd);\n\n    if (N > 3) {\n\tx = ALLOC(DdNode *,N);\n\tv = ALLOC(DdNode *,N);\n\tz = ALLOC(DdNode *,N);\n\n\tfor (i = N-1; i >= 0; i--) {\n\t    Cudd_Ref(x[i]=cuddUniqueInter(dd,3*i,one,zero));\n\t    Cudd_Ref(v[i]=cuddUniqueInter(dd,3*i+1,one,zero));\n\t    Cudd_Ref(z[i]=cuddUniqueInter(dd,3*i+2,one,zero));\n\t}\n\tCudd_Ref(walsh1 = Cudd_addWalsh(dd,v,z,N));\n\tif (pr>0) {(void) printf(\"walsh1\"); Cudd_PrintDebug(dd,walsh1,2*N,pr);}\n\tCudd_Ref(walsh2 = Cudd_addWalsh(dd,x,v,N));\n\tif (cmu) {\n\t    Cudd_Ref(wtw = Cudd_addTimesPlus(dd,walsh2,walsh1,v,N));\n\t} else {\n\t    Cudd_Ref(wtw = Cudd_addMatrixMultiply(dd,walsh2,walsh1,v,N));\n\t}\n\tif (pr>0) {(void) printf(\"wtw\"); Cudd_PrintDebug(dd,wtw,2*N,pr);}\n\n\tif (approach != CUDD_REORDER_NONE) {\n#ifdef DD_DEBUG\n\t    retval = Cudd_DebugCheck(dd);\n\t    if (retval != 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_DebugCheck\\n\");\n\t\treturn(0);\n\t    }\n#endif\n\t    retval = Cudd_ReduceHeap(dd,(Cudd_ReorderingType)approach,5);\n\t    if (retval == 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_ReduceHeap\\n\");\n\t\treturn(0);\n\t    }\n#ifdef DD_DEBUG\n\t    retval = Cudd_DebugCheck(dd);\n\t    if (retval != 0) {\n\t\t(void) fprintf(stderr,\"Error reported by Cudd_DebugCheck\\n\");\n\t\treturn(0);\n\t    }\n#endif\n\t    if (approach == CUDD_REORDER_SYMM_SIFT ||\n\t    approach == CUDD_REORDER_SYMM_SIFT_CONV) {\n\t\tCudd_SymmProfile(dd,0,dd->size-1);\n\t    }\n\t}\n\t/* Clean up. */\n\tCudd_RecursiveDeref(dd, wtw);\n\tCudd_RecursiveDeref(dd, walsh1);\n\tCudd_RecursiveDeref(dd, walsh2);\n\tfor (i=0; i < N; i++) {\n\t    Cudd_RecursiveDeref(dd, x[i]);\n\t    Cudd_RecursiveDeref(dd, v[i]);\n\t    Cudd_RecursiveDeref(dd, z[i]);\n\t}\n\tFREE(x);\n\tFREE(v);\n\tFREE(z);\n    }\n    return(1);\n\n} /* end of testWalsh */\n\n/**\n  @brief Tests iterators on cubes and nodes.\n\n  @sideeffect None\n\n*/\nstatic int\ntestIterators(\n  DdManager *dd,\n  DdNode *M,\n  DdNode *C,\n  int pr)\n{\n    int *cube;\n    CUDD_VALUE_TYPE value;\n    DdGen *gen;\n    int q;\n\n    /* Test iterator for cubes. */\n    if (pr>1) {\n\t(void) printf(\"Testing iterator on cubes:\\n\");\n\tCudd_ForeachCube(dd,M,gen,cube,value) {\n\t    for (q = 0; q < dd->size; q++) {\n\t\tswitch (cube[q]) {\n\t\tcase 0:\n\t\t    (void) printf(\"0\");\n\t\t    break;\n\t\tcase 1:\n\t\t    (void) printf(\"1\");\n\t\t    break;\n\t\tcase 2:\n\t\t    (void) printf(\"-\");\n\t\t    break;\n\t\tdefault:\n\t\t    (void) printf(\"?\");\n\t\t}\n\t    }\n\t    (void) printf(\" %g\\n\",value);\n\t}\n\t(void) printf(\"\\n\");\n    }\n\n    if (pr>1) {\n\t(void) printf(\"Testing prime expansion of cubes:\\n\");\n\tif (!Cudd_bddPrintCover(dd,C,C)) return(0);\n    }\n\n    if (pr>1) {\n\t(void) printf(\"Testing iterator on primes (CNF):\\n\");\n\tCudd_ForeachPrime(dd,Cudd_Not(C),Cudd_Not(C),gen,cube) {\n\t    for (q = 0; q < dd->size; q++) {\n\t\tswitch (cube[q]) {\n\t\tcase 0:\n\t\t    (void) printf(\"1\");\n\t\t    break;\n\t\tcase 1:\n\t\t    (void) printf(\"0\");\n\t\t    break;\n\t\tcase 2:\n\t\t    (void) printf(\"-\");\n\t\t    break;\n\t\tdefault:\n\t\t    (void) printf(\"?\");\n\t\t}\n\t    }\n\t    (void) printf(\" 1\\n\");\n\t}\n\t(void) printf(\"\\n\");\n    }\n\n    /* Test iterator on nodes. */\n    if (pr>2) {\n\tDdNode *node;\n\t(void) printf(\"Testing iterator on nodes:\\n\");\n\tCudd_ForeachNode(dd,M,gen,node) {\n\t    if (Cudd_IsConstant(node)) {\n\t\t(void) printf(\"ID = 0x%\"PRIxPTR\"\\tvalue = %-9g\\n\",\n\t\t\t      (ptruint) node / (ptruint) sizeof(DdNode),\n\t\t\t      Cudd_V(node));\n\t    } else {\n\t\t(void) printf(\"ID = 0x%\"PRIxPTR\"\\tindex = %u\\tr = %u\\n\",\n\t\t\t      (ptruint) node / (ptruint) sizeof(DdNode),\n\t\t\t      node->index, node->ref);\n\t    }\n\t}\n\t(void) printf(\"\\n\");\n    }\n    return(1);\n\n} /* end of testIterators */\n\n\n/**\n  @brief Tests the functions related to the exclusive OR.\n\n  @details Builds the boolean difference of the given function in\n  three different ways and checks that the results is the same.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ntestXor(DdManager *dd, DdNode *f, int pr, int nvars)\n{\n    DdNode *f1, *f0, *res1, *res2;\n    int x;\n\n    /* Extract cofactors w.r.t. mid variable. */\n    x = nvars / 2;\n    f1 = Cudd_Cofactor(dd,f,dd->vars[x]);\n    if (f1 == NULL) return(0);\n    Cudd_Ref(f1);\n\n    f0 = Cudd_Cofactor(dd,f,Cudd_Not(dd->vars[x]));\n    if (f0 == NULL) {\n\tCudd_RecursiveDeref(dd,f1);\n\treturn(0);\n    }\n    Cudd_Ref(f0);\n\n    /* Compute XOR of cofactors with ITE. */\n    res1 = Cudd_bddIte(dd,f1,Cudd_Not(f0),f0);\n    if (res1 == NULL) return(0);\n    Cudd_Ref(res1);\n\n    if (pr>0) {(void) printf(\"xor1\"); Cudd_PrintDebug(dd,res1,nvars,pr);}\n\n    /* Compute XOR of cofactors with XOR. */\n    res2 = Cudd_bddXor(dd,f1,f0);\n    if (res2 == NULL) {\n\tCudd_RecursiveDeref(dd,res1);\n\treturn(0);\n    }\n    Cudd_Ref(res2);\n\n    if (res1 != res2) {\n\tif (pr>0) {(void) printf(\"xor2\"); Cudd_PrintDebug(dd,res2,nvars,pr);}\n\tCudd_RecursiveDeref(dd,res1);\n\tCudd_RecursiveDeref(dd,res2);\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,res1);\n    Cudd_RecursiveDeref(dd,f1);\n    Cudd_RecursiveDeref(dd,f0);\n\n    /* Compute boolean difference directly. */\n    res1 = Cudd_bddBooleanDiff(dd,f,x);\n    if (res1 == NULL) {\n\tCudd_RecursiveDeref(dd,res2);\n\treturn(0);\n    }\n    Cudd_Ref(res1);\n\n    if (res1 != res2) {\n\tif (pr>0) {(void) printf(\"xor3\"); Cudd_PrintDebug(dd,res1,nvars,pr);}\n\tCudd_RecursiveDeref(dd,res1);\n\tCudd_RecursiveDeref(dd,res2);\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,res1);\n    Cudd_RecursiveDeref(dd,res2);\n    return(1);\n\n} /* end of testXor */\n\n\n/**\n  @brief Tests the Hamming distance functions.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ntestHamming(\n  DdManager *dd,\n  DdNode *f,\n  int pr)\n{\n    DdNode **vars, *minBdd, *zero, *scan;\n    int i;\n    int d;\n    int *minterm;\n    int size = Cudd_ReadSize(dd);\n\n    vars = ALLOC(DdNode *, size);\n    if (vars == NULL) return(0);\n    for (i = 0; i < size; i++) {\n\tvars[i] = Cudd_bddIthVar(dd,i);\n    }\n\n    minBdd = Cudd_bddPickOneMinterm(dd,Cudd_Not(f),vars,size);\n    Cudd_Ref(minBdd);\n    if (pr > 0) {\n\t(void) printf(\"Chosen minterm for Hamming distance test: \");\n\tCudd_PrintDebug(dd,minBdd,size,pr);\n    }\n\n    minterm = ALLOC(int,size);\n    if (minterm == NULL) {\n\tFREE(vars);\n\tCudd_RecursiveDeref(dd,minBdd);\n\treturn(0);\n    }\n    scan = minBdd;\n    zero = Cudd_Not(DD_ONE(dd));\n    while (!Cudd_IsConstant(scan)) {\n\tDdNode *R = Cudd_Regular(scan);\n\tDdNode *T = Cudd_T(R);\n\tDdNode *E = Cudd_E(R);\n\tif (R != scan) {\n\t    T = Cudd_Not(T);\n\t    E = Cudd_Not(E);\n\t}\n\tif (T == zero) {\n\t    minterm[R->index] = 0;\n\t    scan = E;\n\t} else {\n\t    minterm[R->index] = 1;\n\t    scan = T;\n\t}\n    }\n    Cudd_RecursiveDeref(dd,minBdd);\n\n    d = Cudd_MinHammingDist(dd,f,minterm,size);\n\n    if (pr > 0)\n        (void) printf(\"Minimum Hamming distance = %d\\n\", d);\n\n    FREE(vars);\n    FREE(minterm);\n    return(1);\n\n} /* end of testHamming */\n\n\n/**\n  @brief Tests the support functions.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\ntestSupport(\n  DdManager *dd,\n  DdNode *f,\n  DdNode *g,\n  int pr)\n{\n    DdNode *sb, *common, *onlyF, *onlyG;\n    DdNode *F[2];\n    int *support;\n    int ret, ssize;\n    int size = Cudd_ReadSize(dd);\n\n    sb = Cudd_Support(dd, f);\n    if (sb == NULL) return(0);\n    Cudd_Ref(sb);\n    if (pr > 0) {\n\t(void) printf(\"Support of f: \");\n\tCudd_PrintDebug(dd,sb,size,pr);\n    }\n    Cudd_RecursiveDeref(dd, sb);\n\n    ssize = Cudd_SupportIndices(dd, f, &support);\n    if (ssize == CUDD_OUT_OF_MEM) return(0);\n    if (pr > 0) {\n\t(void) printf(\"Size of the support of f: %d\\n\", ssize);\n    }\n    FREE(support);\n\n    ssize = Cudd_SupportSize(dd, f);\n    if (pr > 0) {\n\t(void) printf(\"Size of the support of f: %d\\n\", ssize);\n    }\n\n    F[0] = f;\n    F[1] = g;\n    sb = Cudd_VectorSupport(dd, F, 2);\n    if (sb == NULL) return(0);\n    Cudd_Ref(sb);\n    if (pr > 0) {\n\t(void) printf(\"Support of f and g: \");\n\tCudd_PrintDebug(dd,sb,size,pr);\n    }\n    Cudd_RecursiveDeref(dd, sb);\n\n    ssize = Cudd_VectorSupportIndices(dd, F, 2, &support);\n    if (ssize == CUDD_OUT_OF_MEM) return(0);\n    if (pr > 0) {\n\t(void) printf(\"Size of the support of f and g: %d\\n\", ssize);\n    }\n    FREE(support);\n\n    ssize = Cudd_VectorSupportSize(dd, F, 2);\n    if (pr > 0) {\n\t(void) printf(\"Size of the support of f and g: %d\\n\", ssize);\n    }\n\n    ret = Cudd_ClassifySupport(dd, f, g, &common, &onlyF, &onlyG);\n    if (ret == 0) return(0);\n    Cudd_Ref(common); Cudd_Ref(onlyF); Cudd_Ref(onlyG);\n    if (pr > 0) {\n\t(void) printf(\"Support common to f and g: \");\n\tCudd_PrintDebug(dd,common,size,pr);\n\t(void) printf(\"Support private to f: \");\n\tCudd_PrintDebug(dd,onlyF,size,pr);\n\t(void) printf(\"Support private to g: \");\n\tCudd_PrintDebug(dd,onlyG,size,pr);\n    }\n    Cudd_RecursiveDeref(dd, common);\n    Cudd_RecursiveDeref(dd, onlyF);\n    Cudd_RecursiveDeref(dd, onlyG);\n\n    return(1);\n\n} /* end of testSupport */\n"
  },
  {
    "path": "cudd/cudd/testextra.c",
    "content": "/**\n  @file\n\n  @ingroup cudd\n\n  @brief This program tests selected features of CUDD.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n */\n\n#include \"util.h\"\n#include \"epd.h\"\n#include \"cudd.h\"\n#include <setjmp.h>\n\n/** \\cond */\nstatic int testBdd(int verbosity);\nstatic int testAdd(int verbosity);\nstatic int testZdd(int verbosity);\nstatic int testApa(int verbosity);\nstatic int testCount(int verbosity);\nstatic int testLdbl(int verbosity);\nstatic int testTimeout(int verbosity);\nstatic void timeoutHandler(DdManager * dd, void * arg);\n/** \\endcond */\n\n/**\n * @brief Main program for testextra.\n */\nint main(int argc, char const * const * argv)\n{\n  int verbosity = 0;\n  if (argc == 2) {\n    int nread;\n    int ret = sscanf(argv[1], \"%d%n\", &verbosity, &nread);\n    if (ret != 1 || argv[1][nread]) {\n      fprintf(stderr, \"Usage: %s [verbosity]\\n\", argv[0]);\n      return -1;\n    }\n  }\n  if (testBdd(verbosity) != 0)\n    return -1;\n  if (testAdd(verbosity) != 0)\n    return -1;\n  if (testZdd(verbosity) != 0)\n    return -1;\n  if (testApa(verbosity) != 0)\n    return -1;\n  if (testCount(verbosity) != 0)\n    return -1;\n  if (testLdbl(verbosity) != 0)\n    return -1;\n  if (testTimeout(verbosity) != 0)\n    return -1;\n  return 0;\n}\n\n/**\n * @brief Basic BDD test.\n * @return 0 if successful; -1 otherwise.\n */\nstatic int\ntestBdd(int verbosity)\n{\n  DdManager *dd;\n  DdNode *f, *var, *tmp;\n  int i, ret;\n\n  dd = Cudd_Init(0, 0, CUDD_UNIQUE_SLOTS, CUDD_CACHE_SLOTS, 0);\n  if (!dd) {\n    if (verbosity) {\n      printf(\"initialization failed\\n\");\n    }\n    return -1;\n  }\n  if (verbosity) {\n    printf(\"Started CUDD version \");\n    Cudd_PrintVersion(stdout);\n  }\n  f = Cudd_ReadOne(dd);\n  Cudd_Ref(f);\n  for (i = 3; i >= 0; i--) {\n    var = Cudd_bddIthVar(dd, i);\n    tmp = Cudd_bddAnd(dd, Cudd_Not(var), f);\n    if (!tmp) {\n      if (verbosity) {\n        printf(\"computation failed\\n\");\n      }\n      return -1;\n    }\n    Cudd_Ref(tmp);\n    Cudd_RecursiveDeref(dd, f);\n    f = tmp;\n  }\n  if (verbosity) {\n    Cudd_bddPrintCover(dd, f, f);\n  }\n  Cudd_RecursiveDeref(dd, f);\n  ret = Cudd_CheckZeroRef(dd);\n  if (ret != 0 && verbosity) {\n    printf(\"%d unexpected non-zero references\\n\", ret);\n  }\n  Cudd_Quit(dd);\n  return 0;\n}\n\n/**\n * @brief Basic ADD test.\n * @return 0 if successful; -1 otherwise.\n */\nstatic int\ntestAdd(int verbosity)\n{\n  DdManager *manager;\n  DdNode *f, *var, *tmp, *bg;\n  int i, ret;\n  CUDD_VALUE_TYPE pinf;\n\n  manager = Cudd_Init(0, 0, CUDD_UNIQUE_SLOTS, CUDD_CACHE_SLOTS, 0);\n  if (!manager) {\n    if (verbosity) {\n      printf(\"initialization failed\\n\");\n    }\n    return -1;\n  }\n  pinf = Cudd_V(Cudd_ReadPlusInfinity(manager));\n  if (verbosity) {\n    printf(\"Plus infinity is %g\\n\", pinf);\n  }\n  f = Cudd_addConst(manager,5);\n  Cudd_Ref(f);\n  for (i = 3; i >= 0; i--) {\n    var = Cudd_addIthVar(manager,i);\n    Cudd_Ref(var);\n    tmp = Cudd_addApply(manager,Cudd_addTimes,var,f);\n    Cudd_Ref(tmp);\n    Cudd_RecursiveDeref(manager,f);\n    Cudd_RecursiveDeref(manager,var);\n    f = tmp;\n  }\n  if (verbosity) {\n    Cudd_PrintMinterm(manager, f);\n    printf(\"\\n\");\n  }\n  Cudd_RecursiveDeref(manager, f);\n  bg = Cudd_ReadBackground(manager);\n  if (verbosity) {\n    printf(\"background (%g) minterms : \", Cudd_V(bg));\n    Cudd_ApaPrintMinterm(Cudd_ReadStdout(manager), manager, bg, 0);\n  }\n  ret = Cudd_CheckZeroRef(manager);\n  if (ret != 0 && verbosity) {\n    printf(\"%d non-zero ADD reference counts after dereferencing\\n\", ret);\n  }\n  Cudd_Quit(manager);\n  return ret != 0;\n}\n\n/**\n * @brief Basic test of ZDDs.\n * @return 0 if successful; -1 otherwise.\n */\nstatic int\ntestZdd(int verbosity)\n{\n  DdManager *manager;\n  DdNode *f, *var, *tmp;\n  int i, ret;\n\n  manager = Cudd_Init(0,4,CUDD_UNIQUE_SLOTS, CUDD_CACHE_SLOTS,0);\n  if (!manager) {\n    if (verbosity) {\n      printf(\"initialization failed\\n\");\n    }\n    return -1;\n  }\n  tmp = Cudd_ReadZddOne(manager,0);\n  Cudd_Ref(tmp);\n  for (i = 3; i >= 0; i--) {\n    var = Cudd_zddIthVar(manager,i);\n    Cudd_Ref(var);\n    f = Cudd_zddIntersect(manager,var,tmp);\n    Cudd_Ref(f);\n    Cudd_RecursiveDerefZdd(manager,tmp);\n    Cudd_RecursiveDerefZdd(manager,var);\n    tmp = f;\n  }\n  f = Cudd_zddDiff(manager,Cudd_ReadZddOne(manager,0),tmp);\n  Cudd_Ref(f);\n  Cudd_RecursiveDerefZdd(manager,tmp);\n  if (verbosity) {\n    Cudd_zddPrintMinterm(manager,f);\n    printf(\"\\n\");\n  }\n  Cudd_RecursiveDerefZdd(manager,f);\n  ret = Cudd_CheckZeroRef(manager);\n  if (ret != 0 && verbosity) {\n    printf(\"%d unexpected non-zero references\\n\", ret);\n  }\n  Cudd_Quit(manager);\n  return 0;\n}\n\n/**\n * @brief Basic test of arbitrary-precision arithmetic.\n * @return 0 if successful; -1 otherwise.\n */\nstatic int\ntestApa(int verbosity)\n{\n  if (verbosity) {\n    printf(\"DD_APA_BITS = %\" PRIszt \"\\n\", sizeof(DdApaDigit) * 8);\n  }\n  DdApaNumber an = Cudd_NewApaNumber(3);\n  Cudd_ApaSetToLiteral(3, an, (DdApaDigit) 0x0fa5);\n  Cudd_ApaAdd(3, an, an, an);\n  if (verbosity) {\n    Cudd_ApaPrintHex(stdout, 3, an);\n    printf(\"\\n\");\n  }\n  DdApaDigit numbers[] = {1283805, 1283815, 15983557, 1598354, 15999999};\n  size_t i;\n  for (i = 0; i < sizeof(numbers)/sizeof(DdApaDigit); i++) {\n    Cudd_ApaSetToLiteral(3, an, numbers[i]);\n    if (verbosity) {\n      Cudd_ApaPrintDecimal(stdout, 3, an);\n      printf(\" -> \");\n      Cudd_ApaPrintExponential(stdout, 3, an, 6);\n      printf(\"\\n\");\n    }\n  }\n  Cudd_FreeApaNumber(an);\n  return 0;\n}\n\n/**\n * @brief Basic test of Cudd_CountMinterm().\n * @return 0 if successful; -1 otherwise.\n */\nstatic int\ntestCount(int verbosity)\n{\n  DdManager *dd;\n  DdNode *h;\n  int i, ret;\n  int const N = 2044; /* number of variables */\n\n  dd = Cudd_Init(N, 0, CUDD_UNIQUE_SLOTS, CUDD_CACHE_SLOTS, 0);\n  if (!dd) {\n    if (verbosity) {\n      printf(\"initialization failed\\n\");\n    }\n    return -1;\n  }\n  /* Build a cube with N/2 variables. */\n  h = Cudd_ReadOne(dd);\n  Cudd_Ref(h);\n  for (i = 0; i < N; i += 2) {\n    DdNode *var, *tmp;\n    var = Cudd_bddIthVar(dd, N-i-1);\n    tmp = Cudd_bddAnd(dd, h, var);\n    if (!tmp) {\n      Cudd_Quit(dd);\n      return -1;\n    }\n    Cudd_Ref(tmp);\n    Cudd_RecursiveDeref(dd, h);\n    h = tmp;\n  }\n  if (verbosity) {\n    printf(\"h (dbl) \");\n    Cudd_PrintDebug(dd, h, N, 1);\n    printf(\"h (apa) \");\n    Cudd_PrintSummary(dd, h, N, 1);\n  }\n  Cudd_RecursiveDeref(dd, h);\n  if (verbosity) {\n    printf(\"one[%d] (dbl) \", N);\n    Cudd_PrintDebug(dd, Cudd_ReadOne(dd), N, 1);\n    printf(\"one[%d] (apa) \", N);\n    Cudd_PrintSummary(dd, Cudd_ReadOne(dd), N, 1);\n    ret = Cudd_CheckZeroRef(dd);\n    printf(\"one[%d] (dbl) \", N+1);\n    Cudd_PrintDebug(dd, Cudd_ReadOne(dd), N+1, 1);\n    printf(\"one[%d] (apa) \", N+1);\n    Cudd_PrintSummary(dd, Cudd_ReadOne(dd), N+1, 1);\n    ret = Cudd_CheckZeroRef(dd);\n  }\n  if (verbosity && ret != 0) {\n    printf(\"%d non-zero references\\n\", ret);\n  }\n  Cudd_Quit(dd);\n  return 0;\n}\n\n/**\n * @brief Basic test of long double and EPD minterm computation.\n * @return 0 if successful; -1 otherwise.\n */\nstatic int\ntestLdbl(int verbosity)\n{\n  DdManager *dd;\n  DdNode *f, *g;\n  int i, ret;\n  int const N = 12; /* half the number of variables */\n  long double cnt;\n\n  dd = Cudd_Init(2*N, 0, CUDD_UNIQUE_SLOTS, CUDD_CACHE_SLOTS, 0);\n  if (!dd) {\n    if (verbosity) {\n      printf(\"initialization failed\\n\");\n    }\n    return -1;\n  }\n  f = g = Cudd_ReadOne(dd);\n  Cudd_Ref(f);\n  Cudd_Ref(g);\n  for (i = 0; i < N; i++) {\n    DdNode *var1, *var2, *clause, *tmp;\n    var1 = Cudd_bddIthVar(dd, i);\n    var2 = Cudd_bddIthVar(dd, i+N);\n    clause = Cudd_bddOr(dd, var1, var2);\n    if (!clause) {\n      Cudd_Quit(dd);\n      return -1;\n    }\n    Cudd_Ref(clause);\n    tmp = Cudd_bddAnd(dd, f, clause);\n    if (!tmp) {\n      Cudd_Quit(dd);\n      return -1;\n    }\n    Cudd_Ref(tmp);\n    Cudd_RecursiveDeref(dd, clause);\n    Cudd_RecursiveDeref(dd, f);\n    f = tmp;\n    clause = Cudd_bddOr(dd, Cudd_Not(var1), Cudd_Not(var2));\n    if (!clause) {\n      Cudd_Quit(dd);\n      return -1;\n    }\n    Cudd_Ref(clause);\n    tmp = Cudd_bddAnd(dd, g, clause);\n    if (!tmp) {\n      Cudd_Quit(dd);\n      return -1;\n    }\n    Cudd_Ref(tmp);\n    Cudd_RecursiveDeref(dd, clause);\n    Cudd_RecursiveDeref(dd, g);\n    g = tmp;\n  }\n  if (verbosity) {\n    printf(\"f\");\n    Cudd_PrintSummary(dd, f, 2*N, 0);\n  }\n  cnt = Cudd_LdblCountMinterm(dd, f, 2*N);\n  if (verbosity) {\n    printf(\"f has %Lg minterms\\n\", cnt);\n  }\n  if (verbosity) {\n    printf(\"EPD count for f = \");\n    ret = Cudd_EpdPrintMinterm(dd, f, 2*N);\n    printf(\"\\n\");\n    if (!ret) {\n      printf(\"problem with EPD\\n\");\n    }\n  }\n  Cudd_RecursiveDeref(dd, f);\n  if (verbosity) {\n    printf(\"g\");\n    Cudd_PrintSummary(dd, g, 2*N, 0);\n  }\n  cnt = Cudd_LdblCountMinterm(dd, g, 2*N);\n  if (verbosity) {\n    printf(\"g has %Lg minterms\\n\", cnt);\n  }\n  if (verbosity) {\n    printf(\"EPD count for g = \");\n    ret = Cudd_EpdPrintMinterm(dd, g, 2*N);\n    printf(\"\\n\");\n    if (!ret) {\n      printf(\"problem with EPD\\n\");\n    }\n  }\n  Cudd_RecursiveDeref(dd, g);\n  ret = Cudd_CheckZeroRef(dd);\n  if (verbosity && ret != 0) {\n    printf(\"%d non-zero references\\n\", ret);\n  }\n  Cudd_Quit(dd);\n  return 0;\n}\n\n\n/**\n * @brief Basic test of timeout handler.\n *\n * @details Sets a short timeout and then tries to build a function\n * with a large BDD.  Strives to avoid leaking nodes.\n *\n * @return 0 if successful; -1 otherwise.\n */\nstatic int\ntestTimeout(int verbosity)\n{\n  DdManager *dd;\n  /* Declare these \"volatile\" to prevent clobbering by longjmp. */\n  DdNode * volatile f;\n  DdNode * volatile clause = NULL;\n  DdNode * var1, * var2;\n  int i, ret, count;\n  int const N = 20; /* half the number of variables in f */\n  unsigned long timeout = 100UL; /* in milliseconds */\n  jmp_buf timeoutEnv;\n\n  dd = Cudd_Init(0, 0, CUDD_UNIQUE_SLOTS, CUDD_CACHE_SLOTS, 0);\n  if (!dd) {\n    if (verbosity) {\n      printf(\"initialization failed\\n\");\n    }\n    return -1;\n  }\n\n  /* Set up timeout handling. */\n  if (setjmp(timeoutEnv) > 0) {\n    if (verbosity) {\n      printf(\"caught timeout\\n\");\n    }\n    /* The nodes of clause may be leaked if the timeout was\n     * detected while conjoining the clause to f.  We set\n     * clause to NULL when it's not in use to be able to\n     * detect this case.\n     */\n    if (clause)\n      Cudd_RecursiveDeref(dd, clause);\n    goto finally;\n  }\n  (void) Cudd_RegisterTimeoutHandler(dd, timeoutHandler, (void *) &timeoutEnv);\n  (void) Cudd_SetTimeLimit(dd, timeout);\n\n  /* Try to build function.  This is expected to run out of time. */\n  f = Cudd_ReadOne(dd);\n  Cudd_Ref(f);\n  for (i = 0; i < N; i++) {\n    DdNode * tmp;\n    var1 = Cudd_bddIthVar(dd, i);\n    if (!var1) {\n      if (verbosity) {\n        printf(\"computation failed\\n\");\n        return -1;\n      }\n    }\n    var2 = Cudd_bddIthVar(dd, i+N);\n    if (!var2) {\n      if (verbosity) {\n        printf(\"computation failed\\n\");\n        return -1;\n      }\n    }\n    clause = Cudd_bddOr(dd, var1, var2);\n    if (!clause) {\n      if (verbosity) {\n        printf(\"computation failed\\n\");\n      }\n      return -1;\n    }\n    Cudd_Ref(clause);\n    tmp = Cudd_bddAnd(dd, f, clause);\n    if (!tmp) {\n      if (verbosity) {\n        printf(\"computation failed\\n\");\n      }\n      return -1;\n    }\n    Cudd_Ref(tmp);\n    Cudd_RecursiveDeref(dd, clause);\n    clause = NULL;\n    Cudd_RecursiveDeref(dd, f);\n    f = tmp;\n  }\n  if (verbosity > 1) {\n    Cudd_bddPrintCover(dd, f, f);\n  }\n\n finally:\n  if (verbosity) {\n    printf(\"so far\");\n    Cudd_PrintSummary(dd, f, 2*N, 0);\n  }\n  count = 0;\n  for (i = 0; i < N-1; i += 2) {\n    var1 = Cudd_bddIthVar(dd, i);\n    if (!var1) {\n      printf(\"computation failed\\n\");\n      return -1;\n    }\n    var2 = Cudd_bddIthVar(dd, i+1);\n    if (!var2) {\n      printf(\"computation failed\\n\");\n      return -1;\n    }\n    clause = Cudd_bddOr(dd, var1, var2);\n    if (!clause) {\n      printf(\"computation failed\\n\");\n      return -1;\n    }\n    Cudd_Ref(clause);\n    if (Cudd_bddLeq(dd, f, clause)) {\n      count++;\n    }\n    Cudd_RecursiveDeref(dd, clause);\n  }\n  if (verbosity) {\n    printf(\"f implies %d clauses\\n\", count);\n  }\n  Cudd_RecursiveDeref(dd, f);\n  ret = Cudd_CheckZeroRef(dd);\n  if (verbosity) {\n    Cudd_PrintInfo(dd, stdout);\n    if (ret != 0) {\n      printf(\"%d non-zero references\\n\", ret);\n    }\n  }\n  Cudd_Quit(dd);\n  return 0;\n}\n\n/**\n * @brief Timeout handler.\n */\nstatic void\ntimeoutHandler(DdManager * dd, void * arg)\n{\n  jmp_buf * timeoutEnv = (jmp_buf *) arg;\n  /* Reset manager. */\n  Cudd_ClearErrorCode(dd);\n  Cudd_UnsetTimeLimit(dd);\n  Cudd_RegisterTimeoutHandler(dd, NULL, NULL);\n\n  longjmp(*timeoutEnv, 1);\n}\n"
  },
  {
    "path": "cudd/dddmp/Included.am",
    "content": "dddmp_sources = dddmp/dddmp.h dddmp/dddmpInt.h \\\n  dddmp/dddmpBinary.c dddmp/dddmpConvert.c dddmp/dddmpDbg.c \\\n  dddmp/dddmpLoad.c dddmp/dddmpLoadCnf.c dddmp/dddmpNodeAdd.c \\\n  dddmp/dddmpNodeBdd.c dddmp/dddmpNodeCnf.c dddmp/dddmpStoreAdd.c \\\n  dddmp/dddmpStoreBdd.c dddmp/dddmpStoreCnf.c dddmp/dddmpStoreMisc.c \\\n  dddmp/dddmpUtil.c\n\nif DDDMP\ncudd_libcudd_la_SOURCES += $(dddmp_sources)\nelse\nnoinst_LTLIBRARIES += dddmp/libdddmp.la\ndddmp_libdddmp_la_SOURCES = $(dddmp_sources)\ndddmp_libdddmp_la_CPPFLAGS = -I$(top_srcdir)/util -I$(top_srcdir)/mtr \\\n  -I$(top_srcdir)/epd -I$(top_srcdir)/cudd -I$(top_srcdir)/st\nendif !DDDMP\n\ncheck_PROGRAMS += dddmp/testdddmp\ndddmp_testdddmp_SOURCES = dddmp/testdddmp.c\nif DDDMP\ndddmp_testdddmp_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\ndddmp_testdddmp_LDADD =\nelse\ndddmp_testdddmp_CPPFLAGS = $(dddmp_libdddmp_la_CPPFLAGS)\ndddmp_testdddmp_LDADD = dddmp/libdddmp.la\nendif !DDDMP\ndddmp_testdddmp_LDADD += cudd/libcudd.la\n\ncheck_SCRIPTS += dddmp/test_dddmp.test\nif !CROSS_COMPILING\nTESTS += dddmp/test_dddmp.test\nendif !CROSS_COMPILING\nEXTRA_DIST += dddmp/README.dddmp dddmp/README.testdddmp dddmp/RELEASE_NOTES \\\n  dddmp/doc dddmp/test_dddmp.test.in dddmp/exp/test1.sh.in \\\n  dddmp/exp/test2.sh.in dddmp/exp/test3.sh.in dddmp/exp/test4.sh.in \\\n  dddmp/exp/test5.sh.in dddmp/exp/test6.sh.in dddmp/exp/test7.sh.in \\\n  dddmp/exp/0.add dddmp/exp/0.bdd dddmp/exp/0or1.bdd dddmp/exp/1.add \\\n  dddmp/exp/1.bdd dddmp/exp/2and3.bdd dddmp/exp/2.bdd dddmp/exp/3.bdd \\\n  dddmp/exp/4.bdd dddmp/exp/4.bdd.bis1 dddmp/exp/4.bdd.bis2 \\\n  dddmp/exp/4.bdd.bis3 dddmp/exp/4.bdd.bis4 dddmp/exp/4bis.bdd dddmp/exp/4.cnf \\\n  dddmp/exp/4.cnf.bis dddmp/exp/4.max1 dddmp/exp/4.max2 dddmp/exp/4xor5.bdd \\\n  dddmp/exp/5.bdd dddmp/exp/composeids.txt dddmp/exp/one.bdd \\\n  dddmp/exp/s27deltaDddmp1.bdd dddmp/exp/s27deltaDddmp1.bdd.bis \\\n  dddmp/exp/s27deltaDddmp2.bdd dddmp/exp/s27RP1.bdd dddmp/exp/varauxids.ord \\\n  dddmp/exp/varnames.ord dddmp/exp/zero.bdd\n\ndddmp/test_dddmp.test: dddmp/test_dddmp.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\nCLEANFILES +=  dddmp/exp/test1.sh dddmp/exp/test2.sh dddmp/exp/test3.sh \\\n  dddmp/exp/test4.sh dddmp/exp/test5.sh dddmp/exp/test6.sh dddmp/exp/test7.sh\n"
  },
  {
    "path": "cudd/dddmp/README.dddmp",
    "content": "README file for the DDDMP-2.0 package\r\nRevision: Version 2.0.2, February 01, 2004\r\n\r\n\r\n\r\nWHAT IS DDDMP\r\n=============\r\n\r\nThe DDDMP package defines formats for DD storage on file, and it contains a\r\nset of functions to dump DDs and DD forests on file.\r\n\r\nIn the version 1.0, only BDDs (ROBDDs) of the CUDD package (version 2.2.0\r\nor higher) were supported.\r\nThe version 2.0 includes supports for ADDs and CNF formulas.\r\nThe version 2.0.2 is for bug fixes.\r\n\r\n\r\n\r\nMAKE DDDMP\r\n==========\r\n\r\nBefore you build the libraries and programs, you need to check the\r\nMakefile in the top directory.\r\nGo through the definitions contained in the configuration section, and\r\nselect the desired compiler and compilation flags.\r\nInstructions are provided in the comments of the Makefile.\r\n\r\nThen run \"make\".\r\nThis should produce the dddmplib.a library.\r\n\r\n\r\n\r\nDOCUMENTATION\r\n=============\r\n\r\nDirectory dddmp/doc contains HTML documentation for the package.\r\nThe recommended starting point is package.html.\r\nDocumentation in both postscript format and plain text format is also\r\nprovided.\r\n\r\n\r\n\r\nFTP SITE\r\n========\r\n\r\nThe package is singularly available from the author home page:\r\nhttp://staff.polito.it/{gianpiero.cabodi,stefano.quer}\r\n\r\n\r\n\r\n\r\nFEEDBACK\r\n========\r\n\r\nSend feedback to:\r\n\r\nStefano Quer & Gianpiero Cabodi\r\nPolitecnico di Torino\r\nDip. Automatica e Informatica\r\nC.so Duca degli Abruzzi 24\r\nI-10129  Torino\r\nItaly\r\nE-mail: {gianpiero.cabodi,stefano.quer}@polito.it\r\nWEB page: http://staff.polito.it/{gianpiero.cabodi,stefano.quer}\r\n"
  },
  {
    "path": "cudd/dddmp/README.testdddmp",
    "content": "README file for the test program of the DDDMP-2.0 package\r\nRevision: Version 2.0.2, February 01, 2004\r\n\r\n\r\n\r\nWHAT IS TESTDDDMP\r\n=================\r\n\r\ntestdddmp is a test program for the dddmp package.\r\nPractically, it is a naive user interface to load, store and execute\r\noperations with BDDs.\r\nIt is included to provide a sanity check for the installation of the\r\npackage and an easy tool to play with BDDs and BDD on files.\r\n\r\n\r\n\r\nMAKE TESTDDDMP\r\n==============\r\n\r\nRun \"make testdddmp\".\r\nThis should produce the testdddmp executable file.\r\n\r\n\r\n\r\nTEST DDDMP\r\n==========\r\n\r\nRun the runAllTest.script file in the exp directory.\r\nThis should run all the test?.script files in the same directory.\r\nEach of them is specifically written to check a particular feature of\r\nthe package (e.g., store and load of BDDs, store of CNF formulas and\r\nretrieval, etc.).\r\nEach test?.script should terminate with a comparison with a previously\r\ngenerated set of files, then with the following set of messages:\r\n\r\nFiles 0or1.bdd and 0or1.bdd2 are identical\r\nFiles 2and3.bdd and 2and3.bdd2 are identical\r\n...\r\n\r\nIf so everything is OK.\r\n\r\nNotice that mismatches may be caused by the presence of CR - LF characters at\r\nthe end of each BDD file line.\r\n\r\n\r\n\r\nWORK WITH DDDMPTEST\r\n===================\r\n\r\nTo work with dddmptest (once the executable file has been built) it is enough\r\nto run it (no parameter is necessary). \r\nThe help command print out the main commands available.\r\nFor each command further inputs are eventually required on an interactive\r\nbasis.\r\nBDDs and ADDs can be loaded from files by choosing the file name or they\r\ncan be directly created (randomly for example).\r\nThey can be maintained into the main memory trough an array of BDD pointers.\r\nOperations (logical and re-ordering) can be performed on any BDD into this\r\narray.\r\nEventually any of them can be stored in a file giving the file name.\r\nBDDs can also be stored in a CNF format using three different possible\r\nsolution to store them.\r\n\r\n\r\n\r\nFEEDBACK\r\n========\r\n\r\nSend feedback to:\r\n\r\nGianpiero Cabodi and Stefano Quer\r\nPolitecnico di Torino\r\nDip. Automatica e Informatica\r\nC.so Duca degli Abruzzi 24\r\nI-10129  Torino\r\nItaly\r\nE-mail: {gianpiero.cabodi,stefano.quer}@polito.it\r\nWEB page: http://staff.polito.it/{gianpiero.cabodi,stefano.quer}\r\n\r\n"
  },
  {
    "path": "cudd/dddmp/RELEASE_NOTES",
    "content": "RELEASE NOTES FOR DDDMP\nRevision: Version 2.0.2\nTurin, Italy, February 01, 2004\n\ndddmp-2.0.2 is now available at\nWEB page: http://staff.polito.it/{gianpiero.cabodi,stefano.quer}\ndddmp-2.0.2 has a few bug fixes with respect to dddmp-2.0\n   \nRelease 2.0.2 of DDDMP improves DDDMP-1.2 in the following areas:\n \n  1. Support to store and load ADD has been inserted in the dddmp tool\n\n  2. Support to store BDDs as CNF formulas has been inserted in the\n     dddmp tool.\n     As far as the storing process is concerned three possible formats\n     are available:\n\n     DDDMP_CNF_MODE_NODE\n       store a BDD by introducing an auxiliary variable for each BDD node\n\n     DDDMP_CNF_MODE_MAXTERM\n       store a BDD by following the maxterm of the represented function\n\n     DDDMP_CNF_MODE_BEST\n       trade-of between the two previous solution, trying to optimize\n       the number of literals stored.\n     \n     As far as the loading process is concerned three possible formats\n     are available:\n\n     DDDMP_CNF_MODE_NO_CONJ\n       Return the Clauses without Conjunction\n\n     DDDMP_CNF_MODE_NO_QUANT\n       Return the sets of BDDs without Quantification\n\n     DDDMP_CNF_MODE_CONJ_QUANT\n       Return the sets of BDDs AFTER Existential Quantification\n\n  3. Functions to load the header of a BDD/ADD/CNF file, so collecting\n     information regarding variables, variable ordering, etc.\n     This can be seen as a pre-processing step prior a possible BDD/ADD/CNF\n     load of the entire structure.\n     Moreover it can be used in a manager initialization phase.\n\n  4. More precise information are stored in each BDD/ADD header during\n     the storing phase.\n     In particular this information may be used to make up the exact\n     variable ordering present in the manager used during the storing\n     phase.\n     Full compatibility with previously versions of the files (from\n     dddmp-1.0 on) is guaranteed.\n\n  5. Miscellaneous\n     Debugging has been performed on different hardware architectures\n\n  6. The test program, testdddmp has been improved.\n     Now it allows to perform more operations and to better debug the\n     different options.\n\n"
  },
  {
    "path": "cudd/dddmp/dddmp.h",
    "content": "/**CHeaderFile*****************************************************************\n\n  FileName     [dddmp.h]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to read in and write out BDDs, ADDs\n    and CNF formulas from and to files.]\n\n  Description  []\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2002 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#ifndef _DDDMP\n#define _DDDMP\n\n#if 0\n#define DDDMP_DEBUG\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n     \n#include \"util.h\"\n#include \"cudd.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* \n *  Dddmp format version \n */\n\n#define DDDMP_VERSION           \"DDDMP-2.0\"\n\n/* \n *  Returned values (for theorically ALL the function of the package)\n */\n\n#define DDDMP_FAILURE 0\n#define DDDMP_SUCCESS 1\n\n/* \n *  Format modes for DD (BDD and ADD) files\n */\n\n#define DDDMP_MODE_TEXT           ((int)'A')\n#define DDDMP_MODE_BINARY         ((int)'B')\n#define DDDMP_MODE_DEFAULT        ((int)'D')\n\n/*---------------------------------------------------------------------------*/\n/* Structure declarations                                                    */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**Enum************************************************************************\n\n  Synopsis    [Format modes for storing CNF files]\n\n  Description [Type supported for storing BDDs into CNF\n    formulas.\n    Used internally to select the proper storing format:\n      DDDMP_CNF_MODE_NODE: create a CNF temporary variables for\n                           each BDD node\n      DDDMP_CNF_MODE_MAXTERM: no temporary variables\n      DDDMP_CNF_MODE_BEST: trade-off between the two previous methods\n    ]\n\n******************************************************************************/\n\ntypedef enum {\n  DDDMP_CNF_MODE_NODE,\n  DDDMP_CNF_MODE_MAXTERM,\n  DDDMP_CNF_MODE_BEST\n} Dddmp_DecompCnfStoreType;\n\n/**Enum************************************************************************\n\n  Synopsis    [Format modes for loading CNF files.]\n\n  Description [Type supported for loading CNF formulas into BDDs.\n    Used internally to select the proper returning format:\n    ]\n\n******************************************************************************/\n\ntypedef enum {\n  DDDMP_CNF_MODE_NO_CONJ,\n  DDDMP_CNF_MODE_NO_QUANT,\n  DDDMP_CNF_MODE_CONJ_QUANT\n} Dddmp_DecompCnfLoadType;\n\n/**Enum************************************************************************\n\n  Synopsis    [Type for supported decomposition types.]\n\n  Description [Type for supported decomposition types.\n    Used internally to select the proper type (bdd, add, ...).\n    Given externally as information fule content.\n    ]\n\n******************************************************************************/\n\ntypedef enum {\n  DDDMP_BDD,\n  DDDMP_ADD,\n  DDDMP_CNF,\n  DDDMP_NONE\n} Dddmp_DecompType;\n\n\n/**Enum************************************************************************\n\n  Synopsis    [Type for variable extra info.]\n\n  Description [Type for variable extra info. Used to specify info stored\n    in text mode.]\n\n******************************************************************************/\n\ntypedef enum {\n  DDDMP_VARIDS,\n  DDDMP_VARPERMIDS,\n  DDDMP_VARAUXIDS,\n  DDDMP_VARNAMES,\n  DDDMP_VARDEFAULT\n} Dddmp_VarInfoType;\n\n/**Enum************************************************************************\n\n  Synopsis    [Type for variable matching in BDD load.]\n\n  Description []\n\n******************************************************************************/\n\ntypedef enum {\n  DDDMP_VAR_MATCHIDS,\n  DDDMP_VAR_MATCHPERMIDS,\n  DDDMP_VAR_MATCHAUXIDS,\n  DDDMP_VAR_MATCHNAMES,\n  DDDMP_VAR_COMPOSEIDS\n} Dddmp_VarMatchType;\n\n/**Enum************************************************************************\n\n  Synopsis    [Type for BDD root matching in BDD load.]\n\n  Description []\n\n******************************************************************************/\n\ntypedef enum {\n  DDDMP_ROOT_MATCHNAMES,\n  DDDMP_ROOT_MATCHLIST\n} Dddmp_RootMatchType;\n\ntypedef struct Dddmp_Hdr_s Dddmp_Hdr_t;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**Macro***********************************************************************\n \n  Synopsis    [Checks for fatal bugs]\n \n  Description [Conditional safety assertion. It prints out the file\n    name and line number where the fatal error occurred.\n    Messages are printed out on stderr.\n    ]\n \n  SideEffects [None]\n \n  SeeAlso     []\n \n******************************************************************************/\n \n#ifdef DDDMP_DEBUG\n#  define Dddmp_Assert(expr,errMsg) \\\n     { \\\n     if ((expr) == 0) { \\\n       fprintf (stderr, \"FATAL ERROR: %s\\n\", errMsg); \\\n       fprintf (stderr, \"             File %s -> Line %d\\n\", \\\n         __FILE__, __LINE__); \\\n       fflush (stderr); \\\n       exit (DDDMP_FAILURE); \\\n       } \\\n     }\n#else\n#  define Dddmp_Assert(expr,errMsg) \\\n     {}\n#endif\n\n/**Macro***********************************************************************\n \n  Synopsis    [Checks for Warnings: If expr==1 it prints out the warning\n    on stderr.]\n \n  Description []\n \n  SideEffects [None]\n \n  SeeAlso     []\n \n******************************************************************************/\n \n#define Dddmp_Warning(expr,errMsg) \\\n  { \\\n  if ((expr) == 1) { \\\n    fprintf (stderr, \"WARNING: %s\\n\", errMsg); \\\n    fprintf (stderr, \"         File %s -> Line %d\\n\", \\\n      __FILE__, __LINE__); \\\n    fflush (stderr); \\\n    } \\\n  }\n\n/**Macro***********************************************************************\n \n  Synopsis    [Checks for fatal bugs and return the DDDMP_FAILURE flag.]\n \n  Description []\n \n  SideEffects [None]\n \n  SeeAlso     []\n \n******************************************************************************/\n \n#define Dddmp_CheckAndReturn(expr,errMsg) \\\n  { \\\n  if ((expr) == 1) { \\\n    fprintf (stderr, \"FATAL ERROR: %s\\n\", errMsg); \\\n    fprintf (stderr, \"             File %s -> Line %d\\n\", \\\n      __FILE__, __LINE__); \\\n    fflush (stderr); \\\n    return (DDDMP_FAILURE); \\\n    } \\\n  }\n\n/**Macro***********************************************************************\n \n  Synopsis    [Checks for fatal bugs and go to the label to deal with\n    the error.\n    ]\n \n  Description []\n \n  SideEffects [None]\n \n  SeeAlso     []\n \n******************************************************************************/\n \n#define Dddmp_CheckAndGotoLabel(expr,errMsg,label) \\\n  { \\\n  if ((expr) == 1) { \\\n    fprintf (stderr, \"FATAL ERROR: %s\\n\", errMsg); \\\n    fprintf (stderr, \"             File %s -> Line %d\\n\", \\\n      __FILE__, __LINE__); \\\n    fflush (stderr); \\\n    goto label; \\\n    } \\\n  }\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\nextern int Dddmp_Text2Bin(char *filein, char *fileout);\nextern int Dddmp_Bin2Text(char *filein, char *fileout);\nextern int Dddmp_cuddBddDisplayBinary(char *fileIn, char *fileOut);\nextern DdNode * Dddmp_cuddBddLoad(DdManager *ddMgr, Dddmp_VarMatchType varMatchMode, char **varmatchnames, int *varmatchauxids, int *varcomposeids, int mode, char *file, FILE *fp);\nextern int Dddmp_cuddBddArrayLoad(DdManager *ddMgr, Dddmp_RootMatchType rootMatchMode, char **rootmatchnames, Dddmp_VarMatchType varMatchMode, char **varmatchnames, int *varmatchauxids, int *varcomposeids, int mode, char *file, FILE *fp, DdNode ***pproots);\nextern DdNode * Dddmp_cuddAddLoad(DdManager *ddMgr, Dddmp_VarMatchType varMatchMode, char **varmatchnames, int *varmatchauxids, int *varcomposeids, int mode, char *file, FILE *fp);\nextern int Dddmp_cuddAddArrayLoad(DdManager *ddMgr, Dddmp_RootMatchType rootMatchMode, char **rootmatchnames, Dddmp_VarMatchType varMatchMode, char **varmatchnames, int *varmatchauxids, int *varcomposeids, int mode, char *file, FILE *fp, DdNode ***pproots);\nextern int Dddmp_cuddHeaderLoad (Dddmp_DecompType *ddType, int *nVars, int *nsuppvars, char ***suppVarNames, char ***orderedVarNames, int **varIds, int **composeIds, int **auxIds, int *nRoots, char *file, FILE *fp);\nextern int Dddmp_cuddBddLoadCnf(DdManager *ddMgr, Dddmp_VarMatchType varmatchmode, char **varmatchnames, int *varmatchauxids, int *varcomposeids, int mode, char *file, FILE *fp, DdNode ***rootsPtrPtr, int *nRoots);\nextern int Dddmp_cuddBddArrayLoadCnf(DdManager *ddMgr, Dddmp_RootMatchType rootmatchmode, char **rootmatchnames, Dddmp_VarMatchType varmatchmode, char **varmatchnames, int *varmatchauxids, int *varcomposeids, int mode, char *file, FILE *fp, DdNode ***rootsPtrPtr, int *nRoots);\nextern int Dddmp_cuddHeaderLoadCnf (int *nVars, int *nsuppvars, char ***suppVarNames, char ***orderedVarNames, int **varIds, int **composeIds, int **auxIds, int *nRoots, char *file, FILE *fp);\nextern int Dddmp_cuddAddStore(DdManager *ddMgr, char *ddname, DdNode *f, char **varnames, int *auxids, int mode, Dddmp_VarInfoType varinfo, char *fname, FILE *fp);\nextern int Dddmp_cuddAddArrayStore(DdManager *ddMgr, char *ddname, int nRoots, DdNode **f, char **rootnames, char **varnames, int *auxids, int mode, Dddmp_VarInfoType varinfo, char *fname, FILE *fp);\nextern int Dddmp_cuddBddStore(DdManager *ddMgr, char *ddname, DdNode *f, char **varnames, int *auxids, int mode, Dddmp_VarInfoType varinfo, char *fname, FILE *fp);\nextern int Dddmp_cuddBddArrayStore(DdManager *ddMgr, char *ddname, int nRoots, DdNode **f, char **rootnames, char **varnames, int *auxids, int mode, Dddmp_VarInfoType varinfo, char *fname, FILE *fp);\nextern int Dddmp_cuddBddStoreCnf(DdManager *ddMgr, DdNode *f, Dddmp_DecompCnfStoreType mode, int noHeader, char **varNames, int *bddIds, int *bddAuxIds, int *cnfIds, int idInitial, int edgeInTh, int pathLengthTh, char *fname, FILE *fp, int *clauseNPtr, int *varNewNPtr);\nextern int Dddmp_cuddBddArrayStoreCnf(DdManager *ddMgr, DdNode **f, int rootN, Dddmp_DecompCnfStoreType mode, int noHeader, char **varNames, int *bddIds, int *bddAuxIds, int *cnfIds, int idInitial, int edgeInTh, int pathLengthTh, char *fname, FILE *fp, int *clauseNPtr, int *varNewNPtr);\nextern int Dddmp_cuddBddStorePrefix(DdManager *ddMgr, int nRoots, DdNode *f, char **inputNames, char **outputNames, char *modelName, char *fileName, FILE *fp);\nextern int Dddmp_cuddBddArrayStorePrefix(DdManager *ddMgr, int nroots, DdNode **f, char **inputNames, char **outputNames, char *modelName, char *fname, FILE *fp);\nextern int Dddmp_cuddBddStoreBlif(DdManager *ddMgr, int nRoots, DdNode *f, char **inputNames, char **outputNames, char *modelName, char *fileName, FILE *fp);\nextern int Dddmp_cuddBddArrayStoreBlif(DdManager *ddMgr, int nroots, DdNode **f, char **inputNames, char **outputNames, char *modelName, char *fname, FILE *fp);\nextern int Dddmp_cuddBddStoreSmv(DdManager *ddMgr, int nRoots, DdNode *f, char **inputNames, char **outputNames, char *modelName, char *fileName, FILE *fp);\nextern int Dddmp_cuddBddArrayStoreSmv(DdManager *ddMgr, int nroots, DdNode **f, char **inputNames, char **outputNames, char *modelName, char *fname, FILE *fp);\n\n/**AutomaticEnd***************************************************************/\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif\n"
  },
  {
    "path": "cudd/dddmp/dddmpBinary.c",
    "content": "/**CFile**********************************************************************\n\n  FileName    [dddmpBinary.c]\n\n  PackageName [dddmp]\n\n  Synopsis    [Input and output BDD codes and integers from/to file]\n\n  Description [Input and output BDD codes and integers from/to file\n    in binary mode.\n    DD node codes are written as one byte.\n    Integers of any length are written as sequences of \"linked\" bytes.\n    For each byte 7 bits are used for data and one (MSBit) as link with\n    a further byte (MSB = 1 means one more byte).\n    Low level read/write of bytes filter <CR>, <LF> and <ctrl-Z>\n    with escape sequences.\n    ]\n\n  Author      [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright   [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int WriteByteBinary(FILE *fp, unsigned char c);\nstatic int ReadByteBinary(FILE *fp, unsigned char *cp);\n\n/**AutomaticEnd***************************************************************/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [Writes 1 byte node code]\n\n  Description [outputs a 1 byte node code using the following format:\n     <pre>\n     Unused      : 1 bit;\n     V           : 2 bits;     (variable code)\n     T           : 2 bits;     (Then code)\n     Ecompl      : 1 bit;      (Else complemented)\n     E           : 2 bits;     (Else code)\n    </pre>\n    Ecompl is set with complemented edges.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpReadCode()]\n\n******************************************************************************/\n\nint\nDddmpWriteCode (\n  FILE *fp                   /* IN: file where to write the code */,\n  struct binary_dd_code code /* IN: the code to be written */\n  )\n{\n  unsigned char c;\n  int retValue;\n\n  c = (code.Unused<<7)|(code.V<<5)|(code.T<<3)|\n\t\t(code.Ecompl<<2)|(code.E);\n\n  retValue = WriteByteBinary (fp, c);\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a 1 byte node code]\n\n  Description [Reads a 1 byte node code. See DddmpWriteCode()\n    for code description.]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpWriteCode()]\n\n******************************************************************************/\n\nint \nDddmpReadCode (\n  FILE *fp                     /*  IN: file where to read the code */,\n  struct binary_dd_code *pcode /* OUT: the read code */\n  )\n{\n  unsigned char c;\n\n  if (ReadByteBinary (fp, &c) == EOF) {\n    return (0);\n  }\n\n  pcode->Unused =  c>>7;\n  pcode->V      = (c>>5) & 3;\n  pcode->T      = (c>>3) & 3;\n  pcode->Ecompl = (c>>2) & 1;\n  pcode->E      =  c     & 3;\n\n  return (1);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Writes a \"packed integer\"]\n\n  Description [Writes an integer as a sequence of bytes (MSByte first).\n    For each byte 7 bits are used for data and one (LSBit) as link \n    with a further byte (LSB = 1 means one more byte).\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpReadInt()]\n\n******************************************************************************/\n\nint \nDddmpWriteInt (\n  FILE *fp   /* IN: file where to write the integer */,\n  int id     /* IN: integer to be written */\n  )\n{\n  char cvet[4];\n  int i;\n\n  for (i=0; i<4; i++) {\n    cvet[i] = (char)((id & 0x0000007f) << 1);\n    id >>= 7;\n  }\n\n  for (i=3; (i>0) && (cvet[i] == 0); i--);\n\n  for (; i>0; i--) {\n    cvet[i] |= (char)1;\n    if (WriteByteBinary (fp, cvet[i]) == EOF)\n      return (0);\n  }\n\n  if (WriteByteBinary (fp, cvet[0]) == EOF) {\n    return (0);\n  }\n\n  return (1);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a \"packed integer\"]\n\n  Description [Reads an integer coded on a sequence of bytes. See\n    DddmpWriteInt() for format.]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpWriteInt()]\n\n******************************************************************************/\n\nint\nDddmpReadInt (\n  FILE *fp   /*  IN: file where to read the integer */,\n  int *pid   /* OUT: the read integer */\n  )\n{\n  unsigned char c;\n  int i;\n  unsigned int id;\n\n  id = 0;\n  for (i=0; i<4; i++) {\n    if (ReadByteBinary (fp, &c) == EOF)\n      return (0);\n    id = (id<<7) | (c>>1);\n    if ((c & 1) == 0)\n      break;\n  }\n\n /* Check for correct format: last char should \n    be found before i = 4 */\n  assert(i<4);\n\n  *pid = id;\n\n  return (i+1);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [Writes a byte to file filtering <CR>, <LF> and <ctrl-Z>]\n\n  Description [outputs a byte to file fp. Uses 0x00 as escape character\n    to filter <CR>, <LF> and <ctrl-Z>.\n    This is done for compatibility between unix and dos/windows systems.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [ReadByteBinary()]\n\n******************************************************************************/\n\nstatic int\nWriteByteBinary (\n  FILE *fp         /* IN: file where to write the byte */,\n  unsigned char c  /* IN: the byte to be written */\n  )\n{\n  unsigned char BinaryEscape;\n \n  switch (c) {\n\n    case 0x00: /* Escape */\n      BinaryEscape = 0x00;\n      if (fwrite (&BinaryEscape, sizeof(char), 1, fp) != sizeof(char))\n        return (0);\n      c = 0x00;\n      break;\n    case 0x0a: /* <LF> */\n      BinaryEscape = 0x00;\n      if (fwrite (&BinaryEscape, sizeof(char), 1, fp) != sizeof(char))\n        return (0);\n      c = 0x01;\n      break;\n    case 0x0d: /* <CR> */\n      BinaryEscape = 0x00;\n      if (fwrite (&BinaryEscape, sizeof(char), 1, fp) != sizeof(char))\n        return (0);\n      c = 0x02;\n      break;\n    case 0x1a: /* <ctrl-Z> */\n      BinaryEscape = 0x00;\n      if (fwrite (&BinaryEscape, sizeof(char), 1, fp) != sizeof(char))\n        return (0);\n      c = 0x03;\n      break;\n  }\n  if (fwrite (&c, sizeof(char), 1, fp) != sizeof(char))\n    return (0);\n\n  return (1);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a byte from file with escaped <CR>, <LF> and <ctrl-Z>]\n\n  Description [inputs a byte to file fp. 0x00 has been used as escape character\n    to filter <CR>, <LF> and <ctrl-Z>. This is done for\n    compatibility between unix and dos/windows systems.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [WriteByteBinary()]\n\n******************************************************************************/\n\nstatic int\nReadByteBinary (\n  FILE *fp           /*  IN: file where to read the byte */,\n  unsigned char *cp  /* OUT: the read byte */\n  )\n{\n \n  if (fread (cp, sizeof(char), 1, fp) != sizeof(char)) {\n    return (0);\n  }\n\n  if (*cp == 0x00) { /* Escape */\n    if (fread (cp, sizeof(char), 1, fp) != sizeof(char)) {\n      return (0);\n    }\n\n    switch (*cp) {\n\n      case 0x00: /* Escape */\n        break;\n      case 0x01: /* <LF> */\n        *cp = 0x0a;\n        break;\n      case 0x02: /* <CR> */\n        *cp = 0x0d;\n        break;\n      case 0x03: /* <ctrl-Z> */\n        *cp = 0x1a;\n        break;\n    }\n  }\n\n  return (1);\n}\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpConvert.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpConvert.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Conversion between ASCII and binary formats]\n\n  Description  [Conversion between ASCII and binary formats is presently \n    supported by loading a BDD in the source format and storing it \n    in the target one. We plan to introduce ad hoc procedures\n    avoiding explicit BDD node generation.\n    ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright   [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n\n/**AutomaticEnd***************************************************************/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [Converts from ASCII to binary format]\n\n  Description [Converts from ASCII to binary format. A BDD array is loaded and\n    and stored to the target file.]\n\n  SideEffects [None]\n\n  SeeAlso     [Dddmp_Bin2Text()]\n\n******************************************************************************/\n\nint\nDddmp_Text2Bin (\n  char *filein   /* IN: name of ASCII file */,\n  char *fileout  /* IN: name of binary file */\n  )\n{\n  DdManager *ddMgr;      /* pointer to DD manager */\n  DdNode **roots;        /* array of BDD roots to be loaded */\n  int nRoots;            /* number of BDD roots */\n  int retValue;\n \n  ddMgr = Cudd_Init(0,0,CUDD_UNIQUE_SLOTS,CUDD_CACHE_SLOTS,0);\n  if (ddMgr == NULL) {\n    return (0);\n  }\n\n  nRoots = Dddmp_cuddBddArrayLoad(ddMgr,DDDMP_ROOT_MATCHLIST,NULL,\n    DDDMP_VAR_MATCHIDS,NULL,NULL,NULL,\n    DDDMP_MODE_TEXT,filein,NULL,&roots);\n\n  Dddmp_CheckAndGotoLabel (nRoots<=0,\n    \"Negative Number of Roots.\", failure);\n\n  retValue = Dddmp_cuddBddArrayStore (ddMgr,NULL,nRoots,roots,NULL,\n    NULL,NULL,DDDMP_MODE_BINARY,DDDMP_VARIDS,fileout,NULL);\n\n  Dddmp_CheckAndGotoLabel (retValue<=0,\n    \"Error code returned.\", failure);\n   \n  Cudd_Quit(ddMgr);\n  return (1);\n\n  failure:\n    printf(\"error converting BDD format\\n\");\n    Cudd_Quit(ddMgr);\n    return (0);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Converts from binary to ASCII format]\n\n  Description [Converts from binary to ASCII format. A BDD array is loaded and\n    and stored to the target file.]\n\n  SideEffects [None]\n\n  SeeAlso     [Dddmp_Text2Bin()]\n\n******************************************************************************/\n\nint\nDddmp_Bin2Text (\n  char *filein   /* IN: name of binary file */,\n  char *fileout  /* IN: name of ASCII file */\n  )\n{\n  DdManager *ddMgr;      /* pointer to DD manager */\n  DdNode **roots;        /* array of BDD roots to be loaded */\n  int nRoots;            /* number of BDD roots */\n  int retValue;\n\n  ddMgr = Cudd_Init(0,0,CUDD_UNIQUE_SLOTS,CUDD_CACHE_SLOTS,0);\n  if (ddMgr == NULL) {\n    return (0);\n  }\n\n  nRoots = Dddmp_cuddBddArrayLoad(ddMgr,DDDMP_ROOT_MATCHLIST,NULL,\n    DDDMP_VAR_MATCHIDS,NULL,NULL,NULL,\n    DDDMP_MODE_BINARY,filein,NULL,&roots);\n\n  Dddmp_CheckAndGotoLabel (nRoots<=0,\n    \"Negative Number of Roots.\", failure);\n\n  retValue = Dddmp_cuddBddArrayStore (ddMgr,NULL,nRoots,roots,NULL,\n    NULL,NULL,DDDMP_MODE_TEXT,DDDMP_VARIDS,fileout,NULL);\n\n  Dddmp_CheckAndGotoLabel (retValue<=0,\n    \"Error code returned.\", failure);\n   \n  Cudd_Quit(ddMgr);\n  return (1);\n\n  failure:\n    printf(\"error converting BDD format\\n\");\n    Cudd_Quit(ddMgr);\n    return (0);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpDbg.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpDbg.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to display BDD files]\n\n  Description  [Functions to display BDD files in binary format\n    ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright   [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n\n/**AutomaticEnd***************************************************************/\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**Function********************************************************************\n\n  Synopsis     [Display a binary dump file in a text file]\n\n  Description  [Display a binary dump file in a text file]\n\n  SideEffects  [None]\n\n  SeeAlso      [Dddmp_cuddBddStore , Dddmp_cuddBddLoad ]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddDisplayBinary(\n  char *fileIn  /* IN: name of binary file */,\n  char *fileOut /* IN: name of text file */\n  )\n{\n  FILE *fp, *fpo; \n  int id, size;\n  struct binary_dd_code code;\n  char buf[1000];\n  int nnodes, i;\n  char *retval;\n\n  fp = fopen (fileIn, \"rb\");\n  if (fp == 0) {\n    return (0);\n  }\n\n  fpo = fopen (fileOut, \"w\");\n  if (fpo == 0) {\n    return (0);\n  }\n\n  while (fgets(buf, 999,fp)!=NULL) {\n    fprintf (fpo, \"%s\", buf);\n    if (strncmp(buf, \".nnodes\", 7) == 0) {\n      sscanf (buf, \"%*s %d\", &nnodes);\n    }\n    if (strncmp(buf, \".rootids\", 8) == 0) {\n      break;\n    }\n  }\n\n  for (i=1; i<=nnodes; i++) {\n    if (feof(fp)) {\n      return (0);\n    }\n    if (DddmpReadCode(fp,&code) == 0) {\n      return (0);                        \n    }\n    fprintf (fpo, \"c  : v %d | T %d | E %d\\n\",\n      (int)code.V, (int)code.T, \n      (code.Ecompl ? -(int)(code.E) : (int)(code.E)));\n    if (code.V == DDDMP_TERMINAL) {\n      continue;\n    }\n    if (code.V <= DDDMP_RELATIVE_ID) {\n      size = DddmpReadInt(fp,&id);\n      if (size == 0) {\n        return (0);\n      }\n      fprintf(fpo, \"v(%d): %d\\n\", size, id);\n    }\n    if (code.T <= DDDMP_RELATIVE_ID) {\n      size = DddmpReadInt(fp,&id);\n      if (size == 0) {\n        return (0);\n      }\n      fprintf(fpo, \"T(%d): %d\\n\", size, id);\n    }\n    if (code.E <= DDDMP_RELATIVE_ID) {\n      size = DddmpReadInt(fp,&id);\n      if (size == 0) {\n        return (0);\n      }\n      fprintf(fpo, \"E(%d): %d\\n\", size, id);\n    }\n\n  }\n\n  retval = fgets(buf, 999,fp);\n  if (!retval || strncmp(buf, \".end\", 4) != 0) {\n    return (0);\n  }\n\n  fprintf(fpo, \".end\");\n\n  fclose(fp);\n  fclose(fpo);\n\n  return (1);\n}\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpInt.h",
    "content": "/**CHeaderFile*****************************************************************\n\n  FileName     [dddmpInt.h]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Low level functions to read in and write out bdds to file]\n\n  Description  [A set of internal low-level routines of the dddmp package\n    doing:\n    <ul>\n      <li> read and write of node codes in binary mode,\n      <li> read and write of integers in binary mode,\n      <li> marking/unmarking nodes as visited,\n      <li> numbering nodes.\n    </ul>\n    ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2002 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#ifndef _DDDMPINT\n#define _DDDMPINT\n\n#include \"dddmp.h\"\n#include \"cuddInt.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* constants for code fields */\n#define DDDMP_TERMINAL      0\n#define DDDMP_ABSOLUTE_ID   1\n#define DDDMP_RELATIVE_ID   2\n#define DDDMP_RELATIVE_1    3\n\n#define DDDMP_MAXSTRLEN 500\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Structure declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**Struct**********************************************************************\n Synopsis    [used in binary mode to store code info of a dd node]\n Description [V , T , E store the mode used to represent variable, Then \n              and Else indexes. An index is either an absolute\n\t      ( DDDMP_ABSOLUTE_ID ),\n              a relative numbers ( DDDMP_RELATIVE_ID , DDDMP_RELATIVE_1 ) or \n              a terminal node ( DDDMP_TERMINAL ) .\n\t      Ecomp is used for the complemented edge attribute.\n             ]\n SideEffect  [none]\n SeeAlso     [DddmpWriteCode DddmpReadCode] \n******************************************************************************/\n\nstruct binary_dd_code {\n  unsigned  Unused : 1;\n  unsigned  V      : 2;\n  unsigned  T      : 2;\n  unsigned  Ecompl : 1;\n  unsigned  E      : 2;\n};\n\n/**Struct*********************************************************************\n\n Synopsis    [BDD file header]\n\n Description [Structure containing the BDD header file infos]\n\n******************************************************************************/\n\nstruct Dddmp_Hdr_s {\n  char *ver;\n  char mode;\n  Dddmp_DecompType ddType;\n  Dddmp_VarInfoType varinfo;\n  char *dd;\n  int nnodes;\n  int nVars;\n  int nsuppvars;\n  char **orderedVarNames;\n  char **suppVarNames;\n  int *ids;\n  int *permids;\n  int *auxids;\n  int *cnfids;\n  int nRoots;\n  int *rootids;\n  char **rootnames;\n  int nAddedCnfVar;\n  int nVarsCnf;\n  int nClausesCnf;  \n};\t\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**Macro***********************************************************************\n\n  Synopsis     [Memory Allocation Macro for DDDMP]\n\n  Description  []\n\n  SideEffects  [None]\n\n  SeeAlso      []\n\n******************************************************************************/\n\n#ifdef ALLOC\n#  define DDDMP_ALLOC(type, num)\tALLOC(type,num)\n#else\n#  define DDDMP_ALLOC(type, num)\t\\\n     ((type *) malloc(sizeof(type) * (num)))\n#endif\n\n/**Macro***********************************************************************\n\n  Synopsis     [Memory Free Macro for DDDMP]\n\n  Description  []\n\n  SideEffects  [None]\n\n  SeeAlso      []\n\n******************************************************************************/\n\n#ifdef FREE\n#define DDDMP_FREE(p)  (FREE(p))\n#else\n#define DDDMP_FREE(p)\t\\\n    ((p)!=NULL)?(free(p)):0)\n#endif\n\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\nextern int DddmpWriteCode(FILE *fp, struct binary_dd_code code);\nextern int DddmpReadCode(FILE *fp, struct binary_dd_code *pcode);\nextern int DddmpWriteInt(FILE *fp, int id);\nextern int DddmpReadInt(FILE *fp, int *pid);\nextern int DddmpNumberAddNodes(DdManager *ddMgr, DdNode **f, int n);\nextern void DddmpUnnumberAddNodes(DdManager *ddMgr, DdNode **f, int n);\nextern void DddmpWriteNodeIndexAdd(DdNode *f, int id);\nextern int DddmpReadNodeIndexAdd(DdNode *f);\nextern int DddmpVisitedAdd(DdNode *f);\nextern void DddmpSetVisitedAdd(DdNode *f);\nextern void DddmpClearVisitedAdd(DdNode *f);\nextern int DddmpNumberBddNodes(DdManager *ddMgr, DdNode **f, int n);\nextern void DddmpUnnumberBddNodes(DdManager *ddMgr, DdNode **f, int n);\nextern void DddmpWriteNodeIndexBdd(DdNode *f, int id);\nextern int DddmpReadNodeIndexBdd(DdNode *f);\nextern int DddmpVisitedBdd(DdNode *f);\nextern void DddmpSetVisitedBdd(DdNode *f);\nextern void DddmpClearVisitedBdd(DdNode *f);\nextern int DddmpNumberDdNodesCnf(DdManager *ddMgr, DdNode **f, int rootN, int *cnfIds, int id);\nextern int DddmpDdNodesCountEdgesAndNumber(DdManager *ddMgr, DdNode **f, int rootN, int edgeInTh, int pathLengthTh, int *cnfIds, int id);\nextern void DddmpUnnumberDdNodesCnf(DdManager *ddMgr, DdNode **f, int rootN);\nextern int DddmpPrintBddAndNext(DdManager *ddMgr, DdNode **f, int rootN);\nextern int DddmpWriteNodeIndexCnf(DdNode *f, int id);\nextern int DddmpVisitedCnf(DdNode *f);\nextern void DddmpSetVisitedCnf(DdNode *f);\nextern int DddmpReadNodeIndexCnf(DdNode *f);\nextern int DddmpCuddDdArrayStoreBdd(Dddmp_DecompType ddType, DdManager *ddMgr, char *ddname, int nRoots, DdNode **f, char **rootnames, char **varnames, int *auxids, int mode, Dddmp_VarInfoType varinfo, char *fname, FILE *fp);\nextern int DddmpCuddBddArrayStore(Dddmp_DecompType ddType, DdManager *ddMgr, char *ddname, int nRoots, DdNode **f, char **rootnames, char **varnames, int *auxids, int mode, Dddmp_VarInfoType varinfo, char *fname, FILE *fp);\nextern int QsortStrcmp(const void *ps1, const void *ps2);\nextern int FindVarname(char *name, char **array, int n);\nextern char * DddmpStrDup(char *str);\nextern char ** DddmpStrArrayDup(char **array, int n);\nextern char ** DddmpStrArrayRead(FILE *fp, int n);\nextern int DddmpStrArrayWrite(FILE *fp, char **array, int n);\nextern void DddmpStrArrayFree(char **array, int n);\nextern int * DddmpIntArrayDup(int *array, int n);\nextern int * DddmpIntArrayRead(FILE *fp, int n);\nextern int DddmpIntArrayWrite(FILE *fp, int *array, int n);\n\n/**AutomaticEnd***************************************************************/\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif\n"
  },
  {
    "path": "cudd/dddmp/dddmpLoad.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpLoad.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to read in bdds to file]\n\n  Description  [Functions to read in bdds to file.  BDDs\n    are represended on file either in text or binary format under the\n    following rules.  A file contains a forest of BDDs (a vector of\n    Boolean functions).  BDD nodes are numbered with contiguous numbers,\n    from 1 to NNodes (total number of nodes on a file). 0 is not used to\n    allow negative node indexes for complemented edges.  A file contains\n    a header, including information about variables and roots to BDD\n    functions, followed by the list of nodes.  BDD nodes are listed\n    according to their numbering, and in the present implementation\n    numbering follows a post-order strategy, in such a way that a node\n    is never listed before its Then/Else children.\n  ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#define matchkeywd(str,key) (strncmp(str,key,strlen(key))==0)\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int DddmpCuddDdArrayLoad(Dddmp_DecompType ddType, DdManager *ddMgr, Dddmp_RootMatchType rootMatchMode, char **rootmatchnames, Dddmp_VarMatchType varMatchMode, char **varmatchnames, int *varmatchauxids, int *varcomposeids, int mode, char *file, FILE *fp, DdNode ***pproots);\nstatic Dddmp_Hdr_t * DddmpBddReadHeader(char *file, FILE *fp);\nstatic void DddmpFreeHeader(Dddmp_Hdr_t *Hdr);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Reads a dump file representing the argument BDD.]\n\n  Description  [Reads a dump file representing the argument BDD.\n    Dddmp_cuddBddArrayLoad is used through a dummy array (see this\n    function's description for more details).\n    Mode, the requested input file format, is checked against \n    the file format.\n    The loaded BDDs is referenced before returning it.\n    ]\n\n  SideEffects  [A vector of pointers to DD nodes is allocated and freed.]\n\n  SeeAlso      [Dddmp_cuddBddStore, Dddmp_cuddBddArrayLoad]\n\n******************************************************************************/\n\nDdNode *\nDddmp_cuddBddLoad (\n  DdManager *ddMgr                /* IN: DD Manager */,\n  Dddmp_VarMatchType varMatchMode /* IN: storing mode selector */,\n  char **varmatchnames            /* IN: array of variable names - by IDs */,\n  int *varmatchauxids             /* IN: array of variable auxids - by IDs */,\n  int *varcomposeids              /* IN: array of new ids accessed - by IDs */,\n  int mode                        /* IN: requested input file format */,\n  char *file                      /* IN: file name */,\n  FILE *fp                        /* IN: file pointer */\n  )\n{\n  DdNode *f , **tmpArray;\n  int i, nRoots;\n\n  nRoots = Dddmp_cuddBddArrayLoad(ddMgr,DDDMP_ROOT_MATCHLIST,NULL,\n    varMatchMode,varmatchnames,varmatchauxids,varcomposeids,\n    mode,file,fp,&tmpArray);\n\n  if (nRoots == 0) {\n    return (NULL);\n  } else {\n    f = tmpArray[0];\n    if (nRoots > 1) {\n      fprintf (stderr,\n        \"Warning: %d BDD roots found in file. Only first retrieved.\\n\",\n         nRoots);\n      for (i=1; i<nRoots; i++) {\n        Cudd_RecursiveDeref (ddMgr, tmpArray[i]);\n      } \n    } \n    DDDMP_FREE (tmpArray);\n    return (f);\n  }\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a dump file representing the argument BDDs.]\n\n  Description [Reads a dump file representing the argument BDDs. The header is\n    common to both text and binary mode. The node list is either \n    in text or binary format. A dynamic vector of DD pointers \n    is allocated to support conversion from DD indexes to pointers.\n    Several criteria are supported for variable match between file\n    and dd manager. Several changes/permutations/compositions are allowed\n    for variables while loading DDs. Variable of the dd manager are allowed \n    to match with variables on file on ids, permids, varnames, \n    varauxids; also direct composition between ids and \n    composeids is supported. More in detail:\n    <ol>\n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    allows the loading of a DD keeping variable IDs unchanged\n    (regardless of the variable ordering of the reading manager); this\n    is useful, for example, when swapping DDs to file and restoring them\n    later from file, after possible variable reordering activations.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHPERMIDS <p>\n    is used to allow variable match according to the position in the\n    ordering.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHNAMES <p>\n    requires a non NULL varmatchnames parameter; this is a vector of\n    strings in one-to-one correspondence with variable IDs of the\n    reading manager. Variables in the DD file read are matched with\n    manager variables according to their name (a non NULL varnames\n    parameter was required while storing the DD file).\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    has a meaning similar to DDDMP_VAR_MATCHNAMES, but integer auxiliary\n    IDs are used instead of strings; the additional non NULL\n    varmatchauxids parameter is needed.\n    \n    <li> varMatchMode=DDDMP_VAR_COMPOSEIDS <p>\n    uses the additional varcomposeids parameter is used as array of\n    variable ids to be composed with ids stored in file.\n    </ol>\n    \n    In the present implementation, the array varnames (3), varauxids (4)\n    and composeids (5) need to have one entry for each variable in the \n    DD manager (NULL pointers are allowed for unused variables\n    in varnames). Hence variables need to be already present in the \n    manager. All arrays are sorted according to IDs.\n\n    All the loaded BDDs are referenced before returning them.\n    ]\n\n  SideEffects [A vector of pointers to DD nodes is allocated and freed.]\n\n  SeeAlso     [Dddmp_cuddBddArrayStore]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddArrayLoad (\n  DdManager *ddMgr                  /* IN: DD Manager */,\n  Dddmp_RootMatchType rootMatchMode /* IN: storing mode selector */,\n  char **rootmatchnames             /* IN: sorted names for loaded roots */,\n  Dddmp_VarMatchType varMatchMode   /* IN: storing mode selector */,\n  char **varmatchnames              /* IN: array of variable names, by ids */,\n  int *varmatchauxids               /* IN: array of variable auxids, by ids */,\n  int *varcomposeids                /* IN: array of new ids, by ids */,\n  int mode                          /* IN: requested input file format */,\n  char *file                        /* IN: file name */,\n  FILE *fp                          /* IN: file pointer */,\n  DdNode ***pproots                 /* OUT: array of returned BDD roots */\n  )\n{\n  int retValue;\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValueBis;\n\n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Load.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Load.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  retValue = DddmpCuddDdArrayLoad (DDDMP_BDD, ddMgr, rootMatchMode,\n     rootmatchnames, varMatchMode, varmatchnames, varmatchauxids,\n     varcomposeids, mode, file, fp, pproots);\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Load.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Load.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a dump file representing the argument ADD.]\n\n  Description [Reads a dump file representing the argument ADD.\n    Dddmp_cuddAddArrayLoad is used through a dummy array.\n    ]\n\n  SideEffects [A vector of pointers to DD nodes is allocated and freed.]\n\n  SeeAlso     [Dddmp_cuddAddStore, Dddmp_cuddAddArrayLoad]\n\n******************************************************************************/\n\nDdNode *\nDddmp_cuddAddLoad (\n  DdManager *ddMgr                /* IN: Manager */,\n  Dddmp_VarMatchType varMatchMode /* IN: storing mode selector */,\n  char **varmatchnames            /* IN: array of variable names by IDs */,\n  int  *varmatchauxids            /* IN: array of variable auxids by IDs */,\n  int  *varcomposeids             /* IN: array of new ids by IDs */,\n  int mode                        /* IN: requested input file format */,\n  char *file                      /* IN: file name */,\n  FILE *fp                        /* IN: file pointer */\n  )\n{\n  DdNode *f , **tmpArray;\n  int i, nRoots;\n\n  nRoots = Dddmp_cuddAddArrayLoad (ddMgr, DDDMP_ROOT_MATCHLIST,NULL,\n    varMatchMode, varmatchnames, varmatchauxids, varcomposeids,\n    mode, file, fp, &tmpArray);\n\n  if (nRoots == 0) {\n    return (NULL);\n  } else {\n    f = tmpArray[0];\n    if (nRoots > 1) {\n      fprintf (stderr,\n        \"Warning: %d BDD roots found in file. Only first retrieved.\\n\",\n        nRoots);\n      for (i=1; i<nRoots; i++) {\n        Cudd_RecursiveDeref (ddMgr, tmpArray[i]);\n      } \n    } \n    DDDMP_FREE (tmpArray);\n    return (f);\n  }\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a dump file representing the argument ADDs.]\n\n  Description [Reads a dump file representing the argument ADDs. See \n    BDD load functions for detailed explanation.\n    ]\n\n  SideEffects [A vector of pointers to DD nodes is allocated and freed.]\n\n  SeeAlso     [Dddmp_cuddBddArrayStore]\n\n******************************************************************************/\n\nint\nDddmp_cuddAddArrayLoad (\n  DdManager *ddMgr                  /* IN: DD Manager */,\n  Dddmp_RootMatchType rootMatchMode /* IN: storing mode selector */,\n  char **rootmatchnames             /* IN: sorted names for loaded roots */,\n  Dddmp_VarMatchType varMatchMode   /* IN: storing mode selector */,\n  char **varmatchnames              /* IN: array of variable names, by ids */,\n  int *varmatchauxids               /* IN: array of variable auxids, by ids */,\n  int *varcomposeids                /* IN: array of new ids, by ids */,\n  int mode                          /* IN: requested input file format */,\n  char *file                        /* IN: file name */,\n  FILE *fp                          /* IN: file pointer */,\n  DdNode ***pproots                 /* OUT: array of returned BDD roots */\n  )\n{\n\n  int retValue;\n\n#if 0\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValueBis;\n\n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During ADD Load.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During ADD Load.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n#endif\n\n  retValue = DddmpCuddDdArrayLoad (DDDMP_ADD, ddMgr, rootMatchMode,\n    rootmatchnames, varMatchMode, varmatchnames, varmatchauxids,\n    varcomposeids, mode, file, fp, pproots);\n\n#if 0\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During ADD Load.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During ADD Load.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n#endif\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads the header of a dump file representing the argument BDDs]\n\n  Description [Reads the header of a dump file representing the argument BDDs.\n    Returns main information regarding DD type stored in the file,\n    the variable ordering used, the number of variables, etc.\n    It reads only the header of the file NOT the BDD/ADD section. \n    ]\n\n  SideEffects []\n\n  SeeAlso     [Dddmp_cuddBddArrayLoad]\n\n******************************************************************************/\n\nint\nDddmp_cuddHeaderLoad (\n  Dddmp_DecompType *ddType  /* OUT: selects the proper decomp type */,\n  int *nVars                /* OUT: number of DD variables */,\n  int *nsuppvars            /* OUT: number of support variables */,\n  char ***suppVarNames      /* OUT: array of support variable names */,\n  char ***orderedVarNames   /* OUT: array of variable names */,\n  int **varIds              /* OUT: array of variable ids */,\n  int **varComposeIds       /* OUT: array of permids ids */,\n  int **varAuxIds           /* OUT: array of variable aux ids */,\n  int *nRoots               /* OUT: number of root in the file */,\n  char *file                 /* IN: file name */,\n  FILE *fp                   /* IN: file pointer */\n  )\n{\n  Dddmp_Hdr_t *Hdr;\n  int i, fileToClose;\n  int *tmpVarIds = NULL;\n  int *tmpVarComposeIds = NULL;\n  int *tmpVarAuxIds = NULL; \n\n  fileToClose = 0;\n  if (fp == NULL) {\n    fp = fopen (file, \"r\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  Hdr = DddmpBddReadHeader (NULL, fp);\n\n  Dddmp_CheckAndGotoLabel (Hdr->nnodes==0, \"Zero number of nodes.\",\n    failure);\n\n  /*\n   *  Type, number of variables (tot and support)\n   */\n\n  *ddType = Hdr->ddType;\n  *nVars = Hdr->nVars;\n  *nsuppvars = Hdr->nsuppvars;\n\n  /*\n   *  Support Varnames\n   */\n\n  if (Hdr->suppVarNames != NULL) {\n    *suppVarNames = DDDMP_ALLOC (char *, *nsuppvars);\n    Dddmp_CheckAndGotoLabel (*suppVarNames==NULL,\n      \"Error allocating memory.\", failure);\n\n    for (i=0; i<*nsuppvars; i++) {\n      (*suppVarNames)[i] = DDDMP_ALLOC (char,\n        (strlen (Hdr->suppVarNames[i]) + 1));\n      Dddmp_CheckAndGotoLabel (Hdr->suppVarNames[i]==NULL,\n        \"Support Variable Name Missing in File.\", failure);\n      strcpy ((*suppVarNames)[i], Hdr->suppVarNames[i]);\n    }\n  } else {\n    *suppVarNames = NULL;\n  }\n\n  /*\n   *  Ordered Varnames\n   */\n\n  if (Hdr->orderedVarNames != NULL) {\n    *orderedVarNames = DDDMP_ALLOC (char *, *nVars);\n    Dddmp_CheckAndGotoLabel (*orderedVarNames==NULL,\n      \"Error allocating memory.\", failure);\n\n    for (i=0; i<*nVars; i++) {\n      (*orderedVarNames)[i]  = DDDMP_ALLOC (char,\n        (strlen (Hdr->orderedVarNames[i]) + 1));\n      Dddmp_CheckAndGotoLabel (Hdr->orderedVarNames[i]==NULL,\n        \"Support Variable Name Missing in File.\", failure);\n      strcpy ((*orderedVarNames)[i], Hdr->orderedVarNames[i]);\n    }\n  } else {\n    *orderedVarNames = NULL;\n  }\n\n  /*\n   *  Variable Ids\n   */\n\n  if (Hdr->ids != NULL) {\n    tmpVarIds = DDDMP_ALLOC (int, *nsuppvars);\n    Dddmp_CheckAndGotoLabel (tmpVarIds==NULL, \"Error allocating memory.\",\n      failure);\n    for (i=0; i<*nsuppvars; i++) {\n      tmpVarIds[i] = Hdr->ids[i];\n    }\n\n    *varIds = tmpVarIds; \n  } else {\n    *varIds = NULL;\n  }\n\n  /*\n   *  Variable Compose Ids\n   */\n\n  if (Hdr->permids != NULL) {\n    tmpVarComposeIds = DDDMP_ALLOC (int, *nsuppvars);\n    Dddmp_CheckAndGotoLabel (tmpVarComposeIds==NULL,\n      \"Error allocating memory.\", failure);\n    for (i=0; i<*nsuppvars; i++) {\n      tmpVarComposeIds[i] = Hdr->permids[i];\n    }\n\n    *varComposeIds = tmpVarComposeIds; \n  } else {\n    *varComposeIds = NULL;\n  }\n\n  /*\n   *  Variable Auxiliary Ids\n   */\n\n  if (Hdr->auxids != NULL) {\n    tmpVarAuxIds = DDDMP_ALLOC (int, *nsuppvars);\n    Dddmp_CheckAndGotoLabel (tmpVarAuxIds==NULL,\n      \"Error allocating memory.\", failure);\n    for (i=0; i<*nsuppvars; i++) {\n      tmpVarAuxIds[i] = Hdr->auxids[i];\n    }\n\n    *varAuxIds = tmpVarAuxIds; \n  } else {\n    *varAuxIds = NULL;\n  }\n\n  /*\n   *  Number of roots\n   */\n\n  *nRoots = Hdr->nRoots;\n \n /*\n   *  Free and Return\n   */\n\n  if (fileToClose == 1) {\n    fclose (fp);\n  }\n\t\n  DddmpFreeHeader(Hdr);\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n    return (DDDMP_FAILURE);\n}\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a dump file representing the argument BDDs.]\n\n  Description [Reads a dump file representing the argument BDDs. The header is\n    common to both text and binary mode. The node list is either \n    in text or binary format. A dynamic vector of DD pointers \n    is allocated to support conversion from DD indexes to pointers.\n    Several criteria are supported for variable match between file\n    and dd manager. Several changes/permutations/compositions are allowed\n    for variables while loading DDs. Variable of the dd manager are allowed \n    to match with variables on file on ids, permids, varnames, \n    varauxids; also direct composition between ids and \n    composeids is supported. More in detail:\n    <ol>\n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    allows the loading of a DD keeping variable IDs unchanged\n    (regardless of the variable ordering of the reading manager); this\n    is useful, for example, when swapping DDs to file and restoring them\n    later from file, after possible variable reordering activations.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHPERMIDS <p>\n    is used to allow variable match according to the position in the ordering.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHNAMES <p>\n    requires a non NULL varmatchnames parameter; this is a vector of\n    strings in one-to-one correspondence with variable IDs of the\n    reading manager. Variables in the DD file read are matched with\n    manager variables according to their name (a non NULL varnames\n    parameter was required while storing the DD file).\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    has a meaning similar to DDDMP_VAR_MATCHNAMES, but integer auxiliary\n    IDs are used instead of strings; the additional non NULL\n    varmatchauxids parameter is needed.\n    \n    <li> varMatchMode=DDDMP_VAR_COMPOSEIDS <p>\n    uses the additional varcomposeids parameter is used as array of\n    variable ids to be composed with ids stored in file.\n    </ol>\n    \n    In the present implementation, the array varnames (3), varauxids (4)\n    and composeids (5) need to have one entry for each variable in the \n    DD manager (NULL pointers are allowed for unused variables\n    in varnames). Hence variables need to be already present in the \n    manager. All arrays are sorted according to IDs.\n    ]\n\n  SideEffects [A vector of pointers to DD nodes is allocated and freed.]\n\n  SeeAlso     [Dddmp_cuddBddArrayStore]\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayLoad (\n  Dddmp_DecompType ddType           /* IN: Selects decomp type */,\n  DdManager *ddMgr                  /* IN: DD Manager */,\n  Dddmp_RootMatchType rootMatchMode /* IN: storing mode selector */,\n  char **rootmatchnames             /* IN: sorted names for loaded roots */,\n  Dddmp_VarMatchType varMatchMode   /* IN: storing mode selector */,\n  char **varmatchnames              /* IN: array of variable names, by ids */,\n  int *varmatchauxids               /* IN: array of variable auxids, by ids */,\n  int *varcomposeids                /* IN: array of new ids, by ids */,\n  int mode                          /* IN: requested input file format */,\n  char *file                        /* IN: file name */,\n  FILE *fp                          /* IN: file pointer */,\n  DdNode ***pproots                 /* OUT: array BDD roots (by reference) */\n  )\n{\n  Dddmp_Hdr_t *Hdr = NULL;\n  DdNode *f = NULL;\n  DdNode *T = NULL;\n  DdNode *E = NULL;\n  struct binary_dd_code code;\n  char buf[DDDMP_MAXSTRLEN];\n  int retValue, id, size, maxv;\n  int i, j, k, maxaux, var, vT, vE, idT, idE;\n  double addConstant;\n  int *permsupport = NULL;\n  int *convertids = NULL;\n  int *invconvertids = NULL;\n  int *invauxids = NULL;\n  char **sortedvarnames = NULL;\n  int  nddvars, nRoots;\n  DdNode **pnodes = NULL;\n  unsigned char *pvars1byte = NULL;\n  unsigned short *pvars2byte = NULL;\n  DdNode **proots = NULL;\n  int fileToClose = 0;\n  char *retval;\n\n  *pproots = NULL;\n\n  if (fp == NULL) {\n    fp = fopen (file, \"r\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  nddvars = ddMgr->size;\n\n  Hdr = DddmpBddReadHeader (NULL, fp);\n\n  Dddmp_CheckAndGotoLabel (Hdr->nnodes==0, \"Zero number of nodes.\",\n    failure);\n\n  nRoots = Hdr->nRoots;\n\n  if (Hdr->ddType != ddType) {\n    (void) fprintf (stderr, \"DdLoad Error: ddType mismatch\\n\");\n \n   if (Hdr->ddType == DDDMP_BDD)\n      (void) fprintf (stderr, \"BDD found\\n\");\n    if (Hdr->ddType == DDDMP_ADD)\n      (void) fprintf (stderr, \"ADD found\\n\");\n    if (ddType == DDDMP_BDD)\n      (void) fprintf (stderr, \"when loading a BDD\\n\");\n    if (ddType == DDDMP_ADD)\n      (void) fprintf (stderr, \"when loading an ADD\\n\");\n\n    fflush (stderr);\n    goto failure;\n  }\n\n  if (Hdr->mode != mode) {\n    Dddmp_CheckAndGotoLabel (mode!=DDDMP_MODE_DEFAULT,\n      \"Mode Mismatch.\", failure);\n    mode = Hdr->mode;\n  }\n\n  /*\n   *  For each variable in the support\n   *  compute the relative position in the ordering\n   *  (within the support only)\n   */\n\n  permsupport = DDDMP_ALLOC (int, Hdr->nsuppvars);\n  Dddmp_CheckAndGotoLabel (permsupport==NULL, \"Error allocating memory.\",\n    failure);\n  for (i=0,k=0; i < Hdr->nVars; i++) { \n    for (j=0; j < Hdr->nsuppvars; j++) { \n      if (Hdr->permids[j] == i) {\n        permsupport[j] = k++;\n      }\n    }\n  }\n  Dddmp_Assert (k==Hdr->nsuppvars, \"k==Hdr->nsuppvars\");\n\n  if (Hdr->suppVarNames != NULL) {\n    /*\n     *  Varnames are sorted for binary search\n     */\n\n    sortedvarnames = DDDMP_ALLOC(char *, Hdr->nsuppvars);\n    Dddmp_CheckAndGotoLabel (sortedvarnames==NULL, \"Error allocating memory.\",\n      failure);\n    for (i=0; i<Hdr->nsuppvars; i++) {\n      Dddmp_CheckAndGotoLabel (Hdr->suppVarNames[i]==NULL,\n        \"Support Variable Name Missing in File.\", failure);\n      sortedvarnames[i] = Hdr->suppVarNames[i];\n    }    \n    \n    qsort ((void *) sortedvarnames, Hdr->nsuppvars,\n      sizeof(char *), QsortStrcmp);\n    \n  }\n\n  /*\n   *  Convertids is the array used to convert variable ids from positional\n   *  (shrinked) ids used within the DD file.\n   *  Positions in the file are from 0 to nsuppvars-1.\n   */ \n\n  convertids = DDDMP_ALLOC (int, Hdr->nsuppvars);\n  Dddmp_CheckAndGotoLabel (convertids==NULL, \"Error allocating memory.\",\n    failure);\n\n  again_matchmode:\n  switch (varMatchMode) {\n    case DDDMP_VAR_MATCHIDS:\n      for (i=0; i<Hdr->nsuppvars; i++) {\n        convertids[permsupport[i]] = Hdr->ids[i];\n      }\n      break;\n    case DDDMP_VAR_MATCHPERMIDS:\n      for (i=0; i<Hdr->nsuppvars; i++) {\n        convertids[permsupport[i]] = Cudd_ReadInvPerm (ddMgr,\n          Hdr->permids[i]);\n      }\n      break;\n    case DDDMP_VAR_MATCHAUXIDS:\n      if (Hdr->auxids == NULL) {\n        (void) fprintf (stderr,\n           \"DdLoad Error: variable auxids matching requested\\n\");\n        (void) fprintf (stderr, \"but .auxids not found in BDD file\\n\");\n        (void) fprintf (stderr, \"Matching IDs forced.\\n\");\n        fflush (stderr);\n        varMatchMode = DDDMP_VAR_MATCHIDS;\n        goto again_matchmode;\n      }\n      /* find max auxid value to alloc invaux array */\n      for (i=0,maxaux= -1; i<nddvars; i++) {\n        if (varmatchauxids[i]>maxaux) {\n          maxaux = varmatchauxids[i];\n        }\n      }\n      /* generate invaux array */\n      invauxids = DDDMP_ALLOC (int, maxaux+1);\n      Dddmp_CheckAndGotoLabel (invauxids==NULL, \"Error allocating memory.\",\n        failure);\n\n      for (i=0; i<=maxaux; i++) {\n        invauxids[i] = -1;\n      }\n\n      for (i=0; i<Hdr->nsuppvars; i++) {\n        invauxids[varmatchauxids[Hdr->ids[i]]] = Hdr->ids[i];\n      }\n\n      /* generate convertids array */\n      for (i=0; i<Hdr->nsuppvars; i++) {\n        if ((Hdr->auxids[i]>maxaux) || (invauxids[Hdr->auxids[i]]<0)) {\n          (void) fprintf (stderr,\n            \"DdLoad Error: auxid %d not found in DD manager.\\n\", \n            Hdr->auxids[i]);\n          (void) fprintf (stderr, \"ID matching forced (%d).\\n\", i);\n          (void) fprintf (stderr,\n            \"Beware of possible overlappings with other variables\\n\"); \n          fflush (stderr);\n          convertids[permsupport[i]] = i;\n        } else {\n          convertids[permsupport[i]] = invauxids[Hdr->auxids[i]];\n        }\n      }\n      break;\n    case DDDMP_VAR_MATCHNAMES:\n      if (Hdr->suppVarNames == NULL) {\n        (void) fprintf (stderr,\n          \"DdLoad Error: variable names matching requested\\n\");\n        (void) fprintf (stderr, \"but .suppvarnames not found in BDD file\\n\");\n        (void) fprintf (stderr, \"Matching IDs forced.\\n\");\n        fflush (stderr);\n        varMatchMode = DDDMP_VAR_MATCHIDS;\n        goto again_matchmode;\n      }\n\n      /* generate invaux array */\n      invauxids = DDDMP_ALLOC (int, Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (invauxids==NULL, \"Error allocating memory.\",\n        failure);\n\n      for (i=0; i<Hdr->nsuppvars; i++) {\n        invauxids[i] = -1;\n      }\n\n      for (i=0; i<nddvars; i++) {\n        if (varmatchnames[i]==NULL) {\n          (void) fprintf (stderr,\n            \"DdLoad Warning: NULL match variable name (id: %d). Ignored.\\n\",\n            i);\n          fflush (stderr);\n        }\n        else\n          if ((j=FindVarname(varmatchnames[i],sortedvarnames,Hdr->nsuppvars))\n               >=0) {\n            Dddmp_Assert (j<Hdr->nsuppvars, \"j<Hdr->nsuppvars\");\n            invauxids[j] = i;\n          }\n      }\n      /* generate convertids array */\n      for (i=0; i<Hdr->nsuppvars; i++) {\n        Dddmp_Assert (Hdr->suppVarNames[i]!=NULL,\n          \"Hdr->suppVarNames[i] != NULL\");\n        j=FindVarname(Hdr->suppVarNames[i],sortedvarnames,Hdr->nsuppvars);\n        Dddmp_Assert ((j>=0) && (j<Hdr->nsuppvars),\n          \"(j>=0) && (j<Hdr->nsuppvars)\");\n        if (invauxids[j]<0) {\n          fprintf (stderr,\n            \"DdLoad Error: varname %s not found in DD manager.\",\n             Hdr->suppVarNames[i]);\n          fprintf (stderr, \"ID matching forced (%d)\\n\", i);\n          fflush (stderr);\n          convertids[permsupport[i]]=i;\n        } else {\n          convertids[permsupport[i]] = invauxids[j];\n        }\n      }\n      break;\n    case DDDMP_VAR_COMPOSEIDS:\n      for (i=0; i<Hdr->nsuppvars; i++) {\n        convertids[permsupport[i]] = varcomposeids[Hdr->ids[i]];\n      }\n      break;\n  }\n\n  maxv = (-1);\n  for (i=0; i<Hdr->nsuppvars; i++) {\n    if (convertids[i] > maxv) {\n      maxv = convertids[i];\n    }\n  }\n \n  invconvertids = DDDMP_ALLOC (int, maxv+1);\n  Dddmp_CheckAndGotoLabel (invconvertids==NULL, \"Error allocating memory.\",\n    failure);\n\n  for (i=0; i<=maxv; i++) {\n    invconvertids[i]= -1;\n  }\n\n  for (i=0; i<Hdr->nsuppvars; i++) {\n    invconvertids[convertids[i]] = i;\n  }\n\n  pnodes = DDDMP_ALLOC(DdNode *,(Hdr->nnodes+1));\n  Dddmp_CheckAndGotoLabel (pnodes==NULL, \"Error allocating memory.\",\n    failure);\n\n  if (Hdr->nsuppvars < 256) {\n    pvars1byte = DDDMP_ALLOC(unsigned char,(Hdr->nnodes+1));\n    Dddmp_CheckAndGotoLabel (pvars1byte==NULL, \"Error allocating memory.\",\n      failure);\n  }\n  else if (Hdr->nsuppvars < 0xffff) {\n    pvars2byte = DDDMP_ALLOC(unsigned short,(Hdr->nnodes+1));\n    Dddmp_CheckAndGotoLabel (pvars2byte==NULL, \"Error allocating memory.\",\n      failure);\n  } else {\n    (void) fprintf (stderr, \n       \"DdLoad Error: more than %d variables. Not supported.\\n\", 0xffff);\n    fflush (stderr);\n    goto failure;\n  }\n\n  /*-------------- Deal With Nodes ... One Row File at a Time --------------*/\n \n  for (i=1; i<=Hdr->nnodes; i++) {\n\n    Dddmp_CheckAndGotoLabel (feof(fp),\n      \"Unexpected EOF While Reading DD Nodes.\", failure);\n\n    switch (mode) {\n\n      /*\n       *  Text FORMAT\n       */\n\n      case DDDMP_MODE_TEXT:\n\n        switch (Hdr->varinfo) {\n          case DDDMP_VARIDS:\n          case DDDMP_VARPERMIDS:\n          case DDDMP_VARAUXIDS:\n          case DDDMP_VARNAMES:\n            retValue = fscanf(fp, \"%d %*s %s %d %d\\n\", &id, buf, &idT, &idE); \n            Dddmp_CheckAndGotoLabel (retValue<4,\n              \"Error Reading Nodes in Text Mode.\", failure);\n            break;\n          case DDDMP_VARDEFAULT:\n            retValue = fscanf(fp, \"%d %s %d %d\\n\", &id, buf, &idT, &idE);\n            Dddmp_CheckAndGotoLabel (retValue<4,\n              \"Error Reading Nodes in Text Mode.\", failure);\n            break;\n        }\n#ifdef DDDMP_DEBUG\n        Dddmp_Assert (id==i, \"id == i\");\n#endif\n        if (idT==0 && idE==0) {\n          /* leaf node: a constant */\n          if (strcmp(buf, \"1\") == 0) {\n            pnodes[i] = Cudd_ReadOne (ddMgr);       \n          } else {\n            /* this is an ADD constant ! */\n            if (strcmp(buf, \"0\") == 0) {\n              pnodes[i] = Cudd_ReadZero (ddMgr);       \n            } else {\n              addConstant = atof(buf);\n              pnodes[i] = Cudd_addConst (ddMgr,\n                (CUDD_VALUE_TYPE) addConstant);\n            }\n          }\n\n          /* StQ 11.02.2004:\n             Bug fixed --> Reference All Nodes for ADD */\n          Cudd_Ref (pnodes[i]);       \n          Dddmp_CheckAndGotoLabel (pnodes[i]==NULL, \"NULL pnodes.\",\n            failure);\n          continue;\n        } else {\n#ifdef DDDMP_DEBUG\n          Dddmp_Assert (idT>0, \"id > 0\");\n#endif\n          var = atoi(buf);\n          T = pnodes[idT];\n          if(idE<0) {\n            idE = -idE;\n            E = pnodes[idE];\n            E = Cudd_Not(E);\n          } else {\n            E = pnodes[idE];\n          }\n        }\n\n        break;\n\n      /*\n       *  Binary FORMAT\n       */\n\n      case DDDMP_MODE_BINARY:\n\n        Dddmp_CheckAndGotoLabel (DddmpReadCode(fp,&code) == 0,\n          \"Error Reading witn ReadCode.\", failure);\n\n        switch (code.V) {\n        case DDDMP_TERMINAL:     \n          /* only 1 terminal presently supported */    \n          pnodes[i] = Cudd_ReadOne (ddMgr);       \n          continue; \n          break;\n        case DDDMP_RELATIVE_1:\n          break;\n        case DDDMP_RELATIVE_ID:\n        case DDDMP_ABSOLUTE_ID:\n          size = DddmpReadInt (fp, &var);\n          Dddmp_CheckAndGotoLabel (size==0, \"Error reading size.\",\n            failure);\n          break;\n        }\n\n        switch (code.T) {\n        case DDDMP_TERMINAL:     \n          idT = 1;\n          break;\n        case DDDMP_RELATIVE_1:\n          idT = i-1;\n          break;\n        case DDDMP_RELATIVE_ID:\n          size = DddmpReadInt (fp, &id);\n          Dddmp_CheckAndGotoLabel (size==0, \"Error reading size.\",\n            failure);\n          idT = i-id;\n          break;\n        case DDDMP_ABSOLUTE_ID:\n          size = DddmpReadInt (fp, &idT);\n          Dddmp_CheckAndGotoLabel (size==0, \"Error reading size.\",\n            failure);\n          break;\n        }\n\n        switch (code.E) {\n        case DDDMP_TERMINAL:     \n          idE = 1;\n          break;\n        case DDDMP_RELATIVE_1:\n          idE = i-1;\n          break;\n        case DDDMP_RELATIVE_ID:\n          size = DddmpReadInt (fp, &id);\n          Dddmp_CheckAndGotoLabel (size==0, \"Error reading size.\",\n            failure);\n          idE = i-id;\n          break;\n        case DDDMP_ABSOLUTE_ID:\n          size = DddmpReadInt (fp, &idE);\n          Dddmp_CheckAndGotoLabel (size==0, \"Error reading size.\",\n            failure);\n          break;\n        }\n\n#ifdef DDDMP_DEBUG\n      Dddmp_Assert (idT<i, \"id<i\");\n#endif\n      T = pnodes[idT];\n      if (cuddIsConstant(T))\n        vT = Hdr->nsuppvars;\n      else {\n        if (pvars1byte != NULL)\n          vT = pvars1byte[idT];\n        else if (pvars2byte != NULL)\n          vT = pvars2byte[idT];\n        else\n          vT = invconvertids[T->index];\n      }\n#ifdef DDDMP_DEBUG\n      Dddmp_Assert (vT>0, \"vT > 0\");\n      Dddmp_Assert (vT<=Hdr->nsuppvars, \"vT <= Hdr->nsuppvars\");\n#endif\n\n#ifdef DDDMP_DEBUG\n      Dddmp_Assert (idE<i, \"idE < i\");\n#endif\n      E = pnodes[idE];\n      if (cuddIsConstant(E))\n        vE = Hdr->nsuppvars;\n      else {\n        if (pvars1byte != NULL)\n          vE = pvars1byte[idE];\n        else if (pvars2byte != NULL)\n          vE = pvars2byte[idE];\n        else\n          vE = invconvertids[E->index];\n      }\n#ifdef DDDMP_DEBUG\n      Dddmp_Assert (vE>0, \"vE > 0\");\n      Dddmp_Assert (vE<=Hdr->nsuppvars, \"vE <= Hdr->nsuppvars\");\n#endif\n  \n      switch (code.V) {\n        case DDDMP_TERMINAL:     \n        case DDDMP_ABSOLUTE_ID:\n          break;\n        case DDDMP_RELATIVE_1:\n          var = (vT<vE) ? vT-1 : vE-1;\n          break;\n        case DDDMP_RELATIVE_ID:\n          var = (vT<vE) ? vT-var : vE-var;\n          break;\n      }\n\n      if (code.Ecompl) {\n        E = Cudd_Not(E);\n      }\n\n#ifdef DDDMP_DEBUG\n      Dddmp_Assert (var<Hdr->nsuppvars, \"var < Hdr->nsuppvars\");\n#endif\n\n      break;\n    }\n\n    if (pvars1byte != NULL) {\n      pvars1byte[i] = (unsigned char) var;\n    } else {\n      if (pvars2byte != NULL) {\n        pvars2byte[i] = (unsigned short) var;\n      }\n    }\n\n    var = convertids[var];\n    switch (ddType) {\n      case DDDMP_BDD: \n        pnodes[i] = Cudd_bddIte (ddMgr, Cudd_bddIthVar (ddMgr, var),\n          T, E);\n        break;\n      case DDDMP_ADD: \n        { \n        DdNode *tmp = Cudd_addIthVar (ddMgr, var);\n        Cudd_Ref (tmp);\n        pnodes[i] = Cudd_addIte (ddMgr, tmp, T, E);\n        Cudd_RecursiveDeref (ddMgr, tmp);\n        break;\n        }\n      case DDDMP_CNF:\n      case DDDMP_NONE:\n        Dddmp_Warning (1, \"Wrong DD Type.\");\n        break;\n     }\n\n    cuddRef (pnodes[i]);\n  }\n\n  /*------------------------ Deal With the File Tail -----------------------*/\n\n  retval = fgets (buf, DDDMP_MAXSTRLEN-1,fp);\n  Dddmp_CheckAndGotoLabel (!retval, \"Error on reading file tail.\", failure);\n  Dddmp_CheckAndGotoLabel (!matchkeywd(buf, \".end\"),\n    \"Error .end not found.\", failure);\n\n  /* Close File IFF Necessary */\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n  /* BDD Roots */\n  proots = DDDMP_ALLOC(DdNode *,nRoots);\n  Dddmp_CheckAndGotoLabel (proots==NULL, \"Error allocating memory.\",\n    failure);\n\n  for(i=0; i<nRoots; ++i) {\n    switch (rootMatchMode) {\n      case DDDMP_ROOT_MATCHNAMES:\n        for (j=0; j<nRoots; j++) {\n          if (strcmp(rootmatchnames[i], Hdr->rootnames[j]) == 0)\n            break;\n        }\n        if (j>=nRoots) {\n          /* rootname not found */\n          fprintf (stderr, \"Warning: unable to match root name <%s>\\n\",\n            rootmatchnames[i]);\n        }\n        break; \n      case DDDMP_ROOT_MATCHLIST:\n        j = i;\n        break;\n    }\n\n    id = Hdr->rootids[i];\n    if (id==0) {\n      (void) fprintf (stderr, \"DdLoad Warning: NULL root found in file\\n\");\n      fflush (stderr);\n      f = NULL;\n    } else {\n      if (id<0) {\n        f = Cudd_Not(pnodes[-id]);\n      } else {\n        f = pnodes[id];\n      }\n    }\n    proots[i] = f;\n\n    cuddRef (f);\n  } /* end for i = 0..nRoots */\n\n  /*\n   *  Decrease Reference for all Nodes\n   */\n\n  /* StQ 11.02.2004:\n     Bug fixed --> De-Reference All Nodes for ADD */\n  for (i=1; i<=Hdr->nnodes; i++) {\n    f = pnodes[i];\n    Cudd_RecursiveDeref (ddMgr, f);\n  }\n\n  /*\n   *  Free Memory: load_end label\n   */\n\nload_end:\n\n  DddmpFreeHeader(Hdr);\n\n  DDDMP_FREE (pnodes);\n  DDDMP_FREE (pvars1byte);\n  DDDMP_FREE (pvars2byte);\n\n  /* variable names are not freed because they were shared with varnames */\n  DDDMP_FREE (sortedvarnames);\n\n  DDDMP_FREE (permsupport);\n  DDDMP_FREE (convertids);\n  DDDMP_FREE (invconvertids);\n  DDDMP_FREE (invauxids);\n\n  *pproots = proots;\n  return (nRoots);\n\n  /*\n   *  Failure Condition\n   */\n\nfailure:\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n  nRoots = 0; /* return 0 on error ! */\n\n  DDDMP_FREE (proots);\n\n  goto load_end; /* this is done to free memory */\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a the header of a dump file representing the\n    argument BDDs.\n    ]\n\n  Description [Reads the header of a dump file. Builds a Dddmp_Hdr_t struct\n    containing all infos in the header, for next manipulations.\n    ]\n\n  SideEffects [none]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic Dddmp_Hdr_t *\nDddmpBddReadHeader (\n  char *file\t    /* IN: file name */,\n  FILE *fp          /* IN: file pointer */\n  )\n{\n  Dddmp_Hdr_t *Hdr = NULL;\n  char buf[DDDMP_MAXSTRLEN];\n  int retValue, fileToClose = 0;\n  char *retval;\n\n  if (fp == NULL) {\n    fp = fopen (file, \"r\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  /* START HEADER */\n\n  Hdr = DDDMP_ALLOC (Dddmp_Hdr_t,1);\n  if (Hdr == NULL) {\n    return NULL;\n  }\n  Hdr->ver = NULL;\n  Hdr->mode = 0;\n  Hdr->ddType = DDDMP_BDD;\n  Hdr->varinfo = DDDMP_VARIDS;\n  Hdr->dd = NULL;\n  Hdr->nnodes = 0;\n  Hdr->nVars = 0;\n  Hdr->nsuppvars = 0;\n  Hdr->suppVarNames = NULL;\n  Hdr->orderedVarNames = NULL;\n  Hdr->ids = NULL;\n  Hdr->permids = NULL;\n  Hdr->auxids = NULL;\n  Hdr->cnfids = NULL;\n  Hdr->nRoots = 0;\n  Hdr->rootids = NULL;\n  Hdr->rootnames = NULL;\n  Hdr->nAddedCnfVar = 0;\n  Hdr->nVarsCnf = 0;\n  Hdr->nClausesCnf = 0;\n\n  while (fscanf(fp, \"%s\", buf)!=EOF) {\n\n    /* comment */\n    if (buf[0] == '#') {\n      retval = fgets(buf,DDDMP_MAXSTRLEN,fp);\n      Dddmp_CheckAndGotoLabel (!retval, \"Error on reading comment.\", failure);\n      continue;\n    }\n\n    Dddmp_CheckAndGotoLabel (buf[0] != '.',\n      \"Error; line must begin with '.' or '#'.\",\n        failure);\n\n    if (matchkeywd(buf, \".ver\")) {    \n      /* this not checked so far: only read */\n      retValue = fscanf (fp, \"%s\", buf);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading from file.\",\n        failure);\n\n      Hdr->ver=DddmpStrDup(buf);\n      Dddmp_CheckAndGotoLabel (Hdr->ver==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".add\")) {    \n      Hdr->ddType = DDDMP_ADD;\n      continue;\n    }\n\n    if (matchkeywd(buf, \".bdd\")) {    \n      Hdr->ddType = DDDMP_BDD;\n      continue;\n    }\n\n    if (matchkeywd(buf, \".mode\")) {    \n      retValue = fscanf (fp, \"%s\", buf);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading to file.\",\n        failure);\n\n      Hdr->mode = buf[0];\n      continue;\n    }\n\n    if (matchkeywd(buf, \".varinfo\")) {\n      int readMe;\n      retValue = fscanf (fp, \"%d\", &readMe);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n      Hdr->varinfo = (Dddmp_VarInfoType) readMe;\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".dd\")) {    \n      retValue = fscanf (fp, \"%s\", buf);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      Hdr->dd = DddmpStrDup (buf);\n      Dddmp_CheckAndGotoLabel (Hdr->dd==NULL, \"Error allocating memory.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".nnodes\")) {\n      retValue = fscanf (fp, \"%d\", &(Hdr->nnodes));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".nvars\")) {   \n      retValue = fscanf (fp, \"%d\", &(Hdr->nVars));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".nsuppvars\")) {\n      retValue = fscanf (fp, \"%d\", &(Hdr->nsuppvars));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".orderedvarnames\")) {\n      Hdr->orderedVarNames = DddmpStrArrayRead (fp, Hdr->nVars);\n      Dddmp_CheckAndGotoLabel (Hdr->orderedVarNames==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".suppvarnames\") ||\n      (Hdr->ver != NULL && (strcmp (Hdr->ver, \"DDDMP-1.0\") == 0) &&\n      matchkeywd (buf, \".varnames\"))) {\n      Hdr->suppVarNames = DddmpStrArrayRead (fp, Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->suppVarNames==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if matchkeywd(buf, \".ids\") {\n      Hdr->ids = DddmpIntArrayRead(fp,Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->ids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".permids\")) {\n      Hdr->permids = DddmpIntArrayRead(fp,Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->permids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".auxids\")) {\n      Hdr->auxids = DddmpIntArrayRead(fp,Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->auxids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".nroots\")) {\n      retValue = fscanf (fp, \"%d\", &(Hdr->nRoots));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".rootids\")) {\n      Hdr->rootids = DddmpIntArrayRead(fp,Hdr->nRoots);\n      Dddmp_CheckAndGotoLabel (Hdr->rootids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".rootnames\")) {\n      Hdr->rootnames = DddmpStrArrayRead(fp,Hdr->nRoots);\n      Dddmp_CheckAndGotoLabel (Hdr->rootnames==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd(buf, \".nodes\")) {\n      retval = fgets(buf,DDDMP_MAXSTRLEN,fp);\n      Dddmp_CheckAndGotoLabel (!retval, \"Error on reading nodes.\", failure);\n      break;\n    }\n\n  }\n\n  /* END HEADER */\n\n  return (Hdr);\n\nfailure:\n\n  if (fileToClose == 1) {\n    fclose (fp);\n  }\n\n  DddmpFreeHeader(Hdr);\n\n  return (NULL);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis    [Frees the internal header structure.]\n\n  Description [Frees the internal header structureby freeing all internal\n    fields first.\n    ]\n\n  SideEffects []\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic void\nDddmpFreeHeader (\n  Dddmp_Hdr_t *Hdr   /* IN: pointer to header */\n  )\n{\n  DDDMP_FREE (Hdr->ver);\n  DDDMP_FREE (Hdr->dd);\n  DddmpStrArrayFree (Hdr->orderedVarNames, Hdr->nVars);\n  DddmpStrArrayFree (Hdr->suppVarNames, Hdr->nsuppvars);\n  DDDMP_FREE (Hdr->ids);\n  DDDMP_FREE (Hdr->permids);\n  DDDMP_FREE (Hdr->auxids);\n  DDDMP_FREE (Hdr->rootids);\n  DddmpStrArrayFree (Hdr->rootnames, Hdr->nRoots);\n\n  DDDMP_FREE (Hdr);\n\n  return;\n}\n\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpLoadCnf.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpLoadCnf.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to read in CNF from file as BDDs.]\n\n  Description  [Functions to read in CNF from file as BDDs.\n    ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define DDDMP_MAX_CNF_ROW_LENGTH 1000\n#define DDDMP_DEBUG_CNF 0\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#define matchkeywd(str,key) (strncmp(str,key,strlen(key))==0)\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int DddmpCuddDdArrayLoadCnf(DdManager *ddMgr, Dddmp_RootMatchType rootmatchmode, char **rootmatchnames, Dddmp_VarMatchType varmatchmode, char **varmatchnames, int *varmatchauxids, int *varcomposeids, int mode, char *file, FILE *fp, DdNode ***rootsPtrPtr, int *nRoots);\nstatic Dddmp_Hdr_t * DddmpBddReadHeaderCnf(char *file, FILE *fp);\nstatic void DddmpFreeHeaderCnf(Dddmp_Hdr_t *Hdr);\nstatic int DddmpReadCnfClauses(Dddmp_Hdr_t *Hdr, int ***cnfTable, FILE *fp);\nstatic int DddmpCnfClauses2Bdd(Dddmp_Hdr_t *Hdr, DdManager *ddMgr, int **cnfTable, int mode, DdNode ***rootsPtrPtr);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Reads a dump file in a CNF format.]\n\n  Description  [Reads a dump file representing the argument BDD in a\n    CNF formula.\n    Dddmp_cuddBddArrayLoadCnf is used through a dummy array.\n    The results is returned in different formats depending on the \n    mode selection:\n      IFF mode == 0 Return the Clauses without Conjunction\n      IFF mode == 1 Return the sets of BDDs without Quantification\n      IFF mode == 2 Return the sets of BDDs AFTER Existential Quantification\n   ]\n\n  SideEffects  [A vector of pointers to DD nodes is allocated and freed.]\n\n  SeeAlso      [Dddmp_cuddBddLoad, Dddmp_cuddBddArrayLoad]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddLoadCnf (\n  DdManager *ddMgr                /* IN: DD Manager */,\n  Dddmp_VarMatchType varmatchmode /* IN: storing mode selector */,\n  char **varmatchnames            /* IN: array of variable names, by IDs */,\n  int *varmatchauxids             /* IN: array of variable auxids, by IDs */,\n  int *varcomposeids              /* IN: array of new ids accessed, by IDs */,\n  int mode                        /* IN: computation mode */,\n  char *file\t\t          /* IN: file name */,\n  FILE *fp                        /* IN: file pointer */,\n  DdNode ***rootsPtrPtr           /* OUT: array of returned BDD roots */,\n  int *nRoots                     /* OUT: number of BDDs returned */\n  )\n{\n  int i, retValue;\n\n  retValue = Dddmp_cuddBddArrayLoadCnf (ddMgr, DDDMP_ROOT_MATCHLIST, NULL,\n    varmatchmode, varmatchnames, varmatchauxids, varcomposeids, mode,\n    file, fp, rootsPtrPtr, nRoots);\n\n  if (retValue == DDDMP_FAILURE) {\n    return (DDDMP_FAILURE);\n  }\n\n  if (*nRoots > 1) {\n    fprintf (stderr,\n      \"Warning: %d BDD roots found in file. Only first retrieved.\\n\",\n      *nRoots);\n    for (i=1; i<*nRoots; i++) {\n      Cudd_RecursiveDeref (ddMgr, *rootsPtrPtr[i]);\n    } \n  } \n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Reads a dump file in a CNF format.]\n\n  Description  [Reads a dump file representing the argument BDD in a\n    CNF formula.\n    ]\n\n  SideEffects  [A vector of pointers to DD nodes is allocated and freed.]\n\n  SeeAlso      [Dddmp_cuddBddArrayLoad]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddArrayLoadCnf (\n  DdManager *ddMgr                 /* IN: DD Manager */,\n  Dddmp_RootMatchType rootmatchmode/* IN: storing mode selector */,\n  char **rootmatchnames            /* IN: sorted names for loaded roots */,\n  Dddmp_VarMatchType varmatchmode  /* IN: storing mode selector */,\n  char **varmatchnames             /* IN: array of variable names, by IDs */,\n  int *varmatchauxids              /* IN: array of variable auxids, by IDs */,\n  int *varcomposeids               /* IN: array of new ids, by IDs */,\n  int mode                         /* IN: computation Mode */,\n  char *file\t\t           /* IN: file name */,\n  FILE *fp                         /* IN: file pointer */,\n  DdNode ***rootsPtrPtr            /* OUT: array of returned BDD roots */,\n  int *nRoots                      /* OUT: number of BDDs returned */\n  )\n{\n  int retValue;\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValueBis;\n\n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During CNF Load.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During CNF Load.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  retValue = DddmpCuddDdArrayLoadCnf (ddMgr, rootmatchmode,\n    rootmatchnames, varmatchmode, varmatchnames, varmatchauxids,\n    varcomposeids, mode, file, fp, rootsPtrPtr, nRoots);\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During CNF Load.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During CNF Load.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads the header of a dump file representing the argument BDDs]\n\n  Description [Reads the header of a dump file representing the argument BDDs. \n    Returns main information regarding DD type stored in the file,\n    the variable ordering used, the number of variables, etc.\n    It reads only the header of the file NOT the BDD/ADD section. \n    ]\n\n  SideEffects []\n\n  SeeAlso     [Dddmp_cuddBddArrayLoad]\n\n******************************************************************************/\n\nint\nDddmp_cuddHeaderLoadCnf (\n  int *nVars                /* OUT: number of DD variables */,\n  int *nsuppvars            /* OUT: number of support variables */,\n  char ***suppVarNames      /* OUT: array of support variable names */,\n  char ***orderedVarNames   /* OUT: array of variable names */,\n  int **varIds              /* OUT: array of variable ids */,\n  int **varComposeIds       /* OUT: array of permids ids */,\n  int **varAuxIds           /* OUT: array of variable aux ids */,\n  int *nRoots               /* OUT: number of root in the file */,\n  char *file                 /* IN: file name */,\n  FILE *fp                   /* IN: file pointer */\n  )\n{\n  Dddmp_Hdr_t *Hdr;\n  int i, fileToClose;\n  char **tmpOrderedVarNames = NULL;\n  char **tmpSuppVarNames = NULL;\n  int *tmpVarIds = NULL;\n  int *tmpVarComposeIds = NULL;\n  int *tmpVarAuxIds = NULL; \n\n  fileToClose = 0;\n  if (fp == NULL) {\n    fp = fopen (file, \"r\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  Hdr = DddmpBddReadHeaderCnf (NULL, fp);\n\n  Dddmp_CheckAndGotoLabel (Hdr->nnodes==0, \"Zero number of nodes.\",\n    failure);\n\n  /*\n   *  Number of variables (tot and support)\n   */\n\n  *nVars = Hdr->nVars;\n  *nsuppvars = Hdr->nsuppvars;\n\n  /*\n   *  Support Varnames\n   */\n\n  if (Hdr->suppVarNames != NULL) {\n    tmpSuppVarNames = DDDMP_ALLOC (char *, *nsuppvars);\n    Dddmp_CheckAndGotoLabel (tmpSuppVarNames==NULL, \"Error allocating memory.\",\n      failure);\n\n    for (i=0; i<*nsuppvars; i++) {\n      tmpSuppVarNames[i] = DDDMP_ALLOC (char,\n        (strlen (Hdr->suppVarNames[i]) + 1));\n      Dddmp_CheckAndGotoLabel (Hdr->suppVarNames[i]==NULL,\n        \"Support Variable Name Missing in File.\", failure);\n      strcpy (tmpSuppVarNames[i], Hdr->suppVarNames[i]);\n    }\n\n    *suppVarNames = tmpSuppVarNames;\n  } else {\n    *suppVarNames = NULL;\n  }\n\n  /*\n   *  Ordered Varnames\n   */\n\n  if (Hdr->orderedVarNames != NULL) {\n    tmpOrderedVarNames = DDDMP_ALLOC (char *, *nVars);\n    Dddmp_CheckAndGotoLabel (tmpOrderedVarNames==NULL,\n      \"Error allocating memory.\", failure);\n\n    for (i=0; i<*nVars; i++) {\n      tmpOrderedVarNames[i]  = DDDMP_ALLOC (char,\n        (strlen (Hdr->orderedVarNames[i]) + 1));\n      Dddmp_CheckAndGotoLabel (Hdr->orderedVarNames[i]==NULL,\n        \"Support Variable Name Missing in File.\", failure);\n      strcpy (tmpOrderedVarNames[i], Hdr->orderedVarNames[i]);\n    }\n\n    *orderedVarNames = tmpOrderedVarNames;\n  } else {\n    *orderedVarNames = NULL;\n  }\n\n  /*\n   *  Variable Ids\n   */\n\n  if (Hdr->ids != NULL) {\n    tmpVarIds = DDDMP_ALLOC (int, *nsuppvars);\n    Dddmp_CheckAndGotoLabel (tmpVarIds==NULL, \"Error allocating memory.\",\n      failure);\n    for (i=0; i<*nsuppvars; i++) {\n      tmpVarIds[i] = Hdr->ids[i];\n    }\n\n    *varIds = tmpVarIds; \n  } else {\n    *varIds = NULL;\n  }\n\n  /*\n   *  Variable Compose Ids\n   */\n\n  if (Hdr->permids != NULL) {\n    tmpVarComposeIds = DDDMP_ALLOC (int, *nsuppvars);\n    Dddmp_CheckAndGotoLabel (tmpVarComposeIds==NULL,\n      \"Error allocating memory.\", failure);\n    for (i=0; i<*nsuppvars; i++) {\n      tmpVarComposeIds[i] = Hdr->permids[i];\n    }\n\n    *varComposeIds = tmpVarComposeIds; \n  } else {\n    *varComposeIds = NULL;\n  }\n\n  /*\n   *  Variable Auxiliary Ids\n   */\n\n  if (Hdr->auxids != NULL) {\n    tmpVarAuxIds = DDDMP_ALLOC (int, *nsuppvars);\n    Dddmp_CheckAndGotoLabel (tmpVarAuxIds==NULL,\n      \"Error allocating memory.\", failure);\n    for (i=0; i<*nsuppvars; i++) {\n      tmpVarAuxIds[i] = Hdr->auxids[i];\n    }\n\n    *varAuxIds = tmpVarAuxIds; \n  } else {\n    *varAuxIds = NULL;\n  }\n\n  /*\n   *  Number of roots\n   */\n\n  *nRoots = Hdr->nRoots;\n\n  /*\n   *  Free and Return\n   */\n\n  if (fileToClose == 1) {\n    fclose (fp);\n  }\n\t\n  DddmpFreeHeaderCnf (Hdr);\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n    return (DDDMP_FAILURE);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a dump file representing the argument BDDs in CNF\n     format.\n    ]\n\n  Description [Reads a dump file representing the argument BDDs in CNF\n    format.\n      IFF mode == 0 Return the Clauses without Conjunction\n      IFF mode == 1 Return the sets of BDDs without Quantification\n      IFF mode == 2 Return the sets of BDDs AFTER Existential Quantification\n    ]\n\n  SideEffects [A vector of pointers to DD nodes is allocated and freed.]\n\n  SeeAlso     [Dddmp_cuddBddArrayLoad]\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayLoadCnf (\n  DdManager *ddMgr                 /* IN: DD Manager */,\n  Dddmp_RootMatchType rootmatchmode/* IN: storing mode selector */,\n  char **rootmatchnames            /* IN: sorted names for loaded roots */,\n  Dddmp_VarMatchType varmatchmode  /* IN: storing mode selector */,\n  char **varmatchnames             /* IN: array of variable names, by ids */,\n  int *varmatchauxids              /* IN: array of variable auxids, by ids */,\n  int *varcomposeids               /* IN: array of new ids, by ids */,\n  int mode                         /* IN: computation mode */,\n  char *file\t\t           /* IN: file name */,\n  FILE *fp                         /* IN: file pointer */,\n  DdNode ***rootsPtrPtr            /* OUT: array of BDD roots */,\n  int *nRoots                      /* OUT: number of BDDs returned */\n  )\n{\n  Dddmp_Hdr_t *Hdr = NULL;\n  int **cnfTable = NULL;\n  int fileToClose = 0;\n  int retValue, i;\n  (void) rootmatchmode;   /* avoid warning */\n  (void) rootmatchnames;  /* avoid warning */\n  (void) varmatchmode;    /* avoid warning */\n  (void) varmatchnames;   /* avoid warning */\n  (void) varmatchauxids;  /* avoid warning */\n  (void) varcomposeids;   /* avoid warning */\n\n  fileToClose = 0;\n  *rootsPtrPtr = NULL;\n\n  if (fp == NULL) {\n    fp = fopen (file, \"r\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  /*--------------------------- Read the Header -----------------------------*/\n\n  Hdr = DddmpBddReadHeaderCnf (NULL, fp);\n\n  Dddmp_CheckAndGotoLabel (Hdr->nnodes==0, \"Zero number of nodes.\",\n    failure);\n\n  /*------------------------ Read the CNF Clauses ---------------------------*/\n\n  retValue = DddmpReadCnfClauses (Hdr, &cnfTable, fp);\n\n  Dddmp_CheckAndGotoLabel (retValue==DDDMP_FAILURE,\n    \"Read CNF Clauses Failure.\",  failure);\n\n  /*------------------------- From Clauses to BDDs --------------------------*/\n\n  retValue = DddmpCnfClauses2Bdd (Hdr, ddMgr, cnfTable, mode, rootsPtrPtr);\n\n  Dddmp_CheckAndGotoLabel (retValue==DDDMP_FAILURE,\n    \"CNF Clauses To BDDs Failure.\",  failure);\n\n  *nRoots = Hdr->nRoots;\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n  for (i=0; i<Hdr->nClausesCnf; i++) {\n    DDDMP_FREE (cnfTable[i]);\n  }\n  DDDMP_FREE (cnfTable);\n\n  DddmpFreeHeaderCnf (Hdr);\n\n  return (DDDMP_SUCCESS);\n\n  /*\n   *  Failure Condition\n   */\n\nfailure:\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n  for (i=0; i<Hdr->nClausesCnf; i++) {\n    DDDMP_FREE (cnfTable[i]);\n  }\n  DDDMP_FREE (cnfTable);\n\n  DddmpFreeHeaderCnf (Hdr);\n\n  /* return 0 on error ! */\n  nRoots = 0;\n\n  return (DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Reads a the header of a dump file representing the argument \n    BDDs.\n    ]\n\n  Description [Reads the header of a dump file. Builds a Dddmp_Hdr_t struct\n    containing all infos in the header, for next manipulations.\n    ]\n\n  SideEffects [none]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic Dddmp_Hdr_t *\nDddmpBddReadHeaderCnf (\n  char *file\t  /* IN: file name */,\n  FILE *fp        /* IN: file pointer */\n  )\n{\n  Dddmp_Hdr_t *Hdr = NULL;\n  char buf[DDDMP_MAXSTRLEN];\n  int nv, nc, retValue, fileToClose = 0;\n  char *fgetsRet;\n\n  if (fp == NULL) {\n    fp = fopen (file, \"r\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  /* Start Header */\n  Hdr = DDDMP_ALLOC (Dddmp_Hdr_t, 1);\n  if (Hdr == NULL) {\n    return NULL;\n  }\n\n  Hdr->ver = NULL;\n  Hdr->mode = 0;\n  Hdr->ddType = DDDMP_CNF;\n  Hdr->varinfo = DDDMP_VARIDS;\n  Hdr->dd = NULL;\n  Hdr->nnodes = 0;\n  Hdr->nVars = 0;\n  Hdr->nsuppvars = 0;\n  Hdr->orderedVarNames = NULL;\n  Hdr->suppVarNames = NULL;\n  Hdr->ids = NULL;\n  Hdr->permids = NULL;\n  Hdr->auxids = NULL;\n  Hdr->cnfids = NULL;\n  Hdr->nRoots = 0;\n  Hdr->rootids = NULL;\n  Hdr->rootnames = NULL;\n  Hdr->nAddedCnfVar = 0;\n  Hdr->nVarsCnf = 0;\n  Hdr->nClausesCnf = 0;\n\n  while (fscanf (fp, \"%s\", buf) != EOF) {\n\n    /* Init Problem Line */ \n    if (buf[0] == 'p') {\n      retValue = fscanf (fp, \"%*s %d %d\", &nv, &nc);\n      Dddmp_CheckAndGotoLabel (retValue!=2, \"Error reading problem line.\",\n        failure);\n      Hdr->nVarsCnf = nv;\n      Hdr->nClausesCnf = nc;\n      break;\n    }\n\n    /* CNF Comment Line */\n    if (buf[0] == 'c') {\n      if (fscanf (fp, \"%s\", buf) == EOF) {\n        break;\n      }\n    }\n\n    /* Skip Comment? */\n    if (buf[0] != '.') {\n      fgetsRet = fgets (buf, DDDMP_MAXSTRLEN, fp);\n      Dddmp_CheckAndGotoLabel (!fgetsRet, \"Error reading comment.\", failure);\n      continue;\n    }\n\n    if (matchkeywd (buf, \".ver\")) {    \n      /* this not checked so far: only read */\n      retValue = fscanf (fp, \"%s\", buf);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading from file.\",\n        failure);\n\n      Hdr->ver=DddmpStrDup(buf);\n      Dddmp_CheckAndGotoLabel (Hdr->ver==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".dd\")) {    \n      retValue = fscanf (fp, \"%s\", buf);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      Hdr->dd = DddmpStrDup (buf);\n      Dddmp_CheckAndGotoLabel (Hdr->dd==NULL, \"Error allocating memory.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".nnodes\")) {\n      retValue = fscanf (fp, \"%d\", &(Hdr->nnodes));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".nvars\")) {   \n      retValue = fscanf (fp, \"%d\", &(Hdr->nVars));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".nsuppvars\")) {\n      retValue = fscanf (fp, \"%d\", &(Hdr->nsuppvars));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".orderedvarnames\")) {\n      Hdr->orderedVarNames = DddmpStrArrayRead (fp, Hdr->nVars);\n      Dddmp_CheckAndGotoLabel (Hdr->orderedVarNames==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".suppvarnames\")) {\n      Hdr->suppVarNames = DddmpStrArrayRead (fp, Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->suppVarNames==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if matchkeywd (buf, \".ids\") {\n      Hdr->ids = DddmpIntArrayRead(fp,Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->ids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".permids\")) {\n      Hdr->permids = DddmpIntArrayRead(fp,Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->permids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".auxids\")) {\n      Hdr->auxids = DddmpIntArrayRead(fp,Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->auxids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".cnfids\")) {\n      Hdr->cnfids = DddmpIntArrayRead (fp, Hdr->nsuppvars);\n      Dddmp_CheckAndGotoLabel (Hdr->cnfids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".nroots\")) {\n      retValue = fscanf (fp, \"%d\", &(Hdr->nRoots));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".rootids\")) {\n      Hdr->rootids = DddmpIntArrayRead(fp,Hdr->nRoots);\n      Dddmp_CheckAndGotoLabel (Hdr->rootids==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n    if (matchkeywd (buf, \".rootnames\")) {\n      Hdr->rootnames = DddmpStrArrayRead(fp,Hdr->nRoots);\n      Dddmp_CheckAndGotoLabel (Hdr->rootnames==NULL,\n        \"Error allocating memory.\", failure);\n\n      continue;\n    }\n\n\n    if (matchkeywd (buf, \".nAddedCnfVar\")) {\n      retValue = fscanf (fp, \"%d\", &(Hdr->nAddedCnfVar));\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error reading file.\",\n        failure);\n\n      continue;\n    }\n  }\n\n  /* END HEADER */\n  return (Hdr);\n\nfailure:\n\n  if (fileToClose == 1) {\n    fclose (fp);\n  }\n\n  DddmpFreeHeaderCnf (Hdr);\n\n  return (NULL);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis    [Frees the internal header structure.]\n\n  Description [Frees the internal header structure by freeing all internal\n    fields first.\n    ]\n\n  SideEffects []\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic void\nDddmpFreeHeaderCnf (\n  Dddmp_Hdr_t *Hdr   /* IN: pointer to header */\n  )\n{\n  if (Hdr==NULL) {\n    return;\n  }\n\n  DDDMP_FREE (Hdr->ver);\n  DDDMP_FREE (Hdr->dd);\n  DddmpStrArrayFree (Hdr->orderedVarNames, Hdr->nVars);\n  DddmpStrArrayFree (Hdr->suppVarNames, Hdr->nsuppvars);\n  DDDMP_FREE (Hdr->ids);\n  DDDMP_FREE (Hdr->permids);\n  DDDMP_FREE (Hdr->auxids);\n  DDDMP_FREE (Hdr->cnfids);\n  DDDMP_FREE (Hdr->rootids);\n  DddmpStrArrayFree (Hdr->rootnames, Hdr->nRoots);\n\n  DDDMP_FREE (Hdr);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Read the CNF clauses from the file in the standard DIMACS\n    format.\n    ]\n\n  Description [Read the CNF clauses from the file in the standard DIMACS\n    format. Store all the clauses in an internal structure for \n    future transformation into BDDs.\n    ]\n\n  SideEffects []\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic int\nDddmpReadCnfClauses (\n  Dddmp_Hdr_t *Hdr  /*  IN: file header */,\n  int ***cnfTable   /* OUT: CNF table for clauses */,\n  FILE *fp          /*  IN: source file */\n  )\n{\n  char word[DDDMP_MAX_CNF_ROW_LENGTH];\n  int i, j, var;\n  int **cnfTableLocal = NULL;\n  int *clause = NULL;\n  char *fgetsRet;\n\n  cnfTableLocal = DDDMP_ALLOC (int *, Hdr->nClausesCnf);\n  clause = DDDMP_ALLOC (int, 2*Hdr->nVarsCnf+1);\n\n  for (i=0; i<Hdr->nClausesCnf; i++) {\n    cnfTableLocal[i] = NULL;\n  }\n\n  for (i=0; i<=2*Hdr->nVarsCnf; i++) {\n    clause[i] = 0;\n  }\n\n  i = j = 0;\n  do { \n    if (fscanf(fp, \"%s\", word)==EOF) {\n      if (j>0) {\n        /* force last zero */\n        strcpy(word,\"0\");\n      }\n      else break;\n    }\n\n    /* Check for Comment */\n    if (word[0] == 'c') {\n      /* Comment Found: Skip line */\n      fgetsRet = fgets (word, DDDMP_MAX_CNF_ROW_LENGTH-1, fp);\n      if (!fgetsRet) return (DDDMP_FAILURE);\n      break;\n    }\n\n    var = atoi (word);\n    Dddmp_Assert ((var>=(-Hdr->nVarsCnf))&&(var<=Hdr->nVarsCnf),\n      \"Wrong num found\");\n    clause[j++] = var;\n    if (var == 0) {\n      cnfTableLocal[i] = DDDMP_ALLOC (int, j);\n      while (--j >=0) {\n        cnfTableLocal[i][j] = clause[j];\n\t}\n      i++;\n      j=0;\n    }\n\n  } while (!feof(fp));\n\n  Dddmp_Assert (i==Hdr->nClausesCnf,\n    \"Wrong number of clauses in file\");\n\n#if DDDMP_DEBUG_CNF\n  for (i=0; i<Hdr->nClausesCnf; i++) {\n    fprintf (stdout, \"[%4d] \", i);\n    j=0;\n    while ((var = cnfTableLocal[i][j++]) != 0) {\n      fprintf (stdout, \"%d \", var);\n    } \n    fprintf (stdout, \"0\\n\");\n  }\n#endif\n\n  DDDMP_FREE (clause);\n\n  *cnfTable = cnfTableLocal;\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Transforms CNF clauses into BDDs.]\n\n  Description [Transforms CNF clauses into BDDs. Clauses are stored in an\n   internal structure previously read. The results can be given in\n   different format according to the mode selection:\n     IFF mode == 0 Return the Clauses without Conjunction\n     IFF mode == 1 Return the sets of BDDs without Quantification\n     IFF mode == 2 Return the sets of BDDs AFTER Existential Quantification\n   ]\n\n  SideEffects []\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic int\nDddmpCnfClauses2Bdd (\n  Dddmp_Hdr_t *Hdr       /* IN: file header */,\n  DdManager *ddMgr       /* IN: DD Manager */,\n  int **cnfTable         /* IN: CNF table for clauses */,\n  int mode               /* IN: computation mode */,\n  DdNode ***rootsPtrPtr  /* OUT: array of returned BDD roots (by reference) */\n  )\n{\n  DdNode **rel = NULL;\n  DdNode *lit = NULL;\n  DdNode *tmp1 = NULL;\n  DdNode *tmp2 = NULL;\n  DdNode **rootsPtr = NULL;\n  DdNode *cubeAllVar = NULL;\n  DdNode *cubeBddVar = NULL;\n  DdNode *cubeCnfVar = NULL;\n  int i, j, k, n, var1, var2, fromLine, toLine;\n\n  rootsPtr = NULL;\n  *rootsPtrPtr = NULL;\n\n  /*-------------------------- Read The Clauses -----------------------------*/\n\n  rel = DDDMP_ALLOC (DdNode *, Hdr->nClausesCnf);\n\n  cubeBddVar = Cudd_ReadOne (ddMgr);\n  cubeCnfVar = Cudd_ReadOne (ddMgr);\n  cubeAllVar = Cudd_ReadOne (ddMgr);\n  Cudd_Ref (cubeBddVar);\n  Cudd_Ref (cubeCnfVar);\n  Cudd_Ref (cubeAllVar);\n\n  for (i=0; i<Hdr->nClausesCnf; i++) {\n    rel[i] = Cudd_Not (Cudd_ReadOne (ddMgr));\n    Cudd_Ref (rel[i]);\n    j=0;\n    while ((var1 = cnfTable[i][j++]) != 0) {\n\n      /* Deal with the Literal */\n      var2 = abs (var1);\n      n = (-1);\n      for (k=0; k<Hdr->nsuppvars; k++) {\n        if (Hdr->cnfids[k] == var2) {\n          n = k;\n          break;\n        }\n      }\n\n      if (n == (-1)) {\n        lit = Cudd_bddIthVar (ddMgr, var2);\n\n        /* Create the cubes of CNF Variables */\n        tmp1 = Cudd_bddAnd (ddMgr, cubeCnfVar, lit);\n        Cudd_Ref (tmp1);\n        Cudd_RecursiveDeref (ddMgr, cubeCnfVar);\n        cubeCnfVar = tmp1;\n\n      } else {\n        lit = Cudd_bddIthVar (ddMgr, Hdr->ids[n]);\n\n        /* Create the cubes of BDD Variables */\n        tmp1 = Cudd_bddAnd (ddMgr, cubeBddVar, lit);\n        Cudd_Ref (tmp1);\n        Cudd_RecursiveDeref (ddMgr, cubeBddVar);\n        cubeBddVar = tmp1;\n      }\n\n      /* Create the cubes of ALL Variables */\n      tmp1 = Cudd_bddAnd (ddMgr, cubeAllVar, lit);\n      Cudd_Ref (tmp1);\n      Cudd_RecursiveDeref (ddMgr, cubeAllVar);\n      cubeAllVar = tmp1;\n\n      /* Deal with Relations */\n      if (var1<0) {\n        lit = Cudd_Not (lit);\n      }\n      tmp1 = Cudd_bddOr (ddMgr, rel[i], lit);\n      Cudd_Ref (tmp1);\n      Cudd_RecursiveDeref (ddMgr, rel[i]);\n      rel[i] = tmp1;\n    }\n  }\n\n  /*\n   *  Mode == 0 Return the Clauses without Conjunction\n   */\n\n  if (mode == 0) {\n    return (DDDMP_SUCCESS);\n  }\n\n  rootsPtr = DDDMP_ALLOC (DdNode *, Hdr->nRoots);\n  Dddmp_CheckAndGotoLabel (rootsPtr==NULL, \"Error allocating memory.\",\n    failure);\n\n  for (i=0; i<Hdr->nRoots; i++) {\n    if (i == (Hdr->nRoots-1)) {\n      fromLine = Hdr->rootids[i] - 1;\n      toLine = Hdr->nClausesCnf;\n    } else {\n      fromLine = Hdr->rootids[i] - 1;\n      toLine = Hdr->rootids[i+1];\n    }\n\n    tmp1 = Cudd_ReadOne (ddMgr);\n    Cudd_Ref (tmp1);  \n    for (j=fromLine; j<toLine; j++) {\n      tmp2 = Cudd_bddAnd (ddMgr, rel[j], tmp1);\n      Cudd_Ref (tmp2);\n      Cudd_RecursiveDeref (ddMgr, tmp1);\n      Cudd_RecursiveDeref (ddMgr, rel[j]);\n      tmp1 = tmp2;\n    }\n    rootsPtr[i] = tmp1;\n  }\n\n  DDDMP_FREE (rel);\n\n  /*\n   *  Mode == 1 Return the sets of BDDs without Quantification\n   */\n\n  if (mode == 1) {\n    *rootsPtrPtr = rootsPtr;\n    return (DDDMP_SUCCESS);\n  }\n\n  /*\n   *  Mode == 2 Return the sets of BDDs AFTER Existential Quantification\n   */\n\n#if DDDMP_DEBUG_CNF\n  cubeBddVar = Cudd_ReadOne (ddMgr);\n  Cudd_Ref (cubeBddVar);\n  for (i=0; i<Hdr->nsuppvars; i++) {\n    lit = Cudd_bddIthVar (ddMgr, Hdr->ids[i]);\n    tmp1 = Cudd_bddAnd (ddMgr, cubeBddVar, lit);\n    Cudd_Ref (tmp1);\n    Cudd_RecursiveDeref (ddMgr, cubeBddVar);\n    cubeBddVar = tmp1;\n  }\n\n  cubeCnfVar = Cudd_bddExistAbstract (ddMgr, cubeAllVar, cubeBddVar);\n#endif\n\n  for (i=0; i<Hdr->nRoots; i++) {\n#if DDDMP_DEBUG_CNF\n    fprintf (stdout, \"rootsPtr Before Exist:\\n\");\n    Cudd_PrintDebug (ddMgr, rootsPtr[i], 0, 3);\n#endif\n\n    tmp1 = Cudd_bddExistAbstract (ddMgr, rootsPtr[i], cubeCnfVar);\n    Cudd_RecursiveDeref (ddMgr, rootsPtr[i]);\n    rootsPtr[i] = tmp1;\n\n#if DDDMP_DEBUG_CNF\n    fprintf (stdout, \"rootsPtr After Exist:\\n\");\n    Cudd_PrintDebug (ddMgr, rootsPtr[i], 0, 3);\n#endif\n  }\n\n#if DDDMP_DEBUG_CNF\n  fprintf (stdout, \"cubeAllVar:\\n\");\n  Cudd_PrintDebug (ddMgr, cubeAllVar, 0, 3);\n  fprintf (stdout, \"cubeBddVar:\\n\");\n  Cudd_PrintDebug (ddMgr, cubeBddVar, 0, 3);\n  fprintf (stdout, \"cubeCnfVar:\\n\");\n  Cudd_PrintDebug (ddMgr, cubeCnfVar, 0, 3);\n#endif\n    \n  Cudd_RecursiveDeref (ddMgr, cubeAllVar);\n  Cudd_RecursiveDeref (ddMgr, cubeBddVar);\n  Cudd_RecursiveDeref (ddMgr, cubeCnfVar);\n  *rootsPtrPtr = rootsPtr;\n\n  return (DDDMP_SUCCESS);\n\n  /*\n   *  Failure Condition\n   */\n\nfailure:\n\n  DDDMP_FREE (rel);\n  DDDMP_FREE (rootsPtrPtr);\n\n  return (DDDMP_FAILURE);\n}\n\n\n\n\n\n\n\n\n\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpNodeAdd.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpNodeAdd.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to handle ADD node infos and numbering]\n\n  Description  [Functions to handle ADD node infos and numbering.\n    ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int NumberNodeRecurAdd(DdNode *f, int id);\nstatic void RemoveFromUniqueRecurAdd(DdManager *ddMgr, DdNode *f);\nstatic void RestoreInUniqueRecurAdd(DdManager *ddMgr, DdNode *f);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [Removes nodes from unique table and number them]\n\n  Description [Node numbering is required to convert pointers to integers.\n    Since nodes are removed from unique table, no new nodes should \n    be generated before re-inserting nodes in the unique table\n    (DddmpUnnumberDdNodes()).\n    ]\n\n  SideEffects [Nodes are temporarily removed from unique table]\n\n  SeeAlso     [RemoveFromUniqueRecurAdd (), NumberNodeRecurAdd (), \n    DddmpUnnumberDdNodesAdd ()]\n\n******************************************************************************/\n\nint\nDddmpNumberAddNodes (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode **f        /* IN: array of BDDs */,\n  int n             /* IN: number of BDD roots in the array of BDDs */\n  )\n{\n  int id=0, i;\n\n  for (i=0; i<n; i++) {\n    RemoveFromUniqueRecurAdd (ddMgr, f[i]);\n  }\n\n  for (i=0; i<n; i++) {\n    id = NumberNodeRecurAdd (f[i], id);\n  }\n\n  return (id);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis     [Restores nodes in unique table, loosing numbering]\n\n  Description  [Node indexes are no more needed. Nodes are re-linked in the\n    unique table.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpNumberDdNodeAdd ()]\n\n******************************************************************************/\n\nvoid\nDddmpUnnumberAddNodes (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode **f        /* IN: array of BDDs */,\n  int n             /* IN: number of BDD roots in the array of BDDs */\n  )\n{\n  int i;\n\n  for (i=0; i<n; i++) {\n    RestoreInUniqueRecurAdd (ddMgr, f[i]);\n  }\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Write index to node]\n\n  Description  [The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpReadNodeIndexAdd (), DddmpSetVisitedAdd (),\n    DddmpVisitedAdd ()]\n\n******************************************************************************/\n\nvoid \nDddmpWriteNodeIndexAdd (\n  DdNode *f   /* IN: BDD node */,\n  int id      /* IN: index to be written */\n  )\n{\n  if (1 || !Cudd_IsConstant (f)) {\n    f->next = (struct DdNode *)((ptruint)id<<1);\n  }\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Reads the index of a node]\n\n  Description  [Reads the index of a node. LSB is skipped (used as visited\n    flag).\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpWriteNodeIndexAdd (), DddmpSetVisitedAdd  (),\n    DddmpVisitedAdd ()]\n\n******************************************************************************/\n\nint\nDddmpReadNodeIndexAdd (\n  DdNode *f    /* IN: BDD node */\n  )\n{\n  if (1 || !Cudd_IsConstant (f)) {\n    return ((int)(((ptruint)(f->next))>>1));\n  } else {\n    return (1);\n  }\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Returns true if node is visited]\n\n  Description  [Returns true if node is visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpSetVisitedAdd (), DddmpClearVisitedAdd ()]\n\n******************************************************************************/\n\nint\nDddmpVisitedAdd (\n  DdNode *f    /* IN: BDD node to be tested */\n  )\n{\n  f = Cudd_Regular(f);\n  return ((int)((ptruint)(f->next)) & (01));\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Marks a node as visited]\n \n  Description  [Marks a node as visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpVisitedAdd (), DddmpClearVisitedAdd ()]\n\n******************************************************************************/\n\nvoid\nDddmpSetVisitedAdd (\n  DdNode *f   /* IN: BDD node to be marked (as visited) */\n  )\n{\n  f = Cudd_Regular(f);\n\n  f->next = (DdNode *)(ptruint)((int)((ptruint)(f->next))|01);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Marks a node as not visited]\n\n  Description  [Marks a node as not visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpVisitedAdd (), DddmpSetVisitedAdd ()]\n\n******************************************************************************/\n\nvoid\nDddmpClearVisitedAdd (\n  DdNode *f    /* IN: BDD node to be marked (as not visited) */\n  )\n{\n  f = Cudd_Regular (f);\n\n  f->next = (DdNode *)(ptruint)((int)((ptruint)(f->next)) & (~01));\n\n  return;\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Number nodes recursively in post-order]\n\n  Description  [Number nodes recursively in post-order.\n    The \"visited\" flag is used with inverse polarity, because all nodes\n    were set \"visited\" when removing them from unique. \n    ]\n\n  SideEffects  [\"visited\" flags are reset.]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nNumberNodeRecurAdd (\n  DdNode *f  /*  IN: root of the BDD to be numbered */,\n  int id     /* IN/OUT: index to be assigned to the node */\n  )\n{\n  f = Cudd_Regular(f);\n\n  if (!DddmpVisitedAdd (f)) {\n    return (id);\n  }\n\n  if (!cuddIsConstant (f)) {\n    id = NumberNodeRecurAdd (cuddT (f), id);\n    id = NumberNodeRecurAdd (cuddE (f), id);\n  }\n\n  DddmpWriteNodeIndexAdd (f, ++id);\n  DddmpClearVisitedAdd (f);\n\n  return (id);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Removes a node from unique table]\n\n  Description [Removes a node from the unique table by locating the proper\n    subtable and unlinking the node from it. It recurs on the \n    children of the node. Constants remain untouched.\n    ]\n\n  SideEffects [Nodes are left with the \"visited\" flag true.]\n\n  SeeAlso     [RestoreInUniqueRecurAdd ()]\n\n******************************************************************************/\n\nstatic void\nRemoveFromUniqueRecurAdd (\n  DdManager *ddMgr  /*  IN: DD Manager */,\n  DdNode *f         /*  IN: root of the BDD to be extracted */\n  )\n{\n  DdNode *node, *last, *next;\n  DdNode *sentinel = &(ddMgr->sentinel);\n  DdNodePtr *nodelist;\n  DdSubtable *subtable;\n  int pos, level;\n\n  f = Cudd_Regular (f);\n\n  if (DddmpVisitedAdd (f)) {\n    return;\n  }\n\n  if (!cuddIsConstant (f)) {\n\n    RemoveFromUniqueRecurAdd (ddMgr, cuddT (f));\n    RemoveFromUniqueRecurAdd (ddMgr, cuddE (f));\n\n    level = ddMgr->perm[f->index];\n    subtable = &(ddMgr->subtables[level]);\n\n    nodelist = subtable->nodelist;\n\n    pos = ddHash (cuddT (f), cuddE (f), subtable->shift);\n    node = nodelist[pos];\n    last = NULL;\n    while (node != sentinel) {\n      next = node->next;\n      if (node == f) {\n        if (last != NULL)  \n  \t  last->next = next;\n        else \n          nodelist[pos] = next;\n        break;\n      } else {\n        last = node;\n        node = next;\n      }\n    }\n\n    f->next = NULL;\n\n  }\n\n  DddmpSetVisitedAdd (f);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Restores a node in unique table]\n\n  Description  [Restores a node in unique table (recursively)]\n\n  SideEffects  [Nodes are not restored in the same order as before removal]\n\n  SeeAlso      [RemoveFromUniqueAdd ()]\n\n******************************************************************************/\n\nstatic void\nRestoreInUniqueRecurAdd (\n  DdManager *ddMgr /*  IN: DD Manager */,\n  DdNode *f        /*  IN: root of the BDD to be restored */\n  )\n{\n  DdNodePtr *nodelist;\n  DdNode *T, *E, *looking;\n  DdNodePtr *previousP;\n  DdSubtable *subtable;\n  int pos, level;\n#ifdef DDDMP_DEBUG\n  DdNode *node;\n  DdNode *sentinel = &(ddMgr->sentinel);\n#endif\n\n  f = Cudd_Regular(f);\n\n  if (!Cudd_IsComplement (f->next)) {\n    return;\n  }\n\n  if (cuddIsConstant (f)) {\n    /* StQ 11.02.2004:\n       Bug fixed --> restore NULL within the next field */\n    /*DddmpClearVisitedAdd (f);*/\n    f->next = NULL;\n\n    return;\n  }\n\n  RestoreInUniqueRecurAdd (ddMgr, cuddT (f));\n  RestoreInUniqueRecurAdd (ddMgr, cuddE (f));\n\n  level = ddMgr->perm[f->index];\n  subtable = &(ddMgr->subtables[level]);\n\n  nodelist = subtable->nodelist;\n\n  pos = ddHash (cuddT (f), cuddE (f), subtable->shift);\n\n#ifdef DDDMP_DEBUG\n  /* verify uniqueness to avoid duplicate nodes in unique table */\n  for (node=nodelist[pos]; node != sentinel; node=node->next)\n    assert(node!=f);\n#endif\n\n  T = cuddT (f);\n  E = cuddE (f);\n  previousP = &(nodelist[pos]);\n  looking = *previousP;\n\n  while (T < cuddT (looking)) {\n    previousP = &(looking->next);\n    looking = *previousP;\n  }\n\n  while (T == cuddT (looking) && E < cuddE (looking)) {\n    previousP = &(looking->next);\n    looking = *previousP;\n  }\n\n  f->next = *previousP;\n  *previousP = f;\n\n  return;\n}\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpNodeBdd.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpNodeBdd.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to handle BDD node infos and numbering]\n\n  Description  [Functions to handle BDD node infos and numbering.\n    ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int NumberNodeRecurBdd(DdNode *f, int id);\nstatic void RemoveFromUniqueRecurBdd(DdManager *ddMgr, DdNode *f);\nstatic void RestoreInUniqueRecurBdd(DdManager *ddMgr, DdNode *f);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [Removes nodes from unique table and number them]\n\n  Description [Node numbering is required to convert pointers to integers.\n    Since nodes are removed from unique table, no new nodes should \n    be generated before re-inserting nodes in the unique table\n    (DddmpUnnumberBddNodes ()).\n    ]\n\n  SideEffects [Nodes are temporarily removed from unique table]\n\n  SeeAlso     [RemoveFromUniqueRecur(), NumberNodeRecur(), \n    DddmpUnnumberBddNodes ()]\n\n******************************************************************************/\n\nint\nDddmpNumberBddNodes (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode **f        /* IN: array of BDDs */,\n  int n             /* IN: number of BDD roots in the array of BDDs */\n  )\n{\n  int id=0, i;\n\n  for (i=0; i<n; i++) {\n    RemoveFromUniqueRecurBdd (ddMgr, f[i]);\n  }\n\n  for (i=0; i<n; i++) {\n    id = NumberNodeRecurBdd (f[i], id);\n  }\n\n  return (id);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis     [Restores nodes in unique table, loosing numbering]\n\n  Description  [Node indexes are no more needed. Nodes are re-linked in the\n    unique table.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpNumberBddNode ()]\n\n******************************************************************************/\n\nvoid\nDddmpUnnumberBddNodes(\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode **f        /* IN: array of BDDs */,\n  int n             /* IN: number of BDD roots in the array of BDDs */\n  )\n{\n  int i;\n\n  for (i=0; i<n; i++) {\n    RestoreInUniqueRecurBdd (ddMgr, f[i]);\n  }\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Write index to node]\n\n  Description  [The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpReadNodeIndexBdd(), DddmpSetVisitedBdd (),\n    DddmpVisitedBdd ()]\n\n******************************************************************************/\n\nvoid \nDddmpWriteNodeIndexBdd (\n  DdNode *f   /* IN: BDD node */,\n  int id       /* IN: index to be written */\n  )\n{\n  if (!Cudd_IsConstant (f)) {\n    f->next = (struct DdNode *)((ptruint)id<<1);\n  }\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Reads the index of a node]\n\n  Description  [Reads the index of a node. LSB is skipped (used as visited\n    flag).\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpWriteNodeIndexBdd (), DddmpSetVisitedBdd (),\n    DddmpVisitedBdd ()]\n\n******************************************************************************/\n\nint\nDddmpReadNodeIndexBdd (\n  DdNode *f    /* IN: BDD node */\n  )\n{\n  if (!Cudd_IsConstant (f)) {\n    return ((int)(((ptruint)(f->next))>>1));\n  } else {\n    return (1);\n  }\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Returns true if node is visited]\n\n  Description  [Returns true if node is visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpSetVisitedBdd (), DddmpClearVisitedBdd ()]\n\n******************************************************************************/\n\nint\nDddmpVisitedBdd (\n  DdNode *f    /* IN: BDD node to be tested */\n  )\n{\n  f = Cudd_Regular(f);\n\n  return ((int)((ptruint)(f->next)) & (01));\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Marks a node as visited]\n \n  Description  [Marks a node as visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpVisitedBdd (), DddmpClearVisitedBdd ()]\n\n******************************************************************************/\n\nvoid\nDddmpSetVisitedBdd (\n  DdNode *f   /* IN: BDD node to be marked (as visited) */\n  )\n{\n  f = Cudd_Regular(f);\n\n  f->next = (DdNode *)(ptruint)((int)((ptruint)(f->next))|01);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Marks a node as not visited]\n\n  Description  [Marks a node as not visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpVisited (), DddmpSetVisited ()]\n\n******************************************************************************/\n\nvoid\nDddmpClearVisitedBdd (\n  DdNode *f    /* IN: BDD node to be marked (as not visited) */\n  )\n{\n  f = Cudd_Regular (f);\n\n  f->next = (DdNode *)(ptruint)((int)((ptruint)(f->next)) & (~01));\n\n  return;\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Number nodes recursively in post-order]\n\n  Description  [Number nodes recursively in post-order.\n    The \"visited\" flag is used with inverse polarity, because all nodes\n    were set \"visited\" when removing them from unique. \n    ]\n\n  SideEffects  [\"visited\" flags are reset.]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nNumberNodeRecurBdd (\n  DdNode *f  /*  IN: root of the BDD to be numbered */,\n  int id     /* IN/OUT: index to be assigned to the node */\n  )\n{\n  f = Cudd_Regular (f);\n\n  if (!DddmpVisitedBdd (f)) {\n    return (id);\n  }\n\n  if (!cuddIsConstant (f)) {\n    id = NumberNodeRecurBdd (cuddT (f), id);\n    id = NumberNodeRecurBdd (cuddE (f), id);\n  }\n\n  DddmpWriteNodeIndexBdd (f, ++id);\n  DddmpClearVisitedBdd (f);\n\n  return (id);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Removes a node from unique table]\n\n  Description [Removes a node from the unique table by locating the proper\n    subtable and unlinking the node from it. It recurs on the \n    children of the node. Constants remain untouched.\n    ]\n\n  SideEffects [Nodes are left with the \"visited\" flag true.]\n\n  SeeAlso     [RestoreInUniqueRecurBdd ()]\n\n******************************************************************************/\n\nstatic void\nRemoveFromUniqueRecurBdd (\n  DdManager *ddMgr  /*  IN: DD Manager */,\n  DdNode *f         /*  IN: root of the BDD to be extracted */\n  )\n{\n  DdNode *node, *last, *next;\n  DdNode *sentinel = &(ddMgr->sentinel);\n  DdNodePtr *nodelist;\n  DdSubtable *subtable;\n  int pos, level;\n\n  f = Cudd_Regular (f);\n\n  if (DddmpVisitedBdd (f)) {\n    return;\n  }\n\n  if (!cuddIsConstant (f)) {\n\n    RemoveFromUniqueRecurBdd (ddMgr, cuddT (f));\n    RemoveFromUniqueRecurBdd (ddMgr, cuddE (f));\n\n    level = ddMgr->perm[f->index];\n    subtable = &(ddMgr->subtables[level]);\n\n    nodelist = subtable->nodelist;\n\n    pos = ddHash (cuddT (f), cuddE (f), subtable->shift);\n    node = nodelist[pos];\n    last = NULL;\n    while (node != sentinel) {\n      next = node->next;\n      if (node == f) {\n        if (last != NULL)  \n  \t  last->next = next;\n        else \n          nodelist[pos] = next;\n        break;\n      } else {\n        last = node;\n        node = next;\n      }\n    }\n\n    f->next = NULL;\n\n  }\n\n  DddmpSetVisitedBdd (f);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Restores a node in unique table]\n\n  Description  [Restores a node in unique table (recursively)]\n\n  SideEffects  [Nodes are not restored in the same order as before removal]\n\n  SeeAlso      [RemoveFromUnique()]\n\n******************************************************************************/\n\nstatic void\nRestoreInUniqueRecurBdd (\n  DdManager *ddMgr /*  IN: DD Manager */,\n  DdNode *f        /*  IN: root of the BDD to be restored */\n  )\n{\n  DdNodePtr *nodelist;\n  DdNode *T, *E, *looking;\n  DdNodePtr *previousP;\n  DdSubtable *subtable;\n  int pos, level;\n#ifdef DDDMP_DEBUG\n  DdNode *node;\n  DdNode *sentinel = &(ddMgr->sentinel);\n#endif\n\n  f = Cudd_Regular(f);\n\n  if (!Cudd_IsComplement (f->next)) {\n    return;\n  }\n\n  if (cuddIsConstant (f)) {\n    /* StQ 11.02.2004:\n       Bug fixed --> restore NULL within the next field */\n    /*DddmpClearVisitedBdd (f);*/   \n    f->next = NULL;\n\n    return;\n  }\n\n  RestoreInUniqueRecurBdd (ddMgr, cuddT (f));\n  RestoreInUniqueRecurBdd (ddMgr, cuddE (f));\n\n  level = ddMgr->perm[f->index];\n  subtable = &(ddMgr->subtables[level]);\n\n  nodelist = subtable->nodelist;\n\n  pos = ddHash (cuddT (f), cuddE (f), subtable->shift);\n\n#ifdef DDDMP_DEBUG\n  /* verify uniqueness to avoid duplicate nodes in unique table */\n  for (node=nodelist[pos]; node != sentinel; node=node->next)\n    assert(node!=f);\n#endif\n\n  T = cuddT (f);\n  E = cuddE (f);\n  previousP = &(nodelist[pos]);\n  looking = *previousP;\n\n  while (T < cuddT (looking)) {\n    previousP = &(looking->next);\n    looking = *previousP;\n  }\n\n  while (T == cuddT (looking) && E < cuddE (looking)) {\n    previousP = &(looking->next);\n    looking = *previousP;\n  }\n\n  f->next = *previousP;\n  *previousP = f;\n\n  return;\n}\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpNodeCnf.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpNodeCnf.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to handle BDD node infos and numbering\n    while storing a CNF formula from a BDD or an array of BDDs]\n\n  Description  [Functions to handle BDD node infos and numbering\n    while storing a CNF formula from a BDD or an array of BDDs.\n    ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define DDDMP_DEBUG_CNF 0\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int DddmpWriteNodeIndexCnfWithTerminalCheck(DdNode *f, int *cnfIds, int id);\n#if 0\nstatic int DddmpClearVisitedCnfRecur(DdNode *f);\n#endif\nstatic void DddmpClearVisitedCnf(DdNode *f);\nstatic int NumberNodeRecurCnf(DdNode *f, int *cnfIds, int id);\nstatic void DddmpDdNodesCheckIncomingAndScanPath(DdNode *f, int pathLengthCurrent, int edgeInTh, int pathLengthTh);\nstatic int DddmpDdNodesNumberEdgesRecur(DdNode *f, int *cnfIds, int id);\nstatic int DddmpDdNodesResetCountRecur(DdNode *f);\nstatic int DddmpDdNodesCountEdgesRecur(DdNode *f);\nstatic void RemoveFromUniqueRecurCnf(DdManager *ddMgr, DdNode *f);\nstatic void RestoreInUniqueRecurCnf(DdManager *ddMgr, DdNode *f);\nstatic int DddmpPrintBddAndNextRecur(DdManager *ddMgr, DdNode *f);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [Removes nodes from unique table and numbers them]\n\n  Description [Node numbering is required to convert pointers to integers.\n    Since nodes are removed from unique table, no new nodes should \n    be generated before re-inserting nodes in the unique table\n    (DddmpUnnumberDdNodesCnf()).\n    ]\n\n  SideEffects [Nodes are temporarily removed from unique table]\n\n  SeeAlso     [RemoveFromUniqueRecurCnf(), NumberNodeRecurCnf(), \n    DddmpUnnumberDdNodesCnf()]\n\n******************************************************************************/\n\nint\nDddmpNumberDdNodesCnf (\n  DdManager *ddMgr  /*  IN: DD Manager */,\n  DdNode **f        /*  IN: array of BDDs */,\n  int rootN         /*  IN: number of BDD roots in the array of BDDs */,\n  int *cnfIds       /* OUT: CNF identifiers for variables */,\n  int id            /* OUT: number of Temporary Variables Introduced */\n  )\n{\n  int i;\n\n  for (i=0; i<rootN; i++) {\n    RemoveFromUniqueRecurCnf (ddMgr, f[i]);\n  }\n\n  for (i=0; i<rootN; i++) {\n    id = NumberNodeRecurCnf (f[i], cnfIds, id);\n  }\n\n  return (id);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Removes nodes from unique table and numbers each node according\n    to the number of its incoming BDD edges.\n    ]\n\n  Description [Removes nodes from unique table and numbers each node according\n    to the number of its incoming BDD edges.\n    ]\n\n  SideEffects [Nodes are temporarily removed from unique table]\n\n  SeeAlso     [RemoveFromUniqueRecurCnf()]\n\n******************************************************************************/\n\nint\nDddmpDdNodesCountEdgesAndNumber (\n  DdManager *ddMgr    /*  IN: DD Manager */,\n  DdNode **f          /*  IN: Array of BDDs */,\n  int rootN           /*  IN: Number of BDD roots in the array of BDDs */,\n  int edgeInTh        /*  IN: Max # In-Edges, after a Insert Cut Point */,\n  int pathLengthTh    /*  IN: Max Path Length (after, Insert a Cut Point) */,\n  int *cnfIds         /* OUT: CNF identifiers for variables */,\n  int id              /* OUT: Number of Temporary Variables Introduced */\n  )\n{\n  int i;\n\n  /*-------------------------- Remove From Unique ---------------------------*/\n\n  for (i=0; i<rootN; i++) {\n    RemoveFromUniqueRecurCnf (ddMgr, f[i]);\n  }\n\n  /*-------------------- Reset Counter and Reset Visited --------------------*/\n\n  for (i=0; i<rootN; i++) {\n    (void) DddmpDdNodesResetCountRecur (f[i]);\n  }\n\n  /*  Here we must have:\n   *    cnfIndex = 0\n   *    visitedFlag = 0\n   *  FOR ALL nodes\n   */\n\n#if DDDMP_DEBUG_CNF\n  fprintf (stdout, \"###---> BDDs After Count Reset:\\n\");\n  DddmpPrintBddAndNext (ddMgr, f, rootN);\n#endif\n\n  /*----------------------- Count Incoming Edges ----------------------------*/\n\n  for (i=0; i<rootN; i++) {\n    (void) DddmpDdNodesCountEdgesRecur (f[i]);\n  }\n\n  /*  Here we must have:\n   *    cnfIndex = incoming edge count\n   *    visitedFlag = 0 (AGAIN ... remains untouched)\n   *  FOR ALL nodes\n   */\n\n#if DDDMP_DEBUG_CNF\n  fprintf (stdout, \"###---> BDDs After Count Recur:\\n\");\n  DddmpPrintBddAndNext (ddMgr, f, rootN);\n#endif\n\n  /*------------------------- Count Path Length ----------------------------*/\n     \n  for (i=0; i<rootN; i++) {\n    DddmpDdNodesCheckIncomingAndScanPath (f[i], 0, edgeInTh,\n      pathLengthTh);\n  }\n\n  /* Here we must have:\n   *   cnfIndex = 1 if we want to insert there a cut point\n   *              0 if we do NOT want to insert there a cut point\n   *    visitedFlag = 1\n   *  FOR ALL nodes\n   */\n\n#if DDDMP_DEBUG_CNF\n  fprintf (stdout, \"###---> BDDs After Check Incoming And Scan Path:\\n\");\n  DddmpPrintBddAndNext (ddMgr, f, rootN);\n#endif\n\n  /*-------------------- Number Nodes and Set Visited -----------------------*/\n\n  for (i=0; i<rootN; i++) {\n    id = DddmpDdNodesNumberEdgesRecur (f[i], cnfIds, id);\n  }\n\n  /*  Here we must have:\n   *    cnfIndex = CNF auxiliary variable enumeration\n   *    visitedFlag = 0\n   *  FOR ALL nodes\n   */\n\n#if DDDMP_DEBUG_CNF\n  fprintf (stdout, \"###---> BDDs After Count Edges Recur:\\n\");\n  DddmpPrintBddAndNext (ddMgr, f, rootN);\n#endif\n\n  return (id);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Restores nodes in unique table, loosing numbering]\n\n  Description  [Node indexes are no more needed. Nodes are re-linked in the\n    unique table.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpNumberDdNode()]\n\n******************************************************************************/\n\nvoid\nDddmpUnnumberDdNodesCnf(\n  DdManager *ddMgr   /* IN: DD Manager */,\n  DdNode **f         /* IN: array of BDDs */,\n  int rootN           /* IN: number of BDD roots in the array of BDDs */\n  )\n{\n  int i;\n\n  for (i=0; i<rootN; i++) {\n    RestoreInUniqueRecurCnf (ddMgr, f[i]);\n  }\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Prints debug information]\n\n  Description  [Prints debug information for an array of BDDs on the screen]\n\n  SideEffects  [None]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nint\nDddmpPrintBddAndNext (\n  DdManager *ddMgr   /* IN: DD Manager */,\n  DdNode **f         /* IN: Array of BDDs to be displayed */,\n  int rootN          /* IN: Number of BDD roots in the array of BDDs */\n  )\n{\n  int i;\n\n  for (i=0; i<rootN; i++) {\n    fprintf (stdout, \"---> Bdd %d:\\n\", i);\n    fflush (stdout);\n    DddmpPrintBddAndNextRecur (ddMgr, f[i]);\n  }\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Write index to node]\n\n  Description  [The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpReadNodeIndexCnf(), DddmpSetVisitedCnf (),\n    DddmpVisitedCnf ()\n    ]\n\n******************************************************************************/\n\nint\nDddmpWriteNodeIndexCnf (\n  DdNode *f   /* IN: BDD node */,\n  int id      /* IN: index to be written */\n  )\n{\n  if (!Cudd_IsConstant (f)) {\n    f->next = (struct DdNode *)((ptruint)id<<1);\n  }\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Returns true if node is visited]\n\n  Description  [Returns true if node is visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpSetVisitedCnf (), DddmpClearVisitedCnf ()]\n\n******************************************************************************/\n\nint\nDddmpVisitedCnf (\n  DdNode *f      /* IN: BDD node to be tested */\n  )\n{\n  f = Cudd_Regular(f);\n\n  return ((int)((ptruint)(f->next)) & (01));\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Marks a node as visited]\n \n  Description  [Marks a node as visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpVisitedCnf (), DddmpClearVisitedCnf ()]\n\n******************************************************************************/\n\nvoid\nDddmpSetVisitedCnf (\n  DdNode *f     /* IN: BDD node to be marked (as visited) */\n  )\n{\n  f = Cudd_Regular(f);\n\n  f->next = (DdNode *)(ptruint)((int)((ptruint)(f->next))|01);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Reads the index of a node]\n\n  Description  [Reads the index of a node. LSB is skipped (used as visited\n    flag).\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpWriteNodeIndexCnf(), DddmpSetVisitedCnf (),\n    DddmpVisitedCnf ()]\n\n******************************************************************************/\n\nint\nDddmpReadNodeIndexCnf (\n  DdNode *f     /* IN: BDD node */\n  )\n{\n  if (!Cudd_IsConstant (f)) {\n    return ((int)(((ptruint)(f->next))>>1));\n  } else {\n    return (1);\n  }\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Write index to node]\n\n  Description  [The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals. The index corresponds to \n    the BDD node variable if both the node's children are a \n    constant node, otherwise a new CNF variable is used. \n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpReadNodeIndexCnf(), DddmpSetVisitedCnf (),\n    DddmpVisitedCnf ()]\n\n*****************************************************************************/\n\nstatic int\nDddmpWriteNodeIndexCnfWithTerminalCheck (\n  DdNode *f    /* IN: BDD node */,\n  int *cnfIds  /* IN: possible source for the index to be written */,\n  int id       /* IN: possible source for the index to be written */\n  )\n{\n  if (!Cudd_IsConstant (f)) {\n    if (Cudd_IsConstant (cuddT (f)) && Cudd_IsConstant (cuddE (f))) {\n      /* If Variable SET ID as Variable ID */\n      f->next = (struct DdNode *)((ptruint)cnfIds[f->index]<<1);\n    } else {\n      f->next = (struct DdNode *)((ptruint)id<<1);\n      id++;\n    }\n  }\n\n  return(id);\n}\n\n#if 0\n/**Function********************************************************************\n\n  Synopsis     [Mark ALL nodes as not visited]\n\n  Description  [Mark ALL nodes as not visited (it recurs on the node children)]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpVisitedCnf (), DddmpSetVisitedCnf ()]\n\n******************************************************************************/\n\nstatic int\nDddmpClearVisitedCnfRecur (\n  DdNode *f     /* IN: root of the BDD to be marked */\n  )\n{\n  f = Cudd_Regular(f);\n\n  if (cuddIsConstant (f)) {\n    return (DDDMP_SUCCESS);\n  }\n\n  if (!DddmpVisitedCnf (f)) {\n    return (DDDMP_SUCCESS);\n  }\n\n  (void) DddmpClearVisitedCnfRecur (cuddT (f));\n  (void) DddmpClearVisitedCnfRecur (cuddE (f));\n\n  DddmpClearVisitedCnf (f);\n\n  return (DDDMP_SUCCESS);\n}\n#endif\n\n/**Function********************************************************************\n\n  Synopsis     [Marks a node as not visited]\n\n  Description  [Marks a node as not visited]\n\n  SideEffects  [None]\n\n  SeeAlso      [DddmpVisitedCnf (), DddmpSetVisitedCnf ()]\n\n******************************************************************************/\n\nstatic void\nDddmpClearVisitedCnf (\n  DdNode *f     /* IN: BDD node to be marked (as not visited) */\n  )\n{\n  f = Cudd_Regular (f);\n\n  f->next = (DdNode *)(ptruint)((int)((ptruint)(f->next)) & (~01));\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Number nodes recursively in post-order]\n\n  Description  [Number nodes recursively in post-order.\n    The \"visited\" flag is used with inverse polarity, because all nodes\n    were set \"visited\" when removing them from unique. \n    ]\n\n  SideEffects  [\"visited\" flags are reset.]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nNumberNodeRecurCnf(\n  DdNode *f        /*  IN: root of the BDD to be numbered */,\n  int *cnfIds      /*  IN: possible source for numbering */,\n  int id        /* IN/OUT: possible source for numbering */\n  )\n{\n  f = Cudd_Regular(f);\n\n  if (!DddmpVisitedCnf (f)) {\n    return (id);\n  }\n\n  if (!cuddIsConstant (f)) {\n    id = NumberNodeRecurCnf (cuddT (f), cnfIds, id);\n    id = NumberNodeRecurCnf (cuddE (f), cnfIds, id);\n  }\n\n  id = DddmpWriteNodeIndexCnfWithTerminalCheck (f, cnfIds, id);\n  DddmpClearVisitedCnf (f);\n\n  return (id);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Number nodes recursively in post-order]\n\n  Description  [Number nodes recursively in post-order.\n    The \"visited\" flag is used with the right polarity.\n    The node is assigned to a new CNF variable only if it is a \"shared\"\n    node (i.e. the number of its incoming edges is greater than 1). \n    ]\n\n  SideEffects  [\"visited\" flags are set.]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic void\nDddmpDdNodesCheckIncomingAndScanPath (\n  DdNode *f             /* IN: BDD node to be numbered */,\n  int pathLengthCurrent /* IN: Current Path Length */,\n  int edgeInTh          /* IN: Max # In-Edges, after a Insert Cut Point */,\n  int pathLengthTh      /* IN: Max Path Length (after, Insert a Cut Point) */\n  )\n{\n  int retValue;\n\n  f = Cudd_Regular(f);\n\n  if (DddmpVisitedCnf (f)) {\n    return;\n  }\n\n  if (cuddIsConstant (f)) {\n    return;\n  }\n\n  pathLengthCurrent++;\n  retValue = DddmpReadNodeIndexCnf (f);\n\n  if ( ((edgeInTh >= 0) && (retValue > edgeInTh)) ||\n       ((pathLengthTh >= 0) && (pathLengthCurrent > pathLengthTh))\n     ) {\n    DddmpWriteNodeIndexCnf (f, 1);\n    pathLengthCurrent = 0;\n  } else {\n    DddmpWriteNodeIndexCnf (f, 0);\n  }\n\n  DddmpDdNodesCheckIncomingAndScanPath (cuddT (f), pathLengthCurrent,\n    edgeInTh, pathLengthTh);\n  DddmpDdNodesCheckIncomingAndScanPath (cuddE (f), pathLengthCurrent,\n    edgeInTh, pathLengthTh);\n\n  DddmpSetVisitedCnf (f);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Number nodes recursively in post-order]\n\n  Description  [Number nodes recursively in post-order.\n    The \"visited\" flag is used with the inverse polarity.\n    Numbering follows the subsequent strategy:\n    * if the index = 0 it remains so\n    * if the index >= 1 it gets enumerated.\n      This implies that the node is assigned to a new CNF variable only if\n      it is not a terminal node otherwise it is assigned the index of\n      the BDD variable.\n    ]\n\n  SideEffects  [\"visited\" flags are reset.]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nDddmpDdNodesNumberEdgesRecur (\n  DdNode *f      /*  IN: BDD node to be numbered */,\n  int *cnfIds    /*  IN: possible source for numbering */,\n  int id      /* IN/OUT: possible source for numbering */\n  )\n{\n  int retValue;\n\n  f = Cudd_Regular(f);\n\n  if (!DddmpVisitedCnf (f)) {\n    return (id);\n  }\n\n  if (cuddIsConstant (f)) {\n    return (id);\n  }\n\n  id = DddmpDdNodesNumberEdgesRecur (cuddT (f), cnfIds, id);\n  id = DddmpDdNodesNumberEdgesRecur (cuddE (f), cnfIds, id);\n\n  retValue = DddmpReadNodeIndexCnf (f);\n  if (retValue >= 1) {\n    id = DddmpWriteNodeIndexCnfWithTerminalCheck (f, cnfIds, id);\n  } else {\n    DddmpWriteNodeIndexCnf (f, 0);\n  }\n\n  DddmpClearVisitedCnf (f);\n\n  return (id);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Resets counter and visited flag for ALL nodes of a BDD]\n\n  Description  [Resets counter and visited flag for ALL nodes of a BDD (it \n    recurs on the node children). The index field of the node is \n    used as counter.\n    ]\n\n  SideEffects  []\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nDddmpDdNodesResetCountRecur (\n  DdNode *f  /*  IN: root of the BDD whose counters are reset */\n  )\n{\n  f = Cudd_Regular (f);\n\n  if (!DddmpVisitedCnf (f)) {\n    return (DDDMP_SUCCESS);\n  }\n\n  if (!cuddIsConstant (f)) {\n    (void) DddmpDdNodesResetCountRecur (cuddT (f));\n    (void) DddmpDdNodesResetCountRecur (cuddE (f));\n  }\n\n  DddmpWriteNodeIndexCnf (f, 0);\n  DddmpClearVisitedCnf (f);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Counts the number of incoming edges for each node of a BDD]\n\n  Description  [Counts (recursively) the number of incoming edges for each \n    node of a BDD. This number is stored in the index field.\n    ]\n\n  SideEffects  [\"visited\" flags remain untouched.]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nDddmpDdNodesCountEdgesRecur (\n  DdNode *f    /* IN: root of the BDD */\n  )\n{\n  int indexValue;\n\n  f = Cudd_Regular (f);\n\n  if (cuddIsConstant (f)) {\n    return (DDDMP_SUCCESS);\n  }\n\n  if (Cudd_IsConstant (cuddT (f)) && Cudd_IsConstant (cuddE (f))) {\n    return (DDDMP_SUCCESS);\n  }\n\n  indexValue = DddmpReadNodeIndexCnf (f);\n\n  /* IF (first time) THEN recur */\n  if (indexValue == 0) {\n    (void) DddmpDdNodesCountEdgesRecur (cuddT (f));\n    (void) DddmpDdNodesCountEdgesRecur (cuddE (f));\n  }\n\n  /* Increment Incoming-Edge Count Flag */\n  indexValue++;\n  DddmpWriteNodeIndexCnf (f, indexValue);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Removes a node from unique table]\n\n  Description [Removes a node from the unique table by locating the proper\n    subtable and unlinking the node from it. It recurs on  on the \n    children of the node. Constants remain untouched.\n    ]\n\n  SideEffects [Nodes are left with the \"visited\" flag true.]\n\n  SeeAlso     [RestoreInUniqueRecurCnf()]\n\n******************************************************************************/\n\nstatic void\nRemoveFromUniqueRecurCnf (\n  DdManager *ddMgr  /*  IN: DD Manager */,\n  DdNode *f         /*  IN: root of the BDD to be extracted */\n  )\n{\n  DdNode *node, *last, *next;\n  DdNode *sentinel = &(ddMgr->sentinel);\n  DdNodePtr *nodelist;\n  DdSubtable *subtable;\n  int pos, level;\n\n  f = Cudd_Regular (f);\n\n  if (DddmpVisitedCnf (f)) {\n    return;\n  }\n\n  if (!cuddIsConstant (f)) {\n\n    RemoveFromUniqueRecurCnf (ddMgr, cuddT (f));\n    RemoveFromUniqueRecurCnf (ddMgr, cuddE (f));\n\n    level = ddMgr->perm[f->index];\n    subtable = &(ddMgr->subtables[level]);\n\n    nodelist = subtable->nodelist;\n\n    pos = ddHash (cuddT (f), cuddE (f), subtable->shift);\n    node = nodelist[pos];\n    last = NULL;\n    while (node != sentinel) {\n      next = node->next;\n      if (node == f) {\n        if (last != NULL)  \n  \t  last->next = next;\n        else \n          nodelist[pos] = next;\n        break;\n      } else {\n        last = node;\n        node = next;\n      }\n    }\n\n    f->next = NULL;\n\n  }\n\n  DddmpSetVisitedCnf (f);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Restores a node in unique table]\n\n  Description  [Restores a node in unique table (recursive)]\n\n  SideEffects  [Nodes are not restored in the same order as before removal]\n\n  SeeAlso      [RemoveFromUnique()]\n\n******************************************************************************/\n\nstatic void\nRestoreInUniqueRecurCnf (\n  DdManager *ddMgr  /*  IN: DD Manager */,\n  DdNode *f         /*  IN: root of the BDD to be restored */\n  )\n{\n  DdNodePtr *nodelist;\n  DdNode *T, *E, *looking;\n  DdNodePtr *previousP;\n  DdSubtable *subtable;\n  int pos, level;\n#ifdef DDDMP_DEBUG\n  DdNode *node;\n  DdNode *sentinel = &(ddMgr->sentinel);\n#endif\n\n  f = Cudd_Regular(f);\n\n  if (!Cudd_IsComplement (f->next)) {\n    return;\n  }\n\n  if (cuddIsConstant (f)) {\n    /* StQ 11.02.2004:\n       Bug fixed --> restore NULL within the next field */\n    /*DddmpClearVisitedCnf (f);*/\n    f->next = NULL;\n\n    return;\n  }\n\n  RestoreInUniqueRecurCnf (ddMgr, cuddT (f));\n  RestoreInUniqueRecurCnf (ddMgr, cuddE (f));\n\n  level = ddMgr->perm[f->index];\n  subtable = &(ddMgr->subtables[level]);\n\n  nodelist = subtable->nodelist;\n\n  pos = ddHash (cuddT (f), cuddE (f), subtable->shift);\n\n#ifdef DDDMP_DEBUG\n  /* verify uniqueness to avoid duplicate nodes in unique table */\n  for (node=nodelist[pos]; node != sentinel; node=node->next)\n    assert(node!=f);\n#endif\n\n  T = cuddT (f);\n  E = cuddE (f);\n  previousP = &(nodelist[pos]);\n  looking = *previousP;\n\n  while (T < cuddT (looking)) {\n    previousP = &(looking->next);\n    looking = *previousP;\n  }\n\n  while (T == cuddT (looking) && E < cuddE (looking)) {\n    previousP = &(looking->next);\n    looking = *previousP;\n  }\n  f->next = *previousP;\n  *previousP = f;\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Prints debug info]\n\n  Description  [Prints debug info for a BDD on the screen. It recurs on \n    node's children.\n    ]\n\n  SideEffects  []\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nDddmpPrintBddAndNextRecur (\n  DdManager *ddMgr   /* IN: DD Manager */,\n  DdNode *f          /* IN: root of the BDD to be displayed */\n  )\n{\n  DdNode *fPtr, *tPtr, *ePtr;\n\n  fPtr = Cudd_Regular (f);\n\n  if (Cudd_IsComplement (f)) {\n    fprintf (stdout, \"sign=- ptr=%\" PRIiPTR \" \", ((ptrint) fPtr));\n  } else {\n    fprintf (stdout, \"sign=+ ptr=%\" PRIiPTR \" \", ((ptrint) fPtr));\n  }\n\n  if (cuddIsConstant (fPtr)) {\n    fprintf (stdout, \"one\\n\");\n    fflush (stdout);\n    return (DDDMP_SUCCESS);\n  }\n\n  fprintf (stdout,\n    \"thenPtr=%\" PRIiPTR \" elsePtr=%\" PRIiPTR \" BddId=%d CnfId=%d Visited=%d\\n\",\n    ((ptrint) cuddT (fPtr)), ((ptrint) cuddE (fPtr)),\n    fPtr->index, DddmpReadNodeIndexCnf (fPtr),\n    DddmpVisitedCnf (fPtr));\n  \n  tPtr  = cuddT (fPtr);\n  ePtr = cuddE (fPtr);\n  if (Cudd_IsComplement (f)) {\n    tPtr  = Cudd_Not (tPtr);\n    ePtr = Cudd_Not (ePtr);\n  }\n\n  (void) DddmpPrintBddAndNextRecur (ddMgr, tPtr);\n  (void) DddmpPrintBddAndNextRecur (ddMgr, ePtr);\n\n  return (DDDMP_SUCCESS);\n}\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpStoreAdd.c",
    "content": "/**CFile**********************************************************************\n  FileName     [dddmpStoreAdd.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to write ADDs to file.]\n\n  Description  [Functions to write ADDs to file.\n    ADDs are represended on file either in text or binary format under the\n    following rules.  A file contains a forest of ADDs (a vector of\n    Boolean functions).  ADD nodes are numbered with contiguous numbers,\n    from 1 to NNodes (total number of nodes on a file). 0 is not used to\n    allow negative node indexes for complemented edges.  A file contains\n    a header, including information about variables and roots to ADD\n    functions, followed by the list of nodes.\n    ADD nodes are listed according to their numbering, and in the present\n    implementation numbering follows a post-order strategy, in such a way\n    that a node is never listed before its Then/Else children.\n  ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int NodeStoreRecurAdd(DdManager *ddMgr, DdNode *f, int mode, int *supportids, char **varnames, int *outids, FILE *fp);\nstatic int NodeTextStoreAdd(DdManager *ddMgr, DdNode *f, int mode, int *supportids, char **varnames, int *outids, FILE *fp, int idf, int vf, int idT, int idE);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument ADD.]\n\n  Description  [Dumps the argument ADD to file. Dumping is done through\n    Dddmp_cuddAddArrayStore, And a dummy array of 1 ADD root is\n    used for this purpose.\n    ]\n\n  SideEffects  [Nodes are temporarily removed from unique hash. They are \n    re-linked after the store operation in a modified order.]\n\n  SeeAlso      [Dddmp_cuddAddLoad Dddmp_cuddAddArrayLoad]\n\n******************************************************************************/\n\nint\nDddmp_cuddAddStore (\n  DdManager *ddMgr          /* IN: DD Manager */,\n  char *ddname              /* IN: DD name (or NULL) */,\n  DdNode *f                 /* IN: ADD root to be stored */,\n  char **varnames           /* IN: array of variable names (or NULL) */,\n  int *auxids               /* IN: array of converted var ids */,\n  int mode                  /* IN: storing mode selector */,\n  Dddmp_VarInfoType varinfo /* IN: extra info for variables in text mode */,\n  char *fname               /* IN: File name */,\n  FILE *fp                  /* IN: File pointer to the store file */ \n  )\n{\n  int retValue;\n  DdNode *tmpArray[1];\n\n  tmpArray[0] = f;\n  retValue = Dddmp_cuddAddArrayStore (ddMgr, ddname, 1, tmpArray, NULL,\n    varnames, auxids, mode, varinfo, fname, fp);\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Writes a dump file representing the argument Array of ADDs.]\n\n  Description [Dumps the argument array of ADDs to file. Dumping is\n    either in text or binary form. see the corresponding BDD dump \n    function for further details.\n    ]\n\n  SideEffects [Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n    ]\n\n  SeeAlso     [Dddmp_cuddAddStore, Dddmp_cuddAddLoad,\n    Dddmp_cuddAddArrayLoad]\n\n******************************************************************************/\n\nint\nDddmp_cuddAddArrayStore (\n  DdManager *ddMgr          /* IN: DD Manager */,\n  char *ddname              /* IN: DD name (or NULL) */,\n  int nRoots                /* IN: number of output BDD roots to be stored */,\n  DdNode **f                /* IN: array of ADD roots to be stored */,\n  char **rootnames          /* IN: array of root names (or NULL) */,\n  char **varnames           /* IN: array of variable names (or NULL) */,\n  int *auxids               /* IN: array of converted var IDs */,\n  int mode                  /* IN: storing mode selector */,\n  Dddmp_VarInfoType varinfo /* IN: extra info for variables in text mode */,\n  char *fname               /* IN: File name */,\n  FILE *fp                  /* IN: File pointer to the store file */ \n  )\n{\n  int retValue;\n\n#if 0\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValueBis;\n\n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During ADD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During ADD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n#endif\n\n  retValue = DddmpCuddDdArrayStoreBdd (DDDMP_ADD, ddMgr, ddname, nRoots, f,\n    rootnames, varnames, auxids, mode, varinfo, fname, fp);\n\n#if 0\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During ADD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During ADD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n#endif\n\n  return (retValue);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument Array of\n    BDDs/ADDs.\n    ]\n\n  Description  [Dumps the argument array of BDDs/ADDs to file. Internal \n    function doing inner steps of store for BDDs and ADDs.\n    ADD store is presently supported only with the text format.\n    ]\n\n  SideEffects  [Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n    ]\t\n\t\n  SeeAlso      [Dddmp_cuddBddStore, Dddmp_cuddBddLoad,\n    Dddmp_cuddBddArrayLoad\n    ]\n\n******************************************************************************/\n\nint\nDddmpCuddDdArrayStoreBdd (\n  Dddmp_DecompType ddType   /* IN: Selects the decomp type: BDD or ADD */,\n  DdManager *ddMgr          /* IN: DD Manager */,\n  char *ddname              /* IN: DD name (or NULL) */,\n  int nRoots                /* IN: number of output BDD roots to be stored */,\n  DdNode **f                /* IN: array of DD roots to be stored */,\n  char **rootnames          /* IN: array of root names (or NULL) */,\n  char **varnames           /* IN: array of variable names (or NULL) */,\n  int *auxids               /* IN: array of converted var IDs */,\n  int mode                  /* IN: storing mode selector */,\n  Dddmp_VarInfoType varinfo /* IN: extra info for variables in text mode */,\n  char *fname               /* IN: File name */,\n  FILE *fp                  /* IN: File pointer to the store file */ \n  )\n{\n  DdNode *support = NULL;\n  DdNode *scan;\n  int *ids = NULL;\n  int *permids = NULL;\n  int *invpermids = NULL;\n  int *supportids = NULL;\n  int *outids = NULL;\n  char **outvarnames = NULL;\n  int nVars = ddMgr->size;\n  int nnodes;\n  int retValue;\n  int i, var;\n  int fileToClose = 0;\n\n  /* \n   *  Check DD Type and Mode\n   */\n\n  Dddmp_CheckAndGotoLabel (ddType==DDDMP_BDD,\n    \"Error writing to file: BDD Type.\", failure);\n  Dddmp_CheckAndGotoLabel (mode==DDDMP_MODE_BINARY,\n    \"Error writing to file: ADD Type with Binary Mode.\", failure);\n\n  /* \n   *  Check if File needs to be opened in the proper mode.\n   */\n\n  if (fp == NULL) {\n    fp = fopen (fname, \"w\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  /* \n   *  Force binary mode if automatic.\n   */\n\n  switch (mode) {\n    case DDDMP_MODE_TEXT:\n    case DDDMP_MODE_BINARY:\n      break;\n    case DDDMP_MODE_DEFAULT:\n      mode = DDDMP_MODE_BINARY;\n      break;\n    default:\n      mode = DDDMP_MODE_BINARY;\n      break;\n  }\n\n  /* \n   * Alloc vectors for variable IDs, perm IDs and support IDs.\n   *  +1 to include a slot for terminals.\n   */\n\n  ids = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndGotoLabel (ids==NULL, \"Error allocating memory.\", failure);\n  permids = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndGotoLabel (permids==NULL, \"Error allocating memory.\", failure);\n  invpermids = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndGotoLabel (invpermids==NULL, \"Error allocating memory.\",\n    failure);\n  supportids = DDDMP_ALLOC (int, nVars+1);\n  Dddmp_CheckAndGotoLabel (supportids==NULL, \"Error allocating memory.\",\n    failure);\n    \n  for (i=0; i<nVars; i++) {\n    ids[i] = permids[i] = invpermids[i] = supportids[i] = (-1);\n  }\n  /* StQ */\n  supportids[nVars] = -1;\n  \n  /* \n   *  Take the union of the supports of each output function.\n   *  skip NULL functions.\n   *  Set permids and invpermids of support variables to the proper values.\n   */\n\n  for (i=0; i<nRoots; i++) {\n    if (f[i] == NULL) {\n      continue;\n    }\n    support = Cudd_Support (ddMgr, f[i]);\n    Dddmp_CheckAndGotoLabel (support==NULL, \"NULL support returned.\",\n      failure);\n    cuddRef (support);\n    scan = support;\n    while (!cuddIsConstant(scan)) {\n      ids[scan->index] = scan->index;\n      permids[scan->index] = ddMgr->perm[scan->index];\n      invpermids[ddMgr->perm[scan->index]] = scan->index;\n      scan = cuddT (scan);\n    }\n    Cudd_RecursiveDeref (ddMgr, support);\n  }\n  /* so that we do not try to free it in case of failure */\n  support = NULL;\n\n  /*\n   *  Set supportids to incremental (shrinked) values following the ordering.\n   */\n\n  for (i=0, var=0; i<nVars; i++) {\n    if (invpermids[i] >= 0) {\n      supportids[invpermids[i]] = var++;\n    }\n  }\n  /* set a dummy id for terminal nodes */\n  supportids[nVars] = var;\n\n  /*\n   *  Select conversion array for extra var info\n   */\n\n  switch (mode) {\n    case DDDMP_MODE_TEXT:\n      switch (varinfo) {\n        case DDDMP_VARIDS:\n          outids = ids;\n          break;\n        case DDDMP_VARPERMIDS:\n          outids = permids;\n          break;\n        case DDDMP_VARAUXIDS:\n          outids = auxids;\n          break;\n        case DDDMP_VARNAMES:\n          outvarnames = varnames;\n          break;\n        case DDDMP_VARDEFAULT:\n          break;\n      }\n      break;\n    case DDDMP_MODE_BINARY:\n      outids = NULL;\n      break;\n  }\n\n  /* \n   *  Number dd nodes and count them (numbering is from 1 to nnodes)\n   */\n\n  nnodes = DddmpNumberAddNodes (ddMgr, f, nRoots);\n\n  /* \n   * Start Header\n   */\n\n#ifdef DDDMP_VERSION\n  retValue = fprintf (fp, \".ver %s\\n\", DDDMP_VERSION);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n#endif\n\n  retValue = fprintf (fp, \".add\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  retValue = fprintf (fp, \".mode %c\\n\", mode);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  if (mode == DDDMP_MODE_TEXT) {\n    retValue = fprintf (fp, \".varinfo %d\\n\", varinfo);\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  if (ddname != NULL) {\n    retValue = fprintf (fp, \".dd %s\\n\",ddname);\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  retValue = fprintf (fp, \".nnodes %d\\n\", nnodes);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  retValue = fprintf (fp, \".nvars %d\\n\", nVars);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  retValue = fprintf (fp, \".nsuppvars %d\\n\", var);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  /*------------  Write the Var Names by scanning the ids array -------------*/\n\n  if (varnames != NULL) {\n\n    retValue = fprintf (fp, \".suppvarnames\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n\n    for (i=0; i<nVars; i++) {\n      if (ids[i] >= 0) {\n        if (varnames[ids[i]] == NULL) {\n          (void) fprintf (stderr,\n             \"DdStore Warning: null variable name. DUMMY%d generated\\n\", i);\n          fflush (stderr);\n          varnames[ids[i]] = DDDMP_ALLOC (char, 10);\n          Dddmp_CheckAndGotoLabel (varnames[ids[i]] == NULL,\n            \"Error allocating memory.\", failure);\n          sprintf (varnames[ids[i]], \"DUMMY%d\", i);\n        }\n        retValue = fprintf (fp, \" %s\", varnames[ids[i]]);\n        Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n          failure);\n      }\n    }\n\n    retValue = fprintf (fp, \"\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  /*--------- Write the Var SUPPORT Names by scanning the ids array ---------*/\n\n  if (varnames != NULL) {\n    retValue = fprintf (fp, \".orderedvarnames\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n\n    for (i=0; i<nVars; i++) {\n      if (varnames[ddMgr->invperm[i]] == NULL) {\n          (void) fprintf (stderr,\n           \"DdStore Warning: null variable name. DUMMY%d generated\\n\", i);\n        fflush (stderr);\n        varnames[ddMgr->invperm[i]] = DDDMP_ALLOC (char, 10);\n        Dddmp_CheckAndGotoLabel (varnames[ddMgr->invperm[i]] == NULL,\n          \"Error allocating memory.\", failure);\n        sprintf (varnames[ddMgr->invperm[i]], \"DUMMY%d\", i);\n      }\n\n      retValue = fprintf (fp, \" %s\", varnames[ddMgr->invperm[i]]);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n        failure);\n    }\n\n    retValue = fprintf (fp, \"\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  /*------------ Write the var ids by scanning the ids array ---------------*/\n\n  retValue = fprintf (fp, \".ids\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  for (i=0; i<nVars; i++) {\n    if (ids[i] >= 0) {\n      retValue = fprintf (fp, \" %d\", i);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n        failure);\n    }\n  }\n  retValue = fprintf (fp, \"\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  /*\n   *  Write the var permids by scanning the permids array. \n   */\n\n  retValue = fprintf (fp, \".permids\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n  for (i = 0; i < nVars; i++) {\n    if (permids[i] >= 0) {\n      retValue = fprintf (fp, \" %d\", permids[i]);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n        failure);\n    }\n  }\n\n  retValue = fprintf (fp, \"\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  if (auxids != NULL) {\n  \n    /*\n     * Write the var auxids by scanning the ids array. \n     */\n\n    retValue = fprintf (fp, \".auxids\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n    for (i = 0; i < nVars; i++) {\n      if (ids[i] >= 0) {\n        retValue = fprintf (fp, \" %d\", auxids[i]);\n        Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n          failure);\n      }\n    }\n    retValue = fprintf (fp, \"\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  /* \n   * Write the roots info. \n   */\n\n  retValue = fprintf (fp, \".nroots %d\\n\", nRoots);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  if (rootnames != NULL) {\n\n    /* \n     * Write the root names. \n     */\n\n    retValue = fprintf (fp, \".rootnames\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n\n    for (i = 0; i < nRoots; i++) {\n      if (rootnames[i] == NULL) {\n        (void) fprintf (stderr,\n          \"DdStore Warning: null variable name. ROOT%d generated\\n\",i);\n        fflush (stderr);\n        rootnames[i] = DDDMP_ALLOC(char,10);\n        Dddmp_CheckAndGotoLabel (rootnames[i]==NULL,\n          \"Error writing to file.\", failure);\n        sprintf(rootnames[ids[i]], \"ROOT%d\",i);\n      }\n      retValue = fprintf (fp, \" %s\", rootnames[i]);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n        failure);\n    }\n\n    retValue = fprintf (fp, \"\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  retValue = fprintf (fp, \".rootids\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  /* \n   * Write BDD indexes of function roots.\n   * Use negative integers for complemented edges. \n   */\n\n  for (i = 0; i < nRoots; i++) {\n    if (f[i] == NULL) {\n      (void) fprintf (stderr, \"DdStore Warning: %d-th root is NULL\\n\",i);\n      fflush (stderr);\n      retValue = fprintf (fp, \" 0\");\n    }\n    if (Cudd_IsComplement(f[i])) {\n      retValue = fprintf (fp, \" -%d\",\n        DddmpReadNodeIndexAdd (Cudd_Regular (f[i])));\n    } else {\n      retValue = fprintf (fp, \" %d\",\n        DddmpReadNodeIndexAdd (Cudd_Regular (f[i])));\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  retValue = fprintf (fp, \"\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  retValue = fprintf (fp, \".nodes\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  /* \n   *  END HEADER\n   */\n\n  /* \n   *  Call the function that really gets the job done.\n   */\n\n  for (i = 0; i < nRoots; i++) {\n    if (f[i] != NULL) {\n      retValue = NodeStoreRecurAdd (ddMgr, Cudd_Regular(f[i]),\n        mode, supportids, outvarnames, outids, fp);\n      Dddmp_CheckAndGotoLabel (retValue==DDDMP_FAILURE,\n        \"Error writing to file.\", failure);\n    }\n  }\n\n  /* \n   *  Write trailer and return.\n   */\n\n  retValue = fprintf (fp, \".end\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n  DddmpUnnumberAddNodes (ddMgr, f, nRoots);\n  DDDMP_FREE (ids);\n  DDDMP_FREE (permids);\n  DDDMP_FREE (invpermids);\n  DDDMP_FREE (supportids);\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n\n    if (ids != NULL) {\n      DDDMP_FREE (ids);\n    }\n    if (permids != NULL) {\n      DDDMP_FREE (permids);\n    }\n    if (invpermids != NULL) {\n      DDDMP_FREE (invpermids);\n    }\n    if (supportids != NULL) {\n      DDDMP_FREE (supportids);\n    }\n    if (support != NULL) {\n      Cudd_RecursiveDeref (ddMgr, support);\n    }\n    \n    return (DDDMP_FAILURE);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Performs the recursive step of Dddmp_bddStore.]\n\n  Description  [Stores a node to file in either test or binary mode.<l>\n    In text mode a node is represented (on a text line basis) as\n    <UL>\n    <LI> node-index \\[var-extrainfo\\] var-index Then-index Else-index\n    </UL>\n    \n    where all indexes are integer numbers and var-extrainfo \n    (optional redundant field) is either an integer or a string \n    (variable name). Node-index is redundant (due to the node \n    ordering) but we keep it for readability.<p>\n    \n    In binary mode nodes are represented as a sequence of bytes,\n    representing var-index, Then-index, and Else-index in an \n    optimized way. Only the first byte (code) is mandatory. \n    Integer indexes are represented in absolute or relative mode, \n    where relative means offset wrt. a Then/Else node info. \n    Suppose Var(NodeId), Then(NodeId) and Else(NodeId) represent \n    infos about a given node.<p>\n    \n    The generic \"NodeId\" node is stored as \n\n    <UL>\n    <LI> code-byte\n    <LI> \\[var-info\\]\n    <LI> \\[Then-info\\]\n    <LI> \\[Else-info\\]\n    </UL>\n\n    where code-byte contains bit fields\n\n    <UL>\n    <LI>Unused  : 1 bit\n    <LI>Variable: 2 bits, one of the following codes\n    <UL>\n    <LI>DDDMP_ABSOLUTE_ID   var-info = Var(NodeId) follows\n    <LI>DDDMP_RELATIVE_ID   Var(NodeId) is represented in relative form as\n        var-info = Min(Var(Then(NodeId)),Var(Else(NodeId))) -Var(NodeId)\n    <LI>DDDMP_RELATIVE_1    No var-info follows, because\n        Var(NodeId) = Min(Var(Then(NodeId)),Var(Else(NodeId)))-1\n    <LI>DDDMP_TERMINAL      Node is a terminal, no var info required\n    </UL>\n    <LI>T       : 2 bits, with codes similar to V\n    <UL>\n    <LI>DDDMP_ABSOLUTE_ID   Then-info = Then(NodeId) follows\n    <LI>DDDMP_RELATIVE_ID   Then(NodeId) is represented in relative form as\n          Then-info = Nodeid-Then(NodeId)\n    <LI>DDDMP_RELATIVE_1    No info on Then(NodeId) follows, because\n          Then(NodeId) = NodeId-1\n    <LI>DDDMP_TERMINAL Then Node is a terminal, no info required (for BDDs)\n    </UL>\n    <LI>Ecompl  : 1 bit, if 1 means complemented edge\n    <LI>E       : 2 bits, with codes and meanings as for the Then edge\n    </UL>\n    var-info, Then-info, Else-info (if required) are represented as unsigned \n    integer values on a sufficient set of bytes (MSByte first).\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nNodeStoreRecurAdd (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode *f         /* IN: DD node to be stored */,\n  int mode          /* IN: store mode */,\n  int *supportids   /* IN: internal ids for variables */,\n  char **varnames   /* IN: names of variables: to be stored with nodes */,\n  int *outids       /* IN: output ids for variables */,\n  FILE *fp          /* IN: store file */\n  )\n{\n  DdNode *T = NULL;\n  DdNode *E = NULL;\n  int idf = (-1);\n  int idT = (-1);\n  int idE = (-1);\n  int vf = (-1);\n  int retValue;\n\n  T = E = NULL;\n  idf = idT =  idE = (-1);\n\n#ifdef DDDMP_DEBUG\n  assert(!Cudd_IsComplement(f));\n  assert(f!=NULL);\n  assert(supportids!=NULL);\n#endif\n\n  /* If already visited, nothing to do. */\n  if (DddmpVisitedAdd (f)) {\n    return (DDDMP_SUCCESS);\n  }\n\n  /* Mark node as visited. */\n  DddmpSetVisitedAdd (f);\n\n  if (Cudd_IsConstant(f)) {\n    /* Check for special case: don't recur */\n    idf = DddmpReadNodeIndexAdd (f);\n  } else {\n\n#ifdef DDDMP_DEBUG\n    /* BDDs! Only one constant supported */\n    assert (!cuddIsConstant(f));\n#endif\n\n    /* \n     *  Recursive call for Then edge\n     */\n\n    T = cuddT(f);\n#ifdef DDDMP_DEBUG\n    /* ROBDDs! No complemented Then edge */\n    assert (!Cudd_IsComplement(T)); \n#endif\n    /* recur */\n    retValue = NodeStoreRecurAdd (ddMgr, T, mode, supportids, varnames, outids,\n      fp);\n    if (retValue != DDDMP_SUCCESS) {\n      return (retValue);\n    }\n\n    /* \n     *  Recursive call for Else edge\n     */\n\n    E = Cudd_Regular (cuddE (f));\n    retValue = NodeStoreRecurAdd (ddMgr, E, mode, supportids, varnames, outids,\n      fp);\n    if (retValue != DDDMP_SUCCESS) {\n      return (retValue);\n    }\n\n    /* \n     *  Obtain nodeids and variable ids of f, T, E \n     */\n\n    idf = DddmpReadNodeIndexAdd (f);\n    vf = f->index;\n\n    idT = DddmpReadNodeIndexAdd (T);\n\n    idE = DddmpReadNodeIndexAdd (E);\n  }\n\n  retValue = NodeTextStoreAdd (ddMgr, f, mode, supportids, varnames,\n    outids, fp, idf, vf, idT, idE);\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store One Single Node in Text Format.]\n\n  Description  [Store 1 0 0 for the terminal node.\n    Store id, left child pointer, right pointer for all the other nodes.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [NodeBinaryStore]\n\n******************************************************************************/\n\nstatic int\nNodeTextStoreAdd (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode *f         /* IN: DD node to be stored */,\n  int mode          /* IN: store mode */,\n  int *supportids   /* IN: internal ids for variables */,\n  char **varnames   /* IN: names of variables: to be stored with nodes */,\n  int *outids       /* IN: output ids for variables */,\n  FILE *fp          /* IN: Store file */,\n  int idf           /* IN: index of the current node */,\n  int vf            /* IN: variable of the current node */,\n  int idT           /* IN: index of the Then node */,\n  int idE           /* IN: index of the Else node */\n  )\n{\n  int retValue;\n  (void) mode; /* avoid warning */\n\n  /*\n   *  Check for Constant\n   */\n\n  if (Cudd_IsConstant(f)) {\n\n    if (f == Cudd_ReadOne(ddMgr)) {\n      if ((varnames != NULL) || (outids != NULL)) {\n        retValue = fprintf (fp, \"%d T 1 0 0\\n\", idf);\n      } else {\n        retValue = fprintf (fp, \"%d 1 0 0\\n\", idf);\n      }\n\n      if (retValue == EOF) {\n        return (DDDMP_FAILURE);\n      } else {\n        return (DDDMP_SUCCESS);\n      }\n    }\n\n    if (f == Cudd_ReadZero(ddMgr)) {\n      if ((varnames != NULL) || (outids != NULL)) {\n        retValue = fprintf (fp, \"%d T 0 0 0\\n\", idf);\n      } else {\n        retValue = fprintf (fp, \"%d 0 0 0\\n\", idf);\n      }\n\n      if (retValue == EOF) {\n        return (DDDMP_FAILURE);\n      } else {\n        return (DDDMP_SUCCESS);\n      }\n    }\n\n    /*\n     *  A constant node different from 1: an ADD constant\n     */\n\n    if ((varnames != NULL) || (outids != NULL)) {\n      retValue = fprintf (fp, \"%d T %g 0 0\\n\",idf,Cudd_V(f));\n    } else {\n      retValue = fprintf (fp, \"%d %g 0 0\\n\",idf, Cudd_V(f));\n    }\n\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    } else {\n      return (DDDMP_SUCCESS);\n    }\n  }\n\n  /*\n   *  ... Not A Constant\n   */\n\n  if (Cudd_IsComplement (cuddE(f))) {\n    idE = -idE;\n  }\n\n  if (varnames != NULL) {   \n    retValue = fprintf (fp, \"%d %s %d %d %d\\n\",\n       idf, varnames[vf], supportids[vf], idT, idE);\n\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    } else {\n      return (DDDMP_SUCCESS);\n    }\n  }\n\n  if (outids != NULL) {   \n    retValue = fprintf (fp, \"%d %d %d %d %d\\n\",\n       idf, outids[vf], supportids[vf], idT, idE);\n\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    } else {\n      return (DDDMP_SUCCESS);\n    }\n    }\n\n  retValue = fprintf (fp, \"%d %d %d %d\\n\",\n    idf, supportids[vf], idT, idE);\n\n  if (retValue == EOF) {\n    return (DDDMP_FAILURE);\n  } else {\n    return (DDDMP_SUCCESS);\n  }\n}\n"
  },
  {
    "path": "cudd/dddmp/dddmpStoreBdd.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpStoreBdd.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to write BDDs to file.]\n\n  Description  [Functions to write BDDs to file.\n    BDDs are represended on file either in text or binary format under the\n    following rules.  A file contains a forest of BDDs (a vector of\n    Boolean functions).  BDD nodes are numbered with contiguous numbers,\n    from 1 to NNodes (total number of nodes on a file). 0 is not used to\n    allow negative node indexes for complemented edges.  A file contains\n    a header, including information about variables and roots to BDD\n    functions, followed by the list of nodes.  BDD nodes are listed\n    according to their numbering, and in the present implementation\n    numbering follows a post-order strategy, in such a way that a node\n    is never listed before its Then/Else children.\n  ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int NodeStoreRecurBdd(DdManager *ddMgr, DdNode *f, int mode, int *supportids, char **varnames, int *outids, FILE *fp);\nstatic int NodeTextStoreBdd(DdManager *ddMgr, DdNode *f, int mode, int *supportids, char **varnames, int *outids, FILE *fp, int idf, int vf, int idT, int idE);\nstatic int NodeBinaryStoreBdd(DdManager *ddMgr, DdNode *f, int mode, int *supportids, char **varnames, int *outids, FILE *fp, int idf, int vf, int idT, int idE, int vT, int vE, DdNode *T, DdNode *E);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument BDD.]\n\n  Description  [Dumps the argument BDD to file. Dumping is done through\n    Dddmp_cuddBddArrayStore. A dummy array of 1 BDD root is\n    used for this purpose.\n    ]\n\n  SideEffects  [Nodes are temporarily removed from unique hash. They are\n    re-linked after the store operation in a modified order.\n    ]\n\n  SeeAlso      [Dddmp_cuddBddLoad Dddmp_cuddBddArrayLoad]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddStore (\n  DdManager *ddMgr           /* IN: DD Manager */,\n  char *ddname               /* IN: DD name (or NULL) */,\n  DdNode *f                  /* IN: BDD root to be stored */,\n  char **varnames            /* IN: array of variable names (or NULL) */,\n  int *auxids                /* IN: array of converted var ids */,\n  int mode                   /* IN: storing mode selector */,\n  Dddmp_VarInfoType varinfo  /* IN: extra info for variables in text mode */,\n  char *fname                /* IN: File name */,\n  FILE *fp                   /* IN: File pointer to the store file */ \n  )\n{\n  int retValue;\n  DdNode *tmpArray[1];\n\n  tmpArray[0] = f;\n\n  retValue = Dddmp_cuddBddArrayStore (ddMgr,ddname,1,tmpArray,NULL,\n    varnames, auxids, mode, varinfo, fname, fp);\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument Array of BDDs.]\n\n  Description  [Dumps the argument array of BDDs to file. Dumping is either \n    in text or binary form.  BDDs are stored to the fp (already \n    open) file if not NULL. Otherwise the file whose name is \n    fname is opened in write mode. The header has the same format \n    for both textual and binary dump. Names are allowed for input \n    variables (vnames) and for represented functions (rnames). \n    For sake of generality and because of dynamic variable \n    ordering both variable IDs and permuted IDs are included. \n    New IDs are also supported (auxids). Variables are identified \n    with incremental numbers. according with their positiom in \n    the support set. In text mode, an extra info may be added, \n    chosen among the following options: name, ID, PermID, or an \n    auxiliary id. Since conversion from DD pointers to integers \n    is required, DD nodes are temporarily removed from the unique\n    hash table. This allows the use of the next field to store \n    node IDs.\n   ]\n\n  SideEffects  [Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n    ] \n\n  SeeAlso      [Dddmp_cuddBddStore, Dddmp_cuddBddLoad, \n    Dddmp_cuddBddArrayLoad\n    ]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddArrayStore (\n  DdManager *ddMgr           /* IN: DD Manager */,\n  char *ddname               /* IN: dd name (or NULL) */,\n  int nRoots                 /* IN: number of output BDD roots to be stored */,\n  DdNode **f                 /* IN: array of BDD roots to be stored */,\n  char **rootnames           /* IN: array of root names (or NULL) */,\n  char **varnames            /* IN: array of variable names (or NULL) */,\n  int *auxids                /* IN: array of converted var IDs */,\n  int mode                   /* IN: storing mode selector */,\n  Dddmp_VarInfoType varinfo  /* IN: extra info for variables in text mode */,\n  char *fname                /* IN: File name */,\n  FILE *fp                   /* IN: File pointer to the store file */ \n  )\n{\n  int retValue;\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValueBis;\n\n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  retValue = DddmpCuddBddArrayStore (DDDMP_BDD, ddMgr, ddname, nRoots, f,\n    rootnames, varnames, auxids, mode, varinfo, fname, fp);\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  return (retValue);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument Array of\n    BDDs.\n    ]\n\n  Description  [Dumps the argument array of BDDs to file.\n    Internal function doing inner steps of store for BDDs.\n    ]\n\n  SideEffects  [Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n    ]\t\n\t\n  SeeAlso      [Dddmp_cuddBddStore, Dddmp_cuddBddLoad,\n    Dddmp_cuddBddArrayLoad\n    ]\n\n******************************************************************************/\n\nint\nDddmpCuddBddArrayStore (\n  Dddmp_DecompType ddType   /* IN: Selects the decomp type BDD */,\n  DdManager *ddMgr          /* IN: DD Manager */,\n  char *ddname              /* IN: DD name (or NULL) */,\n  int nRoots                /* IN: number of output BDD roots to be stored */,\n  DdNode **f                /* IN: array of DD roots to be stored */,\n  char **rootnames          /* IN: array of root names (or NULL) */,\n  char **varnames           /* IN: array of variable names (or NULL) */,\n  int *auxids               /* IN: array of converted var IDs */,\n  int mode                  /* IN: storing mode selector */,\n  Dddmp_VarInfoType varinfo /* IN: extra info for variables in text mode */,\n  char *fname               /* IN: File name */,\n  FILE *fp                  /* IN: File pointer to the store file */ \n  )\n{\n  DdNode *support = NULL;\n  DdNode *scan;\n  int *ids = NULL;\n  int *permids = NULL;\n  int *invpermids = NULL;\n  int *supportids = NULL;\n  int *outids = NULL;\n  char **outvarnames = NULL;\n  int nVars = ddMgr->size;\n  int nnodes;\n  int retValue;\n  int i, var;\n  int fileToClose = 0;\n\n  /* \n   *  Check DD Type\n   */\n\n  Dddmp_CheckAndGotoLabel (ddType==DDDMP_ADD,\n    \"Error writing to file: ADD Type.\", failure);\n\n  /* \n   *  Check if File needs to be opened in the proper mode.\n   */\n\n  if (fp == NULL) {\n    fp = fopen (fname, \"w\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  /* \n   *  Force binary mode if automatic.\n   */\n\n  switch (mode) {\n    case DDDMP_MODE_TEXT:\n    case DDDMP_MODE_BINARY:\n      break;\n    case DDDMP_MODE_DEFAULT:\n      mode = DDDMP_MODE_BINARY;\n      break;\n    default:\n      mode = DDDMP_MODE_BINARY;\n      break;\n  }\n\n  /* \n   * Alloc vectors for variable IDs, perm IDs and support IDs.\n   *  +1 to include a slot for terminals.\n   */\n\n  ids = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndGotoLabel (ids==NULL, \"Error allocating memory.\", failure);\n  permids = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndGotoLabel (permids==NULL, \"Error allocating memory.\", failure);\n  invpermids = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndGotoLabel (invpermids==NULL, \"Error allocating memory.\",\n    failure);\n  supportids = DDDMP_ALLOC (int, nVars+1);\n  Dddmp_CheckAndGotoLabel (supportids==NULL, \"Error allocating memory.\",\n    failure);\n    \n  for (i=0; i<nVars; i++) {\n    ids[i] = permids[i] = invpermids[i] = supportids[i] = (-1);\n  }\n  /* StQ */\n  supportids[nVars] = -1;\n  \n  /* \n   *  Take the union of the supports of each output function.\n   *  skip NULL functions.\n   *  Set permids and invpermids of support variables to the proper values.\n   */\n\n  for (i=0; i<nRoots; i++) {\n    if (f[i] == NULL) {\n      continue;\n    }\n    support = Cudd_Support (ddMgr, f[i]);\n    Dddmp_CheckAndGotoLabel (support==NULL, \"NULL support returned.\",\n      failure);\n    cuddRef (support);\n    scan = support;\n    while (!cuddIsConstant(scan)) {\n      ids[scan->index] = scan->index;\n      permids[scan->index] = ddMgr->perm[scan->index];\n      invpermids[ddMgr->perm[scan->index]] = scan->index;\n      scan = cuddT (scan);\n    }\n    Cudd_RecursiveDeref (ddMgr, support);\n  }\n  /* so that we do not try to free it in case of failure */\n  support = NULL;\n\n  /*\n   *  Set supportids to incremental (shrinked) values following the ordering.\n   */\n\n  for (i=0, var=0; i<nVars; i++) {\n    if (invpermids[i] >= 0) {\n      supportids[invpermids[i]] = var++;\n    }\n  }\n  /* set a dummy id for terminal nodes */\n  supportids[nVars] = var;\n\n  /*\n   *  Select conversion array for extra var info\n   */\n\n  switch (mode) {\n    case DDDMP_MODE_TEXT:\n      switch (varinfo) {\n        case DDDMP_VARIDS:\n          outids = ids;\n          break;\n        case DDDMP_VARPERMIDS:\n          outids = permids;\n          break;\n        case DDDMP_VARAUXIDS:\n          outids = auxids;\n          break;\n        case DDDMP_VARNAMES:\n          outvarnames = varnames;\n          break;\n        case DDDMP_VARDEFAULT:\n          break;\n      }\n      break;\n    case DDDMP_MODE_BINARY:\n      outids = NULL;\n      break;\n  }\n\n  /* \n   *  Number dd nodes and count them (numbering is from 1 to nnodes)\n   */\n\n  nnodes = DddmpNumberBddNodes (ddMgr, f, nRoots);\n\n  /* \n   * Start Header\n   */\n\n#ifdef DDDMP_VERSION\n  retValue = fprintf (fp, \".ver %s\\n\", DDDMP_VERSION);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n#endif\n\n  retValue = fprintf (fp, \".mode %c\\n\", mode);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  if (mode == DDDMP_MODE_TEXT) {\n    retValue = fprintf (fp, \".varinfo %d\\n\", varinfo);\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  if (ddname != NULL) {\n    retValue = fprintf (fp, \".dd %s\\n\",ddname);\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  retValue = fprintf (fp, \".nnodes %d\\n\", nnodes);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  retValue = fprintf (fp, \".nvars %d\\n\", nVars);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  retValue = fprintf (fp, \".nsuppvars %d\\n\", var);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  /*------------  Write the Var Names by scanning the ids array -------------*/\n\n  if (varnames != NULL) {\n\n    retValue = fprintf (fp, \".suppvarnames\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n\n    for (i=0; i<nVars; i++) {\n      if (ids[i] >= 0) {\n        if (varnames[ids[i]] == NULL) {\n          (void) fprintf (stderr,\n             \"DdStore Warning: null variable name. DUMMY%d generated\\n\", i);\n          fflush (stderr);\n          varnames[ids[i]] = DDDMP_ALLOC (char, 10);\n          Dddmp_CheckAndGotoLabel (varnames[ids[i]] == NULL,\n            \"Error allocating memory.\", failure);\n          sprintf (varnames[ids[i]], \"DUMMY%d\", i);\n        }\n        retValue = fprintf (fp, \" %s\", varnames[ids[i]]);\n        Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n          failure);\n      }\n    }\n\n    retValue = fprintf (fp, \"\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  /*--------- Write the Var SUPPORT Names by scanning the ids array ---------*/\n\n  if (varnames != NULL) {\n    retValue = fprintf (fp, \".orderedvarnames\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n\n    for (i=0; i<nVars; i++) {\n      if (varnames[ddMgr->invperm[i]] == NULL) {\n          (void) fprintf (stderr,\n           \"DdStore Warning: null variable name. DUMMY%d generated\\n\", i);\n        fflush (stderr);\n        varnames[ddMgr->invperm[i]] = DDDMP_ALLOC (char, 10);\n        Dddmp_CheckAndGotoLabel (varnames[ddMgr->invperm[i]] == NULL,\n          \"Error allocating memory.\", failure);\n        sprintf (varnames[ddMgr->invperm[i]], \"DUMMY%d\", i);\n      }\n\n      retValue = fprintf (fp, \" %s\", varnames[ddMgr->invperm[i]]);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n        failure);\n    }\n\n    retValue = fprintf (fp, \"\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  /*------------ Write the var ids by scanning the ids array ---------------*/\n\n  retValue = fprintf (fp, \".ids\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  for (i=0; i<nVars; i++) {\n    if (ids[i] >= 0) {\n      retValue = fprintf (fp, \" %d\", i);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n        failure);\n    }\n  }\n  retValue = fprintf (fp, \"\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  /*\n   *  Write the var permids by scanning the permids array. \n   */\n\n  retValue = fprintf (fp, \".permids\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n  for (i = 0; i < nVars; i++) {\n    if (permids[i] >= 0) {\n      retValue = fprintf (fp, \" %d\", permids[i]);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n        failure);\n    }\n  }\n\n  retValue = fprintf (fp, \"\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  if (auxids != NULL) {\n  \n    /*\n     * Write the var auxids by scanning the ids array. \n     */\n\n    retValue = fprintf (fp, \".auxids\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n    for (i = 0; i < nVars; i++) {\n      if (ids[i] >= 0) {\n        retValue = fprintf (fp, \" %d\", auxids[i]);\n        Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n          failure);\n      }\n    }\n    retValue = fprintf (fp, \"\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  /* \n   * Write the roots info. \n   */\n\n  retValue = fprintf (fp, \".nroots %d\\n\", nRoots);\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  if (rootnames != NULL) {\n\n    /* \n     * Write the root names. \n     */\n\n    retValue = fprintf (fp, \".rootnames\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n\n    for (i = 0; i < nRoots; i++) {\n      if (rootnames[i] == NULL) {\n        (void) fprintf (stderr,\n          \"DdStore Warning: null variable name. ROOT%d generated\\n\",i);\n        fflush (stderr);\n        rootnames[i] = DDDMP_ALLOC(char,10);\n        Dddmp_CheckAndGotoLabel (rootnames[i]==NULL,\n          \"Error writing to file.\", failure);\n        sprintf(rootnames[ids[i]], \"ROOT%d\",i);\n      }\n      retValue = fprintf (fp, \" %s\", rootnames[i]);\n      Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n        failure);\n    }\n\n    retValue = fprintf (fp, \"\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  retValue = fprintf (fp, \".rootids\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  /* \n   * Write BDD indexes of function roots.\n   * Use negative integers for complemented edges. \n   */\n\n  for (i = 0; i < nRoots; i++) {\n    if (f[i] == NULL) {\n      (void) fprintf (stderr, \"DdStore Warning: %d-th root is NULL\\n\",i);\n      fflush (stderr);\n      retValue = fprintf (fp, \" 0\");\n    }\n    if (Cudd_IsComplement(f[i])) {\n      retValue = fprintf (fp, \" -%d\",\n        DddmpReadNodeIndexBdd (Cudd_Regular (f[i])));\n    } else {\n      retValue = fprintf (fp, \" %d\",\n        DddmpReadNodeIndexBdd (Cudd_Regular (f[i])));\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  retValue = fprintf (fp, \"\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  retValue = fprintf (fp, \".nodes\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  /* \n   *  END HEADER\n   */\n\n  /* \n   *  Call the function that really gets the job done.\n   */\n\n  for (i = 0; i < nRoots; i++) {\n    if (f[i] != NULL) {\n      retValue = NodeStoreRecurBdd (ddMgr, Cudd_Regular(f[i]),\n        mode, supportids, outvarnames, outids, fp);\n      Dddmp_CheckAndGotoLabel (retValue==DDDMP_FAILURE,\n        \"Error writing to file.\", failure);\n    }\n  }\n\n  /* \n   *  Write trailer and return.\n   */\n\n  retValue = fprintf (fp, \".end\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n    failure);\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n  DddmpUnnumberBddNodes (ddMgr, f, nRoots);\n  DDDMP_FREE (ids);\n  DDDMP_FREE (permids);\n  DDDMP_FREE (invpermids);\n  DDDMP_FREE (supportids);\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n\n    if (ids != NULL) {\n      DDDMP_FREE (ids);\n    }\n    if (permids != NULL) {\n      DDDMP_FREE (permids);\n    }\n    if (invpermids != NULL) {\n      DDDMP_FREE (invpermids);\n    }\n    if (supportids != NULL) {\n      DDDMP_FREE (supportids);\n    }\n    if (support != NULL) {\n      Cudd_RecursiveDeref (ddMgr, support);\n    }\n    \n    return (DDDMP_FAILURE);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Performs the recursive step of Dddmp_bddStore.]\n\n  Description  [Stores a node to file in either test or binary mode.<l>\n    In text mode a node is represented (on a text line basis) as\n    <UL>\n    <LI> node-index \\[var-extrainfo\\] var-index Then-index Else-index\n    </UL>\n    \n    where all indexes are integer numbers and var-extrainfo \n    (optional redundant field) is either an integer or a string \n    (variable name). Node-index is redundant (due to the node \n    ordering) but we keep it for readability.<p>\n    \n    In binary mode nodes are represented as a sequence of bytes,\n    representing var-index, Then-index, and Else-index in an \n    optimized way. Only the first byte (code) is mandatory. \n    Integer indexes are represented in absolute or relative mode, \n    where relative means offset wrt. a Then/Else node info. \n    Suppose Var(NodeId), Then(NodeId) and Else(NodeId) represent \n    infos about a given node.<p>\n    \n    The generic \"NodeId\" node is stored as \n\n    <UL>\n    <LI> code-byte\n    <LI> \\[var-info\\]\n    <LI> \\[Then-info\\]\n    <LI> \\[Else-info\\]\n    </UL>\n\n    where code-byte contains bit fields\n\n    <UL>\n    <LI>Unused  : 1 bit\n    <LI>Variable: 2 bits, one of the following codes\n    <UL>\n    <LI>DDDMP_ABSOLUTE_ID   var-info = Var(NodeId) follows\n    <LI>DDDMP_RELATIVE_ID   Var(NodeId) is represented in relative form as\n        var-info = Min(Var(Then(NodeId)),Var(Else(NodeId))) -Var(NodeId)\n    <LI>DDDMP_RELATIVE_1    No var-info follows, because\n        Var(NodeId) = Min(Var(Then(NodeId)),Var(Else(NodeId)))-1\n    <LI>DDDMP_TERMINAL      Node is a terminal, no var info required\n    </UL>\n    <LI>T       : 2 bits, with codes similar to V\n    <UL>\n    <LI>DDDMP_ABSOLUTE_ID   Then-info = Then(NodeId) follows\n    <LI>DDDMP_RELATIVE_ID   Then(NodeId) is represented in relative form as\n          Then-info = Nodeid-Then(NodeId)\n    <LI>DDDMP_RELATIVE_1    No info on Then(NodeId) follows, because\n          Then(NodeId) = NodeId-1\n    <LI>DDDMP_TERMINAL Then Node is a terminal, no info required (for BDDs)\n    </UL>\n    <LI>Ecompl  : 1 bit, if 1 means complemented edge\n    <LI>E       : 2 bits, with codes and meanings as for the Then edge\n    </UL>\n    var-info, Then-info, Else-info (if required) are represented as unsigned \n    integer values on a sufficient set of bytes (MSByte first).\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nNodeStoreRecurBdd (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode *f         /* IN: DD node to be stored */,\n  int mode          /* IN: store mode */,\n  int *supportids   /* IN: internal ids for variables */,\n  char **varnames   /* IN: names of variables: to be stored with nodes */,\n  int *outids       /* IN: output ids for variables */,\n  FILE *fp          /* IN: store file */\n  )\n{\n  DdNode *T = NULL;\n  DdNode *E = NULL;\n  int idf = (-1);\n  int idT = (-1);\n  int idE = (-1);\n  int vf = (-1);\n  int vT = (-1);\n  int vE = (-1);\n  int retValue;\n  int nVars;\n\n  nVars = ddMgr->size;\n  T = E = NULL;\n  idf = idT =  idE = (-1);\n\n#ifdef DDDMP_DEBUG\n  assert(!Cudd_IsComplement(f));\n  assert(f!=NULL);\n  assert(supportids!=NULL);\n#endif\n\n  /* If already visited, nothing to do. */\n  if (DddmpVisitedBdd (f)) {\n    return (DDDMP_SUCCESS);\n  }\n\n  /* Mark node as visited. */\n  DddmpSetVisitedBdd (f);\n\n  if (Cudd_IsConstant(f)) {\n    /* Check for special case: don't recur */\n    idf = DddmpReadNodeIndexBdd (f);\n  } else {\n\n#ifdef DDDMP_DEBUG\n    /* BDDs! Only one constant supported */\n    assert (!cuddIsConstant(f));\n#endif\n\n    /* \n     *  Recursive call for Then edge\n     */\n\n    T = cuddT(f);\n#ifdef DDDMP_DEBUG\n    /* ROBDDs! No complemented Then edge */\n    assert (!Cudd_IsComplement(T)); \n#endif\n    /* recur */\n    retValue = NodeStoreRecurBdd (ddMgr, T, mode, supportids, varnames, outids,\n      fp);\n    if (retValue != DDDMP_SUCCESS) {\n      return (retValue);\n    }\n\n    /* \n     *  Recursive call for Else edge\n     */\n\n    E = Cudd_Regular (cuddE (f));\n    retValue = NodeStoreRecurBdd (ddMgr, E, mode, supportids, varnames, outids,\n      fp);\n    if (retValue != DDDMP_SUCCESS) {\n      return (retValue);\n    }\n\n    /* \n     *  Obtain nodeids and variable ids of f, T, E \n     */\n\n    idf = DddmpReadNodeIndexBdd (f);\n    vf = f->index;\n\n    idT = DddmpReadNodeIndexBdd (T);\n    if (Cudd_IsConstant(T)) {\n      vT = nVars;\n    } else {\n      vT = T->index;\n    }\n\n    idE = DddmpReadNodeIndexBdd (E);\n    if (Cudd_IsConstant(E)) {\n      vE = nVars;\n    } else {\n      vE = E->index;\n    }\n  }\n\n  switch (mode) {\n    case DDDMP_MODE_TEXT:\n      retValue = NodeTextStoreBdd (ddMgr, f, mode, supportids, varnames,\n        outids, fp, idf, vf, idT, idE);\n      break;\n    case DDDMP_MODE_BINARY:\n      retValue = NodeBinaryStoreBdd (ddMgr, f, mode, supportids, varnames,\n        outids, fp, idf, vf, idT, idE, vT, vE, T, E);\n      break;\n    default:\n      return (DDDMP_FAILURE);\n  }\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store One Single Node in Text Format.]\n\n  Description  [Store 1 0 0 for the terminal node.\n    Store id, left child pointer, right pointer for all the other nodes.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      [NodeBinaryStoreBdd]\n\n******************************************************************************/\n\nstatic int\nNodeTextStoreBdd (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode *f         /* IN: DD node to be stored */,\n  int mode          /* IN: store mode */,\n  int *supportids   /* IN: internal ids for variables */,\n  char **varnames   /* IN: names of variables: to be stored with nodes */,\n  int *outids       /* IN: output ids for variables */,\n  FILE *fp          /* IN: Store file */,\n  int idf           /* IN: index of the current node */,\n  int vf            /* IN: variable of the current node */,\n  int idT           /* IN: index of the Then node */,\n  int idE           /* IN: index of the Else node */\n  )\n{\n  int retValue = EOF;\n  (void) mode; /* avoid warning */\n\n  /*\n   *  Check for Constant\n   */\n\n  if (Cudd_IsConstant(f)) {\n\n    if (f == Cudd_ReadOne(ddMgr)) {\n      if ((varnames != NULL) || (outids != NULL)) {\n        retValue = fprintf (fp, \"%d T 1 0 0\\n\", idf);\n      } else {\n        retValue = fprintf (fp, \"%d 1 0 0\\n\", idf);\n      }\n\n      if (retValue == EOF) {\n        return (DDDMP_FAILURE);\n      } else {\n        return (DDDMP_SUCCESS);\n      }\n    }\n\n    if (f == Cudd_ReadZero(ddMgr)) {\n      if ((varnames != NULL) || (outids != NULL)) {\n        retValue = fprintf (fp, \"%d T 0 0 0\\n\", idf);\n      } else {\n        retValue = fprintf (fp, \"%d 0 0 0\\n\", idf);\n      }\n\n      if (retValue == EOF) {\n        return (DDDMP_FAILURE);\n      } else {\n        return (DDDMP_SUCCESS);\n      }\n    }\n\n    /*\n     *  A constant node different from 1: an ADD constant\n     */\n\n    Dddmp_CheckAndReturn (((varnames!=NULL)||(outids!=NULL)),\n      \"Error writing to file: ADD Type.\");\n\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    } else {\n      return (DDDMP_SUCCESS);\n    }\n  }\n\n  /*\n   *  ... Not A Constant\n   */\n\n  if (Cudd_IsComplement (cuddE(f))) {\n    idE = -idE;\n  }\n\n  if (varnames != NULL) {   \n    retValue = fprintf (fp, \"%d %s %d %d %d\\n\",\n       idf, varnames[vf], supportids[vf], idT, idE);\n\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    } else {\n      return (DDDMP_SUCCESS);\n    }\n  }\n\n  if (outids != NULL) {   \n    retValue = fprintf (fp, \"%d %d %d %d %d\\n\",\n       idf, outids[vf], supportids[vf], idT, idE);\n\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    } else {\n      return (DDDMP_SUCCESS);\n    }\n    }\n\n  retValue = fprintf (fp, \"%d %d %d %d\\n\",\n    idf, supportids[vf], idT, idE);\n\n  if (retValue == EOF) {\n    return (DDDMP_FAILURE);\n  } else {\n    return (DDDMP_SUCCESS);\n  }\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store One Single Node in Binary Format.]\n\n  Description  [Store 1 0 0 for the terminal node.\n    Store id, left child pointer, right pointer for all the other nodes.\n    Store every information as coded binary values.]\n\n  SideEffects  [None]\n\n  SeeAlso      [NodeTextStoreBdd]\n\n******************************************************************************/\n\nstatic int\nNodeBinaryStoreBdd (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode *f         /* IN: DD node to be stored */,\n  int mode          /* IN: store mode */,\n  int *supportids   /* IN: internal ids for variables */,\n  char **varnames   /* IN: names of variables: to be stored with nodes */,\n  int *outids       /* IN: output ids for variables */,\n  FILE *fp          /* IN: store file */,\n  int idf           /* IN: index of the node */,\n  int vf            /* IN: variable of the node */,\n  int idT           /* IN: index of the Then node */,\n  int idE           /* IN: index of the Else node */,\n  int vT            /* IN: variable of the Then node */,\n  int vE            /* IN: variable of the Else node */,\n  DdNode *T         /* IN: Then node */,\n  DdNode *E         /* IN: Else node */\n  )\n{\n  int retValue, diff, var;\n  struct binary_dd_code code;\n  (void) mode;     /* avoid warning */\n  (void) varnames; /* avoid warning */\n  (void) outids;   /* avoid warning */\n  /*\n   *  Check for Constant\n   */\n\n  /* only integer ids used, varnames ignored */\n  /* Terminal one is coded as DDDMP_TERMINAL, all other fields are 0 */\n  if (Cudd_IsConstant(f)) {\n    code.Unused = 0;\n    code.V = DDDMP_TERMINAL;\n    code.T = 0;\n    code.E = 0;\n    code.Ecompl = 0;\n    retValue = DddmpWriteCode (fp,code);\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    } else {\n      return (DDDMP_SUCCESS);\n    }\n  }\n\n  /*\n   * Non terminal: output variable id\n   */\n\n  var = supportids[vf];\n  diff = (supportids[vT]<supportids[vE]) ? \n    (supportids[vT]-var) : (supportids[vE]-var);\n  code.V = DDDMP_ABSOLUTE_ID;\n\n  if (diff <= var) {\n    if (diff == 1) {\n      code.V = DDDMP_RELATIVE_1;\n    } else {\n      code.V = DDDMP_RELATIVE_ID;\n      var = diff;\n    } \n  }\n\n  if (T == DD_ONE(ddMgr)) {\n    code.T = DDDMP_TERMINAL;\n  } else {\n    /* compute displacement */\n    diff = idf - idT;\n    code.T = DDDMP_ABSOLUTE_ID;\n    if (diff <= idT) {\n      if (diff == 1) {\n         code.T = DDDMP_RELATIVE_1;\n      } else {\n         code.T = DDDMP_RELATIVE_ID;\n\t idT = diff;\n      } \n    }\n  }\n\n  if (E == DD_ONE(ddMgr)) {\n    code.E = DDDMP_TERMINAL;\n  } else {\n    /* compute displacement */\n    diff = idf - idE;\n    code.E = DDDMP_ABSOLUTE_ID;\n    if (diff <= idE) {\n      if (diff == 1) {\n        code.E = DDDMP_RELATIVE_1;\n      } else {\n        code.E = DDDMP_RELATIVE_ID;\n\tidE = diff;\n      } \n    }\n  }\n\n  if (Cudd_IsComplement(cuddE(f))) {\n    code.Ecompl = 1;\n  } else {\n    code.Ecompl = 0;\n  }\n\n  retValue = DddmpWriteCode (fp,code);\n  \n  if (retValue == EOF) {\n    return (DDDMP_FAILURE);\n  }\n\n  if ((code.V == DDDMP_ABSOLUTE_ID) || (code.V == DDDMP_RELATIVE_ID)) { \n    retValue = DddmpWriteInt (fp, var);\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    }\n  }\n\n  if ((code.T == DDDMP_ABSOLUTE_ID) || (code.T == DDDMP_RELATIVE_ID)) { \n    retValue = DddmpWriteInt(fp,idT);\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    }\n  }\n\n  if ((code.E == DDDMP_ABSOLUTE_ID) || (code.E == DDDMP_RELATIVE_ID)) { \n    retValue = DddmpWriteInt(fp,idE);\n    if (retValue == EOF) {\n      return (DDDMP_FAILURE);\n    }\n  }\n\n  return (retValue);\n}\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpStoreCnf.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpStoreCnf.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to write out BDDs to file in a CNF format]\n\n  Description  [Functions to write out BDDs to file in a CNF format.]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include <limits.h>\n#include \"dddmpInt.h\"\n\n/*-------------------------------1--------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define DDDMP_DEBUG_CNF   0\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#define GET_MAX(x,y) (x>y?x:y)\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int DddmpCuddBddArrayStoreCnf(DdManager *ddMgr, DdNode **f, int rootN, Dddmp_DecompCnfStoreType mode, int noHeader, char **varNames, int *bddIds, int *bddAuxIds, int *cnfIds, int idInitial, int edgeInTh, int pathLengthTh, char *fname, FILE *fp, int *clauseNPtr, int *varNewNPtr);\nstatic int StoreCnfNodeByNode(DdManager *ddMgr, DdNode **f, int rootN, int *bddIds, int *cnfIds, FILE *fp, int *clauseN, int *varMax, int *rootStartLine);\nstatic int StoreCnfNodeByNodeRecur(DdManager *ddMgr, DdNode *f, int *bddIds, int *cnfIds, FILE *fp, int *clauseN, int *varMax);\nstatic int StoreCnfOneNode(DdNode *f, int idf, int vf, int idT, int idE, FILE *fp, int *clauseN, int *varMax);\nstatic int StoreCnfMaxtermByMaxterm(DdManager *ddMgr, DdNode **f, int rootN, int *bddIds, int *cnfIds, int idInitial, FILE *fp, int *varMax, int *clauseN, int *rootStartLine);\nstatic int StoreCnfBest(DdManager *ddMgr, DdNode **f, int rootN, int *bddIds, int *cnfIds, int idInitial, FILE *fp, int *varMax, int *clauseN, int *rootStartLine);\nstatic void StoreCnfMaxtermByMaxtermRecur(DdManager *ddMgr, DdNode *node, int *bddIds, int *cnfIds, FILE *fp, int *list, int *clauseN, int *varMax);\nstatic int StoreCnfBestNotSharedRecur(DdManager *ddMgr, DdNode *node, int idf, int *bddIds, int *cnfIds, FILE *fp, int *list, int *clauseN, int *varMax);\nstatic int StoreCnfBestSharedRecur(DdManager *ddMgr, DdNode *node, int *bddIds, int *cnfIds, FILE *fp, int *list, int *clauseN, int *varMax);\nstatic int printCubeCnf(DdManager *ddMgr, DdNode *node, int *cnfIds, FILE *fp, int *list, int *varMax);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument BDD in\n    a CNF format.\n    ]\n\n  Description  [Dumps the argument BDD to file.\n    This task is performed by calling the function\n    Dddmp_cuddBddArrayStoreCnf.\n    ]\n\n  SideEffects  [Nodes are temporarily removed from unique hash. They are\n    re-linked after the store operation in a modified order.\n    ]\n\n  SeeAlso      [Dddmp_cuddBddArrayStoreCnf]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddStoreCnf (\n  DdManager *ddMgr              /* IN: DD Manager */,\n  DdNode *f                     /* IN: BDD root to be stored */,\n  Dddmp_DecompCnfStoreType mode /* IN: format selection */,\n  int noHeader                  /* IN: do not store header iff 1 */,\n  char **varNames               /* IN: array of variable names (or NULL) */,\n  int *bddIds                   /* IN: array of var ids */,\n  int *bddAuxIds                /* IN: array of BDD node Auxiliary Ids */,\n  int *cnfIds                   /* IN: array of CNF var ids */,\n  int idInitial                 /* IN: starting id for cutting variables */,\n  int edgeInTh                  /* IN: Max # Incoming Edges */,\n  int pathLengthTh              /* IN: Max Path Length */,\n  char *fname                   /* IN: file name */,\n  FILE *fp                      /* IN: pointer to the store file */,\n  int *clauseNPtr               /* OUT: number of clause stored */, \n  int *varNewNPtr               /* OUT: number of new variable created */\n  )\n{\n  int retValue;\n  DdNode *tmpArray[1];\n\n  tmpArray[0] = f;\n\n  retValue = Dddmp_cuddBddArrayStoreCnf (ddMgr, tmpArray, 1, mode,\n    noHeader, varNames, bddIds, bddAuxIds, cnfIds, idInitial, edgeInTh,\n    pathLengthTh, fname, fp, clauseNPtr, varNewNPtr);\n\n  Dddmp_CheckAndReturn (retValue==DDDMP_FAILURE, \"Failure.\");\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument array of BDDs\n    in CNF format.\n    ]\n\n  Description  [Dumps the argument array of BDDs to file.]\n\n  SideEffects  [Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n    Three methods are allowed:\n    * NodeByNode method: Insert a cut-point for each BDD node (but the\n                         terminal nodes)\n    * MaxtermByMaxterm method: Insert no cut-points, i.e. the off-set of\n                               trhe function is stored\n    * Best method: Tradeoff between the previous two methods.\n      Auxiliary variables, i.e., cut points are inserted following these\n      criterias:\n      * edgeInTh\n        indicates the maximum number of incoming edges up to which\n        no cut point (auxiliary variable) is inserted.\n        If edgeInTh:\n        * is equal to -1 no cut point due to incoming edges are inserted\n          (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node with a single\n          incoming edge, i.e., each node, (NodeByNode method).\n\t* is equal to n a cut point is inserted for each node with (n+1)\n          incoming edges.\n      * pathLengthTh\n        indicates the maximum length path up to which no cut points\n        (auxiliary variable) is inserted.\n        If the path length between two nodes exceeds this value, a cut point\n        is inserted.\n        If pathLengthTh:\n        * is equal to -1 no cut point due path length are inserted\n          (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node (NodeByNode\n          method).\n\t* is equal to n a cut point is inserted on path whose length is\n          equal to (n+1).\n        Notice that the maximum number of literals in a clause is equal\n        to (pathLengthTh + 2), i.e., for each path we have to keep into\n        account a CNF variable for each node plus 2 added variables for\n        the bottom and top-path cut points.\n    The stored file can contain a file header or not depending on the\n    noHeader parameter (IFF 0, usual setting, the header is usually stored.\n    This option can be useful in storing multiple BDDs, as separate BDDs,\n    on the same file leaving the opening of the file to the caller. \n    ]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nint\nDddmp_cuddBddArrayStoreCnf (\n  DdManager *ddMgr              /* IN: DD Manager */,\n  DdNode **f                    /* IN: array of BDD roots to be stored */,\n  int rootN                     /* IN: # output BDD roots to be stored */,\n  Dddmp_DecompCnfStoreType mode /* IN: format selection */,\n  int noHeader                  /* IN: do not store header iff 1 */,\n  char **varNames               /* IN: array of variable names (or NULL) */,\n  int *bddIds                   /* IN: array of converted var IDs */,\n  int *bddAuxIds                /* IN: array of BDD node Auxiliary Ids */,\n  int *cnfIds                   /* IN: array of converted var IDs */,\n  int idInitial                 /* IN: starting id for cutting variables */,\n  int edgeInTh                  /* IN: Max # Incoming Edges */,\n  int pathLengthTh              /* IN: Max Path Length */,\n  char *fname                   /* IN: file name */,\n  FILE *fp                      /* IN: pointer to the store file */,\n  int *clauseNPtr               /* OUT: number of clause stored */, \n  int *varNewNPtr               /* OUT: number of new variable created */ \n  )\n{\n  int retValue2;\n\n#if 0\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValue1;\n\n  retValue1 = Cudd_DebugCheck (ddMgr);\n  Dddmp_CheckAndReturn (retValue1==1,\n    \"Inconsistency Found During CNF Store.\");\n  Dddmp_CheckAndReturn (retValue1==CUDD_OUT_OF_MEM,\n    \"Out of Memory During CNF Store.\");\n#endif\n#endif\n#endif\n\n  retValue2 = DddmpCuddBddArrayStoreCnf (ddMgr, f, rootN, mode, noHeader,\n    varNames, bddIds, bddAuxIds, cnfIds, idInitial, edgeInTh, pathLengthTh,\n    fname, fp, clauseNPtr, varNewNPtr);\n\n#if 0\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValue1 = Cudd_DebugCheck (ddMgr);\n  Dddmp_CheckAndReturn (retValue1==1,\n    \"Inconsistency Found During CNF Store.\");\n  Dddmp_CheckAndReturn (retValue1==CUDD_OUT_OF_MEM,\n    \"Out of Memory During CNF Store.\");\n#endif\n#endif\n#endif\n\n  return (retValue2);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument Array of\n    BDDs in the CNF standard format.\n    ]\n\n  Description  [Dumps the argument array of BDDs/ADDs to file in CNF format.\n    The following arrays: varNames, bddIds, bddAuxIds, and cnfIds \n    fix the correspondence among variable names, BDD ids, BDD \n    auxiliary ids and the ids used to store the CNF problem.\n    All these arrays are automatically created iff NULL.\n    Auxiliary variable, iff necessary, are created starting from value\n    idInitial.\n    Iff idInitial is <= 0 its value is selected as the number of internal\n    CUDD variable + 2.\n    Auxiliary variables, i.e., cut points are inserted following these\n    criterias:\n    * edgeInTh\n      indicates the maximum number of incoming edges up to which\n      no cut point (auxiliary variable) is inserted.\n      If edgeInTh:\n      * is equal to -1 no cut point due to incoming edges are inserted\n        (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node with a single\n        incoming edge, i.e., each node, (NodeByNode method).\n\t* is equal to n a cut point is inserted for each node with (n+1)\n        incoming edges.\n    * pathLengthTh\n      indicates the maximum length path up to which no cut points\n      (auxiliary variable) is inserted.\n      If the path length between two nodes exceeds this value, a cut point\n      is inserted.\n      If pathLengthTh:\n      * is equal to -1 no cut point due path length are inserted\n        (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node (NodeByNode\n        method).\n\t* is equal to n a cut point is inserted on path whose length is\n        equal to (n+1).\n      Notice that the maximum number of literals in a clause is equal\n      to (pathLengthTh + 2), i.e., for each path we have to keep into\n      account a CNF variable for each node plus 2 added variables for\n      the bottom and top-path cut points.\n    ]\n\n  SideEffects  [Nodes are temporarily removed from the unique hash table. \n    They are re-linked after the store operation in a modified \n    order.\n    ]\n\n  SeeAlso      [Dddmp_cuddBddStore]\n\n******************************************************************************/\n\nstatic int\nDddmpCuddBddArrayStoreCnf (\n  DdManager *ddMgr               /* IN: DD Manager */,\n  DdNode **f                     /* IN: array of BDD roots to be stored */,\n  int rootN                      /* IN: # of output BDD roots to be stored */,\n  Dddmp_DecompCnfStoreType mode  /* IN: format selection */,\n  int noHeader                   /* IN: do not store header iff 1 */,\n  char **varNames                /* IN: array of variable names (or NULL) */,\n  int *bddIds                    /* IN: array of BDD node Ids (or NULL) */,\n  int *bddAuxIds                 /* IN: array of BDD Aux Ids (or NULL) */,\n  int *cnfIds                    /* IN: array of CNF ids (or NULL) */,\n  int idInitial                  /* IN: starting id for cutting variables */,\n  int edgeInTh                   /* IN: Max # Incoming Edges */,\n  int pathLengthTh               /* IN: Max Path Length */,\n  char *fname                    /* IN: file name */,\n  FILE *fp                       /* IN: pointer to the store file */,\n  int *clauseNPtr                /* OUT: number of clause stored */,\n  int *varNewNPtr                /* OUT: number of new variable created */ \n  )\n{\n  DdNode *support = NULL;\n  DdNode *scan = NULL;\n  int *bddIdsInSupport = NULL;\n  int *permIdsInSupport = NULL;\n  int *rootStartLine = NULL;\n  int nVar, nVarInSupport, retValue, i, j, fileToClose;\n  int varMax, clauseN, flagVar, intStringLength;\n  int bddIdsToFree = 0;\n  int bddAuxIdsToFree = 0;\n  int cnfIdsToFree = 0;\n  int varNamesToFree = 0;\n  char intString[DDDMP_MAXSTRLEN];\n  char tmpString[DDDMP_MAXSTRLEN];\n  fpos_t posFile1, posFile2;\n\n  /*---------------------------- Set Initial Values -------------------------*/\n\n  support = scan = NULL;\n  bddIdsInSupport = permIdsInSupport = rootStartLine = NULL;\n  nVar = ddMgr->size;\n  fileToClose = 0;\n  sprintf (intString, \"%d\", INT_MAX);\n  intStringLength = strlen (intString);\n\n  /*---------- Check if File needs to be opened in the proper mode ----------*/\n\n  if (fp == NULL) {\n    fp = fopen (fname, \"w\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  /*--------- Generate Bdd LOCAL IDs and Perm IDs and count them ------------*/\n\n  /* BDD Ids */\n  bddIdsInSupport = DDDMP_ALLOC (int, nVar);\n  Dddmp_CheckAndGotoLabel (bddIdsInSupport==NULL, \"Error allocating memory.\",\n    failure);\n  /* BDD PermIds */\n  permIdsInSupport = DDDMP_ALLOC (int, nVar);\n  Dddmp_CheckAndGotoLabel (permIdsInSupport==NULL, \"Error allocating memory.\",\n    failure);\n  /* Support Size (Number of BDD Ids-PermIds */\n  nVarInSupport = 0;\n\n  for (i=0; i<nVar; i++) {\n    bddIdsInSupport[i] = permIdsInSupport[i] = (-1);\n  }\n\n  /* \n   *  Take the union of the supports of each output function.\n   *  Skip NULL functions.\n   */\n\n\n  for (i=0; i<rootN; i++) {\n    if (f[i] == NULL) {\n      continue;\n    }\n    support = Cudd_Support (ddMgr, f[i]);\n    Dddmp_CheckAndGotoLabel (support==NULL, \"NULL support returned.\",\n      failure);\n    cuddRef (support);\n    scan = support;\n    while (!cuddIsConstant(scan)) {\n      /* Count Number of Variable in the Support */\n      nVarInSupport++;\n      /* Set Ids and Perm-Ids */\n      bddIdsInSupport[scan->index] = scan->index;\n      permIdsInSupport[scan->index] = ddMgr->perm[scan->index];\n      scan = cuddT (scan);\n    }\n    Cudd_RecursiveDeref (ddMgr, support);\n  }\n  /* so that we do not try to free it in case of failure */\n  support = NULL;\n\n  /*---------------------------- Start HEADER -------------------------------*/\n\n  if (noHeader==0) {\n\n    retValue = fprintf (fp,\n      \"c # BDD stored by the DDDMP tool in CNF format\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing on file.\",\n      failure);\n    fprintf (fp, \"c #\\n\");\n  }\n\n  /*-------------------- Generate Bdd IDs IFF necessary ---------------------*/\n\n  if (bddIds == NULL) {\n    if (noHeader==0) {\n      fprintf (fp, \"c # Warning: BDD IDs missing ... evaluating them.\\n\");\n      fprintf (fp, \"c # \\n\");\n      fflush (fp);\n    }\n\n    bddIdsToFree = 1;\n    bddIds = DDDMP_ALLOC (int, nVar);\n    Dddmp_CheckAndGotoLabel (bddIds==NULL, \"Error allocating memory.\",\n      failure);\n\n    /* Get BDD-IDs Directly from Cudd Manager */\n    for (i=0; i<nVar; i++) {\n      bddIds[i] = i;\n    }   \n  } /* end if bddIds == NULL */\n\n  /*------------------ Generate AUX BDD IDs IF necessary --------------------*/\n\n  if (bddAuxIds == NULL) {\n    if (noHeader==0) {\n      fprintf (fp, \"c # Warning: AUX IDs missing ... equal to BDD IDs.\\n\");\n      fprintf (fp, \"c #\\n\");\n      fflush (fp);\n    }\n\n    bddAuxIdsToFree = 1;\n    bddAuxIds = DDDMP_ALLOC (int, nVar);\n    Dddmp_CheckAndGotoLabel (bddAuxIds==NULL, \"Error allocating memory.\",\n      failure);\n\n    for (i=0; i<nVar; i++) {\n      bddAuxIds[i] = bddIds[i];\n    }\n  } /* end if cnfIds == NULL */\n\n  /*------------------- Generate CNF IDs IF necessary -----------------------*/\n\n  if (cnfIds == NULL) {\n    if (noHeader==0) {\n      fprintf (fp, \"c # Warning: CNF IDs missing ... equal to BDD IDs.\\n\");\n      fprintf (fp, \"c #\\n\");\n      fflush (fp);\n    }\n\n    cnfIdsToFree = 1;\n    cnfIds = DDDMP_ALLOC (int, nVar);\n    Dddmp_CheckAndGotoLabel (cnfIds==NULL, \"Error allocating memory.\",\n      failure);\n\n    for (i=0; i<nVar; i++) {\n      cnfIds[i] = bddIds[i] + 1;\n    }\n  } /* end if cnfIds == NULL */\n\n  /*------------------ Generate Var Names IF necessary ----------------------*/\n\n  flagVar = 0;\n  if (varNames == NULL) {\n    if (noHeader==0) {\n      fprintf (fp,\n        \"c # Warning: null variable names ... create DUMMY names.\\n\");\n      fprintf (fp, \"c #\\n\");\n      fflush (stderr);\n    }\n\n    varNamesToFree = 1;\n    varNames = DDDMP_ALLOC (char *, nVar);\n    for (i=0; i<nVar; i++) {\n       varNames[i] = NULL;       \n    }\n    Dddmp_CheckAndGotoLabel (varNames==NULL, \"Error allocating memory.\",\n      failure);\n\n    flagVar = 1;\n  } else {\n    /* Protect the user also from partially loaded varNames array !!! */\n    for (i=0; i<nVar && flagVar==0; i++) {\n      if (varNames[i] == NULL) {\n        flagVar = 1;\n      }\n    }\n  }\n\n  if (flagVar == 1) {\n    for (i=0; i<nVar; i++) {\n      if (varNames[i] == NULL) {\n        sprintf (tmpString, \"DUMMY%d\", bddIds[i]);\n        varNames[i] = DDDMP_ALLOC (char, (strlen (tmpString)+1));\n        strcpy (varNames[i], tmpString);\n      }\n    }\n  }\n\n  /*----------------------- Set Initial ID  IF necessary --------------------*/\n\n  if (idInitial <= 0) {\n    idInitial = nVar + 1;\n  }\n\n  /*--------------------------- Continue HEADER -----------------------------*/\n\n  if (noHeader==0) {\n    fprintf (fp, \"c .ver %s\\n\", DDDMP_VERSION);\n    fprintf (fp, \"c .nnodes %d\\n\", Cudd_SharingSize (f, rootN));\n    fprintf (fp, \"c .nvars %d\\n\", nVar);\n    fprintf (fp, \"c .nsuppvars %d\\n\", nVarInSupport);\n\n    /* Support Variable Names */\n    if (varNames != NULL) {\n      fprintf (fp, \"c .suppvarnames\");\n      for (i=0; i<nVar; i++) {\n        if (bddIdsInSupport[i] >= 0) {\n          fprintf (fp, \" %s\", varNames[i]);\n        }\n      }\n      fprintf (fp, \"\\n\");\n    }\n\n    /* Ordered Variable Names */\n    if (varNames != NULL) {\n      fprintf (fp, \"c .orderedvarnames\");\n      for (i=0; i<nVar; i++) {\n        fprintf (fp, \" %s\", varNames[i]);\n      }\n      fprintf (fp, \"\\n\");\n    }\n\n    /* BDD Variable Ids */\n    fprintf (fp, \"c .ids \");\n    for (i=0; i<nVar; i++) {\n      if (bddIdsInSupport[i] >= 0) {\n        fprintf (fp, \" %d\", bddIdsInSupport[i]);\n      }\n    }\n    fprintf (fp, \"\\n\");\n\n    /* BDD Variable Permutation Ids */\n    fprintf (fp, \"c .permids \");\n    for (i=0; i<nVar; i++) {\n      if (bddIdsInSupport[i] >= 0) {\n        fprintf (fp, \" %d\", permIdsInSupport[i]);\n      }\n    }\n    fprintf (fp, \"\\n\");\n\n    /* BDD Variable Auxiliary Ids */\n    fprintf (fp, \"c .auxids \");\n    for (i=0; i<nVar; i++) {\n      if (bddIdsInSupport[i] >= 0) {\n        fprintf (fp, \" %d\", bddAuxIds[i]);\n      }\n    }\n    fprintf (fp, \"\\n\");\n\n    /* CNF Ids */\n    fprintf (fp, \"c .cnfids \");\n    for (i=0; i<nVar; i++) {\n      if (bddIdsInSupport[i] >= 0) {\n        fprintf (fp, \" %d\", cnfIds[i]);\n      }\n    }\n    fprintf (fp, \"\\n\");\n\n    /* Number of Roots */\n    fprintf (fp, \"c .nroots %d\", rootN);\n    fprintf (fp, \"\\n\");\n\n    /* Root Starting Line */\n    fgetpos (fp, &posFile1);\n    fprintf (fp, \"c .rootids\");\n    for (i=0; i<rootN; i++) {\n      for (j=0; j<intStringLength+1; j++) {\n        retValue = fprintf (fp, \" \");\n      }\n    }\n    retValue = fprintf (fp, \"\\n\");\n    fflush (fp);\n\n  } /* End of noHeader check */\n\n  /*------------ Select Mode and Print Number of Tmp Var Created ------------*/\n\n  switch (mode) {\n    case DDDMP_CNF_MODE_NODE:\n      *varNewNPtr = idInitial;\n      *varNewNPtr = DddmpNumberDdNodesCnf (ddMgr, f, rootN, cnfIds, idInitial)\n        - *varNewNPtr;\n      break;\n    case DDDMP_CNF_MODE_MAXTERM:\n      *varNewNPtr = 0;\n      break;\n    default:\n      Dddmp_Warning (1, \"Wrong DDDMP Store Mode. Force DDDMP_MODE_BEST.\");\n    case DDDMP_CNF_MODE_BEST:\n      *varNewNPtr = idInitial;\n      *varNewNPtr = DddmpDdNodesCountEdgesAndNumber (ddMgr, f, rootN,\n        edgeInTh, pathLengthTh, cnfIds, idInitial) - *varNewNPtr;\n      break;\n  }\n\n  /*------------ Print Space for Number of Variable and Clauses -------------*/\n\n  if (noHeader==0) {\n    fprintf (fp, \"c .nAddedCnfVar %d\\n\", *varNewNPtr);\n    fprintf (fp, \"c #\\n\");\n    fprintf (fp, \"c # Init CNF Clauses\\n\");\n    fprintf (fp, \"c #\\n\");\n    fgetpos (fp, &posFile2);\n    retValue = fprintf (fp, \"p cnf\");\n    for (j=0; j<2*(intStringLength+1); j++) {\n      retValue = fprintf (fp, \" \");\n    }\n    retValue = fprintf (fp, \"\\n\");\n    fflush (fp);\n  }\n\n  /*---------------------- Select Mode and Do the Job -----------------------*/\n\n  clauseN = 0;\n  varMax = -1;\n  rootStartLine = DDDMP_ALLOC (int, rootN);\n  Dddmp_CheckAndGotoLabel (rootStartLine==NULL, \"Error allocating memory.\",\n    failure);\n  for (i=0; i<rootN; i++) {\n    rootStartLine[i] = (-1);\n  }\n\n  switch (mode) {\n    case DDDMP_CNF_MODE_NODE:\n      StoreCnfNodeByNode (ddMgr, f, rootN, bddIds, cnfIds, fp, &clauseN,\n        &varMax, rootStartLine);\n      DddmpUnnumberDdNodesCnf (ddMgr, f, rootN);\n      break;\n    case DDDMP_CNF_MODE_MAXTERM:\n      StoreCnfMaxtermByMaxterm (ddMgr, f, rootN, bddIds, cnfIds, idInitial,\n        fp, &varMax, &clauseN, rootStartLine);\n      break;\n    default:\n      Dddmp_Warning (1, \"Wrong DDDMP Store Mode. Force DDDMP_MODE_BEST.\");\n    case DDDMP_CNF_MODE_BEST:\n      StoreCnfBest (ddMgr, f, rootN, bddIds, cnfIds, idInitial,\n        fp, &varMax, &clauseN, rootStartLine);\n      DddmpUnnumberDdNodesCnf (ddMgr, f, rootN);\n      break;\n  }\n\n  /*------------------------------ Write trailer ----------------------------*/\n\n  if (noHeader==0) {\n    retValue = fprintf (fp, \"c # End of Cnf From dddmp-2.0\\n\");\n    Dddmp_CheckAndGotoLabel (retValue==EOF, \"Error writing to file.\",\n      failure);\n  }\n\n  /*\n   *  Write Root Starting Line\n   */\n\n  if (noHeader==0) {\n    fsetpos (fp, &posFile1);\n    fprintf (fp, \"c .rootids\");\n    for (i=0; i<rootN; i++) {\n      Dddmp_Warning (rootStartLine[i]==(-1),\n        \"Init Line for CNF file = (-1) {[(Stored one or zero BDD)]}.\");\n      sprintf (tmpString, \" %d\", rootStartLine[i]);\n      for (j=strlen(tmpString); j<intStringLength+1; j++) {\n        strcat (tmpString, \" \");\n      }\n      retValue = fprintf (fp, \"%s\", tmpString);\n    }\n    retValue = fprintf (fp, \"\\n\");\n    fflush (fp);\n  }\n\n  /*\n   *  Write Number of clauses and variable in the header \n   */\n\n  *clauseNPtr = clauseN;\n\n  if (noHeader==0) {\n    fsetpos (fp, &posFile2);\n    retValue = fprintf (fp, \"p cnf\");\n    sprintf (tmpString, \" %d %d\", varMax, clauseN);\n    for (j=strlen(tmpString); j<2*(intStringLength+1); j++) {\n      strcat (tmpString, \" \");\n    }\n    retValue = fprintf (fp, \"%s\\n\", tmpString);\n    fflush (fp);\n  }\n\n  /*-------------------------- Close file and return ------------------------*/\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n  DDDMP_FREE (bddIdsInSupport);\n  DDDMP_FREE (permIdsInSupport);\n  DDDMP_FREE (rootStartLine);\n  if (bddIdsToFree == 1) {\n    DDDMP_FREE (bddIds);\n  }\n  if (bddAuxIdsToFree == 1) {\n    DDDMP_FREE (bddAuxIds);\n  }\n  if (cnfIdsToFree == 1) {\n    DDDMP_FREE (cnfIds);\n  }\n  if (varNamesToFree == 1) {\n    for (i=0; i<nVar; i++) {\n      DDDMP_FREE (varNames[i]);\n    }\n    DDDMP_FREE (varNames);\n  }\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n\n    if (support != NULL) {\n      Cudd_RecursiveDeref (ddMgr, support);\n    }\n    DDDMP_FREE (bddIdsInSupport);\n    DDDMP_FREE (permIdsInSupport);\n    DDDMP_FREE (rootStartLine);\n    if (bddIdsToFree == 1) {\n      DDDMP_FREE (bddIds);\n    }\n    if (bddAuxIdsToFree == 1) {\n      DDDMP_FREE (bddAuxIds);\n    }\n    if (cnfIdsToFree == 1) {\n      DDDMP_FREE (cnfIds);\n    }\n    if (varNamesToFree == 1) {\n      for (i=0; i<nVar; i++) {\n        DDDMP_FREE (varNames[i]);\n      }\n      DDDMP_FREE (varNames);\n    }\n\n    return (DDDMP_FAILURE);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Store the BDD as CNF clauses.]\n\n  Description  [Store the BDD as CNF clauses.\n    Use a multiplexer description for each BDD node.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nStoreCnfNodeByNode (\n  DdManager *ddMgr      /* IN: DD Manager */,\n  DdNode **f            /* IN: BDD array to be stored */,\n  int rootN             /* IN: number of BDDs in the array */,\n  int *bddIds           /* IN: BDD ids for variables */,\n  int *cnfIds           /* IN: CNF ids for variables */,\n  FILE *fp              /* IN: store file */,\n  int *clauseN      /* IN/OUT: number of clauses written in the CNF file */,\n  int *varMax       /* IN/OUT: maximum value of id written in the CNF file */,\n  int *rootStartLine   /* OUT: CNF line where root starts */\n  )\n{\n  int retValue = 0;\n  int i, idf;\n\n  for (i=0; i<rootN; i++) {\n    if (f[i] != NULL) {\n      if (!cuddIsConstant(Cudd_Regular (f[i]))) {\n        /*\n         *  Set Starting Line for this Root\n         */\n\n        rootStartLine[i] = *clauseN + 1;\n\n        /*\n         *  Store the BDD\n         */\n\n        retValue = StoreCnfNodeByNodeRecur (ddMgr, Cudd_Regular(f[i]),\n          bddIds, cnfIds, fp, clauseN, varMax);\n        if (retValue == 0) {\n          (void) fprintf (stderr,\n            \"DdStoreCnf: Error in recursive node store\\n\");\n          fflush (stderr);\n        }\n\n        /*\n         *  Store CNF for the root if necessary\n         */\n\n        idf = DddmpReadNodeIndexCnf (Cudd_Regular (f[i]));\n#if DDDMP_DEBUG_CNF\n        retValue = fprintf (fp, \"root %d --> \\n\", i);\n#endif\n        if (Cudd_IsComplement (f[i])) {\n          retValue = fprintf (fp, \"-%d 0\\n\", idf);\n        } else {\n          retValue = fprintf (fp, \"%d 0\\n\", idf);\n        } \n        *varMax = GET_MAX (*varMax, idf);\n        *clauseN = *clauseN + 1;\n\n        if (retValue == EOF) {\n          (void) fprintf (stderr,\n            \"DdStoreCnf: Error in recursive node store\\n\");\n          fflush (stderr);\n        }\n      }\n    }\n  }\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Performs the recursive step of Dddmp_bddStore.]\n\n  Description  [Performs the recursive step of Dddmp_bddStore.\n    Traverse the BDD and store a CNF formula for each \"terminal\" node.\n    ]\n\n  SideEffects  [None]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nStoreCnfNodeByNodeRecur (\n  DdManager *ddMgr   /* IN: DD Manager */,\n  DdNode *f          /* IN: BDD node to be stored */,\n  int *bddIds        /* IN: BDD ids for variables */,\n  int *cnfIds        /* IN: CNF ids for variables */,\n  FILE *fp           /* IN: store file */,\n  int *clauseN      /* OUT: number of clauses written in the CNF file */,\n  int *varMax       /* OUT: maximum value of id written in the CNF file */\n  )\n{\n  DdNode *T, *E;\n  int idf, idT, idE, vf;\n  int retValue;\n\n#ifdef DDDMP_DEBUG\n  assert(!Cudd_IsComplement(f));\n  assert(f!=NULL);\n#endif\n\n  /* If constant, nothing to do. */\n  if (Cudd_IsConstant(f)) {\n    return (1);\n  }\n\n  /* If already visited, nothing to do. */\n  if (DddmpVisitedCnf (f)) {\n    return (1);\n  }\n\n  /* Mark node as visited. */\n  DddmpSetVisitedCnf (f);\n\n  /*------------------ Non Terminal Node -------------------------------*/\n\n#ifdef DDDMP_DEBUG\n  /* BDDs! Only one constant supported */\n  assert (!cuddIsConstant(f));\n#endif\n\n  /* \n   *  Recursive call for Then edge\n   */\n\n  T = cuddT (f);\n#ifdef DDDMP_DEBUG\n  /* ROBDDs! No complemented Then edge */\n  assert (!Cudd_IsComplement(T)); \n#endif\n  /* recur */\n  retValue = StoreCnfNodeByNodeRecur (ddMgr, T, bddIds, cnfIds, fp,\n    clauseN, varMax);\n  if (retValue != 1) {\n    return(retValue);\n  }\n\n  /* \n   *  Recursive call for Else edge\n   */\n\n  E = Cudd_Regular (cuddE (f));\n  retValue = StoreCnfNodeByNodeRecur (ddMgr, E, bddIds, cnfIds, fp,\n    clauseN, varMax);\n  if (retValue != 1) {\n    return (retValue);\n  }\n\n  /* \n   *  Obtain nodeids and variable ids of f, T, E \n   */\n\n  idf = DddmpReadNodeIndexCnf (f);\n  vf = f->index;\n\n  if (bddIds[vf] != vf) {\n    (void) fprintf (stderr, \"DdStoreCnf: Error writing to file\\n\");\n    fflush (stderr);\n    return (0);\n  }\n\n  idT = DddmpReadNodeIndexCnf (T);\n\n  idE = DddmpReadNodeIndexCnf (E);\n  if (Cudd_IsComplement (cuddE (f))) {\n    idE = -idE;\n  }\n\n  retValue = StoreCnfOneNode (f, idf, cnfIds[vf], idT, idE, fp,\n   clauseN, varMax);\n\n  if (retValue == EOF) {\n    return (0);\n  } else {\n    return (1);\n  }\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store One Single BDD Node.]\n\n  Description  [Store One Single BDD Node translating it as a multiplexer.]\n\n  SideEffects  [None]\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nStoreCnfOneNode (\n  DdNode *f       /* IN: node to be stored */,\n  int idf         /* IN: node CNF Index  */,\n  int vf          /* IN: node BDD Index */,\n  int idT         /* IN: Then CNF Index with sign = inverted edge */,\n  int idE         /* IN: Else CNF Index with sign = inverted edge */,\n  FILE *fp        /* IN: store file */,\n  int *clauseN   /* OUT: number of clauses */,\n  int *varMax    /* OUT: maximun Index of variable stored */\n  )\n{\n  int retValue = 0;\n  int idfAbs, idTAbs, idEAbs;\n\n  idfAbs = abs (idf);\n  idTAbs = abs (idT);\n  idEAbs = abs (idE);\n\n  /*----------------------------- Check for Constant ------------------------*/\n\n  assert(!Cudd_IsConstant(f));\n\n  /*------------------------- Check for terminal nodes ----------------------*/\n\n  if ((idTAbs==1) && (idEAbs==1)) { \n    return (1);\n  }\n\n  /*------------------------------ Internal Node ----------------------------*/\n\n#if DDDMP_DEBUG_CNF\n  retValue = fprintf (fp, \"id=%d var=%d idT=%d idE=%d\\n\",\n    idf, vf, idT, idE);\n#endif\n\n  /*\n   *  Then to terminal\n   */\n\n  if ((idTAbs==1) && (idEAbs!=1)) {\n#if DDDMP_DEBUG_CNF\n    retValue = fprintf (fp, \"CASE 1 -->\\n\");\n#endif\n    retValue = fprintf (fp, \"%d %d 0\\n\",\n      idf, -vf);\n    retValue = fprintf (fp, \"%d %d 0\\n\",\n      idf, -idE);\n    retValue = fprintf (fp, \"%d %d %d 0\\n\",\n      -idf, vf, idE);\n    *clauseN = *clauseN + 3;\n\n    *varMax = GET_MAX (*varMax, idfAbs);\n    *varMax = GET_MAX (*varMax, vf);\n    *varMax = GET_MAX (*varMax, idEAbs);\n  }\n\n  /*\n   *  Else to terminal\n   */\n\n  if ((idTAbs!=1) && (idEAbs==1)) {\n    if (idE == 1) {\n#if DDDMP_DEBUG_CNF\n      retValue = fprintf (fp, \"CASE 2 -->\\n\");\n#endif\n      retValue = fprintf (fp, \"%d %d 0\\n\",\n        idf, vf);\n      retValue = fprintf (fp, \"%d %d 0\\n\",\n        idf, -idT);\n      retValue = fprintf (fp, \"%d %d %d 0\\n\",\n        -idf, -vf, idT);\n    } else {\n#if DDDMP_DEBUG_CNF\n      retValue = fprintf (fp, \"CASE 3 -->\\n\");\n#endif\n      retValue = fprintf (fp, \"%d %d 0\\n\",\n        -idf, vf);\n      retValue = fprintf (fp, \"%d %d 0\\n\",\n        -idf, idT);\n      retValue = fprintf (fp, \"%d %d %d 0\\n\",\n        idf, -vf, -idT);\n    }\n\n    *varMax = GET_MAX (*varMax, idfAbs);\n    *varMax = GET_MAX (*varMax, vf);\n    *varMax = GET_MAX (*varMax, idTAbs);\n\n    *clauseN = *clauseN + 3;\n  }\n\n  /*\n   *  Nor Then or Else to terminal\n   */\n\n  if ((idTAbs!=1) && (idEAbs!=1)) {\n#if DDDMP_DEBUG_CNF\n    retValue = fprintf (fp, \"CASE 4 -->\\n\");\n#endif\n    retValue = fprintf (fp, \"%d %d %d 0\\n\",\n      idf, vf, -idE);\n    retValue = fprintf (fp, \"%d %d %d 0\\n\",\n      -idf, vf, idE);\n    retValue = fprintf (fp, \"%d %d %d 0\\n\",\n      idf, -vf, -idT);\n    retValue = fprintf (fp, \"%d %d %d 0\\n\",\n      -idf, -vf, idT);\n\n    *varMax = GET_MAX (*varMax, idfAbs);\n    *varMax = GET_MAX (*varMax, vf);\n    *varMax = GET_MAX (*varMax, idTAbs);\n    *varMax = GET_MAX (*varMax, idEAbs);\n\n    *clauseN = *clauseN + 4;\n  }\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n \n  Synopsis    [Prints a disjoint sum of products.]\n \n  Description [Prints a disjoint sum of product cover for the function\n    rooted at node. Each product corresponds to a path from node a \n    leaf node different from the logical zero, and different from \n    the background value. Uses the standard output.  Returns 1 if \n    successful, 0 otherwise.\n    ]\n \n  SideEffects [None]\n \n  SeeAlso     [StoreCnfBest]\n \n******************************************************************************/\n\nstatic int\nStoreCnfMaxtermByMaxterm (\n  DdManager *ddMgr    /* IN: DD Manager */,\n  DdNode **f          /* IN: array of BDDs to store */,\n  int rootN           /* IN: number of BDDs in the array */,\n  int *bddIds         /* IN: BDD Identifiers */,\n  int *cnfIds         /* IN: corresponding CNF Identifiers */,\n  int idInitial       /* IN: initial value for numbering new CNF variables */,\n  FILE *fp            /* IN: file pointer */,\n  int *varMax        /* OUT: maximum identifier of the variables created */,\n  int *clauseN       /* OUT: number of stored clauses */,\n  int *rootStartLine /* OUT: line where root starts */\n  )\n{\n  int i, j, *list;\n  (void) idInitial; /* avoid warning */\n\n  list = DDDMP_ALLOC (int, ddMgr->size);\n  if (list == NULL) {\n    ddMgr->errorCode = CUDD_MEMORY_OUT;\n    return (DDDMP_FAILURE);\n  }\n\n  for (i=0; i<rootN; i++) {\n    if (f[i] != NULL) {\n      if (!cuddIsConstant(Cudd_Regular (f[i]))) {\n        for (j=0; j<ddMgr->size; j++) {\n          list[j] = 2;\n        }\n\n        /*\n         *  Set Starting Line for this Root\n         */\n\n        rootStartLine[i] = *clauseN + 1;\n\n        StoreCnfMaxtermByMaxtermRecur (ddMgr, f[i], bddIds, cnfIds, fp,\n          list, clauseN, varMax);\n      }\n    }\n  }\n\n  FREE (list);\n\n  return (1);\n}\n\n/**Function********************************************************************\n \n  Synopsis    [Prints a disjoint sum of products with intermediate\n    cutting points.]\n \n  Description [Prints a disjoint sum of product cover for the function\n    rooted at node intorducing cutting points whenever necessary.\n    Each product corresponds to a path from node a leaf\n    node different from the logical zero, and different from the\n    background value. Uses the standard output.  Returns 1 if \n    successful, 0 otherwise.\n    ]\n \n  SideEffects [None]\n \n  SeeAlso     [StoreCnfMaxtermByMaxterm]\n \n******************************************************************************/\n\nstatic int\nStoreCnfBest (\n  DdManager *ddMgr    /* IN: DD Manager */,\n  DdNode **f          /* IN: array of BDDs to store */,\n  int rootN           /* IN: number of BDD in the array */,\n  int *bddIds         /* IN: BDD identifiers */,\n  int *cnfIds         /* IN: corresponding CNF identifiers */,\n  int idInitial       /* IN: initial value for numbering new CNF variables */,\n  FILE *fp            /* IN: file pointer */,\n  int *varMax        /* OUT: maximum identifier of the variables created */,\n  int *clauseN       /* OUT: number of stored clauses */,\n  int *rootStartLine /* OUT: line where root starts */\n  )\n{\n  int i, j, *list;\n  (void) idInitial; /* avoid warning */\n\n  list = DDDMP_ALLOC (int, ddMgr->size);\n  if (list == NULL) {\n    ddMgr->errorCode = CUDD_MEMORY_OUT;\n    return (DDDMP_FAILURE);\n  }\n\n  for (i=0; i<rootN; i++) {\n    if (f[i] != NULL) {\n      if (!cuddIsConstant(Cudd_Regular (f[i]))) {\n        for (j=0; j<ddMgr->size; j++) {\n          list[j] = 2;\n        }\n\n        /*\n         *  Set Starting Line for this Root\n         */\n\n        rootStartLine[i] = *clauseN + 1;\n\n#if DDDMP_DEBUG_CNF\n        fprintf (fp, \"root NOT shared BDDs %d --> \\n\", i);\n#endif\n        StoreCnfBestNotSharedRecur (ddMgr, f[i], 0, bddIds, cnfIds, fp, list,\n          clauseN, varMax);\n\n#if DDDMP_DEBUG_CNF\n        fprintf (fp, \"root SHARED BDDs %d --> \\n\", i);\n#endif\n        StoreCnfBestSharedRecur (ddMgr, Cudd_Regular (f[i]), bddIds, cnfIds,\n          fp, list, clauseN, varMax);\n      }\n    }\n  }\n\n#if DDDMP_DEBUG_CNF\n  fprintf (stdout, \"###---> BDDs After the Storing Process:\\n\");\n  DddmpPrintBddAndNext (ddMgr, f, rootN);\n#endif\n\n  FREE (list);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n \n  Synopsis    [Performs the recursive step of Print Maxterm.]\n \n  Description [Performs the recursive step of Print Maxterm.\n    Traverse a BDD a print out a cube in CNF format each time a terminal\n    node is reached.\n    ]\n \n  SideEffects [None]\n\n  SeeAlso     []\n \n******************************************************************************/\n\nstatic void\nStoreCnfMaxtermByMaxtermRecur (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode *node      /* IN: BDD to store */,\n  int *bddIds       /* IN: BDD identifiers */,\n  int *cnfIds       /* IN: corresponding CNF identifiers */,\n  FILE *fp          /* IN: file pointer */,\n  int *list         /* IN: temporary array to store cubes */,\n  int *clauseN     /* OUT: number of stored clauses */,\n  int *varMax      /* OUT: maximum identifier of the variables created */\n  )\n{\n  DdNode *N, *Nv, *Nnv;\n  int retValue, index;\n \n  N = Cudd_Regular (node);\n\n  /*\n   *  Terminal case: Print one cube based on the current recursion\n   */\n\n  if (cuddIsConstant (N)) {\n    retValue = printCubeCnf (ddMgr, node, cnfIds, fp, list, varMax);\n    if (retValue == DDDMP_SUCCESS) {\n      fprintf (fp, \"0\\n\");\n      *clauseN = *clauseN + 1;\n    }\n    return;\n  }\n\n  /*\n   *  NON Terminal case: Recur\n   */\n\n  Nv  = cuddT (N);\n  Nnv = cuddE (N);\n  if (Cudd_IsComplement (node)) {\n    Nv  = Cudd_Not (Nv);\n    Nnv = Cudd_Not (Nnv);\n  }\n  index = N->index;\n\n  /*\n   *  StQ 06.05.2003\n   *  Perform the optimization:\n   *  f = (a + b)' = (a') ^ (a + b') = (a') ^ (b')\n   *  i.e., if the THEN node is the constant ZERO then that variable\n   *  can be forgotten (list[index] = 2) for subsequent ELSE cubes\n   */\n  if (cuddIsConstant (Cudd_Regular (Nv)) &&  Nv != ddMgr->one) {\n    list[index] = 2;\n  } else {\n    list[index] = 0;\n  }\n  StoreCnfMaxtermByMaxtermRecur (ddMgr, Nnv, bddIds, cnfIds, fp, list,\n    clauseN, varMax);\n\n  /*\n   *  StQ 06.05.2003\n   *  Perform the optimization:\n   *  f = a ^ b = (a) ^ (a' + b) = (a) ^ (b)\n   *  i.e., if the ELSE node is the constant ZERO then that variable\n   *  can be forgotten (list[index] = 2) for subsequent THEN cubes\n   */\n  if (cuddIsConstant (Cudd_Regular (Nnv)) &&  Nnv != ddMgr->one) {\n    list[index] = 2;\n  } else {\n    list[index] = 1;\n  }\n  StoreCnfMaxtermByMaxtermRecur (ddMgr, Nv, bddIds, cnfIds, fp, list,\n    clauseN, varMax);\n  list[index] = 2;\n\n  return;\n}\n\n/**Function********************************************************************\n \n  Synopsis    [Performs the recursive step of Print Best on Not Shared\n    sub-BDDs.]\n \n  Description [Performs the recursive step of Print Best on Not Shared\n    sub-BDDs, i.e., print out information for the nodes belonging to\n    BDDs not shared (whose root has just one incoming edge).\n    ]\n \n  SideEffects [None]\n\n  SeeAlso     []\n \n******************************************************************************/\n\nstatic int\nStoreCnfBestNotSharedRecur (\n  DdManager *ddMgr   /* IN: DD Manager */,\n  DdNode *node       /* IN: BDD to store */,\n  int idf            /* IN: Id to store */,\n  int *bddIds        /* IN: BDD identifiers */,\n  int *cnfIds        /* IN: corresponding CNF identifiers */,\n  FILE *fp           /* IN: file pointer */,\n  int *list          /* IN: temporary array to store cubes */,\n  int *clauseN      /* OUT: number of stored clauses */,\n  int *varMax       /* OUT: maximum identifier of the variables created */\n  )\n{\n  DdNode *N, *Nv, *Nnv;\n  int index, retValue;\n    \n  N = Cudd_Regular (node);\n\n  /*\n   *  Terminal case or Already Visited:\n   *    Print one cube based on the current recursion\n   */\n\n  if (cuddIsConstant (N)) {\n    retValue = printCubeCnf (ddMgr, node, cnfIds, fp, list, varMax);\n    if (retValue == DDDMP_SUCCESS) {\n      if (idf != 0) {\n         fprintf (fp, \"%d \", idf);\n      }\n      fprintf (fp, \"0\\n\");\n      *varMax = GET_MAX (*varMax, abs(idf));\n      *clauseN = *clauseN + 1;\n    }\n    return (DDDMP_SUCCESS);\n  }\n\n  /*\n   *  Shared Sub-Tree: Print Cube\n   */\n\n  index = DddmpReadNodeIndexCnf (N);\n  if (index > 0) {\n    if (idf != 0) {\n      fprintf (fp, \"%d \", idf);\n    }\n    if (Cudd_IsComplement (node)) {\n      retValue = fprintf (fp, \"-%d \", index);\n    } else {\n      retValue = fprintf (fp, \"%d \", index);\n    }\n    retValue = printCubeCnf (ddMgr, node, cnfIds, fp, list, varMax);\n    fprintf (fp, \"0\\n\");\n    *varMax = GET_MAX (*varMax, abs(index));\n    *clauseN = *clauseN + 1;\n    return (DDDMP_SUCCESS);\n  }\n\n  /*\n   *  NON Terminal case: Recur\n   */\n\n  Nv  = cuddT (N);\n  Nnv = cuddE (N);\n  if (Cudd_IsComplement (node)) {\n    Nv  = Cudd_Not (Nv);\n    Nnv = Cudd_Not (Nnv);\n  }\n  index = N->index;\n\n  /*\n   *  StQ 06.05.2003\n   *  Perform the optimization:\n   *  f = (a + b)' = (a') ^ (a + b') = (a') ^ (b')\n   *  i.e., if the THEN node is the constant ZERO then that variable\n   *  can be forgotten (list[index] = 2) for subsequent ELSE cubes\n   */\n  if (cuddIsConstant (Cudd_Regular (Nv)) &&  Nv != ddMgr->one) {\n    list[index] = 2;\n  } else {\n    list[index] = 0;\n  }\n  StoreCnfBestNotSharedRecur (ddMgr, Nnv, idf, bddIds, cnfIds, fp, list,\n    clauseN, varMax);\n\n  /*\n   *  StQ 06.05.2003\n   *  Perform the optimization:\n   *  f = a ^ b = (a) ^ (a' + b) = (a) ^ (b)\n   *  i.e., if the ELSE node is the constant ZERO then that variable\n   *  can be forgotten (list[index] = 2) for subsequent THEN cubes\n   */\n  if (cuddIsConstant (Cudd_Regular (Nnv)) &&  Nnv != ddMgr->one) {\n    list[index] = 2;\n  } else {\n    list[index] = 1;\n  }\n  StoreCnfBestNotSharedRecur (ddMgr, Nv, idf, bddIds, cnfIds, fp, list,\n    clauseN, varMax);\n  list[index] = 2;\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n \n  Synopsis    [Performs the recursive step of Print Best on Shared\n    sub-BDDs.\n    ]\n \n  Description [Performs the recursive step of Print Best on Not Shared\n    sub-BDDs, i.e., print out information for the nodes belonging to\n    BDDs not shared (whose root has just one incoming edge).\n    ]\n \n  SideEffects [None]\n\n  SeeAlso      []\n \n******************************************************************************/\n\nstatic int\nStoreCnfBestSharedRecur (\n  DdManager *ddMgr  /* IN: DD Manager */,\n  DdNode *node      /* IN: BDD to store */,\n  int *bddIds       /* IN: BDD identifiers */,\n  int *cnfIds       /* IN: corresponding CNF identifiers */,\n  FILE *fp          /* IN: file pointer */,\n  int *list         /* IN: temporary array to store cubes */,\n  int *clauseN     /* OUT: number of stored clauses */,\n  int *varMax      /* OUT: maximum identifier of the variables created */\n  )\n{\n  DdNode *nodeThen, *nodeElse;\n  int i, idf;\n\n  Dddmp_Assert (node==Cudd_Regular(node),\n    \"Inverted Edge during Shared Printing.\");\n\n  /* If constant, nothing to do. */\n  if (cuddIsConstant (node)) {\n    return (DDDMP_SUCCESS);\n  }\n\n  /* If already visited, nothing to do. */\n  if (DddmpVisitedCnf (node)) {\n    return (DDDMP_SUCCESS);\n  }\n\n  /*\n   *  Shared Sub-Tree: Print Cube\n   */\n\n  idf = DddmpReadNodeIndexCnf (node);\n  if (idf > 0) {\n    /* Cheat the Recur Function about the Index of the Current Node */\n    DddmpWriteNodeIndexCnf (node, 0);\n\n#if DDDMP_DEBUG_CNF\n    fprintf (fp, \"Else of XNOR\\n\");\n#endif\n    for (i=0; i<ddMgr->size; i++) {\n      list[i] = 2;\n    }\n    StoreCnfBestNotSharedRecur (ddMgr, Cudd_Not (node), idf, bddIds, cnfIds,\n      fp, list, clauseN, varMax);\n\n#if DDDMP_DEBUG_CNF\n    fprintf (fp, \"Then of XNOR\\n\");\n#endif\n    for (i=0; i<ddMgr->size; i++) {\n      list[i] = 2;\n    }\n    StoreCnfBestNotSharedRecur (ddMgr, node, -idf, bddIds, cnfIds,\n      fp, list, clauseN, varMax);\n\n    /* Set Back Index of Current Node */\n    DddmpWriteNodeIndexCnf (node, idf);\n  }\n\n  /* Mark node as visited. */\n  DddmpSetVisitedCnf (node);\n\n  /*\n   *  Recur\n   */\n\n  nodeThen  = cuddT (node);\n  nodeElse = cuddE (node);\n\n  StoreCnfBestSharedRecur (ddMgr, Cudd_Regular (nodeThen), bddIds, cnfIds,\n    fp, list, clauseN, varMax);\n  StoreCnfBestSharedRecur (ddMgr, Cudd_Regular (nodeElse), bddIds, cnfIds,\n    fp, list, clauseN, varMax);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n \n  Synopsis    [Print One Cube in CNF Format.]\n \n  Description [Print One Cube in CNF Format.\n    Return DDDMP_SUCCESS if something is printed out, DDDMP_FAILURE\n    is nothing is printed out.\n    ]\n \n  SideEffects [None]\n\n  SeeAlso      []\n \n******************************************************************************/\n\nstatic int\nprintCubeCnf (\n  DdManager *ddMgr /* IN: DD Manager */,\n  DdNode *node     /* IN: BDD to store */,\n  int *cnfIds      /* IN: CNF identifiers */,\n  FILE *fp         /* IN: file pointer */,\n  int *list        /* IN: temporary array to store cubes */,\n  int *varMax      /* OUT: maximum identifier of the variables created */\n  )\n{\n  int i, retValue;\n  DdNode *one;\n    \n  retValue = DDDMP_FAILURE;\n  one = ddMgr->one;\n\n  if (node != one) {\n    for (i=0; i<ddMgr->size; i++) {\n      if (list[i] == 0) {\n        retValue = DDDMP_SUCCESS;\n        (void) fprintf (fp, \"%d \", cnfIds[i]);\n\t*varMax = GET_MAX(*varMax, cnfIds[i]);\n      } else {\n        if (list[i] == 1) {\n          retValue = DDDMP_SUCCESS;\n          (void) fprintf (fp, \"-%d \", cnfIds[i]);\n  \t  *varMax = GET_MAX(*varMax, cnfIds[i]);\n        }\n      }\n    }\n  }\n\n  return (retValue);\n}\n\n\n\n\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpStoreMisc.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpStoreMisc.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Functions to write out bdds to file in prefixed\n    and in Blif form.]\n\n  Description  [Functions to write out bdds to file. \n    BDDs are represended on file in text format.\n    Each node is stored as a multiplexer in a prefix notation format for\n    the prefix notation file or in PLA format for the blif file.\n  ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int DddmpCuddDdArrayStorePrefix(DdManager *ddMgr, int n, DdNode **f, char **inputNames, char **outputNames, char *modelName, FILE *fp);\nstatic int DddmpCuddDdArrayStorePrefixBody(DdManager *ddMgr, int n, DdNode **f, char **inputNames, char **outputNames, FILE *fp);\nstatic int DddmpCuddDdArrayStorePrefixStep(DdManager * ddMgr, DdNode * f, FILE * fp, st_table * visited, char ** names);\nstatic int DddmpCuddDdArrayStoreBlif(DdManager *ddMgr, int n, DdNode **f, char **inputNames, char **outputNames, char *modelName, FILE *fp);\nstatic int DddmpCuddDdArrayStoreBlifBody(DdManager *ddMgr, int n, DdNode **f, char **inputNames, char **outputNames, FILE *fp);\nstatic int DddmpCuddDdArrayStoreBlifStep(DdManager *ddMgr, DdNode *f, FILE *fp, st_table *visited, char **names);\nstatic int DddmpCuddDdArrayStoreSmv(DdManager *ddMgr, int n, DdNode **f, char **inputNames, char **outputNames, char *modelName, FILE *fp);\nstatic int DddmpCuddDdArrayStoreSmvBody(DdManager *ddMgr, int n, DdNode **f, char **inputNames, char **outputNames, FILE *fp);\nstatic int DddmpCuddDdArrayStoreSmvStep(DdManager * ddMgr, DdNode * f, FILE * fp, st_table * visited, char ** names);\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument BDD in\n    a prefix notation.]\n\n  Description  [Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n    ]\n\n  SideEffects  []\n\n  SeeAlso      [Dddmp_cuddBddStore]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddStorePrefix (\n  DdManager *ddMgr     /* IN: DD Manager */,\n  int nRoots           /* IN: Number of BDD roots */,\n  DdNode *f            /* IN: BDD root to be stored */,\n  char **inputNames    /* IN: Array of variable names */,\n  char **outputNames   /* IN: Array of root names */,\n  char *modelName      /* IN: Model Name */,\n  char *fileName       /* IN: File name */,\n  FILE *fp             /* IN: File pointer to the store file */\n  )\n{\n  int retValue;\n  DdNode *tmpArray[1];\n  (void) nRoots; /* avoid warning */\n\n  tmpArray[0] = f;\n\n  retValue = Dddmp_cuddBddArrayStorePrefix (ddMgr, 1, tmpArray,\n    inputNames, outputNames, modelName, fileName, fp);\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument BDD in\n    a prefix notation.]\n\n  Description  [Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n    ]\n\n  SideEffects  []\n\n  SeeAlso      [Dddmp_cuddBddArrayStore]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddArrayStorePrefix (\n  DdManager *ddMgr       /* IN: DD Manager */,\n  int nroots             /* IN: number of output BDD roots to be stored */,\n  DdNode **f             /* IN: array of BDD roots to be stored */,\n  char **inputNames      /* IN: array of variable names (or NULL) */,\n  char **outputNames     /* IN: array of root names (or NULL) */,\n  char *modelName        /* IN: Model Name */,\n  char *fname            /* IN: File name */,\n  FILE *fp               /* IN: File pointer to the store file */\n  )\n{\n  int retValue;\n  int fileToClose = 0;\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValueBis;\n\n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  /* \n   *  Check if File needs to be opened in the proper mode.\n   */\n\n  if (fp == NULL) {\n    fp = fopen (fname, \"w\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  retValue = DddmpCuddDdArrayStorePrefix (ddMgr, nroots, f,\n    inputNames, outputNames, modelName, fp);\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  return (retValue);\n\n  failure:\n    return (DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument BDD in\n    a Blif/Exlif notation.]\n\n  Description  [Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStoreBlif.\n    A dummy array of 1 BDD root is used for this purpose.\n    ]\n\n  SideEffects  []\n\n  SeeAlso      [Dddmp_cuddBddStorePrefix]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddStoreBlif (\n  DdManager *ddMgr     /* IN: DD Manager */,\n  int nRoots           /* IN: Number of BDD roots */,\n  DdNode *f            /* IN: BDD root to be stored */,\n  char **inputNames    /* IN: Array of variable names */,\n  char **outputNames   /* IN: Array of root names */,\n  char *modelName      /* IN: Model Name */,\n  char *fileName       /* IN: File name */,\n  FILE *fp             /* IN: File pointer to the store file */\n  )\n{\n  int retValue;\n  DdNode *tmpArray[1];\n  (void) nRoots; /* avoid warning */\n\n  tmpArray[0] = f;\n\n  retValue = Dddmp_cuddBddArrayStoreBlif (ddMgr, 1, tmpArray,\n    inputNames, outputNames, modelName, fileName, fp);\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument BDD in\n    a Blif/Exlif notation.]\n\n  Description  [Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStoreBLif.\n    A dummy array of 1 BDD root is used for this purpose.\n    ]\n\n  SideEffects  []\n\n  SeeAlso      [Dddmp_cuddBddArrayStorePrefix]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddArrayStoreBlif (\n  DdManager *ddMgr       /* IN: DD Manager */,\n  int nroots             /* IN: number of output BDD roots to be stored */,\n  DdNode **f             /* IN: array of BDD roots to be stored */,\n  char **inputNames      /* IN: array of variable names (or NULL) */,\n  char **outputNames     /* IN: array of root names (or NULL) */,\n  char *modelName        /* IN: Model Name */,\n  char *fname            /* IN: File name */,\n  FILE *fp               /* IN: File pointer to the store file */\n  )\n{\n  int retValue;\n  int fileToClose = 0;\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValueBis;\n\n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  /* \n   *  Check if File needs to be opened in the proper mode.\n   */\n\n  if (fp == NULL) {\n    fp = fopen (fname, \"w\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  retValue = DddmpCuddDdArrayStoreBlif (ddMgr, nroots, f,\n    inputNames, outputNames, modelName, fp);\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  return (retValue);\n\n  failure:\n    return (DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument BDD in\n    a prefix notation.]\n\n  Description  [Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n    ]\n\n  SideEffects  []\n\n  SeeAlso      [Dddmp_cuddBddStore]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddStoreSmv (\n  DdManager *ddMgr     /* IN: DD Manager */,\n  int nRoots           /* IN: Number of BDD roots */,\n  DdNode *f            /* IN: BDD root to be stored */,\n  char **inputNames    /* IN: Array of variable names */,\n  char **outputNames   /* IN: Array of root names */,\n  char *modelName      /* IN: Model Name */,\n  char *fileName       /* IN: File name */,\n  FILE *fp             /* IN: File pointer to the store file */\n  )\n{\n  int retValue;\n  DdNode *tmpArray[1];\n  (void) nRoots; /* avoid warning */\n\n  tmpArray[0] = f;\n\n  retValue = Dddmp_cuddBddArrayStoreSmv (ddMgr, 1, tmpArray,\n    inputNames, outputNames, modelName, fileName, fp);\n\n  return (retValue);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Writes a dump file representing the argument BDD in\n    a prefix notation.]\n\n  Description  [Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n    ]\n\n  SideEffects  []\n\n  SeeAlso      [Dddmp_cuddBddArrayStore]\n\n******************************************************************************/\n\nint\nDddmp_cuddBddArrayStoreSmv (\n  DdManager *ddMgr       /* IN: DD Manager */,\n  int nroots             /* IN: number of output BDD roots to be stored */,\n  DdNode **f             /* IN: array of BDD roots to be stored */,\n  char **inputNames      /* IN: array of variable names (or NULL) */,\n  char **outputNames     /* IN: array of root names (or NULL) */,\n  char *modelName        /* IN: Model Name */,\n  char *fname            /* IN: File name */,\n  FILE *fp               /* IN: File pointer to the store file */\n  )\n{\n  int retValue;\n  int fileToClose = 0;\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  int retValueBis;\n\n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  /* \n   *  Check if File needs to be opened in the proper mode.\n   */\n\n  if (fp == NULL) {\n    fp = fopen (fname, \"w\");\n    Dddmp_CheckAndGotoLabel (fp==NULL, \"Error opening file.\",\n      failure);\n    fileToClose = 1;\n  }\n\n  retValue = DddmpCuddDdArrayStoreSmv (ddMgr, nroots, f,\n    inputNames, outputNames, modelName, fp);\n\n  if (fileToClose) {\n    fclose (fp);\n  }\n\n#ifdef DDDMP_DEBUG\n#ifndef __alpha__  \n  retValueBis = Cudd_DebugCheck (ddMgr);\n  if (retValueBis == 1) {\n    fprintf (stderr, \"Inconsistency Found During BDD Store.\\n\");\n    fflush (stderr);\n  } else {\n    if (retValueBis == CUDD_OUT_OF_MEM) {\n      fprintf (stderr, \"Out of Memory During BDD Store.\\n\");\n      fflush (stderr);\n    }\n  }\n#endif\n#endif\n\n  return (retValue);\n\n  failure:\n    return (DDDMP_FAILURE);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Internal function to writes a dump file representing the\n    argument BDD in a prefix notation.]\n\n  Description  [One multiplexer is written for each BDD node.\n    It returns 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n    system full, or an ADD with constants different from 0 and 1).\n    It does not close the file: This is the caller responsibility.\n    It uses a minimal unique subset of the hexadecimal address of a node as\n    name for it.\n    If the argument inputNames is non-null, it is assumed to hold the\n    pointers to the names of the inputs. Similarly for outputNames.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    Comments (COMMENT) are added at the beginning of the description to\n    describe inputs and outputs of the design.\n    A buffer (BUF) is add on the output to cope with complemented functions.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpCuddDdArrayStoreBlif]\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStorePrefix (\n  DdManager *ddMgr    /* IN: Manager */,\n  int n               /* IN: Number of output nodes to be dumped */,\n  DdNode **f          /* IN: Array of output nodes to be dumped */,\n  char **inputNames   /* IN: Array of input names (or NULL) */,\n  char **outputNames  /* IN: Array of output names (or NULL) */,\n  char *modelName     /* IN: Model name (or NULL) */,\n  FILE *fp            /* IN: Pointer to the dump file */\n  )\n{\n  DdNode *support = NULL;\n  DdNode *scan;\n  int *sorted = NULL;\n  int nVars = ddMgr->size;\n  int retValue;\n  int i;\n\n  /* Build a bit array with the support of f. */\n  sorted = ALLOC(int, nVars);\n  if (sorted == NULL) {\n    ddMgr->errorCode = CUDD_MEMORY_OUT;\n    Dddmp_CheckAndGotoLabel (1, \"Allocation Error.\", failure);\n  }\n  for (i = 0; i < nVars; i++) {\n    sorted[i] = 0;\n  }\n\n  /* Take the union of the supports of each output function. */\n  support = Cudd_VectorSupport(ddMgr,f,n);\n  Dddmp_CheckAndGotoLabel (support==NULL,\n    \"Error in function Cudd_VectorSupport.\", failure);\n  cuddRef(support);\n  scan = support;\n  while (!cuddIsConstant(scan)) {\n    sorted[scan->index] = 1;\n    scan = cuddT(scan);\n  }\n  Cudd_RecursiveDeref(ddMgr,support);\n  /* so that we do not try to free it in case of failure */\n  support = NULL;\n\n  /* Write the header (.model .inputs .outputs). */\n  if (modelName == NULL) {\n    retValue = fprintf (fp, \"(COMMENT - model name: Unknown )\\n\");\n  } else {\n    retValue = fprintf (fp, \"(COMMENT - model name: %s )\\n\", modelName);\n  }\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  retValue = fprintf(fp, \"(COMMENT - input names: \");\n  if (retValue == EOF) {\n    return(0);\n  }\n  /* Write the input list by scanning the support array. */\n  for (i = 0; i < nVars; i++) {\n    if (sorted[i]) {\n      if (inputNames == NULL) {\n\tretValue = fprintf(fp,\" inNode%d\", i);\n      } else {\n\tretValue = fprintf(fp,\" %s\", inputNames[i]);\n      }\n      Dddmp_CheckAndGotoLabel (retValue==EOF,\n        \"Error during file store.\", failure);\n    }\n  }\n  FREE(sorted);\n  sorted = NULL;\n  retValue = fprintf(fp, \" )\\n\");\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  /* Write the .output line. */\n  retValue = fprintf(fp,\"(COMMENT - output names: \");\n  if (retValue == EOF) {\n    return(0);\n  }\n  for (i = 0; i < n; i++) {\n    if (outputNames == NULL) {\n      retValue = fprintf (fp,\" outNode%d\", i);\n    } else {\n      retValue = fprintf (fp,\" %s\", outputNames[i]);\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF,\n      \"Error during file store.\", failure);\n  } \n  retValue = fprintf(fp, \" )\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF,\n    \"Error during file store.\", failure);\n\n  retValue = DddmpCuddDdArrayStorePrefixBody (ddMgr, n, f, inputNames,\n    outputNames, fp);\n  Dddmp_CheckAndGotoLabel (retValue==0,\n    \"Error in function DddmpCuddDdArrayStorePrefixBody.\", failure);\n\n  return(1);\n\nfailure:\n    if (sorted != NULL) {\n      FREE(sorted);\n    }\n    if (support != NULL) {\n      Cudd_RecursiveDeref(ddMgr,support);\n    }\n    return(0);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Internal function to writes a dump file representing the\n    argument BDD in a prefix notation. Writes the body of the file.]\n\n  Description  [One multiplexer is written for each BDD node.\n    It returns 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n    system full, or an ADD with constants different from 0 and 1).\n    It does not close the file: This is the caller responsibility.\n    It uses a minimal unique subset of the hexadecimal address of a node as\n    name for it.\n    If the argument inputNames is non-null, it is assumed to hold the\n    pointers to the names of the inputs. Similarly for outputNames.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpCuddDdArrayStoreBlif]\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStorePrefixBody (\n  DdManager *ddMgr      /* IN: Manager */,\n  int n                 /* IN: Number of output nodes to be dumped */,\n  DdNode **f            /* IN: Array of output nodes to be dumped */,\n  char **inputNames     /* IN: Array of input names (or NULL) */,\n  char **outputNames    /* IN: Array of output names (or NULL) */,\n  FILE *fp              /* IN: Pointer to the dump file */\n  )\n{\n  st_table *visited = NULL;\n  int retValue;\n  int i;\n\n  /* Initialize symbol table for visited nodes. */\n  visited = st_init_table(st_ptrcmp, st_ptrhash);\n  Dddmp_CheckAndGotoLabel (visited==NULL,\n    \"Error if function st_init_table.\", failure);\n\n  /* Call the function that really gets the job done. */\n  for (i = 0; i < n; i++) {\n    retValue = DddmpCuddDdArrayStorePrefixStep (ddMgr, Cudd_Regular(f[i]),\n      fp, visited, inputNames);\n    Dddmp_CheckAndGotoLabel (retValue==0,\n      \"Error if function DddmpCuddDdArrayStorePrefixStep.\", failure);\n  }\n\n  /* To account for the possible complement on the root,\n   ** we put either a buffer or an inverter at the output of\n   ** the multiplexer representing the top node.\n   */\n  for (i=0; i<n; i++) {\n    if (outputNames == NULL) {\n      retValue = fprintf (fp,  \"(BUF outNode%d \", i);\n    } else {\n      retValue = fprintf (fp,  \"(BUF %s \", outputNames[i]);\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF,\n      \"Error during file store.\", failure);\n\n    if (Cudd_IsComplement(f[i])) {\n      retValue = fprintf (fp, \"(NOT node%\" PRIxPTR \"))\\n\",\n        (ptruint) f[i] / sizeof(DdNode));\n    } else {\n      retValue = fprintf (fp, \"node%\" PRIxPTR \")\\n\",\n        (ptruint) f[i] / sizeof(DdNode));\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF,\n      \"Error during file store.\", failure);\n  }\n\n  st_free_table (visited);\n\n  return(1);\n\nfailure:\n    if (visited != NULL) st_free_table(visited);\n    return(0);\n\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Performs the recursive step of\n    DddmpCuddDdArrayStorePrefixBody.]\n\n  Description [Performs the recursive step of\n    DddmpCuddDdArrayStorePrefixBody.\n    Traverses the BDD f and writes a multiplexer-network description to the\n    file pointed by fp.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    f is assumed to be a regular pointer and the function guarantees this\n    assumption in the recursive calls.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStorePrefixStep (\n  DdManager * ddMgr,\n  DdNode * f,\n  FILE * fp,\n  st_table * visited,\n  char ** names\n  )\n{\n  DdNode *T, *E;\n  int retValue;\n\n#ifdef DDDMP_DEBUG\n  assert(!Cudd_IsComplement(f));\n#endif\n\n  /* If already visited, nothing to do. */\n  if (st_is_member(visited, (char *) f) == 1) {\n    return(1);\n  }\n\n  /* Check for abnormal condition that should never happen. */\n  if (f == NULL) {\n    return(0);\n  }\n\n  /* Mark node as visited. */\n  if (st_insert(visited, (char *) f, NULL) == ST_OUT_OF_MEM) {\n    return(0);\n  }\n\n  /* Check for special case: If constant node, generate constant 1. */\n  if (f == DD_ONE (ddMgr)) {\n    retValue = fprintf (fp, \"(OR node%\" PRIxPTR \" vss vdd)\\n\",\n      (ptruint) f / sizeof(DdNode));\n    if (retValue == EOF) {\n       return(0);\n    } else {\n       return(1);\n    }\n  }\n\n  /*\n   *  Check whether this is an ADD. We deal with 0-1 ADDs, but not\n   *  with the general case.\n   */\n\n  if (f == DD_ZERO(ddMgr)) {\n    retValue = fprintf (fp, \"(AND node%\" PRIxPTR \" vss vdd)\\n\",\n       (ptruint) f / sizeof(DdNode));\n   if (retValue == EOF) {\n     return(0);\n   } else {\n     return(1);\n   }\n  }\n\n  if (cuddIsConstant(f)) {\n    return(0);\n  }\n\n  /* Recursive calls. */\n  T = cuddT(f);\n  retValue = DddmpCuddDdArrayStorePrefixStep (ddMgr,T,fp,visited,names);\n  if (retValue != 1) {\n    return(retValue);\n  }\n  E = Cudd_Regular(cuddE(f));\n  retValue = DddmpCuddDdArrayStorePrefixStep (ddMgr,E,fp,visited,names);\n  if (retValue != 1) {\n    return(retValue);\n  }\n\n  /* Write multiplexer taking complement arc into account. */\n  retValue = fprintf (fp, \"(OR node%\" PRIxPTR \" (AND \",\n    (ptruint) f / sizeof(DdNode));\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  if (names != NULL) {\n    retValue = fprintf(fp, \"%s \", names[f->index]);\n  } else {\n    retValue = fprintf(fp, \"inNode%d \", f->index);\n  }\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  retValue = fprintf (fp, \"node%\" PRIxPTR \") (AND (NOT \",\n    (ptruint) T / sizeof(DdNode));\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  if (names != NULL) {\n    retValue = fprintf (fp, \"%s\", names[f->index]);\n  } else {\n    retValue = fprintf (fp, \"inNode%d\", f->index);\n  }\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  if (Cudd_IsComplement(cuddE(f))) {\n    retValue = fprintf (fp, \") (NOT node%\" PRIxPTR \")))\\n\",\n      (ptruint) E / sizeof(DdNode));\n  } else {\n    retValue = fprintf (fp, \") node%\" PRIxPTR \"))\\n\",\n      (ptruint) E / sizeof(DdNode));\n  }\n\n  if (retValue == EOF) {\n    return(0);\n  } else {\n    return(1);\n  }\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Writes a blif file representing the argument BDDs.]\n\n  Description [Writes a blif file representing the argument BDDs as a\n    network of multiplexers. One multiplexer is written for each BDD\n    node. It returns 1 in case of success; 0 otherwise (e.g.,\n    out-of-memory, file system full, or an ADD with constants different\n    from 0 and 1).\n    DddmpCuddDdArrayStoreBlif does not close the file: This is the\n    caller responsibility.\n    DddmpCuddDdArrayStoreBlif uses a minimal unique subset of\n    the hexadecimal address of a node as name for it.  If the argument\n    inames is non-null, it is assumed to hold the pointers to the names\n    of the inputs. Similarly for outputNames.\n    It prefixes the string \"NODE\" to each nome to have \"regular\" names\n    for each elements.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpCuddDdArrayStoreBlifBody,Cudd_DumpBlif]\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStoreBlif (\n  DdManager *ddMgr    /* IN: Manager */,\n  int n               /* IN: Number of output nodes to be dumped */,\n  DdNode **f          /* IN: Array of output nodes to be dumped */,\n  char **inputNames   /* IN: Array of input names (or NULL) */,\n  char **outputNames  /* IN: Array of output names (or NULL) */,\n  char *modelName     /* IN: Model name (or NULL) */,\n  FILE *fp            /* IN: Pointer to the dump file */\n  )\n{\n  DdNode *support = NULL;\n  DdNode *scan;\n  int *sorted = NULL;\n  int nVars = ddMgr->size;\n  int retValue;\n  int i;\n\n  /* Build a bit array with the support of f. */\n  sorted = ALLOC (int, nVars);\n  if (sorted == NULL) {\n    ddMgr->errorCode = CUDD_MEMORY_OUT;\n    Dddmp_CheckAndGotoLabel (1, \"Allocation Error.\", failure);\n  }\n  for (i = 0; i < nVars; i++) {\n    sorted[i] = 0;\n  }\n\n  /* Take the union of the supports of each output function. */\n  support = Cudd_VectorSupport(ddMgr,f,n);\n  Dddmp_CheckAndGotoLabel (support==NULL,\n    \"Error in function Cudd_VectorSupport.\", failure);\n  cuddRef(support);\n  scan = support;\n  while (!cuddIsConstant(scan)) {\n    sorted[scan->index] = 1;\n    scan = cuddT(scan);\n  }\n  Cudd_RecursiveDeref(ddMgr,support);\n  support = NULL;\n  /* so that we do not try to free it in case of failure */\n\n  /* Write the header (.model .inputs .outputs). */\n  if (modelName == NULL) {\n    retValue = fprintf(fp,\".model DD\\n.inputs\");\n  } else {\n    retValue = fprintf(fp,\".model %s\\n.inputs\", modelName);\n  }\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  /* Write the input list by scanning the support array. */\n  for (i = 0; i < nVars; i++) {\n    if (sorted[i]) {\n      if (inputNames == NULL || (inputNames[i] == NULL)) {\n\tretValue = fprintf(fp,\" inNode%d\", i);\n      } else {\n\tretValue = fprintf(fp,\" %s\", inputNames[i]);\n      }\n      Dddmp_CheckAndGotoLabel (retValue==EOF,\n        \"Error during file store.\", failure);\n    }\n  }\n  FREE(sorted);\n  sorted = NULL;\n\n  /* Write the .output line. */\n  retValue = fprintf(fp,\"\\n.outputs\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF,\n    \"Error during file store.\", failure);\n  for (i = 0; i < n; i++) {\n    if (outputNames == NULL || (outputNames[i] == NULL)) {\n      retValue = fprintf(fp,\" outNode%d\", i);\n    } else {\n      retValue = fprintf(fp,\" %s\", outputNames[i]);\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF,\n      \"Error during file store.\", failure);\n  }\n  retValue = fprintf(fp,\"\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF,\n    \"Error during file store.\", failure);\n\n  retValue = DddmpCuddDdArrayStoreBlifBody(ddMgr, n, f, inputNames,\n    outputNames, fp);\n  Dddmp_CheckAndGotoLabel (retValue==0,\n    \"Error if function DddmpCuddDdArrayStoreBlifBody.\", failure);\n\n  /* Write trailer and return. */\n  retValue = fprintf (fp, \".end\\n\");\n  Dddmp_CheckAndGotoLabel (retValue==EOF,\n    \"Error during file store.\", failure);\n\n  return(1);\n\nfailure:\n  if (sorted != NULL) {\n    FREE(sorted);\n  }\n  if (support != NULL) {\n    Cudd_RecursiveDeref(ddMgr,support);\n  }\n\n  return(0);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis    [Writes a blif body representing the argument BDDs.]\n\n  Description [Writes a blif body representing the argument BDDs as a\n    network of multiplexers. One multiplexer is written for each BDD\n    node. It returns 1 in case of success; 0 otherwise (e.g.,\n    out-of-memory, file system full, or an ADD with constants different\n    from 0 and 1).\n    DddmpCuddDdArrayStoreBlif does not close the file: This is the\n    caller responsibility.\n    DddmpCuddDdArrayStoreBlif uses a minimal unique subset of\n    the hexadecimal address of a node as name for it.  If the argument\n    inputNames is non-null, it is assumed to hold the pointers to the names\n    of the inputs. Similarly for outputNames. This function prints out only\n    .names part.\n  ]\n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStoreBlifBody (\n  DdManager *ddMgr      /* IN: Manager */,\n  int n                 /* IN: Number of output nodes to be dumped */,\n  DdNode **f            /* IN: Array of output nodes to be dumped */,\n  char **inputNames     /* IN: Array of input names (or NULL) */,\n  char **outputNames    /* IN: Array of output names (or NULL) */,\n  FILE *fp              /* IN: Pointer to the dump file */\n  )\n{\n  st_table *visited = NULL;\n  int retValue;\n  int i;\n\n  /* Initialize symbol table for visited nodes. */\n  visited = st_init_table(st_ptrcmp, st_ptrhash);\n  Dddmp_CheckAndGotoLabel (visited==NULL,\n    \"Error if function st_init_table.\", failure);\n\n  /* Call the function that really gets the job done. */\n  for (i = 0; i < n; i++) {\n    retValue = DddmpCuddDdArrayStoreBlifStep (ddMgr, Cudd_Regular(f[i]),\n      fp, visited, inputNames);\n    Dddmp_CheckAndGotoLabel (retValue==0,\n      \"Error if function DddmpCuddDdArrayStoreBlifStep.\", failure);\n  }\n\n  /*\n   *  To account for the possible complement on the root,\n   *  we put either a buffer or an inverter at the output of\n   *  the multiplexer representing the top node.\n   */\n\n  for (i = 0; i < n; i++) {\n    if (outputNames == NULL) {\n      retValue = fprintf(fp, \".names node%\" PRIxPTR \" outNode%d\\n\",\n        (ptruint) f[i] / sizeof(DdNode), i);\n    } else {\n      retValue = fprintf(fp, \".names node%\" PRIxPTR \" %s\\n\",\n        (ptruint) f[i] / sizeof(DdNode), outputNames[i]);\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF,\n      \"Error during file store.\", failure);\n    if (Cudd_IsComplement(f[i])) {\n      retValue = fprintf(fp,\"0 1\\n\");\n    } else {\n      retValue = fprintf(fp,\"1 1\\n\");\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF,\n      \"Error during file store.\", failure);\n  }\n\n  st_free_table(visited);\n  return(1);\n\nfailure:\n  if (visited != NULL) {\n    st_free_table(visited);\n  }\n  return(0);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Performs the recursive step of DddmpCuddDdArrayStoreBlif.]\n\n  Description [Performs the recursive step of DddmpCuddDdArrayStoreBlif.\n    Traverses the BDD f and writes a multiplexer-network description to\n    the file pointed by fp in blif format.\n    f is assumed to be a regular pointer and DddmpCuddDdArrayStoreBlifStep\n    guarantees this assumption in the recursive calls.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStoreBlifStep (\n  DdManager *ddMgr,\n  DdNode *f,\n  FILE *fp,\n  st_table *visited,\n  char **names\n  )\n{\n  DdNode *T, *E;\n  int retValue;\n\n#ifdef DDDMP_DEBUG\n  assert(!Cudd_IsComplement(f));\n#endif\n\n  /* If already visited, nothing to do. */\n  if (st_is_member(visited, (char *) f) == 1) {\n    return(1);\n  }\n\n  /* Check for abnormal condition that should never happen. */\n  if (f == NULL) {\n    return(0);\n  }\n\n  /* Mark node as visited. */\n  if (st_insert(visited, (char *) f, NULL) == ST_OUT_OF_MEM) {\n    return(0);\n  }\n\n  /* Check for special case: If constant node, generate constant 1. */\n  if (f == DD_ONE(ddMgr)) {\n    retValue = fprintf(fp, \".names node%\" PRIxPTR \"\\n1\\n\",\n      (ptruint) f / sizeof(DdNode));\n     if (retValue == EOF) {\n       return(0);\n     } else {\n       return(1);\n    }\n  }\n\n  /* Check whether this is an ADD. We deal with 0-1 ADDs, but not\n  ** with the general case.\n  */\n  if (f == DD_ZERO(ddMgr)) {\n    retValue = fprintf(fp, \".names node%\" PRIxPTR \"\\n\",\n      (ptruint) f / sizeof(DdNode));\n    if (retValue == EOF) {\n      return(0);\n    } else {\n      return(1);\n    }\n  }\n  if (cuddIsConstant(f)) {\n    return(0);\n  }\n\n  /* Recursive calls. */\n  T = cuddT(f);\n  retValue = DddmpCuddDdArrayStoreBlifStep(ddMgr,T,fp,visited,names);\n  if (retValue != 1) return(retValue);\n  E = Cudd_Regular(cuddE(f));\n  retValue = DddmpCuddDdArrayStoreBlifStep(ddMgr,E,fp,visited,names);\n  if (retValue != 1) return(retValue);\n\n  /* Write multiplexer taking complement arc into account. */\n  if (names != NULL) {\n    retValue = fprintf(fp,\".names %s\", names[f->index]);\n  } else {\n    retValue = fprintf(fp,\".names inNode%d\", f->index);\n  }\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  if (Cudd_IsComplement(cuddE(f))) {\n    retValue = fprintf(fp,\n      \" node%\" PRIxPTR \" node%\" PRIxPTR \" node%\" PRIxPTR \"\\n11- 1\\n0-0 1\\n\",\n      (ptruint) T / sizeof(DdNode),\n      (ptruint) E / sizeof(DdNode),\n      (ptruint) f / sizeof(DdNode));\n  } else {\n    retValue = fprintf(fp,\n      \" node%\" PRIxPTR \" node%\" PRIxPTR \" node%\" PRIxPTR \"\\n11- 1\\n0-1 1\\n\",\n      (ptruint) T / sizeof(DdNode),\n      (ptruint) E / sizeof(DdNode),\n      (ptruint) f / sizeof(DdNode));\n  }\n  if (retValue == EOF) {\n    return(0);\n  } else {\n    return(1);\n  }\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Internal function to writes a dump file representing the\n    argument BDD in a SMV notation.]\n\n  Description  [One multiplexer is written for each BDD node.\n    It returns 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n    system full, or an ADD with constants different from 0 and 1).\n    It does not close the file: This is the caller responsibility.\n    It uses a minimal unique subset of the hexadecimal address of a node as\n    name for it.\n    If the argument inputNames is non-null, it is assumed to hold the\n    pointers to the names of the inputs. Similarly for outputNames.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    Comments (COMMENT) are added at the beginning of the description to\n    describe inputs and outputs of the design.\n    A buffer (BUF) is add on the output to cope with complemented functions.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpCuddDdArrayStoreBlif]\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStoreSmv (\n  DdManager *ddMgr    /* IN: Manager */,\n  int n               /* IN: Number of output nodes to be dumped */,\n  DdNode **f          /* IN: Array of output nodes to be dumped */,\n  char **inputNames   /* IN: Array of input names (or NULL) */,\n  char **outputNames  /* IN: Array of output names (or NULL) */,\n  char *modelName     /* IN: Model name (or NULL) */,\n  FILE *fp            /* IN: Pointer to the dump file */\n  )\n{\n  DdNode *support = NULL;\n  DdNode *scan;\n  int *sorted = NULL;\n  int nVars = ddMgr->size;\n  int retValue;\n  int i;\n\n  /* Build a bit array with the support of f. */\n  sorted = ALLOC(int, nVars);\n  if (sorted == NULL) {\n    ddMgr->errorCode = CUDD_MEMORY_OUT;\n    Dddmp_CheckAndGotoLabel (1, \"Allocation Error.\", failure);\n  }\n  for (i = 0; i < nVars; i++) {\n    sorted[i] = 0;\n  }\n\n  /* Take the union of the supports of each output function. */\n  support = Cudd_VectorSupport(ddMgr,f,n);\n  Dddmp_CheckAndGotoLabel (support==NULL,\n    \"Error in function Cudd_VectorSupport.\", failure);\n  cuddRef(support);\n  scan = support;\n  while (!cuddIsConstant(scan)) {\n    sorted[scan->index] = 1;\n    scan = cuddT(scan);\n  }\n  Cudd_RecursiveDeref(ddMgr,support);\n  /* so that we do not try to free it in case of failure */\n  support = NULL;\n\n  /* Write the header */\n  if (modelName == NULL) {\n    retValue = fprintf (fp, \"MODULE main -- Unknown\\n\");\n  } else {\n    retValue = fprintf (fp, \"MODULE main -- %s\\n\", modelName);\n  }\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  retValue = fprintf(fp, \"IVAR\\n\");\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  /* Write the input list by scanning the support array. */\n  for (i=0; i<nVars; i++) {\n    if (sorted[i]) {\n      if (inputNames == NULL) {\n\tretValue = fprintf (fp, \" inNode%d : boolean;\\n\", i);\n      } else {\n\tretValue = fprintf (fp, \" %s : boolean;\\n\", inputNames[i]);\n      }\n      Dddmp_CheckAndGotoLabel (retValue==EOF,\n        \"Error during file store.\", failure);\n    }\n  }\n  FREE(sorted);\n  sorted = NULL;\n\n  retValue = fprintf (fp, \"\\nDEFINE\\n\");\n\n  retValue = DddmpCuddDdArrayStoreSmvBody (ddMgr, n, f, inputNames,\n    outputNames, fp);\n  Dddmp_CheckAndGotoLabel (retValue==0,\n    \"Error in function DddmpCuddDdArrayStoreSmvBody.\", failure);\n\n  return(1);\n\nfailure:\n    if (sorted != NULL) {\n      FREE(sorted);\n    }\n    if (support != NULL) {\n      Cudd_RecursiveDeref(ddMgr,support);\n    }\n    return(0);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Internal function to writes a dump file representing the\n    argument BDD in a SMV notation. Writes the body of the file.]\n\n  Description  [One multiplexer is written for each BDD node.\n    It returns 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n    system full, or an ADD with constants different from 0 and 1).\n    It does not close the file: This is the caller responsibility.\n    It uses a minimal unique subset of the hexadecimal address of a node as\n    name for it.\n    If the argument inputNames is non-null, it is assumed to hold the\n    pointers to the names of the inputs. Similarly for outputNames.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     [DddmpCuddDdArrayStoreBlif]\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStoreSmvBody (\n  DdManager *ddMgr      /* IN: Manager */,\n  int n                 /* IN: Number of output nodes to be dumped */,\n  DdNode **f            /* IN: Array of output nodes to be dumped */,\n  char **inputNames     /* IN: Array of input names (or NULL) */,\n  char **outputNames    /* IN: Array of output names (or NULL) */,\n  FILE *fp              /* IN: Pointer to the dump file */\n  )\n{\n  st_table *visited = NULL;\n  int retValue;\n  int i;\n\n  /* Initialize symbol table for visited nodes. */\n  visited = st_init_table(st_ptrcmp, st_ptrhash);\n  Dddmp_CheckAndGotoLabel (visited==NULL,\n    \"Error if function st_init_table.\", failure);\n\n  /* Call the function that really gets the job done. */\n  for (i = 0; i < n; i++) {\n    retValue = DddmpCuddDdArrayStoreSmvStep (ddMgr, Cudd_Regular(f[i]),\n      fp, visited, inputNames);\n    Dddmp_CheckAndGotoLabel (retValue==0,\n      \"Error if function DddmpCuddDdArrayStoreSmvStep.\", failure);\n  }\n\n  /*\n   *  To account for the possible complement on the root,\n   *  we put either a buffer or an inverter at the output of\n   *  the multiplexer representing the top node.\n   */\n\n  for (i=0; i<n; i++) {\n    if (outputNames == NULL) {\n      retValue = fprintf (fp,  \"outNode%d := \", i);\n    } else {\n      retValue = fprintf (fp,  \"%s := \", outputNames[i]);\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF,\n      \"Error during file store.\", failure);\n\n    if (Cudd_IsComplement(f[i])) {\n      retValue = fprintf (fp, \"!node%\" PRIxPTR \"\\n\",\n        (ptruint) f[i] / sizeof(DdNode));\n    } else {\n      retValue = fprintf (fp, \"node%\" PRIxPTR \"\\n\",\n        (ptruint) f[i] / sizeof(DdNode));\n    }\n    Dddmp_CheckAndGotoLabel (retValue==EOF,\n      \"Error during file store.\", failure);\n  }\n\n  st_free_table (visited);\n\n  return(1);\n\nfailure:\n    if (visited != NULL) st_free_table(visited);\n    return(0);\n\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Performs the recursive step of\n    DddmpCuddDdArrayStoreSmvBody.]\n\n  Description [Performs the recursive step of\n    DddmpCuddDdArrayStoreSmvBody.\n    Traverses the BDD f and writes a multiplexer-network description to the\n    file pointed by fp.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    f is assumed to be a regular pointer and the function guarantees this\n    assumption in the recursive calls.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nstatic int\nDddmpCuddDdArrayStoreSmvStep (\n  DdManager * ddMgr,\n  DdNode * f,\n  FILE * fp,\n  st_table * visited,\n  char ** names\n  )\n{\n  DdNode *T, *E;\n  int retValue;\n\n#ifdef DDDMP_DEBUG\n  assert(!Cudd_IsComplement(f));\n#endif\n\n  /* If already visited, nothing to do. */\n  if (st_is_member(visited, (char *) f) == 1) {\n    return(1);\n  }\n\n  /* Check for abnormal condition that should never happen. */\n  if (f == NULL) {\n    return(0);\n  }\n\n  /* Mark node as visited. */\n  if (st_insert(visited, (char *) f, NULL) == ST_OUT_OF_MEM) {\n    return(0);\n  }\n\n  /* Check for special case: If constant node, generate constant 1. */\n  if (f == DD_ONE (ddMgr)) {\n    retValue = fprintf (fp, \"node%\" PRIxPTR \" := 1;\\n\",\n      (ptruint) f / sizeof(DdNode));\n    if (retValue == EOF) {\n       return(0);\n    } else {\n       return(1);\n    }\n  }\n\n  /*\n   *  Check whether this is an ADD. We deal with 0-1 ADDs, but not\n   *  with the general case.\n   */\n\n  if (f == DD_ZERO(ddMgr)) {\n    retValue = fprintf (fp, \"node%\" PRIxPTR \" := 0;\\n\",\n       (ptruint) f / sizeof(DdNode));\n   if (retValue == EOF) {\n     return(0);\n   } else {\n     return(1);\n   }\n  }\n\n  if (cuddIsConstant(f)) {\n    return(0);\n  }\n\n  /* Recursive calls. */\n  T = cuddT(f);\n  retValue = DddmpCuddDdArrayStoreSmvStep (ddMgr,T,fp,visited,names);\n  if (retValue != 1) {\n    return(retValue);\n  }\n  E = Cudd_Regular(cuddE(f));\n  retValue = DddmpCuddDdArrayStoreSmvStep (ddMgr,E,fp,visited,names);\n  if (retValue != 1) {\n    return(retValue);\n  }\n\n  /* Write multiplexer taking complement arc into account. */\n  retValue = fprintf (fp, \"node%\" PRIxPTR \" := \",\n    (ptruint) f / sizeof(DdNode));\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  if (names != NULL) {\n    retValue = fprintf(fp, \"%s \", names[f->index]);\n  } else {\n    retValue = fprintf(fp, \"inNode%d \", f->index);\n  }\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  retValue = fprintf (fp, \"& node%\" PRIxPTR \" | \",\n    (ptruint) T / sizeof(DdNode));\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  if (names != NULL) {\n    retValue = fprintf (fp, \"!%s \", names[f->index]);\n  } else {\n    retValue = fprintf (fp, \"!inNode%d \", f->index);\n  }\n  if (retValue == EOF) {\n    return(0);\n  }\n\n  if (Cudd_IsComplement(cuddE(f))) {\n    retValue = fprintf (fp, \"& !node%\" PRIxPTR \"\\n\",\n      (ptruint) E / sizeof(DdNode));\n  } else {\n    retValue = fprintf (fp, \"& node%\" PRIxPTR \"\\n\",\n      (ptruint) E / sizeof(DdNode));\n  }\n\n  if (retValue == EOF) {\n    return(0);\n  } else {\n    return(1);\n  }\n}\n\n"
  },
  {
    "path": "cudd/dddmp/dddmpUtil.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [dddmpUtil.c]\n\n  PackageName  [dddmp]\n\n  Synopsis     [Util Functions for the dddmp package]\n\n  Description  [Functions to manipulate arrays.]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n\n/**AutomaticEnd***************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis    [String compare for qsort]\n\n  Description [String compare for qsort]\n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nint\nQsortStrcmp(\n  const void *ps1   /* IN: pointer to the first string */,\n  const void *ps2   /* IN: pointer to the second string */\n  )\n{\n  return (strcmp (*((char**)ps1),*((char **)ps2)));\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Performs binary search of a name within a sorted array]\n\n  Description [Binary search of a name within a sorted array of strings.\n    Used when matching names of variables.\n    ]\n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nint\nFindVarname (\n  char *name   /* IN: name to look for */,\n  char **array /* IN: search array */,\n  int n        /* IN: size of the array */\n  )\n{\n  int d, m, u, t;\n\n  d = 0; u = n-1;\n\n  while (u>=d) {\n    m = (u+d)/2;\n    t=strcmp(name,array[m]);\n    if (t==0)\n      return m;\n    if (t<0)\n      u=m-1;\n    else\n      d=m+1;\n  }\n\n  return (-1);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis    [Duplicates a string]\n\n  Description [Allocates memory and copies source string] \n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nchar *\nDddmpStrDup (\n  char *str   /* IN: string to be duplicated */\n  )\n{\n  char *str2;\n\n  str2 = DDDMP_ALLOC(char,strlen(str)+1);\n  if (str2 != NULL) {\n    strcpy (str2,str);\n  }\n\n  return (str2);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Duplicates an array of strings]\n\n  Description [Allocates memory and copies source array] \n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nchar **\nDddmpStrArrayDup (\n  char **array    /* IN: array of strings to be duplicated */,\n  int n           /* IN: size of the array */\n  )\n{\n  char **array2;\n  int i;\n\n  array2 = DDDMP_ALLOC(char *, n);\n  if (array2 == NULL) {\n    (void) fprintf (stderr, \"DddmpStrArrayDup: Error allocating memory\\n\");\n    fflush (stderr);\n    return NULL;\n  }\n\n  /*\n   * initialize all slots to NULL for fair FREEing in case of failure\n   */\n\n  for (i=0; i<n; i++) {\n    array2[i] = NULL;\n  }\n\n  for (i=0; i<n; i++) { \n    if (array[i] != NULL) {\n      if ((array2[i]=DddmpStrDup(array[i]))==NULL) {\n        DddmpStrArrayFree (array2, n);\n        return (NULL);\n      }\n    }\n  }\n\n  return (array2);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Inputs an array of strings]\n\n  Description [Allocates memory and inputs source array] \n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nchar **\nDddmpStrArrayRead (\n  FILE *fp         /* IN: input file */,\n  int n            /* IN: size of the array */\n  )\n{\n  char buf[DDDMP_MAXSTRLEN];\n  char **array;\n  int i;\n\n  assert(fp!=NULL);\n\n  array = DDDMP_ALLOC(char *, n);\n  if (array == NULL) {\n    (void) fprintf (stderr, \"DddmpStrArrayRead: Error allocating memory\\n\");\n    fflush (stderr);\n    return NULL;\n  }\n\n  /*\n   * initialize all slots to NULL for fair FREEing in case of failure\n   */\n  for (i=0; i<n; i++) \n    array[i] = NULL;\n\n  for (i=0; i < n; i++) { \n    if (fscanf (fp, \"%s\", buf)==EOF) {\n      fprintf (stderr, \"DddmpStrArrayRead: Error reading file - EOF found\\n\");\n      fflush (stderr);\n      DddmpStrArrayFree (array, n);\n      return (NULL);\n    }\n    if ((array[i]=DddmpStrDup(buf))==NULL) {\n      DddmpStrArrayFree (array, n);\n      return (NULL);\n    }\n  }\n\n  return (array);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Outputs an array of strings]\n\n  Description [Outputs an array of strings to a specified file] \n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nint\nDddmpStrArrayWrite (\n  FILE *fp          /* IN: output file */,\n  char **array      /* IN: array of strings */,\n  int n             /* IN: size of the array */\n  )\n{\n  int i;\n\n  assert(fp!=NULL);\n\n  for (i=0; i<n; i++) { \n    if (fprintf (fp, \" %s\", array[i]) == EOF) {\n      fprintf (stderr, \"DddmpStrArrayWrite: Error writing to file\\n\");\n      fflush (stderr);\n      return (EOF);\n    }\n  }\n\n  return (n);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis    [Frees an array of strings]\n\n  Description [Frees memory for strings and the array of pointers] \n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nvoid\nDddmpStrArrayFree (\n  char **array      /* IN: array of strings */,\n  int n             /* IN: size of the array */\n  )\n{\n  int i;\n\n  if (array == NULL) {\n    return;\n  }\n\n  for (i=0; i<n; i++) {\n    DDDMP_FREE (array[i]);\n  }\n\n  DDDMP_FREE (array);\n\n  return;\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Duplicates an array of ints]\n\n  Description [Allocates memory and copies source array] \n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nint *\nDddmpIntArrayDup (\n  int *array      /* IN: array of ints to be duplicated */,\n  int n           /* IN: size of the array */\n  )\n{\n  int *array2;\n  int i;\n\n  array2 = DDDMP_ALLOC(int, n);\n  if (array2 == NULL) {\n    (void) fprintf (stderr, \"DddmpIntArrayDup: Error allocating memory\\n\");\n    fflush (stderr);\n    return (NULL);\n  }\n\n  for (i=0; i<n; i++) { \n    array2[i] = array[i];\n  }\n\n  return (array2);\n}\n\n\n/**Function********************************************************************\n\n  Synopsis    [Inputs an array of ints]\n\n  Description [Allocates memory and inputs source array] \n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nint *\nDddmpIntArrayRead (\n  FILE *fp          /* IN: input file */,\n  int n             /* IN: size of the array */\n  )\n{\n  int *array;\n  int i;\n\n  assert(fp!=NULL);\n\n  array = DDDMP_ALLOC(int, n);\n  if (array == NULL) {\n    (void) fprintf (stderr, \"DddmpIntArrayRead: Error allocating memory\\n\");\n    fflush (stderr);\n    return NULL;\n  }\n\n  for (i=0; i < n; i++) { \n    if (fscanf (fp, \"%d\", &array[i])==EOF) {\n      (void) fprintf (stderr,\n        \"DddmpIntArrayRead: Error reading file - EOF found\\n\");\n      fflush (stderr);\n      DDDMP_FREE (array);\n      return (NULL);\n    }\n  }\n\n  return (array);\n}\n\n/**Function********************************************************************\n\n  Synopsis    [Outputs an array of ints]\n\n  Description [Outputs an array of ints to a specified file]\n\n  SideEffects [None]\n\n  SeeAlso     []\n\n******************************************************************************/\n\nint\nDddmpIntArrayWrite (\n  FILE *fp          /* IN: output file */,\n  int  *array       /* IN: array of ints */,\n  int n              /* IN: size of the array */\n  )\n{\n  int i;\n\n  assert(fp!=NULL);\n\n  for (i=0; i<n; i++) { \n    if (fprintf (fp, \" %d\", array[i]) == EOF) {\n      (void) fprintf (stderr, \"DddmpIntArrayWrite: Error writing to file\\n\");\n      fflush (stderr);\n      return EOF;\n    }\n  }\n\n  return (n);\n}\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n"
  },
  {
    "path": "cudd/dddmp/doc/cmdIndex.html",
    "content": "<HTML>\n<HEAD><TITLE>Command Documentation</TITLE></HEAD>\n<BODY>\n\n<H1>Command Documentation</H1><HR><DL>\n</DL>\n<HR>\nLast updated on 1040218 17h15\n</BODY></HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/commands.html",
    "content": "<HTML>\n<HEAD><TITLE>Command Documentation</TITLE></HEAD>\n\n<FRAMESET ROWS=\"95%,5%\">\n  <FRAMESET COLS=\"40%,60%\">\n    <FRAME SRC=\"cmdIndex.html\">\n    <FRAME SRC=\"credit.html\" NAME=\"MAIN\">\n  </FRAMESET>\n  <FRAME SRC=\"credit.html\">\n</FRAMESET>\n\n</HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/credit.html",
    "content": "<HTML>\n<HEAD><TITLE>Credit</TITLE></HEAD>\n<BODY>\n<TABLE BORDER WIDTH=\"100%\">\n  <TR>\n    <TD ALIGN=center> <A HREF=\"commands.html\" TARGET=\"_top\">\n        Command Documentation</A> </TD>\n    <TD ALIGN=center> <A HREF=\"packages.html\" TARGET=\"_top\">\n\tPackage Documentation</A> </TD>\n    <TD ALIGN=center> Generated by <A HREF=\"http://www.eecs.berkeley.edu/~sedwards/ext\" TARGET=\"_top\">\n        <B>the Ext system</B></A> </TD>\n  </TD>\n</TABLE>\n</BODY>\n</HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmp-2.0-A4.ps",
    "content": "%!PS-Adobe-2.0\n%%Creator: dvips(k) 5.86 Copyright 1999 Radical Eye Software\n%%Title: dddmp-2.0.dvi\n%%Pages: 10\n%%PageOrder: Ascend\n%%BoundingBox: 0 0 596 842\n%%DocumentFonts: Times-Bold Times-Roman Courier Times-Italic Helvetica\n%%DocumentPaperSizes: a4\n%%EndComments\n%DVIPSWebPage: (www.radicaleye.com)\n%DVIPSCommandLine: dvips -t a4 -f dddmp-2.0\n%DVIPSParameters: dpi=600, compressed\n%DVIPSSource:  TeX output 2002.12.11:0557\n%%BeginProcSet: texc.pro\n%!\n/TeXDict 300 dict def TeXDict begin/N{def}def/B{bind def}N/S{exch}N/X{S\nN}B/A{dup}B/TR{translate}N/isls false N/vsize 11 72 mul N/hsize 8.5 72\nmul N/landplus90{false}def/@rigin{isls{[0 landplus90{1 -1}{-1 1}ifelse 0\n0 0]concat}if 72 Resolution div 72 VResolution div neg scale isls{\nlandplus90{VResolution 72 div vsize mul 0 exch}{Resolution -72 div hsize\nmul 0}ifelse TR}if Resolution VResolution vsize -72 div 1 add mul TR[\nmatrix currentmatrix{A A round sub abs 0.00001 lt{round}if}forall round\nexch round exch]setmatrix}N/@landscape{/isls true N}B/@manualfeed{\nstatusdict/manualfeed true put}B/@copies{/#copies X}B/FMat[1 0 0 -1 0 0]\nN/FBB[0 0 0 0]N/nn 0 N/IEn 0 N/ctr 0 N/df-tail{/nn 8 dict N nn begin\n/FontType 3 N/FontMatrix fntrx N/FontBBox FBB N string/base X array\n/BitMaps X/BuildChar{CharBuilder}N/Encoding IEn N end A{/foo setfont}2\narray copy cvx N load 0 nn put/ctr 0 N[}B/sf 0 N/df{/sf 1 N/fntrx FMat N\ndf-tail}B/dfs{div/sf X/fntrx[sf 0 0 sf neg 0 0]N df-tail}B/E{pop nn A\ndefinefont setfont}B/Cw{Cd A length 5 sub get}B/Ch{Cd A length 4 sub get\n}B/Cx{128 Cd A length 3 sub get sub}B/Cy{Cd A length 2 sub get 127 sub}\nB/Cdx{Cd A length 1 sub get}B/Ci{Cd A type/stringtype ne{ctr get/ctr ctr\n1 add N}if}B/id 0 N/rw 0 N/rc 0 N/gp 0 N/cp 0 N/G 0 N/CharBuilder{save 3\n1 roll S A/base get 2 index get S/BitMaps get S get/Cd X pop/ctr 0 N Cdx\n0 Cx Cy Ch sub Cx Cw add Cy setcachedevice Cw Ch true[1 0 0 -1 -.1 Cx\nsub Cy .1 sub]/id Ci N/rw Cw 7 add 8 idiv string N/rc 0 N/gp 0 N/cp 0 N{\nrc 0 ne{rc 1 sub/rc X rw}{G}ifelse}imagemask restore}B/G{{id gp get/gp\ngp 1 add N A 18 mod S 18 idiv pl S get exec}loop}B/adv{cp add/cp X}B\n/chg{rw cp id gp 4 index getinterval putinterval A gp add/gp X adv}B/nd{\n/cp 0 N rw exit}B/lsh{rw cp 2 copy get A 0 eq{pop 1}{A 255 eq{pop 254}{\nA A add 255 and S 1 and or}ifelse}ifelse put 1 adv}B/rsh{rw cp 2 copy\nget A 0 eq{pop 128}{A 255 eq{pop 127}{A 2 idiv S 128 and or}ifelse}\nifelse put 1 adv}B/clr{rw cp 2 index string putinterval adv}B/set{rw cp\nfillstr 0 4 index getinterval putinterval adv}B/fillstr 18 string 0 1 17\n{2 copy 255 put pop}for N/pl[{adv 1 chg}{adv 1 chg nd}{1 add chg}{1 add\nchg nd}{adv lsh}{adv lsh nd}{adv rsh}{adv rsh nd}{1 add adv}{/rc X nd}{\n1 add set}{1 add clr}{adv 2 chg}{adv 2 chg nd}{pop nd}]A{bind pop}\nforall N/D{/cc X A type/stringtype ne{]}if nn/base get cc ctr put nn\n/BitMaps get S ctr S sf 1 ne{A A length 1 sub A 2 index S get sf div put\n}if put/ctr ctr 1 add N}B/I{cc 1 add D}B/bop{userdict/bop-hook known{\nbop-hook}if/SI save N @rigin 0 0 moveto/V matrix currentmatrix A 1 get A\nmul exch 0 get A mul add .99 lt{/QV}{/RV}ifelse load def pop pop}N/eop{\nSI restore userdict/eop-hook known{eop-hook}if showpage}N/@start{\nuserdict/start-hook known{start-hook}if pop/VResolution X/Resolution X\n1000 div/DVImag X/IEn 256 array N 2 string 0 1 255{IEn S A 360 add 36 4\nindex cvrs cvn put}for pop 65781.76 div/vsize X 65781.76 div/hsize X}N\n/p{show}N/RMat[1 0 0 -1 0 0]N/BDot 260 string N/Rx 0 N/Ry 0 N/V{}B/RV/v{\n/Ry X/Rx X V}B statusdict begin/product where{pop false[(Display)(NeXT)\n(LaserWriter 16/600)]{A length product length le{A length product exch 0\nexch getinterval eq{pop true exit}if}{pop}ifelse}forall}{false}ifelse\nend{{gsave TR -.1 .1 TR 1 1 scale Rx Ry false RMat{BDot}imagemask\ngrestore}}{{gsave TR -.1 .1 TR Rx Ry scale 1 1 false RMat{BDot}\nimagemask grestore}}ifelse B/QV{gsave newpath transform round exch round\nexch itransform moveto Rx 0 rlineto 0 Ry neg rlineto Rx neg 0 rlineto\nfill grestore}B/a{moveto}B/delta 0 N/tail{A/delta X 0 rmoveto}B/M{S p\ndelta add tail}B/b{S p tail}B/c{-4 M}B/d{-3 M}B/e{-2 M}B/f{-1 M}B/g{0 M}\nB/h{1 M}B/i{2 M}B/j{3 M}B/k{4 M}B/w{0 rmoveto}B/l{p -4 w}B/m{p -3 w}B/n{\np -2 w}B/o{p -1 w}B/q{p 1 w}B/r{p 2 w}B/s{p 3 w}B/t{p 4 w}B/x{0 S\nrmoveto}B/y{3 2 roll p a}B/bos{/SS save N}B/eos{SS restore}B end\n\n%%EndProcSet\n%%BeginProcSet: 8r.enc\n% @@psencodingfile@{\n%   author = \"S. Rahtz, P. MacKay, Alan Jeffrey, B. Horn, K. Berry\",\n%   version = \"0.6\",\n%   date = \"22 June 1996\",\n%   filename = \"8r.enc\",\n%   email = \"kb@@mail.tug.org\",\n%   address = \"135 Center Hill Rd. // Plymouth, MA 02360\",\n%   codetable = \"ISO/ASCII\",\n%   checksum = \"119     662    4424\",\n%   docstring = \"Encoding for TrueType or Type 1 fonts to be used with TeX.\"\n% @}\n% \n% Idea is to have all the characters normally included in Type 1 fonts\n% available for typesetting. This is effectively the characters in Adobe\n% Standard Encoding + ISO Latin 1 + extra characters from Lucida.\n% \n% Character code assignments were made as follows:\n% \n% (1) the Windows ANSI characters are almost all in their Windows ANSI\n% positions, because some Windows users cannot easily reencode the\n% fonts, and it makes no difference on other systems. The only Windows\n% ANSI characters not available are those that make no sense for\n% typesetting -- rubout (127 decimal), nobreakspace (160), softhyphen\n% (173). quotesingle and grave are moved just because it's such an\n% irritation not having them in TeX positions.\n% \n% (2) Remaining characters are assigned arbitrarily to the lower part\n% of the range, avoiding 0, 10 and 13 in case we meet dumb software.\n% \n% (3) Y&Y Lucida Bright includes some extra text characters; in the\n% hopes that other PostScript fonts, perhaps created for public\n% consumption, will include them, they are included starting at 0x12.\n% \n% (4) Remaining positions left undefined are for use in (hopefully)\n% upward-compatible revisions, if someday more characters are generally\n% available.\n% \n% (5) hyphen appears twice for compatibility with both ASCII and Windows.\n% \n/TeXBase1Encoding [\n% 0x00 (encoded characters from Adobe Standard not in Windows 3.1)\n  /.notdef /dotaccent /fi /fl\n  /fraction /hungarumlaut /Lslash /lslash\n  /ogonek /ring /.notdef\n  /breve /minus /.notdef \n% These are the only two remaining unencoded characters, so may as\n% well include them.\n  /Zcaron /zcaron \n% 0x10\n /caron /dotlessi \n% (unusual TeX characters available in, e.g., Lucida Bright)\n /dotlessj /ff /ffi /ffl \n /.notdef /.notdef /.notdef /.notdef\n /.notdef /.notdef /.notdef /.notdef\n % very contentious; it's so painful not having quoteleft and quoteright\n % at 96 and 145 that we move the things normally found there down to here.\n /grave /quotesingle \n% 0x20 (ASCII begins)\n /space /exclam /quotedbl /numbersign\n /dollar /percent /ampersand /quoteright\n /parenleft /parenright /asterisk /plus /comma /hyphen /period /slash\n% 0x30\n /zero /one /two /three /four /five /six /seven\n /eight /nine /colon /semicolon /less /equal /greater /question\n% 0x40\n /at /A /B /C /D /E /F /G /H /I /J /K /L /M /N /O\n% 0x50\n /P /Q /R /S /T /U /V /W\n /X /Y /Z /bracketleft /backslash /bracketright /asciicircum /underscore\n% 0x60\n /quoteleft /a /b /c /d /e /f /g /h /i /j /k /l /m /n /o\n% 0x70\n /p /q /r /s /t /u /v /w\n /x /y /z /braceleft /bar /braceright /asciitilde\n /.notdef % rubout; ASCII ends\n% 0x80\n /.notdef /.notdef /quotesinglbase /florin\n /quotedblbase /ellipsis /dagger /daggerdbl\n /circumflex /perthousand /Scaron /guilsinglleft\n /OE /.notdef /.notdef /.notdef\n% 0x90\n /.notdef /.notdef /.notdef /quotedblleft\n /quotedblright /bullet /endash /emdash\n /tilde /trademark /scaron /guilsinglright\n /oe /.notdef /.notdef /Ydieresis\n% 0xA0\n /.notdef % nobreakspace\n /exclamdown /cent /sterling\n /currency /yen /brokenbar /section\n /dieresis /copyright /ordfeminine /guillemotleft\n /logicalnot\n /hyphen % Y&Y (also at 45); Windows' softhyphen\n /registered\n /macron\n% 0xD0\n /degree /plusminus /twosuperior /threesuperior\n /acute /mu /paragraph /periodcentered\n /cedilla /onesuperior /ordmasculine /guillemotright\n /onequarter /onehalf /threequarters /questiondown\n% 0xC0\n /Agrave /Aacute /Acircumflex /Atilde /Adieresis /Aring /AE /Ccedilla\n /Egrave /Eacute /Ecircumflex /Edieresis\n /Igrave /Iacute /Icircumflex /Idieresis\n% 0xD0\n /Eth /Ntilde /Ograve /Oacute\n /Ocircumflex /Otilde /Odieresis /multiply\n /Oslash /Ugrave /Uacute /Ucircumflex\n /Udieresis /Yacute /Thorn /germandbls\n% 0xE0\n /agrave /aacute /acircumflex /atilde\n /adieresis /aring /ae /ccedilla\n /egrave /eacute /ecircumflex /edieresis\n /igrave /iacute /icircumflex /idieresis\n% 0xF0\n /eth /ntilde /ograve /oacute\n /ocircumflex /otilde /odieresis /divide\n /oslash /ugrave /uacute /ucircumflex\n /udieresis /yacute /thorn /ydieresis\n] def\n\n%%EndProcSet\n%%BeginProcSet: texps.pro\n%!\nTeXDict begin/rf{findfont dup length 1 add dict begin{1 index/FID ne 2\nindex/UniqueID ne and{def}{pop pop}ifelse}forall[1 index 0 6 -1 roll\nexec 0 exch 5 -1 roll VResolution Resolution div mul neg 0 0]/Metrics\nexch def dict begin Encoding{exch dup type/integertype ne{pop pop 1 sub\ndup 0 le{pop}{[}ifelse}{FontMatrix 0 get div Metrics 0 get div def}\nifelse}forall Metrics/Metrics currentdict end def[2 index currentdict\nend definefont 3 -1 roll makefont/setfont cvx]cvx def}def/ObliqueSlant{\ndup sin S cos div neg}B/SlantFont{4 index mul add}def/ExtendFont{3 -1\nroll mul exch}def/ReEncodeFont{CharStrings rcheck{/Encoding false def\ndup[exch{dup CharStrings exch known not{pop/.notdef/Encoding true def}\nif}forall Encoding{]exch pop}{cleartomark}ifelse}if/Encoding exch def}\ndef end\n\n%%EndProcSet\n%%BeginProcSet: special.pro\n%!\nTeXDict begin/SDict 200 dict N SDict begin/@SpecialDefaults{/hs 612 N\n/vs 792 N/ho 0 N/vo 0 N/hsc 1 N/vsc 1 N/ang 0 N/CLIP 0 N/rwiSeen false N\n/rhiSeen false N/letter{}N/note{}N/a4{}N/legal{}N}B/@scaleunit 100 N\n/@hscale{@scaleunit div/hsc X}B/@vscale{@scaleunit div/vsc X}B/@hsize{\n/hs X/CLIP 1 N}B/@vsize{/vs X/CLIP 1 N}B/@clip{/CLIP 2 N}B/@hoffset{/ho\nX}B/@voffset{/vo X}B/@angle{/ang X}B/@rwi{10 div/rwi X/rwiSeen true N}B\n/@rhi{10 div/rhi X/rhiSeen true N}B/@llx{/llx X}B/@lly{/lly X}B/@urx{\n/urx X}B/@ury{/ury X}B/magscale true def end/@MacSetUp{userdict/md known\n{userdict/md get type/dicttype eq{userdict begin md length 10 add md\nmaxlength ge{/md md dup length 20 add dict copy def}if end md begin\n/letter{}N/note{}N/legal{}N/od{txpose 1 0 mtx defaultmatrix dtransform S\natan/pa X newpath clippath mark{transform{itransform moveto}}{transform{\nitransform lineto}}{6 -2 roll transform 6 -2 roll transform 6 -2 roll\ntransform{itransform 6 2 roll itransform 6 2 roll itransform 6 2 roll\ncurveto}}{{closepath}}pathforall newpath counttomark array astore/gc xdf\npop ct 39 0 put 10 fz 0 fs 2 F/|______Courier fnt invertflag{PaintBlack}\nif}N/txpose{pxs pys scale ppr aload pop por{noflips{pop S neg S TR pop 1\n-1 scale}if xflip yflip and{pop S neg S TR 180 rotate 1 -1 scale ppr 3\nget ppr 1 get neg sub neg ppr 2 get ppr 0 get neg sub neg TR}if xflip\nyflip not and{pop S neg S TR pop 180 rotate ppr 3 get ppr 1 get neg sub\nneg 0 TR}if yflip xflip not and{ppr 1 get neg ppr 0 get neg TR}if}{\nnoflips{TR pop pop 270 rotate 1 -1 scale}if xflip yflip and{TR pop pop\n90 rotate 1 -1 scale ppr 3 get ppr 1 get neg sub neg ppr 2 get ppr 0 get\nneg sub neg TR}if xflip yflip not and{TR pop pop 90 rotate ppr 3 get ppr\n1 get neg sub neg 0 TR}if yflip xflip not and{TR pop pop 270 rotate ppr\n2 get ppr 0 get neg sub neg 0 S TR}if}ifelse scaleby96{ppr aload pop 4\n-1 roll add 2 div 3 1 roll add 2 div 2 copy TR .96 dup scale neg S neg S\nTR}if}N/cp{pop pop showpage pm restore}N end}if}if}N/normalscale{\nResolution 72 div VResolution 72 div neg scale magscale{DVImag dup scale\n}if 0 setgray}N/psfts{S 65781.76 div N}N/startTexFig{/psf$SavedState\nsave N userdict maxlength dict begin/magscale true def normalscale\ncurrentpoint TR/psf$ury psfts/psf$urx psfts/psf$lly psfts/psf$llx psfts\n/psf$y psfts/psf$x psfts currentpoint/psf$cy X/psf$cx X/psf$sx psf$x\npsf$urx psf$llx sub div N/psf$sy psf$y psf$ury psf$lly sub div N psf$sx\npsf$sy scale psf$cx psf$sx div psf$llx sub psf$cy psf$sy div psf$ury sub\nTR/showpage{}N/erasepage{}N/copypage{}N/p 3 def @MacSetUp}N/doclip{\npsf$llx psf$lly psf$urx psf$ury currentpoint 6 2 roll newpath 4 copy 4 2\nroll moveto 6 -1 roll S lineto S lineto S lineto closepath clip newpath\nmoveto}N/endTexFig{end psf$SavedState restore}N/@beginspecial{SDict\nbegin/SpecialSave save N gsave normalscale currentpoint TR\n@SpecialDefaults count/ocount X/dcount countdictstack N}N/@setspecial{\nCLIP 1 eq{newpath 0 0 moveto hs 0 rlineto 0 vs rlineto hs neg 0 rlineto\nclosepath clip}if ho vo TR hsc vsc scale ang rotate rwiSeen{rwi urx llx\nsub div rhiSeen{rhi ury lly sub div}{dup}ifelse scale llx neg lly neg TR\n}{rhiSeen{rhi ury lly sub div dup scale llx neg lly neg TR}if}ifelse\nCLIP 2 eq{newpath llx lly moveto urx lly lineto urx ury lineto llx ury\nlineto closepath clip}if/showpage{}N/erasepage{}N/copypage{}N newpath}N\n/@endspecial{count ocount sub{pop}repeat countdictstack dcount sub{end}\nrepeat grestore SpecialSave restore end}N/@defspecial{SDict begin}N\n/@fedspecial{end}B/li{lineto}B/rl{rlineto}B/rc{rcurveto}B/np{/SaveX\ncurrentpoint/SaveY X N 1 setlinecap newpath}N/st{stroke SaveX SaveY\nmoveto}N/fil{fill SaveX SaveY moveto}N/ellipse{/endangle X/startangle X\n/yrad X/xrad X/savematrix matrix currentmatrix N TR xrad yrad scale 0 0\n1 startangle endangle arc savematrix setmatrix}N end\n\n%%EndProcSet\nTeXDict begin 39158280 55380996 1000 600 600 (dddmp-2.0.dvi)\n@start /Fa 143[55 1[55 7[28 2[50 99[{TeXBase1Encoding ReEncodeFont}4\n99.6264 /Helvetica rf\n%DVIPSBitmapFont: Fb cmr12 12 3\n/Fb 3 53 df<14FF010713E090381F81F890383E007C01FC133F4848EB1F8049130F4848\nEB07C04848EB03E0A2000F15F0491301001F15F8A2003F15FCA390C8FC4815FEA54815FF\nB3A46C15FEA56D1301003F15FCA3001F15F8A26C6CEB03F0A36C6CEB07E0000315C06D13\n0F6C6CEB1F806C6CEB3F00013E137C90381F81F8903807FFE0010090C7FC28447CC131>\n48 D<143014F013011303131F13FFB5FC13E713071200B3B3B0497E497E007FB6FCA320\n4278C131>I<ED0380A21507150FA2151F153FA2157F15FFA25CEC03BF153F1407140614\n0C141C141814301470146014C013011480EB03005B13065B131C13185B1370136013E048\n5A5B120390C7FC1206120E120C5A123812305A12E0B812C0A3C8383F8000ADEDFFE0027F\nEBFFC0A32A437DC231>52 D E\n%EndDVIPSBitmapFont\n/Fc 64[50 29[39 12[55 55 25[44 44 66 44 50 28 39 39 1[50\n50 50 72 28 44 1[28 50 50 28 44 50 44 50 50 10[61 2[50\n4[66 83 55 2[33 2[61 1[72 66 61 61 15[50 2[25 33 25 2[33\n33 37[50 2[{TeXBase1Encoding ReEncodeFont}45 99.6264\n/Times-Italic rf\n%DVIPSBitmapFont: Fd cmmi12 12 3\n/Fd 3 103 df<F001C0F007E0181FF07FC0943801FF00EF07FCEF1FF0EF7FC04C48C7FC\nEE0FFCEE3FF0EEFFC0030390C8FCED0FF8ED3FE0EDFF80DA03FEC9FCEC1FF8EC7FE09038\n01FF80D907FECAFCEB1FF0EB7FC04848CBFCEA07FCEA1FF0EA7FC048CCFCA2EA7FC0EA1F\nF0EA07FCEA01FF38007FC0EB1FF0EB07FE903801FF809038007FE0EC1FF8EC03FE913800\nFF80ED3FE0ED0FF8ED03FF030013C0EE3FF0EE0FFCEE01FF9338007FC0EF1FF0EF07FCEF\n01FF9438007FC0F01FE01807F001C03B3878B44C>60 D<127012FCB4FCEA7FC0EA1FF0EA\n07FCEA01FF38007FC0EB1FF0EB07FE903801FF809038007FE0EC1FF8EC03FE913800FF80\nED3FE0ED0FF8ED03FF030013C0EE3FF0EE0FFCEE01FF9338007FC0EF1FF0EF07FCEF01FF\n9438007FC0F01FE0A2F07FC0943801FF00EF07FCEF1FF0EF7FC04C48C7FCEE0FFCEE3FF0\nEEFFC0030390C8FCED0FF8ED3FE0EDFF80DA03FEC9FCEC1FF8EC7FE0903801FF80D907FE\nCAFCEB1FF0EB7FC04848CBFCEA07FCEA1FF0EA7FC048CCFC12FC12703B3878B44C>62\nD<EE07E0EE1FF8EE7C1CEEF80E923801F03E923803E07F17FFED07E116C117FE92380FC0\nFC177817004B5AA4153F93C7FCA45D157EA491B61280A3DA00FCC7FCA314015DA414035D\nA414075DA4140F5DA5141F5DA4143F92C8FCA45C147EA45CA45C1301A25CA2EA1C03007F\n5B12FF5C13075C4848C9FC12F8EA601EEA783CEA1FF0EA07C0305A7BC530>102\nD E\n%EndDVIPSBitmapFont\n/Fe 134[42 2[42 42 23 32 28 1[42 42 42 65 23 2[23 42\n42 28 37 42 1[42 37 12[51 10[28 4[60 1[55 19[21 28 21\n44[{TeXBase1Encoding ReEncodeFont}26 83.022 /Times-Roman\nrf\n%DVIPSBitmapFont: Ff cmr7 7 2\n/Ff 2 51 df<13381378EA01F8121F12FE12E01200B3AB487EB512F8A215267BA521>49\nD<13FF000313E0380E03F0381800F848137C48137E00787F12FC6CEB1F80A4127CC7FC15\n005C143E147E147C5C495A495A5C495A010EC7FC5B5B903870018013E0EA018039030003\n0012065A001FB5FC5A485BB5FCA219267DA521>I E\n%EndDVIPSBitmapFont\n/Fg 103[60 26[60 1[60 60 60 60 60 60 60 60 60 60 60 60\n60 60 60 60 2[60 60 60 60 60 60 60 60 60 3[60 1[60 3[60\n60 1[60 60 1[60 60 1[60 60 3[60 1[60 1[60 60 60 1[60\n60 1[60 1[60 1[60 60 60 60 60 60 60 60 60 60 60 60 60\n60 60 5[60 38[{TeXBase1Encoding ReEncodeFont}62 99.6264\n/Courier rf\n%DVIPSBitmapFont: Fh cmr8 8 2\n/Fh 2 51 df<130C133C137CEA03FC12FFEAFC7C1200B3B113FE387FFFFEA2172C7AAB23\n>49 D<EB7F803801FFF0380780FC380E003F48EB1F8048EB0FC05A0060EB07E012F000FC\n14F07E1403A3007C1307C7FCA215E0140F15C0141F1580EC3F00147E147C5C495A495A49\n5A495A011EC7FC5B5B4913305B485A4848136048C7FC000E14E0001FB5FC5A4814C0B6FC\nA21C2C7DAB23>I E\n%EndDVIPSBitmapFont\n/Fi 105[50 28[50 50 2[55 33 39 44 1[55 50 55 83 28 2[28\n1[50 33 44 55 44 55 50 10[72 1[66 55 3[78 72 94 66 3[78\n1[61 66 72 72 66 72 13[50 50 50 1[28 25 33 45[{\nTeXBase1Encoding ReEncodeFont}40 99.6264 /Times-Bold\nrf /Fj 139[40 1[53 1[66 60 66 100 33 2[33 3[53 3[60 23[47\n2[73 18[60 60 60 2[30 46[{TeXBase1Encoding ReEncodeFont}16\n119.552 /Times-Bold rf\n%DVIPSBitmapFont: Fk cmsy10 12 1\n/Fk 1 16 df<49B4FC010F13E0013F13F8497F48B6FC4815804815C04815E04815F0A248\n15F8A24815FCA3B712FEA96C15FCA36C15F8A26C15F0A26C15E06C15C06C15806C15006C\n6C13FC6D5B010F13E0010190C7FC27277BAB32>15 D E\n%EndDVIPSBitmapFont\n/Fl 64[44 42[44 44 24[44 50 50 72 50 50 28 39 33 50 50\n50 50 78 28 50 28 28 50 50 33 44 50 44 50 44 6[61 1[72\n94 72 72 61 55 66 72 55 72 72 89 61 1[39 33 72 72 55\n61 72 66 66 72 3[56 1[28 28 50 50 50 50 50 50 50 50 50\n50 28 25 33 25 2[33 33 36[55 55 2[{TeXBase1Encoding ReEncodeFont}74\n99.6264 /Times-Roman rf\n%DVIPSBitmapFont: Fm cmsy10 14.4 2\n/Fm 2 104 df<EE1FE0ED01FF150F92383FF800EDFFC04A90C7FC4A5A4A5A4A5A4A5A5D\nA2143F5DB3B1147F5D14FF92C8FC5B495A495A495AEB3FE0EBFF80D87FFEC9FCEAFFF8A2\nEA7FFEC66C7EEB3FE0EB0FF86D7E6D7E6D7E7F81147F81143FB3B181141FA2816E7E6E7E\n6E7E6E7E6E13C0ED3FF892380FFFE01501ED001F2B7878D93C>102\nD<B4FC13F813FF000313C038007FF0EB1FF8EB07FC6D7E6D7E6D7F147FA281143FB3B181\n141F81140F816E7E6E7E6E7E6E6C7EED3FF092380FFFC0030113E0A2030F13C092383FF0\n00ED7F804A48C7FC4A5A4A5A4A5A5D141F5D143F5DB3B1147F5DA214FF4990C8FC495A49\n5AEB1FF8EB7FF03803FFC0B5C9FC13F890CAFC2B7878D93C>I E\n%EndDVIPSBitmapFont\n/Fn 105[60 27[53 4[60 33 47 40 60 60 60 60 93 33 2[33\n1[60 40 53 60 53 60 53 7[86 4[73 66 1[86 66 3[73 2[40\n1[86 1[73 86 80 1[86 110 5[33 60 4[60 1[60 60 60 1[30\n40 30 44[{TeXBase1Encoding ReEncodeFont}42 119.552 /Times-Roman\nrf /Fo 136[104 1[80 48 56 64 1[80 72 80 120 40 80 1[40\n1[72 1[64 80 64 80 72 12[96 80 104 1[88 1[104 135 3[56\n2[88 1[104 104 96 104 6[48 1[72 72 72 72 72 72 72 72\n72 1[36 46[{TeXBase1Encoding ReEncodeFont}41 143.462\n/Times-Bold rf end\n%%EndProlog\n%%BeginSetup\n%%Feature: *Resolution 600dpi\nTeXDict begin\n%%BeginPaperSize: a4\na4\n%%EndPaperSize\n\n%%EndSetup\n%%Page: 1 1\n1 0 bop 472 600 a Fo(DDDMP:)35 b(Decision)f(Diagram)f(DuMP)j(package)\n1480 830 y(Release)e(2.0)462 1230 y Fn(Gianpiero)c(Cabodi)2402\n1232 y(Stef)o(ano)g(Quer)1316 1506 y(Politecnico)g(di)g(T)-10\nb(orino)1024 1656 y(Dip.)30 b(di)g(Automatica)g(e)g(Informatica)1119\n1805 y(Corso)f(Duca)h(de)n(gli)g(Abruzzi)g(24)1277 1955\ny(I\\22610129)e(T)-5 b(urin,)29 b(IT)-11 b(AL)f(Y)1038\n2104 y(E-mail:)38 b Fm(f)p Fn(cabodi,quer)p Fm(g)p Fn(@polito.it)-189\n2614 y Fo(1)143 b(Intr)m(oduction)-189 2837 y Fl(The)27\nb(DDDMP)h(package)f(de\\002nes)h(formats)f(and)g(rules)g(to)g(store)g\n(DD)g(on)g(\\002le.)39 b(More)27 b(in)g(particular)g(it)g(contains)g(a)\n-189 2958 y(set)e(of)g(functions)e(to)i(dump)e(\\(store)i(and)g(load\\))g\n(DDs)f(and)h(DD)g(forests)f(on)h(\\002le)g(in)f(dif)n(ferent)h(formats.)\n47 3078 y(In)30 b(the)g(present)g(implementation,)f(BDDs)h(\\(R)l\n(OBDDs\\))h(and)f(ADD)g(\\(Algebraic)g(Decision)g(Diagram\\))g(of)-189\n3199 y(the)g(CUDD)g(package)g(\\(v)o(ersion)f(2.3.0)g(or)h(higher\\))g\n(are)g(supported.)45 b(These)30 b(structures)f(can)h(be)g(represented)g\n(on)-189 3319 y(\\002les)25 b(either)g(in)f(te)o(xt,)g(binary)-6\nb(,)24 b(or)h(CNF)g(\\(DIMA)l(CS\\))h(formats.)47 3439\ny(The)f(main)f(rules)h(used)f(are)i(follo)n(wing)d(rules:)-44\n3643 y Fk(\\017)49 b Fl(A)30 b(\\002le)h(contains)e(a)i(single)e(BDD/ADD)\nh(or)g(a)h(forest)f(of)g(BDDs/ADD,)g(i.e.,)i(a)e(v)o(ector)g(of)g\n(Boolean)h(func-)55 3763 y(tions.)-44 3966 y Fk(\\017)49\nb Fl(Inte)o(ger)21 b(inde)o(x)o(es)f(are)i(used)f(instead)g(of)g\n(pointers)g(to)g(reference)i(nodes.)29 b(BDD/ADD)21 b(nodes)g(are)h\n(numbered)55 4087 y(with)j(contiguous)g(numbers,)g(from)h(1)g(to)f\n(NNodes)h(\\(total)f(number)h(of)g(nodes)g(on)f(a)i(\\002le\\).)35\nb(0)26 b(is)f(not)h(used)f(to)55 4207 y(allo)n(w)f(ne)o(gati)n(v)o(e)e\n(inde)o(x)o(es)h(for)i(complemented)f(edges.)-44 4411\ny Fk(\\017)49 b Fl(A)23 b(\\002le)g(contains)f(a)h(header)l(,)h\n(including)d(se)n(v)o(eral)h(informations)f(about)h(v)n(ariables)h(and)\nf(roots)g(of)h(BDD)h(func-)55 4531 y(tions,)32 b(then)e(the)h(list)g\n(of)g(nodes.)49 b(The)32 b(header)f(is)g(al)o(w)o(ays)g(represented)h\n(in)f(te)o(xt)f(format)h(\\(also)g(for)g(binary)55 4651\ny(\\002les\\).)g(BDDs,)25 b(ADDs,)f(and)h(CNF)h(\\002les)f(share)g(a)g\n(similar)f(format)g(header)-5 b(.)-44 4855 y Fk(\\017)49\nb Fl(BDD/ADD)40 b(nodes)g(are)h(listed)f(follo)n(wing)e(their)i\n(numbering,)j(which)d(is)g(produced)g(by)h(a)f(post-order)55\n4975 y(tra)n(v)o(ersal,)24 b(in)h(such)f(a)h(w)o(ay)g(that)g(a)g(node)f\n(is)h(al)o(w)o(ays)f(listed)g(after)h(its)f(Then/Else)g(children.)47\n5179 y(In)32 b(the)f(sequel)g(we)g(describe)h(more)f(in)g(detail)f(the)\nh(dif)n(ferent)g(formats)g(and)g(procedures)h(a)n(v)n(ailable.)49\nb(First)-189 5299 y(of)26 b(all,)f(we)h(describe)f(BDDs)h(and)g(ADDs)f\n(formats)g(and)g(procedure.)33 b(Secondly)-6 b(,)26 b(we)f(concentrate)\nh(on)f(CNF)i(\\002les,)-189 5419 y(i.e.,)e(ho)n(w)f(to)g(translate)g(a)i\n(BDD)f(or)g(a)g(forest)g(of)f(BDDs)h(into)f(a)h(CNF)h(formula)e(and)h\n(vice-v)o(ersa.)1794 5800 y(1)p eop\n%%Page: 2 2\n2 1 bop -189 218 a Fo(2)143 b(BDD)35 b(and)g(ADD)g(Support)-189\n441 y Fl(In)23 b(this)f(section)g(we)g(describe)h(format)g(and)f\n(procedure)h(re)o(garding)f(BDDs)h(and)f(ADDs.)30 b(W)-8\nb(e)23 b(speci\\002cally)g(refer)g(to)-189 562 y(BDDs)h(in)g(the)g\n(description)e(as)j(ADD)e(may)h(be)g(seen)g(as)h(an)f(e)o(xtension)e\n(and)i(will)f(be)h(described)g(later)-5 b(.)30 b(First)24\nb(of)g(all,)-189 682 y(we)29 b(concentrate)f(on)g(the)g(format)g(used)g\n(to)g(store)g(these)g(structure,)h(then)f(we)g(describe)h(the)f\n(procedure)h(a)n(v)n(ailable)-189 802 y(to)24 b(store)h(and)g(load)f\n(them.)-189 1094 y Fj(2.1)119 b(F)m(ormat)-189 1281 y\nFl(BDD)30 b(dump)f(\\002les)g(are)i(composed)e(of)g(tw)o(o)g(sections:)\n40 b(The)29 b(header)h(and)g(the)f(list)g(of)h(nodes.)44\nb(The)30 b(header)g(has)g(a)-189 1402 y(common)c(\\(te)o(xt\\))h(format,)\nh(while)e(the)i(list)e(of)h(nodes)g(is)g(either)g(in)g(te)o(xt)g(or)g\n(binary)g(format.)38 b(In)28 b(te)o(xt)e(format)h(nodes)-189\n1522 y(are)33 b(represented)f(with)f(redundant)g(informations,)h(where)\nh(the)f(main)f(goal)g(is)h(readability)-6 b(,)32 b(while)g(the)f\n(purpose)-189 1642 y(of)i(binary)f(format)g(is)g(minimizing)e(the)i(o)o\n(v)o(erall)f(storage)h(size)h(for)g(BDD)f(nodes.)54 b(The)32\nb(header)h(format)f(is)g(k)o(ept)-189 1763 y(common)h(to)h(te)o(xt)g\n(and)g(binary)g(formats)g(for)h(sak)o(e)f(of)h(simplicity:)47\nb(No)34 b(particular)g(optimization)f(is)h(presently)-189\n1883 y(done)29 b(on)f(binary)h(\\002le)g(headers,)h(whose)f(size)g(is)f\n(by)h(f)o(ar)g(dominated)f(by)h(node)f(lists)g(in)g(the)h(case)g(of)g\n(lar)n(ge)h(BDDs)-189 2003 y(\\(se)n(v)o(eral)24 b(thousands)g(of)h(DD)f\n(nodes\\).)-189 2266 y Fi(2.1.1)99 b(Header)-189 2453\ny Fl(The)23 b(header)h(has)f(the)g(same)g(format)g(both)g(for)g(te)o\n(xtual)f(and)i(binary)e(dump.)30 b(F)o(or)23 b(sak)o(e)g(of)h\n(generality)e(and)h(because)-189 2574 y(of)f(dynamic)g(v)n(ariable)g\n(ordering)g(both)f(v)n(ariable)h(IDs)g(and)g(permutations)2377\n2537 y Fh(1)2438 2574 y Fl(are)h(included.)29 b(Names)22\nb(are)h(optionally)-189 2694 y(listed)35 b(for)h(input)f(v)n(ariables)g\n(and)h(for)h(the)e(stored)h(functions.)63 b(Ne)n(w)36\nb(auxiliary)f(IDs)h(are)h(also)e(allo)n(wed.)64 b(Only)-189\n2814 y(the)34 b(v)n(ariables)f(in)g(the)h(true)g(support)f(of)h(the)f\n(stored)h(BDDs)g(are)h(listed.)56 b(All)34 b(information)e(on)i(v)n\n(ariables)f(\\(IDs,)-189 2935 y(permutations,)c(names,)i(auxiliary)e\n(IDs\\))h(sorted)g(by)g(IDs,)h(and)e(the)o(y)h(are)g(restricted)g(to)f\n(the)h(true)g(support)f(of)h(the)-189 3055 y(dumped)22\nb(BDD,)h(while)g(IDs)g(and)f(permutations)g(are)h(referred)i(to)d(the)h\n(writing)f(BDD)h(manager)-5 b(.)30 b(Names)22 b(can)i(thus)-189\n3175 y(be)h(sorted)f(by)h(v)n(ariable)f(ordering)h(by)f(permuting)g\n(them)g(according)h(to)f(the)h(permutations)e(stored)h(in)h(the)f\n(\\002le.)47 3296 y(As)h(an)g(e)o(xample,)f(the)g(header)i(\\(in)e(te)o\n(xt)g(mode\\))h(of)f(the)h(ne)o(xt)f(state)h(functions)e(of)i(circuit)g\n(s27)f(follo)n(ws:)-189 3494 y Fg(.ver)59 b(DDDMP-2.0)-189\n3615 y(.mode)g(A)-189 3735 y(.varinfo)f(3)-189 3855 y(.dd)h(s27-delta)\n-189 3976 y(.nnodes)f(16)-189 4096 y(.nvars)g(10)-189\n4216 y(.nsuppvars)g(7)-189 4337 y(.varnames)g(G0)h(G1)g(G2)h(G3)f(G5)g\n(G6)h(G7)-189 4457 y(.orderedvarnames)c(G0)k(G1)f(G2)g(G3)h(G5)f(G6)g\n(G7)-189 4578 y(.ids)g(0)g(1)h(2)g(3)f(4)h(5)f(6)-189\n4698 y(.permids)f(0)i(1)f(2)h(3)f(5)h(7)f(9)-189 4818\ny(.auxids)f(1)i(2)f(3)h(4)f(5)h(6)g(7)-189 4939 y(.nroots)e(3)-189\n5059 y(.rootids)g(6)i(-13)f(-16)-189 5179 y(.rootnames)f(G10)h(G11)g\n(G13)47 5378 y Fl(The)25 b(lines)f(contain)g(the)h(follo)n(wing)e\n(informations:)p -189 5460 1607 4 v -77 5521 a Ff(1)-40\n5551 y Fe(The)d(permutation)e(of)i(the)g(i-th)h(v)n(ariable)e(ID)h(is)h\n(the)f(relati)n(v)o(e)g(position)f(of)h(the)g(v)n(ariable)f(in)i(the)f\n(ordering.)1794 5800 y Fl(2)p eop\n%%Page: 3 3\n3 2 bop -44 218 a Fk(\\017)49 b Fl(Dddmp)24 b(v)o(ersion)f(information.)\n-44 411 y Fk(\\017)49 b Fl(File)25 b(mode)f(\\(A)h(for)g(ASCII)h(te)o\n(xt,)e(B)h(for)g(binary)g(mode\\).)-44 604 y Fk(\\017)49\nb Fl(V)-11 b(ar)n(-e)o(xtra-info)25 b(\\(0:)30 b(v)n(ariable)24\nb(ID,)h(1:)31 b(permID,)24 b(2:)31 b(aux)25 b(ID,)g(3:)30\nb(v)n(ariable)24 b(name,)h(4)g(no)f(e)o(xtra)h(info\\).)-44\n797 y Fk(\\017)49 b Fl(Name)25 b(of)g(dd)f(\\(optional\\).)-44\n990 y Fk(\\017)49 b Fl(T)-8 b(otal)24 b(number)g(of)h(nodes)g(in)f(the)h\n(\\002le.)-44 1183 y Fk(\\017)49 b Fl(Number)24 b(of)h(v)n(ariables)f(of)\nh(the)g(writing)f(DD)g(manager)-5 b(.)-44 1375 y Fk(\\017)49\nb Fl(Number)24 b(of)h(v)n(ariables)f(in)h(the)f(true)h(support)f(of)h\n(the)f(stored)h(DDs.)-44 1568 y Fk(\\017)49 b Fl(V)-11\nb(ariable)25 b(names)f(\\(optional\\))g(for)h(all)g(the)f(v)n(ariables)g\n(in)h(the)f(BDD/ADD)h(support.)-44 1761 y Fk(\\017)49\nb Fl(V)-11 b(ariable)20 b(names)g(for)h(all)f(the)g(v)n(ariables)f(in)h\n(the)g(DD)h(manager)f(during)g(the)g(storing)f(phase.)29\nb(Notice)20 b(that)g(this)55 1882 y(information)k(w)o(as)h(not)g\n(stored)g(by)g(pre)n(vious)f(v)o(ersions)g(of)i(the)f(same)g(tool.)32\nb(Full)25 b(backw)o(ard)g(compatibility)55 2002 y(is)f(guaranteed)h(by)\ng(the)f(present)h(implementation)d(of)j(the)g(tool.)-44\n2195 y Fk(\\017)49 b Fl(V)-11 b(ariable)25 b(IDs.)-44\n2388 y Fk(\\017)49 b Fl(V)-11 b(ariable)25 b(permuted)f(IDs.)-44\n2581 y Fk(\\017)49 b Fl(V)-11 b(ariable)25 b(auxiliary)f(IDs)h\n(\\(optional\\).)-44 2774 y Fk(\\017)49 b Fl(Number)24 b(of)h(BDD)g\n(roots.)-44 2967 y Fk(\\017)49 b Fl(Inde)o(x)o(es)24 b(of)h(BDD)g(roots)\nf(\\(complemented)g(edges)g(allo)n(wed\\).)-44 3160 y Fk(\\017)49\nb Fl(Names)24 b(of)h(BDD)h(roots)e(\\(optional\\).)-189\n3332 y(Notice)h(that)f(a)h(\\002eld)-189 3504 y Fg(.add)-189\n3676 y Fl(is)f(present)h(after)g(the)g(dddmp)f(v)o(ersion)f(for)j\n(\\002les)e(containing)g(ADDs.)-189 3936 y Fi(2.1.2)99\nb(T)-9 b(ext)25 b(F)n(ormat)-189 4124 y Fl(In)g(te)o(xt)f(mode)g(nodes)\ng(are)i(listed)e(on)g(a)h(te)o(xt)f(line)h(basis.)30\nb(Each)25 b(a)g(node)f(is)h(represented)g(as)-189 4296\ny Fg(<Node-index>)57 b([<Var-extra-info>])f(<Var-internal-index>)588\n4416 y(<Then-index>)h(<Else-index>)-189 4588 y Fl(where)25\nb(all)g(inde)o(x)o(es)e(are)j(inte)o(ger)e(numbers.)47\n4709 y(This)h(format)g(is)g(redundant)f(\\(due)i(to)f(the)g(node)g\n(ordering,)g Fd(<)p Fl(Node-inde)o(x)p Fd(>)f Fl(is)g(and)i\n(incremental)e(inte)o(ger\\))-189 4829 y(b)n(ut)g(we)h(k)o(eep)g(it)g\n(for)g(readability)-6 b(.)47 4949 y Fd(<)p Fl(V)-11 b(ar)n(-e)o\n(xtra-info)p Fd(>)34 b Fl(\\(optional)e(redundant)i(\\002eld\\))g(is)f\n(either)h(an)g(inte)o(ger)f(\\(ID,)h(PermID,)g(or)g(auxID\\))g(or)g(a)\n-189 5070 y(string)k(\\(v)n(ariable)h(name\\).)75 b Fd(<)p\nFl(V)-11 b(ar)n(-internal-inde)o(x)p Fd(>)38 b Fl(is)h(an)g(internal)g\n(v)n(ariable)g(inde)o(x:)59 b(V)-11 b(ariables)39 b(in)g(the)g(true)\n-189 5190 y(support)25 b(of)h(the)g(stored)g(BDDs)g(are)h(numbered)e\n(with)g(ascending)h(inte)o(gers)f(starting)g(from)h(0,)g(and)g(follo)n\n(wing)e(the)-189 5311 y(v)n(ariable)g(ordering.)31 b\nFd(<)p Fl(Then-inde)o(x)p Fd(>)23 b Fl(and)i Fd(<)p Fl(Else-inde)o(x)p\nFd(>)e Fl(are)j(signed)e(inde)o(x)o(es)f(of)i(children)f(nodes.)47\n5431 y(In)h(the)f(follo)n(wing,)f(we)i(report)f(the)g(list)g(of)h\n(nodes)f(of)g(the)h(s27)f(ne)o(xt)f(state)i(functions)e(\\(see)i(pre)n\n(vious)e(header)-189 5551 y(e)o(xample\\):)1794 5800 y(3)p\neop\n%%Page: 4 4\n4 3 bop -189 218 a Fg(.nodes)-189 338 y(1)60 b(T)f(1)h(0)f(0)-189\n459 y(2)h(G7)f(6)g(1)h(-1)-189 579 y(3)g(G5)f(4)g(1)h(2)-189\n699 y(4)g(G3)f(3)g(3)h(1)-189 820 y(5)g(G1)f(1)g(1)h(4)-189\n940 y(6)g(G0)f(0)g(5)h(-1)-189 1061 y(7)g(G6)f(5)g(1)h(-1)-189\n1181 y(8)g(G5)f(4)g(1)h(-7)-189 1301 y(9)g(G6)f(5)g(1)h(-2)-189\n1422 y(10)f(G5)h(4)f(1)h(-9)-189 1542 y(11)f(G3)h(3)f(10)h(8)-189\n1662 y(12)f(G1)h(1)f(8)h(11)-189 1783 y(13)f(G0)h(0)f(5)h(12)-189\n1903 y(14)f(G2)h(2)f(1)h(-1)-189 2024 y(15)f(G2)h(2)f(1)h(-2)-189\n2144 y(16)f(G1)h(1)f(14)h(15)-189 2264 y(.end)-189 2468\ny Fl(The)27 b(list)f(is)h(enclosed)g(between)g(the)g\nFg(.nodes)f Fl(and)h Fg(.end)f Fl(lines.)37 b(First)27\nb(node)g(is)g(the)g(one)g(constant,)f(each)i(node)-189\n2588 y(contains)c(the)h(optional)e(v)n(ariable)h(name.)47\n2708 y(F)o(or)29 b(ADDs)f(more)h(than)f(one)h(constant)e(is)i(stored)f\n(in)g(the)g(\\002le.)43 b(Each)29 b(constant)f(has)g(the)h(same)f\n(format)h(we)-189 2829 y(ha)n(v)o(e)c(just)e(analyzed)i(for)g(the)g\n(BDD)g(b)n(ut)g(the)f(represented)h(v)n(alue)f(is)h(stored)f(as)h(a)g\n(\\003oat)g(number)-5 b(.)-189 3095 y Fi(2.1.3)99 b(Binary)25\nb(F)n(ormat)-189 3283 y Fl(The)h(binary)g(format)f(is)h(not)f(allo)n\n(wed)g(for)i(ADDs.)33 b(As)26 b(a)h(consequence)f(we)g(concentrate)g\n(only)f(on)h(BDDs)g(in)g(this)-189 3403 y(section.)k(In)25\nb(binary)f(mode)h(nodes)f(are)i(represented)f(as)g(a)g(sequence)g(of)g\n(bytes,)f(encoding)g(tuples)-189 3606 y Fg(<Node-code>)-189\n3727 y([<Var-internal-info>])-189 3847 y([<Then-info>])-189\n3968 y([<Else-info>])-189 4171 y Fl(in)30 b(an)g(optimized)f(w)o(ay)-6\nb(.)46 b(Only)29 b(the)h(\\002rst)g(byte)g(\\(code\\))h(is)e(mandatory)-6\nb(,)30 b(while)g(inte)o(ger)f(inde)o(x)o(es)g(are)i(represented)-189\n4291 y(in)c(absolute)f(or)h(relati)n(v)o(e)f(mode,)h(where)h(relati)n\n(v)o(e)e(means)g(of)n(fset)h(with)f(respect)i(to)e(a)i(Then/Else)e\n(node)h(info.)37 b(The)-189 4412 y(best)23 b(between)g(absolute)f(and)h\n(relati)n(v)o(e)e(representation)i(is)f(chosen)h(and)g(relati)n(v)o(e)f\n(1)h(is)f(directly)g(coded)h(in)g Fd(<)p Fl(Node-)-189\n4532 y(code)p Fd(>)e Fl(without)f(an)o(y)g(e)o(xtra)h(info.)29\nb(Suppose)21 b(V)-11 b(ar\\(NodeId\\),)22 b(Then\\(NodeId\\))f(and)g\n(Else\\(NodeId\\))f(represent)i(infos)-189 4652 y(about)i(a)h(gi)n(v)o\n(en)f(node.)30 b Fd(<)p Fl(Node-code)p Fd(>)25 b Fl(is)f(a)h(byte)g\n(which)f(contains)g(the)h(follo)n(wing)e(bit)h(\\002elds)h(\\(MSB)g(to)g\n(LSB\\))-44 4856 y Fk(\\017)49 b Fl(Unused)24 b(:)31 b(1)24\nb(bit)-44 5059 y Fk(\\017)49 b Fl(V)-11 b(ariable:)30\nb(2)25 b(bits,)f(one)h(of)g(the)f(follo)n(wing)f(codes)171\n5288 y Fi(\\226)49 b Fl(DDDMP)p 636 5288 30 4 v 35 w(ABSOLUTE)p\n1191 5288 V 36 w(ID:)22 b(V)-11 b(ar\\(NodeId\\))22 b(is)f(represented)h\n(in)g(absolute)f(form)g(as)h Fd(<)p Fl(V)-11 b(ar)n(-internal-)270\n5408 y(info)p Fd(>)24 b Fl(=)h(V)-11 b(ar\\(NodeId\\))25\nb(follo)n(ws)e(\\(absolute)i(info\\))1794 5800 y(4)p eop\n%%Page: 5 5\n5 4 bop 171 218 a Fi(\\226)49 b Fl(DDDMP)p 636 218 30\n4 v 35 w(RELA)-11 b(TIVE)p 1147 218 V 36 w(ID:)32 b(V)-11\nb(ar\\(NodeId\\))32 b(is)g(represented)g(in)f(relati)n(v)o(e)g(form)h(as)\ng Fd(<)p Fl(V)-11 b(ar)n(-internal-)270 338 y(info\\277)24\nb(=)h(Min\\(V)-11 b(ar\\(Then\\(NodeId\\)\\),V)g(ar\\(Else\\(NodeId\\)\\)\\)-V)g\n(ar\\(NodeId\\))171 500 y Fi(\\226)49 b Fl(DDDMP)p 636 500\nV 35 w(RELA)-11 b(TIVE)p 1147 500 V 36 w(1:)27 b(the)19\nb(\\002eld)g Fd(<)p Fl(V)-11 b(ar)n(-internal-info)p Fd(>)18\nb Fl(does)h(not)f(follo)n(w)-6 b(,)18 b(because)h(V)-11\nb(ar\\(NodeId\\))270 620 y(=)25 b(Min\\(V)-11 b(ar\\(Then\\(NodeId\\)\\),V)g\n(ar\\(Else\\(NodeId\\)\\)\\)-1)171 782 y Fi(\\226)49 b Fl(DDDMP)p\n636 782 V 35 w(TERMIN)m(AL:)24 b(Node)h(is)f(a)h(terminal,)f(no)g(v)n\n(ar)h(info)g(required)-44 1011 y Fk(\\017)49 b Fl(T)25\nb(:)f(2)h(bits,)f(with)g(codes)h(similar)e(to)i(V)171\n1214 y Fi(\\226)49 b Fl(DDDMP)p 636 1214 V 35 w(ABSOLUTE)p\n1191 1214 V 36 w(ID:)20 b Fd(<)p Fl(Then-info)p Fd(>)f\nFl(is)h(represented)g(in)g(absolute)f(form)h(as)g Fd(<)p\nFl(Then-info)p Fd(>)270 1334 y Fl(=)25 b(Then\\(NodeId\\))171\n1496 y Fi(\\226)49 b Fl(DDDMP)p 636 1496 V 35 w(RELA)-11\nb(TIVE)p 1147 1496 V 36 w(ID:)28 b(Then\\(NodeId\\))f(is)g(represented)h\n(in)g(relati)n(v)o(e)e(form)i(as)g Fd(<)p Fl(Then-info)p\nFd(>)270 1617 y Fl(=)d(Nodeid-Then\\(NodeId\\))171 1779\ny Fi(\\226)49 b Fl(DDDMP)p 636 1779 V 35 w(RELA)-11 b(TIVE)p\n1147 1779 V 36 w(1:)30 b(no)25 b Fd(<)p Fl(Then-info)p\nFd(>)f Fl(follo)n(ws,)f(because)i(Then\\(NodeId\\))g(=)g(NodeId-1)171\n1941 y Fi(\\226)49 b Fl(DDDMP)p 636 1941 V 35 w(TERMIN)m(AL:)24\nb(Then)h(Node)f(is)h(a)g(terminal,)f(no)g(info)h(required)f(\\(for)i(R)l\n(OBDDs\\))-44 2144 y Fk(\\017)49 b Fl(Ecompl)24 b(:)30\nb(1)25 b(bit,)f(if)h(1)g(means)f(that)g(the)h(else)g(edge)g(is)f\n(complemented)-44 2347 y Fk(\\017)49 b Fl(E)25 b(:)f(2)h(bits,)f(with)g\n(codes)h(and)f(meanings)g(as)h(for)g(the)g(Then)f(edge)-189\n2551 y(DD)35 b(node)f(codes)h(are)h(written)e(as)h(one)g(byte.)60\nb Fd(<)p Fl(V)-11 b(ar)n(-internal-inde)o(x)p Fd(>)p\nFl(,)36 b Fd(<)p Fl(Then-inde)o(x)p Fd(>)p Fl(,)g Fd(<)p\nFl(Else-inde)o(x)p Fd(>)e Fl(\\(if)-189 2671 y(required\\))25\nb(are)h(represented)f(as)g(unsigned)e(inte)o(ger)h(v)n(alues)g(on)h(a)g\n(suf)n(\\002cient)f(set)h(of)g(bytes)f(\\(MSByte)h(\\002rst\\).)47\n2792 y(Inte)o(gers)h(of)f(an)o(y)h(length)e(are)j(written)e(as)h\n(sequences)g(of)g(\\224link)o(ed\\224)f(bytes)g(\\(MSByte)h(\\002rst\\).)34\nb(F)o(or)26 b(each)g(byte)-189 2912 y(7)f(bits)f(are)h(used)g(for)g\n(data)g(and)f(one)h(\\(MSBit\\))g(as)g(link)f(with)g(a)h(further)g(byte)g\n(\\(MSB)g(=)g(1)g(means)f(one)h(more)g(byte\\).)47 3032\ny(Lo)n(w)f(le)n(v)o(el)g(read/write)h(of)g(bytes)f(\\002lters)h\nFd(<)p Fl(CR)p Fd(>)p Fl(,)g Fd(<)p Fl(LF)p Fd(>)g Fl(and)g\nFd(<)p Fl(ctrl-Z)p Fd(>)f Fl(through)g(escape)h(sequences.)-189\n3327 y Fj(2.2)119 b(Implementation)-189 3515 y Fl(Store)24\nb(and)g(load)g(for)g(single)g(Boolean)g(functions)f(and)h(arrays)g(of)g\n(Boolean)g(functions)f(are)i(implemented.)k(More-)-189\n3635 y(o)o(v)o(er)l(,)37 b(the)e(current)h(presentation)f(includes)f\n(functions)h(to)g(retrie)n(v)o(e)g(v)n(ariables)f(names,)k(auxiliary)d\n(identi\\002erss,)-189 3756 y(and)c(all)g(the)g(information)f(contained)\nh(in)f(the)h(header)h(of)f(the)h(\\002les.)50 b(This)30\nb(information)g(can)h(be)h(used)f(as)g(a)g(pre-)-189\n3876 y(processing)19 b(step)g(for)i(load)e(operations.)28\nb(These)20 b(functions)f(allo)n(w)f(to)i(o)o(v)o(ercome)f(fe)n(w)g\n(limitations)f(of)h(the)h(pre)n(vious)-189 3997 y(implementations.)-189\n4263 y Fi(2.2.1)99 b(Storing)25 b(Decision)g(Diagrams)-189\n4450 y Fc(Dddmp)p 111 4450 V 35 w(cuddBddStor)l(e)f Fl(and)h\nFc(Dddmp)p 1195 4450 V 35 w(cuddBddArr)o(ayStor)l(e)e\nFl(are)j(the)f(tw)o(o)f(store)h(functions,)f(used)h(to)g(store)f(sin-)\n-189 4571 y(gle)f(BDD)h(or)g(a)f(forest)h(of)f(BDDs,)h(respecti)n(v)o\n(ely)-6 b(.)28 b(Internally)-6 b(,)23 b Fc(Dddmp)p 2275\n4571 V 35 w(cuddBddStor)l(e)f Fl(b)n(uilds)g(a)i(dummy)e(1)h(entry)-189\n4691 y(array)j(of)e(BDDs,)h(and)g(calls)g Fc(dddmp)p\n1102 4691 V 35 w(cuddBddArr)o(ayStor)l(e)p Fl(.)47 4811\ny(Since)30 b(con)l(v)o(ersion)e(from)h(DD)h(pointers)e(to)h(inte)o(ger)\nf(is)h(required,)i(DD)e(nodes)g(are)h(temporarily)e(remo)o(v)o(ed)-189\n4932 y(from)23 b(the)f(unique)h(hash.)29 b(This)23 b(mak)o(es)f(room)g\n(in)h(their)f Fc(ne)n(xt)h Fl(\\002eld)h(to)e(store)h(node)f(IDs.)30\nb(Nodes)23 b(are)h(re-link)o(ed)e(after)-189 5052 y(the)i(store)g\n(operation,)g(possible)f(in)g(a)i(modi\\002ed)e(order)-5\nb(.)31 b(Dumping)22 b(is)i(either)g(in)g(te)o(xt)f(or)i(binary)f(form.)\n30 b(Both)24 b(a)g(\\002le)-189 5173 y(pointer)31 b(\\()p\nFc(fp)p Fl(\\))g(and)g(a)h(\\002le)g(name)f(\\()p Fc(fname)p\nFl(\\))h(are)g(pro)o(vided)e(as)h(inputs)f(parameters)i(to)f(store)g\n(routines.)50 b(BDDs)31 b(are)-189 5293 y(stored)c(to)g(the)g(already)g\n(open)h(\\002le)f Fc(fp)p Fl(,)h(if)f(not)g(NULL.)g(Otherwise)f(\\002le)i\n(whose)f(name)g(is)g Fc(fname)g Fl(is)g(opened.)38 b(This)-189\n5413 y(is)24 b(intended)g(to)h(allo)n(w)f(either)g(DD)h(storage)g\n(within)e(\\002les)i(containing)f(other)g(data,)h(or)g(to)g(speci\\002c)g\n(\\002les.)1794 5800 y(5)p eop\n%%Page: 6 6\n6 5 bop -189 218 a Fi(2.2.2)99 b(Loading)25 b(Decision)g(Diagrams)-189\n405 y Fc(Dddmp)p 111 405 30 4 v 35 w(cuddBddLoad)37 b\nFl(and)h Fc(Dddmp)p 1219 405 V 35 w(cuddBddArr)o(ayLoad)f\nFl(are)h(the)g(load)g(functions,)i(which)e(read)g(a)g(BDD)-189\n526 y(dump)24 b(\\002le.)47 646 y(F)o(ollo)n(wing)34 b(the)h(store)h\n(function,)h(the)f(main)f(BDD)h(load)f(function,)j Fc(Dddmp)p\n2813 646 V 35 w(cuddBddLoad)p Fl(,)f(is)f(imple-)-189\n767 y(mented)g(by)g(calling)f(the)h(main)g(BDD-array)h(loading)f\n(function)f Fc(Dddmp)p 2466 767 V 35 w(cuddBddArr)o(ayLoad)p\nFl(.)63 b(A)37 b(dynamic)-189 887 y(v)o(ector)24 b(of)h(DD)g(pointers)f\n(is)g(temporarily)g(allocated)h(to)f(support)g(con)l(v)o(ersion)f(from)\ni(DD)g(inde)o(x)o(es)e(to)h(pointers.)47 1007 y(Se)n(v)o(eral)40\nb(criteria)f(are)i(supported)d(for)i(v)n(ariable)f(match)g(between)g\n(\\002le)h(and)g(DD)f(manager)l(,)k(practically)-189 1128\ny(allo)n(wing)37 b(v)n(ariable)h(permutations)f(or)i(compositions)d\n(while)i(loading)g(DDs.)71 b(V)-11 b(ariable)39 b(match)f(between)h\n(the)-189 1248 y(DD)32 b(manager)g(and)g(the)g(BDD)g(\\002le)g(is)g\n(optionally)e(based)i(in)f Fc(IDs)p Fl(,)j Fc(perids)p\nFl(,)f Fc(varnames)p Fl(,)g Fc(var)o(auxids)p Fl(;)g(also)f(direct)-189\n1369 y(composition)j(between)j Fc(IDs)g Fl(and)f Fc(composeids)g\nFl(is)g(supported.)68 b(The)38 b Fc(varmatc)o(hmode)e\nFl(parameter)i(is)f(used)g(to)-189 1489 y(select)27 b(mathing)e(mode.)\n37 b(More)27 b(in)f(detail,)h(tw)o(o)f(match)h(modes)f(use)h(the)f\n(information)g(within)f(the)i(DD)g(manager)l(,)-189 1609\ny(the)e(other)f(ones)h(use)g(e)o(xtra)f(information,)f(which)i(support)\nf(an)o(y)g(v)n(ariable)g(remap)h(or)g(change)g(in)f(the)h(ordering.)-44\n1813 y Fk(\\017)49 b Fl(v)n(armatchnode=DDDMP)p 1040 1813\nV 35 w(V)-13 b(AR)p 1272 1813 V 35 w(MA)i(TCHIDS)19 b(allo)n(ws)f\n(loading)g(a)h(DD)g(k)o(eeping)f(v)n(ariable)g(IDs)h(unchanged)55\n1933 y(\\(re)o(gardless)24 b(of)h(the)f(v)n(ariable)h(ordering)f(of)h\n(the)g(reading)f(manager)-5 b(.)55 2095 y(This)24 b(is)g(useful,)g(for)\nh(e)o(xample,)f(when)g(sw)o(apping)g(DDs)g(to)h(\\002le)g(and)f\n(restoring)g(them)g(later)h(from)f(\\002le,)h(after)55\n2215 y(possible)e(v)n(ariable)i(reordering)g(acti)n(v)n(ations.)-44\n2419 y Fk(\\017)49 b Fl(v)n(armatchnode=DDDMP)p 1040 2419\nV 35 w(V)-13 b(AR)p 1272 2419 V 35 w(MA)i(TCHPERMIDS)36\nb(is)e(used)h(to)f(allo)n(w)g(v)n(ariable)g(match)h(according)55\n2539 y(to)h(the)h(position)e(in)i(the)g(ordering)f(\\(retrie)n(v)o(ed)g\n(by)h(array)h(of)f(permutations)e(stored)h(on)h(\\002le)g(and)g(within)\n55 2660 y(the)h(reading)g(DD)h(manager\\).)72 b(A)38 b(possible)f\n(application)h(is)g(retrie)n(ving)f(BDDs)i(stored)f(after)h(dynamic)55\n2780 y(reordering,)28 b(from)g(a)g(DD)g(manager)g(where)h(all)e(v)n\n(ariable)h(IDs)f(map)h(their)f(position)g(in)g(the)h(ordering,)g(and)55\n2900 y(the)d(loaded)f(BDD)h(k)o(eeps)g(the)g(ordering)f(as)h(stored)f\n(on)h(\\002le.)-44 3104 y Fk(\\017)49 b Fl(v)n(armatchnode=DDDMP)p\n1040 3104 V 35 w(V)-13 b(AR)p 1272 3104 V 35 w(MA)i(TCHN)m(AMES)26\nb(requires)h(a)h(not)e(NULL)h(v)n(armatchmodes)f(param-)55\n3224 y(eter;)34 b(this)c(is)g(a)h(v)o(ector)g(of)g(strings)e(in)i\n(one-to-one)f(correspondence)h(with)f(v)n(ariable)h(IDs)f(of)h(the)g\n(reading)55 3344 y(manager)-5 b(.)40 b(V)-11 b(ariables)28\nb(in)g(the)g(DD)g(\\002le)g(read)h(are)g(matched)f(with)f(manager)h(v)n\n(ariables)f(according)h(to)g(their)55 3465 y(name)35\nb(\\(a)h(not)f(NULL)g(v)n(arnames)g(parameter)h(w)o(as)f(required)h\n(while)f(storing)f(the)h(DD)g(\\002le\\).)64 b(The)35 b(most)55\n3585 y(common)c(usage)h(of)g(this)f(feature)i(is)e(in)h(combination)e\n(with)i(a)g(v)n(ariable)g(ordering)g(stored)f(on)h(a)g(\\002le)h(and)55\n3706 y(based)28 b(on)h(v)n(ariables)f(names.)41 b(Names)29\nb(must)e(be)i(loaded)f(in)g(an)h(array)g(of)g(strings)e(and)i(passed)f\n(to)g(the)h(DD)55 3826 y(load)24 b(procedure.)-44 4029\ny Fk(\\017)49 b Fl(v)n(armatchnode=DDDMP)p 1040 4029 V\n35 w(V)-13 b(AR)p 1272 4029 V 35 w(MA)i(TCHIDS)25 b(has)g(a)g(meaning)f\n(similar)g(to)55 4150 y(DDDMP)p 421 4150 V 36 w(V)-13\nb(AR)p 654 4150 V 35 w(MA)i(TCHN)m(AMES)26 b(b)n(ut)h(inte)o(ger)f\n(auxiliary)g(IDs)h(are)h(used)f(instead)f(of)h(strings.)36\nb(The)28 b(ad-)55 4270 y(ditional)23 b(not)h(NULL)h(v)n(armathauxids)e\n(parameter)i(is)g(needed.)-44 4474 y Fk(\\017)49 b Fl(v)n\n(armatchnode=DDDMP)p 1040 4474 V 35 w(V)-13 b(AR)p 1272\n4474 V 35 w(COMPOSEIDS,)38 b(uses)f(the)f(additional)f(v)n\n(arcomposeids)g(parameter)55 4594 y(as)25 b(an)g(array)g(of)g(v)n\n(ariable)f(IDs)h(to)g(be)g(composed)f(with)g(IDs)g(stored)h(in)f\n(\\002le.)-189 4860 y Fi(2.2.3)99 b(DD)25 b(Load/Stor)n(e)h(and)f(V)-9\nb(ariable)25 b(Ordering)-189 5048 y Fl(Loading)31 b(of)i(Decision)e\n(Diagrams)h(from)g(\\002le)g(supports)f(dif)n(ferent)h(v)n(ariables)g\n(ordering)f(strate)o(gies,)i(as)g(already)-189 5168 y(pointed)23\nb(out)h(in)g(the)h(pre)n(vious)e(section.)30 b(This)24\nb(allo)n(ws)f(or)h(e)o(xample)g(storing)f(dif)n(ferent)i(BDDs)f(each)h\n(with)f(its)g(o)n(wn)-189 5288 y(v)n(ariable)29 b(ordering,)h(and)g(to)\nf(mer)n(ge)h(them)f(within)f(the)i(same)f(DD)h(manager)f(by)h(means)f\n(of)g(proper)h(load)f(opera-)-189 5409 y(tions.)44 b(W)-8\nb(e)30 b(suggest)f(using)f(DDDMP)p 1175 5409 V 36 w(V)-13\nb(AR)p 1408 5409 V 36 w(MA)i(TCHIDS)30 b(whene)n(v)o(er)f(IDs)g(k)o\n(eeps)h(on)f(representing)h(the)f(same)-189 5529 y(entities)24\nb(while)h(changing)f(v)n(ariable)h(ordering.)31 b(If)25\nb(this)f(is)h(not)f(true,)h(v)n(ariable)g(names)g(\\(if)g(a)n(v)n\n(ailable\\))f(or)i(auxiliary)1794 5800 y(6)p eop\n%%Page: 7 7\n7 6 bop -189 218 a Fl(IDs)34 b(are)h(a)g(good)e(w)o(ay)i(to)f\n(represent)g(in)l(v)n(ariant)f(attrib)n(uted)g(of)i(v)n(ariables)e\n(across)h(se)n(v)o(eral)g(runs)g(with)f(dif)n(ferent)-189\n338 y(orderings.)50 b(DDDMP)p 629 338 30 4 v 35 w(V)-13\nb(AR)p 861 338 V 36 w(COMPOSEIDS)32 b(is)f(an)h(alternati)n(v)o(e)e\n(solution,)h(that)g(practically)f(corresponds)h(to)-189\n459 y(cascading)23 b(DDDMP)p 593 459 V 36 w(V)-13 b(AR)p\n826 459 V 36 w(MA)i(TCHIDS)23 b(and)h(v)n(ariable)f(composition)e(with)\nh(a)i(gi)n(v)o(en)e(array)i(of)g(ne)n(w)f(v)n(ariables.)-189\n797 y Fo(3)143 b(CNF)35 b(Support)-189 1050 y Fj(3.1)119\nb(F)m(ormat)-189 1237 y Fl(Gi)n(v)o(en)30 b(a)h(BDD)g(representing)g(a)\ng(function)f Fd(f)11 b Fl(,)32 b(we)f(de)n(v)o(elop)f(three)h(basic)g\n(possible)e(w)o(ays)i(to)g(store)f(it)h(as)g(a)g(CNF)-189\n1358 y(formula.)54 b(In)33 b(each)h(method)d(the)i(set)g(of)f(clauses)h\n(is)f(written)h(after)g(an)g(header)g(part.)55 b(Only)32\nb(the)h(te)o(xt)f(format)g(is)-189 1478 y(allo)n(wed.)-189\n1743 y Fi(3.1.1)99 b(Header)-189 1931 y Fl(The)23 b(header)h(part)f(of)\ng(each)h(CNF)g(\\002le)f(has)g(basically)g(the)f(same)h(format)g\n(analyzed)g(for)h(the)f(BDD/ADD)g(\\002les.)30 b(F)o(or)-189\n2051 y(e)o(xample)h(the)g Fg(.rootids)f Fl(line)h(indicates)f(the)i(be)\no(ginning)d(of)j(each)g(CNF)g(formula)f(represented)h(by)f(a)h(single)\n-189 2172 y(BDD.)j(T)-8 b(o)34 b(be)g(compatible)f(with)h(the)g(DIMA)l\n(CS)h(format)f(each)h(header)f(line)g(start)g(with)g(the)g(character)h\n(\\223c\\224)g(to)-189 2292 y(indicate)24 b(a)h(comment.)-189\n2557 y Fi(3.1.2)99 b(T)-9 b(ext)25 b(F)n(ormat)-189 2745\ny Fl(The)j(\\002rst)g(method,)g(which)f(we)h(call)g Fi(Single-Node-Cut)p\nFl(,)j(models)26 b(each)j(BDD)f(nodes,)h(b)n(ut)e(the)h(ones)f(with)h\n(both)-189 2865 y(the)c(children)g(equal)h(to)f(the)g(constant)g(node)g\nFb(1)p Fl(,)g(as)h(a)g(multiple)o(x)o(er)-5 b(.)27 b(Each)e(multiple)o\n(x)o(er)d(has)i(tw)o(o)g(data)h(inputs)e(\\(i.e.,)-189\n2985 y(the)k(node)h(children\\),)f(a)h(selection)f(input)f(\\(i.e.,)i\n(the)g(node)f(v)n(ariable\\))g(and)h(one)f(output)f(\\(i.e.,)i(the)g\n(function)e(v)n(alue\\))-189 3106 y(whose)h(v)n(alue)f(is)h(assigned)f\n(to)h(an)g(additional)f(CNF)i(v)n(ariable.)37 b(The)27\nb(\\002nal)h(number)e(of)h(v)n(ariables)g(is)f(equal)h(to)g(the)-189\n3226 y(number)d(of)h(original)f(BDD)h(v)n(ariables)f(plus)g(the)h\n(number)f(of)h(\\223internal\\224)g(nodes)f(of)h(the)g(BDD.)47\n3346 y(The)k(second)f(method,)g(which)h(we)f(call)h Fi(Maxterm-Cut)p\nFl(,)h(create)g(clauses)e(starting)g(from)g Fd(f)39 b\nFl(corresponds)-189 3467 y(to)25 b(the)h(of)n(f-set)g(\\(i.e.,)f(all)h\n(the)g(paths-cubes)f(from)g(the)h(root)g(node)f(to)h(the)f(terminal)g\nFg(0)p Fl(\\))h(of)g(the)g(function)e Fd(f)11 b Fl(.)34\nb(W)l(ithin)-189 3587 y(the)29 b(BDD)g(for)g Fd(f)11\nb Fl(,)30 b(such)f(clauses)f(are)i(found)e(by)h(follo)n(wing)e(all)i\n(the)f(paths)h(from)f(the)h(root)g(node)f(of)h(the)g(BDD)g(to)-189\n3708 y(the)c(constant)f(node)g Fb(0)p Fl(.)31 b(The)25\nb(\\002nal)g(number)f(of)h(v)n(ariables)f(is)g(equal)h(to)f(the)h\n(number)f(of)h(original)f(BDD)h(v)n(ariables.)47 3828\ny(The)k(third)g(method,)g(which)g(we)g(call)g Fi(A)-5\nb(uxiliary-V)c(ariable-Cut)p Fl(,)30 b(is)f(a)h(trade-of)n(f)f(between)\ng(the)g(\\002rst)g(tw)o(o)-189 3948 y(strate)o(gies.)69\nb(Internal)37 b(v)n(ariables,)j(i.e.,)h(cutting)c(points,)j(are)e\n(added)g(in)f(order)h(to)g(decompose)f(the)h(BDD)g(into)-189\n4069 y(multiple)27 b(sub-trees)i(each)h(of)f(which)f(is)h(stored)g\n(follo)n(wing)e(the)h(second)h(strate)o(gy)-6 b(.)42\nb(The)29 b(trade-of)n(f)g(is)g(guided)f(by)-189 4189\ny(the)23 b(cutting)f(point)g(selection)g(strate)o(gy)-6\nb(,)22 b(and)h(we)g(e)o(xperiment)f(with)g(tw)o(o)g(methodologies.)28\nb(In)23 b(the)g(\\002rst)g(method,)g(a)-189 4310 y(ne)n(w)f(CNF)h(v)n\n(ariable)f(is)f(inserted)h(in)g(correspondence)g(to)g(the)g(shared)g\n(nodes)g(of)g(the)h(BDD,)f(i.e.,)h(the)f(nodes)f(which)-189\n4430 y(ha)n(v)o(e)29 b(more)g(than)h(one)f(incoming)f(edge.)45\nb(This)29 b(technique,)h(albeit)e(optimizing)g(the)h(number)g(of)h\n(literals)e(stored,)-189 4550 y(can)35 b(produce)g(clauses)f(with)g(a)h\n(high)f(number)h(of)f(literals)1894 4514 y Fh(2)1933\n4550 y Fl(.)60 b(T)-8 b(o)35 b(a)n(v)n(oid)f(this)g(dra)o(wback,)j(the)\ne(second)f(method,)-189 4671 y(introduces)28 b(all)g(the)g(pre)n\n(viously)e(indicated)i(cutting)f(points)g(more)h(the)h(ones)f\n(necessary)g(to)g(break)h(the)f(length)g(of)-189 4791\ny(the)d(path)f(to)h(a)g(maximum)e(\\(user\\))i(selected)g(v)n(alue.)47\n4911 y(Actually)-6 b(,)37 b(all)f(the)f(methods)g(described)h(abo)o(v)o\n(e)e(can)j(be)e(re-conducted)h(to)g(the)f(basic)h(idea)g(of)g(possibly)\n-189 5032 y(breaking)24 b(the)h(BDD)g(through)f(the)g(use)h(of)f\n(additional)g(cutting)f(v)n(ariables)h(and)h(dumping)e(the)h(paths)g\n(between)h(the)-189 5152 y(root)34 b(of)h(the)f(BDD,)h(the)g(cutting)e\n(v)n(ariables)h(and)g(the)h(terminal)e(nodes.)60 b(Such)35\nb(internal)f(cutting)f(v)n(ariables)h(are)-189 5273 y(added)25\nb(al)o(w)o(ays)f(\\(for)i(each)f(node\\),)g(ne)n(v)o(er)f(or)h(sometimes)\ne(respecti)n(v)o(ely)-6 b(.)p -189 5360 1607 4 v -77\n5422 a Ff(2)-40 5452 y Fe(This)27 b(v)n(alue)f(is)i(superiorly)d\n(limited)h(by)g(the)h(number)e(of)h(v)n(ariables)g(of)g(the)h(BDD,)g\n(i.e.,)h(the)f(longest)f(path)g(from)g(the)h(root)f(to)g(the)-189\n5551 y(terminal)19 b(node.)1794 5800 y Fl(7)p eop\n%%Page: 8 8\n8 7 bop 47 218 a Fl(While)33 b(the)f Fc(Single-Node-Cut)h\nFl(method)f(minimizes)f(the)i(length)f(of)h(the)f(clauses)h(produced,)i\n(b)n(ut)d(it)g(also)-189 338 y(requires)d(the)h(higher)f(number)g(of)g\n(CNF)i(v)n(ariables,)e(the)h Fc(Maxterm-Cut)f Fl(technique)g(minimizes)\nf(the)h(number)g(of)-189 459 y(CNF)36 b(v)n(ariables)d(required.)61\nb(This)34 b(adv)n(antage)g(is)g(counter)n(-balanced)h(by)f(the)h(f)o\n(act)g(that)f(in)g(the)h(w)o(orst)f(case)h(the)-189 579\ny(number)23 b(of)g(clauses,)g(as)h(well)e(as)i(the)f(total)f(number)h\n(of)g(literals,)g(produced)g(is)g(e)o(xponential)e(in)i(the)g(BDD)h\n(size)f(\\(in)-189 699 y(terms)28 b(of)i(number)e(of)h(nodes\\).)43\nb(The)29 b(application)f(of)h(this)f(method)g(is)g(then)h(limited)e(to)\ni(the)g(cases)g(in)f(which)h(the)-189 820 y(\\223of)n(f-set\\224)c(of)f\n(the)g(represented)h(function)f Fd(f)35 b Fl(has)24 b(a)h(small)f\n(cardinality)-6 b(.)29 b(The)c Fc(A)n(uxiliary-V)-11\nb(ariable-Cut)22 b Fl(strate)o(gy)h(is)-189 940 y(a)k(trade-of)n(f)h\n(between)f(the)g(\\002rst)g(tw)o(o)g(methods)f(and)h(the)g(ones)f(which)\nh(gi)n(v)o(es)f(more)h(compact)f(results.)37 b(As)27\nb(a)h(\\002nal)-189 1061 y(remark)f(notice)e(that)h(the)g(method)g(is)f\n(able)i(to)f(store)g(both)f(monolithic)f(BDDs)j(and)f(conjuncti)n(v)o\n(e)e(forms.)35 b(In)26 b(each)-189 1181 y(case)f(we)g(generate)h(CNF)f\n(\\002les)g(using)f(the)h(standard)f(DIMA)l(CS)i(format.)-189\n1365 y Fi(Example)f(1)49 b Fc(F)l(igur)l(e)20 b(1)h(shows)f(an)h(e)n\n(xample)g(of)f(how)h(our)f(pr)l(ocedur)l(e)h(works)f(to)h(stor)l(e)f(a)\nh(small)f(monolithic)f(BDD.)-189 1486 y(F)l(igur)l(e)j(1\\(a\\))h(r)l\n(epr)l(esents)g(a)g(BDD)g(with)g Fb(4)g Fc(nodes.)30\nb(BDD)23 b(variables)f(ar)l(e)h(named)g(after)f(inte)l(g)o(er)g(number)\no(s)h(r)o(anging)-189 1606 y(fr)l(om)k Fb(1)h Fc(to)g\nFb(4)p Fc(,)h(to)f(have)g(an)g(easy-to-follow)f(corr)l(espondence)h\n(with)g(the)g(CNF)h(variables.)40 b(F)l(igur)l(e)27 b(1\\(b\\),)i(\\(c\\))g\n(and)-189 1727 y(\\(d\\))c(show)g(the)f(corr)l(esponding)f(CNF)j(r)l(epr)\nl(esentations)d(g)o(ener)o(ated)h(by)h(our)f(thr)l(ee)h(methods.)30\nb(As)24 b(in)h(the)f(standar)l(d)-189 1847 y(format)i\nFa(p)i Fc(indicates)e(the)h(total)f(number)g(of)h(variables)f(used)h\n(\\()p Fb(4)g Fc(is)g(the)g(minimum)f(value)h(as)g(the)g(BDD)g(itself)f\n(has)-189 1967 y Fb(4)f Fc(variables\\),)e(and)i Fa(cnf)g\nFc(the)f(total)g(number)g(of)h(clauses.)47 2088 y(As)i(a)g(\\002nal)f(r)\nl(emark)h(notice)f(that)g(for)g(this)g(speci\\002c)h(e)n(xample)g(the)f\n(\\223Maxterm-Cut\\224)i(appr)l(oac)o(h)d(is)h(the)h(one)-189\n2208 y(whic)o(h)36 b(gives)g(the)g(most)f(compact)h(CNF)h(r)l(epr)l\n(esentation)e(b)n(ut)h(also)f(the)h(clause)g(with)g(the)g(lar)l(g)o\n(est)g(number)f(of)-189 2328 y(liter)o(als)23 b(\\()p\nFb(4)p Fc(\\).)188 2471 y\n 6339814 10777681 0 0 11709153 19997655 startTexFig\n 188 2471 a\n%%BeginDocument: bdd.eps\n%!PS-Adobe-2.0 EPSF-2.0\n%%Title: bdd.eps\n%%Creator: fig2dev Version 3.2 Patchlevel 3c\n%%CreationDate: Mon Sep  9 14:21:26 2002\n%%For: quer@pcsq (Stefano Quer)\n%%BoundingBox: 0 0 178 304\n%%Magnification: 1.0000\n%%EndComments\n/$F2psDict 200 dict def\n$F2psDict begin\n$F2psDict /mtrx matrix put\n/col-1 {0 setgray} bind def\n/col0 {0.000 0.000 0.000 srgb} bind def\n/col1 {0.000 0.000 1.000 srgb} bind def\n/col2 {0.000 1.000 0.000 srgb} bind def\n/col3 {0.000 1.000 1.000 srgb} bind def\n/col4 {1.000 0.000 0.000 srgb} bind def\n/col5 {1.000 0.000 1.000 srgb} bind def\n/col6 {1.000 1.000 0.000 srgb} bind def\n/col7 {1.000 1.000 1.000 srgb} bind def\n/col8 {0.000 0.000 0.560 srgb} bind def\n/col9 {0.000 0.000 0.690 srgb} bind def\n/col10 {0.000 0.000 0.820 srgb} bind def\n/col11 {0.530 0.810 1.000 srgb} bind def\n/col12 {0.000 0.560 0.000 srgb} bind def\n/col13 {0.000 0.690 0.000 srgb} bind def\n/col14 {0.000 0.820 0.000 srgb} bind def\n/col15 {0.000 0.560 0.560 srgb} bind def\n/col16 {0.000 0.690 0.690 srgb} bind def\n/col17 {0.000 0.820 0.820 srgb} bind def\n/col18 {0.560 0.000 0.000 srgb} bind def\n/col19 {0.690 0.000 0.000 srgb} bind def\n/col20 {0.820 0.000 0.000 srgb} bind def\n/col21 {0.560 0.000 0.560 srgb} bind def\n/col22 {0.690 0.000 0.690 srgb} bind def\n/col23 {0.820 0.000 0.820 srgb} bind def\n/col24 {0.500 0.190 0.000 srgb} bind def\n/col25 {0.630 0.250 0.000 srgb} bind def\n/col26 {0.750 0.380 0.000 srgb} bind def\n/col27 {1.000 0.500 0.500 srgb} bind def\n/col28 {1.000 0.630 0.630 srgb} bind def\n/col29 {1.000 0.750 0.750 srgb} bind def\n/col30 {1.000 0.880 0.880 srgb} bind def\n/col31 {1.000 0.840 0.000 srgb} bind def\n\nend\nsave\nnewpath 0 304 moveto 0 0 lineto 178 0 lineto 178 304 lineto closepath clip newpath\n-51.0 319.0 translate\n1 -1 scale\n\n/cp {closepath} bind def\n/ef {eofill} bind def\n/gr {grestore} bind def\n/gs {gsave} bind def\n/sa {save} bind def\n/rs {restore} bind def\n/l {lineto} bind def\n/m {moveto} bind def\n/rm {rmoveto} bind def\n/n {newpath} bind def\n/s {stroke} bind def\n/sh {show} bind def\n/slc {setlinecap} bind def\n/slj {setlinejoin} bind def\n/slw {setlinewidth} bind def\n/srgb {setrgbcolor} bind def\n/rot {rotate} bind def\n/sc {scale} bind def\n/sd {setdash} bind def\n/ff {findfont} bind def\n/sf {setfont} bind def\n/scf {scalefont} bind def\n/sw {stringwidth} bind def\n/tr {translate} bind def\n/tnt {dup dup currentrgbcolor\n  4 -2 roll dup 1 exch sub 3 -1 roll mul add\n  4 -2 roll dup 1 exch sub 3 -1 roll mul add\n  4 -2 roll dup 1 exch sub 3 -1 roll mul add srgb}\n  bind def\n/shd {dup dup currentrgbcolor 4 -2 roll mul 4 -2 roll mul\n  4 -2 roll mul srgb} bind def\n /DrawEllipse {\n\t/endangle exch def\n\t/startangle exch def\n\t/yrad exch def\n\t/xrad exch def\n\t/y exch def\n\t/x exch def\n\t/savematrix mtrx currentmatrix def\n\tx y tr xrad yrad sc 0 0 1 startangle endangle arc\n\tclosepath\n\tsavematrix setmatrix\n\t} def\n\n/$F2psBegin {$F2psDict begin /$F2psEnteredState save def} def\n/$F2psEnd {$F2psEnteredState restore end} def\n\n$F2psBegin\n%%Page: 1 1\n10 setmiterlimit\n 0.06299 0.06299 sc\n%\n% Fig objects follow\n%\n% Polyline\n15.000 slw\nn 2010 4515 m 2550 4515 l 2550 5040 l 2010 5040 l\n cp gs col0 s gr \n/Times-Roman ff 300.00 scf sf\n2205 4875 m\ngs 1 -1 sc (1) col0 sh gr\n% Ellipse\nn 1515 1800 270 270 0 360 DrawEllipse gs col0 s gr\n\n% Ellipse\nn 2250 900 270 270 0 360 DrawEllipse gs col0 s gr\n\n% Ellipse\nn 2970 2715 270 270 0 360 DrawEllipse gs col0 s gr\n\n% Ellipse\nn 2280 3705 270 270 0 360 DrawEllipse gs col0 s gr\n\n7.500 slw\n% Ellipse\nn 3555 3555 64 64 0 360 DrawEllipse gs 0.00 setgray ef gr gs col0 s gr\n\n% Ellipse\nn 2712 1726 64 64 0 360 DrawEllipse gs 0.00 setgray ef gr gs col0 s gr\n\n% Ellipse\nn 2430 4230 64 64 0 360 DrawEllipse gs 0.00 setgray ef gr gs col0 s gr\n\n% Polyline\n15.000 slw\nn 2805 2910 m\n 2250 3450 l gs col0 s gr \n% Polyline\n [90] 0 sd\ngs  clippath\n2940 2472 m 3010 2445 l 2931 2239 l 2957 2411 l 2861 2266 l cp\neoclip\nn 2460 1110 m\n 2970 2445 l gs col0 s gr gr\n [] 0 sd\n% arrowhead\nn 2861 2266 m 2957 2411 l 2931 2239 l 2908 2284 l 2861 2266 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\ngs  clippath\n1478 1511 m 1528 1568 l 1693 1422 l 1542 1506 l 1643 1366 l cp\neoclip\nn 2025 1080 m\n 1515 1530 l gs col0 s gr gr\n\n% arrowhead\nn 1643 1366 m 1542 1506 l 1693 1422 l 1643 1416 l 1643 1366 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\ngs  clippath\n2212 645 m 2287 645 l 2287 425 l 2250 594 l 2212 425 l cp\neoclip\nn 2250 270 m\n 2250 630 l gs col0 s gr gr\n\n% arrowhead\nn 2212 425 m 2250 594 l 2287 425 l 2250 459 l 2212 425 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n [90] 0 sd\ngs  clippath\n2692 2664 m 2732 2601 l 2546 2485 l 2670 2606 l 2506 2548 l cp\neoclip\nn 1710 2010 m\n 2700 2625 l gs col0 s gr gr\n [] 0 sd\n% arrowhead\nn 2506 2548 m 2670 2606 l 2546 2485 l 2555 2534 l 2506 2548 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n2 slj\n [90] 0 sd\ngs  clippath\n2504 4653 m 2539 4720 l 2733 4616 l 2567 4663 l 2698 4550 l cp\neoclip\nn 3180 2910 m 3181 2911 l 3183 2913 l 3186 2916 l 3192 2921 l 3200 2929 l\n 3210 2939 l 3223 2951 l 3238 2966 l 3255 2984 l 3274 3003 l\n 3295 3025 l 3317 3049 l 3339 3075 l 3362 3103 l 3385 3131 l\n 3407 3161 l 3429 3192 l 3450 3225 l 3470 3258 l 3488 3293 l\n 3504 3329 l 3519 3367 l 3531 3406 l 3541 3447 l 3548 3490 l\n 3552 3536 l 3552 3583 l 3548 3634 l 3540 3686 l 3528 3740 l\n 3510 3795 l 3490 3844 l 3467 3892 l 3441 3939 l 3413 3985 l\n 3382 4028 l 3350 4070 l 3317 4110 l 3283 4148 l 3248 4184 l\n 3211 4219 l 3174 4253 l 3136 4285 l 3098 4316 l 3059 4347 l\n 3020 4376 l 2980 4405 l 2941 4432 l 2901 4459 l 2862 4484 l\n 2824 4509 l 2787 4532 l 2751 4554 l 2717 4575 l 2686 4593 l\n 2657 4610 l 2631 4626 l 2608 4639 l 2589 4650 l 2572 4659 l\n 2559 4666 l 2550 4672 l\n 2535 4680 l gs col0 s gr gr\n [] 0 sd\n% arrowhead\n0 slj\nn 2698 4550 m 2567 4663 l 2733 4616 l 2686 4599 l 2698 4550 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n2 slj\ngs  clippath\n1985 4734 m 2028 4672 l 1847 4548 l 1965 4675 l 1804 4609 l cp\neoclip\nn 1350 2025 m 1349 2026 l 1348 2027 l 1345 2030 l 1340 2035 l 1334 2042 l\n 1325 2051 l 1314 2063 l 1301 2078 l 1286 2095 l 1268 2114 l\n 1249 2137 l 1227 2161 l 1205 2188 l 1181 2218 l 1156 2249 l\n 1131 2282 l 1105 2316 l 1080 2352 l 1054 2390 l 1029 2428 l\n 1005 2468 l 981 2509 l 959 2552 l 938 2595 l 918 2640 l\n 900 2687 l 884 2736 l 870 2786 l 858 2839 l 848 2894 l\n 841 2951 l 837 3011 l 836 3074 l 838 3139 l 845 3206 l\n 855 3275 l 870 3345 l 888 3412 l 910 3477 l 934 3542 l\n 961 3604 l 990 3665 l 1022 3723 l 1054 3779 l 1088 3833 l\n 1124 3885 l 1160 3935 l 1198 3983 l 1236 4029 l 1275 4074 l\n 1315 4118 l 1356 4160 l 1397 4201 l 1438 4241 l 1480 4280 l\n 1522 4318 l 1563 4355 l 1605 4390 l 1645 4424 l 1685 4457 l\n 1723 4488 l 1760 4517 l 1795 4545 l 1827 4570 l 1857 4593 l\n 1884 4613 l 1909 4632 l 1930 4647 l 1947 4660 l 1962 4671 l\n 1973 4679 l 1982 4686 l\n 1995 4695 l gs col0 s gr gr\n\n% arrowhead\n0 slj\nn 1804 4609 m 1965 4675 l 1847 4548 l 1854 4598 l 1804 4609 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n2 slj\n [90] 0 sd\ngs  clippath\n2300 4492 m 2363 4532 l 2481 4347 l 2359 4470 l 2417 4307 l cp\neoclip\nn 2340 3960 m 2341 3962 l 2344 3966 l 2348 3973 l 2354 3982 l 2362 3995 l\n 2370 4010 l 2379 4028 l 2389 4046 l 2397 4066 l 2406 4088 l\n 2413 4111 l 2420 4137 l 2425 4165 l 2429 4197 l 2430 4230 l\n 2429 4263 l 2425 4295 l 2420 4323 l 2413 4349 l 2406 4372 l\n 2397 4394 l 2389 4414 l 2379 4433 l 2370 4450 l 2362 4465 l\n 2354 4478 l\n 2340 4500 l gs col0 s gr gr\n [] 0 sd\n% arrowhead\n0 slj\nn 2417 4307 m 2359 4470 l 2481 4347 l 2431 4356 l 2417 4307 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n2 slj\ngs  clippath\n2136 4532 m 2199 4492 l 2082 4307 l 2141 4470 l 2018 4347 l cp\neoclip\nn 2160 3960 m 2159 3962 l 2156 3966 l 2152 3973 l 2146 3982 l 2138 3995 l\n 2130 4010 l 2121 4028 l 2111 4046 l 2103 4066 l 2094 4088 l\n 2087 4111 l 2080 4137 l 2075 4165 l 2071 4197 l 2070 4230 l\n 2071 4263 l 2075 4295 l 2080 4323 l 2087 4349 l 2094 4372 l\n 2103 4394 l 2111 4414 l 2121 4433 l 2130 4450 l 2138 4465 l\n 2146 4478 l\n 2160 4500 l gs col0 s gr gr\n\n% arrowhead\n0 slj\nn 2018 4347 m 2141 4470 l 2082 4307 l 2068 4356 l 2018 4347 l \n cp gs 0.00 setgray ef gr  col0 s\n/Times-Roman ff 300.00 scf sf\n2175 990 m\ngs 1 -1 sc (1) col0 sh gr\n/Times-Roman ff 300.00 scf sf\n1440 1890 m\ngs 1 -1 sc (2) col0 sh gr\n/Times-Roman ff 300.00 scf sf\n2895 2805 m\ngs 1 -1 sc (3) col0 sh gr\n/Times-Roman ff 300.00 scf sf\n2205 3795 m\ngs 1 -1 sc (4) col0 sh gr\n$F2psEnd\nrs\n\n%%EndDocument\n\n endTexFig\n 531 3990 a Fc(\\(a\\))1512 2504 y Fg(p)60 b(cnf)f(7)g(11)1512\n2624 y(-5)g(3)h(0)1512 2745 y(-5)f(4)h(0)1512 2865 y(5)g(-3)f(-4)g(0)\n1512 2985 y(6)h(-2)f(0)1512 3106 y(6)h(-5)f(0)1512 3226\ny(-6)g(2)h(5)f(0)1512 3347 y(7)h(1)f(5)h(0)1512 3467\ny(-7)f(1)h(-5)f(0)1512 3587 y(7)h(-1)f(-6)g(0)1512 3708\ny(-7)g(-1)h(6)f(0)1512 3828 y(7)h(0)1836 3990 y Fc(\\(b\\))2541\n2525 y Fg(p)f(cnf)g(4)h(3)2541 2645 y(1)f(-3)h(-4)f(0)2541\n2766 y(-1)g(2)h(3)f(0)2541 2886 y(-1)g(2)h(-3)f(4)h(0)2868\n3048 y Fc(\\(c\\))2541 3251 y Fg(p)f(cnf)g(5)h(5)2541 3371\ny(-5)f(1)h(0)2541 3492 y(5)f(-1)h(2)f(0)2541 3612 y(-3)g(-4)g(5)h(0)\n2541 3733 y(3)f(-5)h(0)2541 3853 y(-3)f(4)h(-5)f(0)2865\n3990 y Fc(\\(d\\))-189 4138 y Fl(Figure)46 b(1:)71 b(\\(a\\))47\nb(BDD;)e(\\(b\\))h(\\223Single-Node-Cut\\224)g(format;)55\nb(\\(c\\))46 b(\\223Maxterm-Cut\\224)g(format;)55 b(\\(d\\))45\nb(\\223)-8 b(Auxiliary-)-189 4258 y(V)d(ariable-Cut\\224)25\nb(F)o(ormat.)-189 4625 y Fj(3.2)119 b(Implementation)-189\n4813 y Fl(Store)25 b(and)g(Load)g(for)g(a)g(single)f(BDD)h(or)g(a)g\n(forest)g(of)g(BDDs)g(is)f(currently)h(implemented.)-189\n5073 y Fi(3.2.1)99 b(Storing)25 b(Decision)g(Diagrams)f(as)g(CNF)h(F)n\n(ormulas)-189 5260 y Fl(As)g(f)o(ar)g(as)g(the)g(storing)e(process)i\n(is)f(concerned)i(three)f(possible)e(formats)h(are)i(a)n(v)n(ailable:)\n-44 5431 y Fk(\\017)49 b Fl(DDDMP)p 421 5431 30 4 v 36\nw(CNF)p 650 5431 V 36 w(MODE)p 980 5431 V 35 w(NODE:)21\nb(store)f(a)h(BDD)h(by)e(introducing)f(an)i(auxiliary)g(v)n(ariable)f\n(for)h(each)g(BDD)55 5551 y(node)1794 5800 y(8)p eop\n%%Page: 9 9\n9 8 bop -44 218 a Fk(\\017)49 b Fl(DDDMP)p 421 218 30\n4 v 36 w(CNF)p 650 218 V 36 w(MODE)p 980 218 V 35 w(MAXTERM:)20\nb(store)g(a)h(BDD)h(by)e(follo)n(wing)f(the)h(maxterm)g(of)h(the)g\n(represented)55 338 y(function)-44 542 y Fk(\\017)49 b\nFl(DDDMP)p 421 542 V 36 w(CNF)p 650 542 V 36 w(MODE)p\n980 542 V 35 w(BEST)-5 b(:)32 b(trade-of)f(between)h(the)f(tw)o(o)f\n(pre)n(vious)g(solution,)h(trying)f(to)h(optimize)55\n662 y(the)25 b(number)f(of)h(literals)f(stored.)-189\n865 y(See)c(procedures)f(Dddmp)p 736 865 V 35 w(cuddBddStoreCnf)g(\\(to)\ng(store)f(a)h(single)f(BDD)i(as)e(a)i(CNF)f(formula\\))g(and)g(Dddmp)p\n3609 865 V 34 w(cuddBddArrayStoreCnf)-189 986 y(\\(to)25\nb(store)f(an)h(array)h(of)f(BDDs)g(as)f(a)i(CNF)f(formula\\).)-189\n1252 y Fi(3.2.2)99 b(Loadinf)26 b(CNF)e(F)n(ormulas)g(as)h(BDDs)-189\n1439 y Fl(As)g(f)o(ar)g(as)g(the)g(loading)e(process)i(is)f(concerned)i\n(three)f(possible)e(formats)i(are)g(a)n(v)n(ailable:)-44\n1643 y Fk(\\017)49 b Fl(DDDMP)p 421 1643 V 36 w(CNF)p\n650 1643 V 36 w(MODE)p 980 1643 V 35 w(NO)p 1159 1643\nV 36 w(CONJ:)25 b(Return)g(the)f(Clauses)h(without)f(Conjunction)-44\n1846 y Fk(\\017)49 b Fl(DDDMP)p 421 1846 V 36 w(CNF)p\n650 1846 V 36 w(MODE)p 980 1846 V 35 w(NO)p 1159 1846\nV 36 w(Q)o(U)l(ANT)-5 b(:)24 b(Return)h(the)g(sets)f(of)h(BDDs)g\n(without)f(Quanti\\002cation)-44 2050 y Fk(\\017)49 b Fl(DDDMP)p\n421 2050 V 36 w(CNF)p 650 2050 V 36 w(MODE)p 980 2050\nV 35 w(CONJ)p 1264 2050 V 36 w(Q)o(U)l(ANT)-5 b(:)23\nb(Return)h(the)g(sets)f(of)h(BDDs)g(AFTER)g(Existential)e(Quanti\\002-)\n55 2170 y(cation)-189 2373 y(See)e(procedures)f(Dddmp)p\n736 2373 V 35 w(cuddBddLoadCnf)f(\\(to)h(load)f(a)i(CNF)f(formula)g(as)g\n(a)g(single)f(BDD\\))h(and)g(Dddmp)p 3581 2373 V 35 w\n(cuddBddArrayLoadCnf)-189 2494 y(\\(to)35 b(load)h(a)g(CNF)g(formula)f\n(as)h(an)g(array)g(of)g(BDDs\\).)63 b(See)36 b(also)g(Dddmp)p\n2485 2494 V 34 w(cuddHeaderLoadCnf)h(to)e(load)g(the)-189\n2614 y(header)25 b(of)g(a)g(CNF)h(\\002le)f(to)g(gather)f(information)f\n(on)i(the)g(sa)n(v)o(ed)f(structure.)-189 2954 y Fo(4)143\nb(T)-13 b(est)35 b(Pr)m(ogram)f(and)h(Regr)m(ession)f(T)-13\nb(ests)-189 3177 y Fl(The)20 b Fc(testddmp.c)e Fl(\\002le,)j(pro)o\n(vided)d(with)h(this)f(distrib)n(ution,)g(e)o(x)o(empli\\002es)g(some)h\n(of)h(the)f(abo)o(v)o(e)g(features.)29 b(Moreo)o(v)o(er)l(,)-189\n3298 y(in)d(the)h Fc(e)n(xp)g Fl(e)o(xperiments)e(a)j(fe)n(w)e\n(scripts,)h(named)f Fc(test\\241n\\277.script)f Fl(are)i(a)n(v)n(ailable)\nf(for)h(a)g(sanity)f(check)h(of)g(the)g(tool)-189 3418\ny(and)e(to)f(tak)o(e)h(a)g(look)f(at)h(some)f(runs)h(e)o(x)o\n(empli\\002cation.)-189 3758 y Fo(5)143 b(Documentation)-189\n3981 y Fl(F)o(or)27 b(further)f(documentation)f(on)i(the)f(package)h\n(see)g(the)g(on-line)f(documentation)f(automatically)g(created)i(from)\n-189 4102 y(the)e(source)g(code)g(\\002les.)-189 4441\ny Fo(6)143 b(Ackno)o(wledgments)-189 4665 y Fl(W)-8 b(e)19\nb(are)h(particular)f(indebted)f(with)g(F)o(abio)g(Somenzi,)i(for)f\n(discussions,)f(advice,)i(and)f(for)g(including)e(the)i(DDDMP)-189\n4785 y(package)28 b(into)f(the)h(CUDD)g(distrib)n(ution.)37\nb(W)-8 b(e)29 b(also)e(thank)g(all)h(the)g(user)g(of)g(the)f(package)i\n(for)f(their)f(useful)h(indi-)-189 4905 y(cation)c(and)h(comments)f(on)\ng(the)h(it.)1794 5800 y(9)p eop\n%%Page: 10 10\n10 9 bop -189 218 a Fo(7)143 b(FTP)35 b(Site)-189 441\ny Fl(The)25 b(package)g(is)f(singularly)g(a)n(v)n(ailable)g(from:)-189\n645 y Fg(site:)59 b(ftp.polito.it)-189 765 y(user:)g(anonymous)-189\n885 y(directory:)f(/pub/research/dddmp)-189 1089 y Fl(or)25\nb(directly)f(from)h(the)f(author)h(WEB)g(pages:)-189\n1292 y Fg(WWW:)59 b(http://www.polito.it/\\230{cabodi)o(,quer)o(})-189\n1632 y Fo(8)143 b(F)l(eedback)-189 1855 y Fl(Send)25\nb(feedback)h(to:)-189 2059 y Fg(Gianpiero)58 b(Cabodi)g(&)i(Stefano)e\n(Quer)-189 2179 y(Politecnico)f(di)j(Torino)-189 2300\ny(Dipartimento)d(di)i(Automatica)f(e)i(Informatica)-189\n2420 y(Corso)f(Duca)g(degli)f(Abruzzi,)g(24)-189 2540\ny(I-10129)g(Torino)-189 2661 y(Italy)-189 2781 y(E-mail:)g\n({cabodi,quer}@polito.it)-189 2901 y(WWW:)h\n(http://www.polito.it/\\230{cabodi)o(,quer)o(})1769 5800\ny Fl(10)p eop\n%%Trailer\nend\nuserdict /end-hook known{end-hook}if\n%%EOF\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmp-2.0-Letter.ps",
    "content": "%!PS-Adobe-2.0\n%%Creator: dvips(k) 5.86 Copyright 1999 Radical Eye Software\n%%Title: dddmp-2.0.dvi\n%%Pages: 10\n%%PageOrder: Ascend\n%%BoundingBox: 0 0 612 792\n%%DocumentFonts: Times-Bold Times-Roman Courier Times-Italic Helvetica\n%%EndComments\n%DVIPSWebPage: (www.radicaleye.com)\n%DVIPSCommandLine: dvips -t letter -f dddmp-2.0\n%DVIPSParameters: dpi=600, compressed\n%DVIPSSource:  TeX output 2002.12.11:0557\n%%BeginProcSet: texc.pro\n%!\n/TeXDict 300 dict def TeXDict begin/N{def}def/B{bind def}N/S{exch}N/X{S\nN}B/A{dup}B/TR{translate}N/isls false N/vsize 11 72 mul N/hsize 8.5 72\nmul N/landplus90{false}def/@rigin{isls{[0 landplus90{1 -1}{-1 1}ifelse 0\n0 0]concat}if 72 Resolution div 72 VResolution div neg scale isls{\nlandplus90{VResolution 72 div vsize mul 0 exch}{Resolution -72 div hsize\nmul 0}ifelse TR}if Resolution VResolution vsize -72 div 1 add mul TR[\nmatrix currentmatrix{A A round sub abs 0.00001 lt{round}if}forall round\nexch round exch]setmatrix}N/@landscape{/isls true N}B/@manualfeed{\nstatusdict/manualfeed true put}B/@copies{/#copies X}B/FMat[1 0 0 -1 0 0]\nN/FBB[0 0 0 0]N/nn 0 N/IEn 0 N/ctr 0 N/df-tail{/nn 8 dict N nn begin\n/FontType 3 N/FontMatrix fntrx N/FontBBox FBB N string/base X array\n/BitMaps X/BuildChar{CharBuilder}N/Encoding IEn N end A{/foo setfont}2\narray copy cvx N load 0 nn put/ctr 0 N[}B/sf 0 N/df{/sf 1 N/fntrx FMat N\ndf-tail}B/dfs{div/sf X/fntrx[sf 0 0 sf neg 0 0]N df-tail}B/E{pop nn A\ndefinefont setfont}B/Cw{Cd A length 5 sub get}B/Ch{Cd A length 4 sub get\n}B/Cx{128 Cd A length 3 sub get sub}B/Cy{Cd A length 2 sub get 127 sub}\nB/Cdx{Cd A length 1 sub get}B/Ci{Cd A type/stringtype ne{ctr get/ctr ctr\n1 add N}if}B/id 0 N/rw 0 N/rc 0 N/gp 0 N/cp 0 N/G 0 N/CharBuilder{save 3\n1 roll S A/base get 2 index get S/BitMaps get S get/Cd X pop/ctr 0 N Cdx\n0 Cx Cy Ch sub Cx Cw add Cy setcachedevice Cw Ch true[1 0 0 -1 -.1 Cx\nsub Cy .1 sub]/id Ci N/rw Cw 7 add 8 idiv string N/rc 0 N/gp 0 N/cp 0 N{\nrc 0 ne{rc 1 sub/rc X rw}{G}ifelse}imagemask restore}B/G{{id gp get/gp\ngp 1 add N A 18 mod S 18 idiv pl S get exec}loop}B/adv{cp add/cp X}B\n/chg{rw cp id gp 4 index getinterval putinterval A gp add/gp X adv}B/nd{\n/cp 0 N rw exit}B/lsh{rw cp 2 copy get A 0 eq{pop 1}{A 255 eq{pop 254}{\nA A add 255 and S 1 and or}ifelse}ifelse put 1 adv}B/rsh{rw cp 2 copy\nget A 0 eq{pop 128}{A 255 eq{pop 127}{A 2 idiv S 128 and or}ifelse}\nifelse put 1 adv}B/clr{rw cp 2 index string putinterval adv}B/set{rw cp\nfillstr 0 4 index getinterval putinterval adv}B/fillstr 18 string 0 1 17\n{2 copy 255 put pop}for N/pl[{adv 1 chg}{adv 1 chg nd}{1 add chg}{1 add\nchg nd}{adv lsh}{adv lsh nd}{adv rsh}{adv rsh nd}{1 add adv}{/rc X nd}{\n1 add set}{1 add clr}{adv 2 chg}{adv 2 chg nd}{pop nd}]A{bind pop}\nforall N/D{/cc X A type/stringtype ne{]}if nn/base get cc ctr put nn\n/BitMaps get S ctr S sf 1 ne{A A length 1 sub A 2 index S get sf div put\n}if put/ctr ctr 1 add N}B/I{cc 1 add D}B/bop{userdict/bop-hook known{\nbop-hook}if/SI save N @rigin 0 0 moveto/V matrix currentmatrix A 1 get A\nmul exch 0 get A mul add .99 lt{/QV}{/RV}ifelse load def pop pop}N/eop{\nSI restore userdict/eop-hook known{eop-hook}if showpage}N/@start{\nuserdict/start-hook known{start-hook}if pop/VResolution X/Resolution X\n1000 div/DVImag X/IEn 256 array N 2 string 0 1 255{IEn S A 360 add 36 4\nindex cvrs cvn put}for pop 65781.76 div/vsize X 65781.76 div/hsize X}N\n/p{show}N/RMat[1 0 0 -1 0 0]N/BDot 260 string N/Rx 0 N/Ry 0 N/V{}B/RV/v{\n/Ry X/Rx X V}B statusdict begin/product where{pop false[(Display)(NeXT)\n(LaserWriter 16/600)]{A length product length le{A length product exch 0\nexch getinterval eq{pop true exit}if}{pop}ifelse}forall}{false}ifelse\nend{{gsave TR -.1 .1 TR 1 1 scale Rx Ry false RMat{BDot}imagemask\ngrestore}}{{gsave TR -.1 .1 TR Rx Ry scale 1 1 false RMat{BDot}\nimagemask grestore}}ifelse B/QV{gsave newpath transform round exch round\nexch itransform moveto Rx 0 rlineto 0 Ry neg rlineto Rx neg 0 rlineto\nfill grestore}B/a{moveto}B/delta 0 N/tail{A/delta X 0 rmoveto}B/M{S p\ndelta add tail}B/b{S p tail}B/c{-4 M}B/d{-3 M}B/e{-2 M}B/f{-1 M}B/g{0 M}\nB/h{1 M}B/i{2 M}B/j{3 M}B/k{4 M}B/w{0 rmoveto}B/l{p -4 w}B/m{p -3 w}B/n{\np -2 w}B/o{p -1 w}B/q{p 1 w}B/r{p 2 w}B/s{p 3 w}B/t{p 4 w}B/x{0 S\nrmoveto}B/y{3 2 roll p a}B/bos{/SS save N}B/eos{SS restore}B end\n\n%%EndProcSet\n%%BeginProcSet: 8r.enc\n% @@psencodingfile@{\n%   author = \"S. Rahtz, P. MacKay, Alan Jeffrey, B. Horn, K. Berry\",\n%   version = \"0.6\",\n%   date = \"22 June 1996\",\n%   filename = \"8r.enc\",\n%   email = \"kb@@mail.tug.org\",\n%   address = \"135 Center Hill Rd. // Plymouth, MA 02360\",\n%   codetable = \"ISO/ASCII\",\n%   checksum = \"119     662    4424\",\n%   docstring = \"Encoding for TrueType or Type 1 fonts to be used with TeX.\"\n% @}\n% \n% Idea is to have all the characters normally included in Type 1 fonts\n% available for typesetting. This is effectively the characters in Adobe\n% Standard Encoding + ISO Latin 1 + extra characters from Lucida.\n% \n% Character code assignments were made as follows:\n% \n% (1) the Windows ANSI characters are almost all in their Windows ANSI\n% positions, because some Windows users cannot easily reencode the\n% fonts, and it makes no difference on other systems. The only Windows\n% ANSI characters not available are those that make no sense for\n% typesetting -- rubout (127 decimal), nobreakspace (160), softhyphen\n% (173). quotesingle and grave are moved just because it's such an\n% irritation not having them in TeX positions.\n% \n% (2) Remaining characters are assigned arbitrarily to the lower part\n% of the range, avoiding 0, 10 and 13 in case we meet dumb software.\n% \n% (3) Y&Y Lucida Bright includes some extra text characters; in the\n% hopes that other PostScript fonts, perhaps created for public\n% consumption, will include them, they are included starting at 0x12.\n% \n% (4) Remaining positions left undefined are for use in (hopefully)\n% upward-compatible revisions, if someday more characters are generally\n% available.\n% \n% (5) hyphen appears twice for compatibility with both ASCII and Windows.\n% \n/TeXBase1Encoding [\n% 0x00 (encoded characters from Adobe Standard not in Windows 3.1)\n  /.notdef /dotaccent /fi /fl\n  /fraction /hungarumlaut /Lslash /lslash\n  /ogonek /ring /.notdef\n  /breve /minus /.notdef \n% These are the only two remaining unencoded characters, so may as\n% well include them.\n  /Zcaron /zcaron \n% 0x10\n /caron /dotlessi \n% (unusual TeX characters available in, e.g., Lucida Bright)\n /dotlessj /ff /ffi /ffl \n /.notdef /.notdef /.notdef /.notdef\n /.notdef /.notdef /.notdef /.notdef\n % very contentious; it's so painful not having quoteleft and quoteright\n % at 96 and 145 that we move the things normally found there down to here.\n /grave /quotesingle \n% 0x20 (ASCII begins)\n /space /exclam /quotedbl /numbersign\n /dollar /percent /ampersand /quoteright\n /parenleft /parenright /asterisk /plus /comma /hyphen /period /slash\n% 0x30\n /zero /one /two /three /four /five /six /seven\n /eight /nine /colon /semicolon /less /equal /greater /question\n% 0x40\n /at /A /B /C /D /E /F /G /H /I /J /K /L /M /N /O\n% 0x50\n /P /Q /R /S /T /U /V /W\n /X /Y /Z /bracketleft /backslash /bracketright /asciicircum /underscore\n% 0x60\n /quoteleft /a /b /c /d /e /f /g /h /i /j /k /l /m /n /o\n% 0x70\n /p /q /r /s /t /u /v /w\n /x /y /z /braceleft /bar /braceright /asciitilde\n /.notdef % rubout; ASCII ends\n% 0x80\n /.notdef /.notdef /quotesinglbase /florin\n /quotedblbase /ellipsis /dagger /daggerdbl\n /circumflex /perthousand /Scaron /guilsinglleft\n /OE /.notdef /.notdef /.notdef\n% 0x90\n /.notdef /.notdef /.notdef /quotedblleft\n /quotedblright /bullet /endash /emdash\n /tilde /trademark /scaron /guilsinglright\n /oe /.notdef /.notdef /Ydieresis\n% 0xA0\n /.notdef % nobreakspace\n /exclamdown /cent /sterling\n /currency /yen /brokenbar /section\n /dieresis /copyright /ordfeminine /guillemotleft\n /logicalnot\n /hyphen % Y&Y (also at 45); Windows' softhyphen\n /registered\n /macron\n% 0xD0\n /degree /plusminus /twosuperior /threesuperior\n /acute /mu /paragraph /periodcentered\n /cedilla /onesuperior /ordmasculine /guillemotright\n /onequarter /onehalf /threequarters /questiondown\n% 0xC0\n /Agrave /Aacute /Acircumflex /Atilde /Adieresis /Aring /AE /Ccedilla\n /Egrave /Eacute /Ecircumflex /Edieresis\n /Igrave /Iacute /Icircumflex /Idieresis\n% 0xD0\n /Eth /Ntilde /Ograve /Oacute\n /Ocircumflex /Otilde /Odieresis /multiply\n /Oslash /Ugrave /Uacute /Ucircumflex\n /Udieresis /Yacute /Thorn /germandbls\n% 0xE0\n /agrave /aacute /acircumflex /atilde\n /adieresis /aring /ae /ccedilla\n /egrave /eacute /ecircumflex /edieresis\n /igrave /iacute /icircumflex /idieresis\n% 0xF0\n /eth /ntilde /ograve /oacute\n /ocircumflex /otilde /odieresis /divide\n /oslash /ugrave /uacute /ucircumflex\n /udieresis /yacute /thorn /ydieresis\n] def\n\n%%EndProcSet\n%%BeginProcSet: texps.pro\n%!\nTeXDict begin/rf{findfont dup length 1 add dict begin{1 index/FID ne 2\nindex/UniqueID ne and{def}{pop pop}ifelse}forall[1 index 0 6 -1 roll\nexec 0 exch 5 -1 roll VResolution Resolution div mul neg 0 0]/Metrics\nexch def dict begin Encoding{exch dup type/integertype ne{pop pop 1 sub\ndup 0 le{pop}{[}ifelse}{FontMatrix 0 get div Metrics 0 get div def}\nifelse}forall Metrics/Metrics currentdict end def[2 index currentdict\nend definefont 3 -1 roll makefont/setfont cvx]cvx def}def/ObliqueSlant{\ndup sin S cos div neg}B/SlantFont{4 index mul add}def/ExtendFont{3 -1\nroll mul exch}def/ReEncodeFont{CharStrings rcheck{/Encoding false def\ndup[exch{dup CharStrings exch known not{pop/.notdef/Encoding true def}\nif}forall Encoding{]exch pop}{cleartomark}ifelse}if/Encoding exch def}\ndef end\n\n%%EndProcSet\n%%BeginProcSet: special.pro\n%!\nTeXDict begin/SDict 200 dict N SDict begin/@SpecialDefaults{/hs 612 N\n/vs 792 N/ho 0 N/vo 0 N/hsc 1 N/vsc 1 N/ang 0 N/CLIP 0 N/rwiSeen false N\n/rhiSeen false N/letter{}N/note{}N/a4{}N/legal{}N}B/@scaleunit 100 N\n/@hscale{@scaleunit div/hsc X}B/@vscale{@scaleunit div/vsc X}B/@hsize{\n/hs X/CLIP 1 N}B/@vsize{/vs X/CLIP 1 N}B/@clip{/CLIP 2 N}B/@hoffset{/ho\nX}B/@voffset{/vo X}B/@angle{/ang X}B/@rwi{10 div/rwi X/rwiSeen true N}B\n/@rhi{10 div/rhi X/rhiSeen true N}B/@llx{/llx X}B/@lly{/lly X}B/@urx{\n/urx X}B/@ury{/ury X}B/magscale true def end/@MacSetUp{userdict/md known\n{userdict/md get type/dicttype eq{userdict begin md length 10 add md\nmaxlength ge{/md md dup length 20 add dict copy def}if end md begin\n/letter{}N/note{}N/legal{}N/od{txpose 1 0 mtx defaultmatrix dtransform S\natan/pa X newpath clippath mark{transform{itransform moveto}}{transform{\nitransform lineto}}{6 -2 roll transform 6 -2 roll transform 6 -2 roll\ntransform{itransform 6 2 roll itransform 6 2 roll itransform 6 2 roll\ncurveto}}{{closepath}}pathforall newpath counttomark array astore/gc xdf\npop ct 39 0 put 10 fz 0 fs 2 F/|______Courier fnt invertflag{PaintBlack}\nif}N/txpose{pxs pys scale ppr aload pop por{noflips{pop S neg S TR pop 1\n-1 scale}if xflip yflip and{pop S neg S TR 180 rotate 1 -1 scale ppr 3\nget ppr 1 get neg sub neg ppr 2 get ppr 0 get neg sub neg TR}if xflip\nyflip not and{pop S neg S TR pop 180 rotate ppr 3 get ppr 1 get neg sub\nneg 0 TR}if yflip xflip not and{ppr 1 get neg ppr 0 get neg TR}if}{\nnoflips{TR pop pop 270 rotate 1 -1 scale}if xflip yflip and{TR pop pop\n90 rotate 1 -1 scale ppr 3 get ppr 1 get neg sub neg ppr 2 get ppr 0 get\nneg sub neg TR}if xflip yflip not and{TR pop pop 90 rotate ppr 3 get ppr\n1 get neg sub neg 0 TR}if yflip xflip not and{TR pop pop 270 rotate ppr\n2 get ppr 0 get neg sub neg 0 S TR}if}ifelse scaleby96{ppr aload pop 4\n-1 roll add 2 div 3 1 roll add 2 div 2 copy TR .96 dup scale neg S neg S\nTR}if}N/cp{pop pop showpage pm restore}N end}if}if}N/normalscale{\nResolution 72 div VResolution 72 div neg scale magscale{DVImag dup scale\n}if 0 setgray}N/psfts{S 65781.76 div N}N/startTexFig{/psf$SavedState\nsave N userdict maxlength dict begin/magscale true def normalscale\ncurrentpoint TR/psf$ury psfts/psf$urx psfts/psf$lly psfts/psf$llx psfts\n/psf$y psfts/psf$x psfts currentpoint/psf$cy X/psf$cx X/psf$sx psf$x\npsf$urx psf$llx sub div N/psf$sy psf$y psf$ury psf$lly sub div N psf$sx\npsf$sy scale psf$cx psf$sx div psf$llx sub psf$cy psf$sy div psf$ury sub\nTR/showpage{}N/erasepage{}N/copypage{}N/p 3 def @MacSetUp}N/doclip{\npsf$llx psf$lly psf$urx psf$ury currentpoint 6 2 roll newpath 4 copy 4 2\nroll moveto 6 -1 roll S lineto S lineto S lineto closepath clip newpath\nmoveto}N/endTexFig{end psf$SavedState restore}N/@beginspecial{SDict\nbegin/SpecialSave save N gsave normalscale currentpoint TR\n@SpecialDefaults count/ocount X/dcount countdictstack N}N/@setspecial{\nCLIP 1 eq{newpath 0 0 moveto hs 0 rlineto 0 vs rlineto hs neg 0 rlineto\nclosepath clip}if ho vo TR hsc vsc scale ang rotate rwiSeen{rwi urx llx\nsub div rhiSeen{rhi ury lly sub div}{dup}ifelse scale llx neg lly neg TR\n}{rhiSeen{rhi ury lly sub div dup scale llx neg lly neg TR}if}ifelse\nCLIP 2 eq{newpath llx lly moveto urx lly lineto urx ury lineto llx ury\nlineto closepath clip}if/showpage{}N/erasepage{}N/copypage{}N newpath}N\n/@endspecial{count ocount sub{pop}repeat countdictstack dcount sub{end}\nrepeat grestore SpecialSave restore end}N/@defspecial{SDict begin}N\n/@fedspecial{end}B/li{lineto}B/rl{rlineto}B/rc{rcurveto}B/np{/SaveX\ncurrentpoint/SaveY X N 1 setlinecap newpath}N/st{stroke SaveX SaveY\nmoveto}N/fil{fill SaveX SaveY moveto}N/ellipse{/endangle X/startangle X\n/yrad X/xrad X/savematrix matrix currentmatrix N TR xrad yrad scale 0 0\n1 startangle endangle arc savematrix setmatrix}N end\n\n%%EndProcSet\nTeXDict begin 40258431 52099146 1000 600 600 (dddmp-2.0.dvi)\n@start /Fa 143[55 1[55 7[28 2[50 99[{TeXBase1Encoding ReEncodeFont}4\n99.6264 /Helvetica rf\n%DVIPSBitmapFont: Fb cmr12 12 3\n/Fb 3 53 df<14FF010713E090381F81F890383E007C01FC133F4848EB1F8049130F4848\nEB07C04848EB03E0A2000F15F0491301001F15F8A2003F15FCA390C8FC4815FEA54815FF\nB3A46C15FEA56D1301003F15FCA3001F15F8A26C6CEB03F0A36C6CEB07E0000315C06D13\n0F6C6CEB1F806C6CEB3F00013E137C90381F81F8903807FFE0010090C7FC28447CC131>\n48 D<143014F013011303131F13FFB5FC13E713071200B3B3B0497E497E007FB6FCA320\n4278C131>I<ED0380A21507150FA2151F153FA2157F15FFA25CEC03BF153F1407140614\n0C141C141814301470146014C013011480EB03005B13065B131C13185B1370136013E048\n5A5B120390C7FC1206120E120C5A123812305A12E0B812C0A3C8383F8000ADEDFFE0027F\nEBFFC0A32A437DC231>52 D E\n%EndDVIPSBitmapFont\n/Fc 64[50 29[39 12[55 55 25[44 44 66 44 50 28 39 39 1[50\n50 50 72 28 44 1[28 50 50 28 44 50 44 50 50 10[61 2[50\n4[66 83 55 2[33 2[61 1[72 66 61 61 15[50 2[25 33 25 2[33\n33 37[50 2[{TeXBase1Encoding ReEncodeFont}45 99.6264\n/Times-Italic rf\n%DVIPSBitmapFont: Fd cmmi12 12 3\n/Fd 3 103 df<F001C0F007E0181FF07FC0943801FF00EF07FCEF1FF0EF7FC04C48C7FC\nEE0FFCEE3FF0EEFFC0030390C8FCED0FF8ED3FE0EDFF80DA03FEC9FCEC1FF8EC7FE09038\n01FF80D907FECAFCEB1FF0EB7FC04848CBFCEA07FCEA1FF0EA7FC048CCFCA2EA7FC0EA1F\nF0EA07FCEA01FF38007FC0EB1FF0EB07FE903801FF809038007FE0EC1FF8EC03FE913800\nFF80ED3FE0ED0FF8ED03FF030013C0EE3FF0EE0FFCEE01FF9338007FC0EF1FF0EF07FCEF\n01FF9438007FC0F01FE01807F001C03B3878B44C>60 D<127012FCB4FCEA7FC0EA1FF0EA\n07FCEA01FF38007FC0EB1FF0EB07FE903801FF809038007FE0EC1FF8EC03FE913800FF80\nED3FE0ED0FF8ED03FF030013C0EE3FF0EE0FFCEE01FF9338007FC0EF1FF0EF07FCEF01FF\n9438007FC0F01FE0A2F07FC0943801FF00EF07FCEF1FF0EF7FC04C48C7FCEE0FFCEE3FF0\nEEFFC0030390C8FCED0FF8ED3FE0EDFF80DA03FEC9FCEC1FF8EC7FE0903801FF80D907FE\nCAFCEB1FF0EB7FC04848CBFCEA07FCEA1FF0EA7FC048CCFC12FC12703B3878B44C>62\nD<EE07E0EE1FF8EE7C1CEEF80E923801F03E923803E07F17FFED07E116C117FE92380FC0\nFC177817004B5AA4153F93C7FCA45D157EA491B61280A3DA00FCC7FCA314015DA414035D\nA414075DA4140F5DA5141F5DA4143F92C8FCA45C147EA45CA45C1301A25CA2EA1C03007F\n5B12FF5C13075C4848C9FC12F8EA601EEA783CEA1FF0EA07C0305A7BC530>102\nD E\n%EndDVIPSBitmapFont\n/Fe 134[42 2[42 42 23 32 28 1[42 42 42 65 23 2[23 42\n42 28 37 42 1[42 37 12[51 10[28 4[60 1[55 19[21 28 21\n44[{TeXBase1Encoding ReEncodeFont}26 83.022 /Times-Roman\nrf\n%DVIPSBitmapFont: Ff cmr7 7 2\n/Ff 2 51 df<13381378EA01F8121F12FE12E01200B3AB487EB512F8A215267BA521>49\nD<13FF000313E0380E03F0381800F848137C48137E00787F12FC6CEB1F80A4127CC7FC15\n005C143E147E147C5C495A495A5C495A010EC7FC5B5B903870018013E0EA018039030003\n0012065A001FB5FC5A485BB5FCA219267DA521>I E\n%EndDVIPSBitmapFont\n/Fg 103[60 26[60 1[60 60 60 60 60 60 60 60 60 60 60 60\n60 60 60 60 2[60 60 60 60 60 60 60 60 60 3[60 1[60 3[60\n60 1[60 60 1[60 60 1[60 60 3[60 1[60 1[60 60 60 1[60\n60 1[60 1[60 1[60 60 60 60 60 60 60 60 60 60 60 60 60\n60 60 5[60 38[{TeXBase1Encoding ReEncodeFont}62 99.6264\n/Courier rf\n%DVIPSBitmapFont: Fh cmr8 8 2\n/Fh 2 51 df<130C133C137CEA03FC12FFEAFC7C1200B3B113FE387FFFFEA2172C7AAB23\n>49 D<EB7F803801FFF0380780FC380E003F48EB1F8048EB0FC05A0060EB07E012F000FC\n14F07E1403A3007C1307C7FCA215E0140F15C0141F1580EC3F00147E147C5C495A495A49\n5A495A011EC7FC5B5B4913305B485A4848136048C7FC000E14E0001FB5FC5A4814C0B6FC\nA21C2C7DAB23>I E\n%EndDVIPSBitmapFont\n/Fi 105[50 28[50 50 2[55 33 39 44 1[55 50 55 83 28 2[28\n1[50 33 44 55 44 55 50 10[72 1[66 55 3[78 72 94 66 3[78\n1[61 66 72 72 66 72 13[50 50 50 1[28 25 33 45[{\nTeXBase1Encoding ReEncodeFont}40 99.6264 /Times-Bold\nrf /Fj 139[40 1[53 1[66 60 66 100 33 2[33 3[53 3[60 23[47\n2[73 18[60 60 60 2[30 46[{TeXBase1Encoding ReEncodeFont}16\n119.552 /Times-Bold rf\n%DVIPSBitmapFont: Fk cmsy10 12 1\n/Fk 1 16 df<49B4FC010F13E0013F13F8497F48B6FC4815804815C04815E04815F0A248\n15F8A24815FCA3B712FEA96C15FCA36C15F8A26C15F0A26C15E06C15C06C15806C15006C\n6C13FC6D5B010F13E0010190C7FC27277BAB32>15 D E\n%EndDVIPSBitmapFont\n/Fl 64[44 42[44 44 24[44 50 50 72 50 50 28 39 33 50 50\n50 50 78 28 50 28 28 50 50 33 44 50 44 50 44 6[61 1[72\n94 72 72 61 55 66 72 55 72 72 89 61 1[39 33 72 72 55\n61 72 66 66 72 3[56 1[28 28 50 50 50 50 50 50 50 50 50\n50 28 25 33 25 2[33 33 36[55 55 2[{TeXBase1Encoding ReEncodeFont}74\n99.6264 /Times-Roman rf\n%DVIPSBitmapFont: Fm cmsy10 14.4 2\n/Fm 2 104 df<EE1FE0ED01FF150F92383FF800EDFFC04A90C7FC4A5A4A5A4A5A4A5A5D\nA2143F5DB3B1147F5D14FF92C8FC5B495A495A495AEB3FE0EBFF80D87FFEC9FCEAFFF8A2\nEA7FFEC66C7EEB3FE0EB0FF86D7E6D7E6D7E7F81147F81143FB3B181141FA2816E7E6E7E\n6E7E6E7E6E13C0ED3FF892380FFFE01501ED001F2B7878D93C>102\nD<B4FC13F813FF000313C038007FF0EB1FF8EB07FC6D7E6D7E6D7F147FA281143FB3B181\n141F81140F816E7E6E7E6E7E6E6C7EED3FF092380FFFC0030113E0A2030F13C092383FF0\n00ED7F804A48C7FC4A5A4A5A4A5A5D141F5D143F5DB3B1147F5DA214FF4990C8FC495A49\n5AEB1FF8EB7FF03803FFC0B5C9FC13F890CAFC2B7878D93C>I E\n%EndDVIPSBitmapFont\n/Fn 105[60 27[53 4[60 33 47 40 60 60 60 60 93 33 2[33\n1[60 40 53 60 53 60 53 7[86 4[73 66 1[86 66 3[73 2[40\n1[86 1[73 86 80 1[86 110 5[33 60 4[60 1[60 60 60 1[30\n40 30 44[{TeXBase1Encoding ReEncodeFont}42 119.552 /Times-Roman\nrf /Fo 136[104 1[80 48 56 64 1[80 72 80 120 40 80 1[40\n1[72 1[64 80 64 80 72 12[96 80 104 1[88 1[104 135 3[56\n2[88 1[104 104 96 104 6[48 1[72 72 72 72 72 72 72 72\n72 1[36 46[{TeXBase1Encoding ReEncodeFont}41 143.462\n/Times-Bold rf end\n%%EndProlog\n%%BeginSetup\n%%Feature: *Resolution 600dpi\nTeXDict begin\n%%BeginPaperSize: Letter\nletter\n%%EndPaperSize\n\n%%EndSetup\n%%Page: 1 1\n1 0 bop 472 600 a Fo(DDDMP:)35 b(Decision)f(Diagram)f(DuMP)j(package)\n1480 830 y(Release)e(2.0)462 1230 y Fn(Gianpiero)c(Cabodi)2402\n1232 y(Stef)o(ano)g(Quer)1316 1506 y(Politecnico)g(di)g(T)-10\nb(orino)1024 1656 y(Dip.)30 b(di)g(Automatica)g(e)g(Informatica)1119\n1805 y(Corso)f(Duca)h(de)n(gli)g(Abruzzi)g(24)1277 1955\ny(I\\22610129)e(T)-5 b(urin,)29 b(IT)-11 b(AL)f(Y)1038\n2104 y(E-mail:)38 b Fm(f)p Fn(cabodi,quer)p Fm(g)p Fn(@polito.it)-189\n2614 y Fo(1)143 b(Intr)m(oduction)-189 2837 y Fl(The)27\nb(DDDMP)h(package)f(de\\002nes)h(formats)f(and)g(rules)g(to)g(store)g\n(DD)g(on)g(\\002le.)39 b(More)27 b(in)g(particular)g(it)g(contains)g(a)\n-189 2958 y(set)e(of)g(functions)e(to)i(dump)e(\\(store)i(and)g(load\\))g\n(DDs)f(and)h(DD)g(forests)f(on)h(\\002le)g(in)f(dif)n(ferent)h(formats.)\n47 3078 y(In)30 b(the)g(present)g(implementation,)f(BDDs)h(\\(R)l\n(OBDDs\\))h(and)f(ADD)g(\\(Algebraic)g(Decision)g(Diagram\\))g(of)-189\n3199 y(the)g(CUDD)g(package)g(\\(v)o(ersion)f(2.3.0)g(or)h(higher\\))g\n(are)g(supported.)45 b(These)30 b(structures)f(can)h(be)g(represented)g\n(on)-189 3319 y(\\002les)25 b(either)g(in)f(te)o(xt,)g(binary)-6\nb(,)24 b(or)h(CNF)g(\\(DIMA)l(CS\\))h(formats.)47 3439\ny(The)f(main)f(rules)h(used)f(are)i(follo)n(wing)d(rules:)-44\n3643 y Fk(\\017)49 b Fl(A)30 b(\\002le)h(contains)e(a)i(single)e(BDD/ADD)\nh(or)g(a)h(forest)f(of)g(BDDs/ADD,)g(i.e.,)i(a)e(v)o(ector)g(of)g\n(Boolean)h(func-)55 3763 y(tions.)-44 3966 y Fk(\\017)49\nb Fl(Inte)o(ger)21 b(inde)o(x)o(es)f(are)i(used)f(instead)g(of)g\n(pointers)g(to)g(reference)i(nodes.)29 b(BDD/ADD)21 b(nodes)g(are)h\n(numbered)55 4087 y(with)j(contiguous)g(numbers,)g(from)h(1)g(to)f\n(NNodes)h(\\(total)f(number)h(of)g(nodes)g(on)f(a)i(\\002le\\).)35\nb(0)26 b(is)f(not)h(used)f(to)55 4207 y(allo)n(w)f(ne)o(gati)n(v)o(e)e\n(inde)o(x)o(es)h(for)i(complemented)f(edges.)-44 4411\ny Fk(\\017)49 b Fl(A)23 b(\\002le)g(contains)f(a)h(header)l(,)h\n(including)d(se)n(v)o(eral)h(informations)f(about)h(v)n(ariables)h(and)\nf(roots)g(of)h(BDD)h(func-)55 4531 y(tions,)32 b(then)e(the)h(list)g\n(of)g(nodes.)49 b(The)32 b(header)f(is)g(al)o(w)o(ays)g(represented)h\n(in)f(te)o(xt)f(format)h(\\(also)g(for)g(binary)55 4651\ny(\\002les\\).)g(BDDs,)25 b(ADDs,)f(and)h(CNF)h(\\002les)f(share)g(a)g\n(similar)f(format)g(header)-5 b(.)-44 4855 y Fk(\\017)49\nb Fl(BDD/ADD)40 b(nodes)g(are)h(listed)f(follo)n(wing)e(their)i\n(numbering,)j(which)d(is)g(produced)g(by)h(a)f(post-order)55\n4975 y(tra)n(v)o(ersal,)24 b(in)h(such)f(a)h(w)o(ay)g(that)g(a)g(node)f\n(is)h(al)o(w)o(ays)f(listed)g(after)h(its)f(Then/Else)g(children.)47\n5179 y(In)32 b(the)f(sequel)g(we)g(describe)h(more)f(in)g(detail)f(the)\nh(dif)n(ferent)g(formats)g(and)g(procedures)h(a)n(v)n(ailable.)49\nb(First)-189 5299 y(of)26 b(all,)f(we)h(describe)f(BDDs)h(and)g(ADDs)f\n(formats)g(and)g(procedure.)33 b(Secondly)-6 b(,)26 b(we)f(concentrate)\nh(on)f(CNF)i(\\002les,)-189 5419 y(i.e.,)e(ho)n(w)f(to)g(translate)g(a)i\n(BDD)f(or)g(a)g(forest)g(of)f(BDDs)h(into)f(a)h(CNF)h(formula)e(and)h\n(vice-v)o(ersa.)1794 5800 y(1)p eop\n%%Page: 2 2\n2 1 bop -189 218 a Fo(2)143 b(BDD)35 b(and)g(ADD)g(Support)-189\n441 y Fl(In)23 b(this)f(section)g(we)g(describe)h(format)g(and)f\n(procedure)h(re)o(garding)f(BDDs)h(and)f(ADDs.)30 b(W)-8\nb(e)23 b(speci\\002cally)g(refer)g(to)-189 562 y(BDDs)h(in)g(the)g\n(description)e(as)j(ADD)e(may)h(be)g(seen)g(as)h(an)f(e)o(xtension)e\n(and)i(will)f(be)h(described)g(later)-5 b(.)30 b(First)24\nb(of)g(all,)-189 682 y(we)29 b(concentrate)f(on)g(the)g(format)g(used)g\n(to)g(store)g(these)g(structure,)h(then)f(we)g(describe)h(the)f\n(procedure)h(a)n(v)n(ailable)-189 802 y(to)24 b(store)h(and)g(load)f\n(them.)-189 1094 y Fj(2.1)119 b(F)m(ormat)-189 1281 y\nFl(BDD)30 b(dump)f(\\002les)g(are)i(composed)e(of)g(tw)o(o)g(sections:)\n40 b(The)29 b(header)h(and)g(the)f(list)g(of)h(nodes.)44\nb(The)30 b(header)g(has)g(a)-189 1402 y(common)c(\\(te)o(xt\\))h(format,)\nh(while)e(the)i(list)e(of)h(nodes)g(is)g(either)g(in)g(te)o(xt)g(or)g\n(binary)g(format.)38 b(In)28 b(te)o(xt)e(format)h(nodes)-189\n1522 y(are)33 b(represented)f(with)f(redundant)g(informations,)h(where)\nh(the)f(main)f(goal)g(is)h(readability)-6 b(,)32 b(while)g(the)f\n(purpose)-189 1642 y(of)i(binary)f(format)g(is)g(minimizing)e(the)i(o)o\n(v)o(erall)f(storage)h(size)h(for)g(BDD)f(nodes.)54 b(The)32\nb(header)h(format)f(is)g(k)o(ept)-189 1763 y(common)h(to)h(te)o(xt)g\n(and)g(binary)g(formats)g(for)h(sak)o(e)f(of)h(simplicity:)47\nb(No)34 b(particular)g(optimization)f(is)h(presently)-189\n1883 y(done)29 b(on)f(binary)h(\\002le)g(headers,)h(whose)f(size)g(is)f\n(by)h(f)o(ar)g(dominated)f(by)h(node)f(lists)g(in)g(the)h(case)g(of)g\n(lar)n(ge)h(BDDs)-189 2003 y(\\(se)n(v)o(eral)24 b(thousands)g(of)h(DD)f\n(nodes\\).)-189 2266 y Fi(2.1.1)99 b(Header)-189 2453\ny Fl(The)23 b(header)h(has)f(the)g(same)g(format)g(both)g(for)g(te)o\n(xtual)f(and)i(binary)e(dump.)30 b(F)o(or)23 b(sak)o(e)g(of)h\n(generality)e(and)h(because)-189 2574 y(of)f(dynamic)g(v)n(ariable)g\n(ordering)g(both)f(v)n(ariable)h(IDs)g(and)g(permutations)2377\n2537 y Fh(1)2438 2574 y Fl(are)h(included.)29 b(Names)22\nb(are)h(optionally)-189 2694 y(listed)35 b(for)h(input)f(v)n(ariables)g\n(and)h(for)h(the)e(stored)h(functions.)63 b(Ne)n(w)36\nb(auxiliary)f(IDs)h(are)h(also)e(allo)n(wed.)64 b(Only)-189\n2814 y(the)34 b(v)n(ariables)f(in)g(the)h(true)g(support)f(of)h(the)f\n(stored)h(BDDs)g(are)h(listed.)56 b(All)34 b(information)e(on)i(v)n\n(ariables)f(\\(IDs,)-189 2935 y(permutations,)c(names,)i(auxiliary)e\n(IDs\\))h(sorted)g(by)g(IDs,)h(and)e(the)o(y)h(are)g(restricted)g(to)f\n(the)h(true)g(support)f(of)h(the)-189 3055 y(dumped)22\nb(BDD,)h(while)g(IDs)g(and)f(permutations)g(are)h(referred)i(to)d(the)h\n(writing)f(BDD)h(manager)-5 b(.)30 b(Names)22 b(can)i(thus)-189\n3175 y(be)h(sorted)f(by)h(v)n(ariable)f(ordering)h(by)f(permuting)g\n(them)g(according)h(to)f(the)h(permutations)e(stored)h(in)h(the)f\n(\\002le.)47 3296 y(As)h(an)g(e)o(xample,)f(the)g(header)i(\\(in)e(te)o\n(xt)g(mode\\))h(of)f(the)h(ne)o(xt)f(state)h(functions)e(of)i(circuit)g\n(s27)f(follo)n(ws:)-189 3494 y Fg(.ver)59 b(DDDMP-2.0)-189\n3615 y(.mode)g(A)-189 3735 y(.varinfo)f(3)-189 3855 y(.dd)h(s27-delta)\n-189 3976 y(.nnodes)f(16)-189 4096 y(.nvars)g(10)-189\n4216 y(.nsuppvars)g(7)-189 4337 y(.varnames)g(G0)h(G1)g(G2)h(G3)f(G5)g\n(G6)h(G7)-189 4457 y(.orderedvarnames)c(G0)k(G1)f(G2)g(G3)h(G5)f(G6)g\n(G7)-189 4578 y(.ids)g(0)g(1)h(2)g(3)f(4)h(5)f(6)-189\n4698 y(.permids)f(0)i(1)f(2)h(3)f(5)h(7)f(9)-189 4818\ny(.auxids)f(1)i(2)f(3)h(4)f(5)h(6)g(7)-189 4939 y(.nroots)e(3)-189\n5059 y(.rootids)g(6)i(-13)f(-16)-189 5179 y(.rootnames)f(G10)h(G11)g\n(G13)47 5378 y Fl(The)25 b(lines)f(contain)g(the)h(follo)n(wing)e\n(informations:)p -189 5460 1607 4 v -77 5521 a Ff(1)-40\n5551 y Fe(The)d(permutation)e(of)i(the)g(i-th)h(v)n(ariable)e(ID)h(is)h\n(the)f(relati)n(v)o(e)g(position)f(of)h(the)g(v)n(ariable)f(in)i(the)f\n(ordering.)1794 5800 y Fl(2)p eop\n%%Page: 3 3\n3 2 bop -44 218 a Fk(\\017)49 b Fl(Dddmp)24 b(v)o(ersion)f(information.)\n-44 411 y Fk(\\017)49 b Fl(File)25 b(mode)f(\\(A)h(for)g(ASCII)h(te)o\n(xt,)e(B)h(for)g(binary)g(mode\\).)-44 604 y Fk(\\017)49\nb Fl(V)-11 b(ar)n(-e)o(xtra-info)25 b(\\(0:)30 b(v)n(ariable)24\nb(ID,)h(1:)31 b(permID,)24 b(2:)31 b(aux)25 b(ID,)g(3:)30\nb(v)n(ariable)24 b(name,)h(4)g(no)f(e)o(xtra)h(info\\).)-44\n797 y Fk(\\017)49 b Fl(Name)25 b(of)g(dd)f(\\(optional\\).)-44\n990 y Fk(\\017)49 b Fl(T)-8 b(otal)24 b(number)g(of)h(nodes)g(in)f(the)h\n(\\002le.)-44 1183 y Fk(\\017)49 b Fl(Number)24 b(of)h(v)n(ariables)f(of)\nh(the)g(writing)f(DD)g(manager)-5 b(.)-44 1375 y Fk(\\017)49\nb Fl(Number)24 b(of)h(v)n(ariables)f(in)h(the)f(true)h(support)f(of)h\n(the)f(stored)h(DDs.)-44 1568 y Fk(\\017)49 b Fl(V)-11\nb(ariable)25 b(names)f(\\(optional\\))g(for)h(all)g(the)f(v)n(ariables)g\n(in)h(the)f(BDD/ADD)h(support.)-44 1761 y Fk(\\017)49\nb Fl(V)-11 b(ariable)20 b(names)g(for)h(all)f(the)g(v)n(ariables)f(in)h\n(the)g(DD)h(manager)f(during)g(the)g(storing)f(phase.)29\nb(Notice)20 b(that)g(this)55 1882 y(information)k(w)o(as)h(not)g\n(stored)g(by)g(pre)n(vious)f(v)o(ersions)g(of)i(the)f(same)g(tool.)32\nb(Full)25 b(backw)o(ard)g(compatibility)55 2002 y(is)f(guaranteed)h(by)\ng(the)f(present)h(implementation)d(of)j(the)g(tool.)-44\n2195 y Fk(\\017)49 b Fl(V)-11 b(ariable)25 b(IDs.)-44\n2388 y Fk(\\017)49 b Fl(V)-11 b(ariable)25 b(permuted)f(IDs.)-44\n2581 y Fk(\\017)49 b Fl(V)-11 b(ariable)25 b(auxiliary)f(IDs)h\n(\\(optional\\).)-44 2774 y Fk(\\017)49 b Fl(Number)24 b(of)h(BDD)g\n(roots.)-44 2967 y Fk(\\017)49 b Fl(Inde)o(x)o(es)24 b(of)h(BDD)g(roots)\nf(\\(complemented)g(edges)g(allo)n(wed\\).)-44 3160 y Fk(\\017)49\nb Fl(Names)24 b(of)h(BDD)h(roots)e(\\(optional\\).)-189\n3332 y(Notice)h(that)f(a)h(\\002eld)-189 3504 y Fg(.add)-189\n3676 y Fl(is)f(present)h(after)g(the)g(dddmp)f(v)o(ersion)f(for)j\n(\\002les)e(containing)g(ADDs.)-189 3936 y Fi(2.1.2)99\nb(T)-9 b(ext)25 b(F)n(ormat)-189 4124 y Fl(In)g(te)o(xt)f(mode)g(nodes)\ng(are)i(listed)e(on)g(a)h(te)o(xt)f(line)h(basis.)30\nb(Each)25 b(a)g(node)f(is)h(represented)g(as)-189 4296\ny Fg(<Node-index>)57 b([<Var-extra-info>])f(<Var-internal-index>)588\n4416 y(<Then-index>)h(<Else-index>)-189 4588 y Fl(where)25\nb(all)g(inde)o(x)o(es)e(are)j(inte)o(ger)e(numbers.)47\n4709 y(This)h(format)g(is)g(redundant)f(\\(due)i(to)f(the)g(node)g\n(ordering,)g Fd(<)p Fl(Node-inde)o(x)p Fd(>)f Fl(is)g(and)i\n(incremental)e(inte)o(ger\\))-189 4829 y(b)n(ut)g(we)h(k)o(eep)g(it)g\n(for)g(readability)-6 b(.)47 4949 y Fd(<)p Fl(V)-11 b(ar)n(-e)o\n(xtra-info)p Fd(>)34 b Fl(\\(optional)e(redundant)i(\\002eld\\))g(is)f\n(either)h(an)g(inte)o(ger)f(\\(ID,)h(PermID,)g(or)g(auxID\\))g(or)g(a)\n-189 5070 y(string)k(\\(v)n(ariable)h(name\\).)75 b Fd(<)p\nFl(V)-11 b(ar)n(-internal-inde)o(x)p Fd(>)38 b Fl(is)h(an)g(internal)g\n(v)n(ariable)g(inde)o(x:)59 b(V)-11 b(ariables)39 b(in)g(the)g(true)\n-189 5190 y(support)25 b(of)h(the)g(stored)g(BDDs)g(are)h(numbered)e\n(with)g(ascending)h(inte)o(gers)f(starting)g(from)h(0,)g(and)g(follo)n\n(wing)e(the)-189 5311 y(v)n(ariable)g(ordering.)31 b\nFd(<)p Fl(Then-inde)o(x)p Fd(>)23 b Fl(and)i Fd(<)p Fl(Else-inde)o(x)p\nFd(>)e Fl(are)j(signed)e(inde)o(x)o(es)f(of)i(children)f(nodes.)47\n5431 y(In)h(the)f(follo)n(wing,)f(we)i(report)f(the)g(list)g(of)h\n(nodes)f(of)g(the)h(s27)f(ne)o(xt)f(state)i(functions)e(\\(see)i(pre)n\n(vious)e(header)-189 5551 y(e)o(xample\\):)1794 5800 y(3)p\neop\n%%Page: 4 4\n4 3 bop -189 218 a Fg(.nodes)-189 338 y(1)60 b(T)f(1)h(0)f(0)-189\n459 y(2)h(G7)f(6)g(1)h(-1)-189 579 y(3)g(G5)f(4)g(1)h(2)-189\n699 y(4)g(G3)f(3)g(3)h(1)-189 820 y(5)g(G1)f(1)g(1)h(4)-189\n940 y(6)g(G0)f(0)g(5)h(-1)-189 1061 y(7)g(G6)f(5)g(1)h(-1)-189\n1181 y(8)g(G5)f(4)g(1)h(-7)-189 1301 y(9)g(G6)f(5)g(1)h(-2)-189\n1422 y(10)f(G5)h(4)f(1)h(-9)-189 1542 y(11)f(G3)h(3)f(10)h(8)-189\n1662 y(12)f(G1)h(1)f(8)h(11)-189 1783 y(13)f(G0)h(0)f(5)h(12)-189\n1903 y(14)f(G2)h(2)f(1)h(-1)-189 2024 y(15)f(G2)h(2)f(1)h(-2)-189\n2144 y(16)f(G1)h(1)f(14)h(15)-189 2264 y(.end)-189 2468\ny Fl(The)27 b(list)f(is)h(enclosed)g(between)g(the)g\nFg(.nodes)f Fl(and)h Fg(.end)f Fl(lines.)37 b(First)27\nb(node)g(is)g(the)g(one)g(constant,)f(each)i(node)-189\n2588 y(contains)c(the)h(optional)e(v)n(ariable)h(name.)47\n2708 y(F)o(or)29 b(ADDs)f(more)h(than)f(one)h(constant)e(is)i(stored)f\n(in)g(the)g(\\002le.)43 b(Each)29 b(constant)f(has)g(the)h(same)f\n(format)h(we)-189 2829 y(ha)n(v)o(e)c(just)e(analyzed)i(for)g(the)g\n(BDD)g(b)n(ut)g(the)f(represented)h(v)n(alue)f(is)h(stored)f(as)h(a)g\n(\\003oat)g(number)-5 b(.)-189 3095 y Fi(2.1.3)99 b(Binary)25\nb(F)n(ormat)-189 3283 y Fl(The)h(binary)g(format)f(is)h(not)f(allo)n\n(wed)g(for)i(ADDs.)33 b(As)26 b(a)h(consequence)f(we)g(concentrate)g\n(only)f(on)h(BDDs)g(in)g(this)-189 3403 y(section.)k(In)25\nb(binary)f(mode)h(nodes)f(are)i(represented)f(as)g(a)g(sequence)g(of)g\n(bytes,)f(encoding)g(tuples)-189 3606 y Fg(<Node-code>)-189\n3727 y([<Var-internal-info>])-189 3847 y([<Then-info>])-189\n3968 y([<Else-info>])-189 4171 y Fl(in)30 b(an)g(optimized)f(w)o(ay)-6\nb(.)46 b(Only)29 b(the)h(\\002rst)g(byte)g(\\(code\\))h(is)e(mandatory)-6\nb(,)30 b(while)g(inte)o(ger)f(inde)o(x)o(es)g(are)i(represented)-189\n4291 y(in)c(absolute)f(or)h(relati)n(v)o(e)f(mode,)h(where)h(relati)n\n(v)o(e)e(means)g(of)n(fset)h(with)f(respect)i(to)e(a)i(Then/Else)e\n(node)h(info.)37 b(The)-189 4412 y(best)23 b(between)g(absolute)f(and)h\n(relati)n(v)o(e)e(representation)i(is)f(chosen)h(and)g(relati)n(v)o(e)f\n(1)h(is)f(directly)g(coded)h(in)g Fd(<)p Fl(Node-)-189\n4532 y(code)p Fd(>)e Fl(without)f(an)o(y)g(e)o(xtra)h(info.)29\nb(Suppose)21 b(V)-11 b(ar\\(NodeId\\),)22 b(Then\\(NodeId\\))f(and)g\n(Else\\(NodeId\\))f(represent)i(infos)-189 4652 y(about)i(a)h(gi)n(v)o\n(en)f(node.)30 b Fd(<)p Fl(Node-code)p Fd(>)25 b Fl(is)f(a)h(byte)g\n(which)f(contains)g(the)h(follo)n(wing)e(bit)h(\\002elds)h(\\(MSB)g(to)g\n(LSB\\))-44 4856 y Fk(\\017)49 b Fl(Unused)24 b(:)31 b(1)24\nb(bit)-44 5059 y Fk(\\017)49 b Fl(V)-11 b(ariable:)30\nb(2)25 b(bits,)f(one)h(of)g(the)f(follo)n(wing)f(codes)171\n5288 y Fi(\\226)49 b Fl(DDDMP)p 636 5288 30 4 v 35 w(ABSOLUTE)p\n1191 5288 V 36 w(ID:)22 b(V)-11 b(ar\\(NodeId\\))22 b(is)f(represented)h\n(in)g(absolute)f(form)g(as)h Fd(<)p Fl(V)-11 b(ar)n(-internal-)270\n5408 y(info)p Fd(>)24 b Fl(=)h(V)-11 b(ar\\(NodeId\\))25\nb(follo)n(ws)e(\\(absolute)i(info\\))1794 5800 y(4)p eop\n%%Page: 5 5\n5 4 bop 171 218 a Fi(\\226)49 b Fl(DDDMP)p 636 218 30\n4 v 35 w(RELA)-11 b(TIVE)p 1147 218 V 36 w(ID:)32 b(V)-11\nb(ar\\(NodeId\\))32 b(is)g(represented)g(in)f(relati)n(v)o(e)g(form)h(as)\ng Fd(<)p Fl(V)-11 b(ar)n(-internal-)270 338 y(info\\277)24\nb(=)h(Min\\(V)-11 b(ar\\(Then\\(NodeId\\)\\),V)g(ar\\(Else\\(NodeId\\)\\)\\)-V)g\n(ar\\(NodeId\\))171 500 y Fi(\\226)49 b Fl(DDDMP)p 636 500\nV 35 w(RELA)-11 b(TIVE)p 1147 500 V 36 w(1:)27 b(the)19\nb(\\002eld)g Fd(<)p Fl(V)-11 b(ar)n(-internal-info)p Fd(>)18\nb Fl(does)h(not)f(follo)n(w)-6 b(,)18 b(because)h(V)-11\nb(ar\\(NodeId\\))270 620 y(=)25 b(Min\\(V)-11 b(ar\\(Then\\(NodeId\\)\\),V)g\n(ar\\(Else\\(NodeId\\)\\)\\)-1)171 782 y Fi(\\226)49 b Fl(DDDMP)p\n636 782 V 35 w(TERMIN)m(AL:)24 b(Node)h(is)f(a)h(terminal,)f(no)g(v)n\n(ar)h(info)g(required)-44 1011 y Fk(\\017)49 b Fl(T)25\nb(:)f(2)h(bits,)f(with)g(codes)h(similar)e(to)i(V)171\n1214 y Fi(\\226)49 b Fl(DDDMP)p 636 1214 V 35 w(ABSOLUTE)p\n1191 1214 V 36 w(ID:)20 b Fd(<)p Fl(Then-info)p Fd(>)f\nFl(is)h(represented)g(in)g(absolute)f(form)h(as)g Fd(<)p\nFl(Then-info)p Fd(>)270 1334 y Fl(=)25 b(Then\\(NodeId\\))171\n1496 y Fi(\\226)49 b Fl(DDDMP)p 636 1496 V 35 w(RELA)-11\nb(TIVE)p 1147 1496 V 36 w(ID:)28 b(Then\\(NodeId\\))f(is)g(represented)h\n(in)g(relati)n(v)o(e)e(form)i(as)g Fd(<)p Fl(Then-info)p\nFd(>)270 1617 y Fl(=)d(Nodeid-Then\\(NodeId\\))171 1779\ny Fi(\\226)49 b Fl(DDDMP)p 636 1779 V 35 w(RELA)-11 b(TIVE)p\n1147 1779 V 36 w(1:)30 b(no)25 b Fd(<)p Fl(Then-info)p\nFd(>)f Fl(follo)n(ws,)f(because)i(Then\\(NodeId\\))g(=)g(NodeId-1)171\n1941 y Fi(\\226)49 b Fl(DDDMP)p 636 1941 V 35 w(TERMIN)m(AL:)24\nb(Then)h(Node)f(is)h(a)g(terminal,)f(no)g(info)h(required)f(\\(for)i(R)l\n(OBDDs\\))-44 2144 y Fk(\\017)49 b Fl(Ecompl)24 b(:)30\nb(1)25 b(bit,)f(if)h(1)g(means)f(that)g(the)h(else)g(edge)g(is)f\n(complemented)-44 2347 y Fk(\\017)49 b Fl(E)25 b(:)f(2)h(bits,)f(with)g\n(codes)h(and)f(meanings)g(as)h(for)g(the)g(Then)f(edge)-189\n2551 y(DD)35 b(node)f(codes)h(are)h(written)e(as)h(one)g(byte.)60\nb Fd(<)p Fl(V)-11 b(ar)n(-internal-inde)o(x)p Fd(>)p\nFl(,)36 b Fd(<)p Fl(Then-inde)o(x)p Fd(>)p Fl(,)g Fd(<)p\nFl(Else-inde)o(x)p Fd(>)e Fl(\\(if)-189 2671 y(required\\))25\nb(are)h(represented)f(as)g(unsigned)e(inte)o(ger)h(v)n(alues)g(on)h(a)g\n(suf)n(\\002cient)f(set)h(of)g(bytes)f(\\(MSByte)h(\\002rst\\).)47\n2792 y(Inte)o(gers)h(of)f(an)o(y)h(length)e(are)j(written)e(as)h\n(sequences)g(of)g(\\224link)o(ed\\224)f(bytes)g(\\(MSByte)h(\\002rst\\).)34\nb(F)o(or)26 b(each)g(byte)-189 2912 y(7)f(bits)f(are)h(used)g(for)g\n(data)g(and)f(one)h(\\(MSBit\\))g(as)g(link)f(with)g(a)h(further)g(byte)g\n(\\(MSB)g(=)g(1)g(means)f(one)h(more)g(byte\\).)47 3032\ny(Lo)n(w)f(le)n(v)o(el)g(read/write)h(of)g(bytes)f(\\002lters)h\nFd(<)p Fl(CR)p Fd(>)p Fl(,)g Fd(<)p Fl(LF)p Fd(>)g Fl(and)g\nFd(<)p Fl(ctrl-Z)p Fd(>)f Fl(through)g(escape)h(sequences.)-189\n3327 y Fj(2.2)119 b(Implementation)-189 3515 y Fl(Store)24\nb(and)g(load)g(for)g(single)g(Boolean)g(functions)f(and)h(arrays)g(of)g\n(Boolean)g(functions)f(are)i(implemented.)k(More-)-189\n3635 y(o)o(v)o(er)l(,)37 b(the)e(current)h(presentation)f(includes)f\n(functions)h(to)g(retrie)n(v)o(e)g(v)n(ariables)f(names,)k(auxiliary)d\n(identi\\002erss,)-189 3756 y(and)c(all)g(the)g(information)f(contained)\nh(in)f(the)h(header)h(of)f(the)h(\\002les.)50 b(This)30\nb(information)g(can)h(be)h(used)f(as)g(a)g(pre-)-189\n3876 y(processing)19 b(step)g(for)i(load)e(operations.)28\nb(These)20 b(functions)f(allo)n(w)f(to)i(o)o(v)o(ercome)f(fe)n(w)g\n(limitations)f(of)h(the)h(pre)n(vious)-189 3997 y(implementations.)-189\n4263 y Fi(2.2.1)99 b(Storing)25 b(Decision)g(Diagrams)-189\n4450 y Fc(Dddmp)p 111 4450 V 35 w(cuddBddStor)l(e)f Fl(and)h\nFc(Dddmp)p 1195 4450 V 35 w(cuddBddArr)o(ayStor)l(e)e\nFl(are)j(the)f(tw)o(o)f(store)h(functions,)f(used)h(to)g(store)f(sin-)\n-189 4571 y(gle)f(BDD)h(or)g(a)f(forest)h(of)f(BDDs,)h(respecti)n(v)o\n(ely)-6 b(.)28 b(Internally)-6 b(,)23 b Fc(Dddmp)p 2275\n4571 V 35 w(cuddBddStor)l(e)f Fl(b)n(uilds)g(a)i(dummy)e(1)h(entry)-189\n4691 y(array)j(of)e(BDDs,)h(and)g(calls)g Fc(dddmp)p\n1102 4691 V 35 w(cuddBddArr)o(ayStor)l(e)p Fl(.)47 4811\ny(Since)30 b(con)l(v)o(ersion)e(from)h(DD)h(pointers)e(to)h(inte)o(ger)\nf(is)h(required,)i(DD)e(nodes)g(are)h(temporarily)e(remo)o(v)o(ed)-189\n4932 y(from)23 b(the)f(unique)h(hash.)29 b(This)23 b(mak)o(es)f(room)g\n(in)h(their)f Fc(ne)n(xt)h Fl(\\002eld)h(to)e(store)h(node)f(IDs.)30\nb(Nodes)23 b(are)h(re-link)o(ed)e(after)-189 5052 y(the)i(store)g\n(operation,)g(possible)f(in)g(a)i(modi\\002ed)e(order)-5\nb(.)31 b(Dumping)22 b(is)i(either)g(in)g(te)o(xt)f(or)i(binary)f(form.)\n30 b(Both)24 b(a)g(\\002le)-189 5173 y(pointer)31 b(\\()p\nFc(fp)p Fl(\\))g(and)g(a)h(\\002le)g(name)f(\\()p Fc(fname)p\nFl(\\))h(are)g(pro)o(vided)e(as)h(inputs)f(parameters)i(to)f(store)g\n(routines.)50 b(BDDs)31 b(are)-189 5293 y(stored)c(to)g(the)g(already)g\n(open)h(\\002le)f Fc(fp)p Fl(,)h(if)f(not)g(NULL.)g(Otherwise)f(\\002le)i\n(whose)f(name)g(is)g Fc(fname)g Fl(is)g(opened.)38 b(This)-189\n5413 y(is)24 b(intended)g(to)h(allo)n(w)f(either)g(DD)h(storage)g\n(within)e(\\002les)i(containing)f(other)g(data,)h(or)g(to)g(speci\\002c)g\n(\\002les.)1794 5800 y(5)p eop\n%%Page: 6 6\n6 5 bop -189 218 a Fi(2.2.2)99 b(Loading)25 b(Decision)g(Diagrams)-189\n405 y Fc(Dddmp)p 111 405 30 4 v 35 w(cuddBddLoad)37 b\nFl(and)h Fc(Dddmp)p 1219 405 V 35 w(cuddBddArr)o(ayLoad)f\nFl(are)h(the)g(load)g(functions,)i(which)e(read)g(a)g(BDD)-189\n526 y(dump)24 b(\\002le.)47 646 y(F)o(ollo)n(wing)34 b(the)h(store)h\n(function,)h(the)f(main)f(BDD)h(load)f(function,)j Fc(Dddmp)p\n2813 646 V 35 w(cuddBddLoad)p Fl(,)f(is)f(imple-)-189\n767 y(mented)g(by)g(calling)f(the)h(main)g(BDD-array)h(loading)f\n(function)f Fc(Dddmp)p 2466 767 V 35 w(cuddBddArr)o(ayLoad)p\nFl(.)63 b(A)37 b(dynamic)-189 887 y(v)o(ector)24 b(of)h(DD)g(pointers)f\n(is)g(temporarily)g(allocated)h(to)f(support)g(con)l(v)o(ersion)f(from)\ni(DD)g(inde)o(x)o(es)e(to)h(pointers.)47 1007 y(Se)n(v)o(eral)40\nb(criteria)f(are)i(supported)d(for)i(v)n(ariable)f(match)g(between)g\n(\\002le)h(and)g(DD)f(manager)l(,)k(practically)-189 1128\ny(allo)n(wing)37 b(v)n(ariable)h(permutations)f(or)i(compositions)d\n(while)i(loading)g(DDs.)71 b(V)-11 b(ariable)39 b(match)f(between)h\n(the)-189 1248 y(DD)32 b(manager)g(and)g(the)g(BDD)g(\\002le)g(is)g\n(optionally)e(based)i(in)f Fc(IDs)p Fl(,)j Fc(perids)p\nFl(,)f Fc(varnames)p Fl(,)g Fc(var)o(auxids)p Fl(;)g(also)f(direct)-189\n1369 y(composition)j(between)j Fc(IDs)g Fl(and)f Fc(composeids)g\nFl(is)g(supported.)68 b(The)38 b Fc(varmatc)o(hmode)e\nFl(parameter)i(is)f(used)g(to)-189 1489 y(select)27 b(mathing)e(mode.)\n37 b(More)27 b(in)f(detail,)h(tw)o(o)f(match)h(modes)f(use)h(the)f\n(information)g(within)f(the)i(DD)g(manager)l(,)-189 1609\ny(the)e(other)f(ones)h(use)g(e)o(xtra)f(information,)f(which)i(support)\nf(an)o(y)g(v)n(ariable)g(remap)h(or)g(change)g(in)f(the)h(ordering.)-44\n1813 y Fk(\\017)49 b Fl(v)n(armatchnode=DDDMP)p 1040 1813\nV 35 w(V)-13 b(AR)p 1272 1813 V 35 w(MA)i(TCHIDS)19 b(allo)n(ws)f\n(loading)g(a)h(DD)g(k)o(eeping)f(v)n(ariable)g(IDs)h(unchanged)55\n1933 y(\\(re)o(gardless)24 b(of)h(the)f(v)n(ariable)h(ordering)f(of)h\n(the)g(reading)f(manager)-5 b(.)55 2095 y(This)24 b(is)g(useful,)g(for)\nh(e)o(xample,)f(when)g(sw)o(apping)g(DDs)g(to)h(\\002le)g(and)f\n(restoring)g(them)g(later)h(from)f(\\002le,)h(after)55\n2215 y(possible)e(v)n(ariable)i(reordering)g(acti)n(v)n(ations.)-44\n2419 y Fk(\\017)49 b Fl(v)n(armatchnode=DDDMP)p 1040 2419\nV 35 w(V)-13 b(AR)p 1272 2419 V 35 w(MA)i(TCHPERMIDS)36\nb(is)e(used)h(to)f(allo)n(w)g(v)n(ariable)g(match)h(according)55\n2539 y(to)h(the)h(position)e(in)i(the)g(ordering)f(\\(retrie)n(v)o(ed)g\n(by)h(array)h(of)f(permutations)e(stored)h(on)h(\\002le)g(and)g(within)\n55 2660 y(the)h(reading)g(DD)h(manager\\).)72 b(A)38 b(possible)f\n(application)h(is)g(retrie)n(ving)f(BDDs)i(stored)f(after)h(dynamic)55\n2780 y(reordering,)28 b(from)g(a)g(DD)g(manager)g(where)h(all)e(v)n\n(ariable)h(IDs)f(map)h(their)f(position)g(in)g(the)h(ordering,)g(and)55\n2900 y(the)d(loaded)f(BDD)h(k)o(eeps)g(the)g(ordering)f(as)h(stored)f\n(on)h(\\002le.)-44 3104 y Fk(\\017)49 b Fl(v)n(armatchnode=DDDMP)p\n1040 3104 V 35 w(V)-13 b(AR)p 1272 3104 V 35 w(MA)i(TCHN)m(AMES)26\nb(requires)h(a)h(not)e(NULL)h(v)n(armatchmodes)f(param-)55\n3224 y(eter;)34 b(this)c(is)g(a)h(v)o(ector)g(of)g(strings)e(in)i\n(one-to-one)f(correspondence)h(with)f(v)n(ariable)h(IDs)f(of)h(the)g\n(reading)55 3344 y(manager)-5 b(.)40 b(V)-11 b(ariables)28\nb(in)g(the)g(DD)g(\\002le)g(read)h(are)g(matched)f(with)f(manager)h(v)n\n(ariables)f(according)h(to)g(their)55 3465 y(name)35\nb(\\(a)h(not)f(NULL)g(v)n(arnames)g(parameter)h(w)o(as)f(required)h\n(while)f(storing)f(the)h(DD)g(\\002le\\).)64 b(The)35 b(most)55\n3585 y(common)c(usage)h(of)g(this)f(feature)i(is)e(in)h(combination)e\n(with)i(a)g(v)n(ariable)g(ordering)g(stored)f(on)h(a)g(\\002le)h(and)55\n3706 y(based)28 b(on)h(v)n(ariables)f(names.)41 b(Names)29\nb(must)e(be)i(loaded)f(in)g(an)h(array)g(of)g(strings)e(and)i(passed)f\n(to)g(the)h(DD)55 3826 y(load)24 b(procedure.)-44 4029\ny Fk(\\017)49 b Fl(v)n(armatchnode=DDDMP)p 1040 4029 V\n35 w(V)-13 b(AR)p 1272 4029 V 35 w(MA)i(TCHIDS)25 b(has)g(a)g(meaning)f\n(similar)g(to)55 4150 y(DDDMP)p 421 4150 V 36 w(V)-13\nb(AR)p 654 4150 V 35 w(MA)i(TCHN)m(AMES)26 b(b)n(ut)h(inte)o(ger)f\n(auxiliary)g(IDs)h(are)h(used)f(instead)f(of)h(strings.)36\nb(The)28 b(ad-)55 4270 y(ditional)23 b(not)h(NULL)h(v)n(armathauxids)e\n(parameter)i(is)g(needed.)-44 4474 y Fk(\\017)49 b Fl(v)n\n(armatchnode=DDDMP)p 1040 4474 V 35 w(V)-13 b(AR)p 1272\n4474 V 35 w(COMPOSEIDS,)38 b(uses)f(the)f(additional)f(v)n\n(arcomposeids)g(parameter)55 4594 y(as)25 b(an)g(array)g(of)g(v)n\n(ariable)f(IDs)h(to)g(be)g(composed)f(with)g(IDs)g(stored)h(in)f\n(\\002le.)-189 4860 y Fi(2.2.3)99 b(DD)25 b(Load/Stor)n(e)h(and)f(V)-9\nb(ariable)25 b(Ordering)-189 5048 y Fl(Loading)31 b(of)i(Decision)e\n(Diagrams)h(from)g(\\002le)g(supports)f(dif)n(ferent)h(v)n(ariables)g\n(ordering)f(strate)o(gies,)i(as)g(already)-189 5168 y(pointed)23\nb(out)h(in)g(the)h(pre)n(vious)e(section.)30 b(This)24\nb(allo)n(ws)f(or)h(e)o(xample)g(storing)f(dif)n(ferent)i(BDDs)f(each)h\n(with)f(its)g(o)n(wn)-189 5288 y(v)n(ariable)29 b(ordering,)h(and)g(to)\nf(mer)n(ge)h(them)f(within)f(the)i(same)f(DD)h(manager)f(by)h(means)f\n(of)g(proper)h(load)f(opera-)-189 5409 y(tions.)44 b(W)-8\nb(e)30 b(suggest)f(using)f(DDDMP)p 1175 5409 V 36 w(V)-13\nb(AR)p 1408 5409 V 36 w(MA)i(TCHIDS)30 b(whene)n(v)o(er)f(IDs)g(k)o\n(eeps)h(on)f(representing)h(the)f(same)-189 5529 y(entities)24\nb(while)h(changing)f(v)n(ariable)h(ordering.)31 b(If)25\nb(this)f(is)h(not)f(true,)h(v)n(ariable)g(names)g(\\(if)g(a)n(v)n\n(ailable\\))f(or)i(auxiliary)1794 5800 y(6)p eop\n%%Page: 7 7\n7 6 bop -189 218 a Fl(IDs)34 b(are)h(a)g(good)e(w)o(ay)i(to)f\n(represent)g(in)l(v)n(ariant)f(attrib)n(uted)g(of)i(v)n(ariables)e\n(across)h(se)n(v)o(eral)g(runs)g(with)f(dif)n(ferent)-189\n338 y(orderings.)50 b(DDDMP)p 629 338 30 4 v 35 w(V)-13\nb(AR)p 861 338 V 36 w(COMPOSEIDS)32 b(is)f(an)h(alternati)n(v)o(e)e\n(solution,)h(that)g(practically)f(corresponds)h(to)-189\n459 y(cascading)23 b(DDDMP)p 593 459 V 36 w(V)-13 b(AR)p\n826 459 V 36 w(MA)i(TCHIDS)23 b(and)h(v)n(ariable)f(composition)e(with)\nh(a)i(gi)n(v)o(en)e(array)i(of)g(ne)n(w)f(v)n(ariables.)-189\n797 y Fo(3)143 b(CNF)35 b(Support)-189 1050 y Fj(3.1)119\nb(F)m(ormat)-189 1237 y Fl(Gi)n(v)o(en)30 b(a)h(BDD)g(representing)g(a)\ng(function)f Fd(f)11 b Fl(,)32 b(we)f(de)n(v)o(elop)f(three)h(basic)g\n(possible)e(w)o(ays)i(to)g(store)f(it)h(as)g(a)g(CNF)-189\n1358 y(formula.)54 b(In)33 b(each)h(method)d(the)i(set)g(of)f(clauses)h\n(is)f(written)h(after)g(an)g(header)g(part.)55 b(Only)32\nb(the)h(te)o(xt)f(format)g(is)-189 1478 y(allo)n(wed.)-189\n1743 y Fi(3.1.1)99 b(Header)-189 1931 y Fl(The)23 b(header)h(part)f(of)\ng(each)h(CNF)g(\\002le)f(has)g(basically)g(the)f(same)h(format)g\n(analyzed)g(for)h(the)f(BDD/ADD)g(\\002les.)30 b(F)o(or)-189\n2051 y(e)o(xample)h(the)g Fg(.rootids)f Fl(line)h(indicates)f(the)i(be)\no(ginning)d(of)j(each)g(CNF)g(formula)f(represented)h(by)f(a)h(single)\n-189 2172 y(BDD.)j(T)-8 b(o)34 b(be)g(compatible)f(with)h(the)g(DIMA)l\n(CS)h(format)f(each)h(header)f(line)g(start)g(with)g(the)g(character)h\n(\\223c\\224)g(to)-189 2292 y(indicate)24 b(a)h(comment.)-189\n2557 y Fi(3.1.2)99 b(T)-9 b(ext)25 b(F)n(ormat)-189 2745\ny Fl(The)j(\\002rst)g(method,)g(which)f(we)h(call)g Fi(Single-Node-Cut)p\nFl(,)j(models)26 b(each)j(BDD)f(nodes,)h(b)n(ut)e(the)h(ones)f(with)h\n(both)-189 2865 y(the)c(children)g(equal)h(to)f(the)g(constant)g(node)g\nFb(1)p Fl(,)g(as)h(a)g(multiple)o(x)o(er)-5 b(.)27 b(Each)e(multiple)o\n(x)o(er)d(has)i(tw)o(o)g(data)h(inputs)e(\\(i.e.,)-189\n2985 y(the)k(node)h(children\\),)f(a)h(selection)f(input)f(\\(i.e.,)i\n(the)g(node)f(v)n(ariable\\))g(and)h(one)f(output)f(\\(i.e.,)i(the)g\n(function)e(v)n(alue\\))-189 3106 y(whose)h(v)n(alue)f(is)h(assigned)f\n(to)h(an)g(additional)f(CNF)i(v)n(ariable.)37 b(The)27\nb(\\002nal)h(number)e(of)h(v)n(ariables)g(is)f(equal)h(to)g(the)-189\n3226 y(number)d(of)h(original)f(BDD)h(v)n(ariables)f(plus)g(the)h\n(number)f(of)h(\\223internal\\224)g(nodes)f(of)h(the)g(BDD.)47\n3346 y(The)k(second)f(method,)g(which)h(we)f(call)h Fi(Maxterm-Cut)p\nFl(,)h(create)g(clauses)e(starting)g(from)g Fd(f)39 b\nFl(corresponds)-189 3467 y(to)25 b(the)h(of)n(f-set)g(\\(i.e.,)f(all)h\n(the)g(paths-cubes)f(from)g(the)h(root)g(node)f(to)h(the)f(terminal)g\nFg(0)p Fl(\\))h(of)g(the)g(function)e Fd(f)11 b Fl(.)34\nb(W)l(ithin)-189 3587 y(the)29 b(BDD)g(for)g Fd(f)11\nb Fl(,)30 b(such)f(clauses)f(are)i(found)e(by)h(follo)n(wing)e(all)i\n(the)f(paths)h(from)f(the)h(root)g(node)f(of)h(the)g(BDD)g(to)-189\n3708 y(the)c(constant)f(node)g Fb(0)p Fl(.)31 b(The)25\nb(\\002nal)g(number)f(of)h(v)n(ariables)f(is)g(equal)h(to)f(the)h\n(number)f(of)h(original)f(BDD)h(v)n(ariables.)47 3828\ny(The)k(third)g(method,)g(which)g(we)g(call)g Fi(A)-5\nb(uxiliary-V)c(ariable-Cut)p Fl(,)30 b(is)f(a)h(trade-of)n(f)f(between)\ng(the)g(\\002rst)g(tw)o(o)-189 3948 y(strate)o(gies.)69\nb(Internal)37 b(v)n(ariables,)j(i.e.,)h(cutting)c(points,)j(are)e\n(added)g(in)f(order)h(to)g(decompose)f(the)h(BDD)g(into)-189\n4069 y(multiple)27 b(sub-trees)i(each)h(of)f(which)f(is)h(stored)g\n(follo)n(wing)e(the)h(second)h(strate)o(gy)-6 b(.)42\nb(The)29 b(trade-of)n(f)g(is)g(guided)f(by)-189 4189\ny(the)23 b(cutting)f(point)g(selection)g(strate)o(gy)-6\nb(,)22 b(and)h(we)g(e)o(xperiment)f(with)g(tw)o(o)g(methodologies.)28\nb(In)23 b(the)g(\\002rst)g(method,)g(a)-189 4310 y(ne)n(w)f(CNF)h(v)n\n(ariable)f(is)f(inserted)h(in)g(correspondence)g(to)g(the)g(shared)g\n(nodes)g(of)g(the)h(BDD,)f(i.e.,)h(the)f(nodes)f(which)-189\n4430 y(ha)n(v)o(e)29 b(more)g(than)h(one)f(incoming)f(edge.)45\nb(This)29 b(technique,)h(albeit)e(optimizing)g(the)h(number)g(of)h\n(literals)e(stored,)-189 4550 y(can)35 b(produce)g(clauses)f(with)g(a)h\n(high)f(number)h(of)f(literals)1894 4514 y Fh(2)1933\n4550 y Fl(.)60 b(T)-8 b(o)35 b(a)n(v)n(oid)f(this)g(dra)o(wback,)j(the)\ne(second)f(method,)-189 4671 y(introduces)28 b(all)g(the)g(pre)n\n(viously)e(indicated)i(cutting)f(points)g(more)h(the)h(ones)f\n(necessary)g(to)g(break)h(the)f(length)g(of)-189 4791\ny(the)d(path)f(to)h(a)g(maximum)e(\\(user\\))i(selected)g(v)n(alue.)47\n4911 y(Actually)-6 b(,)37 b(all)f(the)f(methods)g(described)h(abo)o(v)o\n(e)e(can)j(be)e(re-conducted)h(to)g(the)f(basic)h(idea)g(of)g(possibly)\n-189 5032 y(breaking)24 b(the)h(BDD)g(through)f(the)g(use)h(of)f\n(additional)g(cutting)f(v)n(ariables)h(and)h(dumping)e(the)h(paths)g\n(between)h(the)-189 5152 y(root)34 b(of)h(the)f(BDD,)h(the)g(cutting)e\n(v)n(ariables)h(and)g(the)h(terminal)e(nodes.)60 b(Such)35\nb(internal)f(cutting)f(v)n(ariables)h(are)-189 5273 y(added)25\nb(al)o(w)o(ays)f(\\(for)i(each)f(node\\),)g(ne)n(v)o(er)f(or)h(sometimes)\ne(respecti)n(v)o(ely)-6 b(.)p -189 5360 1607 4 v -77\n5422 a Ff(2)-40 5452 y Fe(This)27 b(v)n(alue)f(is)i(superiorly)d\n(limited)h(by)g(the)h(number)e(of)h(v)n(ariables)g(of)g(the)h(BDD,)g\n(i.e.,)h(the)f(longest)f(path)g(from)g(the)h(root)f(to)g(the)-189\n5551 y(terminal)19 b(node.)1794 5800 y Fl(7)p eop\n%%Page: 8 8\n8 7 bop 47 218 a Fl(While)33 b(the)f Fc(Single-Node-Cut)h\nFl(method)f(minimizes)f(the)i(length)f(of)h(the)f(clauses)h(produced,)i\n(b)n(ut)d(it)g(also)-189 338 y(requires)d(the)h(higher)f(number)g(of)g\n(CNF)i(v)n(ariables,)e(the)h Fc(Maxterm-Cut)f Fl(technique)g(minimizes)\nf(the)h(number)g(of)-189 459 y(CNF)36 b(v)n(ariables)d(required.)61\nb(This)34 b(adv)n(antage)g(is)g(counter)n(-balanced)h(by)f(the)h(f)o\n(act)g(that)f(in)g(the)h(w)o(orst)f(case)h(the)-189 579\ny(number)23 b(of)g(clauses,)g(as)h(well)e(as)i(the)f(total)f(number)h\n(of)g(literals,)g(produced)g(is)g(e)o(xponential)e(in)i(the)g(BDD)h\n(size)f(\\(in)-189 699 y(terms)28 b(of)i(number)e(of)h(nodes\\).)43\nb(The)29 b(application)f(of)h(this)f(method)g(is)g(then)h(limited)e(to)\ni(the)g(cases)g(in)f(which)h(the)-189 820 y(\\223of)n(f-set\\224)c(of)f\n(the)g(represented)h(function)f Fd(f)35 b Fl(has)24 b(a)h(small)f\n(cardinality)-6 b(.)29 b(The)c Fc(A)n(uxiliary-V)-11\nb(ariable-Cut)22 b Fl(strate)o(gy)h(is)-189 940 y(a)k(trade-of)n(f)h\n(between)f(the)g(\\002rst)g(tw)o(o)g(methods)f(and)h(the)g(ones)f(which)\nh(gi)n(v)o(es)f(more)h(compact)f(results.)37 b(As)27\nb(a)h(\\002nal)-189 1061 y(remark)f(notice)e(that)h(the)g(method)g(is)f\n(able)i(to)f(store)g(both)f(monolithic)f(BDDs)j(and)f(conjuncti)n(v)o\n(e)e(forms.)35 b(In)26 b(each)-189 1181 y(case)f(we)g(generate)h(CNF)f\n(\\002les)g(using)f(the)h(standard)f(DIMA)l(CS)i(format.)-189\n1365 y Fi(Example)f(1)49 b Fc(F)l(igur)l(e)20 b(1)h(shows)f(an)h(e)n\n(xample)g(of)f(how)h(our)f(pr)l(ocedur)l(e)h(works)f(to)h(stor)l(e)f(a)\nh(small)f(monolithic)f(BDD.)-189 1486 y(F)l(igur)l(e)j(1\\(a\\))h(r)l\n(epr)l(esents)g(a)g(BDD)g(with)g Fb(4)g Fc(nodes.)30\nb(BDD)23 b(variables)f(ar)l(e)h(named)g(after)f(inte)l(g)o(er)g(number)\no(s)h(r)o(anging)-189 1606 y(fr)l(om)k Fb(1)h Fc(to)g\nFb(4)p Fc(,)h(to)f(have)g(an)g(easy-to-follow)f(corr)l(espondence)h\n(with)g(the)g(CNF)h(variables.)40 b(F)l(igur)l(e)27 b(1\\(b\\),)i(\\(c\\))g\n(and)-189 1727 y(\\(d\\))c(show)g(the)f(corr)l(esponding)f(CNF)j(r)l(epr)\nl(esentations)d(g)o(ener)o(ated)h(by)h(our)f(thr)l(ee)h(methods.)30\nb(As)24 b(in)h(the)f(standar)l(d)-189 1847 y(format)i\nFa(p)i Fc(indicates)e(the)h(total)f(number)g(of)h(variables)f(used)h\n(\\()p Fb(4)g Fc(is)g(the)g(minimum)f(value)h(as)g(the)g(BDD)g(itself)f\n(has)-189 1967 y Fb(4)f Fc(variables\\),)e(and)i Fa(cnf)g\nFc(the)f(total)g(number)g(of)h(clauses.)47 2088 y(As)i(a)g(\\002nal)f(r)\nl(emark)h(notice)f(that)g(for)g(this)g(speci\\002c)h(e)n(xample)g(the)f\n(\\223Maxterm-Cut\\224)i(appr)l(oac)o(h)d(is)h(the)h(one)-189\n2208 y(whic)o(h)36 b(gives)g(the)g(most)f(compact)h(CNF)h(r)l(epr)l\n(esentation)e(b)n(ut)h(also)f(the)h(clause)g(with)g(the)g(lar)l(g)o\n(est)g(number)f(of)-189 2328 y(liter)o(als)23 b(\\()p\nFb(4)p Fc(\\).)188 2471 y\n 6339814 10777681 0 0 11709153 19997655 startTexFig\n 188 2471 a\n%%BeginDocument: bdd.eps\n%!PS-Adobe-2.0 EPSF-2.0\n%%Title: bdd.eps\n%%Creator: fig2dev Version 3.2 Patchlevel 3c\n%%CreationDate: Mon Sep  9 14:21:26 2002\n%%For: quer@pcsq (Stefano Quer)\n%%BoundingBox: 0 0 178 304\n%%Magnification: 1.0000\n%%EndComments\n/$F2psDict 200 dict def\n$F2psDict begin\n$F2psDict /mtrx matrix put\n/col-1 {0 setgray} bind def\n/col0 {0.000 0.000 0.000 srgb} bind def\n/col1 {0.000 0.000 1.000 srgb} bind def\n/col2 {0.000 1.000 0.000 srgb} bind def\n/col3 {0.000 1.000 1.000 srgb} bind def\n/col4 {1.000 0.000 0.000 srgb} bind def\n/col5 {1.000 0.000 1.000 srgb} bind def\n/col6 {1.000 1.000 0.000 srgb} bind def\n/col7 {1.000 1.000 1.000 srgb} bind def\n/col8 {0.000 0.000 0.560 srgb} bind def\n/col9 {0.000 0.000 0.690 srgb} bind def\n/col10 {0.000 0.000 0.820 srgb} bind def\n/col11 {0.530 0.810 1.000 srgb} bind def\n/col12 {0.000 0.560 0.000 srgb} bind def\n/col13 {0.000 0.690 0.000 srgb} bind def\n/col14 {0.000 0.820 0.000 srgb} bind def\n/col15 {0.000 0.560 0.560 srgb} bind def\n/col16 {0.000 0.690 0.690 srgb} bind def\n/col17 {0.000 0.820 0.820 srgb} bind def\n/col18 {0.560 0.000 0.000 srgb} bind def\n/col19 {0.690 0.000 0.000 srgb} bind def\n/col20 {0.820 0.000 0.000 srgb} bind def\n/col21 {0.560 0.000 0.560 srgb} bind def\n/col22 {0.690 0.000 0.690 srgb} bind def\n/col23 {0.820 0.000 0.820 srgb} bind def\n/col24 {0.500 0.190 0.000 srgb} bind def\n/col25 {0.630 0.250 0.000 srgb} bind def\n/col26 {0.750 0.380 0.000 srgb} bind def\n/col27 {1.000 0.500 0.500 srgb} bind def\n/col28 {1.000 0.630 0.630 srgb} bind def\n/col29 {1.000 0.750 0.750 srgb} bind def\n/col30 {1.000 0.880 0.880 srgb} bind def\n/col31 {1.000 0.840 0.000 srgb} bind def\n\nend\nsave\nnewpath 0 304 moveto 0 0 lineto 178 0 lineto 178 304 lineto closepath clip newpath\n-51.0 319.0 translate\n1 -1 scale\n\n/cp {closepath} bind def\n/ef {eofill} bind def\n/gr {grestore} bind def\n/gs {gsave} bind def\n/sa {save} bind def\n/rs {restore} bind def\n/l {lineto} bind def\n/m {moveto} bind def\n/rm {rmoveto} bind def\n/n {newpath} bind def\n/s {stroke} bind def\n/sh {show} bind def\n/slc {setlinecap} bind def\n/slj {setlinejoin} bind def\n/slw {setlinewidth} bind def\n/srgb {setrgbcolor} bind def\n/rot {rotate} bind def\n/sc {scale} bind def\n/sd {setdash} bind def\n/ff {findfont} bind def\n/sf {setfont} bind def\n/scf {scalefont} bind def\n/sw {stringwidth} bind def\n/tr {translate} bind def\n/tnt {dup dup currentrgbcolor\n  4 -2 roll dup 1 exch sub 3 -1 roll mul add\n  4 -2 roll dup 1 exch sub 3 -1 roll mul add\n  4 -2 roll dup 1 exch sub 3 -1 roll mul add srgb}\n  bind def\n/shd {dup dup currentrgbcolor 4 -2 roll mul 4 -2 roll mul\n  4 -2 roll mul srgb} bind def\n /DrawEllipse {\n\t/endangle exch def\n\t/startangle exch def\n\t/yrad exch def\n\t/xrad exch def\n\t/y exch def\n\t/x exch def\n\t/savematrix mtrx currentmatrix def\n\tx y tr xrad yrad sc 0 0 1 startangle endangle arc\n\tclosepath\n\tsavematrix setmatrix\n\t} def\n\n/$F2psBegin {$F2psDict begin /$F2psEnteredState save def} def\n/$F2psEnd {$F2psEnteredState restore end} def\n\n$F2psBegin\n%%Page: 1 1\n10 setmiterlimit\n 0.06299 0.06299 sc\n%\n% Fig objects follow\n%\n% Polyline\n15.000 slw\nn 2010 4515 m 2550 4515 l 2550 5040 l 2010 5040 l\n cp gs col0 s gr \n/Times-Roman ff 300.00 scf sf\n2205 4875 m\ngs 1 -1 sc (1) col0 sh gr\n% Ellipse\nn 1515 1800 270 270 0 360 DrawEllipse gs col0 s gr\n\n% Ellipse\nn 2250 900 270 270 0 360 DrawEllipse gs col0 s gr\n\n% Ellipse\nn 2970 2715 270 270 0 360 DrawEllipse gs col0 s gr\n\n% Ellipse\nn 2280 3705 270 270 0 360 DrawEllipse gs col0 s gr\n\n7.500 slw\n% Ellipse\nn 3555 3555 64 64 0 360 DrawEllipse gs 0.00 setgray ef gr gs col0 s gr\n\n% Ellipse\nn 2712 1726 64 64 0 360 DrawEllipse gs 0.00 setgray ef gr gs col0 s gr\n\n% Ellipse\nn 2430 4230 64 64 0 360 DrawEllipse gs 0.00 setgray ef gr gs col0 s gr\n\n% Polyline\n15.000 slw\nn 2805 2910 m\n 2250 3450 l gs col0 s gr \n% Polyline\n [90] 0 sd\ngs  clippath\n2940 2472 m 3010 2445 l 2931 2239 l 2957 2411 l 2861 2266 l cp\neoclip\nn 2460 1110 m\n 2970 2445 l gs col0 s gr gr\n [] 0 sd\n% arrowhead\nn 2861 2266 m 2957 2411 l 2931 2239 l 2908 2284 l 2861 2266 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\ngs  clippath\n1478 1511 m 1528 1568 l 1693 1422 l 1542 1506 l 1643 1366 l cp\neoclip\nn 2025 1080 m\n 1515 1530 l gs col0 s gr gr\n\n% arrowhead\nn 1643 1366 m 1542 1506 l 1693 1422 l 1643 1416 l 1643 1366 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\ngs  clippath\n2212 645 m 2287 645 l 2287 425 l 2250 594 l 2212 425 l cp\neoclip\nn 2250 270 m\n 2250 630 l gs col0 s gr gr\n\n% arrowhead\nn 2212 425 m 2250 594 l 2287 425 l 2250 459 l 2212 425 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n [90] 0 sd\ngs  clippath\n2692 2664 m 2732 2601 l 2546 2485 l 2670 2606 l 2506 2548 l cp\neoclip\nn 1710 2010 m\n 2700 2625 l gs col0 s gr gr\n [] 0 sd\n% arrowhead\nn 2506 2548 m 2670 2606 l 2546 2485 l 2555 2534 l 2506 2548 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n2 slj\n [90] 0 sd\ngs  clippath\n2504 4653 m 2539 4720 l 2733 4616 l 2567 4663 l 2698 4550 l cp\neoclip\nn 3180 2910 m 3181 2911 l 3183 2913 l 3186 2916 l 3192 2921 l 3200 2929 l\n 3210 2939 l 3223 2951 l 3238 2966 l 3255 2984 l 3274 3003 l\n 3295 3025 l 3317 3049 l 3339 3075 l 3362 3103 l 3385 3131 l\n 3407 3161 l 3429 3192 l 3450 3225 l 3470 3258 l 3488 3293 l\n 3504 3329 l 3519 3367 l 3531 3406 l 3541 3447 l 3548 3490 l\n 3552 3536 l 3552 3583 l 3548 3634 l 3540 3686 l 3528 3740 l\n 3510 3795 l 3490 3844 l 3467 3892 l 3441 3939 l 3413 3985 l\n 3382 4028 l 3350 4070 l 3317 4110 l 3283 4148 l 3248 4184 l\n 3211 4219 l 3174 4253 l 3136 4285 l 3098 4316 l 3059 4347 l\n 3020 4376 l 2980 4405 l 2941 4432 l 2901 4459 l 2862 4484 l\n 2824 4509 l 2787 4532 l 2751 4554 l 2717 4575 l 2686 4593 l\n 2657 4610 l 2631 4626 l 2608 4639 l 2589 4650 l 2572 4659 l\n 2559 4666 l 2550 4672 l\n 2535 4680 l gs col0 s gr gr\n [] 0 sd\n% arrowhead\n0 slj\nn 2698 4550 m 2567 4663 l 2733 4616 l 2686 4599 l 2698 4550 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n2 slj\ngs  clippath\n1985 4734 m 2028 4672 l 1847 4548 l 1965 4675 l 1804 4609 l cp\neoclip\nn 1350 2025 m 1349 2026 l 1348 2027 l 1345 2030 l 1340 2035 l 1334 2042 l\n 1325 2051 l 1314 2063 l 1301 2078 l 1286 2095 l 1268 2114 l\n 1249 2137 l 1227 2161 l 1205 2188 l 1181 2218 l 1156 2249 l\n 1131 2282 l 1105 2316 l 1080 2352 l 1054 2390 l 1029 2428 l\n 1005 2468 l 981 2509 l 959 2552 l 938 2595 l 918 2640 l\n 900 2687 l 884 2736 l 870 2786 l 858 2839 l 848 2894 l\n 841 2951 l 837 3011 l 836 3074 l 838 3139 l 845 3206 l\n 855 3275 l 870 3345 l 888 3412 l 910 3477 l 934 3542 l\n 961 3604 l 990 3665 l 1022 3723 l 1054 3779 l 1088 3833 l\n 1124 3885 l 1160 3935 l 1198 3983 l 1236 4029 l 1275 4074 l\n 1315 4118 l 1356 4160 l 1397 4201 l 1438 4241 l 1480 4280 l\n 1522 4318 l 1563 4355 l 1605 4390 l 1645 4424 l 1685 4457 l\n 1723 4488 l 1760 4517 l 1795 4545 l 1827 4570 l 1857 4593 l\n 1884 4613 l 1909 4632 l 1930 4647 l 1947 4660 l 1962 4671 l\n 1973 4679 l 1982 4686 l\n 1995 4695 l gs col0 s gr gr\n\n% arrowhead\n0 slj\nn 1804 4609 m 1965 4675 l 1847 4548 l 1854 4598 l 1804 4609 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n2 slj\n [90] 0 sd\ngs  clippath\n2300 4492 m 2363 4532 l 2481 4347 l 2359 4470 l 2417 4307 l cp\neoclip\nn 2340 3960 m 2341 3962 l 2344 3966 l 2348 3973 l 2354 3982 l 2362 3995 l\n 2370 4010 l 2379 4028 l 2389 4046 l 2397 4066 l 2406 4088 l\n 2413 4111 l 2420 4137 l 2425 4165 l 2429 4197 l 2430 4230 l\n 2429 4263 l 2425 4295 l 2420 4323 l 2413 4349 l 2406 4372 l\n 2397 4394 l 2389 4414 l 2379 4433 l 2370 4450 l 2362 4465 l\n 2354 4478 l\n 2340 4500 l gs col0 s gr gr\n [] 0 sd\n% arrowhead\n0 slj\nn 2417 4307 m 2359 4470 l 2481 4347 l 2431 4356 l 2417 4307 l \n cp gs 0.00 setgray ef gr  col0 s\n% Polyline\n2 slj\ngs  clippath\n2136 4532 m 2199 4492 l 2082 4307 l 2141 4470 l 2018 4347 l cp\neoclip\nn 2160 3960 m 2159 3962 l 2156 3966 l 2152 3973 l 2146 3982 l 2138 3995 l\n 2130 4010 l 2121 4028 l 2111 4046 l 2103 4066 l 2094 4088 l\n 2087 4111 l 2080 4137 l 2075 4165 l 2071 4197 l 2070 4230 l\n 2071 4263 l 2075 4295 l 2080 4323 l 2087 4349 l 2094 4372 l\n 2103 4394 l 2111 4414 l 2121 4433 l 2130 4450 l 2138 4465 l\n 2146 4478 l\n 2160 4500 l gs col0 s gr gr\n\n% arrowhead\n0 slj\nn 2018 4347 m 2141 4470 l 2082 4307 l 2068 4356 l 2018 4347 l \n cp gs 0.00 setgray ef gr  col0 s\n/Times-Roman ff 300.00 scf sf\n2175 990 m\ngs 1 -1 sc (1) col0 sh gr\n/Times-Roman ff 300.00 scf sf\n1440 1890 m\ngs 1 -1 sc (2) col0 sh gr\n/Times-Roman ff 300.00 scf sf\n2895 2805 m\ngs 1 -1 sc (3) col0 sh gr\n/Times-Roman ff 300.00 scf sf\n2205 3795 m\ngs 1 -1 sc (4) col0 sh gr\n$F2psEnd\nrs\n\n%%EndDocument\n\n endTexFig\n 531 3990 a Fc(\\(a\\))1512 2504 y Fg(p)60 b(cnf)f(7)g(11)1512\n2624 y(-5)g(3)h(0)1512 2745 y(-5)f(4)h(0)1512 2865 y(5)g(-3)f(-4)g(0)\n1512 2985 y(6)h(-2)f(0)1512 3106 y(6)h(-5)f(0)1512 3226\ny(-6)g(2)h(5)f(0)1512 3347 y(7)h(1)f(5)h(0)1512 3467\ny(-7)f(1)h(-5)f(0)1512 3587 y(7)h(-1)f(-6)g(0)1512 3708\ny(-7)g(-1)h(6)f(0)1512 3828 y(7)h(0)1836 3990 y Fc(\\(b\\))2541\n2525 y Fg(p)f(cnf)g(4)h(3)2541 2645 y(1)f(-3)h(-4)f(0)2541\n2766 y(-1)g(2)h(3)f(0)2541 2886 y(-1)g(2)h(-3)f(4)h(0)2868\n3048 y Fc(\\(c\\))2541 3251 y Fg(p)f(cnf)g(5)h(5)2541 3371\ny(-5)f(1)h(0)2541 3492 y(5)f(-1)h(2)f(0)2541 3612 y(-3)g(-4)g(5)h(0)\n2541 3733 y(3)f(-5)h(0)2541 3853 y(-3)f(4)h(-5)f(0)2865\n3990 y Fc(\\(d\\))-189 4138 y Fl(Figure)46 b(1:)71 b(\\(a\\))47\nb(BDD;)e(\\(b\\))h(\\223Single-Node-Cut\\224)g(format;)55\nb(\\(c\\))46 b(\\223Maxterm-Cut\\224)g(format;)55 b(\\(d\\))45\nb(\\223)-8 b(Auxiliary-)-189 4258 y(V)d(ariable-Cut\\224)25\nb(F)o(ormat.)-189 4625 y Fj(3.2)119 b(Implementation)-189\n4813 y Fl(Store)25 b(and)g(Load)g(for)g(a)g(single)f(BDD)h(or)g(a)g\n(forest)g(of)g(BDDs)g(is)f(currently)h(implemented.)-189\n5073 y Fi(3.2.1)99 b(Storing)25 b(Decision)g(Diagrams)f(as)g(CNF)h(F)n\n(ormulas)-189 5260 y Fl(As)g(f)o(ar)g(as)g(the)g(storing)e(process)i\n(is)f(concerned)i(three)f(possible)e(formats)h(are)i(a)n(v)n(ailable:)\n-44 5431 y Fk(\\017)49 b Fl(DDDMP)p 421 5431 30 4 v 36\nw(CNF)p 650 5431 V 36 w(MODE)p 980 5431 V 35 w(NODE:)21\nb(store)f(a)h(BDD)h(by)e(introducing)f(an)i(auxiliary)g(v)n(ariable)f\n(for)h(each)g(BDD)55 5551 y(node)1794 5800 y(8)p eop\n%%Page: 9 9\n9 8 bop -44 218 a Fk(\\017)49 b Fl(DDDMP)p 421 218 30\n4 v 36 w(CNF)p 650 218 V 36 w(MODE)p 980 218 V 35 w(MAXTERM:)20\nb(store)g(a)h(BDD)h(by)e(follo)n(wing)f(the)h(maxterm)g(of)h(the)g\n(represented)55 338 y(function)-44 542 y Fk(\\017)49 b\nFl(DDDMP)p 421 542 V 36 w(CNF)p 650 542 V 36 w(MODE)p\n980 542 V 35 w(BEST)-5 b(:)32 b(trade-of)f(between)h(the)f(tw)o(o)f\n(pre)n(vious)g(solution,)h(trying)f(to)h(optimize)55\n662 y(the)25 b(number)f(of)h(literals)f(stored.)-189\n865 y(See)c(procedures)f(Dddmp)p 736 865 V 35 w(cuddBddStoreCnf)g(\\(to)\ng(store)f(a)h(single)f(BDD)i(as)e(a)i(CNF)f(formula\\))g(and)g(Dddmp)p\n3609 865 V 34 w(cuddBddArrayStoreCnf)-189 986 y(\\(to)25\nb(store)f(an)h(array)h(of)f(BDDs)g(as)f(a)i(CNF)f(formula\\).)-189\n1252 y Fi(3.2.2)99 b(Loadinf)26 b(CNF)e(F)n(ormulas)g(as)h(BDDs)-189\n1439 y Fl(As)g(f)o(ar)g(as)g(the)g(loading)e(process)i(is)f(concerned)i\n(three)f(possible)e(formats)i(are)g(a)n(v)n(ailable:)-44\n1643 y Fk(\\017)49 b Fl(DDDMP)p 421 1643 V 36 w(CNF)p\n650 1643 V 36 w(MODE)p 980 1643 V 35 w(NO)p 1159 1643\nV 36 w(CONJ:)25 b(Return)g(the)f(Clauses)h(without)f(Conjunction)-44\n1846 y Fk(\\017)49 b Fl(DDDMP)p 421 1846 V 36 w(CNF)p\n650 1846 V 36 w(MODE)p 980 1846 V 35 w(NO)p 1159 1846\nV 36 w(Q)o(U)l(ANT)-5 b(:)24 b(Return)h(the)g(sets)f(of)h(BDDs)g\n(without)f(Quanti\\002cation)-44 2050 y Fk(\\017)49 b Fl(DDDMP)p\n421 2050 V 36 w(CNF)p 650 2050 V 36 w(MODE)p 980 2050\nV 35 w(CONJ)p 1264 2050 V 36 w(Q)o(U)l(ANT)-5 b(:)23\nb(Return)h(the)g(sets)f(of)h(BDDs)g(AFTER)g(Existential)e(Quanti\\002-)\n55 2170 y(cation)-189 2373 y(See)e(procedures)f(Dddmp)p\n736 2373 V 35 w(cuddBddLoadCnf)f(\\(to)h(load)f(a)i(CNF)f(formula)g(as)g\n(a)g(single)f(BDD\\))h(and)g(Dddmp)p 3581 2373 V 35 w\n(cuddBddArrayLoadCnf)-189 2494 y(\\(to)35 b(load)h(a)g(CNF)g(formula)f\n(as)h(an)g(array)g(of)g(BDDs\\).)63 b(See)36 b(also)g(Dddmp)p\n2485 2494 V 34 w(cuddHeaderLoadCnf)h(to)e(load)g(the)-189\n2614 y(header)25 b(of)g(a)g(CNF)h(\\002le)f(to)g(gather)f(information)f\n(on)i(the)g(sa)n(v)o(ed)f(structure.)-189 2954 y Fo(4)143\nb(T)-13 b(est)35 b(Pr)m(ogram)f(and)h(Regr)m(ession)f(T)-13\nb(ests)-189 3177 y Fl(The)20 b Fc(testddmp.c)e Fl(\\002le,)j(pro)o\n(vided)d(with)h(this)f(distrib)n(ution,)g(e)o(x)o(empli\\002es)g(some)h\n(of)h(the)f(abo)o(v)o(e)g(features.)29 b(Moreo)o(v)o(er)l(,)-189\n3298 y(in)d(the)h Fc(e)n(xp)g Fl(e)o(xperiments)e(a)j(fe)n(w)e\n(scripts,)h(named)f Fc(test\\241n\\277.script)f Fl(are)i(a)n(v)n(ailable)\nf(for)h(a)g(sanity)f(check)h(of)g(the)g(tool)-189 3418\ny(and)e(to)f(tak)o(e)h(a)g(look)f(at)h(some)f(runs)h(e)o(x)o\n(empli\\002cation.)-189 3758 y Fo(5)143 b(Documentation)-189\n3981 y Fl(F)o(or)27 b(further)f(documentation)f(on)i(the)f(package)h\n(see)g(the)g(on-line)f(documentation)f(automatically)g(created)i(from)\n-189 4102 y(the)e(source)g(code)g(\\002les.)-189 4441\ny Fo(6)143 b(Ackno)o(wledgments)-189 4665 y Fl(W)-8 b(e)19\nb(are)h(particular)f(indebted)f(with)g(F)o(abio)g(Somenzi,)i(for)f\n(discussions,)f(advice,)i(and)f(for)g(including)e(the)i(DDDMP)-189\n4785 y(package)28 b(into)f(the)h(CUDD)g(distrib)n(ution.)37\nb(W)-8 b(e)29 b(also)e(thank)g(all)h(the)g(user)g(of)g(the)f(package)i\n(for)f(their)f(useful)h(indi-)-189 4905 y(cation)c(and)h(comments)f(on)\ng(the)h(it.)1794 5800 y(9)p eop\n%%Page: 10 10\n10 9 bop -189 218 a Fo(7)143 b(FTP)35 b(Site)-189 441\ny Fl(The)25 b(package)g(is)f(singularly)g(a)n(v)n(ailable)g(from:)-189\n645 y Fg(site:)59 b(ftp.polito.it)-189 765 y(user:)g(anonymous)-189\n885 y(directory:)f(/pub/research/dddmp)-189 1089 y Fl(or)25\nb(directly)f(from)h(the)f(author)h(WEB)g(pages:)-189\n1292 y Fg(WWW:)59 b(http://www.polito.it/\\230{cabodi)o(,quer)o(})-189\n1632 y Fo(8)143 b(F)l(eedback)-189 1855 y Fl(Send)25\nb(feedback)h(to:)-189 2059 y Fg(Gianpiero)58 b(Cabodi)g(&)i(Stefano)e\n(Quer)-189 2179 y(Politecnico)f(di)j(Torino)-189 2300\ny(Dipartimento)d(di)i(Automatica)f(e)i(Informatica)-189\n2420 y(Corso)f(Duca)g(degli)f(Abruzzi,)g(24)-189 2540\ny(I-10129)g(Torino)-189 2661 y(Italy)-189 2781 y(E-mail:)g\n({cabodi,quer}@polito.it)-189 2901 y(WWW:)h\n(http://www.polito.it/\\230{cabodi)o(,quer)o(})1769 5800\ny Fl(10)p eop\n%%Trailer\nend\nuserdict /end-hook known{end-hook}if\n%%EOF\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpAllAbs.html",
    "content": "<HTML>\n<HEAD><TITLE>dddmp package abstract</TITLE></HEAD>\n<BODY>\n\n\n<!-- Function Abstracts -->\n\n<dl>\n<DT> <A HREF=\"dddmpAllDet.html#DddmpBddReadHeaderCnf\" TARGET=\"MAIN\"><CODE>DddmpBddReadHeaderCnf()</CODE></A>\n<DD> Reads a the header of a dump file representing the argument \n    BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpBddReadHeader\" TARGET=\"MAIN\"><CODE>DddmpBddReadHeader()</CODE></A>\n<DD> Reads a the header of a dump file representing the\n    argument BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedAdd\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedAdd()</CODE></A>\n<DD> Marks a node as not visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedBdd\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedBdd()</CODE></A>\n<DD> Marks a node as not visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedCnfRecur\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedCnfRecur()</CODE></A>\n<DD> Mark ALL nodes as not visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedCnfRecur\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedCnfRecur()</CODE></A>\n<DD> Mark ALL nodes as not visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedCnf()</CODE></A>\n<DD> Marks a node as not visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedCnf()</CODE></A>\n<DD> Marks a node as not visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisited\" TARGET=\"MAIN\"><CODE>DddmpClearVisited()</CODE></A>\n<DD> Marks a node as not visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCnfClauses2Bdd\" TARGET=\"MAIN\"><CODE>DddmpCnfClauses2Bdd()</CODE></A>\n<DD> Transforms CNF clauses into BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddBddArrayStoreCnf\" TARGET=\"MAIN\"><CODE>DddmpCuddBddArrayStoreCnf()</CODE></A>\n<DD> Writes a dump file representing the argument Array of\n    BDDs in the CNF standard format.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddBddArrayStore\" TARGET=\"MAIN\"><CODE>DddmpCuddBddArrayStore()</CODE></A>\n<DD> Writes a dump file representing the argument Array of\n    BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayLoadCnf\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayLoadCnf()</CODE></A>\n<DD> Reads a dump file representing the argument BDDs in CNF\n     format.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayLoad\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayLoad()</CODE></A>\n<DD> Reads a dump file representing the argument BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreBdd\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreBdd()</CODE></A>\n<DD> Writes a dump file representing the argument Array of\n    BDDs/ADDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreBlifBody\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreBlifBody()</CODE></A>\n<DD> Writes a blif body representing the argument BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreBlifStep\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreBlifStep()</CODE></A>\n<DD> Performs the recursive step of DddmpCuddDdArrayStoreBlif.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreBlif\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreBlif()</CODE></A>\n<DD> Writes a blif file representing the argument BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStorePrefixBody\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStorePrefixBody()</CODE></A>\n<DD> Internal function to writes a dump file representing the\n    argument BDD in a prefix notation. Writes the body of the file.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStorePrefixStep\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStorePrefixStep()</CODE></A>\n<DD> Performs the recursive step of\n    DddmpCuddDdArrayStorePrefixBody.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStorePrefix\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStorePrefix()</CODE></A>\n<DD> Internal function to writes a dump file representing the\n    argument BDD in a prefix notation.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreSmvBody\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreSmvBody()</CODE></A>\n<DD> Internal function to writes a dump file representing the\n    argument BDD in a SMV notation. Writes the body of the file.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreSmvStep\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreSmvStep()</CODE></A>\n<DD> Performs the recursive step of\n    DddmpCuddDdArrayStoreSmvBody.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreSmv\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreSmv()</CODE></A>\n<DD> Internal function to writes a dump file representing the\n    argument BDD in a SMV notation.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCheckIncomingAndScanPath\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCheckIncomingAndScanPath()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCheckIncomingAndScanPath\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCheckIncomingAndScanPath()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCountEdgesAndNumber\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCountEdgesAndNumber()</CODE></A>\n<DD> Removes nodes from unique table and numbers each node according\n    to the number of its incoming BDD edges.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCountEdgesAndNumber\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCountEdgesAndNumber()</CODE></A>\n<DD> Removes nodes from unique table and numbers each node according\n    to the number of its incoming BDD edges.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCountEdgesRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCountEdgesRecur()</CODE></A>\n<DD> Counts the number of incoming edges for each node of a BDD\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCountEdgesRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCountEdgesRecur()</CODE></A>\n<DD> Counts the number of incoming edges for each node of a BDD\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesNumberEdgesRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesNumberEdgesRecur()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesNumberEdgesRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesNumberEdgesRecur()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesResetCountRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesResetCountRecur()</CODE></A>\n<DD> Resets counter and visited flag for ALL nodes of a BDD\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesResetCountRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesResetCountRecur()</CODE></A>\n<DD> Resets counter and visited flag for ALL nodes of a BDD\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpFreeHeaderCnf\" TARGET=\"MAIN\"><CODE>DddmpFreeHeaderCnf()</CODE></A>\n<DD> Frees the internal header structure.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpFreeHeader\" TARGET=\"MAIN\"><CODE>DddmpFreeHeader()</CODE></A>\n<DD> Frees the internal header structure.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpIntArrayDup\" TARGET=\"MAIN\"><CODE>DddmpIntArrayDup()</CODE></A>\n<DD> Duplicates an array of ints\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpIntArrayRead\" TARGET=\"MAIN\"><CODE>DddmpIntArrayRead()</CODE></A>\n<DD> Inputs an array of ints\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpIntArrayWrite\" TARGET=\"MAIN\"><CODE>DddmpIntArrayWrite()</CODE></A>\n<DD> Outputs an array of ints\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpNumberAddNodes\" TARGET=\"MAIN\"><CODE>DddmpNumberAddNodes()</CODE></A>\n<DD> Removes nodes from unique table and number them\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpNumberBddNodes\" TARGET=\"MAIN\"><CODE>DddmpNumberBddNodes()</CODE></A>\n<DD> Removes nodes from unique table and number them\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpNumberDdNodesCnf\" TARGET=\"MAIN\"><CODE>DddmpNumberDdNodesCnf()</CODE></A>\n<DD> Removes nodes from unique table and numbers them\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpNumberDdNodesCnf\" TARGET=\"MAIN\"><CODE>DddmpNumberDdNodesCnf()</CODE></A>\n<DD> Removes nodes from unique table and numbers them\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpNumberDdNodes\" TARGET=\"MAIN\"><CODE>DddmpNumberDdNodes()</CODE></A>\n<DD> Removes nodes from unique table and number them\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpPrintBddAndNextRecur\" TARGET=\"MAIN\"><CODE>DddmpPrintBddAndNextRecur()</CODE></A>\n<DD> Prints debug info\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpPrintBddAndNextRecur\" TARGET=\"MAIN\"><CODE>DddmpPrintBddAndNextRecur()</CODE></A>\n<DD> Prints debug info\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpPrintBddAndNext\" TARGET=\"MAIN\"><CODE>DddmpPrintBddAndNext()</CODE></A>\n<DD> Prints debug information\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpPrintBddAndNext\" TARGET=\"MAIN\"><CODE>DddmpPrintBddAndNext()</CODE></A>\n<DD> Prints debug information\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpReadCnfClauses\" TARGET=\"MAIN\"><CODE>DddmpReadCnfClauses()</CODE></A>\n<DD> Read the CNF clauses from the file in the standard DIMACS\n    format.\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpReadCode\" TARGET=\"MAIN\"><CODE>DddmpReadCode()</CODE></A>\n<DD> Reads a 1 byte node code\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpReadInt\" TARGET=\"MAIN\"><CODE>DddmpReadInt()</CODE></A>\n<DD> Reads a \"packed integer\"\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndexAdd\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndexAdd()</CODE></A>\n<DD> Reads the index of a node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndexBdd\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndexBdd()</CODE></A>\n<DD> Reads the index of a node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndexCnf\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndexCnf()</CODE></A>\n<DD> Reads the index of a node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndexCnf\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndexCnf()</CODE></A>\n<DD> Reads the index of a node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndex\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndex()</CODE></A>\n<DD> Reads the index of a node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisitedAdd\" TARGET=\"MAIN\"><CODE>DddmpSetVisitedAdd()</CODE></A>\n<DD> Marks a node as visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisitedBdd\" TARGET=\"MAIN\"><CODE>DddmpSetVisitedBdd()</CODE></A>\n<DD> Marks a node as visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpSetVisitedCnf()</CODE></A>\n<DD> Marks a node as visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpSetVisitedCnf()</CODE></A>\n<DD> Marks a node as visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisited\" TARGET=\"MAIN\"><CODE>DddmpSetVisited()</CODE></A>\n<DD> Marks a node as visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpStrArrayDup\" TARGET=\"MAIN\"><CODE>DddmpStrArrayDup()</CODE></A>\n<DD> Duplicates an array of strings\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpStrArrayFree\" TARGET=\"MAIN\"><CODE>DddmpStrArrayFree()</CODE></A>\n<DD> Frees an array of strings\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpStrArrayRead\" TARGET=\"MAIN\"><CODE>DddmpStrArrayRead()</CODE></A>\n<DD> Inputs an array of strings\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpStrArrayWrite\" TARGET=\"MAIN\"><CODE>DddmpStrArrayWrite()</CODE></A>\n<DD> Outputs an array of strings\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpStrDup\" TARGET=\"MAIN\"><CODE>DddmpStrDup()</CODE></A>\n<DD> Duplicates a string\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberAddNodes\" TARGET=\"MAIN\"><CODE>DddmpUnnumberAddNodes()</CODE></A>\n<DD> Restores nodes in unique table, loosing numbering\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberBddNodes\" TARGET=\"MAIN\"><CODE>DddmpUnnumberBddNodes()</CODE></A>\n<DD> Restores nodes in unique table, loosing numbering\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberDdNodesCnf\" TARGET=\"MAIN\"><CODE>DddmpUnnumberDdNodesCnf()</CODE></A>\n<DD> Restores nodes in unique table, loosing numbering\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberDdNodesCnf\" TARGET=\"MAIN\"><CODE>DddmpUnnumberDdNodesCnf()</CODE></A>\n<DD> Restores nodes in unique table, loosing numbering\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberDdNodes\" TARGET=\"MAIN\"><CODE>DddmpUnnumberDdNodes()</CODE></A>\n<DD> Restores nodes in unique table, loosing numbering\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpVisitedAdd\" TARGET=\"MAIN\"><CODE>DddmpVisitedAdd()</CODE></A>\n<DD> Returns true if node is visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpVisitedBdd\" TARGET=\"MAIN\"><CODE>DddmpVisitedBdd()</CODE></A>\n<DD> Returns true if node is visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpVisitedCnf()</CODE></A>\n<DD> Returns true if node is visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpVisitedCnf()</CODE></A>\n<DD> Returns true if node is visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpVisited\" TARGET=\"MAIN\"><CODE>DddmpVisited()</CODE></A>\n<DD> Returns true if node is visited\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteCode\" TARGET=\"MAIN\"><CODE>DddmpWriteCode()</CODE></A>\n<DD> Writes 1 byte node code\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteInt\" TARGET=\"MAIN\"><CODE>DddmpWriteInt()</CODE></A>\n<DD> Writes a \"packed integer\"\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexAdd\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexAdd()</CODE></A>\n<DD> Write index to node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexBdd\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexBdd()</CODE></A>\n<DD> Write index to node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexCnfBis\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexCnfBis()</CODE></A>\n<DD> Write index to node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexCnfWithTerminalCheck\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexCnfWithTerminalCheck()</CODE></A>\n<DD> Write index to node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexCnf\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexCnf()</CODE></A>\n<DD> Write index to node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexCnf\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexCnf()</CODE></A>\n<DD> Write index to node\n\n<DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndex\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndex()</CODE></A>\n<DD> Write index to node\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_Bin2Text\" TARGET=\"MAIN\"><CODE>Dddmp_Bin2Text()</CODE></A>\n<DD> Converts from binary to ASCII format\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_Text2Bin\" TARGET=\"MAIN\"><CODE>Dddmp_Text2Bin()</CODE></A>\n<DD> Converts from ASCII to binary format\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddAddArrayLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddAddArrayLoad()</CODE></A>\n<DD> Reads a dump file representing the argument ADDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddAddArrayStore\" TARGET=\"MAIN\"><CODE>Dddmp_cuddAddArrayStore()</CODE></A>\n<DD> Writes a dump file representing the argument Array of ADDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddAddLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddAddLoad()</CODE></A>\n<DD> Reads a dump file representing the argument ADD.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddAddStore\" TARGET=\"MAIN\"><CODE>Dddmp_cuddAddStore()</CODE></A>\n<DD> Writes a dump file representing the argument ADD.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayLoadCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayLoadCnf()</CODE></A>\n<DD> Reads a dump file in a CNF format.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayLoad()</CODE></A>\n<DD> Reads a dump file representing the argument BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreBlif\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStoreBlif()</CODE></A>\n<DD> Writes a dump file representing the argument BDD in\n    a Blif/Exlif notation.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStoreCnf()</CODE></A>\n<DD> Writes a dump file representing the argument array of BDDs\n    in CNF format.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStorePrefix\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStorePrefix()</CODE></A>\n<DD> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreSmv\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStoreSmv()</CODE></A>\n<DD> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStore\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStore()</CODE></A>\n<DD> Writes a dump file representing the argument Array of BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddDisplayBinary\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddDisplayBinary()</CODE></A>\n<DD> Display a binary dump file in a text file\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddLoadCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddLoadCnf()</CODE></A>\n<DD> Reads a dump file in a CNF format.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddLoad()</CODE></A>\n<DD> Reads a dump file representing the argument BDD.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStoreBlif\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStoreBlif()</CODE></A>\n<DD> Writes a dump file representing the argument BDD in\n    a Blif/Exlif notation.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStoreCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStoreCnf()</CODE></A>\n<DD> Writes a dump file representing the argument BDD in\n    a CNF format.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStorePrefix\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStorePrefix()</CODE></A>\n<DD> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStoreSmv\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStoreSmv()</CODE></A>\n<DD> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStore\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStore()</CODE></A>\n<DD> Writes a dump file representing the argument BDD.\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddHeaderLoadCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddHeaderLoadCnf()</CODE></A>\n<DD> Reads the header of a dump file representing the argument BDDs\n\n<DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddHeaderLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddHeaderLoad()</CODE></A>\n<DD> Reads the header of a dump file representing the argument BDDs\n\n<DT> <A HREF=\"dddmpAllDet.html#FindVarname\" TARGET=\"MAIN\"><CODE>FindVarname()</CODE></A>\n<DD> Performs binary search of a name within a sorted array\n\n<DT> <A HREF=\"dddmpAllDet.html#NodeBinaryStoreBdd\" TARGET=\"MAIN\"><CODE>NodeBinaryStoreBdd()</CODE></A>\n<DD> Store One Single Node in Binary Format.\n\n<DT> <A HREF=\"dddmpAllDet.html#NodeStoreRecurAdd\" TARGET=\"MAIN\"><CODE>NodeStoreRecurAdd()</CODE></A>\n<DD> Performs the recursive step of Dddmp_bddStore.\n\n<DT> <A HREF=\"dddmpAllDet.html#NodeStoreRecurBdd\" TARGET=\"MAIN\"><CODE>NodeStoreRecurBdd()</CODE></A>\n<DD> Performs the recursive step of Dddmp_bddStore.\n\n<DT> <A HREF=\"dddmpAllDet.html#NodeTextStoreAdd\" TARGET=\"MAIN\"><CODE>NodeTextStoreAdd()</CODE></A>\n<DD> Store One Single Node in Text Format.\n\n<DT> <A HREF=\"dddmpAllDet.html#NodeTextStoreBdd\" TARGET=\"MAIN\"><CODE>NodeTextStoreBdd()</CODE></A>\n<DD> Store One Single Node in Text Format.\n\n<DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecurAdd\" TARGET=\"MAIN\"><CODE>NumberNodeRecurAdd()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecurBdd\" TARGET=\"MAIN\"><CODE>NumberNodeRecurBdd()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecurCnf\" TARGET=\"MAIN\"><CODE>NumberNodeRecurCnf()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecurCnf\" TARGET=\"MAIN\"><CODE>NumberNodeRecurCnf()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecur\" TARGET=\"MAIN\"><CODE>NumberNodeRecur()</CODE></A>\n<DD> Number nodes recursively in post-order\n\n<DT> <A HREF=\"dddmpAllDet.html#QsortStrcmp\" TARGET=\"MAIN\"><CODE>QsortStrcmp()</CODE></A>\n<DD> String compare for qsort\n\n<DT> <A HREF=\"dddmpAllDet.html#ReadByteBinary\" TARGET=\"MAIN\"><CODE>ReadByteBinary()</CODE></A>\n<DD> Reads a byte from file with escaped <CR>, <LF> and <ctrl-Z>\n\n<DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecurAdd\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecurAdd()</CODE></A>\n<DD> Removes a node from unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecurBdd\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecurBdd()</CODE></A>\n<DD> Removes a node from unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecurCnf\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecurCnf()</CODE></A>\n<DD> Removes a node from unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecurCnf\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecurCnf()</CODE></A>\n<DD> Removes a node from unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecur\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecur()</CODE></A>\n<DD> Removes a node from unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecurAdd\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecurAdd()</CODE></A>\n<DD> Restores a node in unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecurBdd\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecurBdd()</CODE></A>\n<DD> Restores a node in unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecurCnf\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecurCnf()</CODE></A>\n<DD> Restores a node in unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecurCnf\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecurCnf()</CODE></A>\n<DD> Restores a node in unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecur\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecur()</CODE></A>\n<DD> Restores a node in unique table\n\n<DT> <A HREF=\"dddmpAllDet.html#StoreCnfBestNotSharedRecur\" TARGET=\"MAIN\"><CODE>StoreCnfBestNotSharedRecur()</CODE></A>\n<DD> Performs the recursive step of Print Best on Not Shared\n    sub-BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#StoreCnfBestSharedRecur\" TARGET=\"MAIN\"><CODE>StoreCnfBestSharedRecur()</CODE></A>\n<DD> Performs the recursive step of Print Best on Shared\n    sub-BDDs.\n\n<DT> <A HREF=\"dddmpAllDet.html#StoreCnfBest\" TARGET=\"MAIN\"><CODE>StoreCnfBest()</CODE></A>\n<DD> Prints a disjoint sum of products with intermediate\n    cutting points.\n\n<DT> <A HREF=\"dddmpAllDet.html#StoreCnfMaxtermByMaxtermRecur\" TARGET=\"MAIN\"><CODE>StoreCnfMaxtermByMaxtermRecur()</CODE></A>\n<DD> Performs the recursive step of Print Maxterm.\n\n<DT> <A HREF=\"dddmpAllDet.html#StoreCnfMaxtermByMaxterm\" TARGET=\"MAIN\"><CODE>StoreCnfMaxtermByMaxterm()</CODE></A>\n<DD> Prints a disjoint sum of products.\n\n<DT> <A HREF=\"dddmpAllDet.html#StoreCnfNodeByNodeRecur\" TARGET=\"MAIN\"><CODE>StoreCnfNodeByNodeRecur()</CODE></A>\n<DD> Performs the recursive step of Dddmp_bddStore.\n\n<DT> <A HREF=\"dddmpAllDet.html#StoreCnfNodeByNode\" TARGET=\"MAIN\"><CODE>StoreCnfNodeByNode()</CODE></A>\n<DD> Store the BDD as CNF clauses.\n\n<DT> <A HREF=\"dddmpAllDet.html#StoreCnfOneNode\" TARGET=\"MAIN\"><CODE>StoreCnfOneNode()</CODE></A>\n<DD> Store One Single BDD Node.\n\n<DT> <A HREF=\"dddmpAllDet.html#WriteByteBinary\" TARGET=\"MAIN\"><CODE>WriteByteBinary()</CODE></A>\n<DD> Writes a byte to file filtering <CR>, <LF> and <ctrl-Z>\n\n<DT> <A HREF=\"dddmpAllDet.html#printCubeCnf\" TARGET=\"MAIN\"><CODE>printCubeCnf()</CODE></A>\n<DD> Print One Cube in CNF Format.\n\n<DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n<DD> Checks for Warnings: If expr==1 it prints out the warning\n    on stderr.\n\n<DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n<DD> Checks for fatal bugs\n\n<DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n<DD> Checks for fatal bugs and go to the label to deal with\n    the error.\n\n<DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n<DD> Checks for fatal bugs and return the DDDMP_FAILURE flag.\n\n<DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n<DD> Memory Allocation Macro for DDDMP\n\n<DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n<DD> Memory Free Macro for DDDMP\n\n</DL>\n\n<HR>\n\nLast updated on 1040218 17h14\n</BODY></HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpAllByFile.html",
    "content": "<HTML>\n<HEAD><TITLE>The dddmp package for maintainers</TITLE></HEAD>\n\n<FRAMESET ROWS=\"5%,90%,5%\">\n  <FRAME SRC=\"dddmpTitle.html\">\n  <FRAMESET COLS=\"40%,60%\">\n    <FRAME SRC=\"dddmpAllFile.html\" NAME=\"ABSTRACT\">\n    <FRAME SRC=\"dddmpAllDet.html\" NAME=\"MAIN\">\n  </FRAMESET>\n  <FRAME SRC=\"credit.html\">\n</FRAMESET>\n\n</HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpAllByFunc.html",
    "content": "<HTML>\n<HEAD><TITLE>The dddmp package for maintainers</TITLE></HEAD>\n\n<FRAMESET ROWS=\"5%,90%,5%\">\n  <FRAME SRC=\"dddmpTitle.html\">\n  <FRAMESET COLS=\"40%,60%\">\n    <FRAME SRC=\"dddmpAllAbs.html\" NAME=\"ABSTRACT\">\n    <FRAME SRC=\"dddmpAllDet.html\" NAME=\"MAIN\">\n  </FRAMESET>\n  <FRAME SRC=\"credit.html\">\n</FRAMESET>\n\n</HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpAllDet.html",
    "content": "<html>\n<head><title>The dddmp package: all functions </title></head>\n<body>\n\nA set of internal low-level routines of the dddmp package\n    doing:\n    <ul>\n      <li> read and write of node codes in binary mode,\n      <li> read and write of integers in binary mode,\n      <li> marking/unmarking nodes as visited,\n      <li> numbering nodes.\n    </ul>\n<HR>\n<DL>\n<dt><pre>\n<A NAME=\"DddmpBddReadHeaderCnf\"></A>\nstatic Dddmp_Hdr_t * <I></I>\n<B>DddmpBddReadHeaderCnf</B>(\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads the header of a dump file. Builds a Dddmp_Hdr_t struct\n    containing all infos in the header, for next manipulations.\n<p>\n\n<dd> <b>Side Effects</b> none\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoadCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoadCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpBddReadHeader\"></A>\nstatic Dddmp_Hdr_t * <I></I>\n<B>DddmpBddReadHeader</B>(\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads the header of a dump file. Builds a Dddmp_Hdr_t struct\n    containing all infos in the header, for next manipulations.\n<p>\n\n<dd> <b>Side Effects</b> none\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoad.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoad.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpClearVisitedAdd\"></A>\nvoid <I></I>\n<B>DddmpClearVisitedAdd</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as not visited)</i>\n)\n</pre>\n<dd> Marks a node as not visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedAdd\">DddmpVisitedAdd</a>\n()\n<a href=\"#DddmpSetVisitedAdd\">DddmpSetVisitedAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpClearVisitedBdd\"></A>\nvoid <I></I>\n<B>DddmpClearVisitedBdd</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as not visited)</i>\n)\n</pre>\n<dd> Marks a node as not visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisited\">DddmpVisited</a>\n()\n<a href=\"#DddmpSetVisited\">DddmpSetVisited</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpClearVisitedCnfRecur\"></A>\nstatic int <I></I>\n<B>DddmpClearVisitedCnfRecur</B>(\n  DdNode * <b>f</b> <i>IN: root of the BDD to be marked</i>\n)\n</pre>\n<dd> Mark ALL nodes as not visited (it recurs on the node children)\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpClearVisitedCnfRecur\"></A>\nstatic int <I></I>\n<B>DddmpClearVisitedCnfRecur</B>(\n  DdNode * <b>f</b> <i>IN: root of the BDD to be marked</i>\n)\n</pre>\n<dd> Mark ALL nodes as not visited (it recurs on the node children)\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpClearVisitedCnf\"></A>\nstatic void <I></I>\n<B>DddmpClearVisitedCnf</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as not visited)</i>\n)\n</pre>\n<dd> Marks a node as not visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpClearVisitedCnf\"></A>\nstatic void <I></I>\n<B>DddmpClearVisitedCnf</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as not visited)</i>\n)\n</pre>\n<dd> Marks a node as not visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpClearVisited\"></A>\nvoid <I></I>\n<B>DddmpClearVisited</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as not visited)</i>\n)\n</pre>\n<dd> Marks a node as not visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisited\">DddmpVisited</a>\n()\n<a href=\"#DddmpSetVisited\">DddmpSetVisited</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCnfClauses2Bdd\"></A>\nstatic int <I></I>\n<B>DddmpCnfClauses2Bdd</B>(\n  Dddmp_Hdr_t * <b>Hdr</b>, <i>IN: file header</i>\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int ** <b>cnfTable</b>, <i>IN: CNF table for clauses</i>\n  int  <b>mode</b>, <i>IN: computation mode</i>\n  DdNode *** <b>rootsPtrPtr</b> <i>OUT: array of returned BDD roots (by reference)</i>\n)\n</pre>\n<dd> Transforms CNF clauses into BDDs. Clauses are stored in an\n   internal structure previously read. The results can be given in\n   different format according to the mode selection:\n     IFF mode == 0 Return the Clauses without Conjunction\n     IFF mode == 1 Return the sets of BDDs without Quantification\n     IFF mode == 2 Return the sets of BDDs AFTER Existential Quantification\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoadCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoadCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddBddArrayStoreCnf\"></A>\nstatic int <I></I>\n<B>DddmpCuddBddArrayStoreCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  int  <b>rootN</b>, <i>IN: # of output BDD roots to be stored</i>\n  Dddmp_DecompCnfStoreType  <b>mode</b>, <i>IN: format selection</i>\n  int  <b>noHeader</b>, <i>IN: do not store header iff 1</i>\n  char ** <b>varNames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>bddIds</b>, <i>IN: array of BDD node Ids (or NULL)</i>\n  int * <b>bddAuxIds</b>, <i>IN: array of BDD Aux Ids (or NULL)</i>\n  int * <b>cnfIds</b>, <i>IN: array of CNF ids (or NULL)</i>\n  int  <b>idInitial</b>, <i>IN: starting id for cutting variables</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # Incoming Edges</i>\n  int  <b>pathLengthTh</b>, <i>IN: Max Path Length</i>\n  char * <b>fname</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: pointer to the store file</i>\n  int * <b>clauseNPtr</b>, <i>OUT: number of clause stored</i>\n  int * <b>varNewNPtr</b> <i>OUT: number of new variable created</i>\n)\n</pre>\n<dd> Dumps the argument array of BDDs/ADDs to file in CNF format.\n    The following arrays: varNames, bddIds, bddAuxIds, and cnfIds \n    fix the correspondence among variable names, BDD ids, BDD \n    auxiliary ids and the ids used to store the CNF problem.\n    All these arrays are automatically created iff NULL.\n    Auxiliary variable, iff necessary, are created starting from value\n    idInitial.\n    Iff idInitial is <= 0 its value is selected as the number of internal\n    CUDD variable + 2.\n    Auxiliary variables, i.e., cut points are inserted following these\n    criterias:\n    * edgeInTh\n      indicates the maximum number of incoming edges up to which\n      no cut point (auxiliary variable) is inserted.\n      If edgeInTh:\n      * is equal to -1 no cut point due to incoming edges are inserted\n        (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node with a single\n        incoming edge, i.e., each node, (NodeByNode method).\n\t* is equal to n a cut point is inserted for each node with (n+1)\n        incoming edges.\n    * pathLengthTh\n      indicates the maximum length path up to which no cut points\n      (auxiliary variable) is inserted.\n      If the path length between two nodes exceeds this value, a cut point\n      is inserted.\n      If pathLengthTh:\n      * is equal to -1 no cut point due path length are inserted\n        (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node (NodeByNode\n        method).\n\t* is equal to n a cut point is inserted on path whose length is\n        equal to (n+1).\n      Notice that the maximum number of literals in a clause is equal\n      to (pathLengthTh + 2), i.e., for each path we have to keep into\n      account a CNF variable for each node plus 2 added variables for\n      the bottom and top-path cut points.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash table. \n    They are re-linked after the store operation in a modified \n    order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddBddArrayStore\"></A>\nint <I></I>\n<B>DddmpCuddBddArrayStore</B>(\n  Dddmp_DecompType  <b>ddType</b>, <i>IN: Selects the decomp type BDD</i>\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: DD name (or NULL)</i>\n  int  <b>nRoots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of DD roots to be stored</i>\n  char ** <b>rootnames</b>, <i>IN: array of root names (or NULL)</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var IDs</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument array of BDDs to file.\n    Internal function doing inner steps of store for BDDs.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n<a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayLoadCnf\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayLoadCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_RootMatchType  <b>rootmatchmode</b>, <i>IN: storing mode selector</i>\n  char ** <b>rootmatchnames</b>, <i>IN: sorted names for loaded roots</i>\n  Dddmp_VarMatchType  <b>varmatchmode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by ids</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by ids</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids, by ids</i>\n  int  <b>mode</b>, <i>IN: computation mode</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>rootsPtrPtr</b>, <i>OUT: array of BDD roots</i>\n  int * <b>nRoots</b> <i>OUT: number of BDDs returned</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDDs in CNF\n    format.\n      IFF mode == 0 Return the Clauses without Conjunction\n      IFF mode == 1 Return the sets of BDDs without Quantification\n      IFF mode == 2 Return the sets of BDDs AFTER Existential Quantification\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoadCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoadCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayLoad\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayLoad</B>(\n  Dddmp_DecompType  <b>ddType</b>, <i>IN: Selects decomp type</i>\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_RootMatchType  <b>rootMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>rootmatchnames</b>, <i>IN: sorted names for loaded roots</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by ids</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by ids</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids, by ids</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>pproots</b> <i>OUT: array BDD roots (by reference)</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDDs. The header is\n    common to both text and binary mode. The node list is either \n    in text or binary format. A dynamic vector of DD pointers \n    is allocated to support conversion from DD indexes to pointers.\n    Several criteria are supported for variable match between file\n    and dd manager. Several changes/permutations/compositions are allowed\n    for variables while loading DDs. Variable of the dd manager are allowed \n    to match with variables on file on ids, permids, varnames, \n    varauxids; also direct composition between ids and \n    composeids is supported. More in detail:\n    <ol>\n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    allows the loading of a DD keeping variable IDs unchanged\n    (regardless of the variable ordering of the reading manager); this\n    is useful, for example, when swapping DDs to file and restoring them\n    later from file, after possible variable reordering activations.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHPERMIDS <p>\n    is used to allow variable match according to the position in the ordering.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHNAMES <p>\n    requires a non NULL varmatchnames parameter; this is a vector of\n    strings in one-to-one correspondence with variable IDs of the\n    reading manager. Variables in the DD file read are matched with\n    manager variables according to their name (a non NULL varnames\n    parameter was required while storing the DD file).\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    has a meaning similar to DDDMP_VAR_MATCHNAMES, but integer auxiliary\n    IDs are used instead of strings; the additional non NULL\n    varmatchauxids parameter is needed.\n    \n    <li> varMatchMode=DDDMP_VAR_COMPOSEIDS <p>\n    uses the additional varcomposeids parameter is used as array of\n    variable ids to be composed with ids stored in file.\n    </ol>\n    \n    In the present implementation, the array varnames (3), varauxids (4)\n    and composeids (5) need to have one entry for each variable in the \n    DD manager (NULL pointers are allowed for unused variables\n    in varnames). Hence variables need to be already present in the \n    manager. All arrays are sorted according to IDs.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoad.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoad.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStoreBdd\"></A>\nint <I></I>\n<B>DddmpCuddDdArrayStoreBdd</B>(\n  Dddmp_DecompType  <b>ddType</b>, <i>IN: Selects the decomp type: BDD or ADD</i>\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: DD name (or NULL)</i>\n  int  <b>nRoots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of DD roots to be stored</i>\n  char ** <b>rootnames</b>, <i>IN: array of root names (or NULL)</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var IDs</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument array of BDDs/ADDs to file. Internal \n    function doing inner steps of store for BDDs and ADDs.\n    ADD store is presently supported only with the text format.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n<a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStoreBlifBody\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStoreBlifBody</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: Manager</i>\n  int  <b>n</b>, <i>IN: Number of output nodes to be dumped</i>\n  DdNode ** <b>f</b>, <i>IN: Array of output nodes to be dumped</i>\n  char ** <b>inputNames</b>, <i>IN: Array of input names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: Array of output names (or NULL)</i>\n  FILE * <b>fp</b> <i>IN: Pointer to the dump file</i>\n)\n</pre>\n<dd> Writes a blif body representing the argument BDDs as a\n    network of multiplexers. One multiplexer is written for each BDD\n    node. It returns 1 in case of success; 0 otherwise (e.g.,\n    out-of-memory, file system full, or an ADD with constants different\n    from 0 and 1).\n    DddmpCuddDdArrayStoreBlif does not close the file: This is the\n    caller responsibility.\n    DddmpCuddDdArrayStoreBlif uses a minimal unique subset of\n    the hexadecimal address of a node as name for it.  If the argument\n    inputNames is non-null, it is assumed to hold the pointers to the names\n    of the inputs. Similarly for outputNames. This function prints out only\n    .names part.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStoreBlifStep\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStoreBlifStep</B>(\n  DdManager * <b>ddMgr</b>, <i></i>\n  DdNode * <b>f</b>, <i></i>\n  FILE * <b>fp</b>, <i></i>\n  st_table * <b>visited</b>, <i></i>\n  char ** <b>names</b> <i></i>\n)\n</pre>\n<dd> Performs the recursive step of DddmpCuddDdArrayStoreBlif.\n    Traverses the BDD f and writes a multiplexer-network description to\n    the file pointed by fp in blif format.\n    f is assumed to be a regular pointer and DddmpCuddDdArrayStoreBlifStep\n    guarantees this assumption in the recursive calls.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStoreBlif\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStoreBlif</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: Manager</i>\n  int  <b>n</b>, <i>IN: Number of output nodes to be dumped</i>\n  DdNode ** <b>f</b>, <i>IN: Array of output nodes to be dumped</i>\n  char ** <b>inputNames</b>, <i>IN: Array of input names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: Array of output names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model name (or NULL)</i>\n  FILE * <b>fp</b> <i>IN: Pointer to the dump file</i>\n)\n</pre>\n<dd> Writes a blif file representing the argument BDDs as a\n    network of multiplexers. One multiplexer is written for each BDD\n    node. It returns 1 in case of success; 0 otherwise (e.g.,\n    out-of-memory, file system full, or an ADD with constants different\n    from 0 and 1).\n    DddmpCuddDdArrayStoreBlif does not close the file: This is the\n    caller responsibility.\n    DddmpCuddDdArrayStoreBlif uses a minimal unique subset of\n    the hexadecimal address of a node as name for it.  If the argument\n    inames is non-null, it is assumed to hold the pointers to the names\n    of the inputs. Similarly for outputNames.\n    It prefixes the string \"NODE\" to each nome to have \"regular\" names\n    for each elements.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpCuddDdArrayStoreBlifBody\">DddmpCuddDdArrayStoreBlifBody</a>\n<a href=\"#Cudd_DumpBlif\">Cudd_DumpBlif</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStorePrefixBody\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStorePrefixBody</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: Manager</i>\n  int  <b>n</b>, <i>IN: Number of output nodes to be dumped</i>\n  DdNode ** <b>f</b>, <i>IN: Array of output nodes to be dumped</i>\n  char ** <b>inputNames</b>, <i>IN: Array of input names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: Array of output names (or NULL)</i>\n  FILE * <b>fp</b> <i>IN: Pointer to the dump file</i>\n)\n</pre>\n<dd> One multiplexer is written for each BDD node.\n    It returns 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n    system full, or an ADD with constants different from 0 and 1).\n    It does not close the file: This is the caller responsibility.\n    It uses a minimal unique subset of the hexadecimal address of a node as\n    name for it.\n    If the argument inputNames is non-null, it is assumed to hold the\n    pointers to the names of the inputs. Similarly for outputNames.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpCuddDdArrayStoreBlif\">DddmpCuddDdArrayStoreBlif</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStorePrefixStep\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStorePrefixStep</B>(\n  DdManager * <b>ddMgr</b>, <i></i>\n  DdNode * <b>f</b>, <i></i>\n  FILE * <b>fp</b>, <i></i>\n  st_table * <b>visited</b>, <i></i>\n  char ** <b>names</b> <i></i>\n)\n</pre>\n<dd> Performs the recursive step of\n    DddmpCuddDdArrayStorePrefixBody.\n    Traverses the BDD f and writes a multiplexer-network description to the\n    file pointed by fp.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    f is assumed to be a regular pointer and the function guarantees this\n    assumption in the recursive calls.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStorePrefix\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStorePrefix</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: Manager</i>\n  int  <b>n</b>, <i>IN: Number of output nodes to be dumped</i>\n  DdNode ** <b>f</b>, <i>IN: Array of output nodes to be dumped</i>\n  char ** <b>inputNames</b>, <i>IN: Array of input names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: Array of output names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model name (or NULL)</i>\n  FILE * <b>fp</b> <i>IN: Pointer to the dump file</i>\n)\n</pre>\n<dd> One multiplexer is written for each BDD node.\n    It returns 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n    system full, or an ADD with constants different from 0 and 1).\n    It does not close the file: This is the caller responsibility.\n    It uses a minimal unique subset of the hexadecimal address of a node as\n    name for it.\n    If the argument inputNames is non-null, it is assumed to hold the\n    pointers to the names of the inputs. Similarly for outputNames.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    Comments (COMMENT) are added at the beginning of the description to\n    describe inputs and outputs of the design.\n    A buffer (BUF) is add on the output to cope with complemented functions.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpCuddDdArrayStoreBlif\">DddmpCuddDdArrayStoreBlif</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStoreSmvBody\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStoreSmvBody</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: Manager</i>\n  int  <b>n</b>, <i>IN: Number of output nodes to be dumped</i>\n  DdNode ** <b>f</b>, <i>IN: Array of output nodes to be dumped</i>\n  char ** <b>inputNames</b>, <i>IN: Array of input names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: Array of output names (or NULL)</i>\n  FILE * <b>fp</b> <i>IN: Pointer to the dump file</i>\n)\n</pre>\n<dd> One multiplexer is written for each BDD node.\n    It returns 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n    system full, or an ADD with constants different from 0 and 1).\n    It does not close the file: This is the caller responsibility.\n    It uses a minimal unique subset of the hexadecimal address of a node as\n    name for it.\n    If the argument inputNames is non-null, it is assumed to hold the\n    pointers to the names of the inputs. Similarly for outputNames.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpCuddDdArrayStoreBlif\">DddmpCuddDdArrayStoreBlif</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStoreSmvStep\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStoreSmvStep</B>(\n  DdManager * <b>ddMgr</b>, <i></i>\n  DdNode * <b>f</b>, <i></i>\n  FILE * <b>fp</b>, <i></i>\n  st_table * <b>visited</b>, <i></i>\n  char ** <b>names</b> <i></i>\n)\n</pre>\n<dd> Performs the recursive step of\n    DddmpCuddDdArrayStoreSmvBody.\n    Traverses the BDD f and writes a multiplexer-network description to the\n    file pointed by fp.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    f is assumed to be a regular pointer and the function guarantees this\n    assumption in the recursive calls.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpCuddDdArrayStoreSmv\"></A>\nstatic int <I></I>\n<B>DddmpCuddDdArrayStoreSmv</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: Manager</i>\n  int  <b>n</b>, <i>IN: Number of output nodes to be dumped</i>\n  DdNode ** <b>f</b>, <i>IN: Array of output nodes to be dumped</i>\n  char ** <b>inputNames</b>, <i>IN: Array of input names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: Array of output names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model name (or NULL)</i>\n  FILE * <b>fp</b> <i>IN: Pointer to the dump file</i>\n)\n</pre>\n<dd> One multiplexer is written for each BDD node.\n    It returns 1 in case of success; 0 otherwise (e.g., out-of-memory, file\n    system full, or an ADD with constants different from 0 and 1).\n    It does not close the file: This is the caller responsibility.\n    It uses a minimal unique subset of the hexadecimal address of a node as\n    name for it.\n    If the argument inputNames is non-null, it is assumed to hold the\n    pointers to the names of the inputs. Similarly for outputNames.\n    For each BDD node of function f, variable v, then child T, and else\n    child E it stores:\n    f = v * T + v' * E\n    that is\n    (OR f (AND v T) (AND (NOT v) E))\n    If E is a complemented child this results in the following\n    (OR f (AND v T) (AND (NOT v) (NOT E)))\n    Comments (COMMENT) are added at the beginning of the description to\n    describe inputs and outputs of the design.\n    A buffer (BUF) is add on the output to cope with complemented functions.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpCuddDdArrayStoreBlif\">DddmpCuddDdArrayStoreBlif</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesCheckIncomingAndScanPath\"></A>\nstatic void <I></I>\n<B>DddmpDdNodesCheckIncomingAndScanPath</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node to be numbered</i>\n  int  <b>pathLengthCurrent</b>, <i>IN: Current Path Length</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # In-Edges, after a Insert Cut Point</i>\n  int  <b>pathLengthTh</b> <i>IN: Max Path Length (after, Insert a Cut Point)</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with the right polarity.\n    The node is assigned to a new CNF variable only if it is a \"shared\"\n    node (i.e. the number of its incoming edges is greater than 1).\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are set.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesCheckIncomingAndScanPath\"></A>\nstatic void <I></I>\n<B>DddmpDdNodesCheckIncomingAndScanPath</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node to be numbered</i>\n  int  <b>pathLengthCurrent</b>, <i>IN: Current Path Length</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # In-Edges, after a Insert Cut Point</i>\n  int  <b>pathLengthTh</b> <i>IN: Max Path Length (after, Insert a Cut Point)</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with the right polarity.\n    The node is assigned to a new CNF variable only if it is a \"shared\"\n    node (i.e. the number of its incoming edges is greater than 1).\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are set.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesCountEdgesAndNumber\"></A>\nint <I></I>\n<B>DddmpDdNodesCountEdgesAndNumber</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: Array of BDDs</i>\n  int  <b>rootN</b>, <i>IN: Number of BDD roots in the array of BDDs</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # In-Edges, after a Insert Cut Point</i>\n  int  <b>pathLengthTh</b>, <i>IN: Max Path Length (after, Insert a Cut Point)</i>\n  int * <b>cnfIds</b>, <i>OUT: CNF identifiers for variables</i>\n  int  <b>id</b> <i>OUT: Number of Temporary Variables Introduced</i>\n)\n</pre>\n<dd> Removes nodes from unique table and numbers each node according\n    to the number of its incoming BDD edges.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique table\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUniqueRecurCnf()\">RemoveFromUniqueRecurCnf()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesCountEdgesAndNumber\"></A>\nint <I></I>\n<B>DddmpDdNodesCountEdgesAndNumber</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: Array of BDDs</i>\n  int  <b>rootN</b>, <i>IN: Number of BDD roots in the array of BDDs</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # In-Edges, after a Insert Cut Point</i>\n  int  <b>pathLengthTh</b>, <i>IN: Max Path Length (after, Insert a Cut Point)</i>\n  int * <b>cnfIds</b>, <i>OUT: CNF identifiers for variables</i>\n  int  <b>id</b> <i>OUT: Number of Temporary Variables Introduced</i>\n)\n</pre>\n<dd> Removes nodes from unique table and numbers each node according\n    to the number of its incoming BDD edges.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique table\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUniqueRecurCnf()\">RemoveFromUniqueRecurCnf()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesCountEdgesRecur\"></A>\nstatic int <I></I>\n<B>DddmpDdNodesCountEdgesRecur</B>(\n  DdNode * <b>f</b> <i>IN: root of the BDD</i>\n)\n</pre>\n<dd> Counts (recursively) the number of incoming edges for each \n    node of a BDD. This number is stored in the index field.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags remain untouched.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesCountEdgesRecur\"></A>\nstatic int <I></I>\n<B>DddmpDdNodesCountEdgesRecur</B>(\n  DdNode * <b>f</b> <i>IN: root of the BDD</i>\n)\n</pre>\n<dd> Counts (recursively) the number of incoming edges for each \n    node of a BDD. This number is stored in the index field.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags remain untouched.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesNumberEdgesRecur\"></A>\nstatic int <I></I>\n<B>DddmpDdNodesNumberEdgesRecur</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node to be numbered</i>\n  int * <b>cnfIds</b>, <i>IN: possible source for numbering</i>\n  int  <b>id</b> <i>IN/OUT: possible source for numbering</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with the inverse polarity.\n    Numbering follows the subsequent strategy:\n    * if the index = 0 it remains so\n    * if the index >= 1 it gets enumerated.\n      This implies that the node is assigned to a new CNF variable only if\n      it is not a terminal node otherwise it is assigned the index of\n      the BDD variable.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are reset.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesNumberEdgesRecur\"></A>\nstatic int <I></I>\n<B>DddmpDdNodesNumberEdgesRecur</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node to be numbered</i>\n  int * <b>cnfIds</b>, <i>IN: possible source for numbering</i>\n  int  <b>id</b> <i>IN/OUT: possible source for numbering</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with the inverse polarity.\n    Numbering follows the subsequent strategy:\n    * if the index = 0 it remains so\n    * if the index >= 1 it gets enumerated.\n      This implies that the node is assigned to a new CNF variable only if\n      it is not a terminal node otherwise it is assigned the index of\n      the BDD variable.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are reset.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesResetCountRecur\"></A>\nstatic int <I></I>\n<B>DddmpDdNodesResetCountRecur</B>(\n  DdNode * <b>f</b> <i>IN: root of the BDD whose counters are reset</i>\n)\n</pre>\n<dd> Resets counter and visited flag for ALL nodes of a BDD (it \n    recurs on the node children). The index field of the node is \n    used as counter.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpDdNodesResetCountRecur\"></A>\nstatic int <I></I>\n<B>DddmpDdNodesResetCountRecur</B>(\n  DdNode * <b>f</b> <i>IN: root of the BDD whose counters are reset</i>\n)\n</pre>\n<dd> Resets counter and visited flag for ALL nodes of a BDD (it \n    recurs on the node children). The index field of the node is \n    used as counter.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpFreeHeaderCnf\"></A>\nstatic void <I></I>\n<B>DddmpFreeHeaderCnf</B>(\n  Dddmp_Hdr_t * <b>Hdr</b> <i>IN: pointer to header</i>\n)\n</pre>\n<dd> Frees the internal header structure by freeing all internal\n    fields first.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoadCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoadCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpFreeHeader\"></A>\nstatic void <I></I>\n<B>DddmpFreeHeader</B>(\n  Dddmp_Hdr_t * <b>Hdr</b> <i>IN: pointer to header</i>\n)\n</pre>\n<dd> Frees the internal header structureby freeing all internal\n    fields first.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoad.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoad.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpIntArrayDup\"></A>\nint * <I></I>\n<B>DddmpIntArrayDup</B>(\n  int * <b>array</b>, <i>IN: array of ints to be duplicated</i>\n  int  <b>n</b> <i>IN: size of the array</i>\n)\n</pre>\n<dd> Allocates memory and copies source array\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpIntArrayRead\"></A>\nint * <I></I>\n<B>DddmpIntArrayRead</B>(\n  FILE * <b>fp</b>, <i>IN: input file</i>\n  int  <b>n</b> <i>IN: size of the array</i>\n)\n</pre>\n<dd> Allocates memory and inputs source array\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpIntArrayWrite\"></A>\nint <I></I>\n<B>DddmpIntArrayWrite</B>(\n  FILE * <b>fp</b>, <i>IN: output file</i>\n  int * <b>array</b>, <i>IN: array of ints</i>\n  int  <b>n</b> <i>IN: size of the array</i>\n)\n</pre>\n<dd> Outputs an array of ints to a specified file\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpNumberAddNodes\"></A>\nint <I></I>\n<B>DddmpNumberAddNodes</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>n</b> <i>IN: number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Node numbering is required to convert pointers to integers.\n    Since nodes are removed from unique table, no new nodes should \n    be generated before re-inserting nodes in the unique table\n    (DddmpUnnumberDdNodes()).\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique table\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUniqueRecurAdd\">RemoveFromUniqueRecurAdd</a>\n()\n<a href=\"#NumberNodeRecurAdd\">NumberNodeRecurAdd</a>\n()\n<a href=\"#DddmpUnnumberDdNodesAdd\">DddmpUnnumberDdNodesAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpNumberBddNodes\"></A>\nint <I></I>\n<B>DddmpNumberBddNodes</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>n</b> <i>IN: number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Node numbering is required to convert pointers to integers.\n    Since nodes are removed from unique table, no new nodes should \n    be generated before re-inserting nodes in the unique table\n    (DddmpUnnumberBddNodes ()).\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique table\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUniqueRecur()\">RemoveFromUniqueRecur()</a>\n<a href=\"#NumberNodeRecur()\">NumberNodeRecur()</a>\n<a href=\"#DddmpUnnumberBddNodes\">DddmpUnnumberBddNodes</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpNumberDdNodesCnf\"></A>\nint <I></I>\n<B>DddmpNumberDdNodesCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>rootN</b>, <i>IN: number of BDD roots in the array of BDDs</i>\n  int * <b>cnfIds</b>, <i>OUT: CNF identifiers for variables</i>\n  int  <b>id</b> <i>OUT: number of Temporary Variables Introduced</i>\n)\n</pre>\n<dd> Node numbering is required to convert pointers to integers.\n    Since nodes are removed from unique table, no new nodes should \n    be generated before re-inserting nodes in the unique table\n    (DddmpUnnumberDdNodesCnf()).\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique table\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUniqueRecurCnf()\">RemoveFromUniqueRecurCnf()</a>\n<a href=\"#NumberNodeRecurCnf()\">NumberNodeRecurCnf()</a>\n<a href=\"#DddmpUnnumberDdNodesCnf()\">DddmpUnnumberDdNodesCnf()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpNumberDdNodesCnf\"></A>\nint <I></I>\n<B>DddmpNumberDdNodesCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>rootN</b>, <i>IN: number of BDD roots in the array of BDDs</i>\n  int * <b>cnfIds</b>, <i>OUT: CNF identifiers for variables</i>\n  int  <b>id</b> <i>OUT: number of Temporary Variables Introduced</i>\n)\n</pre>\n<dd> Node numbering is required to convert pointers to integers.\n    Since nodes are removed from unique table, no new nodes should \n    be generated before re-inserting nodes in the unique table\n    (DddmpUnnumberDdNodesCnf()).\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique table\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUniqueRecurCnf()\">RemoveFromUniqueRecurCnf()</a>\n<a href=\"#NumberNodeRecurCnf()\">NumberNodeRecurCnf()</a>\n<a href=\"#DddmpUnnumberDdNodesCnf()\">DddmpUnnumberDdNodesCnf()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpNumberDdNodes\"></A>\nint <I></I>\n<B>DddmpNumberDdNodes</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>n</b> <i>IN: number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Node numbering is required to convert pointers to integers.\n    Since nodes are removed from unique table, no new nodes should \n    be generated before re-inserting nodes in the unique table\n    (DddmpUnnumberDdNodes()).\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique table\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUniqueRecur()\">RemoveFromUniqueRecur()</a>\n<a href=\"#NumberNodeRecur()\">NumberNodeRecur()</a>\n<a href=\"#DddmpUnnumberDdNodes()\">DddmpUnnumberDdNodes()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpPrintBddAndNextRecur\"></A>\nstatic int <I></I>\n<B>DddmpPrintBddAndNextRecur</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be displayed</i>\n)\n</pre>\n<dd> Prints debug info for a BDD on the screen. It recurs on \n    node's children.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpPrintBddAndNextRecur\"></A>\nstatic int <I></I>\n<B>DddmpPrintBddAndNextRecur</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be displayed</i>\n)\n</pre>\n<dd> Prints debug info for a BDD on the screen. It recurs on \n    node's children.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpPrintBddAndNext\"></A>\nint <I></I>\n<B>DddmpPrintBddAndNext</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: Array of BDDs to be displayed</i>\n  int  <b>rootN</b> <i>IN: Number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Prints debug information for an array of BDDs on the screen\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpPrintBddAndNext\"></A>\nint <I></I>\n<B>DddmpPrintBddAndNext</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: Array of BDDs to be displayed</i>\n  int  <b>rootN</b> <i>IN: Number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Prints debug information for an array of BDDs on the screen\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpReadCnfClauses\"></A>\nstatic int <I></I>\n<B>DddmpReadCnfClauses</B>(\n  Dddmp_Hdr_t * <b>Hdr</b>, <i>IN: file header</i>\n  int *** <b>cnfTable</b>, <i>OUT: CNF table for clauses</i>\n  FILE * <b>fp</b> <i>IN: source file</i>\n)\n</pre>\n<dd> Read the CNF clauses from the file in the standard DIMACS\n    format. Store all the clauses in an internal structure for \n    future transformation into BDDs.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoadCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoadCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpReadCode\"></A>\nint <I></I>\n<B>DddmpReadCode</B>(\n  FILE * <b>fp</b>, <i>IN: file where to read the code</i>\n  struct binary_dd_code * <b>pcode</b> <i>OUT: the read code</i>\n)\n</pre>\n<dd> Reads a 1 byte node code. See DddmpWriteCode()\n    for code description.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpWriteCode()\">DddmpWriteCode()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpBinary.c\"TARGET=\"ABSTRACT\"><CODE>dddmpBinary.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpReadInt\"></A>\nint <I></I>\n<B>DddmpReadInt</B>(\n  FILE * <b>fp</b>, <i>IN: file where to read the integer</i>\n  int * <b>pid</b> <i>OUT: the read integer</i>\n)\n</pre>\n<dd> Reads an integer coded on a sequence of bytes. See\n    DddmpWriteInt() for format.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpWriteInt()\">DddmpWriteInt()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpBinary.c\"TARGET=\"ABSTRACT\"><CODE>dddmpBinary.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpReadNodeIndexAdd\"></A>\nint <I></I>\n<B>DddmpReadNodeIndexAdd</B>(\n  DdNode * <b>f</b> <i>IN: BDD node</i>\n)\n</pre>\n<dd> Reads the index of a node. LSB is skipped (used as visited\n    flag).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpWriteNodeIndexAdd\">DddmpWriteNodeIndexAdd</a>\n()\n<a href=\"#DddmpSetVisitedAdd\">DddmpSetVisitedAdd</a>\n()\n<a href=\"#DddmpVisitedAdd\">DddmpVisitedAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpReadNodeIndexBdd\"></A>\nint <I></I>\n<B>DddmpReadNodeIndexBdd</B>(\n  DdNode * <b>f</b> <i>IN: BDD node</i>\n)\n</pre>\n<dd> Reads the index of a node. LSB is skipped (used as visited\n    flag).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpWriteNodeIndexBdd\">DddmpWriteNodeIndexBdd</a>\n()\n<a href=\"#DddmpSetVisitedBdd\">DddmpSetVisitedBdd</a>\n()\n<a href=\"#DddmpVisitedBdd\">DddmpVisitedBdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpReadNodeIndexCnf\"></A>\nint <I></I>\n<B>DddmpReadNodeIndexCnf</B>(\n  DdNode * <b>f</b> <i>IN: BDD node</i>\n)\n</pre>\n<dd> Reads the index of a node. LSB is skipped (used as visited\n    flag).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpWriteNodeIndexCnf()\">DddmpWriteNodeIndexCnf()</a>\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n<a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpReadNodeIndexCnf\"></A>\nstatic int <I></I>\n<B>DddmpReadNodeIndexCnf</B>(\n  DdNode * <b>f</b> <i>IN: BDD node</i>\n)\n</pre>\n<dd> Reads the index of a node. LSB is skipped (used as visited\n                flag).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpWriteNodeIndexCnf()\">DddmpWriteNodeIndexCnf()</a>\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n<a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpReadNodeIndex\"></A>\nint <I></I>\n<B>DddmpReadNodeIndex</B>(\n  DdNode * <b>f</b> <i>IN: BDD node</i>\n)\n</pre>\n<dd> Reads the index of a node. LSB is skipped (used as visited\n    flag).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpWriteNodeIndex()\">DddmpWriteNodeIndex()</a>\n<a href=\"#DddmpSetVisited\">DddmpSetVisited</a>\n()\n<a href=\"#DddmpVisited\">DddmpVisited</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpSetVisitedAdd\"></A>\nvoid <I></I>\n<B>DddmpSetVisitedAdd</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as visited)</i>\n)\n</pre>\n<dd> Marks a node as visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedAdd\">DddmpVisitedAdd</a>\n()\n<a href=\"#DddmpClearVisitedAdd\">DddmpClearVisitedAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpSetVisitedBdd\"></A>\nvoid <I></I>\n<B>DddmpSetVisitedBdd</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as visited)</i>\n)\n</pre>\n<dd> Marks a node as visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedBdd\">DddmpVisitedBdd</a>\n()\n<a href=\"#DddmpClearVisitedBdd\">DddmpClearVisitedBdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpSetVisitedCnf\"></A>\nstatic void <I></I>\n<B>DddmpSetVisitedCnf</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as visited)</i>\n)\n</pre>\n<dd> Marks a node as visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n<a href=\"#DddmpClearVisitedCnf\">DddmpClearVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpSetVisitedCnf\"></A>\nvoid <I></I>\n<B>DddmpSetVisitedCnf</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as visited)</i>\n)\n</pre>\n<dd> Marks a node as visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n<a href=\"#DddmpClearVisitedCnf\">DddmpClearVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpSetVisited\"></A>\nvoid <I></I>\n<B>DddmpSetVisited</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be marked (as visited)</i>\n)\n</pre>\n<dd> Marks a node as visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpVisited\">DddmpVisited</a>\n()\n<a href=\"#DddmpClearVisited\">DddmpClearVisited</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpStrArrayDup\"></A>\nchar ** <I></I>\n<B>DddmpStrArrayDup</B>(\n  char ** <b>array</b>, <i>IN: array of strings to be duplicated</i>\n  int  <b>n</b> <i>IN: size of the array</i>\n)\n</pre>\n<dd> Allocates memory and copies source array\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpStrArrayFree\"></A>\nvoid <I></I>\n<B>DddmpStrArrayFree</B>(\n  char ** <b>array</b>, <i>IN: array of strings</i>\n  int  <b>n</b> <i>IN: size of the array</i>\n)\n</pre>\n<dd> Frees memory for strings and the array of pointers\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpStrArrayRead\"></A>\nchar ** <I></I>\n<B>DddmpStrArrayRead</B>(\n  FILE * <b>fp</b>, <i>IN: input file</i>\n  int  <b>n</b> <i>IN: size of the array</i>\n)\n</pre>\n<dd> Allocates memory and inputs source array\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpStrArrayWrite\"></A>\nint <I></I>\n<B>DddmpStrArrayWrite</B>(\n  FILE * <b>fp</b>, <i>IN: output file</i>\n  char ** <b>array</b>, <i>IN: array of strings</i>\n  int  <b>n</b> <i>IN: size of the array</i>\n)\n</pre>\n<dd> Outputs an array of strings to a specified file\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpStrDup\"></A>\nchar * <I></I>\n<B>DddmpStrDup</B>(\n  char * <b>str</b> <i>IN: string to be duplicated</i>\n)\n</pre>\n<dd> Allocates memory and copies source string\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpUnnumberAddNodes\"></A>\nvoid <I></I>\n<B>DddmpUnnumberAddNodes</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>n</b> <i>IN: number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Node indexes are no more needed. Nodes are re-linked in the\n    unique table.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpNumberDdNodeAdd\">DddmpNumberDdNodeAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpUnnumberBddNodes\"></A>\nvoid <I></I>\n<B>DddmpUnnumberBddNodes</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>n</b> <i>IN: number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Node indexes are no more needed. Nodes are re-linked in the\n    unique table.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpNumberBddNode\">DddmpNumberBddNode</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpUnnumberDdNodesCnf\"></A>\nvoid <I></I>\n<B>DddmpUnnumberDdNodesCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>rootN</b> <i>IN: number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Node indexes are no more needed. Nodes are re-linked in the\n    unique table.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpNumberDdNode()\">DddmpNumberDdNode()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpUnnumberDdNodesCnf\"></A>\nvoid <I></I>\n<B>DddmpUnnumberDdNodesCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>rootN</b> <i>IN: number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Node indexes are no more needed. Nodes are re-linked in the\n    unique table.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpNumberDdNode()\">DddmpNumberDdNode()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpUnnumberDdNodes\"></A>\nvoid <I></I>\n<B>DddmpUnnumberDdNodes</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs</i>\n  int  <b>n</b> <i>IN: number of BDD roots in the array of BDDs</i>\n)\n</pre>\n<dd> Node indexes are no more needed. Nodes are re-linked in the\n    unique table.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpNumberDdNode()\">DddmpNumberDdNode()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpVisitedAdd\"></A>\nint <I></I>\n<B>DddmpVisitedAdd</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be tested</i>\n)\n</pre>\n<dd> Returns true if node is visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpSetVisitedAdd\">DddmpSetVisitedAdd</a>\n()\n<a href=\"#DddmpClearVisitedAdd\">DddmpClearVisitedAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpVisitedBdd\"></A>\nint <I></I>\n<B>DddmpVisitedBdd</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be tested</i>\n)\n</pre>\n<dd> Returns true if node is visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpSetVisitedBdd\">DddmpSetVisitedBdd</a>\n()\n<a href=\"#DddmpClearVisitedBdd\">DddmpClearVisitedBdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpVisitedCnf\"></A>\nint <I></I>\n<B>DddmpVisitedCnf</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be tested</i>\n)\n</pre>\n<dd> Returns true if node is visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n<a href=\"#DddmpClearVisitedCnf\">DddmpClearVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpVisitedCnf\"></A>\nstatic int <I></I>\n<B>DddmpVisitedCnf</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be tested</i>\n)\n</pre>\n<dd> Returns true if node is visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n<a href=\"#DddmpClearVisitedCnf\">DddmpClearVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpVisited\"></A>\nint <I></I>\n<B>DddmpVisited</B>(\n  DdNode * <b>f</b> <i>IN: BDD node to be tested</i>\n)\n</pre>\n<dd> Returns true if node is visited\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpSetVisited\">DddmpSetVisited</a>\n()\n<a href=\"#DddmpClearVisited\">DddmpClearVisited</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteCode\"></A>\nint <I></I>\n<B>DddmpWriteCode</B>(\n  FILE * <b>fp</b>, <i>IN: file where to write the code</i>\n  struct binary_dd_code  <b>code</b> <i>IN: the code to be written</i>\n)\n</pre>\n<dd> outputs a 1 byte node code using the following format:\n     <pre>\n     Unused      : 1 bit;\n     V           : 2 bits;     (variable code)\n     T           : 2 bits;     (Then code)\n     Ecompl      : 1 bit;      (Else complemented)\n     E           : 2 bits;     (Else code)\n    </pre>\n    Ecompl is set with complemented edges.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadCode()\">DddmpReadCode()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpBinary.c\"TARGET=\"ABSTRACT\"><CODE>dddmpBinary.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteInt\"></A>\nint <I></I>\n<B>DddmpWriteInt</B>(\n  FILE * <b>fp</b>, <i>IN: file where to write the integer</i>\n  int  <b>id</b> <i>IN: integer to be written</i>\n)\n</pre>\n<dd> Writes an integer as a sequence of bytes (MSByte first).\n    For each byte 7 bits are used for data and one (LSBit) as link \n    with a further byte (LSB = 1 means one more byte).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadInt()\">DddmpReadInt()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpBinary.c\"TARGET=\"ABSTRACT\"><CODE>dddmpBinary.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteNodeIndexAdd\"></A>\nvoid <I></I>\n<B>DddmpWriteNodeIndexAdd</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node</i>\n  int  <b>id</b> <i>IN: index to be written</i>\n)\n</pre>\n<dd> The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadNodeIndexAdd\">DddmpReadNodeIndexAdd</a>\n()\n<a href=\"#DddmpSetVisitedAdd\">DddmpSetVisitedAdd</a>\n()\n<a href=\"#DddmpVisitedAdd\">DddmpVisitedAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteNodeIndexBdd\"></A>\nvoid <I></I>\n<B>DddmpWriteNodeIndexBdd</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node</i>\n  int  <b>id</b> <i>IN: index to be written</i>\n)\n</pre>\n<dd> The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadNodeIndexBdd()\">DddmpReadNodeIndexBdd()</a>\n<a href=\"#DddmpSetVisitedBdd\">DddmpSetVisitedBdd</a>\n()\n<a href=\"#DddmpVisitedBdd\">DddmpVisitedBdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteNodeIndexCnfBis\"></A>\nint <I></I>\n<B>DddmpWriteNodeIndexCnfBis</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node</i>\n  int  <b>id</b> <i>IN: index to be written</i>\n)\n</pre>\n<dd> The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadNodeIndexCnf()\">DddmpReadNodeIndexCnf()</a>\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n<a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteNodeIndexCnfWithTerminalCheck\"></A>\nstatic int <I></I>\n<B>DddmpWriteNodeIndexCnfWithTerminalCheck</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node</i>\n  int * <b>cnfIds</b>, <i>IN: possible source for the index to be written</i>\n  int  <b>id</b> <i>IN: possible source for the index to be written</i>\n)\n</pre>\n<dd> The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals. The index corresponds to \n    the BDD node variable if both the node's children are a \n    constant node, otherwise a new CNF variable is used.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadNodeIndexCnf()\">DddmpReadNodeIndexCnf()</a>\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n<a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteNodeIndexCnf\"></A>\nint <I></I>\n<B>DddmpWriteNodeIndexCnf</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node</i>\n  int  <b>id</b> <i>IN: index to be written</i>\n)\n</pre>\n<dd> The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadNodeIndexCnf()\">DddmpReadNodeIndexCnf()</a>\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n<a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteNodeIndexCnf\"></A>\nstatic int <I></I>\n<B>DddmpWriteNodeIndexCnf</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node</i>\n  int * <b>cnfIds</b>, <i>IN: possible source for the index to be written</i>\n  int  <b>id</b> <i>IN: possible source for the index to be written</i>\n)\n</pre>\n<dd> The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals. The index corresponds to \n    the BDD node variable if both the node's children are a \n    constant node, otherwise a new CNF variable is used.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadNodeIndexCnf()\">DddmpReadNodeIndexCnf()</a>\n<a href=\"#DddmpSetVisitedCnf\">DddmpSetVisitedCnf</a>\n()\n<a href=\"#DddmpVisitedCnf\">DddmpVisitedCnf</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"DddmpWriteNodeIndex\"></A>\nvoid <I></I>\n<B>DddmpWriteNodeIndex</B>(\n  DdNode * <b>f</b>, <i>IN: BDD node</i>\n  int  <b>id</b> <i>IN: index to be written</i>\n)\n</pre>\n<dd> The index of the node is written in the \"next\" field of\n    a DdNode struct. LSB is not used (set to 0). It is used as \n    \"visited\" flag in DD traversals.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#DddmpReadNodeIndex()\">DddmpReadNodeIndex()</a>\n<a href=\"#DddmpSetVisited\">DddmpSetVisited</a>\n()\n<a href=\"#DddmpVisited\">DddmpVisited</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_Bin2Text\"></A>\nint <I></I>\n<B>Dddmp_Bin2Text</B>(\n  char * <b>filein</b>, <i>IN: name of binary file</i>\n  char * <b>fileout</b> <i>IN: name of ASCII file</i>\n)\n</pre>\n<dd> Converts from binary to ASCII format. A BDD array is loaded and\n    and stored to the target file.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_Text2Bin()\">Dddmp_Text2Bin()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpConvert.c\"TARGET=\"ABSTRACT\"><CODE>dddmpConvert.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_Text2Bin\"></A>\nint <I></I>\n<B>Dddmp_Text2Bin</B>(\n  char * <b>filein</b>, <i>IN: name of ASCII file</i>\n  char * <b>fileout</b> <i>IN: name of binary file</i>\n)\n</pre>\n<dd> Converts from ASCII to binary format. A BDD array is loaded and\n    and stored to the target file.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_Bin2Text()\">Dddmp_Bin2Text()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpConvert.c\"TARGET=\"ABSTRACT\"><CODE>dddmpConvert.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddAddArrayLoad\"></A>\nint <I></I>\n<B>Dddmp_cuddAddArrayLoad</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_RootMatchType  <b>rootMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>rootmatchnames</b>, <i>IN: sorted names for loaded roots</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by ids</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by ids</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids, by ids</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>pproots</b> <i>OUT: array of returned BDD roots</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument ADDs. See \n    BDD load functions for detailed explanation.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoad.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoad.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddAddArrayStore\"></A>\nint <I></I>\n<B>Dddmp_cuddAddArrayStore</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: DD name (or NULL)</i>\n  int  <b>nRoots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of ADD roots to be stored</i>\n  char ** <b>rootnames</b>, <i>IN: array of root names (or NULL)</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var IDs</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument array of ADDs to file. Dumping is\n    either in text or binary form. see the corresponding BDD dump \n    function for further details.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddAddStore\">Dddmp_cuddAddStore</a>\n<a href=\"#Dddmp_cuddAddLoad\">Dddmp_cuddAddLoad</a>\n<a href=\"#Dddmp_cuddAddArrayLoad\">Dddmp_cuddAddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddAddLoad\"></A>\nDdNode * <I></I>\n<B>Dddmp_cuddAddLoad</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: Manager</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names by IDs</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids by IDs</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids by IDs</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument ADD.\n    Dddmp_cuddAddArrayLoad is used through a dummy array.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddAddStore\">Dddmp_cuddAddStore</a>\n<a href=\"#Dddmp_cuddAddArrayLoad\">Dddmp_cuddAddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoad.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoad.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddAddStore\"></A>\nint <I></I>\n<B>Dddmp_cuddAddStore</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: DD name (or NULL)</i>\n  DdNode * <b>f</b>, <i>IN: ADD root to be stored</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var ids</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument ADD to file. Dumping is done through\n    Dddmp_cuddAddArrayStore, And a dummy array of 1 ADD root is\n    used for this purpose.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique hash. They are \n    re-linked after the store operation in a modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddAddLoad\">Dddmp_cuddAddLoad</a>\n<a href=\"#Dddmp_cuddAddArrayLoad\">Dddmp_cuddAddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayLoadCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayLoadCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_RootMatchType  <b>rootmatchmode</b>, <i>IN: storing mode selector</i>\n  char ** <b>rootmatchnames</b>, <i>IN: sorted names for loaded roots</i>\n  Dddmp_VarMatchType  <b>varmatchmode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by IDs</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by IDs</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids, by IDs</i>\n  int  <b>mode</b>, <i>IN: computation Mode</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>rootsPtrPtr</b>, <i>OUT: array of returned BDD roots</i>\n  int * <b>nRoots</b> <i>OUT: number of BDDs returned</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDD in a\n    CNF formula.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoadCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoadCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayLoad\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayLoad</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_RootMatchType  <b>rootMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>rootmatchnames</b>, <i>IN: sorted names for loaded roots</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by ids</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by ids</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids, by ids</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>pproots</b> <i>OUT: array of returned BDD roots</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDDs. The header is\n    common to both text and binary mode. The node list is either \n    in text or binary format. A dynamic vector of DD pointers \n    is allocated to support conversion from DD indexes to pointers.\n    Several criteria are supported for variable match between file\n    and dd manager. Several changes/permutations/compositions are allowed\n    for variables while loading DDs. Variable of the dd manager are allowed \n    to match with variables on file on ids, permids, varnames, \n    varauxids; also direct composition between ids and \n    composeids is supported. More in detail:\n    <ol>\n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    allows the loading of a DD keeping variable IDs unchanged\n    (regardless of the variable ordering of the reading manager); this\n    is useful, for example, when swapping DDs to file and restoring them\n    later from file, after possible variable reordering activations.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHPERMIDS <p>\n    is used to allow variable match according to the position in the\n    ordering.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHNAMES <p>\n    requires a non NULL varmatchnames parameter; this is a vector of\n    strings in one-to-one correspondence with variable IDs of the\n    reading manager. Variables in the DD file read are matched with\n    manager variables according to their name (a non NULL varnames\n    parameter was required while storing the DD file).\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    has a meaning similar to DDDMP_VAR_MATCHNAMES, but integer auxiliary\n    IDs are used instead of strings; the additional non NULL\n    varmatchauxids parameter is needed.\n    \n    <li> varMatchMode=DDDMP_VAR_COMPOSEIDS <p>\n    uses the additional varcomposeids parameter is used as array of\n    variable ids to be composed with ids stored in file.\n    </ol>\n    \n    In the present implementation, the array varnames (3), varauxids (4)\n    and composeids (5) need to have one entry for each variable in the \n    DD manager (NULL pointers are allowed for unused variables\n    in varnames). Hence variables need to be already present in the \n    manager. All arrays are sorted according to IDs.\n\n    All the loaded BDDs are referenced before returning them.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoad.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoad.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStoreBlif\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStoreBlif</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nroots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: array of variable names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: array of root names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStoreBLif.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStorePrefix\">Dddmp_cuddBddArrayStorePrefix</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStoreCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStoreCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  int  <b>rootN</b>, <i>IN: # output BDD roots to be stored</i>\n  Dddmp_DecompCnfStoreType  <b>mode</b>, <i>IN: format selection</i>\n  int  <b>noHeader</b>, <i>IN: do not store header iff 1</i>\n  char ** <b>varNames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>bddIds</b>, <i>IN: array of converted var IDs</i>\n  int * <b>bddAuxIds</b>, <i>IN: array of BDD node Auxiliary Ids</i>\n  int * <b>cnfIds</b>, <i>IN: array of converted var IDs</i>\n  int  <b>idInitial</b>, <i>IN: starting id for cutting variables</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # Incoming Edges</i>\n  int  <b>pathLengthTh</b>, <i>IN: Max Path Length</i>\n  char * <b>fname</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: pointer to the store file</i>\n  int * <b>clauseNPtr</b>, <i>OUT: number of clause stored</i>\n  int * <b>varNewNPtr</b> <i>OUT: number of new variable created</i>\n)\n</pre>\n<dd> Dumps the argument array of BDDs to file.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n    Three methods are allowed:\n    * NodeByNode method: Insert a cut-point for each BDD node (but the\n                         terminal nodes)\n    * MaxtermByMaxterm method: Insert no cut-points, i.e. the off-set of\n                               trhe function is stored\n    * Best method: Tradeoff between the previous two methods.\n      Auxiliary variables, i.e., cut points are inserted following these\n      criterias:\n      * edgeInTh\n        indicates the maximum number of incoming edges up to which\n        no cut point (auxiliary variable) is inserted.\n        If edgeInTh:\n        * is equal to -1 no cut point due to incoming edges are inserted\n          (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node with a single\n          incoming edge, i.e., each node, (NodeByNode method).\n\t* is equal to n a cut point is inserted for each node with (n+1)\n          incoming edges.\n      * pathLengthTh\n        indicates the maximum length path up to which no cut points\n        (auxiliary variable) is inserted.\n        If the path length between two nodes exceeds this value, a cut point\n        is inserted.\n        If pathLengthTh:\n        * is equal to -1 no cut point due path length are inserted\n          (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node (NodeByNode\n          method).\n\t* is equal to n a cut point is inserted on path whose length is\n          equal to (n+1).\n        Notice that the maximum number of literals in a clause is equal\n        to (pathLengthTh + 2), i.e., for each path we have to keep into\n        account a CNF variable for each node plus 2 added variables for\n        the bottom and top-path cut points.\n    The stored file can contain a file header or not depending on the\n    noHeader parameter (IFF 0, usual setting, the header is usually stored.\n    This option can be useful in storing multiple BDDs, as separate BDDs,\n    on the same file leaving the opening of the file to the caller.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStorePrefix\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStorePrefix</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nroots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: array of variable names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: array of root names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStoreSmv\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStoreSmv</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nroots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: array of variable names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: array of root names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStore\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStore</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: dd name (or NULL)</i>\n  int  <b>nRoots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  char ** <b>rootnames</b>, <i>IN: array of root names (or NULL)</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var IDs</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument array of BDDs to file. Dumping is either \n    in text or binary form.  BDDs are stored to the fp (already \n    open) file if not NULL. Otherwise the file whose name is \n    fname is opened in write mode. The header has the same format \n    for both textual and binary dump. Names are allowed for input \n    variables (vnames) and for represented functions (rnames). \n    For sake of generality and because of dynamic variable \n    ordering both variable IDs and permuted IDs are included. \n    New IDs are also supported (auxids). Variables are identified \n    with incremental numbers. according with their positiom in \n    the support set. In text mode, an extra info may be added, \n    chosen among the following options: name, ID, PermID, or an \n    auxiliary id. Since conversion from DD pointers to integers \n    is required, DD nodes are temporarily removed from the unique\n    hash table. This allows the use of the next field to store \n    node IDs.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n<a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddDisplayBinary\"></A>\nint <I></I>\n<B>Dddmp_cuddBddDisplayBinary</B>(\n  char * <b>fileIn</b>, <i>IN: name of binary file</i>\n  char * <b>fileOut</b> <i>IN: name of text file</i>\n)\n</pre>\n<dd> Display a binary dump file in a text file\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n<a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDbg.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDbg.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddLoadCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddBddLoadCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_VarMatchType  <b>varmatchmode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by IDs</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by IDs</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids accessed, by IDs</i>\n  int  <b>mode</b>, <i>IN: computation mode</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>rootsPtrPtr</b>, <i>OUT: array of returned BDD roots</i>\n  int * <b>nRoots</b> <i>OUT: number of BDDs returned</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDD in a\n    CNF formula.\n    Dddmp_cuddBddArrayLoadCnf is used through a dummy array.\n    The results is returned in different formats depending on the \n    mode selection:\n      IFF mode == 0 Return the Clauses without Conjunction\n      IFF mode == 1 Return the sets of BDDs without Quantification\n      IFF mode == 2 Return the sets of BDDs AFTER Existential Quantification\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoadCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoadCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddLoad\"></A>\nDdNode * <I></I>\n<B>Dddmp_cuddBddLoad</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names - by IDs</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids - by IDs</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids accessed - by IDs</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDD.\n    Dddmp_cuddBddArrayLoad is used through a dummy array (see this\n    function's description for more details).\n    Mode, the requested input file format, is checked against \n    the file format.\n    The loaded BDDs is referenced before returning it.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoad.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoad.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStoreBlif\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStoreBlif</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nRoots</b>, <i>IN: Number of BDD roots</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: Array of variable names</i>\n  char ** <b>outputNames</b>, <i>IN: Array of root names</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fileName</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStoreBlif.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStorePrefix\">Dddmp_cuddBddStorePrefix</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStoreCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStoreCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  Dddmp_DecompCnfStoreType  <b>mode</b>, <i>IN: format selection</i>\n  int  <b>noHeader</b>, <i>IN: do not store header iff 1</i>\n  char ** <b>varNames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>bddIds</b>, <i>IN: array of var ids</i>\n  int * <b>bddAuxIds</b>, <i>IN: array of BDD node Auxiliary Ids</i>\n  int * <b>cnfIds</b>, <i>IN: array of CNF var ids</i>\n  int  <b>idInitial</b>, <i>IN: starting id for cutting variables</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # Incoming Edges</i>\n  int  <b>pathLengthTh</b>, <i>IN: Max Path Length</i>\n  char * <b>fname</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: pointer to the store file</i>\n  int * <b>clauseNPtr</b>, <i>OUT: number of clause stored</i>\n  int * <b>varNewNPtr</b> <i>OUT: number of new variable created</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    This task is performed by calling the function\n    Dddmp_cuddBddArrayStoreCnf.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique hash. They are\n    re-linked after the store operation in a modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStoreCnf\">Dddmp_cuddBddArrayStoreCnf</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStorePrefix\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStorePrefix</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nRoots</b>, <i>IN: Number of BDD roots</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: Array of variable names</i>\n  char ** <b>outputNames</b>, <i>IN: Array of root names</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fileName</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStoreSmv\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStoreSmv</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nRoots</b>, <i>IN: Number of BDD roots</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: Array of variable names</i>\n  char ** <b>outputNames</b>, <i>IN: Array of root names</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fileName</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreMisc.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreMisc.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStore\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStore</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: DD name (or NULL)</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var ids</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file. Dumping is done through\n    Dddmp_cuddBddArrayStore. A dummy array of 1 BDD root is\n    used for this purpose.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique hash. They are\n    re-linked after the store operation in a modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddHeaderLoadCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddHeaderLoadCnf</B>(\n  int * <b>nVars</b>, <i>OUT: number of DD variables</i>\n  int * <b>nsuppvars</b>, <i>OUT: number of support variables</i>\n  char *** <b>suppVarNames</b>, <i>OUT: array of support variable names</i>\n  char *** <b>orderedVarNames</b>, <i>OUT: array of variable names</i>\n  int ** <b>varIds</b>, <i>OUT: array of variable ids</i>\n  int ** <b>varComposeIds</b>, <i>OUT: array of permids ids</i>\n  int ** <b>varAuxIds</b>, <i>OUT: array of variable aux ids</i>\n  int * <b>nRoots</b>, <i>OUT: number of root in the file</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads the header of a dump file representing the argument BDDs. \n    Returns main information regarding DD type stored in the file,\n    the variable ordering used, the number of variables, etc.\n    It reads only the header of the file NOT the BDD/ADD section.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoadCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoadCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddHeaderLoad\"></A>\nint <I></I>\n<B>Dddmp_cuddHeaderLoad</B>(\n  Dddmp_DecompType * <b>ddType</b>, <i>OUT: selects the proper decomp type</i>\n  int * <b>nVars</b>, <i>OUT: number of DD variables</i>\n  int * <b>nsuppvars</b>, <i>OUT: number of support variables</i>\n  char *** <b>suppVarNames</b>, <i>OUT: array of support variable names</i>\n  char *** <b>orderedVarNames</b>, <i>OUT: array of variable names</i>\n  int ** <b>varIds</b>, <i>OUT: array of variable ids</i>\n  int ** <b>varComposeIds</b>, <i>OUT: array of permids ids</i>\n  int ** <b>varAuxIds</b>, <i>OUT: array of variable aux ids</i>\n  int * <b>nRoots</b>, <i>OUT: number of root in the file</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads the header of a dump file representing the argument BDDs.\n    Returns main information regarding DD type stored in the file,\n    the variable ordering used, the number of variables, etc.\n    It reads only the header of the file NOT the BDD/ADD section.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpLoad.c\"TARGET=\"ABSTRACT\"><CODE>dddmpLoad.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"FindVarname\"></A>\nint <I></I>\n<B>FindVarname</B>(\n  char * <b>name</b>, <i>IN: name to look for</i>\n  char ** <b>array</b>, <i>IN: search array</i>\n  int  <b>n</b> <i>IN: size of the array</i>\n)\n</pre>\n<dd> Binary search of a name within a sorted array of strings.\n    Used when matching names of variables.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NodeBinaryStoreBdd\"></A>\nstatic int <I></I>\n<B>NodeBinaryStoreBdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b>, <i>IN: DD node to be stored</i>\n  int  <b>mode</b>, <i>IN: store mode</i>\n  int * <b>supportids</b>, <i>IN: internal ids for variables</i>\n  char ** <b>varnames</b>, <i>IN: names of variables: to be stored with nodes</i>\n  int * <b>outids</b>, <i>IN: output ids for variables</i>\n  FILE * <b>fp</b>, <i>IN: store file</i>\n  int  <b>idf</b>, <i>IN: index of the node</i>\n  int  <b>vf</b>, <i>IN: variable of the node</i>\n  int  <b>idT</b>, <i>IN: index of the Then node</i>\n  int  <b>idE</b>, <i>IN: index of the Else node</i>\n  int  <b>vT</b>, <i>IN: variable of the Then node</i>\n  int  <b>vE</b>, <i>IN: variable of the Else node</i>\n  DdNode * <b>T</b>, <i>IN: Then node</i>\n  DdNode * <b>E</b> <i>IN: Else node</i>\n)\n</pre>\n<dd> Store 1 0 0 for the terminal node.\n    Store id, left child pointer, right pointer for all the other nodes.\n    Store every information as coded binary values.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#NodeTextStoreBdd\">NodeTextStoreBdd</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NodeStoreRecurAdd\"></A>\nstatic int <I></I>\n<B>NodeStoreRecurAdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b>, <i>IN: DD node to be stored</i>\n  int  <b>mode</b>, <i>IN: store mode</i>\n  int * <b>supportids</b>, <i>IN: internal ids for variables</i>\n  char ** <b>varnames</b>, <i>IN: names of variables: to be stored with nodes</i>\n  int * <b>outids</b>, <i>IN: output ids for variables</i>\n  FILE * <b>fp</b> <i>IN: store file</i>\n)\n</pre>\n<dd> Stores a node to file in either test or binary mode.<l>\n    In text mode a node is represented (on a text line basis) as\n    <UL>\n    <LI> node-index [var-extrainfo] var-index Then-index Else-index\n    </UL>\n    \n    where all indexes are integer numbers and var-extrainfo \n    (optional redundant field) is either an integer or a string \n    (variable name). Node-index is redundant (due to the node \n    ordering) but we keep it for readability.<p>\n    \n    In binary mode nodes are represented as a sequence of bytes,\n    representing var-index, Then-index, and Else-index in an \n    optimized way. Only the first byte (code) is mandatory. \n    Integer indexes are represented in absolute or relative mode, \n    where relative means offset wrt. a Then/Else node info. \n    Suppose Var(NodeId), Then(NodeId) and Else(NodeId) represent \n    infos about a given node.<p>\n    \n    The generic \"NodeId\" node is stored as \n\n    <UL>\n    <LI> code-byte\n    <LI> [var-info]\n    <LI> [Then-info]\n    <LI> [Else-info]\n    </UL>\n\n    where code-byte contains bit fields\n\n    <UL>\n    <LI>Unused  : 1 bit\n    <LI>Variable: 2 bits, one of the following codes\n    <UL>\n    <LI>DDDMP_ABSOLUTE_ID   var-info = Var(NodeId) follows\n    <LI>DDDMP_RELATIVE_ID   Var(NodeId) is represented in relative form as\n        var-info = Min(Var(Then(NodeId)),Var(Else(NodeId))) -Var(NodeId)\n    <LI>DDDMP_RELATIVE_1    No var-info follows, because\n        Var(NodeId) = Min(Var(Then(NodeId)),Var(Else(NodeId)))-1\n    <LI>DDDMP_TERMINAL      Node is a terminal, no var info required\n    </UL>\n    <LI>T       : 2 bits, with codes similar to V\n    <UL>\n    <LI>DDDMP_ABSOLUTE_ID   Then-info = Then(NodeId) follows\n    <LI>DDDMP_RELATIVE_ID   Then(NodeId) is represented in relative form as\n          Then-info = Nodeid-Then(NodeId)\n    <LI>DDDMP_RELATIVE_1    No info on Then(NodeId) follows, because\n          Then(NodeId) = NodeId-1\n    <LI>DDDMP_TERMINAL Then Node is a terminal, no info required (for BDDs)\n    </UL>\n    <LI>Ecompl  : 1 bit, if 1 means complemented edge\n    <LI>E       : 2 bits, with codes and meanings as for the Then edge\n    </UL>\n    var-info, Then-info, Else-info (if required) are represented as unsigned \n    integer values on a sufficient set of bytes (MSByte first).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NodeStoreRecurBdd\"></A>\nstatic int <I></I>\n<B>NodeStoreRecurBdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b>, <i>IN: DD node to be stored</i>\n  int  <b>mode</b>, <i>IN: store mode</i>\n  int * <b>supportids</b>, <i>IN: internal ids for variables</i>\n  char ** <b>varnames</b>, <i>IN: names of variables: to be stored with nodes</i>\n  int * <b>outids</b>, <i>IN: output ids for variables</i>\n  FILE * <b>fp</b> <i>IN: store file</i>\n)\n</pre>\n<dd> Stores a node to file in either test or binary mode.<l>\n    In text mode a node is represented (on a text line basis) as\n    <UL>\n    <LI> node-index [var-extrainfo] var-index Then-index Else-index\n    </UL>\n    \n    where all indexes are integer numbers and var-extrainfo \n    (optional redundant field) is either an integer or a string \n    (variable name). Node-index is redundant (due to the node \n    ordering) but we keep it for readability.<p>\n    \n    In binary mode nodes are represented as a sequence of bytes,\n    representing var-index, Then-index, and Else-index in an \n    optimized way. Only the first byte (code) is mandatory. \n    Integer indexes are represented in absolute or relative mode, \n    where relative means offset wrt. a Then/Else node info. \n    Suppose Var(NodeId), Then(NodeId) and Else(NodeId) represent \n    infos about a given node.<p>\n    \n    The generic \"NodeId\" node is stored as \n\n    <UL>\n    <LI> code-byte\n    <LI> [var-info]\n    <LI> [Then-info]\n    <LI> [Else-info]\n    </UL>\n\n    where code-byte contains bit fields\n\n    <UL>\n    <LI>Unused  : 1 bit\n    <LI>Variable: 2 bits, one of the following codes\n    <UL>\n    <LI>DDDMP_ABSOLUTE_ID   var-info = Var(NodeId) follows\n    <LI>DDDMP_RELATIVE_ID   Var(NodeId) is represented in relative form as\n        var-info = Min(Var(Then(NodeId)),Var(Else(NodeId))) -Var(NodeId)\n    <LI>DDDMP_RELATIVE_1    No var-info follows, because\n        Var(NodeId) = Min(Var(Then(NodeId)),Var(Else(NodeId)))-1\n    <LI>DDDMP_TERMINAL      Node is a terminal, no var info required\n    </UL>\n    <LI>T       : 2 bits, with codes similar to V\n    <UL>\n    <LI>DDDMP_ABSOLUTE_ID   Then-info = Then(NodeId) follows\n    <LI>DDDMP_RELATIVE_ID   Then(NodeId) is represented in relative form as\n          Then-info = Nodeid-Then(NodeId)\n    <LI>DDDMP_RELATIVE_1    No info on Then(NodeId) follows, because\n          Then(NodeId) = NodeId-1\n    <LI>DDDMP_TERMINAL Then Node is a terminal, no info required (for BDDs)\n    </UL>\n    <LI>Ecompl  : 1 bit, if 1 means complemented edge\n    <LI>E       : 2 bits, with codes and meanings as for the Then edge\n    </UL>\n    var-info, Then-info, Else-info (if required) are represented as unsigned \n    integer values on a sufficient set of bytes (MSByte first).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NodeTextStoreAdd\"></A>\nstatic int <I></I>\n<B>NodeTextStoreAdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b>, <i>IN: DD node to be stored</i>\n  int  <b>mode</b>, <i>IN: store mode</i>\n  int * <b>supportids</b>, <i>IN: internal ids for variables</i>\n  char ** <b>varnames</b>, <i>IN: names of variables: to be stored with nodes</i>\n  int * <b>outids</b>, <i>IN: output ids for variables</i>\n  FILE * <b>fp</b>, <i>IN: Store file</i>\n  int  <b>idf</b>, <i>IN: index of the current node</i>\n  int  <b>vf</b>, <i>IN: variable of the current node</i>\n  int  <b>idT</b>, <i>IN: index of the Then node</i>\n  int  <b>idE</b> <i>IN: index of the Else node</i>\n)\n</pre>\n<dd> Store 1 0 0 for the terminal node.\n    Store id, left child pointer, right pointer for all the other nodes.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#NodeBinaryStore\">NodeBinaryStore</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NodeTextStoreBdd\"></A>\nstatic int <I></I>\n<B>NodeTextStoreBdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b>, <i>IN: DD node to be stored</i>\n  int  <b>mode</b>, <i>IN: store mode</i>\n  int * <b>supportids</b>, <i>IN: internal ids for variables</i>\n  char ** <b>varnames</b>, <i>IN: names of variables: to be stored with nodes</i>\n  int * <b>outids</b>, <i>IN: output ids for variables</i>\n  FILE * <b>fp</b>, <i>IN: Store file</i>\n  int  <b>idf</b>, <i>IN: index of the current node</i>\n  int  <b>vf</b>, <i>IN: variable of the current node</i>\n  int  <b>idT</b>, <i>IN: index of the Then node</i>\n  int  <b>idE</b> <i>IN: index of the Else node</i>\n)\n</pre>\n<dd> Store 1 0 0 for the terminal node.\n    Store id, left child pointer, right pointer for all the other nodes.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#NodeBinaryStoreBdd\">NodeBinaryStoreBdd</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NumberNodeRecurAdd\"></A>\nstatic int <I></I>\n<B>NumberNodeRecurAdd</B>(\n  DdNode * <b>f</b>, <i>IN: root of the BDD to be numbered</i>\n  int  <b>id</b> <i>IN/OUT: index to be assigned to the node</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with inverse polarity, because all nodes\n    were set \"visited\" when removing them from unique.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are reset.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NumberNodeRecurBdd\"></A>\nstatic int <I></I>\n<B>NumberNodeRecurBdd</B>(\n  DdNode * <b>f</b>, <i>IN: root of the BDD to be numbered</i>\n  int  <b>id</b> <i>IN/OUT: index to be assigned to the node</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with inverse polarity, because all nodes\n    were set \"visited\" when removing them from unique.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are reset.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NumberNodeRecurCnf\"></A>\nstatic int <I></I>\n<B>NumberNodeRecurCnf</B>(\n  DdNode * <b>f</b>, <i>IN: root of the BDD to be numbered</i>\n  int * <b>cnfIds</b>, <i>IN: possible source for numbering</i>\n  int  <b>id</b> <i>IN/OUT: possible source for numbering</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with inverse polarity, because all nodes\n    were set \"visited\" when removing them from unique.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are reset.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NumberNodeRecurCnf\"></A>\nstatic int <I></I>\n<B>NumberNodeRecurCnf</B>(\n  DdNode * <b>f</b>, <i>IN: root of the BDD to be numbered</i>\n  int * <b>cnfIds</b>, <i>IN: possible source for numbering</i>\n  int  <b>id</b> <i>IN/OUT: possible source for numbering</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with inverse polarity, because all nodes\n    were set \"visited\" when removing them from unique.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are reset.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"NumberNodeRecur\"></A>\nstatic int <I></I>\n<B>NumberNodeRecur</B>(\n  DdNode * <b>f</b>, <i>IN: root of the BDD to be numbered</i>\n  int  <b>id</b> <i>IN/OUT: index to be assigned to the node</i>\n)\n</pre>\n<dd> Number nodes recursively in post-order.\n    The \"visited\" flag is used with inverse polarity, because all nodes\n    were set \"visited\" when removing them from unique.\n<p>\n\n<dd> <b>Side Effects</b> \"visited\" flags are reset.\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"QsortStrcmp\"></A>\nint <I></I>\n<B>QsortStrcmp</B>(\n  const void * <b>ps1</b>, <i>IN: pointer to the first string</i>\n  const void * <b>ps2</b> <i>IN: pointer to the second string</i>\n)\n</pre>\n<dd> String compare for qsort\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpUtil.c\"TARGET=\"ABSTRACT\"><CODE>dddmpUtil.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"ReadByteBinary\"></A>\nstatic int <I></I>\n<B>ReadByteBinary</B>(\n  FILE * <b>fp</b>, <i>IN: file where to read the byte</i>\n  unsigned char * <b>cp</b> <i>OUT: the read byte</i>\n)\n</pre>\n<dd> inputs a byte to file fp. 0x00 has been used as escape character\n    to filter <CR>, <LF> and <ctrl-Z>. This is done for\n    compatibility between unix and dos/windows systems.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#WriteByteBinary()\">WriteByteBinary()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpBinary.c\"TARGET=\"ABSTRACT\"><CODE>dddmpBinary.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RemoveFromUniqueRecurAdd\"></A>\nstatic void <I></I>\n<B>RemoveFromUniqueRecurAdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be extracted</i>\n)\n</pre>\n<dd> Removes a node from the unique table by locating the proper\n    subtable and unlinking the node from it. It recurs on the \n    children of the node. Constants remain untouched.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are left with the \"visited\" flag true.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RestoreInUniqueRecurAdd\">RestoreInUniqueRecurAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RemoveFromUniqueRecurBdd\"></A>\nstatic void <I></I>\n<B>RemoveFromUniqueRecurBdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be extracted</i>\n)\n</pre>\n<dd> Removes a node from the unique table by locating the proper\n    subtable and unlinking the node from it. It recurs on the \n    children of the node. Constants remain untouched.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are left with the \"visited\" flag true.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RestoreInUniqueRecurBdd\">RestoreInUniqueRecurBdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RemoveFromUniqueRecurCnf\"></A>\nstatic void <I></I>\n<B>RemoveFromUniqueRecurCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be extracted</i>\n)\n</pre>\n<dd> Removes a node from the unique table by locating the proper\n    subtable and unlinking the node from it. It recurs on  on the \n    children of the node. Constants remain untouched.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are left with the \"visited\" flag true.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RestoreInUniqueRecurCnf()\">RestoreInUniqueRecurCnf()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RemoveFromUniqueRecurCnf\"></A>\nstatic void <I></I>\n<B>RemoveFromUniqueRecurCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be extracted</i>\n)\n</pre>\n<dd> Removes a node from the unique table by locating the proper\n    subtable and unlinking the node from it. It recurs on son nodes.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are left with the \"visited\" flag true.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RestoreInUniqueRecurCnf()\">RestoreInUniqueRecurCnf()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RemoveFromUniqueRecur\"></A>\nstatic void <I></I>\n<B>RemoveFromUniqueRecur</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be extracted</i>\n)\n</pre>\n<dd> Removes a node from the unique table by locating the proper\n    subtable and unlinking the node from it. It recurs on the \n    children of the node.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are left with the \"visited\" flag true.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RestoreInUniqueRecur()\">RestoreInUniqueRecur()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RestoreInUniqueRecurAdd\"></A>\nstatic void <I></I>\n<B>RestoreInUniqueRecurAdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be restored</i>\n)\n</pre>\n<dd> Restores a node in unique table (recursively)\n<p>\n\n<dd> <b>Side Effects</b> Nodes are not restored in the same order as before removal\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUniqueAdd\">RemoveFromUniqueAdd</a>\n()\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeAdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeAdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RestoreInUniqueRecurBdd\"></A>\nstatic void <I></I>\n<B>RestoreInUniqueRecurBdd</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be restored</i>\n)\n</pre>\n<dd> Restores a node in unique table (recursively)\n<p>\n\n<dd> <b>Side Effects</b> Nodes are not restored in the same order as before removal\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUnique()\">RemoveFromUnique()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RestoreInUniqueRecurCnf\"></A>\nstatic void <I></I>\n<B>RestoreInUniqueRecurCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be restored</i>\n)\n</pre>\n<dd> Restores a node in unique table (recursive)\n<p>\n\n<dd> <b>Side Effects</b> Nodes are not restored in the same order as before removal\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUnique()\">RemoveFromUnique()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RestoreInUniqueRecurCnf\"></A>\nstatic void <I></I>\n<B>RestoreInUniqueRecurCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be restored</i>\n)\n</pre>\n<dd> Restores a node in unique table (recursive)\n<p>\n\n<dd> <b>Side Effects</b> Nodes are not restored in the same order as before removal\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUnique()\">RemoveFromUnique()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpNodeCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpNodeCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"RestoreInUniqueRecur\"></A>\nstatic void <I></I>\n<B>RestoreInUniqueRecur</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b> <i>IN: root of the BDD to be restored</i>\n)\n</pre>\n<dd> Restores a node in unique table (recursively)\n<p>\n\n<dd> <b>Side Effects</b> Nodes are not restored in the same order as before removal\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#RemoveFromUnique()\">RemoveFromUnique()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpDdNodeBdd.c\"TARGET=\"ABSTRACT\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"StoreCnfBestNotSharedRecur\"></A>\nstatic int <I></I>\n<B>StoreCnfBestNotSharedRecur</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>node</b>, <i>IN: BDD to store</i>\n  int  <b>idf</b>, <i>IN: Id to store</i>\n  int * <b>bddIds</b>, <i>IN: BDD identifiers</i>\n  int * <b>cnfIds</b>, <i>IN: corresponding CNF identifiers</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  int * <b>list</b>, <i>IN: temporary array to store cubes</i>\n  int * <b>clauseN</b>, <i>OUT: number of stored clauses</i>\n  int * <b>varMax</b> <i>OUT: maximum identifier of the variables created</i>\n)\n</pre>\n<dd> Performs the recursive step of Print Best on Not Shared\n    sub-BDDs, i.e., print out information for the nodes belonging to\n    BDDs not shared (whose root has just one incoming edge).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"StoreCnfBestSharedRecur\"></A>\nstatic int <I></I>\n<B>StoreCnfBestSharedRecur</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>node</b>, <i>IN: BDD to store</i>\n  int * <b>bddIds</b>, <i>IN: BDD identifiers</i>\n  int * <b>cnfIds</b>, <i>IN: corresponding CNF identifiers</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  int * <b>list</b>, <i>IN: temporary array to store cubes</i>\n  int * <b>clauseN</b>, <i>OUT: number of stored clauses</i>\n  int * <b>varMax</b> <i>OUT: maximum identifier of the variables created</i>\n)\n</pre>\n<dd> Performs the recursive step of Print Best on Not Shared\n    sub-BDDs, i.e., print out information for the nodes belonging to\n    BDDs not shared (whose root has just one incoming edge).\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"StoreCnfBest\"></A>\nstatic int <I></I>\n<B>StoreCnfBest</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs to store</i>\n  int  <b>rootN</b>, <i>IN: number of BDD in the array</i>\n  int * <b>bddIds</b>, <i>IN: BDD identifiers</i>\n  int * <b>cnfIds</b>, <i>IN: corresponding CNF identifiers</i>\n  int  <b>idInitial</b>, <i>IN: initial value for numbering new CNF variables</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  int * <b>varMax</b>, <i>OUT: maximum identifier of the variables created</i>\n  int * <b>clauseN</b>, <i>OUT: number of stored clauses</i>\n  int * <b>rootStartLine</b> <i>OUT: line where root starts</i>\n)\n</pre>\n<dd> Prints a disjoint sum of product cover for the function\n    rooted at node intorducing cutting points whenever necessary.\n    Each product corresponds to a path from node a leaf\n    node different from the logical zero, and different from the\n    background value. Uses the standard output.  Returns 1 if \n    successful, 0 otherwise.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#StoreCnfMaxtermByMaxterm\">StoreCnfMaxtermByMaxterm</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"StoreCnfMaxtermByMaxtermRecur\"></A>\nstatic void <I></I>\n<B>StoreCnfMaxtermByMaxtermRecur</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>node</b>, <i>IN: BDD to store</i>\n  int * <b>bddIds</b>, <i>IN: BDD identifiers</i>\n  int * <b>cnfIds</b>, <i>IN: corresponding CNF identifiers</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  int * <b>list</b>, <i>IN: temporary array to store cubes</i>\n  int * <b>clauseN</b>, <i>OUT: number of stored clauses</i>\n  int * <b>varMax</b> <i>OUT: maximum identifier of the variables created</i>\n)\n</pre>\n<dd> Performs the recursive step of Print Maxterm.\n    Traverse a BDD a print out a cube in CNF format each time a terminal\n    node is reached.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"StoreCnfMaxtermByMaxterm\"></A>\nstatic int <I></I>\n<B>StoreCnfMaxtermByMaxterm</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDDs to store</i>\n  int  <b>rootN</b>, <i>IN: number of BDDs in the array</i>\n  int * <b>bddIds</b>, <i>IN: BDD Identifiers</i>\n  int * <b>cnfIds</b>, <i>IN: corresponding CNF Identifiers</i>\n  int  <b>idInitial</b>, <i>IN: initial value for numbering new CNF variables</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  int * <b>varMax</b>, <i>OUT: maximum identifier of the variables created</i>\n  int * <b>clauseN</b>, <i>OUT: number of stored clauses</i>\n  int * <b>rootStartLine</b> <i>OUT: line where root starts</i>\n)\n</pre>\n<dd> Prints a disjoint sum of product cover for the function\n    rooted at node. Each product corresponds to a path from node a \n    leaf node different from the logical zero, and different from \n    the background value. Uses the standard output.  Returns 1 if \n    successful, 0 otherwise.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#StoreCnfBest\">StoreCnfBest</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"StoreCnfNodeByNodeRecur\"></A>\nstatic int <I></I>\n<B>StoreCnfNodeByNodeRecur</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b>, <i>IN: BDD node to be stored</i>\n  int * <b>bddIds</b>, <i>IN: BDD ids for variables</i>\n  int * <b>cnfIds</b>, <i>IN: CNF ids for variables</i>\n  FILE * <b>fp</b>, <i>IN: store file</i>\n  int * <b>clauseN</b>, <i>OUT: number of clauses written in the CNF file</i>\n  int * <b>varMax</b> <i>OUT: maximum value of id written in the CNF file</i>\n)\n</pre>\n<dd> Performs the recursive step of Dddmp_bddStore.\n    Traverse the BDD and store a CNF formula for each \"terminal\" node.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"StoreCnfNodeByNode\"></A>\nstatic int <I></I>\n<B>StoreCnfNodeByNode</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: BDD array to be stored</i>\n  int  <b>rootN</b>, <i>IN: number of BDDs in the array</i>\n  int * <b>bddIds</b>, <i>IN: BDD ids for variables</i>\n  int * <b>cnfIds</b>, <i>IN: CNF ids for variables</i>\n  FILE * <b>fp</b>, <i>IN: store file</i>\n  int * <b>clauseN</b>, <i>IN/OUT: number of clauses written in the CNF file</i>\n  int * <b>varMax</b>, <i>IN/OUT: maximum value of id written in the CNF file</i>\n  int * <b>rootStartLine</b> <i>OUT: CNF line where root starts</i>\n)\n</pre>\n<dd> Store the BDD as CNF clauses.\n    Use a multiplexer description for each BDD node.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"StoreCnfOneNode\"></A>\nstatic int <I></I>\n<B>StoreCnfOneNode</B>(\n  DdNode * <b>f</b>, <i>IN: node to be stored</i>\n  int  <b>idf</b>, <i>IN: node CNF Index</i>\n  int  <b>vf</b>, <i>IN: node BDD Index</i>\n  int  <b>idT</b>, <i>IN: Then CNF Index with sign = inverted edge</i>\n  int  <b>idE</b>, <i>IN: Else CNF Index with sign = inverted edge</i>\n  FILE * <b>fp</b>, <i>IN: store file</i>\n  int * <b>clauseN</b>, <i>OUT: number of clauses</i>\n  int * <b>varMax</b> <i>OUT: maximun Index of variable stored</i>\n)\n</pre>\n<dd> Store One Single BDD Node translating it as a multiplexer.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"WriteByteBinary\"></A>\nstatic int <I></I>\n<B>WriteByteBinary</B>(\n  FILE * <b>fp</b>, <i>IN: file where to write the byte</i>\n  unsigned char  <b>c</b> <i>IN: the byte to be written</i>\n)\n</pre>\n<dd> outputs a byte to file fp. Uses 0x00 as escape character\n    to filter <CR>, <LF> and <ctrl-Z>.\n    This is done for compatibility between unix and dos/windows systems.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#ReadByteBinary()\">ReadByteBinary()</a>\n</code>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpBinary.c\"TARGET=\"ABSTRACT\"><CODE>dddmpBinary.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"printCubeCnf\"></A>\nstatic int <I></I>\n<B>printCubeCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>node</b>, <i>IN: BDD to store</i>\n  int * <b>cnfIds</b>, <i>IN: CNF identifiers</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  int * <b>list</b>, <i>IN: temporary array to store cubes</i>\n  int * <b>varMax</b> <i>OUT: maximum identifier of the variables created</i>\n)\n</pre>\n<dd> Print One Cube in CNF Format.\n    Return DDDMP_SUCCESS if something is printed out, DDDMP_FAILURE\n    is nothing is printed out.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpStoreCnf.c\"TARGET=\"ABSTRACT\"><CODE>dddmpStoreCnf.c</CODE></A>\n\n<dt><pre>\n<A NAME=\"\"></A>\n <I></I>\n<B></B>(\n   <b></b> <i></i>\n)\n</pre>\n<dd> Checks for Warnings: If expr==1 it prints out the warning\n    on stderr.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmp.h\"TARGET=\"ABSTRACT\"><CODE>dddmp.h</CODE></A>\n\n<dt><pre>\n<A NAME=\"\"></A>\n <I></I>\n<B></B>(\n   <b></b> <i></i>\n)\n</pre>\n<dd> Checks for fatal bugs and go to the label to deal with\n    the error.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmp.h\"TARGET=\"ABSTRACT\"><CODE>dddmp.h</CODE></A>\n\n<dt><pre>\n<A NAME=\"\"></A>\n <I></I>\n<B></B>(\n   <b></b> <i></i>\n)\n</pre>\n<dd> Checks for fatal bugs and return the DDDMP_FAILURE flag.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmp.h\"TARGET=\"ABSTRACT\"><CODE>dddmp.h</CODE></A>\n\n<dt><pre>\n<A NAME=\"\"></A>\n <I></I>\n<B></B>(\n   <b></b> <i></i>\n)\n</pre>\n<dd> Conditional safety assertion. It prints out the file\n    name and line number where the fatal error occurred.\n    Messages are printed out on stderr.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmp.h\"TARGET=\"ABSTRACT\"><CODE>dddmp.h</CODE></A>\n\n<dt><pre>\n<A NAME=\"\"></A>\n <I></I>\n<B></B>(\n   <b></b> <i></i>\n)\n</pre>\n<dd> Memory Allocation Macro for DDDMP\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpInt.h\"TARGET=\"ABSTRACT\"><CODE>dddmpInt.h</CODE></A>\n\n<dt><pre>\n<A NAME=\"\"></A>\n <I></I>\n<B></B>(\n   <b></b> <i></i>\n)\n</pre>\n<dd> Memory Free Macro for DDDMP\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<DD> <B>Defined in </B> <A HREF=\"dddmpAllFile.html#dddmpInt.h\"TARGET=\"ABSTRACT\"><CODE>dddmpInt.h</CODE></A>\n\n\n</DL>\n<HR>\nLast updated on 1040218 17h14\n</BODY></HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpAllFile.html",
    "content": "<HTML>\n<HEAD><TITLE>The dddmp package: files</TITLE></HEAD>\n<BODY>\n\n<DL>\n <DT> <A HREF=\"#dddmp.h\"><CODE>dddmp.h</CODE></A>\n <DD> External header file\n <DT> <A HREF=\"#dddmpInt.h\"><CODE>dddmpInt.h</CODE></A>\n <DD> Internal header file\n <DT> <A HREF=\"#dddmpBinary.c\"><CODE>dddmpBinary.c</CODE></A>\n <DD> Input and output BDD codes and integers from/to file\n <DT> <A HREF=\"#dddmpConvert.c\"><CODE>dddmpConvert.c</CODE></A>\n <DD> Conversion between ASCII and binary formats\n <DT> <A HREF=\"#dddmpDbg.c\"><CODE>dddmpDbg.c</CODE></A>\n <DD> Functions to display BDD files\n <DT> <A HREF=\"#dddmpDdNodeBdd.c\"><CODE>dddmpDdNodeBdd.c</CODE></A>\n <DD> Functions to handle BDD node infos and numbering\n <DT> <A HREF=\"#dddmpDdNodeCnf.c\"><CODE>dddmpDdNodeCnf.c</CODE></A>\n <DD> Functions to handle BDD node infos and numbering\n    while storing a CNF formula from a BDD or an array of BDDs\n <DT> <A HREF=\"#dddmpLoad.c\"><CODE>dddmpLoad.c</CODE></A>\n <DD> Functions to read in bdds to file\n <DT> <A HREF=\"#dddmpLoadCnf.c\"><CODE>dddmpLoadCnf.c</CODE></A>\n <DD> Functions to read in CNF from file as BDDs.\n <DT> <A HREF=\"#dddmpNodeAdd.c\"><CODE>dddmpNodeAdd.c</CODE></A>\n <DD> Functions to handle ADD node infos and numbering\n <DT> <A HREF=\"#dddmpNodeBdd.c\"><CODE>dddmpNodeBdd.c</CODE></A>\n <DD> Functions to handle BDD node infos and numbering\n <DT> <A HREF=\"#dddmpNodeCnf.c\"><CODE>dddmpNodeCnf.c</CODE></A>\n <DD> Functions to handle BDD node infos and numbering\n    while storing a CNF formula from a BDD or an array of BDDs\n <DT> <A HREF=\"#dddmpStoreAdd.c\"><CODE>dddmpStoreAdd.c</CODE></A>\n <DD> Functions to write ADDs to file.\n <DT> <A HREF=\"#dddmpStoreBdd.c\"><CODE>dddmpStoreBdd.c</CODE></A>\n <DD> Functions to write BDDs to file.\n <DT> <A HREF=\"#dddmpStoreCnf.c\"><CODE>dddmpStoreCnf.c</CODE></A>\n <DD> Functions to write out BDDs to file in a CNF format\n <DT> <A HREF=\"#dddmpStoreMisc.c\"><CODE>dddmpStoreMisc.c</CODE></A>\n <DD> Functions to write out bdds to file in prefixed\n    and in Blif form.\n <DT> <A HREF=\"#dddmpUtil.c\"><CODE>dddmpUtil.c</CODE></A>\n <DD> Util Functions for the dddmp package\n</DL><HR>\n<A NAME=\"dddmp.h\"><H1>dddmp.h</H1></A>\nExternal header file <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n <DD> Checks for fatal bugs\n\n <DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n <DD> Checks for Warnings: If expr==1 it prints out the warning\n    on stderr.\n\n <DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n <DD> Checks for fatal bugs and return the DDDMP_FAILURE flag.\n\n <DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n <DD> Checks for fatal bugs and go to the label to deal with\n    the error.\n\n</DL>\n<HR>\n<A NAME=\"dddmpInt.h\"><H1>dddmpInt.h</H1></A>\nInternal header file <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n <DD> Memory Allocation Macro for DDDMP\n\n <DT> <A HREF=\"dddmpAllDet.html#\" TARGET=\"MAIN\"><CODE>()</CODE></A>\n <DD> Memory Free Macro for DDDMP\n\n</DL>\n<HR>\n<A NAME=\"dddmpBinary.c\"><H1>dddmpBinary.c</H1></A>\nInput and output BDD codes and integers from/to file <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nInput and output BDD codes and integers from/to file\n    in binary mode.\n    DD node codes are written as one byte.\n    Integers of any length are written as sequences of \"linked\" bytes.\n    For each byte 7 bits are used for data and one (MSBit) as link with\n    a further byte (MSB = 1 means one more byte).\n    Low level read/write of bytes filter <CR>, <LF> and <ctrl-Z>\n    with escape sequences. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteCode\" TARGET=\"MAIN\"><CODE>DddmpWriteCode()</CODE></A>\n <DD> Writes 1 byte node code\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpReadCode\" TARGET=\"MAIN\"><CODE>DddmpReadCode()</CODE></A>\n <DD> Reads a 1 byte node code\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteInt\" TARGET=\"MAIN\"><CODE>DddmpWriteInt()</CODE></A>\n <DD> Writes a \"packed integer\"\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpReadInt\" TARGET=\"MAIN\"><CODE>DddmpReadInt()</CODE></A>\n <DD> Reads a \"packed integer\"\n\n <DT> <A HREF=\"dddmpAllDet.html#WriteByteBinary\" TARGET=\"MAIN\"><CODE>WriteByteBinary()</CODE></A>\n <DD> Writes a byte to file filtering <CR>, <LF> and <ctrl-Z>\n\n <DT> <A HREF=\"dddmpAllDet.html#ReadByteBinary\" TARGET=\"MAIN\"><CODE>ReadByteBinary()</CODE></A>\n <DD> Reads a byte from file with escaped <CR>, <LF> and <ctrl-Z>\n\n</DL>\n<HR>\n<A NAME=\"dddmpConvert.c\"><H1>dddmpConvert.c</H1></A>\nConversion between ASCII and binary formats <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nConversion between ASCII and binary formats is presently \n    supported by loading a BDD in the source format and storing it \n    in the target one. We plan to introduce ad hoc procedures\n    avoiding explicit BDD node generation. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_Text2Bin\" TARGET=\"MAIN\"><CODE>Dddmp_Text2Bin()</CODE></A>\n <DD> Converts from ASCII to binary format\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_Bin2Text\" TARGET=\"MAIN\"><CODE>Dddmp_Bin2Text()</CODE></A>\n <DD> Converts from binary to ASCII format\n\n</DL>\n<HR>\n<A NAME=\"dddmpDbg.c\"><H1>dddmpDbg.c</H1></A>\nFunctions to display BDD files <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to display BDD files in binary format <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddDisplayBinary\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddDisplayBinary()</CODE></A>\n <DD> Display a binary dump file in a text file\n\n</DL>\n<HR>\n<A NAME=\"dddmpDdNodeBdd.c\"><H1>dddmpDdNodeBdd.c</H1></A>\nFunctions to handle BDD node infos and numbering <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to handle BDD node infos and numbering. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#DddmpNumberDdNodes\" TARGET=\"MAIN\"><CODE>DddmpNumberDdNodes()</CODE></A>\n <DD> Removes nodes from unique table and number them\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberDdNodes\" TARGET=\"MAIN\"><CODE>DddmpUnnumberDdNodes()</CODE></A>\n <DD> Restores nodes in unique table, loosing numbering\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndex\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndex()</CODE></A>\n <DD> Write index to node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndex\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndex()</CODE></A>\n <DD> Reads the index of a node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpVisited\" TARGET=\"MAIN\"><CODE>DddmpVisited()</CODE></A>\n <DD> Returns true if node is visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisited\" TARGET=\"MAIN\"><CODE>DddmpSetVisited()</CODE></A>\n <DD> Marks a node as visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisited\" TARGET=\"MAIN\"><CODE>DddmpClearVisited()</CODE></A>\n <DD> Marks a node as not visited\n\n <DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecur\" TARGET=\"MAIN\"><CODE>NumberNodeRecur()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecur\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecur()</CODE></A>\n <DD> Removes a node from unique table\n\n <DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecur\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecur()</CODE></A>\n <DD> Restores a node in unique table\n\n</DL>\n<HR>\n<A NAME=\"dddmpDdNodeCnf.c\"><H1>dddmpDdNodeCnf.c</H1></A>\nFunctions to handle BDD node infos and numbering\n    while storing a CNF formula from a BDD or an array of BDDs <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to handle BDD node infos and numbering\n    while storing a CNF formula from a BDD or an array of BDDs. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#DddmpNumberDdNodesCnf\" TARGET=\"MAIN\"><CODE>DddmpNumberDdNodesCnf()</CODE></A>\n <DD> Removes nodes from unique table and numbers them\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCountEdgesAndNumber\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCountEdgesAndNumber()</CODE></A>\n <DD> Removes nodes from unique table and numbers each node according\n    to the number of its incoming BDD edges.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberDdNodesCnf\" TARGET=\"MAIN\"><CODE>DddmpUnnumberDdNodesCnf()</CODE></A>\n <DD> Restores nodes in unique table, loosing numbering\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpPrintBddAndNext\" TARGET=\"MAIN\"><CODE>DddmpPrintBddAndNext()</CODE></A>\n <DD> Prints debug information\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexCnfBis\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexCnfBis()</CODE></A>\n <DD> Write index to node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexCnf\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexCnf()</CODE></A>\n <DD> Write index to node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndexCnf\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndexCnf()</CODE></A>\n <DD> Reads the index of a node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedCnfRecur\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedCnfRecur()</CODE></A>\n <DD> Mark ALL nodes as not visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpVisitedCnf()</CODE></A>\n <DD> Returns true if node is visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpSetVisitedCnf()</CODE></A>\n <DD> Marks a node as visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedCnf()</CODE></A>\n <DD> Marks a node as not visited\n\n <DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecurCnf\" TARGET=\"MAIN\"><CODE>NumberNodeRecurCnf()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCheckIncomingAndScanPath\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCheckIncomingAndScanPath()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesNumberEdgesRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesNumberEdgesRecur()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesResetCountRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesResetCountRecur()</CODE></A>\n <DD> Resets counter and visited flag for ALL nodes of a BDD\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCountEdgesRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCountEdgesRecur()</CODE></A>\n <DD> Counts the number of incoming edges for each node of a BDD\n\n <DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecurCnf\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecurCnf()</CODE></A>\n <DD> Removes a node from unique table\n\n <DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecurCnf\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecurCnf()</CODE></A>\n <DD> Restores a node in unique table\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpPrintBddAndNextRecur\" TARGET=\"MAIN\"><CODE>DddmpPrintBddAndNextRecur()</CODE></A>\n <DD> Prints debug info\n\n</DL>\n<HR>\n<A NAME=\"dddmpLoad.c\"><H1>dddmpLoad.c</H1></A>\nFunctions to read in bdds to file <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to read in bdds to file.  BDDs\n    are represended on file either in text or binary format under the\n    following rules.  A file contains a forest of BDDs (a vector of\n    Boolean functions).  BDD nodes are numbered with contiguous numbers,\n    from 1 to NNodes (total number of nodes on a file). 0 is not used to\n    allow negative node indexes for complemented edges.  A file contains\n    a header, including information about variables and roots to BDD\n    functions, followed by the list of nodes.  BDD nodes are listed\n    according to their numbering, and in the present implementation\n    numbering follows a post-order strategy, in such a way that a node\n    is never listed before its Then/Else children. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddLoad()</CODE></A>\n <DD> Reads a dump file representing the argument BDD.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayLoad()</CODE></A>\n <DD> Reads a dump file representing the argument BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddAddLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddAddLoad()</CODE></A>\n <DD> Reads a dump file representing the argument ADD.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddAddArrayLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddAddArrayLoad()</CODE></A>\n <DD> Reads a dump file representing the argument ADDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddHeaderLoad\" TARGET=\"MAIN\"><CODE>Dddmp_cuddHeaderLoad()</CODE></A>\n <DD> Reads the header of a dump file representing the argument BDDs\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayLoad\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayLoad()</CODE></A>\n <DD> Reads a dump file representing the argument BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpBddReadHeader\" TARGET=\"MAIN\"><CODE>DddmpBddReadHeader()</CODE></A>\n <DD> Reads a the header of a dump file representing the\n    argument BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpFreeHeader\" TARGET=\"MAIN\"><CODE>DddmpFreeHeader()</CODE></A>\n <DD> Frees the internal header structure.\n\n</DL>\n<HR>\n<A NAME=\"dddmpLoadCnf.c\"><H1>dddmpLoadCnf.c</H1></A>\nFunctions to read in CNF from file as BDDs. <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to read in CNF from file as BDDs. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddLoadCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddLoadCnf()</CODE></A>\n <DD> Reads a dump file in a CNF format.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayLoadCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayLoadCnf()</CODE></A>\n <DD> Reads a dump file in a CNF format.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddHeaderLoadCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddHeaderLoadCnf()</CODE></A>\n <DD> Reads the header of a dump file representing the argument BDDs\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayLoadCnf\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayLoadCnf()</CODE></A>\n <DD> Reads a dump file representing the argument BDDs in CNF\n     format.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpBddReadHeaderCnf\" TARGET=\"MAIN\"><CODE>DddmpBddReadHeaderCnf()</CODE></A>\n <DD> Reads a the header of a dump file representing the argument \n    BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpFreeHeaderCnf\" TARGET=\"MAIN\"><CODE>DddmpFreeHeaderCnf()</CODE></A>\n <DD> Frees the internal header structure.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpReadCnfClauses\" TARGET=\"MAIN\"><CODE>DddmpReadCnfClauses()</CODE></A>\n <DD> Read the CNF clauses from the file in the standard DIMACS\n    format.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCnfClauses2Bdd\" TARGET=\"MAIN\"><CODE>DddmpCnfClauses2Bdd()</CODE></A>\n <DD> Transforms CNF clauses into BDDs.\n\n</DL>\n<HR>\n<A NAME=\"dddmpNodeAdd.c\"><H1>dddmpNodeAdd.c</H1></A>\nFunctions to handle ADD node infos and numbering <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to handle ADD node infos and numbering. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#DddmpNumberAddNodes\" TARGET=\"MAIN\"><CODE>DddmpNumberAddNodes()</CODE></A>\n <DD> Removes nodes from unique table and number them\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberAddNodes\" TARGET=\"MAIN\"><CODE>DddmpUnnumberAddNodes()</CODE></A>\n <DD> Restores nodes in unique table, loosing numbering\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexAdd\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexAdd()</CODE></A>\n <DD> Write index to node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndexAdd\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndexAdd()</CODE></A>\n <DD> Reads the index of a node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpVisitedAdd\" TARGET=\"MAIN\"><CODE>DddmpVisitedAdd()</CODE></A>\n <DD> Returns true if node is visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisitedAdd\" TARGET=\"MAIN\"><CODE>DddmpSetVisitedAdd()</CODE></A>\n <DD> Marks a node as visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedAdd\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedAdd()</CODE></A>\n <DD> Marks a node as not visited\n\n <DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecurAdd\" TARGET=\"MAIN\"><CODE>NumberNodeRecurAdd()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecurAdd\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecurAdd()</CODE></A>\n <DD> Removes a node from unique table\n\n <DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecurAdd\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecurAdd()</CODE></A>\n <DD> Restores a node in unique table\n\n</DL>\n<HR>\n<A NAME=\"dddmpNodeBdd.c\"><H1>dddmpNodeBdd.c</H1></A>\nFunctions to handle BDD node infos and numbering <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to handle BDD node infos and numbering. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#DddmpNumberBddNodes\" TARGET=\"MAIN\"><CODE>DddmpNumberBddNodes()</CODE></A>\n <DD> Removes nodes from unique table and number them\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberBddNodes\" TARGET=\"MAIN\"><CODE>DddmpUnnumberBddNodes()</CODE></A>\n <DD> Restores nodes in unique table, loosing numbering\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexBdd\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexBdd()</CODE></A>\n <DD> Write index to node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndexBdd\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndexBdd()</CODE></A>\n <DD> Reads the index of a node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpVisitedBdd\" TARGET=\"MAIN\"><CODE>DddmpVisitedBdd()</CODE></A>\n <DD> Returns true if node is visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisitedBdd\" TARGET=\"MAIN\"><CODE>DddmpSetVisitedBdd()</CODE></A>\n <DD> Marks a node as visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedBdd\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedBdd()</CODE></A>\n <DD> Marks a node as not visited\n\n <DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecurBdd\" TARGET=\"MAIN\"><CODE>NumberNodeRecurBdd()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecurBdd\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecurBdd()</CODE></A>\n <DD> Removes a node from unique table\n\n <DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecurBdd\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecurBdd()</CODE></A>\n <DD> Restores a node in unique table\n\n</DL>\n<HR>\n<A NAME=\"dddmpNodeCnf.c\"><H1>dddmpNodeCnf.c</H1></A>\nFunctions to handle BDD node infos and numbering\n    while storing a CNF formula from a BDD or an array of BDDs <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to handle BDD node infos and numbering\n    while storing a CNF formula from a BDD or an array of BDDs. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#DddmpNumberDdNodesCnf\" TARGET=\"MAIN\"><CODE>DddmpNumberDdNodesCnf()</CODE></A>\n <DD> Removes nodes from unique table and numbers them\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCountEdgesAndNumber\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCountEdgesAndNumber()</CODE></A>\n <DD> Removes nodes from unique table and numbers each node according\n    to the number of its incoming BDD edges.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpUnnumberDdNodesCnf\" TARGET=\"MAIN\"><CODE>DddmpUnnumberDdNodesCnf()</CODE></A>\n <DD> Restores nodes in unique table, loosing numbering\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpPrintBddAndNext\" TARGET=\"MAIN\"><CODE>DddmpPrintBddAndNext()</CODE></A>\n <DD> Prints debug information\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexCnf\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexCnf()</CODE></A>\n <DD> Write index to node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpVisitedCnf()</CODE></A>\n <DD> Returns true if node is visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpSetVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpSetVisitedCnf()</CODE></A>\n <DD> Marks a node as visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpReadNodeIndexCnf\" TARGET=\"MAIN\"><CODE>DddmpReadNodeIndexCnf()</CODE></A>\n <DD> Reads the index of a node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpWriteNodeIndexCnfWithTerminalCheck\" TARGET=\"MAIN\"><CODE>DddmpWriteNodeIndexCnfWithTerminalCheck()</CODE></A>\n <DD> Write index to node\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedCnfRecur\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedCnfRecur()</CODE></A>\n <DD> Mark ALL nodes as not visited\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpClearVisitedCnf\" TARGET=\"MAIN\"><CODE>DddmpClearVisitedCnf()</CODE></A>\n <DD> Marks a node as not visited\n\n <DT> <A HREF=\"dddmpAllDet.html#NumberNodeRecurCnf\" TARGET=\"MAIN\"><CODE>NumberNodeRecurCnf()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCheckIncomingAndScanPath\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCheckIncomingAndScanPath()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesNumberEdgesRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesNumberEdgesRecur()</CODE></A>\n <DD> Number nodes recursively in post-order\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesResetCountRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesResetCountRecur()</CODE></A>\n <DD> Resets counter and visited flag for ALL nodes of a BDD\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpDdNodesCountEdgesRecur\" TARGET=\"MAIN\"><CODE>DddmpDdNodesCountEdgesRecur()</CODE></A>\n <DD> Counts the number of incoming edges for each node of a BDD\n\n <DT> <A HREF=\"dddmpAllDet.html#RemoveFromUniqueRecurCnf\" TARGET=\"MAIN\"><CODE>RemoveFromUniqueRecurCnf()</CODE></A>\n <DD> Removes a node from unique table\n\n <DT> <A HREF=\"dddmpAllDet.html#RestoreInUniqueRecurCnf\" TARGET=\"MAIN\"><CODE>RestoreInUniqueRecurCnf()</CODE></A>\n <DD> Restores a node in unique table\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpPrintBddAndNextRecur\" TARGET=\"MAIN\"><CODE>DddmpPrintBddAndNextRecur()</CODE></A>\n <DD> Prints debug info\n\n</DL>\n<HR>\n<A NAME=\"dddmpStoreAdd.c\"><H1>dddmpStoreAdd.c</H1></A>\nFunctions to write ADDs to file. <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to write ADDs to file.\n    ADDs are represended on file either in text or binary format under the\n    following rules.  A file contains a forest of ADDs (a vector of\n    Boolean functions).  ADD nodes are numbered with contiguous numbers,\n    from 1 to NNodes (total number of nodes on a file). 0 is not used to\n    allow negative node indexes for complemented edges.  A file contains\n    a header, including information about variables and roots to ADD\n    functions, followed by the list of nodes.\n    ADD nodes are listed according to their numbering, and in the present\n    implementation numbering follows a post-order strategy, in such a way\n    that a node is never listed before its Then/Else children. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddAddStore\" TARGET=\"MAIN\"><CODE>Dddmp_cuddAddStore()</CODE></A>\n <DD> Writes a dump file representing the argument ADD.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddAddArrayStore\" TARGET=\"MAIN\"><CODE>Dddmp_cuddAddArrayStore()</CODE></A>\n <DD> Writes a dump file representing the argument Array of ADDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreBdd\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreBdd()</CODE></A>\n <DD> Writes a dump file representing the argument Array of\n    BDDs/ADDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#NodeStoreRecurAdd\" TARGET=\"MAIN\"><CODE>NodeStoreRecurAdd()</CODE></A>\n <DD> Performs the recursive step of Dddmp_bddStore.\n\n <DT> <A HREF=\"dddmpAllDet.html#NodeTextStoreAdd\" TARGET=\"MAIN\"><CODE>NodeTextStoreAdd()</CODE></A>\n <DD> Store One Single Node in Text Format.\n\n</DL>\n<HR>\n<A NAME=\"dddmpStoreBdd.c\"><H1>dddmpStoreBdd.c</H1></A>\nFunctions to write BDDs to file. <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to write BDDs to file.\n    BDDs are represended on file either in text or binary format under the\n    following rules.  A file contains a forest of BDDs (a vector of\n    Boolean functions).  BDD nodes are numbered with contiguous numbers,\n    from 1 to NNodes (total number of nodes on a file). 0 is not used to\n    allow negative node indexes for complemented edges.  A file contains\n    a header, including information about variables and roots to BDD\n    functions, followed by the list of nodes.  BDD nodes are listed\n    according to their numbering, and in the present implementation\n    numbering follows a post-order strategy, in such a way that a node\n    is never listed before its Then/Else children. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStore\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStore()</CODE></A>\n <DD> Writes a dump file representing the argument BDD.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStore\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStore()</CODE></A>\n <DD> Writes a dump file representing the argument Array of BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddBddArrayStore\" TARGET=\"MAIN\"><CODE>DddmpCuddBddArrayStore()</CODE></A>\n <DD> Writes a dump file representing the argument Array of\n    BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#NodeStoreRecurBdd\" TARGET=\"MAIN\"><CODE>NodeStoreRecurBdd()</CODE></A>\n <DD> Performs the recursive step of Dddmp_bddStore.\n\n <DT> <A HREF=\"dddmpAllDet.html#NodeTextStoreBdd\" TARGET=\"MAIN\"><CODE>NodeTextStoreBdd()</CODE></A>\n <DD> Store One Single Node in Text Format.\n\n <DT> <A HREF=\"dddmpAllDet.html#NodeBinaryStoreBdd\" TARGET=\"MAIN\"><CODE>NodeBinaryStoreBdd()</CODE></A>\n <DD> Store One Single Node in Binary Format.\n\n</DL>\n<HR>\n<A NAME=\"dddmpStoreCnf.c\"><H1>dddmpStoreCnf.c</H1></A>\nFunctions to write out BDDs to file in a CNF format <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to write out BDDs to file in a CNF format. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStoreCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStoreCnf()</CODE></A>\n <DD> Writes a dump file representing the argument BDD in\n    a CNF format.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreCnf\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStoreCnf()</CODE></A>\n <DD> Writes a dump file representing the argument array of BDDs\n    in CNF format.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddBddArrayStoreCnf\" TARGET=\"MAIN\"><CODE>DddmpCuddBddArrayStoreCnf()</CODE></A>\n <DD> Writes a dump file representing the argument Array of\n    BDDs in the CNF standard format.\n\n <DT> <A HREF=\"dddmpAllDet.html#StoreCnfNodeByNode\" TARGET=\"MAIN\"><CODE>StoreCnfNodeByNode()</CODE></A>\n <DD> Store the BDD as CNF clauses.\n\n <DT> <A HREF=\"dddmpAllDet.html#StoreCnfNodeByNodeRecur\" TARGET=\"MAIN\"><CODE>StoreCnfNodeByNodeRecur()</CODE></A>\n <DD> Performs the recursive step of Dddmp_bddStore.\n\n <DT> <A HREF=\"dddmpAllDet.html#StoreCnfOneNode\" TARGET=\"MAIN\"><CODE>StoreCnfOneNode()</CODE></A>\n <DD> Store One Single BDD Node.\n\n <DT> <A HREF=\"dddmpAllDet.html#StoreCnfMaxtermByMaxterm\" TARGET=\"MAIN\"><CODE>StoreCnfMaxtermByMaxterm()</CODE></A>\n <DD> Prints a disjoint sum of products.\n\n <DT> <A HREF=\"dddmpAllDet.html#StoreCnfBest\" TARGET=\"MAIN\"><CODE>StoreCnfBest()</CODE></A>\n <DD> Prints a disjoint sum of products with intermediate\n    cutting points.\n\n <DT> <A HREF=\"dddmpAllDet.html#StoreCnfMaxtermByMaxtermRecur\" TARGET=\"MAIN\"><CODE>StoreCnfMaxtermByMaxtermRecur()</CODE></A>\n <DD> Performs the recursive step of Print Maxterm.\n\n <DT> <A HREF=\"dddmpAllDet.html#StoreCnfBestNotSharedRecur\" TARGET=\"MAIN\"><CODE>StoreCnfBestNotSharedRecur()</CODE></A>\n <DD> Performs the recursive step of Print Best on Not Shared\n    sub-BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#StoreCnfBestSharedRecur\" TARGET=\"MAIN\"><CODE>StoreCnfBestSharedRecur()</CODE></A>\n <DD> Performs the recursive step of Print Best on Shared\n    sub-BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#printCubeCnf\" TARGET=\"MAIN\"><CODE>printCubeCnf()</CODE></A>\n <DD> Print One Cube in CNF Format.\n\n</DL>\n<HR>\n<A NAME=\"dddmpStoreMisc.c\"><H1>dddmpStoreMisc.c</H1></A>\nFunctions to write out bdds to file in prefixed\n    and in Blif form. <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to write out bdds to file. \n    BDDs are represended on file in text format.\n    Each node is stored as a multiplexer in a prefix notation format for\n    the prefix notation file or in PLA format for the blif file. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStorePrefix\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStorePrefix()</CODE></A>\n <DD> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStorePrefix\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStorePrefix()</CODE></A>\n <DD> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStoreBlif\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStoreBlif()</CODE></A>\n <DD> Writes a dump file representing the argument BDD in\n    a Blif/Exlif notation.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreBlif\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStoreBlif()</CODE></A>\n <DD> Writes a dump file representing the argument BDD in\n    a Blif/Exlif notation.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddStoreSmv\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddStoreSmv()</CODE></A>\n <DD> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n <DT> <A HREF=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreSmv\" TARGET=\"MAIN\"><CODE>Dddmp_cuddBddArrayStoreSmv()</CODE></A>\n <DD> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStorePrefix\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStorePrefix()</CODE></A>\n <DD> Internal function to writes a dump file representing the\n    argument BDD in a prefix notation.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStorePrefixBody\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStorePrefixBody()</CODE></A>\n <DD> Internal function to writes a dump file representing the\n    argument BDD in a prefix notation. Writes the body of the file.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStorePrefixStep\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStorePrefixStep()</CODE></A>\n <DD> Performs the recursive step of\n    DddmpCuddDdArrayStorePrefixBody.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreBlif\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreBlif()</CODE></A>\n <DD> Writes a blif file representing the argument BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreBlifBody\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreBlifBody()</CODE></A>\n <DD> Writes a blif body representing the argument BDDs.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreBlifStep\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreBlifStep()</CODE></A>\n <DD> Performs the recursive step of DddmpCuddDdArrayStoreBlif.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreSmv\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreSmv()</CODE></A>\n <DD> Internal function to writes a dump file representing the\n    argument BDD in a SMV notation.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreSmvBody\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreSmvBody()</CODE></A>\n <DD> Internal function to writes a dump file representing the\n    argument BDD in a SMV notation. Writes the body of the file.\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpCuddDdArrayStoreSmvStep\" TARGET=\"MAIN\"><CODE>DddmpCuddDdArrayStoreSmvStep()</CODE></A>\n <DD> Performs the recursive step of\n    DddmpCuddDdArrayStoreSmvBody.\n\n</DL>\n<HR>\n<A NAME=\"dddmpUtil.c\"><H1>dddmpUtil.c</H1></A>\nUtil Functions for the dddmp package <P>\n<B>By: Gianpiero Cabodi and Stefano Quer</B><P>\nFunctions to manipulate arrays. <P>\n<DL>\n <DT> <A HREF=\"dddmpAllDet.html#QsortStrcmp\" TARGET=\"MAIN\"><CODE>QsortStrcmp()</CODE></A>\n <DD> String compare for qsort\n\n <DT> <A HREF=\"dddmpAllDet.html#FindVarname\" TARGET=\"MAIN\"><CODE>FindVarname()</CODE></A>\n <DD> Performs binary search of a name within a sorted array\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpStrDup\" TARGET=\"MAIN\"><CODE>DddmpStrDup()</CODE></A>\n <DD> Duplicates a string\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpStrArrayDup\" TARGET=\"MAIN\"><CODE>DddmpStrArrayDup()</CODE></A>\n <DD> Duplicates an array of strings\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpStrArrayRead\" TARGET=\"MAIN\"><CODE>DddmpStrArrayRead()</CODE></A>\n <DD> Inputs an array of strings\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpStrArrayWrite\" TARGET=\"MAIN\"><CODE>DddmpStrArrayWrite()</CODE></A>\n <DD> Outputs an array of strings\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpStrArrayFree\" TARGET=\"MAIN\"><CODE>DddmpStrArrayFree()</CODE></A>\n <DD> Frees an array of strings\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpIntArrayDup\" TARGET=\"MAIN\"><CODE>DddmpIntArrayDup()</CODE></A>\n <DD> Duplicates an array of ints\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpIntArrayRead\" TARGET=\"MAIN\"><CODE>DddmpIntArrayRead()</CODE></A>\n <DD> Inputs an array of ints\n\n <DT> <A HREF=\"dddmpAllDet.html#DddmpIntArrayWrite\" TARGET=\"MAIN\"><CODE>DddmpIntArrayWrite()</CODE></A>\n <DD> Outputs an array of ints\n\n</DL>\n<HR>\nLast updated on 1040218 17h14\n</BODY></HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpDesc.html",
    "content": "<HTML>\n<HEAD><TITLE>The dddmp package: Overview</TITLE></HEAD>\n<BODY>\n\n<H1>The dddmp package</H1>\n<H2>Functions to read in and write out BDDs, ADDs\n    and CNF formulas from and to files.</H2>\n<H3>By Gianpiero Cabodi and Stefano Quer</H3>\n\n<UL>\n <LI> <A HREF=\"dddmpExt.html\" TARGET=\"_top\">\n    Information for programmers</A>\n <LI> <A HREF=\"dddmpAllByFunc.html\" TARGET=\"_top\">\n    Information for developers sorted by function</A>\n <LI> <A HREF=\"dddmpAllByFile.html\" TARGET=\"_top\">\n    Information for developers sorted by file</A>\n</UL>\n\n<HR>\n\n\n\n<HR>\n\nLast updated on 1040218 17h14\n\n</BODY>\n</HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpExt.html",
    "content": "<HTML>\n<HEAD><TITLE>The dddmp Package for Programmers</TITLE></HEAD>\n\n<FRAMESET ROWS=\"5%,90%,5%\">\n  <FRAME SRC=\"dddmpTitle.html\">\n  <FRAMESET COLS=\"40%,60%\">\n    <FRAME SRC=\"dddmpExtAbs.html\" NAME=\"ABSTRACT\">\n    <FRAME SRC=\"dddmpExtDet.html\" NAME=\"MAIN\">\n  </FRAMESET>\n  <FRAME SRC=\"credit.html\">\n</FRAMESET>\n\n</HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpExtAbs.html",
    "content": "<html>\n<head><title>dddmp package abstract</title></head>\n<body>\n\n\n<!-- Function Abstracts -->\n\n<dl>\n<dt> <a href=\"dddmpAllDet.html#Dddmp_Bin2Text\" TARGET=\"MAIN\"><code>Dddmp_Bin2Text()</code></a>\n<dd> Converts from binary to ASCII format\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_Text2Bin\" TARGET=\"MAIN\"><code>Dddmp_Text2Bin()</code></a>\n<dd> Converts from ASCII to binary format\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddAddArrayLoad\" TARGET=\"MAIN\"><code>Dddmp_cuddAddArrayLoad()</code></a>\n<dd> Reads a dump file representing the argument ADDs.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddAddArrayStore\" TARGET=\"MAIN\"><code>Dddmp_cuddAddArrayStore()</code></a>\n<dd> Writes a dump file representing the argument Array of ADDs.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddAddLoad\" TARGET=\"MAIN\"><code>Dddmp_cuddAddLoad()</code></a>\n<dd> Reads a dump file representing the argument ADD.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddAddStore\" TARGET=\"MAIN\"><code>Dddmp_cuddAddStore()</code></a>\n<dd> Writes a dump file representing the argument ADD.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddArrayLoadCnf\" TARGET=\"MAIN\"><code>Dddmp_cuddBddArrayLoadCnf()</code></a>\n<dd> Reads a dump file in a CNF format.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddArrayLoad\" TARGET=\"MAIN\"><code>Dddmp_cuddBddArrayLoad()</code></a>\n<dd> Reads a dump file representing the argument BDDs.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreBlif\" TARGET=\"MAIN\"><code>Dddmp_cuddBddArrayStoreBlif()</code></a>\n<dd> Writes a dump file representing the argument BDD in\n    a Blif/Exlif notation.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreCnf\" TARGET=\"MAIN\"><code>Dddmp_cuddBddArrayStoreCnf()</code></a>\n<dd> Writes a dump file representing the argument array of BDDs\n    in CNF format.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddArrayStorePrefix\" TARGET=\"MAIN\"><code>Dddmp_cuddBddArrayStorePrefix()</code></a>\n<dd> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddArrayStoreSmv\" TARGET=\"MAIN\"><code>Dddmp_cuddBddArrayStoreSmv()</code></a>\n<dd> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddArrayStore\" TARGET=\"MAIN\"><code>Dddmp_cuddBddArrayStore()</code></a>\n<dd> Writes a dump file representing the argument Array of BDDs.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddDisplayBinary\" TARGET=\"MAIN\"><code>Dddmp_cuddBddDisplayBinary()</code></a>\n<dd> Display a binary dump file in a text file\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddLoadCnf\" TARGET=\"MAIN\"><code>Dddmp_cuddBddLoadCnf()</code></a>\n<dd> Reads a dump file in a CNF format.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddLoad\" TARGET=\"MAIN\"><code>Dddmp_cuddBddLoad()</code></a>\n<dd> Reads a dump file representing the argument BDD.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddStoreBlif\" TARGET=\"MAIN\"><code>Dddmp_cuddBddStoreBlif()</code></a>\n<dd> Writes a dump file representing the argument BDD in\n    a Blif/Exlif notation.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddStoreCnf\" TARGET=\"MAIN\"><code>Dddmp_cuddBddStoreCnf()</code></a>\n<dd> Writes a dump file representing the argument BDD in\n    a CNF format.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddStorePrefix\" TARGET=\"MAIN\"><code>Dddmp_cuddBddStorePrefix()</code></a>\n<dd> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddStoreSmv\" TARGET=\"MAIN\"><code>Dddmp_cuddBddStoreSmv()</code></a>\n<dd> Writes a dump file representing the argument BDD in\n    a prefix notation.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddBddStore\" TARGET=\"MAIN\"><code>Dddmp_cuddBddStore()</code></a>\n<dd> Writes a dump file representing the argument BDD.\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddHeaderLoadCnf\" TARGET=\"MAIN\"><code>Dddmp_cuddHeaderLoadCnf()</code></a>\n<dd> Reads the header of a dump file representing the argument BDDs\n\n<dt> <a href=\"dddmpAllDet.html#Dddmp_cuddHeaderLoad\" TARGET=\"MAIN\"><code>Dddmp_cuddHeaderLoad()</code></a>\n<dd> Reads the header of a dump file representing the argument BDDs\n\n</dl>\n\n<hr>\n\nLast updated on 1040218 17h14\n</body></html>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpExtDet.html",
    "content": "<HTML>\n<HEAD><TITLE>The dddmp package</TITLE></HEAD>\n<BODY>\n\n<DL>\n<dt><pre>\n<A NAME=\"Dddmp_Bin2Text\"></A>\nint <I></I>\n<B>Dddmp_Bin2Text</B>(\n  char * <b>filein</b>, <i>IN: name of binary file</i>\n  char * <b>fileout</b> <i>IN: name of ASCII file</i>\n)\n</pre>\n<dd> Converts from binary to ASCII format. A BDD array is loaded and\n    and stored to the target file.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_Text2Bin()\">Dddmp_Text2Bin()</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_Text2Bin\"></A>\nint <I></I>\n<B>Dddmp_Text2Bin</B>(\n  char * <b>filein</b>, <i>IN: name of ASCII file</i>\n  char * <b>fileout</b> <i>IN: name of binary file</i>\n)\n</pre>\n<dd> Converts from ASCII to binary format. A BDD array is loaded and\n    and stored to the target file.\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_Bin2Text()\">Dddmp_Bin2Text()</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddAddArrayLoad\"></A>\nint <I></I>\n<B>Dddmp_cuddAddArrayLoad</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_RootMatchType  <b>rootMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>rootmatchnames</b>, <i>IN: sorted names for loaded roots</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by ids</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by ids</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids, by ids</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>pproots</b> <i>OUT: array of returned BDD roots</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument ADDs. See \n    BDD load functions for detailed explanation.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddAddArrayStore\"></A>\nint <I></I>\n<B>Dddmp_cuddAddArrayStore</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: DD name (or NULL)</i>\n  int  <b>nRoots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of ADD roots to be stored</i>\n  char ** <b>rootnames</b>, <i>IN: array of root names (or NULL)</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var IDs</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument array of ADDs to file. Dumping is\n    either in text or binary form. see the corresponding BDD dump \n    function for further details.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddAddStore\">Dddmp_cuddAddStore</a>\n<a href=\"#Dddmp_cuddAddLoad\">Dddmp_cuddAddLoad</a>\n<a href=\"#Dddmp_cuddAddArrayLoad\">Dddmp_cuddAddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddAddLoad\"></A>\nDdNode * <I></I>\n<B>Dddmp_cuddAddLoad</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: Manager</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names by IDs</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids by IDs</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids by IDs</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument ADD.\n    Dddmp_cuddAddArrayLoad is used through a dummy array.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddAddStore\">Dddmp_cuddAddStore</a>\n<a href=\"#Dddmp_cuddAddArrayLoad\">Dddmp_cuddAddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddAddStore\"></A>\nint <I></I>\n<B>Dddmp_cuddAddStore</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: DD name (or NULL)</i>\n  DdNode * <b>f</b>, <i>IN: ADD root to be stored</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var ids</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument ADD to file. Dumping is done through\n    Dddmp_cuddAddArrayStore, And a dummy array of 1 ADD root is\n    used for this purpose.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique hash. They are \n    re-linked after the store operation in a modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddAddLoad\">Dddmp_cuddAddLoad</a>\n<a href=\"#Dddmp_cuddAddArrayLoad\">Dddmp_cuddAddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayLoadCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayLoadCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_RootMatchType  <b>rootmatchmode</b>, <i>IN: storing mode selector</i>\n  char ** <b>rootmatchnames</b>, <i>IN: sorted names for loaded roots</i>\n  Dddmp_VarMatchType  <b>varmatchmode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by IDs</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by IDs</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids, by IDs</i>\n  int  <b>mode</b>, <i>IN: computation Mode</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>rootsPtrPtr</b>, <i>OUT: array of returned BDD roots</i>\n  int * <b>nRoots</b> <i>OUT: number of BDDs returned</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDD in a\n    CNF formula.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayLoad\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayLoad</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_RootMatchType  <b>rootMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>rootmatchnames</b>, <i>IN: sorted names for loaded roots</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by ids</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by ids</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids, by ids</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>pproots</b> <i>OUT: array of returned BDD roots</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDDs. The header is\n    common to both text and binary mode. The node list is either \n    in text or binary format. A dynamic vector of DD pointers \n    is allocated to support conversion from DD indexes to pointers.\n    Several criteria are supported for variable match between file\n    and dd manager. Several changes/permutations/compositions are allowed\n    for variables while loading DDs. Variable of the dd manager are allowed \n    to match with variables on file on ids, permids, varnames, \n    varauxids; also direct composition between ids and \n    composeids is supported. More in detail:\n    <ol>\n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    allows the loading of a DD keeping variable IDs unchanged\n    (regardless of the variable ordering of the reading manager); this\n    is useful, for example, when swapping DDs to file and restoring them\n    later from file, after possible variable reordering activations.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHPERMIDS <p>\n    is used to allow variable match according to the position in the\n    ordering.\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHNAMES <p>\n    requires a non NULL varmatchnames parameter; this is a vector of\n    strings in one-to-one correspondence with variable IDs of the\n    reading manager. Variables in the DD file read are matched with\n    manager variables according to their name (a non NULL varnames\n    parameter was required while storing the DD file).\n    \n    <li> varMatchMode=DDDMP_VAR_MATCHIDS <p>\n    has a meaning similar to DDDMP_VAR_MATCHNAMES, but integer auxiliary\n    IDs are used instead of strings; the additional non NULL\n    varmatchauxids parameter is needed.\n    \n    <li> varMatchMode=DDDMP_VAR_COMPOSEIDS <p>\n    uses the additional varcomposeids parameter is used as array of\n    variable ids to be composed with ids stored in file.\n    </ol>\n    \n    In the present implementation, the array varnames (3), varauxids (4)\n    and composeids (5) need to have one entry for each variable in the \n    DD manager (NULL pointers are allowed for unused variables\n    in varnames). Hence variables need to be already present in the \n    manager. All arrays are sorted according to IDs.\n\n    All the loaded BDDs are referenced before returning them.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStoreBlif\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStoreBlif</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nroots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: array of variable names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: array of root names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStoreBLif.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStorePrefix\">Dddmp_cuddBddArrayStorePrefix</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStoreCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStoreCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  int  <b>rootN</b>, <i>IN: # output BDD roots to be stored</i>\n  Dddmp_DecompCnfStoreType  <b>mode</b>, <i>IN: format selection</i>\n  int  <b>noHeader</b>, <i>IN: do not store header iff 1</i>\n  char ** <b>varNames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>bddIds</b>, <i>IN: array of converted var IDs</i>\n  int * <b>bddAuxIds</b>, <i>IN: array of BDD node Auxiliary Ids</i>\n  int * <b>cnfIds</b>, <i>IN: array of converted var IDs</i>\n  int  <b>idInitial</b>, <i>IN: starting id for cutting variables</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # Incoming Edges</i>\n  int  <b>pathLengthTh</b>, <i>IN: Max Path Length</i>\n  char * <b>fname</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: pointer to the store file</i>\n  int * <b>clauseNPtr</b>, <i>OUT: number of clause stored</i>\n  int * <b>varNewNPtr</b> <i>OUT: number of new variable created</i>\n)\n</pre>\n<dd> Dumps the argument array of BDDs to file.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n    Three methods are allowed:\n    * NodeByNode method: Insert a cut-point for each BDD node (but the\n                         terminal nodes)\n    * MaxtermByMaxterm method: Insert no cut-points, i.e. the off-set of\n                               trhe function is stored\n    * Best method: Tradeoff between the previous two methods.\n      Auxiliary variables, i.e., cut points are inserted following these\n      criterias:\n      * edgeInTh\n        indicates the maximum number of incoming edges up to which\n        no cut point (auxiliary variable) is inserted.\n        If edgeInTh:\n        * is equal to -1 no cut point due to incoming edges are inserted\n          (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node with a single\n          incoming edge, i.e., each node, (NodeByNode method).\n\t* is equal to n a cut point is inserted for each node with (n+1)\n          incoming edges.\n      * pathLengthTh\n        indicates the maximum length path up to which no cut points\n        (auxiliary variable) is inserted.\n        If the path length between two nodes exceeds this value, a cut point\n        is inserted.\n        If pathLengthTh:\n        * is equal to -1 no cut point due path length are inserted\n          (MaxtermByMaxterm method.)\n\t* is equal to 0 a cut point is inserted for each node (NodeByNode\n          method).\n\t* is equal to n a cut point is inserted on path whose length is\n          equal to (n+1).\n        Notice that the maximum number of literals in a clause is equal\n        to (pathLengthTh + 2), i.e., for each path we have to keep into\n        account a CNF variable for each node plus 2 added variables for\n        the bottom and top-path cut points.\n    The stored file can contain a file header or not depending on the\n    noHeader parameter (IFF 0, usual setting, the header is usually stored.\n    This option can be useful in storing multiple BDDs, as separate BDDs,\n    on the same file leaving the opening of the file to the caller.\n<p>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStorePrefix\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStorePrefix</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nroots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: array of variable names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: array of root names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStoreSmv\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStoreSmv</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nroots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: array of variable names (or NULL)</i>\n  char ** <b>outputNames</b>, <i>IN: array of root names (or NULL)</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStore\">Dddmp_cuddBddArrayStore</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddArrayStore\"></A>\nint <I></I>\n<B>Dddmp_cuddBddArrayStore</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: dd name (or NULL)</i>\n  int  <b>nRoots</b>, <i>IN: number of output BDD roots to be stored</i>\n  DdNode ** <b>f</b>, <i>IN: array of BDD roots to be stored</i>\n  char ** <b>rootnames</b>, <i>IN: array of root names (or NULL)</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var IDs</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument array of BDDs to file. Dumping is either \n    in text or binary form.  BDDs are stored to the fp (already \n    open) file if not NULL. Otherwise the file whose name is \n    fname is opened in write mode. The header has the same format \n    for both textual and binary dump. Names are allowed for input \n    variables (vnames) and for represented functions (rnames). \n    For sake of generality and because of dynamic variable \n    ordering both variable IDs and permuted IDs are included. \n    New IDs are also supported (auxids). Variables are identified \n    with incremental numbers. according with their positiom in \n    the support set. In text mode, an extra info may be added, \n    chosen among the following options: name, ID, PermID, or an \n    auxiliary id. Since conversion from DD pointers to integers \n    is required, DD nodes are temporarily removed from the unique\n    hash table. This allows the use of the next field to store \n    node IDs.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from the unique hash\n    table. They are re-linked after the store operation in a \n    modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n<a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddDisplayBinary\"></A>\nint <I></I>\n<B>Dddmp_cuddBddDisplayBinary</B>(\n  char * <b>fileIn</b>, <i>IN: name of binary file</i>\n  char * <b>fileOut</b> <i>IN: name of text file</i>\n)\n</pre>\n<dd> Display a binary dump file in a text file\n<p>\n\n<dd> <b>Side Effects</b> None\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n<a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddLoadCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddBddLoadCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_VarMatchType  <b>varmatchmode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names, by IDs</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids, by IDs</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids accessed, by IDs</i>\n  int  <b>mode</b>, <i>IN: computation mode</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: file pointer</i>\n  DdNode *** <b>rootsPtrPtr</b>, <i>OUT: array of returned BDD roots</i>\n  int * <b>nRoots</b> <i>OUT: number of BDDs returned</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDD in a\n    CNF formula.\n    Dddmp_cuddBddArrayLoadCnf is used through a dummy array.\n    The results is returned in different formats depending on the \n    mode selection:\n      IFF mode == 0 Return the Clauses without Conjunction\n      IFF mode == 1 Return the sets of BDDs without Quantification\n      IFF mode == 2 Return the sets of BDDs AFTER Existential Quantification\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddLoad\"></A>\nDdNode * <I></I>\n<B>Dddmp_cuddBddLoad</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  Dddmp_VarMatchType  <b>varMatchMode</b>, <i>IN: storing mode selector</i>\n  char ** <b>varmatchnames</b>, <i>IN: array of variable names - by IDs</i>\n  int * <b>varmatchauxids</b>, <i>IN: array of variable auxids - by IDs</i>\n  int * <b>varcomposeids</b>, <i>IN: array of new ids accessed - by IDs</i>\n  int  <b>mode</b>, <i>IN: requested input file format</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads a dump file representing the argument BDD.\n    Dddmp_cuddBddArrayLoad is used through a dummy array (see this\n    function's description for more details).\n    Mode, the requested input file format, is checked against \n    the file format.\n    The loaded BDDs is referenced before returning it.\n<p>\n\n<dd> <b>Side Effects</b> A vector of pointers to DD nodes is allocated and freed.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStoreBlif\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStoreBlif</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nRoots</b>, <i>IN: Number of BDD roots</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: Array of variable names</i>\n  char ** <b>outputNames</b>, <i>IN: Array of root names</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fileName</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStoreBlif.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStorePrefix\">Dddmp_cuddBddStorePrefix</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStoreCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStoreCnf</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  Dddmp_DecompCnfStoreType  <b>mode</b>, <i>IN: format selection</i>\n  int  <b>noHeader</b>, <i>IN: do not store header iff 1</i>\n  char ** <b>varNames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>bddIds</b>, <i>IN: array of var ids</i>\n  int * <b>bddAuxIds</b>, <i>IN: array of BDD node Auxiliary Ids</i>\n  int * <b>cnfIds</b>, <i>IN: array of CNF var ids</i>\n  int  <b>idInitial</b>, <i>IN: starting id for cutting variables</i>\n  int  <b>edgeInTh</b>, <i>IN: Max # Incoming Edges</i>\n  int  <b>pathLengthTh</b>, <i>IN: Max Path Length</i>\n  char * <b>fname</b>, <i>IN: file name</i>\n  FILE * <b>fp</b>, <i>IN: pointer to the store file</i>\n  int * <b>clauseNPtr</b>, <i>OUT: number of clause stored</i>\n  int * <b>varNewNPtr</b> <i>OUT: number of new variable created</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    This task is performed by calling the function\n    Dddmp_cuddBddArrayStoreCnf.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique hash. They are\n    re-linked after the store operation in a modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayStoreCnf\">Dddmp_cuddBddArrayStoreCnf</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStorePrefix\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStorePrefix</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nRoots</b>, <i>IN: Number of BDD roots</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: Array of variable names</i>\n  char ** <b>outputNames</b>, <i>IN: Array of root names</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fileName</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStoreSmv\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStoreSmv</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  int  <b>nRoots</b>, <i>IN: Number of BDD roots</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  char ** <b>inputNames</b>, <i>IN: Array of variable names</i>\n  char ** <b>outputNames</b>, <i>IN: Array of root names</i>\n  char * <b>modelName</b>, <i>IN: Model Name</i>\n  char * <b>fileName</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file.\n    Dumping is done through Dddmp_cuddBddArrayStorePrefix.\n    A dummy array of 1 BDD root is used for this purpose.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddStore\">Dddmp_cuddBddStore</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddBddStore\"></A>\nint <I></I>\n<B>Dddmp_cuddBddStore</B>(\n  DdManager * <b>ddMgr</b>, <i>IN: DD Manager</i>\n  char * <b>ddname</b>, <i>IN: DD name (or NULL)</i>\n  DdNode * <b>f</b>, <i>IN: BDD root to be stored</i>\n  char ** <b>varnames</b>, <i>IN: array of variable names (or NULL)</i>\n  int * <b>auxids</b>, <i>IN: array of converted var ids</i>\n  int  <b>mode</b>, <i>IN: storing mode selector</i>\n  Dddmp_VarInfoType  <b>varinfo</b>, <i>IN: extra info for variables in text mode</i>\n  char * <b>fname</b>, <i>IN: File name</i>\n  FILE * <b>fp</b> <i>IN: File pointer to the store file</i>\n)\n</pre>\n<dd> Dumps the argument BDD to file. Dumping is done through\n    Dddmp_cuddBddArrayStore. A dummy array of 1 BDD root is\n    used for this purpose.\n<p>\n\n<dd> <b>Side Effects</b> Nodes are temporarily removed from unique hash. They are\n    re-linked after the store operation in a modified order.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddLoad\">Dddmp_cuddBddLoad</a>\n<a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddHeaderLoadCnf\"></A>\nint <I></I>\n<B>Dddmp_cuddHeaderLoadCnf</B>(\n  int * <b>nVars</b>, <i>OUT: number of DD variables</i>\n  int * <b>nsuppvars</b>, <i>OUT: number of support variables</i>\n  char *** <b>suppVarNames</b>, <i>OUT: array of support variable names</i>\n  char *** <b>orderedVarNames</b>, <i>OUT: array of variable names</i>\n  int ** <b>varIds</b>, <i>OUT: array of variable ids</i>\n  int ** <b>varComposeIds</b>, <i>OUT: array of permids ids</i>\n  int ** <b>varAuxIds</b>, <i>OUT: array of variable aux ids</i>\n  int * <b>nRoots</b>, <i>OUT: number of root in the file</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads the header of a dump file representing the argument BDDs. \n    Returns main information regarding DD type stored in the file,\n    the variable ordering used, the number of variables, etc.\n    It reads only the header of the file NOT the BDD/ADD section.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n<dt><pre>\n<A NAME=\"Dddmp_cuddHeaderLoad\"></A>\nint <I></I>\n<B>Dddmp_cuddHeaderLoad</B>(\n  Dddmp_DecompType * <b>ddType</b>, <i>OUT: selects the proper decomp type</i>\n  int * <b>nVars</b>, <i>OUT: number of DD variables</i>\n  int * <b>nsuppvars</b>, <i>OUT: number of support variables</i>\n  char *** <b>suppVarNames</b>, <i>OUT: array of support variable names</i>\n  char *** <b>orderedVarNames</b>, <i>OUT: array of variable names</i>\n  int ** <b>varIds</b>, <i>OUT: array of variable ids</i>\n  int ** <b>varComposeIds</b>, <i>OUT: array of permids ids</i>\n  int ** <b>varAuxIds</b>, <i>OUT: array of variable aux ids</i>\n  int * <b>nRoots</b>, <i>OUT: number of root in the file</i>\n  char * <b>file</b>, <i>IN: file name</i>\n  FILE * <b>fp</b> <i>IN: file pointer</i>\n)\n</pre>\n<dd> Reads the header of a dump file representing the argument BDDs.\n    Returns main information regarding DD type stored in the file,\n    the variable ordering used, the number of variables, etc.\n    It reads only the header of the file NOT the BDD/ADD section.\n<p>\n\n<dd> <b>See Also</b> <code><a href=\"#Dddmp_cuddBddArrayLoad\">Dddmp_cuddBddArrayLoad</a>\n</code>\n\n\n</DL>\n<HR>\nLast updated on 1040218 17h14\n</BODY></HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/dddmpTitle.html",
    "content": "<HTML>\n<HEAD><TITLE>The dddmp package: Title</TITLE></HEAD>\n<BODY>\n\n<TABLE BORDER WIDTH=\"100%\">\n  <TR>\n    <TD ALIGN=center> <A HREF=\"dddmpExt.html\" TARGET=\"_top\">\n        Programmer view</A> </TD>\n    <TD ALIGN=center> <A HREF=\"dddmpAllByFunc.html\" TARGET=\"_top\">\n\tMaintainer by function</A> </TD>\n    <TD ALIGN=center> <A HREF=\"dddmpAllByFile.html\" TARGET=\"_top\">\n        Maintainer by file</A> </TD>\n  </TR>\n</TABLE>\n\n</BODY>\n</HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/packages.html",
    "content": "<HTML>\n<HEAD><TITLE>Package Documentation</TITLE></HEAD>\n\n<FRAMESET ROWS=\"95%,5%\">\n  <FRAMESET COLS=\"40%,60%\">\n    <FRAME SRC=\"pkgIndex.html\">\n    <FRAME SRC=\"credit.html\" NAME=\"MAIN\">\n  </FRAMESET>\n  <FRAME SRC=\"credit.html\">\n</FRAMESET>\n\n</HTML>\n"
  },
  {
    "path": "cudd/dddmp/doc/pkgIndex.html",
    "content": "<HTML>\n<HEAD><TITLE>Package Documentation</TITLE></HEAD>\n<BODY>\n<H1>Package Documentation</H1><HR><TABLE CELLSPACING=0 CELLPADDING=1>\n<TR>\n  <TD VALIGN=top><A HREF=\"dddmpDesc.html\" TARGET=\"MAIN\"><CODE>dddmp</CODE></A></TD>\n  <TD VALIGN=top>Functions to read in and write out BDDs, ADDs\n</TD>\n</TR>\n</TABLE>\n<HR>\nLast updated on 1040218 17h15\n</BODY></HTML>\n"
  },
  {
    "path": "cudd/dddmp/exp/0.add",
    "content": ".ver DDDMP-2.0\n.add\n.mode A\n.varinfo 0\n.nnodes 5\n.nvars 3\n.nsuppvars 2\n.suppvarnames DUMMY1 DUMMY2\n.orderedvarnames DUMMY0 DUMMY1 DUMMY2\n.ids 1 2\n.permids 1 2\n.auxids 1 2\n.nroots 1\n.rootids 5\n.nodes\n1 T 1 0 0\n2 T 2 0 0\n3 T 0 0 0\n4 2 1 2 3\n5 1 0 1 4\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/0.bdd",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 5\n.nvars 50\n.nsuppvars 3\n.suppvarnames DUMMY1 DUMMY2 DUMMY3\n.ids 1 2 3\n.permids 1 2 3\n.auxids 1 2 3\n.nroots 1\n.rootids -5\n.nodes\n1 T 1 0 0\n2 3 2 1 -1\n3 2 1 1 2\n4 2 1 1 -2\n5 1 0 3 4\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/0or1.bdd",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 104\n.nvars 50\n.nsuppvars 16\n.suppvarnames DUMMY0 DUMMY1 DUMMY2 DUMMY3 DUMMY4 DUMMY10 DUMMY11 DUMMY12 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22\n.orderedvarnames DUMMY0 DUMMY1 DUMMY2 DUMMY3 DUMMY4 DUMMY5 DUMMY6 DUMMY7 DUMMY8 DUMMY9 DUMMY10 DUMMY11 DUMMY12 DUMMY13 DUMMY14 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49\n.ids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\n.permids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\n.auxids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\n.nroots 1\n.rootids -104\n.nodes\n1 T 1 0 0\n2 22 15 1 -1\n3 21 14 1 -2\n4 20 13 1 3\n5 19 12 1 4\n6 20 13 3 1\n7 21 14 1 2\n8 20 13 1 7\n9 19 12 6 8\n10 18 11 5 9\n11 17 10 1 10\n12 18 11 1 9\n13 17 10 1 12\n14 16 9 11 13\n15 20 13 7 -1\n16 21 14 2 -1\n17 20 13 16 -3\n18 19 12 15 -17\n19 21 14 2 1\n20 20 13 19 7\n21 19 12 6 20\n22 18 11 18 21\n23 17 10 1 22\n24 16 9 23 13\n25 18 11 18 9\n26 17 10 1 25\n27 16 9 26 13\n28 15 8 24 27\n29 12 7 28 27\n30 11 6 28 29\n31 11 6 28 27\n32 10 5 30 31\n33 4 4 14 32\n34 3 3 33 -1\n35 2 2 33 34\n36 19 12 1 8\n37 18 11 5 36\n38 17 10 1 37\n39 16 9 38 1\n40 19 12 1 20\n41 18 11 18 40\n42 17 10 1 41\n43 16 9 42 1\n44 18 11 18 36\n45 17 10 1 44\n46 16 9 45 1\n47 15 8 43 46\n48 12 7 47 46\n49 11 6 47 48\n50 11 6 47 46\n51 10 5 49 50\n52 4 4 39 51\n53 3 3 1 -52\n54 2 2 52 -53\n55 1 1 35 54\n56 20 13 16 -1\n57 21 14 1 -1\n58 20 13 1 57\n59 19 12 56 -58\n60 18 11 59 -9\n61 17 10 1 -60\n62 19 12 56 -8\n63 18 11 62 -9\n64 17 10 1 -63\n65 16 9 61 64\n66 21 14 2 -2\n67 20 13 66 1\n68 20 13 16 -57\n69 19 12 67 68\n70 18 11 69 -21\n71 17 10 1 -70\n72 16 9 71 64\n73 18 11 69 -9\n74 17 10 1 -73\n75 16 9 74 64\n76 15 8 72 75\n77 12 7 76 75\n78 11 6 76 77\n79 11 6 76 75\n80 10 5 78 79\n81 4 4 65 80\n82 3 3 81 -1\n83 2 2 81 82\n84 18 11 59 -36\n85 17 10 1 -84\n86 18 11 62 -1\n87 17 10 1 -86\n88 16 9 85 87\n89 18 11 69 -40\n90 17 10 1 -89\n91 16 9 90 87\n92 18 11 69 -36\n93 17 10 1 -92\n94 16 9 93 87\n95 15 8 91 94\n96 12 7 95 94\n97 11 6 95 96\n98 11 6 95 94\n99 10 5 97 98\n100 4 4 88 99\n101 3 3 1 -100\n102 2 2 100 -101\n103 1 1 83 102\n104 0 0 55 103\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/1.add",
    "content": ".ver DDDMP-2.0\n.add\n.mode A\n.varinfo 0\n.nnodes 12\n.nvars 50\n.nsuppvars 4\n.suppvarnames DUMMY1 DUMMY2 DUMMY3 DUMMY4\n.orderedvarnames DUMMY0 DUMMY1 DUMMY2 DUMMY3 DUMMY4 DUMMY5 DUMMY6 DUMMY7 DUMMY8 DUMMY9 DUMMY10 DUMMY11 DUMMY12 DUMMY13 DUMMY14 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49\n.ids 1 2 3 4\n.permids 1 2 3 4\n.auxids 2 3 4 0\n.nroots 1\n.rootids 12\n.nodes\n1 T 0 0 0\n2 T 2 0 0\n3 4 3 1 2\n4 T 1 0 0\n5 4 3 4 1\n6 3 2 3 5\n7 4 3 2 4\n8 3 2 7 3\n9 2 1 6 8\n10 3 2 5 7\n11 2 1 10 6\n12 1 0 9 11\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/1.bdd",
    "content": ".ver DDDMP-2.0\r\n.mode A\r\n.varinfo 0\r\n.nnodes 96\r\n.nvars 50\r\n.nsuppvars 14\r\n.suppvarnames DUMMY0 DUMMY1 DUMMY4 DUMMY10 DUMMY11 DUMMY12 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22\r\n.ids 0 1 4 10 11 12 15 16 17 18 19 20 21 22\r\n.permids 0 1 4 10 11 12 15 16 17 18 19 20 21 22\r\n.auxids 0 1 4 10 11 12 15 16 17 18 19 20 21 22\r\n.nroots 1\r\n.rootids -96\r\n.nodes\r\n1 T 1 0 0\r\n2 22 13 1 -1\r\n3 21 12 1 -2\r\n4 20 11 1 3\r\n5 19 10 1 4\r\n6 20 11 3 1\r\n7 21 12 1 2\r\n8 20 11 1 7\r\n9 19 10 6 8\r\n10 18 9 5 9\r\n11 17 8 1 10\r\n12 18 9 1 9\r\n13 17 8 1 12\r\n14 16 7 11 13\r\n15 20 11 7 -1\r\n16 21 12 2 -1\r\n17 20 11 16 -3\r\n18 19 10 15 -17\r\n19 21 12 2 1\r\n20 20 11 19 7\r\n21 19 10 6 20\r\n22 18 9 18 21\r\n23 17 8 1 22\r\n24 16 7 23 13\r\n25 18 9 18 9\r\n26 17 8 1 25\r\n27 16 7 26 13\r\n28 15 6 24 27\r\n29 12 5 28 27\r\n30 11 4 28 29\r\n31 11 4 28 27\r\n32 10 3 30 31\r\n33 4 2 14 32\r\n34 19 10 1 8\r\n35 18 9 5 34\r\n36 17 8 1 35\r\n37 16 7 36 1\r\n38 19 10 1 20\r\n39 18 9 18 38\r\n40 17 8 1 39\r\n41 16 7 40 1\r\n42 18 9 18 34\r\n43 17 8 1 42\r\n44 16 7 43 1\r\n45 15 6 41 44\r\n46 12 5 45 44\r\n47 11 4 45 46\r\n48 11 4 45 44\r\n49 10 3 47 48\r\n50 4 2 37 49\r\n51 1 1 33 50\r\n52 20 11 16 -1\r\n53 21 12 1 -1\r\n54 20 11 1 53\r\n55 19 10 52 -54\r\n56 18 9 55 -9\r\n57 17 8 1 -56\r\n58 19 10 52 -8\r\n59 18 9 58 -9\r\n60 17 8 1 -59\r\n61 16 7 57 60\r\n62 21 12 2 -2\r\n63 20 11 62 1\r\n64 20 11 16 -53\r\n65 19 10 63 64\r\n66 18 9 65 -21\r\n67 17 8 1 -66\r\n68 16 7 67 60\r\n69 18 9 65 -9\r\n70 17 8 1 -69\r\n71 16 7 70 60\r\n72 15 6 68 71\r\n73 12 5 72 71\r\n74 11 4 72 73\r\n75 11 4 72 71\r\n76 10 3 74 75\r\n77 4 2 61 76\r\n78 18 9 55 -34\r\n79 17 8 1 -78\r\n80 18 9 58 -1\r\n81 17 8 1 -80\r\n82 16 7 79 81\r\n83 18 9 65 -38\r\n84 17 8 1 -83\r\n85 16 7 84 81\r\n86 18 9 65 -34\r\n87 17 8 1 -86\r\n88 16 7 87 81\r\n89 15 6 85 88\r\n90 12 5 89 88\r\n91 11 4 89 90\r\n92 11 4 89 88\r\n93 10 3 91 92\r\n94 4 2 82 93\r\n95 1 1 77 94\r\n96 0 0 51 95\r\n.end\r\n"
  },
  {
    "path": "cudd/dddmp/exp/2.bdd",
    "content": ".ver DDDMP-2.0\r\n.mode A\r\n.varinfo 0\r\n.nnodes 104\r\n.nvars 50\r\n.nsuppvars 16\r\n.suppvarnames DUMMY0 DUMMY1 DUMMY2 DUMMY3 DUMMY4 DUMMY10 DUMMY11 DUMMY12 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22\r\n.ids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\r\n.permids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\r\n.auxids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\r\n.nroots 1\r\n.rootids -104\r\n.nodes\r\n1 T 1 0 0\r\n2 22 15 1 -1\r\n3 21 14 1 -2\r\n4 20 13 1 3\r\n5 19 12 1 4\r\n6 20 13 3 1\r\n7 21 14 1 2\r\n8 20 13 1 7\r\n9 19 12 6 8\r\n10 18 11 5 9\r\n11 17 10 1 10\r\n12 18 11 1 9\r\n13 17 10 1 12\r\n14 16 9 11 13\r\n15 20 13 7 -1\r\n16 21 14 2 -1\r\n17 20 13 16 -3\r\n18 19 12 15 -17\r\n19 21 14 2 1\r\n20 20 13 19 7\r\n21 19 12 6 20\r\n22 18 11 18 21\r\n23 17 10 1 22\r\n24 16 9 23 13\r\n25 18 11 18 9\r\n26 17 10 1 25\r\n27 16 9 26 13\r\n28 15 8 24 27\r\n29 12 7 28 27\r\n30 11 6 28 29\r\n31 11 6 28 27\r\n32 10 5 30 31\r\n33 4 4 14 32\r\n34 3 3 1 33\r\n35 2 2 1 34\r\n36 19 12 1 8\r\n37 18 11 5 36\r\n38 17 10 1 37\r\n39 16 9 38 1\r\n40 19 12 1 20\r\n41 18 11 18 40\r\n42 17 10 1 41\r\n43 16 9 42 1\r\n44 18 11 18 36\r\n45 17 10 1 44\r\n46 16 9 45 1\r\n47 15 8 43 46\r\n48 12 7 47 46\r\n49 11 6 47 48\r\n50 11 6 47 46\r\n51 10 5 49 50\r\n52 4 4 39 51\r\n53 3 3 52 1\r\n54 2 2 1 53\r\n55 1 1 35 54\r\n56 20 13 16 -1\r\n57 21 14 1 -1\r\n58 20 13 1 57\r\n59 19 12 56 -58\r\n60 18 11 59 -9\r\n61 17 10 1 -60\r\n62 19 12 56 -8\r\n63 18 11 62 -9\r\n64 17 10 1 -63\r\n65 16 9 61 64\r\n66 21 14 2 -2\r\n67 20 13 66 1\r\n68 20 13 16 -57\r\n69 19 12 67 68\r\n70 18 11 69 -21\r\n71 17 10 1 -70\r\n72 16 9 71 64\r\n73 18 11 69 -9\r\n74 17 10 1 -73\r\n75 16 9 74 64\r\n76 15 8 72 75\r\n77 12 7 76 75\r\n78 11 6 76 77\r\n79 11 6 76 75\r\n80 10 5 78 79\r\n81 4 4 65 80\r\n82 3 3 1 81\r\n83 2 2 1 82\r\n84 18 11 59 -36\r\n85 17 10 1 -84\r\n86 18 11 62 -1\r\n87 17 10 1 -86\r\n88 16 9 85 87\r\n89 18 11 69 -40\r\n90 17 10 1 -89\r\n91 16 9 90 87\r\n92 18 11 69 -36\r\n93 17 10 1 -92\r\n94 16 9 93 87\r\n95 15 8 91 94\r\n96 12 7 95 94\r\n97 11 6 95 96\r\n98 11 6 95 94\r\n99 10 5 97 98\r\n100 4 4 88 99\r\n101 3 3 100 1\r\n102 2 2 1 101\r\n103 1 1 83 102\r\n104 0 0 55 103\r\n.end\r\n"
  },
  {
    "path": "cudd/dddmp/exp/2and3.bdd",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 61\n.nvars 50\n.nsuppvars 16\n.suppvarnames DUMMY0 DUMMY1 DUMMY2 DUMMY3 DUMMY4 DUMMY10 DUMMY11 DUMMY12 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22\n.orderedvarnames DUMMY0 DUMMY1 DUMMY2 DUMMY3 DUMMY4 DUMMY5 DUMMY6 DUMMY7 DUMMY8 DUMMY9 DUMMY10 DUMMY11 DUMMY12 DUMMY13 DUMMY14 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49\n.ids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\n.permids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\n.auxids 0 1 2 3 4 10 11 12 15 16 17 18 19 20 21 22\n.nroots 1\n.rootids -61\n.nodes\n1 T 1 0 0\n2 22 15 1 -1\n3 21 14 1 2\n4 20 13 3 -1\n5 21 14 2 -1\n6 20 13 5 -1\n7 19 12 4 -6\n8 21 14 2 1\n9 20 13 8 1\n10 19 12 1 9\n11 18 11 7 10\n12 17 10 1 11\n13 16 9 12 1\n14 19 12 4 1\n15 18 11 14 1\n16 17 10 1 15\n17 16 9 16 1\n18 15 8 13 17\n19 18 11 7 1\n20 17 10 1 19\n21 16 9 20 1\n22 15 8 21 17\n23 12 7 18 22\n24 11 6 18 23\n25 11 6 23 22\n26 10 5 24 25\n27 4 4 1 26\n28 3 3 1 27\n29 2 2 1 28\n30 3 3 27 1\n31 2 2 1 30\n32 1 1 29 31\n33 19 12 6 -1\n34 18 11 33 -1\n35 17 10 1 -34\n36 21 14 2 -2\n37 20 13 36 1\n38 19 12 37 6\n39 18 11 38 -10\n40 17 10 1 -39\n41 16 9 40 35\n42 19 12 37 -1\n43 18 11 42 -1\n44 17 10 1 -43\n45 16 9 44 35\n46 15 8 41 45\n47 18 11 38 -1\n48 17 10 1 -47\n49 16 9 48 35\n50 15 8 49 45\n51 12 7 46 50\n52 11 6 46 51\n53 11 6 51 50\n54 10 5 52 53\n55 4 4 35 54\n56 3 3 1 55\n57 2 2 1 56\n58 3 3 55 1\n59 2 2 1 58\n60 1 1 57 59\n61 0 0 32 60\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/3.bdd",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 290\n.nvars 50\n.nsuppvars 17\n.suppvarnames DUMMY0 DUMMY1 DUMMY2 DUMMY3 DUMMY4 DUMMY5 DUMMY10 DUMMY11 DUMMY12 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22\n.ids 0 1 2 3 4 5 10 11 12 15 16 17 18 19 20 21 22\n.permids 0 1 2 3 4 5 10 11 12 15 16 17 18 19 20 21 22\n.auxids 0 1 2 3 4 5 10 11 12 15 16 17 18 19 20 21 22\n.nroots 1\n.rootids -290\n.nodes\n1 T 1 0 0\n2 22 16 1 -1\n3 21 15 2 1\n4 20 14 3 1\n5 19 13 4 1\n6 18 12 1 5\n7 17 11 1 6\n8 20 14 2 1\n9 19 13 8 1\n10 18 12 1 9\n11 17 11 1 10\n12 5 5 7 11\n13 21 15 1 2\n14 20 14 13 -1\n15 21 15 2 -1\n16 20 14 15 -1\n17 19 13 14 -16\n18 20 14 3 -1\n19 21 15 1 -1\n20 20 14 19 -1\n21 19 13 18 -20\n22 18 12 17 21\n23 17 11 1 22\n24 20 14 13 -15\n25 19 13 24 1\n26 20 14 3 -15\n27 19 13 26 1\n28 18 12 25 27\n29 17 11 1 28\n30 16 10 23 29\n31 19 13 14 1\n32 19 13 18 1\n33 18 12 31 32\n34 17 11 1 33\n35 16 10 34 29\n36 15 9 30 35\n37 19 13 18 -16\n38 18 12 17 37\n39 17 11 1 38\n40 16 10 39 29\n41 15 9 40 35\n42 12 8 36 41\n43 11 7 36 42\n44 11 7 42 36\n45 10 6 43 44\n46 20 14 2 -1\n47 19 13 46 -20\n48 18 12 17 47\n49 17 11 1 48\n50 20 14 2 -15\n51 19 13 50 1\n52 18 12 25 51\n53 17 11 1 52\n54 16 10 49 53\n55 19 13 46 1\n56 18 12 31 55\n57 17 11 1 56\n58 16 10 57 53\n59 15 9 54 58\n60 19 13 46 -16\n61 18 12 17 60\n62 17 11 1 61\n63 16 10 62 53\n64 15 9 63 58\n65 12 8 59 64\n66 11 7 59 65\n67 11 7 65 59\n68 10 6 66 67\n69 5 5 45 68\n70 4 4 12 69\n71 21 15 2 -2\n72 20 14 71 1\n73 19 13 72 1\n74 18 12 1 73\n75 17 11 1 74\n76 20 14 1 13\n77 19 13 72 76\n78 18 12 1 77\n79 17 11 1 78\n80 16 10 75 79\n81 20 14 15 1\n82 19 13 81 1\n83 18 12 1 82\n84 17 11 1 83\n85 19 13 81 76\n86 18 12 1 85\n87 17 11 1 86\n88 16 10 84 87\n89 5 5 80 88\n90 20 14 71 -1\n91 19 13 90 -20\n92 18 12 17 91\n93 17 11 1 92\n94 20 14 71 -15\n95 19 13 94 76\n96 18 12 25 95\n97 17 11 1 96\n98 16 10 93 97\n99 19 13 90 1\n100 18 12 31 99\n101 17 11 1 100\n102 16 10 101 97\n103 15 9 98 102\n104 19 13 90 -16\n105 18 12 17 104\n106 17 11 1 105\n107 16 10 106 97\n108 15 9 107 102\n109 12 8 103 108\n110 11 7 103 109\n111 11 7 109 103\n112 10 6 110 111\n113 19 13 16 -20\n114 18 12 17 113\n115 17 11 1 114\n116 20 14 15 -15\n117 19 13 116 76\n118 18 12 25 117\n119 17 11 1 118\n120 16 10 115 119\n121 19 13 16 1\n122 18 12 31 121\n123 17 11 1 122\n124 16 10 123 119\n125 15 9 120 124\n126 19 13 16 -16\n127 18 12 17 126\n128 17 11 1 127\n129 16 10 128 119\n130 15 9 129 124\n131 12 8 125 130\n132 11 7 125 131\n133 11 7 131 125\n134 10 6 132 133\n135 5 5 112 134\n136 4 4 89 135\n137 3 3 70 136\n138 5 5 75 84\n139 19 13 94 1\n140 18 12 25 139\n141 17 11 1 140\n142 16 10 93 141\n143 16 10 101 141\n144 15 9 142 143\n145 16 10 106 141\n146 15 9 145 143\n147 12 8 144 146\n148 11 7 144 147\n149 11 7 147 144\n150 10 6 148 149\n151 19 13 116 1\n152 18 12 25 151\n153 17 11 1 152\n154 16 10 115 153\n155 16 10 123 153\n156 15 9 154 155\n157 16 10 128 153\n158 15 9 157 155\n159 12 8 156 158\n160 11 7 156 159\n161 11 7 159 156\n162 10 6 160 161\n163 5 5 150 162\n164 4 4 138 163\n165 3 3 70 164\n166 2 2 137 165\n167 1 1 70 166\n168 19 13 16 -1\n169 18 12 168 -5\n170 17 11 1 -169\n171 18 12 168 -9\n172 17 11 1 -171\n173 5 5 170 172\n174 19 13 72 16\n175 18 12 174 -21\n176 17 11 1 -175\n177 20 14 71 15\n178 19 13 177 -1\n179 18 12 178 -27\n180 17 11 1 -179\n181 16 10 176 180\n182 19 13 72 -1\n183 18 12 182 -32\n184 17 11 1 -183\n185 16 10 184 180\n186 15 9 181 185\n187 18 12 174 -37\n188 17 11 1 -187\n189 16 10 188 180\n190 15 9 189 185\n191 12 8 186 190\n192 11 7 186 191\n193 11 7 191 186\n194 10 6 192 193\n195 18 12 174 -47\n196 17 11 1 -195\n197 18 12 178 -51\n198 17 11 1 -197\n199 16 10 196 198\n200 18 12 182 -55\n201 17 11 1 -200\n202 16 10 201 198\n203 15 9 199 202\n204 18 12 174 -60\n205 17 11 1 -204\n206 16 10 205 198\n207 15 9 206 202\n208 12 8 203 207\n209 11 7 203 208\n210 11 7 208 203\n211 10 6 209 210\n212 5 5 194 211\n213 4 4 173 212\n214 18 12 168 -73\n215 17 11 1 -214\n216 18 12 168 -77\n217 17 11 1 -216\n218 16 10 215 217\n219 18 12 168 -82\n220 17 11 1 -219\n221 18 12 168 -85\n222 17 11 1 -221\n223 16 10 220 222\n224 5 5 218 223\n225 18 12 174 -91\n226 17 11 1 -225\n227 18 12 178 -95\n228 17 11 1 -227\n229 16 10 226 228\n230 18 12 182 -99\n231 17 11 1 -230\n232 16 10 231 228\n233 15 9 229 232\n234 18 12 174 -104\n235 17 11 1 -234\n236 16 10 235 228\n237 15 9 236 232\n238 12 8 233 237\n239 11 7 233 238\n240 11 7 238 233\n241 10 6 239 240\n242 18 12 174 -113\n243 17 11 1 -242\n244 18 12 178 -117\n245 17 11 1 -244\n246 16 10 243 245\n247 18 12 182 -121\n248 17 11 1 -247\n249 16 10 248 245\n250 15 9 246 249\n251 18 12 174 -126\n252 17 11 1 -251\n253 16 10 252 245\n254 15 9 253 249\n255 12 8 250 254\n256 11 7 250 255\n257 11 7 255 250\n258 10 6 256 257\n259 5 5 241 258\n260 4 4 224 259\n261 3 3 213 260\n262 5 5 215 220\n263 18 12 178 -139\n264 17 11 1 -263\n265 16 10 226 264\n266 16 10 231 264\n267 15 9 265 266\n268 16 10 235 264\n269 15 9 268 266\n270 12 8 267 269\n271 11 7 267 270\n272 11 7 270 267\n273 10 6 271 272\n274 18 12 178 -151\n275 17 11 1 -274\n276 16 10 243 275\n277 16 10 248 275\n278 15 9 276 277\n279 16 10 252 275\n280 15 9 279 277\n281 12 8 278 280\n282 11 7 278 281\n283 11 7 281 278\n284 10 6 282 283\n285 5 5 273 284\n286 4 4 262 285\n287 3 3 213 286\n288 2 2 261 287\n289 1 1 213 288\n290 0 0 167 289\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/4.bdd",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 3\n.nnodes 35\n.nvars 50\n.nsuppvars 15\n.suppvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50\n.orderedvarnames V1 V2 V3 V4 V5 V6 V7 V8 V9 V10 V11 V12 V13 V14 V15 V16 V17 V18 V19 V20 V21 V22 V23 V24 V25 V26 V27 V28 V29 V30 V31 V32 V33 V34 V35 V36 V37 V38 V39 V40 V41 V42 V43 V44 V45 V46 V47 V48 V49 V50\n.ids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.permids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.auxids 3 5 15 17 19 23 43 45 47 73 75 77 95 97 99\n.nroots 1\n.rootids -35\n.nodes\n1 T 1 0 0\n2 V50 14 1 -1\n3 V49 13 1 2\n4 V48 12 3 1\n5 V48 12 1 -1\n6 V48 12 2 1\n7 V39 11 5 -6\n8 V49 13 1 -1\n9 V48 12 8 1\n10 V39 11 9 4\n11 V38 10 7 -10\n12 V37 9 1 -11\n13 V38 10 5 -9\n14 V37 9 1 -13\n15 V24 8 12 14\n16 V37 9 1 -7\n17 V37 9 1 -5\n18 V24 8 16 17\n19 V23 7 15 18\n20 V22 6 19 1\n21 V23 7 14 17\n22 V22 6 21 1\n23 V12 5 20 22\n24 V10 4 23 1\n25 V22 6 18 1\n26 V12 5 20 25\n27 V10 4 26 1\n28 V9 3 24 27\n29 V12 5 20 1\n30 V10 4 29 1\n31 V10 4 20 1\n32 V9 3 30 31\n33 V8 2 28 32\n34 V3 1 4 33\n35 V2 0 1 34\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/4.bdd.bis1",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 35\n.nvars 150\n.nsuppvars 15\n.suppvarnames V3 V8 V23 V24 V37 V39 DUMMY21 DUMMY22 DUMMY23 DUMMY36 DUMMY37 DUMMY38 DUMMY47 DUMMY48 DUMMY49\n.orderedvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49 DUMMY50 DUMMY51 DUMMY52 DUMMY53 DUMMY54 DUMMY55 DUMMY56 DUMMY57 DUMMY58 DUMMY59 DUMMY60 DUMMY61 DUMMY62 DUMMY63 DUMMY64 DUMMY65 DUMMY66 DUMMY67 DUMMY68 DUMMY69 DUMMY70 DUMMY71 DUMMY72 DUMMY73 DUMMY74 DUMMY75 DUMMY76 DUMMY77 DUMMY78 DUMMY79 DUMMY80 DUMMY81 DUMMY82 DUMMY83 DUMMY84 DUMMY85 DUMMY86 DUMMY87 DUMMY88 DUMMY89 DUMMY90 DUMMY91 DUMMY92 DUMMY93 DUMMY94 DUMMY95 DUMMY96 DUMMY97 DUMMY98 DUMMY99 DUMMY100 DUMMY101 DUMMY102 DUMMY103 DUMMY104 DUMMY105 DUMMY106 DUMMY107 DUMMY108 DUMMY109 DUMMY110 DUMMY111 DUMMY112 DUMMY113 DUMMY114 DUMMY115 DUMMY116 DUMMY117 DUMMY118 DUMMY119 DUMMY120 DUMMY121 DUMMY122 DUMMY123 DUMMY124 DUMMY125 DUMMY126 DUMMY127 DUMMY128 DUMMY129 DUMMY130 DUMMY131 DUMMY132 DUMMY133 DUMMY134 DUMMY135 DUMMY136 DUMMY137 DUMMY138 DUMMY139 DUMMY140 DUMMY141 DUMMY142 DUMMY143 DUMMY144 DUMMY145 DUMMY146 DUMMY147 DUMMY148 DUMMY149\n.ids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.permids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.auxids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.nroots 1\n.rootids -35\n.nodes\n1 T 1 0 0\n2 49 14 1 -1\n3 48 13 1 2\n4 47 12 3 1\n5 47 12 1 -1\n6 47 12 2 1\n7 38 11 5 -6\n8 48 13 1 -1\n9 47 12 8 1\n10 38 11 9 4\n11 37 10 7 -10\n12 36 9 1 -11\n13 37 10 5 -9\n14 36 9 1 -13\n15 23 8 12 14\n16 36 9 1 -7\n17 36 9 1 -5\n18 23 8 16 17\n19 22 7 15 18\n20 21 6 19 1\n21 22 7 14 17\n22 21 6 21 1\n23 11 5 20 22\n24 9 4 23 1\n25 21 6 18 1\n26 11 5 20 25\n27 9 4 26 1\n28 8 3 24 27\n29 11 5 20 1\n30 9 4 29 1\n31 9 4 20 1\n32 8 3 30 31\n33 7 2 28 32\n34 2 1 4 33\n35 1 0 1 34\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/4.bdd.bis2",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 35\n.nvars 150\n.nsuppvars 15\n.suppvarnames V3 V8 V23 V24 V37 V39 DUMMY21 DUMMY22 DUMMY23 DUMMY36 DUMMY37 DUMMY38 DUMMY47 DUMMY48 DUMMY49\n.orderedvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49 DUMMY50 DUMMY51 DUMMY52 DUMMY53 DUMMY54 DUMMY55 DUMMY56 DUMMY57 DUMMY58 DUMMY59 DUMMY60 DUMMY61 DUMMY62 DUMMY63 DUMMY64 DUMMY65 DUMMY66 DUMMY67 DUMMY68 DUMMY69 DUMMY70 DUMMY71 DUMMY72 DUMMY73 DUMMY74 DUMMY75 DUMMY76 DUMMY77 DUMMY78 DUMMY79 DUMMY80 DUMMY81 DUMMY82 DUMMY83 DUMMY84 DUMMY85 DUMMY86 DUMMY87 DUMMY88 DUMMY89 DUMMY90 DUMMY91 DUMMY92 DUMMY93 DUMMY94 DUMMY95 DUMMY96 DUMMY97 DUMMY98 DUMMY99 DUMMY100 DUMMY101 DUMMY102 DUMMY103 DUMMY104 DUMMY105 DUMMY106 DUMMY107 DUMMY108 DUMMY109 DUMMY110 DUMMY111 DUMMY112 DUMMY113 DUMMY114 DUMMY115 DUMMY116 DUMMY117 DUMMY118 DUMMY119 DUMMY120 DUMMY121 DUMMY122 DUMMY123 DUMMY124 DUMMY125 DUMMY126 DUMMY127 DUMMY128 DUMMY129 DUMMY130 DUMMY131 DUMMY132 DUMMY133 DUMMY134 DUMMY135 DUMMY136 DUMMY137 DUMMY138 DUMMY139 DUMMY140 DUMMY141 DUMMY142 DUMMY143 DUMMY144 DUMMY145 DUMMY146 DUMMY147 DUMMY148 DUMMY149\n.ids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.permids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.auxids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.nroots 1\n.rootids -35\n.nodes\n1 T 1 0 0\n2 49 14 1 -1\n3 48 13 1 2\n4 47 12 3 1\n5 47 12 1 -1\n6 47 12 2 1\n7 38 11 5 -6\n8 48 13 1 -1\n9 47 12 8 1\n10 38 11 9 4\n11 37 10 7 -10\n12 36 9 1 -11\n13 37 10 5 -9\n14 36 9 1 -13\n15 23 8 12 14\n16 36 9 1 -7\n17 36 9 1 -5\n18 23 8 16 17\n19 22 7 15 18\n20 21 6 19 1\n21 22 7 14 17\n22 21 6 21 1\n23 11 5 20 22\n24 9 4 23 1\n25 21 6 18 1\n26 11 5 20 25\n27 9 4 26 1\n28 8 3 24 27\n29 11 5 20 1\n30 9 4 29 1\n31 9 4 20 1\n32 8 3 30 31\n33 7 2 28 32\n34 2 1 4 33\n35 1 0 1 34\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/4.bdd.bis3",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 35\n.nvars 150\n.nsuppvars 15\n.suppvarnames V3 V8 V23 V24 V37 V39 DUMMY21 DUMMY22 DUMMY23 DUMMY36 DUMMY37 DUMMY38 DUMMY47 DUMMY48 DUMMY49\n.orderedvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49 DUMMY50 DUMMY51 DUMMY52 DUMMY53 DUMMY54 DUMMY55 DUMMY56 DUMMY57 DUMMY58 DUMMY59 DUMMY60 DUMMY61 DUMMY62 DUMMY63 DUMMY64 DUMMY65 DUMMY66 DUMMY67 DUMMY68 DUMMY69 DUMMY70 DUMMY71 DUMMY72 DUMMY73 DUMMY74 DUMMY75 DUMMY76 DUMMY77 DUMMY78 DUMMY79 DUMMY80 DUMMY81 DUMMY82 DUMMY83 DUMMY84 DUMMY85 DUMMY86 DUMMY87 DUMMY88 DUMMY89 DUMMY90 DUMMY91 DUMMY92 DUMMY93 DUMMY94 DUMMY95 DUMMY96 DUMMY97 DUMMY98 DUMMY99 DUMMY100 DUMMY101 DUMMY102 DUMMY103 DUMMY104 DUMMY105 DUMMY106 DUMMY107 DUMMY108 DUMMY109 DUMMY110 DUMMY111 DUMMY112 DUMMY113 DUMMY114 DUMMY115 DUMMY116 DUMMY117 DUMMY118 DUMMY119 DUMMY120 DUMMY121 DUMMY122 DUMMY123 DUMMY124 DUMMY125 DUMMY126 DUMMY127 DUMMY128 DUMMY129 DUMMY130 DUMMY131 DUMMY132 DUMMY133 DUMMY134 DUMMY135 DUMMY136 DUMMY137 DUMMY138 DUMMY139 DUMMY140 DUMMY141 DUMMY142 DUMMY143 DUMMY144 DUMMY145 DUMMY146 DUMMY147 DUMMY148 DUMMY149\n.ids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.permids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.auxids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.nroots 1\n.rootids -35\n.nodes\n1 T 1 0 0\n2 49 14 1 -1\n3 48 13 1 2\n4 47 12 3 1\n5 47 12 1 -1\n6 47 12 2 1\n7 38 11 5 -6\n8 48 13 1 -1\n9 47 12 8 1\n10 38 11 9 4\n11 37 10 7 -10\n12 36 9 1 -11\n13 37 10 5 -9\n14 36 9 1 -13\n15 23 8 12 14\n16 36 9 1 -7\n17 36 9 1 -5\n18 23 8 16 17\n19 22 7 15 18\n20 21 6 19 1\n21 22 7 14 17\n22 21 6 21 1\n23 11 5 20 22\n24 9 4 23 1\n25 21 6 18 1\n26 11 5 20 25\n27 9 4 26 1\n28 8 3 24 27\n29 11 5 20 1\n30 9 4 29 1\n31 9 4 20 1\n32 8 3 30 31\n33 7 2 28 32\n34 2 1 4 33\n35 1 0 1 34\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/4.bdd.bis4",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 35\n.nvars 150\n.nsuppvars 15\n.suppvarnames V3 V8 V23 V24 V37 V39 DUMMY21 DUMMY22 DUMMY23 DUMMY36 DUMMY37 DUMMY38 DUMMY47 DUMMY48 DUMMY49\n.orderedvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49 DUMMY50 DUMMY51 DUMMY52 DUMMY53 DUMMY54 DUMMY55 DUMMY56 DUMMY57 DUMMY58 DUMMY59 DUMMY60 DUMMY61 DUMMY62 DUMMY63 DUMMY64 DUMMY65 DUMMY66 DUMMY67 DUMMY68 DUMMY69 DUMMY70 DUMMY71 DUMMY72 DUMMY73 DUMMY74 DUMMY75 DUMMY76 DUMMY77 DUMMY78 DUMMY79 DUMMY80 DUMMY81 DUMMY82 DUMMY83 DUMMY84 DUMMY85 DUMMY86 DUMMY87 DUMMY88 DUMMY89 DUMMY90 DUMMY91 DUMMY92 DUMMY93 DUMMY94 DUMMY95 DUMMY96 DUMMY97 DUMMY98 DUMMY99 DUMMY100 DUMMY101 DUMMY102 DUMMY103 DUMMY104 DUMMY105 DUMMY106 DUMMY107 DUMMY108 DUMMY109 DUMMY110 DUMMY111 DUMMY112 DUMMY113 DUMMY114 DUMMY115 DUMMY116 DUMMY117 DUMMY118 DUMMY119 DUMMY120 DUMMY121 DUMMY122 DUMMY123 DUMMY124 DUMMY125 DUMMY126 DUMMY127 DUMMY128 DUMMY129 DUMMY130 DUMMY131 DUMMY132 DUMMY133 DUMMY134 DUMMY135 DUMMY136 DUMMY137 DUMMY138 DUMMY139 DUMMY140 DUMMY141 DUMMY142 DUMMY143 DUMMY144 DUMMY145 DUMMY146 DUMMY147 DUMMY148 DUMMY149\n.ids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.permids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.auxids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.nroots 1\n.rootids -35\n.nodes\n1 T 1 0 0\n2 49 14 1 -1\n3 48 13 1 2\n4 47 12 3 1\n5 47 12 1 -1\n6 47 12 2 1\n7 38 11 5 -6\n8 48 13 1 -1\n9 47 12 8 1\n10 38 11 9 4\n11 37 10 7 -10\n12 36 9 1 -11\n13 37 10 5 -9\n14 36 9 1 -13\n15 23 8 12 14\n16 36 9 1 -7\n17 36 9 1 -5\n18 23 8 16 17\n19 22 7 15 18\n20 21 6 19 1\n21 22 7 14 17\n22 21 6 21 1\n23 11 5 20 22\n24 9 4 23 1\n25 21 6 18 1\n26 11 5 20 25\n27 9 4 26 1\n28 8 3 24 27\n29 11 5 20 1\n30 9 4 29 1\n31 9 4 20 1\n32 8 3 30 31\n33 7 2 28 32\n34 2 1 4 33\n35 1 0 1 34\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/4.cnf",
    "content": "c # BDD stored by the DDDMP tool in CNF format\nc #\nc # Warning: AUX IDs missing ... equal to BDD IDs.\nc #\nc .ver DDDMP-2.0\nc .nnodes 35\nc .nvars 50\nc .nsuppvars 15\nc .suppvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50\nc .orderedvarnames V1 V2 V3 V4 V5 V6 V7 V8 V9 V10 V11 V12 V13 V14 V15 V16 V17 V18 V19 V20 V21 V22 V23 V24 V25 V26 V27 V28 V29 V30 V31 V32 V33 V34 V35 V36 V37 V38 V39 V40 V41 V42 V43 V44 V45 V46 V47 V48 V49 V50\nc .ids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .permids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .auxids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .cnfids  2 3 8 9 10 12 22 23 24 37 38 39 48 49 50\nc .nroots 1\nc .rootids 1         \nc .nAddedCnfVar 31\nc #\nc # Init CNF Clauses\nc #\np cnf 130 108              \n100 -49 0\n100 -50 0\n-100 49 50 0\n101 48 0\n101 -100 0\n-101 -48 100 0\n102 48 0\n102 -50 0\n-102 -48 50 0\n103 39 102 0\n-103 39 -102 0\n103 -39 -48 0\n-103 -39 48 0\n104 48 0\n104 -49 0\n-104 -48 49 0\n105 39 -101 0\n-105 39 101 0\n105 -39 -104 0\n-105 -39 104 0\n106 38 105 0\n-106 38 -105 0\n106 -38 -103 0\n-106 -38 103 0\n107 -37 0\n107 106 0\n-107 37 -106 0\n108 38 104 0\n-108 38 -104 0\n108 -38 -48 0\n-108 -38 48 0\n109 -37 0\n109 108 0\n-109 37 -108 0\n110 24 -109 0\n-110 24 109 0\n110 -24 -107 0\n-110 -24 107 0\n111 -37 0\n111 103 0\n-111 37 -103 0\n112 -37 0\n112 48 0\n-112 37 -48 0\n113 24 -112 0\n-113 24 112 0\n113 -24 -111 0\n-113 -24 111 0\n114 23 -113 0\n-114 23 113 0\n114 -23 -110 0\n-114 -23 110 0\n115 22 0\n115 -114 0\n-115 -22 114 0\n116 23 -112 0\n-116 23 112 0\n116 -23 -109 0\n-116 -23 109 0\n117 22 0\n117 -116 0\n-117 -22 116 0\n118 12 -117 0\n-118 12 117 0\n118 -12 -115 0\n-118 -12 115 0\n119 10 0\n119 -118 0\n-119 -10 118 0\n120 22 0\n120 -113 0\n-120 -22 113 0\n121 12 -120 0\n-121 12 120 0\n121 -12 -115 0\n-121 -12 115 0\n122 10 0\n122 -121 0\n-122 -10 121 0\n123 9 -122 0\n-123 9 122 0\n123 -9 -119 0\n-123 -9 119 0\n124 12 0\n124 -115 0\n-124 -12 115 0\n125 10 0\n125 -124 0\n-125 -10 124 0\n126 10 0\n126 -115 0\n-126 -10 115 0\n127 9 -126 0\n-127 9 126 0\n127 -9 -125 0\n-127 -9 125 0\n128 8 -127 0\n-128 8 127 0\n128 -8 -123 0\n-128 -8 123 0\n129 3 -128 0\n-129 3 128 0\n129 -3 -101 0\n-129 -3 101 0\n130 -2 0\n130 -129 0\n-130 2 129 0\n-130 0\nc # End of Cnf From dddmp-2.0\n"
  },
  {
    "path": "cudd/dddmp/exp/4.cnf.bis",
    "content": "c # BDD stored by the DDDMP tool in CNF format\nc #\nc # Warning: AUX IDs missing ... equal to BDD IDs.\nc #\nc .ver DDDMP-2.0\nc .nnodes 35\nc .nvars 150\nc .nsuppvars 15\nc .suppvarnames V3 V8 V23 V24 V37 V39 DUMMY21 DUMMY22 DUMMY23 DUMMY36 DUMMY37 DUMMY38 DUMMY47 DUMMY48 DUMMY49\nc .orderedvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49 DUMMY50 DUMMY51 DUMMY52 DUMMY53 DUMMY54 DUMMY55 DUMMY56 DUMMY57 DUMMY58 DUMMY59 DUMMY60 DUMMY61 DUMMY62 DUMMY63 DUMMY64 DUMMY65 DUMMY66 DUMMY67 DUMMY68 DUMMY69 DUMMY70 DUMMY71 DUMMY72 DUMMY73 DUMMY74 DUMMY75 DUMMY76 DUMMY77 DUMMY78 DUMMY79 DUMMY80 DUMMY81 DUMMY82 DUMMY83 DUMMY84 DUMMY85 DUMMY86 DUMMY87 DUMMY88 DUMMY89 DUMMY90 DUMMY91 DUMMY92 DUMMY93 DUMMY94 DUMMY95 DUMMY96 DUMMY97 DUMMY98 DUMMY99 DUMMY100 DUMMY101 DUMMY102 DUMMY103 DUMMY104 DUMMY105 DUMMY106 DUMMY107 DUMMY108 DUMMY109 DUMMY110 DUMMY111 DUMMY112 DUMMY113 DUMMY114 DUMMY115 DUMMY116 DUMMY117 DUMMY118 DUMMY119 DUMMY120 DUMMY121 DUMMY122 DUMMY123 DUMMY124 DUMMY125 DUMMY126 DUMMY127 DUMMY128 DUMMY129 DUMMY130 DUMMY131 DUMMY132 DUMMY133 DUMMY134 DUMMY135 DUMMY136 DUMMY137 DUMMY138 DUMMY139 DUMMY140 DUMMY141 DUMMY142 DUMMY143 DUMMY144 DUMMY145 DUMMY146 DUMMY147 DUMMY148 DUMMY149\nc .ids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .permids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .auxids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .cnfids  2 3 8 9 10 12 22 23 24 37 38 39 48 49 50\nc .nroots 1\nc .rootids 1         \nc .nAddedCnfVar 31\nc #\nc # Init CNF Clauses\nc #\np cnf 130 108              \n100 -49 0\n100 -50 0\n-100 49 50 0\n101 48 0\n101 -100 0\n-101 -48 100 0\n102 48 0\n102 -50 0\n-102 -48 50 0\n103 39 102 0\n-103 39 -102 0\n103 -39 -48 0\n-103 -39 48 0\n104 48 0\n104 -49 0\n-104 -48 49 0\n105 39 -101 0\n-105 39 101 0\n105 -39 -104 0\n-105 -39 104 0\n106 38 105 0\n-106 38 -105 0\n106 -38 -103 0\n-106 -38 103 0\n107 -37 0\n107 106 0\n-107 37 -106 0\n108 38 104 0\n-108 38 -104 0\n108 -38 -48 0\n-108 -38 48 0\n109 -37 0\n109 108 0\n-109 37 -108 0\n110 24 -109 0\n-110 24 109 0\n110 -24 -107 0\n-110 -24 107 0\n111 -37 0\n111 103 0\n-111 37 -103 0\n112 -37 0\n112 48 0\n-112 37 -48 0\n113 24 -112 0\n-113 24 112 0\n113 -24 -111 0\n-113 -24 111 0\n114 23 -113 0\n-114 23 113 0\n114 -23 -110 0\n-114 -23 110 0\n115 22 0\n115 -114 0\n-115 -22 114 0\n116 23 -112 0\n-116 23 112 0\n116 -23 -109 0\n-116 -23 109 0\n117 22 0\n117 -116 0\n-117 -22 116 0\n118 12 -117 0\n-118 12 117 0\n118 -12 -115 0\n-118 -12 115 0\n119 10 0\n119 -118 0\n-119 -10 118 0\n120 22 0\n120 -113 0\n-120 -22 113 0\n121 12 -120 0\n-121 12 120 0\n121 -12 -115 0\n-121 -12 115 0\n122 10 0\n122 -121 0\n-122 -10 121 0\n123 9 -122 0\n-123 9 122 0\n123 -9 -119 0\n-123 -9 119 0\n124 12 0\n124 -115 0\n-124 -12 115 0\n125 10 0\n125 -124 0\n-125 -10 124 0\n126 10 0\n126 -115 0\n-126 -10 115 0\n127 9 -126 0\n-127 9 126 0\n127 -9 -125 0\n-127 -9 125 0\n128 8 -127 0\n-128 8 127 0\n128 -8 -123 0\n-128 -8 123 0\n129 3 -128 0\n-129 3 128 0\n129 -3 -101 0\n-129 -3 101 0\n130 -2 0\n130 -129 0\n-130 2 129 0\n-130 0\nc # End of Cnf From dddmp-2.0\n"
  },
  {
    "path": "cudd/dddmp/exp/4.max1",
    "content": "c # BDD stored by the DDDMP tool in CNF format\nc #\nc # Warning: AUX IDs missing ... equal to BDD IDs.\nc #\nc .ver DDDMP-2.0\nc .nnodes 35\nc .nvars 150\nc .nsuppvars 15\nc .suppvarnames V3 V8 V23 V24 V37 V39 DUMMY21 DUMMY22 DUMMY23 DUMMY36 DUMMY37 DUMMY38 DUMMY47 DUMMY48 DUMMY49\nc .orderedvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49 DUMMY50 DUMMY51 DUMMY52 DUMMY53 DUMMY54 DUMMY55 DUMMY56 DUMMY57 DUMMY58 DUMMY59 DUMMY60 DUMMY61 DUMMY62 DUMMY63 DUMMY64 DUMMY65 DUMMY66 DUMMY67 DUMMY68 DUMMY69 DUMMY70 DUMMY71 DUMMY72 DUMMY73 DUMMY74 DUMMY75 DUMMY76 DUMMY77 DUMMY78 DUMMY79 DUMMY80 DUMMY81 DUMMY82 DUMMY83 DUMMY84 DUMMY85 DUMMY86 DUMMY87 DUMMY88 DUMMY89 DUMMY90 DUMMY91 DUMMY92 DUMMY93 DUMMY94 DUMMY95 DUMMY96 DUMMY97 DUMMY98 DUMMY99 DUMMY100 DUMMY101 DUMMY102 DUMMY103 DUMMY104 DUMMY105 DUMMY106 DUMMY107 DUMMY108 DUMMY109 DUMMY110 DUMMY111 DUMMY112 DUMMY113 DUMMY114 DUMMY115 DUMMY116 DUMMY117 DUMMY118 DUMMY119 DUMMY120 DUMMY121 DUMMY122 DUMMY123 DUMMY124 DUMMY125 DUMMY126 DUMMY127 DUMMY128 DUMMY129 DUMMY130 DUMMY131 DUMMY132 DUMMY133 DUMMY134 DUMMY135 DUMMY136 DUMMY137 DUMMY138 DUMMY139 DUMMY140 DUMMY141 DUMMY142 DUMMY143 DUMMY144 DUMMY145 DUMMY146 DUMMY147 DUMMY148 DUMMY149\nc .ids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .permids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .auxids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .cnfids  2 3 8 9 10 12 22 23 24 37 38 39 48 49 50\nc .nroots 1\nc .rootids 1         \nc .nAddedCnfVar 0\nc #\nc # Init CNF Clauses\nc #\np cnf 50 103               \n3 8 9 10 0\n3 8 9 22 0\n3 8 9 23 24 48 0\n3 8 9 23 24 -37 0\n3 8 9 23 -24 39 48 0\n3 8 9 23 -24 39 -50 0\n3 8 9 23 -24 -39 48 0\n3 8 9 23 -24 -37 0\n3 8 9 -23 24 38 48 0\n3 8 9 -23 24 38 -49 0\n3 8 9 -23 24 -38 48 0\n3 8 9 -23 24 -37 0\n3 8 9 -23 -24 38 39 48 0\n3 8 9 -23 -24 38 39 -50 0\n3 8 9 -23 -24 38 39 -49 0\n3 8 9 -23 -24 38 -39 48 0\n3 8 9 -23 -24 38 -39 -49 0\n3 8 9 -23 -24 -38 39 48 0\n3 8 9 -23 -24 -38 39 -50 0\n3 8 9 -23 -24 -38 -39 48 0\n3 8 9 -23 -24 -37 0\n3 8 -9 10 0\n3 8 -9 12 0\n3 8 -9 22 0\n3 8 -9 23 24 48 0\n3 8 -9 23 24 -37 0\n3 8 -9 23 -24 39 48 0\n3 8 -9 23 -24 39 -50 0\n3 8 -9 23 -24 -39 48 0\n3 8 -9 23 -24 -37 0\n3 8 -9 -23 24 38 48 0\n3 8 -9 -23 24 38 -49 0\n3 8 -9 -23 24 -38 48 0\n3 8 -9 -23 24 -37 0\n3 8 -9 -23 -24 38 39 48 0\n3 8 -9 -23 -24 38 39 -50 0\n3 8 -9 -23 -24 38 39 -49 0\n3 8 -9 -23 -24 38 -39 48 0\n3 8 -9 -23 -24 38 -39 -49 0\n3 8 -9 -23 -24 -38 39 48 0\n3 8 -9 -23 -24 -38 39 -50 0\n3 8 -9 -23 -24 -38 -39 48 0\n3 8 -9 -23 -24 -37 0\n3 -8 9 10 0\n3 -8 9 12 22 0\n3 -8 9 12 24 48 0\n3 -8 9 12 24 -37 0\n3 -8 9 12 -24 39 48 0\n3 -8 9 12 -24 39 -50 0\n3 -8 9 12 -24 -39 48 0\n3 -8 9 12 -24 -37 0\n3 -8 9 -12 22 0\n3 -8 9 -12 23 24 48 0\n3 -8 9 -12 23 24 -37 0\n3 -8 9 -12 23 -24 39 48 0\n3 -8 9 -12 23 -24 39 -50 0\n3 -8 9 -12 23 -24 -39 48 0\n3 -8 9 -12 23 -24 -37 0\n3 -8 9 -12 -23 24 38 48 0\n3 -8 9 -12 -23 24 38 -49 0\n3 -8 9 -12 -23 24 -38 48 0\n3 -8 9 -12 -23 24 -37 0\n3 -8 9 -12 -23 -24 38 39 48 0\n3 -8 9 -12 -23 -24 38 39 -50 0\n3 -8 9 -12 -23 -24 38 39 -49 0\n3 -8 9 -12 -23 -24 38 -39 48 0\n3 -8 9 -12 -23 -24 38 -39 -49 0\n3 -8 9 -12 -23 -24 -38 39 48 0\n3 -8 9 -12 -23 -24 -38 39 -50 0\n3 -8 9 -12 -23 -24 -38 -39 48 0\n3 -8 9 -12 -23 -24 -37 0\n3 -8 -9 10 0\n3 -8 -9 12 22 0\n3 -8 -9 12 23 48 0\n3 -8 -9 12 23 -37 0\n3 -8 -9 12 -23 38 48 0\n3 -8 -9 12 -23 38 -49 0\n3 -8 -9 12 -23 -38 48 0\n3 -8 -9 12 -23 -37 0\n3 -8 -9 -12 22 0\n3 -8 -9 -12 23 24 48 0\n3 -8 -9 -12 23 24 -37 0\n3 -8 -9 -12 23 -24 39 48 0\n3 -8 -9 -12 23 -24 39 -50 0\n3 -8 -9 -12 23 -24 -39 48 0\n3 -8 -9 -12 23 -24 -37 0\n3 -8 -9 -12 -23 24 38 48 0\n3 -8 -9 -12 -23 24 38 -49 0\n3 -8 -9 -12 -23 24 -38 48 0\n3 -8 -9 -12 -23 24 -37 0\n3 -8 -9 -12 -23 -24 38 39 48 0\n3 -8 -9 -12 -23 -24 38 39 -50 0\n3 -8 -9 -12 -23 -24 38 39 -49 0\n3 -8 -9 -12 -23 -24 38 -39 48 0\n3 -8 -9 -12 -23 -24 38 -39 -49 0\n3 -8 -9 -12 -23 -24 -38 39 48 0\n3 -8 -9 -12 -23 -24 -38 39 -50 0\n3 -8 -9 -12 -23 -24 -38 -39 48 0\n3 -8 -9 -12 -23 -24 -37 0\n-3 48 0\n-3 -50 0\n-3 -49 0\n-2 0\nc # End of Cnf From dddmp-2.0\n"
  },
  {
    "path": "cudd/dddmp/exp/4.max2",
    "content": "c # BDD stored by the DDDMP tool in CNF format\nc #\nc # Warning: AUX IDs missing ... equal to BDD IDs.\nc #\nc .ver DDDMP-2.0\nc .nnodes 35\nc .nvars 150\nc .nsuppvars 15\nc .suppvarnames V3 V8 V23 V24 V37 V39 DUMMY21 DUMMY22 DUMMY23 DUMMY36 DUMMY37 DUMMY38 DUMMY47 DUMMY48 DUMMY49\nc .orderedvarnames V2 V3 V8 V9 V10 V12 V22 V23 V24 V37 V38 V39 V48 V49 V50 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49 DUMMY50 DUMMY51 DUMMY52 DUMMY53 DUMMY54 DUMMY55 DUMMY56 DUMMY57 DUMMY58 DUMMY59 DUMMY60 DUMMY61 DUMMY62 DUMMY63 DUMMY64 DUMMY65 DUMMY66 DUMMY67 DUMMY68 DUMMY69 DUMMY70 DUMMY71 DUMMY72 DUMMY73 DUMMY74 DUMMY75 DUMMY76 DUMMY77 DUMMY78 DUMMY79 DUMMY80 DUMMY81 DUMMY82 DUMMY83 DUMMY84 DUMMY85 DUMMY86 DUMMY87 DUMMY88 DUMMY89 DUMMY90 DUMMY91 DUMMY92 DUMMY93 DUMMY94 DUMMY95 DUMMY96 DUMMY97 DUMMY98 DUMMY99 DUMMY100 DUMMY101 DUMMY102 DUMMY103 DUMMY104 DUMMY105 DUMMY106 DUMMY107 DUMMY108 DUMMY109 DUMMY110 DUMMY111 DUMMY112 DUMMY113 DUMMY114 DUMMY115 DUMMY116 DUMMY117 DUMMY118 DUMMY119 DUMMY120 DUMMY121 DUMMY122 DUMMY123 DUMMY124 DUMMY125 DUMMY126 DUMMY127 DUMMY128 DUMMY129 DUMMY130 DUMMY131 DUMMY132 DUMMY133 DUMMY134 DUMMY135 DUMMY136 DUMMY137 DUMMY138 DUMMY139 DUMMY140 DUMMY141 DUMMY142 DUMMY143 DUMMY144 DUMMY145 DUMMY146 DUMMY147 DUMMY148 DUMMY149\nc .ids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .permids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .auxids  1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\nc .cnfids  2 3 8 9 10 12 22 23 24 37 38 39 48 49 50\nc .nroots 1\nc .rootids 1         \nc .nAddedCnfVar 0\nc #\nc # Init CNF Clauses\nc #\np cnf 50 103               \n3 8 9 10 0\n3 8 9 22 0\n3 8 9 23 24 48 0\n3 8 9 23 24 -37 0\n3 8 9 23 -24 39 48 0\n3 8 9 23 -24 39 -50 0\n3 8 9 23 -24 -39 48 0\n3 8 9 23 -24 -37 0\n3 8 9 -23 24 38 48 0\n3 8 9 -23 24 38 -49 0\n3 8 9 -23 24 -38 48 0\n3 8 9 -23 24 -37 0\n3 8 9 -23 -24 38 39 48 0\n3 8 9 -23 -24 38 39 -50 0\n3 8 9 -23 -24 38 39 -49 0\n3 8 9 -23 -24 38 -39 48 0\n3 8 9 -23 -24 38 -39 -49 0\n3 8 9 -23 -24 -38 39 48 0\n3 8 9 -23 -24 -38 39 -50 0\n3 8 9 -23 -24 -38 -39 48 0\n3 8 9 -23 -24 -37 0\n3 8 -9 10 0\n3 8 -9 12 0\n3 8 -9 22 0\n3 8 -9 23 24 48 0\n3 8 -9 23 24 -37 0\n3 8 -9 23 -24 39 48 0\n3 8 -9 23 -24 39 -50 0\n3 8 -9 23 -24 -39 48 0\n3 8 -9 23 -24 -37 0\n3 8 -9 -23 24 38 48 0\n3 8 -9 -23 24 38 -49 0\n3 8 -9 -23 24 -38 48 0\n3 8 -9 -23 24 -37 0\n3 8 -9 -23 -24 38 39 48 0\n3 8 -9 -23 -24 38 39 -50 0\n3 8 -9 -23 -24 38 39 -49 0\n3 8 -9 -23 -24 38 -39 48 0\n3 8 -9 -23 -24 38 -39 -49 0\n3 8 -9 -23 -24 -38 39 48 0\n3 8 -9 -23 -24 -38 39 -50 0\n3 8 -9 -23 -24 -38 -39 48 0\n3 8 -9 -23 -24 -37 0\n3 -8 9 10 0\n3 -8 9 12 22 0\n3 -8 9 12 24 48 0\n3 -8 9 12 24 -37 0\n3 -8 9 12 -24 39 48 0\n3 -8 9 12 -24 39 -50 0\n3 -8 9 12 -24 -39 48 0\n3 -8 9 12 -24 -37 0\n3 -8 9 -12 22 0\n3 -8 9 -12 23 24 48 0\n3 -8 9 -12 23 24 -37 0\n3 -8 9 -12 23 -24 39 48 0\n3 -8 9 -12 23 -24 39 -50 0\n3 -8 9 -12 23 -24 -39 48 0\n3 -8 9 -12 23 -24 -37 0\n3 -8 9 -12 -23 24 38 48 0\n3 -8 9 -12 -23 24 38 -49 0\n3 -8 9 -12 -23 24 -38 48 0\n3 -8 9 -12 -23 24 -37 0\n3 -8 9 -12 -23 -24 38 39 48 0\n3 -8 9 -12 -23 -24 38 39 -50 0\n3 -8 9 -12 -23 -24 38 39 -49 0\n3 -8 9 -12 -23 -24 38 -39 48 0\n3 -8 9 -12 -23 -24 38 -39 -49 0\n3 -8 9 -12 -23 -24 -38 39 48 0\n3 -8 9 -12 -23 -24 -38 39 -50 0\n3 -8 9 -12 -23 -24 -38 -39 48 0\n3 -8 9 -12 -23 -24 -37 0\n3 -8 -9 10 0\n3 -8 -9 12 22 0\n3 -8 -9 12 23 48 0\n3 -8 -9 12 23 -37 0\n3 -8 -9 12 -23 38 48 0\n3 -8 -9 12 -23 38 -49 0\n3 -8 -9 12 -23 -38 48 0\n3 -8 -9 12 -23 -37 0\n3 -8 -9 -12 22 0\n3 -8 -9 -12 23 24 48 0\n3 -8 -9 -12 23 24 -37 0\n3 -8 -9 -12 23 -24 39 48 0\n3 -8 -9 -12 23 -24 39 -50 0\n3 -8 -9 -12 23 -24 -39 48 0\n3 -8 -9 -12 23 -24 -37 0\n3 -8 -9 -12 -23 24 38 48 0\n3 -8 -9 -12 -23 24 38 -49 0\n3 -8 -9 -12 -23 24 -38 48 0\n3 -8 -9 -12 -23 24 -37 0\n3 -8 -9 -12 -23 -24 38 39 48 0\n3 -8 -9 -12 -23 -24 38 39 -50 0\n3 -8 -9 -12 -23 -24 38 39 -49 0\n3 -8 -9 -12 -23 -24 38 -39 48 0\n3 -8 -9 -12 -23 -24 38 -39 -49 0\n3 -8 -9 -12 -23 -24 -38 39 48 0\n3 -8 -9 -12 -23 -24 -38 39 -50 0\n3 -8 -9 -12 -23 -24 -38 -39 48 0\n3 -8 -9 -12 -23 -24 -37 0\n-3 48 0\n-3 -50 0\n-3 -49 0\n-2 0\nc # End of Cnf From dddmp-2.0\n"
  },
  {
    "path": "cudd/dddmp/exp/4bis.bdd",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 3\n.nnodes 35\n.nvars 50\n.nsuppvars 15\n.ids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.permids 1 2 7 8 9 11 21 22 23 36 37 38 47 48 49\n.nroots 1\n.rootids -35\n.nodes\n1 1 0 0\n2 14 1 -1\n3 13 1 2\n4 12 3 1\n5 12 1 -1\n6 12 2 1\n7 11 5 -6\n8 13 1 -1\n9 12 8 1\n10 11 9 4\n11 10 7 -10\n12 9 1 -11\n13 10 5 -9\n14 9 1 -13\n15 8 12 14\n16 9 1 -7\n17 9 1 -5\n18 8 16 17\n19 7 15 18\n20 6 19 1\n21 7 14 17\n22 6 21 1\n23 5 20 22\n24 4 23 1\n25 6 18 1\n26 5 20 25\n27 4 26 1\n28 3 24 27\n29 5 20 1\n30 4 29 1\n31 4 20 1\n32 3 30 31\n33 2 28 32\n34 1 4 33\n35 0 1 34\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/4xor5.bdd",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 105\n.nvars 50\n.nsuppvars 18\n.suppvarnames DUMMY1 DUMMY2 DUMMY7 DUMMY8 DUMMY9 DUMMY11 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY36 DUMMY37 DUMMY38 DUMMY47 DUMMY48 DUMMY49\n.orderedvarnames DUMMY0 DUMMY1 DUMMY2 DUMMY3 DUMMY4 DUMMY5 DUMMY6 DUMMY7 DUMMY8 DUMMY9 DUMMY10 DUMMY11 DUMMY12 DUMMY13 DUMMY14 DUMMY15 DUMMY16 DUMMY17 DUMMY18 DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24 DUMMY25 DUMMY26 DUMMY27 DUMMY28 DUMMY29 DUMMY30 DUMMY31 DUMMY32 DUMMY33 DUMMY34 DUMMY35 DUMMY36 DUMMY37 DUMMY38 DUMMY39 DUMMY40 DUMMY41 DUMMY42 DUMMY43 DUMMY44 DUMMY45 DUMMY46 DUMMY47 DUMMY48 DUMMY49\n.ids 1 2 7 8 9 11 19 20 21 22 23 24 36 37 38 47 48 49\n.permids 1 2 7 8 9 11 19 20 21 22 23 24 36 37 38 47 48 49\n.auxids 1 2 7 8 9 11 19 20 21 22 23 24 36 37 38 47 48 49\n.nroots 1\n.rootids 105\n.nodes\n1 T 1 0 0\n2 24 11 1 -1\n3 23 10 1 -2\n4 22 9 3 -2\n5 21 8 4 -2\n6 23 10 1 -1\n7 22 9 6 -1\n8 21 8 7 -1\n9 20 7 5 8\n10 23 10 2 -1\n11 22 9 2 10\n12 21 8 11 2\n13 23 10 2 -2\n14 22 9 3 -13\n15 21 8 4 14\n16 20 7 12 15\n17 19 6 9 -16\n18 49 17 1 -1\n19 48 16 1 18\n20 47 15 19 1\n21 24 11 20 -20\n22 23 10 20 -21\n23 22 9 22 -21\n24 21 8 23 -21\n25 23 10 20 -20\n26 22 9 25 -20\n27 21 8 26 -20\n28 20 7 24 27\n29 23 10 21 -20\n30 22 9 21 29\n31 21 8 30 21\n32 23 10 21 -21\n33 22 9 22 -32\n34 21 8 23 33\n35 20 7 31 34\n36 19 6 28 -35\n37 47 15 1 -1\n38 47 15 18 1\n39 38 14 37 -38\n40 48 16 1 -1\n41 47 15 40 1\n42 38 14 41 20\n43 37 13 39 -42\n44 36 12 1 -43\n45 37 13 37 -41\n46 36 12 1 -45\n47 24 11 46 -46\n48 23 10 44 -47\n49 36 12 1 -39\n50 24 11 49 -49\n51 36 12 1 -37\n52 24 11 51 -51\n53 23 10 50 52\n54 22 9 48 -53\n55 21 8 54 -2\n56 23 10 44 -46\n57 23 10 49 51\n58 22 9 56 -57\n59 21 8 58 -1\n60 20 7 55 59\n61 24 11 44 -44\n62 23 10 61 47\n63 23 10 50 -51\n64 22 9 62 63\n65 21 8 64 2\n66 21 8 54 14\n67 20 7 65 66\n68 19 6 60 -67\n69 23 10 46 -47\n70 22 9 69 -52\n71 21 8 70 -2\n72 23 10 46 -46\n73 22 9 72 -51\n74 21 8 73 -1\n75 20 7 71 74\n76 23 10 52 -51\n77 22 9 47 76\n78 21 8 77 2\n79 21 8 70 14\n80 20 7 78 79\n81 19 6 75 -80\n82 11 5 68 81\n83 9 4 82 17\n84 23 10 49 -52\n85 22 9 84 -53\n86 21 8 85 -2\n87 23 10 49 -51\n88 22 9 87 -57\n89 21 8 88 -1\n90 20 7 86 89\n91 22 9 53 63\n92 21 8 91 2\n93 21 8 85 14\n94 20 7 92 93\n95 19 6 90 -94\n96 11 5 68 95\n97 9 4 96 17\n98 8 3 83 97\n99 11 5 68 17\n100 9 4 99 17\n101 9 4 68 17\n102 8 3 100 101\n103 7 2 98 102\n104 2 1 36 103\n105 1 0 17 104\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/5.bdd",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 17\n.nvars 50\n.nsuppvars 6\n.suppvarnames DUMMY19 DUMMY20 DUMMY21 DUMMY22 DUMMY23 DUMMY24\n.ids 19 20 21 22 23 24\n.permids 19 20 21 22 23 24\n.auxids 19 20 21 22 23 24\n.nroots 1\n.rootids 17\n.nodes\n1 T 1 0 0\n2 24 5 1 -1\n3 23 4 1 -2\n4 22 3 3 -2\n5 21 2 4 -2\n6 23 4 1 -1\n7 22 3 6 -1\n8 21 2 7 -1\n9 20 1 5 8\n10 23 4 2 -1\n11 22 3 2 10\n12 21 2 11 2\n13 23 4 2 -2\n14 22 3 3 -13\n15 21 2 4 14\n16 20 1 12 15\n17 19 0 9 -16\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/composeids.txt",
    "content": "0\r\n2\r\n4\r\n6\r\n8\r\n10\r\n12\r\n14\r\n16\r\n18\r\n20\r\n22\r\n24\r\n26\r\n28\r\n30\r\n32\r\n34\r\n36\r\n38\r\n"
  },
  {
    "path": "cudd/dddmp/exp/one.bdd",
    "content": ".ver DDDMP-1.0\n.mode A\n.varinfo 0\n.nnodes 1\n.nvars 100\n.nsuppvars 0\n.ids\n.permids\n.nroots 1\n.rootids 1\n.nodes\n1 T 1 0 0\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/s27RP1.bdd",
    "content": "# MONO\n.ver DDDMP-1.0\n.mode A\n.varinfo 3\n.nnodes 3\n.nvars 10\n.nsuppvars 2\n.varnames G5 G6\n.ids 4 5\n.permids 4 6\n.auxids 4 5\n.nroots 1\n.rootids -3\n.nodes\n1 T 1 0 0\n2 5 1 1 -1\n3 4 0 2 -1\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/s27deltaDddmp1.bdd",
    "content": ".ver DDDMP-1.0\n.mode A\n.varinfo 0\n.dd s27adelta.bdd\n.nnodes 16\n.nvars 10\n.nsuppvars 7\n.varnames G0 G1 G2 G3 G5 G6 G7\n.ids 0 1 2 3 4 5 6\n.permids 0 1 2 3 4 6 8\n.auxids 0 1 2 3 4 5 6\n.nroots 3\n.rootids 6 -13 -16\n.nodes\n1 T 1 0 0\n2 6 6 1 -1\n3 4 4 1 2\n4 3 3 3 1\n5 1 1 1 4\n6 0 0 5 -1\n7 5 5 1 -1\n8 4 4 1 -7\n9 5 5 1 -2\n10 4 4 1 -9\n11 3 3 10 8\n12 1 1 8 11\n13 0 0 5 12\n14 2 2 1 -1\n15 2 2 1 -2\n16 1 1 14 15\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/s27deltaDddmp1.bdd.bis",
    "content": ".ver DDDMP-2.0\n.mode A\n.varinfo 0\n.nnodes 16\n.nvars 10\n.nsuppvars 7\n.suppvarnames G0 G1 G2 G3 G5 G6 G7\n.orderedvarnames G0 G1 G2 G3 G5 G6 G7 DUMMY7 DUMMY8 DUMMY9\n.ids 0 1 2 3 4 5 6\n.permids 0 1 2 3 4 5 6\n.auxids 0 1 2 3 4 5 6\n.nroots 3\n.rootids 6 -13 -16\n.nodes\n1 T 1 0 0\n2 6 6 1 -1\n3 4 4 1 2\n4 3 3 3 1\n5 1 1 1 4\n6 0 0 5 -1\n7 5 5 1 -1\n8 4 4 1 -7\n9 5 5 1 -2\n10 4 4 1 -9\n11 3 3 10 8\n12 1 1 8 11\n13 0 0 5 12\n14 2 2 1 -1\n15 2 2 1 -2\n16 1 1 14 15\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/s27deltaDddmp2.bdd",
    "content": ".ver DDDMP-1.0\n.mode A\n.varinfo 0\n.dd s27adelta.bdd\n.nnodes 16\n.nvars 10\n.nsuppvars 7\n.orderedvarnames G0 G1 G2 G3 G5 G6 G7 TMP1 TMP2 TMP3\n.suppvarnames G0 G1 G2 G3 G5 G6 G7\n.ids 0 1 2 3 4 5 6\n.permids 0 1 2 3 4 6 8\n.auxids 0 1 2 3 4 5 6\n.nroots 3\n.rootids 6 -13 -16\n.nodes\n1 T 1 0 0\n2 6 6 1 -1\n3 4 4 1 2\n4 3 3 3 1\n5 1 1 1 4\n6 0 0 5 -1\n7 5 5 1 -1\n8 4 4 1 -7\n9 5 5 1 -2\n10 4 4 1 -9\n11 3 3 10 8\n12 1 1 8 11\n13 0 0 5 12\n14 2 2 1 -1\n15 2 2 1 -2\n16 1 1 14 15\n.end\n"
  },
  {
    "path": "cudd/dddmp/exp/test1.sh.in",
    "content": "#! /bin/sh \n#\n# Check Header Load/Store for BDD/ADD/CNFs:\n#   Load Header\n#   Write Information on Standard Output\n#\n\nEXE=@EXEEXT@\nsrcdir=@top_srcdir@\nwhere=${srcdir}/dddmp/exp\nexitval=0\n\necho \"---------------------------------------------------------------------------\"\necho \"--------------------- TESTING Load and Write Header -----------------------\"\necho \"---------------------------------------------------------------------------\"\n../testdddmp$EXE << END\nmi\n50\nhlb\n${where}/4.bdd\nhw\nhlb\n${where}/0.add\nhw\nhlc\n${where}/4.cnf\nhw\nmq\nquit\nEND\ntest $? != 1 && exitval=1\necho \"-------------------------------- ... END ----------------------------------\"\nexit $exitval\n"
  },
  {
    "path": "cudd/dddmp/exp/test2.sh.in",
    "content": "#! /bin/sh \n#\n# Check BDDs from DDDMP-1.0:\n#   Load an Array of BDDs from DDDMP-1.0\n#   Store them\n#\n\nEXE=@EXEEXT@\nsrcdir=@top_srcdir@\nwhere=${srcdir}/dddmp/exp\ndest=.\nexitval=0\n\necho \"---------------------------------------------------------------------------\"     \necho \"-------------------- TESTING Load BDD from DDDMP-1.0 ----------------------\"\necho \"---------------------------------------------------------------------------\"     \n../testdddmp$EXE << END\nmi\n10\nhlb\n${where}/s27deltaDddmp1.bdd\nhw\nbal\n${where}/s27deltaDddmp1.bdd\n0 \nbas\n${dest}/s27deltaDddmp1.bdd.tmp\n0\nmq\nquit\nEND\ntest $? != 1 && exitval=1\necho \"----------------------------- ... RESULTS ... -----------------------------\"\ndiff --strip-trailing-cr --brief ${dest}/s27deltaDddmp1.bdd.tmp \\\n     ${where}/s27deltaDddmp1.bdd.bis\ntest $? != 0 && exitval=1\necho \"-------------------------------- ... END ----------------------------------\"\nrm -f ${dest}/s27deltaDddmp1.bdd.tmp\nexit $exitval\n"
  },
  {
    "path": "cudd/dddmp/exp/test3.sh.in",
    "content": "#! /bin/sh \n#\n# BDD check: \n#   Load BDDs\n#   Make some operations\n#   Store BDDs\n#\n\nEXE=@EXEEXT@\nsrcdir=@top_srcdir@\nwhere=${srcdir}/dddmp/exp\ndest=.\nexitval=0\n\necho \"---------------------------------------------------------------------------\"\necho \"----------------------- TESTING basic Load/Store ... ----------------------\"\necho \"---------------------------------------------------------------------------\"\n../testdddmp$EXE << END\nmi\n50\nhlb\n${where}/0or1.bdd\nbl\n${where}/0.bdd\n0\nbl\n${where}/1.bdd\n1\nop\nor\n0\n1\n2\nbs\n${dest}/0or1.bdd.tmp\n2\nbl\n${where}/2.bdd\n2\nbl\n${where}/3.bdd\n3\nop\nand\n2\n3\n4\nbs\n${dest}/2and3.bdd.tmp\n4\nhlb\n${where}/4xor5.bdd\nbl\n${where}/4.bdd\n4\nbl\n${where}/5.bdd\n5\nop\nxor\n4\n5\n6\nbs\n${dest}/4xor5.bdd.tmp\n6\nmq\nquit\nEND\ntest $? != 1 && exitval=1\necho \"----------------------------- ... RESULTS ... -----------------------------\"\ndiff --strip-trailing-cr --brief ${where}/0or1.bdd ${dest}/0or1.bdd.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/2and3.bdd ${dest}/2and3.bdd.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/4xor5.bdd ${dest}/4xor5.bdd.tmp\ntest $? != 0 && exitval=1\necho \"-------------------------------- ... END ----------------------------------\"\nrm -f ${dest}/0or1.bdd.tmp ${dest}/2and3.bdd.tmp ${dest}/4xor5.bdd.tmp\nexit $exitval\n"
  },
  {
    "path": "cudd/dddmp/exp/test4.sh.in",
    "content": "#! /bin/sh \n#\n# BDD Check:\n#   Load BDDs\n#   Make some operations (with reordering)\n#   Store BDDs\n#\n\nEXE=@EXEEXT@\nsrcdir=@top_srcdir@\nwhere=${srcdir}/dddmp/exp\ndest=.\nexitval=0\n\necho \"---------------------------------------------------------------------------\"     \necho \"---------- TESTING Load/Store with sifting, varnames & varauxids ----------\"\necho \"---------------------------------------------------------------------------\"     \n../testdddmp$EXE << END1\nmi\n50\nonl\n${where}/varnames.ord\nbl\n${where}/4.bdd\n4\noil\n${where}/varauxids.ord\nbs\n${dest}/4a.bdd.tmp\n4\ndr\n4\nbs\n${dest}/4b.bdd.tmp\n4\nmq\nquit\nEND1\ntest $? != 1 && exitval=1\necho \"------------------------- ... END PHASE 1 ... -----------------------------\"\n../testdddmp$EXE << END2\nmi\n50\nonl\n${where}/varnames.ord\nslm\n3\nbl\n${dest}/4b.bdd.tmp\n4\noil\n${where}/varauxids.ord\nbs\n${dest}/4c.bdd.tmp\n4\nmq\nquit\nEND2\ntest $? != 1 && exitval=1\necho \"----------------------------- ... RESULTS ... -----------------------------\"\ndiff --strip-trailing-cr --brief ${where}/4.bdd ${dest}/4a.bdd.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${dest}/4a.bdd.tmp ${dest}/4c.bdd.tmp\ntest $? != 0 && exitval=1\necho \"-------------------------------- ... END ----------------------------------\"\nrm -f ${dest}/4a.bdd.tmp ${dest}/4c.bdd.tmp\nexit $exitval\n"
  },
  {
    "path": "cudd/dddmp/exp/test5.sh.in",
    "content": "#! /bin/sh \n#\n# Check ADD:\n#   Load an ADD\n#   Store the same ADD\n#   Compare the two\n# (done twice on a small - 0.add - and a medium - 1.add - ADD).\n#\n\nEXE=@EXEEXT@\nsrcdir=@top_srcdir@\nwhere=${srcdir}/dddmp/exp\ndest=.\nexitval=0\n\necho \"---------------------------------------------------------------------------\"\necho \"--------------------- TESTING Load ADD and Store ADD ----------------------\"\necho \"---------------------------------------------------------------------------\"     \n../testdddmp$EXE << END1\nmi\n3\nhlb\n${where}/0.add\nal\n${where}/0.add\n0\nas\n${dest}/0.add.tmp\n0\nmq\nmi\n50\nhlb\n${where}/1.add\nal\n${where}/1.add\n1\nas\n${dest}/1.add.tmp\n1\nmq\nquit\nEND1\ntest $? != 1 && exitval=1\necho \"----------------------------- ... RESULTS ... -----------------------------\"\ndiff --strip-trailing-cr --brief ${where}/0.add ${dest}/0.add.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/1.add ${dest}/1.add.tmp\ntest $? != 0 && exitval=1\necho \"-------------------------------- ... END ----------------------------------\"\nrm -f ${dest}/0.add.tmp ${dest}/1.add.tmp\nexit $exitval\n"
  },
  {
    "path": "cudd/dddmp/exp/test6.sh.in",
    "content": "#! /bin/sh \n#\n# Check CNF (short check - only NodeByNode method involved):\n#   Load BDDs\n#   Store corresponding CNF\n#   Read CNF\n#   Store corresponding BDD\n#   Compare original and final BDDs\n#\n\nEXE=@EXEEXT@\nsrcdir=@top_srcdir@\nwhere=${srcdir}/dddmp/exp\ndest=.\nexitval=0\n\necho \"---------------------------------------------------------------------------\"     \necho \"--------------------- TESTING Load BDD and Store CNF ----------------------\"\necho \"---------------------------------------------------------------------------\"     \n../testdddmp$EXE << END1\nmi\n150\nhlc\n${where}/4.cnf.bis\nbl\n${where}/4.bdd\n0\ncs\n${dest}/4.cnf.tmp\n0\nN\n100\nmq\nquit\nEND1\ntest $? != 1 && exitval=1\necho \"--------------------- TESTING Load CNF and Store BDD ----------------------\"\n../testdddmp$EXE << END2\nmi\n150\nhlc\n${where}/4.cnf.bis\ncl\n${dest}/4.cnf.tmp\n0\nhw\nbs\n${dest}/4.bdd.tmp\n0\nmq\nquit\nEND2\ntest $? != 1 && exitval=1\necho \"----------------------------- ... RESULTS ... -----------------------------\"\ndiff --strip-trailing-cr --brief ${where}/4.cnf.bis ${dest}/4.cnf.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/4.bdd.bis1 ${dest}/4.bdd.tmp\ntest $? != 0 && exitval=1\necho \"-------------------------------- ... END ----------------------------------\"\nrm -f ${dest}/4.cnf.tmp ${dest}/4.bdd.tmp\nexit $exitval\n"
  },
  {
    "path": "cudd/dddmp/exp/test7.sh.in",
    "content": "#! /bin/sh \n#\n# Check CNF (long check - all methods involved):\n#   Load BDDs\n#   Store corresponding CNF in different format:\n#     NodeByNode method -> file 4.node1.tmp\n#     MaxtermByMaxterm -> file 4.max1.tmp\n#     Best with different options:\n#       MaxEdge=-1 MaxPath= 0 -> similar to NodeByNode -> file 4.node2.tmp\n#       MaxEdge= 0 MaxPath=-1 -> similar to NodeByNode -> file 4.node3.tmp\n#       MaxEdge=-1 MaxPath=-1 -> = MaxtermByMaxterm -> file 4.max2.tmp\n#       MaxEdge= 1 MaxPath=-1 -> = Original Best -> file 4.best1.tmp\n#       MaxEdge= 1 MaxPath= 2 -> = Original Best, With Path Shorter than 3 \n#                                  file 4.best2.tmp\n#   Read CNF\n#   Store corresponding BDD\n#   Compare original and final BDDs\n#\n\nEXE=@EXEEXT@\nsrcdir=@top_srcdir@\nwhere=${srcdir}/dddmp/exp\ndest=.\nexitval=0\n\necho \"---------------------------------------------------------------------------\"     \necho \"--------------------- TESTING Load BDD and Store CNF ----------------------\"\necho \"---------------------------------------------------------------------------\"     \n../testdddmp$EXE << END1\nmi\n150\nhlc\n${where}/4.cnf.bis\nbl\n${where}/4.bdd\n0\ncs\n${dest}/4.node1.tmp\n0\nN\n100\ncs\n${dest}/4.max1.tmp\n0\nM\n100\ncs\n${dest}/4.node2.tmp\n0\nB\n-1\n0\n100\ncs\n${dest}/4.node3.tmp\n0\nB\n0\n-1\n100\ncs\n${dest}/4.max2.tmp\n0\nB\n-1\n-1\n100\ncs\n${dest}/4.best1.tmp\n0\nB\n1\n-1\n100\ncs\n${dest}/4.best2.tmp\n0\nB\n1\n2\n100\nmq\nquit\nEND1\ntest $? != 1 && exitval=1\necho \"---------------------------------------------------------------------------\"     \necho \"--------------------- TESTING Load CNF and Store BDD ----------------------\"\necho \"---------------------------------------------------------------------------\"     \n../testdddmp$EXE << END2\nmi\n150\nhlc\n${dest}/4.node2.tmp\ncl\n${dest}/4.node2.tmp\n0\nhw\nbs\n${dest}/4.node2.bdd.tmp\n0\nmq\nquit\nEND2\ntest $? != 1 && exitval=1\n../testdddmp$EXE << END3\nmi\n150\nhlc\n${dest}/4.node3.tmp\ncl\n${dest}/4.node3.tmp\n0\nhw\nbs\n${dest}/4.node3.bdd.tmp\n0\nmq\nquit\nEND3\ntest $? != 1 && exitval=1\n../testdddmp$EXE << END4\nmi\n150\nhlc\n${dest}/4.best1.tmp\ncl\n${dest}/4.best1.tmp\n0\nhw\nbs\n${dest}/4.best1.bdd.tmp\n0\nmq\nquit\nEND4\ntest $? != 1 && exitval=1\n../testdddmp$EXE << END5\nmi\n150\nhlc\n${dest}/4.best2.tmp\ncl\n${dest}/4.best2.tmp\n0\nhw\nbs\n${dest}/4.best2.bdd.tmp\n0\nmq\nquit\nEND5\ntest $? != 1 && exitval=1\necho \"----------------------------- ... RESULTS ... -----------------------------\"\ndiff --strip-trailing-cr --brief ${where}/4.max1 ${dest}/4.max1.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/4.max2 ${dest}/4.max2.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/4.bdd.bis1 ${dest}/4.node2.bdd.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/4.bdd.bis2 ${dest}/4.node3.bdd.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/4.bdd.bis3 ${dest}/4.best1.bdd.tmp\ntest $? != 0 && exitval=1\ndiff --strip-trailing-cr --brief ${where}/4.bdd.bis4 ${dest}/4.best2.bdd.tmp\ntest $? != 0 && exitval=1\necho \"-------------------------------- ... END ----------------------------------\"\nrm -f ${dest}/4.max1.tmp ${dest}/4.max2.tmp ${dest}/4.node2.bdd.tmp \\\n   ${dest}/4.node3.bdd.tmp ${dest}/4.best1.bdd.tmp ${dest}/4.best2.bdd.tmp \\\n   ${dest}/4b.bdd.tmp ${dest}/4.best1.tmp ${dest}/4.best2.tmp \\\n   ${dest}/4.node1.tmp ${dest}/4.node2.tmp ${dest}/4.node3.tmp\nexit $exitval\n"
  },
  {
    "path": "cudd/dddmp/exp/varauxids.ord",
    "content": "1\r\n3\r\n5\r\n7\r\n9\r\n11\r\n13\r\n15\r\n17\r\n19\r\n21\r\n23\r\n25\r\n27\r\n29\r\n31\r\n33\r\n35\r\n37\r\n39\r\n41\r\n43\r\n45\r\n47\r\n49\r\n51\r\n53\r\n55\r\n57\r\n59\r\n61\r\n63\r\n65\r\n67\r\n69\r\n71\r\n73\r\n75\r\n77\r\n79\r\n81\r\n83\r\n85\r\n87\r\n89\r\n91\r\n93\r\n95\r\n97\r\n99\r\n"
  },
  {
    "path": "cudd/dddmp/exp/varnames.ord",
    "content": "V1\r\nV2\r\nV3\r\nV4\r\nV5\r\nV6\r\nV7\r\nV8\r\nV9\r\nV10\r\nV11\r\nV12\r\nV13\r\nV14\r\nV15\r\nV16\r\nV17\r\nV18\r\nV19\r\nV20\r\nV21\r\nV22\r\nV23\r\nV24\r\nV25\r\nV26\r\nV27\r\nV28\r\nV29\r\nV30\r\nV31\r\nV32\r\nV33\r\nV34\r\nV35\r\nV36\r\nV37\r\nV38\r\nV39\r\nV40\r\nV41\r\nV42\r\nV43\r\nV44\r\nV45\r\nV46\r\nV47\r\nV48\r\nV49\r\nV50\r\n"
  },
  {
    "path": "cudd/dddmp/exp/zero.bdd",
    "content": ".ver DDDMP-1.0\r\n.mode A\r\n.varinfo 0\r\n.nnodes 1\r\n.nvars 100\r\n.nsuppvars 0\r\n.ids\r\n.permids\r\n.nroots 1\r\n.rootids -1\r\n.nodes\r\n1 T 1 0 0\r\n.end\r\n"
  },
  {
    "path": "cudd/dddmp/test_dddmp.test.in",
    "content": "#! /bin/sh \n#\n# Run All Test Files\n#\necho TAP version 13\necho 1..7\ncd dddmp/exp\nfor n in 1 2 3 4 5 6 7\ndo\n    ./test${n}.sh > /dev/null 2>&1\n     if test $? = 0 ; then\n        echo \"ok ${n}\"\n    else\n        echo \"not ok ${n}\"\n    fi\ndone\nexit 0\n"
  },
  {
    "path": "cudd/dddmp/testdddmp.c",
    "content": "/**CFile**********************************************************************\n\n  FileName     [testdddmp.c]\n \n  PackageName  [dddmp]\n\n  Synopsis     [A simple test function for Dddmp package]\n\n  Description  [This program constitutes a simple test program\n    for the dddmp library (version 2.0).\n    A simple interactive command selection allow the users to perform the\n    main operation on BDDs, ADDs, and CNF, such as loading and storing.\n    It can work also as a BDD calculators.\n    ]\n\n  Author       [Gianpiero Cabodi and Stefano Quer]\n\n  Copyright    [\n    Copyright (c) 2004 by Politecnico di Torino.\n    All Rights Reserved. This software is for educational purposes only.\n    Permission is given to academic institutions to use, copy, and modify\n    this software and its documentation provided that this introductory\n    message is not removed, that this software and its documentation is\n    used for the institutions' internal research and educational purposes,\n    and that no monies are exchanged. No guarantee is expressed or implied\n    by the distribution of this code.\n    Send bug-reports and/or questions to:\n    {gianpiero.cabodi,stefano.quer}@polito.it.\n    ]\n\n******************************************************************************/\n\n#include <string.h>\n#include <stdio.h>\n#include \"dddmpInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define DDDMPTEST_MAX_FILENAME_LENGTH 256\n#define DDDMPTEST_MAX_STRING_LENGTH 80\n#define DDDMPTEST_MAX_OPERAND  20\n#define DDDMPTEST_MAX_VARIABLE 50\n#define DDDMP_MAX_BDDARRAY_LEN 1000\n\n/**Enum************************************************************************\n\n  Synopsis    [Message type for output messages]\n\n  Description [Type supported by the output function to print-out\n    the proper message.\n    ]\n\n******************************************************************************/\n\ntypedef enum {\n  /* Int Messages */\n  DDDMP_MESSAGE_MANAGER_VAR,\n  DDDMP_MESSAGE_BDD,\n  DDDMP_MESSAGE_BDD_ARRAY,\n  DDDMP_MESSAGE_SOURCE1,\n  DDDMP_MESSAGE_SOURCE2,\n  DDDMP_MESSAGE_DESTINATION,\n  DDDMP_MESSAGE_CUBE,\n  DDDMP_MESSAGE_INDEX,\n  DDDMP_MESSAGE_I_ID,\n  DDDMP_MESSAGE_EDGE_MAX,\n  DDDMP_MESSAGE_LENGHT_MAX,\n  DDDMP_MESSAGE_REORDERING,\n  /* String Messages */\n  DDDMP_MESSAGE_PROMPT,\n  DDDMP_MESSAGE_FILE,\n  DDDMP_MESSAGE_OP,\n  DDDMP_MESSAGE_FORMAT\n} Dddmp_MessageType;\n\n#if !defined(RAND_MAX) && defined(sun) && defined(sparc)\n#define RAND_MAX 2147483647\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\ntypedef struct dddmpVarInfo {\n  /*\n   *  Local Information\n   */\n\n  int nDdVars;       /* Local Manager Number of Variables */\n  char **rootNames;  /* Root Names */\n\n  /*\n   *  Header File Information\n   */\n\n  Dddmp_DecompType ddType;\n\n  int nVars;      /* File Manager Number of Variables */\n  int nSuppVars;  /* File Structure Number of Variables */\n\n  int varNamesFlagUpdate;      /* 0 to NOT Update */\n  char **suppVarNames;\n  char **orderedVarNames;\n\n  int varIdsFlagUpdate;        /* 0 to NOT Update */\n  int *varIds;                 /* File ids - nSuppVars size */\n  int *varIdsAll;              /* ALL ids - nVars size */\n\n  int varComposeIdsFlagUpdate; /* 0 to NOT Update */\n  int *varComposeIds;          /* File permids - nSuppVars size */\n  int *varComposeIdsAll;       /* ALL permids - nVars size */\n\n  int varAuxIdsFlagUpdate;     /* 0 to NOT Update */\n  int *varAuxIds;              /* File auxids - nSuppVars size */\n  int *varAuxIdsAll;           /* ALL auxids  - nVars size */\n\n  int nRoots;\n} dddmpVarInfo_t;\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\nDddmp_RootMatchType rootmatchmode;\nDddmp_VarMatchType varmatchmode;\nDddmp_VarInfoType varoutinfo;\nchar varname[DDDMPTEST_MAX_STRING_LENGTH];\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**AutomaticStart*************************************************************/\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdManager *ManagerInit (dddmpVarInfo_t *varInfo);\nstatic void ManagerQuit (DdManager **ddMgr, dddmpVarInfo_t *varInfo);\nstatic int OneCreate(DdManager *ddMgr, DdNode **operandBdd);\nstatic int BddZeroCreate(DdManager *ddMgr, DdNode **operandBdd);\nstatic int LeafCreate(DdManager *ddMgr, DdNode **operandBdd);\nstatic int BddCreate(DdManager *ddMgr, DdNode **operandBdd);\nstatic int A2B(void);\nstatic int B2A(void);\nstatic int HeaderLoadBdd(dddmpVarInfo_t *varInfo);\nstatic int HeaderLoadCnf(dddmpVarInfo_t *varInfo);\nstatic int HeaderWrite(dddmpVarInfo_t *varInfo);\nstatic int Help(void);\nstatic int OrderNamesLoad(dddmpVarInfo_t *varInfo);\nstatic int IntArrayLoad(dddmpVarInfo_t *varInfo, const char *mode);\nstatic int BddLoad(DdManager *ddMgr, DdNode **operandBdd, dddmpVarInfo_t *varInfo);\nstatic int BddArrayLoad(DdManager *ddMgr, DdNode ***operandBddArray, int *operandBddArraySize, dddmpVarInfo_t *varInfo);\nstatic int AddLoad(DdManager *ddMgr, DdNode **operandBdd, dddmpVarInfo_t *varInfo);\nstatic int AddArrayLoad(DdManager *ddMgr, DdNode ***operandBddArray, int *operandBddArraySize, dddmpVarInfo_t *varInfo);\nstatic int BddLoadCnf(DdManager *ddMgr, DdNode **operandBdd, dddmpVarInfo_t *varInfo);\nstatic int BddArrayLoadCnf(DdManager *ddMgr, DdNode ***operandBddArray, int *operandBddArraySize, dddmpVarInfo_t *varInfo);\nstatic int Operation(DdManager *ddMgr, DdNode **operandBdd);\nstatic int BddStore(DdManager *ddMgr, DdNode **operandBdd, dddmpVarInfo_t *varInfo);\nstatic int BddArrayStore(DdManager *ddMgr, DdNode ***operandBddArray, int *operandBddArraySize, dddmpVarInfo_t *varInfo);\nstatic int AddStore(DdManager *ddMgr, DdNode **operandBdd, dddmpVarInfo_t *varInfo);\nstatic int AddArrayStore(DdManager *ddMgr, DdNode ***operandBddArray, int *operandBddArraySize, dddmpVarInfo_t *varInfo);\nstatic int BddStoreCnf(DdManager *ddMgr, DdNode **operandBdd, dddmpVarInfo_t *varInfo);\nstatic int BddArrayStoreCnf(DdManager *ddMgr, DdNode ***operandBddArray, int *operandBddArraySize, dddmpVarInfo_t *varInfo);\nstatic int DynamicReordering(DdManager *ddMgr);\nstatic int SetLoadMatchmode();\nstatic int CompleteInfoStruct(Dddmp_DecompType ddType, int nVars, int nSuppVars, char **suppVarNames, char **orderedVarNames, int *varIds, int *varComposeIds, int *varAuxIds, int nRoots, dddmpVarInfo_t *varInfo);\nstatic void ReadInt(Dddmp_MessageType message, int *i);\nstatic void ReadString(Dddmp_MessageType message, char string[]);\n\n/**AutomaticEnd***************************************************************/\n\nint\nmain(\n  int argc,\n  char **argv\n  )\n{\n  DdManager *ddMgr = NULL;\n  DdNode **operandBdd = NULL;\n  DdNode ***operandBddArray = NULL;\n  int *operandBddArraySize = NULL;\n  char *row = NULL;\n  dddmpVarInfo_t varInfo;\n  int i;\n\n  /*--------------------- Echo command line and arguments -------------------*/\n\n  fprintf (stdout, \"#\");\n  for (i=0; i<argc; i++) {\n    fprintf (stdout, \"%s Version 2.0.2 (use command help)\", argv[i]);\n  }\n  fprintf (stdout, \"\\n\");\n  if (argc>1) {\n    Help();\n  }\n\n  /*-------------------------- Init Array of BDDs ---------------------------*/\n\n rootmatchmode = DDDMP_ROOT_MATCHLIST;\n#if 1\n  varmatchmode = DDDMP_VAR_MATCHIDS;\n#else\n  varmatchmode = DDDMP_VAR_MATCHNAMES;\n#endif\n  varoutinfo = DDDMP_VARIDS;\n\n  row = DDDMP_ALLOC (char, DDDMPTEST_MAX_STRING_LENGTH);\n  Dddmp_CheckAndReturn (row==NULL, \"Allocation error.\");\n\n  operandBdd = DDDMP_ALLOC (DdNode *, DDDMPTEST_MAX_OPERAND);\n  Dddmp_CheckAndReturn (operandBdd==NULL, \"Allocation error.\");\n\n  operandBddArray = DDDMP_ALLOC (DdNode **, DDDMPTEST_MAX_OPERAND);\n  Dddmp_CheckAndReturn (operandBddArray==NULL, \"Allocation error.\");\n\n  operandBddArraySize = DDDMP_ALLOC (int, DDDMPTEST_MAX_OPERAND);\n  Dddmp_CheckAndReturn (operandBddArraySize==NULL, \"Allocation error.\");\n\n  for (i=0; i<DDDMPTEST_MAX_OPERAND; i++) {\n    operandBdd[i] = NULL;\n    operandBddArray[i] = NULL;\n    operandBddArraySize[i] = 0;\n  }\n\n  /*--------------------- Manage command line parameters --------------------*/\n\n  while (1) {\n    ReadString (DDDMP_MESSAGE_PROMPT, row);\n    if (row[0]=='\\n') {\n      continue;\n    }\n    if (strncmp (row, \"help\", 4)==0) {\n      Help();\n    } else if (strncmp (row, \"mi\", 2)==0) {\n      ddMgr = ManagerInit (&varInfo);\n    } else if (strncmp (row, \"mq\", 2)==0) {\n      ManagerQuit (&ddMgr, &varInfo);\n    } else if (strncmp (row, \"onl\", 3)==0) {\n      OrderNamesLoad (&varInfo);\n    } else if (strncmp (row, \"oil\", 3)==0) {\n      IntArrayLoad (&varInfo, \"oil\");\n    } else if (strncmp (row, \"cil\", 3)==0) {\n      IntArrayLoad (&varInfo, \"cil\");\n    } else if (strncmp (row, \"slm\", 3)==0) {\n      SetLoadMatchmode ();\n    } else if (strncmp (row, \"op\", 2)==0) {\n      Operation (ddMgr, operandBdd);\n    } else if (strncmp (row, \"oc\", 2)==0) {\n      OneCreate (ddMgr, operandBdd);\n    } else if (strncmp (row, \"zc\", 2)==0) {\n      BddZeroCreate (ddMgr, operandBdd);\n    } else if (strncmp (row, \"lc\", 2)==0) {\n      LeafCreate (ddMgr, operandBdd);\n    } else if (strncmp (row, \"bc\", 2)==0) {\n      BddCreate (ddMgr, operandBdd);\n    } else if (strncmp (row, \"a2b\", 3)==0) {\n      A2B ();\n    } else if (strncmp (row, \"b2a\", 3)==0) {\n      B2A ();\n    } else if (strncmp (row, \"hlb\", 3)==0) {\n      HeaderLoadBdd (&varInfo);\n    } else if (strncmp (row, \"hlc\", 3)==0) {\n      HeaderLoadCnf (&varInfo);\n    } else if (strncmp (row, \"bl\", 3)==0) {\n      BddLoad (ddMgr, operandBdd, &varInfo);\n    } else if (strncmp (row, \"bal\", 3)==0) {\n      BddArrayLoad (ddMgr, operandBddArray, operandBddArraySize, &varInfo);\n    } else if (strncmp (row, \"al\", 2)==0) {\n      AddLoad (ddMgr, operandBdd, &varInfo);\n    } else if (strncmp (row, \"aal\", 3)==0) {\n      AddArrayLoad (ddMgr, operandBddArray, operandBddArraySize, &varInfo);\n    } else if (strncmp (row, \"cl\", 2)==0) {\n      BddLoadCnf (ddMgr, operandBdd, &varInfo);\n    } else if (strncmp (row, \"cal\", 3)==0) {\n      BddArrayLoadCnf (ddMgr, operandBddArray, operandBddArraySize, &varInfo);\n    } else if (strncmp (row, \"hw\", 2)==0) {\n      HeaderWrite (&varInfo);\n    } else if (strncmp (row, \"bs\", 2)==0) {\n      BddStore (ddMgr, operandBdd, &varInfo);\n    } else if (strncmp (row, \"bas\", 3)==0) {\n      BddArrayStore (ddMgr, operandBddArray, operandBddArraySize, &varInfo);\n    } else if (strncmp (row, \"as\", 2)==0) {\n      AddStore (ddMgr, operandBdd, &varInfo);\n    } else if (strncmp (row, \"aas\", 2)==0) {\n      AddArrayStore (ddMgr, operandBddArray, operandBddArraySize, &varInfo);\n    } else if (strncmp (row, \"cs\", 2)==0) {\n      BddStoreCnf (ddMgr, operandBdd, &varInfo);\n    } else if (strncmp (row, \"cas\", 2)==0) {\n      BddArrayStoreCnf (ddMgr, operandBddArray, operandBddArraySize, &varInfo);\n    } else if (strncmp (row, \"dr\", 2)==0) {\n      DynamicReordering (ddMgr);\n    } else if (strncmp (row, \"quit\", 4)==0) {\n      break;\n    } else {\n      fprintf (stderr, \"Command not found: %s\\n\", row);\n    }\n  }\n\n  /*-------------------------------- Free Memory ----------------------------*/\n\n  ManagerQuit (&ddMgr, &varInfo);\n\n  DDDMP_FREE (row);\n  DDDMP_FREE (operandBdd);\n  for (i=0; i<DDDMPTEST_MAX_OPERAND; i++) {\n    if (operandBddArray[i] != NULL) {\n      DDDMP_FREE (operandBddArray[i]);\n    }\n  }\n  DDDMP_FREE (operandBddArray);\n  DDDMP_FREE (operandBddArraySize);\n\n  fprintf (stdout, \"End of test.\\n\");\n\n  return (DDDMP_SUCCESS);\n}\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**Function********************************************************************\n\n  Synopsis     [Create a CUDD Manager with nVars variables.]\n  \n  Description  [Create a CUDD Manager with nVars variables.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic DdManager *\nManagerInit (\n  dddmpVarInfo_t *varInfo\n  )\n{\n  DdManager *ddMgr = NULL;\n  int nVars;\n\n  ReadInt (DDDMP_MESSAGE_MANAGER_VAR, &nVars);\n\n  /*----------------------- Init Var Information Structure ------------------*/\n\n  varInfo->nDdVars = nVars;\n\n  varInfo->rootNames = NULL;\n  varInfo->ddType = DDDMP_NONE;\n  varInfo->nVars = (-1);\n  varInfo->nSuppVars = (-1);\n  varInfo->varNamesFlagUpdate = 1;\n  varInfo->suppVarNames = NULL;\n  varInfo->orderedVarNames = NULL;\n  varInfo->varIdsFlagUpdate = 1;\n  varInfo->varIds = NULL;\n  varInfo->varIdsAll = NULL;\n  varInfo->varComposeIdsFlagUpdate = 1;\n  varInfo->varComposeIds = NULL;\n  varInfo->varComposeIdsAll = NULL;\n  varInfo->varAuxIdsFlagUpdate = 1;\n  varInfo->varAuxIds = NULL;\n  varInfo->varAuxIdsAll = NULL;\n  varInfo->nRoots = (-1);\n\n  /*------------------------------ Init DD Manager --------------------------*/\n\n  ddMgr = Cudd_Init (nVars, 0, CUDD_UNIQUE_SLOTS,\n    CUDD_CACHE_SLOTS, 0);\n\n  Dddmp_CheckAndReturn (ddMgr==NULL, \"DdManager NOT inizializated.\");\n\n  return (ddMgr);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Quit a CUDD Manager.]\n  \n  Description  [Quit a CUDD Manager.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic void\nManagerQuit (\n  DdManager **ddMgrPtr      /* IN: CUDD Manager */,\n  dddmpVarInfo_t *varInfo   /* IN: Internal Manager */\n  )\n{\n  if (*ddMgrPtr == NULL) {\n    return;\n  }\n\n  fprintf (stdout, \"Quitting CUDD Manager.\\n\");\n  Cudd_Quit (*ddMgrPtr);\n  *ddMgrPtr = NULL;\n\n  DddmpStrArrayFree (varInfo->rootNames, varInfo->nRoots);\n  DddmpStrArrayFree (varInfo->suppVarNames, varInfo->nSuppVars);\n  DddmpStrArrayFree (varInfo->orderedVarNames, varInfo->nVars);\n  DDDMP_FREE (varInfo->varIds);\n  DDDMP_FREE (varInfo->varIdsAll);\n  DDDMP_FREE (varInfo->varComposeIds);\n  DDDMP_FREE (varInfo->varComposeIdsAll);\n  DDDMP_FREE (varInfo->varAuxIds);\n  DDDMP_FREE (varInfo->varAuxIdsAll);\n\n  varInfo->nDdVars = (-1);\n  varInfo->rootNames = NULL;\n  varInfo->ddType = DDDMP_NONE;\n  varInfo->nVars = (-1);\n  varInfo->nSuppVars = (-1);\n  varInfo->varNamesFlagUpdate = 1;\n  varInfo->suppVarNames = NULL;\n  varInfo->orderedVarNames = NULL;\n  varInfo->varIdsFlagUpdate = 1;\n  varInfo->varIds = NULL;\n  varInfo->varIdsAll = NULL;\n  varInfo->varComposeIdsFlagUpdate = 1;\n  varInfo->varComposeIds = NULL;\n  varInfo->varComposeIdsAll = NULL;\n  varInfo->varAuxIdsFlagUpdate = 1;\n  varInfo->varAuxIds = NULL;\n  varInfo->varAuxIdsAll = NULL;\n  varInfo->nRoots = (-1);\n\n  return;\n}\n                                                                       \n/**Function********************************************************************\n\n  Synopsis     [Create a One-BDD Leaf.]\n  \n  Description  [Create a One-BDD Leaf.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nOneCreate(\n  DdManager *ddMgr      /* IN: CUDD Manager */,\n  DdNode **operandBdd   /* In/OUT: Array of operand */\n  )\n{\n  int i;\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n\n  operandBdd[i] = Cudd_ReadOne (ddMgr);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Create a Zero-BDD Leaf.]\n  \n  Description  [Create a Zero-BDD Leaf.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddZeroCreate(\n  DdManager *ddMgr      /* IN: CUDD Manager */,\n  DdNode **operandBdd   /* IN/OUT: array of operand */\n  )\n{\n  int i;\n  DdNode *one = NULL;\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n\n  one = Cudd_ReadOne(ddMgr);\n  operandBdd[i] = Cudd_Not(one);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Create a One-Node BDD.]\n  \n  Description  [Create a One-Node BDD.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nLeafCreate(\n  DdManager *ddMgr      /* IN: CUDD Manager */,\n  DdNode **operandBdd   /* IN/OUT: Array of operandBdd */\n  )\n{\n  int i, j;\n  DdNode *f = NULL;\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n  ReadInt (DDDMP_MESSAGE_INDEX, &j);\n\n  f = Cudd_bddIthVar (ddMgr, j);\n  Cudd_Ref(f);\n  operandBdd[i] = f;\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n \n  Synopsis     [Create a BDD.]\n  \n  Description  [Create a BDD: Variable index and number of cubes selection.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddCreate (\n  DdManager *ddMgr      /* IN: CUDD Manager */,\n  DdNode **operandBdd   /* array of operandBdd */\n  )\n{\n  DdNode **vet, *f, *g, *h;\n  int nb, nv, vi0, vi1, nc, i, j;\n  char row[DDDMPTEST_MAX_FILENAME_LENGTH];\n  char *retval;\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadInt (DDDMP_MESSAGE_BDD, &nb);\n\n  fprintf (stdout, \"Variables Index [n-m] (m-n = number of variables): \");\n  retval = fgets (row, DDDMPTEST_MAX_STRING_LENGTH, stdin);\n  if (!retval)\n    return (DDDMP_FAILURE);\n  sscanf (row, \"%d-%d\", &vi0, &vi1);\n  nv = vi1-vi0+1;\n\n  ReadInt (DDDMP_MESSAGE_CUBE, &nc);\n\n  /* Leaf Creation */\n  vet = DDDMP_ALLOC (DdNode *, nv);\n  for (i=0; i<nv; i++) {\n     vet[i] = Cudd_bddIthVar (ddMgr, vi0+i);\n  }\n\n  /* Cubes and BDD creation */\n  f = Cudd_Not (Cudd_ReadOne (ddMgr));\n  for (i=0; i<nc; i++)\n    {\n    g = Cudd_ReadOne (ddMgr);\n    for (j=0; j<nv; j++)\n      {\n      if ( ((float) rand())/((float) RAND_MAX) > 0.5 ) {\n        h = Cudd_bddAnd (ddMgr, g, vet[j]);\n      } else {\n        h = Cudd_bddAnd (ddMgr, g, Cudd_Not (vet[j]));\n      }\n      Cudd_Ref (h);\n      Cudd_RecursiveDeref (ddMgr, g);\n      g = h;\n      }\n    h = Cudd_bddOr (ddMgr, f, g);\n    Cudd_Ref (h);\n    Cudd_RecursiveDeref (ddMgr, f);\n    Cudd_RecursiveDeref (ddMgr, g);\n    f = h;\n    }\n      \n  operandBdd[nb] = f;\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Transform a BDD from the ASCII to the Binary format].]\n  \n  Description  [Input and Output file selection.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nA2B(\n  void\n)\n{\n  fprintf (stderr, \"Not yet Implemented!!!\\n\");\n\n  return (DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Transform a BDD from the Binary to the ASCII format].]\n  \n  Description  [Input and Output file selection.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nB2A(\n  void\n)\n{\n  fprintf (stderr, \"Not yet Implemented!!!\\n\");\n\n  return (DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Read the Header of a file containing a BDD.]\n  \n  Description  [File name Selection.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nHeaderLoadBdd (\n  dddmpVarInfo_t *varInfo      /* IN/OUT: Variable Information */\n  )\n{\n  Dddmp_DecompType ddType;\n  int retValue, nRoots, nVars, nSuppVars;\n  int *tmpVarIds = NULL;\n  int *tmpVarAuxIds = NULL;\n  int *tmpVarComposeIds = NULL;\n  char **tmpOrderedVarNames = NULL;\n  char **tmpSuppVarNames = NULL;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n\n  retValue = Dddmp_cuddHeaderLoad (&ddType, &nVars, &nSuppVars,\n    &tmpSuppVarNames, &tmpOrderedVarNames, &tmpVarIds, &tmpVarComposeIds,\n    &tmpVarAuxIds, &nRoots, fileName, NULL);\n\n  if (retValue == DDDMP_FAILURE) {\n    return (DDDMP_FAILURE);\n  }\n\n  /*---------------------------- Tail Operations ----------------------------*/\n\n  CompleteInfoStruct (ddType, nVars, nSuppVars,\n    tmpSuppVarNames, tmpOrderedVarNames, tmpVarIds, tmpVarComposeIds,\n    tmpVarAuxIds, nRoots, varInfo);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Read the Header of a file containing a CNF formula.]\n  \n  Description  [File name Selection.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nHeaderLoadCnf (\n  dddmpVarInfo_t *varInfo      /* IN/OUT: Variable Information */\n  )\n{\n  int retValue, nRoots, nVars, nSuppVars;\n  int *tmpVarIds = NULL;\n  int *tmpVarComposeIds = NULL;\n  int *tmpVarAuxIds = NULL;\n  char **tmpOrderedVarNames = NULL;\n  char **tmpSuppVarNames = NULL;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n\n  retValue = Dddmp_cuddHeaderLoadCnf (&nVars, &nSuppVars,\n   &tmpSuppVarNames, &tmpOrderedVarNames, &tmpVarIds, &tmpVarComposeIds,\n   &tmpVarAuxIds, &nRoots, fileName, NULL);\n\n  if (retValue == DDDMP_FAILURE) {\n    return (DDDMP_FAILURE);\n  }\n\n  /*---------------------------- Tail Operations ----------------------------*/\n\n  CompleteInfoStruct (DDDMP_CNF, nVars, nSuppVars,\n    tmpSuppVarNames, tmpOrderedVarNames, tmpVarIds, tmpVarComposeIds,\n    tmpVarAuxIds, nRoots, varInfo);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Read the Header of a filke containing a BDD.]\n  \n  Description  [File name Selection.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nHeaderWrite(\n  dddmpVarInfo_t *varInfo      /* IN/OUT: Variable Information */\n  )\n{\n  int i;\n\n  switch (varInfo->ddType) {\n    case DDDMP_BDD:\n      fprintf (stdout, \"DD TYPE: DDDMP_BDD\\n\");\n      break;\n    case DDDMP_ADD:\n      fprintf (stdout, \"DD TYPE: DDDMP_ADD\\n\");\n      break;\n    case DDDMP_CNF:\n      fprintf (stdout, \"DD TYPE: DDDMP_CNF\\n\");\n      break;\n    case DDDMP_NONE:\n      fprintf (stdout, \"DD TYPE: NONE - Error\\n\");\n      break;\n  }\n\n  fprintf (stdout, \"Number of variables: %d\\n\", varInfo->nVars);\n  fprintf (stdout, \"Number of support variables: %d\\n\", varInfo->nSuppVars);\n\n  if (varInfo->suppVarNames != NULL) {\n    fprintf (stdout, \"suppVarNames: \");\n    for (i=0; i<varInfo->nSuppVars; i++) {\n      if (varInfo->suppVarNames[i] != NULL) {\n        fprintf (stdout, \"%s \", varInfo->suppVarNames[i]);\n      }\n    }\n    fprintf (stdout, \"\\n\");\n  }\n\n  if (varInfo->orderedVarNames != NULL) {\n    fprintf (stdout, \"orderedVarNames: \");\n    for (i=0; i<varInfo->nVars; i++) {\n      if (varInfo->orderedVarNames[i] != NULL) {\n        fprintf (stdout, \"%s \", varInfo->orderedVarNames[i]);\n      }\n    }\n    fprintf (stdout, \"\\n\");\n  }\n\n  if (varInfo->varIds != NULL) {\n    fprintf (stdout, \"varIds: \");\n    for (i=0; i<varInfo->nSuppVars; i++) {\n      fprintf (stdout, \"%d \", varInfo->varIds[i]);\n    }\n    fprintf (stdout, \"\\n\");\n  }\n\n  if (varInfo->varIdsAll != NULL) {\n    fprintf (stdout, \"varIds for ALL Manager Variables: \");\n    for (i=0; i<varInfo->nVars; i++) {\n      fprintf (stdout, \"%d \", varInfo->varIdsAll[i]);\n    }\n    fprintf (stdout, \"\\n\");\n  }\n\n  if (varInfo->varComposeIds != NULL) {\n    fprintf (stdout, \"varComposeIds: \");\n    for (i=0; i<varInfo->nSuppVars; i++) {\n      fprintf (stdout, \"%d \", varInfo->varComposeIds[i]);\n    }\n    fprintf (stdout, \"\\n\");\n  }\n\n  if (varInfo->varComposeIdsAll != NULL) {\n    fprintf (stdout, \"varComposeIds for ALL Manager Variables: \");\n    for (i=0; i<varInfo->nVars; i++) {\n      fprintf (stdout, \"%d \", varInfo->varComposeIdsAll[i]);\n    }\n    fprintf (stdout, \"\\n\");\n  }\n\n  if (varInfo->varAuxIds != NULL) {\n    fprintf (stdout, \"varAuxIds: \");\n    for (i=0; i<varInfo->nSuppVars; i++) {\n      fprintf (stdout, \"%d \", varInfo->varAuxIds[i]);\n    }\n    fprintf (stdout, \"\\n\");\n  }\n\n  if (varInfo->varAuxIdsAll != NULL) {\n    fprintf (stdout, \"varAuxIds for ALL Manager Variables: \");\n    for (i=0; i<varInfo->nVars; i++) {\n      fprintf (stdout, \"%d \", varInfo->varAuxIdsAll[i]);\n    }\n    fprintf (stdout, \"\\n\");\n  }\n\n  fprintf (stdout, \"Number of roots: %d\\n\", varInfo->nRoots);\n\n  fflush (stdout);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n  \n  Synopsis     [Print the Help messages.] \n  \n  Description  [Print the Help messages.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nHelp(\n  void\n  )\n{\n  fprintf (stdout, \"Commands:\\n\");\n  fprintf (stdout, \"MAIN\\n\");\n\n  fprintf (stdout, \"\\thelp : Print this set of messages.\\n\");\n  fprintf (stdout, \"\\tquit : Quit the test program.\\n\");\n\n  fprintf (stdout, \"MANAGER OPERATIONs\\n\");\n\n  fprintf (stdout,\n    \"\\thmi  : Manager Init (To do BEFORE any BDD/ADD operation).\\n\");\n  fprintf (stdout, \"\\thmq  : Manager Quit.\\n\");\n\n  fprintf (stdout, \"LOAD\\n\");\n\n  fprintf (stdout, \"\\thlb  : Load the header from a BDD/ADD file.\\n\");\n  fprintf (stdout, \"\\thlc  : Load the header from a CNF file.\\n\");\n  fprintf (stdout, \"\\tbl   : Load a BDD from a file.\\n\");\n  fprintf (stdout, \"\\tbal  : Load an Array-BDD from a file.\\n\");\n  fprintf (stdout, \"\\tal   : Load an ADD from a file.\\n\");\n  fprintf (stdout, \"\\taal  : Load an Array-ADD from a file.\\n\");\n  fprintf (stdout, \"\\tcl   : Load a CNF Formula from a file.\\n\");\n  fprintf (stdout, \"\\tcal  : Load an Array of CNF Formulas from a file.\\n\");\n\n  fprintf (stdout, \"STORE\\n\");\n\n  fprintf (stdout,\n    \"\\thw   : (Header) Write variable information on stdout.\\n\");\n  fprintf (stdout, \"\\tbs   : Store a BDD into a file.\\n\");\n  fprintf (stdout, \"\\tbas  : Store an Array-BDD from a file.\\n\");\n  fprintf (stdout, \"\\tas   : Store an ADD into a file.\\n\");\n  fprintf (stdout, \"\\taas  : Store an Array-ADD into a file.\\n\");\n  fprintf (stdout, \"\\tcs   : Store BDD as a CNF formula.\\n\");\n  fprintf (stdout, \"\\tcas  : Store and Array of BDDs as a CNF formula.\\n\");\n\n  fprintf (stdout, \"MISC\\n\");\n\n  fprintf (stdout, \"\\tdr   : Activate Dynamic Reordering.\\n\");\n  fprintf (stdout, \"\\tonl  : Load the order from a file (varNames).\\n\");\n  fprintf (stdout, \"\\toil  : Load the order from a file (varAuxIds).\\n\");\n  fprintf (stdout, \"\\tcil  : Load compose IDs from a file.\\n\");\n  fprintf (stdout, \"\\tslm  : Set Load matchmode for variables.\\n\");\n  fprintf (stdout,\n    \"\\top   : Operation (or, and, xor, not, =) between BDDs.\\n\");\n  fprintf (stdout, \"\\toc   : Create a terminal-one BDD.\\n\");\n  fprintf (stdout, \"\\tzc   : Create a terminal-zero BDD.\\n\");\n  fprintf (stdout, \"\\tlc   : Create a single variable BDD (1 node).\\n\");\n  fprintf (stdout, \"\\tbc   : Create a random BDD.\\n\");\n\n  fprintf (stdout, \"NOT YET IMPLEMENTED\\n\");\n\n  fprintf (stdout,\n    \"\\ta2b  : Convert a file from the ASCII format to the binary one.\\n\");\n  fprintf (stdout,\n    \"\\tb2a  : Convert a file from the binary format to the ASCII one.\\n\");\n\n  fprintf (stdout, \"HINT\\n\");\n\n  fprintf (stdout,\n    \"  Command 'mi' has to be the first instruction to build:\\n\");\n  fprintf (stdout, \"  a) The CUDD manager.\\n\");\n  fprintf (stdout,\n    \"  b) The internal manager (containing name and variable IDs).\\n\");\n  fprintf (stdout,\n    \"  After that load an header file with 'hlb' or 'hlc' to have proper\\n\");\n  fprintf (stdout,\n    \"  names and ids for each subsequent load/store operation.\\n\");\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Load the BDD order from a file (varNames).] \n  \n  Description  [Load the BDD order from a file (varNames).\n    Force the orderedVarNames field of the varInfo structure,\n    i.e., the local manager, to be stucked to this array of values.\n    ]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nOrderNamesLoad(\n  dddmpVarInfo_t *varInfo      /* IN/OUT: Variable Information */\n  )\n{\n  FILE *fp = NULL;\n  int i;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n  char tmpBuf[DDDMPTEST_MAX_STRING_LENGTH];\n  char tmpName[DDDMPTEST_MAX_STRING_LENGTH];\n  char **tmpOrderedVarNames = NULL;\n\n  /*-------------------------  Red New Var Names Array ----------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n\n  fp = fopen (fileName, \"r\");\n  Dddmp_CheckAndReturn (fp==NULL, \"Cannot open file.\");\n\n  varoutinfo = DDDMP_VARNAMES;\n  tmpOrderedVarNames = DDDMP_ALLOC (char *, varInfo->nDdVars);\n\n  i=0;\n  while (fgets (tmpBuf, DDDMPTEST_MAX_STRING_LENGTH, fp)!=NULL) {\n    if (tmpBuf[0]=='#') {\n      continue;\n    }\n\n    if (i>=varInfo->nDdVars) {\n      fprintf (stdout,\n        \"Number of variables in files higher than DD manager vars (%d)\\n\",\n        varInfo->nDdVars);\n      fprintf (stdout, \"Exceeding variables ignored\\n\");\n      fprintf (stdout,\n        \"You might increase the DDDMPTEST_MAX_VARIABLE constant\\n\");\n      break;\n    }\n\n    sscanf (tmpBuf, \"%s\", tmpName);\n    tmpOrderedVarNames[i] = DDDMP_ALLOC (char, (strlen (tmpName) + 1));\n    if (tmpOrderedVarNames[i]==NULL) {\n      fprintf (stdout, \"Error allocating memory\\n\");\n    } else {\n      strcpy (tmpOrderedVarNames[i], tmpName);\n    }\n    i++;\n  }\n\n  for ( ;i<varInfo->nDdVars; i++) {\n    tmpOrderedVarNames[i] = NULL;\n  }\n\n  fclose(fp);\n\n  /*----------------------- Free and Set Var Names Array --------------------*/\n\n  DddmpStrArrayFree (varInfo->orderedVarNames, varInfo->nVars);\n  varInfo->orderedVarNames = tmpOrderedVarNames;\n  varInfo->nVars = varInfo->nDdVars;\n\n  /* DO NOT ALLOW FURTHER UPDATES */\n  varInfo->varNamesFlagUpdate = 0;\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Load the BDD order from a file (varauxids).] \n  \n  Description  [Load the BDD order from a file (varauxids).\n    Force the\n    varAuxIds and varAuxIdsAll\n    or the\n    varComposeIds and varComposeIdsAll\n    fields of the varInfo structure, i.e., the local manager, to be\n    stucked to this array of values.\n    ]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nIntArrayLoad (\n  dddmpVarInfo_t *varInfo      /* IN/OUT: Variable Information */,\n  const char *mode\n  )\n{\n  FILE *fp = NULL;\n  int i;\n  int *tmpArray1 = NULL;\n  int *tmpArray2 = NULL;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n  char buf[DDDMPTEST_MAX_STRING_LENGTH];\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n\n  fp = fopen(fileName, \"r\");\n  Dddmp_CheckAndReturn (fp==NULL, \"Cannot open file.\");\n\n  tmpArray1 = DDDMP_ALLOC (int, varInfo->nDdVars);\n  tmpArray2 = DDDMP_ALLOC (int, varInfo->nDdVars);\n  Dddmp_CheckAndReturn (tmpArray1==NULL, \"Error allocating memory.\");\n  Dddmp_CheckAndReturn (tmpArray2==NULL, \"Error allocating memory.\");\n\n  i=0;\n  while (fgets(buf, DDDMPTEST_MAX_STRING_LENGTH, fp)!=NULL) {\n    if (buf[0]=='#') {\n      continue;\n    }\n    if (i>=varInfo->nDdVars) {\n      fprintf (stdout,\n        \"Number of variables in files higher than DD manager vars (%d)\\n\",\n        varInfo->nDdVars);\n      fprintf (stdout, \"Exceeding variables ignored.\\n\");\n      fprintf (stdout, \"(Increase the DDDMPTEST_MAX_VARIABLE constant.)\\n\");\n      break;\n    }\n    sscanf(buf, \"%d\", &tmpArray1[i]);\n    sscanf(buf, \"%d\", &tmpArray2[i++]);\n  }\n\n  for (;i<varInfo->nDdVars;i++) {\n    tmpArray1[i]= -1;\n    tmpArray2[i]= -1;\n  }\n\n  fclose(fp);\n\n  if (strcmp (mode, \"oil\") == 0) {\n    varInfo->varAuxIds = tmpArray1;\n    varInfo->varAuxIdsAll = tmpArray2;\n\n    /* DO NOT ALLOW FURTHER UPDATES */\n    varInfo->varAuxIdsFlagUpdate = 0;\n  } else {\n    if (strcmp (mode, \"cil\") == 0) {\n      varInfo->varComposeIds = tmpArray1;\n      varInfo->varComposeIdsAll = tmpArray2;\n\n      /* DO NOT ALLOW FURTHER UPDATES */\n      varInfo->varComposeIdsFlagUpdate = 0;\n    }\n  }\n\n  varInfo->nVars = varInfo->nDdVars;\n  varInfo->nSuppVars = varInfo->nDdVars;\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Load a BDD from a file.]\n  \n  Description  [Load a BDD from a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddLoad (\n  DdManager *ddMgr         /* IN: CUDD Manager */,\n  DdNode **operandBdd      /* IN: Operand BDD */,\n  dddmpVarInfo_t *varInfo  /* IN/OUT: Variable Information */\n  )\n{\n  DdNode *f = NULL;\n  int i;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n  \n  /*-------------------------------- Load BDD -------------------------------*/\n\n  fprintf (stdout, \"Loading %s ...\\n\", fileName);\n\n  f = Dddmp_cuddBddLoad (ddMgr, varmatchmode, varInfo->orderedVarNames,\n    varInfo->varIdsAll, varInfo->varComposeIdsAll, DDDMP_MODE_DEFAULT,\n    fileName, NULL);\n\n  if (f==NULL) {\n    fprintf (stderr, \"Dddmp Test Error : %s is not loaded from file\\n\",\n      fileName);\n  } else {\n    operandBdd[i] = f;\n  }\n\n  /*---------------------------- Tail Operations ----------------------------*/\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Load an array of BDDs from a file.]\n  \n  Description  [Load an array of BDDs from a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddArrayLoad(\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode ***operandBddArray   /* IN: Array of operand BDD */,\n  int *operandBddArraySize    /* IN: Number of ADD in the Array */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  DdNode **bddArray = NULL;  \n  int i, j, nRoots;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD_ARRAY, &i);\n\n  /*---------------------------- Load BDDs ----------------------------------*/\n\n  nRoots = Dddmp_cuddBddArrayLoad (ddMgr, rootmatchmode,\n    varInfo->rootNames, varmatchmode,\n    varInfo->orderedVarNames, varInfo->varIdsAll, varInfo->varComposeIdsAll,\n    DDDMP_MODE_DEFAULT, fileName, NULL, &bddArray);\n\n  Dddmp_CheckAndReturn (nRoots>DDDMP_MAX_BDDARRAY_LEN,\n    \"DDDMP_MAX_BDDARRAY_LEN exceeded by BDD array len (increase it).\");\n\n  if (nRoots<=0) {\n    return (DDDMP_FAILURE);\n  }\n\n  varInfo->nRoots = nRoots;\n  operandBddArray[i] = DDDMP_ALLOC (DdNode *, nRoots);\n  Dddmp_CheckAndReturn (operandBddArray[i]==NULL, \"Allocation error.\");\n\n  for (j=0; j<nRoots; j++) {\n    operandBddArray[i][j] = bddArray[j];\n  }\n  operandBddArraySize[i] = nRoots;\n\n  /*---------------------------- Tail Operations ----------------------------*/\n\n  /* free array */\n  DDDMP_FREE (bddArray);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Load an ADD from a file.]\n  \n  Description  [Load an ADD from a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nAddLoad(\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode **operandBdd         /* IN: Operand BDD */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  DdNode *f = NULL;\n  int i;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n\n  /*-------------------------------- Load ADD -------------------------------*/\n\n  fprintf (stdout, \"Loading %s ...\\n\", fileName);\n\n  f = Dddmp_cuddAddLoad (ddMgr, varmatchmode, varInfo->orderedVarNames,\n    varInfo->varIdsAll, varInfo->varComposeIdsAll, DDDMP_MODE_DEFAULT,\n    fileName, NULL);\n\n  if (f==NULL) {\n    fprintf (stderr, \"Dddmp Test Error : %s is not loaded from file\\n\",\n      fileName);\n  } else {\n    operandBdd[i] = f;\n  }\n\n  /*---------------------------- Tail Operations ----------------------------*/\n\n  fprintf (stdout, \"Load:\\n\");\n  Cudd_PrintMinterm (ddMgr, f);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Load an array of ADDs from a file.]\n  \n  Description  [Load an array of ADDs from a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nAddArrayLoad(\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode ***operandBddArray   /* IN: Array of operand BDD */,\n  int *operandBddArraySize    /* IN: Number of ADD in the Array */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n  int i, j, nRoots;\n  DdNode **bddArray = NULL;\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD_ARRAY, &i);\n\n  /*------------------------------- Load ADDs -------------------------------*/\n\n  nRoots = Dddmp_cuddAddArrayLoad (ddMgr, rootmatchmode,\n    varInfo->rootNames, varmatchmode,\n    varInfo->orderedVarNames, varInfo->varIdsAll, varInfo->varComposeIdsAll,\n    DDDMP_MODE_DEFAULT, fileName, NULL, &bddArray);\n\n  Dddmp_CheckAndReturn (nRoots>DDDMP_MAX_BDDARRAY_LEN,\n    \"DDDMP_MAX_BDDARRAY_LEN exceeded by BDD array len (increase it).\");\n\n  if (nRoots<=0) {\n    return (DDDMP_FAILURE);\n  }\n\n  varInfo->nRoots = nRoots;\n  operandBddArray[i] = DDDMP_ALLOC (DdNode *, nRoots);\n  Dddmp_CheckAndReturn (operandBddArray[i]==NULL, \"Allocation error.\");\n\n  for (j=0; j<nRoots; j++) {\n    operandBddArray[i][j] = bddArray[j];\n  }\n  operandBddArraySize[i] = nRoots;\n\n  /*---------------------------- Tail Operations ----------------------------*/\n\n  /* Free array */\n  DDDMP_FREE (bddArray);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Load a CNF formula from a file, and create a BDD.]\n  \n  Description  [Load a CNF formula from a file, and create a BDD.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddLoadCnf (\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode **operandBdd         /* IN: Operand BDD */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  DdNode **rootsPtr = NULL;\n  Dddmp_DecompCnfLoadType loadingMode = DDDMP_CNF_MODE_CONJ_QUANT;\n  int i, retValue, nRoots;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n  \n  /*------------------------------- Load BDDs -------------------------------*/\n\n  fprintf (stdout, \"Loading %s ...\\n\", fileName);\n\n  retValue = Dddmp_cuddBddLoadCnf (ddMgr, varmatchmode,\n    varInfo->orderedVarNames, varInfo->varAuxIdsAll, varInfo->varComposeIdsAll,\n    loadingMode, fileName, NULL, &rootsPtr, &nRoots);\n\n  Dddmp_CheckAndGotoLabel (retValue==DDDMP_FAILURE,\n    \"Dddmp Test: Load From File Error.\\n\", failure);\n\n  operandBdd[i] = rootsPtr[0];\n\n  /*---------------------------- Tail Operations ----------------------------*/\n\n  /* Free array */\n  DDDMP_FREE (rootsPtr);\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n    return(DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Load a CNF formula from a file, and create an array of\n    BDDs.\n  ]\n\n  Description  [Load a CNF formula from a file, and create an array of\n    BDDs.\n  ]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddArrayLoadCnf (\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode ***operandBddArray   /* IN: Array of operand BDD */,\n  int *operandBddArraySize    /* IN: Number of ADD in the Array */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  DdNode **rootsPtr = NULL;\n  Dddmp_DecompCnfLoadType loadingMode = DDDMP_CNF_MODE_CONJ_QUANT;\n  int i, j, nRoots;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD_ARRAY, &i);\n\n  /*--------------------------- Loading BDDs --------------------------------*/\n\n  (void) Dddmp_cuddBddArrayLoadCnf (ddMgr, rootmatchmode,\n    varInfo->rootNames, varmatchmode,\n    varInfo->orderedVarNames, varInfo->varIdsAll, varInfo->varComposeIdsAll,\n    loadingMode, fileName, NULL, &rootsPtr, &nRoots);\n\n  Dddmp_CheckAndReturn (nRoots>DDDMP_MAX_BDDARRAY_LEN,\n    \"DDDMP_MAX_BDDARRAY_LEN exceeded by BDD array len (increase it).\");\n\n  if (nRoots<=0) {\n    return (DDDMP_FAILURE);\n  }\n\n  varInfo->nRoots = nRoots;\n  operandBddArray[i] = DDDMP_ALLOC (DdNode *, nRoots);\n  Dddmp_CheckAndReturn (operandBddArray[i]==NULL, \"Allocation error.\");\n\n  for (j=0; j<nRoots; j++) {\n    operandBddArray[i][j] = rootsPtr[j];\n  }\n  operandBddArraySize[i] = nRoots;\n\n  /*---------------------------- Tail Operations ----------------------------*/\n\n  /* Free array */\n  DDDMP_FREE (rootsPtr);\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Perform an Operation among BDDs.]\n  \n  Description  [Perform an Operation among BDDs.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nOperation(\n  DdManager *ddMgr      /* IN: CUDD Manager */,\n  DdNode **operandBdd   /* IN: Array of operandBdd */\n  )\n{\n  DdNode *f, *g, *h;\n  char buf[DDDMPTEST_MAX_STRING_LENGTH];\n  int i;\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_OP, buf);\n  ReadInt (DDDMP_MESSAGE_SOURCE1, &i);\n\n  f = operandBdd[i];\n\n  /*-------------------------- Compute Operation ----------------------------*/\n\n  if ((strcmp(buf, \"or\")==0)|| (strcmp(buf, \"OR\")==0)) {\n    ReadInt (DDDMP_MESSAGE_SOURCE2, &i);\n    g = operandBdd[i];\n    h = Cudd_bddOr(ddMgr, f, g);\n    Cudd_RecursiveDeref(ddMgr, f);\n    Cudd_Ref(h);\n    Cudd_RecursiveDeref(ddMgr, g);\n  } else if ((strcmp(buf, \"and\")==0) || (strcmp(buf, \"AND\")==0)) {\n      ReadInt (DDDMP_MESSAGE_SOURCE2, &i);\n      g = operandBdd[i];\n      h = Cudd_bddAnd(ddMgr, f, g);\n      Cudd_Ref(h);\n      Cudd_RecursiveDeref(ddMgr, f);\n      Cudd_RecursiveDeref(ddMgr, g);\n  } else if ((strcmp(buf, \"xor\")==0) || (strcmp(buf, \"XOR\")==0)) {\n      ReadInt (DDDMP_MESSAGE_SOURCE2, &i);\n      g = operandBdd[i];\n      h = Cudd_bddXor(ddMgr, f, g);\n      Cudd_Ref(h);\n      Cudd_RecursiveDeref(ddMgr, f);\n      Cudd_RecursiveDeref(ddMgr, g);\n  } else if (strcmp(buf, \"!\")==0) {\n      h = Cudd_Not(f);\n      Cudd_Ref(h);\n      Cudd_RecursiveDeref(ddMgr, f);\n  } else if ((strcmp(buf, \"buf\")==0)|| (strcmp(buf, \"BUF\")==0)) {\n      h = f;\n  } else {\n      fprintf (stderr, \"Dddmp Test Error : Operation %s unknown\\n\", buf);\n      h = NULL;\n  }\n\n  ReadInt (DDDMP_MESSAGE_DESTINATION, &i);\n\n  operandBdd[i] = h;\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store a BDD in a file.]\n  \n  Description  [Store a BDD in a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddStore (\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode **operandBdd         /* IN: Operand BDD */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  DdNode *f = NULL;\n  int i, retValue;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n\n  fprintf (stdout, \"Storing %s ...\\n\", fileName);\n  fflush (stdout);\n  f = operandBdd[i];\n\n  /*----------------------------- Store BDDs -------------------------------*/\n\n  retValue = Dddmp_cuddBddStore(ddMgr, NULL, f, varInfo->orderedVarNames,\n    varInfo->varAuxIdsAll, DDDMP_MODE_TEXT, varoutinfo, fileName, NULL);\n\n  Dddmp_CheckAndGotoLabel (retValue!=DDDMP_SUCCESS, \"BDD NOT stored.\",\n    failure);\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n    return(DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store an Array of BDD in a file.]\n  \n  Description  [Store an Array of BDD in a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddArrayStore (\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode ***operandBddArray   /* IN: Array of operand BDD */,\n  int *operandBddArraySize    /* IN: Number of ADD in the Array */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  int i, retValue, nRoots;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD_ARRAY, &i);\n\n  nRoots = operandBddArraySize[i];\n\n  /*----------------------------- Store BDDs -------------------------------*/\n\n  fprintf (stdout, \"Storing Array of BDDs in file %s ...\\n\", fileName);\n  fflush (stdout);\n\n  retValue = Dddmp_cuddBddArrayStore (ddMgr, NULL, nRoots, operandBddArray[i],\n    NULL, varInfo->orderedVarNames, varInfo->varAuxIdsAll, DDDMP_MODE_TEXT,\n    DDDMP_VARIDS, fileName, NULL);\n\n  Dddmp_CheckAndGotoLabel (retValue!=DDDMP_SUCCESS, \"BDD NOT stored.\",\n    failure);\n  fprintf (stdout, \"done.\\n\");\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n    return(DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store an ADD in a file.]\n  \n  Description  [Store an ADD in a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nAddStore(\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode **operandBdd         /* IN: operand Bdd */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  DdNode *f;\n  int i, retValue;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n\n  fprintf (stdout, \"Storing %s ...\\n\", fileName);\n  fflush (stdout);\n  f = operandBdd[i];\n\n#if 0\n  /* StQ Patch - CREATE temporary ADD to Store */\n  f = Cudd_addResidue (ddMgr, 4, 3, 1, 1);\n  fprintf (stderr, \"Store:\\n\");\n  Cudd_PrintMinterm (ddMgr, f);\n  /* end ... StQ Patch */\n#endif\n\n  retValue = Dddmp_cuddAddStore (ddMgr, NULL, f, varInfo->orderedVarNames,\n    varInfo->varAuxIdsAll, DDDMP_MODE_TEXT, varoutinfo, fileName, NULL);\n\n  Dddmp_CheckAndReturn (retValue!=DDDMP_SUCCESS, \"BDD NOT stored.\");\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store a BDD in a file.]\n  \n  Description  [Store a BDD in a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nAddArrayStore (\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode ***operandBddArray   /* IN: Array of operand ADD */,\n  int *operandBddArraySize    /* IN: Number of ADD in the Array */,\n  dddmpVarInfo_t *varInfo\n  )\n{\n  int i, retValue, nRoots;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD_ARRAY, &i);\n\n  nRoots = operandBddArraySize[i];\n\n  fprintf (stdout, \"Storing Array of BDDs in file %s ...\\n\", fileName);\n  fflush (stdout);\n\n  retValue = Dddmp_cuddAddArrayStore (ddMgr, NULL, nRoots, operandBddArray[i],\n    NULL, varInfo->orderedVarNames, varInfo->varAuxIdsAll, DDDMP_MODE_TEXT,\n    DDDMP_VARIDS, fileName, NULL);\n\n  Dddmp_CheckAndReturn (retValue!=DDDMP_SUCCESS, \"BDD NOT stored.\");\n\n  fprintf (stdout, \"done.\\n\");\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store a BDD as CNF format in a file.]\n  \n  Description  [Store a BDD as CNF format in a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddStoreCnf(\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode **operandBdd         /* IN: Array of operand ADD */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  DdNode *f = NULL;\n  Dddmp_DecompCnfStoreType storingMode = DDDMP_CNF_MODE_BEST;\n  int noHeader = 0;\n  int i, nVars, retValue, idInitial, varNewN, clauseNewN;\n  int edgeInTh = (-1);\n  int pathLengthTh = (-1);\n  int *tmpBddIds = NULL;\n  int *tmpCnfIds = NULL;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n  char row[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD, &i);\n  ReadString (DDDMP_MESSAGE_FORMAT, row);\n\n  switch (row[0]) {\n    case 'N':\n      storingMode = DDDMP_CNF_MODE_NODE;\n      break;\n    case 'M':\n      storingMode = DDDMP_CNF_MODE_MAXTERM;\n      break;\n    case 'B':\n      storingMode = DDDMP_CNF_MODE_BEST;\n      ReadInt (DDDMP_MESSAGE_EDGE_MAX, &edgeInTh);\n      ReadInt (DDDMP_MESSAGE_LENGHT_MAX, &pathLengthTh);\n      break;\n  }\n  ReadInt (DDDMP_MESSAGE_I_ID, &idInitial);\n\n  fprintf (stdout, \"Storing %s ...\\n\", fileName);\n  fflush (stdout);\n\n  f = operandBdd[i];\n\n  nVars = varInfo->nDdVars;\n\n  /*------------ From BDD and CNF ids to Proper Array of ids ----------------*/\n\n  tmpBddIds = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndGotoLabel (tmpBddIds==NULL, \"Error allocating memory.\",\n    failure);\n  tmpCnfIds = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndGotoLabel (tmpBddIds==NULL, \"Error allocating memory.\",\n    failure);\n\n  for (i=0; i<nVars; i++) {\n    tmpBddIds[i] = i;\n    tmpCnfIds[i] = i+1;\n  }\n\n  retValue = Dddmp_cuddBddStoreCnf (ddMgr, f, storingMode, noHeader,\n    varInfo->orderedVarNames, tmpBddIds, NULL, tmpCnfIds, idInitial,\n    edgeInTh, pathLengthTh, fileName, NULL, &clauseNewN, &varNewN);\n\n  Dddmp_CheckAndGotoLabel (retValue!=DDDMP_SUCCESS, \"BDD NOT stored.\",\n    failure);\n\n  fprintf (stdout, \"Number of Clauses Stored = %d\\n\", clauseNewN);\n  fprintf (stdout, \"Number of New Variable Created Storing = %d\\n\",\n    varNewN);\n  fflush (stdout);\n\n  DDDMP_FREE (tmpBddIds);\n  DDDMP_FREE (tmpCnfIds);\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n    DDDMP_FREE (tmpBddIds);\n    DDDMP_FREE (tmpCnfIds);\n\n    return(DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Store a BDD as CNF format in a file.]\n  \n  Description  [Store a BDD as CNF format in a file.]\n  \n  SideEffects  []\n  \n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nBddArrayStoreCnf(\n  DdManager *ddMgr            /* IN: CUDD Manager */,\n  DdNode ***operandBddArray   /* IN: Array of operand ADD */,\n  int *operandBddArraySize    /* IN: Number of ADD in the Array */,\n  dddmpVarInfo_t *varInfo     /* IN/OUT: Variable Information */\n  )\n{\n  Dddmp_DecompCnfStoreType storingMode = DDDMP_CNF_MODE_BEST;\n  int noHeader = 0;\n  int i, nVars, bddN, retValue, idInitial, varNewN, clauseNewN;\n  int edgeInTh = (-1);\n  int pathLengthTh = (-1);\n  int *tmpBddIds = NULL;\n  int *tmpCnfIds = NULL;\n  char fileName[DDDMPTEST_MAX_FILENAME_LENGTH];\n  char row[DDDMPTEST_MAX_FILENAME_LENGTH];\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadString (DDDMP_MESSAGE_FILE, fileName);\n  ReadInt (DDDMP_MESSAGE_BDD_ARRAY, &bddN);\n  ReadString (DDDMP_MESSAGE_FORMAT, row);\n  switch (row[0]) {\n    case 'N':\n      storingMode = DDDMP_CNF_MODE_NODE;\n      break;\n    case 'M':\n      storingMode = DDDMP_CNF_MODE_MAXTERM;\n      break;\n    case 'B':\n      storingMode = DDDMP_CNF_MODE_BEST;\n      ReadInt (DDDMP_MESSAGE_EDGE_MAX, &edgeInTh);\n      ReadInt (DDDMP_MESSAGE_LENGHT_MAX, &pathLengthTh);\n      break;\n  }\n  ReadInt (DDDMP_MESSAGE_I_ID, &idInitial);\n\n  nVars = varInfo->nDdVars;\n\n  /*------------ From BDD and CNF ids to Proper Array of ids ----------------*/\n\n  tmpBddIds = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndReturn (tmpBddIds==NULL, \"Allocation error.\");\n  tmpCnfIds = DDDMP_ALLOC (int, nVars);\n  Dddmp_CheckAndReturn (tmpCnfIds==NULL, \"Allocation error.\");\n\n  for (i=0; i<nVars; i++) {\n    tmpBddIds[i] = i;\n    tmpCnfIds[i] = i*10+1;\n  }\n\n  fprintf (stdout, \"Storing %s ...\\n\", fileName);\n  fflush (stdout);\n\n  retValue = Dddmp_cuddBddArrayStoreCnf (ddMgr, operandBddArray[bddN],\n    operandBddArraySize[bddN], storingMode, noHeader, varInfo->orderedVarNames,\n    tmpBddIds, NULL, tmpCnfIds, idInitial, edgeInTh, pathLengthTh, fileName,\n    NULL, &varNewN, &clauseNewN);\n\n  Dddmp_CheckAndGotoLabel (retValue!=DDDMP_SUCCESS, \"BDD NOT stored.\",\n    failure);\n\n  fprintf (stdout, \"Number of Clauses Stored = %d\\n\", clauseNewN);\n  fprintf (stdout, \"Number of New Variable Created Storing = %d\\n\",\n    varNewN);\n  fflush (stdout);\n\n  DDDMP_FREE (tmpBddIds);\n  DDDMP_FREE (tmpCnfIds);\n\n  return (DDDMP_SUCCESS);\n\n  failure:\n    DDDMP_FREE (tmpBddIds);\n    DDDMP_FREE (tmpCnfIds);\n\n    return(DDDMP_FAILURE);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Dynamic Reordering BDDs.]\n\n  Description  [Dynamic Reordering BDDs using one of the allowed CUDD\n    methods.]\n\n  SideEffects  []\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nDynamicReordering (\n  DdManager *ddMgr            /* IN: CUDD Manager */\n  )\n{\n  Cudd_ReorderingType approach = CUDD_REORDER_SIFT;\n  int method;\n\n  /*------------------------ Read Operation Operands ------------------------*/\n\n  ReadInt (DDDMP_MESSAGE_REORDERING, &method);\n  approach = (Cudd_ReorderingType) method;\n\n  Cudd_ReduceHeap (ddMgr, approach, 5);\n  \n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Selects variable matching mode.]\n\n  Description  [Selects variable matching mode.]\n\n  SideEffects  []\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nSetLoadMatchmode (\n  )\n{\n  int sel;\n  char row[DDDMPTEST_MAX_FILENAME_LENGTH];\n  char *retval;\n\n  fprintf (stdout, \"Variable matchmode:\\n\");\n  fprintf (stdout, \"Match IDs                                (1)\\n\");\n  fprintf (stdout, \"Match permIDs                            (2)\\n\");\n  fprintf (stdout, \"Match names      (must have been loaded) (3)\\n\");\n  fprintf (stdout, \"Match auxids     (must have been loaded) (4)\\n\");\n  fprintf (stdout, \"Match composeids (must have been loaded) (5)\\n\");\n  fprintf (stdout, \"Your choice: \");\n  fflush (stdout);\n\n  retval = fgets (row, DDDMPTEST_MAX_STRING_LENGTH, stdin);\n  if (!retval)\n    return (DDDMP_FAILURE);\n  sscanf (row, \"%d\", &sel);\n\n  switch (sel) {\n    case 1:\n      varmatchmode = DDDMP_VAR_MATCHIDS;\n      break;\n    case 2:\n      varmatchmode = DDDMP_VAR_MATCHPERMIDS;\n      break;\n    case 3:\n      varmatchmode = DDDMP_VAR_MATCHNAMES;\n      break;\n    case 4:\n      varmatchmode = DDDMP_VAR_MATCHAUXIDS;\n      break;\n    case 5:\n      varmatchmode = DDDMP_VAR_COMPOSEIDS;\n      break;\n    default:\n      fprintf (stderr, \"Wrong choice!\\n\");\n      break;\n  }\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Complete the internal manager structure for subsequent\n    BDD/ADD/CNF operations.\n  ]\n\n  Description  [Complete the internal manager structure for subsequent\n    BDD/ADD/CNF operations.\n    The phylosophy is simple: to have proper names and ids it is necessary\n    to load an header before each actual load/store operation.\n    An header load should initialize variable names, variable ids,\n    variable compose ids, and variable auxiliary ids for all variables\n    stored in the file.\n    This information has to be extended for all variables in the\n    *current* CUDD manager (before any store operation).\n    CompleteInfoStruct does this job.\n    Arrays varIds, varComposeIds, and varAuxIds contain information for\n    all the variable in the BDD/ADD/CNF while arrays varIdsAll,\n    varComposeIdsAll, and varAuxIdsAll contain information for *all*\n    variable in the current CUDD manager.\n  ]\n\n\n  SideEffects  []\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic int\nCompleteInfoStruct (\n  Dddmp_DecompType ddType  /* IN: selects the proper decomp type */,\n  int nVars                /* IN: number of DD variables */,\n  int nSuppVars            /* IN: number of support variables */,\n  char **suppVarNames      /* IN: array of support variable names */,\n  char **orderedVarNames   /* IN: array of variable names */,\n  int *varIds              /* IN: array of variable ids */,\n  int *varComposeIds       /* IN: array of permids ids */,\n  int *varAuxIds           /* IN: array of variable aux ids */,\n  int nRoots               /* IN: number of root in the file */,\n  dddmpVarInfo_t *varInfo  /* IN: Variable Information */\n  )\n{\n  int i;\n  char tmpString[DDDMPTEST_MAX_STRING_LENGTH];\n\n  /*------------------------- Updates Variable Names ------------------------*/\n\n  DddmpStrArrayFree (varInfo->suppVarNames, varInfo->nSuppVars);\n  varInfo->suppVarNames = suppVarNames;\n\n  if (varInfo->varNamesFlagUpdate == 1) {\n\n    DddmpStrArrayFree (varInfo->orderedVarNames, varInfo->nVars);\n\n    if (orderedVarNames != NULL) {\n      varInfo->orderedVarNames = orderedVarNames;\n    } else {\n      varInfo->orderedVarNames = DDDMP_ALLOC (char *, nVars);\n      Dddmp_CheckAndReturn (varInfo->orderedVarNames==NULL,\n        \"Allocation error.\");\n\n      for (i=0; i<nVars; i++) {\n        varInfo->orderedVarNames[i] = NULL;\n      }\n\n      if (varInfo->suppVarNames != NULL) {\n        for (i=0; i<nSuppVars; i++) {\n          varInfo->orderedVarNames[i] = DDDMP_ALLOC (char,\n            (strlen (varInfo->suppVarNames[i]) + 1));\n          strcpy (varInfo->orderedVarNames[i], varInfo->suppVarNames[i]);\n        }\n      }\n \n      for (i=0; i<nVars; i++) {\n        if (varInfo->orderedVarNames[i] == NULL) {\n          sprintf (tmpString, \"DUMMY%d\", i);\n          varInfo->orderedVarNames[i] = DDDMP_ALLOC (char,\n            (strlen (tmpString) + 1));\n          strcpy (varInfo->orderedVarNames[i], tmpString);\n        }\n      }\n    }\n  }\n\n  /*------------------------------ Updates IDs ------------------------------*/\n\n  DDDMP_FREE (varInfo->varIds);\n  varInfo->varIds = varIds;\n\n  if (varInfo->varIdsFlagUpdate == 1) {\n\n    /* Free Previously Allocated Memory */\n    DDDMP_FREE (varInfo->varIdsAll);\n\n    /* Allocate New Memory and Check */\n    varInfo->varIdsAll = DDDMP_ALLOC (int, nVars);\n    Dddmp_CheckAndReturn (varInfo->varIdsAll==NULL, \"Allocation error.\");\n\n    /* Set New Values */\n    for (i=0; i<nVars; i++) {\n      varInfo->varIdsAll[i] = (-1);\n    }\n\n    if (varInfo->varIds != NULL) {\n      for (i=0; i<nSuppVars; i++) {\n        varInfo->varIdsAll[varInfo->varIds[i]] = varInfo->varIds[i];\n      }\n    }\n  }\n\n\n  /*-------------------------- Updates Compose IDs --------------------------*/\n\n  DDDMP_FREE (varInfo->varComposeIds);\n  varInfo->varComposeIds = varComposeIds;\n\n  if (varInfo->varComposeIdsFlagUpdate == 1) {\n\n    /* Free Previously Allocated Memory */\n    DDDMP_FREE (varInfo->varComposeIdsAll);\n\n    /* Allocate New Memory and Check */\n    varInfo->varComposeIdsAll = DDDMP_ALLOC (int, nVars);\n    Dddmp_CheckAndReturn (varInfo->varComposeIdsAll==NULL,\n      \"Allocation error.\");\n\n    /* Set New Values */\n    for (i=0; i<nVars; i++) {\n      varInfo->varComposeIdsAll[i] = (-1);\n    }\n\n    if (varInfo->varComposeIds != NULL) {\n      for (i=0; i<nSuppVars; i++) {\n        varInfo->varComposeIdsAll[varInfo->varIds[i]] =\n          varInfo->varComposeIds[i];\n      }\n    }\n  }\n\n  /*------------------------- Updates Auxiliary IDs -------------------------*/\n\n  DDDMP_FREE (varInfo->varAuxIds);\n  varInfo->varAuxIds = varAuxIds;\n\n  if (varInfo->varAuxIdsFlagUpdate == 1) {\n\n    /* Free Previously Allocated Memory */\n    DDDMP_FREE (varInfo->varAuxIdsAll);\n\n    /* Allocate New Memory and Check */\n    varInfo->varAuxIdsAll = DDDMP_ALLOC (int, nVars);\n    Dddmp_CheckAndReturn (varInfo->varAuxIdsAll==NULL, \"Allocation error.\");\n\n    /* Set New Values */\n    for (i=0; i<nVars; i++) {\n      varInfo->varAuxIdsAll[i] = (-1);\n    }\n\n    if (varInfo->varAuxIds != NULL) {\n      for (i=0; i<nSuppVars; i++) {\n        varInfo->varAuxIdsAll[varInfo->varIds[i]] = varInfo->varAuxIds[i];\n      }\n    }\n  }\n\n  /*----------------------------- Updates Sizes -----------------------------*/\n\n  varInfo->ddType = ddType;\n  varInfo->nVars = nVars;\n  varInfo->nSuppVars = nSuppVars;\n  Dddmp_CheckAndReturn (varInfo->nDdVars<varInfo->nVars,\n    \"Local Manager with Not Enough Variables.\");\n  varInfo->nRoots = nRoots;\n\n  return (DDDMP_SUCCESS);\n}\n\n/**Function********************************************************************\n\n  Synopsis     [Reads an integer value from standard input.]\n\n  Description  [Reads an integer value from standard input.]\n\n  SideEffects  []\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic void\nReadInt (\n  Dddmp_MessageType message,\n  int *i\n  )\n{\n  char row[DDDMPTEST_MAX_FILENAME_LENGTH];\n  char *retval;\n\n  switch (message) {\n    case DDDMP_MESSAGE_MANAGER_VAR:\n      fprintf (stdout, \"Number of Variables: \");\n      break;\n    case DDDMP_MESSAGE_BDD:\n      fprintf (stdout, \"Which BDDs [0..%d]: \",\n        DDDMPTEST_MAX_OPERAND-1);\n      break;\n    case DDDMP_MESSAGE_BDD_ARRAY:\n      fprintf (stdout, \"Which Array of BDDs [0..%d]: \",\n        DDDMPTEST_MAX_OPERAND-1);\n      break;\n    case DDDMP_MESSAGE_CUBE:\n      fprintf (stdout, \"How many cubes [1..]: \");\n      break;\n    case DDDMP_MESSAGE_INDEX:\n      fprintf (stdout, \"Index: \");\n      break;\n    case DDDMP_MESSAGE_SOURCE1:\n      fprintf (stdout, \"Source1 [0..%d]: \", DDDMPTEST_MAX_OPERAND-1);\n      break;\n    case DDDMP_MESSAGE_SOURCE2:\n      fprintf (stdout, \"Source2 [0..%d]: \", DDDMPTEST_MAX_OPERAND-1);\n      break;\n    case DDDMP_MESSAGE_DESTINATION:\n      fprintf (stdout, \"Destination [0..%d]: \", DDDMPTEST_MAX_OPERAND-1);\n      break;\n    case DDDMP_MESSAGE_I_ID:\n      fprintf (stdout, \"Initial ID : \");\n      break;\n    case DDDMP_MESSAGE_EDGE_MAX:\n      fprintf (stdout,\n        \"Max Number of Edges (Insert cut-point from there on) : \");\n      break;\n     case DDDMP_MESSAGE_LENGHT_MAX:\n      fprintf (stdout,\n        \"Max BDD-Path Length (Insert cut-point from there on) : \");\n      break;\n    case DDDMP_MESSAGE_REORDERING:\n      fprintf (stdout, \"Reordering Approach (1..17): \");\n      break;\n    default:\n      fprintf (stdout, \"Input Generic Integer: \");\n      break;\n  }\n  fflush (stdout);\n\n  retval = fgets (row, DDDMPTEST_MAX_STRING_LENGTH, stdin);\n  if (!retval)\n    return;\n  sscanf (row, \"%d\", i);\n\n  return;\n}\n\n\n/**Function********************************************************************\n\n  Synopsis     [Reads a string from standard input.]\n\n  Description  [Reads a string from standard input.]\n\n  SideEffects  []\n\n  SeeAlso      []\n\n******************************************************************************/\n\nstatic void\nReadString (\n  Dddmp_MessageType message,\n  char string[]\n  )\n{\n  char localString[DDDMPTEST_MAX_STRING_LENGTH];\n  char *retval;\n\n  switch (message) {\n    case DDDMP_MESSAGE_PROMPT:\n      fprintf (stdout, \"TestDddmp> \");\n      break;\n    case DDDMP_MESSAGE_FILE:\n      fprintf (stdout, \"File : \");\n      break;\n    case DDDMP_MESSAGE_OP:\n      fprintf (stdout, \"Operation [or,and,xor,!,buf(=)] : \");\n      break;\n    case DDDMP_MESSAGE_FORMAT:\n      fprintf (stdout, \"Format (Node=N, Maxterm=M, Best=B) : \");\n      break;\n    default:\n      fprintf (stdout, \"Input Generic String : \");\n      break;\n  }\n  fflush (stdout);\n\n  string[0] = '\\n';\n  retval = fgets (localString, DDDMPTEST_MAX_STRING_LENGTH, stdin);\n  if (!retval)\n    return;\n  sscanf (localString, \"%s\", string);\n\n  return;\n}\n\n\n\n\n"
  },
  {
    "path": "cudd/doc/Included.am",
    "content": "EXTRA_DIST += doc/phase.pdf\n\nif HAVE_PDFLATEX\n\ndoc/cudd.pdf: doc/cudd.tex $(top_srcdir)/doc/phase.pdf\n\t@if $(AM_V_P); then dest='2>&1'; else dest='> /dev/null 2>&1'; fi; \\\n\tcd doc && eval \"$(PDFLATEX) cudd $${dest}\" && \\\n\teval \"$(MAKEINDEX) cudd $${dest}\" && \\\n\teval \"$(PDFLATEX) cudd $${dest}\" && \\\n\teval \"$(PDFLATEX) cudd $${dest}\"\n\nCLEANFILES += doc/cudd.pdf doc/cudd.aux doc/cudd.idx doc/cudd.ilg doc/cudd.ind \\\n  doc/cudd.log doc/cudd.out doc/cudd.toc\n\nelse\n\ndoc/cudd.pdf:\n\nendif\n"
  },
  {
    "path": "cudd/doc/cudd.tex.in",
    "content": "%\n%  Copyright (c) 1995-2015, Regents of the University of Colorado\n%\n%  All rights reserved.\n%\n\\documentclass[11pt]{article}\n\\usepackage{makeidx}\n\\usepackage{graphicx,color}\n%\\usepackage[pdfpagelabels=false,pageanchor,hyperindex,breaklinks,plainpages=false]{hyperref}\n\\usepackage[pdfpagelabels=false,pageanchor,hyperindex,plainpages=false]{hyperref}\n\\newcommand{\\eidx}[1]{\\index{#1@\\emph{#1}}}\n\\newcommand{\\vnumber}{2.7.0}\n\\title{CUDD: CU Decision Diagram Package\\\\Release \\vnumber}\n\\author{Fabio Somenzi\\\\\nDepartment of Electrical, Computer, and Energy Engineering\\\\\nUniversity of Colorado at Boulder\\\\\n$<$Fabio@Colorado.EDU$>$}\n\\makeindex\n\\begin{document}\n\\bibliographystyle{plain}\n\\maketitle\n\n\\tableofcontents\n\\clearpage\n\n%----------------------------------------\n\\section{Introduction}\n\\label{sec:intro}\n\nThe CUDD package provides functions to manipulate Binary Decision\nDiagrams\\index{BDD} (BDDs) \\cite{BDD,BBR},\nAlgebraic Decision Diagrams\\index{ADD} (ADDs)\n\\cite{Bahar93}, and Zero-suppressed Binary Decision\nDiagrams\\index{ZDD} (ZDDs)\n\\cite{Minato93}. BDDs are used to represent\nswitching\\index{function!switching} functions; ADDs are used to\nrepresent functions from $\\{0,1\\}^n$ to an arbitrary set.  ZDDs\nrepresent switching\\index{function!switching} functions like BDDs;\nhowever, they are much more efficient than BDDs when the functions to\nbe represented are characteristic\\index{function!characteristic}\nfunctions of cube\\index{cube sets} sets, or in general, when the\nON-set\\index{function!ON-set} of the function to be represented is\nvery sparse. They are inferior to BDDs in other cases.\n\nThe package provides a large set of operations on BDDs, ADDs, and\nZDDs, functions to convert BDDs into ADDs or ZDDs and vice versa, and\na large assortment of variable reordering\\index{reordering} methods.\n\nThe CUDD package can be used in three ways:\n\\begin{itemize}\n\\item As a black box\\index{box!black}.  In this case, the application\n  program that needs to manipulate decision diagrams only uses the\n  exported functions of the package. The rich set of functions\n  included in the CUDD package allows many applications to be written\n  in this way.  Section~\\ref{sec:user} describes how to use the\n  exported functions of the package. An application written in terms\n  of the exported functions of the package needs not concern itself\n  with the details of variable reordering\\index{reordering}, which may\n  take place behind the scenes.\n\\item As a clear box\\index{box!clear}. When writing a sophisticated\n  application based on decision diagrams, efficiency often dictates\n  that some functions be implemented as direct recursive manipulation\n  of the diagrams, instead of being written in terms of existing\n  primitive functions.  Section~\\ref{sec:prog} explains how to add new\n  functions to the CUDD package. It also details how to write a\n  recursive function that may be interrupted by\n  dynamic\\index{reordering!dynamic} variable reordering.\n\\item Through an interface. Object-oriented languages like C++ and\n  Perl5 can free the programmer from the burden of memory management.\n  A C++ interface is included in the distribution of CUDD. It\n  automatically frees decision diagrams that are no longer used by the\n  application and overloads operators. Almost all the functionality\n  provided by the CUDD exported functions is available through the C++\n  interface, which is especially recommended for fast prototyping.\n  Section~\\ref{sec:cpp} explains how to use the interface. A Perl5\n  interface also exists and is ditributed separately. (See\n  Section~\\ref{sec:getFriends}.)\n\\end{itemize}\nIn the following, the reader is supposed to be familiar with the basic\nideas about decision diagrams, as found, for instance, in \\cite{BBR}.\n\n%----------------------------------------\n\\section{How to Get CUDD}\n\\label{sec:getting}\n\n\\subsection{The CUDD Package}\n\\label{sec:getCUDD}\n\nThe CUDD package is available via anonymous FTP\\index{FTP} from\nvlsi.Colorado.EDU\\@.  A compressed tar file named\n\\texttt{cudd-\\vnumber.tar.gz} can be found in directory \\texttt{pub}.\nOnce you have this file,\n\\begin{quote}\n  \\tt gzip\\index{gzip} -dc cudd-\\vnumber.tar.gz | tar xvf -\n\\end{quote}\nwill create directory \\texttt{cudd-\\vnumber} and its subdirectories.\nThese directories contain the decision diagram package, a few support\nlibraries\\index{libraries}, and a test application based on the\ndecision diagram package.  There is a README\\index{README file} file\nwith instructions on configuration\\index{configuration} and\ninstallation\\index{installation} in \\texttt{cudd-\\vnumber}.  In short,\nCUDD uses the GNU Autotools for its build.\n\nOnce you have made the libraries and program, you can type\n\\texttt{make check} to perform a sanity check.  Among other things,\n\\texttt{make check} executes commands like\n\\begin{quote}\n  \\tt cd nanotrav\\index{nanotrav} \\\\\n  nanotrav -p 1 -autodyn -reordering sifting -trav mult32a.blif\n\\end{quote}\nThis command runs a simple-minded FSM traversal program on a simple\nmodel. (On a reasonable machine, it takes less than 0.5 s.) The output\nproduced by the program is checked against\n\\texttt{cudd-\\vnumber/nanotrav/mult32a.out}.  More information on the\n\\texttt{nanotrav\\index{nanotrav}} test program can be found in the file\n\\texttt{cudd-\\vnumber/nanotrav/README\\index{README file}}.\n\nIf you want to be notified of new releases of the CUDD package, send a\nmessage to \\texttt{Fabio@Colorado.EDU}.\n\n\\subsection{CUDD Friends}\n\\label{sec:getFriends}\n\nTwo CUDD extensions are available via anonymous FTP\\index{FTP} from\nvlsi.Colorado.EDU\\@.\n\\begin{itemize}\n\\item \\emph{PerlDD} is an object-oriented Perl5 interface to CUDD. It\n  is organized as a standard Perl extension module. The Perl interface\n  is at a somewhat higher level than the C++ interface, but it is not\n  as complete.\n\\item \\emph{DDcal} is a graphic BDD calculator based on CUDD, Perl-Tk,\n  and dot. (See Section~\\ref{sec:dump} for information on \\emph{dot}.)\n\n\\end{itemize}\n%----------------------------------------\n\\section{User's Manual}\n\\label{sec:user}\n\nThis section describes the use of the CUDD package as a black box.\n\n\\subsection{Compiling and Linking}\n\\label{sec:compileExt}\\index{compiling}\n\nTo build an application that uses the CUDD package, you should add\n\\begin{verbatim}\n#include \"cudd.h\"\n\\end{verbatim}\n\\index{cudd.h}\nto your source files, and should link\n\\verb|libcudd.a|\\index{libraries!cudd} to your executable.\n\nKeep in mind that whatever flags affect the size of data\nstructures---for instance the flags used to use 64-bit pointers where\navailable---must be specified when compiling both CUDD and the files\nthat include its header files.\n\n\\subsection{Basic Data Structures}\n\\label{sec:struct}\n\n\\subsubsection{Nodes}\n\\label{sec:nodes}\n\nBDDs, ADDs, and ZDDs are made of DdNode's. A DdNode\\index{DdNode}\n(node\\index{node} for short) is a structure with several fields. Those\nthat are of interest to the application that uses the CUDD package as\na black box are the variable index\\index{node!variable index}, the\nreference\\index{node!reference count} count, and the value. The\nremaining fields are pointers that connect nodes among themselves and\nthat are used to implement the unique\\index{table!unique} table. (See\nSection~\\ref{sec:manager}.)\n\nThe \\emph{index} field holds the name of the variable that labels the\nnode. The index of a variable is a permanent attribute that reflects\nthe order\\index{variable!order} of creation.  Index 0 corresponds to\nthe variable created first. On a machine with 32-bit pointers, the\nmaximum number of variables is the largest value that can be stored in\nan unsigned short integer minus 1. The largest index is reserved for\nthe constant\\index{node!constant} nodes. When 64-bit pointers are\nused, the maximum number of variables is the largest value that can be\nstored in an unsigned integer minus 1.\n\nWhen variables are reordered to reduce the size of the decision\ndiagrams, the variables may shift in the order, but they retain their\nindices. The package keeps track of the variable\npermutation\\index{variable!permutation} (and its inverse). The\napplication is not affected by variable reordering\\index{reordering},\nexcept in the following cases.\n\\begin{itemize}\n\\item If the application uses generators\\index{generator}\n  (\\emph{Cudd\\_ForeachCube} \\eidx{Cudd\\_ForeachCube} and\n  \\emph{Cudd\\_ForeachNode}\\eidx{Cudd\\_ForeachNode}) and reordering is\n  enabled, then it must take care not to call any operation that may\n  create new nodes (and hence possibly trigger reordering). This is\n  because the cubes (i.e., paths) and nodes of a diagram change as a\n  result of reordering.\n\\item If the application uses\n  \\emph{Cudd\\_bddConstrain}\\eidx{Cudd\\_bddConstrain} and reordering\n  takes place, then the property of \\emph{Cudd\\_bddConstrain} of\n  being an image restrictor is lost.\n\\end{itemize}\n\nThe CUDD package relies on garbage\\index{garbage collection}\ncollection to reclaim the memory used by diagrams that are no longer\nin use. The scheme employed for garbage collection is based on keeping\na reference\\index{node!reference count} count for each node.  The\nreferences that are counted are both the internal references\n(references from other nodes) and external references (typically\nreferences from the calling environment).  When an application creates\na new BDD\\index{BDD}, ADD\\index{ADD}, or ZDD\\index{ZDD}, it must\nincrease its reference count explicitly, through a call to\n\\emph{Cudd\\_Ref}\\eidx{Cudd\\_Ref}.  Similarly, when a diagram is no\nlonger needed, the application must call\n\\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref} (for BDDs and\nADDs) or \\emph{Cudd\\_RecursiveDerefZdd}\\eidx{Cudd\\_RecursiveDerefZdd}\n(for ZDDs) to ``recycle\\index{node!recycling}'' the nodes of the\ndiagram.\n\nTerminal\\index{node!constant!value} nodes carry a value. This is especially\nimportant for ADDs.  By default, the value is a double%\n\\index{floating point!double (C type)}.\nTo change to something different (e.g., an integer), the\npackage must be modified and recompiled.  Support for this process is\nvery rudimentary.\n\n\\subsubsection{The Manager}\n\\index{manager}\\label{sec:manager}\n\nAll nodes used in BDDs, ADDs, and ZDDs are kept in special\nhash\\index{table!hash} tables called the\n\\emph{unique\\index{table!unique} tables}.  Specifically, BDDs and ADDs\nshare the same unique table, whereas ZDDs have their own table.  As\nthe name implies, the main purpose of the unique table is to guarantee\nthat each node is unique; that is, there is no other node labeled by\nthe same variable and with the same children.  This uniqueness\nproperty makes decision diagrams canonical\\index{canonical}.  The\nunique\\index{table!unique} tables and some auxiliary data structures\nmake up the DdManager\\index{DdManager} (manager\\index{manager} for\nshort).  Though the application that uses only the exported functions\nneeds not be concerned with most details of the manager, it has to\ndeal with the manager in the following sense. The application must\ninitialize the manager by calling an appropriate function.  (See\nSection~\\ref{sec:init}.)  Subsequently, it must pass a pointer to the\nmanager to all the functions that operate on decision diagrams.\n\n% With the exception of a few statistical counters\\index{statistical\n%   counters}, there are no global\\index{global variables} variables in\n% the CUDD package. Therefore, it is possible to have multiple\n% managers simultaneously active in the same application.\\footnote{The\n%   global statistical counters are used locally; hence they are\n%   compatible with the use of multiple managers.} It is the pointers to\n% the managers that tell the functions on what data they should operate.\n\n\\subsubsection{Cache}\n\\index{cache}\\label{sec:memoize}\n\nEfficient recursive manipulation of decision diagrams requires the use\nof a table to store computed results. This table\\index{table!computed}\nis called here the \\emph{cache\\index{cache}} because it is\neffectively handled like a cache of variable but limited capacity. The\nCUDD package starts by default with a small cache, and increases its\nsize until either no further benefit is achieved, or a limit size is\nreached. The user can influence this policy by choosing initial and\nlimit values for the cache size.\n\nToo small a cache will cause frequent overwriting of useful results.\nToo large a cache will cause overhead, because the whole cache is\nscanned every time garbage\\index{garbage collection} collection takes\nplace. The optimal parameters depend on the specific application. The\ndefault parameters work reasonably well for a large spectrum of\napplications.\n\nThe cache\\index{cache} of the CUDD package is used by most recursive\nfunctions of the package, and can be used by user-supplied functions\nas well. (See Section~\\ref{sec:cache}.)\n\n\\subsection{Initializing and Shutting Down a DdManager}\n\\index{DdManager}\\label{sec:init}\n\nTo use the functions in the CUDD package, one has first to initialize\nthe package itself by calling \\emph{Cudd\\_Init}\\eidx{Cudd\\_Init}.\nThis function takes four parameters:\n\\begin{itemize}\n\\item numVars\\index{numVars}: It is the initial number of variables\n  for BDDs and ADDs. If the total number of variables needed by the\n  application is known, then it is slightly more efficient to create a\n  manager with that number of variables. If the number is unknown, it\n  can be set to 0, or to any other lower bound on the number of\n  variables.  Requesting more variables than are actually needed is\n  not incorrect, but is not efficient.\n\\item numVarsZ\\index{numVarsZ}: It is the initial number of variables\n  for ZDDs. See Sections~\\ref{sec:basicZDD} and~\\ref{sec:convertZ} for\n  a discussion of the value of this argument.\n\\item numSlots\\index{numSlots}: Determines the initial size of each\n  subtable\\index{subtable} of the unique\\index{table!unique} table.\n  There is a subtable for each variable.  The size of each subtable is\n  dynamically adjusted to reflect the number of nodes.  It is normally\n  O.K. to use the default value for this parameter, which is\n  CUDD\\_UNIQUE\\_SLOTS\\index{CUDD\\_UNIQUE\\_SLOTS}.\n\\item cacheSize\\index{cacheSize}: It is the initial size (number of\n  entries) of the cache\\index{cache}. Its default value is\n  CUDD\\_CACHE\\_SLOTS\\index{CUDD\\_CACHE\\_SLOTS}.\n\\item maxMemory\\index{maxMemory}: It is the target value for the\n  maximum memory occupation (in bytes).  The package uses this value to\n  decide two parameters.\n  \\begin{itemize}\n  \\item the maximum size to which the cache will grow, regardless of\n    the hit rate or the size of the unique\\index{table!unique} table.\n  \\item the maximum size to which growth of the unique table will be\n    preferred to garbage collection.\n  \\end{itemize}\n  If maxMemory is set to 0, CUDD tries to guess a good value based on\n  the available memory.\n\\end{itemize}\nA typical call to \\emph{Cudd\\_Init}\\eidx{Cudd\\_Init} may look\nlike this:\n\\begin{verbatim}\n  manager = Cudd_Init(0,0,CUDD_UNIQUE_SLOTS,CUDD_CACHE_SLOTS,0);\n\\end{verbatim}\nTo reclaim all the memory associated with a manager, an application\nmust call \\emph{Cudd\\_Quit}\\eidx{Cudd\\_Quit}.  This is normally\ndone before exiting.\n\n\n\\subsection{Setting Parameters}\n\\label{sec:params}\n\nThe package provides several functions to set the parameters that\ncontrol various functions. For instance, the package has an automatic\nway of determining whether a larger unique\\index{table!unique} table\nwould make the application run faster.  In that case, the package\nenters a ``fast growth\\index{table!growth}'' mode in which resizing of\nthe unique subtables is favored over garbage\\index{garbage collection}\ncollection. When the unique table reaches a given size, however, the\npackage returns to the normal ``slow growth'' mode, even though the\nconditions that caused the transition to fast growth still prevail.\nThe limit size for fast growth\\index{growth} can be read by\n\\emph{Cudd\\_ReadLooseUpTo}\\eidx{Cudd\\_ReadLooseUpto} and changed by\n\\emph{Cudd\\_SetLooseUpTo}\\eidx{Cudd\\_SetLooseUpTo}.  Similar pairs of\nfunctions exist for several other parameters. See also\nSection~\\ref{sec:stats}.\n\n\\subsection{Constant Functions}\n\\index{node!constant}\\label{sec:const}\n\nThe CUDD Package defines several constant functions. These functions\nare created when the manager\\index{manager} is initialized, and are accessible\nthrough the manager itself.\n\n\\subsubsection{One, Logic Zero, and Arithmetic Zero}\n\\index{zero!logical}\\index{zero!arithmetic}\\label{sec:zero}\n\nThe constant\\index{node!constant} 1 (returned by\n\\emph{Cudd\\_ReadOne}\\eidx{Cudd\\_ReadOne}) is common to BDDs, ADDs, and\nZDDs.  However, its meaning is different for ADDs and BDDs, on the one\nhand, and ZDDs, on the other hand.  The diagram consisting of the\nconstant 1 node only represents the constant 1 function for ADDs and\nBDDs. For ZDDs, its meaning depends on the number of variables: It is\nthe conjunction of the complements of all variables.  Conversely, the\nrepresentation of the constant 1 function depends on the number of\nvariables. The constant 1 function of $n$ variables is returned by\n\\emph{Cudd\\_ReadZddOne}\\eidx{Cudd\\_ReadZddOne}.\n\nThe constant 0 is common to ADDs and ZDDs, but not to BDDs.  The\nBDD\\index{BDD} logic 0 is {\\bf not} associated with the constant 0\nfunction: It is obtained by complementation\n(\\emph{Cudd\\_Not}\\eidx{Cudd\\_Not}) of the constant 1.  (It is also\nreturned by \\emph{Cudd\\_ReadLogicZero}\\eidx{Cudd\\_ReadLogicZero}.)\nAll other constants are specific to ADDs.\n\n\\subsubsection{Predefined Constants}\n\\label{sec:predef-const}\n\nBesides 0 (returned by \\emph{Cudd\\_ReadZero}\\eidx{Cudd\\_ReadZero})\nand 1, the following constant\\index{node!constant} functions are\ncreated at initialization time.\n\\begin{enumerate}\n\\item PlusInfinity\\index{PlusInfinity} and\n  MinusInfinity\\index{MinusInfinity}: On computers implementing the\n  IEEE\\index{floating point!IEEE Standard 754} standard 754 for\n  floating-point\\index{floating point} arithmetic, these two constants\n  are set to the signed infinities\\index{infinities}.  The values of\n  these constants are returned by\n  \\emph{Cudd\\_ReadPlusInfinity}\\eidx{Cudd\\_ReadPlusInfinity} and\n  \\emph{Cudd\\_ReadMinusInfinity}\\eidx{Cudd\\_ReadMinusInfinity}.\n\\item Epsilon\\index{Epsilon}: This constant, initially set to\n  $10^{-12}$, is used in comparing floating point values for equality.\n  Its value is returned by the function\n  \\emph{Cudd\\_ReadEpsilon}\\eidx{Cudd\\_ReadEpsilon}, and it can be\n  modified by calling \\emph{Cudd\\_SetEpsilon}\\eidx{Cudd\\_SetEpsilon}.\n  Unlike the other constants, it does not correspond to a node.\n\\end{enumerate}\n\n\\subsubsection{Background}\n\\index{background value}\\label{sec:background}\n\nThe background value is a constant\\index{node!constant} typically used\nto represent non-existing arcs in graphs. Consider a shortest path\nproblem. Two nodes that are not connected by an arc can be regarded as\nbeing joined by an arc\\index{graph!arc length} of infinite length. In\nshortest path problems, it is therefore convenient to set the\nbackground value to PlusInfinity\\index{PlusInfinity}. In network flow\nproblems, on the other hand, two nodes not connected by an arc can be\nregarded as joined by an arc\\index{graph!arc capacity} of 0 capacity.\nFor these problems, therefore, it is more convenient to set the\nbackground value to 0.  In general, when representing\nsparse\\index{matrix!sparse} matrices, the background value is the value that\nis assumed implicitly.\n\nAt initialization, the background value is set to 0. It can be read\nwith \\emph{Cudd\\_ReadBackground}\\eidx{Cudd\\_ReadBackground}, and\nmodified with \\emph{Cudd\\_SetBackground}.  The background value\naffects procedures that read sparse matrices and graphs\n(like \\emph{Cudd\\_addRead}\\eidx{Cudd\\_addRead} and\n\\emph{Cudd\\_addHarwell}\\eidx{Cudd\\_addHarwell}), procedures that print\nout sum-of-product\\index{function!sum of products} expressions for\nADDs (\\emph{Cudd\\_PrintMinterm}\\eidx{Cudd\\_PrintMinterm}), generators\nof cubes (\\emph{Cudd\\_ForeachCube}\\eidx{Cudd\\_ForeachCube}), and\nprocedures that count minterms\\index{function!minterms}\n(\\emph{Cudd\\_CountMinterm}\\eidx{Cudd\\_CountMinterm}).\n\n\\subsubsection{New Constants}\n\\label{sec:newconst}\n\nNew constant\\index{node!constant} can be created by calling\n\\emph{Cudd\\_addConst}\\eidx{Cudd\\_addConst}. This function will\nretrieve the ADD\\index{ADD} for the desired constant, if it already\nexist, or it will create a new one.  Obviously, new constants should\nonly be used when manipulating ADDs.\n\n\\subsection{Creating Variables}\n\\label{sec:newvar}\n\nDecision diagrams are typically created by combining simpler decision\ndiagrams.  The simplest decision diagrams, of course, cannot be\ncreated in that way.  Constant functions have been discussed in\nSection~\\ref{sec:const}.  In this section we discuss the simple\nvariable functions, also known as \\emph{projection\\index{projection\n    functions} functions}.\n\n\\subsubsection{New BDD and ADD Variables}\n\\label{sec:BDDADDvar}\n\nThe projection\\index{projection functions} functions are distinct for\nBDDs and ADDs. A projection function for BDDs consists of an internal\nnode with both outgoing arcs pointing to the constant 1. The\n\\emph{else} arc\\index{arc!complement} is complemented.\n\nAn ADD projection function, on the other hand, has the \\emph{else}\npointer directed to the arithmetic\\index{zero!arithmetic} zero\nfunction. One should never mix the two types of variables.  BDD\nvariables should be used when manipulating BDDs, and ADD variables\nshould be used when manipulating ADDs.  Three functions are provided\nto create BDD variables:\n\\begin{itemize}\n\\item \\emph{Cudd\\_bddIthVar}\\eidx{Cudd\\_bddIthVar}: Returns\n  the projection\\index{projection functions} function with index $i$.\n  If the function does not exist, it is created.\n\\item \\emph{Cudd\\_bddNewVar}\\eidx{Cudd\\_bddNewVar}: Returns a\n  new projection\\index{projection functions} function, whose index is\n  the largest index in use at the time of the call, plus 1.\n\\item \\emph{Cudd\\_bddNewVarAtLevel}\\eidx{Cudd\\_bddNewVarAtLevel}:\n  Similar to \\emph{Cudd\\_bddNewVar}\\eidx{Cudd\\_bddNewVar}.  In\n  addition it allows to specify the position in the variable\n  order\\index{variable!order} at which the new variable should be\n  inserted.  In contrast, \\emph{Cudd\\_bddNewVar}\\eidx{Cudd\\_bddNewVar}\n  adds the new variable at the end of the order.\n\\end{itemize}\nThe analogous functions for ADDs are\n\\emph{Cudd\\_addIthVar}\\eidx{Cudd\\_addIthVar},\n\\emph{Cudd\\_addNewVar}\\eidx{Cudd\\_addNewVar}, and\n\\emph{Cudd\\_addNewVarAtLevel}\\eidx{Cudd\\_addNewVarAtLevel}.\n\n\\subsubsection{New ZDD Variables}\n\\index{ZDD}\\label{sec:ZDDvars}\n\nUnlike the projection functions of BDDs and ADDs, the\nprojection\\index{projection functions} functions of ZDDs have diagrams\nwith $n+1$ nodes, where $n$ is the number of variables.  Therefore the\nZDDs of the projection functions change when new variables are added.\nThis will be discussed in Section~\\ref{sec:basicZDD}.  Here we assume\nthat the number of variables is fixed. The ZDD of the $i$-th\nprojection function is returned by\n\\emph{Cudd\\_zddIthVar}\\eidx{Cudd\\_zddIthVar}.\n\n\\subsection{Basic BDD Manipulation}\n\\index{BDD}\\label{sec:basicBDD}\n\nCommon manipulations of BDDs can be accomplished by calling\n\\emph{Cudd\\_bddIte}.  This function takes three BDDs, $f$, $g$, and\n$h$, as arguments and computes $f\\cdot g + f'\\cdot h$. Like all the\nfunctions that create new BDDs or ADDs, \\emph{Cudd\\_bddIte}\\eidx{Cudd\\_bddIte} returns a result that must be\nexplicitly referenced by the caller.  \\emph{Cudd\\_bddIte} can be used\nto implement all two-argument Boolean functions.  However, the package\nalso provides \\emph{Cudd\\_bddAnd}\\eidx{Cudd\\_bddAnd} as well as the\nother two-operand Boolean functions, which are slightly more efficient\nwhen a two-operand function is called for.  The following fragment of\ncode illustrates how to build the BDD for the function $f =\nx_0'x_1'x_2'x_3'$.\n\\begin{verbatim}\n\tDdManager *manager;\n\tDdNode *f, *var, *tmp;\n\tint i;\n\n\t...\n\n\tf = Cudd_ReadOne(manager);\n\tCudd_Ref(f);\n\tfor (i = 3; i >= 0; i--) {\n\t    var = Cudd_bddIthVar(manager,i);\n\t    tmp = Cudd_bddAnd(manager,Cudd_Not(var),f);\n\t    Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(manager,f);\n\t    f = tmp;\n\t}\n\\end{verbatim}\nThis example illustrates the following points:\n\\begin{itemize}\n\\item Intermediate results must be ``referenced'' and\n  ``dereferenced.''  However, \\texttt{var} is a\n  projection\\index{projection functions} function, and its\n  reference\\index{node!reference count} count is always greater than\n  0.  Therefore, there is no call to \\emph{Cudd\\_Ref}\\eidx{Cudd\\_Ref}.\n\\item The new \\texttt{f} must be assigned to a temporary variable\n  (\\texttt{tmp} in this example).  If the result of\n  \\emph{Cudd\\_bddAnd}\\eidx{Cudd\\_bddAnd} were assigned directly to\n  \\texttt{f}, the old \\texttt{f} would be lost, and there would be no\n  way to free its nodes.\n\\item The statement \\texttt{f = tmp} has the same effect as:\n\\begin{verbatim}\n\t    f = tmp;\n\t    Cudd_Ref(f);\n\t    Cudd_RecursiveDeref(manager,tmp);\n\\end{verbatim}\n  but is more efficient. The reference\\index{node!reference count} is\n  ``passed'' from \\texttt{tmp} to \\texttt{f}, and \\texttt{tmp} is now\n  ready to be reutilized.\n\\item It is normally more efficient to build BDDs ``bottom-up.''  This\n  is why the loop goes from 3 to 0.  Notice, however, that after\n  variable reordering, higher index does not necessarily mean ``closer\n  to the bottom.''  Of course, in this simple example, efficiency is\n  not a concern.\n\\item Had we wanted to conjoin the variables in a bottom-up fashion\n  even after reordering, we should have used\n  \\emph{Cudd\\_ReadInvPerm}\\eidx{Cudd\\_ReadInvPerm}.  One has to be\n  careful, though, to fix the order of conjunction before entering the\n  loop. Otherwise, if reordering takes place, it is possible to use\n  one variable twice and skip another variable.\n\\end{itemize}\n\n\\subsection{Basic ADD Manipulation}\n\\index{ADD}\\label{sec:basicADD}\n\nThe most common way to manipulate ADDs is via\n\\emph{Cudd\\_addApply}\\eidx{Cudd\\_addApply}.  This function can apply a\nwide variety of operators to a pair of ADDs.  Among the available\noperators are addition, multiplication, division, minimum, maximum,\nand Boolean operators that work on ADDs whose leaves are restricted to\n0 and 1 (0-1 ADDs).\n\nThe following fragment of code illustrates how to build the ADD for\nthe function $f = 5x_0x_1x_2x_3$.\n\\begin{verbatim}\n\tDdManager *manager;\n\tDdNode *f, *var, *tmp;\n\tint i;\n\n\t...\n\n\tf = Cudd_addConst(manager,5);\n\tCudd_Ref(f);\n\tfor (i = 3; i >= 0; i--) {\n\t    var = Cudd_addIthVar(manager,i);\n\t    Cudd_Ref(var);\n\t    tmp = Cudd_addApply(manager,Cudd_addTimes,var,f);\n\t    Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(manager,f);\n\t    Cudd_RecursiveDeref(manager,var);\n\t    f = tmp;\n\t}\n\\end{verbatim}\nThis example, contrasted to the example of BDD manipulation,\nillustrates the following points:\n\\begin{itemize}\n\\item The ADD projection\\index{projection functions} function are not\n  maintained by the manager.  It is therefore necessary to\n  reference\\index{node!reference} and\n  dereference\\index{node!dereference} them.\n\\item The product of two ADDs is computed by calling\n  \\emph{Cudd\\_addApply}\\eidx{Cudd\\_addApply} with\n  \\emph{Cudd\\_addTimes}\\eidx{Cudd\\_addTimes} as parameter.  There is\n  no ``apply'' function for BDDs, because\n  \\emph{Cudd\\_bddAnd}\\eidx{Cudd\\_bddAnd} and\n  \\emph{Cudd\\_bddXor}\\eidx{Cudd\\_bddXor} plus complementation are\n  sufficient to implement all two-argument Boolean functions.\n\\end{itemize}\n\n\\subsection{Basic ZDD Manipulation}\n\\index{ZDD}\\label{sec:basicZDD}\n\nZDDs are often generated by converting\\index{conversion!of BDDs to ZDDs}\nexisting BDDs.  (See Section~\\ref{sec:convertZ}.) However, it is also\npossible to build ZDDs by applying Boolean operators to other ZDDs,\nstarting from constants and projection\\index{projection functions}\nfunctions.  The following fragment of code illustrates how to build\nthe ZDD for the function $f = x_0'+x_1'+x_2'+x_3'$. We assume that the\nfour variables already exist in the manager when the ZDD for $f$ is\nbuilt. Note the use of De Morgan's law.\n\\begin{verbatim}\n\tDdManager *manager;\n\tDdNode *f, *var, *tmp;\n\tint i;\n\n\tmanager = Cudd_Init(0,4,CUDD_UNIQUE_SLOTS,\n\t\t\t    CUDD_CACHE_SLOTS,0);\n\t...\n\n\ttmp = Cudd_ReadZddOne(manager,0);\n\tCudd_Ref(tmp);\n\tfor (i = 3; i >= 0; i--) {\n\t    var = Cudd_zddIthVar(manager,i);\n\t    Cudd_Ref(var);\n\t    f = Cudd_zddIntersect(manager,var,tmp);\n\t    Cudd_Ref(f);\n\t    Cudd_RecursiveDerefZdd(manager,tmp);\n\t    Cudd_RecursiveDerefZdd(manager,var);\n\t    tmp = f;\n\t}\n\tf = Cudd_zddDiff(manager,Cudd_ReadZddOne(manager,0),tmp);\n\tCudd_Ref(f);\n\tCudd_RecursiveDerefZdd(manager,tmp);\n\\end{verbatim}\nThis example illustrates the following points:\n\\begin{itemize}\n\\item The projection\\index{projection functions} functions are\n  referenced, because they are not maintained by the manager.\n\\item Complementation is obtained by subtracting from the constant 1\n  function.\n\\item The result of \\emph{Cudd\\_ReadZddOne}\\eidx{Cudd\\_ReadZddOne}\n  does not require referencing.\n\\end{itemize}\nCUDD provides functions for the manipulation of\ncovers\\index{function!cover} represented by ZDDs. For instance,\n\\emph{Cudd\\_zddIsop}\\eidx{Cudd\\_zddIsop} builds a ZDD representing an\nirredundant\\index{function!cover!irredundant} sum of products for the\nincompletely specified function defined by the two BDDs $L$ and $U$.\n\\emph{Cudd\\_zddWeakDiv}\\eidx{Cudd\\_zddWeakDiv} performs the weak\ndivision of two covers given as ZDDs.  These functions expect the two\nZDD variables corresponding to the two literals of the function\nvariable to be adjacent.  One has to create variable groups (see\nSection~\\ref{sec:reordZ}) for reordering\\index{reordering!of ZDDs} of\nthe ZDD variables to work.  BDD automatic reordering is safe even\nwithout groups: If realignment of ZDD and ADD/BDD variables is\nrequested (see Section~\\ref{sec:consist}) groups will be kept\nadjacent.\n\n\\subsection{Converting ADDs to BDDs and Vice Versa}\n\\index{conversion!of ADDs to BDDs}\n\\index{conversion!of BDDs to ADDs}\\label{sec:convert}\n\nSeveral procedures are provided to convert ADDs to BDDs, according to\ndifferent criteria.\n(\\emph{Cudd\\_addBddPattern}\\eidx{Cudd\\_addBddPattern},\n\\emph{Cudd\\_addBddInterval}\\eidx{Cudd\\_addBddInterval}, and\n\\emph{Cudd\\_addBddThreshold}\\eidx{Cudd\\_addBddThreshold}.) The\nconversion from BDDs to ADDs\n(\\emph{Cudd\\_BddToAdd}\\eidx{Cudd\\_BddToAdd}) is based on the simple\nprinciple of mapping the logical 0\\index{zero!logical} and 1 on the\narithmetic\\index{zero!arithmetic} 0 and 1.  It is also possible to\nconvert an ADD with integer values (more precisely, floating point\nnumbers with 0 fractional part) to an array of BDDs by repeatedly\ncalling \\emph{Cudd\\_addIthBit}\\eidx{Cudd\\_addIthBit}.\n\n\\subsection{Converting BDDs to ZDDs and Vice Versa}\n\\index{conversion!of ZDDs to BDDs}\n\\index{conversion!of BDDs to ZDDs}\\label{sec:convertZ}\n\nMany applications first build a set of BDDs and then derive ZDDs from\nthe BDDs. These applications should create the manager with 0\nZDD\\index{ZDD} variables and create the BDDs. Then they should call\n\\emph{Cudd\\_zddVarsFromBddVars}\\eidx{Cudd\\_zddVarsFromBddVars} to\ncreate the necessary ZDD variables---whose number is likely to be\nknown once the BDDs are available.  This approach eliminates the\ndifficulties that arise when the number of ZDD variables changes while\nZDDs are being built.\n\nThe simplest conversion from BDDs to ZDDs is a simple change of\nrepresentation, which preserves the functions. Simply put, given a BDD\nfor $f$, a ZDD for $f$ is requested. In this case the correspondence\nbetween the BDD variables and ZDD variables is one-to-one. Hence,\n\\emph{Cudd\\_zddVarsFromBddVars} should be called with the\n\\emph{multiplicity} parameter equal to 1. The conversion proper can\nthen be performed by calling\n\\emph{Cudd\\_zddPortFromBdd}\\eidx{Cudd\\_zddPortFromBdd}. The inverse\ntransformation is performed by\n\\emph{Cudd\\_zddPortToBdd}\\eidx{Cudd\\_zddPortToBdd}.\n\nZDDs are quite often used for the representation of\n\\emph{covers}\\index{function!cover}. This is normally done by\nassociating two ZDD variables to each variable of the function.  (And\nhence, typically, to each BDD variable.)  One ZDD variable is\nassociated with the positive literal of the BDD variable, while the\nother ZDD variable is associated with the negative literal.  A call to\n\\emph{Cudd\\_zddVarsFromBddVars}\\eidx{Cudd\\_zddVarsFromBddVars} with\n\\emph{multiplicity} equal to 2 will associate to BDD variable $i$ the\ntwo ZDD variables $2i$ and $2i+1$.\n\nIf a BDD variable group tree exists when\n\\emph{Cudd\\_zddVarsFromBddVars} is called (see\nSection~\\ref{sec:group}) the function generates a ZDD variable group\ntree consistent to it.  In any case, all the ZDD variables derived\nfrom the same BDD variable are clustered into a group.\n\nIf the ZDD for $f$ is created and later a new ZDD variable is added to\nthe manager, the function represented by the existing ZDD changes.\nSuppose, for instance, that two variables are initially created, and\nthat the ZDD for $f = x_0 + x_1$ is built. If a third variable is\nadded, say $x_2$, then the ZDD represents $g = (x_0 + x_1) x_2'$\ninstead.  This change in function obviously applies regardless of what\nuse is made of the ZDD\\@. However, if the ZDD is used to represent a\ncover\\index{function!cover}, the cover itself is not changed by the\naddition of new variable. (What changes is the\ncharacteristic\\index{function!characteristic} function of the cover.)\n\n\\subsection{Variable Reordering for BDDs and ADDs}\n\\index{reordering!of BDDs and ADDs}\\label{sec:reorder}\n\nThe CUDD package provides a rich set of\ndynamic\\index{reordering!dynamic} reordering algorithms.  Some of them\nare slight variations of existing techniques\n\\cite{Rudell93,Drechs95,Bollig95,Ishiur91,Plessi93,Jeong93}; some\nothers have been developed specifically for this package\n\\cite{Panda94,Panda95b}.\n\nReordering affects a unique\\index{table!unique} table. This means that\nBDDs and ADDs, which share the same unique table are simultaneously\nreordered. ZDDs, on the other hand, are reordered separately. In the\nfollowing we discuss the reordering of BDDs and ADDs. Reordering for\nZDDs is the subject of Section~\\ref{sec:reordZ}.\n\nReordering of the variables can be invoked directly by the application\nby calling \\emph{Cudd\\_ReduceHeap}\\eidx{Cudd\\_ReduceHeap}. Or it can\nbe automatically triggered by the package when the number of nodes has\nreached a given threshold\\index{reordering!threshold}.  (The threshold\nis initialized and automatically adjusted after each reordering by the\npackage.) To enable automatic dynamic reordering (also called\n\\emph{asynchronous\\index{reordering!asynchronous}} dynamic reordering\nin this document) the application must call\n\\emph{Cudd\\_AutodynEnable}\\eidx{Cudd\\_AutodynEnable}.  Automatic\ndynamic reordering can subsequently be disabled by calling\n\\emph{Cudd\\_AutodynDisable}\\eidx{Cudd\\_AutodynDisable}.\n\nAll reordering methods are available in both the case of direct call\nto \\emph{Cudd\\_ReduceHeap}\\eidx{Cudd\\_ReduceHeap} and the case of\nautomatic invocation.  For many methods, the reordering procedure is\niterated until no further improvement is obtained.  We call these\nmethods the \\emph{converging\\index{reordering!converging}} methods.\nWhen constraints are imposed on the relative position of variables\n(see Section~\\ref{sec:group}) the reordering methods apply inside the\ngroups.  The groups\\index{reordering!group} themselves are reordered\nby sifting\\index{reordering!sifting}.  Each method is identified by a\nconstant of the enumerated type\n\\emph{Cudd\\_ReorderingType\\index{reordering!Cudd\\_ReorderingType}}\ndefined in \\emph{cudd.h\\index{cudd.h}} (the external\nheader\\index{header files} file of the CUDD package):\n\n\\begin{description}\n\\item[CUDD\\_REORDER\\_NONE\\index{CUDD\\_REORDER\\_NONE}:] This method\n  causes no reordering.\n\\item[CUDD\\_REORDER\\_SAME\\index{CUDD\\_REORDER\\_SAME}:] If passed to\n  \\emph{Cudd\\_AutodynEnable}\\eidx{Cudd\\_AutodynEnable}, this\n  method leaves the current method for automatic reordering unchanged.\n  If passed to \\emph{Cudd\\_ReduceHeap}\\eidx{Cudd\\_ReduceHeap},\n  this method causes the current method for automatic reordering to be\n  used.\n\\item[CUDD\\_REORDER\\_RANDOM\\index{CUDD\\_REORDER\\_RANDOM}:] Pairs of\n  variables are randomly chosen, and swapped in the order. The swap is\n  performed by a series of swaps of adjacent variables. The best order\n  among those obtained by the series of swaps is retained. The number\n  of pairs chosen for swapping\\index{reordering!random} equals the\n  number of variables in the diagram.\n\\item[CUDD\\_REORDER\\_RANDOM\\_PIVOT\\index{CUDD\\_REORDER\\_RANDOM\\_PIVOT}:]\n  Same as CUDD\\_REORDER\\_RANDOM, but the two variables are chosen so\n  that the first is above the variable with the largest number of\n  nodes, and the second is below that variable.  In case there are\n  several variables tied for the maximum number of nodes, the one\n  closest to the root is used.\n\\item[CUDD\\_REORDER\\_SIFT\\index{CUDD\\_REORDER\\_SIFT}:] This method is\n  an implementation of Rudell's sifting\\index{reordering!sifting}\n  algorithm \\cite{Rudell93}. A simplified description of sifting is as\n  follows: Each variable is considered in turn. A variable is moved up\n  and down in the order so that it takes all possible positions. The\n  best position is identified and the variable is returned to that\n  position.\n\n  In reality, things are a bit more complicated. For instance, there\n  is a limit on the number of variables that will be sifted. This\n  limit can be read with\n  \\emph{Cudd\\_ReadSiftMaxVar}\\eidx{Cudd\\_ReadSiftMaxVar} and set with\n  \\emph{Cudd\\_SetSiftMaxVar}\\eidx{Cudd\\_SetSiftMaxVar}.  In addition,\n  if the diagram grows too much while moving a variable up or down,\n  that movement is terminated before the variable has reached one end\n  of the order. The maximum ratio by which the diagram is allowed to\n  grow while a variable is being sifted can be read with\n  \\emph{Cudd\\_ReadMaxGrowth}\\eidx{Cudd\\_ReadMaxGrowth} and set with\n  \\emph{Cudd\\_SetMaxGrowth}\\eidx{Cudd\\_SetMaxGrowth}.\n\\item[CUDD\\_REORDER\\_SIFT\\_CONVERGE\\index{CUDD\\_REORDER\\_SIFT\\_CONVERGE}:]\n  This is the converging\\index{reordering!converging} variant of\n  CUDD\\-\\_REORDER\\_SIFT.\n\\item[CUDD\\_REORDER\\_SYMM\\_SIFT\\index{CUDD\\_REORDER\\_SYMM\\_SIFT}:]\n  This method is an implementation of\n  symmetric\\index{reordering!symmetric} sifting \\cite{Panda94}. It is\n  similar to sifting, with one addition: Variables that become\n  adjacent during sifting are tested for symmetry\\index{symmetry}. If\n  they are symmetric, they are linked in a group.  Sifting then\n  continues with a group being moved, instead of a single variable.\n  After symmetric sifting has been run,\n  \\emph{Cudd\\_SymmProfile}\\eidx{Cudd\\_SymmProfile} can be called to\n  report on the symmetry groups found. (Both positive and negative\n  symmetries are reported.)\n\\item[CUDD\\_REORDER\\_SYMM\\_SIFT\\_CONV\\index{CUDD\\_REORDER\\_SYMM\\_SIFT\\_CONV}:]\n  This is the converging\\index{reordering!converging} variant of\n  CUDD\\-\\_REORDER\\_SYMM\\_SIFT.\n\\item[CUDD\\_REORDER\\_GROUP\\_SIFT\\index{CUDD\\_REORDER\\_GROUP\\_SIFT}:]\n  This method is an implementation of group\\index{reordering!group}\n  sifting \\cite{Panda95b}. It is similar to symmetric sifting, but\n  aggregation\\index{aggregation} is not restricted to symmetric\n  variables.\n\\item[CUDD\\_REORDER\\_GROUP\\_SIFT\\_CONV\\index{CUDD\\_REORDER\\_GROUP\\_SIFT\\_CONV}:]\n  This method repeats until convergence the combination of\n  CUDD\\_REORDER\\_GROUP\\_SIFT and CUDD\\-\\_REORDER\\_WINDOW4.\n\\item[CUDD\\_REORDER\\_WINDOW2\\index{CUDD\\_REORDER\\_WINDOW2}:] This\n  method implements the window\\index{reordering!window} permutation\n  approach of Fujita \\cite{Fujita91b} and Ishiura \\cite{Ishiur91}.\n  The size of the window is 2.\n\\item[CUDD\\_REORDER\\_WINDOW3\\index{CUDD\\_REORDER\\_WINDOW3}:] Similar\n  to CUDD\\_REORDER\\_WINDOW2, but with a window of size 3.\n\\item[CUDD\\_REORDER\\_WINDOW4\\index{CUDD\\_REORDER\\_WINDOW4}:] Similar\n  to CUDD\\_REORDER\\_WINDOW2, but with a window of size 4.\n\\item[CUDD\\_REORDER\\_WINDOW2\\_CONV\\index{CUDD\\_REORDER\\_WINDOW2\\_CONV}:]\n  This is the converging\\index{reordering!converging} variant of\n  CUDD\\-\\_REORDER\\_WINDOW2.\n\\item[CUDD\\_REORDER\\_WINDOW3\\_CONV\\index{CUDD\\_REORDER\\_WINDOW3\\_CONV}:]\n  This is the converging variant of CUDD\\-\\_REORDER\\_WINDOW3.\n\\item[CUDD\\_REORDER\\_WINDOW4\\_CONV\\index{CUDD\\_REORDER\\_WINDOW4\\_CONV}:]\n  This is the converging variant of CUDD\\-\\_REORDER\\_WINDOW4.\n\\item[CUDD\\_REORDER\\_ANNEALING\\index{CUDD\\_REORDER\\_ANNEALING}:] This\n  method is an implementation of simulated\n  annealing\\index{reordering!simulated annealing} for variable\n  ordering, vaguely resemblant of the algorithm of \\cite{Bollig95}.\n  This method is potentially very slow.\n\\item[CUDD\\_REORDER\\_GENETIC:\\index{CUDD\\_REORDER\\_GENETIC}] This\n  method is an implementation of a genetic\\index{reordering!genetic}\n  algorithm for variable ordering, inspired by the work of Drechsler\n  \\cite{Drechs95}. This method is potentially very slow.\n\\item[CUDD\\_REORDER\\_EXACT\\index{CUDD\\_REORDER\\_EXACT}:] This method\n  implements a dynamic programming approach to\n  exact\\index{reordering!exact} reordering\n  \\cite{Held62,Friedman90,Ishiur91}, with improvements described in\n  \\cite{Jeong93}. It only stores one BDD at the time. Therefore, it is\n  relatively efficient in terms of memory.  Compared to other\n  reordering strategies, it is very slow, and is not recommended for\n  more than 16 variables.\n\\end{description}\nSo far we have described methods whereby the package selects an order\nautomatically. A given order of the variables can also be imposed by\ncalling \\emph{Cudd\\_ShuffleHeap}\\eidx{Cudd\\_ShuffleHeap}.\n\n\\subsection{Grouping Variables}\n\\index{variable!groups}\\label{sec:group}\n\nCUDD allows the application to specify constraints on the positions of\ngroup of variables. It is possible to request that a group of\ncontiguous variables be kept contiguous by the reordering procedures.\nIt is also possible to request that the relative order of some groups\nof variables be left unchanged. The constraints on the order are\nspecified by means of a tree\\index{variable!tree}, which is created in\none of two ways:\n\\begin{itemize}\n\\item By calling \\emph{Cudd\\_MakeTreeNode}\\eidx{Cudd\\_MakeTreeNode}.\n\\item By calling the functions of the MTR\\index{libraries!mtr} library\n  (part of the distribution), and by registering the result with the\n  manager using \\emph{Cudd\\_SetTree}\\eidx{Cudd\\_SetTree}. The current\n  tree registered with the manager can be read with\n  \\emph{Cudd\\_ReadTree}\\eidx{Cudd\\_ReadTree}.\n\\end{itemize}\n\nEach node in the tree represents a range of variables. The lower bound\nof the range is given by the \\emph{low} field of the node, and the\nsize of the group is given by the \\emph{size} field of the\nnode.\\footnote{When the variables in a group are reordered, the\n  association between the \\emph{low} field and the index of the first\n  variable in the group is lost. The package updates the tree to keep\n  track of the changes. However, the application cannot rely on\n  \\emph{low} to determine the position of variables.}  The variables\nin each range are kept contiguous. Furthermore, if a node is marked\nwith the MTR\\_FIXED\\index{MTR\\_FIXED} flag, then the relative order of\nthe variable ranges associated to its children is not changed.  As an\nexample, suppose the initial variable order is:\n\\begin{verbatim}\n\tx0, y0, z0, x1, y1, z1, ... , x9, y9, z9.\n\\end{verbatim}\nSuppose we want to keep each group of three variables with the same\nindex (e.g., \\verb|x3, y3, z3|) contiguous, while allowing the package\nto change the order of the groups. We can accomplish this with the\nfollowing code:\n\\begin{verbatim}\n\tfor (i = 0; i < 10; i++) {\n\t    (void) Cudd_MakeTreeNode(manager,i*3,3,MTR_DEFAULT);\n\t}\n\\end{verbatim}\nIf we want to keep the order within each group of variables\nfixed (i.e., \\verb|x| before \\verb|y| before \\verb|z|) we need to\nchange MTR\\_DEFAULT\\index{MTR\\_DEFAULT} into MTR\\_FIXED.\n\nThe \\emph{low} parameter passed to\n\\emph{Cudd\\_MakeTreeNode}\\eidx{Cudd\\_MakeTreeNode} is the index of a\nvariable (as opposed to its level or position in the order).  The\ngroup tree\\index{variable!tree} can be created at any time.  The\nresult obviously depends on the variable order in effect at creation\ntime.\n\nIt is possible to create a variable group tree also before the\nvariables themselves are created.  The package assumes in this case\nthat the index of the variables not yet in existence will equal their\nposition in the order when they are created.  Therefore, applications\nthat rely on\n\\emph{Cudd\\_bddNewVarAtLevel}\\eidx{Cudd\\_bddNewVarAtLevel} or\n\\emph{Cudd\\_addNewVarAtLevel}\\eidx{Cudd\\_addNewVarAtLevel} to create\nnew variables have to create the variables before they group them.\n\nThe reordering procedure will skip all groups whose variables are not\nyet in existence.  For groups that are only partially in existence, the\nreordering procedure will try to reorder the variables already\ninstantiated, without violating the adjacency constraints.\n\n\n\\subsection{Variable Reordering for ZDDs}\n\\index{reordering!of ZDDs}\\label{sec:reordZ}\n\nReordering of ZDDs is done in much the same way as the reordering of\nBDDs and ADDs. The functions corresponding to \\emph{Cudd\\_ReduceHeap}\nand \\emph{Cudd\\_ShuffleHeap} are\n\\emph{Cudd\\_zddReduceHeap}\\eidx{Cudd\\_zddReduceHeap} and\n\\emph{Cudd\\_zddShuffleHeap}\\eidx{Cudd\\_zddShuffleHeap}.  To enable\ndynamic\\index{reordering!dynamic} reordering, the application must\ncall \\emph{Cudd\\_AutodynEnableZdd}\\eidx{Cudd\\_AutodynEnableZdd}, and\nto disable dynamic reordering, it must call\n\\emph{Cudd\\_AutodynDisableZdd}\\eidx{Cudd\\_AutodynDisableZdd}.  In the\ncurrent implementation, however, the choice of reordering methods for\nZDDs is more limited. Specifically, these methods are available:\n\n\\begin{description}\n\\item[CUDD\\_REORDER\\_NONE\\index{CUDD\\_REORDER\\_NONE};]\n\\item[CUDD\\_REORDER\\_SAME\\index{CUDD\\_REORDER\\_SAME};]\n\\item[CUDD\\_REORDER\\_RANDOM\\index{CUDD\\_REORDER\\_RANDOM};]\n\\item[CUDD\\_REORDER\\_RANDOM\\_PIVOT\\index{CUDD\\_REORDER\\_RANDOM\\_PIVOT};]\n\\item[CUDD\\_REORDER\\_SIFT\\index{CUDD\\_REORDER\\_SIFT};]\n\\item[CUDD\\_REORDER\\_SIFT\\_CONVERGE\\index{CUDD\\_REORDER\\_SIFT\\_CONVERGE};]\n\\item[CUDD\\_REORDER\\_SYMM\\_SIFT\\index{CUDD\\_REORDER\\_SYMM\\_SIFT};]\n\\item[CUDD\\_REORDER\\_SYMM\\_SIFT\\_CONV\\index{CUDD\\_REORDER\\_SYMM\\_SIFT\\_CONV}.]\n\\end{description}\n\nTo create ZDD variable groups, the application calls\n\\emph{Cudd\\_MakeZddTreeNode}\\eidx{Cudd\\_MakeZddTreeNode}.\n\n\\subsection{Keeping Consistent Variable Orders for BDDs and ZDDs}\n\\label{sec:consist}\n\nSeveral applications that manipulate both BDDs and ZDDs benefit from\nkeeping a fixed correspondence between the order of the BDD variables\nand the order of the ZDD variables.  If each BDD variable corresponds\nto a group of ZDD variables, then it is often desirable that the\ngroups of ZDD variables be in the same order as the corresponding BDD\nvariables.  CUDD allows the ZDD order to track the BDD order and vice\nversa. To have the ZDD order track the BDD order, the application\ncalls \\emph{Cudd\\_zddRealignEnable}\\eidx{Cudd\\_zddRealignEnable}.  The\neffect of this call can be reversed by calling\n\\emph{Cudd\\_zddRealignDisable}\\eidx{Cudd\\_zddRealignDisable}.  When\nZDD realignment is in effect, automatic reordering of ZDDs should be\ndisabled.\n\n\\subsection{Hooks}\n\\index{hook}\\label{sec:hooks}\n\nHooks in CUDD are lists of application-specified functions to be run on\ncertain occasions. Each hook is identified by a constant of the\nenumerated type \\emph{Cudd\\_HookType}\\eidx{Cudd\\_HookType}. In Version\n\\vnumber\\ hooks are defined for these occasions:\n\\begin{itemize}\n\\item before garbage collection (CUDD\\_PRE\\_GC\\_HOOK);\n\\item after garbage collection (CUDD\\_POST\\_GC\\_HOOK);\n\\item before variable reordering (CUDD\\_PRE\\_REORDERING\\_HOOK);\n\\item after variable reordering (CUDD\\_POST\\_REORDERING\\_HOOK).\n\\end{itemize}\nA function added to a hook receives a pointer to the manager, a\npointer to a constant string, and a pointer to void as arguments; it\nmust return 1 if successful; 0 otherwise. The second argument is one\nof ``DD,'' ``BDD,'' and ``ZDD.'' This allows the hook functions to\ntell the type of diagram for which reordering or garbage collection\ntakes place. The third argument varies depending on the hook. The hook\nfunctions called before or after garbage collection\\index{garbage\n  collection!hooks} do not use it. The hook functions called before\nreordering\\index{reordering!hooks} are passed, in addition to the\npointer to the manager, also the method used for reordering. The hook\nfunctions called after reordering are passed the start time. To add a\nfunction to a hook, one uses \\emph{Cudd\\_AddHook}\\eidx{Cudd\\_AddHook}.\nThe function of a given hook are called in the order in which they\nwere added to the hook.  For sample hook functions, one may look at\n\\emph{Cudd\\_StdPreReordHook}\\eidx{Cudd\\_StdPreReordHook} and\n\\emph{Cudd\\_StdPostReordHook}\\eidx{Cudd\\_StdPostReordHook}.\n\n\\subsection{Timeouts and Limits}\n\\index{timeout}\\label{sec:timeouts}\n\nIt is possible to set a time limit for a manager with\n\\emph{Cudd\\_SetTimeLimit}\\eidx{Cudd\\_SetTimeLimit}.  Once set, the\ntime available to the manager can be inspected and modified through\nother API functions.\n(\\emph{Cudd\\_TimeLimited}\\eidx{Cudd\\_TimeLimited},\n\\emph{Cudd\\_ReadTimeLimit}\\eidx{Cudd\\_ReadTimeLimit},\n\\emph{Cudd\\_UnsetTimeLimit}\\eidx{Cudd\\_UnsetTimeLimit},\n\\emph{Cudd\\_UpdateTimeLimit}\\eidx{Cudd\\_UpdateTimeLimit},\n\\emph{Cudd\\_IncreaseTimeLimit}\\eidx{Cudd\\_IncreaseTimeLimit}.) CUDD\nchecks for expiration from time to time.  When deadline has\nexpired, it returns NULL from the call in progress, but it leaves the\nmanager in a consistent state.  The invoking application must be\ndesigned to handle the NULL values returned.\n\nWhen reordering, if a timout is approaching, CUDD will quit reordering\nto give the application a chance to finish some computation.\n\nIt is also possible to invoke some functions that return NULL if they\ncannot complete without creating more than a set number of nodes.\nSee, for instance, \\emph{Cudd\\_bddAndLimit}\\eidx{Cudd\\_bddAndLimit}.\nOnly functions that are documented to check for the number of\ngenerated nodes do so.  (Their names end in ``limit.'')  These\nfunctions set the error code to\n\\emph{CUDD\\_TOO\\_MANY\\_NODES}\\eidx{CUDD\\_TOO\\_MANY\\_NODES} when they\nreturn NULL because of too many nodes.  The error code can be\ninspected with \\emph{Cudd\\_ReadErrorCode}\\eidx{Cudd\\_ReadErrorCode}\nand cleared with\n\\emph{Cudd\\_ClearErrorCode}\\eidx{Cudd\\_ClearErrorCode}.\n\n\\subsection{Writing Decision Diagrams to a File}\n\\label{sec:dump}\n\nThe CUDD package provides several functions to write decision diagrams\nto a file. \\emph{Cudd\\_DumpBlif}\\eidx{Cudd\\_DumpBlif} writes a\nfile in \\emph{blif} format.  It is restricted to BDDs. The diagrams\nare written as a network of multiplexers, one multiplexer for each\ninternal node of the BDD.\n\n\\emph{Cudd\\_DumpDot}\\eidx{Cudd\\_DumpDot} produces input suitable to\nthe graph-drawing\\index{graph!drawing} program\n\\href{http://www.graphviz.org}{\\emph{dot}} written by Eleftherios\nKoutsofios and Stephen C. North.  An example of drawing produced by\ndot from the output of \\emph{Cudd\\_DumpDot} is shown in\nFigure~\\ref{fi:phase}.  \\emph{Cudd\\_DumpDot} is restricted to BDDs and\nADDs; \\emph{Cudd\\_zddDumpDot} may be used to draw ZDDs.\n\\begin{figure}\n  \\centerline{\\includegraphics[height=15.5cm]{@top_srcdir@/doc/phase.pdf}}\n\\caption{A BDD representing a phase constraint for the optimization of\n  fixed-polarity Reed-Muller forms. The label of each node is the\n  unique part of the node address. All nodes on the same level\n  correspond to the same variable, whose name is shown at the left of\n  the diagram. Dotted lines indicate complement\\index{arc!complement}\n  arcs. Dashed lines indicate regular\\index{arc!regular} ``else''\n  arcs.\\label{fi:phase}}\n\\end{figure}\n\\emph{Cudd\\_zddDumpDot}\\eidx{Cudd\\_zddDumpDot} is the analog of\n\\emph{Cudd\\_DumpDot} for ZDDs.\n\n\\emph{Cudd\\_DumpDaVinci}\\eidx{Cudd\\_DumpDaVinci} produces input\nsuitable to the graph-drawing\\index{graph!drawing} program\n\\href{ftp://ftp.uni-bremen.de/pub/graphics/daVinci}{\\emph{daVinci}}\ndeveloped at the University of Bremen. It is restricted to BDDs and\nADDs.\n\nFunctions are also available to produce the input format of\n\\emph{DDcal} (see Section~\\ref{sec:getFriends}) and factored forms.\n\n\n\\subsection{Saving and Restoring BDDs}\n\\label{sec:save-restore}\n\nThe \\href{ftp://ftp.polito.it/pub/research/dddmp/}{\\emph{dddmp}}\nlibrary\\index{libraries!dddmp} by Gianpiero Cabodi and Stefano Quer\nallows a CUDD application to save BDDs to disk in compact form for\nlater retrieval.  See the library's own documentation for the details.\n\n%----------------------------------------\n\\section{Programmer's Manual}\n\\label{sec:prog}\n\nThis section provides additional detail on the workings of the CUDD\npackage and on the programming conventions followed in its writing.\nThe additional detail should help those who want to write procedures\nthat directly manipulate the CUDD data structures.\n\n\\subsection{Compiling and Linking}\n\\index{compiling}\\label{sec:compileInt}\n\nIf you plan to use the CUDD package as a clear box\\index{box!clear}\n(for instance, you want to write a procedure that traverses a decision\ndiagram) you need to add\n\\begin{verbatim}\n#include \"cuddInt.h\"\n\\end{verbatim}\nto your source files. In addition, you should link \\verb|libcudd.a| to\nyour executable.  Some platforms require specific compiler and linker\nflags.  Refer to the \\texttt{Makefile} in the top level directory of\nthe distribution.\n\n\\subsection{Reference Counts}\n\\index{node!reference count}\\label{sec:ref}\n\nGarbage\\index{garbage collection} collection in the CUDD package is\nbased on reference counts.  Each node stores the sum of the external\nreferences and internal references. An internal BDD or ADD node is\ncreated by a call to \\emph{cuddUniqueInter}\\eidx{cuddUniqueInter}, an\ninternal ZDD node is created by a call to\n\\emph{cuddUniqueInterZdd}\\eidx{cuddUniqueInterZdd}, and a\nterminal\\index{node!constant} node is created by a call to\n\\emph{cuddUniqueConst}\\eidx{cuddUniqueConst}. If the node returned by\nthese functions is new, its reference count is zero.  The function\nthat calls \\emph{cuddUniqueInter}\\eidx{cuddUniqueInter},\n\\emph{cuddUniqueInterZdd}\\eidx{cuddUniqueInterZdd}, or\n\\emph{cuddUniqueConst}\\eidx{cuddUniqueConst} is responsible for\nincreasing the reference count of the node.  This is accomplished by\ncalling \\emph{Cudd\\_Ref}\\eidx{Cudd\\_Ref}.\n\nWhen a function is no longer needed by an application, the memory used\nby its diagram can be recycled by calling\n\\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref} (BDDs and ADDs)\nor \\emph{Cudd\\_RecursiveDerefZdd}\\eidx{Cudd\\_RecursiveDerefZdd}\n(ZDDs).  These functions decrease the reference \\index{node!reference\n  count} count of the node passed to them.  If the reference count\nbecomes 0, then two things happen:\n\\begin{enumerate}\n\\item The node is declared ``dead\\index{node!dead};'' this entails\n  increasing the counters\\index{statistical counters} of the dead\n  nodes. (One counter for the subtable\\index{subtable} to which the\n  node belongs, and one global counter for the\n  unique\\index{table!unique} table to which the node belongs.) The\n  node itself is not affected.\n\\item The function is recursively called on the two children of the\n  node.\n\\end{enumerate}\nFor instance, if the diagram of a function does not share any nodes\nwith other diagrams, then calling\n\\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref} or\n\\emph{Cudd\\_RecursiveDerefZdd}\\eidx{Cudd\\_RecursiveDerefZdd} on its\nroot will cause all the nodes of the diagram to become dead.\n\nWhen the number of dead nodes reaches a given level (dynamically\ndetermined by the package) garbage collection takes place. During\ngarbage\\index{garbage collection} collection dead nodes are returned\nto the node free list\\index{free list}.\n\nWhen a new node is created, it is important to increase its\nreference\\index{node!reference count} count before one of the two\nfollowing events occurs:\n\\begin{enumerate}\n\\item A call to \\emph{cuddUniqueInter}\\eidx{cuddUniqueInter},\n  to \\emph{cuddUniqueInterZdd}\\eidx{cuddUniqueInterZdd}, to\n  \\emph{cuddUniqueConst}\\eidx{cuddUniqueConst}, or to a\n  function that may eventually cause a call to them.\n\\item A call to\n  \\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref}, to\n  \\emph{Cudd\\_RecursiveDerefZdd}\\eidx{Cudd\\_RecursiveDerefZdd}, or to\n  a function that may eventually cause a call to them.\n\\end{enumerate}\nIn practice, it is recommended to increase the reference count as soon\nas the returned pointer has been tested for not being NULL.\n\n\\subsubsection{NULL Return Values}\n\\label{sec:null}\n\nThe interface to the memory management functions (e.g., malloc) used\nby CUDD intercepts NULL return values and calls a handler.  The\ndefault handler exits with an error message.  If the application does\nnot install another handler, therefore, a NULL return value from an\nexported function of CUDD signals an internal error.\n\nIf the aplication, however, installs another handler that lets\nexecution continue, a NULL pointer returned by an exported function\ntypically indicates that the process has run out of memory.\n\\emph{Cudd\\_ReadErrorCode}\\eidx{Cudd\\_ReadErrorCode} can be used to\nascertain the nature of the problem.\n\nAn application that tests for the result being NULL can try some\nremedial action, if it runs out of memory.  For instance, it may free\nsome memory that is not strictly necessary, or try a slower algorithm\nthat takes less space. As an example, CUDD overrides the default\nhandler when trying to enlarge the cache or increase the number of\nslots of the unique table. If the allocation fails, the package prints\nout a message and continues without resizing the cache.\n\n\\subsubsection{\\emph{Cudd\\_RecursiveDeref} vs.\\ \\emph{Cudd\\_Deref}}\n\\label{sec:deref}\n\nIt is often the case that a recursive procedure has to protect the\nresult it is going to return, while it disposes of intermediate\nresults.  (See the previous discussion on when to increase reference\ncounts.)  Once the intermediate results have been properly disposed\nof, the final result must be returned to its pristine state, in which\nthe root node may have a reference count of 0. One cannot use\n\\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref} (or\n\\emph{Cudd\\_RecursiveDerefZdd}) for this purpose, because it may\nerroneously make some nodes dead.  Therefore, the package provides a\ndifferent function: \\emph{Cudd\\_Deref}\\eidx{Cudd\\_Deref}. This\nfunction is not recursive, and does not change the dead node counts.\nIts use is almost exclusively the one just described: Decreasing the\nreference count of the root of the final result before returning from\na recursive procedure.\n\n\\subsubsection{When Increasing the Reference Count is Unnecessary}\n\\index{node!reference count}\\label{sec:noref}\n\nWhen a copy of a predefined constant\\index{node!constant} or of a\nsimple BDD variable is needed for comparison purposes, then calling\n\\emph{Cudd\\_Ref}\\eidx{Cudd\\_Ref} is not necessary, because these\nsimple functions are guaranteed to have reference counts greater than\n0 at all times. If no call to \\emph{Cudd\\_Ref} is made, then no\nattempt to free the diagram by calling\n\\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref} or\n\\emph{Cudd\\_RecursiveDerefZdd}\\eidx{Cudd\\_RecursiveDerefZdd} should be\nmade.\n\n\\subsubsection{Saturating Increments and Decrements}\n\\index{saturating!increments}\\index{saturating!decrements}\\label{sec:satur}\n\nOn 32-bit machines, the CUDD package stores the\nreference\\index{node!reference count} counts in unsigned short int's.\nFor large diagrams, it is possible for some reference counts to exceed\nthe capacity of an unsigned short int.  Therefore, increments and\ndecrements of reference counts are \\emph{saturating}. This means that\nonce a reference count has reached the maximum possible value, it is\nno longer changed by calls to \\emph{Cudd\\_Ref},\n\\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref},\n\\emph{Cudd\\_RecursiveDerefZdd}\\eidx{Cudd\\_RecursiveDerefZdd}, or\n\\emph{Cudd\\_Deref}\\eidx{Cudd\\_Deref}.  As a consequence, some nodes\nthat have no references may not be declared dead. This may result in a\nsmall waste of memory, which is normally more than offset by the\nreduction in size of the node structure.\n\nWhen using 64-bit pointers, there is normally no memory advantage from\nusing short int's instead of int's in a DdNode.  Therefore, increments\nand decrements are not saturating in that case.  What option is in\neffect depends on two macros, SIZEOF\\_VOID\\_P\\index{SIZEOF\\_VOID\\_P}\nand SIZEOF\\_INT\\index{SIZEOF\\_INT}, defined in the configuration\nheader\\index{header files} file (\\emph{config.h}\\index{config.h}).\nThe increments and decrements of the reference counts are performed\nusing two macros: \\emph{cuddSatInc}\\eidx{cuddSatInc} and\n\\emph{cuddSatDec}\\eidx{cuddSatDec}, whose definitions depend on\nSIZEOF\\_VOID\\_P\\index{SIZEOF\\_VOID\\_P} and\nSIZEOF\\_INT\\index{SIZEOF\\_INT}.\n\n\\subsection{Complement Arcs}\n\\index{arc!complement}\\label{sec:compl}\n\nIf ADDs are restricted to use only the constants 0 and 1, they behave\nlike BDDs without complement arcs. It is normally easier to write code\nthat manipulates 0-1 ADDs, than to write code for BDDs. However,\ncomplementation is trivial with complement arcs, and is not trivial\nwithout. As a consequence, with complement arcs it is possible to\ncheck for more terminal cases and it is possible to apply De Morgan's\nlaws to reduce problems that are essentially identical to a standard\nform. This in turn increases the utilization of the cache\\index{cache}.\n\nThe complement attribute is stored in the least significant bit of the\n``else'' pointer of each node. An external pointer to a function can\nalso be complemented. The ``then'' pointer to a node, on the other\nhand, is always \\emph{regular\\index{arc!regular}}.  It is a mistake to\nuse a complement\\index{arc!complement} pointer as it is to address\nmemory.  Instead, it is always necessary to obtain a regular version\nof it.  This is normally done by calling\n\\emph{Cudd\\_Regular}\\eidx{Cudd\\_Regular}.  It is also a mistake to\ncall \\emph{cuddUniqueInter}\\eidx{cuddUniqueInter} with a complemented\n``then'' child as argument.  The calling procedure must apply De\nMorgan's laws by complementing both pointers passed to\n\\emph{cuddUniqueInter}\\eidx{cuddUniqueInter} and then taking the\ncomplement of the result.\n\n\\subsection{The Cache}\n\\index{cache}\\label{sec:cache}\n\nEach entry of the cache consists of five fields: The operator, three\npointers to operands and a pointer to the result. The operator and the\nthree pointers to the operands are combined to form three words. The\ncombination relies on two facts:\n\\begin{itemize}\n\\item Most operations have one or two operands. A few bits are\n  sufficient to discriminate all three-operands operations.\n\\item All nodes are aligned to 16-byte boundaries. (32-byte boundaries\n  if 64-bit pointers are used.) Hence, there are a few bits available\n  to distinguish the three-operand operations from te others and to\n  assign unique codes to them.\n\\end{itemize}\n\nThe cache does not contribute to the reference\n\\index{node!reference count}\ncounts of the nodes.  The fact that the cache contains a\npointer to a node does not imply that the node is alive. Instead, when\ngarbage\\index{garbage collection} collection takes place, all entries\nof the cache pointing to dead\\index{node!dead} nodes are cleared.\n\nThe cache is also cleared (of all entries) when dynamic\nreordering\\index{reordering} takes place. In both cases, the entries\nremoved from the cache are about to become invalid.\n\nAll operands and results in a cache entry must be pointers to\nDdNodes\\index{DdNode}.  If a function produces more than one result,\nor uses more than three arguments, there are currently two solutions:\n\\begin{itemize}\n\\item Build a separate, local, cache\\index{cache!local}. (Using, for\n  instance, the \\emph{st} library\\index{libraries!st}.)\n\\item Combine multiple results, or multiple operands, into a single\n  diagram, by building a ``multiplexing structure'' with reserved\n  variables.\n\\end{itemize}\nSupport of the former solution is under development. (See\n\\texttt{cuddLCache.c}..)  Support for the latter solution may be\nprovided in future versions of the package.\n\nThere are three sets of interface\\index{interface!cache} functions to\nthe cache. The first set is for functions with three operands:\n\\emph{cuddCacheInsert}\\eidx{cuddCacheInsert} and\n\\emph{cuddCacheLookup}\\eidx{cuddCacheLookup}. The second set is for\nfunctions with two operands:\n\\emph{cuddCacheInsert2}\\eidx{cuddCacheInsert2} and\n\\emph{cuddCacheLookup2}\\eidx{cuddCacheLookup2}.  The second set is for\nfunctions with one operand:\n\\emph{cuddCacheInsert1}\\eidx{cuddCacheInsert1} and\n\\emph{cuddCacheLookup1}\\eidx{cuddCacheLookup1}.  The second set is\nslightly faster than the first, and the third set is slightly faster\nthan the second.\n\n\\subsubsection{Cache Sizing}\n\\index{cache!sizing}\\label{sec:cache-sizing}\n\nThe size of the cache can increase during the execution of an\napplication. (There is currently no way to decrease the size of the\ncache, though it would not be difficult to do it.) When a cache miss\noccurs, the package uses the following criteria to decide whether to\nresize the cache:\n\\begin{enumerate}\n\\item If the cache already exceeds the limit given by the\n  \\texttt{maxCache\\index{maxCache}} field of the manager, no resizing\n  takes place.  The limit is the minimum of two values: a value set at\n  initialization time and possibly modified by the application, which\n  constitutes the hard limit beyond which the cache will never grow;\n  and a number that depends on the current total number of slots in\n  the unique\\index{table!unique} table.\n\\item If the cache is not too large already, resizing is decided based\n  on the hit rate. The policy adopted by the CUDD package is\n  ``reward-based\\index{cache!reward-based resizing}.'' If the cache hit\n  rate is high, then it is worthwhile to increase the size of the\n  cache.\n\\end{enumerate}\nWhen resizing takes place, the statistical counters \\index{statistical\n  counters} used to compute the hit rate are reinitialized so as to\nprevent immediate resizing. The number of entries is doubled.\n\nThe rationale for the ``reward-based\\index{cache!reward-based resizing}''\npolicy is as follows. In many BDD/ADD applications the hit rate is\nnot very sensitive to the size of the cache: It is primarily a\nfunction of the problem instance at hand.  If a large hit rate is\nobserved, chances are that by using a large cache, the results of\nlarge problems (those that would take longer to solve) will survive in\nthe cache without being overwritten long enough to cause a valuable\ncache hit. Notice that when a large problem is solved more than once,\nso are its recursively generated subproblems.  If the hit rate is\nlow, the probability of large problems being solved more than once is\nlow.\n\nThe other observation about the cache sizing policy is that there is\nlittle point in keeping a cache which is much larger than the unique\ntable. Every time the unique table ``fills up,'' garbage collection is\ninvoked and the cache is cleared of all dead entries. A cache that is\nmuch larger than the unique\\index{table!unique} table is therefore\nless than fully utilized.\n\n\\subsubsection{Local Caches}\n\\index{cache!local}\\label{sec:local-caches}\n\nSometimes it may be necessary or convenient to use a local cache.  A\nlocal cache can be lossless\\index{cache!lossless} (no results are ever\noverwritten), or it may store objects for which\ncanonical\\index{canonical} representations are not available.  One\nimportant fact to keep in mind when using a local cache is that local\ncaches are not cleared during garbage\\index{garbage collection}\ncollection or before reordering. Therefore, it is necessary to\nincrement the reference\\index{node!reference count} count of all nodes\npointed by a local cache. (Unless their reference counts are\nguaranteed positive in some other way. One such way is by including\nall partial results in the global result.) Before disposing of the\nlocal cache, all elements stored in it must be passed to\n\\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref}. As consequence\nof the fact that all results in a local cache are referenced, it is\ngenerally convenient to store in the local cache also the result of\ntrivial problems, which are not usually stored in the global cache.\nOtherwise, after a recursive call, it is difficult to tell whether the\nresult is in the cache, and therefore referenced, or not in the cache,\nand therefore not referenced.\n\nAn alternative approach to referencing the results in the local caches\nis to install hook functions (see Section~\\ref{sec:hooks}) to be\nexecuted before garbage collection.\n\n\\subsection{The Unique Table}\n\\index{table!unique}\\label{sec:unique}\n\nA recursive procedure typically splits the operands by expanding with\nrespect to the topmost variable. Topmost in this context refers to the\nvariable that is closest to the roots in the current variable order.\nThe nodes, on the other hand, hold the index, which is invariant with\nreordering. Therefore, when splitting, one must use the\npermutation\\index{variable!permutation} array maintained by the\npackage to get the right level. Access to the permutation array is\nprovided by the macro \\emph{cuddI}\\eidx{cuddI} for BDDs and ADDs,\nand by the macro \\emph{cuddIZ}\\eidx{cuddIZ} for ZDDs.\n\nThe unique table consists of as many hash\\index{table!hash} tables as\nthere are variables in use. These has tables are called \\emph{unique\n  subtables}.  The sizes of the unique subtables are determined by two\ncriteria:\n\\begin{enumerate}\n\\item The collision\\index{cache!collision list} lists should be short\n  to keep access time down.\n\\item There should be enough room for dead\\index{node!dead} nodes, to\n  prevent too frequent garbage\\index{garbage collection} collections.\n\\end{enumerate}\nWhile the first criterion is fairly straightforward to implement, the\nsecond leaves more room to creativity. The CUDD package tries to\nfigure out whether more dead node should be allowed to increase\nperformance.  (See also Section~\\ref{sec:params}.) There are two\nreasons for not doing garbage collection too often. The obvious one is\nthat it is expensive.  The second is that dead nodes may be\nreclaimed\\index{node!reclaimed}, if they are the result of a\nsuccessful cache lookup. Hence dead nodes may provide a substantial\nspeed-up if they are kept around long enough.  The usefulness of\nkeeping many dead nodes around varies from application to application,\nand from problem instance to problem instance. As in the sizing of the\ncache, the CUDD package adopts a\n``reward-based\\index{table!unique!reward-based resizing}'' policy to\ndecide how much room should be used for the unique table. If the\nnumber of dead nodes reclaimed is large compared to the number of\nnodes directly requested from the memory manager, then the CUDD\npackage assumes that it will be beneficial to allow more room for the\nsubtables, thereby reducing the frequency of garbage collection.  The\npackage does so by switching between two modes of operation:\n\\begin{enumerate}\n\\item Fast growth\\index{table!unique!fast growth}: In this mode, the\n  ratio of dead nodes to total nodes required for garbage collection\n  is higher than in the slow growth mode to favor resizing\n  of the subtables.\n\\item Slow growth\\index{table!unique!slow growth}: In this\n  mode keeping many dead nodes around is not as important as\n  keeping memory requirements low.\n\\end{enumerate}\nSwitching from one mode to the other is based on the following\ncriteria:\n\\begin{enumerate}\n\\item If the unique table is already large, only slow growth is\n  possible.\n\\item If the table is small and many dead nodes are being reclaimed,\n  then fast growth is selected.\n\\end{enumerate}\nThis policy is especially effective when the diagrams being\nmanipulated have lots of recombination. Notice the interplay of the\ncache sizing and unique sizing: Fast growth normally occurs when the\ncache hit rate is large. The cache and the unique table then grow in\nconcert, preserving a healthy balance between their sizes.\n\n\\subsection{Allowing Asynchronous Reordering}\n\\index{reordering!asynchronous}\\label{sec:async}\n\nAsynchronous reordering is the reordering that is triggered\nautomatically by the increase of the number of nodes. Asynchronous\nreordering takes place when a new internal node must be created, and\nthe number of nodes has reached a given\nthreshold\\index{reordering!threshold}. (The threshold is adjusted by\nthe package every time reordering takes place.)\n\nThose procedures that do not create new nodes (e.g., procedures that\ncount the number of nodes or minterms\\index{function!minterms}) need\nnot worry about asynchronous reordering: No special precaution is\nnecessary in writing them.\n\nProcedures that only manipulate decision diagrams through the exported\nfunctions of the CUDD package also need not concern themselves with\nasynchronous reordering. (See Section~\\ref{sec:nodes} for the\nexceptions.)\n\nThe remaining class of procedures is composed of functions that visit\nthe diagrams and may create new nodes. All such procedures in the CUDD\npackage are written so that they can be interrupted by dynamic\nreordering. The general approach followed goes under the name of\n``abort and retry\\index{reordering!abort and retry}.'' As the name\nimplies, a computation that is interrupted by dynamic reordering is\naborted and tried again.\n\nA recursive procedure that can be interrupted by dynamic reordering\n(an interruptible\\index{reordering!interruptible procedure} procedure\nfrom now on) is composed of two functions.  One is responsible for the\nreal computation. The other is a simple\nwrapper\\index{reordering!function wrapper}, which tests whether\nreordering occurred and restarts the computation if it did.\n\nAsynchronous reordering of BDDs and ADDs can only be triggered inside\n\\emph{cuddUniqueInter}\\eidx{cuddUniqueInter}, when a new node is about\nto be created.  Likewise, asynchronous reordering of ZDDs can only be\ntriggered inside \\emph{cuddUniqueInterZdd}\\eidx{cuddUniqueInterZdd}.\nWhen reordering is triggered, three things happen:\n\\begin{enumerate}\n\\item \\emph{cuddUniqueInter}\\eidx{cuddUniqueInter} returns a NULL\n  value;\n\\item The flag \\emph{reordered} of the manager is set to 1. (0 means\n  no reordering, while 2 indicates an error occurred during\n  reordering.)\n\\item The counter \\emph{reorderings} of the manager is incremented.\n  The counter is initialized to 0 when the manager is started and can\n  be accessed by calling\n  \\emph{Cudd\\_ReadReorderings}\\eidx{Cudd\\_ReadReorderings}. By taking\n  two readings of the counter, an application can determine if\n  variable reordering has taken place between the first and the second\n  reading.  The package itself, however, does not make use of the\n  counter: It is mentioned here for completeness.\n\\end{enumerate}\n\nThe recursive procedure that receives a NULL value from\n\\emph{cuddUniqueInter}\\eidx{cuddUniqueInter} must free all\nintermediate results that it may have computed before, and return NULL\nin its turn.\n\nThe wrapper\\index{reordering!function wrapper} function does not\ndecide whether reordering occurred based on the NULL return value,\nbecause the NULL value may be the result of lack of memory. Instead,\nit checks the \\emph{reordered} flag.\n\nWhen a recursive procedure calls another recursive procedure that may\ncause reordering, it should bypass the wrapper and call the recursive\nprocedure directly. Otherwise, the calling procedure will not know\nwhether reordering occurred, and will not be able to restart.  This is\nthe main reason why most recursive procedures are internal, rather\nthan static. (The wrappers, on the other hand, are mostly exported.)\n\n\\subsection{Debugging}\n\\index{debugging}\\label{sec:debug}\n\nBy defining the symbol DD\\_DEBUG\\index{DD\\_DEBUG} during compilation,\nnumerous checks are added to the code.  In addition, the procedures\n\\emph{Cudd\\_DebugCheck}\\eidx{Cudd\\_DebugCheck},\n\\emph{Cudd\\_CheckKeys}\\eidx{Cudd\\_CheckKeys}, and\n\\emph{cuddHeapProfile}\\eidx{cuddHeapProfile} can be called at any\npoint to verify the consistency of the data structure.\n(\\emph{cuddHeapProfile} is an internal procedure.  It is declared in\n\\emph{cuddInt.h}\\index{cuddInt.h}.)  Procedures\n\\emph{Cudd\\_DebugCheck} and \\emph{Cudd\\_CheckKeys} are especially\nuseful when CUDD reports that during garbage collection the number of\nnodes actually deleted from the unique table is different from the\ncount of dead nodes kept by the manager.  The error causing the\ndiscrepancy may have occurred much earlier than it is discovered.  A\nfew strategicaly placed calls to the debugging procedures can\nconsiderably narrow down the search for the source of the problem.\n(For instance, a call to \\emph{Cudd\\_RecursiveDeref} where one to\n\\emph{Cudd\\_Deref} was required may be identified in this way.)\n\nOne of the most common problems encountered in debugging code based on\nthe CUDD package is a missing call to\n\\emph{Cudd\\_RecursiveDeref}\\eidx{Cudd\\_RecursiveDeref}.  To help\nidentify this type of problems, the package provides a function called\n\\emph{Cudd\\_CheckZeroRef}\\eidx{Cudd\\_CheckZeroRef}.  This function\nshould be called immediately before shutting down the manager.\n\\emph{Cudd\\_CheckZeroRef} checks that the only nodes left with\nnon-zero reference\\index{node!reference count} counts are the\npredefined constants, the BDD projection\\index{projection functions}\nfunctions, and nodes whose reference counts are\nsaturated\\index{node!reference count!saturated}.\n\nFor this function to be effective the application must explicitly\ndispose of all diagrams to which it has pointers before calling it.\n\n\\subsection{Gathering and Interpreting Statistics}\n\\index{statistics}\\label{sec:stats}\n\nFunction \\emph{Cudd\\_PrintInfo}\\eidx{Cudd\\_PrintInfo} can be called to\nprint out the values of parameters and statistics for a manager.  The\noutput of \\emph{Cudd\\_PrintInfo} is divided in two sections.  The\nfirst reports the values of parameters that are under the application\ncontrol. The second reports the values of statistical counters and\nother non-modifiable parameters. A quick guide to the interpretation\nof all these quantities follows. For ease of exposition, we reverse\nthe order and describe the non-modifiable parameters first. We'll use\na sample run as example. There is nothing special about this run.\n\n\\subsubsection{Non Modifiable Parameters}\n\\label{sec:nonModPar}\n\nThe list of non-modifiable parameters starts with:\n\\begin{verbatim}\n    **** CUDD non-modifiable parameters ****\n    Memory in use: 32544220\n\\end{verbatim}\nThis is the memory used by CUDD for three things mainly: Unique table\n(including all DD nodes in use), node free list, and computed table.\nThis number almost never decreases in the lifetime of a CUDD manager,\nbecause CUDD does not release memory when it frees nodes.  Rather, it\nputs the nodes on its own free list. This number is in bytes. It does\nnot represent the peak memory occupation, because it does not include\nthe size of data structures created temporarily by some functions (e.g.,\nlocal look-up tables).\n\n\\begin{verbatim}\n    Peak number of nodes: 837018\n\\end{verbatim}\nThis number is the number of nodes that the manager has allocated.\nThis is not the largest size of the BDDs, because the manager will\nnormally have some dead nodes and some nodes on the free list.\n\n\\begin{verbatim}\n    Peak number of live nodes: 836894\n\\end{verbatim}\nThis is the largest number of live nodes that the manager has held\nsince its creation.\n\n\\begin{verbatim}\n    Number of BDD variables: 198\n    Number of ZDD variables: 0\n\\end{verbatim}\nThese numbers tell us this run was not using ZDDs.\n\n\\begin{verbatim}\n    Number of cache entries: 1048576\n\\end{verbatim}\nCurrent number of slots of the computed table.  If one has a\nperformance problem, this is one of the numbers to look at. The cache\nsize is always a power of 2.\n\n\\begin{verbatim}\n    Number of cache look-ups: 2996536\n    Number of cache hits: 1187087\n\\end{verbatim}\nThese numbers give an indication of the hit rate in the computed\ntable. It is not unlikely for model checking runs to get\nhit rates even higher than this one (39.62\\%).\n\n\\begin{verbatim}\n    Number of cache insertions: 1809473\n    Number of cache collisions: 961208\n    Number of cache deletions: 0\n\\end{verbatim}\nA collision\\index{cache!collision} occurs when a cache entry is\noverwritten. A deletion\\index{cache!deletion}\noccurs when a cache entry is invalidated (e.g., during garbage\ncollection).  If the number of deletions is high compared to the\nnumber of collisions, it means that garbage collection occurs too\noften. In this case there were no garbage collections; hence, no\ndeletions.\n\n\\begin{verbatim}\n    Cache used slots = 80.90% (expected 82.19%)\n\\end{verbatim}\nPercentage of cache slots that contain a valid entry. If this\nnumber is small, it may signal one of three conditions:\n\\begin{enumerate}\n\\item The cache may have been recently resized and it is still filling\n  up.\n\\item The cache is too large for the BDDs. This should not happen if\n  the size of the cache is determined by CUDD.\n\\item The hash function is not working properly. This is accompanied\n  by a degradation in performance. Conversely, a degradation in\n  performance may be due to bad hash function behavior.\n\\end{enumerate}\nThe expected value is computed assuming a uniformly random\ndistribution of the accesses.  If the difference between the measured\nvalue and the expected value is large (unlike this case), the cache is\nnot working properly.\n\n\\begin{verbatim}\n    Soft limit for cache size: 1318912\n\\end{verbatim}\nThis number says how large the cache can grow. This limit is based on\nthe size of the unique table.  CUDD uses a reward-based policy for\ngrowing the cache. (See Section~\\ref{sec:cache-sizing}.)  The default\nhit rate for resizing is 30\\% and the value in effect is reported\namong the modifiable parameters.\n\n\\begin{verbatim}\n    Number of buckets in unique table: 329728\n\\end{verbatim}\nThis number is exactly one quarter of the one above. This is indeed\nhow the soft limit is determined currently, unless the computed table\nhits the specified hard limit. (See below.)\n\n\\begin{verbatim}\n    Used buckets in unique table: 87.96% (expected 87.93%)\n\\end{verbatim}\nPercentage of unique table buckets that contain at least one\nnode. Remarks analogous to those made about the used cache slots apply.\n\n\\begin{verbatim}\n    Number of BDD and ADD nodes: 836894\n    Number of ZDD nodes: 0\n\\end{verbatim}\nHow many nodes are currently in the unique table, either alive or dead.\n\n\\begin{verbatim}\n    Number of dead BDD and ADD nodes: 0\n    Number of dead ZDD nodes: 0\n\\end{verbatim}\nSubtract these numbers from those above to get the number of live\nnodes. In this case there are no dead nodes because the application\nuses delayed dereferencing\n\\emph{Cudd\\_DelayedDerefBdd}\\eidx{Cudd\\_DelayedDerefBdd}.\n\n\\begin{verbatim}\n    Total number of nodes allocated: 836894\n\\end{verbatim}\nThis is the total number of nodes that were requested and obtained\nfrom the free list. It never decreases, and is not an indication of\nmemory occupation after the first garbage collection. Rather, it is a\nmeasure of the package activity.\n\n\\begin{verbatim}\n    Total number of nodes reclaimed: 0\n\\end{verbatim}\nThese are the nodes that were resuscitated from the dead.  If they are\nmany more than the allocated nodes, and the total\nnumber of slots is low relative to the number of nodes, then one may\nwant to increase the limit for fast unique table growth. In this case,\nthe number is 0 because of delayed dereferencing.\n\n\\begin{verbatim}\n    Garbage collections so far: 0\n    Time for garbage collections: 0.00 sec\n    Reorderings so far: 0\n    Time for reordering: 0.00 sec\n\\end{verbatim}\nThere is a GC for each reordering. Hence the first count will always be\nat least as large as the second.\n\n\\begin{verbatim}\n    Node swaps in reordering: 0\n\\end{verbatim}\nThis is the number of elementary reordering steps. Each step consists\nof the re-expression of one node while swapping two adjacent\nvariables. This number is a good measure of the amount of work done in\nreordering.\n\n\\subsubsection{Modifiable Parameters}\n\\label{sec:modPar}\n\nLet us now consider the modifiable parameters, that is, those settings on\nwhich the application or the user has control.\n\n\\begin{verbatim}\n    **** CUDD modifiable parameters ****\n    Hard limit for cache size: 8388608\n\\end{verbatim}\nThis number counts entries. Each entry is 16 bytes if CUDD is compiled\nto use 32-bit pointers. Two important observations are in order:\n\\begin{enumerate}\n\\item If the datasize limit is set, CUDD will use it to determine this\n  number automatically. On a Unix system, one can type ``limit'' or\n  ``ulimit'' to verify if this value is set. If the datasize limit is\n  not set, CUDD uses a default which is rather small. If you have\n  enough memory (say 64MB or more) you should seriously consider\n  \\emph{not} using the default. So, either set the datasize limit, or\n  override the default with\n  \\emph{Cudd\\_SetMaxCacheHard}\\eidx{Cudd\\_SetMaxCacheHard}.\n\\item If a process seems to be going nowhere, a small value for\n  this parameter may be the culprit. One cannot overemphasize the\n  importance of the computed table in BDD algorithms.\n\\end{enumerate}\nIn this case the limit was automatically set for a target maximum\nmemory occupation of 104 MB.\n\n\\begin{verbatim}\n    Cache hit threshold for resizing: 15%\n\\end{verbatim}\nThis number can be changed if one suspects performance is hindered by\nthe small size of the cache, and the cache is not growing towards the\nsoft limit sufficiently fast. In such a case one can change the\ndefault 30\\% to 15\\% (as in this case) or even 1\\%.\n\n\\begin{verbatim}\n    Garbage collection enabled: yes\n\\end{verbatim}\nOne can disable it, but there are few good reasons for doing\nso. It is normally preferable to raise the limit for fast unique table\ngrowth. (See below.)\n\n\\begin{verbatim}\n    Limit for fast unique table growth: 1363148\n\\end{verbatim}\nSee Section~\\ref{sec:unique} and the comments above about reclaimed\nnodes and hard limit for the cache size. This value was chosen\nautomatically by CUDD for a datasize limit of 1 GB.\n\n\\begin{verbatim}\n    Maximum number of variables sifted per reordering: 1000\n    Maximum number of variable swaps per reordering: 2000000\n    Maximum growth while sifting a variable: 1.2\n\\end{verbatim}\nLowering these numbers will cause reordering to be less accurate and\nfaster. Results are somewhat unpredictable, because larger BDDs after one\nreordering do not necessarily mean the process will go faster or slower.\n\n\\begin{verbatim}\n    Dynamic reordering of BDDs enabled: yes\n    Default BDD reordering method: 4\n    Dynamic reordering of ZDDs enabled: no\n    Default ZDD reordering method: 4\n\\end{verbatim}\nThese lines tell whether automatic reordering can take place and what\nmethod would be used.  The mapping from numbers to methods is in\n\\texttt{cudd.h}.  One may want to try different BDD reordering\nmethods.  If variable groups are used, however, one should not expect\nto see big differences, because CUDD uses the reported method only to\nreorder each leaf variable group (typically corresponding present and\nnext state variables).  For the relative order of the groups, it\nalways uses the same algorithm, which is effectively sifting.\n\nAs for enabling dynamic reordering or not, a sensible recommendation is the\nfollowing: Unless the circuit is rather small or one has a pretty good\nidea of what the order should be, reordering should be enabled.\n\n\\begin{verbatim}\n    Realignment of ZDDs to BDDs enabled: no\n    Realignment of BDDs to ZDDs enabled: no\n    Dead nodes counted in triggering reordering: no\n    Group checking criterion: 7\n    Recombination threshold: 0\n    Symmetry violation threshold: 0\n    Arc violation threshold: 0\n    GA population size: 0\n    Number of crossovers for GA: 0\n\\end{verbatim}\nParameters for reordering. See the documentation of the functions used\nto control these parameters for the details.\n\n\\begin{verbatim}\n    Next reordering threshold: 100000\n\\end{verbatim}\nWhen the number of nodes crosses this threshold, reordering will be\ntriggered. (If enabled; in this case it is not.)  This parameter is\nupdated by the package whenever reordering takes place.  The\napplication can change it, for instance at start-up.  Another\npossibility is to use a hook function (see Section~\\ref{sec:hooks}) to\noverride the default updating policy.\n\n\\subsubsection{Extended Statistics and Reporting}\n\\label{sec:extendedStats}\n\nThe following symbols can be defined during compilation to increase\nthe amount of statistics gathered and the number of messages produced\nby the package:\n\\begin{itemize}\n\\item DD\\_STATS\\index{DD\\_STATS};\n\\item DD\\_CACHE\\_PROFILE\\index{DD\\_CACHE\\_PROFILE};\n\\item DD\\_UNIQUE\\_PROFILE\\index{DD\\_UNIQUE\\_PROFILE}.\n\\item DD\\_VERBOSE\\index{DD\\_VERBOSE};\n\\end{itemize}\nDefining DD\\_CACHE\\_PROFILE causes each entry of the cache to include\nan access counter, which is used to compute simple statistics on the\ndistribution of the keys.\n\n\\subsection{Guidelines for Documentation}\n\\label{sec:doc}\\index{documentation}\n\nThe documentation of the CUDD functions is extracted automatically\nfrom the sources by \\texttt{doxygen}\\index{doxygen} \n\\href{http://www.doxygen.org}{\\texttt{www.doxygen.org}}.)\nThe following guidelines are adhered to in CUDD to insure consistent and\neffective use of automatic extraction. It is recommended that\nextensions to CUDD follow the same documentation guidelines.\n\\begin{itemize}\n\\item The documentation of an exported procedure should be sufficient\n  to allow one to use it without reading the code. It is not necessary\n  to explain how the procedure works; only what it does.\n\\item The \\emph{see}\\index{documentation!SeeAlso@\\emph{see}}\n  fields should be space-separated lists of function names.  The\n  \\emph{see} field of an exported procedure should only reference\n  other exported procedures. The \\emph{see} field of an internal\n  procedure may reference other internal procedures as well as\n  exported procedures, but no static procedures.\n\\item The return values are detailed in the\n  \\emph{return}\\index{documentation!Description@\\emph{return}}\n  field, not in the\n  \\emph{brief}\\index{documentation!Synopsis@\\emph{brief}} field.\n\\item The parameters are documented alongside their declarations.\n  Further comments may appear in the \\emph{details} field.\n\\item The \\emph{brief} field should be about one line long.\n\\end{itemize}\n\n%----------------------------------------\n\n\\section{The C++ Interface}\n\\label{sec:cpp}\n\n\n\\subsection{Compiling and Linking}\n\\label{sec:compileCpp}\n\nTo build an application that uses the CUDD C++ interface, you should\nadd\n\\begin{verbatim}\n#include \"cuddObj.hh\"\n\\end{verbatim}\nto your source files. In addition to the normal CUDD libraries (see\nSection~\\ref{sec:compileExt}) you should link\n\\verb|libobj.a|\\index{libraries!obj} to your executable. Refer to the\ninstallation notes in the top level directory of the distribution for\nfurther details.\n\n\\subsection{Basic Manipulation}\n\\label{sec:basicCpp}\n\nThe following fragment of code illustrates some simple operations on\nBDDs using the C++ interface.\n\\begin{verbatim}\n\tCudd mgr(0,0);\n\tBDD x = mgr.bddVar();\n\tBDD y = mgr.bddVar();\n\tBDD f = x * y;\n\tBDD g = y + !x;\n\tcout << \"f is\" << (f <= g ? \"\" : \" not\")\n\t     << \" less than or equal to g\\n\";\n\\end{verbatim}\nThis code creates a manager called \\verb|mgr| and two variables in it.\nIt then defines two functions \\verb|f| and \\verb|g| in terms of the\nvariables. Finally, it prints a message based on the comparison of the\ntwo functions. No explicit referencing or dereferencing is required.\nThe operators are overloaded in the intuitive way. BDDs are freed when\nexecution leaves the scope in which they are defined or when the\nvariables referring to them are overwritten.\n\n%----------------------------------------\n\\section{Acknowledgments}\n\\label{sec:ack}\n\nThe contributors: Iris Bahar, Hyunwoo Cho, Erica Frohm, Charlie Gaona,\nCheng Hua, Jae-Young Jang, Seh-Woong Jeong, Balakrishna Kumthekar,\nEnrico Macii, Bobbie Manne, In-Ho Moon, Curt Musfeldt, Shipra Panda,\nAbelardo Pardo, Bernard Plessier, Kavita Ravi, Hyongkyoon Shin, Alan\nShuler, Arun Sivakumaran, Jorgen Sivesind.\n\n\\noindent\nThe early adopters: Gianpiero Cabodi, Jordi Cortadella, Mario Escobar,\nGayani Gamage, Gary Hachtel, Mariano Hermida, Woohyuk Lee, Enric\nPastor, Massimo Poncino, Ellen Sentovich, the students of ECEN5139.\n\nI am also particularly indebted to the following people for in-depth\ndiscussions on BDDs: Armin Biere, Olivier Coudert, Hubert Garavel,\nArie Gurfinkel, Geert Janssen, Don Knuth, David Long, Jean Christophe\nMadre, Ken McMillan, Shin-Ichi Minato, Jaehong Park, Rajeev Ranjan,\nRick Rudell, Ellen Sentovich, Tom Shiple, Christian Stangier, and\nBwolen Yang.\n\nSpecial thanks to Norris Ip for guiding my faltering steps\nin the design of the C++ interface.\nGianpiero Cabodi and Stefano Quer have graciously agreed to let me\ndistribute their dddmp library with CUDD.\n\nMasahiro Fujita, Gary Hachtel, and Carl Pixley have provided\nencouragement and advice.\n\nThe National Science Foundation and the Semiconductor Research\nCorporation have supported in part the development of this package.\n\n\\phantomsection\n\\addcontentsline{toc}{section}{\\numberline{}References}\n%\\bibliography{comb-synthesis,references,ref2}\n\n\\begin{thebibliography}{10}\n\n\\bibitem{Bahar93}\nR.~I. Bahar, E.~A. Frohm, C.~M. Gaona, G.~D. Hachtel, E.~Macii, A.~Pardo, and\n  F.~Somenzi.\n\\newblock Algebraic decision diagrams and their applications.\n\\newblock In {\\em Proceedings of the International Conference on Computer-Aided\n  Design}, pages 188--191, Santa Clara, CA, November 1993.\n\n\\bibitem{Bollig95}\nB.~Bollig, M.~L\\\"obbing, and I.~Wegener.\n\\newblock Simulated annealing to improve variable orderings for {OBDDs}.\n\\newblock Presented at the International Workshop on Logic Synthesis,\n  Granlibakken, CA, May 1995.\n\n\\bibitem{BBR}\nK.~S. Brace, R.~L. Rudell, and R.~E. Bryant.\n\\newblock Efficient implementation of a {BDD} package.\n\\newblock In {\\em Proceedings of the 27th Design Automation Conference}, pages\n  40--45, Orlando, FL, June 1990.\n\n\\bibitem{BDD}\nR.~E. Bryant.\n\\newblock Graph-based algorithms for {Boolean} function manipulation.\n\\newblock {\\em IEEE Transactions on Computers}, C-35(8):677--691, August 1986.\n\n\\bibitem{Drechs95}\nR.~Drechsler, B.~Becker, and N.~G\\\"ockel.\n\\newblock A genetic algorithm for variable ordering of {OBDDs}.\n\\newblock Presented at the International Workshop on Logic Synthesis,\n  Granlibakken, CA, May 1995.\n\n\\bibitem{Friedman90}\nS.~J. Friedman and K.~J. Supowit.\n\\newblock Finding the optimal variable ordering for binary decision diagrams.\n\\newblock {\\em IEEE Transactions on Computers}, 39(5):710--713, May 1990.\n\n\\bibitem{Fujita91b}\nM.~Fujita, Y.~Matsunaga, and T.~Kakuda.\n\\newblock On variable ordering of binary decision diagrams for the application\n  of multi-level logic synthesis.\n\\newblock In {\\em Proceedings of the European Conference on Design Automation},\n  pages 50--54, Amsterdam, February 1991.\n\n\\bibitem{Held62}\nM.~Held and R.~M. Karp.\n\\newblock A dynamic programming approach to sequencing problems.\n\\newblock {\\em J. SIAM}, 10(1):196--210, 1962.\n\n\\bibitem{Ishiur91}\nN.~Ishiura, H.~Sawada, and S.~Yajima.\n\\newblock Minimization of binary decision diagrams based on exchanges of\n  variables.\n\\newblock In {\\em Proceedings of the International Conference on Computer-Aided\n  Design}, pages 472--475, Santa Clara, CA, November 1991.\n\n\\bibitem{Jeong93}\nS.-W. Jeong, T.-S. Kim, and F.~Somenzi.\n\\newblock An efficient method for optimal {BDD} ordering computation.\n\\newblock In {\\em International Conference on VLSI and CAD (ICVC'93)}, Taejon,\n  Korea, November 1993.\n\n\\bibitem{Minato93}\nS.-I. Minato.\n\\newblock Zero-suppressed {BDD}s for set manipulation in combinatorial\n  problems.\n\\newblock In {\\em Proceedings of the Design Automation Conference}, pages\n  272--277, Dallas, TX, June 1993.\n\n\\bibitem{Panda95b}\nS.~Panda and F.~Somenzi.\n\\newblock Who are the variables in your neighborhood.\n\\newblock In {\\em Proceedings of the International Conference on Computer-Aided\n  Design}, pages 74--77, San Jose, CA, November 1995.\n\n\\bibitem{Panda94}\nS.~Panda, F.~Somenzi, and B.~F. Plessier.\n\\newblock Symmetry detection and dynamic variable ordering of decision\n  diagrams.\n\\newblock In {\\em Proceedings of the International Conference on Computer-Aided\n  Design}, pages 628--631, San Jose, CA, November 1994.\n\n\\bibitem{Plessi93}\nB.~F. Plessier.\n\\newblock {\\em A General Framework for Verification of Sequential Circuits}.\n\\newblock PhD thesis, University of Colorado at Boulder, Dept.\\ of Electrical\n  and Computer Engineering, 1993.\n\n\\bibitem{Rudell93}\nR.~Rudell.\n\\newblock Dynamic variable ordering for ordered binary decision diagrams.\n\\newblock In {\\em Proceedings of the International Conference on Computer-Aided\n  Design}, pages 42--47, Santa Clara, CA, November 1993.\n\n\\end{thebibliography}\n\n\n% Index cross-references.\n\\index{Algebraic Decision Diagram|see{ADD}}\n\\index{Binary Decision Diagram|see{BDD}}\n\\index{Zero-suppressed Binary Decision Diagram|see{ZDD}}\n\\index{dot|see{graph, drawing}}\n\\index{extdoc|see{documentation}}\n\\index{node!terminal|see{node, constant}}\n\\phantomsection\n\\addcontentsline{toc}{section}{\\numberline{}Index}\n\\printindex\n\\end{document}\n\n%%% Local Variables:\n%%% mode: latex\n%%% TeX-master: t\n%%% TeX-PDF-mode: t\n%%% End:\n"
  },
  {
    "path": "cudd/epd/Included.am",
    "content": "cudd_libcudd_la_SOURCES += epd/epd.c epd/epdInt.h epd/epd.h\n"
  },
  {
    "path": "cudd/epd/epd.c",
    "content": "/**\n  @file\n\n  @ingroup epd\n\n  @brief Arithmetic functions with extended double precision.\n\n  @author In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include <math.h>\n#include \"util.h\"\n#include \"epdInt.h\"\n\n\n/**\n  @brief Allocates an EpDouble struct.\n*/\nEpDouble *\nEpdAlloc(void)\n{\n  EpDouble\t*epd;\n\n  epd = ALLOC(EpDouble, 1);\n  return(epd);\n}\n\n\n/**\n  @brief Compares two EpDouble struct.\n\n  @return 0 if the two structures hold the same value; 1 otherwise.\n*/\nint\nEpdCmp(const void *key1, const void *key2)\n{\n  EpDouble const *epd1 = (EpDouble const *) key1;\n  EpDouble const *epd2 = (EpDouble const *) key2;\n  if (epd1->type.value != epd2->type.value ||\n      epd1->exponent != epd2->exponent) {\n    return(1);\n  }\n  return(0);\n}\n\n\n/**\n  @brief Frees an EpDouble struct.\n*/\nvoid\nEpdFree(EpDouble *epd)\n{\n  FREE(epd);\n}\n\n\n/**\n  @brief Converts an extended precision double value to a string.\n\n  @sideeffect The string is written at the address passed in `str`.\n*/\nvoid\nEpdGetString(EpDouble const *epd, char *str)\n{\n  double\tvalue;\n  int\t\texponent;\n  char\t\t*pos;\n\n  if (!str) return;\n\n  if (IsNanDouble(epd->type.value)) {\n    sprintf(str, \"NaN\");\n    return;\n  } else if (IsInfDouble(epd->type.value)) {\n    if (epd->type.bits.sign == 1)\n      sprintf(str, \"-inf\");\n    else\n      sprintf(str, \"inf\");\n    return;\n  }\n\n  assert(epd->type.bits.exponent == EPD_MAX_BIN ||\n\t epd->type.bits.exponent == 0);\n\n  EpdGetValueAndDecimalExponent(epd, &value, &exponent);\n  sprintf(str, \"%e\", value);\n  pos = strstr(str, \"e\");\n  if (exponent >= 0) {\n    if (exponent < 10)\n      sprintf(pos + 1, \"+0%d\", exponent);\n    else\n      sprintf(pos + 1, \"+%d\", exponent);\n  } else {\n    exponent *= -1;\n    if (exponent < 10)\n      sprintf(pos + 1, \"-0%d\", exponent);\n    else\n      sprintf(pos + 1, \"-%d\", exponent);\n  }\n}\n\n\n/**\n  @brief Converts double to EpDouble struct.\n*/\nvoid\nEpdConvert(double value, EpDouble *epd)\n{\n  epd->type.value = value;\n  epd->exponent = 0;\n  EpdNormalize(epd);\n}\n\n\n/**\n  @brief Multiplies an extended precision double by a double.\n*/\nvoid\nEpdMultiply(EpDouble *epd1, double value)\n{\n  EpDouble\tepd2;\n  double\ttmp;\n  int\t\texponent;\n\n  if (EpdIsNan(epd1) || IsNanDouble(value)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || IsInfDouble(value)) {\n    int\tsign;\n\n    EpdConvert(value, &epd2);\n    sign = epd1->type.bits.sign ^ epd2.type.bits.sign;\n    EpdMakeInf(epd1, sign);\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n\n  EpdConvert(value, &epd2);\n  tmp = epd1->type.value * epd2.type.value;\n  exponent = epd1->exponent + epd2.exponent;\n  epd1->type.value = tmp;\n  epd1->exponent = exponent;\n  EpdNormalize(epd1);\n}\n\n\n/**\n  @brief Multiplies an extended precision double by another.\n*/\nvoid\nEpdMultiply2(EpDouble *epd1, EpDouble const *epd2)\n{\n  double\tvalue;\n  int\t\texponent;\n\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n    EpdMakeInf(epd1, sign);\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n  assert(epd2->type.bits.exponent == EPD_MAX_BIN);\n\n  value = epd1->type.value * epd2->type.value;\n  exponent = epd1->exponent + epd2->exponent;\n  epd1->type.value = value;\n  epd1->exponent = exponent;\n  EpdNormalize(epd1);\n}\n\n\n/**\n  @brief Multiplies two extended precision double values.\n*/\nvoid\nEpdMultiply2Decimal(EpDouble *epd1, EpDouble const *epd2)\n{\n  double\tvalue;\n  int\t\texponent;\n\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n    EpdMakeInf(epd1, sign);\n    return;\n  }\n\n  value = epd1->type.value * epd2->type.value;\n  exponent = epd1->exponent + epd2->exponent;\n  epd1->type.value = value;\n  epd1->exponent = exponent;\n  EpdNormalizeDecimal(epd1);\n}\n\n\n/**\n  @brief Multiplies two extended precision double values.\n\n  @details The result goes in the third operand.\n*/\nvoid\nEpdMultiply3(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3)\n{\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd3);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n    EpdMakeInf(epd3, sign);\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n  assert(epd2->type.bits.exponent == EPD_MAX_BIN);\n\n  epd3->type.value = epd1->type.value * epd2->type.value;\n  epd3->exponent = epd1->exponent + epd2->exponent;\n  EpdNormalize(epd3);\n}\n\n\n/**\n  @brief Multiplies two extended precision double values.\n*/\nvoid\nEpdMultiply3Decimal(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3)\n{\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd3);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n    EpdMakeInf(epd3, sign);\n    return;\n  }\n\n  epd3->type.value = epd1->type.value * epd2->type.value;\n  epd3->exponent = epd1->exponent + epd2->exponent;\n  EpdNormalizeDecimal(epd3);\n}\n\n\n/**\n  @brief Divides an extended precision double by a double.\n*/\nvoid\nEpdDivide(EpDouble *epd1, double value)\n{\n  EpDouble\tepd2;\n  double\ttmp;\n  int\t\texponent;\n\n  if (EpdIsNan(epd1) || IsNanDouble(value)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || IsInfDouble(value)) {\n    int\tsign;\n\n    EpdConvert(value, &epd2);\n    if (EpdIsInf(epd1) && IsInfDouble(value)) {\n      EpdMakeNan(epd1);\n    } else if (EpdIsInf(epd1)) {\n      sign = epd1->type.bits.sign ^ epd2.type.bits.sign;\n      EpdMakeInf(epd1, sign);\n    } else {\n      sign = epd1->type.bits.sign ^ epd2.type.bits.sign;\n      EpdMakeZero(epd1, sign);\n    }\n    return;\n  }\n\n  if (value == 0.0) {\n    EpdMakeNan(epd1);\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n\n  EpdConvert(value, &epd2);\n  tmp = epd1->type.value / epd2.type.value;\n  exponent = epd1->exponent - epd2.exponent;\n  epd1->type.value = tmp;\n  epd1->exponent = exponent;\n  EpdNormalize(epd1);\n}\n\n\n/**\n  @brief Divides an extended precision double by another.\n*/\nvoid\nEpdDivide2(EpDouble *epd1, EpDouble const *epd2)\n{\n  double\tvalue;\n  int\t\texponent;\n\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    if (EpdIsInf(epd1) && EpdIsInf(epd2)) {\n      EpdMakeNan(epd1);\n    } else if (EpdIsInf(epd1)) {\n      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n      EpdMakeInf(epd1, sign);\n    } else {\n      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n      EpdMakeZero(epd1, sign);\n    }\n    return;\n  }\n\n  if (epd2->type.value == 0.0) {\n    EpdMakeNan(epd1);\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n  assert(epd2->type.bits.exponent == EPD_MAX_BIN);\n\n  value = epd1->type.value / epd2->type.value;\n  exponent = epd1->exponent - epd2->exponent;\n  epd1->type.value = value;\n  epd1->exponent = exponent;\n  EpdNormalize(epd1);\n}\n\n\n/**\n  @brief Divides two extended precision double values.\n*/\nvoid\nEpdDivide3(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3)\n{\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd3);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    if (EpdIsInf(epd1) && EpdIsInf(epd2)) {\n      EpdMakeNan(epd3);\n    } else if (EpdIsInf(epd1)) {\n      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n      EpdMakeInf(epd3, sign);\n    } else {\n      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n      EpdMakeZero(epd3, sign);\n    }\n    return;\n  }\n\n  if (epd2->type.value == 0.0) {\n    EpdMakeNan(epd3);\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n  assert(epd2->type.bits.exponent == EPD_MAX_BIN);\n\n  epd3->type.value = epd1->type.value / epd2->type.value;\n  epd3->exponent = epd1->exponent - epd2->exponent;\n  EpdNormalize(epd3);\n}\n\n\n/**\n  @brief Adds a double to an extended precision double.\n*/\nvoid\nEpdAdd(EpDouble *epd1, double value)\n{\n  EpDouble\tepd2;\n  double\ttmp;\n  int\t\texponent, diff;\n\n  if (EpdIsNan(epd1) || IsNanDouble(value)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || IsInfDouble(value)) {\n    int\tsign;\n\n    EpdConvert(value, &epd2);\n    if (EpdIsInf(epd1) && IsInfDouble(value)) {\n      sign = epd1->type.bits.sign ^ epd2.type.bits.sign;\n      if (sign == 1)\n\tEpdMakeNan(epd1);\n    } else if (EpdIsInf(&epd2)) {\n      EpdCopy(&epd2, epd1);\n    }\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n\n  EpdConvert(value, &epd2);\n  if (epd1->exponent > epd2.exponent) {\n    diff = epd1->exponent - epd2.exponent;\n    if (diff <= EPD_MAX_BIN)\n      tmp = epd1->type.value + epd2.type.value / pow((double)2.0, (double)diff);\n    else\n      tmp = epd1->type.value;\n    exponent = epd1->exponent;\n  } else if (epd1->exponent < epd2.exponent) {\n    diff = epd2.exponent - epd1->exponent;\n    if (diff <= EPD_MAX_BIN)\n      tmp = epd1->type.value / pow((double)2.0, (double)diff) + epd2.type.value;\n    else\n      tmp = epd2.type.value;\n    exponent = epd2.exponent;\n  } else {\n    tmp = epd1->type.value + epd2.type.value;\n    exponent = epd1->exponent;\n  }\n  epd1->type.value = tmp;\n  epd1->exponent = exponent;\n  EpdNormalize(epd1);\n}\n\n\n/**\n  @brief Adds an extended precision double to another.\n\n  @details The sum goes in the first argument.\n*/\nvoid\nEpdAdd2(EpDouble *epd1, EpDouble const *epd2)\n{\n  double\tvalue;\n  int\t\texponent, diff;\n\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    if (EpdIsInf(epd1) && EpdIsInf(epd2)) {\n      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n      if (sign == 1)\n\tEpdMakeNan(epd1);\n    } else if (EpdIsInf(epd2)) {\n      EpdCopy(epd2, epd1);\n    }\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n  assert(epd2->type.bits.exponent == EPD_MAX_BIN);\n\n  if (epd1->exponent > epd2->exponent) {\n    diff = epd1->exponent - epd2->exponent;\n    if (diff <= EPD_MAX_BIN) {\n      value = epd1->type.value +\n\t\tepd2->type.value / pow((double)2.0, (double)diff);\n    } else\n      value = epd1->type.value;\n    exponent = epd1->exponent;\n  } else if (epd1->exponent < epd2->exponent) {\n    diff = epd2->exponent - epd1->exponent;\n    if (diff <= EPD_MAX_BIN) {\n      value = epd1->type.value / pow((double)2.0, (double)diff) +\n\t\tepd2->type.value;\n    } else\n      value = epd2->type.value;\n    exponent = epd2->exponent;\n  } else {\n    value = epd1->type.value + epd2->type.value;\n    exponent = epd1->exponent;\n  }\n  epd1->type.value = value;\n  epd1->exponent = exponent;\n  EpdNormalize(epd1);\n}\n\n\n/**\n  @brief Adds two extended precision double values.\n*/\nvoid\nEpdAdd3(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3)\n{\n  double\tvalue;\n  int\t\texponent, diff;\n\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd3);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    if (EpdIsInf(epd1) && EpdIsInf(epd2)) {\n      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n      if (sign == 1)\n\tEpdMakeNan(epd3);\n      else\n\tEpdCopy(epd1, epd3);\n    } else if (EpdIsInf(epd1)) {\n      EpdCopy(epd1, epd3);\n    } else {\n      EpdCopy(epd2, epd3);\n    }\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n  assert(epd2->type.bits.exponent == EPD_MAX_BIN);\n\n  if (epd1->exponent > epd2->exponent) {\n    diff = epd1->exponent - epd2->exponent;\n    if (diff <= EPD_MAX_BIN) {\n      value = epd1->type.value +\n\t\tepd2->type.value / pow((double)2.0, (double)diff);\n    } else\n      value = epd1->type.value;\n    exponent = epd1->exponent;\n  } else if (epd1->exponent < epd2->exponent) {\n    diff = epd2->exponent - epd1->exponent;\n    if (diff <= EPD_MAX_BIN) {\n      value = epd1->type.value / pow((double)2.0, (double)diff) +\n\t\tepd2->type.value;\n    } else\n      value = epd2->type.value;\n    exponent = epd2->exponent;\n  } else {\n    value = epd1->type.value + epd2->type.value;\n    exponent = epd1->exponent;\n  }\n  epd3->type.value = value;\n  epd3->exponent = exponent;\n  EpdNormalize(epd3);\n}\n\n\n/**\n  @brief Subtracts a double from an extended precision double.\n*/\nvoid\nEpdSubtract(EpDouble *epd1, double value)\n{\n  EpDouble\tepd2;\n  double\ttmp;\n  int\t\texponent, diff;\n\n  if (EpdIsNan(epd1) || IsNanDouble(value)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || IsInfDouble(value)) {\n    int\tsign;\n\n    EpdConvert(value, &epd2);\n    if (EpdIsInf(epd1) && IsInfDouble(value)) {\n      sign = epd1->type.bits.sign ^ epd2.type.bits.sign;\n      if (sign == 0)\n\tEpdMakeNan(epd1);\n    } else if (EpdIsInf(&epd2)) {\n      EpdCopy(&epd2, epd1);\n    }\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n\n  EpdConvert(value, &epd2);\n  if (epd1->exponent > epd2.exponent) {\n    diff = epd1->exponent - epd2.exponent;\n    if (diff <= EPD_MAX_BIN)\n      tmp = epd1->type.value - epd2.type.value / pow((double)2.0, (double)diff);\n    else\n      tmp = epd1->type.value;\n    exponent = epd1->exponent;\n  } else if (epd1->exponent < epd2.exponent) {\n    diff = epd2.exponent - epd1->exponent;\n    if (diff <= EPD_MAX_BIN)\n      tmp = epd1->type.value / pow((double)2.0, (double)diff) - epd2.type.value;\n    else\n      tmp = epd2.type.value * (double)(-1.0);\n    exponent = epd2.exponent;\n  } else {\n    tmp = epd1->type.value - epd2.type.value;\n    exponent = epd1->exponent;\n  }\n  epd1->type.value = tmp;\n  epd1->exponent = exponent;\n  EpdNormalize(epd1);\n}\n\n\n/**\n  @brief Subtracts an extended precision double from another.\n*/\nvoid\nEpdSubtract2(EpDouble *epd1, EpDouble const *epd2)\n{\n  double\tvalue;\n  int\t\texponent, diff;\n\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd1);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    if (EpdIsInf(epd1) && EpdIsInf(epd2)) {\n      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n      if (sign == 0)\n\tEpdMakeNan(epd1);\n    } else if (EpdIsInf(epd2)) {\n      EpdCopy(epd2, epd1);\n    }\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n  assert(epd2->type.bits.exponent == EPD_MAX_BIN);\n\n  if (epd1->exponent > epd2->exponent) {\n    diff = epd1->exponent - epd2->exponent;\n    if (diff <= EPD_MAX_BIN) {\n      value = epd1->type.value -\n\t\tepd2->type.value / pow((double)2.0, (double)diff);\n    } else\n      value = epd1->type.value;\n    exponent = epd1->exponent;\n  } else if (epd1->exponent < epd2->exponent) {\n    diff = epd2->exponent - epd1->exponent;\n    if (diff <= EPD_MAX_BIN) {\n      value = epd1->type.value / pow((double)2.0, (double)diff) -\n\t\tepd2->type.value;\n    } else\n      value = epd2->type.value * (double)(-1.0);\n    exponent = epd2->exponent;\n  } else {\n    value = epd1->type.value - epd2->type.value;\n    exponent = epd1->exponent;\n  }\n  epd1->type.value = value;\n  epd1->exponent = exponent;\n  EpdNormalize(epd1);\n}\n\n\n/**\n  @brief Subtracts two extended precision double values.\n*/\nvoid\nEpdSubtract3(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3)\n{\n  double\tvalue;\n  int\t\texponent, diff;\n\n  if (EpdIsNan(epd1) || EpdIsNan(epd2)) {\n    EpdMakeNan(epd3);\n    return;\n  } else if (EpdIsInf(epd1) || EpdIsInf(epd2)) {\n    int\tsign;\n\n    if (EpdIsInf(epd1) && EpdIsInf(epd2)) {\n      sign = epd1->type.bits.sign ^ epd2->type.bits.sign;\n      if (sign == 0)\n\tEpdCopy(epd1, epd3);\n      else\n\tEpdMakeNan(epd3);\n    } else if (EpdIsInf(epd1)) {\n      EpdCopy(epd1, epd3);\n    } else {\n      sign = epd2->type.bits.sign ^ 0x1;\n      EpdMakeInf(epd3, sign);\n    }\n    return;\n  }\n\n  assert(epd1->type.bits.exponent == EPD_MAX_BIN);\n  assert(epd2->type.bits.exponent == EPD_MAX_BIN);\n\n  if (epd1->exponent > epd2->exponent) {\n    diff = epd1->exponent - epd2->exponent;\n    if (diff <= EPD_MAX_BIN) {\n      value = epd1->type.value -\n\t\tepd2->type.value / pow((double)2.0, (double)diff);\n    } else\n      value = epd1->type.value;\n    exponent = epd1->exponent;\n  } else if (epd1->exponent < epd2->exponent) {\n    diff = epd2->exponent - epd1->exponent;\n    if (diff <= EPD_MAX_BIN) {\n      value = epd1->type.value / pow((double)2.0, (double)diff) -\n\t\tepd2->type.value;\n    } else\n      value = epd2->type.value * (double)(-1.0);\n    exponent = epd2->exponent;\n  } else {\n    value = epd1->type.value - epd2->type.value;\n    exponent = epd1->exponent;\n  }\n  epd3->type.value = value;\n  epd3->exponent = exponent;\n  EpdNormalize(epd3);\n}\n\n\n/**\n  @brief Computes extended precision pow of base 2.\n*/\nvoid\nEpdPow2(int n, EpDouble *epd)\n{\n  if (n <= EPD_MAX_BIN) {\n    EpdConvert(pow((double)2.0, (double)n), epd);\n  } else {\n    EpDouble\tepd1, epd2;\n    int\t\tn1, n2;\n\n    n1 = n / 2;\n    n2 = n - n1;\n    EpdPow2(n1, &epd1);\n    EpdPow2(n2, &epd2);\n    EpdMultiply3(&epd1, &epd2, epd);\n  }\n}\n\n\n/**\n  @brief Computes extended precision pow of base 2.\n*/\nvoid\nEpdPow2Decimal(int n, EpDouble *epd)\n{\n  if (n <= EPD_MAX_BIN) {\n    epd->type.value = pow((double)2.0, (double)n);\n    epd->exponent = 0;\n    EpdNormalizeDecimal(epd);\n  } else {\n    EpDouble\tepd1, epd2;\n    int\t\tn1, n2;\n\n    n1 = n / 2;\n    n2 = n - n1;\n    EpdPow2Decimal(n1, &epd1);\n    EpdPow2Decimal(n2, &epd2);\n    EpdMultiply3Decimal(&epd1, &epd2, epd);\n  }\n}\n\n\n/**\n  @brief Normalize an extended precision double value.\n*/\nvoid\nEpdNormalize(EpDouble *epd)\n{\n  int\t\texponent;\n\n  if (IsNanOrInfDouble(epd->type.value)) {\n    epd->exponent = 0;\n    return;\n  }\n\n  exponent = EpdGetExponent(epd->type.value);\n  if (exponent == EPD_MAX_BIN)\n    return;\n  exponent -= EPD_MAX_BIN;\n  epd->type.bits.exponent = EPD_MAX_BIN;\n  epd->exponent += exponent;\n}\n\n\n/**\n  @brief Normalize an extended precision double value.\n*/\nvoid\nEpdNormalizeDecimal(EpDouble *epd)\n{\n  int\t\texponent;\n\n  if (IsNanOrInfDouble(epd->type.value)) {\n    epd->exponent = 0;\n    return;\n  }\n\n  exponent = EpdGetExponentDecimal(epd->type.value);\n  epd->type.value /= pow((double)10.0, (double)exponent);\n  epd->exponent += exponent;\n}\n\n\n/**\n  @brief Returns value and decimal exponent of EpDouble.\n*/\nvoid\nEpdGetValueAndDecimalExponent(EpDouble const *epd, double *value, int *exponent)\n{\n  EpDouble\tepd1, epd2;\n\n  if (EpdIsNanOrInf(epd)) {\n    *exponent = EPD_EXP_INF;\n    *value = 0.0;\n    return;\n  }\n\n  if (EpdIsZero(epd)) {\n    *value = 0.0;\n    *exponent = 0;\n    return;\n  }\n\n  epd1.type.value = epd->type.value;\n  epd1.exponent = 0;\n  EpdPow2Decimal(epd->exponent, &epd2);\n  EpdMultiply2Decimal(&epd1, &epd2);\n\n  *value = epd1.type.value;\n  *exponent = epd1.exponent;\n}\n\n/**\n  @brief Returns the exponent value of a double.\n*/\nint\nEpdGetExponent(double value)\n{\n  int\t\texponent;\n  EpDouble\tepd;\n\n  epd.type.value = value;\n  exponent = epd.type.bits.exponent;\n  return(exponent);\n}\n\n\n/**\n  @brief Returns the decimal exponent value of a double.\n*/\nint\nEpdGetExponentDecimal(double value)\n{\n  char\t*pos, str[24];\n  int\texponent;\n\n  sprintf(str, \"%E\", value);\n  pos = strstr(str, \"E\");\n  sscanf(pos, \"E%d\", &exponent);\n  return(exponent);\n}\n\n\n/**\n  @brief Makes EpDouble Inf.\n*/\nvoid\nEpdMakeInf(EpDouble *epd, int sign)\n{\n  epd->type.bits.mantissa1 = 0;\n  epd->type.bits.mantissa0 = 0;\n  epd->type.bits.exponent = EPD_EXP_INF;\n  epd->type.bits.sign = sign;\n  epd->exponent = 0;\n}\n\n\n/**\n  @brief Makes EpDouble Zero.\n*/\nvoid\nEpdMakeZero(EpDouble *epd, int sign)\n{\n  epd->type.bits.mantissa1 = 0;\n  epd->type.bits.mantissa0 = 0;\n  epd->type.bits.exponent = 0;\n  epd->type.bits.sign = sign;\n  epd->exponent = 0;\n}\n\n\n/**\n  @brief Makes EpDouble NaN.\n*/\nvoid\nEpdMakeNan(EpDouble *epd)\n{\n  epd->type.nan.mantissa1 = 0;\n  epd->type.nan.mantissa0 = 0;\n  epd->type.nan.quiet_bit = 1;\n  epd->type.nan.exponent = EPD_EXP_INF;\n  epd->type.nan.sign = 1;\n  epd->exponent = 0;\n}\n\n\n/**\n  @brief Copies an EpDouble struct.\n*/\nvoid\nEpdCopy(EpDouble const *from, EpDouble *to)\n{\n  to->type.value = from->type.value;\n  to->exponent = from->exponent;\n}\n\n\n/**\n  @brief Checks whether the value is Inf.\n*/\nint\nEpdIsInf(EpDouble const *epd)\n{\n  return(IsInfDouble(epd->type.value));\n}\n\n\n/**\n  @brief Checks whether the value is Zero.\n*/\nint\nEpdIsZero(EpDouble const *epd)\n{\n  if (epd->type.value == 0.0)\n    return(1);\n  else\n    return(0);\n}\n\n\n/**\n  @brief Checks whether the value is NaN.\n*/\nint\nEpdIsNan(EpDouble const *epd)\n{\n  return(IsNanDouble(epd->type.value));\n}\n\n\n/**\n  @brief Checks whether the value is NaN or Inf.\n*/\nint\nEpdIsNanOrInf(EpDouble const *epd)\n{\n  return(IsNanOrInfDouble(epd->type.value));\n}\n\n\n/**\n  @brief Checks whether the value is Inf.\n*/\nint\nIsInfDouble(double value)\n{\n  EpType val;\n\n  val.value = value;\n  if (val.bits.exponent == EPD_EXP_INF &&\n      val.bits.mantissa0 == 0 &&\n      val.bits.mantissa1 == 0) {\n    if (val.bits.sign == 0)\n      return(1);\n    else\n      return(-1);\n  }\n  return(0);\n}\n\n\n/**\n  @brief Checks whether the value is NaN.\n*/\nint\nIsNanDouble(double value)\n{\n  EpType\tval;\n  \n  val.value = value;\n  if (val.nan.exponent == EPD_EXP_INF &&\n      val.nan.sign == 1 &&\n      val.nan.quiet_bit == 1 &&\n      val.nan.mantissa0 == 0 &&\n      val.nan.mantissa1 == 0) {\n    return(1);\n  }\n  return(0);\n}\n\n\n/**\n  @brief Checks whether the value is NaN or Inf.\n*/\nint\nIsNanOrInfDouble(double value)\n{\n  EpType\tval;\n\n  val.value = value;\n  if (val.nan.exponent == EPD_EXP_INF &&\n      val.nan.mantissa0 == 0 &&\n      val.nan.mantissa1 == 0 &&\n      (val.nan.sign == 1 || val.nan.quiet_bit == 0)) {\n    return(1);\n  }\n  return(0);\n}\n"
  },
  {
    "path": "cudd/epd/epd.h",
    "content": "/**\n  @file \n\n  @ingroup epd\n\n  @brief The University of Colorado extended double precision package.\n\n  @details Arithmetic functions with extended double precision.  The floating\n  point numbers manipulated by this package use an int to hold the exponent.\n  The significand has the same precision as a standard double.\n\n  @author In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef EPD_H_\n#define EPD_H_\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n   @brief The type of extended precision floating-point numbers.\n*/\ntypedef struct EpDoubleStruct EpDouble;\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\nextern EpDouble *EpdAlloc(void);\nextern int EpdCmp(const void *key1, const void *key2);\nextern void EpdFree(EpDouble *epd);\nextern void EpdGetString(EpDouble const *epd, char *str);\nextern void EpdConvert(double value, EpDouble *epd);\nextern void EpdMultiply(EpDouble *epd1, double value);\nextern void EpdMultiply2(EpDouble *epd1, EpDouble const *epd2);\nextern void EpdMultiply2Decimal(EpDouble *epd1, EpDouble const *epd2);\nextern void EpdMultiply3(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3);\nextern void EpdMultiply3Decimal(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3);\nextern void EpdDivide(EpDouble *epd1, double value);\nextern void EpdDivide2(EpDouble *epd1, EpDouble const *epd2);\nextern void EpdDivide3(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3);\nextern void EpdAdd(EpDouble *epd1, double value);\nextern void EpdAdd2(EpDouble *epd1, EpDouble const *epd2);\nextern void EpdAdd3(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3);\nextern void EpdSubtract(EpDouble *epd1, double value);\nextern void EpdSubtract2(EpDouble *epd1, EpDouble const *epd2);\nextern void EpdSubtract3(EpDouble const *epd1, EpDouble const *epd2, EpDouble *epd3);\nextern void EpdPow2(int n, EpDouble *epd);\nextern void EpdPow2Decimal(int n, EpDouble *epd);\nextern void EpdNormalize(EpDouble *epd);\nextern void EpdNormalizeDecimal(EpDouble *epd);\nextern void EpdGetValueAndDecimalExponent(EpDouble const *epd, double *value, int *exponent);\nextern int EpdGetExponent(double value);\nextern int EpdGetExponentDecimal(double value);\nextern void EpdMakeInf(EpDouble *epd, int sign);\nextern void EpdMakeZero(EpDouble *epd, int sign);\nextern void EpdMakeNan(EpDouble *epd);\nextern void EpdCopy(EpDouble const *from, EpDouble *to);\nextern int EpdIsInf(EpDouble const *epd);\nextern int EpdIsZero(EpDouble const *epd);\nextern int EpdIsNan(EpDouble const *epd);\nextern int EpdIsNanOrInf(EpDouble const *epd);\nextern int IsInfDouble(double value);\nextern int IsNanDouble(double value);\nextern int IsNanOrInfDouble(double value);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* EPD_H_ */\n"
  },
  {
    "path": "cudd/epd/epdInt.h",
    "content": "/**\n  @file \n\n  @ingroup epd\n\n  @brief Internal header for the University of Colorado extended\n  double precision package.\n\n  @author In-Ho Moon\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef EPD_INT_H_\n#define EPD_INT_H_\n\n#include \"config.h\"\n#include \"epd.h\"\n\n#if WORDS_BIGENDIAN == 1\n#define EPD_BIG_ENDIAN\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define\tEPD_MAX_BIN\t1023\n#define\tEPD_MAX_DEC\t308\n#define\tEPD_EXP_INF\t0x7ff\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\ntypedef struct IeeeDoubleStruct IeeeDouble;\ntypedef struct IeeeNanStruct IeeeNan;\ntypedef union EpTypeUnion EpType;\n\n/*---------------------------------------------------------------------------*/\n/* Structure declarations                                                    */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief IEEE double struct.\n*/\n#ifdef\tEPD_BIG_ENDIAN\nstruct IeeeDoubleStruct {\t/* BIG_ENDIAN */\n  unsigned int sign: 1;\n  unsigned int exponent: 11;\n  unsigned int mantissa0: 20;\n  unsigned int mantissa1: 32;\n};\n#else\nstruct IeeeDoubleStruct {\t/* LITTLE_ENDIAN */\n  unsigned int mantissa1: 32;\n  unsigned int mantissa0: 20;\n  unsigned int exponent: 11;\n  unsigned int sign: 1;\n};\n#endif\n\n/**\n  @brief IEEE double NaN struct.\n*/\n#ifdef\tEPD_BIG_ENDIAN\nstruct IeeeNanStruct {\t/* BIG_ENDIAN */\n  unsigned int sign: 1;\n  unsigned int exponent: 11;\n  unsigned int quiet_bit: 1;\n  unsigned int mantissa0: 19;\n  unsigned int mantissa1: 32;\n};\n#else\nstruct IeeeNanStruct {\t/* LITTLE_ENDIAN */\n  unsigned int mantissa1: 32;\n  unsigned int mantissa0: 19;\n  unsigned int quiet_bit: 1;\n  unsigned int exponent: 11;\n  unsigned int sign: 1;\n};\n#endif\n\n/**\n  @brief Different views of a double.\n*/\nunion EpTypeUnion {\n  double\t\t\tvalue;\n  struct IeeeDoubleStruct\tbits;\n  struct IeeeNanStruct\t\tnan;\n};\n\n/**\n  @brief Extended precision double to keep very large value.\n*/\nstruct EpDoubleStruct {\n  union EpTypeUnion\t\ttype;\n  int\t\t\t\texponent;\n};\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* EPD_H_ */\n"
  },
  {
    "path": "cudd/groups.dox",
    "content": "/**\n * @mainpage CUDD Documentation\n *\n * @brief The CUDD package manipulates Binary Decision Diagrams (BDDs),\n * Algebraic Decision Diagrams (ADDs), and Zero-suppressed binary Decision\n * Diagrams (ZDDs).\n */\n\n/**\n * @defgroup cudd cudd\n * @brief The University of Colorado Decision Diagram package.\n *\n * @defgroup mtr mtr\n * @brief Multiway-branching Trees.\n *\n * @defgroup epd epd\n * @brief Extended double precision package.\n *\n * @defgroup st st\n * @brief Symbol Table package.\n *\n * @defgroup util util\n * @brief Low-level utilities.\n *\n * @defgroup cstringstream cstringstream\n * @brief (Simple) stringstreams in C.\n *\n * @defgroup cplusplus cplusplus\n * @brief C++ CUDD wrapper.\n *\n * @defgroup nanotrav nanotrav\n * @brief CUDD test application.\n */\n"
  },
  {
    "path": "cudd/install.sh",
    "content": "#!/bin/sh\n\n# PRISM-customised install script for CUDD\n# Needs to be run from the containing directory\n\n# Only re-run configure if Makefile doesn't already exist\n\nif [ ! -f Makefile ]; then\n\n  # Hacking of time-stamps (lost in git) to avoid autoconf issues\n  sleep 1; touch aclocal.m4\n  sleep 1; touch configure; touch config.h.in; touch `find . -name Makefile.in -print`\n  \n  # Collate arguments to be passed to configure\n  CONFIGURE_ARGS=\"\"\n  if [ ! -z \"$MAKE\" ]; then\n    CONFIGURE_ARGS=${CONFIGURE_ARGS}${CONFIGURE_ARGS:+ }MAKE=\"$MAKE\"\n  fi\n  if [ ! -z \"$CC\" ]; then\n    CONFIGURE_ARGS=${CONFIGURE_ARGS}${CONFIGURE_ARGS:+ }CC=\"$CC\"\n  fi\n  if [ ! -z \"$CXX\" ]; then\n    CONFIGURE_ARGS=${CONFIGURE_ARGS}${CONFIGURE_ARGS:+ }CXX=\"$CXX\"\n  fi\n  if [ ! -z \"$LD\" ]; then\n    CONFIGURE_ARGS=${CONFIGURE_ARGS}${CONFIGURE_ARGS:+ }LD=\"$LD\"\n  fi\n  \n  # Build Makefile\n  ./configure --prefix=\"$(pwd)\" $CONFIGURE_ARGS CFLAGS=\"$CFLAGS\" CXXFLAGS=\"$CXXFLAGS\" LDFLAGS=\"$LDFLAGS\" || exit 1\n  \nfi\n\n# Build, install (locally)\n\nmake || exit 1\nmake install || exit 1\n\n# Install links to headers not installed by make install\n\nmkdir -p include # should already exist though\nfor HEADER in cudd/cuddInt.h config.h st/st.h mtr/mtr.h epd/epd.h util/util.h\n#for HEADER in $(find . -name \"*.h\")\ndo\n  if [ ! -L include/`basename $HEADER` ]; then\n\tln -s ../$HEADER include\n  fi\ndone\n"
  },
  {
    "path": "cudd/m4/libtool.m4",
    "content": "# libtool.m4 - Configure libtool for the host system. -*-Autoconf-*-\n#\n#   Copyright (C) 1996-2001, 2003-2019, 2021-2022 Free Software\n#   Foundation, Inc.\n#   Written by Gordon Matzigkeit, 1996\n#\n# This file is free software; the Free Software Foundation gives\n# unlimited permission to copy and/or distribute it, with or without\n# modifications, as long as this notice is preserved.\n\nm4_define([_LT_COPYING], [dnl\n# Copyright (C) 2014 Free Software Foundation, Inc.\n# This is free software; see the source for copying conditions.  There is NO\n# warranty; not even for MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\n\n# GNU Libtool is free software; you can redistribute it and/or modify\n# it under the terms of the GNU General Public License as published by\n# the Free Software Foundation; either version 2 of of the License, or\n# (at your option) any later version.\n#\n# As a special exception to the GNU General Public License, if you\n# distribute this file as part of a program or library that is built\n# using GNU Libtool, you may include this file under the  same\n# distribution terms that you use for the rest of that program.\n#\n# GNU Libtool is distributed in the hope that it will be useful, but\n# WITHOUT ANY WARRANTY; without even the implied warranty of\n# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n# GNU General Public License for more details.\n#\n# You should have received a copy of the GNU General Public License\n# along with this program.  If not, see <http://www.gnu.org/licenses/>.\n])\n\n# serial 59 LT_INIT\n\n\n# LT_PREREQ(VERSION)\n# ------------------\n# Complain and exit if this libtool version is less that VERSION.\nm4_defun([LT_PREREQ],\n[m4_if(m4_version_compare(m4_defn([LT_PACKAGE_VERSION]), [$1]), -1,\n       [m4_default([$3],\n\t\t   [m4_fatal([Libtool version $1 or higher is required],\n\t\t             63)])],\n       [$2])])\n\n\n# _LT_CHECK_BUILDDIR\n# ------------------\n# Complain if the absolute build directory name contains unusual characters\nm4_defun([_LT_CHECK_BUILDDIR],\n[case `pwd` in\n  *\\ * | *\\\t*)\n    AC_MSG_WARN([Libtool does not cope well with whitespace in `pwd`]) ;;\nesac\n])\n\n\n# LT_INIT([OPTIONS])\n# ------------------\nAC_DEFUN([LT_INIT],\n[AC_PREREQ([2.62])dnl We use AC_PATH_PROGS_FEATURE_CHECK\nAC_REQUIRE([AC_CONFIG_AUX_DIR_DEFAULT])dnl\nAC_BEFORE([$0], [LT_LANG])dnl\nAC_BEFORE([$0], [LT_OUTPUT])dnl\nAC_BEFORE([$0], [LTDL_INIT])dnl\nm4_require([_LT_CHECK_BUILDDIR])dnl\n\ndnl Autoconf doesn't catch unexpanded LT_ macros by default:\nm4_pattern_forbid([^_?LT_[A-Z_]+$])dnl\nm4_pattern_allow([^(_LT_EOF|LT_DLGLOBAL|LT_DLLAZY_OR_NOW|LT_MULTI_MODULE)$])dnl\ndnl aclocal doesn't pull ltoptions.m4, ltsugar.m4, or ltversion.m4\ndnl unless we require an AC_DEFUNed macro:\nAC_REQUIRE([LTOPTIONS_VERSION])dnl\nAC_REQUIRE([LTSUGAR_VERSION])dnl\nAC_REQUIRE([LTVERSION_VERSION])dnl\nAC_REQUIRE([LTOBSOLETE_VERSION])dnl\nm4_require([_LT_PROG_LTMAIN])dnl\n\n_LT_SHELL_INIT([SHELL=${CONFIG_SHELL-/bin/sh}])\n\ndnl Parse OPTIONS\n_LT_SET_OPTIONS([$0], [$1])\n\n# This can be used to rebuild libtool when needed\nLIBTOOL_DEPS=$ltmain\n\n# Always use our own libtool.\nLIBTOOL='$(SHELL) $(top_builddir)/libtool'\nAC_SUBST(LIBTOOL)dnl\n\n_LT_SETUP\n\n# Only expand once:\nm4_define([LT_INIT])\n])# LT_INIT\n\n# Old names:\nAU_ALIAS([AC_PROG_LIBTOOL], [LT_INIT])\nAU_ALIAS([AM_PROG_LIBTOOL], [LT_INIT])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_PROG_LIBTOOL], [])\ndnl AC_DEFUN([AM_PROG_LIBTOOL], [])\n\n\n# _LT_PREPARE_CC_BASENAME\n# -----------------------\nm4_defun([_LT_PREPARE_CC_BASENAME], [\n# Calculate cc_basename.  Skip known compiler wrappers and cross-prefix.\nfunc_cc_basename ()\n{\n    for cc_temp in @S|@*\"\"; do\n      case $cc_temp in\n        compile | *[[\\\\/]]compile | ccache | *[[\\\\/]]ccache ) ;;\n        distcc | *[[\\\\/]]distcc | purify | *[[\\\\/]]purify ) ;;\n        \\-*) ;;\n        *) break;;\n      esac\n    done\n    func_cc_basename_result=`$ECHO \"$cc_temp\" | $SED \"s%.*/%%; s%^$host_alias-%%\"`\n}\n])# _LT_PREPARE_CC_BASENAME\n\n\n# _LT_CC_BASENAME(CC)\n# -------------------\n# It would be clearer to call AC_REQUIREs from _LT_PREPARE_CC_BASENAME,\n# but that macro is also expanded into generated libtool script, which\n# arranges for $SED and $ECHO to be set by different means.\nm4_defun([_LT_CC_BASENAME],\n[m4_require([_LT_PREPARE_CC_BASENAME])dnl\nAC_REQUIRE([_LT_DECL_SED])dnl\nAC_REQUIRE([_LT_PROG_ECHO_BACKSLASH])dnl\nfunc_cc_basename $1\ncc_basename=$func_cc_basename_result\n])\n\n\n# _LT_FILEUTILS_DEFAULTS\n# ----------------------\n# It is okay to use these file commands and assume they have been set\n# sensibly after 'm4_require([_LT_FILEUTILS_DEFAULTS])'.\nm4_defun([_LT_FILEUTILS_DEFAULTS],\n[: ${CP=\"cp -f\"}\n: ${MV=\"mv -f\"}\n: ${RM=\"rm -f\"}\n])# _LT_FILEUTILS_DEFAULTS\n\n\n# _LT_SETUP\n# ---------\nm4_defun([_LT_SETUP],\n[AC_REQUIRE([AC_CANONICAL_HOST])dnl\nAC_REQUIRE([AC_CANONICAL_BUILD])dnl\nAC_REQUIRE([_LT_PREPARE_SED_QUOTE_VARS])dnl\nAC_REQUIRE([_LT_PROG_ECHO_BACKSLASH])dnl\n\n_LT_DECL([], [PATH_SEPARATOR], [1], [The PATH separator for the build system])dnl\ndnl\n_LT_DECL([], [host_alias], [0], [The host system])dnl\n_LT_DECL([], [host], [0])dnl\n_LT_DECL([], [host_os], [0])dnl\ndnl\n_LT_DECL([], [build_alias], [0], [The build system])dnl\n_LT_DECL([], [build], [0])dnl\n_LT_DECL([], [build_os], [0])dnl\ndnl\nAC_REQUIRE([AC_PROG_CC])dnl\nAC_REQUIRE([LT_PATH_LD])dnl\nAC_REQUIRE([LT_PATH_NM])dnl\ndnl\nAC_REQUIRE([AC_PROG_LN_S])dnl\ntest -z \"$LN_S\" && LN_S=\"ln -s\"\n_LT_DECL([], [LN_S], [1], [Whether we need soft or hard links])dnl\ndnl\nAC_REQUIRE([LT_CMD_MAX_LEN])dnl\n_LT_DECL([objext], [ac_objext], [0], [Object file suffix (normally \"o\")])dnl\n_LT_DECL([], [exeext], [0], [Executable file suffix (normally \"\")])dnl\ndnl\nm4_require([_LT_FILEUTILS_DEFAULTS])dnl\nm4_require([_LT_CHECK_SHELL_FEATURES])dnl\nm4_require([_LT_PATH_CONVERSION_FUNCTIONS])dnl\nm4_require([_LT_CMD_RELOAD])dnl\nm4_require([_LT_DECL_FILECMD])dnl\nm4_require([_LT_CHECK_MAGIC_METHOD])dnl\nm4_require([_LT_CHECK_SHAREDLIB_FROM_LINKLIB])dnl\nm4_require([_LT_CMD_OLD_ARCHIVE])dnl\nm4_require([_LT_CMD_GLOBAL_SYMBOLS])dnl\nm4_require([_LT_WITH_SYSROOT])dnl\nm4_require([_LT_CMD_TRUNCATE])dnl\n\n_LT_CONFIG_LIBTOOL_INIT([\n# See if we are running on zsh, and set the options that allow our\n# commands through without removal of \\ escapes INIT.\nif test -n \"\\${ZSH_VERSION+set}\"; then\n   setopt NO_GLOB_SUBST\nfi\n])\nif test -n \"${ZSH_VERSION+set}\"; then\n   setopt NO_GLOB_SUBST\nfi\n\n_LT_CHECK_OBJDIR\n\nm4_require([_LT_TAG_COMPILER])dnl\n\ncase $host_os in\naix3*)\n  # AIX sometimes has problems with the GCC collect2 program.  For some\n  # reason, if we set the COLLECT_NAMES environment variable, the problems\n  # vanish in a puff of smoke.\n  if test set != \"${COLLECT_NAMES+set}\"; then\n    COLLECT_NAMES=\n    export COLLECT_NAMES\n  fi\n  ;;\nesac\n\n# Global variables:\nofile=libtool\ncan_build_shared=yes\n\n# All known linkers require a '.a' archive for static linking (except MSVC and\n# ICC, which need '.lib').\nlibext=a\n\nwith_gnu_ld=$lt_cv_prog_gnu_ld\n\nold_CC=$CC\nold_CFLAGS=$CFLAGS\n\n# Set sane defaults for various variables\ntest -z \"$CC\" && CC=cc\ntest -z \"$LTCC\" && LTCC=$CC\ntest -z \"$LTCFLAGS\" && LTCFLAGS=$CFLAGS\ntest -z \"$LD\" && LD=ld\ntest -z \"$ac_objext\" && ac_objext=o\n\n_LT_CC_BASENAME([$compiler])\n\n# Only perform the check for file, if the check method requires it\ntest -z \"$MAGIC_CMD\" && MAGIC_CMD=file\ncase $deplibs_check_method in\nfile_magic*)\n  if test \"$file_magic_cmd\" = '$MAGIC_CMD'; then\n    _LT_PATH_MAGIC\n  fi\n  ;;\nesac\n\n# Use C for the default configuration in the libtool script\nLT_SUPPORTED_TAG([CC])\n_LT_LANG_C_CONFIG\n_LT_LANG_DEFAULT_CONFIG\n_LT_CONFIG_COMMANDS\n])# _LT_SETUP\n\n\n# _LT_PREPARE_SED_QUOTE_VARS\n# --------------------------\n# Define a few sed substitution that help us do robust quoting.\nm4_defun([_LT_PREPARE_SED_QUOTE_VARS],\n[# Backslashify metacharacters that are still active within\n# double-quoted strings.\nsed_quote_subst='s/\\([[\"`$\\\\]]\\)/\\\\\\1/g'\n\n# Same as above, but do not quote variable references.\ndouble_quote_subst='s/\\([[\"`\\\\]]\\)/\\\\\\1/g'\n\n# Sed substitution to delay expansion of an escaped shell variable in a\n# double_quote_subst'ed string.\ndelay_variable_subst='s/\\\\\\\\\\\\\\\\\\\\\\$/\\\\\\\\\\\\$/g'\n\n# Sed substitution to delay expansion of an escaped single quote.\ndelay_single_quote_subst='s/'\\''/'\\'\\\\\\\\\\\\\\'\\''/g'\n\n# Sed substitution to avoid accidental globbing in evaled expressions\nno_glob_subst='s/\\*/\\\\\\*/g'\n])\n\n# _LT_PROG_LTMAIN\n# ---------------\n# Note that this code is called both from 'configure', and 'config.status'\n# now that we use AC_CONFIG_COMMANDS to generate libtool.  Notably,\n# 'config.status' has no value for ac_aux_dir unless we are using Automake,\n# so we pass a copy along to make sure it has a sensible value anyway.\nm4_defun([_LT_PROG_LTMAIN],\n[m4_ifdef([AC_REQUIRE_AUX_FILE], [AC_REQUIRE_AUX_FILE([ltmain.sh])])dnl\n_LT_CONFIG_LIBTOOL_INIT([ac_aux_dir='$ac_aux_dir'])\nltmain=$ac_aux_dir/ltmain.sh\n])# _LT_PROG_LTMAIN\n\n\n## ------------------------------------- ##\n## Accumulate code for creating libtool. ##\n## ------------------------------------- ##\n\n# So that we can recreate a full libtool script including additional\n# tags, we accumulate the chunks of code to send to AC_CONFIG_COMMANDS\n# in macros and then make a single call at the end using the 'libtool'\n# label.\n\n\n# _LT_CONFIG_LIBTOOL_INIT([INIT-COMMANDS])\n# ----------------------------------------\n# Register INIT-COMMANDS to be passed to AC_CONFIG_COMMANDS later.\nm4_define([_LT_CONFIG_LIBTOOL_INIT],\n[m4_ifval([$1],\n          [m4_append([_LT_OUTPUT_LIBTOOL_INIT],\n                     [$1\n])])])\n\n# Initialize.\nm4_define([_LT_OUTPUT_LIBTOOL_INIT])\n\n\n# _LT_CONFIG_LIBTOOL([COMMANDS])\n# ------------------------------\n# Register COMMANDS to be passed to AC_CONFIG_COMMANDS later.\nm4_define([_LT_CONFIG_LIBTOOL],\n[m4_ifval([$1],\n          [m4_append([_LT_OUTPUT_LIBTOOL_COMMANDS],\n                     [$1\n])])])\n\n# Initialize.\nm4_define([_LT_OUTPUT_LIBTOOL_COMMANDS])\n\n\n# _LT_CONFIG_SAVE_COMMANDS([COMMANDS], [INIT_COMMANDS])\n# -----------------------------------------------------\nm4_defun([_LT_CONFIG_SAVE_COMMANDS],\n[_LT_CONFIG_LIBTOOL([$1])\n_LT_CONFIG_LIBTOOL_INIT([$2])\n])\n\n\n# _LT_FORMAT_COMMENT([COMMENT])\n# -----------------------------\n# Add leading comment marks to the start of each line, and a trailing\n# full-stop to the whole comment if one is not present already.\nm4_define([_LT_FORMAT_COMMENT],\n[m4_ifval([$1], [\nm4_bpatsubst([m4_bpatsubst([$1], [^ *], [# ])],\n              [['`$\\]], [\\\\\\&])]m4_bmatch([$1], [[!?.]$], [], [.])\n)])\n\n\n\n## ------------------------ ##\n## FIXME: Eliminate VARNAME ##\n## ------------------------ ##\n\n\n# _LT_DECL([CONFIGNAME], VARNAME, VALUE, [DESCRIPTION], [IS-TAGGED?])\n# -------------------------------------------------------------------\n# CONFIGNAME is the name given to the value in the libtool script.\n# VARNAME is the (base) name used in the configure script.\n# VALUE may be 0, 1 or 2 for a computed quote escaped value based on\n# VARNAME.  Any other value will be used directly.\nm4_define([_LT_DECL],\n[lt_if_append_uniq([lt_decl_varnames], [$2], [, ],\n    [lt_dict_add_subkey([lt_decl_dict], [$2], [libtool_name],\n\t[m4_ifval([$1], [$1], [$2])])\n    lt_dict_add_subkey([lt_decl_dict], [$2], [value], [$3])\n    m4_ifval([$4],\n\t[lt_dict_add_subkey([lt_decl_dict], [$2], [description], [$4])])\n    lt_dict_add_subkey([lt_decl_dict], [$2],\n\t[tagged?], [m4_ifval([$5], [yes], [no])])])\n])\n\n\n# _LT_TAGDECL([CONFIGNAME], VARNAME, VALUE, [DESCRIPTION])\n# --------------------------------------------------------\nm4_define([_LT_TAGDECL], [_LT_DECL([$1], [$2], [$3], [$4], [yes])])\n\n\n# lt_decl_tag_varnames([SEPARATOR], [VARNAME1...])\n# ------------------------------------------------\nm4_define([lt_decl_tag_varnames],\n[_lt_decl_filter([tagged?], [yes], $@)])\n\n\n# _lt_decl_filter(SUBKEY, VALUE, [SEPARATOR], [VARNAME1..])\n# ---------------------------------------------------------\nm4_define([_lt_decl_filter],\n[m4_case([$#],\n  [0], [m4_fatal([$0: too few arguments: $#])],\n  [1], [m4_fatal([$0: too few arguments: $#: $1])],\n  [2], [lt_dict_filter([lt_decl_dict], [$1], [$2], [], lt_decl_varnames)],\n  [3], [lt_dict_filter([lt_decl_dict], [$1], [$2], [$3], lt_decl_varnames)],\n  [lt_dict_filter([lt_decl_dict], $@)])[]dnl\n])\n\n\n# lt_decl_quote_varnames([SEPARATOR], [VARNAME1...])\n# --------------------------------------------------\nm4_define([lt_decl_quote_varnames],\n[_lt_decl_filter([value], [1], $@)])\n\n\n# lt_decl_dquote_varnames([SEPARATOR], [VARNAME1...])\n# ---------------------------------------------------\nm4_define([lt_decl_dquote_varnames],\n[_lt_decl_filter([value], [2], $@)])\n\n\n# lt_decl_varnames_tagged([SEPARATOR], [VARNAME1...])\n# ---------------------------------------------------\nm4_define([lt_decl_varnames_tagged],\n[m4_assert([$# <= 2])dnl\n_$0(m4_quote(m4_default([$1], [[, ]])),\n    m4_ifval([$2], [[$2]], [m4_dquote(lt_decl_tag_varnames)]),\n    m4_split(m4_normalize(m4_quote(_LT_TAGS)), [ ]))])\nm4_define([_lt_decl_varnames_tagged],\n[m4_ifval([$3], [lt_combine([$1], [$2], [_], $3)])])\n\n\n# lt_decl_all_varnames([SEPARATOR], [VARNAME1...])\n# ------------------------------------------------\nm4_define([lt_decl_all_varnames],\n[_$0(m4_quote(m4_default([$1], [[, ]])),\n     m4_if([$2], [],\n\t   m4_quote(lt_decl_varnames),\n\tm4_quote(m4_shift($@))))[]dnl\n])\nm4_define([_lt_decl_all_varnames],\n[lt_join($@, lt_decl_varnames_tagged([$1],\n\t\t\tlt_decl_tag_varnames([[, ]], m4_shift($@))))dnl\n])\n\n\n# _LT_CONFIG_STATUS_DECLARE([VARNAME])\n# ------------------------------------\n# Quote a variable value, and forward it to 'config.status' so that its\n# declaration there will have the same value as in 'configure'.  VARNAME\n# must have a single quote delimited value for this to work.\nm4_define([_LT_CONFIG_STATUS_DECLARE],\n[$1='`$ECHO \"$][$1\" | $SED \"$delay_single_quote_subst\"`'])\n\n\n# _LT_CONFIG_STATUS_DECLARATIONS\n# ------------------------------\n# We delimit libtool config variables with single quotes, so when\n# we write them to config.status, we have to be sure to quote all\n# embedded single quotes properly.  In configure, this macro expands\n# each variable declared with _LT_DECL (and _LT_TAGDECL) into:\n#\n#    <var>='`$ECHO \"$<var>\" | $SED \"$delay_single_quote_subst\"`'\nm4_defun([_LT_CONFIG_STATUS_DECLARATIONS],\n[m4_foreach([_lt_var], m4_quote(lt_decl_all_varnames),\n    [m4_n([_LT_CONFIG_STATUS_DECLARE(_lt_var)])])])\n\n\n# _LT_LIBTOOL_TAGS\n# ----------------\n# Output comment and list of tags supported by the script\nm4_defun([_LT_LIBTOOL_TAGS],\n[_LT_FORMAT_COMMENT([The names of the tagged configurations supported by this script])dnl\navailable_tags='_LT_TAGS'dnl\n])\n\n\n# _LT_LIBTOOL_DECLARE(VARNAME, [TAG])\n# -----------------------------------\n# Extract the dictionary values for VARNAME (optionally with TAG) and\n# expand to a commented shell variable setting:\n#\n#    # Some comment about what VAR is for.\n#    visible_name=$lt_internal_name\nm4_define([_LT_LIBTOOL_DECLARE],\n[_LT_FORMAT_COMMENT(m4_quote(lt_dict_fetch([lt_decl_dict], [$1],\n\t\t\t\t\t   [description])))[]dnl\nm4_pushdef([_libtool_name],\n    m4_quote(lt_dict_fetch([lt_decl_dict], [$1], [libtool_name])))[]dnl\nm4_case(m4_quote(lt_dict_fetch([lt_decl_dict], [$1], [value])),\n    [0], [_libtool_name=[$]$1],\n    [1], [_libtool_name=$lt_[]$1],\n    [2], [_libtool_name=$lt_[]$1],\n    [_libtool_name=lt_dict_fetch([lt_decl_dict], [$1], [value])])[]dnl\nm4_ifval([$2], [_$2])[]m4_popdef([_libtool_name])[]dnl\n])\n\n\n# _LT_LIBTOOL_CONFIG_VARS\n# -----------------------\n# Produce commented declarations of non-tagged libtool config variables\n# suitable for insertion in the LIBTOOL CONFIG section of the 'libtool'\n# script.  Tagged libtool config variables (even for the LIBTOOL CONFIG\n# section) are produced by _LT_LIBTOOL_TAG_VARS.\nm4_defun([_LT_LIBTOOL_CONFIG_VARS],\n[m4_foreach([_lt_var],\n    m4_quote(_lt_decl_filter([tagged?], [no], [], lt_decl_varnames)),\n    [m4_n([_LT_LIBTOOL_DECLARE(_lt_var)])])])\n\n\n# _LT_LIBTOOL_TAG_VARS(TAG)\n# -------------------------\nm4_define([_LT_LIBTOOL_TAG_VARS],\n[m4_foreach([_lt_var], m4_quote(lt_decl_tag_varnames),\n    [m4_n([_LT_LIBTOOL_DECLARE(_lt_var, [$1])])])])\n\n\n# _LT_TAGVAR(VARNAME, [TAGNAME])\n# ------------------------------\nm4_define([_LT_TAGVAR], [m4_ifval([$2], [$1_$2], [$1])])\n\n\n# _LT_CONFIG_COMMANDS\n# -------------------\n# Send accumulated output to $CONFIG_STATUS.  Thanks to the lists of\n# variables for single and double quote escaping we saved from calls\n# to _LT_DECL, we can put quote escaped variables declarations\n# into 'config.status', and then the shell code to quote escape them in\n# for loops in 'config.status'.  Finally, any additional code accumulated\n# from calls to _LT_CONFIG_LIBTOOL_INIT is expanded.\nm4_defun([_LT_CONFIG_COMMANDS],\n[AC_PROVIDE_IFELSE([LT_OUTPUT],\n\tdnl If the libtool generation code has been placed in $CONFIG_LT,\n\tdnl instead of duplicating it all over again into config.status,\n\tdnl then we will have config.status run $CONFIG_LT later, so it\n\tdnl needs to know what name is stored there:\n        [AC_CONFIG_COMMANDS([libtool],\n            [$SHELL $CONFIG_LT || AS_EXIT(1)], [CONFIG_LT='$CONFIG_LT'])],\n    dnl If the libtool generation code is destined for config.status,\n    dnl expand the accumulated commands and init code now:\n    [AC_CONFIG_COMMANDS([libtool],\n        [_LT_OUTPUT_LIBTOOL_COMMANDS], [_LT_OUTPUT_LIBTOOL_COMMANDS_INIT])])\n])#_LT_CONFIG_COMMANDS\n\n\n# Initialize.\nm4_define([_LT_OUTPUT_LIBTOOL_COMMANDS_INIT],\n[\n\n# The HP-UX ksh and POSIX shell print the target directory to stdout\n# if CDPATH is set.\n(unset CDPATH) >/dev/null 2>&1 && unset CDPATH\n\nsed_quote_subst='$sed_quote_subst'\ndouble_quote_subst='$double_quote_subst'\ndelay_variable_subst='$delay_variable_subst'\n_LT_CONFIG_STATUS_DECLARATIONS\nLTCC='$LTCC'\nLTCFLAGS='$LTCFLAGS'\ncompiler='$compiler_DEFAULT'\n\n# A function that is used when there is no print builtin or printf.\nfunc_fallback_echo ()\n{\n  eval 'cat <<_LTECHO_EOF\n\\$[]1\n_LTECHO_EOF'\n}\n\n# Quote evaled strings.\nfor var in lt_decl_all_varnames([[ \\\n]], lt_decl_quote_varnames); do\n    case \\`eval \\\\\\\\\\$ECHO \\\\\\\\\"\"\\\\\\\\\\$\\$var\"\\\\\\\\\"\\` in\n    *[[\\\\\\\\\\\\\\`\\\\\"\\\\\\$]]*)\n      eval \"lt_\\$var=\\\\\\\\\\\\\"\\\\\\`\\\\\\$ECHO \\\\\"\\\\\\$\\$var\\\\\" | \\\\\\$SED \\\\\"\\\\\\$sed_quote_subst\\\\\"\\\\\\`\\\\\\\\\\\\\"\" ## exclude from sc_prohibit_nested_quotes\n      ;;\n    *)\n      eval \"lt_\\$var=\\\\\\\\\\\\\"\\\\\\$\\$var\\\\\\\\\\\\\"\"\n      ;;\n    esac\ndone\n\n# Double-quote double-evaled strings.\nfor var in lt_decl_all_varnames([[ \\\n]], lt_decl_dquote_varnames); do\n    case \\`eval \\\\\\\\\\$ECHO \\\\\\\\\"\"\\\\\\\\\\$\\$var\"\\\\\\\\\"\\` in\n    *[[\\\\\\\\\\\\\\`\\\\\"\\\\\\$]]*)\n      eval \"lt_\\$var=\\\\\\\\\\\\\"\\\\\\`\\\\\\$ECHO \\\\\"\\\\\\$\\$var\\\\\" | \\\\\\$SED -e \\\\\"\\\\\\$double_quote_subst\\\\\" -e \\\\\"\\\\\\$sed_quote_subst\\\\\" -e \\\\\"\\\\\\$delay_variable_subst\\\\\"\\\\\\`\\\\\\\\\\\\\"\" ## exclude from sc_prohibit_nested_quotes\n      ;;\n    *)\n      eval \"lt_\\$var=\\\\\\\\\\\\\"\\\\\\$\\$var\\\\\\\\\\\\\"\"\n      ;;\n    esac\ndone\n\n_LT_OUTPUT_LIBTOOL_INIT\n])\n\n# _LT_GENERATED_FILE_INIT(FILE, [COMMENT])\n# ------------------------------------\n# Generate a child script FILE with all initialization necessary to\n# reuse the environment learned by the parent script, and make the\n# file executable.  If COMMENT is supplied, it is inserted after the\n# '#!' sequence but before initialization text begins.  After this\n# macro, additional text can be appended to FILE to form the body of\n# the child script.  The macro ends with non-zero status if the\n# file could not be fully written (such as if the disk is full).\nm4_ifdef([AS_INIT_GENERATED],\n[m4_defun([_LT_GENERATED_FILE_INIT],[AS_INIT_GENERATED($@)])],\n[m4_defun([_LT_GENERATED_FILE_INIT],\n[m4_require([AS_PREPARE])]dnl\n[m4_pushdef([AS_MESSAGE_LOG_FD])]dnl\n[lt_write_fail=0\ncat >$1 <<_ASEOF || lt_write_fail=1\n#! $SHELL\n# Generated by $as_me.\n$2\nSHELL=\\${CONFIG_SHELL-$SHELL}\nexport SHELL\n_ASEOF\ncat >>$1 <<\\_ASEOF || lt_write_fail=1\nAS_SHELL_SANITIZE\n_AS_PREPARE\nexec AS_MESSAGE_FD>&1\n_ASEOF\ntest 0 = \"$lt_write_fail\" && chmod +x $1[]dnl\nm4_popdef([AS_MESSAGE_LOG_FD])])])# _LT_GENERATED_FILE_INIT\n\n# LT_OUTPUT\n# ---------\n# This macro allows early generation of the libtool script (before\n# AC_OUTPUT is called), incase it is used in configure for compilation\n# tests.\nAC_DEFUN([LT_OUTPUT],\n[: ${CONFIG_LT=./config.lt}\nAC_MSG_NOTICE([creating $CONFIG_LT])\n_LT_GENERATED_FILE_INIT([\"$CONFIG_LT\"],\n[# Run this file to recreate a libtool stub with the current configuration.])\n\ncat >>\"$CONFIG_LT\" <<\\_LTEOF\nlt_cl_silent=false\nexec AS_MESSAGE_LOG_FD>>config.log\n{\n  echo\n  AS_BOX([Running $as_me.])\n} >&AS_MESSAGE_LOG_FD\n\nlt_cl_help=\"\\\n'$as_me' creates a local libtool stub from the current configuration,\nfor use in further configure time tests before the real libtool is\ngenerated.\n\nUsage: $[0] [[OPTIONS]]\n\n  -h, --help      print this help, then exit\n  -V, --version   print version number, then exit\n  -q, --quiet     do not print progress messages\n  -d, --debug     don't remove temporary files\n\nReport bugs to <bug-libtool@gnu.org>.\"\n\nlt_cl_version=\"\\\nm4_ifset([AC_PACKAGE_NAME], [AC_PACKAGE_NAME ])config.lt[]dnl\nm4_ifset([AC_PACKAGE_VERSION], [ AC_PACKAGE_VERSION])\nconfigured by $[0], generated by m4_PACKAGE_STRING.\n\nCopyright (C) 2011 Free Software Foundation, Inc.\nThis config.lt script is free software; the Free Software Foundation\ngives unlimited permision to copy, distribute and modify it.\"\n\nwhile test 0 != $[#]\ndo\n  case $[1] in\n    --version | --v* | -V )\n      echo \"$lt_cl_version\"; exit 0 ;;\n    --help | --h* | -h )\n      echo \"$lt_cl_help\"; exit 0 ;;\n    --debug | --d* | -d )\n      debug=: ;;\n    --quiet | --q* | --silent | --s* | -q )\n      lt_cl_silent=: ;;\n\n    -*) AC_MSG_ERROR([unrecognized option: $[1]\nTry '$[0] --help' for more information.]) ;;\n\n    *) AC_MSG_ERROR([unrecognized argument: $[1]\nTry '$[0] --help' for more information.]) ;;\n  esac\n  shift\ndone\n\nif $lt_cl_silent; then\n  exec AS_MESSAGE_FD>/dev/null\nfi\n_LTEOF\n\ncat >>\"$CONFIG_LT\" <<_LTEOF\n_LT_OUTPUT_LIBTOOL_COMMANDS_INIT\n_LTEOF\n\ncat >>\"$CONFIG_LT\" <<\\_LTEOF\nAC_MSG_NOTICE([creating $ofile])\n_LT_OUTPUT_LIBTOOL_COMMANDS\nAS_EXIT(0)\n_LTEOF\nchmod +x \"$CONFIG_LT\"\n\n# configure is writing to config.log, but config.lt does its own redirection,\n# appending to config.log, which fails on DOS, as config.log is still kept\n# open by configure.  Here we exec the FD to /dev/null, effectively closing\n# config.log, so it can be properly (re)opened and appended to by config.lt.\nlt_cl_success=:\ntest yes = \"$silent\" &&\n  lt_config_lt_args=\"$lt_config_lt_args --quiet\"\nexec AS_MESSAGE_LOG_FD>/dev/null\n$SHELL \"$CONFIG_LT\" $lt_config_lt_args || lt_cl_success=false\nexec AS_MESSAGE_LOG_FD>>config.log\n$lt_cl_success || AS_EXIT(1)\n])# LT_OUTPUT\n\n\n# _LT_CONFIG(TAG)\n# ---------------\n# If TAG is the built-in tag, create an initial libtool script with a\n# default configuration from the untagged config vars.  Otherwise add code\n# to config.status for appending the configuration named by TAG from the\n# matching tagged config vars.\nm4_defun([_LT_CONFIG],\n[m4_require([_LT_FILEUTILS_DEFAULTS])dnl\n_LT_CONFIG_SAVE_COMMANDS([\n  m4_define([_LT_TAG], m4_if([$1], [], [C], [$1]))dnl\n  m4_if(_LT_TAG, [C], [\n    # See if we are running on zsh, and set the options that allow our\n    # commands through without removal of \\ escapes.\n    if test -n \"${ZSH_VERSION+set}\"; then\n      setopt NO_GLOB_SUBST\n    fi\n\n    cfgfile=${ofile}T\n    trap \"$RM \\\"$cfgfile\\\"; exit 1\" 1 2 15\n    $RM \"$cfgfile\"\n\n    cat <<_LT_EOF >> \"$cfgfile\"\n#! $SHELL\n# Generated automatically by $as_me ($PACKAGE) $VERSION\n# Libtool was configured on host `(hostname || uname -n) 2>/dev/null | sed 1q`:\n# NOTE: Changes made to this file will be lost: look at ltmain.sh.\n\n# Provide generalized library-building support services.\n# Written by Gordon Matzigkeit, 1996\n\n_LT_COPYING\n_LT_LIBTOOL_TAGS\n\n# Configured defaults for sys_lib_dlsearch_path munging.\n: \\${LT_SYS_LIBRARY_PATH=\"$configure_time_lt_sys_library_path\"}\n\n# ### BEGIN LIBTOOL CONFIG\n_LT_LIBTOOL_CONFIG_VARS\n_LT_LIBTOOL_TAG_VARS\n# ### END LIBTOOL CONFIG\n\n_LT_EOF\n\n    cat <<'_LT_EOF' >> \"$cfgfile\"\n\n# ### BEGIN FUNCTIONS SHARED WITH CONFIGURE\n\n_LT_PREPARE_MUNGE_PATH_LIST\n_LT_PREPARE_CC_BASENAME\n\n# ### END FUNCTIONS SHARED WITH CONFIGURE\n\n_LT_EOF\n\n  case $host_os in\n  aix3*)\n    cat <<\\_LT_EOF >> \"$cfgfile\"\n# AIX sometimes has problems with the GCC collect2 program.  For some\n# reason, if we set the COLLECT_NAMES environment variable, the problems\n# vanish in a puff of smoke.\nif test set != \"${COLLECT_NAMES+set}\"; then\n  COLLECT_NAMES=\n  export COLLECT_NAMES\nfi\n_LT_EOF\n    ;;\n  esac\n\n  _LT_PROG_LTMAIN\n\n  # We use sed instead of cat because bash on DJGPP gets confused if\n  # if finds mixed CR/LF and LF-only lines.  Since sed operates in\n  # text mode, it properly converts lines to CR/LF.  This bash problem\n  # is reportedly fixed, but why not run on old versions too?\n  $SED '$q' \"$ltmain\" >> \"$cfgfile\" \\\n     || (rm -f \"$cfgfile\"; exit 1)\n\n   mv -f \"$cfgfile\" \"$ofile\" ||\n    (rm -f \"$ofile\" && cp \"$cfgfile\" \"$ofile\" && rm -f \"$cfgfile\")\n  chmod +x \"$ofile\"\n],\n[cat <<_LT_EOF >> \"$ofile\"\n\ndnl Unfortunately we have to use $1 here, since _LT_TAG is not expanded\ndnl in a comment (ie after a #).\n# ### BEGIN LIBTOOL TAG CONFIG: $1\n_LT_LIBTOOL_TAG_VARS(_LT_TAG)\n# ### END LIBTOOL TAG CONFIG: $1\n_LT_EOF\n])dnl /m4_if\n],\n[m4_if([$1], [], [\n    PACKAGE='$PACKAGE'\n    VERSION='$VERSION'\n    RM='$RM'\n    ofile='$ofile'], [])\n])dnl /_LT_CONFIG_SAVE_COMMANDS\n])# _LT_CONFIG\n\n\n# LT_SUPPORTED_TAG(TAG)\n# ---------------------\n# Trace this macro to discover what tags are supported by the libtool\n# --tag option, using:\n#    autoconf --trace 'LT_SUPPORTED_TAG:$1'\nAC_DEFUN([LT_SUPPORTED_TAG], [])\n\n\n# C support is built-in for now\nm4_define([_LT_LANG_C_enabled], [])\nm4_define([_LT_TAGS], [])\n\n\n# LT_LANG(LANG)\n# -------------\n# Enable libtool support for the given language if not already enabled.\nAC_DEFUN([LT_LANG],\n[AC_BEFORE([$0], [LT_OUTPUT])dnl\nm4_case([$1],\n  [C],\t\t\t[_LT_LANG(C)],\n  [C++],\t\t[_LT_LANG(CXX)],\n  [Go],\t\t\t[_LT_LANG(GO)],\n  [Java],\t\t[_LT_LANG(GCJ)],\n  [Fortran 77],\t\t[_LT_LANG(F77)],\n  [Fortran],\t\t[_LT_LANG(FC)],\n  [Windows Resource],\t[_LT_LANG(RC)],\n  [m4_ifdef([_LT_LANG_]$1[_CONFIG],\n    [_LT_LANG($1)],\n    [m4_fatal([$0: unsupported language: \"$1\"])])])dnl\n])# LT_LANG\n\n\n# _LT_LANG(LANGNAME)\n# ------------------\nm4_defun([_LT_LANG],\n[m4_ifdef([_LT_LANG_]$1[_enabled], [],\n  [LT_SUPPORTED_TAG([$1])dnl\n  m4_append([_LT_TAGS], [$1 ])dnl\n  m4_define([_LT_LANG_]$1[_enabled], [])dnl\n  _LT_LANG_$1_CONFIG($1)])dnl\n])# _LT_LANG\n\n\nm4_ifndef([AC_PROG_GO], [\n############################################################\n# NOTE: This macro has been submitted for inclusion into   #\n#  GNU Autoconf as AC_PROG_GO.  When it is available in    #\n#  a released version of Autoconf we should remove this    #\n#  macro and use it instead.                               #\n############################################################\nm4_defun([AC_PROG_GO],\n[AC_LANG_PUSH(Go)dnl\nAC_ARG_VAR([GOC],     [Go compiler command])dnl\nAC_ARG_VAR([GOFLAGS], [Go compiler flags])dnl\n_AC_ARG_VAR_LDFLAGS()dnl\nAC_CHECK_TOOL(GOC, gccgo)\nif test -z \"$GOC\"; then\n  if test -n \"$ac_tool_prefix\"; then\n    AC_CHECK_PROG(GOC, [${ac_tool_prefix}gccgo], [${ac_tool_prefix}gccgo])\n  fi\nfi\nif test -z \"$GOC\"; then\n  AC_CHECK_PROG(GOC, gccgo, gccgo, false)\nfi\n])#m4_defun\n])#m4_ifndef\n\n\n# _LT_LANG_DEFAULT_CONFIG\n# -----------------------\nm4_defun([_LT_LANG_DEFAULT_CONFIG],\n[AC_PROVIDE_IFELSE([AC_PROG_CXX],\n  [LT_LANG(CXX)],\n  [m4_define([AC_PROG_CXX], defn([AC_PROG_CXX])[LT_LANG(CXX)])])\n\nAC_PROVIDE_IFELSE([AC_PROG_F77],\n  [LT_LANG(F77)],\n  [m4_define([AC_PROG_F77], defn([AC_PROG_F77])[LT_LANG(F77)])])\n\nAC_PROVIDE_IFELSE([AC_PROG_FC],\n  [LT_LANG(FC)],\n  [m4_define([AC_PROG_FC], defn([AC_PROG_FC])[LT_LANG(FC)])])\n\ndnl The call to [A][M_PROG_GCJ] is quoted like that to stop aclocal\ndnl pulling things in needlessly.\nAC_PROVIDE_IFELSE([AC_PROG_GCJ],\n  [LT_LANG(GCJ)],\n  [AC_PROVIDE_IFELSE([A][M_PROG_GCJ],\n    [LT_LANG(GCJ)],\n    [AC_PROVIDE_IFELSE([LT_PROG_GCJ],\n      [LT_LANG(GCJ)],\n      [m4_ifdef([AC_PROG_GCJ],\n\t[m4_define([AC_PROG_GCJ], defn([AC_PROG_GCJ])[LT_LANG(GCJ)])])\n       m4_ifdef([A][M_PROG_GCJ],\n\t[m4_define([A][M_PROG_GCJ], defn([A][M_PROG_GCJ])[LT_LANG(GCJ)])])\n       m4_ifdef([LT_PROG_GCJ],\n\t[m4_define([LT_PROG_GCJ], defn([LT_PROG_GCJ])[LT_LANG(GCJ)])])])])])\n\nAC_PROVIDE_IFELSE([AC_PROG_GO],\n  [LT_LANG(GO)],\n  [m4_define([AC_PROG_GO], defn([AC_PROG_GO])[LT_LANG(GO)])])\n\nAC_PROVIDE_IFELSE([LT_PROG_RC],\n  [LT_LANG(RC)],\n  [m4_define([LT_PROG_RC], defn([LT_PROG_RC])[LT_LANG(RC)])])\n])# _LT_LANG_DEFAULT_CONFIG\n\n# Obsolete macros:\nAU_DEFUN([AC_LIBTOOL_CXX], [LT_LANG(C++)])\nAU_DEFUN([AC_LIBTOOL_F77], [LT_LANG(Fortran 77)])\nAU_DEFUN([AC_LIBTOOL_FC], [LT_LANG(Fortran)])\nAU_DEFUN([AC_LIBTOOL_GCJ], [LT_LANG(Java)])\nAU_DEFUN([AC_LIBTOOL_RC], [LT_LANG(Windows Resource)])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_LIBTOOL_CXX], [])\ndnl AC_DEFUN([AC_LIBTOOL_F77], [])\ndnl AC_DEFUN([AC_LIBTOOL_FC], [])\ndnl AC_DEFUN([AC_LIBTOOL_GCJ], [])\ndnl AC_DEFUN([AC_LIBTOOL_RC], [])\n\n\n# _LT_TAG_COMPILER\n# ----------------\nm4_defun([_LT_TAG_COMPILER],\n[AC_REQUIRE([AC_PROG_CC])dnl\n\n_LT_DECL([LTCC], [CC], [1], [A C compiler])dnl\n_LT_DECL([LTCFLAGS], [CFLAGS], [1], [LTCC compiler flags])dnl\n_LT_TAGDECL([CC], [compiler], [1], [A language specific compiler])dnl\n_LT_TAGDECL([with_gcc], [GCC], [0], [Is the compiler the GNU compiler?])dnl\n\n# If no C compiler was specified, use CC.\nLTCC=${LTCC-\"$CC\"}\n\n# If no C compiler flags were specified, use CFLAGS.\nLTCFLAGS=${LTCFLAGS-\"$CFLAGS\"}\n\n# Allow CC to be a program name with arguments.\ncompiler=$CC\n])# _LT_TAG_COMPILER\n\n\n# _LT_COMPILER_BOILERPLATE\n# ------------------------\n# Check for compiler boilerplate output or warnings with\n# the simple compiler test code.\nm4_defun([_LT_COMPILER_BOILERPLATE],\n[m4_require([_LT_DECL_SED])dnl\nac_outfile=conftest.$ac_objext\necho \"$lt_simple_compile_test_code\" >conftest.$ac_ext\neval \"$ac_compile\" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err\n_lt_compiler_boilerplate=`cat conftest.err`\n$RM conftest*\n])# _LT_COMPILER_BOILERPLATE\n\n\n# _LT_LINKER_BOILERPLATE\n# ----------------------\n# Check for linker boilerplate output or warnings with\n# the simple link test code.\nm4_defun([_LT_LINKER_BOILERPLATE],\n[m4_require([_LT_DECL_SED])dnl\nac_outfile=conftest.$ac_objext\necho \"$lt_simple_link_test_code\" >conftest.$ac_ext\neval \"$ac_link\" 2>&1 >/dev/null | $SED '/^$/d; /^ *+/d' >conftest.err\n_lt_linker_boilerplate=`cat conftest.err`\n$RM -r conftest*\n])# _LT_LINKER_BOILERPLATE\n\n# _LT_REQUIRED_DARWIN_CHECKS\n# -------------------------\nm4_defun_once([_LT_REQUIRED_DARWIN_CHECKS],[\n  case $host_os in\n    rhapsody* | darwin*)\n    AC_CHECK_TOOL([DSYMUTIL], [dsymutil], [:])\n    AC_CHECK_TOOL([NMEDIT], [nmedit], [:])\n    AC_CHECK_TOOL([LIPO], [lipo], [:])\n    AC_CHECK_TOOL([OTOOL], [otool], [:])\n    AC_CHECK_TOOL([OTOOL64], [otool64], [:])\n    _LT_DECL([], [DSYMUTIL], [1],\n      [Tool to manipulate archived DWARF debug symbol files on Mac OS X])\n    _LT_DECL([], [NMEDIT], [1],\n      [Tool to change global to local symbols on Mac OS X])\n    _LT_DECL([], [LIPO], [1],\n      [Tool to manipulate fat objects and archives on Mac OS X])\n    _LT_DECL([], [OTOOL], [1],\n      [ldd/readelf like tool for Mach-O binaries on Mac OS X])\n    _LT_DECL([], [OTOOL64], [1],\n      [ldd/readelf like tool for 64 bit Mach-O binaries on Mac OS X 10.4])\n\n    AC_CACHE_CHECK([for -single_module linker flag],[lt_cv_apple_cc_single_mod],\n      [lt_cv_apple_cc_single_mod=no\n      if test -z \"$LT_MULTI_MODULE\"; then\n\t# By default we will add the -single_module flag. You can override\n\t# by either setting the environment variable LT_MULTI_MODULE\n\t# non-empty at configure time, or by adding -multi_module to the\n\t# link flags.\n\trm -rf libconftest.dylib*\n\techo \"int foo(void){return 1;}\" > conftest.c\n\techo \"$LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \\\n-dynamiclib -Wl,-single_module conftest.c\" >&AS_MESSAGE_LOG_FD\n\t$LTCC $LTCFLAGS $LDFLAGS -o libconftest.dylib \\\n\t  -dynamiclib -Wl,-single_module conftest.c 2>conftest.err\n        _lt_result=$?\n\t# If there is a non-empty error log, and \"single_module\"\n\t# appears in it, assume the flag caused a linker warning\n        if test -s conftest.err && $GREP single_module conftest.err; then\n\t  cat conftest.err >&AS_MESSAGE_LOG_FD\n\t# Otherwise, if the output was created with a 0 exit code from\n\t# the compiler, it worked.\n\telif test -f libconftest.dylib && test 0 = \"$_lt_result\"; then\n\t  lt_cv_apple_cc_single_mod=yes\n\telse\n\t  cat conftest.err >&AS_MESSAGE_LOG_FD\n\tfi\n\trm -rf libconftest.dylib*\n\trm -f conftest.*\n      fi])\n\n    AC_CACHE_CHECK([for -exported_symbols_list linker flag],\n      [lt_cv_ld_exported_symbols_list],\n      [lt_cv_ld_exported_symbols_list=no\n      save_LDFLAGS=$LDFLAGS\n      echo \"_main\" > conftest.sym\n      LDFLAGS=\"$LDFLAGS -Wl,-exported_symbols_list,conftest.sym\"\n      AC_LINK_IFELSE([AC_LANG_PROGRAM([],[])],\n\t[lt_cv_ld_exported_symbols_list=yes],\n\t[lt_cv_ld_exported_symbols_list=no])\n\tLDFLAGS=$save_LDFLAGS\n    ])\n\n    AC_CACHE_CHECK([for -force_load linker flag],[lt_cv_ld_force_load],\n      [lt_cv_ld_force_load=no\n      cat > conftest.c << _LT_EOF\nint forced_loaded() { return 2;}\n_LT_EOF\n      echo \"$LTCC $LTCFLAGS -c -o conftest.o conftest.c\" >&AS_MESSAGE_LOG_FD\n      $LTCC $LTCFLAGS -c -o conftest.o conftest.c 2>&AS_MESSAGE_LOG_FD\n      echo \"$AR $AR_FLAGS libconftest.a conftest.o\" >&AS_MESSAGE_LOG_FD\n      $AR $AR_FLAGS libconftest.a conftest.o 2>&AS_MESSAGE_LOG_FD\n      echo \"$RANLIB libconftest.a\" >&AS_MESSAGE_LOG_FD\n      $RANLIB libconftest.a 2>&AS_MESSAGE_LOG_FD\n      cat > conftest.c << _LT_EOF\nint main() { return 0;}\n_LT_EOF\n      echo \"$LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a\" >&AS_MESSAGE_LOG_FD\n      $LTCC $LTCFLAGS $LDFLAGS -o conftest conftest.c -Wl,-force_load,./libconftest.a 2>conftest.err\n      _lt_result=$?\n      if test -s conftest.err && $GREP force_load conftest.err; then\n\tcat conftest.err >&AS_MESSAGE_LOG_FD\n      elif test -f conftest && test 0 = \"$_lt_result\" && $GREP forced_load conftest >/dev/null 2>&1; then\n\tlt_cv_ld_force_load=yes\n      else\n\tcat conftest.err >&AS_MESSAGE_LOG_FD\n      fi\n        rm -f conftest.err libconftest.a conftest conftest.c\n        rm -rf conftest.dSYM\n    ])\n    case $host_os in\n    rhapsody* | darwin1.[[012]])\n      _lt_dar_allow_undefined='$wl-undefined ${wl}suppress' ;;\n    darwin1.*)\n      _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;;\n    darwin*)\n      case $MACOSX_DEPLOYMENT_TARGET,$host in\n        10.[[012]],*|,*powerpc*-darwin[[5-8]]*)\n          _lt_dar_allow_undefined='$wl-flat_namespace $wl-undefined ${wl}suppress' ;;\n        *)\n          _lt_dar_allow_undefined='$wl-undefined ${wl}dynamic_lookup' ;;\n      esac\n    ;;\n  esac\n    if test yes = \"$lt_cv_apple_cc_single_mod\"; then\n      _lt_dar_single_mod='$single_module'\n    fi\n    if test yes = \"$lt_cv_ld_exported_symbols_list\"; then\n      _lt_dar_export_syms=' $wl-exported_symbols_list,$output_objdir/$libname-symbols.expsym'\n    else\n      _lt_dar_export_syms='~$NMEDIT -s $output_objdir/$libname-symbols.expsym $lib'\n    fi\n    if test : != \"$DSYMUTIL\" && test no = \"$lt_cv_ld_force_load\"; then\n      _lt_dsymutil='~$DSYMUTIL $lib || :'\n    else\n      _lt_dsymutil=\n    fi\n    ;;\n  esac\n])\n\n\n# _LT_DARWIN_LINKER_FEATURES([TAG])\n# ---------------------------------\n# Checks for linker and compiler features on darwin\nm4_defun([_LT_DARWIN_LINKER_FEATURES],\n[\n  m4_require([_LT_REQUIRED_DARWIN_CHECKS])\n  _LT_TAGVAR(archive_cmds_need_lc, $1)=no\n  _LT_TAGVAR(hardcode_direct, $1)=no\n  _LT_TAGVAR(hardcode_automatic, $1)=yes\n  _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported\n  if test yes = \"$lt_cv_ld_force_load\"; then\n    _LT_TAGVAR(whole_archive_flag_spec, $1)='`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience $wl-force_load,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"`'\n    m4_case([$1], [F77], [_LT_TAGVAR(compiler_needs_object, $1)=yes],\n                  [FC],  [_LT_TAGVAR(compiler_needs_object, $1)=yes])\n  else\n    _LT_TAGVAR(whole_archive_flag_spec, $1)=''\n  fi\n  _LT_TAGVAR(link_all_deplibs, $1)=yes\n  _LT_TAGVAR(allow_undefined_flag, $1)=$_lt_dar_allow_undefined\n  case $cc_basename in\n     ifort*|nagfor*) _lt_dar_can_shared=yes ;;\n     *) _lt_dar_can_shared=$GCC ;;\n  esac\n  if test yes = \"$_lt_dar_can_shared\"; then\n    output_verbose_link_cmd=func_echo_all\n    _LT_TAGVAR(archive_cmds, $1)=\"\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$libobjs \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring $_lt_dar_single_mod$_lt_dsymutil\"\n    _LT_TAGVAR(module_cmds, $1)=\"\\$CC \\$allow_undefined_flag -o \\$lib -bundle \\$libobjs \\$deplibs \\$compiler_flags$_lt_dsymutil\"\n    _LT_TAGVAR(archive_expsym_cmds, $1)=\"$SED 's|^|_|' < \\$export_symbols > \\$output_objdir/\\$libname-symbols.expsym~\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$libobjs \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring $_lt_dar_single_mod$_lt_dar_export_syms$_lt_dsymutil\"\n    _LT_TAGVAR(module_expsym_cmds, $1)=\"$SED -e 's|^|_|' < \\$export_symbols > \\$output_objdir/\\$libname-symbols.expsym~\\$CC \\$allow_undefined_flag -o \\$lib -bundle \\$libobjs \\$deplibs \\$compiler_flags$_lt_dar_export_syms$_lt_dsymutil\"\n    m4_if([$1], [CXX],\n[   if test yes != \"$lt_cv_apple_cc_single_mod\"; then\n      _LT_TAGVAR(archive_cmds, $1)=\"\\$CC -r -keep_private_externs -nostdlib -o \\$lib-master.o \\$libobjs~\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$lib-master.o \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring$_lt_dsymutil\"\n      _LT_TAGVAR(archive_expsym_cmds, $1)=\"$SED 's|^|_|' < \\$export_symbols > \\$output_objdir/\\$libname-symbols.expsym~\\$CC -r -keep_private_externs -nostdlib -o \\$lib-master.o \\$libobjs~\\$CC -dynamiclib \\$allow_undefined_flag -o \\$lib \\$lib-master.o \\$deplibs \\$compiler_flags -install_name \\$rpath/\\$soname \\$verstring$_lt_dar_export_syms$_lt_dsymutil\"\n    fi\n],[])\n  else\n  _LT_TAGVAR(ld_shlibs, $1)=no\n  fi\n])\n\n# _LT_SYS_MODULE_PATH_AIX([TAGNAME])\n# ----------------------------------\n# Links a minimal program and checks the executable\n# for the system default hardcoded library path. In most cases,\n# this is /usr/lib:/lib, but when the MPI compilers are used\n# the location of the communication and MPI libs are included too.\n# If we don't find anything, use the default library path according\n# to the aix ld manual.\n# Store the results from the different compilers for each TAGNAME.\n# Allow to override them for all tags through lt_cv_aix_libpath.\nm4_defun([_LT_SYS_MODULE_PATH_AIX],\n[m4_require([_LT_DECL_SED])dnl\nif test set = \"${lt_cv_aix_libpath+set}\"; then\n  aix_libpath=$lt_cv_aix_libpath\nelse\n  AC_CACHE_VAL([_LT_TAGVAR([lt_cv_aix_libpath_], [$1])],\n  [AC_LINK_IFELSE([AC_LANG_PROGRAM],[\n  lt_aix_libpath_sed='[\n      /Import File Strings/,/^$/ {\n\t  /^0/ {\n\t      s/^0  *\\([^ ]*\\) *$/\\1/\n\t      p\n\t  }\n      }]'\n  _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=`dump -H conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  # Check for a 64-bit object if we didn't find anything.\n  if test -z \"$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])\"; then\n    _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=`dump -HX64 conftest$ac_exeext 2>/dev/null | $SED -n -e \"$lt_aix_libpath_sed\"`\n  fi],[])\n  if test -z \"$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])\"; then\n    _LT_TAGVAR([lt_cv_aix_libpath_], [$1])=/usr/lib:/lib\n  fi\n  ])\n  aix_libpath=$_LT_TAGVAR([lt_cv_aix_libpath_], [$1])\nfi\n])# _LT_SYS_MODULE_PATH_AIX\n\n\n# _LT_SHELL_INIT(ARG)\n# -------------------\nm4_define([_LT_SHELL_INIT],\n[m4_divert_text([M4SH-INIT], [$1\n])])# _LT_SHELL_INIT\n\n\n\n# _LT_PROG_ECHO_BACKSLASH\n# -----------------------\n# Find how we can fake an echo command that does not interpret backslash.\n# In particular, with Autoconf 2.60 or later we add some code to the start\n# of the generated configure script that will find a shell with a builtin\n# printf (that we can use as an echo command).\nm4_defun([_LT_PROG_ECHO_BACKSLASH],\n[ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'\nECHO=$ECHO$ECHO$ECHO$ECHO$ECHO\nECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO\n\nAC_MSG_CHECKING([how to print strings])\n# Test print first, because it will be a builtin if present.\nif test \"X`( print -r -- -n ) 2>/dev/null`\" = X-n && \\\n   test \"X`print -r -- $ECHO 2>/dev/null`\" = \"X$ECHO\"; then\n  ECHO='print -r --'\nelif test \"X`printf %s $ECHO 2>/dev/null`\" = \"X$ECHO\"; then\n  ECHO='printf %s\\n'\nelse\n  # Use this function as a fallback that always works.\n  func_fallback_echo ()\n  {\n    eval 'cat <<_LTECHO_EOF\n$[]1\n_LTECHO_EOF'\n  }\n  ECHO='func_fallback_echo'\nfi\n\n# func_echo_all arg...\n# Invoke $ECHO with all args, space-separated.\nfunc_echo_all ()\n{\n    $ECHO \"$*\"\n}\n\ncase $ECHO in\n  printf*) AC_MSG_RESULT([printf]) ;;\n  print*) AC_MSG_RESULT([print -r]) ;;\n  *) AC_MSG_RESULT([cat]) ;;\nesac\n\nm4_ifdef([_AS_DETECT_SUGGESTED],\n[_AS_DETECT_SUGGESTED([\n  test -n \"${ZSH_VERSION+set}${BASH_VERSION+set}\" || (\n    ECHO='\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\\'\n    ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO\n    ECHO=$ECHO$ECHO$ECHO$ECHO$ECHO$ECHO\n    PATH=/empty FPATH=/empty; export PATH FPATH\n    test \"X`printf %s $ECHO`\" = \"X$ECHO\" \\\n      || test \"X`print -r -- $ECHO`\" = \"X$ECHO\" )])])\n\n_LT_DECL([], [SHELL], [1], [Shell to use when invoking shell scripts])\n_LT_DECL([], [ECHO], [1], [An echo program that protects backslashes])\n])# _LT_PROG_ECHO_BACKSLASH\n\n\n# _LT_WITH_SYSROOT\n# ----------------\nAC_DEFUN([_LT_WITH_SYSROOT],\n[m4_require([_LT_DECL_SED])dnl\nAC_MSG_CHECKING([for sysroot])\nAC_ARG_WITH([sysroot],\n[AS_HELP_STRING([--with-sysroot@<:@=DIR@:>@],\n  [Search for dependent libraries within DIR (or the compiler's sysroot\n   if not specified).])],\n[], [with_sysroot=no])\n\ndnl lt_sysroot will always be passed unquoted.  We quote it here\ndnl in case the user passed a directory name.\nlt_sysroot=\ncase $with_sysroot in #(\n yes)\n   if test yes = \"$GCC\"; then\n     lt_sysroot=`$CC --print-sysroot 2>/dev/null`\n   fi\n   ;; #(\n /*)\n   lt_sysroot=`echo \"$with_sysroot\" | $SED -e \"$sed_quote_subst\"`\n   ;; #(\n no|'')\n   ;; #(\n *)\n   AC_MSG_RESULT([$with_sysroot])\n   AC_MSG_ERROR([The sysroot must be an absolute path.])\n   ;;\nesac\n\n AC_MSG_RESULT([${lt_sysroot:-no}])\n_LT_DECL([], [lt_sysroot], [0], [The root where to search for ]dnl\n[dependent libraries, and where our libraries should be installed.])])\n\n# _LT_ENABLE_LOCK\n# ---------------\nm4_defun([_LT_ENABLE_LOCK],\n[AC_ARG_ENABLE([libtool-lock],\n  [AS_HELP_STRING([--disable-libtool-lock],\n    [avoid locking (might break parallel builds)])])\ntest no = \"$enable_libtool_lock\" || enable_libtool_lock=yes\n\n# Some flags need to be propagated to the compiler or linker for good\n# libtool support.\ncase $host in\nia64-*-hpux*)\n  # Find out what ABI is being produced by ac_compile, and set mode\n  # options accordingly.\n  echo 'int i;' > conftest.$ac_ext\n  if AC_TRY_EVAL(ac_compile); then\n    case `$FILECMD conftest.$ac_objext` in\n      *ELF-32*)\n\tHPUX_IA64_MODE=32\n\t;;\n      *ELF-64*)\n\tHPUX_IA64_MODE=64\n\t;;\n    esac\n  fi\n  rm -rf conftest*\n  ;;\n*-*-irix6*)\n  # Find out what ABI is being produced by ac_compile, and set linker\n  # options accordingly.\n  echo '[#]line '$LINENO' \"configure\"' > conftest.$ac_ext\n  if AC_TRY_EVAL(ac_compile); then\n    if test yes = \"$lt_cv_prog_gnu_ld\"; then\n      case `$FILECMD conftest.$ac_objext` in\n\t*32-bit*)\n\t  LD=\"${LD-ld} -melf32bsmip\"\n\t  ;;\n\t*N32*)\n\t  LD=\"${LD-ld} -melf32bmipn32\"\n\t  ;;\n\t*64-bit*)\n\t  LD=\"${LD-ld} -melf64bmip\"\n\t;;\n      esac\n    else\n      case `$FILECMD conftest.$ac_objext` in\n\t*32-bit*)\n\t  LD=\"${LD-ld} -32\"\n\t  ;;\n\t*N32*)\n\t  LD=\"${LD-ld} -n32\"\n\t  ;;\n\t*64-bit*)\n\t  LD=\"${LD-ld} -64\"\n\t  ;;\n      esac\n    fi\n  fi\n  rm -rf conftest*\n  ;;\n\nmips64*-*linux*)\n  # Find out what ABI is being produced by ac_compile, and set linker\n  # options accordingly.\n  echo '[#]line '$LINENO' \"configure\"' > conftest.$ac_ext\n  if AC_TRY_EVAL(ac_compile); then\n    emul=elf\n    case `$FILECMD conftest.$ac_objext` in\n      *32-bit*)\n\temul=\"${emul}32\"\n\t;;\n      *64-bit*)\n\temul=\"${emul}64\"\n\t;;\n    esac\n    case `$FILECMD conftest.$ac_objext` in\n      *MSB*)\n\temul=\"${emul}btsmip\"\n\t;;\n      *LSB*)\n\temul=\"${emul}ltsmip\"\n\t;;\n    esac\n    case `$FILECMD conftest.$ac_objext` in\n      *N32*)\n\temul=\"${emul}n32\"\n\t;;\n    esac\n    LD=\"${LD-ld} -m $emul\"\n  fi\n  rm -rf conftest*\n  ;;\n\nx86_64-*kfreebsd*-gnu|x86_64-*linux*|powerpc*-*linux*| \\\ns390*-*linux*|s390*-*tpf*|sparc*-*linux*)\n  # Find out what ABI is being produced by ac_compile, and set linker\n  # options accordingly.  Note that the listed cases only cover the\n  # situations where additional linker options are needed (such as when\n  # doing 32-bit compilation for a host where ld defaults to 64-bit, or\n  # vice versa); the common cases where no linker options are needed do\n  # not appear in the list.\n  echo 'int i;' > conftest.$ac_ext\n  if AC_TRY_EVAL(ac_compile); then\n    case `$FILECMD conftest.o` in\n      *32-bit*)\n\tcase $host in\n\t  x86_64-*kfreebsd*-gnu)\n\t    LD=\"${LD-ld} -m elf_i386_fbsd\"\n\t    ;;\n\t  x86_64-*linux*)\n\t    case `$FILECMD conftest.o` in\n\t      *x86-64*)\n\t\tLD=\"${LD-ld} -m elf32_x86_64\"\n\t\t;;\n\t      *)\n\t\tLD=\"${LD-ld} -m elf_i386\"\n\t\t;;\n\t    esac\n\t    ;;\n\t  powerpc64le-*linux*)\n\t    LD=\"${LD-ld} -m elf32lppclinux\"\n\t    ;;\n\t  powerpc64-*linux*)\n\t    LD=\"${LD-ld} -m elf32ppclinux\"\n\t    ;;\n\t  s390x-*linux*)\n\t    LD=\"${LD-ld} -m elf_s390\"\n\t    ;;\n\t  sparc64-*linux*)\n\t    LD=\"${LD-ld} -m elf32_sparc\"\n\t    ;;\n\tesac\n\t;;\n      *64-bit*)\n\tcase $host in\n\t  x86_64-*kfreebsd*-gnu)\n\t    LD=\"${LD-ld} -m elf_x86_64_fbsd\"\n\t    ;;\n\t  x86_64-*linux*)\n\t    LD=\"${LD-ld} -m elf_x86_64\"\n\t    ;;\n\t  powerpcle-*linux*)\n\t    LD=\"${LD-ld} -m elf64lppc\"\n\t    ;;\n\t  powerpc-*linux*)\n\t    LD=\"${LD-ld} -m elf64ppc\"\n\t    ;;\n\t  s390*-*linux*|s390*-*tpf*)\n\t    LD=\"${LD-ld} -m elf64_s390\"\n\t    ;;\n\t  sparc*-*linux*)\n\t    LD=\"${LD-ld} -m elf64_sparc\"\n\t    ;;\n\tesac\n\t;;\n    esac\n  fi\n  rm -rf conftest*\n  ;;\n\n*-*-sco3.2v5*)\n  # On SCO OpenServer 5, we need -belf to get full-featured binaries.\n  SAVE_CFLAGS=$CFLAGS\n  CFLAGS=\"$CFLAGS -belf\"\n  AC_CACHE_CHECK([whether the C compiler needs -belf], lt_cv_cc_needs_belf,\n    [AC_LANG_PUSH(C)\n     AC_LINK_IFELSE([AC_LANG_PROGRAM([[]],[[]])],[lt_cv_cc_needs_belf=yes],[lt_cv_cc_needs_belf=no])\n     AC_LANG_POP])\n  if test yes != \"$lt_cv_cc_needs_belf\"; then\n    # this is probably gcc 2.8.0, egcs 1.0 or newer; no need for -belf\n    CFLAGS=$SAVE_CFLAGS\n  fi\n  ;;\n*-*solaris*)\n  # Find out what ABI is being produced by ac_compile, and set linker\n  # options accordingly.\n  echo 'int i;' > conftest.$ac_ext\n  if AC_TRY_EVAL(ac_compile); then\n    case `$FILECMD conftest.o` in\n    *64-bit*)\n      case $lt_cv_prog_gnu_ld in\n      yes*)\n        case $host in\n        i?86-*-solaris*|x86_64-*-solaris*)\n          LD=\"${LD-ld} -m elf_x86_64\"\n          ;;\n        sparc*-*-solaris*)\n          LD=\"${LD-ld} -m elf64_sparc\"\n          ;;\n        esac\n        # GNU ld 2.21 introduced _sol2 emulations.  Use them if available.\n        if ${LD-ld} -V | grep _sol2 >/dev/null 2>&1; then\n          LD=${LD-ld}_sol2\n        fi\n        ;;\n      *)\n\tif ${LD-ld} -64 -r -o conftest2.o conftest.o >/dev/null 2>&1; then\n\t  LD=\"${LD-ld} -64\"\n\tfi\n\t;;\n      esac\n      ;;\n    esac\n  fi\n  rm -rf conftest*\n  ;;\nesac\n\nneed_locks=$enable_libtool_lock\n])# _LT_ENABLE_LOCK\n\n\n# _LT_PROG_AR\n# -----------\nm4_defun([_LT_PROG_AR],\n[AC_CHECK_TOOLS(AR, [ar], false)\n: ${AR=ar}\n_LT_DECL([], [AR], [1], [The archiver])\n\n# Use ARFLAGS variable as AR's operation code to sync the variable naming with\n# Automake.  If both AR_FLAGS and ARFLAGS are specified, AR_FLAGS should have\n# higher priority because thats what people were doing historically (setting\n# ARFLAGS for automake and AR_FLAGS for libtool).  FIXME: Make the AR_FLAGS\n# variable obsoleted/removed.\n\ntest ${AR_FLAGS+y} || AR_FLAGS=${ARFLAGS-cr}\nlt_ar_flags=$AR_FLAGS\n_LT_DECL([], [lt_ar_flags], [0], [Flags to create an archive (by configure)])\n\n# Make AR_FLAGS overridable by 'make ARFLAGS='.  Don't try to run-time override\n# by AR_FLAGS because that was never working and AR_FLAGS is about to die.\n_LT_DECL([], [AR_FLAGS], [\\@S|@{ARFLAGS-\"\\@S|@lt_ar_flags\"}],\n         [Flags to create an archive])\n\nAC_CACHE_CHECK([for archiver @FILE support], [lt_cv_ar_at_file],\n  [lt_cv_ar_at_file=no\n   AC_COMPILE_IFELSE([AC_LANG_PROGRAM],\n     [echo conftest.$ac_objext > conftest.lst\n      lt_ar_try='$AR $AR_FLAGS libconftest.a @conftest.lst >&AS_MESSAGE_LOG_FD'\n      AC_TRY_EVAL([lt_ar_try])\n      if test 0 -eq \"$ac_status\"; then\n\t# Ensure the archiver fails upon bogus file names.\n\trm -f conftest.$ac_objext libconftest.a\n\tAC_TRY_EVAL([lt_ar_try])\n\tif test 0 -ne \"$ac_status\"; then\n          lt_cv_ar_at_file=@\n        fi\n      fi\n      rm -f conftest.* libconftest.a\n     ])\n  ])\n\nif test no = \"$lt_cv_ar_at_file\"; then\n  archiver_list_spec=\nelse\n  archiver_list_spec=$lt_cv_ar_at_file\nfi\n_LT_DECL([], [archiver_list_spec], [1],\n  [How to feed a file listing to the archiver])\n])# _LT_PROG_AR\n\n\n# _LT_CMD_OLD_ARCHIVE\n# -------------------\nm4_defun([_LT_CMD_OLD_ARCHIVE],\n[_LT_PROG_AR\n\nAC_CHECK_TOOL(STRIP, strip, :)\ntest -z \"$STRIP\" && STRIP=:\n_LT_DECL([], [STRIP], [1], [A symbol stripping program])\n\nAC_CHECK_TOOL(RANLIB, ranlib, :)\ntest -z \"$RANLIB\" && RANLIB=:\n_LT_DECL([], [RANLIB], [1],\n    [Commands used to install an old-style archive])\n\n# Determine commands to create old-style static archives.\nold_archive_cmds='$AR $AR_FLAGS $oldlib$oldobjs'\nold_postinstall_cmds='chmod 644 $oldlib'\nold_postuninstall_cmds=\n\nif test -n \"$RANLIB\"; then\n  case $host_os in\n  bitrig* | openbsd*)\n    old_postinstall_cmds=\"$old_postinstall_cmds~\\$RANLIB -t \\$tool_oldlib\"\n    ;;\n  *)\n    old_postinstall_cmds=\"$old_postinstall_cmds~\\$RANLIB \\$tool_oldlib\"\n    ;;\n  esac\n  old_archive_cmds=\"$old_archive_cmds~\\$RANLIB \\$tool_oldlib\"\nfi\n\ncase $host_os in\n  darwin*)\n    lock_old_archive_extraction=yes ;;\n  *)\n    lock_old_archive_extraction=no ;;\nesac\n_LT_DECL([], [old_postinstall_cmds], [2])\n_LT_DECL([], [old_postuninstall_cmds], [2])\n_LT_TAGDECL([], [old_archive_cmds], [2],\n    [Commands used to build an old-style archive])\n_LT_DECL([], [lock_old_archive_extraction], [0],\n    [Whether to use a lock for old archive extraction])\n])# _LT_CMD_OLD_ARCHIVE\n\n\n# _LT_COMPILER_OPTION(MESSAGE, VARIABLE-NAME, FLAGS,\n#\t\t[OUTPUT-FILE], [ACTION-SUCCESS], [ACTION-FAILURE])\n# ----------------------------------------------------------------\n# Check whether the given compiler option works\nAC_DEFUN([_LT_COMPILER_OPTION],\n[m4_require([_LT_FILEUTILS_DEFAULTS])dnl\nm4_require([_LT_DECL_SED])dnl\nAC_CACHE_CHECK([$1], [$2],\n  [$2=no\n   m4_if([$4], , [ac_outfile=conftest.$ac_objext], [ac_outfile=$4])\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n   lt_compiler_flag=\"$3\"  ## exclude from sc_useless_quotes_in_assignment\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   # The option is referenced via a variable to avoid confusing sed.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [[^ ]]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&AS_MESSAGE_LOG_FD)\n   (eval \"$lt_compile\" 2>conftest.err)\n   ac_status=$?\n   cat conftest.err >&AS_MESSAGE_LOG_FD\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&AS_MESSAGE_LOG_FD\n   if (exit $ac_status) && test -s \"$ac_outfile\"; then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings other than the usual output.\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' >conftest.exp\n     $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2\n     if test ! -s conftest.er2 || diff conftest.exp conftest.er2 >/dev/null; then\n       $2=yes\n     fi\n   fi\n   $RM conftest*\n])\n\nif test yes = \"[$]$2\"; then\n    m4_if([$5], , :, [$5])\nelse\n    m4_if([$6], , :, [$6])\nfi\n])# _LT_COMPILER_OPTION\n\n# Old name:\nAU_ALIAS([AC_LIBTOOL_COMPILER_OPTION], [_LT_COMPILER_OPTION])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_LIBTOOL_COMPILER_OPTION], [])\n\n\n# _LT_LINKER_OPTION(MESSAGE, VARIABLE-NAME, FLAGS,\n#                  [ACTION-SUCCESS], [ACTION-FAILURE])\n# ----------------------------------------------------\n# Check whether the given linker option works\nAC_DEFUN([_LT_LINKER_OPTION],\n[m4_require([_LT_FILEUTILS_DEFAULTS])dnl\nm4_require([_LT_DECL_SED])dnl\nAC_CACHE_CHECK([$1], [$2],\n  [$2=no\n   save_LDFLAGS=$LDFLAGS\n   LDFLAGS=\"$LDFLAGS $3\"\n   echo \"$lt_simple_link_test_code\" > conftest.$ac_ext\n   if (eval $ac_link 2>conftest.err) && test -s conftest$ac_exeext; then\n     # The linker can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     if test -s conftest.err; then\n       # Append any errors to the config.log.\n       cat conftest.err 1>&AS_MESSAGE_LOG_FD\n       $ECHO \"$_lt_linker_boilerplate\" | $SED '/^$/d' > conftest.exp\n       $SED '/^$/d; /^ *+/d' conftest.err >conftest.er2\n       if diff conftest.exp conftest.er2 >/dev/null; then\n         $2=yes\n       fi\n     else\n       $2=yes\n     fi\n   fi\n   $RM -r conftest*\n   LDFLAGS=$save_LDFLAGS\n])\n\nif test yes = \"[$]$2\"; then\n    m4_if([$4], , :, [$4])\nelse\n    m4_if([$5], , :, [$5])\nfi\n])# _LT_LINKER_OPTION\n\n# Old name:\nAU_ALIAS([AC_LIBTOOL_LINKER_OPTION], [_LT_LINKER_OPTION])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_LIBTOOL_LINKER_OPTION], [])\n\n\n# LT_CMD_MAX_LEN\n#---------------\nAC_DEFUN([LT_CMD_MAX_LEN],\n[AC_REQUIRE([AC_CANONICAL_HOST])dnl\n# find the maximum length of command line arguments\nAC_MSG_CHECKING([the maximum length of command line arguments])\nAC_CACHE_VAL([lt_cv_sys_max_cmd_len], [dnl\n  i=0\n  teststring=ABCD\n\n  case $build_os in\n  msdosdjgpp*)\n    # On DJGPP, this test can blow up pretty badly due to problems in libc\n    # (any single argument exceeding 2000 bytes causes a buffer overrun\n    # during glob expansion).  Even if it were fixed, the result of this\n    # check would be larger than it should be.\n    lt_cv_sys_max_cmd_len=12288;    # 12K is about right\n    ;;\n\n  gnu*)\n    # Under GNU Hurd, this test is not required because there is\n    # no limit to the length of command line arguments.\n    # Libtool will interpret -1 as no limit whatsoever\n    lt_cv_sys_max_cmd_len=-1;\n    ;;\n\n  cygwin* | mingw* | cegcc*)\n    # On Win9x/ME, this test blows up -- it succeeds, but takes\n    # about 5 minutes as the teststring grows exponentially.\n    # Worse, since 9x/ME are not pre-emptively multitasking,\n    # you end up with a \"frozen\" computer, even though with patience\n    # the test eventually succeeds (with a max line length of 256k).\n    # Instead, let's just punt: use the minimum linelength reported by\n    # all of the supported platforms: 8192 (on NT/2K/XP).\n    lt_cv_sys_max_cmd_len=8192;\n    ;;\n\n  mint*)\n    # On MiNT this can take a long time and run out of memory.\n    lt_cv_sys_max_cmd_len=8192;\n    ;;\n\n  amigaos*)\n    # On AmigaOS with pdksh, this test takes hours, literally.\n    # So we just punt and use a minimum line length of 8192.\n    lt_cv_sys_max_cmd_len=8192;\n    ;;\n\n  bitrig* | darwin* | dragonfly* | freebsd* | midnightbsd* | netbsd* | openbsd*)\n    # This has been around since 386BSD, at least.  Likely further.\n    if test -x /sbin/sysctl; then\n      lt_cv_sys_max_cmd_len=`/sbin/sysctl -n kern.argmax`\n    elif test -x /usr/sbin/sysctl; then\n      lt_cv_sys_max_cmd_len=`/usr/sbin/sysctl -n kern.argmax`\n    else\n      lt_cv_sys_max_cmd_len=65536\t# usable default for all BSDs\n    fi\n    # And add a safety zone\n    lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\/ 4`\n    lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\* 3`\n    ;;\n\n  interix*)\n    # We know the value 262144 and hardcode it with a safety zone (like BSD)\n    lt_cv_sys_max_cmd_len=196608\n    ;;\n\n  os2*)\n    # The test takes a long time on OS/2.\n    lt_cv_sys_max_cmd_len=8192\n    ;;\n\n  osf*)\n    # Dr. Hans Ekkehard Plesser reports seeing a kernel panic running configure\n    # due to this test when exec_disable_arg_limit is 1 on Tru64. It is not\n    # nice to cause kernel panics so lets avoid the loop below.\n    # First set a reasonable default.\n    lt_cv_sys_max_cmd_len=16384\n    #\n    if test -x /sbin/sysconfig; then\n      case `/sbin/sysconfig -q proc exec_disable_arg_limit` in\n        *1*) lt_cv_sys_max_cmd_len=-1 ;;\n      esac\n    fi\n    ;;\n  sco3.2v5*)\n    lt_cv_sys_max_cmd_len=102400\n    ;;\n  sysv5* | sco5v6* | sysv4.2uw2*)\n    kargmax=`grep ARG_MAX /etc/conf/cf.d/stune 2>/dev/null`\n    if test -n \"$kargmax\"; then\n      lt_cv_sys_max_cmd_len=`echo $kargmax | $SED 's/.*[[\t ]]//'`\n    else\n      lt_cv_sys_max_cmd_len=32768\n    fi\n    ;;\n  *)\n    lt_cv_sys_max_cmd_len=`(getconf ARG_MAX) 2> /dev/null`\n    if test -n \"$lt_cv_sys_max_cmd_len\" && \\\n       test undefined != \"$lt_cv_sys_max_cmd_len\"; then\n      lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\/ 4`\n      lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\* 3`\n    else\n      # Make teststring a little bigger before we do anything with it.\n      # a 1K string should be a reasonable start.\n      for i in 1 2 3 4 5 6 7 8; do\n        teststring=$teststring$teststring\n      done\n      SHELL=${SHELL-${CONFIG_SHELL-/bin/sh}}\n      # If test is not a shell built-in, we'll probably end up computing a\n      # maximum length that is only half of the actual maximum length, but\n      # we can't tell.\n      while { test X`env echo \"$teststring$teststring\" 2>/dev/null` \\\n\t         = \"X$teststring$teststring\"; } >/dev/null 2>&1 &&\n\t      test 17 != \"$i\" # 1/2 MB should be enough\n      do\n        i=`expr $i + 1`\n        teststring=$teststring$teststring\n      done\n      # Only check the string length outside the loop.\n      lt_cv_sys_max_cmd_len=`expr \"X$teststring\" : \".*\" 2>&1`\n      teststring=\n      # Add a significant safety factor because C++ compilers can tack on\n      # massive amounts of additional arguments before passing them to the\n      # linker.  It appears as though 1/2 is a usable value.\n      lt_cv_sys_max_cmd_len=`expr $lt_cv_sys_max_cmd_len \\/ 2`\n    fi\n    ;;\n  esac\n])\nif test -n \"$lt_cv_sys_max_cmd_len\"; then\n  AC_MSG_RESULT($lt_cv_sys_max_cmd_len)\nelse\n  AC_MSG_RESULT(none)\nfi\nmax_cmd_len=$lt_cv_sys_max_cmd_len\n_LT_DECL([], [max_cmd_len], [0],\n    [What is the maximum length of a command?])\n])# LT_CMD_MAX_LEN\n\n# Old name:\nAU_ALIAS([AC_LIBTOOL_SYS_MAX_CMD_LEN], [LT_CMD_MAX_LEN])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_LIBTOOL_SYS_MAX_CMD_LEN], [])\n\n\n# _LT_HEADER_DLFCN\n# ----------------\nm4_defun([_LT_HEADER_DLFCN],\n[AC_CHECK_HEADERS([dlfcn.h], [], [], [AC_INCLUDES_DEFAULT])dnl\n])# _LT_HEADER_DLFCN\n\n\n# _LT_TRY_DLOPEN_SELF (ACTION-IF-TRUE, ACTION-IF-TRUE-W-USCORE,\n#                      ACTION-IF-FALSE, ACTION-IF-CROSS-COMPILING)\n# ----------------------------------------------------------------\nm4_defun([_LT_TRY_DLOPEN_SELF],\n[m4_require([_LT_HEADER_DLFCN])dnl\nif test yes = \"$cross_compiling\"; then :\n  [$4]\nelse\n  lt_dlunknown=0; lt_dlno_uscore=1; lt_dlneed_uscore=2\n  lt_status=$lt_dlunknown\n  cat > conftest.$ac_ext <<_LT_EOF\n[#line $LINENO \"configure\"\n#include \"confdefs.h\"\n\n#if HAVE_DLFCN_H\n#include <dlfcn.h>\n#endif\n\n#include <stdio.h>\n\n#ifdef RTLD_GLOBAL\n#  define LT_DLGLOBAL\t\tRTLD_GLOBAL\n#else\n#  ifdef DL_GLOBAL\n#    define LT_DLGLOBAL\t\tDL_GLOBAL\n#  else\n#    define LT_DLGLOBAL\t\t0\n#  endif\n#endif\n\n/* We may have to define LT_DLLAZY_OR_NOW in the command line if we\n   find out it does not work in some platform. */\n#ifndef LT_DLLAZY_OR_NOW\n#  ifdef RTLD_LAZY\n#    define LT_DLLAZY_OR_NOW\t\tRTLD_LAZY\n#  else\n#    ifdef DL_LAZY\n#      define LT_DLLAZY_OR_NOW\t\tDL_LAZY\n#    else\n#      ifdef RTLD_NOW\n#        define LT_DLLAZY_OR_NOW\tRTLD_NOW\n#      else\n#        ifdef DL_NOW\n#          define LT_DLLAZY_OR_NOW\tDL_NOW\n#        else\n#          define LT_DLLAZY_OR_NOW\t0\n#        endif\n#      endif\n#    endif\n#  endif\n#endif\n\n/* When -fvisibility=hidden is used, assume the code has been annotated\n   correspondingly for the symbols needed.  */\n#if defined __GNUC__ && (((__GNUC__ == 3) && (__GNUC_MINOR__ >= 3)) || (__GNUC__ > 3))\nint fnord () __attribute__((visibility(\"default\")));\n#endif\n\nint fnord () { return 42; }\nint main ()\n{\n  void *self = dlopen (0, LT_DLGLOBAL|LT_DLLAZY_OR_NOW);\n  int status = $lt_dlunknown;\n\n  if (self)\n    {\n      if (dlsym (self,\"fnord\"))       status = $lt_dlno_uscore;\n      else\n        {\n\t  if (dlsym( self,\"_fnord\"))  status = $lt_dlneed_uscore;\n          else puts (dlerror ());\n\t}\n      /* dlclose (self); */\n    }\n  else\n    puts (dlerror ());\n\n  return status;\n}]\n_LT_EOF\n  if AC_TRY_EVAL(ac_link) && test -s \"conftest$ac_exeext\" 2>/dev/null; then\n    (./conftest; exit; ) >&AS_MESSAGE_LOG_FD 2>/dev/null\n    lt_status=$?\n    case x$lt_status in\n      x$lt_dlno_uscore) $1 ;;\n      x$lt_dlneed_uscore) $2 ;;\n      x$lt_dlunknown|x*) $3 ;;\n    esac\n  else :\n    # compilation failed\n    $3\n  fi\nfi\nrm -fr conftest*\n])# _LT_TRY_DLOPEN_SELF\n\n\n# LT_SYS_DLOPEN_SELF\n# ------------------\nAC_DEFUN([LT_SYS_DLOPEN_SELF],\n[m4_require([_LT_HEADER_DLFCN])dnl\nif test yes != \"$enable_dlopen\"; then\n  enable_dlopen=unknown\n  enable_dlopen_self=unknown\n  enable_dlopen_self_static=unknown\nelse\n  lt_cv_dlopen=no\n  lt_cv_dlopen_libs=\n\n  case $host_os in\n  beos*)\n    lt_cv_dlopen=load_add_on\n    lt_cv_dlopen_libs=\n    lt_cv_dlopen_self=yes\n    ;;\n\n  mingw* | pw32* | cegcc*)\n    lt_cv_dlopen=LoadLibrary\n    lt_cv_dlopen_libs=\n    ;;\n\n  cygwin*)\n    lt_cv_dlopen=dlopen\n    lt_cv_dlopen_libs=\n    ;;\n\n  darwin*)\n    # if libdl is installed we need to link against it\n    AC_CHECK_LIB([dl], [dlopen],\n\t\t[lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl],[\n    lt_cv_dlopen=dyld\n    lt_cv_dlopen_libs=\n    lt_cv_dlopen_self=yes\n    ])\n    ;;\n\n  tpf*)\n    # Don't try to run any link tests for TPF.  We know it's impossible\n    # because TPF is a cross-compiler, and we know how we open DSOs.\n    lt_cv_dlopen=dlopen\n    lt_cv_dlopen_libs=\n    lt_cv_dlopen_self=no\n    ;;\n\n  *)\n    AC_CHECK_FUNC([shl_load],\n\t  [lt_cv_dlopen=shl_load],\n      [AC_CHECK_LIB([dld], [shl_load],\n\t    [lt_cv_dlopen=shl_load lt_cv_dlopen_libs=-ldld],\n\t[AC_CHECK_FUNC([dlopen],\n\t      [lt_cv_dlopen=dlopen],\n\t  [AC_CHECK_LIB([dl], [dlopen],\n\t\t[lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-ldl],\n\t    [AC_CHECK_LIB([svld], [dlopen],\n\t\t  [lt_cv_dlopen=dlopen lt_cv_dlopen_libs=-lsvld],\n\t      [AC_CHECK_LIB([dld], [dld_link],\n\t\t    [lt_cv_dlopen=dld_link lt_cv_dlopen_libs=-ldld])\n\t      ])\n\t    ])\n\t  ])\n\t])\n      ])\n    ;;\n  esac\n\n  if test no = \"$lt_cv_dlopen\"; then\n    enable_dlopen=no\n  else\n    enable_dlopen=yes\n  fi\n\n  case $lt_cv_dlopen in\n  dlopen)\n    save_CPPFLAGS=$CPPFLAGS\n    test yes = \"$ac_cv_header_dlfcn_h\" && CPPFLAGS=\"$CPPFLAGS -DHAVE_DLFCN_H\"\n\n    save_LDFLAGS=$LDFLAGS\n    wl=$lt_prog_compiler_wl eval LDFLAGS=\\\"\\$LDFLAGS $export_dynamic_flag_spec\\\"\n\n    save_LIBS=$LIBS\n    LIBS=\"$lt_cv_dlopen_libs $LIBS\"\n\n    AC_CACHE_CHECK([whether a program can dlopen itself],\n\t  lt_cv_dlopen_self, [dnl\n\t  _LT_TRY_DLOPEN_SELF(\n\t    lt_cv_dlopen_self=yes, lt_cv_dlopen_self=yes,\n\t    lt_cv_dlopen_self=no, lt_cv_dlopen_self=cross)\n    ])\n\n    if test yes = \"$lt_cv_dlopen_self\"; then\n      wl=$lt_prog_compiler_wl eval LDFLAGS=\\\"\\$LDFLAGS $lt_prog_compiler_static\\\"\n      AC_CACHE_CHECK([whether a statically linked program can dlopen itself],\n\t  lt_cv_dlopen_self_static, [dnl\n\t  _LT_TRY_DLOPEN_SELF(\n\t    lt_cv_dlopen_self_static=yes, lt_cv_dlopen_self_static=yes,\n\t    lt_cv_dlopen_self_static=no,  lt_cv_dlopen_self_static=cross)\n      ])\n    fi\n\n    CPPFLAGS=$save_CPPFLAGS\n    LDFLAGS=$save_LDFLAGS\n    LIBS=$save_LIBS\n    ;;\n  esac\n\n  case $lt_cv_dlopen_self in\n  yes|no) enable_dlopen_self=$lt_cv_dlopen_self ;;\n  *) enable_dlopen_self=unknown ;;\n  esac\n\n  case $lt_cv_dlopen_self_static in\n  yes|no) enable_dlopen_self_static=$lt_cv_dlopen_self_static ;;\n  *) enable_dlopen_self_static=unknown ;;\n  esac\nfi\n_LT_DECL([dlopen_support], [enable_dlopen], [0],\n\t [Whether dlopen is supported])\n_LT_DECL([dlopen_self], [enable_dlopen_self], [0],\n\t [Whether dlopen of programs is supported])\n_LT_DECL([dlopen_self_static], [enable_dlopen_self_static], [0],\n\t [Whether dlopen of statically linked programs is supported])\n])# LT_SYS_DLOPEN_SELF\n\n# Old name:\nAU_ALIAS([AC_LIBTOOL_DLOPEN_SELF], [LT_SYS_DLOPEN_SELF])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_LIBTOOL_DLOPEN_SELF], [])\n\n\n# _LT_COMPILER_C_O([TAGNAME])\n# ---------------------------\n# Check to see if options -c and -o are simultaneously supported by compiler.\n# This macro does not hard code the compiler like AC_PROG_CC_C_O.\nm4_defun([_LT_COMPILER_C_O],\n[m4_require([_LT_DECL_SED])dnl\nm4_require([_LT_FILEUTILS_DEFAULTS])dnl\nm4_require([_LT_TAG_COMPILER])dnl\nAC_CACHE_CHECK([if $compiler supports -c -o file.$ac_objext],\n  [_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)],\n  [_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=no\n   $RM -r conftest 2>/dev/null\n   mkdir conftest\n   cd conftest\n   mkdir out\n   echo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n\n   lt_compiler_flag=\"-o out/conftest2.$ac_objext\"\n   # Insert the option either (1) after the last *FLAGS variable, or\n   # (2) before a word containing \"conftest.\", or (3) at the end.\n   # Note that $ac_compile itself does not contain backslashes and begins\n   # with a dollar sign (not a hyphen), so the echo should work correctly.\n   lt_compile=`echo \"$ac_compile\" | $SED \\\n   -e 's:.*FLAGS}\\{0,1\\} :&$lt_compiler_flag :; t' \\\n   -e 's: [[^ ]]*conftest\\.: $lt_compiler_flag&:; t' \\\n   -e 's:$: $lt_compiler_flag:'`\n   (eval echo \"\\\"\\$as_me:$LINENO: $lt_compile\\\"\" >&AS_MESSAGE_LOG_FD)\n   (eval \"$lt_compile\" 2>out/conftest.err)\n   ac_status=$?\n   cat out/conftest.err >&AS_MESSAGE_LOG_FD\n   echo \"$as_me:$LINENO: \\$? = $ac_status\" >&AS_MESSAGE_LOG_FD\n   if (exit $ac_status) && test -s out/conftest2.$ac_objext\n   then\n     # The compiler can only warn and ignore the option if not recognized\n     # So say no if there are warnings\n     $ECHO \"$_lt_compiler_boilerplate\" | $SED '/^$/d' > out/conftest.exp\n     $SED '/^$/d; /^ *+/d' out/conftest.err >out/conftest.er2\n     if test ! -s out/conftest.er2 || diff out/conftest.exp out/conftest.er2 >/dev/null; then\n       _LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=yes\n     fi\n   fi\n   chmod u+w . 2>&AS_MESSAGE_LOG_FD\n   $RM conftest*\n   # SGI C++ compiler will create directory out/ii_files/ for\n   # template instantiation\n   test -d out/ii_files && $RM out/ii_files/* && rmdir out/ii_files\n   $RM out/* && rmdir out\n   cd ..\n   $RM -r conftest\n   $RM conftest*\n])\n_LT_TAGDECL([compiler_c_o], [lt_cv_prog_compiler_c_o], [1],\n\t[Does compiler simultaneously support -c and -o options?])\n])# _LT_COMPILER_C_O\n\n\n# _LT_COMPILER_FILE_LOCKS([TAGNAME])\n# ----------------------------------\n# Check to see if we can do hard links to lock some files if needed\nm4_defun([_LT_COMPILER_FILE_LOCKS],\n[m4_require([_LT_ENABLE_LOCK])dnl\nm4_require([_LT_FILEUTILS_DEFAULTS])dnl\n_LT_COMPILER_C_O([$1])\n\nhard_links=nottested\nif test no = \"$_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)\" && test no != \"$need_locks\"; then\n  # do not overwrite the value of need_locks provided by the user\n  AC_MSG_CHECKING([if we can lock with hard links])\n  hard_links=yes\n  $RM conftest*\n  ln conftest.a conftest.b 2>/dev/null && hard_links=no\n  touch conftest.a\n  ln conftest.a conftest.b 2>&5 || hard_links=no\n  ln conftest.a conftest.b 2>/dev/null && hard_links=no\n  AC_MSG_RESULT([$hard_links])\n  if test no = \"$hard_links\"; then\n    AC_MSG_WARN(['$CC' does not support '-c -o', so 'make -j' may be unsafe])\n    need_locks=warn\n  fi\nelse\n  need_locks=no\nfi\n_LT_DECL([], [need_locks], [1], [Must we lock files when doing compilation?])\n])# _LT_COMPILER_FILE_LOCKS\n\n\n# _LT_CHECK_OBJDIR\n# ----------------\nm4_defun([_LT_CHECK_OBJDIR],\n[AC_CACHE_CHECK([for objdir], [lt_cv_objdir],\n[rm -f .libs 2>/dev/null\nmkdir .libs 2>/dev/null\nif test -d .libs; then\n  lt_cv_objdir=.libs\nelse\n  # MS-DOS does not allow filenames that begin with a dot.\n  lt_cv_objdir=_libs\nfi\nrmdir .libs 2>/dev/null])\nobjdir=$lt_cv_objdir\n_LT_DECL([], [objdir], [0],\n         [The name of the directory that contains temporary libtool files])dnl\nm4_pattern_allow([LT_OBJDIR])dnl\nAC_DEFINE_UNQUOTED([LT_OBJDIR], \"$lt_cv_objdir/\",\n  [Define to the sub-directory where libtool stores uninstalled libraries.])\n])# _LT_CHECK_OBJDIR\n\n\n# _LT_LINKER_HARDCODE_LIBPATH([TAGNAME])\n# --------------------------------------\n# Check hardcoding attributes.\nm4_defun([_LT_LINKER_HARDCODE_LIBPATH],\n[AC_MSG_CHECKING([how to hardcode library paths into programs])\n_LT_TAGVAR(hardcode_action, $1)=\nif test -n \"$_LT_TAGVAR(hardcode_libdir_flag_spec, $1)\" ||\n   test -n \"$_LT_TAGVAR(runpath_var, $1)\" ||\n   test yes = \"$_LT_TAGVAR(hardcode_automatic, $1)\"; then\n\n  # We can hardcode non-existent directories.\n  if test no != \"$_LT_TAGVAR(hardcode_direct, $1)\" &&\n     # If the only mechanism to avoid hardcoding is shlibpath_var, we\n     # have to relink, otherwise we might link with an installed library\n     # when we should be linking with a yet-to-be-installed one\n     ## test no != \"$_LT_TAGVAR(hardcode_shlibpath_var, $1)\" &&\n     test no != \"$_LT_TAGVAR(hardcode_minus_L, $1)\"; then\n    # Linking always hardcodes the temporary library directory.\n    _LT_TAGVAR(hardcode_action, $1)=relink\n  else\n    # We can link without hardcoding, and we can hardcode nonexisting dirs.\n    _LT_TAGVAR(hardcode_action, $1)=immediate\n  fi\nelse\n  # We cannot hardcode anything, or else we can only hardcode existing\n  # directories.\n  _LT_TAGVAR(hardcode_action, $1)=unsupported\nfi\nAC_MSG_RESULT([$_LT_TAGVAR(hardcode_action, $1)])\n\nif test relink = \"$_LT_TAGVAR(hardcode_action, $1)\" ||\n   test yes = \"$_LT_TAGVAR(inherit_rpath, $1)\"; then\n  # Fast installation is not supported\n  enable_fast_install=no\nelif test yes = \"$shlibpath_overrides_runpath\" ||\n     test no = \"$enable_shared\"; then\n  # Fast installation is not necessary\n  enable_fast_install=needless\nfi\n_LT_TAGDECL([], [hardcode_action], [0],\n    [How to hardcode a shared library path into an executable])\n])# _LT_LINKER_HARDCODE_LIBPATH\n\n\n# _LT_CMD_STRIPLIB\n# ----------------\nm4_defun([_LT_CMD_STRIPLIB],\n[m4_require([_LT_DECL_EGREP])\nstriplib=\nold_striplib=\nAC_MSG_CHECKING([whether stripping libraries is possible])\nif test -z \"$STRIP\"; then\n  AC_MSG_RESULT([no])\nelse\n  if $STRIP -V 2>&1 | $GREP \"GNU strip\" >/dev/null; then\n    old_striplib=\"$STRIP --strip-debug\"\n    striplib=\"$STRIP --strip-unneeded\"\n    AC_MSG_RESULT([yes])\n  else\n    case $host_os in\n    darwin*)\n      # FIXME - insert some real tests, host_os isn't really good enough\n      striplib=\"$STRIP -x\"\n      old_striplib=\"$STRIP -S\"\n      AC_MSG_RESULT([yes])\n      ;;\n    freebsd*)\n      if $STRIP -V 2>&1 | $GREP \"elftoolchain\" >/dev/null; then\n        old_striplib=\"$STRIP --strip-debug\"\n        striplib=\"$STRIP --strip-unneeded\"\n        AC_MSG_RESULT([yes])\n      else\n        AC_MSG_RESULT([no])\n      fi\n      ;;\n    *)\n      AC_MSG_RESULT([no])\n      ;;\n    esac\n  fi\nfi\n_LT_DECL([], [old_striplib], [1], [Commands to strip libraries])\n_LT_DECL([], [striplib], [1])\n])# _LT_CMD_STRIPLIB\n\n\n# _LT_PREPARE_MUNGE_PATH_LIST\n# ---------------------------\n# Make sure func_munge_path_list() is defined correctly.\nm4_defun([_LT_PREPARE_MUNGE_PATH_LIST],\n[[# func_munge_path_list VARIABLE PATH\n# -----------------------------------\n# VARIABLE is name of variable containing _space_ separated list of\n# directories to be munged by the contents of PATH, which is string\n# having a format:\n# \"DIR[:DIR]:\"\n#       string \"DIR[ DIR]\" will be prepended to VARIABLE\n# \":DIR[:DIR]\"\n#       string \"DIR[ DIR]\" will be appended to VARIABLE\n# \"DIRP[:DIRP]::[DIRA:]DIRA\"\n#       string \"DIRP[ DIRP]\" will be prepended to VARIABLE and string\n#       \"DIRA[ DIRA]\" will be appended to VARIABLE\n# \"DIR[:DIR]\"\n#       VARIABLE will be replaced by \"DIR[ DIR]\"\nfunc_munge_path_list ()\n{\n    case x@S|@2 in\n    x)\n        ;;\n    *:)\n        eval @S|@1=\\\"`$ECHO @S|@2 | $SED 's/:/ /g'` \\@S|@@S|@1\\\"\n        ;;\n    x:*)\n        eval @S|@1=\\\"\\@S|@@S|@1 `$ECHO @S|@2 | $SED 's/:/ /g'`\\\"\n        ;;\n    *::*)\n        eval @S|@1=\\\"\\@S|@@S|@1\\ `$ECHO @S|@2 | $SED -e 's/.*:://' -e 's/:/ /g'`\\\"\n        eval @S|@1=\\\"`$ECHO @S|@2 | $SED -e 's/::.*//' -e 's/:/ /g'`\\ \\@S|@@S|@1\\\"\n        ;;\n    *)\n        eval @S|@1=\\\"`$ECHO @S|@2 | $SED 's/:/ /g'`\\\"\n        ;;\n    esac\n}\n]])# _LT_PREPARE_PATH_LIST\n\n\n# _LT_SYS_DYNAMIC_LINKER([TAG])\n# -----------------------------\n# PORTME Fill in your ld.so characteristics\nm4_defun([_LT_SYS_DYNAMIC_LINKER],\n[AC_REQUIRE([AC_CANONICAL_HOST])dnl\nm4_require([_LT_DECL_EGREP])dnl\nm4_require([_LT_FILEUTILS_DEFAULTS])dnl\nm4_require([_LT_DECL_OBJDUMP])dnl\nm4_require([_LT_DECL_SED])dnl\nm4_require([_LT_CHECK_SHELL_FEATURES])dnl\nm4_require([_LT_PREPARE_MUNGE_PATH_LIST])dnl\nAC_MSG_CHECKING([dynamic linker characteristics])\nm4_if([$1],\n\t[], [\nif test yes = \"$GCC\"; then\n  case $host_os in\n    darwin*) lt_awk_arg='/^libraries:/,/LR/' ;;\n    *) lt_awk_arg='/^libraries:/' ;;\n  esac\n  case $host_os in\n    mingw* | cegcc*) lt_sed_strip_eq='s|=\\([[A-Za-z]]:\\)|\\1|g' ;;\n    *) lt_sed_strip_eq='s|=/|/|g' ;;\n  esac\n  lt_search_path_spec=`$CC -print-search-dirs | awk $lt_awk_arg | $SED -e \"s/^libraries://\" -e $lt_sed_strip_eq`\n  case $lt_search_path_spec in\n  *\\;*)\n    # if the path contains \";\" then we assume it to be the separator\n    # otherwise default to the standard path separator (i.e. \":\") - it is\n    # assumed that no part of a normal pathname contains \";\" but that should\n    # okay in the real world where \";\" in dirpaths is itself problematic.\n    lt_search_path_spec=`$ECHO \"$lt_search_path_spec\" | $SED 's/;/ /g'`\n    ;;\n  *)\n    lt_search_path_spec=`$ECHO \"$lt_search_path_spec\" | $SED \"s/$PATH_SEPARATOR/ /g\"`\n    ;;\n  esac\n  # Ok, now we have the path, separated by spaces, we can step through it\n  # and add multilib dir if necessary...\n  lt_tmp_lt_search_path_spec=\n  lt_multi_os_dir=/`$CC $CPPFLAGS $CFLAGS $LDFLAGS -print-multi-os-directory 2>/dev/null`\n  # ...but if some path component already ends with the multilib dir we assume\n  # that all is fine and trust -print-search-dirs as is (GCC 4.2? or newer).\n  case \"$lt_multi_os_dir; $lt_search_path_spec \" in\n  \"/; \"* | \"/.; \"* | \"/./; \"* | *\"$lt_multi_os_dir \"* | *\"$lt_multi_os_dir/ \"*)\n    lt_multi_os_dir=\n    ;;\n  esac\n  for lt_sys_path in $lt_search_path_spec; do\n    if test -d \"$lt_sys_path$lt_multi_os_dir\"; then\n      lt_tmp_lt_search_path_spec=\"$lt_tmp_lt_search_path_spec $lt_sys_path$lt_multi_os_dir\"\n    elif test -n \"$lt_multi_os_dir\"; then\n      test -d \"$lt_sys_path\" && \\\n\tlt_tmp_lt_search_path_spec=\"$lt_tmp_lt_search_path_spec $lt_sys_path\"\n    fi\n  done\n  lt_search_path_spec=`$ECHO \"$lt_tmp_lt_search_path_spec\" | awk '\nBEGIN {RS = \" \"; FS = \"/|\\n\";} {\n  lt_foo = \"\";\n  lt_count = 0;\n  for (lt_i = NF; lt_i > 0; lt_i--) {\n    if ($lt_i != \"\" && $lt_i != \".\") {\n      if ($lt_i == \"..\") {\n        lt_count++;\n      } else {\n        if (lt_count == 0) {\n          lt_foo = \"/\" $lt_i lt_foo;\n        } else {\n          lt_count--;\n        }\n      }\n    }\n  }\n  if (lt_foo != \"\") { lt_freq[[lt_foo]]++; }\n  if (lt_freq[[lt_foo]] == 1) { print lt_foo; }\n}'`\n  # AWK program above erroneously prepends '/' to C:/dos/paths\n  # for these hosts.\n  case $host_os in\n    mingw* | cegcc*) lt_search_path_spec=`$ECHO \"$lt_search_path_spec\" |\\\n      $SED 's|/\\([[A-Za-z]]:\\)|\\1|g'` ;;\n  esac\n  sys_lib_search_path_spec=`$ECHO \"$lt_search_path_spec\" | $lt_NL2SP`\nelse\n  sys_lib_search_path_spec=\"/lib /usr/lib /usr/local/lib\"\nfi])\nlibrary_names_spec=\nlibname_spec='lib$name'\nsoname_spec=\nshrext_cmds=.so\npostinstall_cmds=\npostuninstall_cmds=\nfinish_cmds=\nfinish_eval=\nshlibpath_var=\nshlibpath_overrides_runpath=unknown\nversion_type=none\ndynamic_linker=\"$host_os ld.so\"\nsys_lib_dlsearch_path_spec=\"/lib /usr/lib\"\nneed_lib_prefix=unknown\nhardcode_into_libs=no\n\n# when you set need_version to no, make sure it does not cause -set_version\n# flags to be left without arguments\nneed_version=unknown\n\nAC_ARG_VAR([LT_SYS_LIBRARY_PATH],\n[User-defined run-time library search path.])\n\ncase $host_os in\naix3*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname.a'\n  shlibpath_var=LIBPATH\n\n  # AIX 3 has no versioning support, so we append a major version to the name.\n  soname_spec='$libname$release$shared_ext$major'\n  ;;\n\naix[[4-9]]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  hardcode_into_libs=yes\n  if test ia64 = \"$host_cpu\"; then\n    # AIX 5 supports IA64\n    library_names_spec='$libname$release$shared_ext$major $libname$release$shared_ext$versuffix $libname$shared_ext'\n    shlibpath_var=LD_LIBRARY_PATH\n  else\n    # With GCC up to 2.95.x, collect2 would create an import file\n    # for dependence libraries.  The import file would start with\n    # the line '#! .'.  This would cause the generated library to\n    # depend on '.', always an invalid library.  This was fixed in\n    # development snapshots of GCC prior to 3.0.\n    case $host_os in\n      aix4 | aix4.[[01]] | aix4.[[01]].*)\n      if { echo '#if __GNUC__ > 2 || (__GNUC__ == 2 && __GNUC_MINOR__ >= 97)'\n\t   echo ' yes '\n\t   echo '#endif'; } | $CC -E - | $GREP yes > /dev/null; then\n\t:\n      else\n\tcan_build_shared=no\n      fi\n      ;;\n    esac\n    # Using Import Files as archive members, it is possible to support\n    # filename-based versioning of shared library archives on AIX. While\n    # this would work for both with and without runtime linking, it will\n    # prevent static linking of such archives. So we do filename-based\n    # shared library versioning with .so extension only, which is used\n    # when both runtime linking and shared linking is enabled.\n    # Unfortunately, runtime linking may impact performance, so we do\n    # not want this to be the default eventually. Also, we use the\n    # versioned .so libs for executables only if there is the -brtl\n    # linker flag in LDFLAGS as well, or --with-aix-soname=svr4 only.\n    # To allow for filename-based versioning support, we need to create\n    # libNAME.so.V as an archive file, containing:\n    # *) an Import File, referring to the versioned filename of the\n    #    archive as well as the shared archive member, telling the\n    #    bitwidth (32 or 64) of that shared object, and providing the\n    #    list of exported symbols of that shared object, eventually\n    #    decorated with the 'weak' keyword\n    # *) the shared object with the F_LOADONLY flag set, to really avoid\n    #    it being seen by the linker.\n    # At run time we better use the real file rather than another symlink,\n    # but for link time we create the symlink libNAME.so -> libNAME.so.V\n\n    case $with_aix_soname,$aix_use_runtimelinking in\n    # AIX (on Power*) has no versioning support, so currently we cannot hardcode correct\n    # soname into executable. Probably we can add versioning support to\n    # collect2, so additional links can be useful in future.\n    aix,yes) # traditional libtool\n      dynamic_linker='AIX unversionable lib.so'\n      # If using run time linking (on AIX 4.2 or later) use lib<name>.so\n      # instead of lib<name>.a to let people know that these are not\n      # typical AIX shared libraries.\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n      ;;\n    aix,no) # traditional AIX only\n      dynamic_linker='AIX lib.a[(]lib.so.V[)]'\n      # We preserve .a as extension for shared libraries through AIX4.2\n      # and later when we are not doing run time linking.\n      library_names_spec='$libname$release.a $libname.a'\n      soname_spec='$libname$release$shared_ext$major'\n      ;;\n    svr4,*) # full svr4 only\n      dynamic_linker=\"AIX lib.so.V[(]$shared_archive_member_spec.o[)]\"\n      library_names_spec='$libname$release$shared_ext$major $libname$shared_ext'\n      # We do not specify a path in Import Files, so LIBPATH fires.\n      shlibpath_overrides_runpath=yes\n      ;;\n    *,yes) # both, prefer svr4\n      dynamic_linker=\"AIX lib.so.V[(]$shared_archive_member_spec.o[)], lib.a[(]lib.so.V[)]\"\n      library_names_spec='$libname$release$shared_ext$major $libname$shared_ext'\n      # unpreferred sharedlib libNAME.a needs extra handling\n      postinstall_cmds='test -n \"$linkname\" || linkname=\"$realname\"~func_stripname \"\" \".so\" \"$linkname\"~$install_shared_prog \"$dir/$func_stripname_result.$libext\" \"$destdir/$func_stripname_result.$libext\"~test -z \"$tstripme\" || test -z \"$striplib\" || $striplib \"$destdir/$func_stripname_result.$libext\"'\n      postuninstall_cmds='for n in $library_names $old_library; do :; done~func_stripname \"\" \".so\" \"$n\"~test \"$func_stripname_result\" = \"$n\" || func_append rmfiles \" $odir/$func_stripname_result.$libext\"'\n      # We do not specify a path in Import Files, so LIBPATH fires.\n      shlibpath_overrides_runpath=yes\n      ;;\n    *,no) # both, prefer aix\n      dynamic_linker=\"AIX lib.a[(]lib.so.V[)], lib.so.V[(]$shared_archive_member_spec.o[)]\"\n      library_names_spec='$libname$release.a $libname.a'\n      soname_spec='$libname$release$shared_ext$major'\n      # unpreferred sharedlib libNAME.so.V and symlink libNAME.so need extra handling\n      postinstall_cmds='test -z \"$dlname\" || $install_shared_prog $dir/$dlname $destdir/$dlname~test -z \"$tstripme\" || test -z \"$striplib\" || $striplib $destdir/$dlname~test -n \"$linkname\" || linkname=$realname~func_stripname \"\" \".a\" \"$linkname\"~(cd \"$destdir\" && $LN_S -f $dlname $func_stripname_result.so)'\n      postuninstall_cmds='test -z \"$dlname\" || func_append rmfiles \" $odir/$dlname\"~for n in $old_library $library_names; do :; done~func_stripname \"\" \".a\" \"$n\"~func_append rmfiles \" $odir/$func_stripname_result.so\"'\n      ;;\n    esac\n    shlibpath_var=LIBPATH\n  fi\n  ;;\n\namigaos*)\n  case $host_cpu in\n  powerpc)\n    # Since July 2007 AmigaOS4 officially supports .so libraries.\n    # When compiling the executable, add -use-dynld -Lsobjs: to the compileline.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    ;;\n  m68k)\n    library_names_spec='$libname.ixlibrary $libname.a'\n    # Create ${libname}_ixlibrary.a entries in /sys/libs.\n    finish_eval='for lib in `ls $libdir/*.ixlibrary 2>/dev/null`; do libname=`func_echo_all \"$lib\" | $SED '\\''s%^.*/\\([[^/]]*\\)\\.ixlibrary$%\\1%'\\''`; $RM /sys/libs/${libname}_ixlibrary.a; $show \"cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a\"; cd /sys/libs && $LN_S $lib ${libname}_ixlibrary.a || exit 1; done'\n    ;;\n  esac\n  ;;\n\nbeos*)\n  library_names_spec='$libname$shared_ext'\n  dynamic_linker=\"$host_os ld.so\"\n  shlibpath_var=LIBRARY_PATH\n  ;;\n\nbsdi[[45]]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  sys_lib_search_path_spec=\"/shlib /usr/lib /usr/X11/lib /usr/contrib/lib /lib /usr/local/lib\"\n  sys_lib_dlsearch_path_spec=\"/shlib /usr/lib /usr/local/lib\"\n  # the default ld.so.conf also contains /usr/contrib/lib and\n  # /usr/X11R6/lib (/usr/X11 is a link to /usr/X11R6), but let us allow\n  # libtool to hard-code these into programs\n  ;;\n\ncygwin* | mingw* | pw32* | cegcc*)\n  version_type=windows\n  shrext_cmds=.dll\n  need_version=no\n  need_lib_prefix=no\n\n  case $GCC,$cc_basename in\n  yes,*)\n    # gcc\n    library_names_spec='$libname.dll.a'\n    # DLL is installed to $(libdir)/../bin by postinstall_cmds\n    postinstall_cmds='base_file=`basename \\$file`~\n      dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; echo \\$dlname'\\''`~\n      dldir=$destdir/`dirname \\$dlpath`~\n      test -d \\$dldir || mkdir -p \\$dldir~\n      $install_prog $dir/$dlname \\$dldir/$dlname~\n      chmod a+x \\$dldir/$dlname~\n      if test -n '\\''$stripme'\\'' && test -n '\\''$striplib'\\''; then\n        eval '\\''$striplib \\$dldir/$dlname'\\'' || exit \\$?;\n      fi'\n    postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; echo \\$dlname'\\''`~\n      dlpath=$dir/\\$dldll~\n       $RM \\$dlpath'\n    shlibpath_overrides_runpath=yes\n\n    case $host_os in\n    cygwin*)\n      # Cygwin DLLs use 'cyg' prefix rather than 'lib'\n      soname_spec='`echo $libname | $SED -e 's/^lib/cyg/'``echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext'\nm4_if([$1], [],[\n      sys_lib_search_path_spec=\"$sys_lib_search_path_spec /usr/lib/w32api\"])\n      ;;\n    mingw* | cegcc*)\n      # MinGW DLLs use traditional 'lib' prefix\n      soname_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext'\n      ;;\n    pw32*)\n      # pw32 DLLs use 'pw' prefix rather than 'lib'\n      library_names_spec='`echo $libname | $SED -e 's/^lib/pw/'``echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext'\n      ;;\n    esac\n    dynamic_linker='Win32 ld.exe'\n    ;;\n\n  *,cl* | *,icl*)\n    # Native MSVC or ICC\n    libname_spec='$name'\n    soname_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext'\n    library_names_spec='$libname.dll.lib'\n\n    case $build_os in\n    mingw*)\n      sys_lib_search_path_spec=\n      lt_save_ifs=$IFS\n      IFS=';'\n      for lt_path in $LIB\n      do\n        IFS=$lt_save_ifs\n        # Let DOS variable expansion print the short 8.3 style file name.\n        lt_path=`cd \"$lt_path\" 2>/dev/null && cmd //C \"for %i in (\".\") do @echo %~si\"`\n        sys_lib_search_path_spec=\"$sys_lib_search_path_spec $lt_path\"\n      done\n      IFS=$lt_save_ifs\n      # Convert to MSYS style.\n      sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e 's|\\\\\\\\|/|g' -e 's| \\\\([[a-zA-Z]]\\\\):| /\\\\1|g' -e 's|^ ||'`\n      ;;\n    cygwin*)\n      # Convert to unix form, then to dos form, then back to unix form\n      # but this time dos style (no spaces!) so that the unix form looks\n      # like /cygdrive/c/PROGRA~1:/cygdr...\n      sys_lib_search_path_spec=`cygpath --path --unix \"$LIB\"`\n      sys_lib_search_path_spec=`cygpath --path --dos \"$sys_lib_search_path_spec\" 2>/dev/null`\n      sys_lib_search_path_spec=`cygpath --path --unix \"$sys_lib_search_path_spec\" | $SED -e \"s/$PATH_SEPARATOR/ /g\"`\n      ;;\n    *)\n      sys_lib_search_path_spec=$LIB\n      if $ECHO \"$sys_lib_search_path_spec\" | [$GREP ';[c-zC-Z]:/' >/dev/null]; then\n        # It is most probably a Windows format PATH.\n        sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e 's/;/ /g'`\n      else\n        sys_lib_search_path_spec=`$ECHO \"$sys_lib_search_path_spec\" | $SED -e \"s/$PATH_SEPARATOR/ /g\"`\n      fi\n      # FIXME: find the short name or the path components, as spaces are\n      # common. (e.g. \"Program Files\" -> \"PROGRA~1\")\n      ;;\n    esac\n\n    # DLL is installed to $(libdir)/../bin by postinstall_cmds\n    postinstall_cmds='base_file=`basename \\$file`~\n      dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; echo \\$dlname'\\''`~\n      dldir=$destdir/`dirname \\$dlpath`~\n      test -d \\$dldir || mkdir -p \\$dldir~\n      $install_prog $dir/$dlname \\$dldir/$dlname'\n    postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; echo \\$dlname'\\''`~\n      dlpath=$dir/\\$dldll~\n       $RM \\$dlpath'\n    shlibpath_overrides_runpath=yes\n    dynamic_linker='Win32 link.exe'\n    ;;\n\n  *)\n    # Assume MSVC and ICC wrapper\n    library_names_spec='$libname`echo $release | $SED -e 's/[[.]]/-/g'`$versuffix$shared_ext $libname.lib'\n    dynamic_linker='Win32 ld.exe'\n    ;;\n  esac\n  # FIXME: first we should search . and the directory the executable is in\n  shlibpath_var=PATH\n  ;;\n\ndarwin* | rhapsody*)\n  dynamic_linker=\"$host_os dyld\"\n  version_type=darwin\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$major$shared_ext $libname$shared_ext'\n  soname_spec='$libname$release$major$shared_ext'\n  shlibpath_overrides_runpath=yes\n  shlibpath_var=DYLD_LIBRARY_PATH\n  shrext_cmds='`test .$module = .yes && echo .so || echo .dylib`'\nm4_if([$1], [],[\n  sys_lib_search_path_spec=\"$sys_lib_search_path_spec /usr/local/lib\"])\n  sys_lib_dlsearch_path_spec='/usr/local/lib /lib /usr/lib'\n  ;;\n\ndgux*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  ;;\n\nfreebsd* | dragonfly* | midnightbsd*)\n  # DragonFly does not have aout.  When/if they implement a new\n  # versioning mechanism, adjust this.\n  if test -x /usr/bin/objformat; then\n    objformat=`/usr/bin/objformat`\n  else\n    case $host_os in\n    freebsd[[23]].*) objformat=aout ;;\n    *) objformat=elf ;;\n    esac\n  fi\n  version_type=freebsd-$objformat\n  case $version_type in\n    freebsd-elf*)\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n      soname_spec='$libname$release$shared_ext$major'\n      need_version=no\n      need_lib_prefix=no\n      ;;\n    freebsd-*)\n      library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n      need_version=yes\n      ;;\n  esac\n  shlibpath_var=LD_LIBRARY_PATH\n  case $host_os in\n  freebsd2.*)\n    shlibpath_overrides_runpath=yes\n    ;;\n  freebsd3.[[01]]* | freebsdelf3.[[01]]*)\n    shlibpath_overrides_runpath=yes\n    hardcode_into_libs=yes\n    ;;\n  freebsd3.[[2-9]]* | freebsdelf3.[[2-9]]* | \\\n  freebsd4.[[0-5]] | freebsdelf4.[[0-5]] | freebsd4.1.1 | freebsdelf4.1.1)\n    shlibpath_overrides_runpath=no\n    hardcode_into_libs=yes\n    ;;\n  *) # from 4.6 on, and DragonFly\n    shlibpath_overrides_runpath=yes\n    hardcode_into_libs=yes\n    ;;\n  esac\n  ;;\n\nhaiku*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  dynamic_linker=\"$host_os runtime_loader\"\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  sys_lib_dlsearch_path_spec='/boot/home/config/lib /boot/common/lib /boot/system/lib'\n  hardcode_into_libs=yes\n  ;;\n\nhpux9* | hpux10* | hpux11*)\n  # Give a soname corresponding to the major version so that dld.sl refuses to\n  # link against other versions.\n  version_type=sunos\n  need_lib_prefix=no\n  need_version=no\n  case $host_cpu in\n  ia64*)\n    shrext_cmds='.so'\n    hardcode_into_libs=yes\n    dynamic_linker=\"$host_os dld.so\"\n    shlibpath_var=LD_LIBRARY_PATH\n    shlibpath_overrides_runpath=yes # Unless +noenvvar is specified.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    if test 32 = \"$HPUX_IA64_MODE\"; then\n      sys_lib_search_path_spec=\"/usr/lib/hpux32 /usr/local/lib/hpux32 /usr/local/lib\"\n      sys_lib_dlsearch_path_spec=/usr/lib/hpux32\n    else\n      sys_lib_search_path_spec=\"/usr/lib/hpux64 /usr/local/lib/hpux64\"\n      sys_lib_dlsearch_path_spec=/usr/lib/hpux64\n    fi\n    ;;\n  hppa*64*)\n    shrext_cmds='.sl'\n    hardcode_into_libs=yes\n    dynamic_linker=\"$host_os dld.sl\"\n    shlibpath_var=LD_LIBRARY_PATH # How should we handle SHLIB_PATH\n    shlibpath_overrides_runpath=yes # Unless +noenvvar is specified.\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    sys_lib_search_path_spec=\"/usr/lib/pa20_64 /usr/ccs/lib/pa20_64\"\n    sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n    ;;\n  *)\n    shrext_cmds='.sl'\n    dynamic_linker=\"$host_os dld.sl\"\n    shlibpath_var=SHLIB_PATH\n    shlibpath_overrides_runpath=no # +s is required to enable SHLIB_PATH\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    ;;\n  esac\n  # HP-UX runs *really* slowly unless shared libraries are mode 555, ...\n  postinstall_cmds='chmod 555 $lib'\n  # or fails outright, so override atomically:\n  install_override_mode=555\n  ;;\n\ninterix[[3-9]]*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  dynamic_linker='Interix 3.x ld.so.1 (PE, like ELF)'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  ;;\n\nirix5* | irix6* | nonstopux*)\n  case $host_os in\n    nonstopux*) version_type=nonstopux ;;\n    *)\n\tif test yes = \"$lt_cv_prog_gnu_ld\"; then\n\t\tversion_type=linux # correct to gnu/linux during the next big refactor\n\telse\n\t\tversion_type=irix\n\tfi ;;\n  esac\n  need_lib_prefix=no\n  need_version=no\n  soname_spec='$libname$release$shared_ext$major'\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$release$shared_ext $libname$shared_ext'\n  case $host_os in\n  irix5* | nonstopux*)\n    libsuff= shlibsuff=\n    ;;\n  *)\n    case $LD in # libtool.m4 will add one of these switches to LD\n    *-32|*\"-32 \"|*-melf32bsmip|*\"-melf32bsmip \")\n      libsuff= shlibsuff= libmagic=32-bit;;\n    *-n32|*\"-n32 \"|*-melf32bmipn32|*\"-melf32bmipn32 \")\n      libsuff=32 shlibsuff=N32 libmagic=N32;;\n    *-64|*\"-64 \"|*-melf64bmip|*\"-melf64bmip \")\n      libsuff=64 shlibsuff=64 libmagic=64-bit;;\n    *) libsuff= shlibsuff= libmagic=never-match;;\n    esac\n    ;;\n  esac\n  shlibpath_var=LD_LIBRARY${shlibsuff}_PATH\n  shlibpath_overrides_runpath=no\n  sys_lib_search_path_spec=\"/usr/lib$libsuff /lib$libsuff /usr/local/lib$libsuff\"\n  sys_lib_dlsearch_path_spec=\"/usr/lib$libsuff /lib$libsuff\"\n  hardcode_into_libs=yes\n  ;;\n\n# No shared lib support for Linux oldld, aout, or coff.\nlinux*oldld* | linux*aout* | linux*coff*)\n  dynamic_linker=no\n  ;;\n\nlinux*android*)\n  version_type=none # Android doesn't support versioned libraries.\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext'\n  soname_spec='$libname$release$shared_ext'\n  finish_cmds=\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n\n  # This implies no fast_install, which is unacceptable.\n  # Some rework will be needed to allow for fast_install\n  # before this can be enabled.\n  hardcode_into_libs=yes\n\n  dynamic_linker='Android linker'\n  # Don't embed -rpath directories since the linker doesn't support them.\n  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n  ;;\n\n# This must be glibc/ELF.\nlinux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -n $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n\n  # Some binutils ld are patched to set DT_RUNPATH\n  AC_CACHE_VAL([lt_cv_shlibpath_overrides_runpath],\n    [lt_cv_shlibpath_overrides_runpath=no\n    save_LDFLAGS=$LDFLAGS\n    save_libdir=$libdir\n    eval \"libdir=/foo; wl=\\\"$_LT_TAGVAR(lt_prog_compiler_wl, $1)\\\"; \\\n\t LDFLAGS=\\\"\\$LDFLAGS $_LT_TAGVAR(hardcode_libdir_flag_spec, $1)\\\"\"\n    AC_LINK_IFELSE([AC_LANG_PROGRAM([],[])],\n      [AS_IF([ ($OBJDUMP -p conftest$ac_exeext) 2>/dev/null | grep \"RUNPATH.*$libdir\" >/dev/null],\n\t [lt_cv_shlibpath_overrides_runpath=yes])])\n    LDFLAGS=$save_LDFLAGS\n    libdir=$save_libdir\n    ])\n  shlibpath_overrides_runpath=$lt_cv_shlibpath_overrides_runpath\n\n  # This implies no fast_install, which is unacceptable.\n  # Some rework will be needed to allow for fast_install\n  # before this can be enabled.\n  hardcode_into_libs=yes\n\n  # Ideally, we could use ldconfig to report *all* directores which are\n  # searched for libraries, however this is still not possible.  Aside from not\n  # being certain /sbin/ldconfig is available, command\n  # 'ldconfig -N -X -v | grep ^/' on 64bit Fedora does not report /usr/lib64,\n  # even though it is searched at run-time.  Try to do the best guess by\n  # appending ld.so.conf contents (and includes) to the search path.\n  if test -f /etc/ld.so.conf; then\n    lt_ld_extra=`awk '/^include / { system(sprintf(\"cd /etc; cat %s 2>/dev/null\", \\[$]2)); skip = 1; } { if (!skip) print \\[$]0; skip = 0; }' < /etc/ld.so.conf | $SED -e 's/#.*//;/^[\t ]*hwcap[\t ]/d;s/[:,\t]/ /g;s/=[^=]*$//;s/=[^= ]* / /g;s/\"//g;/^$/d' | tr '\\n' ' '`\n    sys_lib_dlsearch_path_spec=\"/lib /usr/lib $lt_ld_extra\"\n  fi\n\n  # We used to test for /lib/ld.so.1 and disable shared libraries on\n  # powerpc, because MkLinux only supported shared libraries with the\n  # GNU dynamic linker.  Since this was broken with cross compilers,\n  # most powerpc-linux boxes support dynamic linking these days and\n  # people can always --disable-shared, the test was removed, and we\n  # assume the GNU/Linux dynamic linker is in use.\n  dynamic_linker='GNU/Linux ld.so'\n  ;;\n\nnetbsd*)\n  version_type=sunos\n  need_lib_prefix=no\n  need_version=no\n  if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n    finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -m $libdir'\n    dynamic_linker='NetBSD (a.out) ld.so'\n  else\n    library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n    soname_spec='$libname$release$shared_ext$major'\n    dynamic_linker='NetBSD ld.elf_so'\n  fi\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  ;;\n\nnewsos6)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  ;;\n\n*nto* | *qnx*)\n  version_type=qnx\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  dynamic_linker='ldqnx.so'\n  ;;\n\nopenbsd* | bitrig*)\n  version_type=sunos\n  sys_lib_dlsearch_path_spec=/usr/lib\n  need_lib_prefix=no\n  if test -z \"`echo __ELF__ | $CC -E - | $GREP __ELF__`\"; then\n    need_version=no\n  else\n    need_version=yes\n  fi\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n  finish_cmds='PATH=\"\\$PATH:/sbin\" ldconfig -m $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  ;;\n\nos2*)\n  libname_spec='$name'\n  version_type=windows\n  shrext_cmds=.dll\n  need_version=no\n  need_lib_prefix=no\n  # OS/2 can only load a DLL with a base name of 8 characters or less.\n  soname_spec='`test -n \"$os2dllname\" && libname=\"$os2dllname\";\n    v=$($ECHO $release$versuffix | tr -d .-);\n    n=$($ECHO $libname | cut -b -$((8 - ${#v})) | tr . _);\n    $ECHO $n$v`$shared_ext'\n  library_names_spec='${libname}_dll.$libext'\n  dynamic_linker='OS/2 ld.exe'\n  shlibpath_var=BEGINLIBPATH\n  sys_lib_search_path_spec=\"/lib /usr/lib /usr/local/lib\"\n  sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n  postinstall_cmds='base_file=`basename \\$file`~\n    dlpath=`$SHELL 2>&1 -c '\\''. $dir/'\\''\\$base_file'\\''i; $ECHO \\$dlname'\\''`~\n    dldir=$destdir/`dirname \\$dlpath`~\n    test -d \\$dldir || mkdir -p \\$dldir~\n    $install_prog $dir/$dlname \\$dldir/$dlname~\n    chmod a+x \\$dldir/$dlname~\n    if test -n '\\''$stripme'\\'' && test -n '\\''$striplib'\\''; then\n      eval '\\''$striplib \\$dldir/$dlname'\\'' || exit \\$?;\n    fi'\n  postuninstall_cmds='dldll=`$SHELL 2>&1 -c '\\''. $file; $ECHO \\$dlname'\\''`~\n    dlpath=$dir/\\$dldll~\n    $RM \\$dlpath'\n  ;;\n\nosf3* | osf4* | osf5*)\n  version_type=osf\n  need_lib_prefix=no\n  need_version=no\n  soname_spec='$libname$release$shared_ext$major'\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  sys_lib_search_path_spec=\"/usr/shlib /usr/ccs/lib /usr/lib/cmplrs/cc /usr/lib /usr/local/lib /var/shlib\"\n  sys_lib_dlsearch_path_spec=$sys_lib_search_path_spec\n  ;;\n\nrdos*)\n  dynamic_linker=no\n  ;;\n\nsolaris*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  # ldd complains unless libraries are executable\n  postinstall_cmds='chmod +x $lib'\n  ;;\n\nsunos4*)\n  version_type=sunos\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$shared_ext$versuffix'\n  finish_cmds='PATH=\"\\$PATH:/usr/etc\" ldconfig $libdir'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  if test yes = \"$with_gnu_ld\"; then\n    need_lib_prefix=no\n  fi\n  need_version=yes\n  ;;\n\nsysv4 | sysv4.3*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  case $host_vendor in\n    sni)\n      shlibpath_overrides_runpath=no\n      need_lib_prefix=no\n      runpath_var=LD_RUN_PATH\n      ;;\n    siemens)\n      need_lib_prefix=no\n      ;;\n    motorola)\n      need_lib_prefix=no\n      need_version=no\n      shlibpath_overrides_runpath=no\n      sys_lib_search_path_spec='/lib /usr/lib /usr/ccs/lib'\n      ;;\n  esac\n  ;;\n\nsysv4*MP*)\n  if test -d /usr/nec; then\n    version_type=linux # correct to gnu/linux during the next big refactor\n    library_names_spec='$libname$shared_ext.$versuffix $libname$shared_ext.$major $libname$shared_ext'\n    soname_spec='$libname$shared_ext.$major'\n    shlibpath_var=LD_LIBRARY_PATH\n  fi\n  ;;\n\nsysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*)\n  version_type=sco\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=yes\n  hardcode_into_libs=yes\n  if test yes = \"$with_gnu_ld\"; then\n    sys_lib_search_path_spec='/usr/local/lib /usr/gnu/lib /usr/ccs/lib /usr/lib /lib'\n  else\n    sys_lib_search_path_spec='/usr/ccs/lib /usr/lib'\n    case $host_os in\n      sco3.2v5*)\n        sys_lib_search_path_spec=\"$sys_lib_search_path_spec /lib\"\n\t;;\n    esac\n  fi\n  sys_lib_dlsearch_path_spec='/usr/lib'\n  ;;\n\ntpf*)\n  # TPF is a cross-target only.  Preferred cross-host = GNU/Linux.\n  version_type=linux # correct to gnu/linux during the next big refactor\n  need_lib_prefix=no\n  need_version=no\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  shlibpath_var=LD_LIBRARY_PATH\n  shlibpath_overrides_runpath=no\n  hardcode_into_libs=yes\n  ;;\n\nuts4*)\n  version_type=linux # correct to gnu/linux during the next big refactor\n  library_names_spec='$libname$release$shared_ext$versuffix $libname$release$shared_ext$major $libname$shared_ext'\n  soname_spec='$libname$release$shared_ext$major'\n  shlibpath_var=LD_LIBRARY_PATH\n  ;;\n\n*)\n  dynamic_linker=no\n  ;;\nesac\nAC_MSG_RESULT([$dynamic_linker])\ntest no = \"$dynamic_linker\" && can_build_shared=no\n\nvariables_saved_for_relink=\"PATH $shlibpath_var $runpath_var\"\nif test yes = \"$GCC\"; then\n  variables_saved_for_relink=\"$variables_saved_for_relink GCC_EXEC_PREFIX COMPILER_PATH LIBRARY_PATH\"\nfi\n\nif test set = \"${lt_cv_sys_lib_search_path_spec+set}\"; then\n  sys_lib_search_path_spec=$lt_cv_sys_lib_search_path_spec\nfi\n\nif test set = \"${lt_cv_sys_lib_dlsearch_path_spec+set}\"; then\n  sys_lib_dlsearch_path_spec=$lt_cv_sys_lib_dlsearch_path_spec\nfi\n\n# remember unaugmented sys_lib_dlsearch_path content for libtool script decls...\nconfigure_time_dlsearch_path=$sys_lib_dlsearch_path_spec\n\n# ... but it needs LT_SYS_LIBRARY_PATH munging for other configure-time code\nfunc_munge_path_list sys_lib_dlsearch_path_spec \"$LT_SYS_LIBRARY_PATH\"\n\n# to be used as default LT_SYS_LIBRARY_PATH value in generated libtool\nconfigure_time_lt_sys_library_path=$LT_SYS_LIBRARY_PATH\n\n_LT_DECL([], [variables_saved_for_relink], [1],\n    [Variables whose values should be saved in libtool wrapper scripts and\n    restored at link time])\n_LT_DECL([], [need_lib_prefix], [0],\n    [Do we need the \"lib\" prefix for modules?])\n_LT_DECL([], [need_version], [0], [Do we need a version for libraries?])\n_LT_DECL([], [version_type], [0], [Library versioning type])\n_LT_DECL([], [runpath_var], [0],  [Shared library runtime path variable])\n_LT_DECL([], [shlibpath_var], [0],[Shared library path variable])\n_LT_DECL([], [shlibpath_overrides_runpath], [0],\n    [Is shlibpath searched before the hard-coded library search path?])\n_LT_DECL([], [libname_spec], [1], [Format of library name prefix])\n_LT_DECL([], [library_names_spec], [1],\n    [[List of archive names.  First name is the real one, the rest are links.\n    The last name is the one that the linker finds with -lNAME]])\n_LT_DECL([], [soname_spec], [1],\n    [[The coded name of the library, if different from the real name]])\n_LT_DECL([], [install_override_mode], [1],\n    [Permission mode override for installation of shared libraries])\n_LT_DECL([], [postinstall_cmds], [2],\n    [Command to use after installation of a shared archive])\n_LT_DECL([], [postuninstall_cmds], [2],\n    [Command to use after uninstallation of a shared archive])\n_LT_DECL([], [finish_cmds], [2],\n    [Commands used to finish a libtool library installation in a directory])\n_LT_DECL([], [finish_eval], [1],\n    [[As \"finish_cmds\", except a single script fragment to be evaled but\n    not shown]])\n_LT_DECL([], [hardcode_into_libs], [0],\n    [Whether we should hardcode library paths into libraries])\n_LT_DECL([], [sys_lib_search_path_spec], [2],\n    [Compile-time system search path for libraries])\n_LT_DECL([sys_lib_dlsearch_path_spec], [configure_time_dlsearch_path], [2],\n    [Detected run-time system search path for libraries])\n_LT_DECL([], [configure_time_lt_sys_library_path], [2],\n    [Explicit LT_SYS_LIBRARY_PATH set during ./configure time])\n])# _LT_SYS_DYNAMIC_LINKER\n\n\n# _LT_PATH_TOOL_PREFIX(TOOL)\n# --------------------------\n# find a file program that can recognize shared library\nAC_DEFUN([_LT_PATH_TOOL_PREFIX],\n[m4_require([_LT_DECL_EGREP])dnl\nAC_MSG_CHECKING([for $1])\nAC_CACHE_VAL(lt_cv_path_MAGIC_CMD,\n[case $MAGIC_CMD in\n[[\\\\/*] |  ?:[\\\\/]*])\n  lt_cv_path_MAGIC_CMD=$MAGIC_CMD # Let the user override the test with a path.\n  ;;\n*)\n  lt_save_MAGIC_CMD=$MAGIC_CMD\n  lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR\ndnl $ac_dummy forces splitting on constant user-supplied paths.\ndnl POSIX.2 word splitting is done only on the output of word expansions,\ndnl not every word.  This closes a longstanding sh security hole.\n  ac_dummy=\"m4_if([$2], , $PATH, [$2])\"\n  for ac_dir in $ac_dummy; do\n    IFS=$lt_save_ifs\n    test -z \"$ac_dir\" && ac_dir=.\n    if test -f \"$ac_dir/$1\"; then\n      lt_cv_path_MAGIC_CMD=$ac_dir/\"$1\"\n      if test -n \"$file_magic_test_file\"; then\n\tcase $deplibs_check_method in\n\t\"file_magic \"*)\n\t  file_magic_regex=`expr \"$deplibs_check_method\" : \"file_magic \\(.*\\)\"`\n\t  MAGIC_CMD=$lt_cv_path_MAGIC_CMD\n\t  if eval $file_magic_cmd \\$file_magic_test_file 2> /dev/null |\n\t    $EGREP \"$file_magic_regex\" > /dev/null; then\n\t    :\n\t  else\n\t    cat <<_LT_EOF 1>&2\n\n*** Warning: the command libtool uses to detect shared libraries,\n*** $file_magic_cmd, produces output that libtool cannot recognize.\n*** The result is that libtool may fail to recognize shared libraries\n*** as such.  This will affect the creation of libtool libraries that\n*** depend on shared libraries, but programs linked with such libtool\n*** libraries will work regardless of this problem.  Nevertheless, you\n*** may want to report the problem to your system manager and/or to\n*** bug-libtool@gnu.org\n\n_LT_EOF\n\t  fi ;;\n\tesac\n      fi\n      break\n    fi\n  done\n  IFS=$lt_save_ifs\n  MAGIC_CMD=$lt_save_MAGIC_CMD\n  ;;\nesac])\nMAGIC_CMD=$lt_cv_path_MAGIC_CMD\nif test -n \"$MAGIC_CMD\"; then\n  AC_MSG_RESULT($MAGIC_CMD)\nelse\n  AC_MSG_RESULT(no)\nfi\n_LT_DECL([], [MAGIC_CMD], [0],\n\t [Used to examine libraries when file_magic_cmd begins with \"file\"])dnl\n])# _LT_PATH_TOOL_PREFIX\n\n# Old name:\nAU_ALIAS([AC_PATH_TOOL_PREFIX], [_LT_PATH_TOOL_PREFIX])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_PATH_TOOL_PREFIX], [])\n\n\n# _LT_PATH_MAGIC\n# --------------\n# find a file program that can recognize a shared library\nm4_defun([_LT_PATH_MAGIC],\n[_LT_PATH_TOOL_PREFIX(${ac_tool_prefix}file, /usr/bin$PATH_SEPARATOR$PATH)\nif test -z \"$lt_cv_path_MAGIC_CMD\"; then\n  if test -n \"$ac_tool_prefix\"; then\n    _LT_PATH_TOOL_PREFIX(file, /usr/bin$PATH_SEPARATOR$PATH)\n  else\n    MAGIC_CMD=:\n  fi\nfi\n])# _LT_PATH_MAGIC\n\n\n# LT_PATH_LD\n# ----------\n# find the pathname to the GNU or non-GNU linker\nAC_DEFUN([LT_PATH_LD],\n[AC_REQUIRE([AC_PROG_CC])dnl\nAC_REQUIRE([AC_CANONICAL_HOST])dnl\nAC_REQUIRE([AC_CANONICAL_BUILD])dnl\nm4_require([_LT_DECL_SED])dnl\nm4_require([_LT_DECL_EGREP])dnl\nm4_require([_LT_PROG_ECHO_BACKSLASH])dnl\n\nAC_ARG_WITH([gnu-ld],\n    [AS_HELP_STRING([--with-gnu-ld],\n\t[assume the C compiler uses GNU ld @<:@default=no@:>@])],\n    [test no = \"$withval\" || with_gnu_ld=yes],\n    [with_gnu_ld=no])dnl\n\nac_prog=ld\nif test yes = \"$GCC\"; then\n  # Check if gcc -print-prog-name=ld gives a path.\n  AC_MSG_CHECKING([for ld used by $CC])\n  case $host in\n  *-*-mingw*)\n    # gcc leaves a trailing carriage return, which upsets mingw\n    ac_prog=`($CC -print-prog-name=ld) 2>&5 | tr -d '\\015'` ;;\n  *)\n    ac_prog=`($CC -print-prog-name=ld) 2>&5` ;;\n  esac\n  case $ac_prog in\n    # Accept absolute paths.\n    [[\\\\/]]* | ?:[[\\\\/]]*)\n      re_direlt='/[[^/]][[^/]]*/\\.\\./'\n      # Canonicalize the pathname of ld\n      ac_prog=`$ECHO \"$ac_prog\"| $SED 's%\\\\\\\\%/%g'`\n      while $ECHO \"$ac_prog\" | $GREP \"$re_direlt\" > /dev/null 2>&1; do\n\tac_prog=`$ECHO $ac_prog| $SED \"s%$re_direlt%/%\"`\n      done\n      test -z \"$LD\" && LD=$ac_prog\n      ;;\n  \"\")\n    # If it fails, then pretend we aren't using GCC.\n    ac_prog=ld\n    ;;\n  *)\n    # If it is relative, then search for the first ld in PATH.\n    with_gnu_ld=unknown\n    ;;\n  esac\nelif test yes = \"$with_gnu_ld\"; then\n  AC_MSG_CHECKING([for GNU ld])\nelse\n  AC_MSG_CHECKING([for non-GNU ld])\nfi\nAC_CACHE_VAL(lt_cv_path_LD,\n[if test -z \"$LD\"; then\n  lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR\n  for ac_dir in $PATH; do\n    IFS=$lt_save_ifs\n    test -z \"$ac_dir\" && ac_dir=.\n    if test -f \"$ac_dir/$ac_prog\" || test -f \"$ac_dir/$ac_prog$ac_exeext\"; then\n      lt_cv_path_LD=$ac_dir/$ac_prog\n      # Check to see if the program is GNU ld.  I'd rather use --version,\n      # but apparently some variants of GNU ld only accept -v.\n      # Break only if it was the GNU/non-GNU ld that we prefer.\n      case `\"$lt_cv_path_LD\" -v 2>&1 </dev/null` in\n      *GNU* | *'with BFD'*)\n\ttest no != \"$with_gnu_ld\" && break\n\t;;\n      *)\n\ttest yes != \"$with_gnu_ld\" && break\n\t;;\n      esac\n    fi\n  done\n  IFS=$lt_save_ifs\nelse\n  lt_cv_path_LD=$LD # Let the user override the test with a path.\nfi])\nLD=$lt_cv_path_LD\nif test -n \"$LD\"; then\n  AC_MSG_RESULT($LD)\nelse\n  AC_MSG_RESULT(no)\nfi\ntest -z \"$LD\" && AC_MSG_ERROR([no acceptable ld found in \\$PATH])\n_LT_PATH_LD_GNU\nAC_SUBST([LD])\n\n_LT_TAGDECL([], [LD], [1], [The linker used to build libraries])\n])# LT_PATH_LD\n\n# Old names:\nAU_ALIAS([AM_PROG_LD], [LT_PATH_LD])\nAU_ALIAS([AC_PROG_LD], [LT_PATH_LD])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AM_PROG_LD], [])\ndnl AC_DEFUN([AC_PROG_LD], [])\n\n\n# _LT_PATH_LD_GNU\n#- --------------\nm4_defun([_LT_PATH_LD_GNU],\n[AC_CACHE_CHECK([if the linker ($LD) is GNU ld], lt_cv_prog_gnu_ld,\n[# I'd rather use --version here, but apparently some GNU lds only accept -v.\ncase `$LD -v 2>&1 </dev/null` in\n*GNU* | *'with BFD'*)\n  lt_cv_prog_gnu_ld=yes\n  ;;\n*)\n  lt_cv_prog_gnu_ld=no\n  ;;\nesac])\nwith_gnu_ld=$lt_cv_prog_gnu_ld\n])# _LT_PATH_LD_GNU\n\n\n# _LT_CMD_RELOAD\n# --------------\n# find reload flag for linker\n#   -- PORTME Some linkers may need a different reload flag.\nm4_defun([_LT_CMD_RELOAD],\n[AC_CACHE_CHECK([for $LD option to reload object files],\n  lt_cv_ld_reload_flag,\n  [lt_cv_ld_reload_flag='-r'])\nreload_flag=$lt_cv_ld_reload_flag\ncase $reload_flag in\n\"\" | \" \"*) ;;\n*) reload_flag=\" $reload_flag\" ;;\nesac\nreload_cmds='$LD$reload_flag -o $output$reload_objs'\ncase $host_os in\n  cygwin* | mingw* | pw32* | cegcc*)\n    if test yes != \"$GCC\"; then\n      reload_cmds=false\n    fi\n    ;;\n  darwin*)\n    if test yes = \"$GCC\"; then\n      reload_cmds='$LTCC $LTCFLAGS -nostdlib $wl-r -o $output$reload_objs'\n    else\n      reload_cmds='$LD$reload_flag -o $output$reload_objs'\n    fi\n    ;;\nesac\n_LT_TAGDECL([], [reload_flag], [1], [How to create reloadable object files])dnl\n_LT_TAGDECL([], [reload_cmds], [2])dnl\n])# _LT_CMD_RELOAD\n\n\n# _LT_PATH_DD\n# -----------\n# find a working dd\nm4_defun([_LT_PATH_DD],\n[AC_CACHE_CHECK([for a working dd], [ac_cv_path_lt_DD],\n[printf 0123456789abcdef0123456789abcdef >conftest.i\ncat conftest.i conftest.i >conftest2.i\n: ${lt_DD:=$DD}\nAC_PATH_PROGS_FEATURE_CHECK([lt_DD], [dd],\n[if \"$ac_path_lt_DD\" bs=32 count=1 <conftest2.i >conftest.out 2>/dev/null; then\n  cmp -s conftest.i conftest.out \\\n  && ac_cv_path_lt_DD=\"$ac_path_lt_DD\" ac_path_lt_DD_found=:\nfi])\nrm -f conftest.i conftest2.i conftest.out])\n])# _LT_PATH_DD\n\n\n# _LT_CMD_TRUNCATE\n# ----------------\n# find command to truncate a binary pipe\nm4_defun([_LT_CMD_TRUNCATE],\n[m4_require([_LT_PATH_DD])\nAC_CACHE_CHECK([how to truncate binary pipes], [lt_cv_truncate_bin],\n[printf 0123456789abcdef0123456789abcdef >conftest.i\ncat conftest.i conftest.i >conftest2.i\nlt_cv_truncate_bin=\nif \"$ac_cv_path_lt_DD\" bs=32 count=1 <conftest2.i >conftest.out 2>/dev/null; then\n  cmp -s conftest.i conftest.out \\\n  && lt_cv_truncate_bin=\"$ac_cv_path_lt_DD bs=4096 count=1\"\nfi\nrm -f conftest.i conftest2.i conftest.out\ntest -z \"$lt_cv_truncate_bin\" && lt_cv_truncate_bin=\"$SED -e 4q\"])\n_LT_DECL([lt_truncate_bin], [lt_cv_truncate_bin], [1],\n  [Command to truncate a binary pipe])\n])# _LT_CMD_TRUNCATE\n\n\n# _LT_CHECK_MAGIC_METHOD\n# ----------------------\n# how to check for library dependencies\n#  -- PORTME fill in with the dynamic library characteristics\nm4_defun([_LT_CHECK_MAGIC_METHOD],\n[m4_require([_LT_DECL_EGREP])\nm4_require([_LT_DECL_OBJDUMP])\nAC_CACHE_CHECK([how to recognize dependent libraries],\nlt_cv_deplibs_check_method,\n[lt_cv_file_magic_cmd='$MAGIC_CMD'\nlt_cv_file_magic_test_file=\nlt_cv_deplibs_check_method='unknown'\n# Need to set the preceding variable on all platforms that support\n# interlibrary dependencies.\n# 'none' -- dependencies not supported.\n# 'unknown' -- same as none, but documents that we really don't know.\n# 'pass_all' -- all dependencies passed with no checks.\n# 'test_compile' -- check by making test program.\n# 'file_magic [[regex]]' -- check by looking for files in library path\n# that responds to the $file_magic_cmd with a given extended regex.\n# If you have 'file' or equivalent on your system and you're not sure\n# whether 'pass_all' will *always* work, you probably want this one.\n\ncase $host_os in\naix[[4-9]]*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nbeos*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nbsdi[[45]]*)\n  lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (shared object|dynamic lib)'\n  lt_cv_file_magic_cmd='$FILECMD -L'\n  lt_cv_file_magic_test_file=/shlib/libc.so\n  ;;\n\ncygwin*)\n  # func_win32_libid is a shell function defined in ltmain.sh\n  lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL'\n  lt_cv_file_magic_cmd='func_win32_libid'\n  ;;\n\nmingw* | pw32*)\n  # Base MSYS/MinGW do not provide the 'file' command needed by\n  # func_win32_libid shell function, so use a weaker test based on 'objdump',\n  # unless we find 'file', for example because we are cross-compiling.\n  if ( file / ) >/dev/null 2>&1; then\n    lt_cv_deplibs_check_method='file_magic ^x86 archive import|^x86 DLL'\n    lt_cv_file_magic_cmd='func_win32_libid'\n  else\n    # Keep this pattern in sync with the one in func_win32_libid.\n    lt_cv_deplibs_check_method='file_magic file format (pei*-i386(.*architecture: i386)?|pe-arm-wince|pe-x86-64)'\n    lt_cv_file_magic_cmd='$OBJDUMP -f'\n  fi\n  ;;\n\ncegcc*)\n  # use the weaker test based on 'objdump'. See mingw*.\n  lt_cv_deplibs_check_method='file_magic file format pe-arm-.*little(.*architecture: arm)?'\n  lt_cv_file_magic_cmd='$OBJDUMP -f'\n  ;;\n\ndarwin* | rhapsody*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nfreebsd* | dragonfly* | midnightbsd*)\n  if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then\n    case $host_cpu in\n    i*86 )\n      # Not sure whether the presence of OpenBSD here was a mistake.\n      # Let's accept both of them until this is cleared up.\n      lt_cv_deplibs_check_method='file_magic (FreeBSD|OpenBSD|DragonFly)/i[[3-9]]86 (compact )?demand paged shared library'\n      lt_cv_file_magic_cmd=$FILECMD\n      lt_cv_file_magic_test_file=`echo /usr/lib/libc.so.*`\n      ;;\n    esac\n  else\n    lt_cv_deplibs_check_method=pass_all\n  fi\n  ;;\n\nhaiku*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nhpux10.20* | hpux11*)\n  lt_cv_file_magic_cmd=$FILECMD\n  case $host_cpu in\n  ia64*)\n    lt_cv_deplibs_check_method='file_magic (s[[0-9]][[0-9]][[0-9]]|ELF-[[0-9]][[0-9]]) shared object file - IA64'\n    lt_cv_file_magic_test_file=/usr/lib/hpux32/libc.so\n    ;;\n  hppa*64*)\n    [lt_cv_deplibs_check_method='file_magic (s[0-9][0-9][0-9]|ELF[ -][0-9][0-9])(-bit)?( [LM]SB)? shared object( file)?[, -]* PA-RISC [0-9]\\.[0-9]']\n    lt_cv_file_magic_test_file=/usr/lib/pa20_64/libc.sl\n    ;;\n  *)\n    lt_cv_deplibs_check_method='file_magic (s[[0-9]][[0-9]][[0-9]]|PA-RISC[[0-9]]\\.[[0-9]]) shared library'\n    lt_cv_file_magic_test_file=/usr/lib/libc.sl\n    ;;\n  esac\n  ;;\n\ninterix[[3-9]]*)\n  # PIC code is broken on Interix 3.x, that's why |\\.a not |_pic\\.a here\n  lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\\.so|\\.a)$'\n  ;;\n\nirix5* | irix6* | nonstopux*)\n  case $LD in\n  *-32|*\"-32 \") libmagic=32-bit;;\n  *-n32|*\"-n32 \") libmagic=N32;;\n  *-64|*\"-64 \") libmagic=64-bit;;\n  *) libmagic=never-match;;\n  esac\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\n# This must be glibc/ELF.\nlinux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nnetbsd*)\n  if echo __ELF__ | $CC -E - | $GREP __ELF__ > /dev/null; then\n    lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\\.so\\.[[0-9]]+\\.[[0-9]]+|_pic\\.a)$'\n  else\n    lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\\.so|_pic\\.a)$'\n  fi\n  ;;\n\nnewos6*)\n  lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (executable|dynamic lib)'\n  lt_cv_file_magic_cmd=$FILECMD\n  lt_cv_file_magic_test_file=/usr/lib/libnls.so\n  ;;\n\n*nto* | *qnx*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nopenbsd* | bitrig*)\n  if test -z \"`echo __ELF__ | $CC -E - | $GREP __ELF__`\"; then\n    lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\\.so\\.[[0-9]]+\\.[[0-9]]+|\\.so|_pic\\.a)$'\n  else\n    lt_cv_deplibs_check_method='match_pattern /lib[[^/]]+(\\.so\\.[[0-9]]+\\.[[0-9]]+|_pic\\.a)$'\n  fi\n  ;;\n\nosf3* | osf4* | osf5*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nrdos*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nsolaris*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nsysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX* | sysv4*uw2*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\n\nsysv4 | sysv4.3*)\n  case $host_vendor in\n  motorola)\n    lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[ML]]SB (shared object|dynamic lib) M[[0-9]][[0-9]]* Version [[0-9]]'\n    lt_cv_file_magic_test_file=`echo /usr/lib/libc.so*`\n    ;;\n  ncr)\n    lt_cv_deplibs_check_method=pass_all\n    ;;\n  sequent)\n    lt_cv_file_magic_cmd='/bin/file'\n    lt_cv_deplibs_check_method='file_magic ELF [[0-9]][[0-9]]*-bit [[LM]]SB (shared object|dynamic lib )'\n    ;;\n  sni)\n    lt_cv_file_magic_cmd='/bin/file'\n    lt_cv_deplibs_check_method=\"file_magic ELF [[0-9]][[0-9]]*-bit [[LM]]SB dynamic lib\"\n    lt_cv_file_magic_test_file=/lib/libc.so\n    ;;\n  siemens)\n    lt_cv_deplibs_check_method=pass_all\n    ;;\n  pc)\n    lt_cv_deplibs_check_method=pass_all\n    ;;\n  esac\n  ;;\n\ntpf*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\nos2*)\n  lt_cv_deplibs_check_method=pass_all\n  ;;\nesac\n])\n\nfile_magic_glob=\nwant_nocaseglob=no\nif test \"$build\" = \"$host\"; then\n  case $host_os in\n  mingw* | pw32*)\n    if ( shopt | grep nocaseglob ) >/dev/null 2>&1; then\n      want_nocaseglob=yes\n    else\n      file_magic_glob=`echo aAbBcCdDeEfFgGhHiIjJkKlLmMnNoOpPqQrRsStTuUvVwWxXyYzZ | $SED -e \"s/\\(..\\)/s\\/[[\\1]]\\/[[\\1]]\\/g;/g\"`\n    fi\n    ;;\n  esac\nfi\n\nfile_magic_cmd=$lt_cv_file_magic_cmd\ndeplibs_check_method=$lt_cv_deplibs_check_method\ntest -z \"$deplibs_check_method\" && deplibs_check_method=unknown\n\n_LT_DECL([], [deplibs_check_method], [1],\n    [Method to check whether dependent libraries are shared objects])\n_LT_DECL([], [file_magic_cmd], [1],\n    [Command to use when deplibs_check_method = \"file_magic\"])\n_LT_DECL([], [file_magic_glob], [1],\n    [How to find potential files when deplibs_check_method = \"file_magic\"])\n_LT_DECL([], [want_nocaseglob], [1],\n    [Find potential files using nocaseglob when deplibs_check_method = \"file_magic\"])\n])# _LT_CHECK_MAGIC_METHOD\n\n\n# LT_PATH_NM\n# ----------\n# find the pathname to a BSD- or MS-compatible name lister\nAC_DEFUN([LT_PATH_NM],\n[AC_REQUIRE([AC_PROG_CC])dnl\nAC_CACHE_CHECK([for BSD- or MS-compatible name lister (nm)], lt_cv_path_NM,\n[if test -n \"$NM\"; then\n  # Let the user override the test.\n  lt_cv_path_NM=$NM\nelse\n  lt_nm_to_check=${ac_tool_prefix}nm\n  if test -n \"$ac_tool_prefix\" && test \"$build\" = \"$host\"; then\n    lt_nm_to_check=\"$lt_nm_to_check nm\"\n  fi\n  for lt_tmp_nm in $lt_nm_to_check; do\n    lt_save_ifs=$IFS; IFS=$PATH_SEPARATOR\n    for ac_dir in $PATH /usr/ccs/bin/elf /usr/ccs/bin /usr/ucb /bin; do\n      IFS=$lt_save_ifs\n      test -z \"$ac_dir\" && ac_dir=.\n      tmp_nm=$ac_dir/$lt_tmp_nm\n      if test -f \"$tmp_nm\" || test -f \"$tmp_nm$ac_exeext\"; then\n\t# Check to see if the nm accepts a BSD-compat flag.\n\t# Adding the 'sed 1q' prevents false positives on HP-UX, which says:\n\t#   nm: unknown option \"B\" ignored\n\t# Tru64's nm complains that /dev/null is an invalid object file\n\t# MSYS converts /dev/null to NUL, MinGW nm treats NUL as empty\n\tcase $build_os in\n\tmingw*) lt_bad_file=conftest.nm/nofile ;;\n\t*) lt_bad_file=/dev/null ;;\n\tesac\n\tcase `\"$tmp_nm\" -B $lt_bad_file 2>&1 | $SED '1q'` in\n\t*$lt_bad_file* | *'Invalid file or object type'*)\n\t  lt_cv_path_NM=\"$tmp_nm -B\"\n\t  break 2\n\t  ;;\n\t*)\n\t  case `\"$tmp_nm\" -p /dev/null 2>&1 | $SED '1q'` in\n\t  */dev/null*)\n\t    lt_cv_path_NM=\"$tmp_nm -p\"\n\t    break 2\n\t    ;;\n\t  *)\n\t    lt_cv_path_NM=${lt_cv_path_NM=\"$tmp_nm\"} # keep the first match, but\n\t    continue # so that we can try to find one that supports BSD flags\n\t    ;;\n\t  esac\n\t  ;;\n\tesac\n      fi\n    done\n    IFS=$lt_save_ifs\n  done\n  : ${lt_cv_path_NM=no}\nfi])\nif test no != \"$lt_cv_path_NM\"; then\n  NM=$lt_cv_path_NM\nelse\n  # Didn't find any BSD compatible name lister, look for dumpbin.\n  if test -n \"$DUMPBIN\"; then :\n    # Let the user override the test.\n  else\n    AC_CHECK_TOOLS(DUMPBIN, [dumpbin \"link -dump\"], :)\n    case `$DUMPBIN -symbols -headers /dev/null 2>&1 | $SED '1q'` in\n    *COFF*)\n      DUMPBIN=\"$DUMPBIN -symbols -headers\"\n      ;;\n    *)\n      DUMPBIN=:\n      ;;\n    esac\n  fi\n  AC_SUBST([DUMPBIN])\n  if test : != \"$DUMPBIN\"; then\n    NM=$DUMPBIN\n  fi\nfi\ntest -z \"$NM\" && NM=nm\nAC_SUBST([NM])\n_LT_DECL([], [NM], [1], [A BSD- or MS-compatible name lister])dnl\n\nAC_CACHE_CHECK([the name lister ($NM) interface], [lt_cv_nm_interface],\n  [lt_cv_nm_interface=\"BSD nm\"\n  echo \"int some_variable = 0;\" > conftest.$ac_ext\n  (eval echo \"\\\"\\$as_me:$LINENO: $ac_compile\\\"\" >&AS_MESSAGE_LOG_FD)\n  (eval \"$ac_compile\" 2>conftest.err)\n  cat conftest.err >&AS_MESSAGE_LOG_FD\n  (eval echo \"\\\"\\$as_me:$LINENO: $NM \\\\\\\"conftest.$ac_objext\\\\\\\"\\\"\" >&AS_MESSAGE_LOG_FD)\n  (eval \"$NM \\\"conftest.$ac_objext\\\"\" 2>conftest.err > conftest.out)\n  cat conftest.err >&AS_MESSAGE_LOG_FD\n  (eval echo \"\\\"\\$as_me:$LINENO: output\\\"\" >&AS_MESSAGE_LOG_FD)\n  cat conftest.out >&AS_MESSAGE_LOG_FD\n  if $GREP 'External.*some_variable' conftest.out > /dev/null; then\n    lt_cv_nm_interface=\"MS dumpbin\"\n  fi\n  rm -f conftest*])\n])# LT_PATH_NM\n\n# Old names:\nAU_ALIAS([AM_PROG_NM], [LT_PATH_NM])\nAU_ALIAS([AC_PROG_NM], [LT_PATH_NM])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AM_PROG_NM], [])\ndnl AC_DEFUN([AC_PROG_NM], [])\n\n# _LT_CHECK_SHAREDLIB_FROM_LINKLIB\n# --------------------------------\n# how to determine the name of the shared library\n# associated with a specific link library.\n#  -- PORTME fill in with the dynamic library characteristics\nm4_defun([_LT_CHECK_SHAREDLIB_FROM_LINKLIB],\n[m4_require([_LT_DECL_EGREP])\nm4_require([_LT_DECL_OBJDUMP])\nm4_require([_LT_DECL_DLLTOOL])\nAC_CACHE_CHECK([how to associate runtime and link libraries],\nlt_cv_sharedlib_from_linklib_cmd,\n[lt_cv_sharedlib_from_linklib_cmd='unknown'\n\ncase $host_os in\ncygwin* | mingw* | pw32* | cegcc*)\n  # two different shell functions defined in ltmain.sh;\n  # decide which one to use based on capabilities of $DLLTOOL\n  case `$DLLTOOL --help 2>&1` in\n  *--identify-strict*)\n    lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib\n    ;;\n  *)\n    lt_cv_sharedlib_from_linklib_cmd=func_cygming_dll_for_implib_fallback\n    ;;\n  esac\n  ;;\n*)\n  # fallback: assume linklib IS sharedlib\n  lt_cv_sharedlib_from_linklib_cmd=$ECHO\n  ;;\nesac\n])\nsharedlib_from_linklib_cmd=$lt_cv_sharedlib_from_linklib_cmd\ntest -z \"$sharedlib_from_linklib_cmd\" && sharedlib_from_linklib_cmd=$ECHO\n\n_LT_DECL([], [sharedlib_from_linklib_cmd], [1],\n    [Command to associate shared and link libraries])\n])# _LT_CHECK_SHAREDLIB_FROM_LINKLIB\n\n\n# _LT_PATH_MANIFEST_TOOL\n# ----------------------\n# locate the manifest tool\nm4_defun([_LT_PATH_MANIFEST_TOOL],\n[AC_CHECK_TOOL(MANIFEST_TOOL, mt, :)\ntest -z \"$MANIFEST_TOOL\" && MANIFEST_TOOL=mt\nAC_CACHE_CHECK([if $MANIFEST_TOOL is a manifest tool], [lt_cv_path_mainfest_tool],\n  [lt_cv_path_mainfest_tool=no\n  echo \"$as_me:$LINENO: $MANIFEST_TOOL '-?'\" >&AS_MESSAGE_LOG_FD\n  $MANIFEST_TOOL '-?' 2>conftest.err > conftest.out\n  cat conftest.err >&AS_MESSAGE_LOG_FD\n  if $GREP 'Manifest Tool' conftest.out > /dev/null; then\n    lt_cv_path_mainfest_tool=yes\n  fi\n  rm -f conftest*])\nif test yes != \"$lt_cv_path_mainfest_tool\"; then\n  MANIFEST_TOOL=:\nfi\n_LT_DECL([], [MANIFEST_TOOL], [1], [Manifest tool])dnl\n])# _LT_PATH_MANIFEST_TOOL\n\n\n# _LT_DLL_DEF_P([FILE])\n# ---------------------\n# True iff FILE is a Windows DLL '.def' file.\n# Keep in sync with func_dll_def_p in the libtool script\nAC_DEFUN([_LT_DLL_DEF_P],\n[dnl\n  test DEF = \"`$SED -n dnl\n    -e '\\''s/^[[\t ]]*//'\\'' dnl Strip leading whitespace\n    -e '\\''/^\\(;.*\\)*$/d'\\'' dnl      Delete empty lines and comments\n    -e '\\''s/^\\(EXPORTS\\|LIBRARY\\)\\([[\t ]].*\\)*$/DEF/p'\\'' dnl\n    -e q dnl                          Only consider the first \"real\" line\n    $1`\" dnl\n])# _LT_DLL_DEF_P\n\n\n# LT_LIB_M\n# --------\n# check for math library\nAC_DEFUN([LT_LIB_M],\n[AC_REQUIRE([AC_CANONICAL_HOST])dnl\nLIBM=\ncase $host in\n*-*-beos* | *-*-cegcc* | *-*-cygwin* | *-*-haiku* | *-*-pw32* | *-*-darwin*)\n  # These system don't have libm, or don't need it\n  ;;\n*-ncr-sysv4.3*)\n  AC_CHECK_LIB(mw, _mwvalidcheckl, LIBM=-lmw)\n  AC_CHECK_LIB(m, cos, LIBM=\"$LIBM -lm\")\n  ;;\n*)\n  AC_CHECK_LIB(m, cos, LIBM=-lm)\n  ;;\nesac\nAC_SUBST([LIBM])\n])# LT_LIB_M\n\n# Old name:\nAU_ALIAS([AC_CHECK_LIBM], [LT_LIB_M])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_CHECK_LIBM], [])\n\n\n# _LT_COMPILER_NO_RTTI([TAGNAME])\n# -------------------------------\nm4_defun([_LT_COMPILER_NO_RTTI],\n[m4_require([_LT_TAG_COMPILER])dnl\n\n_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=\n\nif test yes = \"$GCC\"; then\n  case $cc_basename in\n  nvcc*)\n    _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -Xcompiler -fno-builtin' ;;\n  *)\n    _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -fno-builtin' ;;\n  esac\n\n  _LT_COMPILER_OPTION([if $compiler supports -fno-rtti -fno-exceptions],\n    lt_cv_prog_compiler_rtti_exceptions,\n    [-fno-rtti -fno-exceptions], [],\n    [_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=\"$_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1) -fno-rtti -fno-exceptions\"])\nfi\n_LT_TAGDECL([no_builtin_flag], [lt_prog_compiler_no_builtin_flag], [1],\n\t[Compiler flag to turn off builtin functions])\n])# _LT_COMPILER_NO_RTTI\n\n\n# _LT_CMD_GLOBAL_SYMBOLS\n# ----------------------\nm4_defun([_LT_CMD_GLOBAL_SYMBOLS],\n[AC_REQUIRE([AC_CANONICAL_HOST])dnl\nAC_REQUIRE([AC_PROG_CC])dnl\nAC_REQUIRE([AC_PROG_AWK])dnl\nAC_REQUIRE([LT_PATH_NM])dnl\nAC_REQUIRE([LT_PATH_LD])dnl\nm4_require([_LT_DECL_SED])dnl\nm4_require([_LT_DECL_EGREP])dnl\nm4_require([_LT_TAG_COMPILER])dnl\n\n# Check for command to grab the raw symbol name followed by C symbol from nm.\nAC_MSG_CHECKING([command to parse $NM output from $compiler object])\nAC_CACHE_VAL([lt_cv_sys_global_symbol_pipe],\n[\n# These are sane defaults that work on at least a few old systems.\n# [They come from Ultrix.  What could be older than Ultrix?!! ;)]\n\n# Character class describing NM global symbol codes.\nsymcode='[[BCDEGRST]]'\n\n# Regexp to match symbols that can be accessed directly from C.\nsympat='\\([[_A-Za-z]][[_A-Za-z0-9]]*\\)'\n\n# Define system-specific variables.\ncase $host_os in\naix*)\n  symcode='[[BCDT]]'\n  ;;\ncygwin* | mingw* | pw32* | cegcc*)\n  symcode='[[ABCDGISTW]]'\n  ;;\nhpux*)\n  if test ia64 = \"$host_cpu\"; then\n    symcode='[[ABCDEGRST]]'\n  fi\n  ;;\nirix* | nonstopux*)\n  symcode='[[BCDEGRST]]'\n  ;;\nosf*)\n  symcode='[[BCDEGQRST]]'\n  ;;\nsolaris*)\n  symcode='[[BDRT]]'\n  ;;\nsco3.2v5*)\n  symcode='[[DT]]'\n  ;;\nsysv4.2uw2*)\n  symcode='[[DT]]'\n  ;;\nsysv5* | sco5v6* | unixware* | OpenUNIX*)\n  symcode='[[ABDT]]'\n  ;;\nsysv4)\n  symcode='[[DFNSTU]]'\n  ;;\nesac\n\n# If we're using GNU nm, then use its standard symbol codes.\ncase `$NM -V 2>&1` in\n*GNU* | *'with BFD'*)\n  symcode='[[ABCDGIRSTW]]' ;;\nesac\n\nif test \"$lt_cv_nm_interface\" = \"MS dumpbin\"; then\n  # Gets list of data symbols to import.\n  lt_cv_sys_global_symbol_to_import=\"$SED -n -e 's/^I .* \\(.*\\)$/\\1/p'\"\n  # Adjust the below global symbol transforms to fixup imported variables.\n  lt_cdecl_hook=\" -e 's/^I .* \\(.*\\)$/extern __declspec(dllimport) char \\1;/p'\"\n  lt_c_name_hook=\" -e 's/^I .* \\(.*\\)$/  {\\\"\\1\\\", (void *) 0},/p'\"\n  lt_c_name_lib_hook=\"\\\n  -e 's/^I .* \\(lib.*\\)$/  {\\\"\\1\\\", (void *) 0},/p'\\\n  -e 's/^I .* \\(.*\\)$/  {\\\"lib\\1\\\", (void *) 0},/p'\"\nelse\n  # Disable hooks by default.\n  lt_cv_sys_global_symbol_to_import=\n  lt_cdecl_hook=\n  lt_c_name_hook=\n  lt_c_name_lib_hook=\nfi\n\n# Transform an extracted symbol line into a proper C declaration.\n# Some systems (esp. on ia64) link data and code symbols differently,\n# so use this general approach.\nlt_cv_sys_global_symbol_to_cdecl=\"$SED -n\"\\\n$lt_cdecl_hook\\\n\" -e 's/^T .* \\(.*\\)$/extern int \\1();/p'\"\\\n\" -e 's/^$symcode$symcode* .* \\(.*\\)$/extern char \\1;/p'\"\n\n# Transform an extracted symbol line into symbol name and symbol address\nlt_cv_sys_global_symbol_to_c_name_address=\"$SED -n\"\\\n$lt_c_name_hook\\\n\" -e 's/^: \\(.*\\) .*$/  {\\\"\\1\\\", (void *) 0},/p'\"\\\n\" -e 's/^$symcode$symcode* .* \\(.*\\)$/  {\\\"\\1\\\", (void *) \\&\\1},/p'\"\n\n# Transform an extracted symbol line into symbol name with lib prefix and\n# symbol address.\nlt_cv_sys_global_symbol_to_c_name_address_lib_prefix=\"$SED -n\"\\\n$lt_c_name_lib_hook\\\n\" -e 's/^: \\(.*\\) .*$/  {\\\"\\1\\\", (void *) 0},/p'\"\\\n\" -e 's/^$symcode$symcode* .* \\(lib.*\\)$/  {\\\"\\1\\\", (void *) \\&\\1},/p'\"\\\n\" -e 's/^$symcode$symcode* .* \\(.*\\)$/  {\\\"lib\\1\\\", (void *) \\&\\1},/p'\"\n\n# Handle CRLF in mingw tool chain\nopt_cr=\ncase $build_os in\nmingw*)\n  opt_cr=`$ECHO 'x\\{0,1\\}' | tr x '\\015'` # option cr in regexp\n  ;;\nesac\n\n# Try without a prefix underscore, then with it.\nfor ac_symprfx in \"\" \"_\"; do\n\n  # Transform symcode, sympat, and symprfx into a raw symbol and a C symbol.\n  symxfrm=\"\\\\1 $ac_symprfx\\\\2 \\\\2\"\n\n  # Write the raw and C identifiers.\n  if test \"$lt_cv_nm_interface\" = \"MS dumpbin\"; then\n    # Fake it for dumpbin and say T for any non-static function,\n    # D for any global variable and I for any imported variable.\n    # Also find C++ and __fastcall symbols from MSVC++ or ICC,\n    # which start with @ or ?.\n    lt_cv_sys_global_symbol_pipe=\"$AWK ['\"\\\n\"     {last_section=section; section=\\$ 3};\"\\\n\"     /^COFF SYMBOL TABLE/{for(i in hide) delete hide[i]};\"\\\n\"     /Section length .*#relocs.*(pick any)/{hide[last_section]=1};\"\\\n\"     /^ *Symbol name *: /{split(\\$ 0,sn,\\\":\\\"); si=substr(sn[2],2)};\"\\\n\"     /^ *Type *: code/{print \\\"T\\\",si,substr(si,length(prfx))};\"\\\n\"     /^ *Type *: data/{print \\\"I\\\",si,substr(si,length(prfx))};\"\\\n\"     \\$ 0!~/External *\\|/{next};\"\\\n\"     / 0+ UNDEF /{next}; / UNDEF \\([^|]\\)*()/{next};\"\\\n\"     {if(hide[section]) next};\"\\\n\"     {f=\\\"D\\\"}; \\$ 0~/\\(\\).*\\|/{f=\\\"T\\\"};\"\\\n\"     {split(\\$ 0,a,/\\||\\r/); split(a[2],s)};\"\\\n\"     s[1]~/^[@?]/{print f,s[1],s[1]; next};\"\\\n\"     s[1]~prfx {split(s[1],t,\\\"@\\\"); print f,t[1],substr(t[1],length(prfx))}\"\\\n\"     ' prfx=^$ac_symprfx]\"\n  else\n    lt_cv_sys_global_symbol_pipe=\"$SED -n -e 's/^.*[[\t ]]\\($symcode$symcode*\\)[[\t ]][[\t ]]*$ac_symprfx$sympat$opt_cr$/$symxfrm/p'\"\n  fi\n  lt_cv_sys_global_symbol_pipe=\"$lt_cv_sys_global_symbol_pipe | $SED '/ __gnu_lto/d'\"\n\n  # Check to see that the pipe works correctly.\n  pipe_works=no\n\n  rm -f conftest*\n  cat > conftest.$ac_ext <<_LT_EOF\n#ifdef __cplusplus\nextern \"C\" {\n#endif\nchar nm_test_var;\nvoid nm_test_func(void);\nvoid nm_test_func(void){}\n#ifdef __cplusplus\n}\n#endif\nint main(){nm_test_var='a';nm_test_func();return(0);}\n_LT_EOF\n\n  if AC_TRY_EVAL(ac_compile); then\n    # Now try to grab the symbols.\n    nlist=conftest.nm\n    if AC_TRY_EVAL(NM conftest.$ac_objext \\| \"$lt_cv_sys_global_symbol_pipe\" \\> $nlist) && test -s \"$nlist\"; then\n      # Try sorting and uniquifying the output.\n      if sort \"$nlist\" | uniq > \"$nlist\"T; then\n\tmv -f \"$nlist\"T \"$nlist\"\n      else\n\trm -f \"$nlist\"T\n      fi\n\n      # Make sure that we snagged all the symbols we need.\n      if $GREP ' nm_test_var$' \"$nlist\" >/dev/null; then\n\tif $GREP ' nm_test_func$' \"$nlist\" >/dev/null; then\n\t  cat <<_LT_EOF > conftest.$ac_ext\n/* Keep this code in sync between libtool.m4, ltmain, lt_system.h, and tests.  */\n#if defined _WIN32 || defined __CYGWIN__ || defined _WIN32_WCE\n/* DATA imports from DLLs on WIN32 can't be const, because runtime\n   relocations are performed -- see ld's documentation on pseudo-relocs.  */\n# define LT@&t@_DLSYM_CONST\n#elif defined __osf__\n/* This system does not cope well with relocations in const data.  */\n# define LT@&t@_DLSYM_CONST\n#else\n# define LT@&t@_DLSYM_CONST const\n#endif\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n_LT_EOF\n\t  # Now generate the symbol file.\n\t  eval \"$lt_cv_sys_global_symbol_to_cdecl\"' < \"$nlist\" | $GREP -v main >> conftest.$ac_ext'\n\n\t  cat <<_LT_EOF >> conftest.$ac_ext\n\n/* The mapping between symbol names and symbols.  */\nLT@&t@_DLSYM_CONST struct {\n  const char *name;\n  void       *address;\n}\nlt__PROGRAM__LTX_preloaded_symbols[[]] =\n{\n  { \"@PROGRAM@\", (void *) 0 },\n_LT_EOF\n\t  $SED \"s/^$symcode$symcode* .* \\(.*\\)$/  {\\\"\\1\\\", (void *) \\&\\1},/\" < \"$nlist\" | $GREP -v main >> conftest.$ac_ext\n\t  cat <<\\_LT_EOF >> conftest.$ac_ext\n  {0, (void *) 0}\n};\n\n/* This works around a problem in FreeBSD linker */\n#ifdef FREEBSD_WORKAROUND\nstatic const void *lt_preloaded_setup() {\n  return lt__PROGRAM__LTX_preloaded_symbols;\n}\n#endif\n\n#ifdef __cplusplus\n}\n#endif\n_LT_EOF\n\t  # Now try linking the two files.\n\t  mv conftest.$ac_objext conftstm.$ac_objext\n\t  lt_globsym_save_LIBS=$LIBS\n\t  lt_globsym_save_CFLAGS=$CFLAGS\n\t  LIBS=conftstm.$ac_objext\n\t  CFLAGS=\"$CFLAGS$_LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)\"\n\t  if AC_TRY_EVAL(ac_link) && test -s conftest$ac_exeext; then\n\t    pipe_works=yes\n\t  fi\n\t  LIBS=$lt_globsym_save_LIBS\n\t  CFLAGS=$lt_globsym_save_CFLAGS\n\telse\n\t  echo \"cannot find nm_test_func in $nlist\" >&AS_MESSAGE_LOG_FD\n\tfi\n      else\n\techo \"cannot find nm_test_var in $nlist\" >&AS_MESSAGE_LOG_FD\n      fi\n    else\n      echo \"cannot run $lt_cv_sys_global_symbol_pipe\" >&AS_MESSAGE_LOG_FD\n    fi\n  else\n    echo \"$progname: failed program was:\" >&AS_MESSAGE_LOG_FD\n    cat conftest.$ac_ext >&5\n  fi\n  rm -rf conftest* conftst*\n\n  # Do not use the global_symbol_pipe unless it works.\n  if test yes = \"$pipe_works\"; then\n    break\n  else\n    lt_cv_sys_global_symbol_pipe=\n  fi\ndone\n])\nif test -z \"$lt_cv_sys_global_symbol_pipe\"; then\n  lt_cv_sys_global_symbol_to_cdecl=\nfi\nif test -z \"$lt_cv_sys_global_symbol_pipe$lt_cv_sys_global_symbol_to_cdecl\"; then\n  AC_MSG_RESULT(failed)\nelse\n  AC_MSG_RESULT(ok)\nfi\n\n# Response file support.\nif test \"$lt_cv_nm_interface\" = \"MS dumpbin\"; then\n  nm_file_list_spec='@'\nelif $NM --help 2>/dev/null | grep '[[@]]FILE' >/dev/null; then\n  nm_file_list_spec='@'\nfi\n\n_LT_DECL([global_symbol_pipe], [lt_cv_sys_global_symbol_pipe], [1],\n    [Take the output of nm and produce a listing of raw symbols and C names])\n_LT_DECL([global_symbol_to_cdecl], [lt_cv_sys_global_symbol_to_cdecl], [1],\n    [Transform the output of nm in a proper C declaration])\n_LT_DECL([global_symbol_to_import], [lt_cv_sys_global_symbol_to_import], [1],\n    [Transform the output of nm into a list of symbols to manually relocate])\n_LT_DECL([global_symbol_to_c_name_address],\n    [lt_cv_sys_global_symbol_to_c_name_address], [1],\n    [Transform the output of nm in a C name address pair])\n_LT_DECL([global_symbol_to_c_name_address_lib_prefix],\n    [lt_cv_sys_global_symbol_to_c_name_address_lib_prefix], [1],\n    [Transform the output of nm in a C name address pair when lib prefix is needed])\n_LT_DECL([nm_interface], [lt_cv_nm_interface], [1],\n    [The name lister interface])\n_LT_DECL([], [nm_file_list_spec], [1],\n    [Specify filename containing input files for $NM])\n]) # _LT_CMD_GLOBAL_SYMBOLS\n\n\n# _LT_COMPILER_PIC([TAGNAME])\n# ---------------------------\nm4_defun([_LT_COMPILER_PIC],\n[m4_require([_LT_TAG_COMPILER])dnl\n_LT_TAGVAR(lt_prog_compiler_wl, $1)=\n_LT_TAGVAR(lt_prog_compiler_pic, $1)=\n_LT_TAGVAR(lt_prog_compiler_static, $1)=\n\nm4_if([$1], [CXX], [\n  # C++ specific cases for pic, static, wl, etc.\n  if test yes = \"$GXX\"; then\n    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n    _LT_TAGVAR(lt_prog_compiler_static, $1)='-static'\n\n    case $host_os in\n    aix*)\n      # All AIX code is PIC.\n      if test ia64 = \"$host_cpu\"; then\n\t# AIX 5 now supports IA64 processor\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      fi\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n      ;;\n\n    amigaos*)\n      case $host_cpu in\n      powerpc)\n            # see comment about AmigaOS4 .so support\n            _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n        ;;\n      m68k)\n            # FIXME: we need at least 68020 code to build shared libraries, but\n            # adding the '-m68020' flag to GCC prevents building anything better,\n            # like '-m68040'.\n            _LT_TAGVAR(lt_prog_compiler_pic, $1)='-m68020 -resident32 -malways-restore-a4'\n        ;;\n      esac\n      ;;\n\n    beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*)\n      # PIC is the default for these OSes.\n      ;;\n    mingw* | cygwin* | os2* | pw32* | cegcc*)\n      # This hack is so that the source file can tell whether it is being\n      # built for inclusion in a dll (and should export symbols for example).\n      # Although the cygwin gcc ignores -fPIC, still need this for old-style\n      # (--disable-auto-import) libraries\n      m4_if([$1], [GCJ], [],\n\t[_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT'])\n      case $host_os in\n      os2*)\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static'\n\t;;\n      esac\n      ;;\n    darwin* | rhapsody*)\n      # PIC is the default on this platform\n      # Common symbols not allowed in MH_DYLIB files\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common'\n      ;;\n    *djgpp*)\n      # DJGPP does not support shared libraries at all\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)=\n      ;;\n    haiku*)\n      # PIC is the default for Haiku.\n      # The \"-static\" flag exists, but is broken.\n      _LT_TAGVAR(lt_prog_compiler_static, $1)=\n      ;;\n    interix[[3-9]]*)\n      # Interix 3.x gcc -fpic/-fPIC options generate broken code.\n      # Instead, we relocate shared libraries at runtime.\n      ;;\n    sysv4*MP*)\n      if test -d /usr/nec; then\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)=-Kconform_pic\n      fi\n      ;;\n    hpux*)\n      # PIC is the default for 64-bit PA HP-UX, but not for 32-bit\n      # PA HP-UX.  On IA64 HP-UX, PIC is the default but the pic flag\n      # sets the default TLS model and affects inlining.\n      case $host_cpu in\n      hppa*64*)\n\t;;\n      *)\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n\t;;\n      esac\n      ;;\n    *qnx* | *nto*)\n      # QNX uses GNU C++, but need to define -shared option too, otherwise\n      # it will coredump.\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared'\n      ;;\n    *)\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n      ;;\n    esac\n  else\n    case $host_os in\n      aix[[4-9]]*)\n\t# All AIX code is PIC.\n\tif test ia64 = \"$host_cpu\"; then\n\t  # AIX 5 now supports IA64 processor\n\t  _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\telse\n\t  _LT_TAGVAR(lt_prog_compiler_static, $1)='-bnso -bI:/lib/syscalls.exp'\n\tfi\n\t;;\n      chorus*)\n\tcase $cc_basename in\n\tcxch68*)\n\t  # Green Hills C++ Compiler\n\t  # _LT_TAGVAR(lt_prog_compiler_static, $1)=\"--no_auto_instantiation -u __main -u __premain -u _abort -r $COOL_DIR/lib/libOrb.a $MVME_DIR/lib/CC/libC.a $MVME_DIR/lib/classix/libcx.s.a\"\n\t  ;;\n\tesac\n\t;;\n      mingw* | cygwin* | os2* | pw32* | cegcc*)\n\t# This hack is so that the source file can tell whether it is being\n\t# built for inclusion in a dll (and should export symbols for example).\n\tm4_if([$1], [GCJ], [],\n\t  [_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT'])\n\t;;\n      dgux*)\n\tcase $cc_basename in\n\t  ec++*)\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t    ;;\n\t  ghcx*)\n\t    # Green Hills C++ Compiler\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      freebsd* | dragonfly* | midnightbsd*)\n\t# FreeBSD uses GNU C++\n\t;;\n      hpux9* | hpux10* | hpux11*)\n\tcase $cc_basename in\n\t  CC*)\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive'\n\t    if test ia64 != \"$host_cpu\"; then\n\t      _LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z'\n\t    fi\n\t    ;;\n\t  aCC*)\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive'\n\t    case $host_cpu in\n\t    hppa*64*|ia64*)\n\t      # +Z the default\n\t      ;;\n\t    *)\n\t      _LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z'\n\t      ;;\n\t    esac\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      interix*)\n\t# This is c89, which is MS Visual C++ (no shared libs)\n\t# Anyone wants to do a port?\n\t;;\n      irix5* | irix6* | nonstopux*)\n\tcase $cc_basename in\n\t  CC*)\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared'\n\t    # CC pic flag -KPIC is the default.\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n\tcase $cc_basename in\n\t  KCC*)\n\t    # KAI C++ Compiler\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='--backend -Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n\t    ;;\n\t  ecpc* )\n\t    # old Intel C++ for x86_64, which still supported -KPIC.\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-static'\n\t    ;;\n\t  icpc* )\n\t    # Intel C++, used to be incompatible with GCC.\n\t    # ICC 10 doesn't accept -KPIC any more.\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-static'\n\t    ;;\n\t  pgCC* | pgcpp*)\n\t    # Portland Group C++ compiler\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t    ;;\n\t  cxx*)\n\t    # Compaq C++\n\t    # Make sure the PIC flag is empty.  It appears that all Alpha\n\t    # Linux and Compaq Tru64 Unix objects are PIC.\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)=\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared'\n\t    ;;\n\t  xlc* | xlC* | bgxl[[cC]]* | mpixl[[cC]]*)\n\t    # IBM XL 8.0, 9.0 on PPC and BlueGene\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-qpic'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-qstaticlink'\n\t    ;;\n\t  *)\n\t    case `$CC -V 2>&1 | $SED 5q` in\n\t    *Sun\\ C*)\n\t      # Sun C++ 5.9\n\t      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t      _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld '\n\t      ;;\n\t    esac\n\t    ;;\n\tesac\n\t;;\n      lynxos*)\n\t;;\n      m88k*)\n\t;;\n      mvs*)\n\tcase $cc_basename in\n\t  cxx*)\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-W c,exportall'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      netbsd*)\n\t;;\n      *qnx* | *nto*)\n        # QNX uses GNU C++, but need to define -shared option too, otherwise\n        # it will coredump.\n        _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared'\n        ;;\n      osf3* | osf4* | osf5*)\n\tcase $cc_basename in\n\t  KCC*)\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='--backend -Wl,'\n\t    ;;\n\t  RCC*)\n\t    # Rational C++ 2.4.1\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic'\n\t    ;;\n\t  cxx*)\n\t    # Digital/Compaq C++\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    # Make sure the PIC flag is empty.  It appears that all Alpha\n\t    # Linux and Compaq Tru64 Unix objects are PIC.\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)=\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      psos*)\n\t;;\n      solaris*)\n\tcase $cc_basename in\n\t  CC* | sunCC*)\n\t    # Sun C++ 4.2, 5.x and Centerline C++\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld '\n\t    ;;\n\t  gcx*)\n\t    # Green Hills C++ Compiler\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      sunos4*)\n\tcase $cc_basename in\n\t  CC*)\n\t    # Sun C++ 4.x\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t    ;;\n\t  lcc*)\n\t    # Lucid\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*)\n\tcase $cc_basename in\n\t  CC*)\n\t    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t    _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t    ;;\n\tesac\n\t;;\n      tandem*)\n\tcase $cc_basename in\n\t  NCC*)\n\t    # NonStop-UX NCC 3.20\n\t    _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t    ;;\n\t  *)\n\t    ;;\n\tesac\n\t;;\n      vxworks*)\n\t;;\n      *)\n\t_LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no\n\t;;\n    esac\n  fi\n],\n[\n  if test yes = \"$GCC\"; then\n    _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n    _LT_TAGVAR(lt_prog_compiler_static, $1)='-static'\n\n    case $host_os in\n      aix*)\n      # All AIX code is PIC.\n      if test ia64 = \"$host_cpu\"; then\n\t# AIX 5 now supports IA64 processor\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      fi\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n      ;;\n\n    amigaos*)\n      case $host_cpu in\n      powerpc)\n            # see comment about AmigaOS4 .so support\n            _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n        ;;\n      m68k)\n            # FIXME: we need at least 68020 code to build shared libraries, but\n            # adding the '-m68020' flag to GCC prevents building anything better,\n            # like '-m68040'.\n            _LT_TAGVAR(lt_prog_compiler_pic, $1)='-m68020 -resident32 -malways-restore-a4'\n        ;;\n      esac\n      ;;\n\n    beos* | irix5* | irix6* | nonstopux* | osf3* | osf4* | osf5*)\n      # PIC is the default for these OSes.\n      ;;\n\n    mingw* | cygwin* | pw32* | os2* | cegcc*)\n      # This hack is so that the source file can tell whether it is being\n      # built for inclusion in a dll (and should export symbols for example).\n      # Although the cygwin gcc ignores -fPIC, still need this for old-style\n      # (--disable-auto-import) libraries\n      m4_if([$1], [GCJ], [],\n\t[_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT'])\n      case $host_os in\n      os2*)\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static'\n\t;;\n      esac\n      ;;\n\n    darwin* | rhapsody*)\n      # PIC is the default on this platform\n      # Common symbols not allowed in MH_DYLIB files\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common'\n      ;;\n\n    haiku*)\n      # PIC is the default for Haiku.\n      # The \"-static\" flag exists, but is broken.\n      _LT_TAGVAR(lt_prog_compiler_static, $1)=\n      ;;\n\n    hpux*)\n      # PIC is the default for 64-bit PA HP-UX, but not for 32-bit\n      # PA HP-UX.  On IA64 HP-UX, PIC is the default but the pic flag\n      # sets the default TLS model and affects inlining.\n      case $host_cpu in\n      hppa*64*)\n\t# +Z the default\n\t;;\n      *)\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n\t;;\n      esac\n      ;;\n\n    interix[[3-9]]*)\n      # Interix 3.x gcc -fpic/-fPIC options generate broken code.\n      # Instead, we relocate shared libraries at runtime.\n      ;;\n\n    msdosdjgpp*)\n      # Just because we use GCC doesn't mean we suddenly get shared libraries\n      # on systems that don't support them.\n      _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no\n      enable_shared=no\n      ;;\n\n    *nto* | *qnx*)\n      # QNX uses GNU C++, but need to define -shared option too, otherwise\n      # it will coredump.\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared'\n      ;;\n\n    sysv4*MP*)\n      if test -d /usr/nec; then\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)=-Kconform_pic\n      fi\n      ;;\n\n    *)\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n      ;;\n    esac\n\n    case $cc_basename in\n    nvcc*) # Cuda Compiler Driver 2.2\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Xlinker '\n      if test -n \"$_LT_TAGVAR(lt_prog_compiler_pic, $1)\"; then\n        _LT_TAGVAR(lt_prog_compiler_pic, $1)=\"-Xcompiler $_LT_TAGVAR(lt_prog_compiler_pic, $1)\"\n      fi\n      ;;\n    esac\n  else\n    # PORTME Check for flag to pass linker flags through the system compiler.\n    case $host_os in\n    aix*)\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n      if test ia64 = \"$host_cpu\"; then\n\t# AIX 5 now supports IA64 processor\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      else\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-bnso -bI:/lib/syscalls.exp'\n      fi\n      ;;\n\n    darwin* | rhapsody*)\n      # PIC is the default on this platform\n      # Common symbols not allowed in MH_DYLIB files\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fno-common'\n      case $cc_basename in\n      nagfor*)\n        # NAG Fortran compiler\n        _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,-Wl,,'\n        _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC'\n        _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n        ;;\n      esac\n      ;;\n\n    mingw* | cygwin* | pw32* | os2* | cegcc*)\n      # This hack is so that the source file can tell whether it is being\n      # built for inclusion in a dll (and should export symbols for example).\n      m4_if([$1], [GCJ], [],\n\t[_LT_TAGVAR(lt_prog_compiler_pic, $1)='-DDLL_EXPORT'])\n      case $host_os in\n      os2*)\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-static'\n\t;;\n      esac\n      ;;\n\n    hpux9* | hpux10* | hpux11*)\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n      # PIC is the default for IA64 HP-UX and 64-bit HP-UX, but\n      # not for PA HP-UX.\n      case $host_cpu in\n      hppa*64*|ia64*)\n\t# +Z the default\n\t;;\n      *)\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='+Z'\n\t;;\n      esac\n      # Is there a better lt_prog_compiler_static that works with the bundled CC?\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='$wl-a ${wl}archive'\n      ;;\n\n    irix5* | irix6* | nonstopux*)\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n      # PIC (with -KPIC) is the default.\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared'\n      ;;\n\n    linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n      case $cc_basename in\n      # old Intel for x86_64, which still supported -KPIC.\n      ecc*)\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-static'\n        ;;\n      # icc used to be incompatible with GCC.\n      # ICC 10 doesn't accept -KPIC any more.\n      icc* | ifort*)\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-static'\n        ;;\n      # Lahey Fortran 8.1.\n      lf95*)\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='--shared'\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='--static'\n\t;;\n      nagfor*)\n\t# NAG Fortran compiler\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,-Wl,,'\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC'\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t;;\n      tcc*)\n\t# Fabrice Bellard et al's Tiny C Compiler\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-static'\n\t;;\n      pgcc* | pgf77* | pgf90* | pgf95* | pgfortran*)\n        # Portland Group compilers (*not* the Pentium gcc compiler,\n\t# which looks to be a dead project)\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic'\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n        ;;\n      ccc*)\n        _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n        # All Alpha code is PIC.\n        _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared'\n        ;;\n      xl* | bgxl* | bgf* | mpixl*)\n\t# IBM XL C 8.0/Fortran 10.1, 11.1 on PPC and BlueGene\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-qpic'\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-qstaticlink'\n\t;;\n      *)\n\tcase `$CC -V 2>&1 | $SED 5q` in\n\t*Sun\\ Ceres\\ Fortran* | *Sun*Fortran*\\ [[1-7]].* | *Sun*Fortran*\\ 8.[[0-3]]*)\n\t  # Sun Fortran 8.3 passes all unrecognized flags to the linker\n\t  _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t  _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t  _LT_TAGVAR(lt_prog_compiler_wl, $1)=''\n\t  ;;\n\t*Sun\\ F* | *Sun*Fortran*)\n\t  _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t  _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t  _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld '\n\t  ;;\n\t*Sun\\ C*)\n\t  # Sun C 5.9\n\t  _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n\t  _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t  _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t  ;;\n        *Intel*\\ [[CF]]*Compiler*)\n\t  _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t  _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC'\n\t  _LT_TAGVAR(lt_prog_compiler_static, $1)='-static'\n\t  ;;\n\t*Portland\\ Group*)\n\t  _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n\t  _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fpic'\n\t  _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n\t  ;;\n\tesac\n\t;;\n      esac\n      ;;\n\n    newsos6)\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      ;;\n\n    *nto* | *qnx*)\n      # QNX uses GNU C++, but need to define -shared option too, otherwise\n      # it will coredump.\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-fPIC -shared'\n      ;;\n\n    osf3* | osf4* | osf5*)\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n      # All OSF/1 code is PIC.\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared'\n      ;;\n\n    rdos*)\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-non_shared'\n      ;;\n\n    solaris*)\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      case $cc_basename in\n      f77* | f90* | f95* | sunf77* | sunf90* | sunf95*)\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld ';;\n      *)\n\t_LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,';;\n      esac\n      ;;\n\n    sunos4*)\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Qoption ld '\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-PIC'\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      ;;\n\n    sysv4 | sysv4.2uw2* | sysv4.3*)\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      ;;\n\n    sysv4*MP*)\n      if test -d /usr/nec; then\n\t_LT_TAGVAR(lt_prog_compiler_pic, $1)='-Kconform_pic'\n\t_LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      fi\n      ;;\n\n    sysv5* | unixware* | sco3.2v5* | sco5v6* | OpenUNIX*)\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-KPIC'\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      ;;\n\n    unicos*)\n      _LT_TAGVAR(lt_prog_compiler_wl, $1)='-Wl,'\n      _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no\n      ;;\n\n    uts4*)\n      _LT_TAGVAR(lt_prog_compiler_pic, $1)='-pic'\n      _LT_TAGVAR(lt_prog_compiler_static, $1)='-Bstatic'\n      ;;\n\n    *)\n      _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no\n      ;;\n    esac\n  fi\n])\ncase $host_os in\n  # For platforms that do not support PIC, -DPIC is meaningless:\n  *djgpp*)\n    _LT_TAGVAR(lt_prog_compiler_pic, $1)=\n    ;;\n  *)\n    _LT_TAGVAR(lt_prog_compiler_pic, $1)=\"$_LT_TAGVAR(lt_prog_compiler_pic, $1)@&t@m4_if([$1],[],[ -DPIC],[m4_if([$1],[CXX],[ -DPIC],[])])\"\n    ;;\nesac\n\nAC_CACHE_CHECK([for $compiler option to produce PIC],\n  [_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)],\n  [_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)=$_LT_TAGVAR(lt_prog_compiler_pic, $1)])\n_LT_TAGVAR(lt_prog_compiler_pic, $1)=$_LT_TAGVAR(lt_cv_prog_compiler_pic, $1)\n\n#\n# Check to make sure the PIC flag actually works.\n#\nif test -n \"$_LT_TAGVAR(lt_prog_compiler_pic, $1)\"; then\n  _LT_COMPILER_OPTION([if $compiler PIC flag $_LT_TAGVAR(lt_prog_compiler_pic, $1) works],\n    [_LT_TAGVAR(lt_cv_prog_compiler_pic_works, $1)],\n    [$_LT_TAGVAR(lt_prog_compiler_pic, $1)@&t@m4_if([$1],[],[ -DPIC],[m4_if([$1],[CXX],[ -DPIC],[])])], [],\n    [case $_LT_TAGVAR(lt_prog_compiler_pic, $1) in\n     \"\" | \" \"*) ;;\n     *) _LT_TAGVAR(lt_prog_compiler_pic, $1)=\" $_LT_TAGVAR(lt_prog_compiler_pic, $1)\" ;;\n     esac],\n    [_LT_TAGVAR(lt_prog_compiler_pic, $1)=\n     _LT_TAGVAR(lt_prog_compiler_can_build_shared, $1)=no])\nfi\n_LT_TAGDECL([pic_flag], [lt_prog_compiler_pic], [1],\n\t[Additional compiler flags for building library objects])\n\n_LT_TAGDECL([wl], [lt_prog_compiler_wl], [1],\n\t[How to pass a linker flag through the compiler])\n#\n# Check to make sure the static flag actually works.\n#\nwl=$_LT_TAGVAR(lt_prog_compiler_wl, $1) eval lt_tmp_static_flag=\\\"$_LT_TAGVAR(lt_prog_compiler_static, $1)\\\"\n_LT_LINKER_OPTION([if $compiler static flag $lt_tmp_static_flag works],\n  _LT_TAGVAR(lt_cv_prog_compiler_static_works, $1),\n  $lt_tmp_static_flag,\n  [],\n  [_LT_TAGVAR(lt_prog_compiler_static, $1)=])\n_LT_TAGDECL([link_static_flag], [lt_prog_compiler_static], [1],\n\t[Compiler flag to prevent dynamic linking])\n])# _LT_COMPILER_PIC\n\n\n# _LT_LINKER_SHLIBS([TAGNAME])\n# ----------------------------\n# See if the linker supports building shared libraries.\nm4_defun([_LT_LINKER_SHLIBS],\n[AC_REQUIRE([LT_PATH_LD])dnl\nAC_REQUIRE([LT_PATH_NM])dnl\nm4_require([_LT_PATH_MANIFEST_TOOL])dnl\nm4_require([_LT_FILEUTILS_DEFAULTS])dnl\nm4_require([_LT_DECL_EGREP])dnl\nm4_require([_LT_DECL_SED])dnl\nm4_require([_LT_CMD_GLOBAL_SYMBOLS])dnl\nm4_require([_LT_TAG_COMPILER])dnl\nAC_MSG_CHECKING([whether the $compiler linker ($LD) supports shared libraries])\nm4_if([$1], [CXX], [\n  _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\\''s/.* //'\\'' | sort | uniq > $export_symbols'\n  _LT_TAGVAR(exclude_expsyms, $1)=['_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*']\n  case $host_os in\n  aix[[4-9]]*)\n    # If we're using GNU nm, then we don't want the \"-C\" option.\n    # -C means demangle to GNU nm, but means don't demangle to AIX nm.\n    # Without the \"-l\" option, or with the \"-B\" option, AIX nm treats\n    # weak defined symbols like other global defined symbols, whereas\n    # GNU nm marks them as \"W\".\n    # While the 'weak' keyword is ignored in the Export File, we need\n    # it in the Import File for the 'aix-soname' feature, so we have\n    # to replace the \"-B\" option with \"-P\" for AIX nm.\n    if $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then\n      _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\\''{ if (((\\$ 2 == \"T\") || (\\$ 2 == \"D\") || (\\$ 2 == \"B\") || (\\$ 2 == \"W\")) && ([substr](\\$ 3,1,1) != \".\")) { if (\\$ 2 == \"W\") { print \\$ 3 \" weak\" } else { print \\$ 3 } } }'\\'' | sort -u > $export_symbols'\n    else\n      _LT_TAGVAR(export_symbols_cmds, $1)='`func_echo_all $NM | $SED -e '\\''s/B\\([[^B]]*\\)$/P\\1/'\\''` -PCpgl $libobjs $convenience | awk '\\''{ if (((\\$ 2 == \"T\") || (\\$ 2 == \"D\") || (\\$ 2 == \"B\") || (\\$ 2 == \"L\") || (\\$ 2 == \"W\") || (\\$ 2 == \"V\") || (\\$ 2 == \"Z\")) && ([substr](\\$ 1,1,1) != \".\")) { if ((\\$ 2 == \"W\") || (\\$ 2 == \"V\") || (\\$ 2 == \"Z\")) { print \\$ 1 \" weak\" } else { print \\$ 1 } } }'\\'' | sort -u > $export_symbols'\n    fi\n    ;;\n  pw32*)\n    _LT_TAGVAR(export_symbols_cmds, $1)=$ltdll_cmds\n    ;;\n  cygwin* | mingw* | cegcc*)\n    case $cc_basename in\n    cl* | icl*)\n      _LT_TAGVAR(exclude_expsyms, $1)='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*'\n      ;;\n    *)\n      _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\\([[^ ]]*\\)/\\1 DATA/;s/^.*[[ ]]__nm__\\([[^ ]]*\\)[[ ]][[^ ]]*/\\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\\'' | sort | uniq > $export_symbols'\n      _LT_TAGVAR(exclude_expsyms, $1)=['[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname']\n      ;;\n    esac\n    ;;\n  *)\n    _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\\''s/.* //'\\'' | sort | uniq > $export_symbols'\n    ;;\n  esac\n], [\n  runpath_var=\n  _LT_TAGVAR(allow_undefined_flag, $1)=\n  _LT_TAGVAR(always_export_symbols, $1)=no\n  _LT_TAGVAR(archive_cmds, $1)=\n  _LT_TAGVAR(archive_expsym_cmds, $1)=\n  _LT_TAGVAR(compiler_needs_object, $1)=no\n  _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no\n  _LT_TAGVAR(export_dynamic_flag_spec, $1)=\n  _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED '\\''s/.* //'\\'' | sort | uniq > $export_symbols'\n  _LT_TAGVAR(hardcode_automatic, $1)=no\n  _LT_TAGVAR(hardcode_direct, $1)=no\n  _LT_TAGVAR(hardcode_direct_absolute, $1)=no\n  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=\n  _LT_TAGVAR(hardcode_libdir_separator, $1)=\n  _LT_TAGVAR(hardcode_minus_L, $1)=no\n  _LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported\n  _LT_TAGVAR(inherit_rpath, $1)=no\n  _LT_TAGVAR(link_all_deplibs, $1)=unknown\n  _LT_TAGVAR(module_cmds, $1)=\n  _LT_TAGVAR(module_expsym_cmds, $1)=\n  _LT_TAGVAR(old_archive_from_new_cmds, $1)=\n  _LT_TAGVAR(old_archive_from_expsyms_cmds, $1)=\n  _LT_TAGVAR(thread_safe_flag_spec, $1)=\n  _LT_TAGVAR(whole_archive_flag_spec, $1)=\n  # include_expsyms should be a list of space-separated symbols to be *always*\n  # included in the symbol list\n  _LT_TAGVAR(include_expsyms, $1)=\n  # exclude_expsyms can be an extended regexp of symbols to exclude\n  # it will be wrapped by ' (' and ')$', so one must not match beginning or\n  # end of line.  Example: 'a|bc|.*d.*' will exclude the symbols 'a' and 'bc',\n  # as well as any symbol that contains 'd'.\n  _LT_TAGVAR(exclude_expsyms, $1)=['_GLOBAL_OFFSET_TABLE_|_GLOBAL__F[ID]_.*']\n  # Although _GLOBAL_OFFSET_TABLE_ is a valid symbol C name, most a.out\n  # platforms (ab)use it in PIC code, but their linkers get confused if\n  # the symbol is explicitly referenced.  Since portable code cannot\n  # rely on this symbol name, it's probably fine to never include it in\n  # preloaded symbol tables.\n  # Exclude shared library initialization/finalization symbols.\ndnl Note also adjust exclude_expsyms for C++ above.\n  extract_expsyms_cmds=\n\n  case $host_os in\n  cygwin* | mingw* | pw32* | cegcc*)\n    # FIXME: the MSVC++ and ICC port hasn't been tested in a loooong time\n    # When not using gcc, we currently assume that we are using\n    # Microsoft Visual C++ or Intel C++ Compiler.\n    if test yes != \"$GCC\"; then\n      with_gnu_ld=no\n    fi\n    ;;\n  interix*)\n    # we just hope/assume this is gcc and not c89 (= MSVC++ or ICC)\n    with_gnu_ld=yes\n    ;;\n  openbsd* | bitrig*)\n    with_gnu_ld=no\n    ;;\n  esac\n\n  _LT_TAGVAR(ld_shlibs, $1)=yes\n\n  # On some targets, GNU ld is compatible enough with the native linker\n  # that we're better off using the native interface for both.\n  lt_use_gnu_ld_interface=no\n  if test yes = \"$with_gnu_ld\"; then\n    case $host_os in\n      aix*)\n\t# The AIX port of GNU ld has always aspired to compatibility\n\t# with the native linker.  However, as the warning in the GNU ld\n\t# block says, versions before 2.19.5* couldn't really create working\n\t# shared libraries, regardless of the interface used.\n\tcase `$LD -v 2>&1` in\n\t  *\\ \\(GNU\\ Binutils\\)\\ 2.19.5*) ;;\n\t  *\\ \\(GNU\\ Binutils\\)\\ 2.[[2-9]]*) ;;\n\t  *\\ \\(GNU\\ Binutils\\)\\ [[3-9]]*) ;;\n\t  *)\n\t    lt_use_gnu_ld_interface=yes\n\t    ;;\n\tesac\n\t;;\n      *)\n\tlt_use_gnu_ld_interface=yes\n\t;;\n    esac\n  fi\n\n  if test yes = \"$lt_use_gnu_ld_interface\"; then\n    # If archive_cmds runs LD, not CC, wlarc should be empty\n    wlarc='$wl'\n\n    # Set some defaults for GNU ld with shared library support. These\n    # are reset later if shared libraries are not supported. Putting them\n    # here allows them to be overridden if necessary.\n    runpath_var=LD_RUN_PATH\n    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n    _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic'\n    # ancient GNU ld didn't support --whole-archive et. al.\n    if $LD --help 2>&1 | $GREP 'no-whole-archive' > /dev/null; then\n      _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive'\n    else\n      _LT_TAGVAR(whole_archive_flag_spec, $1)=\n    fi\n    supports_anon_versioning=no\n    case `$LD -v | $SED -e 's/([[^)]]\\+)\\s\\+//' 2>&1` in\n      *GNU\\ gold*) supports_anon_versioning=yes ;;\n      *\\ [[01]].* | *\\ 2.[[0-9]].* | *\\ 2.10.*) ;; # catch versions < 2.11\n      *\\ 2.11.93.0.2\\ *) supports_anon_versioning=yes ;; # RH7.3 ...\n      *\\ 2.11.92.0.12\\ *) supports_anon_versioning=yes ;; # Mandrake 8.2 ...\n      *\\ 2.11.*) ;; # other 2.11 versions\n      *) supports_anon_versioning=yes ;;\n    esac\n\n    # See if GNU ld supports shared libraries.\n    case $host_os in\n    aix[[3-9]]*)\n      # On AIX/PPC, the GNU linker is very broken\n      if test ia64 != \"$host_cpu\"; then\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n\tcat <<_LT_EOF 1>&2\n\n*** Warning: the GNU linker, at least up to release 2.19, is reported\n*** to be unable to reliably create shared libraries on AIX.\n*** Therefore, libtool is disabling shared libraries support.  If you\n*** really care for shared libraries, you may want to install binutils\n*** 2.20 or above, or modify your PATH so that a non-GNU linker is found.\n*** You will then need to restart the configuration process.\n\n_LT_EOF\n      fi\n      ;;\n\n    amigaos*)\n      case $host_cpu in\n      powerpc)\n            # see comment about AmigaOS4 .so support\n            _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n            _LT_TAGVAR(archive_expsym_cmds, $1)=''\n        ;;\n      m68k)\n            _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/a2ixlibrary.data~$ECHO \"#define NAME $libname\" > $output_objdir/a2ixlibrary.data~$ECHO \"#define LIBRARY_ID 1\" >> $output_objdir/a2ixlibrary.data~$ECHO \"#define VERSION $major\" >> $output_objdir/a2ixlibrary.data~$ECHO \"#define REVISION $revision\" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)'\n            _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n            _LT_TAGVAR(hardcode_minus_L, $1)=yes\n        ;;\n      esac\n      ;;\n\n    beos*)\n      if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\t_LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n\t# Joseph Beckenbach <jrb3@best.com> says some releases of gcc\n\t# support --undefined.  This deserves some investigation.  FIXME\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n      else\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n      fi\n      ;;\n\n    cygwin* | mingw* | pw32* | cegcc*)\n      # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless,\n      # as there is no search path for DLLs.\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n      _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-all-symbols'\n      _LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n      _LT_TAGVAR(always_export_symbols, $1)=no\n      _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes\n      _LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\\([[^ ]]*\\)/\\1 DATA/;s/^.*[[ ]]__nm__\\([[^ ]]*\\)[[ ]][[^ ]]*/\\1 DATA/;/^I[[ ]]/d;/^[[AITW]][[ ]]/s/.* //'\\'' | sort | uniq > $export_symbols'\n      _LT_TAGVAR(exclude_expsyms, $1)=['[_]+GLOBAL_OFFSET_TABLE_|[_]+GLOBAL__[FID]_.*|[_]+head_[A-Za-z0-9_]+_dll|[A-Za-z0-9_]+_dll_iname']\n\n      if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then\n        _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib'\n\t# If the export-symbols file already is a .def file, use it as\n\t# is; otherwise, prepend EXPORTS...\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then\n          cp $export_symbols $output_objdir/$soname.def;\n        else\n          echo EXPORTS > $output_objdir/$soname.def;\n          cat $export_symbols >> $output_objdir/$soname.def;\n        fi~\n        $CC -shared $output_objdir/$soname.def $libobjs $deplibs $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib'\n      else\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n      fi\n      ;;\n\n    haiku*)\n      _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n      _LT_TAGVAR(link_all_deplibs, $1)=yes\n      ;;\n\n    os2*)\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n      _LT_TAGVAR(hardcode_minus_L, $1)=yes\n      _LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n      shrext_cmds=.dll\n      _LT_TAGVAR(archive_cmds, $1)='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t$ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t$ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t$ECHO EXPORTS >> $output_objdir/$libname.def~\n\temxexp $libobjs | $SED /\"_DLL_InitTerm\"/d >> $output_objdir/$libname.def~\n\t$CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\temximp -o $lib $output_objdir/$libname.def'\n      _LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t$ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t$ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t$ECHO EXPORTS >> $output_objdir/$libname.def~\n\tprefix_cmds=\"$SED\"~\n\tif test EXPORTS = \"`$SED 1q $export_symbols`\"; then\n\t  prefix_cmds=\"$prefix_cmds -e 1d\";\n\tfi~\n\tprefix_cmds=\"$prefix_cmds -e \\\"s/^\\(.*\\)$/_\\1/g\\\"\"~\n\tcat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~\n\t$CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\temximp -o $lib $output_objdir/$libname.def'\n      _LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def'\n      _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes\n      _LT_TAGVAR(file_list_spec, $1)='@'\n      ;;\n\n    interix[[3-9]]*)\n      _LT_TAGVAR(hardcode_direct, $1)=no\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir'\n      _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n      # Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc.\n      # Instead, shared libraries are loaded at an image base (0x10000000 by\n      # default) and relocated if they conflict, which is a slow very memory\n      # consuming and fragmenting process.  To avoid this, we pick a random,\n      # 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link\n      # time.  Moving up from 0x10000000 also allows more sbrk(2) space.\n      _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \\* 262144 + 1342177280` -o $lib'\n      _LT_TAGVAR(archive_expsym_cmds, $1)='$SED \"s|^|_|\" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \\* 262144 + 1342177280` -o $lib'\n      ;;\n\n    gnu* | linux* | tpf* | k*bsd*-gnu | kopensolaris*-gnu)\n      tmp_diet=no\n      if test linux-dietlibc = \"$host_os\"; then\n\tcase $cc_basename in\n\t  diet\\ *) tmp_diet=yes;;\t# linux-dietlibc with static linking (!diet-dyn)\n\tesac\n      fi\n      if $LD --help 2>&1 | $EGREP ': supported targets:.* elf' > /dev/null \\\n\t && test no = \"$tmp_diet\"\n      then\n\ttmp_addflag=' $pic_flag'\n\ttmp_sharedflag='-shared'\n\tcase $cc_basename,$host_cpu in\n        pgcc*)\t\t\t\t# Portland Group C compiler\n\t  _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t  tmp_addflag=' $pic_flag'\n\t  ;;\n\tpgf77* | pgf90* | pgf95* | pgfortran*)\n\t\t\t\t\t# Portland Group f77 and f90 compilers\n\t  _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t  tmp_addflag=' $pic_flag -Mnomain' ;;\n\tecc*,ia64* | icc*,ia64*)\t# Intel C compiler on ia64\n\t  tmp_addflag=' -i_dynamic' ;;\n\tefc*,ia64* | ifort*,ia64*)\t# Intel Fortran compiler on ia64\n\t  tmp_addflag=' -i_dynamic -nofor_main' ;;\n\tifc* | ifort*)\t\t\t# Intel Fortran compiler\n\t  tmp_addflag=' -nofor_main' ;;\n\tlf95*)\t\t\t\t# Lahey Fortran 8.1\n\t  _LT_TAGVAR(whole_archive_flag_spec, $1)=\n\t  tmp_sharedflag='--shared' ;;\n        nagfor*)                        # NAGFOR 5.3\n          tmp_sharedflag='-Wl,-shared' ;;\n\txl[[cC]]* | bgxl[[cC]]* | mpixl[[cC]]*) # IBM XL C 8.0 on PPC (deal with xlf below)\n\t  tmp_sharedflag='-qmkshrobj'\n\t  tmp_addflag= ;;\n\tnvcc*)\t# Cuda Compiler Driver 2.2\n\t  _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t  _LT_TAGVAR(compiler_needs_object, $1)=yes\n\t  ;;\n\tesac\n\tcase `$CC -V 2>&1 | $SED 5q` in\n\t*Sun\\ C*)\t\t\t# Sun C 5.9\n\t  _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`new_convenience=; for conv in $convenience\\\"\\\"; do test -z \\\"$conv\\\" || new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t  _LT_TAGVAR(compiler_needs_object, $1)=yes\n\t  tmp_sharedflag='-G' ;;\n\t*Sun\\ F*)\t\t\t# Sun Fortran 8.3\n\t  tmp_sharedflag='-G' ;;\n\tesac\n\t_LT_TAGVAR(archive_cmds, $1)='$CC '\"$tmp_sharedflag\"\"$tmp_addflag\"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\n        if test yes = \"$supports_anon_versioning\"; then\n          _LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $output_objdir/$libname.ver~\n            cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $output_objdir/$libname.ver~\n            echo \"local: *; };\" >> $output_objdir/$libname.ver~\n            $CC '\"$tmp_sharedflag\"\"$tmp_addflag\"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib'\n        fi\n\n\tcase $cc_basename in\n\ttcc*)\n\t  _LT_TAGVAR(export_dynamic_flag_spec, $1)='-rdynamic'\n\t  ;;\n\txlf* | bgf* | bgxlf* | mpixlf*)\n\t  # IBM XL Fortran 10.1 on PPC cannot create shared libs itself\n\t  _LT_TAGVAR(whole_archive_flag_spec, $1)='--whole-archive$convenience --no-whole-archive'\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n\t  _LT_TAGVAR(archive_cmds, $1)='$LD -shared $libobjs $deplibs $linker_flags -soname $soname -o $lib'\n\t  if test yes = \"$supports_anon_versioning\"; then\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $output_objdir/$libname.ver~\n              cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $output_objdir/$libname.ver~\n              echo \"local: *; };\" >> $output_objdir/$libname.ver~\n              $LD -shared $libobjs $deplibs $linker_flags -soname $soname -version-script $output_objdir/$libname.ver -o $lib'\n\t  fi\n\t  ;;\n\tesac\n      else\n        _LT_TAGVAR(ld_shlibs, $1)=no\n      fi\n      ;;\n\n    netbsd*)\n      if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n\t_LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable $libobjs $deplibs $linker_flags -o $lib'\n\twlarc=\n      else\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n      fi\n      ;;\n\n    solaris*)\n      if $LD -v 2>&1 | $GREP 'BFD 2\\.8' > /dev/null; then\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n\tcat <<_LT_EOF 1>&2\n\n*** Warning: The releases 2.8.* of the GNU linker cannot reliably\n*** create shared libraries on Solaris systems.  Therefore, libtool\n*** is disabling shared libraries support.  We urge you to upgrade GNU\n*** binutils to release 2.9.1 or newer.  Another option is to modify\n*** your PATH or compiler configuration so that the native linker is\n*** used, and then restart.\n\n_LT_EOF\n      elif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n      else\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n      fi\n      ;;\n\n    sysv5* | sco3.2v5* | sco5v6* | unixware* | OpenUNIX*)\n      case `$LD -v 2>&1` in\n        *\\ [[01]].* | *\\ 2.[[0-9]].* | *\\ 2.1[[0-5]].*)\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n\tcat <<_LT_EOF 1>&2\n\n*** Warning: Releases of the GNU linker prior to 2.16.91.0.3 cannot\n*** reliably create shared libraries on SCO systems.  Therefore, libtool\n*** is disabling shared libraries support.  We urge you to upgrade GNU\n*** binutils to release 2.16.91.0.3 or newer.  Another option is to modify\n*** your PATH or compiler configuration so that the native linker is\n*** used, and then restart.\n\n_LT_EOF\n\t;;\n\t*)\n\t  # For security reasons, it is highly recommended that you always\n\t  # use absolute paths for naming shared libraries, and exclude the\n\t  # DT_RUNPATH tag from executables and libraries.  But doing so\n\t  # requires that you compile everything twice, which is a pain.\n\t  if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t  else\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t  fi\n\t;;\n      esac\n      ;;\n\n    sunos4*)\n      _LT_TAGVAR(archive_cmds, $1)='$LD -assert pure-text -Bshareable -o $lib $libobjs $deplibs $linker_flags'\n      wlarc=\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    *)\n      if $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n      else\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n      fi\n      ;;\n    esac\n\n    if test no = \"$_LT_TAGVAR(ld_shlibs, $1)\"; then\n      runpath_var=\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=\n      _LT_TAGVAR(export_dynamic_flag_spec, $1)=\n      _LT_TAGVAR(whole_archive_flag_spec, $1)=\n    fi\n  else\n    # PORTME fill in a description of your system's linker (not GNU ld)\n    case $host_os in\n    aix3*)\n      _LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n      _LT_TAGVAR(always_export_symbols, $1)=yes\n      _LT_TAGVAR(archive_expsym_cmds, $1)='$LD -o $output_objdir/$soname $libobjs $deplibs $linker_flags -bE:$export_symbols -T512 -H512 -bM:SRE~$AR $AR_FLAGS $lib $output_objdir/$soname'\n      # Note: this linker hardcodes the directories in LIBPATH if there\n      # are no directories specified by -L.\n      _LT_TAGVAR(hardcode_minus_L, $1)=yes\n      if test yes = \"$GCC\" && test -z \"$lt_prog_compiler_static\"; then\n\t# Neither direct hardcoding nor static linking is supported with a\n\t# broken collect2.\n\t_LT_TAGVAR(hardcode_direct, $1)=unsupported\n      fi\n      ;;\n\n    aix[[4-9]]*)\n      if test ia64 = \"$host_cpu\"; then\n\t# On IA64, the linker does run time linking by default, so we don't\n\t# have to do anything special.\n\taix_use_runtimelinking=no\n\texp_sym_flag='-Bexport'\n\tno_entry_flag=\n      else\n\t# If we're using GNU nm, then we don't want the \"-C\" option.\n\t# -C means demangle to GNU nm, but means don't demangle to AIX nm.\n\t# Without the \"-l\" option, or with the \"-B\" option, AIX nm treats\n\t# weak defined symbols like other global defined symbols, whereas\n\t# GNU nm marks them as \"W\".\n\t# While the 'weak' keyword is ignored in the Export File, we need\n\t# it in the Import File for the 'aix-soname' feature, so we have\n\t# to replace the \"-B\" option with \"-P\" for AIX nm.\n\tif $NM -V 2>&1 | $GREP 'GNU' > /dev/null; then\n\t  _LT_TAGVAR(export_symbols_cmds, $1)='$NM -Bpg $libobjs $convenience | awk '\\''{ if (((\\$ 2 == \"T\") || (\\$ 2 == \"D\") || (\\$ 2 == \"B\") || (\\$ 2 == \"W\")) && ([substr](\\$ 3,1,1) != \".\")) { if (\\$ 2 == \"W\") { print \\$ 3 \" weak\" } else { print \\$ 3 } } }'\\'' | sort -u > $export_symbols'\n\telse\n\t  _LT_TAGVAR(export_symbols_cmds, $1)='`func_echo_all $NM | $SED -e '\\''s/B\\([[^B]]*\\)$/P\\1/'\\''` -PCpgl $libobjs $convenience | awk '\\''{ if (((\\$ 2 == \"T\") || (\\$ 2 == \"D\") || (\\$ 2 == \"B\") || (\\$ 2 == \"L\") || (\\$ 2 == \"W\") || (\\$ 2 == \"V\") || (\\$ 2 == \"Z\")) && ([substr](\\$ 1,1,1) != \".\")) { if ((\\$ 2 == \"W\") || (\\$ 2 == \"V\") || (\\$ 2 == \"Z\")) { print \\$ 1 \" weak\" } else { print \\$ 1 } } }'\\'' | sort -u > $export_symbols'\n\tfi\n\taix_use_runtimelinking=no\n\n\t# Test if we are trying to use run time linking or normal\n\t# AIX style linking. If -brtl is somewhere in LDFLAGS, we\n\t# have runtime linking enabled, and use it for executables.\n\t# For shared libraries, we enable/disable runtime linking\n\t# depending on the kind of the shared library created -\n\t# when \"with_aix_soname,aix_use_runtimelinking\" is:\n\t# \"aix,no\"   lib.a(lib.so.V) shared, rtl:no,  for executables\n\t# \"aix,yes\"  lib.so          shared, rtl:yes, for executables\n\t#            lib.a           static archive\n\t# \"both,no\"  lib.so.V(shr.o) shared, rtl:yes\n\t#            lib.a(lib.so.V) shared, rtl:no,  for executables\n\t# \"both,yes\" lib.so.V(shr.o) shared, rtl:yes, for executables\n\t#            lib.a(lib.so.V) shared, rtl:no\n\t# \"svr4,*\"   lib.so.V(shr.o) shared, rtl:yes, for executables\n\t#            lib.a           static archive\n\tcase $host_os in aix4.[[23]]|aix4.[[23]].*|aix[[5-9]]*)\n\t  for ld_flag in $LDFLAGS; do\n\t  if (test x-brtl = \"x$ld_flag\" || test x-Wl,-brtl = \"x$ld_flag\"); then\n\t    aix_use_runtimelinking=yes\n\t    break\n\t  fi\n\t  done\n\t  if test svr4,no = \"$with_aix_soname,$aix_use_runtimelinking\"; then\n\t    # With aix-soname=svr4, we create the lib.so.V shared archives only,\n\t    # so we don't have lib.a shared libs to link our executables.\n\t    # We have to force runtime linking in this case.\n\t    aix_use_runtimelinking=yes\n\t    LDFLAGS=\"$LDFLAGS -Wl,-brtl\"\n\t  fi\n\t  ;;\n\tesac\n\n\texp_sym_flag='-bexport'\n\tno_entry_flag='-bnoentry'\n      fi\n\n      # When large executables or shared objects are built, AIX ld can\n      # have problems creating the table of contents.  If linking a library\n      # or program results in \"error TOC overflow\" add -mminimal-toc to\n      # CXXFLAGS/CFLAGS for g++/gcc.  In the cases where that is not\n      # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS.\n\n      _LT_TAGVAR(archive_cmds, $1)=''\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n      _LT_TAGVAR(hardcode_direct_absolute, $1)=yes\n      _LT_TAGVAR(hardcode_libdir_separator, $1)=':'\n      _LT_TAGVAR(link_all_deplibs, $1)=yes\n      _LT_TAGVAR(file_list_spec, $1)='$wl-f,'\n      case $with_aix_soname,$aix_use_runtimelinking in\n      aix,*) ;; # traditional, no import file\n      svr4,* | *,yes) # use import file\n\t# The Import File defines what to hardcode.\n\t_LT_TAGVAR(hardcode_direct, $1)=no\n\t_LT_TAGVAR(hardcode_direct_absolute, $1)=no\n\t;;\n      esac\n\n      if test yes = \"$GCC\"; then\n\tcase $host_os in aix4.[[012]]|aix4.[[012]].*)\n\t# We only want to do this on AIX 4.2 and lower, the check\n\t# below for broken collect2 doesn't work under 4.3+\n\t  collect2name=`$CC -print-prog-name=collect2`\n\t  if test -f \"$collect2name\" &&\n\t   strings \"$collect2name\" | $GREP resolve_lib_name >/dev/null\n\t  then\n\t  # We have reworked collect2\n\t  :\n\t  else\n\t  # We have old collect2\n\t  _LT_TAGVAR(hardcode_direct, $1)=unsupported\n\t  # It fails to find uninstalled libraries when the uninstalled\n\t  # path is not listed in the libpath.  Setting hardcode_minus_L\n\t  # to unsupported forces relinking\n\t  _LT_TAGVAR(hardcode_minus_L, $1)=yes\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n\t  _LT_TAGVAR(hardcode_libdir_separator, $1)=\n\t  fi\n\t  ;;\n\tesac\n\tshared_flag='-shared'\n\tif test yes = \"$aix_use_runtimelinking\"; then\n\t  shared_flag=\"$shared_flag \"'$wl-G'\n\tfi\n\t# Need to ensure runtime linking is disabled for the traditional\n\t# shared library, or the linker may eventually find shared libraries\n\t# /with/ Import File - we do not want to mix them.\n\tshared_flag_aix='-shared'\n\tshared_flag_svr4='-shared $wl-G'\n      else\n\t# not using gcc\n\tif test ia64 = \"$host_cpu\"; then\n\t# VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release\n\t# chokes on -Wl,-G. The following line is correct:\n\t  shared_flag='-G'\n\telse\n\t  if test yes = \"$aix_use_runtimelinking\"; then\n\t    shared_flag='$wl-G'\n\t  else\n\t    shared_flag='$wl-bM:SRE'\n\t  fi\n\t  shared_flag_aix='$wl-bM:SRE'\n\t  shared_flag_svr4='$wl-G'\n\tfi\n      fi\n\n      _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-bexpall'\n      # It seems that -bexpall does not export symbols beginning with\n      # underscore (_), so it is better to generate a list of symbols to export.\n      _LT_TAGVAR(always_export_symbols, $1)=yes\n      if test aix,yes = \"$with_aix_soname,$aix_use_runtimelinking\"; then\n\t# Warning - without using the other runtime loading flags (-brtl),\n\t# -berok will link without error, but may produce a broken library.\n\t_LT_TAGVAR(allow_undefined_flag, $1)='-berok'\n        # Determine the default libpath from the value encoded in an\n        # empty executable.\n        _LT_SYS_MODULE_PATH_AIX([$1])\n        _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'\"$aix_libpath\"\n        _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n \"$allow_undefined_flag\"; then func_echo_all \"$wl$allow_undefined_flag\"; else :; fi` $wl'$exp_sym_flag:\\$export_symbols' '$shared_flag\n      else\n\tif test ia64 = \"$host_cpu\"; then\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $libdir:/usr/lib:/lib'\n\t  _LT_TAGVAR(allow_undefined_flag, $1)=\"-z nodefs\"\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)=\"\\$CC $shared_flag\"' -o $output_objdir/$soname $libobjs $deplibs '\"\\$wl$no_entry_flag\"' $compiler_flags $wl$allow_undefined_flag '\"\\$wl$exp_sym_flag:\\$export_symbols\"\n\telse\n\t # Determine the default libpath from the value encoded in an\n\t # empty executable.\n\t _LT_SYS_MODULE_PATH_AIX([$1])\n\t _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'\"$aix_libpath\"\n\t  # Warning - without using the other run time loading flags,\n\t  # -berok will link without error, but may produce a broken library.\n\t  _LT_TAGVAR(no_undefined_flag, $1)=' $wl-bernotok'\n\t  _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-berok'\n\t  if test yes = \"$with_gnu_ld\"; then\n\t    # We only use this code for GNU lds that support --whole-archive.\n\t    _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive'\n\t  else\n\t    # Exported symbols can be pulled into shared objects from archives\n\t    _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience'\n\t  fi\n\t  _LT_TAGVAR(archive_cmds_need_lc, $1)=yes\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d'\n\t  # -brtl affects multiple linker settings, -berok does not and is overridden later\n\t  compiler_flags_filtered='`func_echo_all \"$compiler_flags \" | $SED -e \"s%-brtl\\\\([[, ]]\\\\)%-berok\\\\1%g\"`'\n\t  if test svr4 != \"$with_aix_soname\"; then\n\t    # This is similar to how AIX traditionally builds its shared libraries.\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)=\"$_LT_TAGVAR(archive_expsym_cmds, $1)\"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname'\n\t  fi\n\t  if test aix != \"$with_aix_soname\"; then\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)=\"$_LT_TAGVAR(archive_expsym_cmds, $1)\"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all \"#! $soname($shared_archive_member_spec.o)\"; if test shr_64 = \"$shared_archive_member_spec\"; then func_echo_all \"# 64\"; else func_echo_all \"# 32\"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp'\n\t  else\n\t    # used by -dlpreopen to get the symbols\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)=\"$_LT_TAGVAR(archive_expsym_cmds, $1)\"'~$MV  $output_objdir/$realname.d/$soname $output_objdir'\n\t  fi\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)=\"$_LT_TAGVAR(archive_expsym_cmds, $1)\"'~$RM -r $output_objdir/$realname.d'\n\tfi\n      fi\n      ;;\n\n    amigaos*)\n      case $host_cpu in\n      powerpc)\n            # see comment about AmigaOS4 .so support\n            _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n            _LT_TAGVAR(archive_expsym_cmds, $1)=''\n        ;;\n      m68k)\n            _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/a2ixlibrary.data~$ECHO \"#define NAME $libname\" > $output_objdir/a2ixlibrary.data~$ECHO \"#define LIBRARY_ID 1\" >> $output_objdir/a2ixlibrary.data~$ECHO \"#define VERSION $major\" >> $output_objdir/a2ixlibrary.data~$ECHO \"#define REVISION $revision\" >> $output_objdir/a2ixlibrary.data~$AR $AR_FLAGS $lib $libobjs~$RANLIB $lib~(cd $output_objdir && a2ixlibrary -32)'\n            _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n            _LT_TAGVAR(hardcode_minus_L, $1)=yes\n        ;;\n      esac\n      ;;\n\n    bsdi[[45]]*)\n      _LT_TAGVAR(export_dynamic_flag_spec, $1)=-rdynamic\n      ;;\n\n    cygwin* | mingw* | pw32* | cegcc*)\n      # When not using gcc, we currently assume that we are using\n      # Microsoft Visual C++ or Intel C++ Compiler.\n      # hardcode_libdir_flag_spec is actually meaningless, as there is\n      # no search path for DLLs.\n      case $cc_basename in\n      cl* | icl*)\n\t# Native MSVC or ICC\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' '\n\t_LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n\t_LT_TAGVAR(always_export_symbols, $1)=yes\n\t_LT_TAGVAR(file_list_spec, $1)='@'\n\t# Tell ltmain to make .lib files, not .a files.\n\tlibext=lib\n\t# Tell ltmain to make .dll files, not .so files.\n\tshrext_cmds=.dll\n\t# FIXME: Setting linknames here is a bad hack.\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:\"$tool_output_objdir$libname.dll.lib\"~linknames='\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then\n            cp \"$export_symbols\" \"$output_objdir/$soname.def\";\n            echo \"$tool_output_objdir$soname.def\" > \"$output_objdir/$soname.exp\";\n          else\n            $SED -e '\\''s/^/-link -EXPORT:/'\\'' < $export_symbols > $output_objdir/$soname.exp;\n          fi~\n          $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs \"@$tool_output_objdir$soname.exp\" -Wl,-DLL,-IMPLIB:\"$tool_output_objdir$libname.dll.lib\"~\n          linknames='\n\t# The linker will not automatically build a static lib if we build a DLL.\n\t# _LT_TAGVAR(old_archive_from_new_cmds, $1)='true'\n\t_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes\n\t_LT_TAGVAR(exclude_expsyms, $1)='_NULL_IMPORT_DESCRIPTOR|_IMPORT_DESCRIPTOR_.*'\n\t_LT_TAGVAR(export_symbols_cmds, $1)='$NM $libobjs $convenience | $global_symbol_pipe | $SED -e '\\''/^[[BCDGRS]][[ ]]/s/.*[[ ]]\\([[^ ]]*\\)/\\1,DATA/'\\'' | $SED -e '\\''/^[[AITW]][[ ]]/s/.*[[ ]]//'\\'' | sort | uniq > $export_symbols'\n\t# Don't use ranlib\n\t_LT_TAGVAR(old_postinstall_cmds, $1)='chmod 644 $oldlib'\n\t_LT_TAGVAR(postlink_cmds, $1)='lt_outputfile=\"@OUTPUT@\"~\n          lt_tool_outputfile=\"@TOOL_OUTPUT@\"~\n          case $lt_outputfile in\n            *.exe|*.EXE) ;;\n            *)\n              lt_outputfile=$lt_outputfile.exe\n              lt_tool_outputfile=$lt_tool_outputfile.exe\n              ;;\n          esac~\n          if test : != \"$MANIFEST_TOOL\" && test -f \"$lt_outputfile.manifest\"; then\n            $MANIFEST_TOOL -manifest \"$lt_tool_outputfile.manifest\" -outputresource:\"$lt_tool_outputfile\" || exit 1;\n            $RM \"$lt_outputfile.manifest\";\n          fi'\n\t;;\n      *)\n\t# Assume MSVC and ICC wrapper\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' '\n\t_LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n\t# Tell ltmain to make .lib files, not .a files.\n\tlibext=lib\n\t# Tell ltmain to make .dll files, not .so files.\n\tshrext_cmds=.dll\n\t# FIXME: Setting linknames here is a bad hack.\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -o $lib $libobjs $compiler_flags `func_echo_all \"$deplibs\" | $SED '\\''s/ -lc$//'\\''` -link -dll~linknames='\n\t# The linker will automatically build a .lib file if we build a DLL.\n\t_LT_TAGVAR(old_archive_from_new_cmds, $1)='true'\n\t# FIXME: Should let the user specify the lib program.\n\t_LT_TAGVAR(old_archive_cmds, $1)='lib -OUT:$oldlib$oldobjs$old_deplibs'\n\t_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes\n\t;;\n      esac\n      ;;\n\n    darwin* | rhapsody*)\n      _LT_DARWIN_LINKER_FEATURES($1)\n      ;;\n\n    dgux*)\n      _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    # FreeBSD 2.2.[012] allows us to include c++rt0.o to get C++ constructor\n    # support.  Future versions do this automatically, but an explicit c++rt0.o\n    # does not break anything, and helps significantly (at the cost of a little\n    # extra space).\n    freebsd2.2*)\n      _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags /usr/lib/c++rt0.o'\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir'\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    # Unfortunately, older versions of FreeBSD 2 do not have this feature.\n    freebsd2.*)\n      _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags'\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n      _LT_TAGVAR(hardcode_minus_L, $1)=yes\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    # FreeBSD 3 and greater uses gcc -shared to do shared libraries.\n    freebsd* | dragonfly* | midnightbsd*)\n      _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags'\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir'\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    hpux9*)\n      if test yes = \"$GCC\"; then\n\t_LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $libobjs $deplibs $compiler_flags~test \"x$output_objdir/$soname\" = \"x$lib\" || mv $output_objdir/$soname $lib'\n      else\n\t_LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$LD -b +b $install_libdir -o $output_objdir/$soname $libobjs $deplibs $linker_flags~test \"x$output_objdir/$soname\" = \"x$lib\" || mv $output_objdir/$soname $lib'\n      fi\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir'\n      _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n\n      # hardcode_minus_L: Not really in the search PATH,\n      # but as the default location of the library.\n      _LT_TAGVAR(hardcode_minus_L, $1)=yes\n      _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n      ;;\n\n    hpux10*)\n      if test yes,no = \"$GCC,$with_gnu_ld\"; then\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'\n      else\n\t_LT_TAGVAR(archive_cmds, $1)='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags'\n      fi\n      if test no = \"$with_gnu_ld\"; then\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir'\n\t_LT_TAGVAR(hardcode_libdir_separator, $1)=:\n\t_LT_TAGVAR(hardcode_direct, $1)=yes\n\t_LT_TAGVAR(hardcode_direct_absolute, $1)=yes\n\t_LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n\t# hardcode_minus_L: Not really in the search PATH,\n\t# but as the default location of the library.\n\t_LT_TAGVAR(hardcode_minus_L, $1)=yes\n      fi\n      ;;\n\n    hpux11*)\n      if test yes,no = \"$GCC,$with_gnu_ld\"; then\n\tcase $host_cpu in\n\thppa*64*)\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\tia64*)\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\t*)\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\tesac\n      else\n\tcase $host_cpu in\n\thppa*64*)\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\tia64*)\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\t*)\n\tm4_if($1, [], [\n\t  # Older versions of the 11.00 compiler do not understand -b yet\n\t  # (HP92453-01 A.11.01.20 doesn't, HP92453-01 B.11.X.35175-35176.GP does)\n\t  _LT_LINKER_OPTION([if $CC understands -b],\n\t    _LT_TAGVAR(lt_cv_prog_compiler__b, $1), [-b],\n\t    [_LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'],\n\t    [_LT_TAGVAR(archive_cmds, $1)='$LD -b +h $soname +b $install_libdir -o $lib $libobjs $deplibs $linker_flags'])],\n\t  [_LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $libobjs $deplibs $compiler_flags'])\n\t  ;;\n\tesac\n      fi\n      if test no = \"$with_gnu_ld\"; then\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir'\n\t_LT_TAGVAR(hardcode_libdir_separator, $1)=:\n\n\tcase $host_cpu in\n\thppa*64*|ia64*)\n\t  _LT_TAGVAR(hardcode_direct, $1)=no\n\t  _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n\t  ;;\n\t*)\n\t  _LT_TAGVAR(hardcode_direct, $1)=yes\n\t  _LT_TAGVAR(hardcode_direct_absolute, $1)=yes\n\t  _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n\n\t  # hardcode_minus_L: Not really in the search PATH,\n\t  # but as the default location of the library.\n\t  _LT_TAGVAR(hardcode_minus_L, $1)=yes\n\t  ;;\n\tesac\n      fi\n      ;;\n\n    irix5* | irix6* | nonstopux*)\n      if test yes = \"$GCC\"; then\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t# Try to use the -exported_symbol ld option, if it does not\n\t# work, assume that -exports_file does not work either and\n\t# implicitly export all symbols.\n\t# This should be the same for all languages, so no per-tag cache variable.\n\tAC_CACHE_CHECK([whether the $host_os linker accepts -exported_symbol],\n\t  [lt_cv_irix_exported_symbol],\n\t  [save_LDFLAGS=$LDFLAGS\n\t   LDFLAGS=\"$LDFLAGS -shared $wl-exported_symbol ${wl}foo $wl-update_registry $wl/dev/null\"\n\t   AC_LINK_IFELSE(\n\t     [AC_LANG_SOURCE(\n\t        [AC_LANG_CASE([C], [[int foo (void) { return 0; }]],\n\t\t\t      [C++], [[int foo (void) { return 0; }]],\n\t\t\t      [Fortran 77], [[\n      subroutine foo\n      end]],\n\t\t\t      [Fortran], [[\n      subroutine foo\n      end]])])],\n\t      [lt_cv_irix_exported_symbol=yes],\n\t      [lt_cv_irix_exported_symbol=no])\n           LDFLAGS=$save_LDFLAGS])\n\tif test yes = \"$lt_cv_irix_exported_symbol\"; then\n          _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations $wl-exports_file $wl$export_symbols -o $lib'\n\tfi\n      else\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -exports_file $export_symbols -o $lib'\n      fi\n      _LT_TAGVAR(archive_cmds_need_lc, $1)='no'\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n      _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n      _LT_TAGVAR(inherit_rpath, $1)=yes\n      _LT_TAGVAR(link_all_deplibs, $1)=yes\n      ;;\n\n    linux*)\n      case $cc_basename in\n      tcc*)\n\t# Fabrice Bellard et al's Tiny C Compiler\n\t_LT_TAGVAR(ld_shlibs, $1)=yes\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags'\n\t;;\n      esac\n      ;;\n\n    netbsd*)\n      if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n\t_LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable -o $lib $libobjs $deplibs $linker_flags'  # a.out\n      else\n\t_LT_TAGVAR(archive_cmds, $1)='$LD -shared -o $lib $libobjs $deplibs $linker_flags'      # ELF\n      fi\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir'\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    newsos6)\n      _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n      _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    *nto* | *qnx*)\n      ;;\n\n    openbsd* | bitrig*)\n      if test -f /usr/libexec/ld.so; then\n\t_LT_TAGVAR(hardcode_direct, $1)=yes\n\t_LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n\t_LT_TAGVAR(hardcode_direct_absolute, $1)=yes\n\tif test -z \"`echo __ELF__ | $CC -E - | $GREP __ELF__`\"; then\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags'\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags $wl-retain-symbols-file,$export_symbols'\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir'\n\t  _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n\telse\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -o $lib $libobjs $deplibs $compiler_flags'\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir'\n\tfi\n      else\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n      fi\n      ;;\n\n    os2*)\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n      _LT_TAGVAR(hardcode_minus_L, $1)=yes\n      _LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n      shrext_cmds=.dll\n      _LT_TAGVAR(archive_cmds, $1)='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t$ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t$ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t$ECHO EXPORTS >> $output_objdir/$libname.def~\n\temxexp $libobjs | $SED /\"_DLL_InitTerm\"/d >> $output_objdir/$libname.def~\n\t$CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\temximp -o $lib $output_objdir/$libname.def'\n      _LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t$ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t$ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t$ECHO EXPORTS >> $output_objdir/$libname.def~\n\tprefix_cmds=\"$SED\"~\n\tif test EXPORTS = \"`$SED 1q $export_symbols`\"; then\n\t  prefix_cmds=\"$prefix_cmds -e 1d\";\n\tfi~\n\tprefix_cmds=\"$prefix_cmds -e \\\"s/^\\(.*\\)$/_\\1/g\\\"\"~\n\tcat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~\n\t$CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\temximp -o $lib $output_objdir/$libname.def'\n      _LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def'\n      _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes\n      _LT_TAGVAR(file_list_spec, $1)='@'\n      ;;\n\n    osf3*)\n      if test yes = \"$GCC\"; then\n\t_LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\\*'\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n      else\n\t_LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \\*'\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n      fi\n      _LT_TAGVAR(archive_cmds_need_lc, $1)='no'\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n      _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n      ;;\n\n    osf4* | osf5*)\t# as osf3* with the addition of -msym flag\n      if test yes = \"$GCC\"; then\n\t_LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\\*'\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $pic_flag $libobjs $deplibs $compiler_flags $wl-msym $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n      else\n\t_LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \\*'\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $libobjs $deplibs $compiler_flags -msym -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='for i in `cat $export_symbols`; do printf \"%s %s\\\\n\" -exported_symbol \"\\$i\" >> $lib.exp; done; printf \"%s\\\\n\" \"-hidden\">> $lib.exp~\n          $CC -shared$allow_undefined_flag $wl-input $wl$lib.exp $compiler_flags $libobjs $deplibs -soname $soname `test -n \"$verstring\" && $ECHO \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib~$RM $lib.exp'\n\n\t# Both c and cxx compiler support -rpath directly\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir'\n      fi\n      _LT_TAGVAR(archive_cmds_need_lc, $1)='no'\n      _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n      ;;\n\n    solaris*)\n      _LT_TAGVAR(no_undefined_flag, $1)=' -z defs'\n      if test yes = \"$GCC\"; then\n\twlarc='$wl'\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $wl-z ${wl}text $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n          $CC -shared $pic_flag $wl-z ${wl}text $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp'\n      else\n\tcase `$CC -V 2>&1` in\n\t*\"Compilers 5.0\"*)\n\t  wlarc=''\n\t  _LT_TAGVAR(archive_cmds, $1)='$LD -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $linker_flags'\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n            $LD -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $linker_flags~$RM $lib.exp'\n\t  ;;\n\t*)\n\t  wlarc='$wl'\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h $soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n            $CC -G$allow_undefined_flag -M $lib.exp -h $soname -o $lib $libobjs $deplibs $compiler_flags~$RM $lib.exp'\n\t  ;;\n\tesac\n      fi\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir'\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      case $host_os in\n      solaris2.[[0-5]] | solaris2.[[0-5]].*) ;;\n      *)\n\t# The compiler driver will combine and reorder linker options,\n\t# but understands '-z linker_flag'.  GCC discards it without '$wl',\n\t# but is careful enough not to reorder.\n\t# Supported since Solaris 2.6 (maybe 2.5.1?)\n\tif test yes = \"$GCC\"; then\n\t  _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract'\n\telse\n\t  _LT_TAGVAR(whole_archive_flag_spec, $1)='-z allextract$convenience -z defaultextract'\n\tfi\n\t;;\n      esac\n      _LT_TAGVAR(link_all_deplibs, $1)=yes\n      ;;\n\n    sunos4*)\n      if test sequent = \"$host_vendor\"; then\n\t# Use $CC to link under sequent, because it throws in some extra .o\n\t# files that make .init and .fini sections work.\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h $soname -o $lib $libobjs $deplibs $compiler_flags'\n      else\n\t_LT_TAGVAR(archive_cmds, $1)='$LD -assert pure-text -Bstatic -o $lib $libobjs $deplibs $linker_flags'\n      fi\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n      _LT_TAGVAR(hardcode_direct, $1)=yes\n      _LT_TAGVAR(hardcode_minus_L, $1)=yes\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    sysv4)\n      case $host_vendor in\n\tsni)\n\t  _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n\t  _LT_TAGVAR(hardcode_direct, $1)=yes # is this really true???\n\t;;\n\tsiemens)\n\t  ## LD is ld it makes a PLAMLIB\n\t  ## CC just makes a GrossModule.\n\t  _LT_TAGVAR(archive_cmds, $1)='$LD -G -o $lib $libobjs $deplibs $linker_flags'\n\t  _LT_TAGVAR(reload_cmds, $1)='$CC -r -o $output$reload_objs'\n\t  _LT_TAGVAR(hardcode_direct, $1)=no\n        ;;\n\tmotorola)\n\t  _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n\t  _LT_TAGVAR(hardcode_direct, $1)=no #Motorola manual says yes, but my tests say they lie\n\t;;\n      esac\n      runpath_var='LD_RUN_PATH'\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    sysv4.3*)\n      _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      _LT_TAGVAR(export_dynamic_flag_spec, $1)='-Bexport'\n      ;;\n\n    sysv4*MP*)\n      if test -d /usr/nec; then\n\t_LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n\t_LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n\trunpath_var=LD_RUN_PATH\n\thardcode_runpath_var=yes\n\t_LT_TAGVAR(ld_shlibs, $1)=yes\n      fi\n      ;;\n\n    sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[[01]].[[10]]* | unixware7* | sco3.2v5.0.[[024]]*)\n      _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text'\n      _LT_TAGVAR(archive_cmds_need_lc, $1)=no\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      runpath_var='LD_RUN_PATH'\n\n      if test yes = \"$GCC\"; then\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n      else\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n      fi\n      ;;\n\n    sysv5* | sco3.2v5* | sco5v6*)\n      # Note: We CANNOT use -z defs as we might desire, because we do not\n      # link with -lc, and that would cause any symbols used from libc to\n      # always be unresolved, which means just about no library would\n      # ever link correctly.  If we're not using GNU ld we use -z text\n      # though, which does catch some bad symbols but isn't as heavy-handed\n      # as -z defs.\n      _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text'\n      _LT_TAGVAR(allow_undefined_flag, $1)='$wl-z,nodefs'\n      _LT_TAGVAR(archive_cmds_need_lc, $1)=no\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R,$libdir'\n      _LT_TAGVAR(hardcode_libdir_separator, $1)=':'\n      _LT_TAGVAR(link_all_deplibs, $1)=yes\n      _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Bexport'\n      runpath_var='LD_RUN_PATH'\n\n      if test yes = \"$GCC\"; then\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n      else\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n      fi\n      ;;\n\n    uts4*)\n      _LT_TAGVAR(archive_cmds, $1)='$LD -G -h $soname -o $lib $libobjs $deplibs $linker_flags'\n      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      ;;\n\n    *)\n      _LT_TAGVAR(ld_shlibs, $1)=no\n      ;;\n    esac\n\n    if test sni = \"$host_vendor\"; then\n      case $host in\n      sysv4 | sysv4.2uw2* | sysv4.3* | sysv5*)\n\t_LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Blargedynsym'\n\t;;\n      esac\n    fi\n  fi\n])\nAC_MSG_RESULT([$_LT_TAGVAR(ld_shlibs, $1)])\ntest no = \"$_LT_TAGVAR(ld_shlibs, $1)\" && can_build_shared=no\n\n_LT_TAGVAR(with_gnu_ld, $1)=$with_gnu_ld\n\n_LT_DECL([], [libext], [0], [Old archive suffix (normally \"a\")])dnl\n_LT_DECL([], [shrext_cmds], [1], [Shared library suffix (normally \".so\")])dnl\n_LT_DECL([], [extract_expsyms_cmds], [2],\n    [The commands to extract the exported symbol list from a shared archive])\n\n#\n# Do we need to explicitly link libc?\n#\ncase \"x$_LT_TAGVAR(archive_cmds_need_lc, $1)\" in\nx|xyes)\n  # Assume -lc should be added\n  _LT_TAGVAR(archive_cmds_need_lc, $1)=yes\n\n  if test yes,yes = \"$GCC,$enable_shared\"; then\n    case $_LT_TAGVAR(archive_cmds, $1) in\n    *'~'*)\n      # FIXME: we may have to deal with multi-command sequences.\n      ;;\n    '$CC '*)\n      # Test whether the compiler implicitly links with -lc since on some\n      # systems, -lgcc has to come before -lc. If gcc already passes -lc\n      # to ld, don't add -lc before -lgcc.\n      AC_CACHE_CHECK([whether -lc should be explicitly linked in],\n\t[lt_cv_]_LT_TAGVAR(archive_cmds_need_lc, $1),\n\t[$RM conftest*\n\techo \"$lt_simple_compile_test_code\" > conftest.$ac_ext\n\n\tif AC_TRY_EVAL(ac_compile) 2>conftest.err; then\n\t  soname=conftest\n\t  lib=conftest\n\t  libobjs=conftest.$ac_objext\n\t  deplibs=\n\t  wl=$_LT_TAGVAR(lt_prog_compiler_wl, $1)\n\t  pic_flag=$_LT_TAGVAR(lt_prog_compiler_pic, $1)\n\t  compiler_flags=-v\n\t  linker_flags=-v\n\t  verstring=\n\t  output_objdir=.\n\t  libname=conftest\n\t  lt_save_allow_undefined_flag=$_LT_TAGVAR(allow_undefined_flag, $1)\n\t  _LT_TAGVAR(allow_undefined_flag, $1)=\n\t  if AC_TRY_EVAL(_LT_TAGVAR(archive_cmds, $1) 2\\>\\&1 \\| $GREP \\\" -lc \\\" \\>/dev/null 2\\>\\&1)\n\t  then\n\t    lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)=no\n\t  else\n\t    lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)=yes\n\t  fi\n\t  _LT_TAGVAR(allow_undefined_flag, $1)=$lt_save_allow_undefined_flag\n\telse\n\t  cat conftest.err 1>&5\n\tfi\n\t$RM conftest*\n\t])\n      _LT_TAGVAR(archive_cmds_need_lc, $1)=$lt_cv_[]_LT_TAGVAR(archive_cmds_need_lc, $1)\n      ;;\n    esac\n  fi\n  ;;\nesac\n\n_LT_TAGDECL([build_libtool_need_lc], [archive_cmds_need_lc], [0],\n    [Whether or not to add -lc for building shared libraries])\n_LT_TAGDECL([allow_libtool_libs_with_static_runtimes],\n    [enable_shared_with_static_runtimes], [0],\n    [Whether or not to disallow shared libs when runtime libs are static])\n_LT_TAGDECL([], [export_dynamic_flag_spec], [1],\n    [Compiler flag to allow reflexive dlopens])\n_LT_TAGDECL([], [whole_archive_flag_spec], [1],\n    [Compiler flag to generate shared objects directly from archives])\n_LT_TAGDECL([], [compiler_needs_object], [1],\n    [Whether the compiler copes with passing no objects directly])\n_LT_TAGDECL([], [old_archive_from_new_cmds], [2],\n    [Create an old-style archive from a shared archive])\n_LT_TAGDECL([], [old_archive_from_expsyms_cmds], [2],\n    [Create a temporary old-style archive to link instead of a shared archive])\n_LT_TAGDECL([], [archive_cmds], [2], [Commands used to build a shared archive])\n_LT_TAGDECL([], [archive_expsym_cmds], [2])\n_LT_TAGDECL([], [module_cmds], [2],\n    [Commands used to build a loadable module if different from building\n    a shared archive.])\n_LT_TAGDECL([], [module_expsym_cmds], [2])\n_LT_TAGDECL([], [with_gnu_ld], [1],\n    [Whether we are building with GNU ld or not])\n_LT_TAGDECL([], [allow_undefined_flag], [1],\n    [Flag that allows shared libraries with undefined symbols to be built])\n_LT_TAGDECL([], [no_undefined_flag], [1],\n    [Flag that enforces no undefined symbols])\n_LT_TAGDECL([], [hardcode_libdir_flag_spec], [1],\n    [Flag to hardcode $libdir into a binary during linking.\n    This must work even if $libdir does not exist])\n_LT_TAGDECL([], [hardcode_libdir_separator], [1],\n    [Whether we need a single \"-rpath\" flag with a separated argument])\n_LT_TAGDECL([], [hardcode_direct], [0],\n    [Set to \"yes\" if using DIR/libNAME$shared_ext during linking hardcodes\n    DIR into the resulting binary])\n_LT_TAGDECL([], [hardcode_direct_absolute], [0],\n    [Set to \"yes\" if using DIR/libNAME$shared_ext during linking hardcodes\n    DIR into the resulting binary and the resulting library dependency is\n    \"absolute\", i.e impossible to change by setting $shlibpath_var if the\n    library is relocated])\n_LT_TAGDECL([], [hardcode_minus_L], [0],\n    [Set to \"yes\" if using the -LDIR flag during linking hardcodes DIR\n    into the resulting binary])\n_LT_TAGDECL([], [hardcode_shlibpath_var], [0],\n    [Set to \"yes\" if using SHLIBPATH_VAR=DIR during linking hardcodes DIR\n    into the resulting binary])\n_LT_TAGDECL([], [hardcode_automatic], [0],\n    [Set to \"yes\" if building a shared library automatically hardcodes DIR\n    into the library and all subsequent libraries and executables linked\n    against it])\n_LT_TAGDECL([], [inherit_rpath], [0],\n    [Set to yes if linker adds runtime paths of dependent libraries\n    to runtime path list])\n_LT_TAGDECL([], [link_all_deplibs], [0],\n    [Whether libtool must link a program against all its dependency libraries])\n_LT_TAGDECL([], [always_export_symbols], [0],\n    [Set to \"yes\" if exported symbols are required])\n_LT_TAGDECL([], [export_symbols_cmds], [2],\n    [The commands to list exported symbols])\n_LT_TAGDECL([], [exclude_expsyms], [1],\n    [Symbols that should not be listed in the preloaded symbols])\n_LT_TAGDECL([], [include_expsyms], [1],\n    [Symbols that must always be exported])\n_LT_TAGDECL([], [prelink_cmds], [2],\n    [Commands necessary for linking programs (against libraries) with templates])\n_LT_TAGDECL([], [postlink_cmds], [2],\n    [Commands necessary for finishing linking programs])\n_LT_TAGDECL([], [file_list_spec], [1],\n    [Specify filename containing input files])\ndnl FIXME: Not yet implemented\ndnl _LT_TAGDECL([], [thread_safe_flag_spec], [1],\ndnl    [Compiler flag to generate thread safe objects])\n])# _LT_LINKER_SHLIBS\n\n\n# _LT_LANG_C_CONFIG([TAG])\n# ------------------------\n# Ensure that the configuration variables for a C compiler are suitably\n# defined.  These variables are subsequently used by _LT_CONFIG to write\n# the compiler configuration to 'libtool'.\nm4_defun([_LT_LANG_C_CONFIG],\n[m4_require([_LT_DECL_EGREP])dnl\nlt_save_CC=$CC\nAC_LANG_PUSH(C)\n\n# Source file extension for C test sources.\nac_ext=c\n\n# Object file extension for compiled C test sources.\nobjext=o\n_LT_TAGVAR(objext, $1)=$objext\n\n# Code to be used in simple compile tests\nlt_simple_compile_test_code=\"int some_variable = 0;\"\n\n# Code to be used in simple link tests\nlt_simple_link_test_code='int main(){return(0);}'\n\n_LT_TAG_COMPILER\n# Save the default compiler, since it gets overwritten when the other\n# tags are being tested, and _LT_TAGVAR(compiler, []) is a NOP.\ncompiler_DEFAULT=$CC\n\n# save warnings/boilerplate of simple test code\n_LT_COMPILER_BOILERPLATE\n_LT_LINKER_BOILERPLATE\n\n## CAVEAT EMPTOR:\n## There is no encapsulation within the following macros, do not change\n## the running order or otherwise move them around unless you know exactly\n## what you are doing...\nif test -n \"$compiler\"; then\n  _LT_COMPILER_NO_RTTI($1)\n  _LT_COMPILER_PIC($1)\n  _LT_COMPILER_C_O($1)\n  _LT_COMPILER_FILE_LOCKS($1)\n  _LT_LINKER_SHLIBS($1)\n  _LT_SYS_DYNAMIC_LINKER($1)\n  _LT_LINKER_HARDCODE_LIBPATH($1)\n  LT_SYS_DLOPEN_SELF\n  _LT_CMD_STRIPLIB\n\n  # Report what library types will actually be built\n  AC_MSG_CHECKING([if libtool supports shared libraries])\n  AC_MSG_RESULT([$can_build_shared])\n\n  AC_MSG_CHECKING([whether to build shared libraries])\n  test no = \"$can_build_shared\" && enable_shared=no\n\n  # On AIX, shared libraries and static libraries use the same namespace, and\n  # are all built from PIC.\n  case $host_os in\n  aix3*)\n    test yes = \"$enable_shared\" && enable_static=no\n    if test -n \"$RANLIB\"; then\n      archive_cmds=\"$archive_cmds~\\$RANLIB \\$lib\"\n      postinstall_cmds='$RANLIB $lib'\n    fi\n    ;;\n\n  aix[[4-9]]*)\n    if test ia64 != \"$host_cpu\"; then\n      case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in\n      yes,aix,yes) ;;\t\t\t# shared object as lib.so file only\n      yes,svr4,*) ;;\t\t\t# shared object as lib.so archive member only\n      yes,*) enable_static=no ;;\t# shared object in lib.a archive as well\n      esac\n    fi\n    ;;\n  esac\n  AC_MSG_RESULT([$enable_shared])\n\n  AC_MSG_CHECKING([whether to build static libraries])\n  # Make sure either enable_shared or enable_static is yes.\n  test yes = \"$enable_shared\" || enable_static=yes\n  AC_MSG_RESULT([$enable_static])\n\n  _LT_CONFIG($1)\nfi\nAC_LANG_POP\nCC=$lt_save_CC\n])# _LT_LANG_C_CONFIG\n\n\n# _LT_LANG_CXX_CONFIG([TAG])\n# --------------------------\n# Ensure that the configuration variables for a C++ compiler are suitably\n# defined.  These variables are subsequently used by _LT_CONFIG to write\n# the compiler configuration to 'libtool'.\nm4_defun([_LT_LANG_CXX_CONFIG],\n[m4_require([_LT_FILEUTILS_DEFAULTS])dnl\nm4_require([_LT_DECL_EGREP])dnl\nm4_require([_LT_PATH_MANIFEST_TOOL])dnl\nif test -n \"$CXX\" && ( test no != \"$CXX\" &&\n    ( (test g++ = \"$CXX\" && `g++ -v >/dev/null 2>&1` ) ||\n    (test g++ != \"$CXX\"))); then\n  AC_PROG_CXXCPP\nelse\n  _lt_caught_CXX_error=yes\nfi\n\nAC_LANG_PUSH(C++)\n_LT_TAGVAR(archive_cmds_need_lc, $1)=no\n_LT_TAGVAR(allow_undefined_flag, $1)=\n_LT_TAGVAR(always_export_symbols, $1)=no\n_LT_TAGVAR(archive_expsym_cmds, $1)=\n_LT_TAGVAR(compiler_needs_object, $1)=no\n_LT_TAGVAR(export_dynamic_flag_spec, $1)=\n_LT_TAGVAR(hardcode_direct, $1)=no\n_LT_TAGVAR(hardcode_direct_absolute, $1)=no\n_LT_TAGVAR(hardcode_libdir_flag_spec, $1)=\n_LT_TAGVAR(hardcode_libdir_separator, $1)=\n_LT_TAGVAR(hardcode_minus_L, $1)=no\n_LT_TAGVAR(hardcode_shlibpath_var, $1)=unsupported\n_LT_TAGVAR(hardcode_automatic, $1)=no\n_LT_TAGVAR(inherit_rpath, $1)=no\n_LT_TAGVAR(module_cmds, $1)=\n_LT_TAGVAR(module_expsym_cmds, $1)=\n_LT_TAGVAR(link_all_deplibs, $1)=unknown\n_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds\n_LT_TAGVAR(reload_flag, $1)=$reload_flag\n_LT_TAGVAR(reload_cmds, $1)=$reload_cmds\n_LT_TAGVAR(no_undefined_flag, $1)=\n_LT_TAGVAR(whole_archive_flag_spec, $1)=\n_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no\n\n# Source file extension for C++ test sources.\nac_ext=cpp\n\n# Object file extension for compiled C++ test sources.\nobjext=o\n_LT_TAGVAR(objext, $1)=$objext\n\n# No sense in running all these tests if we already determined that\n# the CXX compiler isn't working.  Some variables (like enable_shared)\n# are currently assumed to apply to all compilers on this platform,\n# and will be corrupted by setting them based on a non-working compiler.\nif test yes != \"$_lt_caught_CXX_error\"; then\n  # Code to be used in simple compile tests\n  lt_simple_compile_test_code=\"int some_variable = 0;\"\n\n  # Code to be used in simple link tests\n  lt_simple_link_test_code='int main(int, char *[[]]) { return(0); }'\n\n  # ltmain only uses $CC for tagged configurations so make sure $CC is set.\n  _LT_TAG_COMPILER\n\n  # save warnings/boilerplate of simple test code\n  _LT_COMPILER_BOILERPLATE\n  _LT_LINKER_BOILERPLATE\n\n  # Allow CC to be a program name with arguments.\n  lt_save_CC=$CC\n  lt_save_CFLAGS=$CFLAGS\n  lt_save_LD=$LD\n  lt_save_GCC=$GCC\n  GCC=$GXX\n  lt_save_with_gnu_ld=$with_gnu_ld\n  lt_save_path_LD=$lt_cv_path_LD\n  if test -n \"${lt_cv_prog_gnu_ldcxx+set}\"; then\n    lt_cv_prog_gnu_ld=$lt_cv_prog_gnu_ldcxx\n  else\n    $as_unset lt_cv_prog_gnu_ld\n  fi\n  if test -n \"${lt_cv_path_LDCXX+set}\"; then\n    lt_cv_path_LD=$lt_cv_path_LDCXX\n  else\n    $as_unset lt_cv_path_LD\n  fi\n  test -z \"${LDCXX+set}\" || LD=$LDCXX\n  CC=${CXX-\"c++\"}\n  CFLAGS=$CXXFLAGS\n  compiler=$CC\n  _LT_TAGVAR(compiler, $1)=$CC\n  _LT_CC_BASENAME([$compiler])\n\n  if test -n \"$compiler\"; then\n    # We don't want -fno-exception when compiling C++ code, so set the\n    # no_builtin_flag separately\n    if test yes = \"$GXX\"; then\n      _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=' -fno-builtin'\n    else\n      _LT_TAGVAR(lt_prog_compiler_no_builtin_flag, $1)=\n    fi\n\n    if test yes = \"$GXX\"; then\n      # Set up default GNU C++ configuration\n\n      LT_PATH_LD\n\n      # Check if GNU C++ uses GNU ld as the underlying linker, since the\n      # archiving commands below assume that GNU ld is being used.\n      if test yes = \"$with_gnu_ld\"; then\n        _LT_TAGVAR(archive_cmds, $1)='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n        _LT_TAGVAR(archive_expsym_cmds, $1)='$CC $pic_flag -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\n        _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n        _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic'\n\n        # If archive_cmds runs LD, not CC, wlarc should be empty\n        # XXX I think wlarc can be eliminated in ltcf-cxx, but I need to\n        #     investigate it a little bit more. (MM)\n        wlarc='$wl'\n\n        # ancient GNU ld didn't support --whole-archive et. al.\n        if eval \"`$CC -print-prog-name=ld` --help 2>&1\" |\n\t  $GREP 'no-whole-archive' > /dev/null; then\n          _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive'\n        else\n          _LT_TAGVAR(whole_archive_flag_spec, $1)=\n        fi\n      else\n        with_gnu_ld=no\n        wlarc=\n\n        # A generic and very simple default shared library creation\n        # command for GNU C++ for the case where it uses the native\n        # linker, instead of GNU ld.  If possible, this setting should\n        # overridden to take advantage of the native linker features on\n        # the platform it is being used on.\n        _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $lib'\n      fi\n\n      # Commands to make compiler produce verbose output that lists\n      # what \"hidden\" libraries, object files and flags are used when\n      # linking a shared library.\n      output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v \"^Configured with:\" | $GREP \"\\-L\"'\n\n    else\n      GXX=no\n      with_gnu_ld=no\n      wlarc=\n    fi\n\n    # PORTME: fill in a description of your system's C++ link characteristics\n    AC_MSG_CHECKING([whether the $compiler linker ($LD) supports shared libraries])\n    _LT_TAGVAR(ld_shlibs, $1)=yes\n    case $host_os in\n      aix3*)\n        # FIXME: insert proper C++ library support\n        _LT_TAGVAR(ld_shlibs, $1)=no\n        ;;\n      aix[[4-9]]*)\n        if test ia64 = \"$host_cpu\"; then\n          # On IA64, the linker does run time linking by default, so we don't\n          # have to do anything special.\n          aix_use_runtimelinking=no\n          exp_sym_flag='-Bexport'\n          no_entry_flag=\n        else\n          aix_use_runtimelinking=no\n\n          # Test if we are trying to use run time linking or normal\n          # AIX style linking. If -brtl is somewhere in LDFLAGS, we\n          # have runtime linking enabled, and use it for executables.\n          # For shared libraries, we enable/disable runtime linking\n          # depending on the kind of the shared library created -\n          # when \"with_aix_soname,aix_use_runtimelinking\" is:\n          # \"aix,no\"   lib.a(lib.so.V) shared, rtl:no,  for executables\n          # \"aix,yes\"  lib.so          shared, rtl:yes, for executables\n          #            lib.a           static archive\n          # \"both,no\"  lib.so.V(shr.o) shared, rtl:yes\n          #            lib.a(lib.so.V) shared, rtl:no,  for executables\n          # \"both,yes\" lib.so.V(shr.o) shared, rtl:yes, for executables\n          #            lib.a(lib.so.V) shared, rtl:no\n          # \"svr4,*\"   lib.so.V(shr.o) shared, rtl:yes, for executables\n          #            lib.a           static archive\n          case $host_os in aix4.[[23]]|aix4.[[23]].*|aix[[5-9]]*)\n\t    for ld_flag in $LDFLAGS; do\n\t      case $ld_flag in\n\t      *-brtl*)\n\t        aix_use_runtimelinking=yes\n\t        break\n\t        ;;\n\t      esac\n\t    done\n\t    if test svr4,no = \"$with_aix_soname,$aix_use_runtimelinking\"; then\n\t      # With aix-soname=svr4, we create the lib.so.V shared archives only,\n\t      # so we don't have lib.a shared libs to link our executables.\n\t      # We have to force runtime linking in this case.\n\t      aix_use_runtimelinking=yes\n\t      LDFLAGS=\"$LDFLAGS -Wl,-brtl\"\n\t    fi\n\t    ;;\n          esac\n\n          exp_sym_flag='-bexport'\n          no_entry_flag='-bnoentry'\n        fi\n\n        # When large executables or shared objects are built, AIX ld can\n        # have problems creating the table of contents.  If linking a library\n        # or program results in \"error TOC overflow\" add -mminimal-toc to\n        # CXXFLAGS/CFLAGS for g++/gcc.  In the cases where that is not\n        # enough to fix the problem, add -Wl,-bbigtoc to LDFLAGS.\n\n        _LT_TAGVAR(archive_cmds, $1)=''\n        _LT_TAGVAR(hardcode_direct, $1)=yes\n        _LT_TAGVAR(hardcode_direct_absolute, $1)=yes\n        _LT_TAGVAR(hardcode_libdir_separator, $1)=':'\n        _LT_TAGVAR(link_all_deplibs, $1)=yes\n        _LT_TAGVAR(file_list_spec, $1)='$wl-f,'\n        case $with_aix_soname,$aix_use_runtimelinking in\n        aix,*) ;;\t# no import file\n        svr4,* | *,yes) # use import file\n          # The Import File defines what to hardcode.\n          _LT_TAGVAR(hardcode_direct, $1)=no\n          _LT_TAGVAR(hardcode_direct_absolute, $1)=no\n          ;;\n        esac\n\n        if test yes = \"$GXX\"; then\n          case $host_os in aix4.[[012]]|aix4.[[012]].*)\n          # We only want to do this on AIX 4.2 and lower, the check\n          # below for broken collect2 doesn't work under 4.3+\n\t  collect2name=`$CC -print-prog-name=collect2`\n\t  if test -f \"$collect2name\" &&\n\t     strings \"$collect2name\" | $GREP resolve_lib_name >/dev/null\n\t  then\n\t    # We have reworked collect2\n\t    :\n\t  else\n\t    # We have old collect2\n\t    _LT_TAGVAR(hardcode_direct, $1)=unsupported\n\t    # It fails to find uninstalled libraries when the uninstalled\n\t    # path is not listed in the libpath.  Setting hardcode_minus_L\n\t    # to unsupported forces relinking\n\t    _LT_TAGVAR(hardcode_minus_L, $1)=yes\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n\t    _LT_TAGVAR(hardcode_libdir_separator, $1)=\n\t  fi\n          esac\n          shared_flag='-shared'\n\t  if test yes = \"$aix_use_runtimelinking\"; then\n\t    shared_flag=$shared_flag' $wl-G'\n\t  fi\n\t  # Need to ensure runtime linking is disabled for the traditional\n\t  # shared library, or the linker may eventually find shared libraries\n\t  # /with/ Import File - we do not want to mix them.\n\t  shared_flag_aix='-shared'\n\t  shared_flag_svr4='-shared $wl-G'\n        else\n          # not using gcc\n          if test ia64 = \"$host_cpu\"; then\n\t  # VisualAge C++, Version 5.5 for AIX 5L for IA-64, Beta 3 Release\n\t  # chokes on -Wl,-G. The following line is correct:\n\t  shared_flag='-G'\n          else\n\t    if test yes = \"$aix_use_runtimelinking\"; then\n\t      shared_flag='$wl-G'\n\t    else\n\t      shared_flag='$wl-bM:SRE'\n\t    fi\n\t    shared_flag_aix='$wl-bM:SRE'\n\t    shared_flag_svr4='$wl-G'\n          fi\n        fi\n\n        _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-bexpall'\n        # It seems that -bexpall does not export symbols beginning with\n        # underscore (_), so it is better to generate a list of symbols to\n\t# export.\n        _LT_TAGVAR(always_export_symbols, $1)=yes\n\tif test aix,yes = \"$with_aix_soname,$aix_use_runtimelinking\"; then\n          # Warning - without using the other runtime loading flags (-brtl),\n          # -berok will link without error, but may produce a broken library.\n          # The \"-G\" linker flag allows undefined symbols.\n          _LT_TAGVAR(no_undefined_flag, $1)='-bernotok'\n          # Determine the default libpath from the value encoded in an empty\n          # executable.\n          _LT_SYS_MODULE_PATH_AIX([$1])\n          _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'\"$aix_libpath\"\n\n          _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $deplibs $wl'$no_entry_flag' $compiler_flags `if test -n \"$allow_undefined_flag\"; then func_echo_all \"$wl$allow_undefined_flag\"; else :; fi` $wl'$exp_sym_flag:\\$export_symbols' '$shared_flag\n        else\n          if test ia64 = \"$host_cpu\"; then\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $libdir:/usr/lib:/lib'\n\t    _LT_TAGVAR(allow_undefined_flag, $1)=\"-z nodefs\"\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)=\"\\$CC $shared_flag\"' -o $output_objdir/$soname $libobjs $deplibs '\"\\$wl$no_entry_flag\"' $compiler_flags $wl$allow_undefined_flag '\"\\$wl$exp_sym_flag:\\$export_symbols\"\n          else\n\t    # Determine the default libpath from the value encoded in an\n\t    # empty executable.\n\t    _LT_SYS_MODULE_PATH_AIX([$1])\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-blibpath:$libdir:'\"$aix_libpath\"\n\t    # Warning - without using the other run time loading flags,\n\t    # -berok will link without error, but may produce a broken library.\n\t    _LT_TAGVAR(no_undefined_flag, $1)=' $wl-bernotok'\n\t    _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-berok'\n\t    if test yes = \"$with_gnu_ld\"; then\n\t      # We only use this code for GNU lds that support --whole-archive.\n\t      _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive'\n\t    else\n\t      # Exported symbols can be pulled into shared objects from archives\n\t      _LT_TAGVAR(whole_archive_flag_spec, $1)='$convenience'\n\t    fi\n\t    _LT_TAGVAR(archive_cmds_need_lc, $1)=yes\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='$RM -r $output_objdir/$realname.d~$MKDIR $output_objdir/$realname.d'\n\t    # -brtl affects multiple linker settings, -berok does not and is overridden later\n\t    compiler_flags_filtered='`func_echo_all \"$compiler_flags \" | $SED -e \"s%-brtl\\\\([[, ]]\\\\)%-berok\\\\1%g\"`'\n\t    if test svr4 != \"$with_aix_soname\"; then\n\t      # This is similar to how AIX traditionally builds its shared\n\t      # libraries. Need -bnortl late, we may have -brtl in LDFLAGS.\n\t      _LT_TAGVAR(archive_expsym_cmds, $1)=\"$_LT_TAGVAR(archive_expsym_cmds, $1)\"'~$CC '$shared_flag_aix' -o $output_objdir/$realname.d/$soname $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$AR $AR_FLAGS $output_objdir/$libname$release.a $output_objdir/$realname.d/$soname'\n\t    fi\n\t    if test aix != \"$with_aix_soname\"; then\n\t      _LT_TAGVAR(archive_expsym_cmds, $1)=\"$_LT_TAGVAR(archive_expsym_cmds, $1)\"'~$CC '$shared_flag_svr4' -o $output_objdir/$realname.d/$shared_archive_member_spec.o $libobjs $deplibs $wl-bnoentry '$compiler_flags_filtered'$wl-bE:$export_symbols$allow_undefined_flag~$STRIP -e $output_objdir/$realname.d/$shared_archive_member_spec.o~( func_echo_all \"#! $soname($shared_archive_member_spec.o)\"; if test shr_64 = \"$shared_archive_member_spec\"; then func_echo_all \"# 64\"; else func_echo_all \"# 32\"; fi; cat $export_symbols ) > $output_objdir/$realname.d/$shared_archive_member_spec.imp~$AR $AR_FLAGS $output_objdir/$soname $output_objdir/$realname.d/$shared_archive_member_spec.o $output_objdir/$realname.d/$shared_archive_member_spec.imp'\n\t    else\n\t      # used by -dlpreopen to get the symbols\n\t      _LT_TAGVAR(archive_expsym_cmds, $1)=\"$_LT_TAGVAR(archive_expsym_cmds, $1)\"'~$MV  $output_objdir/$realname.d/$soname $output_objdir'\n\t    fi\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)=\"$_LT_TAGVAR(archive_expsym_cmds, $1)\"'~$RM -r $output_objdir/$realname.d'\n          fi\n        fi\n        ;;\n\n      beos*)\n\tif $LD --help 2>&1 | $GREP ': supported targets:.* elf' > /dev/null; then\n\t  _LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n\t  # Joseph Beckenbach <jrb3@best.com> says some releases of gcc\n\t  # support --undefined.  This deserves some investigation.  FIXME\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -nostart $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\telse\n\t  _LT_TAGVAR(ld_shlibs, $1)=no\n\tfi\n\t;;\n\n      chorus*)\n        case $cc_basename in\n          *)\n\t  # FIXME: insert proper C++ library support\n\t  _LT_TAGVAR(ld_shlibs, $1)=no\n\t  ;;\n        esac\n        ;;\n\n      cygwin* | mingw* | pw32* | cegcc*)\n\tcase $GXX,$cc_basename in\n\t,cl* | no,cl* | ,icl* | no,icl*)\n\t  # Native MSVC or ICC\n\t  # hardcode_libdir_flag_spec is actually meaningless, as there is\n\t  # no search path for DLLs.\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)=' '\n\t  _LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n\t  _LT_TAGVAR(always_export_symbols, $1)=yes\n\t  _LT_TAGVAR(file_list_spec, $1)='@'\n\t  # Tell ltmain to make .lib files, not .a files.\n\t  libext=lib\n\t  # Tell ltmain to make .dll files, not .so files.\n\t  shrext_cmds=.dll\n\t  # FIXME: Setting linknames here is a bad hack.\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -o $output_objdir/$soname $libobjs $compiler_flags $deplibs -Wl,-DLL,-IMPLIB:\"$tool_output_objdir$libname.dll.lib\"~linknames='\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then\n              cp \"$export_symbols\" \"$output_objdir/$soname.def\";\n              echo \"$tool_output_objdir$soname.def\" > \"$output_objdir/$soname.exp\";\n            else\n              $SED -e '\\''s/^/-link -EXPORT:/'\\'' < $export_symbols > $output_objdir/$soname.exp;\n            fi~\n            $CC -o $tool_output_objdir$soname $libobjs $compiler_flags $deplibs \"@$tool_output_objdir$soname.exp\" -Wl,-DLL,-IMPLIB:\"$tool_output_objdir$libname.dll.lib\"~\n            linknames='\n\t  # The linker will not automatically build a static lib if we build a DLL.\n\t  # _LT_TAGVAR(old_archive_from_new_cmds, $1)='true'\n\t  _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes\n\t  # Don't use ranlib\n\t  _LT_TAGVAR(old_postinstall_cmds, $1)='chmod 644 $oldlib'\n\t  _LT_TAGVAR(postlink_cmds, $1)='lt_outputfile=\"@OUTPUT@\"~\n            lt_tool_outputfile=\"@TOOL_OUTPUT@\"~\n            case $lt_outputfile in\n              *.exe|*.EXE) ;;\n              *)\n                lt_outputfile=$lt_outputfile.exe\n                lt_tool_outputfile=$lt_tool_outputfile.exe\n                ;;\n            esac~\n            func_to_tool_file \"$lt_outputfile\"~\n            if test : != \"$MANIFEST_TOOL\" && test -f \"$lt_outputfile.manifest\"; then\n              $MANIFEST_TOOL -manifest \"$lt_tool_outputfile.manifest\" -outputresource:\"$lt_tool_outputfile\" || exit 1;\n              $RM \"$lt_outputfile.manifest\";\n            fi'\n\t  ;;\n\t*)\n\t  # g++\n\t  # _LT_TAGVAR(hardcode_libdir_flag_spec, $1) is actually meaningless,\n\t  # as there is no search path for DLLs.\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n\t  _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-all-symbols'\n\t  _LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n\t  _LT_TAGVAR(always_export_symbols, $1)=no\n\t  _LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes\n\n\t  if $LD --help 2>&1 | $GREP 'auto-import' > /dev/null; then\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib'\n\t    # If the export-symbols file already is a .def file, use it as\n\t    # is; otherwise, prepend EXPORTS...\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='if _LT_DLL_DEF_P([$export_symbols]); then\n              cp $export_symbols $output_objdir/$soname.def;\n            else\n              echo EXPORTS > $output_objdir/$soname.def;\n              cat $export_symbols >> $output_objdir/$soname.def;\n            fi~\n            $CC -shared -nostdlib $output_objdir/$soname.def $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $output_objdir/$soname $wl--enable-auto-image-base -Xlinker --out-implib -Xlinker $lib'\n\t  else\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t  fi\n\t  ;;\n\tesac\n\t;;\n      darwin* | rhapsody*)\n        _LT_DARWIN_LINKER_FEATURES($1)\n\t;;\n\n      os2*)\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-L$libdir'\n\t_LT_TAGVAR(hardcode_minus_L, $1)=yes\n\t_LT_TAGVAR(allow_undefined_flag, $1)=unsupported\n\tshrext_cmds=.dll\n\t_LT_TAGVAR(archive_cmds, $1)='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t  $ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t  $ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t  $ECHO EXPORTS >> $output_objdir/$libname.def~\n\t  emxexp $libobjs | $SED /\"_DLL_InitTerm\"/d >> $output_objdir/$libname.def~\n\t  $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\t  emximp -o $lib $output_objdir/$libname.def'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$ECHO \"LIBRARY ${soname%$shared_ext} INITINSTANCE TERMINSTANCE\" > $output_objdir/$libname.def~\n\t  $ECHO \"DESCRIPTION \\\"$libname\\\"\" >> $output_objdir/$libname.def~\n\t  $ECHO \"DATA MULTIPLE NONSHARED\" >> $output_objdir/$libname.def~\n\t  $ECHO EXPORTS >> $output_objdir/$libname.def~\n\t  prefix_cmds=\"$SED\"~\n\t  if test EXPORTS = \"`$SED 1q $export_symbols`\"; then\n\t    prefix_cmds=\"$prefix_cmds -e 1d\";\n\t  fi~\n\t  prefix_cmds=\"$prefix_cmds -e \\\"s/^\\(.*\\)$/_\\1/g\\\"\"~\n\t  cat $export_symbols | $prefix_cmds >> $output_objdir/$libname.def~\n\t  $CC -Zdll -Zcrtdll -o $output_objdir/$soname $libobjs $deplibs $compiler_flags $output_objdir/$libname.def~\n\t  emximp -o $lib $output_objdir/$libname.def'\n\t_LT_TAGVAR(old_archive_From_new_cmds, $1)='emximp -o $output_objdir/${libname}_dll.a $output_objdir/$libname.def'\n\t_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=yes\n\t_LT_TAGVAR(file_list_spec, $1)='@'\n\t;;\n\n      dgux*)\n        case $cc_basename in\n          ec++*)\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n          ghcx*)\n\t    # Green Hills C++ Compiler\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n          *)\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n        esac\n        ;;\n\n      freebsd2.*)\n        # C++ shared libraries reported to be fairly broken before\n\t# switch to ELF\n        _LT_TAGVAR(ld_shlibs, $1)=no\n        ;;\n\n      freebsd-elf*)\n        _LT_TAGVAR(archive_cmds_need_lc, $1)=no\n        ;;\n\n      freebsd* | dragonfly* | midnightbsd*)\n        # FreeBSD 3 and later use GNU C++ and GNU ld with standard ELF\n        # conventions\n        _LT_TAGVAR(ld_shlibs, $1)=yes\n        ;;\n\n      haiku*)\n        _LT_TAGVAR(archive_cmds, $1)='$CC -shared $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n        _LT_TAGVAR(link_all_deplibs, $1)=yes\n        ;;\n\n      hpux9*)\n        _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir'\n        _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n        _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n        _LT_TAGVAR(hardcode_direct, $1)=yes\n        _LT_TAGVAR(hardcode_minus_L, $1)=yes # Not in the search PATH,\n\t\t\t\t             # but as the default\n\t\t\t\t             # location of the library.\n\n        case $cc_basename in\n          CC*)\n            # FIXME: insert proper C++ library support\n            _LT_TAGVAR(ld_shlibs, $1)=no\n            ;;\n          aCC*)\n            _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -b $wl+b $wl$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test \"x$output_objdir/$soname\" = \"x$lib\" || mv $output_objdir/$soname $lib'\n            # Commands to make compiler produce verbose output that lists\n            # what \"hidden\" libraries, object files and flags are used when\n            # linking a shared library.\n            #\n            # There doesn't appear to be a way to prevent this compiler from\n            # explicitly linking system object files so we need to strip them\n            # from the output so that they don't get included in the library\n            # dependencies.\n            output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $EGREP \"\\-L\"`; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"$list\"'\n            ;;\n          *)\n            if test yes = \"$GXX\"; then\n              _LT_TAGVAR(archive_cmds, $1)='$RM $output_objdir/$soname~$CC -shared -nostdlib $pic_flag $wl+b $wl$install_libdir -o $output_objdir/$soname $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~test \"x$output_objdir/$soname\" = \"x$lib\" || mv $output_objdir/$soname $lib'\n            else\n              # FIXME: insert proper C++ library support\n              _LT_TAGVAR(ld_shlibs, $1)=no\n            fi\n            ;;\n        esac\n        ;;\n\n      hpux10*|hpux11*)\n        if test no = \"$with_gnu_ld\"; then\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl+b $wl$libdir'\n\t  _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n\n          case $host_cpu in\n            hppa*64*|ia64*)\n              ;;\n            *)\n\t      _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n              ;;\n          esac\n        fi\n        case $host_cpu in\n          hppa*64*|ia64*)\n            _LT_TAGVAR(hardcode_direct, $1)=no\n            _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n            ;;\n          *)\n            _LT_TAGVAR(hardcode_direct, $1)=yes\n            _LT_TAGVAR(hardcode_direct_absolute, $1)=yes\n            _LT_TAGVAR(hardcode_minus_L, $1)=yes # Not in the search PATH,\n\t\t\t\t\t         # but as the default\n\t\t\t\t\t         # location of the library.\n            ;;\n        esac\n\n        case $cc_basename in\n          CC*)\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n          aCC*)\n\t    case $host_cpu in\n\t      hppa*64*)\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t        ;;\n\t      ia64*)\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t        ;;\n\t      *)\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -b $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t        ;;\n\t    esac\n\t    # Commands to make compiler produce verbose output that lists\n\t    # what \"hidden\" libraries, object files and flags are used when\n\t    # linking a shared library.\n\t    #\n\t    # There doesn't appear to be a way to prevent this compiler from\n\t    # explicitly linking system object files so we need to strip them\n\t    # from the output so that they don't get included in the library\n\t    # dependencies.\n\t    output_verbose_link_cmd='templist=`($CC -b $CFLAGS -v conftest.$objext 2>&1) | $GREP \"\\-L\"`; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"$list\"'\n\t    ;;\n          *)\n\t    if test yes = \"$GXX\"; then\n\t      if test no = \"$with_gnu_ld\"; then\n\t        case $host_cpu in\n\t          hppa*64*)\n\t            _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib -fPIC $wl+h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t            ;;\n\t          ia64*)\n\t            _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $pic_flag $wl+h $wl$soname $wl+nodefaultrpath -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t            ;;\n\t          *)\n\t            _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $pic_flag $wl+h $wl$soname $wl+b $wl$install_libdir -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t            ;;\n\t        esac\n\t      fi\n\t    else\n\t      # FIXME: insert proper C++ library support\n\t      _LT_TAGVAR(ld_shlibs, $1)=no\n\t    fi\n\t    ;;\n        esac\n        ;;\n\n      interix[[3-9]]*)\n\t_LT_TAGVAR(hardcode_direct, $1)=no\n\t_LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir'\n\t_LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n\t# Hack: On Interix 3.x, we cannot compile PIC because of a broken gcc.\n\t# Instead, shared libraries are loaded at an image base (0x10000000 by\n\t# default) and relocated if they conflict, which is a slow very memory\n\t# consuming and fragmenting process.  To avoid this, we pick a random,\n\t# 256 KiB-aligned image base between 0x50000000 and 0x6FFC0000 at link\n\t# time.  Moving up from 0x10000000 also allows more sbrk(2) space.\n\t_LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \\* 262144 + 1342177280` -o $lib'\n\t_LT_TAGVAR(archive_expsym_cmds, $1)='$SED \"s|^|_|\" $export_symbols >$output_objdir/$soname.expsym~$CC -shared $pic_flag $libobjs $deplibs $compiler_flags $wl-h,$soname $wl--retain-symbols-file,$output_objdir/$soname.expsym $wl--image-base,`expr ${RANDOM-$$} % 4096 / 2 \\* 262144 + 1342177280` -o $lib'\n\t;;\n      irix5* | irix6*)\n        case $cc_basename in\n          CC*)\n\t    # SGI C++\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -shared -all -multigot $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\n\t    # Archives containing C++ object files must be created using\n\t    # \"CC -ar\", where \"CC\" is the IRIX C++ compiler.  This is\n\t    # necessary to make sure instantiated templates are included\n\t    # in the archive.\n\t    _LT_TAGVAR(old_archive_cmds, $1)='$CC -ar -WR,-u -o $oldlib $oldobjs'\n\t    ;;\n          *)\n\t    if test yes = \"$GXX\"; then\n\t      if test no = \"$with_gnu_ld\"; then\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t      else\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` -o $lib'\n\t      fi\n\t    fi\n\t    _LT_TAGVAR(link_all_deplibs, $1)=yes\n\t    ;;\n        esac\n        _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n        _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n        _LT_TAGVAR(inherit_rpath, $1)=yes\n        ;;\n\n      linux* | k*bsd*-gnu | kopensolaris*-gnu | gnu*)\n        case $cc_basename in\n          KCC*)\n\t    # Kuck and Associates, Inc. (KAI) C++ Compiler\n\n\t    # KCC will only create a shared library if the output file\n\t    # ends with \".so\" (or \".sl\" for HP-UX), so rename the library\n\t    # to its proper name (with version) after linking.\n\t    _LT_TAGVAR(archive_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\\''s/\\([[^()0-9A-Za-z{}]]\\)/\\\\\\\\\\1/g'\\''`; templib=`echo $lib | $SED -e \"s/\\$tempext\\..*/.so/\"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \\$templib; mv \\$templib $lib'\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\\''s/\\([[^()0-9A-Za-z{}]]\\)/\\\\\\\\\\1/g'\\''`; templib=`echo $lib | $SED -e \"s/\\$tempext\\..*/.so/\"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \\$templib $wl-retain-symbols-file,$export_symbols; mv \\$templib $lib'\n\t    # Commands to make compiler produce verbose output that lists\n\t    # what \"hidden\" libraries, object files and flags are used when\n\t    # linking a shared library.\n\t    #\n\t    # There doesn't appear to be a way to prevent this compiler from\n\t    # explicitly linking system object files so we need to strip them\n\t    # from the output so that they don't get included in the library\n\t    # dependencies.\n\t    output_verbose_link_cmd='templist=`$CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1 | $GREP \"ld\"`; rm -f libconftest$shared_ext; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"$list\"'\n\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir'\n\t    _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic'\n\n\t    # Archives containing C++ object files must be created using\n\t    # \"CC -Bstatic\", where \"CC\" is the KAI C++ compiler.\n\t    _LT_TAGVAR(old_archive_cmds, $1)='$CC -Bstatic -o $oldlib $oldobjs'\n\t    ;;\n\t  icpc* | ecpc* )\n\t    # Intel C++\n\t    with_gnu_ld=yes\n\t    # version 8.0 and above of icpc choke on multiply defined symbols\n\t    # if we add $predep_objects and $postdep_objects, however 7.1 and\n\t    # earlier do not add the objects themselves.\n\t    case `$CC -V 2>&1` in\n\t      *\"Version 7.\"*)\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n\t\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t\t;;\n\t      *)  # Version 8.0 or newer\n\t        tmp_idyn=\n\t        case $host_cpu in\n\t\t  ia64*) tmp_idyn=' -i_dynamic';;\n\t\tesac\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -shared'\"$tmp_idyn\"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t\t_LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared'\"$tmp_idyn\"' $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t\t;;\n\t    esac\n\t    _LT_TAGVAR(archive_cmds_need_lc, $1)=no\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir'\n\t    _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic'\n\t    _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive$convenience $wl--no-whole-archive'\n\t    ;;\n          pgCC* | pgcpp*)\n            # Portland Group C++ compiler\n\t    case `$CC -V` in\n\t    *pgCC\\ [[1-5]].* | *pgcpp\\ [[1-5]].*)\n\t      _LT_TAGVAR(prelink_cmds, $1)='tpldir=Template.dir~\n               rm -rf $tpldir~\n               $CC --prelink_objects --instantiation_dir $tpldir $objs $libobjs $compile_deplibs~\n               compile_command=\"$compile_command `find $tpldir -name \\*.o | sort | $NL2SP`\"'\n\t      _LT_TAGVAR(old_archive_cmds, $1)='tpldir=Template.dir~\n                rm -rf $tpldir~\n                $CC --prelink_objects --instantiation_dir $tpldir $oldobjs$old_deplibs~\n                $AR $AR_FLAGS $oldlib$oldobjs$old_deplibs `find $tpldir -name \\*.o | sort | $NL2SP`~\n                $RANLIB $oldlib'\n\t      _LT_TAGVAR(archive_cmds, $1)='tpldir=Template.dir~\n                rm -rf $tpldir~\n                $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~\n                $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \\*.o | sort | $NL2SP` $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n\t      _LT_TAGVAR(archive_expsym_cmds, $1)='tpldir=Template.dir~\n                rm -rf $tpldir~\n                $CC --prelink_objects --instantiation_dir $tpldir $predep_objects $libobjs $deplibs $convenience $postdep_objects~\n                $CC -shared $pic_flag $predep_objects $libobjs $deplibs `find $tpldir -name \\*.o | sort | $NL2SP` $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t      ;;\n\t    *) # Version 6 and above use weak symbols\n\t      _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n\t      _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname $wl-retain-symbols-file $wl$export_symbols -o $lib'\n\t      ;;\n\t    esac\n\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl--rpath $wl$libdir'\n\t    _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic'\n\t    _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`for conv in $convenience\\\"\\\"; do test  -n \\\"$conv\\\" && new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n            ;;\n\t  cxx*)\n\t    # Compaq C++\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname -o $lib'\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname  -o $lib $wl-retain-symbols-file $wl$export_symbols'\n\n\t    runpath_var=LD_RUN_PATH\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir'\n\t    _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n\n\t    # Commands to make compiler produce verbose output that lists\n\t    # what \"hidden\" libraries, object files and flags are used when\n\t    # linking a shared library.\n\t    #\n\t    # There doesn't appear to be a way to prevent this compiler from\n\t    # explicitly linking system object files so we need to strip them\n\t    # from the output so that they don't get included in the library\n\t    # dependencies.\n\t    output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP \"ld\"`; templist=`func_echo_all \"$templist\" | $SED \"s/\\(^.*ld.*\\)\\( .*ld .*$\\)/\\1/\"`; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"X$list\" | $Xsed'\n\t    ;;\n\t  xl* | mpixl* | bgxl*)\n\t    # IBM XL 8.0 on PPC, with GNU ld\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n\t    _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl--export-dynamic'\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -qmkshrobj $libobjs $deplibs $compiler_flags $wl-soname $wl$soname -o $lib'\n\t    if test yes = \"$supports_anon_versioning\"; then\n\t      _LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $output_objdir/$libname.ver~\n                cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $output_objdir/$libname.ver~\n                echo \"local: *; };\" >> $output_objdir/$libname.ver~\n                $CC -qmkshrobj $libobjs $deplibs $compiler_flags $wl-soname $wl$soname $wl-version-script $wl$output_objdir/$libname.ver -o $lib'\n\t    fi\n\t    ;;\n\t  *)\n\t    case `$CC -V 2>&1 | $SED 5q` in\n\t    *Sun\\ C*)\n\t      # Sun C++ 5.9\n\t      _LT_TAGVAR(no_undefined_flag, $1)=' -zdefs'\n\t      _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t      _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-retain-symbols-file $wl$export_symbols'\n\t      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir'\n\t      _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl--whole-archive`new_convenience=; for conv in $convenience\\\"\\\"; do test -z \\\"$conv\\\" || new_convenience=\\\"$new_convenience,$conv\\\"; done; func_echo_all \\\"$new_convenience\\\"` $wl--no-whole-archive'\n\t      _LT_TAGVAR(compiler_needs_object, $1)=yes\n\n\t      # Not sure whether something based on\n\t      # $CC $CFLAGS -v conftest.$objext -o libconftest$shared_ext 2>&1\n\t      # would be better.\n\t      output_verbose_link_cmd='func_echo_all'\n\n\t      # Archives containing C++ object files must be created using\n\t      # \"CC -xar\", where \"CC\" is the Sun C++ compiler.  This is\n\t      # necessary to make sure instantiated templates are included\n\t      # in the archive.\n\t      _LT_TAGVAR(old_archive_cmds, $1)='$CC -xar -o $oldlib $oldobjs'\n\t      ;;\n\t    esac\n\t    ;;\n\tesac\n\t;;\n\n      lynxos*)\n        # FIXME: insert proper C++ library support\n\t_LT_TAGVAR(ld_shlibs, $1)=no\n\t;;\n\n      m88k*)\n        # FIXME: insert proper C++ library support\n        _LT_TAGVAR(ld_shlibs, $1)=no\n\t;;\n\n      mvs*)\n        case $cc_basename in\n          cxx*)\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n\t  *)\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n\tesac\n\t;;\n\n      netbsd*)\n        if echo __ELF__ | $CC -E - | $GREP __ELF__ >/dev/null; then\n\t  _LT_TAGVAR(archive_cmds, $1)='$LD -Bshareable  -o $lib $predep_objects $libobjs $deplibs $postdep_objects $linker_flags'\n\t  wlarc=\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir'\n\t  _LT_TAGVAR(hardcode_direct, $1)=yes\n\t  _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n\tfi\n\t# Workaround some broken pre-1.5 toolchains\n\toutput_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP conftest.$objext | $SED -e \"s:-lgcc -lc -lgcc::\"'\n\t;;\n\n      *nto* | *qnx*)\n        _LT_TAGVAR(ld_shlibs, $1)=yes\n\t;;\n\n      openbsd* | bitrig*)\n\tif test -f /usr/libexec/ld.so; then\n\t  _LT_TAGVAR(hardcode_direct, $1)=yes\n\t  _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n\t  _LT_TAGVAR(hardcode_direct_absolute, $1)=yes\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -o $lib'\n\t  _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir'\n\t  if test -z \"`echo __ELF__ | $CC -E - | grep __ELF__`\"; then\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $pic_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-retain-symbols-file,$export_symbols -o $lib'\n\t    _LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-E'\n\t    _LT_TAGVAR(whole_archive_flag_spec, $1)=$wlarc'--whole-archive$convenience '$wlarc'--no-whole-archive'\n\t  fi\n\t  output_verbose_link_cmd=func_echo_all\n\telse\n\t  _LT_TAGVAR(ld_shlibs, $1)=no\n\tfi\n\t;;\n\n      osf3* | osf4* | osf5*)\n        case $cc_basename in\n          KCC*)\n\t    # Kuck and Associates, Inc. (KAI) C++ Compiler\n\n\t    # KCC will only create a shared library if the output file\n\t    # ends with \".so\" (or \".sl\" for HP-UX), so rename the library\n\t    # to its proper name (with version) after linking.\n\t    _LT_TAGVAR(archive_cmds, $1)='tempext=`echo $shared_ext | $SED -e '\\''s/\\([[^()0-9A-Za-z{}]]\\)/\\\\\\\\\\1/g'\\''`; templib=`echo \"$lib\" | $SED -e \"s/\\$tempext\\..*/.so/\"`; $CC $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags --soname $soname -o \\$templib; mv \\$templib $lib'\n\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath,$libdir'\n\t    _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n\n\t    # Archives containing C++ object files must be created using\n\t    # the KAI C++ compiler.\n\t    case $host in\n\t      osf3*) _LT_TAGVAR(old_archive_cmds, $1)='$CC -Bstatic -o $oldlib $oldobjs' ;;\n\t      *) _LT_TAGVAR(old_archive_cmds, $1)='$CC -o $oldlib $oldobjs' ;;\n\t    esac\n\t    ;;\n          RCC*)\n\t    # Rational C++ 2.4.1\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n          cxx*)\n\t    case $host in\n\t      osf3*)\n\t        _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\\*'\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\t        _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n\t\t;;\n\t      *)\n\t        _LT_TAGVAR(allow_undefined_flag, $1)=' -expect_unresolved \\*'\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname `test -n \"$verstring\" && func_echo_all \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib'\n\t        _LT_TAGVAR(archive_expsym_cmds, $1)='for i in `cat $export_symbols`; do printf \"%s %s\\\\n\" -exported_symbol \"\\$i\" >> $lib.exp; done~\n                  echo \"-hidden\">> $lib.exp~\n                  $CC -shared$allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags -msym -soname $soname $wl-input $wl$lib.exp  `test -n \"$verstring\" && $ECHO \"-set_version $verstring\"` -update_registry $output_objdir/so_locations -o $lib~\n                  $RM $lib.exp'\n\t        _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-rpath $libdir'\n\t\t;;\n\t    esac\n\n\t    _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n\n\t    # Commands to make compiler produce verbose output that lists\n\t    # what \"hidden\" libraries, object files and flags are used when\n\t    # linking a shared library.\n\t    #\n\t    # There doesn't appear to be a way to prevent this compiler from\n\t    # explicitly linking system object files so we need to strip them\n\t    # from the output so that they don't get included in the library\n\t    # dependencies.\n\t    output_verbose_link_cmd='templist=`$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP \"ld\" | $GREP -v \"ld:\"`; templist=`func_echo_all \"$templist\" | $SED \"s/\\(^.*ld.*\\)\\( .*ld.*$\\)/\\1/\"`; list= ; for z in $templist; do case $z in conftest.$objext) list=\"$list $z\";; *.$objext);; *) list=\"$list $z\";;esac; done; func_echo_all \"$list\"'\n\t    ;;\n\t  *)\n\t    if test yes,no = \"$GXX,$with_gnu_ld\"; then\n\t      _LT_TAGVAR(allow_undefined_flag, $1)=' $wl-expect_unresolved $wl\\*'\n\t      case $host in\n\t        osf3*)\n\t          _LT_TAGVAR(archive_cmds, $1)='$CC -shared -nostdlib $allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t\t  ;;\n\t        *)\n\t          _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $allow_undefined_flag $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-msym $wl-soname $wl$soname `test -n \"$verstring\" && func_echo_all \"$wl-set_version $wl$verstring\"` $wl-update_registry $wl$output_objdir/so_locations -o $lib'\n\t\t  ;;\n\t      esac\n\n\t      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-rpath $wl$libdir'\n\t      _LT_TAGVAR(hardcode_libdir_separator, $1)=:\n\n\t      # Commands to make compiler produce verbose output that lists\n\t      # what \"hidden\" libraries, object files and flags are used when\n\t      # linking a shared library.\n\t      output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v \"^Configured with:\" | $GREP \"\\-L\"'\n\n\t    else\n\t      # FIXME: insert proper C++ library support\n\t      _LT_TAGVAR(ld_shlibs, $1)=no\n\t    fi\n\t    ;;\n        esac\n        ;;\n\n      psos*)\n        # FIXME: insert proper C++ library support\n        _LT_TAGVAR(ld_shlibs, $1)=no\n        ;;\n\n      sunos4*)\n        case $cc_basename in\n          CC*)\n\t    # Sun C++ 4.x\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n          lcc*)\n\t    # Lucid\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n          *)\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n        esac\n        ;;\n\n      solaris*)\n        case $cc_basename in\n          CC* | sunCC*)\n\t    # Sun C++ 4.2, 5.x and Centerline C++\n            _LT_TAGVAR(archive_cmds_need_lc,$1)=yes\n\t    _LT_TAGVAR(no_undefined_flag, $1)=' -zdefs'\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -G$allow_undefined_flag -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags'\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n              $CC -G$allow_undefined_flag $wl-M $wl$lib.exp -h$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp'\n\n\t    _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='-R$libdir'\n\t    _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n\t    case $host_os in\n\t      solaris2.[[0-5]] | solaris2.[[0-5]].*) ;;\n\t      *)\n\t\t# The compiler driver will combine and reorder linker options,\n\t\t# but understands '-z linker_flag'.\n\t        # Supported since Solaris 2.6 (maybe 2.5.1?)\n\t\t_LT_TAGVAR(whole_archive_flag_spec, $1)='-z allextract$convenience -z defaultextract'\n\t        ;;\n\t    esac\n\t    _LT_TAGVAR(link_all_deplibs, $1)=yes\n\n\t    output_verbose_link_cmd='func_echo_all'\n\n\t    # Archives containing C++ object files must be created using\n\t    # \"CC -xar\", where \"CC\" is the Sun C++ compiler.  This is\n\t    # necessary to make sure instantiated templates are included\n\t    # in the archive.\n\t    _LT_TAGVAR(old_archive_cmds, $1)='$CC -xar -o $oldlib $oldobjs'\n\t    ;;\n          gcx*)\n\t    # Green Hills C++ Compiler\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -shared $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib'\n\n\t    # The C++ compiler must be used to create the archive.\n\t    _LT_TAGVAR(old_archive_cmds, $1)='$CC $LDFLAGS -archive -o $oldlib $oldobjs'\n\t    ;;\n          *)\n\t    # GNU C++ compiler with Solaris linker\n\t    if test yes,no = \"$GXX,$with_gnu_ld\"; then\n\t      _LT_TAGVAR(no_undefined_flag, $1)=' $wl-z ${wl}defs'\n\t      if $CC --version | $GREP -v '^2\\.7' > /dev/null; then\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -shared $pic_flag -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib'\n\t        _LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n                  $CC -shared $pic_flag -nostdlib $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp'\n\n\t        # Commands to make compiler produce verbose output that lists\n\t        # what \"hidden\" libraries, object files and flags are used when\n\t        # linking a shared library.\n\t        output_verbose_link_cmd='$CC -shared $CFLAGS -v conftest.$objext 2>&1 | $GREP -v \"^Configured with:\" | $GREP \"\\-L\"'\n\t      else\n\t        # g++ 2.7 appears to require '-G' NOT '-shared' on this\n\t        # platform.\n\t        _LT_TAGVAR(archive_cmds, $1)='$CC -G -nostdlib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags $wl-h $wl$soname -o $lib'\n\t        _LT_TAGVAR(archive_expsym_cmds, $1)='echo \"{ global:\" > $lib.exp~cat $export_symbols | $SED -e \"s/\\(.*\\)/\\1;/\" >> $lib.exp~echo \"local: *; };\" >> $lib.exp~\n                  $CC -G -nostdlib $wl-M $wl$lib.exp $wl-h $wl$soname -o $lib $predep_objects $libobjs $deplibs $postdep_objects $compiler_flags~$RM $lib.exp'\n\n\t        # Commands to make compiler produce verbose output that lists\n\t        # what \"hidden\" libraries, object files and flags are used when\n\t        # linking a shared library.\n\t        output_verbose_link_cmd='$CC -G $CFLAGS -v conftest.$objext 2>&1 | $GREP -v \"^Configured with:\" | $GREP \"\\-L\"'\n\t      fi\n\n\t      _LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R $wl$libdir'\n\t      case $host_os in\n\t\tsolaris2.[[0-5]] | solaris2.[[0-5]].*) ;;\n\t\t*)\n\t\t  _LT_TAGVAR(whole_archive_flag_spec, $1)='$wl-z ${wl}allextract$convenience $wl-z ${wl}defaultextract'\n\t\t  ;;\n\t      esac\n\t    fi\n\t    ;;\n        esac\n        ;;\n\n    sysv4*uw2* | sysv5OpenUNIX* | sysv5UnixWare7.[[01]].[[10]]* | unixware7* | sco3.2v5.0.[[024]]*)\n      _LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text'\n      _LT_TAGVAR(archive_cmds_need_lc, $1)=no\n      _LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n      runpath_var='LD_RUN_PATH'\n\n      case $cc_basename in\n        CC*)\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n\t*)\n\t  _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t  ;;\n      esac\n      ;;\n\n      sysv5* | sco3.2v5* | sco5v6*)\n\t# Note: We CANNOT use -z defs as we might desire, because we do not\n\t# link with -lc, and that would cause any symbols used from libc to\n\t# always be unresolved, which means just about no library would\n\t# ever link correctly.  If we're not using GNU ld we use -z text\n\t# though, which does catch some bad symbols but isn't as heavy-handed\n\t# as -z defs.\n\t_LT_TAGVAR(no_undefined_flag, $1)='$wl-z,text'\n\t_LT_TAGVAR(allow_undefined_flag, $1)='$wl-z,nodefs'\n\t_LT_TAGVAR(archive_cmds_need_lc, $1)=no\n\t_LT_TAGVAR(hardcode_shlibpath_var, $1)=no\n\t_LT_TAGVAR(hardcode_libdir_flag_spec, $1)='$wl-R,$libdir'\n\t_LT_TAGVAR(hardcode_libdir_separator, $1)=':'\n\t_LT_TAGVAR(link_all_deplibs, $1)=yes\n\t_LT_TAGVAR(export_dynamic_flag_spec, $1)='$wl-Bexport'\n\trunpath_var='LD_RUN_PATH'\n\n\tcase $cc_basename in\n          CC*)\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -G $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -G $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t    _LT_TAGVAR(old_archive_cmds, $1)='$CC -Tprelink_objects $oldobjs~\n              '\"$_LT_TAGVAR(old_archive_cmds, $1)\"\n\t    _LT_TAGVAR(reload_cmds, $1)='$CC -Tprelink_objects $reload_objs~\n              '\"$_LT_TAGVAR(reload_cmds, $1)\"\n\t    ;;\n\t  *)\n\t    _LT_TAGVAR(archive_cmds, $1)='$CC -shared $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t    _LT_TAGVAR(archive_expsym_cmds, $1)='$CC -shared $wl-Bexport:$export_symbols $wl-h,$soname -o $lib $libobjs $deplibs $compiler_flags'\n\t    ;;\n\tesac\n      ;;\n\n      tandem*)\n        case $cc_basename in\n          NCC*)\n\t    # NonStop-UX NCC 3.20\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n          *)\n\t    # FIXME: insert proper C++ library support\n\t    _LT_TAGVAR(ld_shlibs, $1)=no\n\t    ;;\n        esac\n        ;;\n\n      vxworks*)\n        # FIXME: insert proper C++ library support\n        _LT_TAGVAR(ld_shlibs, $1)=no\n        ;;\n\n      *)\n        # FIXME: insert proper C++ library support\n        _LT_TAGVAR(ld_shlibs, $1)=no\n        ;;\n    esac\n\n    AC_MSG_RESULT([$_LT_TAGVAR(ld_shlibs, $1)])\n    test no = \"$_LT_TAGVAR(ld_shlibs, $1)\" && can_build_shared=no\n\n    _LT_TAGVAR(GCC, $1)=$GXX\n    _LT_TAGVAR(LD, $1)=$LD\n\n    ## CAVEAT EMPTOR:\n    ## There is no encapsulation within the following macros, do not change\n    ## the running order or otherwise move them around unless you know exactly\n    ## what you are doing...\n    _LT_SYS_HIDDEN_LIBDEPS($1)\n    _LT_COMPILER_PIC($1)\n    _LT_COMPILER_C_O($1)\n    _LT_COMPILER_FILE_LOCKS($1)\n    _LT_LINKER_SHLIBS($1)\n    _LT_SYS_DYNAMIC_LINKER($1)\n    _LT_LINKER_HARDCODE_LIBPATH($1)\n\n    _LT_CONFIG($1)\n  fi # test -n \"$compiler\"\n\n  CC=$lt_save_CC\n  CFLAGS=$lt_save_CFLAGS\n  LDCXX=$LD\n  LD=$lt_save_LD\n  GCC=$lt_save_GCC\n  with_gnu_ld=$lt_save_with_gnu_ld\n  lt_cv_path_LDCXX=$lt_cv_path_LD\n  lt_cv_path_LD=$lt_save_path_LD\n  lt_cv_prog_gnu_ldcxx=$lt_cv_prog_gnu_ld\n  lt_cv_prog_gnu_ld=$lt_save_with_gnu_ld\nfi # test yes != \"$_lt_caught_CXX_error\"\n\nAC_LANG_POP\n])# _LT_LANG_CXX_CONFIG\n\n\n# _LT_FUNC_STRIPNAME_CNF\n# ----------------------\n# func_stripname_cnf prefix suffix name\n# strip PREFIX and SUFFIX off of NAME.\n# PREFIX and SUFFIX must not contain globbing or regex special\n# characters, hashes, percent signs, but SUFFIX may contain a leading\n# dot (in which case that matches only a dot).\n#\n# This function is identical to the (non-XSI) version of func_stripname,\n# except this one can be used by m4 code that may be executed by configure,\n# rather than the libtool script.\nm4_defun([_LT_FUNC_STRIPNAME_CNF],[dnl\nAC_REQUIRE([_LT_DECL_SED])\nAC_REQUIRE([_LT_PROG_ECHO_BACKSLASH])\nfunc_stripname_cnf ()\n{\n  case @S|@2 in\n  .*) func_stripname_result=`$ECHO \"@S|@3\" | $SED \"s%^@S|@1%%; s%\\\\\\\\@S|@2\\$%%\"`;;\n  *)  func_stripname_result=`$ECHO \"@S|@3\" | $SED \"s%^@S|@1%%; s%@S|@2\\$%%\"`;;\n  esac\n} # func_stripname_cnf\n])# _LT_FUNC_STRIPNAME_CNF\n\n\n# _LT_SYS_HIDDEN_LIBDEPS([TAGNAME])\n# ---------------------------------\n# Figure out \"hidden\" library dependencies from verbose\n# compiler output when linking a shared library.\n# Parse the compiler output and extract the necessary\n# objects, libraries and library flags.\nm4_defun([_LT_SYS_HIDDEN_LIBDEPS],\n[m4_require([_LT_FILEUTILS_DEFAULTS])dnl\nAC_REQUIRE([_LT_FUNC_STRIPNAME_CNF])dnl\n# Dependencies to place before and after the object being linked:\n_LT_TAGVAR(predep_objects, $1)=\n_LT_TAGVAR(postdep_objects, $1)=\n_LT_TAGVAR(predeps, $1)=\n_LT_TAGVAR(postdeps, $1)=\n_LT_TAGVAR(compiler_lib_search_path, $1)=\n\ndnl we can't use the lt_simple_compile_test_code here,\ndnl because it contains code intended for an executable,\ndnl not a library.  It's possible we should let each\ndnl tag define a new lt_????_link_test_code variable,\ndnl but it's only used here...\nm4_if([$1], [], [cat > conftest.$ac_ext <<_LT_EOF\nint a;\nvoid foo (void) { a = 0; }\n_LT_EOF\n], [$1], [CXX], [cat > conftest.$ac_ext <<_LT_EOF\nclass Foo\n{\npublic:\n  Foo (void) { a = 0; }\nprivate:\n  int a;\n};\n_LT_EOF\n], [$1], [F77], [cat > conftest.$ac_ext <<_LT_EOF\n      subroutine foo\n      implicit none\n      integer*4 a\n      a=0\n      return\n      end\n_LT_EOF\n], [$1], [FC], [cat > conftest.$ac_ext <<_LT_EOF\n      subroutine foo\n      implicit none\n      integer a\n      a=0\n      return\n      end\n_LT_EOF\n], [$1], [GCJ], [cat > conftest.$ac_ext <<_LT_EOF\npublic class foo {\n  private int a;\n  public void bar (void) {\n    a = 0;\n  }\n};\n_LT_EOF\n], [$1], [GO], [cat > conftest.$ac_ext <<_LT_EOF\npackage foo\nfunc foo() {\n}\n_LT_EOF\n])\n\n_lt_libdeps_save_CFLAGS=$CFLAGS\ncase \"$CC $CFLAGS \" in #(\n*\\ -flto*\\ *) CFLAGS=\"$CFLAGS -fno-lto\" ;;\n*\\ -fwhopr*\\ *) CFLAGS=\"$CFLAGS -fno-whopr\" ;;\n*\\ -fuse-linker-plugin*\\ *) CFLAGS=\"$CFLAGS -fno-use-linker-plugin\" ;;\nesac\n\ndnl Parse the compiler output and extract the necessary\ndnl objects, libraries and library flags.\nif AC_TRY_EVAL(ac_compile); then\n  # Parse the compiler output and extract the necessary\n  # objects, libraries and library flags.\n\n  # Sentinel used to keep track of whether or not we are before\n  # the conftest object file.\n  pre_test_object_deps_done=no\n\n  for p in `eval \"$output_verbose_link_cmd\"`; do\n    case $prev$p in\n\n    -L* | -R* | -l*)\n       # Some compilers place space between \"-{L,R}\" and the path.\n       # Remove the space.\n       if test x-L = \"$p\" ||\n          test x-R = \"$p\"; then\n\t prev=$p\n\t continue\n       fi\n\n       # Expand the sysroot to ease extracting the directories later.\n       if test -z \"$prev\"; then\n         case $p in\n         -L*) func_stripname_cnf '-L' '' \"$p\"; prev=-L; p=$func_stripname_result ;;\n         -R*) func_stripname_cnf '-R' '' \"$p\"; prev=-R; p=$func_stripname_result ;;\n         -l*) func_stripname_cnf '-l' '' \"$p\"; prev=-l; p=$func_stripname_result ;;\n         esac\n       fi\n       case $p in\n       =*) func_stripname_cnf '=' '' \"$p\"; p=$lt_sysroot$func_stripname_result ;;\n       esac\n       if test no = \"$pre_test_object_deps_done\"; then\n\t case $prev in\n\t -L | -R)\n\t   # Internal compiler library paths should come after those\n\t   # provided the user.  The postdeps already come after the\n\t   # user supplied libs so there is no need to process them.\n\t   if test -z \"$_LT_TAGVAR(compiler_lib_search_path, $1)\"; then\n\t     _LT_TAGVAR(compiler_lib_search_path, $1)=$prev$p\n\t   else\n\t     _LT_TAGVAR(compiler_lib_search_path, $1)=\"${_LT_TAGVAR(compiler_lib_search_path, $1)} $prev$p\"\n\t   fi\n\t   ;;\n\t # The \"-l\" case would never come before the object being\n\t # linked, so don't bother handling this case.\n\t esac\n       else\n\t if test -z \"$_LT_TAGVAR(postdeps, $1)\"; then\n\t   _LT_TAGVAR(postdeps, $1)=$prev$p\n\t else\n\t   _LT_TAGVAR(postdeps, $1)=\"${_LT_TAGVAR(postdeps, $1)} $prev$p\"\n\t fi\n       fi\n       prev=\n       ;;\n\n    *.lto.$objext) ;; # Ignore GCC LTO objects\n    *.$objext)\n       # This assumes that the test object file only shows up\n       # once in the compiler output.\n       if test \"$p\" = \"conftest.$objext\"; then\n\t pre_test_object_deps_done=yes\n\t continue\n       fi\n\n       if test no = \"$pre_test_object_deps_done\"; then\n\t if test -z \"$_LT_TAGVAR(predep_objects, $1)\"; then\n\t   _LT_TAGVAR(predep_objects, $1)=$p\n\t else\n\t   _LT_TAGVAR(predep_objects, $1)=\"$_LT_TAGVAR(predep_objects, $1) $p\"\n\t fi\n       else\n\t if test -z \"$_LT_TAGVAR(postdep_objects, $1)\"; then\n\t   _LT_TAGVAR(postdep_objects, $1)=$p\n\t else\n\t   _LT_TAGVAR(postdep_objects, $1)=\"$_LT_TAGVAR(postdep_objects, $1) $p\"\n\t fi\n       fi\n       ;;\n\n    *) ;; # Ignore the rest.\n\n    esac\n  done\n\n  # Clean up.\n  rm -f a.out a.exe\nelse\n  echo \"libtool.m4: error: problem compiling $1 test program\"\nfi\n\n$RM -f confest.$objext\nCFLAGS=$_lt_libdeps_save_CFLAGS\n\n# PORTME: override above test on systems where it is broken\nm4_if([$1], [CXX],\n[case $host_os in\ninterix[[3-9]]*)\n  # Interix 3.5 installs completely hosed .la files for C++, so rather than\n  # hack all around it, let's just trust \"g++\" to DTRT.\n  _LT_TAGVAR(predep_objects,$1)=\n  _LT_TAGVAR(postdep_objects,$1)=\n  _LT_TAGVAR(postdeps,$1)=\n  ;;\nesac\n])\n\ncase \" $_LT_TAGVAR(postdeps, $1) \" in\n*\" -lc \"*) _LT_TAGVAR(archive_cmds_need_lc, $1)=no ;;\nesac\n _LT_TAGVAR(compiler_lib_search_dirs, $1)=\nif test -n \"${_LT_TAGVAR(compiler_lib_search_path, $1)}\"; then\n _LT_TAGVAR(compiler_lib_search_dirs, $1)=`echo \" ${_LT_TAGVAR(compiler_lib_search_path, $1)}\" | $SED -e 's! -L! !g' -e 's!^ !!'`\nfi\n_LT_TAGDECL([], [compiler_lib_search_dirs], [1],\n    [The directories searched by this compiler when creating a shared library])\n_LT_TAGDECL([], [predep_objects], [1],\n    [Dependencies to place before and after the objects being linked to\n    create a shared library])\n_LT_TAGDECL([], [postdep_objects], [1])\n_LT_TAGDECL([], [predeps], [1])\n_LT_TAGDECL([], [postdeps], [1])\n_LT_TAGDECL([], [compiler_lib_search_path], [1],\n    [The library search path used internally by the compiler when linking\n    a shared library])\n])# _LT_SYS_HIDDEN_LIBDEPS\n\n\n# _LT_LANG_F77_CONFIG([TAG])\n# --------------------------\n# Ensure that the configuration variables for a Fortran 77 compiler are\n# suitably defined.  These variables are subsequently used by _LT_CONFIG\n# to write the compiler configuration to 'libtool'.\nm4_defun([_LT_LANG_F77_CONFIG],\n[AC_LANG_PUSH(Fortran 77)\nif test -z \"$F77\" || test no = \"$F77\"; then\n  _lt_disable_F77=yes\nfi\n\n_LT_TAGVAR(archive_cmds_need_lc, $1)=no\n_LT_TAGVAR(allow_undefined_flag, $1)=\n_LT_TAGVAR(always_export_symbols, $1)=no\n_LT_TAGVAR(archive_expsym_cmds, $1)=\n_LT_TAGVAR(export_dynamic_flag_spec, $1)=\n_LT_TAGVAR(hardcode_direct, $1)=no\n_LT_TAGVAR(hardcode_direct_absolute, $1)=no\n_LT_TAGVAR(hardcode_libdir_flag_spec, $1)=\n_LT_TAGVAR(hardcode_libdir_separator, $1)=\n_LT_TAGVAR(hardcode_minus_L, $1)=no\n_LT_TAGVAR(hardcode_automatic, $1)=no\n_LT_TAGVAR(inherit_rpath, $1)=no\n_LT_TAGVAR(module_cmds, $1)=\n_LT_TAGVAR(module_expsym_cmds, $1)=\n_LT_TAGVAR(link_all_deplibs, $1)=unknown\n_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds\n_LT_TAGVAR(reload_flag, $1)=$reload_flag\n_LT_TAGVAR(reload_cmds, $1)=$reload_cmds\n_LT_TAGVAR(no_undefined_flag, $1)=\n_LT_TAGVAR(whole_archive_flag_spec, $1)=\n_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no\n\n# Source file extension for f77 test sources.\nac_ext=f\n\n# Object file extension for compiled f77 test sources.\nobjext=o\n_LT_TAGVAR(objext, $1)=$objext\n\n# No sense in running all these tests if we already determined that\n# the F77 compiler isn't working.  Some variables (like enable_shared)\n# are currently assumed to apply to all compilers on this platform,\n# and will be corrupted by setting them based on a non-working compiler.\nif test yes != \"$_lt_disable_F77\"; then\n  # Code to be used in simple compile tests\n  lt_simple_compile_test_code=\"\\\n      subroutine t\n      return\n      end\n\"\n\n  # Code to be used in simple link tests\n  lt_simple_link_test_code=\"\\\n      program t\n      end\n\"\n\n  # ltmain only uses $CC for tagged configurations so make sure $CC is set.\n  _LT_TAG_COMPILER\n\n  # save warnings/boilerplate of simple test code\n  _LT_COMPILER_BOILERPLATE\n  _LT_LINKER_BOILERPLATE\n\n  # Allow CC to be a program name with arguments.\n  lt_save_CC=$CC\n  lt_save_GCC=$GCC\n  lt_save_CFLAGS=$CFLAGS\n  CC=${F77-\"f77\"}\n  CFLAGS=$FFLAGS\n  compiler=$CC\n  _LT_TAGVAR(compiler, $1)=$CC\n  _LT_CC_BASENAME([$compiler])\n  GCC=$G77\n  if test -n \"$compiler\"; then\n    AC_MSG_CHECKING([if libtool supports shared libraries])\n    AC_MSG_RESULT([$can_build_shared])\n\n    AC_MSG_CHECKING([whether to build shared libraries])\n    test no = \"$can_build_shared\" && enable_shared=no\n\n    # On AIX, shared libraries and static libraries use the same namespace, and\n    # are all built from PIC.\n    case $host_os in\n      aix3*)\n        test yes = \"$enable_shared\" && enable_static=no\n        if test -n \"$RANLIB\"; then\n          archive_cmds=\"$archive_cmds~\\$RANLIB \\$lib\"\n          postinstall_cmds='$RANLIB $lib'\n        fi\n        ;;\n      aix[[4-9]]*)\n\tif test ia64 != \"$host_cpu\"; then\n\t  case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in\n\t  yes,aix,yes) ;;\t\t# shared object as lib.so file only\n\t  yes,svr4,*) ;;\t\t# shared object as lib.so archive member only\n\t  yes,*) enable_static=no ;;\t# shared object in lib.a archive as well\n\t  esac\n\tfi\n        ;;\n    esac\n    AC_MSG_RESULT([$enable_shared])\n\n    AC_MSG_CHECKING([whether to build static libraries])\n    # Make sure either enable_shared or enable_static is yes.\n    test yes = \"$enable_shared\" || enable_static=yes\n    AC_MSG_RESULT([$enable_static])\n\n    _LT_TAGVAR(GCC, $1)=$G77\n    _LT_TAGVAR(LD, $1)=$LD\n\n    ## CAVEAT EMPTOR:\n    ## There is no encapsulation within the following macros, do not change\n    ## the running order or otherwise move them around unless you know exactly\n    ## what you are doing...\n    _LT_COMPILER_PIC($1)\n    _LT_COMPILER_C_O($1)\n    _LT_COMPILER_FILE_LOCKS($1)\n    _LT_LINKER_SHLIBS($1)\n    _LT_SYS_DYNAMIC_LINKER($1)\n    _LT_LINKER_HARDCODE_LIBPATH($1)\n\n    _LT_CONFIG($1)\n  fi # test -n \"$compiler\"\n\n  GCC=$lt_save_GCC\n  CC=$lt_save_CC\n  CFLAGS=$lt_save_CFLAGS\nfi # test yes != \"$_lt_disable_F77\"\n\nAC_LANG_POP\n])# _LT_LANG_F77_CONFIG\n\n\n# _LT_LANG_FC_CONFIG([TAG])\n# -------------------------\n# Ensure that the configuration variables for a Fortran compiler are\n# suitably defined.  These variables are subsequently used by _LT_CONFIG\n# to write the compiler configuration to 'libtool'.\nm4_defun([_LT_LANG_FC_CONFIG],\n[AC_LANG_PUSH(Fortran)\n\nif test -z \"$FC\" || test no = \"$FC\"; then\n  _lt_disable_FC=yes\nfi\n\n_LT_TAGVAR(archive_cmds_need_lc, $1)=no\n_LT_TAGVAR(allow_undefined_flag, $1)=\n_LT_TAGVAR(always_export_symbols, $1)=no\n_LT_TAGVAR(archive_expsym_cmds, $1)=\n_LT_TAGVAR(export_dynamic_flag_spec, $1)=\n_LT_TAGVAR(hardcode_direct, $1)=no\n_LT_TAGVAR(hardcode_direct_absolute, $1)=no\n_LT_TAGVAR(hardcode_libdir_flag_spec, $1)=\n_LT_TAGVAR(hardcode_libdir_separator, $1)=\n_LT_TAGVAR(hardcode_minus_L, $1)=no\n_LT_TAGVAR(hardcode_automatic, $1)=no\n_LT_TAGVAR(inherit_rpath, $1)=no\n_LT_TAGVAR(module_cmds, $1)=\n_LT_TAGVAR(module_expsym_cmds, $1)=\n_LT_TAGVAR(link_all_deplibs, $1)=unknown\n_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds\n_LT_TAGVAR(reload_flag, $1)=$reload_flag\n_LT_TAGVAR(reload_cmds, $1)=$reload_cmds\n_LT_TAGVAR(no_undefined_flag, $1)=\n_LT_TAGVAR(whole_archive_flag_spec, $1)=\n_LT_TAGVAR(enable_shared_with_static_runtimes, $1)=no\n\n# Source file extension for fc test sources.\nac_ext=${ac_fc_srcext-f}\n\n# Object file extension for compiled fc test sources.\nobjext=o\n_LT_TAGVAR(objext, $1)=$objext\n\n# No sense in running all these tests if we already determined that\n# the FC compiler isn't working.  Some variables (like enable_shared)\n# are currently assumed to apply to all compilers on this platform,\n# and will be corrupted by setting them based on a non-working compiler.\nif test yes != \"$_lt_disable_FC\"; then\n  # Code to be used in simple compile tests\n  lt_simple_compile_test_code=\"\\\n      subroutine t\n      return\n      end\n\"\n\n  # Code to be used in simple link tests\n  lt_simple_link_test_code=\"\\\n      program t\n      end\n\"\n\n  # ltmain only uses $CC for tagged configurations so make sure $CC is set.\n  _LT_TAG_COMPILER\n\n  # save warnings/boilerplate of simple test code\n  _LT_COMPILER_BOILERPLATE\n  _LT_LINKER_BOILERPLATE\n\n  # Allow CC to be a program name with arguments.\n  lt_save_CC=$CC\n  lt_save_GCC=$GCC\n  lt_save_CFLAGS=$CFLAGS\n  CC=${FC-\"f95\"}\n  CFLAGS=$FCFLAGS\n  compiler=$CC\n  GCC=$ac_cv_fc_compiler_gnu\n\n  _LT_TAGVAR(compiler, $1)=$CC\n  _LT_CC_BASENAME([$compiler])\n\n  if test -n \"$compiler\"; then\n    AC_MSG_CHECKING([if libtool supports shared libraries])\n    AC_MSG_RESULT([$can_build_shared])\n\n    AC_MSG_CHECKING([whether to build shared libraries])\n    test no = \"$can_build_shared\" && enable_shared=no\n\n    # On AIX, shared libraries and static libraries use the same namespace, and\n    # are all built from PIC.\n    case $host_os in\n      aix3*)\n        test yes = \"$enable_shared\" && enable_static=no\n        if test -n \"$RANLIB\"; then\n          archive_cmds=\"$archive_cmds~\\$RANLIB \\$lib\"\n          postinstall_cmds='$RANLIB $lib'\n        fi\n        ;;\n      aix[[4-9]]*)\n\tif test ia64 != \"$host_cpu\"; then\n\t  case $enable_shared,$with_aix_soname,$aix_use_runtimelinking in\n\t  yes,aix,yes) ;;\t\t# shared object as lib.so file only\n\t  yes,svr4,*) ;;\t\t# shared object as lib.so archive member only\n\t  yes,*) enable_static=no ;;\t# shared object in lib.a archive as well\n\t  esac\n\tfi\n        ;;\n    esac\n    AC_MSG_RESULT([$enable_shared])\n\n    AC_MSG_CHECKING([whether to build static libraries])\n    # Make sure either enable_shared or enable_static is yes.\n    test yes = \"$enable_shared\" || enable_static=yes\n    AC_MSG_RESULT([$enable_static])\n\n    _LT_TAGVAR(GCC, $1)=$ac_cv_fc_compiler_gnu\n    _LT_TAGVAR(LD, $1)=$LD\n\n    ## CAVEAT EMPTOR:\n    ## There is no encapsulation within the following macros, do not change\n    ## the running order or otherwise move them around unless you know exactly\n    ## what you are doing...\n    _LT_SYS_HIDDEN_LIBDEPS($1)\n    _LT_COMPILER_PIC($1)\n    _LT_COMPILER_C_O($1)\n    _LT_COMPILER_FILE_LOCKS($1)\n    _LT_LINKER_SHLIBS($1)\n    _LT_SYS_DYNAMIC_LINKER($1)\n    _LT_LINKER_HARDCODE_LIBPATH($1)\n\n    _LT_CONFIG($1)\n  fi # test -n \"$compiler\"\n\n  GCC=$lt_save_GCC\n  CC=$lt_save_CC\n  CFLAGS=$lt_save_CFLAGS\nfi # test yes != \"$_lt_disable_FC\"\n\nAC_LANG_POP\n])# _LT_LANG_FC_CONFIG\n\n\n# _LT_LANG_GCJ_CONFIG([TAG])\n# --------------------------\n# Ensure that the configuration variables for the GNU Java Compiler compiler\n# are suitably defined.  These variables are subsequently used by _LT_CONFIG\n# to write the compiler configuration to 'libtool'.\nm4_defun([_LT_LANG_GCJ_CONFIG],\n[AC_REQUIRE([LT_PROG_GCJ])dnl\nAC_LANG_SAVE\n\n# Source file extension for Java test sources.\nac_ext=java\n\n# Object file extension for compiled Java test sources.\nobjext=o\n_LT_TAGVAR(objext, $1)=$objext\n\n# Code to be used in simple compile tests\nlt_simple_compile_test_code=\"class foo {}\"\n\n# Code to be used in simple link tests\nlt_simple_link_test_code='public class conftest { public static void main(String[[]] argv) {}; }'\n\n# ltmain only uses $CC for tagged configurations so make sure $CC is set.\n_LT_TAG_COMPILER\n\n# save warnings/boilerplate of simple test code\n_LT_COMPILER_BOILERPLATE\n_LT_LINKER_BOILERPLATE\n\n# Allow CC to be a program name with arguments.\nlt_save_CC=$CC\nlt_save_CFLAGS=$CFLAGS\nlt_save_GCC=$GCC\nGCC=yes\nCC=${GCJ-\"gcj\"}\nCFLAGS=$GCJFLAGS\ncompiler=$CC\n_LT_TAGVAR(compiler, $1)=$CC\n_LT_TAGVAR(LD, $1)=$LD\n_LT_CC_BASENAME([$compiler])\n\n# GCJ did not exist at the time GCC didn't implicitly link libc in.\n_LT_TAGVAR(archive_cmds_need_lc, $1)=no\n\n_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds\n_LT_TAGVAR(reload_flag, $1)=$reload_flag\n_LT_TAGVAR(reload_cmds, $1)=$reload_cmds\n\n## CAVEAT EMPTOR:\n## There is no encapsulation within the following macros, do not change\n## the running order or otherwise move them around unless you know exactly\n## what you are doing...\nif test -n \"$compiler\"; then\n  _LT_COMPILER_NO_RTTI($1)\n  _LT_COMPILER_PIC($1)\n  _LT_COMPILER_C_O($1)\n  _LT_COMPILER_FILE_LOCKS($1)\n  _LT_LINKER_SHLIBS($1)\n  _LT_LINKER_HARDCODE_LIBPATH($1)\n\n  _LT_CONFIG($1)\nfi\n\nAC_LANG_RESTORE\n\nGCC=$lt_save_GCC\nCC=$lt_save_CC\nCFLAGS=$lt_save_CFLAGS\n])# _LT_LANG_GCJ_CONFIG\n\n\n# _LT_LANG_GO_CONFIG([TAG])\n# --------------------------\n# Ensure that the configuration variables for the GNU Go compiler\n# are suitably defined.  These variables are subsequently used by _LT_CONFIG\n# to write the compiler configuration to 'libtool'.\nm4_defun([_LT_LANG_GO_CONFIG],\n[AC_REQUIRE([LT_PROG_GO])dnl\nAC_LANG_SAVE\n\n# Source file extension for Go test sources.\nac_ext=go\n\n# Object file extension for compiled Go test sources.\nobjext=o\n_LT_TAGVAR(objext, $1)=$objext\n\n# Code to be used in simple compile tests\nlt_simple_compile_test_code=\"package main; func main() { }\"\n\n# Code to be used in simple link tests\nlt_simple_link_test_code='package main; func main() { }'\n\n# ltmain only uses $CC for tagged configurations so make sure $CC is set.\n_LT_TAG_COMPILER\n\n# save warnings/boilerplate of simple test code\n_LT_COMPILER_BOILERPLATE\n_LT_LINKER_BOILERPLATE\n\n# Allow CC to be a program name with arguments.\nlt_save_CC=$CC\nlt_save_CFLAGS=$CFLAGS\nlt_save_GCC=$GCC\nGCC=yes\nCC=${GOC-\"gccgo\"}\nCFLAGS=$GOFLAGS\ncompiler=$CC\n_LT_TAGVAR(compiler, $1)=$CC\n_LT_TAGVAR(LD, $1)=$LD\n_LT_CC_BASENAME([$compiler])\n\n# Go did not exist at the time GCC didn't implicitly link libc in.\n_LT_TAGVAR(archive_cmds_need_lc, $1)=no\n\n_LT_TAGVAR(old_archive_cmds, $1)=$old_archive_cmds\n_LT_TAGVAR(reload_flag, $1)=$reload_flag\n_LT_TAGVAR(reload_cmds, $1)=$reload_cmds\n\n## CAVEAT EMPTOR:\n## There is no encapsulation within the following macros, do not change\n## the running order or otherwise move them around unless you know exactly\n## what you are doing...\nif test -n \"$compiler\"; then\n  _LT_COMPILER_NO_RTTI($1)\n  _LT_COMPILER_PIC($1)\n  _LT_COMPILER_C_O($1)\n  _LT_COMPILER_FILE_LOCKS($1)\n  _LT_LINKER_SHLIBS($1)\n  _LT_LINKER_HARDCODE_LIBPATH($1)\n\n  _LT_CONFIG($1)\nfi\n\nAC_LANG_RESTORE\n\nGCC=$lt_save_GCC\nCC=$lt_save_CC\nCFLAGS=$lt_save_CFLAGS\n])# _LT_LANG_GO_CONFIG\n\n\n# _LT_LANG_RC_CONFIG([TAG])\n# -------------------------\n# Ensure that the configuration variables for the Windows resource compiler\n# are suitably defined.  These variables are subsequently used by _LT_CONFIG\n# to write the compiler configuration to 'libtool'.\nm4_defun([_LT_LANG_RC_CONFIG],\n[AC_REQUIRE([LT_PROG_RC])dnl\nAC_LANG_SAVE\n\n# Source file extension for RC test sources.\nac_ext=rc\n\n# Object file extension for compiled RC test sources.\nobjext=o\n_LT_TAGVAR(objext, $1)=$objext\n\n# Code to be used in simple compile tests\nlt_simple_compile_test_code='sample MENU { MENUITEM \"&Soup\", 100, CHECKED }'\n\n# Code to be used in simple link tests\nlt_simple_link_test_code=$lt_simple_compile_test_code\n\n# ltmain only uses $CC for tagged configurations so make sure $CC is set.\n_LT_TAG_COMPILER\n\n# save warnings/boilerplate of simple test code\n_LT_COMPILER_BOILERPLATE\n_LT_LINKER_BOILERPLATE\n\n# Allow CC to be a program name with arguments.\nlt_save_CC=$CC\nlt_save_CFLAGS=$CFLAGS\nlt_save_GCC=$GCC\nGCC=\nCC=${RC-\"windres\"}\nCFLAGS=\ncompiler=$CC\n_LT_TAGVAR(compiler, $1)=$CC\n_LT_CC_BASENAME([$compiler])\n_LT_TAGVAR(lt_cv_prog_compiler_c_o, $1)=yes\n\nif test -n \"$compiler\"; then\n  :\n  _LT_CONFIG($1)\nfi\n\nGCC=$lt_save_GCC\nAC_LANG_RESTORE\nCC=$lt_save_CC\nCFLAGS=$lt_save_CFLAGS\n])# _LT_LANG_RC_CONFIG\n\n\n# LT_PROG_GCJ\n# -----------\nAC_DEFUN([LT_PROG_GCJ],\n[m4_ifdef([AC_PROG_GCJ], [AC_PROG_GCJ],\n  [m4_ifdef([A][M_PROG_GCJ], [A][M_PROG_GCJ],\n    [AC_CHECK_TOOL(GCJ, gcj,)\n      test set = \"${GCJFLAGS+set}\" || GCJFLAGS=\"-g -O2\"\n      AC_SUBST(GCJFLAGS)])])[]dnl\n])\n\n# Old name:\nAU_ALIAS([LT_AC_PROG_GCJ], [LT_PROG_GCJ])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([LT_AC_PROG_GCJ], [])\n\n\n# LT_PROG_GO\n# ----------\nAC_DEFUN([LT_PROG_GO],\n[AC_CHECK_TOOL(GOC, gccgo,)\n])\n\n\n# LT_PROG_RC\n# ----------\nAC_DEFUN([LT_PROG_RC],\n[AC_CHECK_TOOL(RC, windres,)\n])\n\n# Old name:\nAU_ALIAS([LT_AC_PROG_RC], [LT_PROG_RC])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([LT_AC_PROG_RC], [])\n\n\n# _LT_DECL_EGREP\n# --------------\n# If we don't have a new enough Autoconf to choose the best grep\n# available, choose the one first in the user's PATH.\nm4_defun([_LT_DECL_EGREP],\n[AC_REQUIRE([AC_PROG_EGREP])dnl\nAC_REQUIRE([AC_PROG_FGREP])dnl\ntest -z \"$GREP\" && GREP=grep\n_LT_DECL([], [GREP], [1], [A grep program that handles long lines])\n_LT_DECL([], [EGREP], [1], [An ERE matcher])\n_LT_DECL([], [FGREP], [1], [A literal string matcher])\ndnl Non-bleeding-edge autoconf doesn't subst GREP, so do it here too\nAC_SUBST([GREP])\n])\n\n\n# _LT_DECL_OBJDUMP\n# --------------\n# If we don't have a new enough Autoconf to choose the best objdump\n# available, choose the one first in the user's PATH.\nm4_defun([_LT_DECL_OBJDUMP],\n[AC_CHECK_TOOL(OBJDUMP, objdump, false)\ntest -z \"$OBJDUMP\" && OBJDUMP=objdump\n_LT_DECL([], [OBJDUMP], [1], [An object symbol dumper])\nAC_SUBST([OBJDUMP])\n])\n\n# _LT_DECL_DLLTOOL\n# ----------------\n# Ensure DLLTOOL variable is set.\nm4_defun([_LT_DECL_DLLTOOL],\n[AC_CHECK_TOOL(DLLTOOL, dlltool, false)\ntest -z \"$DLLTOOL\" && DLLTOOL=dlltool\n_LT_DECL([], [DLLTOOL], [1], [DLL creation program])\nAC_SUBST([DLLTOOL])\n])\n\n# _LT_DECL_FILECMD\n# ----------------\n# Check for a file(cmd) program that can be used to detect file type and magic\nm4_defun([_LT_DECL_FILECMD],\n[AC_CHECK_TOOL([FILECMD], [file], [:])\n_LT_DECL([], [FILECMD], [1], [A file(cmd) program that detects file types])\n])# _LD_DECL_FILECMD\n\n# _LT_DECL_SED\n# ------------\n# Check for a fully-functional sed program, that truncates\n# as few characters as possible.  Prefer GNU sed if found.\nm4_defun([_LT_DECL_SED],\n[AC_PROG_SED\ntest -z \"$SED\" && SED=sed\nXsed=\"$SED -e 1s/^X//\"\n_LT_DECL([], [SED], [1], [A sed program that does not truncate output])\n_LT_DECL([], [Xsed], [\"\\$SED -e 1s/^X//\"],\n    [Sed that helps us avoid accidentally triggering echo(1) options like -n])\n])# _LT_DECL_SED\n\nm4_ifndef([AC_PROG_SED], [\n############################################################\n# NOTE: This macro has been submitted for inclusion into   #\n#  GNU Autoconf as AC_PROG_SED.  When it is available in   #\n#  a released version of Autoconf we should remove this    #\n#  macro and use it instead.                               #\n############################################################\n\nm4_defun([AC_PROG_SED],\n[AC_MSG_CHECKING([for a sed that does not truncate output])\nAC_CACHE_VAL(lt_cv_path_SED,\n[# Loop through the user's path and test for sed and gsed.\n# Then use that list of sed's as ones to test for truncation.\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for lt_ac_prog in sed gsed; do\n    for ac_exec_ext in '' $ac_executable_extensions; do\n      if $as_executable_p \"$as_dir/$lt_ac_prog$ac_exec_ext\"; then\n        lt_ac_sed_list=\"$lt_ac_sed_list $as_dir/$lt_ac_prog$ac_exec_ext\"\n      fi\n    done\n  done\ndone\nIFS=$as_save_IFS\nlt_ac_max=0\nlt_ac_count=0\n# Add /usr/xpg4/bin/sed as it is typically found on Solaris\n# along with /bin/sed that truncates output.\nfor lt_ac_sed in $lt_ac_sed_list /usr/xpg4/bin/sed; do\n  test ! -f \"$lt_ac_sed\" && continue\n  cat /dev/null > conftest.in\n  lt_ac_count=0\n  echo $ECHO_N \"0123456789$ECHO_C\" >conftest.in\n  # Check for GNU sed and select it if it is found.\n  if \"$lt_ac_sed\" --version 2>&1 < /dev/null | grep 'GNU' > /dev/null; then\n    lt_cv_path_SED=$lt_ac_sed\n    break\n  fi\n  while true; do\n    cat conftest.in conftest.in >conftest.tmp\n    mv conftest.tmp conftest.in\n    cp conftest.in conftest.nl\n    echo >>conftest.nl\n    $lt_ac_sed -e 's/a$//' < conftest.nl >conftest.out || break\n    cmp -s conftest.out conftest.nl || break\n    # 10000 chars as input seems more than enough\n    test 10 -lt \"$lt_ac_count\" && break\n    lt_ac_count=`expr $lt_ac_count + 1`\n    if test \"$lt_ac_count\" -gt \"$lt_ac_max\"; then\n      lt_ac_max=$lt_ac_count\n      lt_cv_path_SED=$lt_ac_sed\n    fi\n  done\ndone\n])\nSED=$lt_cv_path_SED\nAC_SUBST([SED])\nAC_MSG_RESULT([$SED])\n])#AC_PROG_SED\n])#m4_ifndef\n\n# Old name:\nAU_ALIAS([LT_AC_PROG_SED], [AC_PROG_SED])\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([LT_AC_PROG_SED], [])\n\n\n# _LT_CHECK_SHELL_FEATURES\n# ------------------------\n# Find out whether the shell is Bourne or XSI compatible,\n# or has some other useful features.\nm4_defun([_LT_CHECK_SHELL_FEATURES],\n[if ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then\n  lt_unset=unset\nelse\n  lt_unset=false\nfi\n_LT_DECL([], [lt_unset], [0], [whether the shell understands \"unset\"])dnl\n\n# test EBCDIC or ASCII\ncase `echo X|tr X '\\101'` in\n A) # ASCII based system\n    # \\n is not interpreted correctly by Solaris 8 /usr/ucb/tr\n  lt_SP2NL='tr \\040 \\012'\n  lt_NL2SP='tr \\015\\012 \\040\\040'\n  ;;\n *) # EBCDIC based system\n  lt_SP2NL='tr \\100 \\n'\n  lt_NL2SP='tr \\r\\n \\100\\100'\n  ;;\nesac\n_LT_DECL([SP2NL], [lt_SP2NL], [1], [turn spaces into newlines])dnl\n_LT_DECL([NL2SP], [lt_NL2SP], [1], [turn newlines into spaces])dnl\n])# _LT_CHECK_SHELL_FEATURES\n\n\n# _LT_PATH_CONVERSION_FUNCTIONS\n# -----------------------------\n# Determine what file name conversion functions should be used by\n# func_to_host_file (and, implicitly, by func_to_host_path).  These are needed\n# for certain cross-compile configurations and native mingw.\nm4_defun([_LT_PATH_CONVERSION_FUNCTIONS],\n[AC_REQUIRE([AC_CANONICAL_HOST])dnl\nAC_REQUIRE([AC_CANONICAL_BUILD])dnl\nAC_MSG_CHECKING([how to convert $build file names to $host format])\nAC_CACHE_VAL(lt_cv_to_host_file_cmd,\n[case $host in\n  *-*-mingw* )\n    case $build in\n      *-*-mingw* ) # actually msys\n        lt_cv_to_host_file_cmd=func_convert_file_msys_to_w32\n        ;;\n      *-*-cygwin* )\n        lt_cv_to_host_file_cmd=func_convert_file_cygwin_to_w32\n        ;;\n      * ) # otherwise, assume *nix\n        lt_cv_to_host_file_cmd=func_convert_file_nix_to_w32\n        ;;\n    esac\n    ;;\n  *-*-cygwin* )\n    case $build in\n      *-*-mingw* ) # actually msys\n        lt_cv_to_host_file_cmd=func_convert_file_msys_to_cygwin\n        ;;\n      *-*-cygwin* )\n        lt_cv_to_host_file_cmd=func_convert_file_noop\n        ;;\n      * ) # otherwise, assume *nix\n        lt_cv_to_host_file_cmd=func_convert_file_nix_to_cygwin\n        ;;\n    esac\n    ;;\n  * ) # unhandled hosts (and \"normal\" native builds)\n    lt_cv_to_host_file_cmd=func_convert_file_noop\n    ;;\nesac\n])\nto_host_file_cmd=$lt_cv_to_host_file_cmd\nAC_MSG_RESULT([$lt_cv_to_host_file_cmd])\n_LT_DECL([to_host_file_cmd], [lt_cv_to_host_file_cmd],\n         [0], [convert $build file names to $host format])dnl\n\nAC_MSG_CHECKING([how to convert $build file names to toolchain format])\nAC_CACHE_VAL(lt_cv_to_tool_file_cmd,\n[#assume ordinary cross tools, or native build.\nlt_cv_to_tool_file_cmd=func_convert_file_noop\ncase $host in\n  *-*-mingw* )\n    case $build in\n      *-*-mingw* ) # actually msys\n        lt_cv_to_tool_file_cmd=func_convert_file_msys_to_w32\n        ;;\n    esac\n    ;;\nesac\n])\nto_tool_file_cmd=$lt_cv_to_tool_file_cmd\nAC_MSG_RESULT([$lt_cv_to_tool_file_cmd])\n_LT_DECL([to_tool_file_cmd], [lt_cv_to_tool_file_cmd],\n         [0], [convert $build files to toolchain format])dnl\n])# _LT_PATH_CONVERSION_FUNCTIONS\n"
  },
  {
    "path": "cudd/m4/ltoptions.m4",
    "content": "# Helper functions for option handling.                    -*- Autoconf -*-\n#\n#   Copyright (C) 2004-2005, 2007-2009, 2011-2015 Free Software\n#   Foundation, Inc.\n#   Written by Gary V. Vaughan, 2004\n#\n# This file is free software; the Free Software Foundation gives\n# unlimited permission to copy and/or distribute it, with or without\n# modifications, as long as this notice is preserved.\n\n# serial 8 ltoptions.m4\n\n# This is to help aclocal find these macros, as it can't see m4_define.\nAC_DEFUN([LTOPTIONS_VERSION], [m4_if([1])])\n\n\n# _LT_MANGLE_OPTION(MACRO-NAME, OPTION-NAME)\n# ------------------------------------------\nm4_define([_LT_MANGLE_OPTION],\n[[_LT_OPTION_]m4_bpatsubst($1__$2, [[^a-zA-Z0-9_]], [_])])\n\n\n# _LT_SET_OPTION(MACRO-NAME, OPTION-NAME)\n# ---------------------------------------\n# Set option OPTION-NAME for macro MACRO-NAME, and if there is a\n# matching handler defined, dispatch to it.  Other OPTION-NAMEs are\n# saved as a flag.\nm4_define([_LT_SET_OPTION],\n[m4_define(_LT_MANGLE_OPTION([$1], [$2]))dnl\nm4_ifdef(_LT_MANGLE_DEFUN([$1], [$2]),\n        _LT_MANGLE_DEFUN([$1], [$2]),\n    [m4_warning([Unknown $1 option '$2'])])[]dnl\n])\n\n\n# _LT_IF_OPTION(MACRO-NAME, OPTION-NAME, IF-SET, [IF-NOT-SET])\n# ------------------------------------------------------------\n# Execute IF-SET if OPTION is set, IF-NOT-SET otherwise.\nm4_define([_LT_IF_OPTION],\n[m4_ifdef(_LT_MANGLE_OPTION([$1], [$2]), [$3], [$4])])\n\n\n# _LT_UNLESS_OPTIONS(MACRO-NAME, OPTION-LIST, IF-NOT-SET)\n# -------------------------------------------------------\n# Execute IF-NOT-SET unless all options in OPTION-LIST for MACRO-NAME\n# are set.\nm4_define([_LT_UNLESS_OPTIONS],\n[m4_foreach([_LT_Option], m4_split(m4_normalize([$2])),\n\t    [m4_ifdef(_LT_MANGLE_OPTION([$1], _LT_Option),\n\t\t      [m4_define([$0_found])])])[]dnl\nm4_ifdef([$0_found], [m4_undefine([$0_found])], [$3\n])[]dnl\n])\n\n\n# _LT_SET_OPTIONS(MACRO-NAME, OPTION-LIST)\n# ----------------------------------------\n# OPTION-LIST is a space-separated list of Libtool options associated\n# with MACRO-NAME.  If any OPTION has a matching handler declared with\n# LT_OPTION_DEFINE, dispatch to that macro; otherwise complain about\n# the unknown option and exit.\nm4_defun([_LT_SET_OPTIONS],\n[# Set options\nm4_foreach([_LT_Option], m4_split(m4_normalize([$2])),\n    [_LT_SET_OPTION([$1], _LT_Option)])\n\nm4_if([$1],[LT_INIT],[\n  dnl\n  dnl Simply set some default values (i.e off) if boolean options were not\n  dnl specified:\n  _LT_UNLESS_OPTIONS([LT_INIT], [dlopen], [enable_dlopen=no\n  ])\n  _LT_UNLESS_OPTIONS([LT_INIT], [win32-dll], [enable_win32_dll=no\n  ])\n  dnl\n  dnl If no reference was made to various pairs of opposing options, then\n  dnl we run the default mode handler for the pair.  For example, if neither\n  dnl 'shared' nor 'disable-shared' was passed, we enable building of shared\n  dnl archives by default:\n  _LT_UNLESS_OPTIONS([LT_INIT], [shared disable-shared], [_LT_ENABLE_SHARED])\n  _LT_UNLESS_OPTIONS([LT_INIT], [static disable-static], [_LT_ENABLE_STATIC])\n  _LT_UNLESS_OPTIONS([LT_INIT], [pic-only no-pic], [_LT_WITH_PIC])\n  _LT_UNLESS_OPTIONS([LT_INIT], [fast-install disable-fast-install],\n\t\t   [_LT_ENABLE_FAST_INSTALL])\n  _LT_UNLESS_OPTIONS([LT_INIT], [aix-soname=aix aix-soname=both aix-soname=svr4],\n\t\t   [_LT_WITH_AIX_SONAME([aix])])\n  ])\n])# _LT_SET_OPTIONS\n\n\n## --------------------------------- ##\n## Macros to handle LT_INIT options. ##\n## --------------------------------- ##\n\n# _LT_MANGLE_DEFUN(MACRO-NAME, OPTION-NAME)\n# -----------------------------------------\nm4_define([_LT_MANGLE_DEFUN],\n[[_LT_OPTION_DEFUN_]m4_bpatsubst(m4_toupper([$1__$2]), [[^A-Z0-9_]], [_])])\n\n\n# LT_OPTION_DEFINE(MACRO-NAME, OPTION-NAME, CODE)\n# -----------------------------------------------\nm4_define([LT_OPTION_DEFINE],\n[m4_define(_LT_MANGLE_DEFUN([$1], [$2]), [$3])[]dnl\n])# LT_OPTION_DEFINE\n\n\n# dlopen\n# ------\nLT_OPTION_DEFINE([LT_INIT], [dlopen], [enable_dlopen=yes\n])\n\nAU_DEFUN([AC_LIBTOOL_DLOPEN],\n[_LT_SET_OPTION([LT_INIT], [dlopen])\nAC_DIAGNOSE([obsolete],\n[$0: Remove this warning and the call to _LT_SET_OPTION when you\nput the 'dlopen' option into LT_INIT's first parameter.])\n])\n\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_LIBTOOL_DLOPEN], [])\n\n\n# win32-dll\n# ---------\n# Declare package support for building win32 dll's.\nLT_OPTION_DEFINE([LT_INIT], [win32-dll],\n[enable_win32_dll=yes\n\ncase $host in\n*-*-cygwin* | *-*-mingw* | *-*-pw32* | *-*-cegcc*)\n  AC_CHECK_TOOL(AS, as, false)\n  AC_CHECK_TOOL(DLLTOOL, dlltool, false)\n  AC_CHECK_TOOL(OBJDUMP, objdump, false)\n  ;;\nesac\n\ntest -z \"$AS\" && AS=as\n_LT_DECL([], [AS],      [1], [Assembler program])dnl\n\ntest -z \"$DLLTOOL\" && DLLTOOL=dlltool\n_LT_DECL([], [DLLTOOL], [1], [DLL creation program])dnl\n\ntest -z \"$OBJDUMP\" && OBJDUMP=objdump\n_LT_DECL([], [OBJDUMP], [1], [Object dumper program])dnl\n])# win32-dll\n\nAU_DEFUN([AC_LIBTOOL_WIN32_DLL],\n[AC_REQUIRE([AC_CANONICAL_HOST])dnl\n_LT_SET_OPTION([LT_INIT], [win32-dll])\nAC_DIAGNOSE([obsolete],\n[$0: Remove this warning and the call to _LT_SET_OPTION when you\nput the 'win32-dll' option into LT_INIT's first parameter.])\n])\n\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_LIBTOOL_WIN32_DLL], [])\n\n\n# _LT_ENABLE_SHARED([DEFAULT])\n# ----------------------------\n# implement the --enable-shared flag, and supports the 'shared' and\n# 'disable-shared' LT_INIT options.\n# DEFAULT is either 'yes' or 'no'.  If omitted, it defaults to 'yes'.\nm4_define([_LT_ENABLE_SHARED],\n[m4_define([_LT_ENABLE_SHARED_DEFAULT], [m4_if($1, no, no, yes)])dnl\nAC_ARG_ENABLE([shared],\n    [AS_HELP_STRING([--enable-shared@<:@=PKGS@:>@],\n\t[build shared libraries @<:@default=]_LT_ENABLE_SHARED_DEFAULT[@:>@])],\n    [p=${PACKAGE-default}\n    case $enableval in\n    yes) enable_shared=yes ;;\n    no) enable_shared=no ;;\n    *)\n      enable_shared=no\n      # Look at the argument we got.  We use all the common list separators.\n      lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,\n      for pkg in $enableval; do\n\tIFS=$lt_save_ifs\n\tif test \"X$pkg\" = \"X$p\"; then\n\t  enable_shared=yes\n\tfi\n      done\n      IFS=$lt_save_ifs\n      ;;\n    esac],\n    [enable_shared=]_LT_ENABLE_SHARED_DEFAULT)\n\n    _LT_DECL([build_libtool_libs], [enable_shared], [0],\n\t[Whether or not to build shared libraries])\n])# _LT_ENABLE_SHARED\n\nLT_OPTION_DEFINE([LT_INIT], [shared], [_LT_ENABLE_SHARED([yes])])\nLT_OPTION_DEFINE([LT_INIT], [disable-shared], [_LT_ENABLE_SHARED([no])])\n\n# Old names:\nAC_DEFUN([AC_ENABLE_SHARED],\n[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[shared])\n])\n\nAC_DEFUN([AC_DISABLE_SHARED],\n[_LT_SET_OPTION([LT_INIT], [disable-shared])\n])\n\nAU_DEFUN([AM_ENABLE_SHARED], [AC_ENABLE_SHARED($@)])\nAU_DEFUN([AM_DISABLE_SHARED], [AC_DISABLE_SHARED($@)])\n\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AM_ENABLE_SHARED], [])\ndnl AC_DEFUN([AM_DISABLE_SHARED], [])\n\n\n\n# _LT_ENABLE_STATIC([DEFAULT])\n# ----------------------------\n# implement the --enable-static flag, and support the 'static' and\n# 'disable-static' LT_INIT options.\n# DEFAULT is either 'yes' or 'no'.  If omitted, it defaults to 'yes'.\nm4_define([_LT_ENABLE_STATIC],\n[m4_define([_LT_ENABLE_STATIC_DEFAULT], [m4_if($1, no, no, yes)])dnl\nAC_ARG_ENABLE([static],\n    [AS_HELP_STRING([--enable-static@<:@=PKGS@:>@],\n\t[build static libraries @<:@default=]_LT_ENABLE_STATIC_DEFAULT[@:>@])],\n    [p=${PACKAGE-default}\n    case $enableval in\n    yes) enable_static=yes ;;\n    no) enable_static=no ;;\n    *)\n     enable_static=no\n      # Look at the argument we got.  We use all the common list separators.\n      lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,\n      for pkg in $enableval; do\n\tIFS=$lt_save_ifs\n\tif test \"X$pkg\" = \"X$p\"; then\n\t  enable_static=yes\n\tfi\n      done\n      IFS=$lt_save_ifs\n      ;;\n    esac],\n    [enable_static=]_LT_ENABLE_STATIC_DEFAULT)\n\n    _LT_DECL([build_old_libs], [enable_static], [0],\n\t[Whether or not to build static libraries])\n])# _LT_ENABLE_STATIC\n\nLT_OPTION_DEFINE([LT_INIT], [static], [_LT_ENABLE_STATIC([yes])])\nLT_OPTION_DEFINE([LT_INIT], [disable-static], [_LT_ENABLE_STATIC([no])])\n\n# Old names:\nAC_DEFUN([AC_ENABLE_STATIC],\n[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[static])\n])\n\nAC_DEFUN([AC_DISABLE_STATIC],\n[_LT_SET_OPTION([LT_INIT], [disable-static])\n])\n\nAU_DEFUN([AM_ENABLE_STATIC], [AC_ENABLE_STATIC($@)])\nAU_DEFUN([AM_DISABLE_STATIC], [AC_DISABLE_STATIC($@)])\n\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AM_ENABLE_STATIC], [])\ndnl AC_DEFUN([AM_DISABLE_STATIC], [])\n\n\n\n# _LT_ENABLE_FAST_INSTALL([DEFAULT])\n# ----------------------------------\n# implement the --enable-fast-install flag, and support the 'fast-install'\n# and 'disable-fast-install' LT_INIT options.\n# DEFAULT is either 'yes' or 'no'.  If omitted, it defaults to 'yes'.\nm4_define([_LT_ENABLE_FAST_INSTALL],\n[m4_define([_LT_ENABLE_FAST_INSTALL_DEFAULT], [m4_if($1, no, no, yes)])dnl\nAC_ARG_ENABLE([fast-install],\n    [AS_HELP_STRING([--enable-fast-install@<:@=PKGS@:>@],\n    [optimize for fast installation @<:@default=]_LT_ENABLE_FAST_INSTALL_DEFAULT[@:>@])],\n    [p=${PACKAGE-default}\n    case $enableval in\n    yes) enable_fast_install=yes ;;\n    no) enable_fast_install=no ;;\n    *)\n      enable_fast_install=no\n      # Look at the argument we got.  We use all the common list separators.\n      lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,\n      for pkg in $enableval; do\n\tIFS=$lt_save_ifs\n\tif test \"X$pkg\" = \"X$p\"; then\n\t  enable_fast_install=yes\n\tfi\n      done\n      IFS=$lt_save_ifs\n      ;;\n    esac],\n    [enable_fast_install=]_LT_ENABLE_FAST_INSTALL_DEFAULT)\n\n_LT_DECL([fast_install], [enable_fast_install], [0],\n\t [Whether or not to optimize for fast installation])dnl\n])# _LT_ENABLE_FAST_INSTALL\n\nLT_OPTION_DEFINE([LT_INIT], [fast-install], [_LT_ENABLE_FAST_INSTALL([yes])])\nLT_OPTION_DEFINE([LT_INIT], [disable-fast-install], [_LT_ENABLE_FAST_INSTALL([no])])\n\n# Old names:\nAU_DEFUN([AC_ENABLE_FAST_INSTALL],\n[_LT_SET_OPTION([LT_INIT], m4_if([$1], [no], [disable-])[fast-install])\nAC_DIAGNOSE([obsolete],\n[$0: Remove this warning and the call to _LT_SET_OPTION when you put\nthe 'fast-install' option into LT_INIT's first parameter.])\n])\n\nAU_DEFUN([AC_DISABLE_FAST_INSTALL],\n[_LT_SET_OPTION([LT_INIT], [disable-fast-install])\nAC_DIAGNOSE([obsolete],\n[$0: Remove this warning and the call to _LT_SET_OPTION when you put\nthe 'disable-fast-install' option into LT_INIT's first parameter.])\n])\n\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_ENABLE_FAST_INSTALL], [])\ndnl AC_DEFUN([AM_DISABLE_FAST_INSTALL], [])\n\n\n# _LT_WITH_AIX_SONAME([DEFAULT])\n# ----------------------------------\n# implement the --with-aix-soname flag, and support the `aix-soname=aix'\n# and `aix-soname=both' and `aix-soname=svr4' LT_INIT options. DEFAULT\n# is either `aix', `both' or `svr4'.  If omitted, it defaults to `aix'.\nm4_define([_LT_WITH_AIX_SONAME],\n[m4_define([_LT_WITH_AIX_SONAME_DEFAULT], [m4_if($1, svr4, svr4, m4_if($1, both, both, aix))])dnl\nshared_archive_member_spec=\ncase $host,$enable_shared in\npower*-*-aix[[5-9]]*,yes)\n  AC_MSG_CHECKING([which variant of shared library versioning to provide])\n  AC_ARG_WITH([aix-soname],\n    [AS_HELP_STRING([--with-aix-soname=aix|svr4|both],\n      [shared library versioning (aka \"SONAME\") variant to provide on AIX, @<:@default=]_LT_WITH_AIX_SONAME_DEFAULT[@:>@.])],\n    [case $withval in\n    aix|svr4|both)\n      ;;\n    *)\n      AC_MSG_ERROR([Unknown argument to --with-aix-soname])\n      ;;\n    esac\n    lt_cv_with_aix_soname=$with_aix_soname],\n    [AC_CACHE_VAL([lt_cv_with_aix_soname],\n      [lt_cv_with_aix_soname=]_LT_WITH_AIX_SONAME_DEFAULT)\n    with_aix_soname=$lt_cv_with_aix_soname])\n  AC_MSG_RESULT([$with_aix_soname])\n  if test aix != \"$with_aix_soname\"; then\n    # For the AIX way of multilib, we name the shared archive member\n    # based on the bitwidth used, traditionally 'shr.o' or 'shr_64.o',\n    # and 'shr.imp' or 'shr_64.imp', respectively, for the Import File.\n    # Even when GNU compilers ignore OBJECT_MODE but need '-maix64' flag,\n    # the AIX toolchain works better with OBJECT_MODE set (default 32).\n    if test 64 = \"${OBJECT_MODE-32}\"; then\n      shared_archive_member_spec=shr_64\n    else\n      shared_archive_member_spec=shr\n    fi\n  fi\n  ;;\n*)\n  with_aix_soname=aix\n  ;;\nesac\n\n_LT_DECL([], [shared_archive_member_spec], [0],\n    [Shared archive member basename, for filename based shared library versioning on AIX])dnl\n])# _LT_WITH_AIX_SONAME\n\nLT_OPTION_DEFINE([LT_INIT], [aix-soname=aix], [_LT_WITH_AIX_SONAME([aix])])\nLT_OPTION_DEFINE([LT_INIT], [aix-soname=both], [_LT_WITH_AIX_SONAME([both])])\nLT_OPTION_DEFINE([LT_INIT], [aix-soname=svr4], [_LT_WITH_AIX_SONAME([svr4])])\n\n\n# _LT_WITH_PIC([MODE])\n# --------------------\n# implement the --with-pic flag, and support the 'pic-only' and 'no-pic'\n# LT_INIT options.\n# MODE is either 'yes' or 'no'.  If omitted, it defaults to 'both'.\nm4_define([_LT_WITH_PIC],\n[AC_ARG_WITH([pic],\n    [AS_HELP_STRING([--with-pic@<:@=PKGS@:>@],\n\t[try to use only PIC/non-PIC objects @<:@default=use both@:>@])],\n    [lt_p=${PACKAGE-default}\n    case $withval in\n    yes|no) pic_mode=$withval ;;\n    *)\n      pic_mode=default\n      # Look at the argument we got.  We use all the common list separators.\n      lt_save_ifs=$IFS; IFS=$IFS$PATH_SEPARATOR,\n      for lt_pkg in $withval; do\n\tIFS=$lt_save_ifs\n\tif test \"X$lt_pkg\" = \"X$lt_p\"; then\n\t  pic_mode=yes\n\tfi\n      done\n      IFS=$lt_save_ifs\n      ;;\n    esac],\n    [pic_mode=m4_default([$1], [default])])\n\n_LT_DECL([], [pic_mode], [0], [What type of objects to build])dnl\n])# _LT_WITH_PIC\n\nLT_OPTION_DEFINE([LT_INIT], [pic-only], [_LT_WITH_PIC([yes])])\nLT_OPTION_DEFINE([LT_INIT], [no-pic], [_LT_WITH_PIC([no])])\n\n# Old name:\nAU_DEFUN([AC_LIBTOOL_PICMODE],\n[_LT_SET_OPTION([LT_INIT], [pic-only])\nAC_DIAGNOSE([obsolete],\n[$0: Remove this warning and the call to _LT_SET_OPTION when you\nput the 'pic-only' option into LT_INIT's first parameter.])\n])\n\ndnl aclocal-1.4 backwards compatibility:\ndnl AC_DEFUN([AC_LIBTOOL_PICMODE], [])\n\n## ----------------- ##\n## LTDL_INIT Options ##\n## ----------------- ##\n\nm4_define([_LTDL_MODE], [])\nLT_OPTION_DEFINE([LTDL_INIT], [nonrecursive],\n\t\t [m4_define([_LTDL_MODE], [nonrecursive])])\nLT_OPTION_DEFINE([LTDL_INIT], [recursive],\n\t\t [m4_define([_LTDL_MODE], [recursive])])\nLT_OPTION_DEFINE([LTDL_INIT], [subproject],\n\t\t [m4_define([_LTDL_MODE], [subproject])])\n\nm4_define([_LTDL_TYPE], [])\nLT_OPTION_DEFINE([LTDL_INIT], [installable],\n\t\t [m4_define([_LTDL_TYPE], [installable])])\nLT_OPTION_DEFINE([LTDL_INIT], [convenience],\n\t\t [m4_define([_LTDL_TYPE], [convenience])])\n"
  },
  {
    "path": "cudd/m4/ltsugar.m4",
    "content": "# ltsugar.m4 -- libtool m4 base layer.                         -*-Autoconf-*-\n#\n# Copyright (C) 2004, 2005, 2007, 2008 Free Software Foundation, Inc.\n# Written by Gary V. Vaughan, 2004\n#\n# This file is free software; the Free Software Foundation gives\n# unlimited permission to copy and/or distribute it, with or without\n# modifications, as long as this notice is preserved.\n\n# serial 6 ltsugar.m4\n\n# This is to help aclocal find these macros, as it can't see m4_define.\nAC_DEFUN([LTSUGAR_VERSION], [m4_if([0.1])])\n\n\n# lt_join(SEP, ARG1, [ARG2...])\n# -----------------------------\n# Produce ARG1SEPARG2...SEPARGn, omitting [] arguments and their\n# associated separator.\n# Needed until we can rely on m4_join from Autoconf 2.62, since all earlier\n# versions in m4sugar had bugs.\nm4_define([lt_join],\n[m4_if([$#], [1], [],\n       [$#], [2], [[$2]],\n       [m4_if([$2], [], [], [[$2]_])$0([$1], m4_shift(m4_shift($@)))])])\nm4_define([_lt_join],\n[m4_if([$#$2], [2], [],\n       [m4_if([$2], [], [], [[$1$2]])$0([$1], m4_shift(m4_shift($@)))])])\n\n\n# lt_car(LIST)\n# lt_cdr(LIST)\n# ------------\n# Manipulate m4 lists.\n# These macros are necessary as long as will still need to support\n# Autoconf-2.59 which quotes differently.\nm4_define([lt_car], [[$1]])\nm4_define([lt_cdr],\n[m4_if([$#], 0, [m4_fatal([$0: cannot be called without arguments])],\n       [$#], 1, [],\n       [m4_dquote(m4_shift($@))])])\nm4_define([lt_unquote], $1)\n\n\n# lt_append(MACRO-NAME, STRING, [SEPARATOR])\n# ------------------------------------------\n# Redefine MACRO-NAME to hold its former content plus `SEPARATOR'`STRING'.\n# Note that neither SEPARATOR nor STRING are expanded; they are appended\n# to MACRO-NAME as is (leaving the expansion for when MACRO-NAME is invoked).\n# No SEPARATOR is output if MACRO-NAME was previously undefined (different\n# than defined and empty).\n#\n# This macro is needed until we can rely on Autoconf 2.62, since earlier\n# versions of m4sugar mistakenly expanded SEPARATOR but not STRING.\nm4_define([lt_append],\n[m4_define([$1],\n\t   m4_ifdef([$1], [m4_defn([$1])[$3]])[$2])])\n\n\n\n# lt_combine(SEP, PREFIX-LIST, INFIX, SUFFIX1, [SUFFIX2...])\n# ----------------------------------------------------------\n# Produce a SEP delimited list of all paired combinations of elements of\n# PREFIX-LIST with SUFFIX1 through SUFFIXn.  Each element of the list\n# has the form PREFIXmINFIXSUFFIXn.\n# Needed until we can rely on m4_combine added in Autoconf 2.62.\nm4_define([lt_combine],\n[m4_if(m4_eval([$# > 3]), [1],\n       [m4_pushdef([_Lt_sep], [m4_define([_Lt_sep], m4_defn([lt_car]))])]]dnl\n[[m4_foreach([_Lt_prefix], [$2],\n\t     [m4_foreach([_Lt_suffix],\n\t\t]m4_dquote(m4_dquote(m4_shift(m4_shift(m4_shift($@)))))[,\n\t[_Lt_sep([$1])[]m4_defn([_Lt_prefix])[$3]m4_defn([_Lt_suffix])])])])])\n\n\n# lt_if_append_uniq(MACRO-NAME, VARNAME, [SEPARATOR], [UNIQ], [NOT-UNIQ])\n# -----------------------------------------------------------------------\n# Iff MACRO-NAME does not yet contain VARNAME, then append it (delimited\n# by SEPARATOR if supplied) and expand UNIQ, else NOT-UNIQ.\nm4_define([lt_if_append_uniq],\n[m4_ifdef([$1],\n\t  [m4_if(m4_index([$3]m4_defn([$1])[$3], [$3$2$3]), [-1],\n\t\t [lt_append([$1], [$2], [$3])$4],\n\t\t [$5])],\n\t  [lt_append([$1], [$2], [$3])$4])])\n\n\n# lt_dict_add(DICT, KEY, VALUE)\n# -----------------------------\nm4_define([lt_dict_add],\n[m4_define([$1($2)], [$3])])\n\n\n# lt_dict_add_subkey(DICT, KEY, SUBKEY, VALUE)\n# --------------------------------------------\nm4_define([lt_dict_add_subkey],\n[m4_define([$1($2:$3)], [$4])])\n\n\n# lt_dict_fetch(DICT, KEY, [SUBKEY])\n# ----------------------------------\nm4_define([lt_dict_fetch],\n[m4_ifval([$3],\n\tm4_ifdef([$1($2:$3)], [m4_defn([$1($2:$3)])]),\n    m4_ifdef([$1($2)], [m4_defn([$1($2)])]))])\n\n\n# lt_if_dict_fetch(DICT, KEY, [SUBKEY], VALUE, IF-TRUE, [IF-FALSE])\n# -----------------------------------------------------------------\nm4_define([lt_if_dict_fetch],\n[m4_if(lt_dict_fetch([$1], [$2], [$3]), [$4],\n\t[$5],\n    [$6])])\n\n\n# lt_dict_filter(DICT, [SUBKEY], VALUE, [SEPARATOR], KEY, [...])\n# --------------------------------------------------------------\nm4_define([lt_dict_filter],\n[m4_if([$5], [], [],\n  [lt_join(m4_quote(m4_default([$4], [[, ]])),\n           lt_unquote(m4_split(m4_normalize(m4_foreach(_Lt_key, lt_car([m4_shiftn(4, $@)]),\n\t\t      [lt_if_dict_fetch([$1], _Lt_key, [$2], [$3], [_Lt_key ])])))))])[]dnl\n])\n"
  },
  {
    "path": "cudd/m4/ltversion.m4",
    "content": "# ltversion.m4 -- version numbers\t\t\t-*- Autoconf -*-\n#\n#   Copyright (C) 2004, 2011-2019, 2021-2022 Free Software Foundation,\n#   Inc.\n#   Written by Scott James Remnant, 2004\n#\n# This file is free software; the Free Software Foundation gives\n# unlimited permission to copy and/or distribute it, with or without\n# modifications, as long as this notice is preserved.\n\n# @configure_input@\n\n# serial 4245 ltversion.m4\n# This file is part of GNU Libtool\n\nm4_define([LT_PACKAGE_VERSION], [2.4.7])\nm4_define([LT_PACKAGE_REVISION], [2.4.7])\n\nAC_DEFUN([LTVERSION_VERSION],\n[macro_version='2.4.7'\nmacro_revision='2.4.7'\n_LT_DECL(, macro_version, 0, [Which release of libtool.m4 was used?])\n_LT_DECL(, macro_revision, 0)\n])\n"
  },
  {
    "path": "cudd/m4/lt~obsolete.m4",
    "content": "# lt~obsolete.m4 -- aclocal satisfying obsolete definitions.    -*-Autoconf-*-\n#\n#   Copyright (C) 2004, 2005, 2007, 2009 Free Software Foundation, Inc.\n#   Written by Scott James Remnant, 2004.\n#\n# This file is free software; the Free Software Foundation gives\n# unlimited permission to copy and/or distribute it, with or without\n# modifications, as long as this notice is preserved.\n\n# serial 5 lt~obsolete.m4\n\n# These exist entirely to fool aclocal when bootstrapping libtool.\n#\n# In the past libtool.m4 has provided macros via AC_DEFUN (or AU_DEFUN)\n# which have later been changed to m4_define as they aren't part of the\n# exported API, or moved to Autoconf or Automake where they belong.\n#\n# The trouble is, aclocal is a bit thick.  It'll see the old AC_DEFUN\n# in /usr/share/aclocal/libtool.m4 and remember it, then when it sees us\n# using a macro with the same name in our local m4/libtool.m4 it'll\n# pull the old libtool.m4 in (it doesn't see our shiny new m4_define\n# and doesn't know about Autoconf macros at all.)\n#\n# So we provide this file, which has a silly filename so it's always\n# included after everything else.  This provides aclocal with the\n# AC_DEFUNs it wants, but when m4 processes it, it doesn't do anything\n# because those macros already exist, or will be overwritten later.\n# We use AC_DEFUN over AU_DEFUN for compatibility with aclocal-1.6. \n#\n# Anytime we withdraw an AC_DEFUN or AU_DEFUN, remember to add it here.\n# Yes, that means every name once taken will need to remain here until\n# we give up compatibility with versions before 1.7, at which point\n# we need to keep only those names which we still refer to.\n\n# This is to help aclocal find these macros, as it can't see m4_define.\nAC_DEFUN([LTOBSOLETE_VERSION], [m4_if([1])])\n\nm4_ifndef([AC_LIBTOOL_LINKER_OPTION],\t[AC_DEFUN([AC_LIBTOOL_LINKER_OPTION])])\nm4_ifndef([AC_PROG_EGREP],\t\t[AC_DEFUN([AC_PROG_EGREP])])\nm4_ifndef([_LT_AC_PROG_ECHO_BACKSLASH],\t[AC_DEFUN([_LT_AC_PROG_ECHO_BACKSLASH])])\nm4_ifndef([_LT_AC_SHELL_INIT],\t\t[AC_DEFUN([_LT_AC_SHELL_INIT])])\nm4_ifndef([_LT_AC_SYS_LIBPATH_AIX],\t[AC_DEFUN([_LT_AC_SYS_LIBPATH_AIX])])\nm4_ifndef([_LT_PROG_LTMAIN],\t\t[AC_DEFUN([_LT_PROG_LTMAIN])])\nm4_ifndef([_LT_AC_TAGVAR],\t\t[AC_DEFUN([_LT_AC_TAGVAR])])\nm4_ifndef([AC_LTDL_ENABLE_INSTALL],\t[AC_DEFUN([AC_LTDL_ENABLE_INSTALL])])\nm4_ifndef([AC_LTDL_PREOPEN],\t\t[AC_DEFUN([AC_LTDL_PREOPEN])])\nm4_ifndef([_LT_AC_SYS_COMPILER],\t[AC_DEFUN([_LT_AC_SYS_COMPILER])])\nm4_ifndef([_LT_AC_LOCK],\t\t[AC_DEFUN([_LT_AC_LOCK])])\nm4_ifndef([AC_LIBTOOL_SYS_OLD_ARCHIVE],\t[AC_DEFUN([AC_LIBTOOL_SYS_OLD_ARCHIVE])])\nm4_ifndef([_LT_AC_TRY_DLOPEN_SELF],\t[AC_DEFUN([_LT_AC_TRY_DLOPEN_SELF])])\nm4_ifndef([AC_LIBTOOL_PROG_CC_C_O],\t[AC_DEFUN([AC_LIBTOOL_PROG_CC_C_O])])\nm4_ifndef([AC_LIBTOOL_SYS_HARD_LINK_LOCKS], [AC_DEFUN([AC_LIBTOOL_SYS_HARD_LINK_LOCKS])])\nm4_ifndef([AC_LIBTOOL_OBJDIR],\t\t[AC_DEFUN([AC_LIBTOOL_OBJDIR])])\nm4_ifndef([AC_LTDL_OBJDIR],\t\t[AC_DEFUN([AC_LTDL_OBJDIR])])\nm4_ifndef([AC_LIBTOOL_PROG_LD_HARDCODE_LIBPATH], [AC_DEFUN([AC_LIBTOOL_PROG_LD_HARDCODE_LIBPATH])])\nm4_ifndef([AC_LIBTOOL_SYS_LIB_STRIP],\t[AC_DEFUN([AC_LIBTOOL_SYS_LIB_STRIP])])\nm4_ifndef([AC_PATH_MAGIC],\t\t[AC_DEFUN([AC_PATH_MAGIC])])\nm4_ifndef([AC_PROG_LD_GNU],\t\t[AC_DEFUN([AC_PROG_LD_GNU])])\nm4_ifndef([AC_PROG_LD_RELOAD_FLAG],\t[AC_DEFUN([AC_PROG_LD_RELOAD_FLAG])])\nm4_ifndef([AC_DEPLIBS_CHECK_METHOD],\t[AC_DEFUN([AC_DEPLIBS_CHECK_METHOD])])\nm4_ifndef([AC_LIBTOOL_PROG_COMPILER_NO_RTTI], [AC_DEFUN([AC_LIBTOOL_PROG_COMPILER_NO_RTTI])])\nm4_ifndef([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE], [AC_DEFUN([AC_LIBTOOL_SYS_GLOBAL_SYMBOL_PIPE])])\nm4_ifndef([AC_LIBTOOL_PROG_COMPILER_PIC], [AC_DEFUN([AC_LIBTOOL_PROG_COMPILER_PIC])])\nm4_ifndef([AC_LIBTOOL_PROG_LD_SHLIBS],\t[AC_DEFUN([AC_LIBTOOL_PROG_LD_SHLIBS])])\nm4_ifndef([AC_LIBTOOL_POSTDEP_PREDEP],\t[AC_DEFUN([AC_LIBTOOL_POSTDEP_PREDEP])])\nm4_ifndef([LT_AC_PROG_EGREP],\t\t[AC_DEFUN([LT_AC_PROG_EGREP])])\nm4_ifndef([LT_AC_PROG_SED],\t\t[AC_DEFUN([LT_AC_PROG_SED])])\nm4_ifndef([_LT_CC_BASENAME],\t\t[AC_DEFUN([_LT_CC_BASENAME])])\nm4_ifndef([_LT_COMPILER_BOILERPLATE],\t[AC_DEFUN([_LT_COMPILER_BOILERPLATE])])\nm4_ifndef([_LT_LINKER_BOILERPLATE],\t[AC_DEFUN([_LT_LINKER_BOILERPLATE])])\nm4_ifndef([_AC_PROG_LIBTOOL],\t\t[AC_DEFUN([_AC_PROG_LIBTOOL])])\nm4_ifndef([AC_LIBTOOL_SETUP],\t\t[AC_DEFUN([AC_LIBTOOL_SETUP])])\nm4_ifndef([_LT_AC_CHECK_DLFCN],\t\t[AC_DEFUN([_LT_AC_CHECK_DLFCN])])\nm4_ifndef([AC_LIBTOOL_SYS_DYNAMIC_LINKER],\t[AC_DEFUN([AC_LIBTOOL_SYS_DYNAMIC_LINKER])])\nm4_ifndef([_LT_AC_TAGCONFIG],\t\t[AC_DEFUN([_LT_AC_TAGCONFIG])])\nm4_ifndef([AC_DISABLE_FAST_INSTALL],\t[AC_DEFUN([AC_DISABLE_FAST_INSTALL])])\nm4_ifndef([_LT_AC_LANG_CXX],\t\t[AC_DEFUN([_LT_AC_LANG_CXX])])\nm4_ifndef([_LT_AC_LANG_F77],\t\t[AC_DEFUN([_LT_AC_LANG_F77])])\nm4_ifndef([_LT_AC_LANG_GCJ],\t\t[AC_DEFUN([_LT_AC_LANG_GCJ])])\nm4_ifndef([AC_LIBTOOL_LANG_C_CONFIG],\t[AC_DEFUN([AC_LIBTOOL_LANG_C_CONFIG])])\nm4_ifndef([_LT_AC_LANG_C_CONFIG],\t[AC_DEFUN([_LT_AC_LANG_C_CONFIG])])\nm4_ifndef([AC_LIBTOOL_LANG_CXX_CONFIG],\t[AC_DEFUN([AC_LIBTOOL_LANG_CXX_CONFIG])])\nm4_ifndef([_LT_AC_LANG_CXX_CONFIG],\t[AC_DEFUN([_LT_AC_LANG_CXX_CONFIG])])\nm4_ifndef([AC_LIBTOOL_LANG_F77_CONFIG],\t[AC_DEFUN([AC_LIBTOOL_LANG_F77_CONFIG])])\nm4_ifndef([_LT_AC_LANG_F77_CONFIG],\t[AC_DEFUN([_LT_AC_LANG_F77_CONFIG])])\nm4_ifndef([AC_LIBTOOL_LANG_GCJ_CONFIG],\t[AC_DEFUN([AC_LIBTOOL_LANG_GCJ_CONFIG])])\nm4_ifndef([_LT_AC_LANG_GCJ_CONFIG],\t[AC_DEFUN([_LT_AC_LANG_GCJ_CONFIG])])\nm4_ifndef([AC_LIBTOOL_LANG_RC_CONFIG],\t[AC_DEFUN([AC_LIBTOOL_LANG_RC_CONFIG])])\nm4_ifndef([_LT_AC_LANG_RC_CONFIG],\t[AC_DEFUN([_LT_AC_LANG_RC_CONFIG])])\nm4_ifndef([AC_LIBTOOL_CONFIG],\t\t[AC_DEFUN([AC_LIBTOOL_CONFIG])])\nm4_ifndef([_LT_AC_FILE_LTDLL_C],\t[AC_DEFUN([_LT_AC_FILE_LTDLL_C])])\nm4_ifndef([_LT_REQUIRED_DARWIN_CHECKS],\t[AC_DEFUN([_LT_REQUIRED_DARWIN_CHECKS])])\nm4_ifndef([_LT_AC_PROG_CXXCPP],\t\t[AC_DEFUN([_LT_AC_PROG_CXXCPP])])\nm4_ifndef([_LT_PREPARE_SED_QUOTE_VARS],\t[AC_DEFUN([_LT_PREPARE_SED_QUOTE_VARS])])\nm4_ifndef([_LT_PROG_ECHO_BACKSLASH],\t[AC_DEFUN([_LT_PROG_ECHO_BACKSLASH])])\nm4_ifndef([_LT_PROG_F77],\t\t[AC_DEFUN([_LT_PROG_F77])])\nm4_ifndef([_LT_PROG_FC],\t\t[AC_DEFUN([_LT_PROG_FC])])\nm4_ifndef([_LT_PROG_CXX],\t\t[AC_DEFUN([_LT_PROG_CXX])])\n"
  },
  {
    "path": "cudd/m4/modern_cxx.m4",
    "content": "# MODERN_CXX\n# ----------\n# Check whether the C++ compiler supports enough of C++11.\nAC_DEFUN([MODERN_CXX],\n[AC_CACHE_CHECK([whether enough of C++11 is supported],\n[ac_cv_have_modern_cxx],\n[AC_LANG_PUSH([C++])\n AC_COMPILE_IFELSE([AC_LANG_SOURCE([[\nclass Myclass { explicit operator bool() const { return true; } };\nint main() {\n  void *p = nullptr;\n}]])], [ac_cv_have_modern_cxx=yes], [ac_cv_have_modern_cxx=no])\n AC_LANG_POP([C++])])dnl\n])# MODERN_CXX\n\n"
  },
  {
    "path": "cudd/m4/w32.m4",
    "content": "# MINGW_AC_WIN32_NATIVE_HOST\n# --------------------------\n# Check whether the runtime platform is a native Win32 host.\n#\nAC_DEFUN([MINGW_AC_WIN32_NATIVE_HOST],\n[AC_CACHE_CHECK([whether we are building for a Win32 host],\n[mingw_cv_win32_host],\n AC_COMPILE_IFELSE([AC_LANG_SOURCE([[\n#ifdef _WIN32\n choke me\n#endif]])], [mingw_cv_win32_host=no], [mingw_cv_win32_host=yes]))dnl\n])# MINGW_AC_WIN32_NATIVE_HOST\n"
  },
  {
    "path": "cudd/mtr/Included.am",
    "content": "cudd_libcudd_la_SOURCES += mtr/mtr.h mtr/mtrInt.h mtr/mtrBasic.c mtr/mtrGroup.c\n\ncheck_PROGRAMS += mtr/testmtr\nmtr_testmtr_SOURCES = mtr/testmtr.c\nmtr_testmtr_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\nmtr_testmtr_LDADD = cudd/libcudd.la\n\ncheck_SCRIPTS += mtr/test_mtr.test\ndist_check_DATA += mtr/test.groups mtr/test.out\nEXTRA_DIST += mtr/test_mtr.test.in\nif !CROSS_COMPILING\nTESTS += mtr/test_mtr.test\nendif !CROSS_COMPILING\n\nmtr/test_mtr.test: mtr/test_mtr.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\nCLEANFILES += mtr/test.tst\n"
  },
  {
    "path": "cudd/mtr/mtr.h",
    "content": "/**\n  @file \n\n  @ingroup mtr\n\n  @brief Multiway-branch tree manipulation\n\n  @details This package provides two layers of functions. Functions\n  of the lower level manipulate multiway-branch trees, implemented\n  according to the classical scheme whereby each node points to its\n  first child and its previous and next siblings. These functions are\n  collected in mtrBasic.c.<p>\n  Functions of the upper layer deal with group trees, that is the trees\n  used by group sifting to represent the grouping of variables. These\n  functions are collected in mtrGroup.c.\n\n  @see The CUDD package documentation; specifically on group\n  sifting.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef MTR_H_\n#define MTR_H_\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n\n#include <stdio.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* Flag definitions */\n#define MTR_DEFAULT\t0x00000000\n#define MTR_TERMINAL\t0x00000001\n#define MTR_SOFT\t0x00000002\n#define MTR_FIXED\t0x00000004\n#define MTR_NEWNODE\t0x00000008\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief multi-way tree node.\n */\ntypedef struct MtrNode_ MtrNode;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\nMtrNode * Mtr_AllocNode(void);\nvoid Mtr_DeallocNode(MtrNode *node);\nMtrNode * Mtr_InitTree(void);\nvoid Mtr_FreeTree(MtrNode *node);\nMtrNode * Mtr_CopyTree(MtrNode const *node, int expansion);\nvoid Mtr_MakeFirstChild(MtrNode *parent, MtrNode *child);\nvoid Mtr_MakeLastChild(MtrNode *parent, MtrNode *child);\nMtrNode * Mtr_CreateFirstChild(MtrNode *parent);\nMtrNode * Mtr_CreateLastChild(MtrNode *parent);\nvoid Mtr_MakeNextSibling(MtrNode *first, MtrNode *second);\nvoid Mtr_PrintTree(MtrNode const *node);\nMtrNode * Mtr_InitGroupTree(int lower, int size);\nMtrNode * Mtr_MakeGroup(MtrNode *root, unsigned int low, unsigned int high, unsigned int flags);\nMtrNode * Mtr_DissolveGroup(MtrNode *group);\nMtrNode * Mtr_FindGroup(MtrNode *root, unsigned int low, unsigned int high);\nint Mtr_SwapGroups(MtrNode *first, MtrNode *second);\nvoid Mtr_ReorderGroups(MtrNode *treenode, int *permutation);\nvoid Mtr_PrintGroups(MtrNode const *root, int silent);\nint Mtr_PrintGroupedOrder(MtrNode const * root, int const *invperm, FILE *fp);\nMtrNode * Mtr_ReadGroups(FILE *fp, int nleaves);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* MTR_H_ */\n"
  },
  {
    "path": "cudd/mtr/mtrBasic.c",
    "content": "/**\n  @file\n\n  @ingroup mtr\n\n  @brief Basic manipulation of multiway branching trees.\n\n  @see cudd package\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Allocates new tree node.\n\n  @return pointer to node.\n\n  @sideeffect None\n\n  @see Mtr_DeallocNode\n\n*/\nMtrNode *\nMtr_AllocNode(void)\n{\n    MtrNode *node;\n\n    node = ALLOC(MtrNode,1);\n    node->flags = node->low = node->size = node->index = 0;\n    return node;\n\n} /* Mtr_AllocNode */\n\n\n/**\n  @brief Deallocates tree node.\n\n  @sideeffect None\n\n  @see Mtr_AllocNode\n\n*/\nvoid\nMtr_DeallocNode(\n  MtrNode * node /**< node to be deallocated */)\n{\n    FREE(node);\n    return;\n\n} /* end of Mtr_DeallocNode */\n\n\n/**\n  @brief Initializes tree with one node.\n\n  @return pointer to node.\n\n  @sideeffect None\n\n  @see Mtr_FreeTree Mtr_InitGroupTree\n\n*/\nMtrNode *\nMtr_InitTree(void)\n{\n    MtrNode *node;\n\n    node = Mtr_AllocNode();\n    if (node == NULL) return(NULL);\n\n    node->parent = node->child = node->elder = node->younger = NULL;\n\n    return(node);\n\n} /* end of Mtr_InitTree */\n\n\n/**\n  @brief Disposes of tree rooted at node.\n\n  @sideeffect None\n\n  @see Mtr_InitTree\n\n*/\nvoid\nMtr_FreeTree(\n  MtrNode * node)\n{\n    if (node == NULL) return;\n    if (! MTR_TEST(node,MTR_TERMINAL)) Mtr_FreeTree(node->child);\n    Mtr_FreeTree(node->younger);\n    Mtr_DeallocNode(node);\n    return;\n\n} /* end of Mtr_FreeTree */\n\n\n/**\n  @brief Makes a copy of tree.\n\n  @details If parameter expansion is greater than 1, it will expand\n  the tree by that factor. It is an error for expansion to be less\n  than 1.\n\n  @return a pointer to the copy if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Mtr_InitTree\n\n*/\nMtrNode *\nMtr_CopyTree(\n  MtrNode const * node,\n  int  expansion)\n{\n    MtrNode *copy;\n\n    if (node == NULL) return(NULL);\n    if (expansion < 1) return(NULL);\n    copy = Mtr_AllocNode();\n    if (copy == NULL) return(NULL);\n    copy->parent = copy->elder = copy->child = copy->younger = NULL;\n    if (node->child != NULL) {\n\tcopy->child = Mtr_CopyTree(node->child, expansion);\n\tif (copy->child == NULL) {\n\t    Mtr_DeallocNode(copy);\n\t    return(NULL);\n\t}\n    }\n    if (node->younger != NULL) {\n\tcopy->younger = Mtr_CopyTree(node->younger, expansion);\n\tif (copy->younger == NULL) {\n\t    Mtr_FreeTree(copy);\n\t    return(NULL);\n\t}\n    }\n    copy->flags = node->flags;\n    copy->low = node->low * expansion;\n    copy->size = node->size * expansion;\n    copy->index = node->index * expansion;\n    if (copy->younger) copy->younger->elder = copy;\n    if (copy->child) {\n\tMtrNode *auxnode = copy->child;\n\twhile (auxnode != NULL) {\n\t    auxnode->parent = copy;\n\t    auxnode = auxnode->younger;\n\t}\n    }\n    return(copy);\n\n} /* end of Mtr_CopyTree */\n\n\n/**\n  @brief Makes child the first child of parent.\n\n  @sideeffect None\n\n  @see Mtr_MakeLastChild Mtr_CreateFirstChild\n\n*/\nvoid\nMtr_MakeFirstChild(\n  MtrNode * parent,\n  MtrNode * child)\n{\n    child->parent = parent;\n    child->younger = parent->child;\n    child->elder = NULL;\n    if (parent->child != NULL) {\n#ifdef MTR_DEBUG\n\tassert(parent->child->elder == NULL);\n#endif\n\tparent->child->elder = child;\n    }\n    parent->child = child;\n    return;\n\n} /* end of Mtr_MakeFirstChild */\n\n\n/**\n  @brief Makes child the last child of parent.\n\n  @sideeffect None\n\n  @see Mtr_MakeFirstChild Mtr_CreateLastChild\n\n*/\nvoid\nMtr_MakeLastChild(\n  MtrNode * parent,\n  MtrNode * child)\n{\n    MtrNode *node;\n\n    child->younger = NULL;\n\n    if (parent->child == NULL) {\n\tparent->child = child;\n\tchild->elder = NULL;\n    } else {\n\tfor (node = parent->child;\n\t     node->younger != NULL;\n\t     node = node->younger);\n\tnode->younger = child;\n\tchild->elder = node;\n    }\n    child->parent = parent;\n    return;\n\n} /* end of Mtr_MakeLastChild */\n\n\n/**\n  @brief Creates a new node and makes it the first child of parent.\n\n  @return pointer to new child.\n\n  @sideeffect None\n\n  @see Mtr_MakeFirstChild Mtr_CreateLastChild\n\n*/\nMtrNode *\nMtr_CreateFirstChild(\n  MtrNode * parent)\n{\n    MtrNode *child;\n\n    child = Mtr_AllocNode();\n    if (child == NULL) return(NULL);\n\n    child->child = NULL;\n    Mtr_MakeFirstChild(parent,child);\n    return(child);\n\n} /* end of Mtr_CreateFirstChild */\n\n\n/**\n  @brief Creates a new node and makes it the last child of parent.\n\n  @return pointer to new child.\n\n  @sideeffect None\n\n  @see Mtr_MakeLastChild Mtr_CreateFirstChild\n\n*/\nMtrNode *\nMtr_CreateLastChild(\n  MtrNode * parent)\n{\n    MtrNode *child;\n\n    child = Mtr_AllocNode();\n    if (child == NULL) return(NULL);\n\n    child->child = NULL;\n    Mtr_MakeLastChild(parent,child);\n    return(child);\n\n} /* end of Mtr_CreateLastChild */\n\n\n/**\n  @brief Makes second the next sibling of first.\n\n  @details Second becomes a child of the parent of first.\n\n  @sideeffect None\n\n*/\nvoid\nMtr_MakeNextSibling(\n  MtrNode * first,\n  MtrNode * second)\n{\n    second->parent = first->parent;\n    second->elder = first;\n    second->younger = first->younger;\n    if (first->younger != NULL) {\n\tfirst->younger->elder = second;\n    }\n    first->younger = second;\n    return;\n\n} /* end of Mtr_MakeNextSibling */\n\n\n/**\n  @brief Prints a tree, one node per line.\n\n  @sideeffect None\n\n  @see Mtr_PrintGroups\n\n*/\nvoid\nMtr_PrintTree(\n  MtrNode const * node)\n{\n    if (node == NULL) return;\n    (void) fprintf(stdout,\n        \"N=0x%-8\" PRIxPTR \" C=0x%-8\" PRIxPTR \" Y=0x%-8\" PRIxPTR\n        \" E=0x%-8\" PRIxPTR \" P=0x%-8\" PRIxPTR \" F=%x L=%u S=%u\\n\",\n        (uintptr_t) node, (uintptr_t) node->child,\n        (uintptr_t) node->younger, (uintptr_t) node->elder,\n        (uintptr_t) node->parent, node->flags, node->low, node->size);\n    if (!MTR_TEST(node,MTR_TERMINAL)) Mtr_PrintTree(node->child);\n    Mtr_PrintTree(node->younger);\n    return;\n\n} /* end of Mtr_PrintTree */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n"
  },
  {
    "path": "cudd/mtr/mtrGroup.c",
    "content": "/**\n  @file\n\n  @ingroup mtr\n\n  @brief Functions to support group specification for reordering.\n\n  @see cudd package\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int mtrShiftHL (MtrNode *node, int shift);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Allocate new tree.\n\n  @details Allocate new tree with one node, whose low and size\n  fields are specified by the lower and size parameters.\n\n  @return pointer to tree root.\n\n  @sideeffect None\n\n  @see Mtr_InitTree Mtr_FreeTree\n\n*/\nMtrNode *\nMtr_InitGroupTree(\n  int  lower,\n  int  size)\n{\n    MtrNode *root;\n\n    root = Mtr_InitTree();\n    if (root == NULL) return(NULL);\n    root->flags = MTR_DEFAULT;\n    root->low = lower;\n    root->size = size;\n    return(root);\n\n} /* end of Mtr_InitGroupTree */\n\n\n/**\n  @brief Makes a new group with size leaves starting at low.\n\n  @details If the new group intersects an existing group, it must\n  either contain it or be contained by it.  This procedure relies on\n  the low and size fields of each node. It also assumes that the\n  children of each node are sorted in order of increasing low.  In\n  case of a valid request, the flags of the new group are set to the\n  value passed in `flags.'\n\n  @return the pointer to the root of the new group upon successful\n  termination; NULL otherwise. If the group already exists, the\n  pointer to its root is returned.\n\n  @sideeffect None\n\n  @see Mtr_DissolveGroup Mtr_ReadGroups Mtr_FindGroup\n\n*/\nMtrNode *\nMtr_MakeGroup(\n  MtrNode * root /**< root of the group tree */,\n  unsigned int  low /**< lower bound of the group */,\n  unsigned int  size /**< size of the group */,\n  unsigned int  flags /**< flags for the new group */)\n{\n    MtrNode *node,\n\t    *first,\n\t    *last,\n\t    *previous,\n\t    *newn;\n\n    /* Sanity check. */\n    if (size == 0)\n\treturn(NULL);\n\n    /* Check whether current group includes new group.  This check is\n    ** necessary at the top-level call.  In the subsequent calls it is\n    ** redundant. */\n    if (low < (unsigned int) root->low ||\n\tlow + size > (unsigned int) (root->low + root->size))\n\treturn(NULL);\n\n    /* At this point we know that the new group is contained\n    ** in the group of root. We have two possible cases here:\n    **  - root is a terminal node;\n    **  - root has children.       */\n\n    /* Root has no children: create a new group. */\n    if (root->child == NULL) {\n\tnewn = Mtr_AllocNode();\n\tif (newn == NULL) return(NULL);\t/* out of memory */\n\tnewn->low = low;\n\tnewn->size = size;\n\tnewn->flags = flags;\n\tnewn->parent = root;\n\tnewn->elder = newn->younger = newn->child = NULL;\n\troot->child = newn;\n\treturn(newn);\n    }\n\n    /* Root has children: Find all children of root that are included\n    ** in the new group.  If the group of any child entirely contains\n    ** the new group, call Mtr_MakeGroup recursively. */\n    previous = NULL;\n    first = root->child; /* guaranteed to be non-NULL */\n    while (first != NULL && low >= (unsigned int) (first->low + first->size)) {\n\tprevious = first;\n\tfirst = first->younger;\n    }\n    if (first == NULL) {\n\t/* We have scanned the entire list and we need to append a new\n\t** child at the end of it.  Previous points to the last child\n\t** of root. */\n\tnewn = Mtr_AllocNode();\n\tif (newn == NULL) return(NULL);\t/* out of memory */\n\tnewn->low = low;\n\tnewn->size = size;\n\tnewn->flags = flags;\n\tnewn->parent = root;\n\tnewn->elder = previous;\n\tprevious->younger = newn;\n\tnewn->younger = newn->child = NULL;\n\treturn(newn);\n    }\n    /* Here first is non-NULL and low < first->low + first->size. */\n    if (low >= (unsigned int) first->low &&\n\tlow + size <= (unsigned int) (first->low + first->size)) {\n\t/* The new group is contained in the group of first. */\n\tnewn = Mtr_MakeGroup(first, low, size, flags);\n\treturn(newn);\n    } else if (low + size <= first->low) {\n\t/* The new group is entirely contained in the gap between\n\t** previous and first. */\n\tnewn = Mtr_AllocNode();\n\tif (newn == NULL) return(NULL);\t/* out of memory */\n\tnewn->low = low;\n\tnewn->size = size;\n\tnewn->flags = flags;\n\tnewn->child = NULL;\n\tnewn->parent = root;\n\tnewn->elder = previous;\n\tnewn->younger = first;\n\tfirst->elder = newn;\n\tif (previous != NULL) {\n\t    previous->younger = newn;\n\t} else {\n\t    root->child = newn;\n\t}\n\treturn(newn);\n    } else if (low < (unsigned int) first->low &&\n\t       low + size < (unsigned int) (first->low + first->size)) {\n\t/* Trying to cut an existing group: not allowed. */\n\treturn(NULL);\n    } else if (low > first->low) {\n\t/* The new group neither is contained in the group of first\n\t** (this was tested above) nor contains it. It is therefore\n\t** trying to cut an existing group: not allowed. */\n\treturn(NULL);\n    }\n\n    /* First holds the pointer to the first child contained in the new\n    ** group. Here low <= first->low and low + size >= first->low +\n    ** first->size.  One of the two inequalities is strict. */\n    last = first;\n    while (last->younger != NULL &&\n\t   (unsigned int) (last->younger->low + last->younger->size) <= low + size) {\n\tlast = last->younger;\n    }\n    if (last == NULL) {\n\t/* All the chilren of root from first onward become children\n\t** of the new group. */\n\tnewn = Mtr_AllocNode();\n\tif (newn == NULL) return(NULL);\t/* out of memory */\n\tnewn->low = low;\n\tnewn->size = size;\n\tnewn->flags = flags;\n\tnewn->child = first;\n\tnewn->parent = root;\n\tnewn->elder = previous;\n\tnewn->younger = NULL;\n\tfirst->elder = NULL;\n\tif (previous != NULL) {\n\t    previous->younger = newn;\n\t} else {\n\t    root->child = newn;\n\t}\n\tlast = first;\n\twhile (last != NULL) {\n\t    last->parent = newn;\n\t    last = last->younger;\n\t}\n\treturn(newn);\n    }\n\n    /* Here last != NULL and low + size <= last->low + last->size. */\n    if (low + size - 1 >= (unsigned int) last->low &&\n\tlow + size < (unsigned int) (last->low + last->size)) {\n\t/* Trying to cut an existing group: not allowed. */\n\treturn(NULL);\n    }\n\n    /* First and last point to the first and last of the children of\n    ** root that are included in the new group. Allocate a new node\n    ** and make all children of root between first and last chidren of\n    ** the new node.  Previous points to the child of root immediately\n    ** preceeding first. If it is NULL, then first is the first child\n    ** of root. */\n    newn = Mtr_AllocNode();\n    if (newn == NULL) return(NULL);\t/* out of memory */\n    newn->low = low;\n    newn->size = size;\n    newn->flags = flags;\n    newn->child = first;\n    newn->parent = root;\n    if (previous == NULL) {\n\troot->child = newn;\n    } else {\n\tprevious->younger = newn;\n    }\n    newn->elder = previous;\n    newn->younger = last->younger;\n    if (last->younger != NULL) {\n\tlast->younger->elder = newn;\n    }\n    last->younger = NULL;\n    first->elder = NULL;\n    for (node = first; node != NULL; node = node->younger) {\n\tnode->parent = newn;\n    }\n\n    return(newn);\n\n} /* end of Mtr_MakeGroup */\n\n\n/**\n  @brief Merges the children of `group' with the children of its\n  parent.\n\n  @details Disposes of the node pointed by group. If group is the root\n  of the group tree, this procedure leaves the tree unchanged.\n\n  @return the pointer to the parent of `group' upon successful\n  termination; NULL otherwise.\n\n  @sideeffect None\n\n  @see Mtr_MakeGroup\n\n*/\nMtrNode *\nMtr_DissolveGroup(\n  MtrNode * group /**< group to be dissolved */)\n{\n    MtrNode *parent;\n    MtrNode *last;\n\n    parent = group->parent;\n\n    if (parent == NULL) return(NULL);\n    if (MTR_TEST(group,MTR_TERMINAL) || group->child == NULL) return(NULL);\n\n    /* Make all children of group children of its parent, and make\n    ** last point to the last child of group. */\n    for (last = group->child; last->younger != NULL; last = last->younger) {\n\tlast->parent = parent;\n    }\n    last->parent = parent;\n\n    last->younger = group->younger;\n    if (group->younger != NULL) {\n\tgroup->younger->elder = last;\n    }\n\n    group->child->elder = group->elder;\n    if (group == parent->child) {\n\tparent->child = group->child;\n    } else {\n\tgroup->elder->younger = group->child;\n    }\n\n    Mtr_DeallocNode(group);\n    return(parent);\n\n} /* end of Mtr_DissolveGroup */\n\n\n/**\n  @brief Finds a group with size leaves starting at low, if it exists.\n\n  @details This procedure relies on the low and size fields of each\n  node. It also assumes that the children of each node are sorted in\n  order of increasing low.\n\n  @return the pointer to the root of the group upon successful\n  termination; NULL otherwise.\n\n  @sideeffect None\n\n*/\nMtrNode *\nMtr_FindGroup(\n  MtrNode * root /**< root of the group tree */,\n  unsigned int  low /**< lower bound of the group */,\n  unsigned int  size /**< upper bound of the group */)\n{\n    MtrNode *node;\n\n#ifdef MTR_DEBUG\n    /* We cannot have a non-empty proper subgroup of a singleton set. */\n    assert(!MTR_TEST(root,MTR_TERMINAL));\n#endif\n\n    /* Sanity check. */\n    if (size < 1) return(NULL);\n\n    /* Check whether current group includes the group sought.  This\n    ** check is necessary at the top-level call.  In the subsequent\n    ** calls it is redundant. */\n    if (low < (unsigned int) root->low ||\n\tlow + size > (unsigned int) (root->low + root->size))\n\treturn(NULL);\n\n    if (root->size == size && root->low == low)\n\treturn(root);\n\n    if (root->child == NULL)\n\treturn(NULL);\n\n    /* Find all chidren of root that are included in the new group. If\n    ** the group of any child entirely contains the new group, call\n    ** Mtr_MakeGroup recursively.  */\n    node = root->child;\n    while (low >= (unsigned int) (node->low + node->size)) {\n\tnode = node->younger;\n    }\n    if (low + size <= (unsigned int) (node->low + node->size)) {\n\t/* The group is contained in the group of node. */\n\tnode = Mtr_FindGroup(node, low, size);\n\treturn(node);\n    } else {\n\treturn(NULL);\n    }\n\n} /* end of Mtr_FindGroup */\n\n\n/**\n  @brief Swaps two children of a tree node.\n\n  @details Adjusts the high and low fields of the two nodes and their\n  descendants.  The two children must be adjacent. However, first may\n  be the younger sibling of second.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nMtr_SwapGroups(\n  MtrNode * first /**< first node to be swapped */,\n  MtrNode * second /**< second node to be swapped */)\n{\n    MtrNode *node;\n    MtrNode *parent;\n    int sizeFirst;\n    int sizeSecond;\n\n    if (second->younger == first) { /* make first first */\n\tnode = first;\n\tfirst = second;\n\tsecond = node;\n    } else if (first->younger != second) { /* non-adjacent */\n\treturn(0);\n    }\n\n    sizeFirst = first->size;\n    sizeSecond = second->size;\n\n    /* Swap the two nodes. */\n    parent = first->parent;\n    if (parent == NULL || second->parent != parent) return(0);\n    if (parent->child == first) {\n\tparent->child = second;\n    } else { /* first->elder != NULL */\n\tfirst->elder->younger = second;\n    }\n    if (second->younger != NULL) {\n\tsecond->younger->elder = first;\n    }\n    first->younger = second->younger;\n    second->elder = first->elder;\n    first->elder = second;\n    second->younger = first;\n\n    /* Adjust the high and low fields. */\n    if (!mtrShiftHL(first,sizeSecond)) return(0);\n    if (!mtrShiftHL(second,-sizeFirst)) return(0);\n\n    return(1);\n\n} /* end of Mtr_SwapGroups */\n\n\n/**\n  @brief Fix variable tree at the end of tree sifting.\n\n  @details Fix the levels in the variable tree sorting siblings\n  according to them.  It should be called on a non-NULL tree.  It then\n  maintains this invariant.  It applies insertion sorting to the list of\n  siblings  The order is determined by permutation, which is used to find\n  the new level of the node index.  Index must refer to the first variable\n  in the group.\n\n  @sideeffect The tree is modified.\n\n*/\nvoid\nMtr_ReorderGroups(\n  MtrNode *treenode,\n  int *permutation)\n{\n    MtrNode *auxnode;\n    /* Initialize sorted list to first element. */\n    MtrNode *sorted = treenode;\n    sorted->low = permutation[sorted->index];\n    if (sorted->child != NULL)\n      Mtr_ReorderGroups(sorted->child, permutation);\n\n    auxnode = treenode->younger;\n    while (auxnode != NULL) {\n        MtrNode *rightplace;\n        MtrNode *moving = auxnode;\n\tauxnode->low = permutation[auxnode->index];\n\tif (auxnode->child != NULL)\n          Mtr_ReorderGroups(auxnode->child, permutation);\n        rightplace = auxnode->elder;\n        /* Find insertion point. */\n        while (rightplace != NULL && auxnode->low < rightplace->low)\n            rightplace = rightplace->elder;\n        auxnode = auxnode->younger;\n        if (auxnode != NULL) {\n            auxnode->elder = moving->elder;\n            auxnode->elder->younger = auxnode;\n        } else {\n            moving->elder->younger = NULL;\n        }\n        if (rightplace == NULL) { /* Move to head of sorted list. */\n            sorted->elder = moving;\n            moving->elder = NULL;\n            moving->younger = sorted;\n            sorted = moving;\n        } else { /* Splice. */\n            moving->elder = rightplace;\n            moving->younger = rightplace->younger;\n            if (rightplace->younger != NULL)\n                rightplace->younger->elder = moving;\n            rightplace->younger = moving;\n        }\n    }\n    /* Fix parent. */\n    if (sorted->parent != NULL)\n        sorted->parent->child = sorted;\n\n} /* end of Mtr_ReorderGroups */\n\n\n/**\n  @brief Prints the groups as a parenthesized list.\n\n  @details After each group, the group's flag are printed, preceded by a `|'.\n  For each flag (except MTR_TERMINAL) a character is printed.\n  <ul>\n  <li>F: MTR_FIXED\n  <li>N: MTR_NEWNODE\n  <li>S: MTR_SOFT\n  </ul>\n  The second argument, silent, if different from 0, causes\n  Mtr_PrintGroups to only check the syntax of the group tree.\n\n  @sideeffect None\n\n  @see Mtr_PrintTree\n\n*/\nvoid\nMtr_PrintGroups(\n  MtrNode const * root /**< root of the group tree */,\n  int  silent /**< flag to check tree syntax only */)\n{\n    MtrNode *node;\n\n    assert(root != NULL);\n    assert(root->younger == NULL || root->younger->elder == root);\n    assert(root->elder == NULL || root->elder->younger == root);\n#if SIZEOF_VOID_P == 8\n    if (!silent) (void) printf(\"(%u\",root->low);\n#else\n    if (!silent) (void) printf(\"(%hu\",root->low);\n#endif\n    if (MTR_TEST(root,MTR_TERMINAL) || root->child == NULL) {\n\tif (!silent) (void) printf(\",\");\n    } else {\n\tnode = root->child;\n\twhile (node != NULL) {\n\t    assert(node->low >= root->low && (int) (node->low + node->size) <= (int) (root->low + root->size));\n\t    assert(node->parent == root);\n\t    Mtr_PrintGroups(node,silent);\n\t    node = node->younger;\n\t}\n    }\n    if (!silent) {\n#if SIZEOF_VOID_P == 8\n\t(void) printf(\"%u\", (MtrHalfWord) (root->low + root->size - 1));\n#else\n\t(void) printf(\"%hu\", (MtrHalfWord) (root->low + root->size - 1));\n#endif\n\tif (root->flags != MTR_DEFAULT) {\n\t    (void) printf(\"|\");\n\t    if (MTR_TEST(root,MTR_FIXED)) (void) printf(\"F\");\n\t    if (MTR_TEST(root,MTR_NEWNODE)) (void) printf(\"N\");\n\t    if (MTR_TEST(root,MTR_SOFT)) (void) printf(\"S\");\n\t}\n\t(void) printf(\")\");\n\tif (root->parent == NULL) (void) printf(\"\\n\");\n    }\n    assert((root->flags &~(MTR_TERMINAL | MTR_SOFT | MTR_FIXED | MTR_NEWNODE)) == 0);\n    return;\n\n} /* end of Mtr_PrintGroups */\n\n\n/**\n  @brief Prints the variable order as a parenthesized list.\n\n  @details After each group, the group's flag are printed, preceded by a `|'.\n  For each flag (except MTR_TERMINAL) a character is printed.\n  <ul>\n  <li>F: MTR_FIXED\n  <li>N: MTR_NEWNODE\n  <li>S: MTR_SOFT\n  </ul>\n  The second argument, gives the map from levels to variable indices.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Mtr_PrintGroups\n\n*/\nint\nMtr_PrintGroupedOrder(\n  MtrNode const * root /**< root of the group tree */,\n  int const *invperm /**< map from levels to indices */,\n  FILE *fp /**< output file */)\n{\n    MtrNode *child;\n    MtrHalfWord level;\n    int retval;\n\n    assert(root != NULL);\n    assert(root->younger == NULL || root->younger->elder == root);\n    assert(root->elder == NULL || root->elder->younger == root);\n    retval = fprintf(fp,\"(\");\n    if (retval == EOF) return(0);\n    level = root->low;\n    child = root->child;\n    while (child != NULL) {\n        assert(child->low >= root->low && (child->low + child->size) <= (root->low + root->size));\n        assert(child->parent == root);\n        while (level < child->low) {\n            retval = fprintf(fp,\"%d%s\", invperm[level], (level < root->low + root->size - 1) ? \",\" : \"\");\n            if (retval == EOF) return(0);\n            level++;\n        }\n        retval = Mtr_PrintGroupedOrder(child,invperm,fp);\n        if (retval == 0) return(0);\n        level += child->size;\n        if (level < root->low + root->size - 1) {\n            retval = fprintf(fp,\",\");\n            if (retval == EOF) return(0);\n        }\n        child = child->younger;\n    }\n    while (level < root->low + root->size) {\n        retval = fprintf(fp,\"%d%s\", invperm[level], (level < root->low + root->size - 1) ? \",\" : \"\");\n        if (retval == EOF) return(0);\n        level++;\n    }\n    if (root->flags != MTR_DEFAULT) {\n      retval = fprintf(fp,\"|\");\n      if (retval == EOF) return(0);\n      if (MTR_TEST(root,MTR_FIXED)) {\n          retval = fprintf(fp,\"F\");\n          if (retval == EOF) return(0);\n      }\n      if (MTR_TEST(root,MTR_NEWNODE)) {\n          retval = fprintf(fp,\"N\");\n          if (retval == EOF) return(0);\n      }\n      if (MTR_TEST(root,MTR_SOFT)) {\n          retval = fprintf(fp,\"S\");\n          if (retval == EOF) return(0);\n      }\n    }\n    retval = fprintf(fp,\")\");\n    if (retval == EOF) return(0);\n    if (root->parent == NULL) {\n        retval = fprintf(fp,\"\\n\");\n        if (retval == EOF) return(0);\n    }\n    assert((root->flags &~(MTR_SOFT | MTR_FIXED | MTR_NEWNODE)) == 0);\n    return(1);\n\n} /* end of Mtr_PrintGroupedOrder */\n\n\n/**\n  @brief Reads groups from a file and creates a group tree.\n\n  @details Each group is specified by three fields:\n\n       low size flags.\n\n  Low and size are (short) integers. Flags is a string composed of the\n  following characters (with associated translation):\n  <ul>\n  <li>D: MTR_DEFAULT\n  <li>F: MTR_FIXED\n  <li>N: MTR_NEWNODE\n  <li>S: MTR_SOFT\n  <li>T: MTR_TERMINAL\n  </ul>\n  Normally, the only flags that are needed are D and F.  Groups and\n  fields are separated by white space (spaces, tabs, and newlines).\n\n  @return a pointer to the group tree if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Mtr_InitGroupTree Mtr_MakeGroup\n\n*/\nMtrNode *\nMtr_ReadGroups(\n  FILE * fp /**< file pointer */,\n  int  nleaves /**< number of leaves of the new tree */)\n{\n    int low;\n    int size;\n    int err;\n    unsigned int flags;\n    MtrNode *root;\n    MtrNode *node;\n    char attrib[8*sizeof(unsigned int)+1];\n    char *c;\n\n    root = Mtr_InitGroupTree(0,nleaves);\n    if (root == NULL) return NULL;\n\n    while (! feof(fp)) {\n\t/* Read a triple and check for consistency. */\n\terr = fscanf(fp, \"%d %d %s\", &low, &size, attrib);\n\tif (err == EOF) {\n\t    break;\n\t} else if (err != 3) {\n\t    Mtr_FreeTree(root);\n\t    return(NULL);\n\t} else if (low < 0 || low+size > nleaves || size < 1) {\n\t    Mtr_FreeTree(root);\n\t    return(NULL);\n\t} else if (strlen(attrib) > 8 * sizeof(MtrHalfWord)) {\n\t    /* Not enough bits in the flags word to store these many\n\t    ** attributes. */\n\t    Mtr_FreeTree(root);\n\t    return(NULL);\n\t}\n\n\t/* Parse the flag string. Currently all flags are permitted,\n\t** to make debugging easier. Normally, specifying NEWNODE\n\t** wouldn't be allowed. */\n\tflags = MTR_DEFAULT;\n\tfor (c=attrib; *c != 0; c++) {\n\t    switch (*c) {\n\t    case 'D':\n\t\tbreak;\n\t    case 'F':\n\t\tflags |= MTR_FIXED;\n\t\tbreak;\n\t    case 'N':\n\t\tflags |= MTR_NEWNODE;\n\t\tbreak;\n\t    case 'S':\n\t\tflags |= MTR_SOFT;\n\t\tbreak;\n\t    case 'T':\n\t\tflags |= MTR_TERMINAL;\n\t\tbreak;\n\t    default:\n\t\treturn NULL;\n\t    }\n\t}\n\tnode = Mtr_MakeGroup(root, (MtrHalfWord) low, (MtrHalfWord) size,\n\t\t\t     flags);\n\tif (node == NULL) {\n\t    Mtr_FreeTree(root);\n\t    return(NULL);\n\t}\n    }\n\n    return(root);\n\n} /* end of Mtr_ReadGroups */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Adjusts the low fields of a node and its descendants.\n\n  @details Adds shift to low of each node. Checks that no\n  out-of-bounds values result.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nmtrShiftHL(\n  MtrNode * node /**< group tree node */,\n  int  shift /**< amount by which low should be changed */)\n{\n    MtrNode *auxnode;\n    int low;\n\n    low = (int) node->low;\n\n\n    low += shift;\n\n    if (low < 0 || low + (int) (node->size - 1) > (int) MTR_MAXHIGH) return(0);\n\n    node->low = (MtrHalfWord) low;\n\n    if (!MTR_TEST(node,MTR_TERMINAL) && node->child != NULL) {\n\tauxnode = node->child;\n\tdo {\n\t    if (!mtrShiftHL(auxnode,shift)) return(0);\n\t    auxnode = auxnode->younger;\n\t} while (auxnode != NULL);\n    }\n\n    return(1);\n\n} /* end of mtrShiftHL */\n"
  },
  {
    "path": "cudd/mtr/mtrInt.h",
    "content": "/**\n  @file \n\n  @ingroup mtr\n\n  @brief Internal data structures of the mtr package\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef MTRINT_H_\n#define MTRINT_H_\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n\n#include \"config.h\"\n#include \"mtr.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#ifndef SIZEOF_VOID_P\n#define SIZEOF_VOID_P 4\n#endif\n#ifndef SIZEOF_INT\n#define SIZEOF_INT 4\n#endif\n\n#if defined(__GNUC__)\n#define MTR_INLINE __inline__\n# if (__GNUC__ >2 || __GNUC_MINOR__ >=7)\n#   define MTR_UNUSED __attribute__ ((unused))\n# else\n#   define MTR_UNUSED\n# endif\n#else\n#define MTR_INLINE\n#define MTR_UNUSED\n#endif\n\n/* MTR_MAXHIGH is defined in such a way that on 32-bit and 64-bit\n** machines one can cast a value to (int) without generating a negative\n** number.\n*/\n#if SIZEOF_VOID_P == 8\n#define MTR_MAXHIGH\t(((MtrHalfWord) ~0) >> 1)\n#else\n#define MTR_MAXHIGH\t((MtrHalfWord) ~0)\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief unsigned integer half the size of a pointer.\n */\n#if SIZEOF_VOID_P == 8\ntypedef uint32_t   MtrHalfWord;\n#else\ntypedef uint16_t MtrHalfWord;\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief multi-way tree node.\n */\nstruct MtrNode_ {\n    MtrHalfWord flags;\n    MtrHalfWord low;\n    MtrHalfWord size;\n    MtrHalfWord index;\n    struct MtrNode_ *parent;\n    struct MtrNode_ *child;\n    struct MtrNode_ *elder;\n    struct MtrNode_ *younger;\n};\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/* Flag manipulation macros */\n#define MTR_SET(node, flag)\t(node->flags |= (flag))\n#define MTR_RESET(node, flag)\t(node->flags &= ~ (flag))\n#define MTR_TEST(node, flag)\t(node->flags & (flag))\n\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\n/** \\endcond */\n\n\n#endif /* MTRINT_H_ */\n"
  },
  {
    "path": "cudd/mtr/test.groups",
    "content": "0 6 D\n6 6 F\n0 2 D\n2 2 D\n4 2 D\n"
  },
  {
    "path": "cudd/mtr/test.out",
    "content": "# TestMtr Version #0.6, Release date 2/6/12\n# ./testmtr -p 2 test.groups\nN=0x187a010  C=0x187a0d0  Y=0x0        E=0x0        P=0x0        F=0 L=0 S=0\nN=0x187a0d0  C=0x0        Y=0x187a110  E=0x0        P=0x187a010  F=3 L=0 S=0\nN=0x187a110  C=0x0        Y=0x187a050  E=0x187a0d0  P=0x187a010  F=4 L=0 S=0\nN=0x187a050  C=0x0        Y=0x187a090  E=0x187a110  P=0x187a010  F=1 L=0 S=0\nN=0x187a090  C=0x0        Y=0x0        E=0x187a050  P=0x187a010  F=2 L=0 S=0\n#------------------------\nN=0x187a010  C=0x0        Y=0x0        E=0x0        P=0x0        F=0 L=0 S=12\n#  (0,11)\n\nN=0x187a010  C=0x187a0d0  Y=0x0        E=0x0        P=0x0        F=0 L=0 S=12\nN=0x187a0d0  C=0x0        Y=0x187a110  E=0x0        P=0x187a010  F=0 L=0 S=6\nN=0x187a110  C=0x0        Y=0x0        E=0x187a0d0  P=0x187a010  F=0 L=6 S=6\n#  (0(0,5)(6,11)11)\n\nN=0x187a010  C=0x187a190  Y=0x0        E=0x0        P=0x0        F=0 L=0 S=12\nN=0x187a190  C=0x187a0d0  Y=0x0        E=0x0        P=0x187a010  F=4 L=0 S=12\nN=0x187a0d0  C=0x187a050  Y=0x187a110  E=0x0        P=0x187a190  F=0 L=0 S=6\nN=0x187a050  C=0x0        Y=0x187a090  E=0x0        P=0x187a0d0  F=0 L=0 S=2\nN=0x187a090  C=0x0        Y=0x187a150  E=0x187a050  P=0x187a0d0  F=0 L=2 S=2\nN=0x187a150  C=0x0        Y=0x0        E=0x187a090  P=0x187a0d0  F=0 L=4 S=2\nN=0x187a110  C=0x0        Y=0x0        E=0x187a0d0  P=0x187a190  F=0 L=6 S=6\n#  (0(0(0(0,1)(2,3)(4,5)5)(6,11)11|F)11)\n\n#  (0(0(0,1)(2,3)(4,5)5)(6,11)11|F)\nN=0x187a010  C=0x187a190  Y=0x0        E=0x0        P=0x0        F=0 L=0 S=12\nN=0x187a190  C=0x187a050  Y=0x0        E=0x0        P=0x187a010  F=4 L=0 S=12\nN=0x187a050  C=0x0        Y=0x187a090  E=0x0        P=0x187a190  F=0 L=0 S=2\nN=0x187a090  C=0x0        Y=0x187a150  E=0x187a050  P=0x187a190  F=0 L=2 S=2\nN=0x187a150  C=0x0        Y=0x187a110  E=0x187a090  P=0x187a190  F=0 L=4 S=2\nN=0x187a110  C=0x0        Y=0x0        E=0x187a150  P=0x187a190  F=0 L=6 S=6\n#  (0(0(0,1)(2,3)(4,5)(6,11)11|F)11)\n\nN=0x187a010  C=0x187a190  Y=0x0        E=0x0        P=0x0        F=0 L=0 S=12\nN=0x187a190  C=0x187a050  Y=0x0        E=0x0        P=0x187a010  F=4 L=0 S=12\nN=0x187a050  C=0x0        Y=0x187a090  E=0x0        P=0x187a190  F=0 L=0 S=2\nN=0x187a090  C=0x0        Y=0x187a110  E=0x187a050  P=0x187a190  F=0 L=2 S=2\nN=0x187a110  C=0x0        Y=0x187a150  E=0x187a090  P=0x187a190  F=0 L=4 S=6\nN=0x187a150  C=0x0        Y=0x0        E=0x187a110  P=0x187a190  F=0 L=10 S=2\n#  (0(0(0,1)(2,3)(4,9)(10,11)11|F)11)\n#------------------------\nN=0x187a010  C=0x0        Y=0x0        E=0x0        P=0x0        F=0 L=0 S=4\n#  (0,3)\n\nN=0x187a010  C=0x187a190  Y=0x0        E=0x0        P=0x0        F=0 L=0 S=4\nN=0x187a190  C=0x0        Y=0x187a050  E=0x0        P=0x187a010  F=4 L=0 S=2\nN=0x187a050  C=0x0        Y=0x0        E=0x187a190  P=0x187a010  F=4 L=2 S=2\n#  (0(0,1|F)(2,3|F)3)\n\n#------------------------\nN=0x187a010  C=0x187a190  Y=0x0        E=0x0        P=0x0        F=0 L=0 S=12\nN=0x187a190  C=0x187a090  Y=0x187a050  E=0x0        P=0x187a010  F=0 L=0 S=6\nN=0x187a090  C=0x0        Y=0x187a110  E=0x0        P=0x187a190  F=0 L=0 S=2\nN=0x187a110  C=0x0        Y=0x187a150  E=0x187a090  P=0x187a190  F=0 L=2 S=2\nN=0x187a150  C=0x0        Y=0x0        E=0x187a110  P=0x187a190  F=0 L=4 S=2\nN=0x187a050  C=0x0        Y=0x0        E=0x187a190  P=0x187a010  F=4 L=6 S=6\n#  (0(0(0,1)(2,3)(4,5)5)(6,11|F)11)\n\n"
  },
  {
    "path": "cudd/mtr/test_mtr.test.in",
    "content": "#! /bin/sh\n\nEXE=@EXEEXT@\nsrcdir=@srcdir@\n\nfile=test\nverbosity=2\n\nsed_command='-r:-e:2d:-e:s/0x[0-9a-f][0-9a-f]*//g:-e:/modifiable/,$d'\n\necho TAP version 13\necho 1..1\n\nmtr/testmtr$EXE -p $verbosity ${srcdir}/mtr/${file}.groups > ./mtr/${file}.tst\nfailed=`expr $? != 0`\nif test x$failed = x0; then\n    echo \"# comparing ./mtr/${file}.tst to ${srcdir}/mtr/${file}.out\"\n    mkfifo ./mtr/tst_fifo ./mtr/out_fifo\n    OIFS=$IFS\n    IFS=:\n    `sed ${sed_command} ./mtr/${file}.tst > ./mtr/tst_fifo &\\\n     sed ${sed_command} ${srcdir}/mtr/${file}.out > ./mtr/out_fifo &\\\n     diff -b ./mtr/tst_fifo ./mtr/out_fifo > ./mtr/differences`\n    failed=`expr $? != 0`\n    rm ./mtr/tst_fifo ./mtr/out_fifo\n    IFS=$OIFS\nfi\nif test x$failed = x0; then\n    rm -rf ./mtr/differences\n    echo ok 1\nelse\n    echo not ok 1\n    echo '# Check file \"./mtr/differences\"'\nfi\n\nexit 0\n"
  },
  {
    "path": "cudd/mtr/testmtr.c",
    "content": "/**\n  @file\n\n  @ingroup mtr\n\n  @brief Test program for the mtr package.\n\n  @author Fabio Somenzi\n   \n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"mtrInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#ifndef lint\nstatic char rcsid[] MTR_UNUSED = \"$Id: testmtr.c,v 1.8 2015/07/01 20:43:45 fabio Exp $\";\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define TESTMTR_VERSION\\\n    \"TestMtr Version #0.6, Release date 2/6/12\"\n\n/** \\cond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void usage (char *prog);\nstatic FILE * open_file (const char *filename, const char *mode);\nstatic void printHeader(int argc, char **argv);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Main program for testmtr.\n\n  @details Performs initialization.  Reads command line options and\n  network(s).  Builds some simple trees and prints them out.\n\n  @sideeffect None\n\n*/\nint\nmain(\n  int  argc,\n  char ** argv)\n{\n    MtrNode *root,\n\t    *node;\n    int\t    i,\n\t    pr = 0;\n    FILE    *fp;\n    const char *file = NULL;\n\n    for (i = 1; i < argc; i++) {\n      if (strcmp(\"-M\", argv[i]) == 0) {\n        continue;\n      } else if (strcmp(\"-p\", argv[i]) == 0) {\n        pr = atoi(argv[++i]);\n      } else if (strcmp(\"-h\", argv[i]) == 0) {\n        printHeader(argc, argv);\n        usage(argv[0]);\n      } else if (i == argc - 1) {\n        file = argv[i];\n      } else {\n        printHeader(argc, argv);\n        usage(argv[0]);\n      }\n    }\n    if (file == NULL) {\n      file = \"-\";\n    }\n    if (pr > 0)\n        printHeader(argc, argv);\n\n    /* Create and print a simple tree. */\n    root = Mtr_InitTree();\n    root->flags = 0;\n    node = Mtr_CreateFirstChild(root);\n    node->flags = 1;\n    node = Mtr_CreateLastChild(root);\n    node->flags = 2;\n    node = Mtr_CreateFirstChild(root);\n    node->flags = 3;\n    node = Mtr_AllocNode();\n    node->child = NULL;\n    node->flags = 4;\n    Mtr_MakeNextSibling(root->child,node);\n    if (pr > 0) {\n        Mtr_PrintTree(root);\n        (void) printf(\"#------------------------\\n\");\n    }\n    Mtr_FreeTree(root);\n\n    /* Create an initial tree in which all variables belong to one group. */\n    root = Mtr_InitGroupTree(0,12);\n    if (pr > 0) {\n        Mtr_PrintTree(root); (void) printf(\"#  \");\n        Mtr_PrintGroups(root,pr == 0); (void) printf(\"\\n\");\n    }\n    (void) Mtr_MakeGroup(root,0,6,MTR_DEFAULT);\n    (void) Mtr_MakeGroup(root,6,6,MTR_DEFAULT);\n    if (pr > 0) {\n        Mtr_PrintTree(root); (void) printf(\"#  \");\n        Mtr_PrintGroups(root,pr == 0); (void) printf(\"\\n\");\n    }\n    for (i = 0; i < 6; i+=2) {\n      (void) Mtr_MakeGroup(root,(unsigned) i,(unsigned) 2,MTR_DEFAULT);\n    }\n    (void) Mtr_MakeGroup(root,0,12,MTR_FIXED);\n    if (pr > 0) {\n        Mtr_PrintTree(root); (void) printf(\"#  \");\n        Mtr_PrintGroups(root,pr == 0); (void) printf(\"\\n\");\n        /* Print a partial tree. */\n        (void) printf(\"#  \");\n        Mtr_PrintGroups(root->child,pr == 0); (void) printf(\"\\n\");\n    }\n    node = Mtr_FindGroup(root,0,6);\n    (void) Mtr_DissolveGroup(node);\n    if (pr > 0) {\n        Mtr_PrintTree(root); (void) printf(\"#  \");\n        Mtr_PrintGroups(root,pr == 0); (void) printf(\"\\n\");\n    }\n    node = Mtr_FindGroup(root,4,2);\n    if (!Mtr_SwapGroups(node,node->younger)) {\n\t(void) printf(\"error in Mtr_SwapGroups\\n\");\n\treturn 3;\n    }\n    if (pr > 0) {\n        Mtr_PrintTree(root); (void) printf(\"#  \");\n        Mtr_PrintGroups(root,pr == 0);\n        (void) printf(\"#------------------------\\n\");\n    }\n    Mtr_FreeTree(root);\n\n    /* Create a group tree with fixed subgroups. */\n    root = Mtr_InitGroupTree(0,4);\n    if (pr > 0) {\n        Mtr_PrintTree(root); (void) printf(\"#  \");\n        Mtr_PrintGroups(root,pr == 0); (void) printf(\"\\n\");\n    }\n    (void) Mtr_MakeGroup(root,0,2,MTR_FIXED);\n    (void) Mtr_MakeGroup(root,2,2,MTR_FIXED);\n    if (pr > 0) {\n        Mtr_PrintTree(root); (void) printf(\"#  \");\n        Mtr_PrintGroups(root,pr == 0); (void) printf(\"\\n\");\n    }\n    Mtr_FreeTree(root);\n    if (pr > 0) {\n        (void) printf(\"#------------------------\\n\");\n    }\n\n    /* Open input file. */\n    fp = open_file(file, \"r\");\n    root = Mtr_ReadGroups(fp,12);\n    fclose(fp);\n    if (pr > 0) {\n        if (root) {\n            Mtr_PrintTree(root); (void) printf(\"#  \");\n            Mtr_PrintGroups(root,pr == 0); (void) printf(\"\\n\");\n        } else {\n            (void) printf(\"error in group file\\n\");\n        }\n    }\n    Mtr_FreeTree(root);\n\n    return 0;\n\n} /* end of main */\n\n\n/**\n  @brief Prints usage message and exits.\n\n  @sideeffect none\n\n*/\nstatic void\nusage(\n  char * prog)\n{\n    (void) fprintf(stderr, \"usage: %s [options] [file]\\n\", prog);\n    (void) fprintf(stderr, \"   -M\\t\\tturns off memory allocation recording\\n\");\n    (void) fprintf(stderr, \"   -h\\t\\tprints this message\\n\");\n    (void) fprintf(stderr, \"   -p n\\t\\tcontrols verbosity\\n\");\n    exit(2);\n\n} /* end of usage */\n\n\n/**\n  @brief Opens a file.\n\n  @details Opens a file, or fails with an error message and exits.\n  Allows '-' as a synonym for standard input.\n\n  @sideeffect None\n\n*/\nstatic FILE *\nopen_file(\n  const char * filename,\n  const char * mode)\n{\n    FILE *fp;\n\n    if (strcmp(filename, \"-\") == 0) {\n        return mode[0] == 'r' ? stdin : stdout;\n    } else if ((fp = fopen(filename, mode)) == NULL) {\n        perror(filename);\n        exit(1);\n    }\n    return(fp);\n\n} /* end of open_file */\n\n\n/**\n  @brief Prints the header of the program output.\n\n  @sideeffect None\n\n*/\nstatic void\nprintHeader(\n  int argc,\n  char **argv)\n{\n    int i;\n\n    (void) printf(\"# %s\\n\", TESTMTR_VERSION);\n    /* Echo command line and arguments. */\n    (void) printf(\"#\");\n    for(i = 0; i < argc; i++) {\n\t(void) printf(\" %s\", argv[i]);\n    }\n    (void) printf(\"\\n\");\n    (void) fflush(stdout);\n}\n"
  },
  {
    "path": "cudd/nanotrav/C17.blif",
    "content": ".model C17.iscas\n.inputs 1GAT(0) 2GAT(1) 3GAT(2) 6GAT(3) 7GAT(4)\n.outputs 22GAT(10) 23GAT(9)\n.names 3GAT(2) 6GAT(3) 11GAT(5)\n11 0\n.names 1GAT(0) 3GAT(2) 10GAT(6)\n11 0\n.names 11GAT(5) 7GAT(4) 19GAT(7)\n11 0\n.names 2GAT(1) 11GAT(5) 16GAT(8)\n11 0\n.names 16GAT(8) 19GAT(7) 23GAT(9)\n11 0\n.names 10GAT(6) 16GAT(8) 22GAT(10)\n11 0\n.end\n"
  },
  {
    "path": "cudd/nanotrav/C17.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -cover ./nanotrav/C17.blif\n# CUDD Version 3.0.0\nOrder before final reordering\n1GAT(0) 2GAT(1) 3GAT(2) 6GAT(3) 7GAT(4) \n22GAT(10): 8 nodes 18 minterms\n23GAT(9): 8 nodes 18 minterms\n22GAT(10): 5 nodes 3 minterms\nTesting iterator on ZDD paths:\n-1-0- 1\n-10-- 1\n1-1-- 1\n\n1-1-- 1\n-10-- 1\n-1-0- 1\n23GAT(9): 6 nodes 4 minterms\nTesting iterator on ZDD paths:\n---01 1\n--0-1 1\n-1-0- 1\n-10-- 1\n\n-10-- 1\n-1-0- 1\n--0-1 1\n---01 1\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: yes\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 4004\n**** CUDD non-modifiable parameters ****\nMemory in use: 3182768\nPeak number of nodes: 1022\nPeak number of live nodes: 19\nNumber of BDD variables: 5\nNumber of ZDD variables: 10\nNumber of cache entries: 32768\nNumber of cache look-ups: 125\nNumber of cache hits: 21\nNumber of cache insertions: 117\nNumber of cache collisions: 0\nNumber of cache deletions: 35\nCache used slots = 0.33% (expected 0.25%)\nSoft limit for cache size: 16384\nNumber of buckets in unique table: 4096\nUsed buckets in unique table: 1.20% (expected 1.24%)\nNumber of BDD and ADD nodes: 24\nNumber of ZDD nodes: 27\nNumber of dead BDD and ADD nodes: 8\nNumber of dead ZDD nodes: 17\nTotal number of nodes allocated: 67\nTotal number of nodes reclaimed: 8\nGarbage collections so far: 1\nTime for garbage collection: 0.00 sec\nReorderings so far: 0\nTime for reordering: 0.00 sec\nFinal size: 11\ntotal time = 0.00 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  5968K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 889\nSwaps = 0\nInput blocks = 8\nOutput blocks = 8\nContext switch (voluntary) = 1\nContext switch (involuntary) = 2\n"
  },
  {
    "path": "cudd/nanotrav/C880.blif",
    "content": ".model C880.iscas\n.inputs 1GAT(0) 8GAT(1) 13GAT(2) 17GAT(3) 26GAT(4) 29GAT(5) 36GAT(6) 42GAT(7) 51GAT(8) 55GAT(9) 59GAT(10) 68GAT(11) 72GAT(12) 73GAT(13) 74GAT(14) 75GAT(15) 80GAT(16) 85GAT(17) 86GAT(18) 87GAT(19) 88GAT(20) 89GAT(21) 90GAT(22) 91GAT(23) 96GAT(24) 101GAT(25) 106GAT(26) 111GAT(27) 116GAT(28) 121GAT(29) 126GAT(30) 130GAT(31) 135GAT(32) 138GAT(33) 143GAT(34) 146GAT(35) 149GAT(36) 152GAT(37) 153GAT(38) 156GAT(39) 159GAT(40) 165GAT(41) 171GAT(42) 177GAT(43) 183GAT(44) 189GAT(45) 195GAT(46) 201GAT(47) 207GAT(48) 210GAT(49) 219GAT(50) 228GAT(51) 237GAT(52) 246GAT(53) 255GAT(54) 259GAT(55) 260GAT(56) 261GAT(57) 267GAT(58) 268GAT(59)\n.outputs 388GAT(133) 389GAT(132) 390GAT(131) 391GAT(124) 418GAT(168) 419GAT(164) 420GAT(158) 421GAT(162) 422GAT(161) 423GAT(155) 446GAT(183) 447GAT(182) 448GAT(179) 449GAT(176) 450GAT(173) 767GAT(349) 768GAT(334) 850GAT(404) 863GAT(424) 864GAT(423) 865GAT(422) 866GAT(426) 874GAT(433) 878GAT(442) 879GAT(441) 880GAT(440)\n.names 268GAT(59) 310GAT(60)\n1 0\n.names 255GAT(54) 267GAT(58) 341GAT(61)\n11 1\n.names 255GAT(54) 260GAT(56) 339GAT(62)\n11 1\n.names 255GAT(54) 259GAT(55) 337GAT(63)\n11 1\n.names 195GAT(46) 201GAT(47) 331GAT(64)\n00 0\n.names 195GAT(46) 201GAT(47) 330GAT(65)\n11 0\n.names 183GAT(44) 189GAT(45) 329GAT(66)\n00 0\n.names 183GAT(44) 189GAT(45) 328GAT(67)\n11 0\n.names 171GAT(42) 177GAT(43) 327GAT(68)\n00 0\n.names 171GAT(42) 177GAT(43) 326GAT(69)\n11 0\n.names 159GAT(40) 165GAT(41) 325GAT(70)\n00 0\n.names 159GAT(40) 165GAT(41) 324GAT(71)\n11 0\n.names 152GAT(37) 138GAT(33) 318GAT(72)\n11 1\n.names 210GAT(49) 121GAT(29) 340GAT(73)\n11 1\n.names 121GAT(29) 126GAT(30) 308GAT(74)\n00 0\n.names 121GAT(29) 126GAT(30) 307GAT(75)\n11 0\n.names 210GAT(49) 116GAT(28) 338GAT(76)\n11 1\n.names 210GAT(49) 111GAT(27) 336GAT(77)\n11 1\n.names 111GAT(27) 116GAT(28) 306GAT(78)\n00 0\n.names 111GAT(27) 116GAT(28) 305GAT(79)\n11 0\n.names 210GAT(49) 106GAT(26) 335GAT(80)\n11 1\n.names 210GAT(49) 101GAT(25) 334GAT(81)\n11 1\n.names 101GAT(25) 106GAT(26) 304GAT(82)\n00 0\n.names 101GAT(25) 106GAT(26) 303GAT(83)\n11 0\n.names 210GAT(49) 96GAT(24) 333GAT(84)\n11 1\n.names 210GAT(49) 91GAT(23) 332GAT(85)\n11 1\n.names 91GAT(23) 96GAT(24) 302GAT(86)\n00 0\n.names 91GAT(23) 96GAT(24) 301GAT(87)\n11 0\n.names 87GAT(19) 88GAT(20) 298GAT(88)\n00 0\n.names 85GAT(17) 86GAT(18) 297GAT(89)\n11 1\n.names 59GAT(10) 156GAT(39) 319GAT(90)\n11 0\n.names 59GAT(10) 75GAT(15) 80GAT(16) 293GAT(91)\n111 1\n.names 59GAT(10) 68GAT(11) 74GAT(14) 286GAT(92)\n111 0\n.names 51GAT(8) 138GAT(33) 316GAT(93)\n11 1\n.names 59GAT(10) 75GAT(15) 42GAT(7) 294GAT(94)\n111 1\n.names 59GAT(10) 42GAT(7) 68GAT(11) 72GAT(12) 284GAT(95)\n1111 0\n.names 59GAT(10) 36GAT(6) 42GAT(7) 296GAT(96)\n111 1\n.names 59GAT(10) 36GAT(6) 80GAT(16) 295GAT(97)\n111 1\n.names 29GAT(5) 36GAT(6) 42GAT(7) 292GAT(98)\n111 1\n.names 29GAT(5) 36GAT(6) 80GAT(16) 291GAT(99)\n111 1\n.names 29GAT(5) 75GAT(15) 42GAT(7) 290GAT(100)\n111 1\n.names 29GAT(5) 75GAT(15) 80GAT(16) 287GAT(101)\n111 1\n.names 29GAT(5) 68GAT(11) 285GAT(102)\n11 0\n.names 29GAT(5) 36GAT(6) 42GAT(7) 273GAT(103)\n111 1\n.names 17GAT(3) 42GAT(7) 323GAT(104)\n11 1\n.names 17GAT(3) 42GAT(7) 322GAT(105)\n00 1\n.names 17GAT(3) 138GAT(33) 317GAT(106)\n11 1\n.names 8GAT(1) 138GAT(33) 309GAT(107)\n11 1\n.names 1GAT(0) 8GAT(1) 13GAT(2) 55GAT(9) 280GAT(108)\n1111 0\n.names 1GAT(0) 8GAT(1) 51GAT(8) 17GAT(3) 279GAT(109)\n1111 0\n.names 1GAT(0) 26GAT(4) 51GAT(8) 276GAT(110)\n111 1\n.names 1GAT(0) 26GAT(4) 13GAT(2) 17GAT(3) 270GAT(111)\n1111 0\n.names 1GAT(0) 8GAT(1) 13GAT(2) 17GAT(3) 269GAT(112)\n1111 0\n.names 310GAT(60) 369GAT(113)\n1 0\n.names 330GAT(65) 331GAT(64) 385GAT(114)\n11 0\n.names 328GAT(67) 329GAT(66) 382GAT(115)\n11 0\n.names 326GAT(69) 327GAT(68) 379GAT(116)\n11 0\n.names 324GAT(71) 325GAT(70) 376GAT(117)\n11 0\n.names 307GAT(75) 308GAT(74) 366GAT(118)\n11 0\n.names 305GAT(79) 306GAT(78) 363GAT(119)\n11 0\n.names 303GAT(83) 304GAT(82) 360GAT(120)\n11 0\n.names 301GAT(87) 302GAT(86) 357GAT(121)\n11 0\n.names 90GAT(22) 298GAT(88) 356GAT(122)\n11 1\n.names 89GAT(21) 298GAT(88) 355GAT(123)\n11 0\n.names 297GAT(89) 391GAT(124)\n1 1\n.names 293GAT(91) 351GAT(125)\n1 0\n.names 280GAT(108) 286GAT(92) 350GAT(126)\n00 0\n.names 294GAT(94) 352GAT(127)\n1 0\n.names 280GAT(108) 284GAT(95) 348GAT(128)\n00 1\n.names 296GAT(96) 354GAT(129)\n1 0\n.names 295GAT(97) 353GAT(130)\n1 0\n.names 292GAT(98) 390GAT(131)\n1 1\n.names 291GAT(99) 389GAT(132)\n1 1\n.names 290GAT(100) 388GAT(133)\n1 1\n.names 280GAT(108) 285GAT(102) 349GAT(134)\n00 0\n.names 273GAT(103) 343GAT(135)\n1 0\n.names 270GAT(111) 273GAT(103) 344GAT(136)\n00 0\n.names 322GAT(105) 323GAT(104) 375GAT(137)\n00 1\n.names 279GAT(109) 347GAT(138)\n1 0\n.names 276GAT(110) 345GAT(139)\n1 0\n.names 276GAT(110) 346GAT(140)\n1 0\n.names 269GAT(112) 342GAT(141)\n1 0\n.names 210GAT(49) 369GAT(113) 417GAT(142)\n11 1\n.names 385GAT(114) 415GAT(143)\n1 0\n.names 382GAT(115) 385GAT(114) 416GAT(144)\n11 1\n.names 382GAT(115) 414GAT(145)\n1 0\n.names 379GAT(116) 412GAT(146)\n1 0\n.names 376GAT(117) 379GAT(116) 413GAT(147)\n11 1\n.names 376GAT(117) 411GAT(148)\n1 0\n.names 366GAT(118) 408GAT(149)\n1 0\n.names 363GAT(119) 366GAT(118) 409GAT(150)\n11 1\n.names 363GAT(119) 407GAT(151)\n1 0\n.names 360GAT(120) 405GAT(152)\n1 0\n.names 357GAT(121) 360GAT(120) 406GAT(153)\n11 1\n.names 357GAT(121) 404GAT(154)\n1 0\n.names 356GAT(122) 423GAT(155)\n1 1\n.names 355GAT(123) 403GAT(156)\n1 0\n.names 348GAT(128) 73GAT(13) 400GAT(157)\n11 1\n.names 351GAT(125) 420GAT(158)\n1 1\n.names 350GAT(126) 402GAT(159)\n1 0\n.names 347GAT(138) 352GAT(127) 410GAT(160)\n11 0\n.names 354GAT(129) 422GAT(161)\n1 1\n.names 353GAT(130) 421GAT(162)\n1 1\n.names 349GAT(134) 401GAT(163)\n1 0\n.names 344GAT(136) 419GAT(164)\n1 1\n.names 345GAT(139) 393GAT(165)\n1 0\n.names 346GAT(140) 399GAT(166)\n1 0\n.names 270GAT(111) 343GAT(135) 392GAT(167)\n00 0\n.names 342GAT(141) 418GAT(168)\n1 1\n.names 414GAT(145) 415GAT(143) 445GAT(169)\n11 1\n.names 411GAT(148) 412GAT(146) 444GAT(170)\n11 1\n.names 407GAT(151) 408GAT(149) 426GAT(171)\n11 1\n.names 404GAT(154) 405GAT(152) 425GAT(172)\n11 1\n.names 403GAT(156) 450GAT(173)\n1 1\n.names 400GAT(157) 424GAT(174)\n1 0\n.names 375GAT(137) 59GAT(10) 156GAT(39) 393GAT(165) 442GAT(175)\n1111 0\n.names 402GAT(159) 449GAT(176)\n1 1\n.names 393GAT(165) 287GAT(101) 55GAT(9) 437GAT(177)\n111 0\n.names 319GAT(90) 393GAT(165) 55GAT(9) 427GAT(178)\n111 1\n.names 401GAT(163) 448GAT(179)\n1 1\n.names 393GAT(165) 319GAT(90) 17GAT(3) 443GAT(180)\n111 0\n.names 393GAT(165) 17GAT(3) 287GAT(101) 432GAT(181)\n111 1\n.names 399GAT(166) 447GAT(182)\n1 1\n.names 392GAT(167) 446GAT(183)\n1 1\n.names 369GAT(113) 437GAT(177) 488GAT(184)\n00 0\n.names 369GAT(113) 437GAT(177) 489GAT(185)\n00 0\n.names 369GAT(113) 437GAT(177) 490GAT(186)\n00 0\n.names 369GAT(113) 437GAT(177) 491GAT(187)\n00 0\n.names 310GAT(60) 432GAT(181) 476GAT(188)\n11 1\n.names 310GAT(60) 432GAT(181) 478GAT(189)\n11 1\n.names 310GAT(60) 432GAT(181) 480GAT(190)\n11 1\n.names 310GAT(60) 432GAT(181) 482GAT(191)\n11 1\n.names 416GAT(144) 445GAT(169) 495GAT(192)\n00 1\n.names 413GAT(147) 444GAT(170) 492GAT(193)\n00 1\n.names 153GAT(38) 427GAT(178) 481GAT(194)\n11 1\n.names 149GAT(36) 427GAT(178) 479GAT(195)\n11 1\n.names 146GAT(35) 427GAT(178) 477GAT(196)\n11 1\n.names 143GAT(34) 427GAT(178) 475GAT(197)\n11 1\n.names 409GAT(150) 426GAT(171) 463GAT(198)\n00 1\n.names 406GAT(153) 425GAT(172) 460GAT(199)\n00 1\n.names 424GAT(174) 451GAT(200)\n1 0\n.names 442GAT(175) 410GAT(160) 466GAT(201)\n11 0\n.names 443GAT(180) 1GAT(0) 483GAT(202)\n11 0\n.names 475GAT(197) 476GAT(188) 503GAT(203)\n00 1\n.names 477GAT(196) 478GAT(189) 505GAT(204)\n00 1\n.names 479GAT(195) 480GAT(190) 507GAT(205)\n00 1\n.names 481GAT(194) 482GAT(191) 509GAT(206)\n00 1\n.names 495GAT(192) 207GAT(48) 521GAT(207)\n00 0\n.names 495GAT(192) 207GAT(48) 520GAT(208)\n11 0\n.names 451GAT(200) 201GAT(47) 529GAT(209)\n11 0\n.names 451GAT(200) 195GAT(46) 528GAT(210)\n11 0\n.names 451GAT(200) 189GAT(45) 527GAT(211)\n11 0\n.names 451GAT(200) 183GAT(44) 526GAT(212)\n11 1\n.names 451GAT(200) 177GAT(43) 525GAT(213)\n11 1\n.names 451GAT(200) 171GAT(42) 524GAT(214)\n11 1\n.names 451GAT(200) 165GAT(41) 523GAT(215)\n11 1\n.names 451GAT(200) 159GAT(40) 522GAT(216)\n11 1\n.names 153GAT(38) 483GAT(202) 516GAT(217)\n11 1\n.names 149GAT(36) 483GAT(202) 514GAT(218)\n11 1\n.names 146GAT(35) 483GAT(202) 512GAT(219)\n11 1\n.names 143GAT(34) 483GAT(202) 510GAT(220)\n11 1\n.names 463GAT(198) 135GAT(32) 501GAT(221)\n00 0\n.names 463GAT(198) 135GAT(32) 500GAT(222)\n11 0\n.names 130GAT(31) 492GAT(193) 519GAT(223)\n00 0\n.names 130GAT(31) 492GAT(193) 518GAT(224)\n11 0\n.names 130GAT(31) 460GAT(199) 499GAT(225)\n00 0\n.names 130GAT(31) 460GAT(199) 498GAT(226)\n11 0\n.names 126GAT(30) 466GAT(201) 517GAT(227)\n11 1\n.names 121GAT(29) 466GAT(201) 515GAT(228)\n11 1\n.names 116GAT(28) 466GAT(201) 513GAT(229)\n11 1\n.names 111GAT(27) 466GAT(201) 511GAT(230)\n11 1\n.names 106GAT(26) 466GAT(201) 508GAT(231)\n11 1\n.names 101GAT(25) 466GAT(201) 506GAT(232)\n11 1\n.names 96GAT(24) 466GAT(201) 504GAT(233)\n11 1\n.names 91GAT(23) 466GAT(201) 502GAT(234)\n11 1\n.names 520GAT(208) 521GAT(207) 547GAT(235)\n11 0\n.names 516GAT(217) 517GAT(227) 543GAT(236)\n00 1\n.names 514GAT(218) 515GAT(228) 542GAT(237)\n00 1\n.names 512GAT(219) 513GAT(229) 541GAT(238)\n00 1\n.names 510GAT(220) 511GAT(230) 540GAT(239)\n00 1\n.names 318GAT(72) 508GAT(231) 539GAT(240)\n00 1\n.names 500GAT(222) 501GAT(221) 533GAT(241)\n11 0\n.names 518GAT(224) 519GAT(223) 544GAT(242)\n11 0\n.names 498GAT(226) 499GAT(225) 530GAT(243)\n11 0\n.names 316GAT(93) 504GAT(233) 537GAT(244)\n00 1\n.names 317GAT(106) 506GAT(232) 538GAT(245)\n00 1\n.names 309GAT(107) 502GAT(234) 536GAT(246)\n00 1\n.names 488GAT(184) 540GAT(239) 569GAT(247)\n11 0\n.names 489GAT(185) 541GAT(238) 573GAT(248)\n11 0\n.names 490GAT(186) 542GAT(237) 577GAT(249)\n11 0\n.names 491GAT(187) 543GAT(236) 581GAT(250)\n11 0\n.names 536GAT(246) 503GAT(203) 553GAT(251)\n11 0\n.names 537GAT(244) 505GAT(204) 557GAT(252)\n11 0\n.names 538GAT(245) 507GAT(205) 561GAT(253)\n11 0\n.names 539GAT(240) 509GAT(206) 565GAT(254)\n11 0\n.names 547GAT(235) 586GAT(255)\n1 0\n.names 544GAT(242) 547GAT(235) 587GAT(256)\n11 1\n.names 533GAT(241) 551GAT(257)\n1 0\n.names 530GAT(243) 533GAT(241) 552GAT(258)\n11 1\n.names 544GAT(242) 585GAT(259)\n1 0\n.names 530GAT(243) 550GAT(260)\n1 0\n.names 246GAT(53) 581GAT(250) 659GAT(261)\n11 1\n.names 246GAT(53) 577GAT(249) 650GAT(262)\n11 1\n.names 246GAT(53) 573GAT(248) 640GAT(263)\n11 1\n.names 246GAT(53) 569GAT(247) 631GAT(264)\n11 1\n.names 246GAT(53) 565GAT(254) 624GAT(265)\n11 1\n.names 246GAT(53) 561GAT(253) 615GAT(266)\n11 1\n.names 246GAT(53) 557GAT(252) 605GAT(267)\n11 1\n.names 246GAT(53) 553GAT(251) 596GAT(268)\n11 1\n.names 585GAT(259) 586GAT(255) 589GAT(269)\n11 1\n.names 581GAT(250) 201GAT(47) 654GAT(270)\n00 0\n.names 581GAT(250) 201GAT(47) 651GAT(271)\n11 0\n.names 577GAT(249) 195GAT(46) 644GAT(272)\n00 0\n.names 577GAT(249) 195GAT(46) 641GAT(273)\n11 0\n.names 573GAT(248) 189GAT(45) 635GAT(274)\n00 0\n.names 573GAT(248) 189GAT(45) 632GAT(275)\n11 0\n.names 569GAT(247) 183GAT(44) 628GAT(276)\n00 0\n.names 569GAT(247) 183GAT(44) 625GAT(277)\n11 0\n.names 565GAT(254) 177GAT(43) 619GAT(278)\n00 0\n.names 565GAT(254) 177GAT(43) 616GAT(279)\n11 0\n.names 561GAT(253) 171GAT(42) 609GAT(280)\n00 0\n.names 561GAT(253) 171GAT(42) 606GAT(281)\n11 0\n.names 557GAT(252) 165GAT(41) 600GAT(282)\n00 0\n.names 557GAT(252) 165GAT(41) 597GAT(283)\n11 0\n.names 553GAT(251) 159GAT(40) 593GAT(284)\n00 0\n.names 553GAT(251) 159GAT(40) 590GAT(285)\n11 0\n.names 550GAT(260) 551GAT(257) 588GAT(286)\n11 1\n.names 635GAT(274) 644GAT(272) 654GAT(270) 261GAT(57) 734GAT(287)\n1111 0\n.names 644GAT(272) 654GAT(270) 261GAT(57) 733GAT(288)\n111 0\n.names 654GAT(270) 261GAT(57) 732GAT(289)\n11 0\n.names 341GAT(61) 659GAT(261) 731GAT(290)\n00 1\n.names 339GAT(62) 650GAT(262) 721GAT(291)\n00 1\n.names 337GAT(63) 640GAT(263) 712GAT(292)\n00 1\n.names 587GAT(256) 589GAT(269) 661GAT(293)\n00 1\n.names 654GAT(270) 651GAT(271) 727GAT(294)\n11 1\n.names 651GAT(271) 722GAT(295)\n1 0\n.names 644GAT(272) 641GAT(273) 717GAT(296)\n11 1\n.names 641GAT(273) 713GAT(297)\n1 0\n.names 635GAT(274) 632GAT(275) 708GAT(298)\n11 1\n.names 632GAT(275) 705GAT(299)\n1 0\n.names 628GAT(276) 625GAT(277) 700GAT(300)\n11 1\n.names 625GAT(277) 697GAT(301)\n1 0\n.names 631GAT(264) 526GAT(212) 704GAT(302)\n00 1\n.names 619GAT(278) 616GAT(279) 692GAT(303)\n11 1\n.names 616GAT(279) 687GAT(304)\n1 0\n.names 624GAT(265) 525GAT(213) 696GAT(305)\n00 1\n.names 609GAT(280) 606GAT(281) 682GAT(306)\n11 1\n.names 606GAT(281) 678GAT(307)\n1 0\n.names 615GAT(266) 524GAT(214) 686GAT(308)\n00 1\n.names 600GAT(282) 597GAT(283) 673GAT(309)\n11 1\n.names 597GAT(283) 670GAT(310)\n1 0\n.names 605GAT(267) 523GAT(215) 677GAT(311)\n00 1\n.names 593GAT(284) 590GAT(285) 665GAT(312)\n11 1\n.names 590GAT(285) 662GAT(313)\n1 0\n.names 596GAT(268) 522GAT(216) 669GAT(314)\n00 1\n.names 552GAT(258) 588GAT(286) 660GAT(315)\n00 1\n.names 727GAT(294) 261GAT(57) 758GAT(316)\n11 1\n.names 727GAT(294) 261GAT(57) 757GAT(317)\n00 1\n.names 237GAT(52) 722GAT(295) 760GAT(318)\n11 1\n.names 237GAT(52) 713GAT(297) 755GAT(319)\n11 1\n.names 237GAT(52) 705GAT(299) 752GAT(320)\n11 1\n.names 237GAT(52) 697GAT(301) 749GAT(321)\n11 1\n.names 237GAT(52) 687GAT(304) 746GAT(322)\n11 1\n.names 237GAT(52) 678GAT(307) 743GAT(323)\n11 1\n.names 237GAT(52) 670GAT(310) 740GAT(324)\n11 1\n.names 237GAT(52) 662GAT(313) 737GAT(325)\n11 1\n.names 228GAT(51) 727GAT(294) 759GAT(326)\n11 1\n.names 228GAT(51) 717GAT(296) 754GAT(327)\n11 1\n.names 228GAT(51) 708GAT(298) 751GAT(328)\n11 1\n.names 228GAT(51) 700GAT(300) 748GAT(329)\n11 1\n.names 228GAT(51) 692GAT(303) 745GAT(330)\n11 1\n.names 228GAT(51) 682GAT(306) 742GAT(331)\n11 1\n.names 228GAT(51) 673GAT(309) 739GAT(332)\n11 1\n.names 228GAT(51) 665GAT(312) 736GAT(333)\n11 1\n.names 661GAT(293) 768GAT(334)\n1 1\n.names 722GAT(295) 756GAT(335)\n1 0\n.names 644GAT(272) 722GAT(295) 761GAT(336)\n11 0\n.names 635GAT(274) 644GAT(272) 722GAT(295) 763GAT(337)\n111 0\n.names 713GAT(297) 753GAT(338)\n1 0\n.names 635GAT(274) 713GAT(297) 762GAT(339)\n11 0\n.names 705GAT(299) 750GAT(340)\n1 0\n.names 697GAT(301) 747GAT(341)\n1 0\n.names 687GAT(304) 744GAT(342)\n1 0\n.names 609GAT(280) 687GAT(304) 764GAT(343)\n11 0\n.names 600GAT(282) 609GAT(280) 687GAT(304) 766GAT(344)\n111 0\n.names 678GAT(307) 741GAT(345)\n1 0\n.names 600GAT(282) 678GAT(307) 765GAT(346)\n11 0\n.names 670GAT(310) 738GAT(347)\n1 0\n.names 662GAT(313) 735GAT(348)\n1 0\n.names 660GAT(315) 767GAT(349)\n1 1\n.names 757GAT(317) 758GAT(316) 786GAT(350)\n00 1\n.names 750GAT(340) 762GAT(339) 763GAT(337) 734GAT(287) 773GAT(351)\n1111 0\n.names 753GAT(338) 761GAT(336) 733GAT(288) 778GAT(352)\n111 0\n.names 756GAT(335) 732GAT(289) 782GAT(353)\n11 0\n.names 759GAT(326) 760GAT(318) 787GAT(354)\n00 1\n.names 754GAT(327) 755GAT(319) 785GAT(355)\n00 1\n.names 751GAT(328) 752GAT(320) 781GAT(356)\n00 1\n.names 748GAT(329) 749GAT(321) 777GAT(357)\n00 1\n.names 745GAT(330) 746GAT(322) 772GAT(358)\n00 1\n.names 742GAT(331) 743GAT(323) 771GAT(359)\n00 1\n.names 739GAT(332) 740GAT(324) 770GAT(360)\n00 1\n.names 736GAT(333) 737GAT(325) 769GAT(361)\n00 1\n.names 219GAT(50) 786GAT(350) 794GAT(362)\n11 1\n.names 717GAT(296) 782GAT(353) 792GAT(363)\n00 1\n.names 717GAT(296) 782GAT(353) 793GAT(364)\n11 1\n.names 708GAT(298) 778GAT(352) 790GAT(365)\n00 1\n.names 708GAT(298) 778GAT(352) 791GAT(366)\n11 1\n.names 700GAT(300) 773GAT(351) 788GAT(367)\n00 1\n.names 700GAT(300) 773GAT(351) 789GAT(368)\n11 1\n.names 628GAT(276) 773GAT(351) 795GAT(369)\n11 0\n.names 792GAT(363) 793GAT(364) 804GAT(370)\n00 1\n.names 790GAT(365) 791GAT(366) 803GAT(371)\n00 1\n.names 788GAT(367) 789GAT(368) 802GAT(372)\n00 1\n.names 795GAT(369) 747GAT(341) 796GAT(373)\n11 0\n.names 340GAT(73) 794GAT(362) 805GAT(374)\n00 1\n.names 219GAT(50) 804GAT(370) 810GAT(375)\n11 1\n.names 219GAT(50) 803GAT(371) 809GAT(376)\n11 1\n.names 219GAT(50) 802GAT(372) 808GAT(377)\n11 1\n.names 805GAT(374) 787GAT(354) 731GAT(290) 529GAT(209) 811GAT(378)\n1111 0\n.names 692GAT(303) 796GAT(373) 806GAT(379)\n00 1\n.names 692GAT(303) 796GAT(373) 807GAT(380)\n11 1\n.names 619GAT(278) 796GAT(373) 812GAT(381)\n11 0\n.names 609GAT(280) 619GAT(278) 796GAT(373) 813GAT(382)\n111 0\n.names 600GAT(282) 609GAT(280) 619GAT(278) 796GAT(373) 814GAT(383)\n1111 0\n.names 811GAT(378) 829GAT(384)\n1 0\n.names 806GAT(379) 807GAT(380) 825GAT(385)\n00 1\n.names 744GAT(342) 812GAT(381) 822GAT(386)\n11 0\n.names 741GAT(345) 764GAT(343) 813GAT(382) 819GAT(387)\n111 0\n.names 738GAT(347) 765GAT(346) 766GAT(344) 814GAT(383) 815GAT(388)\n1111 0\n.names 338GAT(76) 810GAT(375) 828GAT(389)\n00 1\n.names 336GAT(77) 809GAT(376) 827GAT(390)\n00 1\n.names 335GAT(80) 808GAT(377) 826GAT(391)\n00 1\n.names 219GAT(50) 825GAT(385) 836GAT(392)\n11 1\n.names 829GAT(384) 840GAT(393)\n1 0\n.names 828GAT(389) 785GAT(355) 721GAT(291) 528GAT(210) 839GAT(394)\n1111 0\n.names 827GAT(390) 781GAT(356) 712GAT(292) 527GAT(211) 838GAT(395)\n1111 0\n.names 826GAT(391) 777GAT(357) 704GAT(302) 837GAT(396)\n111 0\n.names 682GAT(306) 822GAT(386) 834GAT(397)\n00 1\n.names 682GAT(306) 822GAT(386) 835GAT(398)\n11 1\n.names 673GAT(309) 819GAT(387) 832GAT(399)\n00 1\n.names 673GAT(309) 819GAT(387) 833GAT(400)\n11 1\n.names 665GAT(312) 815GAT(388) 830GAT(401)\n00 1\n.names 665GAT(312) 815GAT(388) 831GAT(402)\n11 1\n.names 815GAT(388) 593GAT(284) 841GAT(403)\n11 0\n.names 840GAT(393) 850GAT(404)\n1 1\n.names 839GAT(394) 848GAT(405)\n1 0\n.names 838GAT(395) 847GAT(406)\n1 0\n.names 837GAT(396) 846GAT(407)\n1 0\n.names 834GAT(397) 835GAT(398) 844GAT(408)\n00 1\n.names 832GAT(399) 833GAT(400) 843GAT(409)\n00 1\n.names 830GAT(401) 831GAT(402) 842GAT(410)\n00 1\n.names 735GAT(348) 841GAT(403) 849GAT(411)\n11 1\n.names 334GAT(81) 836GAT(392) 845GAT(412)\n00 1\n.names 219GAT(50) 844GAT(408) 853GAT(413)\n11 1\n.names 219GAT(50) 843GAT(409) 852GAT(414)\n11 1\n.names 219GAT(50) 842GAT(410) 851GAT(415)\n11 1\n.names 848GAT(405) 857GAT(416)\n1 0\n.names 847GAT(406) 856GAT(417)\n1 0\n.names 846GAT(407) 855GAT(418)\n1 0\n.names 845GAT(412) 772GAT(358) 696GAT(305) 854GAT(419)\n111 0\n.names 849GAT(411) 858GAT(420)\n1 0\n.names 417GAT(142) 851GAT(415) 859GAT(421)\n00 1\n.names 857GAT(416) 865GAT(422)\n1 1\n.names 856GAT(417) 864GAT(423)\n1 1\n.names 855GAT(418) 863GAT(424)\n1 1\n.names 854GAT(419) 862GAT(425)\n1 0\n.names 858GAT(420) 866GAT(426)\n1 1\n.names 333GAT(84) 853GAT(413) 861GAT(427)\n00 1\n.names 332GAT(85) 852GAT(414) 860GAT(428)\n00 1\n.names 862GAT(425) 870GAT(429)\n1 0\n.names 861GAT(427) 771GAT(359) 686GAT(308) 869GAT(430)\n111 0\n.names 860GAT(428) 770GAT(360) 677GAT(311) 868GAT(431)\n111 0\n.names 859GAT(421) 769GAT(361) 669GAT(314) 867GAT(432)\n111 0\n.names 870GAT(429) 874GAT(433)\n1 1\n.names 869GAT(430) 873GAT(434)\n1 0\n.names 868GAT(431) 872GAT(435)\n1 0\n.names 867GAT(432) 871GAT(436)\n1 0\n.names 873GAT(434) 877GAT(437)\n1 0\n.names 872GAT(435) 876GAT(438)\n1 0\n.names 871GAT(436) 875GAT(439)\n1 0\n.names 877GAT(437) 880GAT(440)\n1 1\n.names 876GAT(438) 879GAT(441)\n1 1\n.names 875GAT(439) 878GAT(442)\n1 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/C880.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -ordering dfs -autodyn -automethod sifting -reordering sifting -drop ./nanotrav/C880.blif\n# CUDD Version 3.0.0\nBDD reordering with sifting: from 3974 to ... 2432 nodes in 0.01 sec\nBDD reordering with sifting: from 4893 to ... 3549 nodes in 0.01 sec\nBDD reordering with sifting: from 7133 to ... 6246 nodes in 0.03 sec\nBDD reordering with sifting: from 12522 to ... 6465 nodes in 0.04 sec\nOrder before final reordering\n86GAT(18) 85GAT(17) 90GAT(22) 89GAT(21) 88GAT(20) 87GAT(19) 1GAT(0) 51GAT(8) \n75GAT(15) 26GAT(4) 268GAT(59) 36GAT(6) 29GAT(5) 80GAT(16) 59GAT(10) 42GAT(7) \n156GAT(39) 17GAT(3) 74GAT(14) 55GAT(9) 8GAT(1) 219GAT(50) 210GAT(49) 91GAT(23) \n101GAT(25) 138GAT(33) 96GAT(24) 171GAT(42) 152GAT(37) 146GAT(35) 116GAT(28) 189GAT(45) \n149GAT(36) 121GAT(29) 195GAT(46) 153GAT(38) 126GAT(30) 261GAT(57) 201GAT(47) 143GAT(34) \n111GAT(27) 183GAT(44) 130GAT(31) 135GAT(32) 106GAT(26) 177GAT(43) 165GAT(41) 207GAT(48) \n159GAT(40) 228GAT(51) 237GAT(52) 246GAT(53) 73GAT(13) 72GAT(12) 68GAT(11) 13GAT(2) \n260GAT(56) 267GAT(58) 259GAT(55) 255GAT(54) \nNumber of inputs = 60\nBDD reordering with sifting: from 6204 to ... 4623 nodes in 0.02 sec\nNew order\n135GAT(32) 207GAT(48) 130GAT(31) 86GAT(18) 85GAT(17) 89GAT(21) 90GAT(22) 88GAT(20) \n87GAT(19) 1GAT(0) 51GAT(8) 26GAT(4) 268GAT(59) 29GAT(5) 80GAT(16) 59GAT(10) \n42GAT(7) 75GAT(15) 156GAT(39) 36GAT(6) 17GAT(3) 74GAT(14) 55GAT(9) 8GAT(1) \n210GAT(49) 91GAT(23) 138GAT(33) 165GAT(41) 96GAT(24) 159GAT(40) 101GAT(25) 171GAT(42) \n152GAT(37) 149GAT(36) 146GAT(35) 116GAT(28) 189GAT(45) 121GAT(29) 195GAT(46) 153GAT(38) \n143GAT(34) 126GAT(30) 201GAT(47) 261GAT(57) 111GAT(27) 106GAT(26) 183GAT(44) 177GAT(43) \n219GAT(50) 246GAT(53) 237GAT(52) 228GAT(51) 73GAT(13) 72GAT(12) 68GAT(11) 13GAT(2) \n260GAT(56) 267GAT(58) 259GAT(55) 255GAT(54) \n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000000\nMaximum number of variable swaps per reordering: 1000000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: yes\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 9340\n**** CUDD non-modifiable parameters ****\nMemory in use: 4926992\nPeak number of nodes: 19418\nPeak number of live nodes: 12568\nNumber of BDD variables: 60\nNumber of ZDD variables: 0\nNumber of cache entries: 65536\nNumber of cache look-ups: 59150\nNumber of cache hits: 28634\nNumber of cache insertions: 30595\nNumber of cache collisions: 2450\nNumber of cache deletions: 28145\nCache used slots = 18.22% (expected 0.00%)\nSoft limit for cache size: 62464\nNumber of buckets in unique table: 15616\nUsed buckets in unique table: 20.72% (expected 20.96%)\nNumber of BDD and ADD nodes: 4671\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 0\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 32671\nTotal number of nodes reclaimed: 1974\nGarbage collections so far: 5\nTime for garbage collection: 0.00 sec\nReorderings so far: 5\nTime for reordering: 0.11 sec\nFinal size: 4623\ntotal time = 0.11 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.1 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  6616K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 1302\nSwaps = 0\nInput blocks = 40\nOutput blocks = 8\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/Included.am",
    "content": "check_PROGRAMS += nanotrav/nanotrav\nnanotrav_nanotrav_SOURCES = nanotrav/bnet.h nanotrav/ntr.h \\\n  nanotrav/bnet.c nanotrav/chkMterm.c nanotrav/main.c nanotrav/ntrBddTest.c \\\n  nanotrav/ntr.c nanotrav/ntrHeap.c nanotrav/ntrMflow.c nanotrav/ntrShort.c \\\n  nanotrav/ntrZddTest.c\nnanotrav_nanotrav_CPPFLAGS = -I$(top_srcdir)/cudd -I$(top_srcdir)/mtr \\\n  -I$(top_srcdir)/epd -I$(top_srcdir)/st -I$(top_srcdir)/dddmp \\\n  -I$(top_srcdir)/util\nif DDDMP\nnanotrav_nanotrav_LDADD =\nelse\nnanotrav_nanotrav_LDADD = dddmp/libdddmp.la\nendif\nnanotrav_nanotrav_LDADD += cudd/libcudd.la\n\ncheck_SCRIPTS += nanotrav/test_ntrv.test\ndist_check_DATA += nanotrav/adj49.blif nanotrav/adj49.out nanotrav/C17.blif \\\n  nanotrav/C17.out nanotrav/C880.blif nanotrav/C880.out nanotrav/closest.blif \\\n  nanotrav/closest.out nanotrav/ham01.blif nanotrav/ham01.out \\\n  nanotrav/mult32a.blif nanotrav/mult32a.out nanotrav/rcn25.blif \\\n  nanotrav/rcn25.out nanotrav/s27.blif nanotrav/s27.out nanotrav/s27b.blif \\\n  nanotrav/s27b.out nanotrav/s27c.blif nanotrav/s27c.out nanotrav/s382.blif \\\n  nanotrav/s382.out nanotrav/s641.blif nanotrav/s641.out \\\n  nanotrav/miniFirst.blif nanotrav/miniSecond.blif nanotrav/miniFirst.out\nif !CROSS_COMPILING\nTESTS += nanotrav/test_ntrv.test\nendif !CROSS_COMPILING\nEXTRA_DIST += nanotrav/README nanotrav/nanotrav.1 nanotrav/test_ntrv.test.in\n\nnanotrav/test_ntrv.test: nanotrav/test_ntrv.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n\nCLEANFILES += nanotrav/adj49.tst nanotrav/C17.tst nanotrav/C880.tst \\\n  nanotrav/closest.tst nanotrav/ham01.tst nanotrav/mult32a.tst \\\n  nanotrav/rcn25.tst nanotrav/s27.tst nanotrav/s27b.tst nanotrav/s27c.tst \\\n  nanotrav/s382.tst nanotrav/s641.tst nanotrav/miniFirst.tst\n"
  },
  {
    "path": "cudd/nanotrav/README",
    "content": "$Id: README,v 1.8 1997/01/23 07:33:22 fabio Exp fabio $\n\nWHAT IS NANOTRAV\n================\n\nThis directory contains nanotrav, a simple reachability analysis program\nbased on the CUDD package. Nanotrav uses a very naive approach and is\nonly included to provide a sanity check for the installation of the\nCUDD package.\n\nNanotrav reads a circuit written in a small subset of blif. This\nformat is described in the comments in bnet.c. Nanotrav then creates\nBDDs for the primary outputs and the next state functions (if any) of\nthe circuit.\n\nIf, passed the -trav option, nanotrav builds a BDD for the\ncharacteristic function of the transition relation of the graph. It then\nbuilds a BDD for the initial state(s), and performs reachability\nanalysis.  Reachability analysys is performed with either the method\nknown as \"monolithic transition relation method,\" whose main virtue is\nsimplicity, or with an unsophisticated partitioned transition relation\nmethod.\n\nOnce it has completed reachability analysis, nanotrav prints results and\nexits. The amount of information printed, as well as several other\nfeatures are controlled by the options. For a complete list of the\noptions, consult the man page. Here, we only mention that the options allow\nthe user of nanotrav to select among different reordering options.\n\nTEST CIRCUITS\n=============\n\nTwelve test circuits are contained in this directory.  The results or running\nnanotrav on them with various options are also included.  These tests are run\nas part of \"make check.\"  Notice that rcn25 requires approximately 30 s. All\nother tests take much less.\n"
  },
  {
    "path": "cudd/nanotrav/adj49.blif",
    "content": ".model adj49\n.inputs CA\n.inputs WA\n.inputs OR\n.inputs NV\n.inputs ID\n.inputs UT\n.inputs AZ\n.inputs MT\n.inputs WY\n.inputs CO\n.inputs NM\n.inputs ND\n.inputs SD\n.inputs NE\n.inputs KS\n.inputs OK\n.inputs TX\n.inputs MN\n.inputs IA\n.inputs MO\n.inputs AR\n.inputs LA\n.inputs WI\n.inputs IL\n.inputs MS\n.inputs MI\n.inputs IN\n.inputs KY\n.inputs TN\n.inputs AL\n.inputs OH\n.inputs WV\n.inputs VA\n.inputs GA\n.inputs FL\n.inputs PA\n.inputs MD\n.inputs DC\n.inputs NC\n.inputs SC\n.inputs VT\n.inputs NY\n.inputs NJ\n.inputs DE\n.inputs NH\n.inputs MA\n.inputs CT\n.inputs ME\n.inputs RI\n.outputs indep\n.names CA OR caor\n11 0\n.names CA NV canv\n11 0\n.names CA AZ caaz\n11 0\n.names WA OR waor\n11 0\n.names WA ID waid\n11 0\n.names OR ID orid\n11 0\n.names OR NV ornv\n11 0\n.names NV ID nvid\n11 0\n.names NV UT nvut\n11 0\n.names NV AZ nvaz\n11 0\n.names ID MT idmt\n11 0\n.names ID WY idwy\n11 0\n.names ID UT idut\n11 0\n.names UT WY utwy\n11 0\n.names UT CO utco\n11 0\n.names UT AZ utaz\n11 0\n.names AZ NM aznm\n11 0\n.names MT ND mtnd\n11 0\n.names MT SD mtsd\n11 0\n.names MT WY mtwy\n11 0\n.names WY SD wysd\n11 0\n.names WY NE wyne\n11 0\n.names WY CO wyco\n11 0\n.names CO NE cone\n11 0\n.names CO KS coks\n11 0\n.names CO OK cook\n11 0\n.names CO NM conm\n11 0\n.names NM OK nmok\n11 0\n.names NM TX nmtx\n11 0\n.names ND MN ndmn\n11 0\n.names ND SD ndsd\n11 0\n.names SD MN sdmn\n11 0\n.names SD IA sdia\n11 0\n.names SD NE sdne\n11 0\n.names NE IA neia\n11 0\n.names NE MO nemo\n11 0\n.names NE KS neks\n11 0\n.names KS MO ksmo\n11 0\n.names KS OK ksok\n11 0\n.names OK MO okmo\n11 0\n.names OK AR okar\n11 0\n.names OK TX oktx\n11 0\n.names TX AR txar\n11 0\n.names TX LA txla\n11 0\n.names MN WI mnwi\n11 0\n.names MN IA mnia\n11 0\n.names IA WI iawi\n11 0\n.names IA IL iail\n11 0\n.names IA MO iamo\n11 0\n.names MO IL moil\n11 0\n.names MO KY moky\n11 0\n.names MO TN motn\n11 0\n.names MO AR moar\n11 0\n.names AR TN artn\n11 0\n.names AR MS arms\n11 0\n.names AR LA arla\n11 0\n.names LA MS lams\n11 0\n.names WI MI wimi\n11 0\n.names WI IL wiil\n11 0\n.names IL IN ilin\n11 0\n.names IL KY ilky\n11 0\n.names MS TN mstn\n11 0\n.names MS AL msal\n11 0\n.names MI OH mioh\n11 0\n.names MI IN miin\n11 0\n.names IN OH inoh\n11 0\n.names IN KY inky\n11 0\n.names KY OH kyoh\n11 0\n.names KY WV kywv\n11 0\n.names KY VA kyva\n11 0\n.names KY TN kytn\n11 0\n.names TN VA tnva\n11 0\n.names TN NC tnnc\n11 0\n.names TN GA tnga\n11 0\n.names TN AL tnal\n11 0\n.names AL GA alga\n11 0\n.names AL FL alfl\n11 0\n.names OH PA ohpa\n11 0\n.names OH WV ohwv\n11 0\n.names WV PA wvpa\n11 0\n.names WV MD wvmd\n11 0\n.names WV VA wvva\n11 0\n.names VA MD vamd\n11 0\n.names VA DC vadc\n11 0\n.names VA NC vanc\n11 0\n.names GA NC ganc\n11 0\n.names GA SC gasc\n11 0\n.names GA FL gafl\n11 0\n.names PA NY pany\n11 0\n.names PA NJ panj\n11 0\n.names PA DE pade\n11 0\n.names PA MD pamd\n11 0\n.names MD DE mdde\n11 0\n.names MD DC mddc\n11 0\n.names NC SC ncsc\n11 0\n.names VT NH vtnh\n11 0\n.names VT MA vtma\n11 0\n.names VT NY vtny\n11 0\n.names NY MA nyma\n11 0\n.names NY CT nyct\n11 0\n.names NY NJ nynj\n11 0\n.names NJ DE njde\n11 0\n.names NH ME nhme\n11 0\n.names NH MA nhma\n11 0\n.names MA RI mari\n11 0\n.names MA CT mact\n11 0\n.names CT RI ctri\n11 0\n.names caor canv caaz waor waid orid ornv nvid nvut nvaz idmt idwy w0\n111111111111 1\n.names idut utwy utco utaz aznm mtnd mtsd mtwy wysd wyne wyco cone w1\n111111111111 1\n.names coks cook conm nmok nmtx ndmn ndsd sdmn sdia sdne neia nemo w2\n111111111111 1\n.names neks ksmo ksok okmo okar oktx txar txla mnwi mnia iawi iail w3\n111111111111 1\n.names iamo moil moky motn moar artn arms arla lams wimi wiil ilin ilky w4\n1111111111111 1\n.names mstn msal mioh miin inoh inky kyoh kywv kyva kytn tnva tnnc w5\n111111111111 1\n.names tnga tnal alga alfl ohpa ohwv wvpa wvmd wvva vamd vadc vanc w6\n111111111111 1\n.names ganc gasc gafl pany panj pade pamd mdde mddc ncsc vtnh vtma vtny w7\n1111111111111 1\n.names nyma nyct nynj njde nhme nhma mari mact ctri w8\n1111111111 1\n.names w0 w1 w2 w3 w4 w5 w6 w7 w8 indep\n111111111 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/adj49.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -ordering dfs -reordering cogroup -drop -char2vect -cofest ./nanotrav/adj49.blif\n# CUDD Version 3.0.0\nOrder before final reordering\nCA OR NV AZ WA ID UT MT \nWY CO NM ND SD NE KS OK \nTX MN IA MO AR LA WI IL \nKY TN MS MI IN AL OH WV \nVA NC GA FL PA MD DC SC \nNY NJ DE VT NH MA CT ME \nRI \nNumber of inputs = 49\nBDD reordering with converging group sifting: from 431 to ... 338 nodes in 0.01 sec\nNew order\nID OR WA NV AZ CA UT NM \nWY MT CO SD MN ND NE IA \nKS MO TX OK LA WI AR MS \nKY MI IN IL AL TN FL NC \nSC GA WV OH MD DC VA PA \nNJ DE NY RI CT NH ME VT \nMA \nTesting char-to-vect\n*** indep ***\nf: 338 nodes 1 leaves 2.11955e+08 minterms\nVector Size: 49 components 1171 nodes\nv[0]: 6 nodes 1 leaves 8.79609e+13 minterms\nv[1]: 3 nodes 1 leaves 1.40737e+14 minterms\nv[2]: 4 nodes 1 leaves 7.03687e+13 minterms\nv[3]: 5 nodes 1 leaves 2.46291e+14 minterms\nv[4]: 4 nodes 1 leaves 7.03687e+13 minterms\nv[5]: 2 nodes 1 leaves 2.81475e+14 minterms\nv[6]: 6 nodes 1 leaves 5.27766e+13 minterms\nv[7]: 8 nodes 1 leaves 8.35629e+13 minterms\nv[8]: 7 nodes 1 leaves 1.14349e+14 minterms\nv[9]: 11 nodes 1 leaves 1.47335e+14 minterms\nv[10]: 6 nodes 1 leaves 1.5833e+14 minterms\nv[11]: 11 nodes 1 leaves 7.4217e+13 minterms\nv[12]: 9 nodes 1 leaves 1.82519e+14 minterms\nv[13]: 17 nodes 1 leaves 9.09846e+13 minterms\nv[14]: 18 nodes 1 leaves 1.62315e+14 minterms\nv[15]: 26 nodes 1 leaves 2.79388e+13 minterms\nv[16]: 7 nodes 1 leaves 2.0231e+14 minterms\nv[17]: 10 nodes 1 leaves 1.90216e+14 minterms\nv[18]: 21 nodes 1 leaves 7.23616e+13 minterms\nv[19]: 26 nodes 1 leaves 1.31478e+14 minterms\nv[20]: 43 nodes 1 leaves 6.3558e+13 minterms\nv[21]: 8 nodes 1 leaves 1.8032e+14 minterms\nv[22]: 22 nodes 1 leaves 1.50186e+14 minterms\nv[23]: 33 nodes 1 leaves 4.71217e+13 minterms\nv[24]: 27 nodes 1 leaves 2.15736e+14 minterms\nv[25]: 48 nodes 1 leaves 3.18125e+13 minterms\nv[26]: 46 nodes 1 leaves 1.59536e+14 minterms\nv[27]: 23 nodes 1 leaves 2.06382e+14 minterms\nv[28]: 34 nodes 1 leaves 1.10876e+14 minterms\nv[29]: 47 nodes 1 leaves 2.01707e+14 minterms\nv[30]: 36 nodes 1 leaves 2.77189e+13 minterms\nv[31]: 28 nodes 1 leaves 1.73607e+14 minterms\nv[32]: 54 nodes 1 leaves 9.85629e+12 minterms\nv[33]: 49 nodes 1 leaves 2.65569e+14 minterms\nv[34]: 56 nodes 1 leaves 2.05894e+13 minterms\nv[35]: 48 nodes 1 leaves 1.80621e+14 minterms\nv[36]: 39 nodes 1 leaves 9.0406e+13 minterms\nv[37]: 29 nodes 1 leaves 1.94672e+14 minterms\nv[38]: 30 nodes 1 leaves 1.84139e+14 minterms\nv[39]: 50 nodes 1 leaves 1.48691e+14 minterms\nv[40]: 41 nodes 1 leaves 1.18136e+14 minterms\nv[41]: 40 nodes 1 leaves 2.36272e+14 minterms\nv[42]: 42 nodes 1 leaves 6.94681e+13 minterms\nv[43]: 43 nodes 1 leaves 1.11203e+14 minterms\nv[44]: 2 nodes 1 leaves 2.81475e+14 minterms\nv[45]: 46 nodes 1 leaves 1.39004e+13 minterms\nv[46]: 43 nodes 1 leaves 1.11203e+14 minterms\nv[47]: 3 nodes 1 leaves 1.40737e+14 minterms\nv[48]: 2 nodes 1 leaves 2.81475e+14 minterms\nTesting BDD cofactor estimation algorithms\nTEST-COF:: indep (49 vars): 338 nodes 1 leaves 2.11955e+08 minterms\nT-c   : 13145\nT-c E : 13619 42\nT-c S : 14592 131\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000000\nMaximum number of variable swaps per reordering: 1000000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 776\n**** CUDD non-modifiable parameters ****\nMemory in use: 3791664\nPeak number of nodes: 17374\nPeak number of live nodes: 3444\nNumber of BDD variables: 49\nNumber of ZDD variables: 0\nNumber of cache entries: 32768\nNumber of cache look-ups: 51760\nNumber of cache hits: 17171\nNumber of cache insertions: 25262\nNumber of cache collisions: 6513\nNumber of cache deletions: 1736\nCache used slots = 54.25% (expected 51.16%)\nSoft limit for cache size: 51200\nNumber of buckets in unique table: 12800\nUsed buckets in unique table: 56.12% (expected 55.54%)\nNumber of BDD and ADD nodes: 16471\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 16082\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 18850\nTotal number of nodes reclaimed: 1757\nGarbage collections so far: 1\nTime for garbage collection: 0.00 sec\nReorderings so far: 1\nTime for reordering: 0.01 sec\nFinal size: 338\ntotal time = 0.01 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  6700K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 1054\nSwaps = 0\nInput blocks = 8\nOutput blocks = 8\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/bnet.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief Functions to read in a boolean network.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"cuddInt.h\"\n#include \"bnet.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define MAXLENGTH 131072\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\nstatic\tchar\tBuffLine[MAXLENGTH];\nstatic\tchar\t*CurPos;\nstatic\tint\tnewNameNumber = 0;\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic char * readString (FILE *fp);\nstatic char ** readList (FILE *fp, int *n);\nstatic void printList (char **list, int n);\nstatic char ** bnetGenerateNewNames (st_table *hash, int n);\nstatic int bnetDumpReencodingLogic (DdManager *dd, char *mname, int noutputs, DdNode **outputs, char **inames, char **altnames, char **onames, FILE *fp);\n#if 0\nstatic int bnetBlifXnorTable (FILE *fp, int n);\n#endif\nstatic int bnetBlifWriteReencode (DdManager *dd, char *mname, char **inames, char **altnames, int *support, FILE *fp);\nstatic int * bnetFindVectorSupport (DdManager *dd, DdNode **list, int n);\nstatic int buildExorBDD (DdManager *dd, BnetNode *nd, st_table *hash, int params, int nodrop);\nstatic int buildMuxBDD (DdManager * dd, BnetNode * nd, st_table * hash, int  params, int  nodrop);\nstatic int bnetSetLevel (BnetNetwork *net);\nstatic int bnetLevelDFS (BnetNetwork *net, BnetNode *node);\nstatic BnetNode ** bnetOrderRoots (BnetNetwork *net, int *nroots);\nstatic int bnetLevelCompare (BnetNode **x, BnetNode **y);\nstatic int bnetDfsOrder (DdManager *dd, BnetNetwork *net, BnetNode *node);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Reads boolean network from blif file.\n\n  @details A very restricted subset of blif is supported. Specifically:\n  <ul>\n  <li> The only directives recognized are:\n    <ul>\n    <li> .model\n    <li> .inputs\n    <li> .outputs\n    <li> .latch\n    <li> .names\n    <li> .exdc\n    <li> .wire_load_slope\n    <li> .end\n    </ul>\n  <li> Latches must have an initial values and no other parameters\n       specified.\n  <li> Lines must not exceed MAXLENGTH-1 characters, and individual names must\n       not exceed 1023 characters.\n  </ul>\n  Caveat emptor: There may be other limitations as well. One should\n  check the syntax of the blif file with some other tool before relying\n  on this parser.\n\n  @return a pointer to the network if successful; NULL otherwise.\n  \n  @sideeffect None\n\n  @see Bnet_PrintNetwork Bnet_FreeNetwork\n\n*/\nBnetNetwork *\nBnet_ReadNetwork(\n  FILE * fp /**< pointer to the blif file */,\n  int  pr /**< verbosity level */)\n{\n    char *savestring;\n    char **list;\n    int i, j, n;\n    BnetNetwork *net;\n    BnetNode *newnode;\n    BnetNode *lastnode = NULL;\n    BnetTabline *newline;\n    BnetTabline *lastline;\n    char ***latches = NULL;\n    int maxlatches = 0;\n    int exdc = 0;\n    BnetNode\t*node;\n    int\tcount;\n\n    /* Allocate network object and initialize symbol table. */\n    net = ALLOC(BnetNetwork,1);\n    if (net == NULL) goto failure;\n    memset((char *) net, 0, sizeof(BnetNetwork));\n    net->hash = st_init_table((st_compare_t) strcmp, st_strhash);\n    if (net->hash == NULL) goto failure;\n\n    savestring = readString(fp);\n    if (savestring == NULL) goto failure;\n    net->nlatches = 0;\n    while (strcmp(savestring, \".model\") == 0 ||\n\tstrcmp(savestring, \".inputs\") == 0 ||\n\tstrcmp(savestring, \".outputs\") == 0 ||\n\tstrcmp(savestring, \".latch\") == 0 ||\n\tstrcmp(savestring, \".wire_load_slope\") == 0 ||\n\tstrcmp(savestring, \".exdc\") == 0 ||\n\tstrcmp(savestring, \".names\") == 0 || strcmp(savestring,\".end\") == 0) {\n\tif (strcmp(savestring, \".model\") == 0) {\n\t    /* Read .model directive. */\n\t    FREE(savestring);\n\t    /* Read network name. */\n\t    savestring = readString(fp);\n\t    if (savestring == NULL) goto failure;\n\t    if (savestring[0] == '.') {\n\t\tnet->name = ALLOC(char,  1);\n\t\tif (net->name == NULL) goto failure;\n                net->name[0] = '\\0';\n\t    } else {\n\t\tnet->name = savestring;\n\t    }\n\t} else if (strcmp(savestring, \".inputs\") == 0) {\n\t    /* Read .inputs directive. */\n\t    FREE(savestring);\n\t    /* Read input names. */\n\t    list = readList(fp,&n);\n\t    if (list == NULL) goto failure;\n\t    if (pr > 2) printList(list,n);\n\t    /* Expect at least one input. */\n\t    if (n < 1) {\n\t\t(void) fprintf(stdout,\"Empty input list.\\n\");\n\t\tgoto failure;\n\t    }\n\t    if (exdc) {\n\t\tfor (i = 0; i < n; i++)\n\t\t    FREE(list[i]);\n\t\tFREE(list);\n\t\tsavestring = readString(fp);\n\t\tif (savestring == NULL) goto failure;\n\t\tcontinue;\n\t    }\n\t    if (net->ninputs) {\n\t\tnet->inputs = REALLOC(char *, net->inputs,\n\t\t    (net->ninputs + n) * sizeof(char *));\n\t\tfor (i = 0; i < n; i++)\n\t\t    net->inputs[net->ninputs + i] = list[i];\n\t    }\n\t    else\n\t\tnet->inputs = list;\n\t    /* Create a node for each primary input. */\n\t    for (i = 0; i < n; i++) {\n\t\tnewnode = ALLOC(BnetNode,1);\n\t\tmemset((char *) newnode, 0, sizeof(BnetNode));\n\t\tif (newnode == NULL) goto failure;\n\t\tnewnode->name = list[i];\n\t\tnewnode->inputs = NULL;\n\t\tnewnode->type = BNET_INPUT_NODE;\n\t\tnewnode->active = FALSE;\n\t\tnewnode->nfo = 0;\n\t\tnewnode->ninp = 0;\n\t\tnewnode->f = NULL;\n\t\tnewnode->polarity = 0;\n\t\tnewnode->dd = NULL;\n\t\tnewnode->next = NULL;\n\t\tif (lastnode == NULL) {\n\t\t    net->nodes = newnode;\n\t\t} else {\n\t\t    lastnode->next = newnode;\n\t\t}\n\t\tlastnode = newnode;\n\t    }\n\t    net->npis += n;\n\t    net->ninputs += n;\n\t} else if (strcmp(savestring, \".outputs\") == 0) {\n\t    /* Read .outputs directive. We do not create nodes for the primary\n\t    ** outputs, because the nodes will be created when the same names\n\t    ** appear as outputs of some gates.\n\t    */\n\t    FREE(savestring);\n\t    /* Read output names. */\n\t    list = readList(fp,&n);\n\t    if (list == NULL) goto failure;\n\t    if (pr > 2) printList(list,n);\n\t    if (n < 1) {\n\t\t(void) fprintf(stdout,\"Empty .outputs list.\\n\");\n\t\tgoto failure;\n\t    }\n\t    if (exdc) {\n\t\tfor (i = 0; i < n; i++)\n\t\t    FREE(list[i]);\n\t\tFREE(list);\n\t\tsavestring = readString(fp);\n\t\tif (savestring == NULL) goto failure;\n\t\tcontinue;\n\t    }\n\t    if (net->noutputs) {\n\t\tnet->outputs = REALLOC(char *, net->outputs,\n\t\t    (net->noutputs + n) * sizeof(char *));\n\t\tfor (i = 0; i < n; i++)\n\t\t    net->outputs[net->noutputs + i] = list[i];\n\t    } else {\n\t\tnet->outputs = list;\n\t    }\n\t    net->npos += n;\n\t    net->noutputs += n;\n\t} else if (strcmp(savestring,\".wire_load_slope\") == 0) {\n\t    FREE(savestring);\n\t    savestring = readString(fp);\n\t    net->slope = savestring;\n\t} else if (strcmp(savestring,\".latch\") == 0) {\n\t    FREE(savestring);\n\t    newnode = ALLOC(BnetNode,1);\n\t    if (newnode == NULL) goto failure;\n\t    memset((char *) newnode, 0, sizeof(BnetNode));\n\t    newnode->type = BNET_PRESENT_STATE_NODE;\n\t    list = readList(fp,&n);\n\t    if (list == NULL) goto failure;\n\t    if (pr > 2) printList(list,n);\n\t    /* Expect three names. */\n\t    if (n != 3) {\n\t\t(void) fprintf(stdout,\n\t\t\t       \".latch not followed by three tokens.\\n\");\n\t\tgoto failure;\n\t    }\n\t    newnode->name = list[1];\n\t    newnode->inputs = NULL;\n\t    newnode->ninp = 0;\n\t    newnode->f = NULL;\n\t    newnode->active = FALSE;\n\t    newnode->nfo = 0;\n\t    newnode->polarity = 0;\n\t    newnode->dd = NULL;\n\t    newnode->next = NULL;\n\t    if (lastnode == NULL) {\n\t\tnet->nodes = newnode;\n\t    } else {\n\t\tlastnode->next = newnode;\n\t    }\n\t    lastnode = newnode;\n\t    /* Add next state variable to list. */\n\t    if (maxlatches == 0) {\n\t\tmaxlatches = 20;\n\t\tlatches = ALLOC(char **,maxlatches);\n\t    } else if (maxlatches <= net->nlatches) {\n\t\tmaxlatches += 20;\n\t\tlatches = REALLOC(char **,latches,maxlatches);\n\t    }\n\t    latches[net->nlatches] = list;\n\t    net->nlatches++;\n\t    savestring = readString(fp);\n\t    if (savestring == NULL) goto failure;\n\t} else if (strcmp(savestring,\".names\") == 0) {\n\t    FREE(savestring);\n\t    newnode = ALLOC(BnetNode,1);\n\t    memset((char *) newnode, 0, sizeof(BnetNode));\n\t    if (newnode == NULL) goto failure;\n\t    list = readList(fp,&n);\n\t    if (list == NULL) goto failure;\n\t    if (pr > 2) printList(list,n);\n\t    /* Expect at least one name (the node output). */\n\t    if (n < 1) {\n\t\t(void) fprintf(stdout,\"Missing output name.\\n\");\n\t\tgoto failure;\n\t    }\n\t    newnode->name = list[n-1];\n\t    newnode->inputs = list;\n\t    newnode->ninp = n-1;\n\t    newnode->active = FALSE;\n\t    newnode->nfo = 0;\n\t    newnode->polarity = 0;\n\t    if (newnode->ninp > 0) {\n\t\tnewnode->type = BNET_INTERNAL_NODE;\n\t\tfor (i = 0; i < net->noutputs; i++) {\n\t\t    if (strcmp(net->outputs[i], newnode->name) == 0) {\n\t\t\tnewnode->type = BNET_OUTPUT_NODE;\n\t\t\tbreak;\n\t\t    }\n\t\t}\n\t    } else {\n\t\tnewnode->type = BNET_CONSTANT_NODE;\n\t    }\n\t    newnode->dd = NULL;\n\t    newnode->next = NULL;\n\t    if (lastnode == NULL) {\n\t\tnet->nodes = newnode;\n\t    } else {\n\t\tlastnode->next = newnode;\n\t    }\n\t    lastnode = newnode;\n\t    /* Read node function. */\n\t    newnode->f = NULL;\n\t    if (exdc) {\n\t\tnewnode->exdc_flag = 1;\n\t\tnode = net->nodes;\n\t\twhile (node) {\n\t\t    if (node->type == BNET_OUTPUT_NODE &&\n\t\t\tstrcmp(node->name, newnode->name) == 0) {\n\t\t\tnode->exdc = newnode;\n\t\t\tbreak;\n\t\t    }\n\t\t    node = node->next;\n\t\t}\n\t    }\n\t    savestring = readString(fp);\n\t    if (savestring == NULL) goto failure;\n\t    lastline = NULL;\n\t    while (savestring[0] != '.') {\n\t\t/* Reading a table line. */\n\t\tnewline = ALLOC(BnetTabline,1);\n\t\tif (newline == NULL) goto failure;\n\t\tnewline->next = NULL;\n\t\tif (lastline == NULL) {\n\t\t    newnode->f = newline;\n\t\t} else {\n\t\t    lastline->next = newline;\n\t\t}\n\t\tlastline = newline;\n\t\tif (newnode->type == BNET_INTERNAL_NODE ||\n\t\t    newnode->type == BNET_OUTPUT_NODE) {\n\t\t    newline->values = savestring;\n\t\t    /* Read output 1 or 0. */\n\t\t    savestring = readString(fp);\n\t\t    if (savestring == NULL) goto failure;\n\t\t} else {\n\t\t    newline->values = NULL;\n\t\t}\n\t\tif (savestring[0] == '0') newnode->polarity = 1;\n\t\tFREE(savestring);\n\t\tsavestring = readString(fp);\n\t\tif (savestring == NULL) goto failure;\n\t    }\n\t} else if (strcmp(savestring,\".exdc\") == 0) {\n\t    FREE(savestring);\n\t    exdc = 1;\n\t} else if (strcmp(savestring,\".end\") == 0) {\n\t    FREE(savestring);\n\t    break;\n\t}\n\tif ((!savestring) || savestring[0] != '.')\n\t    savestring = readString(fp);\n\tif (savestring == NULL) goto failure;\n    }\n\n    /* Put nodes in symbol table. */\n    newnode = net->nodes;\n    while (newnode != NULL) {\n\tint retval = st_insert(net->hash,newnode->name,(char *) newnode);\n\tif (retval == ST_OUT_OF_MEM) {\n\t    goto failure;\n\t} else if (retval == 1) {\n\t    printf(\"Error: Multiple drivers for node %s\\n\", newnode->name);\n\t    goto failure;\n\t} else {\n\t    if (pr > 2) printf(\"Inserted %s\\n\",newnode->name);\n\t}\n\tnewnode = newnode->next;\n    }\n\n    if (latches) {\n\tnet->latches = latches;\n\n\tcount = 0;\n\tnet->outputs = REALLOC(char *, net->outputs,\n\t    (net->noutputs + net->nlatches) * sizeof(char *));\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    for (j = 0; j < net->noutputs; j++) {\n\t\tif (strcmp(latches[i][0], net->outputs[j]) == 0)\n\t\t    break;\n\t    }\n\t    if (j < net->noutputs)\n\t\tcontinue;\n\t    savestring = ALLOC(char, strlen(latches[i][0]) + 1);\n\t    strcpy(savestring, latches[i][0]);\n\t    net->outputs[net->noutputs + count] = savestring;\n\t    count++;\n\t    if (st_lookup(net->hash, savestring, (void **) &node)) {\n\t\tif (node->type == BNET_INTERNAL_NODE) {\n\t\t    node->type = BNET_OUTPUT_NODE;\n\t\t}\n\t    }\n\t}\n\tnet->noutputs += count;\n\n\tnet->inputs = REALLOC(char *, net->inputs,\n\t    (net->ninputs + net->nlatches) * sizeof(char *));\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    savestring = ALLOC(char, strlen(latches[i][1]) + 1);\n\t    strcpy(savestring, latches[i][1]);\n\t    net->inputs[net->ninputs + i] = savestring;\n\t}\n\tnet->ninputs += net->nlatches;\n    }\n\n    /* Compute fanout counts. For each node in the linked list, fetch\n    ** all its fanins using the symbol table, and increment the fanout of\n    ** each fanin.\n    */\n    newnode = net->nodes;\n    while (newnode != NULL) {\n\tBnetNode *auxnd;\n\tfor (i = 0; i < newnode->ninp; i++) {\n\t    if (!st_lookup(net->hash,newnode->inputs[i],(void **)&auxnd)) {\n\t\t(void) fprintf(stdout,\"%s not driven\\n\", newnode->inputs[i]);\n\t\tgoto failure;\n\t    }\n\t    auxnd->nfo++;\n\t}\n\tnewnode = newnode->next;\n    }\n\n    if (!bnetSetLevel(net)) goto failure;\n\n    return(net);\n\nfailure:\n    /* Here we should clean up the mess. */\n    (void) fprintf(stdout,\"Error in reading network from file.\\n\");\n    return(NULL);\n\n} /* end of Bnet_ReadNetwork */\n\n\n/**\n  @brief Prints to stdout a boolean network created by Bnet_ReadNetwork.\n\n  @details Uses the blif format; this way, one can verify the\n  equivalence of the input and the output with, say, sis.\n\n  @sideeffect None\n\n  @see Bnet_ReadNetwork\n\n*/\nvoid\nBnet_PrintNetwork(\n  BnetNetwork * net /**< boolean network */)\n{\n    BnetNode *nd;\n    BnetTabline *tl;\n    int i;\n\n    if (net == NULL) return;\n\n    (void) fprintf(stdout,\".model %s\\n\", net->name);\n    (void) fprintf(stdout,\".inputs\");\n    printList(net->inputs,net->npis);\n    (void) fprintf(stdout,\".outputs\");\n    printList(net->outputs,net->npos);\n    for (i = 0; i < net->nlatches; i++) {\n\t(void) fprintf(stdout,\".latch\");\n\tprintList(net->latches[i],3);\n    }\n    nd = net->nodes;\n    while (nd != NULL) {\n\tif (nd->type != BNET_INPUT_NODE && nd->type != BNET_PRESENT_STATE_NODE) {\n\t    (void) fprintf(stdout,\".names\");\n\t    for (i = 0; i < nd->ninp; i++) {\n\t\t(void) fprintf(stdout,\" %s\",nd->inputs[i]);\n\t    }\n\t    (void) fprintf(stdout,\" %s\\n\",nd->name);\n\t    tl = nd->f;\n\t    while (tl != NULL) {\n\t\tif (tl->values != NULL) {\n\t\t    (void) fprintf(stdout,\"%s %d\\n\",tl->values,\n\t\t    1 - nd->polarity);\n\t\t} else {\n\t\t    (void) fprintf(stdout,\"%d\\n\", 1 - nd->polarity);\n\t\t}\n\t\ttl = tl->next;\n\t    }\n\t}\n\tnd = nd->next;\n    }\n    (void) fprintf(stdout,\".end\\n\");\n\n} /* end of Bnet_PrintNetwork */\n\n\n/**\n  @brief Frees a boolean network created by Bnet_ReadNetwork.\n\n  @sideeffect None\n\n  @see Bnet_ReadNetwork\n\n*/\nvoid\nBnet_FreeNetwork(\n  BnetNetwork * net)\n{\n    BnetNode *node, *nextnode;\n    BnetTabline *line, *nextline;\n    int i;\n\n    FREE(net->name);\n    /* The input name strings are already pointed by the input nodes.\n    ** Here we only need to free the latch names and the array that\n    ** points to them.\n    */\n    for (i = 0; i < net->nlatches; i++) {\n\tFREE(net->inputs[net->npis + i]);\n    }\n    FREE(net->inputs);\n    /* Free the output name strings and then the array pointing to them.  */\n    for (i = 0; i < net->noutputs; i++) {\n\tFREE(net->outputs[i]);\n    }\n    FREE(net->outputs);\n\n    for (i = 0; i < net->nlatches; i++) {\n\tFREE(net->latches[i][0]);\n\tFREE(net->latches[i][1]);\n\tFREE(net->latches[i][2]);\n\tFREE(net->latches[i]);\n    }\n    if (net->nlatches) FREE(net->latches);\n    node = net->nodes;\n    while (node != NULL) {\n\tnextnode = node->next;\n\tif (node->type != BNET_PRESENT_STATE_NODE)\n\t    FREE(node->name);\n\tfor (i = 0; i < node->ninp; i++) {\n\t    FREE(node->inputs[i]);\n\t}\n\tif (node->inputs != NULL) {\n\t    FREE(node->inputs);\n\t}\n\t/* Free the function table. */\n\tline = node->f;\n\twhile (line != NULL) {\n\t    nextline = line->next;\n\t    FREE(line->values);\n\t    FREE(line);\n\t    line = nextline;\n\t}\n\tFREE(node);\n\tnode = nextnode;\n    }\n    st_free_table(net->hash);\n    if (net->slope != NULL) FREE(net->slope);\n    FREE(net);\n\n} /* end of Bnet_FreeNetwork */\n\n\n/**\n  @brief Builds the %BDD for the function of a node.\n\n  @details Builds the %BDD for the function of a node and stores a\n  pointer to it in the dd field of the node itself. The reference count\n  of the %BDD is incremented. If params is BNET_LOCAL_DD, then the %BDD is\n  built in terms of the local inputs to the node; otherwise, if params\n  is BNET_GLOBAL_DD, the %BDD is built in terms of the network primary\n  inputs. To build the global %BDD of a node, the BDDs for its local\n  inputs must exist. If that is not the case, Bnet_BuildNodeBDD\n  recursively builds them. Likewise, to create the local %BDD for a node,\n  the local inputs must have variables assigned to them. If that is not\n  the case, Bnet_BuildNodeBDD recursively assigns variables to nodes.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect Sets the dd field of the node.\n\n*/\nint\nBnet_BuildNodeBDD(\n  DdManager * dd /**< %DD manager */,\n  BnetNode * nd /**< node of the boolean network */,\n  st_table * hash /**< symbol table of the boolean network */,\n  int  params /**< type of %DD to be built */,\n  int  nodrop /**< retain the intermediate node DDs until the end */)\n{\n    DdNode *func;\n    BnetNode *auxnd;\n    DdNode *tmp;\n    DdNode *prod, *var;\n    BnetTabline *line;\n    int i;\n\n    if (nd->dd != NULL) return(1);\n\n    if (nd->type == BNET_CONSTANT_NODE) {\n\tif (nd->f == NULL) { /* constant 0 */\n\t    func = Cudd_ReadLogicZero(dd);\n\t} else { /* either constant depending on the polarity */\n\t    func = Cudd_ReadOne(dd);\n\t}\n\tCudd_Ref(func);\n    } else if (nd->type == BNET_INPUT_NODE ||\n\t       nd->type == BNET_PRESENT_STATE_NODE) {\n\tif (nd->active == TRUE) { /* a variable is already associated: use it */\n\t    func = Cudd_ReadVars(dd,nd->var);\n\t    if (func == NULL) goto failure;\n\t} else { /* no variable associated: get a new one */\n\t    func = Cudd_bddNewVar(dd);\n\t    if (func == NULL) goto failure;\n\t    nd->var = func->index;\n\t    nd->active = TRUE;\n\t}\n\tCudd_Ref(func);\n    } else if (buildExorBDD(dd,nd,hash,params,nodrop)) {\n\tfunc = nd->dd;\n    } else if (buildMuxBDD(dd,nd,hash,params,nodrop)) {\n\tfunc = nd->dd;\n    } else { /* type == BNET_INTERNAL_NODE or BNET_OUTPUT_NODE */\n\t/* Initialize the sum to logical 0. */\n\tfunc = Cudd_ReadLogicZero(dd);\n\tCudd_Ref(func);\n\n\t/* Build a term for each line of the table and add it to the\n\t** accumulator (func).\n\t*/\n\tline = nd->f;\n\twhile (line != NULL) {\n#ifdef BNET_DEBUG\n\t    (void) fprintf(stdout,\"line = %s\\n\", line->values);\n#endif\n\t    /* Initialize the product to logical 1. */\n\t    prod = Cudd_ReadOne(dd);\n\t    Cudd_Ref(prod);\n\t    /* Scan the table line. */\n\t    for (i = 0; i < nd->ninp; i++) {\n\t\tif (line->values[i] == '-') continue;\n\t\tif (!st_lookup(hash,nd->inputs[i],(void **)&auxnd)) {\n\t\t    goto failure;\n\t\t}\n\t\tif (params == BNET_LOCAL_DD) {\n\t\t    if (auxnd->active == FALSE) {\n\t\t\tif (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\t\t    goto failure;\n\t\t\t}\n\t\t    }\n\t\t    var = Cudd_ReadVars(dd,auxnd->var);\n\t\t    if (var == NULL) goto failure;\n\t\t    Cudd_Ref(var);\n\t\t    if (line->values[i] == '0') {\n\t\t\tvar = Cudd_Not(var);\n\t\t    }\n\t\t} else { /* params == BNET_GLOBAL_DD */\n\t\t    if (auxnd->dd == NULL) {\n\t\t\tif (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\t\t    goto failure;\n\t\t\t}\n\t\t    }\n\t\t    if (line->values[i] == '1') {\n\t\t\tvar = auxnd->dd;\n\t\t    } else { /* line->values[i] == '0' */\n\t\t\tvar = Cudd_Not(auxnd->dd);\n\t\t    }\n\t\t}\n\t\ttmp = Cudd_bddAnd(dd,prod,var);\n\t\tif (tmp == NULL) goto failure;\n\t\tCudd_Ref(tmp);\n\t\tCudd_IterDerefBdd(dd,prod);\n\t\tif (params == BNET_LOCAL_DD) {\n\t\t    Cudd_IterDerefBdd(dd,var);\n\t\t}\n\t\tprod = tmp;\n\t    }\n\t    tmp = Cudd_bddOr(dd,func,prod);\n\t    if (tmp == NULL) goto failure;\n\t    Cudd_Ref(tmp);\n\t    Cudd_IterDerefBdd(dd,func);\n\t    Cudd_IterDerefBdd(dd,prod);\n\t    func = tmp;\n\t    line = line->next;\n\t}\n\t/* Associate a variable to this node if local BDDs are being\n\t** built. This is done at the end, so that the primary inputs tend\n\t** to get lower indices.\n\t*/\n\tif (params == BNET_LOCAL_DD && nd->active == FALSE) {\n\t    DdNode *auxfunc = Cudd_bddNewVar(dd);\n\t    if (auxfunc == NULL) goto failure;\n\t    Cudd_Ref(auxfunc);\n\t    nd->var = auxfunc->index;\n\t    nd->active = TRUE;\n\t    Cudd_IterDerefBdd(dd,auxfunc);\n\t}\n    }\n    if (nd->polarity == 1) {\n\tnd->dd = Cudd_Not(func);\n    } else {\n\tnd->dd = func;\n    }\n\n    if (params == BNET_GLOBAL_DD && nodrop == FALSE) {\n\t/* Decrease counters for all faninis.\n\t** When count reaches 0, the DD is freed.\n\t*/\n\tfor (i = 0; i < nd->ninp; i++) {\n\t    if (!st_lookup(hash,nd->inputs[i],(void **)&auxnd)) {\n\t\tgoto failure;\n\t    }\n\t    auxnd->count--;\n\t    if (auxnd->count == 0) {\n\t\tCudd_IterDerefBdd(dd,auxnd->dd);\n\t\tif (auxnd->type == BNET_INTERNAL_NODE ||\n\t\t    auxnd->type == BNET_CONSTANT_NODE) auxnd->dd = NULL;\n\t    }\n\t}\n    }\n    return(1);\n\nfailure:\n    /* Here we should clean up the mess. */\n    return(0);\n\n} /* end of Bnet_BuildNodeBDD */\n\n\n/**\n  @brief Orders the %BDD variables by DFS.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect Uses the visited flags of the nodes.\n\n*/\nint\nBnet_DfsVariableOrder(\n  DdManager * dd,\n  BnetNetwork * net)\n{\n    BnetNode **roots;\n    BnetNode *node;\n    int nroots;\n    int i;\n\n    roots = bnetOrderRoots(net,&nroots);\n    if (roots == NULL) return(0);\n    for (i = 0; i < nroots; i++) {\n\tif (!bnetDfsOrder(dd,net,roots[i])) {\n\t    FREE(roots);\n\t    return(0);\n\t}\n    }\n    /* Clear visited flags. */\n    node = net->nodes;\n    while (node != NULL) {\n\tnode->visited = 0;\n\tnode = node->next;\n    }\n    FREE(roots);\n    return(1);\n\n} /* end of Bnet_DfsVariableOrder */\n\n\n/**\n  @brief Writes the network BDDs to a file in dot, blif, or daVinci\n  format.\n\n  @details If \"-\" is passed as file name, the BDDs are dumped to the\n  standard output.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nBnet_bddDump(\n  DdManager * dd /**< %DD manager */,\n  BnetNetwork * network /**< network whose BDDs should be dumped */,\n  char * dfile /**< file name */,\n  int  dumpFmt /**< 0 -> dot */,\n  int  reencoded /**< whether variables have been reencoded */)\n{\n    int noutputs;\n    FILE *dfp = NULL;\n    DdNode **outputs = NULL;\n    char **inames = NULL;\n    char **onames = NULL;\n    char **altnames = NULL;\n    BnetNode *node;\n    int i;\n    int retval = 0; /* 0 -> failure; 1 -> success */\n\n    /* Open dump file. */\n    if (strcmp(dfile, \"-\") == 0) {\n\tdfp = stdout;\n    } else {\n\tdfp = fopen(dfile,\"w\");\n    }\n    if (dfp == NULL) goto endgame;\n\n    /* Initialize data structures. */\n    noutputs = network->noutputs;\n    outputs = ALLOC(DdNode *,noutputs);\n    if (outputs == NULL) goto endgame;\n    onames = ALLOC(char *,noutputs);\n    if (onames == NULL) goto endgame;\n    inames = ALLOC(char *,Cudd_ReadSize(dd));\n    if (inames == NULL) goto endgame;\n\n    /* Find outputs and their names. */\n    for (i = 0; i < network->nlatches; i++) {\n\tonames[i] = network->latches[i][0];\n\tif (!st_lookup(network->hash,network->latches[i][0],(void **)&node)) {\n\t    goto endgame;\n\t}\n\toutputs[i] = node->dd;\n    }\n    for (i = 0; i < network->npos; i++) {\n\tonames[i + network->nlatches] = network->outputs[i];\n\tif (!st_lookup(network->hash,network->outputs[i],(void **)&node)) {\n\t    goto endgame;\n\t}\n\toutputs[i + network->nlatches] = node->dd;\n    }\n\n    /* Find the input names. */\n    for (i = 0; i < network->ninputs; i++) {\n\tif (!st_lookup(network->hash,network->inputs[i],(void **)&node)) {\n\t    goto endgame;\n\t}\n\tinames[node->var] = network->inputs[i];\n    }\n    for (i = 0; i < network->nlatches; i++) {\n\tif (!st_lookup(network->hash,network->latches[i][1],(void **)&node)) {\n\t    goto endgame;\n\t}\n\tinames[node->var] = network->latches[i][1];\n    }\n\n    if (reencoded == 1 && dumpFmt == 1) {\n\taltnames = bnetGenerateNewNames(network->hash,network->ninputs);\n\tif (altnames == NULL) {\n\t    retval = 0;\n\t    goto endgame;\n\t}\n\tretval = bnetDumpReencodingLogic(dd,network->name,noutputs,outputs,\n\t\t inames,altnames,onames,dfp);\n\tfor (i = 0; i < network->ninputs; i++) {\n\t    FREE(altnames[i]);\n\t}\n\tFREE(altnames);\n\tif (retval == 0) goto endgame;\n    }\n\n    /* Dump the BDDs. */\n    if (dumpFmt == 1) {\n\tretval = Cudd_DumpBlif(dd,noutputs,outputs,\n\t\t\t       (char const * const *) inames,\n\t\t\t       (char const * const *) onames,\n\t\t\t       network->name,dfp,0);\n    } else if (dumpFmt == 2) {\n\tretval = Cudd_DumpDaVinci(dd,noutputs,outputs,\n\t\t\t\t  (char const * const *) inames,\n\t\t\t\t  (char const * const *) onames,dfp);\n    } else if (dumpFmt == 3) {\n\tretval = Cudd_DumpDDcal(dd,noutputs,outputs,\n\t\t\t\t(char const * const *) inames,\n\t\t\t\t(char const * const *) onames,dfp);\n    } else if (dumpFmt == 4) {\n\tretval = Cudd_DumpFactoredForm(dd,noutputs,outputs,\n\t\t\t\t       (char const * const *) inames,\n\t\t\t\t       (char const * const *) onames,dfp);\n    } else if (dumpFmt == 5) {\n\tretval = Cudd_DumpBlif(dd,noutputs,outputs,\n\t\t\t       (char const * const *) inames,\n\t\t\t       (char const * const *) onames,\n\t\t\t       network->name,dfp,1);\n    } else {\n\tretval = Cudd_DumpDot(dd,noutputs,outputs,\n\t\t\t      (char const * const *) inames,\n\t\t\t      (char const * const *) onames,dfp);\n    }\n\nendgame:\n    if (dfp != stdout && dfp != NULL) {\n\tif (fclose(dfp) == EOF) retval = 0;\n    }\n    if (outputs != NULL) FREE(outputs);\n    if (onames  != NULL) FREE(onames);\n    if (inames  != NULL) FREE(inames);\n\n    return(retval);\n\n} /* end of Bnet_bddDump */\n\n\n/**\n  @brief Writes an array of BDDs to a file in dot, blif, DDcal,\n  factored-form, daVinci, or blif-MV format.\n\n  @details The BDDs and their names are passed as arguments.  The\n  inputs and their names are taken from the network. If \"-\" is passed\n  as file name, the BDDs are dumped to the standard output.  The encoding\n  of the format is:\n  <ul>\n  <li>0: dot\n  <li>1: blif\n  <li>2: da Vinci\n  <li>3: ddcal\n  <li>4: factored form\n  <li>5: blif-MV\n  </ul>\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nBnet_bddArrayDump(\n  DdManager * dd /**< %DD manager */,\n  BnetNetwork * network /**< network whose BDDs should be dumped */,\n  char * dfile /**< file name */,\n  DdNode ** outputs /**< BDDs to be dumped */,\n  char ** onames /**< names of the BDDs to be dumped */,\n  int  noutputs /**< number of BDDs to be dumped */,\n  int  dumpFmt /**< 0 -> dot */)\n{\n    FILE *dfp = NULL;\n    char **inames = NULL;\n    BnetNode *node;\n    int i;\n    int retval = 0; /* 0 -> failure; 1 -> success */\n\n    /* Open dump file. */\n    if (strcmp(dfile, \"-\") == 0) {\n\tdfp = stdout;\n    } else {\n\tdfp = fopen(dfile,\"w\");\n    }\n    if (dfp == NULL) goto endgame;\n\n    /* Initialize data structures. */\n    inames = ALLOC(char *,Cudd_ReadSize(dd));\n    if (inames == NULL) goto endgame;\n    for (i = 0; i < Cudd_ReadSize(dd); i++) {\n\tinames[i] = NULL;\n    }\n\n    /* Find the input names. */\n    for (i = 0; i < network->ninputs; i++) {\n\tif (!st_lookup(network->hash,network->inputs[i],(void **)&node)) {\n\t    goto endgame;\n\t}\n\tinames[node->var] = network->inputs[i];\n    }\n    for (i = 0; i < network->nlatches; i++) {\n\tif (!st_lookup(network->hash,network->latches[i][1],(void **)&node)) {\n\t    goto endgame;\n\t}\n\tinames[node->var] = network->latches[i][1];\n    }\n\n    /* Dump the BDDs. */\n    if (dumpFmt == 1) {\n\tretval = Cudd_DumpBlif(dd,noutputs,outputs,\n\t\t\t       (char const * const *) inames,\n\t\t\t       (char const * const *) onames,\n\t\t\t       network->name,dfp,0);\n    } else if (dumpFmt == 2) {\n\tretval = Cudd_DumpDaVinci(dd,noutputs,outputs,\n\t\t\t\t  (char const * const *) inames,\n\t\t\t\t  (char const * const *) onames,dfp);\n    } else if (dumpFmt == 3) {\n\tretval = Cudd_DumpDDcal(dd,noutputs,outputs,\n\t\t\t\t(char const * const *) inames,\n\t\t\t\t(char const * const *) onames,dfp);\n    } else if (dumpFmt == 4) {\n\tretval = Cudd_DumpFactoredForm(dd,noutputs,outputs,\n\t\t\t\t       (char const * const *) inames,\n\t\t\t\t       (char const * const *) onames,dfp);\n    } else if (dumpFmt == 5) {\n\tretval = Cudd_DumpBlif(dd,noutputs,outputs,\n\t\t\t       (char const * const *) inames,\n\t\t\t       (char const * const *) onames,\n\t\t\t       network->name,dfp,1);\n    } else {\n\tretval = Cudd_DumpDot(dd,noutputs,outputs,\n\t\t\t      (char const * const *) inames,\n\t\t\t      (char const * const *) onames,dfp);\n    }\n\nendgame:\n    if (dfp != stdout && dfp != NULL) {\n\tif (fclose(dfp) == EOF) retval = 0;\n    }\n    if (inames  != NULL) FREE(inames);\n\n    return(retval);\n\n} /* end of Bnet_bddArrayDump */\n\n\n/**\n  @brief Reads the variable order from a file.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect The BDDs for the primary inputs and present state variables\n  are built.\n\n*/\nint\nBnet_ReadOrder(\n  DdManager * dd,\n  char * ordFile,\n  BnetNetwork * net,\n  int  locGlob,\n  int  nodrop)\n{\n    FILE *fp;\n    st_table *dict;\n    int result;\n    BnetNode *node;\n    char name[MAXLENGTH];\n\n    if (ordFile == NULL) {\n\treturn(0);\n    }\n\n    dict = st_init_table((st_compare_t) strcmp,st_strhash);\n    if (dict == NULL) {\n\treturn(0);\n    }\n\n    if ((fp = fopen(ordFile,\"r\")) == NULL) {\n\t(void) fprintf(stderr,\"Unable to open %s\\n\",ordFile);\n\tst_free_table(dict);\n\treturn(0);\n    }\n\n    while (!feof(fp)) {\n\tresult = fscanf(fp, \"%s\", name);\n\tif (result == EOF) {\n\t    break;\n\t} else if (result != 1) {\n\t    st_free_table(dict);\n\t    return(0);\n\t} else if (strlen(name) > MAXLENGTH) {\n\t    st_free_table(dict);\n\t    return(0);\n\t}\n\t/* There should be a node named \"name\" in the network. */\n\tif (!st_lookup(net->hash,name,(void **)&node)) {\n\t    (void) fprintf(stderr,\"Unknown name in order file (%s)\\n\", name);\n\t    st_free_table(dict);\n\t    return(0);\n\t}\n\t/* A name should not appear more than once in the order. */\n\tif (st_is_member(dict,name)) {\n\t    (void) fprintf(stderr,\"Duplicate name in order file (%s)\\n\", name);\n\t    st_free_table(dict);\n\t    return(0);\n\t}\n\t/* The name should correspond to a primary input or present state. */\n\tif (node->type != BNET_INPUT_NODE &&\n\t    node->type != BNET_PRESENT_STATE_NODE) {\n\t    (void) fprintf(stderr,\"%s has the wrong type (%d)\\n\", name,\n\t\t\t   node->type);\n\t    st_free_table(dict);\n\t    return(0);\n\t}\n\t/* Insert in table. Use node->name rather than name, because the\n\t** latter gets overwritten.\n\t*/\n\tif (st_insert(dict,node->name,NULL) == ST_OUT_OF_MEM) {\n\t    (void) fprintf(stderr,\"Out of memory in Bnet_ReadOrder\\n\");\n\t    st_free_table(dict);\n\t    return(0);\n\t}\n\tresult = Bnet_BuildNodeBDD(dd,node,net->hash,locGlob,nodrop);\n\tif (result == 0) {\n\t    (void) fprintf(stderr,\"Construction of BDD failed\\n\");\n\t    st_free_table(dict);\n\t    return(0);\n\t}\n    } /* while (!feof(fp)) */\n    result = fclose(fp);\n    if (result == EOF) {\n\t(void) fprintf(stderr,\"Error closing order file %s\\n\", ordFile);\n\tst_free_table(dict);\n\treturn(0);\n    }\n\n    /* The number of names in the order file should match exactly the\n    ** number of primary inputs and present states.\n    */\n    if (st_count(dict) != net->ninputs) {\n\t(void) fprintf(stderr,\"Order incomplete: %d names instead of %d\\n\",\n\t\t       st_count(dict), net->ninputs);\n\tst_free_table(dict);\n\treturn(0);\n    }\n\n    st_free_table(dict);\n    return(1);\n\n} /* end of Bnet_ReadOrder */\n\n\n/**\n  @brief Prints the order of the %DD variables of a network.\n\n  @details Only primary inputs and present states are printed.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nBnet_PrintOrder(\n  BnetNetwork * net,\n  DdManager *dd)\n{\n    char **names;\t\t/* array used to print variable orders */\n    int\tlevel;\t\t\t/* position of a variable in current order */\n    BnetNode *node;\t\t/* auxiliary pointer to network node */\n    int i,j;\n    int retval;\n    int nvars;\n\n    nvars = Cudd_ReadSize(dd);\n    names = ALLOC(char *, nvars);\n    if (names == NULL) return(0);\n    for (i = 0; i < nvars; i++) {\n\tnames[i] = NULL;\n    }\n    for (i = 0; i < net->npis; i++) {\n\tif (!st_lookup(net->hash,net->inputs[i],(void **)&node)) {\n\t    FREE(names);\n\t    return(0);\n\t}\n\tif (node->dd == NULL) {\n\t    FREE(names);\n\t    return(0);\n\t}\n\tlevel = Cudd_ReadPerm(dd,node->var);\n\tnames[level] = node->name;\n    }\n    for (i = 0; i < net->nlatches; i++) {\n\tif (!st_lookup(net->hash,net->latches[i][1],(void **)&node)) {\n\t    FREE(names);\n\t    return(0);\n\t}\n\tif (node->dd == NULL) {\n\t    FREE(names);\n\t    return(0);\n\t}\n\tlevel = Cudd_ReadPerm(dd,node->var);\n\tnames[level] = node->name;\n    }\n    for (i = 0, j = 0; i < nvars; i++) {\n\tif (names[i] == NULL) continue;\n\tif ((j%8 == 0)&&j) {\n\t    retval = printf(\"\\n\");\n\t    if (retval == EOF) {\n\t\tFREE(names);\n\t\treturn(0);\n\t    }\n\t}\n\tretval = printf(\"%s \",names[i]);\n\tif (retval == EOF) {\n\t    FREE(names);\n\t    return(0);\n\t}\n\tj++;\n    }\n    FREE(names);\n    retval = printf(\"\\n\");\n    if (retval == EOF) {\n\treturn(0);\n    }\n    return(1);\n\n} /* end of Bnet_PrintOrder */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Reads a string from a file.\n\n  @details The string can be MAXLENGTH-1 characters at\n  most. readString allocates memory to hold the string.\n\n  @return a pointer to the result string if successful. It returns\n  NULL otherwise.\n\n  @sideeffect None\n\n  @see readList\n\n*/\nstatic char *\nreadString(\n  FILE * fp /**< pointer to the file from which the string is read */)\n{\n    char *savestring;\n    int length;\n\n    while (!CurPos) {\n\tif (!fgets(BuffLine, MAXLENGTH, fp))\n\t    return(NULL);\n\tBuffLine[strlen(BuffLine) - 1] = '\\0';\n\tCurPos = strtok(BuffLine, \" \\t\");\n\tif (CurPos && CurPos[0] == '#') CurPos = (char *)NULL;\n    }\n    length = strlen(CurPos);\n    savestring = ALLOC(char,length+1);\n    if (savestring == NULL)\n\treturn(NULL);\n    strcpy(savestring,CurPos);\n    CurPos = strtok(NULL, \" \\t\");\n    return(savestring);\n\n} /* end of readString */\n\n\n/**\n  @brief Reads a list of strings from a line of a file.\n\n  @details The strings are sequences of characters separated by spaces\n  or tabs.  The total length of the list, white space included, must\n  not exceed MAXLENGTH-1 characters.  readList allocates memory for\n  the strings and creates an array of pointers to the individual\n  lists. Only two pieces of memory are allocated by readList: One to\n  hold all the strings, and one to hold the pointers to\n  them. Therefore, when freeing the memory allocated by readList, only\n  the pointer to the list of pointers, and the pointer to the\n  beginning of the first string should be freed.\n\n  @return the pointer to the list of pointers if successful; NULL\n  otherwise.\n\n  @sideeffect n is set to the number of strings in the list.\n\n  @see readString printList\n\n*/\nstatic char **\nreadList(\n  FILE * fp /**< pointer to the file from which the list is read */,\n  int * n /**< on return, number of strings in the list */)\n{\n    char\t*savestring;\n    int\t\tlength;\n    char\t*stack[8192];\n    char\t**list;\n    int\t\ti, count = 0;\n\n    while (CurPos) {\n\tif (strcmp(CurPos, \"\\\\\") == 0) {\n\t    CurPos = (char *)NULL;\n\t    while (!CurPos) {\n\t\tif (!fgets(BuffLine, MAXLENGTH, fp)) return(NULL);\n\t\tBuffLine[strlen(BuffLine) - 1] = '\\0';\n\t\tCurPos = strtok(BuffLine, \" \\t\");\n\t    }\n\t}\n\tlength = strlen(CurPos);\n\tsavestring = ALLOC(char,length+1);\n\tif (savestring == NULL) return(NULL);\n\tstrcpy(savestring,CurPos);\n\tstack[count] = savestring;\n\tcount++;\n\tCurPos = strtok(NULL, \" \\t\");\n    }\n    list = ALLOC(char *, count);\n    for (i = 0; i < count; i++)\n\tlist[i] = stack[i];\n    *n = count;\n    return(list);\n\n} /* end of readList */\n\n\n/**\n  @brief Prints a list of strings to the standard output.\n\n  @details The list is in the format created by readList.\n\n  @sideeffect None\n\n  @see readList Bnet_PrintNetwork\n\n*/\nstatic void\nprintList(\n  char ** list /**< list of pointers to strings */,\n  int  n /**< length of the list */)\n{\n    int i;\n\n    for (i = 0; i < n; i++) {\n\t(void) fprintf(stdout,\" %s\",list[i]);\n    }\n    (void) fprintf(stdout,\"\\n\");\n\n} /* end of printList */\n\n\n/**\n  @brief Generates n names not currently in a symbol table.\n\n  @details The pointer to the symbol table may be NULL, in which case\n  no test is made. The names generated by the procedure are\n  unique. So, if there is no possibility of conflict with pre-existing\n  names, NULL can be passed for the hash table.\n\n  @return an array of names if succesful; NULL otherwise.\n\n  @sideeffect None\n\n  @see \n\n*/\nstatic char **\nbnetGenerateNewNames(\n  st_table * hash /* table of existing names (or NULL) */,\n  int  n /* number of names to be generated */)\n{\n    char **list;\n    char name[256];\n    int i;\n\n    if (n < 1) return(NULL);\n\n    list = ALLOC(char *,n);\n    if (list == NULL) return(NULL);\n    for (i = 0; i < n; i++) {\n\tdo {\n\t    sprintf(name, \"var%d\", newNameNumber);\n\t    newNameNumber++;\n\t} while (hash != NULL && st_is_member(hash,name));\n\tlist[i] = util_strsav(name);\n    }\n\n    return(list);\n\n} /* bnetGenerateNewNames */\n\n\n/**\n  @brief Writes blif for the reencoding logic.\n\n  @sideeffect None\n\n*/\nstatic int\nbnetDumpReencodingLogic(\n  DdManager * dd /**< %DD manager */,\n  char * mname /**< model name */,\n  int  noutputs /**< number of outputs */,\n  DdNode ** outputs /**< array of network outputs */,\n  char ** inames /**< array of network input names */,\n  char ** altnames /**< array of names of reencoded inputs */,\n  char ** onames /**< array of network output names */,\n  FILE * fp /**< file pointer */)\n{\n    int i;\n    int retval;\n    int nvars = Cudd_ReadSize(dd);\n    int *support = NULL;\n\n    support = bnetFindVectorSupport(dd,outputs,noutputs);\n    if (support == NULL) return(0);\n\n    /* Write the header (.model .inputs .outputs). */\n    retval = fprintf(fp,\".model %s.global\\n.inputs\",mname);\n    if (retval == EOF) goto failure;\n\n    for (i = 0; i < nvars; i++) {\n\tif ((i%8 == 0)&&i) {\n\t    retval = fprintf(fp,\" \\\\\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n\tretval = fprintf(fp,\" %s\", inames[i]);\n\tif (retval == EOF) goto failure;\n    }\n\n    /* Write the .output line. */\n    retval = fprintf(fp,\"\\n.outputs\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < noutputs; i++) {\n\tif ((i%8 == 0)&&i) {\n\t    retval = fprintf(fp,\" \\\\\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n\tretval = fprintf(fp,\" %s\", onames[i]);\n\tif (retval == EOF) goto failure;\n    }\n    retval = fprintf(fp,\"\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Instantiate main subcircuit. */\n    retval = fprintf(fp,\"\\n.subckt %s\", mname);\n    if (retval == EOF) goto failure;\n    for (i = 0; i < nvars; i++) {\n\tif ((i%8 == 0)&&i) {\n\t    retval = fprintf(fp,\" \\\\\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n\tif (support[i] == 1) {\n\t    retval = fprintf(fp,\" %s=%s\", inames[i], altnames[i]);\n\t    if (retval == EOF) goto failure;\n\t}\n    }\n    for (i = 0; i < noutputs; i++) {\n\tif ((i%8 == 0)&&i) {\n\t    retval = fprintf(fp,\" \\\\\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n\tretval = fprintf(fp,\" %s=%s\", onames[i], onames[i]);\n\tif (retval == EOF) goto failure;\n    }\n    retval = fprintf(fp,\"\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Instantiate reencoding subcircuit. */\n    retval = fprintf(fp,\"\\n.subckt %s.reencode\",mname);\n    if (retval == EOF) goto failure;\n    for (i = 0; i < nvars; i++) {\n\tif ((i%8 == 0)&&i) {\n\t    retval = fprintf(fp,\" \\\\\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n\tretval = fprintf(fp,\" %s=%s\", inames[i], inames[i]);\n\tif (retval == EOF) goto failure;\n    }\n    retval = fprintf(fp,\" \\\\\\n\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < nvars; i++) {\n\tif ((i%8 == 0)&&i) {\n\t    retval = fprintf(fp,\" \\\\\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n\tif (support[i] == 1) {\n\t    retval = fprintf(fp,\" %s=%s\", altnames[i],altnames[i]);\n\t    if (retval == EOF) goto failure;\n\t}\n    }\n    retval = fprintf(fp,\"\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Write trailer. */\n    retval = fprintf(fp,\".end\\n\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Write reencoding subcircuit. */\n    retval = bnetBlifWriteReencode(dd,mname,inames,altnames,support,fp);\n    if (retval == EOF) goto failure;\n\n    FREE(support);\n    return(1);\n\nfailure:\n    if (support != NULL) FREE(support);\n    return(0);\n\n} /* end of bnetDumpReencodingLogic */\n\n\n/**\n  @brief Writes blif for the truth table of an n-input xnor.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\n#if 0\nstatic int\nbnetBlifXnorTable(\n  FILE * fp /**< file pointer */,\n  int  n /**< number of inputs */)\n{\n    int power;\t/* 2 to the power n */\n    int i,j,k;\n    int nzeroes;\n    int retval;\n    char *line;\n\n    line = ALLOC(char,n+1);\n    if (line == NULL) return(0);\n    line[n] = '\\0';\n\n    for (i = 0, power = 1; i < n; i++) {\n\tpower *= 2;\n    }\n\n    for (i = 0; i < power; i++) {\n\tk = i;\n\tnzeroes = 0;\n\tfor (j = 0; j < n; j++) {\n\t    if (k & 1) {\n\t\tline[j] = '1';\n\t    } else {\n\t\tline[j] = '0';\n\t\tnzeroes++;\n\t    }\n\t    k >>= 1;\n\t}\n\tif ((nzeroes & 1) == 0) {\n\t    retval = fprintf(fp,\"%s 1\\n\",line);\n\t    if (retval == 0) return(0);\n\t}\n    }\n    return(1);\n\n} /* end of bnetBlifXnorTable */\n#endif\n\n\n/**\n  @brief Writes blif for the reencoding logic.\n\n  @details Exclusive NORs with more than two inputs are decomposed\n  into cascaded two-input gates.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nbnetBlifWriteReencode(\n  DdManager * dd,\n  char * mname,\n  char ** inames,\n  char ** altnames,\n  int * support,\n  FILE * fp)\n{\n    int retval;\n    int nvars = Cudd_ReadSize(dd);\n    int i,j;\n    int ninp;\n\n    /* Write the header (.model .inputs .outputs). */\n    retval = fprintf(fp,\".model %s.reencode\\n.inputs\",mname);\n    if (retval == EOF) return(0);\n\n    for (i = 0; i < nvars; i++) {\n\tif ((i%8 == 0)&&i) {\n\t    retval = fprintf(fp,\" \\\\\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n\tretval = fprintf(fp,\" %s\", inames[i]);\n\tif (retval == EOF) goto failure;\n    }\n\n    /* Write the .output line. */\n    retval = fprintf(fp,\"\\n.outputs\");\n    if (retval == EOF) goto failure;\n    for (i = 0; i < nvars; i++) {\n\tif ((i%8 == 0)&&i) {\n\t    retval = fprintf(fp,\" \\\\\\n\");\n\t    if (retval == EOF) goto failure;\n\t}\n\tif (support[i] == 1) {\n\t    retval = fprintf(fp,\" %s\", altnames[i]);\n\t    if (retval == EOF) goto failure;\n\t}\n    }\n    retval = fprintf(fp,\"\\n\");\n    if (retval == EOF) goto failure;\n\n    /* Instantiate exclusive nors. */\n    for (i = 0; i < nvars; i++) {\n\tchar *in1 = NULL;\n\tchar *in2 = NULL;\n\tchar **oname;\n\tif (support[i] == 0) continue;\n\tninp = 0;\n\tfor (j = 0; j < nvars; j++) {\n\t    if (Cudd_ReadLinear(dd,i,j)) {\n\t\tswitch (ninp) {\n\t\tcase 0:\n\t\t    in1 = inames[j];\n\t\t    ninp++;\n\t\t    break;\n\t\tcase 1:\n\t\t    in2 = inames[j];\n\t\t    ninp++;\n\t\t    break;\n\t\tcase 2:\n\t\t    oname = bnetGenerateNewNames(NULL,1);\n\t\t    retval = fprintf(fp,\".names %s %s %s\\n11 1\\n00 1\\n\",\n\t\t\t     in1, in2, oname[0]);\n\t\t    if (retval == EOF) goto failure;\n\t\t    in1 = oname[0];\n\t\t    in2 = inames[j];\n\t\t    FREE(oname);\n\t\t    break;\n\t\tdefault:\n\t\t    goto failure;\n\t\t}\n\t    }\n\t}\n\tswitch (ninp) {\n\tcase 1:\n\t    retval = fprintf(fp,\".names %s %s\\n1 1\\n\", in1, altnames[i]);\n\t    if (retval == EOF) goto failure;\n\t    break;\n\tcase 2:\n\t    retval = fprintf(fp,\".names %s %s %s\\n11 1\\n00 1\\n\",\n\t\t     in1, in2, altnames[i]);\n\t    if (retval == EOF) goto failure;\n\t    break;\n\tdefault:\n\t    goto failure;\n\t}\n    }\n\n    /* Write trailer. */\n    retval = fprintf(fp,\"\\n.end\\n\\n\");\n    if (retval == EOF) goto failure;\n\n    return(1);\n\nfailure:\n    return(0);\n\n} /* end of bnetBlifWriteReencode */\n\n\n/**\n  @brief Finds the support of a list of DDs.\n\n  @sideeffect None\n\n*/\nstatic int *\nbnetFindVectorSupport(\n  DdManager * dd,\n  DdNode ** list,\n  int  n)\n{\n    DdNode\t*support = NULL;\n    DdNode\t*scan;\n    int\t\t*array = NULL;\n    int\t\tnvars = Cudd_ReadSize(dd);\n    int\t\ti;\n\n    /* Build an array with the support of the functions in list. */\n    array = ALLOC(int,nvars);\n    if (array == NULL) return(NULL);\n    for (i = 0; i < nvars; i++) {\n\tarray[i] = 0;\n    }\n\n    /* Take the union of the supports of each output function. */\n    for (i = 0; i < n; i++) {\n\tsupport = Cudd_Support(dd,list[i]);\n\tif (support == NULL) {\n\t    FREE(array);\n\t    return(NULL);\n\t}\n\tCudd_Ref(support);\n\tscan = support;\n\twhile (!Cudd_IsConstant(scan)) {\n\t    array[scan->index] = 1;\n\t    scan = Cudd_T(scan);\n\t}\n\tCudd_IterDerefBdd(dd,support);\n    }\n\n    return(array);\n\n} /* end of bnetFindVectorSupport */\n\n\n/**\n  @brief Builds %BDD for a XOR function.\n\n  @details Checks whether a function is a XOR with 2 or 3 inputs. If so,\n  it builds the %BDD.\n\n  @return 1 if the %BDD has been built; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nbuildExorBDD(\n  DdManager * dd,\n  BnetNode * nd,\n  st_table * hash,\n  int  params,\n  int  nodrop)\n{\n    int check[8];\n    int i;\n    int nlines;\n    BnetTabline *line;\n    DdNode *func, *var, *tmp;\n    BnetNode *auxnd;\n\n    if (nd->ninp < 2 || nd->ninp > 3) return(0);\n\n    nlines = 1 << (nd->ninp - 1);\n    for (i = 0; i < 8; i++) check[i] = 0;\n    line = nd->f;\n    while (line != NULL) {\n\tint num = 0;\n\tint count = 0;\n\tnlines--;\n\tfor (i = 0; i < nd->ninp; i++) {\n\t    num <<= 1;\n\t    if (line->values[i] == '-') {\n\t\treturn(0);\n\t    } else if (line->values[i] == '1') {\n\t\tcount++;\n\t\tnum++;\n\t    }\n\t}\n\tif ((count & 1) == 0) return(0);\n\tif (check[num]) return(0);\n\tline = line->next;\n    }\n    if (nlines != 0) return(0);\n\n    /* Initialize the exclusive sum to logical 0. */\n    func = Cudd_ReadLogicZero(dd);\n    Cudd_Ref(func);\n\n    /* Scan the inputs. */\n    for (i = 0; i < nd->ninp; i++) {\n\tif (!st_lookup(hash, nd->inputs[i], (void **) &auxnd)) {\n\t    goto failure;\n\t}\n\tif (params == BNET_LOCAL_DD) {\n\t    if (auxnd->active == FALSE) {\n\t\tif (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\t    goto failure;\n\t\t}\n\t    }\n\t    var = Cudd_ReadVars(dd,auxnd->var);\n\t    if (var == NULL) goto failure;\n\t    Cudd_Ref(var);\n\t} else { /* params == BNET_GLOBAL_DD */\n\t    if (auxnd->dd == NULL) {\n\t\tif (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\t    goto failure;\n\t\t}\n\t    }\n\t    var = auxnd->dd;\n\t}\n\ttmp = Cudd_bddXor(dd,func,var);\n\tif (tmp == NULL) goto failure;\n\tCudd_Ref(tmp);\n\tCudd_IterDerefBdd(dd,func);\n\tif (params == BNET_LOCAL_DD) {\n\t    Cudd_IterDerefBdd(dd,var);\n\t}\n\tfunc = tmp;\n    }\n    nd->dd = func;\n\n    /* Associate a variable to this node if local BDDs are being\n    ** built. This is done at the end, so that the primary inputs tend\n    ** to get lower indices.\n    */\n    if (params == BNET_LOCAL_DD && nd->active == FALSE) {\n\tDdNode *auxfunc = Cudd_bddNewVar(dd);\n\tif (auxfunc == NULL) goto failure;\n\tCudd_Ref(auxfunc);\n\tnd->var = auxfunc->index;\n\tnd->active = TRUE;\n\tCudd_IterDerefBdd(dd,auxfunc);\n    }\n\n    return(1);\nfailure:\n    return(0);\n\n} /* end of buildExorBDD */\n\n\n/**\n  @brief Builds %BDD for a multiplexer.\n\n  @details Checks whether a function is a 2-to-1 multiplexer. If so,\n  it builds the %BDD.\n\n  @return 1 if the %BDD has been built; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nbuildMuxBDD(\n  DdManager * dd,\n  BnetNode * nd,\n  st_table * hash,\n  int  params,\n  int  nodrop)\n{\n    BnetTabline *line;\n    char *values[2];\n    int mux[2] = {0, 0};\n    int phase[2] = {0, 0};\n    int j;\n    int nlines = 0;\n    int controlC = -1;\n    int controlR = -1;\n    DdNode *func, *f, *g, *h;\n    BnetNode *auxnd;\n\n    if (nd->ninp != 3 || nd->f == NULL) return(0);\n\n    for (line = nd->f; line != NULL; line = line->next) {\n\tint dc = 0;\n\tif (nlines > 1) return(0);\n\tvalues[nlines] = line->values;\n\tfor (j = 0; j < 3; j++) {\n\t    if (values[nlines][j] == '-') {\n\t\tif (dc) return(0);\n\t\tdc = 1;\n\t    }\n\t}\n\tif (!dc) return(0);\n\tnlines++;\n    }\n    if (nlines != 2) return(0);\n    /* At this point we know we have:\n    **   3 inputs\n    **   2 lines\n    **   1 dash in each line\n    ** If the two dashes are not in the same column, then there is\n    ** exaclty one column without dashes: the control column.\n    */\n    for (j = 0; j < 3; j++) {\n\tif (values[0][j] == '-' && values[1][j] == '-') return(0);\n\tif (values[0][j] != '-' && values[1][j] != '-') {\n\t    if (values[0][j] == values[1][j]) return(0);\n\t    controlC = j;\n\t    controlR = values[0][j] == '0';\n\t}\n    }\n    assert(controlC != -1 && controlR != -1);\n    /* At this point we know that there is indeed no column with two\n    ** dashes. The control column has been identified, and we know that\n    ** its two elelments are different. */\n    for (j = 0; j < 3; j++) {\n\tif (j == controlC) continue;\n\tif (values[controlR][j] == '1') {\n\t    mux[0] = j;\n\t    phase[0] = 0;\n\t} else if (values[controlR][j] == '0') {\n\t    mux[0] = j;\n\t    phase[0] = 1;\n\t} else if (values[1-controlR][j] == '1') {\n\t    mux[1] = j;\n\t    phase[1] = 0;\n\t} else if (values[1-controlR][j] == '0') {\n\t    mux[1] = j;\n\t    phase[1] = 1;\n\t}\n    }\n\n    /* Get the inputs. */\n    if (!st_lookup(hash, nd->inputs[controlC], (void **) &auxnd)) {\n\tgoto failure;\n    }\n    if (params == BNET_LOCAL_DD) {\n\tif (auxnd->active == FALSE) {\n\t    if (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\tgoto failure;\n\t    }\n\t}\n\tf = Cudd_ReadVars(dd,auxnd->var);\n\tif (f == NULL) goto failure;\n\tCudd_Ref(f);\n    } else { /* params == BNET_GLOBAL_DD */\n\tif (auxnd->dd == NULL) {\n\t    if (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\tgoto failure;\n\t    }\n\t}\n\tf = auxnd->dd;\n    }\n    if (!st_lookup(hash, nd->inputs[mux[0]], (void **) &auxnd)) {\n\tgoto failure;\n    }\n    if (params == BNET_LOCAL_DD) {\n\tif (auxnd->active == FALSE) {\n\t    if (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\tgoto failure;\n\t    }\n\t}\n\tg = Cudd_ReadVars(dd,auxnd->var);\n\tif (g == NULL) goto failure;\n\tCudd_Ref(g);\n    } else { /* params == BNET_GLOBAL_DD */\n\tif (auxnd->dd == NULL) {\n\t    if (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\tgoto failure;\n\t    }\n\t}\n\tg = auxnd->dd;\n    }\n    g = Cudd_NotCond(g,phase[0]);\n    if (!st_lookup(hash, nd->inputs[mux[1]], (void **) &auxnd)) {\n\tgoto failure;\n    }\n    if (params == BNET_LOCAL_DD) {\n\tif (auxnd->active == FALSE) {\n\t    if (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\tgoto failure;\n\t    }\n\t}\n\th = Cudd_ReadVars(dd,auxnd->var);\n\tif (h == NULL) goto failure;\n\tCudd_Ref(h);\n    } else { /* params == BNET_GLOBAL_DD */\n\tif (auxnd->dd == NULL) {\n\t    if (!Bnet_BuildNodeBDD(dd,auxnd,hash,params,nodrop)) {\n\t\tgoto failure;\n\t    }\n\t}\n\th = auxnd->dd;\n    }\n    h = Cudd_NotCond(h,phase[1]);\n    func = Cudd_bddIte(dd,f,g,h);\n    if (func == NULL) goto failure;\n    Cudd_Ref(func);\n    if (params == BNET_LOCAL_DD) {\n\tCudd_IterDerefBdd(dd,f);\n\tCudd_IterDerefBdd(dd,g);\n\tCudd_IterDerefBdd(dd,h);\n    }\n    nd->dd = func;\n\n    /* Associate a variable to this node if local BDDs are being\n    ** built. This is done at the end, so that the primary inputs tend\n    ** to get lower indices.\n    */\n    if (params == BNET_LOCAL_DD && nd->active == FALSE) {\n\tDdNode *auxfunc = Cudd_bddNewVar(dd);\n\tif (auxfunc == NULL) goto failure;\n\tCudd_Ref(auxfunc);\n\tnd->var = auxfunc->index;\n\tnd->active = TRUE;\n\tCudd_IterDerefBdd(dd,auxfunc);\n    }\n\n    return(1);\nfailure:\n    return(0);\n\n} /* end of buildExorBDD */\n\n\n/**\n  @brief Sets the level of each node.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Changes the level and visited fields of the nodes it\n  visits.\n\n  @see bnetLevelDFS\n\n*/\nstatic int\nbnetSetLevel(\n  BnetNetwork * net)\n{\n    BnetNode *node;\n\n    /* Recursively visit nodes. This is pretty inefficient, because we\n    ** visit all nodes in this loop, and most of them in the recursive\n    ** calls to bnetLevelDFS. However, this approach guarantees that\n    ** all nodes will be reached ven if there are dangling outputs. */\n    node = net->nodes;\n    while (node != NULL) {\n\tif (!bnetLevelDFS(net,node)) return(0);\n\tnode = node->next;\n    }\n\n    /* Clear visited flags. */\n    node = net->nodes;\n    while (node != NULL) {\n\tnode->visited = 0;\n\tnode = node->next;\n    }\n    return(1);\n\n} /* end of bnetSetLevel */\n\n\n/**\n  @brief Does a DFS from a node setting the level field.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Changes the level and visited fields of the nodes it\n  visits.\n\n  @see bnetSetLevel\n\n*/\nstatic int\nbnetLevelDFS(\n  BnetNetwork * net,\n  BnetNode * node)\n{\n    int i;\n    BnetNode *auxnd;\n\n    if (node->visited == 1) {\n\treturn(1);\n    }\n\n    node->visited = 1;\n\n    /* Graphical sources have level 0.  This is the final value if the\n    ** node has no fan-ins. Otherwise the successive loop will\n    ** increase the level. */\n    node->level = 0;\n    for (i = 0; i < node->ninp; i++) {\n\tif (!st_lookup(net->hash, node->inputs[i], (void **) &auxnd)) {\n\t    return(0);\n\t}\n\tif (!bnetLevelDFS(net,auxnd)) {\n\t    return(0);\n\t}\n\tif (auxnd->level >= node->level) node->level = 1 + auxnd->level;\n    }\n    return(1);\n\n} /* end of bnetLevelDFS */\n\n\n/**\n  @brief Orders network roots for variable ordering.\n\n  @return an array with the ordered outputs and next state variables\n  if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic BnetNode **\nbnetOrderRoots(\n  BnetNetwork * net,\n  int * nroots)\n{\n    int i, noutputs;\n    BnetNode *node;\n    BnetNode **nodes = NULL;\n\n    /* Initialize data structures. */\n    noutputs = net->noutputs;\n    nodes = ALLOC(BnetNode *, noutputs);\n    if (nodes == NULL) goto endgame;\n\n    /* Find output names and levels. */\n    for (i = 0; i < net->noutputs; i++) {\n\tif (!st_lookup(net->hash,net->outputs[i],(void **)&node)) {\n\t    goto endgame;\n\t}\n\tnodes[i] = node;\n    }\n\n    util_qsort(nodes, noutputs, sizeof(BnetNode *),\n               (DD_QSFP)bnetLevelCompare);\n    *nroots = noutputs;\n    return(nodes);\n\nendgame:\n    if (nodes != NULL) FREE(nodes);\n    return(NULL);\n\n} /* end of bnetOrderRoots */\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Used to order the variables according to the number of keys\n  in the subtables.\n\n  @return the difference in number of keys between the two variables\n  being compared.\n\n  @sideeffect None\n\n*/\nstatic int\nbnetLevelCompare(\n  BnetNode ** x,\n  BnetNode ** y)\n{\n    return((*y)->level - (*x)->level);\n\n} /* end of bnetLevelCompare */\n\n\n/**\n  @brief Does a DFS from a node ordering the inputs.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Changes visited fields of the nodes it visits.\n\n  @see Bnet_DfsVariableOrder\n\n*/\nstatic int\nbnetDfsOrder(\n  DdManager * dd,\n  BnetNetwork * net,\n  BnetNode * node)\n{\n    int i;\n    BnetNode *auxnd;\n    BnetNode **fanins;\n\n    if (node->visited == 1) {\n\treturn(1);\n    }\n\n    node->visited = 1;\n    if (node->type == BNET_INPUT_NODE ||\n\tnode->type == BNET_PRESENT_STATE_NODE) {\n\tnode->dd = Cudd_bddNewVar(dd);\n\tif (node->dd == NULL) return(0);\n\tCudd_Ref(node->dd);\n\tnode->active = TRUE;\n\tnode->var = node->dd->index;\n\treturn(1);\n    }\n\n    fanins = ALLOC(BnetNode *, node->ninp);\n    if (fanins == NULL) return(0);\n\n    for (i = 0; i < node->ninp; i++) {\n\tif (!st_lookup(net->hash, node->inputs[i], (void **) &auxnd)) {\n\t    FREE(fanins);\n\t    return(0);\n\t}\n\tfanins[i] = auxnd;\n    }\n\n    util_qsort(fanins, node->ninp, sizeof(BnetNode *),\n               (DD_QSFP)bnetLevelCompare);\n    for (i = 0; i < node->ninp; i++) {\n\t/* for (i = node->ninp - 1; i >= 0; i--) { */\n\tint res = bnetDfsOrder(dd,net,fanins[i]);\n\tif (res == 0) {\n\t    FREE(fanins);\n\t    return(0);\n\t}\n    }\n    FREE(fanins);\n    return(1);\n\n} /* end of bnetLevelDFS */\n"
  },
  {
    "path": "cudd/nanotrav/bnet.h",
    "content": "/**\n  @file \n\n  @ingroup nanotrav\n\n  @brief Simple-minded package to read a blif file.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef _BNET\n#define _BNET\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n\n#include \"util.h\"\n#include \"st.h\"\n#include \"cudd.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/* Different types of nodes. (Used in the \"BnetNode\" type.) */\n#define BNET_CONSTANT_NODE 0\n#define BNET_INPUT_NODE 1\n#define BNET_PRESENT_STATE_NODE 2\n#define BNET_INTERNAL_NODE 3\n#define BNET_OUTPUT_NODE 4\n#define BNET_NEXT_STATE_NODE 5\n\n/* Type of DD of a node. */\n#define BNET_LOCAL_DD 0\n#define BNET_GLOBAL_DD 1\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/* The following types implement a very simple data structure for a boolean\n** network. The intent is to be able to read a minimal subset of the blif\n** format in a data structure from which it's easy to build DDs for the\n** circuit.\n*/\n\n/**\n ** @brief Type to store a line of the truth table of a node.\n **\n ** @details The entire truth table implemented as a linked list of\n ** objects of this type.\n */\ntypedef struct BnetTabline {\n    char *values;\t\t/**< string of 1, 0, and - */\n    struct BnetTabline *next;\t/**< pointer to next table line */\n} BnetTabline;\n\n/**\n **  @brief Node of the boolean network.\n **\n ** @details There is one node in the network for each primary input\n ** and for each .names directive. This structure has a field to point\n ** to the DD of the node function. The function may be either in\n ** terms of primary inputs, or it may be in terms of the local\n ** inputs. The latter implies that each node has a variable index\n ** associated to it at some point in time. The field \"var\" stores\n ** that variable index, and \"active\" says if the association is\n ** currently valid.  (It is indeed possible for an index to be\n ** associated to different nodes at different times.)\n */\ntypedef struct BnetNode {\n    char *name;\t\t/**< name of the output signal */\n    int type;\t\t/**< input, internal, constant, ... */\n    int ninp;\t\t/**< number of inputs to the node */\n    int nfo;\t\t/**< number of fanout nodes for this node */\n    char **inputs;\t/**< input names */\n    BnetTabline *f;\t/**< truth table for this node */\n    int polarity;\t/**< f is the onset (0) or the offset (1) */\n    int active;\t\t/**< node has variable associated to it (1) or not (0) */\n    int var;\t\t/**< %DD variable index associated to this node */\n    DdNode *dd;\t\t/**< decision diagram for the function of this node */\n    int exdc_flag;\t/**< whether an exdc node or not */\n    struct BnetNode *exdc; /**< pointer to exdc of dd node */\n    int count;\t\t/**< auxiliary field for %DD dropping */\n    int level;\t\t/**< maximum distance from the inputs */\n    int visited;\t/**< flag for search */\n    struct BnetNode *next; /**< pointer to implement the linked list of nodes */\n} BnetNode;\n\n/**\n ** @brief Very simple boolean network data structure.\n */\ntypedef struct BnetNetwork {\n    char *name;\t\t/**< network name: from the .model directive */\n    int npis;\t\t/**< number of primary inputs */\n    int ninputs;\t/**< number of inputs */\n    char **inputs;\t/**< primary input names: from the .inputs directive */\n    int npos;\t\t/**< number of primary outputs */\n    int noutputs;\t/**< number of outputs */\n    char **outputs;\t/**< primary output names: from the .outputs directive */\n    int nlatches;\t/**< number of latches */\n    char ***latches;\t/**< next state names: from the .latch directives */\n    BnetNode *nodes;\t/**< linked list of the nodes */\n    st_table *hash;\t/**< symbol table to access nodes by name */\n    char *slope;\t/**< wire_load_slope */\n} BnetNetwork;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#ifndef TRUE\n#   define TRUE 1\n#endif\n#ifndef FALSE\n#   define FALSE 0\n#endif\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\nextern BnetNetwork * Bnet_ReadNetwork (FILE *fp, int pr);\nextern void Bnet_PrintNetwork (BnetNetwork *net);\nextern void Bnet_FreeNetwork (BnetNetwork *net);\nextern int Bnet_BuildNodeBDD (DdManager *dd, BnetNode *nd, st_table *hash, int params, int nodrop);\nextern int Bnet_DfsVariableOrder (DdManager *dd, BnetNetwork *net);\nextern int Bnet_bddDump (DdManager *dd, BnetNetwork *network, char *dfile, int dumpFmt, int reencoded);\nextern int Bnet_bddArrayDump (DdManager *dd, BnetNetwork *network, char *dfile, DdNode **outputs, char **onames, int noutputs, int dumpFmt);\nextern int Bnet_ReadOrder (DdManager *dd, char *ordFile, BnetNetwork *net, int locGlob, int nodrop);\nextern int Bnet_PrintOrder (BnetNetwork * net, DdManager *dd);\n\n/** \\endcond */\n\n\n#ifdef __cplusplus\n} /* end of extern \"C\" */\n#endif\n\n#endif /* _BNET */\n"
  },
  {
    "path": "cudd/nanotrav/chkMterm.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief Functions to check that the minterm counts have not changed\n  during reordering.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"ntr.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic enum st_retval stFree (void *key, void *value, void *arg);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Check that minterm counts have not changed.\n\n  @details Counts the minterms in the global functions of the\n  primary outputs of the network passed as argument.\n  When it is calld with the second argument set to NULL, it allocates\n  a symbol table and stores, for each output, the minterm count. If\n  an output does not have a %BDD, it stores a NULL pointer for it.\n  If it is called with a non-null second argument, it assumes that\n  the symbol table contains the minterm counts measured previously\n  and it compares the new counts to the old ones. Finally, it frees\n  the symbol table.\n  check_minterms is designed so that it can be called twice: once before\n  reordering, and once after reordering.\n\n  @return a pointer to the symbol table on the first invocation and\n  NULL on the second invocation.\n\n  @sideeffect None\n\n*/\nst_table *\ncheckMinterms(\n  BnetNetwork * net,\n  DdManager * dd,\n  st_table * previous)\n{\n    BnetNode *po;\n    int numPi;\n    char *name;\n    double *count, newcount, *oldcount;\n    int flag,err,i;\n\n    numPi = net->ninputs;\n\n    if (previous == NULL) {\n      previous = st_init_table((st_compare_t) strcmp, st_strhash);\n\tif (previous == NULL) {\n\t    (void) printf(\"checkMinterms out-of-memory\\n\");\n\t    return(NULL);\n\t}\n\tfor (i = 0; i < net->noutputs; i++) {\n\t    if (!st_lookup(net->hash,net->outputs[i],(void **)&po)) {\n\t\texit(2);\n\t    }\n\t    name = net->outputs[i];\n\t    if (po->dd != NULL) {\n\t\tcount = ALLOC(double,1);\n\t\t*count = Cudd_CountMinterm(dd,po->dd,numPi);\n\t\terr = st_insert(previous, name, (void *) count);\n\t    } else {\n\t\terr = st_insert(previous, name, NULL);\n\t    }\n\t    if (err) {\n\t\t(void) printf(\"Duplicate input name (%s)\\n\",name);\n\t\treturn(NULL);\n\t    }\n\t}\n\treturn(previous);\n    } else {\n\tflag = 0;\n\tif (st_count(previous) != net->noutputs) {\n\t    (void) printf(\"Number of outputs has changed from %d to %d\\n\",\n\t    st_count(previous), net->noutputs);\n\t    flag = 1;\n\t}\n\tfor (i = 0; i < net->noutputs; i++) {\n\t    if (!st_lookup(net->hash,net->outputs[i],(void **)&po)) {\n\t\texit(2);\n\t    }\n\t    name = net->outputs[i];\n\t    if (st_lookup(previous,name,(void **)&oldcount)) {\n\t\tif (po->dd != NULL) {\n\t\t    newcount = Cudd_CountMinterm(dd,po->dd,numPi);\n\t\t    if (newcount != *oldcount) {\n\t\t\t(void) printf(\"Number of minterms of %s has changed from %g to %g\\n\",name,*oldcount,newcount);\n\t\t\tflag = 1;\n\t\t    }\n\t\t} else {\n\t\t    if (oldcount != NULL) {\n\t\t\t(void) printf(\"Output %s lost its BDD!\\n\",name);\n\t\t\tflag = 1;\n\t\t    }\n\t\t}\n\t    } else {\n\t\t(void) printf(\"Output %s is new!\\n\",name);\n\t\tflag = 1;\n\t    }\n\t}\n\t/*st_foreach(previous,(enum st_retval)stFree,NULL);*/\n\tst_foreach(previous,stFree,NULL);\n\tst_free_table(previous);\n\tif (flag) {\n\t    return((st_table *) 1);\n\t} else {\n\t    return(NULL);\n\t}\n    }\n\n} /* end of checkMinterms */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Frees the data of the symbol table.\n\n  @sideeffect None\n\n*/\nstatic enum st_retval\nstFree(\n  void *key,\n  void *value,\n  void *arg)\n{\n    (void) key; /* avoid warning */\n    (void) arg; /* avoid warning */\n    if (value != NULL) {\n\tFREE(value);\n    }\n    return(ST_CONTINUE);\n\n} /* end of stFree */\n"
  },
  {
    "path": "cudd/nanotrav/closest.blif",
    "content": ".model closest\n.inputs a b c\n.outputs f g h\n.names a b c f\n1-1 1\n-11 1\n.names a b c g\n000 1\n.names a b c h\n111 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/closest.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -reordering genetic -drop -closest ./nanotrav/closest.blif\n# CUDD Version 3.0.0\nOrder before final reordering\na b c \nNumber of inputs = 3\nBDD reordering with genetic: from 7 to ... 7 nodes in 0 sec\nNew order\nc a b \nTesting Cudd_bddClosestCube\nTEST-CC:: H(f, f)\nT-F    : 4 nodes 1 leaves 3 minterms\nT-G    : 4 nodes 1 leaves 3 minterms\nT-C (0) : 3 nodes 1 leaves 2 minterms\nT-GN   : 4 nodes 1 leaves 5 minterms\nT-N (1) : 4 nodes 1 leaves 1 minterms\nTEST-CC:: H(f, g)\nT-F    : 4 nodes 1 leaves 3 minterms\nT-G    : 4 nodes 1 leaves 1 minterms\nT-C (2) : 4 nodes 1 leaves 1 minterms\nT-GN   : 4 nodes 1 leaves 7 minterms\nT-N (0) : 3 nodes 1 leaves 2 minterms\nTEST-CC:: H(f, h)\nT-F    : 4 nodes 1 leaves 3 minterms\nT-G    : 4 nodes 1 leaves 1 minterms\nT-C (0) : 4 nodes 1 leaves 1 minterms\nT-GN   : 4 nodes 1 leaves 7 minterms\nT-N (0) : 4 nodes 1 leaves 1 minterms\nTEST-CC:: H(g, f)\nT-F    : 4 nodes 1 leaves 1 minterms\nT-G    : 4 nodes 1 leaves 3 minterms\nT-C (2) : 4 nodes 1 leaves 1 minterms\nT-GN   : 4 nodes 1 leaves 5 minterms\nT-N (0) : 4 nodes 1 leaves 1 minterms\nTEST-CC:: H(g, g)\nT-F    : 4 nodes 1 leaves 1 minterms\nT-G    : 4 nodes 1 leaves 1 minterms\nT-C (0) : 4 nodes 1 leaves 1 minterms\nT-GN   : 4 nodes 1 leaves 7 minterms\nT-N (1) : 4 nodes 1 leaves 1 minterms\nTEST-CC:: H(g, h)\nT-F    : 4 nodes 1 leaves 1 minterms\nT-G    : 4 nodes 1 leaves 1 minterms\nT-C (3) : 4 nodes 1 leaves 1 minterms\nT-GN   : 4 nodes 1 leaves 7 minterms\nT-N (0) : 4 nodes 1 leaves 1 minterms\nTEST-CC:: H(h, f)\nT-F    : 4 nodes 1 leaves 1 minterms\nT-G    : 4 nodes 1 leaves 3 minterms\nT-C (0) : 4 nodes 1 leaves 1 minterms\nT-GN   : 4 nodes 1 leaves 5 minterms\nT-N (1) : 4 nodes 1 leaves 1 minterms\nTEST-CC:: H(h, g)\nT-F    : 4 nodes 1 leaves 1 minterms\nT-G    : 4 nodes 1 leaves 1 minterms\nT-C (3) : 4 nodes 1 leaves 1 minterms\nT-GN   : 4 nodes 1 leaves 7 minterms\nT-N (0) : 4 nodes 1 leaves 1 minterms\nTEST-CC:: H(h, h)\nT-F    : 4 nodes 1 leaves 1 minterms\nT-G    : 4 nodes 1 leaves 1 minterms\nT-C (0) : 4 nodes 1 leaves 1 minterms\nT-GN   : 4 nodes 1 leaves 7 minterms\nT-N (1) : 4 nodes 1 leaves 1 minterms\nEnd of test.  Performed 0 recursive calls.\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000000\nMaximum number of variable swaps per reordering: 1000000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 22\n**** CUDD non-modifiable parameters ****\nMemory in use: 3182768\nPeak number of nodes: 1022\nPeak number of live nodes: 18\nNumber of BDD variables: 3\nNumber of ZDD variables: 0\nNumber of cache entries: 32768\nNumber of cache look-ups: 94\nNumber of cache hits: 32\nNumber of cache insertions: 63\nNumber of cache collisions: 0\nNumber of cache deletions: 9\nCache used slots = 0.18% (expected 0.16%)\nSoft limit for cache size: 4096\nNumber of buckets in unique table: 1024\nUsed buckets in unique table: 4.79% (expected 4.93%)\nNumber of BDD and ADD nodes: 52\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 40\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 55\nTotal number of nodes reclaimed: 142\nGarbage collections so far: 1\nTime for garbage collection: 0.00 sec\nReorderings so far: 1\nTime for reordering: 0.00 sec\nFinal size: 7\ntotal time = 0.00 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  5816K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 887\nSwaps = 0\nInput blocks = 8\nOutput blocks = 8\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/ham01.blif",
    "content": "# Checks whether the Hamming distance between X and Y is 0 or 1.\n.model ham01.blif\n.inputs x2 y2 x1 y1 x0 y0\n.outputs H01\n.names one\n1\n.names y0 one one a\n11- 1\n0-0 1\n.names x0 a a b\n11- 1\n0-0 1\n.names y1 one b c\n11- 1\n0-1 1\n.names y1 b one d\n11- 1\n0-1 1\n.names y1 b one e\n11- 1\n0-0 1\n.names y1 one b f\n11- 1\n0-0 1\n.names x1 c d g\n11- 1\n0-1 1\n.names x1 e f h\n11- 1\n0-0 1\n.names y2 g h i\n11- 1\n0-1 1\n.names y2 h g j\n11- 1\n0-1 1\n.names x2 i j k\n11- 1\n0-1 1\n.names k H01\n1 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/ham01.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -reordering linear ./nanotrav/ham01.blif\n# CUDD Version 3.0.0\nOrder before final reordering\nx2 y2 x1 y1 x0 y0 \nNumber of inputs = 6\nBDD reordering with linear sifting: from 12 to ... 8 nodes in 0 sec\nNew order\ny1 x2 x1 y2 x0 y0 \nx2 : 2 nodes 1 leaves 32 minterms\ny2 : 2 nodes 1 leaves 32 minterms\nx1 : 2 nodes 1 leaves 32 minterms\ny1 : 4 nodes 1 leaves 32 minterms\nx0 : 2 nodes 1 leaves 32 minterms\ny0 : 2 nodes 1 leaves 32 minterms\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000000\nMaximum number of variable swaps per reordering: 1000000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 28\n**** CUDD non-modifiable parameters ****\nMemory in use: 3182816\nPeak number of nodes: 1022\nPeak number of live nodes: 20\nNumber of BDD variables: 6\nNumber of ZDD variables: 0\nNumber of cache entries: 32768\nNumber of cache look-ups: 5\nNumber of cache hits: 0\nNumber of cache insertions: 5\nNumber of cache collisions: 0\nNumber of cache deletions: 5\nCache used slots = 0.02% (expected 0.00%)\nSoft limit for cache size: 7168\nNumber of buckets in unique table: 1792\nUsed buckets in unique table: 0.89% (expected 0.89%)\nNumber of BDD and ADD nodes: 16\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 1\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 21\nTotal number of nodes reclaimed: 2\nGarbage collections so far: 0\nTime for garbage collection: 0.00 sec\nReorderings so far: 1\nTime for reordering: 0.00 sec\nFinal size: 8\ntotal time = 0.00 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  5984K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 891\nSwaps = 0\nInput blocks = 0\nOutput blocks = 8\nContext switch (voluntary) = 0\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/main.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief Main program for the nanotrav program.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"cuddInt.h\"\n#include \"ntr.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define NTR_VERSION \"Nanotrav Version #0.13, Release date 2015/7/15\"\n\n#define BUFLENGTH 8192\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\nstatic  char    buffer[BUFLENGTH];\n#ifdef DD_DEBUG\nextern  st_table *checkMinterms (BnetNetwork *net, DdManager *dd, st_table *previous);\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic NtrOptions * mainInit ();\nstatic void ntrReadOptions (int argc, char **argv, NtrOptions *option);\nstatic void ntrReadOptionsFile (char *name, char ***argv, int *argc);\nstatic char* readLine (FILE *fp);\nstatic FILE * open_file (char *filename, const char *mode);\nstatic int reorder (BnetNetwork *net, DdManager *dd, NtrOptions *option);\nstatic void freeOption (NtrOptions *option);\nstatic DdManager * startCudd (NtrOptions *option, int nvars);\nstatic int ntrReadTree (DdManager *dd, char *treefile, int nvars);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Main program for ntr.\n\n  @details Performs initialization. Reads command line options and\n  network(s). Builds BDDs with reordering, and optionally does\n  reachability analysis. Prints stats.\n\n  @sideeffect None\n\n*/\nint\nmain(\n  int  argc,\n  char ** argv)\n{\n    NtrOptions\t*option;\t/* options */\n    FILE\t*fp1;\t\t/* first network file pointer */\n    BnetNetwork\t*net1 = NULL;\t/* first network */\n    FILE\t*fp2;\t\t/* second network file pointer */\n    BnetNetwork\t*net2 = NULL;\t/* second network */\n    DdManager\t*dd;\t\t/* pointer to DD manager */\n    int\t\texitval;\t/* return value of Cudd_CheckZeroRef */\n    int\t\tok;\t\t/* overall return value from main() */\n    int\t\tresult;\t\t/* stores the return value of functions */\n    BnetNode\t*node;\t\t/* auxiliary pointer to network node */\n    int\t\ti;\t\t/* loop index */\n    int\t\tj;\t\t/* loop index */\n    double\t*signatures;\t/* array of signatures */\n    int\t\tpr;\t\t/* verbosity level */\n    int\t\treencoded;\t/* linear transformations attempted */\n\n    /* Initialize. */\n#if defined(_WIN32) && defined(_TWO_DIGIT_EXPONENT)\n    (void) _set_output_format(_TWO_DIGIT_EXPONENT);\n#endif\n    option = mainInit();\n    ntrReadOptions(argc,argv,option);\n    pr = option->verb;\n    reencoded = option->reordering == CUDD_REORDER_LINEAR ||\n\t\toption->reordering == CUDD_REORDER_LINEAR_CONVERGE ||\n\t\toption->autoMethod == CUDD_REORDER_LINEAR ||\n\t\toption->autoMethod == CUDD_REORDER_LINEAR_CONVERGE;\n    /* Currently traversal requires global BDDs. Override whatever\n    ** was specified for locGlob.\n    */\n    if (option->traverse == TRUE || option->envelope == TRUE ||\n\toption->scc == TRUE) {\n\toption->locGlob = BNET_GLOBAL_DD;\n    }\n\n    /* Read the first network... */\n    fp1 = open_file(option->file1, \"r\");\n    net1 = Bnet_ReadNetwork(fp1,pr);\n    (void) fclose(fp1);\n    if (net1 == NULL) {\n\t(void) fprintf(stderr,\"Syntax error in %s.\\n\",option->file1);\n\texit(2);\n    }\n    /* ... and optionally echo it to the standard output. */\n    if (pr > 2) {\n\tBnet_PrintNetwork(net1);\n    }\n\n    /* Read the second network... */\n    if (option->verify == TRUE || option->second == TRUE ||\n\toption->clip > 0.0 || option->dontcares) {\n\tfp2 = open_file(option->file2, \"r\");\n\tnet2 = Bnet_ReadNetwork(fp2,pr);\n\t(void) fclose(fp2);\n\tif (net2 == NULL) {\n\t    (void) fprintf(stderr,\"Syntax error in %s.\\n\",option->file2);\n\t    exit(2);\n\t}\n\t/* ... and optionally echo it to the standard output. */\n\tif (pr > 2) {\n\t    Bnet_PrintNetwork(net2);\n\t}\n    }\n\n    /* Initialize manager. We start with 0 variables, because\n    ** Ntr_buildDDs will create new variables rather than using\n    ** whatever already exists.\n    */\n    dd = startCudd(option,net1->ninputs);\n    if (dd == NULL) { exit(2); }\n\n    /* Build the BDDs for the nodes of the first network. */\n    result = Ntr_buildDDs(net1,dd,option,NULL);\n    if (result == 0) { exit(2); }\n\n    /* Build the BDDs for the nodes of the second network if requested. */\n    if (option->verify == TRUE || option->second == TRUE ||\n\toption->clip > 0.0 || option->dontcares == TRUE) {\n\tchar *nodesave = option->node;\n\toption->node = NULL;\n\tresult = Ntr_buildDDs(net2,dd,option,net1);\n\toption->node = nodesave;\n\tif (result == 0) { exit(2); }\n    }\n\n    if (option->noBuild == TRUE) {\n\tBnet_FreeNetwork(net1);\n\tif (option->verify == TRUE || option->second == TRUE ||\n\t    option->clip > 0.0) {\n\t    Bnet_FreeNetwork(net2);\n\t}\n\tfreeOption(option);\n\texit(0);\n    }\n    if (option->locGlob != BNET_LOCAL_DD) {\n\t/* Print the order before the final reordering. */\n\t(void) printf(\"Order before final reordering\\n\");\n\tresult = Bnet_PrintOrder(net1,dd);\n\tif (result == 0) exit(2);\n    }\n\n    /* Perform final reordering */\n    if (option->zddtest == FALSE) {\n\tresult = reorder(net1,dd,option);\n\tif (result == 0) exit(2);\n\n\t/* Print final order. */\n\tif ((option->reordering != CUDD_REORDER_NONE || option->gaOnOff) &&\n\t    option->locGlob != BNET_LOCAL_DD) {\n\t    (void) printf(\"New order\\n\");\n\t    result = Bnet_PrintOrder(net1,dd);\n\t    if (result == 0) exit(2);\n\t}\n\n\t/* Print the re-encoded inputs. */\n\tif (pr >= 1 && reencoded == 1) {\n\t    for (i = 0; i < net1->npis; i++) {\n\t\tif (!st_lookup(net1->hash,net1->inputs[i],(void **)&node)) {\n\t\t    exit(2);\n\t\t}\n\t\t(void) fprintf(stdout,\"%s \",node->name);\n\t\tCudd_PrintDebug(dd,node->dd,Cudd_ReadSize(dd),pr);\n\t    }\n\t    for (i = 0; i < net1->nlatches; i++) {\n\t\tif (!st_lookup(net1->hash,net1->latches[i][1],(void **)&node)) {\n\t\t    exit(2);\n\t\t}\n\t\t(void) fprintf(stdout,\"%s \",node->name);\n\t\tCudd_PrintDebug(dd,node->dd,Cudd_ReadSize(dd),pr);\n\t    }\n\t    if (pr >= 3) {\n\t\tresult = Cudd_PrintLinear(dd);\n\t\tif (result == 0) exit(2);\n\t    }\n\t}\n    }\n\n    /* Verify (combinational) equivalence. */\n    if (option->verify == TRUE) {\n\tresult = Ntr_VerifyEquivalence(dd,net1,net2,option);\n\tif (result == 0) {\n\t    (void) printf(\"Verification abnormally terminated\\n\");\n\t    exit(2);\n\t} else if (result == -1) {\n\t    (void) printf(\"Combinational verification failed\\n\");\n\t} else {\n\t    (void) printf(\"Verification succeeded\\n\");\n\t}\n    }\n\n    /* Traverse if requested and if the circuit is sequential. */\n    result = Ntr_Trav(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Traverse with trasitive closure. */\n    result = Ntr_ClosureTrav(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Compute outer envelope if requested and if the circuit is sequential. */\n    if (option->envelope == TRUE && net1->nlatches > 0) {\n\tNtrPartTR *T;\n\tT = Ntr_buildTR(dd,net1,option,option->image);\n\tresult = Ntr_Envelope(dd,T,NULL,option);\n        if (result == 0) exit(2);\n\tNtr_freeTR(dd,T);\n    }\n\n    /* Compute SCCs if requested and if the circuit is sequential. */\n    result = Ntr_SCC(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Test Constrain Decomposition. */\n    if (option->partition == TRUE && net1->nlatches > 0) {\n\tNtrPartTR *T;\n\tDdNode *product;\n\tDdNode **decomp;\n\tint sharingSize;\n\tT = Ntr_buildTR(dd,net1,option,NTR_IMAGE_MONO);\n\tdecomp = Cudd_bddConstrainDecomp(dd,T->part[0]);\n\tif (decomp == NULL) exit(2);\n\tsharingSize = Cudd_SharingSize(decomp, Cudd_ReadSize(dd));\n\t(void) fprintf(stdout, \"Decomposition Size: %d components %d nodes\\n\",\n\t\t       Cudd_ReadSize(dd), sharingSize);\n\tproduct = Cudd_ReadOne(dd);\n\tCudd_Ref(product);\n\tfor (i = 0; i < Cudd_ReadSize(dd); i++) {\n\t    DdNode *intermediate = Cudd_bddAnd(dd, product, decomp[i]);\n\t    if (intermediate == NULL) {\n\t\texit(2);\n\t    }\n\t    Cudd_Ref(intermediate);\n\t    Cudd_IterDerefBdd(dd, product);\n\t    product = intermediate;\n\t}\n\tif (product != T->part[0])\n\t    exit(2);\n\tCudd_IterDerefBdd(dd, product);\n\tfor (i = 0; i < Cudd_ReadSize(dd); i++) {\n\t    Cudd_IterDerefBdd(dd, decomp[i]);\n\t}\n\tFREE(decomp);\n\tNtr_freeTR(dd,T);\n    }\n\n    /* Test char-to-vect conversion. */\n    result = Ntr_TestCharToVect(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Test extraction of two-literal clauses. */\n    result = Ntr_TestTwoLiteralClauses(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Test BDD minimization functions. */\n    result = Ntr_TestMinimization(dd,net1,net2,option);\n    if (result == 0) exit(2);\n\n    /* Test density-related functions. */\n    result = Ntr_TestDensity(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Test decomposition functions. */\n    result = Ntr_TestDecomp(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Test cofactor estimation functions. */\n    result = Ntr_TestCofactorEstimate(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Test BDD clipping functions. */\n    result = Ntr_TestClipping(dd,net1,net2,option);\n    if (result == 0) exit(2);\n\n    /* Test BDD equivalence and containment under DC functions. */\n    result = Ntr_TestEquivAndContain(dd,net1,net2,option);\n    if (result == 0) exit(2);\n\n    /* Test BDD Cudd_bddClosestCube. */\n    result = Ntr_TestClosestCube(dd,net1,option);\n    if (result == 0) exit(2);\n\n    /* Test ZDDs if requested. */\n    if (option->stateOnly == FALSE && option->zddtest == TRUE) {\n\tresult = Ntr_testZDD(dd,net1,option);\n\tif (result == 0)\n\t    (void) fprintf(stdout,\"ZDD test failed.\\n\");\n\tresult = Ntr_testISOP(dd,net1,option);\n\tif (result == 0)\n\t    (void) fprintf(stdout,\"ISOP test failed.\\n\");\n    }\n\n    /* Compute maximum flow if requested and if the circuit is sequential. */\n    if (option->maxflow == TRUE && net1->nlatches > 0) {\n\tresult = Ntr_maxflow(dd,net1,option);\n\tif (result == 0)\n\t    (void) fprintf(stdout,\"Maxflow computation failed.\\n\");\n    }\n\n    /* Compute shortest paths if requested and if the circuit is sequential. */\n    if (option->shortPath != NTR_SHORT_NONE && net1->nlatches > 0) {\n\tresult = Ntr_ShortestPaths(dd,net1,option);\n\tif (result == 0)\n\t    (void) fprintf(stdout,\"Shortest paths computation failed.\\n\");\n    }\n\n    /* Compute output signatures if so requested. */\n    if (option->signatures) {\n\t(void) printf(\"Positive cofactor measures\\n\");\n\tfor (i = 0; i < net1->noutputs; i++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[i],(void **)&node)) {\n\t\texit(2);\n\t    }\n\t    signatures = Cudd_CofMinterm(dd, node->dd);\n\t    if (signatures) {\n\t\t(void) printf(\"%s:\\n\", node->name);\n\t\tfor (j = 0; j < Cudd_ReadSize(dd); j++) {\n\t\t    if((j%5 == 0)&&i) (void) printf(\"\\n\");\n\t\t    (void) printf(\"%5d: %-#8.4g \", j, signatures[j]);\n\t\t}\n\t\t(void) printf(\"\\n\");\n\t\tFREE(signatures);\n\t    } else {\n\t\t(void) printf(\"Signature computation failed.\\n\");\n\t    }\n\t}\n    }\n\n    /* Dump BDDs if so requested. */\n    if (option->bdddump && option->second == FALSE &&\n\toption->density == FALSE && option->decomp == FALSE &&\n\toption->cofest == FALSE && option->clip < 0.0 &&\n\toption->scc == FALSE) {\n\t(void) printf(\"Dumping BDDs to %s\\n\", option->dumpfile);\n\tif (option->node != NULL) {\n\t    if (!st_lookup(net1->hash,option->node,(void **)&node)) {\n\t\texit(2);\n\t    }\n\t    result = Bnet_bddArrayDump(dd,net1,option->dumpfile,&(node->dd),\n\t\t\t\t       &(node->name),1,option->dumpFmt);\n\t} else {\n\t    result = Bnet_bddDump(dd, net1, option->dumpfile,\n\t\t\t\t  option->dumpFmt, reencoded);\n\t}\n\tif (result != 1) {\n\t    (void) printf(\"BDD dump failed.\\n\");\n\t}\n    }\n\n    /* Print stats and clean up. */\n    if (pr >= 0) {\n\tresult = Cudd_PrintInfo(dd,stdout);\n\tif (result != 1) {\n\t    (void) printf(\"Cudd_PrintInfo failed.\\n\");\n\t}\n    }\n\n#if defined(DD_DEBUG) && !defined(DD_NO_DEATH_ROW)\n    (void) fprintf(dd->err,\"%d empty slots in death row\\n\",\n    cuddTimesInDeathRow(dd,NULL));\n#endif\n    (void) printf(\"Final size: %ld\\n\", Cudd_ReadNodeCount(dd));\n\n    /* Dispose of node BDDs. */\n    node = net1->nodes;\n    while (node != NULL) {\n\tif (node->dd != NULL &&\n\tnode->type != BNET_INPUT_NODE &&\n\tnode->type != BNET_PRESENT_STATE_NODE) {\n\t    Cudd_IterDerefBdd(dd,node->dd);\n            node->dd = NULL;\n\t}\n\tnode = node->next;\n    }\n    /* Dispose of network. */\n    Bnet_FreeNetwork(net1);\n    /* Do the same cleanup for the second network if it was created. */\n    if (option->verify == TRUE || option->second == TRUE ||\n\toption->clip > 0.0 || option->dontcares == TRUE) {\n        /* Since option->second is TRUE and reading the second network\n         * didn't result in a failure, we know net2 is not NULL. */\n        assert(net2 != NULL);\n\tnode = net2->nodes;\n\twhile (node != NULL) {\n\t    if (node->dd != NULL &&\n\t\tnode->type != BNET_INPUT_NODE &&\n\t\tnode->type != BNET_PRESENT_STATE_NODE) {\n\t\tCudd_IterDerefBdd(dd,node->dd);\n                node->dd = NULL;\n\t    }\n\t    node = node->next;\n\t}\n\tBnet_FreeNetwork(net2);\n    }\n\n    /* Check reference counts: At this point we should have dereferenced\n    ** everything we had, except in the case of re-encoding.\n    */\n    if (reencoded == CUDD_FALSE) {\n        exitval = Cudd_CheckZeroRef(dd);\n        ok = exitval != 0;  /* ok == 0 means O.K. */\n        if (exitval != 0) {\n            (void) fflush(stdout);\n            (void) fprintf(stderr,\n                           \"%d non-zero DD reference counts after dereferencing\\n\", exitval);\n        }\n    } else {\n        ok = 0;\n    }\n\n#ifdef DD_DEBUG\n    Cudd_CheckKeys(dd);\n#endif\n\n    Cudd_Quit(dd);\n\n    if (pr >= 0) (void) printf(\"total time = %s\\n\",\n\t    util_print_time(util_cpu_time() - option->initialTime));\n    freeOption(option);\n    if (pr >= 0) util_print_cpu_stats(stdout);\n\n    exit(ok);\n\n} /* end of main */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Allocates the option structure and initializes it.\n\n  @sideeffect none\n\n  @see ntrReadOptions\n\n*/\nstatic NtrOptions *\nmainInit(\n   )\n{\n    NtrOptions\t*option;\n\n    /* Initialize option structure. */\n    option = ALLOC(NtrOptions,1);\n    option->initialTime    = util_cpu_time();\n    option->verify         = FALSE;\n    option->second         = FALSE;\n    option->file1          = NULL;\n    option->file2          = NULL;\n    option->traverse       = FALSE;\n    option->depend         = FALSE;\n    option->image          = NTR_IMAGE_MONO;\n    option->imageClip      = 1.0;\n    option->approx         = NTR_UNDER_APPROX;\n    option->threshold      = -1;\n    option->from\t   = NTR_FROM_NEW;\n    option->groupnsps      = NTR_GROUP_NONE;\n    option->closure        = FALSE;\n    option->closureClip    = 1.0;\n    option->envelope       = FALSE;\n    option->scc            = FALSE;\n    option->maxflow        = FALSE;\n    option->shortPath      = NTR_SHORT_NONE;\n    option->selectiveTrace = FALSE;\n    option->zddtest        = FALSE;\n    option->printcover     = FALSE;\n    option->sinkfile       = NULL;\n    option->partition      = FALSE;\n    option->char2vect      = FALSE;\n    option->density        = FALSE;\n    option->quality        = 1.0;\n    option->decomp         = FALSE;\n    option->cofest         = FALSE;\n    option->clip           = -1.0;\n    option->dontcares      = FALSE;\n    option->closestCube    = FALSE;\n    option->clauses        = FALSE;\n    option->noBuild        = FALSE;\n    option->stateOnly      = FALSE;\n    option->node           = NULL;\n    option->locGlob        = BNET_GLOBAL_DD;\n    option->progress       = FALSE;\n    option->cacheSize      = 32768;\n    option->maxMemory      = 0;\t/* set automatically */\n    option->maxMemHard     = 0; /* don't set */\n    option->maxLive        = ~0U; /* very large number */\n    option->slots          = CUDD_UNIQUE_SLOTS;\n    option->ordering       = PI_PS_FROM_FILE;\n    option->orderPiPs      = NULL;\n    option->reordering     = CUDD_REORDER_NONE;\n    option->autoMethod     = CUDD_REORDER_SIFT;\n    option->autoDyn        = 0;\n    option->treefile       = NULL;\n    option->firstReorder   = DD_FIRST_REORDER;\n    option->countDead      = FALSE;\n    option->maxGrowth      = 20;\n    option->groupcheck     = CUDD_GROUP_CHECK7;\n    option->arcviolation   = 10;\n    option->symmviolation  = 10;\n    option->recomb         = DD_DEFAULT_RECOMB;\n    option->nodrop         = TRUE;\n    option->signatures     = FALSE;\n    option->verb           = 0;\n    option->gaOnOff        = 0;\n    option->populationSize = 0;\t/* use default */\n    option->numberXovers   = 0;\t/* use default */\n    option->bdddump\t   = FALSE;\n    option->dumpFmt\t   = 0;\t/* dot */\n    option->dumpfile\t   = NULL;\n    option->store          = -1; /* do not store */\n    option->storefile      = NULL;\n    option->load           = FALSE;\n    option->loadfile       = NULL;\n    option->seed           = 1;\n\n    return(option);\n\n} /* end of mainInit */\n\n\n/**\n  @brief Reads the command line options.\n\n  @details Scans the command line one argument at a time and performs\n  a switch on each arguement it hits.  Some arguemnts also read in the\n  following arg from the list (i.e., -f also gets the filename which\n  should folow.)  Gives a usage message and exits if any unrecognized\n  args are found.\n\n  @sideeffect May initialize the random number generator.\n\n  @see mainInit ntrReadOptionsFile\n\n*/\nstatic void\nntrReadOptions(\n  int  argc,\n  char ** argv,\n  NtrOptions * option)\n{\n    int\ti = 0;\n\n    if (argc < 2) goto usage;\n\n    if (STRING_EQUAL(argv[1],\"-f\")) {\n\tntrReadOptionsFile(argv[2],&argv,&argc);\n    }\n\n    for (i = 1; i < argc; i++) {\n\tif (argv[i][0] != '-' ) {\n\t    if (option->file1 == NULL) {\n\t\toption->file1 = util_strsav(argv[i]);\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-second\")) {\n\t    i++;\n\t    option->file2 = util_strsav(argv[i]);\n\t    option->second = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-verify\")) {\n\t    i++;\n\t    option->file2 = util_strsav(argv[i]);\n\t    option->verify = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-trav\")) {\n\t    option->traverse = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-depend\")) {\n\t    option->traverse = TRUE;\n\t    option->depend = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-image\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"part\")) {\n\t\toption->image = NTR_IMAGE_PART;\n\t    } else if (STRING_EQUAL(argv[i],\"clip\")) {\n\t\toption->image = NTR_IMAGE_CLIP;\n\t    } else if (STRING_EQUAL(argv[i],\"depend\")) {\n\t\toption->image = NTR_IMAGE_DEPEND;\n\t    } else if (STRING_EQUAL(argv[i],\"mono\")) {\n\t\toption->image = NTR_IMAGE_MONO;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-depth\")) {\n\t    i++;\n\t    option->imageClip = (double) atof(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-cdepth\")) {\n\t    i++;\n\t    option->closureClip = (double) atof(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-approx\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"under\")) {\n\t\toption->approx = NTR_UNDER_APPROX;\n\t    } else if (STRING_EQUAL(argv[i],\"over\")) {\n\t\toption->approx = NTR_OVER_APPROX;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-threshold\")) {\n\t    i++;\n\t    option->threshold = (int) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-from\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"new\")) {\n\t\toption->from = NTR_FROM_NEW;\n\t    } else if (STRING_EQUAL(argv[i],\"reached\")) {\n\t\toption->from = NTR_FROM_REACHED;\n\t    } else if (STRING_EQUAL(argv[i],\"restrict\")) {\n\t\toption->from = NTR_FROM_RESTRICT;\n\t    } else if (STRING_EQUAL(argv[i],\"compact\")) {\n\t\toption->from = NTR_FROM_COMPACT;\n\t    } else if (STRING_EQUAL(argv[i],\"squeeze\")) {\n\t\toption->from = NTR_FROM_SQUEEZE;\n\t    } else if (STRING_EQUAL(argv[i],\"subset\")) {\n\t\toption->from = NTR_FROM_UNDERAPPROX;\n\t    } else if (STRING_EQUAL(argv[i],\"superset\")) {\n\t\toption->from = NTR_FROM_OVERAPPROX;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-groupnsps\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"none\")) {\n\t\toption->groupnsps = NTR_GROUP_NONE;\n\t    } else if (STRING_EQUAL(argv[i],\"default\")) {\n\t\toption->groupnsps = NTR_GROUP_DEFAULT;\n\t    } else if (STRING_EQUAL(argv[i],\"fixed\")) {\n\t\toption->groupnsps = NTR_GROUP_FIXED;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-closure\")) {\n\t    option->closure = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-envelope\")) {\n\t    option->envelope = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-scc\")) {\n\t    option->scc = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-maxflow\")) {\n\t    option->maxflow = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-shortpaths\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"none\")) {\n\t\toption->shortPath = NTR_SHORT_NONE;\n\t    } else if (STRING_EQUAL(argv[i],\"bellman\")) {\n\t\toption->shortPath = NTR_SHORT_BELLMAN;\n\t    } else if (STRING_EQUAL(argv[i],\"floyd\")) {\n\t\toption->shortPath = NTR_SHORT_FLOYD;\n\t    } else if (STRING_EQUAL(argv[i],\"square\")) {\n\t\toption->shortPath = NTR_SHORT_SQUARE;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-selective\")) {\n\t    option->selectiveTrace = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-zdd\")) {\n\t    option->zddtest = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-cover\")) {\n\t    option->zddtest = TRUE;\n\t    option->printcover = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-sink\")) {\n\t    i++;\n\t    option->maxflow = TRUE;\n\t    option->sinkfile = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-part\")) {\n\t    option->partition = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-char2vect\")) {\n\t    option->char2vect = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-density\")) {\n\t    option->density = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-quality\")) {\n\t    i++;\n\t    option->quality = (double) atof(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-decomp\")) {\n\t    option->decomp = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-cofest\")) {\n\t    option->cofest = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-clip\")) {\n\t    i++;\n\t    option->clip = (double) atof(argv[i]);\n\t    i++;\n\t    option->file2 = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-dctest\")) {\n\t    option->dontcares = TRUE;\n\t    i++;\n\t    option->file2 = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-closest\")) {\n\t    option->closestCube = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-clauses\")) {\n\t    option->clauses = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-nobuild\")) {\n\t    option->noBuild = TRUE;\n\t    option->reordering = CUDD_REORDER_NONE;\n\t} else if (STRING_EQUAL(argv[i],\"-delta\")) {\n\t    option->stateOnly = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-node\")) {\n\t    i++;\n\t    option->node = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-local\")) {\n\t    option->locGlob = BNET_LOCAL_DD;\n\t} else if (STRING_EQUAL(argv[i],\"-progress\")) {\n\t    option->progress = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-cache\")) {\n\t    i++;\n\t    option->cacheSize = (int) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-maxmem\")) {\n\t    i++;\n\t    option->maxMemory = 1048576 * (int) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-memhard\")) {\n\t    i++;\n\t    option->maxMemHard = 1048576 * (int) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-maxlive\")) {\n\t    i++;\n\t    option->maxLive = (unsigned int) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-slots\")) {\n\t    i++;\n\t    option->slots = (int) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-ordering\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"dfs\")) {\n\t\toption->ordering = PI_PS_DFS;\n\t    } else if (STRING_EQUAL(argv[i],\"hw\")) {\n\t\toption->ordering = PI_PS_FROM_FILE;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-order\")) {\n\t    i++;\n\t    option->ordering = PI_PS_GIVEN;\n\t    option->orderPiPs = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-reordering\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"none\")) {\n\t\toption->reordering = CUDD_REORDER_NONE;\n\t    } else if (STRING_EQUAL(argv[i],\"random\")) {\n\t\toption->reordering = CUDD_REORDER_RANDOM;\n\t    } else if (STRING_EQUAL(argv[i],\"bernard\") ||\n\t\tSTRING_EQUAL(argv[i],\"pivot\")) {\n\t\toption->reordering = CUDD_REORDER_RANDOM_PIVOT;\n\t    } else if (STRING_EQUAL(argv[i],\"sifting\")) {\n\t\toption->reordering = CUDD_REORDER_SIFT;\n\t    } else if (STRING_EQUAL(argv[i],\"converge\")) {\n\t\toption->reordering = CUDD_REORDER_SIFT_CONVERGE;\n\t    } else if (STRING_EQUAL(argv[i],\"symm\")) {\n\t\toption->reordering = CUDD_REORDER_SYMM_SIFT;\n\t    } else if (STRING_EQUAL(argv[i],\"cosymm\")) {\n\t\toption->reordering = CUDD_REORDER_SYMM_SIFT_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"tree\") ||\n\t\tSTRING_EQUAL(argv[i],\"group\")) {\n\t\toption->reordering = CUDD_REORDER_GROUP_SIFT;\n\t    } else if (STRING_EQUAL(argv[i],\"cotree\") ||\n\t\tSTRING_EQUAL(argv[i],\"cogroup\")) {\n\t\toption->reordering = CUDD_REORDER_GROUP_SIFT_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"win2\")) {\n\t\toption->reordering = CUDD_REORDER_WINDOW2;\n\t    } else if (STRING_EQUAL(argv[i],\"win3\")) {\n\t\toption->reordering = CUDD_REORDER_WINDOW3;\n\t    } else if (STRING_EQUAL(argv[i],\"win4\")) {\n\t\toption->reordering = CUDD_REORDER_WINDOW4;\n\t    } else if (STRING_EQUAL(argv[i],\"win2conv\")) {\n\t\toption->reordering = CUDD_REORDER_WINDOW2_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"win3conv\")) {\n\t\toption->reordering = CUDD_REORDER_WINDOW3_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"win4conv\")) {\n\t\toption->reordering = CUDD_REORDER_WINDOW4_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"annealing\")) {\n\t\toption->reordering = CUDD_REORDER_ANNEALING;\n\t    } else if (STRING_EQUAL(argv[i],\"genetic\")) {\n\t\toption->reordering = CUDD_REORDER_GENETIC;\n\t    } else if (STRING_EQUAL(argv[i],\"linear\")) {\n\t\toption->reordering = CUDD_REORDER_LINEAR;\n\t    } else if (STRING_EQUAL(argv[i],\"linconv\")) {\n\t\toption->reordering = CUDD_REORDER_LINEAR_CONVERGE;\n\t    } else if (STRING_EQUAL(argv[i],\"exact\")) {\n\t\toption->reordering = CUDD_REORDER_EXACT;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-autodyn\")) {\n\t    option->autoDyn = 3;\n\t} else if (STRING_EQUAL(argv[i],\"-autodynB\")) {\n\t    option->autoDyn |= 1;\n\t} else if (STRING_EQUAL(argv[i],\"-autodynZ\")) {\n\t    option->autoDyn |= 2;\n\t} else if (STRING_EQUAL(argv[i],\"-automethod\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"none\")) {\n\t\toption->autoMethod = CUDD_REORDER_NONE;\n\t    } else if (STRING_EQUAL(argv[i],\"random\")) {\n\t\toption->autoMethod = CUDD_REORDER_RANDOM;\n\t    } else if (STRING_EQUAL(argv[i],\"bernard\") ||\n\t\tSTRING_EQUAL(argv[i],\"pivot\")) {\n\t\toption->autoMethod = CUDD_REORDER_RANDOM_PIVOT;\n\t    } else if (STRING_EQUAL(argv[i],\"sifting\")) {\n\t\toption->autoMethod = CUDD_REORDER_SIFT;\n\t    } else if (STRING_EQUAL(argv[i],\"converge\")) {\n\t\toption->autoMethod = CUDD_REORDER_SIFT_CONVERGE;\n\t    } else if (STRING_EQUAL(argv[i],\"symm\")) {\n\t\toption->autoMethod = CUDD_REORDER_SYMM_SIFT;\n\t    } else if (STRING_EQUAL(argv[i],\"cosymm\")) {\n\t\toption->autoMethod = CUDD_REORDER_SYMM_SIFT_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"tree\") ||\n\t\tSTRING_EQUAL(argv[i],\"group\")) {\n\t\toption->autoMethod = CUDD_REORDER_GROUP_SIFT;\n\t    } else if (STRING_EQUAL(argv[i],\"cotree\") ||\n\t\tSTRING_EQUAL(argv[i],\"cogroup\")) {\n\t\toption->autoMethod = CUDD_REORDER_GROUP_SIFT_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"win2\")) {\n\t\toption->autoMethod = CUDD_REORDER_WINDOW2;\n\t    } else if (STRING_EQUAL(argv[i],\"win3\")) {\n\t\toption->autoMethod = CUDD_REORDER_WINDOW3;\n\t    } else if (STRING_EQUAL(argv[i],\"win4\")) {\n\t\toption->autoMethod = CUDD_REORDER_WINDOW4;\n\t    } else if (STRING_EQUAL(argv[i],\"win2conv\")) {\n\t\toption->autoMethod = CUDD_REORDER_WINDOW2_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"win3conv\")) {\n\t\toption->autoMethod = CUDD_REORDER_WINDOW3_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"win4conv\")) {\n\t\toption->autoMethod = CUDD_REORDER_WINDOW4_CONV;\n\t    } else if (STRING_EQUAL(argv[i],\"annealing\")) {\n\t\toption->autoMethod = CUDD_REORDER_ANNEALING;\n\t    } else if (STRING_EQUAL(argv[i],\"genetic\")) {\n\t\toption->autoMethod = CUDD_REORDER_GENETIC;\n\t    } else if (STRING_EQUAL(argv[i],\"linear\")) {\n\t\toption->autoMethod = CUDD_REORDER_LINEAR;\n\t    } else if (STRING_EQUAL(argv[i],\"linconv\")) {\n\t\toption->autoMethod = CUDD_REORDER_LINEAR_CONVERGE;\n\t    } else if (STRING_EQUAL(argv[i],\"exact\")) {\n\t\toption->autoMethod = CUDD_REORDER_EXACT;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-tree\")) {\n\t    i++;\n\t    option->treefile = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-first\")) {\n\t    i++;\n\t    option->firstReorder = (int)atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-countdead\")) {\n\t    option->countDead = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-growth\")) {\n\t    i++;\n\t    option->maxGrowth = (int)atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-groupcheck\")) {\n\t    i++;\n\t    if (STRING_EQUAL(argv[i],\"check\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK;\n\t    } else if (STRING_EQUAL(argv[i],\"nocheck\")) {\n\t\toption->groupcheck = CUDD_NO_CHECK;\n\t    } else if (STRING_EQUAL(argv[i],\"check2\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK2;\n\t    } else if (STRING_EQUAL(argv[i],\"check3\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK3;\n\t    } else if (STRING_EQUAL(argv[i],\"check4\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK4;\n\t    } else if (STRING_EQUAL(argv[i],\"check5\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK5;\n\t    } else if (STRING_EQUAL(argv[i],\"check6\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK6;\n\t    } else if (STRING_EQUAL(argv[i],\"check7\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK7;\n\t    } else if (STRING_EQUAL(argv[i],\"check8\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK8;\n\t    } else if (STRING_EQUAL(argv[i],\"check9\")) {\n\t\toption->groupcheck = CUDD_GROUP_CHECK9;\n\t    } else {\n\t\tgoto usage;\n\t    }\n\t} else if (STRING_EQUAL(argv[i],\"-arcviolation\")) {\n\t    i++;\n\t    option->arcviolation = (int)atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-symmviolation\")) {\n\t    i++;\n\t    option->symmviolation = (int)atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-recomb\")) {\n\t    i++;\n\t    option->recomb = (int)atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-drop\")) {\n\t    option->nodrop = FALSE;\n\t} else if (STRING_EQUAL(argv[i],\"-sign\")) {\n\t    option->signatures = TRUE;\n\t} else if (STRING_EQUAL(argv[i],\"-genetic\")) {\n\t    option->gaOnOff = 1;\n\t} else if (STRING_EQUAL(argv[i],\"-genepop\")) {\n\t    option->gaOnOff = 1;\n\t    i++;\n\t    option->populationSize = (int)atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-genexover\")) {\n\t    option->gaOnOff = 1;\n\t    i++;\n\t    option->numberXovers = (int) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-seed\")) {\n\t    i++;\n            option->seed = (int32_t) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-dumpfile\")) {\n\t    i++;\n\t    option->bdddump = TRUE;\n\t    option->dumpfile = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-dumpblif\")) {\n\t    option->dumpFmt = 1; /* blif */\n\t} else if (STRING_EQUAL(argv[i],\"-dumpdaVinci\")) {\n\t    option->dumpFmt = 2; /* daVinci */\n\t} else if (STRING_EQUAL(argv[i],\"-dumpddcal\")) {\n\t    option->dumpFmt = 3; /* DDcal */\n\t} else if (STRING_EQUAL(argv[i],\"-dumpfact\")) {\n\t    option->dumpFmt = 4; /* factored form */\n\t} else if (STRING_EQUAL(argv[i],\"-dumpmv\")) {\n\t    option->dumpFmt = 5; /* blif-MV */\n\t} else if (STRING_EQUAL(argv[i],\"-store\")) {\n\t    i++;\n\t    option->store = (int) atoi(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-storefile\")) {\n\t    i++;\n\t    option->storefile = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-loadfile\")) {\n\t    i++;\n\t    option->load = 1;\n\t    option->loadfile = util_strsav(argv[i]);\n\t} else if (STRING_EQUAL(argv[i],\"-p\")) {\n\t    i++;\n\t    option->verb = (int) atoi(argv[i]);\n\t} else {\n\t    goto usage;\n\t}\n    }\n\n    if (option->store >= 0 && option->storefile == NULL) {\n\t(void) fprintf(stdout,\"-storefile mandatory with -store\\n\");\n\texit(-1);\n    }\n\n    if (option->verb >= 0) {\n\t(void) printf(\"# %s\\n\", NTR_VERSION);\n\t/* echo command line and arguments */\n\t(void) printf(\"#\");\n\tfor (i = 0; i < argc; i++) {\n\t    (void) printf(\" %s\", argv[i]);\n\t}\n\t(void) printf(\"\\n\");\n\t(void) printf(\"# CUDD Version \");\n\tCudd_PrintVersion(stdout);\n\t(void) fflush(stdout);\n    }\n\n    return;\n\nusage:\t/* convenient goto */\n    printf(\"Usage: please read man page\\n\");\n    if (i == 0) {\n\t(void) fprintf(stdout,\"too few arguments\\n\");\n    } else {\n\t(void) fprintf(stdout,\"option: %s is not defined\\n\",argv[i]);\n    }\n    exit(-1);\n\n} /* end of ntrReadOptions */\n\n\n/**\n  @brief Reads the program options from a file.\n\n  @details Opens file. Reads the command line from the otpions file\n  using the read_line func. Scans the line looking for spaces, each\n  space is a searator and demarks a new option.  When a space is\n  found, it is changed to a \\0 to terminate that string; then the next\n  value of slot points to the next non-space character.  There is a\n  limit of 1024 options.  Should produce an error (presently doesn't)\n  on overrun of options, but this is very unlikely to happen.\n\n  @sideeffect none\n\n*/\nstatic void\nntrReadOptionsFile(\n  char * name,\n  char *** argv,\n  int * argc)\n{\n    char\t**slot;\n    char\t*line;\n    char\tc;\n    int\t\tindex,flag;\n    FILE\t*fp;\n\n    if ((fp = fopen(name,\"r\")) == NULL) {\n\tfprintf(stderr,\"Error: can not find cmd file %s\\n\",name);\n\texit(-1);\n    }\n\n    slot = ALLOC(char *,1024);\n    index = 1;\n    line = readLine(fp);\n    flag = TRUE;\n\n    do {\n\tc = *line;\n\tif ( c == ' ')  {\n\t    flag = TRUE;\n\t    *line = '\\0';\n\t} else if ( c != ' ' && flag == TRUE) {\n\t    flag = FALSE;\n\t    slot[index] = line;\n\t    index++;\n\t}\n\tline++;\n    } while ( *line != '\\0');\n\n\n    *argv = slot;\n    *argc = index;\n\n    fclose(fp);\n\n} /* end of ntrReadOptionsFile */\n\n\n/**\n  @brief Reads a line from the option file.\n\n  @sideeffect none\n\n*/\nstatic char*\nreadLine(\n  FILE * fp)\n{\n    int  c;\n    char *pbuffer;\n\n    pbuffer = buffer;\n\n    /* Strip white space from beginning of line. */\n    for(;;) {\n\tc = getc(fp);\n\tif ( c == EOF) return(NULL);\n\tif ( c == '\\n') {\n\t    *pbuffer = '\\0';\n\t    return(buffer); /* got a blank line */\n\t}\n\tif ( c != ' ') break;\n    }\n    do {\n\tif ( c == '\\\\' ) { /* if we have a continuation character.. */\n\t    do {\t/* scan to end of line */\n\t\tc = getc(fp);\n\t\tif ( c == '\\n' ) break;\n\t    } while ( c != EOF);\n\t    if ( c != EOF) {\n\t\t*pbuffer = ' ';\n\t\tpbuffer++;\n\t    } else return( buffer);\n\t    c = getc(fp);\n\t    continue;\n\t}\n\t*pbuffer = (char) c;\n\tpbuffer++;\n\tc = getc(fp);\n    } while( c != '\\n' &&  c != EOF);\n    *pbuffer = '\\0';\n    return(buffer);\n\n} /* end of readLine */\n\n\n/**\n  @brief Opens a file.\n\n  @details Opens a file, or fails with an error message and exits.\n  Allows '-' as a synonym for standard input.\n\n  @sideeffect None\n\n*/\nstatic FILE *\nopen_file(\n  char * filename,\n  const char * mode)\n{\n    FILE *fp;\n\n    if (strcmp(filename, \"-\") == 0) {\n\treturn mode[0] == 'r' ? stdin : stdout;\n    } else if ((fp = fopen(filename, mode)) == NULL) {\n\tperror(filename);\n\texit(1);\n    }\n    return(fp);\n\n} /* end of open_file */\n\n\n/**\n  @brief Explicitly applies reordering to the DDs.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nreorder(\n  BnetNetwork * net,\n  DdManager * dd,\n  NtrOptions * option)\n{\n#ifdef DD_DEBUG\n    st_table\t*mintermTable;\t/* minterm counts for each output */\n#endif\n    int result;\t\t\t/* return value from functions */\n\n    (void) printf(\"Number of inputs = %d\\n\",net->ninputs);\n\n    /* Perform the final reordering */\n    if (option->reordering != CUDD_REORDER_NONE) {\n#ifdef DD_DEBUG\n\tresult = Cudd_DebugCheck(dd);\n\tif (result != 0) {\n\t    (void) fprintf(stderr,\"Error reported by Cudd_DebugCheck\\n\");\n\t    return(0);\n\t}\n\tresult = Cudd_CheckKeys(dd);\n\tif (result != 0) {\n\t    (void) fprintf(stderr,\"Error reported by Cudd_CheckKeys\\n\");\n\t    return(0);\n\t}\n\tmintermTable = checkMinterms(net,dd,NULL);\n\tif (mintermTable == NULL) exit(2);\n#endif\n\n\tdd->siftMaxVar = 1000000;\n\tdd->siftMaxSwap = 1000000000;\n\tresult = Cudd_ReduceHeap(dd,option->reordering,1);\n\tif (result == 0) return(0);\n#ifdef DD_DEBUG\n\tresult = Cudd_DebugCheck(dd);\n\tif (result != 0) {\n\t    (void) fprintf(stderr,\"Error reported by Cudd_DebugCheck\\n\");\n\t    return(0);\n\t}\n\tresult = Cudd_CheckKeys(dd);\n\tif (result != 0) {\n\t    (void) fprintf(stderr,\"Error reported by Cudd_CheckKeys\\n\");\n\t    return(0);\n\t}\n\tmintermTable = checkMinterms(net,dd,mintermTable);\n        if (mintermTable != NULL) {\n            (void) fprintf(stderr,\"Error in checkMinterms\\n\");\n            return(0);\n        }\n#endif\n\n\t/* Print symmetry stats if pertinent */\n\tif (dd->tree == NULL &&\n\t    (option->reordering == CUDD_REORDER_SYMM_SIFT ||\n\t    option->reordering == CUDD_REORDER_SYMM_SIFT_CONV))\n\t    Cudd_SymmProfile(dd,0,dd->size - 1);\n    }\n\n    if (option->gaOnOff) {\n\tresult = Cudd_ReduceHeap(dd,CUDD_REORDER_GENETIC,1);\n\tif (result == 0) {\n\t    (void) printf(\"Something went wrong in cuddGa\\n\");\n\t    return(0);\n\t}\n    }\n\n    return(1);\n\n} /* end of reorder */\n\n\n/**\n  @brief Frees the option structure and its appendages.\n\n  @sideeffect None\n\n*/\nstatic void\nfreeOption(\n  NtrOptions * option)\n{\n    if (option->file1 != NULL) FREE(option->file1);\n    if (option->file2 != NULL) FREE(option->file2);\n    if (option->orderPiPs != NULL) FREE(option->orderPiPs);\n    if (option->treefile != NULL) FREE(option->treefile);\n    if (option->sinkfile != NULL) FREE(option->sinkfile);\n    if (option->dumpfile != NULL) FREE(option->dumpfile);\n    if (option->loadfile != NULL) FREE(option->loadfile);\n    if (option->storefile != NULL) FREE(option->storefile);\n    if (option->node != NULL) FREE(option->node);\n    FREE(option);\n\n} /* end of freeOption */\n\n\n/**\n  @brief Starts the CUDD manager with the desired options.\n\n  @details Starts with 0 variables, because Ntr_buildDDs will create\n  new variables rather than using whatever already exists.\n\n  @sideeffect None\n\n*/\nstatic DdManager *\nstartCudd(\n  NtrOptions * option,\n  int  nvars)\n{\n    DdManager *dd;\n    int result;\n\n    dd = Cudd_Init(0, 0, option->slots, option->cacheSize, option->maxMemory);\n    if (dd == NULL) return(NULL);\n\n    Cudd_Srandom(dd, option->seed);\n    if (option->maxMemHard != 0) {\n\tCudd_SetMaxMemory(dd,option->maxMemHard);\n    }\n    Cudd_SetMaxLive(dd,option->maxLive);\n    Cudd_SetGroupcheck(dd,option->groupcheck);\n    if (option->autoDyn & 1) {\n\tCudd_AutodynEnable(dd,option->autoMethod);\n    }\n    dd->nextDyn = option->firstReorder;\n    dd->countDead = (option->countDead == FALSE) ? ~0 : 0;\n    dd->maxGrowth = 1.0 + ((float) option->maxGrowth / 100.0);\n    dd->recomb = option->recomb;\n    dd->arcviolation = option->arcviolation;\n    dd->symmviolation = option->symmviolation;\n    dd->populationSize = option->populationSize;\n    dd->numberXovers = option->numberXovers;\n    result = ntrReadTree(dd,option->treefile,nvars);\n    if (result == 0) {\n\tCudd_Quit(dd);\n\treturn(NULL);\n    }\n#ifndef DD_STATS\n    result = Cudd_EnableReorderingReporting(dd);\n    if (result == 0) {\n\t(void) fprintf(stderr,\n\t\t       \"Error reported by Cudd_EnableReorderingReporting\\n\");\n\tCudd_Quit(dd);\n\treturn(NULL);\n    }\n#endif\n\n    return(dd);\n\n} /* end of startCudd */\n\n\n/**\n  @brief Reads the variable group tree from a file.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nntrReadTree(\n  DdManager * dd,\n  char * treefile,\n  int  nvars)\n{\n    FILE *fp;\n    MtrNode *root;\n\n    if (treefile == NULL) {\n\treturn(1);\n    }\n\n    if ((fp = fopen(treefile,\"r\")) == NULL) {\n\t(void) fprintf(stderr,\"Unable to open %s\\n\",treefile);\n\treturn(0);\n    }\n\n    root = Mtr_ReadGroups(fp,ddMax(Cudd_ReadSize(dd),nvars));\n    if (root == NULL) {\n\treturn(0);\n    }\n\n    Cudd_SetTree(dd,root);\n\n    return(1);\n\n} /* end of ntrReadTree */\n"
  },
  {
    "path": "cudd/nanotrav/miniFirst.blif",
    "content": ".model first\n.inputs a b c d\n.outputs A\n.names a b c d A\n--01 0\n-0-0 0\n-011 0\n1-00 0\n01-0 0\n.end\n"
  },
  {
    "path": "cudd/nanotrav/miniFirst.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -second ./nanotrav/miniSecond.blif ./nanotrav/miniFirst.blif\n# CUDD Version 3.0.0\nOrder before final reordering\na b c d \nNumber of inputs = 4\nTesting BDD minimization algorithms\nTEST-MINI: Constrain (B) 4 nodes\nTEST-MINI:: A\nT-M    : 7 nodes 1 leaves 3 minterms\nT-M L1 : 5 nodes 1 leaves 6 minterms\nT-M M1 : 5 nodes 1 leaves 6 minterms\nT-M R1 : 5 nodes 1 leaves 6 minterms\nT-M C1 : 5 nodes 1 leaves 6 minterms\nTEST-MINI: (lb,ub) : (7,7) nodes\nT-M S1 : 5 nodes 1 leaves 6 minterms\nT-M N1 : 7 nodes 1 leaves 3 minterms\nT-M A1 : 7 nodes 1 leaves 3 minterms\nTEST-MINI: f 7 comp 5 mini 5 rest 5 cons 5 sque 5 na 7 and 7\nTEST-MINI:: A\nT-M    : 7 nodes 1 leaves 3 minterms\nT-M L0 : is the zero DD\nT-M M0 : is the zero DD\nT-M R0 : is the zero DD\nT-M C0 : is the zero DD\nTEST-MINI: (lb,ub) : (1,4) nodes\nT-M S0 : is the zero DD\nT-M N0 : is the zero DD\nT-M A0 : is the zero DD\nTEST-MINI: f 7 comp 1 mini 1 rest 1 cons 1 sque 1 na 1, and 1\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 4004\n**** CUDD non-modifiable parameters ****\nMemory in use: 3183024\nPeak number of nodes: 1022\nPeak number of live nodes: 22\nNumber of BDD variables: 4\nNumber of ZDD variables: 0\nNumber of cache entries: 32768\nNumber of cache look-ups: 89\nNumber of cache hits: 23\nNumber of cache insertions: 63\nNumber of cache collisions: 0\nNumber of cache deletions: 0\nCache used slots = 0.19% (expected 0.19%)\nSoft limit for cache size: 5120\nNumber of buckets in unique table: 1280\nUsed buckets in unique table: 2.89% (expected 3.21%)\nNumber of BDD and ADD nodes: 42\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 28\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 42\nTotal number of nodes reclaimed: 17\nGarbage collections so far: 0\nTime for garbage collection: 0.00 sec\nReorderings so far: 0\nTime for reordering: 0.00 sec\nFinal size: 9\ntotal time = 0.00 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  5960K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 891\nSwaps = 0\nInput blocks = 0\nOutput blocks = 8\nContext switch (voluntary) = 0\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/miniSecond.blif",
    "content": ".model second\n.inputs a b c\n.outputs B\n.names a b c B\n000 1\n-11 1\n101 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/mult32a.blif",
    "content": ".model MultiplierA_32\n.inputs 1 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 \n.outputs 68 \n.latch 67 2  0\n.latch 69 36  0\n.latch 70 37  0\n.latch 71 38  0\n.latch 72 39  0\n.latch 73 40  0\n.latch 74 41  0\n.latch 75 42  0\n.latch 76 43  0\n.latch 77 44  0\n.latch 78 45  0\n.latch 79 46  0\n.latch 80 47  0\n.latch 81 48  0\n.latch 82 49  0\n.latch 83 50  0\n.latch 84 51  0\n.latch 85 52  0\n.latch 86 53  0\n.latch 87 54  0\n.latch 88 55  0\n.latch 89 56  0\n.latch 90 57  0\n.latch 91 58  0\n.latch 92 59  0\n.latch 93 60  0\n.latch 94 61  0\n.latch 95 62  0\n.latch 96 63  0\n.latch 97 64  0\n.latch 98 65  0\n.latch 99 66  0\n.names 101 100\n0 1\n.names 1 204 101\n00 1\n11 1\n.names 3 102\n1 1\n.names 4 103\n1 1\n.names 5 104\n1 1\n.names 6 105\n1 1\n.names 7 106\n1 1\n.names 8 107\n1 1\n.names 9 108\n1 1\n.names 10 109\n1 1\n.names 11 110\n1 1\n.names 12 111\n1 1\n.names 13 112\n1 1\n.names 14 113\n1 1\n.names 15 114\n1 1\n.names 16 115\n1 1\n.names 17 116\n1 1\n.names 18 117\n1 1\n.names 19 118\n1 1\n.names 20 119\n1 1\n.names 21 120\n1 1\n.names 22 121\n1 1\n.names 23 122\n1 1\n.names 24 123\n1 1\n.names 25 124\n1 1\n.names 26 125\n1 1\n.names 27 126\n1 1\n.names 28 127\n1 1\n.names 29 128\n1 1\n.names 30 129\n1 1\n.names 31 130\n1 1\n.names 32 131\n1 1\n.names 33 132\n1 1\n.names 34 133\n1 1\n.names 134\n.names 135\n.names 136\n.names 137\n.names 138\n.names 139\n.names 140\n.names 141\n.names 142\n.names 143\n.names 144\n.names 145\n.names 146\n.names 147\n.names 148\n.names 149\n.names 150\n.names 151\n.names 152\n.names 153\n.names 154\n.names 155\n.names 156\n.names 157\n.names 158\n.names 159\n.names 160\n.names 161\n.names 162\n.names 163\n.names 164\n.names 165\n.names 66 265 266 166\n-11 1\n1-1 1\n11- 1\n.names 36 205 206 167\n010 1\n001 1\n100 1\n111 1\n.names 37 207 208 168\n010 1\n001 1\n100 1\n111 1\n.names 38 209 210 169\n010 1\n001 1\n100 1\n111 1\n.names 39 211 212 170\n010 1\n001 1\n100 1\n111 1\n.names 40 213 214 171\n010 1\n001 1\n100 1\n111 1\n.names 41 215 216 172\n010 1\n001 1\n100 1\n111 1\n.names 42 217 218 173\n010 1\n001 1\n100 1\n111 1\n.names 43 219 220 174\n010 1\n001 1\n100 1\n111 1\n.names 44 221 222 175\n010 1\n001 1\n100 1\n111 1\n.names 45 223 224 176\n010 1\n001 1\n100 1\n111 1\n.names 46 225 226 177\n010 1\n001 1\n100 1\n111 1\n.names 47 227 228 178\n010 1\n001 1\n100 1\n111 1\n.names 48 229 230 179\n010 1\n001 1\n100 1\n111 1\n.names 49 231 232 180\n010 1\n001 1\n100 1\n111 1\n.names 50 233 234 181\n010 1\n001 1\n100 1\n111 1\n.names 51 235 236 182\n010 1\n001 1\n100 1\n111 1\n.names 52 237 238 183\n010 1\n001 1\n100 1\n111 1\n.names 53 239 240 184\n010 1\n001 1\n100 1\n111 1\n.names 54 241 242 185\n010 1\n001 1\n100 1\n111 1\n.names 55 243 244 186\n010 1\n001 1\n100 1\n111 1\n.names 56 245 246 187\n010 1\n001 1\n100 1\n111 1\n.names 57 247 248 188\n010 1\n001 1\n100 1\n111 1\n.names 58 249 250 189\n010 1\n001 1\n100 1\n111 1\n.names 59 251 252 190\n010 1\n001 1\n100 1\n111 1\n.names 60 253 254 191\n010 1\n001 1\n100 1\n111 1\n.names 61 255 256 192\n010 1\n001 1\n100 1\n111 1\n.names 62 257 258 193\n010 1\n001 1\n100 1\n111 1\n.names 63 259 260 194\n010 1\n001 1\n100 1\n111 1\n.names 64 261 262 195\n010 1\n001 1\n100 1\n111 1\n.names 65 263 264 196\n010 1\n001 1\n100 1\n111 1\n.names 66 265 266 197\n010 1\n001 1\n100 1\n111 1\n.names 2 268 198\n10 1\n01 1\n.names 269 270 199\n11 1\n.names 166 272 200\n11 1\n.names 166 274 201\n11 1\n.names 166 275 202\n11 1\n.names 276 277 203\n-1 1\n1- 1\n.names 204\n.names 205\n.names 340 341 206\n-1 1\n1- 1\n.names 36 205 206 207\n-11 1\n1-1 1\n11- 1\n.names 338 339 208\n-1 1\n1- 1\n.names 37 207 208 209\n-11 1\n1-1 1\n11- 1\n.names 336 337 210\n-1 1\n1- 1\n.names 38 209 210 211\n-11 1\n1-1 1\n11- 1\n.names 334 335 212\n-1 1\n1- 1\n.names 39 211 212 213\n-11 1\n1-1 1\n11- 1\n.names 332 333 214\n-1 1\n1- 1\n.names 40 213 214 215\n-11 1\n1-1 1\n11- 1\n.names 330 331 216\n-1 1\n1- 1\n.names 41 215 216 217\n-11 1\n1-1 1\n11- 1\n.names 328 329 218\n-1 1\n1- 1\n.names 42 217 218 219\n-11 1\n1-1 1\n11- 1\n.names 326 327 220\n-1 1\n1- 1\n.names 43 219 220 221\n-11 1\n1-1 1\n11- 1\n.names 324 325 222\n-1 1\n1- 1\n.names 44 221 222 223\n-11 1\n1-1 1\n11- 1\n.names 322 323 224\n-1 1\n1- 1\n.names 45 223 224 225\n-11 1\n1-1 1\n11- 1\n.names 320 321 226\n-1 1\n1- 1\n.names 46 225 226 227\n-11 1\n1-1 1\n11- 1\n.names 318 319 228\n-1 1\n1- 1\n.names 47 227 228 229\n-11 1\n1-1 1\n11- 1\n.names 316 317 230\n-1 1\n1- 1\n.names 48 229 230 231\n-11 1\n1-1 1\n11- 1\n.names 314 315 232\n-1 1\n1- 1\n.names 49 231 232 233\n-11 1\n1-1 1\n11- 1\n.names 312 313 234\n-1 1\n1- 1\n.names 50 233 234 235\n-11 1\n1-1 1\n11- 1\n.names 310 311 236\n-1 1\n1- 1\n.names 51 235 236 237\n-11 1\n1-1 1\n11- 1\n.names 308 309 238\n-1 1\n1- 1\n.names 52 237 238 239\n-11 1\n1-1 1\n11- 1\n.names 306 307 240\n-1 1\n1- 1\n.names 53 239 240 241\n-11 1\n1-1 1\n11- 1\n.names 304 305 242\n-1 1\n1- 1\n.names 54 241 242 243\n-11 1\n1-1 1\n11- 1\n.names 302 303 244\n-1 1\n1- 1\n.names 55 243 244 245\n-11 1\n1-1 1\n11- 1\n.names 300 301 246\n-1 1\n1- 1\n.names 56 245 246 247\n-11 1\n1-1 1\n11- 1\n.names 298 299 248\n-1 1\n1- 1\n.names 57 247 248 249\n-11 1\n1-1 1\n11- 1\n.names 296 297 250\n-1 1\n1- 1\n.names 58 249 250 251\n-11 1\n1-1 1\n11- 1\n.names 294 295 252\n-1 1\n1- 1\n.names 59 251 252 253\n-11 1\n1-1 1\n11- 1\n.names 292 293 254\n-1 1\n1- 1\n.names 60 253 254 255\n-11 1\n1-1 1\n11- 1\n.names 290 291 256\n-1 1\n1- 1\n.names 61 255 256 257\n-11 1\n1-1 1\n11- 1\n.names 288 289 258\n-1 1\n1- 1\n.names 62 257 258 259\n-11 1\n1-1 1\n11- 1\n.names 286 287 260\n-1 1\n1- 1\n.names 63 259 260 261\n-11 1\n1-1 1\n11- 1\n.names 284 285 262\n-1 1\n1- 1\n.names 64 261 262 263\n-11 1\n1-1 1\n11- 1\n.names 282 283 264\n-1 1\n1- 1\n.names 65 263 264 265\n-11 1\n1-1 1\n11- 1\n.names 280 281 266\n-1 1\n1- 1\n.names 278 279 267\n-1 1\n1- 1\n.names 166 267 268\n01 1\n10 1\n.names 2 267 269\n11 1\n.names 166 270\n0 1\n.names 267 271\n0 1\n.names 2 271 272\n11 1\n.names 2 273\n0 1\n.names 267 273 274\n11 1\n.names 2 267 275\n11 1\n.names 199 200 276\n-1 1\n1- 1\n.names 201 202 277\n-1 1\n1- 1\n.names 203 67\n1 1\n.names 167 68\n1 1\n.names 168 69\n1 1\n.names 169 70\n1 1\n.names 170 71\n1 1\n.names 171 72\n1 1\n.names 172 73\n1 1\n.names 173 74\n1 1\n.names 174 75\n1 1\n.names 175 76\n1 1\n.names 176 77\n1 1\n.names 177 78\n1 1\n.names 178 79\n1 1\n.names 179 80\n1 1\n.names 180 81\n1 1\n.names 181 82\n1 1\n.names 182 83\n1 1\n.names 183 84\n1 1\n.names 184 85\n1 1\n.names 185 86\n1 1\n.names 186 87\n1 1\n.names 187 88\n1 1\n.names 188 89\n1 1\n.names 189 90\n1 1\n.names 190 91\n1 1\n.names 191 92\n1 1\n.names 192 93\n1 1\n.names 193 94\n1 1\n.names 194 95\n1 1\n.names 195 96\n1 1\n.names 196 97\n1 1\n.names 197 98\n1 1\n.names 198 99\n1 1\n.names 100 133 278\n11 1\n.names 101 165 279\n11 1\n.names 100 132 280\n11 1\n.names 101 164 281\n11 1\n.names 100 131 282\n11 1\n.names 101 163 283\n11 1\n.names 100 130 284\n11 1\n.names 101 162 285\n11 1\n.names 100 129 286\n11 1\n.names 101 161 287\n11 1\n.names 100 128 288\n11 1\n.names 101 160 289\n11 1\n.names 100 127 290\n11 1\n.names 101 159 291\n11 1\n.names 100 126 292\n11 1\n.names 101 158 293\n11 1\n.names 100 125 294\n11 1\n.names 101 157 295\n11 1\n.names 100 124 296\n11 1\n.names 101 156 297\n11 1\n.names 100 123 298\n11 1\n.names 101 155 299\n11 1\n.names 100 122 300\n11 1\n.names 101 154 301\n11 1\n.names 100 121 302\n11 1\n.names 101 153 303\n11 1\n.names 100 120 304\n11 1\n.names 101 152 305\n11 1\n.names 100 119 306\n11 1\n.names 101 151 307\n11 1\n.names 100 118 308\n11 1\n.names 101 150 309\n11 1\n.names 100 117 310\n11 1\n.names 101 149 311\n11 1\n.names 100 116 312\n11 1\n.names 101 148 313\n11 1\n.names 100 115 314\n11 1\n.names 101 147 315\n11 1\n.names 100 114 316\n11 1\n.names 101 146 317\n11 1\n.names 100 113 318\n11 1\n.names 101 145 319\n11 1\n.names 100 112 320\n11 1\n.names 101 144 321\n11 1\n.names 100 111 322\n11 1\n.names 101 143 323\n11 1\n.names 100 110 324\n11 1\n.names 101 142 325\n11 1\n.names 100 109 326\n11 1\n.names 101 141 327\n11 1\n.names 100 108 328\n11 1\n.names 101 140 329\n11 1\n.names 100 107 330\n11 1\n.names 101 139 331\n11 1\n.names 100 106 332\n11 1\n.names 101 138 333\n11 1\n.names 100 105 334\n11 1\n.names 101 137 335\n11 1\n.names 100 104 336\n11 1\n.names 101 136 337\n11 1\n.names 100 103 338\n11 1\n.names 101 135 339\n11 1\n.names 100 102 340\n11 1\n.names 101 134 341\n11 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/mult32a.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -autodyn -reordering sifting -trav ./nanotrav/mult32a.blif\n# CUDD Version 3.0.0\nBDD reordering with sifting: from 4001 to ... 268 nodes in 0 sec\nBDD reordering with sifting: from 537 to ... 246 nodes in 0 sec\nBDD reordering with sifting: from 493 to ... 250 nodes in 0 sec\nBDD reordering with sifting: from 501 to ... 280 nodes in 0 sec\nBDD reordering with sifting: from 561 to ... 296 nodes in 0.01 sec\nOrder before final reordering\n2 34 33 66 32 65 31 64 \n63 30 62 29 28 61 27 60 \n26 59 25 58 24 57 23 56 \n22 55 21 54 20 53 19 52 \n51 18 50 17 49 16 48 15 \n47 14 46 13 45 12 36 3 \n37 4 38 5 39 6 40 7 \n41 8 42 9 43 10 44 11 \n1 \nNumber of inputs = 65\nBDD reordering with sifting: from 380 to ... 317 nodes in 0 sec\nNew order\n1 2 34 66 33 65 32 64 \n31 63 30 62 29 61 28 60 \n27 59 26 58 25 57 24 56 \n23 55 22 54 21 53 20 52 \n19 51 18 50 17 49 16 48 \n15 47 14 46 13 45 12 36 \n3 4 37 5 38 6 39 7 \n40 8 41 9 42 10 43 44 \n11 \nBuilding transition relation. Time = 0.01 sec\nBDD reordering with sifting: from 669 to ... 452 nodes in 0.01 sec\n@@BDD reordering with sifting: from 939 to ... 705 nodes in 0 sec\n@@BDD reordering with sifting: from 1443 to ... 847 nodes in 0.02 sec\n@@BDD reordering with sifting: from 1727 to ... 1076 nodes in 0.01 sec\n@@@BDD reordering with sifting: from 2185 to ... 770 nodes in 0.01 sec\n@@@@BDD reordering with sifting: from 1573 to ... 922 nodes in 0.01 sec\n@@@@BDD reordering with sifting: from 1877 to ... 1013 nodes in 0.01 sec\n@@@@@BDD reordering with sifting: from 2059 to ... 873 nodes in 0.02 sec\n@@@@@BDD reordering with sifting: from 1779 to ... 975 nodes in 0.01 sec\n@@@@@\nTransition relation: 1 parts 32 latches 196 nodes\nTraversing. Time = 0.11 sec\nS0: 33 nodes 1 leaves 1 minterms\nFrom[1]: 33 nodes 1 leaves 2.14748e+09 minterms\nReached[1]: 2 nodes 1 leaves 2.14748e+09 minterms\n2147483648\n2.14748e+09\nFrom[2]: 3 nodes 1 leaves 1.07374e+09 minterms\nReached[2]: 3 nodes 1 leaves 3.22123e+09 minterms\n3221225472\n3.22123e+09\nFrom[3]: 4 nodes 1 leaves 5.36871e+08 minterms\nReached[3]: 4 nodes 1 leaves 3.7581e+09 minterms\n3758096384\n3.7581e+09\nFrom[4]: 5 nodes 1 leaves 2.68435e+08 minterms\nReached[4]: 5 nodes 1 leaves 4.02653e+09 minterms\n4026531840\n4.02653e+09\nFrom[5]: 6 nodes 1 leaves 1.34218e+08 minterms\nReached[5]: 6 nodes 1 leaves 4.16075e+09 minterms\n4160749568\n4.16075e+09\nFrom[6]: 7 nodes 1 leaves 6.71089e+07 minterms\nReached[6]: 7 nodes 1 leaves 4.22786e+09 minterms\n4227858432\n4.22786e+09\nFrom[7]: 8 nodes 1 leaves 3.35544e+07 minterms\nReached[7]: 8 nodes 1 leaves 4.26141e+09 minterms\n4261412864\n4.26141e+09\nFrom[8]: 9 nodes 1 leaves 1.67772e+07 minterms\nReached[8]: 9 nodes 1 leaves 4.27819e+09 minterms\n4278190080\n4.27819e+09\nFrom[9]: 10 nodes 1 leaves 8.38861e+06 minterms\nReached[9]: 10 nodes 1 leaves 4.28658e+09 minterms\n4286578688\n4.28658e+09\nFrom[10]: 11 nodes 1 leaves 4.1943e+06 minterms\nReached[10]: 11 nodes 1 leaves 4.29077e+09 minterms\n4290772992\n4.29077e+09\nFrom[11]: 12 nodes 1 leaves 2.09715e+06 minterms\nReached[11]: 12 nodes 1 leaves 4.29287e+09 minterms\n4292870144\n4.29287e+09\nFrom[12]: 13 nodes 1 leaves 1.04858e+06 minterms\nReached[12]: 13 nodes 1 leaves 4.29392e+09 minterms\n4293918720\n4.29392e+09\nFrom[13]: 14 nodes 1 leaves 524288 minterms\nReached[13]: 14 nodes 1 leaves 4.29444e+09 minterms\n4294443008\n4.29444e+09\nFrom[14]: 15 nodes 1 leaves 262144 minterms\nReached[14]: 15 nodes 1 leaves 4.29471e+09 minterms\n4294705152\n4.29471e+09\nFrom[15]: 16 nodes 1 leaves 131072 minterms\nReached[15]: 16 nodes 1 leaves 4.29484e+09 minterms\n4294836224\n4.29484e+09\nFrom[16]: 17 nodes 1 leaves 65536 minterms\nReached[16]: 17 nodes 1 leaves 4.2949e+09 minterms\n4294901760\n4.2949e+09\nFrom[17]: 18 nodes 1 leaves 32768 minterms\nReached[17]: 18 nodes 1 leaves 4.29493e+09 minterms\n4294934528\n4.29493e+09\nFrom[18]: 19 nodes 1 leaves 16384 minterms\nReached[18]: 19 nodes 1 leaves 4.29495e+09 minterms\n4294950912\n4.29495e+09\nFrom[19]: 20 nodes 1 leaves 8192 minterms\nReached[19]: 20 nodes 1 leaves 4.29496e+09 minterms\n4294959104\n4.29496e+09\nFrom[20]: 21 nodes 1 leaves 4096 minterms\nReached[20]: 21 nodes 1 leaves 4.29496e+09 minterms\n4294963200\n4.29496e+09\nFrom[21]: 22 nodes 1 leaves 2048 minterms\nReached[21]: 22 nodes 1 leaves 4.29497e+09 minterms\n4294965248\n4.29497e+09\nFrom[22]: 23 nodes 1 leaves 1024 minterms\nReached[22]: 23 nodes 1 leaves 4.29497e+09 minterms\n4294966272\n4.29497e+09\nFrom[23]: 24 nodes 1 leaves 512 minterms\nReached[23]: 24 nodes 1 leaves 4.29497e+09 minterms\n4294966784\n4.29497e+09\nFrom[24]: 25 nodes 1 leaves 256 minterms\nReached[24]: 25 nodes 1 leaves 4.29497e+09 minterms\n4294967040\n4.29497e+09\nFrom[25]: 26 nodes 1 leaves 128 minterms\nReached[25]: 26 nodes 1 leaves 4.29497e+09 minterms\n4294967168\n4.29497e+09\nFrom[26]: 27 nodes 1 leaves 64 minterms\nReached[26]: 27 nodes 1 leaves 4.29497e+09 minterms\n4294967232\n4.29497e+09\nFrom[27]: 28 nodes 1 leaves 32 minterms\nReached[27]: 28 nodes 1 leaves 4.29497e+09 minterms\n4294967264\n4.29497e+09\nFrom[28]: 29 nodes 1 leaves 16 minterms\nReached[28]: 29 nodes 1 leaves 4.29497e+09 minterms\n4294967280\n4.29497e+09\nFrom[29]: 30 nodes 1 leaves 8 minterms\nReached[29]: 30 nodes 1 leaves 4.29497e+09 minterms\n4294967288\n4.29497e+09\nFrom[30]: 31 nodes 1 leaves 4 minterms\nReached[30]: 31 nodes 1 leaves 4.29497e+09 minterms\n4294967292\n4.29497e+09\nFrom[31]: 32 nodes 1 leaves 2 minterms\nReached[31]: 32 nodes 1 leaves 4.29497e+09 minterms\n4294967294\n4.29497e+09\nFrom[32]: 33 nodes 1 leaves 1 minterms\nReached[32]: 33 nodes 1 leaves 4.29497e+09 minterms\n4294967295\n4.29497e+09\ndepth = 32\nR: 33 nodes 1 leaves 4.29497e+09 minterms\nOrder at the end of reachability analysis\n1 2 34 33 66 32 65 31 \n64 63 30 29 62 28 61 27 \n60 59 26 58 25 57 24 56 \n23 55 22 54 21 20 53 19 \n52 18 51 17 50 49 16 15 \n48 14 47 13 46 12 45 11 \n44 10 43 3 36 4 37 5 \n38 6 39 7 40 8 41 42 \n9 \n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000000\nMaximum number of variable swaps per reordering: 1000000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: yes\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 2018\n**** CUDD non-modifiable parameters ****\nMemory in use: 4625812\nPeak number of nodes: 7154\nPeak number of live nodes: 4004\nNumber of BDD variables: 97\nNumber of ZDD variables: 0\nNumber of cache entries: 65536\nNumber of cache look-ups: 49867\nNumber of cache hits: 20816\nNumber of cache insertions: 29312\nNumber of cache collisions: 1359\nNumber of cache deletions: 21085\nCache used slots = 17.70% (expected 10.53%)\nSoft limit for cache size: 100352\nNumber of buckets in unique table: 25088\nUsed buckets in unique table: 12.40% (expected 12.44%)\nNumber of BDD and ADD nodes: 3613\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 3266\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 26901\nTotal number of nodes reclaimed: 16737\nGarbage collections so far: 15\nTime for garbage collection: 0.00 sec\nReorderings so far: 15\nTime for reordering: 0.11 sec\nFinal size: 275\ntotal time = 0.11 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.1 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  8080K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 1509\nSwaps = 0\nInput blocks = 16\nOutput blocks = 16\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/nanotrav.1",
    "content": ".\\\" $Id: nanotrav.1,v 1.23 2009/02/21 06:00:31 fabio Exp fabio $\n.\\\"\n.TH NANOTRAV 1 \"18 June 2002\" \"Release 0.11\"\n.SH NAME\nnanotrav \\- a simple state graph traversal program\n.SH SYNOPSIS\n.B nanotrav\n[option ...]\n.SH DESCRIPTION\n\nnanotrav builds the BDDs of a circuit and applies various reordering\nmethods to the BDDs. It then traverses the state transition graph of\nthe circuit if the circuit is sequential, and if the user so requires.\nnanotrav is based on the CUDD package. The ordering of the variables\nis affected by three sets of options: the options that specify the\ninitial order (-order -ordering); the options that specify the\nreordering while the BDDs are being built (-autodyn -automethod); and\nthe options to specify the final reordering (-reordering\n-genetic). Notice that both -autodyn and -automethod must be specified\nto get dynamic reordering. The first enables reordering, while the\nsecond says what method to use.\n.SH OPTIONS\n.TP 10\n.B \\fIfile\\fB\nread input in blif format from \\fIfile\\fR.\n.TP 10\n.B \\-f \\fIfile\\fB\nread options from \\fIfile\\fR.\n.TP 10\n.B \\-trav\ntraverse the state transition graph after building the BDDs. This\noption has effect only if the circuit is sequential. The initial\nstates for traversal are taken from the blif file.\n.TP 10\n.B \\-depend\nperform dependent variable analysis after traversal.\n.TP 10\n.B \\-from \\fImethod\\fB\nuse \\fImethod\\fR to choose the frontier states for image computation\nduring traversal. Allowed methods are: \\fInew\\fR (default), \\fIreached\\fR,\n\\fIrestrict\\fR, \\fIcompact\\fR, \\fIsqueeze\\fR, \\fIsubset\\fR, \\fIsuperset\\fR.\n.TP 10\n.B \\-groupnsps \\fImethod\\fB\nuse \\fImethod\\fR to group the corresponding current and next state\nvariables. Allowed methods are: \\fInone\\fR (default), \\fIdefault\\fR,\n\\fIfixed\\fR.\n.TP 10\n.B \\-image \\fImethod\\fB\nuse \\fImethod\\fR for image computation during traversal. Allowed\nmethods are: \\fImono\\fR (default), \\fIpart\\fR, \\fIdepend\\fR, and\n\\fIclip\\fR.\n.TP 10\n.B \\-depth \\fIn\\fB\nuse \\fIn\\fR to derive the clipping depth for image\ncomputation. It should be a number between 0 and 1. The default value\nis 1 (no clipping).\n.TP 10\n.B \\-verify \\fIfile\\fB\nperform combinational verification checking for equivalence to\nthe network in \\fIfile\\fR. The two networks being compared must use\nthe same names for inputs, outputs, and present and next state\nvariables.  The method used for verification is extremely\nsimplistic. BDDs are built for all outputs of both networks, and are\nthen compared.\n.TP 10\n.B \\-closure\nperform reachability analysis using the transitive closure of the\ntransition relation.\n.TP 10\n.B \\-cdepth \\fIn\\fB\nuse \\fIn\\fR to derive the clipping depth for transitive closure\ncomputation. It should be a number between 0 and 1. The default value\nis 1 (no clipping).\n.TP 10\n.B \\-envelope\ncompute the greatest fixed point of the state transition\nrelation. (This greatest fixed point is also called the outer envelope\nof the graph.)\n.TP 10\n.B \\-scc\ncompute the strongly connected components of the state transition\ngraph. The algorithm enumerates the SCCs; therefore it stops after a\nsmall number of them has been computed.\n.TP 10\n.B \\-maxflow\ncompute the maximum flow in the network defined by the state graph.\n.TP 10\n.B \\-sink \\fIfile\\fB\nread the sink for maximum flow computation from \\fIfile\\fR. The source\nis given by the initial states.\n.TP 10\n.B \\-shortpaths \\fImethod\\fB\ncompute the distances between states.  Allowed methods are: \\fInone\\fR\n(default), \\fIbellman\\fR, \\fIfloyd\\fR, and \\fIsquare\\fR.\n.TP 10\n.B \\-selective\nuse selective tracing variant of the \\fIsquare\\fR method for shortest\npaths.\n.TP 10\n.B \\-part\ncompute the conjunctive decomposition of the transition relation.  The\nnetwork must be sequential for the test to take place.\n.TP 10\n.B \\-sign\ncompute signatures. For each output of the circuit, all inputs are\nassigned a signature. The signature is the fraction of minterms in the\nON\\-set of the positive cofactor of the output with respect to the\ninput. Signatures are useful in identifying the equivalence of circuits\nwith unknown input or output correspondence.\n.TP 10\n.B \\-zdd\nperform a simple test of ZDD functions. This test is not executed if\n-delta is also specified, because it uses the BDDs of the primary\noutputs of the circuit. These are converted to ZDDs and the ZDDs are\nthen converted back to BDDs and checked against the original ones.  A\nfew more functions are exercised and reordering is applied if it is\nenabled. Then irredundant sums of products are produced for the\nprimary outputs.\n.TP 10\n.B \\-cover\nprint irredundant sums of products for the primary outputs.  This\noption implies \\fB\\-zdd\\fR.\n.TP 10\n.B \\-second \\fIfile\\fB\nread a second network from \\fIfile\\fR. Currently, if this option is\nspecified, a test of BDD minimization algorithms is performed using\nthe largest output of the second network as constraint.  Inputs of the\ntwo networks with the same names are merged.\n.TP 10\n.B \\-density\ntest BDD approximation functions.\n.TP 10\n.B \\-approx \\fImethod\\fB\nif \\fImethod\\fR is \\fIunder\\fR (default) perform underapproximation\nwhen BDDs are approximated. If \\fImethod\\fR is \\fIover\\fR perform\noverapproximation when BDDs are approximated.\n.TP 10\n.B \\-threshold \\fIn\\fB\nUse \\fIn\\fR as threshold when approximating BDDs.\n.TP 10\n.B \\-quality \\fIn\\fB\nUse \\fIn\\fR (a floating point number) as quality factor when\napproximating BDDs. Default value is 1.\n.TP 10\n.B \\-decomp\ntest BDD decomposition functions.\n.TP 10\n.B \\-cofest\ntest cofactor estimation functions.\n.TP 10\n.B \\-clip \\fIn file\\fB\ntest clipping functions using \\fIn\\fR to determine the clipping depth\nand taking one operand from the network in \\fIfile\\fR.\n.TP 10\n.B \\-dctest \\fIfile\\fB\ntest functions for equality and containment under don't care\nconditions taking the don't care conditions from \\fIfile\\fR.\n.TP 10\n.B \\-closest\ntest function that finds a cube in a BDD at minimum Hamming distance\nfrom another BDD.\n.TP 10\n.B \\-clauses\ntest function that extracts two-literal clauses from a DD.\n.TP 10\n.B \\-char2vect\nperform a simple test of the conversion from characteristic function\nto functional vector.  If the network is sequential, the test is\napplied to the monolithic transition relation; otherwise to the primary\noutputs.\n.TP 10\n.B \\-local\nbuild local BDDs for each gate of the circuit.  This option is not in\neffect if traversal, outer envelope computation, or maximum flow\ncomputation are requested.  The local BDD of a gate is in terms of its\nlocal inputs.\n.TP 10\n.B \\-cache \\fIn\\fB\nset the initial size of the computed table to \\fIn\\fR.\n.TP 10\n.B \\-slots \\fIn\\fB\nset the initial size of each unique subtable to \\fIn\\fR.\n.TP 10\n.B \\-maxmem \\fIn\\fB\nset the target maximum memory occupation to \\fIn\\fR MB.  If this\nparameter is not specified or if \\fIn\\fR is 0, then a suitable value\nis computed automatically.\n.TP 10\n.B \\-memhard \\fIn\\fB\nset the hard limit to memory occupation to \\fIn\\fR MB.  If this\nparameter is not specified or if \\fIn\\fR is 0, no hard limit is\nenforced by the program.\n.TP 10\n.B \\-maxlive \\fIn\\fB\nset the hard limit to the number of live BDD nodes to \\fIn\\fR.  If\nthis parameter is not specified, the limit is four billion nodes.\n.TP 10\n.B \\-dumpfile \\fIfile\\fB\ndump BDDs to \\fIfile\\fR. The BDDs are dumped just before program\ntermination. (Hence, after reordering, if reordering is specified.)\n.TP 10\n.B \\-dumpblif\nuse blif format for dump of BDDs (default is dot format). If blif is\nused, the BDDs are dumped as a network of multiplexers. The dot format\nis suitable for input to the dot program, which produces a\ndrawing of the BDDs.\n.TP 10\n.B \\-dumpmv\nuse blif-MV format for dump of BDDs.  The BDDs are dumped as a network\nof multiplexers.\n.TP 10\n.B \\-dumpdaVinci\nuse daVinci format for dump of BDDs.\n.TP 10\n.B \\-dumpddcal\nuse DDcal format for dump of BDDs.  This option may produce an invalid\noutput if the variable and output names of the BDDs being dumped do\nnot comply with the restrictions imposed by the DDcal format.\n.TP 10\n.B \\-dumpfact\nuse factored form format for dump of BDDs. This option must be used\nwith caution because the size of the output is proportional to the\nnumber of paths in the BDD.\n.TP 10\n.B \\-storefile \\fIfile\\fB\nSave the BDD of the reachable states to \\fIfile\\fR. The BDD is stored at\nthe iteration specified by \\fB\\-store\\fR. This option uses the format of\nthe \\fIdddmp\\fR library. Together with \\fB\\-loadfile\\fR, it implements a\nprimitive checkpointing capability. It is primitive because the transition\nrelation is not saved; because the frontier states are not saved; and\nbecause only one check point can be specified.\n.TP 10\n.B \\-store \\fIn\\fB\nSave the BDD of the reached states at iteration \\fIn\\fR. This option\nrequires \\fB\\-storefile\\fR.\n.TP 10\n.B \\-loadfile \\fIfile\\fB\nLoad the BDD of the initial states from \\fIfile\\fR.  This option uses the\nformat of the \\fIdddmp\\fR library. Together with \\fB\\-storefile\\fR, it\nimplements a primitive checkpointing capability.\n.TP 10\n.B \\-nobuild\ndo not build the BDDs. Quit after determining the initial variable\norder.\n.TP 10\n.B \\-drop\ndrop BDDs for intermediate nodes as soon as possible. If this option is\nnot specified, the BDDs for the intermediate nodes of the circuit are\ndropped just before the final reordering.\n.TP 10\n.B \\-delta\nbuild BDDs only for the next state functions of a sequential circuit.\n.TP 10\n.B \\-node\nbuild BDD only for \\fInode\\fR.\n.TP 10\n.B \\-order \\fIfile\\fB\nread the variable order from \\fIfile\\fR. This file must contain the\nnames of the inputs (and present state variables) in the desired order.\nNames must be separated by white space or newlines.\n.TP 10\n.B \\-ordering \\fImethod\\fB\nuse \\fImethod\\fR to derive an initial variable order. \\fImethod\\fR can\nbe one of \\fIhw\\fR, \\fIdfs\\fR. Method \\fIhw\\fR uses the order in which the\ninputs are listed in the circuit description.\n.TP 10\n.B \\-autodyn\nenable dynamic reordering. By default, dynamic reordering is disabled.\nIf enabled, the default method is sifting.\n.TP 10\n.B \\-first \\fIn\\fB\ndo first dynamic reordering when the BDDs reach \\fIn\\fR nodes.\nThe default value is 4004. (Don't ask why.)\n.TP 10\n.B \\-countdead\ninclude dead nodes in node count when deciding whether to reorder\ndynamically. By default, only live nodes are counted.\n.TP 10\n.B \\-growth \\fIn\\fB\nmaximum percentage by which the BDDs may grow while sifting one\nvariable. The default value is 20.\n.TP 10\n.B \\-automethod \\fImethod\\fB\nuse \\fImethod\\fR for dynamic reordering of the BDDs. \\fImethod\\fR can\nbe one of none, random, pivot, sifting, converge, symm, cosymm, group,\ncogroup, win2, win3, win4, win2conv, win3conv, win4conv, annealing,\ngenetic, linear, linconv, exact. The default method is sifting.\n.TP 10\n.B \\-reordering \\fImethod\\fB\nuse \\fImethod\\fR for the final reordering of the BDDs. \\fImethod\\fR can\nbe one of none, random, pivot, sifting, converge, symm, cosymm, group,\ncogroup, win2, win3, win4, win2conv, win3conv, win4conv, annealing,\ngenetic, linear, linconv, exact. The default method is none.\n.TP 10\n.B \\-genetic\nrun the genetic algorithm after the final reordering (which in this case\nis no longer final). This allows the genetic algorithm to have one good\nsolution generated by, say, sifting, in the initial population.\n.TP 10\n.B \\-groupcheck \\fImethod\\fB\nuse \\fImethod\\fR for the the creation of groups in group sifting.\n\\fImethod\\fR can be one of nocheck, check5, check7. Method check5 uses\nextended symmetry as aggregation criterion; group7, in addition, also\nuses the second difference criterion. The default value is check7.\n.TP 10\n.B \\-arcviolation \\fIn\\fB\npercentage of arcs that violate the symmetry condition in the aggregation\ncheck of group sifting. Should be between 0 and 100. The default value is\n10. A larger value causes more aggregation.\n.TP 10\n.B \\-symmviolation \\fIn\\fB\npercentage of nodes that violate the symmetry condition in the aggregation\ncheck of group sifting. Should be between 0 and 100. The default value is\n10. A larger value causes more aggregation.\n.TP 10\n.B \\-recomb \\fIn\\fB\nthreshold used in the second difference criterion for aggregation. (Used\nby check7.) The default value is 0. A larger value causes more\naggregation. It can be either positive or negative.\n.TP 10\n.B \\-tree \\fIfile\\fB\nread the variable group tree from \\fIfile\\fR. The format of this file is\na sequence of triplets: \\fIlb ub flag\\fR. Each triplet describes a\ngroup: \\fIlb\\fR is the lowest index of the group; \\fIub\\fR is the\nhighest index of the group; \\fIflag\\fR can be either D (default) or F\n(fixed). Fixed groups are not reordered.\n.TP 10\n.B \\-genepop \\fIn\\fB\nsize of the population for genetic algorithm. By default, the size of\nthe population is 3 times the number of variables, with a maximum of 120.\n.TP 10\n.B \\-genexover \\fIn\\fB\nnumber of crossovers at each generation for the genetic algorithm. By\ndefault, the number of crossovers is 3 times the number of variables,\nwith a maximum of 50.\n.TP 10\n.B \\-seed \\fIn\\fB\nrandom number generator seed for the genetic algorithm and the random\nand pivot reordering methods.\n.TP 10\n.B \\-progress\nreport progress when building the BDDs for a network. This option\ncauses the name of each primary output or next state function to be\nprinted after its BDD is built. It does not take effect if local BDDs\nare requested.\n.TP 10\n.B -p \\fIn\\fB\nverbosity level. If negative, the program is very quiet. Larger values cause\nmore information to be printed.\n.SH SEE ALSO\nThe documentation for the CUDD package explains the various\nreordering methods.\n\nThe documentation for the MTR package provides details on the variable\ngroups.\n\ndot(1)\n.SH REFERENCES\nF. Somenzi,\n\"Efficient Manipulation of Decision Diagrams,\"\nSoftware Tools for Technology Transfer,\nvol. 3, no. 2, pp. 171-181, 2001.\n\nS. Panda, F. Somenzi, and B. F. Plessier,\n\"Symmetry Detection and Dynamic Variable Ordering of Decision Diagrams,\"\nIEEE International Conference on Computer-Aided Design,\npp. 628-631, November 1994.\n\nS. Panda and F. Somenzi,\n\"Who Are the Variables in Your Neighborhood,\"\nIEEE International Conference on Computer-Aided Design,\npp. 74-77, November 1995.\n\nG. D. Hachtel and F. Somenzi,\n\"A Symbolic Algorithm for Maximum Flow in 0-1 Networks,\"\nIEEE International Conference on Computer-Aided Design,\npp. 403-406, November 1993.\n.SH AUTHOR\nFabio Somenzi, University of Colorado at Boulder.\n"
  },
  {
    "path": "cudd/nanotrav/ntr.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief A very simple reachability analysis program.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"cuddInt.h\"\n#include \"ntr.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define NTR_MAX_DEP_SIZE 20\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\nstatic char const *onames[] = {\"T\", \"R\"}; /**< names of functions to be dumped */\nstatic double *signatures;\t/**< signatures for all variables */\nstatic BnetNetwork *staticNet;\t/**< pointer to network used by qsort\n\t\t\t\t ** comparison function */\nstatic DdNode **staticPart;\t/**< pointer to parts used by qsort\n\t\t\t\t ** comparison function */\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * makecube (DdManager *dd, DdNode **x, int n);\nstatic void ntrInitializeCount (BnetNetwork *net, NtrOptions *option);\nstatic void ntrCountDFS (BnetNetwork *net, BnetNode *node);\nstatic DdNode * ntrImage (DdManager *dd, NtrPartTR *TR, DdNode *from, NtrOptions *option);\nstatic DdNode * ntrPreimage (DdManager *dd, NtrPartTR *T, DdNode *from);\nstatic DdNode * ntrChooseFrom (DdManager *dd, DdNode *neW, DdNode *reached, NtrOptions *option);\nstatic DdNode * ntrUpdateReached (DdManager *dd, DdNode *oldreached, DdNode *to);\nstatic int ntrLatchDependencies (DdManager *dd, DdNode *reached, BnetNetwork *net, NtrOptions *option);\nstatic NtrPartTR * ntrEliminateDependencies (DdManager *dd, NtrPartTR *TR, DdNode **states, NtrOptions *option);\nstatic int ntrUpdateQuantificationSchedule (DdManager *dd, NtrPartTR *T);\nstatic int ntrSignatureCompare (int * ptrX, int * ptrY);\nstatic int ntrSignatureCompare2 (int * ptrX, int * ptrY);\nstatic int ntrPartCompare (int * ptrX, int * ptrY);\nstatic char ** ntrAllocMatrix (int nrows, int ncols);\nstatic void ntrFreeMatrix (char **matrix);\nstatic void ntrPermuteParts (DdNode **a, DdNode **b, int *comesFrom, int *goesTo, int size);\nstatic void ntrIncreaseRef(void * e, void * arg);\nstatic void ntrDecreaseRef(void * e, void * arg);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Builds DDs for a network outputs and next state functions.\n\n  @details The method is really brain-dead, but it is very simple.\n  Some inputs to the network may be shared with another network whose\n  DDs have already been built.  In this case we want to share the DDs\n  as well.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect the dd fields of the network nodes are modified. Uses the\n  count fields of the nodes.\n\n*/\nint\nNtr_buildDDs(\n  BnetNetwork * net /**< network for which DDs are to be built */,\n  DdManager * dd /**< %DD manager */,\n  NtrOptions * option /**< option structure */,\n  BnetNetwork * net2 /**< companion network with which inputs may be shared */)\n{\n    int pr = option->verb;\n    int result;\n    int i;\n    BnetNode *node, *node2;\n\n    /* If some inputs or present state variables are shared with\n    ** another network, we initialize their BDDs from that network.\n    */\n    if (net2 != NULL) {\n\tfor (i = 0; i < net->npis; i++) {\n\t    if (!st_lookup(net->hash,net->inputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    if (!st_lookup(net2->hash,net->inputs[i],(void **)&node2)) {\n\t\t/* This input is not shared. */\n\t\tresult = Bnet_BuildNodeBDD(dd,node,net->hash,\n\t\t\t\t\t   option->locGlob,option->nodrop);\n\t\tif (result == 0) return(0);\n\t    } else {\n\t\tif (node2->dd == NULL) return(0);\n\t\tnode->dd = node2->dd;\n\t\tCudd_Ref(node->dd);\n\t\tnode->var = node2->var;\n\t\tnode->active = node2->active;\n\t    }\n\t}\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    if (!st_lookup(net->hash,net->latches[i][1],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    if (!st_lookup(net2->hash,net->latches[i][1],(void **)&node2)) {\n\t\t/* This present state variable is not shared. */\n\t\tresult = Bnet_BuildNodeBDD(dd,node,net->hash,\n\t\t\t\t\t   option->locGlob,option->nodrop);\n\t\tif (result == 0) return(0);\n\t    } else {\n\t\tif (node2->dd == NULL) return(0);\n\t\tnode->dd = node2->dd;\n\t\tCudd_Ref(node->dd);\n\t\tnode->var = node2->var;\n\t\tnode->active = node2->active;\n\t    }\n\t}\n    } else {\n\t/* First assign variables to inputs if the order is provided.\n\t** (Either in the .blif file or in an order file.)\n\t*/\n\tif (option->ordering == PI_PS_FROM_FILE) {\n\t    /* Follow order given in input file. First primary inputs\n\t    ** and then present state variables.\n\t    */\n\t    for (i = 0; i < net->npis; i++) {\n\t\tif (!st_lookup(net->hash,net->inputs[i],(void **)&node)) {\n\t\t    return(0);\n\t\t}\n\t\tresult = Bnet_BuildNodeBDD(dd,node,net->hash,\n\t\t\t\t\t   option->locGlob,option->nodrop);\n\t\tif (result == 0) return(0);\n\t    }\n\t    for (i = 0; i < net->nlatches; i++) {\n\t\tif (!st_lookup(net->hash,net->latches[i][1],(void **)&node)) {\n\t\t    return(0);\n\t\t}\n\t\tresult = Bnet_BuildNodeBDD(dd,node,net->hash,\n\t\t\t\t\t   option->locGlob,option->nodrop);\n\t\tif (result == 0) return(0);\n\t    }\n\t} else if (option->ordering == PI_PS_GIVEN) {\n\t    result = Bnet_ReadOrder(dd,option->orderPiPs,net,option->locGlob,\n\t\t\t\t    option->nodrop);\n\t    if (result == 0) return(0);\n\t} else {\n\t    result = Bnet_DfsVariableOrder(dd,net);\n\t    if (result == 0) return(0);\n\t}\n    }\n    /* At this point the BDDs of all primary inputs and present state\n    ** variables have been built. */\n\n    /* Currently noBuild doesn't do much. */\n    if (option->noBuild == TRUE)\n\treturn(1);\n\n    if (option->locGlob == BNET_LOCAL_DD) {\n\tnode = net->nodes;\n\twhile (node != NULL) {\n\t    result = Bnet_BuildNodeBDD(dd,node,net->hash,BNET_LOCAL_DD,TRUE);\n\t    if (result == 0) {\n\t\treturn(0);\n\t    }\n\t    if (pr > 2) {\n\t\t(void) fprintf(stdout,\"%s\",node->name);\n\t\tCudd_PrintDebug(dd,node->dd,Cudd_ReadSize(dd),pr);\n\t    }\n\t    node = node->next;\n\t}\n    } else { /* option->locGlob == BNET_GLOBAL_DD */\n\t/* Create BDDs with DFS from the primary outputs and the next\n\t** state functions. If the inputs had not been ordered yet,\n\t** this would result in a DFS order for the variables.\n\t*/\n\n\tntrInitializeCount(net,option);\n\n\tif (option->node != NULL &&\n\t    option->closestCube == FALSE && option->dontcares == FALSE) {\n\t    if (!st_lookup(net->hash,option->node,(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    result = Bnet_BuildNodeBDD(dd,node,net->hash,BNET_GLOBAL_DD,\n\t\t\t\t       option->nodrop);\n\t    if (result == 0) return(0);\n\t} else {\n\t    if (option->stateOnly == FALSE) {\n\t\tfor (i = 0; i < net->npos; i++) {\n\t\t    if (!st_lookup(net->hash,net->outputs[i],(void **)&node)) {\n\t\t\tcontinue;\n\t\t    }\n\t\t    result = Bnet_BuildNodeBDD(dd,node,net->hash,\n\t\t\t\t\t       BNET_GLOBAL_DD,option->nodrop);\n\t\t    if (result == 0) return(0);\n\t\t    if (option->progress)  {\n\t\t\t(void) fprintf(stdout,\"%s\\n\",node->name);\n\t\t    }\n#if 0\n\t\t    Cudd_PrintDebug(dd,node->dd,net->ninputs,option->verb);\n#endif\n\t\t}\n\t    }\n\t    for (i = 0; i < net->nlatches; i++) {\n\t\tif (!st_lookup(net->hash,net->latches[i][0],(void **)&node)) {\n\t\t    continue;\n\t\t}\n\t\tresult = Bnet_BuildNodeBDD(dd,node,net->hash,BNET_GLOBAL_DD,\n\t\t\t\t\t   option->nodrop);\n\t\tif (result == 0) return(0);\n\t\tif (option->progress)  {\n\t\t    (void) fprintf(stdout,\"%s\\n\",node->name);\n\t\t}\n#if 0\n\t\tCudd_PrintDebug(dd,node->dd,net->ninputs,option->verb);\n#endif\n\t    }\n\t}\n\t/* Make sure all inputs have a DD and dereference the DDs of\n\t** the nodes that are not reachable from the outputs.\n\t*/\n\tfor (i = 0; i < net->npis; i++) {\n\t    if (!st_lookup(net->hash,net->inputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    result = Bnet_BuildNodeBDD(dd,node,net->hash,BNET_GLOBAL_DD,\n\t\t\t\t       option->nodrop);\n\t    if (result == 0) return(0);\n\t    if (node->count == -1) Cudd_RecursiveDeref(dd,node->dd);\n\t}\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    if (!st_lookup(net->hash,net->latches[i][1],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    result = Bnet_BuildNodeBDD(dd,node,net->hash,BNET_GLOBAL_DD,\n\t\t\t\t       option->nodrop);\n\t    if (result == 0) return(0);\n\t    if (node->count == -1) Cudd_RecursiveDeref(dd,node->dd);\n\t}\n\n\t/* Dispose of the BDDs of the internal nodes if they have not\n\t** been dropped already.\n\t*/\n\tif (option->nodrop == TRUE) {\n\t    for (node = net->nodes; node != NULL; node = node->next) {\n\t\tif (node->dd != NULL && node->count != -1 &&\n\t\t    (node->type == BNET_INTERNAL_NODE ||\n\t\t    node->type == BNET_INPUT_NODE ||\n\t\t    node->type == BNET_PRESENT_STATE_NODE)) {\n\t\t    Cudd_RecursiveDeref(dd,node->dd);\n\t\t    if (node->type == BNET_INTERNAL_NODE) node->dd = NULL;\n\t\t}\n\t    }\n\t}\n    }\n\n    return(1);\n\n} /* end of Ntr_buildDDs */\n\n\n/**\n  @brief Builds the transition relation for a network.\n\n  @return a pointer to the transition relation structure if\n  successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nNtrPartTR *\nNtr_buildTR(\n  DdManager * dd /**< manager */,\n  BnetNetwork * net /**< network */,\n  NtrOptions * option /**< options */,\n  int  image /**< image type: monolithic ... */)\n{\n    NtrPartTR *TR;\n    DdNode *T, *delta, *support, *scan, *tmp, *preiabs, *prepabs;\n    DdNode **part, **absicubes, **abspcubes, **nscube, *mnscube;\n    DdNode **x, **y;\n    DdNode **pi;\n    int i;\n    int xlevel;\n    BnetNode *node;\n    int *schedule;\n    int depth = 0;\n\n    /* Initialize transition relation structure. */\n    TR = ALLOC(NtrPartTR,1);\n    if (TR == NULL) goto endgame;\n    TR->nlatches = net->nlatches;\n    if (image == NTR_IMAGE_MONO) {\n\tTR->nparts = 1;\n    } else if (image == NTR_IMAGE_PART || image == NTR_IMAGE_CLIP ||\n\t       image == NTR_IMAGE_DEPEND) {\n\tTR->nparts = net->nlatches;\n    } else {\n\t(void) fprintf(stderr,\"Unrecognized image method (%d). Using part.\\n\",\n\t\t       image);\n\tTR->nparts = net->nlatches;\n    }\n    TR->factors = Ntr_InitHeap(TR->nlatches);\n    if (TR->factors == NULL) goto endgame;\n    /* Allocate arrays for present state and next state variables. */\n    TR->x = x = ALLOC(DdNode *,TR->nlatches);\n    if (x == NULL) goto endgame;\n    TR->y = y = ALLOC(DdNode *,TR->nlatches);\n    if (y == NULL) goto endgame;\n    /* Allocate array for primary input variables. */\n    pi = ALLOC(DdNode *,net->npis);\n    if (pi == NULL) goto endgame;\n    /* Allocate array for partitioned transition relation. */\n    part = ALLOC(DdNode *,net->nlatches);\n    if (part == NULL) goto endgame;\n    /* Allocate array of next state cubes. */\n    nscube = ALLOC(DdNode *,net->nlatches);\n    if (nscube == NULL) goto endgame;\n    /* Allocate array for quantification schedule and initialize it. */\n    schedule = ALLOC(int,Cudd_ReadSize(dd));\n    if (schedule == NULL) goto endgame;\n    for (i = 0; i < Cudd_ReadSize(dd); i++) {\n\tschedule[i] = -1;\n    }\n\n    /* Create partitioned transition relation from network. */\n    TR->xw = Cudd_ReadOne(dd);\n    Cudd_Ref(TR->xw);\n    for (i = 0; i < net->nlatches; i++) {\n\tif (!st_lookup(net->hash,net->latches[i][1],(void **)&node)) {\n\t    goto endgame;\n\t}\n\tx[i] = node->dd;\n\tCudd_Ref(x[i]);\n\t/* Add present state variable to cube TR->xw. */\n\ttmp = Cudd_bddAnd(dd,TR->xw,x[i]);\n\tif (tmp == NULL) return(NULL); Cudd_Ref(tmp);\n\tCudd_RecursiveDeref(dd,TR->xw);\n\tTR->xw = tmp;\n\t/* Create new y variable immediately above the x variable. */\n\txlevel = Cudd_ReadPerm(dd,x[i]->index);\n\ty[i] = Cudd_bddNewVarAtLevel(dd,xlevel);\n\tCudd_Ref(y[i]);\n\t/* Initialize cube of next state variables for this part. */\n\tnscube[i] = y[i];\n\tCudd_Ref(nscube[i]);\n\t/* Group present and next state variable if so requested. */\n\tif (option->groupnsps != NTR_GROUP_NONE) {\n\t    int method = option->groupnsps == NTR_GROUP_DEFAULT ?\n\t\tMTR_DEFAULT : MTR_FIXED;\n\t    if (Cudd_MakeTreeNode(dd,y[i]->index,2,method) == NULL)\n\t\tgoto endgame;\n\t}\n\t/* Get next state function and create transition relation part. */\n\tif (!st_lookup(net->hash,net->latches[i][0],(void **)&node)) {\n\t    goto endgame;\n\t}\n\tdelta = node->dd;\n\tif (image != NTR_IMAGE_DEPEND) {\n\t    part[i] = Cudd_bddXnor(dd,delta,y[i]);\n\t    if (part[i] == NULL) goto endgame;\n\t} else {\n\t    part[i] = delta;\n\t}\n\tCudd_Ref(part[i]);\n\t/* Collect scheduling info for this delta. At the end of this loop\n\t** schedule[i] == j means that the variable of index i does not\n\t** appear in any part with index greater than j, unless j == -1,\n\t** in which case the variable appears in no part.\n\t*/\n\tsupport = Cudd_Support(dd,delta);\n\tCudd_Ref(support);\n\tscan = support;\n\twhile (!Cudd_IsConstant(scan)) {\n\t    schedule[scan->index] = i;\n\t    scan = Cudd_T(scan);\n\t}\n\tCudd_RecursiveDeref(dd,support);\n    }\n\n    /* Collect primary inputs. */\n    for (i = 0; i < net->npis; i++) {\n\tif (!st_lookup(net->hash,net->inputs[i],(void **)&node)) {\n\t    goto endgame;\n\t}\n\tpi[i] = node->dd;\n\ttmp  = Cudd_bddAnd(dd,TR->xw,pi[i]);\n\tif (tmp == NULL) goto endgame; Cudd_Ref(tmp);\n\tCudd_RecursiveDeref(dd,TR->xw);\n\tTR->xw = tmp;\n    }\n\n    /* Build abstraction cubes. First primary input variables that go\n    ** in the abstraction cubes for both monolithic and partitioned\n    ** transition relations. */\n    absicubes = ALLOC(DdNode *, net->nlatches);\n    if (absicubes == NULL) goto endgame;\n    abspcubes = ALLOC(DdNode *, net->nlatches);\n    if (abspcubes == NULL) goto endgame;\n\n    for (i = 0; i < net->nlatches; i++) {\n\tabsicubes[i] = Cudd_ReadOne(dd);\n\tCudd_Ref(absicubes[i]);\n    }\n    preiabs = Cudd_ReadOne(dd);\n    Cudd_Ref(preiabs);\n\n    for (i = 0; i < net->npis; i++) {\n\tint j = pi[i]->index;\n\tint k = schedule[j];\n\tif (k >= 0) {\n\t    tmp = Cudd_bddAnd(dd,absicubes[k],pi[i]);\n\t    if (tmp == NULL) return(NULL); Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(dd,absicubes[k]);\n\t    absicubes[k] = tmp;\n\t} else {\n\t    tmp = Cudd_bddAnd(dd,preiabs,pi[i]);\n\t    if (tmp == NULL) return(NULL); Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(dd,preiabs);\n\t    preiabs = tmp;\n\t}\n    }\n    FREE(pi);\n\n    /* Build preimage abstraction cubes from image abstraction cubes. */\n    for (i = 0; i < net->nlatches; i++) {\n\tabspcubes[i] = Cudd_bddAnd(dd,absicubes[i],nscube[i]);\n\tif (abspcubes[i] == NULL) return(NULL);\n\tCudd_Ref(abspcubes[i]);\n    }\n    Cudd_Ref(prepabs = preiabs);\n\n    /* For partitioned transition relations we add present state variables\n    ** to the image abstraction cubes. */\n    if (image != NTR_IMAGE_MONO) {\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    int j = x[i]->index;\n\t    int k = schedule[j];\n\t    if (k >= 0) {\n\t\ttmp = Cudd_bddAnd(dd,absicubes[k],x[i]);\n\t\tif (tmp == NULL) return(NULL); Cudd_Ref(tmp);\n\t\tCudd_RecursiveDeref(dd,absicubes[k]);\n\t\tabsicubes[k] = tmp;\n\t    } else {\n\t\ttmp = Cudd_bddAnd(dd,preiabs,x[i]);\n\t\tif (tmp == NULL) return(NULL); Cudd_Ref(tmp);\n\t\tCudd_RecursiveDeref(dd,preiabs);\n\t\tpreiabs = tmp;\n\t    }\n\t}\n    }\n    FREE(schedule);\n\n    if (image != NTR_IMAGE_MONO) {\n\tTR->part = part;\n\tTR->icube = absicubes;\n\tTR->pcube = abspcubes;\n\tTR->nscube = nscube;\n\tTR->preiabs = preiabs;\n\tTR->prepabs = prepabs;\n\treturn(TR);\n    }\n\n    /* Here we are building a monolithic TR. */\n\n    /* Reinitialize the cube of variables to be quantified before\n    ** image computation. */\n    Cudd_RecursiveDeref(dd,preiabs);\n    preiabs = Cudd_ReadOne(dd);\n    Cudd_Ref(preiabs);\n\n    if (option->imageClip != 1.0) {\n\tdepth = (int) ((double) Cudd_ReadSize(dd) * option->imageClip);\n    }\n\n    /* Collapse transition relation. */\n    T = Cudd_ReadOne(dd);\n    Cudd_Ref(T);\n    mnscube = Cudd_ReadOne(dd);\n    Cudd_Ref(mnscube);\n    for (i = 0; i < net->nlatches; i++) {\n\t/* Eliminate the primary inputs that do not appear in other parts. */\n\tif (depth != 0) {\n\t    tmp = Cudd_bddClippingAndAbstract(dd,T,part[i],absicubes[i],\n\t\t\t\t\t      depth,option->approx);\n\t} else {\n\t    tmp = Cudd_bddAndAbstract(dd,T,part[i],absicubes[i]);\n\t}\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDeref(dd,T);\n\tCudd_RecursiveDeref(dd,part[i]);\n\tCudd_RecursiveDeref(dd,absicubes[i]);\n\tCudd_RecursiveDeref(dd,abspcubes[i]);\n\tif (option->threshold >= 0) {\n\t    if (option->approx) {\n\t\tT = Cudd_RemapOverApprox(dd,tmp,2*net->nlatches,\n\t\t\t\t\t option->threshold,option->quality);\n\t    } else {\n\t\tT = Cudd_RemapUnderApprox(dd,tmp,2*net->nlatches,\n\t\t\t\t\t  option->threshold,option->quality);\n\t    }\n\t} else {\n\t    T = tmp;\n\t}\n\tif (T == NULL) return(NULL);\n\tCudd_Ref(T);\n\tCudd_RecursiveDeref(dd,tmp);\n\t/* Add the next state variables of this part to the cube of all\n\t** next state variables. */\n\ttmp = Cudd_bddAnd(dd,mnscube,nscube[i]);\n\tif (tmp == NULL) return(NULL);\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDeref(dd,mnscube);\n\tmnscube = tmp;\n\tCudd_RecursiveDeref(dd,nscube[i]);\n\t(void) printf(\"@\"); fflush(stdout);\n    }\n    (void) printf(\"\\n\");\n#if 0\n    (void) printf(\"T\"); Cudd_PrintDebug(dd,T,2*net->nlatches,2);\n#endif\n\n    /* Clean up. */\n    FREE(absicubes);\n    FREE(abspcubes);\n    FREE(part);\n    FREE(nscube);\n\n    TR->part = part = ALLOC(DdNode *,1);\n    if (part == NULL) goto endgame;\n    part[0] = T;\n\n    /* Build cube of x (present state) variables for abstraction. */\n    TR->icube = absicubes = ALLOC(DdNode *,1);\n    if (absicubes == NULL) goto endgame;\n    absicubes[0] = makecube(dd,x,TR->nlatches);\n    if (absicubes[0] == NULL) return(0);\n    Cudd_Ref(absicubes[0]);\n    /* Build cube of y (next state) variables for abstraction. */\n    TR->pcube = abspcubes = ALLOC(DdNode *,1);\n    if (abspcubes == NULL) goto endgame;\n    abspcubes[0] = makecube(dd,y,TR->nlatches);\n    if (abspcubes[0] == NULL) return(0);\n    Cudd_Ref(abspcubes[0]);\n    TR->preiabs = preiabs;\n    TR->prepabs = prepabs;\n\n    TR->nscube = ALLOC(DdNode *,1);\n    if (TR->nscube == NULL) return(NULL);\n    TR->nscube[0] = mnscube;\n\n    return(TR);\n\nendgame:\n\n    return(NULL);\n\n} /* end of Ntr_buildTR */\n\n\n/**\n  @brief Frees the transition relation for a network.\n\n  @sideeffect None\n\n*/\nvoid\nNtr_freeTR(\n  DdManager * dd,\n  NtrPartTR * TR)\n{\n    int i;\n    for (i = 0; i < TR->nlatches; i++) {\n\tCudd_RecursiveDeref(dd,TR->x[i]);\n\tCudd_RecursiveDeref(dd,TR->y[i]);\n    }\n    FREE(TR->x);\n    FREE(TR->y);\n    for (i = 0; i < TR->nparts; i++) {\n\tCudd_RecursiveDeref(dd,TR->part[i]);\n\tCudd_RecursiveDeref(dd,TR->icube[i]);\n\tCudd_RecursiveDeref(dd,TR->pcube[i]);\n\tCudd_RecursiveDeref(dd,TR->nscube[i]);\n    }\n    FREE(TR->part);\n    FREE(TR->icube);\n    FREE(TR->pcube);\n    FREE(TR->nscube);\n    Cudd_RecursiveDeref(dd,TR->preiabs);\n    Cudd_RecursiveDeref(dd,TR->prepabs);\n    Cudd_RecursiveDeref(dd,TR->xw);\n    Ntr_HeapForeach(TR->factors, ntrDecreaseRef, dd);\n    Ntr_FreeHeap(TR->factors);\n    FREE(TR);\n\n    return;\n\n} /* end of Ntr_freeTR */\n\n\n/**\n  @brief Makes a copy of a transition relation.\n\n  @return a pointer to the copy if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Ntr_buildTR Ntr_freeTR\n\n*/\nNtrPartTR *\nNtr_cloneTR(\n  NtrPartTR *TR)\n{\n    NtrPartTR *T;\n    int nparts, nlatches, i;\n\n    T = ALLOC(NtrPartTR,1);\n    if (T == NULL) return(NULL);\n    nparts = T->nparts = TR->nparts;\n    nlatches = T->nlatches = TR->nlatches;\n    T->part = ALLOC(DdNode *,nparts);\n    if (T->part == NULL) {\n\tFREE(T);\n\treturn(NULL);\n    }\n    T->icube = ALLOC(DdNode *,nparts);\n    if (T->icube == NULL) {\n\tFREE(T->part);\n\tFREE(T);\n\treturn(NULL);\n    }\n    T->pcube = ALLOC(DdNode *,nparts);\n    if (T->pcube == NULL) {\n\tFREE(T->icube);\n\tFREE(T->part);\n\tFREE(T);\n\treturn(NULL);\n    }\n    T->x = ALLOC(DdNode *,nlatches);\n    if (T->x == NULL) {\n\tFREE(T->pcube);\n\tFREE(T->icube);\n\tFREE(T->part);\n\tFREE(T);\n\treturn(NULL);\n    }\n    T->y = ALLOC(DdNode *,nlatches);\n    if (T->y == NULL) {\n\tFREE(T->x);\n\tFREE(T->pcube);\n\tFREE(T->icube);\n\tFREE(T->part);\n\tFREE(T);\n\treturn(NULL);\n    }\n    T->nscube = ALLOC(DdNode *,nparts);\n    if (T->nscube == NULL) {\n\tFREE(T->y);\n\tFREE(T->x);\n\tFREE(T->pcube);\n\tFREE(T->icube);\n\tFREE(T->part);\n\tFREE(T);\n\treturn(NULL);\n    }\n    T->factors = Ntr_HeapClone(TR->factors);\n    if (T->factors == NULL) {\n\tFREE(T->nscube);\n\tFREE(T->y);\n\tFREE(T->x);\n\tFREE(T->pcube);\n\tFREE(T->icube);\n\tFREE(T->part);\n\tFREE(T);\n\treturn(NULL);\n    }\n    Ntr_HeapForeach(T->factors, ntrIncreaseRef, NULL);\n    for (i = 0; i < nparts; i++) {\n\tT->part[i] = TR->part[i];\n\tCudd_Ref(T->part[i]);\n\tT->icube[i] = TR->icube[i];\n\tCudd_Ref(T->icube[i]);\n\tT->pcube[i] = TR->pcube[i];\n\tCudd_Ref(T->pcube[i]);\n\tT->nscube[i] = TR->nscube[i];\n\tCudd_Ref(T->nscube[i]);\n    }\n    T->preiabs = TR->preiabs;\n    Cudd_Ref(T->preiabs);\n    T->prepabs = TR->prepabs;\n    Cudd_Ref(T->prepabs);\n    T->xw = TR->xw;\n    Cudd_Ref(T->xw);\n    for (i = 0; i < nlatches; i++) {\n\tT->x[i] = TR->x[i];\n\tCudd_Ref(T->x[i]);\n\tT->y[i] = TR->y[i];\n\tCudd_Ref(T->y[i]);\n    }\n\n    return(T);\n\n} /* end of Ntr_cloneTR */\n\n\n/**\n  @brief Poor man's traversal procedure.\n\n  @details Based on the monolithic transition relation.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_ClosureTrav\n\n*/\nint\nNtr_Trav(\n  DdManager * dd /**< %DD manager */,\n  BnetNetwork * net /**< network */,\n  NtrOptions * option /**< options */)\n{\n    NtrPartTR *TR;\t\t/* Transition relation */\n    DdNode *init;\t\t/* initial state(s) */\n    DdNode *from;\n    DdNode *to;\n    DdNode *reached;\n    DdNode *neW;\n    DdNode *one, *zero;\n    int depth;\n    int retval;\n    int pr = option->verb;\n    unsigned int initReord = Cudd_ReadReorderings(dd);\n\n    if (option->traverse == FALSE || net->nlatches == 0) return(1);\n    (void) printf(\"Building transition relation. Time = %s\\n\",\n\t\t  util_print_time(util_cpu_time() - option->initialTime));\n    one = Cudd_ReadOne(dd);\n    zero = Cudd_Not(one);\n\n    /* Build transition relation and initial states. */\n    TR = Ntr_buildTR(dd,net,option,option->image);\n    if (TR == NULL) return(0);\n    retval = Cudd_SetVarMap(dd,TR->x,TR->y,TR->nlatches);\n    if (retval == 0) return(0);\n    (void) printf(\"Transition relation: %d parts %d latches %d nodes\\n\",\n\t\t  TR->nparts, TR->nlatches,\n\t\t  Cudd_SharingSize(TR->part, TR->nparts));\n    (void) printf(\"Traversing. Time = %s\\n\",\n\t\t  util_print_time(util_cpu_time() - option->initialTime));\n    init = Ntr_initState(dd,net,option);\n    if (init == NULL) return(0);\n\n    /* Initialize From. */\n    Cudd_Ref(from = init);\n    (void) printf(\"S0\"); Cudd_PrintDebug(dd,from,TR->nlatches,pr);\n\n    /* Initialize Reached. */\n    Cudd_Ref(reached = from);\n\n    /* Start traversal. */\n    for (depth = 0; ; depth++) {\n\t/* Image computation. */\n\tto = ntrImage(dd,TR,from,option);\n\tif (to == NULL) {\n\t    Cudd_RecursiveDeref(dd,reached);\n\t    Cudd_RecursiveDeref(dd,from);\n\t    return(0);\n\t}\n\tCudd_RecursiveDeref(dd,from);\n\n\t/* Find new states. */\n\tneW = Cudd_bddAnd(dd,to,Cudd_Not(reached));\n\tif (neW == NULL) {\n\t    Cudd_RecursiveDeref(dd,reached);\n\t    Cudd_RecursiveDeref(dd,to);\n\t    return(0);\n\t}\n\tCudd_Ref(neW);\n\tCudd_RecursiveDeref(dd,to);\n\n\t/* Check for convergence. */\n\tif (neW == zero) break;\n\n\t/* Dump current reached states if requested. */\n\tif (option->store == depth) {\n\t    int ok = Dddmp_cuddBddStore(dd, NULL, reached, NULL,\n\t\t\t\t\tNULL, DDDMP_MODE_TEXT, DDDMP_VARIDS,\n\t\t\t\t\toption->storefile, NULL);\n\t    if (ok == 0) return(0);\n\t    (void) printf(\"Storing reached in %s after %i iterations.\\n\",\n\t\t\t  option->storefile, depth);\n\t    break;\n\t}\n\n\t/* Update reached. */\n\treached = ntrUpdateReached(dd,reached,neW);\n\tif (reached == NULL) {\n\t    Cudd_RecursiveDeref(dd,neW);\n\t    return(0);\n\t}\n\n\t/* Prepare for new iteration. */\n\tfrom = ntrChooseFrom(dd,neW,reached,option);\n\tif (from == NULL) {\n\t    Cudd_RecursiveDeref(dd,reached);\n\t    Cudd_RecursiveDeref(dd,neW);\n\t    return(0);\n\t}\n\tCudd_RecursiveDeref(dd,neW);\n\t(void) printf(\"From[%d]\",depth+1);\n\tCudd_PrintDebug(dd,from,TR->nlatches,pr);\n\t(void) printf(\"Reached[%d]\",depth+1);\n\tCudd_PrintDebug(dd,reached,TR->nlatches,pr);\n\tif (pr > 0) {\n\t    if (!Cudd_ApaPrintMinterm(stdout, dd, reached, TR->nlatches))\n\t\treturn(0);\n\t    if (!Cudd_ApaPrintMintermExp(stdout, dd, reached, TR->nlatches, 6))\n\t\treturn(0);\n\t} else {\n\t    (void) printf(\"\\n\");\n\t}\n    }\n\n    /* Print out result. */\n    (void) printf(\"depth = %d\\n\", depth);\n    (void) printf(\"R\"); Cudd_PrintDebug(dd,reached,TR->nlatches,pr);\n\n    /* Dump to file if requested. */\n    if (option->bdddump) {\n\tDdNode *dfunc[2];\t/* addresses of the functions to be dumped */\n\tchar *onames[2];\t/* names of the functions to be dumped */\n\tdfunc[0] = TR->part[0];\t\tonames[0] = (char *) \"T\";\n\tdfunc[1] = reached;\t\tonames[1] = (char *) \"R\";\n\tretval = Bnet_bddArrayDump(dd, net, option->dumpfile, dfunc,\n\t\t\t\t   onames, 2, option->dumpFmt);\n\tif (retval == 0) return(0);\n    }\n\n    if (option->depend) {\n\tretval = ntrLatchDependencies(dd, reached, net, option);\n\tif (retval == -1) return(0);\n\t(void) printf(\"%d latches are redundant\\n\", retval);\n    }\n    /* Clean up. */\n    Cudd_RecursiveDeref(dd,reached);\n    Cudd_RecursiveDeref(dd,neW);\n    Cudd_RecursiveDeref(dd,init);\n    Ntr_freeTR(dd,TR);\n\n    if (Cudd_ReadReorderings(dd) > initReord) {\n\t(void) printf(\"Order at the end of reachability analysis\\n\");\n\tretval = Bnet_PrintOrder(net,dd);\n\tif (retval == 0) return(0);\n    }\n    return(1);\n\n} /* end of Ntr_Trav */\n\n\n/**\n  @brief Computes the SCCs of the STG.\n\n  @details Computes the strongly connected components of the state\n  transition graph.  Only the first 10 SCCs are computed.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_Trav\n\n*/\nint\nNtr_SCC(\n  DdManager * dd /**< %DD manager */,\n  BnetNetwork * net /**< network */,\n  NtrOptions * option /**< options */)\n{\n    NtrPartTR *TR;\t\t/* Transition relation */\n    DdNode *init;\t\t/* initial state(s) */\n    DdNode *from;\n    DdNode *to;\n    DdNode *reached, *reaching;\n    DdNode *neW;\n    DdNode *one, *zero;\n    DdNode *states, *scc;\n    DdNode *tmp = NULL;\n    DdNode *SCCs[10];\n    int depth;\n    int nscc = 0;\n    int retval;\n    int pr = option->verb;\n    int i;\n\n    if (option->scc == FALSE || net->nlatches == 0) return(1);\n    (void) printf(\"Building transition relation. Time = %s\\n\",\n\t\t  util_print_time(util_cpu_time() - option->initialTime));\n    one = Cudd_ReadOne(dd);\n    zero = Cudd_Not(one);\n\n    /* Build transition relation and initial states. */\n    TR = Ntr_buildTR(dd,net,option,option->image);\n    if (TR == NULL) return(0);\n    retval = Cudd_SetVarMap(dd,TR->x,TR->y,TR->nlatches);\n    if (retval == 0) return(0);\n    (void) printf(\"Transition relation: %d parts %d latches %d nodes\\n\",\n\t\t  TR->nparts, TR->nlatches,\n\t\t  Cudd_SharingSize(TR->part, TR->nparts));\n    (void) printf(\"Computing SCCs. Time = %s\\n\",\n\t\t  util_print_time(util_cpu_time() - option->initialTime));\n\n    /* Consider all SCCs, including those not reachable. */\n    states = one;\n    Cudd_Ref(states);\n\n    while (states != zero) {\n\tif (nscc == 0) {\n\t    tmp = Ntr_initState(dd,net,option);\n\t    if (tmp == NULL) return(0);\n\t    init = Cudd_bddPickOneMinterm(dd,tmp,TR->x,TR->nlatches);\n\t} else {\n\t    init = Cudd_bddPickOneMinterm(dd,states,TR->x,TR->nlatches);\n\t}\n\tif (init == NULL) return(0);\n\tCudd_Ref(init);\n\tif (nscc == 0) {\n\t    Cudd_RecursiveDeref(dd,tmp);\n\t}\n\t/* Initialize From. */\n\tCudd_Ref(from = init);\n\t(void) printf(\"S0\"); Cudd_PrintDebug(dd,from,TR->nlatches,pr);\n\n\t/* Initialize Reached. */\n\tCudd_Ref(reached = from);\n\n\t/* Start forward traversal. */\n\tfor (depth = 0; ; depth++) {\n\t    /* Image computation. */\n\t    to = ntrImage(dd,TR,from,option);\n\t    if (to == NULL) {\n\t\treturn(0);\n\t    }\n\t    Cudd_RecursiveDeref(dd,from);\n\n\t    /* Find new states. */\n\t    tmp = Cudd_bddAnd(dd,to,states);\n\t    if (tmp == NULL) return(0); Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(dd,to);\n\t    neW = Cudd_bddAnd(dd,tmp,Cudd_Not(reached));\n\t    if (neW == NULL) return(0); Cudd_Ref(neW);\n\t    Cudd_RecursiveDeref(dd,tmp);\n\n\t    /* Check for convergence. */\n\t    if (neW == zero) break;\n\n\t    /* Update reached. */\n\t    reached = ntrUpdateReached(dd,reached,neW);\n\t    if (reached == NULL) {\n\t\treturn(0);\n\t    }\n\n\t    /* Prepare for new iteration. */\n\t    from = ntrChooseFrom(dd,neW,reached,option);\n\t    if (from == NULL) {\n\t\treturn(0);\n\t    }\n\t    Cudd_RecursiveDeref(dd,neW);\n\t    (void) printf(\"From[%d]\",depth+1);\n\t    Cudd_PrintDebug(dd,from,TR->nlatches,pr);\n\t    (void) printf(\"Reached[%d]\",depth+1);\n\t    Cudd_PrintDebug(dd,reached,TR->nlatches,pr);\n\t    if (pr <= 0) {\n\t\t(void) printf(\"\\n\");\n\t    }\n\t}\n\tCudd_RecursiveDeref(dd,neW);\n\n\t/* Express reached in terms of y variables. This allows us to\n\t** efficiently test for termination during the backward traversal. */\n\ttmp = Cudd_bddVarMap(dd,reached);\n\tif (tmp == NULL) return(0);\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDeref(dd,reached);\n\treached = tmp;\n\n\t/* Initialize from and reaching. */\n\tfrom = Cudd_bddVarMap(dd,init);\n\tCudd_Ref(from);\n\t(void) printf(\"S0\"); Cudd_PrintDebug(dd,from,TR->nlatches,pr);\n\tCudd_Ref(reaching = from);\n\n\t/* Start backward traversal. */\n\tfor (depth = 0; ; depth++) {\n\t    /* Preimage computation. */\n\t    to = ntrPreimage(dd,TR,from);\n\t    if (to == NULL) {\n\t\treturn(0);\n\t    }\n\t    Cudd_RecursiveDeref(dd,from);\n\n\t    /* Find new states. */\n\t    tmp = Cudd_bddAnd(dd,to,reached);\n\t    if (tmp == NULL) return(0); Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(dd,to);\n\t    neW = Cudd_bddAnd(dd,tmp,Cudd_Not(reaching));\n\t    if (neW == NULL) return(0); Cudd_Ref(neW);\n\t    Cudd_RecursiveDeref(dd,tmp);\n\n\t    /* Check for convergence. */\n\t    if (neW == zero) break;\n\n\t    /* Update reaching. */\n\t    reaching = ntrUpdateReached(dd,reaching,neW);\n\t    if (reaching == NULL) {\n\t\treturn(0);\n\t    }\n\n\t    /* Prepare for new iteration. */\n\t    from = ntrChooseFrom(dd,neW,reaching,option);\n\t    if (from == NULL) {\n\t\treturn(0);\n\t    }\n\t    Cudd_RecursiveDeref(dd,neW);\n\t    (void) printf(\"From[%d]\",depth+1);\n\t    Cudd_PrintDebug(dd,from,TR->nlatches,pr);\n\t    (void) printf(\"Reaching[%d]\",depth+1);\n\t    Cudd_PrintDebug(dd,reaching,TR->nlatches,pr);\n\t    if (pr <= 0) {\n\t\t(void) printf(\"\\n\");\n\t    }\n\t}\n\n\tscc = Cudd_bddAnd(dd,reached,reaching);\n\tif (scc == NULL) {\n\t    return(0);\n\t}\n\tCudd_Ref(scc);\n\tSCCs[nscc] = Cudd_bddVarMap(dd,scc);\n\tif (SCCs[nscc] == NULL) return(0);\n\tCudd_Ref(SCCs[nscc]);\n\tCudd_RecursiveDeref(dd,scc);\n\t/* Print out result. */\n\t(void) printf(\"SCC[%d]\",nscc);\n\tCudd_PrintDebug(dd,SCCs[nscc],TR->nlatches,pr);\n\ttmp = Cudd_bddAnd(dd,states,Cudd_Not(SCCs[nscc]));\n\tif (tmp == NULL) {\n\t    return(0);\n\t}\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDeref(dd,states);\n\tstates = tmp;\n\tCudd_RecursiveDeref(dd,reached);\n\tCudd_RecursiveDeref(dd,reaching);\n\tCudd_RecursiveDeref(dd,neW);\n\tCudd_RecursiveDeref(dd,init);\n\tnscc++;\n\tif (nscc > 9) break;\n    }\n\n    if (states != zero) {\n\t(void) fprintf(stdout,\"More than 10 SCCs. Only the first 10 are computed.\\n\");\n    }\n\n    /* Dump to file if requested. */\n    if (option->bdddump) {\n\tchar *sccnames[10];\t/* names of the SCCs */\n\tsccnames[0] = (char *) \"SCC0\";\n\tsccnames[1] = (char *) \"SCC1\";\n\tsccnames[2] = (char *) \"SCC2\";\n\tsccnames[3] = (char *) \"SCC3\";\n\tsccnames[4] = (char *) \"SCC4\";\n\tsccnames[5] = (char *) \"SCC5\";\n\tsccnames[6] = (char *) \"SCC6\";\n\tsccnames[7] = (char *) \"SCC7\";\n\tsccnames[8] = (char *) \"SCC8\";\n\tsccnames[9] = (char *) \"SCC9\";\n\tretval = Bnet_bddArrayDump(dd, net, option->dumpfile, SCCs,\n\t\t\t\t   sccnames, nscc, option->dumpFmt);\n\tif (retval == 0) return(0);\n    }\n\n    /* Verify that the SCCs form a partition of the universe. */\n    scc = zero;\n    Cudd_Ref(scc);\n    for (i = 0; i < nscc; i++) {\n\tassert(Cudd_bddLeq(dd,SCCs[i],Cudd_Not(scc)));\n\ttmp = Cudd_bddOr(dd,SCCs[i],scc);\n\tif (tmp == NULL) return(0);\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDeref(dd,scc);\n\tscc = tmp;\n\tCudd_RecursiveDeref(dd,SCCs[i]);\n    }\n    assert(scc == Cudd_Not(states));\n\n    /* Clean up. */\n    Cudd_RecursiveDeref(dd,scc);\n    Cudd_RecursiveDeref(dd,states);\n    Ntr_freeTR(dd,TR);\n\n    return(1);\n\n} /* end of Ntr_SCC */\n\n\n/**\n  @brief Transitive closure traversal procedure.\n\n  @details Traversal procedure based on the transitive closure of the\n  transition relation.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_Trav\n\n*/\nint\nNtr_ClosureTrav(\n  DdManager * dd /**< %DD manager */,\n  BnetNetwork * net /**< network */,\n  NtrOptions * option /**< options */)\n{\n    DdNode *init;\n    DdNode *T;\n    NtrPartTR *TR;\n    int retval;\n    int pr = option->verb;\t/* verbosity level */\n    DdNode *dfunc[2];\t\t/* addresses of the functions to be dumped */\n    char *onames[2];\t\t/* names of the functions to be dumped */\n    DdNode *reached, *reachedy, *reachedx;\n\n    /* Traverse if requested and if the circuit is sequential. */\n    if (option->closure == FALSE || net->nlatches == 0) return(1);\n\n    TR = Ntr_buildTR(dd,net,option,NTR_IMAGE_MONO);\n    if (TR == NULL) return(0);\n    (void) printf(\"TR\"); Cudd_PrintDebug(dd,TR->part[0],2*TR->nlatches,pr);\n    T = Ntr_TransitiveClosure(dd,TR,option);\n    if (T == NULL) return(0);\n    Cudd_Ref(T);\n    (void) printf(\"TC\"); Cudd_PrintDebug(dd,T,2*TR->nlatches,pr);\n\n    init = Ntr_initState(dd,net,option);\n    if (init == NULL) return(0);\n    (void) printf(\"S0\"); Cudd_PrintDebug(dd,init,TR->nlatches,pr);\n\n    /* Image computation. */\n    if (option->closureClip != 1.0) {\n\tint depth = (int) ((double) Cudd_ReadSize(dd) * option->closureClip);\n\treachedy = Cudd_bddClippingAndAbstract(dd,T,init,TR->icube[0],\n\t\t\t\t\t       depth,option->approx);\n    } else {\n\treachedy = Cudd_bddAndAbstract(dd,T,init,TR->icube[0]);\n    }\n    if (reachedy == NULL) return(0);\n    Cudd_Ref(reachedy);\n\n    /* Express in terms of present state variables. */\n    reachedx = Cudd_bddSwapVariables(dd,reachedy,TR->x,TR->y,TR->nlatches);\n    if (reachedx == NULL) return(0);\n    Cudd_Ref(reachedx);\n    Cudd_RecursiveDeref(dd,reachedy);\n\n    /* Add initial state. */\n    reached = Cudd_bddOr(dd,reachedx,init);\n    if (reached == NULL) return(0);\n    Cudd_Ref(reached);\n    Cudd_RecursiveDeref(dd,reachedx);\n\n    /* Print out result. */\n    (void) printf(\"R\"); Cudd_PrintDebug(dd,reached,TR->nlatches,pr);\n\n    /* Dump to file if requested. */\n    if (option->bdddump) {\n\tdfunc[0] = T;\t\tonames[0] = (char *) \"TC\";\n\tdfunc[1] = reached;\tonames[1] = (char *) \"R\";\n\tretval = Bnet_bddArrayDump(dd, net, option->dumpfile, dfunc,\n\t\t\t\t   onames, 2, option->dumpFmt);\n\tif (retval == 0) return(0);\n    }\n\n    /* Clean up. */\n    Cudd_RecursiveDeref(dd,reached);\n    Cudd_RecursiveDeref(dd,init);\n    Cudd_RecursiveDeref(dd,T);\n    Ntr_freeTR(dd,TR);\n\n    return(1);\n\n} /* end of Ntr_ClosureTrav */\n\n\n/**\n  @brief Builds the transitive closure of a transition relation.\n\n  @details Uses a simple squaring algorithm.\n\n  @return a %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nNtr_TransitiveClosure(\n  DdManager * dd,\n  NtrPartTR * TR,\n  NtrOptions * option)\n{\n    DdNode *T,*oldT,*Txz,*Tzy,*Tred,*square,*zcube;\n    DdNode **z;\n    int i;\n    int depth = 0;\n    int ylevel;\n    int done;\n\n    if (option->image != NTR_IMAGE_MONO) return(NULL);\n\n    /* Create array of auxiliary variables. */\n    z = ALLOC(DdNode *,TR->nlatches);\n    if (z == NULL)\n\treturn(NULL);\n    for (i = 0; i < TR->nlatches; i++) {\n\tylevel = Cudd_ReadIndex(dd,TR->y[i]->index);\n\tz[i] = Cudd_bddNewVarAtLevel(dd,ylevel);\n\tif (z[i] == NULL)\n\t    return(NULL);\n    }\n    /* Build cube of auxiliary variables. */\n    zcube = makecube(dd,z,TR->nlatches);\n    if (zcube == NULL) return(NULL);\n    Cudd_Ref(zcube);\n\n    if (option->closureClip != 1.0) {\n\tdepth = (int) ((double) Cudd_ReadSize(dd) * option->imageClip);\n    }\n\n    T = TR->part[0];\n    Cudd_Ref(T);\n    for (i = 0; ; i++) {\n\tif (option->threshold >= 0) {\n\t    if (option->approx) {\n\t\tTred = Cudd_RemapOverApprox(dd,T,TR->nlatches*2,\n\t\t\t\t\t    option->threshold,\n\t\t\t\t\t    option->quality);\n\t    } else {\n\t\tTred = Cudd_RemapUnderApprox(dd,T,TR->nlatches*2,\n\t\t\t\t\t     option->threshold,\n\t\t\t\t\t     option->quality);\n\t    }\n\t} else {\n\t    Tred = T;\n\t}\n\tif (Tred == NULL) return(NULL);\n\tCudd_Ref(Tred);\n\t/* Express T in terms of z and y variables. */\n\tTzy = Cudd_bddSwapVariables(dd,Tred,TR->x,z,TR->nlatches);\n\tif (Tzy == NULL) return(NULL);\n\tCudd_Ref(Tzy);\n\t/* Express T in terms of x and z variables. */\n\tTxz = Cudd_bddSwapVariables(dd,Tred,TR->y,z,TR->nlatches);\n\tif (Txz == NULL) return(NULL);\n\tCudd_Ref(Txz);\n\tCudd_RecursiveDeref(dd,Tred);\n\t/* Square */\n\tif (depth == 0) {\n\t    square = Cudd_bddAndAbstract(dd,Txz,Tzy,zcube);\n\t} else {\n\t    square = Cudd_bddClippingAndAbstract(dd,Txz,Tzy,zcube,depth,\n\t\t\t\t\t\t option->approx);\n\t}\n\tif (square == NULL) return(NULL);\n\tCudd_Ref(square);\n\tCudd_RecursiveDeref(dd,Tzy);\n\tCudd_RecursiveDeref(dd,Txz);\n\toldT = T;\n\tT = Cudd_bddOr(dd,square,TR->part[0]);\n\tif (T == NULL) return(NULL);\n\tCudd_Ref(T);\n\tCudd_RecursiveDeref(dd,square);\n\tdone = T == oldT;\n\tCudd_RecursiveDeref(dd,oldT);\n\tif (done) break;\n\t(void) fprintf(stdout,\"@\"); fflush(stdout);\n    }\n    (void) fprintf(stdout, \"\\n\");\n\n    Cudd_RecursiveDeref(dd,zcube);\n    Cudd_Deref(T);\n    FREE(z);\n    return(T);\n\n} /* end of Ntr_TransitiveClosure */\n\n\n/**\n  @brief Builds the %BDD of the initial state(s).\n\n  @return a %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nNtr_initState(\n  DdManager * dd,\n  BnetNetwork * net,\n  NtrOptions * option)\n{\n    DdNode *res, *x, *w, *one;\n    BnetNode *node;\n    int i;\n\n    if (option->load) {\n\tres = Dddmp_cuddBddLoad(dd, DDDMP_VAR_MATCHIDS, NULL, NULL, NULL,\n\t\t\t\tDDDMP_MODE_DEFAULT, option->loadfile, NULL);\n    } else {\n\tone = Cudd_ReadOne(dd);\n\tCudd_Ref(res = one);\n\n\tif (net->nlatches == 0) return(res);\n\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    if (!st_lookup(net->hash,net->latches[i][1],(void **)&node)) {\n\t\tgoto endgame;\n\t    }\n\t    x = node->dd;\n\t    switch (net->latches[i][2][0]) {\n\t    case '0':\n\t\tw = Cudd_bddAnd(dd,res,Cudd_Not(x));\n\t\tbreak;\n\t    case '1':\n\t\tw = Cudd_bddAnd(dd,res,x);\n\t\tbreak;\n\t    default: /* don't care */\n\t\tw = res;\n\t\tbreak;\n\t    }\n\n\t    if (w == NULL) {\n\t\tCudd_RecursiveDeref(dd,res);\n\t\treturn(NULL);\n\t    }\n\t    Cudd_Ref(w);\n\t    Cudd_RecursiveDeref(dd,res);\n\t    res = w;\n\t}\n    }\n    return(res);\n\nendgame:\n\n    return(NULL);\n\n} /* end of Ntr_initState */\n\n\n/**\n  @brief Reads a state cube from a file or creates a random one.\n\n  @return a pointer to the %BDD of the sink nodes if successful; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\nDdNode *\nNtr_getStateCube(\n  DdManager * dd,\n  BnetNetwork * net,\n  char * filename,\n  int  pr)\n{\n    FILE *fp;\n    DdNode *cube;\n    DdNode *w;\n    char *state;\n    int i;\n    int err;\n    BnetNode *node;\n    DdNode *x;\n    char c[2];\n\n    cube = Cudd_ReadOne(dd);\n    if (net->nlatches == 0) {\n\tCudd_Ref(cube);\n\treturn(cube);\n    }\n\n    state = ALLOC(char,net->nlatches+1);\n    if (state == NULL)\n\treturn(NULL);\n    state[net->nlatches] = 0;\n\n    if (filename == NULL) {\n\t/* Pick one random minterm. */\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    state[i] = (char) ((Cudd_Random(dd) & 0x2000) ? '1' : '0');\n\t}\n    } else {\n\tif ((fp = fopen(filename,\"r\")) == NULL) {\n\t    (void) fprintf(stderr,\"Unable to open %s\\n\",filename);\n\t    return(NULL);\n\t}\n\n\t/* Read string from file. Allow arbitrary amount of white space. */\n\tfor (i = 0; !feof(fp); i++) {\n\t    err = fscanf(fp, \"%1s\", c);\n\t    state[i] = c[0];\n\t    if (err == EOF || i == net->nlatches - 1) {\n\t\tbreak;\n\t    } else if (err != 1 || strchr(\"012xX-\", c[0]) == NULL ) {\n\t\tFREE(state);\n\t\treturn(NULL);\n\t    }\n\t}\n\terr = fclose(fp);\n\tif (err == EOF) {\n\t    FREE(state);\n\t    return(NULL);\n\t}\n    }\n\n    /* Echo the chosen state(s). */\n    if (pr > 0) {(void) fprintf(stdout,\"%s\\n\", state);}\n\n    Cudd_Ref(cube);\n    for (i = 0; i < net->nlatches; i++) {\n\tif (!st_lookup(net->hash,net->latches[i][1],(void **)&node)) {\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    FREE(state);\n\t    return(NULL);\n\t}\n\tx = node->dd;\n\tswitch (state[i]) {\n\tcase '0':\n\t    w = Cudd_bddAnd(dd,cube,Cudd_Not(x));\n\t    break;\n\tcase '1':\n\t    w = Cudd_bddAnd(dd,cube,x);\n\t    break;\n\tdefault: /* don't care */\n\t    w = cube;\n\t    break;\n\t}\n\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd,cube);\n\t    FREE(state);\n\t    return(NULL);\n\t}\n\tCudd_Ref(w);\n\tCudd_RecursiveDeref(dd,cube);\n\tcube = w;\n    }\n\n    FREE(state);\n    return(cube);\n\n} /* end of Ntr_getStateCube */\n\n\n/**\n  @brief Poor man's outer envelope computation.\n\n  @details Based on the monolithic transition relation.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_Envelope(\n  DdManager * dd /**< %DD manager */,\n  NtrPartTR * TR /**< transition relation */,\n  FILE * dfp /**< pointer to file for %DD dump */,\n  NtrOptions * option /**< program options */)\n{\n    DdNode **x;\t/* array of x variables */\n    DdNode **y;\t/* array of y variables */\n    int ns;\t/* number of x and y variables */\n    DdNode *dfunc[2];\t/* addresses of the functions to be dumped */\n    DdNode *envelope, *oldEnvelope;\n    DdNode *one;\n    int depth;\n    int retval;\n    int pr = option->verb;\n    int dumpFmt = option->dumpFmt;\n\n    x = TR->x;\n    y = TR->y;\n    ns = TR->nlatches;\n\n    one = Cudd_ReadOne(dd);\n    retval = Cudd_SetVarMap(dd,x,y,ns);\n    if (retval == 0) return(0);\n\n    /* Initialize From. */\n    envelope = one;\n    if (envelope == NULL) return(0);\n    Cudd_Ref(envelope);\n    (void) printf(\"S0\"); Cudd_PrintDebug(dd,envelope,ns,pr);\n\n    /* Start traversal. */\n    for (depth = 0; ; depth++) {\n\toldEnvelope = envelope;\n\t/* Image computation. */\n\tenvelope = ntrImage(dd,TR,oldEnvelope,option);\n\tif (envelope == NULL) {\n\t    Cudd_RecursiveDeref(dd,oldEnvelope);\n\t    return(0);\n\t}\n\n\t/* Check for convergence. */\n\tif (envelope == oldEnvelope) break;\n\n\t/* Prepare for new iteration. */\n\tCudd_RecursiveDeref(dd,oldEnvelope);\n\t(void) fprintf(stdout,\"Envelope[%d]%s\",depth+1,(pr>0)? \"\" : \"\\n\");\n        if (pr > 0 ) {\n            Cudd_PrintSummary(dd, envelope, ns, 1 /* exponential format */);\n        }\n    }\n    /* Clean up. */\n    Cudd_RecursiveDeref(dd,oldEnvelope);\n\n    /* Print out result. */\n    (void) printf(\"depth = %d\\n\", depth);\n    (void) printf(\"Envelope\"); Cudd_PrintDebug(dd,envelope,ns,pr);\n\n    /* Write dump file if requested. */\n    if (dfp != NULL) {\n\tdfunc[0] = TR->part[0];\n\tdfunc[1] = envelope;\n\tif (dumpFmt == 1) {\n\t    retval = Cudd_DumpBlif(dd,2,dfunc,NULL,(char const * const *)onames,NULL,dfp,0);\n\t} else if (dumpFmt == 2) {\n\t    retval = Cudd_DumpDaVinci(dd,2,dfunc,NULL,\n                                      (char const * const *)onames,dfp);\n\t} else if (dumpFmt == 3) {\n\t    retval = Cudd_DumpDDcal(dd,2,dfunc,NULL,\n                                    (char const * const *)onames,dfp);\n\t} else if (dumpFmt == 4) {\n\t    retval = Cudd_DumpFactoredForm(dd,2,dfunc,NULL,\n\t\t\t\t\t   (char const * const *)onames,dfp);\n\t} else if (dumpFmt == 5) {\n\t    retval = Cudd_DumpBlif(dd,2,dfunc,NULL,\n                                   (char const * const *)onames,NULL,dfp,1);\n\t} else {\n\t    retval = Cudd_DumpDot(dd,2,dfunc,NULL,\n                                  (char const * const *)onames,dfp);\n\t}\n\tif (retval != 1) {\n\t    (void) fprintf(stderr,\"abnormal termination\\n\");\n\t    return(0);\n\t}\n\tfclose(dfp);\n    }\n\n    /* Clean up. */\n    Cudd_RecursiveDeref(dd,envelope);\n\n    return(1);\n\n} /* end of Ntr_Envelope */\n\n\n/**\n  @brief Maximum 0-1 flow between source and sink states.\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect Creates two new sets of variables.\n\n*/\nint\nNtr_maxflow(\n  DdManager * dd,\n  BnetNetwork * net,\n  NtrOptions * option)\n{\n    DdNode **x = NULL;\n    DdNode **y = NULL;\n    DdNode **z = NULL;\n    DdNode *E = NULL;\n    DdNode *F = NULL;\n    DdNode *cut = NULL;\n    DdNode *sx = NULL;\n    DdNode *ty = NULL;\n    DdNode *tx = NULL;\n    int n;\n    int pr;\n    int ylevel;\n    int i;\n    double flow;\n    int result = 0;\n    NtrPartTR *TR;\n\n    n = net->nlatches;\n    pr = option->verb;\n    TR = Ntr_buildTR(dd,net,option,NTR_IMAGE_MONO);\n    if (TR == NULL)\n\tgoto endgame;\n    E = TR->part[0];\n    x = TR->x;\n    y = TR->y;\n    /* Create array of auxiliary variables. */\n    z = ALLOC(DdNode *,n);\n    if (z == NULL)\n\tgoto endgame;\n    for (i = 0; i < n; i++) {\n\tylevel = Cudd_ReadIndex(dd,y[i]->index);\n\tz[i] = Cudd_bddNewVarAtLevel(dd,ylevel);\n\tif (z[i] == NULL)\n\t    goto endgame;\n\tCudd_Ref(z[i]);\n    }\n    /* Create BDDs for source and sink. */\n    sx = Ntr_initState(dd,net,option);\n    if (sx == NULL)\n\tgoto endgame;\n    if (pr > 0) (void) fprintf(stdout, \"Sink(s): \");\n    tx = Ntr_getStateCube(dd,net,option->sinkfile,pr);\n    if (tx == NULL)\n\tgoto endgame;\n    ty = Cudd_bddSwapVariables(dd,tx,x,y,n);\n    if (ty == NULL)\n\tgoto endgame;\n    Cudd_Ref(ty);\n    Cudd_RecursiveDeref(dd,tx);\n    tx = NULL;\n\n    flow = Ntr_maximum01Flow(dd, sx, ty, E, &F, &cut, x, y, z, n, pr);\n    if (flow >= 0.0)\n\tresult = 1;\n    if (pr >= 0) {\n\t(void) fprintf(stdout,\"Maximum flow = %g\\n\", flow);\n\t(void) fprintf(stdout,\"E\"); Cudd_PrintDebug(dd,E,2*n,pr);\n\t(void) fprintf(stdout,\"F\"); Cudd_PrintDebug(dd,F,2*n,pr);\n\t(void) fprintf(stdout,\"cut\"); Cudd_PrintDebug(dd,cut,2*n,pr);\n    }\nendgame:\n    /* Clean up. */\n    if (TR != NULL) Ntr_freeTR(dd,TR);\n    for (i = 0; i < n; i++) {\n\tif (z != NULL && z[i] != NULL) Cudd_RecursiveDeref(dd,z[i]);\n    }\n    if (z != NULL) FREE(z);\n    if (F != NULL) Cudd_RecursiveDeref(dd,F);\n    if (cut != NULL) Cudd_RecursiveDeref(dd,cut);\n    if (sx != NULL) Cudd_RecursiveDeref(dd,sx);\n    if (ty != NULL) Cudd_RecursiveDeref(dd,ty);\n    return(result);\n\n} /* end of Ntr_Maxflow */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Builds a positive cube of all the variables in x.\n\n  @return a %BDD for the cube if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic DdNode *\nmakecube(\n  DdManager * dd,\n  DdNode ** x,\n  int  n)\n{\n    DdNode *res, *w, *one;\n    int i;\n\n    one = Cudd_ReadOne(dd);\n    Cudd_Ref(res = one);\n\n    for (i = n-1; i >= 0; i--) {\n\tw = Cudd_bddAnd(dd,res,x[i]);\n\tif (w == NULL) {\n\t    Cudd_RecursiveDeref(dd,res);\n\t    return(NULL);\n\t}\n\tCudd_Ref(w);\n\tCudd_RecursiveDeref(dd,res);\n\tres = w;\n    }\n    Cudd_Deref(res);\n    return(res);\n\n} /* end of makecube */\n\n\n/**\n  @brief Initializes the count fields used to drop DDs.\n\n  @details Before actually building the BDDs, we perform a DFS from\n  the outputs to initialize the count fields of the nodes.  The\n  initial value of the count field will normally coincide with the\n  fanout of the node.  However, if there are nodes with no path to any\n  primary output or next state variable, then the initial value of\n  count for some nodes will be less than the fanout. For primary\n  outputs and next state functions we add 1, so that we will never try\n  to free their DDs. The count fields of the nodes that are not\n  reachable from the outputs are set to -1.\n\n  @sideeffect Changes the count fields of the network nodes. Uses the\n  visited fields.\n\n*/\nstatic void\nntrInitializeCount(\n  BnetNetwork * net,\n  NtrOptions * option)\n{\n    BnetNode *node;\n    int i;\n\n    if (option->node != NULL &&\n\toption->closestCube == FALSE && option->dontcares == FALSE) {\n\tif (!st_lookup(net->hash,option->node,(void **)&node)) {\n\t    (void) fprintf(stdout, \"Warning: node %s not found!\\n\",\n\t\t\t   option->node);\n\t} else {\n\t    ntrCountDFS(net,node);\n\t    node->count++;\n\t}\n    } else {\n\tif (option->stateOnly == FALSE) {\n\t    for (i = 0; i < net->npos; i++) {\n\t\tif (!st_lookup(net->hash,net->outputs[i],(void **)&node)) {\n\t\t    (void) fprintf(stdout,\n\t\t\t\t   \"Warning: output %s is not driven!\\n\",\n\t\t\t\t   net->outputs[i]);\n\t\t    continue;\n\t\t}\n\t\tntrCountDFS(net,node);\n\t\tnode->count++;\n\t    }\n\t}\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    if (!st_lookup(net->hash,net->latches[i][0],(void **)&node)) {\n\t\t(void) fprintf(stdout,\n\t\t\t       \"Warning: latch input %s is not driven!\\n\",\n\t\t\t       net->outputs[i]);\n\t\tcontinue;\n\t    }\n\t    ntrCountDFS(net,node);\n\t    node->count++;\n\t}\n    }\n\n    /* Clear visited flags. */\n    node = net->nodes;\n    while (node != NULL) {\n\tif (node->visited == 0) {\n\t    node->count = -1;\n\t} else {\n\t    node->visited = 0;\n\t}\n\tnode = node->next;\n    }\n\n} /* end of ntrInitializeCount */\n\n\n/**\n  @brief Does a DFS from a node setting the count field.\n\n  @sideeffect Changes the count and visited fields of the nodes it\n  visits.\n\n  @see ntrLevelDFS\n\n*/\nstatic void\nntrCountDFS(\n  BnetNetwork * net,\n  BnetNode * node)\n{\n    int i;\n    BnetNode *auxnd;\n\n    node->count++;\n\n    if (node->visited == 1) {\n\treturn;\n    }\n\n    node->visited = 1;\n\n    for (i = 0; i < node->ninp; i++) {\n\tif (!st_lookup(net->hash, node->inputs[i], (void **)&auxnd)) {\n\t    exit(2);\n\t}\n\tntrCountDFS(net,auxnd);\n    }\n\n} /* end of ntrCountDFS */\n\n\n/**\n  @brief Computes the image of a set given a transition relation.\n\n  @details The image is returned in terms of the present state\n  variables; its reference count is already increased.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Ntr_Trav\n\n*/\nstatic DdNode *\nntrImage(\n  DdManager * dd,\n  NtrPartTR * TR,\n  DdNode * from,\n  NtrOptions * option)\n{\n    int i;\n    DdNode *image;\n    DdNode *to;\n    NtrPartTR *T;\n    int depth = 0;\n\n    if (option->image == NTR_IMAGE_CLIP) {\n\tdepth = (int) ((double) Cudd_ReadSize(dd) * option->imageClip);\n    }\n\n    /* Existentially quantify the present state variables that are not\n    ** in the support of any next state function. */\n    image = Cudd_bddExistAbstract(dd,from,TR->preiabs);\n    if (image == NULL) return(NULL);\n    Cudd_Ref(image);\n    if (option->image == NTR_IMAGE_DEPEND) {\n\t/* Simplify the transition relation based on dependencies\n\t** and build the conjuncts from the deltas. */\n\tT = ntrEliminateDependencies(dd,TR,&image,option);\n    } else {\n\tT = TR;\n    }\n    if (T == NULL) return(NULL);\n    for (i = 0; i < T->nparts; i++) {\n#if 0\n\t(void) printf(\"  Intermediate product[%d]: %d nodes\\n\",\n\t\t      i,Cudd_DagSize(image));\n#endif\n\tif (option->image == NTR_IMAGE_CLIP) {\n\t    to = Cudd_bddClippingAndAbstract(dd,T->part[i],image,T->icube[i],\n\t\t\t\t\t     depth,option->approx);\n\t} else {\n\t    to = Cudd_bddAndAbstract(dd,T->part[i],image,T->icube[i]);\n\t}\n\tif (to == NULL) return(NULL);\n\tCudd_Ref(to);\n\tif (option->image == NTR_IMAGE_DEPEND) {\n\t    /* Extract dependencies from intermediate product. */\n\t    DdNode *abs, *positive, *absabs, *phi, *exnor, *tmp;\n\t    abs = Cudd_bddExistAbstract(dd,to,T->xw);\n\t    if (abs == NULL) return(NULL); Cudd_Ref(abs);\n\t    if (Cudd_bddVarIsDependent(dd,abs,T->nscube[i]) &&\n\t\tCudd_EstimateCofactor(dd,abs,T->nscube[i]->index,1) <=\n\t\tT->nlatches) {\n\t\tint retval, sizex;\n\t\tpositive = Cudd_Cofactor(dd,abs,T->nscube[i]);\n\t\tif (positive == NULL) return(NULL); Cudd_Ref(positive);\n\t\tabsabs = Cudd_bddExistAbstract(dd,abs,T->nscube[i]);\n\t\tif (absabs == NULL) return(NULL); Cudd_Ref(absabs);\n\t\tCudd_RecursiveDeref(dd,abs);\n\t\tphi = Cudd_bddLICompaction(dd,positive,absabs);\n\t\tif (phi == NULL) return(NULL); Cudd_Ref(phi);\n\t\tCudd_RecursiveDeref(dd,positive);\n\t\tCudd_RecursiveDeref(dd,absabs);\n\t\texnor = Cudd_bddXnor(dd,T->nscube[i],phi);\n\t\tif (exnor == NULL) return(NULL); Cudd_Ref(exnor);\n\t\tCudd_RecursiveDeref(dd,phi);\n\t\tsizex = Cudd_DagSize(exnor);\n\t\t(void) printf(\"new factor of %d nodes\\n\", sizex);\n\t\tretval = Ntr_HeapInsert(T->factors,exnor,sizex);\n\t\tif (retval == 0) return(NULL);\n\t\ttmp = Cudd_bddExistAbstract(dd,to,T->nscube[i]);\n\t\tif (tmp == NULL) return(NULL); Cudd_Ref(tmp);\n\t\tCudd_RecursiveDeref(dd,to);\n\t\tto = tmp;\n\t    } else {\n\t\tCudd_RecursiveDeref(dd,abs);\n\t    }\n\t}\n\tCudd_RecursiveDeref(dd,image);\n\timage = to;\n    }\n    if (option->image == NTR_IMAGE_DEPEND) {\n\tint size1, size2;\n\tDdNode *factor1, *factor2, *tmp;\n\tint retval;\n\tsize1 = Cudd_DagSize(image);\n\tretval = Ntr_HeapInsert(T->factors,image,size1);\n\tif (retval == 0) return(NULL);\n\t(void) printf(\"Merging %d factors. Independent image: %d nodes\\n\",\n\t\t      Ntr_HeapCount(T->factors), size1);\n\twhile (Ntr_HeapCount(T->factors) > 1) {\n\t    retval = Ntr_HeapExtractMin(T->factors,&factor1,&size1);\n\t    if (retval == 0) return(NULL);\n\t    retval = Ntr_HeapExtractMin(T->factors,&factor2,&size2);\n\t    if (retval == 0) return(NULL);\n\t    tmp = Cudd_bddAnd(dd,factor1,factor2);\n\t    if (tmp == NULL) return(NULL); Cudd_Ref(tmp);\n\t    size1 = Cudd_DagSize(tmp);\n\t    (void) printf(\"new factor %d nodes\\n\", size1);\n\t    Cudd_RecursiveDeref(dd,factor1);\n\t    Cudd_RecursiveDeref(dd,factor2);\n\t    retval = Ntr_HeapInsert(T->factors,tmp,size1);\n\t    if (retval == 0) return(NULL);\n\t}\n\tretval = Ntr_HeapExtractMin(T->factors,&image,&size1);\n\tif (retval == 0) return(NULL);\n\tNtr_freeTR(dd,T);\n    }\n\n    /* Express image in terms of x variables. */\n    to = Cudd_bddVarMap(dd,image);\n    if (to == NULL) {\n\tCudd_RecursiveDeref(dd,image);\n\treturn(NULL);\n    }\n    Cudd_Ref(to);\n    Cudd_RecursiveDeref(dd,image);\n    return(to);\n\n} /* end of ntrImage */\n\n\n/**\n  @brief Computes the preimage of a set given a transition relation.\n\n  @details The preimage is returned in terms of the next state\n  variables; its reference count is already increased.\n\n  @return a pointer to the result if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see ntrImage Ntr_SCC\n\n*/\nstatic DdNode *\nntrPreimage(\n  DdManager * dd,\n  NtrPartTR * T,\n  DdNode * from)\n{\n    int i;\n    DdNode *preimage;\n    DdNode *to;\n\n    /* Existentially quantify the present state variables that are not\n    ** in the support of any next state function. */\n    preimage = Cudd_bddExistAbstract(dd,from,T->prepabs);\n    if (preimage == NULL) return(NULL);\n    Cudd_Ref(preimage);\n    for (i = 0; i < T->nparts; i++) {\n#if 0\n\t(void) printf(\"  Intermediate product[%d]: %d nodes\\n\",\n\t\t      i,Cudd_DagSize(preimage));\n#endif\n\tto = Cudd_bddAndAbstract(dd,T->part[i],preimage,T->pcube[i]);\n\tif (to == NULL) return(NULL);\n\tCudd_Ref(to);\n\tCudd_RecursiveDeref(dd,preimage);\n\tpreimage = to;\n    }\n\n    /* Express preimage in terms of x variables. */\n    to = Cudd_bddVarMap(dd,preimage);\n    if (to == NULL) {\n\tCudd_RecursiveDeref(dd,preimage);\n\treturn(NULL);\n    }\n    Cudd_Ref(to);\n    Cudd_RecursiveDeref(dd,preimage);\n    return(to);\n\n} /* end of ntrPreimage */\n\n\n/**\n  @brief Chooses the initial states for a BFS step.\n\n  @details The reference count of the result is already incremented.\n\n  @return a pointer to the chose set if successful; NULL otherwise.\n\n  @sideeffect none\n\n  @see Ntr_Trav\n\n*/\nstatic DdNode *\nntrChooseFrom(\n  DdManager * dd,\n  DdNode * neW,\n  DdNode * reached,\n  NtrOptions * option)\n{\n    DdNode *min, *c;\n    int threshold;\n\n    switch (option->from) {\n    case NTR_FROM_NEW:\n\tCudd_Ref(neW);\n\treturn(neW);\n    case NTR_FROM_REACHED:\n\tCudd_Ref(reached);\n\treturn(reached);\n    case NTR_FROM_RESTRICT:\n\tc = Cudd_bddOr(dd, neW, Cudd_Not(reached));\n\tif (c == NULL) return(NULL);\n\tCudd_Ref(c);\n\tmin = Cudd_bddRestrict(dd,neW,c);\n\tif (min == NULL) {\n\t    Cudd_RecursiveDeref(dd, c);\n\t    return(NULL);\n\t}\n\tCudd_Ref(min);\n\tCudd_RecursiveDeref(dd, c);\n\treturn(min);\n    case NTR_FROM_COMPACT:\n\tc = Cudd_bddOr(dd, neW, Cudd_Not(reached));\n\tif (c == NULL) return(NULL);\n\tCudd_Ref(c);\n\tmin = Cudd_bddLICompaction(dd,neW,c);\n\tif (min == NULL) {\n\t    Cudd_RecursiveDeref(dd, c);\n\t    return(NULL);\n\t}\n\tCudd_Ref(min);\n\tCudd_RecursiveDeref(dd, c);\n\treturn(min);\n    case NTR_FROM_SQUEEZE:\n\tmin = Cudd_bddSqueeze(dd,neW,reached);\n\tif (min == NULL) return(NULL);\n\tCudd_Ref(min);\n\treturn(min);\n    case NTR_FROM_UNDERAPPROX:\n\tthreshold = (option->threshold < 0) ? 0 : option->threshold;\n\tmin = Cudd_RemapUnderApprox(dd,neW,Cudd_SupportSize(dd,neW),\n\t\tthreshold,option->quality);\n\tif (min == NULL) return(NULL);\n\tCudd_Ref(min);\n\treturn(min);\n    case NTR_FROM_OVERAPPROX:\n\tthreshold = (option->threshold < 0) ? 0 : option->threshold;\n\tmin = Cudd_RemapOverApprox(dd,neW,Cudd_SupportSize(dd,neW),\n\t\tthreshold,option->quality);\n\tif (min == NULL) return(NULL);\n\tCudd_Ref(min);\n\treturn(min);\n    default:\n\treturn(NULL);\n    }\n\n} /* end of ntrChooseFrom */\n\n\n/**\n  @brief Updates the reached states after a traversal step.\n\n  @details The reference count of the result is already incremented.\n\n  @return a pointer to the new reached set if successful; NULL\n  otherwise.\n\n  @sideeffect The old reached set is dereferenced.\n\n  @see Ntr_Trav\n\n*/\nstatic DdNode *\nntrUpdateReached(\n  DdManager * dd /**< manager */,\n  DdNode * oldreached /**< old reached state set */,\n  DdNode * to /**< result of last image computation */)\n{\n    DdNode *reached;\n\n    reached = Cudd_bddOr(dd,oldreached,to);\n    if (reached == NULL) {\n\tCudd_RecursiveDeref(dd,oldreached);\n\treturn(NULL);\n    }\n    Cudd_Ref(reached);\n    Cudd_RecursiveDeref(dd,oldreached);\n    return(reached);\n\n} /* end of ntrUpdateReached */\n\n\n/**\n  @brief Analyzes the reached states after traversal to find\n  dependent latches.\n\n  @details The algorithm is greedy and determines a local optimum, not\n  a global one.\n\n  @return the number of latches that can be eliminated because they\n  are stuck at a constant value or are dependent on others if\n  successful; -1 otherwise.\n\n  @see Ntr_Trav\n\n*/\nstatic int\nntrLatchDependencies(\n  DdManager *dd,\n  DdNode *reached,\n  BnetNetwork *net,\n  NtrOptions *option)\n{\n    int i;\n    int howMany;\t\t/* number of latches that can be eliminated */\n    DdNode *var, *newreached, *abs, *positive, *phi;\n    char *name;\n    BnetNode *node;\n    int initVars, finalVars;\n    double initStates, finalStates;\n    DdNode **roots;\n    char **onames;\n    int howManySmall = 0;\n    int *candidates;\n    double minStates;\n    int totalVars;\n\n    (void) printf(\"Analyzing latch dependencies\\n\");\n    roots = ALLOC(DdNode *, net->nlatches);\n    if (roots == NULL) return(-1);\n    onames = ALLOC(char *, net->nlatches);\n    if (onames == NULL) return(-1);\n\n    candidates = ALLOC(int,net->nlatches);\n    if (candidates == NULL) return(-1);\n    for (i = 0; i < net->nlatches; i++) {\n\tcandidates[i] = i;\n    }\n    /* The signatures of the variables in a function are the number\n    ** of minterms of the positive cofactors with respect to the\n    ** variables themselves. */\n    newreached = reached;\n    Cudd_Ref(newreached);\n    signatures = Cudd_CofMinterm(dd,newreached);\n    if (signatures == NULL) return(-1);\n    /* We now extract a positive quantity which is higher for those\n    ** variables that are closer to being essential. */\n    totalVars = Cudd_ReadSize(dd);\n    minStates = signatures[totalVars];\n#if 0\n    (void) printf(\"Raw signatures (minStates = %g)\\n\", minStates);\n    for (i = 0; i < net->nlatches; i++) {\n\tint j = candidates[i];\n\tif (!st_lookup(net->hash,net->latches[j][1],(void **)&node)) {\n\t    return(-1);\n\t}\n\t(void) printf(\"%s -> %g\\n\", node->name, signatures[node->dd->index]);\n    }\n#endif\n    for (i = 0; i < totalVars; i++) {\n\tdouble z = signatures[i] / minStates - 1.0;\n\tsignatures[i] = (z >= 0.0) ? z : -z;\t/* make positive */\n    }\n    staticNet = net;\n    util_qsort(candidates,net->nlatches,sizeof(int),\n               (DD_QSFP)ntrSignatureCompare2);\n#if 0\n    (void) printf(\"Cooked signatures\\n\");\n    for (i = 0; i < net->nlatches; i++) {\n\tint j = candidates[i];\n\tif (!st_lookup(net->hash,net->latches[j][1],(void **)&node)) {\n\t    return(-1);\n\t}\n\t(void) printf(\"%s -> %g\\n\", node->name, signatures[node->dd->index]);\n    }\n#endif\n    FREE(signatures);\n\n    /* Extract simple dependencies. */\n    for (i = 0; i < net->nlatches; i++) {\n\tint j = candidates[i];\n\tif (!st_lookup(net->hash,net->latches[j][1],(void **)&node)) {\n\t    return(-1);\n\t}\n\tvar = node->dd;\n\tname = node->name;\n\tif (Cudd_bddVarIsDependent(dd,newreached,var)) {\n\t    positive = Cudd_Cofactor(dd,newreached,var);\n\t    if (positive == NULL) return(-1); Cudd_Ref(positive);\n\t    abs = Cudd_bddExistAbstract(dd,newreached,var);\n\t    if (abs == NULL) return(-1); Cudd_Ref(abs);\n\t    phi = Cudd_bddLICompaction(dd,positive,abs);\n\t    if (phi == NULL) return(-1); Cudd_Ref(phi);\n\t    Cudd_RecursiveDeref(dd,positive);\n\t    if (Cudd_DagSize(phi) < NTR_MAX_DEP_SIZE) {\n\t\tif (Cudd_bddLeq(dd,newreached,var)) {\n\t\t    (void) printf(\"%s is stuck at 1\\n\",name);\n\t\t} else if (Cudd_bddLeq(dd,newreached,Cudd_Not(var))) {\n\t\t    (void) printf(\"%s is stuck at 0\\n\",name);\n\t\t} else {\n\t\t    (void) printf(\"%s depends on the other variables\\n\",name);\n\t\t}\n\t\troots[howManySmall] = phi;\n\t\tonames[howManySmall] = util_strsav(name);\n\t\tCudd_RecursiveDeref(dd,newreached);\n\t\tnewreached = abs;\n\t\thowManySmall++;\n\t\tcandidates[i] = -1; /* do not reconsider */\n\t    } else {\n\t\tCudd_RecursiveDeref(dd,abs);\n\t\tCudd_RecursiveDeref(dd,phi);\n\t    }\n\t} else {\n\t    candidates[i] = -1;\t/* do not reconsider */\n\t}\n    }\n    /* Now remove remaining dependent variables. */\n    howMany = howManySmall;\n    for (i = 0; i < net->nlatches; i++) {\n\tint j = candidates[i];\n\tif (j == -1) continue;\n\tif (!st_lookup(net->hash,net->latches[j][1],(void **)&node)) {\n\t    return(-1);\n\t}\n\tvar = node->dd;\n\tname = node->name;\n\tif (Cudd_bddVarIsDependent(dd,newreached,var)) {\n\t    if (Cudd_bddLeq(dd,newreached,var)) {\n\t\t(void) printf(\"%s is stuck at 1\\n\",name);\n\t    } else if (Cudd_bddLeq(dd,newreached,Cudd_Not(var))) {\n\t\t(void) printf(\"%s is stuck at 0\\n\",name);\n\t    } else {\n\t\t(void) printf(\"%s depends on the other variables\\n\",name);\n\t    }\n\t    abs = Cudd_bddExistAbstract(dd,newreached,var);\n\t    if (abs == NULL) return(-1); Cudd_Ref(abs);\n\t    Cudd_RecursiveDeref(dd,newreached);\n\t    newreached = abs;\n\t    howMany++;\n\t}\n    }\n    FREE(candidates);\n    if (howManySmall > 0 && option->verb > 1) {\n\tif (!Bnet_bddArrayDump(dd,net,(char *)\"-\",roots,onames,howManySmall,1))\n\t    return(-1);\n    }\n    for (i = 0; i < howManySmall; i++) {\n\tCudd_RecursiveDeref(dd,roots[i]);\n\tFREE(onames[i]);\n    }\n    FREE(roots);\n    FREE(onames);\n\n    initVars = net->nlatches;\n    initStates = Cudd_CountMinterm(dd,reached,initVars);\n    finalVars = initVars - howMany;\n    finalStates = Cudd_CountMinterm(dd,newreached,finalVars);\n    if (initStates != finalStates) {\n\t(void) printf(\"Error: the number of states changed from %g to %g\\n\",\n\t\t      initStates, finalStates);\n\treturn(-1);\n    }\n    (void) printf(\"new reached\");\n    Cudd_PrintDebug(dd,newreached,finalVars,option->verb);\n    Cudd_RecursiveDeref(dd,newreached);\n    return(howMany);\n\n} /* end of ntrLatchDependencies */\n\n\n/**\n  @brief Eliminates dependent variables from a transition relation.\n\n  @return a simplified copy of the given transition relation if\n  successful; NULL otherwise.\n\n  @sideeffect The modified set of states is returned as a side effect.\n\n  @see ntrImage\n\n*/\nstatic NtrPartTR *\nntrEliminateDependencies(\n  DdManager *dd,\n  NtrPartTR *TR,\n  DdNode **states,\n  NtrOptions *option)\n{\n    NtrPartTR *T;\t\t/* new TR without dependent vars */\n    int pr = option->verb;\n    int i, j;\n    int howMany = 0;\t\t/* number of latches that can be eliminated */\n    DdNode *var, *newstates, *abs, *positive, *phi;\n    DdNode *support, *scan, *tmp;\n    int finalSize;\t\t/* size of the TR after substitutions */\n    int nvars;\t\t\t/* vars in the support of the state set */\n    int *candidates;\t\t/* vars to be considered for elimination */\n    int totalVars;\n    double minStates;\n\n    /* Initialize the new transition relation by copying the old one. */\n    T = Ntr_cloneTR(TR);\n    if (T == NULL) return(NULL);\n\n    /* Find and rank the candidate variables. */\n    newstates = *states;\n    Cudd_Ref(newstates);\n    support = Cudd_Support(dd,newstates);\n    if (support == NULL) {\n        Cudd_RecursiveDeref(dd,newstates);\n\tNtr_freeTR(dd,T);\n\treturn(NULL);\n    }\n    Cudd_Ref(support);\n    nvars = Cudd_DagSize(support) - 1;\n    candidates = ALLOC(int,nvars);\n    if (candidates == NULL) {\n\tCudd_RecursiveDeref(dd,support);\n        Cudd_RecursiveDeref(dd,newstates);\n\tNtr_freeTR(dd,T);\n\treturn(NULL);\n    }\n    scan  = support;\n    for (i = 0; i < nvars; i++) {\n\tcandidates[i] = scan->index;\n\tscan = Cudd_T(scan);\n    }\n    Cudd_RecursiveDeref(dd,support);\n    /* The signatures of the variables in a function are the number\n    ** of minterms of the positive cofactors with respect to the\n    ** variables themselves. */\n    signatures = Cudd_CofMinterm(dd,newstates);\n    if (signatures == NULL) {\n\tFREE(candidates);\n        Cudd_RecursiveDeref(dd,newstates);\n\tNtr_freeTR(dd,T);\n\treturn(NULL);\n    }\n    /* We now extract a positive quantity which is higher for those\n    ** variables that are closer to being essential. */\n    totalVars = Cudd_ReadSize(dd);\n    minStates = signatures[totalVars];\n    for (i = 0; i < totalVars; i++) {\n\tdouble z = signatures[i] / minStates - 1.0;\n\tsignatures[i] = (z < 0.0) ? -z : z;\t/* make positive */\n    }\n    /* Sort candidates in decreasing order of signature. */\n    util_qsort(candidates,nvars,sizeof(int), (DD_QSFP)ntrSignatureCompare);\n    FREE(signatures);\n\n    /* Now process the candidates in the given order. */\n    for (i = 0; i < nvars; i++) {\n\tvar = Cudd_bddIthVar(dd,candidates[i]);\n\tif (Cudd_bddVarIsDependent(dd,newstates,var)) {\n\t    abs = Cudd_bddExistAbstract(dd,newstates,var);\n\t    if (abs == NULL) return(NULL); Cudd_Ref(abs);\n\t    positive = Cudd_Cofactor(dd,newstates,var);\n\t    if (positive == NULL) return(NULL); Cudd_Ref(positive);\n\t    phi = Cudd_bddLICompaction(dd,positive,abs);\n\t    if (phi == NULL) return(NULL); Cudd_Ref(phi);\n\t    Cudd_RecursiveDeref(dd,positive);\n#if 0\n\t    if (pr > 0) {\n\t\t(void) printf(\"Phi\");\n\t\tCudd_PrintDebug(dd,phi,T->nlatches,pr);\n\t    }\n#endif\n\t    if (Cudd_DagSize(phi) < NTR_MAX_DEP_SIZE) {\n\t\thowMany++;\n\t\tfor (j = 0; j < T->nparts; j++) {\n\t\t    tmp = Cudd_bddCompose(dd,T->part[j],phi,candidates[i]);\n\t\t    if (tmp == NULL) return(NULL); Cudd_Ref(tmp);\n\t\t    Cudd_RecursiveDeref(dd,T->part[j]);\n\t\t    T->part[j] = tmp;\n\t\t}\n\t\tCudd_RecursiveDeref(dd,newstates);\n\t\tnewstates = abs;\n\t    } else {\n\t\tCudd_RecursiveDeref(dd,abs);\n\t    }\n\t    Cudd_RecursiveDeref(dd,phi);\n\t}\n    }\n    FREE(candidates);\n\n    if (pr > 0) {\n\tfinalSize = Cudd_SharingSize(T->part,T->nparts);\n\t(void) printf(\"Eliminated %d vars. Transition function %d nodes.\\n\",\n\t\t      howMany,finalSize);\n    }\n\n    if (!ntrUpdateQuantificationSchedule(dd,T)) return(NULL);\n\n    /* Quantify out of states variables that no longer appear in any part. */\n    Cudd_RecursiveDeref(dd,*states);\n    *states = Cudd_bddExistAbstract(dd,newstates,T->preiabs);\n    if (*states == NULL) {\n        Cudd_RecursiveDeref(dd,newstates);\n        return(NULL);\n    }\n    Cudd_Ref(*states);\n    Cudd_RecursiveDeref(dd,newstates);\n    return(T);\n\n} /* end of ntrEliminateDependencies */\n\n\n/**\n  @brief Updates the quantification schedule of a transition relation.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see ntrEliminateDependencies\n\n*/\nstatic int\nntrUpdateQuantificationSchedule(\n  DdManager *dd,\n  NtrPartTR *T)\n{\n    int i, j, k;\n    int *schedule;\n    DdNode *one, *support, *scan, *var, *tmp;\n    char **matrix;\n    int *position, *row;\n    char *flags;\n    int nparts, nvars;\n    int extracted;\n#if 0\n    int schedcost;\n#endif\n\n    nparts = T->nparts;\n    nvars = Cudd_ReadSize(dd);\n    one = Cudd_ReadOne(dd);\n\n    /* Reinitialize the abstraction cubes. */\n    Cudd_RecursiveDeref(dd,T->preiabs);\n    T->preiabs = one;\n    Cudd_Ref(one);\n    for (i = 0; i < nparts; i++) {\n\tCudd_RecursiveDeref(dd,T->icube[i]);\n\tT->icube[i] = one;\n\tCudd_Ref(one);\n    }\n\n    /* Initialize row permutations to the identity. */\n    position = ALLOC(int,nparts);\n    if (position == NULL) return(0);\n    for (i = 0; i < nparts; i++) {\n\tposition[i] = i;\n    }\n    /* Sort parts so that parts that differ only\n    ** in the index of the next state variable are contiguous. */\n    staticPart = T->part;\n    util_qsort(position,nparts,sizeof(int), (DD_QSFP)ntrPartCompare);\n    /* Extract repeated parts. */\n    extracted = 0;\n    for (i = 0; i < nparts - 1; i += j) {\n\tint pi, pij;\n\tDdNode *eq;\n\tj = 1;\n\tpi = position[i];\n\teq = one;\n\tCudd_Ref(eq);\n\tpij = position[i+j];\n\twhile (Cudd_Regular(staticPart[pij]) == Cudd_Regular(staticPart[pi])) {\n\t    int comple = staticPart[pij] != staticPart[pi];\n\t    DdNode *xnor = Cudd_bddXnor(dd,T->nscube[pi],\n\t\t\t\t\tCudd_NotCond(T->nscube[pij],comple));\n\t    if (xnor == NULL) return(0); Cudd_Ref(xnor);\n\t    tmp = Cudd_bddAnd(dd,xnor,eq);\n\t    if (tmp == NULL) return(0); Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(dd,xnor);\n\t    Cudd_RecursiveDeref(dd,eq);\n\t    eq = tmp;\n\t    Cudd_RecursiveDeref(dd,T->part[pij]);\n\t    Cudd_RecursiveDeref(dd,T->icube[pij]);\n\t    Cudd_RecursiveDeref(dd,T->pcube[pij]);\n\t    Cudd_RecursiveDeref(dd,T->nscube[pij]);\n\t    T->part[pij] = NULL;\n\t    j++;\n\t    if (i+j == nparts) break;\n\t    pij = position[i+j];\n\t}\n\tif (eq != one) {\n\t    int retval = Ntr_HeapInsert(T->factors,eq,Cudd_DagSize(eq));\n\t    if (retval == 0) return(0);\n\t    extracted += j - 1;\n\t} else {\n\t    Cudd_RecursiveDeref(dd,eq);\n\t}\n    }\n    /* Compact the part array by removing extracted parts. */\n    for (i = 0, j = 0; i < nparts; i++) {\n\tif (T->part[i] != NULL) {\n\t    T->part[j] = T->part[i];\n\t    T->icube[j] = T->icube[i];\n            T->pcube[j] = T->pcube[i];\n\t    T->nscube[j] = T->nscube[i];\n\t    j++;\n\t}\n    }\n    nparts = T->nparts -= extracted;\n    (void) printf(\"Extracted %d repeated parts in %d factors.\\n\",\n\t\t  extracted, Ntr_HeapCount(T->factors));\n\n    /* Build the support matrix. Each row corresponds to a part of the\n    ** transition relation; each column corresponds to a variable in\n    ** the manager. A 1 in position (i,j) means that Part i depends\n    ** on Variable j. */\n    matrix = ntrAllocMatrix(nparts,nvars);\n    if (matrix == NULL) return(0);\n\n    /* Allocate array for quantification schedule and initialize it. */\n    schedule = ALLOC(int,nvars);\n    if (schedule == NULL) return(0);\n    for (i = 0; i < nvars; i++) {\n\tschedule[i] = -1;\n    }\n    /* Collect scheduling info for this part. At the end of this loop\n    ** schedule[i] == j means that the variable of index i does not\n    ** appear in any part with index greater than j, unless j == -1,\n    ** in which case the variable appears in no part.\n    */\n    for (i = 0; i < nparts; i++) {\n\tsupport = Cudd_Support(dd,T->part[i]);\n\tif (support == NULL) return(0); Cudd_Ref(support);\n\tscan = support;\n\twhile (!Cudd_IsConstant(scan)) {\n\t    int index = scan->index;\n\t    schedule[index] = i;\n\t    matrix[i][index] = 1;\n\t    scan = Cudd_T(scan);\n\t}\n\tCudd_RecursiveDeref(dd,support);\n    }\n#if 0\n    (void) printf(\"Initial schedule:\");\n    schedcost = 0;\n    for (i = 0; i < nvars; i++) {\n\t(void) printf(\" %d\", schedule[i]);\n\tif (schedule[i] != -1) schedcost += schedule[i];\n    }\n    (void) printf(\"\\nCost = %d\\n\", schedcost);\n#endif\n\n    /* Initialize direct and inverse row permutations to the identity\n    ** permutation. */\n    row = ALLOC(int,nparts);\n    if (row == NULL) return(0);\n    for (i = 0; i < nparts; i++) {\n\tposition[i] = row[i] = i;\n    }\n\n    /* Sift the matrix. */\n    flags = ALLOC(char,nvars);\n    if (flags == NULL) return(0);\n    for (i = 0; i < nparts; i++) {\n\tint cost = 0;\t\t/* cost of moving the row */\n\tint bestcost = 0;\n\tint posn = position[i];\n\tint bestposn = posn;\n\t/* Sift up. */\n\t/* Initialize the flags to one is for the variables that are\n\t** currently scheduled to be quantified after this part gets\n\t** multiplied. When we cross a row of a part that depends on\n\t** a variable whose flag is 1, we know that the row being sifted\n\t** is no longer responsible for that variable. */\n\tfor (k = 0; k < nvars; k++) {\n\t    flags[k] = (char) (schedule[k] == i);\n\t}\n\tfor (j = posn - 1; j >= 0; j--) {\n\t    for (k = 0; k < nvars; k++) {\n\t\tif (schedule[k] == row[j]) {\n\t\t    cost++;\n\t\t} else {\n\t\t    flags[k] &= (matrix[row[j]][k] == 0);\n\t\t    cost -= flags[k];\n\t\t}\n\t    }\n\t    if (cost < bestcost) {\n\t\tbestposn = j;\n\t\tbestcost = cost;\n\t    }\n\t}\n\t/* Sift down. */\n\t/* Reinitialize the flags. (We are implicitly undoing the sift\n\t** down step.) */\n\tfor (k = 0; k < nvars; k++) {\n\t    flags[k] = (char) (schedule[k] == i);\n\t}\n\tfor (j = posn + 1; j < nparts; j++) {\n\t    for (k = 0; k < nvars; k++) {\n\t\tif (schedule[k] == row[j]) {\n\t\t    flags[k] |= (matrix[i][k] == 1);\n\t\t    cost -= flags[k] == 0;\n\t\t} else {\n\t\t    cost += flags[k];\n\t\t}\n\t    }\n\t    if (cost < bestcost) {\n\t\tbestposn = j;\n\t\tbestcost = cost;\n\t    }\n\t}\n\t/* Move to best position. */\n\tif (bestposn < posn) {\n\t    for (j = posn; j >= bestposn; j--) {\n\t\tk = row[j];\n\t\tif (j > 0) row[j] = row[j-1];\n\t\tposition[k]++;\n\t    }\n\t} else {\n\t    for (j = posn; j <= bestposn; j++) {\n\t\tk = row[j];\n\t\tif (j < nparts - 1) row[j] = row[j+1];\n\t\tposition[k]--;\n\t    }\n\t}\n\tposition[i] = bestposn;\n\trow[bestposn] = i;\n\t/* Fix the schedule. */\n\tfor (k = 0; k < nvars; k++) {\n\t    if (matrix[i][k] == 1) {\n\t\tif (position[schedule[k]] < bestposn) {\n\t\t    schedule[k] = i;\n\t\t} else {\n\t\t    for (j = nparts - 1; j >= position[i]; j--) {\n\t\t\tif (matrix[row[j]][k] == 1) break;\n\t\t    }\n\t\t    schedule[k] = row[j];\n\t\t}\n\t    }\n\t}\n    }\n    ntrFreeMatrix(matrix);\n    FREE(flags);\n\n    /* Update schedule to account for the permutation. */\n    for (i = 0; i < nvars; i++) {\n\tif (schedule[i] >= 0) {\n\t    schedule[i] = position[schedule[i]];\n\t}\n    }\n    /* Sort parts. */\n    ntrPermuteParts(T->part,T->nscube,row,position,nparts);\n    FREE(position);\n    FREE(row);\n#if 0\n    (void) printf(\"New schedule:\");\n    schedcost = 0;\n    for (i = 0; i < nvars; i++) {\n\t(void) printf(\" %d\", schedule[i]);\n\tif (schedule[i] != -1) schedcost += schedule[i];\n    }\n    (void) printf(\"\\nCost = %d\\n\", schedcost);\n#endif\n\n    /* Mark the next state varibles so that they do not go in the\n    ** abstraction cubes. */\n    for (i = 0; i < T->nlatches; i++) {\n\tschedule[T->y[i]->index] = -2;\n    }\n\n    /* Rebuild the cubes from the schedule. */\n    for (i = 0; i < nvars; i++) {\n\tk = schedule[i];\n\tvar = Cudd_bddIthVar(dd,i);\n\tif (k >= 0) {\n\t    tmp = Cudd_bddAnd(dd,T->icube[k],var);\n\t    if (tmp == NULL) return(0); Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(dd,T->icube[k]);\n\t    T->icube[k] = tmp;\n\t} else if (k != -2) {\n\t    tmp = Cudd_bddAnd(dd,T->preiabs,var);\n\t    if (tmp == NULL) return(0); Cudd_Ref(tmp);\n\t    Cudd_RecursiveDeref(dd,T->preiabs);\n\t    T->preiabs = tmp;\n\t}\n    }\n    FREE(schedule);\n\n    /* Build the conjuncts. */\n    for (i = 0; i < nparts; i++) {\n\ttmp = Cudd_bddXnor(dd,T->nscube[i],T->part[i]);\n\tif (tmp == NULL) return(0); Cudd_Ref(tmp);\n\tCudd_RecursiveDeref(dd,T->part[i]);\n\tT->part[i] = tmp;\n    }\n\n    return(1);\n\n} /* end of ntrUpdateQuantificationSchedule */\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Used to order the variables according to their signatures.\n\n  @sideeffect None\n\n*/\nstatic int\nntrSignatureCompare(\n  int * ptrX,\n  int * ptrY)\n{\n    if (signatures[*ptrY] > signatures[*ptrX]) return(1);\n    if (signatures[*ptrY] < signatures[*ptrX]) return(-1);\n    return(0);\n\n} /* end of ntrSignatureCompare */\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Used to order the variables according to their signatures.\n\n  @sideeffect None\n\n*/\nstatic int\nntrSignatureCompare2(\n  int * ptrX,\n  int * ptrY)\n{\n    BnetNode *node;\n    int x,y;\n    if (!st_lookup(staticNet->hash,staticNet->latches[*ptrX][1],(void**)&node)) {\n\treturn(0);\n    }\n    x = node->dd->index;\n    if (!st_lookup(staticNet->hash,staticNet->latches[*ptrY][1],(void**)&node)) {\n\treturn(0);\n    }\n    y = node->dd->index;\n    if (signatures[x] < signatures[y]) return(1);\n    if (signatures[x] > signatures[y]) return(-1);\n    return(0);\n\n} /* end of ntrSignatureCompare2 */\n\n\n/**\n  @brief Comparison function used by qsort.\n\n  @details Used to order the parts according to their %BDD addresses.\n\n  @sideeffect None\n\n*/\nstatic int\nntrPartCompare(\n  int * ptrX,\n  int * ptrY)\n{\n    if (staticPart[*ptrY] > staticPart[*ptrX]) return(1);\n    if (staticPart[*ptrY] < staticPart[*ptrX]) return(-1);\n    return(0);\n\n} /* end of ntrPartCompare */\n\n\n/**\n  @brief Allocates a matrix of char's.\n\n  @return a pointer to the matrix if successful; NULL otherwise.\n\n  @sideeffect None\n\n*/\nstatic char **\nntrAllocMatrix(\n  int nrows,\n  int ncols)\n{\n    int i;\n    char **matrix;\n\n    matrix = ALLOC(char *,nrows);\n    if (matrix == NULL) return(NULL);\n    matrix[0] = ALLOC(char,nrows * ncols);\n    if (matrix[0] == NULL) {\n\tFREE(matrix);\n\treturn(NULL);\n    }\n    for (i = 1; i < nrows; i++) {\n\tmatrix[i] = matrix[i-1] + ncols;\n    }\n    for (i = 0; i < nrows * ncols; i++) {\n\tmatrix[0][i] = 0;\n    }\n    return(matrix);\n\n} /* end of ntrAllocMatrix */\n\n\n/**\n  @brief Frees a matrix of char's.\n\n  @sideeffect None\n\n*/\nstatic void\nntrFreeMatrix(\n  char **matrix)\n{\n    FREE(matrix[0]);\n    FREE(matrix);\n    return;\n\n} /* end of ntrFreeMatrix */\n\n\n/**\n  @brief Sorts parts according to given permutation.\n\n  @sideeffect The permutation arrays are turned into the identity\n  permutations.\n\n*/\nstatic void\nntrPermuteParts(\n  DdNode **a,\n  DdNode **b,\n  int *comesFrom,\n  int *goesTo,\n  int size)\n{\n    int i, j;\n    DdNode *tmp;\n\n    for (i = 0; i < size; i++) {\n\tif (comesFrom[i] == i) continue;\n\tj = comesFrom[i];\n\ttmp = a[i]; a[i] = a[j]; a[j] = tmp;\n\ttmp = b[i]; b[i] = b[j]; b[j] = tmp;\n\tcomesFrom[goesTo[i]] = j;\n\tcomesFrom[i] = i;\n\tgoesTo[j] = goesTo[i];\n\tgoesTo[i] = i;\n    }\n    return;\n\n} /* end of ntrPermuteParts */\n\n\n/**\n  @brief Calls Cudd_Ref on its first argument.\n*/\nstatic void\nntrIncreaseRef(\n  void * e,\n  void * arg)\n{\n  DdNode * node = (DdNode *) e;\n  (void) arg; /* avoid warning */\n  Cudd_Ref(node);\n\n} /* end of ntrIncreaseRef */\n\n\n/**\n  @brief Calls Cudd_RecursiveDeref on its first argument.\n*/\nstatic void\nntrDecreaseRef(\n  void * e,\n  void * arg)\n{\n  DdNode * node = (DdNode *) e;\n  DdManager * dd = (DdManager *) arg;\n  Cudd_RecursiveDeref(dd, node);\n\n} /* end of ntrIncreaseRef */\n"
  },
  {
    "path": "cudd/nanotrav/ntr.h",
    "content": "/**\n  @file \n\n  @ingroup nanotrav\n\n  @brief Simple-minded package to do traversal.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef _NTR\n#define _NTR\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n\n#include \"dddmp.h\"\n#include \"bnet.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define PI_PS_FROM_FILE\t0\n#define PI_PS_DFS\t1\n#define PI_PS_GIVEN\t2\n\n#define NTR_IMAGE_MONO 0\n#define NTR_IMAGE_PART 1\n#define NTR_IMAGE_CLIP 2\n#define NTR_IMAGE_DEPEND 3\n\n#define NTR_UNDER_APPROX 0\n#define NTR_OVER_APPROX 1\n\n#define NTR_FROM_NEW 0\n#define NTR_FROM_REACHED 1\n#define NTR_FROM_RESTRICT 2\n#define NTR_FROM_COMPACT 3\n#define NTR_FROM_SQUEEZE 4\n#define NTR_FROM_UNDERAPPROX 5\n#define NTR_FROM_OVERAPPROX 6\n\n#define NTR_GROUP_NONE 0\n#define NTR_GROUP_DEFAULT 1\n#define NTR_GROUP_FIXED 2\n\n#define NTR_SHORT_NONE 0\n#define NTR_SHORT_BELLMAN 1\n#define NTR_SHORT_FLOYD 2\n#define NTR_SHORT_SQUARE 3\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n   @brief Options for nanotrav.\n*/\ntypedef\tstruct\tNtrOptions {\n    long\tinitialTime;\t/**< this is here for convenience */\n    int\t\tverify;\t\t/**< read two networks and compare them */\n    char\t*file1;\t\t/**< first network file name */\n    char\t*file2;\t\t/**< second network file name */\n    int\t\tsecond;\t\t/**< a second network is given */\n    int\t\ttraverse;\t/**< do reachability analysis */\n    int\t\tdepend;\t\t/**< do latch dependence analysis */\n    int\t\timage;\t\t/**< monolithic, partitioned, or clip */\n    double\timageClip;\t/**< clipping depth in image computation */\n    int\t\tapprox;\t\t/**< under or over approximation */\n    int\t\tthreshold;\t/**< approximation threshold */\n    int\t\tfrom;\t\t/**< method to compute from states */\n    int\t\tgroupnsps;\t/**< group present state and next state vars */\n    int\t\tclosure;\t/**< use transitive closure */\n    double\tclosureClip;\t/**< clipping depth in closure computation */\n    int\t\tenvelope;\t/**< compute outer envelope */\n    int\t\tscc;\t\t/**< compute strongly connected components */\n    int\t\tzddtest;\t/**< do zdd test */\n    int\t\tprintcover;\t/**< print ISOP covers when testing ZDDs */\n    int\t\tmaxflow;\t/**< compute maximum flow in network */\n    int\t\tshortPath;\t/**< compute shortest paths in network */\n    int\t\tselectiveTrace;\t/**< use selective trace in shortest paths */\n    char\t*sinkfile;\t/**< file for externally provided sink node */\n    int\t\tpartition;\t/**< test McMillan conjunctive partitioning */\n    int\t\tchar2vect;\t/**< test char-to-vect decomposition */\n    int\t\tdensity;\t/**< test density-related functions */\n    double\tquality;\t/**< quality parameter for density functions */\n    int\t\tdecomp;\t\t/**< test decomposition functions */\n    int\t\tcofest;\t\t/**< test cofactor estimation */\n    double\tclip;\t\t/**< test clipping functions */\n    int\t\tdontcares;\t/**< test equivalence and containment with DCs */\n    int\t\tclosestCube;\t/**< test Cudd_bddClosestCube */\n    int\t\tclauses;\t/**< test extraction of two-literal clauses */\n    int\t\tnoBuild;\t/**< do not build BDDs; just echo order */\n    int\t\tstateOnly;\t/**< ignore primary outputs */\n    char\t*node;\t\t/**< only node for which to build %BDD */\n    int\t\tlocGlob;\t/**< build global or local BDDs */\n    int\t\tprogress;\t/**< report output names while building BDDs */\n    int\t\tcacheSize;\t/**< computed table initial size */\n    size_t\t maxMemory;\t/**< target maximum memory */\n    size_t\t maxMemHard;\t/**< maximum allowed memory */\n    unsigned int maxLive;\t/**< maximum number of nodes */\n    int\t\tslots;\t\t/**< unique subtable initial slots */\n    int\t\tordering;\t/**< FANIN DFS ... */\n    char\t*orderPiPs;\t/**< file for externally provided order */\n    Cudd_ReorderingType\treordering; /**< NONE RANDOM PIVOT SIFTING ... */\n    int\t\tautoDyn;\t/**< ON OFF */\n    Cudd_ReorderingType autoMethod; /**< RANDOM PIVOT SIFTING CONVERGE ... */\n    char\t*treefile;\t/**< file name for variable tree */\n    int\t\tfirstReorder;\t/**< when to do first reordering */\n    int\t\tcountDead;\t/**< count dead nodes toward triggering\n\t\t\t\t     reordering */\n    int\t\tmaxGrowth;\t/**< maximum growth during reordering (%) */\n    Cudd_AggregationType groupcheck; /**< grouping function */\n    int\t\tarcviolation;   /**< percent violation of arcs in\n\t\t\t\t     extended symmetry check */\n    int\t\tsymmviolation;  /**< percent symm violation in\n\t\t\t\t     extended symmetry check */\n    int\t\trecomb;\t\t/**< recombination parameter for grouping */\n    int\t\tnodrop;\t\t/**< don't drop intermediate BDDs ASAP */\n    int\t\tsignatures;\t/**< computation of signatures */\n    int\t\tgaOnOff;\t/**< whether to run GA at the end */\n    int\t\tpopulationSize;\t/**< population size for GA */\n    int\t\tnumberXovers;\t/**< number of crossovers for GA */\n    int\t\tbdddump;\t/**< ON OFF */\n    int\t\tdumpFmt;\t/**< 0 -> dot 1 -> blif 2 ->daVinci 3 -> DDcal\n\t\t\t\t ** 4 -> factored form */\n    char\t*dumpfile;\t/**< filename for dump */\n    int\t\tstore;\t\t/**< iteration at which to store Reached */\n    char\t*storefile;\t/**< filename for storing Reached */\n    int\t\tload;\t\t/**< load initial states from file */\n    char\t*loadfile;\t/**< filename for loading states */\n    int\t\tverb;\t\t/**< level of verbosity */\n    int32_t\tseed;\t\t/**< seed for random number generator */\n} NtrOptions;\n\n/**\n   @brief Type of entry of NtrHeap.\n*/\ntypedef struct NtrHeapSlot NtrHeapSlot;\n\n/**\n   @brief Type of heap-based priority queue.\n*/\ntypedef struct NtrHeap NtrHeap;\n\n/**\n   @brief Data structure for partitioned transition relation.\n*/\ntypedef struct NtrPartTR {\n    int nparts;\t\t\t/**< number of parts */\n    DdNode **part;\t\t/**< array of parts */\n    DdNode **icube;\t\t/**< quantification cubes for image */\n    DdNode **pcube;\t\t/**< quantification cubes for preimage */\n    DdNode **nscube;\t\t/**< next state variables in each part */\n    DdNode *preiabs;\t\t/**< present state vars and inputs in no part */\n    DdNode *prepabs;\t\t/**< inputs in no part */\n    DdNode *xw;\t\t\t/**< cube of all present states and PIs */\n    NtrHeap *factors;\t\t/**< factors extracted from the image */\n    int nlatches;\t\t/**< number of latches */\n    DdNode **x;\t\t\t/**< array of present state variables */\n    DdNode **y;\t\t\t/**< array of next state variables */\n} NtrPartTR;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#ifndef TRUE\n#   define TRUE 1\n#endif\n#ifndef FALSE\n#   define FALSE 0\n#endif\n\n/**\n  @brief Returns 1 if the two arguments are identical strings.\n\n  @sideeffect none\n\n*/\n#define STRING_EQUAL(s1,s2) (strcmp((s1),(s2)) == 0)\n\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\nextern int Ntr_buildDDs (BnetNetwork *net, DdManager *dd, NtrOptions *option, BnetNetwork *net2);\nextern NtrPartTR * Ntr_buildTR (DdManager *dd, BnetNetwork *net, NtrOptions *option, int image);\nextern DdNode * Ntr_TransitiveClosure (DdManager *dd, NtrPartTR *TR, NtrOptions *option);\nextern int Ntr_Trav (DdManager *dd, BnetNetwork *net, NtrOptions *option);\nextern int Ntr_SCC (DdManager *dd, BnetNetwork *net, NtrOptions *option);\nextern int Ntr_ClosureTrav (DdManager *dd, BnetNetwork *net, NtrOptions *option);\nextern void Ntr_freeTR (DdManager *dd, NtrPartTR *TR);\nextern NtrPartTR * Ntr_cloneTR (NtrPartTR *TR);\nextern DdNode * Ntr_initState (DdManager *dd, BnetNetwork *net, NtrOptions *option);\nextern DdNode * Ntr_getStateCube (DdManager *dd, BnetNetwork *net, char *filename, int pr);\nextern int Ntr_Envelope (DdManager *dd, NtrPartTR *TR, FILE *dfp, NtrOptions *option);\nextern int Ntr_TestMinimization (DdManager *dd, BnetNetwork *net1, BnetNetwork *net2, NtrOptions *option);\nextern int Ntr_TestDensity (DdManager *dd, BnetNetwork *net1, NtrOptions *option);\nextern int Ntr_TestDecomp (DdManager *dd, BnetNetwork *net1, NtrOptions *option);\nextern int Ntr_VerifyEquivalence (DdManager *dd, BnetNetwork *net1, BnetNetwork *net2, NtrOptions *option);\nextern int Ntr_TestCofactorEstimate (DdManager * dd, BnetNetwork * net, NtrOptions * option);\nextern int Ntr_TestClipping (DdManager *dd, BnetNetwork *net1, BnetNetwork *net2, NtrOptions *option);\nextern int Ntr_TestEquivAndContain (DdManager *dd, BnetNetwork *net1, BnetNetwork *net2, NtrOptions *option);\nextern int Ntr_TestClosestCube (DdManager * dd, BnetNetwork * net, NtrOptions * option);\nextern int Ntr_TestTwoLiteralClauses (DdManager * dd, BnetNetwork * net1, NtrOptions * option);\nextern int Ntr_TestCharToVect(DdManager * dd, BnetNetwork * net1, NtrOptions * option);\nextern int Ntr_maxflow (DdManager *dd, BnetNetwork *net, NtrOptions *option);\nextern double Ntr_maximum01Flow (DdManager *bdd, DdNode *sx, DdNode *ty, DdNode *E, DdNode **F, DdNode **cut, DdNode **x, DdNode **y, DdNode **z, int n, int pr);\nextern int Ntr_testZDD (DdManager *dd, BnetNetwork *net, NtrOptions *option);\nextern int Ntr_testISOP (DdManager *dd, BnetNetwork *net, NtrOptions *option);\nextern NtrHeap * Ntr_InitHeap (int size);\nextern void Ntr_FreeHeap (NtrHeap *heap);\nextern int Ntr_HeapInsert (NtrHeap *heap, void *item, int key);\nextern int Ntr_HeapExtractMin (NtrHeap *heap, void *item, int *key);\nextern int Ntr_HeapCount (NtrHeap *heap);\nextern NtrHeap * Ntr_HeapClone (NtrHeap *source);\nextern void Ntr_HeapForeach (NtrHeap *heap, void (*f)(void *e, void *arg), void *arg);\nextern int Ntr_TestHeap (NtrHeap *heap, int i);\nextern int Ntr_ShortestPaths (DdManager *dd, BnetNetwork *net, NtrOptions *option);\n\n/** \\endcond */\n\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* _NTR */\n"
  },
  {
    "path": "cudd/nanotrav/ntrBddTest.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief %BDD test functions for the nanotrav program.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"ntr.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int ntrTestMinimizationAux (DdManager *dd, BnetNetwork *net1, DdNode *f, char *name, DdNode *c, char *cname, NtrOptions *option);\nstatic int ntrTestDensityAux (DdManager *dd, BnetNetwork *net, DdNode *f, char *name, NtrOptions *option);\nstatic int ntrTestDecompAux (DdManager *dd, BnetNetwork *net, DdNode *f, char *name, NtrOptions *option);\nstatic int ntrTestCofEstAux (DdManager * dd, BnetNetwork * net, DdNode * f, char * name, NtrOptions * option);\nstatic int ntrTestClippingAux (DdManager *dd, BnetNetwork *net1, DdNode *f, char *name, DdNode *g, char *gname, NtrOptions *option);\nstatic int ntrTestEquivAndContainAux (DdManager *dd, BnetNetwork *net1, DdNode *f, char *fname, DdNode *g, char *gname, DdNode *d, char *dname, NtrOptions *option);\nstatic int ntrTestClosestCubeAux (DdManager *dd, BnetNetwork *net, DdNode *f, char *fname, DdNode *g, char *gname, DdNode **vars, NtrOptions *option);\nstatic int ntrTestCharToVect(DdManager * dd, DdNode * f, NtrOptions *option);\n#if 0\nstatic DdNode * ntrCompress1 (DdManager *dd, DdNode *f, int nvars, int threshold);\n#endif\nstatic DdNode * ntrCompress2 (DdManager *dd, DdNode *f, int nvars, int threshold);\nstatic BnetNode * ntrNodeIsBuffer (BnetNode *nd, st_table *hash);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Tests %BDD minimization functions.\n\n  @details Tests %BDD minimization functions, including\n  leaf-identifying compaction, squeezing, and restrict. This function\n  uses as constraint the first output of net2 and computes positive\n  and negative cofactors of all the outputs of net1. For each\n  cofactor, it checks whether compaction was safe (cofactor not larger\n  than original function) and that the expansion based on each\n  minimization function (used as a generalized cofactor) equals the\n  original function.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestMinimization(\n  DdManager * dd,\n  BnetNetwork * net1,\n  BnetNetwork * net2,\n  NtrOptions * option)\n{\n    DdNode *f;\n    DdNode *c = NULL;\n    char *cname = NULL;\n    BnetNode *node;\n    int i;\n    int result;\n    int nsize, csize;\n\n    if (option->second == FALSE) return(1);\n\n    (void) printf(\"Testing BDD minimization algorithms\\n\");\n    /* Use largest output of second network as constraint. */\n    csize = -1;\n    for (i = 0; i < net2->noutputs; i++) {\n\tif (!st_lookup(net2->hash,net2->outputs[i],(void **)&node)) {\n\t    return(0);\n\t}\n\tnsize = Cudd_DagSize(node->dd);\n\tif (nsize > csize) {\n\t    c = node->dd;\n\t    cname = node->name;\n\t    csize = nsize;\n\t}\n    }\n    if (c == NULL || cname == NULL) return(0);\n    (void) printf(\"TEST-MINI: Constrain (%s) %d nodes\\n\",\n\t\t  cname, Cudd_DagSize(c));\n\n    if (option->node == NULL) {\n\tfor (i = 0; i < net1->noutputs; i++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    f = node->dd;\n\t    if (f == NULL) return(0);\n\t    result = ntrTestMinimizationAux(dd,net1,f,node->name,c,cname,\n\t\t\t\t\t    option);\n\t    if (result == 0) return(0);\n\t}\n    } else {\n\tif (!st_lookup(net1->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tf = node->dd;\n\tif (f == NULL) return(0);\n\tresult = ntrTestMinimizationAux(dd,net1,f,option->node,c,cname,option);\n\tif (result == 0) return(0);\n    }\n\n    return(1);\n\n} /* end of Ntr_TestMinimization */\n\n\n/**\n  @brief Tests %BDD density-related functions.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestDensity(\n  DdManager * dd,\n  BnetNetwork * net1,\n  NtrOptions * option)\n{\n    DdNode *f;\n    BnetNode *node;\n    int i;\n    int result;\n\n    if (option->density == FALSE) return(1);\n\n    (void) printf(\"Testing BDD density-related algorithms\\n\");\n    if (option->node == NULL) {\n\tfor (i = 0; i < net1->noutputs; i++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    f = node->dd;\n\t    if (f == NULL) return(0);\n\t    result = ntrTestDensityAux(dd,net1,f,node->name,option);\n\t    if (result == 0) return(0);\n\t}\n    } else {\n\tif (!st_lookup(net1->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tf = node->dd;\n\tif (f == NULL) return(0);\n\tresult = ntrTestDensityAux(dd,net1,f,option->node,option);\n\tif (result == 0) return(0);\n    }\n\n    return(1);\n\n} /* end of Ntr_TestDensity */\n\n\n/**\n  @brief Tests %BDD decomposition functions.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestDecomp(\n  DdManager * dd,\n  BnetNetwork * net1,\n  NtrOptions * option)\n{\n    DdNode *f;\n    BnetNode *node;\n    int i;\n    int result;\n\n    if (option->decomp == FALSE) return(1);\n\n    (void) printf(\"Testing BDD decomposition algorithms\\n\");\n    if (option->node == NULL) {\n\tfor (i = 0; i < net1->noutputs; i++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    f = node->dd;\n\t    if (f == NULL) return(0);\n\t    result = ntrTestDecompAux(dd,net1,f,node->name,option);\n\t    if (result == 0) return(0);\n\t}\n    } else {\n\tif (!st_lookup(net1->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tf = node->dd;\n\tif (f == NULL) return(0);\n\tresult = ntrTestDecompAux(dd,net1,f,option->node,option);\n\tif (result == 0) return(0);\n    }\n\n    return(1);\n\n} /* end of ntrTestDecomp */\n\n\n/**\n  @brief Verify equivalence of combinational networks.\n\n  @details The two networks are supposed to have the same names for\n  inputs and outputs. The only exception is that the second network\n  may miss output buffers that are present in the first network. This\n  function tries to match both the output and the input of the buffer.\n\n  @return 1 if successful and if the networks are equivalent; -1 if\n  successful, but the networks are not equivalent; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_VerifyEquivalence(\n  DdManager * dd,\n  BnetNetwork * net1,\n  BnetNetwork * net2,\n  NtrOptions * option)\n{\n    BnetNode *node;\n    char *oname;\n    DdNode *odd1, *odd2;\n    int i;\n    int pr;\n\n    (void) printf(\"Testing equivalence\\n\");\n    if (net2->noutputs != net1->noutputs) {\n\t(void) printf(\"The two networks have different number of outputs\\n\");\n\t(void) printf(\"  %s has %d outputs\\n  %s has %d outputs\\n\",\n\t\t      net1->name, net1->noutputs, net2->name, net2->noutputs);\n\treturn(-1);\n    }\n    if (net2->nlatches != net1->nlatches) {\n\t(void) printf(\"The two networks have different number of latches\\n\");\n\t(void) printf(\"  %s has %d latches\\n  %s has %d latches\\n\",\n\t\t      net1->name, net1->nlatches, net2->name, net2->nlatches);\n\treturn(-1);\n    }\n\n    pr = option->verb;\n    for (i = 0; i < net1->noutputs; i++) {\n\toname = net1->outputs[i];\n\tif (!st_lookup(net1->hash,oname,(void **)&node)) {\n\t    return(0);\n\t}\n\todd1 = node->dd;\n\t(void) printf(\"%s\", oname);\n\tCudd_PrintDebug(dd, node->dd, Cudd_ReadSize(dd), pr);\n\tif (!st_lookup(net2->hash,oname,(void **)&node)) {\n\t    BnetNode *inpnd;\n\t    if ((inpnd = ntrNodeIsBuffer(node,net1->hash)) == NULL ||\n\t\t!st_lookup(net2->hash,inpnd->name,(void **)&node)) {\n\t\t(void) printf(\"Output %s missing from network %s\\n\",\n\t\t\t      oname, net2->name);\n\t\treturn(-1);\n\t    } else {\n\t\todd2 = inpnd->dd;\n\t    }\n\t} else {\n\t    odd2 = node->dd;\n\t}\n\tif (odd1 != odd2) {\n\t    (void) printf(\"Output %s is not equivalent\\n\", oname);\n\t    return(-1);\n\t}\n    }\n    return(1);\n\n} /* end of Ntr_VerifyEquivalence */\n\n\n/**\n  @brief Tests %BDD cofactor estimate functions.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestCofactorEstimate(\n  DdManager * dd,\n  BnetNetwork * net,\n  NtrOptions * option)\n{\n    DdNode *f;\n    BnetNode *node;\n    int i;\n    int result;\n\n    if (option->cofest == FALSE) return(1);\n\n    (void) printf(\"Testing BDD cofactor estimation algorithms\\n\");\n    if (option->node == NULL) {\n\tfor (i = 0; i < net->noutputs; i++) {\n\t    if (!st_lookup(net->hash,net->outputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    f = node->dd;\n\t    if (f == NULL) return(0);\n\t    result = ntrTestCofEstAux(dd,net,f,node->name,option);\n\t    if (result == 0) return(0);\n\t}\n    } else {\n\tif (!st_lookup(net->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tf = node->dd;\n\tif (f == NULL) return(0);\n\tresult = ntrTestCofEstAux(dd,net,f,option->node,option);\n\tif (result == 0) return(0);\n    }\n\n    return(1);\n\n} /* end of Ntr_TestCofactorEstimate */\n\n\n/**\n  @brief Tests %BDD clipping functions.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestClipping(\n  DdManager * dd,\n  BnetNetwork * net1,\n  BnetNetwork * net2,\n  NtrOptions * option)\n{\n    DdNode *f;\n    DdNode *g = NULL;\n    char *gname = NULL;\n    BnetNode *node;\n    int i;\n    int result;\n    int nsize, gsize;\n\n    if (option->clip < 0.0) return(1);\n\n    (void) printf(\"Testing BDD clipping algorithms\\n\");\n    /* Use largest output of second network as second operand. */\n    gsize = -1;\n    for (i = 0; i < net2->noutputs; i++) {\n\tif (!st_lookup(net2->hash,net2->outputs[i],(void **)&node)) {\n\t    return(0);\n\t}\n\tnsize = Cudd_DagSize(node->dd);\n\tif (nsize > gsize) {\n\t    g = node->dd;\n\t    gname = node->name;\n\t    gsize = nsize;\n\t}\n    }\n    if (g == NULL || gname == NULL) return(0);\n    (void) printf(\"TEST-CLIP: Second operand (%s) %d nodes\\n\",\n\t\t  gname, Cudd_DagSize(g));\n\n    if (option->node == NULL) {\n\tfor (i = 0; i < net1->noutputs; i++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    f = node->dd;\n\t    if (f == NULL) return(0);\n\t    result = ntrTestClippingAux(dd,net1,f,node->name,g,gname,option);\n\t    if (result == 0) return(0);\n\t}\n    } else {\n\tif (!st_lookup(net1->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tf = node->dd;\n\tif (f == NULL) return(0);\n\tresult = ntrTestClippingAux(dd,net1,f,option->node,g,gname,option);\n\tif (result == 0) return(0);\n    }\n\n    return(1);\n\n} /* end of Ntr_TestClipping */\n\n\n/**\n  @brief Tests %BDD equivalence and containment with don't cares.\n\n  @details Tests functions for %BDD equivalence and containment\n  with don't cares, including Cudd_EquivDC and Cudd_bddLeqUnless. This\n  function uses as care set the first output of net2 and checkes\n  equivalence and containment for of all the output pairs of net1.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestEquivAndContain(\n  DdManager *dd,\n  BnetNetwork *net1,\n  BnetNetwork *net2,\n  NtrOptions *option)\n{\n    DdNode *f, *g;\n    DdNode *d = NULL;\n    char *dname = NULL;\n    BnetNode *node1, *node2;\n    int i, j;\n    int result;\n    int nsize, dsize;\n\n    if (option->dontcares == FALSE) return(1);\n\n    (void) printf(\"Testing BDD equivalence and containment algorithms\\n\");\n    /* Use largest output of second network as constraint. */\n    dsize = -1;\n    for (i = 0; i < net2->noutputs; i++) {\n\tif (!st_lookup(net2->hash,net2->outputs[i],(void **)&node1)) {\n\t    return(0);\n\t}\n\tnsize = Cudd_DagSize(node1->dd);\n\tif (nsize > dsize) {\n\t    d = node1->dd;\n\t    dname = node1->name;\n\t    dsize = nsize;\n\t}\n    }\n    if (d == NULL || dname == NULL) return(0);\n    (void) printf(\"TEST-DC: Don't care set (%s) %d nodes\\n\",\n\t\t  dname, Cudd_DagSize(d));\n\n    if (option->node == NULL) {\n\tfor (i = 0; i < net1->noutputs; i++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[i],(void **)&node1)) {\n\t\treturn(0);\n\t    }\n\t    f = node1->dd;\n\t    if (f == NULL) return(0);\n\t    for (j = 0; j < net1->noutputs; j++) {\n\t\tif (!st_lookup(net1->hash,net1->outputs[j],(void **)&node2)) {\n\t\t    return(0);\n\t\t}\n\t\tg = node2->dd;\n\t\tif (g == NULL) return(0);\n\t\tresult = ntrTestEquivAndContainAux(dd,net1,f,node1->name,g,\n\t\t\t\t\t\t   node2->name,d,dname,option);\n\t\tif (result == 0) return(0);\n\t    }\n\t}\n    } else {\n\tif (!st_lookup(net1->hash,option->node,(void **)&node1)) {\n\t    return(0);\n\t}\n\tf = node1->dd;\n\tif (f == NULL) return(0);\n\tfor (j = 0; j < net1->noutputs; j++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[j],(void **)&node2)) {\n\t\treturn(0);\n\t    }\n\t    g = node2->dd;\n\t    if (g == NULL) return(0);\n\t    result = ntrTestEquivAndContainAux(dd,net1,f,option->node,\n\t\t\t\t\t       g,node2->name,d,dname,option);\n\t    if (result == 0) return(0);\n\t}\n    }\n\n    return(1);\n\n} /* end of Ntr_TestEquivAndContain */\n\n\n/**\n  @brief Tests the Cudd_bddClosestCube function.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestClosestCube(\n  DdManager * dd,\n  BnetNetwork * net,\n  NtrOptions * option)\n{\n    DdNode *f, *g;\n    BnetNode *node1, *node2;\n    int i, j, nvars;\n    int result;\n    DdNode **vars;\n    double calls;\n\n    if (option->closestCube == FALSE) return(1);\n\n    (void) printf(\"Testing Cudd_bddClosestCube\\n\");\n    nvars = Cudd_ReadSize(dd);\n    vars = ALLOC(DdNode *, nvars);\n    if (vars == NULL) return(0);\n    for (i = 0; i < nvars; i++) {\n\tvars[i] = Cudd_bddIthVar(dd,i);\n    }\n    calls = Cudd_ReadRecursiveCalls(dd);\n    if (option->node == NULL) {\n\tfor (i = 0; i < net->noutputs; i++) {\n\t    if (!st_lookup(net->hash,net->outputs[i],(void **)&node1)) {\n\t\tFREE(vars);\n\t\treturn(0);\n\t    }\n\t    f = node1->dd;\n\t    if (f == NULL) {\n\t\tFREE(vars);\n\t\treturn(0);\n\t    }\n\t    for (j = 0; j < net->noutputs; j++) {\n\t\tif (!st_lookup(net->hash,net->outputs[j],(void **)&node2)) {\n\t\t    FREE(vars);\n\t\t    return(0);\n\t\t}\n\t\tg = node2->dd;\n\t\tif (g == NULL) {\n\t\t    FREE(vars);\n\t\t    return(0);\n\t\t}\n\t\tresult = ntrTestClosestCubeAux(dd,net,f,node1->name,g,\n\t\t\t\t\t       node2->name,vars,option);\n\t\tif (result == 0) {\n\t\t    FREE(vars);\n\t\t    return(0);\n\t\t}\n\t    }\n\t}\n    } else {\n\tif (!st_lookup(net->hash,option->node,(void **)&node1)) {\n\t    FREE(vars);\n\t    return(0);\n\t}\n\tf = node1->dd;\n\tif (f == NULL) {\n\t    FREE(vars);\n\t    return(0);\n\t}\n\tfor (j = 0; j < net->noutputs; j++) {\n\t    if (!st_lookup(net->hash,net->outputs[j],(void **)&node2)) {\n\t\tFREE(vars);\n\t\treturn(0);\n\t    }\n\t    g = node2->dd;\n\t    if (g == NULL) {\n\t\tFREE(vars);\n\t\treturn(0);\n\t    }\n\t    result = ntrTestClosestCubeAux(dd,net,f,option->node,g,\n\t\t\t\t\t   node2->name,vars,option);\n\t    if (result == 0) {\n\t\tFREE(vars);\n\t\treturn(0);\n\t    }\n\t}\n    }\n    (void) printf(\"End of test.  Performed %.0f recursive calls.\\n\",\n\t\t  Cudd_ReadRecursiveCalls(dd) - calls);\n    FREE(vars);\n    return(1);\n\n} /* end of Ntr_TestClosestCube */\n\n\n/**\n  @brief Tests extraction of two-literal clauses.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestTwoLiteralClauses(\n  DdManager * dd,\n  BnetNetwork * net1,\n  NtrOptions * option)\n{\n    DdNode *f;\n    BnetNode *node;\n    int result;\n    char **inames = NULL;\n    int i;\n\n    if (option->clauses == FALSE) return(1);\n\n    /* Initialize data structures. */\n    inames = ALLOC(char *,Cudd_ReadSize(dd));\n    if (inames == NULL) return(0);\n    for (i = 0; i < Cudd_ReadSize(dd); i++) {\n\tinames[i] = NULL;\n    }\n\n    /* Find the input names. */\n    for (i = 0; i < net1->ninputs; i++) {\n\tif (!st_lookup(net1->hash,net1->inputs[i],(void **)&node)) {\n\t    FREE(inames);\n\t    return(0);\n\t}\n\tinames[node->var] = net1->inputs[i];\n    }\n    for (i = 0; i < net1->nlatches; i++) {\n\tif (!st_lookup(net1->hash,net1->latches[i][1],(void **)&node)) {\n\t    FREE(inames);\n\t    return(0);\n\t}\n\tinames[node->var] = net1->latches[i][1];\n    }\n\n    (void) printf(\"Testing extraction of two literal clauses\\n\");\n    if (option->node == NULL) {\n\tfor (i = 0; i < net1->noutputs; i++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    f = node->dd;\n\t    if (f == NULL) {\n\t\tFREE(inames);\n\t\treturn(0);\n\t    }\n\t    (void) printf(\"*** %s ***\\n\", net1->outputs[i]);\n\t    result = Cudd_PrintTwoLiteralClauses(dd, f, inames, NULL);\n\t    if (result == 0) {\n\t\tFREE(inames);\n\t\treturn(0);\n\t    }\n\t}\n    } else {\n\tif (!st_lookup(net1->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tf = node->dd;\n\tif (f == NULL) {\n\t    FREE(inames);\n\t    return(0);\n\t}\n\t(void) printf(\"*** %s ***\\n\", option->node);\n\tresult = Cudd_PrintTwoLiteralClauses(dd, f, inames, NULL);\n\tif (result == 0) {\n\t    FREE(inames);\n\t    return(0);\n\t}\n    }\n\n    FREE(inames);\n    return(1);\n\n} /* end of Ntr_TestTwoLiteralClauses */\n\n\n/**\n  @brief Test char-to-vect conversion.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestCharToVect(\n  DdManager * dd,\n  BnetNetwork * net1,\n  NtrOptions * option)\n{\n    DdNode *f;\n    int result;\n    BnetNode *node;\n    int i;\n\n    if (option->char2vect == FALSE) return(1);\n\n    (void) printf(\"Testing char-to-vect\\n\");\n    if (net1->nlatches > 0) {\n\tNtrPartTR *T;\n\tT = Ntr_buildTR(dd,net1,option,NTR_IMAGE_MONO);\n\tresult = ntrTestCharToVect(dd,T->part[0],option);\n\tNtr_freeTR(dd,T);\n    } else if (option->node == NULL) {\n\tresult = 1;\n\tfor (i = 0; i < net1->noutputs; i++) {\n\t    if (!st_lookup(net1->hash,net1->outputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    f = node->dd;\n\t    if (f == NULL) return(0);\n\t    (void) printf(\"*** %s ***\\n\", net1->outputs[i]);\n\t    result = ntrTestCharToVect(dd,f,option);\n\t    if (result == 0) return(0);\n\t}\n    } else {\n\tif (!st_lookup(net1->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tf = node->dd;\n\tif (f == NULL) return(0);\n\tresult = ntrTestCharToVect(dd,f,option);\n    }\n    return(result);\n\n} /* end of Ntr_TestCharToVect */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Processes one %BDD for Ntr_TestMinimization.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_TestMinimization\n\n*/\nstatic int\nntrTestMinimizationAux(\n  DdManager * dd,\n  BnetNetwork * net1,\n  DdNode * f,\n  char * name,\n  DdNode * c,\n  char * cname,\n  NtrOptions * option)\n{\n    DdNode *com1, *com0, *min1, *min0, *sq1, *sq0;\n    DdNode *rs1, *rs0, *cs1, *cs0, *na1, *na0, *a1, *a0;\n    DdNode *g, *u1, *l1, *u0, *l0;\n    int pr, nvars;\n    int sizeF, sizeMin1, sizeMin0, sizeSq1, sizeSq0, sizeCom1, sizeCom0;\n    int sizeRs1, sizeRs0, sizeCs1, sizeCs0, sizeNa1, sizeNa0, sizeA1, sizeA0;\n    static char *onames[11];\n    DdNode *outputs[11];\n    DdNode *fc[2];\n\n    pr = option->verb;\n    fc[0] = f; fc[1] = c;\n    nvars = Cudd_VectorSupportSize(dd,fc,2);\n    if (nvars == CUDD_OUT_OF_MEM) return(0);\n    (void) printf(\"TEST-MINI:: %s\\n\", name);\n    (void) printf(\"T-M    \");\n    Cudd_PrintDebug(dd, f, nvars, pr);\n    sizeF = Cudd_DagSize(f);\n\n    /* Compute positive generalized cofactor. */\n    com1 = Cudd_bddLICompaction(dd, f, c);\n    if (com1 == NULL) {\n\t(void) printf(\"TEST-MINI: LI-compaction failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(com1);\n    (void) printf(\"T-M L1 \");\n    Cudd_PrintDebug(dd, com1, nvars, pr);\n    sizeCom1 = Cudd_DagSize(com1);\n    if (sizeCom1 > sizeF) {\n\t(void) printf(\"TEST-MINI: LI-compaction not safe (1).\\n\");\n\treturn(0);\n    }\n    min1 = Cudd_bddMinimize(dd, f, c);\n    if (min1 == NULL) {\n\t(void) printf(\"TEST-MINI: minimize failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(min1);\n    (void) printf(\"T-M M1 \");\n    Cudd_PrintDebug(dd, min1, nvars, pr);\n    sizeMin1 = Cudd_DagSize(min1);\n    if (sizeMin1 > sizeF) {\n\t(void) printf(\"TEST-MINI: minimize not safe (1).\\n\");\n\treturn(0);\n    }\n    rs1 = Cudd_bddRestrict(dd, f, c);\n    if (rs1 == NULL) {\n\t(void) printf(\"TEST-MINI: restrict failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(rs1);\n    (void) printf(\"T-M R1 \");\n    Cudd_PrintDebug(dd, rs1, nvars, pr);\n    sizeRs1 = Cudd_DagSize(rs1);\n    cs1 = Cudd_bddConstrain(dd, f, c);\n    if (cs1 == NULL) {\n\t(void) printf(\"TEST-MINI: constrain failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(cs1);\n    (void) printf(\"T-M C1 \");\n    Cudd_PrintDebug(dd, cs1, nvars, pr);\n    sizeCs1 = Cudd_DagSize(cs1);\n    l1 = Cudd_bddAnd(dd, f, c);\n    if (l1 == NULL) {\n\t(void) printf(\"TEST-MINI: lower bound failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(l1);\n    u1 = Cudd_bddOr(dd, f, Cudd_Not(c));\n    if (u1 == NULL) {\n\t(void) printf(\"TEST-MINI: upper bound failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(u1);\n    (void) printf(\"TEST-MINI: (lb,ub) : (%d,%d) nodes\\n\",\n\t\t  Cudd_DagSize(l1), Cudd_DagSize(u1));\n    sq1 = Cudd_bddSqueeze(dd, l1, u1);\n    if (sq1 == NULL) {\n\t(void) printf(\"TEST-MINI: squeezing failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(sq1);\n    sizeSq1 = Cudd_DagSize(sq1);\n    if (sizeSq1 > sizeF) {\n\tCudd_RecursiveDeref(dd,sq1);\n\tsq1 = f;\n\tCudd_Ref(sq1);\n\tsizeSq1 = sizeF;\n    }\n    (void) printf(\"T-M S1 \");\n    Cudd_PrintDebug(dd, sq1, nvars, pr);\n    na1 = Cudd_bddNPAnd(dd, f, c);\n    if (na1 == NULL) {\n\t(void) printf(\"TEST-MINI: NPand failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(na1);\n    (void) printf(\"T-M N1 \");\n    Cudd_PrintDebug(dd, na1, nvars, pr);\n    sizeNa1 = Cudd_DagSize(na1);\n    a1 = Cudd_bddAnd(dd, f, c);\n    if (a1 == NULL) {\n\t(void) printf(\"TEST-MINI: and failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(a1);\n    (void) printf(\"T-M A1 \");\n    Cudd_PrintDebug(dd, a1, nvars, pr);\n    sizeA1 = Cudd_DagSize(a1);\n    (void) printf(\"TEST-MINI: f %d comp %d mini %d rest %d cons %d sque %d na %d and %d\\n\",\n\t\t  sizeF, sizeCom1, sizeMin1, sizeRs1, sizeCs1, sizeSq1, sizeNa1, sizeA1);\n    if (option->bdddump) {\n\tonames[0] = name;\t\toutputs[0] = f;\n\tonames[1] = cname;\t\toutputs[1] = c;\n\tonames[2] = (char *) \"cons\";\toutputs[2] = cs1;\n\tonames[3] = (char *) \"rest\";\toutputs[3] = rs1;\n\tonames[4] = (char *) \"comp\";\toutputs[4] = com1;\n\tonames[5] = (char *) \"mini\";\toutputs[5] = min1;\n\tonames[6] = (char *) \"sqee\";\toutputs[6] = sq1;\n\tonames[7] = (char *) \"lb\";\toutputs[7] = l1;\n\tonames[8] = (char *) \"ub\";\toutputs[8] = u1;\n\tonames[9] = (char *) \"na\";\toutputs[9] = na1;\n\tonames[10] = (char *) \"and\";\toutputs[10] = a1;\n\tif (!Bnet_bddArrayDump(dd, net1, option->dumpfile, outputs, onames,\n\t\t\t       11, option->dumpFmt))\n\t    return(0);\n    }\n    Cudd_RecursiveDeref(dd,l1);\n    Cudd_RecursiveDeref(dd,u1);\n\n    /* Compute negative generalized cofactor. */\n    (void) printf(\"TEST-MINI:: %s\\n\", name);\n    (void) printf(\"T-M    \");\n    Cudd_PrintDebug(dd, f, nvars, pr);\n\n    com0 = Cudd_bddLICompaction(dd, f, Cudd_Not(c));\n    if (com0 == NULL) {\n\t(void) printf(\"TEST-MINI: LI-compaction failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(com0);\n    (void) printf(\"T-M L0 \");\n    Cudd_PrintDebug(dd, com0, nvars, pr);\n    sizeCom0 = Cudd_DagSize(com0);\n    if (sizeCom0 > sizeF) {\n\t(void) printf(\"TEST-MINI: LI-compaction not safe (2).\\n\");\n\treturn(0);\n    }\n    min0 = Cudd_bddMinimize(dd, f, Cudd_Not(c));\n    if (min0 == NULL) {\n\t(void) printf(\"TEST-MINI: minimize failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(min0);\n    (void) printf(\"T-M M0 \");\n    Cudd_PrintDebug(dd, min0, nvars, pr);\n    sizeMin0 = Cudd_DagSize(min0);\n    if (sizeMin0 > sizeF) {\n\t(void) printf(\"TEST-MINI: minimize not safe (2).\\n\");\n\treturn(0);\n    }\n    rs0 = Cudd_bddRestrict(dd, f, Cudd_Not(c));\n    if (rs0 == NULL) {\n\t(void) printf(\"TEST-MINI: restrict failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(rs0);\n    (void) printf(\"T-M R0 \");\n    Cudd_PrintDebug(dd, rs0, nvars, pr);\n    sizeRs0 = Cudd_DagSize(rs0);\n    cs0 = Cudd_bddConstrain(dd, f, Cudd_Not(c));\n    if (cs0 == NULL) {\n\t(void) printf(\"TEST-MINI: constrain failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(cs0);\n    (void) printf(\"T-M C0 \");\n    Cudd_PrintDebug(dd, cs0, nvars, pr);\n    sizeCs0 = Cudd_DagSize(cs0);\n\n    l0 = Cudd_bddAnd(dd, f, Cudd_Not(c));\n    if (l0 == NULL) {\n\t(void) printf(\"TEST-MINI: lower bound failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(l0);\n    u0 = Cudd_bddOr(dd, f, c);\n    if (u0 == NULL) {\n\t(void) printf(\"TEST-MINI: upper bound failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(u0);\n    (void) printf(\"TEST-MINI: (lb,ub) : (%d,%d) nodes\\n\",\n\t\t  Cudd_DagSize(l0), Cudd_DagSize(u0));\n    sq0 = Cudd_bddSqueeze(dd, l0, u0);\n    if (sq0 == NULL) {\n\t(void) printf(\"TEST-MINI: squeezing failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(sq0);\n    Cudd_RecursiveDeref(dd,l0);\n    Cudd_RecursiveDeref(dd,u0);\n    sizeSq0 = Cudd_DagSize(sq0);\n    if (sizeSq0 > sizeF) {\n\tCudd_RecursiveDeref(dd,sq0);\n\tsq0 = f;\n\tCudd_Ref(sq0);\n\tsizeSq0 = sizeF;\n    }\n    (void) printf(\"T-M S0 \");\n    Cudd_PrintDebug(dd, sq0, nvars, pr);\n    na0 = Cudd_bddNPAnd(dd, f, Cudd_Not(c));\n    if (na0 == NULL) {\n\t(void) printf(\"TEST-MINI: NPand failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(na0);\n    (void) printf(\"T-M N0 \");\n    Cudd_PrintDebug(dd, na0, nvars, pr);\n    sizeNa0 = Cudd_DagSize(na0);\n    a0 = Cudd_bddAnd(dd, f, Cudd_Not(c));\n    if (a0 == NULL) {\n\t(void) printf(\"TEST-MINI: and failed (2).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(a0);\n    (void) printf(\"T-M A0 \");\n    Cudd_PrintDebug(dd, a0, nvars, pr);\n    sizeA0 = Cudd_DagSize(a0);\n    (void) printf(\"TEST-MINI: f %d comp %d mini %d rest %d cons %d sque %d na %d, and %d\\n\",\n\t\t  sizeF, sizeCom0, sizeMin0, sizeRs0, sizeCs0, sizeSq0, sizeNa0, sizeA0);\n\n    /* Check fundamental identity. */\n    g = Cudd_bddIte(dd,c,com1,com0);\n    if (g == NULL) {\n\t(void) printf(\"TEST-MINI: LI-compaction failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(g);\n    if (g != f) {\n\t(void) printf(\"TEST-MINI: LI-compaction failed (4).\\n\");\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,com1);\n    Cudd_RecursiveDeref(dd,com0);\n    Cudd_RecursiveDeref(dd,g);\n    g = Cudd_bddIte(dd,c,min1,min0);\n    if (g == NULL) {\n\t(void) printf(\"TEST-MINI: minimize failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(g);\n    if (g != f) {\n\t(void) printf(\"TEST-MINI: minimize failed (4).\\n\");\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,min1);\n    Cudd_RecursiveDeref(dd,min0);\n    Cudd_RecursiveDeref(dd,g);\n    g = Cudd_bddIte(dd,c,sq1,sq0);\n    if (g == NULL) {\n\t(void) printf(\"TEST-MINI: squeezing failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(g);\n    if (g != f) {\n\t(void) printf(\"TEST-MINI: squeezing failed (4).\\n\");\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,sq1);\n    Cudd_RecursiveDeref(dd,sq0);\n    Cudd_RecursiveDeref(dd,g);\n    g = Cudd_bddIte(dd,c,rs1,rs0);\n    if (g == NULL) {\n\t(void) printf(\"TEST-MINI: restrict failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(g);\n    if (g != f) {\n\t(void) printf(\"TEST-MINI: restrict failed (4).\\n\");\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,rs1);\n    Cudd_RecursiveDeref(dd,rs0);\n    Cudd_RecursiveDeref(dd,g);\n    g = Cudd_bddIte(dd,c,cs1,cs0);\n    if (g == NULL) {\n\t(void) printf(\"TEST-MINI: constrain failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(g);\n    if (g != f) {\n\t(void) printf(\"TEST-MINI: constrain failed (4).\\n\");\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,cs1);\n    Cudd_RecursiveDeref(dd,cs0);\n    Cudd_RecursiveDeref(dd,g);\n    g = Cudd_bddIte(dd,c,na1,na0);\n    if (g == NULL) {\n\t(void) printf(\"TEST-MINI: NPand failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(g);\n    if (g != f) {\n\t(void) printf(\"TEST-MINI: NPand failed (4).\\n\");\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,na1);\n    Cudd_RecursiveDeref(dd,na0);\n    Cudd_RecursiveDeref(dd,g);\n    g = Cudd_bddIte(dd,c,a1,a0);\n    if (g == NULL) {\n\t(void) printf(\"TEST-MINI: and failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(g);\n    if (g != f) {\n\t(void) printf(\"TEST-MINI: and failed (4).\\n\");\n\treturn(0);\n    }\n    Cudd_RecursiveDeref(dd,a1);\n    Cudd_RecursiveDeref(dd,a0);\n    Cudd_RecursiveDeref(dd,g);\n\n    return(1);\n\n} /* end of ntrTestMinimizationAux */\n\n\n/**\n  @brief Processes one %BDD for Ntr_TestDensity.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_TestDensity ntrCompress1\n\n*/\nstatic int\nntrTestDensityAux(\n  DdManager * dd,\n  BnetNetwork * net,\n  DdNode * f,\n  char * name,\n  NtrOptions * option)\n{\n    DdNode *s, *b, *hb, *sp, *ua, *c1, *c2;\n    int pr;\n    int result;\n    int nvars;\n    int size, sizeS;\n    double densityF, densityB, densityS, densityHB, densitySP, densityUA;\n    double densityC1, densityC2;\n    char *onames[8];\n    DdNode *outputs[8];\n\n    result = 1;\n    pr = option->verb;\n    nvars = Cudd_SupportSize(dd,f);\n    if (nvars == CUDD_OUT_OF_MEM) return(0);\n    densityF = Cudd_Density(dd,f,nvars);\n    (void) printf(\"TEST-DENSITY:: %s (%d variables)\\n\", name, nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-D    (%g)\", densityF);\n\tCudd_PrintDebug(dd, f, nvars, pr);\n\t(void) printf(\"T-D APA \");\n\tif (!Cudd_ApaPrintMinterm(stdout, dd, f, nvars))\n\t    result = 0;\n    }\n    /* Test remapping underapproximation. */\n    /* s = Cudd_SubsetRemap(dd,f); */\n    s = Cudd_RemapUnderApprox(dd,f,nvars,0,option->quality);\n    if (s == NULL) {\n\t(void) printf(\"TEST-DENSITY: computation failed\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(s);\n    sizeS = Cudd_DagSize(s);\n    densityS = Cudd_Density(dd,s,nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-D ID (%g)\", densityS);\n\tCudd_PrintDebug(dd, s, nvars, pr);\n    }\n    if (!Cudd_bddLeq(dd,s,f)) {\n\t(void) printf(\"TEST-DENSITY: result not a subset\\n\");\n\tresult = 0;\n    }\n    if (densityF > densityS) {\n\t(void) printf(\"TEST-DENSITY: result less dense\\n\");\n\t/* result = 0; */\n    }\n    size = sizeS;\n    /* Test biased underapproximation. */\n    b = Cudd_BiasedUnderApprox(dd,f,Cudd_Not(s),nvars,0,\n\t\t\t       option->quality*1.1,option->quality*0.5);\n    if (b == NULL) {\n\t(void) printf(\"TEST-DENSITY: computation failed\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(b);\n    densityB = Cudd_Density(dd,b,nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-D BU (%g)\", densityB);\n\tCudd_PrintDebug(dd, b, nvars, pr);\n    }\n    if (!Cudd_bddLeq(dd,b,f)) {\n\t(void) printf(\"TEST-DENSITY: result not a subset\\n\");\n\tresult = 0;\n    }\n    if (densityF > densityB) {\n\t(void) printf(\"TEST-DENSITY: result less dense\\n\");\n\t/* result = 0; */\n    }\n    /* Test heavy-branch subsetting. */\n    hb = Cudd_SubsetHeavyBranch(dd, f, nvars, size);\n    if (hb == NULL) {\n\t(void) printf(\"TEST-DENSITY: HB computation failed\\n\");\n\tCudd_RecursiveDeref(dd,s);\n\treturn(0);\n    }\n    Cudd_Ref(hb);\n    densityHB = Cudd_Density(dd,hb,nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-D HB (%g)\", densityHB);\n\tCudd_PrintDebug(dd, hb, nvars, pr);\n    }\n    if (!Cudd_bddLeq(dd,hb,f)) {\n\t(void) printf(\"TEST-DENSITY: HB not a subset\\n\");\n\tresult = 0;\n    }\n    /* Test short paths subsetting. */\n    sp = Cudd_SubsetShortPaths(dd, f, nvars, size, 0);\n    if (sp == NULL) {\n\t(void) printf(\"TEST-DENSITY: SP computation failed\\n\");\n\tCudd_RecursiveDeref(dd,s);\n\tCudd_RecursiveDeref(dd,hb);\n\treturn(0);\n    }\n    Cudd_Ref(sp);\n    densitySP = Cudd_Density(dd,sp,nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-D SP (%g)\", densitySP);\n\tCudd_PrintDebug(dd, sp, nvars, pr);\n    }\n    if (!Cudd_bddLeq(dd,sp,f)) {\n\t(void) printf(\"TEST-DENSITY: SP not a subset\\n\");\n\tresult = 0;\n    }\n    /* Test underapproximation. */\n    ua = Cudd_UnderApprox(dd,f,nvars,0,FALSE,option->quality);\n    if (ua == NULL) {\n\t(void) printf(\"TEST-DENSITY: computation failed\\n\");\n\tCudd_RecursiveDeref(dd,s);\n\tCudd_RecursiveDeref(dd,hb);\n\tCudd_RecursiveDeref(dd,sp);\n\treturn(0);\n    }\n    Cudd_Ref(ua);\n    densityUA = Cudd_Density(dd,ua,nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-D UA (%g)\", densityUA);\n\tCudd_PrintDebug(dd, ua, nvars, pr);\n    }\n    if (!Cudd_bddLeq(dd,ua,f)) {\n\t(void) printf(\"TEST-DENSITY: result not a subset\\n\");\n\tresult = 0;\n    }\n    if (densityF > densityUA) {\n\t(void) printf(\"TEST-DENSITY: result less dense\\n\");\n    }\n    /* Test compress 2 method. */\n    c1 = ntrCompress2(dd, f, nvars, size);\n    if (c1 == NULL) {\n\t(void) printf(\"TEST-DENSITY: C1 computation failed\\n\");\n\tCudd_RecursiveDeref(dd,s);\n\tCudd_RecursiveDeref(dd,hb);\n\tCudd_RecursiveDeref(dd,sp);\n\tCudd_RecursiveDeref(dd,ua);\n\treturn(0);\n    }\n    densityC1 = Cudd_Density(dd,c1,nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-D C1 (%g)\", densityC1);\n\tCudd_PrintDebug(dd, c1, nvars, pr);\n    }\n    if (!Cudd_bddLeq(dd,c1,f)) {\n\t(void) printf(\"TEST-DENSITY: C1 not a subset\\n\");\n\tresult = 0;\n    }\n    /* Test compress subsetting. */\n    c2 = Cudd_SubsetCompress(dd, f, nvars, size);\n    if (c2 == NULL) {\n\t(void) printf(\"TEST-DENSITY: C2 computation failed\\n\");\n\tCudd_RecursiveDeref(dd,s);\n\tCudd_RecursiveDeref(dd,hb);\n\tCudd_RecursiveDeref(dd,sp);\n\tCudd_RecursiveDeref(dd,ua);\n\tCudd_RecursiveDeref(dd,c1);\n\treturn(0);\n    }\n    Cudd_Ref(c2);\n    densityC2 = Cudd_Density(dd,c2,nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-D C2 (%g)\", densityC2);\n\tCudd_PrintDebug(dd, c2, nvars, pr);\n    }\n    if (!Cudd_bddLeq(dd,c2,f)) {\n\t(void) printf(\"TEST-DENSITY: C2 not a subset\\n\");\n\tresult = 0;\n    }\n    /* Dump results if so requested. */\n    if (option->bdddump) {\n\tonames[0] = name;\t\toutputs[0] = f;\n\tonames[1] = (char *) \"id\";\toutputs[1] = s;\n\tonames[2] = (char *) \"bu\";\toutputs[2] = b;\n\tonames[3] = (char *) \"hb\";\toutputs[3] = hb;\n\tonames[4] = (char *) \"sp\";\toutputs[4] = sp;\n\tonames[5] = (char *) \"ua\";\toutputs[5] = ua;\n\tonames[6] = (char *) \"c1\";\toutputs[6] = c1;\n\tonames[7] = (char *) \"c2\";\toutputs[7] = c2;\n\tresult &= Bnet_bddArrayDump(dd, net, option->dumpfile, outputs,\n\t\t\t\t     onames, 8, option->dumpFmt);\n    }\n\n    Cudd_RecursiveDeref(dd,s);\n    Cudd_RecursiveDeref(dd,b);\n    Cudd_RecursiveDeref(dd,hb);\n    Cudd_RecursiveDeref(dd,sp);\n    Cudd_RecursiveDeref(dd,ua);\n    Cudd_RecursiveDeref(dd,c1);\n    Cudd_RecursiveDeref(dd,c2);\n\n    return(result);\n\n} /* end of ntrTestDensityAux */\n\n\n/**\n  @brief Processes one %BDD for Ntr_TestDecomp.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_TestDecomp\n\n*/\nstatic int\nntrTestDecompAux(\n  DdManager * dd,\n  BnetNetwork * net,\n  DdNode * f,\n  char * name,\n  NtrOptions * option)\n{\n    DdNode *one, *g, *h, *product;\n    DdNode **A, **I, **G, **V;\n    int pr;\n    int i, result;\n    int nA, nI, nG, nV;\n    int nvars;\n    int sizeSa;\n    int sizeSi, sizeSg, sizeSv;\n    char *onames[9];\n    DdNode *outputs[9];\n\n    result = 1;\n    pr = option->verb;\n    nvars = Cudd_SupportSize(dd,f);\n    if (nvars == CUDD_OUT_OF_MEM) return(0);\n    (void) printf(\"TEST-DECOMP:: %s (%d variables)\\n\", name, nvars);\n    if (pr > 0) {\n\t(void) printf(\"T-d    \");\n\tCudd_PrintDebug(dd, f, nvars, pr);\n    }\n    one = Cudd_ReadOne(dd);\n\n    /* Test Cudd_bddApproxConjDecomp */\n    nA = Cudd_bddApproxConjDecomp(dd,f,&A);\n    if (nA == 0) {\n\t(void) printf(\"TEST-DECOMP: computation failed\\n\");\n\treturn(0);\n    }\n    g = A[0];\n    h = (nA == 2) ? A[1] : one;\n    sizeSa = Cudd_SharingSize(A,nA);\n    if (pr > 0) {\n\t(void) printf(\"T-d SS : %d nodes\\n\", sizeSa);\n\t(void) printf(\"T-d GS \");\n\tCudd_PrintDebug(dd, g, nvars, pr);\n\t(void) printf(\"T-d HS \");\n\tCudd_PrintDebug(dd, h, nvars, pr);\n    }\n    product = Cudd_bddAnd(dd,g,h);\n    if (product == NULL) {\n\t(void) printf(\"TEST-DECOMP: computation failed\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(product);\n    if (product != f) {\n\t(void) printf(\"TEST-DECOMP: result not a decomposition\\n\");\n\tresult = 0;\n    }\n    Cudd_RecursiveDeref(dd,product);\n\n    /* Test Cudd_bddIterConjDecomp */\n    nI = Cudd_bddIterConjDecomp(dd,f,&I);\n    if (nI == 0) {\n\t(void) printf(\"TEST-DECOMP: computation failed\\n\");\n\treturn(0);\n    }\n    g = I[0];\n    h = (nI == 2) ? I[1] : one;\n    sizeSi = Cudd_SharingSize(I,nI);\n    if (pr > 0) {\n\t(void) printf(\"T-d SI : %d nodes\\n\", sizeSi);\n\t(void) printf(\"T-d GI \");\n\tCudd_PrintDebug(dd, g, nvars, pr);\n\t(void) printf(\"T-d HI \");\n\tCudd_PrintDebug(dd, h, nvars, pr);\n    }\n    product = Cudd_bddAnd(dd,g,h);\n    if (product == NULL) {\n\t(void) printf(\"TEST-DECOMP: computation failed\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(product);\n    if (product != f) {\n\t(void) printf(\"TEST-DECOMP: result not a decomposition\\n\");\n\tresult = 0;\n    }\n    Cudd_RecursiveDeref(dd,product);\n\n    /* Test Cudd_bddGenConjDecomp */\n    nG = Cudd_bddGenConjDecomp(dd,f,&G);\n    if (nG == 0) {\n\t(void) printf(\"TEST-DECOMP: computation failed\\n\");\n\treturn(0);\n    }\n    g = G[0];\n    h = (nG == 2) ? G[1] : one;\n    sizeSg = Cudd_SharingSize(G,nG);\n    if (pr > 0) {\n\t(void) printf(\"T-d SD : %d nodes\\n\", sizeSg);\n\t(void) printf(\"T-d GD \");\n\tCudd_PrintDebug(dd, g, nvars, pr);\n\t(void) printf(\"T-d HD \");\n\tCudd_PrintDebug(dd, h, nvars, pr);\n    }\n    product = Cudd_bddAnd(dd,g,h);\n    if (product == NULL) {\n\t(void) printf(\"TEST-DECOMP: computation failed\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(product);\n    if (product != f) {\n\t(void) printf(\"TEST-DECOMP: result not a decomposition\\n\");\n\tresult = 0;\n    }\n    Cudd_RecursiveDeref(dd,product);\n\n    /* Test Cudd_bddVarConjDecomp */\n    nV = Cudd_bddVarConjDecomp(dd,f,&V);\n    if (nV == 0) {\n\t(void) printf(\"TEST-DECOMP: computation failed\\n\");\n\treturn(0);\n    }\n    g = V[0];\n    h = (nV == 2) ? V[1] : one;\n    sizeSv = Cudd_SharingSize(V,nV);\n    if (pr > 0) {\n\t(void) printf(\"T-d SQ : %d nodes\\n\", sizeSv);\n\t(void) printf(\"T-d GQ \");\n\tCudd_PrintDebug(dd, g, nvars, pr);\n\t(void) printf(\"T-d HQ \");\n\tCudd_PrintDebug(dd, h, nvars, pr);\n    }\n    product = Cudd_bddAnd(dd,g,h);\n    if (product == NULL) {\n\t(void) printf(\"TEST-DECOMP: computation failed\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(product);\n    if (product != f) {\n\t(void) printf(\"TEST-DECOMP: result not a decomposition\\n\");\n\tresult = 0;\n    }\n    Cudd_RecursiveDeref(dd,product);\n\n    /* Dump to file if requested. */\n    if (option->bdddump) {\n\tonames[0] = name;\t\toutputs[0] = f;\n\tonames[1] = (char *) \"ga\";\toutputs[1] = A[0];\n\tonames[2] = (char *) \"ha\";\toutputs[2] = (nA == 2) ? A[1] : one;\n\tonames[3] = (char *) \"gi\";\toutputs[3] = I[0];\n\tonames[4] = (char *) \"hi\";\toutputs[4] = (nI == 2) ? I[1] : one;\n\tonames[5] = (char *) \"gg\";\toutputs[5] = G[0];\n\tonames[6] = (char *) \"hg\";\toutputs[6] = (nG == 2) ? G[1] : one;\n\tonames[7] = (char *) \"gv\";\toutputs[7] = V[0];\n\tonames[8] = (char *) \"hv\";\toutputs[8] = (nV == 2) ? V[1] : one;\n\tresult &= Bnet_bddArrayDump(dd, net, option->dumpfile, outputs,\n\t\t\t\t     onames, 9, option->dumpFmt);\n    }\n\n    /* Clean up. */\n    for (i = 0; i < nA; i++) {\n\tCudd_RecursiveDeref(dd,A[i]);\n    }\n    for (i = 0; i < nI; i++) {\n\tCudd_RecursiveDeref(dd,I[i]);\n    }\n    for (i = 0; i < nG; i++) {\n\tCudd_RecursiveDeref(dd,G[i]);\n    }\n    for (i = 0; i < nV; i++) {\n\tCudd_RecursiveDeref(dd,V[i]);\n    }\n    FREE(A);\n    FREE(I);\n    FREE(G);\n    FREE(V);\n\n    return(result);\n\n} /* end of ntrTestDecompAux */\n\n\n/**\n  @brief Processes one %BDD for Ntr_TestCofactorEstimate.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nntrTestCofEstAux(\n  DdManager * dd,\n  BnetNetwork * net,\n  DdNode * f,\n  char * name,\n  NtrOptions * option)\n{\n    DdNode *support, *scan, *cof;\n    int pr;\n    int nvars;\n    int exactSize, estimate, estimateS;\n    int totalExactSize = 0;\n    int totalEstimate = 0;\n    int totalEstimateS = 0;\n    int largestError = -1;\n    int largestErrorS = -1;\n    DdNode *errorVar = NULL;\n\n    pr = option->verb;\n    support = Cudd_Support(dd,f);\n    if (support == NULL) return(0);\n    Cudd_Ref(support);\n    nvars = Cudd_DagSize(support) - 1;\n    scan = support;\n    while (!Cudd_IsConstant(scan)) {\n\tDdNode *var = Cudd_bddIthVar(dd,scan->index);\n\tcof = Cudd_Cofactor(dd,f,var);\n\tif (cof == NULL) return(0);\n\tCudd_Ref(cof);\n\texactSize = Cudd_DagSize(cof);\n\ttotalExactSize += exactSize;\n\testimate = Cudd_EstimateCofactor(dd,f,scan->index,1);\n\ttotalEstimate += estimate;\n\tif (estimate < exactSize)\n\t    (void) printf(\"Optimistic estimate!\\n\");\n\tif (estimate - exactSize > largestError) {\n\t    largestError = estimate - exactSize;\n\t    errorVar = var;\n\t}\n\testimateS = Cudd_EstimateCofactorSimple(f,scan->index);\n\ttotalEstimateS += estimateS;\n\tif (estimateS < exactSize)\n\t    (void) printf(\"Optimistic estimateS!\\n\");\n\tif (estimateS - exactSize > largestErrorS)\n\t    largestErrorS = estimateS - exactSize;\n\tCudd_RecursiveDeref(dd,cof);\n\tscan = cuddT(scan);\n    }\n    Cudd_RecursiveDeref(dd,support);\n    (void) printf(\"TEST-COF:: %s (%d vars)\", name, nvars);\n    Cudd_PrintDebug(dd, f, nvars, pr);\n    (void) printf(\"T-c   : %d\\n\", totalExactSize);\n    (void) printf(\"T-c E : %d %d\\n\", totalEstimate, largestError);\n    (void) printf(\"T-c S : %d %d\\n\", totalEstimateS, largestErrorS);\n\n    /* Dump to file if requested. */\n    if (option->bdddump) {\n\tchar *onames[3];\n\tDdNode *outputs[3];\n\tint result;\n\tcof = Cudd_Cofactor(dd,f,errorVar);\n\tif (cof == NULL) return(0);\n\tCudd_Ref(cof);\n\tonames[0] = name;\t\toutputs[0] = f;\n\tonames[1] = (char *) \"var\";\toutputs[1] = errorVar;\n\tonames[2] = (char *) \"cof\";\toutputs[2] = cof;\n\tresult = Bnet_bddArrayDump(dd, net, option->dumpfile, outputs,\n\t\t\t\t     onames, 3, option->dumpFmt);\n\tCudd_RecursiveDeref(dd,cof);\n\tif (result == 0) return(0);\n    }\n\n    return(1);\n\n} /* end of ntrTestCofEstAux */\n\n\n/**\n  @brief Processes one %BDD for Ntr_TestClipping.\n\n  @details It checks whether clipping was correct.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_TestClipping\n\n*/\nstatic int\nntrTestClippingAux(\n  DdManager * dd,\n  BnetNetwork * net1,\n  DdNode * f,\n  char * name,\n  DdNode * g,\n  char * gname,\n  NtrOptions * option)\n{\n    DdNode *prod, *sub, *sup;\n    DdNode *subF, *subG, *psub;\n    DdNode *supF, *supG, *psup;\n    int pr, nvars, depth;\n    int sizeProd, sizeSub, sizeSup;\n    static char *onames[7];\n    DdNode *outputs[7];\n    DdNode *operands[2];\n    int retval = 1;\n    int threshold = (option->threshold < 0) ? 0 : option->threshold;\n\n    pr = option->verb;\n    operands[0] = f; operands[1] = g;\n    nvars = Cudd_VectorSupportSize(dd,operands,2);\n    if (nvars == CUDD_OUT_OF_MEM) return(0);\n    depth = (int) ((double) nvars * option->clip);\n    (void) printf(\"TEST-CLIP:: %s depth = %d\\n\", name, depth);\n    (void) printf(\"T-C    \");\n    Cudd_PrintDebug(dd, f, nvars, pr);\n\n    /* Compute product. */\n    prod = Cudd_bddAnd(dd, f, g);\n    if (prod == NULL) {\n\t(void) printf(\"TEST-CLIP: product failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(prod);\n    (void) printf(\"T-C P= \");\n    Cudd_PrintDebug(dd, prod, nvars, pr);\n    sizeProd = Cudd_DagSize(prod);\n\n    /* Compute subset of product. */\n    sub = Cudd_bddClippingAnd(dd, f, g, depth, 0);\n    if (sub == NULL) {\n\t(void) printf(\"TEST-CLIP: subsetting product failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(sub);\n    (void) printf(\"T-C P- \");\n    Cudd_PrintDebug(dd, sub, nvars, pr);\n    sizeSub = Cudd_DagSize(sub);\n    if (sizeSub > sizeProd) {\n\t(void) printf(\"TEST-CLIP: subsetting product not safe.\\n\");\n    }\n\n    /* Compute product of subsets. */\n    subF = Cudd_RemapUnderApprox(dd,f,nvars,threshold,option->quality);\n    if (subF == NULL) {\n\t(void) printf(\"TEST-CLIP: subsetting of f failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(subF);\n    subG = Cudd_RemapUnderApprox(dd,g,nvars,threshold,option->quality);\n    if (subF == NULL) {\n\t(void) printf(\"TEST-CLIP: subsetting of g failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(subG);\n    psub = Cudd_bddAnd(dd,subF,subG);\n    if (psub == NULL) {\n\t(void) printf(\"TEST-CLIP: product of subsets failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(psub);\n    Cudd_RecursiveDeref(dd,subF);\n    Cudd_RecursiveDeref(dd,subG);\n    (void) printf(\"T-C P< \");\n    Cudd_PrintDebug(dd, psub, nvars, pr);\n\n    /* Compute superset of product. */\n    sup = Cudd_bddClippingAnd(dd, f, g, depth, 1);\n    if (sup == NULL) {\n\t(void) printf(\"TEST-CLIP: supersetting product failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(sup);\n    (void) printf(\"T-C P+ \");\n    Cudd_PrintDebug(dd, sup, nvars, pr);\n    sizeSup = Cudd_DagSize(sup);\n    if (sizeSup > sizeProd) {\n\t(void) printf(\"TEST-CLIP: supersetting product not safe.\\n\");\n    }\n\n    /* Compute product of supersets. */\n    supF = Cudd_RemapOverApprox(dd,f,nvars,threshold,option->quality);\n    if (supF == NULL) {\n\t(void) printf(\"TEST-CLIP: supersetting of f failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(supF);\n    supG = Cudd_RemapOverApprox(dd,g,nvars,threshold,option->quality);\n    if (supF == NULL) {\n\t(void) printf(\"TEST-CLIP: supersetting of g failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(supG);\n    psup = Cudd_bddAnd(dd,supF,supG);\n    if (psup == NULL) {\n\t(void) printf(\"TEST-CLIP: product of supersets failed.\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(psup);\n    Cudd_RecursiveDeref(dd,supF);\n    Cudd_RecursiveDeref(dd,supG);\n    (void) printf(\"T-C P> \");\n    Cudd_PrintDebug(dd, psup, nvars, pr);\n\n    if (option->bdddump) {\n\tonames[0] = name;\t\toutputs[0] = f;\n\tonames[1] = gname;\t\toutputs[1] = g;\n\tonames[2] = (char *) \"prod\";\toutputs[2] = prod;\n\tonames[3] = (char *) \"sub\";\toutputs[3] = sub;\n\tonames[4] = (char *) \"sup\";\toutputs[4] = sup;\n\tonames[5] = (char *) \"psub\";\toutputs[5] = psub;\n\tonames[6] = (char *) \"psup\";\toutputs[6] = psup;\n\tretval &= Bnet_bddArrayDump(dd, net1, option->dumpfile, outputs,\n\t\t\t\t     onames, 7, option->dumpFmt);\n    }\n\n    /* Check correctness. */\n    if (!Cudd_bddLeq(dd,sub,prod)) {\n\t(void) printf(\"TEST-CLIP: subsetting product not a subset.\\n\");\n\treturn(0);\n    }\n    if (!Cudd_bddLeq(dd,prod,sup)) {\n\t(void) printf(\"TEST-CLIP: supersetting product not a superset.\\n\");\n\treturn(0);\n    }\n    if (!Cudd_bddLeq(dd,psub,prod)) {\n\t(void) printf(\"TEST-CLIP: product of subsets not a subset.\\n\");\n\treturn(0);\n    }\n    if (!Cudd_bddLeq(dd,prod,psup)) {\n\t(void) printf(\"TEST-CLIP: product of supersets not a superset.\\n\");\n\treturn(0);\n    }\n\n    Cudd_RecursiveDeref(dd,prod);\n    Cudd_RecursiveDeref(dd,sub);\n    Cudd_RecursiveDeref(dd,sup);\n    Cudd_RecursiveDeref(dd,psub);\n    Cudd_RecursiveDeref(dd,psup);\n\n    return(retval);\n\n} /* end of ntrTestClippingAux */\n\n\n\n/**\n  @brief Processes one triplet of BDDs for Ntr_TestEquivAndContain.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_TestEquivAndContain\n\n*/\nstatic int\nntrTestEquivAndContainAux(\n  DdManager *dd,\n  BnetNetwork *net1,\n  DdNode *f,\n  char *fname,\n  DdNode *g,\n  char *gname,\n  DdNode *d,\n  char *dname,\n  NtrOptions *option)\n{\n    DdNode *xor_, *diff, *ndiff;\n    int pr, nvars;\n    int equiv, implies;\n    static char *onames[6];\n    DdNode *outputs[6];\n    DdNode *fgd[3];\n\n    pr = option->verb;\n    fgd[0] = f; fgd[1] = g; fgd[2] = d;\n    nvars = Cudd_VectorSupportSize(dd,fgd,3);\n    if (nvars == CUDD_OUT_OF_MEM) return(0);\n    (void) printf(\"TEST-DC:: %s [=<]= %s unless %s\\n\", fname, gname, dname);\n    (void) printf(\"T-F    \");\n    Cudd_PrintDebug(dd, f, nvars, pr);\n    (void) printf(\"T-G    \");\n    Cudd_PrintDebug(dd, g, nvars, pr);\n    (void) printf(\"T-D    \");\n    Cudd_PrintDebug(dd, d, nvars, pr);\n\n    /* Check equivalence unless don't cares. */\n    xor_ = Cudd_bddXor(dd, f, g);\n    if (xor_ == NULL) {\n\t(void) printf(\"TEST-DC: XOR computation failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(xor_);\n    equiv = Cudd_EquivDC(dd, f, g, d);\n    if (equiv != Cudd_bddLeq(dd,xor_,d)) {\n\t(void) printf(\"TEST-DC: EquivDC computation incorrect (1).\\n\");\n\t(void) printf(\"  EquivDC states that %s and %s are %s\\n\",\n\t\t      fname, gname, equiv ? \"equivalent\" : \"not equivalent\");\n\t(void) printf(\"T-X    \");\n\tCudd_PrintDebug(dd, xor_, nvars, pr);\n\treturn(0);\n    }\n    equiv = Cudd_EquivDC(dd, f, g, Cudd_Not(d));\n    if (equiv != Cudd_bddLeq(dd,xor_,Cudd_Not(d))) {\n\t(void) printf(\"TEST-DC: EquivDC computation incorrect (2).\\n\");\n\t(void) printf(\"  EquivDC states that %s and %s are %s\\n\",\n\t\t      fname, gname, equiv ? \"equivalent\" : \"not equivalent\");\n\t(void) printf(\"T-X    \");\n\tCudd_PrintDebug(dd, xor_, nvars, pr);\n\treturn(0);\n    }\n    equiv = Cudd_EquivDC(dd, f, Cudd_Not(g), d);\n    if (equiv != Cudd_bddLeq(dd,Cudd_Not(xor_),d)) {\n\t(void) printf(\"TEST-DC: EquivDC computation incorrect (3).\\n\");\n\t(void) printf(\"  EquivDC states that %s and not %s are %s\\n\",\n\t\t      fname, gname, equiv ? \"equivalent\" : \"not equivalent\");\n\t(void) printf(\"T-X    \");\n\tCudd_PrintDebug(dd, Cudd_Not(xor_), nvars, pr);\n\treturn(0);\n    }\n    equiv = Cudd_EquivDC(dd, f, Cudd_Not(g), Cudd_Not(d));\n    if (equiv != Cudd_bddLeq(dd,d,xor_)) {\n\t(void) printf(\"TEST-DC: EquivDC computation incorrect (4).\\n\");\n\t(void) printf(\"  EquivDC states that %s and not %s are %s\\n\",\n\t\t      fname, gname, equiv ? \"equivalent\" : \"not equivalent\");\n\t(void) printf(\"T-X    \");\n\tCudd_PrintDebug(dd, Cudd_Not(xor_), nvars, pr);\n\treturn(0);\n    }\n\n    /* Check containment unless don't cares. */\n    diff = Cudd_bddAnd(dd, f, Cudd_Not(g));\n    if (diff == NULL) {\n\t(void) printf(\"TEST-DC: AND/NOT computation failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(diff);\n    implies = Cudd_bddLeqUnless(dd, f, g, d);\n    if (implies != Cudd_bddLeq(dd,diff,d)) {\n\t(void) printf(\"TEST-DC: LeqUnless computation incorrect (1).\\n\");\n\t(void) printf(\"  LeqUnless states that %s %s %s\\n\",\n\t\t      fname, implies ? \"implies\" : \"does not imply\", gname);\n\t(void) printf(\"T-I    \");\n\tCudd_PrintDebug(dd, diff, nvars, pr);\n\treturn(0);\n    }\n    implies = Cudd_bddLeqUnless(dd, f, g, Cudd_Not(d));\n    if (implies != Cudd_bddLeq(dd,diff,Cudd_Not(d))) {\n\t(void) printf(\"TEST-DC: LeqUnless computation incorrect (2).\\n\");\n\t(void) printf(\"  LeqUnless states that %s %s %s\\n\",\n\t\t      fname, implies ? \"implies\" : \"does not imply\", gname);\n\t(void) printf(\"T-I    \");\n\tCudd_PrintDebug(dd, diff, nvars, pr);\n\treturn(0);\n    }\n    ndiff = Cudd_bddAnd(dd, f, g);\n    if (ndiff == NULL) {\n\t(void) printf(\"TEST-DC: AND computation failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(ndiff);\n    implies = Cudd_bddLeqUnless(dd, f, Cudd_Not(g), d);\n    if (implies != Cudd_bddLeq(dd,ndiff,d)) {\n\t(void) printf(\"TEST-DC: LeqUnless computation incorrect (3).\\n\");\n\t(void) printf(\"  LeqUnless states that %s %s not(%s)\\n\",\n\t\t      fname, implies ? \"implies\" : \"does not imply\", gname);\n\t(void) printf(\"T-I    \");\n\tCudd_PrintDebug(dd, ndiff, nvars, pr);\n\treturn(0);\n    }\n    implies = Cudd_bddLeqUnless(dd, f, Cudd_Not(g), Cudd_Not(d));\n    if (implies != Cudd_bddLeq(dd,ndiff,Cudd_Not(d))) {\n\t(void) printf(\"TEST-DC: LeqUnless computation incorrect (3).\\n\");\n\t(void) printf(\"  LeqUnless states that %s %s not(%s)\\n\",\n\t\t      fname, implies ? \"implies\" : \"does not imply\", gname);\n\t(void) printf(\"T-I    \");\n\tCudd_PrintDebug(dd, ndiff, nvars, pr);\n\treturn(0);\n    }\n    if (option->bdddump) {\n\tonames[0] = fname;\t\toutputs[0] = f;\n\tonames[1] = gname;\t\toutputs[1] = g;\n\tonames[2] = dname;\t\toutputs[2] = d;\n\tonames[3] = (char *) \"xor\";\toutputs[3] = xor_;\n\tonames[4] = (char *) \"diff\";\toutputs[4] = diff;\n\tonames[5] = (char *) \"ndiff\";\toutputs[5] = ndiff;\n\tif (!Bnet_bddArrayDump(dd, net1, option->dumpfile, outputs, onames,\n\t\t\t       6, option->dumpFmt))\n\t    return(0);\n    }\n    Cudd_RecursiveDeref(dd,xor_);\n    Cudd_RecursiveDeref(dd,diff);\n    Cudd_RecursiveDeref(dd,ndiff);\n\n    return(1);\n\n} /* end of ntrTestEquivAndContainAux */\n\n\n/**\n  @brief Processes one pair of BDDs for Ntr_TestClosestCube.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_TestClosestCube\n\n*/\nstatic int\nntrTestClosestCubeAux(\n  DdManager *dd,\n  BnetNetwork *net,\n  DdNode *f,\n  char *fname,\n  DdNode *g,\n  char *gname,\n  DdNode **vars,\n  NtrOptions *option)\n{\n    DdNode *cube, *cubeN;\n    int distance, pr, nvars;\n    DdNode *fg[2];\n    static char *onames[4];\n    DdNode *outputs[4];\n\n    pr = option->verb;\n    fg[0] = f; fg[1] = g;\n    nvars = Cudd_VectorSupportSize(dd,fg,2);\n    if (nvars == CUDD_OUT_OF_MEM) return(0);\n    (void) printf(\"TEST-CC:: H(%s, %s)\\n\", fname, gname);\n    (void) printf(\"T-F    \");\n    Cudd_PrintDebug(dd, f, nvars, pr);\n    (void) printf(\"T-G    \");\n    Cudd_PrintDebug(dd, g, nvars, pr);\n\n    cube = Cudd_bddClosestCube(dd, f, g, &distance);\n    if (cube == NULL) {\n\t(void) printf(\"TEST-CC: computation failed (1).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(cube);\n    (void) printf(\"T-C (%d) \", distance);\n    Cudd_PrintDebug(dd, cube, nvars, pr);\n    if (distance == 0) {\n\tif (!Cudd_bddLeq(dd,cube,g)) {\n\t    (void) printf(\"TEST-CC: distance-0 cube not in g (2).\\n\");\n\t    return(0);\n\t}\n    }\n\n    (void) printf(\"T-GN   \");\n    Cudd_PrintDebug(dd, Cudd_Not(g), nvars, pr);\n    cubeN = Cudd_bddClosestCube(dd, f, Cudd_Not(g), &distance);\n    if (cubeN == NULL) {\n\t(void) printf(\"TEST-CC: computation failed (3).\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(cubeN);\n    (void) printf(\"T-N (%d) \", distance);\n    Cudd_PrintDebug(dd, cubeN, nvars, pr);\n    if (distance == 0) {\n\tif (!Cudd_bddLeq(dd,cubeN,Cudd_Not(g))) {\n\t    (void) printf(\"TEST-CC: distance-0 cube not in not(g) (4).\\n\");\n\t    return(0);\n\t}\n    } else {\n\tint d, *minterm;\n\tint numvars = Cudd_ReadSize(dd);\n\tDdNode *scan, *zero;\n\tDdNode *minBdd = Cudd_bddPickOneMinterm(dd,cubeN,vars,numvars);\n\tif (minBdd == NULL) {\n\t    (void) printf(\"TEST-CC: minterm selection failed (5).\\n\");\n\t    return(0);\n\t}\n\tCudd_Ref(minBdd);\n\tminterm = ALLOC(int,numvars);\n\tif (minterm == NULL) {\n\t    (void) printf(\"TEST-CC: allocation failed (6).\\n\");\n\t    Cudd_RecursiveDeref(dd,minBdd);\n\t    return(0);\n\t}\n\tscan = minBdd;\n\tzero = Cudd_Not(DD_ONE(dd));\n\twhile (!Cudd_IsConstant(scan)) {\n\t    DdNode *R = Cudd_Regular(scan);\n\t    DdNode *T = Cudd_T(R);\n\t    DdNode *E = Cudd_E(R);\n\t    if (R != scan) {\n\t\tT = Cudd_Not(T);\n\t\tE = Cudd_Not(E);\n\t    }\n\t    if (T == zero) {\n\t\tminterm[Cudd_NodeReadIndex(R)] = 0;\n\t\tscan = E;\n\t    } else {\n\t\tminterm[Cudd_NodeReadIndex(R)] = 1;\n\t\tscan = T;\n\t    }\n\t}\n\tCudd_RecursiveDeref(dd,minBdd);\n\td = Cudd_MinHammingDist(dd,Cudd_Not(g),minterm,numvars);\n\tFREE(minterm);\n\tif (d != distance) {\n\t    (void) printf(\"TEST-CC: distance disagreement (7).\\n\");\n\t    return(0);\n\t}\n    }\n\n    if (option->bdddump) {\n\tonames[0] = fname;\t\toutputs[0] = f;\n\tonames[1] = gname;\t\toutputs[1] = g;\n\tonames[2] = (char *) \"cube\";\toutputs[2] = cube;\n\tonames[3] = (char *) \"cubeN\";\toutputs[3] = cubeN;\n\tif (!Bnet_bddArrayDump(dd, net, option->dumpfile, outputs, onames,\n\t\t\t       4, option->dumpFmt))\n\t    return(0);\n    }\n    Cudd_RecursiveDeref(dd,cube);\n    Cudd_RecursiveDeref(dd,cubeN);\n\n    return(1);\n\n} /* end of ntrTestClosestCubeAux */\n\n\n/**\n  @brief Processes one BDDs for Ntr_TestCharToVect.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_TestCharToVect\n\n*/\nstatic int\nntrTestCharToVect(\n  DdManager * dd,\n  DdNode * f,\n  NtrOptions *option)\n{\n    DdNode **vector;\n    int sharingSize;\n    DdNode *verify;\n    int pr = option->verb;\n    int i;\n\n    (void) fprintf(stdout,\"f\");\n    Cudd_PrintDebug(dd, f, Cudd_ReadSize(dd), 1);\n    if (pr > 1) {\n\tCudd_bddPrintCover(dd, f, f);\n    }\n    vector = Cudd_bddCharToVect(dd,f);\n    if (vector == NULL) return(0);\n    sharingSize = Cudd_SharingSize(vector, Cudd_ReadSize(dd));\n    (void) fprintf(stdout, \"Vector Size: %d components %d nodes\\n\",\n\t\t   Cudd_ReadSize(dd), sharingSize);\n    for (i = 0; i < Cudd_ReadSize(dd); i++) {\n\t(void) fprintf(stdout,\"v[%d]\",i);\n\tCudd_PrintDebug(dd, vector[i], Cudd_ReadSize(dd), 1);\n\tif (pr > 1) {\n\t    Cudd_bddPrintCover(dd, vector[i], vector[i]);\n\t}\n    }\n    verify = Cudd_bddVectorCompose(dd,f,vector);\n    if (verify != Cudd_ReadOne(dd)) {\n\t(void) fprintf(stdout, \"Verification failed!\\n\");\n\treturn(0);\n    }\n    Cudd_Ref(verify);\n    Cudd_IterDerefBdd(dd, verify);\n    for (i = 0; i < Cudd_ReadSize(dd); i++) {\n\tCudd_IterDerefBdd(dd, vector[i]);\n    }\n    FREE(vector);\n    return(1);\n\n} /* end of ntrTestCharToVect */\n\n\n#if 0\n/**\n  @brief Try hard to squeeze a %BDD.\n\n  @return a pointer to the squeezed %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see ntrTestDensityAux Cudd_SubsetCompress\n\n*/\nstatic DdNode *\nntrCompress1(\n  DdManager * dd,\n  DdNode * f,\n  int  nvars,\n  int  threshold)\n{\n    DdNode *res, *tmp1, *tmp2;\n    int sizeI, size;\n\n    tmp1 = Cudd_RemapUnderApprox(dd,f,nvars,0,1.0);\n    if (tmp1 == NULL) return(NULL);\n    Cudd_Ref(tmp1);\n    sizeI = Cudd_DagSize(tmp1);\n    size = (sizeI < threshold) ? sizeI : threshold;\n    tmp2 = Cudd_SubsetShortPaths(dd, tmp1, nvars, size, 0);\n    if (tmp2 == NULL) {\n\tCudd_RecursiveDeref(dd,tmp1);\n\treturn(NULL);\n    }\n    Cudd_Ref(tmp2);\n    Cudd_RecursiveDeref(dd,tmp1);\n    res = Cudd_bddSqueeze(dd,tmp2,f);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd,tmp2);\n\treturn(NULL);\n    }\n    Cudd_Ref(res);\n    Cudd_RecursiveDeref(dd,tmp2);\n    return(res);\n\n} /* end of ntrCompress1 */\n#endif\n\n\n/**\n  @brief Try hard to squeeze a %BDD.\n\n  @return a pointer to the squeezed %BDD if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see ntrTestDensityAux Cudd_SubsetCompress\n\n*/\nstatic DdNode *\nntrCompress2(\n  DdManager * dd,\n  DdNode * f,\n  int  nvars,\n  int  threshold)\n{\n    DdNode *res, *tmp1, *tmp2;\n    int sizeI;\n\n    tmp1 = Cudd_RemapUnderApprox(dd,f,nvars,0,1.0);\n    if (tmp1 == NULL) return(NULL);\n    Cudd_Ref(tmp1);\n    sizeI = Cudd_DagSize(tmp1);\n    if (sizeI > threshold) {\n\ttmp2 = Cudd_SubsetShortPaths(dd, tmp1, nvars, threshold, 0);\n\tif (tmp2 == NULL) {\n\t    Cudd_RecursiveDeref(dd,tmp1);\n\t    return(NULL);\n\t}\n\tCudd_Ref(tmp2);\n\tCudd_RecursiveDeref(dd,tmp1);\n    } else {\n\ttmp2 = tmp1;\n    }\n    res = Cudd_bddSqueeze(dd,tmp2,f);\n    if (res == NULL) {\n\tCudd_RecursiveDeref(dd,tmp2);\n\treturn(NULL);\n    }\n    Cudd_Ref(res);\n    if (Cudd_Density(dd,res,nvars) < Cudd_Density(dd,tmp2,nvars)) {\n\tCudd_RecursiveDeref(dd,res);\n\treturn(tmp2);\n    } else {\n\tCudd_RecursiveDeref(dd,tmp2);\n\treturn(res);\n    }\n\n} /* end of ntrCompress2 */\n\n\n/**\n  @brief Checks whether node is a buffer.\n\n  @return a pointer to the input node if nd is a buffer; NULL\n  otherwise.\n\n  @sideeffect None\n\n*/\nstatic BnetNode *\nntrNodeIsBuffer(\n  BnetNode *nd,\n  st_table *hash)\n{\n    BnetNode *inpnd;\n\n    if (nd->ninp != 1) return(0);\n    if (!st_lookup(hash, nd->inputs[0], (void **) &inpnd)) return(0);\n\n    return(nd->dd == inpnd->dd ? inpnd : NULL);\n\n} /* end of ntrNodeIsBuffer */\n"
  },
  {
    "path": "cudd/nanotrav/ntrHeap.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief Functions for heap-based priority queues.\n\n  @details The functions in this file manage a priority queue\n  implemented as a heap. The first element of the heap is the one with\n  the smallest key.  The queue stores generic pointers, but the key\n  must be an int.  Refer to Chapter 7 of Cormen, Leiserson, and Rivest\n  for the theory.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"ntr.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n   @brief Entry of NtrHeap.\n*/\nstruct NtrHeapSlot {\n    void *item;\n    int key;\n};\n\n/**\n   @brief Heap-based priority queue.\n*/\nstruct NtrHeap {\n    int size;\n    int nslots;\n    NtrHeapSlot *slots;\n};\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n#define PARENT(i)\t(((i)-1)>>1)\n#define RIGHT(i)\t(((i)+1)<<1)\n#define LEFT(i)\t\t(((i)<<1)|1)\n#define ITEM(p,i)\t((p)[i].item)\n#define KEY(p,i)\t((p)[i].key)\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void ntrHeapify (NtrHeap *heap, int i);\nstatic int ntrHeapResize (NtrHeap *heap);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Initializes a priority queue.\n\n  @return a pointer to the heap if successful; NULL otherwise.\n\n  @sideeffect None\n\n  @see Ntr_FreeHeap\n\n*/\nNtrHeap *\nNtr_InitHeap(\n  int size)\n{\n    NtrHeap *heap;\n\n    heap = ALLOC(NtrHeap,1);\n    if (heap == NULL) return(NULL);\n    heap->size = size;\n    heap->nslots = 0;\n    heap->slots = ALLOC(NtrHeapSlot,size);\n    if (heap->slots == NULL) {\n\tFREE(heap);\n\treturn(NULL);\n    }\n    return(heap);\n\n} /* end of Ntr_InitHeap */\n\n\n/**\n  @brief Frees a priority queue.\n\n  @sideeffect None\n\n  @see Ntr_InitHeap\n\n*/\nvoid\nNtr_FreeHeap(\n  NtrHeap *heap)\n{\n    FREE(heap->slots);\n    FREE(heap);\n    return;\n\n} /* end of Ntr_FreeHeap */\n\n\n/**\n  @brief Inserts an item in a priority queue.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_HeapExtractMin\n\n*/\nint\nNtr_HeapInsert(\n  NtrHeap *heap,\n  void *item,\n  int key)\n{\n    NtrHeapSlot *slots;\n    int i = heap->nslots;\n\n    if (i == heap->size && !ntrHeapResize(heap)) return(0);\n    slots = heap->slots;\n    heap->nslots++;\n    while (i > 0 && KEY(slots,PARENT(i)) > key) {\n\tITEM(slots,i) = ITEM(slots,PARENT(i));\n\tKEY(slots,i) = KEY(slots,PARENT(i));\n\ti = PARENT(i);\n    }\n    ITEM(slots,i) = item;\n    KEY(slots,i) = key;\n    return(1);\n\n} /* end of Ntr_HeapInsert */\n\n\n/**\n  @brief Extracts the element with the minimum key from a priority\n  queue.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect The minimum key and the associated item are returned as\n  side effects.\n\n  @see Ntr_HeapInsert\n\n*/\nint\nNtr_HeapExtractMin(\n  NtrHeap *heap,\n  void *item,\n  int *key)\n{\n    NtrHeapSlot *slots = heap->slots;\n\n    if (heap->nslots == 0) return(0);\n    *(void **)item = ITEM(slots,0);\n    *key = KEY(slots,0);\n    heap->nslots--;\n    ITEM(slots,0) = ITEM(slots,heap->nslots);\n    KEY(slots,0) = KEY(slots,heap->nslots);\n    ntrHeapify(heap,0);\n\n    return(1);\n\n} /* end of Ntr_HeapExtractMin */\n\n\n/**\n  @brief Returns the number of items in a priority queue.\n\n  @sideeffect None\n\n*/\nint\nNtr_HeapCount(\n  NtrHeap *heap)\n{\n    return(heap->nslots);\n\n} /* end of Ntr_HeapCount */\n\n\n/**\n  @brief Clones a priority queue.\n\n  @sideeffect None\n\n  @see Ntr_InitHeap\n\n*/\nNtrHeap *\nNtr_HeapClone(\n  NtrHeap *source)\n{\n    NtrHeap *dest;\n    int i;\n    int nslots = source->nslots;\n    NtrHeapSlot *sslots = source->slots;\n    NtrHeapSlot *dslots;\n\n    dest = Ntr_InitHeap(source->size);\n    if (dest == NULL) return(NULL);\n    dest->nslots = nslots;\n    dslots = dest->slots;\n    for (i = 0; i < nslots; i++) {\n\tKEY(dslots,i) = KEY(sslots,i);\n\tITEM(dslots,i) = ITEM(sslots,i);\n    }\n    return(dest);\n\n} /* end of Ntr_HeapClone */\n\n\n/**\n  @brief Calls a function on all items in a heap.\n*/\nvoid\nNtr_HeapForeach(\n  NtrHeap *heap,\n  void (*f)(void * e, void * arg),\n  void * arg)\n{\n    int i;\n\n    for (i = 0; i < heap->nslots; i++) {\n        f(heap->slots[i].item, arg);\n    }\n\n} /* end of Ntr_HeapForeach */\n\n\n/**\n  @brief Tests the heap property of a priority queue.\n\n  @return 1 if Successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nint\nNtr_TestHeap(\n  NtrHeap *heap,\n  int i)\n{\n    NtrHeapSlot *slots = heap->slots;\n    int nslots = heap->nslots;\n\n    if (i > 0 && KEY(slots,i) < KEY(slots,PARENT(i)))\n\treturn(0);\n    if (LEFT(i) < nslots) {\n\tif (!Ntr_TestHeap(heap,LEFT(i)))\n\t    return(0);\n    }\n    if (RIGHT(i) < nslots) {\n\tif (!Ntr_TestHeap(heap,RIGHT(i)))\n\t    return(0);\n    }\n    return(1);\n\n} /* end of Ntr_TestHeap */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Maintains the heap property of a priority queue.\n\n  @sideeffect None\n\n  @see Ntr_HeapExtractMin\n\n*/\nstatic void\nntrHeapify(\n  NtrHeap *heap,\n  int i)\n{\n    int smallest;\n    int left = LEFT(i);\n    int right = RIGHT(i);\n    int nslots = heap->nslots;\n    NtrHeapSlot *slots = heap->slots;\n    int key = KEY(slots,i);\n\n    if (left < nslots && KEY(slots,left) < key) {\n\tsmallest = left;\n    } else {\n\tsmallest = i;\n    }\n    if (right < nslots && KEY(slots,right) < KEY(slots,smallest)) {\n\tsmallest = right;\n    }\n    if (smallest != i) {\n\tvoid *item = ITEM(slots,i);\n\tKEY(slots,i) = KEY(slots,smallest);\n\tITEM(slots,i) = ITEM(slots,smallest);\n\tKEY(slots,smallest) = key;\n\tITEM(slots,smallest) = item;\n\tntrHeapify(heap,smallest);\n    }\n\n    return;\n\n} /* end of ntrHeapify */\n\n\n/**\n  @brief Resizes a priority queue.\n\n  @details Resizes a priority queue by doubling the number of\n  available slots.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n  @see Ntr_HeapInsert\n\n*/\nstatic int\nntrHeapResize(\n  NtrHeap *heap)\n{\n  int oldlength = heap->size;\n  int newlength = 2 * oldlength;\n  NtrHeapSlot *oldslots = heap->slots;\n  NtrHeapSlot *newslots = REALLOC(NtrHeapSlot, oldslots, newlength);\n  if (newslots == NULL) return 0;\n  heap->size = newlength;\n  heap->slots = newslots;\n  assert(Ntr_TestHeap(heap, 0));\n  return 1;\n\n} /* end of ntrHeapResize */\n"
  },
  {
    "path": "cudd/nanotrav/ntrMflow.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief Symbolic maxflow algorithm.\n\n  @details This file contains the functions that implement the\n  symbolic version of Dinits's maxflow algorithm described in the\n  ICCAD93 paper. The present implementation differs from the algorithm\n  described in the paper in that more than one matching techniques is\n  used. The technique of the paper is the one applied to\n  hourglass-type bilayers here.\n\n  @author Fabio Somenzi, Gary Hachtel\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"ntr.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n#define MAXPHASE 1000\n#define MAXLAYER 1000\n#define MAXFPIT  100000\n#define MANY_TIMES 3.0\n\n#define PRUNE\t\t/* If defined, enables pruning of E */\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n   @brief Structure to hold statistics.\n*/\ntypedef struct flowStatsStruct {\n    int pr;\t\t\t/**< level of verbosity */\n    long start_time;\t\t/**< cpu time when the covering started */\n    int phases;\t\t\t/**< number of phases */\n    int layers;\t\t\t/**< number of layers */\n    int fpit;\t\t\t/**< number of fixed point iterations */\n} flowStats;\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode *xcube, *ycube, *zcube;\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic void maximal_pull (DdManager *bdd, int l, DdNode *ty, DdNode **neW, DdNode **U, DdNode *E, DdNode **F, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\nstatic void propagate_maximal_flow (DdManager *bdd, int m, DdNode **neW, DdNode **U, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\nstatic void trellis (DdManager *bdd, int m, DdNode **neW, DdNode **U, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\nstatic void rhombus (DdManager *bdd, int m, DdNode **neW, DdNode **U, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\nstatic void hourglass (DdManager *bdd, int m, DdNode **neW, DdNode **U, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\nstatic void maximal_push (DdManager *bdd, int l, DdNode **U, DdNode **F, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\nstatic void trellisPush (DdManager *bdd, int m, DdNode **U, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\nstatic void rhombusPush (DdManager *bdd, int m, DdNode **U, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\nstatic void hourglassPush (DdManager *bdd, int m, DdNode **U, DdNode **x, DdNode **y, DdNode **z, int n, DdNode *pryz, DdNode *prxz, flowStats *stats);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Symbolic Dinit's algorithm.\n\n  @details@parblock\n  This function implements Dinits's algorithm for (0-1)\n  max flow, using BDDs and a symbolic technique to trace multiple\n  edge-disjoint augmenting paths to complete a phase. The outer\n  forever loop is over phases, and the inner forever loop is to\n  propagate a (not yet) maximal flow of edge-disjoint augmenting paths\n  from one layer to the previous. The subprocedure call implements a\n  least fixed point iteration to compute a (not yet) maximal flow\n  update between layers. At the end of each phase (except the last\n  one) the flow is actually pushed from the source to the sink.\n\n  Data items:\n    <ul>\n    <li> sx(ty)\tBDD representations of s(t).\n    <li> x(y)\tThe variables encoding the from(to)-node u(v) of an\n\t\tedge (u,v) in the given digraph.\n    <li> z\tAnother set of variables.\n    <li> E(x,y)\tThe edge relation.\n    <li> F(x,y) %BDD representation of the current flow, initialized to 0\n\t\tfor each arc, and updated by +1, -1, or 0 at the\n\t\tend of each phase.\n    <li> Ms Mt\tThe maximum flow, that is, the cardinality of a minimum cut,\n\t\tmeasured at the source and at the sink, respectively.\n\t\tThe two values should be identical.\n    <li> reached The set of nodes already visited in the BFS of the digraph.\n    <li> fos\tfanout of the source node s.\n    <li> fit\tfanin of the sink node t.\n    </ul>\n  \n  @endparblock\n\n  @sideeffect The flow realtion F and the cutset relation cut are returned\n  as side effects.\n\n*/\ndouble\nNtr_maximum01Flow(\n  DdManager * bdd /**< manager */,\n  DdNode * sx /**< source node */,\n  DdNode * ty /**< sink node */,\n  DdNode * E /**< edge relation */,\n  DdNode ** F /**< flow relation */,\n  DdNode ** cut /**< cutset relation */,\n  DdNode ** x /**< array of row variables */,\n  DdNode ** y /**< array of column variables */,\n  DdNode ** z /**< arrays of auxiliary variables */,\n  int  n /**< number of variables in each array */,\n  int  pr /**< verbosity level */)\n{\n    flowStats stats;\n    DdNode *one, *zero,\n#ifdef PRUNE\n\t     *EDC,\t    /* Edge don't care set */\n#endif\n\t     *reached,      /* states reached through useful edges */\n\t     *fos, *fit,    /* fanout of source, fanin of sink */\n\t     *rF, *rB, *tx,\n\t     *I, *P,\n\t     *w, *p, *q, *r,/* intemediate results */\n\t     *pryz, *prxz,  /* priority functions for disjoint path tracing */\n\t     **neW, **U;    /* arrays of BDDs for flow propagation */\n    int\t     i, j, l;\n    double   Ms, Mt;\n\n    /* Initialize debugging structure. */\n    stats.pr = pr;\n    stats.start_time = util_cpu_time();\n    stats.phases = 0;\n    stats.layers = 0;\n    stats.fpit = 0;\n\n    /* Allocate arrays for new (just reached vertex sets)\n    ** and U (useful edge sets).\n    */\n    U   = ALLOC(DdNode *, ((unsigned) MAXLAYER));\n    neW = ALLOC(DdNode *, ((unsigned) MAXLAYER));\n\n    one = Cudd_ReadOne(bdd);\n    zero = Cudd_Not(one);\n\n    /* Initialize xcube, ycube, and zcube (for abstractions). */\n    Cudd_Ref(xcube = Cudd_bddComputeCube(bdd,x,NULL,n));\n    Cudd_Ref(ycube = Cudd_bddComputeCube(bdd,y,NULL,n));\n    Cudd_Ref(zcube = Cudd_bddComputeCube(bdd,z,NULL,n));\n\n    /* Build the BDD for the priority functions. */\n    Cudd_Ref(pryz = Cudd_Dxygtdxz(bdd, n, x, y, z));\n    Cudd_Ref(prxz = Cudd_Dxygtdyz(bdd, n, x, y, z));\n    /* Now \"randomize\" by shuffling the x variables in pryz and the y\n    ** variables in prxz.\n    */\n    Cudd_Ref(p = Cudd_bddAdjPermuteX(bdd,pryz,x,n));\n    Cudd_RecursiveDeref(bdd,pryz);\n    pryz = p;\n    if(pr>2){(void) fprintf(stdout,\"pryz\");Cudd_PrintDebug(bdd,pryz,n*3,pr);}\n    Cudd_Ref(p = Cudd_bddAdjPermuteX(bdd,prxz,y,n));\n    Cudd_RecursiveDeref(bdd,prxz);\n    prxz = p;\n    if(pr>2){(void) fprintf(stdout,\"prxz\");Cudd_PrintDebug(bdd,prxz,n*3,pr);}\n\n#ifdef PRUNE\n    /* Build the edge don't care set and prune E. The edge don't care\n    ** set consists of the edges into the source(s), the edges out of the\n    ** sink(s), and the self-loops. These edges cannot contribute to the\n    ** maximum flow.\n    */\n    Cudd_Ref(p = Cudd_bddSwapVariables(bdd, sx, x, y, n));\n    Cudd_Ref(q = Cudd_bddSwapVariables(bdd, ty, x, y, n));\n    Cudd_Ref(r = Cudd_bddOr(bdd, p, q));\n    Cudd_RecursiveDeref(bdd,p);\n    Cudd_RecursiveDeref(bdd,q);\n    Cudd_Ref(p = Cudd_Xeqy(bdd, n, x, y));\n    Cudd_Ref(EDC = Cudd_bddOr(bdd, p, r));\n    Cudd_RecursiveDeref(bdd,p);\n    Cudd_RecursiveDeref(bdd,r);\n    if(pr>2){(void) fprintf(stdout,\"EDC\");Cudd_PrintDebug(bdd,EDC,n<<1,pr);}\n    Cudd_Ref(p = Cudd_bddAnd(bdd, E, Cudd_Not(EDC)));\n    Cudd_RecursiveDeref(bdd,EDC);\n    if(pr>0){(void) fprintf(stdout,\"Given  E\");Cudd_PrintDebug(bdd,E,n<<1,pr);}\n    E = p;\n    if(pr>0){(void) fprintf(stdout,\"Pruned E\");Cudd_PrintDebug(bdd,E,n<<1,pr);}\n#endif\n\n    /* Compute fanin of sink node t: it is an upper bound for the flow. */\n    Cudd_Ref(fit = Cudd_bddAnd(bdd, E, ty));\n    if (pr>2) {\n\t/* Compute fanout of source node s. */\n\tCudd_Ref(fos = Cudd_bddAnd(bdd, E, sx));\n\t(void) fprintf(stdout,\"fos\");Cudd_PrintDebug(bdd,fos,n<<1,pr);\n\tCudd_RecursiveDeref(bdd,fos);\n\n\t(void) fprintf(stdout,\"fit\");Cudd_PrintDebug(bdd,fit,n<<1,pr);\n    }\n    /* t(x) is used to check for termination of forward traversal. */\n    Cudd_Ref(tx = Cudd_bddSwapVariables(bdd, ty, x, y, n));\n\n    /* \\KW{Procedure}\\ \\ \\PC{maximum\\_flow}$(s,t,E(x,y)) */\n    Cudd_Ref(*F = zero);\n\n    for (i = 1; i < MAXPHASE; i++) {\n\tstats.phases++;\n\tif(pr>0){(void) fprintf(stdout,\"## Starting Phase %d at time = %s\\n\",i,\n\t\tutil_print_time(util_cpu_time() - stats.start_time));}\n\t/* new[0](x) = s(x);U^0(x,y)=E(x,y)\\cdot s(x) \\cdot \\overline{F(x,y)};\n\t** reached=s; new[1](x)=\\exists_xU^0(x,y);\n\t*/\n\tCudd_Ref(neW[0] = sx);\n\tCudd_Ref(p = Cudd_bddAnd(bdd, sx, Cudd_Not(*F)));\n\tCudd_Ref(U[0] = Cudd_bddAnd(bdd, p, E));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(reached = sx);\n\tCudd_Ref(r = Cudd_bddExistAbstract(bdd, U[0], xcube));\n\tCudd_RecursiveDeref(bdd,U[0]);\n\tCudd_Ref(q = Cudd_bddSwapVariables(bdd, r, x, y, n));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_Ref(neW[1] = Cudd_bddAnd(bdd, q, Cudd_Not(reached)));\n\tCudd_RecursiveDeref(bdd,q);\n\tif(pr>0) {\n\t    (void) fprintf(stdout,\"neW[1]\");Cudd_PrintDebug(bdd,neW[1],n,pr);\n\t}\n\tfor (l = 1; l < MAXLAYER; l++) {\n\t    if (neW[l] == zero) {\t/* flow is maximum */\n\t\t/* cut=reached(x) \\cdot E(x,y) \\cdot \\overline{reached(y)} */\n\t\tCudd_Ref(p = Cudd_bddAnd(bdd, reached, E));\n\t\tCudd_Ref(q = Cudd_bddSwapVariables(bdd, reached, x, y, n));\n\t\tCudd_Ref(*cut = Cudd_bddAnd(bdd, p, Cudd_Not(q)));\n\t\tCudd_RecursiveDeref(bdd,p);\n\t\tCudd_RecursiveDeref(bdd,q);\n\t\tCudd_RecursiveDeref(bdd,reached);\n\t\tfor (j = 0; j <= l; j++)\n\t\t    Cudd_RecursiveDeref(bdd,neW[j]);\n\t\tgoto endPhases;\n\t    }\n\t    /* As soon as we touch one sink node we stop traversal.\n\t    ** \\KW{if} ($t\\cdot new^{l} \\neq 0$)\n\t    */\n\t    if (!Cudd_bddLeq(bdd, tx, Cudd_Not(neW[l]))) {\n\t\tCudd_RecursiveDeref(bdd,reached);\n\t\tmaximal_pull(bdd,l-1,ty,neW,U,E,F,x,y,z,n,pryz,prxz,&stats);\n\t\tgoto endLayers;\n\t    }\n\t    stats.layers++;\n\t    if(pr>2){(void) fprintf(stdout,\"===== Layer %d =====\\n\",l);}\n\t    /* reached(x) = reached(x) + new^l(x) */\n\t    Cudd_Ref(w = Cudd_bddOr(bdd, reached, neW[l]));\n\t    Cudd_RecursiveDeref(bdd,reached);\n\t    reached = w;\n\t    /* I(y) = \\exists_x((E(x,y) \\cdot \\overline{F(x,y)})\n\t    **        \\cdot new^l(x))\n\t    */\n\t    Cudd_Ref(p = Cudd_bddAnd(bdd, E, Cudd_Not(*F)));\n\t    Cudd_Ref(I = Cudd_bddAndAbstract(bdd, p, neW[l], xcube));\n\t    if(pr>3){(void) fprintf(stdout,\"I\");Cudd_PrintDebug(bdd,I,n,pr);}\n\t    Cudd_RecursiveDeref(bdd,p);\n\t    /* rF(x)= I(x) \\cdot \\overline{reached(x)}) */\n\t    Cudd_Ref(p = Cudd_bddSwapVariables(bdd, I, x, y, n));\n\t    Cudd_RecursiveDeref(bdd,I);\n\t    Cudd_Ref(rF = Cudd_bddAnd(bdd, p, Cudd_Not(reached)));\n\t    Cudd_RecursiveDeref(bdd,p);\n\t    if(pr>2){(void) fprintf(stdout,\"rF\");Cudd_PrintDebug(bdd,rF,n,pr);}\n\t    /* P(x) = \\exists_{y}(F(x,y) \\cdot new^l(y)) */\n\t    Cudd_Ref(p = Cudd_bddSwapVariables(bdd, neW[l], x, y, n));\n\t    Cudd_Ref(P = Cudd_bddAndAbstract(bdd, *F, p, ycube));\n\t    Cudd_RecursiveDeref(bdd,p);\n\t    /* rB(x) = P(x) \\cdot \\overline{reached(x)}) */\n\t    Cudd_Ref(rB = Cudd_bddAnd(bdd, P, Cudd_Not(reached)));\n\t    Cudd_RecursiveDeref(bdd,P);\n\t    if(pr>2){(void) fprintf(stdout,\"rB\");Cudd_PrintDebug(bdd,rB,n,pr);}\n\t    /* new^{l+1}(x) = rF(x) + rB(x) */\n\t    Cudd_Ref(neW[l+1] = Cudd_bddOr(bdd, rF, rB));\n\t    Cudd_RecursiveDeref(bdd,rB);\n\t    Cudd_RecursiveDeref(bdd,rF);\n\t    if(pr>0) {\n\t\t(void) fprintf(stdout,\"new[%d]\",l+1);\n\t\tCudd_PrintDebug(bdd,neW[l+1],n,pr);\n\t    }\n\t} /* start next layer */\n\tif (l==MAXLAYER) (void) fprintf(stderr,\"ERROR! MAXLAYER exceeded.\\n\");\n\texit(3);\nendLayers:\n\tmaximal_push(bdd, l-1, U, F, x, y, z, n, pryz, prxz, &stats);\n\tfor (j = 0; j < l; j++) {\n\t    Cudd_RecursiveDeref(bdd,U[j]);\n\t    Cudd_RecursiveDeref(bdd,neW[j]);\n\t}\n\tCudd_RecursiveDeref(bdd,neW[l]);\n\tif (pr > 0) {\n\t    Cudd_Ref(p = Cudd_bddAnd(bdd, sx, *F));\n\t    Ms=Cudd_CountMinterm(bdd, p, n<<1);\n\t    (void) fprintf(stdout,\"# Flow out of s: %g\\n\", Ms);\n\t    Cudd_RecursiveDeref(bdd,p);\n\t}\n\tif (Cudd_bddLeq(bdd, fit, *F)) {\n\t    Cudd_Ref(*cut = fit);\n\t    goto endPhases;\n\t}\n    } /* start next phase */\n    if (i == MAXPHASE) (void) fprintf(stderr,\"ERROR! MAXPHASE exceeded.\\n\");\n\n    /* Last phase is completed --- print flow results. */\nendPhases:\n    Cudd_RecursiveDeref(bdd,tx);\n\n    Cudd_Ref(q = Cudd_bddAnd(bdd, *F, sx));\n    Ms = Cudd_CountMinterm(bdd, q, n<<1);\n    Cudd_RecursiveDeref(bdd,q);\n\n    Cudd_Ref(q = Cudd_bddAnd(bdd, *F, ty));\n    Mt = Cudd_CountMinterm(bdd, q, n<<1);\n    Cudd_RecursiveDeref(bdd,q);\n\n    if (pr>1) (void) fprintf(stdout,\"Mt= %g, Ms= %g \\n\", Mt, Ms);\n\n    if (pr>3){(void) fprintf(stdout,\"pryz\");Cudd_PrintDebug(bdd,pryz,n*3,pr);}\n    if (pr>3){(void) fprintf(stdout,\"prxz\");Cudd_PrintDebug(bdd,prxz,n*3,pr);}\n\n    if (pr>0) {\n\t(void) fprintf(stdout,\"#### Stats for maximum_flow ####\\n\");\n\t(void) fprintf(stdout,\"%d variables %d of which x[i]\\n\", Cudd_ReadSize(bdd), n);\n\t(void) fprintf(stdout,\"time       = %s\\n\",\n\t\tutil_print_time(util_cpu_time() - stats.start_time));\n\t(void) fprintf(stdout,\"phases     = %d\\n\", stats.phases);\n\t(void) fprintf(stdout,\"layers     = %d\\n\", stats.layers);\n\t(void) fprintf(stdout,\"FP iter.   = %d\\n\", stats.fpit);\n    }\n\n    Cudd_RecursiveDeref(bdd,fit);\n    Cudd_RecursiveDeref(bdd,pryz);\n    Cudd_RecursiveDeref(bdd,prxz);\n    Cudd_RecursiveDeref(bdd,xcube);\n    Cudd_RecursiveDeref(bdd,ycube);\n    Cudd_RecursiveDeref(bdd,zcube);\n#ifdef PRUNE\n    Cudd_RecursiveDeref(bdd,E);\n#endif\n\n    FREE(U);\n    FREE(neW);\n\n    return(Ms);\n\n} /* end of Ntr_maximum01Flow */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Selects set of edge-disjoint paths from layered network.\n\n  @details maximal_pull is called when the BFS constructing the\n  layered graph reaches a sink. At this point the new sets of the\n  BFS have been formed, and we know every vertex in these sets is\n  reachable from the source vertex (or vertices) s. The new sets are\n  used to compute the set of useful edges exiting each layer to the\n  right. In each layer, propagate_maximal_flow is called to select a\n  maximal subset of these useful edges. This subset is then used to\n  prune new and U.\n\n  @sideeffect None\n\n  @see maximal_push\n\n*/\nstatic void\nmaximal_pull(\n  DdManager * bdd /**< manager */,\n  int  l /**< depth of layered network for current phase */,\n  DdNode * ty /**< sink node */,\n  DdNode ** neW /**< array of BFS layers */,\n  DdNode ** U /**< array of useful edges */,\n  DdNode * E /**< edge relation */,\n  DdNode ** F /**< flow relation */,\n  DdNode ** x /**< array of variables for rows and columns */,\n  DdNode ** y /**< array of variables for rows and columns */,\n  DdNode ** z /**< array of variables for rows and columns */,\n  int  n /**< number of x variables */,\n  DdNode * pryz /**< priority function */,\n  DdNode * prxz /**< priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *p, *q, *r,\n\t   *UF, *UB;\n    int\t   m,\n\t   pr;\t\t/* Print control */\n\n    pr = stats->pr;\n\n    /* The useful edges of the last layer are all the empty edges into\n    ** the sink(s) from new[l].\n    ** U^{l}(x,y) = t(y)\\cdot \\overline{F(x,y)}\\cdot E(x,y)\\cdot new^{l}(x)\n    */\n    Cudd_Ref(p = Cudd_bddAnd(bdd, E, Cudd_Not(*F)));\n    Cudd_Ref(q = Cudd_bddAnd(bdd, neW[l], p));\n    Cudd_RecursiveDeref(bdd,p);\n    Cudd_Ref(U[l] = Cudd_bddAnd(bdd, ty, q));\n    Cudd_RecursiveDeref(bdd,q);\n    if(pr>1){(void) fprintf(stdout,\"U[%d]\",l);Cudd_PrintDebug(bdd,U[l],n<<1,pr);}\n    /* Eliminate from new[l] the states with no paths to the sink(s).\n    ** new^{l}(x)=\\exists_y U^{l}(x,y)\n    */\n    Cudd_RecursiveDeref(bdd,neW[l]);\n    Cudd_Ref(neW[l] = Cudd_bddExistAbstract(bdd, U[l], ycube));\n\n    for (m = l; m >= 1; m--) {\n\t/* Find usable backward edges from level m-1 to level m.\n\t** UB(x,y) = new^{m}(x) \\cdot F(x,y) \\cdot new^{m-1}(y)\n\t*/\n\tCudd_Ref(r = Cudd_bddSwapVariables(bdd, neW[m-1], x, y, n));\n\tCudd_Ref(q = Cudd_bddAnd(bdd, r, *F));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_Ref(UB = Cudd_bddAnd(bdd, neW[m], q));\n\tCudd_RecursiveDeref(bdd,q);\n\tif(pr>2){(void) fprintf(stdout,\"UB\");Cudd_PrintDebug(bdd,UB,n<<1,pr);}\n\t/* Find usable forward edges.\n\t** UF(x,y) = new^{m}(y) \\cdot \\overline{F(x,y)} \\cdot E(x,y)\n\t** \\cdot new^{m-1}(x)\n\t*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, E, Cudd_Not(*F)));\n\tCudd_Ref(q = Cudd_bddAnd(bdd, neW[m-1], p));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(r = Cudd_bddSwapVariables(bdd, neW[m], x, y, n));\n\tCudd_Ref(UF = Cudd_bddAnd(bdd, r, q));\n\tCudd_RecursiveDeref(bdd,q);\n\tCudd_RecursiveDeref(bdd,r);\n\tif(pr>2){(void) fprintf(stdout,\"UF\");Cudd_PrintDebug(bdd,UF,n<<1,pr);}\n\t/* U^{m-1}(x,y) = UB(y,x) + UF(x,y) */\n\tCudd_Ref(r = Cudd_bddSwapVariables(bdd, UB, x, y, n));\n\tCudd_RecursiveDeref(bdd,UB);\n\tCudd_Ref(U[m-1] = Cudd_bddOr(bdd, UF, r));\n\tCudd_RecursiveDeref(bdd,UF);\n\tCudd_RecursiveDeref(bdd,r);\n\tif(pr>2){(void)fprintf(stdout,\"U[%d]\",m-1);\n\t\tCudd_PrintDebug(bdd,U[m-1],n<<1,pr);}\n\t/* new[m-1](x) = \\exists_{y}U^{m-1}(x,y) */\n\tCudd_RecursiveDeref(bdd,neW[m-1]);\n\tCudd_Ref(neW[m-1] = Cudd_bddExistAbstract(bdd, U[m-1], ycube));\n\t/* Compute maximal disjoint interlayer edge set. */\n\tpropagate_maximal_flow(bdd, m, neW, U, x, y, z, n, pryz, prxz, stats);\n\tif(pr>0) {\n\t    (void)fprintf(stdout,\"U[%d]\",m-1);\n\t    Cudd_PrintDebug(bdd,U[m-1],n<<1,pr);\n\t}\n    } /* prune next layer */\n\n    return;\n\n} /* end of maximal_pull */\n\n\n/**\n  @brief Pulls flow though a layer.\n\n  @details propagate_maximal_flow only\n  affects U[m-1 and new[m-1].  At the end of this function, the edges\n  in U[m] are guaranteed to drain all the flow supplied by the edges\n  in U[m-1]. This effect is obtained by pruning U[m-1]. After the\n  pruned U[m-1] is computed, new[m-1] is updated to keep track of what\n  nodes are still useful.\n\n  The pruning is performed without actually measuring the in-potential\n  and the out-potential of each node. Instead, pairs of nodes from U[m-1]\n  and U[m] are matched. To avoid counting, the procedure computes sets of\n  paths that connect layer m-1 to layer m+1 and are edge-disjoint.\n\n  Two paths from layer m-1 to layer m+1 are disjoint if they have distinct\n  end-point or if they have distinct middle points. What condition to\n  enforce depends on the \"shape\" of the layers.]\n\n  @sideeffect Changes U[m-1 and new[m-1]]\n\n  @see trellis rhombus hourglass\n\n*/\nstatic void\npropagate_maximal_flow(\n  DdManager * bdd /**< %DD manager */,\n  int  m /**< center of current bilayer */,\n  DdNode ** neW /**< array of reachable or useful nodes */,\n  DdNode ** U /**< array of usable or useful edges */,\n  DdNode ** x /**< array of variables for rows and columns */,\n  DdNode ** y /**< array of variables for rows and columns */,\n  DdNode ** z /**< array of variables for rows and columns */,\n  int  n /**< number of x variables */,\n  DdNode * pryz /**< priority function */,\n  DdNode * prxz /**< priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *rN;\n    double   mtl, mtc, mtr;\t/* minterms for left, center, right levels */\n    int      pr;\t\t/* print control */\n\n    pr = stats->pr;\n\n    mtl = Cudd_CountMinterm(bdd, neW[m-1], n);\n    mtc = Cudd_CountMinterm(bdd, neW[m], n);\n\n    /* rN(y) = \\exists_x U^{m}(x,y) */\n    Cudd_Ref(rN = Cudd_bddExistAbstract(bdd, U[m], xcube));\n    mtr = Cudd_CountMinterm(bdd, rN, n);\n    Cudd_RecursiveDeref(bdd,rN);\n\n    if (pr > 0) {\n\t(void) fprintf(stdout, \"layer = %d mtl = %g  mtc = %g  mtr = %g\",\n\t\t       m, mtl, mtc, mtr);\n    }\n\n    if ((mtc > MANY_TIMES * mtl) || (mtc > MANY_TIMES * mtr)) {\n\tif (pr>0) (void) fprintf(stdout, \" R\\n\");\n\trhombus(bdd, m, neW, U, x, y, z, n, pryz, prxz, stats);\n    } else if (mtr > MANY_TIMES * mtc) {\n\tif (pr>0) (void) fprintf(stdout, \" H\\n\");\n\thourglass(bdd, m, neW, U, x, y, z, n, pryz, prxz, stats);\n    } else {\n\tif (pr>0) (void) fprintf(stdout, \" T\\n\");\n\ttrellis(bdd, m, neW, U, x, y, z, n, pryz, prxz, stats);\n    }\n    return;\n\n} /* end of propagate_maximal_flow */\n\n\n/**\n  @brief Selects edges from a trellis-type bilayer.\n\n  @details Used to pull flow.  First a matching is found in the left\n  layer. Then the paths are extended (if possible) through the right\n  layer. This process is repeated until a maximal flow is found.\n\n  @sideeffect None\n\n  @see rhombus hourglass trellisPush\n\n*/\nstatic void\ntrellis(\n  DdManager * bdd /**< %DD manager */,\n  int  m /**< center level of current bilayer */,\n  DdNode ** neW /**< array of node levels */,\n  DdNode ** U /**< array of edge layers */,\n  DdNode ** x /**< array of variables for rows and columns */,\n  DdNode ** y /**< array of variables for rows and columns */,\n  DdNode ** z /**< array of variables for rows and columns */,\n  int  n /**< number of x variables */,\n  DdNode * pryz /**< priority function */,\n  DdNode * prxz /**< priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *one, *zero,\n\t     *p, *q, *r,\n\t     *Uin,\t\t/* edges to be matched from U[m-1] */\n\t     *Uout,\t\t/* edges to be matched from U[m] */\n\t     *P,\n\t     *LU, *RU,\t\t/* left-unique and right-unique sets of edges */\n\t     *D,\n\t     *Ml, *Mr;\t\t/* nodes matched from left and right */\n    int      k,\n\t     pr;\t\t/* print control */\n\n    pr = stats->pr;\n\n    one = Cudd_ReadOne(bdd);\n    zero = Cudd_Not(one);\n\n    /*Uout(x,y)=U^m(x,y)*/\n    Cudd_Ref(Uout = U[m]);\n    if(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n    /*Uin(x,y)=U^{m-1}(x,y)*/\n    Cudd_Ref(Uin = U[m-1]);\n    if(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n    for(k = 0; k < MAXFPIT; k++) {\n\tstats->fpit++;\n\t/*LU(x,y)=Uin(x,y)\\cdot\\overline{\\exists_{z}(Uin(z,y)\\cdot\\Pi(x,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Uin, x, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, prxz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(LU = Cudd_bddAnd(bdd, Uin, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tif(pr>3){(void)fprintf(stdout,\"LU\");Cudd_PrintDebug(bdd,LU,n<<1,pr);}\n\t/*D(x,y)= LU(x,y)\\cdot \\overline{\\exists_{z}(LU(x,z)\\cdot \\Pi(y,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, LU, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, pryz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(D = Cudd_bddAnd(bdd, LU, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,LU);\n\tif(pr>3){(void)fprintf(stdout,\"D\");Cudd_PrintDebug(bdd,D,n<<1,pr);}\n\t/*Ml(y)=\\exists_{x}D(x,y)*/\n\tCudd_Ref(Ml = Cudd_bddExistAbstract(bdd, D, xcube));\n\tif(pr>3){(void)fprintf(stdout,\"Ml\");Cudd_PrintDebug(bdd,Ml,n,pr);}\n\t/*P(x,y)=Ml(x)\\cdot Uout(x,y)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Ml, x, y, n));\n\tCudd_Ref(P = Cudd_bddAnd(bdd, p, Uout));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,Ml);\n\tif(pr>3){(void)fprintf(stdout,\"P\");Cudd_PrintDebug(bdd,P,n<<1,pr);}\n\t/*RU(x,y)= P(x,y)\\cdot \\overline{\\exists_{z}(P(x,z)\\cdot \\Pi(y,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, P, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, pryz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(RU = Cudd_bddAnd(bdd, P, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,P);\n\tif(pr>3){(void)fprintf(stdout,\"RU\");Cudd_PrintDebug(bdd,RU,n<<1,pr);}\n\t/*Mr(x)=\\exists_{y}RU(x,y)*/\n\tCudd_Ref(Mr = Cudd_bddExistAbstract(bdd, RU, ycube));\n\tif(pr>3){(void)fprintf(stdout,\"Mr\");Cudd_PrintDebug(bdd,Mr,n,pr);}\n\t/*D(x,y)=D(x,y)\\cdot Mr(y)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Mr, x, y, n));\n\tCudd_RecursiveDeref(bdd,Mr);\n\tCudd_Ref(q = Cudd_bddAnd(bdd, D, p));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,D);\n\tD = q;\n\tif(pr>3){(void)fprintf(stdout,\"D\");Cudd_PrintDebug(bdd,D,n<<1,pr);}\n\t/*Uin(x,y)=Uin(x,y)-D(x,y)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, Uin, Cudd_Not(D)));\n\tCudd_RecursiveDeref(bdd,Uin);\n\tUin = p;\n\tif(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\t/*Uout(x,y)=Uout(x,y)-RU(x,y)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, Uout, Cudd_Not(RU)));\n\tCudd_RecursiveDeref(bdd,Uout);\n\tCudd_RecursiveDeref(bdd,RU);\n\tUout = p;\n\tif(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\t/*\\KW{if}(($D(x,y)=zero$)~~\\KW{or}~~($Uin(x,y)=zero$)~~\\KW{or}\n\t  ($Uout(x,y)=zero$))~~KW{break}*/\n\tif ((D == zero)||(Uin == zero)||(Uout == zero)) {\n\t    Cudd_RecursiveDeref(bdd,D);\n\t    break;\n\t}\n\tCudd_RecursiveDeref(bdd,D);\n\n    } /* Next least fixed point iteration with smaller Uin and Uout */\n    if (k == MAXFPIT) (void) fprintf(stderr,\n\t\"Trellis: WARNING! MAXFPIT (%d) exceeded processing Layer %d.\\n\",\n\tMAXFPIT, m);\n\n    if (Uin != zero) {\n\t/* $U^{m-1}(x,y) = U^{m-1}(x,y)-Uin(x,y)$*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, U[m-1], Cudd_Not(Uin)));\n\tCudd_RecursiveDeref(bdd,U[m-1]);\n\tU[m-1] = p;\n\t/* $new^{m-1}(x,y) = \\esists_yU^{m-1}(x,y)$*/\n\tCudd_RecursiveDeref(bdd,neW[m-1]);\n\tCudd_Ref(neW[m-1] = Cudd_bddExistAbstract(bdd, U[m-1], ycube));\n    }\n    if(pr>2){(void)fprintf(stdout,\"U[%d]\",m-1); Cudd_PrintDebug(bdd,U[m-1],n<<1,pr);}\n    if(pr>2){(void)fprintf(stdout,\"new[%d]\",m-1);\n\t\tCudd_PrintDebug(bdd,neW[m-1],n,pr);}\n\n    Cudd_RecursiveDeref(bdd,Uin);\n    Cudd_RecursiveDeref(bdd,Uout);\n\n    return;\n\n} /* end of trellis */\n\n\n/**\n  @brief Selects edges from a rhombus-type bilayer.\n\n  @details Used to pull flow.  Makes the left layer left-unique and\n  the right layer right-unique. Prunes and repeats until convergence\n  to a maximal flow. It makes sure that all intermediate points of the\n  two-arc paths are disjoint at each iteration.\n\n  @sideeffect None\n\n  @see trellis hourglass rhombusPush\n\n*/\nstatic void\nrhombus(\n  DdManager * bdd /**< %DD manager */,\n  int  m /**< center of current bilayer */,\n  DdNode ** neW /**< array for flow propagation */,\n  DdNode ** U /**< array for flow propagation */,\n  DdNode ** x /**< array of variables for rows and columns */,\n  DdNode ** y /**< array of variables for rows and columns */,\n  DdNode ** z /**< array of variables for rows and columns */,\n  int  n /**< number of x variables */,\n  DdNode * pryz /**< priority function */,\n  DdNode * prxz /**< priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *one, *zero,\n\t     *p, *q, *r,\n\t     *Uin,\t\t/* edges to be matched from U[m-1] */\n\t     *Uout,\t\t/* edges to be matched from U[m] */\n\t     *P,\n\t     *LU, *RU,\t\t/* left-unique and right-unique sets of edges */\n\t     *Ml, *Mr;\t\t/* nodes matched from left and right */\n    int      k,\n\t     pr;\t\t/* print control */\n\n    pr = stats->pr;\n\n    one = Cudd_ReadOne(bdd);\n    zero = Cudd_Not(one);\n\n    /*Uout(x,y)=U^m(x,y)*/\n    Cudd_Ref(Uout = U[m]);\n    if(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\n    /*Uin(x,y)=U^{m-1}(x,y)*/\n    Cudd_Ref(Uin = U[m-1]);\n    if(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n    for(k = 0; k < MAXFPIT; k++) {\n\tstats->fpit++;\n\t/*LU(x,y)=Uin(x,y)\\cdot\\overline{\\exists_{z}(Uin(z,y)\\cdot\\Pi(x,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Uin, x, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, prxz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(LU = Cudd_bddAnd(bdd, Uin, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tif(pr>3){(void)fprintf(stdout,\"LU\");Cudd_PrintDebug(bdd,LU,n<<1,pr);}\n\t/*Ml(y)=\\exists_{x}LU(x,y)*/\n\tCudd_Ref(Ml = Cudd_bddExistAbstract(bdd, LU, xcube));\n\tif(pr>3){(void)fprintf(stdout,\"Ml\");Cudd_PrintDebug(bdd,Ml,n,pr);}\n\t/*P(x,y)=Ml(x)\\cdot Uout(x,y)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Ml, x, y, n));\n\tCudd_Ref(P = Cudd_bddAnd(bdd, p, Uout));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,Ml);\n\tif(pr>3){(void)fprintf(stdout,\"P\");Cudd_PrintDebug(bdd,P,n<<1,pr);}\n\t/*RU(x,y)= P(x,y)\\cdot \\overline{\\exists_{z}(P(x,z)\\cdot \\Pi(y,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, P, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, pryz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(RU = Cudd_bddAnd(bdd, P, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,P);\n\tif(pr>3){(void)fprintf(stdout,\"RU\");Cudd_PrintDebug(bdd,RU,n<<1,pr);}\n\t/*Mr(x)=\\exists_{y}RU(x,y)*/\n\tCudd_Ref(Mr = Cudd_bddExistAbstract(bdd, RU, ycube));\n\tif(pr>3){(void)fprintf(stdout,\"Mr\");Cudd_PrintDebug(bdd,Mr,n,pr);}\n\t/*LU(x,y)=LU(x,y)\\cdot Mr(y)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Mr, x, y, n));\n\tCudd_RecursiveDeref(bdd,Mr);\n\tCudd_Ref(q = Cudd_bddAnd(bdd, LU, p));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,LU);\n\tLU = q;\n\tif(pr>3){(void)fprintf(stdout,\"LU\");Cudd_PrintDebug(bdd,LU,n<<1,pr);}\n\t/*Uin(x,y)=Uin(x,y)-LU(x,y)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, Uin, Cudd_Not(LU)));\n\tCudd_RecursiveDeref(bdd,Uin);\n\tUin = p;\n\tif(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\t/*Uout(x,y)=Uout(x,y)-RU(x,y)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, Uout, Cudd_Not(RU)));\n\tCudd_RecursiveDeref(bdd,Uout);\n\tCudd_RecursiveDeref(bdd,RU);\n\tUout = p;\n\tif(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\t/*\\KW{if}(($LU(x,y)=zero$)~~\\KW{or}~~($Uin(x,y)=zero$)~~\\KW{or}\n\t  ($Uout(x,y)=zero$))~~KW{break}*/\n\tif((LU == zero)||(Uin == zero)||(Uout == zero)) {\n\t    Cudd_RecursiveDeref(bdd,LU);\n\t    break;\n\t}\n\tCudd_RecursiveDeref(bdd,LU);\n\n    } /* Next least fixed point iteration with smaller Uin and Uout */\n    if (k == MAXFPIT) (void) fprintf(stderr,\n\t\"Rhombus: WARNING! MAXFPIT (%d) exceeded processing Layer %d.\\n\",\n\tMAXFPIT, m);\n\n    if (Uin != zero) {\n\t/* $U^{m-1}(x,y) = U^{m-1}(x,y)-Uin(x,y)$*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, U[m-1], Cudd_Not(Uin)));\n\tCudd_RecursiveDeref(bdd,U[m-1]);\n\tU[m-1] = p;\n\t/* $new^{m-1}(x,y) = \\esists_yU^{m-1}(x,y)$*/\n\tCudd_RecursiveDeref(bdd,neW[m-1]);\n\tCudd_Ref(neW[m-1] = Cudd_bddExistAbstract(bdd, U[m-1], ycube));\n    }\n    if(pr>2){(void)fprintf(stdout,\"U[%d]\",m-1); Cudd_PrintDebug(bdd,U[m-1],n<<1,pr);}\n    if(pr>2){\n\t(void)fprintf(stdout,\"new[%d]\",m-1);\n\tCudd_PrintDebug(bdd,neW[m-1],n,pr);\n    }\n    Cudd_RecursiveDeref(bdd,Uin);\n    Cudd_RecursiveDeref(bdd,Uout);\n\n    return;\n\n} /* end of rhombus */\n\n\n/**\n  @brief Selects edges from a hourglass-type bilayer.\n\n  @details Used to pull flow.  Method described in paper. More\n  general, but more expensive than the others.\n\n  @sideeffect None\n\n  @see trellis rhombus hourglassPush\n\n*/\nstatic void\nhourglass(\n  DdManager * bdd /**< %DD manager */,\n  int  m /**< center level of current bilayer */,\n  DdNode ** neW /**< array for flow propagation */,\n  DdNode ** U /**< array for flow propagation */,\n  DdNode ** x /**< array of variables for rows and columns */,\n  DdNode ** y /**< array of variables for rows and columns */,\n  DdNode ** z /**< array of variables for rows and columns */,\n  int  n /**< number of x variables */,\n  DdNode * pryz /**< priority function */,\n  DdNode * prxz /**< priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *one, *zero,\n\t     *przy,\n\t     *p, *q, *r,\n\t     *Uin,\t\t/* edges to be matched from U[m-1] */\n\t     *Uout,\t\t/* edges to be matched from U[m] */\n\t     *P, *Q,\n\t     *PA, *D;\n    int      k,\n\t     pr;\t\t/* print control */\n\n    pr = stats->pr;\n\n    one = Cudd_ReadOne(bdd);\n    zero = Cudd_Not(one);\n\n    /* Build priority function. */\n    Cudd_Ref(p = Cudd_bddSwapVariables(bdd, pryz, y, z, n));\n    Cudd_Ref(przy = Cudd_bddAdjPermuteX(bdd,p,x,n));\n    Cudd_RecursiveDeref(bdd,p);\n    if(pr>2){(void)fprintf(stdout,\"przy\");Cudd_PrintDebug(bdd,przy,n*3,pr);}\n\n    /*Uout(x,y)=U^m(x,y)*/\n    Cudd_Ref(Uout = U[m]);\n    if(pr>1){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\n    /*Uin(x,y)=U^{m-1}(x,y)*/\n    Cudd_Ref(Uin = U[m-1]);\n    if(pr>1){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n    for(k = 0; k < MAXFPIT; k++) {\n\tstats->fpit++;\n\t/*P(x,y,z)=Uin(x,y)\\cdot Uout(y,z)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Uout, y, z, n));\n\tif(pr>2){(void)fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n<<1,pr);}\n\tCudd_Ref(q = Cudd_bddSwapVariables(bdd, p, x, y, n));\n\tCudd_RecursiveDeref(bdd,p);\n\tif(pr>2){(void)fprintf(stdout,\"q\");Cudd_PrintDebug(bdd,q,n<<1,pr);}\n\tCudd_Ref(P = Cudd_bddAnd(bdd, Uin, q));\n\tCudd_RecursiveDeref(bdd,q);\n\tif(pr>1){(void)fprintf(stdout,\"P\");Cudd_PrintDebug(bdd,P,n*3,pr);}\n\t/*PA(x,z)=\\exists_yP(x,y,z)*/\n\tCudd_Ref(PA = Cudd_bddExistAbstract(bdd, P, ycube));\n\tif(pr>2){(void)fprintf(stdout,\"PA\");Cudd_PrintDebug(bdd,PA,n<<1,pr);}\n\tif(pr>3) {\n\t    Cudd_Ref(p = Cudd_bddExistAbstract(bdd, PA, xcube));\n\t    (void) fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n,pr);\n\t    Cudd_RecursiveDeref(bdd,p);\n\t    Cudd_Ref(p = Cudd_bddExistAbstract(bdd, PA, zcube));\n\t    (void) fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n,pr);\n\t    Cudd_RecursiveDeref(bdd,p);\n\t}\n\t/*Q(x,z)= PA(x,z)\\cdot \\overline{\\exists_{y}(PA(x,y)\\cdot \\Pi(z,y))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, PA, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, przy, ycube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(Q = Cudd_bddAnd(bdd, PA, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,PA);\n\tif(pr>2){(void)fprintf(stdout,\"Q\");Cudd_PrintDebug(bdd,Q,n<<1,pr);}\n\tif(pr>3) {\n\t    Cudd_Ref(p = Cudd_bddExistAbstract(bdd, Q, xcube));\n\t    (void) fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n,pr);\n\t    Cudd_RecursiveDeref(bdd,p);\n\t}\n\t/*D(x,z)= Q(x,z)\\cdot \\overline{\\exists_{y}(Q(y,z)\\cdot \\Pi(x,y))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Q, x, y, n));\n\tCudd_Ref(q = Cudd_bddSwapVariables(bdd, prxz, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, q, ycube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,q);\n\tCudd_Ref(D = Cudd_bddAnd(bdd, Q, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,Q);\n\tif(pr>1){(void)fprintf(stdout,\"D\");Cudd_PrintDebug(bdd,D,n<<1,pr);}\n\t/*P(x,y,z)=P(x,y,z)\\cdot D(x,z)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, P, D));\n\tCudd_RecursiveDeref(bdd,D);\n\tCudd_RecursiveDeref(bdd,P);\n\tP = p;\n\tif(pr>2){(void)fprintf(stdout,\"P\");Cudd_PrintDebug(bdd,P,n*3,pr);}\n\t/*Uin(x,y)=Uin(x,y)-\\exists_zP(x,y,z)*/\n\tCudd_Ref(p = Cudd_bddExistAbstract(bdd, P, zcube));\n\tif(pr>3){(void)fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n<<1,pr);}\n\tCudd_Ref(q = Cudd_bddAnd(bdd, Uin, Cudd_Not(p)));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,Uin);\n\tUin = q;\n\tif(pr>1){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\t/*Uout(x,y)=Uout(x,y)-\\exists_zP(z,x,y)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, P, x, y, n));\n\tif(pr>3){(void)fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n*3,pr);}\n\tCudd_Ref(r = Cudd_bddSwapVariables(bdd, p, y, z, n));\n\tCudd_RecursiveDeref(bdd,p);\n\tif(pr>3){(void)fprintf(stdout,\"r\");Cudd_PrintDebug(bdd,r,n*3,pr);}\n\tCudd_Ref(p = Cudd_bddExistAbstract(bdd, r, zcube));\n\tCudd_RecursiveDeref(bdd,r);\n\tif(pr>3){(void)fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n<<1,pr);}\n\tCudd_Ref(q = Cudd_bddAnd(bdd, Uout, Cudd_Not(p)));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,Uout);\n\tUout = q;\n\tif(pr>1){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\t/*\\KW{if}(($P(x,y,z)=zero$)~~\\KW{or}~~($Uin(x,y)=zero$)~~\\KW{or}\n\t  ($Uout(x,y)=zero$))~~KW{break}*/\n\tif((P == zero)||(Uin == zero)||(Uout == zero)) {\n\t    Cudd_RecursiveDeref(bdd,P);\n\t    break;\n\t}\n\tCudd_RecursiveDeref(bdd,P);\n\n    } /* Next least fixed point iteration with smaller P */\n    if (k == MAXFPIT) (void) fprintf(stderr,\n\t\"Hourglass: WARNING! MAXFPIT (%d) exceeded processing Layer %d.\\n\",\n\tMAXFPIT, m);\n\n    if (Uin != zero) {\n\t/* $U^{m-1}(x,y) = U^{m-1}(x,y)-Uin(x,y)$*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, U[m-1], Cudd_Not(Uin)));\n\tCudd_RecursiveDeref(bdd,U[m-1]);\n\tU[m-1] = p;\n\t/* $new^{m-1}(x,y) = \\esists_yU^{m-1}(x,y)$*/\n\tCudd_RecursiveDeref(bdd,neW[m-1]);\n\tCudd_Ref(neW[m-1] = Cudd_bddExistAbstract(bdd, U[m-1], ycube));\n    }\n    if(pr>1){(void)fprintf(stdout,\"U[%d]\",m-1); Cudd_PrintDebug(bdd,U[m-1],n<<1,pr);}\n    if(pr>1){(void)fprintf(stdout,\"new[%d]\",m-1);\n\t     Cudd_PrintDebug(bdd,neW[m-1],n,pr);}\n\n    Cudd_RecursiveDeref(bdd,Uin);\n    Cudd_RecursiveDeref(bdd,Uout);\n    Cudd_RecursiveDeref(bdd,przy);\n\n    return;\n\n} /* end of hourglass */\n\n\n/**\n  @brief Pushes flow through useful edges.\n\n  @details Pushes flow from the source(s) to the sink(s) through\n  useful edges.\n\n  @sideeffect None\n\n*/\nstatic void\nmaximal_push(\n  DdManager * bdd /**< %DD manager */,\n  int  l /**< Depth of layered network for current phase */,\n  DdNode ** U /**< array of edge sets for flow propagation */,\n  DdNode ** F /**< edge and flow relations */,\n  DdNode ** x /**< array of variables for rows and columns */,\n  DdNode ** y /**< array of variables for rows and columns */,\n  DdNode ** z /**< array of variables for rows and columns */,\n  int  n /**< number of x variables */,\n  DdNode * pryz /**< priority function */,\n  DdNode * prxz /**< priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *p, *q, *r,\n\t   *UT,\n\t   *lN, *cN, *rN; /* left, center, right nodes of bilayer */\n    double mtl, mtc, mtr;\n    int    m,\n\t   pr;\t  /* print control */\n\n    pr = stats->pr;\n\n    if (l == 0) {\n\t/* F(x,y) = F(x,y) + U^{0}(x,y) */\n\tCudd_Ref(q = Cudd_bddOr(bdd, *F, U[0]));\n\tCudd_RecursiveDeref(bdd,*F);\n\t*F = q;\n\tif(pr>3){(void) fprintf(stdout,\"F\");Cudd_PrintDebug(bdd,*F,n<<1,pr);}\n\treturn;\n    }\n\n    for (m = 1; m < l; m++) {\n\t/* lN(x) = \\exists_y U^{m-1}(x,y) */\n\tCudd_Ref(lN = Cudd_bddExistAbstract(bdd, U[m-1], ycube));\n\tmtl = Cudd_CountMinterm(bdd, lN, n);\n\tCudd_RecursiveDeref(bdd,lN);\n\n\t/* cN(y) = \\exists_x U^{m-1}(x,y) */\n\tCudd_Ref(cN = Cudd_bddExistAbstract(bdd, U[m-1], xcube));\n\tmtc = Cudd_CountMinterm(bdd, cN, n);\n\tCudd_RecursiveDeref(bdd,cN);\n\n\t/* rN(y) = \\exists_x U^{m}(x,y) */\n\tCudd_Ref(rN = Cudd_bddExistAbstract(bdd, U[m], xcube));\n\tmtr = Cudd_CountMinterm(bdd, rN, n);\n\tCudd_RecursiveDeref(bdd,rN);\n\n\tif (pr > 0) {\n\t    (void) fprintf(stdout, \"layer = %d mtl = %g  mtc = %g  mtr = %g\",\n\t\t\t   m, mtl, mtc, mtr);\n\t}\n\tif ((mtc > MANY_TIMES * mtl) && !(mtr > MANY_TIMES * mtl)) {\n\t    if (pr>0) (void) fprintf(stdout, \" R\\n\");\n\t    rhombusPush(bdd, m, U, x, y, z, n, pryz, prxz, stats);\n\t} else if (mtl > MANY_TIMES * mtc) {\n\t    if (pr>0) (void) fprintf(stdout, \" H\\n\");\n\t    hourglassPush(bdd, m, U, x, y, z, n, pryz, prxz, stats);\n\t} else {\n\t    if (pr>0) (void) fprintf(stdout, \" T\\n\");\n\t    trellisPush(bdd, m, U, x, y, z, n, pryz, prxz, stats);\n\t}\n\n\t/* F(x,y) = F(x,y) + U^{m-1}(x,y) \\cdot \\overline{F(y,x)} */\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, *F, x, y, n));\n\tCudd_Ref(q = Cudd_bddAnd(bdd, Cudd_Not(p), U[m-1]));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(r = Cudd_bddOr(bdd, *F, q));\n\tCudd_RecursiveDeref(bdd,q);\n\tCudd_RecursiveDeref(bdd,*F);\n\t*F = r;\n\tif(pr>3){(void) fprintf(stdout,\"F\");Cudd_PrintDebug(bdd,*F,n<<1,pr);}\n\n\t/* F(x,y) = F(x,y) - U^{m-1}(y,x) */\n\tCudd_Ref(r = Cudd_bddSwapVariables(bdd, U[m-1], x, y, n));\n\tCudd_Ref(q = Cudd_bddAnd(bdd, *F, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,*F);\n\t*F = q;\n\tif(pr>3){(void) fprintf(stdout,\"F\");Cudd_PrintDebug(bdd,*F,n<<1,pr);}\n\n    } /* Push maximal flow to next layer */\n\n    /*F(x,y)=F(x,y)+U^{l-1}(x,y)\\cdot\\overline{F(y,x)}*/\n    Cudd_Ref(p = Cudd_bddSwapVariables(bdd, *F, x, y, n));\n    Cudd_Ref(q = Cudd_bddAnd(bdd, Cudd_Not(p), U[l-1]));\n    Cudd_RecursiveDeref(bdd,p);\n    Cudd_Ref(r = Cudd_bddOr(bdd, *F, q));\n    Cudd_RecursiveDeref(bdd,q);\n    Cudd_RecursiveDeref(bdd,*F);\n    *F = r;\n    if(pr>3){(void) fprintf(stdout,\"F\");Cudd_PrintDebug(bdd,*F,n<<1,pr);}\n\n    /*F(y,x)=F(y,x)-U^{l-1}(x,y)*/\n    Cudd_Ref(r = Cudd_bddSwapVariables(bdd, U[l-1], x, y, n));\n    Cudd_Ref(q = Cudd_bddAnd(bdd, *F, Cudd_Not(r)));\n    Cudd_RecursiveDeref(bdd,r);\n    Cudd_RecursiveDeref(bdd,*F);\n    *F = q;\n    if(pr>1){(void) fprintf(stdout,\"F\");Cudd_PrintDebug(bdd,*F,n<<1,pr);}\n\n    /*UT(x,y)=\\exists_y(U^{l-1}(y,x))\\cdot U^{l}(x,y)*/\n    Cudd_Ref(p = Cudd_bddExistAbstract(bdd, U[l-1], xcube));\n    if(pr>4){(void) fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n,pr);}\n    Cudd_Ref(q = Cudd_bddSwapVariables(bdd, p, x, y, n));\n    Cudd_RecursiveDeref(bdd,p);\n    if(pr>4){(void) fprintf(stdout,\"q\");Cudd_PrintDebug(bdd,q,n,pr);}\n    Cudd_Ref(UT = Cudd_bddAnd(bdd, U[l], q));\n    Cudd_RecursiveDeref(bdd,q);\n    if(pr>2){(void) fprintf(stdout,\"UT\");Cudd_PrintDebug(bdd,UT,n<<1,pr);}\n\n    /*F(x,y)=F(x,y)+UT(x,y)\\cdot\\overline{F(y,x)}*/\n    Cudd_Ref(p = Cudd_bddSwapVariables(bdd, *F, x, y, n));\n    Cudd_Ref(q = Cudd_bddAnd(bdd, Cudd_Not(p), UT));\n    Cudd_RecursiveDeref(bdd,p);\n    Cudd_Ref(r = Cudd_bddOr(bdd, *F, q));\n    Cudd_RecursiveDeref(bdd,q);\n    Cudd_RecursiveDeref(bdd,*F);\n    *F = r;\n    if(pr>3){(void) fprintf(stdout,\"F\");Cudd_PrintDebug(bdd,*F,n<<1,pr);}\n\n    /*F(y,x)=F(y,x)-UT(x,y)*/\n    Cudd_Ref(r = Cudd_bddSwapVariables(bdd, UT, x, y, n));\n    Cudd_RecursiveDeref(bdd,UT);\n    Cudd_Ref(q = Cudd_bddAnd(bdd, *F, Cudd_Not(r)));\n    Cudd_RecursiveDeref(bdd,r);\n    Cudd_RecursiveDeref(bdd,*F);\n    *F = q;\n    if(pr>1){(void) fprintf(stdout,\"F\");Cudd_PrintDebug(bdd,*F,n<<1,pr);}\n\n    return;\n\n} /* end of maximal_push */\n\n\n/**\n  @brief Pushes flow through a trellis.\n\n  @sideeffect None\n\n*/\nstatic void\ntrellisPush(\n  DdManager * bdd /**< %DD manager */,\n  int  m /**< Current layer */,\n  DdNode ** U /**< Array of edge sets for flow propagation */,\n  DdNode ** x /**< Array of variables for rows and columns */,\n  DdNode ** y /**< Array of variables for rows and columns */,\n  DdNode ** z /**< Array of variables for rows and columns */,\n  int  n /**< Number of x variables */,\n  DdNode * pryz /**< Priority function */,\n  DdNode * prxz /**< Priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *one, *zero,\n\t     *p, *r,\n\t     *Uin,              /* Edges to be matched from U[m-1] */\n\t     *Uout,             /* Edges to be matched from U[m] */\n\t     *RU, *LU,\n\t     *P,\n\t     *Ml;\n\n    int      i,\n\t     pr;\t  /* Print control */\n\n    pr = stats->pr;\n\n    one = Cudd_ReadOne(bdd);\n    zero = Cudd_Not(one);\n\n    /*Uout(x,y)=U^m(x,y)*/\n    Cudd_Ref(Uout = U[m]);\n    if(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\n    /*Uin(x,y)=U^{m-1}(x,y)*/\n    Cudd_Ref(Uin = U[m-1]);\n    if(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n    for(i=0; i<MAXFPIT; i++) {\n\tstats->fpit++;\n\t/*LU(x,y)=Uin(x,y)\\cdot\\overline{\\exists_{z}(Uin(z,y)\\cdot\\Pi(x,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Uin, x, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, prxz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(LU = Cudd_bddAnd(bdd, Uin, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tif(pr>3){(void)fprintf(stdout,\"LU\");Cudd_PrintDebug(bdd,LU,n<<1,pr);}\n\n\t/*Ml(y)=\\exists_{x}LU(x,y)*/\n\tCudd_Ref(Ml = Cudd_bddExistAbstract(bdd, LU, xcube));\n\tif(pr>3){(void)fprintf(stdout,\"Ml\");Cudd_PrintDebug(bdd,Ml,n,pr);}\n\n\t/*P(x,y)=Ml(x)\\cdot Uout(x,y)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Ml, x, y, n));\n\tCudd_Ref(P = Cudd_bddAnd(bdd, p, Uout));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,Ml);\n\tif(pr>3){(void)fprintf(stdout,\"P\");Cudd_PrintDebug(bdd,P,n<<1,pr);}\n\n\t/*RU(x,y)= P(x,y)\\cdot \\overline{\\exists_{z}(P(x,z)\\cdot \\Pi(y,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, P, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, pryz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(RU = Cudd_bddAnd(bdd, P, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,P);\n\tif(pr>3){(void)fprintf(stdout,\"RU\");Cudd_PrintDebug(bdd,RU,n<<1,pr);}\n\n\t/*Uin(x,y)=Uin(x,y)-LU(x,y)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, Uin, Cudd_Not(LU)));\n\tCudd_RecursiveDeref(bdd,Uin);\n\tUin = p;\n\tif(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n\t/*Uout(x,y)=Uout(x,y)-RU(x,y)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, Uout, Cudd_Not(RU)));\n\tCudd_RecursiveDeref(bdd,Uout);\n\tCudd_RecursiveDeref(bdd,RU);\n\tUout = p;\n\tif(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\n\t/*\\KW{if}(($LU(x,y)=zero$)~~\\KW{or}~~($Uin(x,y)=zero$))~~KW{break}*/\n\tif((LU == zero)||(Uin == zero)) {\n\t    Cudd_RecursiveDeref(bdd,LU);\n\t    break;\n\t}\n\n\tCudd_RecursiveDeref(bdd,LU);\n\n    } /* Next least fixed point iteration with smaller Uin and Uout */\n    if (i == MAXFPIT) (void) fprintf(stderr,\n\t\"TrellisPush: ERROR! MAXFPIT (%d) exceeded at layer %d.\\n\",\n\tMAXFPIT, m);\n\n    /* $U^{m}(x,y) = U^{m}(x,y)-Uout(x,y)$*/\n    if (Uout != zero) {\n\tCudd_Ref(p = Cudd_bddAnd(bdd, U[m], Cudd_Not(Uout)));\n\tCudd_RecursiveDeref(bdd,U[m]);\n\tU[m] = p;\n\tif(pr>3){(void)fprintf(stdout,\"U[%d]\",m);\n\t    Cudd_PrintDebug(bdd,U[m],n<<1,pr);}\n    }\n\n    Cudd_RecursiveDeref(bdd,Uin);\n    Cudd_RecursiveDeref(bdd,Uout);\n\n} /* end of trellisPush */\n\n\n/**\n  @brief Pushes flow through a rhombus.\n\n  @sideeffect None\n\n*/\nstatic void\nrhombusPush(\n  DdManager * bdd /**< %DD manager */,\n  int  m /**< Current layer */,\n  DdNode ** U /**< Array of edge sets for flow propagation */,\n  DdNode ** x /**< Array of variables for rows and columns */,\n  DdNode ** y /**< Array of variables for rows and columns */,\n  DdNode ** z /**< Array of variables for rows and columns */,\n  int  n /**< Number of x variables */,\n  DdNode * pryz /**< Priority function */,\n  DdNode * prxz /**< Priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *one, *zero,\n\t     *p, *r,\n\t     *Uin,              /* Edges to be matched from U[m-1] */\n\t     *Uout,             /* Edges to be matched from U[m] */\n\t     *RU, *LU,\n\t     *P,\n\t     *Ml;\n\n    int      i,\n\t     pr;\t  /* Print control */\n\n    pr = stats->pr;\n\n    one = Cudd_ReadOne(bdd);\n    zero = Cudd_Not(one);\n\n    /*Uout(x,y)=U^m(x,y)*/\n    Cudd_Ref(Uout = U[m]);\n    if(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\n    /*Uin(x,y)=U^{m-1}(x,y)*/\n    Cudd_Ref(Uin = U[m-1]);\n    if(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n    for(i = 0; i < MAXFPIT; i++) {\n\tstats->fpit++;\n\t/*RU(x,y)=Uin(x,y)\\cdot\\overline{\\exists_{z}(Uin(x,z)\\cdot\\Pi(y,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Uin, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, pryz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(RU = Cudd_bddAnd(bdd, Uin, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tif(pr>3){(void)fprintf(stdout,\"RU\");Cudd_PrintDebug(bdd,RU,n<<1,pr);}\n\n\t/*Ml(y)=\\exists_{x}RU(x,y)*/\n\tCudd_Ref(Ml = Cudd_bddExistAbstract(bdd, RU, xcube));\n\tif(pr>3){(void)fprintf(stdout,\"Ml\");Cudd_PrintDebug(bdd,Ml,n,pr);}\n\n\t/*P(x,y)=Ml(x)\\cdot Uout(x,y)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Ml, x, y, n));\n\tCudd_Ref(P = Cudd_bddAnd(bdd, p, Uout));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,Ml);\n\tif(pr>3){(void)fprintf(stdout,\"P\");Cudd_PrintDebug(bdd,P,n<<1,pr);}\n\n\t/*LU(x,y)= P(x,y)\\cdot \\overline{\\exists_{z}(P(z,y)\\cdot \\Pi(x,z))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, P, x, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, prxz, zcube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(LU = Cudd_bddAnd(bdd, P, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,P);\n\tif(pr>3){(void)fprintf(stdout,\"LU\");Cudd_PrintDebug(bdd,LU,n<<1,pr);}\n\n\t/*Uin(x,y)=Uin(x,y)-RU(x,y)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, Uin, Cudd_Not(RU)));\n\tCudd_RecursiveDeref(bdd,Uin);\n\tUin = p;\n\tif(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n\t/*Uout(x,y)=Uout(x,y)-LU(x,y)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, Uout, Cudd_Not(LU)));\n\tCudd_RecursiveDeref(bdd,Uout);\n\tCudd_RecursiveDeref(bdd,LU);\n\tUout = p;\n\tif(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\n\t/*\\KW{if}(($RU(x,y)=zero$)~~\\KW{or}~~($Uin(x,y)=zero$))~~KW{break}*/\n\tif((RU == zero)||(Uin == zero)) {\n\t    Cudd_RecursiveDeref(bdd,RU);\n\t    break;\n\t}\n\n\tCudd_RecursiveDeref(bdd,RU);\n\n    } /* Next least fixed point iteration with smaller Uin and Uout */\n    if (i == MAXFPIT) (void) fprintf(stderr,\n\t\"RhombusPush: ERROR! MAXFPIT (%d) exceeded at layer %d.\\n\",\n\tMAXFPIT, m);\n\n    /* $U^{m}(x,y) = U^{m}(x,y)-Uout(x,y)$*/\n    if (Uout != zero) {\n\tCudd_Ref(p = Cudd_bddAnd(bdd, U[m], Cudd_Not(Uout)));\n\tCudd_RecursiveDeref(bdd,U[m]);\n\tU[m] = p;\n\tif(pr>3){(void)fprintf(stdout,\"U[%d]\",m);\n\t    Cudd_PrintDebug(bdd,U[m],n<<1,pr);}\n    }\n\n    Cudd_RecursiveDeref(bdd,Uin);\n    Cudd_RecursiveDeref(bdd,Uout);\n\n    return;\n\n} /* end of rhombusPush */\n\n\n/**\n  @brief Pushes flow through an hourglass.\n\n  @sideeffect None\n\n*/\nstatic void\nhourglassPush(\n  DdManager * bdd /**< %DD manager */,\n  int  m /**< Current layer */,\n  DdNode ** U /**< Array of edge sets for flow propagation */,\n  DdNode ** x /**< Array of variables for rows and columns */,\n  DdNode ** y /**< Array of variables for rows and columns */,\n  DdNode ** z /**< Array of variables for rows and columns */,\n  int  n /**< Number of x variables */,\n  DdNode * pryz /**< Priority function */,\n  DdNode * prxz /**< Priority function */,\n  flowStats * stats /**< statistics */)\n{\n    DdNode *one, *zero,\n\t     *przy,\n\t     *p, *q, *r,\n\t     *Uin,              /* Edges to be matched from U[m-1] */\n\t     *Uout,             /* Edges to be matched from U[m] */\n\t     *P, *Q,\n\t     *PA, *D;\n\n    int      i,\n\t     pr;\t  /* Print control */\n\n    pr = stats->pr;\n\n    one = Cudd_ReadOne(bdd);\n    zero = Cudd_Not(one);\n\n    /* Build priority function. */\n    Cudd_Ref(p = Cudd_bddSwapVariables(bdd, pryz, y, z, n));\n    Cudd_Ref(przy = Cudd_bddAdjPermuteX(bdd,p,x,n));\n    Cudd_RecursiveDeref(bdd,p);\n    if(pr>2){(void)fprintf(stdout,\"przy\");Cudd_PrintDebug(bdd,przy,n*3,pr);}\n\n    /*Uout(x,y)=U^m(x,y)*/\n    Cudd_Ref(Uout = U[m]);\n    if(pr>3){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\n    /*Uin(x,y)=U^{m-1}(x,y)*/\n    Cudd_Ref(Uin = U[m-1]);\n    if(pr>3){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n    for(i = 0; i < MAXFPIT; i++) {\n\tstats->fpit++;\n\t/*P(x,y,z)=Uin(x,y)\\cdot Uout(y,z)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Uout, y, z, n));\n\tif(pr>2){(void)fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n<<1,pr);}\n\tCudd_Ref(q = Cudd_bddSwapVariables(bdd, p, x, y, n));\n\tCudd_RecursiveDeref(bdd,p);\n\tif(pr>2){(void)fprintf(stdout,\"q\");Cudd_PrintDebug(bdd,q,n<<1,pr);}\n\tCudd_Ref(P = Cudd_bddAnd(bdd, Uin, q));\n\tCudd_RecursiveDeref(bdd,q);\n\tif(pr>1){(void)fprintf(stdout,\"P\");Cudd_PrintDebug(bdd,P,n*3,pr);}\n\n\t/*PA(x,z)=\\exists_yP(x,y,z)*/\n\tCudd_Ref(PA = Cudd_bddExistAbstract(bdd, P, ycube));\n\tif(pr>2){(void)fprintf(stdout,\"PA\");Cudd_PrintDebug(bdd,PA,n<<1,pr);}\n\tif(pr>3) {\n\t    Cudd_Ref(p = Cudd_bddExistAbstract(bdd, PA, xcube));\n\t    (void) fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n,pr);\n\t    Cudd_RecursiveDeref(bdd,p);\n\t    Cudd_Ref(p = Cudd_bddExistAbstract(bdd, PA, zcube));\n\t    (void) fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n,pr);\n\t    Cudd_RecursiveDeref(bdd,p);\n\t}\n\n\t/*Q(x,z)= PA(x,z)\\cdot \\overline{\\exists_{y}(PA(x,y)\\cdot \\Pi(z,y))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, PA, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, przy, ycube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_Ref(Q = Cudd_bddAnd(bdd, PA, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,PA);\n\tif(pr>2){(void)fprintf(stdout,\"Q\");Cudd_PrintDebug(bdd,Q,n<<1,pr);}\n\tif(pr>3) {\n\t    Cudd_Ref(p = Cudd_bddExistAbstract(bdd, Q, xcube));\n\t    (void) fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n,pr);\n\t    Cudd_RecursiveDeref(bdd,p);\n\t}\n\n\t/*D(x,z)= Q(x,z)\\cdot \\overline{\\exists_{y}(Q(y,z)\\cdot \\Pi(x,y))}*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, Q, x, y, n));\n\tCudd_Ref(q = Cudd_bddSwapVariables(bdd, prxz, y, z, n));\n\tCudd_Ref(r = Cudd_bddAndAbstract(bdd, p, q, ycube));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,q);\n\tCudd_Ref(D = Cudd_bddAnd(bdd, Q, Cudd_Not(r)));\n\tCudd_RecursiveDeref(bdd,r);\n\tCudd_RecursiveDeref(bdd,Q);\n\tif(pr>1){(void)fprintf(stdout,\"D\");Cudd_PrintDebug(bdd,D,n<<1,pr);}\n\n\t/*P(x,y,z)=P(x,y,z)\\cdot D(x,z)*/\n\tCudd_Ref(p = Cudd_bddAnd(bdd, P, D));\n\tCudd_RecursiveDeref(bdd,D);\n\tCudd_RecursiveDeref(bdd,P);\n\tP = p;\n\tif(pr>2){(void)fprintf(stdout,\"P\");Cudd_PrintDebug(bdd,P,n*3,pr);}\n\n\t/*Uin(x,y)=Uin(x,y)-\\exists_zP(x,y,z)*/\n\tCudd_Ref(p = Cudd_bddExistAbstract(bdd, P, zcube));\n\tif(pr>3){(void)fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n<<1,pr);}\n\tCudd_Ref(q = Cudd_bddAnd(bdd, Uin, Cudd_Not(p)));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,Uin);\n\tUin = q;\n\tif(pr>1){(void)fprintf(stdout,\"Uin\");Cudd_PrintDebug(bdd,Uin,n<<1,pr);}\n\n\t/*Uout(x,y)=Uout(x,y)-\\exists_zP(z,x,y)*/\n\tCudd_Ref(p = Cudd_bddSwapVariables(bdd, P, x, y, n));\n\tif(pr>3){(void)fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n*3,pr);}\n\tCudd_Ref(r = Cudd_bddSwapVariables(bdd, p, y, z, n));\n\tCudd_RecursiveDeref(bdd,p);\n\tif(pr>3){(void)fprintf(stdout,\"r\");Cudd_PrintDebug(bdd,r,n*3,pr);}\n\tCudd_Ref(p = Cudd_bddExistAbstract(bdd, r, zcube));\n\tCudd_RecursiveDeref(bdd,r);\n\tif(pr>3){(void)fprintf(stdout,\"p\");Cudd_PrintDebug(bdd,p,n<<1,pr);}\n\tCudd_Ref(q = Cudd_bddAnd(bdd, Uout, Cudd_Not(p)));\n\tCudd_RecursiveDeref(bdd,p);\n\tCudd_RecursiveDeref(bdd,Uout);\n\tUout = q;\n\tif(pr>1){(void)fprintf(stdout,\"Uout\");Cudd_PrintDebug(bdd,Uout,n<<1,pr);}\n\n\t/*\\KW{if}(($P(x,y,z)=zero$)~~\\KW{or}~~($Uin(x,y)=zero$)~~\\KW{or}\n\t  ($Uout(x,y)=zero$))~~KW{break}*/\n\tif((P == zero)||(Uin == zero)||(Uout == zero)) {\n\t    Cudd_RecursiveDeref(bdd,P);\n\t    break;\n\t}\n\n\tCudd_RecursiveDeref(bdd,P);\n\n    } /* Next least fixed point iteration with smaller P */\n    if (i == MAXFPIT) (void) fprintf(stderr,\n\t\"HourglassPush: ERROR! MAXFPIT (%d) exceeded at layer %d.\\n\",\n\tMAXFPIT, m);\n\n    /* $U^{m}(x,y) = U^{m}(x,y)-Uout(x,y)$*/\n    if (Uout != zero) {\n\tCudd_Ref(p = Cudd_bddAnd(bdd, U[m], Cudd_Not(Uout)));\n\tCudd_RecursiveDeref(bdd,U[m]);\n\tU[m] = p;\n    }\n    if(pr>1){(void)fprintf(stdout,\"U[%d]\",m); Cudd_PrintDebug(bdd,U[m],n<<1,pr);}\n\n    Cudd_RecursiveDeref(bdd,Uin);\n    Cudd_RecursiveDeref(bdd,Uout);\n    Cudd_RecursiveDeref(bdd,przy);\n\n    return;\n\n} /* end of hourglassPush */\n"
  },
  {
    "path": "cudd/nanotrav/ntrShort.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief Symbolic shortest paths algorithms.\n\n  @details This file contains the functions that implement the\n  symbolic version of several shortest path algorithms described in the\n  JFM paper on ADDs.\n\n  @author Fabio Somenzi, Iris Bahar\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"ntr.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic DdNode * ntrBellman (DdManager *dd, DdNode *D, DdNode *source, DdNode **x, DdNode **y, int vars, int pr);\nstatic DdNode * ntrWarshall (DdManager *dd, DdNode *D, DdNode **x, DdNode **y, int vars, int pr);\nstatic DdNode * ntrSquare (DdManager *dd, DdNode *D, DdNode **x, DdNode **y, DdNode **z, int vars, int pr, int st);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Computes shortest paths in a state graph.\n\n  @details Computes shortest paths in the state transition graph of\n  a network.  Three methods are availabe:\n  <ul>\n  <li> Bellman-Ford algorithm for single-source shortest paths; the\n  algorithm computes the distance (number of transitions) from the initial\n  states to all states.\n  <li> Floyd-Warshall algorithm for all-pair shortest paths.\n  <li> Repeated squaring algorithm for all-pair shortest paths.\n  </ul>\n\n  @return 1 in case of success; 0 otherwise.\n\n  @sideeffect %ADD variables are created in the manager.\n\n*/\nint\nNtr_ShortestPaths(\n  DdManager * dd,\n  BnetNetwork * net,\n  NtrOptions * option)\n{\n    NtrPartTR *TR;\n    DdNode *edges, *source, *res, *r, *q, *bddSource;\n    DdNode **xadd, **yadd, **zadd;\n    int i;\n    int pr = option->verb;\n    int algorithm = option->shortPath;\n    int selectiveTrace = option->selectiveTrace;\n    int nvars = net->nlatches;\n\n    /* Set background to infinity for shortest paths. */\n    Cudd_SetBackground(dd,Cudd_ReadPlusInfinity(dd));\n\n    /* Build the monolithic TR. */\n    TR = Ntr_buildTR(dd,net,option,NTR_IMAGE_MONO);\n\n    /* Build the ADD variable vectors for x and y. */\n    xadd = ALLOC(DdNode *, nvars);\n    yadd = ALLOC(DdNode *, nvars);\n    for(i = 0; i < nvars; i++) {\n\tq = Cudd_addIthVar(dd,TR->x[i]->index);\n\tCudd_Ref(q);\n\txadd[i] = q;\n\tq = Cudd_addIthVar(dd,TR->y[i]->index);\n\tCudd_Ref(q);\n\tyadd[i] = q;\n    }\n\n    /* Convert the transition relation BDD into an ADD... */\n    q = Cudd_BddToAdd(dd,TR->part[0]);\n    Cudd_Ref(q);\n    /* ...replacing zeroes with infinities... */\n    r = Cudd_addIte(dd,q,Cudd_ReadOne(dd),Cudd_ReadPlusInfinity(dd));\n    Cudd_Ref(r);\n    Cudd_RecursiveDeref(dd,q);\n    /* ...and zeroing the diagonal. */\n    q = Cudd_addXeqy(dd,nvars,xadd,yadd);\n    Cudd_Ref(q);\n    edges = Cudd_addIte(dd,q,Cudd_ReadZero(dd),r);\n    Cudd_Ref(edges);\n    Cudd_RecursiveDeref(dd,r);\n    Cudd_RecursiveDeref(dd,q);\n\n    switch(algorithm) {\n    case NTR_SHORT_BELLMAN:\n\tbddSource = Ntr_initState(dd,net,option);\n\tsource = Cudd_BddToAdd(dd,bddSource);\n\tCudd_Ref(source);\n\tres = ntrBellman(dd,edges,source,xadd,yadd,nvars,pr);\n\tif (res == NULL) return(0);\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(dd,source);\n\tCudd_RecursiveDeref(dd,bddSource);\n\tif (pr >= 0) {\n\t    (void) fprintf(stdout,\"Distance Matrix\");\n\t    Cudd_PrintDebug(dd,res,nvars,pr);\n\t}\n\tbreak;\n    case NTR_SHORT_FLOYD:\n\tres = ntrWarshall(dd,edges,xadd,yadd,nvars,pr);\n\tif (res == NULL) return(0);\n\tCudd_Ref(res);\n\tif (pr >= 0) {\n\t    (void) fprintf(stdout,\"Distance Matrix\");\n\t    Cudd_PrintDebug(dd,res,2*nvars,pr);\n\t}\n\tbreak;\n    case NTR_SHORT_SQUARE:\n\t/* Create a third set of ADD variables. */\n\tzadd = ALLOC(DdNode *, nvars);\n\tfor(i = 0; i < nvars; i++) {\n\t    int level;\n\t    level = Cudd_ReadIndex(dd,TR->x[i]->index);\n\t    q = Cudd_addNewVarAtLevel(dd,level);\n\t    Cudd_Ref(q);\n\t    zadd[i] = q;\n\t}\n\t/* Compute the shortest paths. */\n\tres = ntrSquare(dd,edges,zadd,yadd,xadd,nvars,pr,selectiveTrace);\n\tif (res == NULL) return(0);\n\tCudd_Ref(res);\n\t/* Dispose of the extra variables. */\n\tfor(i = 0; i < nvars; i++) {\n\t    Cudd_RecursiveDeref(dd,zadd[i]);\n\t}\n\tFREE(zadd);\n\tif (pr >= 0) {\n\t    (void) fprintf(stdout,\"Distance Matrix\");\n\t    Cudd_PrintDebug(dd,res,2*nvars,pr);\n\t}\n\tbreak;\n    default:\n\t(void) printf(\"Unrecognized method. Try again.\\n\");\n\treturn(0);\n    }\n\n    /* Here we should compute the paths. */\n\n    /* Clean up. */\n    Ntr_freeTR(dd,TR);\n    Cudd_RecursiveDeref(dd,edges);\n    Cudd_RecursiveDeref(dd,res);\n    for(i = 0; i < nvars; i++) {\n\tCudd_RecursiveDeref(dd,xadd[i]);\n\tCudd_RecursiveDeref(dd,yadd[i]);\n    }\n    FREE(xadd);\n    FREE(yadd);\n\n    if (option->autoDyn & 1) {\n\t(void) printf(\"Order after short path computation\\n\");\n\tif (!Bnet_PrintOrder(net,dd)) return(0);\n    }\n\n    return(1);\n\n} /* end of Ntr_ShortestPaths */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Bellman-Ford algorithm for single-source shortest paths.\n\n  @return the vector of the distances of all states from the initial\n  states.\n\n  @details In case of multiple initial states the distance for\n  each state is from the nearest initial state.  Negative-weight\n  cycles are detected, though only in the naive way.  (Lack of\n  convergence after nodes-1 iterations.)  In such a case, a constant\n  %ADD with value minus infinity is returned.  Bellman-Ford is based on\n  matrix-vector multiplication.  The matrix is the distance matrix\n  D(x,y), such that D(a,b) is the length of the arc connecting state a\n  to state b.  The vector V(x) stores the distances of all states from\n  the initial states.  The actual vector used in the matrix-vector\n  multiplication is diff(x), that holds those distances that have\n  changed during the last update.\n\n  @see ntrWarshall ntrSquare\n\n*/\nstatic DdNode *\nntrBellman(\n  DdManager *dd,\n  DdNode *D,\n  DdNode *source,\n  DdNode **x,\n  DdNode **y,\n  int vars,\n  int pr)\n{\n    DdNode *u, *w, *V, *min, *diff;\n    DdApaNumber i, nodes, one;\n    int digits = vars + 1;\n\n    /* To avoid overflow when there are many variables, use APA. */\n    nodes = Cudd_NewApaNumber(digits);\n    Cudd_ApaPowerOfTwo(digits,nodes,vars);\n    i = Cudd_NewApaNumber(digits);\n    one = Cudd_NewApaNumber(digits);\n    Cudd_ApaSetToLiteral(digits,one,1);\n\n#if 0\n    /* Find the distances from the initial state along paths using one\n    ** arc. */\n    w = Cudd_Cofactor(dd,D,source); /* works only if source is a cube */\n    Cudd_Ref(w);\n    V = Cudd_addSwapVariables(dd,w,x,y,vars);\n    Cudd_Ref(V);\n    Cudd_RecursiveDeref(dd,w);\n#endif\n\n    /* The initial states are at distance 0. The other states are\n    ** initially at infinite distance. */\n    V = Cudd_addIte(dd,source,Cudd_ReadZero(dd),Cudd_ReadPlusInfinity(dd));\n    Cudd_Ref(V);\n\n    /* Selective trace algorithm.  For the next update, only consider the\n    ** nodes whose distance has changed in the last update. */\n    diff = V;\n    Cudd_Ref(diff);\n\n    for (Cudd_ApaSetToLiteral(digits,i,1);\n\t Cudd_ApaCompare(digits,i,digits,nodes) < 0;\n\t Cudd_ApaAdd(digits,i,one,i)) {\n\tif (pr>2) {(void) printf(\"V\"); Cudd_PrintDebug(dd,V,vars,pr);}\n\t/* Compute the distances via triangulation as a function of x. */\n\tw = Cudd_addTriangle(dd,diff,D,x,vars);\n\tCudd_Ref(w);\n\tCudd_RecursiveDeref(dd,diff);\n\tu = Cudd_addSwapVariables(dd,w,x,y,vars);\n\tCudd_Ref(u);\n\tCudd_RecursiveDeref(dd,w);\n\tif (pr>2) {(void) printf(\"u\"); Cudd_PrintDebug(dd,u,vars,pr);}\n\n\t/* Take the minimum of the previous distances and those just\n\t** computed. */\n\tmin = Cudd_addApply(dd,Cudd_addMinimum,V,u);\n\tCudd_Ref(min);\n\tCudd_RecursiveDeref(dd,u);\n\tif (pr>2) {(void) printf(\"min\"); Cudd_PrintDebug(dd,min,vars,pr);}\n\n\tif (V == min) {\t\t/* convergence */\n\t    Cudd_RecursiveDeref(dd,min);\n\t    if (pr>0) {\n\t\t(void) printf(\"Terminating after \");\n\t\tCudd_ApaPrintDecimal(stdout,digits,i);\n\t\t(void) printf(\" iterations\\n\");\n\t    }\n\t    break;\n\t}\n\t/* Find the distances that decreased. */\n\tdiff = Cudd_addApply(dd,Cudd_addDiff,V,min);\n\tCudd_Ref(diff);\n\tif (pr>2) {(void) printf(\"diff\"); Cudd_PrintDebug(dd,diff,vars,pr);}\n\tCudd_RecursiveDeref(dd,V);\n\tV = min;\n    }\n    /* Negative cycle detection. */\n    if (Cudd_ApaCompare(digits,i,digits,nodes) == 0 &&\n\tdiff != Cudd_ReadPlusInfinity(dd)) {\n\t(void) printf(\"Negative cycle\\n\");\n\tCudd_RecursiveDeref(dd,diff);\n\tCudd_RecursiveDeref(dd,V);\n\tV = Cudd_ReadMinusInfinity(dd);\n\tCudd_Ref(V);\n    }\n\n    Cudd_Deref(V);\n    FREE(i);\n    FREE(nodes);\n    FREE(one);\n    return(V);\n\n} /* end of ntrBellman */\n\n\n/**\n  @brief Floyd-Warshall algorithm for all-pair shortest paths.\n*/\nstatic DdNode *\nntrWarshall(\n  DdManager *dd,\n  DdNode *D,\n  DdNode **x,\n  DdNode **y,\n  int vars,\n  int pr)\n{\n    DdNode *one, *zero;\n    DdNode *xminterm,  *w, *V, *V2;\n    DdNode *P, *R;\n    int i;\n    int nodes;\n    int k,u;\n    long start_time;\n    if (vars > 30)\n\tnodes = 1000000000;\n    else\n\tnodes = 1 << vars;\n\n    one = DD_ONE(dd);\n    zero = DD_ZERO(dd);\n    Cudd_Ref(R = D);                        /* make copy of original matrix */\n\n    /* Extract pivot row and column from D */\n    start_time = util_cpu_time();\n    for (k = 0; k < nodes; k++) {\n        if (k % 10000 == 0) {\n\t    (void) printf(\"Starting iteration  %d  at time %s\\n\",\n\t\t\t  k,util_print_time(util_cpu_time() - start_time));\n        }\n        Cudd_Ref(xminterm = one);\n        u = k;\n\tfor (i = vars-1; i >= 0; i--) {\n\t    if (u&1) {\n\t        Cudd_Ref(w = Cudd_addIte(dd,x[i],xminterm,zero));\n\t    } else {\n\t        Cudd_Ref(w = Cudd_addIte(dd,x[i],zero,xminterm));\n\t    }\n\t    Cudd_RecursiveDeref(dd,xminterm);\n\t    xminterm = w;\n\t    u >>= 1;\n\t}\n\n\tCudd_Ref(V = Cudd_Cofactor(dd,R,xminterm));\n\tCudd_RecursiveDeref(dd,xminterm);\n\tif (pr>2) {(void) printf(\"V\"); Cudd_PrintDebug(dd,V,vars,pr);}\n\n\n\tCudd_Ref(xminterm = one);\n\tu = k;\n\tfor (i = vars-1; i >= 0; i--) {\n\t    if (u&1) {\n\t        Cudd_Ref(w = Cudd_addIte(dd,y[i],xminterm,zero));\n\t    } else {\n\t        Cudd_Ref(w = Cudd_addIte(dd,y[i],zero,xminterm));\n\t    }\n\t    Cudd_RecursiveDeref(dd,xminterm);\n\t    xminterm = w;\n\t    u >>= 1;\n\t}\n\n\tCudd_Ref(V2 = Cudd_Cofactor(dd,R,xminterm));\n\tCudd_RecursiveDeref(dd,xminterm);\n\tif (pr>2) {(void) printf(\"V2\"); Cudd_PrintDebug(dd,V2,vars,pr);}\n\n\tCudd_Ref(P = Cudd_addOuterSum(dd,R,V,V2));\n\n\tCudd_RecursiveDeref(dd,V);\n\tCudd_RecursiveDeref(dd,V2);\n\tCudd_RecursiveDeref(dd,R);\n\tR = P;\n\tif (pr>2) {(void) printf(\"R\"); Cudd_PrintDebug(dd,R,vars,pr);}\n    }\n\n    Cudd_Deref(R);\n    return(R);\n\n} /* end of ntrWarshall */\n\n\n/**\n  @brief Repeated squaring algorithm for all-pairs shortest paths.\n*/\nstatic DdNode *\nntrSquare(\n  DdManager *dd /**< manager */,\n  DdNode *D /**< D(z,y): distance matrix */,\n  DdNode **x /**< array of x variables */,\n  DdNode **y /**< array of y variables */,\n  DdNode **z /**< array of z variables */,\n  int vars /**< number of variables in each of the three arrays */,\n  int pr /**< verbosity level */,\n  int st /**< use the selective trace algorithm */)\n{\n    DdNode *zero;\n    DdNode *I;              /* identity matirix */\n    DdNode *w, *V, *P, *M, *R, *RT;\n    DdNode *diff, *min, *minDiag;\n    int n;\n    int neg;\n    long start_time;\n\n    zero = Cudd_ReadZero(dd);\n    /* Make a working copy of the original matrix. */\n    R = D;\n    Cudd_Ref(R);\n    I = Cudd_addXeqy(dd,vars,z,y);    /* identity matrix */\n    Cudd_Ref(I);\n\n    /* Make a copy of the matrix for the selective trace algorithm. */\n    diff = R;\n    Cudd_Ref(diff);\n\n    start_time = util_cpu_time();\n    for (n = vars; n >= 0; n--) {\n\tprintf(\"Starting iteration %d at time %s\\n\",vars-n,\n\t       util_print_time(util_cpu_time() - start_time));\n\n\t/* Check for negative cycles: They are identified by negative\n\t** elements on the diagonal.\n\t*/\n\n\t/* Extract values from the diagonal. */\n        Cudd_Ref(w = Cudd_addIte(dd,I,R,zero));\n\tminDiag = Cudd_addFindMin(dd,w);\t/* no need to ref */\n\tneg = Cudd_V(minDiag) < 0;\n\tCudd_RecursiveDeref(dd,w);\n\tif (neg) {\n\t    Cudd_RecursiveDeref(dd,diff);\n            (void) printf(\"Negative cycle after %d iterations!\\n\",vars-n);\n            break;\n        }\n\n\t/* Prepare the first operand of matrix multiplication:\n\t**   diff(z,y) -> RT(x,y) -> V(x,z)\n\t*/\n\n\t/* RT(x,y) */\n\tCudd_Ref(RT = Cudd_addSwapVariables(dd,diff,x,z,vars));\n\tCudd_RecursiveDeref(dd,diff);\n\t/* V(x,z) */\n\tCudd_Ref(V = Cudd_addSwapVariables(dd,RT,y,z,vars));\n\tCudd_RecursiveDeref(dd,RT);\n\tif (pr > 0) {\n\t    double pathcount;\n\t    (void) printf(\"V\"); Cudd_PrintDebug(dd,V,2*vars,pr);\n\t    pathcount = Cudd_CountPath(V);\n\t    (void) printf(\"Path count = %g\\n\", pathcount);\n\t}\n\n\t/* V(x,z) * R(z,y) -> P(x,y) */\n\tCudd_Ref(P = Cudd_addTriangle(dd,V,R,z,vars));\n\tCudd_RecursiveDeref(dd,V);\n\t/* P(x,y) => M(z,y) */\n\tCudd_Ref(M = Cudd_addSwapVariables(dd,P,x,z,vars));\n\tCudd_RecursiveDeref(dd,P);\n\tif (pr>0) {(void) printf(\"M\"); Cudd_PrintDebug(dd,M,2*vars,pr);}\n\n\t/* min(z,y) */\n\tCudd_Ref(min = Cudd_addApply(dd,Cudd_addMinimum,R,M));\n\tCudd_RecursiveDeref(dd,M);\n\n\tif (R == min) {\n\t    Cudd_RecursiveDeref(dd,min);\n\t    if (pr>0) {printf(\"Done after %d iterations\\n\",vars-n+1); }\n\t    break;\n\t}\n\t/* diff(z,y) */\n\tif (st) {\n\t    Cudd_Ref(diff = Cudd_addApply(dd,Cudd_addDiff,min,R));\n\t} else {\n\t    Cudd_Ref(diff = min);\n\t}\n\tCudd_RecursiveDeref(dd,R);\n\tR = min;                  /* keep a copy of matrix at current iter. */\n\tif (pr > 0) {\n\t    double pathcount;\n\t    (void) printf(\"R\"); Cudd_PrintDebug(dd,R,2*vars,pr);\n\t    pathcount = Cudd_CountPath(R);\n\t    (void) printf(\"Path count = %g\\n\", pathcount);\n\t}\n\n\tif (n == 0) {\n\t    (void) printf(\"Negative cycle!\\n\");\n\t    break;\n\t}\n\n    }\n    Cudd_RecursiveDeref(dd,I);\n    Cudd_Deref(R);\n    return(R);\n\n} /* end of ntrSquare */\n"
  },
  {
    "path": "cudd/nanotrav/ntrZddTest.c",
    "content": "/**\n  @file\n\n  @ingroup nanotrav\n\n  @brief %ZDD test functions.\n\n  @author Fabio Somenzi\n   \n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"ntr.h\"\n#include \"cuddInt.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int reorderZdd (BnetNetwork *net, DdManager *dd, NtrOptions *option);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Tests ZDDs.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect Creates %ZDD variables in the manager.\n\n*/\nint\nNtr_testZDD(\n  DdManager * dd,\n  BnetNetwork * net,\n  NtrOptions * option)\n{\n    DdNode **zdd;\t\t/* array of converted outputs */\n    int nz;\t\t\t/* actual number of ZDDs */\n    int result;\n    int i, j;\n    BnetNode *node;\t\t/* auxiliary pointer to network node */\n    int pr = option->verb;\n    int level;\t\t\t/* aux. var. used to print variable orders */\n    char **names;\t\t/* array used to print variable orders */\n    int nvars;\n\n    /* Build an array of ZDDs for the output functions or for the\n    ** specified node. */\n    Cudd_AutodynDisable(dd);\n    Cudd_AutodynDisableZdd(dd);\n    zdd = ALLOC(DdNode *,net->noutputs);\n    result = Cudd_zddVarsFromBddVars(dd,1);\n    if (result == 0) return(0);\n    if (option->node == NULL) {\n\tfor (nz = 0; nz < net->noutputs; nz++) {\n\t    if (!st_lookup(net->hash,net->outputs[nz],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    zdd[nz] = Cudd_zddPortFromBdd(dd, node->dd);\n\t    if (zdd[nz]) {\n\t\tCudd_Ref(zdd[nz]);\n\t\t(void) printf(\"%s\", node->name);\n\t\tresult = Cudd_zddPrintDebug(dd,zdd[nz],Cudd_ReadZddSize(dd),pr);\n\t\tif (result == 0) return(0);\n\t    } else {\n\t\t(void) printf(\"Conversion to ZDD failed.\\n\");\n\t    }\n\t}\n    } else {\n\tif (!st_lookup(net->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tzdd[0] = Cudd_zddPortFromBdd(dd, node->dd);\n\tif (zdd[0]) {\n\t    Cudd_Ref(zdd[0]);\n\t    (void) printf(\"%s\", node->name);\n\t    result = Cudd_zddPrintDebug(dd,zdd[0],Cudd_ReadZddSize(dd),pr);\n\t    if (result == 0) return(0);\n\t} else {\n\t    (void) printf(\"Conversion to ZDD failed.\\n\");\n\t}\n\tnz = 1;\n    }\n\n#ifdef DD_DEBUG\n    result = Cudd_CheckKeys(dd);\n    if (result != 0) {\n\t(void) fprintf(stderr,\"Error reported by Cudd_CheckKeys\\n\");\n\treturn(0);\n    }\n#endif\n\n    if (option->autoDyn & 1) {\n\tCudd_AutodynEnable(dd,CUDD_REORDER_SAME);\n    }\n    if (option->autoDyn & 2) {\n\tCudd_AutodynEnableZdd(dd,CUDD_REORDER_SAME);\n    }\n\n    /* Convert the ZDDs back to BDDs and check identity. */\n    for (i = 0; i < nz; i++) {\n\tDdNode *checkBdd;\n\tcheckBdd = Cudd_zddPortToBdd(dd,zdd[i]);\n\tif (checkBdd) {\n\t    Cudd_Ref(checkBdd);\n\t    if (option->node == NULL) {\n\t\tif (!st_lookup(net->hash,net->outputs[i],(void **)&node)) {\n\t\t    return(0);\n\t\t}\n\t    } else {\n\t\tif (!st_lookup(net->hash,option->node,(void **)&node)) {\n\t\t    return(0);\n\t\t}\n\t    }\n\t    if (checkBdd != node->dd) {\n\t\t(void) fprintf(stdout,\"Equivalence failed at node %s\",\n\t\t\t       node->name);\n\t\tresult = Cudd_PrintDebug(dd,checkBdd,Cudd_ReadZddSize(dd),pr);\n\t\tif (result == 0) return(0);\n\t    }\n\t    Cudd_RecursiveDeref(dd,checkBdd);\n\t} else {\n\t    (void) printf(\"Conversion to BDD failed.\\n\");\n\t}\n    }\n\n#ifdef DD_DEBUG\n    result = Cudd_CheckKeys(dd);\n    if (result != 0) {\n\t(void) fprintf(stderr,\"Error reported by Cudd_CheckKeys\\n\");\n\treturn(0);\n    }\n#endif\n\n    /* Play with the ZDDs a little. */\n    if (nz > 2) {\n\tDdNode *f;\n\tDdNode *g1, *g2, *g;\n\tf = Cudd_zddIte(dd,zdd[0],zdd[1],zdd[2]);\n\tif (f == NULL) return(0);\n\tcuddRef(f);\n\tg1 = Cudd_zddIntersect(dd,zdd[0],zdd[1]);\n\tif (g1 == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd,f);\n\t    return(0);\n\t}\n\tcuddRef(g1);\n\tg2 = Cudd_zddDiff(dd,zdd[2],zdd[0]);\n\tif (g2 == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd,f);\n\t    Cudd_RecursiveDerefZdd(dd,g1);\n\t    return(0);\n\t}\n\tcuddRef(g2);\n\tg = Cudd_zddUnion(dd,g1,g2);\n\tif (g == NULL) {\n\t    Cudd_RecursiveDerefZdd(dd,f);\n\t    Cudd_RecursiveDerefZdd(dd,g1);\n\t    Cudd_RecursiveDerefZdd(dd,g2);\n\t    return(0);\n\t}\n\tcuddRef(g);\n\tCudd_RecursiveDerefZdd(dd,g1);\n\tCudd_RecursiveDerefZdd(dd,g2);\n\tif (g != f) {\n\t    (void) fprintf(stderr,\"f != g!\\n\");\n\t}\n\tCudd_RecursiveDerefZdd(dd,g);\n\tCudd_RecursiveDerefZdd(dd,f);\n    }\n\n#ifdef DD_DEBUG\n    result = Cudd_CheckKeys(dd);\n    if (result != 0) {\n\t(void) fprintf(stderr,\"Error reported by Cudd_CheckKeys\\n\");\n\treturn(0);\n    }\n#endif\n\n    /* Perform ZDD reordering. */\n    result = reorderZdd(net,dd,option);\n    if (result == 0) {\n\t(void) fprintf(stderr,\"Error during ZDD reordering\\n\");\n        return(0);\n    }\n\n    /* Print final ZDD order. */\n    nvars = Cudd_ReadZddSize(dd);\n    names = ALLOC(char *, nvars);\n    if (names == NULL) return(0);\n    for (i = 0; i < nvars; i++) {\n\tnames[i] = NULL;\n    }\n    if (option->reordering != CUDD_REORDER_NONE) {\n\tfor (i = 0; i < net->npis; i++) {\n\t    if (!st_lookup(net->hash,net->inputs[i],(void **)&node)) {\n\t\tFREE(names);\n\t\treturn(0);\n\t    }\n\t    level = Cudd_ReadPermZdd(dd,node->var);\n\t    names[level] = node->name;\n\t}\n\tfor (i = 0; i < net->nlatches; i++) {\n\t    if (!st_lookup(net->hash,net->latches[i][1],(void **)&node)) {\n\t\tFREE(names);\n\t\treturn(0);\n\t    }\n\t    level = Cudd_ReadPermZdd(dd,node->var);\n\t    names[level] = node->name;\n\t}\n\t(void) printf(\"New order\\n\");\n\tfor (i = 0, j = 0; i < nvars; i++) {\n\t    if (names[i] == NULL) continue;\n\t    if((j%8 == 0)&&j) (void) printf(\"\\n\");\n\t    (void) printf(\"%s \",names[i]);\n\t    j++;\n\t}\n\t(void) printf(\"\\n\");\n    }\n    FREE(names);\n\n    /* Dispose of ZDDs. */\n    for (i = 0; i < nz; i++) {\n\tCudd_RecursiveDerefZdd(dd,zdd[i]);\n    }\n    FREE(zdd);\n    return(1);\n\n} /* end of Ntr_testZDD */\n\n\n/**\n  @brief Builds %ZDD covers.\n\n  @sideeffect Creates %ZDD variables in the manager.\n\n*/\nint\nNtr_testISOP(\n  DdManager * dd,\n  BnetNetwork * net,\n  NtrOptions * option)\n{\n    DdNode **zdd;\t\t/* array of converted outputs */\n    DdNode *bdd;\t\t/* return value of Cudd_zddIsop */\n    int nz;\t\t\t/* actual number of ZDDs */\n    int result;\n    int i;\n    BnetNode *node;\t\t/* auxiliary pointer to network node */\n    int pr = option->verb;\n\n    /* Build an array of ZDDs for the output functions or the specified\n    ** node. */\n    Cudd_zddRealignEnable(dd);\n    Cudd_AutodynDisableZdd(dd);\n    zdd = ALLOC(DdNode *,net->noutputs);\n    result = Cudd_zddVarsFromBddVars(dd,2);\n    if (result == 0) return(0);\n    if (option->node == NULL) {\n\tnz = net->noutputs;\n\tfor (i = 0; i < nz; i++) {\n\t    if (!st_lookup(net->hash,net->outputs[i],(void **)&node)) {\n\t\treturn(0);\n\t    }\n\t    bdd = Cudd_zddIsop(dd, node->dd, node->dd, &zdd[i]);\n\t    if (bdd != node->dd) return(0);\n\t    Cudd_Ref(bdd);\n\t    Cudd_RecursiveDeref(dd,bdd);\n\t    if (zdd[i]) {\n\t\tCudd_Ref(zdd[i]);\n\t\t(void) printf(\"%s\", node->name);\n\t\tresult = Cudd_zddPrintDebug(dd,zdd[i],Cudd_ReadZddSize(dd),pr);\n\t\tif (result == 0) return(0);\n\t\tif (option->printcover) {\n\t\t    int *path;\n\t\t    DdGen *gen;\n\t\t    char *str = ALLOC(char,Cudd_ReadSize(dd)+1);\n\t\t    if (str == NULL) return(0);\n\t\t    (void) printf(\"Testing iterator on ZDD paths:\\n\");\n\t\t    Cudd_zddForeachPath(dd,zdd[i],gen,path) {\n\t\t\tstr = Cudd_zddCoverPathToString(dd,path,str);\n\t\t\t(void) printf(\"%s 1\\n\", str);\n\t\t    }\n\t\t    (void) printf(\"\\n\");\n\t\t    FREE(str);\n\t\t    result = Cudd_zddPrintCover(dd,zdd[i]);\n\n\t\t    if (result == 0) return(0);\n\t\t}\n\t    } else {\n\t\t(void) printf(\"Conversion to ISOP failed.\\n\");\n\t\treturn(0);\n\t    }\n\t}\n    } else {\n\tnz = 1;\n\tif (!st_lookup(net->hash,option->node,(void **)&node)) {\n\t    return(0);\n\t}\n\tbdd = Cudd_zddIsop(dd, node->dd, node->dd, &zdd[0]);\n\tif (bdd != node->dd) return(0);\n\tCudd_Ref(bdd);\n\tCudd_RecursiveDeref(dd,bdd);\n\tif (zdd[0]) {\n\t    Cudd_Ref(zdd[0]);\n\t    (void) printf(\"%s\", node->name);\n\t    result = Cudd_zddPrintDebug(dd,zdd[0],Cudd_ReadZddSize(dd),pr);\n\t    if (result == 0) return(0);\n\t    if (option->printcover) {\n\t\tint *path;\n\t\tDdGen *gen;\n\t\tchar *str = ALLOC(char,Cudd_ReadSize(dd)+1);\n\t\tif (str == NULL) return(0);\n\t\t(void) printf(\"Testing iterator on ZDD paths:\\n\");\n\t\tCudd_zddForeachPath(dd,zdd[0],gen,path) {\n\t\t    str = Cudd_zddCoverPathToString(dd,path,str);\n\t\t    (void) printf(\"%s 1\\n\", str);\n\t\t}\n\t\t(void) printf(\"\\n\");\n\t\tFREE(str);\n\n\t\tresult = Cudd_zddPrintCover(dd,zdd[0]);\n\t\tif (result == 0) return(0);\n\t    }\n\t} else {\n\t    (void) printf(\"Conversion to ISOP failed.\\n\");\n\t    return(0);\n\t}\n    }\n    if (option->autoDyn) {\n\tCudd_AutodynEnableZdd(dd,CUDD_REORDER_SAME);\n    }\n\n    /* Perform ZDD reordering. */\n    result = reorderZdd(net,dd,option);\n    if (result == 0) return(0);\n\n    /* Dispose of ZDDs. */\n    for (i = 0; i < nz; i++) {\n\tCudd_RecursiveDerefZdd(dd,zdd[i]);\n    }\n    FREE(zdd);\n\n    return(1);\n\n} /* end of Ntr_testISOP */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n\n/**\n  @brief Applies reordering to the ZDDs.\n\n  @details Explicitly applies reordering to the ZDDs.\n\n  @return 1 if successful; 0 otherwise.\n\n  @sideeffect None\n\n*/\nstatic int\nreorderZdd(\n  BnetNetwork * net /**< boolean network */,\n  DdManager * dd /**< DD Manager */,\n  NtrOptions * option /**< options */)\n{\n    int result;\t\t\t/* return value from functions */\n\n    /* Perform the final reordering. */\n    if (option->reordering != CUDD_REORDER_NONE) {\n\t(void) printf(\"Number of inputs = %d\\n\",net->ninputs);\n\n\tdd->siftMaxVar = 1000000; \n\tresult = Cudd_zddReduceHeap(dd,option->reordering,1);\n\tif (result == 0) return(0);\n\n\t/* Print symmetry stats if pertinent */\n\tif (option->reordering == CUDD_REORDER_SYMM_SIFT ||\n\t    option->reordering == CUDD_REORDER_SYMM_SIFT_CONV)\n\t    Cudd_zddSymmProfile(dd, 0, dd->sizeZ - 1);\n    }\n\n    return(1);\n\n} /* end of reorderZdd */\n\n"
  },
  {
    "path": "cudd/nanotrav/rcn25.blif",
    "content": ".model rcn25\n.outputs n0 n1 n2 n3 n4 n5 n6 n7 n8 n9 n10 n11 n12 n13 n14 n15 n16 n17 \\\nn18 n19 n20 n21 n22 n23 n24\n\n.latch nn0 n0 2\n.latch nn1 n1 2\n.latch nn2 n2 2\n.latch nn3 n3 2\n.latch nn4 n4 2\n.latch nn5 n5 2\n.latch nn6 n6 2\n.latch nn7 n7 2\n.latch nn8 n8 2\n.latch nn9 n9 2\n.latch nn10 n10 2\n.latch nn11 n11 2\n.latch nn12 n12 2\n.latch nn13 n13 2\n.latch nn14 n14 2\n.latch nn15 n15 2\n.latch nn16 n16 2\n.latch nn17 n17 2\n.latch nn18 n18 2\n.latch nn19 n19 2\n.latch nn20 n20 2\n.latch nn21 n21 2\n.latch nn22 n22 2\n.latch nn23 n23 2\n.latch nn24 n24 2\n\n.names n0 s0\n0 1\n.names n0 c1\n1 1\n.names n1 n0 c1 s1\n100 1\n010 1\n001 1\n111 1\n.names n1 n0 c1 c2\n11- 1\n1-1 1\n-11 1\n.names n2 n1 c2 s2\n100 1\n010 1\n001 1\n111 1\n.names n2 n1 c2 c3\n11- 1\n1-1 1\n-11 1\n.names n3 n2 c3 s3\n100 1\n010 1\n001 1\n111 1\n.names n3 n2 c3 c4\n11- 1\n1-1 1\n-11 1\n.names n4 n3 c4 s4\n100 1\n010 1\n001 1\n111 1\n.names n4 n3 c4 c5\n11- 1\n1-1 1\n-11 1\n.names n5 n4 c5 s5\n100 1\n010 1\n001 1\n111 1\n.names n5 n4 c5 c6\n11- 1\n1-1 1\n-11 1\n.names n6 n5 c6 s6\n100 1\n010 1\n001 1\n111 1\n.names n6 n5 c6 c7\n11- 1\n1-1 1\n-11 1\n.names n7 n6 c7 s7\n100 1\n010 1\n001 1\n111 1\n.names n7 n6 c7 c8\n11- 1\n1-1 1\n-11 1\n.names n8 n7 c8 s8\n100 1\n010 1\n001 1\n111 1\n.names n8 n7 c8 c9\n11- 1\n1-1 1\n-11 1\n.names n9 n8 c9 s9\n100 1\n010 1\n001 1\n111 1\n.names n9 n8 c9 c10\n11- 1\n1-1 1\n-11 1\n.names n10 n9 c10 s10\n100 1\n010 1\n001 1\n111 1\n.names n10 n9 c10 c11\n11- 1\n1-1 1\n-11 1\n.names n11 n10 c11 s11\n100 1\n010 1\n001 1\n111 1\n.names n11 n10 c11 c12\n11- 1\n1-1 1\n-11 1\n.names n12 n11 c12 s12\n100 1\n010 1\n001 1\n111 1\n.names n12 n11 c12 c13\n11- 1\n1-1 1\n-11 1\n.names n13 n12 c13 s13\n100 1\n010 1\n001 1\n111 1\n.names n13 n12 c13 c14\n11- 1\n1-1 1\n-11 1\n.names n14 n13 c14 s14\n100 1\n010 1\n001 1\n111 1\n.names n14 n13 c14 c15\n11- 1\n1-1 1\n-11 1\n.names n15 n14 c15 s15\n100 1\n010 1\n001 1\n111 1\n.names n15 n14 c15 c16\n11- 1\n1-1 1\n-11 1\n.names n16 n15 c16 s16\n100 1\n010 1\n001 1\n111 1\n.names n16 n15 c16 c17\n11- 1\n1-1 1\n-11 1\n.names n17 n16 c17 s17\n100 1\n010 1\n001 1\n111 1\n.names n17 n16 c17 c18\n11- 1\n1-1 1\n-11 1\n.names n18 n17 c18 s18\n100 1\n010 1\n001 1\n111 1\n.names n18 n17 c18 c19\n11- 1\n1-1 1\n-11 1\n.names n19 n18 c19 s19\n100 1\n010 1\n001 1\n111 1\n.names n19 n18 c19 c20\n11- 1\n1-1 1\n-11 1\n.names n20 n19 c20 s20\n100 1\n010 1\n001 1\n111 1\n.names n20 n19 c20 c21\n11- 1\n1-1 1\n-11 1\n.names n21 n20 c21 s21\n100 1\n010 1\n001 1\n111 1\n.names n21 n20 c21 c22\n11- 1\n1-1 1\n-11 1\n.names n22 n21 c22 s22\n100 1\n010 1\n001 1\n111 1\n.names n22 n21 c22 c23\n11- 1\n1-1 1\n-11 1\n.names n23 n22 c23 s23\n100 1\n010 1\n001 1\n111 1\n.names n23 n22 c23 c24\n11- 1\n1-1 1\n-11 1\n.names n24 n23 c24 s24\n100 1\n010 1\n001 1\n111 1\n.names n24 n23 c24 c25\n11- 1\n1-1 1\n-11 1\n.names n24 c25 s25\n10 1\n01 1\n.names n24 c25 s26\n11 1\n\n.names s25 s26 of\n00 0\n\n.names n0 of s0 n1 nn0\n101- 1\n0--1 1\n.names n0 of s1 n2 nn1\n101- 1\n0--1 1\n.names n0 of s2 n3 nn2\n101- 1\n0--1 1\n.names n0 of s3 n4 nn3\n101- 1\n0--1 1\n.names n0 of s4 n5 nn4\n101- 1\n0--1 1\n.names n0 of s5 n6 nn5\n101- 1\n0--1 1\n.names n0 of s6 n7 nn6\n101- 1\n0--1 1\n.names n0 of s7 n8 nn7\n101- 1\n0--1 1\n.names n0 of s8 n9 nn8\n101- 1\n0--1 1\n.names n0 of s9 n10 nn9\n101- 1\n0--1 1\n.names n0 of s10 n11 nn10\n101- 1\n0--1 1\n.names n0 of s11 n12 nn11\n101- 1\n0--1 1\n.names n0 of s12 n13 nn12\n101- 1\n0--1 1\n.names n0 of s13 n14 nn13\n101- 1\n0--1 1\n.names n0 of s14 n15 nn14\n101- 1\n0--1 1\n.names n0 of s15 n16 nn15\n101- 1\n0--1 1\n.names n0 of s16 n17 nn16\n101- 1\n0--1 1\n.names n0 of s17 n18 nn17\n101- 1\n0--1 1\n.names n0 of s18 n19 nn18\n101- 1\n0--1 1\n.names n0 of s19 n20 nn19\n101- 1\n0--1 1\n.names n0 of s20 n21 nn20\n101- 1\n0--1 1\n.names n0 of s21 n22 nn21\n101- 1\n0--1 1\n.names n0 of s22 n23 nn22\n101- 1\n0--1 1\n.names n0 of s23 n24 nn23\n101- 1\n0--1 1\n.names n0 of s24 nn24\n101 1\n\n.end\n"
  },
  {
    "path": "cudd/nanotrav/rcn25.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -envelope ./nanotrav/rcn25.blif\n# CUDD Version 3.0.0\nOrder before final reordering\nn0 n1 n2 n3 n4 n5 n6 n7 \nn8 n9 n10 n11 n12 n13 n14 n15 \nn16 n17 n18 n19 n20 n21 n22 n23 \nn24 \nNumber of inputs = 25\n@@@@@@@@@@@@@@@@@@@@@@@@@\nS0: 1 nodes 1 leaves 3.35544e+07 minterms\nEnvelope[1]: 68 nodes 1 leaves 1.95734e+07 minterms\nEnvelope[2]: 131 nodes 1 leaves 1.53791e+07 minterms\nEnvelope[3]: 240 nodes 1 leaves 1.30489e+07 minterms\nEnvelope[4]: 351 nodes 1 leaves 1.07188e+07 minterms\nEnvelope[5]: 365 nodes 1 leaves 9.08766e+06 minterms\nEnvelope[6]: 672 nodes 1 leaves 7.88374e+06 minterms\nEnvelope[7]: 977 nodes 1 leaves 6.85458e+06 minterms\nEnvelope[8]: 1697 nodes 1 leaves 6.16039e+06 minterms\nEnvelope[9]: 2507 nodes 1 leaves 5.53173e+06 minterms\nEnvelope[10]: 2728 nodes 1 leaves 4.99328e+06 minterms\nEnvelope[11]: 4877 nodes 1 leaves 4.56022e+06 minterms\nEnvelope[12]: 7131 nodes 1 leaves 4.15173e+06 minterms\nEnvelope[13]: 10837 nodes 1 leaves 3.83181e+06 minterms\nEnvelope[14]: 16376 nodes 1 leaves 3.53694e+06 minterms\nEnvelope[15]: 18686 nodes 1 leaves 3.26485e+06 minterms\nEnvelope[16]: 27175 nodes 1 leaves 3.03016e+06 minterms\nEnvelope[17]: 37624 nodes 1 leaves 2.81134e+06 minterms\nEnvelope[18]: 42091 nodes 1 leaves 2.62598e+06 minterms\nEnvelope[19]: 64761 nodes 1 leaves 2.45532e+06 minterms\nEnvelope[20]: 88199 nodes 1 leaves 2.29512e+06 minterms\nEnvelope[21]: 112012 nodes 1 leaves 2.15501e+06 minterms\nEnvelope[22]: 148131 nodes 1 leaves 2.02284e+06 minterms\nEnvelope[23]: 178957 nodes 1 leaves 1.90343e+06 minterms\nEnvelope[24]: 213207 nodes 1 leaves 1.79426e+06 minterms\nEnvelope[25]: 251015 nodes 1 leaves 1.69064e+06 minterms\nEnvelope[26]: 278969 nodes 1 leaves 1.59836e+06 minterms\nEnvelope[27]: 298983 nodes 1 leaves 1.51117e+06 minterms\nEnvelope[28]: 310186 nodes 1 leaves 1.4295e+06 minterms\nEnvelope[29]: 314312 nodes 1 leaves 1.35474e+06 minterms\nEnvelope[30]: 312346 nodes 1 leaves 1.2838e+06 minterms\nEnvelope[31]: 308909 nodes 1 leaves 1.21948e+06 minterms\nEnvelope[32]: 304183 nodes 1 leaves 1.15867e+06 minterms\nEnvelope[33]: 298541 nodes 1 leaves 1.10083e+06 minterms\nEnvelope[34]: 292868 nodes 1 leaves 1.04754e+06 minterms\nEnvelope[35]: 286698 nodes 1 leaves 996946 minterms\nEnvelope[36]: 280610 nodes 1 leaves 949953 minterms\nEnvelope[37]: 274275 nodes 1 leaves 905778 minterms\nEnvelope[38]: 267711 nodes 1 leaves 863616 minterms\nEnvelope[39]: 261513 nodes 1 leaves 824606 minterms\nEnvelope[40]: 255196 nodes 1 leaves 787378 minterms\nEnvelope[41]: 248890 nodes 1 leaves 752197 minterms\nEnvelope[42]: 242617 nodes 1 leaves 719152 minterms\nEnvelope[43]: 236080 nodes 1 leaves 687560 minterms\nEnvelope[44]: 230130 nodes 1 leaves 658155 minterms\nEnvelope[45]: 224259 nodes 1 leaves 629967 minterms\nEnvelope[46]: 218166 nodes 1 leaves 603079 minterms\nEnvelope[47]: 212397 nodes 1 leaves 577815 minterms\nEnvelope[48]: 206597 nodes 1 leaves 553658 minterms\nEnvelope[49]: 201169 nodes 1 leaves 531033 minterms\nEnvelope[50]: 195784 nodes 1 leaves 509531 minterms\nEnvelope[51]: 190388 nodes 1 leaves 488904 minterms\nEnvelope[52]: 185402 nodes 1 leaves 469490 minterms\nEnvelope[53]: 180396 nodes 1 leaves 450891 minterms\nEnvelope[54]: 175724 nodes 1 leaves 433247 minterms\nEnvelope[55]: 171253 nodes 1 leaves 416458 minterms\nEnvelope[56]: 166524 nodes 1 leaves 400345 minterms\nEnvelope[57]: 162304 nodes 1 leaves 385129 minterms\nEnvelope[58]: 158158 nodes 1 leaves 370518 minterms\nEnvelope[59]: 154136 nodes 1 leaves 356541 minterms\nEnvelope[60]: 150218 nodes 1 leaves 343262 minterms\nEnvelope[61]: 146293 nodes 1 leaves 330504 minterms\nEnvelope[62]: 142731 nodes 1 leaves 318444 minterms\nEnvelope[63]: 139152 nodes 1 leaves 306873 minterms\nEnvelope[64]: 135570 nodes 1 leaves 295766 minterms\nEnvelope[65]: 132114 nodes 1 leaves 285183 minterms\nEnvelope[66]: 128777 nodes 1 leaves 275032 minterms\nEnvelope[67]: 125644 nodes 1 leaves 265348 minterms\nEnvelope[68]: 122532 nodes 1 leaves 256089 minterms\nEnvelope[69]: 119388 nodes 1 leaves 247191 minterms\nEnvelope[70]: 116557 nodes 1 leaves 238707 minterms\nEnvelope[71]: 113576 nodes 1 leaves 230531 minterms\nEnvelope[72]: 110737 nodes 1 leaves 222700 minterms\nEnvelope[73]: 107964 nodes 1 leaves 215170 minterms\nEnvelope[74]: 105272 nodes 1 leaves 207896 minterms\nEnvelope[75]: 102720 nodes 1 leaves 200935 minterms\nEnvelope[76]: 100098 nodes 1 leaves 194214 minterms\nEnvelope[77]: 97630 nodes 1 leaves 187719 minterms\nEnvelope[78]: 95248 nodes 1 leaves 181488 minterms\nEnvelope[79]: 92891 nodes 1 leaves 175479 minterms\nEnvelope[80]: 90738 nodes 1 leaves 169733 minterms\nEnvelope[81]: 88566 nodes 1 leaves 164201 minterms\nEnvelope[82]: 86372 nodes 1 leaves 158855 minterms\nEnvelope[83]: 84200 nodes 1 leaves 153722 minterms\nEnvelope[84]: 82108 nodes 1 leaves 148752 minterms\nEnvelope[85]: 80162 nodes 1 leaves 143977 minterms\nEnvelope[86]: 78254 nodes 1 leaves 139369 minterms\nEnvelope[87]: 76349 nodes 1 leaves 134921 minterms\nEnvelope[88]: 74645 nodes 1 leaves 130668 minterms\nEnvelope[89]: 72849 nodes 1 leaves 126558 minterms\nEnvelope[90]: 71140 nodes 1 leaves 122588 minterms\nEnvelope[91]: 69484 nodes 1 leaves 118779 minterms\nEnvelope[92]: 67898 nodes 1 leaves 115076 minterms\nEnvelope[93]: 66429 nodes 1 leaves 111539 minterms\nEnvelope[94]: 64879 nodes 1 leaves 108113 minterms\nEnvelope[95]: 63332 nodes 1 leaves 104807 minterms\nEnvelope[96]: 61892 nodes 1 leaves 101634 minterms\nEnvelope[97]: 60487 nodes 1 leaves 98554 minterms\nEnvelope[98]: 59076 nodes 1 leaves 95579 minterms\nEnvelope[99]: 57675 nodes 1 leaves 92712 minterms\nEnvelope[100]: 56346 nodes 1 leaves 89943 minterms\nEnvelope[101]: 55101 nodes 1 leaves 87270 minterms\nEnvelope[102]: 53857 nodes 1 leaves 84669 minterms\nEnvelope[103]: 52673 nodes 1 leaves 82155 minterms\nEnvelope[104]: 51498 nodes 1 leaves 79722 minterms\nEnvelope[105]: 50375 nodes 1 leaves 77355 minterms\nEnvelope[106]: 49253 nodes 1 leaves 75077 minterms\nEnvelope[107]: 48157 nodes 1 leaves 72867 minterms\nEnvelope[108]: 47096 nodes 1 leaves 70729 minterms\nEnvelope[109]: 46100 nodes 1 leaves 68652 minterms\nEnvelope[110]: 45047 nodes 1 leaves 66635 minterms\nEnvelope[111]: 44107 nodes 1 leaves 64689 minterms\nEnvelope[112]: 43198 nodes 1 leaves 62806 minterms\nEnvelope[113]: 42227 nodes 1 leaves 60981 minterms\nEnvelope[114]: 41297 nodes 1 leaves 59228 minterms\nEnvelope[115]: 40371 nodes 1 leaves 57524 minterms\nEnvelope[116]: 39479 nodes 1 leaves 55874 minterms\nEnvelope[117]: 38623 nodes 1 leaves 54279 minterms\nEnvelope[118]: 37792 nodes 1 leaves 52739 minterms\nEnvelope[119]: 37000 nodes 1 leaves 51264 minterms\nEnvelope[120]: 36185 nodes 1 leaves 49837 minterms\nEnvelope[121]: 35400 nodes 1 leaves 48443 minterms\nEnvelope[122]: 34580 nodes 1 leaves 47093 minterms\nEnvelope[123]: 33793 nodes 1 leaves 45782 minterms\nEnvelope[124]: 33084 nodes 1 leaves 44519 minterms\nEnvelope[125]: 32388 nodes 1 leaves 43292 minterms\nEnvelope[126]: 31710 nodes 1 leaves 42089 minterms\nEnvelope[127]: 31025 nodes 1 leaves 40920 minterms\nEnvelope[128]: 30350 nodes 1 leaves 39778 minterms\nEnvelope[129]: 29683 nodes 1 leaves 38664 minterms\nEnvelope[130]: 29050 nodes 1 leaves 37589 minterms\nEnvelope[131]: 28418 nodes 1 leaves 36551 minterms\nEnvelope[132]: 27804 nodes 1 leaves 35547 minterms\nEnvelope[133]: 27184 nodes 1 leaves 34573 minterms\nEnvelope[134]: 26621 nodes 1 leaves 33636 minterms\nEnvelope[135]: 26074 nodes 1 leaves 32724 minterms\nEnvelope[136]: 25528 nodes 1 leaves 31831 minterms\nEnvelope[137]: 24996 nodes 1 leaves 30967 minterms\nEnvelope[138]: 24472 nodes 1 leaves 30133 minterms\nEnvelope[139]: 23993 nodes 1 leaves 29324 minterms\nEnvelope[140]: 23514 nodes 1 leaves 28535 minterms\nEnvelope[141]: 23008 nodes 1 leaves 27769 minterms\nEnvelope[142]: 22525 nodes 1 leaves 27029 minterms\nEnvelope[143]: 22039 nodes 1 leaves 26318 minterms\nEnvelope[144]: 21561 nodes 1 leaves 25624 minterms\nEnvelope[145]: 21094 nodes 1 leaves 24950 minterms\nEnvelope[146]: 20685 nodes 1 leaves 24289 minterms\nEnvelope[147]: 20249 nodes 1 leaves 23651 minterms\nEnvelope[148]: 19794 nodes 1 leaves 23023 minterms\nEnvelope[149]: 19369 nodes 1 leaves 22418 minterms\nEnvelope[150]: 18976 nodes 1 leaves 21837 minterms\nEnvelope[151]: 18589 nodes 1 leaves 21272 minterms\nEnvelope[152]: 18201 nodes 1 leaves 20723 minterms\nEnvelope[153]: 17806 nodes 1 leaves 20198 minterms\nEnvelope[154]: 17419 nodes 1 leaves 19684 minterms\nEnvelope[155]: 17049 nodes 1 leaves 19180 minterms\nEnvelope[156]: 16672 nodes 1 leaves 18691 minterms\nEnvelope[157]: 16315 nodes 1 leaves 18214 minterms\nEnvelope[158]: 16005 nodes 1 leaves 17741 minterms\nEnvelope[159]: 15679 nodes 1 leaves 17284 minterms\nEnvelope[160]: 15341 nodes 1 leaves 16836 minterms\nEnvelope[161]: 14999 nodes 1 leaves 16397 minterms\nEnvelope[162]: 14667 nodes 1 leaves 15962 minterms\nEnvelope[163]: 14365 nodes 1 leaves 15544 minterms\nEnvelope[164]: 14066 nodes 1 leaves 15138 minterms\nEnvelope[165]: 13792 nodes 1 leaves 14743 minterms\nEnvelope[166]: 13539 nodes 1 leaves 14361 minterms\nEnvelope[167]: 13283 nodes 1 leaves 13992 minterms\nEnvelope[168]: 13022 nodes 1 leaves 13632 minterms\nEnvelope[169]: 12765 nodes 1 leaves 13280 minterms\nEnvelope[170]: 12497 nodes 1 leaves 12938 minterms\nEnvelope[171]: 12257 nodes 1 leaves 12605 minterms\nEnvelope[172]: 11990 nodes 1 leaves 12279 minterms\nEnvelope[173]: 11716 nodes 1 leaves 11958 minterms\nEnvelope[174]: 11436 nodes 1 leaves 11646 minterms\nEnvelope[175]: 11180 nodes 1 leaves 11345 minterms\nEnvelope[176]: 10939 nodes 1 leaves 11056 minterms\nEnvelope[177]: 10717 nodes 1 leaves 10771 minterms\nEnvelope[178]: 10488 nodes 1 leaves 10493 minterms\nEnvelope[179]: 10255 nodes 1 leaves 10221 minterms\nEnvelope[180]: 10013 nodes 1 leaves 9957 minterms\nEnvelope[181]: 9810 nodes 1 leaves 9699 minterms\nEnvelope[182]: 9568 nodes 1 leaves 9449 minterms\nEnvelope[183]: 9355 nodes 1 leaves 9206 minterms\nEnvelope[184]: 9176 nodes 1 leaves 8967 minterms\nEnvelope[185]: 8990 nodes 1 leaves 8733 minterms\nEnvelope[186]: 8810 nodes 1 leaves 8512 minterms\nEnvelope[187]: 8621 nodes 1 leaves 8297 minterms\nEnvelope[188]: 8421 nodes 1 leaves 8091 minterms\nEnvelope[189]: 8200 nodes 1 leaves 7895 minterms\nEnvelope[190]: 7992 nodes 1 leaves 7705 minterms\nEnvelope[191]: 7816 nodes 1 leaves 7519 minterms\nEnvelope[192]: 7641 nodes 1 leaves 7338 minterms\nEnvelope[193]: 7475 nodes 1 leaves 7161 minterms\nEnvelope[194]: 7307 nodes 1 leaves 6986 minterms\nEnvelope[195]: 7137 nodes 1 leaves 6814 minterms\nEnvelope[196]: 6956 nodes 1 leaves 6644 minterms\nEnvelope[197]: 6784 nodes 1 leaves 6477 minterms\nEnvelope[198]: 6642 nodes 1 leaves 6315 minterms\nEnvelope[199]: 6515 nodes 1 leaves 6157 minterms\nEnvelope[200]: 6377 nodes 1 leaves 6000 minterms\nEnvelope[201]: 6221 nodes 1 leaves 5847 minterms\nEnvelope[202]: 6069 nodes 1 leaves 5699 minterms\nEnvelope[203]: 5919 nodes 1 leaves 5555 minterms\nEnvelope[204]: 5797 nodes 1 leaves 5417 minterms\nEnvelope[205]: 5662 nodes 1 leaves 5282 minterms\nEnvelope[206]: 5535 nodes 1 leaves 5149 minterms\nEnvelope[207]: 5414 nodes 1 leaves 5018 minterms\nEnvelope[208]: 5293 nodes 1 leaves 4890 minterms\nEnvelope[209]: 5170 nodes 1 leaves 4765 minterms\nEnvelope[210]: 5057 nodes 1 leaves 4644 minterms\nEnvelope[211]: 4948 nodes 1 leaves 4526 minterms\nEnvelope[212]: 4856 nodes 1 leaves 4410 minterms\nEnvelope[213]: 4763 nodes 1 leaves 4296 minterms\nEnvelope[214]: 4651 nodes 1 leaves 4183 minterms\nEnvelope[215]: 4568 nodes 1 leaves 4076 minterms\nEnvelope[216]: 4488 nodes 1 leaves 3972 minterms\nEnvelope[217]: 4406 nodes 1 leaves 3869 minterms\nEnvelope[218]: 4322 nodes 1 leaves 3771 minterms\nEnvelope[219]: 4249 nodes 1 leaves 3677 minterms\nEnvelope[220]: 4177 nodes 1 leaves 3586 minterms\nEnvelope[221]: 4102 nodes 1 leaves 3496 minterms\nEnvelope[222]: 4021 nodes 1 leaves 3408 minterms\nEnvelope[223]: 3949 nodes 1 leaves 3322 minterms\nEnvelope[224]: 3871 nodes 1 leaves 3238 minterms\nEnvelope[225]: 3800 nodes 1 leaves 3158 minterms\nEnvelope[226]: 3740 nodes 1 leaves 3079 minterms\nEnvelope[227]: 3674 nodes 1 leaves 3002 minterms\nEnvelope[228]: 3618 nodes 1 leaves 2926 minterms\nEnvelope[229]: 3552 nodes 1 leaves 2852 minterms\nEnvelope[230]: 3485 nodes 1 leaves 2780 minterms\nEnvelope[231]: 3428 nodes 1 leaves 2711 minterms\nEnvelope[232]: 3370 nodes 1 leaves 2643 minterms\nEnvelope[233]: 3304 nodes 1 leaves 2575 minterms\nEnvelope[234]: 3244 nodes 1 leaves 2510 minterms\nEnvelope[235]: 3177 nodes 1 leaves 2447 minterms\nEnvelope[236]: 3112 nodes 1 leaves 2385 minterms\nEnvelope[237]: 3054 nodes 1 leaves 2324 minterms\nEnvelope[238]: 2999 nodes 1 leaves 2268 minterms\nEnvelope[239]: 2947 nodes 1 leaves 2212 minterms\nEnvelope[240]: 2892 nodes 1 leaves 2157 minterms\nEnvelope[241]: 2831 nodes 1 leaves 2104 minterms\nEnvelope[242]: 2769 nodes 1 leaves 2052 minterms\nEnvelope[243]: 2709 nodes 1 leaves 2001 minterms\nEnvelope[244]: 2644 nodes 1 leaves 1952 minterms\nEnvelope[245]: 2569 nodes 1 leaves 1903 minterms\nEnvelope[246]: 2505 nodes 1 leaves 1855 minterms\nEnvelope[247]: 2432 nodes 1 leaves 1807 minterms\nEnvelope[248]: 2361 nodes 1 leaves 1760 minterms\nEnvelope[249]: 2289 nodes 1 leaves 1715 minterms\nEnvelope[250]: 2215 nodes 1 leaves 1673 minterms\nEnvelope[251]: 2169 nodes 1 leaves 1632 minterms\nEnvelope[252]: 2114 nodes 1 leaves 1591 minterms\nEnvelope[253]: 2063 nodes 1 leaves 1551 minterms\nEnvelope[254]: 2011 nodes 1 leaves 1512 minterms\nEnvelope[255]: 1957 nodes 1 leaves 1473 minterms\nEnvelope[256]: 1902 nodes 1 leaves 1434 minterms\nEnvelope[257]: 1852 nodes 1 leaves 1396 minterms\nEnvelope[258]: 1805 nodes 1 leaves 1359 minterms\nEnvelope[259]: 1763 nodes 1 leaves 1322 minterms\nEnvelope[260]: 1711 nodes 1 leaves 1287 minterms\nEnvelope[261]: 1653 nodes 1 leaves 1255 minterms\nEnvelope[262]: 1604 nodes 1 leaves 1223 minterms\nEnvelope[263]: 1557 nodes 1 leaves 1193 minterms\nEnvelope[264]: 1515 nodes 1 leaves 1164 minterms\nEnvelope[265]: 1482 nodes 1 leaves 1136 minterms\nEnvelope[266]: 1447 nodes 1 leaves 1108 minterms\nEnvelope[267]: 1416 nodes 1 leaves 1081 minterms\nEnvelope[268]: 1383 nodes 1 leaves 1054 minterms\nEnvelope[269]: 1353 nodes 1 leaves 1028 minterms\nEnvelope[270]: 1323 nodes 1 leaves 1003 minterms\nEnvelope[271]: 1290 nodes 1 leaves 978 minterms\nEnvelope[272]: 1252 nodes 1 leaves 954 minterms\nEnvelope[273]: 1215 nodes 1 leaves 931 minterms\nEnvelope[274]: 1174 nodes 1 leaves 908 minterms\nEnvelope[275]: 1144 nodes 1 leaves 887 minterms\nEnvelope[276]: 1120 nodes 1 leaves 867 minterms\nEnvelope[277]: 1102 nodes 1 leaves 848 minterms\nEnvelope[278]: 1082 nodes 1 leaves 830 minterms\nEnvelope[279]: 1061 nodes 1 leaves 812 minterms\nEnvelope[280]: 1045 nodes 1 leaves 795 minterms\nEnvelope[281]: 1031 nodes 1 leaves 778 minterms\nEnvelope[282]: 1015 nodes 1 leaves 763 minterms\nEnvelope[283]: 1004 nodes 1 leaves 748 minterms\nEnvelope[284]: 996 nodes 1 leaves 733 minterms\nEnvelope[285]: 983 nodes 1 leaves 719 minterms\nEnvelope[286]: 964 nodes 1 leaves 705 minterms\nEnvelope[287]: 949 nodes 1 leaves 691 minterms\nEnvelope[288]: 938 nodes 1 leaves 677 minterms\nEnvelope[289]: 925 nodes 1 leaves 663 minterms\nEnvelope[290]: 913 nodes 1 leaves 650 minterms\nEnvelope[291]: 907 nodes 1 leaves 637 minterms\nEnvelope[292]: 901 nodes 1 leaves 624 minterms\nEnvelope[293]: 887 nodes 1 leaves 611 minterms\nEnvelope[294]: 878 nodes 1 leaves 598 minterms\nEnvelope[295]: 872 nodes 1 leaves 585 minterms\nEnvelope[296]: 860 nodes 1 leaves 573 minterms\nEnvelope[297]: 852 nodes 1 leaves 561 minterms\nEnvelope[298]: 842 nodes 1 leaves 549 minterms\nEnvelope[299]: 834 nodes 1 leaves 537 minterms\nEnvelope[300]: 826 nodes 1 leaves 526 minterms\nEnvelope[301]: 819 nodes 1 leaves 515 minterms\nEnvelope[302]: 808 nodes 1 leaves 505 minterms\nEnvelope[303]: 797 nodes 1 leaves 495 minterms\nEnvelope[304]: 789 nodes 1 leaves 485 minterms\nEnvelope[305]: 773 nodes 1 leaves 475 minterms\nEnvelope[306]: 758 nodes 1 leaves 465 minterms\nEnvelope[307]: 742 nodes 1 leaves 455 minterms\nEnvelope[308]: 727 nodes 1 leaves 445 minterms\nEnvelope[309]: 711 nodes 1 leaves 435 minterms\nEnvelope[310]: 698 nodes 1 leaves 425 minterms\nEnvelope[311]: 677 nodes 1 leaves 415 minterms\nEnvelope[312]: 662 nodes 1 leaves 405 minterms\nEnvelope[313]: 653 nodes 1 leaves 395 minterms\nEnvelope[314]: 638 nodes 1 leaves 386 minterms\nEnvelope[315]: 625 nodes 1 leaves 377 minterms\nEnvelope[316]: 611 nodes 1 leaves 368 minterms\nEnvelope[317]: 603 nodes 1 leaves 359 minterms\nEnvelope[318]: 598 nodes 1 leaves 350 minterms\nEnvelope[319]: 588 nodes 1 leaves 342 minterms\nEnvelope[320]: 581 nodes 1 leaves 334 minterms\nEnvelope[321]: 576 nodes 1 leaves 326 minterms\nEnvelope[322]: 566 nodes 1 leaves 318 minterms\nEnvelope[323]: 555 nodes 1 leaves 311 minterms\nEnvelope[324]: 546 nodes 1 leaves 305 minterms\nEnvelope[325]: 537 nodes 1 leaves 299 minterms\nEnvelope[326]: 526 nodes 1 leaves 293 minterms\nEnvelope[327]: 515 nodes 1 leaves 287 minterms\nEnvelope[328]: 505 nodes 1 leaves 281 minterms\nEnvelope[329]: 493 nodes 1 leaves 275 minterms\nEnvelope[330]: 481 nodes 1 leaves 270 minterms\nEnvelope[331]: 468 nodes 1 leaves 265 minterms\nEnvelope[332]: 455 nodes 1 leaves 260 minterms\nEnvelope[333]: 446 nodes 1 leaves 255 minterms\nEnvelope[334]: 438 nodes 1 leaves 250 minterms\nEnvelope[335]: 433 nodes 1 leaves 245 minterms\nEnvelope[336]: 430 nodes 1 leaves 240 minterms\nEnvelope[337]: 421 nodes 1 leaves 235 minterms\nEnvelope[338]: 415 nodes 1 leaves 230 minterms\nEnvelope[339]: 405 nodes 1 leaves 225 minterms\nEnvelope[340]: 397 nodes 1 leaves 220 minterms\nEnvelope[341]: 390 nodes 1 leaves 215 minterms\nEnvelope[342]: 382 nodes 1 leaves 210 minterms\nEnvelope[343]: 374 nodes 1 leaves 205 minterms\nEnvelope[344]: 368 nodes 1 leaves 200 minterms\nEnvelope[345]: 357 nodes 1 leaves 195 minterms\nEnvelope[346]: 349 nodes 1 leaves 190 minterms\nEnvelope[347]: 345 nodes 1 leaves 185 minterms\nEnvelope[348]: 343 nodes 1 leaves 180 minterms\nEnvelope[349]: 338 nodes 1 leaves 175 minterms\nEnvelope[350]: 329 nodes 1 leaves 170 minterms\nEnvelope[351]: 318 nodes 1 leaves 165 minterms\nEnvelope[352]: 312 nodes 1 leaves 160 minterms\nEnvelope[353]: 305 nodes 1 leaves 156 minterms\nEnvelope[354]: 298 nodes 1 leaves 152 minterms\nEnvelope[355]: 291 nodes 1 leaves 148 minterms\nEnvelope[356]: 284 nodes 1 leaves 144 minterms\nEnvelope[357]: 274 nodes 1 leaves 140 minterms\nEnvelope[358]: 267 nodes 1 leaves 136 minterms\nEnvelope[359]: 258 nodes 1 leaves 132 minterms\nEnvelope[360]: 250 nodes 1 leaves 129 minterms\nEnvelope[361]: 242 nodes 1 leaves 126 minterms\nEnvelope[362]: 239 nodes 1 leaves 123 minterms\nEnvelope[363]: 230 nodes 1 leaves 120 minterms\nEnvelope[364]: 224 nodes 1 leaves 117 minterms\nEnvelope[365]: 218 nodes 1 leaves 114 minterms\nEnvelope[366]: 217 nodes 1 leaves 111 minterms\nEnvelope[367]: 216 nodes 1 leaves 108 minterms\nEnvelope[368]: 214 nodes 1 leaves 105 minterms\nEnvelope[369]: 213 nodes 1 leaves 102 minterms\nEnvelope[370]: 213 nodes 1 leaves 99 minterms\nEnvelope[371]: 210 nodes 1 leaves 96 minterms\nEnvelope[372]: 206 nodes 1 leaves 93 minterms\nEnvelope[373]: 203 nodes 1 leaves 90 minterms\nEnvelope[374]: 199 nodes 1 leaves 87 minterms\nEnvelope[375]: 195 nodes 1 leaves 84 minterms\nEnvelope[376]: 191 nodes 1 leaves 81 minterms\nEnvelope[377]: 188 nodes 1 leaves 78 minterms\nEnvelope[378]: 186 nodes 1 leaves 75 minterms\nEnvelope[379]: 184 nodes 1 leaves 72 minterms\nEnvelope[380]: 183 nodes 1 leaves 70 minterms\nEnvelope[381]: 183 nodes 1 leaves 68 minterms\nEnvelope[382]: 182 nodes 1 leaves 66 minterms\nEnvelope[383]: 181 nodes 1 leaves 64 minterms\nEnvelope[384]: 179 nodes 1 leaves 62 minterms\nEnvelope[385]: 179 nodes 1 leaves 60 minterms\nEnvelope[386]: 178 nodes 1 leaves 58 minterms\nEnvelope[387]: 177 nodes 1 leaves 56 minterms\nEnvelope[388]: 175 nodes 1 leaves 54 minterms\nEnvelope[389]: 171 nodes 1 leaves 52 minterms\nEnvelope[390]: 168 nodes 1 leaves 50 minterms\nEnvelope[391]: 164 nodes 1 leaves 48 minterms\nEnvelope[392]: 159 nodes 1 leaves 46 minterms\nEnvelope[393]: 153 nodes 1 leaves 45 minterms\nEnvelope[394]: 148 nodes 1 leaves 44 minterms\nEnvelope[395]: 144 nodes 1 leaves 43 minterms\nEnvelope[396]: 140 nodes 1 leaves 42 minterms\nEnvelope[397]: 135 nodes 1 leaves 41 minterms\nEnvelope[398]: 132 nodes 1 leaves 40 minterms\nEnvelope[399]: 127 nodes 1 leaves 39 minterms\nEnvelope[400]: 122 nodes 1 leaves 38 minterms\nEnvelope[401]: 118 nodes 1 leaves 37 minterms\nEnvelope[402]: 114 nodes 1 leaves 36 minterms\nEnvelope[403]: 107 nodes 1 leaves 35 minterms\nEnvelope[404]: 100 nodes 1 leaves 34 minterms\nEnvelope[405]: 95 nodes 1 leaves 33 minterms\nEnvelope[406]: 92 nodes 1 leaves 32 minterms\nEnvelope[407]: 89 nodes 1 leaves 31 minterms\nEnvelope[408]: 84 nodes 1 leaves 30 minterms\nEnvelope[409]: 81 nodes 1 leaves 29 minterms\nEnvelope[410]: 78 nodes 1 leaves 28 minterms\nEnvelope[411]: 73 nodes 1 leaves 27 minterms\nEnvelope[412]: 70 nodes 1 leaves 26 minterms\nEnvelope[413]: 67 nodes 1 leaves 25 minterms\nEnvelope[414]: 63 nodes 1 leaves 24 minterms\nEnvelope[415]: 59 nodes 1 leaves 23 minterms\nEnvelope[416]: 56 nodes 1 leaves 22 minterms\nEnvelope[417]: 55 nodes 1 leaves 21 minterms\nEnvelope[418]: 54 nodes 1 leaves 20 minterms\nEnvelope[419]: 53 nodes 1 leaves 19 minterms\nEnvelope[420]: 52 nodes 1 leaves 18 minterms\nEnvelope[421]: 52 nodes 1 leaves 17 minterms\nEnvelope[422]: 50 nodes 1 leaves 16 minterms\nEnvelope[423]: 47 nodes 1 leaves 15 minterms\nEnvelope[424]: 44 nodes 1 leaves 14 minterms\nEnvelope[425]: 40 nodes 1 leaves 13 minterms\nEnvelope[426]: 36 nodes 1 leaves 12 minterms\nEnvelope[427]: 33 nodes 1 leaves 11 minterms\nEnvelope[428]: 31 nodes 1 leaves 10 minterms\nEnvelope[429]: 30 nodes 1 leaves 9 minterms\nEnvelope[430]: 29 nodes 1 leaves 8 minterms\nEnvelope[431]: 29 nodes 1 leaves 7 minterms\nEnvelope[432]: 29 nodes 1 leaves 6 minterms\nEnvelope[433]: 28 nodes 1 leaves 5 minterms\nEnvelope[434]: 27 nodes 1 leaves 4 minterms\ndepth = 434\nEnvelope: 27 nodes 1 leaves 4 minterms\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 4004\n**** CUDD non-modifiable parameters ****\nMemory in use: 250182096\nPeak number of nodes: 5201980\nPeak number of live nodes: 2068734\nNumber of BDD variables: 50\nNumber of ZDD variables: 0\nNumber of cache entries: 2097152\nNumber of cache look-ups: 57137789\nNumber of cache hits: 32454226\nNumber of cache insertions: 24683505\nNumber of cache collisions: 17087296\nNumber of cache deletions: 7366016\nCache used slots = 99.98% (expected 100.00%)\nSoft limit for cache size: 2796202\nNumber of buckets in unique table: 1795072\nUsed buckets in unique table: 5.77% (expected 5.77%)\nNumber of BDD and ADD nodes: 193317\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 140806\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 15634687\nTotal number of nodes reclaimed: 8157933\nGarbage collections so far: 7\nTime for garbage collection: 0.83 sec\nReorderings so far: 0\nTime for reordering: 0.00 sec\nFinal size: 869\ntotal time = 16.95 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time     17.0 seconds\nSystem time    0.1 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            = 249384K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 48366\nSwaps = 0\nInput blocks = 8\nOutput blocks = 48\nContext switch (voluntary) = 1\nContext switch (involuntary) = 18\n"
  },
  {
    "path": "cudd/nanotrav/s27.blif",
    "content": ".model s27.bench\n.inputs G0 G1 G2 G3\n.outputs G17\n.latch     G10 G5  0\n.latch     G11 G6  0\n.latch     G13 G7  0\n.names G11 G17\n0 1\n.names G14 G11 G10\n00 1\n.names G5 G9 G11\n00 1\n.names G2 G12 G13\n00 1\n.names G0 G14\n0 1\n.names G14 G6 G8\n11 1\n.names G1 G7 G12\n00 1\n.names G12 G8 G15\n1- 1\n-1 1\n.names G3 G8 G16\n1- 1\n-1 1\n.names G16 G15 G9\n0- 1\n-0 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/s27.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -ordering hw -reordering annealing -trav ./nanotrav/s27.blif\n# CUDD Version 3.0.0\nOrder before final reordering\nG0 G1 G2 G3 G5 G6 G7 \nNumber of inputs = 7\nBDD reordering with annealing: from 16 to ... 10 nodes in 0 sec\nNew order\nG0 G5 G6 G3 G2 G7 G1 \nBuilding transition relation. Time = 0.00 sec\n@@@\nTransition relation: 1 parts 3 latches 9 nodes\nTraversing. Time = 0.00 sec\nS0: 4 nodes 1 leaves 1 minterms\nFrom[1]: 5 nodes 1 leaves 4 minterms\nReached[1]: 5 nodes 1 leaves 5 minterms\n5\n5\nFrom[2]: 4 nodes 1 leaves 1 minterms\nReached[2]: 3 nodes 1 leaves 6 minterms\n6\n6\ndepth = 2\nR: 3 nodes 1 leaves 6 minterms\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000000\nMaximum number of variable swaps per reordering: 1000000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 36\n**** CUDD non-modifiable parameters ****\nMemory in use: 3182808\nPeak number of nodes: 1022\nPeak number of live nodes: 51\nNumber of BDD variables: 10\nNumber of ZDD variables: 0\nNumber of cache entries: 32768\nNumber of cache look-ups: 151\nNumber of cache hits: 30\nNumber of cache insertions: 115\nNumber of cache collisions: 0\nNumber of cache deletions: 24\nCache used slots = 0.35% (expected 0.28%)\nSoft limit for cache size: 11264\nNumber of buckets in unique table: 2816\nUsed buckets in unique table: 3.30% (expected 3.29%)\nNumber of BDD and ADD nodes: 95\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 66\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 110\nTotal number of nodes reclaimed: 21\nGarbage collections so far: 1\nTime for garbage collection: 0.00 sec\nReorderings so far: 1\nTime for reordering: 0.00 sec\nFinal size: 10\ntotal time = 0.00 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  6100K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 896\nSwaps = 0\nInput blocks = 8\nOutput blocks = 8\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/s27b.blif",
    "content": ".model s27b.bench\n.inputs G0 G1 G2 G3\n.outputs G17\n.latch     G10 G5  0\n.latch     G11 G6  0\n.latch     G13 G7  0\n.names G11 G17\n0 1\n.names G0 G11 G10\n10 1\n.names G5 G9 G11\n00 1\n.names G2 G12 G13\n00 1\n.names G0 G6 G8\n01 1\n.names G1 G7 G12\n00 1\n.names G3 G8 G12 G9\n-1- 0\n1-1 0\n.end\n"
  },
  {
    "path": "cudd/nanotrav/s27b.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -ordering dfs -reordering win4 -verify ./nanotrav/s27.blif ./nanotrav/s27b.blif\n# CUDD Version 3.0.0\nOrder before final reordering\nG0 G6 G1 G7 G3 G5 G2 \nNumber of inputs = 7\nBDD reordering with window: from 11 to ... 11 nodes in 0 sec\nNew order\nG0 G6 G1 G7 G3 G5 G2 \nTesting equivalence\nG17: 7 nodes 1 leaves 106 minterms\nG10: 6 nodes 1 leaves 60 minterms\nG11: 7 nodes 1 leaves 22 minterms\nG13: 4 nodes 1 leaves 48 minterms\nVerification succeeded\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000000\nMaximum number of variable swaps per reordering: 1000000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 36\n**** CUDD non-modifiable parameters ****\nMemory in use: 3182768\nPeak number of nodes: 1022\nPeak number of live nodes: 29\nNumber of BDD variables: 7\nNumber of ZDD variables: 0\nNumber of cache entries: 32768\nNumber of cache look-ups: 27\nNumber of cache hits: 8\nNumber of cache insertions: 19\nNumber of cache collisions: 0\nNumber of cache deletions: 19\nCache used slots = 0.06% (expected 0.00%)\nSoft limit for cache size: 8192\nNumber of buckets in unique table: 2048\nUsed buckets in unique table: 1.27% (expected 1.25%)\nNumber of BDD and ADD nodes: 26\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 7\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 36\nTotal number of nodes reclaimed: 10\nGarbage collections so far: 1\nTime for garbage collection: 0.00 sec\nReorderings so far: 1\nTime for reordering: 0.00 sec\nFinal size: 11\ntotal time = 0.00 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  6052K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 895\nSwaps = 0\nInput blocks = 8\nOutput blocks = 8\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/s27c.blif",
    "content": ".model s27c.bench\n.outputs G11\n.latch     G10 G5  0\n.latch     G11 G6  0\n.latch     G7 G7  0\n.names G11 G10\n0 1\n.names G5 G9 G11\n00 1\n.names G6 G8\n1 1\n.names G8 G7 G9\n01 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/s27c.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -trav -image depend -depend ./nanotrav/s27c.blif\n# CUDD Version 3.0.0\nOrder before final reordering\nG5 G6 G7 \nNumber of inputs = 3\nBuilding transition relation. Time = 0.00 sec\nTransition relation: 3 parts 3 latches 4 nodes\nTraversing. Time = 0.00 sec\nS0: 4 nodes 1 leaves 1 minterms\nEliminated 3 vars. Transition function 1 nodes.\nExtracted 2 repeated parts in 1 factors.\nnew factor of 2 nodes\nMerging 3 factors. Independent image: 1 nodes\nnew factor 2 nodes\nnew factor 4 nodes\nFrom[1]: 4 nodes 1 leaves 1 minterms\nReached[1]: 3 nodes 1 leaves 2 minterms\n2\n2\nEliminated 3 vars. Transition function 1 nodes.\nExtracted 2 repeated parts in 1 factors.\nnew factor of 2 nodes\nMerging 3 factors. Independent image: 1 nodes\nnew factor 2 nodes\nnew factor 4 nodes\ndepth = 1\nR: 3 nodes 1 leaves 2 minterms\nAnalyzing latch dependencies\nG5 is stuck at 0\nG7 is stuck at 0\nnew reached: 1 nodes 1 leaves 2 minterms\n2 latches are redundant\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: no\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 4004\n**** CUDD non-modifiable parameters ****\nMemory in use: 3182808\nPeak number of nodes: 1022\nPeak number of live nodes: 25\nNumber of BDD variables: 6\nNumber of ZDD variables: 0\nNumber of cache entries: 32768\nNumber of cache look-ups: 88\nNumber of cache hits: 33\nNumber of cache insertions: 48\nNumber of cache collisions: 5\nNumber of cache deletions: 0\nCache used slots = 0.13% (expected 0.15%)\nSoft limit for cache size: 7168\nNumber of buckets in unique table: 1792\nUsed buckets in unique table: 1.45% (expected 1.55%)\nNumber of BDD and ADD nodes: 28\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 16\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 28\nTotal number of nodes reclaimed: 15\nGarbage collections so far: 0\nTime for garbage collection: 0.00 sec\nReorderings so far: 0\nTime for reordering: 0.00 sec\nFinal size: 4\ntotal time = 0.00 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.0 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  5940K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 891\nSwaps = 0\nInput blocks = 8\nOutput blocks = 8\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/s382.blif",
    "content": ".model s382.bench\n.inputs FM TEST CLR\n.outputs GRN1 GRN2 RED1 YLW2 RED2 YLW1\n.latch     TESTLVIINLATCHVCDAD TESTL  0\n.latch     FMLVIINLATCHVCDAD FML  0\n.latch     TCOMB_YA2 OLATCH_Y2L  0\n.latch     Y1C OLATCHVUC_6  0\n.latch     R2C OLATCHVUC_5  0\n.latch     TCOMB_RA1 OLATCH_R1L  0\n.latch     TCOMB_GA2 OLATCH_G2L  0\n.latch     TCOMB_GA1 OLATCH_G1L  0\n.latch     TCOMB_FE_BF OLATCH_FEL  0\n.latch     C3_Q3VD C3_Q3  0\n.latch     C3_Q2VD C3_Q2  0\n.latch     C3_Q1VD C3_Q1  0\n.latch     C3_Q0VD C3_Q0  0\n.latch     UC_16VD UC_16  0\n.latch     UC_17VD UC_17  0\n.latch     UC_18VD UC_18  0\n.latch     UC_19VD UC_19  0\n.latch     UC_8VD UC_8  0\n.latch     UC_9VD UC_9  0\n.latch     UC_10VD UC_10  0\n.latch     UC_11VD UC_11  0\n.names OUTBUFVBUFG1VIIR1 GRN1\n0 1\n.names OUTBUFVBUFG2VIIR1 GRN2\n0 1\n.names OUTBUFVBUFR1VIIR1 RED1\n0 1\n.names OUTBUFVBUFY2VIIR1 YLW2\n0 1\n.names OUTBUFVBUFR2VIIR1 RED2\n0 1\n.names OUTBUFVBUFY1VIIR1 YLW1\n0 1\n.names TESTLVIINLATCHVCDN TESTLVIINMUX TESTLVIINLATCHVCDAD\n11 1\n.names FMLVIINLATCHVCDN FMLVIINMUX FMLVIINLATCHVCDAD\n11 1\n.names TCOMBVNODE12 TCOMBVNQA TCOMB_YA2\n00 1\n.names Y1CVAD2NF Y1CVAD1NF Y1C\n00 1\n.names R2CVAD2NF R2CVAD1NF R2C\n00 1\n.names TCOMBVNCLR TCOMB_RA1VOR2NF TCOMB_RA1VOR1NF TCOMB_RA1\n0-- 1\n-0- 1\n--0 1\n.names TCOMB_GA2VAD4NF TCOMB_GA2VAD3NF TCOMB_GA2VAD2NF TCOMB_GA2VAD1NF TCOMB_GA2\n0000 1\n.names TCOMBVNODE8 TCOMB_GA1VAD1NF TCOMB_GA1\n00 1\n.names II84 TCOMB_FE_BF\n0 1\n.names CLRB C3_Q3VZ UC_27 C3_Q3VD\n000 1\n.names CLRB C3_Q2VZ UC_27 C3_Q2VD\n000 1\n.names CLRB C3_Q1VZ UC_27 C3_Q1VD\n000 1\n.names CLRB C3_Q0VZ UC_27 C3_Q0VD\n000 1\n.names CLRB UC_16VZ C2_CO UC_16VD\n000 1\n.names CLRB UC_17VZ C2_CO UC_17VD\n000 1\n.names CLRB UC_18VZ C2_CO UC_18VD\n000 1\n.names CLRB UC_19VZ C2_CO UC_19VD\n000 1\n.names CLRB UC_8VZ C1_CO UC_8VD\n000 1\n.names CLRB UC_9VZ C1_CO UC_9VD\n000 1\n.names CLRB UC_10VZ C1_CO UC_10VD\n000 1\n.names CLRB UC_11VZ C1_CO UC_11VD\n000 1\n.names TESTL TESTLVIINLATCHN\n0 1\n.names FML FMLVIINLATCHN\n0 1\n.names OLATCHVUC_6 OLATCH_Y1L\n0 1\n.names OLATCHVUC_5 OLATCH_R2L\n0 1\n.names C3_Q3 UC_23\n0 1\n.names C3_Q2 UC_24\n0 1\n.names C3_Q1 UC_25\n0 1\n.names C3_Q0 UC_26\n0 1\n.names UC_16 UC_20\n0 1\n.names UC_17 C2_QN2\n0 1\n.names UC_18 UC_21\n0 1\n.names UC_19 UC_22\n0 1\n.names UC_8 UC_12\n0 1\n.names UC_9 UC_13\n0 1\n.names UC_10 UC_14\n0 1\n.names UC_11 UC_15\n0 1\n.names FM FMBVIIR1\n0 1\n.names CLR CLRBVIIR1\n0 1\n.names FML TCOMBVNFM\n0 1\n.names TEST TESTBVIIR1\n0 1\n.names C3_Q0 TCOMBVNQA\n0 1\n.names C3_Q1 TCOMBVNQB\n0 1\n.names C3_Q2 TCOMBVNQC\n0 1\n.names C3_Q3 TCOMBVNQD\n0 1\n.names UC_11 UC_11VUC_0\n0 1\n.names OLATCH_G1L OUTBUFVBUFG1VIIR1\n0 1\n.names OLATCH_G2L OUTBUFVBUFG2VIIR1\n0 1\n.names OLATCH_FEL TCOMBVNFEL\n0 1\n.names OLATCH_R1L OUTBUFVBUFR1VIIR1\n0 1\n.names OLATCH_Y2L OUTBUFVBUFY2VIIR1\n0 1\n.names FMBVIIR1 FMB\n0 1\n.names CLRBVIIR1 CLRB\n0 1\n.names TESTBVIIR1 TESTB\n0 1\n.names UC_11VUC_0 UC_11VZ\n0 1\n.names UC_15 C1VCO0\n0 1\n.names OLATCH_R2L OUTBUFVBUFR2VIIR1\n0 1\n.names OLATCH_Y1L OUTBUFVBUFY1VIIR1\n0 1\n.names FMB FMLVIINMUXVIIR1\n0 1\n.names CLRB TESTLVIINLATCHVCDN\n0 1\n.names CLRB FMLVIINLATCHVCDN\n0 1\n.names CLRB TCOMBVNCLR\n0 1\n.names TESTB TESTLVIINMUXVIIR1\n0 1\n.names C1_CO TESTL CTST\n00 1\n.names CTST C2VIINHN\n0 1\n.names C1VCO2 UC_8 UC_8VZVOR1NF\n1- 1\n-1 1\n.names UC_8VZVOR1NF UC_8VZ\n0 1\n.names C2VCIIA CTST UC_20 C2_CO\n000 1\n.names C2_CO CO2\n0 1\n.names FMLVIINMUXVOR2NF FMLVIINMUXVOR1NF FMLVIINMUXVND1\n0- 1\n-0 1\n.names FMLVIINMUXVND1 FMLVIINMUX\n0 1\n.names TESTLVIINMUXVOR2NF TESTLVIINMUXVOR1NF TESTLVIINMUXVND1\n0- 1\n-0 1\n.names TESTLVIINMUXVND1 TESTLVIINMUX\n0 1\n.names TCOMBVNODE16 TCOMBVNODE14 TCOMB_FE\n0- 1\n-0 1\n.names TCOMB_FE II84\n0 1\n.names TCOMB_FE FEN\n0 1\n.names C2VCO2 UC_16 UC_16VZVOR1NF\n1- 1\n-1 1\n.names UC_16VZVOR1NF UC_16VZ\n0 1\n.names CO2 C3VIINHN\n0 1\n.names C3VCO2 C3_Q3 C3_Q3VZVOR1NF\n1- 1\n-1 1\n.names C3_Q3VZVOR1NF C3_Q3VZ\n0 1\n.names TCOMBVNFM TCOMBVNQD TCOMBVNQB C3_Q0 TCOMBVNODE6\n0--- 1\n-0-- 1\n--0- 1\n---0 1\n.names TCOMBVNODE6 OLATCH_FEL TCOMB_GA1VAD1NF\n11 1\n.names OLATCH_FEL TCOMBVNCLR TCOMB_GA2VAD4NF\n11 1\n.names C3_Q2 TCOMBVNCLR TCOMB_GA2VAD3NF\n11 1\n.names C3_Q0 C3_Q1 TCOMBVNCLR TCOMB_GA2VAD2NF\n111 1\n.names TCOMBVNQA C3_Q3 TCOMBVNCLR TCOMB_GA2VAD1NF\n111 1\n.names TCOMB_FE C2_QN2 R2CVAD1NF\n11 1\n.names TCOMBVNODE16 TCOMBVNODE3 TCOMB_YA1\n0- 1\n-0 1\n.names TCOMB_YA1 C2_QN2 Y1CVAD1NF\n11 1\n.names FEN TCOMB_YA1 Y1CVAD2NF\n11 1\n.names TCOMB_RA2VOR3NF TCOMB_RA2VOR1NF TCOMB_RA2\n0- 1\n-0 1\n.names FEN TCOMB_RA2 R2CVAD2NF\n11 1\n.names C3_Q2 C3_Q3 OLATCH_FEL TCOMB_RA1VOR2NF\n1-- 1\n-1- 1\n--1 1\n.names C3_Q0 C3_Q1 TCOMBVNFM TCOMBVNODE8VOR1NF\n1-- 1\n-1- 1\n--1 1\n.names TCOMBVNQA C3_Q1 C3_Q2 OLATCH_FEL TCOMB_RA1VOR1NF\n1--- 1\n-1-- 1\n--1- 1\n---1 1\n.names TCOMBVNQD TCOMBVNFM TCOMBVNODE8VOR2NF\n1- 1\n-1 1\n.names FMB FML FMLVIINMUXVOR1NF\n1- 1\n-1 1\n.names TCOMBVNQC CLRB TCOMB_RA2VOR3NF\n1- 1\n-1 1\n.names C3_Q0 C3_Q1 TCOMBVNQD CLRB TCOMB_RA2VOR1NF\n1--- 1\n-1-- 1\n--1- 1\n---1 1\n.names C3_Q2 TCOMBVNQD CLRB TCOMBVNODE4VOR2NF\n1-- 1\n-1- 1\n--1 1\n.names TCOMBVNQC C3_Q3 TCOMBVNFM CLRB TCOMBVNODE4VOR1NF\n1--- 1\n-1-- 1\n--1- 1\n---1 1\n.names TESTB TESTL TESTLVIINMUXVOR1NF\n1- 1\n-1 1\n.names TCOMBVNQB C3_Q0 TCOMBVNODE18\n0- 1\n-0 1\n.names TCOMBVNODE18 FML C3_Q3 TCOMBVNQC TCOMBVNODE16VOR1NF\n1--- 1\n-1-- 1\n--1- 1\n---1 1\n.names UC_13 UC_14 UC_15 C1VCO2\n000 1\n.names UC_14 UC_15 C1VCO1\n00 1\n.names C1VCO1 UC_9 UC_9VZVOR1NF\n1- 1\n-1 1\n.names C1VCO0 UC_10 UC_10VZVOR1NF\n1- 1\n-1 1\n.names FMLVIINMUXVIIR1 FMLVIINLATCHN FMLVIINMUXVOR2NF\n1- 1\n-1 1\n.names TESTLVIINMUXVIIR1 TESTLVIINLATCHN TESTLVIINMUXVOR2NF\n1- 1\n-1 1\n.names CTST C2_QN2 UC_21 UC_22 C2VCO2\n0000 1\n.names CTST UC_21 UC_22 C2VCO1\n000 1\n.names C2VCO1 UC_17 UC_17VZVOR1NF\n1- 1\n-1 1\n.names CTST UC_22 C2VCO0\n00 1\n.names C2VCO0 UC_18 UC_18VZVOR1NF\n1- 1\n-1 1\n.names C2VIINHN UC_19 UC_19VZVOR1NF\n1- 1\n-1 1\n.names CO2 UC_24 UC_25 UC_26 C3VCO2\n0000 1\n.names CO2 UC_25 UC_26 C3VCO1\n000 1\n.names C3VCO1 C3_Q2 C3_Q2VZVOR1NF\n1- 1\n-1 1\n.names CO2 UC_26 C3VCO0\n00 1\n.names C3VCO0 C3_Q1 C3_Q1VZVOR1NF\n1- 1\n-1 1\n.names C3VIINHN C3_Q0 C3_Q0VZVOR1NF\n1- 1\n-1 1\n.names C1VCO1 UC_9 UC_9VUC_0\n0- 1\n-0 1\n.names C1VCO0 UC_10 UC_10VUC_0\n0- 1\n-0 1\n.names TCOMBVNODE4VOR2NF TCOMBVNODE4VOR1NF TCOMBVNODE4\n0- 1\n-0 1\n.names CLRB TCOMBVNFM TCOMBVNQC C3_Q1 TCOMBVNODE15\n0000 1\n.names TCOMBVNODE15 TCOMBVNQA TCOMBVNODE14\n0- 1\n-0 1\n.names TCOMBVNCLR TCOMBVNFEL TCOMBVNQC C3_Q1 TCOMBVNODE12\n0--- 1\n-0-- 1\n--0- 1\n---0 1\n.names TCOMBVNCLR C3_Q2 TCOMBVNODE8VOR2NF TCOMBVNODE8VOR1NF TCOMBVNODE8\n0--- 1\n-0-- 1\n--0- 1\n---0 1\n.names CLRB TCOMBVNFEL TCOMBVNODE19\n00 1\n.names TCOMBVNODE19 TCOMBVNODE16VOR1NF TCOMBVNODE16\n0- 1\n-0 1\n.names UC_9VZVOR1NF UC_9VUC_0 UC_9VZ\n0- 1\n-0 1\n.names UC_10VZVOR1NF UC_10VUC_0 UC_10VZ\n0- 1\n-0 1\n.names TCOMBVNODE4 TCOMBVNQB TCOMBVNQA TCOMBVNODE3\n0-- 1\n-0- 1\n--0 1\n.names C2VCO1 UC_17 UC_17VUC_0\n0- 1\n-0 1\n.names C2VCO0 UC_18 UC_18VUC_0\n0- 1\n-0 1\n.names C2VIINHN UC_19 UC_19VUC_0\n0- 1\n-0 1\n.names UC_17VZVOR1NF UC_17VUC_0 UC_17VZ\n0- 1\n-0 1\n.names UC_18VZVOR1NF UC_18VUC_0 UC_18VZ\n0- 1\n-0 1\n.names UC_19VZVOR1NF UC_19VUC_0 UC_19VZ\n0- 1\n-0 1\n.names C3VCO1 C3_Q2 C3_Q2VUC_0\n0- 1\n-0 1\n.names C3VCO0 C3_Q1 C3_Q1VUC_0\n0- 1\n-0 1\n.names C3VIINHN C3_Q0 C3_Q0VUC_0\n0- 1\n-0 1\n.names C3_Q2VZVOR1NF C3_Q2VUC_0 C3_Q2VZ\n0- 1\n-0 1\n.names C3_Q1VZVOR1NF C3_Q1VUC_0 C3_Q1VZ\n0- 1\n-0 1\n.names C3_Q0VZVOR1NF C3_Q0VUC_0 C3_Q0VZ\n0- 1\n-0 1\n.names C3_Q2 C3_Q1 C3_Q0 C3VCIIA\n000 1\n.names UC_9 UC_10 UC_11 C1VCIIA\n000 1\n.names UC_17 UC_18 UC_19 C2VCIIA\n000 1\n.names C1VCIIA UC_12 C1_CO\n00 1\n.names C3VCIIA CO2 UC_23 UC_27\n000 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/s382.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -trav -image part -autodyn -automethod sifting -drop -scc -shortpaths bellman ./nanotrav/s382.blif\n# CUDD Version 3.0.0\nOrder before final reordering\nFM TEST CLR TESTL FML OLATCH_Y2L OLATCHVUC_6 OLATCHVUC_5 \nOLATCH_R1L OLATCH_G2L OLATCH_G1L OLATCH_FEL C3_Q3 C3_Q2 C3_Q1 C3_Q0 \nUC_16 UC_17 UC_18 UC_19 UC_8 UC_9 UC_10 UC_11 \nNumber of inputs = 24\nBuilding transition relation. Time = 0.00 sec\nTransition relation: 21 parts 21 latches 229 nodes\nTraversing. Time = 0.00 sec\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 40 nodes 1 leaves 5 minterms\nReached[1]: 56 nodes 1 leaves 6 minterms\n6\n6\nFrom[2]: 19 nodes 1 leaves 8 minterms\nReached[2]: 59 nodes 1 leaves 14 minterms\n14\n14\nFrom[3]: 20 nodes 1 leaves 12 minterms\nReached[3]: 61 nodes 1 leaves 26 minterms\n26\n26\nFrom[4]: 18 nodes 1 leaves 16 minterms\nReached[4]: 63 nodes 1 leaves 42 minterms\n42\n42\nFrom[5]: 20 nodes 1 leaves 20 minterms\nReached[5]: 68 nodes 1 leaves 62 minterms\n62\n62\nFrom[6]: 19 nodes 1 leaves 24 minterms\nReached[6]: 71 nodes 1 leaves 86 minterms\n86\n86\nFrom[7]: 20 nodes 1 leaves 28 minterms\nReached[7]: 70 nodes 1 leaves 114 minterms\n114\n114\nFrom[8]: 17 nodes 1 leaves 32 minterms\nReached[8]: 71 nodes 1 leaves 146 minterms\n146\n146\nFrom[9]: 20 nodes 1 leaves 36 minterms\nReached[9]: 77 nodes 1 leaves 182 minterms\n182\n182\nFrom[10]: 22 nodes 1 leaves 36 minterms\nReached[10]: 78 nodes 1 leaves 218 minterms\n218\n218\nFrom[11]: 26 nodes 1 leaves 40 minterms\nReached[11]: 81 nodes 1 leaves 258 minterms\n258\n258\nFrom[12]: 22 nodes 1 leaves 40 minterms\nReached[12]: 85 nodes 1 leaves 298 minterms\n298\n298\nFrom[13]: 26 nodes 1 leaves 40 minterms\nReached[13]: 82 nodes 1 leaves 338 minterms\n338\n338\nFrom[14]: 22 nodes 1 leaves 40 minterms\nReached[14]: 83 nodes 1 leaves 378 minterms\n378\n378\nFrom[15]: 26 nodes 1 leaves 40 minterms\nReached[15]: 84 nodes 1 leaves 418 minterms\n418\n418\nFrom[16]: 23 nodes 1 leaves 40 minterms\nReached[16]: 85 nodes 1 leaves 458 minterms\n458\n458\nFrom[17]: 26 nodes 1 leaves 40 minterms\nReached[17]: 79 nodes 1 leaves 498 minterms\n498\n498\nFrom[18]: 20 nodes 1 leaves 40 minterms\nReached[18]: 77 nodes 1 leaves 538 minterms\n538\n538\nFrom[19]: 24 nodes 1 leaves 40 minterms\nReached[19]: 80 nodes 1 leaves 578 minterms\n578\n578\nFrom[20]: 19 nodes 1 leaves 40 minterms\nReached[20]: 81 nodes 1 leaves 618 minterms\n618\n618\nFrom[21]: 27 nodes 1 leaves 40 minterms\nReached[21]: 85 nodes 1 leaves 658 minterms\n658\n658\nFrom[22]: 23 nodes 1 leaves 40 minterms\nReached[22]: 89 nodes 1 leaves 698 minterms\n698\n698\nFrom[23]: 27 nodes 1 leaves 40 minterms\nReached[23]: 86 nodes 1 leaves 738 minterms\n738\n738\nFrom[24]: 23 nodes 1 leaves 40 minterms\nReached[24]: 87 nodes 1 leaves 778 minterms\n778\n778\nFrom[25]: 27 nodes 1 leaves 40 minterms\nReached[25]: 88 nodes 1 leaves 818 minterms\n818\n818\nFrom[26]: 24 nodes 1 leaves 40 minterms\nReached[26]: 89 nodes 1 leaves 858 minterms\n858\n858\nFrom[27]: 27 nodes 1 leaves 40 minterms\nReached[27]: 83 nodes 1 leaves 898 minterms\n898\n898\nFrom[28]: 21 nodes 1 leaves 40 minterms\nReached[28]: 81 nodes 1 leaves 938 minterms\n938\n938\nFrom[29]: 25 nodes 1 leaves 40 minterms\nReached[29]: 80 nodes 1 leaves 978 minterms\n978\n978\nFrom[30]: 19 nodes 1 leaves 40 minterms\nReached[30]: 81 nodes 1 leaves 1018 minterms\n1018\n1018\nFrom[31]: 26 nodes 1 leaves 40 minterms\nReached[31]: 84 nodes 1 leaves 1058 minterms\n1058\n1058\nFrom[32]: 36 nodes 1 leaves 44 minterms\nReached[32]: 101 nodes 1 leaves 1102 minterms\n1102\n1102\nFrom[33]: 39 nodes 1 leaves 44 minterms\nReached[33]: 98 nodes 1 leaves 1146 minterms\n1146\n1146\nFrom[34]: 36 nodes 1 leaves 44 minterms\nReached[34]: 99 nodes 1 leaves 1190 minterms\n1190\n1190\nFrom[35]: 38 nodes 1 leaves 44 minterms\nReached[35]: 100 nodes 1 leaves 1234 minterms\n1234\n1234\nFrom[36]: 37 nodes 1 leaves 44 minterms\nReached[36]: 101 nodes 1 leaves 1278 minterms\n1278\n1278\nFrom[37]: 39 nodes 1 leaves 44 minterms\nReached[37]: 95 nodes 1 leaves 1322 minterms\n1322\n1322\nFrom[38]: 34 nodes 1 leaves 44 minterms\nReached[38]: 93 nodes 1 leaves 1366 minterms\n1366\n1366\nFrom[39]: 35 nodes 1 leaves 44 minterms\nReached[39]: 93 nodes 1 leaves 1410 minterms\n1410\n1410\nFrom[40]: 36 nodes 1 leaves 40 minterms\nReached[40]: 96 nodes 1 leaves 1450 minterms\n1450\n1450\nFrom[41]: 25 nodes 1 leaves 44 minterms\nReached[41]: 100 nodes 1 leaves 1494 minterms\n1494\n1494\nFrom[42]: 43 nodes 1 leaves 52 minterms\nReached[42]: 120 nodes 1 leaves 1546 minterms\n1546\n1546\nFrom[43]: 46 nodes 1 leaves 56 minterms\nReached[43]: 117 nodes 1 leaves 1602 minterms\n1602\n1602\nFrom[44]: 43 nodes 1 leaves 60 minterms\nReached[44]: 118 nodes 1 leaves 1662 minterms\n1662\n1662\nFrom[45]: 45 nodes 1 leaves 64 minterms\nReached[45]: 119 nodes 1 leaves 1726 minterms\n1726\n1726\nFrom[46]: 60 nodes 1 leaves 72 minterms\nReached[46]: 138 nodes 1 leaves 1798 minterms\n1798\n1798\nFrom[47]: 62 nodes 1 leaves 76 minterms\nReached[47]: 132 nodes 1 leaves 1874 minterms\n1874\n1874\nFrom[48]: 57 nodes 1 leaves 80 minterms\nReached[48]: 130 nodes 1 leaves 1954 minterms\n1954\n1954\nFrom[49]: 58 nodes 1 leaves 84 minterms\nReached[49]: 130 nodes 1 leaves 2038 minterms\n2038\n2038\nFrom[50]: 59 nodes 1 leaves 76 minterms\nReached[50]: 138 nodes 1 leaves 2114 minterms\n2114\n2114\nFrom[51]: 44 nodes 1 leaves 96 minterms\nReached[51]: 140 nodes 1 leaves 2210 minterms\n2210\n2210\nFrom[52]: 46 nodes 1 leaves 88 minterms\nReached[52]: 144 nodes 1 leaves 2298 minterms\n2298\n2298\nFrom[53]: 49 nodes 1 leaves 88 minterms\nReached[53]: 141 nodes 1 leaves 2386 minterms\n2386\n2386\nFrom[54]: 45 nodes 1 leaves 88 minterms\nReached[54]: 140 nodes 1 leaves 2474 minterms\n2474\n2474\nFrom[55]: 47 nodes 1 leaves 88 minterms\nReached[55]: 138 nodes 1 leaves 2562 minterms\n2562\n2562\nFrom[56]: 49 nodes 1 leaves 88 minterms\nReached[56]: 146 nodes 1 leaves 2650 minterms\n2650\n2650\nFrom[57]: 51 nodes 1 leaves 88 minterms\nReached[57]: 139 nodes 1 leaves 2738 minterms\n2738\n2738\nFrom[58]: 45 nodes 1 leaves 88 minterms\nReached[58]: 134 nodes 1 leaves 2826 minterms\n2826\n2826\nFrom[59]: 48 nodes 1 leaves 88 minterms\nReached[59]: 133 nodes 1 leaves 2914 minterms\n2914\n2914\nFrom[60]: 47 nodes 1 leaves 80 minterms\nReached[60]: 143 nodes 1 leaves 2994 minterms\n2994\n2994\nFrom[61]: 48 nodes 1 leaves 88 minterms\nReached[61]: 147 nodes 1 leaves 3082 minterms\n3082\n3082\nFrom[62]: 47 nodes 1 leaves 88 minterms\nReached[62]: 151 nodes 1 leaves 3170 minterms\n3170\n3170\nFrom[63]: 50 nodes 1 leaves 88 minterms\nReached[63]: 148 nodes 1 leaves 3258 minterms\n3258\n3258\nFrom[64]: 46 nodes 1 leaves 88 minterms\nReached[64]: 147 nodes 1 leaves 3346 minterms\n3346\n3346\nFrom[65]: 48 nodes 1 leaves 88 minterms\nReached[65]: 145 nodes 1 leaves 3434 minterms\n3434\n3434\nFrom[66]: 52 nodes 1 leaves 88 minterms\nReached[66]: 155 nodes 1 leaves 3522 minterms\n3522\n3522\nFrom[67]: 54 nodes 1 leaves 88 minterms\nReached[67]: 147 nodes 1 leaves 3610 minterms\n3610\n3610\nFrom[68]: 47 nodes 1 leaves 88 minterms\nReached[68]: 140 nodes 1 leaves 3698 minterms\n3698\n3698\nFrom[69]: 50 nodes 1 leaves 88 minterms\nReached[69]: 136 nodes 1 leaves 3786 minterms\n3786\n3786\nFrom[70]: 47 nodes 1 leaves 80 minterms\nReached[70]: 146 nodes 1 leaves 3866 minterms\n3866\n3866\nFrom[71]: 47 nodes 1 leaves 88 minterms\nReached[71]: 149 nodes 1 leaves 3954 minterms\n3954\n3954\nFrom[72]: 46 nodes 1 leaves 88 minterms\nReached[72]: 153 nodes 1 leaves 4042 minterms\n4042\n4042\nFrom[73]: 49 nodes 1 leaves 88 minterms\nReached[73]: 150 nodes 1 leaves 4130 minterms\n4130\n4130\nFrom[74]: 45 nodes 1 leaves 88 minterms\nReached[74]: 148 nodes 1 leaves 4218 minterms\n4218\n4218\nFrom[75]: 47 nodes 1 leaves 88 minterms\nReached[75]: 146 nodes 1 leaves 4306 minterms\n4306\n4306\nFrom[76]: 49 nodes 1 leaves 88 minterms\nReached[76]: 154 nodes 1 leaves 4394 minterms\n4394\n4394\nFrom[77]: 51 nodes 1 leaves 88 minterms\nReached[77]: 146 nodes 1 leaves 4482 minterms\n4482\n4482\nFrom[78]: 45 nodes 1 leaves 88 minterms\nReached[78]: 140 nodes 1 leaves 4570 minterms\n4570\n4570\nFrom[79]: 48 nodes 1 leaves 88 minterms\nReached[79]: 136 nodes 1 leaves 4658 minterms\n4658\n4658\nFrom[80]: 47 nodes 1 leaves 80 minterms\nReached[80]: 146 nodes 1 leaves 4738 minterms\n4738\n4738\nFrom[81]: 50 nodes 1 leaves 88 minterms\nReached[81]: 152 nodes 1 leaves 4826 minterms\n4826\n4826\nFrom[82]: 54 nodes 1 leaves 92 minterms\nReached[82]: 170 nodes 1 leaves 4918 minterms\n4918\n4918\nFrom[83]: 57 nodes 1 leaves 92 minterms\nReached[83]: 167 nodes 1 leaves 5010 minterms\n5010\n5010\nFrom[84]: 53 nodes 1 leaves 92 minterms\nReached[84]: 165 nodes 1 leaves 5102 minterms\n5102\n5102\nFrom[85]: 55 nodes 1 leaves 92 minterms\nReached[85]: 163 nodes 1 leaves 5194 minterms\n5194\n5194\nFrom[86]: 63 nodes 1 leaves 92 minterms\nReached[86]: 172 nodes 1 leaves 5286 minterms\n5286\n5286\nFrom[87]: 65 nodes 1 leaves 92 minterms\nReached[87]: 164 nodes 1 leaves 5378 minterms\n5378\n5378\nFrom[88]: 56 nodes 1 leaves 92 minterms\nReached[88]: 156 nodes 1 leaves 5470 minterms\n5470\n5470\nFrom[89]: 59 nodes 1 leaves 92 minterms\nReached[89]: 150 nodes 1 leaves 5562 minterms\n5562\n5562\nFrom[90]: 53 nodes 1 leaves 80 minterms\nReached[90]: 156 nodes 1 leaves 5642 minterms\n5642\n5642\nFrom[91]: 42 nodes 1 leaves 92 minterms\nReached[91]: 157 nodes 1 leaves 5734 minterms\n5734\n5734\nFrom[92]: 50 nodes 1 leaves 92 minterms\nReached[92]: 171 nodes 1 leaves 5826 minterms\n5826\n5826\nFrom[93]: 53 nodes 1 leaves 92 minterms\nReached[93]: 167 nodes 1 leaves 5918 minterms\n5918\n5918\nFrom[94]: 49 nodes 1 leaves 92 minterms\nReached[94]: 165 nodes 1 leaves 6010 minterms\n6010\n6010\nFrom[95]: 51 nodes 1 leaves 92 minterms\nReached[95]: 163 nodes 1 leaves 6102 minterms\n6102\n6102\nFrom[96]: 53 nodes 1 leaves 92 minterms\nReached[96]: 169 nodes 1 leaves 6194 minterms\n6194\n6194\nFrom[97]: 55 nodes 1 leaves 92 minterms\nReached[97]: 161 nodes 1 leaves 6286 minterms\n6286\n6286\nFrom[98]: 49 nodes 1 leaves 92 minterms\nReached[98]: 155 nodes 1 leaves 6378 minterms\n6378\n6378\nFrom[99]: 52 nodes 1 leaves 92 minterms\nReached[99]: 151 nodes 1 leaves 6470 minterms\n6470\n6470\nFrom[100]: 52 nodes 1 leaves 80 minterms\nReached[100]: 159 nodes 1 leaves 6550 minterms\n6550\n6550\nFrom[101]: 48 nodes 1 leaves 88 minterms\nReached[101]: 162 nodes 1 leaves 6638 minterms\n6638\n6638\nFrom[102]: 48 nodes 1 leaves 80 minterms\nReached[102]: 166 nodes 1 leaves 6718 minterms\n6718\n6718\nFrom[103]: 51 nodes 1 leaves 76 minterms\nReached[103]: 162 nodes 1 leaves 6794 minterms\n6794\n6794\nFrom[104]: 47 nodes 1 leaves 72 minterms\nReached[104]: 160 nodes 1 leaves 6866 minterms\n6866\n6866\nFrom[105]: 49 nodes 1 leaves 68 minterms\nReached[105]: 158 nodes 1 leaves 6934 minterms\n6934\n6934\nFrom[106]: 52 nodes 1 leaves 64 minterms\nReached[106]: 164 nodes 1 leaves 6998 minterms\n6998\n6998\nFrom[107]: 54 nodes 1 leaves 60 minterms\nReached[107]: 156 nodes 1 leaves 7058 minterms\n7058\n7058\nFrom[108]: 46 nodes 1 leaves 56 minterms\nReached[108]: 149 nodes 1 leaves 7114 minterms\n7114\n7114\nFrom[109]: 49 nodes 1 leaves 52 minterms\nReached[109]: 143 nodes 1 leaves 7166 minterms\n7166\n7166\nFrom[110]: 50 nodes 1 leaves 43 minterms\nReached[110]: 142 nodes 1 leaves 7209 minterms\n7209\n7209\nFrom[111]: 37 nodes 1 leaves 48 minterms\nReached[111]: 145 nodes 1 leaves 7257 minterms\n7257\n7257\nFrom[112]: 36 nodes 1 leaves 48 minterms\nReached[112]: 149 nodes 1 leaves 7305 minterms\n7305\n7305\nFrom[113]: 39 nodes 1 leaves 48 minterms\nReached[113]: 146 nodes 1 leaves 7353 minterms\n7353\n7353\nFrom[114]: 36 nodes 1 leaves 48 minterms\nReached[114]: 144 nodes 1 leaves 7401 minterms\n7401\n7401\nFrom[115]: 35 nodes 1 leaves 48 minterms\nReached[115]: 143 nodes 1 leaves 7449 minterms\n7449\n7449\nFrom[116]: 38 nodes 1 leaves 48 minterms\nReached[116]: 147 nodes 1 leaves 7497 minterms\n7497\n7497\nFrom[117]: 40 nodes 1 leaves 48 minterms\nReached[117]: 141 nodes 1 leaves 7545 minterms\n7545\n7545\nFrom[118]: 36 nodes 1 leaves 48 minterms\nReached[118]: 135 nodes 1 leaves 7593 minterms\n7593\n7593\nFrom[119]: 35 nodes 1 leaves 48 minterms\nReached[119]: 135 nodes 1 leaves 7641 minterms\n7641\n7641\nFrom[120]: 36 nodes 1 leaves 40 minterms\nReached[120]: 142 nodes 1 leaves 7681 minterms\n7681\n7681\nFrom[121]: 38 nodes 1 leaves 48 minterms\nReached[121]: 146 nodes 1 leaves 7729 minterms\n7729\n7729\nFrom[122]: 37 nodes 1 leaves 48 minterms\nReached[122]: 150 nodes 1 leaves 7777 minterms\n7777\n7777\nFrom[123]: 40 nodes 1 leaves 48 minterms\nReached[123]: 147 nodes 1 leaves 7825 minterms\n7825\n7825\nFrom[124]: 37 nodes 1 leaves 48 minterms\nReached[124]: 145 nodes 1 leaves 7873 minterms\n7873\n7873\nFrom[125]: 36 nodes 1 leaves 48 minterms\nReached[125]: 144 nodes 1 leaves 7921 minterms\n7921\n7921\nFrom[126]: 40 nodes 1 leaves 48 minterms\nReached[126]: 149 nodes 1 leaves 7969 minterms\n7969\n7969\nFrom[127]: 42 nodes 1 leaves 48 minterms\nReached[127]: 143 nodes 1 leaves 8017 minterms\n8017\n8017\nFrom[128]: 38 nodes 1 leaves 48 minterms\nReached[128]: 136 nodes 1 leaves 8065 minterms\n8065\n8065\nFrom[129]: 36 nodes 1 leaves 48 minterms\nReached[129]: 135 nodes 1 leaves 8113 minterms\n8113\n8113\nFrom[130]: 36 nodes 1 leaves 40 minterms\nReached[130]: 142 nodes 1 leaves 8153 minterms\n8153\n8153\nFrom[131]: 37 nodes 1 leaves 48 minterms\nReached[131]: 145 nodes 1 leaves 8201 minterms\n8201\n8201\nFrom[132]: 36 nodes 1 leaves 48 minterms\nReached[132]: 149 nodes 1 leaves 8249 minterms\n8249\n8249\nFrom[133]: 39 nodes 1 leaves 48 minterms\nReached[133]: 146 nodes 1 leaves 8297 minterms\n8297\n8297\nFrom[134]: 36 nodes 1 leaves 48 minterms\nReached[134]: 144 nodes 1 leaves 8345 minterms\n8345\n8345\nFrom[135]: 35 nodes 1 leaves 48 minterms\nReached[135]: 143 nodes 1 leaves 8393 minterms\n8393\n8393\nFrom[136]: 38 nodes 1 leaves 48 minterms\nReached[136]: 147 nodes 1 leaves 8441 minterms\n8441\n8441\nFrom[137]: 40 nodes 1 leaves 48 minterms\nReached[137]: 141 nodes 1 leaves 8489 minterms\n8489\n8489\nFrom[138]: 36 nodes 1 leaves 48 minterms\nReached[138]: 135 nodes 1 leaves 8537 minterms\n8537\n8537\nFrom[139]: 35 nodes 1 leaves 48 minterms\nReached[139]: 135 nodes 1 leaves 8585 minterms\n8585\n8585\nFrom[140]: 36 nodes 1 leaves 40 minterms\nReached[140]: 142 nodes 1 leaves 8625 minterms\n8625\n8625\nFrom[141]: 36 nodes 1 leaves 44 minterms\nReached[141]: 141 nodes 1 leaves 8669 minterms\n8669\n8669\nFrom[142]: 35 nodes 1 leaves 40 minterms\nReached[142]: 142 nodes 1 leaves 8709 minterms\n8709\n8709\nFrom[143]: 36 nodes 1 leaves 36 minterms\nReached[143]: 137 nodes 1 leaves 8745 minterms\n8745\n8745\nFrom[144]: 34 nodes 1 leaves 32 minterms\nReached[144]: 132 nodes 1 leaves 8777 minterms\n8777\n8777\nFrom[145]: 33 nodes 1 leaves 28 minterms\nReached[145]: 127 nodes 1 leaves 8805 minterms\n8805\n8805\nFrom[146]: 34 nodes 1 leaves 20 minterms\nReached[146]: 125 nodes 1 leaves 8825 minterms\n8825\n8825\nFrom[147]: 35 nodes 1 leaves 16 minterms\nReached[147]: 118 nodes 1 leaves 8841 minterms\n8841\n8841\nFrom[148]: 32 nodes 1 leaves 12 minterms\nReached[148]: 108 nodes 1 leaves 8853 minterms\n8853\n8853\nFrom[149]: 19 nodes 1 leaves 8 minterms\nReached[149]: 100 nodes 1 leaves 8861 minterms\n8861\n8861\nFrom[150]: 20 nodes 1 leaves 4 minterms\nReached[150]: 95 nodes 1 leaves 8865 minterms\n8865\n8865\ndepth = 150\nR: 95 nodes 1 leaves 8865 minterms\nBuilding transition relation. Time = 0.02 sec\nTransition relation: 21 parts 21 latches 229 nodes\nComputing SCCs. Time = 0.02 sec\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 40 nodes 1 leaves 5 minterms\nReached[1]: 56 nodes 1 leaves 6 minterms\nFrom[2]: 19 nodes 1 leaves 8 minterms\nReached[2]: 59 nodes 1 leaves 14 minterms\nFrom[3]: 20 nodes 1 leaves 12 minterms\nReached[3]: 61 nodes 1 leaves 26 minterms\nFrom[4]: 18 nodes 1 leaves 16 minterms\nReached[4]: 63 nodes 1 leaves 42 minterms\nFrom[5]: 20 nodes 1 leaves 20 minterms\nReached[5]: 68 nodes 1 leaves 62 minterms\nFrom[6]: 19 nodes 1 leaves 24 minterms\nReached[6]: 71 nodes 1 leaves 86 minterms\nFrom[7]: 20 nodes 1 leaves 28 minterms\nReached[7]: 70 nodes 1 leaves 114 minterms\nFrom[8]: 17 nodes 1 leaves 32 minterms\nReached[8]: 71 nodes 1 leaves 146 minterms\nFrom[9]: 20 nodes 1 leaves 36 minterms\nReached[9]: 77 nodes 1 leaves 182 minterms\nFrom[10]: 22 nodes 1 leaves 36 minterms\nReached[10]: 78 nodes 1 leaves 218 minterms\nFrom[11]: 26 nodes 1 leaves 40 minterms\nReached[11]: 81 nodes 1 leaves 258 minterms\nFrom[12]: 22 nodes 1 leaves 40 minterms\nReached[12]: 85 nodes 1 leaves 298 minterms\nFrom[13]: 26 nodes 1 leaves 40 minterms\nReached[13]: 82 nodes 1 leaves 338 minterms\nFrom[14]: 22 nodes 1 leaves 40 minterms\nReached[14]: 83 nodes 1 leaves 378 minterms\nFrom[15]: 26 nodes 1 leaves 40 minterms\nReached[15]: 84 nodes 1 leaves 418 minterms\nFrom[16]: 23 nodes 1 leaves 40 minterms\nReached[16]: 85 nodes 1 leaves 458 minterms\nFrom[17]: 26 nodes 1 leaves 40 minterms\nReached[17]: 79 nodes 1 leaves 498 minterms\nFrom[18]: 20 nodes 1 leaves 40 minterms\nReached[18]: 77 nodes 1 leaves 538 minterms\nFrom[19]: 24 nodes 1 leaves 40 minterms\nReached[19]: 80 nodes 1 leaves 578 minterms\nFrom[20]: 19 nodes 1 leaves 40 minterms\nReached[20]: 81 nodes 1 leaves 618 minterms\nFrom[21]: 27 nodes 1 leaves 40 minterms\nReached[21]: 85 nodes 1 leaves 658 minterms\nFrom[22]: 23 nodes 1 leaves 40 minterms\nReached[22]: 89 nodes 1 leaves 698 minterms\nFrom[23]: 27 nodes 1 leaves 40 minterms\nReached[23]: 86 nodes 1 leaves 738 minterms\nFrom[24]: 23 nodes 1 leaves 40 minterms\nReached[24]: 87 nodes 1 leaves 778 minterms\nFrom[25]: 27 nodes 1 leaves 40 minterms\nReached[25]: 88 nodes 1 leaves 818 minterms\nFrom[26]: 24 nodes 1 leaves 40 minterms\nReached[26]: 89 nodes 1 leaves 858 minterms\nFrom[27]: 27 nodes 1 leaves 40 minterms\nReached[27]: 83 nodes 1 leaves 898 minterms\nFrom[28]: 21 nodes 1 leaves 40 minterms\nReached[28]: 81 nodes 1 leaves 938 minterms\nFrom[29]: 25 nodes 1 leaves 40 minterms\nReached[29]: 80 nodes 1 leaves 978 minterms\nFrom[30]: 19 nodes 1 leaves 40 minterms\nReached[30]: 81 nodes 1 leaves 1018 minterms\nFrom[31]: 26 nodes 1 leaves 40 minterms\nReached[31]: 84 nodes 1 leaves 1058 minterms\nFrom[32]: 36 nodes 1 leaves 44 minterms\nReached[32]: 101 nodes 1 leaves 1102 minterms\nFrom[33]: 39 nodes 1 leaves 44 minterms\nReached[33]: 98 nodes 1 leaves 1146 minterms\nFrom[34]: 36 nodes 1 leaves 44 minterms\nReached[34]: 99 nodes 1 leaves 1190 minterms\nFrom[35]: 38 nodes 1 leaves 44 minterms\nReached[35]: 100 nodes 1 leaves 1234 minterms\nFrom[36]: 37 nodes 1 leaves 44 minterms\nReached[36]: 101 nodes 1 leaves 1278 minterms\nFrom[37]: 39 nodes 1 leaves 44 minterms\nReached[37]: 95 nodes 1 leaves 1322 minterms\nFrom[38]: 34 nodes 1 leaves 44 minterms\nReached[38]: 93 nodes 1 leaves 1366 minterms\nFrom[39]: 35 nodes 1 leaves 44 minterms\nReached[39]: 93 nodes 1 leaves 1410 minterms\nFrom[40]: 36 nodes 1 leaves 40 minterms\nReached[40]: 96 nodes 1 leaves 1450 minterms\nFrom[41]: 25 nodes 1 leaves 44 minterms\nReached[41]: 100 nodes 1 leaves 1494 minterms\nFrom[42]: 43 nodes 1 leaves 52 minterms\nReached[42]: 120 nodes 1 leaves 1546 minterms\nFrom[43]: 46 nodes 1 leaves 56 minterms\nReached[43]: 117 nodes 1 leaves 1602 minterms\nFrom[44]: 43 nodes 1 leaves 60 minterms\nReached[44]: 118 nodes 1 leaves 1662 minterms\nFrom[45]: 45 nodes 1 leaves 64 minterms\nReached[45]: 119 nodes 1 leaves 1726 minterms\nFrom[46]: 60 nodes 1 leaves 72 minterms\nReached[46]: 138 nodes 1 leaves 1798 minterms\nFrom[47]: 62 nodes 1 leaves 76 minterms\nReached[47]: 132 nodes 1 leaves 1874 minterms\nFrom[48]: 57 nodes 1 leaves 80 minterms\nReached[48]: 130 nodes 1 leaves 1954 minterms\nFrom[49]: 58 nodes 1 leaves 84 minterms\nReached[49]: 130 nodes 1 leaves 2038 minterms\nFrom[50]: 59 nodes 1 leaves 76 minterms\nReached[50]: 138 nodes 1 leaves 2114 minterms\nFrom[51]: 44 nodes 1 leaves 96 minterms\nReached[51]: 140 nodes 1 leaves 2210 minterms\nFrom[52]: 46 nodes 1 leaves 88 minterms\nReached[52]: 144 nodes 1 leaves 2298 minterms\nFrom[53]: 49 nodes 1 leaves 88 minterms\nReached[53]: 141 nodes 1 leaves 2386 minterms\nFrom[54]: 45 nodes 1 leaves 88 minterms\nReached[54]: 140 nodes 1 leaves 2474 minterms\nFrom[55]: 47 nodes 1 leaves 88 minterms\nReached[55]: 138 nodes 1 leaves 2562 minterms\nFrom[56]: 49 nodes 1 leaves 88 minterms\nReached[56]: 146 nodes 1 leaves 2650 minterms\nFrom[57]: 51 nodes 1 leaves 88 minterms\nReached[57]: 139 nodes 1 leaves 2738 minterms\nFrom[58]: 45 nodes 1 leaves 88 minterms\nReached[58]: 134 nodes 1 leaves 2826 minterms\nFrom[59]: 48 nodes 1 leaves 88 minterms\nReached[59]: 133 nodes 1 leaves 2914 minterms\nFrom[60]: 47 nodes 1 leaves 80 minterms\nReached[60]: 143 nodes 1 leaves 2994 minterms\nFrom[61]: 48 nodes 1 leaves 88 minterms\nReached[61]: 147 nodes 1 leaves 3082 minterms\nFrom[62]: 47 nodes 1 leaves 88 minterms\nReached[62]: 151 nodes 1 leaves 3170 minterms\nFrom[63]: 50 nodes 1 leaves 88 minterms\nReached[63]: 148 nodes 1 leaves 3258 minterms\nFrom[64]: 46 nodes 1 leaves 88 minterms\nReached[64]: 147 nodes 1 leaves 3346 minterms\nFrom[65]: 48 nodes 1 leaves 88 minterms\nReached[65]: 145 nodes 1 leaves 3434 minterms\nFrom[66]: 52 nodes 1 leaves 88 minterms\nReached[66]: 155 nodes 1 leaves 3522 minterms\nFrom[67]: 54 nodes 1 leaves 88 minterms\nReached[67]: 147 nodes 1 leaves 3610 minterms\nFrom[68]: 47 nodes 1 leaves 88 minterms\nReached[68]: 140 nodes 1 leaves 3698 minterms\nFrom[69]: 50 nodes 1 leaves 88 minterms\nReached[69]: 136 nodes 1 leaves 3786 minterms\nFrom[70]: 47 nodes 1 leaves 80 minterms\nReached[70]: 146 nodes 1 leaves 3866 minterms\nFrom[71]: 47 nodes 1 leaves 88 minterms\nReached[71]: 149 nodes 1 leaves 3954 minterms\nFrom[72]: 46 nodes 1 leaves 88 minterms\nReached[72]: 153 nodes 1 leaves 4042 minterms\nFrom[73]: 49 nodes 1 leaves 88 minterms\nReached[73]: 150 nodes 1 leaves 4130 minterms\nFrom[74]: 45 nodes 1 leaves 88 minterms\nReached[74]: 148 nodes 1 leaves 4218 minterms\nFrom[75]: 47 nodes 1 leaves 88 minterms\nReached[75]: 146 nodes 1 leaves 4306 minterms\nFrom[76]: 49 nodes 1 leaves 88 minterms\nReached[76]: 154 nodes 1 leaves 4394 minterms\nFrom[77]: 51 nodes 1 leaves 88 minterms\nReached[77]: 146 nodes 1 leaves 4482 minterms\nFrom[78]: 45 nodes 1 leaves 88 minterms\nReached[78]: 140 nodes 1 leaves 4570 minterms\nFrom[79]: 48 nodes 1 leaves 88 minterms\nReached[79]: 136 nodes 1 leaves 4658 minterms\nFrom[80]: 47 nodes 1 leaves 80 minterms\nReached[80]: 146 nodes 1 leaves 4738 minterms\nFrom[81]: 50 nodes 1 leaves 88 minterms\nReached[81]: 152 nodes 1 leaves 4826 minterms\nFrom[82]: 54 nodes 1 leaves 92 minterms\nReached[82]: 170 nodes 1 leaves 4918 minterms\nFrom[83]: 57 nodes 1 leaves 92 minterms\nReached[83]: 167 nodes 1 leaves 5010 minterms\nFrom[84]: 53 nodes 1 leaves 92 minterms\nReached[84]: 165 nodes 1 leaves 5102 minterms\nFrom[85]: 55 nodes 1 leaves 92 minterms\nReached[85]: 163 nodes 1 leaves 5194 minterms\nFrom[86]: 63 nodes 1 leaves 92 minterms\nReached[86]: 172 nodes 1 leaves 5286 minterms\nFrom[87]: 65 nodes 1 leaves 92 minterms\nReached[87]: 164 nodes 1 leaves 5378 minterms\nFrom[88]: 56 nodes 1 leaves 92 minterms\nReached[88]: 156 nodes 1 leaves 5470 minterms\nFrom[89]: 59 nodes 1 leaves 92 minterms\nReached[89]: 150 nodes 1 leaves 5562 minterms\nFrom[90]: 53 nodes 1 leaves 80 minterms\nReached[90]: 156 nodes 1 leaves 5642 minterms\nFrom[91]: 42 nodes 1 leaves 92 minterms\nReached[91]: 157 nodes 1 leaves 5734 minterms\nFrom[92]: 50 nodes 1 leaves 92 minterms\nReached[92]: 171 nodes 1 leaves 5826 minterms\nFrom[93]: 53 nodes 1 leaves 92 minterms\nReached[93]: 167 nodes 1 leaves 5918 minterms\nFrom[94]: 49 nodes 1 leaves 92 minterms\nReached[94]: 165 nodes 1 leaves 6010 minterms\nFrom[95]: 51 nodes 1 leaves 92 minterms\nReached[95]: 163 nodes 1 leaves 6102 minterms\nFrom[96]: 53 nodes 1 leaves 92 minterms\nReached[96]: 169 nodes 1 leaves 6194 minterms\nFrom[97]: 55 nodes 1 leaves 92 minterms\nReached[97]: 161 nodes 1 leaves 6286 minterms\nFrom[98]: 49 nodes 1 leaves 92 minterms\nReached[98]: 155 nodes 1 leaves 6378 minterms\nFrom[99]: 52 nodes 1 leaves 92 minterms\nReached[99]: 151 nodes 1 leaves 6470 minterms\nFrom[100]: 52 nodes 1 leaves 80 minterms\nReached[100]: 159 nodes 1 leaves 6550 minterms\nFrom[101]: 48 nodes 1 leaves 88 minterms\nReached[101]: 162 nodes 1 leaves 6638 minterms\nFrom[102]: 48 nodes 1 leaves 80 minterms\nReached[102]: 166 nodes 1 leaves 6718 minterms\nFrom[103]: 51 nodes 1 leaves 76 minterms\nReached[103]: 162 nodes 1 leaves 6794 minterms\nFrom[104]: 47 nodes 1 leaves 72 minterms\nReached[104]: 160 nodes 1 leaves 6866 minterms\nFrom[105]: 49 nodes 1 leaves 68 minterms\nReached[105]: 158 nodes 1 leaves 6934 minterms\nFrom[106]: 52 nodes 1 leaves 64 minterms\nReached[106]: 164 nodes 1 leaves 6998 minterms\nFrom[107]: 54 nodes 1 leaves 60 minterms\nReached[107]: 156 nodes 1 leaves 7058 minterms\nFrom[108]: 46 nodes 1 leaves 56 minterms\nReached[108]: 149 nodes 1 leaves 7114 minterms\nFrom[109]: 49 nodes 1 leaves 52 minterms\nReached[109]: 143 nodes 1 leaves 7166 minterms\nFrom[110]: 50 nodes 1 leaves 43 minterms\nReached[110]: 142 nodes 1 leaves 7209 minterms\nFrom[111]: 37 nodes 1 leaves 48 minterms\nReached[111]: 145 nodes 1 leaves 7257 minterms\nFrom[112]: 36 nodes 1 leaves 48 minterms\nReached[112]: 149 nodes 1 leaves 7305 minterms\nFrom[113]: 39 nodes 1 leaves 48 minterms\nReached[113]: 146 nodes 1 leaves 7353 minterms\nFrom[114]: 36 nodes 1 leaves 48 minterms\nReached[114]: 144 nodes 1 leaves 7401 minterms\nFrom[115]: 35 nodes 1 leaves 48 minterms\nReached[115]: 143 nodes 1 leaves 7449 minterms\nFrom[116]: 38 nodes 1 leaves 48 minterms\nReached[116]: 147 nodes 1 leaves 7497 minterms\nFrom[117]: 40 nodes 1 leaves 48 minterms\nReached[117]: 141 nodes 1 leaves 7545 minterms\nFrom[118]: 36 nodes 1 leaves 48 minterms\nReached[118]: 135 nodes 1 leaves 7593 minterms\nFrom[119]: 35 nodes 1 leaves 48 minterms\nReached[119]: 135 nodes 1 leaves 7641 minterms\nFrom[120]: 36 nodes 1 leaves 40 minterms\nReached[120]: 142 nodes 1 leaves 7681 minterms\nFrom[121]: 38 nodes 1 leaves 48 minterms\nReached[121]: 146 nodes 1 leaves 7729 minterms\nFrom[122]: 37 nodes 1 leaves 48 minterms\nReached[122]: 150 nodes 1 leaves 7777 minterms\nFrom[123]: 40 nodes 1 leaves 48 minterms\nReached[123]: 147 nodes 1 leaves 7825 minterms\nFrom[124]: 37 nodes 1 leaves 48 minterms\nReached[124]: 145 nodes 1 leaves 7873 minterms\nFrom[125]: 36 nodes 1 leaves 48 minterms\nReached[125]: 144 nodes 1 leaves 7921 minterms\nFrom[126]: 40 nodes 1 leaves 48 minterms\nReached[126]: 149 nodes 1 leaves 7969 minterms\nFrom[127]: 42 nodes 1 leaves 48 minterms\nReached[127]: 143 nodes 1 leaves 8017 minterms\nFrom[128]: 38 nodes 1 leaves 48 minterms\nReached[128]: 136 nodes 1 leaves 8065 minterms\nFrom[129]: 36 nodes 1 leaves 48 minterms\nReached[129]: 135 nodes 1 leaves 8113 minterms\nFrom[130]: 36 nodes 1 leaves 40 minterms\nReached[130]: 142 nodes 1 leaves 8153 minterms\nFrom[131]: 37 nodes 1 leaves 48 minterms\nReached[131]: 145 nodes 1 leaves 8201 minterms\nFrom[132]: 36 nodes 1 leaves 48 minterms\nReached[132]: 149 nodes 1 leaves 8249 minterms\nFrom[133]: 39 nodes 1 leaves 48 minterms\nReached[133]: 146 nodes 1 leaves 8297 minterms\nFrom[134]: 36 nodes 1 leaves 48 minterms\nReached[134]: 144 nodes 1 leaves 8345 minterms\nFrom[135]: 35 nodes 1 leaves 48 minterms\nReached[135]: 143 nodes 1 leaves 8393 minterms\nFrom[136]: 38 nodes 1 leaves 48 minterms\nReached[136]: 147 nodes 1 leaves 8441 minterms\nFrom[137]: 40 nodes 1 leaves 48 minterms\nReached[137]: 141 nodes 1 leaves 8489 minterms\nFrom[138]: 36 nodes 1 leaves 48 minterms\nReached[138]: 135 nodes 1 leaves 8537 minterms\nFrom[139]: 35 nodes 1 leaves 48 minterms\nReached[139]: 135 nodes 1 leaves 8585 minterms\nFrom[140]: 36 nodes 1 leaves 40 minterms\nReached[140]: 142 nodes 1 leaves 8625 minterms\nFrom[141]: 36 nodes 1 leaves 44 minterms\nReached[141]: 141 nodes 1 leaves 8669 minterms\nFrom[142]: 35 nodes 1 leaves 40 minterms\nReached[142]: 142 nodes 1 leaves 8709 minterms\nFrom[143]: 36 nodes 1 leaves 36 minterms\nReached[143]: 137 nodes 1 leaves 8745 minterms\nFrom[144]: 34 nodes 1 leaves 32 minterms\nReached[144]: 132 nodes 1 leaves 8777 minterms\nFrom[145]: 33 nodes 1 leaves 28 minterms\nReached[145]: 127 nodes 1 leaves 8805 minterms\nFrom[146]: 34 nodes 1 leaves 20 minterms\nReached[146]: 125 nodes 1 leaves 8825 minterms\nFrom[147]: 35 nodes 1 leaves 16 minterms\nReached[147]: 118 nodes 1 leaves 8841 minterms\nFrom[148]: 32 nodes 1 leaves 12 minterms\nReached[148]: 108 nodes 1 leaves 8853 minterms\nFrom[149]: 19 nodes 1 leaves 8 minterms\nReached[149]: 100 nodes 1 leaves 8861 minterms\nFrom[150]: 20 nodes 1 leaves 4 minterms\nReached[150]: 95 nodes 1 leaves 8865 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[0]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 40 nodes 1 leaves 5 minterms\nReached[1]: 57 nodes 1 leaves 6 minterms\nFrom[2]: 37 nodes 1 leaves 8 minterms\nReached[2]: 80 nodes 1 leaves 14 minterms\nFrom[3]: 37 nodes 1 leaves 16 minterms\nReached[3]: 89 nodes 1 leaves 30 minterms\nFrom[4]: 37 nodes 1 leaves 24 minterms\nReached[4]: 95 nodes 1 leaves 54 minterms\nFrom[5]: 37 nodes 1 leaves 32 minterms\nReached[5]: 99 nodes 1 leaves 86 minterms\nFrom[6]: 38 nodes 1 leaves 40 minterms\nReached[6]: 105 nodes 1 leaves 126 minterms\nFrom[7]: 38 nodes 1 leaves 48 minterms\nReached[7]: 112 nodes 1 leaves 174 minterms\nFrom[8]: 37 nodes 1 leaves 56 minterms\nReached[8]: 114 nodes 1 leaves 230 minterms\nFrom[9]: 37 nodes 1 leaves 64 minterms\nReached[9]: 110 nodes 1 leaves 294 minterms\nFrom[10]: 39 nodes 1 leaves 72 minterms\nReached[10]: 111 nodes 1 leaves 366 minterms\nFrom[11]: 47 nodes 1 leaves 76 minterms\nReached[11]: 123 nodes 1 leaves 442 minterms\nFrom[12]: 67 nodes 1 leaves 84 minterms\nReached[12]: 149 nodes 1 leaves 526 minterms\nFrom[13]: 63 nodes 1 leaves 96 minterms\nReached[13]: 150 nodes 1 leaves 622 minterms\nFrom[14]: 64 nodes 1 leaves 100 minterms\nReached[14]: 152 nodes 1 leaves 722 minterms\nFrom[15]: 62 nodes 1 leaves 104 minterms\nReached[15]: 152 nodes 1 leaves 826 minterms\nFrom[16]: 80 nodes 1 leaves 112 minterms\nReached[16]: 172 nodes 1 leaves 938 minterms\nFrom[17]: 79 nodes 1 leaves 116 minterms\nReached[17]: 171 nodes 1 leaves 1054 minterms\nFrom[18]: 77 nodes 1 leaves 120 minterms\nReached[18]: 167 nodes 1 leaves 1174 minterms\nFrom[19]: 72 nodes 1 leaves 124 minterms\nReached[19]: 160 nodes 1 leaves 1298 minterms\nFrom[20]: 72 nodes 1 leaves 132 minterms\nReached[20]: 160 nodes 1 leaves 1430 minterms\nFrom[21]: 57 nodes 1 leaves 136 minterms\nReached[21]: 169 nodes 1 leaves 1566 minterms\nFrom[22]: 71 nodes 1 leaves 120 minterms\nReached[22]: 183 nodes 1 leaves 1686 minterms\nFrom[23]: 66 nodes 1 leaves 128 minterms\nReached[23]: 183 nodes 1 leaves 1814 minterms\nFrom[24]: 66 nodes 1 leaves 128 minterms\nReached[24]: 183 nodes 1 leaves 1942 minterms\nFrom[25]: 64 nodes 1 leaves 128 minterms\nReached[25]: 180 nodes 1 leaves 2070 minterms\nFrom[26]: 70 nodes 1 leaves 128 minterms\nReached[26]: 189 nodes 1 leaves 2198 minterms\nFrom[27]: 69 nodes 1 leaves 128 minterms\nReached[27]: 186 nodes 1 leaves 2326 minterms\nFrom[28]: 66 nodes 1 leaves 128 minterms\nReached[28]: 179 nodes 1 leaves 2454 minterms\nFrom[29]: 63 nodes 1 leaves 128 minterms\nReached[29]: 167 nodes 1 leaves 2582 minterms\nFrom[30]: 62 nodes 1 leaves 128 minterms\nReached[30]: 165 nodes 1 leaves 2710 minterms\nFrom[31]: 61 nodes 1 leaves 128 minterms\nReached[31]: 175 nodes 1 leaves 2838 minterms\nFrom[32]: 71 nodes 1 leaves 120 minterms\nReached[32]: 183 nodes 1 leaves 2958 minterms\nFrom[33]: 79 nodes 1 leaves 128 minterms\nReached[33]: 184 nodes 1 leaves 3086 minterms\nFrom[34]: 76 nodes 1 leaves 124 minterms\nReached[34]: 182 nodes 1 leaves 3210 minterms\nFrom[35]: 76 nodes 1 leaves 120 minterms\nReached[35]: 177 nodes 1 leaves 3330 minterms\nFrom[36]: 82 nodes 1 leaves 116 minterms\nReached[36]: 184 nodes 1 leaves 3446 minterms\nFrom[37]: 83 nodes 1 leaves 112 minterms\nReached[37]: 177 nodes 1 leaves 3558 minterms\nFrom[38]: 77 nodes 1 leaves 108 minterms\nReached[38]: 166 nodes 1 leaves 3666 minterms\nFrom[39]: 77 nodes 1 leaves 104 minterms\nReached[39]: 154 nodes 1 leaves 3770 minterms\nFrom[40]: 71 nodes 1 leaves 96 minterms\nReached[40]: 151 nodes 1 leaves 3866 minterms\nFrom[41]: 61 nodes 1 leaves 92 minterms\nReached[41]: 151 nodes 1 leaves 3958 minterms\nFrom[42]: 67 nodes 1 leaves 84 minterms\nReached[42]: 154 nodes 1 leaves 4042 minterms\nFrom[43]: 49 nodes 1 leaves 88 minterms\nReached[43]: 152 nodes 1 leaves 4130 minterms\nFrom[44]: 45 nodes 1 leaves 88 minterms\nReached[44]: 153 nodes 1 leaves 4218 minterms\nFrom[45]: 47 nodes 1 leaves 88 minterms\nReached[45]: 149 nodes 1 leaves 4306 minterms\nFrom[46]: 49 nodes 1 leaves 88 minterms\nReached[46]: 157 nodes 1 leaves 4394 minterms\nFrom[47]: 51 nodes 1 leaves 88 minterms\nReached[47]: 153 nodes 1 leaves 4482 minterms\nFrom[48]: 45 nodes 1 leaves 88 minterms\nReached[48]: 150 nodes 1 leaves 4570 minterms\nFrom[49]: 48 nodes 1 leaves 88 minterms\nReached[49]: 140 nodes 1 leaves 4658 minterms\nFrom[50]: 43 nodes 1 leaves 88 minterms\nReached[50]: 142 nodes 1 leaves 4746 minterms\nFrom[51]: 50 nodes 1 leaves 88 minterms\nReached[51]: 150 nodes 1 leaves 4834 minterms\nFrom[52]: 62 nodes 1 leaves 80 minterms\nReached[52]: 172 nodes 1 leaves 4914 minterms\nFrom[53]: 57 nodes 1 leaves 92 minterms\nReached[53]: 170 nodes 1 leaves 5006 minterms\nFrom[54]: 53 nodes 1 leaves 92 minterms\nReached[54]: 171 nodes 1 leaves 5098 minterms\nFrom[55]: 55 nodes 1 leaves 92 minterms\nReached[55]: 167 nodes 1 leaves 5190 minterms\nFrom[56]: 63 nodes 1 leaves 92 minterms\nReached[56]: 176 nodes 1 leaves 5282 minterms\nFrom[57]: 65 nodes 1 leaves 92 minterms\nReached[57]: 172 nodes 1 leaves 5374 minterms\nFrom[58]: 56 nodes 1 leaves 92 minterms\nReached[58]: 167 nodes 1 leaves 5466 minterms\nFrom[59]: 59 nodes 1 leaves 92 minterms\nReached[59]: 155 nodes 1 leaves 5558 minterms\nFrom[60]: 48 nodes 1 leaves 92 minterms\nReached[60]: 151 nodes 1 leaves 5650 minterms\nFrom[61]: 42 nodes 1 leaves 92 minterms\nReached[61]: 155 nodes 1 leaves 5742 minterms\nFrom[62]: 55 nodes 1 leaves 80 minterms\nReached[62]: 173 nodes 1 leaves 5822 minterms\nFrom[63]: 53 nodes 1 leaves 92 minterms\nReached[63]: 170 nodes 1 leaves 5914 minterms\nFrom[64]: 49 nodes 1 leaves 92 minterms\nReached[64]: 171 nodes 1 leaves 6006 minterms\nFrom[65]: 51 nodes 1 leaves 92 minterms\nReached[65]: 167 nodes 1 leaves 6098 minterms\nFrom[66]: 53 nodes 1 leaves 92 minterms\nReached[66]: 173 nodes 1 leaves 6190 minterms\nFrom[67]: 55 nodes 1 leaves 92 minterms\nReached[67]: 169 nodes 1 leaves 6282 minterms\nFrom[68]: 49 nodes 1 leaves 92 minterms\nReached[68]: 166 nodes 1 leaves 6374 minterms\nFrom[69]: 52 nodes 1 leaves 92 minterms\nReached[69]: 156 nodes 1 leaves 6466 minterms\nFrom[70]: 47 nodes 1 leaves 92 minterms\nReached[70]: 154 nodes 1 leaves 6558 minterms\nFrom[71]: 48 nodes 1 leaves 88 minterms\nReached[71]: 160 nodes 1 leaves 6646 minterms\nFrom[72]: 66 nodes 1 leaves 75 minterms\nReached[72]: 156 nodes 1 leaves 6721 minterms\nFrom[73]: 51 nodes 1 leaves 76 minterms\nReached[73]: 153 nodes 1 leaves 6797 minterms\nFrom[74]: 47 nodes 1 leaves 72 minterms\nReached[74]: 154 nodes 1 leaves 6869 minterms\nFrom[75]: 49 nodes 1 leaves 68 minterms\nReached[75]: 150 nodes 1 leaves 6937 minterms\nFrom[76]: 52 nodes 1 leaves 64 minterms\nReached[76]: 156 nodes 1 leaves 7001 minterms\nFrom[77]: 54 nodes 1 leaves 60 minterms\nReached[77]: 152 nodes 1 leaves 7061 minterms\nFrom[78]: 46 nodes 1 leaves 56 minterms\nReached[78]: 148 nodes 1 leaves 7117 minterms\nFrom[79]: 49 nodes 1 leaves 52 minterms\nReached[79]: 136 nodes 1 leaves 7169 minterms\nFrom[80]: 34 nodes 1 leaves 48 minterms\nReached[80]: 135 nodes 1 leaves 7217 minterms\nFrom[81]: 37 nodes 1 leaves 48 minterms\nReached[81]: 140 nodes 1 leaves 7265 minterms\nFrom[82]: 40 nodes 1 leaves 40 minterms\nReached[82]: 147 nodes 1 leaves 7305 minterms\nFrom[83]: 39 nodes 1 leaves 48 minterms\nReached[83]: 145 nodes 1 leaves 7353 minterms\nFrom[84]: 36 nodes 1 leaves 48 minterms\nReached[84]: 146 nodes 1 leaves 7401 minterms\nFrom[85]: 35 nodes 1 leaves 48 minterms\nReached[85]: 143 nodes 1 leaves 7449 minterms\nFrom[86]: 38 nodes 1 leaves 48 minterms\nReached[86]: 147 nodes 1 leaves 7497 minterms\nFrom[87]: 40 nodes 1 leaves 48 minterms\nReached[87]: 145 nodes 1 leaves 7545 minterms\nFrom[88]: 36 nodes 1 leaves 48 minterms\nReached[88]: 142 nodes 1 leaves 7593 minterms\nFrom[89]: 35 nodes 1 leaves 48 minterms\nReached[89]: 136 nodes 1 leaves 7641 minterms\nFrom[90]: 34 nodes 1 leaves 48 minterms\nReached[90]: 135 nodes 1 leaves 7689 minterms\nFrom[91]: 38 nodes 1 leaves 48 minterms\nReached[91]: 141 nodes 1 leaves 7737 minterms\nFrom[92]: 41 nodes 1 leaves 40 minterms\nReached[92]: 148 nodes 1 leaves 7777 minterms\nFrom[93]: 40 nodes 1 leaves 48 minterms\nReached[93]: 146 nodes 1 leaves 7825 minterms\nFrom[94]: 37 nodes 1 leaves 48 minterms\nReached[94]: 147 nodes 1 leaves 7873 minterms\nFrom[95]: 36 nodes 1 leaves 48 minterms\nReached[95]: 144 nodes 1 leaves 7921 minterms\nFrom[96]: 40 nodes 1 leaves 48 minterms\nReached[96]: 149 nodes 1 leaves 7969 minterms\nFrom[97]: 42 nodes 1 leaves 48 minterms\nReached[97]: 147 nodes 1 leaves 8017 minterms\nFrom[98]: 38 nodes 1 leaves 48 minterms\nReached[98]: 143 nodes 1 leaves 8065 minterms\nFrom[99]: 36 nodes 1 leaves 48 minterms\nReached[99]: 136 nodes 1 leaves 8113 minterms\nFrom[100]: 34 nodes 1 leaves 48 minterms\nReached[100]: 135 nodes 1 leaves 8161 minterms\nFrom[101]: 37 nodes 1 leaves 48 minterms\nReached[101]: 140 nodes 1 leaves 8209 minterms\nFrom[102]: 40 nodes 1 leaves 40 minterms\nReached[102]: 147 nodes 1 leaves 8249 minterms\nFrom[103]: 39 nodes 1 leaves 48 minterms\nReached[103]: 145 nodes 1 leaves 8297 minterms\nFrom[104]: 36 nodes 1 leaves 48 minterms\nReached[104]: 146 nodes 1 leaves 8345 minterms\nFrom[105]: 35 nodes 1 leaves 48 minterms\nReached[105]: 143 nodes 1 leaves 8393 minterms\nFrom[106]: 38 nodes 1 leaves 48 minterms\nReached[106]: 147 nodes 1 leaves 8441 minterms\nFrom[107]: 40 nodes 1 leaves 48 minterms\nReached[107]: 145 nodes 1 leaves 8489 minterms\nFrom[108]: 36 nodes 1 leaves 48 minterms\nReached[108]: 142 nodes 1 leaves 8537 minterms\nFrom[109]: 35 nodes 1 leaves 48 minterms\nReached[109]: 136 nodes 1 leaves 8585 minterms\nFrom[110]: 34 nodes 1 leaves 48 minterms\nReached[110]: 135 nodes 1 leaves 8633 minterms\nFrom[111]: 36 nodes 1 leaves 44 minterms\nReached[111]: 133 nodes 1 leaves 8677 minterms\nFrom[112]: 40 nodes 1 leaves 36 minterms\nReached[112]: 137 nodes 1 leaves 8713 minterms\nFrom[113]: 36 nodes 1 leaves 36 minterms\nReached[113]: 133 nodes 1 leaves 8749 minterms\nFrom[114]: 34 nodes 1 leaves 32 minterms\nReached[114]: 129 nodes 1 leaves 8781 minterms\nFrom[115]: 33 nodes 1 leaves 28 minterms\nReached[115]: 123 nodes 1 leaves 8809 minterms\nFrom[116]: 34 nodes 1 leaves 20 minterms\nReached[116]: 122 nodes 1 leaves 8829 minterms\nFrom[117]: 35 nodes 1 leaves 16 minterms\nReached[117]: 116 nodes 1 leaves 8845 minterms\nFrom[118]: 32 nodes 1 leaves 12 minterms\nReached[118]: 107 nodes 1 leaves 8857 minterms\nFrom[119]: 19 nodes 1 leaves 8 minterms\nReached[119]: 95 nodes 1 leaves 8865 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[1]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 40 nodes 1 leaves 5 minterms\nReached[1]: 59 nodes 1 leaves 6 minterms\nFrom[2]: 23 nodes 1 leaves 12 minterms\nReached[2]: 76 nodes 1 leaves 18 minterms\nFrom[3]: 23 nodes 1 leaves 20 minterms\nReached[3]: 80 nodes 1 leaves 38 minterms\nFrom[4]: 27 nodes 1 leaves 24 minterms\nReached[4]: 84 nodes 1 leaves 62 minterms\nFrom[5]: 27 nodes 1 leaves 32 minterms\nReached[5]: 83 nodes 1 leaves 94 minterms\nFrom[6]: 26 nodes 1 leaves 36 minterms\nReached[6]: 86 nodes 1 leaves 130 minterms\nFrom[7]: 27 nodes 1 leaves 40 minterms\nReached[7]: 87 nodes 1 leaves 170 minterms\nFrom[8]: 26 nodes 1 leaves 44 minterms\nReached[8]: 88 nodes 1 leaves 214 minterms\nFrom[9]: 28 nodes 1 leaves 40 minterms\nReached[9]: 89 nodes 1 leaves 254 minterms\nFrom[10]: 28 nodes 1 leaves 40 minterms\nReached[10]: 87 nodes 1 leaves 294 minterms\nFrom[11]: 31 nodes 1 leaves 40 minterms\nReached[11]: 89 nodes 1 leaves 334 minterms\nFrom[12]: 30 nodes 1 leaves 40 minterms\nReached[12]: 92 nodes 1 leaves 374 minterms\nFrom[13]: 30 nodes 1 leaves 40 minterms\nReached[13]: 95 nodes 1 leaves 414 minterms\nFrom[14]: 32 nodes 1 leaves 40 minterms\nReached[14]: 92 nodes 1 leaves 454 minterms\nFrom[15]: 30 nodes 1 leaves 40 minterms\nReached[15]: 94 nodes 1 leaves 494 minterms\nFrom[16]: 30 nodes 1 leaves 40 minterms\nReached[16]: 92 nodes 1 leaves 534 minterms\nFrom[17]: 27 nodes 1 leaves 40 minterms\nReached[17]: 92 nodes 1 leaves 574 minterms\nFrom[18]: 28 nodes 1 leaves 40 minterms\nReached[18]: 91 nodes 1 leaves 614 minterms\nFrom[19]: 28 nodes 1 leaves 40 minterms\nReached[19]: 92 nodes 1 leaves 654 minterms\nFrom[20]: 28 nodes 1 leaves 40 minterms\nReached[20]: 90 nodes 1 leaves 694 minterms\nFrom[21]: 32 nodes 1 leaves 40 minterms\nReached[21]: 92 nodes 1 leaves 734 minterms\nFrom[22]: 31 nodes 1 leaves 40 minterms\nReached[22]: 96 nodes 1 leaves 774 minterms\nFrom[23]: 31 nodes 1 leaves 40 minterms\nReached[23]: 99 nodes 1 leaves 814 minterms\nFrom[24]: 33 nodes 1 leaves 40 minterms\nReached[24]: 96 nodes 1 leaves 854 minterms\nFrom[25]: 31 nodes 1 leaves 40 minterms\nReached[25]: 98 nodes 1 leaves 894 minterms\nFrom[26]: 31 nodes 1 leaves 40 minterms\nReached[26]: 92 nodes 1 leaves 934 minterms\nFrom[27]: 27 nodes 1 leaves 40 minterms\nReached[27]: 92 nodes 1 leaves 974 minterms\nFrom[28]: 28 nodes 1 leaves 40 minterms\nReached[28]: 91 nodes 1 leaves 1014 minterms\nFrom[29]: 28 nodes 1 leaves 40 minterms\nReached[29]: 92 nodes 1 leaves 1054 minterms\nFrom[30]: 28 nodes 1 leaves 40 minterms\nReached[30]: 90 nodes 1 leaves 1094 minterms\nFrom[31]: 31 nodes 1 leaves 40 minterms\nReached[31]: 92 nodes 1 leaves 1134 minterms\nFrom[32]: 43 nodes 1 leaves 44 minterms\nReached[32]: 108 nodes 1 leaves 1178 minterms\nFrom[33]: 44 nodes 1 leaves 48 minterms\nReached[33]: 111 nodes 1 leaves 1226 minterms\nFrom[34]: 47 nodes 1 leaves 44 minterms\nReached[34]: 111 nodes 1 leaves 1270 minterms\nFrom[35]: 42 nodes 1 leaves 48 minterms\nReached[35]: 113 nodes 1 leaves 1318 minterms\nFrom[36]: 44 nodes 1 leaves 44 minterms\nReached[36]: 108 nodes 1 leaves 1362 minterms\nFrom[37]: 41 nodes 1 leaves 44 minterms\nReached[37]: 108 nodes 1 leaves 1406 minterms\nFrom[38]: 26 nodes 1 leaves 44 minterms\nReached[38]: 105 nodes 1 leaves 1450 minterms\nFrom[39]: 28 nodes 1 leaves 40 minterms\nReached[39]: 106 nodes 1 leaves 1490 minterms\nFrom[40]: 28 nodes 1 leaves 40 minterms\nReached[40]: 104 nodes 1 leaves 1530 minterms\nFrom[41]: 33 nodes 1 leaves 40 minterms\nReached[41]: 106 nodes 1 leaves 1570 minterms\nFrom[42]: 50 nodes 1 leaves 52 minterms\nReached[42]: 127 nodes 1 leaves 1622 minterms\nFrom[43]: 51 nodes 1 leaves 68 minterms\nReached[43]: 130 nodes 1 leaves 1690 minterms\nFrom[44]: 54 nodes 1 leaves 68 minterms\nReached[44]: 130 nodes 1 leaves 1758 minterms\nFrom[45]: 49 nodes 1 leaves 84 minterms\nReached[45]: 132 nodes 1 leaves 1842 minterms\nFrom[46]: 70 nodes 1 leaves 84 minterms\nReached[46]: 142 nodes 1 leaves 1926 minterms\nFrom[47]: 64 nodes 1 leaves 92 minterms\nReached[47]: 138 nodes 1 leaves 2018 minterms\nFrom[48]: 49 nodes 1 leaves 96 minterms\nReached[48]: 135 nodes 1 leaves 2114 minterms\nFrom[49]: 51 nodes 1 leaves 88 minterms\nReached[49]: 136 nodes 1 leaves 2202 minterms\nFrom[50]: 56 nodes 1 leaves 88 minterms\nReached[50]: 139 nodes 1 leaves 2290 minterms\nFrom[51]: 62 nodes 1 leaves 84 minterms\nReached[51]: 144 nodes 1 leaves 2374 minterms\nFrom[52]: 53 nodes 1 leaves 92 minterms\nReached[52]: 145 nodes 1 leaves 2466 minterms\nFrom[53]: 54 nodes 1 leaves 88 minterms\nReached[53]: 148 nodes 1 leaves 2554 minterms\nFrom[54]: 54 nodes 1 leaves 84 minterms\nReached[54]: 144 nodes 1 leaves 2638 minterms\nFrom[55]: 47 nodes 1 leaves 84 minterms\nReached[55]: 143 nodes 1 leaves 2722 minterms\nFrom[56]: 57 nodes 1 leaves 88 minterms\nReached[56]: 142 nodes 1 leaves 2810 minterms\nFrom[57]: 50 nodes 1 leaves 88 minterms\nReached[57]: 142 nodes 1 leaves 2898 minterms\nFrom[58]: 51 nodes 1 leaves 88 minterms\nReached[58]: 141 nodes 1 leaves 2986 minterms\nFrom[59]: 51 nodes 1 leaves 88 minterms\nReached[59]: 142 nodes 1 leaves 3074 minterms\nFrom[60]: 56 nodes 1 leaves 88 minterms\nReached[60]: 145 nodes 1 leaves 3162 minterms\nFrom[61]: 63 nodes 1 leaves 84 minterms\nReached[61]: 150 nodes 1 leaves 3246 minterms\nFrom[62]: 54 nodes 1 leaves 92 minterms\nReached[62]: 152 nodes 1 leaves 3338 minterms\nFrom[63]: 55 nodes 1 leaves 88 minterms\nReached[63]: 155 nodes 1 leaves 3426 minterms\nFrom[64]: 55 nodes 1 leaves 84 minterms\nReached[64]: 150 nodes 1 leaves 3510 minterms\nFrom[65]: 48 nodes 1 leaves 84 minterms\nReached[65]: 147 nodes 1 leaves 3594 minterms\nFrom[66]: 59 nodes 1 leaves 88 minterms\nReached[66]: 145 nodes 1 leaves 3682 minterms\nFrom[67]: 50 nodes 1 leaves 88 minterms\nReached[67]: 145 nodes 1 leaves 3770 minterms\nFrom[68]: 51 nodes 1 leaves 88 minterms\nReached[68]: 144 nodes 1 leaves 3858 minterms\nFrom[69]: 51 nodes 1 leaves 88 minterms\nReached[69]: 145 nodes 1 leaves 3946 minterms\nFrom[70]: 56 nodes 1 leaves 88 minterms\nReached[70]: 148 nodes 1 leaves 4034 minterms\nFrom[71]: 62 nodes 1 leaves 84 minterms\nReached[71]: 152 nodes 1 leaves 4118 minterms\nFrom[72]: 53 nodes 1 leaves 92 minterms\nReached[72]: 153 nodes 1 leaves 4210 minterms\nFrom[73]: 54 nodes 1 leaves 88 minterms\nReached[73]: 156 nodes 1 leaves 4298 minterms\nFrom[74]: 54 nodes 1 leaves 84 minterms\nReached[74]: 151 nodes 1 leaves 4382 minterms\nFrom[75]: 47 nodes 1 leaves 84 minterms\nReached[75]: 149 nodes 1 leaves 4466 minterms\nFrom[76]: 57 nodes 1 leaves 88 minterms\nReached[76]: 145 nodes 1 leaves 4554 minterms\nFrom[77]: 50 nodes 1 leaves 88 minterms\nReached[77]: 145 nodes 1 leaves 4642 minterms\nFrom[78]: 51 nodes 1 leaves 88 minterms\nReached[78]: 144 nodes 1 leaves 4730 minterms\nFrom[79]: 51 nodes 1 leaves 88 minterms\nReached[79]: 145 nodes 1 leaves 4818 minterms\nFrom[80]: 56 nodes 1 leaves 88 minterms\nReached[80]: 148 nodes 1 leaves 4906 minterms\nFrom[81]: 65 nodes 1 leaves 84 minterms\nReached[81]: 152 nodes 1 leaves 4990 minterms\nFrom[82]: 67 nodes 1 leaves 96 minterms\nReached[82]: 170 nodes 1 leaves 5086 minterms\nFrom[83]: 65 nodes 1 leaves 96 minterms\nReached[83]: 173 nodes 1 leaves 5182 minterms\nFrom[84]: 72 nodes 1 leaves 88 minterms\nReached[84]: 171 nodes 1 leaves 5270 minterms\nFrom[85]: 61 nodes 1 leaves 92 minterms\nReached[85]: 167 nodes 1 leaves 5362 minterms\nFrom[86]: 71 nodes 1 leaves 92 minterms\nReached[86]: 162 nodes 1 leaves 5454 minterms\nFrom[87]: 58 nodes 1 leaves 92 minterms\nReached[87]: 156 nodes 1 leaves 5546 minterms\nFrom[88]: 47 nodes 1 leaves 92 minterms\nReached[88]: 152 nodes 1 leaves 5638 minterms\nFrom[89]: 47 nodes 1 leaves 88 minterms\nReached[89]: 153 nodes 1 leaves 5726 minterms\nFrom[90]: 52 nodes 1 leaves 88 minterms\nReached[90]: 155 nodes 1 leaves 5814 minterms\nFrom[91]: 58 nodes 1 leaves 84 minterms\nReached[91]: 159 nodes 1 leaves 5898 minterms\nFrom[92]: 60 nodes 1 leaves 96 minterms\nReached[92]: 170 nodes 1 leaves 5994 minterms\nFrom[93]: 61 nodes 1 leaves 96 minterms\nReached[93]: 173 nodes 1 leaves 6090 minterms\nFrom[94]: 65 nodes 1 leaves 88 minterms\nReached[94]: 171 nodes 1 leaves 6178 minterms\nFrom[95]: 57 nodes 1 leaves 92 minterms\nReached[95]: 169 nodes 1 leaves 6270 minterms\nFrom[96]: 64 nodes 1 leaves 92 minterms\nReached[96]: 163 nodes 1 leaves 6362 minterms\nFrom[97]: 57 nodes 1 leaves 92 minterms\nReached[97]: 159 nodes 1 leaves 6454 minterms\nFrom[98]: 50 nodes 1 leaves 92 minterms\nReached[98]: 155 nodes 1 leaves 6546 minterms\nFrom[99]: 50 nodes 1 leaves 88 minterms\nReached[99]: 156 nodes 1 leaves 6634 minterms\nFrom[100]: 55 nodes 1 leaves 88 minterms\nReached[100]: 158 nodes 1 leaves 6722 minterms\nFrom[101]: 64 nodes 1 leaves 80 minterms\nReached[101]: 162 nodes 1 leaves 6802 minterms\nFrom[102]: 55 nodes 1 leaves 80 minterms\nReached[102]: 165 nodes 1 leaves 6882 minterms\nFrom[103]: 56 nodes 1 leaves 68 minterms\nReached[103]: 168 nodes 1 leaves 6950 minterms\nFrom[104]: 73 nodes 1 leaves 59 minterms\nReached[104]: 152 nodes 1 leaves 7009 minterms\nFrom[105]: 50 nodes 1 leaves 52 minterms\nReached[105]: 149 nodes 1 leaves 7061 minterms\nFrom[106]: 55 nodes 1 leaves 52 minterms\nReached[106]: 141 nodes 1 leaves 7113 minterms\nFrom[107]: 40 nodes 1 leaves 48 minterms\nReached[107]: 141 nodes 1 leaves 7161 minterms\nFrom[108]: 41 nodes 1 leaves 48 minterms\nReached[108]: 140 nodes 1 leaves 7209 minterms\nFrom[109]: 39 nodes 1 leaves 48 minterms\nReached[109]: 141 nodes 1 leaves 7257 minterms\nFrom[110]: 43 nodes 1 leaves 48 minterms\nReached[110]: 141 nodes 1 leaves 7305 minterms\nFrom[111]: 49 nodes 1 leaves 44 minterms\nReached[111]: 145 nodes 1 leaves 7349 minterms\nFrom[112]: 41 nodes 1 leaves 52 minterms\nReached[112]: 147 nodes 1 leaves 7401 minterms\nFrom[113]: 42 nodes 1 leaves 48 minterms\nReached[113]: 150 nodes 1 leaves 7449 minterms\nFrom[114]: 45 nodes 1 leaves 44 minterms\nReached[114]: 147 nodes 1 leaves 7493 minterms\nFrom[115]: 43 nodes 1 leaves 44 minterms\nReached[115]: 145 nodes 1 leaves 7537 minterms\nFrom[116]: 41 nodes 1 leaves 48 minterms\nReached[116]: 141 nodes 1 leaves 7585 minterms\nFrom[117]: 40 nodes 1 leaves 48 minterms\nReached[117]: 141 nodes 1 leaves 7633 minterms\nFrom[118]: 41 nodes 1 leaves 48 minterms\nReached[118]: 140 nodes 1 leaves 7681 minterms\nFrom[119]: 39 nodes 1 leaves 48 minterms\nReached[119]: 141 nodes 1 leaves 7729 minterms\nFrom[120]: 43 nodes 1 leaves 48 minterms\nReached[120]: 141 nodes 1 leaves 7777 minterms\nFrom[121]: 50 nodes 1 leaves 44 minterms\nReached[121]: 145 nodes 1 leaves 7821 minterms\nFrom[122]: 42 nodes 1 leaves 52 minterms\nReached[122]: 148 nodes 1 leaves 7873 minterms\nFrom[123]: 43 nodes 1 leaves 48 minterms\nReached[123]: 151 nodes 1 leaves 7921 minterms\nFrom[124]: 46 nodes 1 leaves 44 minterms\nReached[124]: 148 nodes 1 leaves 7965 minterms\nFrom[125]: 44 nodes 1 leaves 44 minterms\nReached[125]: 144 nodes 1 leaves 8009 minterms\nFrom[126]: 42 nodes 1 leaves 48 minterms\nReached[126]: 141 nodes 1 leaves 8057 minterms\nFrom[127]: 40 nodes 1 leaves 48 minterms\nReached[127]: 141 nodes 1 leaves 8105 minterms\nFrom[128]: 41 nodes 1 leaves 48 minterms\nReached[128]: 140 nodes 1 leaves 8153 minterms\nFrom[129]: 39 nodes 1 leaves 48 minterms\nReached[129]: 141 nodes 1 leaves 8201 minterms\nFrom[130]: 43 nodes 1 leaves 48 minterms\nReached[130]: 141 nodes 1 leaves 8249 minterms\nFrom[131]: 49 nodes 1 leaves 44 minterms\nReached[131]: 145 nodes 1 leaves 8293 minterms\nFrom[132]: 41 nodes 1 leaves 52 minterms\nReached[132]: 147 nodes 1 leaves 8345 minterms\nFrom[133]: 42 nodes 1 leaves 48 minterms\nReached[133]: 150 nodes 1 leaves 8393 minterms\nFrom[134]: 45 nodes 1 leaves 44 minterms\nReached[134]: 147 nodes 1 leaves 8437 minterms\nFrom[135]: 43 nodes 1 leaves 44 minterms\nReached[135]: 145 nodes 1 leaves 8481 minterms\nFrom[136]: 41 nodes 1 leaves 48 minterms\nReached[136]: 141 nodes 1 leaves 8529 minterms\nFrom[137]: 40 nodes 1 leaves 48 minterms\nReached[137]: 141 nodes 1 leaves 8577 minterms\nFrom[138]: 41 nodes 1 leaves 48 minterms\nReached[138]: 140 nodes 1 leaves 8625 minterms\nFrom[139]: 39 nodes 1 leaves 48 minterms\nReached[139]: 141 nodes 1 leaves 8673 minterms\nFrom[140]: 43 nodes 1 leaves 48 minterms\nReached[140]: 141 nodes 1 leaves 8721 minterms\nFrom[141]: 45 nodes 1 leaves 40 minterms\nReached[141]: 145 nodes 1 leaves 8761 minterms\nFrom[142]: 36 nodes 1 leaves 40 minterms\nReached[142]: 140 nodes 1 leaves 8801 minterms\nFrom[143]: 37 nodes 1 leaves 28 minterms\nReached[143]: 138 nodes 1 leaves 8829 minterms\nFrom[144]: 44 nodes 1 leaves 20 minterms\nReached[144]: 128 nodes 1 leaves 8849 minterms\nFrom[145]: 32 nodes 1 leaves 12 minterms\nReached[145]: 120 nodes 1 leaves 8861 minterms\nFrom[146]: 19 nodes 1 leaves 8 minterms\nReached[146]: 108 nodes 1 leaves 8869 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[2]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 40 nodes 1 leaves 5 minterms\nReached[1]: 58 nodes 1 leaves 6 minterms\nFrom[2]: 33 nodes 1 leaves 12 minterms\nReached[2]: 87 nodes 1 leaves 18 minterms\nFrom[3]: 33 nodes 1 leaves 20 minterms\nReached[3]: 94 nodes 1 leaves 38 minterms\nFrom[4]: 32 nodes 1 leaves 28 minterms\nReached[4]: 97 nodes 1 leaves 66 minterms\nFrom[5]: 33 nodes 1 leaves 36 minterms\nReached[5]: 102 nodes 1 leaves 102 minterms\nFrom[6]: 49 nodes 1 leaves 40 minterms\nReached[6]: 110 nodes 1 leaves 142 minterms\nFrom[7]: 50 nodes 1 leaves 52 minterms\nReached[7]: 123 nodes 1 leaves 194 minterms\nFrom[8]: 51 nodes 1 leaves 60 minterms\nReached[8]: 128 nodes 1 leaves 254 minterms\nFrom[9]: 50 nodes 1 leaves 68 minterms\nReached[9]: 130 nodes 1 leaves 322 minterms\nFrom[10]: 52 nodes 1 leaves 76 minterms\nReached[10]: 133 nodes 1 leaves 398 minterms\nFrom[11]: 54 nodes 1 leaves 80 minterms\nReached[11]: 137 nodes 1 leaves 478 minterms\nFrom[12]: 60 nodes 1 leaves 88 minterms\nReached[12]: 148 nodes 1 leaves 566 minterms\nFrom[13]: 58 nodes 1 leaves 88 minterms\nReached[13]: 148 nodes 1 leaves 654 minterms\nFrom[14]: 58 nodes 1 leaves 88 minterms\nReached[14]: 144 nodes 1 leaves 742 minterms\nFrom[15]: 52 nodes 1 leaves 88 minterms\nReached[15]: 143 nodes 1 leaves 830 minterms\nFrom[16]: 56 nodes 1 leaves 80 minterms\nReached[16]: 150 nodes 1 leaves 910 minterms\nFrom[17]: 54 nodes 1 leaves 88 minterms\nReached[17]: 159 nodes 1 leaves 998 minterms\nFrom[18]: 56 nodes 1 leaves 88 minterms\nReached[18]: 157 nodes 1 leaves 1086 minterms\nFrom[19]: 53 nodes 1 leaves 88 minterms\nReached[19]: 153 nodes 1 leaves 1174 minterms\nFrom[20]: 54 nodes 1 leaves 88 minterms\nReached[20]: 150 nodes 1 leaves 1262 minterms\nFrom[21]: 48 nodes 1 leaves 88 minterms\nReached[21]: 151 nodes 1 leaves 1350 minterms\nFrom[22]: 59 nodes 1 leaves 88 minterms\nReached[22]: 162 nodes 1 leaves 1438 minterms\nFrom[23]: 57 nodes 1 leaves 88 minterms\nReached[23]: 161 nodes 1 leaves 1526 minterms\nFrom[24]: 57 nodes 1 leaves 88 minterms\nReached[24]: 154 nodes 1 leaves 1614 minterms\nFrom[25]: 52 nodes 1 leaves 88 minterms\nReached[25]: 151 nodes 1 leaves 1702 minterms\nFrom[26]: 57 nodes 1 leaves 80 minterms\nReached[26]: 158 nodes 1 leaves 1782 minterms\nFrom[27]: 57 nodes 1 leaves 88 minterms\nReached[27]: 169 nodes 1 leaves 1870 minterms\nFrom[28]: 59 nodes 1 leaves 88 minterms\nReached[28]: 167 nodes 1 leaves 1958 minterms\nFrom[29]: 56 nodes 1 leaves 88 minterms\nReached[29]: 163 nodes 1 leaves 2046 minterms\nFrom[30]: 57 nodes 1 leaves 88 minterms\nReached[30]: 155 nodes 1 leaves 2134 minterms\nFrom[31]: 50 nodes 1 leaves 88 minterms\nReached[31]: 156 nodes 1 leaves 2222 minterms\nFrom[32]: 62 nodes 1 leaves 88 minterms\nReached[32]: 168 nodes 1 leaves 2310 minterms\nFrom[33]: 74 nodes 1 leaves 92 minterms\nReached[33]: 179 nodes 1 leaves 2402 minterms\nFrom[34]: 73 nodes 1 leaves 92 minterms\nReached[34]: 170 nodes 1 leaves 2494 minterms\nFrom[35]: 67 nodes 1 leaves 92 minterms\nReached[35]: 165 nodes 1 leaves 2586 minterms\nFrom[36]: 68 nodes 1 leaves 84 minterms\nReached[36]: 172 nodes 1 leaves 2670 minterms\nFrom[37]: 68 nodes 1 leaves 92 minterms\nReached[37]: 181 nodes 1 leaves 2762 minterms\nFrom[38]: 77 nodes 1 leaves 100 minterms\nReached[38]: 190 nodes 1 leaves 2862 minterms\nFrom[39]: 75 nodes 1 leaves 104 minterms\nReached[39]: 186 nodes 1 leaves 2966 minterms\nFrom[40]: 73 nodes 1 leaves 108 minterms\nReached[40]: 179 nodes 1 leaves 3074 minterms\nFrom[41]: 73 nodes 1 leaves 108 minterms\nReached[41]: 179 nodes 1 leaves 3182 minterms\nFrom[42]: 70 nodes 1 leaves 116 minterms\nReached[42]: 192 nodes 1 leaves 3298 minterms\nFrom[43]: 75 nodes 1 leaves 120 minterms\nReached[43]: 193 nodes 1 leaves 3418 minterms\nFrom[44]: 73 nodes 1 leaves 124 minterms\nReached[44]: 185 nodes 1 leaves 3542 minterms\nFrom[45]: 69 nodes 1 leaves 128 minterms\nReached[45]: 181 nodes 1 leaves 3670 minterms\nFrom[46]: 75 nodes 1 leaves 120 minterms\nReached[46]: 193 nodes 1 leaves 3790 minterms\nFrom[47]: 73 nodes 1 leaves 136 minterms\nReached[47]: 201 nodes 1 leaves 3926 minterms\nFrom[48]: 75 nodes 1 leaves 132 minterms\nReached[48]: 199 nodes 1 leaves 4058 minterms\nFrom[49]: 73 nodes 1 leaves 132 minterms\nReached[49]: 194 nodes 1 leaves 4190 minterms\nFrom[50]: 70 nodes 1 leaves 132 minterms\nReached[50]: 187 nodes 1 leaves 4322 minterms\nFrom[51]: 71 nodes 1 leaves 128 minterms\nReached[51]: 185 nodes 1 leaves 4450 minterms\nFrom[52]: 58 nodes 1 leaves 128 minterms\nReached[52]: 195 nodes 1 leaves 4578 minterms\nFrom[53]: 62 nodes 1 leaves 120 minterms\nReached[53]: 186 nodes 1 leaves 4698 minterms\nFrom[54]: 57 nodes 1 leaves 116 minterms\nReached[54]: 176 nodes 1 leaves 4814 minterms\nFrom[55]: 57 nodes 1 leaves 112 minterms\nReached[55]: 167 nodes 1 leaves 4926 minterms\nFrom[56]: 57 nodes 1 leaves 100 minterms\nReached[56]: 176 nodes 1 leaves 5026 minterms\nFrom[57]: 56 nodes 1 leaves 104 minterms\nReached[57]: 178 nodes 1 leaves 5130 minterms\nFrom[58]: 56 nodes 1 leaves 100 minterms\nReached[58]: 177 nodes 1 leaves 5230 minterms\nFrom[59]: 56 nodes 1 leaves 96 minterms\nReached[59]: 172 nodes 1 leaves 5326 minterms\nFrom[60]: 53 nodes 1 leaves 92 minterms\nReached[60]: 162 nodes 1 leaves 5418 minterms\nFrom[61]: 55 nodes 1 leaves 92 minterms\nReached[61]: 158 nodes 1 leaves 5510 minterms\nFrom[62]: 49 nodes 1 leaves 88 minterms\nReached[62]: 171 nodes 1 leaves 5598 minterms\nFrom[63]: 51 nodes 1 leaves 88 minterms\nReached[63]: 162 nodes 1 leaves 5686 minterms\nFrom[64]: 45 nodes 1 leaves 88 minterms\nReached[64]: 157 nodes 1 leaves 5774 minterms\nFrom[65]: 48 nodes 1 leaves 88 minterms\nReached[65]: 151 nodes 1 leaves 5862 minterms\nFrom[66]: 47 nodes 1 leaves 80 minterms\nReached[66]: 162 nodes 1 leaves 5942 minterms\nFrom[67]: 50 nodes 1 leaves 88 minterms\nReached[67]: 169 nodes 1 leaves 6030 minterms\nFrom[68]: 54 nodes 1 leaves 92 minterms\nReached[68]: 187 nodes 1 leaves 6122 minterms\nFrom[69]: 57 nodes 1 leaves 92 minterms\nReached[69]: 183 nodes 1 leaves 6214 minterms\nFrom[70]: 53 nodes 1 leaves 92 minterms\nReached[70]: 179 nodes 1 leaves 6306 minterms\nFrom[71]: 55 nodes 1 leaves 92 minterms\nReached[71]: 175 nodes 1 leaves 6398 minterms\nFrom[72]: 63 nodes 1 leaves 92 minterms\nReached[72]: 189 nodes 1 leaves 6490 minterms\nFrom[73]: 65 nodes 1 leaves 92 minterms\nReached[73]: 180 nodes 1 leaves 6582 minterms\nFrom[74]: 56 nodes 1 leaves 92 minterms\nReached[74]: 173 nodes 1 leaves 6674 minterms\nFrom[75]: 59 nodes 1 leaves 92 minterms\nReached[75]: 164 nodes 1 leaves 6766 minterms\nFrom[76]: 53 nodes 1 leaves 80 minterms\nReached[76]: 171 nodes 1 leaves 6846 minterms\nFrom[77]: 42 nodes 1 leaves 92 minterms\nReached[77]: 173 nodes 1 leaves 6938 minterms\nFrom[78]: 50 nodes 1 leaves 92 minterms\nReached[78]: 187 nodes 1 leaves 7030 minterms\nFrom[79]: 53 nodes 1 leaves 92 minterms\nReached[79]: 182 nodes 1 leaves 7122 minterms\nFrom[80]: 49 nodes 1 leaves 92 minterms\nReached[80]: 178 nodes 1 leaves 7214 minterms\nFrom[81]: 51 nodes 1 leaves 92 minterms\nReached[81]: 174 nodes 1 leaves 7306 minterms\nFrom[82]: 53 nodes 1 leaves 92 minterms\nReached[82]: 185 nodes 1 leaves 7398 minterms\nFrom[83]: 55 nodes 1 leaves 92 minterms\nReached[83]: 176 nodes 1 leaves 7490 minterms\nFrom[84]: 49 nodes 1 leaves 92 minterms\nReached[84]: 171 nodes 1 leaves 7582 minterms\nFrom[85]: 52 nodes 1 leaves 92 minterms\nReached[85]: 165 nodes 1 leaves 7674 minterms\nFrom[86]: 52 nodes 1 leaves 80 minterms\nReached[86]: 174 nodes 1 leaves 7754 minterms\nFrom[87]: 48 nodes 1 leaves 88 minterms\nReached[87]: 176 nodes 1 leaves 7842 minterms\nFrom[88]: 48 nodes 1 leaves 80 minterms\nReached[88]: 180 nodes 1 leaves 7922 minterms\nFrom[89]: 51 nodes 1 leaves 76 minterms\nReached[89]: 175 nodes 1 leaves 7998 minterms\nFrom[90]: 47 nodes 1 leaves 72 minterms\nReached[90]: 171 nodes 1 leaves 8070 minterms\nFrom[91]: 49 nodes 1 leaves 68 minterms\nReached[91]: 167 nodes 1 leaves 8138 minterms\nFrom[92]: 52 nodes 1 leaves 64 minterms\nReached[92]: 176 nodes 1 leaves 8202 minterms\nFrom[93]: 54 nodes 1 leaves 60 minterms\nReached[93]: 167 nodes 1 leaves 8262 minterms\nFrom[94]: 46 nodes 1 leaves 56 minterms\nReached[94]: 161 nodes 1 leaves 8318 minterms\nFrom[95]: 49 nodes 1 leaves 52 minterms\nReached[95]: 153 nodes 1 leaves 8370 minterms\nFrom[96]: 50 nodes 1 leaves 43 minterms\nReached[96]: 150 nodes 1 leaves 8413 minterms\nFrom[97]: 37 nodes 1 leaves 48 minterms\nReached[97]: 152 nodes 1 leaves 8461 minterms\nFrom[98]: 36 nodes 1 leaves 48 minterms\nReached[98]: 156 nodes 1 leaves 8509 minterms\nFrom[99]: 39 nodes 1 leaves 48 minterms\nReached[99]: 152 nodes 1 leaves 8557 minterms\nFrom[100]: 36 nodes 1 leaves 48 minterms\nReached[100]: 148 nodes 1 leaves 8605 minterms\nFrom[101]: 35 nodes 1 leaves 44 minterms\nReached[101]: 145 nodes 1 leaves 8649 minterms\nFrom[102]: 36 nodes 1 leaves 40 minterms\nReached[102]: 144 nodes 1 leaves 8689 minterms\nFrom[103]: 37 nodes 1 leaves 36 minterms\nReached[103]: 136 nodes 1 leaves 8725 minterms\nFrom[104]: 34 nodes 1 leaves 32 minterms\nReached[104]: 129 nodes 1 leaves 8757 minterms\nFrom[105]: 23 nodes 1 leaves 28 minterms\nReached[105]: 123 nodes 1 leaves 8785 minterms\nFrom[106]: 20 nodes 1 leaves 20 minterms\nReached[106]: 125 nodes 1 leaves 8805 minterms\nFrom[107]: 33 nodes 1 leaves 20 minterms\nReached[107]: 122 nodes 1 leaves 8825 minterms\nFrom[108]: 32 nodes 1 leaves 16 minterms\nReached[108]: 120 nodes 1 leaves 8841 minterms\nFrom[109]: 33 nodes 1 leaves 12 minterms\nReached[109]: 113 nodes 1 leaves 8853 minterms\nFrom[110]: 21 nodes 1 leaves 8 minterms\nReached[110]: 106 nodes 1 leaves 8861 minterms\nFrom[111]: 20 nodes 1 leaves 4 minterms\nReached[111]: 96 nodes 1 leaves 8865 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[3]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 37 nodes 1 leaves 5 minterms\nReached[1]: 56 nodes 1 leaves 6 minterms\nFrom[2]: 31 nodes 1 leaves 12 minterms\nReached[2]: 70 nodes 1 leaves 18 minterms\nFrom[3]: 30 nodes 1 leaves 20 minterms\nReached[3]: 72 nodes 1 leaves 38 minterms\nFrom[4]: 33 nodes 1 leaves 28 minterms\nReached[4]: 78 nodes 1 leaves 66 minterms\nFrom[5]: 44 nodes 1 leaves 40 minterms\nReached[5]: 93 nodes 1 leaves 106 minterms\nFrom[6]: 45 nodes 1 leaves 48 minterms\nReached[6]: 100 nodes 1 leaves 154 minterms\nFrom[7]: 45 nodes 1 leaves 56 minterms\nReached[7]: 101 nodes 1 leaves 210 minterms\nFrom[8]: 47 nodes 1 leaves 64 minterms\nReached[8]: 103 nodes 1 leaves 274 minterms\nFrom[9]: 45 nodes 1 leaves 72 minterms\nReached[9]: 104 nodes 1 leaves 346 minterms\nFrom[10]: 45 nodes 1 leaves 80 minterms\nReached[10]: 110 nodes 1 leaves 426 minterms\nFrom[11]: 51 nodes 1 leaves 76 minterms\nReached[11]: 121 nodes 1 leaves 502 minterms\nFrom[12]: 51 nodes 1 leaves 88 minterms\nReached[12]: 122 nodes 1 leaves 590 minterms\nFrom[13]: 47 nodes 1 leaves 88 minterms\nReached[13]: 126 nodes 1 leaves 678 minterms\nFrom[14]: 49 nodes 1 leaves 88 minterms\nReached[14]: 123 nodes 1 leaves 766 minterms\nFrom[15]: 44 nodes 1 leaves 88 minterms\nReached[15]: 127 nodes 1 leaves 854 minterms\nFrom[16]: 51 nodes 1 leaves 88 minterms\nReached[16]: 131 nodes 1 leaves 942 minterms\nFrom[17]: 50 nodes 1 leaves 88 minterms\nReached[17]: 132 nodes 1 leaves 1030 minterms\nFrom[18]: 53 nodes 1 leaves 88 minterms\nReached[18]: 128 nodes 1 leaves 1118 minterms\nFrom[19]: 48 nodes 1 leaves 88 minterms\nReached[19]: 124 nodes 1 leaves 1206 minterms\nFrom[20]: 50 nodes 1 leaves 88 minterms\nReached[20]: 126 nodes 1 leaves 1294 minterms\nFrom[21]: 55 nodes 1 leaves 80 minterms\nReached[21]: 140 nodes 1 leaves 1374 minterms\nFrom[22]: 58 nodes 1 leaves 88 minterms\nReached[22]: 141 nodes 1 leaves 1462 minterms\nFrom[23]: 54 nodes 1 leaves 88 minterms\nReached[23]: 142 nodes 1 leaves 1550 minterms\nFrom[24]: 53 nodes 1 leaves 88 minterms\nReached[24]: 137 nodes 1 leaves 1638 minterms\nFrom[25]: 45 nodes 1 leaves 88 minterms\nReached[25]: 141 nodes 1 leaves 1726 minterms\nFrom[26]: 49 nodes 1 leaves 88 minterms\nReached[26]: 142 nodes 1 leaves 1814 minterms\nFrom[27]: 48 nodes 1 leaves 88 minterms\nReached[27]: 143 nodes 1 leaves 1902 minterms\nFrom[28]: 51 nodes 1 leaves 88 minterms\nReached[28]: 139 nodes 1 leaves 1990 minterms\nFrom[29]: 46 nodes 1 leaves 88 minterms\nReached[29]: 134 nodes 1 leaves 2078 minterms\nFrom[30]: 48 nodes 1 leaves 88 minterms\nReached[30]: 132 nodes 1 leaves 2166 minterms\nFrom[31]: 49 nodes 1 leaves 80 minterms\nReached[31]: 143 nodes 1 leaves 2246 minterms\nFrom[32]: 51 nodes 1 leaves 88 minterms\nReached[32]: 142 nodes 1 leaves 2334 minterms\nFrom[33]: 58 nodes 1 leaves 92 minterms\nReached[33]: 156 nodes 1 leaves 2426 minterms\nFrom[34]: 60 nodes 1 leaves 92 minterms\nReached[34]: 150 nodes 1 leaves 2518 minterms\nFrom[35]: 55 nodes 1 leaves 92 minterms\nReached[35]: 154 nodes 1 leaves 2610 minterms\nFrom[36]: 61 nodes 1 leaves 92 minterms\nReached[36]: 157 nodes 1 leaves 2702 minterms\nFrom[37]: 61 nodes 1 leaves 92 minterms\nReached[37]: 158 nodes 1 leaves 2794 minterms\nFrom[38]: 64 nodes 1 leaves 92 minterms\nReached[38]: 154 nodes 1 leaves 2886 minterms\nFrom[39]: 59 nodes 1 leaves 92 minterms\nReached[39]: 149 nodes 1 leaves 2978 minterms\nFrom[40]: 61 nodes 1 leaves 92 minterms\nReached[40]: 148 nodes 1 leaves 3070 minterms\nFrom[41]: 68 nodes 1 leaves 80 minterms\nReached[41]: 160 nodes 1 leaves 3150 minterms\nFrom[42]: 60 nodes 1 leaves 92 minterms\nReached[42]: 159 nodes 1 leaves 3242 minterms\nFrom[43]: 67 nodes 1 leaves 100 minterms\nReached[43]: 170 nodes 1 leaves 3342 minterms\nFrom[44]: 66 nodes 1 leaves 104 minterms\nReached[44]: 163 nodes 1 leaves 3446 minterms\nFrom[45]: 58 nodes 1 leaves 108 minterms\nReached[45]: 167 nodes 1 leaves 3554 minterms\nFrom[46]: 61 nodes 1 leaves 112 minterms\nReached[46]: 168 nodes 1 leaves 3666 minterms\nFrom[47]: 69 nodes 1 leaves 120 minterms\nReached[47]: 178 nodes 1 leaves 3786 minterms\nFrom[48]: 72 nodes 1 leaves 124 minterms\nReached[48]: 174 nodes 1 leaves 3910 minterms\nFrom[49]: 66 nodes 1 leaves 128 minterms\nReached[49]: 169 nodes 1 leaves 4038 minterms\nFrom[50]: 62 nodes 1 leaves 132 minterms\nReached[50]: 168 nodes 1 leaves 4170 minterms\nFrom[51]: 71 nodes 1 leaves 116 minterms\nReached[51]: 182 nodes 1 leaves 4286 minterms\nFrom[52]: 57 nodes 1 leaves 144 minterms\nReached[52]: 180 nodes 1 leaves 4430 minterms\nFrom[53]: 55 nodes 1 leaves 136 minterms\nReached[53]: 180 nodes 1 leaves 4566 minterms\nFrom[54]: 56 nodes 1 leaves 136 minterms\nReached[54]: 174 nodes 1 leaves 4702 minterms\nFrom[55]: 51 nodes 1 leaves 136 minterms\nReached[55]: 176 nodes 1 leaves 4838 minterms\nFrom[56]: 55 nodes 1 leaves 136 minterms\nReached[56]: 175 nodes 1 leaves 4974 minterms\nFrom[57]: 59 nodes 1 leaves 136 minterms\nReached[57]: 183 nodes 1 leaves 5110 minterms\nFrom[58]: 62 nodes 1 leaves 136 minterms\nReached[58]: 177 nodes 1 leaves 5246 minterms\nFrom[59]: 55 nodes 1 leaves 136 minterms\nReached[59]: 170 nodes 1 leaves 5382 minterms\nFrom[60]: 50 nodes 1 leaves 136 minterms\nReached[60]: 167 nodes 1 leaves 5518 minterms\nFrom[61]: 60 nodes 1 leaves 120 minterms\nReached[61]: 184 nodes 1 leaves 5638 minterms\nFrom[62]: 63 nodes 1 leaves 136 minterms\nReached[62]: 185 nodes 1 leaves 5774 minterms\nFrom[63]: 58 nodes 1 leaves 136 minterms\nReached[63]: 184 nodes 1 leaves 5910 minterms\nFrom[64]: 58 nodes 1 leaves 136 minterms\nReached[64]: 177 nodes 1 leaves 6046 minterms\nFrom[65]: 52 nodes 1 leaves 136 minterms\nReached[65]: 178 nodes 1 leaves 6182 minterms\nFrom[66]: 55 nodes 1 leaves 136 minterms\nReached[66]: 176 nodes 1 leaves 6318 minterms\nFrom[67]: 61 nodes 1 leaves 132 minterms\nReached[67]: 180 nodes 1 leaves 6450 minterms\nFrom[68]: 64 nodes 1 leaves 128 minterms\nReached[68]: 174 nodes 1 leaves 6578 minterms\nFrom[69]: 56 nodes 1 leaves 124 minterms\nReached[69]: 166 nodes 1 leaves 6702 minterms\nFrom[70]: 56 nodes 1 leaves 120 minterms\nReached[70]: 161 nodes 1 leaves 6822 minterms\nFrom[71]: 52 nodes 1 leaves 100 minterms\nReached[71]: 174 nodes 1 leaves 6922 minterms\nFrom[72]: 60 nodes 1 leaves 108 minterms\nReached[72]: 173 nodes 1 leaves 7030 minterms\nFrom[73]: 56 nodes 1 leaves 104 minterms\nReached[73]: 173 nodes 1 leaves 7134 minterms\nFrom[74]: 58 nodes 1 leaves 100 minterms\nReached[74]: 167 nodes 1 leaves 7234 minterms\nFrom[75]: 49 nodes 1 leaves 96 minterms\nReached[75]: 166 nodes 1 leaves 7330 minterms\nFrom[76]: 52 nodes 1 leaves 88 minterms\nReached[76]: 158 nodes 1 leaves 7418 minterms\nFrom[77]: 47 nodes 1 leaves 80 minterms\nReached[77]: 159 nodes 1 leaves 7498 minterms\nFrom[78]: 49 nodes 1 leaves 76 minterms\nReached[78]: 154 nodes 1 leaves 7574 minterms\nFrom[79]: 44 nodes 1 leaves 72 minterms\nReached[79]: 149 nodes 1 leaves 7646 minterms\nFrom[80]: 46 nodes 1 leaves 68 minterms\nReached[80]: 148 nodes 1 leaves 7714 minterms\nFrom[81]: 49 nodes 1 leaves 60 minterms\nReached[81]: 149 nodes 1 leaves 7774 minterms\nFrom[82]: 50 nodes 1 leaves 56 minterms\nReached[82]: 151 nodes 1 leaves 7830 minterms\nFrom[83]: 52 nodes 1 leaves 56 minterms\nReached[83]: 155 nodes 1 leaves 7886 minterms\nFrom[84]: 46 nodes 1 leaves 52 minterms\nReached[84]: 144 nodes 1 leaves 7938 minterms\nFrom[85]: 38 nodes 1 leaves 44 minterms\nReached[85]: 145 nodes 1 leaves 7982 minterms\nFrom[86]: 40 nodes 1 leaves 44 minterms\nReached[86]: 145 nodes 1 leaves 8026 minterms\nFrom[87]: 39 nodes 1 leaves 44 minterms\nReached[87]: 146 nodes 1 leaves 8070 minterms\nFrom[88]: 41 nodes 1 leaves 44 minterms\nReached[88]: 141 nodes 1 leaves 8114 minterms\nFrom[89]: 36 nodes 1 leaves 44 minterms\nReached[89]: 139 nodes 1 leaves 8158 minterms\nFrom[90]: 37 nodes 1 leaves 44 minterms\nReached[90]: 138 nodes 1 leaves 8202 minterms\nFrom[91]: 35 nodes 1 leaves 40 minterms\nReached[91]: 136 nodes 1 leaves 8242 minterms\nFrom[92]: 23 nodes 1 leaves 44 minterms\nReached[92]: 136 nodes 1 leaves 8286 minterms\nFrom[93]: 35 nodes 1 leaves 44 minterms\nReached[93]: 146 nodes 1 leaves 8330 minterms\nFrom[94]: 38 nodes 1 leaves 44 minterms\nReached[94]: 144 nodes 1 leaves 8374 minterms\nFrom[95]: 35 nodes 1 leaves 44 minterms\nReached[95]: 145 nodes 1 leaves 8418 minterms\nFrom[96]: 37 nodes 1 leaves 44 minterms\nReached[96]: 145 nodes 1 leaves 8462 minterms\nFrom[97]: 36 nodes 1 leaves 44 minterms\nReached[97]: 146 nodes 1 leaves 8506 minterms\nFrom[98]: 38 nodes 1 leaves 44 minterms\nReached[98]: 141 nodes 1 leaves 8550 minterms\nFrom[99]: 33 nodes 1 leaves 44 minterms\nReached[99]: 139 nodes 1 leaves 8594 minterms\nFrom[100]: 34 nodes 1 leaves 44 minterms\nReached[100]: 139 nodes 1 leaves 8638 minterms\nFrom[101]: 35 nodes 1 leaves 40 minterms\nReached[101]: 139 nodes 1 leaves 8678 minterms\nFrom[102]: 19 nodes 1 leaves 40 minterms\nReached[102]: 134 nodes 1 leaves 8718 minterms\nFrom[103]: 21 nodes 1 leaves 32 minterms\nReached[103]: 134 nodes 1 leaves 8750 minterms\nFrom[104]: 22 nodes 1 leaves 28 minterms\nReached[104]: 130 nodes 1 leaves 8778 minterms\nFrom[105]: 20 nodes 1 leaves 24 minterms\nReached[105]: 128 nodes 1 leaves 8802 minterms\nFrom[106]: 22 nodes 1 leaves 20 minterms\nReached[106]: 124 nodes 1 leaves 8822 minterms\nFrom[107]: 21 nodes 1 leaves 16 minterms\nReached[107]: 123 nodes 1 leaves 8838 minterms\nFrom[108]: 22 nodes 1 leaves 12 minterms\nReached[108]: 117 nodes 1 leaves 8850 minterms\nFrom[109]: 19 nodes 1 leaves 8 minterms\nReached[109]: 114 nodes 1 leaves 8858 minterms\nFrom[110]: 20 nodes 1 leaves 4 minterms\nReached[110]: 108 nodes 1 leaves 8862 minterms\nFrom[111]: 22 nodes 1 leaves 3 minterms\nReached[111]: 97 nodes 1 leaves 8865 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[4]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 37 nodes 1 leaves 5 minterms\nReached[1]: 54 nodes 1 leaves 6 minterms\nFrom[2]: 31 nodes 1 leaves 12 minterms\nReached[2]: 69 nodes 1 leaves 18 minterms\nFrom[3]: 30 nodes 1 leaves 20 minterms\nReached[3]: 72 nodes 1 leaves 38 minterms\nFrom[4]: 39 nodes 1 leaves 28 minterms\nReached[4]: 82 nodes 1 leaves 66 minterms\nFrom[5]: 38 nodes 1 leaves 32 minterms\nReached[5]: 84 nodes 1 leaves 98 minterms\nFrom[6]: 38 nodes 1 leaves 36 minterms\nReached[6]: 90 nodes 1 leaves 134 minterms\nFrom[7]: 38 nodes 1 leaves 40 minterms\nReached[7]: 93 nodes 1 leaves 174 minterms\nFrom[8]: 39 nodes 1 leaves 44 minterms\nReached[8]: 93 nodes 1 leaves 218 minterms\nFrom[9]: 37 nodes 1 leaves 48 minterms\nReached[9]: 94 nodes 1 leaves 266 minterms\nFrom[10]: 37 nodes 1 leaves 52 minterms\nReached[10]: 100 nodes 1 leaves 318 minterms\nFrom[11]: 37 nodes 1 leaves 48 minterms\nReached[11]: 102 nodes 1 leaves 366 minterms\nFrom[12]: 39 nodes 1 leaves 48 minterms\nReached[12]: 104 nodes 1 leaves 414 minterms\nFrom[13]: 33 nodes 1 leaves 44 minterms\nReached[13]: 108 nodes 1 leaves 458 minterms\nFrom[14]: 26 nodes 1 leaves 40 minterms\nReached[14]: 104 nodes 1 leaves 498 minterms\nFrom[15]: 22 nodes 1 leaves 40 minterms\nReached[15]: 105 nodes 1 leaves 538 minterms\nFrom[16]: 26 nodes 1 leaves 40 minterms\nReached[16]: 107 nodes 1 leaves 578 minterms\nFrom[17]: 23 nodes 1 leaves 40 minterms\nReached[17]: 108 nodes 1 leaves 618 minterms\nFrom[18]: 26 nodes 1 leaves 40 minterms\nReached[18]: 102 nodes 1 leaves 658 minterms\nFrom[19]: 20 nodes 1 leaves 40 minterms\nReached[19]: 100 nodes 1 leaves 698 minterms\nFrom[20]: 24 nodes 1 leaves 40 minterms\nReached[20]: 101 nodes 1 leaves 738 minterms\nFrom[21]: 19 nodes 1 leaves 40 minterms\nReached[21]: 103 nodes 1 leaves 778 minterms\nFrom[22]: 27 nodes 1 leaves 40 minterms\nReached[22]: 106 nodes 1 leaves 818 minterms\nFrom[23]: 23 nodes 1 leaves 40 minterms\nReached[23]: 110 nodes 1 leaves 858 minterms\nFrom[24]: 27 nodes 1 leaves 40 minterms\nReached[24]: 106 nodes 1 leaves 898 minterms\nFrom[25]: 23 nodes 1 leaves 40 minterms\nReached[25]: 107 nodes 1 leaves 938 minterms\nFrom[26]: 27 nodes 1 leaves 40 minterms\nReached[26]: 109 nodes 1 leaves 978 minterms\nFrom[27]: 24 nodes 1 leaves 40 minterms\nReached[27]: 110 nodes 1 leaves 1018 minterms\nFrom[28]: 27 nodes 1 leaves 40 minterms\nReached[28]: 104 nodes 1 leaves 1058 minterms\nFrom[29]: 21 nodes 1 leaves 40 minterms\nReached[29]: 102 nodes 1 leaves 1098 minterms\nFrom[30]: 25 nodes 1 leaves 40 minterms\nReached[30]: 101 nodes 1 leaves 1138 minterms\nFrom[31]: 19 nodes 1 leaves 40 minterms\nReached[31]: 103 nodes 1 leaves 1178 minterms\nFrom[32]: 26 nodes 1 leaves 40 minterms\nReached[32]: 105 nodes 1 leaves 1218 minterms\nFrom[33]: 36 nodes 1 leaves 44 minterms\nReached[33]: 122 nodes 1 leaves 1262 minterms\nFrom[34]: 39 nodes 1 leaves 44 minterms\nReached[34]: 118 nodes 1 leaves 1306 minterms\nFrom[35]: 36 nodes 1 leaves 44 minterms\nReached[35]: 119 nodes 1 leaves 1350 minterms\nFrom[36]: 38 nodes 1 leaves 44 minterms\nReached[36]: 121 nodes 1 leaves 1394 minterms\nFrom[37]: 37 nodes 1 leaves 44 minterms\nReached[37]: 122 nodes 1 leaves 1438 minterms\nFrom[38]: 39 nodes 1 leaves 44 minterms\nReached[38]: 116 nodes 1 leaves 1482 minterms\nFrom[39]: 34 nodes 1 leaves 44 minterms\nReached[39]: 114 nodes 1 leaves 1526 minterms\nFrom[40]: 35 nodes 1 leaves 44 minterms\nReached[40]: 114 nodes 1 leaves 1570 minterms\nFrom[41]: 36 nodes 1 leaves 40 minterms\nReached[41]: 114 nodes 1 leaves 1610 minterms\nFrom[42]: 25 nodes 1 leaves 44 minterms\nReached[42]: 117 nodes 1 leaves 1654 minterms\nFrom[43]: 43 nodes 1 leaves 52 minterms\nReached[43]: 137 nodes 1 leaves 1706 minterms\nFrom[44]: 46 nodes 1 leaves 56 minterms\nReached[44]: 133 nodes 1 leaves 1762 minterms\nFrom[45]: 43 nodes 1 leaves 60 minterms\nReached[45]: 134 nodes 1 leaves 1822 minterms\nFrom[46]: 45 nodes 1 leaves 64 minterms\nReached[46]: 136 nodes 1 leaves 1886 minterms\nFrom[47]: 60 nodes 1 leaves 72 minterms\nReached[47]: 152 nodes 1 leaves 1958 minterms\nFrom[48]: 62 nodes 1 leaves 76 minterms\nReached[48]: 146 nodes 1 leaves 2034 minterms\nFrom[49]: 57 nodes 1 leaves 80 minterms\nReached[49]: 144 nodes 1 leaves 2114 minterms\nFrom[50]: 58 nodes 1 leaves 84 minterms\nReached[50]: 144 nodes 1 leaves 2198 minterms\nFrom[51]: 59 nodes 1 leaves 76 minterms\nReached[51]: 151 nodes 1 leaves 2274 minterms\nFrom[52]: 44 nodes 1 leaves 96 minterms\nReached[52]: 152 nodes 1 leaves 2370 minterms\nFrom[53]: 46 nodes 1 leaves 88 minterms\nReached[53]: 156 nodes 1 leaves 2458 minterms\nFrom[54]: 49 nodes 1 leaves 88 minterms\nReached[54]: 152 nodes 1 leaves 2546 minterms\nFrom[55]: 45 nodes 1 leaves 88 minterms\nReached[55]: 151 nodes 1 leaves 2634 minterms\nFrom[56]: 47 nodes 1 leaves 88 minterms\nReached[56]: 150 nodes 1 leaves 2722 minterms\nFrom[57]: 49 nodes 1 leaves 88 minterms\nReached[57]: 158 nodes 1 leaves 2810 minterms\nFrom[58]: 51 nodes 1 leaves 88 minterms\nReached[58]: 151 nodes 1 leaves 2898 minterms\nFrom[59]: 45 nodes 1 leaves 88 minterms\nReached[59]: 146 nodes 1 leaves 2986 minterms\nFrom[60]: 48 nodes 1 leaves 88 minterms\nReached[60]: 145 nodes 1 leaves 3074 minterms\nFrom[61]: 47 nodes 1 leaves 80 minterms\nReached[61]: 156 nodes 1 leaves 3154 minterms\nFrom[62]: 48 nodes 1 leaves 88 minterms\nReached[62]: 159 nodes 1 leaves 3242 minterms\nFrom[63]: 47 nodes 1 leaves 88 minterms\nReached[63]: 163 nodes 1 leaves 3330 minterms\nFrom[64]: 50 nodes 1 leaves 88 minterms\nReached[64]: 159 nodes 1 leaves 3418 minterms\nFrom[65]: 46 nodes 1 leaves 88 minterms\nReached[65]: 158 nodes 1 leaves 3506 minterms\nFrom[66]: 48 nodes 1 leaves 88 minterms\nReached[66]: 157 nodes 1 leaves 3594 minterms\nFrom[67]: 52 nodes 1 leaves 88 minterms\nReached[67]: 167 nodes 1 leaves 3682 minterms\nFrom[68]: 54 nodes 1 leaves 88 minterms\nReached[68]: 159 nodes 1 leaves 3770 minterms\nFrom[69]: 47 nodes 1 leaves 88 minterms\nReached[69]: 152 nodes 1 leaves 3858 minterms\nFrom[70]: 50 nodes 1 leaves 88 minterms\nReached[70]: 148 nodes 1 leaves 3946 minterms\nFrom[71]: 47 nodes 1 leaves 80 minterms\nReached[71]: 159 nodes 1 leaves 4026 minterms\nFrom[72]: 47 nodes 1 leaves 88 minterms\nReached[72]: 161 nodes 1 leaves 4114 minterms\nFrom[73]: 46 nodes 1 leaves 88 minterms\nReached[73]: 165 nodes 1 leaves 4202 minterms\nFrom[74]: 49 nodes 1 leaves 88 minterms\nReached[74]: 161 nodes 1 leaves 4290 minterms\nFrom[75]: 45 nodes 1 leaves 88 minterms\nReached[75]: 159 nodes 1 leaves 4378 minterms\nFrom[76]: 47 nodes 1 leaves 88 minterms\nReached[76]: 158 nodes 1 leaves 4466 minterms\nFrom[77]: 49 nodes 1 leaves 88 minterms\nReached[77]: 166 nodes 1 leaves 4554 minterms\nFrom[78]: 51 nodes 1 leaves 88 minterms\nReached[78]: 158 nodes 1 leaves 4642 minterms\nFrom[79]: 45 nodes 1 leaves 88 minterms\nReached[79]: 152 nodes 1 leaves 4730 minterms\nFrom[80]: 48 nodes 1 leaves 88 minterms\nReached[80]: 148 nodes 1 leaves 4818 minterms\nFrom[81]: 47 nodes 1 leaves 80 minterms\nReached[81]: 159 nodes 1 leaves 4898 minterms\nFrom[82]: 50 nodes 1 leaves 88 minterms\nReached[82]: 164 nodes 1 leaves 4986 minterms\nFrom[83]: 54 nodes 1 leaves 92 minterms\nReached[83]: 182 nodes 1 leaves 5078 minterms\nFrom[84]: 57 nodes 1 leaves 92 minterms\nReached[84]: 178 nodes 1 leaves 5170 minterms\nFrom[85]: 53 nodes 1 leaves 92 minterms\nReached[85]: 176 nodes 1 leaves 5262 minterms\nFrom[86]: 55 nodes 1 leaves 92 minterms\nReached[86]: 175 nodes 1 leaves 5354 minterms\nFrom[87]: 63 nodes 1 leaves 92 minterms\nReached[87]: 184 nodes 1 leaves 5446 minterms\nFrom[88]: 65 nodes 1 leaves 92 minterms\nReached[88]: 176 nodes 1 leaves 5538 minterms\nFrom[89]: 56 nodes 1 leaves 92 minterms\nReached[89]: 168 nodes 1 leaves 5630 minterms\nFrom[90]: 59 nodes 1 leaves 92 minterms\nReached[90]: 162 nodes 1 leaves 5722 minterms\nFrom[91]: 53 nodes 1 leaves 80 minterms\nReached[91]: 168 nodes 1 leaves 5802 minterms\nFrom[92]: 42 nodes 1 leaves 92 minterms\nReached[92]: 168 nodes 1 leaves 5894 minterms\nFrom[93]: 50 nodes 1 leaves 92 minterms\nReached[93]: 182 nodes 1 leaves 5986 minterms\nFrom[94]: 53 nodes 1 leaves 92 minterms\nReached[94]: 177 nodes 1 leaves 6078 minterms\nFrom[95]: 49 nodes 1 leaves 92 minterms\nReached[95]: 175 nodes 1 leaves 6170 minterms\nFrom[96]: 51 nodes 1 leaves 92 minterms\nReached[96]: 174 nodes 1 leaves 6262 minterms\nFrom[97]: 53 nodes 1 leaves 92 minterms\nReached[97]: 180 nodes 1 leaves 6354 minterms\nFrom[98]: 55 nodes 1 leaves 92 minterms\nReached[98]: 172 nodes 1 leaves 6446 minterms\nFrom[99]: 49 nodes 1 leaves 92 minterms\nReached[99]: 166 nodes 1 leaves 6538 minterms\nFrom[100]: 52 nodes 1 leaves 92 minterms\nReached[100]: 162 nodes 1 leaves 6630 minterms\nFrom[101]: 52 nodes 1 leaves 80 minterms\nReached[101]: 171 nodes 1 leaves 6710 minterms\nFrom[102]: 48 nodes 1 leaves 88 minterms\nReached[102]: 173 nodes 1 leaves 6798 minterms\nFrom[103]: 48 nodes 1 leaves 80 minterms\nReached[103]: 177 nodes 1 leaves 6878 minterms\nFrom[104]: 51 nodes 1 leaves 76 minterms\nReached[104]: 172 nodes 1 leaves 6954 minterms\nFrom[105]: 47 nodes 1 leaves 72 minterms\nReached[105]: 170 nodes 1 leaves 7026 minterms\nFrom[106]: 49 nodes 1 leaves 68 minterms\nReached[106]: 169 nodes 1 leaves 7094 minterms\nFrom[107]: 52 nodes 1 leaves 64 minterms\nReached[107]: 175 nodes 1 leaves 7158 minterms\nFrom[108]: 54 nodes 1 leaves 60 minterms\nReached[108]: 167 nodes 1 leaves 7218 minterms\nFrom[109]: 46 nodes 1 leaves 56 minterms\nReached[109]: 160 nodes 1 leaves 7274 minterms\nFrom[110]: 49 nodes 1 leaves 52 minterms\nReached[110]: 154 nodes 1 leaves 7326 minterms\nFrom[111]: 50 nodes 1 leaves 43 minterms\nReached[111]: 152 nodes 1 leaves 7369 minterms\nFrom[112]: 37 nodes 1 leaves 48 minterms\nReached[112]: 154 nodes 1 leaves 7417 minterms\nFrom[113]: 36 nodes 1 leaves 48 minterms\nReached[113]: 158 nodes 1 leaves 7465 minterms\nFrom[114]: 39 nodes 1 leaves 48 minterms\nReached[114]: 154 nodes 1 leaves 7513 minterms\nFrom[115]: 36 nodes 1 leaves 48 minterms\nReached[115]: 152 nodes 1 leaves 7561 minterms\nFrom[116]: 35 nodes 1 leaves 48 minterms\nReached[116]: 152 nodes 1 leaves 7609 minterms\nFrom[117]: 38 nodes 1 leaves 48 minterms\nReached[117]: 156 nodes 1 leaves 7657 minterms\nFrom[118]: 40 nodes 1 leaves 48 minterms\nReached[118]: 150 nodes 1 leaves 7705 minterms\nFrom[119]: 36 nodes 1 leaves 48 minterms\nReached[119]: 144 nodes 1 leaves 7753 minterms\nFrom[120]: 35 nodes 1 leaves 48 minterms\nReached[120]: 144 nodes 1 leaves 7801 minterms\nFrom[121]: 36 nodes 1 leaves 40 minterms\nReached[121]: 152 nodes 1 leaves 7841 minterms\nFrom[122]: 38 nodes 1 leaves 48 minterms\nReached[122]: 155 nodes 1 leaves 7889 minterms\nFrom[123]: 37 nodes 1 leaves 48 minterms\nReached[123]: 159 nodes 1 leaves 7937 minterms\nFrom[124]: 40 nodes 1 leaves 48 minterms\nReached[124]: 155 nodes 1 leaves 7985 minterms\nFrom[125]: 37 nodes 1 leaves 48 minterms\nReached[125]: 153 nodes 1 leaves 8033 minterms\nFrom[126]: 36 nodes 1 leaves 48 minterms\nReached[126]: 153 nodes 1 leaves 8081 minterms\nFrom[127]: 40 nodes 1 leaves 48 minterms\nReached[127]: 158 nodes 1 leaves 8129 minterms\nFrom[128]: 42 nodes 1 leaves 48 minterms\nReached[128]: 152 nodes 1 leaves 8177 minterms\nFrom[129]: 38 nodes 1 leaves 48 minterms\nReached[129]: 145 nodes 1 leaves 8225 minterms\nFrom[130]: 36 nodes 1 leaves 48 minterms\nReached[130]: 144 nodes 1 leaves 8273 minterms\nFrom[131]: 36 nodes 1 leaves 40 minterms\nReached[131]: 152 nodes 1 leaves 8313 minterms\nFrom[132]: 37 nodes 1 leaves 48 minterms\nReached[132]: 154 nodes 1 leaves 8361 minterms\nFrom[133]: 36 nodes 1 leaves 48 minterms\nReached[133]: 158 nodes 1 leaves 8409 minterms\nFrom[134]: 39 nodes 1 leaves 48 minterms\nReached[134]: 154 nodes 1 leaves 8457 minterms\nFrom[135]: 36 nodes 1 leaves 48 minterms\nReached[135]: 152 nodes 1 leaves 8505 minterms\nFrom[136]: 35 nodes 1 leaves 48 minterms\nReached[136]: 152 nodes 1 leaves 8553 minterms\nFrom[137]: 38 nodes 1 leaves 48 minterms\nReached[137]: 156 nodes 1 leaves 8601 minterms\nFrom[138]: 40 nodes 1 leaves 48 minterms\nReached[138]: 150 nodes 1 leaves 8649 minterms\nFrom[139]: 36 nodes 1 leaves 48 minterms\nReached[139]: 144 nodes 1 leaves 8697 minterms\nFrom[140]: 35 nodes 1 leaves 48 minterms\nReached[140]: 144 nodes 1 leaves 8745 minterms\nFrom[141]: 36 nodes 1 leaves 40 minterms\nReached[141]: 152 nodes 1 leaves 8785 minterms\nFrom[142]: 36 nodes 1 leaves 44 minterms\nReached[142]: 150 nodes 1 leaves 8829 minterms\nFrom[143]: 35 nodes 1 leaves 40 minterms\nReached[143]: 151 nodes 1 leaves 8869 minterms\nFrom[144]: 36 nodes 1 leaves 36 minterms\nReached[144]: 145 nodes 1 leaves 8905 minterms\nFrom[145]: 34 nodes 1 leaves 32 minterms\nReached[145]: 141 nodes 1 leaves 8937 minterms\nFrom[146]: 33 nodes 1 leaves 28 minterms\nReached[146]: 136 nodes 1 leaves 8965 minterms\nFrom[147]: 34 nodes 1 leaves 20 minterms\nReached[147]: 134 nodes 1 leaves 8985 minterms\nFrom[148]: 35 nodes 1 leaves 16 minterms\nReached[148]: 127 nodes 1 leaves 9001 minterms\nFrom[149]: 32 nodes 1 leaves 12 minterms\nReached[149]: 117 nodes 1 leaves 9013 minterms\nFrom[150]: 19 nodes 1 leaves 8 minterms\nReached[150]: 109 nodes 1 leaves 9021 minterms\nFrom[151]: 20 nodes 1 leaves 4 minterms\nReached[151]: 104 nodes 1 leaves 9025 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[5]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 33 nodes 1 leaves 5 minterms\nReached[1]: 52 nodes 1 leaves 6 minterms\nFrom[2]: 32 nodes 1 leaves 12 minterms\nReached[2]: 72 nodes 1 leaves 18 minterms\nFrom[3]: 32 nodes 1 leaves 20 minterms\nReached[3]: 75 nodes 1 leaves 38 minterms\nFrom[4]: 31 nodes 1 leaves 28 minterms\nReached[4]: 77 nodes 1 leaves 66 minterms\nFrom[5]: 31 nodes 1 leaves 36 minterms\nReached[5]: 82 nodes 1 leaves 102 minterms\nFrom[6]: 39 nodes 1 leaves 48 minterms\nReached[6]: 97 nodes 1 leaves 150 minterms\nFrom[7]: 42 nodes 1 leaves 56 minterms\nReached[7]: 101 nodes 1 leaves 206 minterms\nFrom[8]: 41 nodes 1 leaves 64 minterms\nReached[8]: 101 nodes 1 leaves 270 minterms\nFrom[9]: 40 nodes 1 leaves 72 minterms\nReached[9]: 105 nodes 1 leaves 342 minterms\nFrom[10]: 42 nodes 1 leaves 84 minterms\nReached[10]: 113 nodes 1 leaves 426 minterms\nFrom[11]: 50 nodes 1 leaves 76 minterms\nReached[11]: 125 nodes 1 leaves 502 minterms\nFrom[12]: 50 nodes 1 leaves 88 minterms\nReached[12]: 126 nodes 1 leaves 590 minterms\nFrom[13]: 52 nodes 1 leaves 88 minterms\nReached[13]: 129 nodes 1 leaves 678 minterms\nFrom[14]: 52 nodes 1 leaves 88 minterms\nReached[14]: 125 nodes 1 leaves 766 minterms\nFrom[15]: 47 nodes 1 leaves 88 minterms\nReached[15]: 127 nodes 1 leaves 854 minterms\nFrom[16]: 53 nodes 1 leaves 88 minterms\nReached[16]: 133 nodes 1 leaves 942 minterms\nFrom[17]: 56 nodes 1 leaves 88 minterms\nReached[17]: 133 nodes 1 leaves 1030 minterms\nFrom[18]: 54 nodes 1 leaves 88 minterms\nReached[18]: 125 nodes 1 leaves 1118 minterms\nFrom[19]: 45 nodes 1 leaves 88 minterms\nReached[19]: 124 nodes 1 leaves 1206 minterms\nFrom[20]: 46 nodes 1 leaves 88 minterms\nReached[20]: 129 nodes 1 leaves 1294 minterms\nFrom[21]: 47 nodes 1 leaves 80 minterms\nReached[21]: 139 nodes 1 leaves 1374 minterms\nFrom[22]: 57 nodes 1 leaves 96 minterms\nReached[22]: 152 nodes 1 leaves 1470 minterms\nFrom[23]: 59 nodes 1 leaves 100 minterms\nReached[23]: 155 nodes 1 leaves 1570 minterms\nFrom[24]: 59 nodes 1 leaves 104 minterms\nReached[24]: 148 nodes 1 leaves 1674 minterms\nFrom[25]: 54 nodes 1 leaves 108 minterms\nReached[25]: 150 nodes 1 leaves 1782 minterms\nFrom[26]: 60 nodes 1 leaves 112 minterms\nReached[26]: 156 nodes 1 leaves 1894 minterms\nFrom[27]: 63 nodes 1 leaves 116 minterms\nReached[27]: 155 nodes 1 leaves 2010 minterms\nFrom[28]: 60 nodes 1 leaves 120 minterms\nReached[28]: 145 nodes 1 leaves 2130 minterms\nFrom[29]: 53 nodes 1 leaves 124 minterms\nReached[29]: 141 nodes 1 leaves 2254 minterms\nFrom[30]: 56 nodes 1 leaves 128 minterms\nReached[30]: 145 nodes 1 leaves 2382 minterms\nFrom[31]: 58 nodes 1 leaves 120 minterms\nReached[31]: 156 nodes 1 leaves 2502 minterms\nFrom[32]: 59 nodes 1 leaves 128 minterms\nReached[32]: 157 nodes 1 leaves 2630 minterms\nFrom[33]: 72 nodes 1 leaves 132 minterms\nReached[33]: 172 nodes 1 leaves 2762 minterms\nFrom[34]: 71 nodes 1 leaves 132 minterms\nReached[34]: 165 nodes 1 leaves 2894 minterms\nFrom[35]: 69 nodes 1 leaves 132 minterms\nReached[35]: 166 nodes 1 leaves 3026 minterms\nFrom[36]: 74 nodes 1 leaves 132 minterms\nReached[36]: 176 nodes 1 leaves 3158 minterms\nFrom[37]: 77 nodes 1 leaves 132 minterms\nReached[37]: 173 nodes 1 leaves 3290 minterms\nFrom[38]: 72 nodes 1 leaves 132 minterms\nReached[38]: 162 nodes 1 leaves 3422 minterms\nFrom[39]: 69 nodes 1 leaves 132 minterms\nReached[39]: 153 nodes 1 leaves 3554 minterms\nFrom[40]: 66 nodes 1 leaves 132 minterms\nReached[40]: 158 nodes 1 leaves 3686 minterms\nFrom[41]: 66 nodes 1 leaves 120 minterms\nReached[41]: 167 nodes 1 leaves 3806 minterms\nFrom[42]: 60 nodes 1 leaves 132 minterms\nReached[42]: 169 nodes 1 leaves 3938 minterms\nFrom[43]: 67 nodes 1 leaves 132 minterms\nReached[43]: 175 nodes 1 leaves 4070 minterms\nFrom[44]: 66 nodes 1 leaves 132 minterms\nReached[44]: 168 nodes 1 leaves 4202 minterms\nFrom[45]: 64 nodes 1 leaves 132 minterms\nReached[45]: 169 nodes 1 leaves 4334 minterms\nFrom[46]: 67 nodes 1 leaves 132 minterms\nReached[46]: 177 nodes 1 leaves 4466 minterms\nFrom[47]: 70 nodes 1 leaves 132 minterms\nReached[47]: 174 nodes 1 leaves 4598 minterms\nFrom[48]: 66 nodes 1 leaves 132 minterms\nReached[48]: 164 nodes 1 leaves 4730 minterms\nFrom[49]: 63 nodes 1 leaves 132 minterms\nReached[49]: 156 nodes 1 leaves 4862 minterms\nFrom[50]: 62 nodes 1 leaves 132 minterms\nReached[50]: 161 nodes 1 leaves 4994 minterms\nFrom[51]: 61 nodes 1 leaves 120 minterms\nReached[51]: 172 nodes 1 leaves 5114 minterms\nFrom[52]: 56 nodes 1 leaves 132 minterms\nReached[52]: 182 nodes 1 leaves 5246 minterms\nFrom[53]: 61 nodes 1 leaves 124 minterms\nReached[53]: 185 nodes 1 leaves 5370 minterms\nFrom[54]: 58 nodes 1 leaves 120 minterms\nReached[54]: 177 nodes 1 leaves 5490 minterms\nFrom[55]: 57 nodes 1 leaves 116 minterms\nReached[55]: 178 nodes 1 leaves 5606 minterms\nFrom[56]: 68 nodes 1 leaves 112 minterms\nReached[56]: 185 nodes 1 leaves 5718 minterms\nFrom[57]: 69 nodes 1 leaves 108 minterms\nReached[57]: 182 nodes 1 leaves 5826 minterms\nFrom[58]: 63 nodes 1 leaves 104 minterms\nReached[58]: 169 nodes 1 leaves 5930 minterms\nFrom[59]: 60 nodes 1 leaves 100 minterms\nReached[59]: 158 nodes 1 leaves 6030 minterms\nFrom[60]: 55 nodes 1 leaves 96 minterms\nReached[60]: 153 nodes 1 leaves 6126 minterms\nFrom[61]: 53 nodes 1 leaves 84 minterms\nReached[61]: 163 nodes 1 leaves 6210 minterms\nFrom[62]: 50 nodes 1 leaves 92 minterms\nReached[62]: 171 nodes 1 leaves 6302 minterms\nFrom[63]: 53 nodes 1 leaves 92 minterms\nReached[63]: 173 nodes 1 leaves 6394 minterms\nFrom[64]: 49 nodes 1 leaves 92 minterms\nReached[64]: 167 nodes 1 leaves 6486 minterms\nFrom[65]: 51 nodes 1 leaves 92 minterms\nReached[65]: 168 nodes 1 leaves 6578 minterms\nFrom[66]: 53 nodes 1 leaves 92 minterms\nReached[66]: 173 nodes 1 leaves 6670 minterms\nFrom[67]: 55 nodes 1 leaves 92 minterms\nReached[67]: 170 nodes 1 leaves 6762 minterms\nFrom[68]: 49 nodes 1 leaves 92 minterms\nReached[68]: 162 nodes 1 leaves 6854 minterms\nFrom[69]: 52 nodes 1 leaves 92 minterms\nReached[69]: 154 nodes 1 leaves 6946 minterms\nFrom[70]: 47 nodes 1 leaves 92 minterms\nReached[70]: 156 nodes 1 leaves 7038 minterms\nFrom[71]: 61 nodes 1 leaves 79 minterms\nReached[71]: 156 nodes 1 leaves 7117 minterms\nFrom[72]: 48 nodes 1 leaves 80 minterms\nReached[72]: 154 nodes 1 leaves 7197 minterms\nFrom[73]: 51 nodes 1 leaves 76 minterms\nReached[73]: 156 nodes 1 leaves 7273 minterms\nFrom[74]: 47 nodes 1 leaves 72 minterms\nReached[74]: 150 nodes 1 leaves 7345 minterms\nFrom[75]: 49 nodes 1 leaves 68 minterms\nReached[75]: 151 nodes 1 leaves 7413 minterms\nFrom[76]: 52 nodes 1 leaves 64 minterms\nReached[76]: 155 nodes 1 leaves 7477 minterms\nFrom[77]: 54 nodes 1 leaves 60 minterms\nReached[77]: 152 nodes 1 leaves 7537 minterms\nFrom[78]: 46 nodes 1 leaves 56 minterms\nReached[78]: 143 nodes 1 leaves 7593 minterms\nFrom[79]: 49 nodes 1 leaves 52 minterms\nReached[79]: 133 nodes 1 leaves 7645 minterms\nFrom[80]: 34 nodes 1 leaves 48 minterms\nReached[80]: 136 nodes 1 leaves 7693 minterms\nFrom[81]: 37 nodes 1 leaves 40 minterms\nReached[81]: 146 nodes 1 leaves 7733 minterms\nFrom[82]: 36 nodes 1 leaves 48 minterms\nReached[82]: 144 nodes 1 leaves 7781 minterms\nFrom[83]: 39 nodes 1 leaves 48 minterms\nReached[83]: 147 nodes 1 leaves 7829 minterms\nFrom[84]: 36 nodes 1 leaves 48 minterms\nReached[84]: 141 nodes 1 leaves 7877 minterms\nFrom[85]: 35 nodes 1 leaves 48 minterms\nReached[85]: 143 nodes 1 leaves 7925 minterms\nFrom[86]: 38 nodes 1 leaves 48 minterms\nReached[86]: 146 nodes 1 leaves 7973 minterms\nFrom[87]: 40 nodes 1 leaves 48 minterms\nReached[87]: 145 nodes 1 leaves 8021 minterms\nFrom[88]: 36 nodes 1 leaves 48 minterms\nReached[88]: 137 nodes 1 leaves 8069 minterms\nFrom[89]: 35 nodes 1 leaves 48 minterms\nReached[89]: 133 nodes 1 leaves 8117 minterms\nFrom[90]: 34 nodes 1 leaves 48 minterms\nReached[90]: 136 nodes 1 leaves 8165 minterms\nFrom[91]: 38 nodes 1 leaves 40 minterms\nReached[91]: 146 nodes 1 leaves 8205 minterms\nFrom[92]: 37 nodes 1 leaves 48 minterms\nReached[92]: 144 nodes 1 leaves 8253 minterms\nFrom[93]: 40 nodes 1 leaves 48 minterms\nReached[93]: 147 nodes 1 leaves 8301 minterms\nFrom[94]: 37 nodes 1 leaves 48 minterms\nReached[94]: 141 nodes 1 leaves 8349 minterms\nFrom[95]: 36 nodes 1 leaves 48 minterms\nReached[95]: 143 nodes 1 leaves 8397 minterms\nFrom[96]: 40 nodes 1 leaves 48 minterms\nReached[96]: 146 nodes 1 leaves 8445 minterms\nFrom[97]: 42 nodes 1 leaves 48 minterms\nReached[97]: 145 nodes 1 leaves 8493 minterms\nFrom[98]: 38 nodes 1 leaves 48 minterms\nReached[98]: 136 nodes 1 leaves 8541 minterms\nFrom[99]: 36 nodes 1 leaves 48 minterms\nReached[99]: 131 nodes 1 leaves 8589 minterms\nFrom[100]: 34 nodes 1 leaves 48 minterms\nReached[100]: 134 nodes 1 leaves 8637 minterms\nFrom[101]: 36 nodes 1 leaves 36 minterms\nReached[101]: 139 nodes 1 leaves 8673 minterms\nFrom[102]: 35 nodes 1 leaves 40 minterms\nReached[102]: 136 nodes 1 leaves 8713 minterms\nFrom[103]: 36 nodes 1 leaves 36 minterms\nReached[103]: 135 nodes 1 leaves 8749 minterms\nFrom[104]: 34 nodes 1 leaves 32 minterms\nReached[104]: 129 nodes 1 leaves 8781 minterms\nFrom[105]: 33 nodes 1 leaves 28 minterms\nReached[105]: 126 nodes 1 leaves 8809 minterms\nFrom[106]: 34 nodes 1 leaves 20 minterms\nReached[106]: 124 nodes 1 leaves 8829 minterms\nFrom[107]: 35 nodes 1 leaves 16 minterms\nReached[107]: 118 nodes 1 leaves 8845 minterms\nFrom[108]: 32 nodes 1 leaves 12 minterms\nReached[108]: 108 nodes 1 leaves 8857 minterms\nFrom[109]: 19 nodes 1 leaves 8 minterms\nReached[109]: 97 nodes 1 leaves 8865 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[6]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 36 nodes 1 leaves 5 minterms\nReached[1]: 54 nodes 1 leaves 6 minterms\nFrom[2]: 32 nodes 1 leaves 12 minterms\nReached[2]: 71 nodes 1 leaves 18 minterms\nFrom[3]: 33 nodes 1 leaves 20 minterms\nReached[3]: 75 nodes 1 leaves 38 minterms\nFrom[4]: 43 nodes 1 leaves 32 minterms\nReached[4]: 87 nodes 1 leaves 70 minterms\nFrom[5]: 42 nodes 1 leaves 40 minterms\nReached[5]: 91 nodes 1 leaves 110 minterms\nFrom[6]: 41 nodes 1 leaves 48 minterms\nReached[6]: 96 nodes 1 leaves 158 minterms\nFrom[7]: 43 nodes 1 leaves 56 minterms\nReached[7]: 102 nodes 1 leaves 214 minterms\nFrom[8]: 45 nodes 1 leaves 68 minterms\nReached[8]: 104 nodes 1 leaves 282 minterms\nFrom[9]: 47 nodes 1 leaves 76 minterms\nReached[9]: 112 nodes 1 leaves 358 minterms\nFrom[10]: 47 nodes 1 leaves 84 minterms\nReached[10]: 118 nodes 1 leaves 442 minterms\nFrom[11]: 54 nodes 1 leaves 76 minterms\nReached[11]: 126 nodes 1 leaves 518 minterms\nFrom[12]: 51 nodes 1 leaves 88 minterms\nReached[12]: 128 nodes 1 leaves 606 minterms\nFrom[13]: 49 nodes 1 leaves 88 minterms\nReached[13]: 130 nodes 1 leaves 694 minterms\nFrom[14]: 58 nodes 1 leaves 88 minterms\nReached[14]: 133 nodes 1 leaves 782 minterms\nFrom[15]: 57 nodes 1 leaves 88 minterms\nReached[15]: 134 nodes 1 leaves 870 minterms\nFrom[16]: 53 nodes 1 leaves 88 minterms\nReached[16]: 133 nodes 1 leaves 958 minterms\nFrom[17]: 50 nodes 1 leaves 88 minterms\nReached[17]: 134 nodes 1 leaves 1046 minterms\nFrom[18]: 48 nodes 1 leaves 88 minterms\nReached[18]: 130 nodes 1 leaves 1134 minterms\nFrom[19]: 46 nodes 1 leaves 88 minterms\nReached[19]: 131 nodes 1 leaves 1222 minterms\nFrom[20]: 48 nodes 1 leaves 88 minterms\nReached[20]: 134 nodes 1 leaves 1310 minterms\nFrom[21]: 50 nodes 1 leaves 80 minterms\nReached[21]: 141 nodes 1 leaves 1390 minterms\nFrom[22]: 49 nodes 1 leaves 88 minterms\nReached[22]: 142 nodes 1 leaves 1478 minterms\nFrom[23]: 47 nodes 1 leaves 88 minterms\nReached[23]: 144 nodes 1 leaves 1566 minterms\nFrom[24]: 53 nodes 1 leaves 88 minterms\nReached[24]: 144 nodes 1 leaves 1654 minterms\nFrom[25]: 52 nodes 1 leaves 88 minterms\nReached[25]: 144 nodes 1 leaves 1742 minterms\nFrom[26]: 48 nodes 1 leaves 88 minterms\nReached[26]: 141 nodes 1 leaves 1830 minterms\nFrom[27]: 48 nodes 1 leaves 88 minterms\nReached[27]: 140 nodes 1 leaves 1918 minterms\nFrom[28]: 49 nodes 1 leaves 88 minterms\nReached[28]: 136 nodes 1 leaves 2006 minterms\nFrom[29]: 48 nodes 1 leaves 88 minterms\nReached[29]: 138 nodes 1 leaves 2094 minterms\nFrom[30]: 50 nodes 1 leaves 88 minterms\nReached[30]: 137 nodes 1 leaves 2182 minterms\nFrom[31]: 51 nodes 1 leaves 80 minterms\nReached[31]: 144 nodes 1 leaves 2262 minterms\nFrom[32]: 49 nodes 1 leaves 88 minterms\nReached[32]: 143 nodes 1 leaves 2350 minterms\nFrom[33]: 58 nodes 1 leaves 92 minterms\nReached[33]: 158 nodes 1 leaves 2442 minterms\nFrom[34]: 65 nodes 1 leaves 92 minterms\nReached[34]: 159 nodes 1 leaves 2534 minterms\nFrom[35]: 64 nodes 1 leaves 92 minterms\nReached[35]: 159 nodes 1 leaves 2626 minterms\nFrom[36]: 60 nodes 1 leaves 92 minterms\nReached[36]: 155 nodes 1 leaves 2718 minterms\nFrom[37]: 59 nodes 1 leaves 92 minterms\nReached[37]: 152 nodes 1 leaves 2810 minterms\nFrom[38]: 59 nodes 1 leaves 92 minterms\nReached[38]: 148 nodes 1 leaves 2902 minterms\nFrom[39]: 56 nodes 1 leaves 92 minterms\nReached[39]: 149 nodes 1 leaves 2994 minterms\nFrom[40]: 59 nodes 1 leaves 92 minterms\nReached[40]: 149 nodes 1 leaves 3086 minterms\nFrom[41]: 62 nodes 1 leaves 80 minterms\nReached[41]: 155 nodes 1 leaves 3166 minterms\nFrom[42]: 50 nodes 1 leaves 92 minterms\nReached[42]: 155 nodes 1 leaves 3258 minterms\nFrom[43]: 60 nodes 1 leaves 100 minterms\nReached[43]: 168 nodes 1 leaves 3358 minterms\nFrom[44]: 66 nodes 1 leaves 104 minterms\nReached[44]: 168 nodes 1 leaves 3462 minterms\nFrom[45]: 65 nodes 1 leaves 108 minterms\nReached[45]: 168 nodes 1 leaves 3570 minterms\nFrom[46]: 61 nodes 1 leaves 112 minterms\nReached[46]: 165 nodes 1 leaves 3682 minterms\nFrom[47]: 67 nodes 1 leaves 120 minterms\nReached[47]: 174 nodes 1 leaves 3802 minterms\nFrom[48]: 69 nodes 1 leaves 124 minterms\nReached[48]: 170 nodes 1 leaves 3926 minterms\nFrom[49]: 66 nodes 1 leaves 124 minterms\nReached[49]: 167 nodes 1 leaves 4050 minterms\nFrom[50]: 67 nodes 1 leaves 124 minterms\nReached[50]: 167 nodes 1 leaves 4174 minterms\nFrom[51]: 66 nodes 1 leaves 108 minterms\nReached[51]: 181 nodes 1 leaves 4282 minterms\nFrom[52]: 50 nodes 1 leaves 128 minterms\nReached[52]: 179 nodes 1 leaves 4410 minterms\nFrom[53]: 51 nodes 1 leaves 116 minterms\nReached[53]: 179 nodes 1 leaves 4526 minterms\nFrom[54]: 57 nodes 1 leaves 108 minterms\nReached[54]: 175 nodes 1 leaves 4634 minterms\nFrom[55]: 54 nodes 1 leaves 104 minterms\nReached[55]: 171 nodes 1 leaves 4738 minterms\nFrom[56]: 52 nodes 1 leaves 100 minterms\nReached[56]: 163 nodes 1 leaves 4838 minterms\nFrom[57]: 51 nodes 1 leaves 96 minterms\nReached[57]: 163 nodes 1 leaves 4934 minterms\nFrom[58]: 51 nodes 1 leaves 88 minterms\nReached[58]: 155 nodes 1 leaves 5022 minterms\nFrom[59]: 45 nodes 1 leaves 88 minterms\nReached[59]: 149 nodes 1 leaves 5110 minterms\nFrom[60]: 48 nodes 1 leaves 88 minterms\nReached[60]: 145 nodes 1 leaves 5198 minterms\nFrom[61]: 47 nodes 1 leaves 80 minterms\nReached[61]: 156 nodes 1 leaves 5278 minterms\nFrom[62]: 48 nodes 1 leaves 88 minterms\nReached[62]: 159 nodes 1 leaves 5366 minterms\nFrom[63]: 47 nodes 1 leaves 88 minterms\nReached[63]: 162 nodes 1 leaves 5454 minterms\nFrom[64]: 50 nodes 1 leaves 88 minterms\nReached[64]: 159 nodes 1 leaves 5542 minterms\nFrom[65]: 46 nodes 1 leaves 88 minterms\nReached[65]: 158 nodes 1 leaves 5630 minterms\nFrom[66]: 48 nodes 1 leaves 88 minterms\nReached[66]: 156 nodes 1 leaves 5718 minterms\nFrom[67]: 52 nodes 1 leaves 88 minterms\nReached[67]: 166 nodes 1 leaves 5806 minterms\nFrom[68]: 54 nodes 1 leaves 88 minterms\nReached[68]: 158 nodes 1 leaves 5894 minterms\nFrom[69]: 47 nodes 1 leaves 88 minterms\nReached[69]: 151 nodes 1 leaves 5982 minterms\nFrom[70]: 50 nodes 1 leaves 88 minterms\nReached[70]: 145 nodes 1 leaves 6070 minterms\nFrom[71]: 47 nodes 1 leaves 80 minterms\nReached[71]: 156 nodes 1 leaves 6150 minterms\nFrom[72]: 47 nodes 1 leaves 88 minterms\nReached[72]: 158 nodes 1 leaves 6238 minterms\nFrom[73]: 46 nodes 1 leaves 88 minterms\nReached[73]: 161 nodes 1 leaves 6326 minterms\nFrom[74]: 49 nodes 1 leaves 88 minterms\nReached[74]: 158 nodes 1 leaves 6414 minterms\nFrom[75]: 45 nodes 1 leaves 88 minterms\nReached[75]: 157 nodes 1 leaves 6502 minterms\nFrom[76]: 47 nodes 1 leaves 88 minterms\nReached[76]: 155 nodes 1 leaves 6590 minterms\nFrom[77]: 49 nodes 1 leaves 88 minterms\nReached[77]: 163 nodes 1 leaves 6678 minterms\nFrom[78]: 51 nodes 1 leaves 88 minterms\nReached[78]: 155 nodes 1 leaves 6766 minterms\nFrom[79]: 45 nodes 1 leaves 88 minterms\nReached[79]: 149 nodes 1 leaves 6854 minterms\nFrom[80]: 48 nodes 1 leaves 88 minterms\nReached[80]: 145 nodes 1 leaves 6942 minterms\nFrom[81]: 47 nodes 1 leaves 80 minterms\nReached[81]: 156 nodes 1 leaves 7022 minterms\nFrom[82]: 50 nodes 1 leaves 88 minterms\nReached[82]: 161 nodes 1 leaves 7110 minterms\nFrom[83]: 54 nodes 1 leaves 92 minterms\nReached[83]: 177 nodes 1 leaves 7202 minterms\nFrom[84]: 57 nodes 1 leaves 92 minterms\nReached[84]: 174 nodes 1 leaves 7294 minterms\nFrom[85]: 53 nodes 1 leaves 92 minterms\nReached[85]: 173 nodes 1 leaves 7386 minterms\nFrom[86]: 55 nodes 1 leaves 92 minterms\nReached[86]: 171 nodes 1 leaves 7478 minterms\nFrom[87]: 63 nodes 1 leaves 92 minterms\nReached[87]: 179 nodes 1 leaves 7570 minterms\nFrom[88]: 65 nodes 1 leaves 92 minterms\nReached[88]: 171 nodes 1 leaves 7662 minterms\nFrom[89]: 56 nodes 1 leaves 92 minterms\nReached[89]: 162 nodes 1 leaves 7754 minterms\nFrom[90]: 59 nodes 1 leaves 92 minterms\nReached[90]: 154 nodes 1 leaves 7846 minterms\nFrom[91]: 53 nodes 1 leaves 80 minterms\nReached[91]: 161 nodes 1 leaves 7926 minterms\nFrom[92]: 42 nodes 1 leaves 92 minterms\nReached[92]: 161 nodes 1 leaves 8018 minterms\nFrom[93]: 50 nodes 1 leaves 92 minterms\nReached[93]: 174 nodes 1 leaves 8110 minterms\nFrom[94]: 53 nodes 1 leaves 92 minterms\nReached[94]: 170 nodes 1 leaves 8202 minterms\nFrom[95]: 49 nodes 1 leaves 92 minterms\nReached[95]: 169 nodes 1 leaves 8294 minterms\nFrom[96]: 51 nodes 1 leaves 92 minterms\nReached[96]: 167 nodes 1 leaves 8386 minterms\nFrom[97]: 53 nodes 1 leaves 92 minterms\nReached[97]: 173 nodes 1 leaves 8478 minterms\nFrom[98]: 55 nodes 1 leaves 92 minterms\nReached[98]: 165 nodes 1 leaves 8570 minterms\nFrom[99]: 49 nodes 1 leaves 92 minterms\nReached[99]: 159 nodes 1 leaves 8662 minterms\nFrom[100]: 52 nodes 1 leaves 92 minterms\nReached[100]: 155 nodes 1 leaves 8754 minterms\nFrom[101]: 52 nodes 1 leaves 80 minterms\nReached[101]: 164 nodes 1 leaves 8834 minterms\nFrom[102]: 44 nodes 1 leaves 84 minterms\nReached[102]: 160 nodes 1 leaves 8918 minterms\nFrom[103]: 44 nodes 1 leaves 72 minterms\nReached[103]: 160 nodes 1 leaves 8990 minterms\nFrom[104]: 45 nodes 1 leaves 64 minterms\nReached[104]: 155 nodes 1 leaves 9054 minterms\nFrom[105]: 42 nodes 1 leaves 56 minterms\nReached[105]: 151 nodes 1 leaves 9110 minterms\nFrom[106]: 44 nodes 1 leaves 48 minterms\nReached[106]: 145 nodes 1 leaves 9158 minterms\nFrom[107]: 42 nodes 1 leaves 36 minterms\nReached[107]: 142 nodes 1 leaves 9194 minterms\nFrom[108]: 43 nodes 1 leaves 28 minterms\nReached[108]: 134 nodes 1 leaves 9222 minterms\nFrom[109]: 35 nodes 1 leaves 20 minterms\nReached[109]: 126 nodes 1 leaves 9242 minterms\nFrom[110]: 32 nodes 1 leaves 12 minterms\nReached[110]: 114 nodes 1 leaves 9254 minterms\nFrom[111]: 22 nodes 1 leaves 3 minterms\nReached[111]: 104 nodes 1 leaves 9257 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[7]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 37 nodes 1 leaves 5 minterms\nReached[1]: 56 nodes 1 leaves 6 minterms\nFrom[2]: 20 nodes 1 leaves 12 minterms\nReached[2]: 59 nodes 1 leaves 18 minterms\nFrom[3]: 26 nodes 1 leaves 16 minterms\nReached[3]: 68 nodes 1 leaves 34 minterms\nFrom[4]: 26 nodes 1 leaves 24 minterms\nReached[4]: 68 nodes 1 leaves 58 minterms\nFrom[5]: 26 nodes 1 leaves 28 minterms\nReached[5]: 73 nodes 1 leaves 86 minterms\nFrom[6]: 27 nodes 1 leaves 32 minterms\nReached[6]: 72 nodes 1 leaves 118 minterms\nFrom[7]: 25 nodes 1 leaves 36 minterms\nReached[7]: 74 nodes 1 leaves 154 minterms\nFrom[8]: 26 nodes 1 leaves 40 minterms\nReached[8]: 76 nodes 1 leaves 194 minterms\nFrom[9]: 28 nodes 1 leaves 40 minterms\nReached[9]: 78 nodes 1 leaves 234 minterms\nFrom[10]: 28 nodes 1 leaves 40 minterms\nReached[10]: 76 nodes 1 leaves 274 minterms\nFrom[11]: 27 nodes 1 leaves 40 minterms\nReached[11]: 82 nodes 1 leaves 314 minterms\nFrom[12]: 26 nodes 1 leaves 40 minterms\nReached[12]: 82 nodes 1 leaves 354 minterms\nFrom[13]: 31 nodes 1 leaves 40 minterms\nReached[13]: 82 nodes 1 leaves 394 minterms\nFrom[14]: 31 nodes 1 leaves 40 minterms\nReached[14]: 82 nodes 1 leaves 434 minterms\nFrom[15]: 32 nodes 1 leaves 40 minterms\nReached[15]: 82 nodes 1 leaves 474 minterms\nFrom[16]: 30 nodes 1 leaves 40 minterms\nReached[16]: 81 nodes 1 leaves 514 minterms\nFrom[17]: 29 nodes 1 leaves 40 minterms\nReached[17]: 79 nodes 1 leaves 554 minterms\nFrom[18]: 26 nodes 1 leaves 40 minterms\nReached[18]: 79 nodes 1 leaves 594 minterms\nFrom[19]: 28 nodes 1 leaves 40 minterms\nReached[19]: 81 nodes 1 leaves 634 minterms\nFrom[20]: 28 nodes 1 leaves 40 minterms\nReached[20]: 79 nodes 1 leaves 674 minterms\nFrom[21]: 28 nodes 1 leaves 40 minterms\nReached[21]: 86 nodes 1 leaves 714 minterms\nFrom[22]: 27 nodes 1 leaves 40 minterms\nReached[22]: 86 nodes 1 leaves 754 minterms\nFrom[23]: 32 nodes 1 leaves 40 minterms\nReached[23]: 86 nodes 1 leaves 794 minterms\nFrom[24]: 32 nodes 1 leaves 40 minterms\nReached[24]: 86 nodes 1 leaves 834 minterms\nFrom[25]: 33 nodes 1 leaves 40 minterms\nReached[25]: 86 nodes 1 leaves 874 minterms\nFrom[26]: 31 nodes 1 leaves 40 minterms\nReached[26]: 85 nodes 1 leaves 914 minterms\nFrom[27]: 30 nodes 1 leaves 40 minterms\nReached[27]: 79 nodes 1 leaves 954 minterms\nFrom[28]: 26 nodes 1 leaves 40 minterms\nReached[28]: 79 nodes 1 leaves 994 minterms\nFrom[29]: 28 nodes 1 leaves 40 minterms\nReached[29]: 81 nodes 1 leaves 1034 minterms\nFrom[30]: 28 nodes 1 leaves 40 minterms\nReached[30]: 79 nodes 1 leaves 1074 minterms\nFrom[31]: 27 nodes 1 leaves 40 minterms\nReached[31]: 85 nodes 1 leaves 1114 minterms\nFrom[32]: 39 nodes 1 leaves 44 minterms\nReached[32]: 98 nodes 1 leaves 1158 minterms\nFrom[33]: 46 nodes 1 leaves 44 minterms\nReached[33]: 102 nodes 1 leaves 1202 minterms\nFrom[34]: 44 nodes 1 leaves 48 minterms\nReached[34]: 101 nodes 1 leaves 1250 minterms\nFrom[35]: 46 nodes 1 leaves 44 minterms\nReached[35]: 101 nodes 1 leaves 1294 minterms\nFrom[36]: 44 nodes 1 leaves 44 minterms\nReached[36]: 99 nodes 1 leaves 1338 minterms\nFrom[37]: 43 nodes 1 leaves 44 minterms\nReached[37]: 94 nodes 1 leaves 1382 minterms\nFrom[38]: 40 nodes 1 leaves 44 minterms\nReached[38]: 94 nodes 1 leaves 1426 minterms\nFrom[39]: 26 nodes 1 leaves 44 minterms\nReached[39]: 95 nodes 1 leaves 1470 minterms\nFrom[40]: 28 nodes 1 leaves 40 minterms\nReached[40]: 93 nodes 1 leaves 1510 minterms\nFrom[41]: 29 nodes 1 leaves 40 minterms\nReached[41]: 101 nodes 1 leaves 1550 minterms\nFrom[42]: 46 nodes 1 leaves 52 minterms\nReached[42]: 117 nodes 1 leaves 1602 minterms\nFrom[43]: 53 nodes 1 leaves 60 minterms\nReached[43]: 121 nodes 1 leaves 1662 minterms\nFrom[44]: 51 nodes 1 leaves 76 minterms\nReached[44]: 120 nodes 1 leaves 1738 minterms\nFrom[45]: 53 nodes 1 leaves 72 minterms\nReached[45]: 120 nodes 1 leaves 1810 minterms\nFrom[46]: 70 nodes 1 leaves 80 minterms\nReached[46]: 136 nodes 1 leaves 1890 minterms\nFrom[47]: 68 nodes 1 leaves 88 minterms\nReached[47]: 131 nodes 1 leaves 1978 minterms\nFrom[48]: 62 nodes 1 leaves 92 minterms\nReached[48]: 127 nodes 1 leaves 2070 minterms\nFrom[49]: 49 nodes 1 leaves 92 minterms\nReached[49]: 128 nodes 1 leaves 2162 minterms\nFrom[50]: 56 nodes 1 leaves 88 minterms\nReached[50]: 131 nodes 1 leaves 2250 minterms\nFrom[51]: 57 nodes 1 leaves 84 minterms\nReached[51]: 142 nodes 1 leaves 2334 minterms\nFrom[52]: 51 nodes 1 leaves 92 minterms\nReached[52]: 141 nodes 1 leaves 2426 minterms\nFrom[53]: 54 nodes 1 leaves 88 minterms\nReached[53]: 139 nodes 1 leaves 2514 minterms\nFrom[54]: 53 nodes 1 leaves 84 minterms\nReached[54]: 138 nodes 1 leaves 2598 minterms\nFrom[55]: 54 nodes 1 leaves 84 minterms\nReached[55]: 137 nodes 1 leaves 2682 minterms\nFrom[56]: 58 nodes 1 leaves 88 minterms\nReached[56]: 140 nodes 1 leaves 2770 minterms\nFrom[57]: 55 nodes 1 leaves 92 minterms\nReached[57]: 132 nodes 1 leaves 2862 minterms\nFrom[58]: 50 nodes 1 leaves 88 minterms\nReached[58]: 132 nodes 1 leaves 2950 minterms\nFrom[59]: 51 nodes 1 leaves 84 minterms\nReached[59]: 134 nodes 1 leaves 3034 minterms\nFrom[60]: 56 nodes 1 leaves 88 minterms\nReached[60]: 137 nodes 1 leaves 3122 minterms\nFrom[61]: 58 nodes 1 leaves 84 minterms\nReached[61]: 149 nodes 1 leaves 3206 minterms\nFrom[62]: 52 nodes 1 leaves 92 minterms\nReached[62]: 148 nodes 1 leaves 3298 minterms\nFrom[63]: 55 nodes 1 leaves 88 minterms\nReached[63]: 146 nodes 1 leaves 3386 minterms\nFrom[64]: 54 nodes 1 leaves 84 minterms\nReached[64]: 145 nodes 1 leaves 3470 minterms\nFrom[65]: 55 nodes 1 leaves 84 minterms\nReached[65]: 143 nodes 1 leaves 3554 minterms\nFrom[66]: 60 nodes 1 leaves 88 minterms\nReached[66]: 146 nodes 1 leaves 3642 minterms\nFrom[67]: 57 nodes 1 leaves 92 minterms\nReached[67]: 135 nodes 1 leaves 3734 minterms\nFrom[68]: 50 nodes 1 leaves 88 minterms\nReached[68]: 135 nodes 1 leaves 3822 minterms\nFrom[69]: 51 nodes 1 leaves 84 minterms\nReached[69]: 137 nodes 1 leaves 3906 minterms\nFrom[70]: 56 nodes 1 leaves 88 minterms\nReached[70]: 140 nodes 1 leaves 3994 minterms\nFrom[71]: 57 nodes 1 leaves 84 minterms\nReached[71]: 151 nodes 1 leaves 4078 minterms\nFrom[72]: 51 nodes 1 leaves 92 minterms\nReached[72]: 149 nodes 1 leaves 4170 minterms\nFrom[73]: 54 nodes 1 leaves 88 minterms\nReached[73]: 147 nodes 1 leaves 4258 minterms\nFrom[74]: 53 nodes 1 leaves 84 minterms\nReached[74]: 146 nodes 1 leaves 4342 minterms\nFrom[75]: 54 nodes 1 leaves 84 minterms\nReached[75]: 144 nodes 1 leaves 4426 minterms\nFrom[76]: 58 nodes 1 leaves 88 minterms\nReached[76]: 146 nodes 1 leaves 4514 minterms\nFrom[77]: 55 nodes 1 leaves 92 minterms\nReached[77]: 135 nodes 1 leaves 4606 minterms\nFrom[78]: 50 nodes 1 leaves 88 minterms\nReached[78]: 135 nodes 1 leaves 4694 minterms\nFrom[79]: 51 nodes 1 leaves 84 minterms\nReached[79]: 137 nodes 1 leaves 4778 minterms\nFrom[80]: 56 nodes 1 leaves 88 minterms\nReached[80]: 140 nodes 1 leaves 4866 minterms\nFrom[81]: 60 nodes 1 leaves 84 minterms\nReached[81]: 154 nodes 1 leaves 4950 minterms\nFrom[82]: 68 nodes 1 leaves 96 minterms\nReached[82]: 166 nodes 1 leaves 5046 minterms\nFrom[83]: 72 nodes 1 leaves 92 minterms\nReached[83]: 168 nodes 1 leaves 5138 minterms\nFrom[84]: 67 nodes 1 leaves 92 minterms\nReached[84]: 166 nodes 1 leaves 5230 minterms\nFrom[85]: 62 nodes 1 leaves 88 minterms\nReached[85]: 164 nodes 1 leaves 5318 minterms\nFrom[86]: 69 nodes 1 leaves 92 minterms\nReached[86]: 164 nodes 1 leaves 5410 minterms\nFrom[87]: 69 nodes 1 leaves 96 minterms\nReached[87]: 151 nodes 1 leaves 5506 minterms\nFrom[88]: 56 nodes 1 leaves 92 minterms\nReached[88]: 145 nodes 1 leaves 5598 minterms\nFrom[89]: 47 nodes 1 leaves 88 minterms\nReached[89]: 145 nodes 1 leaves 5686 minterms\nFrom[90]: 52 nodes 1 leaves 88 minterms\nReached[90]: 148 nodes 1 leaves 5774 minterms\nFrom[91]: 53 nodes 1 leaves 84 minterms\nReached[91]: 158 nodes 1 leaves 5858 minterms\nFrom[92]: 61 nodes 1 leaves 96 minterms\nReached[92]: 166 nodes 1 leaves 5954 minterms\nFrom[93]: 65 nodes 1 leaves 92 minterms\nReached[93]: 168 nodes 1 leaves 6046 minterms\nFrom[94]: 60 nodes 1 leaves 92 minterms\nReached[94]: 166 nodes 1 leaves 6138 minterms\nFrom[95]: 58 nodes 1 leaves 88 minterms\nReached[95]: 164 nodes 1 leaves 6226 minterms\nFrom[96]: 62 nodes 1 leaves 92 minterms\nReached[96]: 163 nodes 1 leaves 6318 minterms\nFrom[97]: 62 nodes 1 leaves 96 minterms\nReached[97]: 152 nodes 1 leaves 6414 minterms\nFrom[98]: 55 nodes 1 leaves 92 minterms\nReached[98]: 148 nodes 1 leaves 6506 minterms\nFrom[99]: 50 nodes 1 leaves 88 minterms\nReached[99]: 148 nodes 1 leaves 6594 minterms\nFrom[100]: 55 nodes 1 leaves 88 minterms\nReached[100]: 151 nodes 1 leaves 6682 minterms\nFrom[101]: 59 nodes 1 leaves 80 minterms\nReached[101]: 163 nodes 1 leaves 6762 minterms\nFrom[102]: 53 nodes 1 leaves 80 minterms\nReached[102]: 161 nodes 1 leaves 6842 minterms\nFrom[103]: 72 nodes 1 leaves 71 minterms\nReached[103]: 148 nodes 1 leaves 6913 minterms\nFrom[104]: 55 nodes 1 leaves 60 minterms\nReached[104]: 147 nodes 1 leaves 6973 minterms\nFrom[105]: 56 nodes 1 leaves 56 minterms\nReached[105]: 145 nodes 1 leaves 7029 minterms\nFrom[106]: 56 nodes 1 leaves 56 minterms\nReached[106]: 144 nodes 1 leaves 7085 minterms\nFrom[107]: 55 nodes 1 leaves 56 minterms\nReached[107]: 131 nodes 1 leaves 7141 minterms\nFrom[108]: 38 nodes 1 leaves 48 minterms\nReached[108]: 131 nodes 1 leaves 7189 minterms\nFrom[109]: 41 nodes 1 leaves 44 minterms\nReached[109]: 133 nodes 1 leaves 7233 minterms\nFrom[110]: 43 nodes 1 leaves 48 minterms\nReached[110]: 133 nodes 1 leaves 7281 minterms\nFrom[111]: 45 nodes 1 leaves 44 minterms\nReached[111]: 144 nodes 1 leaves 7325 minterms\nFrom[112]: 39 nodes 1 leaves 52 minterms\nReached[112]: 142 nodes 1 leaves 7377 minterms\nFrom[113]: 42 nodes 1 leaves 48 minterms\nReached[113]: 141 nodes 1 leaves 7425 minterms\nFrom[114]: 44 nodes 1 leaves 44 minterms\nReached[114]: 140 nodes 1 leaves 7469 minterms\nFrom[115]: 45 nodes 1 leaves 44 minterms\nReached[115]: 140 nodes 1 leaves 7513 minterms\nFrom[116]: 46 nodes 1 leaves 48 minterms\nReached[116]: 138 nodes 1 leaves 7561 minterms\nFrom[117]: 41 nodes 1 leaves 52 minterms\nReached[117]: 131 nodes 1 leaves 7613 minterms\nFrom[118]: 38 nodes 1 leaves 48 minterms\nReached[118]: 131 nodes 1 leaves 7661 minterms\nFrom[119]: 41 nodes 1 leaves 44 minterms\nReached[119]: 133 nodes 1 leaves 7705 minterms\nFrom[120]: 43 nodes 1 leaves 48 minterms\nReached[120]: 133 nodes 1 leaves 7753 minterms\nFrom[121]: 46 nodes 1 leaves 44 minterms\nReached[121]: 145 nodes 1 leaves 7797 minterms\nFrom[122]: 40 nodes 1 leaves 52 minterms\nReached[122]: 143 nodes 1 leaves 7849 minterms\nFrom[123]: 43 nodes 1 leaves 48 minterms\nReached[123]: 142 nodes 1 leaves 7897 minterms\nFrom[124]: 45 nodes 1 leaves 44 minterms\nReached[124]: 141 nodes 1 leaves 7941 minterms\nFrom[125]: 46 nodes 1 leaves 44 minterms\nReached[125]: 141 nodes 1 leaves 7985 minterms\nFrom[126]: 48 nodes 1 leaves 48 minterms\nReached[126]: 139 nodes 1 leaves 8033 minterms\nFrom[127]: 42 nodes 1 leaves 52 minterms\nReached[127]: 131 nodes 1 leaves 8085 minterms\nFrom[128]: 38 nodes 1 leaves 48 minterms\nReached[128]: 131 nodes 1 leaves 8133 minterms\nFrom[129]: 41 nodes 1 leaves 44 minterms\nReached[129]: 133 nodes 1 leaves 8177 minterms\nFrom[130]: 43 nodes 1 leaves 48 minterms\nReached[130]: 133 nodes 1 leaves 8225 minterms\nFrom[131]: 45 nodes 1 leaves 44 minterms\nReached[131]: 144 nodes 1 leaves 8269 minterms\nFrom[132]: 39 nodes 1 leaves 52 minterms\nReached[132]: 142 nodes 1 leaves 8321 minterms\nFrom[133]: 42 nodes 1 leaves 48 minterms\nReached[133]: 141 nodes 1 leaves 8369 minterms\nFrom[134]: 44 nodes 1 leaves 44 minterms\nReached[134]: 140 nodes 1 leaves 8413 minterms\nFrom[135]: 45 nodes 1 leaves 44 minterms\nReached[135]: 140 nodes 1 leaves 8457 minterms\nFrom[136]: 46 nodes 1 leaves 48 minterms\nReached[136]: 138 nodes 1 leaves 8505 minterms\nFrom[137]: 41 nodes 1 leaves 52 minterms\nReached[137]: 131 nodes 1 leaves 8557 minterms\nFrom[138]: 38 nodes 1 leaves 48 minterms\nReached[138]: 131 nodes 1 leaves 8605 minterms\nFrom[139]: 41 nodes 1 leaves 44 minterms\nReached[139]: 133 nodes 1 leaves 8649 minterms\nFrom[140]: 43 nodes 1 leaves 48 minterms\nReached[140]: 133 nodes 1 leaves 8697 minterms\nFrom[141]: 41 nodes 1 leaves 40 minterms\nReached[141]: 139 nodes 1 leaves 8737 minterms\nFrom[142]: 34 nodes 1 leaves 40 minterms\nReached[142]: 135 nodes 1 leaves 8777 minterms\nFrom[143]: 42 nodes 1 leaves 32 minterms\nReached[143]: 125 nodes 1 leaves 8809 minterms\nFrom[144]: 34 nodes 1 leaves 20 minterms\nReached[144]: 122 nodes 1 leaves 8829 minterms\nFrom[145]: 35 nodes 1 leaves 16 minterms\nReached[145]: 119 nodes 1 leaves 8845 minterms\nFrom[146]: 32 nodes 1 leaves 12 minterms\nReached[146]: 109 nodes 1 leaves 8857 minterms\nFrom[147]: 19 nodes 1 leaves 8 minterms\nReached[147]: 97 nodes 1 leaves 8865 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[8]: 22 nodes 1 leaves 1 minterms\nS0: 22 nodes 1 leaves 1 minterms\nFrom[1]: 40 nodes 1 leaves 5 minterms\nReached[1]: 59 nodes 1 leaves 6 minterms\nFrom[2]: 35 nodes 1 leaves 12 minterms\nReached[2]: 87 nodes 1 leaves 18 minterms\nFrom[3]: 35 nodes 1 leaves 20 minterms\nReached[3]: 93 nodes 1 leaves 38 minterms\nFrom[4]: 34 nodes 1 leaves 28 minterms\nReached[4]: 98 nodes 1 leaves 66 minterms\nFrom[5]: 35 nodes 1 leaves 32 minterms\nReached[5]: 107 nodes 1 leaves 98 minterms\nFrom[6]: 47 nodes 1 leaves 44 minterms\nReached[6]: 107 nodes 1 leaves 142 minterms\nFrom[7]: 46 nodes 1 leaves 52 minterms\nReached[7]: 116 nodes 1 leaves 194 minterms\nFrom[8]: 46 nodes 1 leaves 60 minterms\nReached[8]: 120 nodes 1 leaves 254 minterms\nFrom[9]: 44 nodes 1 leaves 68 minterms\nReached[9]: 127 nodes 1 leaves 322 minterms\nFrom[10]: 49 nodes 1 leaves 80 minterms\nReached[10]: 130 nodes 1 leaves 402 minterms\nFrom[11]: 53 nodes 1 leaves 84 minterms\nReached[11]: 136 nodes 1 leaves 486 minterms\nFrom[12]: 64 nodes 1 leaves 96 minterms\nReached[12]: 151 nodes 1 leaves 582 minterms\nFrom[13]: 63 nodes 1 leaves 100 minterms\nReached[13]: 154 nodes 1 leaves 682 minterms\nFrom[14]: 64 nodes 1 leaves 104 minterms\nReached[14]: 150 nodes 1 leaves 786 minterms\nFrom[15]: 62 nodes 1 leaves 96 minterms\nReached[15]: 158 nodes 1 leaves 882 minterms\nFrom[16]: 67 nodes 1 leaves 112 minterms\nReached[16]: 161 nodes 1 leaves 994 minterms\nFrom[17]: 66 nodes 1 leaves 116 minterms\nReached[17]: 166 nodes 1 leaves 1110 minterms\nFrom[18]: 64 nodes 1 leaves 120 minterms\nReached[18]: 160 nodes 1 leaves 1230 minterms\nFrom[19]: 57 nodes 1 leaves 124 minterms\nReached[19]: 161 nodes 1 leaves 1354 minterms\nFrom[20]: 60 nodes 1 leaves 128 minterms\nReached[20]: 163 nodes 1 leaves 1482 minterms\nFrom[21]: 60 nodes 1 leaves 132 minterms\nReached[21]: 166 nodes 1 leaves 1614 minterms\nFrom[22]: 68 nodes 1 leaves 128 minterms\nReached[22]: 171 nodes 1 leaves 1742 minterms\nFrom[23]: 67 nodes 1 leaves 128 minterms\nReached[23]: 172 nodes 1 leaves 1870 minterms\nFrom[24]: 67 nodes 1 leaves 128 minterms\nReached[24]: 166 nodes 1 leaves 1998 minterms\nFrom[25]: 65 nodes 1 leaves 120 minterms\nReached[25]: 172 nodes 1 leaves 2118 minterms\nFrom[26]: 72 nodes 1 leaves 128 minterms\nReached[26]: 177 nodes 1 leaves 2246 minterms\nFrom[27]: 71 nodes 1 leaves 128 minterms\nReached[27]: 180 nodes 1 leaves 2374 minterms\nFrom[28]: 67 nodes 1 leaves 128 minterms\nReached[28]: 173 nodes 1 leaves 2502 minterms\nFrom[29]: 64 nodes 1 leaves 128 minterms\nReached[29]: 168 nodes 1 leaves 2630 minterms\nFrom[30]: 61 nodes 1 leaves 128 minterms\nReached[30]: 166 nodes 1 leaves 2758 minterms\nFrom[31]: 60 nodes 1 leaves 128 minterms\nReached[31]: 171 nodes 1 leaves 2886 minterms\nFrom[32]: 66 nodes 1 leaves 128 minterms\nReached[32]: 175 nodes 1 leaves 3014 minterms\nFrom[33]: 79 nodes 1 leaves 132 minterms\nReached[33]: 190 nodes 1 leaves 3146 minterms\nFrom[34]: 78 nodes 1 leaves 132 minterms\nReached[34]: 183 nodes 1 leaves 3278 minterms\nFrom[35]: 77 nodes 1 leaves 124 minterms\nReached[35]: 189 nodes 1 leaves 3402 minterms\nFrom[36]: 80 nodes 1 leaves 132 minterms\nReached[36]: 192 nodes 1 leaves 3534 minterms\nFrom[37]: 81 nodes 1 leaves 132 minterms\nReached[37]: 194 nodes 1 leaves 3666 minterms\nFrom[38]: 77 nodes 1 leaves 132 minterms\nReached[38]: 186 nodes 1 leaves 3798 minterms\nFrom[39]: 75 nodes 1 leaves 132 minterms\nReached[39]: 180 nodes 1 leaves 3930 minterms\nFrom[40]: 71 nodes 1 leaves 132 minterms\nReached[40]: 179 nodes 1 leaves 4062 minterms\nFrom[41]: 80 nodes 1 leaves 128 minterms\nReached[41]: 186 nodes 1 leaves 4190 minterms\nFrom[42]: 76 nodes 1 leaves 136 minterms\nReached[42]: 205 nodes 1 leaves 4326 minterms\nFrom[43]: 83 nodes 1 leaves 140 minterms\nReached[43]: 211 nodes 1 leaves 4466 minterms\nFrom[44]: 82 nodes 1 leaves 140 minterms\nReached[44]: 205 nodes 1 leaves 4606 minterms\nFrom[45]: 86 nodes 1 leaves 128 minterms\nReached[45]: 212 nodes 1 leaves 4734 minterms\nFrom[46]: 90 nodes 1 leaves 140 minterms\nReached[46]: 216 nodes 1 leaves 4874 minterms\nFrom[47]: 91 nodes 1 leaves 140 minterms\nReached[47]: 218 nodes 1 leaves 5014 minterms\nFrom[48]: 86 nodes 1 leaves 136 minterms\nReached[48]: 209 nodes 1 leaves 5150 minterms\nFrom[49]: 82 nodes 1 leaves 136 minterms\nReached[49]: 201 nodes 1 leaves 5286 minterms\nFrom[50]: 74 nodes 1 leaves 136 minterms\nReached[50]: 196 nodes 1 leaves 5422 minterms\nFrom[51]: 73 nodes 1 leaves 132 minterms\nReached[51]: 193 nodes 1 leaves 5554 minterms\nFrom[52]: 71 nodes 1 leaves 136 minterms\nReached[52]: 199 nodes 1 leaves 5690 minterms\nFrom[53]: 69 nodes 1 leaves 124 minterms\nReached[53]: 196 nodes 1 leaves 5814 minterms\nFrom[54]: 66 nodes 1 leaves 120 minterms\nReached[54]: 188 nodes 1 leaves 5934 minterms\nFrom[55]: 68 nodes 1 leaves 104 minterms\nReached[55]: 194 nodes 1 leaves 6038 minterms\nFrom[56]: 69 nodes 1 leaves 112 minterms\nReached[56]: 195 nodes 1 leaves 6150 minterms\nFrom[57]: 70 nodes 1 leaves 108 minterms\nReached[57]: 194 nodes 1 leaves 6258 minterms\nFrom[58]: 65 nodes 1 leaves 104 minterms\nReached[58]: 183 nodes 1 leaves 6362 minterms\nFrom[59]: 65 nodes 1 leaves 100 minterms\nReached[59]: 176 nodes 1 leaves 6462 minterms\nFrom[60]: 61 nodes 1 leaves 96 minterms\nReached[60]: 168 nodes 1 leaves 6558 minterms\nFrom[61]: 63 nodes 1 leaves 92 minterms\nReached[61]: 170 nodes 1 leaves 6650 minterms\nFrom[62]: 48 nodes 1 leaves 80 minterms\nReached[62]: 171 nodes 1 leaves 6730 minterms\nFrom[63]: 51 nodes 1 leaves 76 minterms\nReached[63]: 168 nodes 1 leaves 6806 minterms\nFrom[64]: 47 nodes 1 leaves 72 minterms\nReached[64]: 165 nodes 1 leaves 6878 minterms\nFrom[65]: 64 nodes 1 leaves 63 minterms\nReached[65]: 160 nodes 1 leaves 6941 minterms\nFrom[66]: 52 nodes 1 leaves 64 minterms\nReached[66]: 163 nodes 1 leaves 7005 minterms\nFrom[67]: 54 nodes 1 leaves 60 minterms\nReached[67]: 163 nodes 1 leaves 7065 minterms\nFrom[68]: 46 nodes 1 leaves 56 minterms\nReached[68]: 156 nodes 1 leaves 7121 minterms\nFrom[69]: 49 nodes 1 leaves 52 minterms\nReached[69]: 148 nodes 1 leaves 7173 minterms\nFrom[70]: 34 nodes 1 leaves 48 minterms\nReached[70]: 147 nodes 1 leaves 7221 minterms\nFrom[71]: 37 nodes 1 leaves 48 minterms\nReached[71]: 150 nodes 1 leaves 7269 minterms\nFrom[72]: 36 nodes 1 leaves 48 minterms\nReached[72]: 151 nodes 1 leaves 7317 minterms\nFrom[73]: 39 nodes 1 leaves 48 minterms\nReached[73]: 149 nodes 1 leaves 7365 minterms\nFrom[74]: 36 nodes 1 leaves 48 minterms\nReached[74]: 146 nodes 1 leaves 7413 minterms\nFrom[75]: 37 nodes 1 leaves 40 minterms\nReached[75]: 153 nodes 1 leaves 7453 minterms\nFrom[76]: 38 nodes 1 leaves 48 minterms\nReached[76]: 154 nodes 1 leaves 7501 minterms\nFrom[77]: 40 nodes 1 leaves 48 minterms\nReached[77]: 156 nodes 1 leaves 7549 minterms\nFrom[78]: 36 nodes 1 leaves 48 minterms\nReached[78]: 150 nodes 1 leaves 7597 minterms\nFrom[79]: 35 nodes 1 leaves 48 minterms\nReached[79]: 148 nodes 1 leaves 7645 minterms\nFrom[80]: 34 nodes 1 leaves 48 minterms\nReached[80]: 147 nodes 1 leaves 7693 minterms\nFrom[81]: 38 nodes 1 leaves 48 minterms\nReached[81]: 151 nodes 1 leaves 7741 minterms\nFrom[82]: 37 nodes 1 leaves 48 minterms\nReached[82]: 152 nodes 1 leaves 7789 minterms\nFrom[83]: 40 nodes 1 leaves 48 minterms\nReached[83]: 150 nodes 1 leaves 7837 minterms\nFrom[84]: 37 nodes 1 leaves 48 minterms\nReached[84]: 147 nodes 1 leaves 7885 minterms\nFrom[85]: 38 nodes 1 leaves 40 minterms\nReached[85]: 154 nodes 1 leaves 7925 minterms\nFrom[86]: 40 nodes 1 leaves 48 minterms\nReached[86]: 156 nodes 1 leaves 7973 minterms\nFrom[87]: 42 nodes 1 leaves 48 minterms\nReached[87]: 158 nodes 1 leaves 8021 minterms\nFrom[88]: 38 nodes 1 leaves 48 minterms\nReached[88]: 151 nodes 1 leaves 8069 minterms\nFrom[89]: 36 nodes 1 leaves 48 minterms\nReached[89]: 148 nodes 1 leaves 8117 minterms\nFrom[90]: 34 nodes 1 leaves 48 minterms\nReached[90]: 147 nodes 1 leaves 8165 minterms\nFrom[91]: 37 nodes 1 leaves 48 minterms\nReached[91]: 150 nodes 1 leaves 8213 minterms\nFrom[92]: 36 nodes 1 leaves 48 minterms\nReached[92]: 151 nodes 1 leaves 8261 minterms\nFrom[93]: 39 nodes 1 leaves 48 minterms\nReached[93]: 149 nodes 1 leaves 8309 minterms\nFrom[94]: 36 nodes 1 leaves 48 minterms\nReached[94]: 146 nodes 1 leaves 8357 minterms\nFrom[95]: 37 nodes 1 leaves 40 minterms\nReached[95]: 153 nodes 1 leaves 8397 minterms\nFrom[96]: 38 nodes 1 leaves 48 minterms\nReached[96]: 154 nodes 1 leaves 8445 minterms\nFrom[97]: 40 nodes 1 leaves 48 minterms\nReached[97]: 156 nodes 1 leaves 8493 minterms\nFrom[98]: 36 nodes 1 leaves 48 minterms\nReached[98]: 150 nodes 1 leaves 8541 minterms\nFrom[99]: 35 nodes 1 leaves 48 minterms\nReached[99]: 148 nodes 1 leaves 8589 minterms\nFrom[100]: 34 nodes 1 leaves 48 minterms\nReached[100]: 147 nodes 1 leaves 8637 minterms\nFrom[101]: 36 nodes 1 leaves 44 minterms\nReached[101]: 148 nodes 1 leaves 8681 minterms\nFrom[102]: 35 nodes 1 leaves 40 minterms\nReached[102]: 143 nodes 1 leaves 8721 minterms\nFrom[103]: 36 nodes 1 leaves 36 minterms\nReached[103]: 139 nodes 1 leaves 8757 minterms\nFrom[104]: 34 nodes 1 leaves 32 minterms\nReached[104]: 134 nodes 1 leaves 8789 minterms\nFrom[105]: 38 nodes 1 leaves 24 minterms\nReached[105]: 134 nodes 1 leaves 8813 minterms\nFrom[106]: 34 nodes 1 leaves 20 minterms\nReached[106]: 131 nodes 1 leaves 8833 minterms\nFrom[107]: 35 nodes 1 leaves 16 minterms\nReached[107]: 128 nodes 1 leaves 8849 minterms\nFrom[108]: 32 nodes 1 leaves 12 minterms\nReached[108]: 117 nodes 1 leaves 8861 minterms\nFrom[109]: 19 nodes 1 leaves 8 minterms\nReached[109]: 107 nodes 1 leaves 8869 minterms\nS0: 22 nodes 1 leaves 1 minterms\nSCC[9]: 22 nodes 1 leaves 1 minterms\nMore than 10 SCCs. Only the first 10 are computed.\n@@@@@@@@@@@@@@@@@@@@@\nTerminating after 151 iterations\nDistance Matrix: 1194 nodes 152 leaves 8865 minterms\nOrder after short path computation\nFM TEST CLR TESTL FML OLATCH_Y2L OLATCHVUC_6 OLATCHVUC_5 \nOLATCH_R1L OLATCH_G2L OLATCH_G1L OLATCH_FEL C3_Q3 C3_Q2 C3_Q1 C3_Q0 \nUC_16 UC_17 UC_18 UC_19 UC_8 UC_9 UC_10 UC_11 \n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: yes\nDefault BDD reordering method: 4\nDynamic reordering of ZDDs enabled: no\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: no\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 4004\n**** CUDD non-modifiable parameters ****\nMemory in use: 11285152\nPeak number of nodes: 134904\nPeak number of live nodes: 3927\nNumber of BDD variables: 87\nNumber of ZDD variables: 0\nNumber of cache entries: 131072\nNumber of cache look-ups: 1261573\nNumber of cache hits: 372031\nNumber of cache insertions: 920113\nNumber of cache collisions: 467699\nNumber of cache deletions: 344369\nCache used slots = 94.64% (expected 94.56%)\nSoft limit for cache size: 332800\nNumber of buckets in unique table: 83200\nUsed buckets in unique table: 64.41% (expected 64.12%)\nNumber of BDD and ADD nodes: 129608\nNumber of ZDD nodes: 0\nNumber of dead BDD and ADD nodes: 129343\nNumber of dead ZDD nodes: 0\nTotal number of nodes allocated: 1105700\nTotal number of nodes reclaimed: 687182\nGarbage collections so far: 10\nTime for garbage collection: 0.03 sec\nReorderings so far: 0\nTime for reordering: 0.00 sec\nFinal size: 168\ntotal time = 0.29 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.3 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            = 14644K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 2956\nSwaps = 0\nInput blocks = 16\nOutput blocks = 248\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/s641.blif",
    "content": ".model s641.bench\n.inputs G1 G2 G3 G4 G5 G6 G8 G9 G10 G11 G12 G13 G14 G15 G16 G17 G18 G19 G20 G21 G22 G23 G24 G25 G26 G27 G28 G29 G30 G31 G32 G33 G34 G35 G36\n.outputs G91 G94 G107 G83 G84 G85 G100BF G98BF G96BF G92 G87BF G89BF G101BF G106BF G97BF G104BF G88BF G99BF G105BF G86BF G95BF G103BF G90\n.latch     G380 G64  0\n.latch     G262 G65  0\n.latch     G394 G66  0\n.latch     G250 G67  0\n.latch     G122 G68  0\n.latch     G133 G69  0\n.latch     G138 G70  0\n.latch     G139 G71  0\n.latch     G140 G72  0\n.latch     G141 G73  0\n.latch     G142 G74  0\n.latch     G125 G75  0\n.latch     G126 G76  0\n.latch     G127 G77  0\n.latch     G128 G78  0\n.latch     G129 G79  0\n.latch     G130 G80  0\n.latch     G131 G81  0\n.latch     G132 G82  0\n.names II165 G91\n0 1\n.names IIII178 G94\n0 1\n.names G313 G18 G107\n11 1\n.names G316 G19 G83\n11 1\n.names G319 G20 G84\n11 1\n.names G322 G21 G85\n11 1\n.names G100 G100BF\n0 1\n.names G98 G98BF\n0 1\n.names G96 G96BF\n0 1\n.names G350 G28 G92\n11 1\n.names G87 G87BF\n0 1\n.names G89 G89BF\n0 1\n.names G101 G101BF\n0 1\n.names G106 G106BF\n0 1\n.names G97 G97BF\n0 1\n.names G104 G104BF\n0 1\n.names G88 G88BF\n0 1\n.names G99 G99BF\n0 1\n.names G105 G105BF\n0 1\n.names IIII322 G138\n0 1\n.names G86 G86BF\n0 1\n.names G95 G95BF\n0 1\n.names G103 G103BF\n0 1\n.names G298 G26 G90\n11 1\n.names II551 G380\n0 1\n.names G366 G392 G395 G397 G262\n1111 1\n.names II476 G394\n0 1\n.names G366 G396 G250\n11 1\n.names IIII210 G122\n0 1\n.names IIII287 G133\n0 1\n.names IIII329 G139\n0 1\n.names IIII336 G140\n0 1\n.names IIII343 G141\n0 1\n.names IIII350 G142\n0 1\n.names IIII230 G125\n0 1\n.names IIII237 G126\n0 1\n.names IIII244 G127\n0 1\n.names IIII251 G128\n0 1\n.names IIII258 G129\n0 1\n.names IIII265 G130\n0 1\n.names IIII272 G131\n0 1\n.names IIII279 G132\n0 1\n.names G1 IIII633\n0 1\n.names G2 G366\n0 1\n.names G3 G379\n0 1\n.names G4 IIII643\n0 1\n.names G5 IIII646\n0 1\n.names G6 IIII649\n0 1\n.names G8 IIII652\n0 1\n.names G9 IIII655\n0 1\n.names G10 IIII660\n0 1\n.names G11 IIII680\n0 1\n.names G12 IIII684\n0 1\n.names G13 IIII687\n0 1\n.names G27 II165\n0 1\n.names G29 IIII178\n0 1\n.names G70 II169\n0 1\n.names G71 II172\n0 1\n.names G72 II175\n0 1\n.names G80 II178\n0 1\n.names G73 II181\n0 1\n.names G81 II184\n0 1\n.names G74 II187\n0 1\n.names G82 II190\n0 1\n.names G75 II193\n0 1\n.names G68 II196\n0 1\n.names G76 II199\n0 1\n.names G69 II202\n0 1\n.names G77 II205\n0 1\n.names G78 II208\n0 1\n.names G79 II211\n0 1\n.names IIII633 G352\n0 1\n.names IIII643 G360\n0 1\n.names IIII646 G361\n0 1\n.names IIII649 G362\n0 1\n.names IIII652 G363\n0 1\n.names IIII655 G364\n0 1\n.names IIII660 G367\n0 1\n.names IIII680 G386\n0 1\n.names IIII684 G388\n0 1\n.names IIII687 G389\n0 1\n.names II169 G113\n0 1\n.names II172 G115\n0 1\n.names II175 G117\n0 1\n.names II178 G219\n0 1\n.names II181 G119\n0 1\n.names II184 G221\n0 1\n.names II187 G121\n0 1\n.names II190 G223\n0 1\n.names II193 G209\n0 1\n.names II196 G109\n0 1\n.names II199 G211\n0 1\n.names II202 G111\n0 1\n.names II205 G213\n0 1\n.names II208 G215\n0 1\n.names II211 G217\n0 1\n.names G360 G110\n0 1\n.names G360 G114\n0 1\n.names G360 G118\n0 1\n.names G360 G216\n0 1\n.names G360 G218\n0 1\n.names G360 G220\n0 1\n.names G360 G222\n0 1\n.names G364 G365\n0 1\n.names G367 G368\n0 1\n.names G386 G387\n0 1\n.names G388 G225\n0 1\n.names G389 G390\n0 1\n.names G386 G388 G389 G289\n111 1\n.names G289 IIII356\n0 1\n.names G110 G111 G324\n11 1\n.names G324 II254\n0 1\n.names G324 II257\n0 1\n.names G114 G115 G338\n11 1\n.names G338 II260\n0 1\n.names G338 II263\n0 1\n.names G118 G119 G344\n11 1\n.names G344 II266\n0 1\n.names G344 II269\n0 1\n.names G216 G217 G312\n11 1\n.names G312 II272\n0 1\n.names G218 G219 G315\n11 1\n.names G315 II275\n0 1\n.names G220 G221 G318\n11 1\n.names G318 II278\n0 1\n.names G222 G223 G321\n11 1\n.names G321 II281\n0 1\n.names IIII356 G143\n0 1\n.names II254 G166\n0 1\n.names II257 G325\n0 1\n.names II260 G194\n0 1\n.names II263 G339\n0 1\n.names II266 G202\n0 1\n.names II269 G345\n0 1\n.names II272 G313\n0 1\n.names II275 G316\n0 1\n.names II278 G319\n0 1\n.names II281 G322\n0 1\n.names G143 II303\n0 1\n.names G232 G248 G65 G281\n1-- 1\n-1- 1\n--1 1\n.names G281 IIII299\n0 1\n.names G234 G67 G264 G283\n1-- 1\n-1- 1\n--1 1\n.names G283 IIII313\n0 1\n.names G166 II287\n0 1\n.names G194 II291\n0 1\n.names G202 II295\n0 1\n.names II303 G350\n0 1\n.names IIII299 IIII301\n0 1\n.names IIII313 IIII315\n0 1\n.names II287 G381\n0 1\n.names G325 G35 G100\n11 1\n.names II291 G375\n0 1\n.names G339 G33 G98\n11 1\n.names II295 G371\n0 1\n.names G345 G31 G96\n11 1\n.names IIII301 G135\n0 1\n.names IIII315 G137\n0 1\n.names G381 G382\n0 1\n.names G375 G376\n0 1\n.names G371 G372\n0 1\n.names G135 II321\n0 1\n.names G137 II324\n0 1\n.names II321 G329\n0 1\n.names II324 G333\n0 1\n.names G329 G23 G87\n11 1\n.names G87 IIII406\n0 1\n.names G333 G25 G89\n11 1\n.names G89 IIII422\n0 1\n.names IIII406 G173\n0 1\n.names IIII422 G183\n0 1\n.names G173 II335\n0 1\n.names G183 II338\n0 1\n.names II335 G174\n0 1\n.names II338 G184\n0 1\n.names G174 II341\n0 1\n.names G184 G359\n0 1\n.names II341 G355\n0 1\n.names G359 G108\n0 1\n.names G355 G356\n0 1\n.names G356 G116\n0 1\n.names G108 G109 G293\n11 1\n.names G293 II354\n0 1\n.names G293 II357\n0 1\n.names G214 G215 G309\n11 1\n.names G309 II360\n0 1\n.names G309 II363\n0 1\n.names II354 G146\n0 1\n.names II357 G294\n0 1\n.names II360 G162\n0 1\n.names II363 G310\n0 1\n.names G116 G117 G341\n11 1\n.names G341 II366\n0 1\n.names G341 II369\n0 1\n.names G210 G211 G303\n11 1\n.names G303 II372\n0 1\n.names G303 II375\n0 1\n.names G146 II378\n0 1\n.names G162 II382\n0 1\n.names II366 G198\n0 1\n.names II369 G342\n0 1\n.names II372 G154\n0 1\n.names II375 G304\n0 1\n.names II378 G383\n0 1\n.names G294 G36 G101\n11 1\n.names II382 G396\n0 1\n.names G310 G17 G106\n11 1\n.names G198 II386\n0 1\n.names G154 II390\n0 1\n.names G383 G384\n0 1\n.names G396 G397\n0 1\n.names II386 G373\n0 1\n.names G342 G32 G97\n11 1\n.names II390 G392\n0 1\n.names G304 G15 G104\n11 1\n.names G384 IIII476\n0 1\n.names G366 G396 G278\n11 1\n.names G278 IIII279\n0 1\n.names G373 G374\n0 1\n.names G392 G393\n0 1\n.names IIII476 G224\n0 1\n.names G233 G249 G263 G282\n1-- 1\n-1- 1\n--1 1\n.names G282 IIII306\n0 1\n.names G374 G375 G237\n11 1\n.names G237 II373\n0 1\n.names II373 G286\n0 1\n.names G224 IIII208\n0 1\n.names IIII306 IIII308\n0 1\n.names G286 IIII334\n0 1\n.names G236 G252 G285\n1- 1\n-1 1\n.names G285 IIII327\n0 1\n.names IIII208 IIII210\n0 1\n.names IIII308 G136\n0 1\n.names IIII334 IIII336\n0 1\n.names IIII327 IIII329\n0 1\n.names G136 II442\n0 1\n.names II442 G331\n0 1\n.names G331 G24 G88\n11 1\n.names G88 IIII414\n0 1\n.names IIII414 G178\n0 1\n.names G178 II449\n0 1\n.names II449 G179\n0 1\n.names G179 II452\n0 1\n.names II452 G357\n0 1\n.names G357 G358\n0 1\n.names G358 G112\n0 1\n.names G112 G113 G335\n11 1\n.names G335 II460\n0 1\n.names G335 II463\n0 1\n.names G212 G213 G306\n11 1\n.names G306 II466\n0 1\n.names G306 II469\n0 1\n.names II460 G190\n0 1\n.names II463 G336\n0 1\n.names II466 G158\n0 1\n.names II469 G307\n0 1\n.names G190 II472\n0 1\n.names G158 II476\n0 1\n.names G158 G395\n0 1\n.names II472 G377\n0 1\n.names G336 G34 G99\n11 1\n.names G366 G158 G397 G277\n111 1\n.names G277 IIII272\n0 1\n.names G307 G16 G105\n11 1\n.names G377 G378\n0 1\n.names G366 G392 G395 G397 G276\n1111 1\n.names G276 IIII265\n0 1\n.names G231 G247 G261 G280\n1-- 1\n-1- 1\n--1 1\n.names G280 IIII292\n0 1\n.names G378 G381 G235\n11 1\n.names G235 II440\n0 1\n.names II440 G284\n0 1\n.names IIII292 IIII294\n0 1\n.names G284 IIII320\n0 1\n.names G230 G246 G279\n1- 1\n-1 1\n.names G279 IIII285\n0 1\n.names IIII294 G134\n0 1\n.names IIII320 IIII322\n0 1\n.names IIII285 IIII287\n0 1\n.names G134 II517\n0 1\n.names II517 G327\n0 1\n.names G327 G22 G86\n11 1\n.names G86 IIII398\n0 1\n.names IIII398 G168\n0 1\n.names G168 II524\n0 1\n.names II524 G169\n0 1\n.names G169 II527\n0 1\n.names II527 G353\n0 1\n.names G353 G354\n0 1\n.names G354 G120\n0 1\n.names G120 G121 G347\n11 1\n.names G347 II535\n0 1\n.names G347 II538\n0 1\n.names G208 G209 G300\n11 1\n.names G300 II541\n0 1\n.names G300 II544\n0 1\n.names II535 G206\n0 1\n.names II538 G348\n0 1\n.names II541 G150\n0 1\n.names II544 G301\n0 1\n.names G206 II547\n0 1\n.names G150 II551\n0 1\n.names G150 G391\n0 1\n.names II547 G369\n0 1\n.names G348 G30 G95\n11 1\n.names G301 G14 G103\n11 1\n.names G369 G370\n0 1\n.names G395 G397 IIII553 G275\n111 1\n.names G275 IIII258\n0 1\n.names G226 G242 G257 G271\n1-- 1\n-1- 1\n--1 1\n.names G271 IIII230\n0 1\n.names G370 G371 G239\n11 1\n.names G239 II511\n0 1\n.names II511 G288\n0 1\n.names G227 G243 G258 G272\n1-- 1\n-1- 1\n--1 1\n.names G272 IIII237\n0 1\n.names G228 G244 G259 G273\n1-- 1\n-1- 1\n--1 1\n.names G273 IIII244\n0 1\n.names G229 G245 G260 G274\n1-- 1\n-1- 1\n--1 1\n.names G274 IIII251\n0 1\n.names G288 IIII348\n0 1\n.names G238 G254 G287\n1- 1\n-1 1\n.names G287 IIII341\n0 1\n.names G265 G266 G267 IIII546 G270\n1--- 1\n-1-- 1\n--1- 1\n---1 1\n.names G270 IIII222\n0 1\n.names IIII348 IIII350\n0 1\n.names IIII341 IIII343\n0 1\n.names IIII222 IIII224\n0 1\n.names IIII224 G124\n0 1\n.names G124 II608\n0 1\n.names II608 G298\n0 1\n.names G379 G387 G231\n11 1\n.names G379 G387 G232\n11 1\n.names G379 G387 G233\n11 1\n.names G379 G387 G234\n11 1\n.names G379 G365 G368 G390 G247\n1111 1\n.names G379 G365 G367 G390 G248\n1111 1\n.names G379 G364 G368 G390 G263\n1111 1\n.names G379 G364 G367 G390 G264\n1111 1\n.names G379 G359 G214\n0- 1\n-0 1\n.names G379 G356 G210\n0- 1\n-0 1\n.names G364 G367 G383 G390 G266\n1111 1\n.names G366 G396 G229\n11 1\n.names G352 G396 G245\n11 1\n.names G366 G66 G397 G249\n111 1\n.names G365 G367 G373 IIII533\n111 1\n.names G366 G392 G227\n11 1\n.names G392 G361 G243\n11 1\n.names G375 G390 IIII533 G265\n111 1\n.names G374 G376 G236\n11 1\n.names G355 G374 G252\n11 1\n.names G366 G64 G393 IIII527\n111 1\n.names G379 G358 G212\n0- 1\n-0 1\n.names G366 G158 G228\n11 1\n.names G158 G362 G244\n11 1\n.names G393 G395 G397 IIII515\n111 1\n.names G395 G397 IIII527 G261\n111 1\n.names G364 G368 G377 IIII512\n111 1\n.names G377 G381 G383 G387 IIII538\n1111 1\n.names G381 G390 IIII512 G256\n111 1\n.names G378 G382 G230\n11 1\n.names G357 G378 G246\n11 1\n.names G379 G354 G208\n0- 1\n-0 1\n.names G366 G150 G226\n11 1\n.names G150 G363 G242\n11 1\n.names G366 G150 G393 IIII553\n111 1\n.names G391 G395 G397 IIII518\n111 1\n.names G391 G393 G397 IIII521\n111 1\n.names G352 G391 G393 IIII524\n111 1\n.names G365 G368 G369 IIII495\n111 1\n.names G363 G369 G371 IIII515 G257\n1111 1\n.names G369 G371 G373 G375 IIII537\n1111 1\n.names G361 G373 G375 IIII518 G258\n1111 1\n.names G362 G377 G381 IIII521 G259\n1111 1\n.names G395 G383 IIII524 G260\n111 1\n.names G371 G390 IIII495 G241\n111 1\n.names IIII537 IIII538 G267\n11 1\n.names G370 G372 G238\n11 1\n.names G353 G370 G254\n11 1\n.names G225 G241 G256 IIII546\n1-- 1\n-1- 1\n--1 1\n.end\n"
  },
  {
    "path": "cudd/nanotrav/s641.out",
    "content": "# Nanotrav Version #0.13, Release date 2015/7/15\n# nanotrav/nanotrav -p 1 -trav -autodyn -automethod group -drop -clauses -density -decomp -zdd ./nanotrav/s641.blif\n# CUDD Version 3.0.0\nOrder before final reordering\nG1 G2 G3 G4 G5 G6 G8 G9 \nG10 G11 G12 G13 G14 G15 G16 G17 \nG18 G19 G20 G21 G22 G23 G24 G25 \nG26 G27 G28 G29 G30 G31 G32 G33 \nG34 G35 G36 G64 G65 G66 G67 G68 \nG69 G70 G71 G72 G73 G74 G75 G76 \nG77 G78 G79 G80 G81 G82 \nBuilding transition relation. Time = 0.00 sec\n@@@@@BDD reordering with group sifting: from 3979 to ... 1316 nodes in 0.01 sec\n@@BDD reordering with group sifting: from 2656 to ... 1332 nodes in 0.01 sec\n@@BDD reordering with group sifting: from 2687 to ... 1855 nodes in 0.02 sec\n@@@BDD reordering with group sifting: from 3708 to ... 2468 nodes in 0.01 sec\n@@@@BDD reordering with group sifting: from 4224 to ... 2505 nodes in 0.02 sec\n@@@\nTransition relation: 1 parts 19 latches 721 nodes\nTraversing. Time = 0.08 sec\nS0: 20 nodes 1 leaves 1 minterms\nFrom[1]: 20 nodes 1 leaves 1 minterms\nReached[1]: 25 nodes 1 leaves 2 minterms\n2\n2\nFrom[2]: 23 nodes 1 leaves 7 minterms\nReached[2]: 23 nodes 1 leaves 9 minterms\n9\n9\nFrom[3]: 45 nodes 1 leaves 56 minterms\nReached[3]: 48 nodes 1 leaves 65 minterms\n65\n65\nFrom[4]: 134 nodes 1 leaves 649 minterms\nReached[4]: 111 nodes 1 leaves 714 minterms\n714\n714\nFrom[5]: 163 nodes 1 leaves 560 minterms\nReached[5]: 153 nodes 1 leaves 1274 minterms\n1274\n1274\nFrom[6]: 110 nodes 1 leaves 270 minterms\nReached[6]: 87 nodes 1 leaves 1544 minterms\n1544\n1544\ndepth = 6\nR: 87 nodes 1 leaves 1544 minterms\nOrder at the end of reachability analysis\nG81 G31 G79 G82 G32 G34 G17 G20 \nG26 G15 G30 G36 G14 G28 G12 G16 \nG1 G3 G11 G5 G25 G67 G6 G13 \nG9 G10 G68 G78 G2 G66 G64 G76 \nG8 G75 G24 G77 G74 G73 G23 G65 \nG72 G33 G71 G70 G35 G69 G4 G22 \nG80 G27 G19 G29 G21 G18 \nTesting extraction of two literal clauses\n*** G91 ***\n G27\n*** G94 ***\n G29\n*** G107 ***\n G18\n~G4\n G79\n*** G83 ***\n G19\n G80\n~G4\n*** G84 ***\n~G4\n G20\n G81\n*** G85 ***\n G21\n~G4\n G82\n*** G100BF ***\n*** G98BF ***\n*** G96BF ***\n*** G92 ***\n G13\n G11\n G12\n G28\n*** G87BF ***\n*** G89BF ***\n*** G101BF ***\n*** G106BF ***\n*** G97BF ***\n*** G104BF ***\n*** G88BF ***\n*** G99BF ***\n*** G105BF ***\n*** G86BF ***\n*** G95BF ***\n*** G103BF ***\n*** G90 ***\n G12\n G26\n*** G380 ***\n G22 |  G75\n G11 |  G75\n G3 |  G22\n G3 |  G11\n~G3 |  G75\n~G2 |  G75\n*** G262 ***\n~G65 | ~G77\n~G65 |  G76\n~G65 | ~G78\n G23 | ~G77\n G23 |  G76\n G23 | ~G78\n G76 | ~G77\n G76 | ~G78\n G11 | ~G77\n G11 |  G76\n G11 | ~G78\n G3 | ~G65\n G3 |  G23\n G3 |  G76\n G3 |  G11\n~G3 | ~G77\n~G3 |  G76\n~G3 | ~G78\n~G2\n*** G394 ***\n G77\n G3 |  G24\n G3 |  G11\n*** G250 ***\n~G2\n G78\n G3 | ~G67\n G3 |  G25\n G3 |  G11\n*** G122 ***\n G68\n~G67\n G25\n G3 |  G11\n*** G133 ***\n~G4 |  G70\n G69 |  G70\n G24 | ~G4\n G24 |  G69\n*** G138 ***\n*** G139 ***\n~G4 |  G72\n G71 |  G72\n~G65 | ~G4\n~G65 |  G71\n G23 | ~G4\n G23 |  G71\n*** G140 ***\n*** G141 ***\n~G4 |  G74\n G73 |  G74\n~G4 |  G22\n*** G142 ***\n*** G125 ***\n G3 |  G11\n~G2 |  G8\n*** G126 ***\n G3 |  G11\n~G2 |  G5\n*** G127 ***\n~G4 |  G77\n G69 |  G77\n G70 |  G77\n G6 |  G77\n G3 |  G11\n~G2 |  G6\n*** G128 ***\n G1 | ~G2\n G1 |  G78\n*** G129 ***\n G22 | ~G77\n G22 |  G75\n G22 | ~G76\n G22 | ~G78\n G75 | ~G77\n G75 | ~G76\n G75 | ~G78\n~G64 | ~G77\n~G64 |  G75\n~G64 | ~G76\n~G64 | ~G78\n G11 | ~G77\n G11 |  G75\n G11 | ~G76\n G11 | ~G78\n G3 |  G22\n G3 |  G75\n G3 | ~G64\n G3 |  G11\n~G3 | ~G77\n~G3 |  G75\n~G3 | ~G76\n~G3 | ~G78\n~G2\n*** G130 ***\n~G65 | ~G77\n~G65 |  G76\n~G65 | ~G78\n G23 | ~G77\n G23 |  G76\n G23 | ~G78\n G76 | ~G77\n G76 | ~G78\n G11 | ~G77\n G11 |  G76\n G11 | ~G78\n G3 | ~G65\n G3 |  G23\n G3 |  G76\n G3 |  G11\n~G3 | ~G77\n~G3 |  G76\n~G3 | ~G78\n~G2\n*** G131 ***\n G77\n G24 | ~G78\n~G66 | ~G78\n G11 | ~G78\n G3 |  G24\n G3 | ~G66\n G3 |  G11\n~G3 | ~G78\n~G2\n*** G132 ***\n~G2\n G78\n G3 | ~G67\n G3 |  G25\n G3 |  G11\nTesting BDD density-related algorithms\nTEST-DENSITY:: G91 (1 variables)\nT-D    (0.5): 2 nodes 1 leaves 1 minterms\nT-D APA 1\nT-D ID (0.5): 2 nodes 1 leaves 1 minterms\nT-D BU (0.5): 2 nodes 1 leaves 1 minterms\nT-D HB (0.5): 2 nodes 1 leaves 1 minterms\nT-D SP (0.5): 2 nodes 1 leaves 1 minterms\nT-D UA (0.5): 2 nodes 1 leaves 1 minterms\nT-D C1 (0.5): 2 nodes 1 leaves 1 minterms\nT-D C2 (0.5): 2 nodes 1 leaves 1 minterms\nTEST-DENSITY:: G94 (1 variables)\nT-D    (0.5): 2 nodes 1 leaves 1 minterms\nT-D APA 1\nT-D ID (0.5): 2 nodes 1 leaves 1 minterms\nT-D BU (0.5): 2 nodes 1 leaves 1 minterms\nT-D HB (0.5): 2 nodes 1 leaves 1 minterms\nT-D SP (0.5): 2 nodes 1 leaves 1 minterms\nT-D UA (0.5): 2 nodes 1 leaves 1 minterms\nT-D C1 (0.5): 2 nodes 1 leaves 1 minterms\nT-D C2 (0.5): 2 nodes 1 leaves 1 minterms\nTEST-DENSITY:: G107 (3 variables)\nT-D    (0.25): 4 nodes 1 leaves 1 minterms\nT-D APA 1\nT-D ID (0.25): 4 nodes 1 leaves 1 minterms\nT-D BU (0.25): 4 nodes 1 leaves 1 minterms\nT-D HB (0.25): 4 nodes 1 leaves 1 minterms\nT-D SP (0.25): 4 nodes 1 leaves 1 minterms\nT-D UA (0.25): 4 nodes 1 leaves 1 minterms\nT-D C1 (0.25): 4 nodes 1 leaves 1 minterms\nT-D C2 (0.25): 4 nodes 1 leaves 1 minterms\nTEST-DENSITY:: G83 (3 variables)\nT-D    (0.25): 4 nodes 1 leaves 1 minterms\nT-D APA 1\nT-D ID (0.25): 4 nodes 1 leaves 1 minterms\nT-D BU (0.25): 4 nodes 1 leaves 1 minterms\nT-D HB (0.25): 4 nodes 1 leaves 1 minterms\nT-D SP (0.25): 4 nodes 1 leaves 1 minterms\nT-D UA (0.25): 4 nodes 1 leaves 1 minterms\nT-D C1 (0.25): 4 nodes 1 leaves 1 minterms\nT-D C2 (0.25): 4 nodes 1 leaves 1 minterms\nTEST-DENSITY:: G84 (3 variables)\nT-D    (0.25): 4 nodes 1 leaves 1 minterms\nT-D APA 1\nT-D ID (0.25): 4 nodes 1 leaves 1 minterms\nT-D BU (0.25): 4 nodes 1 leaves 1 minterms\nT-D HB (0.25): 4 nodes 1 leaves 1 minterms\nT-D SP (0.25): 4 nodes 1 leaves 1 minterms\nT-D UA (0.25): 4 nodes 1 leaves 1 minterms\nT-D C1 (0.25): 4 nodes 1 leaves 1 minterms\nT-D C2 (0.25): 4 nodes 1 leaves 1 minterms\nTEST-DENSITY:: G85 (3 variables)\nT-D    (0.25): 4 nodes 1 leaves 1 minterms\nT-D APA 1\nT-D ID (0.25): 4 nodes 1 leaves 1 minterms\nT-D BU (0.25): 4 nodes 1 leaves 1 minterms\nT-D HB (0.25): 4 nodes 1 leaves 1 minterms\nT-D SP (0.25): 4 nodes 1 leaves 1 minterms\nT-D UA (0.25): 4 nodes 1 leaves 1 minterms\nT-D C1 (0.25): 4 nodes 1 leaves 1 minterms\nT-D C2 (0.25): 4 nodes 1 leaves 1 minterms\nTEST-DENSITY:: G100BF (3 variables)\nT-D    (1.75): 4 nodes 1 leaves 7 minterms\nT-D APA 7\nT-D ID (2): 3 nodes 1 leaves 6 minterms\nT-D BU (2): 3 nodes 1 leaves 6 minterms\nT-D HB (1.75): 4 nodes 1 leaves 7 minterms\nT-D SP (1.75): 4 nodes 1 leaves 7 minterms\nT-D UA (2): 2 nodes 1 leaves 4 minterms\nT-D C1 (2): 3 nodes 1 leaves 6 minterms\nT-D C2 (2): 2 nodes 1 leaves 4 minterms\nTEST-DENSITY:: G98BF (3 variables)\nT-D    (1.75): 4 nodes 1 leaves 7 minterms\nT-D APA 7\nT-D ID (2): 3 nodes 1 leaves 6 minterms\nT-D BU (2): 3 nodes 1 leaves 6 minterms\nT-D HB (1.75): 4 nodes 1 leaves 7 minterms\nT-D SP (1.75): 4 nodes 1 leaves 7 minterms\nT-D UA (2): 2 nodes 1 leaves 4 minterms\nT-D C1 (2): 3 nodes 1 leaves 6 minterms\nT-D C2 (2): 2 nodes 1 leaves 4 minterms\nTEST-DENSITY:: G96BF (3 variables)\nT-D    (1.75): 4 nodes 1 leaves 7 minterms\nT-D APA 7\nT-D ID (2): 3 nodes 1 leaves 6 minterms\nT-D BU (2): 3 nodes 1 leaves 6 minterms\nT-D HB (1.75): 4 nodes 1 leaves 7 minterms\nT-D SP (1.75): 4 nodes 1 leaves 7 minterms\nT-D UA (2): 2 nodes 1 leaves 4 minterms\nT-D C1 (2): 3 nodes 1 leaves 6 minterms\nT-D C2 (2): 2 nodes 1 leaves 4 minterms\nTEST-DENSITY:: G92 (4 variables)\nT-D    (0.2): 5 nodes 1 leaves 1 minterms\nT-D APA 1\nT-D ID (0.2): 5 nodes 1 leaves 1 minterms\nT-D BU (0.2): 5 nodes 1 leaves 1 minterms\nT-D HB (0.2): 5 nodes 1 leaves 1 minterms\nT-D SP (0.2): 5 nodes 1 leaves 1 minterms\nT-D UA (0.2): 5 nodes 1 leaves 1 minterms\nT-D C1 (0.2): 5 nodes 1 leaves 1 minterms\nT-D C2 (0.2): 5 nodes 1 leaves 1 minterms\nTEST-DENSITY:: G87BF (7 variables)\nT-D    (13.125): 8 nodes 1 leaves 105 minterms\nT-D APA 105\nT-D ID (32): 3 nodes 1 leaves 96 minterms\nT-D BU (32): 3 nodes 1 leaves 96 minterms\nT-D HB (10.6667): 3 nodes 1 leaves 32 minterms\nT-D SP (16): 4 nodes 1 leaves 64 minterms\nT-D UA (16): 5 nodes 1 leaves 80 minterms\nT-D C1 (32): 3 nodes 1 leaves 96 minterms\nT-D C2 (16): 4 nodes 1 leaves 64 minterms\nTEST-DENSITY:: G89BF (7 variables)\nT-D    (10.5): 10 nodes 1 leaves 105 minterms\nT-D APA 105\nT-D ID (32): 3 nodes 1 leaves 96 minterms\nT-D BU (32): 3 nodes 1 leaves 96 minterms\nT-D HB (10.6667): 3 nodes 1 leaves 32 minterms\nT-D SP (16): 4 nodes 1 leaves 64 minterms\nT-D UA (12): 4 nodes 1 leaves 48 minterms\nT-D C1 (32): 3 nodes 1 leaves 96 minterms\nT-D C2 (16): 4 nodes 1 leaves 64 minterms\nTEST-DENSITY:: G101BF (9 variables)\nT-D    (40.75): 12 nodes 1 leaves 489 minterms\nT-D APA 489\nT-D ID (128): 3 nodes 1 leaves 384 minterms\nT-D BU (128): 3 nodes 1 leaves 384 minterms\nT-D HB (128): 2 nodes 1 leaves 256 minterms\nT-D SP (80): 4 nodes 1 leaves 320 minterms\nT-D UA (128): 2 nodes 1 leaves 256 minterms\nT-D C1 (128): 3 nodes 1 leaves 384 minterms\nT-D C2 (128): 2 nodes 1 leaves 256 minterms\nTEST-DENSITY:: G106BF (9 variables)\nT-D    (44.1): 10 nodes 1 leaves 441 minterms\nT-D APA 441\nT-D ID (128): 3 nodes 1 leaves 384 minterms\nT-D BU (128): 3 nodes 1 leaves 384 minterms\nT-D HB (128): 2 nodes 1 leaves 256 minterms\nT-D SP (80): 4 nodes 1 leaves 320 minterms\nT-D UA (128): 2 nodes 1 leaves 256 minterms\nT-D C1 (128): 3 nodes 1 leaves 384 minterms\nT-D C2 (128): 2 nodes 1 leaves 256 minterms\nTEST-DENSITY:: G97BF (9 variables)\nT-D    (48.9): 10 nodes 1 leaves 489 minterms\nT-D APA 489\nT-D ID (128): 3 nodes 1 leaves 384 minterms\nT-D BU (128): 3 nodes 1 leaves 384 minterms\nT-D HB (128): 2 nodes 1 leaves 256 minterms\nT-D SP (80): 4 nodes 1 leaves 320 minterms\nT-D UA (128): 2 nodes 1 leaves 256 minterms\nT-D C1 (128): 3 nodes 1 leaves 384 minterms\nT-D C2 (128): 2 nodes 1 leaves 256 minterms\nTEST-DENSITY:: G104BF (9 variables)\nT-D    (40.0909): 11 nodes 1 leaves 441 minterms\nT-D APA 441\nT-D ID (128): 3 nodes 1 leaves 384 minterms\nT-D BU (128): 3 nodes 1 leaves 384 minterms\nT-D HB (128): 2 nodes 1 leaves 256 minterms\nT-D SP (80): 4 nodes 1 leaves 320 minterms\nT-D UA (128): 2 nodes 1 leaves 256 minterms\nT-D C1 (128): 3 nodes 1 leaves 384 minterms\nT-D C2 (128): 2 nodes 1 leaves 256 minterms\nTEST-DENSITY:: G88BF (11 variables)\nT-D    (101.857): 14 nodes 1 leaves 1426 minterms\nT-D APA 1426\nT-D ID (512): 2 nodes 1 leaves 1024 minterms\nT-D BU (512): 2 nodes 1 leaves 1024 minterms\nT-D HB (170.667): 3 nodes 1 leaves 512 minterms\nT-D SP (170.667): 3 nodes 1 leaves 512 minterms\nT-D UA (170.667): 3 nodes 1 leaves 512 minterms\nT-D C1 (512): 2 nodes 1 leaves 1024 minterms\nT-D C2 (170.667): 3 nodes 1 leaves 512 minterms\nTEST-DENSITY:: G99BF (13 variables)\nT-D    (473.125): 16 nodes 1 leaves 7570 minterms\nT-D APA 7570\nT-D ID (2048): 3 nodes 1 leaves 6144 minterms\nT-D BU (2048): 3 nodes 1 leaves 6144 minterms\nT-D HB (2048): 2 nodes 1 leaves 4096 minterms\nT-D SP (1280): 4 nodes 1 leaves 5120 minterms\nT-D UA (2048): 2 nodes 1 leaves 4096 minterms\nT-D C1 (2048): 3 nodes 1 leaves 6144 minterms\nT-D C2 (2048): 2 nodes 1 leaves 4096 minterms\nTEST-DENSITY:: G105BF (13 variables)\nT-D    (437.125): 16 nodes 1 leaves 6994 minterms\nT-D APA 6994\nT-D ID (2048): 3 nodes 1 leaves 6144 minterms\nT-D BU (2048): 3 nodes 1 leaves 6144 minterms\nT-D HB (2048): 2 nodes 1 leaves 4096 minterms\nT-D SP (1280): 4 nodes 1 leaves 5120 minterms\nT-D UA (2048): 2 nodes 1 leaves 4096 minterms\nT-D C1 (2048): 3 nodes 1 leaves 6144 minterms\nT-D C2 (2048): 2 nodes 1 leaves 4096 minterms\nTEST-DENSITY:: G86BF (17 variables)\nT-D    (2303.68): 38 nodes 1 leaves 87540 minterms\nT-D APA 87540\nT-D ID (32768): 2 nodes 1 leaves 65536 minterms\nT-D BU (32768): 2 nodes 1 leaves 65536 minterms\nT-D HB (10922.7): 3 nodes 1 leaves 32768 minterms\nT-D SP (10922.7): 3 nodes 1 leaves 32768 minterms\nT-D UA (4915.2): 5 nodes 1 leaves 24576 minterms\nT-D C1 (32768): 2 nodes 1 leaves 65536 minterms\nT-D C2 (10922.7): 3 nodes 1 leaves 32768 minterms\nTEST-DENSITY:: G95BF (19 variables)\nT-D    (11725.8): 41 nodes 1 leaves 480756 minterms\nT-D APA 480756\nT-D ID (131072): 3 nodes 1 leaves 393216 minterms\nT-D BU (131072): 3 nodes 1 leaves 393216 minterms\nT-D HB (131072): 2 nodes 1 leaves 262144 minterms\nT-D SP (81920): 4 nodes 1 leaves 327680 minterms\nT-D UA (131072): 2 nodes 1 leaves 262144 minterms\nT-D C1 (131072): 3 nodes 1 leaves 393216 minterms\nT-D C2 (131072): 2 nodes 1 leaves 262144 minterms\nTEST-DENSITY:: G103BF (19 variables)\nT-D    (11174.1): 40 nodes 1 leaves 446964 minterms\nT-D APA 446964\nT-D ID (131072): 3 nodes 1 leaves 393216 minterms\nT-D BU (131072): 3 nodes 1 leaves 393216 minterms\nT-D HB (131072): 2 nodes 1 leaves 262144 minterms\nT-D SP (81920): 4 nodes 1 leaves 327680 minterms\nT-D UA (131072): 2 nodes 1 leaves 262144 minterms\nT-D C1 (131072): 3 nodes 1 leaves 393216 minterms\nT-D C2 (131072): 2 nodes 1 leaves 262144 minterms\nTEST-DENSITY:: G90 (27 variables)\nT-D    (599725): 55 nodes 1 leaves 3.29849e+07 minterms\nT-D APA 32984868\nT-D ID (1.92239e+06): 12 nodes 1 leaves 2.30687e+07 minterms\nT-D BU (1.41476e+06): 20 nodes 1 leaves 2.82952e+07 minterms\nT-D HB (4.1943e+06): 4 nodes 1 leaves 1.67772e+07 minterms\nT-D SP (1.97616e+06): 13 nodes 1 leaves 2.56901e+07 minterms\nT-D UA (4.1943e+06): 4 nodes 1 leaves 1.67772e+07 minterms\nT-D C1 (1.92239e+06): 12 nodes 1 leaves 2.30687e+07 minterms\nT-D C2 (4.1943e+06): 4 nodes 1 leaves 1.67772e+07 minterms\nTEST-DENSITY:: G380 (18 variables)\nT-D    (1982.67): 39 nodes 1 leaves 77324 minterms\nT-D APA 77324\nT-D ID (21845.3): 3 nodes 1 leaves 65536 minterms\nT-D BU (21845.3): 3 nodes 1 leaves 65536 minterms\nT-D HB (21845.3): 3 nodes 1 leaves 65536 minterms\nT-D SP (7509.33): 9 nodes 1 leaves 67584 minterms\nT-D UA (21845.3): 3 nodes 1 leaves 65536 minterms\nT-D C1 (21845.3): 3 nodes 1 leaves 65536 minterms\nT-D C2 (21845.3): 3 nodes 1 leaves 65536 minterms\nTEST-DENSITY:: G262 (15 variables)\nT-D    (49.3214): 28 nodes 1 leaves 1381 minterms\nT-D APA 1381\nT-D ID (170.667): 6 nodes 1 leaves 1024 minterms\nT-D BU (170.667): 6 nodes 1 leaves 1024 minterms\nT-D HB (170.667): 6 nodes 1 leaves 1024 minterms\nT-D SP (77.7143): 14 nodes 1 leaves 1088 minterms\nT-D UA (170.667): 6 nodes 1 leaves 1024 minterms\nT-D C1 (170.667): 6 nodes 1 leaves 1024 minterms\nT-D C2 (170.667): 6 nodes 1 leaves 1024 minterms\nTEST-DENSITY:: G394 (12 variables)\nT-D    (79.8667): 15 nodes 1 leaves 1198 minterms\nT-D APA 1198\nT-D ID (341.333): 3 nodes 1 leaves 1024 minterms\nT-D BU (341.333): 3 nodes 1 leaves 1024 minterms\nT-D HB (341.333): 3 nodes 1 leaves 1024 minterms\nT-D SP (132): 8 nodes 1 leaves 1056 minterms\nT-D UA (341.333): 3 nodes 1 leaves 1024 minterms\nT-D C1 (341.333): 3 nodes 1 leaves 1024 minterms\nT-D C2 (341.333): 3 nodes 1 leaves 1024 minterms\nTEST-DENSITY:: G250 (9 variables)\nT-D    (7.1): 10 nodes 1 leaves 71 minterms\nT-D APA 71\nT-D ID (16): 4 nodes 1 leaves 64 minterms\nT-D BU (16): 4 nodes 1 leaves 64 minterms\nT-D HB (16): 4 nodes 1 leaves 64 minterms\nT-D SP (8.5): 8 nodes 1 leaves 68 minterms\nT-D UA (16): 4 nodes 1 leaves 64 minterms\nT-D C1 (16): 4 nodes 1 leaves 64 minterms\nT-D C2 (16): 4 nodes 1 leaves 64 minterms\nTEST-DENSITY:: G122 (8 variables)\nT-D    (2.09091): 11 nodes 1 leaves 23 minterms\nT-D APA 23\nT-D ID (3.2): 5 nodes 1 leaves 16 minterms\nT-D BU (3.2): 5 nodes 1 leaves 16 minterms\nT-D HB (3.2): 5 nodes 1 leaves 16 minterms\nT-D SP (2.22222): 9 nodes 1 leaves 20 minterms\nT-D UA (3.2): 5 nodes 1 leaves 16 minterms\nT-D C1 (3.2): 5 nodes 1 leaves 16 minterms\nT-D C2 (3.2): 5 nodes 1 leaves 16 minterms\nTEST-DENSITY:: G133 (14 variables)\nT-D    (314.118): 17 nodes 1 leaves 5340 minterms\nT-D APA 5340\nT-D ID (327.111): 9 nodes 1 leaves 2944 minterms\nT-D BU (396.8): 10 nodes 1 leaves 3968 minterms\nT-D HB (327.111): 9 nodes 1 leaves 2944 minterms\nT-D SP (396.8): 10 nodes 1 leaves 3968 minterms\nT-D UA (327.111): 9 nodes 1 leaves 2944 minterms\nT-D C1 (327.111): 9 nodes 1 leaves 2944 minterms\nT-D C2 (396.8): 10 nodes 1 leaves 3968 minterms\nTEST-DENSITY:: G138 (14 variables)\nT-D    (759.412): 17 nodes 1 leaves 12910 minterms\nT-D APA 12910\nT-D ID (4096): 3 nodes 1 leaves 12288 minterms\nT-D BU (4096): 3 nodes 1 leaves 12288 minterms\nT-D HB (204.8): 5 nodes 1 leaves 1024 minterms\nT-D SP (512): 4 nodes 1 leaves 2048 minterms\nT-D UA (966.4): 10 nodes 1 leaves 9664 minterms\nT-D C1 (4096): 3 nodes 1 leaves 12288 minterms\nT-D C2 (4096): 2 nodes 1 leaves 8192 minterms\nTEST-DENSITY:: G139 (10 variables)\nT-D    (27.4545): 11 nodes 1 leaves 302 minterms\nT-D APA 302\nT-D ID (28): 8 nodes 1 leaves 224 minterms\nT-D BU (27.4545): 11 nodes 1 leaves 302 minterms\nT-D HB (22.8571): 7 nodes 1 leaves 160 minterms\nT-D SP (29.3333): 9 nodes 1 leaves 264 minterms\nT-D UA (28): 8 nodes 1 leaves 224 minterms\nT-D C1 (28): 8 nodes 1 leaves 224 minterms\nT-D C2 (28): 8 nodes 1 leaves 224 minterms\nTEST-DENSITY:: G140 (10 variables)\nT-D    (71.9091): 11 nodes 1 leaves 791 minterms\nT-D APA 791\nT-D ID (256): 3 nodes 1 leaves 768 minterms\nT-D BU (256): 3 nodes 1 leaves 768 minterms\nT-D HB (12.8): 5 nodes 1 leaves 64 minterms\nT-D SP (51.2): 5 nodes 1 leaves 256 minterms\nT-D UA (74): 8 nodes 1 leaves 592 minterms\nT-D C1 (256): 3 nodes 1 leaves 768 minterms\nT-D C2 (256): 2 nodes 1 leaves 512 minterms\nTEST-DENSITY:: G141 (20 variables)\nT-D    (6715.54): 52 nodes 1 leaves 349208 minterms\nT-D APA 349208\nT-D ID (16384): 6 nodes 1 leaves 98304 minterms\nT-D BU (14745.6): 10 nodes 1 leaves 147456 minterms\nT-D HB (11702.9): 7 nodes 1 leaves 81920 minterms\nT-D SP (14043.4): 7 nodes 1 leaves 98304 minterms\nT-D UA (15360): 8 nodes 1 leaves 122880 minterms\nT-D C1 (16384): 6 nodes 1 leaves 98304 minterms\nT-D C2 (14043.4): 7 nodes 1 leaves 98304 minterms\nTEST-DENSITY:: G142 (20 variables)\nT-D    (18443.6): 45 nodes 1 leaves 829964 minterms\nT-D APA 829964\nT-D ID (262144): 3 nodes 1 leaves 786432 minterms\nT-D BU (262144): 3 nodes 1 leaves 786432 minterms\nT-D HB (13107.2): 5 nodes 1 leaves 65536 minterms\nT-D SP (32768): 4 nodes 1 leaves 131072 minterms\nT-D UA (49152): 7 nodes 1 leaves 344064 minterms\nT-D C1 (262144): 3 nodes 1 leaves 786432 minterms\nT-D C2 (262144): 2 nodes 1 leaves 524288 minterms\nTEST-DENSITY:: G125 (22 variables)\nT-D    (11894.8): 78 nodes 1 leaves 927796 minterms\nT-D APA 927796\nT-D ID (157286): 5 nodes 1 leaves 786432 minterms\nT-D BU (157286): 5 nodes 1 leaves 786432 minterms\nT-D HB (52428.8): 5 nodes 1 leaves 262144 minterms\nT-D SP (65536): 6 nodes 1 leaves 393216 minterms\nT-D UA (65536): 6 nodes 1 leaves 393216 minterms\nT-D C1 (157286): 5 nodes 1 leaves 786432 minterms\nT-D C2 (157286): 5 nodes 1 leaves 786432 minterms\nTEST-DENSITY:: G126 (22 variables)\nT-D    (15155.4): 58 nodes 1 leaves 879012 minterms\nT-D APA 879012\nT-D ID (131072): 4 nodes 1 leaves 524288 minterms\nT-D BU (131072): 4 nodes 1 leaves 524288 minterms\nT-D HB (131072): 4 nodes 1 leaves 524288 minterms\nT-D SP (131072): 4 nodes 1 leaves 524288 minterms\nT-D UA (87381.3): 6 nodes 1 leaves 524288 minterms\nT-D C1 (131072): 4 nodes 1 leaves 524288 minterms\nT-D C2 (131072): 4 nodes 1 leaves 524288 minterms\nTEST-DENSITY:: G127 (22 variables)\nT-D    (13692): 67 nodes 1 leaves 917364 minterms\nT-D APA 917364\nT-D ID (131072): 4 nodes 1 leaves 524288 minterms\nT-D BU (131072): 4 nodes 1 leaves 524288 minterms\nT-D HB (65536): 6 nodes 1 leaves 393216 minterms\nT-D SP (87381.3): 6 nodes 1 leaves 524288 minterms\nT-D UA (87381.3): 6 nodes 1 leaves 524288 minterms\nT-D C1 (131072): 4 nodes 1 leaves 524288 minterms\nT-D C2 (157286): 5 nodes 1 leaves 786432 minterms\nTEST-DENSITY:: G128 (20 variables)\nT-D    (3404.18): 66 nodes 1 leaves 224676 minterms\nT-D APA 224676\nT-D ID (32768): 4 nodes 1 leaves 131072 minterms\nT-D BU (32768): 4 nodes 1 leaves 131072 minterms\nT-D HB (32768): 4 nodes 1 leaves 131072 minterms\nT-D SP (16384): 8 nodes 1 leaves 131072 minterms\nT-D UA (13107.2): 5 nodes 1 leaves 65536 minterms\nT-D C1 (32768): 4 nodes 1 leaves 131072 minterms\nT-D C2 (28086.9): 7 nodes 1 leaves 196608 minterms\nTEST-DENSITY:: G129 (18 variables)\nT-D    (154.512): 43 nodes 1 leaves 6644 minterms\nT-D APA 6644\nT-D ID (585.143): 7 nodes 1 leaves 4096 minterms\nT-D BU (585.143): 7 nodes 1 leaves 4096 minterms\nT-D HB (585.143): 7 nodes 1 leaves 4096 minterms\nT-D SP (272): 16 nodes 1 leaves 4352 minterms\nT-D UA (585.143): 7 nodes 1 leaves 4096 minterms\nT-D C1 (585.143): 7 nodes 1 leaves 4096 minterms\nT-D C2 (585.143): 7 nodes 1 leaves 4096 minterms\nTEST-DENSITY:: G130 (15 variables)\nT-D    (49.3214): 28 nodes 1 leaves 1381 minterms\nT-D APA 1381\nT-D ID (170.667): 6 nodes 1 leaves 1024 minterms\nT-D BU (170.667): 6 nodes 1 leaves 1024 minterms\nT-D HB (170.667): 6 nodes 1 leaves 1024 minterms\nT-D SP (77.7143): 14 nodes 1 leaves 1088 minterms\nT-D UA (170.667): 6 nodes 1 leaves 1024 minterms\nT-D C1 (170.667): 6 nodes 1 leaves 1024 minterms\nT-D C2 (170.667): 6 nodes 1 leaves 1024 minterms\nTEST-DENSITY:: G131 (12 variables)\nT-D    (18): 17 nodes 1 leaves 306 minterms\nT-D APA 306\nT-D ID (51.2): 5 nodes 1 leaves 256 minterms\nT-D BU (51.2): 5 nodes 1 leaves 256 minterms\nT-D HB (51.2): 5 nodes 1 leaves 256 minterms\nT-D SP (24.7273): 11 nodes 1 leaves 272 minterms\nT-D UA (51.2): 5 nodes 1 leaves 256 minterms\nT-D C1 (51.2): 5 nodes 1 leaves 256 minterms\nT-D C2 (51.2): 5 nodes 1 leaves 256 minterms\nTEST-DENSITY:: G132 (9 variables)\nT-D    (7.1): 10 nodes 1 leaves 71 minterms\nT-D APA 71\nT-D ID (16): 4 nodes 1 leaves 64 minterms\nT-D BU (16): 4 nodes 1 leaves 64 minterms\nT-D HB (16): 4 nodes 1 leaves 64 minterms\nT-D SP (8.5): 8 nodes 1 leaves 68 minterms\nT-D UA (16): 4 nodes 1 leaves 64 minterms\nT-D C1 (16): 4 nodes 1 leaves 64 minterms\nT-D C2 (16): 4 nodes 1 leaves 64 minterms\nTesting BDD decomposition algorithms\nTEST-DECOMP:: G91 (1 variables)\nT-d    : 2 nodes 1 leaves 1 minterms\nT-d SS : 2 nodes\nT-d GS : 2 nodes 1 leaves 1 minterms\nT-d HS : 1 nodes 1 leaves 2 minterms\nT-d SI : 2 nodes\nT-d GI : 2 nodes 1 leaves 1 minterms\nT-d HI : 1 nodes 1 leaves 2 minterms\nT-d SD : 2 nodes\nT-d GD : 2 nodes 1 leaves 1 minterms\nT-d HD : 1 nodes 1 leaves 2 minterms\nT-d SQ : 2 nodes\nT-d GQ : 2 nodes 1 leaves 1 minterms\nT-d HQ : 1 nodes 1 leaves 2 minterms\nTEST-DECOMP:: G94 (1 variables)\nT-d    : 2 nodes 1 leaves 1 minterms\nT-d SS : 2 nodes\nT-d GS : 2 nodes 1 leaves 1 minterms\nT-d HS : 1 nodes 1 leaves 2 minterms\nT-d SI : 2 nodes\nT-d GI : 2 nodes 1 leaves 1 minterms\nT-d HI : 1 nodes 1 leaves 2 minterms\nT-d SD : 2 nodes\nT-d GD : 2 nodes 1 leaves 1 minterms\nT-d HD : 1 nodes 1 leaves 2 minterms\nT-d SQ : 2 nodes\nT-d GQ : 2 nodes 1 leaves 1 minterms\nT-d HQ : 1 nodes 1 leaves 2 minterms\nTEST-DECOMP:: G107 (3 variables)\nT-d    : 4 nodes 1 leaves 1 minterms\nT-d SS : 4 nodes\nT-d GS : 3 nodes 1 leaves 2 minterms\nT-d HS : 2 nodes 1 leaves 4 minterms\nT-d SI : 4 nodes\nT-d GI : 4 nodes 1 leaves 1 minterms\nT-d HI : 1 nodes 1 leaves 8 minterms\nT-d SD : 4 nodes\nT-d GD : 4 nodes 1 leaves 1 minterms\nT-d HD : 1 nodes 1 leaves 8 minterms\nT-d SQ : 5 nodes\nT-d GQ : 2 nodes 1 leaves 4 minterms\nT-d HQ : 4 nodes 1 leaves 5 minterms\nTEST-DECOMP:: G83 (3 variables)\nT-d    : 4 nodes 1 leaves 1 minterms\nT-d SS : 4 nodes\nT-d GS : 3 nodes 1 leaves 2 minterms\nT-d HS : 2 nodes 1 leaves 4 minterms\nT-d SI : 4 nodes\nT-d GI : 4 nodes 1 leaves 1 minterms\nT-d HI : 1 nodes 1 leaves 8 minterms\nT-d SD : 4 nodes\nT-d GD : 4 nodes 1 leaves 1 minterms\nT-d HD : 1 nodes 1 leaves 8 minterms\nT-d SQ : 5 nodes\nT-d GQ : 4 nodes 1 leaves 5 minterms\nT-d HQ : 2 nodes 1 leaves 4 minterms\nTEST-DECOMP:: G84 (3 variables)\nT-d    : 4 nodes 1 leaves 1 minterms\nT-d SS : 4 nodes\nT-d GS : 3 nodes 1 leaves 2 minterms\nT-d HS : 2 nodes 1 leaves 4 minterms\nT-d SI : 4 nodes\nT-d GI : 4 nodes 1 leaves 1 minterms\nT-d HI : 1 nodes 1 leaves 8 minterms\nT-d SD : 4 nodes\nT-d GD : 4 nodes 1 leaves 1 minterms\nT-d HD : 1 nodes 1 leaves 8 minterms\nT-d SQ : 5 nodes\nT-d GQ : 2 nodes 1 leaves 4 minterms\nT-d HQ : 4 nodes 1 leaves 5 minterms\nTEST-DECOMP:: G85 (3 variables)\nT-d    : 4 nodes 1 leaves 1 minterms\nT-d SS : 4 nodes\nT-d GS : 3 nodes 1 leaves 2 minterms\nT-d HS : 2 nodes 1 leaves 4 minterms\nT-d SI : 4 nodes\nT-d GI : 4 nodes 1 leaves 1 minterms\nT-d HI : 1 nodes 1 leaves 8 minterms\nT-d SD : 4 nodes\nT-d GD : 4 nodes 1 leaves 1 minterms\nT-d HD : 1 nodes 1 leaves 8 minterms\nT-d SQ : 5 nodes\nT-d GQ : 2 nodes 1 leaves 4 minterms\nT-d HQ : 4 nodes 1 leaves 5 minterms\nTEST-DECOMP:: G100BF (3 variables)\nT-d    : 4 nodes 1 leaves 7 minterms\nT-d SS : 4 nodes\nT-d GS : 4 nodes 1 leaves 7 minterms\nT-d HS : 1 nodes 1 leaves 8 minterms\nT-d SI : 4 nodes\nT-d GI : 4 nodes 1 leaves 7 minterms\nT-d HI : 1 nodes 1 leaves 8 minterms\nT-d SD : 4 nodes\nT-d GD : 4 nodes 1 leaves 7 minterms\nT-d HD : 1 nodes 1 leaves 8 minterms\nT-d SQ : 4 nodes\nT-d GQ : 4 nodes 1 leaves 7 minterms\nT-d HQ : 1 nodes 1 leaves 8 minterms\nTEST-DECOMP:: G98BF (3 variables)\nT-d    : 4 nodes 1 leaves 7 minterms\nT-d SS : 4 nodes\nT-d GS : 4 nodes 1 leaves 7 minterms\nT-d HS : 1 nodes 1 leaves 8 minterms\nT-d SI : 4 nodes\nT-d GI : 4 nodes 1 leaves 7 minterms\nT-d HI : 1 nodes 1 leaves 8 minterms\nT-d SD : 4 nodes\nT-d GD : 4 nodes 1 leaves 7 minterms\nT-d HD : 1 nodes 1 leaves 8 minterms\nT-d SQ : 4 nodes\nT-d GQ : 4 nodes 1 leaves 7 minterms\nT-d HQ : 1 nodes 1 leaves 8 minterms\nTEST-DECOMP:: G96BF (3 variables)\nT-d    : 4 nodes 1 leaves 7 minterms\nT-d SS : 4 nodes\nT-d GS : 4 nodes 1 leaves 7 minterms\nT-d HS : 1 nodes 1 leaves 8 minterms\nT-d SI : 4 nodes\nT-d GI : 4 nodes 1 leaves 7 minterms\nT-d HI : 1 nodes 1 leaves 8 minterms\nT-d SD : 4 nodes\nT-d GD : 4 nodes 1 leaves 7 minterms\nT-d HD : 1 nodes 1 leaves 8 minterms\nT-d SQ : 4 nodes\nT-d GQ : 4 nodes 1 leaves 7 minterms\nT-d HQ : 1 nodes 1 leaves 8 minterms\nTEST-DECOMP:: G92 (4 variables)\nT-d    : 5 nodes 1 leaves 1 minterms\nT-d SS : 5 nodes\nT-d GS : 3 nodes 1 leaves 4 minterms\nT-d HS : 3 nodes 1 leaves 4 minterms\nT-d SI : 5 nodes\nT-d GI : 5 nodes 1 leaves 1 minterms\nT-d HI : 1 nodes 1 leaves 16 minterms\nT-d SD : 5 nodes\nT-d GD : 5 nodes 1 leaves 1 minterms\nT-d HD : 1 nodes 1 leaves 16 minterms\nT-d SQ : 6 nodes\nT-d GQ : 2 nodes 1 leaves 8 minterms\nT-d HQ : 5 nodes 1 leaves 9 minterms\nTEST-DECOMP:: G87BF (7 variables)\nT-d    : 8 nodes 1 leaves 105 minterms\nT-d SS : 9 nodes\nT-d GS : 4 nodes 1 leaves 112 minterms\nT-d HS : 8 nodes 1 leaves 121 minterms\nT-d SI : 8 nodes\nT-d GI : 8 nodes 1 leaves 105 minterms\nT-d HI : 1 nodes 1 leaves 128 minterms\nT-d SD : 8 nodes\nT-d GD : 8 nodes 1 leaves 105 minterms\nT-d HD : 1 nodes 1 leaves 128 minterms\nT-d SQ : 9 nodes\nT-d GQ : 8 nodes 1 leaves 121 minterms\nT-d HQ : 4 nodes 1 leaves 112 minterms\nTEST-DECOMP:: G89BF (7 variables)\nT-d    : 10 nodes 1 leaves 105 minterms\nT-d SS : 11 nodes\nT-d GS : 4 nodes 1 leaves 112 minterms\nT-d HS : 8 nodes 1 leaves 121 minterms\nT-d SI : 10 nodes\nT-d GI : 10 nodes 1 leaves 105 minterms\nT-d HI : 1 nodes 1 leaves 128 minterms\nT-d SD : 14 nodes\nT-d GD : 7 nodes 1 leaves 122 minterms\nT-d HD : 8 nodes 1 leaves 108 minterms\nT-d SQ : 11 nodes\nT-d GQ : 8 nodes 1 leaves 121 minterms\nT-d HQ : 4 nodes 1 leaves 112 minterms\nTEST-DECOMP:: G101BF (9 variables)\nT-d    : 12 nodes 1 leaves 489 minterms\nT-d SS : 14 nodes\nT-d GS : 6 nodes 1 leaves 496 minterms\nT-d HS : 10 nodes 1 leaves 505 minterms\nT-d SI : 12 nodes\nT-d GI : 12 nodes 1 leaves 489 minterms\nT-d HI : 1 nodes 1 leaves 512 minterms\nT-d SD : 12 nodes\nT-d GD : 12 nodes 1 leaves 489 minterms\nT-d HD : 1 nodes 1 leaves 512 minterms\nT-d SQ : 14 nodes\nT-d GQ : 10 nodes 1 leaves 505 minterms\nT-d HQ : 6 nodes 1 leaves 496 minterms\nTEST-DECOMP:: G106BF (9 variables)\nT-d    : 10 nodes 1 leaves 441 minterms\nT-d SS : 12 nodes\nT-d GS : 4 nodes 1 leaves 448 minterms\nT-d HS : 10 nodes 1 leaves 505 minterms\nT-d SI : 10 nodes\nT-d GI : 10 nodes 1 leaves 441 minterms\nT-d HI : 1 nodes 1 leaves 512 minterms\nT-d SD : 10 nodes\nT-d GD : 10 nodes 1 leaves 441 minterms\nT-d HD : 1 nodes 1 leaves 512 minterms\nT-d SQ : 10 nodes\nT-d GQ : 10 nodes 1 leaves 441 minterms\nT-d HQ : 1 nodes 1 leaves 512 minterms\nTEST-DECOMP:: G97BF (9 variables)\nT-d    : 10 nodes 1 leaves 489 minterms\nT-d SS : 12 nodes\nT-d GS : 6 nodes 1 leaves 496 minterms\nT-d HS : 10 nodes 1 leaves 505 minterms\nT-d SI : 10 nodes\nT-d GI : 10 nodes 1 leaves 489 minterms\nT-d HI : 1 nodes 1 leaves 512 minterms\nT-d SD : 10 nodes\nT-d GD : 10 nodes 1 leaves 489 minterms\nT-d HD : 1 nodes 1 leaves 512 minterms\nT-d SQ : 10 nodes\nT-d GQ : 10 nodes 1 leaves 489 minterms\nT-d HQ : 1 nodes 1 leaves 512 minterms\nTEST-DECOMP:: G104BF (9 variables)\nT-d    : 11 nodes 1 leaves 441 minterms\nT-d SS : 13 nodes\nT-d GS : 4 nodes 1 leaves 448 minterms\nT-d HS : 10 nodes 1 leaves 505 minterms\nT-d SI : 11 nodes\nT-d GI : 11 nodes 1 leaves 441 minterms\nT-d HI : 1 nodes 1 leaves 512 minterms\nT-d SD : 13 nodes\nT-d GD : 4 nodes 1 leaves 448 minterms\nT-d HD : 10 nodes 1 leaves 505 minterms\nT-d SQ : 13 nodes\nT-d GQ : 10 nodes 1 leaves 505 minterms\nT-d HQ : 4 nodes 1 leaves 448 minterms\nTEST-DECOMP:: G88BF (11 variables)\nT-d    : 14 nodes 1 leaves 1426 minterms\nT-d SS : 14 nodes\nT-d GS : 14 nodes 1 leaves 1426 minterms\nT-d HS : 1 nodes 1 leaves 2048 minterms\nT-d SI : 14 nodes\nT-d GI : 14 nodes 1 leaves 1426 minterms\nT-d HI : 1 nodes 1 leaves 2048 minterms\nT-d SD : 14 nodes\nT-d GD : 14 nodes 1 leaves 1426 minterms\nT-d HD : 1 nodes 1 leaves 2048 minterms\nT-d SQ : 21 nodes\nT-d GQ : 15 nodes 1 leaves 1750 minterms\nT-d HQ : 11 nodes 1 leaves 1724 minterms\nTEST-DECOMP:: G99BF (13 variables)\nT-d    : 16 nodes 1 leaves 7570 minterms\nT-d SS : 18 nodes\nT-d GS : 8 nodes 1 leaves 7744 minterms\nT-d HS : 16 nodes 1 leaves 8018 minterms\nT-d SI : 16 nodes\nT-d GI : 16 nodes 1 leaves 7570 minterms\nT-d HI : 1 nodes 1 leaves 8192 minterms\nT-d SD : 16 nodes\nT-d GD : 16 nodes 1 leaves 7570 minterms\nT-d HD : 1 nodes 1 leaves 8192 minterms\nT-d SQ : 24 nodes\nT-d GQ : 17 nodes 1 leaves 7894 minterms\nT-d HQ : 13 nodes 1 leaves 7868 minterms\nTEST-DECOMP:: G105BF (13 variables)\nT-d    : 16 nodes 1 leaves 6994 minterms\nT-d SS : 18 nodes\nT-d GS : 4 nodes 1 leaves 7168 minterms\nT-d HS : 16 nodes 1 leaves 8018 minterms\nT-d SI : 16 nodes\nT-d GI : 16 nodes 1 leaves 6994 minterms\nT-d HI : 1 nodes 1 leaves 8192 minterms\nT-d SD : 16 nodes\nT-d GD : 16 nodes 1 leaves 6994 minterms\nT-d HD : 1 nodes 1 leaves 8192 minterms\nT-d SQ : 25 nodes\nT-d GQ : 17 nodes 1 leaves 7606 minterms\nT-d HQ : 14 nodes 1 leaves 7580 minterms\nTEST-DECOMP:: G86BF (17 variables)\nT-d    : 38 nodes 1 leaves 87540 minterms\nT-d SS : 38 nodes\nT-d GS : 5 nodes 1 leaves 106496 minterms\nT-d HS : 36 nodes 1 leaves 90612 minterms\nT-d SI : 38 nodes\nT-d GI : 5 nodes 1 leaves 106496 minterms\nT-d HI : 36 nodes 1 leaves 90612 minterms\nT-d SD : 49 nodes\nT-d GD : 27 nodes 1 leaves 130476 minterms\nT-d HD : 26 nodes 1 leaves 88136 minterms\nT-d SQ : 48 nodes\nT-d GQ : 32 nodes 1 leaves 109972 minterms\nT-d HQ : 35 nodes 1 leaves 108640 minterms\nTEST-DECOMP:: G95BF (19 variables)\nT-d    : 41 nodes 1 leaves 480756 minterms\nT-d SS : 43 nodes\nT-d GS : 8 nodes 1 leaves 495616 minterms\nT-d HS : 39 nodes 1 leaves 487924 minterms\nT-d SI : 41 nodes\nT-d GI : 41 nodes 1 leaves 480756 minterms\nT-d HI : 1 nodes 1 leaves 524288 minterms\nT-d SD : 59 nodes\nT-d GD : 36 nodes 1 leaves 520672 minterms\nT-d HD : 29 nodes 1 leaves 484372 minterms\nT-d SQ : 52 nodes\nT-d GQ : 35 nodes 1 leaves 503188 minterms\nT-d HQ : 38 nodes 1 leaves 501856 minterms\nTEST-DECOMP:: G103BF (19 variables)\nT-d    : 40 nodes 1 leaves 446964 minterms\nT-d SS : 42 nodes\nT-d GS : 4 nodes 1 leaves 458752 minterms\nT-d HS : 39 nodes 1 leaves 512500 minterms\nT-d SI : 40 nodes\nT-d GI : 40 nodes 1 leaves 446964 minterms\nT-d HI : 1 nodes 1 leaves 524288 minterms\nT-d SD : 54 nodes\nT-d GD : 19 nodes 1 leaves 447616 minterms\nT-d HD : 37 nodes 1 leaves 523636 minterms\nT-d SQ : 55 nodes\nT-d GQ : 39 nodes 1 leaves 486454 minterms\nT-d HQ : 36 nodes 1 leaves 484798 minterms\nTEST-DECOMP:: G90 (27 variables)\nT-d    : 55 nodes 1 leaves 3.29849e+07 minterms\nT-d SS : 55 nodes\nT-d GS : 3 nodes 1 leaves 3.35544e+07 minterms\nT-d HS : 53 nodes 1 leaves 1.31939e+08 minterms\nT-d SI : 55 nodes\nT-d GI : 3 nodes 1 leaves 3.35544e+07 minterms\nT-d HI : 53 nodes 1 leaves 1.31939e+08 minterms\nT-d SD : 56 nodes\nT-d GD : 28 nodes 1 leaves 3.32472e+07 minterms\nT-d HD : 31 nodes 1 leaves 1.33168e+08 minterms\nT-d SQ : 59 nodes\nT-d GQ : 35 nodes 1 leaves 8.33167e+07 minterms\nT-d HQ : 28 nodes 1 leaves 8.38859e+07 minterms\nTEST-DECOMP:: G380 (18 variables)\nT-d    : 39 nodes 1 leaves 77324 minterms\nT-d SS : 35 nodes\nT-d GS : 2 nodes 1 leaves 131072 minterms\nT-d HS : 34 nodes 1 leaves 154648 minterms\nT-d SI : 35 nodes\nT-d GI : 2 nodes 1 leaves 131072 minterms\nT-d HI : 34 nodes 1 leaves 154648 minterms\nT-d SD : 54 nodes\nT-d GD : 30 nodes 1 leaves 115720 minterms\nT-d HD : 32 nodes 1 leaves 164480 minterms\nT-d SQ : 54 nodes\nT-d GQ : 39 nodes 1 leaves 168906 minterms\nT-d HQ : 36 nodes 1 leaves 170562 minterms\nTEST-DECOMP:: G262 (15 variables)\nT-d    : 28 nodes 1 leaves 1381 minterms\nT-d SS : 29 nodes\nT-d GS : 4 nodes 1 leaves 20480 minterms\nT-d HS : 26 nodes 1 leaves 4453 minterms\nT-d SI : 28 nodes\nT-d GI : 28 nodes 1 leaves 1381 minterms\nT-d HI : 1 nodes 1 leaves 32768 minterms\nT-d SD : 37 nodes\nT-d GD : 19 nodes 1 leaves 9424 minterms\nT-d HD : 19 nodes 1 leaves 7200 minterms\nT-d SQ : 36 nodes\nT-d GQ : 23 nodes 1 leaves 17608 minterms\nT-d HQ : 24 nodes 1 leaves 16541 minterms\nTEST-DECOMP:: G394 (12 variables)\nT-d    : 15 nodes 1 leaves 1198 minterms\nT-d SS : 15 nodes\nT-d GS : 2 nodes 1 leaves 2048 minterms\nT-d HS : 14 nodes 1 leaves 2396 minterms\nT-d SI : 15 nodes\nT-d GI : 2 nodes 1 leaves 2048 minterms\nT-d HI : 14 nodes 1 leaves 2396 minterms\nT-d SD : 16 nodes\nT-d GD : 8 nodes 1 leaves 2272 minterms\nT-d HD : 10 nodes 1 leaves 2608 minterms\nT-d SQ : 24 nodes\nT-d GQ : 17 nodes 1 leaves 2634 minterms\nT-d HQ : 14 nodes 1 leaves 2660 minterms\nTEST-DECOMP:: G250 (9 variables)\nT-d    : 10 nodes 1 leaves 71 minterms\nT-d SS : 10 nodes\nT-d GS : 3 nodes 1 leaves 128 minterms\nT-d HS : 8 nodes 1 leaves 284 minterms\nT-d SI : 10 nodes\nT-d GI : 3 nodes 1 leaves 128 minterms\nT-d HI : 8 nodes 1 leaves 284 minterms\nT-d SD : 11 nodes\nT-d GD : 7 nodes 1 leaves 72 minterms\nT-d HD : 5 nodes 1 leaves 480 minterms\nT-d SQ : 11 nodes\nT-d GQ : 10 nodes 1 leaves 263 minterms\nT-d HQ : 4 nodes 1 leaves 320 minterms\nTEST-DECOMP:: G122 (8 variables)\nT-d    : 11 nodes 1 leaves 23 minterms\nT-d SS : 10 nodes\nT-d GS : 3 nodes 1 leaves 64 minterms\nT-d HS : 8 nodes 1 leaves 92 minterms\nT-d SI : 9 nodes\nT-d GI : 4 nodes 1 leaves 32 minterms\nT-d HI : 6 nodes 1 leaves 184 minterms\nT-d SD : 12 nodes\nT-d GD : 7 nodes 1 leaves 48 minterms\nT-d HD : 7 nodes 1 leaves 120 minterms\nT-d SQ : 12 nodes\nT-d GQ : 9 nodes 1 leaves 135 minterms\nT-d HQ : 5 nodes 1 leaves 144 minterms\nTEST-DECOMP:: G133 (14 variables)\nT-d    : 17 nodes 1 leaves 5340 minterms\nT-d SS : 19 nodes\nT-d GS : 10 nodes 1 leaves 8064 minterms\nT-d HS : 17 nodes 1 leaves 13660 minterms\nT-d SI : 17 nodes\nT-d GI : 17 nodes 1 leaves 5340 minterms\nT-d HI : 1 nodes 1 leaves 16384 minterms\nT-d SD : 19 nodes\nT-d GD : 10 nodes 1 leaves 8064 minterms\nT-d HD : 17 nodes 1 leaves 13660 minterms\nT-d SQ : 26 nodes\nT-d GQ : 19 nodes 1 leaves 10836 minterms\nT-d HQ : 15 nodes 1 leaves 10888 minterms\nTEST-DECOMP:: G138 (14 variables)\nT-d    : 17 nodes 1 leaves 12910 minterms\nT-d SS : 17 nodes\nT-d GS : 5 nodes 1 leaves 13312 minterms\nT-d HS : 15 nodes 1 leaves 14776 minterms\nT-d SI : 17 nodes\nT-d GI : 5 nodes 1 leaves 13312 minterms\nT-d HI : 15 nodes 1 leaves 14776 minterms\nT-d SD : 17 nodes\nT-d GD : 17 nodes 1 leaves 12910 minterms\nT-d HD : 1 nodes 1 leaves 16384 minterms\nT-d SQ : 26 nodes\nT-d GQ : 19 nodes 1 leaves 14634 minterms\nT-d HQ : 15 nodes 1 leaves 14660 minterms\nTEST-DECOMP:: G139 (10 variables)\nT-d    : 11 nodes 1 leaves 302 minterms\nT-d SS : 13 nodes\nT-d GS : 5 nodes 1 leaves 832 minterms\nT-d HS : 11 nodes 1 leaves 494 minterms\nT-d SI : 11 nodes\nT-d GI : 11 nodes 1 leaves 302 minterms\nT-d HI : 1 nodes 1 leaves 1024 minterms\nT-d SD : 11 nodes\nT-d GD : 11 nodes 1 leaves 302 minterms\nT-d HD : 1 nodes 1 leaves 1024 minterms\nT-d SQ : 12 nodes\nT-d GQ : 11 nodes 1 leaves 654 minterms\nT-d HQ : 7 nodes 1 leaves 672 minterms\nTEST-DECOMP:: G140 (10 variables)\nT-d    : 11 nodes 1 leaves 791 minterms\nT-d SS : 11 nodes\nT-d GS : 5 nodes 1 leaves 832 minterms\nT-d HS : 9 nodes 1 leaves 860 minterms\nT-d SI : 11 nodes\nT-d GI : 6 nodes 1 leaves 800 minterms\nT-d HI : 8 nodes 1 leaves 952 minterms\nT-d SD : 11 nodes\nT-d GD : 11 nodes 1 leaves 791 minterms\nT-d HD : 1 nodes 1 leaves 1024 minterms\nT-d SQ : 12 nodes\nT-d GQ : 11 nodes 1 leaves 903 minterms\nT-d HQ : 7 nodes 1 leaves 912 minterms\nTEST-DECOMP:: G141 (20 variables)\nT-d    : 52 nodes 1 leaves 349208 minterms\nT-d SS : 55 nodes\nT-d GS : 10 nodes 1 leaves 802816 minterms\nT-d HS : 52 nodes 1 leaves 594968 minterms\nT-d SI : 52 nodes\nT-d GI : 52 nodes 1 leaves 349208 minterms\nT-d HI : 1 nodes 1 leaves 1.04858e+06 minterms\nT-d SD : 74 nodes\nT-d GD : 26 nodes 1 leaves 837440 minterms\nT-d HD : 51 nodes 1 leaves 557572 minterms\nT-d SQ : 64 nodes\nT-d GQ : 47 nodes 1 leaves 697560 minterms\nT-d HQ : 50 nodes 1 leaves 700224 minterms\nTEST-DECOMP:: G142 (20 variables)\nT-d    : 45 nodes 1 leaves 829964 minterms\nT-d SS : 45 nodes\nT-d GS : 4 nodes 1 leaves 917504 minterms\nT-d HS : 42 nodes 1 leaves 873496 minterms\nT-d SI : 45 nodes\nT-d GI : 7 nodes 1 leaves 851968 minterms\nT-d HI : 41 nodes 1 leaves 962408 minterms\nT-d SD : 67 nodes\nT-d GD : 45 nodes 1 leaves 901164 minterms\nT-d HD : 25 nodes 1 leaves 977376 minterms\nT-d SQ : 57 nodes\nT-d GQ : 40 nodes 1 leaves 938604 minterms\nT-d HQ : 43 nodes 1 leaves 939936 minterms\nTEST-DECOMP:: G125 (22 variables)\nT-d    : 78 nodes 1 leaves 927796 minterms\nT-d SS : 79 nodes\nT-d GS : 3 nodes 1 leaves 3.14573e+06 minterms\nT-d HS : 77 nodes 1 leaves 1.06609e+06 minterms\nT-d SI : 78 nodes\nT-d GI : 78 nodes 1 leaves 927796 minterms\nT-d HI : 1 nodes 1 leaves 4.1943e+06 minterms\nT-d SD : 104 nodes\nT-d GD : 66 nodes 1 leaves 2.15491e+06 minterms\nT-d HD : 54 nodes 1 leaves 2.16694e+06 minterms\nT-d SQ : 94 nodes\nT-d GQ : 54 nodes 1 leaves 2.10725e+06 minterms\nT-d HQ : 43 nodes 1 leaves 3.01485e+06 minterms\nTEST-DECOMP:: G126 (22 variables)\nT-d    : 58 nodes 1 leaves 879012 minterms\nT-d SS : 60 nodes\nT-d GS : 5 nodes 1 leaves 2.62144e+06 minterms\nT-d HS : 56 nodes 1 leaves 1.23169e+06 minterms\nT-d SI : 58 nodes\nT-d GI : 58 nodes 1 leaves 879012 minterms\nT-d HI : 1 nodes 1 leaves 4.1943e+06 minterms\nT-d SD : 83 nodes\nT-d GD : 56 nodes 1 leaves 1.40178e+06 minterms\nT-d HD : 39 nodes 1 leaves 3.06502e+06 minterms\nT-d SQ : 65 nodes\nT-d GQ : 50 nodes 1 leaves 2.10372e+06 minterms\nT-d HQ : 17 nodes 1 leaves 2.9696e+06 minterms\nTEST-DECOMP:: G127 (22 variables)\nT-d    : 67 nodes 1 leaves 917364 minterms\nT-d SS : 68 nodes\nT-d GS : 3 nodes 1 leaves 3.14573e+06 minterms\nT-d HS : 66 nodes 1 leaves 1.04522e+06 minterms\nT-d SI : 67 nodes\nT-d GI : 67 nodes 1 leaves 917364 minterms\nT-d HI : 1 nodes 1 leaves 4.1943e+06 minterms\nT-d SD : 86 nodes\nT-d GD : 57 nodes 1 leaves 1.04469e+06 minterms\nT-d HD : 39 nodes 1 leaves 3.65808e+06 minterms\nT-d SQ : 80 nodes\nT-d GQ : 55 nodes 1 leaves 2.10725e+06 minterms\nT-d HQ : 27 nodes 1 leaves 3.00442e+06 minterms\nTEST-DECOMP:: G128 (20 variables)\nT-d    : 66 nodes 1 leaves 224676 minterms\nT-d SS : 64 nodes\nT-d GS : 5 nodes 1 leaves 589824 minterms\nT-d HS : 60 nodes 1 leaves 406816 minterms\nT-d SI : 64 nodes\nT-d GI : 5 nodes 1 leaves 589824 minterms\nT-d HI : 60 nodes 1 leaves 406816 minterms\nT-d SD : 71 nodes\nT-d GD : 26 nodes 1 leaves 587184 minterms\nT-d HD : 57 nodes 1 leaves 417376 minterms\nT-d SQ : 74 nodes\nT-d GQ : 57 nodes 1 leaves 530852 minterms\nT-d HQ : 19 nodes 1 leaves 742400 minterms\nTEST-DECOMP:: G129 (18 variables)\nT-d    : 43 nodes 1 leaves 6644 minterms\nT-d SS : 44 nodes\nT-d GS : 4 nodes 1 leaves 163840 minterms\nT-d HS : 41 nodes 1 leaves 18932 minterms\nT-d SI : 43 nodes\nT-d GI : 43 nodes 1 leaves 6644 minterms\nT-d HI : 1 nodes 1 leaves 262144 minterms\nT-d SD : 49 nodes\nT-d GD : 32 nodes 1 leaves 76224 minterms\nT-d HD : 22 nodes 1 leaves 46336 minterms\nT-d SQ : 52 nodes\nT-d GQ : 38 nodes 1 leaves 136596 minterms\nT-d HQ : 38 nodes 1 leaves 132192 minterms\nTEST-DECOMP:: G130 (15 variables)\nT-d    : 28 nodes 1 leaves 1381 minterms\nT-d SS : 29 nodes\nT-d GS : 4 nodes 1 leaves 20480 minterms\nT-d HS : 26 nodes 1 leaves 4453 minterms\nT-d SI : 28 nodes\nT-d GI : 28 nodes 1 leaves 1381 minterms\nT-d HI : 1 nodes 1 leaves 32768 minterms\nT-d SD : 33 nodes\nT-d GD : 22 nodes 1 leaves 4560 minterms\nT-d HD : 12 nodes 1 leaves 10688 minterms\nT-d SQ : 36 nodes\nT-d GQ : 23 nodes 1 leaves 17608 minterms\nT-d HQ : 24 nodes 1 leaves 16541 minterms\nTEST-DECOMP:: G131 (12 variables)\nT-d    : 17 nodes 1 leaves 306 minterms\nT-d SS : 17 nodes\nT-d GS : 2 nodes 1 leaves 2048 minterms\nT-d HS : 16 nodes 1 leaves 612 minterms\nT-d SI : 17 nodes\nT-d GI : 2 nodes 1 leaves 2048 minterms\nT-d HI : 16 nodes 1 leaves 612 minterms\nT-d SD : 18 nodes\nT-d GD : 6 nodes 1 leaves 1280 minterms\nT-d HD : 14 nodes 1 leaves 912 minterms\nT-d SQ : 18 nodes\nT-d GQ : 15 nodes 1 leaves 2098 minterms\nT-d HQ : 5 nodes 1 leaves 2304 minterms\nTEST-DECOMP:: G132 (9 variables)\nT-d    : 10 nodes 1 leaves 71 minterms\nT-d SS : 10 nodes\nT-d GS : 3 nodes 1 leaves 128 minterms\nT-d HS : 8 nodes 1 leaves 284 minterms\nT-d SI : 10 nodes\nT-d GI : 3 nodes 1 leaves 128 minterms\nT-d HI : 8 nodes 1 leaves 284 minterms\nT-d SD : 10 nodes\nT-d GD : 8 nodes 1 leaves 284 minterms\nT-d HD : 3 nodes 1 leaves 128 minterms\nT-d SQ : 11 nodes\nT-d GQ : 10 nodes 1 leaves 263 minterms\nT-d HQ : 4 nodes 1 leaves 320 minterms\nG91: 73 nodes 4.72237e+21 minterms\nG94: 73 nodes 4.72237e+21 minterms\nG107: 72 nodes 1.18059e+21 minterms\nG83: 72 nodes 1.18059e+21 minterms\nG84: 72 nodes 1.18059e+21 minterms\nG85: 72 nodes 1.18059e+21 minterms\nG100BF: 75 nodes 8.26414e+21 minterms\nG98BF: 81 nodes 8.26414e+21 minterms\nG96BF: 137 nodes 8.26414e+21 minterms\nG92: 73 nodes 5.90296e+20 minterms\nG87BF: 115 nodes 7.74763e+21 minterms\nG89BF: 83 nodes 7.74763e+21 minterms\nG101BF: 97 nodes 9.02046e+21 minterms\nG106BF: 104 nodes 8.13501e+21 minterms\nG97BF: 132 nodes 9.02046e+21 minterms\nG104BF: 141 nodes 8.13501e+21 minterms\nG88BF: 123 nodes 6.57626e+21 minterms\nG99BF: 152 nodes 8.72762e+21 minterms\nG105BF: 150 nodes 8.06353e+21 minterms\nG86BF: 230 nodes 6.30792e+21 minterms\nG95BF: 240 nodes 8.66053e+21 minterms\nG103BF: 236 nodes 8.05179e+21 minterms\nG90: 286 nodes 2.3211e+21 minterms\nG380: 203 nodes 2.78589e+21 minterms\nG262: 134 nodes 3.98046e+20 minterms\nG394: 118 nodes 2.7624e+21 minterms\nG250: 78 nodes 1.30972e+21 minterms\nG122: 78 nodes 8.4855e+20 minterms\nG133: 142 nodes 3.0783e+21 minterms\nG138: 143 nodes 7.44211e+21 minterms\nG139: 125 nodes 2.78546e+21 minterms\nG140: 126 nodes 7.29569e+21 minterms\nG141: 260 nodes 3.14539e+21 minterms\nG142: 244 nodes 7.47565e+21 minterms\nG125: 304 nodes 2.08921e+21 minterms\nG126: 272 nodes 1.97936e+21 minterms\nG127: 290 nodes 2.06572e+21 minterms\nG128: 271 nodes 2.0237e+21 minterms\nG129: 180 nodes 2.39375e+20 minterms\nG130: 134 nodes 3.98046e+20 minterms\nG131: 106 nodes 7.05588e+20 minterms\nG132: 78 nodes 1.30972e+21 minterms\nG91: 1 nodes 1 minterms\nG94: 1 nodes 1 minterms\nG107: 3 nodes 1 minterms\nG83: 3 nodes 1 minterms\nG84: 3 nodes 1 minterms\nG85: 3 nodes 1 minterms\nG100BF: 3 nodes 3 minterms\nG98BF: 3 nodes 3 minterms\nG96BF: 3 nodes 3 minterms\nG92: 4 nodes 1 minterms\nG87BF: 7 nodes 4 minterms\nG89BF: 7 nodes 4 minterms\nG101BF: 9 nodes 6 minterms\nG106BF: 9 nodes 6 minterms\nG97BF: 9 nodes 6 minterms\nG104BF: 9 nodes 6 minterms\nG88BF: 11 nodes 7 minterms\nG99BF: 13 nodes 9 minterms\nG105BF: 13 nodes 9 minterms\nG86BF: 43 nodes 57 minterms\nG95BF: 45 nodes 59 minterms\nG103BF: 36 nodes 59 minterms\nG90: 52 nodes 35 minterms\nG380: 30 nodes 14 minterms\nG262: 41 nodes 25 minterms\nG394: 14 nodes 9 minterms\nG250: 9 nodes 4 minterms\nG122: 10 nodes 4 minterms\nG133: 28 nodes 18 minterms\nG138: 17 nodes 13 minterms\nG139: 17 nodes 8 minterms\nG140: 10 nodes 6 minterms\nG141: 80 nodes 75 minterms\nG142: 34 nodes 20 minterms\nG125: 97 nodes 110 minterms\nG126: 68 nodes 63 minterms\nG127: 84 nodes 105 minterms\nG128: 74 nodes 63 minterms\nG129: 61 nodes 55 minterms\nG130: 41 nodes 25 minterms\nG131: 20 nodes 8 minterms\nG132: 9 nodes 4 minterms\n**** CUDD modifiable parameters ****\nHard limit for cache size: 2796202\nCache hit threshold for resizing: 30%\nGarbage collection enabled: yes\nLimit for fast unique table growth: 1677721\nMaximum number of variables sifted per reordering: 1000\nMaximum number of variable swaps per reordering: 2000000\nMaximum growth while sifting a variable: 1.2\nDynamic reordering of BDDs enabled: yes\nDefault BDD reordering method: 14\nDynamic reordering of ZDDs enabled: yes\nDefault ZDD reordering method: 4\nRealignment of ZDDs to BDDs enabled: yes\nRealignment of BDDs to ZDDs enabled: no\nDead nodes counted in triggering reordering: no\nGroup checking criterion: 7\nRecombination threshold: 0\nSymmetry violation threshold: 10\nArc violation threshold: 10\nGA population size: 0\nNumber of crossovers for GA: 0\nNext reordering threshold: 5060\n**** CUDD non-modifiable parameters ****\nMemory in use: 5183736\nPeak number of nodes: 16352\nPeak number of live nodes: 4984\nNumber of BDD variables: 73\nNumber of ZDD variables: 146\nNumber of cache entries: 65536\nNumber of cache look-ups: 102052\nNumber of cache hits: 38879\nNumber of cache insertions: 65143\nNumber of cache collisions: 11005\nNumber of cache deletions: 40310\nCache used slots = 21.10% (expected 21.28%)\nSoft limit for cache size: 225280\nNumber of buckets in unique table: 56320\nUsed buckets in unique table: 6.69% (expected 6.75%)\nNumber of BDD and ADD nodes: 4289\nNumber of ZDD nodes: 1185\nNumber of dead BDD and ADD nodes: 3545\nNumber of dead ZDD nodes: 1039\nTotal number of nodes allocated: 38976\nTotal number of nodes reclaimed: 10413\nGarbage collections so far: 6\nTime for garbage collection: 0.00 sec\nReorderings so far: 5\nTime for reordering: 0.07 sec\nFinal size: 688\ntotal time = 0.10 sec\nRuntime Statistics\n------------------\nMachine name: crozzon\nUser time      0.1 seconds\nSystem time    0.0 seconds\n\nAverage resident text size       =     0K\nAverage resident data+stack size =     0K\nMaximum resident size            =  8276K\n\nVirtual memory limit             = unlimited (unlimited)\nMajor page faults = 0\nMinor page faults = 1540\nSwaps = 0\nInput blocks = 24\nOutput blocks = 88\nContext switch (voluntary) = 1\nContext switch (involuntary) = 1\n"
  },
  {
    "path": "cudd/nanotrav/test_ntrv.test.in",
    "content": "#! /bin/sh\n\n# A script to test nanotrav.\n# Each item in argslist corresponds to one run.\n\nEXE=@EXEEXT@\nsrcdir=@srcdir@\n\n# The separator IFS is set to a colon so that we can have spaces between\n# arguments.  Each entry consists of a model name and a list of arguments.\nOIFS=$IFS\nIFS=:\nargslist=\"\\\nC17,-cover:\\\nC880,-ordering dfs -autodyn -automethod sifting -reordering sifting -drop:\\\ns27,-ordering hw -reordering annealing -trav:\\\ns27b,-ordering dfs -reordering win4 -verify ${srcdir}/nanotrav/s27.blif:\\\ns27c,-trav -image depend -depend:\\\nmult32a,-autodyn -reordering sifting -trav:\\\ns382,-trav -image part -autodyn -automethod sifting -drop -scc -shortpaths bellman:\\\ns641,-trav -autodyn -automethod group -drop -clauses -density -decomp -zdd:\\\nclosest,-reordering genetic -drop -closest:\\\nadj49,-ordering dfs -reordering cogroup -drop -char2vect -cofest:\\\nham01,-reordering linear:\\\nminiFirst,-second ${srcdir}/nanotrav/miniSecond.blif:\\\nrcn25,-envelope\"\n\nverbosity=1\n\n# Discard statistics and remove CPU times.\nsed_command='-r:-e:2d:-e:/modifiable/,$d:-e:s/[0-9][0-9]*\\.?[0-9]* sec//:-e:s/[0-9][0-9]* recursive//'\n\necho TAP version 13\necho 1..13\nexitstatus=0\ncount=0\n\n# Create FIFOs for communication between sed processes and diff.\nmkfifo nanotrav/tst_fifo nanotrav/out_fifo\n# Create empty file.\n: > ./nanotrav/differences\n\nfor argres in $argslist\ndo\n    IFS=, # split model name from arguments\n    set -- $argres\n    IFS=:\n    echo \"# executing\" \"nanotrav/nanotrav$EXE -p $verbosity\" \\\n         \"$2 ${srcdir}/nanotrav/${1}.blif > ./nanotrav/${1}.tst\"\n    `eval \"nanotrav/nanotrav -p $verbosity $2 ${srcdir}/nanotrav/${1}.blif > ./nanotrav/${1}.tst\"`\n    failed=`expr $? != 0`\n    # If nanotrav completed successfully, compare this run's fitered output\n    # to the reference filtered output.\n    if test x$failed = x0; then\n        echo \"# comparing\" \"./nanotrav/${1}.tst to ${srcdir}/nanotrav/${1}.out\"\n        `sed ${sed_command} ./nanotrav/${1}.tst > nanotrav/tst_fifo &\\\n         sed ${sed_command} ${srcdir}/nanotrav/${1}.out > nanotrav/out_fifo &\\\n         diff -b nanotrav/tst_fifo nanotrav/out_fifo >> ./nanotrav/differences`\n        failed=`expr $? != 0`\n    fi\n    exitstatus=`expr $exitstatus + $failed`\n    count=`expr $count + 1`\n    if test x$failed = x0 ; then\n        echo \"ok $count $1\"\n    else\n        echo \"not ok $count $1\"\n    fi\ndone\n\n# Clean up and report.\nrm nanotrav/tst_fifo nanotrav/out_fifo\necho \"# $exitstatus failed sub-tests out of $count\"\nif test x$exitstatus = x0; then\n    rm ./nanotrav/differences\nelse\n    echo '# Check file \"./nanotrav/differences\"'\nfi\n# Restore internal field separator.\nIFS=$OIFS\n\nexit 0\n"
  },
  {
    "path": "cudd/st/Included.am",
    "content": "cudd_libcudd_la_SOURCES += st/st.h st/st.c\n\ncheck_PROGRAMS += st/testst\nst_testst_SOURCES = st/testst.c\nst_testst_CPPFLAGS = $(cudd_libcudd_la_CPPFLAGS)\nst_testst_LDADD = cudd/libcudd.la\n\ncheck_SCRIPTS += st/test_st.test\nEXTRA_DIST += st/test_st.test.in\nif !CROSS_COMPILING\nTESTS += st/test_st.test\nendif !CROSS_COMPILING\n\nst/test_st.test: st/test_st.test.in Makefile\n\t$(do_subst) $< > $@\n\tchmod +x $@\n"
  },
  {
    "path": "cudd/st/st.c",
    "content": "/**\n  @file\n\n  @ingroup st\n\n  @brief Symbol table package.\n\n  @details The st library provides functions to create, maintain,\n  and query symbol tables.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"st.h\"\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Type of symbol table entries.\n */     \ntypedef struct st_table_entry st_table_entry;\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Symbol table entry.\n */\nstruct st_table_entry {\n    void *key;\n    void *record;\n    st_table_entry *next;\n};\n\n/**\n * @brief Symbol table header.\n */\nstruct st_table {\n    st_compare_t compare;\n    st_hash_t hash;\n    st_compare_arg_t compare_arg;\n    st_hash_arg_t hash_arg;\n    void const * arg;\n    int num_bins;\n    int num_entries;\n    int max_density;\n    int reorder_flag;\n    double grow_factor;\n    st_table_entry **bins;\n};\n\n/**\n * @brief Symbol table generator.\n */\nstruct st_generator {\n    st_table const *table;\n    st_table_entry const *entry;\n    int index;\n};\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Compares two numbers or two pointers.\n *\n * @details Used by the default comparison functions.\n */\n#define ST_NUMCMP(x,y) ((x) != (y))\n\n/**\n * @brief Hash function for numbers.\n */\n#define ST_NUMHASH(x,size) ((int)((uintptr_t)(x)%(uintptr_t)(size)))\n\n/**\n * @brief Amount by which pointers should be shifted right when hashing.\n *\n * @details This is to discard bits that are (likely to be) 0 due to\n * alignment constraints.\n */\n#if SIZEOF_VOID_P == 8\n#define st_shift 3\n#else\n#define st_shift 2\n#endif\n\n/**\n * @brief Hash function for pointers.\n */\n#define ST_PTRHASH(x,size) ((int)(((uintptr_t)(x)>>st_shift)%(uintptr_t)(size)))\n\n/**\n * @brief Compares two entries.\n */\n#define EQUAL(table, x, y) \\\n    ((((table)->compare == st_numcmp) || ((table)->compare == st_ptrcmp)) ?\\\n     (ST_NUMCMP((x),(y)) == 0) : ((table)->compare) ?\\\n     ((*(table)->compare)((x), (y)) == 0) :\\\n     ((*(table)->compare_arg)((x), (y), (table)->arg) == 0))\n\n/**\n * @brief Computes the hash of one entry.\n */\n#define do_hash(key, table)\\\n    (((table)->hash == st_ptrhash) ? ST_PTRHASH((key), (table)->num_bins) : \\\n     ((table)->hash == st_numhash) ? ST_NUMHASH((key), (table)->num_bins) : \\\n     ((table)->hash) ? (*(table)->hash)((key), (table)->num_bins) : \\\n     (*(table)->hash_arg)((key), (table)->num_bins, (table)->arg))\n\n/**\n * @brief Compares the new key to one in a collision list.\n */\n#define PTR_NOT_EQUAL(table, ptr, user_key)\\\n    ((ptr) != NIL(st_table_entry) && \\\n     !EQUAL((table), (user_key), (ptr)->key))\n\n/**\n * @brief Looks up an entry in a collision list.\n *\n * @details If the entry is found and the reorder flag is set, the found\n * entry is brought to the fore of the collision list.\n */\n#define FIND_ENTRY(table, hash_val, key, ptr, last) \\\n    (last) = &(table)->bins[hash_val];\\\n    (ptr) = *(last);\\\n    while (PTR_NOT_EQUAL((table), (ptr), (key))) {\\\n\t(last) = &(ptr)->next; (ptr) = *(last);\\\n    }\\\n    if ((ptr) != NIL(st_table_entry) && (table)->reorder_flag) {\\\n\t*(last) = (ptr)->next;\\\n\t(ptr)->next = (table)->bins[hash_val];\\\n\t(table)->bins[hash_val] = (ptr);\\\n    }\n\n/**\n * @brief Adds an entry to a table.\n *\n * @deprecated This macro does not check if memory allocation fails.\n * Use at your own risk.\n */\n#define ADD_DIRECT(table, key, value, hash_val, newt)\\\n{\\\n    if (table->num_entries/table->num_bins >= table->max_density) {\\\n\trehash(table);\\\n\thash_val = do_hash(key,table);\\\n    }\\\n    \\\n    newt = ALLOC(st_table_entry, 1);\\\n    \\\n    newt->key = key;\\\n    newt->record = value;\\\n    newt->next = table->bins[hash_val];\\\n    table->bins[hash_val] = newt;\\\n    table->num_entries++;\\\n}\n\n/** \\cond */\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\nstatic int rehash (st_table *);\n\n/** \\endcond */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Creates and initializes a table.\n\n  @details Creates and initializes a table with the comparison function\n  compare_fn and hash function hash_fn. compare_fn is\n\n      int compare_fn(const void *key1, const void *key2)\n\n  It returns `<,=,> 0` depending on whether `key1 <,=,> key2` by some\n  measure.<p>\n  hash_fn is\n\n      int hash_fn(void *key, int modulus)\n\n  It returns an integer between `0` and `modulus-1` such that if\n  `compare_fn(key1,key2) == 0` then `hash_fn(key1) == hash_fn(key2)`.<p>\n  There are five predefined hash and comparison functions in st.\n  For keys as numbers:\n\n      st_numhash(key, modulus) { return (unsigned int) key % modulus; }\n      st_numcmp(x,y) { return (int) x - (int) y; }\n\n  For keys as pointers:\n\n      st_ptrhash(key, modulus) { return ((unsigned int) key/4) % modulus }\n      st_ptrcmp(x,y) { return (int) x - (int) y; }\n\n  For keys as strings:\n\n      st_strhash(x,y) - a reasonable hashing function for strings\n      strcmp(x,y) - the standard library function\n\n  It is recommended to use these particular functions if they fit your\n  needs, since st will recognize certain of them and run more quickly\n  because of it.\n\n  @sideeffect None\n\n  @see st_init_table_with_params st_free_table\n\n*/\nst_table *\nst_init_table(st_compare_t compare, st_hash_t hash)\n{\n    return st_init_table_with_params(compare, hash, ST_DEFAULT_INIT_TABLE_SIZE,\n\t\t\t\t     ST_DEFAULT_MAX_DENSITY,\n\t\t\t\t     ST_DEFAULT_GROW_FACTOR,\n\t\t\t\t     ST_DEFAULT_REORDER_FLAG);\n\n} /* st_init_table */\n\n\n/**\n  @brief Create a table with given parameters.\n\n  @details The full blown table initializer.  compare and hash are\n  the same as in st_init_table. density is the largest the average\n  number of entries per hash bin there should be before the table is\n  grown.  grow_factor is the factor the table is grown by when it\n  becomes too full. size is the initial number of bins to be allocated\n  for the hash table.  If reorder_flag is non-zero, then every time an\n  entry is found, it is moved to the top of the chain.<p>\n  st_init_table(compare, hash) is equivelent to\n\n      st_init_table_with_params(compare, hash, ST_DEFAULT_INIT_TABLE_SIZE,\n                                ST_DEFAULT_MAX_DENSITY, ST_DEFAULT_GROW_FACTOR,\n                                ST_DEFAULT_REORDER_FLAG);\n\n  @sideeffect None\n\n  @see st_init_table st_free_table\n\n*/\nst_table *\nst_init_table_with_params(\n  st_compare_t compare,\n  st_hash_t hash,\n  int size,\n  int density,\n  double grow_factor,\n  int reorder_flag)\n{\n    int i;\n    st_table *newt;\n\n    newt = ALLOC(st_table, 1);\n    if (newt == NIL(st_table)) {\n\treturn NIL(st_table);\n    }\n    newt->compare = compare;\n    newt->hash = hash;\n    newt->compare_arg = (st_compare_arg_t) 0;\n    newt->hash_arg = (st_hash_arg_t) 0;\n    newt->arg = NIL(void);\n    newt->num_entries = 0;\n    newt->max_density = density;\n    newt->grow_factor = grow_factor;\n    newt->reorder_flag = reorder_flag;\n    if (size <= 0) {\n\tsize = 1;\n    }\n    newt->num_bins = size;\n    newt->bins = ALLOC(st_table_entry *, size);\n    if (newt->bins == NIL(st_table_entry *)) {\n\tFREE(newt);\n\treturn NIL(st_table);\n    }\n    for(i = 0; i < size; i++) {\n\tnewt->bins[i] = 0;\n    }\n    return newt;\n\n} /* st_init_table_with_params */\n\n\n/**\n   @brief Creates and initializes a table.\n\n   @details Like st_init_table_with_params, but the comparison and\n   hash functions are passed an extra parameter `arg` that is\n   registered in the table at initialization.\n\n   @see st_init_table_with_params\n*/\nst_table *\nst_init_table_with_params_and_arg(\n  st_compare_arg_t compare,\n  st_hash_arg_t hash,\n  void const * arg,\n  int size,\n  int density,\n  double growth_factor,\n  int reorder_flag)\n{\n    st_table *table;\n\n    table = st_init_table_with_params((st_compare_t) 0, (st_hash_t) 0, size,\n                                      density, growth_factor, reorder_flag);\n    if (table == NIL(st_table))\n        return NIL(st_table);\n    table->compare_arg = compare;\n    table->hash_arg = hash;\n    table->arg = arg;\n\n    return table;\n\n} /* st_init_table_with_params_and_arg */\n\n\n/**\n   @brief Creates and initializes a table.\n\n   @details Like st_init_table, but the comparison and hash functions are\n   passed an extra parameter `arg` that is registered in the table at\n   initialization.\n\n   @see st_init_table st_init_table_with_params_and_arg\n*/\nst_table *\nst_init_table_with_arg(\n  st_compare_arg_t compare,\n  st_hash_arg_t hash,\n  void const * arg)\n{\n    return st_init_table_with_params_and_arg(compare, hash, arg,\n                                             ST_DEFAULT_INIT_TABLE_SIZE,\n                                             ST_DEFAULT_MAX_DENSITY,\n                                             ST_DEFAULT_GROW_FACTOR,\n                                             ST_DEFAULT_REORDER_FLAG);\n\n} /* st_init_table_with_arg */\n\n\n/**\n  @brief Free a table.\n\n  @details Any internal storage associated with table is freed.  It is\n  the user's responsibility to free any storage associated with the\n  pointers he placed in the table (by perhaps using st_foreach).\n\n  @sideeffect None\n\n  @see st_init_table st_init_table_with_params\n\n*/\nvoid\nst_free_table(st_table *table)\n{\n    st_table_entry *ptr, *next;\n    int i;\n\n    for(i = 0; i < table->num_bins ; i++) {\n\tptr = table->bins[i];\n\twhile (ptr != NIL(st_table_entry)) {\n\t    next = ptr->next;\n\t    FREE(ptr);\n\t    ptr = next;\n\t}\n    }\n    FREE(table->bins);\n    FREE(table);\n\n} /* st_free_table */\n\n\n/**\n  @brief Lookup up `key` in `table`.\n\n  @details If an entry is found, 1 is returned and if `value` is not\n  nil, the variable it points to is set to the associated value.  If\n  an entry is not found, 0 is returned and the variable pointed by\n  value is unchanged.\n\n  @sideeffect The location pointed by value is modified.\n\n  @see st_lookup_int\n\n*/\nint\nst_lookup(st_table *table, void const *key, void **value)\n{\n    int hash_val;\n    st_table_entry *ptr, **last;\n\n    hash_val = do_hash(key, table);\n\n    FIND_ENTRY(table, hash_val, key, ptr, last);\n\n    if (ptr == NIL(st_table_entry)) {\n\treturn 0;\n    } else {\n\tif (value != NIL(void *)) {\n\t    *value = ptr->record;\n\t}\n\treturn 1;\n    }\n\n} /* st_lookup */\n\n\n/**\n  @brief Lookup up `key` in `table`.\n\n  @details If an entry is found, 1 is returned and if `value` is not\n  nil, the variable it points to is set to the associated integer\n  value.  If an entry is not found, 0 is return and the variable\n  pointed by `value` is unchanged.\n\n  @sideeffect The location pointed by value is modified.\n\n  @see st_lookup\n\n*/\nint\nst_lookup_int(st_table *table, void const *key, int *value)\n{\n    int hash_val;\n    st_table_entry *ptr, **last;\n\n    hash_val = do_hash(key, table);\n\n    FIND_ENTRY(table, hash_val, key, ptr, last);\n    \n    if (ptr == NIL(st_table_entry)) {\n\treturn 0;\n    } else {\n\tif (value != NIL(int)) {\n\t    *value = (int) (intptr_t) ptr->record;\n\t}\n\treturn 1;\n    }\n\n} /* st_lookup_int */\n\n\n/**\n  @brief Insert value in `table` under the key `key`.\n\n  @return 1 if there was an entry already under the key; 0 if there\n  was no entry under the key and insertion was successful;\n  ST_OUT_OF_MEM otherwise.  In either of the first two cases the new\n  value is added.\n\n  @sideeffect None\n\n*/\nint\nst_insert(st_table *table, void *key, void *value)\n{\n    int hash_val;\n    st_table_entry *newt;\n    st_table_entry *ptr, **last;\n\n    hash_val = do_hash(key, table);\n\n    FIND_ENTRY(table, hash_val, key, ptr, last);\n\n    if (ptr == NIL(st_table_entry)) {\n\tif (table->num_entries/table->num_bins >= table->max_density) {\n\t    if (rehash(table) == ST_OUT_OF_MEM) {\n\t\treturn ST_OUT_OF_MEM;\n\t    }\n\t    hash_val = do_hash(key, table);\n\t}\n\tnewt = ALLOC(st_table_entry, 1);\n\tif (newt == NIL(st_table_entry)) {\n\t    return ST_OUT_OF_MEM;\n\t}\n\tnewt->key = key;\n\tnewt->record = value;\n\tnewt->next = table->bins[hash_val];\n\ttable->bins[hash_val] = newt;\n\ttable->num_entries++;\n\treturn 0;\n    } else {\n\tptr->record = value;\n\treturn 1;\n    }\n\n} /* st_insert */\n\n\n/**\n  @brief Place 'value' in 'table' under the key 'key'.\n\n  @details This is done without checking if 'key' is in 'table'\n  already.  This should only be used if you are sure there is not\n  already an entry for 'key', since it is undefined which entry you\n  would later get from st_lookup or st_find_or_add.\n\n  @return 1 if successful; ST_OUT_OF_MEM otherwise.\n\n  @sideeffect None\n\n  @see st_lookup st_find_or_add\n\n*/\nint\nst_add_direct(st_table *table, void *key, void *value)\n{\n    int hash_val;\n    st_table_entry *newt;\n\n    if (table->num_entries / table->num_bins >= table->max_density) {\n\tif (rehash(table) == ST_OUT_OF_MEM) {\n\t    return ST_OUT_OF_MEM;\n\t}\n    }\n    hash_val = do_hash(key, table);\n    newt = ALLOC(st_table_entry, 1);\n    if (newt == NIL(st_table_entry)) {\n\treturn ST_OUT_OF_MEM;\n    }\n    newt->key = key;\n    newt->record = value;\n    newt->next = table->bins[hash_val];\n    table->bins[hash_val] = newt;\n    table->num_entries++;\n    return 1;\n\n} /* st_add_direct */\n\n\n/**\n  @brief Lookup `key` in `table`; if not found, create an entry.\n\n  @details In either case set slot to point to the field in the entry\n  where the value is stored.  The value associated with `key` may then\n  be changed by accessing directly through slot.  As an example:\n\n      void **slot;\n      void *key;\n      void *value = item_ptr // ptr to a malloc'd structure\n\n      if (st_find_or_add(table, key, &slot) == 1) {\n          FREE(*slot); // free the old value of the record\n      }\n      *slot = value;  // attach the new value to the record\n\n  This replaces the equivelent code:\n\n      if (st_lookup(table, key, &ovalue) == 1) {\n          FREE(ovalue);\n      }\n      st_insert(table, key, value);\n\n  @return 1 if an entry already existed, 0 if it did not exist and\n  creation was successful; ST_OUT_OF_MEM otherwise.\n\n  @sideeffect The location pointed by slot is modified.\n\n  @see st_find\n\n*/\nint\nst_find_or_add(st_table *table, void *key, void ***slot)\n{\n    int hash_val;\n    st_table_entry *newt, *ptr, **last;\n\n    hash_val = do_hash(key, table);\n\n    FIND_ENTRY(table, hash_val, key, ptr, last);\n\n    if (ptr == NIL(st_table_entry)) {\n\tif (table->num_entries / table->num_bins >= table->max_density) {\n\t    if (rehash(table) == ST_OUT_OF_MEM) {\n\t\treturn ST_OUT_OF_MEM;\n\t    }\n\t    hash_val = do_hash(key, table);\n\t}\n\tnewt = ALLOC(st_table_entry, 1);\n\tif (newt == NIL(st_table_entry)) {\n\t    return ST_OUT_OF_MEM;\n\t}\n\tnewt->key = key;\n\tnewt->record = NIL(void);\n\tnewt->next = table->bins[hash_val];\n\ttable->bins[hash_val] = newt;\n\ttable->num_entries++;\n\tif (slot != NIL(void **)) *slot = &newt->record;\n\treturn 0;\n    } else {\n\tif (slot != NIL(void **)) *slot = &ptr->record;\n\treturn 1;\n    }\n\n} /* st_find_or_add */\n\n\n/**\n  @brief Lookup `key` in `table`.\n\n  @details Like st_find_or_add, but does not create an entry if one is\n  not found.\n\n  @sideeffect The location pointed by slot is modified.\n\n  @see st_find_or_add\n\n*/\nint\nst_find(st_table *table, void const *key, void ***slot)\n{\n    int hash_val;\n    st_table_entry *ptr, **last;\n\n    hash_val = do_hash(key, table);\n\n    FIND_ENTRY(table, hash_val, key, ptr, last);\n\n    if (ptr == NIL(st_table_entry)) {\n\treturn 0;\n    } else {\n\tif (slot != NIL(void **)) {\n\t    *slot = &ptr->record;\n\t}\n\treturn 1;\n    }\n\n} /* st_find */\n\n\n/**\n  @brief Returns a copy of old_table and all its members.\n\n  @details (st_table *) 0 is returned if there was insufficient memory\n  to do the copy.\n\n  @sideeffect None\n\n*/\nst_table *\nst_copy\n(st_table const *old_table)\n{\n    st_table *new_table;\n    st_table_entry *ptr, *newptr, *next, *newt;\n    int i, j, num_bins = old_table->num_bins;\n\n    new_table = ALLOC(st_table, 1);\n    if (new_table == NIL(st_table)) {\n\treturn NIL(st_table);\n    }\n\n    *new_table = *old_table;\n    new_table->bins = ALLOC(st_table_entry *, num_bins);\n    if (new_table->bins == NIL(st_table_entry *)) {\n\tFREE(new_table);\n\treturn NIL(st_table);\n    }\n    for(i = 0; i < num_bins ; i++) {\n\tnew_table->bins[i] = NIL(st_table_entry);\n\tptr = old_table->bins[i];\n\twhile (ptr != NIL(st_table_entry)) {\n\t    newt = ALLOC(st_table_entry, 1);\n\t    if (newt == NIL(st_table_entry)) {\n\t\tfor (j = 0; j <= i; j++) {\n\t\t    newptr = new_table->bins[j];\n\t\t    while (newptr != NIL(st_table_entry)) {\n\t\t\tnext = newptr->next;\n\t\t\tFREE(newptr);\n\t\t\tnewptr = next;\n\t\t    }\n\t\t}\n\t\tFREE(new_table->bins);\n\t\tFREE(new_table);\n\t\treturn NIL(st_table);\n\t    }\n\t    *newt = *ptr;\n\t    newt->next = new_table->bins[i];\n\t    new_table->bins[i] = newt;\n\t    ptr = ptr->next;\n\t}\n    }\n    return new_table;\n\n} /* st_copy */\n\n\n/**\n  @brief Deletes the entry with the key pointed to by `keyp`.\n\n  @details If the entry is found, 1 is returned, the variable pointed\n  by `keyp` is set to the actual key and the variable pointed by\n  `value` is set to the corresponding entry.  (This allows the freeing\n  of the associated storage.)  If the entry is not found, then 0 is\n  returned and nothing is changed.\n\n  @sideeffect The locations pointed by keyp and value are modified.\n\n  @see st_delete_int\n\n*/\nint\nst_delete(st_table *table, void **keyp, void **value)\n{\n    int hash_val;\n    void *key = *keyp;\n    st_table_entry *ptr, **last;\n\n    hash_val = do_hash(key, table);\n\n    FIND_ENTRY(table, hash_val, key, ptr ,last);\n\n    if (ptr == NIL(st_table_entry)) {\n\treturn 0;\n    }\n\n    *last = ptr->next;\n    if (value != NIL(void *)) *value = ptr->record;\n    *keyp = ptr->key;\n    FREE(ptr);\n    table->num_entries--;\n    return 1;\n\n} /* st_delete */\n\n\n/**\n  @brief Deletes the entry with the key pointed to by `keyp`.\n\n  @details `value` must be a pointer to an integer.  If the entry is\n  found, 1 is returned, the variable pointed by `keyp` is set to the\n  actual key and the variable pointed by `value` is set to the\n  corresponding entry.  (This allows the freeing of the associated\n  storage.) If the entry is not found, then 0 is returned and nothing\n  is changed.\n\n  @sideeffect The locations pointed by keyp and value are modified.\n\n  @see st_delete\n\n*/\nint\nst_delete_int(st_table *table, void **keyp, int *value)\n{\n    int hash_val;\n    void *key = *keyp;\n    st_table_entry *ptr, **last;\n\n    hash_val = do_hash(key, table);\n\n    FIND_ENTRY(table, hash_val, key, ptr ,last);\n\n    if (ptr == NIL(st_table_entry)) {\n        return 0;\n    }\n\n    *last = ptr->next;\n    if (value != NIL(int)) *value = (int) (intptr_t) ptr->record;\n    *keyp = ptr->key;\n    FREE(ptr);\n    table->num_entries--;\n    return 1;\n\n} /* st_delete_int */\n\n\n/**\n  @brief Returns the number of entries in the table `table`.\n\n  @sideeffect None\n\n*/\nint st_count(st_table const *table)\n{\n  return table->num_entries;\n}\n\n\n/**\n  @brief Iterates over the elements of a table.\n\n  @details\n  For each (key, value) record in `table`, st_foreach\n  calls func with the arguments\n\n      (*func)(key, value, arg)\n\n  If func returns ST_CONTINUE, st_foreach continues\n  processing entries.  If func returns ST_STOP, st_foreach stops\n  processing and returns immediately.  If func returns ST_DELETE, then\n  the entry is deleted from the symbol table and st_foreach continues.\n  In the case of ST_DELETE, it is func's responsibility to free the\n  key and value, if necessary.  The order in which the records are\n  visited will be seemingly random.\n\n  @return 1 if all items in the table were generated and 0 if the\n  generation sequence was aborted using ST_STOP.\n\n  @sideeffect None\n\n  @see st_foreach_item st_foreach_item_int\n\n*/\nint\nst_foreach(st_table *table, st_foreach_t func, void *arg)\n{\n    st_table_entry *ptr, **last;\n    enum st_retval retval;\n    int i;\n\n    for(i = 0; i < table->num_bins; i++) {\n\tlast = &table->bins[i]; ptr = *last;\n\twhile (ptr != NIL(st_table_entry)) {\n\t    retval = (*func)(ptr->key, ptr->record, arg);\n\t    switch (retval) {\n\t    case ST_CONTINUE:\n\t\tlast = &ptr->next; ptr = *last;\n\t\tbreak;\n\t    case ST_STOP:\n\t\treturn 0;\n\t    case ST_DELETE:\n\t\t*last = ptr->next;\n\t\ttable->num_entries--;\t/* cstevens@ic */\n\t\tFREE(ptr);\n\t\tptr = *last;\n\t    }\n\t}\n    }\n    return 1;\n\n} /* st_foreach */\n\n\n/**\n  @brief String hash function.\n\n  @sideeffect None\n\n  @see st_init_table\n\n*/\nint\nst_strhash(void const *string, int modulus)\n{\n    int val = 0;\n    int c;\n    char const * s = (char const *) string;\n    \n    while ((c = *s++) != '\\0') {\n\tval = val*997 + c;\n    }\n\n    return ((val < 0) ? -val : val)%modulus;\n\n} /* st_strhash */\n\n\n/**\n  @brief Integral number hash function.\n\n  @sideeffect None\n\n  @see st_init_table st_numcmp\n\n*/\nint\nst_numhash(void const *x, int size)\n{\n    return ST_NUMHASH(x, size);\n\n} /* st_numhash */\n\n\n/**\n  @brief Pointer hash function.\n\n  @sideeffect None\n\n  @see st_init_table st_ptrcmp\n\n*/\nint\nst_ptrhash(void const *x, int size)\n{\n    return ST_PTRHASH(x, size);\n\n} /* st_ptrhash */\n\n\n/**\n  @brief Integral number comparison function.\n\n  @sideeffect None\n\n  @see st_init_table st_numhash\n\n*/\nint\nst_numcmp(void const *x, void const *y)\n{\n    return ST_NUMCMP(x, y);\n\n} /* st_numcmp */\n\n\n/**\n  @brief Pointer comparison function.\n\n  @sideeffect None\n\n  @see st_init_table st_ptrhash\n\n*/\nint\nst_ptrcmp(void const *x, void const *y)\n{\n    return ST_NUMCMP(x, y);\n\n} /* st_ptrcmp */\n\n\n/**\n  @brief Initializes a generator.\n\n  @details Returns a generator handle which when used with\n  st_gen() will progressively return each (key, value) record in\n  `table`.\n\n  @sideeffect None\n\n  @see st_free_gen\n\n*/\nst_generator *\nst_init_gen(st_table const *table)\n{\n    st_generator *gen;\n\n    gen = ALLOC(st_generator, 1);\n    if (gen == NIL(st_generator)) {\n\treturn NIL(st_generator);\n    }\n    gen->table = table;\n    gen->entry = NIL(st_table_entry);\n    gen->index = 0;\n    return gen;\n\n} /* st_init_gen */\n\n\n/**\n  @brief Returns the next (key, value) pair in the generation sequence.\n\n  @details@parblock\n  Given a generator returned by st_init_gen(), this\n  routine returns the next (key, value) pair in the generation\n  sequence.  The pointer `value_p` can be zero which means no value\n  will be returned.  When there are no more items in the generation\n  sequence, the routine returns 0.\n\n  While using a generation sequence, deleting any (key, value) pair\n  other than the one just generated may cause a fatal error when\n  st_gen() is called later in the sequence and is therefore not\n  recommended.\n  @endparblock\n\n  @sideeffect The locations pointed by key_p and value_p are modified.\n\n  @see st_gen_int\n\n*/\nint\nst_gen(st_generator *gen, void **key_p, void **value_p)\n{\n    int i;\n\n    if (gen->entry == NIL(st_table_entry)) {\n\t/* try to find next entry */\n\tfor(i = gen->index; i < gen->table->num_bins; i++) {\n\t    if (gen->table->bins[i] != NIL(st_table_entry)) {\n\t\tgen->index = i+1;\n\t\tgen->entry = gen->table->bins[i];\n\t\tbreak;\n\t    }\n\t}\n\tif (gen->entry == NIL(st_table_entry)) {\n\t    return 0;\t\t/* that's all folks ! */\n\t}\n    }\n    *key_p = gen->entry->key;\n    if (value_p != NIL(void *)) {\n\t*value_p = gen->entry->record;\n    }\n    gen->entry = gen->entry->next;\n    return 1;\n\n} /* st_gen */\n\n\n/**\n  @brief Returns the next (key, value) pair in the generation\n  sequence.\n\n  @details Given a generator returned by st_init_gen(), this\n  routine returns the next (key, value) pair in the generation\n  sequence.  `value_p` must be a pointer to an integer.  The pointer\n  `value_p` can be zero which means no value will be returned.  When\n  there are no more items in the generation sequence, the routine\n  returns 0.\n\n  @sideeffect The locations pointed by key_p and value_p are modified.\n\n  @see st_gen\n\n*/\nint \nst_gen_int(st_generator *gen, void **key_p, int *value_p)\n{\n    int i;\n\n    if (gen->entry == NIL(st_table_entry)) {\n\t/* try to find next entry */\n\tfor(i = gen->index; i < gen->table->num_bins; i++) {\n\t    if (gen->table->bins[i] != NIL(st_table_entry)) {\n\t\tgen->index = i+1;\n\t\tgen->entry = gen->table->bins[i];\n\t\tbreak;\n\t    }\n\t}\n\tif (gen->entry == NIL(st_table_entry)) {\n\t    return 0;\t\t/* that's all folks ! */\n\t}\n    }\n    *key_p = gen->entry->key;\n    if (value_p != NIL(int)) {\n   \t*value_p = (int) (intptr_t) gen->entry->record;\n    }\n    gen->entry = gen->entry->next;\n    return 1;\n\n} /* st_gen_int */\n\n\n/**\n  @brief Reclaims the resources associated with `gen`.\n\n  @details After generating all items in a generation sequence,\n  this routine must be called to reclaim the resources associated with\n  `gen`.\n\n  @sideeffect None\n\n  @see st_init_gen\n\n*/\nvoid\nst_free_gen(st_generator *gen)\n{\n    FREE(gen);\n\n} /* st_free_gen */\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of internal functions                                          */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Rehashes a symbol table.\n\n  @sideeffect None\n\n  @see st_insert\n\n*/\nstatic int\nrehash(st_table *table)\n{\n    st_table_entry *ptr, *next, **old_bins;\n    int             i, old_num_bins, hash_val, old_num_entries;\n\n    /* save old values */\n    old_bins = table->bins;\n    old_num_bins = table->num_bins;\n    old_num_entries = table->num_entries;\n\n    /* rehash */\n    table->num_bins = (int) (table->grow_factor * old_num_bins);\n    if (table->num_bins % 2 == 0) {\n\ttable->num_bins += 1;\n    }\n    table->num_entries = 0;\n    table->bins = ALLOC(st_table_entry *, table->num_bins);\n    if (table->bins == NIL(st_table_entry *)) {\n\ttable->bins = old_bins;\n\ttable->num_bins = old_num_bins;\n\ttable->num_entries = old_num_entries;\n\treturn ST_OUT_OF_MEM;\n    }\n    /* initialize */\n    for (i = 0; i < table->num_bins; i++) {\n\ttable->bins[i] = 0;\n    }\n\n    /* copy data over */\n    for (i = 0; i < old_num_bins; i++) {\n\tptr = old_bins[i];\n\twhile (ptr != NIL(st_table_entry)) {\n\t    next = ptr->next;\n\t    hash_val = do_hash(ptr->key, table);\n\t    ptr->next = table->bins[hash_val];\n\t    table->bins[hash_val] = ptr;\n\t    table->num_entries++;\n\t    ptr = next;\n\t}\n    }\n    FREE(old_bins);\n\n    return 1;\n\n} /* rehash */\n"
  },
  {
    "path": "cudd/st/st.h",
    "content": "/**\n  @file \n\n  @ingroup st\n\n  @brief Symbol table package.\n\n  @details The st library provides functions to create, maintain,\n  and query symbol tables.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#ifndef ST_H_\n#define ST_H_\n\n/*---------------------------------------------------------------------------*/\n/* Nested includes                                                           */\n/*---------------------------------------------------------------------------*/\n\n/*---------------------------------------------------------------------------*/\n/* Constant declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Value returned if memory is exhausted.\n */\n#define ST_OUT_OF_MEM -10000\n\n/**\n * @brief Default value for the maximum table density.\n * @see st_init_table_with_params\n */\n#define ST_DEFAULT_MAX_DENSITY 5\n\n/**\n * @brief Default value for the initial table size.\n * @see st_init_table_with_params\n */\n#define ST_DEFAULT_INIT_TABLE_SIZE 11\n\n/**\n * @brief Default table growth factor.\n * @see st_init_table_with_params\n */\n#define ST_DEFAULT_GROW_FACTOR 2.0\n\n/**\n * @brief Default table reorder flag.\n * @see st_init_table_with_params\n */\n#define ST_DEFAULT_REORDER_FLAG 0\n\n/*---------------------------------------------------------------------------*/\n/* Stucture declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Type of symbol tables.\n */\ntypedef struct st_table st_table;\n\n/**\n * @brief Type of symbol table generators.\n */\ntypedef struct st_generator st_generator;\n\n/**\n * @brief Type of return values for iterators.\n */\nenum st_retval {ST_CONTINUE, ST_STOP, ST_DELETE};\n\n/**\n *  @brief Type for function passed to @ref st_foreach.\n */\ntypedef enum st_retval (*st_foreach_t)(void *, void *, void *);\n\n/**\n * @brief Type of comparison functions.\n */\ntypedef int (*st_compare_t)(void const *, void const *);\n\n/**\n * @brief Type of hash functions.\n */\ntypedef int (*st_hash_t)(void const *, int);\n\n/**\n * @brief Type of comparison functions with extra argument.\n */\ntypedef int (*st_compare_arg_t)(void const *, void const *, void const *);\n\n/**\n * @brief Type of hash functions with extra argument.\n */\ntypedef int (*st_hash_arg_t)(void const *, int, void const *);\n\n/*---------------------------------------------------------------------------*/\n/* Variable declarations                                                     */\n/*---------------------------------------------------------------------------*/\n\n\n/*---------------------------------------------------------------------------*/\n/* Macro declarations                                                        */\n/*---------------------------------------------------------------------------*/\n\n/**\n  @brief Checks whethere `key` is in `table`.\n\n  @details Returns 1 if there is an entry under `key` in `table`, 0\n  otherwise.\n\n  @sideeffect None\n\n  @see st_lookup\n\n*/\n#define st_is_member(table,key) st_lookup(table,key,(void **) 0)\n\n\n/**\n  @brief Iteration macro.\n\n  @details\n  An iteration macro which loops over all the entries in\n  `table`, setting `key` to point to the key and `value` to the\n  associated value (if it is not nil). `gen` is a generator variable\n  used internally. Sample usage:\n\n      void *key, *value;\n      st_generator *gen;\n\n      st_foreach_item(table, gen, &key, &value) {\n          process_item(value);\n      }\n\n  @sideeffect None\n\n  @see st_foreach_item_int st_foreach\n\n*/\n#define st_foreach_item(table, gen, key, value) \\\n    for(gen=st_init_gen(table); st_gen(gen,key,value) || (st_free_gen(gen),0);)\n\n\n/**\n  @brief Iteration macro.\n\n  @details\n  An iteration macro which loops over all the entries in\n  `table`, setting `key` to point to the key and `value` to the\n  associated value (if it is not nil). `value` is assumed to be a\n  pointer to an integer.  `gen` is a generator variable used\n  internally. Sample usage:\n\n      void *key;\n      int value;\n      st_generator *gen;\n\n      st_foreach_item_int(table, gen, &key, &value) {\n          process_item(value);\n      }\n\n  @sideeffect None\n\n  @see st_foreach_item st_foreach\n\n*/\n#define st_foreach_item_int(table, gen, key, value) \\\n    for(gen=st_init_gen(table); st_gen_int(gen,key,value) || (st_free_gen(gen),0);)\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nst_table *st_init_table_with_params (st_compare_t, st_hash_t, int, int, double, int);\nst_table *st_init_table (st_compare_t, st_hash_t);\nst_table *st_init_table_with_params_and_arg (st_compare_arg_t, st_hash_arg_t, void const *, int, int, double, int);\n    st_table *st_init_table_with_arg (st_compare_arg_t, st_hash_arg_t, void const *);\nvoid st_free_table (st_table *);\nint st_lookup (st_table *, void const *, void **);\nint st_lookup_int (st_table *, void const *, int *);\nint st_insert (st_table *, void *, void *);\nint st_add_direct (st_table *, void *, void *);\nint st_find_or_add (st_table *, void *, void ***);\nint st_find (st_table *, void const *, void ***);\nst_table *st_copy (st_table const *);\nint st_delete (st_table *, void **, void **);\nint st_delete_int (st_table *, void **, int *);\nint st_count(st_table const *);\nint st_foreach (st_table *, st_foreach_t, void *);\nint st_strhash (void const *, int);\nint st_numhash (void const *, int);\nint st_ptrhash (void const *, int);\nint st_numcmp (void const *, void const *);\nint st_ptrcmp (void const *, void const *);\nst_generator *st_init_gen (st_table const *);\nint st_gen (st_generator *, void **, void **);\nint st_gen_int (st_generator *, void **, int *);\nvoid st_free_gen (st_generator *);\n\n#ifdef __cplusplus\n} /* end of extern \"C\" */\n#endif\n\n#endif /* ST_H_ */\n"
  },
  {
    "path": "cudd/st/test_st.test.in",
    "content": "#! /bin/sh\n\nEXE=@EXEEXT@\nsrcdir=@srcdir@\n\nst/testst$EXE\n\nexit 0\n"
  },
  {
    "path": "cudd/st/testst.c",
    "content": "/**\n  @file\n\n  @ingroup st\n\n  @brief Simple test program of the st library.\n\n  @copyright@parblock\n  Copyright (c) 2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n#include \"st.h\"\n\n/**\n   @brief Just some struct type.\n*/\ntypedef struct mys {\n    double a;\n    int b;\n    int c;\n} mys_t;\n\n\n/** \\cond */\n\nstatic int testString(void);\nstatic int testStruct(void);\nstatic int testUintPtr(void);\nstatic int testInt(void);\nstatic int testArg(void);\nstatic int mys_cmp(void const * key1, void const * key2);\nstatic int mys_hash(void const * key, int size);\nstatic enum st_retval mys_accm(void * key, void * value, void * arg);\nstatic int array_hash(void const * key, int modulus, void const * arg);\nstatic int array_cmp(void const * key1, void const * key2, void const *arg);\n\n/** \\endcond */\n\n/**\n   @brief Main program.\n\n   @return the number of failed tests.\n\n   @details Uses TAP (Test Anything Protocol) to report results.\n*/\nint\nmain(void)\n{\n    int ret = 0;\n    printf(\"TAP version 13\\n1..5\\n\");\n\n    if (testString() != 0) {\n        ret++;\n        printf(\"not \");\n    }\n    printf(\"ok 1 string table\\n\");\n\n    if (testStruct() != 0) {\n        ret++;\n        printf(\"not \");\n    }\n    printf(\"ok 2 struct-to-uintptr_t map\\n\");\n\n    if (testUintPtr() != 0) {\n        ret++;\n        printf(\"not \");\n    }\n    printf(\"ok 3 uintptr_t-to-string map\\n\");\n\n    if (testInt() != 0) {\n        ret++;\n        printf(\"not \");\n    }\n    printf(\"ok 4 int-to-int map\\n\");\n\n    if (testArg() != 0) {\n        ret++;\n        printf(\"not \");\n    }\n    printf(\"ok 5 table with arg\\n\");\n\n    return ret;\n}\n\n\n/**\n   @brief Tests a table that stores C strings.\n\n   @return 0 if successful; the number of errors otherwise.\n*/\nstatic int\ntestString(void)\n{\n    int error = 0;\n    char foo[] = \"foo\";\n    char *cp = foo;\n    char bar[] = \"bar\";\n    char foobar[] = \"foobar\";\n    st_table * tbl = st_init_table((st_compare_t) strcmp, st_strhash);\n    if (!tbl)\n        error++;\n    if (st_insert(tbl, foo, NULL) != 0)\n        error++;\n    if (st_insert(tbl, bar, NULL) != 0)\n        error++;\n    if (st_insert(tbl, foobar, NULL) != 0)\n        error++;\n    if (!st_is_member(tbl, \"foo\"))\n        error++;\n    if (!st_delete(tbl, (void **) &cp, NULL))\n        error++;\n    if (st_count(tbl) != 2)\n        error++;\n    if (st_insert(tbl, bar, NULL) != 1)\n        error++;\n    st_free_table(tbl);\n    return error;\n}\n\n\n/**\n   @brief Tests a table that maps user-defined structs to uintptr_t.\n\n   @return 0 if successful; the number of errors otherwise.\n*/\nstatic int\ntestStruct(void)\n{\n    int error = 0;\n    mys_t m1 = {3.5, 4, 11};\n    mys_t m2 = {6.7, 5, -2};\n    uintptr_t u;\n    st_table * tbl = st_init_table(mys_cmp, mys_hash);\n    if (!tbl)\n        error++;\n    if (st_insert(tbl, &m1, (void *)(uintptr_t) 2) != 0)\n        error++;\n    if (st_insert(tbl, &m2, (void *)(uintptr_t) 5) != 0)\n        error++;\n    if (st_lookup(tbl, &m1, (void **) &u) != 1)\n        error++;\n    if (u != 2)\n        error++;\n    u = 0;\n    if (st_foreach(tbl, mys_accm, &u) != 1)\n        error++;\n    if (u != 7)\n        error++;\n    st_free_table(tbl);    \n    return error;\n}\n\n\n/**\n   @brief Tests a table that maps values of type uintptr_t to strings.\n\n   @return 0 if successful; the number of errors otherwise.\n*/\nstatic int\ntestUintPtr(void)\n{\n    int error = 0;\n    char foo[] = \"foo\";\n    char * cp;\n    st_table * tbl = st_init_table(st_numcmp, st_numhash);\n    if (!tbl)\n        error++;\n    if (st_insert(tbl, (void *)(uintptr_t) 2, foo) != 0)\n        error++;\n    if (st_lookup(tbl, (void *)(uintptr_t) 2, (void **) &cp) != 1)\n        error++;\n    if (strcmp(cp, \"foo\") != 0)\n        error++;\n    if (st_is_member(tbl, (void *)(uintptr_t) 76))\n        error++;\n    st_free_table(tbl);\n    return error;\n}\n\n\n/**\n   @brief Tests a table that maps ints to ints.\n\n   @return 0 if successful; the number of errors otherwise.\n*/\nstatic int\ntestInt(void)\n{\n    int error = 0;\n    int n1 = -2;\n    int n2;\n    void * e;\n    int i;\n    st_generator * gen;\n    st_table * tbl = st_init_table(st_numcmp, st_numhash);\n    if (!tbl)\n        error++;\n    if (st_insert(tbl, (void *)(intptr_t) n1, (void *)(intptr_t) 3) != 0)\n        error++;\n    if (st_lookup_int(tbl, (void *)(intptr_t) n1, &n2) != 1)\n        error++;\n    if (n2 != 3)\n        error++;\n    e = (void *)(intptr_t) n1;\n    if (st_delete_int(tbl, &e, &n2) != 1)\n        error++;\n    if ((int)(intptr_t) e != n1 || n2 != 3)\n        error++;\n    if (st_count(tbl) != 0)\n        error++;\n    for (i = 0; i < 100000; i++) {\n        if (st_insert(tbl, (void *)(intptr_t) i, (void *)(intptr_t) i) != 0)\n            error++;\n    }\n    st_foreach_item_int(tbl, gen, &e, &n1) {\n        if ((int)(intptr_t) e != n1)\n            error++;\n    }\n    st_free_table(tbl);\n    return error;\n}\n\n\n/**\n   @brief Tests a table of arrays of ints.\n\n   @return 0 if successful; 1 otherwise.\n*/\nstatic int\ntestArg(void)\n{\n    size_t const n = 5;\n    int error = 0;\n    int a1[] = {0,1,2,3,4};\n    int a2[] = {4,3,2,1,0};\n    int *a3 = a1;\n    intptr_t val = 0;\n    st_table *tbl = st_init_table_with_arg(array_cmp, array_hash, (void *) n);\n    if (!tbl)\n        error++;\n    if (st_insert(tbl, a1, (void *)(intptr_t) 1) != 0)\n        error++;\n    if (st_insert(tbl, a2, (void *)(intptr_t) 2) != 0)\n        error++;\n    if (!st_is_member(tbl, a1))\n        error++;\n    if (!st_delete(tbl, (void **) &a3, (void **) &val))\n        error++;\n    if (a3[0] != a1[0] || val != 1)\n        error++;\n    if (st_is_member(tbl, a1))\n        error++;\n    if (!st_is_member(tbl, a2))\n        error++;\n    st_free_table(tbl);\n    return error;\n}\n\n\n/**\n   @brief Compares two items of type mys_t.\n\n   @return 0 if they compare equal and 1 otherwise.\n*/\nstatic int\nmys_cmp(void const * key1, void const * key2)\n{\n    mys_t const *m1 = (mys_t const *) key1;\n    mys_t const *m2 = (mys_t const *) key2;\n\n    return m1->b != m2->b || m1->c != m2->c;\n}\n\n\n/**\n   @brief Hashes one item of type mys_t.\n\n   @return the hash value.\n*/\nstatic int\nmys_hash(void const * key, int size)\n{\n    mys_t const *m = (mys_t const *) key;\n    return (int)((((unsigned) m->b >> 4) ^ ((unsigned) m->c >> 5)) % size);\n}\n\n\n/**\n   @brief Accumulates the values associated to items of type mys_t.\n\n   @return ST_CONTINUE\n*/\nstatic enum st_retval\nmys_accm(void * key, void * value, void * arg)\n{\n    (void) key; /* avoid warning */\n    uintptr_t v = (uintptr_t) value;\n    uintptr_t * accum = (uintptr_t *) arg;\n    *accum += v;\n    return ST_CONTINUE;\n}\n\n\n/**\n   @brief Compares two arrays of ints.\n\n   @details The length of the two arrays is in `arg`.\n\n   @return 0 if they compare equal and 1 otherwise.\n*/\nstatic int\narray_cmp(void const * key1, void const * key2, void const *arg)\n{\n    int const *a1 = (int const *) key1;\n    int const *a2 = (int const *) key2;\n    size_t const size = (size_t const) arg;\n    size_t i;\n    for (i = 0; i < size; i++) {\n        if (a1[i] != a2[i])\n            return 1;\n    }\n    return 0;\n}\n\n\n/**\n   @brief Hashes one array of ints.\n\n   @return the hash value.\n*/\nstatic int\narray_hash(void const * key, int modulus, void const * arg)\n{\n    int const *a = (int const *) key;\n    size_t const size = (size_t const) arg;\n    int val = 0;\n    size_t i;\n    for (i = 0; i < size; i++) {\n        val = val * 997 + a[i];\n    }\n    return ((val < 0) ? -val : val) % modulus;\n}\n"
  },
  {
    "path": "cudd/util/Included.am",
    "content": "cudd_libcudd_la_SOURCES += util/util.h util/cstringstream.h \\\n  util/cpu_stats.c util/cpu_time.c util/cstringstream.c util/datalimit.c \\\n  util/pathsearch.c util/pipefork.c util/prtime.c util/safe_mem.c \\\n  util/strsav.c util/texpand.c util/ucbqsort.c\nif MINGW64\nif CROSS_COMPILING\ncudd_libcudd_la_LIBADD = -lws2_32 -lpsapi\nendif\nendif\n"
  },
  {
    "path": "cudd/util/cpu_stats.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief CPU statistics.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#define _BSD_SOURCE\n#include \"util.h\"\n\n#if HAVE_SYS_TIME_H == 1\n#include <sys/time.h>\n#endif\n#if HAVE_SYS_RESOURCE_H == 1\n#include <sys/resource.h>\n#endif\n\n#ifdef BSD\n#if defined(_IBMR2)\n#define etext _etext\n#define edata _edata\n#define end _end\n#endif\n\nextern int end, etext, edata;\n\n#endif\n\n#ifdef _WIN32\n#include <winsock2.h>\n#include <psapi.h>\n#endif\n\n/**\n   @brief Prints CPU statistics.\n\n   The amount of detail printed depends on the host operating system.\n\n*/\nvoid\nutil_print_cpu_stats(FILE *fp)\n{\n#if HAVE_GETRUSAGE == 1 && HAVE_GETRLIMIT == 1\n    struct rusage rusage;\n    double user, system, scale;\n    long text, data;\n    struct rlimit rlp;\n    long vm_limit, vm_soft_limit;\n    char hostname[257];\n#ifdef BSD\n    long vm_text, vm_init_data, vm_uninit_data, vm_sbrk_data;\n#endif\n\n    /* Get the hostname */\n    (void) gethostname(hostname, sizeof(hostname));\n    hostname[sizeof(hostname)-1] = '\\0';\t/* just in case */\n\n#ifdef BSD\n    /* Get the virtual memory sizes */\n    vm_text = (long) (((long) (&etext)) / 1024.0 + 0.5);\n    vm_init_data = (long) (((long) (&edata) - (long) (&etext)) / 1024.0 + 0.5);\n    vm_uninit_data = (long) (((long) (&end) - (long) (&edata)) / 1024.0 + 0.5);\n    vm_sbrk_data = (long) (((long) sbrk(0) - (long) (&end)) / 1024.0 + 0.5);\n#endif\n\n    /* Get virtual memory limits */\n    (void) getrlimit(RLIMIT_DATA, &rlp);\n    vm_limit = (long) (rlp.rlim_max / 1024.0 + 0.5);\n    vm_soft_limit = (long) (rlp.rlim_cur / 1024.0 + 0.5);\n\n    /* Get usage stats */\n    (void) getrusage(RUSAGE_SELF, &rusage);\n    user = rusage.ru_utime.tv_sec + rusage.ru_utime.tv_usec * 1e-6;\n    system = rusage.ru_stime.tv_sec + rusage.ru_stime.tv_usec * 1e-6;\n    scale = (user + system)*100.0;\n    if (scale == 0.0) scale = 0.001;\n    text = (int) (rusage.ru_ixrss / scale + 0.5);\n    data = (int) ((rusage.ru_idrss + rusage.ru_isrss) / scale + 0.5);\n\n#elif defined(_WIN32)\n    char hostname[257];\n    WSADATA wsaData;\n    FILETIME creationTime, exitTime, kernelTime, userTime;\n    double user, system;\n    MEMORYSTATUSEX statex;\n    size_t vm_limit;\n    PROCESS_MEMORY_COUNTERS pmc;\n    size_t peak_working_set;\n    long page_faults;\n\n    /* Get the hostname */\n    WSAStartup(MAKEWORD(2, 2), &wsaData);\n    (void) gethostname(hostname, sizeof(hostname));\n    hostname[sizeof(hostname)-1] = '\\0';\t/* just in case */\n    WSACleanup();\n\n    /* Get usage stats */\n    if (GetProcessTimes(GetCurrentProcess(), &creationTime, &exitTime,\n\t\t\t&kernelTime, &userTime)) {\n\tULARGE_INTEGER integerSystemTime, integerUserTime;\n\tintegerUserTime.u.LowPart = userTime.dwLowDateTime;\n\tintegerUserTime.u.HighPart = userTime.dwHighDateTime;\n\tuser = (double) integerUserTime.QuadPart * 1e-7;\n\tintegerSystemTime.u.LowPart = kernelTime.dwLowDateTime;\n\tintegerSystemTime.u.HighPart = kernelTime.dwHighDateTime;\n\tsystem = (double) integerSystemTime.QuadPart * 1e-7;\n    } else {\n\tuser = system = 0.0;\n    }\n    statex.dwLength = sizeof(statex);\n    if (GlobalMemoryStatusEx(&statex)) {\n\tvm_limit = (size_t) (statex.ullTotalVirtual / 1024.0 + 0.5);\n    } else {\n\tvm_limit = 0;\n    }\n    if (GetProcessMemoryInfo(GetCurrentProcess(), &pmc, sizeof(pmc))) {\n\tpeak_working_set = (size_t) (pmc.PeakWorkingSetSize / 1024.0 + 0.5);\n\tpage_faults = (long) pmc.PageFaultCount;\n    } else {\n\tpeak_working_set = 0;\n\tpage_faults = 0;\n    }\n#endif\n\n#if (HAVE_GETRUSAGE == 1 && HAVE_GETRLIMIT == 1) || defined(_WIN32)\n    (void) fprintf(fp, \"Runtime Statistics\\n\");\n    (void) fprintf(fp, \"------------------\\n\");\n    (void) fprintf(fp, \"Machine name: %s\\n\", hostname);\n    (void) fprintf(fp, \"User time   %6.1f seconds\\n\", user);\n    (void) fprintf(fp, \"System time %6.1f seconds\\n\\n\", system);\n\n#if HAVE_GETRUSAGE == 1 && HAVE_GETRLIMIT == 1\n    (void) fprintf(fp, \"Average resident text size       = %5ldK\\n\", text);\n    (void) fprintf(fp, \"Average resident data+stack size = %5ldK\\n\", data);\n    (void) fprintf(fp, \"Maximum resident size            = %5ldK\\n\\n\",\n\trusage.ru_maxrss);\n#if defined(BSD)\n    (void) fprintf(fp, \"Virtual text size                = %5ldK\\n\",\n\tvm_text);\n    (void) fprintf(fp, \"Virtual data size                = %5ldK\\n\",\n\tvm_init_data + vm_uninit_data + vm_sbrk_data);\n    (void) fprintf(fp, \"    data size initialized        = %5ldK\\n\",\n\tvm_init_data);\n    (void) fprintf(fp, \"    data size uninitialized      = %5ldK\\n\",\n\tvm_uninit_data);\n    (void) fprintf(fp, \"    data size sbrk               = %5ldK\\n\",\n\tvm_sbrk_data);\n#endif\n    (void) fprintf(fp, \"Virtual memory limit             = \");\n    if (rlp.rlim_cur == RLIM_INFINITY)\n        (void) fprintf(fp, \"unlimited\");\n    else\n        (void) fprintf(fp, \"%5ldK\", vm_soft_limit);\n    if (rlp.rlim_max == RLIM_INFINITY)\n        (void) fprintf(fp, \" (unlimited)\\n\");\n    else\n        (void) fprintf(fp, \" (%ldK)\\n\\n\", vm_limit);\n\n    (void) fprintf(fp, \"Major page faults = %ld\\n\", rusage.ru_majflt);\n    (void) fprintf(fp, \"Minor page faults = %ld\\n\", rusage.ru_minflt);\n    (void) fprintf(fp, \"Swaps = %ld\\n\", rusage.ru_nswap);\n    (void) fprintf(fp, \"Input blocks = %ld\\n\", rusage.ru_inblock);\n    (void) fprintf(fp, \"Output blocks = %ld\\n\", rusage.ru_oublock);\n    (void) fprintf(fp, \"Context switch (voluntary) = %ld\\n\", rusage.ru_nvcsw);\n    (void) fprintf(fp, \"Context switch (involuntary) = %ld\\n\", rusage.ru_nivcsw);\n#else\n    (void) fprintf(fp, \"Maximum resident size            = \");\n    if (peak_working_set == 0)\n\t(void) fprintf(fp, \"unavailable\\n\");\n    else\n\t(void) fprintf(fp, \"%\" PRIszt \"K\\n\", peak_working_set);\n    (void) fprintf(fp, \"Virtual memory limit             = \");\n    if (vm_limit == 0)\n\t(void) fprintf(fp, \"unavailable\\n\");\n    else\n\t(void) fprintf(fp, \"%5\" PRIszt \"K\\n\", vm_limit);\n    (void) fprintf(fp, \"Page faults       = %ld\\n\", page_faults);\n#endif\n#else\n    (void) fprintf(fp, \"Usage statistics not available\\n\");\n#endif\n}\n"
  },
  {
    "path": "cudd/util/cpu_time.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief System time calls\n\n  @details Provide a uniform interface across different operating systems.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n\n#if HAVE_SYS_TIMES_H == 1\n#include <sys/times.h>\n#endif\n\n#ifdef _WIN32\n#include <windows.h>\n#endif\n\n/**\n * @brief returns a long which represents the elapsed processor\n * time in milliseconds since some constant reference.\n */\nlong\nutil_cpu_time(void)\n{\n#if HAVE_SYSCONF == 1\n\n    /* Code for POSIX systems */\n\n    struct tms buffer;\n    long nticks;                /* number of clock ticks per second */\n\n    nticks = sysconf(_SC_CLK_TCK);\n    times(&buffer);\n    return (long) ((buffer.tms_utime + buffer.tms_stime) * (1000.0/nticks));\n\n#elif defined(_WIN32)\n    FILETIME creationTime, exitTime, kernelTime, userTime;\n    if (GetProcessTimes(GetCurrentProcess(), &creationTime, &exitTime,\n\t\t\t&kernelTime, &userTime)) {\n\tULARGE_INTEGER integerTime;\n\tintegerTime.u.LowPart = userTime.dwLowDateTime;\n\tintegerTime.u.HighPart = userTime.dwHighDateTime;\n\treturn (long) (integerTime.QuadPart / 10000);\n    } else {\n\treturn 0;\n    }\n#else\n    return 0L;\n#endif\n\n}\n\n/**\n * @brief returns a long which represents the elapsed processor\n * time in milliseconds since some constant reference.  It includes\n * waited-for terminated children.\n */\nlong\nutil_cpu_ctime(void)\n{\n#if HAVE_SYSCONF == 1\n\n    /* Code for POSIX systems */\n\n    struct tms buffer;\n    long nticks;                /* number of clock ticks per second */\n\n    nticks = sysconf(_SC_CLK_TCK);\n    times(&buffer);\n    return (long) ((buffer.tms_utime + buffer.tms_cutime) * (1000.0/nticks));\n\n#else\n    return 0L;\n#endif\n\n}\n\n"
  },
  {
    "path": "cudd/util/cstringstream.c",
    "content": "/**\n  @file \n\n  @ingroup cstringstream\n\n  @brief Simple string streams in C.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 2014-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include <stdio.h>\n#include <stdlib.h>\n#include <string.h>\n#include \"cstringstream.h\"\n\n/**\n * @brief Type of a simple extensible string buffer.\n */\nstruct _cstringstream {\n  size_t capacity; /**< elements allocated */\n  size_t inUse;    /**< elements currently in use */\n  char * data;     /**< actual data */\n};\n\ncstringstream newStringStream(void) {\n  cstringstream ss;\n  ss = (cstringstream) malloc(sizeof(struct _cstringstream));\n  if (!ss) return NULL;\n  ss->capacity = 1; /* parsimonious */\n  ss->inUse = 0;\n  ss->data = (char *) malloc(sizeof(char) * ss->capacity);\n  if (!ss->data) {\n    free(ss);\n    return NULL;\n  }\n  return ss;\n}\n\nvoid deleteStringStream(cstringstream ss) {\n  if (ss) {\n    free(ss->data);\n    free(ss);\n  }\n}\n\nint clearStringStream(cstringstream ss) {\n  if (!ss) return -1;\n  ss->inUse = 0;\n  return 0;\n}\n\ncstringstream copyStringStream(const_cstringstream src) {\n  cstringstream dest;\n  if (!src) return 0;\n  dest = newStringStream();\n  if (!dest) return 0;\n  if (resizeStringStream(dest, src->inUse)) {\n    deleteStringStream(dest);\n    return 0;\n  }\n  strncpy(dest->data, src->data, src->inUse);\n  return dest;\n}\n\nint resizeStringStream(cstringstream ss, size_t newSize) {\n  if (newSize > ss->capacity) {\n    /* To avoid too many calls to realloc, we choose the larger of\n     * twice the current size and the new requested size. */\n    size_t newCapacity = 2 * ss->capacity;\n    if (newCapacity < newSize)\n      newCapacity = newSize;\n    char * tmp = (char *) realloc(ss->data, newCapacity * sizeof(char));\n    /* If the allocation fails, leave the array alone. */\n    if (!tmp) return -1;\n    ss->data = tmp;\n    ss->capacity = newCapacity;\n  }\n  /* Here we are guaranteed that newSize <= ss->capacity. */\n  ss->inUse = newSize;\n  return 0;\n}\n\nint sizeStringStream(const_cstringstream ss, size_t * num) {\n  if (!ss || !num) return -1;\n  *num = ss->inUse;\n  return 0;\n}\n\nint getStringStream(const_cstringstream ss, size_t index, char * c) {\n  if (!ss || !c || index >= ss->inUse) return -1;\n  *c = ss->data[index];\n  return 0;\n}\n\nint appendCharStringStream(cstringstream ss, char c) {\n  if (!ss) return -1;\n  if (resizeStringStream(ss, ss->inUse + 1)) return -1;\n  /* Now we have space. */\n  ss->data[ss->inUse-1] = c;\n  return 0;\n}\n\nint appendStringStringStream(cstringstream ss, char const * s) {\n  if (!ss) return -1;\n  size_t len = strlen(s);\n  if (resizeStringStream(ss, ss->inUse + len)) return -1;\n  /* Now we have space. */\n  strncpy(ss->data + ss->inUse - len, s, len); \n  return 0;\n}\n\nint appendIntStringStream(cstringstream ss, int d) {\n  char str[256];\n  if (!ss) return -1;\n  sprintf(str, \"%d\", d);\n  return appendStringStringStream(ss, str);\n}\n\nint appendUnsignedStringStream(cstringstream ss, unsigned u) {\n  char str[256];\n  if (!ss) return -1;\n  sprintf(str, \"%u\", u);\n  return appendStringStringStream(ss, str);\n}\n\nint appendLongStringStream(cstringstream ss, long ld) {\n  char str[256];\n  if (!ss) return -1;\n  sprintf(str, \"%ld\", ld);\n  return appendStringStringStream(ss, str);\n}\n\nint appendUnsignedLongStringStream(cstringstream ss, unsigned long lu) {\n  char str[256];\n  if (!ss) return -1;\n  sprintf(str, \"%lu\", lu);\n  return appendStringStringStream(ss, str);\n}\n\nint appendDoubleStringStream(cstringstream ss, double g) {\n  char str[256];\n  if (!ss) return -1;\n  sprintf(str, \"%g\", g);\n  return appendStringStringStream(ss, str);\n}\n\nint putStringStream(cstringstream ss, size_t index, char c) {\n  if (!ss || index >= ss->inUse) return -1;\n  ss->data[index] = c;\n  return 0;\n}\n\nchar * stringFromStringStream(const_cstringstream ss) {\n  if (!ss) return 0;\n  char * str = (char *) malloc(sizeof(char) * (ss->inUse + 1));\n  if (!str) return 0;\n  strncpy(str, ss->data, ss->inUse);\n  str[ss->inUse] = '\\0';\n  return str;\n}\n"
  },
  {
    "path": "cudd/util/cstringstream.h",
    "content": "/**\n  @file \n\n  @ingroup cstringstream\n\n  @brief Package for simple stringstreams in C.\n\n  @author Fabio Somenzi\n\n  @copyright@parblock\n  Copyright (c) 2014-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n  $Id: cstringstream.h,v 1.1 2015/07/01 20:36:47 fabio Exp fabio $\n\n*/\n#ifndef CSTRINGSTREAM_H_\n#define CSTRINGSTREAM_H_\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/*---------------------------------------------------------------------------*/\n/* Type declarations                                                         */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Type of a string stream.\n */\ntypedef struct _cstringstream * cstringstream;\n\n/**\n * @brief Const-qualified version of cstringstream.\n */\ntypedef struct _cstringstream const * const_cstringstream;\n\n/*---------------------------------------------------------------------------*/\n/* Function prototypes                                                       */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Returns a new cstringstream with an empty string.\n * @return NULL if creation fails.\n */\ncstringstream newStringStream(void);\n/**\n * @brief Frees cstringstream ss.\n */\nvoid deleteStringStream(cstringstream ss);\n/**\n * @brief Clears the contents of cstringstream ss.\n * @return 0 if succesful and -1 if ss is an invalid pointer.\n */\nint clearStringStream(cstringstream ss);\n/**\n * @brief Copies cstringstream src to a new cstringstream.\n * @return 0 if succesful or -1 if src is an invalid pointer\n * or memory allocation fails.\n */\ncstringstream copyStringStream(const_cstringstream src);\n/**\n * @brief Changes the size of cstringstream ss.\n * @return 0 if successful or -1 if resizing fails.\n */\nint resizeStringStream(cstringstream ss, size_t newSize);\n/**\n * @brief Writes the size of cstringstream ss to the location pointed by num.\n * @return 0 if succesful or -1 if ss is an invalid pointer.\n */\nint sizeStringStream(const_cstringstream ss, size_t * num);\n/**\n * @brief Writes the i-th element of cstringstream ss to the location\n * pointed by c.\n * @return 0 if successful or -1 otherwise.\n */\nint getStringStream(const_cstringstream ss, size_t i, char * c);\n/**\n * @brief Adds char c at the end of cstringstream ss.\n * @return 0 if successful or -1 otherwise.\n */\nint appendCharStringStream(cstringstream ss, char c);\n/**\n * @brief Adds string s at the end of cstringstream ss.\n * @return 0 if successful or -1 otherwise.\n */\nint appendStringStringStream(cstringstream ss, char const * s);\n/**\n * @brief Adds int d at the end of cstringstream ss.\n * @return 0 if successful or -1 otherwise.\n */\nint appendIntStringStream(cstringstream ss, int d);\n/**\n * @brief Adds unsigned u at the end of cstringstream ss.\n * @return 0 if successful or -1 otherwise.\n */\nint appendUnsignedStringStream(cstringstream ss, unsigned u);\n/**\n * @brief Adds long ld at the end of cstringstream ss.\n * @return 0 if successful or -1 otherwise.\n */\nint appendLongStringStream(cstringstream ss, long ld);\n/**\n * @brief Adds unsigned long lu at the end of cstringstream ss.\n * @return 0 if successful or -1 otherwise.\n */\nint appendUnsignedLongStringStream(cstringstream ss, unsigned long lu);\n/**\n * @brief Adds double g at the end of cstringstream ss.\n * @return 0 if successful or -1 otherwise.\n */\nint appendDoubleStringStream(cstringstream ss, double g);\n/**\n * @brief Sets the i-th element of cstringstream ss to c.\n * @return 0 if successful or -1 otherwise.\n *\n * The i-th element of ss must already exist.\n */\nint putStringStream(cstringstream ss, size_t index, char c);\n/**\n * @brief Returns a NULL-terminated string from the contents of\n * cstringstream ss.\n * @details In case of failure, it returns NULL.\n * The returned string must be freed by the caller.\n */\nchar * stringFromStringStream(const_cstringstream ss);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif\n"
  },
  {
    "path": "cudd/util/datalimit.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief Access to datasize limit.\n\n  @copyright@parblock\n  Copyright (c) 1995-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"config.h\"\n\n#if HAVE_STDINT_H == 1\n#include <stdint.h>\n#endif\n#if HAVE_STDDEF_H == 1\n#include <stddef.h>\n#endif\n\n#if HAVE_SYS_RESOURCE_H == 1\n#if HAVE_SYS_TIME_H == 1\n#include <sys/time.h>\n#endif\n#include <sys/resource.h>\n#endif\n\n#ifdef _WIN32\n#include <windows.h>\n#endif\n\n/**\n * @brief Default value returned if getrlimit not available.\n */\n#ifndef RLIMIT_DATA_DEFAULT\n#define RLIMIT_DATA_DEFAULT 268435456\t/* assume 256MB by default */\n#endif\n\n/**\n * @def EXTERN\n * @brief Allows C linkage when compiling as C++.\n */\n#ifndef EXTERN\n#   ifdef __cplusplus\n#\tdefine EXTERN extern \"C\"\n#   else\n#\tdefine EXTERN extern\n#   endif\n#endif\n\nEXTERN size_t getSoftDataLimit(void);\n\n/**\n * @brief Gets the soft datasize limit.\n */\nsize_t\ngetSoftDataLimit(void)\n{\n#if HAVE_SYS_RESOURCE_H == 1 && HAVE_GETRLIMIT == 1 && defined(RLIMIT_DATA)\n    struct rlimit rl;\n    int result;\n\n    result = getrlimit(RLIMIT_DATA, &rl);\n    if (result != 0 || rl.rlim_cur == RLIM_INFINITY)\n\treturn (size_t) RLIMIT_DATA_DEFAULT;\n    else\n\treturn (size_t) rl.rlim_cur;\n#elif defined(_WIN32)\n    /* Not quite the same, because this returns available physical memory. */\n    MEMORYSTATUSEX statex;\n    statex.dwLength = sizeof(statex);\n    if (GlobalMemoryStatusEx(&statex))\n\treturn (size_t) statex.ullTotalPhys;\n    else\n\treturn (size_t) RLIMIT_DATA_DEFAULT;\n#else\n    return (size_t) RLIMIT_DATA_DEFAULT;\n#endif\n\n} /* end of getSoftDataLimit */\n"
  },
  {
    "path": "cudd/util/pathsearch.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief Search in PATH.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n\n/** \\cond */\n\nstatic int check_file (char const *, char const *);\n\n/** \\endcond */\n\n/**\n * @brief Looks for a program in the directories specified by PATH.\n */\nchar *\nutil_path_search(char const *prog)\n{\n#ifdef UNIX\n    return util_file_search(prog, getenv(\"PATH\"), (char *) \"x\");\n#else\n    return util_file_search(prog, NIL(char), (char *) \"x\");\n#endif\n}\n\n\n/**\n * @brief Searches for a file given a set of paths.\n */\nchar *\nutil_file_search(\n  char const *file,\t\t/**< file we're looking for */\n  char *path,\t\t\t/**< search path, colon separated */\n  char const *mode\t\t/**< \"r\", \"w\", or \"x\" */)\n{\n    int quit;\n    char *buffer, *filename, *save_path, *cp;\n\n    if (path == 0 || strcmp(path, \"\") == 0) {\n\tpath = (char *) \".\";\t/* just look in the current directory */\n    }\n\n    save_path = path = util_strsav(path);\n    quit = 0;\n    do {\n\tcp = strchr(path, ':');\n\tif (cp != 0) {\n\t    *cp = '\\0';\n\t} else {\n\t    quit = 1;\n\t}\n\n\t/* cons up the filename out of the path and file name */\n\tif (strcmp(path, \".\") == 0) {\n\t    buffer = util_strsav(file);\n\t} else {\n\t    buffer = ALLOC(char, strlen(path) + strlen(file) + 4);\n\t    (void) sprintf(buffer, \"%s/%s\", path, file);\n\t}\n\tfilename = util_tilde_expand(buffer);\n\tFREE(buffer);\n\n\t/* see if we can access it */\n\tif (check_file(filename, mode)) {\n\t    FREE(save_path);\n\t    return filename;\n\t}\n\tFREE(filename);\n\tpath = ++cp;\n    } while (! quit); \n\n    FREE(save_path);\n    return 0;\n}\n\n/**\n * @brief Checks user permissions for a file.\n */\nstatic int\ncheck_file(char const *filename, char const *mode)\n{\n#ifdef UNIX\n    int access_mode = /*F_OK*/ 0;\n\n    if (strcmp(mode, \"r\") == 0) {\n\taccess_mode = /*R_OK*/ 4;\n    } else if (strcmp(mode, \"w\") == 0) {\n\taccess_mode = /*W_OK*/ 2;\n    } else if (strcmp(mode, \"x\") == 0) {\n\taccess_mode = /*X_OK*/ 1;\n    }\n    return access(filename, access_mode) == 0;\n#else\n    FILE *fp;\n    int got_file;\n\n    if (strcmp(mode, \"x\") == 0) {\n\tmode = \"r\";\n    }\n    fp = fopen(filename, mode);\n    got_file = (fp != 0);\n    if (fp != 0) {\n\t(void) fclose(fp);\n    }\n    return got_file;\n#endif\n}\n"
  },
  {
    "path": "cudd/util/pipefork.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief Forks a command and sets up pipes to and from.\n\n  @author Rick L Spickelmier\n  @author Richard Rudell\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"config.h\"\n#if HAVE_UNISTD_H == 1\n#define _POSIX_SOURCE\n#include <unistd.h>\n#endif\n#include <stdio.h>\n#if HAVE_SYS_WAIT_H == 1\n#include <sys/wait.h>\n#endif\n\n/**\n * @def EXTERN\n * @brief Allows C linkage when compiling as C++.\n */\n#ifndef EXTERN\n#   ifdef __cplusplus\n#\tdefine EXTERN extern \"C\"\n#   else\n#\tdefine EXTERN extern\n#   endif\n#endif\n\n\n/**\n * @brief Forks a command and sets up pipes to and from.\n *\n * @return 1 for success, with toCommand and fromCommand pointing to\n *   the streams; 0 for failure\n */\nint\nutil_pipefork(\n  char * const *argv,\t/**< normal argv argument list */\n  FILE **toCommand,\t/**< pointer to the sending stream */\n  FILE **fromCommand,\t/**< pointer to the reading stream */\n  int *pid /**< process ID */)\n{\n#if HAVE_SYS_WAIT_H == 1\n    int forkpid, waitPid;\n    int topipe[2], frompipe[2];\n    char buffer[1024];\n    int status;\n\n    /* create the PIPES...\n     * fildes[0] for reading from command\n     * fildes[1] for writing to command\n     */\n    if (pipe(topipe)) return(0);\n    if (pipe(frompipe)) return(0);\n\n    if ((forkpid = fork()) == 0) {\n\t/* child here, connect the pipes */\n\t(void) dup2(topipe[0], fileno(stdin));\n\t(void) dup2(frompipe[1], fileno(stdout));\n\n\t(void) close(topipe[0]);\n\t(void) close(topipe[1]);\n\t(void) close(frompipe[0]);\n\t(void) close(frompipe[1]);\n\n\t(void) execvp(argv[0], argv);\n\t(void) sprintf(buffer, \"util_pipefork: can not exec %s\", argv[0]);\n\tperror(buffer);\n\t(void) _exit(1);\n    }\n\n    if (pid) {\n        *pid = forkpid;\n    }\n\n    waitPid = waitpid(-1, &status, WNOHANG);\n\n    /* parent here, use fork() semantics to get return status */\n    if (waitPid == forkpid && WIFEXITED(status)) {\n\treturn 0;\n    }\n    if ((*toCommand = fdopen(topipe[1], \"w\")) == NULL) {\n\treturn 0;\n    }\n    if ((*fromCommand = fdopen(frompipe[0], \"r\")) == NULL) {\n\treturn 0;\n    }\n    (void) close(topipe[0]);\n    (void) close(frompipe[1]);\n    return 1;\n#else\n    (void) argv;        /* to avoid warning */\n    (void) toCommand;   /* to avoid warning */\n    (void) fromCommand; /* to avoid warning */\n    (void) pid;         /* to avoid warning */\n    (void) fprintf(stderr, \n\t\"util_pipefork: not implemented on your operating system\\n\");\n    return 0;\n#endif\n}\n"
  },
  {
    "path": "cudd/util/prtime.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief Time printing utility.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n\n/**\n *  @brief Massages a long that represents a time interval in\n *  milliseconds into a string suitable for output.\n *\n *  Hack for IBM/PC -- avoids using floating point.\n */\nchar *\nutil_print_time(unsigned long t)\n{\n    static char s[40];\n\n    (void) sprintf(s, \"%lu.%02lu sec\", t/1000, (t%1000)/10);\n    return s;\n}\n"
  },
  {
    "path": "cudd/util/safe_mem.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief Interface routines to be placed between a program and the\n  system memory allocator.  \n\n  The function pointer MMoutOfMemory() contains a vector to handle a\n  'out-of-memory' error (which, by default, points at a simple wrap-up \n  and exit routine).\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/**\n * @brief Global out-of-memory handler.\n */\nvoid (*MMoutOfMemory)(size_t) = MMout_of_memory;\n\n#ifdef __cplusplus\n}\n#endif\n\n\n/**\n * @brief Out of memory for lazy people: flush and exit.\n */\nvoid \nMMout_of_memory(size_t size)\n{\n    (void) fflush(stdout);\n    (void) fprintf(stderr,\n                   \"\\nCUDD: out of memory allocating %\" PRIszt \" bytes\\n\",\n\t\t   (size_t) size);\n    exit(1);\n}\n\n/**\n * @brief malloc replacement.\n */\nvoid *\nMMalloc(size_t size)\n{\n    void *p;\n\n    if ((p = malloc(size)) == NIL(void)) {\n\tif (MMoutOfMemory != 0 ) (*MMoutOfMemory)(size);\n\treturn NIL(void);\n    }\n    return p;\n}\n\n\n/**\n * @brief realloc replacement.\n */\nvoid *\nMMrealloc(void *obj, size_t size)\n{\n    void *p;\n\n    if ((p = realloc(obj, size)) == NIL(void)) {\n\tif (MMoutOfMemory != 0 ) (*MMoutOfMemory)(size);\n\treturn NIL(void);\n    }\n    return p;\n}\n"
  },
  {
    "path": "cudd/util/strsav.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief String copying.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n\n/**\n *  @brief Returns a copy of a string.\n */\nchar *\nutil_strsav(char const *s)\n{\n    return strcpy(ALLOC(char, strlen(s)+1), s);\n}\n"
  },
  {
    "path": "cudd/util/texpand.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief Tilde expansion.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n\n#include \"util.h\"\n\n#ifdef BSD\n#include <pwd.h>\n#endif\n\n/**\n * @brief Expands tilde in a file name\n */\nchar *\nutil_tilde_expand(char const *fname)\n{\n#ifdef BSD\n    struct passwd *userRecord;\n    char username[256], *filename;\n    register int i, j;\n\n    filename = ALLOC(char, strlen(fname) + 256);\n\n    /* Clear the return string */\n    i = 0;\n    filename[0] = '\\0';\n\n    /* Tilde? */\n    if (fname[0] == '~') {\n\tj = 0;\n\ti = 1;\n\twhile ((fname[i] != '\\0') && (fname[i] != '/')) {\n\t    username[j++] = fname[i++];\n\t}\n\tusername[j] = '\\0';\n\n\tif (username[0] == '\\0') {\n\t    /* ~/ resolves to home directory of current user */\n\t    if ((userRecord = getpwuid(getuid())) != 0) {\n\t\t(void) strcat(filename, userRecord->pw_dir);\n\t    } else {\n\t\ti = 0;\n\t    }\n\t} else {\n\t    /* ~user/ resolves to home directory of 'user' */\n\t    if ((userRecord = getpwnam(username)) != 0) {\n\t\t(void) strcat(filename, userRecord->pw_dir);\n\t    } else {\n\t\ti = 0;\n\t    }\n\t}\n    }\n\n    /* Concantenate remaining portion of file name */\n    (void) strcat(filename, fname + i);\n    return filename;\n#else\n    return util_strsav(fname);\n#endif\n}\n"
  },
  {
    "path": "cudd/util/ucbqsort.c",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief Ancient implementation of qsort.\n\n  @details This is shipped with CUDD so that results of reordering may\n  be more reproducible across different platforms.\n\n  qsort.c\t4.2 (Berkeley) 3/9/83\n\n  Our own version of the system qsort routine which is faster by an average\n  of 25%, with lows and highs of 10% and 50%.\n  The THRESHold below is the insertion sort threshold, and has been adjusted\n  for records of size 48 bytes.\n  The MTHREShold is where we stop finding a better median.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n */\n\n#include \"util.h\"\n\n#ifndef USE_SYSTEM_QSORT\n/**\n   @brief Threshold for insertion.\n*/\n#define\t\tTHRESH\t\t4\n/**\n   @brief Threshold for median.\n*/\n#define\t\tMTHRESH\t\t6\n\n/**\n   @brief Miscellaneous information.\n*/\ntypedef struct {\n    QSFP\tqcmp;\t\t\t/**< the comparison routine */\n    int\t\tqsz;\t\t\t/**< size of each record */\n    int\t\tthresh;\t\t\t/**< THRESHold in chars */\n    int\t\tmthresh;\t\t/**< MTHRESHold in chars */\n} info_t;\n\n/*---------------------------------------------------------------------------*/\n/* Static function prototypes                                                */\n/*---------------------------------------------------------------------------*/\n\n/** \\cond */\n\nstatic\tvoid\t\tqst (char *base, char *max, info_t const * info);\n\n/** \\endcond */\n\n/*---------------------------------------------------------------------------*/\n/* Definition of exported functions                                          */\n/*---------------------------------------------------------------------------*/\n\n#undef min\n#undef max\n#endif\n/**\n * @brief Implements the quicksort algorithm.\n *\n * @details First, set up some global parameters for qst to share.\n * Then, quicksort with qst(), and then a cleanup insertion sort\n * ourselves.  Sound simple?  It's not...\n */\nvoid\nutil_qsort(\n  void *vbase /**< start address of array */,\n  int n       /**< number of items */,\n  int size    /**< size of each item */,\n  QSFP compar /**< comparison function */)\n{\n#ifdef USE_SYSTEM_QSORT\n    qsort(vbase, n, size, compar);\n#else\n    char *base = (char *) vbase;\n    char c, *i, *j, *lo, *hi;\n    char *min, *max;\n    info_t info;\n\n    if (n <= 1)\n        return;\n    info.qsz = size;\n    info.qcmp = compar;\n    info.thresh = size * THRESH;\n    info.mthresh = size * MTHRESH;\n    max = base + n * size;\n    if (n >= THRESH) {\n        qst(base, max, &info);\n        hi = base + info.thresh;\n    } else {\n        hi = max;\n    }\n    /*\n     * First put smallest element, which must be in the first THRESH, in\n     * the first position as a sentinel.  This is done just by searching\n     * the first THRESH elements (or the first n if n < THRESH), finding\n     * the min, and swapping it into the first position.\n     */\n    for (j = lo = base; (lo += size) < hi; )\n        if ((*compar)(j, lo) > 0)\n            j = lo;\n    if (j != base) {\n        /* swap j into place */\n        for (i = base, hi = base + size; i < hi; ) {\n            c = *j;\n            *j++ = *i;\n            *i++ = c;\n        }\n    }\n    /*\n     * With our sentinel in place, we now run the following hyper-fast\n     * insertion sort. For each remaining element, min, from [1] to [n-1],\n     * set hi to the index of the element AFTER which this one goes.\n     * Then, do the standard insertion sort shift on a character at a time\n     * basis for each element in the frob.\n     */\n    for (min = base; (hi = min += size) < max; ) {\n        while ((*compar)(hi -= size, min) > 0)\n            /* void */;\n        if ((hi += size) != min) {\n            for (lo = min + size; --lo >= min; ) {\n                c = *lo;\n                for (i = j = lo; (j -= size) >= hi; i = j)\n                    *i = *j;\n                *i = c;\n            }\n        }\n    }\n#endif\n}\n\n\n/*---------------------------------------------------------------------------*/\n/* Definition of static functions                                            */\n/*---------------------------------------------------------------------------*/\n\n/**\n * @brief Do a quicksort.\n *\n * @details First, find the median element, and put that one in the\n * first place as the discriminator.  (This \"median\" is just the\n * median of the first, last and middle elements).  (Using this median\n * instead of the first element is a big win).  Then, the usual\n * partitioning/swapping, followed by moving the discriminator into\n * the right place.  Then, figure out the sizes of the two partions,\n * do the smaller one recursively and the larger one via a repeat of\n * this code.  Stopping when there are less than THRESH elements in a\n * partition and cleaning up with an insertion sort (in our caller) is\n * a huge win.  All data swaps are done in-line, which is space-losing\n * but time-saving.  (And there are only three places where this is\n * done).\n */\n#ifndef USE_SYSTEM_QSORT\nstatic void\nqst(char *base, char *max, info_t const * info)\n{\n    char c, *i, *j, *jj;\n    int ii;\n    char *mid, *tmp;\n    intptr_t lo, hi;\n\n    /*\n     * At the top here, lo is the number of characters of elements in the\n     * current partition.  (Which should be max - base).\n     * Find the median of the first, last, and middle element and make\n     * that the middle element.  Set j to largest of first and middle.\n     * If max is larger than that guy, then it's that guy, else compare\n     * max with loser of first and take larger.  Things are set up to\n     * prefer the middle, then the first in case of ties.\n     */\n    lo = max - base;\t\t/* number of elements as chars */\n    do\t{\n        mid = i = base + info->qsz * ((lo / info->qsz) >> 1);\n        if (lo >= info->mthresh) {\n            j = ((*info->qcmp)((jj = base), i) > 0 ? jj : i);\n            if ((*info->qcmp)(j, (tmp = max - info->qsz)) > 0) {\n                /* switch to first loser */\n                j = (j == jj ? i : jj);\n                if ((*info->qcmp)(j, tmp) < 0)\n                    j = tmp;\n            }\n            if (j != i) {\n                ii = info->qsz;\n                do\t{\n                    c = *i;\n                    *i++ = *j;\n                    *j++ = c;\n                } while (--ii);\n            }\n        }\n        /*\n         * Semi-standard quicksort partitioning/swapping\n         */\n        for (i = base, j = max - info->qsz; ; ) {\n            while (i < mid && (*info->qcmp)(i, mid) <= 0)\n                i += info->qsz;\n            while (j > mid) {\n                if ((*info->qcmp)(mid, j) <= 0) {\n                    j -= info->qsz;\n                    continue;\n                }\n                tmp = i + info->qsz;\t/* value of i after swap */\n                if (i == mid) {\n                    /* j <-> mid, new mid is j */\n                    mid = jj = j;\n                } else {\n                    /* i <-> j */\n                    jj = j;\n                    j -= info->qsz;\n                }\n                goto swap;\n            }\n            if (i == mid) {\n                break;\n            } else {\n                /* i <-> mid, new mid is i */\n                jj = mid;\n                tmp = mid = i;\t/* value of i after swap */\n                j -= info->qsz;\n            }\n        swap:\n            ii = info->qsz;\n            do\t{\n                c = *i;\n                *i++ = *jj;\n                *jj++ = c;\n            } while (--ii);\n            i = tmp;\n        }\n        /*\n         * Look at sizes of the two partitions, do the smaller\n         * one first by recursion, then do the larger one by\n         * making sure lo is its size, base and max are update\n         * correctly, and branching back.  But only repeat\n         * (recursively or by branching) if the partition is\n         * of at least size THRESH.\n         */\n        i = (j = mid) + info->qsz;\n        if ((lo = j - base) <= (hi = max - i)) {\n            if (lo >= info->thresh)\n                qst(base, j, info);\n            base = i;\n            lo = hi;\n        } else {\n            if (hi >= info->thresh)\n                qst(i, max, info);\n            max = j;\n        }\n    } while (lo >= info->thresh);\n}\n#endif\n"
  },
  {
    "path": "cudd/util/util.h",
    "content": "/**\n  @file\n\n  @ingroup util\n\n  @brief Low-level utilities.\n\n  @copyright@parblock\n  Copyright (c) 1994-1998 The Regents of the Univ. of California.\n  All rights reserved.\n\n  Permission is hereby granted, without written agreement and without license\n  or royalty fees, to use, copy, modify, and distribute this software and its\n  documentation for any purpose, provided that the above copyright notice and\n  the following two paragraphs appear in all copies of this software.\n\n  IN NO EVENT SHALL THE UNIVERSITY OF CALIFORNIA BE LIABLE TO ANY PARTY FOR\n  DIRECT, INDIRECT, SPECIAL, INCIDENTAL, OR CONSEQUENTIAL DAMAGES ARISING OUT\n  OF THE USE OF THIS SOFTWARE AND ITS DOCUMENTATION, EVEN IF THE UNIVERSITY OF\n  CALIFORNIA HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.\n\n  THE UNIVERSITY OF CALIFORNIA SPECIFICALLY DISCLAIMS ANY WARRANTIES,\n  INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND\n  FITNESS FOR A PARTICULAR PURPOSE.  THE SOFTWARE PROVIDED HEREUNDER IS ON AN\n  \"AS IS\" BASIS, AND THE UNIVERSITY OF CALIFORNIA HAS NO OBLIGATION TO PROVIDE\n  MAINTENANCE, SUPPORT, UPDATES, ENHANCEMENTS, OR MODIFICATIONS.\n  @endparblock\n\n  @copyright@parblock\n  Copyright (c) 1999-2015, Regents of the University of Colorado\n\n  All rights reserved.\n\n  Redistribution and use in source and binary forms, with or without\n  modification, are permitted provided that the following conditions\n  are met:\n\n  Redistributions of source code must retain the above copyright\n  notice, this list of conditions and the following disclaimer.\n\n  Redistributions in binary form must reproduce the above copyright\n  notice, this list of conditions and the following disclaimer in the\n  documentation and/or other materials provided with the distribution.\n\n  Neither the name of the University of Colorado nor the names of its\n  contributors may be used to endorse or promote products derived from\n  this software without specific prior written permission.\n\n  THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS\n  \"AS IS\" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT\n  LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS\n  FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE\n  COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,\n  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,\n  BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;\n  LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER\n  CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT\n  LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN\n  ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE\n  POSSIBILITY OF SUCH DAMAGE.\n  @endparblock\n\n*/\n#ifndef UTIL_H_\n#define UTIL_H_\n\n#include \"config.h\"\n\n#if HAVE_ASSERT_H == 1\n#include <assert.h>\n#else\n#error assert.h is needed to build this package\n#endif\n\n#if HAVE_UNISTD_H == 1\n#include <unistd.h>\n#endif\n\n#include <stdio.h>\n#include <ctype.h>\n\n#if HAVE_STDLIB_H\n#include <stdlib.h>\n#else\n#error stdlib.h is needed to build this package\n#endif\n\n#if HAVE_STRING_H == 1\n#include <string.h>\n#else\n#error string.h is needed to build this package\n#endif\n\n#if HAVE_INTTYPES_H == 1\n#include <inttypes.h>\n#else\n#error inttypes.h is needed to build this package\n#endif\n\n/**\n * @def PRIszt\n * @brief Format string for a size_t value.\n */\n#if defined(_WIN32) && !defined(__USE_MINGW_ANSI_STDIO)\n#ifndef PRIuPTR\n#define PRIuPTR \"Iu\"\n#endif\n#ifndef PRIxPTR\n#define PRIxPTR \"Ix\"\n#endif\n#ifndef PRIiPTR\n#define PRIiPTR \"Id\"\n#endif\n#define PRIszt \"Iu\"\n#else\n#define PRIszt \"zu\"\n#endif\n\n/**\n * @def UTIL_UNUSED\n * @brief Macro to tell gcc that a variable is intentionally unused.\n */\n#if defined(__GNUC__)\n#if __GNUC__ > 2 || __GNUC_MINOR__ >= 7\n#define UTIL_UNUSED __attribute__ ((unused))\n#else\n#define UTIL_UNUSED\n#endif\n#else\n#define UTIL_UNUSED\n#endif\n\n/**\n * @brief Type-decorated NULL (for documentation).\n */\n#define NIL(type)\t\t((type *) 0)\n\n/* #define USE_MM */\t\t/* choose default memory allocator */\n\n/**\n * @def ALLOC\n * @brief Wrapper for either malloc or MMalloc.\n * @details Which function is wrapped depends on whether USE_MM is defined.\n */\n\n/**\n * @def REALLOC\n * @brief Wrapper for either realloc or MMrealloc.\n * @details Which function is wrapped depends on whether USE_MM is defined.\n */\n\n/**\n * @def FREE\n * @brief Wrapper for free.\n * @details Sets its argument to 0 after freeing.\n */\n\n#if defined(USE_MM)\n/* Assumes the memory manager is default one. */\n#define ALLOC(type, num)\t\\\n    ((type *) malloc(sizeof(type) * (num)))\n#define REALLOC(type, obj, num)\t\\\n    ((type *) realloc(obj, sizeof(type) * (num)))\n#else\n/* Use replacements that call MMoutOfMemory if allocation fails. */\n#define ALLOC(type, num)\t\\\n    ((type *) MMalloc(sizeof(type) * (size_t) (num)))\n#define REALLOC(type, obj, num)\t\\\n    ((type *) MMrealloc((obj), sizeof(type) * (size_t) (num)))\n#endif\n/* In any case, set to zero the pointer to freed memory. */\n#define FREE(obj) (free(obj), (obj) = 0)\n\n/**\n * @brief Prints message and terminates execution.\n */\n/*#define fail(why) {\\\n    (void) fprintf(stderr, \"Fatal error: file %s, line %d\\n%s\\n\",\\\n\t__FILE__, __LINE__, why);\\\n    (void) fflush(stdout);\\\n    abort();\\\n}*/\n\n/* These arguably do NOT belong in util.h */\n/**\n * @brief Computes the absolute value of its argument.\n */\n#define ABS(a)\t\t\t((a) < 0 ? -(a) : (a))\n/**\n * @brief Computes the maximum of its two arguments.\n */\n#define MAX(a,b)\t\t((a) > (b) ? (a) : (b))\n/**\n * @brief Computes the minimum of its two arguments.\n */\n#define MIN(a,b)\t\t((a) < (b) ? (a) : (b))\n\n/**\n * @brief Type of comparison functions for util_qsort.\n */\ntypedef int (*QSFP)(void const *, void const *);\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n#ifndef USE_MM\nextern void *MMalloc(size_t);\nextern void *MMrealloc(void *, size_t);\n#endif\nextern void MMout_of_memory(size_t);\nextern void (*MMoutOfMemory) (size_t);\n\nextern long util_cpu_time(void);\nextern long util_cpu_ctime(void);\nextern char *util_path_search(char const *);\nextern char *util_file_search(char const *, char *, char const *);\nextern void util_print_cpu_stats(FILE *);\nextern char *util_print_time(unsigned long);\nextern char *util_strsav(char const *);\nextern char *util_tilde_expand(char const *);\nextern size_t getSoftDataLimit(void);\nextern void util_qsort (void *vbase, int n, int size, QSFP compar);\nextern int util_pipefork(char * const * argv, FILE ** toCommand,\n                         FILE ** fromCommand, int * pid);\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* UTIL_H_ */\n"
  },
  {
    "path": "manual/Appendices/AllOnOnePage.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / All On One Page \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Appendices</span></h1>\n<hr />\n<h1>Explicit Model Files</h1>\n<p>This appendix details the plain text file formats used by PRISM for <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>exporting</a> and <a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>importing</a> models that have already been constructed, i.e., they comprise an explicit list of states, transitions, etc. making up the model, rather than a high-level model description in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM modelling language</a>.\nBelow, we describe:\n</p>\n<div class='vspace'></div><ul><li><a href='AllOnOnePage.html#tra'>Transitions (.tra) files</a>\n</li><li><a href='AllOnOnePage.html#trarows'>Transitions (.tra) files (row form)</a>\n</li><li><a href='AllOnOnePage.html#lab'>Labels (.lab) files</a>\n</li><li><a href='AllOnOnePage.html#srew'>State rewards (.srew) files</a>\n</li><li><a href='AllOnOnePage.html#trew'>Transition rewards (.trew) files</a>\n</li><li><a href='AllOnOnePage.html#sta'>State (.sta) files</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='tra' id='tra'></a>\n</p><h3>Transitions (.tra) files</h3>\n<p>These contain an explicit list of the transitions making up a probabilistic model, i.e. they are essentially a sparse matrix representation of the transition probability/rate matrix. The first line of the file contains information about the size of the model, the remaining lines contain information about transitions, one per line.\n</p>\n<p class='vspace'><strong>DTMCs and CTMCs</strong>\n</p>\n<p class='vspace'>For Markov chains the first line take the form \"<code>n m</code>\", giving the number of states (<code>n</code>) and the number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i j x</code>\" or \"<code>i j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, and <code>x</code> is the probability (for a DTMC) or rate (for a CTMC) of the transition. State indices are zero-indexed (i.e. between <code>0</code> and <code>n-1</code>). Probability/rate values are written as (positive) floating point numbers (examples: <code>0.5</code>, <code>.5</code>, <code>5.6e-6</code>, <code>1</code>). <code>a</code> is optional and gives the action label for the transition. Action labels can be present for some, all or no transitions.\n</p>\n<p class='vspace'>It is assumed that source states (rows) are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each source state.\n</p>\n<p class='vspace'>For a DTMC, the probabilities for the outgoing transitions of each state should sum to 1.\n</p>\n<p class='vspace'>Here is an example, for the (DTMC) PRISM model <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (which looks like <a class='urllink' href='../uploads/lec3.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 1 0.5<br />\n0 3 0.5<br />\n1 0 0.5<br />\n1 2 0.25<br />\n1 4 0.25<br />\n2 5 1<br />\n3 3 1<br />\n4 4 1<br />\n5 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is one for the (CTMC) PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a> (which looks like <a class='urllink' href='../uploads/poll2.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"text\">12 22<br />\n0 1 0.5<br />\n0 2 0.5<br />\n0 6 200<br />\n1 3 0.5<br />\n1 7 200<br />\n2 3 0.5<br />\n2 4 200<br />\n3 5 200<br />\n4 5 0.5<br />\n4 6 1<br />\n5 7 1<br />\n6 0 200<br />\n6 7 0.5<br />\n6 8 0.5<br />\n7 9 0.5<br />\n7 10 200<br />\n8 2 200<br />\n8 9 0.5<br />\n9 11 200<br />\n10 0 1<br />\n10 11 0.5<br />\n11 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>MDPs (or PAs)</strong>\n</p>\n<p class='vspace'>For MDPs, the format is an extension of the above\nTo clarify terminology: each <em>state</em> of the MDP contains (nondeterministic) <em>choices</em>, each of which is essentially a probability distribution over successor states that we can view as a set of <em>transitions</em>. Optionally, each choice can be labelled with an <em>action</em>.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m</code>\", giving the number of states (<code>n</code>), the total number of choices (<code>c</code>) and the total number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i k j x</code>\" or \"<code>i k j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, <code>k</code> is the index of the choice that it belongs to, and <code>x</code> is the probability of the transition. <code>a</code> is optional and gives the action label for the choice of the transition. Action labels can be present for some, all or no states but, in slightly redundant fashion, the action labels, if present, must be the same for all transitions belonging to the same choice.\n</p>\n<p class='vspace'>State indices and choice indices are all zero-indexed. Probability values (as above) are written as (positive) floating point numbers and should sum to 1 for each choice.\nIt is assumed that source states (rows) and choices within states are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each choice.\n</p>\n<p class='vspace'>Here is an example, for the (MDP) PRISM model <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdp.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 <br />\n1 0 0 0.7 <br />\n1 0 1 0.3 <br />\n1 1 2 0.5 <br />\n1 1 3 0.5 <br />\n2 0 2 1 <br />\n3 0 3 1 </div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is an action-labelled version of the same model, <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdpa.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 a<br />\n1 0 2 0.5 c<br />\n1 0 3 0.5 c<br />\n1 1 0 0.7 b<br />\n1 1 1 0.3 b<br />\n2 0 2 1 a<br />\n3 0 3 1 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>POMDPs</strong>\n</p>\n<p class='vspace'>The format of a <code>.tra</code> file for a POMDP is similar to an MDP,\nbut also contains information about observations.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m o</code>\", where <code>n</code>, <code>c</code> and <code>m</code> are, as for MDPs, the numbers of states, choices and transitions,\nand <code>o</code> is the number of observations.\nThe lines that list transitions contain an additional integer after the transition probability\n(and before the action, if present), giving the (deterministic) observation that is made\nwhen entering the target state of that transition.\nCurrently, it is assumed that these are consistent for all states.\n</p>\n<p class='vspace'>In order to also specify the observation for the initial state,\na dummy transition line of the form <code>- - s - o</code> is used,\ngiving both the initial state <code>s</code> and its observation <code>o</code>.\n</p>\n<p class='vspace'>An example file is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"text\">10 16 18 4<br />\n- - 0 - 0<br />\n0 0 1 0.1 1 toss<br />\n0 0 2 0.3 1 toss<br />\n0 0 3 0.6 1 toss<br />\n1 0 4 1 2 guess1<br />\n1 1 7 1 3 guess2<br />\n1 2 7 1 3 guess3<br />\n2 0 8 1 3 guess1<br />\n2 1 5 1 2 guess2<br />\n2 2 8 1 3 guess3<br />\n3 0 9 1 3 guess1<br />\n3 1 9 1 3 guess2<br />\n3 2 6 1 2 guess3<br />\n4 0 4 1 2 loop<br />\n5 0 5 1 2 loop<br />\n6 0 6 1 2 loop<br />\n7 0 7 1 3<br />\n8 0 8 1 3<br />\n9 0 9 1 3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trarows' id='trarows'></a>\n</p><h3>Transitions (.tra) files (row form)</h3>\n<p>There is alternative format for transition matrices (see the <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html#other'>rows</a> option for <code>-exportmodel</code>) where transitions for each state/choice are collated on a single line.\n</p>\n<p class='vspace'>Here is the result for the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> example from above (a DTMC):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 0.5:1 0.5:3<br />\n1 0.5:0 0.25:2 0.25:4<br />\n2 1:5<br />\n3 1:3<br />\n4 1:4<br />\n5 1:2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> example (an MDP):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 <br />\n1 0.7:0 0.3:1 <br />\n1 0.5:2 0.5:3 <br />\n2 1:2 <br />\n3 1:3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and for the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> example (an MDP with actions):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 a<br />\n1 0.5:2 0.5:3 c<br />\n1 0.7:0 0.3:1 b<br />\n2 1:2 a<br />\n3 1:3 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='lab' id='lab'></a>\n</p><h3>Labels (.lab) files</h3>\n<p>These contain an explicit list of which <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> are satisfied in each state.\nThe first line lists the labels, assigning each one an index.\nThe remaining lines list indices of all states satisfying one or more labels,\nfollowed by a list of the the indices of labels that that are satisfied in it.\nThis includes the built-in labels <code>\"init\"</code> (initial states) and <code>deadlock</code> (deadlock states).\nAn example is shown below, where, for example, both <code>\"heads\"</code> and <code>\"end\"</code> are satisfied in state 2.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"text\">0=&quot;init&quot; 1=&quot;deadlock&quot; 2=&quot;heads&quot; 3=&quot;tails&quot; 4=&quot;end&quot;<br />\n0: 0<br />\n2: 2 4<br />\n3: 3 4</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='srew' id='srew'></a>\n</p><h3>State rewards (.srew) files</h3>\n<p>Reward files contain an (optional) header, giving the name of the reward structure that generated it\nand the type of rewards (state or transitions) stored in the file.\nFor state rewards, the information following this header is an explicit list of the (non-zero) state rewards.\nThe first line is of the form <code>n m</code> where <code>n</code> is the number of states in the model and <code>m</code> is the number of non-zero state rewards.\nThe following <code>m</code> lines are of the form <code>i r</code>, denoting that the state reward for state <code>i</code> is <code>r</code>.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get rewards in 3 states (0, 4 and 5):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure &quot;r&quot;<br />\n# State rewards<br />\n6 3<br />\n0 2<br />\n4 1<br />\n5 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trew' id='trew'></a>\n</p><h3>Transition rewards (.trew) files</h3>\n<p>Files containing transition rewards, like those for state rewards, start with an (optional) header.\nThe rest of the file is formatted identically to transitions files (see <a href='AllOnOnePage.html#tra'>above</a>),\nexcept that probabilities/rates are replaced with reward values,\nand the number of transitions (the last number on the first line) is replaced with the number of non-zero transition rewards.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n6 4<br />\n1 0 1<br />\n1 2 1<br />\n1 4 1<br />\n2 5 2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And or the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (4-state) MDP example, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n4 5 4<br />\n1 0 2 6<br />\n1 0 3 6<br />\n1 1 0 5<br />\n1 1 1 5</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='sta' id='sta'></a>\n</p><h3>States (.sta) files</h3>\n<p>These contain an explicit list of the reachable states of a model. The first line is of the form <code>(v1,...,vn)</code>, listing the names of all the variables in the model in the order that they appear in the PRISM model. Subsequent lines list the values of the <code>n</code> variables in each state of the model. Each line is of the form <code>i:(x1,...,xn)</code>, where <code>i</code> is the index of the state (starting from 0) and <code>x1,...,xn</code> are the values of each variable in the state. States are ordered by their index (and, therefore, given PRISM's default behaviour, lexicographically according to the tuple of variable values).\n</p>\n<p class='vspace'>For the example PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a>, the states file looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"text\">(s,a,s1,s2)<br />\n0:(1,0,0,0)<br />\n1:(1,0,0,1)<br />\n2:(1,0,1,0)<br />\n3:(1,0,1,1)<br />\n4:(1,1,1,0)<br />\n5:(1,1,1,1)<br />\n6:(2,0,0,0)<br />\n7:(2,0,0,1)<br />\n8:(2,0,1,0)<br />\n9:(2,0,1,1)<br />\n10:(2,1,0,1)<br />\n11:(2,1,1,1)</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 13, 2013, at 11:23 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='wikilink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/AllOnOnePage@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / All On One Page | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Appendices</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 13, 2013, at 11:23 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='wikilink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/AllOnOnePage@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / All On One Page | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Appendices</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 13, 2013, at 11:23 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='wikilink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/AllOnOnePage@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Appendices / AllOnOnePage </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Appendices</span></h1>\n<hr />\n<h1>Explicit Model Files</h1>\n<p>This appendix details the plain text file formats used by PRISM for <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>exporting</a> and <a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>importing</a> models that have already been constructed, i.e., they comprise an explicit list of states, transitions, etc. making up the model, rather than a high-level model description in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM modelling language</a>.\nBelow, we describe:\n</p>\n<div class='vspace'></div><ul><li><a href='AllOnOnePage@action=print.html#tra'>Transitions (.tra) files</a>\n</li><li><a href='AllOnOnePage@action=print.html#trarows'>Transitions (.tra) files (row form)</a>\n</li><li><a href='AllOnOnePage@action=print.html#lab'>Labels (.lab) files</a>\n</li><li><a href='AllOnOnePage@action=print.html#srew'>State rewards (.srew) files</a>\n</li><li><a href='AllOnOnePage@action=print.html#trew'>Transition rewards (.trew) files</a>\n</li><li><a href='AllOnOnePage@action=print.html#sta'>State (.sta) files</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='tra' id='tra'></a>\n</p><h3>Transitions (.tra) files</h3>\n<p>These contain an explicit list of the transitions making up a probabilistic model, i.e. they are essentially a sparse matrix representation of the transition probability/rate matrix. The first line of the file contains information about the size of the model, the remaining lines contain information about transitions, one per line.\n</p>\n<p class='vspace'><strong>DTMCs and CTMCs</strong>\n</p>\n<p class='vspace'>For Markov chains the first line take the form \"<code>n m</code>\", giving the number of states (<code>n</code>) and the number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i j x</code>\" or \"<code>i j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, and <code>x</code> is the probability (for a DTMC) or rate (for a CTMC) of the transition. State indices are zero-indexed (i.e. between <code>0</code> and <code>n-1</code>). Probability/rate values are written as (positive) floating point numbers (examples: <code>0.5</code>, <code>.5</code>, <code>5.6e-6</code>, <code>1</code>). <code>a</code> is optional and gives the action label for the transition. Action labels can be present for some, all or no transitions.\n</p>\n<p class='vspace'>It is assumed that source states (rows) are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each source state.\n</p>\n<p class='vspace'>For a DTMC, the probabilities for the outgoing transitions of each state should sum to 1.\n</p>\n<p class='vspace'>Here is an example, for the (DTMC) PRISM model <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (which looks like <a class='urllink' href='../uploads/lec3.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 1 0.5<br />\n0 3 0.5<br />\n1 0 0.5<br />\n1 2 0.25<br />\n1 4 0.25<br />\n2 5 1<br />\n3 3 1<br />\n4 4 1<br />\n5 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is one for the (CTMC) PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a> (which looks like <a class='urllink' href='../uploads/poll2.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"text\">12 22<br />\n0 1 0.5<br />\n0 2 0.5<br />\n0 6 200<br />\n1 3 0.5<br />\n1 7 200<br />\n2 3 0.5<br />\n2 4 200<br />\n3 5 200<br />\n4 5 0.5<br />\n4 6 1<br />\n5 7 1<br />\n6 0 200<br />\n6 7 0.5<br />\n6 8 0.5<br />\n7 9 0.5<br />\n7 10 200<br />\n8 2 200<br />\n8 9 0.5<br />\n9 11 200<br />\n10 0 1<br />\n10 11 0.5<br />\n11 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>MDPs (or PAs)</strong>\n</p>\n<p class='vspace'>For MDPs, the format is an extension of the above\nTo clarify terminology: each <em>state</em> of the MDP contains (nondeterministic) <em>choices</em>, each of which is essentially a probability distribution over successor states that we can view as a set of <em>transitions</em>. Optionally, each choice can be labelled with an <em>action</em>.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m</code>\", giving the number of states (<code>n</code>), the total number of choices (<code>c</code>) and the total number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i k j x</code>\" or \"<code>i k j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, <code>k</code> is the index of the choice that it belongs to, and <code>x</code> is the probability of the transition. <code>a</code> is optional and gives the action label for the choice of the transition. Action labels can be present for some, all or no states but, in slightly redundant fashion, the action labels, if present, must be the same for all transitions belonging to the same choice.\n</p>\n<p class='vspace'>State indices and choice indices are all zero-indexed. Probability values (as above) are written as (positive) floating point numbers and should sum to 1 for each choice.\nIt is assumed that source states (rows) and choices within states are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each choice.\n</p>\n<p class='vspace'>Here is an example, for the (MDP) PRISM model <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdp.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 <br />\n1 0 0 0.7 <br />\n1 0 1 0.3 <br />\n1 1 2 0.5 <br />\n1 1 3 0.5 <br />\n2 0 2 1 <br />\n3 0 3 1 </div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is an action-labelled version of the same model, <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdpa.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 a<br />\n1 0 2 0.5 c<br />\n1 0 3 0.5 c<br />\n1 1 0 0.7 b<br />\n1 1 1 0.3 b<br />\n2 0 2 1 a<br />\n3 0 3 1 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>POMDPs</strong>\n</p>\n<p class='vspace'>The format of a <code>.tra</code> file for a POMDP is similar to an MDP,\nbut also contains information about observations.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m o</code>\", where <code>n</code>, <code>c</code> and <code>m</code> are, as for MDPs, the numbers of states, choices and transitions,\nand <code>o</code> is the number of observations.\nThe lines that list transitions contain an additional integer after the transition probability\n(and before the action, if present), giving the (deterministic) observation that is made\nwhen entering the target state of that transition.\nCurrently, it is assumed that these are consistent for all states.\n</p>\n<p class='vspace'>In order to also specify the observation for the initial state,\na dummy transition line of the form <code>- - s - o</code> is used,\ngiving both the initial state <code>s</code> and its observation <code>o</code>.\n</p>\n<p class='vspace'>An example file is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"text\">10 16 18 4<br />\n- - 0 - 0<br />\n0 0 1 0.1 1 toss<br />\n0 0 2 0.3 1 toss<br />\n0 0 3 0.6 1 toss<br />\n1 0 4 1 2 guess1<br />\n1 1 7 1 3 guess2<br />\n1 2 7 1 3 guess3<br />\n2 0 8 1 3 guess1<br />\n2 1 5 1 2 guess2<br />\n2 2 8 1 3 guess3<br />\n3 0 9 1 3 guess1<br />\n3 1 9 1 3 guess2<br />\n3 2 6 1 2 guess3<br />\n4 0 4 1 2 loop<br />\n5 0 5 1 2 loop<br />\n6 0 6 1 2 loop<br />\n7 0 7 1 3<br />\n8 0 8 1 3<br />\n9 0 9 1 3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trarows' id='trarows'></a>\n</p><h3>Transitions (.tra) files (row form)</h3>\n<p>There is alternative format for transition matrices (see the <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html#other'>rows</a> option for <code>-exportmodel</code>) where transitions for each state/choice are collated on a single line.\n</p>\n<p class='vspace'>Here is the result for the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> example from above (a DTMC):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 0.5:1 0.5:3<br />\n1 0.5:0 0.25:2 0.25:4<br />\n2 1:5<br />\n3 1:3<br />\n4 1:4<br />\n5 1:2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> example (an MDP):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 <br />\n1 0.7:0 0.3:1 <br />\n1 0.5:2 0.5:3 <br />\n2 1:2 <br />\n3 1:3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and for the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> example (an MDP with actions):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 a<br />\n1 0.5:2 0.5:3 c<br />\n1 0.7:0 0.3:1 b<br />\n2 1:2 a<br />\n3 1:3 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='lab' id='lab'></a>\n</p><h3>Labels (.lab) files</h3>\n<p>These contain an explicit list of which <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> are satisfied in each state.\nThe first line lists the labels, assigning each one an index.\nThe remaining lines list indices of all states satisfying one or more labels,\nfollowed by a list of the the indices of labels that that are satisfied in it.\nThis includes the built-in labels <code>\"init\"</code> (initial states) and <code>deadlock</code> (deadlock states).\nAn example is shown below, where, for example, both <code>\"heads\"</code> and <code>\"end\"</code> are satisfied in state 2.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"text\">0=&quot;init&quot; 1=&quot;deadlock&quot; 2=&quot;heads&quot; 3=&quot;tails&quot; 4=&quot;end&quot;<br />\n0: 0<br />\n2: 2 4<br />\n3: 3 4</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='srew' id='srew'></a>\n</p><h3>State rewards (.srew) files</h3>\n<p>Reward files contain an (optional) header, giving the name of the reward structure that generated it\nand the type of rewards (state or transitions) stored in the file.\nFor state rewards, the information following this header is an explicit list of the (non-zero) state rewards.\nThe first line is of the form <code>n m</code> where <code>n</code> is the number of states in the model and <code>m</code> is the number of non-zero state rewards.\nThe following <code>m</code> lines are of the form <code>i r</code>, denoting that the state reward for state <code>i</code> is <code>r</code>.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get rewards in 3 states (0, 4 and 5):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure &quot;r&quot;<br />\n# State rewards<br />\n6 3<br />\n0 2<br />\n4 1<br />\n5 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trew' id='trew'></a>\n</p><h3>Transition rewards (.trew) files</h3>\n<p>Files containing transition rewards, like those for state rewards, start with an (optional) header.\nThe rest of the file is formatted identically to transitions files (see <a href='AllOnOnePage@action=print.html#tra'>above</a>),\nexcept that probabilities/rates are replaced with reward values,\nand the number of transitions (the last number on the first line) is replaced with the number of non-zero transition rewards.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n6 4<br />\n1 0 1<br />\n1 2 1<br />\n1 4 1<br />\n2 5 2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And or the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (4-state) MDP example, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n4 5 4<br />\n1 0 2 6<br />\n1 0 3 6<br />\n1 1 0 5<br />\n1 1 1 5</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='sta' id='sta'></a>\n</p><h3>States (.sta) files</h3>\n<p>These contain an explicit list of the reachable states of a model. The first line is of the form <code>(v1,...,vn)</code>, listing the names of all the variables in the model in the order that they appear in the PRISM model. Subsequent lines list the values of the <code>n</code> variables in each state of the model. Each line is of the form <code>i:(x1,...,xn)</code>, where <code>i</code> is the index of the state (starting from 0) and <code>x1,...,xn</code> are the values of each variable in the state. States are ordered by their index (and, therefore, given PRISM's default behaviour, lexicographically according to the tuple of variable values).\n</p>\n<p class='vspace'>For the example PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a>, the states file looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"text\">(s,a,s1,s2)<br />\n0:(1,0,0,0)<br />\n1:(1,0,0,1)<br />\n2:(1,0,1,0)<br />\n3:(1,0,1,1)<br />\n4:(1,1,1,0)<br />\n5:(1,1,1,1)<br />\n6:(2,0,0,0)<br />\n7:(2,0,0,1)<br />\n8:(2,0,1,0)<br />\n9:(2,0,1,1)<br />\n10:(2,1,0,1)<br />\n11:(2,1,1,1)</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/ExplicitModelFiles.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / Explicit Model Files \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExplicitModelFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Appendices</a> /\n</p><h1>Explicit Model Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>This appendix details the plain text file formats used by PRISM for <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>exporting</a> and <a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>importing</a> models that have already been constructed, i.e., they comprise an explicit list of states, transitions, etc. making up the model, rather than a high-level model description in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM modelling language</a>.\nBelow, we describe:\n</p>\n<div class='vspace'></div><ul><li><a href='ExplicitModelFiles.html#tra'>Transitions (.tra) files</a>\n</li><li><a href='ExplicitModelFiles.html#trarows'>Transitions (.tra) files (row form)</a>\n</li><li><a href='ExplicitModelFiles.html#lab'>Labels (.lab) files</a>\n</li><li><a href='ExplicitModelFiles.html#srew'>State rewards (.srew) files</a>\n</li><li><a href='ExplicitModelFiles.html#trew'>Transition rewards (.trew) files</a>\n</li><li><a href='ExplicitModelFiles.html#sta'>State (.sta) files</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='tra' id='tra'></a>\n</p><h3>Transitions (.tra) files</h3>\n<p>These contain an explicit list of the transitions making up a probabilistic model, i.e. they are essentially a sparse matrix representation of the transition probability/rate matrix. The first line of the file contains information about the size of the model, the remaining lines contain information about transitions, one per line.\n</p>\n<p class='vspace'><strong>DTMCs and CTMCs</strong>\n</p>\n<p class='vspace'>For Markov chains the first line take the form \"<code>n m</code>\", giving the number of states (<code>n</code>) and the number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i j x</code>\" or \"<code>i j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, and <code>x</code> is the probability (for a DTMC) or rate (for a CTMC) of the transition. State indices are zero-indexed (i.e. between <code>0</code> and <code>n-1</code>). Probability/rate values are written as (positive) floating point numbers (examples: <code>0.5</code>, <code>.5</code>, <code>5.6e-6</code>, <code>1</code>). <code>a</code> is optional and gives the action label for the transition. Action labels can be present for some, all or no transitions.\n</p>\n<p class='vspace'>It is assumed that source states (rows) are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each source state.\n</p>\n<p class='vspace'>For a DTMC, the probabilities for the outgoing transitions of each state should sum to 1.\n</p>\n<p class='vspace'>Here is an example, for the (DTMC) PRISM model <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (which looks like <a class='urllink' href='../uploads/lec3.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 1 0.5<br />\n0 3 0.5<br />\n1 0 0.5<br />\n1 2 0.25<br />\n1 4 0.25<br />\n2 5 1<br />\n3 3 1<br />\n4 4 1<br />\n5 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is one for the (CTMC) PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a> (which looks like <a class='urllink' href='../uploads/poll2.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"text\">12 22<br />\n0 1 0.5<br />\n0 2 0.5<br />\n0 6 200<br />\n1 3 0.5<br />\n1 7 200<br />\n2 3 0.5<br />\n2 4 200<br />\n3 5 200<br />\n4 5 0.5<br />\n4 6 1<br />\n5 7 1<br />\n6 0 200<br />\n6 7 0.5<br />\n6 8 0.5<br />\n7 9 0.5<br />\n7 10 200<br />\n8 2 200<br />\n8 9 0.5<br />\n9 11 200<br />\n10 0 1<br />\n10 11 0.5<br />\n11 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>MDPs (or PAs)</strong>\n</p>\n<p class='vspace'>For MDPs, the format is an extension of the above\nTo clarify terminology: each <em>state</em> of the MDP contains (nondeterministic) <em>choices</em>, each of which is essentially a probability distribution over successor states that we can view as a set of <em>transitions</em>. Optionally, each choice can be labelled with an <em>action</em>.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m</code>\", giving the number of states (<code>n</code>), the total number of choices (<code>c</code>) and the total number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i k j x</code>\" or \"<code>i k j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, <code>k</code> is the index of the choice that it belongs to, and <code>x</code> is the probability of the transition. <code>a</code> is optional and gives the action label for the choice of the transition. Action labels can be present for some, all or no states but, in slightly redundant fashion, the action labels, if present, must be the same for all transitions belonging to the same choice.\n</p>\n<p class='vspace'>State indices and choice indices are all zero-indexed. Probability values (as above) are written as (positive) floating point numbers and should sum to 1 for each choice.\nIt is assumed that source states (rows) and choices within states are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each choice.\n</p>\n<p class='vspace'>Here is an example, for the (MDP) PRISM model <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdp.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 <br />\n1 0 0 0.7 <br />\n1 0 1 0.3 <br />\n1 1 2 0.5 <br />\n1 1 3 0.5 <br />\n2 0 2 1 <br />\n3 0 3 1 </div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is an action-labelled version of the same model, <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdpa.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 a<br />\n1 0 2 0.5 c<br />\n1 0 3 0.5 c<br />\n1 1 0 0.7 b<br />\n1 1 1 0.3 b<br />\n2 0 2 1 a<br />\n3 0 3 1 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>POMDPs</strong>\n</p>\n<p class='vspace'>The format of a <code>.tra</code> file for a POMDP is similar to an MDP,\nbut also contains information about observations.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m o</code>\", where <code>n</code>, <code>c</code> and <code>m</code> are, as for MDPs, the numbers of states, choices and transitions,\nand <code>o</code> is the number of observations.\nThe lines that list transitions contain an additional integer after the transition probability\n(and before the action, if present), giving the (deterministic) observation that is made\nwhen entering the target state of that transition.\nCurrently, it is assumed that these are consistent for all states.\n</p>\n<p class='vspace'>In order to also specify the observation for the initial state,\na dummy transition line of the form <code>- - s - o</code> is used,\ngiving both the initial state <code>s</code> and its observation <code>o</code>.\n</p>\n<p class='vspace'>An example file is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"text\">10 16 18 4<br />\n- - 0 - 0<br />\n0 0 1 0.1 1 toss<br />\n0 0 2 0.3 1 toss<br />\n0 0 3 0.6 1 toss<br />\n1 0 4 1 2 guess1<br />\n1 1 7 1 3 guess2<br />\n1 2 7 1 3 guess3<br />\n2 0 8 1 3 guess1<br />\n2 1 5 1 2 guess2<br />\n2 2 8 1 3 guess3<br />\n3 0 9 1 3 guess1<br />\n3 1 9 1 3 guess2<br />\n3 2 6 1 2 guess3<br />\n4 0 4 1 2 loop<br />\n5 0 5 1 2 loop<br />\n6 0 6 1 2 loop<br />\n7 0 7 1 3<br />\n8 0 8 1 3<br />\n9 0 9 1 3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trarows' id='trarows'></a>\n</p><h3>Transitions (.tra) files (row form)</h3>\n<p>There is alternative format for transition matrices (see the <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html#other'>rows</a> option for <code>-exportmodel</code>) where transitions for each state/choice are collated on a single line.\n</p>\n<p class='vspace'>Here is the result for the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> example from above (a DTMC):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 0.5:1 0.5:3<br />\n1 0.5:0 0.25:2 0.25:4<br />\n2 1:5<br />\n3 1:3<br />\n4 1:4<br />\n5 1:2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> example (an MDP):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 <br />\n1 0.7:0 0.3:1 <br />\n1 0.5:2 0.5:3 <br />\n2 1:2 <br />\n3 1:3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and for the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> example (an MDP with actions):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 a<br />\n1 0.5:2 0.5:3 c<br />\n1 0.7:0 0.3:1 b<br />\n2 1:2 a<br />\n3 1:3 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='lab' id='lab'></a>\n</p><h3>Labels (.lab) files</h3>\n<p>These contain an explicit list of which <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> are satisfied in each state.\nThe first line lists the labels, assigning each one an index.\nThe remaining lines list indices of all states satisfying one or more labels,\nfollowed by a list of the the indices of labels that that are satisfied in it.\nThis includes the built-in labels <code>\"init\"</code> (initial states) and <code>deadlock</code> (deadlock states).\nAn example is shown below, where, for example, both <code>\"heads\"</code> and <code>\"end\"</code> are satisfied in state 2.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"text\">0=&quot;init&quot; 1=&quot;deadlock&quot; 2=&quot;heads&quot; 3=&quot;tails&quot; 4=&quot;end&quot;<br />\n0: 0<br />\n2: 2 4<br />\n3: 3 4</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='srew' id='srew'></a>\n</p><h3>State rewards (.srew) files</h3>\n<p>Reward files contain an (optional) header, giving the name of the reward structure that generated it\nand the type of rewards (state or transitions) stored in the file.\nFor state rewards, the information following this header is an explicit list of the (non-zero) state rewards.\nThe first line is of the form <code>n m</code> where <code>n</code> is the number of states in the model and <code>m</code> is the number of non-zero state rewards.\nThe following <code>m</code> lines are of the form <code>i r</code>, denoting that the state reward for state <code>i</code> is <code>r</code>.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get rewards in 3 states (0, 4 and 5):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure &quot;r&quot;<br />\n# State rewards<br />\n6 3<br />\n0 2<br />\n4 1<br />\n5 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trew' id='trew'></a>\n</p><h3>Transition rewards (.trew) files</h3>\n<p>Files containing transition rewards, like those for state rewards, start with an (optional) header.\nThe rest of the file is formatted identically to transitions files (see <a href='ExplicitModelFiles.html#tra'>above</a>),\nexcept that probabilities/rates are replaced with reward values,\nand the number of transitions (the last number on the first line) is replaced with the number of non-zero transition rewards.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n6 4<br />\n1 0 1<br />\n1 2 1<br />\n1 4 1<br />\n2 5 2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And or the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (4-state) MDP example, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n4 5 4<br />\n1 0 2 6<br />\n1 0 3 6<br />\n1 1 0 5<br />\n1 1 1 5</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='sta' id='sta'></a>\n</p><h3>States (.sta) files</h3>\n<p>These contain an explicit list of the reachable states of a model. The first line is of the form <code>(v1,...,vn)</code>, listing the names of all the variables in the model in the order that they appear in the PRISM model. Subsequent lines list the values of the <code>n</code> variables in each state of the model. Each line is of the form <code>i:(x1,...,xn)</code>, where <code>i</code> is the index of the state (starting from 0) and <code>x1,...,xn</code> are the values of each variable in the state. States are ordered by their index (and, therefore, given PRISM's default behaviour, lexicographically according to the tuple of variable values).\n</p>\n<p class='vspace'>For the example PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a>, the states file looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"text\">(s,a,s1,s2)<br />\n0:(1,0,0,0)<br />\n1:(1,0,0,1)<br />\n2:(1,0,1,0)<br />\n3:(1,0,1,1)<br />\n4:(1,1,1,0)<br />\n5:(1,1,1,1)<br />\n6:(2,0,0,0)<br />\n7:(2,0,0,1)<br />\n8:(2,0,1,0)<br />\n9:(2,0,1,1)<br />\n10:(2,1,0,1)<br />\n11:(2,1,1,1)</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExplicitModelFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 09:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='selflink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/ExplicitModelFiles@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / Explicit Model Files | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExplicitModelFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Appendices</a> /\n</p><h1>Explicit Model Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ExplicitModelFiles@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExplicitModelFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 09:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='selflink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/ExplicitModelFiles@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / Explicit Model Files | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExplicitModelFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Appendices</a> /\n</p><h1>Explicit Model Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ExplicitModelFiles@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExplicitModelFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 09:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='selflink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/ExplicitModelFiles@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Appendices / ExplicitModelFiles </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Appendices</a> /\n</p><h1>Explicit Model Files</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>This appendix details the plain text file formats used by PRISM for <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>exporting</a> and <a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>importing</a> models that have already been constructed, i.e., they comprise an explicit list of states, transitions, etc. making up the model, rather than a high-level model description in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM modelling language</a>.\nBelow, we describe:\n</p>\n<div class='vspace'></div><ul><li><a href='ExplicitModelFiles@action=print.html#tra'>Transitions (.tra) files</a>\n</li><li><a href='ExplicitModelFiles@action=print.html#trarows'>Transitions (.tra) files (row form)</a>\n</li><li><a href='ExplicitModelFiles@action=print.html#lab'>Labels (.lab) files</a>\n</li><li><a href='ExplicitModelFiles@action=print.html#srew'>State rewards (.srew) files</a>\n</li><li><a href='ExplicitModelFiles@action=print.html#trew'>Transition rewards (.trew) files</a>\n</li><li><a href='ExplicitModelFiles@action=print.html#sta'>State (.sta) files</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='tra' id='tra'></a>\n</p><h3>Transitions (.tra) files</h3>\n<p>These contain an explicit list of the transitions making up a probabilistic model, i.e. they are essentially a sparse matrix representation of the transition probability/rate matrix. The first line of the file contains information about the size of the model, the remaining lines contain information about transitions, one per line.\n</p>\n<p class='vspace'><strong>DTMCs and CTMCs</strong>\n</p>\n<p class='vspace'>For Markov chains the first line take the form \"<code>n m</code>\", giving the number of states (<code>n</code>) and the number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i j x</code>\" or \"<code>i j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, and <code>x</code> is the probability (for a DTMC) or rate (for a CTMC) of the transition. State indices are zero-indexed (i.e. between <code>0</code> and <code>n-1</code>). Probability/rate values are written as (positive) floating point numbers (examples: <code>0.5</code>, <code>.5</code>, <code>5.6e-6</code>, <code>1</code>). <code>a</code> is optional and gives the action label for the transition. Action labels can be present for some, all or no transitions.\n</p>\n<p class='vspace'>It is assumed that source states (rows) are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each source state.\n</p>\n<p class='vspace'>For a DTMC, the probabilities for the outgoing transitions of each state should sum to 1.\n</p>\n<p class='vspace'>Here is an example, for the (DTMC) PRISM model <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (which looks like <a class='urllink' href='../uploads/lec3.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 1 0.5<br />\n0 3 0.5<br />\n1 0 0.5<br />\n1 2 0.25<br />\n1 4 0.25<br />\n2 5 1<br />\n3 3 1<br />\n4 4 1<br />\n5 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is one for the (CTMC) PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a> (which looks like <a class='urllink' href='../uploads/poll2.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"text\">12 22<br />\n0 1 0.5<br />\n0 2 0.5<br />\n0 6 200<br />\n1 3 0.5<br />\n1 7 200<br />\n2 3 0.5<br />\n2 4 200<br />\n3 5 200<br />\n4 5 0.5<br />\n4 6 1<br />\n5 7 1<br />\n6 0 200<br />\n6 7 0.5<br />\n6 8 0.5<br />\n7 9 0.5<br />\n7 10 200<br />\n8 2 200<br />\n8 9 0.5<br />\n9 11 200<br />\n10 0 1<br />\n10 11 0.5<br />\n11 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>MDPs (or PAs)</strong>\n</p>\n<p class='vspace'>For MDPs, the format is an extension of the above\nTo clarify terminology: each <em>state</em> of the MDP contains (nondeterministic) <em>choices</em>, each of which is essentially a probability distribution over successor states that we can view as a set of <em>transitions</em>. Optionally, each choice can be labelled with an <em>action</em>.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m</code>\", giving the number of states (<code>n</code>), the total number of choices (<code>c</code>) and the total number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i k j x</code>\" or \"<code>i k j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, <code>k</code> is the index of the choice that it belongs to, and <code>x</code> is the probability of the transition. <code>a</code> is optional and gives the action label for the choice of the transition. Action labels can be present for some, all or no states but, in slightly redundant fashion, the action labels, if present, must be the same for all transitions belonging to the same choice.\n</p>\n<p class='vspace'>State indices and choice indices are all zero-indexed. Probability values (as above) are written as (positive) floating point numbers and should sum to 1 for each choice.\nIt is assumed that source states (rows) and choices within states are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each choice.\n</p>\n<p class='vspace'>Here is an example, for the (MDP) PRISM model <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdp.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 <br />\n1 0 0 0.7 <br />\n1 0 1 0.3 <br />\n1 1 2 0.5 <br />\n1 1 3 0.5 <br />\n2 0 2 1 <br />\n3 0 3 1 </div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is an action-labelled version of the same model, <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdpa.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 a<br />\n1 0 2 0.5 c<br />\n1 0 3 0.5 c<br />\n1 1 0 0.7 b<br />\n1 1 1 0.3 b<br />\n2 0 2 1 a<br />\n3 0 3 1 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>POMDPs</strong>\n</p>\n<p class='vspace'>The format of a <code>.tra</code> file for a POMDP is similar to an MDP,\nbut also contains information about observations.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m o</code>\", where <code>n</code>, <code>c</code> and <code>m</code> are, as for MDPs, the numbers of states, choices and transitions,\nand <code>o</code> is the number of observations.\nThe lines that list transitions contain an additional integer after the transition probability\n(and before the action, if present), giving the (deterministic) observation that is made\nwhen entering the target state of that transition.\nCurrently, it is assumed that these are consistent for all states.\n</p>\n<p class='vspace'>In order to also specify the observation for the initial state,\na dummy transition line of the form <code>- - s - o</code> is used,\ngiving both the initial state <code>s</code> and its observation <code>o</code>.\n</p>\n<p class='vspace'>An example file is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"text\">10 16 18 4<br />\n- - 0 - 0<br />\n0 0 1 0.1 1 toss<br />\n0 0 2 0.3 1 toss<br />\n0 0 3 0.6 1 toss<br />\n1 0 4 1 2 guess1<br />\n1 1 7 1 3 guess2<br />\n1 2 7 1 3 guess3<br />\n2 0 8 1 3 guess1<br />\n2 1 5 1 2 guess2<br />\n2 2 8 1 3 guess3<br />\n3 0 9 1 3 guess1<br />\n3 1 9 1 3 guess2<br />\n3 2 6 1 2 guess3<br />\n4 0 4 1 2 loop<br />\n5 0 5 1 2 loop<br />\n6 0 6 1 2 loop<br />\n7 0 7 1 3<br />\n8 0 8 1 3<br />\n9 0 9 1 3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trarows' id='trarows'></a>\n</p><h3>Transitions (.tra) files (row form)</h3>\n<p>There is alternative format for transition matrices (see the <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html#other'>rows</a> option for <code>-exportmodel</code>) where transitions for each state/choice are collated on a single line.\n</p>\n<p class='vspace'>Here is the result for the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> example from above (a DTMC):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 0.5:1 0.5:3<br />\n1 0.5:0 0.25:2 0.25:4<br />\n2 1:5<br />\n3 1:3<br />\n4 1:4<br />\n5 1:2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> example (an MDP):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 <br />\n1 0.7:0 0.3:1 <br />\n1 0.5:2 0.5:3 <br />\n2 1:2 <br />\n3 1:3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and for the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> example (an MDP with actions):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 a<br />\n1 0.5:2 0.5:3 c<br />\n1 0.7:0 0.3:1 b<br />\n2 1:2 a<br />\n3 1:3 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='lab' id='lab'></a>\n</p><h3>Labels (.lab) files</h3>\n<p>These contain an explicit list of which <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> are satisfied in each state.\nThe first line lists the labels, assigning each one an index.\nThe remaining lines list indices of all states satisfying one or more labels,\nfollowed by a list of the the indices of labels that that are satisfied in it.\nThis includes the built-in labels <code>\"init\"</code> (initial states) and <code>deadlock</code> (deadlock states).\nAn example is shown below, where, for example, both <code>\"heads\"</code> and <code>\"end\"</code> are satisfied in state 2.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"text\">0=&quot;init&quot; 1=&quot;deadlock&quot; 2=&quot;heads&quot; 3=&quot;tails&quot; 4=&quot;end&quot;<br />\n0: 0<br />\n2: 2 4<br />\n3: 3 4</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='srew' id='srew'></a>\n</p><h3>State rewards (.srew) files</h3>\n<p>Reward files contain an (optional) header, giving the name of the reward structure that generated it\nand the type of rewards (state or transitions) stored in the file.\nFor state rewards, the information following this header is an explicit list of the (non-zero) state rewards.\nThe first line is of the form <code>n m</code> where <code>n</code> is the number of states in the model and <code>m</code> is the number of non-zero state rewards.\nThe following <code>m</code> lines are of the form <code>i r</code>, denoting that the state reward for state <code>i</code> is <code>r</code>.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get rewards in 3 states (0, 4 and 5):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure &quot;r&quot;<br />\n# State rewards<br />\n6 3<br />\n0 2<br />\n4 1<br />\n5 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trew' id='trew'></a>\n</p><h3>Transition rewards (.trew) files</h3>\n<p>Files containing transition rewards, like those for state rewards, start with an (optional) header.\nThe rest of the file is formatted identically to transitions files (see <a href='ExplicitModelFiles@action=print.html#tra'>above</a>),\nexcept that probabilities/rates are replaced with reward values,\nand the number of transitions (the last number on the first line) is replaced with the number of non-zero transition rewards.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n6 4<br />\n1 0 1<br />\n1 2 1<br />\n1 4 1<br />\n2 5 2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And or the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (4-state) MDP example, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n4 5 4<br />\n1 0 2 6<br />\n1 0 3 6<br />\n1 1 0 5<br />\n1 1 1 5</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='sta' id='sta'></a>\n</p><h3>States (.sta) files</h3>\n<p>These contain an explicit list of the reachable states of a model. The first line is of the form <code>(v1,...,vn)</code>, listing the names of all the variables in the model in the order that they appear in the PRISM model. Subsequent lines list the values of the <code>n</code> variables in each state of the model. Each line is of the form <code>i:(x1,...,xn)</code>, where <code>i</code> is the index of the state (starting from 0) and <code>x1,...,xn</code> are the values of each variable in the state. States are ordered by their index (and, therefore, given PRISM's default behaviour, lexicographically according to the tuple of variable values).\n</p>\n<p class='vspace'>For the example PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a>, the states file looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"text\">(s,a,s1,s2)<br />\n0:(1,0,0,0)<br />\n1:(1,0,0,1)<br />\n2:(1,0,1,0)<br />\n3:(1,0,1,1)<br />\n4:(1,1,1,0)<br />\n5:(1,1,1,1)<br />\n6:(2,0,0,0)<br />\n7:(2,0,0,1)<br />\n8:(2,0,1,0)<br />\n9:(2,0,1,1)<br />\n10:(2,1,0,1)<br />\n11:(2,1,1,1)</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Appendices/ExplicitModelFiles?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/Main.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / Main \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <h1>Appendices</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<ul><li><a class='wikilink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Main@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 01, 2013, at 08:34 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='selflink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='wikilink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/Main@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / Main | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <h1>Appendices</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Main@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Main@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 01, 2013, at 08:34 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='selflink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='wikilink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/Main@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Appendices / Main | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <h1>Appendices</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Main@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Main@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 01, 2013, at 08:34 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='selflink' href='Main.html'>Appendices</a></strong>\n</p><ul><li><a class='wikilink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Appendices/Main@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Appendices / Main </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <h1>Appendices</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<ul><li><a class='wikilink' href='ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/AllOnOnePage.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / All On One Page \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Configuring PRISM</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>The operation of PRISM can be configured in a number of ways. From the GUI, select \"Options\" from the main menu to bring up the \"Options\" dialog. The settings are grouped under several tabs. Those which affect the basic model checking functionality of the tool are under the heading \"PRISM\". Separate settings are available for the simulator and various aspects of the GUI (the model editor, the property editor and the log).\n</p>\n<p class='vspace'>User options and settings for the GUI are saved in a file locally and reused. Currently the \"Options\" dialog in the GUI represents the easiest way to modify the settings, but the settings file is in a simple textual format and can also be edited by hand. To restore the default options for PRISM, click \"Load Defaults\" and then \"Save Options\" from the \"Options\" dialog in the GUI. Alternatively, delete the settings file re-launch the GUI. The location of the settings file depends on the operating system. As of PRISM 4.5, it is stored in:\n</p>\n<div class='vspace'></div><ul><li><code>$HOME/.prism</code> (if the settings file was already created by an older version of PRISM)\n</li><li><code>$XDG_CONFIG_HOME/prism.settings</code> (on Linux, if that environment variable is set)\n</li><li><code>$HOME/.config/prism.settings</code> (on Linux, if <code>$XDG_CONFIG_HOME</code> is not set)\n</li><li><code>$HOME/Library/Preferences/prism.settings</code> (on Mac OS)\n</li><li><code>.prism</code> in the user's home directory, e.g. <code>C:\\Documents and Settings\\username</code> (on Windows)\n</li></ul><p class='vspace'>From the command-line version of PRISM, options are controlled by switches. A full list can be displayed by typing:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For some switches, whose format is not straightforward, there is additional help available on the command-line, using <code>-help switch</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help const</span><br/>\n<span style=\"font-weight:bold;\">prism -help simpath</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportresults</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportmodel</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The settings file is <em>ignored</em> by the command-line version (unlike earlier versions of PRISM, where it was used). You can, however, request that the settings file <em>is</em> read, using the <code>-settings</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -settings ~/.prism</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the following sections, we give a brief description of the most important configuration options available.\n</p>\n<div class='vspace'></div><hr />\n<h1>Computation Engines</h1>\n<h3>Computation engines</h3>\n<p>PRISM contains four main <em>engines</em>,\nwhich implement the majority of its model checking functionality:\n</p>\n<div class='vspace'></div><ul><li>\"MTBDD\"\n</li><li>\"sparse\"\n</li><li>\"hybrid\"\n</li><li>\"explicit\"\n</li></ul><p class='vspace'>The first three of these engines are either wholly or partly <em>symbolic</em>,\nmeaning that they use data structures such as\nbinary decision diagrams (BDDs) and multi-terminal BDDs (MTBDDs).\nFor these three engines, the process of\nconstructing a probabilistic model (DTMC, MDP or CTMC)\nis performed in a symbolic fashion,\nrepresenting the model as an MTBDD.\nSubsequent numerical computation performed during model checking, however,\nis carried out differently for the three engines.\nThe \"MTBDD\" engine is implemented purely using MTBDDs and BDDs;\nthe \"sparse\" engine uses sparse matrices;\nand the \"hybrid\" engine uses a combination of the other two.\nThe \"hybrid\" engine is described in [<a class='wikilink' href='../Main/References.html#KNP04b'>KNP04b</a>].\nFor detailed information about all three engines, see [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>].\n</p>\n<p class='vspace'>The fourth engine, \"explicit\", performs all aspects of model construction\nand model checking using <em>explicit-state</em> data structures.\nModels are typically stored as sparse matrices or variants of.\nThis engine is implemented purely in Java, unlike the other engines\nwhich make use of code/libraries implemented in C/C++.\nOne goal of the \"explicit\" engine is to provide an easily extensible model\nchecking engine without the complication of symbolic data structures,\nalthough it also has other benefits (see below).\n</p>\n<p class='vspace'>The choice of engine (\"MTBDD\", \"sparse\", \"hybrid\" or \"engine\") should not affect the results of model checking - all engines perform essentially the same calculations. In some cases, though, certain functionality is not available with all engines and PRISM will either automatically switch to an appropriate engine, or prompt you to do so.\nPerformance (time and space), however, may vary significantly and if you are using too much time/memory with one engine, it may be worth experimenting. Below, we briefly summarise the key characteristics of each engine.\n</p>\n<div class='vspace'></div><ul><li>The <strong>hybrid</strong> engine is enabled by default in PRISM. It uses a combination of <em>symbolic</em> and <em>explicit-state</em> data structures (as used in the MTBDD and sparse engines, respectively). In general it provides the best compromise between time and memory usage: it (almost) always uses less memory than the sparse engine, but is typically slightly slower. The size of model which can be handled with this engine is quite predictable. The limiting factor in terms of memory usage comes from the storage of 2-4 (depending on the computation being performed) arrays of 8-byte values, one for each state in the model. So, a typical PC can handle models with between 10<sup>7</sup> and 10<sup>8</sup> states (one vector for 10<sup>7</sup> states uses approximately 75 MB).\n<div class='vspace'></div></li><li>The <strong>sparse</strong> engine can be a good option for smaller models where model checking takes a long time. For larger models, however, memory usage quickly becomes prohibitive. As a rule of thumb, the upper limit for this engine, in terms of model sizes which can be handled, is about a factor of 10 less than the hybrid engine.\n<div class='vspace'></div></li><li>The <strong>MTBDD</strong> engine is much more unpredictable in terms of performance but, when a model exhibits a lot of structure and regularity, can be very effective. This engine has been successfully applied to extremely large structured (but non-trivial) models, in cases where the other two engines cannot be applied. The MTBDD engine often performs poorly when the model (or solutions computed from it) contain lots of distinct probabilities/rates; it performs best when there are few such values. For this reason the engine is often successfully applied to MDP models, but much less frequently to CTMCs. When using the MTBDD engine, the <em>variable ordering</em> of your model is especially important. This topic is covered in the <a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html#ordering'>FAQ</a> section.\n<div class='vspace'></div></li><li>The <strong>explicit</strong> engine is similar to the sparse engine, in that it can be a good option for relatively small models, but will not scale up to some of the models that can be handled by the hybrid or MTBDD engines. However, unlike the sparse engine, the explicit engine does not use symbolic data structures for model construction, which can be beneficial in some cases. One example is models with a potentially very large state space, only a fraction of which is actually reachable.\n</li></ul><p class='vspace'>When using the PRISM GUI, the engine to be used for model checking can be selected from the \"Engine\" option under the \"PRISM\" tab of the \"Options\" dialog. From the command-line, engines are activated using the <code>-mtbdd</code>, <code>-sparse</code>, <code>-hybrid</code> and <code>-explicit</code> (or <code>-m</code>, <code>-s</code>, <code>-h</code> and <code>-ex</code>, respectively) switches, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -m</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -s</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -h</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note also that precise details regarding the memory usage of the current engine are displayed during model checking (from the GUI, check the \"Log\" tab). This can provide valuable feedback when experimenting with different engines.\n</p>\n<p class='vspace'>PRISM also has some basic support for automatically selecting the engine (and other settings) heuristically,\nbased on the size and type of the model, and the property being checked.\nUse, for example, <code>-heuristic speed</code> from the command-line to choose options\nwhich target computation speed rather than saving memory.\nThis is also available from the \"Heuristic\" option under the \"PRISM\" tab of the \"Options\" dialog in the GUI.\n</p>\n<div class='vspace'></div><h3>Approximate/statistical model checking</h3>\n<p>Although it is not treated as a separate \"engine\", like those above,\nPRISM also provides approximate/statistical model checking,\nwhich is based on the use of discrete-event simulation.\nFrom the GUI, this is enabled by choosing \"Simulate\" menu items or tick boxes;\nfrom the command-line, add the <code>-sim</code> switch.\nSee the \"<a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\"\nsection for more details.\n</p>\n<p class='vspace'><a name='exact' id='exact'></a>\n</p><h3>Exact model checking</h3>\n<p>Most of PRISM's model checking functionality uses numerical solution based on floating point arithmetic and, often, this uses iterative numerical methods, which are run until some user-specified precision is reached. PRISM currently has some support for \"exact\" model checking, i.e., using arbitrary precision arithmetic to provide exact numerical values. Currently, this is implemented as a special case of <a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>parametric model checking</a>, which limits is application to relatively small models. It can be used for analysing DTMCs/CTMCs (unbounded until, steady-state probabilities, reachability reward and steady-state reward) or MDPs (unbounded until and reachability rewards). You can enable this functionality using the \"Do exact model checking\" option in the GUI or using switch <code>-exact</code> from the command line.\n</p>\n<p class='vspace'><a name='pta' id='pta'></a>\n</p><h3>PTA engines</h3>\n<p>The techniques used to model check PTAs are different to the ones used for DTMCs, MDPs and CTMCs. For PTAs, PRISM currently has three distinct engines that can be used:\n</p>\n<div class='vspace'></div><ul><li>The <strong>stochastic games</strong> engine uses abstraction-refinement techniques based on stochastic two-player games [<a class='wikilink' href='../Main/References.html#KNP09c'>KNP09c</a>].\n<div class='vspace'></div></li><li>The <strong>digital clocks</strong> engine performs a discretisation, in the form of a language-level model translation, that reduces the problem to one of model checking over a finite-state MDP [<a class='wikilink' href='../Main/References.html#KNPS06'>KNPS06</a>].\n<div class='vspace'></div></li><li>The <strong>backwards reachability</strong> engine is a zone-based method based on a backwards traversal of the state space and solution of the resulting finite-state MDP [<a class='wikilink' href='../Main/References.html#KNSW07'>KNSW07</a>].\n</li></ul><p class='vspace'>The default engine for PTAs is \"stochastic games\". The engine to be used can be specified using the \"PTA model checking method\" setting in the \"PRISM\" options panel in the GUI. From the command-line, switch <code>-ptamethod &lt;name&gt;</code> should be used where <code>&lt;name&gt;</code> is either <code>games</code>, <code>digital</code> or <code>backwards</code>.\n</p>\n<p class='vspace'>The choice of engine for PTA model checking affects restrictions that imposed on both\nthe <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>modelling language</a>\nand the types of <a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>properties</a> that can be checked.\n</p><hr />\n<h1>Solution Methods and Options</h1>\n<p>Separately from the choice of <a class='wikilink' href='ComputationEngines.html'>engines</a>,\nPRISM often offers several different solution methods\nthat can be used for the computation of probabilities and expected costs/rewards during model checking.\nMany, but not all, of these are iterative numerical methods.\nThe choice of method (and their settings) depends on the type of analysis that is being done (i.e., what type of model and property).\n</p>\n<div class='vspace'></div><h3>Linear Equation Systems</h3>\n<p>For many properties of Markov chains\n(e.g. \"reachability\"/\"until\" properties for DTMCs and CTMCs, steady-state properties for CTMCs and \"reachability reward\" properties for DTMCs),\nPRISM solves a set of linear equation systems, for which several numerical methods are available.\nBelow is a list of the alternatives and the switches used to select them from the command-line.\nThe corresponding GUI option is \"Linear equations method\".\n</p>\n<div class='vspace'></div><ul><li>Power method: <code>-power</code> (or <code>-pow</code>, <code>-pwr</code>)\n</li><li>Jacobi method: <code>-jacobi</code> (or <code>-jac</code>)\n</li><li>Gauss-Seidel method: <code>-gaussseidel</code> (or <code>-gs</code>)\n</li><li>Backwards Gauss-Seidel method: <code>-bgaussseidel</code> (or <code>-bgs</code>)\n</li><li>JOR method (Jacobi with over-relaxation): <code>-jor</code>\n</li><li>SOR method: <code>-sor</code>\n</li><li>Backwards SOR method: <code>-bsor</code>\n</li></ul><p class='vspace'>When using the MTBDD engine, Gauss-Seidel/SOR based methods are not available.\nWhen using the hybrid engine, <em>pseudo</em> variants of Gauss-Seidel/SOR based method can also be used [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>]\n(type <code>prism -help</code> at the command-line for details of the corresponding switches).\nFor methods which use over-relaxation (JOR/SOR), the over-relaxation parameter (between 0.0 and 2.0)\ncan also be specified with option \"Over-relaxation parameter\" (switch <code>-omega &lt;val&gt;</code>).\n</p>\n<p class='vspace'>For options relating to convergence (of this and other iterative methods),\nsee the <a class='wikilink' href='SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='mdp' id='mdp'></a>\n</p><h3>MDP Solution Methods</h3>\n<p>When analysing MDPs, there are multiple solution methods on offer.\nFor most of these, you can select them under the \"MDP solution method\" setting from the GUI,\nor use the command-line switches listed below.\nCurrently, all except value iteration are only supported by the <a class='wikilink' href='ComputationEngines.html'>explicit engine</a>.\nFor more details of the methods, see e.g. [<a class='wikilink' href='../Main/References.html#FKNP11'>FKNP11</a>] (about probabilistic verification of MDPs)\nor classic MDP texts such as [<a class='wikilink' href='../Main/References.html#Put94'>Put94</a>]).\n</p>\n<div class='vspace'></div><ul><li><strong>Value iteration</strong> (switch <code>-valiter</code>) [this is the default]\n</li><li><strong>Gauss Seidel</strong> (switch <code>-gs</code>)\n</li><li><strong>Policy iteration</strong> (switch <code>-politer</code>)\n</li><li><strong>Modified policy iteration</strong> (switch <code>-modpoliter</code>)\n</li></ul><p class='vspace'>Where the methods above use iterative numerical solution,\nyou can also use the settings under described in the <a class='wikilink' href='SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='iiter' id='iiter'></a>\n</p><h3>Interval Iteration</h3>\n<p>Interval iteration [<a class='wikilink' href='../Main/References.html#HM14'>HM14</a>],[<a class='wikilink' href='../Main/References.html#BKLPW17'>BKLPW17</a>] is an alternative solution method for either MDPs or DTMCs\nwhich performs two separate instances of numerical iterative solution,\none from below and one from above. This is designed to provide clearer information\nabout the accuracy of the computed values and avoid possible problems with premature convergence.\nThis can be enabled using the switch <code>-intervaliter</code> (or <code>-ii</code>)\nor via the \"Use interval iteration\" GUI option.\nA variety of options can be configured, either using\n<code>-intervaliter:option1,option2,...</code> or by\nsetting the string \"<code>option1,option2,...</code>\" under \"Interval iteration options\" in the GUI.\nType <code>prism -help intervaliter</code> from the command-line for a list of the options\nand see [<a class='wikilink' href='../Main/References.html#BKLPW17'>BKLPW17</a>] for the details.\n</p>\n<p class='vspace'><a name='topo' id='topo'></a>\n</p><h3>Topological Value Iteration</h3>\n<p>Topological value iteration is a variant of value iteration which improves efficiency\nby analysing the graph structure of the model and using this to update the values for\nstates in an alternative order which increases the speed of convergence.\nUse switch <code>-topological</code> or GUI option \"Use topological value iteration\" to enable this.\nIn addition to standard value iteration for MDPs, the topological variant can be used to optimise\nboth interval iteration (see above) and the numerical solution of DTMCs.\n</p>\n<p class='vspace'><a name='transient' id='transient'></a>\n</p><h3>CTMC Transient Analysis</h3>\n<p>When computing transient probabilities of a CTMC\n(either <a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>directly</a> or when verifying <a class='wikilink' href='../PropertySpecification/ThePOperator.html#bounded'>time-bounded operators</a> of CSL), there are two options:\n<em>uniformisation</em> and <em>fast adaptive uniformisation</em> (FAU). These can be selected using the GUI option \"Transient probability computation method\", or using the command-line switch <code>-transientmethod &lt;name&gt;</code>, where <code>&lt;name&gt;</code> is either <code>unif</code> or <code>fau</code>.\n</p>\n<p class='vspace'><strong>Uniformisation</strong> is a standard iterative numerical method for computing transient probabilities on a CTMC, which works by reducing the problem to an analysis of a \"uniformised\" DTMC.\nAs an optimisation, when it is detected that the transient probabilities have converged, no further iterations are performed. If necessary (e.g. in case of round-off problems), this optimisation can be disabled with the \"Use steady-state detection\" option (command-line switch <code>-nossdetect</code>).\n</p>\n<p class='vspace'><a name='fau' id='fau'></a>\n<strong>Fast adaptive uniformisation</strong> (FAU) [<a class='wikilink' href='../Main/References.html#MWDH10'>MWDH10</a>] is a method to efficiently approximate transient properties of large CTMCs. The basic idea is that only the parts of the model that are relevant for the current time period are kept in memory. In more detail, starting with the initial states, in each step FAU\nexplores further states in a DTMC which is a discrete-time version of the original CTMC. By combining the\nprobabilities there with those of a certain continuous-time stochastic process (a birth process), transient properties in the original CTMC can be computed. If it turns out that the probability of being in some state in the DTMC is below a given threshold, this state is removed from the model explored so far. After a given number of steps, which corresponds to the number of steps which are likely to happen within the time bound, the exploration can be stopped. In the implementation in PRISM [<a class='wikilink' href='../Main/References.html#DHK13'>DHK13</a>], FAU can be used to compute transient probability distributions and to model check the following types of non-nested CSL formulas: time-bounded until, instantaneous reward, cumulative reward.\n</p>\n<p class='vspace'>The following options can be used to configure FAU:\n</p>\n<div class='vspace'></div><ul><li>\"FAU epsilon\" (switch <code>-fauepsilon &lt;x&gt;</code>): FAU analyses the DTMC for a number of iterations such that the probability of more steps being relevant is below this value. The default is 1e-6.\n<div class='vspace'></div></li><li>\"FAU cut off delta\" (switch <code>-faudelta &lt;x&gt;</code>): States that have a lower probability than this value are discarded. The default is 1e-12.\n<div class='vspace'></div></li><li>\"FAU array threshold\" (switch <code>-fauarraythreshold &lt;x&gt;</code>): After this number of steps without any new states being explored or discarded, FAU will switch to a faster, fixed-size data structure until further states have to be explored or discarded. The default is 100.\n<div class='vspace'></div></li><li>\"FAU time intervals\" (switch <code>-fauintervals &lt;x&gt;</code>): In some cases, it is advantageous to divide the time interval the analysis is done for into several smaller intervals. This option dictates the number of (equal length) intervals used for this split. The default is 1, meaning that only one time interval is used.\n<div class='vspace'></div></li><li>\"FAU initial time interval\" (switch <code>-fauinitival &lt;x&gt;</code>): It is also possible to specify an additional initial time interval which is handled separately from the rest of the time. This is often advantageous, because in this interval certain parameters of the model can be explored, which can subsequently be used to speed up the computation of the remaining time interval. The default for this option is 1.0.\n</li></ul><p class='vspace'><a name='convergence' id='convergence'></a>\n</p><h3>Convergence</h3>\n<p>Common to all of these methods is the way that PRISM checks convergence, i.e. decides when to terminate the iterative methods because the answers have converged sufficiently. This is done by checking when the maximum difference between elements in the solution vectors from successive iterations drops below a given threshold (or, in the case of interval iteration, if the difference of the elements in the iterations from above and below are below the threshold).\nThe default value for this threshold is 10<sup>-6</sup> but it can be altered with the \"Termination epsilon\" option (switch <code>-epsilon &lt;val&gt;</code>). The way that the maximum difference is computed can also be varied:\neither \"relative\" or \"absolute\" (the default is \"relative\"). This can be changed using the \"Termination criteria\" option (command-line switches <code>-relative</code> and <code>-absolute</code>, or <code>-rel</code> and <code>-abs</code> for short).\n</p>\n<p class='vspace'>Also, the maximum number of iterations performed is given an upper limit\nin order to trap the cases when computation will not converge.\nThe default limit is 10,000 but can be changed with the \"Termination max. iterations\" option (switch <code>-maxiters &lt;val&gt;</code>). Computations that reach this upper limit will trigger an error during model checking to alert the user to this fact.\n</p><hr />\n<h1>Automata Generation</h1>\n<p>When PRISM performs verification of <a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>LTL formulas</a>, it does so by converting the formula into an automaton (such as a deterministic Rabin automaton) and then analysing a larger product model, constructed from the model being verified and the omega automaton. For this reason, the size of the automaton has an important effect on the efficiency of verification.\n</p>\n<p class='vspace'>By default PRISM uses a port of the <a class='urllink' href='http://www.ltl2dstar.de/'>ltl2dstar</a> library to construct these automata. But it also allows the use of external LTL-to-automata converters producing deterministic automata through support for the <a class='urllink' href='http://adl.github.io/hoaf/'>Hanoi Omega Automaton</a> (HOA) format. From the command line, an example of this is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-ltl2datool</code> switch specifies the location of the program to be executed to perform the LTL-to-automaton conversion. This will be called by PRISM as \"<code>exec</code> <code>in-file</code> <code>out-file</code>\", where <code>exec</code> is the executable, <code>in-file</code> is the name of a file containing the LTL formula to be converted and <code>out-file</code> is the name of a file where the resulting automaton should be written, in HOA format. Typically, the executable will be a script. Here is a simple example (called as <code>hoa-ltl2dstar-for-prism</code> in the above example), which calls an external copy of <code>ltl2dstar</code> in the required fashion (assuming that the <code>ltl2dstar</code> and <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a>  executables are located in the current directory or on the PATH).\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#! /bin/bash</span><br />\nltl2dstar <span class=\"re5\">--output</span>=automaton <span class=\"re5\">--output-format</span>=hoa <span class=\"st0\">&quot;$1&quot;</span> <span class=\"st0\">&quot;$2&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM is known to work with these HOA-enabled tools:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>\n</li><li><a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>\n</li><li><a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>\n</li><li><a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>\n</li></ul><p class='vspace'>and contains ready-made scripts for calling them in the <code>etc/scripts/hoa</code> directory of the distribution:\n</p>\n<div class='vspace'></div><ul><li><code>hoa-ltl2dstar-for-prism</code> <br />  (<a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>, using <a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>, <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a> or <a class='urllink' href='https://github.com/xblahoud/ltl3dra'>LTL3BA</a> as the LTL-to-NBA tool as the LTL-to-NBA tool)\n</li><li><code>hoa-ltl2tgba-for-prism</code> <br />  (<a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>)\n</li><li><code>hoa-ltl3dra-for-prism</code> <br />  (<a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>)\n</li><li><code>hoa-rabinizer-for-prism</code> <br />  (<a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>'s <code>ltl2dra</code>)\n</li></ul><p class='vspace'>See the files themselves for details of any configuration required, possible options and for a reminder of the PRISM command-line arguments required.\n</p>\n<p class='vspace'>There is also a <code>hoa-rabinizer-for-prism.bat</code> script for connecting to Rabinizer on Windows.\n</p>\n<p class='vspace'>The <code>-ltl2dasyntax</code> switch is used to specify the textual format for passing the LTL formula to the external converter (i.e., in the file <code>out-file</code>). The options are:\n</p>\n<div class='vspace'></div><ul><li><code>lbt</code> - LBT format\n</li><li><code>spin</code> - SPIN format\n</li><li><code>spot</code> - Spot format\n</li><li><code>rabinizer</code> - Rabinizer format\n</li></ul><p class='vspace'>Typical usage is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2tgba-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl3dra-for-prism -ltl2dasyntax spin</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-rabinizer-for-prism -ltl2dasyntax rabinizer</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, configuring the external LTL converter is done with the two options \n\"Use external LTL-&gt;DA tool\" and \"LTL syntax for external LTL-&gt;DA tool\".\n</p>\n<p class='vspace'>Another related option is \"All path formulas via automata\" (command-line switch <code>-pathviaautomata</code>), which forces construction of an automata\nwhen computing the probability of a path formula, even if it is not needed. This is primarily intended for debugging/testing, not regular use.\n</p>\n<p class='vspace'>As mentioned above, PRISM's external LTL-to-automaton interfacing works using the\n<a class='urllink' href='http://adl.github.io/hoaf/'>HOA</a> format\n(and, in particular,  using the <a class='urllink' href='http://automata.tools/hoa/jhoafparser/'><code>jhoafparser</code></a> HOA parser.\nCurrently, PRISM can handle automata in HOA format that are \ndeterministic and complete, with state-based acceptance.\nAutomata with transition-based acceptance are converted to state-based acceptance by PRISM.\nFor DTMC and  CTMC model checking, generic acceptance conditions are supported, i.e., \nanything that can be specified as an <code>Acceptance:</code> header in HOA format. \nFor MDP model checking, currently Rabin and generalized Rabin acceptance \nspecified via the <code>acc-name:</code> header are supported. See the <a class='urllink' href='http://adl.github.io/hoaf/'>HOA format specification</a> for details.\n</p>\n<div class='vspace'></div><hr />\n<h1>Other Options</h1>\n<h3>Output options</h3>\n<p>To increase the amount of information displayed by PRISM (in particular, to display lists of states and probability vectors), you can use the \"Verbose output\" option (activated with command-line switch <code>-verbose</code> or <code>-v</code>). To display additional statistics about MTBDDs after model construction, use the \"Extra MTBDD information\" option (switch <code>-extraddinfo</code>) and, to view MTBDD sizes during the process of reachability, use option \"Extra reachability information\" (switch <code>-extrareachinfo</code>).\n</p>\n<div class='vspace'></div><h3>Fairness</h3>\n<p>Sometimes, model checking of properties for MDPs requires fairness constraints to be taken into account.\nSee e.g. [<a class='wikilink' href='../Main/References.html#BK98'>BK98</a>],[<a class='wikilink' href='../Main/References.html#Bai98'>Bai98</a>] for more information.\nTo enable the use of fairness constraints (for <code><strong>P</strong></code> operator properties), use the <code>-fair</code> switch.\n</p>\n<div class='vspace'></div><h3>Probability/rate checks</h3>\n<p>By default, when constructing a model, PRISM checks that all probabilities and rates are within acceptable ranges (i.e. are between 0 and 1, or are non-negative, respectively). For DTMCs and MDPs, it also checks that the probabilities sum up to one for each command. These checks are often very useful for highlighting user modelling errors and it is strongly recommended that you keep them enabled, however if you need to disable them you can do so via option \"do prob checks?\" in the GUI or command-line switch <code>-noprobchecks</code>.\nYou can also change the level of precision used to check that probabilities sum to 1 using the option \"Probability sum threshold\" (or command-line switch <code>-sumroundoff</code>.\n</p>\n<div class='vspace'></div><h3>CUDD memory</h3>\n<p>CUDD, the underlying BDD and MTBDD library used in PRISM has an upper memory limit. By default, this limit is 1 GB. If you are working on a machine with significantly more memory this and PRISM runs out of memory when model checking, it may help to change this. To set the limit, from the command-line, use the <code>-cuddmaxmem</code> switch. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -cuddmaxmem 2g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Above, <code>g</code> denotes GB. You can also use <code>m</code> for MB.\nYou can also the CUDD maximum memory setting from the options panel in the GUI, but you will need to close and restart the GUI (saving the settings as you do) for this to take effect.\n</p>\n<p class='vspace'><a name='javamaxmem' id='javamaxmem'></a>\n</p><h3>Java memory</h3>\n<p>The Java virtual machine (JVM) used to execute PRISM also has upper memory limits. Sometimes this limit will be exceeded and you will see an error of the form <code>java.lang.OutOfMemory</code>. To resolve this problem, you can increase this memory limit. On Unix, Linux or Mac OS X platforms, this can done by using the <code>-javamaxmem</code> switch, passed either to the command-line script <code>prism</code> or the GUI launcher <code>xprism</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javamaxmem 4g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javamaxmem 4g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>each set the limit to 4GB. Alternatively, you set the environment variable PRISM_JAVAMAXMEM before running PRISM. For example, under a <code>bash</code> shell:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVAMAXMEM=4g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVAMAXMEM</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you get an error of the form <code>java.lang.StackOverflowError</code>, then you can try increasing the stack size of the JVM.\nOn Unix, Linux or Mac OS X platforms, this can done by using the <code>-javastack</code> switch or the <code>PRISM_JAVASTACKSIZE</code> environment variable.\nExamples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javastack 1g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javastack 1g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVASTACKSIZE=1g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVASTACKSIZE</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are running PRISM on Windows you will have to do make adjustments to Java memory manually, by modifying the <code>prism.bat</code> or <code>xprism.bat</code> scripts.\nTo set the memory to 4GB, for example, add <code> -Xmx4g</code> to the list of arguments in the call to <code>java</code> or <code>javaw</code> at the end of the file.\nTo change the stack size to 1GB, add <code>-Xss1g</code>.\n</p>\n<div class='vspace'></div><h3>Other Java options</h3>\n<p>If you want to pass additional switches to the JVM used to run PRISM, you can use the <code>-javaparams</code> switch.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javaparams \"-XX:AutoBoxCacheMax=100000000 -Xmn2g\" -javamaxmem 12g</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Precomputation</h3>\n<p>By default, PRISM's probabilistic model checking algorithms use an initial <em>precomputation</em> step which uses graph-based techniques to efficient detect trivial cases where probabilities are 0 or 1. This can often result in improved performance and also reduce round-off errors. Occasionally, though, you may want to disable this step for efficiency (e.g. if you know that there are no/few such states and the precomputation process is slow). This can be done with the <code>-nopre</code> switch. You can also disable the individual algorithms for probability 0/1 using switches <code>-noprob0</code> and <code>-noprob1</code>.\n</p>\n<div class='vspace'></div><h3>Time-outs</h3>\n<p>The command-line version of PRISM has a time-out option, specified using the switch <code>-timeout &lt;n&gt;</code>.\nThis causes the program to exit after <code>&lt;n&gt;</code> seconds if it has not already terminated by that point.\nThis is particularly useful for benchmarking scenarios where you wish to ignore runs of PRISM that exceed a certain length of time.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 26, 2017, at 09:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/AllOnOnePage@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / All On One Page | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 26, 2017, at 09:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/AllOnOnePage@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / All On One Page | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 26, 2017, at 09:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/AllOnOnePage@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ConfiguringPRISM / AllOnOnePage </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Configuring PRISM</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>The operation of PRISM can be configured in a number of ways. From the GUI, select \"Options\" from the main menu to bring up the \"Options\" dialog. The settings are grouped under several tabs. Those which affect the basic model checking functionality of the tool are under the heading \"PRISM\". Separate settings are available for the simulator and various aspects of the GUI (the model editor, the property editor and the log).\n</p>\n<p class='vspace'>User options and settings for the GUI are saved in a file locally and reused. Currently the \"Options\" dialog in the GUI represents the easiest way to modify the settings, but the settings file is in a simple textual format and can also be edited by hand. To restore the default options for PRISM, click \"Load Defaults\" and then \"Save Options\" from the \"Options\" dialog in the GUI. Alternatively, delete the settings file re-launch the GUI. The location of the settings file depends on the operating system. As of PRISM 4.5, it is stored in:\n</p>\n<div class='vspace'></div><ul><li><code>$HOME/.prism</code> (if the settings file was already created by an older version of PRISM)\n</li><li><code>$XDG_CONFIG_HOME/prism.settings</code> (on Linux, if that environment variable is set)\n</li><li><code>$HOME/.config/prism.settings</code> (on Linux, if <code>$XDG_CONFIG_HOME</code> is not set)\n</li><li><code>$HOME/Library/Preferences/prism.settings</code> (on Mac OS)\n</li><li><code>.prism</code> in the user's home directory, e.g. <code>C:\\Documents and Settings\\username</code> (on Windows)\n</li></ul><p class='vspace'>From the command-line version of PRISM, options are controlled by switches. A full list can be displayed by typing:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For some switches, whose format is not straightforward, there is additional help available on the command-line, using <code>-help switch</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help const</span><br/>\n<span style=\"font-weight:bold;\">prism -help simpath</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportresults</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportmodel</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The settings file is <em>ignored</em> by the command-line version (unlike earlier versions of PRISM, where it was used). You can, however, request that the settings file <em>is</em> read, using the <code>-settings</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -settings ~/.prism</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the following sections, we give a brief description of the most important configuration options available.\n</p>\n<div class='vspace'></div><hr />\n<h1>Computation Engines</h1>\n<h3>Computation engines</h3>\n<p>PRISM contains four main <em>engines</em>,\nwhich implement the majority of its model checking functionality:\n</p>\n<div class='vspace'></div><ul><li>\"MTBDD\"\n</li><li>\"sparse\"\n</li><li>\"hybrid\"\n</li><li>\"explicit\"\n</li></ul><p class='vspace'>The first three of these engines are either wholly or partly <em>symbolic</em>,\nmeaning that they use data structures such as\nbinary decision diagrams (BDDs) and multi-terminal BDDs (MTBDDs).\nFor these three engines, the process of\nconstructing a probabilistic model (DTMC, MDP or CTMC)\nis performed in a symbolic fashion,\nrepresenting the model as an MTBDD.\nSubsequent numerical computation performed during model checking, however,\nis carried out differently for the three engines.\nThe \"MTBDD\" engine is implemented purely using MTBDDs and BDDs;\nthe \"sparse\" engine uses sparse matrices;\nand the \"hybrid\" engine uses a combination of the other two.\nThe \"hybrid\" engine is described in [<a class='wikilink' href='../Main/References.html#KNP04b'>KNP04b</a>].\nFor detailed information about all three engines, see [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>].\n</p>\n<p class='vspace'>The fourth engine, \"explicit\", performs all aspects of model construction\nand model checking using <em>explicit-state</em> data structures.\nModels are typically stored as sparse matrices or variants of.\nThis engine is implemented purely in Java, unlike the other engines\nwhich make use of code/libraries implemented in C/C++.\nOne goal of the \"explicit\" engine is to provide an easily extensible model\nchecking engine without the complication of symbolic data structures,\nalthough it also has other benefits (see below).\n</p>\n<p class='vspace'>The choice of engine (\"MTBDD\", \"sparse\", \"hybrid\" or \"engine\") should not affect the results of model checking - all engines perform essentially the same calculations. In some cases, though, certain functionality is not available with all engines and PRISM will either automatically switch to an appropriate engine, or prompt you to do so.\nPerformance (time and space), however, may vary significantly and if you are using too much time/memory with one engine, it may be worth experimenting. Below, we briefly summarise the key characteristics of each engine.\n</p>\n<div class='vspace'></div><ul><li>The <strong>hybrid</strong> engine is enabled by default in PRISM. It uses a combination of <em>symbolic</em> and <em>explicit-state</em> data structures (as used in the MTBDD and sparse engines, respectively). In general it provides the best compromise between time and memory usage: it (almost) always uses less memory than the sparse engine, but is typically slightly slower. The size of model which can be handled with this engine is quite predictable. The limiting factor in terms of memory usage comes from the storage of 2-4 (depending on the computation being performed) arrays of 8-byte values, one for each state in the model. So, a typical PC can handle models with between 10<sup>7</sup> and 10<sup>8</sup> states (one vector for 10<sup>7</sup> states uses approximately 75 MB).\n<div class='vspace'></div></li><li>The <strong>sparse</strong> engine can be a good option for smaller models where model checking takes a long time. For larger models, however, memory usage quickly becomes prohibitive. As a rule of thumb, the upper limit for this engine, in terms of model sizes which can be handled, is about a factor of 10 less than the hybrid engine.\n<div class='vspace'></div></li><li>The <strong>MTBDD</strong> engine is much more unpredictable in terms of performance but, when a model exhibits a lot of structure and regularity, can be very effective. This engine has been successfully applied to extremely large structured (but non-trivial) models, in cases where the other two engines cannot be applied. The MTBDD engine often performs poorly when the model (or solutions computed from it) contain lots of distinct probabilities/rates; it performs best when there are few such values. For this reason the engine is often successfully applied to MDP models, but much less frequently to CTMCs. When using the MTBDD engine, the <em>variable ordering</em> of your model is especially important. This topic is covered in the <a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html#ordering'>FAQ</a> section.\n<div class='vspace'></div></li><li>The <strong>explicit</strong> engine is similar to the sparse engine, in that it can be a good option for relatively small models, but will not scale up to some of the models that can be handled by the hybrid or MTBDD engines. However, unlike the sparse engine, the explicit engine does not use symbolic data structures for model construction, which can be beneficial in some cases. One example is models with a potentially very large state space, only a fraction of which is actually reachable.\n</li></ul><p class='vspace'>When using the PRISM GUI, the engine to be used for model checking can be selected from the \"Engine\" option under the \"PRISM\" tab of the \"Options\" dialog. From the command-line, engines are activated using the <code>-mtbdd</code>, <code>-sparse</code>, <code>-hybrid</code> and <code>-explicit</code> (or <code>-m</code>, <code>-s</code>, <code>-h</code> and <code>-ex</code>, respectively) switches, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -m</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -s</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -h</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note also that precise details regarding the memory usage of the current engine are displayed during model checking (from the GUI, check the \"Log\" tab). This can provide valuable feedback when experimenting with different engines.\n</p>\n<p class='vspace'>PRISM also has some basic support for automatically selecting the engine (and other settings) heuristically,\nbased on the size and type of the model, and the property being checked.\nUse, for example, <code>-heuristic speed</code> from the command-line to choose options\nwhich target computation speed rather than saving memory.\nThis is also available from the \"Heuristic\" option under the \"PRISM\" tab of the \"Options\" dialog in the GUI.\n</p>\n<div class='vspace'></div><h3>Approximate/statistical model checking</h3>\n<p>Although it is not treated as a separate \"engine\", like those above,\nPRISM also provides approximate/statistical model checking,\nwhich is based on the use of discrete-event simulation.\nFrom the GUI, this is enabled by choosing \"Simulate\" menu items or tick boxes;\nfrom the command-line, add the <code>-sim</code> switch.\nSee the \"<a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\"\nsection for more details.\n</p>\n<p class='vspace'><a name='exact' id='exact'></a>\n</p><h3>Exact model checking</h3>\n<p>Most of PRISM's model checking functionality uses numerical solution based on floating point arithmetic and, often, this uses iterative numerical methods, which are run until some user-specified precision is reached. PRISM currently has some support for \"exact\" model checking, i.e., using arbitrary precision arithmetic to provide exact numerical values. Currently, this is implemented as a special case of <a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>parametric model checking</a>, which limits is application to relatively small models. It can be used for analysing DTMCs/CTMCs (unbounded until, steady-state probabilities, reachability reward and steady-state reward) or MDPs (unbounded until and reachability rewards). You can enable this functionality using the \"Do exact model checking\" option in the GUI or using switch <code>-exact</code> from the command line.\n</p>\n<p class='vspace'><a name='pta' id='pta'></a>\n</p><h3>PTA engines</h3>\n<p>The techniques used to model check PTAs are different to the ones used for DTMCs, MDPs and CTMCs. For PTAs, PRISM currently has three distinct engines that can be used:\n</p>\n<div class='vspace'></div><ul><li>The <strong>stochastic games</strong> engine uses abstraction-refinement techniques based on stochastic two-player games [<a class='wikilink' href='../Main/References.html#KNP09c'>KNP09c</a>].\n<div class='vspace'></div></li><li>The <strong>digital clocks</strong> engine performs a discretisation, in the form of a language-level model translation, that reduces the problem to one of model checking over a finite-state MDP [<a class='wikilink' href='../Main/References.html#KNPS06'>KNPS06</a>].\n<div class='vspace'></div></li><li>The <strong>backwards reachability</strong> engine is a zone-based method based on a backwards traversal of the state space and solution of the resulting finite-state MDP [<a class='wikilink' href='../Main/References.html#KNSW07'>KNSW07</a>].\n</li></ul><p class='vspace'>The default engine for PTAs is \"stochastic games\". The engine to be used can be specified using the \"PTA model checking method\" setting in the \"PRISM\" options panel in the GUI. From the command-line, switch <code>-ptamethod &lt;name&gt;</code> should be used where <code>&lt;name&gt;</code> is either <code>games</code>, <code>digital</code> or <code>backwards</code>.\n</p>\n<p class='vspace'>The choice of engine for PTA model checking affects restrictions that imposed on both\nthe <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>modelling language</a>\nand the types of <a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>properties</a> that can be checked.\n</p><hr />\n<h1>Solution Methods and Options</h1>\n<p>Separately from the choice of <a class='wikilink' href='ComputationEngines.html'>engines</a>,\nPRISM often offers several different solution methods\nthat can be used for the computation of probabilities and expected costs/rewards during model checking.\nMany, but not all, of these are iterative numerical methods.\nThe choice of method (and their settings) depends on the type of analysis that is being done (i.e., what type of model and property).\n</p>\n<div class='vspace'></div><h3>Linear Equation Systems</h3>\n<p>For many properties of Markov chains\n(e.g. \"reachability\"/\"until\" properties for DTMCs and CTMCs, steady-state properties for CTMCs and \"reachability reward\" properties for DTMCs),\nPRISM solves a set of linear equation systems, for which several numerical methods are available.\nBelow is a list of the alternatives and the switches used to select them from the command-line.\nThe corresponding GUI option is \"Linear equations method\".\n</p>\n<div class='vspace'></div><ul><li>Power method: <code>-power</code> (or <code>-pow</code>, <code>-pwr</code>)\n</li><li>Jacobi method: <code>-jacobi</code> (or <code>-jac</code>)\n</li><li>Gauss-Seidel method: <code>-gaussseidel</code> (or <code>-gs</code>)\n</li><li>Backwards Gauss-Seidel method: <code>-bgaussseidel</code> (or <code>-bgs</code>)\n</li><li>JOR method (Jacobi with over-relaxation): <code>-jor</code>\n</li><li>SOR method: <code>-sor</code>\n</li><li>Backwards SOR method: <code>-bsor</code>\n</li></ul><p class='vspace'>When using the MTBDD engine, Gauss-Seidel/SOR based methods are not available.\nWhen using the hybrid engine, <em>pseudo</em> variants of Gauss-Seidel/SOR based method can also be used [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>]\n(type <code>prism -help</code> at the command-line for details of the corresponding switches).\nFor methods which use over-relaxation (JOR/SOR), the over-relaxation parameter (between 0.0 and 2.0)\ncan also be specified with option \"Over-relaxation parameter\" (switch <code>-omega &lt;val&gt;</code>).\n</p>\n<p class='vspace'>For options relating to convergence (of this and other iterative methods),\nsee the <a class='wikilink' href='SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='mdp' id='mdp'></a>\n</p><h3>MDP Solution Methods</h3>\n<p>When analysing MDPs, there are multiple solution methods on offer.\nFor most of these, you can select them under the \"MDP solution method\" setting from the GUI,\nor use the command-line switches listed below.\nCurrently, all except value iteration are only supported by the <a class='wikilink' href='ComputationEngines.html'>explicit engine</a>.\nFor more details of the methods, see e.g. [<a class='wikilink' href='../Main/References.html#FKNP11'>FKNP11</a>] (about probabilistic verification of MDPs)\nor classic MDP texts such as [<a class='wikilink' href='../Main/References.html#Put94'>Put94</a>]).\n</p>\n<div class='vspace'></div><ul><li><strong>Value iteration</strong> (switch <code>-valiter</code>) [this is the default]\n</li><li><strong>Gauss Seidel</strong> (switch <code>-gs</code>)\n</li><li><strong>Policy iteration</strong> (switch <code>-politer</code>)\n</li><li><strong>Modified policy iteration</strong> (switch <code>-modpoliter</code>)\n</li></ul><p class='vspace'>Where the methods above use iterative numerical solution,\nyou can also use the settings under described in the <a class='wikilink' href='SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='iiter' id='iiter'></a>\n</p><h3>Interval Iteration</h3>\n<p>Interval iteration [<a class='wikilink' href='../Main/References.html#HM14'>HM14</a>],[<a class='wikilink' href='../Main/References.html#BKLPW17'>BKLPW17</a>] is an alternative solution method for either MDPs or DTMCs\nwhich performs two separate instances of numerical iterative solution,\none from below and one from above. This is designed to provide clearer information\nabout the accuracy of the computed values and avoid possible problems with premature convergence.\nThis can be enabled using the switch <code>-intervaliter</code> (or <code>-ii</code>)\nor via the \"Use interval iteration\" GUI option.\nA variety of options can be configured, either using\n<code>-intervaliter:option1,option2,...</code> or by\nsetting the string \"<code>option1,option2,...</code>\" under \"Interval iteration options\" in the GUI.\nType <code>prism -help intervaliter</code> from the command-line for a list of the options\nand see [<a class='wikilink' href='../Main/References.html#BKLPW17'>BKLPW17</a>] for the details.\n</p>\n<p class='vspace'><a name='topo' id='topo'></a>\n</p><h3>Topological Value Iteration</h3>\n<p>Topological value iteration is a variant of value iteration which improves efficiency\nby analysing the graph structure of the model and using this to update the values for\nstates in an alternative order which increases the speed of convergence.\nUse switch <code>-topological</code> or GUI option \"Use topological value iteration\" to enable this.\nIn addition to standard value iteration for MDPs, the topological variant can be used to optimise\nboth interval iteration (see above) and the numerical solution of DTMCs.\n</p>\n<p class='vspace'><a name='transient' id='transient'></a>\n</p><h3>CTMC Transient Analysis</h3>\n<p>When computing transient probabilities of a CTMC\n(either <a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>directly</a> or when verifying <a class='wikilink' href='../PropertySpecification/ThePOperator.html#bounded'>time-bounded operators</a> of CSL), there are two options:\n<em>uniformisation</em> and <em>fast adaptive uniformisation</em> (FAU). These can be selected using the GUI option \"Transient probability computation method\", or using the command-line switch <code>-transientmethod &lt;name&gt;</code>, where <code>&lt;name&gt;</code> is either <code>unif</code> or <code>fau</code>.\n</p>\n<p class='vspace'><strong>Uniformisation</strong> is a standard iterative numerical method for computing transient probabilities on a CTMC, which works by reducing the problem to an analysis of a \"uniformised\" DTMC.\nAs an optimisation, when it is detected that the transient probabilities have converged, no further iterations are performed. If necessary (e.g. in case of round-off problems), this optimisation can be disabled with the \"Use steady-state detection\" option (command-line switch <code>-nossdetect</code>).\n</p>\n<p class='vspace'><a name='fau' id='fau'></a>\n<strong>Fast adaptive uniformisation</strong> (FAU) [<a class='wikilink' href='../Main/References.html#MWDH10'>MWDH10</a>] is a method to efficiently approximate transient properties of large CTMCs. The basic idea is that only the parts of the model that are relevant for the current time period are kept in memory. In more detail, starting with the initial states, in each step FAU\nexplores further states in a DTMC which is a discrete-time version of the original CTMC. By combining the\nprobabilities there with those of a certain continuous-time stochastic process (a birth process), transient properties in the original CTMC can be computed. If it turns out that the probability of being in some state in the DTMC is below a given threshold, this state is removed from the model explored so far. After a given number of steps, which corresponds to the number of steps which are likely to happen within the time bound, the exploration can be stopped. In the implementation in PRISM [<a class='wikilink' href='../Main/References.html#DHK13'>DHK13</a>], FAU can be used to compute transient probability distributions and to model check the following types of non-nested CSL formulas: time-bounded until, instantaneous reward, cumulative reward.\n</p>\n<p class='vspace'>The following options can be used to configure FAU:\n</p>\n<div class='vspace'></div><ul><li>\"FAU epsilon\" (switch <code>-fauepsilon &lt;x&gt;</code>): FAU analyses the DTMC for a number of iterations such that the probability of more steps being relevant is below this value. The default is 1e-6.\n<div class='vspace'></div></li><li>\"FAU cut off delta\" (switch <code>-faudelta &lt;x&gt;</code>): States that have a lower probability than this value are discarded. The default is 1e-12.\n<div class='vspace'></div></li><li>\"FAU array threshold\" (switch <code>-fauarraythreshold &lt;x&gt;</code>): After this number of steps without any new states being explored or discarded, FAU will switch to a faster, fixed-size data structure until further states have to be explored or discarded. The default is 100.\n<div class='vspace'></div></li><li>\"FAU time intervals\" (switch <code>-fauintervals &lt;x&gt;</code>): In some cases, it is advantageous to divide the time interval the analysis is done for into several smaller intervals. This option dictates the number of (equal length) intervals used for this split. The default is 1, meaning that only one time interval is used.\n<div class='vspace'></div></li><li>\"FAU initial time interval\" (switch <code>-fauinitival &lt;x&gt;</code>): It is also possible to specify an additional initial time interval which is handled separately from the rest of the time. This is often advantageous, because in this interval certain parameters of the model can be explored, which can subsequently be used to speed up the computation of the remaining time interval. The default for this option is 1.0.\n</li></ul><p class='vspace'><a name='convergence' id='convergence'></a>\n</p><h3>Convergence</h3>\n<p>Common to all of these methods is the way that PRISM checks convergence, i.e. decides when to terminate the iterative methods because the answers have converged sufficiently. This is done by checking when the maximum difference between elements in the solution vectors from successive iterations drops below a given threshold (or, in the case of interval iteration, if the difference of the elements in the iterations from above and below are below the threshold).\nThe default value for this threshold is 10<sup>-6</sup> but it can be altered with the \"Termination epsilon\" option (switch <code>-epsilon &lt;val&gt;</code>). The way that the maximum difference is computed can also be varied:\neither \"relative\" or \"absolute\" (the default is \"relative\"). This can be changed using the \"Termination criteria\" option (command-line switches <code>-relative</code> and <code>-absolute</code>, or <code>-rel</code> and <code>-abs</code> for short).\n</p>\n<p class='vspace'>Also, the maximum number of iterations performed is given an upper limit\nin order to trap the cases when computation will not converge.\nThe default limit is 10,000 but can be changed with the \"Termination max. iterations\" option (switch <code>-maxiters &lt;val&gt;</code>). Computations that reach this upper limit will trigger an error during model checking to alert the user to this fact.\n</p><hr />\n<h1>Automata Generation</h1>\n<p>When PRISM performs verification of <a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>LTL formulas</a>, it does so by converting the formula into an automaton (such as a deterministic Rabin automaton) and then analysing a larger product model, constructed from the model being verified and the omega automaton. For this reason, the size of the automaton has an important effect on the efficiency of verification.\n</p>\n<p class='vspace'>By default PRISM uses a port of the <a class='urllink' href='http://www.ltl2dstar.de/'>ltl2dstar</a> library to construct these automata. But it also allows the use of external LTL-to-automata converters producing deterministic automata through support for the <a class='urllink' href='http://adl.github.io/hoaf/'>Hanoi Omega Automaton</a> (HOA) format. From the command line, an example of this is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-ltl2datool</code> switch specifies the location of the program to be executed to perform the LTL-to-automaton conversion. This will be called by PRISM as \"<code>exec</code> <code>in-file</code> <code>out-file</code>\", where <code>exec</code> is the executable, <code>in-file</code> is the name of a file containing the LTL formula to be converted and <code>out-file</code> is the name of a file where the resulting automaton should be written, in HOA format. Typically, the executable will be a script. Here is a simple example (called as <code>hoa-ltl2dstar-for-prism</code> in the above example), which calls an external copy of <code>ltl2dstar</code> in the required fashion (assuming that the <code>ltl2dstar</code> and <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a>  executables are located in the current directory or on the PATH).\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#! /bin/bash</span><br />\nltl2dstar <span class=\"re5\">--output</span>=automaton <span class=\"re5\">--output-format</span>=hoa <span class=\"st0\">&quot;$1&quot;</span> <span class=\"st0\">&quot;$2&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM is known to work with these HOA-enabled tools:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>\n</li><li><a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>\n</li><li><a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>\n</li><li><a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>\n</li></ul><p class='vspace'>and contains ready-made scripts for calling them in the <code>etc/scripts/hoa</code> directory of the distribution:\n</p>\n<div class='vspace'></div><ul><li><code>hoa-ltl2dstar-for-prism</code> <br />  (<a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>, using <a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>, <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a> or <a class='urllink' href='https://github.com/xblahoud/ltl3dra'>LTL3BA</a> as the LTL-to-NBA tool as the LTL-to-NBA tool)\n</li><li><code>hoa-ltl2tgba-for-prism</code> <br />  (<a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>)\n</li><li><code>hoa-ltl3dra-for-prism</code> <br />  (<a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>)\n</li><li><code>hoa-rabinizer-for-prism</code> <br />  (<a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>'s <code>ltl2dra</code>)\n</li></ul><p class='vspace'>See the files themselves for details of any configuration required, possible options and for a reminder of the PRISM command-line arguments required.\n</p>\n<p class='vspace'>There is also a <code>hoa-rabinizer-for-prism.bat</code> script for connecting to Rabinizer on Windows.\n</p>\n<p class='vspace'>The <code>-ltl2dasyntax</code> switch is used to specify the textual format for passing the LTL formula to the external converter (i.e., in the file <code>out-file</code>). The options are:\n</p>\n<div class='vspace'></div><ul><li><code>lbt</code> - LBT format\n</li><li><code>spin</code> - SPIN format\n</li><li><code>spot</code> - Spot format\n</li><li><code>rabinizer</code> - Rabinizer format\n</li></ul><p class='vspace'>Typical usage is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2tgba-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl3dra-for-prism -ltl2dasyntax spin</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-rabinizer-for-prism -ltl2dasyntax rabinizer</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, configuring the external LTL converter is done with the two options \n\"Use external LTL-&gt;DA tool\" and \"LTL syntax for external LTL-&gt;DA tool\".\n</p>\n<p class='vspace'>Another related option is \"All path formulas via automata\" (command-line switch <code>-pathviaautomata</code>), which forces construction of an automata\nwhen computing the probability of a path formula, even if it is not needed. This is primarily intended for debugging/testing, not regular use.\n</p>\n<p class='vspace'>As mentioned above, PRISM's external LTL-to-automaton interfacing works using the\n<a class='urllink' href='http://adl.github.io/hoaf/'>HOA</a> format\n(and, in particular,  using the <a class='urllink' href='http://automata.tools/hoa/jhoafparser/'><code>jhoafparser</code></a> HOA parser.\nCurrently, PRISM can handle automata in HOA format that are \ndeterministic and complete, with state-based acceptance.\nAutomata with transition-based acceptance are converted to state-based acceptance by PRISM.\nFor DTMC and  CTMC model checking, generic acceptance conditions are supported, i.e., \nanything that can be specified as an <code>Acceptance:</code> header in HOA format. \nFor MDP model checking, currently Rabin and generalized Rabin acceptance \nspecified via the <code>acc-name:</code> header are supported. See the <a class='urllink' href='http://adl.github.io/hoaf/'>HOA format specification</a> for details.\n</p>\n<div class='vspace'></div><hr />\n<h1>Other Options</h1>\n<h3>Output options</h3>\n<p>To increase the amount of information displayed by PRISM (in particular, to display lists of states and probability vectors), you can use the \"Verbose output\" option (activated with command-line switch <code>-verbose</code> or <code>-v</code>). To display additional statistics about MTBDDs after model construction, use the \"Extra MTBDD information\" option (switch <code>-extraddinfo</code>) and, to view MTBDD sizes during the process of reachability, use option \"Extra reachability information\" (switch <code>-extrareachinfo</code>).\n</p>\n<div class='vspace'></div><h3>Fairness</h3>\n<p>Sometimes, model checking of properties for MDPs requires fairness constraints to be taken into account.\nSee e.g. [<a class='wikilink' href='../Main/References.html#BK98'>BK98</a>],[<a class='wikilink' href='../Main/References.html#Bai98'>Bai98</a>] for more information.\nTo enable the use of fairness constraints (for <code><strong>P</strong></code> operator properties), use the <code>-fair</code> switch.\n</p>\n<div class='vspace'></div><h3>Probability/rate checks</h3>\n<p>By default, when constructing a model, PRISM checks that all probabilities and rates are within acceptable ranges (i.e. are between 0 and 1, or are non-negative, respectively). For DTMCs and MDPs, it also checks that the probabilities sum up to one for each command. These checks are often very useful for highlighting user modelling errors and it is strongly recommended that you keep them enabled, however if you need to disable them you can do so via option \"do prob checks?\" in the GUI or command-line switch <code>-noprobchecks</code>.\nYou can also change the level of precision used to check that probabilities sum to 1 using the option \"Probability sum threshold\" (or command-line switch <code>-sumroundoff</code>.\n</p>\n<div class='vspace'></div><h3>CUDD memory</h3>\n<p>CUDD, the underlying BDD and MTBDD library used in PRISM has an upper memory limit. By default, this limit is 1 GB. If you are working on a machine with significantly more memory this and PRISM runs out of memory when model checking, it may help to change this. To set the limit, from the command-line, use the <code>-cuddmaxmem</code> switch. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -cuddmaxmem 2g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Above, <code>g</code> denotes GB. You can also use <code>m</code> for MB.\nYou can also the CUDD maximum memory setting from the options panel in the GUI, but you will need to close and restart the GUI (saving the settings as you do) for this to take effect.\n</p>\n<p class='vspace'><a name='javamaxmem' id='javamaxmem'></a>\n</p><h3>Java memory</h3>\n<p>The Java virtual machine (JVM) used to execute PRISM also has upper memory limits. Sometimes this limit will be exceeded and you will see an error of the form <code>java.lang.OutOfMemory</code>. To resolve this problem, you can increase this memory limit. On Unix, Linux or Mac OS X platforms, this can done by using the <code>-javamaxmem</code> switch, passed either to the command-line script <code>prism</code> or the GUI launcher <code>xprism</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javamaxmem 4g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javamaxmem 4g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>each set the limit to 4GB. Alternatively, you set the environment variable PRISM_JAVAMAXMEM before running PRISM. For example, under a <code>bash</code> shell:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVAMAXMEM=4g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVAMAXMEM</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you get an error of the form <code>java.lang.StackOverflowError</code>, then you can try increasing the stack size of the JVM.\nOn Unix, Linux or Mac OS X platforms, this can done by using the <code>-javastack</code> switch or the <code>PRISM_JAVASTACKSIZE</code> environment variable.\nExamples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javastack 1g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javastack 1g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVASTACKSIZE=1g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVASTACKSIZE</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are running PRISM on Windows you will have to do make adjustments to Java memory manually, by modifying the <code>prism.bat</code> or <code>xprism.bat</code> scripts.\nTo set the memory to 4GB, for example, add <code> -Xmx4g</code> to the list of arguments in the call to <code>java</code> or <code>javaw</code> at the end of the file.\nTo change the stack size to 1GB, add <code>-Xss1g</code>.\n</p>\n<div class='vspace'></div><h3>Other Java options</h3>\n<p>If you want to pass additional switches to the JVM used to run PRISM, you can use the <code>-javaparams</code> switch.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javaparams \"-XX:AutoBoxCacheMax=100000000 -Xmn2g\" -javamaxmem 12g</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Precomputation</h3>\n<p>By default, PRISM's probabilistic model checking algorithms use an initial <em>precomputation</em> step which uses graph-based techniques to efficient detect trivial cases where probabilities are 0 or 1. This can often result in improved performance and also reduce round-off errors. Occasionally, though, you may want to disable this step for efficiency (e.g. if you know that there are no/few such states and the precomputation process is slow). This can be done with the <code>-nopre</code> switch. You can also disable the individual algorithms for probability 0/1 using switches <code>-noprob0</code> and <code>-noprob1</code>.\n</p>\n<div class='vspace'></div><h3>Time-outs</h3>\n<p>The command-line version of PRISM has a time-out option, specified using the switch <code>-timeout &lt;n&gt;</code>.\nThis causes the program to exit after <code>&lt;n&gt;</code> seconds if it has not already terminated by that point.\nThis is particularly useful for benchmarking scenarios where you wish to ignore runs of PRISM that exceed a certain length of time.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/AutomataGeneration.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Automata Generation \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AutomataGeneration.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=edit.html'>Edit</a> - <a class='wikilink' href='AutomataGeneration@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Automata Generation</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>When PRISM performs verification of <a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>LTL formulas</a>, it does so by converting the formula into an automaton (such as a deterministic Rabin automaton) and then analysing a larger product model, constructed from the model being verified and the omega automaton. For this reason, the size of the automaton has an important effect on the efficiency of verification.\n</p>\n<p class='vspace'>By default PRISM uses a port of the <a class='urllink' href='http://www.ltl2dstar.de/'>ltl2dstar</a> library to construct these automata. But it also allows the use of external LTL-to-automata converters producing deterministic automata through support for the <a class='urllink' href='http://adl.github.io/hoaf/'>Hanoi Omega Automaton</a> (HOA) format. From the command line, an example of this is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AutomataGeneration?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-ltl2datool</code> switch specifies the location of the program to be executed to perform the LTL-to-automaton conversion. This will be called by PRISM as \"<code>exec</code> <code>in-file</code> <code>out-file</code>\", where <code>exec</code> is the executable, <code>in-file</code> is the name of a file containing the LTL formula to be converted and <code>out-file</code> is the name of a file where the resulting automaton should be written, in HOA format. Typically, the executable will be a script. Here is a simple example (called as <code>hoa-ltl2dstar-for-prism</code> in the above example), which calls an external copy of <code>ltl2dstar</code> in the required fashion (assuming that the <code>ltl2dstar</code> and <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a>  executables are located in the current directory or on the PATH).\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#! /bin/bash</span><br />\nltl2dstar <span class=\"re5\">--output</span>=automaton <span class=\"re5\">--output-format</span>=hoa <span class=\"st0\">&quot;$1&quot;</span> <span class=\"st0\">&quot;$2&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AutomataGeneration?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM is known to work with these HOA-enabled tools:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>\n</li><li><a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>\n</li><li><a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>\n</li><li><a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>\n</li></ul><p class='vspace'>and contains ready-made scripts for calling them in the <code>etc/scripts/hoa</code> directory of the distribution:\n</p>\n<div class='vspace'></div><ul><li><code>hoa-ltl2dstar-for-prism</code> <br />  (<a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>, using <a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>, <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a> or <a class='urllink' href='https://github.com/xblahoud/ltl3dra'>LTL3BA</a> as the LTL-to-NBA tool as the LTL-to-NBA tool)\n</li><li><code>hoa-ltl2tgba-for-prism</code> <br />  (<a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>)\n</li><li><code>hoa-ltl3dra-for-prism</code> <br />  (<a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>)\n</li><li><code>hoa-rabinizer-for-prism</code> <br />  (<a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>'s <code>ltl2dra</code>)\n</li></ul><p class='vspace'>See the files themselves for details of any configuration required, possible options and for a reminder of the PRISM command-line arguments required.\n</p>\n<p class='vspace'>There is also a <code>hoa-rabinizer-for-prism.bat</code> script for connecting to Rabinizer on Windows.\n</p>\n<p class='vspace'>The <code>-ltl2dasyntax</code> switch is used to specify the textual format for passing the LTL formula to the external converter (i.e., in the file <code>out-file</code>). The options are:\n</p>\n<div class='vspace'></div><ul><li><code>lbt</code> - LBT format\n</li><li><code>spin</code> - SPIN format\n</li><li><code>spot</code> - Spot format\n</li><li><code>rabinizer</code> - Rabinizer format\n</li></ul><p class='vspace'>Typical usage is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2tgba-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl3dra-for-prism -ltl2dasyntax spin</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-rabinizer-for-prism -ltl2dasyntax rabinizer</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AutomataGeneration?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, configuring the external LTL converter is done with the two options \n\"Use external LTL-&gt;DA tool\" and \"LTL syntax for external LTL-&gt;DA tool\".\n</p>\n<p class='vspace'>Another related option is \"All path formulas via automata\" (command-line switch <code>-pathviaautomata</code>), which forces construction of an automata\nwhen computing the probability of a path formula, even if it is not needed. This is primarily intended for debugging/testing, not regular use.\n</p>\n<p class='vspace'>As mentioned above, PRISM's external LTL-to-automaton interfacing works using the\n<a class='urllink' href='http://adl.github.io/hoaf/'>HOA</a> format\n(and, in particular,  using the <a class='urllink' href='http://automata.tools/hoa/jhoafparser/'><code>jhoafparser</code></a> HOA parser.\nCurrently, PRISM can handle automata in HOA format that are \ndeterministic and complete, with state-based acceptance.\nAutomata with transition-based acceptance are converted to state-based acceptance by PRISM.\nFor DTMC and  CTMC model checking, generic acceptance conditions are supported, i.e., \nanything that can be specified as an <code>Acceptance:</code> header in HOA format. \nFor MDP model checking, currently Rabin and generalized Rabin acceptance \nspecified via the <code>acc-name:</code> header are supported. See the <a class='urllink' href='http://adl.github.io/hoaf/'>HOA format specification</a> for details.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AutomataGeneration.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=edit.html'>Edit</a> - <a class='wikilink' href='AutomataGeneration@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 07:46 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='selflink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/AutomataGeneration@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Automata Generation | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AutomataGeneration.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=edit.html'>Edit</a> - <a class='wikilink' href='AutomataGeneration@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Automata Generation</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AutomataGeneration@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AutomataGeneration.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=edit.html'>Edit</a> - <a class='wikilink' href='AutomataGeneration@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 07:46 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='selflink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/AutomataGeneration@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Automata Generation | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AutomataGeneration.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=edit.html'>Edit</a> - <a class='wikilink' href='AutomataGeneration@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Automata Generation</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AutomataGeneration@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AutomataGeneration.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=edit.html'>Edit</a> - <a class='wikilink' href='AutomataGeneration@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AutomataGeneration@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 07:46 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='selflink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/AutomataGeneration@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ConfiguringPRISM / AutomataGeneration </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Automata Generation</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>When PRISM performs verification of <a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>LTL formulas</a>, it does so by converting the formula into an automaton (such as a deterministic Rabin automaton) and then analysing a larger product model, constructed from the model being verified and the omega automaton. For this reason, the size of the automaton has an important effect on the efficiency of verification.\n</p>\n<p class='vspace'>By default PRISM uses a port of the <a class='urllink' href='http://www.ltl2dstar.de/'>ltl2dstar</a> library to construct these automata. But it also allows the use of external LTL-to-automata converters producing deterministic automata through support for the <a class='urllink' href='http://adl.github.io/hoaf/'>Hanoi Omega Automaton</a> (HOA) format. From the command line, an example of this is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AutomataGeneration?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-ltl2datool</code> switch specifies the location of the program to be executed to perform the LTL-to-automaton conversion. This will be called by PRISM as \"<code>exec</code> <code>in-file</code> <code>out-file</code>\", where <code>exec</code> is the executable, <code>in-file</code> is the name of a file containing the LTL formula to be converted and <code>out-file</code> is the name of a file where the resulting automaton should be written, in HOA format. Typically, the executable will be a script. Here is a simple example (called as <code>hoa-ltl2dstar-for-prism</code> in the above example), which calls an external copy of <code>ltl2dstar</code> in the required fashion (assuming that the <code>ltl2dstar</code> and <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a>  executables are located in the current directory or on the PATH).\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#! /bin/bash</span><br />\nltl2dstar <span class=\"re5\">--output</span>=automaton <span class=\"re5\">--output-format</span>=hoa <span class=\"st0\">&quot;$1&quot;</span> <span class=\"st0\">&quot;$2&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AutomataGeneration?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM is known to work with these HOA-enabled tools:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>\n</li><li><a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>\n</li><li><a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>\n</li><li><a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>\n</li></ul><p class='vspace'>and contains ready-made scripts for calling them in the <code>etc/scripts/hoa</code> directory of the distribution:\n</p>\n<div class='vspace'></div><ul><li><code>hoa-ltl2dstar-for-prism</code> <br />  (<a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>, using <a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>, <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a> or <a class='urllink' href='https://github.com/xblahoud/ltl3dra'>LTL3BA</a> as the LTL-to-NBA tool as the LTL-to-NBA tool)\n</li><li><code>hoa-ltl2tgba-for-prism</code> <br />  (<a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>)\n</li><li><code>hoa-ltl3dra-for-prism</code> <br />  (<a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>)\n</li><li><code>hoa-rabinizer-for-prism</code> <br />  (<a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>'s <code>ltl2dra</code>)\n</li></ul><p class='vspace'>See the files themselves for details of any configuration required, possible options and for a reminder of the PRISM command-line arguments required.\n</p>\n<p class='vspace'>There is also a <code>hoa-rabinizer-for-prism.bat</code> script for connecting to Rabinizer on Windows.\n</p>\n<p class='vspace'>The <code>-ltl2dasyntax</code> switch is used to specify the textual format for passing the LTL formula to the external converter (i.e., in the file <code>out-file</code>). The options are:\n</p>\n<div class='vspace'></div><ul><li><code>lbt</code> - LBT format\n</li><li><code>spin</code> - SPIN format\n</li><li><code>spot</code> - Spot format\n</li><li><code>rabinizer</code> - Rabinizer format\n</li></ul><p class='vspace'>Typical usage is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2tgba-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl3dra-for-prism -ltl2dasyntax spin</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-rabinizer-for-prism -ltl2dasyntax rabinizer</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/AutomataGeneration?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, configuring the external LTL converter is done with the two options \n\"Use external LTL-&gt;DA tool\" and \"LTL syntax for external LTL-&gt;DA tool\".\n</p>\n<p class='vspace'>Another related option is \"All path formulas via automata\" (command-line switch <code>-pathviaautomata</code>), which forces construction of an automata\nwhen computing the probability of a path formula, even if it is not needed. This is primarily intended for debugging/testing, not regular use.\n</p>\n<p class='vspace'>As mentioned above, PRISM's external LTL-to-automaton interfacing works using the\n<a class='urllink' href='http://adl.github.io/hoaf/'>HOA</a> format\n(and, in particular,  using the <a class='urllink' href='http://automata.tools/hoa/jhoafparser/'><code>jhoafparser</code></a> HOA parser.\nCurrently, PRISM can handle automata in HOA format that are \ndeterministic and complete, with state-based acceptance.\nAutomata with transition-based acceptance are converted to state-based acceptance by PRISM.\nFor DTMC and  CTMC model checking, generic acceptance conditions are supported, i.e., \nanything that can be specified as an <code>Acceptance:</code> header in HOA format. \nFor MDP model checking, currently Rabin and generalized Rabin acceptance \nspecified via the <code>acc-name:</code> header are supported. See the <a class='urllink' href='http://adl.github.io/hoaf/'>HOA format specification</a> for details.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/ComputationEngines.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Computation Engines \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ComputationEngines.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ComputationEngines@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputationEngines@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Computation Engines</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<h3>Computation engines</h3>\n<p>PRISM contains four main <em>engines</em>,\nwhich implement the majority of its model checking functionality:\n</p>\n<div class='vspace'></div><ul><li>\"MTBDD\"\n</li><li>\"sparse\"\n</li><li>\"hybrid\"\n</li><li>\"explicit\"\n</li></ul><p class='vspace'>The first three of these engines are either wholly or partly <em>symbolic</em>,\nmeaning that they use data structures such as\nbinary decision diagrams (BDDs) and multi-terminal BDDs (MTBDDs).\nFor these three engines, the process of\nconstructing a probabilistic model (DTMC, MDP or CTMC)\nis performed in a symbolic fashion,\nrepresenting the model as an MTBDD.\nSubsequent numerical computation performed during model checking, however,\nis carried out differently for the three engines.\nThe \"MTBDD\" engine is implemented purely using MTBDDs and BDDs;\nthe \"sparse\" engine uses sparse matrices;\nand the \"hybrid\" engine uses a combination of the other two.\nThe \"hybrid\" engine is described in [<a class='wikilink' href='../Main/References.html#KNP04b'>KNP04b</a>].\nFor detailed information about all three engines, see [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>].\n</p>\n<p class='vspace'>The fourth engine, \"explicit\", performs all aspects of model construction\nand model checking using <em>explicit-state</em> data structures.\nModels are typically stored as sparse matrices or variants of.\nThis engine is implemented purely in Java, unlike the other engines\nwhich make use of code/libraries implemented in C/C++.\nOne goal of the \"explicit\" engine is to provide an easily extensible model\nchecking engine without the complication of symbolic data structures,\nalthough it also has other benefits (see below).\n</p>\n<p class='vspace'>The choice of engine (\"MTBDD\", \"sparse\", \"hybrid\" or \"engine\") should not affect the results of model checking - all engines perform essentially the same calculations. In some cases, though, certain functionality is not available with all engines and PRISM will either automatically switch to an appropriate engine, or prompt you to do so.\nPerformance (time and space), however, may vary significantly and if you are using too much time/memory with one engine, it may be worth experimenting. Below, we briefly summarise the key characteristics of each engine.\n</p>\n<div class='vspace'></div><ul><li>The <strong>hybrid</strong> engine is enabled by default in PRISM. It uses a combination of <em>symbolic</em> and <em>explicit-state</em> data structures (as used in the MTBDD and sparse engines, respectively). In general it provides the best compromise between time and memory usage: it (almost) always uses less memory than the sparse engine, but is typically slightly slower. The size of model which can be handled with this engine is quite predictable. The limiting factor in terms of memory usage comes from the storage of 2-4 (depending on the computation being performed) arrays of 8-byte values, one for each state in the model. So, a typical PC can handle models with between 10<sup>7</sup> and 10<sup>8</sup> states (one vector for 10<sup>7</sup> states uses approximately 75 MB).\n<div class='vspace'></div></li><li>The <strong>sparse</strong> engine can be a good option for smaller models where model checking takes a long time. For larger models, however, memory usage quickly becomes prohibitive. As a rule of thumb, the upper limit for this engine, in terms of model sizes which can be handled, is about a factor of 10 less than the hybrid engine.\n<div class='vspace'></div></li><li>The <strong>MTBDD</strong> engine is much more unpredictable in terms of performance but, when a model exhibits a lot of structure and regularity, can be very effective. This engine has been successfully applied to extremely large structured (but non-trivial) models, in cases where the other two engines cannot be applied. The MTBDD engine often performs poorly when the model (or solutions computed from it) contain lots of distinct probabilities/rates; it performs best when there are few such values. For this reason the engine is often successfully applied to MDP models, but much less frequently to CTMCs. When using the MTBDD engine, the <em>variable ordering</em> of your model is especially important. This topic is covered in the <a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html#ordering'>FAQ</a> section.\n<div class='vspace'></div></li><li>The <strong>explicit</strong> engine is similar to the sparse engine, in that it can be a good option for relatively small models, but will not scale up to some of the models that can be handled by the hybrid or MTBDD engines. However, unlike the sparse engine, the explicit engine does not use symbolic data structures for model construction, which can be beneficial in some cases. One example is models with a potentially very large state space, only a fraction of which is actually reachable.\n</li></ul><p class='vspace'>When using the PRISM GUI, the engine to be used for model checking can be selected from the \"Engine\" option under the \"PRISM\" tab of the \"Options\" dialog. From the command-line, engines are activated using the <code>-mtbdd</code>, <code>-sparse</code>, <code>-hybrid</code> and <code>-explicit</code> (or <code>-m</code>, <code>-s</code>, <code>-h</code> and <code>-ex</code>, respectively) switches, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -m</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -s</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -h</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/ComputationEngines?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note also that precise details regarding the memory usage of the current engine are displayed during model checking (from the GUI, check the \"Log\" tab). This can provide valuable feedback when experimenting with different engines.\n</p>\n<p class='vspace'>PRISM also has some basic support for automatically selecting the engine (and other settings) heuristically,\nbased on the size and type of the model, and the property being checked.\nUse, for example, <code>-heuristic speed</code> from the command-line to choose options\nwhich target computation speed rather than saving memory.\nThis is also available from the \"Heuristic\" option under the \"PRISM\" tab of the \"Options\" dialog in the GUI.\n</p>\n<div class='vspace'></div><h3>Approximate/statistical model checking</h3>\n<p>Although it is not treated as a separate \"engine\", like those above,\nPRISM also provides approximate/statistical model checking,\nwhich is based on the use of discrete-event simulation.\nFrom the GUI, this is enabled by choosing \"Simulate\" menu items or tick boxes;\nfrom the command-line, add the <code>-sim</code> switch.\nSee the \"<a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\"\nsection for more details.\n</p>\n<p class='vspace'><a name='exact' id='exact'></a>\n</p><h3>Exact model checking</h3>\n<p>Most of PRISM's model checking functionality uses numerical solution based on floating point arithmetic and, often, this uses iterative numerical methods, which are run until some user-specified precision is reached. PRISM currently has some support for \"exact\" model checking, i.e., using arbitrary precision arithmetic to provide exact numerical values. Currently, this is implemented as a special case of <a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>parametric model checking</a>, which limits is application to relatively small models. It can be used for analysing DTMCs/CTMCs (unbounded until, steady-state probabilities, reachability reward and steady-state reward) or MDPs (unbounded until and reachability rewards). You can enable this functionality using the \"Do exact model checking\" option in the GUI or using switch <code>-exact</code> from the command line.\n</p>\n<p class='vspace'><a name='pta' id='pta'></a>\n</p><h3>PTA engines</h3>\n<p>The techniques used to model check PTAs are different to the ones used for DTMCs, MDPs and CTMCs. For PTAs, PRISM currently has three distinct engines that can be used:\n</p>\n<div class='vspace'></div><ul><li>The <strong>stochastic games</strong> engine uses abstraction-refinement techniques based on stochastic two-player games [<a class='wikilink' href='../Main/References.html#KNP09c'>KNP09c</a>].\n<div class='vspace'></div></li><li>The <strong>digital clocks</strong> engine performs a discretisation, in the form of a language-level model translation, that reduces the problem to one of model checking over a finite-state MDP [<a class='wikilink' href='../Main/References.html#KNPS06'>KNPS06</a>].\n<div class='vspace'></div></li><li>The <strong>backwards reachability</strong> engine is a zone-based method based on a backwards traversal of the state space and solution of the resulting finite-state MDP [<a class='wikilink' href='../Main/References.html#KNSW07'>KNSW07</a>].\n</li></ul><p class='vspace'>The default engine for PTAs is \"stochastic games\". The engine to be used can be specified using the \"PTA model checking method\" setting in the \"PRISM\" options panel in the GUI. From the command-line, switch <code>-ptamethod &lt;name&gt;</code> should be used where <code>&lt;name&gt;</code> is either <code>games</code>, <code>digital</code> or <code>backwards</code>.\n</p>\n<p class='vspace'>The choice of engine for PTA model checking affects restrictions that imposed on both\nthe <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>modelling language</a>\nand the types of <a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>properties</a> that can be checked.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ComputationEngines.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ComputationEngines@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputationEngines@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ComputationEngines@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:08 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/ComputationEngines@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Computation Engines | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ComputationEngines.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ComputationEngines@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputationEngines@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Computation Engines</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ComputationEngines@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ComputationEngines.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ComputationEngines@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputationEngines@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ComputationEngines@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:08 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/ComputationEngines@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Computation Engines | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ComputationEngines.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ComputationEngines@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputationEngines@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Computation Engines</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ComputationEngines@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ComputationEngines.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ComputationEngines@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputationEngines@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ComputationEngines@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:08 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/ComputationEngines@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ConfiguringPRISM / ComputationEngines </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Computation Engines</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<h3>Computation engines</h3>\n<p>PRISM contains four main <em>engines</em>,\nwhich implement the majority of its model checking functionality:\n</p>\n<div class='vspace'></div><ul><li>\"MTBDD\"\n</li><li>\"sparse\"\n</li><li>\"hybrid\"\n</li><li>\"explicit\"\n</li></ul><p class='vspace'>The first three of these engines are either wholly or partly <em>symbolic</em>,\nmeaning that they use data structures such as\nbinary decision diagrams (BDDs) and multi-terminal BDDs (MTBDDs).\nFor these three engines, the process of\nconstructing a probabilistic model (DTMC, MDP or CTMC)\nis performed in a symbolic fashion,\nrepresenting the model as an MTBDD.\nSubsequent numerical computation performed during model checking, however,\nis carried out differently for the three engines.\nThe \"MTBDD\" engine is implemented purely using MTBDDs and BDDs;\nthe \"sparse\" engine uses sparse matrices;\nand the \"hybrid\" engine uses a combination of the other two.\nThe \"hybrid\" engine is described in [<a class='wikilink' href='../Main/References.html#KNP04b'>KNP04b</a>].\nFor detailed information about all three engines, see [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>].\n</p>\n<p class='vspace'>The fourth engine, \"explicit\", performs all aspects of model construction\nand model checking using <em>explicit-state</em> data structures.\nModels are typically stored as sparse matrices or variants of.\nThis engine is implemented purely in Java, unlike the other engines\nwhich make use of code/libraries implemented in C/C++.\nOne goal of the \"explicit\" engine is to provide an easily extensible model\nchecking engine without the complication of symbolic data structures,\nalthough it also has other benefits (see below).\n</p>\n<p class='vspace'>The choice of engine (\"MTBDD\", \"sparse\", \"hybrid\" or \"engine\") should not affect the results of model checking - all engines perform essentially the same calculations. In some cases, though, certain functionality is not available with all engines and PRISM will either automatically switch to an appropriate engine, or prompt you to do so.\nPerformance (time and space), however, may vary significantly and if you are using too much time/memory with one engine, it may be worth experimenting. Below, we briefly summarise the key characteristics of each engine.\n</p>\n<div class='vspace'></div><ul><li>The <strong>hybrid</strong> engine is enabled by default in PRISM. It uses a combination of <em>symbolic</em> and <em>explicit-state</em> data structures (as used in the MTBDD and sparse engines, respectively). In general it provides the best compromise between time and memory usage: it (almost) always uses less memory than the sparse engine, but is typically slightly slower. The size of model which can be handled with this engine is quite predictable. The limiting factor in terms of memory usage comes from the storage of 2-4 (depending on the computation being performed) arrays of 8-byte values, one for each state in the model. So, a typical PC can handle models with between 10<sup>7</sup> and 10<sup>8</sup> states (one vector for 10<sup>7</sup> states uses approximately 75 MB).\n<div class='vspace'></div></li><li>The <strong>sparse</strong> engine can be a good option for smaller models where model checking takes a long time. For larger models, however, memory usage quickly becomes prohibitive. As a rule of thumb, the upper limit for this engine, in terms of model sizes which can be handled, is about a factor of 10 less than the hybrid engine.\n<div class='vspace'></div></li><li>The <strong>MTBDD</strong> engine is much more unpredictable in terms of performance but, when a model exhibits a lot of structure and regularity, can be very effective. This engine has been successfully applied to extremely large structured (but non-trivial) models, in cases where the other two engines cannot be applied. The MTBDD engine often performs poorly when the model (or solutions computed from it) contain lots of distinct probabilities/rates; it performs best when there are few such values. For this reason the engine is often successfully applied to MDP models, but much less frequently to CTMCs. When using the MTBDD engine, the <em>variable ordering</em> of your model is especially important. This topic is covered in the <a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html#ordering'>FAQ</a> section.\n<div class='vspace'></div></li><li>The <strong>explicit</strong> engine is similar to the sparse engine, in that it can be a good option for relatively small models, but will not scale up to some of the models that can be handled by the hybrid or MTBDD engines. However, unlike the sparse engine, the explicit engine does not use symbolic data structures for model construction, which can be beneficial in some cases. One example is models with a potentially very large state space, only a fraction of which is actually reachable.\n</li></ul><p class='vspace'>When using the PRISM GUI, the engine to be used for model checking can be selected from the \"Engine\" option under the \"PRISM\" tab of the \"Options\" dialog. From the command-line, engines are activated using the <code>-mtbdd</code>, <code>-sparse</code>, <code>-hybrid</code> and <code>-explicit</code> (or <code>-m</code>, <code>-s</code>, <code>-h</code> and <code>-ex</code>, respectively) switches, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -m</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -s</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -h</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/ComputationEngines?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note also that precise details regarding the memory usage of the current engine are displayed during model checking (from the GUI, check the \"Log\" tab). This can provide valuable feedback when experimenting with different engines.\n</p>\n<p class='vspace'>PRISM also has some basic support for automatically selecting the engine (and other settings) heuristically,\nbased on the size and type of the model, and the property being checked.\nUse, for example, <code>-heuristic speed</code> from the command-line to choose options\nwhich target computation speed rather than saving memory.\nThis is also available from the \"Heuristic\" option under the \"PRISM\" tab of the \"Options\" dialog in the GUI.\n</p>\n<div class='vspace'></div><h3>Approximate/statistical model checking</h3>\n<p>Although it is not treated as a separate \"engine\", like those above,\nPRISM also provides approximate/statistical model checking,\nwhich is based on the use of discrete-event simulation.\nFrom the GUI, this is enabled by choosing \"Simulate\" menu items or tick boxes;\nfrom the command-line, add the <code>-sim</code> switch.\nSee the \"<a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\"\nsection for more details.\n</p>\n<p class='vspace'><a name='exact' id='exact'></a>\n</p><h3>Exact model checking</h3>\n<p>Most of PRISM's model checking functionality uses numerical solution based on floating point arithmetic and, often, this uses iterative numerical methods, which are run until some user-specified precision is reached. PRISM currently has some support for \"exact\" model checking, i.e., using arbitrary precision arithmetic to provide exact numerical values. Currently, this is implemented as a special case of <a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>parametric model checking</a>, which limits is application to relatively small models. It can be used for analysing DTMCs/CTMCs (unbounded until, steady-state probabilities, reachability reward and steady-state reward) or MDPs (unbounded until and reachability rewards). You can enable this functionality using the \"Do exact model checking\" option in the GUI or using switch <code>-exact</code> from the command line.\n</p>\n<p class='vspace'><a name='pta' id='pta'></a>\n</p><h3>PTA engines</h3>\n<p>The techniques used to model check PTAs are different to the ones used for DTMCs, MDPs and CTMCs. For PTAs, PRISM currently has three distinct engines that can be used:\n</p>\n<div class='vspace'></div><ul><li>The <strong>stochastic games</strong> engine uses abstraction-refinement techniques based on stochastic two-player games [<a class='wikilink' href='../Main/References.html#KNP09c'>KNP09c</a>].\n<div class='vspace'></div></li><li>The <strong>digital clocks</strong> engine performs a discretisation, in the form of a language-level model translation, that reduces the problem to one of model checking over a finite-state MDP [<a class='wikilink' href='../Main/References.html#KNPS06'>KNPS06</a>].\n<div class='vspace'></div></li><li>The <strong>backwards reachability</strong> engine is a zone-based method based on a backwards traversal of the state space and solution of the resulting finite-state MDP [<a class='wikilink' href='../Main/References.html#KNSW07'>KNSW07</a>].\n</li></ul><p class='vspace'>The default engine for PTAs is \"stochastic games\". The engine to be used can be specified using the \"PTA model checking method\" setting in the \"PRISM\" options panel in the GUI. From the command-line, switch <code>-ptamethod &lt;name&gt;</code> should be used where <code>&lt;name&gt;</code> is either <code>games</code>, <code>digital</code> or <code>backwards</code>.\n</p>\n<p class='vspace'>The choice of engine for PTA model checking affects restrictions that imposed on both\nthe <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>modelling language</a>\nand the types of <a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>properties</a> that can be checked.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/Introduction@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Introduction | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Introduction@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 28, 2021, at 10:30 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/Introduction@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Introduction | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Introduction@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 28, 2021, at 10:30 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/Introduction@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ConfiguringPRISM / Introduction </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Introduction</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>The operation of PRISM can be configured in a number of ways. From the GUI, select \"Options\" from the main menu to bring up the \"Options\" dialog. The settings are grouped under several tabs. Those which affect the basic model checking functionality of the tool are under the heading \"PRISM\". Separate settings are available for the simulator and various aspects of the GUI (the model editor, the property editor and the log).\n</p>\n<p class='vspace'>User options and settings for the GUI are saved in a file locally and reused. Currently the \"Options\" dialog in the GUI represents the easiest way to modify the settings, but the settings file is in a simple textual format and can also be edited by hand. To restore the default options for PRISM, click \"Load Defaults\" and then \"Save Options\" from the \"Options\" dialog in the GUI. Alternatively, delete the settings file re-launch the GUI. The location of the settings file depends on the operating system. As of PRISM 4.5, it is stored in:\n</p>\n<div class='vspace'></div><ul><li><code>$HOME/.prism</code> (if the settings file was already created by an older version of PRISM)\n</li><li><code>$XDG_CONFIG_HOME/prism.settings</code> (on Linux, if that environment variable is set)\n</li><li><code>$HOME/.config/prism.settings</code> (on Linux, if <code>$XDG_CONFIG_HOME</code> is not set)\n</li><li><code>$HOME/Library/Preferences/prism.settings</code> (on Mac OS)\n</li><li><code>.prism</code> in the user's home directory, e.g. <code>C:\\Documents and Settings\\username</code> (on Windows)\n</li></ul><p class='vspace'>From the command-line version of PRISM, options are controlled by switches. A full list can be displayed by typing:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/Introduction?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For some switches, whose format is not straightforward, there is additional help available on the command-line, using <code>-help switch</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help const</span><br/>\n<span style=\"font-weight:bold;\">prism -help simpath</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportresults</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportmodel</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/Introduction?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The settings file is <em>ignored</em> by the command-line version (unlike earlier versions of PRISM, where it was used). You can, however, request that the settings file <em>is</em> read, using the <code>-settings</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -settings ~/.prism</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/Introduction?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the following sections, we give a brief description of the most important configuration options available.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/Main.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Introduction \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The operation of PRISM can be configured in a number of ways. From the GUI, select \"Options\" from the main menu to bring up the \"Options\" dialog. The settings are grouped under several tabs. Those which affect the basic model checking functionality of the tool are under the heading \"PRISM\". Separate settings are available for the simulator and various aspects of the GUI (the model editor, the property editor and the log).\n</p>\n<p class='vspace'>User options and settings for the GUI are saved in a file locally and reused. Currently the \"Options\" dialog in the GUI represents the easiest way to modify the settings, but the settings file is in a simple textual format and can also be edited by hand. To restore the default options for PRISM, click \"Load Defaults\" and then \"Save Options\" from the \"Options\" dialog in the GUI. Alternatively, delete the settings file re-launch the GUI. The location of the settings file depends on the operating system. As of PRISM 4.5, it is stored in:\n</p>\n<div class='vspace'></div><ul><li><code>$HOME/.prism</code> (if the settings file was already created by an older version of PRISM)\n</li><li><code>$XDG_CONFIG_HOME/prism.settings</code> (on Linux, if that environment variable is set)\n</li><li><code>$HOME/.config/prism.settings</code> (on Linux, if <code>$XDG_CONFIG_HOME</code> is not set)\n</li><li><code>$HOME/Library/Preferences/prism.settings</code> (on Mac OS)\n</li><li><code>.prism</code> in the user's home directory, e.g. <code>C:\\Documents and Settings\\username</code> (on Windows)\n</li></ul><p class='vspace'>From the command-line version of PRISM, options are controlled by switches. A full list can be displayed by typing:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/Introduction?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For some switches, whose format is not straightforward, there is additional help available on the command-line, using <code>-help switch</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help const</span><br/>\n<span style=\"font-weight:bold;\">prism -help simpath</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportresults</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportmodel</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/Introduction?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The settings file is <em>ignored</em> by the command-line version (unlike earlier versions of PRISM, where it was used). You can, however, request that the settings file <em>is</em> read, using the <code>-settings</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -settings ~/.prism</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/Introduction?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the following sections, we give a brief description of the most important configuration options available.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 28, 2021, at 10:30 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/OtherOptions.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Other Options \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='OtherOptions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='OtherOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='OtherOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Other Options</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<h3>Output options</h3>\n<p>To increase the amount of information displayed by PRISM (in particular, to display lists of states and probability vectors), you can use the \"Verbose output\" option (activated with command-line switch <code>-verbose</code> or <code>-v</code>). To display additional statistics about MTBDDs after model construction, use the \"Extra MTBDD information\" option (switch <code>-extraddinfo</code>) and, to view MTBDD sizes during the process of reachability, use option \"Extra reachability information\" (switch <code>-extrareachinfo</code>).\n</p>\n<div class='vspace'></div><h3>Fairness</h3>\n<p>Sometimes, model checking of properties for MDPs requires fairness constraints to be taken into account.\nSee e.g. [<a class='wikilink' href='../Main/References.html#BK98'>BK98</a>],[<a class='wikilink' href='../Main/References.html#Bai98'>Bai98</a>] for more information.\nTo enable the use of fairness constraints (for <code><strong>P</strong></code> operator properties), use the <code>-fair</code> switch.\n</p>\n<div class='vspace'></div><h3>Probability/rate checks</h3>\n<p>By default, when constructing a model, PRISM checks that all probabilities and rates are within acceptable ranges (i.e. are between 0 and 1, or are non-negative, respectively). For DTMCs and MDPs, it also checks that the probabilities sum up to one for each command. These checks are often very useful for highlighting user modelling errors and it is strongly recommended that you keep them enabled, however if you need to disable them you can do so via option \"do prob checks?\" in the GUI or command-line switch <code>-noprobchecks</code>.\nYou can also change the level of precision used to check that probabilities sum to 1 using the option \"Probability sum threshold\" (or command-line switch <code>-sumroundoff</code>.\n</p>\n<div class='vspace'></div><h3>CUDD memory</h3>\n<p>CUDD, the underlying BDD and MTBDD library used in PRISM has an upper memory limit. By default, this limit is 1 GB. If you are working on a machine with significantly more memory this and PRISM runs out of memory when model checking, it may help to change this. To set the limit, from the command-line, use the <code>-cuddmaxmem</code> switch. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -cuddmaxmem 2g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Above, <code>g</code> denotes GB. You can also use <code>m</code> for MB.\nYou can also the CUDD maximum memory setting from the options panel in the GUI, but you will need to close and restart the GUI (saving the settings as you do) for this to take effect.\n</p>\n<p class='vspace'><a name='javamaxmem' id='javamaxmem'></a>\n</p><h3>Java memory</h3>\n<p>The Java virtual machine (JVM) used to execute PRISM also has upper memory limits. Sometimes this limit will be exceeded and you will see an error of the form <code>java.lang.OutOfMemory</code>. To resolve this problem, you can increase this memory limit. On Unix, Linux or Mac OS X platforms, this can done by using the <code>-javamaxmem</code> switch, passed either to the command-line script <code>prism</code> or the GUI launcher <code>xprism</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javamaxmem 4g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javamaxmem 4g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>each set the limit to 4GB. Alternatively, you set the environment variable PRISM_JAVAMAXMEM before running PRISM. For example, under a <code>bash</code> shell:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVAMAXMEM=4g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVAMAXMEM</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you get an error of the form <code>java.lang.StackOverflowError</code>, then you can try increasing the stack size of the JVM.\nOn Unix, Linux or Mac OS X platforms, this can done by using the <code>-javastack</code> switch or the <code>PRISM_JAVASTACKSIZE</code> environment variable.\nExamples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javastack 1g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javastack 1g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVASTACKSIZE=1g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVASTACKSIZE</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are running PRISM on Windows you will have to do make adjustments to Java memory manually, by modifying the <code>prism.bat</code> or <code>xprism.bat</code> scripts.\nTo set the memory to 4GB, for example, add <code> -Xmx4g</code> to the list of arguments in the call to <code>java</code> or <code>javaw</code> at the end of the file.\nTo change the stack size to 1GB, add <code>-Xss1g</code>.\n</p>\n<div class='vspace'></div><h3>Other Java options</h3>\n<p>If you want to pass additional switches to the JVM used to run PRISM, you can use the <code>-javaparams</code> switch.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javaparams \"-XX:AutoBoxCacheMax=100000000 -Xmn2g\" -javamaxmem 12g</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Precomputation</h3>\n<p>By default, PRISM's probabilistic model checking algorithms use an initial <em>precomputation</em> step which uses graph-based techniques to efficient detect trivial cases where probabilities are 0 or 1. This can often result in improved performance and also reduce round-off errors. Occasionally, though, you may want to disable this step for efficiency (e.g. if you know that there are no/few such states and the precomputation process is slow). This can be done with the <code>-nopre</code> switch. You can also disable the individual algorithms for probability 0/1 using switches <code>-noprob0</code> and <code>-noprob1</code>.\n</p>\n<div class='vspace'></div><h3>Time-outs</h3>\n<p>The command-line version of PRISM has a time-out option, specified using the switch <code>-timeout &lt;n&gt;</code>.\nThis causes the program to exit after <code>&lt;n&gt;</code> seconds if it has not already terminated by that point.\nThis is particularly useful for benchmarking scenarios where you wish to ignore runs of PRISM that exceed a certain length of time.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='OtherOptions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='OtherOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='OtherOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='OtherOptions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:41 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='selflink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/OtherOptions@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Other Options | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='OtherOptions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='OtherOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='OtherOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Other Options</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='OtherOptions@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='OtherOptions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='OtherOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='OtherOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='OtherOptions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:41 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='selflink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/OtherOptions@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Other Options | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='OtherOptions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='OtherOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='OtherOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Other Options</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='OtherOptions@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='OtherOptions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='OtherOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='OtherOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='OtherOptions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:41 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='selflink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/OtherOptions@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ConfiguringPRISM / OtherOptions </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Other Options</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<h3>Output options</h3>\n<p>To increase the amount of information displayed by PRISM (in particular, to display lists of states and probability vectors), you can use the \"Verbose output\" option (activated with command-line switch <code>-verbose</code> or <code>-v</code>). To display additional statistics about MTBDDs after model construction, use the \"Extra MTBDD information\" option (switch <code>-extraddinfo</code>) and, to view MTBDD sizes during the process of reachability, use option \"Extra reachability information\" (switch <code>-extrareachinfo</code>).\n</p>\n<div class='vspace'></div><h3>Fairness</h3>\n<p>Sometimes, model checking of properties for MDPs requires fairness constraints to be taken into account.\nSee e.g. [<a class='wikilink' href='../Main/References.html#BK98'>BK98</a>],[<a class='wikilink' href='../Main/References.html#Bai98'>Bai98</a>] for more information.\nTo enable the use of fairness constraints (for <code><strong>P</strong></code> operator properties), use the <code>-fair</code> switch.\n</p>\n<div class='vspace'></div><h3>Probability/rate checks</h3>\n<p>By default, when constructing a model, PRISM checks that all probabilities and rates are within acceptable ranges (i.e. are between 0 and 1, or are non-negative, respectively). For DTMCs and MDPs, it also checks that the probabilities sum up to one for each command. These checks are often very useful for highlighting user modelling errors and it is strongly recommended that you keep them enabled, however if you need to disable them you can do so via option \"do prob checks?\" in the GUI or command-line switch <code>-noprobchecks</code>.\nYou can also change the level of precision used to check that probabilities sum to 1 using the option \"Probability sum threshold\" (or command-line switch <code>-sumroundoff</code>.\n</p>\n<div class='vspace'></div><h3>CUDD memory</h3>\n<p>CUDD, the underlying BDD and MTBDD library used in PRISM has an upper memory limit. By default, this limit is 1 GB. If you are working on a machine with significantly more memory this and PRISM runs out of memory when model checking, it may help to change this. To set the limit, from the command-line, use the <code>-cuddmaxmem</code> switch. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -cuddmaxmem 2g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Above, <code>g</code> denotes GB. You can also use <code>m</code> for MB.\nYou can also the CUDD maximum memory setting from the options panel in the GUI, but you will need to close and restart the GUI (saving the settings as you do) for this to take effect.\n</p>\n<p class='vspace'><a name='javamaxmem' id='javamaxmem'></a>\n</p><h3>Java memory</h3>\n<p>The Java virtual machine (JVM) used to execute PRISM also has upper memory limits. Sometimes this limit will be exceeded and you will see an error of the form <code>java.lang.OutOfMemory</code>. To resolve this problem, you can increase this memory limit. On Unix, Linux or Mac OS X platforms, this can done by using the <code>-javamaxmem</code> switch, passed either to the command-line script <code>prism</code> or the GUI launcher <code>xprism</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javamaxmem 4g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javamaxmem 4g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>each set the limit to 4GB. Alternatively, you set the environment variable PRISM_JAVAMAXMEM before running PRISM. For example, under a <code>bash</code> shell:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVAMAXMEM=4g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVAMAXMEM</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you get an error of the form <code>java.lang.StackOverflowError</code>, then you can try increasing the stack size of the JVM.\nOn Unix, Linux or Mac OS X platforms, this can done by using the <code>-javastack</code> switch or the <code>PRISM_JAVASTACKSIZE</code> environment variable.\nExamples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javastack 1g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javastack 1g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVASTACKSIZE=1g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVASTACKSIZE</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are running PRISM on Windows you will have to do make adjustments to Java memory manually, by modifying the <code>prism.bat</code> or <code>xprism.bat</code> scripts.\nTo set the memory to 4GB, for example, add <code> -Xmx4g</code> to the list of arguments in the call to <code>java</code> or <code>javaw</code> at the end of the file.\nTo change the stack size to 1GB, add <code>-Xss1g</code>.\n</p>\n<div class='vspace'></div><h3>Other Java options</h3>\n<p>If you want to pass additional switches to the JVM used to run PRISM, you can use the <code>-javaparams</code> switch.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javaparams \"-XX:AutoBoxCacheMax=100000000 -Xmn2g\" -javamaxmem 12g</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ConfiguringPRISM/OtherOptions?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Precomputation</h3>\n<p>By default, PRISM's probabilistic model checking algorithms use an initial <em>precomputation</em> step which uses graph-based techniques to efficient detect trivial cases where probabilities are 0 or 1. This can often result in improved performance and also reduce round-off errors. Occasionally, though, you may want to disable this step for efficiency (e.g. if you know that there are no/few such states and the precomputation process is slow). This can be done with the <code>-nopre</code> switch. You can also disable the individual algorithms for probability 0/1 using switches <code>-noprob0</code> and <code>-noprob1</code>.\n</p>\n<div class='vspace'></div><h3>Time-outs</h3>\n<p>The command-line version of PRISM has a time-out option, specified using the switch <code>-timeout &lt;n&gt;</code>.\nThis causes the program to exit after <code>&lt;n&gt;</code> seconds if it has not already terminated by that point.\nThis is particularly useful for benchmarking scenarios where you wish to ignore runs of PRISM that exceed a certain length of time.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/SolutionMethodsAndOptions.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Solution Methods And Options \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SolutionMethodsAndOptions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='SolutionMethodsAndOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Solution Methods And Options</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Separately from the choice of <a class='wikilink' href='ComputationEngines.html'>engines</a>,\nPRISM often offers several different solution methods\nthat can be used for the computation of probabilities and expected costs/rewards during model checking.\nMany, but not all, of these are iterative numerical methods.\nThe choice of method (and their settings) depends on the type of analysis that is being done (i.e., what type of model and property).\n</p>\n<div class='vspace'></div><h3>Linear Equation Systems</h3>\n<p>For many properties of Markov chains\n(e.g. \"reachability\"/\"until\" properties for DTMCs and CTMCs, steady-state properties for CTMCs and \"reachability reward\" properties for DTMCs),\nPRISM solves a set of linear equation systems, for which several numerical methods are available.\nBelow is a list of the alternatives and the switches used to select them from the command-line.\nThe corresponding GUI option is \"Linear equations method\".\n</p>\n<div class='vspace'></div><ul><li>Power method: <code>-power</code> (or <code>-pow</code>, <code>-pwr</code>)\n</li><li>Jacobi method: <code>-jacobi</code> (or <code>-jac</code>)\n</li><li>Gauss-Seidel method: <code>-gaussseidel</code> (or <code>-gs</code>)\n</li><li>Backwards Gauss-Seidel method: <code>-bgaussseidel</code> (or <code>-bgs</code>)\n</li><li>JOR method (Jacobi with over-relaxation): <code>-jor</code>\n</li><li>SOR method: <code>-sor</code>\n</li><li>Backwards SOR method: <code>-bsor</code>\n</li></ul><p class='vspace'>When using the MTBDD engine, Gauss-Seidel/SOR based methods are not available.\nWhen using the hybrid engine, <em>pseudo</em> variants of Gauss-Seidel/SOR based method can also be used [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>]\n(type <code>prism -help</code> at the command-line for details of the corresponding switches).\nFor methods which use over-relaxation (JOR/SOR), the over-relaxation parameter (between 0.0 and 2.0)\ncan also be specified with option \"Over-relaxation parameter\" (switch <code>-omega &lt;val&gt;</code>).\n</p>\n<p class='vspace'>For options relating to convergence (of this and other iterative methods),\nsee the <a class='wikilink' href='SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='mdp' id='mdp'></a>\n</p><h3>MDP Solution Methods</h3>\n<p>When analysing MDPs, there are multiple solution methods on offer.\nFor most of these, you can select them under the \"MDP solution method\" setting from the GUI,\nor use the command-line switches listed below.\nCurrently, all except value iteration are only supported by the <a class='wikilink' href='ComputationEngines.html'>explicit engine</a>.\nFor more details of the methods, see e.g. [<a class='wikilink' href='../Main/References.html#FKNP11'>FKNP11</a>] (about probabilistic verification of MDPs)\nor classic MDP texts such as [<a class='wikilink' href='../Main/References.html#Put94'>Put94</a>]).\n</p>\n<div class='vspace'></div><ul><li><strong>Value iteration</strong> (switch <code>-valiter</code>) [this is the default]\n</li><li><strong>Gauss Seidel</strong> (switch <code>-gs</code>)\n</li><li><strong>Policy iteration</strong> (switch <code>-politer</code>)\n</li><li><strong>Modified policy iteration</strong> (switch <code>-modpoliter</code>)\n</li></ul><p class='vspace'>Where the methods above use iterative numerical solution,\nyou can also use the settings under described in the <a class='wikilink' href='SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='iiter' id='iiter'></a>\n</p><h3>Interval Iteration</h3>\n<p>Interval iteration [<a class='wikilink' href='../Main/References.html#HM14'>HM14</a>],[<a class='wikilink' href='../Main/References.html#BKLPW17'>BKLPW17</a>] is an alternative solution method for either MDPs or DTMCs\nwhich performs two separate instances of numerical iterative solution,\none from below and one from above. This is designed to provide clearer information\nabout the accuracy of the computed values and avoid possible problems with premature convergence.\nThis can be enabled using the switch <code>-intervaliter</code> (or <code>-ii</code>)\nor via the \"Use interval iteration\" GUI option.\nA variety of options can be configured, either using\n<code>-intervaliter:option1,option2,...</code> or by\nsetting the string \"<code>option1,option2,...</code>\" under \"Interval iteration options\" in the GUI.\nType <code>prism -help intervaliter</code> from the command-line for a list of the options\nand see [<a class='wikilink' href='../Main/References.html#BKLPW17'>BKLPW17</a>] for the details.\n</p>\n<p class='vspace'><a name='topo' id='topo'></a>\n</p><h3>Topological Value Iteration</h3>\n<p>Topological value iteration is a variant of value iteration which improves efficiency\nby analysing the graph structure of the model and using this to update the values for\nstates in an alternative order which increases the speed of convergence.\nUse switch <code>-topological</code> or GUI option \"Use topological value iteration\" to enable this.\nIn addition to standard value iteration for MDPs, the topological variant can be used to optimise\nboth interval iteration (see above) and the numerical solution of DTMCs.\n</p>\n<p class='vspace'><a name='transient' id='transient'></a>\n</p><h3>CTMC Transient Analysis</h3>\n<p>When computing transient probabilities of a CTMC\n(either <a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>directly</a> or when verifying <a class='wikilink' href='../PropertySpecification/ThePOperator.html#bounded'>time-bounded operators</a> of CSL), there are two options:\n<em>uniformisation</em> and <em>fast adaptive uniformisation</em> (FAU). These can be selected using the GUI option \"Transient probability computation method\", or using the command-line switch <code>-transientmethod &lt;name&gt;</code>, where <code>&lt;name&gt;</code> is either <code>unif</code> or <code>fau</code>.\n</p>\n<p class='vspace'><strong>Uniformisation</strong> is a standard iterative numerical method for computing transient probabilities on a CTMC, which works by reducing the problem to an analysis of a \"uniformised\" DTMC.\nAs an optimisation, when it is detected that the transient probabilities have converged, no further iterations are performed. If necessary (e.g. in case of round-off problems), this optimisation can be disabled with the \"Use steady-state detection\" option (command-line switch <code>-nossdetect</code>).\n</p>\n<p class='vspace'><a name='fau' id='fau'></a>\n<strong>Fast adaptive uniformisation</strong> (FAU) [<a class='wikilink' href='../Main/References.html#MWDH10'>MWDH10</a>] is a method to efficiently approximate transient properties of large CTMCs. The basic idea is that only the parts of the model that are relevant for the current time period are kept in memory. In more detail, starting with the initial states, in each step FAU\nexplores further states in a DTMC which is a discrete-time version of the original CTMC. By combining the\nprobabilities there with those of a certain continuous-time stochastic process (a birth process), transient properties in the original CTMC can be computed. If it turns out that the probability of being in some state in the DTMC is below a given threshold, this state is removed from the model explored so far. After a given number of steps, which corresponds to the number of steps which are likely to happen within the time bound, the exploration can be stopped. In the implementation in PRISM [<a class='wikilink' href='../Main/References.html#DHK13'>DHK13</a>], FAU can be used to compute transient probability distributions and to model check the following types of non-nested CSL formulas: time-bounded until, instantaneous reward, cumulative reward.\n</p>\n<p class='vspace'>The following options can be used to configure FAU:\n</p>\n<div class='vspace'></div><ul><li>\"FAU epsilon\" (switch <code>-fauepsilon &lt;x&gt;</code>): FAU analyses the DTMC for a number of iterations such that the probability of more steps being relevant is below this value. The default is 1e-6.\n<div class='vspace'></div></li><li>\"FAU cut off delta\" (switch <code>-faudelta &lt;x&gt;</code>): States that have a lower probability than this value are discarded. The default is 1e-12.\n<div class='vspace'></div></li><li>\"FAU array threshold\" (switch <code>-fauarraythreshold &lt;x&gt;</code>): After this number of steps without any new states being explored or discarded, FAU will switch to a faster, fixed-size data structure until further states have to be explored or discarded. The default is 100.\n<div class='vspace'></div></li><li>\"FAU time intervals\" (switch <code>-fauintervals &lt;x&gt;</code>): In some cases, it is advantageous to divide the time interval the analysis is done for into several smaller intervals. This option dictates the number of (equal length) intervals used for this split. The default is 1, meaning that only one time interval is used.\n<div class='vspace'></div></li><li>\"FAU initial time interval\" (switch <code>-fauinitival &lt;x&gt;</code>): It is also possible to specify an additional initial time interval which is handled separately from the rest of the time. This is often advantageous, because in this interval certain parameters of the model can be explored, which can subsequently be used to speed up the computation of the remaining time interval. The default for this option is 1.0.\n</li></ul><p class='vspace'><a name='convergence' id='convergence'></a>\n</p><h3>Convergence</h3>\n<p>Common to all of these methods is the way that PRISM checks convergence, i.e. decides when to terminate the iterative methods because the answers have converged sufficiently. This is done by checking when the maximum difference between elements in the solution vectors from successive iterations drops below a given threshold (or, in the case of interval iteration, if the difference of the elements in the iterations from above and below are below the threshold).\nThe default value for this threshold is 10<sup>-6</sup> but it can be altered with the \"Termination epsilon\" option (switch <code>-epsilon &lt;val&gt;</code>). The way that the maximum difference is computed can also be varied:\neither \"relative\" or \"absolute\" (the default is \"relative\"). This can be changed using the \"Termination criteria\" option (command-line switches <code>-relative</code> and <code>-absolute</code>, or <code>-rel</code> and <code>-abs</code> for short).\n</p>\n<p class='vspace'>Also, the maximum number of iterations performed is given an upper limit\nin order to trap the cases when computation will not converge.\nThe default limit is 10,000 but can be changed with the \"Termination max. iterations\" option (switch <code>-maxiters &lt;val&gt;</code>). Computations that reach this upper limit will trigger an error during model checking to alert the user to this fact.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SolutionMethodsAndOptions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='SolutionMethodsAndOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 26, 2017, at 09:24 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='selflink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/SolutionMethodsAndOptions@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Solution Methods And Options | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SolutionMethodsAndOptions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='SolutionMethodsAndOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Solution Methods And Options</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='SolutionMethodsAndOptions@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SolutionMethodsAndOptions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='SolutionMethodsAndOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 26, 2017, at 09:24 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='selflink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/SolutionMethodsAndOptions@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Configuring PRISM / Solution Methods And Options | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SolutionMethodsAndOptions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='SolutionMethodsAndOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Solution Methods And Options</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='SolutionMethodsAndOptions@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SolutionMethodsAndOptions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=edit.html'>Edit</a> - <a class='wikilink' href='SolutionMethodsAndOptions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SolutionMethodsAndOptions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 26, 2017, at 09:24 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Configuring PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='selflink' href='SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='OtherOptions.html'>Other Options</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ConfiguringPRISM/SolutionMethodsAndOptions@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ConfiguringPRISM / SolutionMethodsAndOptions </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Configuring PRISM</a> /\n</p><h1>Solution Methods And Options</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Separately from the choice of <a class='wikilink' href='ComputationEngines.html'>engines</a>,\nPRISM often offers several different solution methods\nthat can be used for the computation of probabilities and expected costs/rewards during model checking.\nMany, but not all, of these are iterative numerical methods.\nThe choice of method (and their settings) depends on the type of analysis that is being done (i.e., what type of model and property).\n</p>\n<div class='vspace'></div><h3>Linear Equation Systems</h3>\n<p>For many properties of Markov chains\n(e.g. \"reachability\"/\"until\" properties for DTMCs and CTMCs, steady-state properties for CTMCs and \"reachability reward\" properties for DTMCs),\nPRISM solves a set of linear equation systems, for which several numerical methods are available.\nBelow is a list of the alternatives and the switches used to select them from the command-line.\nThe corresponding GUI option is \"Linear equations method\".\n</p>\n<div class='vspace'></div><ul><li>Power method: <code>-power</code> (or <code>-pow</code>, <code>-pwr</code>)\n</li><li>Jacobi method: <code>-jacobi</code> (or <code>-jac</code>)\n</li><li>Gauss-Seidel method: <code>-gaussseidel</code> (or <code>-gs</code>)\n</li><li>Backwards Gauss-Seidel method: <code>-bgaussseidel</code> (or <code>-bgs</code>)\n</li><li>JOR method (Jacobi with over-relaxation): <code>-jor</code>\n</li><li>SOR method: <code>-sor</code>\n</li><li>Backwards SOR method: <code>-bsor</code>\n</li></ul><p class='vspace'>When using the MTBDD engine, Gauss-Seidel/SOR based methods are not available.\nWhen using the hybrid engine, <em>pseudo</em> variants of Gauss-Seidel/SOR based method can also be used [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>]\n(type <code>prism -help</code> at the command-line for details of the corresponding switches).\nFor methods which use over-relaxation (JOR/SOR), the over-relaxation parameter (between 0.0 and 2.0)\ncan also be specified with option \"Over-relaxation parameter\" (switch <code>-omega &lt;val&gt;</code>).\n</p>\n<p class='vspace'>For options relating to convergence (of this and other iterative methods),\nsee the <a class='wikilink' href='SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='mdp' id='mdp'></a>\n</p><h3>MDP Solution Methods</h3>\n<p>When analysing MDPs, there are multiple solution methods on offer.\nFor most of these, you can select them under the \"MDP solution method\" setting from the GUI,\nor use the command-line switches listed below.\nCurrently, all except value iteration are only supported by the <a class='wikilink' href='ComputationEngines.html'>explicit engine</a>.\nFor more details of the methods, see e.g. [<a class='wikilink' href='../Main/References.html#FKNP11'>FKNP11</a>] (about probabilistic verification of MDPs)\nor classic MDP texts such as [<a class='wikilink' href='../Main/References.html#Put94'>Put94</a>]).\n</p>\n<div class='vspace'></div><ul><li><strong>Value iteration</strong> (switch <code>-valiter</code>) [this is the default]\n</li><li><strong>Gauss Seidel</strong> (switch <code>-gs</code>)\n</li><li><strong>Policy iteration</strong> (switch <code>-politer</code>)\n</li><li><strong>Modified policy iteration</strong> (switch <code>-modpoliter</code>)\n</li></ul><p class='vspace'>Where the methods above use iterative numerical solution,\nyou can also use the settings under described in the <a class='wikilink' href='SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='iiter' id='iiter'></a>\n</p><h3>Interval Iteration</h3>\n<p>Interval iteration [<a class='wikilink' href='../Main/References.html#HM14'>HM14</a>],[<a class='wikilink' href='../Main/References.html#BKLPW17'>BKLPW17</a>] is an alternative solution method for either MDPs or DTMCs\nwhich performs two separate instances of numerical iterative solution,\none from below and one from above. This is designed to provide clearer information\nabout the accuracy of the computed values and avoid possible problems with premature convergence.\nThis can be enabled using the switch <code>-intervaliter</code> (or <code>-ii</code>)\nor via the \"Use interval iteration\" GUI option.\nA variety of options can be configured, either using\n<code>-intervaliter:option1,option2,...</code> or by\nsetting the string \"<code>option1,option2,...</code>\" under \"Interval iteration options\" in the GUI.\nType <code>prism -help intervaliter</code> from the command-line for a list of the options\nand see [<a class='wikilink' href='../Main/References.html#BKLPW17'>BKLPW17</a>] for the details.\n</p>\n<p class='vspace'><a name='topo' id='topo'></a>\n</p><h3>Topological Value Iteration</h3>\n<p>Topological value iteration is a variant of value iteration which improves efficiency\nby analysing the graph structure of the model and using this to update the values for\nstates in an alternative order which increases the speed of convergence.\nUse switch <code>-topological</code> or GUI option \"Use topological value iteration\" to enable this.\nIn addition to standard value iteration for MDPs, the topological variant can be used to optimise\nboth interval iteration (see above) and the numerical solution of DTMCs.\n</p>\n<p class='vspace'><a name='transient' id='transient'></a>\n</p><h3>CTMC Transient Analysis</h3>\n<p>When computing transient probabilities of a CTMC\n(either <a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>directly</a> or when verifying <a class='wikilink' href='../PropertySpecification/ThePOperator.html#bounded'>time-bounded operators</a> of CSL), there are two options:\n<em>uniformisation</em> and <em>fast adaptive uniformisation</em> (FAU). These can be selected using the GUI option \"Transient probability computation method\", or using the command-line switch <code>-transientmethod &lt;name&gt;</code>, where <code>&lt;name&gt;</code> is either <code>unif</code> or <code>fau</code>.\n</p>\n<p class='vspace'><strong>Uniformisation</strong> is a standard iterative numerical method for computing transient probabilities on a CTMC, which works by reducing the problem to an analysis of a \"uniformised\" DTMC.\nAs an optimisation, when it is detected that the transient probabilities have converged, no further iterations are performed. If necessary (e.g. in case of round-off problems), this optimisation can be disabled with the \"Use steady-state detection\" option (command-line switch <code>-nossdetect</code>).\n</p>\n<p class='vspace'><a name='fau' id='fau'></a>\n<strong>Fast adaptive uniformisation</strong> (FAU) [<a class='wikilink' href='../Main/References.html#MWDH10'>MWDH10</a>] is a method to efficiently approximate transient properties of large CTMCs. The basic idea is that only the parts of the model that are relevant for the current time period are kept in memory. In more detail, starting with the initial states, in each step FAU\nexplores further states in a DTMC which is a discrete-time version of the original CTMC. By combining the\nprobabilities there with those of a certain continuous-time stochastic process (a birth process), transient properties in the original CTMC can be computed. If it turns out that the probability of being in some state in the DTMC is below a given threshold, this state is removed from the model explored so far. After a given number of steps, which corresponds to the number of steps which are likely to happen within the time bound, the exploration can be stopped. In the implementation in PRISM [<a class='wikilink' href='../Main/References.html#DHK13'>DHK13</a>], FAU can be used to compute transient probability distributions and to model check the following types of non-nested CSL formulas: time-bounded until, instantaneous reward, cumulative reward.\n</p>\n<p class='vspace'>The following options can be used to configure FAU:\n</p>\n<div class='vspace'></div><ul><li>\"FAU epsilon\" (switch <code>-fauepsilon &lt;x&gt;</code>): FAU analyses the DTMC for a number of iterations such that the probability of more steps being relevant is below this value. The default is 1e-6.\n<div class='vspace'></div></li><li>\"FAU cut off delta\" (switch <code>-faudelta &lt;x&gt;</code>): States that have a lower probability than this value are discarded. The default is 1e-12.\n<div class='vspace'></div></li><li>\"FAU array threshold\" (switch <code>-fauarraythreshold &lt;x&gt;</code>): After this number of steps without any new states being explored or discarded, FAU will switch to a faster, fixed-size data structure until further states have to be explored or discarded. The default is 100.\n<div class='vspace'></div></li><li>\"FAU time intervals\" (switch <code>-fauintervals &lt;x&gt;</code>): In some cases, it is advantageous to divide the time interval the analysis is done for into several smaller intervals. This option dictates the number of (equal length) intervals used for this split. The default is 1, meaning that only one time interval is used.\n<div class='vspace'></div></li><li>\"FAU initial time interval\" (switch <code>-fauinitival &lt;x&gt;</code>): It is also possible to specify an additional initial time interval which is handled separately from the rest of the time. This is often advantageous, because in this interval certain parameters of the model can be explored, which can subsequently be used to speed up the computation of the remaining time interval. The default for this option is 1.0.\n</li></ul><p class='vspace'><a name='convergence' id='convergence'></a>\n</p><h3>Convergence</h3>\n<p>Common to all of these methods is the way that PRISM checks convergence, i.e. decides when to terminate the iterative methods because the answers have converged sufficiently. This is done by checking when the maximum difference between elements in the solution vectors from successive iterations drops below a given threshold (or, in the case of interval iteration, if the difference of the elements in the iterations from above and below are below the threshold).\nThe default value for this threshold is 10<sup>-6</sup> but it can be altered with the \"Termination epsilon\" option (switch <code>-epsilon &lt;val&gt;</code>). The way that the maximum difference is computed can also be varied:\neither \"relative\" or \"absolute\" (the default is \"relative\"). This can be changed using the \"Termination criteria\" option (command-line switches <code>-relative</code> and <code>-absolute</code>, or <code>-rel</code> and <code>-abs</code> for short).\n</p>\n<p class='vspace'>Also, the maximum number of iterations performed is given an upper limit\nin order to trap the cases when computation will not converge.\nThe default limit is 10,000 but can be changed with the \"Termination max. iterations\" option (switch <code>-maxiters &lt;val&gt;</code>). Computations that reach this upper limit will trigger an error during model checking to alert the user to this fact.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/AllOnOnePage.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / All On One Page \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Frequently Asked Questions</span></h1>\n<hr />\n<h1>Memory Problems</h1>\n<p><a name='crash' id='crash'></a>\n</p><h3>PRISM crashed or stopped responding. Why?</h3>\n<div class='answer' > \n<p>When PRISM crashes, the most likely cause is that it has run out of memory.\nSimilarly, if PRISM (or the machine you are running it on) becomes very slow or seems to have stopped responding, this is probably because it is using too much of your machine's memory. Probabilistic model checking, much like other formal verification techniques, can be a very resource-intensive process. It is very easy to create a seemingly simple PRISM model that requires a large amount of time and/or memory to construct and analyse. See some of the other questions in this section for tips on how to avoid this.\n</p>\n<p class='vspace'>The other possibility is that you have found a bug.\nIf PRISM crashes or freezes whilst not using all/most of the available memory (you can check this with the <code>top</code> command in a Unix/Linux terminal or the Task Manager (via Ctrl-Alt-Delete) on Windows) then please file a <a class='urllink' href='https://github.com/prismmodelchecker/prism/issues'>bug report</a>.\n</p></div>\n<p class='vspace'><a name='memout' id='memout'></a>\n</p><h3>I ran out of memory. What can I do?</h3>\n<div class='answer' > \n<p>It depends. First, you need to establish at what point in PRISM's operation, you ran out of memory. If you are running the command-line version of PRISM then the output from the tool so far should give an indication of this. If using the GUI, check the log tab for this information. If PRISM crashed because of its memory usage, the error message can be helpful. If using the GUI, you may need to start the GUI from the command-line to see any error messages.\n</p>\n<p class='vspace'>The two main steps that PRISM typically has to perform are:\n</p>\n<div class='vspace'></div><ol><li><strong>Model construction</strong> (conversion of a PRISM language description to the corresponding probabilistic model)\n</li><li><strong>Model checking/analysis</strong> (processing/analysis of a constructed probabilistic model in order to determine the result of a property or to compute steady-state/transient probabilities)\n</li></ol><p class='vspace'>Memory usage issues for each of these steps are discussed in separate sections below. In some cases the process performed prior to step 1 (<strong>model parsing</strong> - reading in a model description in the PRISM language and checking it for correctness) can also be resource intensive. This is also discussed below.\n</p>\n<p class='vspace'>If you are using the <strong>simulator</strong> to generate approximate model checking results then step 1 (model construction) is not performed and step 2 is carried out very differently. Memory consumption is not usually a problem in this case.\n</p></div>\n<p class='vspace'><a name='memout_constr' id='memout_constr'></a>\n</p><h3>I ran out of memory during model construction. What can I do?</h3>\n<div class='answer' > \n<p>If PRISM has already output this:\n</p>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Building model...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>but there is no line of the form:\n</p>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Time for model construction: 34.3 seconds.</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>and then you get an error like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by Java Runtime Environment:</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">#  SIGSEGV (0xb) at pc=0xb5249323, pid=19298, tid=3086363536</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.6.0-b105 mixed mode, sharing)</span><br/>\n<span style=\"font-style:italic;\"># Problematic frame:</span><br/>\n<span style=\"font-style:italic;\"># C  [libdd.so+0x39323]  Cudd_Ref+0xf</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An error report file with more information is saved as hs_err_pid19298.log</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># If you would like to submit a bug report, please visit:</span><br/>\n<span style=\"font-style:italic;\">#   http://java.sun.com/webapps/bugreport/crash.jsp</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50: 19298 Aborted                 \"$PRISM_JAVA\" #$PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by HotSpot Virtual Machine: </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0b1c7da3, pid=2884, tid=2544 </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.5.0_06-b05 mixed mode) </span><br/>\n<span style=\"font-style:italic;\"># Problematic frame: </span><br/>\n<span style=\"font-style:italic;\"># C [dd.dll+0x7da3] </span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then PRISM ran out of memory whilst trying to construct the model.\nModel construction in PRISM is performed using BDDs (binary decision diagrams) and MTBDDs (multi-terminal) BDDs which are implemented in the CUDD library.\nThe first thing to try in this case is to increase the amount of memory available to CUDD. See the entry \"CUDD memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p>\n<p class='vspace'>If increasing this memory limit does not resolve the problem, then you will need to consider ways to reduce the size of your model. You can find some tips on this in the <a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a> section. Bear in mind also that if you are having to increase the CUDD memory limit too high (e.g. close to the physical memory available on your computer) just for model construction, then it is unlikely that you will have enough memory for subsequent model checking operations.\n</p>\n<p class='vspace'>Finally, it is also worth considering the ordering of the modules and variables in your model since this can have a (in some cases dramatic) effect on the size of MTBDD representation of the model. This topic is covered in the \"<a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n</p></div>\n<p class='vspace'><a name='memout_check' id='memout_check'></a>\n</p><h3>I ran out of memory during model checking. What can I do?</h3>\n<div class='answer' > \n<p>If model construction was successfully completed (see previous question) but model checking was not, there are several things you can try. First of all, if the error message you see looks like the one in the previous question or you see a message such as\n</p>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">DD_MatrixMultiply: res is NULL</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then it may be worth increasing the memory limit for CUDD (as described above). However, if you see an error more like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50:  3139 Aborted                 \"$PRISM_JAVA\" $PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then increasing the memory CUDD probably will not help - PRISM is just trying to allocate more memory than is physically available on your system.\n</p>\n<p class='vspace'>Here are some general tips:\n</p>\n<div class='vspace'></div><ul><li>Try experimenting with using the different <em>engines</em> in PRISM. Read the section \"<a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Configuring PRISM - Computation Engines</a>\" for details.\n<div class='vspace'></div></li><li>Look at the detailed output of PRISM for information about memory usage. If you are using the hybrid (or sparse) engine and the limiting factor in terms of memory is creation of the vectors, then you have no choice but to try and reduce the size (number of states) of your model. If you are using the MTBDD engine, it is also well worth considering the variable ordering of your model. Both topics are discussed in the \"<a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n<div class='vspace'></div></li><li>Finally, if you can find no way to reduce the size of your model and are happy to consider an approximate (rather than exact) analysis, you may wish to try using PRISM's <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>discrete-event simulation engine</a> for analysis.\n</li></ul></div>\n<p class='vspace'><a name='memout_parse' id='memout_parse'></a>\n</p><h3>I ran out of memory during model parsing. What can I do?</h3>\n<div class='answer' > \n<p>This is a less common problem and will only occur if the actual PRISM language description of your model is very large. This may be the case, for example, if you are automatically generating PRISM models in some way. Errors due to lack of memory during parsing usually look like:\n</p>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.OutOfMemoryError: Java heap space </span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or:\n</p>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.StackOverflowError</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>You can resolve this problem by increasing the memory allocated to Java.\nSee the entry \"Java memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p></div>\n<hr />\n<h1>PRISM Modelling</h1>\n<p><a name='max_model_size' id='max_model_size'></a>\n</p><h3>What size models can PRISM handle?</h3>\n<div class='answer' > \n<p>There is no definitive answer to this. Because of PRISM's symbolic implementation, using data structures based on binary decision diagrams (BDDs), its performance can be unpredictable in this respect. There are also several factors that affect performance, including the type of model and property being checked and the engine being used (PRISM has several different engines, which have varying performance).\n</p>\n<p class='vspace'>Having said that, using the default engine in PRISM (the hybrid engine), you can normally expect to be able to handle models with up to 10^7-10^8 states on a typical PC. Using the MTBDD engine, you may be able to analyse much larger models (on some of the PRISM case studies, for example, PRISM can do numerical analysis of models with as many as 10^10 or 10^11 states). The manual has more information about PRISM's <a class='urllink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a>.\n</p></div>\n<p class='vspace'><a name='model_size' id='model_size'></a>\n</p><h3>How can I reduce the size of my model?</h3>\n<div class='answer' > \n<p>The size of a probabilistic model (i.e. the number of states/transitions) is critical to the efficiency of performing probabilistic model checking on it, since both the time and memory required to do so are often proportional to the model size. Unfortunately, it is very easy to create models that are extremely large. Below are a few general tips for reducing model size.\n</p>\n<div class='vspace'></div><ul><li>Look for variables that have unnecessarily large ranges and try to reduce them. Even if your model needs large variables, it is generally a good strategy to first get a smaller version building successfully and then scale it up afterwards.\n<div class='vspace'></div></li><li>Similarly, can you (if only temporarily) reduce the number of modules/components of your model? Start with the smallest number of components possible and then add others one by one.\n<div class='vspace'></div></li><li>Do you have any inter-dependencies between variables? For example, perhaps you have some variables which are simply functions of other variables of the model. Even if these are convenient for model checking, they can be replaced with <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>formulas or labels</a>, which do not contribute to the state space.\n<div class='vspace'></div></li><li>Do any variables include more detail than is necessary for the model? Perhaps this can be exploited in order to reduce the number of variables in your model.\n<div class='vspace'></div></li><li>More generally, are any aspects of the model not relevant to the properties that you are interested in? If so, start with a simpler, more abstract version of the model and then add more details if possible.\n</li></ul></div>\n<p class='vspace'><a name='ordering' id='ordering'></a>\n</p><h3>How can I choose a good variable ordering?</h3>\n<div class='answer' > \n<p>Because PRISM is a symbolic model checker, the amount of memory required to store the probabilistic model can vary (sometime unpredictably) according to several factors. One example is the order in which the variables of your model appear in the model file. In general, there is no definitive answer to what the best ordering is but the following heuristics are a good guide.\n</p>\n<div class='vspace'></div><ul><li>Variables which are closely related should appear close together\n<div class='vspace'></div></li><li>Variables which are related to most or all other variables should appear near the start of the ordering\n</li></ul><p class='vspace'>Variables <code>x</code> and <code>y</code> are \"related\" if, for example, the value of one is has an effect on how the other changes (e.g. <code>(y'=x+1)</code>) or if both appear together in an expression (e.g. a guard).\n</p>\n<p class='vspace'>These heuristics also apply to the ordering of <em>modules</em> within the model file.\n</p>\n<p class='vspace'>For technical details about variable ordering issues, see e.g. section 8 of [<a class='wikilink' href='../Main/References.html#HKN+03'>HKN+03</a>] or section 4.1.2 of [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>].\n</p></div>\n<p class='vspace'><a name='det_delay' id='det_delay'></a>\n</p><h3>How can I add deterministic time delays to a CTMC model?</h3>\n<div class='answer' > \n<p>All delays in a CTMC need to be modelled as <em>exponential</em> distributions. This is what makes them efficient to analyse. If you included a transition whose delay was <em>deterministic</em>, i.e. which always occurred after exactly the same delay,  the model would no longer be a CTMC.\n</p>\n<p class='vspace'>One solution to this, if your model require such a delay, is to approximate a deterministic delay with an <a class='urllink' href='http://en.wikipedia.org/wiki/Erlang_distribution'>Erlang distribution</a> (a special case of a phase-type distribution). See for example this PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mean</span> = <span class=\"prismnum\">10</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">trigger</span><br/>\n<br/>\n\t<span class=\"prismident\">i</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[]&nbsp;&nbsp;&nbsp;<span class=\"prismident\">i</span> &lt; <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">i</span> = <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">main</span><br/>\n<br/>\n\t<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the model, the occurrence of the the go-labelled action occurs with an Erlang distribution with mean <code>mean</code> and shape <code>k</code>. The special case of <code>k</code>=1 is just an exponential distribution. The graph below shows the probability distribution of the delay, i.e. of <code>P=? [ F&lt;=T x=1 ]</code> for different values of <code>k</code>.\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/faq-erlang.jpg' alt='' /></div>\n<p class='vspace'>There is an obvious trade-off here between the accuracy (how close it is to modelling a deterministic time delay) and the resulting blow-up in the size of the model that you add this to. For <code>k</code>=1000, you can see that the shape is quite \"deterministic\" but this would increase your model size by a factor of ~1000.\n</p></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 02:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/AllOnOnePage@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / All On One Page | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 02:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/AllOnOnePage@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / All On One Page | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 02:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/AllOnOnePage@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | FrequentlyAskedQuestions / AllOnOnePage </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Frequently Asked Questions</span></h1>\n<hr />\n<h1>Memory Problems</h1>\n<p><a name='crash' id='crash'></a>\n</p><h3>PRISM crashed or stopped responding. Why?</h3>\n<div class='answer' > \n<p>When PRISM crashes, the most likely cause is that it has run out of memory.\nSimilarly, if PRISM (or the machine you are running it on) becomes very slow or seems to have stopped responding, this is probably because it is using too much of your machine's memory. Probabilistic model checking, much like other formal verification techniques, can be a very resource-intensive process. It is very easy to create a seemingly simple PRISM model that requires a large amount of time and/or memory to construct and analyse. See some of the other questions in this section for tips on how to avoid this.\n</p>\n<p class='vspace'>The other possibility is that you have found a bug.\nIf PRISM crashes or freezes whilst not using all/most of the available memory (you can check this with the <code>top</code> command in a Unix/Linux terminal or the Task Manager (via Ctrl-Alt-Delete) on Windows) then please file a <a class='urllink' href='https://github.com/prismmodelchecker/prism/issues'>bug report</a>.\n</p></div>\n<p class='vspace'><a name='memout' id='memout'></a>\n</p><h3>I ran out of memory. What can I do?</h3>\n<div class='answer' > \n<p>It depends. First, you need to establish at what point in PRISM's operation, you ran out of memory. If you are running the command-line version of PRISM then the output from the tool so far should give an indication of this. If using the GUI, check the log tab for this information. If PRISM crashed because of its memory usage, the error message can be helpful. If using the GUI, you may need to start the GUI from the command-line to see any error messages.\n</p>\n<p class='vspace'>The two main steps that PRISM typically has to perform are:\n</p>\n<div class='vspace'></div><ol><li><strong>Model construction</strong> (conversion of a PRISM language description to the corresponding probabilistic model)\n</li><li><strong>Model checking/analysis</strong> (processing/analysis of a constructed probabilistic model in order to determine the result of a property or to compute steady-state/transient probabilities)\n</li></ol><p class='vspace'>Memory usage issues for each of these steps are discussed in separate sections below. In some cases the process performed prior to step 1 (<strong>model parsing</strong> - reading in a model description in the PRISM language and checking it for correctness) can also be resource intensive. This is also discussed below.\n</p>\n<p class='vspace'>If you are using the <strong>simulator</strong> to generate approximate model checking results then step 1 (model construction) is not performed and step 2 is carried out very differently. Memory consumption is not usually a problem in this case.\n</p></div>\n<p class='vspace'><a name='memout_constr' id='memout_constr'></a>\n</p><h3>I ran out of memory during model construction. What can I do?</h3>\n<div class='answer' > \n<p>If PRISM has already output this:\n</p>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Building model...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>but there is no line of the form:\n</p>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Time for model construction: 34.3 seconds.</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>and then you get an error like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by Java Runtime Environment:</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">#  SIGSEGV (0xb) at pc=0xb5249323, pid=19298, tid=3086363536</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.6.0-b105 mixed mode, sharing)</span><br/>\n<span style=\"font-style:italic;\"># Problematic frame:</span><br/>\n<span style=\"font-style:italic;\"># C  [libdd.so+0x39323]  Cudd_Ref+0xf</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An error report file with more information is saved as hs_err_pid19298.log</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># If you would like to submit a bug report, please visit:</span><br/>\n<span style=\"font-style:italic;\">#   http://java.sun.com/webapps/bugreport/crash.jsp</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50: 19298 Aborted                 \"$PRISM_JAVA\" #$PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by HotSpot Virtual Machine: </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0b1c7da3, pid=2884, tid=2544 </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.5.0_06-b05 mixed mode) </span><br/>\n<span style=\"font-style:italic;\"># Problematic frame: </span><br/>\n<span style=\"font-style:italic;\"># C [dd.dll+0x7da3] </span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then PRISM ran out of memory whilst trying to construct the model.\nModel construction in PRISM is performed using BDDs (binary decision diagrams) and MTBDDs (multi-terminal) BDDs which are implemented in the CUDD library.\nThe first thing to try in this case is to increase the amount of memory available to CUDD. See the entry \"CUDD memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p>\n<p class='vspace'>If increasing this memory limit does not resolve the problem, then you will need to consider ways to reduce the size of your model. You can find some tips on this in the <a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a> section. Bear in mind also that if you are having to increase the CUDD memory limit too high (e.g. close to the physical memory available on your computer) just for model construction, then it is unlikely that you will have enough memory for subsequent model checking operations.\n</p>\n<p class='vspace'>Finally, it is also worth considering the ordering of the modules and variables in your model since this can have a (in some cases dramatic) effect on the size of MTBDD representation of the model. This topic is covered in the \"<a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n</p></div>\n<p class='vspace'><a name='memout_check' id='memout_check'></a>\n</p><h3>I ran out of memory during model checking. What can I do?</h3>\n<div class='answer' > \n<p>If model construction was successfully completed (see previous question) but model checking was not, there are several things you can try. First of all, if the error message you see looks like the one in the previous question or you see a message such as\n</p>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">DD_MatrixMultiply: res is NULL</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then it may be worth increasing the memory limit for CUDD (as described above). However, if you see an error more like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50:  3139 Aborted                 \"$PRISM_JAVA\" $PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then increasing the memory CUDD probably will not help - PRISM is just trying to allocate more memory than is physically available on your system.\n</p>\n<p class='vspace'>Here are some general tips:\n</p>\n<div class='vspace'></div><ul><li>Try experimenting with using the different <em>engines</em> in PRISM. Read the section \"<a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Configuring PRISM - Computation Engines</a>\" for details.\n<div class='vspace'></div></li><li>Look at the detailed output of PRISM for information about memory usage. If you are using the hybrid (or sparse) engine and the limiting factor in terms of memory is creation of the vectors, then you have no choice but to try and reduce the size (number of states) of your model. If you are using the MTBDD engine, it is also well worth considering the variable ordering of your model. Both topics are discussed in the \"<a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n<div class='vspace'></div></li><li>Finally, if you can find no way to reduce the size of your model and are happy to consider an approximate (rather than exact) analysis, you may wish to try using PRISM's <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>discrete-event simulation engine</a> for analysis.\n</li></ul></div>\n<p class='vspace'><a name='memout_parse' id='memout_parse'></a>\n</p><h3>I ran out of memory during model parsing. What can I do?</h3>\n<div class='answer' > \n<p>This is a less common problem and will only occur if the actual PRISM language description of your model is very large. This may be the case, for example, if you are automatically generating PRISM models in some way. Errors due to lack of memory during parsing usually look like:\n</p>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.OutOfMemoryError: Java heap space </span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or:\n</p>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.StackOverflowError</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>You can resolve this problem by increasing the memory allocated to Java.\nSee the entry \"Java memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p></div>\n<hr />\n<h1>PRISM Modelling</h1>\n<p><a name='max_model_size' id='max_model_size'></a>\n</p><h3>What size models can PRISM handle?</h3>\n<div class='answer' > \n<p>There is no definitive answer to this. Because of PRISM's symbolic implementation, using data structures based on binary decision diagrams (BDDs), its performance can be unpredictable in this respect. There are also several factors that affect performance, including the type of model and property being checked and the engine being used (PRISM has several different engines, which have varying performance).\n</p>\n<p class='vspace'>Having said that, using the default engine in PRISM (the hybrid engine), you can normally expect to be able to handle models with up to 10^7-10^8 states on a typical PC. Using the MTBDD engine, you may be able to analyse much larger models (on some of the PRISM case studies, for example, PRISM can do numerical analysis of models with as many as 10^10 or 10^11 states). The manual has more information about PRISM's <a class='urllink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a>.\n</p></div>\n<p class='vspace'><a name='model_size' id='model_size'></a>\n</p><h3>How can I reduce the size of my model?</h3>\n<div class='answer' > \n<p>The size of a probabilistic model (i.e. the number of states/transitions) is critical to the efficiency of performing probabilistic model checking on it, since both the time and memory required to do so are often proportional to the model size. Unfortunately, it is very easy to create models that are extremely large. Below are a few general tips for reducing model size.\n</p>\n<div class='vspace'></div><ul><li>Look for variables that have unnecessarily large ranges and try to reduce them. Even if your model needs large variables, it is generally a good strategy to first get a smaller version building successfully and then scale it up afterwards.\n<div class='vspace'></div></li><li>Similarly, can you (if only temporarily) reduce the number of modules/components of your model? Start with the smallest number of components possible and then add others one by one.\n<div class='vspace'></div></li><li>Do you have any inter-dependencies between variables? For example, perhaps you have some variables which are simply functions of other variables of the model. Even if these are convenient for model checking, they can be replaced with <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>formulas or labels</a>, which do not contribute to the state space.\n<div class='vspace'></div></li><li>Do any variables include more detail than is necessary for the model? Perhaps this can be exploited in order to reduce the number of variables in your model.\n<div class='vspace'></div></li><li>More generally, are any aspects of the model not relevant to the properties that you are interested in? If so, start with a simpler, more abstract version of the model and then add more details if possible.\n</li></ul></div>\n<p class='vspace'><a name='ordering' id='ordering'></a>\n</p><h3>How can I choose a good variable ordering?</h3>\n<div class='answer' > \n<p>Because PRISM is a symbolic model checker, the amount of memory required to store the probabilistic model can vary (sometime unpredictably) according to several factors. One example is the order in which the variables of your model appear in the model file. In general, there is no definitive answer to what the best ordering is but the following heuristics are a good guide.\n</p>\n<div class='vspace'></div><ul><li>Variables which are closely related should appear close together\n<div class='vspace'></div></li><li>Variables which are related to most or all other variables should appear near the start of the ordering\n</li></ul><p class='vspace'>Variables <code>x</code> and <code>y</code> are \"related\" if, for example, the value of one is has an effect on how the other changes (e.g. <code>(y'=x+1)</code>) or if both appear together in an expression (e.g. a guard).\n</p>\n<p class='vspace'>These heuristics also apply to the ordering of <em>modules</em> within the model file.\n</p>\n<p class='vspace'>For technical details about variable ordering issues, see e.g. section 8 of [<a class='wikilink' href='../Main/References.html#HKN+03'>HKN+03</a>] or section 4.1.2 of [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>].\n</p></div>\n<p class='vspace'><a name='det_delay' id='det_delay'></a>\n</p><h3>How can I add deterministic time delays to a CTMC model?</h3>\n<div class='answer' > \n<p>All delays in a CTMC need to be modelled as <em>exponential</em> distributions. This is what makes them efficient to analyse. If you included a transition whose delay was <em>deterministic</em>, i.e. which always occurred after exactly the same delay,  the model would no longer be a CTMC.\n</p>\n<p class='vspace'>One solution to this, if your model require such a delay, is to approximate a deterministic delay with an <a class='urllink' href='http://en.wikipedia.org/wiki/Erlang_distribution'>Erlang distribution</a> (a special case of a phase-type distribution). See for example this PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mean</span> = <span class=\"prismnum\">10</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">trigger</span><br/>\n<br/>\n\t<span class=\"prismident\">i</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[]&nbsp;&nbsp;&nbsp;<span class=\"prismident\">i</span> &lt; <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">i</span> = <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">main</span><br/>\n<br/>\n\t<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the model, the occurrence of the the go-labelled action occurs with an Erlang distribution with mean <code>mean</code> and shape <code>k</code>. The special case of <code>k</code>=1 is just an exponential distribution. The graph below shows the probability distribution of the delay, i.e. of <code>P=? [ F&lt;=T x=1 ]</code> for different values of <code>k</code>.\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/faq-erlang.jpg' alt='' /></div>\n<p class='vspace'>There is an obvious trade-off here between the accuracy (how close it is to modelling a deterministic time delay) and the resulting blow-up in the size of the model that you add this to. For <code>k</code>=1000, you can see that the shape is quite \"deterministic\" but this would increase your model size by a factor of ~1000.\n</p></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/Main@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / Main | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='index.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <h1>Frequently Asked Questions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Main@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='index.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Main@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 27, 2014, at 05:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='selflink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/Main@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / Main | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='index.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <h1>Frequently Asked Questions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Main@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='index.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Main@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 27, 2014, at 05:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='selflink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/Main@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | FrequentlyAskedQuestions / Main </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <h1>Frequently Asked Questions</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Below are some frequently asked questions about the use of PRISM.\nFor issues regarding the installation of PRISM, see the \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\" section in the <a class='wikilink' href='../InstallingPRISM/Main.html'>installation instructions</a>. If you have questions that are not answered here, please use the <a class='urllink' href='http://groups.google.com/group/prismmodelchecker'>discussion group</a>.\n</p>\n<p class='vspace'>Questions are grouped into the several topics, as shown below. You can also view <a class='wikilink' href='AllOnOnePage.html'>all topics together</a>.\n</p>\n<div class='vspace'></div><h3><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a></h3>\n<ul><li><a class='wikilink' href='MemoryProblems.html#crash'>PRISM crashed or stopped responding. Why?</a>\n</li><li><a class='wikilink' href='MemoryProblems.html#memout'>I ran out of memory. What can I do?</a>\n</li><li><a class='wikilink' href='MemoryProblems.html#memout_constr'>I ran out of memory during model construction. What can I do?</a>\n</li><li><a class='wikilink' href='MemoryProblems.html#memout_check'>I ran out of memory during model checking What can I do?</a>\n</li><li><a class='wikilink' href='MemoryProblems.html#memout_parse'>I ran out of memory during model parsing. What can I do?</a>\n</li></ul><div class='vspace'></div><h3><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a></h3>\n<ul><li><a class='wikilink' href='PRISMModelling.html#max_model_size'>What size models can PRISM handle?</a>\n</li><li><a class='wikilink' href='PRISMModelling.html#model_size'>How can I reduce the size of my model?</a>\n</li><li><a class='wikilink' href='PRISMModelling.html#ordering'>How can I choose a good variable ordering?</a>\n</li><li><a class='wikilink' href='PRISMModelling.html#det_delay'>How can I add deterministic time delays to a CTMC model?</a>\n</li></ul><div class='vspace'></div><h3><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a></h3>\n<ul><li><a class='wikilink' href='PRISMProperties.html#inf_rewards'>Why is my expected reward infinite?</a>\n</li><li><a class='wikilink' href='PRISMProperties.html#mult_states'>How do I check if a property is true in multiple (or all) states?</a>\n</li><li><a class='wikilink' href='PRISMProperties.html#action'>How do I compute the probability of an action occurring?</a>\n</li></ul>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/MemoryProblems.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / Memory Problems \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='MemoryProblems.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='MemoryProblems@action=edit.html'>Edit</a> - <a class='wikilink' href='MemoryProblems@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>Memory Problems</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><a name='crash' id='crash'></a>\n</p><h3>PRISM crashed or stopped responding. Why?</h3>\n<div class='answer' > \n<p>When PRISM crashes, the most likely cause is that it has run out of memory.\nSimilarly, if PRISM (or the machine you are running it on) becomes very slow or seems to have stopped responding, this is probably because it is using too much of your machine's memory. Probabilistic model checking, much like other formal verification techniques, can be a very resource-intensive process. It is very easy to create a seemingly simple PRISM model that requires a large amount of time and/or memory to construct and analyse. See some of the other questions in this section for tips on how to avoid this.\n</p>\n<p class='vspace'>The other possibility is that you have found a bug.\nIf PRISM crashes or freezes whilst not using all/most of the available memory (you can check this with the <code>top</code> command in a Unix/Linux terminal or the Task Manager (via Ctrl-Alt-Delete) on Windows) then please file a <a class='urllink' href='https://github.com/prismmodelchecker/prism/issues'>bug report</a>.\n</p></div>\n<p class='vspace'><a name='memout' id='memout'></a>\n</p><h3>I ran out of memory. What can I do?</h3>\n<div class='answer' > \n<p>It depends. First, you need to establish at what point in PRISM's operation, you ran out of memory. If you are running the command-line version of PRISM then the output from the tool so far should give an indication of this. If using the GUI, check the log tab for this information. If PRISM crashed because of its memory usage, the error message can be helpful. If using the GUI, you may need to start the GUI from the command-line to see any error messages.\n</p>\n<p class='vspace'>The two main steps that PRISM typically has to perform are:\n</p>\n<div class='vspace'></div><ol><li><strong>Model construction</strong> (conversion of a PRISM language description to the corresponding probabilistic model)\n</li><li><strong>Model checking/analysis</strong> (processing/analysis of a constructed probabilistic model in order to determine the result of a property or to compute steady-state/transient probabilities)\n</li></ol><p class='vspace'>Memory usage issues for each of these steps are discussed in separate sections below. In some cases the process performed prior to step 1 (<strong>model parsing</strong> - reading in a model description in the PRISM language and checking it for correctness) can also be resource intensive. This is also discussed below.\n</p>\n<p class='vspace'>If you are using the <strong>simulator</strong> to generate approximate model checking results then step 1 (model construction) is not performed and step 2 is carried out very differently. Memory consumption is not usually a problem in this case.\n</p></div>\n<p class='vspace'><a name='memout_constr' id='memout_constr'></a>\n</p><h3>I ran out of memory during model construction. What can I do?</h3>\n<div class='answer' > \n<p>If PRISM has already output this:\n</p>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Building model...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>but there is no line of the form:\n</p>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Time for model construction: 34.3 seconds.</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>and then you get an error like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by Java Runtime Environment:</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">#  SIGSEGV (0xb) at pc=0xb5249323, pid=19298, tid=3086363536</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.6.0-b105 mixed mode, sharing)</span><br/>\n<span style=\"font-style:italic;\"># Problematic frame:</span><br/>\n<span style=\"font-style:italic;\"># C  [libdd.so+0x39323]  Cudd_Ref+0xf</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An error report file with more information is saved as hs_err_pid19298.log</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># If you would like to submit a bug report, please visit:</span><br/>\n<span style=\"font-style:italic;\">#   http://java.sun.com/webapps/bugreport/crash.jsp</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50: 19298 Aborted                 \"$PRISM_JAVA\" #$PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by HotSpot Virtual Machine: </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0b1c7da3, pid=2884, tid=2544 </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.5.0_06-b05 mixed mode) </span><br/>\n<span style=\"font-style:italic;\"># Problematic frame: </span><br/>\n<span style=\"font-style:italic;\"># C [dd.dll+0x7da3] </span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then PRISM ran out of memory whilst trying to construct the model.\nModel construction in PRISM is performed using BDDs (binary decision diagrams) and MTBDDs (multi-terminal) BDDs which are implemented in the CUDD library.\nThe first thing to try in this case is to increase the amount of memory available to CUDD. See the entry \"CUDD memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p>\n<p class='vspace'>If increasing this memory limit does not resolve the problem, then you will need to consider ways to reduce the size of your model. You can find some tips on this in the <a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a> section. Bear in mind also that if you are having to increase the CUDD memory limit too high (e.g. close to the physical memory available on your computer) just for model construction, then it is unlikely that you will have enough memory for subsequent model checking operations.\n</p>\n<p class='vspace'>Finally, it is also worth considering the ordering of the modules and variables in your model since this can have a (in some cases dramatic) effect on the size of MTBDD representation of the model. This topic is covered in the \"<a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n</p></div>\n<p class='vspace'><a name='memout_check' id='memout_check'></a>\n</p><h3>I ran out of memory during model checking. What can I do?</h3>\n<div class='answer' > \n<p>If model construction was successfully completed (see previous question) but model checking was not, there are several things you can try. First of all, if the error message you see looks like the one in the previous question or you see a message such as\n</p>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">DD_MatrixMultiply: res is NULL</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then it may be worth increasing the memory limit for CUDD (as described above). However, if you see an error more like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50:  3139 Aborted                 \"$PRISM_JAVA\" $PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then increasing the memory CUDD probably will not help - PRISM is just trying to allocate more memory than is physically available on your system.\n</p>\n<p class='vspace'>Here are some general tips:\n</p>\n<div class='vspace'></div><ul><li>Try experimenting with using the different <em>engines</em> in PRISM. Read the section \"<a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Configuring PRISM - Computation Engines</a>\" for details.\n<div class='vspace'></div></li><li>Look at the detailed output of PRISM for information about memory usage. If you are using the hybrid (or sparse) engine and the limiting factor in terms of memory is creation of the vectors, then you have no choice but to try and reduce the size (number of states) of your model. If you are using the MTBDD engine, it is also well worth considering the variable ordering of your model. Both topics are discussed in the \"<a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n<div class='vspace'></div></li><li>Finally, if you can find no way to reduce the size of your model and are happy to consider an approximate (rather than exact) analysis, you may wish to try using PRISM's <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>discrete-event simulation engine</a> for analysis.\n</li></ul></div>\n<p class='vspace'><a name='memout_parse' id='memout_parse'></a>\n</p><h3>I ran out of memory during model parsing. What can I do?</h3>\n<div class='answer' > \n<p>This is a less common problem and will only occur if the actual PRISM language description of your model is very large. This may be the case, for example, if you are automatically generating PRISM models in some way. Errors due to lack of memory during parsing usually look like:\n</p>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.OutOfMemoryError: Java heap space </span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or:\n</p>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.StackOverflowError</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>You can resolve this problem by increasing the memory allocated to Java.\nSee the entry \"Java memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='MemoryProblems.html'>View</a> - <a rel='nofollow'  class='wikilink' href='MemoryProblems@action=edit.html'>Edit</a> - <a class='wikilink' href='MemoryProblems@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='MemoryProblems@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 22, 2016, at 11:01 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='selflink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/MemoryProblems@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / Memory Problems | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='MemoryProblems.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='MemoryProblems@action=edit.html'>Edit</a> - <a class='wikilink' href='MemoryProblems@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>Memory Problems</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='MemoryProblems@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='MemoryProblems.html'>View</a> - <a rel='nofollow'  class='wikilink' href='MemoryProblems@action=edit.html'>Edit</a> - <a class='wikilink' href='MemoryProblems@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='MemoryProblems@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 22, 2016, at 11:01 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='selflink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/MemoryProblems@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / Memory Problems | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='MemoryProblems.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='MemoryProblems@action=edit.html'>Edit</a> - <a class='wikilink' href='MemoryProblems@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>Memory Problems</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='MemoryProblems@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='MemoryProblems.html'>View</a> - <a rel='nofollow'  class='wikilink' href='MemoryProblems@action=edit.html'>Edit</a> - <a class='wikilink' href='MemoryProblems@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='MemoryProblems@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 22, 2016, at 11:01 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='selflink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/MemoryProblems@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | FrequentlyAskedQuestions / MemoryProblems </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>Memory Problems</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p><a name='crash' id='crash'></a>\n</p><h3>PRISM crashed or stopped responding. Why?</h3>\n<div class='answer' > \n<p>When PRISM crashes, the most likely cause is that it has run out of memory.\nSimilarly, if PRISM (or the machine you are running it on) becomes very slow or seems to have stopped responding, this is probably because it is using too much of your machine's memory. Probabilistic model checking, much like other formal verification techniques, can be a very resource-intensive process. It is very easy to create a seemingly simple PRISM model that requires a large amount of time and/or memory to construct and analyse. See some of the other questions in this section for tips on how to avoid this.\n</p>\n<p class='vspace'>The other possibility is that you have found a bug.\nIf PRISM crashes or freezes whilst not using all/most of the available memory (you can check this with the <code>top</code> command in a Unix/Linux terminal or the Task Manager (via Ctrl-Alt-Delete) on Windows) then please file a <a class='urllink' href='https://github.com/prismmodelchecker/prism/issues'>bug report</a>.\n</p></div>\n<p class='vspace'><a name='memout' id='memout'></a>\n</p><h3>I ran out of memory. What can I do?</h3>\n<div class='answer' > \n<p>It depends. First, you need to establish at what point in PRISM's operation, you ran out of memory. If you are running the command-line version of PRISM then the output from the tool so far should give an indication of this. If using the GUI, check the log tab for this information. If PRISM crashed because of its memory usage, the error message can be helpful. If using the GUI, you may need to start the GUI from the command-line to see any error messages.\n</p>\n<p class='vspace'>The two main steps that PRISM typically has to perform are:\n</p>\n<div class='vspace'></div><ol><li><strong>Model construction</strong> (conversion of a PRISM language description to the corresponding probabilistic model)\n</li><li><strong>Model checking/analysis</strong> (processing/analysis of a constructed probabilistic model in order to determine the result of a property or to compute steady-state/transient probabilities)\n</li></ol><p class='vspace'>Memory usage issues for each of these steps are discussed in separate sections below. In some cases the process performed prior to step 1 (<strong>model parsing</strong> - reading in a model description in the PRISM language and checking it for correctness) can also be resource intensive. This is also discussed below.\n</p>\n<p class='vspace'>If you are using the <strong>simulator</strong> to generate approximate model checking results then step 1 (model construction) is not performed and step 2 is carried out very differently. Memory consumption is not usually a problem in this case.\n</p></div>\n<p class='vspace'><a name='memout_constr' id='memout_constr'></a>\n</p><h3>I ran out of memory during model construction. What can I do?</h3>\n<div class='answer' > \n<p>If PRISM has already output this:\n</p>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Building model...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>but there is no line of the form:\n</p>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Time for model construction: 34.3 seconds.</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>and then you get an error like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by Java Runtime Environment:</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">#  SIGSEGV (0xb) at pc=0xb5249323, pid=19298, tid=3086363536</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.6.0-b105 mixed mode, sharing)</span><br/>\n<span style=\"font-style:italic;\"># Problematic frame:</span><br/>\n<span style=\"font-style:italic;\"># C  [libdd.so+0x39323]  Cudd_Ref+0xf</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An error report file with more information is saved as hs_err_pid19298.log</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># If you would like to submit a bug report, please visit:</span><br/>\n<span style=\"font-style:italic;\">#   http://java.sun.com/webapps/bugreport/crash.jsp</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50: 19298 Aborted                 \"$PRISM_JAVA\" #$PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by HotSpot Virtual Machine: </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0b1c7da3, pid=2884, tid=2544 </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.5.0_06-b05 mixed mode) </span><br/>\n<span style=\"font-style:italic;\"># Problematic frame: </span><br/>\n<span style=\"font-style:italic;\"># C [dd.dll+0x7da3] </span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then PRISM ran out of memory whilst trying to construct the model.\nModel construction in PRISM is performed using BDDs (binary decision diagrams) and MTBDDs (multi-terminal) BDDs which are implemented in the CUDD library.\nThe first thing to try in this case is to increase the amount of memory available to CUDD. See the entry \"CUDD memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p>\n<p class='vspace'>If increasing this memory limit does not resolve the problem, then you will need to consider ways to reduce the size of your model. You can find some tips on this in the <a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a> section. Bear in mind also that if you are having to increase the CUDD memory limit too high (e.g. close to the physical memory available on your computer) just for model construction, then it is unlikely that you will have enough memory for subsequent model checking operations.\n</p>\n<p class='vspace'>Finally, it is also worth considering the ordering of the modules and variables in your model since this can have a (in some cases dramatic) effect on the size of MTBDD representation of the model. This topic is covered in the \"<a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n</p></div>\n<p class='vspace'><a name='memout_check' id='memout_check'></a>\n</p><h3>I ran out of memory during model checking. What can I do?</h3>\n<div class='answer' > \n<p>If model construction was successfully completed (see previous question) but model checking was not, there are several things you can try. First of all, if the error message you see looks like the one in the previous question or you see a message such as\n</p>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">DD_MatrixMultiply: res is NULL</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then it may be worth increasing the memory limit for CUDD (as described above). However, if you see an error more like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50:  3139 Aborted                 \"$PRISM_JAVA\" $PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then increasing the memory CUDD probably will not help - PRISM is just trying to allocate more memory than is physically available on your system.\n</p>\n<p class='vspace'>Here are some general tips:\n</p>\n<div class='vspace'></div><ul><li>Try experimenting with using the different <em>engines</em> in PRISM. Read the section \"<a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Configuring PRISM - Computation Engines</a>\" for details.\n<div class='vspace'></div></li><li>Look at the detailed output of PRISM for information about memory usage. If you are using the hybrid (or sparse) engine and the limiting factor in terms of memory is creation of the vectors, then you have no choice but to try and reduce the size (number of states) of your model. If you are using the MTBDD engine, it is also well worth considering the variable ordering of your model. Both topics are discussed in the \"<a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n<div class='vspace'></div></li><li>Finally, if you can find no way to reduce the size of your model and are happy to consider an approximate (rather than exact) analysis, you may wish to try using PRISM's <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>discrete-event simulation engine</a> for analysis.\n</li></ul></div>\n<p class='vspace'><a name='memout_parse' id='memout_parse'></a>\n</p><h3>I ran out of memory during model parsing. What can I do?</h3>\n<div class='answer' > \n<p>This is a less common problem and will only occur if the actual PRISM language description of your model is very large. This may be the case, for example, if you are automatically generating PRISM models in some way. Errors due to lack of memory during parsing usually look like:\n</p>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.OutOfMemoryError: Java heap space </span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or:\n</p>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.StackOverflowError</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/MemoryProblems?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>You can resolve this problem by increasing the memory allocated to Java.\nSee the entry \"Java memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/PRISMModelling.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / PRISM Modelling \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMModelling.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMModelling@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelling@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>PRISM Modelling</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><a name='max_model_size' id='max_model_size'></a>\n</p><h3>What size models can PRISM handle?</h3>\n<div class='answer' > \n<p>There is no definitive answer to this. Because of PRISM's symbolic implementation, using data structures based on binary decision diagrams (BDDs), its performance can be unpredictable in this respect. There are also several factors that affect performance, including the type of model and property being checked and the engine being used (PRISM has several different engines, which have varying performance).\n</p>\n<p class='vspace'>Having said that, using the default engine in PRISM (the hybrid engine), you can normally expect to be able to handle models with up to 10^7-10^8 states on a typical PC. Using the MTBDD engine, you may be able to analyse much larger models (on some of the PRISM case studies, for example, PRISM can do numerical analysis of models with as many as 10^10 or 10^11 states). The manual has more information about PRISM's <a class='urllink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a>.\n</p></div>\n<p class='vspace'><a name='model_size' id='model_size'></a>\n</p><h3>How can I reduce the size of my model?</h3>\n<div class='answer' > \n<p>The size of a probabilistic model (i.e. the number of states/transitions) is critical to the efficiency of performing probabilistic model checking on it, since both the time and memory required to do so are often proportional to the model size. Unfortunately, it is very easy to create models that are extremely large. Below are a few general tips for reducing model size.\n</p>\n<div class='vspace'></div><ul><li>Look for variables that have unnecessarily large ranges and try to reduce them. Even if your model needs large variables, it is generally a good strategy to first get a smaller version building successfully and then scale it up afterwards.\n<div class='vspace'></div></li><li>Similarly, can you (if only temporarily) reduce the number of modules/components of your model? Start with the smallest number of components possible and then add others one by one.\n<div class='vspace'></div></li><li>Do you have any inter-dependencies between variables? For example, perhaps you have some variables which are simply functions of other variables of the model. Even if these are convenient for model checking, they can be replaced with <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>formulas or labels</a>, which do not contribute to the state space.\n<div class='vspace'></div></li><li>Do any variables include more detail than is necessary for the model? Perhaps this can be exploited in order to reduce the number of variables in your model.\n<div class='vspace'></div></li><li>More generally, are any aspects of the model not relevant to the properties that you are interested in? If so, start with a simpler, more abstract version of the model and then add more details if possible.\n</li></ul></div>\n<p class='vspace'><a name='ordering' id='ordering'></a>\n</p><h3>How can I choose a good variable ordering?</h3>\n<div class='answer' > \n<p>Because PRISM is a symbolic model checker, the amount of memory required to store the probabilistic model can vary (sometime unpredictably) according to several factors. One example is the order in which the variables of your model appear in the model file. In general, there is no definitive answer to what the best ordering is but the following heuristics are a good guide.\n</p>\n<div class='vspace'></div><ul><li>Variables which are closely related should appear close together\n<div class='vspace'></div></li><li>Variables which are related to most or all other variables should appear near the start of the ordering\n</li></ul><p class='vspace'>Variables <code>x</code> and <code>y</code> are \"related\" if, for example, the value of one is has an effect on how the other changes (e.g. <code>(y'=x+1)</code>) or if both appear together in an expression (e.g. a guard).\n</p>\n<p class='vspace'>These heuristics also apply to the ordering of <em>modules</em> within the model file.\n</p>\n<p class='vspace'>For technical details about variable ordering issues, see e.g. section 8 of [<a class='wikilink' href='../Main/References.html#HKN+03'>HKN+03</a>] or section 4.1.2 of [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>].\n</p></div>\n<p class='vspace'><a name='det_delay' id='det_delay'></a>\n</p><h3>How can I add deterministic time delays to a CTMC model?</h3>\n<div class='answer' > \n<p>All delays in a CTMC need to be modelled as <em>exponential</em> distributions. This is what makes them efficient to analyse. If you included a transition whose delay was <em>deterministic</em>, i.e. which always occurred after exactly the same delay,  the model would no longer be a CTMC.\n</p>\n<p class='vspace'>One solution to this, if your model require such a delay, is to approximate a deterministic delay with an <a class='urllink' href='http://en.wikipedia.org/wiki/Erlang_distribution'>Erlang distribution</a> (a special case of a phase-type distribution). See for example this PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mean</span> = <span class=\"prismnum\">10</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">trigger</span><br/>\n<br/>\n\t<span class=\"prismident\">i</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[]&nbsp;&nbsp;&nbsp;<span class=\"prismident\">i</span> &lt; <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">i</span> = <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">main</span><br/>\n<br/>\n\t<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMModelling?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the model, the occurrence of the the go-labelled action occurs with an Erlang distribution with mean <code>mean</code> and shape <code>k</code>. The special case of <code>k</code>=1 is just an exponential distribution. The graph below shows the probability distribution of the delay, i.e. of <code>P=? [ F&lt;=T x=1 ]</code> for different values of <code>k</code>.\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/faq-erlang.jpg' alt='' /></div>\n<p class='vspace'>There is an obvious trade-off here between the accuracy (how close it is to modelling a deterministic time delay) and the resulting blow-up in the size of the model that you add this to. For <code>k</code>=1000, you can see that the shape is quite \"deterministic\" but this would increase your model size by a factor of ~1000.\n</p></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMModelling.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelling@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelling@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelling@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 24, 2010, at 01:59 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='selflink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/PRISMModelling@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / PRISM Modelling | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMModelling.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMModelling@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelling@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>PRISM Modelling</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PRISMModelling@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMModelling.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelling@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelling@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelling@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 24, 2010, at 01:59 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='selflink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/PRISMModelling@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / PRISM Modelling | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMModelling.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMModelling@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelling@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>PRISM Modelling</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PRISMModelling@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMModelling.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelling@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelling@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelling@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 24, 2010, at 01:59 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='selflink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/PRISMModelling@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | FrequentlyAskedQuestions / PRISMModelling </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>PRISM Modelling</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p><a name='max_model_size' id='max_model_size'></a>\n</p><h3>What size models can PRISM handle?</h3>\n<div class='answer' > \n<p>There is no definitive answer to this. Because of PRISM's symbolic implementation, using data structures based on binary decision diagrams (BDDs), its performance can be unpredictable in this respect. There are also several factors that affect performance, including the type of model and property being checked and the engine being used (PRISM has several different engines, which have varying performance).\n</p>\n<p class='vspace'>Having said that, using the default engine in PRISM (the hybrid engine), you can normally expect to be able to handle models with up to 10^7-10^8 states on a typical PC. Using the MTBDD engine, you may be able to analyse much larger models (on some of the PRISM case studies, for example, PRISM can do numerical analysis of models with as many as 10^10 or 10^11 states). The manual has more information about PRISM's <a class='urllink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a>.\n</p></div>\n<p class='vspace'><a name='model_size' id='model_size'></a>\n</p><h3>How can I reduce the size of my model?</h3>\n<div class='answer' > \n<p>The size of a probabilistic model (i.e. the number of states/transitions) is critical to the efficiency of performing probabilistic model checking on it, since both the time and memory required to do so are often proportional to the model size. Unfortunately, it is very easy to create models that are extremely large. Below are a few general tips for reducing model size.\n</p>\n<div class='vspace'></div><ul><li>Look for variables that have unnecessarily large ranges and try to reduce them. Even if your model needs large variables, it is generally a good strategy to first get a smaller version building successfully and then scale it up afterwards.\n<div class='vspace'></div></li><li>Similarly, can you (if only temporarily) reduce the number of modules/components of your model? Start with the smallest number of components possible and then add others one by one.\n<div class='vspace'></div></li><li>Do you have any inter-dependencies between variables? For example, perhaps you have some variables which are simply functions of other variables of the model. Even if these are convenient for model checking, they can be replaced with <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>formulas or labels</a>, which do not contribute to the state space.\n<div class='vspace'></div></li><li>Do any variables include more detail than is necessary for the model? Perhaps this can be exploited in order to reduce the number of variables in your model.\n<div class='vspace'></div></li><li>More generally, are any aspects of the model not relevant to the properties that you are interested in? If so, start with a simpler, more abstract version of the model and then add more details if possible.\n</li></ul></div>\n<p class='vspace'><a name='ordering' id='ordering'></a>\n</p><h3>How can I choose a good variable ordering?</h3>\n<div class='answer' > \n<p>Because PRISM is a symbolic model checker, the amount of memory required to store the probabilistic model can vary (sometime unpredictably) according to several factors. One example is the order in which the variables of your model appear in the model file. In general, there is no definitive answer to what the best ordering is but the following heuristics are a good guide.\n</p>\n<div class='vspace'></div><ul><li>Variables which are closely related should appear close together\n<div class='vspace'></div></li><li>Variables which are related to most or all other variables should appear near the start of the ordering\n</li></ul><p class='vspace'>Variables <code>x</code> and <code>y</code> are \"related\" if, for example, the value of one is has an effect on how the other changes (e.g. <code>(y'=x+1)</code>) or if both appear together in an expression (e.g. a guard).\n</p>\n<p class='vspace'>These heuristics also apply to the ordering of <em>modules</em> within the model file.\n</p>\n<p class='vspace'>For technical details about variable ordering issues, see e.g. section 8 of [<a class='wikilink' href='../Main/References.html#HKN+03'>HKN+03</a>] or section 4.1.2 of [<a class='wikilink' href='../Main/References.html#Par02'>Par02</a>].\n</p></div>\n<p class='vspace'><a name='det_delay' id='det_delay'></a>\n</p><h3>How can I add deterministic time delays to a CTMC model?</h3>\n<div class='answer' > \n<p>All delays in a CTMC need to be modelled as <em>exponential</em> distributions. This is what makes them efficient to analyse. If you included a transition whose delay was <em>deterministic</em>, i.e. which always occurred after exactly the same delay,  the model would no longer be a CTMC.\n</p>\n<p class='vspace'>One solution to this, if your model require such a delay, is to approximate a deterministic delay with an <a class='urllink' href='http://en.wikipedia.org/wiki/Erlang_distribution'>Erlang distribution</a> (a special case of a phase-type distribution). See for example this PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mean</span> = <span class=\"prismnum\">10</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">trigger</span><br/>\n<br/>\n\t<span class=\"prismident\">i</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[]&nbsp;&nbsp;&nbsp;<span class=\"prismident\">i</span> &lt; <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">i</span> = <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">main</span><br/>\n<br/>\n\t<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMModelling?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the model, the occurrence of the the go-labelled action occurs with an Erlang distribution with mean <code>mean</code> and shape <code>k</code>. The special case of <code>k</code>=1 is just an exponential distribution. The graph below shows the probability distribution of the delay, i.e. of <code>P=? [ F&lt;=T x=1 ]</code> for different values of <code>k</code>.\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/faq-erlang.jpg' alt='' /></div>\n<p class='vspace'>There is an obvious trade-off here between the accuracy (how close it is to modelling a deterministic time delay) and the resulting blow-up in the size of the model that you add this to. For <code>k</code>=1000, you can see that the shape is quite \"deterministic\" but this would increase your model size by a factor of ~1000.\n</p></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/PRISMProperties.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / PRISM Properties \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>PRISM Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><a name='inf_rewards' id='inf_rewards'></a>\n</p><h3>Why is my expected reward infinite?</h3>\n<div class='answer' > \n<p>This mostly commonly occurs when you are computing the expected reward that is accumulated up until some target set of states is reached (\"reachability reward\" properties). For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">end</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As mentioned <a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>earlier</a>, this kind of property returns infinity if <code>\"end\"</code> is not eventually reached with probability 1. This is a choice that we made when designing the property specification language. Often, it is reasonable to assume that, if a path continues indefinitely without reaching a goal state, then reward will continue to be accumulated infinitely often (this would usually be true when modelling time as a reward structure, for instance). If there is a non-zero probability of <em>not</em> reaching the target (i.e. the probability of reaching it is less than 1), we would then expect the overall expected reward to be infinite.\n</p>\n<p class='vspace'>You can check whether the probability of reaching the target <em>is</em> 1 with a property like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">end</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A similar situation arises with models that contain nondeterminism, such as MDPs. The <em>maximum</em> expected reward to reach a target is finite if and only if the <em>minimum</em> probability of reaching the target is 1. Conversely, the <em>minimum</em> expected reward is finite if and only if the <em>maximum</em> probability is 1. \n</p>\n<div class='vspace'></div></div>\n<p class='vspace'><a name='mult_states' id='mult_states'></a>\n</p><h3>How do I check if a property is true in multiple (or all) states?</h3>\n<div class='answer' > \n<p>Consider a typical boolean-valued PRISM property, such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>i.e. \"the probability of reaching a state labelled with <code>\"error\"</code> is less than 0.01. By default, when model checking this query, PRISM will report the result of this property <em>for the initial state</em> of the model, i.e. whether, <em>starting from the initial state</em>, the probability of reaching <code>\"error\"</code> is below 0.01.\n(This is in contrast to older versions of PRISM, which used to report whether the property was true <em>for all</em> states.)\n</p>\n<p class='vspace'>To check whether the above property is true for, say, all (reachable) states satisfying the label <code>\"safe\"</code>, you should use <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>, as \nillustrated below:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismident\">safe</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you want to check whether the property is true for <em>all</em> reachable states, you can use either of the following two (equivalent) properties:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismkeyword\">true</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In older versions of PRISM, checking that a property was true in a particular set of states was done using implication (<code>=&gt;</code>). If you wish, you can still use a similar form of property to achieve this, as shown by the following example: \n</p>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, \"<span class=\"prismident\">safe</span>\" =&gt; <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n<p class='vspace'><a name='action' id='action'></a>\n</p><h3>How do I compute the probability of an action occurring?</h3>\n<div class='answer' > \n<p>PRISM's property specification language is primarily state-based, e.g. you can compute the probability of reaching a <em>state</em> that satisfies the label <code>\"error\"</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>So how do you compute the probability of a some action <code>b</code> occurring? You need to make a small change to your model. The cleanest way to do this is to add a small module that changes state when the action occurs, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">module</span> <span class=\"prismident\">checker</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">q</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismident\">q</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">q</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismident\">q</span>=<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">q</span>'=<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can determine the probability of action <code>b</code> occurring in the model with the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">q</span>=<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By design, the module above will not affect the behaviour (timing, probability, etc.) of your model at all, so all other properties will remain unchanged. This is true for any of the model types that PRISM supports. It may, though, lead to a (hopefully small) increase in total model size.\n</p>\n<p class='vspace'>You can also modify the property above to compute, for example, the probability of <code>b</code> occurring within <code>T</code> time-units or the expected time until <code>b</code> occurs:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">q</span>=<span class=\"prismnum\">1</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">q</span>=<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>(where a constant <code>T</code> or reward structure <code>time</code> have been added to the model, as appropriate).\n</p></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 20, 2014, at 10:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='selflink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/PRISMProperties@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / PRISM Properties | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>PRISM Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PRISMProperties@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 20, 2014, at 10:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='selflink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/PRISMProperties@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / PRISM Properties | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>PRISM Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PRISMProperties@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 20, 2014, at 10:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='selflink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/PRISMProperties@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | FrequentlyAskedQuestions / PRISMProperties </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='index.html'>Frequently Asked Questions</a> /\n</p><h1>PRISM Properties</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p><a name='inf_rewards' id='inf_rewards'></a>\n</p><h3>Why is my expected reward infinite?</h3>\n<div class='answer' > \n<p>This mostly commonly occurs when you are computing the expected reward that is accumulated up until some target set of states is reached (\"reachability reward\" properties). For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">end</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As mentioned <a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>earlier</a>, this kind of property returns infinity if <code>\"end\"</code> is not eventually reached with probability 1. This is a choice that we made when designing the property specification language. Often, it is reasonable to assume that, if a path continues indefinitely without reaching a goal state, then reward will continue to be accumulated infinitely often (this would usually be true when modelling time as a reward structure, for instance). If there is a non-zero probability of <em>not</em> reaching the target (i.e. the probability of reaching it is less than 1), we would then expect the overall expected reward to be infinite.\n</p>\n<p class='vspace'>You can check whether the probability of reaching the target <em>is</em> 1 with a property like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">end</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A similar situation arises with models that contain nondeterminism, such as MDPs. The <em>maximum</em> expected reward to reach a target is finite if and only if the <em>minimum</em> probability of reaching the target is 1. Conversely, the <em>minimum</em> expected reward is finite if and only if the <em>maximum</em> probability is 1. \n</p>\n<div class='vspace'></div></div>\n<p class='vspace'><a name='mult_states' id='mult_states'></a>\n</p><h3>How do I check if a property is true in multiple (or all) states?</h3>\n<div class='answer' > \n<p>Consider a typical boolean-valued PRISM property, such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>i.e. \"the probability of reaching a state labelled with <code>\"error\"</code> is less than 0.01. By default, when model checking this query, PRISM will report the result of this property <em>for the initial state</em> of the model, i.e. whether, <em>starting from the initial state</em>, the probability of reaching <code>\"error\"</code> is below 0.01.\n(This is in contrast to older versions of PRISM, which used to report whether the property was true <em>for all</em> states.)\n</p>\n<p class='vspace'>To check whether the above property is true for, say, all (reachable) states satisfying the label <code>\"safe\"</code>, you should use <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>, as \nillustrated below:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismident\">safe</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you want to check whether the property is true for <em>all</em> reachable states, you can use either of the following two (equivalent) properties:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismkeyword\">true</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In older versions of PRISM, checking that a property was true in a particular set of states was done using implication (<code>=&gt;</code>). If you wish, you can still use a similar form of property to achieve this, as shown by the following example: \n</p>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, \"<span class=\"prismident\">safe</span>\" =&gt; <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n<p class='vspace'><a name='action' id='action'></a>\n</p><h3>How do I compute the probability of an action occurring?</h3>\n<div class='answer' > \n<p>PRISM's property specification language is primarily state-based, e.g. you can compute the probability of reaching a <em>state</em> that satisfies the label <code>\"error\"</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>So how do you compute the probability of a some action <code>b</code> occurring? You need to make a small change to your model. The cleanest way to do this is to add a small module that changes state when the action occurs, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">module</span> <span class=\"prismident\">checker</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">q</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismident\">q</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">q</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismident\">q</span>=<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">q</span>'=<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can determine the probability of action <code>b</code> occurring in the model with the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">q</span>=<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By design, the module above will not affect the behaviour (timing, probability, etc.) of your model at all, so all other properties will remain unchanged. This is true for any of the model types that PRISM supports. It may, though, lead to a (hopefully small) increase in total model size.\n</p>\n<p class='vspace'>You can also modify the property above to compute, for example, the probability of <code>b</code> occurring within <code>T</code> time-units or the expected time until <code>b</code> occurs:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">q</span>=<span class=\"prismnum\">1</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">q</span>=<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/FrequentlyAskedQuestions/PRISMProperties?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>(where a constant <code>T</code> or reward structure <code>time</code> have been added to the model, as appropriate).\n</p></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions/index.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / Main \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='index.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <h1>Frequently Asked Questions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Below are some frequently asked questions about the use of PRISM.\nFor issues regarding the installation of PRISM, see the \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\" section in the <a class='wikilink' href='../InstallingPRISM/Main.html'>installation instructions</a>. If you have questions that are not answered here, please use the <a class='urllink' href='http://groups.google.com/group/prismmodelchecker'>discussion group</a>.\n</p>\n<p class='vspace'>Questions are grouped into the several topics, as shown below. You can also view <a class='wikilink' href='AllOnOnePage.html'>all topics together</a>.\n</p>\n<div class='vspace'></div><h3><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a></h3>\n<ul><li><a class='wikilink' href='MemoryProblems.html#crash'>PRISM crashed or stopped responding. Why?</a>\n</li><li><a class='wikilink' href='MemoryProblems.html#memout'>I ran out of memory. What can I do?</a>\n</li><li><a class='wikilink' href='MemoryProblems.html#memout_constr'>I ran out of memory during model construction. What can I do?</a>\n</li><li><a class='wikilink' href='MemoryProblems.html#memout_check'>I ran out of memory during model checking What can I do?</a>\n</li><li><a class='wikilink' href='MemoryProblems.html#memout_parse'>I ran out of memory during model parsing. What can I do?</a>\n</li></ul><div class='vspace'></div><h3><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a></h3>\n<ul><li><a class='wikilink' href='PRISMModelling.html#max_model_size'>What size models can PRISM handle?</a>\n</li><li><a class='wikilink' href='PRISMModelling.html#model_size'>How can I reduce the size of my model?</a>\n</li><li><a class='wikilink' href='PRISMModelling.html#ordering'>How can I choose a good variable ordering?</a>\n</li><li><a class='wikilink' href='PRISMModelling.html#det_delay'>How can I add deterministic time delays to a CTMC model?</a>\n</li></ul><div class='vspace'></div><h3><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a></h3>\n<ul><li><a class='wikilink' href='PRISMProperties.html#inf_rewards'>Why is my expected reward infinite?</a>\n</li><li><a class='wikilink' href='PRISMProperties.html#mult_states'>How do I check if a property is true in multiple (or all) states?</a>\n</li><li><a class='wikilink' href='PRISMProperties.html#action'>How do I compute the probability of an action occurring?</a>\n</li></ul>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='index.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Main@action=edit.html'>Edit</a> - <a class='wikilink' href='Main@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Main@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 27, 2014, at 05:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='selflink' href='index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/FrequentlyAskedQuestions.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Frequently Asked Questions / Main \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='FrequentlyAskedQuestions/index.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='FrequentlyAskedQuestions/Main@action=edit.html'>Edit</a> - <a class='wikilink' href='FrequentlyAskedQuestions/Main@action=print.html'>Print</a> - <a class='wikilink' href='Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <h1>Frequently Asked Questions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Below are some frequently asked questions about the use of PRISM.\nFor issues regarding the installation of PRISM, see the \"<a class='wikilink' href='InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\" section in the <a class='wikilink' href='InstallingPRISM/Main.html'>installation instructions</a>. If you have questions that are not answered here, please use the <a class='urllink' href='http://groups.google.com/group/prismmodelchecker'>discussion group</a>.\n</p>\n<p class='vspace'>Questions are grouped into the several topics, as shown below. You can also view <a class='wikilink' href='FrequentlyAskedQuestions/AllOnOnePage.html'>all topics together</a>.\n</p>\n<div class='vspace'></div><h3><a class='wikilink' href='FrequentlyAskedQuestions/MemoryProblems.html'>Memory Problems</a></h3>\n<ul><li><a class='wikilink' href='FrequentlyAskedQuestions/MemoryProblems.html#crash'>PRISM crashed or stopped responding. Why?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/MemoryProblems.html#memout'>I ran out of memory. What can I do?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/MemoryProblems.html#memout_constr'>I ran out of memory during model construction. What can I do?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/MemoryProblems.html#memout_check'>I ran out of memory during model checking What can I do?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/MemoryProblems.html#memout_parse'>I ran out of memory during model parsing. What can I do?</a>\n</li></ul><div class='vspace'></div><h3><a class='wikilink' href='FrequentlyAskedQuestions/PRISMModelling.html'>PRISM Modelling</a></h3>\n<ul><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMModelling.html#max_model_size'>What size models can PRISM handle?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMModelling.html#model_size'>How can I reduce the size of my model?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMModelling.html#ordering'>How can I choose a good variable ordering?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMModelling.html#det_delay'>How can I add deterministic time delays to a CTMC model?</a>\n</li></ul><div class='vspace'></div><h3><a class='wikilink' href='FrequentlyAskedQuestions/PRISMProperties.html'>PRISM Properties</a></h3>\n<ul><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMProperties.html#inf_rewards'>Why is my expected reward infinite?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMProperties.html#mult_states'>How do I check if a property is true in multiple (or all) states?</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMProperties.html#action'>How do I compute the probability of an action occurring?</a>\n</li></ul>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='FrequentlyAskedQuestions/index.html'>View</a> - <a rel='nofollow'  class='wikilink' href='FrequentlyAskedQuestions/Main@action=edit.html'>Edit</a> - <a class='wikilink' href='FrequentlyAskedQuestions/Main@action=print.html'>Print</a> - <a class='wikilink' href='Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='FrequentlyAskedQuestions/Main@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 27, 2014, at 05:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='selflink' href='FrequentlyAskedQuestions/index.html'>Frequently Asked Questions</a></strong>\n</p><ul><li><a class='wikilink' href='FrequentlyAskedQuestions/MemoryProblems.html'>Memory Problems</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMModelling.html'>PRISM Modelling</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/PRISMProperties.html'>PRISM Properties</a>\n</li></ul><p>[ <a class='wikilink' href='FrequentlyAskedQuestions/AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/AllOnOnePage.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / All On One Page \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Installing PRISM</span></h1>\n<hr />\n<h1>Instructions</h1>\n<h3>Prerequisites</h3>\n<p>PRISM is known to run on Linux, Windows and macOS, both 64-bit and 32-bit versions.\n</p>\n<p class='vspace'>You will need <strong>Java</strong>, version 11 or above.\nTo run binary versions of PRISM, you only need the Java Runtime Environment (JRE), not the full Java Development Kit (JDK).\n</p>\n<p class='vspace'>To compile PRISM from source, you need the Java Development Kit (JDK), GNU make and a C/C++ compiler (e.g. gcc/g++). For compilation under Windows, you will need Cygwin. See below for more information:\n</p>\n<div class='vspace'></div><ul><li><a href='AllOnOnePage.html#windows'>Installation on Windows</a>\n</li><li><a href='AllOnOnePage.html#binaries'>Installation of Linux/Mac binary versions</a>\n</li><li><a href='AllOnOnePage.html#source'>Building PRISM from source (non-Windows)</a>\n</li><li><a href='AllOnOnePage.html#cygwin'>Building PRISM from source on Windows using Cygwin</a>\n</li><li><a href='AllOnOnePage.html#msys'>Building PRISM from source on Windows using MSYS2</a>\n</li></ul><p class='vspace'>If you are installing on a completely fresh operating system installation (e.g. in a virtual machine), you may find the following scripts useful,\nwhich install the required dependencies and PRISM itself. They can be found in the <code>prism/etc/scripts</code> directory:\n</p>\n<div class='vspace'></div><ul><li>Script to build on a clean install of Ubuntu: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-ubuntu'>prism-install-ubuntu</a>\n</li><li>Script to build on a clean install of Fedora-based Linux (e.g. Amazon Linux): <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-fedora'>prism-install-fedora</a>\n</li><li>Scripts to build on a clean install of Windows: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> and <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-cygwin'>prism-install-cygwin</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='windows' id='windows'></a>\n<a name='windows64' id='windows64'></a>\n</p><h3>Installation on Windows</h3>\n<p>If you don't yet have <strong>Java</strong>, install it, for example with the <a class='urllink' href='https://adoptium.net/temurin/releases'>Temurin installer</a>.\n</p>\n<p class='vspace'>To install PRISM on Windows, just run the self-extracting installer which you <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>downloaded</a>. You do <strong>not</strong> need administrator privileges for this, just write-access to the directory chosen for installation.\n</p>\n<p class='vspace'>If requested, the installer will place shortcuts to run PRISM on the desktop and/or start menu. If not, you can run by PRISM double-clicking the file <code>xprism.bat</code> (which may just appear as <code>xprism</code>) in the <code>bin</code> folder of your PRISM folder. If nothing happens, the most likely explanation is that Java is not installed or not in your path. To check, open a command prompt window, navigate to the PRISM directory, type <code>cd bin</code>, then <code>xprism.bat</code> and examine the resulting error. If you want to create shortcuts to <code>xprism.bat</code> manually, you will find some PRISM icons in the <code>etc</code> folder.\n</p>\n<p class='vspace'>If you wish to use the command-line version of PRISM on Windows, open a command prompt window and type for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd \"c:\\Program Files\\prism-4.8-win\\bin\"</span><br/>\n<span style=\"font-weight:bold;\">prism ..\\prism-examples\\simple\\dice\\dice.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n    \n<p class='vspace'>You can also edit the file <code>bin\\prism.bat</code> to allow it to be run from any location. See the instructions within the file for further details.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='binaries' id='binaries'></a>\n</p><h3>Installation of Linux/Mac binary versions</h3>\n<p>We provide pre-compiled <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>binary distributions</a> for Linux and macOS\n(if you have any problems running these, try compiling PRISM from source instead - see below for instructions).\nTo install a binary distribution, unpack the tarred/zipped PRISM distribution into a suitable location, enter the directory and run the <code>install.sh</code> script, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-linux64-x86.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-linux64-x86</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>On macOS, you may want to run the following command,\nwhich avoids <a class='urllink' href='https://support.apple.com/en-gb/102445'>manual approving</a> the integrity of the binary files:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You do not need to be root to install PRISM. The install script simply makes some small customisations to the scripts used to launch PRISM. The PRISM distribution is self-contained and can be freely moved/renamed, however if you do so you will need to re-run <code>./install.sh</code> afterwards.\n</p>\n<p class='vspace'>To run PRISM, execute either the <code>xprism</code> or <code>prism</code> script (for the graphical user interface or command-line version, respectively). These can be found in the <code>bin</code> directory. These scripts are designed to be run from anywhere and you can easily create symbolic links or aliases to them. If you want icons to create desktop shortcuts to PRISM, you can find some in the <code>etc</code> directory.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='source' id='source'></a>\n</p><h3>Building PRISM from source (non-Windows)</h3>\n<p>To compile PRISM form source code, you will need:\n</p>\n<div class='vspace'></div><ul><li>GNU make (sometimes called gmake)\n</li><li>a C/C++ compiler (e.g. gcc/g++)\n</li><li>a Java Development Kit, version 11 or above\n</li></ul><p class='vspace'>To check that you have the development kit, type <code>javac</code>. If you get an error message that <code>javac</code> cannot be found, you probably do not have the JDK installed (or your path is not set up correctly). To check what version you have, type <code>javac -version</code>. \n</p>\n<p class='vspace'>Hopefully, you can build PRISM simply by entering the PRISM directory and running <code>make</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-src.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-src/prism</span><br/>\n<span style=\"font-weight:bold;\">make</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For this process to complete correctly, PRISM needs to be able to determine your operating system (<code>OSTYPE</code>), machine architecture (<code>ARCH</code>) and the location of your Java distribution (<code>JAVA_DIR</code>). If there is a problem with either of these, you will see an error message and will need to specify one or more of these manually, such as in these examples:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">  </span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux ARCH=aarch64</span><br/>\n<span style=\"font-weight:bold;\">make JAVA_DIR=/usr/java/jdk1.8.0</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin JAVA_DIR=\"/cygdrive/c/Program Files/Java/jdk1.8.0\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of double quotes for the case where the directory contains a space. If you don't know the location of your Java installation, try typing <code>which javac</code>. If the result is e.g. <code>/usr/java/jdk1.8.0/bin/javac</code> then your Java directory is <code>/usr/java/jdk1.8.0</code>. Sometimes <code>javac</code> will be a symbolic link, in which case use \"<code>ls -l</code>\" to determine the actual location.\n</p>\n<p class='vspace'>It is also possible to to set the environment variables directly or edit their values in the Makefile directly. Note that even when you specify <code>JAVA_DIR</code> explicitly (in either way), PRISM still uses the version of <code>javac</code> that is in your path. To override this, you can also specify a specific version by setting <code>JAVAC</code>.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='cygwin' id='cygwin'></a>\n</p><h3>Building PRISM from source on Windows using Cygwin</h3>\n<p>The compilation of PRISM currently relies on a Unix-like environment. On Windows, this can be achieved using the <a class='urllink' href='http://www.cygwin.com/'>Cygwin</a> development environment, with the packages below installed.\nYou can run the script <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> in a Command Prompt to automate this.\n</p><ul><li><code>make</code>\n</li><li><code>mingw64-x86_64-gcc-g++</code> (for 64-bit Windows) or <code>mingw64-i686-gcc-g++</code> (for 32-bit Windows)\n</li><li><code>binutils</code>\n</li><li><code>dos2unix</code>\n</li><li><code>git</code> (if you will pull source code from GitHub)\n</li><li><code>wget</code> (if you will pull source code from the web)\n</li></ul><p>Then proceed as described in the previous section. Note that the PRISM compilation process uses the <a class='urllink' href='http://www.mingw.org/'>MinGW</a> libraries so that the final result is independent of Cygwin at run-time.\n</p>\n<p class='vspace'>One thing to note: make sure you unzip the PRISM distribution from within Cygwin (e.g. using <code>tar xfz prism-XXX-src.tar.gz</code>). Don't use a Windows program (Winzip, etc.) since this can cause problems.\n</p>\n<p class='vspace'>If you use git to checkout the PRISM repository, we recommend that you use the version of git provided by Cygwin.\nIf you use a native Windows version of git, you may want to disable the Unix-to-Windows line-ending conversion, e.g., via\n</p>\n<div class='vspace'></div><ul><li><code>git config --global core.autocrlf false</code>\n</li></ul><p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='msys' id='msys'></a>\n</p><h3>Building PRISM from source on Windows using MSYS2</h3>\n<p>An alternative to Cygwin on Windows is <a class='urllink' href='https://www.msys2.org/'>MSYS2</a>.\nYou can install the required MSYS2 packages like this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">pacman -S make mingw-w64-x86_64-gcc binutils dos2unix git wget unzip python nano</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The environment is currently not directly supported in the Makefile,\nwhich can be fixed as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Additionally, MSYS2 does not handle symlinks in the same way as Cygwin does.\nAt some point <code>make</code> will fail, saying that it cannot find the CUDD library.\nYou can solve this as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd ../cudd/</span><br/>\n<span style=\"font-weight:bold;\">rmdir lib/ </span><br/>\n<span style=\"font-weight:bold;\">./setup.sh</span><br/>\n<span style=\"font-weight:bold;\">cd ../prism</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p><hr />\n<h1>Common Problems And Questions</h1>\n<p>This section describes some of the most common problems and questions related to the installation and running of PRISM. These are grouped into the following categories:\n</p>\n<div class='vspace'></div><ul><li>Running PRISM on Windows\n</li><li>Running PRISM on non-Windows platforms\n</li><li>Compiling PRISM\n</li><li>Other issues\n</li></ul><div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on Windows</h2>\n<p><strong>When I try to run PRISM on Windows, I double-click the PRISM shortcut but nothing happens.</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>The most common cause of this is that you either do not have Java installed or the <code>java</code> executable is not in your path. In any case, to determine the exact problem, launch a command shell and navigate to the <code>bin</code> directory inside the directory where you installed PRISM (you can use the \"PRISM (console)\" shortcut installed in the start menu to do this). Then, type <code>prism.bat</code> and see what error message is displayed.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on non-Windows platforms</h2>\n<p><strong>When I try to run PRISM, I get one of these errors:</strong><br />\n</p><ul><li><strong><code>Exception in thread \"main\" java.lang.NoClassDefFoundError: ...</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: no prism in java.library.path</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: ...<br />Library not loaded: ../../lib/libdd.dylib</code></strong>\n</li></ul><div class='vspace'></div><div class='answer' > \n<p>Things to check:\n</p>\n<p class='vspace'>(1) Did you run <code>install.sh</code> from the PRISM directory? (non-Windows platforms)\n</p>\n<p class='vspace'>(2) If you compiled PRISM from source code, are you sure no errors occurred during the process? To check, go into the PRISM directory, type <code>make clean_all</code> and then <code>make</code>, checking the output (especially at the end) carefully for any error messages.\n</p>\n<p class='vspace'>(3) Are you running on Mac OS? See the next question.\n</p>\n<p class='vspace'>(3) Are you running on an old version of Mac OS (notably El Capitan)? This had some issues with PRISM calling <code>java</code>.\nA workaround is to specify the exact path to the <code>java</code> when running PRISM, e.g.:\n</p>\n<p class='vspace'><code>PRISM_JAVA=/Library/Java/JavaVirtualMachines/jdk1.9.jdk/Contents/Home/bin/java prism</code>\n</p>\n<p class='vspace'>or by replacing the value of PRISM_JAVA directly in the prism script\ndirectly.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM on macOS, I get an error of the form: \"<code>libprism.dylib</code> cant be opened because Apple cannot check it for malicious software.\" or \"<code>libprism.dylib not valid for use in process: library load disallowed by system policy</code>\".</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM's macOS binaries are currently not signed/notarised,\nso you need to approve the binary files manually to run them.\nRun this command from the same place you ran <code>./install.sh</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or approve the libraries one by one through the\n<a class='urllink' href='https://support.apple.com/en-gb/102445'>security settings</a>.\n</p>\n<p class='vspace'>You can also avoid this issue by compiling from source code.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM, I get an error of the form:<br /><code>Exception in thread \"main\" java.lang.UnsupportedClassVersionError: Bad version number in .class file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Your version of Java is too old. Update or install a newer version of Java, and then try again.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Compiling PRISM</h2>\n<p><strong>When I try to compile PRISM, <code>make</code> seems to get stuck in an infinite loop</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>This is probably due to the detection of Java failing. Specify the location of your Java directory by hand, e.g. <code>make JAVA_DIR=/usr/java/jdk1.9.0</code>. See the <a class='wikilink' href='Main.html'>Instructions</a> page for more on this.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>/usr/bin/libtool: for architecture: cputype (16777234) cpusubtype (0) file: -lSystem is not an object file (not allowed in a library)</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you compiling PRISM on Max OS X? If so, the likely explanation is that you have upgraded to a new version of Mac OS X but have not upgraded the developer tools (eg. XCode). Upgrade and try again.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, nothing seems to happen</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>Unexpected end of line seen...</code><br />or:<br /><code>make: Fatal error in reader: Makefile, line 58: Unexpected end of line seen...</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>./setup.sh: line 33: syntax error: unexpected end of file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you building on Cygwin? And did you unpack PRISM using WinZip? If so, unpack from Cygwin, using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>Assembler messages:  Fatal error: can't create ../../obj/dd/dd_abstr.o: No such file or directory</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Did you unpack PRISM using a graphical tool or file manager? If so, unpack using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>Do I have to use GNU <code>make</code> to build PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Strictly speaking, no, but you will have to modify the various PRISM Makefiles manually to overcome this.\n</p></div>\n<p class='vspace'><strong>Can I build PRISM on operating systems other than those currently supported?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM should be suitable for any Unix/Linux variant.\n</p>\n<p class='vspace'>The first thing you will need to do is compile CUDD (the BDD library used by and included in PRISM) on that platform.\nFortunately, CUDD has already been successfully built on a large number of\noperating systems. Have a look at the sample Makefiles we provide (i.e. the\nfiles <code>cudd/Makefile.*</code>) which are slight variants of the original Makefile\nprovided with CUDD (found here: <code>cudd/modified/orig/Makefile</code>). They contain\ninstructions on how to modify it for various platforms. You can then call\nyour new modified makefile something appropriate (<code>cudd/Makefile.$OSTYPE</code>) and\nproceed to build PRISM as usual. To just build CUDD, not PRISM, type\n<code>make cuddpackage</code> instead of <code>make</code>.\n</p>\n<p class='vspace'>Next, look at the main PRISM Makefile, in particular, each place where the\nvariable <code>$OSTYPE</code> is referred to. Most lines include comments and further\ninstructions. Once you have done this, proceed as usual.\n</p>\n<p class='vspace'>If you do successfully build PRISM on other platforms, please let us know\nso we can include this information in future releases. Thanks.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Other issues</h2>\n<p><strong>How do I uninstall PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>If you installed PRISM on Windows using the self-extracting installer, you can uninstall it using the option on the start menu. If you didn't add these shortcuts, just run <code>uninstall.exe</code> from the directory where you installed PRISM.\n</p>\n<p class='vspace'>For older versions of PRISM on Windows or on any other platform, simply delete the directory containing it.\n</p>\n<p class='vspace'>The only thing that is not removed via either of these methods is the <code>.prism</code> file containing your PRISM settings which is in your home directory (see the section \"<a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\"). You may wish to retain this when upgrading.\n</p></div>\n<p class='vspace'><strong>I still have a problem installing/running PRISM. What can I do?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Please post a message in the discussion group (see the <a class='urllink' href='http://www.prismmodelchecker.org/support.php'>support</a> section of the PRISM website).\n</p></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 11, 2007, at 03:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/AllOnOnePage@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / All On One Page | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 11, 2007, at 03:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/AllOnOnePage@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / All On One Page | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 11, 2007, at 03:29 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/AllOnOnePage@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | InstallingPRISM / AllOnOnePage </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Installing PRISM</span></h1>\n<hr />\n<h1>Instructions</h1>\n<h3>Prerequisites</h3>\n<p>PRISM is known to run on Linux, Windows and macOS, both 64-bit and 32-bit versions.\n</p>\n<p class='vspace'>You will need <strong>Java</strong>, version 11 or above.\nTo run binary versions of PRISM, you only need the Java Runtime Environment (JRE), not the full Java Development Kit (JDK).\n</p>\n<p class='vspace'>To compile PRISM from source, you need the Java Development Kit (JDK), GNU make and a C/C++ compiler (e.g. gcc/g++). For compilation under Windows, you will need Cygwin. See below for more information:\n</p>\n<div class='vspace'></div><ul><li><a href='AllOnOnePage@action=print.html#windows'>Installation on Windows</a>\n</li><li><a href='AllOnOnePage@action=print.html#binaries'>Installation of Linux/Mac binary versions</a>\n</li><li><a href='AllOnOnePage@action=print.html#source'>Building PRISM from source (non-Windows)</a>\n</li><li><a href='AllOnOnePage@action=print.html#cygwin'>Building PRISM from source on Windows using Cygwin</a>\n</li><li><a href='AllOnOnePage@action=print.html#msys'>Building PRISM from source on Windows using MSYS2</a>\n</li></ul><p class='vspace'>If you are installing on a completely fresh operating system installation (e.g. in a virtual machine), you may find the following scripts useful,\nwhich install the required dependencies and PRISM itself. They can be found in the <code>prism/etc/scripts</code> directory:\n</p>\n<div class='vspace'></div><ul><li>Script to build on a clean install of Ubuntu: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-ubuntu'>prism-install-ubuntu</a>\n</li><li>Script to build on a clean install of Fedora-based Linux (e.g. Amazon Linux): <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-fedora'>prism-install-fedora</a>\n</li><li>Scripts to build on a clean install of Windows: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> and <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-cygwin'>prism-install-cygwin</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='windows' id='windows'></a>\n<a name='windows64' id='windows64'></a>\n</p><h3>Installation on Windows</h3>\n<p>If you don't yet have <strong>Java</strong>, install it, for example with the <a class='urllink' href='https://adoptium.net/temurin/releases'>Temurin installer</a>.\n</p>\n<p class='vspace'>To install PRISM on Windows, just run the self-extracting installer which you <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>downloaded</a>. You do <strong>not</strong> need administrator privileges for this, just write-access to the directory chosen for installation.\n</p>\n<p class='vspace'>If requested, the installer will place shortcuts to run PRISM on the desktop and/or start menu. If not, you can run by PRISM double-clicking the file <code>xprism.bat</code> (which may just appear as <code>xprism</code>) in the <code>bin</code> folder of your PRISM folder. If nothing happens, the most likely explanation is that Java is not installed or not in your path. To check, open a command prompt window, navigate to the PRISM directory, type <code>cd bin</code>, then <code>xprism.bat</code> and examine the resulting error. If you want to create shortcuts to <code>xprism.bat</code> manually, you will find some PRISM icons in the <code>etc</code> folder.\n</p>\n<p class='vspace'>If you wish to use the command-line version of PRISM on Windows, open a command prompt window and type for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd \"c:\\Program Files\\prism-4.8-win\\bin\"</span><br/>\n<span style=\"font-weight:bold;\">prism ..\\prism-examples\\simple\\dice\\dice.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n    \n<p class='vspace'>You can also edit the file <code>bin\\prism.bat</code> to allow it to be run from any location. See the instructions within the file for further details.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='binaries' id='binaries'></a>\n</p><h3>Installation of Linux/Mac binary versions</h3>\n<p>We provide pre-compiled <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>binary distributions</a> for Linux and macOS\n(if you have any problems running these, try compiling PRISM from source instead - see below for instructions).\nTo install a binary distribution, unpack the tarred/zipped PRISM distribution into a suitable location, enter the directory and run the <code>install.sh</code> script, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-linux64-x86.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-linux64-x86</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>On macOS, you may want to run the following command,\nwhich avoids <a class='urllink' href='https://support.apple.com/en-gb/102445'>manual approving</a> the integrity of the binary files:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You do not need to be root to install PRISM. The install script simply makes some small customisations to the scripts used to launch PRISM. The PRISM distribution is self-contained and can be freely moved/renamed, however if you do so you will need to re-run <code>./install.sh</code> afterwards.\n</p>\n<p class='vspace'>To run PRISM, execute either the <code>xprism</code> or <code>prism</code> script (for the graphical user interface or command-line version, respectively). These can be found in the <code>bin</code> directory. These scripts are designed to be run from anywhere and you can easily create symbolic links or aliases to them. If you want icons to create desktop shortcuts to PRISM, you can find some in the <code>etc</code> directory.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='source' id='source'></a>\n</p><h3>Building PRISM from source (non-Windows)</h3>\n<p>To compile PRISM form source code, you will need:\n</p>\n<div class='vspace'></div><ul><li>GNU make (sometimes called gmake)\n</li><li>a C/C++ compiler (e.g. gcc/g++)\n</li><li>a Java Development Kit, version 11 or above\n</li></ul><p class='vspace'>To check that you have the development kit, type <code>javac</code>. If you get an error message that <code>javac</code> cannot be found, you probably do not have the JDK installed (or your path is not set up correctly). To check what version you have, type <code>javac -version</code>. \n</p>\n<p class='vspace'>Hopefully, you can build PRISM simply by entering the PRISM directory and running <code>make</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-src.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-src/prism</span><br/>\n<span style=\"font-weight:bold;\">make</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For this process to complete correctly, PRISM needs to be able to determine your operating system (<code>OSTYPE</code>), machine architecture (<code>ARCH</code>) and the location of your Java distribution (<code>JAVA_DIR</code>). If there is a problem with either of these, you will see an error message and will need to specify one or more of these manually, such as in these examples:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">  </span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux ARCH=aarch64</span><br/>\n<span style=\"font-weight:bold;\">make JAVA_DIR=/usr/java/jdk1.8.0</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin JAVA_DIR=\"/cygdrive/c/Program Files/Java/jdk1.8.0\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of double quotes for the case where the directory contains a space. If you don't know the location of your Java installation, try typing <code>which javac</code>. If the result is e.g. <code>/usr/java/jdk1.8.0/bin/javac</code> then your Java directory is <code>/usr/java/jdk1.8.0</code>. Sometimes <code>javac</code> will be a symbolic link, in which case use \"<code>ls -l</code>\" to determine the actual location.\n</p>\n<p class='vspace'>It is also possible to to set the environment variables directly or edit their values in the Makefile directly. Note that even when you specify <code>JAVA_DIR</code> explicitly (in either way), PRISM still uses the version of <code>javac</code> that is in your path. To override this, you can also specify a specific version by setting <code>JAVAC</code>.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='cygwin' id='cygwin'></a>\n</p><h3>Building PRISM from source on Windows using Cygwin</h3>\n<p>The compilation of PRISM currently relies on a Unix-like environment. On Windows, this can be achieved using the <a class='urllink' href='http://www.cygwin.com/'>Cygwin</a> development environment, with the packages below installed.\nYou can run the script <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> in a Command Prompt to automate this.\n</p><ul><li><code>make</code>\n</li><li><code>mingw64-x86_64-gcc-g++</code> (for 64-bit Windows) or <code>mingw64-i686-gcc-g++</code> (for 32-bit Windows)\n</li><li><code>binutils</code>\n</li><li><code>dos2unix</code>\n</li><li><code>git</code> (if you will pull source code from GitHub)\n</li><li><code>wget</code> (if you will pull source code from the web)\n</li></ul><p>Then proceed as described in the previous section. Note that the PRISM compilation process uses the <a class='urllink' href='http://www.mingw.org/'>MinGW</a> libraries so that the final result is independent of Cygwin at run-time.\n</p>\n<p class='vspace'>One thing to note: make sure you unzip the PRISM distribution from within Cygwin (e.g. using <code>tar xfz prism-XXX-src.tar.gz</code>). Don't use a Windows program (Winzip, etc.) since this can cause problems.\n</p>\n<p class='vspace'>If you use git to checkout the PRISM repository, we recommend that you use the version of git provided by Cygwin.\nIf you use a native Windows version of git, you may want to disable the Unix-to-Windows line-ending conversion, e.g., via\n</p>\n<div class='vspace'></div><ul><li><code>git config --global core.autocrlf false</code>\n</li></ul><p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='msys' id='msys'></a>\n</p><h3>Building PRISM from source on Windows using MSYS2</h3>\n<p>An alternative to Cygwin on Windows is <a class='urllink' href='https://www.msys2.org/'>MSYS2</a>.\nYou can install the required MSYS2 packages like this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">pacman -S make mingw-w64-x86_64-gcc binutils dos2unix git wget unzip python nano</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The environment is currently not directly supported in the Makefile,\nwhich can be fixed as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Additionally, MSYS2 does not handle symlinks in the same way as Cygwin does.\nAt some point <code>make</code> will fail, saying that it cannot find the CUDD library.\nYou can solve this as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd ../cudd/</span><br/>\n<span style=\"font-weight:bold;\">rmdir lib/ </span><br/>\n<span style=\"font-weight:bold;\">./setup.sh</span><br/>\n<span style=\"font-weight:bold;\">cd ../prism</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p><hr />\n<h1>Common Problems And Questions</h1>\n<p>This section describes some of the most common problems and questions related to the installation and running of PRISM. These are grouped into the following categories:\n</p>\n<div class='vspace'></div><ul><li>Running PRISM on Windows\n</li><li>Running PRISM on non-Windows platforms\n</li><li>Compiling PRISM\n</li><li>Other issues\n</li></ul><div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on Windows</h2>\n<p><strong>When I try to run PRISM on Windows, I double-click the PRISM shortcut but nothing happens.</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>The most common cause of this is that you either do not have Java installed or the <code>java</code> executable is not in your path. In any case, to determine the exact problem, launch a command shell and navigate to the <code>bin</code> directory inside the directory where you installed PRISM (you can use the \"PRISM (console)\" shortcut installed in the start menu to do this). Then, type <code>prism.bat</code> and see what error message is displayed.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on non-Windows platforms</h2>\n<p><strong>When I try to run PRISM, I get one of these errors:</strong><br />\n</p><ul><li><strong><code>Exception in thread \"main\" java.lang.NoClassDefFoundError: ...</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: no prism in java.library.path</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: ...<br />Library not loaded: ../../lib/libdd.dylib</code></strong>\n</li></ul><div class='vspace'></div><div class='answer' > \n<p>Things to check:\n</p>\n<p class='vspace'>(1) Did you run <code>install.sh</code> from the PRISM directory? (non-Windows platforms)\n</p>\n<p class='vspace'>(2) If you compiled PRISM from source code, are you sure no errors occurred during the process? To check, go into the PRISM directory, type <code>make clean_all</code> and then <code>make</code>, checking the output (especially at the end) carefully for any error messages.\n</p>\n<p class='vspace'>(3) Are you running on Mac OS? See the next question.\n</p>\n<p class='vspace'>(3) Are you running on an old version of Mac OS (notably El Capitan)? This had some issues with PRISM calling <code>java</code>.\nA workaround is to specify the exact path to the <code>java</code> when running PRISM, e.g.:\n</p>\n<p class='vspace'><code>PRISM_JAVA=/Library/Java/JavaVirtualMachines/jdk1.9.jdk/Contents/Home/bin/java prism</code>\n</p>\n<p class='vspace'>or by replacing the value of PRISM_JAVA directly in the prism script\ndirectly.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM on macOS, I get an error of the form: \"<code>libprism.dylib</code> cant be opened because Apple cannot check it for malicious software.\" or \"<code>libprism.dylib not valid for use in process: library load disallowed by system policy</code>\".</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM's macOS binaries are currently not signed/notarised,\nso you need to approve the binary files manually to run them.\nRun this command from the same place you ran <code>./install.sh</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or approve the libraries one by one through the\n<a class='urllink' href='https://support.apple.com/en-gb/102445'>security settings</a>.\n</p>\n<p class='vspace'>You can also avoid this issue by compiling from source code.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM, I get an error of the form:<br /><code>Exception in thread \"main\" java.lang.UnsupportedClassVersionError: Bad version number in .class file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Your version of Java is too old. Update or install a newer version of Java, and then try again.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Compiling PRISM</h2>\n<p><strong>When I try to compile PRISM, <code>make</code> seems to get stuck in an infinite loop</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>This is probably due to the detection of Java failing. Specify the location of your Java directory by hand, e.g. <code>make JAVA_DIR=/usr/java/jdk1.9.0</code>. See the <a class='wikilink' href='Main.html'>Instructions</a> page for more on this.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>/usr/bin/libtool: for architecture: cputype (16777234) cpusubtype (0) file: -lSystem is not an object file (not allowed in a library)</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you compiling PRISM on Max OS X? If so, the likely explanation is that you have upgraded to a new version of Mac OS X but have not upgraded the developer tools (eg. XCode). Upgrade and try again.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, nothing seems to happen</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>Unexpected end of line seen...</code><br />or:<br /><code>make: Fatal error in reader: Makefile, line 58: Unexpected end of line seen...</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>./setup.sh: line 33: syntax error: unexpected end of file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you building on Cygwin? And did you unpack PRISM using WinZip? If so, unpack from Cygwin, using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>Assembler messages:  Fatal error: can't create ../../obj/dd/dd_abstr.o: No such file or directory</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Did you unpack PRISM using a graphical tool or file manager? If so, unpack using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>Do I have to use GNU <code>make</code> to build PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Strictly speaking, no, but you will have to modify the various PRISM Makefiles manually to overcome this.\n</p></div>\n<p class='vspace'><strong>Can I build PRISM on operating systems other than those currently supported?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM should be suitable for any Unix/Linux variant.\n</p>\n<p class='vspace'>The first thing you will need to do is compile CUDD (the BDD library used by and included in PRISM) on that platform.\nFortunately, CUDD has already been successfully built on a large number of\noperating systems. Have a look at the sample Makefiles we provide (i.e. the\nfiles <code>cudd/Makefile.*</code>) which are slight variants of the original Makefile\nprovided with CUDD (found here: <code>cudd/modified/orig/Makefile</code>). They contain\ninstructions on how to modify it for various platforms. You can then call\nyour new modified makefile something appropriate (<code>cudd/Makefile.$OSTYPE</code>) and\nproceed to build PRISM as usual. To just build CUDD, not PRISM, type\n<code>make cuddpackage</code> instead of <code>make</code>.\n</p>\n<p class='vspace'>Next, look at the main PRISM Makefile, in particular, each place where the\nvariable <code>$OSTYPE</code> is referred to. Most lines include comments and further\ninstructions. Once you have done this, proceed as usual.\n</p>\n<p class='vspace'>If you do successfully build PRISM on other platforms, please let us know\nso we can include this information in future releases. Thanks.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Other issues</h2>\n<p><strong>How do I uninstall PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>If you installed PRISM on Windows using the self-extracting installer, you can uninstall it using the option on the start menu. If you didn't add these shortcuts, just run <code>uninstall.exe</code> from the directory where you installed PRISM.\n</p>\n<p class='vspace'>For older versions of PRISM on Windows or on any other platform, simply delete the directory containing it.\n</p>\n<p class='vspace'>The only thing that is not removed via either of these methods is the <code>.prism</code> file containing your PRISM settings which is in your home directory (see the section \"<a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\"). You may wish to retain this when upgrading.\n</p></div>\n<p class='vspace'><strong>I still have a problem installing/running PRISM. What can I do?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Please post a message in the discussion group (see the <a class='urllink' href='http://www.prismmodelchecker.org/support.php'>support</a> section of the PRISM website).\n</p></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/CommonProblemsAndQuestions.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / Common Problems And Questions \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CommonProblemsAndQuestions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=edit.html'>Edit</a> - <a class='wikilink' href='CommonProblemsAndQuestions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>Common Problems And Questions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>This section describes some of the most common problems and questions related to the installation and running of PRISM. These are grouped into the following categories:\n</p>\n<div class='vspace'></div><ul><li>Running PRISM on Windows\n</li><li>Running PRISM on non-Windows platforms\n</li><li>Compiling PRISM\n</li><li>Other issues\n</li></ul><div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on Windows</h2>\n<p><strong>When I try to run PRISM on Windows, I double-click the PRISM shortcut but nothing happens.</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>The most common cause of this is that you either do not have Java installed or the <code>java</code> executable is not in your path. In any case, to determine the exact problem, launch a command shell and navigate to the <code>bin</code> directory inside the directory where you installed PRISM (you can use the \"PRISM (console)\" shortcut installed in the start menu to do this). Then, type <code>prism.bat</code> and see what error message is displayed.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on non-Windows platforms</h2>\n<p><strong>When I try to run PRISM, I get one of these errors:</strong><br />\n</p><ul><li><strong><code>Exception in thread \"main\" java.lang.NoClassDefFoundError: ...</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: no prism in java.library.path</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: ...<br />Library not loaded: ../../lib/libdd.dylib</code></strong>\n</li></ul><div class='vspace'></div><div class='answer' > \n<p>Things to check:\n</p>\n<p class='vspace'>(1) Did you run <code>install.sh</code> from the PRISM directory? (non-Windows platforms)\n</p>\n<p class='vspace'>(2) If you compiled PRISM from source code, are you sure no errors occurred during the process? To check, go into the PRISM directory, type <code>make clean_all</code> and then <code>make</code>, checking the output (especially at the end) carefully for any error messages.\n</p>\n<p class='vspace'>(3) Are you running on Mac OS? See the next question.\n</p>\n<p class='vspace'>(3) Are you running on an old version of Mac OS (notably El Capitan)? This had some issues with PRISM calling <code>java</code>.\nA workaround is to specify the exact path to the <code>java</code> when running PRISM, e.g.:\n</p>\n<p class='vspace'><code>PRISM_JAVA=/Library/Java/JavaVirtualMachines/jdk1.9.jdk/Contents/Home/bin/java prism</code>\n</p>\n<p class='vspace'>or by replacing the value of PRISM_JAVA directly in the prism script\ndirectly.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM on macOS, I get an error of the form: \"<code>libprism.dylib</code> cant be opened because Apple cannot check it for malicious software.\" or \"<code>libprism.dylib not valid for use in process: library load disallowed by system policy</code>\".</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM's macOS binaries are currently not signed/notarised,\nso you need to approve the binary files manually to run them.\nRun this command from the same place you ran <code>./install.sh</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/CommonProblemsAndQuestions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or approve the libraries one by one through the\n<a class='urllink' href='https://support.apple.com/en-gb/102445'>security settings</a>.\n</p>\n<p class='vspace'>You can also avoid this issue by compiling from source code.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM, I get an error of the form:<br /><code>Exception in thread \"main\" java.lang.UnsupportedClassVersionError: Bad version number in .class file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Your version of Java is too old. Update or install a newer version of Java, and then try again.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Compiling PRISM</h2>\n<p><strong>When I try to compile PRISM, <code>make</code> seems to get stuck in an infinite loop</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>This is probably due to the detection of Java failing. Specify the location of your Java directory by hand, e.g. <code>make JAVA_DIR=/usr/java/jdk1.9.0</code>. See the <a class='wikilink' href='Main.html'>Instructions</a> page for more on this.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>/usr/bin/libtool: for architecture: cputype (16777234) cpusubtype (0) file: -lSystem is not an object file (not allowed in a library)</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you compiling PRISM on Max OS X? If so, the likely explanation is that you have upgraded to a new version of Mac OS X but have not upgraded the developer tools (eg. XCode). Upgrade and try again.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, nothing seems to happen</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>Unexpected end of line seen...</code><br />or:<br /><code>make: Fatal error in reader: Makefile, line 58: Unexpected end of line seen...</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>./setup.sh: line 33: syntax error: unexpected end of file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you building on Cygwin? And did you unpack PRISM using WinZip? If so, unpack from Cygwin, using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>Assembler messages:  Fatal error: can't create ../../obj/dd/dd_abstr.o: No such file or directory</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Did you unpack PRISM using a graphical tool or file manager? If so, unpack using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>Do I have to use GNU <code>make</code> to build PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Strictly speaking, no, but you will have to modify the various PRISM Makefiles manually to overcome this.\n</p></div>\n<p class='vspace'><strong>Can I build PRISM on operating systems other than those currently supported?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM should be suitable for any Unix/Linux variant.\n</p>\n<p class='vspace'>The first thing you will need to do is compile CUDD (the BDD library used by and included in PRISM) on that platform.\nFortunately, CUDD has already been successfully built on a large number of\noperating systems. Have a look at the sample Makefiles we provide (i.e. the\nfiles <code>cudd/Makefile.*</code>) which are slight variants of the original Makefile\nprovided with CUDD (found here: <code>cudd/modified/orig/Makefile</code>). They contain\ninstructions on how to modify it for various platforms. You can then call\nyour new modified makefile something appropriate (<code>cudd/Makefile.$OSTYPE</code>) and\nproceed to build PRISM as usual. To just build CUDD, not PRISM, type\n<code>make cuddpackage</code> instead of <code>make</code>.\n</p>\n<p class='vspace'>Next, look at the main PRISM Makefile, in particular, each place where the\nvariable <code>$OSTYPE</code> is referred to. Most lines include comments and further\ninstructions. Once you have done this, proceed as usual.\n</p>\n<p class='vspace'>If you do successfully build PRISM on other platforms, please let us know\nso we can include this information in future releases. Thanks.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Other issues</h2>\n<p><strong>How do I uninstall PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>If you installed PRISM on Windows using the self-extracting installer, you can uninstall it using the option on the start menu. If you didn't add these shortcuts, just run <code>uninstall.exe</code> from the directory where you installed PRISM.\n</p>\n<p class='vspace'>For older versions of PRISM on Windows or on any other platform, simply delete the directory containing it.\n</p>\n<p class='vspace'>The only thing that is not removed via either of these methods is the <code>.prism</code> file containing your PRISM settings which is in your home directory (see the section \"<a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\"). You may wish to retain this when upgrading.\n</p></div>\n<p class='vspace'><strong>I still have a problem installing/running PRISM. What can I do?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Please post a message in the discussion group (see the <a class='urllink' href='http://www.prismmodelchecker.org/support.php'>support</a> section of the PRISM website).\n</p></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CommonProblemsAndQuestions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=edit.html'>Edit</a> - <a class='wikilink' href='CommonProblemsAndQuestions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 07, 2025, at 12:31 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Instructions</a>\n</li><li><a class='selflink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/CommonProblemsAndQuestions@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / Common Problems And Questions | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CommonProblemsAndQuestions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=edit.html'>Edit</a> - <a class='wikilink' href='CommonProblemsAndQuestions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>Common Problems And Questions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='CommonProblemsAndQuestions@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CommonProblemsAndQuestions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=edit.html'>Edit</a> - <a class='wikilink' href='CommonProblemsAndQuestions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 07, 2025, at 12:31 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Instructions</a>\n</li><li><a class='selflink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/CommonProblemsAndQuestions@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / Common Problems And Questions | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CommonProblemsAndQuestions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=edit.html'>Edit</a> - <a class='wikilink' href='CommonProblemsAndQuestions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>Common Problems And Questions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='CommonProblemsAndQuestions@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CommonProblemsAndQuestions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=edit.html'>Edit</a> - <a class='wikilink' href='CommonProblemsAndQuestions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CommonProblemsAndQuestions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 07, 2025, at 12:31 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Instructions</a>\n</li><li><a class='selflink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/CommonProblemsAndQuestions@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | InstallingPRISM / CommonProblemsAndQuestions </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>Common Problems And Questions</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>This section describes some of the most common problems and questions related to the installation and running of PRISM. These are grouped into the following categories:\n</p>\n<div class='vspace'></div><ul><li>Running PRISM on Windows\n</li><li>Running PRISM on non-Windows platforms\n</li><li>Compiling PRISM\n</li><li>Other issues\n</li></ul><div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on Windows</h2>\n<p><strong>When I try to run PRISM on Windows, I double-click the PRISM shortcut but nothing happens.</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>The most common cause of this is that you either do not have Java installed or the <code>java</code> executable is not in your path. In any case, to determine the exact problem, launch a command shell and navigate to the <code>bin</code> directory inside the directory where you installed PRISM (you can use the \"PRISM (console)\" shortcut installed in the start menu to do this). Then, type <code>prism.bat</code> and see what error message is displayed.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on non-Windows platforms</h2>\n<p><strong>When I try to run PRISM, I get one of these errors:</strong><br />\n</p><ul><li><strong><code>Exception in thread \"main\" java.lang.NoClassDefFoundError: ...</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: no prism in java.library.path</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: ...<br />Library not loaded: ../../lib/libdd.dylib</code></strong>\n</li></ul><div class='vspace'></div><div class='answer' > \n<p>Things to check:\n</p>\n<p class='vspace'>(1) Did you run <code>install.sh</code> from the PRISM directory? (non-Windows platforms)\n</p>\n<p class='vspace'>(2) If you compiled PRISM from source code, are you sure no errors occurred during the process? To check, go into the PRISM directory, type <code>make clean_all</code> and then <code>make</code>, checking the output (especially at the end) carefully for any error messages.\n</p>\n<p class='vspace'>(3) Are you running on Mac OS? See the next question.\n</p>\n<p class='vspace'>(3) Are you running on an old version of Mac OS (notably El Capitan)? This had some issues with PRISM calling <code>java</code>.\nA workaround is to specify the exact path to the <code>java</code> when running PRISM, e.g.:\n</p>\n<p class='vspace'><code>PRISM_JAVA=/Library/Java/JavaVirtualMachines/jdk1.9.jdk/Contents/Home/bin/java prism</code>\n</p>\n<p class='vspace'>or by replacing the value of PRISM_JAVA directly in the prism script\ndirectly.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM on macOS, I get an error of the form: \"<code>libprism.dylib</code> cant be opened because Apple cannot check it for malicious software.\" or \"<code>libprism.dylib not valid for use in process: library load disallowed by system policy</code>\".</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM's macOS binaries are currently not signed/notarised,\nso you need to approve the binary files manually to run them.\nRun this command from the same place you ran <code>./install.sh</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/CommonProblemsAndQuestions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or approve the libraries one by one through the\n<a class='urllink' href='https://support.apple.com/en-gb/102445'>security settings</a>.\n</p>\n<p class='vspace'>You can also avoid this issue by compiling from source code.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM, I get an error of the form:<br /><code>Exception in thread \"main\" java.lang.UnsupportedClassVersionError: Bad version number in .class file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Your version of Java is too old. Update or install a newer version of Java, and then try again.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Compiling PRISM</h2>\n<p><strong>When I try to compile PRISM, <code>make</code> seems to get stuck in an infinite loop</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>This is probably due to the detection of Java failing. Specify the location of your Java directory by hand, e.g. <code>make JAVA_DIR=/usr/java/jdk1.9.0</code>. See the <a class='wikilink' href='Main.html'>Instructions</a> page for more on this.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>/usr/bin/libtool: for architecture: cputype (16777234) cpusubtype (0) file: -lSystem is not an object file (not allowed in a library)</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you compiling PRISM on Max OS X? If so, the likely explanation is that you have upgraded to a new version of Mac OS X but have not upgraded the developer tools (eg. XCode). Upgrade and try again.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, nothing seems to happen</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>Unexpected end of line seen...</code><br />or:<br /><code>make: Fatal error in reader: Makefile, line 58: Unexpected end of line seen...</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>./setup.sh: line 33: syntax error: unexpected end of file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you building on Cygwin? And did you unpack PRISM using WinZip? If so, unpack from Cygwin, using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>Assembler messages:  Fatal error: can't create ../../obj/dd/dd_abstr.o: No such file or directory</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Did you unpack PRISM using a graphical tool or file manager? If so, unpack using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>Do I have to use GNU <code>make</code> to build PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Strictly speaking, no, but you will have to modify the various PRISM Makefiles manually to overcome this.\n</p></div>\n<p class='vspace'><strong>Can I build PRISM on operating systems other than those currently supported?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM should be suitable for any Unix/Linux variant.\n</p>\n<p class='vspace'>The first thing you will need to do is compile CUDD (the BDD library used by and included in PRISM) on that platform.\nFortunately, CUDD has already been successfully built on a large number of\noperating systems. Have a look at the sample Makefiles we provide (i.e. the\nfiles <code>cudd/Makefile.*</code>) which are slight variants of the original Makefile\nprovided with CUDD (found here: <code>cudd/modified/orig/Makefile</code>). They contain\ninstructions on how to modify it for various platforms. You can then call\nyour new modified makefile something appropriate (<code>cudd/Makefile.$OSTYPE</code>) and\nproceed to build PRISM as usual. To just build CUDD, not PRISM, type\n<code>make cuddpackage</code> instead of <code>make</code>.\n</p>\n<p class='vspace'>Next, look at the main PRISM Makefile, in particular, each place where the\nvariable <code>$OSTYPE</code> is referred to. Most lines include comments and further\ninstructions. Once you have done this, proceed as usual.\n</p>\n<p class='vspace'>If you do successfully build PRISM on other platforms, please let us know\nso we can include this information in future releases. Thanks.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Other issues</h2>\n<p><strong>How do I uninstall PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>If you installed PRISM on Windows using the self-extracting installer, you can uninstall it using the option on the start menu. If you didn't add these shortcuts, just run <code>uninstall.exe</code> from the directory where you installed PRISM.\n</p>\n<p class='vspace'>For older versions of PRISM on Windows or on any other platform, simply delete the directory containing it.\n</p>\n<p class='vspace'>The only thing that is not removed via either of these methods is the <code>.prism</code> file containing your PRISM settings which is in your home directory (see the section \"<a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\"). You may wish to retain this when upgrading.\n</p></div>\n<p class='vspace'><strong>I still have a problem installing/running PRISM. What can I do?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Please post a message in the discussion group (see the <a class='urllink' href='http://www.prismmodelchecker.org/support.php'>support</a> section of the PRISM website).\n</p></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/Instructions@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / Instructions | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Instructions@action=edit.html'>Edit</a> - <a class='wikilink' href='Instructions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>Instructions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Instructions@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Instructions@action=edit.html'>Edit</a> - <a class='wikilink' href='Instructions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Instructions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:57 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/Instructions@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / Instructions | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Instructions@action=edit.html'>Edit</a> - <a class='wikilink' href='Instructions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>Instructions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Instructions@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Instructions@action=edit.html'>Edit</a> - <a class='wikilink' href='Instructions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Instructions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:57 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/Instructions@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | InstallingPRISM / Instructions </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>Instructions</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<h3>Prerequisites</h3>\n<p>PRISM is known to run on Linux, Windows and macOS, both 64-bit and 32-bit versions.\n</p>\n<p class='vspace'>You will need <strong>Java</strong>, version 11 or above.\nTo run binary versions of PRISM, you only need the Java Runtime Environment (JRE), not the full Java Development Kit (JDK).\n</p>\n<p class='vspace'>To compile PRISM from source, you need the Java Development Kit (JDK), GNU make and a C/C++ compiler (e.g. gcc/g++). For compilation under Windows, you will need Cygwin. See below for more information:\n</p>\n<div class='vspace'></div><ul><li><a href='Instructions@action=print.html#windows'>Installation on Windows</a>\n</li><li><a href='Instructions@action=print.html#binaries'>Installation of Linux/Mac binary versions</a>\n</li><li><a href='Instructions@action=print.html#source'>Building PRISM from source (non-Windows)</a>\n</li><li><a href='Instructions@action=print.html#cygwin'>Building PRISM from source on Windows using Cygwin</a>\n</li><li><a href='Instructions@action=print.html#msys'>Building PRISM from source on Windows using MSYS2</a>\n</li></ul><p class='vspace'>If you are installing on a completely fresh operating system installation (e.g. in a virtual machine), you may find the following scripts useful,\nwhich install the required dependencies and PRISM itself. They can be found in the <code>prism/etc/scripts</code> directory:\n</p>\n<div class='vspace'></div><ul><li>Script to build on a clean install of Ubuntu: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-ubuntu'>prism-install-ubuntu</a>\n</li><li>Script to build on a clean install of Fedora-based Linux (e.g. Amazon Linux): <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-fedora'>prism-install-fedora</a>\n</li><li>Scripts to build on a clean install of Windows: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> and <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-cygwin'>prism-install-cygwin</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='windows' id='windows'></a>\n<a name='windows64' id='windows64'></a>\n</p><h3>Installation on Windows</h3>\n<p>If you don't yet have <strong>Java</strong>, install it, for example with the <a class='urllink' href='https://adoptium.net/temurin/releases'>Temurin installer</a>.\n</p>\n<p class='vspace'>To install PRISM on Windows, just run the self-extracting installer which you <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>downloaded</a>. You do <strong>not</strong> need administrator privileges for this, just write-access to the directory chosen for installation.\n</p>\n<p class='vspace'>If requested, the installer will place shortcuts to run PRISM on the desktop and/or start menu. If not, you can run by PRISM double-clicking the file <code>xprism.bat</code> (which may just appear as <code>xprism</code>) in the <code>bin</code> folder of your PRISM folder. If nothing happens, the most likely explanation is that Java is not installed or not in your path. To check, open a command prompt window, navigate to the PRISM directory, type <code>cd bin</code>, then <code>xprism.bat</code> and examine the resulting error. If you want to create shortcuts to <code>xprism.bat</code> manually, you will find some PRISM icons in the <code>etc</code> folder.\n</p>\n<p class='vspace'>If you wish to use the command-line version of PRISM on Windows, open a command prompt window and type for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd \"c:\\Program Files\\prism-4.8-win\\bin\"</span><br/>\n<span style=\"font-weight:bold;\">prism ..\\prism-examples\\simple\\dice\\dice.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n    \n<p class='vspace'>You can also edit the file <code>bin\\prism.bat</code> to allow it to be run from any location. See the instructions within the file for further details.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='binaries' id='binaries'></a>\n</p><h3>Installation of Linux/Mac binary versions</h3>\n<p>We provide pre-compiled <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>binary distributions</a> for Linux and macOS\n(if you have any problems running these, try compiling PRISM from source instead - see below for instructions).\nTo install a binary distribution, unpack the tarred/zipped PRISM distribution into a suitable location, enter the directory and run the <code>install.sh</code> script, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-linux64-x86.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-linux64-x86</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>On macOS, you may want to run the following command,\nwhich avoids <a class='urllink' href='https://support.apple.com/en-gb/102445'>manual approving</a> the integrity of the binary files:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You do not need to be root to install PRISM. The install script simply makes some small customisations to the scripts used to launch PRISM. The PRISM distribution is self-contained and can be freely moved/renamed, however if you do so you will need to re-run <code>./install.sh</code> afterwards.\n</p>\n<p class='vspace'>To run PRISM, execute either the <code>xprism</code> or <code>prism</code> script (for the graphical user interface or command-line version, respectively). These can be found in the <code>bin</code> directory. These scripts are designed to be run from anywhere and you can easily create symbolic links or aliases to them. If you want icons to create desktop shortcuts to PRISM, you can find some in the <code>etc</code> directory.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='source' id='source'></a>\n</p><h3>Building PRISM from source (non-Windows)</h3>\n<p>To compile PRISM form source code, you will need:\n</p>\n<div class='vspace'></div><ul><li>GNU make (sometimes called gmake)\n</li><li>a C/C++ compiler (e.g. gcc/g++)\n</li><li>a Java Development Kit, version 11 or above\n</li></ul><p class='vspace'>To check that you have the development kit, type <code>javac</code>. If you get an error message that <code>javac</code> cannot be found, you probably do not have the JDK installed (or your path is not set up correctly). To check what version you have, type <code>javac -version</code>. \n</p>\n<p class='vspace'>Hopefully, you can build PRISM simply by entering the PRISM directory and running <code>make</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-src.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-src/prism</span><br/>\n<span style=\"font-weight:bold;\">make</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For this process to complete correctly, PRISM needs to be able to determine your operating system (<code>OSTYPE</code>), machine architecture (<code>ARCH</code>) and the location of your Java distribution (<code>JAVA_DIR</code>). If there is a problem with either of these, you will see an error message and will need to specify one or more of these manually, such as in these examples:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">  </span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux ARCH=aarch64</span><br/>\n<span style=\"font-weight:bold;\">make JAVA_DIR=/usr/java/jdk1.8.0</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin JAVA_DIR=\"/cygdrive/c/Program Files/Java/jdk1.8.0\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of double quotes for the case where the directory contains a space. If you don't know the location of your Java installation, try typing <code>which javac</code>. If the result is e.g. <code>/usr/java/jdk1.8.0/bin/javac</code> then your Java directory is <code>/usr/java/jdk1.8.0</code>. Sometimes <code>javac</code> will be a symbolic link, in which case use \"<code>ls -l</code>\" to determine the actual location.\n</p>\n<p class='vspace'>It is also possible to to set the environment variables directly or edit their values in the Makefile directly. Note that even when you specify <code>JAVA_DIR</code> explicitly (in either way), PRISM still uses the version of <code>javac</code> that is in your path. To override this, you can also specify a specific version by setting <code>JAVAC</code>.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='cygwin' id='cygwin'></a>\n</p><h3>Building PRISM from source on Windows using Cygwin</h3>\n<p>The compilation of PRISM currently relies on a Unix-like environment. On Windows, this can be achieved using the <a class='urllink' href='http://www.cygwin.com/'>Cygwin</a> development environment, with the packages below installed.\nYou can run the script <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> in a Command Prompt to automate this.\n</p><ul><li><code>make</code>\n</li><li><code>mingw64-x86_64-gcc-g++</code> (for 64-bit Windows) or <code>mingw64-i686-gcc-g++</code> (for 32-bit Windows)\n</li><li><code>binutils</code>\n</li><li><code>dos2unix</code>\n</li><li><code>git</code> (if you will pull source code from GitHub)\n</li><li><code>wget</code> (if you will pull source code from the web)\n</li></ul><p>Then proceed as described in the previous section. Note that the PRISM compilation process uses the <a class='urllink' href='http://www.mingw.org/'>MinGW</a> libraries so that the final result is independent of Cygwin at run-time.\n</p>\n<p class='vspace'>One thing to note: make sure you unzip the PRISM distribution from within Cygwin (e.g. using <code>tar xfz prism-XXX-src.tar.gz</code>). Don't use a Windows program (Winzip, etc.) since this can cause problems.\n</p>\n<p class='vspace'>If you use git to checkout the PRISM repository, we recommend that you use the version of git provided by Cygwin.\nIf you use a native Windows version of git, you may want to disable the Unix-to-Windows line-ending conversion, e.g., via\n</p>\n<div class='vspace'></div><ul><li><code>git config --global core.autocrlf false</code>\n</li></ul><p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='msys' id='msys'></a>\n</p><h3>Building PRISM from source on Windows using MSYS2</h3>\n<p>An alternative to Cygwin on Windows is <a class='urllink' href='https://www.msys2.org/'>MSYS2</a>.\nYou can install the required MSYS2 packages like this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">pacman -S make mingw-w64-x86_64-gcc binutils dos2unix git wget unzip python nano</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The environment is currently not directly supported in the Makefile,\nwhich can be fixed as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Additionally, MSYS2 does not handle symlinks in the same way as Cygwin does.\nAt some point <code>make</code> will fail, saying that it cannot find the CUDD library.\nYou can solve this as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd ../cudd/</span><br/>\n<span style=\"font-weight:bold;\">rmdir lib/ </span><br/>\n<span style=\"font-weight:bold;\">./setup.sh</span><br/>\n<span style=\"font-weight:bold;\">cd ../prism</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM/Main.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / Instructions \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Instructions@action=edit.html'>Edit</a> - <a class='wikilink' href='Instructions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Installing PRISM</a> /\n</p><h1>Instructions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<h3>Prerequisites</h3>\n<p>PRISM is known to run on Linux, Windows and macOS, both 64-bit and 32-bit versions.\n</p>\n<p class='vspace'>You will need <strong>Java</strong>, version 11 or above.\nTo run binary versions of PRISM, you only need the Java Runtime Environment (JRE), not the full Java Development Kit (JDK).\n</p>\n<p class='vspace'>To compile PRISM from source, you need the Java Development Kit (JDK), GNU make and a C/C++ compiler (e.g. gcc/g++). For compilation under Windows, you will need Cygwin. See below for more information:\n</p>\n<div class='vspace'></div><ul><li><a href='Main.html#windows'>Installation on Windows</a>\n</li><li><a href='Main.html#binaries'>Installation of Linux/Mac binary versions</a>\n</li><li><a href='Main.html#source'>Building PRISM from source (non-Windows)</a>\n</li><li><a href='Main.html#cygwin'>Building PRISM from source on Windows using Cygwin</a>\n</li><li><a href='Main.html#msys'>Building PRISM from source on Windows using MSYS2</a>\n</li></ul><p class='vspace'>If you are installing on a completely fresh operating system installation (e.g. in a virtual machine), you may find the following scripts useful,\nwhich install the required dependencies and PRISM itself. They can be found in the <code>prism/etc/scripts</code> directory:\n</p>\n<div class='vspace'></div><ul><li>Script to build on a clean install of Ubuntu: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-ubuntu'>prism-install-ubuntu</a>\n</li><li>Script to build on a clean install of Fedora-based Linux (e.g. Amazon Linux): <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-fedora'>prism-install-fedora</a>\n</li><li>Scripts to build on a clean install of Windows: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> and <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-cygwin'>prism-install-cygwin</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='windows' id='windows'></a>\n<a name='windows64' id='windows64'></a>\n</p><h3>Installation on Windows</h3>\n<p>If you don't yet have <strong>Java</strong>, install it, for example with the <a class='urllink' href='https://adoptium.net/temurin/releases'>Temurin installer</a>.\n</p>\n<p class='vspace'>To install PRISM on Windows, just run the self-extracting installer which you <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>downloaded</a>. You do <strong>not</strong> need administrator privileges for this, just write-access to the directory chosen for installation.\n</p>\n<p class='vspace'>If requested, the installer will place shortcuts to run PRISM on the desktop and/or start menu. If not, you can run by PRISM double-clicking the file <code>xprism.bat</code> (which may just appear as <code>xprism</code>) in the <code>bin</code> folder of your PRISM folder. If nothing happens, the most likely explanation is that Java is not installed or not in your path. To check, open a command prompt window, navigate to the PRISM directory, type <code>cd bin</code>, then <code>xprism.bat</code> and examine the resulting error. If you want to create shortcuts to <code>xprism.bat</code> manually, you will find some PRISM icons in the <code>etc</code> folder.\n</p>\n<p class='vspace'>If you wish to use the command-line version of PRISM on Windows, open a command prompt window and type for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd \"c:\\Program Files\\prism-4.8-win\\bin\"</span><br/>\n<span style=\"font-weight:bold;\">prism ..\\prism-examples\\simple\\dice\\dice.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n    \n<p class='vspace'>You can also edit the file <code>bin\\prism.bat</code> to allow it to be run from any location. See the instructions within the file for further details.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='binaries' id='binaries'></a>\n</p><h3>Installation of Linux/Mac binary versions</h3>\n<p>We provide pre-compiled <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>binary distributions</a> for Linux and macOS\n(if you have any problems running these, try compiling PRISM from source instead - see below for instructions).\nTo install a binary distribution, unpack the tarred/zipped PRISM distribution into a suitable location, enter the directory and run the <code>install.sh</code> script, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-linux64-x86.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-linux64-x86</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>On macOS, you may want to run the following command,\nwhich avoids <a class='urllink' href='https://support.apple.com/en-gb/102445'>manual approving</a> the integrity of the binary files:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You do not need to be root to install PRISM. The install script simply makes some small customisations to the scripts used to launch PRISM. The PRISM distribution is self-contained and can be freely moved/renamed, however if you do so you will need to re-run <code>./install.sh</code> afterwards.\n</p>\n<p class='vspace'>To run PRISM, execute either the <code>xprism</code> or <code>prism</code> script (for the graphical user interface or command-line version, respectively). These can be found in the <code>bin</code> directory. These scripts are designed to be run from anywhere and you can easily create symbolic links or aliases to them. If you want icons to create desktop shortcuts to PRISM, you can find some in the <code>etc</code> directory.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='source' id='source'></a>\n</p><h3>Building PRISM from source (non-Windows)</h3>\n<p>To compile PRISM form source code, you will need:\n</p>\n<div class='vspace'></div><ul><li>GNU make (sometimes called gmake)\n</li><li>a C/C++ compiler (e.g. gcc/g++)\n</li><li>a Java Development Kit, version 11 or above\n</li></ul><p class='vspace'>To check that you have the development kit, type <code>javac</code>. If you get an error message that <code>javac</code> cannot be found, you probably do not have the JDK installed (or your path is not set up correctly). To check what version you have, type <code>javac -version</code>. \n</p>\n<p class='vspace'>Hopefully, you can build PRISM simply by entering the PRISM directory and running <code>make</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-src.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-src/prism</span><br/>\n<span style=\"font-weight:bold;\">make</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For this process to complete correctly, PRISM needs to be able to determine your operating system (<code>OSTYPE</code>), machine architecture (<code>ARCH</code>) and the location of your Java distribution (<code>JAVA_DIR</code>). If there is a problem with either of these, you will see an error message and will need to specify one or more of these manually, such as in these examples:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">  </span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux ARCH=aarch64</span><br/>\n<span style=\"font-weight:bold;\">make JAVA_DIR=/usr/java/jdk1.8.0</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin JAVA_DIR=\"/cygdrive/c/Program Files/Java/jdk1.8.0\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of double quotes for the case where the directory contains a space. If you don't know the location of your Java installation, try typing <code>which javac</code>. If the result is e.g. <code>/usr/java/jdk1.8.0/bin/javac</code> then your Java directory is <code>/usr/java/jdk1.8.0</code>. Sometimes <code>javac</code> will be a symbolic link, in which case use \"<code>ls -l</code>\" to determine the actual location.\n</p>\n<p class='vspace'>It is also possible to to set the environment variables directly or edit their values in the Makefile directly. Note that even when you specify <code>JAVA_DIR</code> explicitly (in either way), PRISM still uses the version of <code>javac</code> that is in your path. To override this, you can also specify a specific version by setting <code>JAVAC</code>.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='cygwin' id='cygwin'></a>\n</p><h3>Building PRISM from source on Windows using Cygwin</h3>\n<p>The compilation of PRISM currently relies on a Unix-like environment. On Windows, this can be achieved using the <a class='urllink' href='http://www.cygwin.com/'>Cygwin</a> development environment, with the packages below installed.\nYou can run the script <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> in a Command Prompt to automate this.\n</p><ul><li><code>make</code>\n</li><li><code>mingw64-x86_64-gcc-g++</code> (for 64-bit Windows) or <code>mingw64-i686-gcc-g++</code> (for 32-bit Windows)\n</li><li><code>binutils</code>\n</li><li><code>dos2unix</code>\n</li><li><code>git</code> (if you will pull source code from GitHub)\n</li><li><code>wget</code> (if you will pull source code from the web)\n</li></ul><p>Then proceed as described in the previous section. Note that the PRISM compilation process uses the <a class='urllink' href='http://www.mingw.org/'>MinGW</a> libraries so that the final result is independent of Cygwin at run-time.\n</p>\n<p class='vspace'>One thing to note: make sure you unzip the PRISM distribution from within Cygwin (e.g. using <code>tar xfz prism-XXX-src.tar.gz</code>). Don't use a Windows program (Winzip, etc.) since this can cause problems.\n</p>\n<p class='vspace'>If you use git to checkout the PRISM repository, we recommend that you use the version of git provided by Cygwin.\nIf you use a native Windows version of git, you may want to disable the Unix-to-Windows line-ending conversion, e.g., via\n</p>\n<div class='vspace'></div><ul><li><code>git config --global core.autocrlf false</code>\n</li></ul><p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='msys' id='msys'></a>\n</p><h3>Building PRISM from source on Windows using MSYS2</h3>\n<p>An alternative to Cygwin on Windows is <a class='urllink' href='https://www.msys2.org/'>MSYS2</a>.\nYou can install the required MSYS2 packages like this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">pacman -S make mingw-w64-x86_64-gcc binutils dos2unix git wget unzip python nano</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The environment is currently not directly supported in the Makefile,\nwhich can be fixed as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Additionally, MSYS2 does not handle symlinks in the same way as Cygwin does.\nAt some point <code>make</code> will fail, saying that it cannot find the CUDD library.\nYou can solve this as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd ../cudd/</span><br/>\n<span style=\"font-weight:bold;\">rmdir lib/ </span><br/>\n<span style=\"font-weight:bold;\">./setup.sh</span><br/>\n<span style=\"font-weight:bold;\">cd ../prism</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Instructions@action=edit.html'>Edit</a> - <a class='wikilink' href='Instructions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Instructions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:57 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/InstallingPRISM.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Installing PRISM / Instructions \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='InstallingPRISM/Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='InstallingPRISM/Instructions@action=edit.html'>Edit</a> - <a class='wikilink' href='InstallingPRISM/Instructions@action=print.html'>Print</a> - <a class='wikilink' href='Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='InstallingPRISM/Main.html'>Installing PRISM</a> /\n</p><h1>Instructions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<h3>Prerequisites</h3>\n<p>PRISM is known to run on Linux, Windows and macOS, both 64-bit and 32-bit versions.\n</p>\n<p class='vspace'>You will need <strong>Java</strong>, version 11 or above.\nTo run binary versions of PRISM, you only need the Java Runtime Environment (JRE), not the full Java Development Kit (JDK).\n</p>\n<p class='vspace'>To compile PRISM from source, you need the Java Development Kit (JDK), GNU make and a C/C++ compiler (e.g. gcc/g++). For compilation under Windows, you will need Cygwin. See below for more information:\n</p>\n<div class='vspace'></div><ul><li><a href='InstallingPRISM/Main.html#windows'>Installation on Windows</a>\n</li><li><a href='InstallingPRISM/Main.html#binaries'>Installation of Linux/Mac binary versions</a>\n</li><li><a href='InstallingPRISM/Main.html#source'>Building PRISM from source (non-Windows)</a>\n</li><li><a href='InstallingPRISM/Main.html#cygwin'>Building PRISM from source on Windows using Cygwin</a>\n</li><li><a href='InstallingPRISM/Main.html#msys'>Building PRISM from source on Windows using MSYS2</a>\n</li></ul><p class='vspace'>If you are installing on a completely fresh operating system installation (e.g. in a virtual machine), you may find the following scripts useful,\nwhich install the required dependencies and PRISM itself. They can be found in the <code>prism/etc/scripts</code> directory:\n</p>\n<div class='vspace'></div><ul><li>Script to build on a clean install of Ubuntu: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-ubuntu'>prism-install-ubuntu</a>\n</li><li>Script to build on a clean install of Fedora-based Linux (e.g. Amazon Linux): <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-fedora'>prism-install-fedora</a>\n</li><li>Scripts to build on a clean install of Windows: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> and <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-cygwin'>prism-install-cygwin</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='windows' id='windows'></a>\n<a name='windows64' id='windows64'></a>\n</p><h3>Installation on Windows</h3>\n<p>If you don't yet have <strong>Java</strong>, install it, for example with the <a class='urllink' href='https://adoptium.net/temurin/releases'>Temurin installer</a>.\n</p>\n<p class='vspace'>To install PRISM on Windows, just run the self-extracting installer which you <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>downloaded</a>. You do <strong>not</strong> need administrator privileges for this, just write-access to the directory chosen for installation.\n</p>\n<p class='vspace'>If requested, the installer will place shortcuts to run PRISM on the desktop and/or start menu. If not, you can run by PRISM double-clicking the file <code>xprism.bat</code> (which may just appear as <code>xprism</code>) in the <code>bin</code> folder of your PRISM folder. If nothing happens, the most likely explanation is that Java is not installed or not in your path. To check, open a command prompt window, navigate to the PRISM directory, type <code>cd bin</code>, then <code>xprism.bat</code> and examine the resulting error. If you want to create shortcuts to <code>xprism.bat</code> manually, you will find some PRISM icons in the <code>etc</code> folder.\n</p>\n<p class='vspace'>If you wish to use the command-line version of PRISM on Windows, open a command prompt window and type for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd \"c:\\Program Files\\prism-4.8-win\\bin\"</span><br/>\n<span style=\"font-weight:bold;\">prism ..\\prism-examples\\simple\\dice\\dice.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n    \n<p class='vspace'>You can also edit the file <code>bin\\prism.bat</code> to allow it to be run from any location. See the instructions within the file for further details.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='binaries' id='binaries'></a>\n</p><h3>Installation of Linux/Mac binary versions</h3>\n<p>We provide pre-compiled <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>binary distributions</a> for Linux and macOS\n(if you have any problems running these, try compiling PRISM from source instead - see below for instructions).\nTo install a binary distribution, unpack the tarred/zipped PRISM distribution into a suitable location, enter the directory and run the <code>install.sh</code> script, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-linux64-x86.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-linux64-x86</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>On macOS, you may want to run the following command,\nwhich avoids <a class='urllink' href='https://support.apple.com/en-gb/102445'>manual approving</a> the integrity of the binary files:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You do not need to be root to install PRISM. The install script simply makes some small customisations to the scripts used to launch PRISM. The PRISM distribution is self-contained and can be freely moved/renamed, however if you do so you will need to re-run <code>./install.sh</code> afterwards.\n</p>\n<p class='vspace'>To run PRISM, execute either the <code>xprism</code> or <code>prism</code> script (for the graphical user interface or command-line version, respectively). These can be found in the <code>bin</code> directory. These scripts are designed to be run from anywhere and you can easily create symbolic links or aliases to them. If you want icons to create desktop shortcuts to PRISM, you can find some in the <code>etc</code> directory.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='source' id='source'></a>\n</p><h3>Building PRISM from source (non-Windows)</h3>\n<p>To compile PRISM form source code, you will need:\n</p>\n<div class='vspace'></div><ul><li>GNU make (sometimes called gmake)\n</li><li>a C/C++ compiler (e.g. gcc/g++)\n</li><li>a Java Development Kit, version 11 or above\n</li></ul><p class='vspace'>To check that you have the development kit, type <code>javac</code>. If you get an error message that <code>javac</code> cannot be found, you probably do not have the JDK installed (or your path is not set up correctly). To check what version you have, type <code>javac -version</code>. \n</p>\n<p class='vspace'>Hopefully, you can build PRISM simply by entering the PRISM directory and running <code>make</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-src.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-src/prism</span><br/>\n<span style=\"font-weight:bold;\">make</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For this process to complete correctly, PRISM needs to be able to determine your operating system (<code>OSTYPE</code>), machine architecture (<code>ARCH</code>) and the location of your Java distribution (<code>JAVA_DIR</code>). If there is a problem with either of these, you will see an error message and will need to specify one or more of these manually, such as in these examples:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">  </span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux ARCH=aarch64</span><br/>\n<span style=\"font-weight:bold;\">make JAVA_DIR=/usr/java/jdk1.8.0</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin JAVA_DIR=\"/cygdrive/c/Program Files/Java/jdk1.8.0\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of double quotes for the case where the directory contains a space. If you don't know the location of your Java installation, try typing <code>which javac</code>. If the result is e.g. <code>/usr/java/jdk1.8.0/bin/javac</code> then your Java directory is <code>/usr/java/jdk1.8.0</code>. Sometimes <code>javac</code> will be a symbolic link, in which case use \"<code>ls -l</code>\" to determine the actual location.\n</p>\n<p class='vspace'>It is also possible to to set the environment variables directly or edit their values in the Makefile directly. Note that even when you specify <code>JAVA_DIR</code> explicitly (in either way), PRISM still uses the version of <code>javac</code> that is in your path. To override this, you can also specify a specific version by setting <code>JAVAC</code>.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='cygwin' id='cygwin'></a>\n</p><h3>Building PRISM from source on Windows using Cygwin</h3>\n<p>The compilation of PRISM currently relies on a Unix-like environment. On Windows, this can be achieved using the <a class='urllink' href='http://www.cygwin.com/'>Cygwin</a> development environment, with the packages below installed.\nYou can run the script <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> in a Command Prompt to automate this.\n</p><ul><li><code>make</code>\n</li><li><code>mingw64-x86_64-gcc-g++</code> (for 64-bit Windows) or <code>mingw64-i686-gcc-g++</code> (for 32-bit Windows)\n</li><li><code>binutils</code>\n</li><li><code>dos2unix</code>\n</li><li><code>git</code> (if you will pull source code from GitHub)\n</li><li><code>wget</code> (if you will pull source code from the web)\n</li></ul><p>Then proceed as described in the previous section. Note that the PRISM compilation process uses the <a class='urllink' href='http://www.mingw.org/'>MinGW</a> libraries so that the final result is independent of Cygwin at run-time.\n</p>\n<p class='vspace'>One thing to note: make sure you unzip the PRISM distribution from within Cygwin (e.g. using <code>tar xfz prism-XXX-src.tar.gz</code>). Don't use a Windows program (Winzip, etc.) since this can cause problems.\n</p>\n<p class='vspace'>If you use git to checkout the PRISM repository, we recommend that you use the version of git provided by Cygwin.\nIf you use a native Windows version of git, you may want to disable the Unix-to-Windows line-ending conversion, e.g., via\n</p>\n<div class='vspace'></div><ul><li><code>git config --global core.autocrlf false</code>\n</li></ul><p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='msys' id='msys'></a>\n</p><h3>Building PRISM from source on Windows using MSYS2</h3>\n<p>An alternative to Cygwin on Windows is <a class='urllink' href='https://www.msys2.org/'>MSYS2</a>.\nYou can install the required MSYS2 packages like this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">pacman -S make mingw-w64-x86_64-gcc binutils dos2unix git wget unzip python nano</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The environment is currently not directly supported in the Makefile,\nwhich can be fixed as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Additionally, MSYS2 does not handle symlinks in the same way as Cygwin does.\nAt some point <code>make</code> will fail, saying that it cannot find the CUDD library.\nYou can solve this as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd ../cudd/</span><br/>\n<span style=\"font-weight:bold;\">rmdir lib/ </span><br/>\n<span style=\"font-weight:bold;\">./setup.sh</span><br/>\n<span style=\"font-weight:bold;\">cd ../prism</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/InstallingPRISM/Instructions?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='InstallingPRISM/Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='InstallingPRISM/Instructions@action=edit.html'>Edit</a> - <a class='wikilink' href='InstallingPRISM/Instructions@action=print.html'>Print</a> - <a class='wikilink' href='Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='InstallingPRISM/Instructions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:57 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='InstallingPRISM/Main.html'>Installing PRISM</a></strong>\n</p><ul><li><a class='selflink' href='InstallingPRISM/Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><p>[ <a class='wikilink' href='InstallingPRISM/AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/AllOnOnePage.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Real-time Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for xml\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.xml .de1, .xml .de2 {font-family: monospace; font-weight: normal;}\n.xml  {font-family:monospace;}\n.xml .imp {font-weight: bold; color: red;}\n.xml li, .xml .li1 {font-family: monospace; color: black; font-weight: normal;}\n.xml .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.xml .li2 {font-weight: bold;}\n.xml .es0 {color: #000099; font-weight: bold;}\n.xml .br0 {color: #66cc66;}\n.xml .sy0 {color: #66cc66;}\n.xml .st0 {color: #ff0000;}\n.xml .nu0 {color: #cc66cc;}\n.xml .sc-1 {color: #808080; font-style: italic;}\n.xml .sc0 {color: #00bbdd;}\n.xml .sc1 {color: #ddbb00;}\n.xml .sc2 {color: #339933;}\n.xml .sc3 {color: #009900;}\n.xml .re0 {color: #000066;}\n.xml .re1 {color: #000000; font-weight: bold;}\n.xml .re2 {color: #000000; font-weight: bold;}\n.xml .ln-xtra, .xml li.ln-xtra, .xml div.ln-xtra {background-color: #ffc;}\n.xml span.xtra { display:block; }\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>PRISM Manual</span> &nbsp; version 4.10.1</h1>\n<hr />\n<h1><span class='big'>Contents</span></h1>\n<hr />\n<h1><a class='wikilink' href='Introduction.html'>Introduction</a></h1>\n<div class='vspace'></div><h1><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a></h1>\n<ul><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a></h1>\n<ul><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a></h1>\n<ul><li><a class='wikilink' href='../PropertySpecification/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../PropertySpecification/IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='../PropertySpecification/ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='../PropertySpecification/TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='../PropertySpecification/PropertiesFiles.html'>Properties Files</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a></h1>\n<ul><li><a class='wikilink' href='../RunningPRISM/Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='../RunningPRISM/LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='../RunningPRISM/SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a></h1>\n<ul><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Other Options</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='References.html'>References</a></h1>\n<div class='vspace'></div><h1><a class='wikilink' href='../Appendices/Main.html'>Appendices</a></h1>\n<ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p><br /><br />\n</p><hr />\n<h1><span class='big'>Introduction</span></h1>\n<hr />\n<p>PRISM is a <em>probabilistic model checker</em>,\na tool for the modelling and analysis of systems which exhibit probabilistic behaviour.\nProbabilistic model checking is a <em>formal verification</em> technique.\nIt is based on the construction of a precise mathematical model of a system which is to be analysed.\nProperties of this system are then expressed formally in temporal logic\nand automatically analysed against the constructed model.\n</p>\n<p class='vspace'>PRISM has support for a wide range of probabilistic models:\n</p>\n<div class='vspace'></div><ul><li>discrete-time Markov chains (DTMCs)\n</li><li>continuous-time Markov chains (CTMCs)\n</li><li>Markov decision processes (MDPs)\n</li><li>probabilistic timed automata (PTAs)\n</li><li>partially observable Markov decision processes (POMDPs)\n</li><li>partially observable probabilistic timed automata (POPTAs)\n</li></ul><p class='vspace'>In fact, PRISM's support for MDPs extends to the more general model of \nprobabilistic automata (PAs) [<a class='wikilink' href='References.html#Seg95'>Seg95</a>], which does not require unique action names in each state.\nFor background material on these models, look at the pointers to\n<a class='urllink' href='http://www.prismmodelchecker.org/about.php'>resources</a>\non the PRISM web site.\n</p>\n<p class='vspace'>PRISM also supports non-probabilistic models, notably labelled transition systems (LTSs).\n</p>\n<p class='vspace'>Models are supplied to the tool by writing descriptions in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM language</a>, a simple, high-level modelling language.\n</p>\n<p class='vspace'>Properties of these models are written in the PRISM <a class='wikilink' href='../PropertySpecification/Main.html'>property specification language</a> which is based on temporal logic. It incorporates several well-known probabilistic temporal logics:\n</p>\n<div class='vspace'></div><ul><li>PCTL (probabilistic computation tree logic),\n</li><li>CSL (continuous stochastic logic),\n</li><li>(probabiistic) LTL (linear time logic),\n</li><li>PCTL* (which subsumes both PCTL and LTL).\n</li></ul><p class='vspace'>The property language also supports <a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>costs and rewards</a>, \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>numerical</a>\" properties, several other custom features and extensions, and also also incorporates the non-probabilistic temporal logics CTL (computation tree logic) and LTL.\n</p>\n<p class='vspace'>PRISM performs probabilistic model checking, based on exhaustive search and numerical solution, to automatically analyse such properties. It also contains a <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>discrete-event simulation</a> engine for <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a>.\n<br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Installing PRISM</span></h1>\n<hr />\n<h1>Instructions</h1>\n<h3>Prerequisites</h3>\n<p>PRISM is known to run on Linux, Windows and macOS, both 64-bit and 32-bit versions.\n</p>\n<p class='vspace'>You will need <strong>Java</strong>, version 11 or above.\nTo run binary versions of PRISM, you only need the Java Runtime Environment (JRE), not the full Java Development Kit (JDK).\n</p>\n<p class='vspace'>To compile PRISM from source, you need the Java Development Kit (JDK), GNU make and a C/C++ compiler (e.g. gcc/g++). For compilation under Windows, you will need Cygwin. See below for more information:\n</p>\n<div class='vspace'></div><ul><li><a href='AllOnOnePage.html#windows'>Installation on Windows</a>\n</li><li><a href='AllOnOnePage.html#binaries'>Installation of Linux/Mac binary versions</a>\n</li><li><a href='AllOnOnePage.html#source'>Building PRISM from source (non-Windows)</a>\n</li><li><a href='AllOnOnePage.html#cygwin'>Building PRISM from source on Windows using Cygwin</a>\n</li><li><a href='AllOnOnePage.html#msys'>Building PRISM from source on Windows using MSYS2</a>\n</li></ul><p class='vspace'>If you are installing on a completely fresh operating system installation (e.g. in a virtual machine), you may find the following scripts useful,\nwhich install the required dependencies and PRISM itself. They can be found in the <code>prism/etc/scripts</code> directory:\n</p>\n<div class='vspace'></div><ul><li>Script to build on a clean install of Ubuntu: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-ubuntu'>prism-install-ubuntu</a>\n</li><li>Script to build on a clean install of Fedora-based Linux (e.g. Amazon Linux): <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-fedora'>prism-install-fedora</a>\n</li><li>Scripts to build on a clean install of Windows: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> and <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-cygwin'>prism-install-cygwin</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='windows' id='windows'></a>\n<a name='windows64' id='windows64'></a>\n</p><h3>Installation on Windows</h3>\n<p>If you don't yet have <strong>Java</strong>, install it, for example with the <a class='urllink' href='https://adoptium.net/temurin/releases'>Temurin installer</a>.\n</p>\n<p class='vspace'>To install PRISM on Windows, just run the self-extracting installer which you <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>downloaded</a>. You do <strong>not</strong> need administrator privileges for this, just write-access to the directory chosen for installation.\n</p>\n<p class='vspace'>If requested, the installer will place shortcuts to run PRISM on the desktop and/or start menu. If not, you can run by PRISM double-clicking the file <code>xprism.bat</code> (which may just appear as <code>xprism</code>) in the <code>bin</code> folder of your PRISM folder. If nothing happens, the most likely explanation is that Java is not installed or not in your path. To check, open a command prompt window, navigate to the PRISM directory, type <code>cd bin</code>, then <code>xprism.bat</code> and examine the resulting error. If you want to create shortcuts to <code>xprism.bat</code> manually, you will find some PRISM icons in the <code>etc</code> folder.\n</p>\n<p class='vspace'>If you wish to use the command-line version of PRISM on Windows, open a command prompt window and type for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd \"c:\\Program Files\\prism-4.8-win\\bin\"</span><br/>\n<span style=\"font-weight:bold;\">prism ..\\prism-examples\\simple\\dice\\dice.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n    \n<p class='vspace'>You can also edit the file <code>bin\\prism.bat</code> to allow it to be run from any location. See the instructions within the file for further details.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='binaries' id='binaries'></a>\n</p><h3>Installation of Linux/Mac binary versions</h3>\n<p>We provide pre-compiled <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>binary distributions</a> for Linux and macOS\n(if you have any problems running these, try compiling PRISM from source instead - see below for instructions).\nTo install a binary distribution, unpack the tarred/zipped PRISM distribution into a suitable location, enter the directory and run the <code>install.sh</code> script, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-linux64-x86.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-linux64-x86</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>On macOS, you may want to run the following command,\nwhich avoids <a class='urllink' href='https://support.apple.com/en-gb/102445'>manual approving</a> the integrity of the binary files:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You do not need to be root to install PRISM. The install script simply makes some small customisations to the scripts used to launch PRISM. The PRISM distribution is self-contained and can be freely moved/renamed, however if you do so you will need to re-run <code>./install.sh</code> afterwards.\n</p>\n<p class='vspace'>To run PRISM, execute either the <code>xprism</code> or <code>prism</code> script (for the graphical user interface or command-line version, respectively). These can be found in the <code>bin</code> directory. These scripts are designed to be run from anywhere and you can easily create symbolic links or aliases to them. If you want icons to create desktop shortcuts to PRISM, you can find some in the <code>etc</code> directory.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='source' id='source'></a>\n</p><h3>Building PRISM from source (non-Windows)</h3>\n<p>To compile PRISM form source code, you will need:\n</p>\n<div class='vspace'></div><ul><li>GNU make (sometimes called gmake)\n</li><li>a C/C++ compiler (e.g. gcc/g++)\n</li><li>a Java Development Kit, version 11 or above\n</li></ul><p class='vspace'>To check that you have the development kit, type <code>javac</code>. If you get an error message that <code>javac</code> cannot be found, you probably do not have the JDK installed (or your path is not set up correctly). To check what version you have, type <code>javac -version</code>. \n</p>\n<p class='vspace'>Hopefully, you can build PRISM simply by entering the PRISM directory and running <code>make</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-src.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-src/prism</span><br/>\n<span style=\"font-weight:bold;\">make</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For this process to complete correctly, PRISM needs to be able to determine your operating system (<code>OSTYPE</code>), machine architecture (<code>ARCH</code>) and the location of your Java distribution (<code>JAVA_DIR</code>). If there is a problem with either of these, you will see an error message and will need to specify one or more of these manually, such as in these examples:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">  </span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux ARCH=aarch64</span><br/>\n<span style=\"font-weight:bold;\">make JAVA_DIR=/usr/java/jdk1.8.0</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin JAVA_DIR=\"/cygdrive/c/Program Files/Java/jdk1.8.0\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of double quotes for the case where the directory contains a space. If you don't know the location of your Java installation, try typing <code>which javac</code>. If the result is e.g. <code>/usr/java/jdk1.8.0/bin/javac</code> then your Java directory is <code>/usr/java/jdk1.8.0</code>. Sometimes <code>javac</code> will be a symbolic link, in which case use \"<code>ls -l</code>\" to determine the actual location.\n</p>\n<p class='vspace'>It is also possible to to set the environment variables directly or edit their values in the Makefile directly. Note that even when you specify <code>JAVA_DIR</code> explicitly (in either way), PRISM still uses the version of <code>javac</code> that is in your path. To override this, you can also specify a specific version by setting <code>JAVAC</code>.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='cygwin' id='cygwin'></a>\n</p><h3>Building PRISM from source on Windows using Cygwin</h3>\n<p>The compilation of PRISM currently relies on a Unix-like environment. On Windows, this can be achieved using the <a class='urllink' href='http://www.cygwin.com/'>Cygwin</a> development environment, with the packages below installed.\nYou can run the script <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> in a Command Prompt to automate this.\n</p><ul><li><code>make</code>\n</li><li><code>mingw64-x86_64-gcc-g++</code> (for 64-bit Windows) or <code>mingw64-i686-gcc-g++</code> (for 32-bit Windows)\n</li><li><code>binutils</code>\n</li><li><code>dos2unix</code>\n</li><li><code>git</code> (if you will pull source code from GitHub)\n</li><li><code>wget</code> (if you will pull source code from the web)\n</li></ul><p>Then proceed as described in the previous section. Note that the PRISM compilation process uses the <a class='urllink' href='http://www.mingw.org/'>MinGW</a> libraries so that the final result is independent of Cygwin at run-time.\n</p>\n<p class='vspace'>One thing to note: make sure you unzip the PRISM distribution from within Cygwin (e.g. using <code>tar xfz prism-XXX-src.tar.gz</code>). Don't use a Windows program (Winzip, etc.) since this can cause problems.\n</p>\n<p class='vspace'>If you use git to checkout the PRISM repository, we recommend that you use the version of git provided by Cygwin.\nIf you use a native Windows version of git, you may want to disable the Unix-to-Windows line-ending conversion, e.g., via\n</p>\n<div class='vspace'></div><ul><li><code>git config --global core.autocrlf false</code>\n</li></ul><p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='msys' id='msys'></a>\n</p><h3>Building PRISM from source on Windows using MSYS2</h3>\n<p>An alternative to Cygwin on Windows is <a class='urllink' href='https://www.msys2.org/'>MSYS2</a>.\nYou can install the required MSYS2 packages like this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">pacman -S make mingw-w64-x86_64-gcc binutils dos2unix git wget unzip python nano</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The environment is currently not directly supported in the Makefile,\nwhich can be fixed as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Additionally, MSYS2 does not handle symlinks in the same way as Cygwin does.\nAt some point <code>make</code> will fail, saying that it cannot find the CUDD library.\nYou can solve this as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd ../cudd/</span><br/>\n<span style=\"font-weight:bold;\">rmdir lib/ </span><br/>\n<span style=\"font-weight:bold;\">./setup.sh</span><br/>\n<span style=\"font-weight:bold;\">cd ../prism</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p><hr />\n<h1>Common Problems And Questions</h1>\n<p>This section describes some of the most common problems and questions related to the installation and running of PRISM. These are grouped into the following categories:\n</p>\n<div class='vspace'></div><ul><li>Running PRISM on Windows\n</li><li>Running PRISM on non-Windows platforms\n</li><li>Compiling PRISM\n</li><li>Other issues\n</li></ul><div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on Windows</h2>\n<p><strong>When I try to run PRISM on Windows, I double-click the PRISM shortcut but nothing happens.</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>The most common cause of this is that you either do not have Java installed or the <code>java</code> executable is not in your path. In any case, to determine the exact problem, launch a command shell and navigate to the <code>bin</code> directory inside the directory where you installed PRISM (you can use the \"PRISM (console)\" shortcut installed in the start menu to do this). Then, type <code>prism.bat</code> and see what error message is displayed.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on non-Windows platforms</h2>\n<p><strong>When I try to run PRISM, I get one of these errors:</strong><br />\n</p><ul><li><strong><code>Exception in thread \"main\" java.lang.NoClassDefFoundError: ...</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: no prism in java.library.path</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: ...<br />Library not loaded: ../../lib/libdd.dylib</code></strong>\n</li></ul><div class='vspace'></div><div class='answer' > \n<p>Things to check:\n</p>\n<p class='vspace'>(1) Did you run <code>install.sh</code> from the PRISM directory? (non-Windows platforms)\n</p>\n<p class='vspace'>(2) If you compiled PRISM from source code, are you sure no errors occurred during the process? To check, go into the PRISM directory, type <code>make clean_all</code> and then <code>make</code>, checking the output (especially at the end) carefully for any error messages.\n</p>\n<p class='vspace'>(3) Are you running on Mac OS? See the next question.\n</p>\n<p class='vspace'>(3) Are you running on an old version of Mac OS (notably El Capitan)? This had some issues with PRISM calling <code>java</code>.\nA workaround is to specify the exact path to the <code>java</code> when running PRISM, e.g.:\n</p>\n<p class='vspace'><code>PRISM_JAVA=/Library/Java/JavaVirtualMachines/jdk1.9.jdk/Contents/Home/bin/java prism</code>\n</p>\n<p class='vspace'>or by replacing the value of PRISM_JAVA directly in the prism script\ndirectly.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM on macOS, I get an error of the form: \"<code>libprism.dylib</code> cant be opened because Apple cannot check it for malicious software.\" or \"<code>libprism.dylib not valid for use in process: library load disallowed by system policy</code>\".</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM's macOS binaries are currently not signed/notarised,\nso you need to approve the binary files manually to run them.\nRun this command from the same place you ran <code>./install.sh</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or approve the libraries one by one through the\n<a class='urllink' href='https://support.apple.com/en-gb/102445'>security settings</a>.\n</p>\n<p class='vspace'>You can also avoid this issue by compiling from source code.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM, I get an error of the form:<br /><code>Exception in thread \"main\" java.lang.UnsupportedClassVersionError: Bad version number in .class file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Your version of Java is too old. Update or install a newer version of Java, and then try again.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Compiling PRISM</h2>\n<p><strong>When I try to compile PRISM, <code>make</code> seems to get stuck in an infinite loop</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>This is probably due to the detection of Java failing. Specify the location of your Java directory by hand, e.g. <code>make JAVA_DIR=/usr/java/jdk1.9.0</code>. See the <a class='wikilink' href='../InstallingPRISM/Main.html'>Instructions</a> page for more on this.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>/usr/bin/libtool: for architecture: cputype (16777234) cpusubtype (0) file: -lSystem is not an object file (not allowed in a library)</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you compiling PRISM on Max OS X? If so, the likely explanation is that you have upgraded to a new version of Mac OS X but have not upgraded the developer tools (eg. XCode). Upgrade and try again.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, nothing seems to happen</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>Unexpected end of line seen...</code><br />or:<br /><code>make: Fatal error in reader: Makefile, line 58: Unexpected end of line seen...</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>./setup.sh: line 33: syntax error: unexpected end of file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you building on Cygwin? And did you unpack PRISM using WinZip? If so, unpack from Cygwin, using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>Assembler messages:  Fatal error: can't create ../../obj/dd/dd_abstr.o: No such file or directory</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Did you unpack PRISM using a graphical tool or file manager? If so, unpack using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>Do I have to use GNU <code>make</code> to build PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Strictly speaking, no, but you will have to modify the various PRISM Makefiles manually to overcome this.\n</p></div>\n<p class='vspace'><strong>Can I build PRISM on operating systems other than those currently supported?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM should be suitable for any Unix/Linux variant.\n</p>\n<p class='vspace'>The first thing you will need to do is compile CUDD (the BDD library used by and included in PRISM) on that platform.\nFortunately, CUDD has already been successfully built on a large number of\noperating systems. Have a look at the sample Makefiles we provide (i.e. the\nfiles <code>cudd/Makefile.*</code>) which are slight variants of the original Makefile\nprovided with CUDD (found here: <code>cudd/modified/orig/Makefile</code>). They contain\ninstructions on how to modify it for various platforms. You can then call\nyour new modified makefile something appropriate (<code>cudd/Makefile.$OSTYPE</code>) and\nproceed to build PRISM as usual. To just build CUDD, not PRISM, type\n<code>make cuddpackage</code> instead of <code>make</code>.\n</p>\n<p class='vspace'>Next, look at the main PRISM Makefile, in particular, each place where the\nvariable <code>$OSTYPE</code> is referred to. Most lines include comments and further\ninstructions. Once you have done this, proceed as usual.\n</p>\n<p class='vspace'>If you do successfully build PRISM on other platforms, please let us know\nso we can include this information in future releases. Thanks.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Other issues</h2>\n<p><strong>How do I uninstall PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>If you installed PRISM on Windows using the self-extracting installer, you can uninstall it using the option on the start menu. If you didn't add these shortcuts, just run <code>uninstall.exe</code> from the directory where you installed PRISM.\n</p>\n<p class='vspace'>For older versions of PRISM on Windows or on any other platform, simply delete the directory containing it.\n</p>\n<p class='vspace'>The only thing that is not removed via either of these methods is the <code>.prism</code> file containing your PRISM settings which is in your home directory (see the section \"<a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\"). You may wish to retain this when upgrading.\n</p></div>\n<p class='vspace'><strong>I still have a problem installing/running PRISM. What can I do?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Please post a message in the discussion group (see the <a class='urllink' href='http://www.prismmodelchecker.org/support.php'>support</a> section of the PRISM website).\n</p></div>\n<p><br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>The PRISM Language</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>In order to construct and analyse a model with PRISM,\nit must be specified in the PRISM language,\na simple, state-based language,\nbased on the Reactive Modules formalism of Alur and Henzinger [<a class='wikilink' href='References.html#AH99'>AH99</a>].\nThis is used for <a class='wikilink' href='Introduction.html'>all of the types of model</a> that PRISM supports.\n</p>\n<p class='vspace'>In this section, we describe the PRISM language and present a number of small illustrative examples.\nA precise definition of the semantics of the language is available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site. One of the best ways to learn what can be done with the PRISM language is to look at some existing examples.\nA number of these are included with the tool distribution in the <code>prism-examples</code> directory.\nMany additional examples can be found on the \"<a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a>\" section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<p class='vspace'>The fundamental components of the PRISM language are <em>modules</em> and <em>variables</em>.\nA model is composed of a number of <em>modules</em> which can interact with each other.\nA module contains a number of local <em>variables</em>.\nThe values of these variables at any given time constitute the state of the module.\nThe <em>global state</em> of the whole model is determined by the <em>local state</em> of all modules.\nThe behaviour of each module is described by a set of <em>commands</em>.\nA command takes the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[<span class=\"prismident\">action</span>] <span class=\"prismident\">guard</span> -&gt; <span class=\"prismident\">prob_1</span> : <span class=\"prismident\">update_1</span> + ... + <span class=\"prismident\">prob_n</span> : <span class=\"prismident\">update_n</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <em>guard</em> is a predicate over all the variables in the model (including those belonging to other modules). Each <em>update</em> describes a transition which the module can make if the guard is true. A transition is specified by giving the new values of the variables in the module, possibly as a function of other variables. Each update is assigned a probability (or in some cases a rate) which will be assigned to the corresponding transition. The command also optionally includes an <em>action</em>, either just to annotate it, or for <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation</a>.\n</p><hr />\n<h1>Example 1</h1>\n<p>We will use the following simple example to illustrate the basic concepts of the PRISM language.\nConsider a system comprising two identical processes which must operate under mutual exclusion.\nEach process can be in one of 3 states: {0,1,2}.\nFrom state 0, a process will move to state 1 with probability 0.2\nand remain in the same state with probability 0.8.\nFrom state 1, it tries to move to the critical section: state 2.\nThis can only occur if the other process is not in its critical section.\nFinally, from state 2, a process will either remain there or move back to state 0\nwith equal probability.\nThe PRISM code to describe an MDP model of this system can be seen below.\nIn the next sections, we explain each aspect of the code in turn.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 1</span><br/>\n<span class=\"prismcomment\">// Two process mutual exclusion</span><br/>\n<br/>\n<span class=\"prismkeyword\">mdp</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M1</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">y</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 1</strong>\n</p><hr />\n<h1>Model Type</h1>\n<p>As mentioned above, the PRISM language can be used to describe several types of probabilistic models.\nTo indicate which type is being described, a PRISM model usually includes a model type keyword:\n</p>\n<div class='vspace'></div><ul><li><code><strong>dtmc</strong></code>: discrete-time Markov chain\n</li><li><code><strong>ctmc</strong></code>: continuous-time Markov chain\n</li><li><code><strong>mdp</strong></code>: Markov decision process (or probabilistic automaton)\n</li><li><code><strong>pta</strong></code>: probabilistic timed automaton\n</li><li><code><strong>pomdp</strong></code>: partially observable Markov decision process\n</li><li><code><strong>popta</strong></code>: partially observable probabilistic timed automaton\n</li></ul><p class='vspace'>This is typically at the very start of the file,\nbut can actually occur anywhere in the file (except inside modules and other declarations).\n</p>\n<p class='vspace'>If no such model type declaration is included, the model is by default assumed to be an MDP.\nPRISM also performs some auto-detection of the model type;\nfor example, an MDP with <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>clock variables</a> is assumed to be a PTA,\nand an MDP with <a class='createlinktext' rel='nofollow'\n    href='../ThePRISMLanguage/POMDPs@action=edit.html'>observables</a><a rel='nofollow' \n    class='createlink' href='../ThePRISMLanguage/POMDPs@action=edit.html'>?</a> is assumed to be a POMDP.\n</p>\n<p class='vspace'><strong>Note:</strong> For compatibility with old versions of PRISM,\nthe keywords <code><strong>probabilistic</strong></code>, <code><strong>stochastic</strong></code> and <code><strong>nondeterministic</strong></code>\ncan be used as alternatives for <code><strong>dtmc</strong></code>, <code><strong>ctmc</strong></code> and <code><strong>mdp</strong></code>, respectively.\n</p>\n<div class='vspace'></div><hr />\n<h1>Modules And Variables</h1>\n<p>The <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>previous example</a> uses two modules, <code>M1</code> and <code>M2</code>, one representing each process.\nA module is specified as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">name</span> ... <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The definition of a module contains two parts: its <em>variables</em> and its <em>commands</em>.\nThe variables describe the possible states that the module can be in;\nthe <a class='wikilink' href='../ThePRISMLanguage/Commands.html'>commands</a> describe its behaviour, i.e. the way in which the state changes over time.\nCurrently, PRISM supports just a few simple types of variables:\nthey can either be (finite ranges of) integers or Booleans\n(we ignore <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>clocks</a> for now).\n</p>\n<p class='vspace'>In the example above, each module has one integer variable with range <code>[0..2]</code>.\nA variable declaration looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the initial value of the variable is also specified.\nA Boolean variable is declared as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">false</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It is also possible to omit the initial value of a variable,\nin which case it is assumed to be the lowest value in the range (or <code>false</code> for a Boolean).\nThus, the variable declarations shown below are equivalent to the ones above.\nAs will be described later, it is also possible to specify\n<a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>multiple initial states</a> for a model.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>];<br/>\n<span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We also mention that, for a few kinds of model analysis (typically those based on simulation, such as <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a> or <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#fau'>fast adaptive simulation</a>, it is also permissable to use integer variables with unbounded ranges, denoted as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : <span class=\"prismkeyword\">int</span>;<br/>\n<span class=\"prismident\">y</span> : <span class=\"prismkeyword\">int</span> <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">3</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Where the state space of the model remains finite, despite the presence of such unbounded variables, you can use the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>explicit engine</a> to build and analyse the model.\n</p>\n<div class='vspace'></div><h3>Identifiers</h3>\n<p>The names given to modules and variables are referred to as <em>identifiers</em>.\nIdentifiers can be made up of letters, digits and the underscore character, but cannot begin with a digit,\ni.e. they must satisfy the regular expression [A-Za-z_][A-Za-z0-9_]*, and are case-sensitive.\nFurthermore, identifiers cannot be any of the following, which are all reserved keywords in PRISM:\n<code><strong>A</strong></code>,\n<code><strong>bool</strong></code>,\n<code><strong>clock</strong></code>,\n<code><strong>const</strong></code>,\n<code><strong>ctmc</strong></code>,\n<code><strong>C</strong></code>,\n<code><strong>double</strong></code>,\n<code><strong>dtmc</strong></code>,\n<code><strong>E</strong></code>,\n<code><strong>endinit</strong></code>,\n<code><strong>endinvariant</strong></code>,\n<code><strong>endmodule</strong></code>,\n<code><strong>endobservables</strong></code>,\n<code><strong>endrewards</strong></code>,\n<code><strong>endsystem</strong></code>,\n<code><strong>false</strong></code>,\n<code><strong>formula</strong></code>,\n<code><strong>filter</strong></code>,\n<code><strong>func</strong></code>,\n<code><strong>F</strong></code>,\n<code><strong>global</strong></code>,\n<code><strong>G</strong></code>,\n<code><strong>init</strong></code>,\n<code><strong>invariant</strong></code>,\n<code><strong>I</strong></code>,\n<code><strong>int</strong></code>,\n<code><strong>label</strong></code>,\n<code><strong>max</strong></code>,\n<code><strong>mdp</strong></code>,\n<code><strong>min</strong></code>,\n<code><strong>module</strong></code>,\n<code><strong>X</strong></code>,\n<code><strong>nondeterministic</strong></code>,\n<code><strong>observable</strong></code>,\n<code><strong>observables</strong></code>,\n<code><strong>of</strong></code>,\n<code><strong>Pmax</strong></code>,\n<code><strong>Pmin</strong></code>,\n<code><strong>P</strong></code>,\n<code><strong>pomdp</strong></code>,\n<code><strong>popta</strong></code>,\n<code><strong>probabilistic</strong></code>,\n<code><strong>prob</strong></code>,\n<code><strong>pta</strong></code>,\n<code><strong>rate</strong></code>,\n<code><strong>rewards</strong></code>,\n<code><strong>Rmax</strong></code>,\n<code><strong>Rmin</strong></code>,\n<code><strong>R</strong></code>,\n<code><strong>S</strong></code>,\n<code><strong>stochastic</strong></code>,\n<code><strong>system</strong></code>,\n<code><strong>true</strong></code>,\n<code><strong>U</strong></code>,\n<code><strong>W</strong></code>.\n</p><hr />\n<h1>Commands</h1>\n<p>The behaviour of each module is described by <em>commands</em>,\ncomprising a <em>guard</em> and one or more <em>updates</em>.\nThe first command of module <code>M1</code> in our <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>example</a> is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The guard <code>x=0</code> indicates that this describes the behaviour of the module when the variable <code>x</code> has value 0.\nThe updates <code>(x'=0)</code> and <code>(x'=1)</code> and their associated probabilities state that the value of <code>x</code> will\nremain at 0 with probability 0.8 and change to 1 with probability 0.2.\nNote that the inclusion of updates in parentheses, e.g. <code>(x'=1)</code>, is essential.\nWhile older versions of PRISM did not report the absence of parentheses as an error, newer versions do.\nNote also that PRISM will complain if the probabilities on the right hand side of a command do not sum to one.\n</p>\n<p class='vspace'>The second command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>illustrates that guards can contain constraints on any variable, not just the ones in that module,\ni.e. the behaviour of one module can depend on the state of another.\nUpdates, however, can only specify values for variables belonging to the module.\nIn general a module can <em>read</em> the variables of any other module, but only <em>write</em> to its own.\nWhen a command comprises a single update with probability 1, the <code>1.0:</code> can be omitted,\nas is done in the example above.\n</p>\n<p class='vspace'>If a module has more than one variable, updates describe the new value for each of them.\nFor example, if it had two variables <code>x1</code> and <code>x2</code>, a possible command would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&lt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>+<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that elements of the updates are concatenated with <code>&amp;</code> and that each element must be bracketed individually.\nIf an update does not give a new value for a local variable, it is assumed not to change.\nAs a special case, the keyword <code><strong>true</strong></code> can be used to denote an update where no variable's value changes, i.e. the following are all equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Finally, it is important to remember that the expressions on the right hand side of each update refer to the state of the model <em>before</em> the update occurs. So, for example, this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>=<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x1</span>) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>updates variable <code>x2</code> to 0, not 2.\n</p>\n<div class='vspace'></div><hr />\n<h1>Parallel Composition</h1>\n<p>The probabilistic model corresponding to a PRISM language description is constructed as the <em>parallel composition</em> of its modules. In every state of the model, there is a set of commands (belonging to any of the modules) which are enabled, i.e. whose guards are satisfied in that state. The choice between which command is performed (i.e. the <em>scheduling</em>) depends on the model type.\n</p>\n<p class='vspace'>For an MDP, as in <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>, the choice is <em>nondeterministic</em>. By way of example, consider state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>). There are two commands enabled, one from each module:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In state <code>(0,0)</code> of the MDP, there would be a nondeterministic choice between these two probability distributions:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.2:(1,0)</code> (module <code>M1</code> moves)\n</li><li><code>0.8:(0,0) + 0.2:(0,1)</code> (module <code>M2</code> moves)\n</li></ul><p class='vspace'>For a DTMC, the choice is <em>probabilistic</em>: each enabled command is selected with equal probability.\nIf <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a> was a DTMC, then in state <code>(0,0)</code> of the model\nthe following probability distribution would result:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.1:(1,0) + 0.1:(0,1)</code>\n</li></ul><p class='vspace'>For a <a class='wikilink' href='../ThePRISMLanguage/CTMCs.html'>CTMC</a>, as will be discussed shortly,\nthe choice is modelled as a \"race\" between transitions.\n</p>\n<p class='vspace'>See the later sections on \"<a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>Synchronisation</a>\" and \"<a class='wikilink' href='../ThePRISMLanguage/ProcessAlgebraOperators.html'>Process Algebra Operators</a>\" for other topics related to parallel composition.\n</p><hr />\n<h1>Local Nondeterminism</h1>\n<p>PRISM models that support nondeterminism, such as are MDPs, can also exhibit <em>local nondeterminism</em>,\nwhich allows the modules themselves to make nondeterministic choices.\nIn <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>, we can make the probabilistic choice in the first state of module <code>M1</code> nondeterministic by replacing the command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock24'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=24' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>with the commands:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock25'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=25' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Assuming we do the same for module <code>M2</code>, in state <code>(0,0)</code> of the MDP\nthere will be a nondeterministic choice between the three (trivial) probability distributions listed below. (There are three, not four, distributions because two possibilities result in identical behaviour: staying with probability 1 in the state state.)\n</p>\n<div class='vspace'></div><ul><li><code>1.0:(0,0)</code>\n</li><li><code>1.0:(1,0)</code>\n</li><li><code>1.0:(0,1)</code>\n</li></ul><p class='vspace'>More generally, local nondeterminism can also arise when the guards of two commands overlap only partially, rather than completely as in the example above.\n</p>\n<p class='vspace'>PRISM also permits local nondeterminism in models which are DTMCs,\nalthough the nondeterministic choice is randomised when the parallel composition of the modules occurs.\nSince the appearance of nondeterminism in a DTMC is often the result of\na user error in the model specification, PRISM displays a warning when local nondeterminism is detected in a DTMC.\nOverlapping guards in <a class='wikilink' href='../ThePRISMLanguage/CTMCs.html'>CTMCs</a> are not treated as nondeterministic choices.\n</p>\n<div class='vspace'></div><hr />\n<h1>CTMCs</h1>\n<p class='vspace'>Specifying the behaviour of a continuous-time Markov chain (CTMC)\nis done in similar fashion to a DTMC or an MDP, as discussed so far.\nThe main difference is that updates in commands are\nlabelled with (positive-valued) <em>rates</em>, rather than probabilities.\nThe notation used in commands, however, to associate rates to transitions is identical to\nthe one used to assign probabilities:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock26'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">rate_1</span>:<span class=\"prismident\">update_1</span> + <span class=\"prismident\">rate_2</span>:<span class=\"prismident\">update_2</span> + ... <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=26' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In a CTMC, when multiple possible transitions are available in a state, a <em>race condition</em> occurs\n(see e.g. [<a class='wikilink' href='References.html#KNP07a'>KNP07a</a>] for more details).\nIn terms of PRISM commands, this can arise in several ways.\nFirstly, within in a module, multiple transitions can be specified either as several different updates in a command, or as multiple commands with overlapping guards. The following, for example. are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock27'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=27' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock28'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=28' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Furthermore, parallel composition between modules in a CTMC is modelled as a race condition,\nrather as a nondeterministic choice, like for <a class='wikilink' href='../ThePRISMLanguage/ParallelComposition.html'>MDPs</a>.\n</p><hr />\n<h1>Example 2</h1>\n<p>We now introduce a second example: a CTMC that models an <em>N</em>-place queue of jobs and\na server which removes jobs from the queue and processes them.\nThe PRISM code is as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock29'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 2</span><br/>\n<span class=\"prismcomment\">// N-place queue + server</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span> = <span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mu</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">lambda</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">2</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">gamma</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">3</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">queue</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">q</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">N</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>&lt;<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>+<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>=<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">server</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">s</span>=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismident\">gamma</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">0</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=29' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 2</strong>\n</p>\n<p class='vspace'>This example also introduces a number of other PRISM language concepts,\nincluding <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a>, action labels and <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation</a>.\nThese are described in the following sections.\n</p><hr />\n<h1>Constants</h1>\n<p>PRISM supports the use of <em>constants</em>, as seen in <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>.\nConstants can be integers, doubles or Booleans\nand can be defined using literal values or as constant expressions (including in terms of each other) using the <code><strong>const</strong></code>\nkeyword. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock30'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">radius</span> = <span class=\"prismnum\">12</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">pi</span> = <span class=\"prismnum\">3.141592</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">area</span> = <span class=\"prismident\">pi</span> * <span class=\"prismident\">radius</span> * <span class=\"prismident\">radius</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">bool</span> <span class=\"prismident\">yes</span> = <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=30' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The identifiers used for their names are subject to the same rules as <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variables</a>.\n</p>\n<p class='vspace'>Constants can be used anywhere that a constant value would be expected,\nsuch as the lower or upper range of a variable (e.g. <code>N</code> in <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>),\nthe probability or rate associated with an update (<code>mu</code> in <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>),\nor anywhere in a guard or update.\nAs will be described later constants can also be left undefined\nand specified later, either to a single value or a range of values, using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'><strong>Note:</strong> For the sake of backward-compatibility, the notation used in earlier versions of PRISM\n(<code><strong>const</strong></code> for <code><strong>const int</strong></code> and <code><strong>rate</strong></code> or <code><strong>prob</strong></code> for <code><strong>const double</strong></code>) is still supported.\n</p><hr />\n<h1>Expressions</h1>\n<p>The definition of the <code>area</code> constant, in the example above, uses an <em>expression</em>.\nWe now define more precisely what types of expression are supported by PRISM.\nExpressions can contain literal values (12, 3.141592, <code><strong>true</strong></code>, <code><strong>false</strong></code>, etc.),\nidentifiers (corresponding to variables, constants, etc.) and operators from the following list:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>^</code> (power)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li></ul><p class='vspace'>All of these operators except <code>?</code> and <code>=&gt;</code> are left associative\n(i.e. they are evaluated from left to right).\nThe precedence of the operators is as found in the list above,\nmost strongly binding operators first.\nOperators on the same line (e.g. <code>+</code> and <code>-</code>) are of equal precedence.\n</p>\n<p class='vspace'>Much of the notation for expressions is hence essentially equivalent to that of C/C++ or Java.\nOne notable exception to this is that  the division operator <code>/</code> always performs floating point, not integer, division,\ni.e. the result of <code>22/7</code> is 3.142857... not 3.\nAll expressions must evaluate correctly in terms of type (integer, double or Boolean).\n</p>\n<p class='vspace'><strong>Built-in Functions</strong>\n</p>\n<p class='vspace'>Expressions can make use of several built-in functions:\n</p>\n<div class='vspace'></div><ul><li><code>min(...)</code> and <code>max(...)</code>, which select the minimum and maximum value, respectively, of two or more numbers\n</li><li><code>floor(x)</code> and <code>ceil(x)</code>, which round <code>x</code> down and up, respectively, to the nearest integer\n</li><li><code>round(x)</code>, which rounds <code>x</code> to the nearest integer (note, in a tie-break, we always round <em>up</em>, e.g. <code>round(-1.5)</code> gives <code>-1</code> not <code>-2</code>)\n</li><li><code>pow(x,y)</code> which computes <code>x</code> to the power of <code>y</code> (same as <code>x^y</code>)\n</li><li><code>mod(i,n)</code> for integer modulo operations\n</li><li><code>log(x,b)</code>, which computes the logarithm of <code>x</code> to base <code>b</code>\n</li></ul><p class='vspace'>Examples of their usage are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock31'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">min</span>(<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>, <span class=\"prismident\">x_max</span>)<br/>\n<span class=\"prismkeyword\">max</span>(<span class=\"prismident\">a</span>,<span class=\"prismident\">b</span>,<span class=\"prismident\">c</span>)<br/>\n<span class=\"prismident\">floor</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">ceil</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">round</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">2</span>, <span class=\"prismnum\">8</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">9.0</span>, <span class=\"prismnum\">0.5</span>)<br/>\n<span class=\"prismident\">mod</span>(<span class=\"prismnum\">1977</span>, <span class=\"prismnum\">100</span>)<br/>\n<span class=\"prismident\">log</span>(<span class=\"prismnum\">123</span>, <span class=\"prismnum\">2.71828183</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=31' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For compatibility with older versions of PRISM, all functions can also be expressed via the <code><strong>func</strong></code> keyword, e.g. <code>func(floor, 13.5)</code>.\n</p>\n<p class='vspace'><strong>Use of Expressions</strong>\n</p>\n<p class='vspace'>Expressions can be used in a wide range of places in a PRISM language description, e.g.:\n</p>\n<div class='vspace'></div><ul><li>constant definitions\n</li><li>lower/upper bounds and initial values for variables\n</li><li>guards\n</li><li>probabilities/rates\n</li><li>updates\n</li></ul><p class='vspace'>This allows, for example, the probability in a command to be dependent on the current state:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock32'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] (<span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span>) -&gt; <span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">max</span>(<span class=\"prismnum\">1</span>,<span class=\"prismident\">x</span>-<span class=\"prismnum\">1</span>)) + <span class=\"prismnum\">1</span>-<span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">min</span>(<span class=\"prismnum\">10</span>,<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>)) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=32' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Synchronisation</h1>\n<p>Another feature of PRISM introduced in <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a> is <em>synchronisation</em>.\nIn the style of many process algebras, we allow commands to be labelled with <em>actions</em>.\nThese are placed inside the square brackets which mark the start of the command,\nfor example <code>serve</code> in this command from <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock33'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=33' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These actions can be used to force two or more modules to make transitions simultaneously\n(i.e. to <em>synchronise</em>).\nFor example, in state <code>(3,0)</code> (i.e.  <code>q=3</code> and <code>s=0</code>),\nthe composed model can move to state <code>(2,1)</code>,\nsynchronising over the <code>serve</code> action.\nThe rate of this transition is equal to the product of the two individual rates\n(in this case, <code>lambda * 1 = lambda</code>).\nThe product of two rates does not always meaningfully represent the rate of a synchronised transition.\nA common technique, as seen here, is to make one action <em>passive</em>, with rate 1 and one action <em>active</em>,\nwhich actually defines the rate for the synchronised transition.\nBy default, all modules are combined using the standard CSP parallel composition\n(i.e. modules synchronise over all their common actions).\n</p><hr />\n<h1>Module Renaming</h1>\n<p>PRISM also supports <em>module renaming</em>, which allows duplication of modules.\nIn <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>, module <code>M2</code> is identical to module <code>M1</code> so we can in fact replace its entire definition with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock34'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span> = <span class=\"prismident\">M1</span> [ <span class=\"prismident\">x</span>=<span class=\"prismident\">y</span>, <span class=\"prismident\">y</span>=<span class=\"prismident\">x</span> ] <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=34' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>All of the variables in the module being renamed (in this case, just <code>x</code>) <em>must</em> be renamed to new, unused names. Optionally, it is also possible to rename other aspects of the module definition. In fact, the renaming is done at a textual level, so any identifiers (including <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>action labels</a>, <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a> and <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>functions</a>) used in the module definition can be changed in this way.\n</p>\n<p class='vspace'><strong>Note:</strong> Care should be taken when renaming modules that make use of <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>formulas</a>.\n</p><hr />\n<h1>Multiple Initial States</h1>\n<p>Typically, a <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variable</a> declaration\nspecifies the initial value for that variable.\nThe <em>initial state</em> for the model is then defined by the initial value for all variables.\nIt is possible, however, to specify that a model has <em>multiple</em> initial states.\nThis is done using the <code><strong>init</strong>...<strong>endinit</strong></code> construct,\nwhich can be placed anywhere in the file except within a module definition,\nand removing any initial values from variable declarations.\nBetween the <code><strong>init</strong></code> and <code><strong>endinit</strong></code> keywords, there should be a\npredicate over all the variables of the model.\nAny state which satisfies this predicate is an initial state.\n</p>\n<p class='vspace'>Consider again <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>.\nAs it stands, there is a single initial state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>).\nIf we remove the <code><strong>init</strong> 0</code> part of both variable declarations\nand add the following to the end of the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock35'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=35' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>there will be three initial states: <code>(0,0)</code>, <code>(0,1)</code> and <code>(0,2)</code>.\nSimilarly, we could instead add:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock36'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>+<span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=36' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>in which case there would be two initial states: <code>(0,1)</code> and <code>(1,0)</code>.\n</p><hr />\n<h1>Global Variables</h1>\n<p>In addition to the local variables belonging to each module, a PRISM model can also include <em>global variables</em>,\nwhich can be written to, as well as read, by all modules.\nLike local variables, these can be integers or Booleans.\nGlobal variables are declared in identical fashion to a module's local variables,\nexcept that the declaration must not be inside the definition of any module.\nSome example declarations are as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock37'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">global</span> <span class=\"prismident\">g</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismnum\">10</span>];<br/>\n<span class=\"prismkeyword\">global</span> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=37' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A global variable can be modified by any module and provides another way for modules to interact.\nAn important restriction on the use of global variables is the fact that commands which synchronise with other modules\n(i.e. those with an action label attached; see the section \"<a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>Synchronisation</a>\") cannot modify global variables.\nPRISM will detect this and report an error.\n</p><hr />\n<h1>Formulas And Labels</h1>\n<p>PRISM models can include <em>formulas</em> which are used to avoid duplication of code.\nA formula comprises a name (an identifier) and an <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a>.\nThe formula name can then be used as shorthand for the expression anywhere an expression might usually be accepted.\nA formula is defined as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock38'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">formula</span> <span class=\"prismident\">num_tokens</span> = <span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=38' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It can then be used anywhere within that file, as for example in this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock39'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">num_tokens</span>=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=39' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The effect is exactly as if the following had been typed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock40'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; (<span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>)=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=40' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Formulas defined in a model can also be used when specifying its properties.\n</p>\n<div class='vspace'></div><h3>Formulas and renaming</h3>\n<p>During parsing of the model, expansion of formulas is done before module renaming so, if a module which uses formulas is renamed to another module, it is the contents of the formula which will be renamed, not the formula itself.\n</p>\n<div class='vspace'></div><h3>Labels</h3>\n<p>PRISM models can also contain <em>labels</em>. These are a way of identifying sets of states that are of particular interest. Labels can only be used when specifying <a class='wikilink' href='../PropertySpecification/Main.html'>properties</a> but, for convenience, can be defined in model files as well as property files. \n</p>\n<p class='vspace'>Labels differ from formulas in two other ways: firstly, they must be of Boolean type;\nsecondly, they are written using quotation marks (<code>\"...\"</code>), as illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock41'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=41' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Costs And Rewards </h1>\n<p>PRISM supports the specification and analysis of\nproperties based on <em>costs</em> and <em>rewards</em>.\nThis means that it can be used to reason,\nnot just about the probability that a model behaves in a certain fashion,\nbut about a wider range of quantitative measures relating to model behaviour.\nFor example, PRISM can be used to compute properties such as\n\"expected time\", \"expected number of lost messages\" or \"expected power consumption\".\nThe implementation of cost- and reward-based techniques in the tool is only partially completed and is still ongoing.\nIf you have questions, comments or feature-requests relating to this functionality,\nplease feel free to contact the PRISM team about this.\n</p>\n<p class='vspace'>The basic idea is that probabilistic models (of all types) developed in PRISM\ncan be augmented with costs or rewards: real values associated with certain states or transitions of the model.\nIn fact, since there is no practical distinction between costs and rewards\n(except that costs are generally perceived to be \"bad\" and rewards to be \"good\"),\nPRISM only supports rewards.\nThe user is, however, free to interpret the values however they choose.\n</p>\n<p class='vspace'>In this section, we describe how models described in the PRISM language\ncan be augmented with rewards.\nLater, we will discuss how to express properties that relate to these rewards.\nRewards are associated with models using <code><strong>rewards</strong> ... <strong>endrewards</strong></code> constructs,\nwhich can appear anywhere in a model file except within a module definition.\nThese constructs contains one or more <em>reward items</em>.\nConsider the following simple example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock42'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r1</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=42' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This defines a reward structure with name <code>r1</code> (the name is optional)\nwhich assigns a reward of 1 to every state of the model.\nIt comprises a single reward item, the left part of which (<code><strong>true</strong></code>) is a guard\nand the right part of which (<code>1</code>) is a reward.\nStates of the model which satisfy the predicate in the guard are assigned the corresponding reward.\nMore generally, state rewards can be specified using multiple reward items,\neach of the form <code>guard : reward;</code>,\nwhere <code>guard</code> is a predicate (over all the variables of the model)\nand <code>reward</code> is an expression (containing any variables, constants, etc. from the model).\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock43'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r2</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> : <span class=\"prismnum\">100</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&lt;<span class=\"prismnum\">10</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">10</span> : <span class=\"prismnum\">100</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=43' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 100 to states satisfying <code>x=0</code> or <code>x=10</code>\nand a reward of <code>2*x</code> to states satisfying <code>x&gt;0 &amp; x&lt;10</code>.\nNote that a single reward item can assign different rewards to different states,\ndepending on the values of model variables in each one.\nAny states which do not satisfy the guard of any reward item will have no reward assigned to them.\nFor states which satisfy multiple guards, the reward assigned to the state\nis the sum of the rewards for all the corresponding reward items.\n</p>\n<p class='vspace'>Rewards can also be assigned to transitions of a model.\nThese are specified in a similar fashion to state rewards,\nwithin the <code><strong>rewards</strong> ... <strong>endrewards</strong></code> construct.\nReward items describing transition rewards are of the form <code>[action] guard : reward;</code>,\nthe interpretation being that transitions from states which satisfy the guard <code>guard</code>\nand are labelled with the action <code>action</code> acquire the reward <code>reward</code>.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock44'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r3</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">a</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=44' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 1 to all transitions in the model with no action label,\nand rewards of <code>x</code> and <code>2*x</code> to all transitions labelled with actions <code>a</code> and <code>b</code>, respectively.\n</p>\n<p class='vspace'>As is the case for states, multiple reward items can specify rewards for a single transition,\nin which case the resulting reward is the sum of all the individual rewards.\nA model description can specify rewards for both states and transitions.\nThese are all placed together in a single <code><strong>rewards</strong>...<strong>endrewards</strong></code> construct.\n</p>\n<p class='vspace'>A PRISM model will often have multiple reward structures, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock45'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">total_time</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n<br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">num_failures</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">fail</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=45' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<h1>Real-time Models</h1>\n<p class='vspace'>So far in this section, we have mainly focused on three types of models: DTMCs, MDPs and CTMCs,\nin which all the variables making up their state are finite.\nPRISM also supports <em>real-time</em> models, in particular,\n<em>probabilistic timed automata</em> (PTAs), which extend MDPs with the ability to model real-time behaviour.\nThis is done in the style of <em>timed automata</em> [<a class='wikilink' href='References.html#AD94'>AD94</a>], by adding <em>clocks</em>,\nreal-valued variables which increase with time and can be reset. For background material on PTAs, see for example [<a class='wikilink' href='References.html#NPS13'>NPS13</a>].\nYou can also find several example PTA models included in the PRISM distribution. Look in the <code>prism-examples/ptas</code> directory.\n</p>\n<p class='vspace'>Before describing how PTA features are incorporated into the PRISM modelling language, we give a simple example. Here is a small PTA:\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/pta.png' alt='' /></div>\n<p class='vspace'>and here is a corresponding PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock46'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">pta</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : <span class=\"prismkeyword\">clock</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">invariant</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">2</span>) &amp;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">3</span>)<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">endinvariant</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">send</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismnum\">0.9</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">retry</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.95</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.05</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=46' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For modelling PTAs in PRISM, there is a new datatype, <strong><code>clock</code></strong>, used for variables that are clocks. Other types of PRISM variables can be defined in the usual way. In the example above, we use just a single integer variable <code>s</code> to represent the locations of the PTAs.\n</p>\n<p class='vspace'>In a PTA, transitions can include a <em>guard</em>, which constrains when it can occur based on the current value of clocks, and <em>resets</em>, which specify that a clock's values should be set to a new (integer) value. These are both specified in PRISM commands in the usual way: see, for example, the inclusion of <code>x&gt;=1</code> in the guard for the <code>send</code>-labelled command and the updates of the form <code>(x'=0)</code> which reset the clock <code>x</code> to 0.\n</p>\n<p class='vspace'>The other new addition is an <code>invariant</code> construct, which is used to specify an expression describing the clock <em>invariants</em> for each PRISM module. These impose restrictions on the allowable values of clock variables, depending on the values of the other non-clock variables. The <code>invariant</code> construct should appear between the variable declarations and the commands of the module. Often, clock invariants are described separately for each PTA location; hence, the invariant will often take the form of a conjunction of implications, as in the example model above, but more general expressions are also permitted. In the example, the clock <code>x</code> must satisfy <code>x&lt;=2</code> or <code>x&lt;=3</code> when local variables <code>s</code> is 0 or 2, respectively. If <code>s</code> is 1, there is no restriction (since the invariant is effectively <code>true</code> in this case).\n</p>\n<p class='vspace'>Expressions that include reference to clocks, whether in guards or invariants, must satisfy certain conditions to facilitate model checking. In particular, references to clocks must appear as conjunctions of <em>simple clock constraints</em>, i.e. conjunctions of expressions of the form <code>x~c</code> or <code>x~y</code> where <code>x</code> and <code>y</code> are clocks, <code>c</code> is an integer-valued expression and <code>~</code> is one of <code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code>, <code>=</code>).\n</p>\n<p class='vspace'>There are also some additional restrictions imposed on PTA models that are dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is in use.\n</p>\n<p class='vspace'>For the <strong>stochastic games</strong> and <strong>backwards reachability</strong> engines:\n</p>\n<div class='vspace'></div><ul><li>The model must also have a single initial state (i.e. the <code>init...endinit</code> construct is not permitted).\n</li></ul><p class='vspace'>For the <strong>digital clocks</strong> engine:\n</p>\n<div class='vspace'></div><ul><li>Clock constraints cannot use strict comparison operators, e.g. <code>x&lt;=5</code> is allowed, but <code>x&lt;5</code> is not.\n<div class='vspace'></div></li><li>Diagonal clock constraints are not allowed, i.e. those containing references to two clocks, such as <code>x&lt;=y</code>.\n</li></ul><p class='vspace'>Finally, PRISM makes several assumptions about PTAs, regardless of the engine used.\n</p>\n<div class='vspace'></div><ul><li>Firstly PTAs should not exhibit <em>timelocks</em>, i.e. the possibility of reaching a state where no transitions are possible and time cannot elapse beyond a certain point (due to invariant conditions). PRISM checks for timelocks and reports an error if one is found.\n<div class='vspace'></div></li><li>Secondly, PTAs should be <em>well-formed</em> and <em>non-zeno</em> (see e.g. [<a class='wikilink' href='References.html#KNSW07'>KNSW07</a>] for details). Currently, PRISM does not check automatically that these assumptions are satisfied.\n</li></ul><div class='vspace'></div><hr />\n<h1>Partially Observable Models</h1>\n<p>PRISM supports analysis of <em>partially observable</em> probabilistic models,\nmost notably partially observable Markov decision processes (POMDPs),\nbut also partially observable probabilistic timed automata (POPTAs).\nPOMDPs are a variant of MDPs in which the strategy/policy\nwhich resolves nondeterministic choices in the model is unable to\nsee the precise state of the model, but instead just <em>observations</em> of it.\nFor background material on POMDPs and POPTAs, see for example [<a class='wikilink' href='References.html#NPZ17'>NPZ17</a>].\nYou can also find several example models included in the PRISM distribution.\nLook in the <code>prism-examples/pomdps</code> and <code>prism-examples/poptas</code> directories.\n</p>\n<p class='vspace'>PRISM currently supports state-based observations:\nthis means that, upon entering a new POMDP state,\nthe observation is determined by that state.\nIn the same way that a model state comprises the values or one or more variables,\nan observation comprises one or more <em>observables</em>.\nThere are several way to define these observables.\nThe simplest is to specify a subset of the model's variables\nthat are designated as being observable. The rest are unobservable.\n</p>\n<p class='vspace'>For example, in a POMDP with 3 variables, <code>s</code>, <code>l</code> and <code>h</code>, the following:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock47'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">observables</span> <span class=\"prismident\">s</span>, <span class=\"prismident\">l</span> <span class=\"prismkeyword\">endobservables</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=47' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>specifies that <code>s</code> and <code>l</code> are observable and <code>h</code> is not.\n</p>\n<p class='vspace'>Alternatively, observables can be specified as arbitrary expressions over variables.\nFor example, assuming the same variables <code>s</code>, <code>l</code> and <code>h</code>, this specification:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock48'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">s</span>\" = <span class=\"prismident\">s</span>;<br/>\n<span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">pos</span>\" = <span class=\"prismident\">l</span>&gt;<span class=\"prismnum\">0</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=48' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>defines 2 observables. The first is, as above, the variable <code>s</code>.\nThe second, named <code>\"pos\"</code>, determines if variable <code>l</code> is positive.\nOther than this, the values of <code>l</code> and <code>h</code> are unobservable.\nThe named observables can then be used in properties\nin the same way that <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> can.\n</p>\n<p class='vspace'>The above two styles of definition can also be mixed\nto specify a combined set of observables.\n</p>\n<p class='vspace'>POPTAs (partially observable PTAs) combine the features of both PTAs and POMDPs.\nThey are are currently analysed using the digital clocks engine,\nso inherit the <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>restrictions for that engine</a>.\nFurthermore, for a POPTA, all clock variables must be observable.\n</p><hr />\n<h1>Uncertain models</h1>\n<p>PRISM has support for <em>uncertain</em> models, in which there is epistemic uncertainty regarding some quantitative aspects of the probabilistic models being verified. In particular, it currently supports <em>interval MDPs</em> (IMDPs) and <em>interval DTMCs</em> (IDTMCs), which are MDPs or DTMCs in which transition probabilities can be specified as intervals, indicating that the exact probability is not precisely known. This can be useful, for example, when the transition probabilities have been estimated from data.\n</p>\n<p class='vspace'>Currently, this is achieved by simply replacing the probabilities attached to updates in commands with intervals, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock49'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismnum\">0.8</span>,<span class=\"prismnum\">0.9</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.1</span>,<span class=\"prismnum\">0.2</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=49' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As usual, the probability thresholds can be expressions involving state variables or constants, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock50'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismident\">p</span>,<span class=\"prismident\">p</span>+<span class=\"prismnum\">0.1</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.9</span>-<span class=\"prismident\">p</span>,<span class=\"prismnum\">1</span>-<span class=\"prismident\">p</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=50' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When two commands in different modules <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronise</a> and specify the probabilities for updates to variables as intervals, these are considered to be independent, i.e., the probability of each combined transition is taken to be the product of the two component intervals.\n</p>\n<p class='vspace'>See the <a class='wikilink' href='../PropertySpecification/UncertainModels.html'>property specification</a> section for details of how these models are analysed.\n</p><hr />\n<h1>Process Algebra Operators</h1>\n<p>To make the concept of synchronisation described above more powerful,\nPRISM allows you to define precisely the way in which the set of modules are composed in parallel.\nThis is specified using the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct,\nplaced at the end of the model description, which should contain a process-algebraic expression.\nThis expression should feature each module exactly once, and can use the following (CSP-based) operators:\n</p>\n<div class='vspace'></div><ul><li><code>M1 || M2</code> : alphabetised parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising on only actions appearing in both <code>M1</code> and <code>M2</code>)\n<div class='vspace'></div></li><li><code>M1 ||| M2</code> : asynchronous parallel composition of <code>M1</code> and <code>M2</code> (fully interleaved, no synchronisation)\n<div class='vspace'></div></li><li><code>M1 |[a,b,...]| M2</code> : restricted parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising only on actions from the set {<code>a</code>, <code>b</code>,...})\n<div class='vspace'></div></li><li><code>M / {a,b,...</code>} : hiding of actions {<code>a</code>, <code>b</code>, ...} in module <code>M</code>\n<div class='vspace'></div></li><li><code>M {a&lt;-b,c&lt;-d,...</code>} : renaming of actions <code>a</code> to <code>b</code>, <code>c</code> to <code>d</code>, etc. in module <code>M</code>.\n</li></ul><p class='vspace'>The first two types of parallel composition (<code>||</code> and <code>|||</code>) are associative and can be applied to more than two modules at once.\nWhen evaluating the expression, the hiding and renaming operators bind more tightly than the three parallel composition operators.\nNo other rules of precedence are defined and parentheses should be used to specify the order in which modules are composed.\n</p>\n<p class='vspace'>Some examples of expressions which could be included in the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct are as follows:\n</p>\n<div class='vspace'></div><ul><li><code>(station1 ||| station2 ||| station3) |[serve]| server</code>\n</li><li><code>((P1 |[a]| P2) / {a}) || Q</code>\n</li><li><code>((P1 |[a]| P2) {a&lt;-b}) |[b]| Q</code>\n</li></ul><p class='vspace'>When no parallel composition is specified by the user,\nPRISM implicitly assumes an expression of the form <code>M1 || M2 || ...</code> containing all of the modules in the model.\nFor a more formal definition of the process algebra operators described above, check the semantics of the PRISM language, available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site.\n</p>\n<p class='vspace'>PRISM is also able to <a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>import</a> model descriptions written in (a subset of) the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='References.html#Hil96'>Hil96</a>].\n</p><hr />\n<h1>PRISM Model Files</h1>\n<p>Files containing model descriptions written in the PRISM language\ncan contain any amount of white space (spaces, tabs, new lines, etc.),\nall of which is ignored when the file is parsed by the tool.\nComments can also be used included in files in the style of the C programming language,\nby preceding them with the characters <code>//</code>.\nThis is illustrated by the PRISM language examples from earlier in this section.\n</p>\n<p class='vspace'>We recommend that the <code>.prism</code> extension is used for PRISM model files.\nHistorically (when the tool supported fewer types of model),\ndifferent extensions were often used for each model type:\n<code>.nm</code> for MDPs or PTAs, <code>.pm</code> for DTMCs and <code>.sm</code> for CTMCs.\n</p>\n<p class='vspace'><br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Property Specification</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>In order to analyse a probabilistic model which has been specified and constructed in PRISM,\nit is necessary to identify one or more <em>properties</em> of the model\nwhich can be evaluated by the tool.\nPRISM's <em>property specification language</em> subsumes several well-known probabilistic temporal logics, including PCTL, CSL, probabilistic LTL and PCTL*.\nPCTL is used for specifying properties of discrete-time models such as DTMCs or PTAs,\nand also real-time models such as PTAs; CSL is an extension of PCTL for CTMCs;\nLTL and PCTL* can be used to specify properties of \ndiscrete-time models (or untimed properties of CTMCs).\nPRISM also supports most of the (non-probabilistic) temporal logic CTL.\n</p>\n<p class='vspace'>In fact, PRISM also supports numerous additional customisations and extensions of these two logics.\nFull details of the property specifications permitted in PRISM are provided in the following sections. The presentation given here is relatively informal. For the precise syntax and semantics of the various logics, see [<a class='wikilink' href='References.html#HJ94'>HJ94</a>],[<a class='wikilink' href='References.html#BdA95'>BdA95</a>] for PCTL, [<a class='wikilink' href='References.html#ASSB96'>ASSB96</a>],[<a class='wikilink' href='References.html#BKH99'>BKH99</a>] for CSL and, for example, [<a class='wikilink' href='References.html#Bai98'>Bai98</a>] for LTL and PCTL*. You can also find various pointers to useful papers in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>Before discussing property specifications in more detail,\nit is perhaps instructive to first illustrate some typical examples of properties which PRISM can handle.\nThe following are a selection of such properties.\nIn each case, we give both the PRISM syntax and a natural language translation:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock51'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=51' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the algorithm eventually terminates successfully with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock52'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> \"<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=52' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that more than 5 errors occur within the first 100 time units is less than 0.1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock53'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismident\">num_sensors</span> &lt; <span class=\"prismident\">min_sensors</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=53' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"in the long-run, the probability that an inadequate number of sensors are operational is less than 0.01\"\n</p>\n<p class='vspace'>Note that the above properties are all assertions,\ni.e. ones to which we would expect a \"yes\" or \"no\" answer.\nThis is because all references to probabilities are associated with an upper or lower bound\nwhich can be checked to be either true or false.\nIn PRISM, we can also directly specify properties which evaluate to a numerical value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock54'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ !<span class=\"prismident\">proc2_terminate</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">proc1_terminate</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=54' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that process 1 terminates before process 2 does\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock55'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">messages_lost</span> &gt; <span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=55' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the maximum probability that more than 10 messages have been lost by time <code>T</code>\" (for an MDP/PTA)\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock56'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=56' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the long-run probability that the queue is more than 75% full\"\n</p>\n<p class='vspace'>Furthermore, PRISM makes it easy to combine such properties into more complex expressions,\ncompute their values for a range of parameters\nand plot graphs of the results using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\nThis is often a very useful way of identifying interesting\npatterns or trends in the behaviour of a system.\nSee the <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a> section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a> for many examples of this kind of analysis.\n</p><hr />\n<h1>Identifying A Set Of States</h1>\n<p>One of the most fundamental tasks when specifying properties of a model\nis to identify particular sets or classes of states of the model.\nFor example, to verify a property such as\n\"the algorithm eventually terminates successfully with probability 1\",\nit is first necessary to identify the states of the model\nwhich correspond to situations where \"the algorithm has terminated successfully\".\nIn terms of the way temporal logics are usually presented,\nthese correspond to <em>atomic propositions</em>.\n</p>\n<p class='vspace'>In PRISM, this is achieved simply by writing an <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a> in the PRISM language which evaluates to a Boolean value. This expression will typically contain references to variables (and constants) from the model to which it relates. The set of states corresponding to this expression is those for which it evaluates to <code>true</code>. We say that the expression is \"satisfied\" in these states.\n</p>\n<p class='vspace'>For example, in the property given above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock57'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=57' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>the expression <code>num_errors &gt; 5</code> is used to identify states of the model where more than 5 errors have occurred.\n</p>\n<p class='vspace'>It is also common to use <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> to identify states in this way, like <code>\"terminate\"</code> in the example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock58'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=58' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Properties can refer to <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> either from the model to which the property relates, or included in the same <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html'>properties file</a>.\n</p><hr />\n<h1>The P Operator</h1>\n<p>One of the most important operators in the PRISM property specification language is the <code><strong>P</strong></code> operator, which is used to reason about the probability of an event's occurrence. This operator was originally proposed in the logic PCTL but also features in the other logics supported by PRISM, such as CSL. The <code><strong>P</strong></code> operator is applicable to all types of models supported by PRISM.\n</p>\n<p class='vspace'>Informally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock59'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=59' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a model if\n\"the probability that path property <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code>\".\nA typical example of a bound would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock60'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=60' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em> is greater than 0.98\". More precisely, <code>bound</code> can be any of <code>&gt;=p</code>, <code>&gt;p</code>, <code>&lt;=p</code> or <code>&lt;p</code>,\nwhere <code>p</code> is a PRISM language expression evaluating to a double in the range [0,1].\n</p>\n<p class='vspace'>The types of path property supported by PRISM and their semantics will be discussed shortly.\n</p>\n<div class='vspace'></div><h3>Nondeterminism</h3>\n<p>For models that can exhibit nondeterministic behaviour, such as MDPs or PTAs, some additional clarifications are necessary. Whereas for fully probabilistic models such as DTMCs and CTMCs, probability measures over paths are well defined (see e.g. [<a class='wikilink' href='References.html#KSK76'>KSK76</a>] and [<a class='wikilink' href='References.html#BKH99'>BKH99</a>], respectively), for nondeterministic models a probability measure can only be feasibly defined once all nondeterminism has been removed.\n</p>\n<p class='vspace'>Hence, the actual meaning of the property <code>P bound [ pathprop ]</code> in these cases is: \n\"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code> <em>for all possible resolutions of nondeterminism</em>\".\nThis means that, properties using the <code><strong>P</strong></code> operator then effectively reason about the\n<em>minimum</em> or <em>maximum</em> probability, over all possible resolutions of nondeterminism,\nthat a certain type of behaviour is observed.\nThis depends on the bound attached to the <code><strong>P</strong></code> operator:\na lower bound (<code>&gt;</code> or <code>&gt;=</code>) relates to minimum probabilities\nand an upper bound (<code>&lt;</code> or <code>&lt;=</code>) to maximum probabilities.\n</p>\n<div class='vspace'></div><h3>Quantitative properties</h3>\n<p>It is also very often useful to take a <em>quantitative</em> approach to probabilistic model checking, computing the actual probability that some behaviour of a model is observed,\nrather than just verifying whether or not the probability is above or below a given bound.\nHence, PRISM allows the <code><strong>P</strong></code> operator to take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock61'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=61' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These properties return a numerical rather than a Boolean value.\nThe <a class='wikilink' href='../PropertySpecification/TheSOperator.html'>S</a> and <a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>R</a> operators, discussed later, can also be used in this way.\n</p>\n<p class='vspace'>As mentioned above, for nondeterministic models (MDPs or PTAs), either minimum or maximum probability values can be computed. Therefore, in this case, we have two possible types of property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock62'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=62' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which return the minimum and maximum probabilities, respectively.\n</p>\n<p class='vspace'>It is also possible to specify to which state the probability returned by a quantitative property refers. This is covered in the later section on <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\n</p>\n<div class='vspace'></div><h3>Path properties</h3>\n<p>PRISM supports a wide range of path properties that can be used with the <code><strong>P</strong></code> operator.\nA path property is a formula that evaluates to either true or false for a single path in a model.\nHere, we review some of the simpler properties that feature a single <em>temporal operator</em>,\nas used for example in the logics PCTL and CSL. Later, we briefly describe how PRISM also supports more complex LTL-style path properties.\n</p>\n<p class='vspace'>The basic different types of path property that can be used inside the <code><strong>P</strong></code> operator are:\n</p>\n<div class='vspace'></div><ul><li><code><strong>X</strong></code> : \"ne<strong>x</strong>t\"\n</li><li><code><strong>U</strong></code> : \"<strong>u</strong>ntil\"\n</li><li><code><strong>F</strong></code> : \"eventually\" (sometimes called \"<strong>f</strong>uture\")\n</li><li><code><strong>G</strong></code> : \"always\" (sometimes called \"<strong>g</strong>lobally\")\n</li><li><code><strong>W</strong></code> : \"<strong>w</strong>eak until\"\n</li><li><code><strong>R</strong></code> : \"<strong>r</strong>elease\"\n</li></ul><p class='vspace'>In the following sections, we describe each of these <em>temporal operators</em>. We then discuss the (optional) use of time bounds with these operators. Finally, we also discuss LTL-style path properties.\n</p>\n<div class='vspace'></div><h3>\"Next\" path properties</h3>\n<p>The property <code><strong>X</strong> prop</code> is true for a path if <code>prop</code> is true in its second state,\nAn example of this type of property, used inside a <code><strong>P</strong></code> operator, is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock63'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">X</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=63' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of the expression <code>y=1</code> being true in the next state is less than 0.01\".\n</p>\n<div class='vspace'></div><h3>\"Until\" path properties</h3>\n<p>The property <code>prop1 <strong>U</strong> prop2</code> is true for a path if\n<code>prop2</code> is true in some state of the path and <code>prop1</code> is true in all preceding states.\nA simple example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock64'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=64' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually equal to 2, and that <code>z</code> remains less than 2 up until that point, is greater than 0.5\".\n</p>\n<div class='vspace'></div><h3>\"Eventually\" path properties</h3>\n<p>The property <code><strong>F</strong> prop</code> is true for a path if <code>prop</code> eventually becomes true at some point along the path. The <code><strong>F</strong></code> operator is in fact a special case of the <code><strong>U</strong></code> operator (you will often see <code> <strong>F</strong> prop</code> written as <code><strong>true</strong> <strong>U</strong> prop</code>). A simple example is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock65'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>&gt;<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=65' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually greater than 2is less than 0.1\".\n</p>\n<div class='vspace'></div><h3>\"Globally\" path properties</h3>\n<p>Whereas the <code><strong>F</strong></code> operator is used for \"reachability\" properties, <code><strong>G</strong></code> represents \"invariance\". The property <code><strong>G</strong> prop</code> is true of a path if <code>prop</code> remains true at all states along the path. Thus, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock66'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=66' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>states that, with probability at least 0.99, <code>z</code> never exceeds 10.\n</p>\n<div class='vspace'></div><h3>\"Weak until\" and \"release\" path properties</h3>\n<p>Like <code><strong>F</strong></code> and <code><strong>G</strong></code>, the operators <code><strong>W</strong></code> and <code><strong>R</strong></code> are derivable from other temporal operators.\n</p>\n<p class='vspace'>Weak until (<code>a <strong>W</strong> b</code>), which is equivalent to <code>(a <strong>U</strong> b) | <strong>G</strong> a</code>, requires that <code>a</code> remains true until <code>b</code> becomes true, but does not require that <code>b</code> ever does becomes true (i.e. <code>a</code> remains true forever). For example, a weak form of the until example used above is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock67'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=67' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which states that, with probability greater than 0.5, either <code>z</code> is always less than 2, or it is less than 2 until the point where <code>z</code> is 2.\n</p>\n<p class='vspace'>Release (<code>a <strong>R</strong> b</code>),  which is equivalent to <code>!(!a U !b)</code>, informally means that <code>b</code> is true until <code>a</code> becomes true, or <code>b</code> is true forever.\n</p>\n<p class='vspace'><a name='bounded' id='bounded'></a>\n</p><h3>\"Bounded\" variants of path properties</h3>\n<p>All of the temporal operators given above, with the exception of <code><strong>X</strong></code>, have \"bounded\" variants, where an additional time bound is imposed on the property being satisfied.\nThe most common case is to use an upper time bound, i.e. of the form \"<code>&lt;=t</code>\" or \"<code>&lt;t</code>\", where <code>t</code> is a PRISM expression evaluating to a constant, non-negative value.\n</p>\n<p class='vspace'>For example, a bounded until property <code>prop1 <strong>U</strong>&lt;=t prop2</code>, is satisfied along a path if <code>prop2</code> becomes true within <code>t</code> steps and <code>prop1</code> is true in all states before that point.\nA typical example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock68'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">y</span>&lt;<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=68' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of <code>y</code> first exceeding 3 within 7 time units is greater than or equal to 0.98\". Similarly:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock69'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=69' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state if \"the probability of <code>y</code> being equal to 4 within 7 time units is greater than or equal to 0.98\" and:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock70'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=70' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true if the probability of <code>y</code> staying equal to 4 for 7 time units is at least 0.98.\n</p>\n<p class='vspace'>The time bound can be an arbitrary (constant) expression,\nbut note that you may need to bracket it,\nas in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock71'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=(<span class=\"prismnum\">2</span>*<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>) <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=71' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use lower time-bounds (i.e. <code>&gt;=t</code> or <code>&gt;t</code>) and time intervals <code>[t1,t2]</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock72'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&gt;=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">20</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=72' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which refer to the probability of <code>y</code> becoming equal to 4 after 10 or more time units, and after between 10 and 20 time-units respectively.\n</p>\n<p class='vspace'>For CTMCs, the time bounds can be any (non-negative) numerical values - they are not restricted to integers, as for discrete-time models.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock73'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.25</span> [ <span class=\"prismident\">y</span>&lt;=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">6.5</span> <span class=\"prismident\">y</span>&gt;<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=73' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means that the probability of <code>y</code> being greater than 1 within 6.5 time-units (and remaining less than or equal to 1 at all preceding time-points) is at least 0.25.\n</p>\n<div class='vspace'></div><h3>Transient probabilities</h3>\n<p>We can also use the bounded <code><strong>F</strong></code> operator to refer to a single time instant, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock74'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">10</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=74' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or, equivalently:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock75'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=75' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>both of which give the probability of <code>y</code> being 6 at time instant 10.\n</p>\n<p class='vspace'><a name='ltl' id='ltl'></a>\n</p><h3>LTL-style path properties</h3>\n<p>PRISM also supports probabilistic model checking of the temporal logic LTL (and, in fact, PCTL*). LTL provides a richer set of path properties for use with the <code><strong>P</strong></code> operator, by permitting temporal operators to be combined. Here are a few examples of properties expressible using this functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock76'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">F</span> ( \"<span class=\"prismident\">request</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">ack</span>\") ) ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=76' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"with probability greater than 0.99, a request is eventually received, followed immediately by an acknowledgement\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock77'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">send</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=77' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"a message is sent infinitely often with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock78'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">G</span> (\"<span class=\"prismident\">error</span>\" &amp; !\"<span class=\"prismident\">repair</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=78' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of an error occurring that is never repaired\n</p>\n<p class='vspace'>Note that logical operators have precedence over temporal ones, so you will often need to include parentheses when using logical operators, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock79'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\") &amp; (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=79' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For temporal operators, unary operators (such as <code><strong>F</strong></code>, <code><strong>G</strong></code> and <code><strong>X</strong></code>) have precedence over binary ones (such as <code><strong>U</strong></code>). Unary operators can be nested, without parentheses, but binary ones cannot.\n</p>\n<p class='vspace'>So, these are allowed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock80'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">a</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ (\"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\") <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=80' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>but this is not:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock81'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=81' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>The S Operator</h1>\n<p>The <code><strong>S</strong></code> operator is used to reason about the <em>steady-state</em> behaviour of a model,\ni.e. its behaviour in the <em>long-run</em> or <em>equilibrium</em>.\nPRISM currently only provides support for DTMCs and CTMCs.\nThe definition of steady-state (long-run) probabilities for finite DTMCS and CTMCs is well defined (see e.g. [<a class='wikilink' href='References.html#Ste94'>Ste94</a>]).\nInformally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock82'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">prop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=82' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a DTMC or CTMC if\n\"starting from <em>s</em>, the steady-state (long-run) probability of being in a state which satisfies the (Boolean-valued) PRISM property <code>prop</code>, meets the bound <code>bound</code>\".\nA typical example of this type of property would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock83'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.05</span> [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=83' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the long-run probability of the queue being more than 75% full is less than 0.05\".\n</p>\n<p class='vspace'>Like the <code><strong>P</strong></code> <a class='wikilink' href='../PropertySpecification/ThePOperator.html'>operator</a>, the <code><strong>S</strong></code> operator can be used in a <em>quantitative</em> form, which returns the actual probability value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock84'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=84' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and can be further customised with the use of <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\n</p><hr />\n<h1>Reward-based Properties</h1>\n<p>PRISM models can be augmented with information about <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>rewards</a> (or, equivalently, costs).\nThe tool can analyse properties which relate to the <em>expected values</em> of these rewards.\nThis is achieved using the <code><strong>R</strong></code> operator, which works in a similar fashion to the\n<code><strong>P</strong></code> and <code><strong>S</strong></code> operators, and can be used either in a Boolean-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock85'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=85' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>bound</code> takes the form <code>&lt;r</code>, <code>&lt;=r</code>, <code>&gt;r</code> or <code>&gt;=r</code> for an expression <code>r</code> evaluating to a non-negative double,\nor a real-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock86'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">query</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=86' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>query</code> is <code>=?</code>, <code>min=?</code> or <code>max=?</code>.\nIn the latter case, <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a> can be used, as for the <code><strong>P</strong></code> and <code><strong>S</strong></code> operators.\n</p>\n<p class='vspace'>Informally, \"<code><strong>R</strong> bound [ rewardprop ]</code>\" is true in a state of a model if\n\"the expected reward associated with <code>rewardprop</code> of the model when starting from that state''\nmeets the bound <code>bound</code> and \"<code><strong>R</strong> query [ rewardprop ]</code>\"  returns the actual expected reward value.\n</p>\n<p class='vspace'>There are various different types of reward properties:\n</p>\n<div class='vspace'></div><ul><li>\"reachability reward\": <code><strong>F</strong> prop</code>\n</li><li>\"co-safe LTL reward\": e.g. <code><strong>F</strong> (prop1 &amp; <strong>F</strong> prop2)</code>\n</li><li>\"cumulative reward\" : <code><strong>C</strong>&lt;=t</code>\n</li><li>\"total reward\" : <code><strong>C</strong></code>\n</li><li>\"instantaneous reward\" : <code><strong>I</strong>=t</code>\n</li><li>\"steady-state reward\" : <code><strong>S</strong></code>.\n</li></ul><p class='vspace'>Below, we consider each of these cases in turn.\nThe descriptions here are kept relatively informal.\nPrecise definitions for most of these can be found in, for example,\n[<a class='wikilink' href='References.html#KNP07a'>KNP07a</a>] (for DTMCs and CTMCs) or [<a class='wikilink' href='References.html#FKNP11'>FKNP11</a>] (for MDPs).\n</p>\n<div class='vspace'></div><h3>\"Reachability reward\" properties</h3>\n<p>\"Reachability reward\" properties associate a reward with each path of a model.\nMore specifically, they refer to the reward accumulated along a path until a certain point is reached.\nThe manner in which rewards are accumulated depends on the model type.\nFor DTMCs and MDPs, the total reward for a path is the sum of the state rewards for each state along the path\nplus the sum of the transition rewards for each transition between these states.\nThe situation for CTMCs is similar, except that the state reward assigned to each state\nof the model is interpreted as the <em>rate</em> at which rewards are accumulated in that state,\ni.e. if <em>t</em> time units are spent in a state with state reward <em>r</em>,\nthe reward accumulated in that state is <em>r</em> x <em>t</em>.\nHence, the total reward for a path in a CTMC is the sum of these products for each state along the path\nplus the sum of the transition rewards for each transition between these states.\n</p>\n<p class='vspace'>The reward property \"<code>F prop</code>\" corresponds to the reward cumulated along a path\nuntil a state satisfying property <code>prop</code> is reached,\nwhere rewards are cumulated as described above.\nState rewards for the <code>prop</code>-satisfying state reached are not included in the cumulated value.\nIn the case where the probability of reaching a state satisfying <code>prop</code> is less than 1, the reward is equal to infinity.\n</p>\n<p class='vspace'>A common application of this type of property is the case when the rewards associated with the model correspond to time.\nOne can then state, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock87'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">9.5</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=87' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"the expected time taken to reach, from <em>s</em>, a state where <code>z</code> equals 2 is less than or equal to 9.5\".\n</p>\n<div class='vspace'></div><h3>\"Co-safe LTL reward\" properties</h3>\n<p>These generalise the \"reachability\" properties above. Again, reward is accumulated along a path up until some point,\nbut this is specified in a more general way, by giving a formula in the co-safe fragment of linear temporal logic (LTL).\nRewards are accumulated up until the point where the formula is first satisfied. For example, this property, for a DTMC or CTMC,\nqueries the expected reward accumulated until first <code>goal</code> equals 1 and then subsequently <code>goal</code> equals 2:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock88'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">F</span> (<span class=\"prismident\">goal</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismkeyword\">F</span> <span class=\"prismident\">goal</span>=<span class=\"prismnum\">2</span>) ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=88' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and this property, for an MDP, minimises the expected reward until <code>loc</code> equals 1,\nhaving passed only through states where <code>loc</code> never equals 4\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock89'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismident\">loc</span>!=<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">loc</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=89' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As for reachability rewards, if the probability of satisfying the formula is less than 1,\nthen the expected reward is defined to be infinite.\n</p>\n<p class='vspace'>Intuitively, a <em>co-safe</em> formula is one that is satisfied within a finite period of time,\nand remains true for ever once it becomes true for the first time.\nFor simplicity, PRISM actually supports the <em>syntactic</em> co-safe fragment of LTL,\nwhich is defined as any LTL formula that only uses the temporal operators <code><strong>F</strong></code>, <code><strong>U</strong></code> and <code><strong>X</strong></code>\n(but not <code><strong>G</strong></code>, for example).\nPRISM's notation for LTL formulas is described <a class='wikilink' href='../PropertySpecification/ThePOperator.html'>here</a>.\n</p>\n<div class='vspace'></div><h3>\"Cumulative reward\" properties</h3>\n<p>\"Cumulative reward\" properties also associate a reward with each path of a model,\nbut only up to a given time bound.\nThe property <code>C&lt;=t</code> corresponds to the reward cumulated along a path\nuntil <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\nState and transition rewards along a path are cumulated exactly as described in the previous section.\n</p>\n<p class='vspace'>A typical application of this type of property is the following.\nConsider a model of a disk-drive controller which includes a queue of incoming disk requests.\nIf we assign a reward of 1 to each transition of the model\ncorresponding to the situation where an incoming request is lost because the queue is full,\nthen the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock90'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">15.5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=90' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would return, for a given state of the model,\n\"the expected number of lost requests within 15.5 time units of operation\".\n</p>\n<p class='vspace'><a name='total' id='total'></a>\n</p><h3>\"Total reward\" properties</h3>\n<p>\"Total reward\" properties refer to the accumulation of state and transition rewards\nin the same way as for \"reachability reward\" and \"cumulative reward\" properties,\nbut the rewards is accumulated indefinitely,\ni.e. the total reward accumulated along the whole (infinite) path.\nNote that this means that, unless a path ends up remaining forever in states with zero reward,\nthe total reward will be infinite.\n</p>\n<p class='vspace'>Re-using the reward structure in the previous example,\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock91'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=91' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>returns \"the expected total number of lost requests\".\n</p>\n<div class='vspace'></div><h3>\"Instantaneous reward\" properties</h3>\n<p>\"Instantaneous reward\" properties refer to the reward of a model at a particular instant in time.\nThe reward property <code>I=t</code> associates with a path the reward in the state \nof that path when exactly <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\n</p>\n<p class='vspace'>Returning to our example from the previous section of a model for a disk-request queue in a disk-drive controller,\nconsider the case where the rewards assigned to each state of the model give the current size of the queue in that state.\nThen, the following property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock92'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;<span class=\"prismnum\">4.4</span> [ <span class=\"prismkeyword\">I</span>=<span class=\"prismnum\">100</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=92' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would be true in a state <em>s</em> of the model if\n\"starting from <em>s</em>, the expected queue size exactly 100 time units later is less than 4.4\".\nNote that, for this type of reward property, state rewards for CTMCs do not have to refer to rates;\nthey can refer to any instantaneous measure of interest for a state.\n</p>\n<div class='vspace'></div><h3>\"Steady-state reward\" properties</h3>\n<p>Unlike the previous three types of property,\n\"steady-state reward\" properties relate not to paths, but rather to the reward in the long-run.\nA typical application of this type of property would be, in the case where\nthe rewards associated with the model correspond to power consumption, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock93'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">0.7</span> [ <span class=\"prismkeyword\">S</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=93' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"starting from <em>s</em>, the long-run average power consumption is less than 0.7\".\n</p>\n<div class='vspace'></div><h3>Which reward structure?</h3>\n<p>In the case where a PRISM model has multiple <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structures</a> you may need to specify which reward structure your property refers to. This is done by placing the information in braces (<code>{}</code>) after the <code>R</code> operator. You can do so either using the name assigned to a reward structure (if any) or using the index (where <code>1</code> means the first rewards structure in the PRISM model file, <code>2</code> the second, etc.). Examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock94'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">num_failures</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">10.0</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismnum\">2</span>}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=94' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note that when using an index to specify the reward structure, you can actually put any expression that evaluates to an integer. This allows you to, for example, write a property of the form <code>R{c}=?[...]</code> where <code>c</code> is an undefined integer constant. You can then vary the value of <code>c</code> in an experiment and compute values for several different reward structures at once.\n</p>\n<p class='vspace'>If you don't specify a reward structure to the <code>R</code> operator, by default, the first one in the model file is used.\n</p>\n<div class='vspace'></div><h3>Availability</h3>\n<p>There are currently a few restrictions on the model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a> that can be used for some reward properties. The following table summarises the currently availability, where S, M, H and E denote the \"sparse\", \"MTBDD\", \"hybrid\" and \"explicit\" engines, respectively, for DTMCs, CTMCs and MDPs. For PTAs, support for rewards is currently quite restrictive; see the later section on <a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>real-time model properties</a> for details.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><code><strong>F</strong></code></td><td  align='center'>cosafe</td><td  align='center'><code><strong>C</strong>&lt;=t</code></td><td  align='center'><code><strong>C</strong></code></td><td  align='left'><code><strong>I</strong>=t</code></td><td  align='right'><code><strong>S</strong></code></td></tr>\n<tr ><td  align='center'><strong>DTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>CTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>MDPs</strong></td><td  align='center'>SM-E</td><td  align='center'>SMHE</td><td  align='center'>S--E</td><td  align='center'>----</td><td  align='center'>SM-E</td><td  align='right'>----</td></tr>\n</table><hr />\n<h1>Multi-objective Properties</h1>\n<p>For MDPs, PRISM supports <em>multi-objective</em> properties. Consider a property that uses the <code><strong>P</strong></code> operator. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock95'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=95' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This states that, <em>for all</em> strategies (or policies) of the MDP, the probability of reaching an <code>\"error\"</code> state is less than 0.01.\n</p>\n<p class='vspace'>Multi-objective queries differ in two important ways. Firstly, (by default) they ask about the <em>existence</em> of a strategy. Secondly they refer to <em>multiple</em> properties of a strategy. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock96'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=96' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means: \"does there exist a strategy of the MDP under which the probability of reaching an <code>\"error1\"</code> state is less than 0.01 <em>and</em> the probability of reaching an <code>\"error2\"</code> state is less than 0.02?\"\n</p>\n<p class='vspace'>To use the terminology from [<a class='wikilink' href='References.html#FKP12'>FKP12</a>], the above is an \"achievability\" query (i.e., is this combination of objectives achievable by some strategy?). PRISM also supports two other kinds of multi-objective query: \"numerical\" and \"Pareto\" queries.\n</p>\n<p class='vspace'>A \"numerical\" query looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock97'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=97' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>meaning \"what is the minimum possible probability of reaching <code>\"error1\"</code>, over all strategies of the MDP for which the probability of reaching <code>\"error2\"</code> is less than 0.02?\".\n</p>\n<p class='vspace'>A \"Pareto\" queries leaves both of the objectives unbounded, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock98'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=98' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This asks PRISM to compute (approximately), the <em>Pareto curve</em> for this pair objectives. Intuitively, this is the set of pairs of probabilities (of reaching <code>\"error1\"</code>/<code>\"error2\"</code>) such that reducing one probability any more would necessitate an increase in the other probability.\n</p>\n<div class='vspace'></div><h3>Types of Objectives</h3>\n<p>For simplicity, the examples above all refer to the probability of reaching classes of states in the model. Other types of property (objective) are also possible.\n</p>\n<p class='vspace'>Firstly, we can extend the examples above by referring to the probability of any\n<a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>LTL</a> property. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock99'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=99' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9?\".\n</p>\n<p class='vspace'>We can also use more than 2 objectives, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock100'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.95</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good3</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=100' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9 and the probability of visiting <code>\"good3\"</code> states infinitely often remains at least 0.95?\".\n</p>\n<p class='vspace'>Multi-objective queries can also refer to the expected total cumulative value of a reward structure. We write such properties in the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock101'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}<span class=\"prismkeyword\">min</span>=?[ <span class=\"prismkeyword\">C</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">energy</span>\"}&lt;=<span class=\"prismnum\">1.45</span> [ <span class=\"prismkeyword\">C</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=101' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the minimum expected cumulative value of reward structure <code>\"time\"</code>, such that the expected cumulative value of reward structure <code>\"energy\"</code> is below 1.45.\n</p>\n<p class='vspace'>Note that this <code><strong>C</strong></code> reward operator differs from the <code><strong>F</strong> \"target\"</code> operator, usually used for standard (single-objective) MDP model checking. Whereas the <code><strong>F</strong> \"target\"</code> operator refers to the expected reward accumulated until a <code>\"target\"</code> state is reached the <code><strong>C</strong></code> operator refers to the expected <em>total</em> reward.\n</p>\n<p class='vspace'>A few important notes regarding rewards:\n</p>\n<div class='vspace'></div><ul><li>Currently only transition rewards are supported; state rewards are not.\n<div class='vspace'></div></li><li>Certain assumptions are made regarding the finiteness of rewards; see p.7 of [<a class='wikilink' href='References.html#FKP12'>FKP12</a>] for details.\n</li></ul><p class='vspace'>Finally, time-bounded variants of both probabilistic reachability and expected cumulative rewards objectives can be used. Here is an example that uses the latter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock102'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">power</span>\"}<span class=\"prismkeyword\">min</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">queue</span>\"}&lt;=<span class=\"prismident\">r</span> [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=102' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Solution Methods</h3>\n<p>PRISM can perform multi-objective model checking using two distinct solution methods, which are described in [<a class='wikilink' href='References.html#FKN+11'>FKN+11</a>] and [<a class='wikilink' href='References.html#FKP12'>FKP12</a>]. The former is based on the use of linear programming; the latter reduces multi-objective model checking to a series of simpler problems, solved using value iteration (or the Gauss-Seidel variant of value iteration). The default is \"Value iteration\". You can change this in the GUI using the option \"MDP multi-objective solution methods\", or using the command-line switches <code>-lp</code>, <code>-valiter</code>, <code>-gs</code>.\n</p>\n<p class='vspace'>There are some restrictions for the different methods, e.g.\n</p>\n<div class='vspace'></div><ul><li>Linear programming does not support time-bounded properties or Pareto queries\n</li></ul><div class='vspace'></div><hr />\n<h1>Real-time Models</h1>\n<p>The classes of property that can be checked for real-time models (PTAs and POPTAs) are currently more restricted than for the other kinds of models that PRISM supports. This is because the model checking procedures are quite different for this type of model. We describe these restrictions here. The situation is also dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is being used.\n</p>\n<p class='vspace'>For the \"<strong>stochastic games</strong>\" engine, we essentially only allow unbounded or time-bounded probabilistic reachability properties, i.e. properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock103'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=103' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>target</code> is a Boolean-valued expression that does not include references to any clock variables and <code>T</code> is an integer-valued expression. The <code><strong>P</strong></code> operator cannot be nested and the <code><strong>S</strong></code> and <code><strong>R</strong></code> operators are not supported.\n</p>\n<p class='vspace'>The \"<strong>backwards reachability</strong>\" engine is similar but currently only handles maximum probabilities.\n</p>\n<p class='vspace'>For the \"<strong>digital clocks</strong>\" engine, there is slightly more flexibility,\ne.g. until (<code><strong>U</strong></code>) properties are allowed, as are clock variables in expressions and arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock104'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=104' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This engine, like the \"stochastic games\" engine, does not allowed nested properties. Also, references to clocks must, like in the modelling language, not use strict comparisons\n(e.g. <code>x&lt;=5</code> is allowed, <code>x&lt;5</code> is not).\n</p>\n<p class='vspace'>The digital clocks also has support for rewards:\nit is possible to check reachability reward properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock105'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=105' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Reward structures specified in the model, though, must not depend on clock variables.\nFormally, the class of PTAs with this kind of reward structure is sometime called <em>linearly priced PTAs</em> (see e.g. [<a class='wikilink' href='References.html#KNPS06'>KNPS06</a>].\n</p>\n<p class='vspace'>The digital clocks method is based on a language-level translation from a PTA model to an MDP one. If you want to see the MDP PRISM model that was generated, add the switch <code>-exportdigital digital.nm</code> when model checking property to export the model file to <code>digital.nm</code>.\n</p><hr />\n<h1>Partially Observable Models</h1>\n<p>For partially observable models (POMDPs and POPTAs),\nPRISM uses the same property language as the their\nfully observational equivalents (MDPs and PTAs).\nHowever, a more limited range of properties are available.\nFor POMDPs, PRISM currently supports probabilistic reachability,\nprobabilistic until, or expected reachability rewards properties, i.e.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock106'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=106' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or bounded variants with a probability/threshold instead\nof the <code>min=?</code> or <code>max=?</code>.\n</p>\n<p class='vspace'>For the verification methods currently implemented,\nthere are a few additional restrictions.\nFirstly, the <code>target</code> (and <code>remain</code>) expression appearing\nin the property must be an observable.\nIn other words, if any state of the POMDP satisfies the expression,\nthen all other observationally equivalent states must also satisfy it.\nThis is easily achieved by only using either observable variables\nor named observables in the expression, but that is not required.\nSecondly, probabilities and expected rewards are only computed from a single state.\n</p>\n<p class='vspace'>POPTAs are currently verified using the \"digital clocks\" approach to\ntranslate them into a POMDP, so they inherit the same\n<a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>restrictions</a>\n(that strict or diagonal clock comparisons are not allowed).\nHowever for POPTAs, time-bounded probabilistic reachability is also supported.\n</p><hr />\n<h1>Uncertain Models</h1>\n<p>For uncertain models, currently interval MDPs (IMDPs) or interval DTMCs (IDTMCs), PRISM performs <em>robust</em> verification, which considers the best- or worst-case behaviour that can arise depending on the way that probabilities are selected from intervals.\n</p>\n<p class='vspace'>For example, instead of a property for a DTMC such as\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock107'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=107' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which asks for the probability to reach a state satisfying <code>\"goal\"</code>, IDTMCs use MDP-style queries:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock108'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=108' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which compute the minimum or maximum possible probability that can arise.\n</p>\n<p class='vspace'>Similarly, for an IMDP, there are now two separate quantifications, firstly over strategies (policies) and secondly over the distinct ways that transition probabilities can be selected from intervals, for which <code>min</code> or <code>max</code> appear in that order in the query. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock109'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmaxmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmaxmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=109' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>return the minimum and maximum values, respectively, over resolutions of transition probabilities for the maximum probability of reaching <code>\"goal\"</code>. Similarly, <code>minmin</code> and <code>minmax</code> are used for the minimum probability of reaching <code>\"goal\"</code>. Model checking is supported for:\n</p>\n<div class='vspace'></div><ul><li>the <code><strong>P</strong></code> operator, including single temporal operators and LTL formulae\n</li><li>the <code><strong>R</strong></code> operator, for the expected reward to reach a target or satisfy a co-safe LTL formula\n</li></ul><div class='vspace'></div><hr />\n<h1>Non-Probabilistic Properties</h1>\n<p>PRISM also supports model checking of the non-probabilistic temporal logics CTL (computation tree logic) and LTL (linear temporal logic).\nProperties in these logics use the <code><strong>A</strong></code> (for all) and <code><strong>E</strong></code> (there exists) operators,\ninstead of the probabilistic <code><strong>P</strong></code> operator used in many other properties supported by PRISM.\n</p>\n<p class='vspace'>Properties take the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock110'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">A</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=110' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which are true in a state <em>s</em> of a model if\n\"path property <code>pathprop</code> is satisfied by <em>all</em> paths from state <em>s</em>\"\nand\n\"path property <code>pathprop</code> is satisfied by <em>some</em> path from state <em>s</em>\",\nrespectively.\nThe syntax for LTL formulas is the same as those allowed within the <a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>P operator</a>.\n</p>\n<p class='vspace'>Example properties include:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock111'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ] <span class=\"prismcomment\">// There exists a path that reaches a state satisfying \"goal\"</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span> ] <span class=\"prismcomment\">// Variable x is always at most 10 along all paths of the model</span><br/>\n<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">ready</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">launch</span>\") ] <span class=\"prismcomment\">// There exists a path along which label \"ready\" eventually becomes true and label \"launch\" is true immediately afterwards</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span>) | (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>) ] <span class=\"prismcomment\">// Along all paths, either x=1 or x=2 is true infinitely often</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=111' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Counterexamples and Witnesses</h3>\n<p>If you check a CTL property of the form <code>A [ G \"inv\" ]</code> and it is false, PRISM will generate a counterexample in the form of a path that reaches a state where <code>\"inv\"</code> is not true. This is displayed either in the simulator (from the GUI) or at the command-line. Similarly, if you check <code>E [ F \"goal\" ]</code> and the result is true, a witness (a path reaching a <code>\"goal\"</code> state) will be generated.\n</p><hr />\n<h1>Syntax And Semantics</h1>\n<h3>Syntax</h3>\n<p>The syntax of the PRISM property specification language subsumes various probabilistic temporal logics, including PCTL, CSL, (probabilistic) LTL, PCTL* and CTL. Informally, the syntax can be summarised as follows: a property can be any valid, well-typed PRISM <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a>, which (optionally) also includes the probabilistic operators discussed previously (<code><strong>P</strong></code>, <code><strong>S</strong></code> and <code><strong>R</strong></code>) and the non-probabilistic (CTL) ones <code><strong>A</strong></code> and <code><strong>E</strong></code>). This mean that any of the following operators can be used:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li><li><code><strong>P</strong></code> (probabilistic operator)\n</li><li><code><strong>S</strong></code> (steady-state operator)\n</li><li><code><strong>R</strong></code> (reward operator)\n</li><li><code><strong>A</strong></code> (for-all operator)\n</li><li><code><strong>E</strong></code> (there-exists operator)\n</li></ul><p class='vspace'>This allows you to write any property expressible in logics such as PCTL and CSL. For example, CSL allows you to nest <code><strong>P</strong></code> and <code><strong>S</strong></code> operators:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock112'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>&gt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">S</span>&gt;<span class=\"prismnum\">0.9</span>[ <span class=\"prismident\">num_servers</span> &gt;= <span class=\"prismnum\">5</span> ] ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=112' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of it taking more than 2 hours to get to a state from which the long-run probability of at least 5 servers being operational is &gt;0.9\"\n</p>\n<p class='vspace'>You can also express various arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock113'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">3600</span>,<span class=\"prismnum\">7200</span>] <span class=\"prismident\">oper</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=113' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability that the system is <strong>not</strong> operational at any point during the second hour of operation\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock114'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">oper</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">t</span> ] / <span class=\"prismident\">t</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=114' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the expected fraction of time that the system is available (i.e. the expected interval availability) in the time interval [0, t]\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock115'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">fail_A</span> ] / <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">any_fail</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=115' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the (conditional) probability that component A eventually fails, given\nthat at least one component fails\"\n</p>\n<div class='vspace'></div><h3>Semantics</h3>\n<p>We omit a formal presentation of the semantics of the PRISM property language. The semantics of the probabilistic temporal logics that the language incorporates can be found from a variety of sources. See for example the pointers given in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>It is worth, however, clarifying a few points specific to PRISM. A property is evaluated with respect to a particular state of a model. Depending on the type of the property, this value may either be a Boolean, an integer or a double. When performing model checking, PRISM usually has to actually compute the value for <em>all</em> states of the model but, for clarity, will by default report just a single value. Typically, this is the value for the (single) initial state of the model. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock116'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=116' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will report the probability, from the initial state of the model, of reaching an \"error\" state.\nThis:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock117'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=117' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will return <code>true</code> if and only if the probability, from the initial state, is greater than 0.5.\n</p>\n<p class='vspace'><strong>Note:</strong> This is contrast to older versions of PRISM, which treated numerical and Boolean-valued properties differently in this respect.\n</p>\n<p class='vspace'>For models with <a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>multiple initial states</a>, we need to adapt these definitions slightly. In this case, the two properties above will yield, respectively:\n</p>\n<div class='vspace'></div><ul><li>the range of values (over all initial states) of the probability of reaching \"error\"\n<div class='vspace'></div></li><li><code>true</code> if and only if the probability is greater than 0.5 from <em>all</em> initial states.\n</li></ul><p class='vspace'>You can also ask PRISM to return different values using <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>,\nwhich are described in the next section.\n</p><hr />\n<h1>Filters</h1>\n<p>As discussed above, when reporting the result of model checking a property, PRISM will by default return the value for the (single) initial state of the model. However, since PRISM in fact usually has to compute values for <em>all</em> states simultaneously, you can customise PRISM properties to obtain different results. This is done using <em>filters</em>.\n</p>\n<p class='vspace'>Filters are created using the <code>filter</code> keyword. They take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock118'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=118' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>op</code> is the filter <em>operator</em> (see below), <code>prop</code> is any PRISM property and <code>states</code> is a Boolean-valued expression identifying a set of states over which to apply the filter.\n</p>\n<p class='vspace'>In fact, the <code>states</code> argument is optional; if omitted, the filter is applied over all states. So, the following properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock119'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismkeyword\">true</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=119' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Here's a simple example of a filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock120'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=120' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This gives the <em>maximum</em> value, starting from any state satisfying <code>x=0</code>, of the probability of reaching an \"error\" state.\n</p>\n<p class='vspace'>Here's another simple example,\nwhich checks whether, <em>starting from any reachable state</em>,\nwe eventually reach a \"done\" state with probability 1.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock121'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=121' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We could modify this property slightly to instead check whether, from any state that satisfies the label \"ready\", we eventually reach a \"done\" state with probability 1. This could be done with either of the following two equivalent properties:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock122'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, \"<span class=\"prismident\">ready</span>\" =&gt; <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ], \"<span class=\"prismident\">ready</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=122' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Note:</strong> In older versions of PRISM, the property above could be written just as <code>\"ready\" =&gt; P&gt;=1 [ F \"done\" ]</code> since the result was checked for all states by default, not just the <a class='wikilink' href='../PropertySpecification/SyntaxAndSemantics.html'>initial state</a>. Now, you need to explicitly include a filter, as shown above, to achieve this.\n</p>\n<div class='vspace'></div><h3>Types of filter</h3>\n<p>Most filters of the form <code>filter(op, prop, states)</code>\napply some operator <code>op</code> to the values of property <code>prop</code>\nfor all the states satisfying <code>states</code>,\nresulting in a single value.\nThe full list of filter operators <code>op</code> in this category is:\n</p>\n<div class='vspace'></div><ul><li><code>min</code>: the minimum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>max</code>: the maximum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>count</code>: counts the number of states satisfying <code>states</code> for which <code>prop</code> is true\n</li><li><code>sum</code> (or <code>+</code>): sums the value of <code>prop</code> for states satisfying <code>states</code>\n</li><li><code>avg</code>: the average value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>first</code>: the value of <code>prop</code> for the first (lowest-indexed) state satisfying <code>states</code>\n</li><li><code>range</code>: the range (interval) of values of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>forall</code> (or <code>&amp;</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for all states satisfying <code>states</code>\n</li><li><code>exists</code> (or <code>|</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for some states satisfying <code>states</code>\n</li><li><code>state</code>: returns the value for the single state satisfying <code>states</code> (if there is more than one, this is an error)\n</li></ul><p class='vspace'>There are also a few filters that, rather than returning a single value, return different values for each state, like a normal PRISM property:\n</p>\n<div class='vspace'></div><ul><li><code>argmin</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the minimum value of <code>prop</code>\n</li><li><code>argmax</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the maximum value of <code>prop</code>\n</li><li><code>print</code>: does not change the result of <code>prop</code> but prints the (non-zero) values to the log\n</li><li><code>printall</code>: like <code>print</code>, but displays <em>all</em> values, even for states where the value is zero\n</li></ul><div class='vspace'></div><h3>More examples</h3>\n<p>Here are some further illustrative examples of properties that use filters.\n</p>\n<p class='vspace'>Filters provide a quick way to <em>print</em> the results of a model checking query for several states. In most cases, for example, a <code>P=?</code> query just returns the probability from the initial state. To see the probability for all states satisfying <code>x&gt;2</code>, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock123'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">P</span>=? [ ... ], <span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">2</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=123' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Values are printed in the log (i.e. to the \"Log\" tab in the GUI or to the terminal from the command-line). For small models, you could omit the final <code>states</code> argument (<code>x&gt;2</code> here) and view the probabilities from all states. You can also use PRISM's <a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>verbose</a> mode to view values for all states, but filters provide an easier and more flexible solution.\n<code>print</code> filters do not actually alter the result returned so, in the example above, PRISM will still return the probability for the initial state, in addition to printing other probabilities in the log.\n</p>\n<p class='vspace'>You can also use <code>print</code> filters to display lists of states. For example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock124'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">argmax</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]))<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=124' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>prints the states which have the highest probability of reaching an error state.\nHowever, you should exercise caution when using <code>argmax</code> (or <code>argmin</code>) on properties such as <code>P=? [ ... ]</code> (or <code>S=? [ ... ]</code> or <code>R=? [ ... ]</code>), whose results are only approximate due to the nature of the methods used to compute them (or because of round-off errors.)\n</p>\n<p class='vspace'>Another common use of filters is to display the value for a particular state of the model (rather than the initial state, which is used by default). To achieve this, use e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock125'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>&amp;<span class=\"prismident\">y</span>=<span class=\"prismnum\">3</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=125' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>x=2&amp;y=3</code> is assumed to specify one particular state.\nA <code>state</code> filter will produce an error if the filter expression is not satisfied by exactly one state of the model.\n</p>\n<p class='vspace'>Filters can also be built up into more complex expressions. For example, the following two properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock126'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">avg</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">sum</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\") / <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">count</span>, \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=126' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>range</code> filter, unlike most PRISM expressions which are of type Boolean, integer or double, actually returns an interval: a pair of integers or doubles. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock127'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">count</span>=<span class=\"prismnum\">10</span> ], <span class=\"prismident\">count</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=127' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>gives the range of all possible values for the probability of reach a state satisfying <code>count=10</code>, from all states satisfying <code>count=0</code>.\nAs will be described below, this kind of property also results from the use of old-style (<code>{...}</code>) filters and properties on models with multiple initial states.\n</p>\n<div class='vspace'></div><h3>Old-style filters</h3>\n<p>In older versions of PRISM, filters were also available, but in a less expressive form. Previously, they were only usable on <code><strong>P</strong></code>, <code><strong>S</strong></code> or <code><strong>R</strong></code> properties and only a small set of filter operators were permitted. They were also specified in a different way, using braces (<code>{</code>...<code>}</code>). For compatibility with old properties files (and for compactness), these forms of filters are still allowed. These old-style forms of filters:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock128'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=128' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are equivalent to:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock129'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">min</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=129' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the first of the four properties above (i.e. an old-style filter of the form <code>{states}</code> will result in an error if <code>states</code> is not satisfied by exactly one state of the model. Older versions of PRISM just gave you the value for the first state state satisfying the filter, without warning you about this. If you want to recreate the old behaviour, just use a <code>first</code> filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock130'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">first</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=130' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Default filters</h3>\n<p>Finally, for completeness, we show what the <em>default</em> filters are in PRISM,\ni.e. how the way that PRISM returns values from properties by default\ncould have been achieved equivalently using filters.\n</p>\n<p class='vspace'>Queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock131'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=131' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock132'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=132' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock133'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=133' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as either:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock134'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=134' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the cases where there the model has a single initial state\nor multiple initial states, respectively.\n</p><hr />\n<h1>Properties Files</h1>\n<h3>Constants</h3>\n<p>Files containing properties to be analysed by PRISM can also contain constants, as is the case for model files.\nThese are defined in identical fashion, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock135'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span> = <span class=\"prismnum\">7</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span> = <span class=\"prismnum\">9.5</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">p</span> = <span class=\"prismnum\">0.01</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismident\">p</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">x</span>=<span class=\"prismident\">k</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=135' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As before, these constants can actually be left undefined and then later\nassigned either a single value or a range of values using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'>In fact, values such as the probability bounds for the <code><strong>P</strong></code> or <code><strong>S</strong></code> operators (like <code><strong>P</strong></code> above)\nand upper or lower bounds for the <code><strong>U</strong></code> operator (like <code> T</code> above)\ncan be arbitrary expressions, provided they are constant.\nFurthermore, expressions in the properties file can also refer to constants previous defined in the model file.\n</p>\n<p class='vspace'><a name='labels' id='labels'></a>\n</p><h3>Labels</h3>\n<p>Another feature of properties files is <em>labels</em>. These are a way of defining sets of states that will be referred to in properties (they correspond to <em>atomic propositions</em> in a temporal logic setting). As described <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>earlier</a>, labels can be defined in either model files or property files.\n</p>\n<p class='vspace'>Labels are defined using the keyword <code><strong>label</strong></code>, followed by a name (identifier) in double quotes, and then an expression which evaluates to a Boolean. Definition and usage of labels are illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock136'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ \"<span class=\"prismident\">safe</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">fail</span>\" ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=136' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Two special cases are the <code>\"init\"</code> and <code>\"deadlock\"</code> labels which are always defined.\nThese are true in initial states of the model and states where deadlocks were found (and, usually, fixed by adding self-loops), respectively.\n</p>\n<p class='vspace'><a name='names' id='names'></a>\n</p><h3>Property names</h3>\n<p>For convenience, properties can be annotated with <em>names</em>, as shown in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock137'>\r\n  <div class='sourceblocktext'><div class=\"prism\">\"<span class=\"prismident\">safe</span>\": <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">temperature</span> &gt; <span class=\"prismident\">t_max</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=137' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which gives the name <code>\"safe\"</code> to the property. It is then possible to include named properties as sub-expressions of other properties, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock138'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismident\">num_sensors</span>&gt;<span class=\"prismnum\">0</span> =&gt; \"<span class=\"prismident\">safe</span>\");<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=138' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the syntax for referring to named properties is identical to the syntax for labels. For this reason, property names must be disjoint from those of any existing labels.\n</p>\n<p class='vspace'>You can refer to property names when using the command-line switch <a class='wikilink' href='../RunningPRISM/ModelChecking.html#cl'><code>-prop</code></a> to specify which property is to be model checked.\n</p>\n<div class='vspace'></div><h3>Properties files</h3>\n<p>A PRISM properties file can contain any number of properties.\nIt is good practice, as shown in the examples above, to terminate each property with a semicolon. Currently, this is not enforced by PRISM (to prevent incompatibility with old properties files) but this may change in the future.\n</p>\n<p class='vspace'>Like model files, properties can also include any amount of white space (spaces, tabs, new lines, etc.) and C-style comments, which are both ignored.\nThe recommended file extension for PRISM properties is now <code>.props</code>.\nPreviously, though, the convention was to use extension <code>.pctl</code> for properties of DTMCs, MDPs or PTAs\nand extension <code>.csl</code> for properties of CTMCs, so these are still also valid.\n<br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Running PRISM</span></h1>\n<hr />\n<h1>Starting PRISM</h1>\n<p>There are two versions of PRISM, one based on a graphical user interface (GUI),\nthe other based on a command line interface. Both use the same underlying model checker.\nThe latter is useful for running large batches of jobs, leaving long-running model checking tasks in the background, or simply for running the tool quickly and easily once you are familiar with its operation. \n</p>\n<p class='vspace'>Details how how to run PRISM can be found in the <a class='wikilink' href='../InstallingPRISM/Main.html'>installation instructions</a>.\nIn short, to run the PRISM GUI:\n</p>\n<div class='vspace'></div><ul><li>(on Windows) click the short-cut (to <code>xprism.bat</code>) installed on the Desktop/Start Menu\n</li><li>(on other OSs) run the <code>xprism</code> script in the <code>bin</code> directory\n</li></ul><p class='vspace'>You can also optionally specify a model file and a properties file to load upon starting the GUI, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock139'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xprism example.prism</span><br/>\n<span style=\"font-weight:bold;\">xprism example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=139' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To use the command-line version of PRISM, run the <code>prism</code> script, also in the <code>bin</code> directory, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock140'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism example.prism example.props -prop 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=140' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-dir</code> switch can be used to specify a directory for input (and output) files.\nSo the following are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock141'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism ~/myfiles/example.prism ~/myfiles/example.props</span><br/>\n<span style=\"font-weight:bold;\">prism -dir ~/myfiles example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=141' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The remainder of this section of the manual describes the main types of functionality offered by PRISM.\nFor a more introductory guide to using the tool, try the\n<a class='urllink' href='http://www.prismmodelchecker.org/tutorial/'>tutorial</a> on the PRISM web site.\nSome screenshots of the GUI version of PRISM are shown below.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui1.gif'><img width='500' src='../uploads/gui1.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (editing a model)</strong></span></div>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui2.gif'><img width='500' src='../uploads/gui2.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (model checking)</strong></span></div>\n<div class='vspace'></div><hr />\n<h1>Loading And Building a Model</h1>\n<p>Typically, when using PRISM, the first step is to load a model that has been specified in the PRISM modelling language. If using the GUI, select menu option \"Model | Open Model\" and choose a file. There are a selection of sample PRISM model files in the <code>prism-examples</code> directory of the distribution.\nA few very small models are contained in the subdirectory <code>simple</code>;\nthe rest are in subdirectories grouped by model type.\n</p>\n<p class='vspace'>The model will then be displayed in the editor in the \"Model\" tab of the GUI window. The file is parsed upon loading. If there are no errors, information about the modules, variables, and other components of the model is displayed in the panel to the left and a green tick will be visible. If there are errors in the file, a red cross will appear instead and the errors will be highlighted in the model editor. To view details of the error, position the mouse pointer over the source of the error (or over the red cross). Alternatively, select menu option \"Model | Parse Model\" and the error mIessage will be displayed in a message box. Model descriptions can, of course, also be typed from scratch into the GUI's editor.\n</p>\n<div class='vspace'></div><h3>Building the model</h3>\n<p>In order to perform model checking, PRISM will (in most cases) need to construct the corresponding probabilistic model, i.e. convert the PRISM model description to, for example, an MDP, DTMC, etc. During this process, PRISM computes the set of states in the model which are reachable from the initial states and the transition matrix which represents the model.\n</p>\n<p class='vspace'>Model construction is done automatically when you perform <a class='wikilink' href='../RunningPRISM/ModelChecking.html'>model checking</a>. However, you may always want to explicitly ask PRISM to build the model in order to test for errors or to see how large the model is. From the GUI, you can do this by by selecting \"Model | Build Model\". If there are no errors during model construction, the number of states and transitions in the model will be displayed in the bottom left corner of the window.\n</p>\n<p class='vspace'>From the command-line, simply type:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock142'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.nm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=142' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>model.nm</code> is the name of the file containing the model description.\n</p>\n<p class='vspace'>For some types of models, notably PTAs, models are not constructed in this way (because the models are infinite-state). In these cases, analysis of the model is not performed until model checking is performed.\n</p>\n<p class='vspace'><a name='deadlocks' id='deadlocks'></a>\n</p><h3>Deadlocks</h3>\n<p>You should be aware of the possibility of <em>deadlock states</em> (or <em>deadlocks</em>) in the model,\ni.e. states which are reachable but from which there are no outgoing transitions.\nPRISM will automatically search your model for deadlocks and, by default,\n\"fix\" them by adding self-loops in these states.\nSince deadlocks are sometimes caused by modelling errors,\nPRISM will display a warning message in the log when deadlocks are fixed in this way.\n</p>\n<p class='vspace'>You can control whether deadlocks are automatically fixed in this way using the \"Automatically fix deadlocks\" option (or with command-line switches <code>-nofixdl</code> and <code>-fixdl</code>). When fixing is disabled, PRISM will report and error when the model contains deadlocks (this used to be the default behaviour in older versions of PRISM).\n</p>\n<p class='vspace'>If you have unwanted or unexpected deadlocks in your model, there are several ways you can detect then. Firstly, by disabling deadlock fixing (as described above), PRISM will display a list of deadlock states in the log. Alternatively, you can model check the <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> property <code>filter(print, \"deadlock\")</code>, which has the safe effect.\n</p>\n<p class='vspace'>To find out <em>how</em> deadlocks occur, i.e. which paths through the model lead to a deadlock state, there are several possibilities. Firstly, you can model check the <a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>CTL</a> property <code>E[F \"deadlock\"]</code>. When checked from the GUI, this will provide you with the option of display a path to a deadlock in the simulator. From the command-line, for example with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock143'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -pf 'E[F \"deadlock\"]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=143' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>a path to a deadlock will be displayed in the log.\n</p>\n<p class='vspace'>Finally, in the eventuality that the model is too large to be model checked, you can still use the <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>simulator</a> to search for deadlocks. This can be done either by manually generating random paths using the <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html#gui'>simulator in the GUI</a> or, <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html#cl'>from the command-line</a>, e.g. by running:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock144'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath deadlock stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=144' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Debugging Models With The Simulator</h1>\n<p>PRISM includes a <em>simulator</em>, a tool which can be used to generate sample paths (executions) through a PRISM model. From the GUI, the simulator allows you to explore a model by interactively generating such paths. This is particularly useful for debugging models during development and for running sanity checks on completed models. Paths can also be generated from the command-line.\n</p>\n<p class='vspace'><a name='gui' id='gui'></a>\n</p><h3>Generating a path in the GUI</h3>\n<p>Once you have loaded a model into the PRISM GUI\n(note that it is not necessary to build the model),\nselect the \"Simulator\" tab at the bottom of the main window.\nYou can now start a new path by double-clicking in the bottom half of the window\n(or right-clicking and selecting \"New path\").\nIf there are undefined constants in the\nmodel (or in any currently loaded properties files) you will be prompted to give values for these. You\ncan also specify the state from which you wish to generate a path. By default, this is the initial state of\nthe model.\n</p>\n<p class='vspace'>The main portion of the user interface (the bottom part) displays a path through the currently loaded model. Initially, this will comprise just a single state. The table above shows the list of available transitions from this state. Double-click one of these to extend the path with this transition. The process can be repeated to extend the path in an interactive fashion. Clicking on any state in the current path shows the transition which was taken at this stage. Click on the final state in the path to continue\nextending the path. Alternatively, clicking the \"Simulate\" button will select a transition randomly (according to the probabilities/rates of the available transitions). By changing the number in the box below this button, you can easily generate random paths of a given length with a single click.\nThere are also options (in the accompanying drop-down menu) to allow generation of paths up until a particular length or, for CTMCs, in terms of the time taken.\n</p>\n<p class='vspace'>The figure shows the simulator in action.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui-sim.png'><img width='500' src='../uploads/gui-sim.png' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI: exploring a model using the simulator</strong></span></div>\n<p class='vspace'>It is also possible to:\n</p>\n<div class='vspace'></div><ul><li>backtrack to an earlier point in a path\n</li><li>remove all of the states before some point in a path\n</li><li>restart a path from its first state\n</li><li>export a path to a text file\n</li></ul><p class='vspace'>Notice that the table containing the path displays not just the value of each variable in each\nstate but also the time spent in that state and any rewards accumulated there. You can configure exactly which columns appear by right-clicking on the path and selecting \"Configure view\". For rewards (and for CTMC models, for the time-values), you can can opt to display the reward/time for each individual state and/or the cumulative total up until each point in the path.\n</p>\n<p class='vspace'>At the top-right of the interface, any labels contained in the currently loaded model/properties file are displayed, along with their value in the currently selected state of the path. In addition, the built-in <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>labels</a> <code>\"init\"</code> and <code>\"deadlock\"</code> are also included. Selecting a label from the list highlights all states in the current path which satisfy it.\n</p>\n<p class='vspace'>The other tabs in this panel allow the value of path operators (taken from properties in the current file) to be viewed for the current path, as well as various other statistics.\n</p>\n<p class='vspace'>Another very useful feature for some models is to use the \"Plot new path\" option from the simulator, which generates a plot of some/all of the variable/reward values for a particular randomly generated path through the model.\n</p>\n<p class='vspace'><a name='cl' id='cl'></a>\n</p><h3>Path generation from the command-line</h3>\n<p>It is also possible to generate random paths through a model using the command-line version of PRISM. This is achieved using the <code>-simpath</code> switch, which requires two arguments, the first describing the path to be generated and the second specifying the file to which the path should be output (as usual, specifying <code>stdout</code> sends output to the terminal). The following examples illustrate the various ways of generating paths in this way:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock145'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -simpath 10 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath time=7.5 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath deadlock path.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=145' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These generate a path of 10 steps, a path of at least 7.5 time units and a path ending in deadlock, respectively.\n</p>\n<p class='vspace'>Here's an example of the output:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock146'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 1 0.007479539729154247 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 2 0.00782819795294666 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 3 0.01570585559933703 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 4 0.017061111948220263 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 5 0.026816317516034468 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 6 0.039878416276337814 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 7 0.04456566315999103 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 8 0.047368359683643765 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 9 0.04934857366557349 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 10 0.055031679365844674 1 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=146' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This shows the sequence of states in the path, i.e. the values of the variables in each state. In the example above, there are 4 variables: <code>s</code>, <code>a</code>, <code>s1</code> and <code>s2</code>.\nThe first three columns show the type of transition taken to reach that state, its index within the path (starting from 0) and the time at which it was entered. The latter is only shown for continuous time models. The type of the transition is written as <em>[act]</em> if action label <code>act</code> was taken, and as <em>module1</em> if the module named <code>module1</code> takes an unlabelled transition). \n</p>\n<p class='vspace'>Further options can also be appended to the first parameter. For example, option <code>probs=true</code> also displays the probability/rate associated with each transition. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock147'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '5,probs=true' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 1 0.0011880118081395378 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 2 0.0037798355025401888 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 3 0.01029212322894221 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 4 0.023258883912578403 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 5 0.027402404026254504 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=147' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this example, the rate is 200.0 for all transitions.\nTo show the state/transition rewards for each step, use option <code>rewards=true</code>.\n</p>\n<p class='vspace'>If you are only interested in values of certain variables of your model, use the <code>vars=(...)</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock148'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '500,probs=true,vars=(a,s1,s2)' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 110 0.5025332771499665 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 111 0.5109407735244359 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 112 0.9960642154887506 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station1 0.5 130 1.0645858553472822 0 1 0</span><br/>\n<span style=\"font-style:italic;\">[loop1b] 200.0 132 1.0732572896618477 1 1 0</span><br/>\n<span style=\"font-style:italic;\">[serve1] 1.0 133 2.939742026148121 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 225 3.4311507854807677 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 227 3.434285492243098 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 228 3.553118276800078 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 250 3.6354431222941406 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 251 3.637552738997181 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 252 3.7343375346150576 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=148' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of single quotes around the path description argument to prevent the shell from misinterpreting special characters such as \"<code>(</code>\".\n</p>\n<p class='vspace'>Notice also that the above only displays states in which the values of some variable of interest changes. This is achieved with the option <code>changes=true</code>, which is automatically enabled when you use <code>vars=(...)</code>. If you want to see all steps of the path, add the option <code>changes=false</code>.\n</p>\n<p class='vspace'>An alternative way of viewing paths is to only display paths at certain fixed points in time. This is achieved with the <code>snapshot=x</code> option, where <code>x</code> is the time step. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock149'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 'time=5.0,snapshot=0.5' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">94 0.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">198 1.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">314 1.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">375 2.0 1 1 1 1</span><br/>\n<span style=\"font-style:italic;\">376 2.5 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">376 3.0 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">378 3.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">378 4.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">478 4.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">511 5.0 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=149' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use the <code>sep=...</code> option to specify the column separator. Possible values are <code>space</code> (the default), <code>tab</code> and <code>comma</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock150'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '10,vars=(a,b),sep=comma' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step,a,b,time</span><br/>\n<span style=\"font-style:italic;\">0,0,0,0.0</span><br/>\n<span style=\"font-style:italic;\">2,1,0,0.058443536856580006</span><br/>\n<span style=\"font-style:italic;\">3,1,1,0.09281024515535738</span><br/>\n<span style=\"font-style:italic;\">6,1,2,0.2556555786269585</span><br/>\n<span style=\"font-style:italic;\">7,1,3,0.284062896359802</span><br/>\n<span style=\"font-style:italic;\">8,1,4,1.1792064236954896</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=150' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When generating paths to a deadlock state, additional <code>repeat=...</code> option is available which will construct multiple paths until a deadlock is found. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock151'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath 'deadlock,repeat=100' stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=151' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, the simulator detects deterministic loops in paths (e.g. if a path reaches a state from which there is a just a single self-loop leaving that state) and stops generating the path any further. You can disable this behaviour with the <code>loopcheck=false</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock152'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">Warning: Deterministic loop detected after 6 steps (use loopcheck=false option to extend path).</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 3</span><br/>\n<span style=\"font-style:italic;\">die 4 7 3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=152' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock153'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10,loopcheck=false stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 2</span><br/>\n<span style=\"font-style:italic;\">die 4 7 2</span><br/>\n<span style=\"font-style:italic;\">die 5 7 2</span><br/>\n<span style=\"font-style:italic;\">die 6 7 2</span><br/>\n<span style=\"font-style:italic;\">die 7 7 2</span><br/>\n<span style=\"font-style:italic;\">die 8 7 2</span><br/>\n<span style=\"font-style:italic;\">die 9 7 2</span><br/>\n<span style=\"font-style:italic;\">die 10 7 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=153' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>One final note: the <code>-simpath</code> switch only generates paths up to the maximum path length setting of the simulator (the default is 10,000). If you want to generate longer paths, either change the\n<a class='wikilink' href='../ConfiguringPRISM/Main.html'>default setting</a> or override it temporarily from the command-line using the <code>-simpathlen</code> switch.\nYou might also use the latter to decrease the setting,\ne.g. to look for a path leading to a deadlock state,\nbut only within 100 steps:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock154'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath deadlock stdout -simpathlen 100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=154' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Exporting The Model</h1>\n<p>If required, once the model has been constructed, it can be exported, either for manual examination or for use in another tool. The following can all be exported:\n</p>\n<div class='vspace'></div><ul><li>the <strong>transition matrix</strong> (or function);\n</li><li>the <strong>rewards</strong> (state/transition) rewards;\n</li><li>the <strong>labels</strong> (in the <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>model</a> or <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>properties</a>) and the states that satisfy them\n</li><li>the definition of (reachable) <strong>states</strong>, i.e., their variable values\n</li><li>the definition of <strong>observations</strong>, i.e., their observable values, for partially observable models\n</li></ul><p class='vspace'>From the command-line version of PRISM, the most convenient and flexible approach is to use the <code>-exportmodel</code> switch.\nThis will, by default, use the extension of the filename(s) to determine the format.\n</p>\n<p class='vspace'>From the GUI, use the \"Model | Export\" menu to export the data to a file or, for small models, use the \"Model | View\" menu to print the details directly to the log. For the case of labels, if you want to export labels from the properties file too, use the \"Properties | Export labels\" option, rather than the \"Model | Export\" one.\n</p>\n<p class='vspace'>The main formats for model export are:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \".tra\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li><li><a class='urllink' href='https://www.graphviz.org/'>Dot</a> format, for a graphical view of the model\n</li></ul><p class='vspace'><a name='explicit' id='explicit'></a>\n</p><h3>Plain text (explicit files)</h3>\n<p>This format exports different parts of the model in different file, with the expected filename extensions being:\n</p>\n<div class='vspace'></div><ul><li><code>.tra</code> - transition matrix\n</li><li><code>.srew</code>, <code>.trew</code>, <code>.rew</code> - rewards: states, transitions or both\n</li><li><code>.lab</code> - labels\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>To export just the transition matrix in this format, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock155'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=155' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To export multiple parts, use, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock156'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=156' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you omit the file basename of the export files and the basename of the model will be used, so this is equivalent to the above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock157'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel .tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=157' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can use the shorthand <code>.all</code> to export everything, and <code>.rew</code> to export both state and transition rewards. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock158'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=158' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can always use <code>stdout</code> instead of a filename. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock159'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=159' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is a quick way to print all details (of a small model) to the terminal.\n</p>\n<p class='vspace'>The labels (<code>.lab</code>) export includes the built-in labels <code>\"init\"</code> and <code>\"deadlock\"</code>,\nproviding a way to export information about initial states and (fixed) deadlock states.\n</p>\n<p class='vspace'>When there are multiple reward structures, a separate file is created for each one and a (1-indexed) suffix is added to distinguish them.\nBy default, a header in each file (see the \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html#srew'>Explicit Model Files</a>\" appendix) also shows the name of the reward structure.\nThis can be omitted - see the options below - or via the option \"Include headers in model exports\" in the GUI.\n</p>\n<p class='vspace'><a name='umb' id='umb'></a>\n</p><h3>UMB (Unified Markov binary) format</h3>\n<p>UMB is a binary format that can incorporate all parts of the model listed above.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock160'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=160' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, everything is included. You can omit some parts with the <code>-exportmodel</code>\noptions <code>rewards</code>, <code>labels</code>, <code>states</code> and <code>obs</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock161'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb:states=false,rewards=false</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=161' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For a small model, you can also see a textual version of the UMB format\nusing file extension <code>.umbt</code> (or option <code>text</code>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock162'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.umbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=162' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also configure the compression used: <code>zip=false</code> turns it off,\n<code>zip=gzip</code> uses gzip and <code>zip=xz</code> uses xz (smaller but slower to read/write).\n</p>\n<p class='vspace'><a name='other' id='other'></a>\n</p><h3>Other formats and options</h3>\n<p>If the file extension is not recognised, PRISM defaults to plain text (explicit) format.\nYou can always override this using the @format@ option, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock163'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=umb,text</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=163' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can perform multiple model exports using several instances of <code>-exportmodel</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock164'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit -exportmodel model.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=164' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Other file formats are also available:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://www.mathworks.com/'>Matlab</a> code (extension <code>.m</code>) or <code>format=matlab</code>\n</li><li>Storm's DRN model format (extension <code>.drn</code>) or <code>format=drn</code>\n</li></ul><p class='vspace'>Other <code>-exportmodel</code> options are:\n</p>\n<div class='vspace'></div><ul><li><code>actions</code> (=<code>true</code>/<code>false</code>) - whether to  actions on choices/transitions\n</li><li><code>precision</code> (=<code>&lt;n&gt;</code>) - use <code>&lt;n&gt;</code> significant figures for floating point values (in text)\n</li><li><code>headers</code> (<code>=true/false</code>) - whether to include headers when exporting rewards\n</li><li><code>rows</code> - export matrices with one row/distribution on each line (plain text)\n</li><li><code>proplabels</code> - also export labels from a properties file into a <code>.lab</code> file\n</li></ul><p class='vspace'>For plain text export, although <code>-exportmodel</code> is now usually the best switch to use,\nother older switches still exist. For example, you can export individual files using\n<code>-exporttrans &lt;file&gt;</code>,\n<code>-exportstates &lt;file&gt;</code>,\n<code>-exportstaterewards &lt;file&gt;</code>,\n<code>-exporttransrewards &lt;file&gt;</code>,\n<code>-exportrewards &lt;file&gt; &lt;file&gt;</code>,\n<code>-exportlabels &lt;file&gt;</code>, and\n<code>-exportproplabels &lt;file&gt;</code>.\nAnd you can use switches\n<code>-exportmodelprecision &lt;x&gt;</code>,\n<code>-exportmatlab</code> and\n<code>-exportrows</code>\nto specify format options affecting all of them.\n</p>\n<p class='vspace'><a name='scc' id='scc'></a>\n</p><h3>Exporting (B)SCCs and end components</h3>\n<p>It is also possible to export the set of (bottom) strongly connected components (SCCs or BSCCs) for a model. This can only be done from the command-line currently. Use, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock165'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportsccs stdout</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportbsccs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=165' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For an MDP, you can also export the set of maximal end components (MECs):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock166'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -exportmecs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=166' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<h1>Model Checking</h1>\n<p>Typically, once a model has been constructed, it is analysed through model checking.\nProperties are specified as described in the \"<a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\" section,\nand are usually kept in files with extensions <code>.props</code>, <code>.pctl</code> or <code>.csl</code>.\nThere are properties files accompanying most of the sample PRISM models in the <code>prism-examples</code> directory.\n</p>\n<p class='vspace'>\n</p><h3>GUI</h3>\n<p>To load a file containing properties into the GUI, select menu option \"Properties | Open properties list\".\nThe file can only be loaded if there are no errors, otherwise an error is displayed.\nNote that it may be necessary to have loaded the corresponding model first,\nsince the properties will probably make reference to variables (and perhaps constants) declared in the model file.\nOnce loaded, the properties contained in the file are displayed in a list in the \"Properties\" tab of the GUI.\nConstants and labels are displayed in separate lists below.\nYou can modify or create new properties, constants and labels from the GUI,\nby right-clicking on the appropriate list and selecting from the pop-up menu which appears. Properties with errors are shaded red and marked with a warning sign.\nPositioning the mouse pointer over the property displays the corresponding error message.\n</p>\n<p class='vspace'>The pop-up menu for the properties list also contains a \"Verify\" option,\nwhich allows you instruct PRISM to model check the currently selected properties\n(hold down Ctrl/Cmd to select more than one property simultaneously).\nAll properties can be model checked at once by selecting \"Verify all\".\nPRISM verifies each property individually.\nUpon completion, the icon next to the property changes according to the result of model checking. For Boolean-valued properties, a result of true or false is indicated by a green tick or red cross, respectively. For properties which have a numerical result (e.g. <code>P=? [ ...]</code>), position the mouse pointer over the property to view the result.\nIn addition, this and further information about model checking is displayed in the log in the \"Log\" tab.\n</p>\n<p class='vspace'>\n</p><h3>Command-line</h3>\n<p>From the command-line, model checking is achieved by passing both a model file and a properties file as arguments, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock167'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=167' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The results of model checking are sent to the display and are as described above for the GUI version.\nBy default, all properties in the file are checked.\nTo model check only a single property, use the <code>-prop</code> switch.\nFor example, to check only the fourth property in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock168'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=168' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or to check only the property with <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#names'>name</a> \"safe\" in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock169'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=169' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also provide a comma-separated list of multiple properties to check,\nusing neither numerical indices or property names:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock170'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4,5,safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=170' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, the contents of a properties file can be specified directly from the command-line, using the <code>-pf</code> switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock171'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -pf 'P&gt;=0.5 [ true U&lt;=5 (s=1 &amp; a=0) ]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=171' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The switches <code>-pctl</code> and <code>-csl</code> are aliases for <code>-pf</code>.\n</p>\n<p class='vspace'>Note the use of single quotes (<code>'...'</code>) to avoid characters such as\n<code>(</code> and <code>&gt;</code> being interpreted by the command-line shell.\nSingle quotes are preferable to double quotes since PRISM properties often include double quotes, e.g. for references to labels or properties.\n</p><hr />\n<h1>Approximate Model Checking</h1>\n<p>The discrete-event simulator built into PRISM (see the section \"<a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\") can also be used to generate <em>approximate</em> results for PRISM properties, a technique often called <em>statistical model checking</em>. Essentially, this is achieved by <em>sampling</em>: generating a large number of random paths through the model, evaluating the result of the given properties on each run, and using this information to generate an approximately correct result. This approach is particularly useful on very large models when normal model checking is infeasible. This is because discrete-event simulation is performed using the PRISM language model description, without explicitly constructing the corresponding probabilistic model.\n</p>\n<p class='vspace'>Currently, statistical model checking can only be applied to <code><strong>P</strong></code> or <code><strong>R</strong></code> operators\nand does not support LTL-style path properties or <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\nThere are also a few restrictions on the modelling language features that can be used; see below for details.\n</p>\n<p class='vspace'>To use this functionality, load a model and some properties into PRISM, as described in the previous sections. To generate an approximate value for one or more properties, select them in the list, right-click and select \"Simulate\" (as opposed to \"Verify\"). As usual, it is first necessary to provide values for any undefined constants. Subsequently, a dialog appears. Here, the state from which approximate values are to be computed (i.e. from which the paths will be generated) can be selected. By default, this is the initial state of the model. The other settings in the dialog concern the methods used for simulation.\n</p>\n<p class='vspace'>PRISM supports four different methods for performing statistical model checking:\n</p>\n<div class='vspace'></div><ul><li>CI (Confidence Interval)\n</li><li>ACI (Asymptotic Confidence Interval)\n</li><li>APMC (Approximate Probabilistic Model Checking)\n</li><li>SPRT (Sequential Probability Ratio Test)\n</li></ul><p class='vspace'>The first three of these are intended primarily for \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>quantitative</a>\" properties (e.g. of the form <code><strong>P</strong>=?[...]</code>), but can also be used for \"bounded\" properties (e.g. of the form <code><strong>P</strong>&lt;p[...]</code>). The SPRT method is only applicable to \"bounded\" properties.\n</p>\n<p class='vspace'>Each method has several parameters that control its execution, i.e. the number of samples that are generated and the accuracy of the computed approximation. In most cases, these parameters are inter-related so one of them must be left unspecified and its value computed automatically based on the others. In some cases, this is done before simulation; in others, it must be done afterwards.\n</p>\n<p class='vspace'>Below, we describe each method in more detail.\nFor simplicity, we describe the case of checking a <code><strong>P</strong></code> operator.\nDetails for the case of an <code><strong>R</strong></code> operator can be found in [<a class='wikilink' href='References.html#Nim10'>Nim10</a>].\n</p>\n<div class='vspace'></div><h3>CI (Confidence Interval) Method</h3>\n<p>The CI method gives a <em>confidence interval</em> for the approximate value generated for a <code><strong>P</strong>=?</code> property, based on a given <em>confidence level</em> and the number of samples generated.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Width\" (<em>w</em>)\n</li><li>\"Confidence\" (<em>alpha</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Let <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated.\nThe confidence interval is [<em>Y-w</em>,<em>Y+w</em>], i.e. <em>w</em> gives the half-width of the interval.\nThe confidence level, which is usually stated as a percentage, is 100(1-<em>alpha</em>)%.\nThis means that the actual value <em>X</em> should fall into the confidence interval [<em>Y-w</em>,<em>Y+w</em>] 100(1-<em>alpha</em>)% of the time.\n</p>\n<p class='vspace'>To determine, for example, the width <em>w</em> for given <em>alpha</em> and <em>N</em>,\nwe use <em>w</em> = <em>q</em> * sqrt(<em>v</em> / <em>N</em>) where\n<em>q</em> is a quantile, for probability 1-<em>alpha</em>/2, from the Student's t-distribution with <em>N</em>-1 degrees of freedom and <em>v</em> is (an estimation of) the variance for <em>X</em>.\nSimilarly, we can determine the required number of iterations, from <em>w</em> and <em>alpha</em>,\nas N = (<em>v</em> * <em>q</em><sup>2</sup>)/<em>w</em><sup>2</sup>, where <em>q</em> and <em>v</em> are as before.\n</p>\n<p class='vspace'>For a bounded property  <code><strong>P</strong>~p[...]</code>, the (Boolean) result is determined according to the generated approximation for the probability. This is not the case, however, if the threshold <em>p</em> falls within the confidence interval [<em>Y-w</em>,<em>Y+w</em>], in which case no value is returned.\n</p>\n<div class='vspace'></div><h3>ACI (Asymptotic Confidence Interval) Method</h3>\n<p>The ACI method works in exactly same fashion as the CI method, except that it uses the Normal distribution to approximate the Student's t-distribution when determining the confidence interval. This is appropriate when the number of samples is large (because we can get a reliable estimation of the variance from the samples) but may be less accurate for small numbers of samples.\n</p>\n<div class='vspace'></div><h3>APMC (Approximate Probabilistic Model Checking) Method</h3>\n<p>The APMC method, based on [<a class='wikilink' href='References.html#HLMP04'>HLMP04</a>], offers a probabilistic guarantee on the accuracy of the  approximate value generated for a <code><strong>P</strong>=?</code> property, based on the Chernoff-Hoeffding bound.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Approximation\" (<em>epsilon</em>)\n</li><li>\"Confidence\" (<em>delta</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Letting <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated, we have:\n</p>\n<div class='vspace'></div><ul><li>Prob(|<em>Y</em>-<em>X</em>| &gt; <em>epsilon</em>) &lt; <em>delta</em>\n</li></ul><p class='vspace'>where the parameters are related as follows:\n<em>N</em> = ln(2/<em>delta</em>) / 2<em>epsilon</em><sup>2</sup>.\nThis imposes certain restrictions on the parameters,\nnamely that <em>N</em>(<em>epsilon</em><sup>2</sup>) &#8805; ln(2/delta)/2.\n</p>\n<p class='vspace'>In similar fashion to the CI/ACI methods, the APMC method can be also be used for bounded properties such as <code><strong>P</strong>~p[...]</code>, as long as the threshold <em>p</em> falls outside the interval [<em>Y-epsilon</em>,<em>Y+epsilon</em>].\n</p>\n<div class='vspace'></div><h3>SPRT (Sequential Probability Ratio Test) Method</h3>\n<p>The SPRT method is specifically for bounded properties, such as <code><strong>P</strong>~p[...]</code> and is based on <em>acceptance sampling</em> techniques [<a class='wikilink' href='References.html#YS02'>YS02</a>]. It uses Wald's sequential probability ratio test (SPRT), which generates a succession of samples, deciding on-the-fly when an answer can be given with a sufficiently high confidence.\n</p>\n<p class='vspace'>The parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Indifference\" (<em>delta</em>)\n</li><li>\"Type I/II error\" (<em>alpha</em>/<em>beta</em>)\n</li></ul><p class='vspace'>Consider a property of the form <code><strong>P</strong>&#8805;p[...]</code>. The parameter <em>delta</em> is used as the half-width of an <em>indifference region</em> [p-delta,p+delta]. PRISM will attempt to determine whether either the hypothesis <code><strong>P</strong>&#8805;(p+delta)[...]</code> or <code><strong>P</strong>&#8804;(p-delta)[...]</code> is true, based on which it will return either <code>true</code> or <code>false</code>, respectively. The parameters <em>alpha</em> and <em>beta</em> represent the probability of the occurrence of a <em>type I error</em> (wrongly accepting the first hypothesis) and a <em>type II error</em> (wrongly accepting the second hypothesis), respectively. For simplicity, PRISM assigns the same value to both <em>alpha</em> and <em>beta</em>.\n</p>\n<div class='vspace'></div><h3>Maximum Path Length</h3>\n<p>Another setting that can be configured from the \"Simulation Parameters\" dialog is the maximum length of paths generated by PRISM during statistical model checking. In order to perform statistical model checking, PRISM needs to evaluate the property being checked along every generated path. For example, when checking <code>P=? [ F&lt;=10 \"end\" ]</code>, PRISM must check whether <code>F&lt;=10 \"end\"</code> is true for each path. On this example (assuming a discrete-time model), this can always be done within the first 10 steps. For a property such as <code>P=? [ F \"end\" ]</code>, however, there may be paths along which no finite fragment can show <code>F \"end\"</code> to be true or false. So, PRISM imposes a maximum path length to avoid the need to generate excessively long (or infinite) paths.\nThe default maximum length is 10,000 steps.\nIf, for a given property, statistical model checking results in one or more paths on which the property cannot be evaluated, an error is reported.\n</p>\n<div class='vspace'></div><h3>Command-line Statistical Model Checking</h3>\n<p>Statistical model checking can also be enabled from the command-line version of PRISM, by including the <code>-sim</code> switch. The default methods used are CI (Confidence Interval) for \"quantitative\" properties and SPRT (Sequential Probability Ratio Test) for \"bounded\" properties. To select a particular method, use switch <code>-simmethod &lt;method&gt;</code> where <code>&lt;method&gt;</code> is one of <code>ci</code>, <code>aci</code>, <code>apmc</code> and <code>sprt</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock172'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.pctl -prop 1 -sim -simmethod aci</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=172' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM has default values for the various simulation method parameters, but these can also be specified using the switches <code>-simsamples</code>, <code>-simconf</code>, <code>-simwidth</code> and <code>-simapprox</code>. The exact meaning of these switches for each simulation method is given in the table below.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><strong>CI</strong></td><td  align='center'><strong>ACI</strong></td><td  align='center'><strong>APMC</strong></td><td  align='right'><strong>SPRT</strong></td></tr>\n<tr ><td  align='center'><code>-simsamples</code></td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='right'>n/a</td></tr>\n<tr ><td  align='center'><code>-simconf</code></td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='right'>\"Type I/II error\"</td></tr>\n<tr ><td  align='center'><code>-simwidth</code></td><td  align='center'>\"Width\"</td><td  align='center'>\"Width\"</td><td  align='center'>n/a</td><td  align='right'>\"Indifference\"</td></tr>\n<tr ><td  align='center'><code>-simapprox</code></td><td  align='center'>n/a</td><td  align='center'>n/a</td><td  align='center'>\"Approximation\"</td><td  align='right'>n/a</td></tr>\n</table>\n<p class='vspace'>The maximum length of simulation paths is set with switch <code>-simpathlen</code>.\n</p>\n<div class='vspace'></div><h3>Limitations</h3>\n<p>Currently, the simulator does not support every part of the PRISM modelling languages. For example, it does not handle models with multiple initial states or with <code><strong>system</strong>...<strong>endsystem</strong></code> definitions.\n</p>\n<p class='vspace'>It is also worth pointing out that statistical model checking techniques are not well suited to models that exhibit nondeterminism, such as MDPs. This because the techniques rely on generation of <em>random</em> paths, which are not well defined for a MDP. PRISM does allow statistical model checking to be performed on an MDP, but does so by simply resolving nondeterministic choices in a (uniformly) random fashion (and displaying a warning message). Currently PTAs are not supported by the simulator.\n</p><hr />\n<h1>Computing Steady-state And Transient Probabilities</h1>\n<p>If the model is a CTMC or DTMC, it is possible to compute corresponding vectors of\nsteady-state or transient probabilities directly\n(rather than indirectly by analysing a property which requires their computation).\nFrom the GUI, select an option from the \"Model | Compute\" menu.\nFor transient probabilities, you will be asked to supply the\ntime value for which you wish to compute probabilities.\nFrom the command-line, add the <code>-steadystate</code> (or <code>-ss</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock173'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=173' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for steady-state probabilities or the <code>-transient</code> (or <code>-tr</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock174'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=174' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for transient probabilities, again specifying a time value in the latter case.\nThe probabilities are computed for all states of the model and displayed,\neither on the screen (from the command-line) or in the log (from the GUI).\n</p>\n<p class='vspace'>To instead export the vector of computed probabilities to a file, use the \"Model | Compute/export\" option from the GUI, or the <code>-exportsteadystate</code> (or <code>-exportss</code>) and <code>-exporttransient</code> (or <code>-exporttr</code>) switches from the command-line:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock175'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss -exportss poll2-ss.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=175' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the command-line, you can request that the probability vectors exported are in Matlab format by adding the <code>-exportmatlab</code> switch.\n</p>\n<div class='vspace'></div><h3>Initial probability distributions</h3>\n<p>By default, for both steady-state and transient probability computation,\nPRISM assumes that the initial probability distribution of the model is\nan equiprobable choice over the set of initial states.\nYou can override this and provide a specific initial distribution. This is done using the <code>-importinitdist</code> switch. The format for this imported distribution is identical to the ones exported by PRISM, i.e. simply a list of probabilities for all states separated by new lines. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock176'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -exporttr poll2-tr1.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -importinitdist poll2-tr1.txt -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=176' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is (essentially) equivalent to this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock177'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=177' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Ranges of time values</h3>\n<p>Finally, you can compute transient probabilities for a range of time values, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock178'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 0.1:0.01:0.2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=178' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which computes transient probabilities for the time points 0.1, 0.11, 0.12, .., 0.2. In this case, the computation is done incrementally, with probabilities for each time point being computed from the previous point for efficiency.\n</p><hr />\n<h1>Experiments</h1>\n<p>PRISM supports <em>experiments</em>, which is a way of automating multiple instances of model checking.\nThis is done by leaving one or more <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a> undefined, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock179'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=179' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This can be done for constants in the model file, the properties file, or both.\nBefore any verification can be performed, values must be provided for any such constants. In the GUI, a dialog appears in which the user is required to enter values. From the command line, the <code>-const</code> switch must be used, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock180'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=180' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To run an experiment, provide a <em>range</em> of values for one or more of the constants. Model checking will be performed for all combinations of the constant values provided. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock181'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4:6,T=60:10:100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=181' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>N=4:6</code> means that values of 4,5 and 6 are used for <code>N</code>,\nand <code>T=60:10:100</code> means that values of 60, 70, 80, 90 and 100 (i.e. steps of 10) are used for <code>T</code>.\n</p>\n<p class='vspace'>For convenience, constant specifications can be split across separate instances of the <code>-const</code> switch, if desired.\nYou can also specify double-valued constants as fractions rather than decimals. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock182'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9 -const p=1/3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=182' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, the same thing can be achieved by selecting a single property,\nright clicking on it and selecting \"New experiment\"\n(or alternatively using the popup menu in the \"Experiments\" panel).\nValues or ranges for each undefined constant can then be supplied in the resulting dialog.\nDetails of the new experiment and its progress are shown in the panel.\nTo stop the experiment before it has completed, click the red \"Stop\" button and it will\nhalt after finishing the current iteration of model checking.\nOnce the experiment has finished, right clicking on the experiment produces a pop-up menu,\nfrom which you can view the results of the experiment or export them to a file.\n</p>\n<p class='vspace'>For experiments based on properties which return numerical results, you can also use the GUI to plot graphs of the results.\nThis can be done either before the experiment starts, by selecting the \"Create graph\" tick-box in the dialog used to create the experiment\n(in fact this box is ticked by default), or after the experiment's completion, by choosing \"Plot results\" from the pop-up menu on the experiment.\nA dialog appears, where you can choose which constant (if there are more than one) to use for the x-axis of the graph,\nand for which values of any other constants the results should be plotted.\nThe graph will appear in the panel below the list of experiments.\nRight clicking on a graph and selecting \"Graph options\" brings up a dialog from which many properties of the graph can be configured.\nFrom the pop-up menu of a graph, you can also choose to print the graph (to a printer or Postscript file)\nor export it in a variety of formats:\nas an image (PNG or JPEG),\nas an encapsulated Postscript file (EPS),\nin an XML-based format (for reloading back into PRISM),\nor as code which can be used to generate the graph in Matlab.\n</p>\n<p class='vspace'>Approximate computation of quantitive results obtained with the <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>simulator</a> can also be used on experiments. In the GUI, select the \"Use Simulation\" option when defining the parameters for the experiment. From the command-line, just add the <code>-sim</code> switch as usual.\n</p>\n<p class='vspace'><a name='exportresults' id='exportresults'></a>\n</p><h3>Exporting results</h3>\n<p>You can export all the results from an experiment to a file or to the screen. From the command-line, use the <code>-exportresults</code> switch, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock183'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=183' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send to output file <code>res.txt</code>, or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock184'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=184' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send the results straight to the screen. From the GUI, right click on the experiment and select \"Export results\".\n</p>\n<p class='vspace'>The default behaviour is to export a <em>list</em> of results in <em>text</em> form, using tabs to separate items. The above examples produce:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock185'>\r\n  <div class='sourceblocktext'><div class=\"text\">N &nbsp; &nbsp; &nbsp; T &nbsp; &nbsp; &nbsp; Result<br />\n4 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n4 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 4.707364688019771E-6<br />\n4 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 1.3126420636755292E-5<br />\n5 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n5 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 3.267731327728599E-6<br />\n5 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=185' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can change the format in which the results are exported by appending one or more comma-separated options to the end of the <code>-exportresults</code> switch, for example to export in CSV (comma-separated values) format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock186'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=186' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock187'>\r\n  <div class='sourceblocktext'><div class=\"text\">N, T, Result<br />\n4, 0, 0.0<br />\n4, 10, 4.707364688019771E-6<br />\n4, 20, 1.3126420636755292E-5<br />\n5, 0, 0.0<br />\n5, 10, 3.267731327728599E-6<br />\n5, 20, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=187' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock188'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:dataframe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=188' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock189'>\r\n  <div class='sourceblocktext'><div class=\"text\">N,T,Result<br />\n4,0,0<br />\n4,10,4.70736468802e-06<br />\n4,20,1.31264206368e-05<br />\n5,0,0<br />\n5,10,3.26773132773e-06<br />\n5,20,8.34357506036e-06</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=189' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also add the <code>matrix</code> option, to export the results as one or more 2D matrices, rather than a list.\nThis is particularly useful if you want to create a surface plot from results that vary over two constants.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock190'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv,matrix</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=190' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock191'>\r\n  <div class='sourceblocktext'><div class=\"text\">&quot;N\\T&quot;<br />\n, 0.0, 10.0, 20.0<br />\n4, 0.0, 4.707364688019771E-6, 1.3126420636755292E-5<br />\n5, 0.0, 3.267731327728599E-6, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=191' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>matrix</code> option is also available in normal (non-CSV) mode.\n</p>\n<p class='vspace'>You can also export results in the form of comments, used by PRISM's <a class='urllink' href='https://github.com/prismmodelchecker/prism/wiki/Regression-Testing'>regression testing</a> functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock192'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:comment</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=192' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock193'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// RESULT (N=4,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=10): 4.707364688019771E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=20): 1.3126420636755292E-5</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=10): 3.267731327728599E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=20): 8.343575060356386E-6</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=193' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, it is also possible to <em>import</em> previously exported results (in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format).\n</p>\n<p class='vspace'>A related option is the <code>-exportvector &lt;file&gt;</code> switch, useful in general contexts, not for experiments.\nThis exports the results for all states of the model\n(typically, the log just displays the result for the initial state, unless a <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> has been used)\nto the the file <code>file</code>.\n</p><hr />\n<h1>Strategies</h1>\n<p>Properties to be model checked on MDPs (and their variants, such as POMDPs or IMDPs) usually quantify over <em>strategies</em> (or <em>policies</em>) of the model, i.e., over the different possible ways that nondeterminism can be resolved in the model.\nFor example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock194'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=194' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>determines the maximum probability, over all strategies, of reaching a state satisfying the label <code>\"goal\"</code>. When checking such properties, you can also ask PRISM to generate a corresponding (optimal) strategy, which yields this maximum probability when followed. The strategy can then be viewed, exported or simulated.\n</p>\n<p class='vspace'><strong>Note:</strong> For consistency across models, PRISM now uses the terminology <em>strategy</em> (rather than alternatives such as <em>policy</em>). In older versions of the tool, these were referred to as <em>adversaries</em>. Currently, the newer (and more extensive) <em>strategy generation</em> functionality is implemented just for the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>\"explicit\"</a> model checking engine,\nwhich is used automatically if strategy generation is requested.\nThe old <em>adversary generation</em> functionality (see below) still exists for the \"sparse\" engine, but will be updated in the future.\n</p>\n<p class='vspace'><strong>Generating strategies</strong>. Optimal strategies can be generated either from the command-line or the graphical user interface (GUI). For the former, use the <code>-exportstrat</code> switch. Simple examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock195'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat stdout</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.tra</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=195' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, you can trigger strategy generation by ticking the \"Generate strategy\" box either on the popup menu that appears when you right-click a property, or from the \"Strategies\" menu at the top. As long as it is supported, a strategy will be then generated once \"Verify\" is clicked.\n</p>\n<p class='vspace'>From the same menu(s), you can then\n</p>\n<div class='vspace'></div><ul><li>export the strategy to a file\n</li><li>view the strategy by printing it in the log\n</li><li>explore the strategy in the simulator\n</li></ul><p class='vspace'><strong>Strategy export types</strong>. Strategies can be viewed or exported in several different formats:\n</p>\n<p class='vspace'>(i) <em>Action list</em>. This is a list of the action taken in each state of the model, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock196'>\r\n  <div class='sourceblocktext'><div class=\"text\">(0,0):east<br />\n(0,1):north<br />\n(0,2):north<br />\n(1,0):south<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=196' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where states, by default, are shown as a tuple of variable values.\n</p>\n<p class='vspace'>(ii) <em>Induced model</em>. This is a representation of the model that is induced when the strategy is applied. There are two \"modes\" for this export. The first (and default) is \n<em>reduce</em>, which removes the nondeterminism resolved by the strategy (e.g., an MDP becomes a DTMC). This can be useful to re-import the model back into PRISM and analyse the induced model. The second is <em>restrict</em>, which shows the original model but with a restricted set of choices (e.g., an MDP with just one choice in each state). In each case, the transitions of the induced model are presented as a <code>.tra</code> file (as for normal <a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>model export</a>), e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock197'>\r\n  <div class='sourceblocktext'><div class=\"text\">9 11<br />\n0 5 1 east<br />\n1 10 1 north<br />\n2 15 0.9 north<br />\n2 16 0.1 north<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=197' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>(iii) <em>Dot file</em>. This is, like the previous format, a view of the model induced by the strategy, but in <a class='urllink' href='http://www.graphviz.org'>Dot</a> format, which allows it to be visualised.\n</p>\n<p class='vspace'><strong>Configuring strategy export</strong>. \nAs hinted in the command-line examples above, the <code>-exportstrat</code> switch uses the file extension to determine the preferred format: if the strategy is exported to a file with extension <code>.tra</code> or <code>.dot</code>, then it uses an induced model or Dot file, respectively. Otherwise, the default is an action list. You can specify the desired format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock198'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=actions</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=198' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Further options can be added, e.g., to specify whether an induced model is exported in \"restrict\" or \"reduce\" mode:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock199'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced,mode=restrict</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=199' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A full list of available options is as follows:\n</p>\n<div class='vspace'></div><ul><li><code>type</code> (<code>actions</code>, <code>induced</code> or <code>dot</code>): the type of strategy export to use (action list, induced model or Dot file)\n</li><li><code>mode</code> (<code>restrict</code> or <code>reduce</code>): when exporting as an induced model or Dot file, whether to \"restrict\" or \"reduce\" the model (see above); the default is \"restrict\"\n</li><li><code>reach</code> (<code>true</code> or <code>false</code>): whether to restrict the strategy to states that are reachable when it is applied to the model (this is currently only used for exporting induced models and Dot files, and the default value is false and true, respectively, in these two cases)\n</li><li><code>states</code> (<code>true</code> or <code>false</code>): whether to show states, rather than state indices, for actions lists or Dot files; this is true by default\n</li><li><code>obs</code> (<code>true</code> or <code>false</code>): for partially observable models, whether to merge observationally equivalent states; this is true by default\n</li></ul><p class='vspace'><strong>Strategy types</strong>. PRISM generates several types of strategies. The simplest are <em>memoryless deterministic</em> strategies, which pick a single action in each state, as in the examples above. For some query types (e.g., step-bounded properties, or LTL-based properties), <em>finite-memory</em> strategies are generated, where an additional memory value is used. For these, induced models or Dot files are most useful since they will also show how the memory values are updated as the strategy is executed. Note that, in these cases, the state indices of the strategy will correspond to the product model constructed during model checking, not the original model. The product model can be exported using the <code>-exportprodtrans</code> and <code>-exportprodstates</code> switches.\n</p>\n<p class='vspace'><strong>Adversary generation</strong>. As mentioned above, the \"sparse\" model checking engine still includes older so-called \"adversary generation\" functionality. This can be used to export the induced model to a file using the <code>-exportadv</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock200'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadv adv.tra -s</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadvmdp adv.tra -s</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=200' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where the <code>-exportadv</code> and <code>-exportadvmdp</code> export a DTMC and an MDP, respectively, i.e., corresponding to the \"reduce\" and \"restrict\" modes described above.\nFrom the GUI, change the \"Adversary export\" option (under the \"PRISM\" settings) from \"None\" to \"DTMC\" or \"MDP\". You can also change the filename for the export adversary which, by default, is <code>adv.tra</code> as in the example above.\n</p><hr />\n<h1>Support For PEPA Models</h1>\n<p>For CTMCs, PRISM also accepts model descriptions in the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='References.html#Hil96'>Hil96</a>].\nThe tool compiles such descriptions into the PRISM language and then constructs the model as normal.\nThe language accepted by the PEPA to PRISM compiler is actually a subset of PEPA.\nThe restrictions applied to the language are firstly that component identifiers can only be bound to sequential components\n(formed using prefix and choice and references to other sequential components only).\nSecondly, each local state of a  sequential component must be named.  For example, we would rewrite:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).(b,s).P;\n</li></ul><p class='vspace'>as:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).P';\n</li><li>P' = (b,s).P;\n</li></ul><p class='vspace'>Finally, active/active synchronisations are not allowed since the PRISM \ndefinition of these differs from the PEPA definition.  Every PEPA \nsynchronisation must have exactly one active component.\nSome examples of PEPA model descriptions which can be imported into PRISM\ncan be found in the <code>prism-examples/pepa</code> directory.\n</p>\n<p class='vspace'>From the command-line version of PRISM, add the <code>-importpepa</code> switch and the model will be treated as a PEPA description.\nFrom the GUI, select \"Model | Open model\" and then choose \"PEPA models\"\non the \"Files of type\" drop-down menu.\nAlternatively, select \"Model | New | PEPA model\" and either type a description from scratch\nor paste in an existing one from elsewhere.\nOnce the PEPA model has been successfully parsed by PRISM,\nyou can view the corresponding PRISM code (as generated by the PEPA-to-PRISM compiler)\nby selecting menu option \"Model | View | Parsed PRISM model\".\n</p><hr />\n<h1>Support For SBML</h1>\n<p>PRISM includes a (prototype) tool to translate specifications in <a class='urllink' href='http://sbml.org/'>SBML</a> (Systems Biology Markup Language) to model descriptions in the PRISM language. SBML is an XML-based format for representing models of biochemical reaction networks. The translator currently works with Level 2 Version 1 of the SBML specification, details of which can be found <a class='urllink' href='http://sbml.org/documents/'>here</a>.\n</p>\n<p class='vspace'>Since PRISM is a tool for analysing discrete-state systems, the translator is designed for SBML files intended for discrete stochastic simulation. A useful set of such files can be found in the CaliBayes <a class='urllink' href='http://code.google.com/p/dsmts/'>Discrete Stochastic Model Test Suite</a>. There are also many more SBML files available in the <a class='urllink' href='http://www.ebi.ac.uk/biomodels/'>BioModels Database</a>.\n</p>\n<p class='vspace'>We first give a simple example of an SBML file and its PRISM translation. We then give some more precise details of the translation process.\n</p>\n<div class='vspace'></div><h3>Example</h3>\n<p>An SBML file comprises a set of <em>species</em> and a set of <em>reactions</em> which they undergo. Below is the SBML file for the simple reversible reaction: <strong>Na + Cl &#8596; Na<sup>+</sup> + Cl<sup>-</sup></strong>, where there are initially 100 Na and Cl atoms and no ions, and the base rates for the forwards and backwards reactions are 100 and 10, respectively.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock201'>\r\n  <div class='sourceblocktext'><div class=\"xml\"><span class=\"re1\">&lt;?xml</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1.0&quot;</span> <span class=\"re0\">encoding</span>=<span class=\"st0\">&quot;UTF-8&quot;</span><span class=\"re2\">?&gt;</span><br />\n<span class=\"re1\">&lt;sbml</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.sbml.org/sbml/level2&quot;</span> <span class=\"re0\">metaid</span>=<span class=\"st0\">&quot;_000000&quot;</span> <span class=\"re0\">level</span>=<span class=\"st0\">&quot;2&quot;</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; <span class=\"re1\">&lt;model</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;nacl&quot;</span> <span class=\"re0\">name</span>=<span class=\"st0\">&quot;Na+Cl&quot;</span><span class=\"re2\">&gt;</span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;compartment</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;compartment&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na_plus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl_minus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactions<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>forwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;100&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>backwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na_plus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl_minus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;10&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactions<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; <span class=\"re1\">&lt;/model<span class=\"re2\">&gt;</span></span><br />\n<span class=\"re1\">&lt;/sbml<span class=\"re2\">&gt;</span></span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=201' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And here is the resulting PRISM code:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock202'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// File generated by automatic SBML-to-PRISM conversion</span><br/>\n<span class=\"prismcomment\">// Original SBML file: nacl.xml</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">MAX_AMOUNT</span> = <span class=\"prismnum\">100</span>;<br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction forwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">forwards_rate</span> = <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// forwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction backwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">backwards_rate</span> = <span class=\"prismnum\">10</span>; <span class=\"prismcomment\">// backwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na</span><br/>\n<br/>\n\t<span class=\"prismident\">na</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">na</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na</span> &lt;= <span class=\"prismident\">na_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl</span><br/>\n<br/>\n\t<span class=\"prismident\">cl</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">cl</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl</span> &lt;= <span class=\"prismident\">cl_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na_plus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_plus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na_plus</span><br/>\n<br/>\n\t<span class=\"prismident\">na_plus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_plus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na_plus</span> &lt;= <span class=\"prismident\">na_plus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">na_plus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl_minus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_minus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl_minus</span><br/>\n<br/>\n\t<span class=\"prismident\">cl_minus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_minus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl_minus</span> &lt;= <span class=\"prismident\">cl_minus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">cl_minus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reaction rates</span><br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">reaction_rates</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reward structures (one per species)</span><br/>\n<br/>\n<span class=\"prismcomment\">// 1</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 2</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 3</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na_plus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na_plus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 4</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl_minus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl_minus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=202' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the latter, we can use PRISM to generate a simple plot of the expected amount of Na and Na+ over time (using both model checking and a single random trace from the simulator):\n</p>\n<div class='vspace'></div><div class='img imgcaption'><a class='urllink' href='../uploads/sbml_ex_graph.png'><img src='../uploads/sbml_ex_graph.png' alt='' /></a><br /><span class='caption'><strong>Expected amount of Na/Na+ at time T</strong></span></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Using the translator</h3>\n<p>At present, the SBML-to-PRISM translator is included in the PRISM code-base, but not integrated into the application itself.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock203'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=203' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are using a binary (rather than source code) distribution of PRISM, replace <code>classes</code> with <code>lib/prism.jar</code> in the above.\n</p>\n<p class='vspace'>Alternatively (on Linux or Mac OS X), ensure <code>prism</code> is in your path and then save the script below as an executable file called <code>sbml2prism</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock204'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#!/bin/sh</span><br />\n<br />\n<span class=\"co0\"># Startup script for SBML-to-PRISM translator</span><br />\n<br />\n<span class=\"co0\"># Launch using main PRISM script</span><br />\n<span class=\"re2\">PRISM_MAINCLASS</span>=<span class=\"st0\">&quot;prism.SBML2Prism&quot;</span><br />\n<span class=\"kw3\">export</span> PRISM_MAINCLASS<br />\nprism <span class=\"st0\">&quot;$@&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=204' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Then use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock205'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">sbml2prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=205' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The following PRISM properties file will also be useful:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock206'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">c</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismident\">c</span>}=? [<span class=\"prismkeyword\">I</span>=<span class=\"prismident\">T</span>]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=206' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This contains a single property which, based on the reward structures in the PRISM model generated by the translator, means \"the expected amount of species <em>c</em> at time <em>T</em>\". The constant <em>c</em> is an integer index which can range between 1 and <em>N</em>, where <em>N</em> is the number of species in the model. To view the expected amount of each species over time, create an <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiment</a> in PRISM which varies <em>c</em> from 1 to <em>N</em> and <em>T</em> over the desired time range.\n</p>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Details of the translation</h3>\n<p>The basic structure of the translation process is as follows:\n</p>\n<div class='vspace'></div><ul><li>Each <em>species</em> in the SBML file is represented by a <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>module</a> in the resulting PRISM file. This module, which (where possible) retains the SBML species id as its name, contains a single <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variable</a> whose value represents the amount of the species present. A corresponding <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structure</a> for computing the expected amount of the species at a given time instant is also created. Species for which the <code>boundaryCondition</code> flag is set to <code>true</code> in the SBML file do not have a corresponding module.\n<div class='vspace'></div></li><li>Each <em>reaction</em> in the SBML file is associated with a unique <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation action label</a>. The module for each species which takes part in the reaction will include a synchronous <a class='wikilink' href='../ThePRISMLanguage/Commands.html'>command</a> to represent this. An additional PRISM module called <code>reaction_rates</code> stores the expression representing the rate of each reaction (from the corresponding <code>kineticLaw</code> section in the SBML file). Reaction stoichiometry information is respected but must be provided in the scalar <code>stoichiometry</code> field of a <code>speciesReference</code> element, not in a separate <code>StoichiometryMath</code> element.\n<div class='vspace'></div></li><li>Each <em>parameter</em> in the SBML file, either global to the file or specific to a reaction, becomes a <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constant</a> in the PRISM file. If a value for this parameter is given, it used. If not, the constant is left as undefined.\n</li></ul><p class='vspace'>As described above, this translation process is designed for discrete systems and so the amount of each species in the model is represented by an integer variable. It is therefore assumed that the initial amount for each species specified in the SBML file is also given as an integer. If this is not the case, then the values will need to be scaled accordingly first.\n</p>\n<p class='vspace'>Furthermore, since PRISM is primarily a model checking (rather than simulation) tool, it is important that the amount of each species also has an upper bound (to ensure a finite state space). When model checking, the efficiency (or even feasibility) of the process is likely to be very sensitive to the upper bound(s) chosen. When using the discrete-event simulation functionality of PRISM, this is not the case and the bounds can can be set much higher. By default the translator uses an upper bound of 100 (which is increased if the initial amount exceeds this). A different value can specified through a second command-line argument as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock207'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml 1000 &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=207' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, upper bounds can be modified manually after the translation process.\n</p>\n<p class='vspace'>Finally, The following aspects of SBML files are not currently supported and are ignored during the translation process:\n</p>\n<div class='vspace'></div><ul><li>compartments\n</li><li>events/triggers\n</li></ul><hr />\n<h1>Explicit Model Import</h1>\n<p>It is also possible to construct models in PRISM through direct specification of their transition matrix.\nTwo formats for explicit model import are currently supported:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \"<code>.tra</code>\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li></ul><p class='vspace'>Presently, this functionality is only supported in the command-line version of the tool, usually using the <code>-importmodel</code> switch.\nIn a similar fashion to <code>-exportmodel</code> switch, the type of import is usually determined from the file extension.\n</p>\n<p class='vspace'>For UMB, all model info is contained in a single file. An example of import is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock208'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=208' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For the plain text files (<code>.tra</code> etc.), various options are possible.\nTo just import the core part of the model (the transition function) use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock209'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=209' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM tries to determine the model type from the format of the <code>.tra</code> file,\nbut if this does not work, the model type can be overwritten using the <code>-dtmc</code>, <code>-ctmc</code> and <code>-mdp</code> switches.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock210'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=210' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Using the same formats as for <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>model export</a>, other parts of the model can also be imported:\n</p>\n<div class='vspace'></div><ul><li><code>.lab</code> - labels\n</li><li><code>.srew</code>, <code>.trew</code> - rewards: states, transitions\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>Here is an example of also importing labels and states:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock211'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra,sta,lab</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=211' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If state information is not imported, a single zero-indexed variable <code>x</code> is assumed.\n</p>\n<p class='vspace'>Note also that, since details about the initial state(s) of a model are not preserved in the <code>.tra</code> file,\nbut are included in the labels file, this should also be used to designate a particular initial state for a model.\nOtherwise, state 0 is assumed to be the initial state or,\nif state information is imported, the state in which all variables take their minimum value is used.\n</p>\n<p class='vspace'>Use the extension <code>.all</code> to import from any matching files with appropriate extensions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock212'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=212' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this case, you can omit the <code>-importmodel</code> switch and just specify the <code>.all</code>-ended filename, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock213'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=213' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Efficiency</h3>\n<p>Please note, for PRISM's symbolic model construction/engines, which are often used by default,\nthis explicit method of constructing models in PRISM is typically less efficient than using the PRISM language.\nThis is because the underlying data structures used to represent the model\nfunction better when there is high-level structure and regularity to exploit.\nYou may want to switch to the \"explicit\" engine:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock214'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=214' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The situation can also be alleviated to a certain extent for the symbolic implementations by importing\nthe <code>.sta</code> file, since the composition of the states reintroduces some regularity\n(although is still typically inefficient to construct).\n</p>\n<p class='vspace'>\n</p><h3>Other options</h3>\n<p>In a similar style to PRISM's <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'><code>-exportmodel</code></a> switch, while <code>-importmodel</code> is usually the most convenient, you can also specify each part separately, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock215'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importtrans poll2.tra -importstates poll2.sta -importlabels poll2.lab -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=215' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>There are also <code>-importstaterewards</code> and <code>-impottransrewards</code> switches.\nYou can import multiple reward structures using multiple instances of the these switches.\nIf present in the rewards files (see the appendix \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\"),\nthe names of the reward structures are read too.\n</p>\n<p class='vspace'><br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Configuring PRISM</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>The operation of PRISM can be configured in a number of ways. From the GUI, select \"Options\" from the main menu to bring up the \"Options\" dialog. The settings are grouped under several tabs. Those which affect the basic model checking functionality of the tool are under the heading \"PRISM\". Separate settings are available for the simulator and various aspects of the GUI (the model editor, the property editor and the log).\n</p>\n<p class='vspace'>User options and settings for the GUI are saved in a file locally and reused. Currently the \"Options\" dialog in the GUI represents the easiest way to modify the settings, but the settings file is in a simple textual format and can also be edited by hand. To restore the default options for PRISM, click \"Load Defaults\" and then \"Save Options\" from the \"Options\" dialog in the GUI. Alternatively, delete the settings file re-launch the GUI. The location of the settings file depends on the operating system. As of PRISM 4.5, it is stored in:\n</p>\n<div class='vspace'></div><ul><li><code>$HOME/.prism</code> (if the settings file was already created by an older version of PRISM)\n</li><li><code>$XDG_CONFIG_HOME/prism.settings</code> (on Linux, if that environment variable is set)\n</li><li><code>$HOME/.config/prism.settings</code> (on Linux, if <code>$XDG_CONFIG_HOME</code> is not set)\n</li><li><code>$HOME/Library/Preferences/prism.settings</code> (on Mac OS)\n</li><li><code>.prism</code> in the user's home directory, e.g. <code>C:\\Documents and Settings\\username</code> (on Windows)\n</li></ul><p class='vspace'>From the command-line version of PRISM, options are controlled by switches. A full list can be displayed by typing:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock216'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=216' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For some switches, whose format is not straightforward, there is additional help available on the command-line, using <code>-help switch</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock217'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help const</span><br/>\n<span style=\"font-weight:bold;\">prism -help simpath</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportresults</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportmodel</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=217' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The settings file is <em>ignored</em> by the command-line version (unlike earlier versions of PRISM, where it was used). You can, however, request that the settings file <em>is</em> read, using the <code>-settings</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock218'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -settings ~/.prism</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=218' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the following sections, we give a brief description of the most important configuration options available.\n</p>\n<div class='vspace'></div><hr />\n<h1>Computation Engines</h1>\n<h3>Computation engines</h3>\n<p>PRISM contains four main <em>engines</em>,\nwhich implement the majority of its model checking functionality:\n</p>\n<div class='vspace'></div><ul><li>\"MTBDD\"\n</li><li>\"sparse\"\n</li><li>\"hybrid\"\n</li><li>\"explicit\"\n</li></ul><p class='vspace'>The first three of these engines are either wholly or partly <em>symbolic</em>,\nmeaning that they use data structures such as\nbinary decision diagrams (BDDs) and multi-terminal BDDs (MTBDDs).\nFor these three engines, the process of\nconstructing a probabilistic model (DTMC, MDP or CTMC)\nis performed in a symbolic fashion,\nrepresenting the model as an MTBDD.\nSubsequent numerical computation performed during model checking, however,\nis carried out differently for the three engines.\nThe \"MTBDD\" engine is implemented purely using MTBDDs and BDDs;\nthe \"sparse\" engine uses sparse matrices;\nand the \"hybrid\" engine uses a combination of the other two.\nThe \"hybrid\" engine is described in [<a class='wikilink' href='References.html#KNP04b'>KNP04b</a>].\nFor detailed information about all three engines, see [<a class='wikilink' href='References.html#Par02'>Par02</a>].\n</p>\n<p class='vspace'>The fourth engine, \"explicit\", performs all aspects of model construction\nand model checking using <em>explicit-state</em> data structures.\nModels are typically stored as sparse matrices or variants of.\nThis engine is implemented purely in Java, unlike the other engines\nwhich make use of code/libraries implemented in C/C++.\nOne goal of the \"explicit\" engine is to provide an easily extensible model\nchecking engine without the complication of symbolic data structures,\nalthough it also has other benefits (see below).\n</p>\n<p class='vspace'>The choice of engine (\"MTBDD\", \"sparse\", \"hybrid\" or \"engine\") should not affect the results of model checking - all engines perform essentially the same calculations. In some cases, though, certain functionality is not available with all engines and PRISM will either automatically switch to an appropriate engine, or prompt you to do so.\nPerformance (time and space), however, may vary significantly and if you are using too much time/memory with one engine, it may be worth experimenting. Below, we briefly summarise the key characteristics of each engine.\n</p>\n<div class='vspace'></div><ul><li>The <strong>hybrid</strong> engine is enabled by default in PRISM. It uses a combination of <em>symbolic</em> and <em>explicit-state</em> data structures (as used in the MTBDD and sparse engines, respectively). In general it provides the best compromise between time and memory usage: it (almost) always uses less memory than the sparse engine, but is typically slightly slower. The size of model which can be handled with this engine is quite predictable. The limiting factor in terms of memory usage comes from the storage of 2-4 (depending on the computation being performed) arrays of 8-byte values, one for each state in the model. So, a typical PC can handle models with between 10<sup>7</sup> and 10<sup>8</sup> states (one vector for 10<sup>7</sup> states uses approximately 75 MB).\n<div class='vspace'></div></li><li>The <strong>sparse</strong> engine can be a good option for smaller models where model checking takes a long time. For larger models, however, memory usage quickly becomes prohibitive. As a rule of thumb, the upper limit for this engine, in terms of model sizes which can be handled, is about a factor of 10 less than the hybrid engine.\n<div class='vspace'></div></li><li>The <strong>MTBDD</strong> engine is much more unpredictable in terms of performance but, when a model exhibits a lot of structure and regularity, can be very effective. This engine has been successfully applied to extremely large structured (but non-trivial) models, in cases where the other two engines cannot be applied. The MTBDD engine often performs poorly when the model (or solutions computed from it) contain lots of distinct probabilities/rates; it performs best when there are few such values. For this reason the engine is often successfully applied to MDP models, but much less frequently to CTMCs. When using the MTBDD engine, the <em>variable ordering</em> of your model is especially important. This topic is covered in the <a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html#ordering'>FAQ</a> section.\n<div class='vspace'></div></li><li>The <strong>explicit</strong> engine is similar to the sparse engine, in that it can be a good option for relatively small models, but will not scale up to some of the models that can be handled by the hybrid or MTBDD engines. However, unlike the sparse engine, the explicit engine does not use symbolic data structures for model construction, which can be beneficial in some cases. One example is models with a potentially very large state space, only a fraction of which is actually reachable.\n</li></ul><p class='vspace'>When using the PRISM GUI, the engine to be used for model checking can be selected from the \"Engine\" option under the \"PRISM\" tab of the \"Options\" dialog. From the command-line, engines are activated using the <code>-mtbdd</code>, <code>-sparse</code>, <code>-hybrid</code> and <code>-explicit</code> (or <code>-m</code>, <code>-s</code>, <code>-h</code> and <code>-ex</code>, respectively) switches, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock219'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -m</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -s</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -h</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=219' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note also that precise details regarding the memory usage of the current engine are displayed during model checking (from the GUI, check the \"Log\" tab). This can provide valuable feedback when experimenting with different engines.\n</p>\n<p class='vspace'>PRISM also has some basic support for automatically selecting the engine (and other settings) heuristically,\nbased on the size and type of the model, and the property being checked.\nUse, for example, <code>-heuristic speed</code> from the command-line to choose options\nwhich target computation speed rather than saving memory.\nThis is also available from the \"Heuristic\" option under the \"PRISM\" tab of the \"Options\" dialog in the GUI.\n</p>\n<div class='vspace'></div><h3>Approximate/statistical model checking</h3>\n<p>Although it is not treated as a separate \"engine\", like those above,\nPRISM also provides approximate/statistical model checking,\nwhich is based on the use of discrete-event simulation.\nFrom the GUI, this is enabled by choosing \"Simulate\" menu items or tick boxes;\nfrom the command-line, add the <code>-sim</code> switch.\nSee the \"<a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\"\nsection for more details.\n</p>\n<p class='vspace'><a name='exact' id='exact'></a>\n</p><h3>Exact model checking</h3>\n<p>Most of PRISM's model checking functionality uses numerical solution based on floating point arithmetic and, often, this uses iterative numerical methods, which are run until some user-specified precision is reached. PRISM currently has some support for \"exact\" model checking, i.e., using arbitrary precision arithmetic to provide exact numerical values. Currently, this is implemented as a special case of <a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>parametric model checking</a>, which limits is application to relatively small models. It can be used for analysing DTMCs/CTMCs (unbounded until, steady-state probabilities, reachability reward and steady-state reward) or MDPs (unbounded until and reachability rewards). You can enable this functionality using the \"Do exact model checking\" option in the GUI or using switch <code>-exact</code> from the command line.\n</p>\n<p class='vspace'><a name='pta' id='pta'></a>\n</p><h3>PTA engines</h3>\n<p>The techniques used to model check PTAs are different to the ones used for DTMCs, MDPs and CTMCs. For PTAs, PRISM currently has three distinct engines that can be used:\n</p>\n<div class='vspace'></div><ul><li>The <strong>stochastic games</strong> engine uses abstraction-refinement techniques based on stochastic two-player games [<a class='wikilink' href='References.html#KNP09c'>KNP09c</a>].\n<div class='vspace'></div></li><li>The <strong>digital clocks</strong> engine performs a discretisation, in the form of a language-level model translation, that reduces the problem to one of model checking over a finite-state MDP [<a class='wikilink' href='References.html#KNPS06'>KNPS06</a>].\n<div class='vspace'></div></li><li>The <strong>backwards reachability</strong> engine is a zone-based method based on a backwards traversal of the state space and solution of the resulting finite-state MDP [<a class='wikilink' href='References.html#KNSW07'>KNSW07</a>].\n</li></ul><p class='vspace'>The default engine for PTAs is \"stochastic games\". The engine to be used can be specified using the \"PTA model checking method\" setting in the \"PRISM\" options panel in the GUI. From the command-line, switch <code>-ptamethod &lt;name&gt;</code> should be used where <code>&lt;name&gt;</code> is either <code>games</code>, <code>digital</code> or <code>backwards</code>.\n</p>\n<p class='vspace'>The choice of engine for PTA model checking affects restrictions that imposed on both\nthe <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>modelling language</a>\nand the types of <a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>properties</a> that can be checked.\n</p><hr />\n<h1>Solution Methods and Options</h1>\n<p>Separately from the choice of <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a>,\nPRISM often offers several different solution methods\nthat can be used for the computation of probabilities and expected costs/rewards during model checking.\nMany, but not all, of these are iterative numerical methods.\nThe choice of method (and their settings) depends on the type of analysis that is being done (i.e., what type of model and property).\n</p>\n<div class='vspace'></div><h3>Linear Equation Systems</h3>\n<p>For many properties of Markov chains\n(e.g. \"reachability\"/\"until\" properties for DTMCs and CTMCs, steady-state properties for CTMCs and \"reachability reward\" properties for DTMCs),\nPRISM solves a set of linear equation systems, for which several numerical methods are available.\nBelow is a list of the alternatives and the switches used to select them from the command-line.\nThe corresponding GUI option is \"Linear equations method\".\n</p>\n<div class='vspace'></div><ul><li>Power method: <code>-power</code> (or <code>-pow</code>, <code>-pwr</code>)\n</li><li>Jacobi method: <code>-jacobi</code> (or <code>-jac</code>)\n</li><li>Gauss-Seidel method: <code>-gaussseidel</code> (or <code>-gs</code>)\n</li><li>Backwards Gauss-Seidel method: <code>-bgaussseidel</code> (or <code>-bgs</code>)\n</li><li>JOR method (Jacobi with over-relaxation): <code>-jor</code>\n</li><li>SOR method: <code>-sor</code>\n</li><li>Backwards SOR method: <code>-bsor</code>\n</li></ul><p class='vspace'>When using the MTBDD engine, Gauss-Seidel/SOR based methods are not available.\nWhen using the hybrid engine, <em>pseudo</em> variants of Gauss-Seidel/SOR based method can also be used [<a class='wikilink' href='References.html#Par02'>Par02</a>]\n(type <code>prism -help</code> at the command-line for details of the corresponding switches).\nFor methods which use over-relaxation (JOR/SOR), the over-relaxation parameter (between 0.0 and 2.0)\ncan also be specified with option \"Over-relaxation parameter\" (switch <code>-omega &lt;val&gt;</code>).\n</p>\n<p class='vspace'>For options relating to convergence (of this and other iterative methods),\nsee the <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='mdp' id='mdp'></a>\n</p><h3>MDP Solution Methods</h3>\n<p>When analysing MDPs, there are multiple solution methods on offer.\nFor most of these, you can select them under the \"MDP solution method\" setting from the GUI,\nor use the command-line switches listed below.\nCurrently, all except value iteration are only supported by the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>explicit engine</a>.\nFor more details of the methods, see e.g. [<a class='wikilink' href='References.html#FKNP11'>FKNP11</a>] (about probabilistic verification of MDPs)\nor classic MDP texts such as [<a class='wikilink' href='References.html#Put94'>Put94</a>]).\n</p>\n<div class='vspace'></div><ul><li><strong>Value iteration</strong> (switch <code>-valiter</code>) [this is the default]\n</li><li><strong>Gauss Seidel</strong> (switch <code>-gs</code>)\n</li><li><strong>Policy iteration</strong> (switch <code>-politer</code>)\n</li><li><strong>Modified policy iteration</strong> (switch <code>-modpoliter</code>)\n</li></ul><p class='vspace'>Where the methods above use iterative numerical solution,\nyou can also use the settings under described in the <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='iiter' id='iiter'></a>\n</p><h3>Interval Iteration</h3>\n<p>Interval iteration [<a class='wikilink' href='References.html#HM14'>HM14</a>],[<a class='wikilink' href='References.html#BKLPW17'>BKLPW17</a>] is an alternative solution method for either MDPs or DTMCs\nwhich performs two separate instances of numerical iterative solution,\none from below and one from above. This is designed to provide clearer information\nabout the accuracy of the computed values and avoid possible problems with premature convergence.\nThis can be enabled using the switch <code>-intervaliter</code> (or <code>-ii</code>)\nor via the \"Use interval iteration\" GUI option.\nA variety of options can be configured, either using\n<code>-intervaliter:option1,option2,...</code> or by\nsetting the string \"<code>option1,option2,...</code>\" under \"Interval iteration options\" in the GUI.\nType <code>prism -help intervaliter</code> from the command-line for a list of the options\nand see [<a class='wikilink' href='References.html#BKLPW17'>BKLPW17</a>] for the details.\n</p>\n<p class='vspace'><a name='topo' id='topo'></a>\n</p><h3>Topological Value Iteration</h3>\n<p>Topological value iteration is a variant of value iteration which improves efficiency\nby analysing the graph structure of the model and using this to update the values for\nstates in an alternative order which increases the speed of convergence.\nUse switch <code>-topological</code> or GUI option \"Use topological value iteration\" to enable this.\nIn addition to standard value iteration for MDPs, the topological variant can be used to optimise\nboth interval iteration (see above) and the numerical solution of DTMCs.\n</p>\n<p class='vspace'><a name='transient' id='transient'></a>\n</p><h3>CTMC Transient Analysis</h3>\n<p>When computing transient probabilities of a CTMC\n(either <a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>directly</a> or when verifying <a class='wikilink' href='../PropertySpecification/ThePOperator.html#bounded'>time-bounded operators</a> of CSL), there are two options:\n<em>uniformisation</em> and <em>fast adaptive uniformisation</em> (FAU). These can be selected using the GUI option \"Transient probability computation method\", or using the command-line switch <code>-transientmethod &lt;name&gt;</code>, where <code>&lt;name&gt;</code> is either <code>unif</code> or <code>fau</code>.\n</p>\n<p class='vspace'><strong>Uniformisation</strong> is a standard iterative numerical method for computing transient probabilities on a CTMC, which works by reducing the problem to an analysis of a \"uniformised\" DTMC.\nAs an optimisation, when it is detected that the transient probabilities have converged, no further iterations are performed. If necessary (e.g. in case of round-off problems), this optimisation can be disabled with the \"Use steady-state detection\" option (command-line switch <code>-nossdetect</code>).\n</p>\n<p class='vspace'><a name='fau' id='fau'></a>\n<strong>Fast adaptive uniformisation</strong> (FAU) [<a class='wikilink' href='References.html#MWDH10'>MWDH10</a>] is a method to efficiently approximate transient properties of large CTMCs. The basic idea is that only the parts of the model that are relevant for the current time period are kept in memory. In more detail, starting with the initial states, in each step FAU\nexplores further states in a DTMC which is a discrete-time version of the original CTMC. By combining the\nprobabilities there with those of a certain continuous-time stochastic process (a birth process), transient properties in the original CTMC can be computed. If it turns out that the probability of being in some state in the DTMC is below a given threshold, this state is removed from the model explored so far. After a given number of steps, which corresponds to the number of steps which are likely to happen within the time bound, the exploration can be stopped. In the implementation in PRISM [<a class='wikilink' href='References.html#DHK13'>DHK13</a>], FAU can be used to compute transient probability distributions and to model check the following types of non-nested CSL formulas: time-bounded until, instantaneous reward, cumulative reward.\n</p>\n<p class='vspace'>The following options can be used to configure FAU:\n</p>\n<div class='vspace'></div><ul><li>\"FAU epsilon\" (switch <code>-fauepsilon &lt;x&gt;</code>): FAU analyses the DTMC for a number of iterations such that the probability of more steps being relevant is below this value. The default is 1e-6.\n<div class='vspace'></div></li><li>\"FAU cut off delta\" (switch <code>-faudelta &lt;x&gt;</code>): States that have a lower probability than this value are discarded. The default is 1e-12.\n<div class='vspace'></div></li><li>\"FAU array threshold\" (switch <code>-fauarraythreshold &lt;x&gt;</code>): After this number of steps without any new states being explored or discarded, FAU will switch to a faster, fixed-size data structure until further states have to be explored or discarded. The default is 100.\n<div class='vspace'></div></li><li>\"FAU time intervals\" (switch <code>-fauintervals &lt;x&gt;</code>): In some cases, it is advantageous to divide the time interval the analysis is done for into several smaller intervals. This option dictates the number of (equal length) intervals used for this split. The default is 1, meaning that only one time interval is used.\n<div class='vspace'></div></li><li>\"FAU initial time interval\" (switch <code>-fauinitival &lt;x&gt;</code>): It is also possible to specify an additional initial time interval which is handled separately from the rest of the time. This is often advantageous, because in this interval certain parameters of the model can be explored, which can subsequently be used to speed up the computation of the remaining time interval. The default for this option is 1.0.\n</li></ul><p class='vspace'><a name='convergence' id='convergence'></a>\n</p><h3>Convergence</h3>\n<p>Common to all of these methods is the way that PRISM checks convergence, i.e. decides when to terminate the iterative methods because the answers have converged sufficiently. This is done by checking when the maximum difference between elements in the solution vectors from successive iterations drops below a given threshold (or, in the case of interval iteration, if the difference of the elements in the iterations from above and below are below the threshold).\nThe default value for this threshold is 10<sup>-6</sup> but it can be altered with the \"Termination epsilon\" option (switch <code>-epsilon &lt;val&gt;</code>). The way that the maximum difference is computed can also be varied:\neither \"relative\" or \"absolute\" (the default is \"relative\"). This can be changed using the \"Termination criteria\" option (command-line switches <code>-relative</code> and <code>-absolute</code>, or <code>-rel</code> and <code>-abs</code> for short).\n</p>\n<p class='vspace'>Also, the maximum number of iterations performed is given an upper limit\nin order to trap the cases when computation will not converge.\nThe default limit is 10,000 but can be changed with the \"Termination max. iterations\" option (switch <code>-maxiters &lt;val&gt;</code>). Computations that reach this upper limit will trigger an error during model checking to alert the user to this fact.\n</p><hr />\n<h1>Automata Generation</h1>\n<p>When PRISM performs verification of <a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>LTL formulas</a>, it does so by converting the formula into an automaton (such as a deterministic Rabin automaton) and then analysing a larger product model, constructed from the model being verified and the omega automaton. For this reason, the size of the automaton has an important effect on the efficiency of verification.\n</p>\n<p class='vspace'>By default PRISM uses a port of the <a class='urllink' href='http://www.ltl2dstar.de/'>ltl2dstar</a> library to construct these automata. But it also allows the use of external LTL-to-automata converters producing deterministic automata through support for the <a class='urllink' href='http://adl.github.io/hoaf/'>Hanoi Omega Automaton</a> (HOA) format. From the command line, an example of this is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock220'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=220' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-ltl2datool</code> switch specifies the location of the program to be executed to perform the LTL-to-automaton conversion. This will be called by PRISM as \"<code>exec</code> <code>in-file</code> <code>out-file</code>\", where <code>exec</code> is the executable, <code>in-file</code> is the name of a file containing the LTL formula to be converted and <code>out-file</code> is the name of a file where the resulting automaton should be written, in HOA format. Typically, the executable will be a script. Here is a simple example (called as <code>hoa-ltl2dstar-for-prism</code> in the above example), which calls an external copy of <code>ltl2dstar</code> in the required fashion (assuming that the <code>ltl2dstar</code> and <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a>  executables are located in the current directory or on the PATH).\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock221'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#! /bin/bash</span><br />\nltl2dstar <span class=\"re5\">--output</span>=automaton <span class=\"re5\">--output-format</span>=hoa <span class=\"st0\">&quot;$1&quot;</span> <span class=\"st0\">&quot;$2&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=221' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM is known to work with these HOA-enabled tools:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>\n</li><li><a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>\n</li><li><a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>\n</li><li><a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>\n</li></ul><p class='vspace'>and contains ready-made scripts for calling them in the <code>etc/scripts/hoa</code> directory of the distribution:\n</p>\n<div class='vspace'></div><ul><li><code>hoa-ltl2dstar-for-prism</code> <br />  (<a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>, using <a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>, <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a> or <a class='urllink' href='https://github.com/xblahoud/ltl3dra'>LTL3BA</a> as the LTL-to-NBA tool as the LTL-to-NBA tool)\n</li><li><code>hoa-ltl2tgba-for-prism</code> <br />  (<a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>)\n</li><li><code>hoa-ltl3dra-for-prism</code> <br />  (<a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>)\n</li><li><code>hoa-rabinizer-for-prism</code> <br />  (<a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>'s <code>ltl2dra</code>)\n</li></ul><p class='vspace'>See the files themselves for details of any configuration required, possible options and for a reminder of the PRISM command-line arguments required.\n</p>\n<p class='vspace'>There is also a <code>hoa-rabinizer-for-prism.bat</code> script for connecting to Rabinizer on Windows.\n</p>\n<p class='vspace'>The <code>-ltl2dasyntax</code> switch is used to specify the textual format for passing the LTL formula to the external converter (i.e., in the file <code>out-file</code>). The options are:\n</p>\n<div class='vspace'></div><ul><li><code>lbt</code> - LBT format\n</li><li><code>spin</code> - SPIN format\n</li><li><code>spot</code> - Spot format\n</li><li><code>rabinizer</code> - Rabinizer format\n</li></ul><p class='vspace'>Typical usage is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock222'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2tgba-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl3dra-for-prism -ltl2dasyntax spin</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-rabinizer-for-prism -ltl2dasyntax rabinizer</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=222' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, configuring the external LTL converter is done with the two options \n\"Use external LTL-&gt;DA tool\" and \"LTL syntax for external LTL-&gt;DA tool\".\n</p>\n<p class='vspace'>Another related option is \"All path formulas via automata\" (command-line switch <code>-pathviaautomata</code>), which forces construction of an automata\nwhen computing the probability of a path formula, even if it is not needed. This is primarily intended for debugging/testing, not regular use.\n</p>\n<p class='vspace'>As mentioned above, PRISM's external LTL-to-automaton interfacing works using the\n<a class='urllink' href='http://adl.github.io/hoaf/'>HOA</a> format\n(and, in particular,  using the <a class='urllink' href='http://automata.tools/hoa/jhoafparser/'><code>jhoafparser</code></a> HOA parser.\nCurrently, PRISM can handle automata in HOA format that are \ndeterministic and complete, with state-based acceptance.\nAutomata with transition-based acceptance are converted to state-based acceptance by PRISM.\nFor DTMC and  CTMC model checking, generic acceptance conditions are supported, i.e., \nanything that can be specified as an <code>Acceptance:</code> header in HOA format. \nFor MDP model checking, currently Rabin and generalized Rabin acceptance \nspecified via the <code>acc-name:</code> header are supported. See the <a class='urllink' href='http://adl.github.io/hoaf/'>HOA format specification</a> for details.\n</p>\n<div class='vspace'></div><hr />\n<h1>Other Options</h1>\n<h3>Output options</h3>\n<p>To increase the amount of information displayed by PRISM (in particular, to display lists of states and probability vectors), you can use the \"Verbose output\" option (activated with command-line switch <code>-verbose</code> or <code>-v</code>). To display additional statistics about MTBDDs after model construction, use the \"Extra MTBDD information\" option (switch <code>-extraddinfo</code>) and, to view MTBDD sizes during the process of reachability, use option \"Extra reachability information\" (switch <code>-extrareachinfo</code>).\n</p>\n<div class='vspace'></div><h3>Fairness</h3>\n<p>Sometimes, model checking of properties for MDPs requires fairness constraints to be taken into account.\nSee e.g. [<a class='wikilink' href='References.html#BK98'>BK98</a>],[<a class='wikilink' href='References.html#Bai98'>Bai98</a>] for more information.\nTo enable the use of fairness constraints (for <code><strong>P</strong></code> operator properties), use the <code>-fair</code> switch.\n</p>\n<div class='vspace'></div><h3>Probability/rate checks</h3>\n<p>By default, when constructing a model, PRISM checks that all probabilities and rates are within acceptable ranges (i.e. are between 0 and 1, or are non-negative, respectively). For DTMCs and MDPs, it also checks that the probabilities sum up to one for each command. These checks are often very useful for highlighting user modelling errors and it is strongly recommended that you keep them enabled, however if you need to disable them you can do so via option \"do prob checks?\" in the GUI or command-line switch <code>-noprobchecks</code>.\nYou can also change the level of precision used to check that probabilities sum to 1 using the option \"Probability sum threshold\" (or command-line switch <code>-sumroundoff</code>.\n</p>\n<div class='vspace'></div><h3>CUDD memory</h3>\n<p>CUDD, the underlying BDD and MTBDD library used in PRISM has an upper memory limit. By default, this limit is 1 GB. If you are working on a machine with significantly more memory this and PRISM runs out of memory when model checking, it may help to change this. To set the limit, from the command-line, use the <code>-cuddmaxmem</code> switch. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock223'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -cuddmaxmem 2g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=223' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Above, <code>g</code> denotes GB. You can also use <code>m</code> for MB.\nYou can also the CUDD maximum memory setting from the options panel in the GUI, but you will need to close and restart the GUI (saving the settings as you do) for this to take effect.\n</p>\n<p class='vspace'><a name='javamaxmem' id='javamaxmem'></a>\n</p><h3>Java memory</h3>\n<p>The Java virtual machine (JVM) used to execute PRISM also has upper memory limits. Sometimes this limit will be exceeded and you will see an error of the form <code>java.lang.OutOfMemory</code>. To resolve this problem, you can increase this memory limit. On Unix, Linux or Mac OS X platforms, this can done by using the <code>-javamaxmem</code> switch, passed either to the command-line script <code>prism</code> or the GUI launcher <code>xprism</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock224'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javamaxmem 4g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javamaxmem 4g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=224' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>each set the limit to 4GB. Alternatively, you set the environment variable PRISM_JAVAMAXMEM before running PRISM. For example, under a <code>bash</code> shell:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock225'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVAMAXMEM=4g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVAMAXMEM</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=225' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you get an error of the form <code>java.lang.StackOverflowError</code>, then you can try increasing the stack size of the JVM.\nOn Unix, Linux or Mac OS X platforms, this can done by using the <code>-javastack</code> switch or the <code>PRISM_JAVASTACKSIZE</code> environment variable.\nExamples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock226'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javastack 1g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javastack 1g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=226' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock227'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVASTACKSIZE=1g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVASTACKSIZE</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=227' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are running PRISM on Windows you will have to do make adjustments to Java memory manually, by modifying the <code>prism.bat</code> or <code>xprism.bat</code> scripts.\nTo set the memory to 4GB, for example, add <code> -Xmx4g</code> to the list of arguments in the call to <code>java</code> or <code>javaw</code> at the end of the file.\nTo change the stack size to 1GB, add <code>-Xss1g</code>.\n</p>\n<div class='vspace'></div><h3>Other Java options</h3>\n<p>If you want to pass additional switches to the JVM used to run PRISM, you can use the <code>-javaparams</code> switch.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock228'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javaparams \"-XX:AutoBoxCacheMax=100000000 -Xmn2g\" -javamaxmem 12g</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=228' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Precomputation</h3>\n<p>By default, PRISM's probabilistic model checking algorithms use an initial <em>precomputation</em> step which uses graph-based techniques to efficient detect trivial cases where probabilities are 0 or 1. This can often result in improved performance and also reduce round-off errors. Occasionally, though, you may want to disable this step for efficiency (e.g. if you know that there are no/few such states and the precomputation process is slow). This can be done with the <code>-nopre</code> switch. You can also disable the individual algorithms for probability 0/1 using switches <code>-noprob0</code> and <code>-noprob1</code>.\n</p>\n<div class='vspace'></div><h3>Time-outs</h3>\n<p>The command-line version of PRISM has a time-out option, specified using the switch <code>-timeout &lt;n&gt;</code>.\nThis causes the program to exit after <code>&lt;n&gt;</code> seconds if it has not already terminated by that point.\nThis is particularly useful for benchmarking scenarios where you wish to ignore runs of PRISM that exceed a certain length of time.\n<br /><br />\n</p><hr />\n<h1><span class='big'>References</span></h1>\n<hr />\n<ul><li><a name='AD94' id='AD94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=AD94'>AD94</a>: R. Alur and D. Dill.  A theory of timed automata.  Theoretical Computer Science, 126:183-235, 1994.\n<div class='vspace'></div></li><li><a name='AH99' id='AH99'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=AH99'>AH99</a> R. Alur and T. Henzinger.  Reactive modules.  Formal Methods in System Design, 15(1):7-48, 1999.\n<div class='vspace'></div></li><li><a name='ASSB96' id='ASSB96'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=ASSB96'>ASSB96</a>: A. Aziz, K. Sanwal, V. Singhal, and R. Brayton.  Verifying continuous time Markov chains.  In R. Alur and T. Henzinger, editors, Proc. 8th International Conference on Computer Aided Verification (CAV'96), volume 1102 of LNCS, pages 269-276. Springer, 1996.\n<div class='vspace'></div></li><li><a name='Bai98' id='Bai98'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Bai98'>Bai98</a>: C. Baier.  On algorithmic verification methods for probabilistic systems, 1998.  Habilitation thesis, Fakultt fr Mathematik &amp; Informatik, Universitt Mannheim.\n<div class='vspace'></div></li><li><a name='BKLPW17' id='BKLPW17'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BKLPW17'>BKLPW17</a>: Christel Baier, Joachim Klein, Linda Leuschner, David Parker and Sascha Wunderlich. Ensuring the Reliability of Your Model Checker: Interval Iteration for Markov Decision Processes. In Proc. 28th International Conference on Computer Aided Verification (CAV'17), volume 10426 of LNCS, pages 160-180, Springer, 2017.\n<div class='vspace'></div></li><li><a name='BKH99' id='BKH99'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BKH99'>BKH99</a>: C. Baier, J.-P. Katoen, and H. Hermanns.  Approximate symbolic model checking of continuous-time Markov chains.  In J. Baeten and S. Mauw, editors, Proc. 10th International Conference on Concurrency Theory (CONCUR'99), volume 1664 of LNCS, pages 146-161. Springer, 1999.\n<div class='vspace'></div></li><li><a name='BK98' id='BK98'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BK98'>BK98</a>: C. Baier and M. Kwiatkowska.  Model checking for a probabilistic branching time logic with fairness.  Distributed Computing, 11(3):125-155, 1998.\n<div class='vspace'></div></li><li><a name='BdA95' id='BdA95'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BdA95'>BdA95</a>: A. Bianco and L. de Alfaro.  Model checking of probabilistic and nondeterministic systems.  In P. Thiagarajan, editor, Proc. 15th Conference on Foundations of Software Technology and Theoretical Computer Science (FSTTCS'95), volume 1026 of LNCS, pages 499-513. Springer, 1995.\n<div class='vspace'></div></li><li><a name='CHH13' id='CHH13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=CHH+13'>CHH+13</a>: Taolue Chen, Ernst Moritz Hahn, Tingting Han, Marta Kwiatkowska, Hongyang Qu, and Lijun Zhang.  Model repair for Markov decision processes.  In Proc. 7th International Symposium on Theoretical Aspects of Software Engineering (TASE'13), pages 85-92. IEEE, 2013.\n<div class='vspace'></div></li><li><a name='CE81' id='CE81'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=CE81'>CE81</a>: E. Clarke and A. Emerson.  Design and synthesis of synchronization skeletons using branching time temporal logic.  In Proc. Workshop on Logic of Programs, volume 131 of LNCS. Springer, 1981.\n<div class='vspace'></div></li><li><a name='DHK13' id='DHK13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=DHK13'>DHK13</a>: F. Dannenberg, E. M. Hahn, and M. Kwiatkowska.  Computing cumulative rewards using fast adaptive uniformisation.  In A. Gupta and T. Henzinger, editors, Proc. 11th Conference on Computational Methods in Systems Biology (CMSB'13), volume 8130 of LNCS, pages 33-49. Springer, 2013.\n<div class='vspace'></div></li><li><a name='FKNP11' id='FKNP11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKNP11'>FKNP11</a>: V. Forejt, M. Kwiatkowska, G. Norman, and D. Parker.  Automated verification techniques for probabilistic systems.  In M. Bernardo and V. Issarny, editors, Formal Methods for Eternal Networked Software Systems (SFM'11), volume 6659 of LNCS, pages 53-113. Springer, 2011.\n<div class='vspace'></div></li><li><a name='FKN11' id='FKN11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKN+11'>FKN+11</a>: V. Forejt, M. Kwiatkowska, G. Norman, D. Parker, and H. Qu.  Quantitative multi-objective verification for probabilistic systems.  In P. Abdulla and K. Leino, editors, Proc. 17th International Conference on Tools and Algorithms for the Construction and Analysis of Systems (TACAS'11), volume 6605 of LNCS, pages 112-127. Springer, 2011.\n<div class='vspace'></div></li><li><a name='FKP12' id='FKP12'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKP12'>FKP12</a>: V. Forejt, M. Kwiatkowska, and D. Parker.  Pareto curves for probabilistic model checking.  In S. Chakraborty and M. Mukund, editors, Proc. 10th International Symposium on Automated Technology for Verification and Analysis (ATVA'12), volume 7561 of LNCS, pages 317-332. Springer, 2012.\n<div class='vspace'></div></li><li><a name='HM14' id='HM14'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HM14'>HM14</a>: S. Haddad and B. Monmege. Reachability in MDPs: Refining convergence of value iteration. In 8th International Workshop on Reachability Problems (RP), volume 8762 of LNCS, pages 125137, Springer. 2014.\n<div class='vspace'></div></li><li><a name='HHZ11b' id='HHZ11b'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HHZ11b'>HHZ11b</a>: E. M. Hahn, H. Hermanns, and L. Zhang.  Probabilistic reachability for parametric Markov models.  International Journal on Software Tools for Technology Transfer (STTT), 13(1):3-19, 2011.\n<div class='vspace'></div></li><li><a name='HHZ11' id='HHZ11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HHZ11'>HHZ11</a>: Ernst Moritz Hahn, Tingting Han, and Lijun Zhang.  Synthesis for PCTL in parametric Markov decision processes.  In Proc. 3rd NASA Formal Methods Symposium (NFM'11), volume 6617 of LNCS. Springer, 2011.\n<div class='vspace'></div></li><li><a name='HJ94' id='HJ94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HJ94'>HJ94</a>: H. Hansson and B. Jonsson.  A logic for reasoning about time and reliability.  Formal Aspects of Computing, 6(5):512-535, 1994.\n<div class='vspace'></div></li><li><a name='HLMP04' id='HLMP04'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HLMP04'>HLMP04</a>: T. Hrault, R. Lassaigne, F. Magniette, and S. Peyronnet.  Approximate probabilistic model checking.  In Proc. 5th International Conference on Verification, Model Checking and Abstract Interpretation (VMCAI'04), volume 2937 of LNCS, pages 307-329. Springer, 2004.\n<div class='vspace'></div></li><li><a name='Hil96' id='Hil96'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Hil96'>Hil96</a>: J. Hillston.  A Compositional Approach to Performance Modelling.  Cambridge University Press, 1996.\n<div class='vspace'></div></li><li><a name='KSK76' id='KSK76'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KSK76'>KSK76</a>: J. Kemeny, J. Snell, and A. Knapp.  Denumerable Markov Chains.  Springer-Verlag, 2nd edition, 1976.\n<div class='vspace'></div></li><li><a name='KNP04b' id='KNP04b'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP04b'>KNP04b</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Probabilistic symbolic model checking with PRISM: A hybrid approach.  International Journal on Software Tools for Technology Transfer (STTT), 6(2):128-142, 2004.\n<div class='vspace'></div></li><li><a name='KNP07a' id='KNP07a'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP07a'>KNP07a</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Stochastic model checking.  In M. Bernardo and J. Hillston, editors, Formal Methods for the Design of Computer, Communication and Software Systems: Performance Evaluation (SFM'07), volume 4486 of LNCS (Tutorial Volume), pages 220-270. Springer, 2007.\n<div class='vspace'></div></li><li><a name='KNP09c' id='KNP09c'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP09c'>KNP09c</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Stochastic games for verification of probabilistic timed automata.  In J. Ouaknine and F. Vaandrager, editors, Proc. 7th International Conference on Formal Modelling and Analysis of Timed Systems (FORMATS'09), volume 5813 of LNCS, pages 212-227. Springer, 2009.\n<div class='vspace'></div></li><li><a name='KNPS06' id='KNPS06'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNPS06'>KNPS06</a>: M. Kwiatkowska, G. Norman, D. Parker, and J. Sproston.  Performance analysis of probabilistic timed automata using digital clocks.  Formal Methods in System Design, 29:33-78, 2006.\n<div class='vspace'></div></li><li><a name='KNSW07' id='KNSW07'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNSW07'>KNSW07</a>: M. Kwiatkowska, G. Norman, J. Sproston, and F. Wang.  Symbolic model checking for probabilistic timed automata.  Information and Computation, 205(7):1027-1077, 2007.\n<div class='vspace'></div></li><li><a name='MWDH10' id='MWDH10'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=MWDH10'>MWDH10</a>: F. Didier M. Mateescu, V. Wolf and T. Henzinger.  Fast adaptive uniformisation of the chemical master equation.  IET Syst Biol, 4(6):441-452, 2010.\n<div class='vspace'></div></li><li><a name='Nim10' id='Nim10'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Nim10'>Nim10</a>: V. Nimal.  Statistical Approaches for Probabilistic Model Checking.  MSc Mini-project Dissertation, Oxford University Computing Laboratory, 2010.\n<div class='vspace'></div></li><li><a name='NPS13' id='NPS13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=NPS13'>NPS13</a>: Gethin Norman, David Parker, and Jeremy Sproston.  Model checking for probabilistic timed automata.  Formal Methods in System Design, 43(2):164-190, 2013.\n<div class='vspace'></div></li><li><a name='NPZ17' id='NPZ17'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=NPZ17'>NPZ17</a>: Gethin Norman, David Parker and Xueyi Zou. Verification and Control of Partially Observable Probabilistic Systems. Real-Time Systems, 53(3):354-402, Springer, 2017.\n<div class='vspace'></div></li><li><a name='Par02' id='Par02'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Par02'>Par02</a>: D. Parker.  Implementation of Symbolic Model Checking for Probabilistic Systems.  Ph.D. thesis, University of Birmingham, 2002.\n<div class='vspace'></div></li><li><a name='Put94' id='Put94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Put94'>Put94</a>: M. Puterman.  Markov Decision Processes: Discrete Stochastic Dynamic Programming.  John Wiley and Sons, 1994.\n<div class='vspace'></div></li><li><a name='Seg95' id='Seg95'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Seg95'>Seg95</a>: R. Segala.  Modelling and Verification of Randomized Distributed Real Time Systems.  Ph.D. thesis, Massachusetts Institute of Technology, 1995.\n<div class='vspace'></div></li><li><a name='Ste94' id='Ste94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Ste94'>Ste94</a>: W. Stewart.  Introduction to the Numerical Solution of Markov Chains.  Princeton, 1994.\n<div class='vspace'></div></li><li><a name='YS02' id='YS02'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=YS02'>YS02</a>: H. Younes and R. Simmons.  Probabilistic verification of discrete event systems using acceptance sampling.  In E. Brinksma and K. Larsen, editors, Proc. 14th International Conference on Computer Aided Verification (CAV'02), volume 2404 of LNCS, pages 223-235. Springer, 2002.\n</li></ul><p class='vspace'><br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Frequently Asked Questions</span></h1>\n<hr />\n<h1>Memory Problems</h1>\n<p><a name='crash' id='crash'></a>\n</p><h3>PRISM crashed or stopped responding. Why?</h3>\n<div class='answer' > \n<p>When PRISM crashes, the most likely cause is that it has run out of memory.\nSimilarly, if PRISM (or the machine you are running it on) becomes very slow or seems to have stopped responding, this is probably because it is using too much of your machine's memory. Probabilistic model checking, much like other formal verification techniques, can be a very resource-intensive process. It is very easy to create a seemingly simple PRISM model that requires a large amount of time and/or memory to construct and analyse. See some of the other questions in this section for tips on how to avoid this.\n</p>\n<p class='vspace'>The other possibility is that you have found a bug.\nIf PRISM crashes or freezes whilst not using all/most of the available memory (you can check this with the <code>top</code> command in a Unix/Linux terminal or the Task Manager (via Ctrl-Alt-Delete) on Windows) then please file a <a class='urllink' href='https://github.com/prismmodelchecker/prism/issues'>bug report</a>.\n</p></div>\n<p class='vspace'><a name='memout' id='memout'></a>\n</p><h3>I ran out of memory. What can I do?</h3>\n<div class='answer' > \n<p>It depends. First, you need to establish at what point in PRISM's operation, you ran out of memory. If you are running the command-line version of PRISM then the output from the tool so far should give an indication of this. If using the GUI, check the log tab for this information. If PRISM crashed because of its memory usage, the error message can be helpful. If using the GUI, you may need to start the GUI from the command-line to see any error messages.\n</p>\n<p class='vspace'>The two main steps that PRISM typically has to perform are:\n</p>\n<div class='vspace'></div><ol><li><strong>Model construction</strong> (conversion of a PRISM language description to the corresponding probabilistic model)\n</li><li><strong>Model checking/analysis</strong> (processing/analysis of a constructed probabilistic model in order to determine the result of a property or to compute steady-state/transient probabilities)\n</li></ol><p class='vspace'>Memory usage issues for each of these steps are discussed in separate sections below. In some cases the process performed prior to step 1 (<strong>model parsing</strong> - reading in a model description in the PRISM language and checking it for correctness) can also be resource intensive. This is also discussed below.\n</p>\n<p class='vspace'>If you are using the <strong>simulator</strong> to generate approximate model checking results then step 1 (model construction) is not performed and step 2 is carried out very differently. Memory consumption is not usually a problem in this case.\n</p></div>\n<p class='vspace'><a name='memout_constr' id='memout_constr'></a>\n</p><h3>I ran out of memory during model construction. What can I do?</h3>\n<div class='answer' > \n<p>If PRISM has already output this:\n</p>\r\n<div class='sourceblock ' id='sourceblock229'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Building model...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=229' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>but there is no line of the form:\n</p>\r\n<div class='sourceblock ' id='sourceblock230'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Time for model construction: 34.3 seconds.</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=230' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>and then you get an error like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock231'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by Java Runtime Environment:</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">#  SIGSEGV (0xb) at pc=0xb5249323, pid=19298, tid=3086363536</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.6.0-b105 mixed mode, sharing)</span><br/>\n<span style=\"font-style:italic;\"># Problematic frame:</span><br/>\n<span style=\"font-style:italic;\"># C  [libdd.so+0x39323]  Cudd_Ref+0xf</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An error report file with more information is saved as hs_err_pid19298.log</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># If you would like to submit a bug report, please visit:</span><br/>\n<span style=\"font-style:italic;\">#   http://java.sun.com/webapps/bugreport/crash.jsp</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50: 19298 Aborted                 \"$PRISM_JAVA\" #$PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=231' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock232'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by HotSpot Virtual Machine: </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0b1c7da3, pid=2884, tid=2544 </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.5.0_06-b05 mixed mode) </span><br/>\n<span style=\"font-style:italic;\"># Problematic frame: </span><br/>\n<span style=\"font-style:italic;\"># C [dd.dll+0x7da3] </span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=232' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then PRISM ran out of memory whilst trying to construct the model.\nModel construction in PRISM is performed using BDDs (binary decision diagrams) and MTBDDs (multi-terminal) BDDs which are implemented in the CUDD library.\nThe first thing to try in this case is to increase the amount of memory available to CUDD. See the entry \"CUDD memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p>\n<p class='vspace'>If increasing this memory limit does not resolve the problem, then you will need to consider ways to reduce the size of your model. You can find some tips on this in the <a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html'>PRISM Modelling</a> section. Bear in mind also that if you are having to increase the CUDD memory limit too high (e.g. close to the physical memory available on your computer) just for model construction, then it is unlikely that you will have enough memory for subsequent model checking operations.\n</p>\n<p class='vspace'>Finally, it is also worth considering the ordering of the modules and variables in your model since this can have a (in some cases dramatic) effect on the size of MTBDD representation of the model. This topic is covered in the \"<a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n</p></div>\n<p class='vspace'><a name='memout_check' id='memout_check'></a>\n</p><h3>I ran out of memory during model checking. What can I do?</h3>\n<div class='answer' > \n<p>If model construction was successfully completed (see previous question) but model checking was not, there are several things you can try. First of all, if the error message you see looks like the one in the previous question or you see a message such as\n</p>\r\n<div class='sourceblock ' id='sourceblock233'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">DD_MatrixMultiply: res is NULL</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=233' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then it may be worth increasing the memory limit for CUDD (as described above). However, if you see an error more like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock234'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50:  3139 Aborted                 \"$PRISM_JAVA\" $PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=234' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then increasing the memory CUDD probably will not help - PRISM is just trying to allocate more memory than is physically available on your system.\n</p>\n<p class='vspace'>Here are some general tips:\n</p>\n<div class='vspace'></div><ul><li>Try experimenting with using the different <em>engines</em> in PRISM. Read the section \"<a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Configuring PRISM - Computation Engines</a>\" for details.\n<div class='vspace'></div></li><li>Look at the detailed output of PRISM for information about memory usage. If you are using the hybrid (or sparse) engine and the limiting factor in terms of memory is creation of the vectors, then you have no choice but to try and reduce the size (number of states) of your model. If you are using the MTBDD engine, it is also well worth considering the variable ordering of your model. Both topics are discussed in the \"<a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n<div class='vspace'></div></li><li>Finally, if you can find no way to reduce the size of your model and are happy to consider an approximate (rather than exact) analysis, you may wish to try using PRISM's <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>discrete-event simulation engine</a> for analysis.\n</li></ul></div>\n<p class='vspace'><a name='memout_parse' id='memout_parse'></a>\n</p><h3>I ran out of memory during model parsing. What can I do?</h3>\n<div class='answer' > \n<p>This is a less common problem and will only occur if the actual PRISM language description of your model is very large. This may be the case, for example, if you are automatically generating PRISM models in some way. Errors due to lack of memory during parsing usually look like:\n</p>\r\n<div class='sourceblock ' id='sourceblock235'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.OutOfMemoryError: Java heap space </span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=235' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or:\n</p>\r\n<div class='sourceblock ' id='sourceblock236'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.StackOverflowError</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=236' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>You can resolve this problem by increasing the memory allocated to Java.\nSee the entry \"Java memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p></div>\n<hr />\n<h1>PRISM Modelling</h1>\n<p><a name='max_model_size' id='max_model_size'></a>\n</p><h3>What size models can PRISM handle?</h3>\n<div class='answer' > \n<p>There is no definitive answer to this. Because of PRISM's symbolic implementation, using data structures based on binary decision diagrams (BDDs), its performance can be unpredictable in this respect. There are also several factors that affect performance, including the type of model and property being checked and the engine being used (PRISM has several different engines, which have varying performance).\n</p>\n<p class='vspace'>Having said that, using the default engine in PRISM (the hybrid engine), you can normally expect to be able to handle models with up to 10^7-10^8 states on a typical PC. Using the MTBDD engine, you may be able to analyse much larger models (on some of the PRISM case studies, for example, PRISM can do numerical analysis of models with as many as 10^10 or 10^11 states). The manual has more information about PRISM's <a class='urllink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a>.\n</p></div>\n<p class='vspace'><a name='model_size' id='model_size'></a>\n</p><h3>How can I reduce the size of my model?</h3>\n<div class='answer' > \n<p>The size of a probabilistic model (i.e. the number of states/transitions) is critical to the efficiency of performing probabilistic model checking on it, since both the time and memory required to do so are often proportional to the model size. Unfortunately, it is very easy to create models that are extremely large. Below are a few general tips for reducing model size.\n</p>\n<div class='vspace'></div><ul><li>Look for variables that have unnecessarily large ranges and try to reduce them. Even if your model needs large variables, it is generally a good strategy to first get a smaller version building successfully and then scale it up afterwards.\n<div class='vspace'></div></li><li>Similarly, can you (if only temporarily) reduce the number of modules/components of your model? Start with the smallest number of components possible and then add others one by one.\n<div class='vspace'></div></li><li>Do you have any inter-dependencies between variables? For example, perhaps you have some variables which are simply functions of other variables of the model. Even if these are convenient for model checking, they can be replaced with <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>formulas or labels</a>, which do not contribute to the state space.\n<div class='vspace'></div></li><li>Do any variables include more detail than is necessary for the model? Perhaps this can be exploited in order to reduce the number of variables in your model.\n<div class='vspace'></div></li><li>More generally, are any aspects of the model not relevant to the properties that you are interested in? If so, start with a simpler, more abstract version of the model and then add more details if possible.\n</li></ul></div>\n<p class='vspace'><a name='ordering' id='ordering'></a>\n</p><h3>How can I choose a good variable ordering?</h3>\n<div class='answer' > \n<p>Because PRISM is a symbolic model checker, the amount of memory required to store the probabilistic model can vary (sometime unpredictably) according to several factors. One example is the order in which the variables of your model appear in the model file. In general, there is no definitive answer to what the best ordering is but the following heuristics are a good guide.\n</p>\n<div class='vspace'></div><ul><li>Variables which are closely related should appear close together\n<div class='vspace'></div></li><li>Variables which are related to most or all other variables should appear near the start of the ordering\n</li></ul><p class='vspace'>Variables <code>x</code> and <code>y</code> are \"related\" if, for example, the value of one is has an effect on how the other changes (e.g. <code>(y'=x+1)</code>) or if both appear together in an expression (e.g. a guard).\n</p>\n<p class='vspace'>These heuristics also apply to the ordering of <em>modules</em> within the model file.\n</p>\n<p class='vspace'>For technical details about variable ordering issues, see e.g. section 8 of [<a class='wikilink' href='References.html#HKN+03'>HKN+03</a>] or section 4.1.2 of [<a class='wikilink' href='References.html#Par02'>Par02</a>].\n</p></div>\n<p class='vspace'><a name='det_delay' id='det_delay'></a>\n</p><h3>How can I add deterministic time delays to a CTMC model?</h3>\n<div class='answer' > \n<p>All delays in a CTMC need to be modelled as <em>exponential</em> distributions. This is what makes them efficient to analyse. If you included a transition whose delay was <em>deterministic</em>, i.e. which always occurred after exactly the same delay,  the model would no longer be a CTMC.\n</p>\n<p class='vspace'>One solution to this, if your model require such a delay, is to approximate a deterministic delay with an <a class='urllink' href='http://en.wikipedia.org/wiki/Erlang_distribution'>Erlang distribution</a> (a special case of a phase-type distribution). See for example this PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock237'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mean</span> = <span class=\"prismnum\">10</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">trigger</span><br/>\n<br/>\n\t<span class=\"prismident\">i</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[]&nbsp;&nbsp;&nbsp;<span class=\"prismident\">i</span> &lt; <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">i</span> = <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">main</span><br/>\n<br/>\n\t<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=237' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the model, the occurrence of the the go-labelled action occurs with an Erlang distribution with mean <code>mean</code> and shape <code>k</code>. The special case of <code>k</code>=1 is just an exponential distribution. The graph below shows the probability distribution of the delay, i.e. of <code>P=? [ F&lt;=T x=1 ]</code> for different values of <code>k</code>.\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/faq-erlang.jpg' alt='' /></div>\n<p class='vspace'>There is an obvious trade-off here between the accuracy (how close it is to modelling a deterministic time delay) and the resulting blow-up in the size of the model that you add this to. For <code>k</code>=1000, you can see that the shape is quite \"deterministic\" but this would increase your model size by a factor of ~1000.\n</p></div>\n<p><br /><br />----\n</p>\n<div class='vspace'></div><h1><span class='big'>Appendices</span></h1>\n<hr />\n<h1>Explicit Model Files</h1>\n<p>This appendix details the plain text file formats used by PRISM for <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>exporting</a> and <a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>importing</a> models that have already been constructed, i.e., they comprise an explicit list of states, transitions, etc. making up the model, rather than a high-level model description in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM modelling language</a>.\nBelow, we describe:\n</p>\n<div class='vspace'></div><ul><li><a href='AllOnOnePage.html#tra'>Transitions (.tra) files</a>\n</li><li><a href='AllOnOnePage.html#trarows'>Transitions (.tra) files (row form)</a>\n</li><li><a href='AllOnOnePage.html#lab'>Labels (.lab) files</a>\n</li><li><a href='AllOnOnePage.html#srew'>State rewards (.srew) files</a>\n</li><li><a href='AllOnOnePage.html#trew'>Transition rewards (.trew) files</a>\n</li><li><a href='AllOnOnePage.html#sta'>State (.sta) files</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='tra' id='tra'></a>\n</p><h3>Transitions (.tra) files</h3>\n<p>These contain an explicit list of the transitions making up a probabilistic model, i.e. they are essentially a sparse matrix representation of the transition probability/rate matrix. The first line of the file contains information about the size of the model, the remaining lines contain information about transitions, one per line.\n</p>\n<p class='vspace'><strong>DTMCs and CTMCs</strong>\n</p>\n<p class='vspace'>For Markov chains the first line take the form \"<code>n m</code>\", giving the number of states (<code>n</code>) and the number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i j x</code>\" or \"<code>i j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, and <code>x</code> is the probability (for a DTMC) or rate (for a CTMC) of the transition. State indices are zero-indexed (i.e. between <code>0</code> and <code>n-1</code>). Probability/rate values are written as (positive) floating point numbers (examples: <code>0.5</code>, <code>.5</code>, <code>5.6e-6</code>, <code>1</code>). <code>a</code> is optional and gives the action label for the transition. Action labels can be present for some, all or no transitions.\n</p>\n<p class='vspace'>It is assumed that source states (rows) are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each source state.\n</p>\n<p class='vspace'>For a DTMC, the probabilities for the outgoing transitions of each state should sum to 1.\n</p>\n<p class='vspace'>Here is an example, for the (DTMC) PRISM model <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (which looks like <a class='urllink' href='../uploads/lec3.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock238'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 1 0.5<br />\n0 3 0.5<br />\n1 0 0.5<br />\n1 2 0.25<br />\n1 4 0.25<br />\n2 5 1<br />\n3 3 1<br />\n4 4 1<br />\n5 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=238' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is one for the (CTMC) PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a> (which looks like <a class='urllink' href='../uploads/poll2.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock239'>\r\n  <div class='sourceblocktext'><div class=\"text\">12 22<br />\n0 1 0.5<br />\n0 2 0.5<br />\n0 6 200<br />\n1 3 0.5<br />\n1 7 200<br />\n2 3 0.5<br />\n2 4 200<br />\n3 5 200<br />\n4 5 0.5<br />\n4 6 1<br />\n5 7 1<br />\n6 0 200<br />\n6 7 0.5<br />\n6 8 0.5<br />\n7 9 0.5<br />\n7 10 200<br />\n8 2 200<br />\n8 9 0.5<br />\n9 11 200<br />\n10 0 1<br />\n10 11 0.5<br />\n11 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=239' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>MDPs (or PAs)</strong>\n</p>\n<p class='vspace'>For MDPs, the format is an extension of the above\nTo clarify terminology: each <em>state</em> of the MDP contains (nondeterministic) <em>choices</em>, each of which is essentially a probability distribution over successor states that we can view as a set of <em>transitions</em>. Optionally, each choice can be labelled with an <em>action</em>.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m</code>\", giving the number of states (<code>n</code>), the total number of choices (<code>c</code>) and the total number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i k j x</code>\" or \"<code>i k j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, <code>k</code> is the index of the choice that it belongs to, and <code>x</code> is the probability of the transition. <code>a</code> is optional and gives the action label for the choice of the transition. Action labels can be present for some, all or no states but, in slightly redundant fashion, the action labels, if present, must be the same for all transitions belonging to the same choice.\n</p>\n<p class='vspace'>State indices and choice indices are all zero-indexed. Probability values (as above) are written as (positive) floating point numbers and should sum to 1 for each choice.\nIt is assumed that source states (rows) and choices within states are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each choice.\n</p>\n<p class='vspace'>Here is an example, for the (MDP) PRISM model <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdp.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock240'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 <br />\n1 0 0 0.7 <br />\n1 0 1 0.3 <br />\n1 1 2 0.5 <br />\n1 1 3 0.5 <br />\n2 0 2 1 <br />\n3 0 3 1 </div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=240' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is an action-labelled version of the same model, <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdpa.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock241'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 a<br />\n1 0 2 0.5 c<br />\n1 0 3 0.5 c<br />\n1 1 0 0.7 b<br />\n1 1 1 0.3 b<br />\n2 0 2 1 a<br />\n3 0 3 1 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=241' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>POMDPs</strong>\n</p>\n<p class='vspace'>The format of a <code>.tra</code> file for a POMDP is similar to an MDP,\nbut also contains information about observations.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m o</code>\", where <code>n</code>, <code>c</code> and <code>m</code> are, as for MDPs, the numbers of states, choices and transitions,\nand <code>o</code> is the number of observations.\nThe lines that list transitions contain an additional integer after the transition probability\n(and before the action, if present), giving the (deterministic) observation that is made\nwhen entering the target state of that transition.\nCurrently, it is assumed that these are consistent for all states.\n</p>\n<p class='vspace'>In order to also specify the observation for the initial state,\na dummy transition line of the form <code>- - s - o</code> is used,\ngiving both the initial state <code>s</code> and its observation <code>o</code>.\n</p>\n<p class='vspace'>An example file is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock242'>\r\n  <div class='sourceblocktext'><div class=\"text\">10 16 18 4<br />\n- - 0 - 0<br />\n0 0 1 0.1 1 toss<br />\n0 0 2 0.3 1 toss<br />\n0 0 3 0.6 1 toss<br />\n1 0 4 1 2 guess1<br />\n1 1 7 1 3 guess2<br />\n1 2 7 1 3 guess3<br />\n2 0 8 1 3 guess1<br />\n2 1 5 1 2 guess2<br />\n2 2 8 1 3 guess3<br />\n3 0 9 1 3 guess1<br />\n3 1 9 1 3 guess2<br />\n3 2 6 1 2 guess3<br />\n4 0 4 1 2 loop<br />\n5 0 5 1 2 loop<br />\n6 0 6 1 2 loop<br />\n7 0 7 1 3<br />\n8 0 8 1 3<br />\n9 0 9 1 3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=242' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trarows' id='trarows'></a>\n</p><h3>Transitions (.tra) files (row form)</h3>\n<p>There is alternative format for transition matrices (see the <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html#other'>rows</a> option for <code>-exportmodel</code>) where transitions for each state/choice are collated on a single line.\n</p>\n<p class='vspace'>Here is the result for the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> example from above (a DTMC):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock243'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 0.5:1 0.5:3<br />\n1 0.5:0 0.25:2 0.25:4<br />\n2 1:5<br />\n3 1:3<br />\n4 1:4<br />\n5 1:2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=243' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> example (an MDP):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock244'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 <br />\n1 0.7:0 0.3:1 <br />\n1 0.5:2 0.5:3 <br />\n2 1:2 <br />\n3 1:3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=244' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and for the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> example (an MDP with actions):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock245'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 a<br />\n1 0.5:2 0.5:3 c<br />\n1 0.7:0 0.3:1 b<br />\n2 1:2 a<br />\n3 1:3 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=245' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='lab' id='lab'></a>\n</p><h3>Labels (.lab) files</h3>\n<p>These contain an explicit list of which <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> are satisfied in each state.\nThe first line lists the labels, assigning each one an index.\nThe remaining lines list indices of all states satisfying one or more labels,\nfollowed by a list of the the indices of labels that that are satisfied in it.\nThis includes the built-in labels <code>\"init\"</code> (initial states) and <code>deadlock</code> (deadlock states).\nAn example is shown below, where, for example, both <code>\"heads\"</code> and <code>\"end\"</code> are satisfied in state 2.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock246'>\r\n  <div class='sourceblocktext'><div class=\"text\">0=&quot;init&quot; 1=&quot;deadlock&quot; 2=&quot;heads&quot; 3=&quot;tails&quot; 4=&quot;end&quot;<br />\n0: 0<br />\n2: 2 4<br />\n3: 3 4</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=246' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='srew' id='srew'></a>\n</p><h3>State rewards (.srew) files</h3>\n<p>Reward files contain an (optional) header, giving the name of the reward structure that generated it\nand the type of rewards (state or transitions) stored in the file.\nFor state rewards, the information following this header is an explicit list of the (non-zero) state rewards.\nThe first line is of the form <code>n m</code> where <code>n</code> is the number of states in the model and <code>m</code> is the number of non-zero state rewards.\nThe following <code>m</code> lines are of the form <code>i r</code>, denoting that the state reward for state <code>i</code> is <code>r</code>.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get rewards in 3 states (0, 4 and 5):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock247'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure &quot;r&quot;<br />\n# State rewards<br />\n6 3<br />\n0 2<br />\n4 1<br />\n5 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=247' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trew' id='trew'></a>\n</p><h3>Transition rewards (.trew) files</h3>\n<p>Files containing transition rewards, like those for state rewards, start with an (optional) header.\nThe rest of the file is formatted identically to transitions files (see <a href='AllOnOnePage.html#tra'>above</a>),\nexcept that probabilities/rates are replaced with reward values,\nand the number of transitions (the last number on the first line) is replaced with the number of non-zero transition rewards.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock248'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n6 4<br />\n1 0 1<br />\n1 2 1<br />\n1 4 1<br />\n2 5 2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=248' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And or the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (4-state) MDP example, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock249'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n4 5 4<br />\n1 0 2 6<br />\n1 0 3 6<br />\n1 1 0 5<br />\n1 1 1 5</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=249' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='sta' id='sta'></a>\n</p><h3>States (.sta) files</h3>\n<p>These contain an explicit list of the reachable states of a model. The first line is of the form <code>(v1,...,vn)</code>, listing the names of all the variables in the model in the order that they appear in the PRISM model. Subsequent lines list the values of the <code>n</code> variables in each state of the model. Each line is of the form <code>i:(x1,...,xn)</code>, where <code>i</code> is the index of the state (starting from 0) and <code>x1,...,xn</code> are the values of each variable in the state. States are ordered by their index (and, therefore, given PRISM's default behaviour, lexicographically according to the tuple of variable values).\n</p>\n<p class='vspace'>For the example PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a>, the states file looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock250'>\r\n  <div class='sourceblocktext'><div class=\"text\">(s,a,s1,s2)<br />\n0:(1,0,0,0)<br />\n1:(1,0,0,1)<br />\n2:(1,0,1,0)<br />\n3:(1,0,1,1)<br />\n4:(1,1,1,0)<br />\n5:(1,1,1,1)<br />\n6:(2,0,0,0)<br />\n7:(2,0,0,1)<br />\n8:(2,0,1,0)<br />\n9:(2,0,1,1)<br />\n10:(2,1,0,1)<br />\n11:(2,1,1,1)</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=250' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><br /><br />\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/AllOnOnePage@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / All On One Page | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/AllOnOnePage@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / All On One Page | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/AllOnOnePage@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Main / Real-time Models </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for xml\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.xml .de1, .xml .de2 {font-family: monospace; font-weight: normal;}\n.xml  {font-family:monospace;}\n.xml .imp {font-weight: bold; color: red;}\n.xml li, .xml .li1 {font-family: monospace; color: black; font-weight: normal;}\n.xml .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.xml .li2 {font-weight: bold;}\n.xml .es0 {color: #000099; font-weight: bold;}\n.xml .br0 {color: #66cc66;}\n.xml .sy0 {color: #66cc66;}\n.xml .st0 {color: #ff0000;}\n.xml .nu0 {color: #cc66cc;}\n.xml .sc-1 {color: #808080; font-style: italic;}\n.xml .sc0 {color: #00bbdd;}\n.xml .sc1 {color: #ddbb00;}\n.xml .sc2 {color: #339933;}\n.xml .sc3 {color: #009900;}\n.xml .re0 {color: #000066;}\n.xml .re1 {color: #000000; font-weight: bold;}\n.xml .re2 {color: #000000; font-weight: bold;}\n.xml .ln-xtra, .xml li.ln-xtra, .xml div.ln-xtra {background-color: #ffc;}\n.xml span.xtra { display:block; }\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>PRISM Manual</span> &nbsp; version 4.10.1</h1>\n<hr />\n<h1><span class='big'>Contents</span></h1>\n<hr />\n<h1><a class='wikilink' href='Introduction.html'>Introduction</a></h1>\n<div class='vspace'></div><h1><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a></h1>\n<ul><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a></h1>\n<ul><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a></h1>\n<ul><li><a class='wikilink' href='../PropertySpecification/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../PropertySpecification/IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='../PropertySpecification/ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='../PropertySpecification/TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='../PropertySpecification/PropertiesFiles.html'>Properties Files</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a></h1>\n<ul><li><a class='wikilink' href='../RunningPRISM/Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='../RunningPRISM/LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='../RunningPRISM/SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a></h1>\n<ul><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Other Options</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='References.html'>References</a></h1>\n<div class='vspace'></div><h1><a class='wikilink' href='../Appendices/Main.html'>Appendices</a></h1>\n<ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul><p><br /><br />\n</p><hr />\n<h1><span class='big'>Introduction</span></h1>\n<hr />\n<p>PRISM is a <em>probabilistic model checker</em>,\na tool for the modelling and analysis of systems which exhibit probabilistic behaviour.\nProbabilistic model checking is a <em>formal verification</em> technique.\nIt is based on the construction of a precise mathematical model of a system which is to be analysed.\nProperties of this system are then expressed formally in temporal logic\nand automatically analysed against the constructed model.\n</p>\n<p class='vspace'>PRISM has support for a wide range of probabilistic models:\n</p>\n<div class='vspace'></div><ul><li>discrete-time Markov chains (DTMCs)\n</li><li>continuous-time Markov chains (CTMCs)\n</li><li>Markov decision processes (MDPs)\n</li><li>probabilistic timed automata (PTAs)\n</li><li>partially observable Markov decision processes (POMDPs)\n</li><li>partially observable probabilistic timed automata (POPTAs)\n</li></ul><p class='vspace'>In fact, PRISM's support for MDPs extends to the more general model of \nprobabilistic automata (PAs) [<a class='wikilink' href='References.html#Seg95'>Seg95</a>], which does not require unique action names in each state.\nFor background material on these models, look at the pointers to\n<a class='urllink' href='http://www.prismmodelchecker.org/about.php'>resources</a>\non the PRISM web site.\n</p>\n<p class='vspace'>PRISM also supports non-probabilistic models, notably labelled transition systems (LTSs).\n</p>\n<p class='vspace'>Models are supplied to the tool by writing descriptions in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM language</a>, a simple, high-level modelling language.\n</p>\n<p class='vspace'>Properties of these models are written in the PRISM <a class='wikilink' href='../PropertySpecification/Main.html'>property specification language</a> which is based on temporal logic. It incorporates several well-known probabilistic temporal logics:\n</p>\n<div class='vspace'></div><ul><li>PCTL (probabilistic computation tree logic),\n</li><li>CSL (continuous stochastic logic),\n</li><li>(probabiistic) LTL (linear time logic),\n</li><li>PCTL* (which subsumes both PCTL and LTL).\n</li></ul><p class='vspace'>The property language also supports <a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>costs and rewards</a>, \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>numerical</a>\" properties, several other custom features and extensions, and also also incorporates the non-probabilistic temporal logics CTL (computation tree logic) and LTL.\n</p>\n<p class='vspace'>PRISM performs probabilistic model checking, based on exhaustive search and numerical solution, to automatically analyse such properties. It also contains a <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>discrete-event simulation</a> engine for <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a>.\n<br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Installing PRISM</span></h1>\n<hr />\n<h1>Instructions</h1>\n<h3>Prerequisites</h3>\n<p>PRISM is known to run on Linux, Windows and macOS, both 64-bit and 32-bit versions.\n</p>\n<p class='vspace'>You will need <strong>Java</strong>, version 11 or above.\nTo run binary versions of PRISM, you only need the Java Runtime Environment (JRE), not the full Java Development Kit (JDK).\n</p>\n<p class='vspace'>To compile PRISM from source, you need the Java Development Kit (JDK), GNU make and a C/C++ compiler (e.g. gcc/g++). For compilation under Windows, you will need Cygwin. See below for more information:\n</p>\n<div class='vspace'></div><ul><li><a href='AllOnOnePage@action=print.html#windows'>Installation on Windows</a>\n</li><li><a href='AllOnOnePage@action=print.html#binaries'>Installation of Linux/Mac binary versions</a>\n</li><li><a href='AllOnOnePage@action=print.html#source'>Building PRISM from source (non-Windows)</a>\n</li><li><a href='AllOnOnePage@action=print.html#cygwin'>Building PRISM from source on Windows using Cygwin</a>\n</li><li><a href='AllOnOnePage@action=print.html#msys'>Building PRISM from source on Windows using MSYS2</a>\n</li></ul><p class='vspace'>If you are installing on a completely fresh operating system installation (e.g. in a virtual machine), you may find the following scripts useful,\nwhich install the required dependencies and PRISM itself. They can be found in the <code>prism/etc/scripts</code> directory:\n</p>\n<div class='vspace'></div><ul><li>Script to build on a clean install of Ubuntu: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-ubuntu'>prism-install-ubuntu</a>\n</li><li>Script to build on a clean install of Fedora-based Linux (e.g. Amazon Linux): <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-fedora'>prism-install-fedora</a>\n</li><li>Scripts to build on a clean install of Windows: <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> and <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-cygwin'>prism-install-cygwin</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='windows' id='windows'></a>\n<a name='windows64' id='windows64'></a>\n</p><h3>Installation on Windows</h3>\n<p>If you don't yet have <strong>Java</strong>, install it, for example with the <a class='urllink' href='https://adoptium.net/temurin/releases'>Temurin installer</a>.\n</p>\n<p class='vspace'>To install PRISM on Windows, just run the self-extracting installer which you <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>downloaded</a>. You do <strong>not</strong> need administrator privileges for this, just write-access to the directory chosen for installation.\n</p>\n<p class='vspace'>If requested, the installer will place shortcuts to run PRISM on the desktop and/or start menu. If not, you can run by PRISM double-clicking the file <code>xprism.bat</code> (which may just appear as <code>xprism</code>) in the <code>bin</code> folder of your PRISM folder. If nothing happens, the most likely explanation is that Java is not installed or not in your path. To check, open a command prompt window, navigate to the PRISM directory, type <code>cd bin</code>, then <code>xprism.bat</code> and examine the resulting error. If you want to create shortcuts to <code>xprism.bat</code> manually, you will find some PRISM icons in the <code>etc</code> folder.\n</p>\n<p class='vspace'>If you wish to use the command-line version of PRISM on Windows, open a command prompt window and type for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd \"c:\\Program Files\\prism-4.8-win\\bin\"</span><br/>\n<span style=\"font-weight:bold;\">prism ..\\prism-examples\\simple\\dice\\dice.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n    \n<p class='vspace'>You can also edit the file <code>bin\\prism.bat</code> to allow it to be run from any location. See the instructions within the file for further details.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='binaries' id='binaries'></a>\n</p><h3>Installation of Linux/Mac binary versions</h3>\n<p>We provide pre-compiled <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>binary distributions</a> for Linux and macOS\n(if you have any problems running these, try compiling PRISM from source instead - see below for instructions).\nTo install a binary distribution, unpack the tarred/zipped PRISM distribution into a suitable location, enter the directory and run the <code>install.sh</code> script, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-linux64-x86.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-linux64-x86</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>On macOS, you may want to run the following command,\nwhich avoids <a class='urllink' href='https://support.apple.com/en-gb/102445'>manual approving</a> the integrity of the binary files:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You do not need to be root to install PRISM. The install script simply makes some small customisations to the scripts used to launch PRISM. The PRISM distribution is self-contained and can be freely moved/renamed, however if you do so you will need to re-run <code>./install.sh</code> afterwards.\n</p>\n<p class='vspace'>To run PRISM, execute either the <code>xprism</code> or <code>prism</code> script (for the graphical user interface or command-line version, respectively). These can be found in the <code>bin</code> directory. These scripts are designed to be run from anywhere and you can easily create symbolic links or aliases to them. If you want icons to create desktop shortcuts to PRISM, you can find some in the <code>etc</code> directory.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='source' id='source'></a>\n</p><h3>Building PRISM from source (non-Windows)</h3>\n<p>To compile PRISM form source code, you will need:\n</p>\n<div class='vspace'></div><ul><li>GNU make (sometimes called gmake)\n</li><li>a C/C++ compiler (e.g. gcc/g++)\n</li><li>a Java Development Kit, version 11 or above\n</li></ul><p class='vspace'>To check that you have the development kit, type <code>javac</code>. If you get an error message that <code>javac</code> cannot be found, you probably do not have the JDK installed (or your path is not set up correctly). To check what version you have, type <code>javac -version</code>. \n</p>\n<p class='vspace'>Hopefully, you can build PRISM simply by entering the PRISM directory and running <code>make</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">tar xfz prism-4.8-src.tar.gz</span><br/>\n<span style=\"font-weight:bold;\">cd prism-4.8-src/prism</span><br/>\n<span style=\"font-weight:bold;\">make</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For this process to complete correctly, PRISM needs to be able to determine your operating system (<code>OSTYPE</code>), machine architecture (<code>ARCH</code>) and the location of your Java distribution (<code>JAVA_DIR</code>). If there is a problem with either of these, you will see an error message and will need to specify one or more of these manually, such as in these examples:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">  </span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=linux ARCH=aarch64</span><br/>\n<span style=\"font-weight:bold;\">make JAVA_DIR=/usr/java/jdk1.8.0</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin JAVA_DIR=\"/cygdrive/c/Program Files/Java/jdk1.8.0\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of double quotes for the case where the directory contains a space. If you don't know the location of your Java installation, try typing <code>which javac</code>. If the result is e.g. <code>/usr/java/jdk1.8.0/bin/javac</code> then your Java directory is <code>/usr/java/jdk1.8.0</code>. Sometimes <code>javac</code> will be a symbolic link, in which case use \"<code>ls -l</code>\" to determine the actual location.\n</p>\n<p class='vspace'>It is also possible to to set the environment variables directly or edit their values in the Makefile directly. Note that even when you specify <code>JAVA_DIR</code> explicitly (in either way), PRISM still uses the version of <code>javac</code> that is in your path. To override this, you can also specify a specific version by setting <code>JAVAC</code>.\n</p>\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='cygwin' id='cygwin'></a>\n</p><h3>Building PRISM from source on Windows using Cygwin</h3>\n<p>The compilation of PRISM currently relies on a Unix-like environment. On Windows, this can be achieved using the <a class='urllink' href='http://www.cygwin.com/'>Cygwin</a> development environment, with the packages below installed.\nYou can run the script <a class='urllink' href='https://raw.githubusercontent.com/prismmodelchecker/prism/master/prism/etc/scripts/prism-install-windows.bat'>prism-install-windows.bat</a> in a Command Prompt to automate this.\n</p><ul><li><code>make</code>\n</li><li><code>mingw64-x86_64-gcc-g++</code> (for 64-bit Windows) or <code>mingw64-i686-gcc-g++</code> (for 32-bit Windows)\n</li><li><code>binutils</code>\n</li><li><code>dos2unix</code>\n</li><li><code>git</code> (if you will pull source code from GitHub)\n</li><li><code>wget</code> (if you will pull source code from the web)\n</li></ul><p>Then proceed as described in the previous section. Note that the PRISM compilation process uses the <a class='urllink' href='http://www.mingw.org/'>MinGW</a> libraries so that the final result is independent of Cygwin at run-time.\n</p>\n<p class='vspace'>One thing to note: make sure you unzip the PRISM distribution from within Cygwin (e.g. using <code>tar xfz prism-XXX-src.tar.gz</code>). Don't use a Windows program (Winzip, etc.) since this can cause problems.\n</p>\n<p class='vspace'>If you use git to checkout the PRISM repository, we recommend that you use the version of git provided by Cygwin.\nIf you use a native Windows version of git, you may want to disable the Unix-to-Windows line-ending conversion, e.g., via\n</p>\n<div class='vspace'></div><ul><li><code>git config --global core.autocrlf false</code>\n</li></ul><p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p>\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='msys' id='msys'></a>\n</p><h3>Building PRISM from source on Windows using MSYS2</h3>\n<p>An alternative to Cygwin on Windows is <a class='urllink' href='https://www.msys2.org/'>MSYS2</a>.\nYou can install the required MSYS2 packages like this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">pacman -S make mingw-w64-x86_64-gcc binutils dos2unix git wget unzip python nano</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The environment is currently not directly supported in the Makefile,\nwhich can be fixed as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Additionally, MSYS2 does not handle symlinks in the same way as Cygwin does.\nAt some point <code>make</code> will fail, saying that it cannot find the CUDD library.\nYou can solve this as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd ../cudd/</span><br/>\n<span style=\"font-weight:bold;\">rmdir lib/ </span><br/>\n<span style=\"font-weight:bold;\">./setup.sh</span><br/>\n<span style=\"font-weight:bold;\">cd ../prism</span><br/>\n<span style=\"font-weight:bold;\">make OSTYPE=cygwin CC=/mingw64/bin/gcc CXX=/mingw64/bin/g++</span><br/>\n<span style=\"font-weight:bold;\">./install.sh</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Problems?</strong> See the section \"<a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>''.\n</p><hr />\n<h1>Common Problems And Questions</h1>\n<p>This section describes some of the most common problems and questions related to the installation and running of PRISM. These are grouped into the following categories:\n</p>\n<div class='vspace'></div><ul><li>Running PRISM on Windows\n</li><li>Running PRISM on non-Windows platforms\n</li><li>Compiling PRISM\n</li><li>Other issues\n</li></ul><div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on Windows</h2>\n<p><strong>When I try to run PRISM on Windows, I double-click the PRISM shortcut but nothing happens.</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>The most common cause of this is that you either do not have Java installed or the <code>java</code> executable is not in your path. In any case, to determine the exact problem, launch a command shell and navigate to the <code>bin</code> directory inside the directory where you installed PRISM (you can use the \"PRISM (console)\" shortcut installed in the start menu to do this). Then, type <code>prism.bat</code> and see what error message is displayed.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Running PRISM on non-Windows platforms</h2>\n<p><strong>When I try to run PRISM, I get one of these errors:</strong><br />\n</p><ul><li><strong><code>Exception in thread \"main\" java.lang.NoClassDefFoundError: ...</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: no prism in java.library.path</code></strong>\n</li><li><strong><code>java.lang.UnsatisfiedLinkError: ...<br />Library not loaded: ../../lib/libdd.dylib</code></strong>\n</li></ul><div class='vspace'></div><div class='answer' > \n<p>Things to check:\n</p>\n<p class='vspace'>(1) Did you run <code>install.sh</code> from the PRISM directory? (non-Windows platforms)\n</p>\n<p class='vspace'>(2) If you compiled PRISM from source code, are you sure no errors occurred during the process? To check, go into the PRISM directory, type <code>make clean_all</code> and then <code>make</code>, checking the output (especially at the end) carefully for any error messages.\n</p>\n<p class='vspace'>(3) Are you running on Mac OS? See the next question.\n</p>\n<p class='vspace'>(3) Are you running on an old version of Mac OS (notably El Capitan)? This had some issues with PRISM calling <code>java</code>.\nA workaround is to specify the exact path to the <code>java</code> when running PRISM, e.g.:\n</p>\n<p class='vspace'><code>PRISM_JAVA=/Library/Java/JavaVirtualMachines/jdk1.9.jdk/Contents/Home/bin/java prism</code>\n</p>\n<p class='vspace'>or by replacing the value of PRISM_JAVA directly in the prism script\ndirectly.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM on macOS, I get an error of the form: \"<code>libprism.dylib</code> cant be opened because Apple cannot check it for malicious software.\" or \"<code>libprism.dylib not valid for use in process: library load disallowed by system policy</code>\".</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM's macOS binaries are currently not signed/notarised,\nso you need to approve the binary files manually to run them.\nRun this command from the same place you ran <code>./install.sh</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xattr -d com.apple.quarantine lib/*lib</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or approve the libraries one by one through the\n<a class='urllink' href='https://support.apple.com/en-gb/102445'>security settings</a>.\n</p>\n<p class='vspace'>You can also avoid this issue by compiling from source code.\n</p></div>\n<p class='vspace'><strong>When I try to run PRISM, I get an error of the form:<br /><code>Exception in thread \"main\" java.lang.UnsupportedClassVersionError: Bad version number in .class file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Your version of Java is too old. Update or install a newer version of Java, and then try again.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Compiling PRISM</h2>\n<p><strong>When I try to compile PRISM, <code>make</code> seems to get stuck in an infinite loop</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>This is probably due to the detection of Java failing. Specify the location of your Java directory by hand, e.g. <code>make JAVA_DIR=/usr/java/jdk1.9.0</code>. See the <a class='wikilink' href='../InstallingPRISM/Main.html'>Instructions</a> page for more on this.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>/usr/bin/libtool: for architecture: cputype (16777234) cpusubtype (0) file: -lSystem is not an object file (not allowed in a library)</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you compiling PRISM on Max OS X? If so, the likely explanation is that you have upgraded to a new version of Mac OS X but have not upgraded the developer tools (eg. XCode). Upgrade and try again.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, nothing seems to happen</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get errors of the form:<br /><code>Unexpected end of line seen...</code><br />or:<br /><code>make: Fatal error in reader: Makefile, line 58: Unexpected end of line seen...</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Perhaps you are not using the GNU version of <code>make</code>. Try typing <code>make -v</code> to find out. On some systems, GNU make is called <code>gmake</code>.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>./setup.sh: line 33: syntax error: unexpected end of file</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Are you building on Cygwin? And did you unpack PRISM using WinZip? If so, unpack from Cygwin, using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>When I try to compile PRISM, I get an error of the form:<br /><code>Assembler messages:  Fatal error: can't create ../../obj/dd/dd_abstr.o: No such file or directory</code></strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Did you unpack PRISM using a graphical tool or file manager? If so, unpack using <code>tar xfz</code> (or similar) instead.\n</p></div>\n<p class='vspace'><strong>Do I have to use GNU <code>make</code> to build PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Strictly speaking, no, but you will have to modify the various PRISM Makefiles manually to overcome this.\n</p></div>\n<p class='vspace'><strong>Can I build PRISM on operating systems other than those currently supported?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>PRISM should be suitable for any Unix/Linux variant.\n</p>\n<p class='vspace'>The first thing you will need to do is compile CUDD (the BDD library used by and included in PRISM) on that platform.\nFortunately, CUDD has already been successfully built on a large number of\noperating systems. Have a look at the sample Makefiles we provide (i.e. the\nfiles <code>cudd/Makefile.*</code>) which are slight variants of the original Makefile\nprovided with CUDD (found here: <code>cudd/modified/orig/Makefile</code>). They contain\ninstructions on how to modify it for various platforms. You can then call\nyour new modified makefile something appropriate (<code>cudd/Makefile.$OSTYPE</code>) and\nproceed to build PRISM as usual. To just build CUDD, not PRISM, type\n<code>make cuddpackage</code> instead of <code>make</code>.\n</p>\n<p class='vspace'>Next, look at the main PRISM Makefile, in particular, each place where the\nvariable <code>$OSTYPE</code> is referred to. Most lines include comments and further\ninstructions. Once you have done this, proceed as usual.\n</p>\n<p class='vspace'>If you do successfully build PRISM on other platforms, please let us know\nso we can include this information in future releases. Thanks.\n</p></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h2>Other issues</h2>\n<p><strong>How do I uninstall PRISM?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>If you installed PRISM on Windows using the self-extracting installer, you can uninstall it using the option on the start menu. If you didn't add these shortcuts, just run <code>uninstall.exe</code> from the directory where you installed PRISM.\n</p>\n<p class='vspace'>For older versions of PRISM on Windows or on any other platform, simply delete the directory containing it.\n</p>\n<p class='vspace'>The only thing that is not removed via either of these methods is the <code>.prism</code> file containing your PRISM settings which is in your home directory (see the section \"<a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\"). You may wish to retain this when upgrading.\n</p></div>\n<p class='vspace'><strong>I still have a problem installing/running PRISM. What can I do?</strong>\n</p>\n<div class='vspace'></div><div class='answer' > \n<p>Please post a message in the discussion group (see the <a class='urllink' href='http://www.prismmodelchecker.org/support.php'>support</a> section of the PRISM website).\n</p></div>\n<p><br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>The PRISM Language</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>In order to construct and analyse a model with PRISM,\nit must be specified in the PRISM language,\na simple, state-based language,\nbased on the Reactive Modules formalism of Alur and Henzinger [<a class='wikilink' href='References.html#AH99'>AH99</a>].\nThis is used for <a class='wikilink' href='Introduction.html'>all of the types of model</a> that PRISM supports.\n</p>\n<p class='vspace'>In this section, we describe the PRISM language and present a number of small illustrative examples.\nA precise definition of the semantics of the language is available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site. One of the best ways to learn what can be done with the PRISM language is to look at some existing examples.\nA number of these are included with the tool distribution in the <code>prism-examples</code> directory.\nMany additional examples can be found on the \"<a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a>\" section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<p class='vspace'>The fundamental components of the PRISM language are <em>modules</em> and <em>variables</em>.\nA model is composed of a number of <em>modules</em> which can interact with each other.\nA module contains a number of local <em>variables</em>.\nThe values of these variables at any given time constitute the state of the module.\nThe <em>global state</em> of the whole model is determined by the <em>local state</em> of all modules.\nThe behaviour of each module is described by a set of <em>commands</em>.\nA command takes the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[<span class=\"prismident\">action</span>] <span class=\"prismident\">guard</span> -&gt; <span class=\"prismident\">prob_1</span> : <span class=\"prismident\">update_1</span> + ... + <span class=\"prismident\">prob_n</span> : <span class=\"prismident\">update_n</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <em>guard</em> is a predicate over all the variables in the model (including those belonging to other modules). Each <em>update</em> describes a transition which the module can make if the guard is true. A transition is specified by giving the new values of the variables in the module, possibly as a function of other variables. Each update is assigned a probability (or in some cases a rate) which will be assigned to the corresponding transition. The command also optionally includes an <em>action</em>, either just to annotate it, or for <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation</a>.\n</p><hr />\n<h1>Example 1</h1>\n<p>We will use the following simple example to illustrate the basic concepts of the PRISM language.\nConsider a system comprising two identical processes which must operate under mutual exclusion.\nEach process can be in one of 3 states: {0,1,2}.\nFrom state 0, a process will move to state 1 with probability 0.2\nand remain in the same state with probability 0.8.\nFrom state 1, it tries to move to the critical section: state 2.\nThis can only occur if the other process is not in its critical section.\nFinally, from state 2, a process will either remain there or move back to state 0\nwith equal probability.\nThe PRISM code to describe an MDP model of this system can be seen below.\nIn the next sections, we explain each aspect of the code in turn.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 1</span><br/>\n<span class=\"prismcomment\">// Two process mutual exclusion</span><br/>\n<br/>\n<span class=\"prismkeyword\">mdp</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M1</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">y</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 1</strong>\n</p><hr />\n<h1>Model Type</h1>\n<p>As mentioned above, the PRISM language can be used to describe several types of probabilistic models.\nTo indicate which type is being described, a PRISM model usually includes a model type keyword:\n</p>\n<div class='vspace'></div><ul><li><code><strong>dtmc</strong></code>: discrete-time Markov chain\n</li><li><code><strong>ctmc</strong></code>: continuous-time Markov chain\n</li><li><code><strong>mdp</strong></code>: Markov decision process (or probabilistic automaton)\n</li><li><code><strong>pta</strong></code>: probabilistic timed automaton\n</li><li><code><strong>pomdp</strong></code>: partially observable Markov decision process\n</li><li><code><strong>popta</strong></code>: partially observable probabilistic timed automaton\n</li></ul><p class='vspace'>This is typically at the very start of the file,\nbut can actually occur anywhere in the file (except inside modules and other declarations).\n</p>\n<p class='vspace'>If no such model type declaration is included, the model is by default assumed to be an MDP.\nPRISM also performs some auto-detection of the model type;\nfor example, an MDP with <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>clock variables</a> is assumed to be a PTA,\nand an MDP with <a class='createlinktext' rel='nofollow'\n    href='../ThePRISMLanguage/POMDPs@action=edit.html'>observables</a><a rel='nofollow' \n    class='createlink' href='../ThePRISMLanguage/POMDPs@action=edit.html'>?</a> is assumed to be a POMDP.\n</p>\n<p class='vspace'><strong>Note:</strong> For compatibility with old versions of PRISM,\nthe keywords <code><strong>probabilistic</strong></code>, <code><strong>stochastic</strong></code> and <code><strong>nondeterministic</strong></code>\ncan be used as alternatives for <code><strong>dtmc</strong></code>, <code><strong>ctmc</strong></code> and <code><strong>mdp</strong></code>, respectively.\n</p>\n<div class='vspace'></div><hr />\n<h1>Modules And Variables</h1>\n<p>The <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>previous example</a> uses two modules, <code>M1</code> and <code>M2</code>, one representing each process.\nA module is specified as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">name</span> ... <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The definition of a module contains two parts: its <em>variables</em> and its <em>commands</em>.\nThe variables describe the possible states that the module can be in;\nthe <a class='wikilink' href='../ThePRISMLanguage/Commands.html'>commands</a> describe its behaviour, i.e. the way in which the state changes over time.\nCurrently, PRISM supports just a few simple types of variables:\nthey can either be (finite ranges of) integers or Booleans\n(we ignore <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>clocks</a> for now).\n</p>\n<p class='vspace'>In the example above, each module has one integer variable with range <code>[0..2]</code>.\nA variable declaration looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the initial value of the variable is also specified.\nA Boolean variable is declared as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">false</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It is also possible to omit the initial value of a variable,\nin which case it is assumed to be the lowest value in the range (or <code>false</code> for a Boolean).\nThus, the variable declarations shown below are equivalent to the ones above.\nAs will be described later, it is also possible to specify\n<a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>multiple initial states</a> for a model.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>];<br/>\n<span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We also mention that, for a few kinds of model analysis (typically those based on simulation, such as <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a> or <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#fau'>fast adaptive simulation</a>, it is also permissable to use integer variables with unbounded ranges, denoted as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : <span class=\"prismkeyword\">int</span>;<br/>\n<span class=\"prismident\">y</span> : <span class=\"prismkeyword\">int</span> <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">3</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Where the state space of the model remains finite, despite the presence of such unbounded variables, you can use the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>explicit engine</a> to build and analyse the model.\n</p>\n<div class='vspace'></div><h3>Identifiers</h3>\n<p>The names given to modules and variables are referred to as <em>identifiers</em>.\nIdentifiers can be made up of letters, digits and the underscore character, but cannot begin with a digit,\ni.e. they must satisfy the regular expression [A-Za-z_][A-Za-z0-9_]*, and are case-sensitive.\nFurthermore, identifiers cannot be any of the following, which are all reserved keywords in PRISM:\n<code><strong>A</strong></code>,\n<code><strong>bool</strong></code>,\n<code><strong>clock</strong></code>,\n<code><strong>const</strong></code>,\n<code><strong>ctmc</strong></code>,\n<code><strong>C</strong></code>,\n<code><strong>double</strong></code>,\n<code><strong>dtmc</strong></code>,\n<code><strong>E</strong></code>,\n<code><strong>endinit</strong></code>,\n<code><strong>endinvariant</strong></code>,\n<code><strong>endmodule</strong></code>,\n<code><strong>endobservables</strong></code>,\n<code><strong>endrewards</strong></code>,\n<code><strong>endsystem</strong></code>,\n<code><strong>false</strong></code>,\n<code><strong>formula</strong></code>,\n<code><strong>filter</strong></code>,\n<code><strong>func</strong></code>,\n<code><strong>F</strong></code>,\n<code><strong>global</strong></code>,\n<code><strong>G</strong></code>,\n<code><strong>init</strong></code>,\n<code><strong>invariant</strong></code>,\n<code><strong>I</strong></code>,\n<code><strong>int</strong></code>,\n<code><strong>label</strong></code>,\n<code><strong>max</strong></code>,\n<code><strong>mdp</strong></code>,\n<code><strong>min</strong></code>,\n<code><strong>module</strong></code>,\n<code><strong>X</strong></code>,\n<code><strong>nondeterministic</strong></code>,\n<code><strong>observable</strong></code>,\n<code><strong>observables</strong></code>,\n<code><strong>of</strong></code>,\n<code><strong>Pmax</strong></code>,\n<code><strong>Pmin</strong></code>,\n<code><strong>P</strong></code>,\n<code><strong>pomdp</strong></code>,\n<code><strong>popta</strong></code>,\n<code><strong>probabilistic</strong></code>,\n<code><strong>prob</strong></code>,\n<code><strong>pta</strong></code>,\n<code><strong>rate</strong></code>,\n<code><strong>rewards</strong></code>,\n<code><strong>Rmax</strong></code>,\n<code><strong>Rmin</strong></code>,\n<code><strong>R</strong></code>,\n<code><strong>S</strong></code>,\n<code><strong>stochastic</strong></code>,\n<code><strong>system</strong></code>,\n<code><strong>true</strong></code>,\n<code><strong>U</strong></code>,\n<code><strong>W</strong></code>.\n</p><hr />\n<h1>Commands</h1>\n<p>The behaviour of each module is described by <em>commands</em>,\ncomprising a <em>guard</em> and one or more <em>updates</em>.\nThe first command of module <code>M1</code> in our <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>example</a> is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The guard <code>x=0</code> indicates that this describes the behaviour of the module when the variable <code>x</code> has value 0.\nThe updates <code>(x'=0)</code> and <code>(x'=1)</code> and their associated probabilities state that the value of <code>x</code> will\nremain at 0 with probability 0.8 and change to 1 with probability 0.2.\nNote that the inclusion of updates in parentheses, e.g. <code>(x'=1)</code>, is essential.\nWhile older versions of PRISM did not report the absence of parentheses as an error, newer versions do.\nNote also that PRISM will complain if the probabilities on the right hand side of a command do not sum to one.\n</p>\n<p class='vspace'>The second command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>illustrates that guards can contain constraints on any variable, not just the ones in that module,\ni.e. the behaviour of one module can depend on the state of another.\nUpdates, however, can only specify values for variables belonging to the module.\nIn general a module can <em>read</em> the variables of any other module, but only <em>write</em> to its own.\nWhen a command comprises a single update with probability 1, the <code>1.0:</code> can be omitted,\nas is done in the example above.\n</p>\n<p class='vspace'>If a module has more than one variable, updates describe the new value for each of them.\nFor example, if it had two variables <code>x1</code> and <code>x2</code>, a possible command would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&lt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>+<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that elements of the updates are concatenated with <code>&amp;</code> and that each element must be bracketed individually.\nIf an update does not give a new value for a local variable, it is assumed not to change.\nAs a special case, the keyword <code><strong>true</strong></code> can be used to denote an update where no variable's value changes, i.e. the following are all equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Finally, it is important to remember that the expressions on the right hand side of each update refer to the state of the model <em>before</em> the update occurs. So, for example, this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>=<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x1</span>) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>updates variable <code>x2</code> to 0, not 2.\n</p>\n<div class='vspace'></div><hr />\n<h1>Parallel Composition</h1>\n<p>The probabilistic model corresponding to a PRISM language description is constructed as the <em>parallel composition</em> of its modules. In every state of the model, there is a set of commands (belonging to any of the modules) which are enabled, i.e. whose guards are satisfied in that state. The choice between which command is performed (i.e. the <em>scheduling</em>) depends on the model type.\n</p>\n<p class='vspace'>For an MDP, as in <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>, the choice is <em>nondeterministic</em>. By way of example, consider state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>). There are two commands enabled, one from each module:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In state <code>(0,0)</code> of the MDP, there would be a nondeterministic choice between these two probability distributions:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.2:(1,0)</code> (module <code>M1</code> moves)\n</li><li><code>0.8:(0,0) + 0.2:(0,1)</code> (module <code>M2</code> moves)\n</li></ul><p class='vspace'>For a DTMC, the choice is <em>probabilistic</em>: each enabled command is selected with equal probability.\nIf <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a> was a DTMC, then in state <code>(0,0)</code> of the model\nthe following probability distribution would result:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.1:(1,0) + 0.1:(0,1)</code>\n</li></ul><p class='vspace'>For a <a class='wikilink' href='../ThePRISMLanguage/CTMCs.html'>CTMC</a>, as will be discussed shortly,\nthe choice is modelled as a \"race\" between transitions.\n</p>\n<p class='vspace'>See the later sections on \"<a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>Synchronisation</a>\" and \"<a class='wikilink' href='../ThePRISMLanguage/ProcessAlgebraOperators.html'>Process Algebra Operators</a>\" for other topics related to parallel composition.\n</p><hr />\n<h1>Local Nondeterminism</h1>\n<p>PRISM models that support nondeterminism, such as are MDPs, can also exhibit <em>local nondeterminism</em>,\nwhich allows the modules themselves to make nondeterministic choices.\nIn <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>, we can make the probabilistic choice in the first state of module <code>M1</code> nondeterministic by replacing the command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock24'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=24' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>with the commands:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock25'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=25' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Assuming we do the same for module <code>M2</code>, in state <code>(0,0)</code> of the MDP\nthere will be a nondeterministic choice between the three (trivial) probability distributions listed below. (There are three, not four, distributions because two possibilities result in identical behaviour: staying with probability 1 in the state state.)\n</p>\n<div class='vspace'></div><ul><li><code>1.0:(0,0)</code>\n</li><li><code>1.0:(1,0)</code>\n</li><li><code>1.0:(0,1)</code>\n</li></ul><p class='vspace'>More generally, local nondeterminism can also arise when the guards of two commands overlap only partially, rather than completely as in the example above.\n</p>\n<p class='vspace'>PRISM also permits local nondeterminism in models which are DTMCs,\nalthough the nondeterministic choice is randomised when the parallel composition of the modules occurs.\nSince the appearance of nondeterminism in a DTMC is often the result of\na user error in the model specification, PRISM displays a warning when local nondeterminism is detected in a DTMC.\nOverlapping guards in <a class='wikilink' href='../ThePRISMLanguage/CTMCs.html'>CTMCs</a> are not treated as nondeterministic choices.\n</p>\n<div class='vspace'></div><hr />\n<h1>CTMCs</h1>\n<p class='vspace'>Specifying the behaviour of a continuous-time Markov chain (CTMC)\nis done in similar fashion to a DTMC or an MDP, as discussed so far.\nThe main difference is that updates in commands are\nlabelled with (positive-valued) <em>rates</em>, rather than probabilities.\nThe notation used in commands, however, to associate rates to transitions is identical to\nthe one used to assign probabilities:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock26'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">rate_1</span>:<span class=\"prismident\">update_1</span> + <span class=\"prismident\">rate_2</span>:<span class=\"prismident\">update_2</span> + ... <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=26' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In a CTMC, when multiple possible transitions are available in a state, a <em>race condition</em> occurs\n(see e.g. [<a class='wikilink' href='References.html#KNP07a'>KNP07a</a>] for more details).\nIn terms of PRISM commands, this can arise in several ways.\nFirstly, within in a module, multiple transitions can be specified either as several different updates in a command, or as multiple commands with overlapping guards. The following, for example. are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock27'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=27' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock28'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=28' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Furthermore, parallel composition between modules in a CTMC is modelled as a race condition,\nrather as a nondeterministic choice, like for <a class='wikilink' href='../ThePRISMLanguage/ParallelComposition.html'>MDPs</a>.\n</p><hr />\n<h1>Example 2</h1>\n<p>We now introduce a second example: a CTMC that models an <em>N</em>-place queue of jobs and\na server which removes jobs from the queue and processes them.\nThe PRISM code is as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock29'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 2</span><br/>\n<span class=\"prismcomment\">// N-place queue + server</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span> = <span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mu</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">lambda</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">2</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">gamma</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">3</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">queue</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">q</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">N</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>&lt;<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>+<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>=<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">server</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">s</span>=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismident\">gamma</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">0</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=29' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 2</strong>\n</p>\n<p class='vspace'>This example also introduces a number of other PRISM language concepts,\nincluding <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a>, action labels and <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation</a>.\nThese are described in the following sections.\n</p><hr />\n<h1>Constants</h1>\n<p>PRISM supports the use of <em>constants</em>, as seen in <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>.\nConstants can be integers, doubles or Booleans\nand can be defined using literal values or as constant expressions (including in terms of each other) using the <code><strong>const</strong></code>\nkeyword. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock30'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">radius</span> = <span class=\"prismnum\">12</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">pi</span> = <span class=\"prismnum\">3.141592</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">area</span> = <span class=\"prismident\">pi</span> * <span class=\"prismident\">radius</span> * <span class=\"prismident\">radius</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">bool</span> <span class=\"prismident\">yes</span> = <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=30' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The identifiers used for their names are subject to the same rules as <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variables</a>.\n</p>\n<p class='vspace'>Constants can be used anywhere that a constant value would be expected,\nsuch as the lower or upper range of a variable (e.g. <code>N</code> in <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>),\nthe probability or rate associated with an update (<code>mu</code> in <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>),\nor anywhere in a guard or update.\nAs will be described later constants can also be left undefined\nand specified later, either to a single value or a range of values, using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'><strong>Note:</strong> For the sake of backward-compatibility, the notation used in earlier versions of PRISM\n(<code><strong>const</strong></code> for <code><strong>const int</strong></code> and <code><strong>rate</strong></code> or <code><strong>prob</strong></code> for <code><strong>const double</strong></code>) is still supported.\n</p><hr />\n<h1>Expressions</h1>\n<p>The definition of the <code>area</code> constant, in the example above, uses an <em>expression</em>.\nWe now define more precisely what types of expression are supported by PRISM.\nExpressions can contain literal values (12, 3.141592, <code><strong>true</strong></code>, <code><strong>false</strong></code>, etc.),\nidentifiers (corresponding to variables, constants, etc.) and operators from the following list:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>^</code> (power)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li></ul><p class='vspace'>All of these operators except <code>?</code> and <code>=&gt;</code> are left associative\n(i.e. they are evaluated from left to right).\nThe precedence of the operators is as found in the list above,\nmost strongly binding operators first.\nOperators on the same line (e.g. <code>+</code> and <code>-</code>) are of equal precedence.\n</p>\n<p class='vspace'>Much of the notation for expressions is hence essentially equivalent to that of C/C++ or Java.\nOne notable exception to this is that  the division operator <code>/</code> always performs floating point, not integer, division,\ni.e. the result of <code>22/7</code> is 3.142857... not 3.\nAll expressions must evaluate correctly in terms of type (integer, double or Boolean).\n</p>\n<p class='vspace'><strong>Built-in Functions</strong>\n</p>\n<p class='vspace'>Expressions can make use of several built-in functions:\n</p>\n<div class='vspace'></div><ul><li><code>min(...)</code> and <code>max(...)</code>, which select the minimum and maximum value, respectively, of two or more numbers\n</li><li><code>floor(x)</code> and <code>ceil(x)</code>, which round <code>x</code> down and up, respectively, to the nearest integer\n</li><li><code>round(x)</code>, which rounds <code>x</code> to the nearest integer (note, in a tie-break, we always round <em>up</em>, e.g. <code>round(-1.5)</code> gives <code>-1</code> not <code>-2</code>)\n</li><li><code>pow(x,y)</code> which computes <code>x</code> to the power of <code>y</code> (same as <code>x^y</code>)\n</li><li><code>mod(i,n)</code> for integer modulo operations\n</li><li><code>log(x,b)</code>, which computes the logarithm of <code>x</code> to base <code>b</code>\n</li></ul><p class='vspace'>Examples of their usage are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock31'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">min</span>(<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>, <span class=\"prismident\">x_max</span>)<br/>\n<span class=\"prismkeyword\">max</span>(<span class=\"prismident\">a</span>,<span class=\"prismident\">b</span>,<span class=\"prismident\">c</span>)<br/>\n<span class=\"prismident\">floor</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">ceil</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">round</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">2</span>, <span class=\"prismnum\">8</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">9.0</span>, <span class=\"prismnum\">0.5</span>)<br/>\n<span class=\"prismident\">mod</span>(<span class=\"prismnum\">1977</span>, <span class=\"prismnum\">100</span>)<br/>\n<span class=\"prismident\">log</span>(<span class=\"prismnum\">123</span>, <span class=\"prismnum\">2.71828183</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=31' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For compatibility with older versions of PRISM, all functions can also be expressed via the <code><strong>func</strong></code> keyword, e.g. <code>func(floor, 13.5)</code>.\n</p>\n<p class='vspace'><strong>Use of Expressions</strong>\n</p>\n<p class='vspace'>Expressions can be used in a wide range of places in a PRISM language description, e.g.:\n</p>\n<div class='vspace'></div><ul><li>constant definitions\n</li><li>lower/upper bounds and initial values for variables\n</li><li>guards\n</li><li>probabilities/rates\n</li><li>updates\n</li></ul><p class='vspace'>This allows, for example, the probability in a command to be dependent on the current state:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock32'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] (<span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span>) -&gt; <span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">max</span>(<span class=\"prismnum\">1</span>,<span class=\"prismident\">x</span>-<span class=\"prismnum\">1</span>)) + <span class=\"prismnum\">1</span>-<span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">min</span>(<span class=\"prismnum\">10</span>,<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>)) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=32' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Synchronisation</h1>\n<p>Another feature of PRISM introduced in <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a> is <em>synchronisation</em>.\nIn the style of many process algebras, we allow commands to be labelled with <em>actions</em>.\nThese are placed inside the square brackets which mark the start of the command,\nfor example <code>serve</code> in this command from <a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock33'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=33' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These actions can be used to force two or more modules to make transitions simultaneously\n(i.e. to <em>synchronise</em>).\nFor example, in state <code>(3,0)</code> (i.e.  <code>q=3</code> and <code>s=0</code>),\nthe composed model can move to state <code>(2,1)</code>,\nsynchronising over the <code>serve</code> action.\nThe rate of this transition is equal to the product of the two individual rates\n(in this case, <code>lambda * 1 = lambda</code>).\nThe product of two rates does not always meaningfully represent the rate of a synchronised transition.\nA common technique, as seen here, is to make one action <em>passive</em>, with rate 1 and one action <em>active</em>,\nwhich actually defines the rate for the synchronised transition.\nBy default, all modules are combined using the standard CSP parallel composition\n(i.e. modules synchronise over all their common actions).\n</p><hr />\n<h1>Module Renaming</h1>\n<p>PRISM also supports <em>module renaming</em>, which allows duplication of modules.\nIn <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>, module <code>M2</code> is identical to module <code>M1</code> so we can in fact replace its entire definition with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock34'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span> = <span class=\"prismident\">M1</span> [ <span class=\"prismident\">x</span>=<span class=\"prismident\">y</span>, <span class=\"prismident\">y</span>=<span class=\"prismident\">x</span> ] <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=34' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>All of the variables in the module being renamed (in this case, just <code>x</code>) <em>must</em> be renamed to new, unused names. Optionally, it is also possible to rename other aspects of the module definition. In fact, the renaming is done at a textual level, so any identifiers (including <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>action labels</a>, <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a> and <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>functions</a>) used in the module definition can be changed in this way.\n</p>\n<p class='vspace'><strong>Note:</strong> Care should be taken when renaming modules that make use of <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>formulas</a>.\n</p><hr />\n<h1>Multiple Initial States</h1>\n<p>Typically, a <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variable</a> declaration\nspecifies the initial value for that variable.\nThe <em>initial state</em> for the model is then defined by the initial value for all variables.\nIt is possible, however, to specify that a model has <em>multiple</em> initial states.\nThis is done using the <code><strong>init</strong>...<strong>endinit</strong></code> construct,\nwhich can be placed anywhere in the file except within a module definition,\nand removing any initial values from variable declarations.\nBetween the <code><strong>init</strong></code> and <code><strong>endinit</strong></code> keywords, there should be a\npredicate over all the variables of the model.\nAny state which satisfies this predicate is an initial state.\n</p>\n<p class='vspace'>Consider again <a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>.\nAs it stands, there is a single initial state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>).\nIf we remove the <code><strong>init</strong> 0</code> part of both variable declarations\nand add the following to the end of the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock35'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=35' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>there will be three initial states: <code>(0,0)</code>, <code>(0,1)</code> and <code>(0,2)</code>.\nSimilarly, we could instead add:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock36'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>+<span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=36' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>in which case there would be two initial states: <code>(0,1)</code> and <code>(1,0)</code>.\n</p><hr />\n<h1>Global Variables</h1>\n<p>In addition to the local variables belonging to each module, a PRISM model can also include <em>global variables</em>,\nwhich can be written to, as well as read, by all modules.\nLike local variables, these can be integers or Booleans.\nGlobal variables are declared in identical fashion to a module's local variables,\nexcept that the declaration must not be inside the definition of any module.\nSome example declarations are as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock37'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">global</span> <span class=\"prismident\">g</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismnum\">10</span>];<br/>\n<span class=\"prismkeyword\">global</span> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=37' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A global variable can be modified by any module and provides another way for modules to interact.\nAn important restriction on the use of global variables is the fact that commands which synchronise with other modules\n(i.e. those with an action label attached; see the section \"<a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>Synchronisation</a>\") cannot modify global variables.\nPRISM will detect this and report an error.\n</p><hr />\n<h1>Formulas And Labels</h1>\n<p>PRISM models can include <em>formulas</em> which are used to avoid duplication of code.\nA formula comprises a name (an identifier) and an <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a>.\nThe formula name can then be used as shorthand for the expression anywhere an expression might usually be accepted.\nA formula is defined as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock38'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">formula</span> <span class=\"prismident\">num_tokens</span> = <span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=38' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It can then be used anywhere within that file, as for example in this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock39'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">num_tokens</span>=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=39' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The effect is exactly as if the following had been typed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock40'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; (<span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>)=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=40' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Formulas defined in a model can also be used when specifying its properties.\n</p>\n<div class='vspace'></div><h3>Formulas and renaming</h3>\n<p>During parsing of the model, expansion of formulas is done before module renaming so, if a module which uses formulas is renamed to another module, it is the contents of the formula which will be renamed, not the formula itself.\n</p>\n<div class='vspace'></div><h3>Labels</h3>\n<p>PRISM models can also contain <em>labels</em>. These are a way of identifying sets of states that are of particular interest. Labels can only be used when specifying <a class='wikilink' href='../PropertySpecification/Main.html'>properties</a> but, for convenience, can be defined in model files as well as property files. \n</p>\n<p class='vspace'>Labels differ from formulas in two other ways: firstly, they must be of Boolean type;\nsecondly, they are written using quotation marks (<code>\"...\"</code>), as illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock41'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=41' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Costs And Rewards </h1>\n<p>PRISM supports the specification and analysis of\nproperties based on <em>costs</em> and <em>rewards</em>.\nThis means that it can be used to reason,\nnot just about the probability that a model behaves in a certain fashion,\nbut about a wider range of quantitative measures relating to model behaviour.\nFor example, PRISM can be used to compute properties such as\n\"expected time\", \"expected number of lost messages\" or \"expected power consumption\".\nThe implementation of cost- and reward-based techniques in the tool is only partially completed and is still ongoing.\nIf you have questions, comments or feature-requests relating to this functionality,\nplease feel free to contact the PRISM team about this.\n</p>\n<p class='vspace'>The basic idea is that probabilistic models (of all types) developed in PRISM\ncan be augmented with costs or rewards: real values associated with certain states or transitions of the model.\nIn fact, since there is no practical distinction between costs and rewards\n(except that costs are generally perceived to be \"bad\" and rewards to be \"good\"),\nPRISM only supports rewards.\nThe user is, however, free to interpret the values however they choose.\n</p>\n<p class='vspace'>In this section, we describe how models described in the PRISM language\ncan be augmented with rewards.\nLater, we will discuss how to express properties that relate to these rewards.\nRewards are associated with models using <code><strong>rewards</strong> ... <strong>endrewards</strong></code> constructs,\nwhich can appear anywhere in a model file except within a module definition.\nThese constructs contains one or more <em>reward items</em>.\nConsider the following simple example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock42'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r1</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=42' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This defines a reward structure with name <code>r1</code> (the name is optional)\nwhich assigns a reward of 1 to every state of the model.\nIt comprises a single reward item, the left part of which (<code><strong>true</strong></code>) is a guard\nand the right part of which (<code>1</code>) is a reward.\nStates of the model which satisfy the predicate in the guard are assigned the corresponding reward.\nMore generally, state rewards can be specified using multiple reward items,\neach of the form <code>guard : reward;</code>,\nwhere <code>guard</code> is a predicate (over all the variables of the model)\nand <code>reward</code> is an expression (containing any variables, constants, etc. from the model).\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock43'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r2</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> : <span class=\"prismnum\">100</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&lt;<span class=\"prismnum\">10</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">10</span> : <span class=\"prismnum\">100</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=43' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 100 to states satisfying <code>x=0</code> or <code>x=10</code>\nand a reward of <code>2*x</code> to states satisfying <code>x&gt;0 &amp; x&lt;10</code>.\nNote that a single reward item can assign different rewards to different states,\ndepending on the values of model variables in each one.\nAny states which do not satisfy the guard of any reward item will have no reward assigned to them.\nFor states which satisfy multiple guards, the reward assigned to the state\nis the sum of the rewards for all the corresponding reward items.\n</p>\n<p class='vspace'>Rewards can also be assigned to transitions of a model.\nThese are specified in a similar fashion to state rewards,\nwithin the <code><strong>rewards</strong> ... <strong>endrewards</strong></code> construct.\nReward items describing transition rewards are of the form <code>[action] guard : reward;</code>,\nthe interpretation being that transitions from states which satisfy the guard <code>guard</code>\nand are labelled with the action <code>action</code> acquire the reward <code>reward</code>.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock44'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r3</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">a</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=44' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 1 to all transitions in the model with no action label,\nand rewards of <code>x</code> and <code>2*x</code> to all transitions labelled with actions <code>a</code> and <code>b</code>, respectively.\n</p>\n<p class='vspace'>As is the case for states, multiple reward items can specify rewards for a single transition,\nin which case the resulting reward is the sum of all the individual rewards.\nA model description can specify rewards for both states and transitions.\nThese are all placed together in a single <code><strong>rewards</strong>...<strong>endrewards</strong></code> construct.\n</p>\n<p class='vspace'>A PRISM model will often have multiple reward structures, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock45'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">total_time</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n<br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">num_failures</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">fail</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=45' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<h1>Real-time Models</h1>\n<p class='vspace'>So far in this section, we have mainly focused on three types of models: DTMCs, MDPs and CTMCs,\nin which all the variables making up their state are finite.\nPRISM also supports <em>real-time</em> models, in particular,\n<em>probabilistic timed automata</em> (PTAs), which extend MDPs with the ability to model real-time behaviour.\nThis is done in the style of <em>timed automata</em> [<a class='wikilink' href='References.html#AD94'>AD94</a>], by adding <em>clocks</em>,\nreal-valued variables which increase with time and can be reset. For background material on PTAs, see for example [<a class='wikilink' href='References.html#NPS13'>NPS13</a>].\nYou can also find several example PTA models included in the PRISM distribution. Look in the <code>prism-examples/ptas</code> directory.\n</p>\n<p class='vspace'>Before describing how PTA features are incorporated into the PRISM modelling language, we give a simple example. Here is a small PTA:\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/pta.png' alt='' /></div>\n<p class='vspace'>and here is a corresponding PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock46'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">pta</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : <span class=\"prismkeyword\">clock</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">invariant</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">2</span>) &amp;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">3</span>)<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">endinvariant</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">send</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismnum\">0.9</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">retry</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.95</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.05</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=46' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For modelling PTAs in PRISM, there is a new datatype, <strong><code>clock</code></strong>, used for variables that are clocks. Other types of PRISM variables can be defined in the usual way. In the example above, we use just a single integer variable <code>s</code> to represent the locations of the PTAs.\n</p>\n<p class='vspace'>In a PTA, transitions can include a <em>guard</em>, which constrains when it can occur based on the current value of clocks, and <em>resets</em>, which specify that a clock's values should be set to a new (integer) value. These are both specified in PRISM commands in the usual way: see, for example, the inclusion of <code>x&gt;=1</code> in the guard for the <code>send</code>-labelled command and the updates of the form <code>(x'=0)</code> which reset the clock <code>x</code> to 0.\n</p>\n<p class='vspace'>The other new addition is an <code>invariant</code> construct, which is used to specify an expression describing the clock <em>invariants</em> for each PRISM module. These impose restrictions on the allowable values of clock variables, depending on the values of the other non-clock variables. The <code>invariant</code> construct should appear between the variable declarations and the commands of the module. Often, clock invariants are described separately for each PTA location; hence, the invariant will often take the form of a conjunction of implications, as in the example model above, but more general expressions are also permitted. In the example, the clock <code>x</code> must satisfy <code>x&lt;=2</code> or <code>x&lt;=3</code> when local variables <code>s</code> is 0 or 2, respectively. If <code>s</code> is 1, there is no restriction (since the invariant is effectively <code>true</code> in this case).\n</p>\n<p class='vspace'>Expressions that include reference to clocks, whether in guards or invariants, must satisfy certain conditions to facilitate model checking. In particular, references to clocks must appear as conjunctions of <em>simple clock constraints</em>, i.e. conjunctions of expressions of the form <code>x~c</code> or <code>x~y</code> where <code>x</code> and <code>y</code> are clocks, <code>c</code> is an integer-valued expression and <code>~</code> is one of <code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code>, <code>=</code>).\n</p>\n<p class='vspace'>There are also some additional restrictions imposed on PTA models that are dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is in use.\n</p>\n<p class='vspace'>For the <strong>stochastic games</strong> and <strong>backwards reachability</strong> engines:\n</p>\n<div class='vspace'></div><ul><li>The model must also have a single initial state (i.e. the <code>init...endinit</code> construct is not permitted).\n</li></ul><p class='vspace'>For the <strong>digital clocks</strong> engine:\n</p>\n<div class='vspace'></div><ul><li>Clock constraints cannot use strict comparison operators, e.g. <code>x&lt;=5</code> is allowed, but <code>x&lt;5</code> is not.\n<div class='vspace'></div></li><li>Diagonal clock constraints are not allowed, i.e. those containing references to two clocks, such as <code>x&lt;=y</code>.\n</li></ul><p class='vspace'>Finally, PRISM makes several assumptions about PTAs, regardless of the engine used.\n</p>\n<div class='vspace'></div><ul><li>Firstly PTAs should not exhibit <em>timelocks</em>, i.e. the possibility of reaching a state where no transitions are possible and time cannot elapse beyond a certain point (due to invariant conditions). PRISM checks for timelocks and reports an error if one is found.\n<div class='vspace'></div></li><li>Secondly, PTAs should be <em>well-formed</em> and <em>non-zeno</em> (see e.g. [<a class='wikilink' href='References.html#KNSW07'>KNSW07</a>] for details). Currently, PRISM does not check automatically that these assumptions are satisfied.\n</li></ul><div class='vspace'></div><hr />\n<h1>Partially Observable Models</h1>\n<p>PRISM supports analysis of <em>partially observable</em> probabilistic models,\nmost notably partially observable Markov decision processes (POMDPs),\nbut also partially observable probabilistic timed automata (POPTAs).\nPOMDPs are a variant of MDPs in which the strategy/policy\nwhich resolves nondeterministic choices in the model is unable to\nsee the precise state of the model, but instead just <em>observations</em> of it.\nFor background material on POMDPs and POPTAs, see for example [<a class='wikilink' href='References.html#NPZ17'>NPZ17</a>].\nYou can also find several example models included in the PRISM distribution.\nLook in the <code>prism-examples/pomdps</code> and <code>prism-examples/poptas</code> directories.\n</p>\n<p class='vspace'>PRISM currently supports state-based observations:\nthis means that, upon entering a new POMDP state,\nthe observation is determined by that state.\nIn the same way that a model state comprises the values or one or more variables,\nan observation comprises one or more <em>observables</em>.\nThere are several way to define these observables.\nThe simplest is to specify a subset of the model's variables\nthat are designated as being observable. The rest are unobservable.\n</p>\n<p class='vspace'>For example, in a POMDP with 3 variables, <code>s</code>, <code>l</code> and <code>h</code>, the following:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock47'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">observables</span> <span class=\"prismident\">s</span>, <span class=\"prismident\">l</span> <span class=\"prismkeyword\">endobservables</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=47' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>specifies that <code>s</code> and <code>l</code> are observable and <code>h</code> is not.\n</p>\n<p class='vspace'>Alternatively, observables can be specified as arbitrary expressions over variables.\nFor example, assuming the same variables <code>s</code>, <code>l</code> and <code>h</code>, this specification:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock48'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">s</span>\" = <span class=\"prismident\">s</span>;<br/>\n<span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">pos</span>\" = <span class=\"prismident\">l</span>&gt;<span class=\"prismnum\">0</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=48' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>defines 2 observables. The first is, as above, the variable <code>s</code>.\nThe second, named <code>\"pos\"</code>, determines if variable <code>l</code> is positive.\nOther than this, the values of <code>l</code> and <code>h</code> are unobservable.\nThe named observables can then be used in properties\nin the same way that <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> can.\n</p>\n<p class='vspace'>The above two styles of definition can also be mixed\nto specify a combined set of observables.\n</p>\n<p class='vspace'>POPTAs (partially observable PTAs) combine the features of both PTAs and POMDPs.\nThey are are currently analysed using the digital clocks engine,\nso inherit the <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>restrictions for that engine</a>.\nFurthermore, for a POPTA, all clock variables must be observable.\n</p><hr />\n<h1>Uncertain models</h1>\n<p>PRISM has support for <em>uncertain</em> models, in which there is epistemic uncertainty regarding some quantitative aspects of the probabilistic models being verified. In particular, it currently supports <em>interval MDPs</em> (IMDPs) and <em>interval DTMCs</em> (IDTMCs), which are MDPs or DTMCs in which transition probabilities can be specified as intervals, indicating that the exact probability is not precisely known. This can be useful, for example, when the transition probabilities have been estimated from data.\n</p>\n<p class='vspace'>Currently, this is achieved by simply replacing the probabilities attached to updates in commands with intervals, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock49'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismnum\">0.8</span>,<span class=\"prismnum\">0.9</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.1</span>,<span class=\"prismnum\">0.2</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=49' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As usual, the probability thresholds can be expressions involving state variables or constants, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock50'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismident\">p</span>,<span class=\"prismident\">p</span>+<span class=\"prismnum\">0.1</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.9</span>-<span class=\"prismident\">p</span>,<span class=\"prismnum\">1</span>-<span class=\"prismident\">p</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=50' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When two commands in different modules <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronise</a> and specify the probabilities for updates to variables as intervals, these are considered to be independent, i.e., the probability of each combined transition is taken to be the product of the two component intervals.\n</p>\n<p class='vspace'>See the <a class='wikilink' href='../PropertySpecification/UncertainModels.html'>property specification</a> section for details of how these models are analysed.\n</p><hr />\n<h1>Process Algebra Operators</h1>\n<p>To make the concept of synchronisation described above more powerful,\nPRISM allows you to define precisely the way in which the set of modules are composed in parallel.\nThis is specified using the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct,\nplaced at the end of the model description, which should contain a process-algebraic expression.\nThis expression should feature each module exactly once, and can use the following (CSP-based) operators:\n</p>\n<div class='vspace'></div><ul><li><code>M1 || M2</code> : alphabetised parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising on only actions appearing in both <code>M1</code> and <code>M2</code>)\n<div class='vspace'></div></li><li><code>M1 ||| M2</code> : asynchronous parallel composition of <code>M1</code> and <code>M2</code> (fully interleaved, no synchronisation)\n<div class='vspace'></div></li><li><code>M1 |[a,b,...]| M2</code> : restricted parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising only on actions from the set {<code>a</code>, <code>b</code>,...})\n<div class='vspace'></div></li><li><code>M / {a,b,...</code>} : hiding of actions {<code>a</code>, <code>b</code>, ...} in module <code>M</code>\n<div class='vspace'></div></li><li><code>M {a&lt;-b,c&lt;-d,...</code>} : renaming of actions <code>a</code> to <code>b</code>, <code>c</code> to <code>d</code>, etc. in module <code>M</code>.\n</li></ul><p class='vspace'>The first two types of parallel composition (<code>||</code> and <code>|||</code>) are associative and can be applied to more than two modules at once.\nWhen evaluating the expression, the hiding and renaming operators bind more tightly than the three parallel composition operators.\nNo other rules of precedence are defined and parentheses should be used to specify the order in which modules are composed.\n</p>\n<p class='vspace'>Some examples of expressions which could be included in the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct are as follows:\n</p>\n<div class='vspace'></div><ul><li><code>(station1 ||| station2 ||| station3) |[serve]| server</code>\n</li><li><code>((P1 |[a]| P2) / {a}) || Q</code>\n</li><li><code>((P1 |[a]| P2) {a&lt;-b}) |[b]| Q</code>\n</li></ul><p class='vspace'>When no parallel composition is specified by the user,\nPRISM implicitly assumes an expression of the form <code>M1 || M2 || ...</code> containing all of the modules in the model.\nFor a more formal definition of the process algebra operators described above, check the semantics of the PRISM language, available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site.\n</p>\n<p class='vspace'>PRISM is also able to <a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>import</a> model descriptions written in (a subset of) the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='References.html#Hil96'>Hil96</a>].\n</p><hr />\n<h1>PRISM Model Files</h1>\n<p>Files containing model descriptions written in the PRISM language\ncan contain any amount of white space (spaces, tabs, new lines, etc.),\nall of which is ignored when the file is parsed by the tool.\nComments can also be used included in files in the style of the C programming language,\nby preceding them with the characters <code>//</code>.\nThis is illustrated by the PRISM language examples from earlier in this section.\n</p>\n<p class='vspace'>We recommend that the <code>.prism</code> extension is used for PRISM model files.\nHistorically (when the tool supported fewer types of model),\ndifferent extensions were often used for each model type:\n<code>.nm</code> for MDPs or PTAs, <code>.pm</code> for DTMCs and <code>.sm</code> for CTMCs.\n</p>\n<p class='vspace'><br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Property Specification</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>In order to analyse a probabilistic model which has been specified and constructed in PRISM,\nit is necessary to identify one or more <em>properties</em> of the model\nwhich can be evaluated by the tool.\nPRISM's <em>property specification language</em> subsumes several well-known probabilistic temporal logics, including PCTL, CSL, probabilistic LTL and PCTL*.\nPCTL is used for specifying properties of discrete-time models such as DTMCs or PTAs,\nand also real-time models such as PTAs; CSL is an extension of PCTL for CTMCs;\nLTL and PCTL* can be used to specify properties of \ndiscrete-time models (or untimed properties of CTMCs).\nPRISM also supports most of the (non-probabilistic) temporal logic CTL.\n</p>\n<p class='vspace'>In fact, PRISM also supports numerous additional customisations and extensions of these two logics.\nFull details of the property specifications permitted in PRISM are provided in the following sections. The presentation given here is relatively informal. For the precise syntax and semantics of the various logics, see [<a class='wikilink' href='References.html#HJ94'>HJ94</a>],[<a class='wikilink' href='References.html#BdA95'>BdA95</a>] for PCTL, [<a class='wikilink' href='References.html#ASSB96'>ASSB96</a>],[<a class='wikilink' href='References.html#BKH99'>BKH99</a>] for CSL and, for example, [<a class='wikilink' href='References.html#Bai98'>Bai98</a>] for LTL and PCTL*. You can also find various pointers to useful papers in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>Before discussing property specifications in more detail,\nit is perhaps instructive to first illustrate some typical examples of properties which PRISM can handle.\nThe following are a selection of such properties.\nIn each case, we give both the PRISM syntax and a natural language translation:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock51'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=51' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the algorithm eventually terminates successfully with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock52'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> \"<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=52' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that more than 5 errors occur within the first 100 time units is less than 0.1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock53'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismident\">num_sensors</span> &lt; <span class=\"prismident\">min_sensors</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=53' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"in the long-run, the probability that an inadequate number of sensors are operational is less than 0.01\"\n</p>\n<p class='vspace'>Note that the above properties are all assertions,\ni.e. ones to which we would expect a \"yes\" or \"no\" answer.\nThis is because all references to probabilities are associated with an upper or lower bound\nwhich can be checked to be either true or false.\nIn PRISM, we can also directly specify properties which evaluate to a numerical value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock54'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ !<span class=\"prismident\">proc2_terminate</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">proc1_terminate</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=54' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that process 1 terminates before process 2 does\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock55'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">messages_lost</span> &gt; <span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=55' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the maximum probability that more than 10 messages have been lost by time <code>T</code>\" (for an MDP/PTA)\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock56'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=56' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the long-run probability that the queue is more than 75% full\"\n</p>\n<p class='vspace'>Furthermore, PRISM makes it easy to combine such properties into more complex expressions,\ncompute their values for a range of parameters\nand plot graphs of the results using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\nThis is often a very useful way of identifying interesting\npatterns or trends in the behaviour of a system.\nSee the <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a> section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a> for many examples of this kind of analysis.\n</p><hr />\n<h1>Identifying A Set Of States</h1>\n<p>One of the most fundamental tasks when specifying properties of a model\nis to identify particular sets or classes of states of the model.\nFor example, to verify a property such as\n\"the algorithm eventually terminates successfully with probability 1\",\nit is first necessary to identify the states of the model\nwhich correspond to situations where \"the algorithm has terminated successfully\".\nIn terms of the way temporal logics are usually presented,\nthese correspond to <em>atomic propositions</em>.\n</p>\n<p class='vspace'>In PRISM, this is achieved simply by writing an <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a> in the PRISM language which evaluates to a Boolean value. This expression will typically contain references to variables (and constants) from the model to which it relates. The set of states corresponding to this expression is those for which it evaluates to <code>true</code>. We say that the expression is \"satisfied\" in these states.\n</p>\n<p class='vspace'>For example, in the property given above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock57'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=57' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>the expression <code>num_errors &gt; 5</code> is used to identify states of the model where more than 5 errors have occurred.\n</p>\n<p class='vspace'>It is also common to use <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> to identify states in this way, like <code>\"terminate\"</code> in the example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock58'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=58' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Properties can refer to <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> either from the model to which the property relates, or included in the same <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html'>properties file</a>.\n</p><hr />\n<h1>The P Operator</h1>\n<p>One of the most important operators in the PRISM property specification language is the <code><strong>P</strong></code> operator, which is used to reason about the probability of an event's occurrence. This operator was originally proposed in the logic PCTL but also features in the other logics supported by PRISM, such as CSL. The <code><strong>P</strong></code> operator is applicable to all types of models supported by PRISM.\n</p>\n<p class='vspace'>Informally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock59'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=59' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a model if\n\"the probability that path property <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code>\".\nA typical example of a bound would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock60'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=60' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em> is greater than 0.98\". More precisely, <code>bound</code> can be any of <code>&gt;=p</code>, <code>&gt;p</code>, <code>&lt;=p</code> or <code>&lt;p</code>,\nwhere <code>p</code> is a PRISM language expression evaluating to a double in the range [0,1].\n</p>\n<p class='vspace'>The types of path property supported by PRISM and their semantics will be discussed shortly.\n</p>\n<div class='vspace'></div><h3>Nondeterminism</h3>\n<p>For models that can exhibit nondeterministic behaviour, such as MDPs or PTAs, some additional clarifications are necessary. Whereas for fully probabilistic models such as DTMCs and CTMCs, probability measures over paths are well defined (see e.g. [<a class='wikilink' href='References.html#KSK76'>KSK76</a>] and [<a class='wikilink' href='References.html#BKH99'>BKH99</a>], respectively), for nondeterministic models a probability measure can only be feasibly defined once all nondeterminism has been removed.\n</p>\n<p class='vspace'>Hence, the actual meaning of the property <code>P bound [ pathprop ]</code> in these cases is: \n\"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code> <em>for all possible resolutions of nondeterminism</em>\".\nThis means that, properties using the <code><strong>P</strong></code> operator then effectively reason about the\n<em>minimum</em> or <em>maximum</em> probability, over all possible resolutions of nondeterminism,\nthat a certain type of behaviour is observed.\nThis depends on the bound attached to the <code><strong>P</strong></code> operator:\na lower bound (<code>&gt;</code> or <code>&gt;=</code>) relates to minimum probabilities\nand an upper bound (<code>&lt;</code> or <code>&lt;=</code>) to maximum probabilities.\n</p>\n<div class='vspace'></div><h3>Quantitative properties</h3>\n<p>It is also very often useful to take a <em>quantitative</em> approach to probabilistic model checking, computing the actual probability that some behaviour of a model is observed,\nrather than just verifying whether or not the probability is above or below a given bound.\nHence, PRISM allows the <code><strong>P</strong></code> operator to take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock61'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=61' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These properties return a numerical rather than a Boolean value.\nThe <a class='wikilink' href='../PropertySpecification/TheSOperator.html'>S</a> and <a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>R</a> operators, discussed later, can also be used in this way.\n</p>\n<p class='vspace'>As mentioned above, for nondeterministic models (MDPs or PTAs), either minimum or maximum probability values can be computed. Therefore, in this case, we have two possible types of property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock62'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=62' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which return the minimum and maximum probabilities, respectively.\n</p>\n<p class='vspace'>It is also possible to specify to which state the probability returned by a quantitative property refers. This is covered in the later section on <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\n</p>\n<div class='vspace'></div><h3>Path properties</h3>\n<p>PRISM supports a wide range of path properties that can be used with the <code><strong>P</strong></code> operator.\nA path property is a formula that evaluates to either true or false for a single path in a model.\nHere, we review some of the simpler properties that feature a single <em>temporal operator</em>,\nas used for example in the logics PCTL and CSL. Later, we briefly describe how PRISM also supports more complex LTL-style path properties.\n</p>\n<p class='vspace'>The basic different types of path property that can be used inside the <code><strong>P</strong></code> operator are:\n</p>\n<div class='vspace'></div><ul><li><code><strong>X</strong></code> : \"ne<strong>x</strong>t\"\n</li><li><code><strong>U</strong></code> : \"<strong>u</strong>ntil\"\n</li><li><code><strong>F</strong></code> : \"eventually\" (sometimes called \"<strong>f</strong>uture\")\n</li><li><code><strong>G</strong></code> : \"always\" (sometimes called \"<strong>g</strong>lobally\")\n</li><li><code><strong>W</strong></code> : \"<strong>w</strong>eak until\"\n</li><li><code><strong>R</strong></code> : \"<strong>r</strong>elease\"\n</li></ul><p class='vspace'>In the following sections, we describe each of these <em>temporal operators</em>. We then discuss the (optional) use of time bounds with these operators. Finally, we also discuss LTL-style path properties.\n</p>\n<div class='vspace'></div><h3>\"Next\" path properties</h3>\n<p>The property <code><strong>X</strong> prop</code> is true for a path if <code>prop</code> is true in its second state,\nAn example of this type of property, used inside a <code><strong>P</strong></code> operator, is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock63'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">X</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=63' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of the expression <code>y=1</code> being true in the next state is less than 0.01\".\n</p>\n<div class='vspace'></div><h3>\"Until\" path properties</h3>\n<p>The property <code>prop1 <strong>U</strong> prop2</code> is true for a path if\n<code>prop2</code> is true in some state of the path and <code>prop1</code> is true in all preceding states.\nA simple example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock64'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=64' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually equal to 2, and that <code>z</code> remains less than 2 up until that point, is greater than 0.5\".\n</p>\n<div class='vspace'></div><h3>\"Eventually\" path properties</h3>\n<p>The property <code><strong>F</strong> prop</code> is true for a path if <code>prop</code> eventually becomes true at some point along the path. The <code><strong>F</strong></code> operator is in fact a special case of the <code><strong>U</strong></code> operator (you will often see <code> <strong>F</strong> prop</code> written as <code><strong>true</strong> <strong>U</strong> prop</code>). A simple example is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock65'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>&gt;<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=65' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually greater than 2is less than 0.1\".\n</p>\n<div class='vspace'></div><h3>\"Globally\" path properties</h3>\n<p>Whereas the <code><strong>F</strong></code> operator is used for \"reachability\" properties, <code><strong>G</strong></code> represents \"invariance\". The property <code><strong>G</strong> prop</code> is true of a path if <code>prop</code> remains true at all states along the path. Thus, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock66'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=66' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>states that, with probability at least 0.99, <code>z</code> never exceeds 10.\n</p>\n<div class='vspace'></div><h3>\"Weak until\" and \"release\" path properties</h3>\n<p>Like <code><strong>F</strong></code> and <code><strong>G</strong></code>, the operators <code><strong>W</strong></code> and <code><strong>R</strong></code> are derivable from other temporal operators.\n</p>\n<p class='vspace'>Weak until (<code>a <strong>W</strong> b</code>), which is equivalent to <code>(a <strong>U</strong> b) | <strong>G</strong> a</code>, requires that <code>a</code> remains true until <code>b</code> becomes true, but does not require that <code>b</code> ever does becomes true (i.e. <code>a</code> remains true forever). For example, a weak form of the until example used above is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock67'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=67' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which states that, with probability greater than 0.5, either <code>z</code> is always less than 2, or it is less than 2 until the point where <code>z</code> is 2.\n</p>\n<p class='vspace'>Release (<code>a <strong>R</strong> b</code>),  which is equivalent to <code>!(!a U !b)</code>, informally means that <code>b</code> is true until <code>a</code> becomes true, or <code>b</code> is true forever.\n</p>\n<p class='vspace'><a name='bounded' id='bounded'></a>\n</p><h3>\"Bounded\" variants of path properties</h3>\n<p>All of the temporal operators given above, with the exception of <code><strong>X</strong></code>, have \"bounded\" variants, where an additional time bound is imposed on the property being satisfied.\nThe most common case is to use an upper time bound, i.e. of the form \"<code>&lt;=t</code>\" or \"<code>&lt;t</code>\", where <code>t</code> is a PRISM expression evaluating to a constant, non-negative value.\n</p>\n<p class='vspace'>For example, a bounded until property <code>prop1 <strong>U</strong>&lt;=t prop2</code>, is satisfied along a path if <code>prop2</code> becomes true within <code>t</code> steps and <code>prop1</code> is true in all states before that point.\nA typical example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock68'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">y</span>&lt;<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=68' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of <code>y</code> first exceeding 3 within 7 time units is greater than or equal to 0.98\". Similarly:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock69'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=69' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state if \"the probability of <code>y</code> being equal to 4 within 7 time units is greater than or equal to 0.98\" and:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock70'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=70' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true if the probability of <code>y</code> staying equal to 4 for 7 time units is at least 0.98.\n</p>\n<p class='vspace'>The time bound can be an arbitrary (constant) expression,\nbut note that you may need to bracket it,\nas in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock71'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=(<span class=\"prismnum\">2</span>*<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>) <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=71' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use lower time-bounds (i.e. <code>&gt;=t</code> or <code>&gt;t</code>) and time intervals <code>[t1,t2]</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock72'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&gt;=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">20</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=72' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which refer to the probability of <code>y</code> becoming equal to 4 after 10 or more time units, and after between 10 and 20 time-units respectively.\n</p>\n<p class='vspace'>For CTMCs, the time bounds can be any (non-negative) numerical values - they are not restricted to integers, as for discrete-time models.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock73'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.25</span> [ <span class=\"prismident\">y</span>&lt;=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">6.5</span> <span class=\"prismident\">y</span>&gt;<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=73' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means that the probability of <code>y</code> being greater than 1 within 6.5 time-units (and remaining less than or equal to 1 at all preceding time-points) is at least 0.25.\n</p>\n<div class='vspace'></div><h3>Transient probabilities</h3>\n<p>We can also use the bounded <code><strong>F</strong></code> operator to refer to a single time instant, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock74'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">10</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=74' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or, equivalently:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock75'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=75' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>both of which give the probability of <code>y</code> being 6 at time instant 10.\n</p>\n<p class='vspace'><a name='ltl' id='ltl'></a>\n</p><h3>LTL-style path properties</h3>\n<p>PRISM also supports probabilistic model checking of the temporal logic LTL (and, in fact, PCTL*). LTL provides a richer set of path properties for use with the <code><strong>P</strong></code> operator, by permitting temporal operators to be combined. Here are a few examples of properties expressible using this functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock76'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">F</span> ( \"<span class=\"prismident\">request</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">ack</span>\") ) ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=76' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"with probability greater than 0.99, a request is eventually received, followed immediately by an acknowledgement\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock77'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">send</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=77' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"a message is sent infinitely often with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock78'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">G</span> (\"<span class=\"prismident\">error</span>\" &amp; !\"<span class=\"prismident\">repair</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=78' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of an error occurring that is never repaired\n</p>\n<p class='vspace'>Note that logical operators have precedence over temporal ones, so you will often need to include parentheses when using logical operators, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock79'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\") &amp; (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=79' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For temporal operators, unary operators (such as <code><strong>F</strong></code>, <code><strong>G</strong></code> and <code><strong>X</strong></code>) have precedence over binary ones (such as <code><strong>U</strong></code>). Unary operators can be nested, without parentheses, but binary ones cannot.\n</p>\n<p class='vspace'>So, these are allowed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock80'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">a</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ (\"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\") <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=80' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>but this is not:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock81'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=81' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>The S Operator</h1>\n<p>The <code><strong>S</strong></code> operator is used to reason about the <em>steady-state</em> behaviour of a model,\ni.e. its behaviour in the <em>long-run</em> or <em>equilibrium</em>.\nPRISM currently only provides support for DTMCs and CTMCs.\nThe definition of steady-state (long-run) probabilities for finite DTMCS and CTMCs is well defined (see e.g. [<a class='wikilink' href='References.html#Ste94'>Ste94</a>]).\nInformally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock82'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">prop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=82' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a DTMC or CTMC if\n\"starting from <em>s</em>, the steady-state (long-run) probability of being in a state which satisfies the (Boolean-valued) PRISM property <code>prop</code>, meets the bound <code>bound</code>\".\nA typical example of this type of property would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock83'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.05</span> [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=83' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the long-run probability of the queue being more than 75% full is less than 0.05\".\n</p>\n<p class='vspace'>Like the <code><strong>P</strong></code> <a class='wikilink' href='../PropertySpecification/ThePOperator.html'>operator</a>, the <code><strong>S</strong></code> operator can be used in a <em>quantitative</em> form, which returns the actual probability value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock84'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=84' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and can be further customised with the use of <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\n</p><hr />\n<h1>Reward-based Properties</h1>\n<p>PRISM models can be augmented with information about <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>rewards</a> (or, equivalently, costs).\nThe tool can analyse properties which relate to the <em>expected values</em> of these rewards.\nThis is achieved using the <code><strong>R</strong></code> operator, which works in a similar fashion to the\n<code><strong>P</strong></code> and <code><strong>S</strong></code> operators, and can be used either in a Boolean-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock85'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=85' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>bound</code> takes the form <code>&lt;r</code>, <code>&lt;=r</code>, <code>&gt;r</code> or <code>&gt;=r</code> for an expression <code>r</code> evaluating to a non-negative double,\nor a real-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock86'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">query</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=86' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>query</code> is <code>=?</code>, <code>min=?</code> or <code>max=?</code>.\nIn the latter case, <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a> can be used, as for the <code><strong>P</strong></code> and <code><strong>S</strong></code> operators.\n</p>\n<p class='vspace'>Informally, \"<code><strong>R</strong> bound [ rewardprop ]</code>\" is true in a state of a model if\n\"the expected reward associated with <code>rewardprop</code> of the model when starting from that state''\nmeets the bound <code>bound</code> and \"<code><strong>R</strong> query [ rewardprop ]</code>\"  returns the actual expected reward value.\n</p>\n<p class='vspace'>There are various different types of reward properties:\n</p>\n<div class='vspace'></div><ul><li>\"reachability reward\": <code><strong>F</strong> prop</code>\n</li><li>\"co-safe LTL reward\": e.g. <code><strong>F</strong> (prop1 &amp; <strong>F</strong> prop2)</code>\n</li><li>\"cumulative reward\" : <code><strong>C</strong>&lt;=t</code>\n</li><li>\"total reward\" : <code><strong>C</strong></code>\n</li><li>\"instantaneous reward\" : <code><strong>I</strong>=t</code>\n</li><li>\"steady-state reward\" : <code><strong>S</strong></code>.\n</li></ul><p class='vspace'>Below, we consider each of these cases in turn.\nThe descriptions here are kept relatively informal.\nPrecise definitions for most of these can be found in, for example,\n[<a class='wikilink' href='References.html#KNP07a'>KNP07a</a>] (for DTMCs and CTMCs) or [<a class='wikilink' href='References.html#FKNP11'>FKNP11</a>] (for MDPs).\n</p>\n<div class='vspace'></div><h3>\"Reachability reward\" properties</h3>\n<p>\"Reachability reward\" properties associate a reward with each path of a model.\nMore specifically, they refer to the reward accumulated along a path until a certain point is reached.\nThe manner in which rewards are accumulated depends on the model type.\nFor DTMCs and MDPs, the total reward for a path is the sum of the state rewards for each state along the path\nplus the sum of the transition rewards for each transition between these states.\nThe situation for CTMCs is similar, except that the state reward assigned to each state\nof the model is interpreted as the <em>rate</em> at which rewards are accumulated in that state,\ni.e. if <em>t</em> time units are spent in a state with state reward <em>r</em>,\nthe reward accumulated in that state is <em>r</em> x <em>t</em>.\nHence, the total reward for a path in a CTMC is the sum of these products for each state along the path\nplus the sum of the transition rewards for each transition between these states.\n</p>\n<p class='vspace'>The reward property \"<code>F prop</code>\" corresponds to the reward cumulated along a path\nuntil a state satisfying property <code>prop</code> is reached,\nwhere rewards are cumulated as described above.\nState rewards for the <code>prop</code>-satisfying state reached are not included in the cumulated value.\nIn the case where the probability of reaching a state satisfying <code>prop</code> is less than 1, the reward is equal to infinity.\n</p>\n<p class='vspace'>A common application of this type of property is the case when the rewards associated with the model correspond to time.\nOne can then state, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock87'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">9.5</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=87' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"the expected time taken to reach, from <em>s</em>, a state where <code>z</code> equals 2 is less than or equal to 9.5\".\n</p>\n<div class='vspace'></div><h3>\"Co-safe LTL reward\" properties</h3>\n<p>These generalise the \"reachability\" properties above. Again, reward is accumulated along a path up until some point,\nbut this is specified in a more general way, by giving a formula in the co-safe fragment of linear temporal logic (LTL).\nRewards are accumulated up until the point where the formula is first satisfied. For example, this property, for a DTMC or CTMC,\nqueries the expected reward accumulated until first <code>goal</code> equals 1 and then subsequently <code>goal</code> equals 2:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock88'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">F</span> (<span class=\"prismident\">goal</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismkeyword\">F</span> <span class=\"prismident\">goal</span>=<span class=\"prismnum\">2</span>) ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=88' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and this property, for an MDP, minimises the expected reward until <code>loc</code> equals 1,\nhaving passed only through states where <code>loc</code> never equals 4\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock89'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismident\">loc</span>!=<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">loc</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=89' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As for reachability rewards, if the probability of satisfying the formula is less than 1,\nthen the expected reward is defined to be infinite.\n</p>\n<p class='vspace'>Intuitively, a <em>co-safe</em> formula is one that is satisfied within a finite period of time,\nand remains true for ever once it becomes true for the first time.\nFor simplicity, PRISM actually supports the <em>syntactic</em> co-safe fragment of LTL,\nwhich is defined as any LTL formula that only uses the temporal operators <code><strong>F</strong></code>, <code><strong>U</strong></code> and <code><strong>X</strong></code>\n(but not <code><strong>G</strong></code>, for example).\nPRISM's notation for LTL formulas is described <a class='wikilink' href='../PropertySpecification/ThePOperator.html'>here</a>.\n</p>\n<div class='vspace'></div><h3>\"Cumulative reward\" properties</h3>\n<p>\"Cumulative reward\" properties also associate a reward with each path of a model,\nbut only up to a given time bound.\nThe property <code>C&lt;=t</code> corresponds to the reward cumulated along a path\nuntil <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\nState and transition rewards along a path are cumulated exactly as described in the previous section.\n</p>\n<p class='vspace'>A typical application of this type of property is the following.\nConsider a model of a disk-drive controller which includes a queue of incoming disk requests.\nIf we assign a reward of 1 to each transition of the model\ncorresponding to the situation where an incoming request is lost because the queue is full,\nthen the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock90'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">15.5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=90' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would return, for a given state of the model,\n\"the expected number of lost requests within 15.5 time units of operation\".\n</p>\n<p class='vspace'><a name='total' id='total'></a>\n</p><h3>\"Total reward\" properties</h3>\n<p>\"Total reward\" properties refer to the accumulation of state and transition rewards\nin the same way as for \"reachability reward\" and \"cumulative reward\" properties,\nbut the rewards is accumulated indefinitely,\ni.e. the total reward accumulated along the whole (infinite) path.\nNote that this means that, unless a path ends up remaining forever in states with zero reward,\nthe total reward will be infinite.\n</p>\n<p class='vspace'>Re-using the reward structure in the previous example,\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock91'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=91' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>returns \"the expected total number of lost requests\".\n</p>\n<div class='vspace'></div><h3>\"Instantaneous reward\" properties</h3>\n<p>\"Instantaneous reward\" properties refer to the reward of a model at a particular instant in time.\nThe reward property <code>I=t</code> associates with a path the reward in the state \nof that path when exactly <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\n</p>\n<p class='vspace'>Returning to our example from the previous section of a model for a disk-request queue in a disk-drive controller,\nconsider the case where the rewards assigned to each state of the model give the current size of the queue in that state.\nThen, the following property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock92'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;<span class=\"prismnum\">4.4</span> [ <span class=\"prismkeyword\">I</span>=<span class=\"prismnum\">100</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=92' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would be true in a state <em>s</em> of the model if\n\"starting from <em>s</em>, the expected queue size exactly 100 time units later is less than 4.4\".\nNote that, for this type of reward property, state rewards for CTMCs do not have to refer to rates;\nthey can refer to any instantaneous measure of interest for a state.\n</p>\n<div class='vspace'></div><h3>\"Steady-state reward\" properties</h3>\n<p>Unlike the previous three types of property,\n\"steady-state reward\" properties relate not to paths, but rather to the reward in the long-run.\nA typical application of this type of property would be, in the case where\nthe rewards associated with the model correspond to power consumption, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock93'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">0.7</span> [ <span class=\"prismkeyword\">S</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=93' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"starting from <em>s</em>, the long-run average power consumption is less than 0.7\".\n</p>\n<div class='vspace'></div><h3>Which reward structure?</h3>\n<p>In the case where a PRISM model has multiple <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structures</a> you may need to specify which reward structure your property refers to. This is done by placing the information in braces (<code>{}</code>) after the <code>R</code> operator. You can do so either using the name assigned to a reward structure (if any) or using the index (where <code>1</code> means the first rewards structure in the PRISM model file, <code>2</code> the second, etc.). Examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock94'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">num_failures</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">10.0</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismnum\">2</span>}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=94' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note that when using an index to specify the reward structure, you can actually put any expression that evaluates to an integer. This allows you to, for example, write a property of the form <code>R{c}=?[...]</code> where <code>c</code> is an undefined integer constant. You can then vary the value of <code>c</code> in an experiment and compute values for several different reward structures at once.\n</p>\n<p class='vspace'>If you don't specify a reward structure to the <code>R</code> operator, by default, the first one in the model file is used.\n</p>\n<div class='vspace'></div><h3>Availability</h3>\n<p>There are currently a few restrictions on the model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a> that can be used for some reward properties. The following table summarises the currently availability, where S, M, H and E denote the \"sparse\", \"MTBDD\", \"hybrid\" and \"explicit\" engines, respectively, for DTMCs, CTMCs and MDPs. For PTAs, support for rewards is currently quite restrictive; see the later section on <a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>real-time model properties</a> for details.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><code><strong>F</strong></code></td><td  align='center'>cosafe</td><td  align='center'><code><strong>C</strong>&lt;=t</code></td><td  align='center'><code><strong>C</strong></code></td><td  align='left'><code><strong>I</strong>=t</code></td><td  align='right'><code><strong>S</strong></code></td></tr>\n<tr ><td  align='center'><strong>DTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>CTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>MDPs</strong></td><td  align='center'>SM-E</td><td  align='center'>SMHE</td><td  align='center'>S--E</td><td  align='center'>----</td><td  align='center'>SM-E</td><td  align='right'>----</td></tr>\n</table><hr />\n<h1>Multi-objective Properties</h1>\n<p>For MDPs, PRISM supports <em>multi-objective</em> properties. Consider a property that uses the <code><strong>P</strong></code> operator. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock95'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=95' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This states that, <em>for all</em> strategies (or policies) of the MDP, the probability of reaching an <code>\"error\"</code> state is less than 0.01.\n</p>\n<p class='vspace'>Multi-objective queries differ in two important ways. Firstly, (by default) they ask about the <em>existence</em> of a strategy. Secondly they refer to <em>multiple</em> properties of a strategy. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock96'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=96' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means: \"does there exist a strategy of the MDP under which the probability of reaching an <code>\"error1\"</code> state is less than 0.01 <em>and</em> the probability of reaching an <code>\"error2\"</code> state is less than 0.02?\"\n</p>\n<p class='vspace'>To use the terminology from [<a class='wikilink' href='References.html#FKP12'>FKP12</a>], the above is an \"achievability\" query (i.e., is this combination of objectives achievable by some strategy?). PRISM also supports two other kinds of multi-objective query: \"numerical\" and \"Pareto\" queries.\n</p>\n<p class='vspace'>A \"numerical\" query looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock97'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=97' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>meaning \"what is the minimum possible probability of reaching <code>\"error1\"</code>, over all strategies of the MDP for which the probability of reaching <code>\"error2\"</code> is less than 0.02?\".\n</p>\n<p class='vspace'>A \"Pareto\" queries leaves both of the objectives unbounded, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock98'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=98' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This asks PRISM to compute (approximately), the <em>Pareto curve</em> for this pair objectives. Intuitively, this is the set of pairs of probabilities (of reaching <code>\"error1\"</code>/<code>\"error2\"</code>) such that reducing one probability any more would necessitate an increase in the other probability.\n</p>\n<div class='vspace'></div><h3>Types of Objectives</h3>\n<p>For simplicity, the examples above all refer to the probability of reaching classes of states in the model. Other types of property (objective) are also possible.\n</p>\n<p class='vspace'>Firstly, we can extend the examples above by referring to the probability of any\n<a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>LTL</a> property. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock99'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=99' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9?\".\n</p>\n<p class='vspace'>We can also use more than 2 objectives, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock100'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.95</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good3</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=100' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9 and the probability of visiting <code>\"good3\"</code> states infinitely often remains at least 0.95?\".\n</p>\n<p class='vspace'>Multi-objective queries can also refer to the expected total cumulative value of a reward structure. We write such properties in the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock101'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}<span class=\"prismkeyword\">min</span>=?[ <span class=\"prismkeyword\">C</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">energy</span>\"}&lt;=<span class=\"prismnum\">1.45</span> [ <span class=\"prismkeyword\">C</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=101' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the minimum expected cumulative value of reward structure <code>\"time\"</code>, such that the expected cumulative value of reward structure <code>\"energy\"</code> is below 1.45.\n</p>\n<p class='vspace'>Note that this <code><strong>C</strong></code> reward operator differs from the <code><strong>F</strong> \"target\"</code> operator, usually used for standard (single-objective) MDP model checking. Whereas the <code><strong>F</strong> \"target\"</code> operator refers to the expected reward accumulated until a <code>\"target\"</code> state is reached the <code><strong>C</strong></code> operator refers to the expected <em>total</em> reward.\n</p>\n<p class='vspace'>A few important notes regarding rewards:\n</p>\n<div class='vspace'></div><ul><li>Currently only transition rewards are supported; state rewards are not.\n<div class='vspace'></div></li><li>Certain assumptions are made regarding the finiteness of rewards; see p.7 of [<a class='wikilink' href='References.html#FKP12'>FKP12</a>] for details.\n</li></ul><p class='vspace'>Finally, time-bounded variants of both probabilistic reachability and expected cumulative rewards objectives can be used. Here is an example that uses the latter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock102'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">power</span>\"}<span class=\"prismkeyword\">min</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">queue</span>\"}&lt;=<span class=\"prismident\">r</span> [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=102' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Solution Methods</h3>\n<p>PRISM can perform multi-objective model checking using two distinct solution methods, which are described in [<a class='wikilink' href='References.html#FKN+11'>FKN+11</a>] and [<a class='wikilink' href='References.html#FKP12'>FKP12</a>]. The former is based on the use of linear programming; the latter reduces multi-objective model checking to a series of simpler problems, solved using value iteration (or the Gauss-Seidel variant of value iteration). The default is \"Value iteration\". You can change this in the GUI using the option \"MDP multi-objective solution methods\", or using the command-line switches <code>-lp</code>, <code>-valiter</code>, <code>-gs</code>.\n</p>\n<p class='vspace'>There are some restrictions for the different methods, e.g.\n</p>\n<div class='vspace'></div><ul><li>Linear programming does not support time-bounded properties or Pareto queries\n</li></ul><div class='vspace'></div><hr />\n<h1>Real-time Models</h1>\n<p>The classes of property that can be checked for real-time models (PTAs and POPTAs) are currently more restricted than for the other kinds of models that PRISM supports. This is because the model checking procedures are quite different for this type of model. We describe these restrictions here. The situation is also dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is being used.\n</p>\n<p class='vspace'>For the \"<strong>stochastic games</strong>\" engine, we essentially only allow unbounded or time-bounded probabilistic reachability properties, i.e. properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock103'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=103' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>target</code> is a Boolean-valued expression that does not include references to any clock variables and <code>T</code> is an integer-valued expression. The <code><strong>P</strong></code> operator cannot be nested and the <code><strong>S</strong></code> and <code><strong>R</strong></code> operators are not supported.\n</p>\n<p class='vspace'>The \"<strong>backwards reachability</strong>\" engine is similar but currently only handles maximum probabilities.\n</p>\n<p class='vspace'>For the \"<strong>digital clocks</strong>\" engine, there is slightly more flexibility,\ne.g. until (<code><strong>U</strong></code>) properties are allowed, as are clock variables in expressions and arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock104'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=104' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This engine, like the \"stochastic games\" engine, does not allowed nested properties. Also, references to clocks must, like in the modelling language, not use strict comparisons\n(e.g. <code>x&lt;=5</code> is allowed, <code>x&lt;5</code> is not).\n</p>\n<p class='vspace'>The digital clocks also has support for rewards:\nit is possible to check reachability reward properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock105'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=105' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Reward structures specified in the model, though, must not depend on clock variables.\nFormally, the class of PTAs with this kind of reward structure is sometime called <em>linearly priced PTAs</em> (see e.g. [<a class='wikilink' href='References.html#KNPS06'>KNPS06</a>].\n</p>\n<p class='vspace'>The digital clocks method is based on a language-level translation from a PTA model to an MDP one. If you want to see the MDP PRISM model that was generated, add the switch <code>-exportdigital digital.nm</code> when model checking property to export the model file to <code>digital.nm</code>.\n</p><hr />\n<h1>Partially Observable Models</h1>\n<p>For partially observable models (POMDPs and POPTAs),\nPRISM uses the same property language as the their\nfully observational equivalents (MDPs and PTAs).\nHowever, a more limited range of properties are available.\nFor POMDPs, PRISM currently supports probabilistic reachability,\nprobabilistic until, or expected reachability rewards properties, i.e.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock106'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=106' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or bounded variants with a probability/threshold instead\nof the <code>min=?</code> or <code>max=?</code>.\n</p>\n<p class='vspace'>For the verification methods currently implemented,\nthere are a few additional restrictions.\nFirstly, the <code>target</code> (and <code>remain</code>) expression appearing\nin the property must be an observable.\nIn other words, if any state of the POMDP satisfies the expression,\nthen all other observationally equivalent states must also satisfy it.\nThis is easily achieved by only using either observable variables\nor named observables in the expression, but that is not required.\nSecondly, probabilities and expected rewards are only computed from a single state.\n</p>\n<p class='vspace'>POPTAs are currently verified using the \"digital clocks\" approach to\ntranslate them into a POMDP, so they inherit the same\n<a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>restrictions</a>\n(that strict or diagonal clock comparisons are not allowed).\nHowever for POPTAs, time-bounded probabilistic reachability is also supported.\n</p><hr />\n<h1>Uncertain Models</h1>\n<p>For uncertain models, currently interval MDPs (IMDPs) or interval DTMCs (IDTMCs), PRISM performs <em>robust</em> verification, which considers the best- or worst-case behaviour that can arise depending on the way that probabilities are selected from intervals.\n</p>\n<p class='vspace'>For example, instead of a property for a DTMC such as\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock107'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=107' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which asks for the probability to reach a state satisfying <code>\"goal\"</code>, IDTMCs use MDP-style queries:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock108'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=108' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which compute the minimum or maximum possible probability that can arise.\n</p>\n<p class='vspace'>Similarly, for an IMDP, there are now two separate quantifications, firstly over strategies (policies) and secondly over the distinct ways that transition probabilities can be selected from intervals, for which <code>min</code> or <code>max</code> appear in that order in the query. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock109'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmaxmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmaxmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=109' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>return the minimum and maximum values, respectively, over resolutions of transition probabilities for the maximum probability of reaching <code>\"goal\"</code>. Similarly, <code>minmin</code> and <code>minmax</code> are used for the minimum probability of reaching <code>\"goal\"</code>. Model checking is supported for:\n</p>\n<div class='vspace'></div><ul><li>the <code><strong>P</strong></code> operator, including single temporal operators and LTL formulae\n</li><li>the <code><strong>R</strong></code> operator, for the expected reward to reach a target or satisfy a co-safe LTL formula\n</li></ul><div class='vspace'></div><hr />\n<h1>Non-Probabilistic Properties</h1>\n<p>PRISM also supports model checking of the non-probabilistic temporal logics CTL (computation tree logic) and LTL (linear temporal logic).\nProperties in these logics use the <code><strong>A</strong></code> (for all) and <code><strong>E</strong></code> (there exists) operators,\ninstead of the probabilistic <code><strong>P</strong></code> operator used in many other properties supported by PRISM.\n</p>\n<p class='vspace'>Properties take the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock110'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">A</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=110' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which are true in a state <em>s</em> of a model if\n\"path property <code>pathprop</code> is satisfied by <em>all</em> paths from state <em>s</em>\"\nand\n\"path property <code>pathprop</code> is satisfied by <em>some</em> path from state <em>s</em>\",\nrespectively.\nThe syntax for LTL formulas is the same as those allowed within the <a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>P operator</a>.\n</p>\n<p class='vspace'>Example properties include:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock111'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ] <span class=\"prismcomment\">// There exists a path that reaches a state satisfying \"goal\"</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span> ] <span class=\"prismcomment\">// Variable x is always at most 10 along all paths of the model</span><br/>\n<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">ready</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">launch</span>\") ] <span class=\"prismcomment\">// There exists a path along which label \"ready\" eventually becomes true and label \"launch\" is true immediately afterwards</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span>) | (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>) ] <span class=\"prismcomment\">// Along all paths, either x=1 or x=2 is true infinitely often</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=111' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Counterexamples and Witnesses</h3>\n<p>If you check a CTL property of the form <code>A [ G \"inv\" ]</code> and it is false, PRISM will generate a counterexample in the form of a path that reaches a state where <code>\"inv\"</code> is not true. This is displayed either in the simulator (from the GUI) or at the command-line. Similarly, if you check <code>E [ F \"goal\" ]</code> and the result is true, a witness (a path reaching a <code>\"goal\"</code> state) will be generated.\n</p><hr />\n<h1>Syntax And Semantics</h1>\n<h3>Syntax</h3>\n<p>The syntax of the PRISM property specification language subsumes various probabilistic temporal logics, including PCTL, CSL, (probabilistic) LTL, PCTL* and CTL. Informally, the syntax can be summarised as follows: a property can be any valid, well-typed PRISM <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a>, which (optionally) also includes the probabilistic operators discussed previously (<code><strong>P</strong></code>, <code><strong>S</strong></code> and <code><strong>R</strong></code>) and the non-probabilistic (CTL) ones <code><strong>A</strong></code> and <code><strong>E</strong></code>). This mean that any of the following operators can be used:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li><li><code><strong>P</strong></code> (probabilistic operator)\n</li><li><code><strong>S</strong></code> (steady-state operator)\n</li><li><code><strong>R</strong></code> (reward operator)\n</li><li><code><strong>A</strong></code> (for-all operator)\n</li><li><code><strong>E</strong></code> (there-exists operator)\n</li></ul><p class='vspace'>This allows you to write any property expressible in logics such as PCTL and CSL. For example, CSL allows you to nest <code><strong>P</strong></code> and <code><strong>S</strong></code> operators:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock112'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>&gt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">S</span>&gt;<span class=\"prismnum\">0.9</span>[ <span class=\"prismident\">num_servers</span> &gt;= <span class=\"prismnum\">5</span> ] ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=112' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of it taking more than 2 hours to get to a state from which the long-run probability of at least 5 servers being operational is &gt;0.9\"\n</p>\n<p class='vspace'>You can also express various arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock113'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">3600</span>,<span class=\"prismnum\">7200</span>] <span class=\"prismident\">oper</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=113' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability that the system is <strong>not</strong> operational at any point during the second hour of operation\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock114'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">oper</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">t</span> ] / <span class=\"prismident\">t</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=114' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the expected fraction of time that the system is available (i.e. the expected interval availability) in the time interval [0, t]\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock115'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">fail_A</span> ] / <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">any_fail</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=115' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the (conditional) probability that component A eventually fails, given\nthat at least one component fails\"\n</p>\n<div class='vspace'></div><h3>Semantics</h3>\n<p>We omit a formal presentation of the semantics of the PRISM property language. The semantics of the probabilistic temporal logics that the language incorporates can be found from a variety of sources. See for example the pointers given in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>It is worth, however, clarifying a few points specific to PRISM. A property is evaluated with respect to a particular state of a model. Depending on the type of the property, this value may either be a Boolean, an integer or a double. When performing model checking, PRISM usually has to actually compute the value for <em>all</em> states of the model but, for clarity, will by default report just a single value. Typically, this is the value for the (single) initial state of the model. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock116'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=116' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will report the probability, from the initial state of the model, of reaching an \"error\" state.\nThis:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock117'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=117' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will return <code>true</code> if and only if the probability, from the initial state, is greater than 0.5.\n</p>\n<p class='vspace'><strong>Note:</strong> This is contrast to older versions of PRISM, which treated numerical and Boolean-valued properties differently in this respect.\n</p>\n<p class='vspace'>For models with <a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>multiple initial states</a>, we need to adapt these definitions slightly. In this case, the two properties above will yield, respectively:\n</p>\n<div class='vspace'></div><ul><li>the range of values (over all initial states) of the probability of reaching \"error\"\n<div class='vspace'></div></li><li><code>true</code> if and only if the probability is greater than 0.5 from <em>all</em> initial states.\n</li></ul><p class='vspace'>You can also ask PRISM to return different values using <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>,\nwhich are described in the next section.\n</p><hr />\n<h1>Filters</h1>\n<p>As discussed above, when reporting the result of model checking a property, PRISM will by default return the value for the (single) initial state of the model. However, since PRISM in fact usually has to compute values for <em>all</em> states simultaneously, you can customise PRISM properties to obtain different results. This is done using <em>filters</em>.\n</p>\n<p class='vspace'>Filters are created using the <code>filter</code> keyword. They take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock118'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=118' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>op</code> is the filter <em>operator</em> (see below), <code>prop</code> is any PRISM property and <code>states</code> is a Boolean-valued expression identifying a set of states over which to apply the filter.\n</p>\n<p class='vspace'>In fact, the <code>states</code> argument is optional; if omitted, the filter is applied over all states. So, the following properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock119'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismkeyword\">true</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=119' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Here's a simple example of a filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock120'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=120' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This gives the <em>maximum</em> value, starting from any state satisfying <code>x=0</code>, of the probability of reaching an \"error\" state.\n</p>\n<p class='vspace'>Here's another simple example,\nwhich checks whether, <em>starting from any reachable state</em>,\nwe eventually reach a \"done\" state with probability 1.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock121'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=121' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We could modify this property slightly to instead check whether, from any state that satisfies the label \"ready\", we eventually reach a \"done\" state with probability 1. This could be done with either of the following two equivalent properties:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock122'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, \"<span class=\"prismident\">ready</span>\" =&gt; <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ], \"<span class=\"prismident\">ready</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=122' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Note:</strong> In older versions of PRISM, the property above could be written just as <code>\"ready\" =&gt; P&gt;=1 [ F \"done\" ]</code> since the result was checked for all states by default, not just the <a class='wikilink' href='../PropertySpecification/SyntaxAndSemantics.html'>initial state</a>. Now, you need to explicitly include a filter, as shown above, to achieve this.\n</p>\n<div class='vspace'></div><h3>Types of filter</h3>\n<p>Most filters of the form <code>filter(op, prop, states)</code>\napply some operator <code>op</code> to the values of property <code>prop</code>\nfor all the states satisfying <code>states</code>,\nresulting in a single value.\nThe full list of filter operators <code>op</code> in this category is:\n</p>\n<div class='vspace'></div><ul><li><code>min</code>: the minimum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>max</code>: the maximum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>count</code>: counts the number of states satisfying <code>states</code> for which <code>prop</code> is true\n</li><li><code>sum</code> (or <code>+</code>): sums the value of <code>prop</code> for states satisfying <code>states</code>\n</li><li><code>avg</code>: the average value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>first</code>: the value of <code>prop</code> for the first (lowest-indexed) state satisfying <code>states</code>\n</li><li><code>range</code>: the range (interval) of values of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>forall</code> (or <code>&amp;</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for all states satisfying <code>states</code>\n</li><li><code>exists</code> (or <code>|</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for some states satisfying <code>states</code>\n</li><li><code>state</code>: returns the value for the single state satisfying <code>states</code> (if there is more than one, this is an error)\n</li></ul><p class='vspace'>There are also a few filters that, rather than returning a single value, return different values for each state, like a normal PRISM property:\n</p>\n<div class='vspace'></div><ul><li><code>argmin</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the minimum value of <code>prop</code>\n</li><li><code>argmax</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the maximum value of <code>prop</code>\n</li><li><code>print</code>: does not change the result of <code>prop</code> but prints the (non-zero) values to the log\n</li><li><code>printall</code>: like <code>print</code>, but displays <em>all</em> values, even for states where the value is zero\n</li></ul><div class='vspace'></div><h3>More examples</h3>\n<p>Here are some further illustrative examples of properties that use filters.\n</p>\n<p class='vspace'>Filters provide a quick way to <em>print</em> the results of a model checking query for several states. In most cases, for example, a <code>P=?</code> query just returns the probability from the initial state. To see the probability for all states satisfying <code>x&gt;2</code>, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock123'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">P</span>=? [ ... ], <span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">2</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=123' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Values are printed in the log (i.e. to the \"Log\" tab in the GUI or to the terminal from the command-line). For small models, you could omit the final <code>states</code> argument (<code>x&gt;2</code> here) and view the probabilities from all states. You can also use PRISM's <a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>verbose</a> mode to view values for all states, but filters provide an easier and more flexible solution.\n<code>print</code> filters do not actually alter the result returned so, in the example above, PRISM will still return the probability for the initial state, in addition to printing other probabilities in the log.\n</p>\n<p class='vspace'>You can also use <code>print</code> filters to display lists of states. For example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock124'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">argmax</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]))<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=124' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>prints the states which have the highest probability of reaching an error state.\nHowever, you should exercise caution when using <code>argmax</code> (or <code>argmin</code>) on properties such as <code>P=? [ ... ]</code> (or <code>S=? [ ... ]</code> or <code>R=? [ ... ]</code>), whose results are only approximate due to the nature of the methods used to compute them (or because of round-off errors.)\n</p>\n<p class='vspace'>Another common use of filters is to display the value for a particular state of the model (rather than the initial state, which is used by default). To achieve this, use e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock125'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>&amp;<span class=\"prismident\">y</span>=<span class=\"prismnum\">3</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=125' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>x=2&amp;y=3</code> is assumed to specify one particular state.\nA <code>state</code> filter will produce an error if the filter expression is not satisfied by exactly one state of the model.\n</p>\n<p class='vspace'>Filters can also be built up into more complex expressions. For example, the following two properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock126'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">avg</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">sum</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\") / <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">count</span>, \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=126' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>range</code> filter, unlike most PRISM expressions which are of type Boolean, integer or double, actually returns an interval: a pair of integers or doubles. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock127'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">count</span>=<span class=\"prismnum\">10</span> ], <span class=\"prismident\">count</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=127' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>gives the range of all possible values for the probability of reach a state satisfying <code>count=10</code>, from all states satisfying <code>count=0</code>.\nAs will be described below, this kind of property also results from the use of old-style (<code>{...}</code>) filters and properties on models with multiple initial states.\n</p>\n<div class='vspace'></div><h3>Old-style filters</h3>\n<p>In older versions of PRISM, filters were also available, but in a less expressive form. Previously, they were only usable on <code><strong>P</strong></code>, <code><strong>S</strong></code> or <code><strong>R</strong></code> properties and only a small set of filter operators were permitted. They were also specified in a different way, using braces (<code>{</code>...<code>}</code>). For compatibility with old properties files (and for compactness), these forms of filters are still allowed. These old-style forms of filters:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock128'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=128' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are equivalent to:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock129'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">min</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=129' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the first of the four properties above (i.e. an old-style filter of the form <code>{states}</code> will result in an error if <code>states</code> is not satisfied by exactly one state of the model. Older versions of PRISM just gave you the value for the first state state satisfying the filter, without warning you about this. If you want to recreate the old behaviour, just use a <code>first</code> filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock130'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">first</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=130' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Default filters</h3>\n<p>Finally, for completeness, we show what the <em>default</em> filters are in PRISM,\ni.e. how the way that PRISM returns values from properties by default\ncould have been achieved equivalently using filters.\n</p>\n<p class='vspace'>Queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock131'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=131' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock132'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=132' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock133'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=133' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as either:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock134'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=134' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the cases where there the model has a single initial state\nor multiple initial states, respectively.\n</p><hr />\n<h1>Properties Files</h1>\n<h3>Constants</h3>\n<p>Files containing properties to be analysed by PRISM can also contain constants, as is the case for model files.\nThese are defined in identical fashion, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock135'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span> = <span class=\"prismnum\">7</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span> = <span class=\"prismnum\">9.5</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">p</span> = <span class=\"prismnum\">0.01</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismident\">p</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">x</span>=<span class=\"prismident\">k</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=135' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As before, these constants can actually be left undefined and then later\nassigned either a single value or a range of values using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'>In fact, values such as the probability bounds for the <code><strong>P</strong></code> or <code><strong>S</strong></code> operators (like <code><strong>P</strong></code> above)\nand upper or lower bounds for the <code><strong>U</strong></code> operator (like <code> T</code> above)\ncan be arbitrary expressions, provided they are constant.\nFurthermore, expressions in the properties file can also refer to constants previous defined in the model file.\n</p>\n<p class='vspace'><a name='labels' id='labels'></a>\n</p><h3>Labels</h3>\n<p>Another feature of properties files is <em>labels</em>. These are a way of defining sets of states that will be referred to in properties (they correspond to <em>atomic propositions</em> in a temporal logic setting). As described <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>earlier</a>, labels can be defined in either model files or property files.\n</p>\n<p class='vspace'>Labels are defined using the keyword <code><strong>label</strong></code>, followed by a name (identifier) in double quotes, and then an expression which evaluates to a Boolean. Definition and usage of labels are illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock136'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ \"<span class=\"prismident\">safe</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">fail</span>\" ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=136' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Two special cases are the <code>\"init\"</code> and <code>\"deadlock\"</code> labels which are always defined.\nThese are true in initial states of the model and states where deadlocks were found (and, usually, fixed by adding self-loops), respectively.\n</p>\n<p class='vspace'><a name='names' id='names'></a>\n</p><h3>Property names</h3>\n<p>For convenience, properties can be annotated with <em>names</em>, as shown in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock137'>\r\n  <div class='sourceblocktext'><div class=\"prism\">\"<span class=\"prismident\">safe</span>\": <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">temperature</span> &gt; <span class=\"prismident\">t_max</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=137' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which gives the name <code>\"safe\"</code> to the property. It is then possible to include named properties as sub-expressions of other properties, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock138'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismident\">num_sensors</span>&gt;<span class=\"prismnum\">0</span> =&gt; \"<span class=\"prismident\">safe</span>\");<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=138' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the syntax for referring to named properties is identical to the syntax for labels. For this reason, property names must be disjoint from those of any existing labels.\n</p>\n<p class='vspace'>You can refer to property names when using the command-line switch <a class='wikilink' href='../RunningPRISM/ModelChecking.html#cl'><code>-prop</code></a> to specify which property is to be model checked.\n</p>\n<div class='vspace'></div><h3>Properties files</h3>\n<p>A PRISM properties file can contain any number of properties.\nIt is good practice, as shown in the examples above, to terminate each property with a semicolon. Currently, this is not enforced by PRISM (to prevent incompatibility with old properties files) but this may change in the future.\n</p>\n<p class='vspace'>Like model files, properties can also include any amount of white space (spaces, tabs, new lines, etc.) and C-style comments, which are both ignored.\nThe recommended file extension for PRISM properties is now <code>.props</code>.\nPreviously, though, the convention was to use extension <code>.pctl</code> for properties of DTMCs, MDPs or PTAs\nand extension <code>.csl</code> for properties of CTMCs, so these are still also valid.\n<br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Running PRISM</span></h1>\n<hr />\n<h1>Starting PRISM</h1>\n<p>There are two versions of PRISM, one based on a graphical user interface (GUI),\nthe other based on a command line interface. Both use the same underlying model checker.\nThe latter is useful for running large batches of jobs, leaving long-running model checking tasks in the background, or simply for running the tool quickly and easily once you are familiar with its operation. \n</p>\n<p class='vspace'>Details how how to run PRISM can be found in the <a class='wikilink' href='../InstallingPRISM/Main.html'>installation instructions</a>.\nIn short, to run the PRISM GUI:\n</p>\n<div class='vspace'></div><ul><li>(on Windows) click the short-cut (to <code>xprism.bat</code>) installed on the Desktop/Start Menu\n</li><li>(on other OSs) run the <code>xprism</code> script in the <code>bin</code> directory\n</li></ul><p class='vspace'>You can also optionally specify a model file and a properties file to load upon starting the GUI, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock139'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xprism example.prism</span><br/>\n<span style=\"font-weight:bold;\">xprism example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=139' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To use the command-line version of PRISM, run the <code>prism</code> script, also in the <code>bin</code> directory, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock140'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism example.prism example.props -prop 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=140' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-dir</code> switch can be used to specify a directory for input (and output) files.\nSo the following are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock141'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism ~/myfiles/example.prism ~/myfiles/example.props</span><br/>\n<span style=\"font-weight:bold;\">prism -dir ~/myfiles example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=141' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The remainder of this section of the manual describes the main types of functionality offered by PRISM.\nFor a more introductory guide to using the tool, try the\n<a class='urllink' href='http://www.prismmodelchecker.org/tutorial/'>tutorial</a> on the PRISM web site.\nSome screenshots of the GUI version of PRISM are shown below.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui1.gif'><img width='500' src='../uploads/gui1.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (editing a model)</strong></span></div>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui2.gif'><img width='500' src='../uploads/gui2.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (model checking)</strong></span></div>\n<div class='vspace'></div><hr />\n<h1>Loading And Building a Model</h1>\n<p>Typically, when using PRISM, the first step is to load a model that has been specified in the PRISM modelling language. If using the GUI, select menu option \"Model | Open Model\" and choose a file. There are a selection of sample PRISM model files in the <code>prism-examples</code> directory of the distribution.\nA few very small models are contained in the subdirectory <code>simple</code>;\nthe rest are in subdirectories grouped by model type.\n</p>\n<p class='vspace'>The model will then be displayed in the editor in the \"Model\" tab of the GUI window. The file is parsed upon loading. If there are no errors, information about the modules, variables, and other components of the model is displayed in the panel to the left and a green tick will be visible. If there are errors in the file, a red cross will appear instead and the errors will be highlighted in the model editor. To view details of the error, position the mouse pointer over the source of the error (or over the red cross). Alternatively, select menu option \"Model | Parse Model\" and the error mIessage will be displayed in a message box. Model descriptions can, of course, also be typed from scratch into the GUI's editor.\n</p>\n<div class='vspace'></div><h3>Building the model</h3>\n<p>In order to perform model checking, PRISM will (in most cases) need to construct the corresponding probabilistic model, i.e. convert the PRISM model description to, for example, an MDP, DTMC, etc. During this process, PRISM computes the set of states in the model which are reachable from the initial states and the transition matrix which represents the model.\n</p>\n<p class='vspace'>Model construction is done automatically when you perform <a class='wikilink' href='../RunningPRISM/ModelChecking.html'>model checking</a>. However, you may always want to explicitly ask PRISM to build the model in order to test for errors or to see how large the model is. From the GUI, you can do this by by selecting \"Model | Build Model\". If there are no errors during model construction, the number of states and transitions in the model will be displayed in the bottom left corner of the window.\n</p>\n<p class='vspace'>From the command-line, simply type:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock142'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.nm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=142' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>model.nm</code> is the name of the file containing the model description.\n</p>\n<p class='vspace'>For some types of models, notably PTAs, models are not constructed in this way (because the models are infinite-state). In these cases, analysis of the model is not performed until model checking is performed.\n</p>\n<p class='vspace'><a name='deadlocks' id='deadlocks'></a>\n</p><h3>Deadlocks</h3>\n<p>You should be aware of the possibility of <em>deadlock states</em> (or <em>deadlocks</em>) in the model,\ni.e. states which are reachable but from which there are no outgoing transitions.\nPRISM will automatically search your model for deadlocks and, by default,\n\"fix\" them by adding self-loops in these states.\nSince deadlocks are sometimes caused by modelling errors,\nPRISM will display a warning message in the log when deadlocks are fixed in this way.\n</p>\n<p class='vspace'>You can control whether deadlocks are automatically fixed in this way using the \"Automatically fix deadlocks\" option (or with command-line switches <code>-nofixdl</code> and <code>-fixdl</code>). When fixing is disabled, PRISM will report and error when the model contains deadlocks (this used to be the default behaviour in older versions of PRISM).\n</p>\n<p class='vspace'>If you have unwanted or unexpected deadlocks in your model, there are several ways you can detect then. Firstly, by disabling deadlock fixing (as described above), PRISM will display a list of deadlock states in the log. Alternatively, you can model check the <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> property <code>filter(print, \"deadlock\")</code>, which has the safe effect.\n</p>\n<p class='vspace'>To find out <em>how</em> deadlocks occur, i.e. which paths through the model lead to a deadlock state, there are several possibilities. Firstly, you can model check the <a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>CTL</a> property <code>E[F \"deadlock\"]</code>. When checked from the GUI, this will provide you with the option of display a path to a deadlock in the simulator. From the command-line, for example with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock143'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -pf 'E[F \"deadlock\"]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=143' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>a path to a deadlock will be displayed in the log.\n</p>\n<p class='vspace'>Finally, in the eventuality that the model is too large to be model checked, you can still use the <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>simulator</a> to search for deadlocks. This can be done either by manually generating random paths using the <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html#gui'>simulator in the GUI</a> or, <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html#cl'>from the command-line</a>, e.g. by running:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock144'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath deadlock stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=144' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Debugging Models With The Simulator</h1>\n<p>PRISM includes a <em>simulator</em>, a tool which can be used to generate sample paths (executions) through a PRISM model. From the GUI, the simulator allows you to explore a model by interactively generating such paths. This is particularly useful for debugging models during development and for running sanity checks on completed models. Paths can also be generated from the command-line.\n</p>\n<p class='vspace'><a name='gui' id='gui'></a>\n</p><h3>Generating a path in the GUI</h3>\n<p>Once you have loaded a model into the PRISM GUI\n(note that it is not necessary to build the model),\nselect the \"Simulator\" tab at the bottom of the main window.\nYou can now start a new path by double-clicking in the bottom half of the window\n(or right-clicking and selecting \"New path\").\nIf there are undefined constants in the\nmodel (or in any currently loaded properties files) you will be prompted to give values for these. You\ncan also specify the state from which you wish to generate a path. By default, this is the initial state of\nthe model.\n</p>\n<p class='vspace'>The main portion of the user interface (the bottom part) displays a path through the currently loaded model. Initially, this will comprise just a single state. The table above shows the list of available transitions from this state. Double-click one of these to extend the path with this transition. The process can be repeated to extend the path in an interactive fashion. Clicking on any state in the current path shows the transition which was taken at this stage. Click on the final state in the path to continue\nextending the path. Alternatively, clicking the \"Simulate\" button will select a transition randomly (according to the probabilities/rates of the available transitions). By changing the number in the box below this button, you can easily generate random paths of a given length with a single click.\nThere are also options (in the accompanying drop-down menu) to allow generation of paths up until a particular length or, for CTMCs, in terms of the time taken.\n</p>\n<p class='vspace'>The figure shows the simulator in action.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui-sim.png'><img width='500' src='../uploads/gui-sim.png' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI: exploring a model using the simulator</strong></span></div>\n<p class='vspace'>It is also possible to:\n</p>\n<div class='vspace'></div><ul><li>backtrack to an earlier point in a path\n</li><li>remove all of the states before some point in a path\n</li><li>restart a path from its first state\n</li><li>export a path to a text file\n</li></ul><p class='vspace'>Notice that the table containing the path displays not just the value of each variable in each\nstate but also the time spent in that state and any rewards accumulated there. You can configure exactly which columns appear by right-clicking on the path and selecting \"Configure view\". For rewards (and for CTMC models, for the time-values), you can can opt to display the reward/time for each individual state and/or the cumulative total up until each point in the path.\n</p>\n<p class='vspace'>At the top-right of the interface, any labels contained in the currently loaded model/properties file are displayed, along with their value in the currently selected state of the path. In addition, the built-in <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>labels</a> <code>\"init\"</code> and <code>\"deadlock\"</code> are also included. Selecting a label from the list highlights all states in the current path which satisfy it.\n</p>\n<p class='vspace'>The other tabs in this panel allow the value of path operators (taken from properties in the current file) to be viewed for the current path, as well as various other statistics.\n</p>\n<p class='vspace'>Another very useful feature for some models is to use the \"Plot new path\" option from the simulator, which generates a plot of some/all of the variable/reward values for a particular randomly generated path through the model.\n</p>\n<p class='vspace'><a name='cl' id='cl'></a>\n</p><h3>Path generation from the command-line</h3>\n<p>It is also possible to generate random paths through a model using the command-line version of PRISM. This is achieved using the <code>-simpath</code> switch, which requires two arguments, the first describing the path to be generated and the second specifying the file to which the path should be output (as usual, specifying <code>stdout</code> sends output to the terminal). The following examples illustrate the various ways of generating paths in this way:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock145'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -simpath 10 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath time=7.5 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath deadlock path.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=145' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These generate a path of 10 steps, a path of at least 7.5 time units and a path ending in deadlock, respectively.\n</p>\n<p class='vspace'>Here's an example of the output:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock146'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 1 0.007479539729154247 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 2 0.00782819795294666 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 3 0.01570585559933703 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 4 0.017061111948220263 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 5 0.026816317516034468 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 6 0.039878416276337814 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 7 0.04456566315999103 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 8 0.047368359683643765 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 9 0.04934857366557349 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 10 0.055031679365844674 1 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=146' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This shows the sequence of states in the path, i.e. the values of the variables in each state. In the example above, there are 4 variables: <code>s</code>, <code>a</code>, <code>s1</code> and <code>s2</code>.\nThe first three columns show the type of transition taken to reach that state, its index within the path (starting from 0) and the time at which it was entered. The latter is only shown for continuous time models. The type of the transition is written as <em>[act]</em> if action label <code>act</code> was taken, and as <em>module1</em> if the module named <code>module1</code> takes an unlabelled transition). \n</p>\n<p class='vspace'>Further options can also be appended to the first parameter. For example, option <code>probs=true</code> also displays the probability/rate associated with each transition. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock147'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '5,probs=true' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 1 0.0011880118081395378 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 2 0.0037798355025401888 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 3 0.01029212322894221 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 4 0.023258883912578403 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 5 0.027402404026254504 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=147' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this example, the rate is 200.0 for all transitions.\nTo show the state/transition rewards for each step, use option <code>rewards=true</code>.\n</p>\n<p class='vspace'>If you are only interested in values of certain variables of your model, use the <code>vars=(...)</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock148'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '500,probs=true,vars=(a,s1,s2)' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 110 0.5025332771499665 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 111 0.5109407735244359 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 112 0.9960642154887506 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station1 0.5 130 1.0645858553472822 0 1 0</span><br/>\n<span style=\"font-style:italic;\">[loop1b] 200.0 132 1.0732572896618477 1 1 0</span><br/>\n<span style=\"font-style:italic;\">[serve1] 1.0 133 2.939742026148121 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 225 3.4311507854807677 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 227 3.434285492243098 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 228 3.553118276800078 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 250 3.6354431222941406 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 251 3.637552738997181 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 252 3.7343375346150576 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=148' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of single quotes around the path description argument to prevent the shell from misinterpreting special characters such as \"<code>(</code>\".\n</p>\n<p class='vspace'>Notice also that the above only displays states in which the values of some variable of interest changes. This is achieved with the option <code>changes=true</code>, which is automatically enabled when you use <code>vars=(...)</code>. If you want to see all steps of the path, add the option <code>changes=false</code>.\n</p>\n<p class='vspace'>An alternative way of viewing paths is to only display paths at certain fixed points in time. This is achieved with the <code>snapshot=x</code> option, where <code>x</code> is the time step. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock149'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 'time=5.0,snapshot=0.5' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">94 0.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">198 1.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">314 1.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">375 2.0 1 1 1 1</span><br/>\n<span style=\"font-style:italic;\">376 2.5 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">376 3.0 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">378 3.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">378 4.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">478 4.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">511 5.0 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=149' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use the <code>sep=...</code> option to specify the column separator. Possible values are <code>space</code> (the default), <code>tab</code> and <code>comma</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock150'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '10,vars=(a,b),sep=comma' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step,a,b,time</span><br/>\n<span style=\"font-style:italic;\">0,0,0,0.0</span><br/>\n<span style=\"font-style:italic;\">2,1,0,0.058443536856580006</span><br/>\n<span style=\"font-style:italic;\">3,1,1,0.09281024515535738</span><br/>\n<span style=\"font-style:italic;\">6,1,2,0.2556555786269585</span><br/>\n<span style=\"font-style:italic;\">7,1,3,0.284062896359802</span><br/>\n<span style=\"font-style:italic;\">8,1,4,1.1792064236954896</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=150' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When generating paths to a deadlock state, additional <code>repeat=...</code> option is available which will construct multiple paths until a deadlock is found. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock151'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath 'deadlock,repeat=100' stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=151' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, the simulator detects deterministic loops in paths (e.g. if a path reaches a state from which there is a just a single self-loop leaving that state) and stops generating the path any further. You can disable this behaviour with the <code>loopcheck=false</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock152'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">Warning: Deterministic loop detected after 6 steps (use loopcheck=false option to extend path).</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 3</span><br/>\n<span style=\"font-style:italic;\">die 4 7 3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=152' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock153'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10,loopcheck=false stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 2</span><br/>\n<span style=\"font-style:italic;\">die 4 7 2</span><br/>\n<span style=\"font-style:italic;\">die 5 7 2</span><br/>\n<span style=\"font-style:italic;\">die 6 7 2</span><br/>\n<span style=\"font-style:italic;\">die 7 7 2</span><br/>\n<span style=\"font-style:italic;\">die 8 7 2</span><br/>\n<span style=\"font-style:italic;\">die 9 7 2</span><br/>\n<span style=\"font-style:italic;\">die 10 7 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=153' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>One final note: the <code>-simpath</code> switch only generates paths up to the maximum path length setting of the simulator (the default is 10,000). If you want to generate longer paths, either change the\n<a class='wikilink' href='../ConfiguringPRISM/Main.html'>default setting</a> or override it temporarily from the command-line using the <code>-simpathlen</code> switch.\nYou might also use the latter to decrease the setting,\ne.g. to look for a path leading to a deadlock state,\nbut only within 100 steps:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock154'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath deadlock stdout -simpathlen 100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=154' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Exporting The Model</h1>\n<p>If required, once the model has been constructed, it can be exported, either for manual examination or for use in another tool. The following can all be exported:\n</p>\n<div class='vspace'></div><ul><li>the <strong>transition matrix</strong> (or function);\n</li><li>the <strong>rewards</strong> (state/transition) rewards;\n</li><li>the <strong>labels</strong> (in the <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>model</a> or <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>properties</a>) and the states that satisfy them\n</li><li>the definition of (reachable) <strong>states</strong>, i.e., their variable values\n</li><li>the definition of <strong>observations</strong>, i.e., their observable values, for partially observable models\n</li></ul><p class='vspace'>From the command-line version of PRISM, the most convenient and flexible approach is to use the <code>-exportmodel</code> switch.\nThis will, by default, use the extension of the filename(s) to determine the format.\n</p>\n<p class='vspace'>From the GUI, use the \"Model | Export\" menu to export the data to a file or, for small models, use the \"Model | View\" menu to print the details directly to the log. For the case of labels, if you want to export labels from the properties file too, use the \"Properties | Export labels\" option, rather than the \"Model | Export\" one.\n</p>\n<p class='vspace'>The main formats for model export are:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \".tra\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li><li><a class='urllink' href='https://www.graphviz.org/'>Dot</a> format, for a graphical view of the model\n</li></ul><p class='vspace'><a name='explicit' id='explicit'></a>\n</p><h3>Plain text (explicit files)</h3>\n<p>This format exports different parts of the model in different file, with the expected filename extensions being:\n</p>\n<div class='vspace'></div><ul><li><code>.tra</code> - transition matrix\n</li><li><code>.srew</code>, <code>.trew</code>, <code>.rew</code> - rewards: states, transitions or both\n</li><li><code>.lab</code> - labels\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>To export just the transition matrix in this format, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock155'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=155' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To export multiple parts, use, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock156'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=156' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you omit the file basename of the export files and the basename of the model will be used, so this is equivalent to the above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock157'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel .tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=157' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can use the shorthand <code>.all</code> to export everything, and <code>.rew</code> to export both state and transition rewards. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock158'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=158' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can always use <code>stdout</code> instead of a filename. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock159'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=159' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is a quick way to print all details (of a small model) to the terminal.\n</p>\n<p class='vspace'>The labels (<code>.lab</code>) export includes the built-in labels <code>\"init\"</code> and <code>\"deadlock\"</code>,\nproviding a way to export information about initial states and (fixed) deadlock states.\n</p>\n<p class='vspace'>When there are multiple reward structures, a separate file is created for each one and a (1-indexed) suffix is added to distinguish them.\nBy default, a header in each file (see the \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html#srew'>Explicit Model Files</a>\" appendix) also shows the name of the reward structure.\nThis can be omitted - see the options below - or via the option \"Include headers in model exports\" in the GUI.\n</p>\n<p class='vspace'><a name='umb' id='umb'></a>\n</p><h3>UMB (Unified Markov binary) format</h3>\n<p>UMB is a binary format that can incorporate all parts of the model listed above.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock160'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=160' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, everything is included. You can omit some parts with the <code>-exportmodel</code>\noptions <code>rewards</code>, <code>labels</code>, <code>states</code> and <code>obs</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock161'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb:states=false,rewards=false</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=161' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For a small model, you can also see a textual version of the UMB format\nusing file extension <code>.umbt</code> (or option <code>text</code>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock162'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.umbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=162' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also configure the compression used: <code>zip=false</code> turns it off,\n<code>zip=gzip</code> uses gzip and <code>zip=xz</code> uses xz (smaller but slower to read/write).\n</p>\n<p class='vspace'><a name='other' id='other'></a>\n</p><h3>Other formats and options</h3>\n<p>If the file extension is not recognised, PRISM defaults to plain text (explicit) format.\nYou can always override this using the @format@ option, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock163'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=umb,text</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=163' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can perform multiple model exports using several instances of <code>-exportmodel</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock164'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit -exportmodel model.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=164' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Other file formats are also available:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://www.mathworks.com/'>Matlab</a> code (extension <code>.m</code>) or <code>format=matlab</code>\n</li><li>Storm's DRN model format (extension <code>.drn</code>) or <code>format=drn</code>\n</li></ul><p class='vspace'>Other <code>-exportmodel</code> options are:\n</p>\n<div class='vspace'></div><ul><li><code>actions</code> (=<code>true</code>/<code>false</code>) - whether to  actions on choices/transitions\n</li><li><code>precision</code> (=<code>&lt;n&gt;</code>) - use <code>&lt;n&gt;</code> significant figures for floating point values (in text)\n</li><li><code>headers</code> (<code>=true/false</code>) - whether to include headers when exporting rewards\n</li><li><code>rows</code> - export matrices with one row/distribution on each line (plain text)\n</li><li><code>proplabels</code> - also export labels from a properties file into a <code>.lab</code> file\n</li></ul><p class='vspace'>For plain text export, although <code>-exportmodel</code> is now usually the best switch to use,\nother older switches still exist. For example, you can export individual files using\n<code>-exporttrans &lt;file&gt;</code>,\n<code>-exportstates &lt;file&gt;</code>,\n<code>-exportstaterewards &lt;file&gt;</code>,\n<code>-exporttransrewards &lt;file&gt;</code>,\n<code>-exportrewards &lt;file&gt; &lt;file&gt;</code>,\n<code>-exportlabels &lt;file&gt;</code>, and\n<code>-exportproplabels &lt;file&gt;</code>.\nAnd you can use switches\n<code>-exportmodelprecision &lt;x&gt;</code>,\n<code>-exportmatlab</code> and\n<code>-exportrows</code>\nto specify format options affecting all of them.\n</p>\n<p class='vspace'><a name='scc' id='scc'></a>\n</p><h3>Exporting (B)SCCs and end components</h3>\n<p>It is also possible to export the set of (bottom) strongly connected components (SCCs or BSCCs) for a model. This can only be done from the command-line currently. Use, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock165'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportsccs stdout</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportbsccs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=165' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For an MDP, you can also export the set of maximal end components (MECs):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock166'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -exportmecs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=166' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<h1>Model Checking</h1>\n<p>Typically, once a model has been constructed, it is analysed through model checking.\nProperties are specified as described in the \"<a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\" section,\nand are usually kept in files with extensions <code>.props</code>, <code>.pctl</code> or <code>.csl</code>.\nThere are properties files accompanying most of the sample PRISM models in the <code>prism-examples</code> directory.\n</p>\n<p class='vspace'>\n</p><h3>GUI</h3>\n<p>To load a file containing properties into the GUI, select menu option \"Properties | Open properties list\".\nThe file can only be loaded if there are no errors, otherwise an error is displayed.\nNote that it may be necessary to have loaded the corresponding model first,\nsince the properties will probably make reference to variables (and perhaps constants) declared in the model file.\nOnce loaded, the properties contained in the file are displayed in a list in the \"Properties\" tab of the GUI.\nConstants and labels are displayed in separate lists below.\nYou can modify or create new properties, constants and labels from the GUI,\nby right-clicking on the appropriate list and selecting from the pop-up menu which appears. Properties with errors are shaded red and marked with a warning sign.\nPositioning the mouse pointer over the property displays the corresponding error message.\n</p>\n<p class='vspace'>The pop-up menu for the properties list also contains a \"Verify\" option,\nwhich allows you instruct PRISM to model check the currently selected properties\n(hold down Ctrl/Cmd to select more than one property simultaneously).\nAll properties can be model checked at once by selecting \"Verify all\".\nPRISM verifies each property individually.\nUpon completion, the icon next to the property changes according to the result of model checking. For Boolean-valued properties, a result of true or false is indicated by a green tick or red cross, respectively. For properties which have a numerical result (e.g. <code>P=? [ ...]</code>), position the mouse pointer over the property to view the result.\nIn addition, this and further information about model checking is displayed in the log in the \"Log\" tab.\n</p>\n<p class='vspace'>\n</p><h3>Command-line</h3>\n<p>From the command-line, model checking is achieved by passing both a model file and a properties file as arguments, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock167'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=167' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The results of model checking are sent to the display and are as described above for the GUI version.\nBy default, all properties in the file are checked.\nTo model check only a single property, use the <code>-prop</code> switch.\nFor example, to check only the fourth property in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock168'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=168' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or to check only the property with <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#names'>name</a> \"safe\" in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock169'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=169' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also provide a comma-separated list of multiple properties to check,\nusing neither numerical indices or property names:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock170'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4,5,safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=170' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, the contents of a properties file can be specified directly from the command-line, using the <code>-pf</code> switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock171'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -pf 'P&gt;=0.5 [ true U&lt;=5 (s=1 &amp; a=0) ]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=171' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The switches <code>-pctl</code> and <code>-csl</code> are aliases for <code>-pf</code>.\n</p>\n<p class='vspace'>Note the use of single quotes (<code>'...'</code>) to avoid characters such as\n<code>(</code> and <code>&gt;</code> being interpreted by the command-line shell.\nSingle quotes are preferable to double quotes since PRISM properties often include double quotes, e.g. for references to labels or properties.\n</p><hr />\n<h1>Approximate Model Checking</h1>\n<p>The discrete-event simulator built into PRISM (see the section \"<a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\") can also be used to generate <em>approximate</em> results for PRISM properties, a technique often called <em>statistical model checking</em>. Essentially, this is achieved by <em>sampling</em>: generating a large number of random paths through the model, evaluating the result of the given properties on each run, and using this information to generate an approximately correct result. This approach is particularly useful on very large models when normal model checking is infeasible. This is because discrete-event simulation is performed using the PRISM language model description, without explicitly constructing the corresponding probabilistic model.\n</p>\n<p class='vspace'>Currently, statistical model checking can only be applied to <code><strong>P</strong></code> or <code><strong>R</strong></code> operators\nand does not support LTL-style path properties or <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\nThere are also a few restrictions on the modelling language features that can be used; see below for details.\n</p>\n<p class='vspace'>To use this functionality, load a model and some properties into PRISM, as described in the previous sections. To generate an approximate value for one or more properties, select them in the list, right-click and select \"Simulate\" (as opposed to \"Verify\"). As usual, it is first necessary to provide values for any undefined constants. Subsequently, a dialog appears. Here, the state from which approximate values are to be computed (i.e. from which the paths will be generated) can be selected. By default, this is the initial state of the model. The other settings in the dialog concern the methods used for simulation.\n</p>\n<p class='vspace'>PRISM supports four different methods for performing statistical model checking:\n</p>\n<div class='vspace'></div><ul><li>CI (Confidence Interval)\n</li><li>ACI (Asymptotic Confidence Interval)\n</li><li>APMC (Approximate Probabilistic Model Checking)\n</li><li>SPRT (Sequential Probability Ratio Test)\n</li></ul><p class='vspace'>The first three of these are intended primarily for \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>quantitative</a>\" properties (e.g. of the form <code><strong>P</strong>=?[...]</code>), but can also be used for \"bounded\" properties (e.g. of the form <code><strong>P</strong>&lt;p[...]</code>). The SPRT method is only applicable to \"bounded\" properties.\n</p>\n<p class='vspace'>Each method has several parameters that control its execution, i.e. the number of samples that are generated and the accuracy of the computed approximation. In most cases, these parameters are inter-related so one of them must be left unspecified and its value computed automatically based on the others. In some cases, this is done before simulation; in others, it must be done afterwards.\n</p>\n<p class='vspace'>Below, we describe each method in more detail.\nFor simplicity, we describe the case of checking a <code><strong>P</strong></code> operator.\nDetails for the case of an <code><strong>R</strong></code> operator can be found in [<a class='wikilink' href='References.html#Nim10'>Nim10</a>].\n</p>\n<div class='vspace'></div><h3>CI (Confidence Interval) Method</h3>\n<p>The CI method gives a <em>confidence interval</em> for the approximate value generated for a <code><strong>P</strong>=?</code> property, based on a given <em>confidence level</em> and the number of samples generated.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Width\" (<em>w</em>)\n</li><li>\"Confidence\" (<em>alpha</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Let <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated.\nThe confidence interval is [<em>Y-w</em>,<em>Y+w</em>], i.e. <em>w</em> gives the half-width of the interval.\nThe confidence level, which is usually stated as a percentage, is 100(1-<em>alpha</em>)%.\nThis means that the actual value <em>X</em> should fall into the confidence interval [<em>Y-w</em>,<em>Y+w</em>] 100(1-<em>alpha</em>)% of the time.\n</p>\n<p class='vspace'>To determine, for example, the width <em>w</em> for given <em>alpha</em> and <em>N</em>,\nwe use <em>w</em> = <em>q</em> * sqrt(<em>v</em> / <em>N</em>) where\n<em>q</em> is a quantile, for probability 1-<em>alpha</em>/2, from the Student's t-distribution with <em>N</em>-1 degrees of freedom and <em>v</em> is (an estimation of) the variance for <em>X</em>.\nSimilarly, we can determine the required number of iterations, from <em>w</em> and <em>alpha</em>,\nas N = (<em>v</em> * <em>q</em><sup>2</sup>)/<em>w</em><sup>2</sup>, where <em>q</em> and <em>v</em> are as before.\n</p>\n<p class='vspace'>For a bounded property  <code><strong>P</strong>~p[...]</code>, the (Boolean) result is determined according to the generated approximation for the probability. This is not the case, however, if the threshold <em>p</em> falls within the confidence interval [<em>Y-w</em>,<em>Y+w</em>], in which case no value is returned.\n</p>\n<div class='vspace'></div><h3>ACI (Asymptotic Confidence Interval) Method</h3>\n<p>The ACI method works in exactly same fashion as the CI method, except that it uses the Normal distribution to approximate the Student's t-distribution when determining the confidence interval. This is appropriate when the number of samples is large (because we can get a reliable estimation of the variance from the samples) but may be less accurate for small numbers of samples.\n</p>\n<div class='vspace'></div><h3>APMC (Approximate Probabilistic Model Checking) Method</h3>\n<p>The APMC method, based on [<a class='wikilink' href='References.html#HLMP04'>HLMP04</a>], offers a probabilistic guarantee on the accuracy of the  approximate value generated for a <code><strong>P</strong>=?</code> property, based on the Chernoff-Hoeffding bound.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Approximation\" (<em>epsilon</em>)\n</li><li>\"Confidence\" (<em>delta</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Letting <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated, we have:\n</p>\n<div class='vspace'></div><ul><li>Prob(|<em>Y</em>-<em>X</em>| &gt; <em>epsilon</em>) &lt; <em>delta</em>\n</li></ul><p class='vspace'>where the parameters are related as follows:\n<em>N</em> = ln(2/<em>delta</em>) / 2<em>epsilon</em><sup>2</sup>.\nThis imposes certain restrictions on the parameters,\nnamely that <em>N</em>(<em>epsilon</em><sup>2</sup>) &#8805; ln(2/delta)/2.\n</p>\n<p class='vspace'>In similar fashion to the CI/ACI methods, the APMC method can be also be used for bounded properties such as <code><strong>P</strong>~p[...]</code>, as long as the threshold <em>p</em> falls outside the interval [<em>Y-epsilon</em>,<em>Y+epsilon</em>].\n</p>\n<div class='vspace'></div><h3>SPRT (Sequential Probability Ratio Test) Method</h3>\n<p>The SPRT method is specifically for bounded properties, such as <code><strong>P</strong>~p[...]</code> and is based on <em>acceptance sampling</em> techniques [<a class='wikilink' href='References.html#YS02'>YS02</a>]. It uses Wald's sequential probability ratio test (SPRT), which generates a succession of samples, deciding on-the-fly when an answer can be given with a sufficiently high confidence.\n</p>\n<p class='vspace'>The parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Indifference\" (<em>delta</em>)\n</li><li>\"Type I/II error\" (<em>alpha</em>/<em>beta</em>)\n</li></ul><p class='vspace'>Consider a property of the form <code><strong>P</strong>&#8805;p[...]</code>. The parameter <em>delta</em> is used as the half-width of an <em>indifference region</em> [p-delta,p+delta]. PRISM will attempt to determine whether either the hypothesis <code><strong>P</strong>&#8805;(p+delta)[...]</code> or <code><strong>P</strong>&#8804;(p-delta)[...]</code> is true, based on which it will return either <code>true</code> or <code>false</code>, respectively. The parameters <em>alpha</em> and <em>beta</em> represent the probability of the occurrence of a <em>type I error</em> (wrongly accepting the first hypothesis) and a <em>type II error</em> (wrongly accepting the second hypothesis), respectively. For simplicity, PRISM assigns the same value to both <em>alpha</em> and <em>beta</em>.\n</p>\n<div class='vspace'></div><h3>Maximum Path Length</h3>\n<p>Another setting that can be configured from the \"Simulation Parameters\" dialog is the maximum length of paths generated by PRISM during statistical model checking. In order to perform statistical model checking, PRISM needs to evaluate the property being checked along every generated path. For example, when checking <code>P=? [ F&lt;=10 \"end\" ]</code>, PRISM must check whether <code>F&lt;=10 \"end\"</code> is true for each path. On this example (assuming a discrete-time model), this can always be done within the first 10 steps. For a property such as <code>P=? [ F \"end\" ]</code>, however, there may be paths along which no finite fragment can show <code>F \"end\"</code> to be true or false. So, PRISM imposes a maximum path length to avoid the need to generate excessively long (or infinite) paths.\nThe default maximum length is 10,000 steps.\nIf, for a given property, statistical model checking results in one or more paths on which the property cannot be evaluated, an error is reported.\n</p>\n<div class='vspace'></div><h3>Command-line Statistical Model Checking</h3>\n<p>Statistical model checking can also be enabled from the command-line version of PRISM, by including the <code>-sim</code> switch. The default methods used are CI (Confidence Interval) for \"quantitative\" properties and SPRT (Sequential Probability Ratio Test) for \"bounded\" properties. To select a particular method, use switch <code>-simmethod &lt;method&gt;</code> where <code>&lt;method&gt;</code> is one of <code>ci</code>, <code>aci</code>, <code>apmc</code> and <code>sprt</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock172'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.pctl -prop 1 -sim -simmethod aci</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=172' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM has default values for the various simulation method parameters, but these can also be specified using the switches <code>-simsamples</code>, <code>-simconf</code>, <code>-simwidth</code> and <code>-simapprox</code>. The exact meaning of these switches for each simulation method is given in the table below.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><strong>CI</strong></td><td  align='center'><strong>ACI</strong></td><td  align='center'><strong>APMC</strong></td><td  align='right'><strong>SPRT</strong></td></tr>\n<tr ><td  align='center'><code>-simsamples</code></td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='right'>n/a</td></tr>\n<tr ><td  align='center'><code>-simconf</code></td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='right'>\"Type I/II error\"</td></tr>\n<tr ><td  align='center'><code>-simwidth</code></td><td  align='center'>\"Width\"</td><td  align='center'>\"Width\"</td><td  align='center'>n/a</td><td  align='right'>\"Indifference\"</td></tr>\n<tr ><td  align='center'><code>-simapprox</code></td><td  align='center'>n/a</td><td  align='center'>n/a</td><td  align='center'>\"Approximation\"</td><td  align='right'>n/a</td></tr>\n</table>\n<p class='vspace'>The maximum length of simulation paths is set with switch <code>-simpathlen</code>.\n</p>\n<div class='vspace'></div><h3>Limitations</h3>\n<p>Currently, the simulator does not support every part of the PRISM modelling languages. For example, it does not handle models with multiple initial states or with <code><strong>system</strong>...<strong>endsystem</strong></code> definitions.\n</p>\n<p class='vspace'>It is also worth pointing out that statistical model checking techniques are not well suited to models that exhibit nondeterminism, such as MDPs. This because the techniques rely on generation of <em>random</em> paths, which are not well defined for a MDP. PRISM does allow statistical model checking to be performed on an MDP, but does so by simply resolving nondeterministic choices in a (uniformly) random fashion (and displaying a warning message). Currently PTAs are not supported by the simulator.\n</p><hr />\n<h1>Computing Steady-state And Transient Probabilities</h1>\n<p>If the model is a CTMC or DTMC, it is possible to compute corresponding vectors of\nsteady-state or transient probabilities directly\n(rather than indirectly by analysing a property which requires their computation).\nFrom the GUI, select an option from the \"Model | Compute\" menu.\nFor transient probabilities, you will be asked to supply the\ntime value for which you wish to compute probabilities.\nFrom the command-line, add the <code>-steadystate</code> (or <code>-ss</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock173'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=173' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for steady-state probabilities or the <code>-transient</code> (or <code>-tr</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock174'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=174' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for transient probabilities, again specifying a time value in the latter case.\nThe probabilities are computed for all states of the model and displayed,\neither on the screen (from the command-line) or in the log (from the GUI).\n</p>\n<p class='vspace'>To instead export the vector of computed probabilities to a file, use the \"Model | Compute/export\" option from the GUI, or the <code>-exportsteadystate</code> (or <code>-exportss</code>) and <code>-exporttransient</code> (or <code>-exporttr</code>) switches from the command-line:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock175'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss -exportss poll2-ss.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=175' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the command-line, you can request that the probability vectors exported are in Matlab format by adding the <code>-exportmatlab</code> switch.\n</p>\n<div class='vspace'></div><h3>Initial probability distributions</h3>\n<p>By default, for both steady-state and transient probability computation,\nPRISM assumes that the initial probability distribution of the model is\nan equiprobable choice over the set of initial states.\nYou can override this and provide a specific initial distribution. This is done using the <code>-importinitdist</code> switch. The format for this imported distribution is identical to the ones exported by PRISM, i.e. simply a list of probabilities for all states separated by new lines. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock176'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -exporttr poll2-tr1.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -importinitdist poll2-tr1.txt -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=176' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is (essentially) equivalent to this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock177'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=177' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Ranges of time values</h3>\n<p>Finally, you can compute transient probabilities for a range of time values, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock178'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 0.1:0.01:0.2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=178' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which computes transient probabilities for the time points 0.1, 0.11, 0.12, .., 0.2. In this case, the computation is done incrementally, with probabilities for each time point being computed from the previous point for efficiency.\n</p><hr />\n<h1>Experiments</h1>\n<p>PRISM supports <em>experiments</em>, which is a way of automating multiple instances of model checking.\nThis is done by leaving one or more <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a> undefined, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock179'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=179' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This can be done for constants in the model file, the properties file, or both.\nBefore any verification can be performed, values must be provided for any such constants. In the GUI, a dialog appears in which the user is required to enter values. From the command line, the <code>-const</code> switch must be used, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock180'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=180' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To run an experiment, provide a <em>range</em> of values for one or more of the constants. Model checking will be performed for all combinations of the constant values provided. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock181'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4:6,T=60:10:100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=181' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>N=4:6</code> means that values of 4,5 and 6 are used for <code>N</code>,\nand <code>T=60:10:100</code> means that values of 60, 70, 80, 90 and 100 (i.e. steps of 10) are used for <code>T</code>.\n</p>\n<p class='vspace'>For convenience, constant specifications can be split across separate instances of the <code>-const</code> switch, if desired.\nYou can also specify double-valued constants as fractions rather than decimals. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock182'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9 -const p=1/3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=182' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, the same thing can be achieved by selecting a single property,\nright clicking on it and selecting \"New experiment\"\n(or alternatively using the popup menu in the \"Experiments\" panel).\nValues or ranges for each undefined constant can then be supplied in the resulting dialog.\nDetails of the new experiment and its progress are shown in the panel.\nTo stop the experiment before it has completed, click the red \"Stop\" button and it will\nhalt after finishing the current iteration of model checking.\nOnce the experiment has finished, right clicking on the experiment produces a pop-up menu,\nfrom which you can view the results of the experiment or export them to a file.\n</p>\n<p class='vspace'>For experiments based on properties which return numerical results, you can also use the GUI to plot graphs of the results.\nThis can be done either before the experiment starts, by selecting the \"Create graph\" tick-box in the dialog used to create the experiment\n(in fact this box is ticked by default), or after the experiment's completion, by choosing \"Plot results\" from the pop-up menu on the experiment.\nA dialog appears, where you can choose which constant (if there are more than one) to use for the x-axis of the graph,\nand for which values of any other constants the results should be plotted.\nThe graph will appear in the panel below the list of experiments.\nRight clicking on a graph and selecting \"Graph options\" brings up a dialog from which many properties of the graph can be configured.\nFrom the pop-up menu of a graph, you can also choose to print the graph (to a printer or Postscript file)\nor export it in a variety of formats:\nas an image (PNG or JPEG),\nas an encapsulated Postscript file (EPS),\nin an XML-based format (for reloading back into PRISM),\nor as code which can be used to generate the graph in Matlab.\n</p>\n<p class='vspace'>Approximate computation of quantitive results obtained with the <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>simulator</a> can also be used on experiments. In the GUI, select the \"Use Simulation\" option when defining the parameters for the experiment. From the command-line, just add the <code>-sim</code> switch as usual.\n</p>\n<p class='vspace'><a name='exportresults' id='exportresults'></a>\n</p><h3>Exporting results</h3>\n<p>You can export all the results from an experiment to a file or to the screen. From the command-line, use the <code>-exportresults</code> switch, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock183'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=183' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send to output file <code>res.txt</code>, or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock184'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=184' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send the results straight to the screen. From the GUI, right click on the experiment and select \"Export results\".\n</p>\n<p class='vspace'>The default behaviour is to export a <em>list</em> of results in <em>text</em> form, using tabs to separate items. The above examples produce:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock185'>\r\n  <div class='sourceblocktext'><div class=\"text\">N &nbsp; &nbsp; &nbsp; T &nbsp; &nbsp; &nbsp; Result<br />\n4 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n4 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 4.707364688019771E-6<br />\n4 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 1.3126420636755292E-5<br />\n5 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n5 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 3.267731327728599E-6<br />\n5 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=185' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can change the format in which the results are exported by appending one or more comma-separated options to the end of the <code>-exportresults</code> switch, for example to export in CSV (comma-separated values) format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock186'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=186' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock187'>\r\n  <div class='sourceblocktext'><div class=\"text\">N, T, Result<br />\n4, 0, 0.0<br />\n4, 10, 4.707364688019771E-6<br />\n4, 20, 1.3126420636755292E-5<br />\n5, 0, 0.0<br />\n5, 10, 3.267731327728599E-6<br />\n5, 20, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=187' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock188'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:dataframe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=188' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock189'>\r\n  <div class='sourceblocktext'><div class=\"text\">N,T,Result<br />\n4,0,0<br />\n4,10,4.70736468802e-06<br />\n4,20,1.31264206368e-05<br />\n5,0,0<br />\n5,10,3.26773132773e-06<br />\n5,20,8.34357506036e-06</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=189' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also add the <code>matrix</code> option, to export the results as one or more 2D matrices, rather than a list.\nThis is particularly useful if you want to create a surface plot from results that vary over two constants.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock190'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv,matrix</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=190' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock191'>\r\n  <div class='sourceblocktext'><div class=\"text\">&quot;N\\T&quot;<br />\n, 0.0, 10.0, 20.0<br />\n4, 0.0, 4.707364688019771E-6, 1.3126420636755292E-5<br />\n5, 0.0, 3.267731327728599E-6, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=191' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>matrix</code> option is also available in normal (non-CSV) mode.\n</p>\n<p class='vspace'>You can also export results in the form of comments, used by PRISM's <a class='urllink' href='https://github.com/prismmodelchecker/prism/wiki/Regression-Testing'>regression testing</a> functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock192'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:comment</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=192' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock193'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// RESULT (N=4,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=10): 4.707364688019771E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=20): 1.3126420636755292E-5</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=10): 3.267731327728599E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=20): 8.343575060356386E-6</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=193' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, it is also possible to <em>import</em> previously exported results (in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format).\n</p>\n<p class='vspace'>A related option is the <code>-exportvector &lt;file&gt;</code> switch, useful in general contexts, not for experiments.\nThis exports the results for all states of the model\n(typically, the log just displays the result for the initial state, unless a <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> has been used)\nto the the file <code>file</code>.\n</p><hr />\n<h1>Strategies</h1>\n<p>Properties to be model checked on MDPs (and their variants, such as POMDPs or IMDPs) usually quantify over <em>strategies</em> (or <em>policies</em>) of the model, i.e., over the different possible ways that nondeterminism can be resolved in the model.\nFor example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock194'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=194' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>determines the maximum probability, over all strategies, of reaching a state satisfying the label <code>\"goal\"</code>. When checking such properties, you can also ask PRISM to generate a corresponding (optimal) strategy, which yields this maximum probability when followed. The strategy can then be viewed, exported or simulated.\n</p>\n<p class='vspace'><strong>Note:</strong> For consistency across models, PRISM now uses the terminology <em>strategy</em> (rather than alternatives such as <em>policy</em>). In older versions of the tool, these were referred to as <em>adversaries</em>. Currently, the newer (and more extensive) <em>strategy generation</em> functionality is implemented just for the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>\"explicit\"</a> model checking engine,\nwhich is used automatically if strategy generation is requested.\nThe old <em>adversary generation</em> functionality (see below) still exists for the \"sparse\" engine, but will be updated in the future.\n</p>\n<p class='vspace'><strong>Generating strategies</strong>. Optimal strategies can be generated either from the command-line or the graphical user interface (GUI). For the former, use the <code>-exportstrat</code> switch. Simple examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock195'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat stdout</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.tra</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=195' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, you can trigger strategy generation by ticking the \"Generate strategy\" box either on the popup menu that appears when you right-click a property, or from the \"Strategies\" menu at the top. As long as it is supported, a strategy will be then generated once \"Verify\" is clicked.\n</p>\n<p class='vspace'>From the same menu(s), you can then\n</p>\n<div class='vspace'></div><ul><li>export the strategy to a file\n</li><li>view the strategy by printing it in the log\n</li><li>explore the strategy in the simulator\n</li></ul><p class='vspace'><strong>Strategy export types</strong>. Strategies can be viewed or exported in several different formats:\n</p>\n<p class='vspace'>(i) <em>Action list</em>. This is a list of the action taken in each state of the model, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock196'>\r\n  <div class='sourceblocktext'><div class=\"text\">(0,0):east<br />\n(0,1):north<br />\n(0,2):north<br />\n(1,0):south<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=196' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where states, by default, are shown as a tuple of variable values.\n</p>\n<p class='vspace'>(ii) <em>Induced model</em>. This is a representation of the model that is induced when the strategy is applied. There are two \"modes\" for this export. The first (and default) is \n<em>reduce</em>, which removes the nondeterminism resolved by the strategy (e.g., an MDP becomes a DTMC). This can be useful to re-import the model back into PRISM and analyse the induced model. The second is <em>restrict</em>, which shows the original model but with a restricted set of choices (e.g., an MDP with just one choice in each state). In each case, the transitions of the induced model are presented as a <code>.tra</code> file (as for normal <a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>model export</a>), e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock197'>\r\n  <div class='sourceblocktext'><div class=\"text\">9 11<br />\n0 5 1 east<br />\n1 10 1 north<br />\n2 15 0.9 north<br />\n2 16 0.1 north<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=197' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>(iii) <em>Dot file</em>. This is, like the previous format, a view of the model induced by the strategy, but in <a class='urllink' href='http://www.graphviz.org'>Dot</a> format, which allows it to be visualised.\n</p>\n<p class='vspace'><strong>Configuring strategy export</strong>. \nAs hinted in the command-line examples above, the <code>-exportstrat</code> switch uses the file extension to determine the preferred format: if the strategy is exported to a file with extension <code>.tra</code> or <code>.dot</code>, then it uses an induced model or Dot file, respectively. Otherwise, the default is an action list. You can specify the desired format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock198'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=actions</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=198' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Further options can be added, e.g., to specify whether an induced model is exported in \"restrict\" or \"reduce\" mode:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock199'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced,mode=restrict</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=199' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A full list of available options is as follows:\n</p>\n<div class='vspace'></div><ul><li><code>type</code> (<code>actions</code>, <code>induced</code> or <code>dot</code>): the type of strategy export to use (action list, induced model or Dot file)\n</li><li><code>mode</code> (<code>restrict</code> or <code>reduce</code>): when exporting as an induced model or Dot file, whether to \"restrict\" or \"reduce\" the model (see above); the default is \"restrict\"\n</li><li><code>reach</code> (<code>true</code> or <code>false</code>): whether to restrict the strategy to states that are reachable when it is applied to the model (this is currently only used for exporting induced models and Dot files, and the default value is false and true, respectively, in these two cases)\n</li><li><code>states</code> (<code>true</code> or <code>false</code>): whether to show states, rather than state indices, for actions lists or Dot files; this is true by default\n</li><li><code>obs</code> (<code>true</code> or <code>false</code>): for partially observable models, whether to merge observationally equivalent states; this is true by default\n</li></ul><p class='vspace'><strong>Strategy types</strong>. PRISM generates several types of strategies. The simplest are <em>memoryless deterministic</em> strategies, which pick a single action in each state, as in the examples above. For some query types (e.g., step-bounded properties, or LTL-based properties), <em>finite-memory</em> strategies are generated, where an additional memory value is used. For these, induced models or Dot files are most useful since they will also show how the memory values are updated as the strategy is executed. Note that, in these cases, the state indices of the strategy will correspond to the product model constructed during model checking, not the original model. The product model can be exported using the <code>-exportprodtrans</code> and <code>-exportprodstates</code> switches.\n</p>\n<p class='vspace'><strong>Adversary generation</strong>. As mentioned above, the \"sparse\" model checking engine still includes older so-called \"adversary generation\" functionality. This can be used to export the induced model to a file using the <code>-exportadv</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock200'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadv adv.tra -s</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadvmdp adv.tra -s</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=200' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where the <code>-exportadv</code> and <code>-exportadvmdp</code> export a DTMC and an MDP, respectively, i.e., corresponding to the \"reduce\" and \"restrict\" modes described above.\nFrom the GUI, change the \"Adversary export\" option (under the \"PRISM\" settings) from \"None\" to \"DTMC\" or \"MDP\". You can also change the filename for the export adversary which, by default, is <code>adv.tra</code> as in the example above.\n</p><hr />\n<h1>Support For PEPA Models</h1>\n<p>For CTMCs, PRISM also accepts model descriptions in the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='References.html#Hil96'>Hil96</a>].\nThe tool compiles such descriptions into the PRISM language and then constructs the model as normal.\nThe language accepted by the PEPA to PRISM compiler is actually a subset of PEPA.\nThe restrictions applied to the language are firstly that component identifiers can only be bound to sequential components\n(formed using prefix and choice and references to other sequential components only).\nSecondly, each local state of a  sequential component must be named.  For example, we would rewrite:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).(b,s).P;\n</li></ul><p class='vspace'>as:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).P';\n</li><li>P' = (b,s).P;\n</li></ul><p class='vspace'>Finally, active/active synchronisations are not allowed since the PRISM \ndefinition of these differs from the PEPA definition.  Every PEPA \nsynchronisation must have exactly one active component.\nSome examples of PEPA model descriptions which can be imported into PRISM\ncan be found in the <code>prism-examples/pepa</code> directory.\n</p>\n<p class='vspace'>From the command-line version of PRISM, add the <code>-importpepa</code> switch and the model will be treated as a PEPA description.\nFrom the GUI, select \"Model | Open model\" and then choose \"PEPA models\"\non the \"Files of type\" drop-down menu.\nAlternatively, select \"Model | New | PEPA model\" and either type a description from scratch\nor paste in an existing one from elsewhere.\nOnce the PEPA model has been successfully parsed by PRISM,\nyou can view the corresponding PRISM code (as generated by the PEPA-to-PRISM compiler)\nby selecting menu option \"Model | View | Parsed PRISM model\".\n</p><hr />\n<h1>Support For SBML</h1>\n<p>PRISM includes a (prototype) tool to translate specifications in <a class='urllink' href='http://sbml.org/'>SBML</a> (Systems Biology Markup Language) to model descriptions in the PRISM language. SBML is an XML-based format for representing models of biochemical reaction networks. The translator currently works with Level 2 Version 1 of the SBML specification, details of which can be found <a class='urllink' href='http://sbml.org/documents/'>here</a>.\n</p>\n<p class='vspace'>Since PRISM is a tool for analysing discrete-state systems, the translator is designed for SBML files intended for discrete stochastic simulation. A useful set of such files can be found in the CaliBayes <a class='urllink' href='http://code.google.com/p/dsmts/'>Discrete Stochastic Model Test Suite</a>. There are also many more SBML files available in the <a class='urllink' href='http://www.ebi.ac.uk/biomodels/'>BioModels Database</a>.\n</p>\n<p class='vspace'>We first give a simple example of an SBML file and its PRISM translation. We then give some more precise details of the translation process.\n</p>\n<div class='vspace'></div><h3>Example</h3>\n<p>An SBML file comprises a set of <em>species</em> and a set of <em>reactions</em> which they undergo. Below is the SBML file for the simple reversible reaction: <strong>Na + Cl &#8596; Na<sup>+</sup> + Cl<sup>-</sup></strong>, where there are initially 100 Na and Cl atoms and no ions, and the base rates for the forwards and backwards reactions are 100 and 10, respectively.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock201'>\r\n  <div class='sourceblocktext'><div class=\"xml\"><span class=\"re1\">&lt;?xml</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1.0&quot;</span> <span class=\"re0\">encoding</span>=<span class=\"st0\">&quot;UTF-8&quot;</span><span class=\"re2\">?&gt;</span><br />\n<span class=\"re1\">&lt;sbml</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.sbml.org/sbml/level2&quot;</span> <span class=\"re0\">metaid</span>=<span class=\"st0\">&quot;_000000&quot;</span> <span class=\"re0\">level</span>=<span class=\"st0\">&quot;2&quot;</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; <span class=\"re1\">&lt;model</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;nacl&quot;</span> <span class=\"re0\">name</span>=<span class=\"st0\">&quot;Na+Cl&quot;</span><span class=\"re2\">&gt;</span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;compartment</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;compartment&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na_plus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl_minus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactions<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>forwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;100&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>backwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na_plus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl_minus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;10&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactions<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; <span class=\"re1\">&lt;/model<span class=\"re2\">&gt;</span></span><br />\n<span class=\"re1\">&lt;/sbml<span class=\"re2\">&gt;</span></span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=201' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And here is the resulting PRISM code:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock202'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// File generated by automatic SBML-to-PRISM conversion</span><br/>\n<span class=\"prismcomment\">// Original SBML file: nacl.xml</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">MAX_AMOUNT</span> = <span class=\"prismnum\">100</span>;<br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction forwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">forwards_rate</span> = <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// forwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction backwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">backwards_rate</span> = <span class=\"prismnum\">10</span>; <span class=\"prismcomment\">// backwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na</span><br/>\n<br/>\n\t<span class=\"prismident\">na</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">na</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na</span> &lt;= <span class=\"prismident\">na_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl</span><br/>\n<br/>\n\t<span class=\"prismident\">cl</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">cl</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl</span> &lt;= <span class=\"prismident\">cl_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na_plus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_plus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na_plus</span><br/>\n<br/>\n\t<span class=\"prismident\">na_plus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_plus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na_plus</span> &lt;= <span class=\"prismident\">na_plus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">na_plus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl_minus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_minus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl_minus</span><br/>\n<br/>\n\t<span class=\"prismident\">cl_minus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_minus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl_minus</span> &lt;= <span class=\"prismident\">cl_minus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">cl_minus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reaction rates</span><br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">reaction_rates</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reward structures (one per species)</span><br/>\n<br/>\n<span class=\"prismcomment\">// 1</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 2</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 3</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na_plus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na_plus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 4</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl_minus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl_minus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=202' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the latter, we can use PRISM to generate a simple plot of the expected amount of Na and Na+ over time (using both model checking and a single random trace from the simulator):\n</p>\n<div class='vspace'></div><div class='img imgcaption'><a class='urllink' href='../uploads/sbml_ex_graph.png'><img src='../uploads/sbml_ex_graph.png' alt='' /></a><br /><span class='caption'><strong>Expected amount of Na/Na+ at time T</strong></span></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Using the translator</h3>\n<p>At present, the SBML-to-PRISM translator is included in the PRISM code-base, but not integrated into the application itself.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock203'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=203' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are using a binary (rather than source code) distribution of PRISM, replace <code>classes</code> with <code>lib/prism.jar</code> in the above.\n</p>\n<p class='vspace'>Alternatively (on Linux or Mac OS X), ensure <code>prism</code> is in your path and then save the script below as an executable file called <code>sbml2prism</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock204'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#!/bin/sh</span><br />\n<br />\n<span class=\"co0\"># Startup script for SBML-to-PRISM translator</span><br />\n<br />\n<span class=\"co0\"># Launch using main PRISM script</span><br />\n<span class=\"re2\">PRISM_MAINCLASS</span>=<span class=\"st0\">&quot;prism.SBML2Prism&quot;</span><br />\n<span class=\"kw3\">export</span> PRISM_MAINCLASS<br />\nprism <span class=\"st0\">&quot;$@&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=204' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Then use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock205'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">sbml2prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=205' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The following PRISM properties file will also be useful:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock206'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">c</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismident\">c</span>}=? [<span class=\"prismkeyword\">I</span>=<span class=\"prismident\">T</span>]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=206' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This contains a single property which, based on the reward structures in the PRISM model generated by the translator, means \"the expected amount of species <em>c</em> at time <em>T</em>\". The constant <em>c</em> is an integer index which can range between 1 and <em>N</em>, where <em>N</em> is the number of species in the model. To view the expected amount of each species over time, create an <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiment</a> in PRISM which varies <em>c</em> from 1 to <em>N</em> and <em>T</em> over the desired time range.\n</p>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Details of the translation</h3>\n<p>The basic structure of the translation process is as follows:\n</p>\n<div class='vspace'></div><ul><li>Each <em>species</em> in the SBML file is represented by a <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>module</a> in the resulting PRISM file. This module, which (where possible) retains the SBML species id as its name, contains a single <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variable</a> whose value represents the amount of the species present. A corresponding <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structure</a> for computing the expected amount of the species at a given time instant is also created. Species for which the <code>boundaryCondition</code> flag is set to <code>true</code> in the SBML file do not have a corresponding module.\n<div class='vspace'></div></li><li>Each <em>reaction</em> in the SBML file is associated with a unique <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation action label</a>. The module for each species which takes part in the reaction will include a synchronous <a class='wikilink' href='../ThePRISMLanguage/Commands.html'>command</a> to represent this. An additional PRISM module called <code>reaction_rates</code> stores the expression representing the rate of each reaction (from the corresponding <code>kineticLaw</code> section in the SBML file). Reaction stoichiometry information is respected but must be provided in the scalar <code>stoichiometry</code> field of a <code>speciesReference</code> element, not in a separate <code>StoichiometryMath</code> element.\n<div class='vspace'></div></li><li>Each <em>parameter</em> in the SBML file, either global to the file or specific to a reaction, becomes a <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constant</a> in the PRISM file. If a value for this parameter is given, it used. If not, the constant is left as undefined.\n</li></ul><p class='vspace'>As described above, this translation process is designed for discrete systems and so the amount of each species in the model is represented by an integer variable. It is therefore assumed that the initial amount for each species specified in the SBML file is also given as an integer. If this is not the case, then the values will need to be scaled accordingly first.\n</p>\n<p class='vspace'>Furthermore, since PRISM is primarily a model checking (rather than simulation) tool, it is important that the amount of each species also has an upper bound (to ensure a finite state space). When model checking, the efficiency (or even feasibility) of the process is likely to be very sensitive to the upper bound(s) chosen. When using the discrete-event simulation functionality of PRISM, this is not the case and the bounds can can be set much higher. By default the translator uses an upper bound of 100 (which is increased if the initial amount exceeds this). A different value can specified through a second command-line argument as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock207'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml 1000 &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=207' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, upper bounds can be modified manually after the translation process.\n</p>\n<p class='vspace'>Finally, The following aspects of SBML files are not currently supported and are ignored during the translation process:\n</p>\n<div class='vspace'></div><ul><li>compartments\n</li><li>events/triggers\n</li></ul><hr />\n<h1>Explicit Model Import</h1>\n<p>It is also possible to construct models in PRISM through direct specification of their transition matrix.\nTwo formats for explicit model import are currently supported:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \"<code>.tra</code>\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li></ul><p class='vspace'>Presently, this functionality is only supported in the command-line version of the tool, usually using the <code>-importmodel</code> switch.\nIn a similar fashion to <code>-exportmodel</code> switch, the type of import is usually determined from the file extension.\n</p>\n<p class='vspace'>For UMB, all model info is contained in a single file. An example of import is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock208'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=208' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For the plain text files (<code>.tra</code> etc.), various options are possible.\nTo just import the core part of the model (the transition function) use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock209'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=209' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM tries to determine the model type from the format of the <code>.tra</code> file,\nbut if this does not work, the model type can be overwritten using the <code>-dtmc</code>, <code>-ctmc</code> and <code>-mdp</code> switches.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock210'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=210' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Using the same formats as for <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>model export</a>, other parts of the model can also be imported:\n</p>\n<div class='vspace'></div><ul><li><code>.lab</code> - labels\n</li><li><code>.srew</code>, <code>.trew</code> - rewards: states, transitions\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>Here is an example of also importing labels and states:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock211'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra,sta,lab</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=211' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If state information is not imported, a single zero-indexed variable <code>x</code> is assumed.\n</p>\n<p class='vspace'>Note also that, since details about the initial state(s) of a model are not preserved in the <code>.tra</code> file,\nbut are included in the labels file, this should also be used to designate a particular initial state for a model.\nOtherwise, state 0 is assumed to be the initial state or,\nif state information is imported, the state in which all variables take their minimum value is used.\n</p>\n<p class='vspace'>Use the extension <code>.all</code> to import from any matching files with appropriate extensions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock212'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=212' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this case, you can omit the <code>-importmodel</code> switch and just specify the <code>.all</code>-ended filename, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock213'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=213' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Efficiency</h3>\n<p>Please note, for PRISM's symbolic model construction/engines, which are often used by default,\nthis explicit method of constructing models in PRISM is typically less efficient than using the PRISM language.\nThis is because the underlying data structures used to represent the model\nfunction better when there is high-level structure and regularity to exploit.\nYou may want to switch to the \"explicit\" engine:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock214'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=214' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The situation can also be alleviated to a certain extent for the symbolic implementations by importing\nthe <code>.sta</code> file, since the composition of the states reintroduces some regularity\n(although is still typically inefficient to construct).\n</p>\n<p class='vspace'>\n</p><h3>Other options</h3>\n<p>In a similar style to PRISM's <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'><code>-exportmodel</code></a> switch, while <code>-importmodel</code> is usually the most convenient, you can also specify each part separately, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock215'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importtrans poll2.tra -importstates poll2.sta -importlabels poll2.lab -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=215' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>There are also <code>-importstaterewards</code> and <code>-impottransrewards</code> switches.\nYou can import multiple reward structures using multiple instances of the these switches.\nIf present in the rewards files (see the appendix \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\"),\nthe names of the reward structures are read too.\n</p>\n<p class='vspace'><br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Configuring PRISM</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>The operation of PRISM can be configured in a number of ways. From the GUI, select \"Options\" from the main menu to bring up the \"Options\" dialog. The settings are grouped under several tabs. Those which affect the basic model checking functionality of the tool are under the heading \"PRISM\". Separate settings are available for the simulator and various aspects of the GUI (the model editor, the property editor and the log).\n</p>\n<p class='vspace'>User options and settings for the GUI are saved in a file locally and reused. Currently the \"Options\" dialog in the GUI represents the easiest way to modify the settings, but the settings file is in a simple textual format and can also be edited by hand. To restore the default options for PRISM, click \"Load Defaults\" and then \"Save Options\" from the \"Options\" dialog in the GUI. Alternatively, delete the settings file re-launch the GUI. The location of the settings file depends on the operating system. As of PRISM 4.5, it is stored in:\n</p>\n<div class='vspace'></div><ul><li><code>$HOME/.prism</code> (if the settings file was already created by an older version of PRISM)\n</li><li><code>$XDG_CONFIG_HOME/prism.settings</code> (on Linux, if that environment variable is set)\n</li><li><code>$HOME/.config/prism.settings</code> (on Linux, if <code>$XDG_CONFIG_HOME</code> is not set)\n</li><li><code>$HOME/Library/Preferences/prism.settings</code> (on Mac OS)\n</li><li><code>.prism</code> in the user's home directory, e.g. <code>C:\\Documents and Settings\\username</code> (on Windows)\n</li></ul><p class='vspace'>From the command-line version of PRISM, options are controlled by switches. A full list can be displayed by typing:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock216'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=216' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For some switches, whose format is not straightforward, there is additional help available on the command-line, using <code>-help switch</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock217'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -help const</span><br/>\n<span style=\"font-weight:bold;\">prism -help simpath</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportresults</span><br/>\n<span style=\"font-weight:bold;\">prism -help exportmodel</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=217' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The settings file is <em>ignored</em> by the command-line version (unlike earlier versions of PRISM, where it was used). You can, however, request that the settings file <em>is</em> read, using the <code>-settings</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock218'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -settings ~/.prism</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=218' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the following sections, we give a brief description of the most important configuration options available.\n</p>\n<div class='vspace'></div><hr />\n<h1>Computation Engines</h1>\n<h3>Computation engines</h3>\n<p>PRISM contains four main <em>engines</em>,\nwhich implement the majority of its model checking functionality:\n</p>\n<div class='vspace'></div><ul><li>\"MTBDD\"\n</li><li>\"sparse\"\n</li><li>\"hybrid\"\n</li><li>\"explicit\"\n</li></ul><p class='vspace'>The first three of these engines are either wholly or partly <em>symbolic</em>,\nmeaning that they use data structures such as\nbinary decision diagrams (BDDs) and multi-terminal BDDs (MTBDDs).\nFor these three engines, the process of\nconstructing a probabilistic model (DTMC, MDP or CTMC)\nis performed in a symbolic fashion,\nrepresenting the model as an MTBDD.\nSubsequent numerical computation performed during model checking, however,\nis carried out differently for the three engines.\nThe \"MTBDD\" engine is implemented purely using MTBDDs and BDDs;\nthe \"sparse\" engine uses sparse matrices;\nand the \"hybrid\" engine uses a combination of the other two.\nThe \"hybrid\" engine is described in [<a class='wikilink' href='References.html#KNP04b'>KNP04b</a>].\nFor detailed information about all three engines, see [<a class='wikilink' href='References.html#Par02'>Par02</a>].\n</p>\n<p class='vspace'>The fourth engine, \"explicit\", performs all aspects of model construction\nand model checking using <em>explicit-state</em> data structures.\nModels are typically stored as sparse matrices or variants of.\nThis engine is implemented purely in Java, unlike the other engines\nwhich make use of code/libraries implemented in C/C++.\nOne goal of the \"explicit\" engine is to provide an easily extensible model\nchecking engine without the complication of symbolic data structures,\nalthough it also has other benefits (see below).\n</p>\n<p class='vspace'>The choice of engine (\"MTBDD\", \"sparse\", \"hybrid\" or \"engine\") should not affect the results of model checking - all engines perform essentially the same calculations. In some cases, though, certain functionality is not available with all engines and PRISM will either automatically switch to an appropriate engine, or prompt you to do so.\nPerformance (time and space), however, may vary significantly and if you are using too much time/memory with one engine, it may be worth experimenting. Below, we briefly summarise the key characteristics of each engine.\n</p>\n<div class='vspace'></div><ul><li>The <strong>hybrid</strong> engine is enabled by default in PRISM. It uses a combination of <em>symbolic</em> and <em>explicit-state</em> data structures (as used in the MTBDD and sparse engines, respectively). In general it provides the best compromise between time and memory usage: it (almost) always uses less memory than the sparse engine, but is typically slightly slower. The size of model which can be handled with this engine is quite predictable. The limiting factor in terms of memory usage comes from the storage of 2-4 (depending on the computation being performed) arrays of 8-byte values, one for each state in the model. So, a typical PC can handle models with between 10<sup>7</sup> and 10<sup>8</sup> states (one vector for 10<sup>7</sup> states uses approximately 75 MB).\n<div class='vspace'></div></li><li>The <strong>sparse</strong> engine can be a good option for smaller models where model checking takes a long time. For larger models, however, memory usage quickly becomes prohibitive. As a rule of thumb, the upper limit for this engine, in terms of model sizes which can be handled, is about a factor of 10 less than the hybrid engine.\n<div class='vspace'></div></li><li>The <strong>MTBDD</strong> engine is much more unpredictable in terms of performance but, when a model exhibits a lot of structure and regularity, can be very effective. This engine has been successfully applied to extremely large structured (but non-trivial) models, in cases where the other two engines cannot be applied. The MTBDD engine often performs poorly when the model (or solutions computed from it) contain lots of distinct probabilities/rates; it performs best when there are few such values. For this reason the engine is often successfully applied to MDP models, but much less frequently to CTMCs. When using the MTBDD engine, the <em>variable ordering</em> of your model is especially important. This topic is covered in the <a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html#ordering'>FAQ</a> section.\n<div class='vspace'></div></li><li>The <strong>explicit</strong> engine is similar to the sparse engine, in that it can be a good option for relatively small models, but will not scale up to some of the models that can be handled by the hybrid or MTBDD engines. However, unlike the sparse engine, the explicit engine does not use symbolic data structures for model construction, which can be beneficial in some cases. One example is models with a potentially very large state space, only a fraction of which is actually reachable.\n</li></ul><p class='vspace'>When using the PRISM GUI, the engine to be used for model checking can be selected from the \"Engine\" option under the \"PRISM\" tab of the \"Options\" dialog. From the command-line, engines are activated using the <code>-mtbdd</code>, <code>-sparse</code>, <code>-hybrid</code> and <code>-explicit</code> (or <code>-m</code>, <code>-s</code>, <code>-h</code> and <code>-ex</code>, respectively) switches, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock219'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -m</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -s</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -h</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1000 -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=219' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note also that precise details regarding the memory usage of the current engine are displayed during model checking (from the GUI, check the \"Log\" tab). This can provide valuable feedback when experimenting with different engines.\n</p>\n<p class='vspace'>PRISM also has some basic support for automatically selecting the engine (and other settings) heuristically,\nbased on the size and type of the model, and the property being checked.\nUse, for example, <code>-heuristic speed</code> from the command-line to choose options\nwhich target computation speed rather than saving memory.\nThis is also available from the \"Heuristic\" option under the \"PRISM\" tab of the \"Options\" dialog in the GUI.\n</p>\n<div class='vspace'></div><h3>Approximate/statistical model checking</h3>\n<p>Although it is not treated as a separate \"engine\", like those above,\nPRISM also provides approximate/statistical model checking,\nwhich is based on the use of discrete-event simulation.\nFrom the GUI, this is enabled by choosing \"Simulate\" menu items or tick boxes;\nfrom the command-line, add the <code>-sim</code> switch.\nSee the \"<a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\"\nsection for more details.\n</p>\n<p class='vspace'><a name='exact' id='exact'></a>\n</p><h3>Exact model checking</h3>\n<p>Most of PRISM's model checking functionality uses numerical solution based on floating point arithmetic and, often, this uses iterative numerical methods, which are run until some user-specified precision is reached. PRISM currently has some support for \"exact\" model checking, i.e., using arbitrary precision arithmetic to provide exact numerical values. Currently, this is implemented as a special case of <a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>parametric model checking</a>, which limits is application to relatively small models. It can be used for analysing DTMCs/CTMCs (unbounded until, steady-state probabilities, reachability reward and steady-state reward) or MDPs (unbounded until and reachability rewards). You can enable this functionality using the \"Do exact model checking\" option in the GUI or using switch <code>-exact</code> from the command line.\n</p>\n<p class='vspace'><a name='pta' id='pta'></a>\n</p><h3>PTA engines</h3>\n<p>The techniques used to model check PTAs are different to the ones used for DTMCs, MDPs and CTMCs. For PTAs, PRISM currently has three distinct engines that can be used:\n</p>\n<div class='vspace'></div><ul><li>The <strong>stochastic games</strong> engine uses abstraction-refinement techniques based on stochastic two-player games [<a class='wikilink' href='References.html#KNP09c'>KNP09c</a>].\n<div class='vspace'></div></li><li>The <strong>digital clocks</strong> engine performs a discretisation, in the form of a language-level model translation, that reduces the problem to one of model checking over a finite-state MDP [<a class='wikilink' href='References.html#KNPS06'>KNPS06</a>].\n<div class='vspace'></div></li><li>The <strong>backwards reachability</strong> engine is a zone-based method based on a backwards traversal of the state space and solution of the resulting finite-state MDP [<a class='wikilink' href='References.html#KNSW07'>KNSW07</a>].\n</li></ul><p class='vspace'>The default engine for PTAs is \"stochastic games\". The engine to be used can be specified using the \"PTA model checking method\" setting in the \"PRISM\" options panel in the GUI. From the command-line, switch <code>-ptamethod &lt;name&gt;</code> should be used where <code>&lt;name&gt;</code> is either <code>games</code>, <code>digital</code> or <code>backwards</code>.\n</p>\n<p class='vspace'>The choice of engine for PTA model checking affects restrictions that imposed on both\nthe <a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>modelling language</a>\nand the types of <a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>properties</a> that can be checked.\n</p><hr />\n<h1>Solution Methods and Options</h1>\n<p>Separately from the choice of <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a>,\nPRISM often offers several different solution methods\nthat can be used for the computation of probabilities and expected costs/rewards during model checking.\nMany, but not all, of these are iterative numerical methods.\nThe choice of method (and their settings) depends on the type of analysis that is being done (i.e., what type of model and property).\n</p>\n<div class='vspace'></div><h3>Linear Equation Systems</h3>\n<p>For many properties of Markov chains\n(e.g. \"reachability\"/\"until\" properties for DTMCs and CTMCs, steady-state properties for CTMCs and \"reachability reward\" properties for DTMCs),\nPRISM solves a set of linear equation systems, for which several numerical methods are available.\nBelow is a list of the alternatives and the switches used to select them from the command-line.\nThe corresponding GUI option is \"Linear equations method\".\n</p>\n<div class='vspace'></div><ul><li>Power method: <code>-power</code> (or <code>-pow</code>, <code>-pwr</code>)\n</li><li>Jacobi method: <code>-jacobi</code> (or <code>-jac</code>)\n</li><li>Gauss-Seidel method: <code>-gaussseidel</code> (or <code>-gs</code>)\n</li><li>Backwards Gauss-Seidel method: <code>-bgaussseidel</code> (or <code>-bgs</code>)\n</li><li>JOR method (Jacobi with over-relaxation): <code>-jor</code>\n</li><li>SOR method: <code>-sor</code>\n</li><li>Backwards SOR method: <code>-bsor</code>\n</li></ul><p class='vspace'>When using the MTBDD engine, Gauss-Seidel/SOR based methods are not available.\nWhen using the hybrid engine, <em>pseudo</em> variants of Gauss-Seidel/SOR based method can also be used [<a class='wikilink' href='References.html#Par02'>Par02</a>]\n(type <code>prism -help</code> at the command-line for details of the corresponding switches).\nFor methods which use over-relaxation (JOR/SOR), the over-relaxation parameter (between 0.0 and 2.0)\ncan also be specified with option \"Over-relaxation parameter\" (switch <code>-omega &lt;val&gt;</code>).\n</p>\n<p class='vspace'>For options relating to convergence (of this and other iterative methods),\nsee the <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='mdp' id='mdp'></a>\n</p><h3>MDP Solution Methods</h3>\n<p>When analysing MDPs, there are multiple solution methods on offer.\nFor most of these, you can select them under the \"MDP solution method\" setting from the GUI,\nor use the command-line switches listed below.\nCurrently, all except value iteration are only supported by the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>explicit engine</a>.\nFor more details of the methods, see e.g. [<a class='wikilink' href='References.html#FKNP11'>FKNP11</a>] (about probabilistic verification of MDPs)\nor classic MDP texts such as [<a class='wikilink' href='References.html#Put94'>Put94</a>]).\n</p>\n<div class='vspace'></div><ul><li><strong>Value iteration</strong> (switch <code>-valiter</code>) [this is the default]\n</li><li><strong>Gauss Seidel</strong> (switch <code>-gs</code>)\n</li><li><strong>Policy iteration</strong> (switch <code>-politer</code>)\n</li><li><strong>Modified policy iteration</strong> (switch <code>-modpoliter</code>)\n</li></ul><p class='vspace'>Where the methods above use iterative numerical solution,\nyou can also use the settings under described in the <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#convergence'>Convergence</a> section below.\n</p>\n<p class='vspace'><a name='iiter' id='iiter'></a>\n</p><h3>Interval Iteration</h3>\n<p>Interval iteration [<a class='wikilink' href='References.html#HM14'>HM14</a>],[<a class='wikilink' href='References.html#BKLPW17'>BKLPW17</a>] is an alternative solution method for either MDPs or DTMCs\nwhich performs two separate instances of numerical iterative solution,\none from below and one from above. This is designed to provide clearer information\nabout the accuracy of the computed values and avoid possible problems with premature convergence.\nThis can be enabled using the switch <code>-intervaliter</code> (or <code>-ii</code>)\nor via the \"Use interval iteration\" GUI option.\nA variety of options can be configured, either using\n<code>-intervaliter:option1,option2,...</code> or by\nsetting the string \"<code>option1,option2,...</code>\" under \"Interval iteration options\" in the GUI.\nType <code>prism -help intervaliter</code> from the command-line for a list of the options\nand see [<a class='wikilink' href='References.html#BKLPW17'>BKLPW17</a>] for the details.\n</p>\n<p class='vspace'><a name='topo' id='topo'></a>\n</p><h3>Topological Value Iteration</h3>\n<p>Topological value iteration is a variant of value iteration which improves efficiency\nby analysing the graph structure of the model and using this to update the values for\nstates in an alternative order which increases the speed of convergence.\nUse switch <code>-topological</code> or GUI option \"Use topological value iteration\" to enable this.\nIn addition to standard value iteration for MDPs, the topological variant can be used to optimise\nboth interval iteration (see above) and the numerical solution of DTMCs.\n</p>\n<p class='vspace'><a name='transient' id='transient'></a>\n</p><h3>CTMC Transient Analysis</h3>\n<p>When computing transient probabilities of a CTMC\n(either <a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>directly</a> or when verifying <a class='wikilink' href='../PropertySpecification/ThePOperator.html#bounded'>time-bounded operators</a> of CSL), there are two options:\n<em>uniformisation</em> and <em>fast adaptive uniformisation</em> (FAU). These can be selected using the GUI option \"Transient probability computation method\", or using the command-line switch <code>-transientmethod &lt;name&gt;</code>, where <code>&lt;name&gt;</code> is either <code>unif</code> or <code>fau</code>.\n</p>\n<p class='vspace'><strong>Uniformisation</strong> is a standard iterative numerical method for computing transient probabilities on a CTMC, which works by reducing the problem to an analysis of a \"uniformised\" DTMC.\nAs an optimisation, when it is detected that the transient probabilities have converged, no further iterations are performed. If necessary (e.g. in case of round-off problems), this optimisation can be disabled with the \"Use steady-state detection\" option (command-line switch <code>-nossdetect</code>).\n</p>\n<p class='vspace'><a name='fau' id='fau'></a>\n<strong>Fast adaptive uniformisation</strong> (FAU) [<a class='wikilink' href='References.html#MWDH10'>MWDH10</a>] is a method to efficiently approximate transient properties of large CTMCs. The basic idea is that only the parts of the model that are relevant for the current time period are kept in memory. In more detail, starting with the initial states, in each step FAU\nexplores further states in a DTMC which is a discrete-time version of the original CTMC. By combining the\nprobabilities there with those of a certain continuous-time stochastic process (a birth process), transient properties in the original CTMC can be computed. If it turns out that the probability of being in some state in the DTMC is below a given threshold, this state is removed from the model explored so far. After a given number of steps, which corresponds to the number of steps which are likely to happen within the time bound, the exploration can be stopped. In the implementation in PRISM [<a class='wikilink' href='References.html#DHK13'>DHK13</a>], FAU can be used to compute transient probability distributions and to model check the following types of non-nested CSL formulas: time-bounded until, instantaneous reward, cumulative reward.\n</p>\n<p class='vspace'>The following options can be used to configure FAU:\n</p>\n<div class='vspace'></div><ul><li>\"FAU epsilon\" (switch <code>-fauepsilon &lt;x&gt;</code>): FAU analyses the DTMC for a number of iterations such that the probability of more steps being relevant is below this value. The default is 1e-6.\n<div class='vspace'></div></li><li>\"FAU cut off delta\" (switch <code>-faudelta &lt;x&gt;</code>): States that have a lower probability than this value are discarded. The default is 1e-12.\n<div class='vspace'></div></li><li>\"FAU array threshold\" (switch <code>-fauarraythreshold &lt;x&gt;</code>): After this number of steps without any new states being explored or discarded, FAU will switch to a faster, fixed-size data structure until further states have to be explored or discarded. The default is 100.\n<div class='vspace'></div></li><li>\"FAU time intervals\" (switch <code>-fauintervals &lt;x&gt;</code>): In some cases, it is advantageous to divide the time interval the analysis is done for into several smaller intervals. This option dictates the number of (equal length) intervals used for this split. The default is 1, meaning that only one time interval is used.\n<div class='vspace'></div></li><li>\"FAU initial time interval\" (switch <code>-fauinitival &lt;x&gt;</code>): It is also possible to specify an additional initial time interval which is handled separately from the rest of the time. This is often advantageous, because in this interval certain parameters of the model can be explored, which can subsequently be used to speed up the computation of the remaining time interval. The default for this option is 1.0.\n</li></ul><p class='vspace'><a name='convergence' id='convergence'></a>\n</p><h3>Convergence</h3>\n<p>Common to all of these methods is the way that PRISM checks convergence, i.e. decides when to terminate the iterative methods because the answers have converged sufficiently. This is done by checking when the maximum difference between elements in the solution vectors from successive iterations drops below a given threshold (or, in the case of interval iteration, if the difference of the elements in the iterations from above and below are below the threshold).\nThe default value for this threshold is 10<sup>-6</sup> but it can be altered with the \"Termination epsilon\" option (switch <code>-epsilon &lt;val&gt;</code>). The way that the maximum difference is computed can also be varied:\neither \"relative\" or \"absolute\" (the default is \"relative\"). This can be changed using the \"Termination criteria\" option (command-line switches <code>-relative</code> and <code>-absolute</code>, or <code>-rel</code> and <code>-abs</code> for short).\n</p>\n<p class='vspace'>Also, the maximum number of iterations performed is given an upper limit\nin order to trap the cases when computation will not converge.\nThe default limit is 10,000 but can be changed with the \"Termination max. iterations\" option (switch <code>-maxiters &lt;val&gt;</code>). Computations that reach this upper limit will trigger an error during model checking to alert the user to this fact.\n</p><hr />\n<h1>Automata Generation</h1>\n<p>When PRISM performs verification of <a class='wikilink' href='../PropertySpecification/ThePOperator.html#ltl'>LTL formulas</a>, it does so by converting the formula into an automaton (such as a deterministic Rabin automaton) and then analysing a larger product model, constructed from the model being verified and the omega automaton. For this reason, the size of the automaton has an important effect on the efficiency of verification.\n</p>\n<p class='vspace'>By default PRISM uses a port of the <a class='urllink' href='http://www.ltl2dstar.de/'>ltl2dstar</a> library to construct these automata. But it also allows the use of external LTL-to-automata converters producing deterministic automata through support for the <a class='urllink' href='http://adl.github.io/hoaf/'>Hanoi Omega Automaton</a> (HOA) format. From the command line, an example of this is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock220'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=220' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-ltl2datool</code> switch specifies the location of the program to be executed to perform the LTL-to-automaton conversion. This will be called by PRISM as \"<code>exec</code> <code>in-file</code> <code>out-file</code>\", where <code>exec</code> is the executable, <code>in-file</code> is the name of a file containing the LTL formula to be converted and <code>out-file</code> is the name of a file where the resulting automaton should be written, in HOA format. Typically, the executable will be a script. Here is a simple example (called as <code>hoa-ltl2dstar-for-prism</code> in the above example), which calls an external copy of <code>ltl2dstar</code> in the required fashion (assuming that the <code>ltl2dstar</code> and <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a>  executables are located in the current directory or on the PATH).\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock221'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#! /bin/bash</span><br />\nltl2dstar <span class=\"re5\">--output</span>=automaton <span class=\"re5\">--output-format</span>=hoa <span class=\"st0\">&quot;$1&quot;</span> <span class=\"st0\">&quot;$2&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=221' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM is known to work with these HOA-enabled tools:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>\n</li><li><a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>\n</li><li><a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>\n</li><li><a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>\n</li></ul><p class='vspace'>and contains ready-made scripts for calling them in the <code>etc/scripts/hoa</code> directory of the distribution:\n</p>\n<div class='vspace'></div><ul><li><code>hoa-ltl2dstar-for-prism</code> <br />  (<a class='urllink' href='http://ltl2dstar.de/'>ltl2dstar</a>, using <a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>, <a class='urllink' href='http://www.lsv.ens-cachan.fr/~gastin/ltl2ba/'><code>ltl2ba</code></a> or <a class='urllink' href='https://github.com/xblahoud/ltl3dra'>LTL3BA</a> as the LTL-to-NBA tool as the LTL-to-NBA tool)\n</li><li><code>hoa-ltl2tgba-for-prism</code> <br />  (<a class='urllink' href='https://spot.lre.epita.fr/'>Spot</a>'s <a class='urllink' href='https://spot.lre.epita.fr/ltl2tgba.html'><code>ltl2tgba</code></a>)\n</li><li><code>hoa-ltl3dra-for-prism</code> <br />  (<a class='urllink' href='https://github.com/xblahoud/ltl3dra'>ltl3dra</a>)\n</li><li><code>hoa-rabinizer-for-prism</code> <br />  (<a class='urllink' href='https://www7.in.tum.de/~kretinsk/rabinizer4.html'>Rabinizer</a>'s <code>ltl2dra</code>)\n</li></ul><p class='vspace'>See the files themselves for details of any configuration required, possible options and for a reminder of the PRISM command-line arguments required.\n</p>\n<p class='vspace'>There is also a <code>hoa-rabinizer-for-prism.bat</code> script for connecting to Rabinizer on Windows.\n</p>\n<p class='vspace'>The <code>-ltl2dasyntax</code> switch is used to specify the textual format for passing the LTL formula to the external converter (i.e., in the file <code>out-file</code>). The options are:\n</p>\n<div class='vspace'></div><ul><li><code>lbt</code> - LBT format\n</li><li><code>spin</code> - SPIN format\n</li><li><code>spot</code> - Spot format\n</li><li><code>rabinizer</code> - Rabinizer format\n</li></ul><p class='vspace'>Typical usage is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock222'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl2tgba-for-prism -ltl2dasyntax lbt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-ltl3dra-for-prism -ltl2dasyntax spin</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -pf \"P=? [ G F x=1 ]\" -ltl2datool hoa-rabinizer-for-prism -ltl2dasyntax rabinizer</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=222' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, configuring the external LTL converter is done with the two options \n\"Use external LTL-&gt;DA tool\" and \"LTL syntax for external LTL-&gt;DA tool\".\n</p>\n<p class='vspace'>Another related option is \"All path formulas via automata\" (command-line switch <code>-pathviaautomata</code>), which forces construction of an automata\nwhen computing the probability of a path formula, even if it is not needed. This is primarily intended for debugging/testing, not regular use.\n</p>\n<p class='vspace'>As mentioned above, PRISM's external LTL-to-automaton interfacing works using the\n<a class='urllink' href='http://adl.github.io/hoaf/'>HOA</a> format\n(and, in particular,  using the <a class='urllink' href='http://automata.tools/hoa/jhoafparser/'><code>jhoafparser</code></a> HOA parser.\nCurrently, PRISM can handle automata in HOA format that are \ndeterministic and complete, with state-based acceptance.\nAutomata with transition-based acceptance are converted to state-based acceptance by PRISM.\nFor DTMC and  CTMC model checking, generic acceptance conditions are supported, i.e., \nanything that can be specified as an <code>Acceptance:</code> header in HOA format. \nFor MDP model checking, currently Rabin and generalized Rabin acceptance \nspecified via the <code>acc-name:</code> header are supported. See the <a class='urllink' href='http://adl.github.io/hoaf/'>HOA format specification</a> for details.\n</p>\n<div class='vspace'></div><hr />\n<h1>Other Options</h1>\n<h3>Output options</h3>\n<p>To increase the amount of information displayed by PRISM (in particular, to display lists of states and probability vectors), you can use the \"Verbose output\" option (activated with command-line switch <code>-verbose</code> or <code>-v</code>). To display additional statistics about MTBDDs after model construction, use the \"Extra MTBDD information\" option (switch <code>-extraddinfo</code>) and, to view MTBDD sizes during the process of reachability, use option \"Extra reachability information\" (switch <code>-extrareachinfo</code>).\n</p>\n<div class='vspace'></div><h3>Fairness</h3>\n<p>Sometimes, model checking of properties for MDPs requires fairness constraints to be taken into account.\nSee e.g. [<a class='wikilink' href='References.html#BK98'>BK98</a>],[<a class='wikilink' href='References.html#Bai98'>Bai98</a>] for more information.\nTo enable the use of fairness constraints (for <code><strong>P</strong></code> operator properties), use the <code>-fair</code> switch.\n</p>\n<div class='vspace'></div><h3>Probability/rate checks</h3>\n<p>By default, when constructing a model, PRISM checks that all probabilities and rates are within acceptable ranges (i.e. are between 0 and 1, or are non-negative, respectively). For DTMCs and MDPs, it also checks that the probabilities sum up to one for each command. These checks are often very useful for highlighting user modelling errors and it is strongly recommended that you keep them enabled, however if you need to disable them you can do so via option \"do prob checks?\" in the GUI or command-line switch <code>-noprobchecks</code>.\nYou can also change the level of precision used to check that probabilities sum to 1 using the option \"Probability sum threshold\" (or command-line switch <code>-sumroundoff</code>.\n</p>\n<div class='vspace'></div><h3>CUDD memory</h3>\n<p>CUDD, the underlying BDD and MTBDD library used in PRISM has an upper memory limit. By default, this limit is 1 GB. If you are working on a machine with significantly more memory this and PRISM runs out of memory when model checking, it may help to change this. To set the limit, from the command-line, use the <code>-cuddmaxmem</code> switch. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock223'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -cuddmaxmem 2g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=223' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Above, <code>g</code> denotes GB. You can also use <code>m</code> for MB.\nYou can also the CUDD maximum memory setting from the options panel in the GUI, but you will need to close and restart the GUI (saving the settings as you do) for this to take effect.\n</p>\n<p class='vspace'><a name='javamaxmem' id='javamaxmem'></a>\n</p><h3>Java memory</h3>\n<p>The Java virtual machine (JVM) used to execute PRISM also has upper memory limits. Sometimes this limit will be exceeded and you will see an error of the form <code>java.lang.OutOfMemory</code>. To resolve this problem, you can increase this memory limit. On Unix, Linux or Mac OS X platforms, this can done by using the <code>-javamaxmem</code> switch, passed either to the command-line script <code>prism</code> or the GUI launcher <code>xprism</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock224'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javamaxmem 4g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javamaxmem 4g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=224' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>each set the limit to 4GB. Alternatively, you set the environment variable PRISM_JAVAMAXMEM before running PRISM. For example, under a <code>bash</code> shell:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock225'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVAMAXMEM=4g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVAMAXMEM</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=225' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you get an error of the form <code>java.lang.StackOverflowError</code>, then you can try increasing the stack size of the JVM.\nOn Unix, Linux or Mac OS X platforms, this can done by using the <code>-javastack</code> switch or the <code>PRISM_JAVASTACKSIZE</code> environment variable.\nExamples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock226'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javastack 1g big_model.pm</span><br/>\n<span style=\"font-weight:bold;\">xprism -javastack 1g big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=226' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock227'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">PRISM_JAVASTACKSIZE=1g</span><br/>\n<span style=\"font-weight:bold;\">export PRISM_JAVASTACKSIZE</span><br/>\n<span style=\"font-weight:bold;\">prism big_model.pm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=227' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are running PRISM on Windows you will have to do make adjustments to Java memory manually, by modifying the <code>prism.bat</code> or <code>xprism.bat</code> scripts.\nTo set the memory to 4GB, for example, add <code> -Xmx4g</code> to the list of arguments in the call to <code>java</code> or <code>javaw</code> at the end of the file.\nTo change the stack size to 1GB, add <code>-Xss1g</code>.\n</p>\n<div class='vspace'></div><h3>Other Java options</h3>\n<p>If you want to pass additional switches to the JVM used to run PRISM, you can use the <code>-javaparams</code> switch.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock228'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -javaparams \"-XX:AutoBoxCacheMax=100000000 -Xmn2g\" -javamaxmem 12g</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=228' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Precomputation</h3>\n<p>By default, PRISM's probabilistic model checking algorithms use an initial <em>precomputation</em> step which uses graph-based techniques to efficient detect trivial cases where probabilities are 0 or 1. This can often result in improved performance and also reduce round-off errors. Occasionally, though, you may want to disable this step for efficiency (e.g. if you know that there are no/few such states and the precomputation process is slow). This can be done with the <code>-nopre</code> switch. You can also disable the individual algorithms for probability 0/1 using switches <code>-noprob0</code> and <code>-noprob1</code>.\n</p>\n<div class='vspace'></div><h3>Time-outs</h3>\n<p>The command-line version of PRISM has a time-out option, specified using the switch <code>-timeout &lt;n&gt;</code>.\nThis causes the program to exit after <code>&lt;n&gt;</code> seconds if it has not already terminated by that point.\nThis is particularly useful for benchmarking scenarios where you wish to ignore runs of PRISM that exceed a certain length of time.\n<br /><br />\n</p><hr />\n<h1><span class='big'>References</span></h1>\n<hr />\n<ul><li><a name='AD94' id='AD94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=AD94'>AD94</a>: R. Alur and D. Dill.  A theory of timed automata.  Theoretical Computer Science, 126:183-235, 1994.\n<div class='vspace'></div></li><li><a name='AH99' id='AH99'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=AH99'>AH99</a> R. Alur and T. Henzinger.  Reactive modules.  Formal Methods in System Design, 15(1):7-48, 1999.\n<div class='vspace'></div></li><li><a name='ASSB96' id='ASSB96'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=ASSB96'>ASSB96</a>: A. Aziz, K. Sanwal, V. Singhal, and R. Brayton.  Verifying continuous time Markov chains.  In R. Alur and T. Henzinger, editors, Proc. 8th International Conference on Computer Aided Verification (CAV'96), volume 1102 of LNCS, pages 269-276. Springer, 1996.\n<div class='vspace'></div></li><li><a name='Bai98' id='Bai98'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Bai98'>Bai98</a>: C. Baier.  On algorithmic verification methods for probabilistic systems, 1998.  Habilitation thesis, Fakultt fr Mathematik &amp; Informatik, Universitt Mannheim.\n<div class='vspace'></div></li><li><a name='BKLPW17' id='BKLPW17'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BKLPW17'>BKLPW17</a>: Christel Baier, Joachim Klein, Linda Leuschner, David Parker and Sascha Wunderlich. Ensuring the Reliability of Your Model Checker: Interval Iteration for Markov Decision Processes. In Proc. 28th International Conference on Computer Aided Verification (CAV'17), volume 10426 of LNCS, pages 160-180, Springer, 2017.\n<div class='vspace'></div></li><li><a name='BKH99' id='BKH99'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BKH99'>BKH99</a>: C. Baier, J.-P. Katoen, and H. Hermanns.  Approximate symbolic model checking of continuous-time Markov chains.  In J. Baeten and S. Mauw, editors, Proc. 10th International Conference on Concurrency Theory (CONCUR'99), volume 1664 of LNCS, pages 146-161. Springer, 1999.\n<div class='vspace'></div></li><li><a name='BK98' id='BK98'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BK98'>BK98</a>: C. Baier and M. Kwiatkowska.  Model checking for a probabilistic branching time logic with fairness.  Distributed Computing, 11(3):125-155, 1998.\n<div class='vspace'></div></li><li><a name='BdA95' id='BdA95'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BdA95'>BdA95</a>: A. Bianco and L. de Alfaro.  Model checking of probabilistic and nondeterministic systems.  In P. Thiagarajan, editor, Proc. 15th Conference on Foundations of Software Technology and Theoretical Computer Science (FSTTCS'95), volume 1026 of LNCS, pages 499-513. Springer, 1995.\n<div class='vspace'></div></li><li><a name='CHH13' id='CHH13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=CHH+13'>CHH+13</a>: Taolue Chen, Ernst Moritz Hahn, Tingting Han, Marta Kwiatkowska, Hongyang Qu, and Lijun Zhang.  Model repair for Markov decision processes.  In Proc. 7th International Symposium on Theoretical Aspects of Software Engineering (TASE'13), pages 85-92. IEEE, 2013.\n<div class='vspace'></div></li><li><a name='CE81' id='CE81'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=CE81'>CE81</a>: E. Clarke and A. Emerson.  Design and synthesis of synchronization skeletons using branching time temporal logic.  In Proc. Workshop on Logic of Programs, volume 131 of LNCS. Springer, 1981.\n<div class='vspace'></div></li><li><a name='DHK13' id='DHK13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=DHK13'>DHK13</a>: F. Dannenberg, E. M. Hahn, and M. Kwiatkowska.  Computing cumulative rewards using fast adaptive uniformisation.  In A. Gupta and T. Henzinger, editors, Proc. 11th Conference on Computational Methods in Systems Biology (CMSB'13), volume 8130 of LNCS, pages 33-49. Springer, 2013.\n<div class='vspace'></div></li><li><a name='FKNP11' id='FKNP11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKNP11'>FKNP11</a>: V. Forejt, M. Kwiatkowska, G. Norman, and D. Parker.  Automated verification techniques for probabilistic systems.  In M. Bernardo and V. Issarny, editors, Formal Methods for Eternal Networked Software Systems (SFM'11), volume 6659 of LNCS, pages 53-113. Springer, 2011.\n<div class='vspace'></div></li><li><a name='FKN11' id='FKN11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKN+11'>FKN+11</a>: V. Forejt, M. Kwiatkowska, G. Norman, D. Parker, and H. Qu.  Quantitative multi-objective verification for probabilistic systems.  In P. Abdulla and K. Leino, editors, Proc. 17th International Conference on Tools and Algorithms for the Construction and Analysis of Systems (TACAS'11), volume 6605 of LNCS, pages 112-127. Springer, 2011.\n<div class='vspace'></div></li><li><a name='FKP12' id='FKP12'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKP12'>FKP12</a>: V. Forejt, M. Kwiatkowska, and D. Parker.  Pareto curves for probabilistic model checking.  In S. Chakraborty and M. Mukund, editors, Proc. 10th International Symposium on Automated Technology for Verification and Analysis (ATVA'12), volume 7561 of LNCS, pages 317-332. Springer, 2012.\n<div class='vspace'></div></li><li><a name='HM14' id='HM14'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HM14'>HM14</a>: S. Haddad and B. Monmege. Reachability in MDPs: Refining convergence of value iteration. In 8th International Workshop on Reachability Problems (RP), volume 8762 of LNCS, pages 125137, Springer. 2014.\n<div class='vspace'></div></li><li><a name='HHZ11b' id='HHZ11b'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HHZ11b'>HHZ11b</a>: E. M. Hahn, H. Hermanns, and L. Zhang.  Probabilistic reachability for parametric Markov models.  International Journal on Software Tools for Technology Transfer (STTT), 13(1):3-19, 2011.\n<div class='vspace'></div></li><li><a name='HHZ11' id='HHZ11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HHZ11'>HHZ11</a>: Ernst Moritz Hahn, Tingting Han, and Lijun Zhang.  Synthesis for PCTL in parametric Markov decision processes.  In Proc. 3rd NASA Formal Methods Symposium (NFM'11), volume 6617 of LNCS. Springer, 2011.\n<div class='vspace'></div></li><li><a name='HJ94' id='HJ94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HJ94'>HJ94</a>: H. Hansson and B. Jonsson.  A logic for reasoning about time and reliability.  Formal Aspects of Computing, 6(5):512-535, 1994.\n<div class='vspace'></div></li><li><a name='HLMP04' id='HLMP04'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HLMP04'>HLMP04</a>: T. Hrault, R. Lassaigne, F. Magniette, and S. Peyronnet.  Approximate probabilistic model checking.  In Proc. 5th International Conference on Verification, Model Checking and Abstract Interpretation (VMCAI'04), volume 2937 of LNCS, pages 307-329. Springer, 2004.\n<div class='vspace'></div></li><li><a name='Hil96' id='Hil96'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Hil96'>Hil96</a>: J. Hillston.  A Compositional Approach to Performance Modelling.  Cambridge University Press, 1996.\n<div class='vspace'></div></li><li><a name='KSK76' id='KSK76'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KSK76'>KSK76</a>: J. Kemeny, J. Snell, and A. Knapp.  Denumerable Markov Chains.  Springer-Verlag, 2nd edition, 1976.\n<div class='vspace'></div></li><li><a name='KNP04b' id='KNP04b'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP04b'>KNP04b</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Probabilistic symbolic model checking with PRISM: A hybrid approach.  International Journal on Software Tools for Technology Transfer (STTT), 6(2):128-142, 2004.\n<div class='vspace'></div></li><li><a name='KNP07a' id='KNP07a'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP07a'>KNP07a</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Stochastic model checking.  In M. Bernardo and J. Hillston, editors, Formal Methods for the Design of Computer, Communication and Software Systems: Performance Evaluation (SFM'07), volume 4486 of LNCS (Tutorial Volume), pages 220-270. Springer, 2007.\n<div class='vspace'></div></li><li><a name='KNP09c' id='KNP09c'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP09c'>KNP09c</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Stochastic games for verification of probabilistic timed automata.  In J. Ouaknine and F. Vaandrager, editors, Proc. 7th International Conference on Formal Modelling and Analysis of Timed Systems (FORMATS'09), volume 5813 of LNCS, pages 212-227. Springer, 2009.\n<div class='vspace'></div></li><li><a name='KNPS06' id='KNPS06'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNPS06'>KNPS06</a>: M. Kwiatkowska, G. Norman, D. Parker, and J. Sproston.  Performance analysis of probabilistic timed automata using digital clocks.  Formal Methods in System Design, 29:33-78, 2006.\n<div class='vspace'></div></li><li><a name='KNSW07' id='KNSW07'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNSW07'>KNSW07</a>: M. Kwiatkowska, G. Norman, J. Sproston, and F. Wang.  Symbolic model checking for probabilistic timed automata.  Information and Computation, 205(7):1027-1077, 2007.\n<div class='vspace'></div></li><li><a name='MWDH10' id='MWDH10'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=MWDH10'>MWDH10</a>: F. Didier M. Mateescu, V. Wolf and T. Henzinger.  Fast adaptive uniformisation of the chemical master equation.  IET Syst Biol, 4(6):441-452, 2010.\n<div class='vspace'></div></li><li><a name='Nim10' id='Nim10'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Nim10'>Nim10</a>: V. Nimal.  Statistical Approaches for Probabilistic Model Checking.  MSc Mini-project Dissertation, Oxford University Computing Laboratory, 2010.\n<div class='vspace'></div></li><li><a name='NPS13' id='NPS13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=NPS13'>NPS13</a>: Gethin Norman, David Parker, and Jeremy Sproston.  Model checking for probabilistic timed automata.  Formal Methods in System Design, 43(2):164-190, 2013.\n<div class='vspace'></div></li><li><a name='NPZ17' id='NPZ17'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=NPZ17'>NPZ17</a>: Gethin Norman, David Parker and Xueyi Zou. Verification and Control of Partially Observable Probabilistic Systems. Real-Time Systems, 53(3):354-402, Springer, 2017.\n<div class='vspace'></div></li><li><a name='Par02' id='Par02'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Par02'>Par02</a>: D. Parker.  Implementation of Symbolic Model Checking for Probabilistic Systems.  Ph.D. thesis, University of Birmingham, 2002.\n<div class='vspace'></div></li><li><a name='Put94' id='Put94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Put94'>Put94</a>: M. Puterman.  Markov Decision Processes: Discrete Stochastic Dynamic Programming.  John Wiley and Sons, 1994.\n<div class='vspace'></div></li><li><a name='Seg95' id='Seg95'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Seg95'>Seg95</a>: R. Segala.  Modelling and Verification of Randomized Distributed Real Time Systems.  Ph.D. thesis, Massachusetts Institute of Technology, 1995.\n<div class='vspace'></div></li><li><a name='Ste94' id='Ste94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Ste94'>Ste94</a>: W. Stewart.  Introduction to the Numerical Solution of Markov Chains.  Princeton, 1994.\n<div class='vspace'></div></li><li><a name='YS02' id='YS02'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=YS02'>YS02</a>: H. Younes and R. Simmons.  Probabilistic verification of discrete event systems using acceptance sampling.  In E. Brinksma and K. Larsen, editors, Proc. 14th International Conference on Computer Aided Verification (CAV'02), volume 2404 of LNCS, pages 223-235. Springer, 2002.\n</li></ul><p class='vspace'><br /><br />\n</p><hr />\n<div class='vspace'></div><h1><span class='big'>Frequently Asked Questions</span></h1>\n<hr />\n<h1>Memory Problems</h1>\n<p><a name='crash' id='crash'></a>\n</p><h3>PRISM crashed or stopped responding. Why?</h3>\n<div class='answer' > \n<p>When PRISM crashes, the most likely cause is that it has run out of memory.\nSimilarly, if PRISM (or the machine you are running it on) becomes very slow or seems to have stopped responding, this is probably because it is using too much of your machine's memory. Probabilistic model checking, much like other formal verification techniques, can be a very resource-intensive process. It is very easy to create a seemingly simple PRISM model that requires a large amount of time and/or memory to construct and analyse. See some of the other questions in this section for tips on how to avoid this.\n</p>\n<p class='vspace'>The other possibility is that you have found a bug.\nIf PRISM crashes or freezes whilst not using all/most of the available memory (you can check this with the <code>top</code> command in a Unix/Linux terminal or the Task Manager (via Ctrl-Alt-Delete) on Windows) then please file a <a class='urllink' href='https://github.com/prismmodelchecker/prism/issues'>bug report</a>.\n</p></div>\n<p class='vspace'><a name='memout' id='memout'></a>\n</p><h3>I ran out of memory. What can I do?</h3>\n<div class='answer' > \n<p>It depends. First, you need to establish at what point in PRISM's operation, you ran out of memory. If you are running the command-line version of PRISM then the output from the tool so far should give an indication of this. If using the GUI, check the log tab for this information. If PRISM crashed because of its memory usage, the error message can be helpful. If using the GUI, you may need to start the GUI from the command-line to see any error messages.\n</p>\n<p class='vspace'>The two main steps that PRISM typically has to perform are:\n</p>\n<div class='vspace'></div><ol><li><strong>Model construction</strong> (conversion of a PRISM language description to the corresponding probabilistic model)\n</li><li><strong>Model checking/analysis</strong> (processing/analysis of a constructed probabilistic model in order to determine the result of a property or to compute steady-state/transient probabilities)\n</li></ol><p class='vspace'>Memory usage issues for each of these steps are discussed in separate sections below. In some cases the process performed prior to step 1 (<strong>model parsing</strong> - reading in a model description in the PRISM language and checking it for correctness) can also be resource intensive. This is also discussed below.\n</p>\n<p class='vspace'>If you are using the <strong>simulator</strong> to generate approximate model checking results then step 1 (model construction) is not performed and step 2 is carried out very differently. Memory consumption is not usually a problem in this case.\n</p></div>\n<p class='vspace'><a name='memout_constr' id='memout_constr'></a>\n</p><h3>I ran out of memory during model construction. What can I do?</h3>\n<div class='answer' > \n<p>If PRISM has already output this:\n</p>\r\n<div class='sourceblock ' id='sourceblock229'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Building model...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=229' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>but there is no line of the form:\n</p>\r\n<div class='sourceblock ' id='sourceblock230'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">Time for model construction: 34.3 seconds.</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=230' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>and then you get an error like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock231'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by Java Runtime Environment:</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">#  SIGSEGV (0xb) at pc=0xb5249323, pid=19298, tid=3086363536</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.6.0-b105 mixed mode, sharing)</span><br/>\n<span style=\"font-style:italic;\"># Problematic frame:</span><br/>\n<span style=\"font-style:italic;\"># C  [libdd.so+0x39323]  Cudd_Ref+0xf</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># An error report file with more information is saved as hs_err_pid19298.log</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\"># If you would like to submit a bug report, please visit:</span><br/>\n<span style=\"font-style:italic;\">#   http://java.sun.com/webapps/bugreport/crash.jsp</span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50: 19298 Aborted                 \"$PRISM_JAVA\" #$PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=231' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock232'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># An unexpected error has been detected by HotSpot Virtual Machine: </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># EXCEPTION_ACCESS_VIOLATION (0xc0000005) at pc=0x0b1c7da3, pid=2884, tid=2544 </span><br/>\n<span style=\"font-style:italic;\"># </span><br/>\n<span style=\"font-style:italic;\"># Java VM: Java HotSpot(TM) Client VM (1.5.0_06-b05 mixed mode) </span><br/>\n<span style=\"font-style:italic;\"># Problematic frame: </span><br/>\n<span style=\"font-style:italic;\"># C [dd.dll+0x7da3] </span><br/>\n<span style=\"font-style:italic;\">#</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=232' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then PRISM ran out of memory whilst trying to construct the model.\nModel construction in PRISM is performed using BDDs (binary decision diagrams) and MTBDDs (multi-terminal) BDDs which are implemented in the CUDD library.\nThe first thing to try in this case is to increase the amount of memory available to CUDD. See the entry \"CUDD memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p>\n<p class='vspace'>If increasing this memory limit does not resolve the problem, then you will need to consider ways to reduce the size of your model. You can find some tips on this in the <a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html'>PRISM Modelling</a> section. Bear in mind also that if you are having to increase the CUDD memory limit too high (e.g. close to the physical memory available on your computer) just for model construction, then it is unlikely that you will have enough memory for subsequent model checking operations.\n</p>\n<p class='vspace'>Finally, it is also worth considering the ordering of the modules and variables in your model since this can have a (in some cases dramatic) effect on the size of MTBDD representation of the model. This topic is covered in the \"<a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n</p></div>\n<p class='vspace'><a name='memout_check' id='memout_check'></a>\n</p><h3>I ran out of memory during model checking. What can I do?</h3>\n<div class='answer' > \n<p>If model construction was successfully completed (see previous question) but model checking was not, there are several things you can try. First of all, if the error message you see looks like the one in the previous question or you see a message such as\n</p>\r\n<div class='sourceblock ' id='sourceblock233'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">DD_MatrixMultiply: res is NULL</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=233' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then it may be worth increasing the memory limit for CUDD (as described above). However, if you see an error more like this:\n</p>\r\n<div class='sourceblock ' id='sourceblock234'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-style:italic;\">/home/dxp/bin/prism: line 50:  3139 Aborted                 \"$PRISM_JAVA\" $PRISM_JAVAMAXMEM -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=$PRISM_DIR/lib -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=234' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>then increasing the memory CUDD probably will not help - PRISM is just trying to allocate more memory than is physically available on your system.\n</p>\n<p class='vspace'>Here are some general tips:\n</p>\n<div class='vspace'></div><ul><li>Try experimenting with using the different <em>engines</em> in PRISM. Read the section \"<a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Configuring PRISM - Computation Engines</a>\" for details.\n<div class='vspace'></div></li><li>Look at the detailed output of PRISM for information about memory usage. If you are using the hybrid (or sparse) engine and the limiting factor in terms of memory is creation of the vectors, then you have no choice but to try and reduce the size (number of states) of your model. If you are using the MTBDD engine, it is also well worth considering the variable ordering of your model. Both topics are discussed in the \"<a class='wikilink' href='../FrequentlyAskedQuestions/PRISMModelling.html'>PRISM Modelling</a>\" section of this FAQ.\n<div class='vspace'></div></li><li>Finally, if you can find no way to reduce the size of your model and are happy to consider an approximate (rather than exact) analysis, you may wish to try using PRISM's <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>discrete-event simulation engine</a> for analysis.\n</li></ul></div>\n<p class='vspace'><a name='memout_parse' id='memout_parse'></a>\n</p><h3>I ran out of memory during model parsing. What can I do?</h3>\n<div class='answer' > \n<p>This is a less common problem and will only occur if the actual PRISM language description of your model is very large. This may be the case, for example, if you are automatically generating PRISM models in some way. Errors due to lack of memory during parsing usually look like:\n</p>\r\n<div class='sourceblock ' id='sourceblock235'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.OutOfMemoryError: Java heap space </span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=235' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>or:\n</p>\r\n<div class='sourceblock ' id='sourceblock236'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">Exception in thread \"main\" java.lang.StackOverflowError</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=236' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>You can resolve this problem by increasing the memory allocated to Java.\nSee the entry \"Java memory\" in the section \"<a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Configuring PRISM - Other Options</a>\" for details of this.\n</p></div>\n<hr />\n<h1>PRISM Modelling</h1>\n<p><a name='max_model_size' id='max_model_size'></a>\n</p><h3>What size models can PRISM handle?</h3>\n<div class='answer' > \n<p>There is no definitive answer to this. Because of PRISM's symbolic implementation, using data structures based on binary decision diagrams (BDDs), its performance can be unpredictable in this respect. There are also several factors that affect performance, including the type of model and property being checked and the engine being used (PRISM has several different engines, which have varying performance).\n</p>\n<p class='vspace'>Having said that, using the default engine in PRISM (the hybrid engine), you can normally expect to be able to handle models with up to 10^7-10^8 states on a typical PC. Using the MTBDD engine, you may be able to analyse much larger models (on some of the PRISM case studies, for example, PRISM can do numerical analysis of models with as many as 10^10 or 10^11 states). The manual has more information about PRISM's <a class='urllink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a>.\n</p></div>\n<p class='vspace'><a name='model_size' id='model_size'></a>\n</p><h3>How can I reduce the size of my model?</h3>\n<div class='answer' > \n<p>The size of a probabilistic model (i.e. the number of states/transitions) is critical to the efficiency of performing probabilistic model checking on it, since both the time and memory required to do so are often proportional to the model size. Unfortunately, it is very easy to create models that are extremely large. Below are a few general tips for reducing model size.\n</p>\n<div class='vspace'></div><ul><li>Look for variables that have unnecessarily large ranges and try to reduce them. Even if your model needs large variables, it is generally a good strategy to first get a smaller version building successfully and then scale it up afterwards.\n<div class='vspace'></div></li><li>Similarly, can you (if only temporarily) reduce the number of modules/components of your model? Start with the smallest number of components possible and then add others one by one.\n<div class='vspace'></div></li><li>Do you have any inter-dependencies between variables? For example, perhaps you have some variables which are simply functions of other variables of the model. Even if these are convenient for model checking, they can be replaced with <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>formulas or labels</a>, which do not contribute to the state space.\n<div class='vspace'></div></li><li>Do any variables include more detail than is necessary for the model? Perhaps this can be exploited in order to reduce the number of variables in your model.\n<div class='vspace'></div></li><li>More generally, are any aspects of the model not relevant to the properties that you are interested in? If so, start with a simpler, more abstract version of the model and then add more details if possible.\n</li></ul></div>\n<p class='vspace'><a name='ordering' id='ordering'></a>\n</p><h3>How can I choose a good variable ordering?</h3>\n<div class='answer' > \n<p>Because PRISM is a symbolic model checker, the amount of memory required to store the probabilistic model can vary (sometime unpredictably) according to several factors. One example is the order in which the variables of your model appear in the model file. In general, there is no definitive answer to what the best ordering is but the following heuristics are a good guide.\n</p>\n<div class='vspace'></div><ul><li>Variables which are closely related should appear close together\n<div class='vspace'></div></li><li>Variables which are related to most or all other variables should appear near the start of the ordering\n</li></ul><p class='vspace'>Variables <code>x</code> and <code>y</code> are \"related\" if, for example, the value of one is has an effect on how the other changes (e.g. <code>(y'=x+1)</code>) or if both appear together in an expression (e.g. a guard).\n</p>\n<p class='vspace'>These heuristics also apply to the ordering of <em>modules</em> within the model file.\n</p>\n<p class='vspace'>For technical details about variable ordering issues, see e.g. section 8 of [<a class='wikilink' href='References.html#HKN+03'>HKN+03</a>] or section 4.1.2 of [<a class='wikilink' href='References.html#Par02'>Par02</a>].\n</p></div>\n<p class='vspace'><a name='det_delay' id='det_delay'></a>\n</p><h3>How can I add deterministic time delays to a CTMC model?</h3>\n<div class='answer' > \n<p>All delays in a CTMC need to be modelled as <em>exponential</em> distributions. This is what makes them efficient to analyse. If you included a transition whose delay was <em>deterministic</em>, i.e. which always occurred after exactly the same delay,  the model would no longer be a CTMC.\n</p>\n<p class='vspace'>One solution to this, if your model require such a delay, is to approximate a deterministic delay with an <a class='urllink' href='http://en.wikipedia.org/wiki/Erlang_distribution'>Erlang distribution</a> (a special case of a phase-type distribution). See for example this PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock237'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mean</span> = <span class=\"prismnum\">10</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">trigger</span><br/>\n<br/>\n\t<span class=\"prismident\">i</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[]&nbsp;&nbsp;&nbsp;<span class=\"prismident\">i</span> &lt; <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">i</span> = <span class=\"prismident\">k</span> -&gt; <span class=\"prismident\">k</span>/<span class=\"prismident\">mean</span> : (<span class=\"prismident\">i</span>'=<span class=\"prismident\">i</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">main</span><br/>\n<br/>\n\t<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n\t[<span class=\"prismident\">go</span>] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=237' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In the model, the occurrence of the the go-labelled action occurs with an Erlang distribution with mean <code>mean</code> and shape <code>k</code>. The special case of <code>k</code>=1 is just an exponential distribution. The graph below shows the probability distribution of the delay, i.e. of <code>P=? [ F&lt;=T x=1 ]</code> for different values of <code>k</code>.\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/faq-erlang.jpg' alt='' /></div>\n<p class='vspace'>There is an obvious trade-off here between the accuracy (how close it is to modelling a deterministic time delay) and the resulting blow-up in the size of the model that you add this to. For <code>k</code>=1000, you can see that the shape is quite \"deterministic\" but this would increase your model size by a factor of ~1000.\n</p></div>\n<p><br /><br />----\n</p>\n<div class='vspace'></div><h1><span class='big'>Appendices</span></h1>\n<hr />\n<h1>Explicit Model Files</h1>\n<p>This appendix details the plain text file formats used by PRISM for <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>exporting</a> and <a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>importing</a> models that have already been constructed, i.e., they comprise an explicit list of states, transitions, etc. making up the model, rather than a high-level model description in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM modelling language</a>.\nBelow, we describe:\n</p>\n<div class='vspace'></div><ul><li><a href='AllOnOnePage@action=print.html#tra'>Transitions (.tra) files</a>\n</li><li><a href='AllOnOnePage@action=print.html#trarows'>Transitions (.tra) files (row form)</a>\n</li><li><a href='AllOnOnePage@action=print.html#lab'>Labels (.lab) files</a>\n</li><li><a href='AllOnOnePage@action=print.html#srew'>State rewards (.srew) files</a>\n</li><li><a href='AllOnOnePage@action=print.html#trew'>Transition rewards (.trew) files</a>\n</li><li><a href='AllOnOnePage@action=print.html#sta'>State (.sta) files</a>\n</li></ul><div class='vspace'></div><hr />\n<p class='vspace'><a name='tra' id='tra'></a>\n</p><h3>Transitions (.tra) files</h3>\n<p>These contain an explicit list of the transitions making up a probabilistic model, i.e. they are essentially a sparse matrix representation of the transition probability/rate matrix. The first line of the file contains information about the size of the model, the remaining lines contain information about transitions, one per line.\n</p>\n<p class='vspace'><strong>DTMCs and CTMCs</strong>\n</p>\n<p class='vspace'>For Markov chains the first line take the form \"<code>n m</code>\", giving the number of states (<code>n</code>) and the number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i j x</code>\" or \"<code>i j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, and <code>x</code> is the probability (for a DTMC) or rate (for a CTMC) of the transition. State indices are zero-indexed (i.e. between <code>0</code> and <code>n-1</code>). Probability/rate values are written as (positive) floating point numbers (examples: <code>0.5</code>, <code>.5</code>, <code>5.6e-6</code>, <code>1</code>). <code>a</code> is optional and gives the action label for the transition. Action labels can be present for some, all or no transitions.\n</p>\n<p class='vspace'>It is assumed that source states (rows) are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each source state.\n</p>\n<p class='vspace'>For a DTMC, the probabilities for the outgoing transitions of each state should sum to 1.\n</p>\n<p class='vspace'>Here is an example, for the (DTMC) PRISM model <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (which looks like <a class='urllink' href='../uploads/lec3.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock238'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 1 0.5<br />\n0 3 0.5<br />\n1 0 0.5<br />\n1 2 0.25<br />\n1 4 0.25<br />\n2 5 1<br />\n3 3 1<br />\n4 4 1<br />\n5 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=238' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is one for the (CTMC) PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a> (which looks like <a class='urllink' href='../uploads/poll2.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock239'>\r\n  <div class='sourceblocktext'><div class=\"text\">12 22<br />\n0 1 0.5<br />\n0 2 0.5<br />\n0 6 200<br />\n1 3 0.5<br />\n1 7 200<br />\n2 3 0.5<br />\n2 4 200<br />\n3 5 200<br />\n4 5 0.5<br />\n4 6 1<br />\n5 7 1<br />\n6 0 200<br />\n6 7 0.5<br />\n6 8 0.5<br />\n7 9 0.5<br />\n7 10 200<br />\n8 2 200<br />\n8 9 0.5<br />\n9 11 200<br />\n10 0 1<br />\n10 11 0.5<br />\n11 2 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=239' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>MDPs (or PAs)</strong>\n</p>\n<p class='vspace'>For MDPs, the format is an extension of the above\nTo clarify terminology: each <em>state</em> of the MDP contains (nondeterministic) <em>choices</em>, each of which is essentially a probability distribution over successor states that we can view as a set of <em>transitions</em>. Optionally, each choice can be labelled with an <em>action</em>.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m</code>\", giving the number of states (<code>n</code>), the total number of choices (<code>c</code>) and the total number of transitions (<code>m</code>). The remaining lines are of the form \"<code>i k j x</code>\" or \"<code>i k j x a</code>\", where <code>i</code> and <code>j</code> are the indices of the source state (row) and destination state (column) of the transition, <code>k</code> is the index of the choice that it belongs to, and <code>x</code> is the probability of the transition. <code>a</code> is optional and gives the action label for the choice of the transition. Action labels can be present for some, all or no states but, in slightly redundant fashion, the action labels, if present, must be the same for all transitions belonging to the same choice.\n</p>\n<p class='vspace'>State indices and choice indices are all zero-indexed. Probability values (as above) are written as (positive) floating point numbers and should sum to 1 for each choice.\nIt is assumed that source states (rows) and choices within states are in ascending order, but there is no assumption about the ordering of destination states (columns) within the transitions for each choice.\n</p>\n<p class='vspace'>Here is an example, for the (MDP) PRISM model <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdp.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock240'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 <br />\n1 0 0 0.7 <br />\n1 0 1 0.3 <br />\n1 1 2 0.5 <br />\n1 1 3 0.5 <br />\n2 0 2 1 <br />\n3 0 3 1 </div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=240' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and here is an action-labelled version of the same model, <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (which looks like <a class='urllink' href='../uploads/lec12mdpa.dot.pdf'>this</a>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock241'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 0 1 1 a<br />\n1 0 2 0.5 c<br />\n1 0 3 0.5 c<br />\n1 1 0 0.7 b<br />\n1 1 1 0.3 b<br />\n2 0 2 1 a<br />\n3 0 3 1 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=241' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>POMDPs</strong>\n</p>\n<p class='vspace'>The format of a <code>.tra</code> file for a POMDP is similar to an MDP,\nbut also contains information about observations.\n</p>\n<p class='vspace'>The first line of the file take the form \"<code>n c m o</code>\", where <code>n</code>, <code>c</code> and <code>m</code> are, as for MDPs, the numbers of states, choices and transitions,\nand <code>o</code> is the number of observations.\nThe lines that list transitions contain an additional integer after the transition probability\n(and before the action, if present), giving the (deterministic) observation that is made\nwhen entering the target state of that transition.\nCurrently, it is assumed that these are consistent for all states.\n</p>\n<p class='vspace'>In order to also specify the observation for the initial state,\na dummy transition line of the form <code>- - s - o</code> is used,\ngiving both the initial state <code>s</code> and its observation <code>o</code>.\n</p>\n<p class='vspace'>An example file is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock242'>\r\n  <div class='sourceblocktext'><div class=\"text\">10 16 18 4<br />\n- - 0 - 0<br />\n0 0 1 0.1 1 toss<br />\n0 0 2 0.3 1 toss<br />\n0 0 3 0.6 1 toss<br />\n1 0 4 1 2 guess1<br />\n1 1 7 1 3 guess2<br />\n1 2 7 1 3 guess3<br />\n2 0 8 1 3 guess1<br />\n2 1 5 1 2 guess2<br />\n2 2 8 1 3 guess3<br />\n3 0 9 1 3 guess1<br />\n3 1 9 1 3 guess2<br />\n3 2 6 1 2 guess3<br />\n4 0 4 1 2 loop<br />\n5 0 5 1 2 loop<br />\n6 0 6 1 2 loop<br />\n7 0 7 1 3<br />\n8 0 8 1 3<br />\n9 0 9 1 3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=242' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trarows' id='trarows'></a>\n</p><h3>Transitions (.tra) files (row form)</h3>\n<p>There is alternative format for transition matrices (see the <a class='wikilink' href='../RunningPRISM/ExportingTheModel.html#other'>rows</a> option for <code>-exportmodel</code>) where transitions for each state/choice are collated on a single line.\n</p>\n<p class='vspace'>Here is the result for the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> example from above (a DTMC):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock243'>\r\n  <div class='sourceblocktext'><div class=\"text\">6 9<br />\n0 0.5:1 0.5:3<br />\n1 0.5:0 0.25:2 0.25:4<br />\n2 1:5<br />\n3 1:3<br />\n4 1:4<br />\n5 1:2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=243' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the <a class='urllink' href='../uploads/lec12mdp.nm.html'>lec12mdp.nm</a> example (an MDP):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock244'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 <br />\n1 0.7:0 0.3:1 <br />\n1 0.5:2 0.5:3 <br />\n2 1:2 <br />\n3 1:3</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=244' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and for the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> example (an MDP with actions):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock245'>\r\n  <div class='sourceblocktext'><div class=\"text\">4 5 7<br />\n0 1:1 a<br />\n1 0.5:2 0.5:3 c<br />\n1 0.7:0 0.3:1 b<br />\n2 1:2 a<br />\n3 1:3 a</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=245' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='lab' id='lab'></a>\n</p><h3>Labels (.lab) files</h3>\n<p>These contain an explicit list of which <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> are satisfied in each state.\nThe first line lists the labels, assigning each one an index.\nThe remaining lines list indices of all states satisfying one or more labels,\nfollowed by a list of the the indices of labels that that are satisfied in it.\nThis includes the built-in labels <code>\"init\"</code> (initial states) and <code>deadlock</code> (deadlock states).\nAn example is shown below, where, for example, both <code>\"heads\"</code> and <code>\"end\"</code> are satisfied in state 2.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock246'>\r\n  <div class='sourceblocktext'><div class=\"text\">0=&quot;init&quot; 1=&quot;deadlock&quot; 2=&quot;heads&quot; 3=&quot;tails&quot; 4=&quot;end&quot;<br />\n0: 0<br />\n2: 2 4<br />\n3: 3 4</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=246' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='srew' id='srew'></a>\n</p><h3>State rewards (.srew) files</h3>\n<p>Reward files contain an (optional) header, giving the name of the reward structure that generated it\nand the type of rewards (state or transitions) stored in the file.\nFor state rewards, the information following this header is an explicit list of the (non-zero) state rewards.\nThe first line is of the form <code>n m</code> where <code>n</code> is the number of states in the model and <code>m</code> is the number of non-zero state rewards.\nThe following <code>m</code> lines are of the form <code>i r</code>, denoting that the state reward for state <code>i</code> is <code>r</code>.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get rewards in 3 states (0, 4 and 5):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock247'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure &quot;r&quot;<br />\n# State rewards<br />\n6 3<br />\n0 2<br />\n4 1<br />\n5 1</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=247' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='trew' id='trew'></a>\n</p><h3>Transition rewards (.trew) files</h3>\n<p>Files containing transition rewards, like those for state rewards, start with an (optional) header.\nThe rest of the file is formatted identically to transitions files (see <a href='AllOnOnePage@action=print.html#tra'>above</a>),\nexcept that probabilities/rates are replaced with reward values,\nand the number of transitions (the last number on the first line) is replaced with the number of non-zero transition rewards.\n</p>\n<p class='vspace'>For the <a class='urllink' href='../uploads/lec3.pm'>lec3.pm</a> (6-state) DTMC example from above, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock248'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n6 4<br />\n1 0 1<br />\n1 2 1<br />\n1 4 1<br />\n2 5 2</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=248' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And or the <a class='urllink' href='../uploads/lec12mdpa.nm.html'>lec12mdpa.nm</a> (4-state) MDP example, we get non-zero transition rewards on 4 transitions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock249'>\r\n  <div class='sourceblocktext'><div class=\"text\"># Reward structure: &quot;r&quot;<br />\n# Transition rewards<br />\n4 5 4<br />\n1 0 2 6<br />\n1 0 3 6<br />\n1 1 0 5<br />\n1 1 1 5</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=249' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<p class='vspace'><a name='sta' id='sta'></a>\n</p><h3>States (.sta) files</h3>\n<p>These contain an explicit list of the reachable states of a model. The first line is of the form <code>(v1,...,vn)</code>, listing the names of all the variables in the model in the order that they appear in the PRISM model. Subsequent lines list the values of the <code>n</code> variables in each state of the model. Each line is of the form <code>i:(x1,...,xn)</code>, where <code>i</code> is the index of the state (starting from 0) and <code>x1,...,xn</code> are the values of each variable in the state. States are ordered by their index (and, therefore, given PRISM's default behaviour, lexicographically according to the tuple of variable values).\n</p>\n<p class='vspace'>For the example PRISM model <a class='urllink' href='../uploads/poll2.sm'>poll2.sm</a>, the states file looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock250'>\r\n  <div class='sourceblocktext'><div class=\"text\">(s,a,s1,s2)<br />\n0:(1,0,0,0)<br />\n1:(1,0,0,1)<br />\n2:(1,0,1,0)<br />\n3:(1,0,1,1)<br />\n4:(1,1,1,0)<br />\n5:(1,1,1,1)<br />\n6:(2,0,0,0)<br />\n7:(2,0,0,1)<br />\n8:(2,0,1,0)<br />\n9:(2,0,1,1)<br />\n10:(2,1,0,1)<br />\n11:(2,1,1,1)</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/Main/AllOnOnePage?action=sourceblock&amp;num=250' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><br /><br />\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Contents.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Contents \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Contents.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Contents@action=edit.html'>Edit</a> - <a class='wikilink' href='Contents@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Contents</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<h1><a class='wikilink' href='Introduction.html'>Introduction</a></h1>\n<div class='vspace'></div><h1><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a></h1>\n<ul><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a></h1>\n<ul><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a></h1>\n<ul><li><a class='wikilink' href='../PropertySpecification/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../PropertySpecification/IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='../PropertySpecification/ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='../PropertySpecification/TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='../PropertySpecification/PropertiesFiles.html'>Properties Files</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a></h1>\n<ul><li><a class='wikilink' href='../RunningPRISM/Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='../RunningPRISM/LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='../RunningPRISM/SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a></h1>\n<ul><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Other Options</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='References.html'>References</a></h1>\n<div class='vspace'></div><h1><a class='wikilink' href='../Appendices/Main.html'>Appendices</a></h1>\n<ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Contents.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Contents@action=edit.html'>Edit</a> - <a class='wikilink' href='Contents@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Contents@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 13, 2013, at 11:25 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='selflink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Contents@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Contents | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Contents.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Contents@action=edit.html'>Edit</a> - <a class='wikilink' href='Contents@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Contents</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Contents@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Contents.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Contents@action=edit.html'>Edit</a> - <a class='wikilink' href='Contents@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Contents@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 13, 2013, at 11:25 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='selflink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Contents@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Contents | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Contents.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Contents@action=edit.html'>Edit</a> - <a class='wikilink' href='Contents@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Contents</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Contents@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Contents.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Contents@action=edit.html'>Edit</a> - <a class='wikilink' href='Contents@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Contents@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 13, 2013, at 11:25 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='selflink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Contents@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Main / Contents </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Contents</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<h1><a class='wikilink' href='Introduction.html'>Introduction</a></h1>\n<div class='vspace'></div><h1><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a></h1>\n<ul><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Instructions</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/CommonProblemsAndQuestions.html'>Common Problems And Questions</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a></h1>\n<ul><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a></h1>\n<ul><li><a class='wikilink' href='../PropertySpecification/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../PropertySpecification/IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='../PropertySpecification/ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='../PropertySpecification/TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='../PropertySpecification/SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='../PropertySpecification/PropertiesFiles.html'>Properties Files</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a></h1>\n<ul><li><a class='wikilink' href='../RunningPRISM/Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='../RunningPRISM/LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='../RunningPRISM/SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='../RunningPRISM/ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a></h1>\n<ul><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>Computation Engines</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html'>Solution Methods And Options</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/AutomataGeneration.html'>Automata Generation</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>Other Options</a>\n</li></ul><div class='vspace'></div><h1><a class='wikilink' href='References.html'>References</a></h1>\n<div class='vspace'></div><h1><a class='wikilink' href='../Appendices/Main.html'>Appendices</a></h1>\n<ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\n</li></ul>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Introduction.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Introduction \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Introduction.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM is a <em>probabilistic model checker</em>,\na tool for the modelling and analysis of systems which exhibit probabilistic behaviour.\nProbabilistic model checking is a <em>formal verification</em> technique.\nIt is based on the construction of a precise mathematical model of a system which is to be analysed.\nProperties of this system are then expressed formally in temporal logic\nand automatically analysed against the constructed model.\n</p>\n<p class='vspace'>PRISM has support for a wide range of probabilistic models:\n</p>\n<div class='vspace'></div><ul><li>discrete-time Markov chains (DTMCs)\n</li><li>continuous-time Markov chains (CTMCs)\n</li><li>Markov decision processes (MDPs)\n</li><li>probabilistic timed automata (PTAs)\n</li><li>partially observable Markov decision processes (POMDPs)\n</li><li>partially observable probabilistic timed automata (POPTAs)\n</li></ul><p class='vspace'>In fact, PRISM's support for MDPs extends to the more general model of \nprobabilistic automata (PAs) [<a class='wikilink' href='References.html#Seg95'>Seg95</a>], which does not require unique action names in each state.\nFor background material on these models, look at the pointers to\n<a class='urllink' href='http://www.prismmodelchecker.org/about.php'>resources</a>\non the PRISM web site.\n</p>\n<p class='vspace'>PRISM also supports non-probabilistic models, notably labelled transition systems (LTSs).\n</p>\n<p class='vspace'>Models are supplied to the tool by writing descriptions in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM language</a>, a simple, high-level modelling language.\n</p>\n<p class='vspace'>Properties of these models are written in the PRISM <a class='wikilink' href='../PropertySpecification/Main.html'>property specification language</a> which is based on temporal logic. It incorporates several well-known probabilistic temporal logics:\n</p>\n<div class='vspace'></div><ul><li>PCTL (probabilistic computation tree logic),\n</li><li>CSL (continuous stochastic logic),\n</li><li>(probabiistic) LTL (linear time logic),\n</li><li>PCTL* (which subsumes both PCTL and LTL).\n</li></ul><p class='vspace'>The property language also supports <a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>costs and rewards</a>, \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>numerical</a>\" properties, several other custom features and extensions, and also also incorporates the non-probabilistic temporal logics CTL (computation tree logic) and LTL.\n</p>\n<p class='vspace'>PRISM performs probabilistic model checking, based on exhaustive search and numerical solution, to automatically analyse such properties. It also contains a <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>discrete-event simulation</a> engine for <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Introduction.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 09:32 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='selflink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Introduction@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Introduction | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Introduction.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Introduction@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Introduction.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 09:32 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='selflink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Introduction@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Introduction | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Introduction.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Introduction@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Introduction.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 09:32 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='selflink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Introduction@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Main / Introduction </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Introduction</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM is a <em>probabilistic model checker</em>,\na tool for the modelling and analysis of systems which exhibit probabilistic behaviour.\nProbabilistic model checking is a <em>formal verification</em> technique.\nIt is based on the construction of a precise mathematical model of a system which is to be analysed.\nProperties of this system are then expressed formally in temporal logic\nand automatically analysed against the constructed model.\n</p>\n<p class='vspace'>PRISM has support for a wide range of probabilistic models:\n</p>\n<div class='vspace'></div><ul><li>discrete-time Markov chains (DTMCs)\n</li><li>continuous-time Markov chains (CTMCs)\n</li><li>Markov decision processes (MDPs)\n</li><li>probabilistic timed automata (PTAs)\n</li><li>partially observable Markov decision processes (POMDPs)\n</li><li>partially observable probabilistic timed automata (POPTAs)\n</li></ul><p class='vspace'>In fact, PRISM's support for MDPs extends to the more general model of \nprobabilistic automata (PAs) [<a class='wikilink' href='References.html#Seg95'>Seg95</a>], which does not require unique action names in each state.\nFor background material on these models, look at the pointers to\n<a class='urllink' href='http://www.prismmodelchecker.org/about.php'>resources</a>\non the PRISM web site.\n</p>\n<p class='vspace'>PRISM also supports non-probabilistic models, notably labelled transition systems (LTSs).\n</p>\n<p class='vspace'>Models are supplied to the tool by writing descriptions in the <a class='wikilink' href='../ThePRISMLanguage/Main.html'>PRISM language</a>, a simple, high-level modelling language.\n</p>\n<p class='vspace'>Properties of these models are written in the PRISM <a class='wikilink' href='../PropertySpecification/Main.html'>property specification language</a> which is based on temporal logic. It incorporates several well-known probabilistic temporal logics:\n</p>\n<div class='vspace'></div><ul><li>PCTL (probabilistic computation tree logic),\n</li><li>CSL (continuous stochastic logic),\n</li><li>(probabiistic) LTL (linear time logic),\n</li><li>PCTL* (which subsumes both PCTL and LTL).\n</li></ul><p class='vspace'>The property language also supports <a class='wikilink' href='../PropertySpecification/Reward-basedProperties.html'>costs and rewards</a>, \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>numerical</a>\" properties, several other custom features and extensions, and also also incorporates the non-probabilistic temporal logics CTL (computation tree logic) and LTL.\n</p>\n<p class='vspace'>PRISM performs probabilistic model checking, based on exhaustive search and numerical solution, to automatically analyse such properties. It also contains a <a class='wikilink' href='../RunningPRISM/DebuggingModelsWithTheSimulator.html'>discrete-event simulation</a> engine for <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Main.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Welcome \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Welcome</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Welcome to the manual for <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM</a>.\nThis document is the main source of information regarding the installation and operation of the PRISM tool. For access to other resources, such as <a class='urllink' href='http://www.prismmodelchecker.org/publications.php'>related publications</a> and details of <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>case studies</a>, or to <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>download</a> the tool itself, see the main <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<div class='vspace'></div><h3>Which version of PRISM does this manual describe?</h3>\n<p>This manual describes version <strong>4.10.1</strong>.\nIn general, the online copy of the manual corresponds to the most recent\n<a class='urllink' href='http://www.prismmodelchecker.org/download.php'>publically available</a>\nversion of PRISM (including beta versions).\nIf you need the manual for an older version of PRISM,\nuse the version included in that distribution.\n</p>\n<div class='vspace'></div><h3>How do I search the manual?</h3>\n<p>This documentation is continuously updated and is best viewed online. If you are reading this online, you can use the built-in <a class='wikilink' href='Search.html'>search</a> facility (there is a link in the grey box at the top of each page). For a nicer search interface (but possibly not 100% up-to-date index), you can also search with Google, using the search box in the banner at the top of the site.\n</p>\n<p class='vspace'>If you are browsing these pages off-line, for example using the copy distributed with the tool, you can view the whole manual on <a class='wikilink' href='AllOnOnePage.html'>one page</a> and use the search functionality of your browser.\n</p>\n<div class='vspace'></div><h3>How do I print the manual?</h3>\n<p>To print an individual page of the manual click on the \"Print\" link at the top-right hand corner of the page (in the online version) and print the page from your web browser. You can also print an entire section (see the \"View all\" link under the contents on the left) or the <a class='wikilink' href='AllOnOnePage.html'>entire manual</a> in this way.\n</p>\n<div class='vspace'></div><h3>More questions?</h3>\n<p>If you have a question about PRISM and you cannot find the answer in this manual, please use the discussion group provided. Check the\n<a class='urllink' href='http://www.prismmodelchecker.org/support/'>support</a>\nsection of the PRISM website for details.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Welcome@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='selflink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/References.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / References \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='References.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='References@action=edit.html'>Edit</a> - <a class='wikilink' href='References@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>References</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<ul><li><a name='AD94' id='AD94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=AD94'>AD94</a>: R. Alur and D. Dill.  A theory of timed automata.  Theoretical Computer Science, 126:183-235, 1994.\n<div class='vspace'></div></li><li><a name='AH99' id='AH99'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=AH99'>AH99</a> R. Alur and T. Henzinger.  Reactive modules.  Formal Methods in System Design, 15(1):7-48, 1999.\n<div class='vspace'></div></li><li><a name='ASSB96' id='ASSB96'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=ASSB96'>ASSB96</a>: A. Aziz, K. Sanwal, V. Singhal, and R. Brayton.  Verifying continuous time Markov chains.  In R. Alur and T. Henzinger, editors, Proc. 8th International Conference on Computer Aided Verification (CAV'96), volume 1102 of LNCS, pages 269-276. Springer, 1996.\n<div class='vspace'></div></li><li><a name='Bai98' id='Bai98'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Bai98'>Bai98</a>: C. Baier.  On algorithmic verification methods for probabilistic systems, 1998.  Habilitation thesis, Fakultt fr Mathematik &amp; Informatik, Universitt Mannheim.\n<div class='vspace'></div></li><li><a name='BKLPW17' id='BKLPW17'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BKLPW17'>BKLPW17</a>: Christel Baier, Joachim Klein, Linda Leuschner, David Parker and Sascha Wunderlich. Ensuring the Reliability of Your Model Checker: Interval Iteration for Markov Decision Processes. In Proc. 28th International Conference on Computer Aided Verification (CAV'17), volume 10426 of LNCS, pages 160-180, Springer, 2017.\n<div class='vspace'></div></li><li><a name='BKH99' id='BKH99'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BKH99'>BKH99</a>: C. Baier, J.-P. Katoen, and H. Hermanns.  Approximate symbolic model checking of continuous-time Markov chains.  In J. Baeten and S. Mauw, editors, Proc. 10th International Conference on Concurrency Theory (CONCUR'99), volume 1664 of LNCS, pages 146-161. Springer, 1999.\n<div class='vspace'></div></li><li><a name='BK98' id='BK98'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BK98'>BK98</a>: C. Baier and M. Kwiatkowska.  Model checking for a probabilistic branching time logic with fairness.  Distributed Computing, 11(3):125-155, 1998.\n<div class='vspace'></div></li><li><a name='BdA95' id='BdA95'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BdA95'>BdA95</a>: A. Bianco and L. de Alfaro.  Model checking of probabilistic and nondeterministic systems.  In P. Thiagarajan, editor, Proc. 15th Conference on Foundations of Software Technology and Theoretical Computer Science (FSTTCS'95), volume 1026 of LNCS, pages 499-513. Springer, 1995.\n<div class='vspace'></div></li><li><a name='CHH13' id='CHH13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=CHH+13'>CHH+13</a>: Taolue Chen, Ernst Moritz Hahn, Tingting Han, Marta Kwiatkowska, Hongyang Qu, and Lijun Zhang.  Model repair for Markov decision processes.  In Proc. 7th International Symposium on Theoretical Aspects of Software Engineering (TASE'13), pages 85-92. IEEE, 2013.\n<div class='vspace'></div></li><li><a name='CE81' id='CE81'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=CE81'>CE81</a>: E. Clarke and A. Emerson.  Design and synthesis of synchronization skeletons using branching time temporal logic.  In Proc. Workshop on Logic of Programs, volume 131 of LNCS. Springer, 1981.\n<div class='vspace'></div></li><li><a name='DHK13' id='DHK13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=DHK13'>DHK13</a>: F. Dannenberg, E. M. Hahn, and M. Kwiatkowska.  Computing cumulative rewards using fast adaptive uniformisation.  In A. Gupta and T. Henzinger, editors, Proc. 11th Conference on Computational Methods in Systems Biology (CMSB'13), volume 8130 of LNCS, pages 33-49. Springer, 2013.\n<div class='vspace'></div></li><li><a name='FKNP11' id='FKNP11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKNP11'>FKNP11</a>: V. Forejt, M. Kwiatkowska, G. Norman, and D. Parker.  Automated verification techniques for probabilistic systems.  In M. Bernardo and V. Issarny, editors, Formal Methods for Eternal Networked Software Systems (SFM'11), volume 6659 of LNCS, pages 53-113. Springer, 2011.\n<div class='vspace'></div></li><li><a name='FKN11' id='FKN11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKN+11'>FKN+11</a>: V. Forejt, M. Kwiatkowska, G. Norman, D. Parker, and H. Qu.  Quantitative multi-objective verification for probabilistic systems.  In P. Abdulla and K. Leino, editors, Proc. 17th International Conference on Tools and Algorithms for the Construction and Analysis of Systems (TACAS'11), volume 6605 of LNCS, pages 112-127. Springer, 2011.\n<div class='vspace'></div></li><li><a name='FKP12' id='FKP12'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKP12'>FKP12</a>: V. Forejt, M. Kwiatkowska, and D. Parker.  Pareto curves for probabilistic model checking.  In S. Chakraborty and M. Mukund, editors, Proc. 10th International Symposium on Automated Technology for Verification and Analysis (ATVA'12), volume 7561 of LNCS, pages 317-332. Springer, 2012.\n<div class='vspace'></div></li><li><a name='HM14' id='HM14'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HM14'>HM14</a>: S. Haddad and B. Monmege. Reachability in MDPs: Refining convergence of value iteration. In 8th International Workshop on Reachability Problems (RP), volume 8762 of LNCS, pages 125137, Springer. 2014.\n<div class='vspace'></div></li><li><a name='HHZ11b' id='HHZ11b'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HHZ11b'>HHZ11b</a>: E. M. Hahn, H. Hermanns, and L. Zhang.  Probabilistic reachability for parametric Markov models.  International Journal on Software Tools for Technology Transfer (STTT), 13(1):3-19, 2011.\n<div class='vspace'></div></li><li><a name='HHZ11' id='HHZ11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HHZ11'>HHZ11</a>: Ernst Moritz Hahn, Tingting Han, and Lijun Zhang.  Synthesis for PCTL in parametric Markov decision processes.  In Proc. 3rd NASA Formal Methods Symposium (NFM'11), volume 6617 of LNCS. Springer, 2011.\n<div class='vspace'></div></li><li><a name='HJ94' id='HJ94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HJ94'>HJ94</a>: H. Hansson and B. Jonsson.  A logic for reasoning about time and reliability.  Formal Aspects of Computing, 6(5):512-535, 1994.\n<div class='vspace'></div></li><li><a name='HLMP04' id='HLMP04'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HLMP04'>HLMP04</a>: T. Hrault, R. Lassaigne, F. Magniette, and S. Peyronnet.  Approximate probabilistic model checking.  In Proc. 5th International Conference on Verification, Model Checking and Abstract Interpretation (VMCAI'04), volume 2937 of LNCS, pages 307-329. Springer, 2004.\n<div class='vspace'></div></li><li><a name='Hil96' id='Hil96'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Hil96'>Hil96</a>: J. Hillston.  A Compositional Approach to Performance Modelling.  Cambridge University Press, 1996.\n<div class='vspace'></div></li><li><a name='KSK76' id='KSK76'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KSK76'>KSK76</a>: J. Kemeny, J. Snell, and A. Knapp.  Denumerable Markov Chains.  Springer-Verlag, 2nd edition, 1976.\n<div class='vspace'></div></li><li><a name='KNP04b' id='KNP04b'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP04b'>KNP04b</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Probabilistic symbolic model checking with PRISM: A hybrid approach.  International Journal on Software Tools for Technology Transfer (STTT), 6(2):128-142, 2004.\n<div class='vspace'></div></li><li><a name='KNP07a' id='KNP07a'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP07a'>KNP07a</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Stochastic model checking.  In M. Bernardo and J. Hillston, editors, Formal Methods for the Design of Computer, Communication and Software Systems: Performance Evaluation (SFM'07), volume 4486 of LNCS (Tutorial Volume), pages 220-270. Springer, 2007.\n<div class='vspace'></div></li><li><a name='KNP09c' id='KNP09c'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP09c'>KNP09c</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Stochastic games for verification of probabilistic timed automata.  In J. Ouaknine and F. Vaandrager, editors, Proc. 7th International Conference on Formal Modelling and Analysis of Timed Systems (FORMATS'09), volume 5813 of LNCS, pages 212-227. Springer, 2009.\n<div class='vspace'></div></li><li><a name='KNPS06' id='KNPS06'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNPS06'>KNPS06</a>: M. Kwiatkowska, G. Norman, D. Parker, and J. Sproston.  Performance analysis of probabilistic timed automata using digital clocks.  Formal Methods in System Design, 29:33-78, 2006.\n<div class='vspace'></div></li><li><a name='KNSW07' id='KNSW07'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNSW07'>KNSW07</a>: M. Kwiatkowska, G. Norman, J. Sproston, and F. Wang.  Symbolic model checking for probabilistic timed automata.  Information and Computation, 205(7):1027-1077, 2007.\n<div class='vspace'></div></li><li><a name='MWDH10' id='MWDH10'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=MWDH10'>MWDH10</a>: F. Didier M. Mateescu, V. Wolf and T. Henzinger.  Fast adaptive uniformisation of the chemical master equation.  IET Syst Biol, 4(6):441-452, 2010.\n<div class='vspace'></div></li><li><a name='Nim10' id='Nim10'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Nim10'>Nim10</a>: V. Nimal.  Statistical Approaches for Probabilistic Model Checking.  MSc Mini-project Dissertation, Oxford University Computing Laboratory, 2010.\n<div class='vspace'></div></li><li><a name='NPS13' id='NPS13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=NPS13'>NPS13</a>: Gethin Norman, David Parker, and Jeremy Sproston.  Model checking for probabilistic timed automata.  Formal Methods in System Design, 43(2):164-190, 2013.\n<div class='vspace'></div></li><li><a name='NPZ17' id='NPZ17'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=NPZ17'>NPZ17</a>: Gethin Norman, David Parker and Xueyi Zou. Verification and Control of Partially Observable Probabilistic Systems. Real-Time Systems, 53(3):354-402, Springer, 2017.\n<div class='vspace'></div></li><li><a name='Par02' id='Par02'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Par02'>Par02</a>: D. Parker.  Implementation of Symbolic Model Checking for Probabilistic Systems.  Ph.D. thesis, University of Birmingham, 2002.\n<div class='vspace'></div></li><li><a name='Put94' id='Put94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Put94'>Put94</a>: M. Puterman.  Markov Decision Processes: Discrete Stochastic Dynamic Programming.  John Wiley and Sons, 1994.\n<div class='vspace'></div></li><li><a name='Seg95' id='Seg95'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Seg95'>Seg95</a>: R. Segala.  Modelling and Verification of Randomized Distributed Real Time Systems.  Ph.D. thesis, Massachusetts Institute of Technology, 1995.\n<div class='vspace'></div></li><li><a name='Ste94' id='Ste94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Ste94'>Ste94</a>: W. Stewart.  Introduction to the Numerical Solution of Markov Chains.  Princeton, 1994.\n<div class='vspace'></div></li><li><a name='YS02' id='YS02'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=YS02'>YS02</a>: H. Younes and R. Simmons.  Probabilistic verification of discrete event systems using acceptance sampling.  In E. Brinksma and K. Larsen, editors, Proc. 14th International Conference on Computer Aided Verification (CAV'02), volume 2404 of LNCS, pages 223-235. Springer, 2002.\n</li></ul><div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='References.html'>View</a> - <a rel='nofollow'  class='wikilink' href='References@action=edit.html'>Edit</a> - <a class='wikilink' href='References@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='References@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 12:57 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='selflink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/References@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / References | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='References.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='References@action=edit.html'>Edit</a> - <a class='wikilink' href='References@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>References</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='References@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='References.html'>View</a> - <a rel='nofollow'  class='wikilink' href='References@action=edit.html'>Edit</a> - <a class='wikilink' href='References@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='References@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 12:57 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='selflink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/References@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / References | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='References.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='References@action=edit.html'>Edit</a> - <a class='wikilink' href='References@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>References</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='References@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='References.html'>View</a> - <a rel='nofollow'  class='wikilink' href='References@action=edit.html'>Edit</a> - <a class='wikilink' href='References@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='References@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 12:57 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='selflink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/References@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Main / References </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>References</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<ul><li><a name='AD94' id='AD94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=AD94'>AD94</a>: R. Alur and D. Dill.  A theory of timed automata.  Theoretical Computer Science, 126:183-235, 1994.\n<div class='vspace'></div></li><li><a name='AH99' id='AH99'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=AH99'>AH99</a> R. Alur and T. Henzinger.  Reactive modules.  Formal Methods in System Design, 15(1):7-48, 1999.\n<div class='vspace'></div></li><li><a name='ASSB96' id='ASSB96'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=ASSB96'>ASSB96</a>: A. Aziz, K. Sanwal, V. Singhal, and R. Brayton.  Verifying continuous time Markov chains.  In R. Alur and T. Henzinger, editors, Proc. 8th International Conference on Computer Aided Verification (CAV'96), volume 1102 of LNCS, pages 269-276. Springer, 1996.\n<div class='vspace'></div></li><li><a name='Bai98' id='Bai98'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Bai98'>Bai98</a>: C. Baier.  On algorithmic verification methods for probabilistic systems, 1998.  Habilitation thesis, Fakultt fr Mathematik &amp; Informatik, Universitt Mannheim.\n<div class='vspace'></div></li><li><a name='BKLPW17' id='BKLPW17'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BKLPW17'>BKLPW17</a>: Christel Baier, Joachim Klein, Linda Leuschner, David Parker and Sascha Wunderlich. Ensuring the Reliability of Your Model Checker: Interval Iteration for Markov Decision Processes. In Proc. 28th International Conference on Computer Aided Verification (CAV'17), volume 10426 of LNCS, pages 160-180, Springer, 2017.\n<div class='vspace'></div></li><li><a name='BKH99' id='BKH99'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BKH99'>BKH99</a>: C. Baier, J.-P. Katoen, and H. Hermanns.  Approximate symbolic model checking of continuous-time Markov chains.  In J. Baeten and S. Mauw, editors, Proc. 10th International Conference on Concurrency Theory (CONCUR'99), volume 1664 of LNCS, pages 146-161. Springer, 1999.\n<div class='vspace'></div></li><li><a name='BK98' id='BK98'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BK98'>BK98</a>: C. Baier and M. Kwiatkowska.  Model checking for a probabilistic branching time logic with fairness.  Distributed Computing, 11(3):125-155, 1998.\n<div class='vspace'></div></li><li><a name='BdA95' id='BdA95'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=BdA95'>BdA95</a>: A. Bianco and L. de Alfaro.  Model checking of probabilistic and nondeterministic systems.  In P. Thiagarajan, editor, Proc. 15th Conference on Foundations of Software Technology and Theoretical Computer Science (FSTTCS'95), volume 1026 of LNCS, pages 499-513. Springer, 1995.\n<div class='vspace'></div></li><li><a name='CHH13' id='CHH13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=CHH+13'>CHH+13</a>: Taolue Chen, Ernst Moritz Hahn, Tingting Han, Marta Kwiatkowska, Hongyang Qu, and Lijun Zhang.  Model repair for Markov decision processes.  In Proc. 7th International Symposium on Theoretical Aspects of Software Engineering (TASE'13), pages 85-92. IEEE, 2013.\n<div class='vspace'></div></li><li><a name='CE81' id='CE81'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=CE81'>CE81</a>: E. Clarke and A. Emerson.  Design and synthesis of synchronization skeletons using branching time temporal logic.  In Proc. Workshop on Logic of Programs, volume 131 of LNCS. Springer, 1981.\n<div class='vspace'></div></li><li><a name='DHK13' id='DHK13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=DHK13'>DHK13</a>: F. Dannenberg, E. M. Hahn, and M. Kwiatkowska.  Computing cumulative rewards using fast adaptive uniformisation.  In A. Gupta and T. Henzinger, editors, Proc. 11th Conference on Computational Methods in Systems Biology (CMSB'13), volume 8130 of LNCS, pages 33-49. Springer, 2013.\n<div class='vspace'></div></li><li><a name='FKNP11' id='FKNP11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKNP11'>FKNP11</a>: V. Forejt, M. Kwiatkowska, G. Norman, and D. Parker.  Automated verification techniques for probabilistic systems.  In M. Bernardo and V. Issarny, editors, Formal Methods for Eternal Networked Software Systems (SFM'11), volume 6659 of LNCS, pages 53-113. Springer, 2011.\n<div class='vspace'></div></li><li><a name='FKN11' id='FKN11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKN+11'>FKN+11</a>: V. Forejt, M. Kwiatkowska, G. Norman, D. Parker, and H. Qu.  Quantitative multi-objective verification for probabilistic systems.  In P. Abdulla and K. Leino, editors, Proc. 17th International Conference on Tools and Algorithms for the Construction and Analysis of Systems (TACAS'11), volume 6605 of LNCS, pages 112-127. Springer, 2011.\n<div class='vspace'></div></li><li><a name='FKP12' id='FKP12'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=FKP12'>FKP12</a>: V. Forejt, M. Kwiatkowska, and D. Parker.  Pareto curves for probabilistic model checking.  In S. Chakraborty and M. Mukund, editors, Proc. 10th International Symposium on Automated Technology for Verification and Analysis (ATVA'12), volume 7561 of LNCS, pages 317-332. Springer, 2012.\n<div class='vspace'></div></li><li><a name='HM14' id='HM14'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HM14'>HM14</a>: S. Haddad and B. Monmege. Reachability in MDPs: Refining convergence of value iteration. In 8th International Workshop on Reachability Problems (RP), volume 8762 of LNCS, pages 125137, Springer. 2014.\n<div class='vspace'></div></li><li><a name='HHZ11b' id='HHZ11b'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HHZ11b'>HHZ11b</a>: E. M. Hahn, H. Hermanns, and L. Zhang.  Probabilistic reachability for parametric Markov models.  International Journal on Software Tools for Technology Transfer (STTT), 13(1):3-19, 2011.\n<div class='vspace'></div></li><li><a name='HHZ11' id='HHZ11'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HHZ11'>HHZ11</a>: Ernst Moritz Hahn, Tingting Han, and Lijun Zhang.  Synthesis for PCTL in parametric Markov decision processes.  In Proc. 3rd NASA Formal Methods Symposium (NFM'11), volume 6617 of LNCS. Springer, 2011.\n<div class='vspace'></div></li><li><a name='HJ94' id='HJ94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HJ94'>HJ94</a>: H. Hansson and B. Jonsson.  A logic for reasoning about time and reliability.  Formal Aspects of Computing, 6(5):512-535, 1994.\n<div class='vspace'></div></li><li><a name='HLMP04' id='HLMP04'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=HLMP04'>HLMP04</a>: T. Hrault, R. Lassaigne, F. Magniette, and S. Peyronnet.  Approximate probabilistic model checking.  In Proc. 5th International Conference on Verification, Model Checking and Abstract Interpretation (VMCAI'04), volume 2937 of LNCS, pages 307-329. Springer, 2004.\n<div class='vspace'></div></li><li><a name='Hil96' id='Hil96'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Hil96'>Hil96</a>: J. Hillston.  A Compositional Approach to Performance Modelling.  Cambridge University Press, 1996.\n<div class='vspace'></div></li><li><a name='KSK76' id='KSK76'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KSK76'>KSK76</a>: J. Kemeny, J. Snell, and A. Knapp.  Denumerable Markov Chains.  Springer-Verlag, 2nd edition, 1976.\n<div class='vspace'></div></li><li><a name='KNP04b' id='KNP04b'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP04b'>KNP04b</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Probabilistic symbolic model checking with PRISM: A hybrid approach.  International Journal on Software Tools for Technology Transfer (STTT), 6(2):128-142, 2004.\n<div class='vspace'></div></li><li><a name='KNP07a' id='KNP07a'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP07a'>KNP07a</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Stochastic model checking.  In M. Bernardo and J. Hillston, editors, Formal Methods for the Design of Computer, Communication and Software Systems: Performance Evaluation (SFM'07), volume 4486 of LNCS (Tutorial Volume), pages 220-270. Springer, 2007.\n<div class='vspace'></div></li><li><a name='KNP09c' id='KNP09c'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNP09c'>KNP09c</a>: M. Kwiatkowska, G. Norman, and D. Parker.  Stochastic games for verification of probabilistic timed automata.  In J. Ouaknine and F. Vaandrager, editors, Proc. 7th International Conference on Formal Modelling and Analysis of Timed Systems (FORMATS'09), volume 5813 of LNCS, pages 212-227. Springer, 2009.\n<div class='vspace'></div></li><li><a name='KNPS06' id='KNPS06'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNPS06'>KNPS06</a>: M. Kwiatkowska, G. Norman, D. Parker, and J. Sproston.  Performance analysis of probabilistic timed automata using digital clocks.  Formal Methods in System Design, 29:33-78, 2006.\n<div class='vspace'></div></li><li><a name='KNSW07' id='KNSW07'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=KNSW07'>KNSW07</a>: M. Kwiatkowska, G. Norman, J. Sproston, and F. Wang.  Symbolic model checking for probabilistic timed automata.  Information and Computation, 205(7):1027-1077, 2007.\n<div class='vspace'></div></li><li><a name='MWDH10' id='MWDH10'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=MWDH10'>MWDH10</a>: F. Didier M. Mateescu, V. Wolf and T. Henzinger.  Fast adaptive uniformisation of the chemical master equation.  IET Syst Biol, 4(6):441-452, 2010.\n<div class='vspace'></div></li><li><a name='Nim10' id='Nim10'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Nim10'>Nim10</a>: V. Nimal.  Statistical Approaches for Probabilistic Model Checking.  MSc Mini-project Dissertation, Oxford University Computing Laboratory, 2010.\n<div class='vspace'></div></li><li><a name='NPS13' id='NPS13'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=NPS13'>NPS13</a>: Gethin Norman, David Parker, and Jeremy Sproston.  Model checking for probabilistic timed automata.  Formal Methods in System Design, 43(2):164-190, 2013.\n<div class='vspace'></div></li><li><a name='NPZ17' id='NPZ17'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=NPZ17'>NPZ17</a>: Gethin Norman, David Parker and Xueyi Zou. Verification and Control of Partially Observable Probabilistic Systems. Real-Time Systems, 53(3):354-402, Springer, 2017.\n<div class='vspace'></div></li><li><a name='Par02' id='Par02'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Par02'>Par02</a>: D. Parker.  Implementation of Symbolic Model Checking for Probabilistic Systems.  Ph.D. thesis, University of Birmingham, 2002.\n<div class='vspace'></div></li><li><a name='Put94' id='Put94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Put94'>Put94</a>: M. Puterman.  Markov Decision Processes: Discrete Stochastic Dynamic Programming.  John Wiley and Sons, 1994.\n<div class='vspace'></div></li><li><a name='Seg95' id='Seg95'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Seg95'>Seg95</a>: R. Segala.  Modelling and Verification of Randomized Distributed Real Time Systems.  Ph.D. thesis, Massachusetts Institute of Technology, 1995.\n<div class='vspace'></div></li><li><a name='Ste94' id='Ste94'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=Ste94'>Ste94</a>: W. Stewart.  Introduction to the Numerical Solution of Markov Chains.  Princeton, 1994.\n<div class='vspace'></div></li><li><a name='YS02' id='YS02'></a><a class='urllink' href='http://www.prismmodelchecker.org/bibitem.php?key=YS02'>YS02</a>: H. Younes and R. Simmons.  Probabilistic verification of discrete event systems using acceptance sampling.  In E. Brinksma and K. Larsen, editors, Proc. 14th International Conference on Computer Aided Verification (CAV'02), volume 2404 of LNCS, pages 223-235. Springer, 2002.\n</li></ul><div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Search.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Search \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Search.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Search@action=edit.html'>Edit</a> - <a class='wikilink' href='Search@action=print.html'>Print</a> - <a class='selflink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Search</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<form  class='wikisearch' action='Search.html' method='get'><input type='hidden' name='action' value='search' /><input type='text' name='q' value=''   placeholder='Search'   class='inputbox searchbox' size='40' /><input type='submit' class='inputbutton searchbutton' value='Search' /></form>\n<p class='vspace'>A search for more than one word will find pages that contain all of the words.\nUse quotation marks to search for a phrase.  Also use quotes for text with punctuation or special characters.\n</p>\n<p class='vspace'>To limit your search to a single group, enter the group name followed by a slash at the beginning of the search string (e.g., \"PmWiki/\" or \"Main/\").  To list all pages, enter a slash for the search.  \n</p>\n<div class='vspace'></div><h2><span style='font-size: 83%;'>Search examples</span></h2>\n<table border='0' cellspacing='0' width='100%' cellpadding='0' ><tr ><td  align='left'><strong>Enter</strong></td><td  align='left'><strong>To find pages containing</strong></td></tr>\n<tr ><td  align='left'>apple pie</td><td  align='left'>both 'apple' and 'pie'</td></tr>\n<tr ><td  align='left'>\"apple pie\"</td><td  align='left'>the phrase 'apple pie'</td></tr>\n<tr ><td  align='left'>pmwiki/apple</td><td  align='left'>'apple' in the PmWiki group</td></tr>\n<tr ><td  align='left'>\"pmwiki/apple\"</td><td  align='left'>the phrase 'pmwiki/apple' in all groups</td></tr>\n<tr ><td  align='left'>apple -pie</td><td  align='left'>'apple', omitting those containing 'pie'</td></tr>\n<tr ><td  align='left'>food -\"apple pie\"</td><td  align='left'>'food', omitting those containing 'apple pie'</td></tr>\n<tr ><td  align='left'>apple \"-pie\"</td><td  align='left'>the words 'apple' and '-pie'</td></tr>\n<tr ><td  align='left'>apple - pie</td><td  align='left'>'apple', '-', and 'pie'</td></tr>\n<tr ><td  align='left'>\"pie:\"</td><td  align='left'>the word 'pie' with a colon</td></tr>\n<tr ><td  align='left'>\"pie=tasty\"</td><td  align='left'>the phrase 'pie=tasty'</td></tr>\n</table>\n<p class='vspace'>Some special characters need to be enclosed in quotes, including the colon (:), equals sign (=), single quote (') and double quote(\").\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Search.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Search@action=edit.html'>Edit</a> - <a class='wikilink' href='Search@action=print.html'>Print</a> - <a class='selflink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Search@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 09, 2007, at 09:53 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Search@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Search | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Search.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Search@action=edit.html'>Edit</a> - <a class='wikilink' href='Search@action=print.html'>Print</a> - <a class='selflink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Search</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Search@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Search.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Search@action=edit.html'>Edit</a> - <a class='wikilink' href='Search@action=print.html'>Print</a> - <a class='selflink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Search@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 09, 2007, at 09:53 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Search@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Search | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Search.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Search@action=edit.html'>Edit</a> - <a class='wikilink' href='Search@action=print.html'>Print</a> - <a class='selflink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Search</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Search@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Search.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Search@action=edit.html'>Edit</a> - <a class='wikilink' href='Search@action=print.html'>Print</a> - <a class='selflink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Search@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 09, 2007, at 09:53 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Search@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Main / Search </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Search</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<form  class='wikisearch' action='Search.html' method='get'><input type='hidden' name='action' value='search' /><input type='text' name='q' value=''   placeholder='Search'   class='inputbox searchbox' size='40' /><input type='submit' class='inputbutton searchbutton' value='Search' /></form>\n<p class='vspace'>A search for more than one word will find pages that contain all of the words.\nUse quotation marks to search for a phrase.  Also use quotes for text with punctuation or special characters.\n</p>\n<p class='vspace'>To limit your search to a single group, enter the group name followed by a slash at the beginning of the search string (e.g., \"PmWiki/\" or \"Main/\").  To list all pages, enter a slash for the search.  \n</p>\n<div class='vspace'></div><h2><span style='font-size: 83%;'>Search examples</span></h2>\n<table border='0' cellspacing='0' width='100%' cellpadding='0' ><tr ><td  align='left'><strong>Enter</strong></td><td  align='left'><strong>To find pages containing</strong></td></tr>\n<tr ><td  align='left'>apple pie</td><td  align='left'>both 'apple' and 'pie'</td></tr>\n<tr ><td  align='left'>\"apple pie\"</td><td  align='left'>the phrase 'apple pie'</td></tr>\n<tr ><td  align='left'>pmwiki/apple</td><td  align='left'>'apple' in the PmWiki group</td></tr>\n<tr ><td  align='left'>\"pmwiki/apple\"</td><td  align='left'>the phrase 'pmwiki/apple' in all groups</td></tr>\n<tr ><td  align='left'>apple -pie</td><td  align='left'>'apple', omitting those containing 'pie'</td></tr>\n<tr ><td  align='left'>food -\"apple pie\"</td><td  align='left'>'food', omitting those containing 'apple pie'</td></tr>\n<tr ><td  align='left'>apple \"-pie\"</td><td  align='left'>the words 'apple' and '-pie'</td></tr>\n<tr ><td  align='left'>apple - pie</td><td  align='left'>'apple', '-', and 'pie'</td></tr>\n<tr ><td  align='left'>\"pie:\"</td><td  align='left'>the word 'pie' with a colon</td></tr>\n<tr ><td  align='left'>\"pie=tasty\"</td><td  align='left'>the phrase 'pie=tasty'</td></tr>\n</table>\n<p class='vspace'>Some special characters need to be enclosed in quotes, including the colon (:), equals sign (=), single quote (') and double quote(\").\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Welcome.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Welcome \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Welcome</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Welcome to the manual for <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM</a>.\nThis document is the main source of information regarding the installation and operation of the PRISM tool. For access to other resources, such as <a class='urllink' href='http://www.prismmodelchecker.org/publications.php'>related publications</a> and details of <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>case studies</a>, or to <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>download</a> the tool itself, see the main <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<div class='vspace'></div><h3>Which version of PRISM does this manual describe?</h3>\n<p>This manual describes version <strong>4.10.1</strong>.\nIn general, the online copy of the manual corresponds to the most recent\n<a class='urllink' href='http://www.prismmodelchecker.org/download.php'>publically available</a>\nversion of PRISM (including beta versions).\nIf you need the manual for an older version of PRISM,\nuse the version included in that distribution.\n</p>\n<div class='vspace'></div><h3>How do I search the manual?</h3>\n<p>This documentation is continuously updated and is best viewed online. If you are reading this online, you can use the built-in <a class='wikilink' href='Search.html'>search</a> facility (there is a link in the grey box at the top of each page). For a nicer search interface (but possibly not 100% up-to-date index), you can also search with Google, using the search box in the banner at the top of the site.\n</p>\n<p class='vspace'>If you are browsing these pages off-line, for example using the copy distributed with the tool, you can view the whole manual on <a class='wikilink' href='AllOnOnePage.html'>one page</a> and use the search functionality of your browser.\n</p>\n<div class='vspace'></div><h3>How do I print the manual?</h3>\n<p>To print an individual page of the manual click on the \"Print\" link at the top-right hand corner of the page (in the online version) and print the page from your web browser. You can also print an entire section (see the \"View all\" link under the contents on the left) or the <a class='wikilink' href='AllOnOnePage.html'>entire manual</a> in this way.\n</p>\n<div class='vspace'></div><h3>More questions?</h3>\n<p>If you have a question about PRISM and you cannot find the answer in this manual, please use the discussion group provided. Check the\n<a class='urllink' href='http://www.prismmodelchecker.org/support/'>support</a>\nsection of the PRISM website for details.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Welcome@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='selflink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Welcome@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Welcome | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Welcome</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Welcome@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Welcome@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='selflink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Welcome@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Welcome | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Welcome</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Welcome@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Welcome@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='selflink' href='Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='../InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='../ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='../RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='../ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='References.html'>References</a>\n</li><li><a class='wikilink' href='../FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='../Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/Main/Welcome@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | Main / Welcome </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Main</a> /\n</p><h1>Welcome</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Welcome to the manual for <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM</a>.\nThis document is the main source of information regarding the installation and operation of the PRISM tool. For access to other resources, such as <a class='urllink' href='http://www.prismmodelchecker.org/publications.php'>related publications</a> and details of <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>case studies</a>, or to <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>download</a> the tool itself, see the main <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<div class='vspace'></div><h3>Which version of PRISM does this manual describe?</h3>\n<p>This manual describes version <strong>4.10.1</strong>.\nIn general, the online copy of the manual corresponds to the most recent\n<a class='urllink' href='http://www.prismmodelchecker.org/download.php'>publically available</a>\nversion of PRISM (including beta versions).\nIf you need the manual for an older version of PRISM,\nuse the version included in that distribution.\n</p>\n<div class='vspace'></div><h3>How do I search the manual?</h3>\n<p>This documentation is continuously updated and is best viewed online. If you are reading this online, you can use the built-in <a class='wikilink' href='Search.html'>search</a> facility (there is a link in the grey box at the top of each page). For a nicer search interface (but possibly not 100% up-to-date index), you can also search with Google, using the search box in the banner at the top of the site.\n</p>\n<p class='vspace'>If you are browsing these pages off-line, for example using the copy distributed with the tool, you can view the whole manual on <a class='wikilink' href='AllOnOnePage.html'>one page</a> and use the search functionality of your browser.\n</p>\n<div class='vspace'></div><h3>How do I print the manual?</h3>\n<p>To print an individual page of the manual click on the \"Print\" link at the top-right hand corner of the page (in the online version) and print the page from your web browser. You can also print an entire section (see the \"View all\" link under the contents on the left) or the <a class='wikilink' href='AllOnOnePage.html'>entire manual</a> in this way.\n</p>\n<div class='vspace'></div><h3>More questions?</h3>\n<p>If you have a question about PRISM and you cannot find the answer in this manual, please use the discussion group provided. Check the\n<a class='urllink' href='http://www.prismmodelchecker.org/support/'>support</a>\nsection of the PRISM website for details.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/AllOnOnePage.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / All On One Page \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Property Specification</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>In order to analyse a probabilistic model which has been specified and constructed in PRISM,\nit is necessary to identify one or more <em>properties</em> of the model\nwhich can be evaluated by the tool.\nPRISM's <em>property specification language</em> subsumes several well-known probabilistic temporal logics, including PCTL, CSL, probabilistic LTL and PCTL*.\nPCTL is used for specifying properties of discrete-time models such as DTMCs or PTAs,\nand also real-time models such as PTAs; CSL is an extension of PCTL for CTMCs;\nLTL and PCTL* can be used to specify properties of \ndiscrete-time models (or untimed properties of CTMCs).\nPRISM also supports most of the (non-probabilistic) temporal logic CTL.\n</p>\n<p class='vspace'>In fact, PRISM also supports numerous additional customisations and extensions of these two logics.\nFull details of the property specifications permitted in PRISM are provided in the following sections. The presentation given here is relatively informal. For the precise syntax and semantics of the various logics, see [<a class='wikilink' href='../Main/References.html#HJ94'>HJ94</a>],[<a class='wikilink' href='../Main/References.html#BdA95'>BdA95</a>] for PCTL, [<a class='wikilink' href='../Main/References.html#ASSB96'>ASSB96</a>],[<a class='wikilink' href='../Main/References.html#BKH99'>BKH99</a>] for CSL and, for example, [<a class='wikilink' href='../Main/References.html#Bai98'>Bai98</a>] for LTL and PCTL*. You can also find various pointers to useful papers in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>Before discussing property specifications in more detail,\nit is perhaps instructive to first illustrate some typical examples of properties which PRISM can handle.\nThe following are a selection of such properties.\nIn each case, we give both the PRISM syntax and a natural language translation:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the algorithm eventually terminates successfully with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> \"<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that more than 5 errors occur within the first 100 time units is less than 0.1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismident\">num_sensors</span> &lt; <span class=\"prismident\">min_sensors</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"in the long-run, the probability that an inadequate number of sensors are operational is less than 0.01\"\n</p>\n<p class='vspace'>Note that the above properties are all assertions,\ni.e. ones to which we would expect a \"yes\" or \"no\" answer.\nThis is because all references to probabilities are associated with an upper or lower bound\nwhich can be checked to be either true or false.\nIn PRISM, we can also directly specify properties which evaluate to a numerical value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ !<span class=\"prismident\">proc2_terminate</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">proc1_terminate</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that process 1 terminates before process 2 does\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">messages_lost</span> &gt; <span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the maximum probability that more than 10 messages have been lost by time <code>T</code>\" (for an MDP/PTA)\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the long-run probability that the queue is more than 75% full\"\n</p>\n<p class='vspace'>Furthermore, PRISM makes it easy to combine such properties into more complex expressions,\ncompute their values for a range of parameters\nand plot graphs of the results using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\nThis is often a very useful way of identifying interesting\npatterns or trends in the behaviour of a system.\nSee the <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a> section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a> for many examples of this kind of analysis.\n</p><hr />\n<h1>Identifying A Set Of States</h1>\n<p>One of the most fundamental tasks when specifying properties of a model\nis to identify particular sets or classes of states of the model.\nFor example, to verify a property such as\n\"the algorithm eventually terminates successfully with probability 1\",\nit is first necessary to identify the states of the model\nwhich correspond to situations where \"the algorithm has terminated successfully\".\nIn terms of the way temporal logics are usually presented,\nthese correspond to <em>atomic propositions</em>.\n</p>\n<p class='vspace'>In PRISM, this is achieved simply by writing an <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a> in the PRISM language which evaluates to a Boolean value. This expression will typically contain references to variables (and constants) from the model to which it relates. The set of states corresponding to this expression is those for which it evaluates to <code>true</code>. We say that the expression is \"satisfied\" in these states.\n</p>\n<p class='vspace'>For example, in the property given above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>the expression <code>num_errors &gt; 5</code> is used to identify states of the model where more than 5 errors have occurred.\n</p>\n<p class='vspace'>It is also common to use <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> to identify states in this way, like <code>\"terminate\"</code> in the example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Properties can refer to <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> either from the model to which the property relates, or included in the same <a class='wikilink' href='PropertiesFiles.html'>properties file</a>.\n</p><hr />\n<h1>The P Operator</h1>\n<p>One of the most important operators in the PRISM property specification language is the <code><strong>P</strong></code> operator, which is used to reason about the probability of an event's occurrence. This operator was originally proposed in the logic PCTL but also features in the other logics supported by PRISM, such as CSL. The <code><strong>P</strong></code> operator is applicable to all types of models supported by PRISM.\n</p>\n<p class='vspace'>Informally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a model if\n\"the probability that path property <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code>\".\nA typical example of a bound would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em> is greater than 0.98\". More precisely, <code>bound</code> can be any of <code>&gt;=p</code>, <code>&gt;p</code>, <code>&lt;=p</code> or <code>&lt;p</code>,\nwhere <code>p</code> is a PRISM language expression evaluating to a double in the range [0,1].\n</p>\n<p class='vspace'>The types of path property supported by PRISM and their semantics will be discussed shortly.\n</p>\n<div class='vspace'></div><h3>Nondeterminism</h3>\n<p>For models that can exhibit nondeterministic behaviour, such as MDPs or PTAs, some additional clarifications are necessary. Whereas for fully probabilistic models such as DTMCs and CTMCs, probability measures over paths are well defined (see e.g. [<a class='wikilink' href='../Main/References.html#KSK76'>KSK76</a>] and [<a class='wikilink' href='../Main/References.html#BKH99'>BKH99</a>], respectively), for nondeterministic models a probability measure can only be feasibly defined once all nondeterminism has been removed.\n</p>\n<p class='vspace'>Hence, the actual meaning of the property <code>P bound [ pathprop ]</code> in these cases is: \n\"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code> <em>for all possible resolutions of nondeterminism</em>\".\nThis means that, properties using the <code><strong>P</strong></code> operator then effectively reason about the\n<em>minimum</em> or <em>maximum</em> probability, over all possible resolutions of nondeterminism,\nthat a certain type of behaviour is observed.\nThis depends on the bound attached to the <code><strong>P</strong></code> operator:\na lower bound (<code>&gt;</code> or <code>&gt;=</code>) relates to minimum probabilities\nand an upper bound (<code>&lt;</code> or <code>&lt;=</code>) to maximum probabilities.\n</p>\n<div class='vspace'></div><h3>Quantitative properties</h3>\n<p>It is also very often useful to take a <em>quantitative</em> approach to probabilistic model checking, computing the actual probability that some behaviour of a model is observed,\nrather than just verifying whether or not the probability is above or below a given bound.\nHence, PRISM allows the <code><strong>P</strong></code> operator to take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These properties return a numerical rather than a Boolean value.\nThe <a class='wikilink' href='TheSOperator.html'>S</a> and <a class='wikilink' href='Reward-basedProperties.html'>R</a> operators, discussed later, can also be used in this way.\n</p>\n<p class='vspace'>As mentioned above, for nondeterministic models (MDPs or PTAs), either minimum or maximum probability values can be computed. Therefore, in this case, we have two possible types of property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which return the minimum and maximum probabilities, respectively.\n</p>\n<p class='vspace'>It is also possible to specify to which state the probability returned by a quantitative property refers. This is covered in the later section on <a class='wikilink' href='Filters.html'>filters</a>.\n</p>\n<div class='vspace'></div><h3>Path properties</h3>\n<p>PRISM supports a wide range of path properties that can be used with the <code><strong>P</strong></code> operator.\nA path property is a formula that evaluates to either true or false for a single path in a model.\nHere, we review some of the simpler properties that feature a single <em>temporal operator</em>,\nas used for example in the logics PCTL and CSL. Later, we briefly describe how PRISM also supports more complex LTL-style path properties.\n</p>\n<p class='vspace'>The basic different types of path property that can be used inside the <code><strong>P</strong></code> operator are:\n</p>\n<div class='vspace'></div><ul><li><code><strong>X</strong></code> : \"ne<strong>x</strong>t\"\n</li><li><code><strong>U</strong></code> : \"<strong>u</strong>ntil\"\n</li><li><code><strong>F</strong></code> : \"eventually\" (sometimes called \"<strong>f</strong>uture\")\n</li><li><code><strong>G</strong></code> : \"always\" (sometimes called \"<strong>g</strong>lobally\")\n</li><li><code><strong>W</strong></code> : \"<strong>w</strong>eak until\"\n</li><li><code><strong>R</strong></code> : \"<strong>r</strong>elease\"\n</li></ul><p class='vspace'>In the following sections, we describe each of these <em>temporal operators</em>. We then discuss the (optional) use of time bounds with these operators. Finally, we also discuss LTL-style path properties.\n</p>\n<div class='vspace'></div><h3>\"Next\" path properties</h3>\n<p>The property <code><strong>X</strong> prop</code> is true for a path if <code>prop</code> is true in its second state,\nAn example of this type of property, used inside a <code><strong>P</strong></code> operator, is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">X</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of the expression <code>y=1</code> being true in the next state is less than 0.01\".\n</p>\n<div class='vspace'></div><h3>\"Until\" path properties</h3>\n<p>The property <code>prop1 <strong>U</strong> prop2</code> is true for a path if\n<code>prop2</code> is true in some state of the path and <code>prop1</code> is true in all preceding states.\nA simple example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually equal to 2, and that <code>z</code> remains less than 2 up until that point, is greater than 0.5\".\n</p>\n<div class='vspace'></div><h3>\"Eventually\" path properties</h3>\n<p>The property <code><strong>F</strong> prop</code> is true for a path if <code>prop</code> eventually becomes true at some point along the path. The <code><strong>F</strong></code> operator is in fact a special case of the <code><strong>U</strong></code> operator (you will often see <code> <strong>F</strong> prop</code> written as <code><strong>true</strong> <strong>U</strong> prop</code>). A simple example is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>&gt;<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually greater than 2is less than 0.1\".\n</p>\n<div class='vspace'></div><h3>\"Globally\" path properties</h3>\n<p>Whereas the <code><strong>F</strong></code> operator is used for \"reachability\" properties, <code><strong>G</strong></code> represents \"invariance\". The property <code><strong>G</strong> prop</code> is true of a path if <code>prop</code> remains true at all states along the path. Thus, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>states that, with probability at least 0.99, <code>z</code> never exceeds 10.\n</p>\n<div class='vspace'></div><h3>\"Weak until\" and \"release\" path properties</h3>\n<p>Like <code><strong>F</strong></code> and <code><strong>G</strong></code>, the operators <code><strong>W</strong></code> and <code><strong>R</strong></code> are derivable from other temporal operators.\n</p>\n<p class='vspace'>Weak until (<code>a <strong>W</strong> b</code>), which is equivalent to <code>(a <strong>U</strong> b) | <strong>G</strong> a</code>, requires that <code>a</code> remains true until <code>b</code> becomes true, but does not require that <code>b</code> ever does becomes true (i.e. <code>a</code> remains true forever). For example, a weak form of the until example used above is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which states that, with probability greater than 0.5, either <code>z</code> is always less than 2, or it is less than 2 until the point where <code>z</code> is 2.\n</p>\n<p class='vspace'>Release (<code>a <strong>R</strong> b</code>),  which is equivalent to <code>!(!a U !b)</code>, informally means that <code>b</code> is true until <code>a</code> becomes true, or <code>b</code> is true forever.\n</p>\n<p class='vspace'><a name='bounded' id='bounded'></a>\n</p><h3>\"Bounded\" variants of path properties</h3>\n<p>All of the temporal operators given above, with the exception of <code><strong>X</strong></code>, have \"bounded\" variants, where an additional time bound is imposed on the property being satisfied.\nThe most common case is to use an upper time bound, i.e. of the form \"<code>&lt;=t</code>\" or \"<code>&lt;t</code>\", where <code>t</code> is a PRISM expression evaluating to a constant, non-negative value.\n</p>\n<p class='vspace'>For example, a bounded until property <code>prop1 <strong>U</strong>&lt;=t prop2</code>, is satisfied along a path if <code>prop2</code> becomes true within <code>t</code> steps and <code>prop1</code> is true in all states before that point.\nA typical example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">y</span>&lt;<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of <code>y</code> first exceeding 3 within 7 time units is greater than or equal to 0.98\". Similarly:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state if \"the probability of <code>y</code> being equal to 4 within 7 time units is greater than or equal to 0.98\" and:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true if the probability of <code>y</code> staying equal to 4 for 7 time units is at least 0.98.\n</p>\n<p class='vspace'>The time bound can be an arbitrary (constant) expression,\nbut note that you may need to bracket it,\nas in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=(<span class=\"prismnum\">2</span>*<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>) <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use lower time-bounds (i.e. <code>&gt;=t</code> or <code>&gt;t</code>) and time intervals <code>[t1,t2]</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&gt;=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">20</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which refer to the probability of <code>y</code> becoming equal to 4 after 10 or more time units, and after between 10 and 20 time-units respectively.\n</p>\n<p class='vspace'>For CTMCs, the time bounds can be any (non-negative) numerical values - they are not restricted to integers, as for discrete-time models.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.25</span> [ <span class=\"prismident\">y</span>&lt;=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">6.5</span> <span class=\"prismident\">y</span>&gt;<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means that the probability of <code>y</code> being greater than 1 within 6.5 time-units (and remaining less than or equal to 1 at all preceding time-points) is at least 0.25.\n</p>\n<div class='vspace'></div><h3>Transient probabilities</h3>\n<p>We can also use the bounded <code><strong>F</strong></code> operator to refer to a single time instant, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock24'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">10</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=24' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or, equivalently:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock25'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=25' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>both of which give the probability of <code>y</code> being 6 at time instant 10.\n</p>\n<p class='vspace'><a name='ltl' id='ltl'></a>\n</p><h3>LTL-style path properties</h3>\n<p>PRISM also supports probabilistic model checking of the temporal logic LTL (and, in fact, PCTL*). LTL provides a richer set of path properties for use with the <code><strong>P</strong></code> operator, by permitting temporal operators to be combined. Here are a few examples of properties expressible using this functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock26'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">F</span> ( \"<span class=\"prismident\">request</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">ack</span>\") ) ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=26' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"with probability greater than 0.99, a request is eventually received, followed immediately by an acknowledgement\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock27'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">send</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=27' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"a message is sent infinitely often with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock28'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">G</span> (\"<span class=\"prismident\">error</span>\" &amp; !\"<span class=\"prismident\">repair</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=28' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of an error occurring that is never repaired\n</p>\n<p class='vspace'>Note that logical operators have precedence over temporal ones, so you will often need to include parentheses when using logical operators, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock29'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\") &amp; (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=29' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For temporal operators, unary operators (such as <code><strong>F</strong></code>, <code><strong>G</strong></code> and <code><strong>X</strong></code>) have precedence over binary ones (such as <code><strong>U</strong></code>). Unary operators can be nested, without parentheses, but binary ones cannot.\n</p>\n<p class='vspace'>So, these are allowed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock30'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">a</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ (\"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\") <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=30' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>but this is not:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock31'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=31' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>The S Operator</h1>\n<p>The <code><strong>S</strong></code> operator is used to reason about the <em>steady-state</em> behaviour of a model,\ni.e. its behaviour in the <em>long-run</em> or <em>equilibrium</em>.\nPRISM currently only provides support for DTMCs and CTMCs.\nThe definition of steady-state (long-run) probabilities for finite DTMCS and CTMCs is well defined (see e.g. [<a class='wikilink' href='../Main/References.html#Ste94'>Ste94</a>]).\nInformally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock32'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">prop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=32' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a DTMC or CTMC if\n\"starting from <em>s</em>, the steady-state (long-run) probability of being in a state which satisfies the (Boolean-valued) PRISM property <code>prop</code>, meets the bound <code>bound</code>\".\nA typical example of this type of property would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock33'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.05</span> [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=33' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the long-run probability of the queue being more than 75% full is less than 0.05\".\n</p>\n<p class='vspace'>Like the <code><strong>P</strong></code> <a class='wikilink' href='ThePOperator.html'>operator</a>, the <code><strong>S</strong></code> operator can be used in a <em>quantitative</em> form, which returns the actual probability value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock34'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=34' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and can be further customised with the use of <a class='wikilink' href='Filters.html'>filters</a>.\n</p><hr />\n<h1>Reward-based Properties</h1>\n<p>PRISM models can be augmented with information about <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>rewards</a> (or, equivalently, costs).\nThe tool can analyse properties which relate to the <em>expected values</em> of these rewards.\nThis is achieved using the <code><strong>R</strong></code> operator, which works in a similar fashion to the\n<code><strong>P</strong></code> and <code><strong>S</strong></code> operators, and can be used either in a Boolean-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock35'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=35' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>bound</code> takes the form <code>&lt;r</code>, <code>&lt;=r</code>, <code>&gt;r</code> or <code>&gt;=r</code> for an expression <code>r</code> evaluating to a non-negative double,\nor a real-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock36'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">query</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=36' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>query</code> is <code>=?</code>, <code>min=?</code> or <code>max=?</code>.\nIn the latter case, <a class='wikilink' href='Filters.html'>filters</a> can be used, as for the <code><strong>P</strong></code> and <code><strong>S</strong></code> operators.\n</p>\n<p class='vspace'>Informally, \"<code><strong>R</strong> bound [ rewardprop ]</code>\" is true in a state of a model if\n\"the expected reward associated with <code>rewardprop</code> of the model when starting from that state''\nmeets the bound <code>bound</code> and \"<code><strong>R</strong> query [ rewardprop ]</code>\"  returns the actual expected reward value.\n</p>\n<p class='vspace'>There are various different types of reward properties:\n</p>\n<div class='vspace'></div><ul><li>\"reachability reward\": <code><strong>F</strong> prop</code>\n</li><li>\"co-safe LTL reward\": e.g. <code><strong>F</strong> (prop1 &amp; <strong>F</strong> prop2)</code>\n</li><li>\"cumulative reward\" : <code><strong>C</strong>&lt;=t</code>\n</li><li>\"total reward\" : <code><strong>C</strong></code>\n</li><li>\"instantaneous reward\" : <code><strong>I</strong>=t</code>\n</li><li>\"steady-state reward\" : <code><strong>S</strong></code>.\n</li></ul><p class='vspace'>Below, we consider each of these cases in turn.\nThe descriptions here are kept relatively informal.\nPrecise definitions for most of these can be found in, for example,\n[<a class='wikilink' href='../Main/References.html#KNP07a'>KNP07a</a>] (for DTMCs and CTMCs) or [<a class='wikilink' href='../Main/References.html#FKNP11'>FKNP11</a>] (for MDPs).\n</p>\n<div class='vspace'></div><h3>\"Reachability reward\" properties</h3>\n<p>\"Reachability reward\" properties associate a reward with each path of a model.\nMore specifically, they refer to the reward accumulated along a path until a certain point is reached.\nThe manner in which rewards are accumulated depends on the model type.\nFor DTMCs and MDPs, the total reward for a path is the sum of the state rewards for each state along the path\nplus the sum of the transition rewards for each transition between these states.\nThe situation for CTMCs is similar, except that the state reward assigned to each state\nof the model is interpreted as the <em>rate</em> at which rewards are accumulated in that state,\ni.e. if <em>t</em> time units are spent in a state with state reward <em>r</em>,\nthe reward accumulated in that state is <em>r</em> x <em>t</em>.\nHence, the total reward for a path in a CTMC is the sum of these products for each state along the path\nplus the sum of the transition rewards for each transition between these states.\n</p>\n<p class='vspace'>The reward property \"<code>F prop</code>\" corresponds to the reward cumulated along a path\nuntil a state satisfying property <code>prop</code> is reached,\nwhere rewards are cumulated as described above.\nState rewards for the <code>prop</code>-satisfying state reached are not included in the cumulated value.\nIn the case where the probability of reaching a state satisfying <code>prop</code> is less than 1, the reward is equal to infinity.\n</p>\n<p class='vspace'>A common application of this type of property is the case when the rewards associated with the model correspond to time.\nOne can then state, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock37'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">9.5</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=37' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"the expected time taken to reach, from <em>s</em>, a state where <code>z</code> equals 2 is less than or equal to 9.5\".\n</p>\n<div class='vspace'></div><h3>\"Co-safe LTL reward\" properties</h3>\n<p>These generalise the \"reachability\" properties above. Again, reward is accumulated along a path up until some point,\nbut this is specified in a more general way, by giving a formula in the co-safe fragment of linear temporal logic (LTL).\nRewards are accumulated up until the point where the formula is first satisfied. For example, this property, for a DTMC or CTMC,\nqueries the expected reward accumulated until first <code>goal</code> equals 1 and then subsequently <code>goal</code> equals 2:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock38'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">F</span> (<span class=\"prismident\">goal</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismkeyword\">F</span> <span class=\"prismident\">goal</span>=<span class=\"prismnum\">2</span>) ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=38' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and this property, for an MDP, minimises the expected reward until <code>loc</code> equals 1,\nhaving passed only through states where <code>loc</code> never equals 4\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock39'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismident\">loc</span>!=<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">loc</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=39' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As for reachability rewards, if the probability of satisfying the formula is less than 1,\nthen the expected reward is defined to be infinite.\n</p>\n<p class='vspace'>Intuitively, a <em>co-safe</em> formula is one that is satisfied within a finite period of time,\nand remains true for ever once it becomes true for the first time.\nFor simplicity, PRISM actually supports the <em>syntactic</em> co-safe fragment of LTL,\nwhich is defined as any LTL formula that only uses the temporal operators <code><strong>F</strong></code>, <code><strong>U</strong></code> and <code><strong>X</strong></code>\n(but not <code><strong>G</strong></code>, for example).\nPRISM's notation for LTL formulas is described <a class='wikilink' href='ThePOperator.html'>here</a>.\n</p>\n<div class='vspace'></div><h3>\"Cumulative reward\" properties</h3>\n<p>\"Cumulative reward\" properties also associate a reward with each path of a model,\nbut only up to a given time bound.\nThe property <code>C&lt;=t</code> corresponds to the reward cumulated along a path\nuntil <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\nState and transition rewards along a path are cumulated exactly as described in the previous section.\n</p>\n<p class='vspace'>A typical application of this type of property is the following.\nConsider a model of a disk-drive controller which includes a queue of incoming disk requests.\nIf we assign a reward of 1 to each transition of the model\ncorresponding to the situation where an incoming request is lost because the queue is full,\nthen the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock40'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">15.5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=40' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would return, for a given state of the model,\n\"the expected number of lost requests within 15.5 time units of operation\".\n</p>\n<p class='vspace'><a name='total' id='total'></a>\n</p><h3>\"Total reward\" properties</h3>\n<p>\"Total reward\" properties refer to the accumulation of state and transition rewards\nin the same way as for \"reachability reward\" and \"cumulative reward\" properties,\nbut the rewards is accumulated indefinitely,\ni.e. the total reward accumulated along the whole (infinite) path.\nNote that this means that, unless a path ends up remaining forever in states with zero reward,\nthe total reward will be infinite.\n</p>\n<p class='vspace'>Re-using the reward structure in the previous example,\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock41'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=41' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>returns \"the expected total number of lost requests\".\n</p>\n<div class='vspace'></div><h3>\"Instantaneous reward\" properties</h3>\n<p>\"Instantaneous reward\" properties refer to the reward of a model at a particular instant in time.\nThe reward property <code>I=t</code> associates with a path the reward in the state \nof that path when exactly <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\n</p>\n<p class='vspace'>Returning to our example from the previous section of a model for a disk-request queue in a disk-drive controller,\nconsider the case where the rewards assigned to each state of the model give the current size of the queue in that state.\nThen, the following property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock42'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;<span class=\"prismnum\">4.4</span> [ <span class=\"prismkeyword\">I</span>=<span class=\"prismnum\">100</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=42' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would be true in a state <em>s</em> of the model if\n\"starting from <em>s</em>, the expected queue size exactly 100 time units later is less than 4.4\".\nNote that, for this type of reward property, state rewards for CTMCs do not have to refer to rates;\nthey can refer to any instantaneous measure of interest for a state.\n</p>\n<div class='vspace'></div><h3>\"Steady-state reward\" properties</h3>\n<p>Unlike the previous three types of property,\n\"steady-state reward\" properties relate not to paths, but rather to the reward in the long-run.\nA typical application of this type of property would be, in the case where\nthe rewards associated with the model correspond to power consumption, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock43'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">0.7</span> [ <span class=\"prismkeyword\">S</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=43' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"starting from <em>s</em>, the long-run average power consumption is less than 0.7\".\n</p>\n<div class='vspace'></div><h3>Which reward structure?</h3>\n<p>In the case where a PRISM model has multiple <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structures</a> you may need to specify which reward structure your property refers to. This is done by placing the information in braces (<code>{}</code>) after the <code>R</code> operator. You can do so either using the name assigned to a reward structure (if any) or using the index (where <code>1</code> means the first rewards structure in the PRISM model file, <code>2</code> the second, etc.). Examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock44'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">num_failures</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">10.0</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismnum\">2</span>}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=44' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note that when using an index to specify the reward structure, you can actually put any expression that evaluates to an integer. This allows you to, for example, write a property of the form <code>R{c}=?[...]</code> where <code>c</code> is an undefined integer constant. You can then vary the value of <code>c</code> in an experiment and compute values for several different reward structures at once.\n</p>\n<p class='vspace'>If you don't specify a reward structure to the <code>R</code> operator, by default, the first one in the model file is used.\n</p>\n<div class='vspace'></div><h3>Availability</h3>\n<p>There are currently a few restrictions on the model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a> that can be used for some reward properties. The following table summarises the currently availability, where S, M, H and E denote the \"sparse\", \"MTBDD\", \"hybrid\" and \"explicit\" engines, respectively, for DTMCs, CTMCs and MDPs. For PTAs, support for rewards is currently quite restrictive; see the later section on <a class='wikilink' href='Real-timeModels.html'>real-time model properties</a> for details.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><code><strong>F</strong></code></td><td  align='center'>cosafe</td><td  align='center'><code><strong>C</strong>&lt;=t</code></td><td  align='center'><code><strong>C</strong></code></td><td  align='left'><code><strong>I</strong>=t</code></td><td  align='right'><code><strong>S</strong></code></td></tr>\n<tr ><td  align='center'><strong>DTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>CTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>MDPs</strong></td><td  align='center'>SM-E</td><td  align='center'>SMHE</td><td  align='center'>S--E</td><td  align='center'>----</td><td  align='center'>SM-E</td><td  align='right'>----</td></tr>\n</table><hr />\n<h1>Multi-objective Properties</h1>\n<p>For MDPs, PRISM supports <em>multi-objective</em> properties. Consider a property that uses the <code><strong>P</strong></code> operator. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock45'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=45' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This states that, <em>for all</em> strategies (or policies) of the MDP, the probability of reaching an <code>\"error\"</code> state is less than 0.01.\n</p>\n<p class='vspace'>Multi-objective queries differ in two important ways. Firstly, (by default) they ask about the <em>existence</em> of a strategy. Secondly they refer to <em>multiple</em> properties of a strategy. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock46'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=46' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means: \"does there exist a strategy of the MDP under which the probability of reaching an <code>\"error1\"</code> state is less than 0.01 <em>and</em> the probability of reaching an <code>\"error2\"</code> state is less than 0.02?\"\n</p>\n<p class='vspace'>To use the terminology from [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>], the above is an \"achievability\" query (i.e., is this combination of objectives achievable by some strategy?). PRISM also supports two other kinds of multi-objective query: \"numerical\" and \"Pareto\" queries.\n</p>\n<p class='vspace'>A \"numerical\" query looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock47'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=47' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>meaning \"what is the minimum possible probability of reaching <code>\"error1\"</code>, over all strategies of the MDP for which the probability of reaching <code>\"error2\"</code> is less than 0.02?\".\n</p>\n<p class='vspace'>A \"Pareto\" queries leaves both of the objectives unbounded, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock48'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=48' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This asks PRISM to compute (approximately), the <em>Pareto curve</em> for this pair objectives. Intuitively, this is the set of pairs of probabilities (of reaching <code>\"error1\"</code>/<code>\"error2\"</code>) such that reducing one probability any more would necessitate an increase in the other probability.\n</p>\n<div class='vspace'></div><h3>Types of Objectives</h3>\n<p>For simplicity, the examples above all refer to the probability of reaching classes of states in the model. Other types of property (objective) are also possible.\n</p>\n<p class='vspace'>Firstly, we can extend the examples above by referring to the probability of any\n<a class='wikilink' href='ThePOperator.html#ltl'>LTL</a> property. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock49'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=49' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9?\".\n</p>\n<p class='vspace'>We can also use more than 2 objectives, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock50'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.95</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good3</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=50' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9 and the probability of visiting <code>\"good3\"</code> states infinitely often remains at least 0.95?\".\n</p>\n<p class='vspace'>Multi-objective queries can also refer to the expected total cumulative value of a reward structure. We write such properties in the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock51'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}<span class=\"prismkeyword\">min</span>=?[ <span class=\"prismkeyword\">C</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">energy</span>\"}&lt;=<span class=\"prismnum\">1.45</span> [ <span class=\"prismkeyword\">C</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=51' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the minimum expected cumulative value of reward structure <code>\"time\"</code>, such that the expected cumulative value of reward structure <code>\"energy\"</code> is below 1.45.\n</p>\n<p class='vspace'>Note that this <code><strong>C</strong></code> reward operator differs from the <code><strong>F</strong> \"target\"</code> operator, usually used for standard (single-objective) MDP model checking. Whereas the <code><strong>F</strong> \"target\"</code> operator refers to the expected reward accumulated until a <code>\"target\"</code> state is reached the <code><strong>C</strong></code> operator refers to the expected <em>total</em> reward.\n</p>\n<p class='vspace'>A few important notes regarding rewards:\n</p>\n<div class='vspace'></div><ul><li>Currently only transition rewards are supported; state rewards are not.\n<div class='vspace'></div></li><li>Certain assumptions are made regarding the finiteness of rewards; see p.7 of [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>] for details.\n</li></ul><p class='vspace'>Finally, time-bounded variants of both probabilistic reachability and expected cumulative rewards objectives can be used. Here is an example that uses the latter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock52'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">power</span>\"}<span class=\"prismkeyword\">min</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">queue</span>\"}&lt;=<span class=\"prismident\">r</span> [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=52' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Solution Methods</h3>\n<p>PRISM can perform multi-objective model checking using two distinct solution methods, which are described in [<a class='wikilink' href='../Main/References.html#FKN+11'>FKN+11</a>] and [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>]. The former is based on the use of linear programming; the latter reduces multi-objective model checking to a series of simpler problems, solved using value iteration (or the Gauss-Seidel variant of value iteration). The default is \"Value iteration\". You can change this in the GUI using the option \"MDP multi-objective solution methods\", or using the command-line switches <code>-lp</code>, <code>-valiter</code>, <code>-gs</code>.\n</p>\n<p class='vspace'>There are some restrictions for the different methods, e.g.\n</p>\n<div class='vspace'></div><ul><li>Linear programming does not support time-bounded properties or Pareto queries\n</li></ul><div class='vspace'></div><hr />\n<h1>Real-time Models</h1>\n<p>The classes of property that can be checked for real-time models (PTAs and POPTAs) are currently more restricted than for the other kinds of models that PRISM supports. This is because the model checking procedures are quite different for this type of model. We describe these restrictions here. The situation is also dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is being used.\n</p>\n<p class='vspace'>For the \"<strong>stochastic games</strong>\" engine, we essentially only allow unbounded or time-bounded probabilistic reachability properties, i.e. properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock53'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=53' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>target</code> is a Boolean-valued expression that does not include references to any clock variables and <code>T</code> is an integer-valued expression. The <code><strong>P</strong></code> operator cannot be nested and the <code><strong>S</strong></code> and <code><strong>R</strong></code> operators are not supported.\n</p>\n<p class='vspace'>The \"<strong>backwards reachability</strong>\" engine is similar but currently only handles maximum probabilities.\n</p>\n<p class='vspace'>For the \"<strong>digital clocks</strong>\" engine, there is slightly more flexibility,\ne.g. until (<code><strong>U</strong></code>) properties are allowed, as are clock variables in expressions and arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock54'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=54' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This engine, like the \"stochastic games\" engine, does not allowed nested properties. Also, references to clocks must, like in the modelling language, not use strict comparisons\n(e.g. <code>x&lt;=5</code> is allowed, <code>x&lt;5</code> is not).\n</p>\n<p class='vspace'>The digital clocks also has support for rewards:\nit is possible to check reachability reward properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock55'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=55' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Reward structures specified in the model, though, must not depend on clock variables.\nFormally, the class of PTAs with this kind of reward structure is sometime called <em>linearly priced PTAs</em> (see e.g. [<a class='wikilink' href='../Main/References.html#KNPS06'>KNPS06</a>].\n</p>\n<p class='vspace'>The digital clocks method is based on a language-level translation from a PTA model to an MDP one. If you want to see the MDP PRISM model that was generated, add the switch <code>-exportdigital digital.nm</code> when model checking property to export the model file to <code>digital.nm</code>.\n</p><hr />\n<h1>Partially Observable Models</h1>\n<p>For partially observable models (POMDPs and POPTAs),\nPRISM uses the same property language as the their\nfully observational equivalents (MDPs and PTAs).\nHowever, a more limited range of properties are available.\nFor POMDPs, PRISM currently supports probabilistic reachability,\nprobabilistic until, or expected reachability rewards properties, i.e.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock56'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=56' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or bounded variants with a probability/threshold instead\nof the <code>min=?</code> or <code>max=?</code>.\n</p>\n<p class='vspace'>For the verification methods currently implemented,\nthere are a few additional restrictions.\nFirstly, the <code>target</code> (and <code>remain</code>) expression appearing\nin the property must be an observable.\nIn other words, if any state of the POMDP satisfies the expression,\nthen all other observationally equivalent states must also satisfy it.\nThis is easily achieved by only using either observable variables\nor named observables in the expression, but that is not required.\nSecondly, probabilities and expected rewards are only computed from a single state.\n</p>\n<p class='vspace'>POPTAs are currently verified using the \"digital clocks\" approach to\ntranslate them into a POMDP, so they inherit the same\n<a class='wikilink' href='Real-timeModels.html'>restrictions</a>\n(that strict or diagonal clock comparisons are not allowed).\nHowever for POPTAs, time-bounded probabilistic reachability is also supported.\n</p><hr />\n<h1>Uncertain Models</h1>\n<p>For uncertain models, currently interval MDPs (IMDPs) or interval DTMCs (IDTMCs), PRISM performs <em>robust</em> verification, which considers the best- or worst-case behaviour that can arise depending on the way that probabilities are selected from intervals.\n</p>\n<p class='vspace'>For example, instead of a property for a DTMC such as\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock57'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=57' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which asks for the probability to reach a state satisfying <code>\"goal\"</code>, IDTMCs use MDP-style queries:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock58'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=58' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which compute the minimum or maximum possible probability that can arise.\n</p>\n<p class='vspace'>Similarly, for an IMDP, there are now two separate quantifications, firstly over strategies (policies) and secondly over the distinct ways that transition probabilities can be selected from intervals, for which <code>min</code> or <code>max</code> appear in that order in the query. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock59'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmaxmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmaxmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=59' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>return the minimum and maximum values, respectively, over resolutions of transition probabilities for the maximum probability of reaching <code>\"goal\"</code>. Similarly, <code>minmin</code> and <code>minmax</code> are used for the minimum probability of reaching <code>\"goal\"</code>. Model checking is supported for:\n</p>\n<div class='vspace'></div><ul><li>the <code><strong>P</strong></code> operator, including single temporal operators and LTL formulae\n</li><li>the <code><strong>R</strong></code> operator, for the expected reward to reach a target or satisfy a co-safe LTL formula\n</li></ul><div class='vspace'></div><hr />\n<h1>Non-Probabilistic Properties</h1>\n<p>PRISM also supports model checking of the non-probabilistic temporal logics CTL (computation tree logic) and LTL (linear temporal logic).\nProperties in these logics use the <code><strong>A</strong></code> (for all) and <code><strong>E</strong></code> (there exists) operators,\ninstead of the probabilistic <code><strong>P</strong></code> operator used in many other properties supported by PRISM.\n</p>\n<p class='vspace'>Properties take the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock60'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">A</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=60' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which are true in a state <em>s</em> of a model if\n\"path property <code>pathprop</code> is satisfied by <em>all</em> paths from state <em>s</em>\"\nand\n\"path property <code>pathprop</code> is satisfied by <em>some</em> path from state <em>s</em>\",\nrespectively.\nThe syntax for LTL formulas is the same as those allowed within the <a class='wikilink' href='ThePOperator.html#ltl'>P operator</a>.\n</p>\n<p class='vspace'>Example properties include:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock61'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ] <span class=\"prismcomment\">// There exists a path that reaches a state satisfying \"goal\"</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span> ] <span class=\"prismcomment\">// Variable x is always at most 10 along all paths of the model</span><br/>\n<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">ready</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">launch</span>\") ] <span class=\"prismcomment\">// There exists a path along which label \"ready\" eventually becomes true and label \"launch\" is true immediately afterwards</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span>) | (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>) ] <span class=\"prismcomment\">// Along all paths, either x=1 or x=2 is true infinitely often</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=61' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Counterexamples and Witnesses</h3>\n<p>If you check a CTL property of the form <code>A [ G \"inv\" ]</code> and it is false, PRISM will generate a counterexample in the form of a path that reaches a state where <code>\"inv\"</code> is not true. This is displayed either in the simulator (from the GUI) or at the command-line. Similarly, if you check <code>E [ F \"goal\" ]</code> and the result is true, a witness (a path reaching a <code>\"goal\"</code> state) will be generated.\n</p><hr />\n<h1>Syntax And Semantics</h1>\n<h3>Syntax</h3>\n<p>The syntax of the PRISM property specification language subsumes various probabilistic temporal logics, including PCTL, CSL, (probabilistic) LTL, PCTL* and CTL. Informally, the syntax can be summarised as follows: a property can be any valid, well-typed PRISM <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a>, which (optionally) also includes the probabilistic operators discussed previously (<code><strong>P</strong></code>, <code><strong>S</strong></code> and <code><strong>R</strong></code>) and the non-probabilistic (CTL) ones <code><strong>A</strong></code> and <code><strong>E</strong></code>). This mean that any of the following operators can be used:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li><li><code><strong>P</strong></code> (probabilistic operator)\n</li><li><code><strong>S</strong></code> (steady-state operator)\n</li><li><code><strong>R</strong></code> (reward operator)\n</li><li><code><strong>A</strong></code> (for-all operator)\n</li><li><code><strong>E</strong></code> (there-exists operator)\n</li></ul><p class='vspace'>This allows you to write any property expressible in logics such as PCTL and CSL. For example, CSL allows you to nest <code><strong>P</strong></code> and <code><strong>S</strong></code> operators:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock62'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>&gt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">S</span>&gt;<span class=\"prismnum\">0.9</span>[ <span class=\"prismident\">num_servers</span> &gt;= <span class=\"prismnum\">5</span> ] ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=62' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of it taking more than 2 hours to get to a state from which the long-run probability of at least 5 servers being operational is &gt;0.9\"\n</p>\n<p class='vspace'>You can also express various arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock63'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">3600</span>,<span class=\"prismnum\">7200</span>] <span class=\"prismident\">oper</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=63' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability that the system is <strong>not</strong> operational at any point during the second hour of operation\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock64'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">oper</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">t</span> ] / <span class=\"prismident\">t</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=64' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the expected fraction of time that the system is available (i.e. the expected interval availability) in the time interval [0, t]\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock65'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">fail_A</span> ] / <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">any_fail</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=65' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the (conditional) probability that component A eventually fails, given\nthat at least one component fails\"\n</p>\n<div class='vspace'></div><h3>Semantics</h3>\n<p>We omit a formal presentation of the semantics of the PRISM property language. The semantics of the probabilistic temporal logics that the language incorporates can be found from a variety of sources. See for example the pointers given in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>It is worth, however, clarifying a few points specific to PRISM. A property is evaluated with respect to a particular state of a model. Depending on the type of the property, this value may either be a Boolean, an integer or a double. When performing model checking, PRISM usually has to actually compute the value for <em>all</em> states of the model but, for clarity, will by default report just a single value. Typically, this is the value for the (single) initial state of the model. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock66'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=66' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will report the probability, from the initial state of the model, of reaching an \"error\" state.\nThis:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock67'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=67' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will return <code>true</code> if and only if the probability, from the initial state, is greater than 0.5.\n</p>\n<p class='vspace'><strong>Note:</strong> This is contrast to older versions of PRISM, which treated numerical and Boolean-valued properties differently in this respect.\n</p>\n<p class='vspace'>For models with <a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>multiple initial states</a>, we need to adapt these definitions slightly. In this case, the two properties above will yield, respectively:\n</p>\n<div class='vspace'></div><ul><li>the range of values (over all initial states) of the probability of reaching \"error\"\n<div class='vspace'></div></li><li><code>true</code> if and only if the probability is greater than 0.5 from <em>all</em> initial states.\n</li></ul><p class='vspace'>You can also ask PRISM to return different values using <a class='wikilink' href='Filters.html'>filters</a>,\nwhich are described in the next section.\n</p><hr />\n<h1>Filters</h1>\n<p>As discussed above, when reporting the result of model checking a property, PRISM will by default return the value for the (single) initial state of the model. However, since PRISM in fact usually has to compute values for <em>all</em> states simultaneously, you can customise PRISM properties to obtain different results. This is done using <em>filters</em>.\n</p>\n<p class='vspace'>Filters are created using the <code>filter</code> keyword. They take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock68'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=68' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>op</code> is the filter <em>operator</em> (see below), <code>prop</code> is any PRISM property and <code>states</code> is a Boolean-valued expression identifying a set of states over which to apply the filter.\n</p>\n<p class='vspace'>In fact, the <code>states</code> argument is optional; if omitted, the filter is applied over all states. So, the following properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock69'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismkeyword\">true</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=69' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Here's a simple example of a filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock70'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=70' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This gives the <em>maximum</em> value, starting from any state satisfying <code>x=0</code>, of the probability of reaching an \"error\" state.\n</p>\n<p class='vspace'>Here's another simple example,\nwhich checks whether, <em>starting from any reachable state</em>,\nwe eventually reach a \"done\" state with probability 1.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock71'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=71' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We could modify this property slightly to instead check whether, from any state that satisfies the label \"ready\", we eventually reach a \"done\" state with probability 1. This could be done with either of the following two equivalent properties:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock72'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, \"<span class=\"prismident\">ready</span>\" =&gt; <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ], \"<span class=\"prismident\">ready</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=72' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Note:</strong> In older versions of PRISM, the property above could be written just as <code>\"ready\" =&gt; P&gt;=1 [ F \"done\" ]</code> since the result was checked for all states by default, not just the <a class='wikilink' href='SyntaxAndSemantics.html'>initial state</a>. Now, you need to explicitly include a filter, as shown above, to achieve this.\n</p>\n<div class='vspace'></div><h3>Types of filter</h3>\n<p>Most filters of the form <code>filter(op, prop, states)</code>\napply some operator <code>op</code> to the values of property <code>prop</code>\nfor all the states satisfying <code>states</code>,\nresulting in a single value.\nThe full list of filter operators <code>op</code> in this category is:\n</p>\n<div class='vspace'></div><ul><li><code>min</code>: the minimum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>max</code>: the maximum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>count</code>: counts the number of states satisfying <code>states</code> for which <code>prop</code> is true\n</li><li><code>sum</code> (or <code>+</code>): sums the value of <code>prop</code> for states satisfying <code>states</code>\n</li><li><code>avg</code>: the average value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>first</code>: the value of <code>prop</code> for the first (lowest-indexed) state satisfying <code>states</code>\n</li><li><code>range</code>: the range (interval) of values of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>forall</code> (or <code>&amp;</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for all states satisfying <code>states</code>\n</li><li><code>exists</code> (or <code>|</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for some states satisfying <code>states</code>\n</li><li><code>state</code>: returns the value for the single state satisfying <code>states</code> (if there is more than one, this is an error)\n</li></ul><p class='vspace'>There are also a few filters that, rather than returning a single value, return different values for each state, like a normal PRISM property:\n</p>\n<div class='vspace'></div><ul><li><code>argmin</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the minimum value of <code>prop</code>\n</li><li><code>argmax</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the maximum value of <code>prop</code>\n</li><li><code>print</code>: does not change the result of <code>prop</code> but prints the (non-zero) values to the log\n</li><li><code>printall</code>: like <code>print</code>, but displays <em>all</em> values, even for states where the value is zero\n</li></ul><div class='vspace'></div><h3>More examples</h3>\n<p>Here are some further illustrative examples of properties that use filters.\n</p>\n<p class='vspace'>Filters provide a quick way to <em>print</em> the results of a model checking query for several states. In most cases, for example, a <code>P=?</code> query just returns the probability from the initial state. To see the probability for all states satisfying <code>x&gt;2</code>, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock73'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">P</span>=? [ ... ], <span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">2</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=73' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Values are printed in the log (i.e. to the \"Log\" tab in the GUI or to the terminal from the command-line). For small models, you could omit the final <code>states</code> argument (<code>x&gt;2</code> here) and view the probabilities from all states. You can also use PRISM's <a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>verbose</a> mode to view values for all states, but filters provide an easier and more flexible solution.\n<code>print</code> filters do not actually alter the result returned so, in the example above, PRISM will still return the probability for the initial state, in addition to printing other probabilities in the log.\n</p>\n<p class='vspace'>You can also use <code>print</code> filters to display lists of states. For example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock74'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">argmax</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]))<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=74' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>prints the states which have the highest probability of reaching an error state.\nHowever, you should exercise caution when using <code>argmax</code> (or <code>argmin</code>) on properties such as <code>P=? [ ... ]</code> (or <code>S=? [ ... ]</code> or <code>R=? [ ... ]</code>), whose results are only approximate due to the nature of the methods used to compute them (or because of round-off errors.)\n</p>\n<p class='vspace'>Another common use of filters is to display the value for a particular state of the model (rather than the initial state, which is used by default). To achieve this, use e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock75'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>&amp;<span class=\"prismident\">y</span>=<span class=\"prismnum\">3</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=75' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>x=2&amp;y=3</code> is assumed to specify one particular state.\nA <code>state</code> filter will produce an error if the filter expression is not satisfied by exactly one state of the model.\n</p>\n<p class='vspace'>Filters can also be built up into more complex expressions. For example, the following two properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock76'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">avg</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">sum</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\") / <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">count</span>, \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=76' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>range</code> filter, unlike most PRISM expressions which are of type Boolean, integer or double, actually returns an interval: a pair of integers or doubles. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock77'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">count</span>=<span class=\"prismnum\">10</span> ], <span class=\"prismident\">count</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=77' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>gives the range of all possible values for the probability of reach a state satisfying <code>count=10</code>, from all states satisfying <code>count=0</code>.\nAs will be described below, this kind of property also results from the use of old-style (<code>{...}</code>) filters and properties on models with multiple initial states.\n</p>\n<div class='vspace'></div><h3>Old-style filters</h3>\n<p>In older versions of PRISM, filters were also available, but in a less expressive form. Previously, they were only usable on <code><strong>P</strong></code>, <code><strong>S</strong></code> or <code><strong>R</strong></code> properties and only a small set of filter operators were permitted. They were also specified in a different way, using braces (<code>{</code>...<code>}</code>). For compatibility with old properties files (and for compactness), these forms of filters are still allowed. These old-style forms of filters:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock78'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=78' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are equivalent to:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock79'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">min</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=79' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the first of the four properties above (i.e. an old-style filter of the form <code>{states}</code> will result in an error if <code>states</code> is not satisfied by exactly one state of the model. Older versions of PRISM just gave you the value for the first state state satisfying the filter, without warning you about this. If you want to recreate the old behaviour, just use a <code>first</code> filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock80'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">first</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=80' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Default filters</h3>\n<p>Finally, for completeness, we show what the <em>default</em> filters are in PRISM,\ni.e. how the way that PRISM returns values from properties by default\ncould have been achieved equivalently using filters.\n</p>\n<p class='vspace'>Queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock81'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=81' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock82'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=82' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock83'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=83' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as either:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock84'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=84' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the cases where there the model has a single initial state\nor multiple initial states, respectively.\n</p><hr />\n<h1>Properties Files</h1>\n<h3>Constants</h3>\n<p>Files containing properties to be analysed by PRISM can also contain constants, as is the case for model files.\nThese are defined in identical fashion, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock85'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span> = <span class=\"prismnum\">7</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span> = <span class=\"prismnum\">9.5</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">p</span> = <span class=\"prismnum\">0.01</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismident\">p</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">x</span>=<span class=\"prismident\">k</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=85' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As before, these constants can actually be left undefined and then later\nassigned either a single value or a range of values using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'>In fact, values such as the probability bounds for the <code><strong>P</strong></code> or <code><strong>S</strong></code> operators (like <code><strong>P</strong></code> above)\nand upper or lower bounds for the <code><strong>U</strong></code> operator (like <code> T</code> above)\ncan be arbitrary expressions, provided they are constant.\nFurthermore, expressions in the properties file can also refer to constants previous defined in the model file.\n</p>\n<p class='vspace'><a name='labels' id='labels'></a>\n</p><h3>Labels</h3>\n<p>Another feature of properties files is <em>labels</em>. These are a way of defining sets of states that will be referred to in properties (they correspond to <em>atomic propositions</em> in a temporal logic setting). As described <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>earlier</a>, labels can be defined in either model files or property files.\n</p>\n<p class='vspace'>Labels are defined using the keyword <code><strong>label</strong></code>, followed by a name (identifier) in double quotes, and then an expression which evaluates to a Boolean. Definition and usage of labels are illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock86'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ \"<span class=\"prismident\">safe</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">fail</span>\" ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=86' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Two special cases are the <code>\"init\"</code> and <code>\"deadlock\"</code> labels which are always defined.\nThese are true in initial states of the model and states where deadlocks were found (and, usually, fixed by adding self-loops), respectively.\n</p>\n<p class='vspace'><a name='names' id='names'></a>\n</p><h3>Property names</h3>\n<p>For convenience, properties can be annotated with <em>names</em>, as shown in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock87'>\r\n  <div class='sourceblocktext'><div class=\"prism\">\"<span class=\"prismident\">safe</span>\": <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">temperature</span> &gt; <span class=\"prismident\">t_max</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=87' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which gives the name <code>\"safe\"</code> to the property. It is then possible to include named properties as sub-expressions of other properties, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock88'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismident\">num_sensors</span>&gt;<span class=\"prismnum\">0</span> =&gt; \"<span class=\"prismident\">safe</span>\");<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=88' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the syntax for referring to named properties is identical to the syntax for labels. For this reason, property names must be disjoint from those of any existing labels.\n</p>\n<p class='vspace'>You can refer to property names when using the command-line switch <a class='wikilink' href='../RunningPRISM/ModelChecking.html#cl'><code>-prop</code></a> to specify which property is to be model checked.\n</p>\n<div class='vspace'></div><h3>Properties files</h3>\n<p>A PRISM properties file can contain any number of properties.\nIt is good practice, as shown in the examples above, to terminate each property with a semicolon. Currently, this is not enforced by PRISM (to prevent incompatibility with old properties files) but this may change in the future.\n</p>\n<p class='vspace'>Like model files, properties can also include any amount of white space (spaces, tabs, new lines, etc.) and C-style comments, which are both ignored.\nThe recommended file extension for PRISM properties is now <code>.props</code>.\nPreviously, though, the convention was to use extension <code>.pctl</code> for properties of DTMCs, MDPs or PTAs\nand extension <code>.csl</code> for properties of CTMCs, so these are still also valid.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 03:32 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/AllOnOnePage@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / All On One Page | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 03:32 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/AllOnOnePage@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / All On One Page | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 03:32 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/AllOnOnePage@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / AllOnOnePage </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Property Specification</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>In order to analyse a probabilistic model which has been specified and constructed in PRISM,\nit is necessary to identify one or more <em>properties</em> of the model\nwhich can be evaluated by the tool.\nPRISM's <em>property specification language</em> subsumes several well-known probabilistic temporal logics, including PCTL, CSL, probabilistic LTL and PCTL*.\nPCTL is used for specifying properties of discrete-time models such as DTMCs or PTAs,\nand also real-time models such as PTAs; CSL is an extension of PCTL for CTMCs;\nLTL and PCTL* can be used to specify properties of \ndiscrete-time models (or untimed properties of CTMCs).\nPRISM also supports most of the (non-probabilistic) temporal logic CTL.\n</p>\n<p class='vspace'>In fact, PRISM also supports numerous additional customisations and extensions of these two logics.\nFull details of the property specifications permitted in PRISM are provided in the following sections. The presentation given here is relatively informal. For the precise syntax and semantics of the various logics, see [<a class='wikilink' href='../Main/References.html#HJ94'>HJ94</a>],[<a class='wikilink' href='../Main/References.html#BdA95'>BdA95</a>] for PCTL, [<a class='wikilink' href='../Main/References.html#ASSB96'>ASSB96</a>],[<a class='wikilink' href='../Main/References.html#BKH99'>BKH99</a>] for CSL and, for example, [<a class='wikilink' href='../Main/References.html#Bai98'>Bai98</a>] for LTL and PCTL*. You can also find various pointers to useful papers in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>Before discussing property specifications in more detail,\nit is perhaps instructive to first illustrate some typical examples of properties which PRISM can handle.\nThe following are a selection of such properties.\nIn each case, we give both the PRISM syntax and a natural language translation:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the algorithm eventually terminates successfully with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> \"<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that more than 5 errors occur within the first 100 time units is less than 0.1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismident\">num_sensors</span> &lt; <span class=\"prismident\">min_sensors</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"in the long-run, the probability that an inadequate number of sensors are operational is less than 0.01\"\n</p>\n<p class='vspace'>Note that the above properties are all assertions,\ni.e. ones to which we would expect a \"yes\" or \"no\" answer.\nThis is because all references to probabilities are associated with an upper or lower bound\nwhich can be checked to be either true or false.\nIn PRISM, we can also directly specify properties which evaluate to a numerical value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ !<span class=\"prismident\">proc2_terminate</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">proc1_terminate</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that process 1 terminates before process 2 does\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">messages_lost</span> &gt; <span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the maximum probability that more than 10 messages have been lost by time <code>T</code>\" (for an MDP/PTA)\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the long-run probability that the queue is more than 75% full\"\n</p>\n<p class='vspace'>Furthermore, PRISM makes it easy to combine such properties into more complex expressions,\ncompute their values for a range of parameters\nand plot graphs of the results using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\nThis is often a very useful way of identifying interesting\npatterns or trends in the behaviour of a system.\nSee the <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a> section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a> for many examples of this kind of analysis.\n</p><hr />\n<h1>Identifying A Set Of States</h1>\n<p>One of the most fundamental tasks when specifying properties of a model\nis to identify particular sets or classes of states of the model.\nFor example, to verify a property such as\n\"the algorithm eventually terminates successfully with probability 1\",\nit is first necessary to identify the states of the model\nwhich correspond to situations where \"the algorithm has terminated successfully\".\nIn terms of the way temporal logics are usually presented,\nthese correspond to <em>atomic propositions</em>.\n</p>\n<p class='vspace'>In PRISM, this is achieved simply by writing an <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a> in the PRISM language which evaluates to a Boolean value. This expression will typically contain references to variables (and constants) from the model to which it relates. The set of states corresponding to this expression is those for which it evaluates to <code>true</code>. We say that the expression is \"satisfied\" in these states.\n</p>\n<p class='vspace'>For example, in the property given above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>the expression <code>num_errors &gt; 5</code> is used to identify states of the model where more than 5 errors have occurred.\n</p>\n<p class='vspace'>It is also common to use <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> to identify states in this way, like <code>\"terminate\"</code> in the example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Properties can refer to <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> either from the model to which the property relates, or included in the same <a class='wikilink' href='PropertiesFiles.html'>properties file</a>.\n</p><hr />\n<h1>The P Operator</h1>\n<p>One of the most important operators in the PRISM property specification language is the <code><strong>P</strong></code> operator, which is used to reason about the probability of an event's occurrence. This operator was originally proposed in the logic PCTL but also features in the other logics supported by PRISM, such as CSL. The <code><strong>P</strong></code> operator is applicable to all types of models supported by PRISM.\n</p>\n<p class='vspace'>Informally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a model if\n\"the probability that path property <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code>\".\nA typical example of a bound would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em> is greater than 0.98\". More precisely, <code>bound</code> can be any of <code>&gt;=p</code>, <code>&gt;p</code>, <code>&lt;=p</code> or <code>&lt;p</code>,\nwhere <code>p</code> is a PRISM language expression evaluating to a double in the range [0,1].\n</p>\n<p class='vspace'>The types of path property supported by PRISM and their semantics will be discussed shortly.\n</p>\n<div class='vspace'></div><h3>Nondeterminism</h3>\n<p>For models that can exhibit nondeterministic behaviour, such as MDPs or PTAs, some additional clarifications are necessary. Whereas for fully probabilistic models such as DTMCs and CTMCs, probability measures over paths are well defined (see e.g. [<a class='wikilink' href='../Main/References.html#KSK76'>KSK76</a>] and [<a class='wikilink' href='../Main/References.html#BKH99'>BKH99</a>], respectively), for nondeterministic models a probability measure can only be feasibly defined once all nondeterminism has been removed.\n</p>\n<p class='vspace'>Hence, the actual meaning of the property <code>P bound [ pathprop ]</code> in these cases is: \n\"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code> <em>for all possible resolutions of nondeterminism</em>\".\nThis means that, properties using the <code><strong>P</strong></code> operator then effectively reason about the\n<em>minimum</em> or <em>maximum</em> probability, over all possible resolutions of nondeterminism,\nthat a certain type of behaviour is observed.\nThis depends on the bound attached to the <code><strong>P</strong></code> operator:\na lower bound (<code>&gt;</code> or <code>&gt;=</code>) relates to minimum probabilities\nand an upper bound (<code>&lt;</code> or <code>&lt;=</code>) to maximum probabilities.\n</p>\n<div class='vspace'></div><h3>Quantitative properties</h3>\n<p>It is also very often useful to take a <em>quantitative</em> approach to probabilistic model checking, computing the actual probability that some behaviour of a model is observed,\nrather than just verifying whether or not the probability is above or below a given bound.\nHence, PRISM allows the <code><strong>P</strong></code> operator to take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These properties return a numerical rather than a Boolean value.\nThe <a class='wikilink' href='TheSOperator.html'>S</a> and <a class='wikilink' href='Reward-basedProperties.html'>R</a> operators, discussed later, can also be used in this way.\n</p>\n<p class='vspace'>As mentioned above, for nondeterministic models (MDPs or PTAs), either minimum or maximum probability values can be computed. Therefore, in this case, we have two possible types of property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which return the minimum and maximum probabilities, respectively.\n</p>\n<p class='vspace'>It is also possible to specify to which state the probability returned by a quantitative property refers. This is covered in the later section on <a class='wikilink' href='Filters.html'>filters</a>.\n</p>\n<div class='vspace'></div><h3>Path properties</h3>\n<p>PRISM supports a wide range of path properties that can be used with the <code><strong>P</strong></code> operator.\nA path property is a formula that evaluates to either true or false for a single path in a model.\nHere, we review some of the simpler properties that feature a single <em>temporal operator</em>,\nas used for example in the logics PCTL and CSL. Later, we briefly describe how PRISM also supports more complex LTL-style path properties.\n</p>\n<p class='vspace'>The basic different types of path property that can be used inside the <code><strong>P</strong></code> operator are:\n</p>\n<div class='vspace'></div><ul><li><code><strong>X</strong></code> : \"ne<strong>x</strong>t\"\n</li><li><code><strong>U</strong></code> : \"<strong>u</strong>ntil\"\n</li><li><code><strong>F</strong></code> : \"eventually\" (sometimes called \"<strong>f</strong>uture\")\n</li><li><code><strong>G</strong></code> : \"always\" (sometimes called \"<strong>g</strong>lobally\")\n</li><li><code><strong>W</strong></code> : \"<strong>w</strong>eak until\"\n</li><li><code><strong>R</strong></code> : \"<strong>r</strong>elease\"\n</li></ul><p class='vspace'>In the following sections, we describe each of these <em>temporal operators</em>. We then discuss the (optional) use of time bounds with these operators. Finally, we also discuss LTL-style path properties.\n</p>\n<div class='vspace'></div><h3>\"Next\" path properties</h3>\n<p>The property <code><strong>X</strong> prop</code> is true for a path if <code>prop</code> is true in its second state,\nAn example of this type of property, used inside a <code><strong>P</strong></code> operator, is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">X</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of the expression <code>y=1</code> being true in the next state is less than 0.01\".\n</p>\n<div class='vspace'></div><h3>\"Until\" path properties</h3>\n<p>The property <code>prop1 <strong>U</strong> prop2</code> is true for a path if\n<code>prop2</code> is true in some state of the path and <code>prop1</code> is true in all preceding states.\nA simple example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually equal to 2, and that <code>z</code> remains less than 2 up until that point, is greater than 0.5\".\n</p>\n<div class='vspace'></div><h3>\"Eventually\" path properties</h3>\n<p>The property <code><strong>F</strong> prop</code> is true for a path if <code>prop</code> eventually becomes true at some point along the path. The <code><strong>F</strong></code> operator is in fact a special case of the <code><strong>U</strong></code> operator (you will often see <code> <strong>F</strong> prop</code> written as <code><strong>true</strong> <strong>U</strong> prop</code>). A simple example is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>&gt;<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually greater than 2is less than 0.1\".\n</p>\n<div class='vspace'></div><h3>\"Globally\" path properties</h3>\n<p>Whereas the <code><strong>F</strong></code> operator is used for \"reachability\" properties, <code><strong>G</strong></code> represents \"invariance\". The property <code><strong>G</strong> prop</code> is true of a path if <code>prop</code> remains true at all states along the path. Thus, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>states that, with probability at least 0.99, <code>z</code> never exceeds 10.\n</p>\n<div class='vspace'></div><h3>\"Weak until\" and \"release\" path properties</h3>\n<p>Like <code><strong>F</strong></code> and <code><strong>G</strong></code>, the operators <code><strong>W</strong></code> and <code><strong>R</strong></code> are derivable from other temporal operators.\n</p>\n<p class='vspace'>Weak until (<code>a <strong>W</strong> b</code>), which is equivalent to <code>(a <strong>U</strong> b) | <strong>G</strong> a</code>, requires that <code>a</code> remains true until <code>b</code> becomes true, but does not require that <code>b</code> ever does becomes true (i.e. <code>a</code> remains true forever). For example, a weak form of the until example used above is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which states that, with probability greater than 0.5, either <code>z</code> is always less than 2, or it is less than 2 until the point where <code>z</code> is 2.\n</p>\n<p class='vspace'>Release (<code>a <strong>R</strong> b</code>),  which is equivalent to <code>!(!a U !b)</code>, informally means that <code>b</code> is true until <code>a</code> becomes true, or <code>b</code> is true forever.\n</p>\n<p class='vspace'><a name='bounded' id='bounded'></a>\n</p><h3>\"Bounded\" variants of path properties</h3>\n<p>All of the temporal operators given above, with the exception of <code><strong>X</strong></code>, have \"bounded\" variants, where an additional time bound is imposed on the property being satisfied.\nThe most common case is to use an upper time bound, i.e. of the form \"<code>&lt;=t</code>\" or \"<code>&lt;t</code>\", where <code>t</code> is a PRISM expression evaluating to a constant, non-negative value.\n</p>\n<p class='vspace'>For example, a bounded until property <code>prop1 <strong>U</strong>&lt;=t prop2</code>, is satisfied along a path if <code>prop2</code> becomes true within <code>t</code> steps and <code>prop1</code> is true in all states before that point.\nA typical example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">y</span>&lt;<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of <code>y</code> first exceeding 3 within 7 time units is greater than or equal to 0.98\". Similarly:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state if \"the probability of <code>y</code> being equal to 4 within 7 time units is greater than or equal to 0.98\" and:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true if the probability of <code>y</code> staying equal to 4 for 7 time units is at least 0.98.\n</p>\n<p class='vspace'>The time bound can be an arbitrary (constant) expression,\nbut note that you may need to bracket it,\nas in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=(<span class=\"prismnum\">2</span>*<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>) <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use lower time-bounds (i.e. <code>&gt;=t</code> or <code>&gt;t</code>) and time intervals <code>[t1,t2]</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&gt;=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">20</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which refer to the probability of <code>y</code> becoming equal to 4 after 10 or more time units, and after between 10 and 20 time-units respectively.\n</p>\n<p class='vspace'>For CTMCs, the time bounds can be any (non-negative) numerical values - they are not restricted to integers, as for discrete-time models.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.25</span> [ <span class=\"prismident\">y</span>&lt;=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">6.5</span> <span class=\"prismident\">y</span>&gt;<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means that the probability of <code>y</code> being greater than 1 within 6.5 time-units (and remaining less than or equal to 1 at all preceding time-points) is at least 0.25.\n</p>\n<div class='vspace'></div><h3>Transient probabilities</h3>\n<p>We can also use the bounded <code><strong>F</strong></code> operator to refer to a single time instant, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock24'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">10</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=24' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or, equivalently:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock25'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=25' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>both of which give the probability of <code>y</code> being 6 at time instant 10.\n</p>\n<p class='vspace'><a name='ltl' id='ltl'></a>\n</p><h3>LTL-style path properties</h3>\n<p>PRISM also supports probabilistic model checking of the temporal logic LTL (and, in fact, PCTL*). LTL provides a richer set of path properties for use with the <code><strong>P</strong></code> operator, by permitting temporal operators to be combined. Here are a few examples of properties expressible using this functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock26'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">F</span> ( \"<span class=\"prismident\">request</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">ack</span>\") ) ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=26' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"with probability greater than 0.99, a request is eventually received, followed immediately by an acknowledgement\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock27'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">send</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=27' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"a message is sent infinitely often with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock28'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">G</span> (\"<span class=\"prismident\">error</span>\" &amp; !\"<span class=\"prismident\">repair</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=28' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of an error occurring that is never repaired\n</p>\n<p class='vspace'>Note that logical operators have precedence over temporal ones, so you will often need to include parentheses when using logical operators, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock29'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\") &amp; (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=29' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For temporal operators, unary operators (such as <code><strong>F</strong></code>, <code><strong>G</strong></code> and <code><strong>X</strong></code>) have precedence over binary ones (such as <code><strong>U</strong></code>). Unary operators can be nested, without parentheses, but binary ones cannot.\n</p>\n<p class='vspace'>So, these are allowed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock30'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">a</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ (\"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\") <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=30' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>but this is not:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock31'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=31' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>The S Operator</h1>\n<p>The <code><strong>S</strong></code> operator is used to reason about the <em>steady-state</em> behaviour of a model,\ni.e. its behaviour in the <em>long-run</em> or <em>equilibrium</em>.\nPRISM currently only provides support for DTMCs and CTMCs.\nThe definition of steady-state (long-run) probabilities for finite DTMCS and CTMCs is well defined (see e.g. [<a class='wikilink' href='../Main/References.html#Ste94'>Ste94</a>]).\nInformally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock32'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">prop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=32' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a DTMC or CTMC if\n\"starting from <em>s</em>, the steady-state (long-run) probability of being in a state which satisfies the (Boolean-valued) PRISM property <code>prop</code>, meets the bound <code>bound</code>\".\nA typical example of this type of property would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock33'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.05</span> [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=33' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the long-run probability of the queue being more than 75% full is less than 0.05\".\n</p>\n<p class='vspace'>Like the <code><strong>P</strong></code> <a class='wikilink' href='ThePOperator.html'>operator</a>, the <code><strong>S</strong></code> operator can be used in a <em>quantitative</em> form, which returns the actual probability value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock34'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=34' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and can be further customised with the use of <a class='wikilink' href='Filters.html'>filters</a>.\n</p><hr />\n<h1>Reward-based Properties</h1>\n<p>PRISM models can be augmented with information about <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>rewards</a> (or, equivalently, costs).\nThe tool can analyse properties which relate to the <em>expected values</em> of these rewards.\nThis is achieved using the <code><strong>R</strong></code> operator, which works in a similar fashion to the\n<code><strong>P</strong></code> and <code><strong>S</strong></code> operators, and can be used either in a Boolean-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock35'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=35' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>bound</code> takes the form <code>&lt;r</code>, <code>&lt;=r</code>, <code>&gt;r</code> or <code>&gt;=r</code> for an expression <code>r</code> evaluating to a non-negative double,\nor a real-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock36'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">query</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=36' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>query</code> is <code>=?</code>, <code>min=?</code> or <code>max=?</code>.\nIn the latter case, <a class='wikilink' href='Filters.html'>filters</a> can be used, as for the <code><strong>P</strong></code> and <code><strong>S</strong></code> operators.\n</p>\n<p class='vspace'>Informally, \"<code><strong>R</strong> bound [ rewardprop ]</code>\" is true in a state of a model if\n\"the expected reward associated with <code>rewardprop</code> of the model when starting from that state''\nmeets the bound <code>bound</code> and \"<code><strong>R</strong> query [ rewardprop ]</code>\"  returns the actual expected reward value.\n</p>\n<p class='vspace'>There are various different types of reward properties:\n</p>\n<div class='vspace'></div><ul><li>\"reachability reward\": <code><strong>F</strong> prop</code>\n</li><li>\"co-safe LTL reward\": e.g. <code><strong>F</strong> (prop1 &amp; <strong>F</strong> prop2)</code>\n</li><li>\"cumulative reward\" : <code><strong>C</strong>&lt;=t</code>\n</li><li>\"total reward\" : <code><strong>C</strong></code>\n</li><li>\"instantaneous reward\" : <code><strong>I</strong>=t</code>\n</li><li>\"steady-state reward\" : <code><strong>S</strong></code>.\n</li></ul><p class='vspace'>Below, we consider each of these cases in turn.\nThe descriptions here are kept relatively informal.\nPrecise definitions for most of these can be found in, for example,\n[<a class='wikilink' href='../Main/References.html#KNP07a'>KNP07a</a>] (for DTMCs and CTMCs) or [<a class='wikilink' href='../Main/References.html#FKNP11'>FKNP11</a>] (for MDPs).\n</p>\n<div class='vspace'></div><h3>\"Reachability reward\" properties</h3>\n<p>\"Reachability reward\" properties associate a reward with each path of a model.\nMore specifically, they refer to the reward accumulated along a path until a certain point is reached.\nThe manner in which rewards are accumulated depends on the model type.\nFor DTMCs and MDPs, the total reward for a path is the sum of the state rewards for each state along the path\nplus the sum of the transition rewards for each transition between these states.\nThe situation for CTMCs is similar, except that the state reward assigned to each state\nof the model is interpreted as the <em>rate</em> at which rewards are accumulated in that state,\ni.e. if <em>t</em> time units are spent in a state with state reward <em>r</em>,\nthe reward accumulated in that state is <em>r</em> x <em>t</em>.\nHence, the total reward for a path in a CTMC is the sum of these products for each state along the path\nplus the sum of the transition rewards for each transition between these states.\n</p>\n<p class='vspace'>The reward property \"<code>F prop</code>\" corresponds to the reward cumulated along a path\nuntil a state satisfying property <code>prop</code> is reached,\nwhere rewards are cumulated as described above.\nState rewards for the <code>prop</code>-satisfying state reached are not included in the cumulated value.\nIn the case where the probability of reaching a state satisfying <code>prop</code> is less than 1, the reward is equal to infinity.\n</p>\n<p class='vspace'>A common application of this type of property is the case when the rewards associated with the model correspond to time.\nOne can then state, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock37'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">9.5</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=37' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"the expected time taken to reach, from <em>s</em>, a state where <code>z</code> equals 2 is less than or equal to 9.5\".\n</p>\n<div class='vspace'></div><h3>\"Co-safe LTL reward\" properties</h3>\n<p>These generalise the \"reachability\" properties above. Again, reward is accumulated along a path up until some point,\nbut this is specified in a more general way, by giving a formula in the co-safe fragment of linear temporal logic (LTL).\nRewards are accumulated up until the point where the formula is first satisfied. For example, this property, for a DTMC or CTMC,\nqueries the expected reward accumulated until first <code>goal</code> equals 1 and then subsequently <code>goal</code> equals 2:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock38'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">F</span> (<span class=\"prismident\">goal</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismkeyword\">F</span> <span class=\"prismident\">goal</span>=<span class=\"prismnum\">2</span>) ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=38' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and this property, for an MDP, minimises the expected reward until <code>loc</code> equals 1,\nhaving passed only through states where <code>loc</code> never equals 4\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock39'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismident\">loc</span>!=<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">loc</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=39' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As for reachability rewards, if the probability of satisfying the formula is less than 1,\nthen the expected reward is defined to be infinite.\n</p>\n<p class='vspace'>Intuitively, a <em>co-safe</em> formula is one that is satisfied within a finite period of time,\nand remains true for ever once it becomes true for the first time.\nFor simplicity, PRISM actually supports the <em>syntactic</em> co-safe fragment of LTL,\nwhich is defined as any LTL formula that only uses the temporal operators <code><strong>F</strong></code>, <code><strong>U</strong></code> and <code><strong>X</strong></code>\n(but not <code><strong>G</strong></code>, for example).\nPRISM's notation for LTL formulas is described <a class='wikilink' href='ThePOperator.html'>here</a>.\n</p>\n<div class='vspace'></div><h3>\"Cumulative reward\" properties</h3>\n<p>\"Cumulative reward\" properties also associate a reward with each path of a model,\nbut only up to a given time bound.\nThe property <code>C&lt;=t</code> corresponds to the reward cumulated along a path\nuntil <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\nState and transition rewards along a path are cumulated exactly as described in the previous section.\n</p>\n<p class='vspace'>A typical application of this type of property is the following.\nConsider a model of a disk-drive controller which includes a queue of incoming disk requests.\nIf we assign a reward of 1 to each transition of the model\ncorresponding to the situation where an incoming request is lost because the queue is full,\nthen the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock40'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">15.5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=40' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would return, for a given state of the model,\n\"the expected number of lost requests within 15.5 time units of operation\".\n</p>\n<p class='vspace'><a name='total' id='total'></a>\n</p><h3>\"Total reward\" properties</h3>\n<p>\"Total reward\" properties refer to the accumulation of state and transition rewards\nin the same way as for \"reachability reward\" and \"cumulative reward\" properties,\nbut the rewards is accumulated indefinitely,\ni.e. the total reward accumulated along the whole (infinite) path.\nNote that this means that, unless a path ends up remaining forever in states with zero reward,\nthe total reward will be infinite.\n</p>\n<p class='vspace'>Re-using the reward structure in the previous example,\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock41'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=41' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>returns \"the expected total number of lost requests\".\n</p>\n<div class='vspace'></div><h3>\"Instantaneous reward\" properties</h3>\n<p>\"Instantaneous reward\" properties refer to the reward of a model at a particular instant in time.\nThe reward property <code>I=t</code> associates with a path the reward in the state \nof that path when exactly <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\n</p>\n<p class='vspace'>Returning to our example from the previous section of a model for a disk-request queue in a disk-drive controller,\nconsider the case where the rewards assigned to each state of the model give the current size of the queue in that state.\nThen, the following property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock42'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;<span class=\"prismnum\">4.4</span> [ <span class=\"prismkeyword\">I</span>=<span class=\"prismnum\">100</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=42' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would be true in a state <em>s</em> of the model if\n\"starting from <em>s</em>, the expected queue size exactly 100 time units later is less than 4.4\".\nNote that, for this type of reward property, state rewards for CTMCs do not have to refer to rates;\nthey can refer to any instantaneous measure of interest for a state.\n</p>\n<div class='vspace'></div><h3>\"Steady-state reward\" properties</h3>\n<p>Unlike the previous three types of property,\n\"steady-state reward\" properties relate not to paths, but rather to the reward in the long-run.\nA typical application of this type of property would be, in the case where\nthe rewards associated with the model correspond to power consumption, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock43'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">0.7</span> [ <span class=\"prismkeyword\">S</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=43' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"starting from <em>s</em>, the long-run average power consumption is less than 0.7\".\n</p>\n<div class='vspace'></div><h3>Which reward structure?</h3>\n<p>In the case where a PRISM model has multiple <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structures</a> you may need to specify which reward structure your property refers to. This is done by placing the information in braces (<code>{}</code>) after the <code>R</code> operator. You can do so either using the name assigned to a reward structure (if any) or using the index (where <code>1</code> means the first rewards structure in the PRISM model file, <code>2</code> the second, etc.). Examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock44'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">num_failures</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">10.0</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismnum\">2</span>}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=44' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note that when using an index to specify the reward structure, you can actually put any expression that evaluates to an integer. This allows you to, for example, write a property of the form <code>R{c}=?[...]</code> where <code>c</code> is an undefined integer constant. You can then vary the value of <code>c</code> in an experiment and compute values for several different reward structures at once.\n</p>\n<p class='vspace'>If you don't specify a reward structure to the <code>R</code> operator, by default, the first one in the model file is used.\n</p>\n<div class='vspace'></div><h3>Availability</h3>\n<p>There are currently a few restrictions on the model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a> that can be used for some reward properties. The following table summarises the currently availability, where S, M, H and E denote the \"sparse\", \"MTBDD\", \"hybrid\" and \"explicit\" engines, respectively, for DTMCs, CTMCs and MDPs. For PTAs, support for rewards is currently quite restrictive; see the later section on <a class='wikilink' href='Real-timeModels.html'>real-time model properties</a> for details.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><code><strong>F</strong></code></td><td  align='center'>cosafe</td><td  align='center'><code><strong>C</strong>&lt;=t</code></td><td  align='center'><code><strong>C</strong></code></td><td  align='left'><code><strong>I</strong>=t</code></td><td  align='right'><code><strong>S</strong></code></td></tr>\n<tr ><td  align='center'><strong>DTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>CTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>MDPs</strong></td><td  align='center'>SM-E</td><td  align='center'>SMHE</td><td  align='center'>S--E</td><td  align='center'>----</td><td  align='center'>SM-E</td><td  align='right'>----</td></tr>\n</table><hr />\n<h1>Multi-objective Properties</h1>\n<p>For MDPs, PRISM supports <em>multi-objective</em> properties. Consider a property that uses the <code><strong>P</strong></code> operator. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock45'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=45' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This states that, <em>for all</em> strategies (or policies) of the MDP, the probability of reaching an <code>\"error\"</code> state is less than 0.01.\n</p>\n<p class='vspace'>Multi-objective queries differ in two important ways. Firstly, (by default) they ask about the <em>existence</em> of a strategy. Secondly they refer to <em>multiple</em> properties of a strategy. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock46'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=46' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means: \"does there exist a strategy of the MDP under which the probability of reaching an <code>\"error1\"</code> state is less than 0.01 <em>and</em> the probability of reaching an <code>\"error2\"</code> state is less than 0.02?\"\n</p>\n<p class='vspace'>To use the terminology from [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>], the above is an \"achievability\" query (i.e., is this combination of objectives achievable by some strategy?). PRISM also supports two other kinds of multi-objective query: \"numerical\" and \"Pareto\" queries.\n</p>\n<p class='vspace'>A \"numerical\" query looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock47'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=47' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>meaning \"what is the minimum possible probability of reaching <code>\"error1\"</code>, over all strategies of the MDP for which the probability of reaching <code>\"error2\"</code> is less than 0.02?\".\n</p>\n<p class='vspace'>A \"Pareto\" queries leaves both of the objectives unbounded, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock48'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=48' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This asks PRISM to compute (approximately), the <em>Pareto curve</em> for this pair objectives. Intuitively, this is the set of pairs of probabilities (of reaching <code>\"error1\"</code>/<code>\"error2\"</code>) such that reducing one probability any more would necessitate an increase in the other probability.\n</p>\n<div class='vspace'></div><h3>Types of Objectives</h3>\n<p>For simplicity, the examples above all refer to the probability of reaching classes of states in the model. Other types of property (objective) are also possible.\n</p>\n<p class='vspace'>Firstly, we can extend the examples above by referring to the probability of any\n<a class='wikilink' href='ThePOperator.html#ltl'>LTL</a> property. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock49'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=49' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9?\".\n</p>\n<p class='vspace'>We can also use more than 2 objectives, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock50'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.95</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good3</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=50' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9 and the probability of visiting <code>\"good3\"</code> states infinitely often remains at least 0.95?\".\n</p>\n<p class='vspace'>Multi-objective queries can also refer to the expected total cumulative value of a reward structure. We write such properties in the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock51'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}<span class=\"prismkeyword\">min</span>=?[ <span class=\"prismkeyword\">C</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">energy</span>\"}&lt;=<span class=\"prismnum\">1.45</span> [ <span class=\"prismkeyword\">C</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=51' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the minimum expected cumulative value of reward structure <code>\"time\"</code>, such that the expected cumulative value of reward structure <code>\"energy\"</code> is below 1.45.\n</p>\n<p class='vspace'>Note that this <code><strong>C</strong></code> reward operator differs from the <code><strong>F</strong> \"target\"</code> operator, usually used for standard (single-objective) MDP model checking. Whereas the <code><strong>F</strong> \"target\"</code> operator refers to the expected reward accumulated until a <code>\"target\"</code> state is reached the <code><strong>C</strong></code> operator refers to the expected <em>total</em> reward.\n</p>\n<p class='vspace'>A few important notes regarding rewards:\n</p>\n<div class='vspace'></div><ul><li>Currently only transition rewards are supported; state rewards are not.\n<div class='vspace'></div></li><li>Certain assumptions are made regarding the finiteness of rewards; see p.7 of [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>] for details.\n</li></ul><p class='vspace'>Finally, time-bounded variants of both probabilistic reachability and expected cumulative rewards objectives can be used. Here is an example that uses the latter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock52'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">power</span>\"}<span class=\"prismkeyword\">min</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">queue</span>\"}&lt;=<span class=\"prismident\">r</span> [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=52' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Solution Methods</h3>\n<p>PRISM can perform multi-objective model checking using two distinct solution methods, which are described in [<a class='wikilink' href='../Main/References.html#FKN+11'>FKN+11</a>] and [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>]. The former is based on the use of linear programming; the latter reduces multi-objective model checking to a series of simpler problems, solved using value iteration (or the Gauss-Seidel variant of value iteration). The default is \"Value iteration\". You can change this in the GUI using the option \"MDP multi-objective solution methods\", or using the command-line switches <code>-lp</code>, <code>-valiter</code>, <code>-gs</code>.\n</p>\n<p class='vspace'>There are some restrictions for the different methods, e.g.\n</p>\n<div class='vspace'></div><ul><li>Linear programming does not support time-bounded properties or Pareto queries\n</li></ul><div class='vspace'></div><hr />\n<h1>Real-time Models</h1>\n<p>The classes of property that can be checked for real-time models (PTAs and POPTAs) are currently more restricted than for the other kinds of models that PRISM supports. This is because the model checking procedures are quite different for this type of model. We describe these restrictions here. The situation is also dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is being used.\n</p>\n<p class='vspace'>For the \"<strong>stochastic games</strong>\" engine, we essentially only allow unbounded or time-bounded probabilistic reachability properties, i.e. properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock53'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=53' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>target</code> is a Boolean-valued expression that does not include references to any clock variables and <code>T</code> is an integer-valued expression. The <code><strong>P</strong></code> operator cannot be nested and the <code><strong>S</strong></code> and <code><strong>R</strong></code> operators are not supported.\n</p>\n<p class='vspace'>The \"<strong>backwards reachability</strong>\" engine is similar but currently only handles maximum probabilities.\n</p>\n<p class='vspace'>For the \"<strong>digital clocks</strong>\" engine, there is slightly more flexibility,\ne.g. until (<code><strong>U</strong></code>) properties are allowed, as are clock variables in expressions and arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock54'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=54' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This engine, like the \"stochastic games\" engine, does not allowed nested properties. Also, references to clocks must, like in the modelling language, not use strict comparisons\n(e.g. <code>x&lt;=5</code> is allowed, <code>x&lt;5</code> is not).\n</p>\n<p class='vspace'>The digital clocks also has support for rewards:\nit is possible to check reachability reward properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock55'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=55' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Reward structures specified in the model, though, must not depend on clock variables.\nFormally, the class of PTAs with this kind of reward structure is sometime called <em>linearly priced PTAs</em> (see e.g. [<a class='wikilink' href='../Main/References.html#KNPS06'>KNPS06</a>].\n</p>\n<p class='vspace'>The digital clocks method is based on a language-level translation from a PTA model to an MDP one. If you want to see the MDP PRISM model that was generated, add the switch <code>-exportdigital digital.nm</code> when model checking property to export the model file to <code>digital.nm</code>.\n</p><hr />\n<h1>Partially Observable Models</h1>\n<p>For partially observable models (POMDPs and POPTAs),\nPRISM uses the same property language as the their\nfully observational equivalents (MDPs and PTAs).\nHowever, a more limited range of properties are available.\nFor POMDPs, PRISM currently supports probabilistic reachability,\nprobabilistic until, or expected reachability rewards properties, i.e.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock56'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=56' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or bounded variants with a probability/threshold instead\nof the <code>min=?</code> or <code>max=?</code>.\n</p>\n<p class='vspace'>For the verification methods currently implemented,\nthere are a few additional restrictions.\nFirstly, the <code>target</code> (and <code>remain</code>) expression appearing\nin the property must be an observable.\nIn other words, if any state of the POMDP satisfies the expression,\nthen all other observationally equivalent states must also satisfy it.\nThis is easily achieved by only using either observable variables\nor named observables in the expression, but that is not required.\nSecondly, probabilities and expected rewards are only computed from a single state.\n</p>\n<p class='vspace'>POPTAs are currently verified using the \"digital clocks\" approach to\ntranslate them into a POMDP, so they inherit the same\n<a class='wikilink' href='Real-timeModels.html'>restrictions</a>\n(that strict or diagonal clock comparisons are not allowed).\nHowever for POPTAs, time-bounded probabilistic reachability is also supported.\n</p><hr />\n<h1>Uncertain Models</h1>\n<p>For uncertain models, currently interval MDPs (IMDPs) or interval DTMCs (IDTMCs), PRISM performs <em>robust</em> verification, which considers the best- or worst-case behaviour that can arise depending on the way that probabilities are selected from intervals.\n</p>\n<p class='vspace'>For example, instead of a property for a DTMC such as\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock57'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=57' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which asks for the probability to reach a state satisfying <code>\"goal\"</code>, IDTMCs use MDP-style queries:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock58'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=58' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which compute the minimum or maximum possible probability that can arise.\n</p>\n<p class='vspace'>Similarly, for an IMDP, there are now two separate quantifications, firstly over strategies (policies) and secondly over the distinct ways that transition probabilities can be selected from intervals, for which <code>min</code> or <code>max</code> appear in that order in the query. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock59'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmaxmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmaxmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=59' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>return the minimum and maximum values, respectively, over resolutions of transition probabilities for the maximum probability of reaching <code>\"goal\"</code>. Similarly, <code>minmin</code> and <code>minmax</code> are used for the minimum probability of reaching <code>\"goal\"</code>. Model checking is supported for:\n</p>\n<div class='vspace'></div><ul><li>the <code><strong>P</strong></code> operator, including single temporal operators and LTL formulae\n</li><li>the <code><strong>R</strong></code> operator, for the expected reward to reach a target or satisfy a co-safe LTL formula\n</li></ul><div class='vspace'></div><hr />\n<h1>Non-Probabilistic Properties</h1>\n<p>PRISM also supports model checking of the non-probabilistic temporal logics CTL (computation tree logic) and LTL (linear temporal logic).\nProperties in these logics use the <code><strong>A</strong></code> (for all) and <code><strong>E</strong></code> (there exists) operators,\ninstead of the probabilistic <code><strong>P</strong></code> operator used in many other properties supported by PRISM.\n</p>\n<p class='vspace'>Properties take the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock60'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">A</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=60' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which are true in a state <em>s</em> of a model if\n\"path property <code>pathprop</code> is satisfied by <em>all</em> paths from state <em>s</em>\"\nand\n\"path property <code>pathprop</code> is satisfied by <em>some</em> path from state <em>s</em>\",\nrespectively.\nThe syntax for LTL formulas is the same as those allowed within the <a class='wikilink' href='ThePOperator.html#ltl'>P operator</a>.\n</p>\n<p class='vspace'>Example properties include:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock61'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ] <span class=\"prismcomment\">// There exists a path that reaches a state satisfying \"goal\"</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span> ] <span class=\"prismcomment\">// Variable x is always at most 10 along all paths of the model</span><br/>\n<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">ready</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">launch</span>\") ] <span class=\"prismcomment\">// There exists a path along which label \"ready\" eventually becomes true and label \"launch\" is true immediately afterwards</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span>) | (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>) ] <span class=\"prismcomment\">// Along all paths, either x=1 or x=2 is true infinitely often</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=61' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Counterexamples and Witnesses</h3>\n<p>If you check a CTL property of the form <code>A [ G \"inv\" ]</code> and it is false, PRISM will generate a counterexample in the form of a path that reaches a state where <code>\"inv\"</code> is not true. This is displayed either in the simulator (from the GUI) or at the command-line. Similarly, if you check <code>E [ F \"goal\" ]</code> and the result is true, a witness (a path reaching a <code>\"goal\"</code> state) will be generated.\n</p><hr />\n<h1>Syntax And Semantics</h1>\n<h3>Syntax</h3>\n<p>The syntax of the PRISM property specification language subsumes various probabilistic temporal logics, including PCTL, CSL, (probabilistic) LTL, PCTL* and CTL. Informally, the syntax can be summarised as follows: a property can be any valid, well-typed PRISM <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a>, which (optionally) also includes the probabilistic operators discussed previously (<code><strong>P</strong></code>, <code><strong>S</strong></code> and <code><strong>R</strong></code>) and the non-probabilistic (CTL) ones <code><strong>A</strong></code> and <code><strong>E</strong></code>). This mean that any of the following operators can be used:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li><li><code><strong>P</strong></code> (probabilistic operator)\n</li><li><code><strong>S</strong></code> (steady-state operator)\n</li><li><code><strong>R</strong></code> (reward operator)\n</li><li><code><strong>A</strong></code> (for-all operator)\n</li><li><code><strong>E</strong></code> (there-exists operator)\n</li></ul><p class='vspace'>This allows you to write any property expressible in logics such as PCTL and CSL. For example, CSL allows you to nest <code><strong>P</strong></code> and <code><strong>S</strong></code> operators:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock62'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>&gt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">S</span>&gt;<span class=\"prismnum\">0.9</span>[ <span class=\"prismident\">num_servers</span> &gt;= <span class=\"prismnum\">5</span> ] ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=62' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of it taking more than 2 hours to get to a state from which the long-run probability of at least 5 servers being operational is &gt;0.9\"\n</p>\n<p class='vspace'>You can also express various arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock63'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">3600</span>,<span class=\"prismnum\">7200</span>] <span class=\"prismident\">oper</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=63' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability that the system is <strong>not</strong> operational at any point during the second hour of operation\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock64'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">oper</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">t</span> ] / <span class=\"prismident\">t</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=64' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the expected fraction of time that the system is available (i.e. the expected interval availability) in the time interval [0, t]\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock65'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">fail_A</span> ] / <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">any_fail</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=65' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the (conditional) probability that component A eventually fails, given\nthat at least one component fails\"\n</p>\n<div class='vspace'></div><h3>Semantics</h3>\n<p>We omit a formal presentation of the semantics of the PRISM property language. The semantics of the probabilistic temporal logics that the language incorporates can be found from a variety of sources. See for example the pointers given in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>It is worth, however, clarifying a few points specific to PRISM. A property is evaluated with respect to a particular state of a model. Depending on the type of the property, this value may either be a Boolean, an integer or a double. When performing model checking, PRISM usually has to actually compute the value for <em>all</em> states of the model but, for clarity, will by default report just a single value. Typically, this is the value for the (single) initial state of the model. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock66'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=66' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will report the probability, from the initial state of the model, of reaching an \"error\" state.\nThis:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock67'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=67' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will return <code>true</code> if and only if the probability, from the initial state, is greater than 0.5.\n</p>\n<p class='vspace'><strong>Note:</strong> This is contrast to older versions of PRISM, which treated numerical and Boolean-valued properties differently in this respect.\n</p>\n<p class='vspace'>For models with <a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>multiple initial states</a>, we need to adapt these definitions slightly. In this case, the two properties above will yield, respectively:\n</p>\n<div class='vspace'></div><ul><li>the range of values (over all initial states) of the probability of reaching \"error\"\n<div class='vspace'></div></li><li><code>true</code> if and only if the probability is greater than 0.5 from <em>all</em> initial states.\n</li></ul><p class='vspace'>You can also ask PRISM to return different values using <a class='wikilink' href='Filters.html'>filters</a>,\nwhich are described in the next section.\n</p><hr />\n<h1>Filters</h1>\n<p>As discussed above, when reporting the result of model checking a property, PRISM will by default return the value for the (single) initial state of the model. However, since PRISM in fact usually has to compute values for <em>all</em> states simultaneously, you can customise PRISM properties to obtain different results. This is done using <em>filters</em>.\n</p>\n<p class='vspace'>Filters are created using the <code>filter</code> keyword. They take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock68'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=68' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>op</code> is the filter <em>operator</em> (see below), <code>prop</code> is any PRISM property and <code>states</code> is a Boolean-valued expression identifying a set of states over which to apply the filter.\n</p>\n<p class='vspace'>In fact, the <code>states</code> argument is optional; if omitted, the filter is applied over all states. So, the following properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock69'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismkeyword\">true</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=69' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Here's a simple example of a filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock70'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=70' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This gives the <em>maximum</em> value, starting from any state satisfying <code>x=0</code>, of the probability of reaching an \"error\" state.\n</p>\n<p class='vspace'>Here's another simple example,\nwhich checks whether, <em>starting from any reachable state</em>,\nwe eventually reach a \"done\" state with probability 1.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock71'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=71' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We could modify this property slightly to instead check whether, from any state that satisfies the label \"ready\", we eventually reach a \"done\" state with probability 1. This could be done with either of the following two equivalent properties:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock72'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, \"<span class=\"prismident\">ready</span>\" =&gt; <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ], \"<span class=\"prismident\">ready</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=72' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Note:</strong> In older versions of PRISM, the property above could be written just as <code>\"ready\" =&gt; P&gt;=1 [ F \"done\" ]</code> since the result was checked for all states by default, not just the <a class='wikilink' href='SyntaxAndSemantics.html'>initial state</a>. Now, you need to explicitly include a filter, as shown above, to achieve this.\n</p>\n<div class='vspace'></div><h3>Types of filter</h3>\n<p>Most filters of the form <code>filter(op, prop, states)</code>\napply some operator <code>op</code> to the values of property <code>prop</code>\nfor all the states satisfying <code>states</code>,\nresulting in a single value.\nThe full list of filter operators <code>op</code> in this category is:\n</p>\n<div class='vspace'></div><ul><li><code>min</code>: the minimum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>max</code>: the maximum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>count</code>: counts the number of states satisfying <code>states</code> for which <code>prop</code> is true\n</li><li><code>sum</code> (or <code>+</code>): sums the value of <code>prop</code> for states satisfying <code>states</code>\n</li><li><code>avg</code>: the average value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>first</code>: the value of <code>prop</code> for the first (lowest-indexed) state satisfying <code>states</code>\n</li><li><code>range</code>: the range (interval) of values of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>forall</code> (or <code>&amp;</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for all states satisfying <code>states</code>\n</li><li><code>exists</code> (or <code>|</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for some states satisfying <code>states</code>\n</li><li><code>state</code>: returns the value for the single state satisfying <code>states</code> (if there is more than one, this is an error)\n</li></ul><p class='vspace'>There are also a few filters that, rather than returning a single value, return different values for each state, like a normal PRISM property:\n</p>\n<div class='vspace'></div><ul><li><code>argmin</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the minimum value of <code>prop</code>\n</li><li><code>argmax</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the maximum value of <code>prop</code>\n</li><li><code>print</code>: does not change the result of <code>prop</code> but prints the (non-zero) values to the log\n</li><li><code>printall</code>: like <code>print</code>, but displays <em>all</em> values, even for states where the value is zero\n</li></ul><div class='vspace'></div><h3>More examples</h3>\n<p>Here are some further illustrative examples of properties that use filters.\n</p>\n<p class='vspace'>Filters provide a quick way to <em>print</em> the results of a model checking query for several states. In most cases, for example, a <code>P=?</code> query just returns the probability from the initial state. To see the probability for all states satisfying <code>x&gt;2</code>, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock73'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">P</span>=? [ ... ], <span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">2</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=73' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Values are printed in the log (i.e. to the \"Log\" tab in the GUI or to the terminal from the command-line). For small models, you could omit the final <code>states</code> argument (<code>x&gt;2</code> here) and view the probabilities from all states. You can also use PRISM's <a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>verbose</a> mode to view values for all states, but filters provide an easier and more flexible solution.\n<code>print</code> filters do not actually alter the result returned so, in the example above, PRISM will still return the probability for the initial state, in addition to printing other probabilities in the log.\n</p>\n<p class='vspace'>You can also use <code>print</code> filters to display lists of states. For example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock74'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">argmax</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]))<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=74' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>prints the states which have the highest probability of reaching an error state.\nHowever, you should exercise caution when using <code>argmax</code> (or <code>argmin</code>) on properties such as <code>P=? [ ... ]</code> (or <code>S=? [ ... ]</code> or <code>R=? [ ... ]</code>), whose results are only approximate due to the nature of the methods used to compute them (or because of round-off errors.)\n</p>\n<p class='vspace'>Another common use of filters is to display the value for a particular state of the model (rather than the initial state, which is used by default). To achieve this, use e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock75'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>&amp;<span class=\"prismident\">y</span>=<span class=\"prismnum\">3</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=75' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>x=2&amp;y=3</code> is assumed to specify one particular state.\nA <code>state</code> filter will produce an error if the filter expression is not satisfied by exactly one state of the model.\n</p>\n<p class='vspace'>Filters can also be built up into more complex expressions. For example, the following two properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock76'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">avg</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">sum</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\") / <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">count</span>, \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=76' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>range</code> filter, unlike most PRISM expressions which are of type Boolean, integer or double, actually returns an interval: a pair of integers or doubles. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock77'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">count</span>=<span class=\"prismnum\">10</span> ], <span class=\"prismident\">count</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=77' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>gives the range of all possible values for the probability of reach a state satisfying <code>count=10</code>, from all states satisfying <code>count=0</code>.\nAs will be described below, this kind of property also results from the use of old-style (<code>{...}</code>) filters and properties on models with multiple initial states.\n</p>\n<div class='vspace'></div><h3>Old-style filters</h3>\n<p>In older versions of PRISM, filters were also available, but in a less expressive form. Previously, they were only usable on <code><strong>P</strong></code>, <code><strong>S</strong></code> or <code><strong>R</strong></code> properties and only a small set of filter operators were permitted. They were also specified in a different way, using braces (<code>{</code>...<code>}</code>). For compatibility with old properties files (and for compactness), these forms of filters are still allowed. These old-style forms of filters:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock78'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=78' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are equivalent to:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock79'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">min</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=79' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the first of the four properties above (i.e. an old-style filter of the form <code>{states}</code> will result in an error if <code>states</code> is not satisfied by exactly one state of the model. Older versions of PRISM just gave you the value for the first state state satisfying the filter, without warning you about this. If you want to recreate the old behaviour, just use a <code>first</code> filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock80'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">first</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=80' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Default filters</h3>\n<p>Finally, for completeness, we show what the <em>default</em> filters are in PRISM,\ni.e. how the way that PRISM returns values from properties by default\ncould have been achieved equivalently using filters.\n</p>\n<p class='vspace'>Queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock81'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=81' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock82'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=82' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock83'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=83' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as either:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock84'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=84' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the cases where there the model has a single initial state\nor multiple initial states, respectively.\n</p><hr />\n<h1>Properties Files</h1>\n<h3>Constants</h3>\n<p>Files containing properties to be analysed by PRISM can also contain constants, as is the case for model files.\nThese are defined in identical fashion, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock85'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span> = <span class=\"prismnum\">7</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span> = <span class=\"prismnum\">9.5</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">p</span> = <span class=\"prismnum\">0.01</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismident\">p</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">x</span>=<span class=\"prismident\">k</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=85' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As before, these constants can actually be left undefined and then later\nassigned either a single value or a range of values using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'>In fact, values such as the probability bounds for the <code><strong>P</strong></code> or <code><strong>S</strong></code> operators (like <code><strong>P</strong></code> above)\nand upper or lower bounds for the <code><strong>U</strong></code> operator (like <code> T</code> above)\ncan be arbitrary expressions, provided they are constant.\nFurthermore, expressions in the properties file can also refer to constants previous defined in the model file.\n</p>\n<p class='vspace'><a name='labels' id='labels'></a>\n</p><h3>Labels</h3>\n<p>Another feature of properties files is <em>labels</em>. These are a way of defining sets of states that will be referred to in properties (they correspond to <em>atomic propositions</em> in a temporal logic setting). As described <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>earlier</a>, labels can be defined in either model files or property files.\n</p>\n<p class='vspace'>Labels are defined using the keyword <code><strong>label</strong></code>, followed by a name (identifier) in double quotes, and then an expression which evaluates to a Boolean. Definition and usage of labels are illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock86'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ \"<span class=\"prismident\">safe</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">fail</span>\" ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=86' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Two special cases are the <code>\"init\"</code> and <code>\"deadlock\"</code> labels which are always defined.\nThese are true in initial states of the model and states where deadlocks were found (and, usually, fixed by adding self-loops), respectively.\n</p>\n<p class='vspace'><a name='names' id='names'></a>\n</p><h3>Property names</h3>\n<p>For convenience, properties can be annotated with <em>names</em>, as shown in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock87'>\r\n  <div class='sourceblocktext'><div class=\"prism\">\"<span class=\"prismident\">safe</span>\": <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">temperature</span> &gt; <span class=\"prismident\">t_max</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=87' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which gives the name <code>\"safe\"</code> to the property. It is then possible to include named properties as sub-expressions of other properties, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock88'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismident\">num_sensors</span>&gt;<span class=\"prismnum\">0</span> =&gt; \"<span class=\"prismident\">safe</span>\");<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/AllOnOnePage?action=sourceblock&amp;num=88' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the syntax for referring to named properties is identical to the syntax for labels. For this reason, property names must be disjoint from those of any existing labels.\n</p>\n<p class='vspace'>You can refer to property names when using the command-line switch <a class='wikilink' href='../RunningPRISM/ModelChecking.html#cl'><code>-prop</code></a> to specify which property is to be model checked.\n</p>\n<div class='vspace'></div><h3>Properties files</h3>\n<p>A PRISM properties file can contain any number of properties.\nIt is good practice, as shown in the examples above, to terminate each property with a semicolon. Currently, this is not enforced by PRISM (to prevent incompatibility with old properties files) but this may change in the future.\n</p>\n<p class='vspace'>Like model files, properties can also include any amount of white space (spaces, tabs, new lines, etc.) and C-style comments, which are both ignored.\nThe recommended file extension for PRISM properties is now <code>.props</code>.\nPreviously, though, the convention was to use extension <code>.pctl</code> for properties of DTMCs, MDPs or PTAs\nand extension <code>.csl</code> for properties of CTMCs, so these are still also valid.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Filters.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Filters \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Filters.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Filters@action=edit.html'>Edit</a> - <a class='wikilink' href='Filters@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Filters</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>As discussed above, when reporting the result of model checking a property, PRISM will by default return the value for the (single) initial state of the model. However, since PRISM in fact usually has to compute values for <em>all</em> states simultaneously, you can customise PRISM properties to obtain different results. This is done using <em>filters</em>.\n</p>\n<p class='vspace'>Filters are created using the <code>filter</code> keyword. They take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>op</code> is the filter <em>operator</em> (see below), <code>prop</code> is any PRISM property and <code>states</code> is a Boolean-valued expression identifying a set of states over which to apply the filter.\n</p>\n<p class='vspace'>In fact, the <code>states</code> argument is optional; if omitted, the filter is applied over all states. So, the following properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismkeyword\">true</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Here's a simple example of a filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This gives the <em>maximum</em> value, starting from any state satisfying <code>x=0</code>, of the probability of reaching an \"error\" state.\n</p>\n<p class='vspace'>Here's another simple example,\nwhich checks whether, <em>starting from any reachable state</em>,\nwe eventually reach a \"done\" state with probability 1.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We could modify this property slightly to instead check whether, from any state that satisfies the label \"ready\", we eventually reach a \"done\" state with probability 1. This could be done with either of the following two equivalent properties:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, \"<span class=\"prismident\">ready</span>\" =&gt; <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ], \"<span class=\"prismident\">ready</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Note:</strong> In older versions of PRISM, the property above could be written just as <code>\"ready\" =&gt; P&gt;=1 [ F \"done\" ]</code> since the result was checked for all states by default, not just the <a class='wikilink' href='SyntaxAndSemantics.html'>initial state</a>. Now, you need to explicitly include a filter, as shown above, to achieve this.\n</p>\n<div class='vspace'></div><h3>Types of filter</h3>\n<p>Most filters of the form <code>filter(op, prop, states)</code>\napply some operator <code>op</code> to the values of property <code>prop</code>\nfor all the states satisfying <code>states</code>,\nresulting in a single value.\nThe full list of filter operators <code>op</code> in this category is:\n</p>\n<div class='vspace'></div><ul><li><code>min</code>: the minimum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>max</code>: the maximum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>count</code>: counts the number of states satisfying <code>states</code> for which <code>prop</code> is true\n</li><li><code>sum</code> (or <code>+</code>): sums the value of <code>prop</code> for states satisfying <code>states</code>\n</li><li><code>avg</code>: the average value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>first</code>: the value of <code>prop</code> for the first (lowest-indexed) state satisfying <code>states</code>\n</li><li><code>range</code>: the range (interval) of values of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>forall</code> (or <code>&amp;</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for all states satisfying <code>states</code>\n</li><li><code>exists</code> (or <code>|</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for some states satisfying <code>states</code>\n</li><li><code>state</code>: returns the value for the single state satisfying <code>states</code> (if there is more than one, this is an error)\n</li></ul><p class='vspace'>There are also a few filters that, rather than returning a single value, return different values for each state, like a normal PRISM property:\n</p>\n<div class='vspace'></div><ul><li><code>argmin</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the minimum value of <code>prop</code>\n</li><li><code>argmax</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the maximum value of <code>prop</code>\n</li><li><code>print</code>: does not change the result of <code>prop</code> but prints the (non-zero) values to the log\n</li><li><code>printall</code>: like <code>print</code>, but displays <em>all</em> values, even for states where the value is zero\n</li></ul><div class='vspace'></div><h3>More examples</h3>\n<p>Here are some further illustrative examples of properties that use filters.\n</p>\n<p class='vspace'>Filters provide a quick way to <em>print</em> the results of a model checking query for several states. In most cases, for example, a <code>P=?</code> query just returns the probability from the initial state. To see the probability for all states satisfying <code>x&gt;2</code>, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">P</span>=? [ ... ], <span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">2</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Values are printed in the log (i.e. to the \"Log\" tab in the GUI or to the terminal from the command-line). For small models, you could omit the final <code>states</code> argument (<code>x&gt;2</code> here) and view the probabilities from all states. You can also use PRISM's <a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>verbose</a> mode to view values for all states, but filters provide an easier and more flexible solution.\n<code>print</code> filters do not actually alter the result returned so, in the example above, PRISM will still return the probability for the initial state, in addition to printing other probabilities in the log.\n</p>\n<p class='vspace'>You can also use <code>print</code> filters to display lists of states. For example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">argmax</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]))<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>prints the states which have the highest probability of reaching an error state.\nHowever, you should exercise caution when using <code>argmax</code> (or <code>argmin</code>) on properties such as <code>P=? [ ... ]</code> (or <code>S=? [ ... ]</code> or <code>R=? [ ... ]</code>), whose results are only approximate due to the nature of the methods used to compute them (or because of round-off errors.)\n</p>\n<p class='vspace'>Another common use of filters is to display the value for a particular state of the model (rather than the initial state, which is used by default). To achieve this, use e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>&amp;<span class=\"prismident\">y</span>=<span class=\"prismnum\">3</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>x=2&amp;y=3</code> is assumed to specify one particular state.\nA <code>state</code> filter will produce an error if the filter expression is not satisfied by exactly one state of the model.\n</p>\n<p class='vspace'>Filters can also be built up into more complex expressions. For example, the following two properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">avg</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">sum</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\") / <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">count</span>, \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>range</code> filter, unlike most PRISM expressions which are of type Boolean, integer or double, actually returns an interval: a pair of integers or doubles. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">count</span>=<span class=\"prismnum\">10</span> ], <span class=\"prismident\">count</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>gives the range of all possible values for the probability of reach a state satisfying <code>count=10</code>, from all states satisfying <code>count=0</code>.\nAs will be described below, this kind of property also results from the use of old-style (<code>{...}</code>) filters and properties on models with multiple initial states.\n</p>\n<div class='vspace'></div><h3>Old-style filters</h3>\n<p>In older versions of PRISM, filters were also available, but in a less expressive form. Previously, they were only usable on <code><strong>P</strong></code>, <code><strong>S</strong></code> or <code><strong>R</strong></code> properties and only a small set of filter operators were permitted. They were also specified in a different way, using braces (<code>{</code>...<code>}</code>). For compatibility with old properties files (and for compactness), these forms of filters are still allowed. These old-style forms of filters:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are equivalent to:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">min</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the first of the four properties above (i.e. an old-style filter of the form <code>{states}</code> will result in an error if <code>states</code> is not satisfied by exactly one state of the model. Older versions of PRISM just gave you the value for the first state state satisfying the filter, without warning you about this. If you want to recreate the old behaviour, just use a <code>first</code> filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">first</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Default filters</h3>\n<p>Finally, for completeness, we show what the <em>default</em> filters are in PRISM,\ni.e. how the way that PRISM returns values from properties by default\ncould have been achieved equivalently using filters.\n</p>\n<p class='vspace'>Queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as either:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the cases where there the model has a single initial state\nor multiple initial states, respectively.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Filters.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Filters@action=edit.html'>Edit</a> - <a class='wikilink' href='Filters@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Filters@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 10:03 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='selflink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Filters@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Filters | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Filters.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Filters@action=edit.html'>Edit</a> - <a class='wikilink' href='Filters@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Filters</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Filters@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Filters.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Filters@action=edit.html'>Edit</a> - <a class='wikilink' href='Filters@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Filters@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 10:03 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='selflink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Filters@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Filters | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Filters.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Filters@action=edit.html'>Edit</a> - <a class='wikilink' href='Filters@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Filters</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Filters@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Filters.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Filters@action=edit.html'>Edit</a> - <a class='wikilink' href='Filters@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Filters@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 10:03 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='selflink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Filters@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / Filters </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Filters</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>As discussed above, when reporting the result of model checking a property, PRISM will by default return the value for the (single) initial state of the model. However, since PRISM in fact usually has to compute values for <em>all</em> states simultaneously, you can customise PRISM properties to obtain different results. This is done using <em>filters</em>.\n</p>\n<p class='vspace'>Filters are created using the <code>filter</code> keyword. They take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>op</code> is the filter <em>operator</em> (see below), <code>prop</code> is any PRISM property and <code>states</code> is a Boolean-valued expression identifying a set of states over which to apply the filter.\n</p>\n<p class='vspace'>In fact, the <code>states</code> argument is optional; if omitted, the filter is applied over all states. So, the following properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">op</span>, <span class=\"prismident\">prop</span>, <span class=\"prismkeyword\">true</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Here's a simple example of a filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This gives the <em>maximum</em> value, starting from any state satisfying <code>x=0</code>, of the probability of reaching an \"error\" state.\n</p>\n<p class='vspace'>Here's another simple example,\nwhich checks whether, <em>starting from any reachable state</em>,\nwe eventually reach a \"done\" state with probability 1.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We could modify this property slightly to instead check whether, from any state that satisfies the label \"ready\", we eventually reach a \"done\" state with probability 1. This could be done with either of the following two equivalent properties:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, \"<span class=\"prismident\">ready</span>\" =&gt; <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ])<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">done</span>\" ], \"<span class=\"prismident\">ready</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'><strong>Note:</strong> In older versions of PRISM, the property above could be written just as <code>\"ready\" =&gt; P&gt;=1 [ F \"done\" ]</code> since the result was checked for all states by default, not just the <a class='wikilink' href='SyntaxAndSemantics.html'>initial state</a>. Now, you need to explicitly include a filter, as shown above, to achieve this.\n</p>\n<div class='vspace'></div><h3>Types of filter</h3>\n<p>Most filters of the form <code>filter(op, prop, states)</code>\napply some operator <code>op</code> to the values of property <code>prop</code>\nfor all the states satisfying <code>states</code>,\nresulting in a single value.\nThe full list of filter operators <code>op</code> in this category is:\n</p>\n<div class='vspace'></div><ul><li><code>min</code>: the minimum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>max</code>: the maximum value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>count</code>: counts the number of states satisfying <code>states</code> for which <code>prop</code> is true\n</li><li><code>sum</code> (or <code>+</code>): sums the value of <code>prop</code> for states satisfying <code>states</code>\n</li><li><code>avg</code>: the average value of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>first</code>: the value of <code>prop</code> for the first (lowest-indexed) state satisfying <code>states</code>\n</li><li><code>range</code>: the range (interval) of values of <code>prop</code> over states satisfying <code>states</code>\n</li><li><code>forall</code> (or <code>&amp;</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for all states satisfying <code>states</code>\n</li><li><code>exists</code> (or <code>|</code>): returns <code>true</code> if <code>prop</code> is <code>true</code> for some states satisfying <code>states</code>\n</li><li><code>state</code>: returns the value for the single state satisfying <code>states</code> (if there is more than one, this is an error)\n</li></ul><p class='vspace'>There are also a few filters that, rather than returning a single value, return different values for each state, like a normal PRISM property:\n</p>\n<div class='vspace'></div><ul><li><code>argmin</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the minimum value of <code>prop</code>\n</li><li><code>argmax</code>: returns <code>true</code> for the states satisfying <code>states</code> that yield the maximum value of <code>prop</code>\n</li><li><code>print</code>: does not change the result of <code>prop</code> but prints the (non-zero) values to the log\n</li><li><code>printall</code>: like <code>print</code>, but displays <em>all</em> values, even for states where the value is zero\n</li></ul><div class='vspace'></div><h3>More examples</h3>\n<p>Here are some further illustrative examples of properties that use filters.\n</p>\n<p class='vspace'>Filters provide a quick way to <em>print</em> the results of a model checking query for several states. In most cases, for example, a <code>P=?</code> query just returns the probability from the initial state. To see the probability for all states satisfying <code>x&gt;2</code>, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">P</span>=? [ ... ], <span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">2</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Values are printed in the log (i.e. to the \"Log\" tab in the GUI or to the terminal from the command-line). For small models, you could omit the final <code>states</code> argument (<code>x&gt;2</code> here) and view the probabilities from all states. You can also use PRISM's <a class='wikilink' href='../ConfiguringPRISM/OtherOptions.html'>verbose</a> mode to view values for all states, but filters provide an easier and more flexible solution.\n<code>print</code> filters do not actually alter the result returned so, in the example above, PRISM will still return the probability for the initial state, in addition to printing other probabilities in the log.\n</p>\n<p class='vspace'>You can also use <code>print</code> filters to display lists of states. For example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">print</span>, <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">argmax</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]))<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>prints the states which have the highest probability of reaching an error state.\nHowever, you should exercise caution when using <code>argmax</code> (or <code>argmin</code>) on properties such as <code>P=? [ ... ]</code> (or <code>S=? [ ... ]</code> or <code>R=? [ ... ]</code>), whose results are only approximate due to the nature of the methods used to compute them (or because of round-off errors.)\n</p>\n<p class='vspace'>Another common use of filters is to display the value for a particular state of the model (rather than the initial state, which is used by default). To achieve this, use e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>&amp;<span class=\"prismident\">y</span>=<span class=\"prismnum\">3</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>x=2&amp;y=3</code> is assumed to specify one particular state.\nA <code>state</code> filter will produce an error if the filter expression is not satisfied by exactly one state of the model.\n</p>\n<p class='vspace'>Filters can also be built up into more complex expressions. For example, the following two properties are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">avg</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">sum</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\") / <span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">count</span>, \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>range</code> filter, unlike most PRISM expressions which are of type Boolean, integer or double, actually returns an interval: a pair of integers or doubles. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">count</span>=<span class=\"prismnum\">10</span> ], <span class=\"prismident\">count</span>=<span class=\"prismnum\">0</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>gives the range of all possible values for the probability of reach a state satisfying <code>count=10</code>, from all states satisfying <code>count=0</code>.\nAs will be described below, this kind of property also results from the use of old-style (<code>{...}</code>) filters and properties on models with multiple initial states.\n</p>\n<div class='vspace'></div><h3>Old-style filters</h3>\n<p>In older versions of PRISM, filters were also available, but in a less expressive form. Previously, they were only usable on <code><strong>P</strong></code>, <code><strong>S</strong></code> or <code><strong>R</strong></code> properties and only a small set of filter operators were permitted. They were also specified in a different way, using braces (<code>{</code>...<code>}</code>). For compatibility with old properties files (and for compactness), these forms of filters are still allowed. These old-style forms of filters:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> {<span class=\"prismident\">states</span>}{<span class=\"prismkeyword\">min</span>}{<span class=\"prismkeyword\">max</span>} ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are equivalent to:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">min</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismkeyword\">max</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the first of the four properties above (i.e. an old-style filter of the form <code>{states}</code> will result in an error if <code>states</code> is not satisfied by exactly one state of the model. Older versions of PRISM just gave you the value for the first state state satisfying the filter, without warning you about this. If you want to recreate the old behaviour, just use a <code>first</code> filter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">first</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ], <span class=\"prismident\">states</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Default filters</h3>\n<p>Finally, for completeness, we show what the <em>default</em> filters are in PRISM,\ni.e. how the way that PRISM returns values from properties by default\ncould have been achieved equivalently using filters.\n</p>\n<p class='vspace'>Queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and queries of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>are the same as either:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">state</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n<span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">range</span>, <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ], \"<span class=\"prismkeyword\">init</span>\")<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Filters?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for the cases where there the model has a single initial state\nor multiple initial states, respectively.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/IdentifyingASetOfStates.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Identifying A Set Of States \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='IdentifyingASetOfStates.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=edit.html'>Edit</a> - <a class='wikilink' href='IdentifyingASetOfStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Identifying A Set Of States</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>One of the most fundamental tasks when specifying properties of a model\nis to identify particular sets or classes of states of the model.\nFor example, to verify a property such as\n\"the algorithm eventually terminates successfully with probability 1\",\nit is first necessary to identify the states of the model\nwhich correspond to situations where \"the algorithm has terminated successfully\".\nIn terms of the way temporal logics are usually presented,\nthese correspond to <em>atomic propositions</em>.\n</p>\n<p class='vspace'>In PRISM, this is achieved simply by writing an <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a> in the PRISM language which evaluates to a Boolean value. This expression will typically contain references to variables (and constants) from the model to which it relates. The set of states corresponding to this expression is those for which it evaluates to <code>true</code>. We say that the expression is \"satisfied\" in these states.\n</p>\n<p class='vspace'>For example, in the property given above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/IdentifyingASetOfStates?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>the expression <code>num_errors &gt; 5</code> is used to identify states of the model where more than 5 errors have occurred.\n</p>\n<p class='vspace'>It is also common to use <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> to identify states in this way, like <code>\"terminate\"</code> in the example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/IdentifyingASetOfStates?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Properties can refer to <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> either from the model to which the property relates, or included in the same <a class='wikilink' href='PropertiesFiles.html'>properties file</a>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='IdentifyingASetOfStates.html'>View</a> - <a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=edit.html'>Edit</a> - <a class='wikilink' href='IdentifyingASetOfStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 08, 2010, at 08:03 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/IdentifyingASetOfStates@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Identifying A Set Of States | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='IdentifyingASetOfStates.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=edit.html'>Edit</a> - <a class='wikilink' href='IdentifyingASetOfStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Identifying A Set Of States</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='IdentifyingASetOfStates@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='IdentifyingASetOfStates.html'>View</a> - <a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=edit.html'>Edit</a> - <a class='wikilink' href='IdentifyingASetOfStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 08, 2010, at 08:03 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/IdentifyingASetOfStates@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Identifying A Set Of States | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='IdentifyingASetOfStates.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=edit.html'>Edit</a> - <a class='wikilink' href='IdentifyingASetOfStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Identifying A Set Of States</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='IdentifyingASetOfStates@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='IdentifyingASetOfStates.html'>View</a> - <a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=edit.html'>Edit</a> - <a class='wikilink' href='IdentifyingASetOfStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='IdentifyingASetOfStates@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 08, 2010, at 08:03 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/IdentifyingASetOfStates@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / IdentifyingASetOfStates </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Identifying A Set Of States</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>One of the most fundamental tasks when specifying properties of a model\nis to identify particular sets or classes of states of the model.\nFor example, to verify a property such as\n\"the algorithm eventually terminates successfully with probability 1\",\nit is first necessary to identify the states of the model\nwhich correspond to situations where \"the algorithm has terminated successfully\".\nIn terms of the way temporal logics are usually presented,\nthese correspond to <em>atomic propositions</em>.\n</p>\n<p class='vspace'>In PRISM, this is achieved simply by writing an <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a> in the PRISM language which evaluates to a Boolean value. This expression will typically contain references to variables (and constants) from the model to which it relates. The set of states corresponding to this expression is those for which it evaluates to <code>true</code>. We say that the expression is \"satisfied\" in these states.\n</p>\n<p class='vspace'>For example, in the property given above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/IdentifyingASetOfStates?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>the expression <code>num_errors &gt; 5</code> is used to identify states of the model where more than 5 errors have occurred.\n</p>\n<p class='vspace'>It is also common to use <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> to identify states in this way, like <code>\"terminate\"</code> in the example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/IdentifyingASetOfStates?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Properties can refer to <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>labels</a> either from the model to which the property relates, or included in the same <a class='wikilink' href='PropertiesFiles.html'>properties file</a>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Introduction@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Introduction | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Introduction@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Introduction@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Introduction | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Introduction@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Introduction@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / Introduction </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Introduction</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>In order to analyse a probabilistic model which has been specified and constructed in PRISM,\nit is necessary to identify one or more <em>properties</em> of the model\nwhich can be evaluated by the tool.\nPRISM's <em>property specification language</em> subsumes several well-known probabilistic temporal logics, including PCTL, CSL, probabilistic LTL and PCTL*.\nPCTL is used for specifying properties of discrete-time models such as DTMCs or PTAs,\nand also real-time models such as PTAs; CSL is an extension of PCTL for CTMCs;\nLTL and PCTL* can be used to specify properties of \ndiscrete-time models (or untimed properties of CTMCs).\nPRISM also supports most of the (non-probabilistic) temporal logic CTL.\n</p>\n<p class='vspace'>In fact, PRISM also supports numerous additional customisations and extensions of these two logics.\nFull details of the property specifications permitted in PRISM are provided in the following sections. The presentation given here is relatively informal. For the precise syntax and semantics of the various logics, see [<a class='wikilink' href='../Main/References.html#HJ94'>HJ94</a>],[<a class='wikilink' href='../Main/References.html#BdA95'>BdA95</a>] for PCTL, [<a class='wikilink' href='../Main/References.html#ASSB96'>ASSB96</a>],[<a class='wikilink' href='../Main/References.html#BKH99'>BKH99</a>] for CSL and, for example, [<a class='wikilink' href='../Main/References.html#Bai98'>Bai98</a>] for LTL and PCTL*. You can also find various pointers to useful papers in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>Before discussing property specifications in more detail,\nit is perhaps instructive to first illustrate some typical examples of properties which PRISM can handle.\nThe following are a selection of such properties.\nIn each case, we give both the PRISM syntax and a natural language translation:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the algorithm eventually terminates successfully with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> \"<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that more than 5 errors occur within the first 100 time units is less than 0.1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismident\">num_sensors</span> &lt; <span class=\"prismident\">min_sensors</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"in the long-run, the probability that an inadequate number of sensors are operational is less than 0.01\"\n</p>\n<p class='vspace'>Note that the above properties are all assertions,\ni.e. ones to which we would expect a \"yes\" or \"no\" answer.\nThis is because all references to probabilities are associated with an upper or lower bound\nwhich can be checked to be either true or false.\nIn PRISM, we can also directly specify properties which evaluate to a numerical value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ !<span class=\"prismident\">proc2_terminate</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">proc1_terminate</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that process 1 terminates before process 2 does\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">messages_lost</span> &gt; <span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the maximum probability that more than 10 messages have been lost by time <code>T</code>\" (for an MDP/PTA)\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the long-run probability that the queue is more than 75% full\"\n</p>\n<p class='vspace'>Furthermore, PRISM makes it easy to combine such properties into more complex expressions,\ncompute their values for a range of parameters\nand plot graphs of the results using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\nThis is often a very useful way of identifying interesting\npatterns or trends in the behaviour of a system.\nSee the <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a> section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a> for many examples of this kind of analysis.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Main.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Introduction \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>In order to analyse a probabilistic model which has been specified and constructed in PRISM,\nit is necessary to identify one or more <em>properties</em> of the model\nwhich can be evaluated by the tool.\nPRISM's <em>property specification language</em> subsumes several well-known probabilistic temporal logics, including PCTL, CSL, probabilistic LTL and PCTL*.\nPCTL is used for specifying properties of discrete-time models such as DTMCs or PTAs,\nand also real-time models such as PTAs; CSL is an extension of PCTL for CTMCs;\nLTL and PCTL* can be used to specify properties of \ndiscrete-time models (or untimed properties of CTMCs).\nPRISM also supports most of the (non-probabilistic) temporal logic CTL.\n</p>\n<p class='vspace'>In fact, PRISM also supports numerous additional customisations and extensions of these two logics.\nFull details of the property specifications permitted in PRISM are provided in the following sections. The presentation given here is relatively informal. For the precise syntax and semantics of the various logics, see [<a class='wikilink' href='../Main/References.html#HJ94'>HJ94</a>],[<a class='wikilink' href='../Main/References.html#BdA95'>BdA95</a>] for PCTL, [<a class='wikilink' href='../Main/References.html#ASSB96'>ASSB96</a>],[<a class='wikilink' href='../Main/References.html#BKH99'>BKH99</a>] for CSL and, for example, [<a class='wikilink' href='../Main/References.html#Bai98'>Bai98</a>] for LTL and PCTL*. You can also find various pointers to useful papers in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>Before discussing property specifications in more detail,\nit is perhaps instructive to first illustrate some typical examples of properties which PRISM can handle.\nThe following are a selection of such properties.\nIn each case, we give both the PRISM syntax and a natural language translation:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">terminate</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the algorithm eventually terminates successfully with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> \"<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">100</span> <span class=\"prismident\">num_errors</span> &gt; <span class=\"prismnum\">5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that more than 5 errors occur within the first 100 time units is less than 0.1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismident\">num_sensors</span> &lt; <span class=\"prismident\">min_sensors</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"in the long-run, the probability that an inadequate number of sensors are operational is less than 0.01\"\n</p>\n<p class='vspace'>Note that the above properties are all assertions,\ni.e. ones to which we would expect a \"yes\" or \"no\" answer.\nThis is because all references to probabilities are associated with an upper or lower bound\nwhich can be checked to be either true or false.\nIn PRISM, we can also directly specify properties which evaluate to a numerical value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ !<span class=\"prismident\">proc2_terminate</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">proc1_terminate</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the probability that process 1 terminates before process 2 does\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">messages_lost</span> &gt; <span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the maximum probability that more than 10 messages have been lost by time <code>T</code>\" (for an MDP/PTA)\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Introduction?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p>\"the long-run probability that the queue is more than 75% full\"\n</p>\n<p class='vspace'>Furthermore, PRISM makes it easy to combine such properties into more complex expressions,\ncompute their values for a range of parameters\nand plot graphs of the results using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\nThis is often a very useful way of identifying interesting\npatterns or trends in the behaviour of a system.\nSee the <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a> section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a> for many examples of this kind of analysis.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Multi-objectiveProperties.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Multi-objective Properties \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Multi-objectiveProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Multi-objectiveProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Multi-objective Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>For MDPs, PRISM supports <em>multi-objective</em> properties. Consider a property that uses the <code><strong>P</strong></code> operator. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This states that, <em>for all</em> strategies (or policies) of the MDP, the probability of reaching an <code>\"error\"</code> state is less than 0.01.\n</p>\n<p class='vspace'>Multi-objective queries differ in two important ways. Firstly, (by default) they ask about the <em>existence</em> of a strategy. Secondly they refer to <em>multiple</em> properties of a strategy. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means: \"does there exist a strategy of the MDP under which the probability of reaching an <code>\"error1\"</code> state is less than 0.01 <em>and</em> the probability of reaching an <code>\"error2\"</code> state is less than 0.02?\"\n</p>\n<p class='vspace'>To use the terminology from [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>], the above is an \"achievability\" query (i.e., is this combination of objectives achievable by some strategy?). PRISM also supports two other kinds of multi-objective query: \"numerical\" and \"Pareto\" queries.\n</p>\n<p class='vspace'>A \"numerical\" query looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>meaning \"what is the minimum possible probability of reaching <code>\"error1\"</code>, over all strategies of the MDP for which the probability of reaching <code>\"error2\"</code> is less than 0.02?\".\n</p>\n<p class='vspace'>A \"Pareto\" queries leaves both of the objectives unbounded, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This asks PRISM to compute (approximately), the <em>Pareto curve</em> for this pair objectives. Intuitively, this is the set of pairs of probabilities (of reaching <code>\"error1\"</code>/<code>\"error2\"</code>) such that reducing one probability any more would necessitate an increase in the other probability.\n</p>\n<div class='vspace'></div><h3>Types of Objectives</h3>\n<p>For simplicity, the examples above all refer to the probability of reaching classes of states in the model. Other types of property (objective) are also possible.\n</p>\n<p class='vspace'>Firstly, we can extend the examples above by referring to the probability of any\n<a class='wikilink' href='ThePOperator.html#ltl'>LTL</a> property. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9?\".\n</p>\n<p class='vspace'>We can also use more than 2 objectives, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.95</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good3</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9 and the probability of visiting <code>\"good3\"</code> states infinitely often remains at least 0.95?\".\n</p>\n<p class='vspace'>Multi-objective queries can also refer to the expected total cumulative value of a reward structure. We write such properties in the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}<span class=\"prismkeyword\">min</span>=?[ <span class=\"prismkeyword\">C</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">energy</span>\"}&lt;=<span class=\"prismnum\">1.45</span> [ <span class=\"prismkeyword\">C</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the minimum expected cumulative value of reward structure <code>\"time\"</code>, such that the expected cumulative value of reward structure <code>\"energy\"</code> is below 1.45.\n</p>\n<p class='vspace'>Note that this <code><strong>C</strong></code> reward operator differs from the <code><strong>F</strong> \"target\"</code> operator, usually used for standard (single-objective) MDP model checking. Whereas the <code><strong>F</strong> \"target\"</code> operator refers to the expected reward accumulated until a <code>\"target\"</code> state is reached the <code><strong>C</strong></code> operator refers to the expected <em>total</em> reward.\n</p>\n<p class='vspace'>A few important notes regarding rewards:\n</p>\n<div class='vspace'></div><ul><li>Currently only transition rewards are supported; state rewards are not.\n<div class='vspace'></div></li><li>Certain assumptions are made regarding the finiteness of rewards; see p.7 of [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>] for details.\n</li></ul><p class='vspace'>Finally, time-bounded variants of both probabilistic reachability and expected cumulative rewards objectives can be used. Here is an example that uses the latter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">power</span>\"}<span class=\"prismkeyword\">min</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">queue</span>\"}&lt;=<span class=\"prismident\">r</span> [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Solution Methods</h3>\n<p>PRISM can perform multi-objective model checking using two distinct solution methods, which are described in [<a class='wikilink' href='../Main/References.html#FKN+11'>FKN+11</a>] and [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>]. The former is based on the use of linear programming; the latter reduces multi-objective model checking to a series of simpler problems, solved using value iteration (or the Gauss-Seidel variant of value iteration). The default is \"Value iteration\". You can change this in the GUI using the option \"MDP multi-objective solution methods\", or using the command-line switches <code>-lp</code>, <code>-valiter</code>, <code>-gs</code>.\n</p>\n<p class='vspace'>There are some restrictions for the different methods, e.g.\n</p>\n<div class='vspace'></div><ul><li>Linear programming does not support time-bounded properties or Pareto queries\n</li></ul><div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Multi-objectiveProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Multi-objectiveProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:28 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='selflink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Multi-objectiveProperties@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Multi-objective Properties | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Multi-objectiveProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Multi-objectiveProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Multi-objective Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Multi-objectiveProperties@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Multi-objectiveProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Multi-objectiveProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:28 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='selflink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Multi-objectiveProperties@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Multi-objective Properties | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Multi-objectiveProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Multi-objectiveProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Multi-objective Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Multi-objectiveProperties@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Multi-objectiveProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Multi-objectiveProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Multi-objectiveProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:28 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='selflink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Multi-objectiveProperties@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / Multi-objectiveProperties </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Multi-objective Properties</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>For MDPs, PRISM supports <em>multi-objective</em> properties. Consider a property that uses the <code><strong>P</strong></code> operator. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This states that, <em>for all</em> strategies (or policies) of the MDP, the probability of reaching an <code>\"error\"</code> state is less than 0.01.\n</p>\n<p class='vspace'>Multi-objective queries differ in two important ways. Firstly, (by default) they ask about the <em>existence</em> of a strategy. Secondly they refer to <em>multiple</em> properties of a strategy. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means: \"does there exist a strategy of the MDP under which the probability of reaching an <code>\"error1\"</code> state is less than 0.01 <em>and</em> the probability of reaching an <code>\"error2\"</code> state is less than 0.02?\"\n</p>\n<p class='vspace'>To use the terminology from [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>], the above is an \"achievability\" query (i.e., is this combination of objectives achievable by some strategy?). PRISM also supports two other kinds of multi-objective query: \"numerical\" and \"Pareto\" queries.\n</p>\n<p class='vspace'>A \"numerical\" query looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.02</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>meaning \"what is the minimum possible probability of reaching <code>\"error1\"</code>, over all strategies of the MDP for which the probability of reaching <code>\"error2\"</code> is less than 0.02?\".\n</p>\n<p class='vspace'>A \"Pareto\" queries leaves both of the objectives unbounded, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\" ], <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This asks PRISM to compute (approximately), the <em>Pareto curve</em> for this pair objectives. Intuitively, this is the set of pairs of probabilities (of reaching <code>\"error1\"</code>/<code>\"error2\"</code>) such that reducing one probability any more would necessitate an increase in the other probability.\n</p>\n<div class='vspace'></div><h3>Types of Objectives</h3>\n<p>For simplicity, the examples above all refer to the probability of reaching classes of states in the model. Other types of property (objective) are also possible.\n</p>\n<p class='vspace'>Firstly, we can extend the examples above by referring to the probability of any\n<a class='wikilink' href='ThePOperator.html#ltl'>LTL</a> property. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9?\".\n</p>\n<p class='vspace'>We can also use more than 2 objectives, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">G</span> \"<span class=\"prismident\">good1</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.9</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good2</span>\" ], <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.95</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">good3</span>\" ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the maximum probability of staying forever in <code>\"good1\"</code> states, such that the probability of visiting <code>\"good2\"</code> states infinitely often remains at least 0.9 and the probability of visiting <code>\"good3\"</code> states infinitely often remains at least 0.95?\".\n</p>\n<p class='vspace'>Multi-objective queries can also refer to the expected total cumulative value of a reward structure. We write such properties in the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}<span class=\"prismkeyword\">min</span>=?[ <span class=\"prismkeyword\">C</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">energy</span>\"}&lt;=<span class=\"prismnum\">1.45</span> [ <span class=\"prismkeyword\">C</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"What is the minimum expected cumulative value of reward structure <code>\"time\"</code>, such that the expected cumulative value of reward structure <code>\"energy\"</code> is below 1.45.\n</p>\n<p class='vspace'>Note that this <code><strong>C</strong></code> reward operator differs from the <code><strong>F</strong> \"target\"</code> operator, usually used for standard (single-objective) MDP model checking. Whereas the <code><strong>F</strong> \"target\"</code> operator refers to the expected reward accumulated until a <code>\"target\"</code> state is reached the <code><strong>C</strong></code> operator refers to the expected <em>total</em> reward.\n</p>\n<p class='vspace'>A few important notes regarding rewards:\n</p>\n<div class='vspace'></div><ul><li>Currently only transition rewards are supported; state rewards are not.\n<div class='vspace'></div></li><li>Certain assumptions are made regarding the finiteness of rewards; see p.7 of [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>] for details.\n</li></ul><p class='vspace'>Finally, time-bounded variants of both probabilistic reachability and expected cumulative rewards objectives can be used. Here is an example that uses the latter:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">multi</span>(<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">power</span>\"}<span class=\"prismkeyword\">min</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ], <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">queue</span>\"}&lt;=<span class=\"prismident\">r</span> [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">k</span> ]) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Multi-objectiveProperties?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Solution Methods</h3>\n<p>PRISM can perform multi-objective model checking using two distinct solution methods, which are described in [<a class='wikilink' href='../Main/References.html#FKN+11'>FKN+11</a>] and [<a class='wikilink' href='../Main/References.html#FKP12'>FKP12</a>]. The former is based on the use of linear programming; the latter reduces multi-objective model checking to a series of simpler problems, solved using value iteration (or the Gauss-Seidel variant of value iteration). The default is \"Value iteration\". You can change this in the GUI using the option \"MDP multi-objective solution methods\", or using the command-line switches <code>-lp</code>, <code>-valiter</code>, <code>-gs</code>.\n</p>\n<p class='vspace'>There are some restrictions for the different methods, e.g.\n</p>\n<div class='vspace'></div><ul><li>Linear programming does not support time-bounded properties or Pareto queries\n</li></ul><div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Non-probabilisticProperties.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Non-probabilistic Properties \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Non-probabilisticProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Non-probabilisticProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Non-probabilistic Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM also supports model checking of the non-probabilistic temporal logics CTL (computation tree logic) and LTL (linear temporal logic).\nProperties in these logics use the <code><strong>A</strong></code> (for all) and <code><strong>E</strong></code> (there exists) operators,\ninstead of the probabilistic <code><strong>P</strong></code> operator used in many other properties supported by PRISM.\n</p>\n<p class='vspace'>Properties take the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">A</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Non-probabilisticProperties?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which are true in a state <em>s</em> of a model if\n\"path property <code>pathprop</code> is satisfied by <em>all</em> paths from state <em>s</em>\"\nand\n\"path property <code>pathprop</code> is satisfied by <em>some</em> path from state <em>s</em>\",\nrespectively.\nThe syntax for LTL formulas is the same as those allowed within the <a class='wikilink' href='ThePOperator.html#ltl'>P operator</a>.\n</p>\n<p class='vspace'>Example properties include:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ] <span class=\"prismcomment\">// There exists a path that reaches a state satisfying \"goal\"</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span> ] <span class=\"prismcomment\">// Variable x is always at most 10 along all paths of the model</span><br/>\n<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">ready</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">launch</span>\") ] <span class=\"prismcomment\">// There exists a path along which label \"ready\" eventually becomes true and label \"launch\" is true immediately afterwards</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span>) | (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>) ] <span class=\"prismcomment\">// Along all paths, either x=1 or x=2 is true infinitely often</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Non-probabilisticProperties?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Counterexamples and Witnesses</h3>\n<p>If you check a CTL property of the form <code>A [ G \"inv\" ]</code> and it is false, PRISM will generate a counterexample in the form of a path that reaches a state where <code>\"inv\"</code> is not true. This is displayed either in the simulator (from the GUI) or at the command-line. Similarly, if you check <code>E [ F \"goal\" ]</code> and the result is true, a witness (a path reaching a <code>\"goal\"</code> state) will be generated.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Non-probabilisticProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Non-probabilisticProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 22, 2017, at 11:03 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='selflink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Non-probabilisticProperties@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Non-probabilistic Properties | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Non-probabilisticProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Non-probabilisticProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Non-probabilistic Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Non-probabilisticProperties@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Non-probabilisticProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Non-probabilisticProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 22, 2017, at 11:03 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='selflink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Non-probabilisticProperties@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Non-probabilistic Properties | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Non-probabilisticProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Non-probabilisticProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Non-probabilistic Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Non-probabilisticProperties@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Non-probabilisticProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Non-probabilisticProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Non-probabilisticProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 22, 2017, at 11:03 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='selflink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Non-probabilisticProperties@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / Non-probabilisticProperties </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Non-probabilistic Properties</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM also supports model checking of the non-probabilistic temporal logics CTL (computation tree logic) and LTL (linear temporal logic).\nProperties in these logics use the <code><strong>A</strong></code> (for all) and <code><strong>E</strong></code> (there exists) operators,\ninstead of the probabilistic <code><strong>P</strong></code> operator used in many other properties supported by PRISM.\n</p>\n<p class='vspace'>Properties take the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">A</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Non-probabilisticProperties?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which are true in a state <em>s</em> of a model if\n\"path property <code>pathprop</code> is satisfied by <em>all</em> paths from state <em>s</em>\"\nand\n\"path property <code>pathprop</code> is satisfied by <em>some</em> path from state <em>s</em>\",\nrespectively.\nThe syntax for LTL formulas is the same as those allowed within the <a class='wikilink' href='ThePOperator.html#ltl'>P operator</a>.\n</p>\n<p class='vspace'>Example properties include:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ] <span class=\"prismcomment\">// There exists a path that reaches a state satisfying \"goal\"</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span> ] <span class=\"prismcomment\">// Variable x is always at most 10 along all paths of the model</span><br/>\n<br/>\n<span class=\"prismkeyword\">E</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">ready</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">launch</span>\") ] <span class=\"prismcomment\">// There exists a path along which label \"ready\" eventually becomes true and label \"launch\" is true immediately afterwards</span><br/>\n<br/>\n<span class=\"prismkeyword\">A</span> [ (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span>) | (<span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span>) ] <span class=\"prismcomment\">// Along all paths, either x=1 or x=2 is true infinitely often</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Non-probabilisticProperties?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Counterexamples and Witnesses</h3>\n<p>If you check a CTL property of the form <code>A [ G \"inv\" ]</code> and it is false, PRISM will generate a counterexample in the form of a path that reaches a state where <code>\"inv\"</code> is not true. This is displayed either in the simulator (from the GUI) or at the command-line. Similarly, if you check <code>E [ F \"goal\" ]</code> and the result is true, a witness (a path reaching a <code>\"goal\"</code> state) will be generated.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/PartiallyObservableModels.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Partially Observable Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PartiallyObservableModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Partially Observable Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>For partially observable models (POMDPs and POPTAs),\nPRISM uses the same property language as the their\nfully observational equivalents (MDPs and PTAs).\nHowever, a more limited range of properties are available.\nFor POMDPs, PRISM currently supports probabilistic reachability,\nprobabilistic until, or expected reachability rewards properties, i.e.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PartiallyObservableModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or bounded variants with a probability/threshold instead\nof the <code>min=?</code> or <code>max=?</code>.\n</p>\n<p class='vspace'>For the verification methods currently implemented,\nthere are a few additional restrictions.\nFirstly, the <code>target</code> (and <code>remain</code>) expression appearing\nin the property must be an observable.\nIn other words, if any state of the POMDP satisfies the expression,\nthen all other observationally equivalent states must also satisfy it.\nThis is easily achieved by only using either observable variables\nor named observables in the expression, but that is not required.\nSecondly, probabilities and expected rewards are only computed from a single state.\n</p>\n<p class='vspace'>POPTAs are currently verified using the \"digital clocks\" approach to\ntranslate them into a POMDP, so they inherit the same\n<a class='wikilink' href='Real-timeModels.html'>restrictions</a>\n(that strict or diagonal clock comparisons are not allowed).\nHowever for POPTAs, time-bounded probabilistic reachability is also supported.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PartiallyObservableModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 08:51 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='selflink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/PartiallyObservableModels@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Partially Observable Models | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PartiallyObservableModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Partially Observable Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PartiallyObservableModels@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PartiallyObservableModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 08:51 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='selflink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/PartiallyObservableModels@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Partially Observable Models | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PartiallyObservableModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Partially Observable Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PartiallyObservableModels@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PartiallyObservableModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 08:51 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='selflink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/PartiallyObservableModels@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / PartiallyObservableModels </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Partially Observable Models</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>For partially observable models (POMDPs and POPTAs),\nPRISM uses the same property language as the their\nfully observational equivalents (MDPs and PTAs).\nHowever, a more limited range of properties are available.\nFor POMDPs, PRISM currently supports probabilistic reachability,\nprobabilistic until, or expected reachability rewards properties, i.e.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">remain</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PartiallyObservableModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or bounded variants with a probability/threshold instead\nof the <code>min=?</code> or <code>max=?</code>.\n</p>\n<p class='vspace'>For the verification methods currently implemented,\nthere are a few additional restrictions.\nFirstly, the <code>target</code> (and <code>remain</code>) expression appearing\nin the property must be an observable.\nIn other words, if any state of the POMDP satisfies the expression,\nthen all other observationally equivalent states must also satisfy it.\nThis is easily achieved by only using either observable variables\nor named observables in the expression, but that is not required.\nSecondly, probabilities and expected rewards are only computed from a single state.\n</p>\n<p class='vspace'>POPTAs are currently verified using the \"digital clocks\" approach to\ntranslate them into a POMDP, so they inherit the same\n<a class='wikilink' href='Real-timeModels.html'>restrictions</a>\n(that strict or diagonal clock comparisons are not allowed).\nHowever for POPTAs, time-bounded probabilistic reachability is also supported.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/PropertiesFiles.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Properties Files \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PropertiesFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PropertiesFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Properties Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<h3>Constants</h3>\n<p>Files containing properties to be analysed by PRISM can also contain constants, as is the case for model files.\nThese are defined in identical fashion, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span> = <span class=\"prismnum\">7</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span> = <span class=\"prismnum\">9.5</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">p</span> = <span class=\"prismnum\">0.01</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismident\">p</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">x</span>=<span class=\"prismident\">k</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PropertiesFiles?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As before, these constants can actually be left undefined and then later\nassigned either a single value or a range of values using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'>In fact, values such as the probability bounds for the <code><strong>P</strong></code> or <code><strong>S</strong></code> operators (like <code><strong>P</strong></code> above)\nand upper or lower bounds for the <code><strong>U</strong></code> operator (like <code> T</code> above)\ncan be arbitrary expressions, provided they are constant.\nFurthermore, expressions in the properties file can also refer to constants previous defined in the model file.\n</p>\n<p class='vspace'><a name='labels' id='labels'></a>\n</p><h3>Labels</h3>\n<p>Another feature of properties files is <em>labels</em>. These are a way of defining sets of states that will be referred to in properties (they correspond to <em>atomic propositions</em> in a temporal logic setting). As described <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>earlier</a>, labels can be defined in either model files or property files.\n</p>\n<p class='vspace'>Labels are defined using the keyword <code><strong>label</strong></code>, followed by a name (identifier) in double quotes, and then an expression which evaluates to a Boolean. Definition and usage of labels are illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ \"<span class=\"prismident\">safe</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">fail</span>\" ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PropertiesFiles?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Two special cases are the <code>\"init\"</code> and <code>\"deadlock\"</code> labels which are always defined.\nThese are true in initial states of the model and states where deadlocks were found (and, usually, fixed by adding self-loops), respectively.\n</p>\n<p class='vspace'><a name='names' id='names'></a>\n</p><h3>Property names</h3>\n<p>For convenience, properties can be annotated with <em>names</em>, as shown in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\">\"<span class=\"prismident\">safe</span>\": <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">temperature</span> &gt; <span class=\"prismident\">t_max</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PropertiesFiles?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which gives the name <code>\"safe\"</code> to the property. It is then possible to include named properties as sub-expressions of other properties, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismident\">num_sensors</span>&gt;<span class=\"prismnum\">0</span> =&gt; \"<span class=\"prismident\">safe</span>\");<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PropertiesFiles?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the syntax for referring to named properties is identical to the syntax for labels. For this reason, property names must be disjoint from those of any existing labels.\n</p>\n<p class='vspace'>You can refer to property names when using the command-line switch <a class='wikilink' href='../RunningPRISM/ModelChecking.html#cl'><code>-prop</code></a> to specify which property is to be model checked.\n</p>\n<div class='vspace'></div><h3>Properties files</h3>\n<p>A PRISM properties file can contain any number of properties.\nIt is good practice, as shown in the examples above, to terminate each property with a semicolon. Currently, this is not enforced by PRISM (to prevent incompatibility with old properties files) but this may change in the future.\n</p>\n<p class='vspace'>Like model files, properties can also include any amount of white space (spaces, tabs, new lines, etc.) and C-style comments, which are both ignored.\nThe recommended file extension for PRISM properties is now <code>.props</code>.\nPreviously, though, the convention was to use extension <code>.pctl</code> for properties of DTMCs, MDPs or PTAs\nand extension <code>.csl</code> for properties of CTMCs, so these are still also valid.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PropertiesFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PropertiesFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 01:10 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='selflink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/PropertiesFiles@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Properties Files | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PropertiesFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PropertiesFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Properties Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PropertiesFiles@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PropertiesFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PropertiesFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 01:10 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='selflink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/PropertiesFiles@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Properties Files | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PropertiesFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PropertiesFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Properties Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PropertiesFiles@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PropertiesFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PropertiesFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PropertiesFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 01:10 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='selflink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/PropertiesFiles@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / PropertiesFiles </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Properties Files</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<h3>Constants</h3>\n<p>Files containing properties to be analysed by PRISM can also contain constants, as is the case for model files.\nThese are defined in identical fashion, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">k</span> = <span class=\"prismnum\">7</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span> = <span class=\"prismnum\">9.5</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">p</span> = <span class=\"prismnum\">0.01</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&lt;<span class=\"prismident\">p</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">x</span>=<span class=\"prismident\">k</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PropertiesFiles?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As before, these constants can actually be left undefined and then later\nassigned either a single value or a range of values using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'>In fact, values such as the probability bounds for the <code><strong>P</strong></code> or <code><strong>S</strong></code> operators (like <code><strong>P</strong></code> above)\nand upper or lower bounds for the <code><strong>U</strong></code> operator (like <code> T</code> above)\ncan be arbitrary expressions, provided they are constant.\nFurthermore, expressions in the properties file can also refer to constants previous defined in the model file.\n</p>\n<p class='vspace'><a name='labels' id='labels'></a>\n</p><h3>Labels</h3>\n<p>Another feature of properties files is <em>labels</em>. These are a way of defining sets of states that will be referred to in properties (they correspond to <em>atomic propositions</em> in a temporal logic setting). As described <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>earlier</a>, labels can be defined in either model files or property files.\n</p>\n<p class='vspace'>Labels are defined using the keyword <code><strong>label</strong></code>, followed by a name (identifier) in double quotes, and then an expression which evaluates to a Boolean. Definition and usage of labels are illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ \"<span class=\"prismident\">safe</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">fail</span>\" ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PropertiesFiles?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Two special cases are the <code>\"init\"</code> and <code>\"deadlock\"</code> labels which are always defined.\nThese are true in initial states of the model and states where deadlocks were found (and, usually, fixed by adding self-loops), respectively.\n</p>\n<p class='vspace'><a name='names' id='names'></a>\n</p><h3>Property names</h3>\n<p>For convenience, properties can be annotated with <em>names</em>, as shown in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\">\"<span class=\"prismident\">safe</span>\": <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">temperature</span> &gt; <span class=\"prismident\">t_max</span> ];<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PropertiesFiles?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which gives the name <code>\"safe\"</code> to the property. It is then possible to include named properties as sub-expressions of other properties, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">filter</span>(<span class=\"prismident\">forall</span>, <span class=\"prismident\">num_sensors</span>&gt;<span class=\"prismnum\">0</span> =&gt; \"<span class=\"prismident\">safe</span>\");<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/PropertiesFiles?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the syntax for referring to named properties is identical to the syntax for labels. For this reason, property names must be disjoint from those of any existing labels.\n</p>\n<p class='vspace'>You can refer to property names when using the command-line switch <a class='wikilink' href='../RunningPRISM/ModelChecking.html#cl'><code>-prop</code></a> to specify which property is to be model checked.\n</p>\n<div class='vspace'></div><h3>Properties files</h3>\n<p>A PRISM properties file can contain any number of properties.\nIt is good practice, as shown in the examples above, to terminate each property with a semicolon. Currently, this is not enforced by PRISM (to prevent incompatibility with old properties files) but this may change in the future.\n</p>\n<p class='vspace'>Like model files, properties can also include any amount of white space (spaces, tabs, new lines, etc.) and C-style comments, which are both ignored.\nThe recommended file extension for PRISM properties is now <code>.props</code>.\nPreviously, though, the convention was to use extension <code>.pctl</code> for properties of DTMCs, MDPs or PTAs\nand extension <code>.csl</code> for properties of CTMCs, so these are still also valid.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Real-timeModels.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Real-time Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Real-timeModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Real-time Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The classes of property that can be checked for real-time models (PTAs and POPTAs) are currently more restricted than for the other kinds of models that PRISM supports. This is because the model checking procedures are quite different for this type of model. We describe these restrictions here. The situation is also dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is being used.\n</p>\n<p class='vspace'>For the \"<strong>stochastic games</strong>\" engine, we essentially only allow unbounded or time-bounded probabilistic reachability properties, i.e. properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Real-timeModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>target</code> is a Boolean-valued expression that does not include references to any clock variables and <code>T</code> is an integer-valued expression. The <code><strong>P</strong></code> operator cannot be nested and the <code><strong>S</strong></code> and <code><strong>R</strong></code> operators are not supported.\n</p>\n<p class='vspace'>The \"<strong>backwards reachability</strong>\" engine is similar but currently only handles maximum probabilities.\n</p>\n<p class='vspace'>For the \"<strong>digital clocks</strong>\" engine, there is slightly more flexibility,\ne.g. until (<code><strong>U</strong></code>) properties are allowed, as are clock variables in expressions and arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Real-timeModels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This engine, like the \"stochastic games\" engine, does not allowed nested properties. Also, references to clocks must, like in the modelling language, not use strict comparisons\n(e.g. <code>x&lt;=5</code> is allowed, <code>x&lt;5</code> is not).\n</p>\n<p class='vspace'>The digital clocks also has support for rewards:\nit is possible to check reachability reward properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Real-timeModels?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Reward structures specified in the model, though, must not depend on clock variables.\nFormally, the class of PTAs with this kind of reward structure is sometime called <em>linearly priced PTAs</em> (see e.g. [<a class='wikilink' href='../Main/References.html#KNPS06'>KNPS06</a>].\n</p>\n<p class='vspace'>The digital clocks method is based on a language-level translation from a PTA model to an MDP one. If you want to see the MDP PRISM model that was generated, add the switch <code>-exportdigital digital.nm</code> when model checking property to export the model file to <code>digital.nm</code>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Real-timeModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:06 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='selflink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Real-timeModels@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Real-time Models | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Real-timeModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Real-time Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Real-timeModels@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Real-timeModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:06 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='selflink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Real-timeModels@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Real-time Models | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Real-timeModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Real-time Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Real-timeModels@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Real-timeModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:06 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='selflink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Real-timeModels@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / Real-timeModels </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Real-time Models</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>The classes of property that can be checked for real-time models (PTAs and POPTAs) are currently more restricted than for the other kinds of models that PRISM supports. This is because the model checking procedures are quite different for this type of model. We describe these restrictions here. The situation is also dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is being used.\n</p>\n<p class='vspace'>For the \"<strong>stochastic games</strong>\" engine, we essentially only allow unbounded or time-bounded probabilistic reachability properties, i.e. properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismident\">T</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Real-timeModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>target</code> is a Boolean-valued expression that does not include references to any clock variables and <code>T</code> is an integer-valued expression. The <code><strong>P</strong></code> operator cannot be nested and the <code><strong>S</strong></code> and <code><strong>R</strong></code> operators are not supported.\n</p>\n<p class='vspace'>The \"<strong>backwards reachability</strong>\" engine is similar but currently only handles maximum probabilities.\n</p>\n<p class='vspace'>For the \"<strong>digital clocks</strong>\" engine, there is slightly more flexibility,\ne.g. until (<code><strong>U</strong></code>) properties are allowed, as are clock variables in expressions and arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Real-timeModels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This engine, like the \"stochastic games\" engine, does not allowed nested properties. Also, references to clocks must, like in the modelling language, not use strict comparisons\n(e.g. <code>x&lt;=5</code> is allowed, <code>x&lt;5</code> is not).\n</p>\n<p class='vspace'>The digital clocks also has support for rewards:\nit is possible to check reachability reward properties of the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n<span class=\"prismkeyword\">Rmax</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">target</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Real-timeModels?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Reward structures specified in the model, though, must not depend on clock variables.\nFormally, the class of PTAs with this kind of reward structure is sometime called <em>linearly priced PTAs</em> (see e.g. [<a class='wikilink' href='../Main/References.html#KNPS06'>KNPS06</a>].\n</p>\n<p class='vspace'>The digital clocks method is based on a language-level translation from a PTA model to an MDP one. If you want to see the MDP PRISM model that was generated, add the switch <code>-exportdigital digital.nm</code> when model checking property to export the model file to <code>digital.nm</code>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Reward-basedProperties.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Reward-based Properties \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Reward-basedProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Reward-basedProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Reward-based Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM models can be augmented with information about <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>rewards</a> (or, equivalently, costs).\nThe tool can analyse properties which relate to the <em>expected values</em> of these rewards.\nThis is achieved using the <code><strong>R</strong></code> operator, which works in a similar fashion to the\n<code><strong>P</strong></code> and <code><strong>S</strong></code> operators, and can be used either in a Boolean-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>bound</code> takes the form <code>&lt;r</code>, <code>&lt;=r</code>, <code>&gt;r</code> or <code>&gt;=r</code> for an expression <code>r</code> evaluating to a non-negative double,\nor a real-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">query</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>query</code> is <code>=?</code>, <code>min=?</code> or <code>max=?</code>.\nIn the latter case, <a class='wikilink' href='Filters.html'>filters</a> can be used, as for the <code><strong>P</strong></code> and <code><strong>S</strong></code> operators.\n</p>\n<p class='vspace'>Informally, \"<code><strong>R</strong> bound [ rewardprop ]</code>\" is true in a state of a model if\n\"the expected reward associated with <code>rewardprop</code> of the model when starting from that state''\nmeets the bound <code>bound</code> and \"<code><strong>R</strong> query [ rewardprop ]</code>\"  returns the actual expected reward value.\n</p>\n<p class='vspace'>There are various different types of reward properties:\n</p>\n<div class='vspace'></div><ul><li>\"reachability reward\": <code><strong>F</strong> prop</code>\n</li><li>\"co-safe LTL reward\": e.g. <code><strong>F</strong> (prop1 &amp; <strong>F</strong> prop2)</code>\n</li><li>\"cumulative reward\" : <code><strong>C</strong>&lt;=t</code>\n</li><li>\"total reward\" : <code><strong>C</strong></code>\n</li><li>\"instantaneous reward\" : <code><strong>I</strong>=t</code>\n</li><li>\"steady-state reward\" : <code><strong>S</strong></code>.\n</li></ul><p class='vspace'>Below, we consider each of these cases in turn.\nThe descriptions here are kept relatively informal.\nPrecise definitions for most of these can be found in, for example,\n[<a class='wikilink' href='../Main/References.html#KNP07a'>KNP07a</a>] (for DTMCs and CTMCs) or [<a class='wikilink' href='../Main/References.html#FKNP11'>FKNP11</a>] (for MDPs).\n</p>\n<div class='vspace'></div><h3>\"Reachability reward\" properties</h3>\n<p>\"Reachability reward\" properties associate a reward with each path of a model.\nMore specifically, they refer to the reward accumulated along a path until a certain point is reached.\nThe manner in which rewards are accumulated depends on the model type.\nFor DTMCs and MDPs, the total reward for a path is the sum of the state rewards for each state along the path\nplus the sum of the transition rewards for each transition between these states.\nThe situation for CTMCs is similar, except that the state reward assigned to each state\nof the model is interpreted as the <em>rate</em> at which rewards are accumulated in that state,\ni.e. if <em>t</em> time units are spent in a state with state reward <em>r</em>,\nthe reward accumulated in that state is <em>r</em> x <em>t</em>.\nHence, the total reward for a path in a CTMC is the sum of these products for each state along the path\nplus the sum of the transition rewards for each transition between these states.\n</p>\n<p class='vspace'>The reward property \"<code>F prop</code>\" corresponds to the reward cumulated along a path\nuntil a state satisfying property <code>prop</code> is reached,\nwhere rewards are cumulated as described above.\nState rewards for the <code>prop</code>-satisfying state reached are not included in the cumulated value.\nIn the case where the probability of reaching a state satisfying <code>prop</code> is less than 1, the reward is equal to infinity.\n</p>\n<p class='vspace'>A common application of this type of property is the case when the rewards associated with the model correspond to time.\nOne can then state, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">9.5</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"the expected time taken to reach, from <em>s</em>, a state where <code>z</code> equals 2 is less than or equal to 9.5\".\n</p>\n<div class='vspace'></div><h3>\"Co-safe LTL reward\" properties</h3>\n<p>These generalise the \"reachability\" properties above. Again, reward is accumulated along a path up until some point,\nbut this is specified in a more general way, by giving a formula in the co-safe fragment of linear temporal logic (LTL).\nRewards are accumulated up until the point where the formula is first satisfied. For example, this property, for a DTMC or CTMC,\nqueries the expected reward accumulated until first <code>goal</code> equals 1 and then subsequently <code>goal</code> equals 2:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">F</span> (<span class=\"prismident\">goal</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismkeyword\">F</span> <span class=\"prismident\">goal</span>=<span class=\"prismnum\">2</span>) ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and this property, for an MDP, minimises the expected reward until <code>loc</code> equals 1,\nhaving passed only through states where <code>loc</code> never equals 4\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismident\">loc</span>!=<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">loc</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As for reachability rewards, if the probability of satisfying the formula is less than 1,\nthen the expected reward is defined to be infinite.\n</p>\n<p class='vspace'>Intuitively, a <em>co-safe</em> formula is one that is satisfied within a finite period of time,\nand remains true for ever once it becomes true for the first time.\nFor simplicity, PRISM actually supports the <em>syntactic</em> co-safe fragment of LTL,\nwhich is defined as any LTL formula that only uses the temporal operators <code><strong>F</strong></code>, <code><strong>U</strong></code> and <code><strong>X</strong></code>\n(but not <code><strong>G</strong></code>, for example).\nPRISM's notation for LTL formulas is described <a class='wikilink' href='ThePOperator.html'>here</a>.\n</p>\n<div class='vspace'></div><h3>\"Cumulative reward\" properties</h3>\n<p>\"Cumulative reward\" properties also associate a reward with each path of a model,\nbut only up to a given time bound.\nThe property <code>C&lt;=t</code> corresponds to the reward cumulated along a path\nuntil <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\nState and transition rewards along a path are cumulated exactly as described in the previous section.\n</p>\n<p class='vspace'>A typical application of this type of property is the following.\nConsider a model of a disk-drive controller which includes a queue of incoming disk requests.\nIf we assign a reward of 1 to each transition of the model\ncorresponding to the situation where an incoming request is lost because the queue is full,\nthen the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">15.5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would return, for a given state of the model,\n\"the expected number of lost requests within 15.5 time units of operation\".\n</p>\n<p class='vspace'><a name='total' id='total'></a>\n</p><h3>\"Total reward\" properties</h3>\n<p>\"Total reward\" properties refer to the accumulation of state and transition rewards\nin the same way as for \"reachability reward\" and \"cumulative reward\" properties,\nbut the rewards is accumulated indefinitely,\ni.e. the total reward accumulated along the whole (infinite) path.\nNote that this means that, unless a path ends up remaining forever in states with zero reward,\nthe total reward will be infinite.\n</p>\n<p class='vspace'>Re-using the reward structure in the previous example,\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>returns \"the expected total number of lost requests\".\n</p>\n<div class='vspace'></div><h3>\"Instantaneous reward\" properties</h3>\n<p>\"Instantaneous reward\" properties refer to the reward of a model at a particular instant in time.\nThe reward property <code>I=t</code> associates with a path the reward in the state \nof that path when exactly <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\n</p>\n<p class='vspace'>Returning to our example from the previous section of a model for a disk-request queue in a disk-drive controller,\nconsider the case where the rewards assigned to each state of the model give the current size of the queue in that state.\nThen, the following property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;<span class=\"prismnum\">4.4</span> [ <span class=\"prismkeyword\">I</span>=<span class=\"prismnum\">100</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would be true in a state <em>s</em> of the model if\n\"starting from <em>s</em>, the expected queue size exactly 100 time units later is less than 4.4\".\nNote that, for this type of reward property, state rewards for CTMCs do not have to refer to rates;\nthey can refer to any instantaneous measure of interest for a state.\n</p>\n<div class='vspace'></div><h3>\"Steady-state reward\" properties</h3>\n<p>Unlike the previous three types of property,\n\"steady-state reward\" properties relate not to paths, but rather to the reward in the long-run.\nA typical application of this type of property would be, in the case where\nthe rewards associated with the model correspond to power consumption, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">0.7</span> [ <span class=\"prismkeyword\">S</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"starting from <em>s</em>, the long-run average power consumption is less than 0.7\".\n</p>\n<div class='vspace'></div><h3>Which reward structure?</h3>\n<p>In the case where a PRISM model has multiple <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structures</a> you may need to specify which reward structure your property refers to. This is done by placing the information in braces (<code>{}</code>) after the <code>R</code> operator. You can do so either using the name assigned to a reward structure (if any) or using the index (where <code>1</code> means the first rewards structure in the PRISM model file, <code>2</code> the second, etc.). Examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">num_failures</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">10.0</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismnum\">2</span>}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note that when using an index to specify the reward structure, you can actually put any expression that evaluates to an integer. This allows you to, for example, write a property of the form <code>R{c}=?[...]</code> where <code>c</code> is an undefined integer constant. You can then vary the value of <code>c</code> in an experiment and compute values for several different reward structures at once.\n</p>\n<p class='vspace'>If you don't specify a reward structure to the <code>R</code> operator, by default, the first one in the model file is used.\n</p>\n<div class='vspace'></div><h3>Availability</h3>\n<p>There are currently a few restrictions on the model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a> that can be used for some reward properties. The following table summarises the currently availability, where S, M, H and E denote the \"sparse\", \"MTBDD\", \"hybrid\" and \"explicit\" engines, respectively, for DTMCs, CTMCs and MDPs. For PTAs, support for rewards is currently quite restrictive; see the later section on <a class='wikilink' href='Real-timeModels.html'>real-time model properties</a> for details.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><code><strong>F</strong></code></td><td  align='center'>cosafe</td><td  align='center'><code><strong>C</strong>&lt;=t</code></td><td  align='center'><code><strong>C</strong></code></td><td  align='left'><code><strong>I</strong>=t</code></td><td  align='right'><code><strong>S</strong></code></td></tr>\n<tr ><td  align='center'><strong>DTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>CTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>MDPs</strong></td><td  align='center'>SM-E</td><td  align='center'>SMHE</td><td  align='center'>S--E</td><td  align='center'>----</td><td  align='center'>SM-E</td><td  align='right'>----</td></tr>\n</table>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Reward-basedProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Reward-basedProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on October 18, 2021, at 07:31 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='selflink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Reward-basedProperties@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Reward-based Properties | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Reward-basedProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Reward-basedProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Reward-based Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Reward-basedProperties@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Reward-basedProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Reward-basedProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on October 18, 2021, at 07:31 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='selflink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Reward-basedProperties@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Reward-based Properties | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Reward-basedProperties.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Reward-basedProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Reward-based Properties</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Reward-basedProperties@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Reward-basedProperties.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=edit.html'>Edit</a> - <a class='wikilink' href='Reward-basedProperties@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Reward-basedProperties@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on October 18, 2021, at 07:31 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='selflink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/Reward-basedProperties@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / Reward-basedProperties </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Reward-based Properties</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM models can be augmented with information about <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>rewards</a> (or, equivalently, costs).\nThe tool can analyse properties which relate to the <em>expected values</em> of these rewards.\nThis is achieved using the <code><strong>R</strong></code> operator, which works in a similar fashion to the\n<code><strong>P</strong></code> and <code><strong>S</strong></code> operators, and can be used either in a Boolean-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>bound</code> takes the form <code>&lt;r</code>, <code>&lt;=r</code>, <code>&gt;r</code> or <code>&gt;=r</code> for an expression <code>r</code> evaluating to a non-negative double,\nor a real-valued query, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span> <span class=\"prismident\">query</span> [ <span class=\"prismident\">rewardprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>query</code> is <code>=?</code>, <code>min=?</code> or <code>max=?</code>.\nIn the latter case, <a class='wikilink' href='Filters.html'>filters</a> can be used, as for the <code><strong>P</strong></code> and <code><strong>S</strong></code> operators.\n</p>\n<p class='vspace'>Informally, \"<code><strong>R</strong> bound [ rewardprop ]</code>\" is true in a state of a model if\n\"the expected reward associated with <code>rewardprop</code> of the model when starting from that state''\nmeets the bound <code>bound</code> and \"<code><strong>R</strong> query [ rewardprop ]</code>\"  returns the actual expected reward value.\n</p>\n<p class='vspace'>There are various different types of reward properties:\n</p>\n<div class='vspace'></div><ul><li>\"reachability reward\": <code><strong>F</strong> prop</code>\n</li><li>\"co-safe LTL reward\": e.g. <code><strong>F</strong> (prop1 &amp; <strong>F</strong> prop2)</code>\n</li><li>\"cumulative reward\" : <code><strong>C</strong>&lt;=t</code>\n</li><li>\"total reward\" : <code><strong>C</strong></code>\n</li><li>\"instantaneous reward\" : <code><strong>I</strong>=t</code>\n</li><li>\"steady-state reward\" : <code><strong>S</strong></code>.\n</li></ul><p class='vspace'>Below, we consider each of these cases in turn.\nThe descriptions here are kept relatively informal.\nPrecise definitions for most of these can be found in, for example,\n[<a class='wikilink' href='../Main/References.html#KNP07a'>KNP07a</a>] (for DTMCs and CTMCs) or [<a class='wikilink' href='../Main/References.html#FKNP11'>FKNP11</a>] (for MDPs).\n</p>\n<div class='vspace'></div><h3>\"Reachability reward\" properties</h3>\n<p>\"Reachability reward\" properties associate a reward with each path of a model.\nMore specifically, they refer to the reward accumulated along a path until a certain point is reached.\nThe manner in which rewards are accumulated depends on the model type.\nFor DTMCs and MDPs, the total reward for a path is the sum of the state rewards for each state along the path\nplus the sum of the transition rewards for each transition between these states.\nThe situation for CTMCs is similar, except that the state reward assigned to each state\nof the model is interpreted as the <em>rate</em> at which rewards are accumulated in that state,\ni.e. if <em>t</em> time units are spent in a state with state reward <em>r</em>,\nthe reward accumulated in that state is <em>r</em> x <em>t</em>.\nHence, the total reward for a path in a CTMC is the sum of these products for each state along the path\nplus the sum of the transition rewards for each transition between these states.\n</p>\n<p class='vspace'>The reward property \"<code>F prop</code>\" corresponds to the reward cumulated along a path\nuntil a state satisfying property <code>prop</code> is reached,\nwhere rewards are cumulated as described above.\nState rewards for the <code>prop</code>-satisfying state reached are not included in the cumulated value.\nIn the case where the probability of reaching a state satisfying <code>prop</code> is less than 1, the reward is equal to infinity.\n</p>\n<p class='vspace'>A common application of this type of property is the case when the rewards associated with the model correspond to time.\nOne can then state, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">9.5</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"the expected time taken to reach, from <em>s</em>, a state where <code>z</code> equals 2 is less than or equal to 9.5\".\n</p>\n<div class='vspace'></div><h3>\"Co-safe LTL reward\" properties</h3>\n<p>These generalise the \"reachability\" properties above. Again, reward is accumulated along a path up until some point,\nbut this is specified in a more general way, by giving a formula in the co-safe fragment of linear temporal logic (LTL).\nRewards are accumulated up until the point where the formula is first satisfied. For example, this property, for a DTMC or CTMC,\nqueries the expected reward accumulated until first <code>goal</code> equals 1 and then subsequently <code>goal</code> equals 2:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">F</span> (<span class=\"prismident\">goal</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismkeyword\">F</span> <span class=\"prismident\">goal</span>=<span class=\"prismnum\">2</span>) ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and this property, for an MDP, minimises the expected reward until <code>loc</code> equals 1,\nhaving passed only through states where <code>loc</code> never equals 4\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">Rmin</span>=? [ <span class=\"prismident\">loc</span>!=<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">loc</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As for reachability rewards, if the probability of satisfying the formula is less than 1,\nthen the expected reward is defined to be infinite.\n</p>\n<p class='vspace'>Intuitively, a <em>co-safe</em> formula is one that is satisfied within a finite period of time,\nand remains true for ever once it becomes true for the first time.\nFor simplicity, PRISM actually supports the <em>syntactic</em> co-safe fragment of LTL,\nwhich is defined as any LTL formula that only uses the temporal operators <code><strong>F</strong></code>, <code><strong>U</strong></code> and <code><strong>X</strong></code>\n(but not <code><strong>G</strong></code>, for example).\nPRISM's notation for LTL formulas is described <a class='wikilink' href='ThePOperator.html'>here</a>.\n</p>\n<div class='vspace'></div><h3>\"Cumulative reward\" properties</h3>\n<p>\"Cumulative reward\" properties also associate a reward with each path of a model,\nbut only up to a given time bound.\nThe property <code>C&lt;=t</code> corresponds to the reward cumulated along a path\nuntil <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\nState and transition rewards along a path are cumulated exactly as described in the previous section.\n</p>\n<p class='vspace'>A typical application of this type of property is the following.\nConsider a model of a disk-drive controller which includes a queue of incoming disk requests.\nIf we assign a reward of 1 to each transition of the model\ncorresponding to the situation where an incoming request is lost because the queue is full,\nthen the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">15.5</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would return, for a given state of the model,\n\"the expected number of lost requests within 15.5 time units of operation\".\n</p>\n<p class='vspace'><a name='total' id='total'></a>\n</p><h3>\"Total reward\" properties</h3>\n<p>\"Total reward\" properties refer to the accumulation of state and transition rewards\nin the same way as for \"reachability reward\" and \"cumulative reward\" properties,\nbut the rewards is accumulated indefinitely,\ni.e. the total reward accumulated along the whole (infinite) path.\nNote that this means that, unless a path ends up remaining forever in states with zero reward,\nthe total reward will be infinite.\n</p>\n<p class='vspace'>Re-using the reward structure in the previous example,\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>=? [ <span class=\"prismkeyword\">C</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>returns \"the expected total number of lost requests\".\n</p>\n<div class='vspace'></div><h3>\"Instantaneous reward\" properties</h3>\n<p>\"Instantaneous reward\" properties refer to the reward of a model at a particular instant in time.\nThe reward property <code>I=t</code> associates with a path the reward in the state \nof that path when exactly <code>t</code> time units have elapsed.\nFor DTMCs and MDPs, the bound <code>t</code> must evaluate to an integer;\nfor CTMCs, it can evaluate to double.\n</p>\n<p class='vspace'>Returning to our example from the previous section of a model for a disk-request queue in a disk-drive controller,\nconsider the case where the rewards assigned to each state of the model give the current size of the queue in that state.\nThen, the following property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;<span class=\"prismnum\">4.4</span> [ <span class=\"prismkeyword\">I</span>=<span class=\"prismnum\">100</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would be true in a state <em>s</em> of the model if\n\"starting from <em>s</em>, the expected queue size exactly 100 time units later is less than 4.4\".\nNote that, for this type of reward property, state rewards for CTMCs do not have to refer to rates;\nthey can refer to any instantaneous measure of interest for a state.\n</p>\n<div class='vspace'></div><h3>\"Steady-state reward\" properties</h3>\n<p>Unlike the previous three types of property,\n\"steady-state reward\" properties relate not to paths, but rather to the reward in the long-run.\nA typical application of this type of property would be, in the case where\nthe rewards associated with the model correspond to power consumption, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>&lt;=<span class=\"prismnum\">0.7</span> [ <span class=\"prismkeyword\">S</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state <em>s</em> if \"starting from <em>s</em>, the long-run average power consumption is less than 0.7\".\n</p>\n<div class='vspace'></div><h3>Which reward structure?</h3>\n<p>In the case where a PRISM model has multiple <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structures</a> you may need to specify which reward structure your property refers to. This is done by placing the information in braces (<code>{}</code>) after the <code>R</code> operator. You can do so either using the name assigned to a reward structure (if any) or using the index (where <code>1</code> means the first rewards structure in the PRISM model file, <code>2</code> the second, etc.). Examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">num_failures</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismnum\">10.0</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">time</span>\"}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismnum\">2</span>}=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">step</span>=<span class=\"prismident\">final</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/Reward-basedProperties?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note that when using an index to specify the reward structure, you can actually put any expression that evaluates to an integer. This allows you to, for example, write a property of the form <code>R{c}=?[...]</code> where <code>c</code> is an undefined integer constant. You can then vary the value of <code>c</code> in an experiment and compute values for several different reward structures at once.\n</p>\n<p class='vspace'>If you don't specify a reward structure to the <code>R</code> operator, by default, the first one in the model file is used.\n</p>\n<div class='vspace'></div><h3>Availability</h3>\n<p>There are currently a few restrictions on the model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>engines</a> that can be used for some reward properties. The following table summarises the currently availability, where S, M, H and E denote the \"sparse\", \"MTBDD\", \"hybrid\" and \"explicit\" engines, respectively, for DTMCs, CTMCs and MDPs. For PTAs, support for rewards is currently quite restrictive; see the later section on <a class='wikilink' href='Real-timeModels.html'>real-time model properties</a> for details.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><code><strong>F</strong></code></td><td  align='center'>cosafe</td><td  align='center'><code><strong>C</strong>&lt;=t</code></td><td  align='center'><code><strong>C</strong></code></td><td  align='left'><code><strong>I</strong>=t</code></td><td  align='right'><code><strong>S</strong></code></td></tr>\n<tr ><td  align='center'><strong>DTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>CTMCs</strong></td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='center'>SMHE</td><td  align='right'>SMHE</td></tr>\n<tr ><td  align='center'><strong>MDPs</strong></td><td  align='center'>SM-E</td><td  align='center'>SMHE</td><td  align='center'>S--E</td><td  align='center'>----</td><td  align='center'>SM-E</td><td  align='right'>----</td></tr>\n</table>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/SyntaxAndSemantics.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Syntax And Semantics \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SyntaxAndSemantics.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=edit.html'>Edit</a> - <a class='wikilink' href='SyntaxAndSemantics@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Syntax And Semantics</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<h3>Syntax</h3>\n<p>The syntax of the PRISM property specification language subsumes various probabilistic temporal logics, including PCTL, CSL, (probabilistic) LTL, PCTL* and CTL. Informally, the syntax can be summarised as follows: a property can be any valid, well-typed PRISM <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a>, which (optionally) also includes the probabilistic operators discussed previously (<code><strong>P</strong></code>, <code><strong>S</strong></code> and <code><strong>R</strong></code>) and the non-probabilistic (CTL) ones <code><strong>A</strong></code> and <code><strong>E</strong></code>). This mean that any of the following operators can be used:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li><li><code><strong>P</strong></code> (probabilistic operator)\n</li><li><code><strong>S</strong></code> (steady-state operator)\n</li><li><code><strong>R</strong></code> (reward operator)\n</li><li><code><strong>A</strong></code> (for-all operator)\n</li><li><code><strong>E</strong></code> (there-exists operator)\n</li></ul><p class='vspace'>This allows you to write any property expressible in logics such as PCTL and CSL. For example, CSL allows you to nest <code><strong>P</strong></code> and <code><strong>S</strong></code> operators:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>&gt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">S</span>&gt;<span class=\"prismnum\">0.9</span>[ <span class=\"prismident\">num_servers</span> &gt;= <span class=\"prismnum\">5</span> ] ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of it taking more than 2 hours to get to a state from which the long-run probability of at least 5 servers being operational is &gt;0.9\"\n</p>\n<p class='vspace'>You can also express various arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">3600</span>,<span class=\"prismnum\">7200</span>] <span class=\"prismident\">oper</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability that the system is <strong>not</strong> operational at any point during the second hour of operation\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">oper</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">t</span> ] / <span class=\"prismident\">t</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the expected fraction of time that the system is available (i.e. the expected interval availability) in the time interval [0, t]\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">fail_A</span> ] / <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">any_fail</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the (conditional) probability that component A eventually fails, given\nthat at least one component fails\"\n</p>\n<div class='vspace'></div><h3>Semantics</h3>\n<p>We omit a formal presentation of the semantics of the PRISM property language. The semantics of the probabilistic temporal logics that the language incorporates can be found from a variety of sources. See for example the pointers given in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>It is worth, however, clarifying a few points specific to PRISM. A property is evaluated with respect to a particular state of a model. Depending on the type of the property, this value may either be a Boolean, an integer or a double. When performing model checking, PRISM usually has to actually compute the value for <em>all</em> states of the model but, for clarity, will by default report just a single value. Typically, this is the value for the (single) initial state of the model. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will report the probability, from the initial state of the model, of reaching an \"error\" state.\nThis:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will return <code>true</code> if and only if the probability, from the initial state, is greater than 0.5.\n</p>\n<p class='vspace'><strong>Note:</strong> This is contrast to older versions of PRISM, which treated numerical and Boolean-valued properties differently in this respect.\n</p>\n<p class='vspace'>For models with <a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>multiple initial states</a>, we need to adapt these definitions slightly. In this case, the two properties above will yield, respectively:\n</p>\n<div class='vspace'></div><ul><li>the range of values (over all initial states) of the probability of reaching \"error\"\n<div class='vspace'></div></li><li><code>true</code> if and only if the probability is greater than 0.5 from <em>all</em> initial states.\n</li></ul><p class='vspace'>You can also ask PRISM to return different values using <a class='wikilink' href='Filters.html'>filters</a>,\nwhich are described in the next section.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SyntaxAndSemantics.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=edit.html'>Edit</a> - <a class='wikilink' href='SyntaxAndSemantics@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 10:10 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='selflink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/SyntaxAndSemantics@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Syntax And Semantics | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SyntaxAndSemantics.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=edit.html'>Edit</a> - <a class='wikilink' href='SyntaxAndSemantics@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Syntax And Semantics</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='SyntaxAndSemantics@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SyntaxAndSemantics.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=edit.html'>Edit</a> - <a class='wikilink' href='SyntaxAndSemantics@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 10:10 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='selflink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/SyntaxAndSemantics@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Syntax And Semantics | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SyntaxAndSemantics.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=edit.html'>Edit</a> - <a class='wikilink' href='SyntaxAndSemantics@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Syntax And Semantics</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='SyntaxAndSemantics@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SyntaxAndSemantics.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=edit.html'>Edit</a> - <a class='wikilink' href='SyntaxAndSemantics@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SyntaxAndSemantics@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 30, 2013, at 10:10 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='selflink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/SyntaxAndSemantics@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / SyntaxAndSemantics </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Syntax And Semantics</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<h3>Syntax</h3>\n<p>The syntax of the PRISM property specification language subsumes various probabilistic temporal logics, including PCTL, CSL, (probabilistic) LTL, PCTL* and CTL. Informally, the syntax can be summarised as follows: a property can be any valid, well-typed PRISM <a class='wikilink' href='../ThePRISMLanguage/Expressions.html'>expression</a>, which (optionally) also includes the probabilistic operators discussed previously (<code><strong>P</strong></code>, <code><strong>S</strong></code> and <code><strong>R</strong></code>) and the non-probabilistic (CTL) ones <code><strong>A</strong></code> and <code><strong>E</strong></code>). This mean that any of the following operators can be used:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li><li><code><strong>P</strong></code> (probabilistic operator)\n</li><li><code><strong>S</strong></code> (steady-state operator)\n</li><li><code><strong>R</strong></code> (reward operator)\n</li><li><code><strong>A</strong></code> (for-all operator)\n</li><li><code><strong>E</strong></code> (there-exists operator)\n</li></ul><p class='vspace'>This allows you to write any property expressible in logics such as PCTL and CSL. For example, CSL allows you to nest <code><strong>P</strong></code> and <code><strong>S</strong></code> operators:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>&gt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">S</span>&gt;<span class=\"prismnum\">0.9</span>[ <span class=\"prismident\">num_servers</span> &gt;= <span class=\"prismnum\">5</span> ] ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of it taking more than 2 hours to get to a state from which the long-run probability of at least 5 servers being operational is &gt;0.9\"\n</p>\n<p class='vspace'>You can also express various arithmetic expressions such as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismnum\">1</span> - <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">3600</span>,<span class=\"prismnum\">7200</span>] <span class=\"prismident\">oper</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability that the system is <strong>not</strong> operational at any point during the second hour of operation\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">R</span>{\"<span class=\"prismident\">oper</span>\"}=? [ <span class=\"prismkeyword\">C</span>&lt;=<span class=\"prismident\">t</span> ] / <span class=\"prismident\">t</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the expected fraction of time that the system is available (i.e. the expected interval availability) in the time interval [0, t]\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">fail_A</span> ] / <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">any_fail</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the (conditional) probability that component A eventually fails, given\nthat at least one component fails\"\n</p>\n<div class='vspace'></div><h3>Semantics</h3>\n<p>We omit a formal presentation of the semantics of the PRISM property language. The semantics of the probabilistic temporal logics that the language incorporates can be found from a variety of sources. See for example the pointers given in the <a class='urllink' href='http://www.prismmodelchecker.org/about.php'>About</a> and <a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a> sections of the PRISM website.\n</p>\n<p class='vspace'>It is worth, however, clarifying a few points specific to PRISM. A property is evaluated with respect to a particular state of a model. Depending on the type of the property, this value may either be a Boolean, an integer or a double. When performing model checking, PRISM usually has to actually compute the value for <em>all</em> states of the model but, for clarity, will by default report just a single value. Typically, this is the value for the (single) initial state of the model. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will report the probability, from the initial state of the model, of reaching an \"error\" state.\nThis:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error</span>\" ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/SyntaxAndSemantics?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>will return <code>true</code> if and only if the probability, from the initial state, is greater than 0.5.\n</p>\n<p class='vspace'><strong>Note:</strong> This is contrast to older versions of PRISM, which treated numerical and Boolean-valued properties differently in this respect.\n</p>\n<p class='vspace'>For models with <a class='wikilink' href='../ThePRISMLanguage/MultipleInitialStates.html'>multiple initial states</a>, we need to adapt these definitions slightly. In this case, the two properties above will yield, respectively:\n</p>\n<div class='vspace'></div><ul><li>the range of values (over all initial states) of the probability of reaching \"error\"\n<div class='vspace'></div></li><li><code>true</code> if and only if the probability is greater than 0.5 from <em>all</em> initial states.\n</li></ul><p class='vspace'>You can also ask PRISM to return different values using <a class='wikilink' href='Filters.html'>filters</a>,\nwhich are described in the next section.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/ThePOperator.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / The P Operator \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ThePOperator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ThePOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='ThePOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>The P Operator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>One of the most important operators in the PRISM property specification language is the <code><strong>P</strong></code> operator, which is used to reason about the probability of an event's occurrence. This operator was originally proposed in the logic PCTL but also features in the other logics supported by PRISM, such as CSL. The <code><strong>P</strong></code> operator is applicable to all types of models supported by PRISM.\n</p>\n<p class='vspace'>Informally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a model if\n\"the probability that path property <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code>\".\nA typical example of a bound would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em> is greater than 0.98\". More precisely, <code>bound</code> can be any of <code>&gt;=p</code>, <code>&gt;p</code>, <code>&lt;=p</code> or <code>&lt;p</code>,\nwhere <code>p</code> is a PRISM language expression evaluating to a double in the range [0,1].\n</p>\n<p class='vspace'>The types of path property supported by PRISM and their semantics will be discussed shortly.\n</p>\n<div class='vspace'></div><h3>Nondeterminism</h3>\n<p>For models that can exhibit nondeterministic behaviour, such as MDPs or PTAs, some additional clarifications are necessary. Whereas for fully probabilistic models such as DTMCs and CTMCs, probability measures over paths are well defined (see e.g. [<a class='wikilink' href='../Main/References.html#KSK76'>KSK76</a>] and [<a class='wikilink' href='../Main/References.html#BKH99'>BKH99</a>], respectively), for nondeterministic models a probability measure can only be feasibly defined once all nondeterminism has been removed.\n</p>\n<p class='vspace'>Hence, the actual meaning of the property <code>P bound [ pathprop ]</code> in these cases is: \n\"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code> <em>for all possible resolutions of nondeterminism</em>\".\nThis means that, properties using the <code><strong>P</strong></code> operator then effectively reason about the\n<em>minimum</em> or <em>maximum</em> probability, over all possible resolutions of nondeterminism,\nthat a certain type of behaviour is observed.\nThis depends on the bound attached to the <code><strong>P</strong></code> operator:\na lower bound (<code>&gt;</code> or <code>&gt;=</code>) relates to minimum probabilities\nand an upper bound (<code>&lt;</code> or <code>&lt;=</code>) to maximum probabilities.\n</p>\n<div class='vspace'></div><h3>Quantitative properties</h3>\n<p>It is also very often useful to take a <em>quantitative</em> approach to probabilistic model checking, computing the actual probability that some behaviour of a model is observed,\nrather than just verifying whether or not the probability is above or below a given bound.\nHence, PRISM allows the <code><strong>P</strong></code> operator to take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These properties return a numerical rather than a Boolean value.\nThe <a class='wikilink' href='TheSOperator.html'>S</a> and <a class='wikilink' href='Reward-basedProperties.html'>R</a> operators, discussed later, can also be used in this way.\n</p>\n<p class='vspace'>As mentioned above, for nondeterministic models (MDPs or PTAs), either minimum or maximum probability values can be computed. Therefore, in this case, we have two possible types of property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which return the minimum and maximum probabilities, respectively.\n</p>\n<p class='vspace'>It is also possible to specify to which state the probability returned by a quantitative property refers. This is covered in the later section on <a class='wikilink' href='Filters.html'>filters</a>.\n</p>\n<div class='vspace'></div><h3>Path properties</h3>\n<p>PRISM supports a wide range of path properties that can be used with the <code><strong>P</strong></code> operator.\nA path property is a formula that evaluates to either true or false for a single path in a model.\nHere, we review some of the simpler properties that feature a single <em>temporal operator</em>,\nas used for example in the logics PCTL and CSL. Later, we briefly describe how PRISM also supports more complex LTL-style path properties.\n</p>\n<p class='vspace'>The basic different types of path property that can be used inside the <code><strong>P</strong></code> operator are:\n</p>\n<div class='vspace'></div><ul><li><code><strong>X</strong></code> : \"ne<strong>x</strong>t\"\n</li><li><code><strong>U</strong></code> : \"<strong>u</strong>ntil\"\n</li><li><code><strong>F</strong></code> : \"eventually\" (sometimes called \"<strong>f</strong>uture\")\n</li><li><code><strong>G</strong></code> : \"always\" (sometimes called \"<strong>g</strong>lobally\")\n</li><li><code><strong>W</strong></code> : \"<strong>w</strong>eak until\"\n</li><li><code><strong>R</strong></code> : \"<strong>r</strong>elease\"\n</li></ul><p class='vspace'>In the following sections, we describe each of these <em>temporal operators</em>. We then discuss the (optional) use of time bounds with these operators. Finally, we also discuss LTL-style path properties.\n</p>\n<div class='vspace'></div><h3>\"Next\" path properties</h3>\n<p>The property <code><strong>X</strong> prop</code> is true for a path if <code>prop</code> is true in its second state,\nAn example of this type of property, used inside a <code><strong>P</strong></code> operator, is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">X</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of the expression <code>y=1</code> being true in the next state is less than 0.01\".\n</p>\n<div class='vspace'></div><h3>\"Until\" path properties</h3>\n<p>The property <code>prop1 <strong>U</strong> prop2</code> is true for a path if\n<code>prop2</code> is true in some state of the path and <code>prop1</code> is true in all preceding states.\nA simple example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually equal to 2, and that <code>z</code> remains less than 2 up until that point, is greater than 0.5\".\n</p>\n<div class='vspace'></div><h3>\"Eventually\" path properties</h3>\n<p>The property <code><strong>F</strong> prop</code> is true for a path if <code>prop</code> eventually becomes true at some point along the path. The <code><strong>F</strong></code> operator is in fact a special case of the <code><strong>U</strong></code> operator (you will often see <code> <strong>F</strong> prop</code> written as <code><strong>true</strong> <strong>U</strong> prop</code>). A simple example is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>&gt;<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually greater than 2is less than 0.1\".\n</p>\n<div class='vspace'></div><h3>\"Globally\" path properties</h3>\n<p>Whereas the <code><strong>F</strong></code> operator is used for \"reachability\" properties, <code><strong>G</strong></code> represents \"invariance\". The property <code><strong>G</strong> prop</code> is true of a path if <code>prop</code> remains true at all states along the path. Thus, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>states that, with probability at least 0.99, <code>z</code> never exceeds 10.\n</p>\n<div class='vspace'></div><h3>\"Weak until\" and \"release\" path properties</h3>\n<p>Like <code><strong>F</strong></code> and <code><strong>G</strong></code>, the operators <code><strong>W</strong></code> and <code><strong>R</strong></code> are derivable from other temporal operators.\n</p>\n<p class='vspace'>Weak until (<code>a <strong>W</strong> b</code>), which is equivalent to <code>(a <strong>U</strong> b) | <strong>G</strong> a</code>, requires that <code>a</code> remains true until <code>b</code> becomes true, but does not require that <code>b</code> ever does becomes true (i.e. <code>a</code> remains true forever). For example, a weak form of the until example used above is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which states that, with probability greater than 0.5, either <code>z</code> is always less than 2, or it is less than 2 until the point where <code>z</code> is 2.\n</p>\n<p class='vspace'>Release (<code>a <strong>R</strong> b</code>),  which is equivalent to <code>!(!a U !b)</code>, informally means that <code>b</code> is true until <code>a</code> becomes true, or <code>b</code> is true forever.\n</p>\n<p class='vspace'><a name='bounded' id='bounded'></a>\n</p><h3>\"Bounded\" variants of path properties</h3>\n<p>All of the temporal operators given above, with the exception of <code><strong>X</strong></code>, have \"bounded\" variants, where an additional time bound is imposed on the property being satisfied.\nThe most common case is to use an upper time bound, i.e. of the form \"<code>&lt;=t</code>\" or \"<code>&lt;t</code>\", where <code>t</code> is a PRISM expression evaluating to a constant, non-negative value.\n</p>\n<p class='vspace'>For example, a bounded until property <code>prop1 <strong>U</strong>&lt;=t prop2</code>, is satisfied along a path if <code>prop2</code> becomes true within <code>t</code> steps and <code>prop1</code> is true in all states before that point.\nA typical example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">y</span>&lt;<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of <code>y</code> first exceeding 3 within 7 time units is greater than or equal to 0.98\". Similarly:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state if \"the probability of <code>y</code> being equal to 4 within 7 time units is greater than or equal to 0.98\" and:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true if the probability of <code>y</code> staying equal to 4 for 7 time units is at least 0.98.\n</p>\n<p class='vspace'>The time bound can be an arbitrary (constant) expression,\nbut note that you may need to bracket it,\nas in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=(<span class=\"prismnum\">2</span>*<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>) <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use lower time-bounds (i.e. <code>&gt;=t</code> or <code>&gt;t</code>) and time intervals <code>[t1,t2]</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&gt;=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">20</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which refer to the probability of <code>y</code> becoming equal to 4 after 10 or more time units, and after between 10 and 20 time-units respectively.\n</p>\n<p class='vspace'>For CTMCs, the time bounds can be any (non-negative) numerical values - they are not restricted to integers, as for discrete-time models.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.25</span> [ <span class=\"prismident\">y</span>&lt;=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">6.5</span> <span class=\"prismident\">y</span>&gt;<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means that the probability of <code>y</code> being greater than 1 within 6.5 time-units (and remaining less than or equal to 1 at all preceding time-points) is at least 0.25.\n</p>\n<div class='vspace'></div><h3>Transient probabilities</h3>\n<p>We can also use the bounded <code><strong>F</strong></code> operator to refer to a single time instant, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">10</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or, equivalently:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>both of which give the probability of <code>y</code> being 6 at time instant 10.\n</p>\n<p class='vspace'><a name='ltl' id='ltl'></a>\n</p><h3>LTL-style path properties</h3>\n<p>PRISM also supports probabilistic model checking of the temporal logic LTL (and, in fact, PCTL*). LTL provides a richer set of path properties for use with the <code><strong>P</strong></code> operator, by permitting temporal operators to be combined. Here are a few examples of properties expressible using this functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">F</span> ( \"<span class=\"prismident\">request</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">ack</span>\") ) ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"with probability greater than 0.99, a request is eventually received, followed immediately by an acknowledgement\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">send</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"a message is sent infinitely often with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">G</span> (\"<span class=\"prismident\">error</span>\" &amp; !\"<span class=\"prismident\">repair</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of an error occurring that is never repaired\n</p>\n<p class='vspace'>Note that logical operators have precedence over temporal ones, so you will often need to include parentheses when using logical operators, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\") &amp; (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For temporal operators, unary operators (such as <code><strong>F</strong></code>, <code><strong>G</strong></code> and <code><strong>X</strong></code>) have precedence over binary ones (such as <code><strong>U</strong></code>). Unary operators can be nested, without parentheses, but binary ones cannot.\n</p>\n<p class='vspace'>So, these are allowed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">a</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ (\"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\") <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>but this is not:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ThePOperator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ThePOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='ThePOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ThePOperator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:30 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='selflink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/ThePOperator@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / The P Operator | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ThePOperator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ThePOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='ThePOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>The P Operator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ThePOperator@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ThePOperator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ThePOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='ThePOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ThePOperator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:30 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='selflink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/ThePOperator@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / The P Operator | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ThePOperator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ThePOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='ThePOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>The P Operator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ThePOperator@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ThePOperator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ThePOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='ThePOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ThePOperator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:30 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='selflink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/ThePOperator@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / ThePOperator </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>The P Operator</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>One of the most important operators in the PRISM property specification language is the <code><strong>P</strong></code> operator, which is used to reason about the probability of an event's occurrence. This operator was originally proposed in the logic PCTL but also features in the other logics supported by PRISM, such as CSL. The <code><strong>P</strong></code> operator is applicable to all types of models supported by PRISM.\n</p>\n<p class='vspace'>Informally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a model if\n\"the probability that path property <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code>\".\nA typical example of a bound would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">pathprop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em> is greater than 0.98\". More precisely, <code>bound</code> can be any of <code>&gt;=p</code>, <code>&gt;p</code>, <code>&lt;=p</code> or <code>&lt;p</code>,\nwhere <code>p</code> is a PRISM language expression evaluating to a double in the range [0,1].\n</p>\n<p class='vspace'>The types of path property supported by PRISM and their semantics will be discussed shortly.\n</p>\n<div class='vspace'></div><h3>Nondeterminism</h3>\n<p>For models that can exhibit nondeterministic behaviour, such as MDPs or PTAs, some additional clarifications are necessary. Whereas for fully probabilistic models such as DTMCs and CTMCs, probability measures over paths are well defined (see e.g. [<a class='wikilink' href='../Main/References.html#KSK76'>KSK76</a>] and [<a class='wikilink' href='../Main/References.html#BKH99'>BKH99</a>], respectively), for nondeterministic models a probability measure can only be feasibly defined once all nondeterminism has been removed.\n</p>\n<p class='vspace'>Hence, the actual meaning of the property <code>P bound [ pathprop ]</code> in these cases is: \n\"the probability that <code>pathprop</code> is satisfied by the paths from state <em>s</em>\nmeets the bound <code>bound</code> <em>for all possible resolutions of nondeterminism</em>\".\nThis means that, properties using the <code><strong>P</strong></code> operator then effectively reason about the\n<em>minimum</em> or <em>maximum</em> probability, over all possible resolutions of nondeterminism,\nthat a certain type of behaviour is observed.\nThis depends on the bound attached to the <code><strong>P</strong></code> operator:\na lower bound (<code>&gt;</code> or <code>&gt;=</code>) relates to minimum probabilities\nand an upper bound (<code>&lt;</code> or <code>&lt;=</code>) to maximum probabilities.\n</p>\n<div class='vspace'></div><h3>Quantitative properties</h3>\n<p>It is also very often useful to take a <em>quantitative</em> approach to probabilistic model checking, computing the actual probability that some behaviour of a model is observed,\nrather than just verifying whether or not the probability is above or below a given bound.\nHence, PRISM allows the <code><strong>P</strong></code> operator to take the following form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These properties return a numerical rather than a Boolean value.\nThe <a class='wikilink' href='TheSOperator.html'>S</a> and <a class='wikilink' href='Reward-basedProperties.html'>R</a> operators, discussed later, can also be used in this way.\n</p>\n<p class='vspace'>As mentioned above, for nondeterministic models (MDPs or PTAs), either minimum or maximum probability values can be computed. Therefore, in this case, we have two possible types of property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismident\">pathprop</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which return the minimum and maximum probabilities, respectively.\n</p>\n<p class='vspace'>It is also possible to specify to which state the probability returned by a quantitative property refers. This is covered in the later section on <a class='wikilink' href='Filters.html'>filters</a>.\n</p>\n<div class='vspace'></div><h3>Path properties</h3>\n<p>PRISM supports a wide range of path properties that can be used with the <code><strong>P</strong></code> operator.\nA path property is a formula that evaluates to either true or false for a single path in a model.\nHere, we review some of the simpler properties that feature a single <em>temporal operator</em>,\nas used for example in the logics PCTL and CSL. Later, we briefly describe how PRISM also supports more complex LTL-style path properties.\n</p>\n<p class='vspace'>The basic different types of path property that can be used inside the <code><strong>P</strong></code> operator are:\n</p>\n<div class='vspace'></div><ul><li><code><strong>X</strong></code> : \"ne<strong>x</strong>t\"\n</li><li><code><strong>U</strong></code> : \"<strong>u</strong>ntil\"\n</li><li><code><strong>F</strong></code> : \"eventually\" (sometimes called \"<strong>f</strong>uture\")\n</li><li><code><strong>G</strong></code> : \"always\" (sometimes called \"<strong>g</strong>lobally\")\n</li><li><code><strong>W</strong></code> : \"<strong>w</strong>eak until\"\n</li><li><code><strong>R</strong></code> : \"<strong>r</strong>elease\"\n</li></ul><p class='vspace'>In the following sections, we describe each of these <em>temporal operators</em>. We then discuss the (optional) use of time bounds with these operators. Finally, we also discuss LTL-style path properties.\n</p>\n<div class='vspace'></div><h3>\"Next\" path properties</h3>\n<p>The property <code><strong>X</strong> prop</code> is true for a path if <code>prop</code> is true in its second state,\nAn example of this type of property, used inside a <code><strong>P</strong></code> operator, is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.01</span> [ <span class=\"prismkeyword\">X</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of the expression <code>y=1</code> being true in the next state is less than 0.01\".\n</p>\n<div class='vspace'></div><h3>\"Until\" path properties</h3>\n<p>The property <code>prop1 <strong>U</strong> prop2</code> is true for a path if\n<code>prop2</code> is true in some state of the path and <code>prop1</code> is true in all preceding states.\nA simple example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually equal to 2, and that <code>z</code> remains less than 2 up until that point, is greater than 0.5\".\n</p>\n<div class='vspace'></div><h3>\"Eventually\" path properties</h3>\n<p>The property <code><strong>F</strong> prop</code> is true for a path if <code>prop</code> eventually becomes true at some point along the path. The <code><strong>F</strong></code> operator is in fact a special case of the <code><strong>U</strong></code> operator (you will often see <code> <strong>F</strong> prop</code> written as <code><strong>true</strong> <strong>U</strong> prop</code>). A simple example is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&lt;<span class=\"prismnum\">0.1</span> [ <span class=\"prismkeyword\">F</span> <span class=\"prismident\">z</span>&gt;<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability that <code>z</code> is eventually greater than 2is less than 0.1\".\n</p>\n<div class='vspace'></div><h3>\"Globally\" path properties</h3>\n<p>Whereas the <code><strong>F</strong></code> operator is used for \"reachability\" properties, <code><strong>G</strong></code> represents \"invariance\". The property <code><strong>G</strong> prop</code> is true of a path if <code>prop</code> remains true at all states along the path. Thus, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">10</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>states that, with probability at least 0.99, <code>z</code> never exceeds 10.\n</p>\n<div class='vspace'></div><h3>\"Weak until\" and \"release\" path properties</h3>\n<p>Like <code><strong>F</strong></code> and <code><strong>G</strong></code>, the operators <code><strong>W</strong></code> and <code><strong>R</strong></code> are derivable from other temporal operators.\n</p>\n<p class='vspace'>Weak until (<code>a <strong>W</strong> b</code>), which is equivalent to <code>(a <strong>U</strong> b) | <strong>G</strong> a</code>, requires that <code>a</code> remains true until <code>b</code> becomes true, but does not require that <code>b</code> ever does becomes true (i.e. <code>a</code> remains true forever). For example, a weak form of the until example used above is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.5</span> [ <span class=\"prismident\">z</span>&lt;<span class=\"prismnum\">2</span> <span class=\"prismkeyword\">U</span> <span class=\"prismident\">z</span>=<span class=\"prismnum\">2</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which states that, with probability greater than 0.5, either <code>z</code> is always less than 2, or it is less than 2 until the point where <code>z</code> is 2.\n</p>\n<p class='vspace'>Release (<code>a <strong>R</strong> b</code>),  which is equivalent to <code>!(!a U !b)</code>, informally means that <code>b</code> is true until <code>a</code> becomes true, or <code>b</code> is true forever.\n</p>\n<p class='vspace'><a name='bounded' id='bounded'></a>\n</p><h3>\"Bounded\" variants of path properties</h3>\n<p>All of the temporal operators given above, with the exception of <code><strong>X</strong></code>, have \"bounded\" variants, where an additional time bound is imposed on the property being satisfied.\nThe most common case is to use an upper time bound, i.e. of the form \"<code>&lt;=t</code>\" or \"<code>&lt;t</code>\", where <code>t</code> is a PRISM expression evaluating to a constant, non-negative value.\n</p>\n<p class='vspace'>For example, a bounded until property <code>prop1 <strong>U</strong>&lt;=t prop2</code>, is satisfied along a path if <code>prop2</code> becomes true within <code>t</code> steps and <code>prop1</code> is true in all states before that point.\nA typical example of this would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismident\">y</span>&lt;<span class=\"prismnum\">4</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which is true in a state if \"the probability of <code>y</code> first exceeding 3 within 7 time units is greater than or equal to 0.98\". Similarly:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state if \"the probability of <code>y</code> being equal to 4 within 7 time units is greater than or equal to 0.98\" and:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=<span class=\"prismnum\">7</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true if the probability of <code>y</code> staying equal to 4 for 7 time units is at least 0.98.\n</p>\n<p class='vspace'>The time bound can be an arbitrary (constant) expression,\nbut note that you may need to bracket it,\nas in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">G</span>&lt;=(<span class=\"prismnum\">2</span>*<span class=\"prismident\">k</span>+<span class=\"prismnum\">1</span>) <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use lower time-bounds (i.e. <code>&gt;=t</code> or <code>&gt;t</code>) and time intervals <code>[t1,t2]</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>&gt;=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n<span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.98</span> [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">20</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">4</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which refer to the probability of <code>y</code> becoming equal to 4 after 10 or more time units, and after between 10 and 20 time-units respectively.\n</p>\n<p class='vspace'>For CTMCs, the time bounds can be any (non-negative) numerical values - they are not restricted to integers, as for discrete-time models.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">0.25</span> [ <span class=\"prismident\">y</span>&lt;=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">U</span>&lt;=<span class=\"prismnum\">6.5</span> <span class=\"prismident\">y</span>&gt;<span class=\"prismnum\">1</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>means that the probability of <code>y</code> being greater than 1 within 6.5 time-units (and remaining less than or equal to 1 at all preceding time-points) is at least 0.25.\n</p>\n<div class='vspace'></div><h3>Transient probabilities</h3>\n<p>We can also use the bounded <code><strong>F</strong></code> operator to refer to a single time instant, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>[<span class=\"prismnum\">10</span>,<span class=\"prismnum\">10</span>] <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or, equivalently:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span>=<span class=\"prismnum\">10</span> <span class=\"prismident\">y</span>=<span class=\"prismnum\">6</span> ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>both of which give the probability of <code>y</code> being 6 at time instant 10.\n</p>\n<p class='vspace'><a name='ltl' id='ltl'></a>\n</p><h3>LTL-style path properties</h3>\n<p>PRISM also supports probabilistic model checking of the temporal logic LTL (and, in fact, PCTL*). LTL provides a richer set of path properties for use with the <code><strong>P</strong></code> operator, by permitting temporal operators to be combined. Here are a few examples of properties expressible using this functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;<span class=\"prismnum\">0.99</span> [ <span class=\"prismkeyword\">F</span> ( \"<span class=\"prismident\">request</span>\" &amp; (<span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">ack</span>\") ) ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"with probability greater than 0.99, a request is eventually received, followed immediately by an acknowledgement\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>&gt;=<span class=\"prismnum\">1</span> [ <span class=\"prismkeyword\">G</span> <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">send</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"a message is sent infinitely often with probability 1\"\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">G</span> (\"<span class=\"prismident\">error</span>\" &amp; !\"<span class=\"prismident\">repair</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>\"the probability of an error occurring that is never repaired\n</p>\n<p class='vspace'>Note that logical operators have precedence over temporal ones, so you will often need to include parentheses when using logical operators, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error1</span>\") &amp; (<span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">error2</span>\") ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For temporal operators, unary operators (such as <code><strong>F</strong></code>, <code><strong>G</strong></code> and <code><strong>X</strong></code>) have precedence over binary ones (such as <code><strong>U</strong></code>). Unary operators can be nested, without parentheses, but binary ones cannot.\n</p>\n<p class='vspace'>So, these are allowed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">a</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> <span class=\"prismkeyword\">X</span> \"<span class=\"prismident\">error</span>\" ]<br/>\n<span class=\"prismkeyword\">P</span>=? [ (\"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\") <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>but this is not:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ \"<span class=\"prismident\">a</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">b</span>\" <span class=\"prismkeyword\">U</span> \"<span class=\"prismident\">c</span>\" \"<span class=\"prismident\">error</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/ThePOperator?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/TheSOperator.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / The S Operator \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='TheSOperator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='TheSOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='TheSOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>The S Operator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The <code><strong>S</strong></code> operator is used to reason about the <em>steady-state</em> behaviour of a model,\ni.e. its behaviour in the <em>long-run</em> or <em>equilibrium</em>.\nPRISM currently only provides support for DTMCs and CTMCs.\nThe definition of steady-state (long-run) probabilities for finite DTMCS and CTMCs is well defined (see e.g. [<a class='wikilink' href='../Main/References.html#Ste94'>Ste94</a>]).\nInformally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">prop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/TheSOperator?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a DTMC or CTMC if\n\"starting from <em>s</em>, the steady-state (long-run) probability of being in a state which satisfies the (Boolean-valued) PRISM property <code>prop</code>, meets the bound <code>bound</code>\".\nA typical example of this type of property would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.05</span> [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/TheSOperator?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the long-run probability of the queue being more than 75% full is less than 0.05\".\n</p>\n<p class='vspace'>Like the <code><strong>P</strong></code> <a class='wikilink' href='ThePOperator.html'>operator</a>, the <code><strong>S</strong></code> operator can be used in a <em>quantitative</em> form, which returns the actual probability value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/TheSOperator?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and can be further customised with the use of <a class='wikilink' href='Filters.html'>filters</a>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='TheSOperator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='TheSOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='TheSOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='TheSOperator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:31 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='selflink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/TheSOperator@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / The S Operator | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='TheSOperator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='TheSOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='TheSOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>The S Operator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='TheSOperator@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='TheSOperator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='TheSOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='TheSOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='TheSOperator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:31 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='selflink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/TheSOperator@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / The S Operator | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='TheSOperator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='TheSOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='TheSOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>The S Operator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='TheSOperator@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='TheSOperator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='TheSOperator@action=edit.html'>Edit</a> - <a class='wikilink' href='TheSOperator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='TheSOperator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:31 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='selflink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/TheSOperator@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / TheSOperator </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>The S Operator</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>The <code><strong>S</strong></code> operator is used to reason about the <em>steady-state</em> behaviour of a model,\ni.e. its behaviour in the <em>long-run</em> or <em>equilibrium</em>.\nPRISM currently only provides support for DTMCs and CTMCs.\nThe definition of steady-state (long-run) probabilities for finite DTMCS and CTMCs is well defined (see e.g. [<a class='wikilink' href='../Main/References.html#Ste94'>Ste94</a>]).\nInformally, the property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span> <span class=\"prismident\">bound</span> [ <span class=\"prismident\">prop</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/TheSOperator?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is true in a state <em>s</em> of a DTMC or CTMC if\n\"starting from <em>s</em>, the steady-state (long-run) probability of being in a state which satisfies the (Boolean-valued) PRISM property <code>prop</code>, meets the bound <code>bound</code>\".\nA typical example of this type of property would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>&lt;<span class=\"prismnum\">0.05</span> [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/TheSOperator?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which means: \"the long-run probability of the queue being more than 75% full is less than 0.05\".\n</p>\n<p class='vspace'>Like the <code><strong>P</strong></code> <a class='wikilink' href='ThePOperator.html'>operator</a>, the <code><strong>S</strong></code> operator can be used in a <em>quantitative</em> form, which returns the actual probability value, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">S</span>=? [ <span class=\"prismident\">queue_size</span> / <span class=\"prismident\">max_size</span> &gt; <span class=\"prismnum\">0.75</span> ] <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/TheSOperator?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>and can be further customised with the use of <a class='wikilink' href='Filters.html'>filters</a>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/UncertainModels.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Uncertain Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='UncertainModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Uncertain Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>For uncertain models, currently interval MDPs (IMDPs) or interval DTMCs (IDTMCs), PRISM performs <em>robust</em> verification, which considers the best- or worst-case behaviour that can arise depending on the way that probabilities are selected from intervals.\n</p>\n<p class='vspace'>For example, instead of a property for a DTMC such as\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/UncertainModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which asks for the probability to reach a state satisfying <code>\"goal\"</code>, IDTMCs use MDP-style queries:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/UncertainModels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which compute the minimum or maximum possible probability that can arise.\n</p>\n<p class='vspace'>Similarly, for an IMDP, there are now two separate quantifications, firstly over strategies (policies) and secondly over the distinct ways that transition probabilities can be selected from intervals, for which <code>min</code> or <code>max</code> appear in that order in the query. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmaxmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmaxmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/UncertainModels?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>return the minimum and maximum values, respectively, over resolutions of transition probabilities for the maximum probability of reaching <code>\"goal\"</code>. Similarly, <code>minmin</code> and <code>minmax</code> are used for the minimum probability of reaching <code>\"goal\"</code>. Model checking is supported for:\n</p>\n<div class='vspace'></div><ul><li>the <code><strong>P</strong></code> operator, including single temporal operators and LTL formulae\n</li><li>the <code><strong>R</strong></code> operator, for the expected reward to reach a target or satisfy a co-safe LTL formula\n</li></ul><div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='UncertainModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 10:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='selflink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/UncertainModels@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Uncertain Models | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='UncertainModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Uncertain Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='UncertainModels@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='UncertainModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 10:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='selflink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/UncertainModels@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Property Specification / Uncertain Models | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='UncertainModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Uncertain Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='UncertainModels@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='UncertainModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 10:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Property Specification</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='IdentifyingASetOfStates.html'>Identifying A Set Of States</a>\n</li><li><a class='wikilink' href='ThePOperator.html'>The P Operator</a>\n</li><li><a class='wikilink' href='TheSOperator.html'>The S Operator</a>\n</li><li><a class='wikilink' href='Reward-basedProperties.html'>Reward-based Properties</a>\n</li><li><a class='wikilink' href='Multi-objectiveProperties.html'>Multi-objective Properties</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='selflink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='Non-probabilisticProperties.html'>Non-probabilistic Properties</a>\n</li><li><a class='wikilink' href='SyntaxAndSemantics.html'>Syntax And Semantics</a>\n</li><li><a class='wikilink' href='Filters.html'>Filters</a>\n</li><li><a class='wikilink' href='PropertiesFiles.html'>Properties Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/PropertySpecification/UncertainModels@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | PropertySpecification / UncertainModels </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Property Specification</a> /\n</p><h1>Uncertain Models</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>For uncertain models, currently interval MDPs (IMDPs) or interval DTMCs (IDTMCs), PRISM performs <em>robust</em> verification, which considers the best- or worst-case behaviour that can arise depending on the way that probabilities are selected from intervals.\n</p>\n<p class='vspace'>For example, instead of a property for a DTMC such as\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">P</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/UncertainModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which asks for the probability to reach a state satisfying <code>\"goal\"</code>, IDTMCs use MDP-style queries:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/UncertainModels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which compute the minimum or maximum possible probability that can arise.\n</p>\n<p class='vspace'>Similarly, for an IMDP, there are now two separate quantifications, firstly over strategies (policies) and secondly over the distinct ways that transition probabilities can be selected from intervals, for which <code>min</code> or <code>max</code> appear in that order in the query. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmaxmin</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n<span class=\"prismkeyword\">Pmaxmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/PropertySpecification/UncertainModels?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>return the minimum and maximum values, respectively, over resolutions of transition probabilities for the maximum probability of reaching <code>\"goal\"</code>. Similarly, <code>minmin</code> and <code>minmax</code> are used for the minimum probability of reaching <code>\"goal\"</code>. Model checking is supported for:\n</p>\n<div class='vspace'></div><ul><li>the <code><strong>P</strong></code> operator, including single temporal operators and LTL formulae\n</li><li>the <code><strong>R</strong></code> operator, for the expected reward to reach a target or satisfy a co-safe LTL formula\n</li></ul><div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/AllOnOnePage.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / All On One Page \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for xml\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.xml .de1, .xml .de2 {font-family: monospace; font-weight: normal;}\n.xml  {font-family:monospace;}\n.xml .imp {font-weight: bold; color: red;}\n.xml li, .xml .li1 {font-family: monospace; color: black; font-weight: normal;}\n.xml .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.xml .li2 {font-weight: bold;}\n.xml .es0 {color: #000099; font-weight: bold;}\n.xml .br0 {color: #66cc66;}\n.xml .sy0 {color: #66cc66;}\n.xml .st0 {color: #ff0000;}\n.xml .nu0 {color: #cc66cc;}\n.xml .sc-1 {color: #808080; font-style: italic;}\n.xml .sc0 {color: #00bbdd;}\n.xml .sc1 {color: #ddbb00;}\n.xml .sc2 {color: #339933;}\n.xml .sc3 {color: #009900;}\n.xml .re0 {color: #000066;}\n.xml .re1 {color: #000000; font-weight: bold;}\n.xml .re2 {color: #000000; font-weight: bold;}\n.xml .ln-xtra, .xml li.ln-xtra, .xml div.ln-xtra {background-color: #ffc;}\n.xml span.xtra { display:block; }\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Running PRISM</span></h1>\n<hr />\n<h1>Starting PRISM</h1>\n<p>There are two versions of PRISM, one based on a graphical user interface (GUI),\nthe other based on a command line interface. Both use the same underlying model checker.\nThe latter is useful for running large batches of jobs, leaving long-running model checking tasks in the background, or simply for running the tool quickly and easily once you are familiar with its operation. \n</p>\n<p class='vspace'>Details how how to run PRISM can be found in the <a class='wikilink' href='../InstallingPRISM/Main.html'>installation instructions</a>.\nIn short, to run the PRISM GUI:\n</p>\n<div class='vspace'></div><ul><li>(on Windows) click the short-cut (to <code>xprism.bat</code>) installed on the Desktop/Start Menu\n</li><li>(on other OSs) run the <code>xprism</code> script in the <code>bin</code> directory\n</li></ul><p class='vspace'>You can also optionally specify a model file and a properties file to load upon starting the GUI, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xprism example.prism</span><br/>\n<span style=\"font-weight:bold;\">xprism example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To use the command-line version of PRISM, run the <code>prism</code> script, also in the <code>bin</code> directory, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism example.prism example.props -prop 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-dir</code> switch can be used to specify a directory for input (and output) files.\nSo the following are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism ~/myfiles/example.prism ~/myfiles/example.props</span><br/>\n<span style=\"font-weight:bold;\">prism -dir ~/myfiles example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The remainder of this section of the manual describes the main types of functionality offered by PRISM.\nFor a more introductory guide to using the tool, try the\n<a class='urllink' href='http://www.prismmodelchecker.org/tutorial/'>tutorial</a> on the PRISM web site.\nSome screenshots of the GUI version of PRISM are shown below.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui1.gif'><img width='500' src='../uploads/gui1.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (editing a model)</strong></span></div>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui2.gif'><img width='500' src='../uploads/gui2.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (model checking)</strong></span></div>\n<div class='vspace'></div><hr />\n<h1>Loading And Building a Model</h1>\n<p>Typically, when using PRISM, the first step is to load a model that has been specified in the PRISM modelling language. If using the GUI, select menu option \"Model | Open Model\" and choose a file. There are a selection of sample PRISM model files in the <code>prism-examples</code> directory of the distribution.\nA few very small models are contained in the subdirectory <code>simple</code>;\nthe rest are in subdirectories grouped by model type.\n</p>\n<p class='vspace'>The model will then be displayed in the editor in the \"Model\" tab of the GUI window. The file is parsed upon loading. If there are no errors, information about the modules, variables, and other components of the model is displayed in the panel to the left and a green tick will be visible. If there are errors in the file, a red cross will appear instead and the errors will be highlighted in the model editor. To view details of the error, position the mouse pointer over the source of the error (or over the red cross). Alternatively, select menu option \"Model | Parse Model\" and the error mIessage will be displayed in a message box. Model descriptions can, of course, also be typed from scratch into the GUI's editor.\n</p>\n<div class='vspace'></div><h3>Building the model</h3>\n<p>In order to perform model checking, PRISM will (in most cases) need to construct the corresponding probabilistic model, i.e. convert the PRISM model description to, for example, an MDP, DTMC, etc. During this process, PRISM computes the set of states in the model which are reachable from the initial states and the transition matrix which represents the model.\n</p>\n<p class='vspace'>Model construction is done automatically when you perform <a class='wikilink' href='ModelChecking.html'>model checking</a>. However, you may always want to explicitly ask PRISM to build the model in order to test for errors or to see how large the model is. From the GUI, you can do this by by selecting \"Model | Build Model\". If there are no errors during model construction, the number of states and transitions in the model will be displayed in the bottom left corner of the window.\n</p>\n<p class='vspace'>From the command-line, simply type:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.nm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>model.nm</code> is the name of the file containing the model description.\n</p>\n<p class='vspace'>For some types of models, notably PTAs, models are not constructed in this way (because the models are infinite-state). In these cases, analysis of the model is not performed until model checking is performed.\n</p>\n<p class='vspace'><a name='deadlocks' id='deadlocks'></a>\n</p><h3>Deadlocks</h3>\n<p>You should be aware of the possibility of <em>deadlock states</em> (or <em>deadlocks</em>) in the model,\ni.e. states which are reachable but from which there are no outgoing transitions.\nPRISM will automatically search your model for deadlocks and, by default,\n\"fix\" them by adding self-loops in these states.\nSince deadlocks are sometimes caused by modelling errors,\nPRISM will display a warning message in the log when deadlocks are fixed in this way.\n</p>\n<p class='vspace'>You can control whether deadlocks are automatically fixed in this way using the \"Automatically fix deadlocks\" option (or with command-line switches <code>-nofixdl</code> and <code>-fixdl</code>). When fixing is disabled, PRISM will report and error when the model contains deadlocks (this used to be the default behaviour in older versions of PRISM).\n</p>\n<p class='vspace'>If you have unwanted or unexpected deadlocks in your model, there are several ways you can detect then. Firstly, by disabling deadlock fixing (as described above), PRISM will display a list of deadlock states in the log. Alternatively, you can model check the <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> property <code>filter(print, \"deadlock\")</code>, which has the safe effect.\n</p>\n<p class='vspace'>To find out <em>how</em> deadlocks occur, i.e. which paths through the model lead to a deadlock state, there are several possibilities. Firstly, you can model check the <a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>CTL</a> property <code>E[F \"deadlock\"]</code>. When checked from the GUI, this will provide you with the option of display a path to a deadlock in the simulator. From the command-line, for example with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -pf 'E[F \"deadlock\"]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>a path to a deadlock will be displayed in the log.\n</p>\n<p class='vspace'>Finally, in the eventuality that the model is too large to be model checked, you can still use the <a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>simulator</a> to search for deadlocks. This can be done either by manually generating random paths using the <a class='wikilink' href='DebuggingModelsWithTheSimulator.html#gui'>simulator in the GUI</a> or, <a class='wikilink' href='DebuggingModelsWithTheSimulator.html#cl'>from the command-line</a>, e.g. by running:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath deadlock stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Debugging Models With The Simulator</h1>\n<p>PRISM includes a <em>simulator</em>, a tool which can be used to generate sample paths (executions) through a PRISM model. From the GUI, the simulator allows you to explore a model by interactively generating such paths. This is particularly useful for debugging models during development and for running sanity checks on completed models. Paths can also be generated from the command-line.\n</p>\n<p class='vspace'><a name='gui' id='gui'></a>\n</p><h3>Generating a path in the GUI</h3>\n<p>Once you have loaded a model into the PRISM GUI\n(note that it is not necessary to build the model),\nselect the \"Simulator\" tab at the bottom of the main window.\nYou can now start a new path by double-clicking in the bottom half of the window\n(or right-clicking and selecting \"New path\").\nIf there are undefined constants in the\nmodel (or in any currently loaded properties files) you will be prompted to give values for these. You\ncan also specify the state from which you wish to generate a path. By default, this is the initial state of\nthe model.\n</p>\n<p class='vspace'>The main portion of the user interface (the bottom part) displays a path through the currently loaded model. Initially, this will comprise just a single state. The table above shows the list of available transitions from this state. Double-click one of these to extend the path with this transition. The process can be repeated to extend the path in an interactive fashion. Clicking on any state in the current path shows the transition which was taken at this stage. Click on the final state in the path to continue\nextending the path. Alternatively, clicking the \"Simulate\" button will select a transition randomly (according to the probabilities/rates of the available transitions). By changing the number in the box below this button, you can easily generate random paths of a given length with a single click.\nThere are also options (in the accompanying drop-down menu) to allow generation of paths up until a particular length or, for CTMCs, in terms of the time taken.\n</p>\n<p class='vspace'>The figure shows the simulator in action.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui-sim.png'><img width='500' src='../uploads/gui-sim.png' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI: exploring a model using the simulator</strong></span></div>\n<p class='vspace'>It is also possible to:\n</p>\n<div class='vspace'></div><ul><li>backtrack to an earlier point in a path\n</li><li>remove all of the states before some point in a path\n</li><li>restart a path from its first state\n</li><li>export a path to a text file\n</li></ul><p class='vspace'>Notice that the table containing the path displays not just the value of each variable in each\nstate but also the time spent in that state and any rewards accumulated there. You can configure exactly which columns appear by right-clicking on the path and selecting \"Configure view\". For rewards (and for CTMC models, for the time-values), you can can opt to display the reward/time for each individual state and/or the cumulative total up until each point in the path.\n</p>\n<p class='vspace'>At the top-right of the interface, any labels contained in the currently loaded model/properties file are displayed, along with their value in the currently selected state of the path. In addition, the built-in <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>labels</a> <code>\"init\"</code> and <code>\"deadlock\"</code> are also included. Selecting a label from the list highlights all states in the current path which satisfy it.\n</p>\n<p class='vspace'>The other tabs in this panel allow the value of path operators (taken from properties in the current file) to be viewed for the current path, as well as various other statistics.\n</p>\n<p class='vspace'>Another very useful feature for some models is to use the \"Plot new path\" option from the simulator, which generates a plot of some/all of the variable/reward values for a particular randomly generated path through the model.\n</p>\n<p class='vspace'><a name='cl' id='cl'></a>\n</p><h3>Path generation from the command-line</h3>\n<p>It is also possible to generate random paths through a model using the command-line version of PRISM. This is achieved using the <code>-simpath</code> switch, which requires two arguments, the first describing the path to be generated and the second specifying the file to which the path should be output (as usual, specifying <code>stdout</code> sends output to the terminal). The following examples illustrate the various ways of generating paths in this way:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -simpath 10 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath time=7.5 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath deadlock path.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These generate a path of 10 steps, a path of at least 7.5 time units and a path ending in deadlock, respectively.\n</p>\n<p class='vspace'>Here's an example of the output:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 1 0.007479539729154247 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 2 0.00782819795294666 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 3 0.01570585559933703 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 4 0.017061111948220263 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 5 0.026816317516034468 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 6 0.039878416276337814 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 7 0.04456566315999103 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 8 0.047368359683643765 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 9 0.04934857366557349 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 10 0.055031679365844674 1 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This shows the sequence of states in the path, i.e. the values of the variables in each state. In the example above, there are 4 variables: <code>s</code>, <code>a</code>, <code>s1</code> and <code>s2</code>.\nThe first three columns show the type of transition taken to reach that state, its index within the path (starting from 0) and the time at which it was entered. The latter is only shown for continuous time models. The type of the transition is written as <em>[act]</em> if action label <code>act</code> was taken, and as <em>module1</em> if the module named <code>module1</code> takes an unlabelled transition). \n</p>\n<p class='vspace'>Further options can also be appended to the first parameter. For example, option <code>probs=true</code> also displays the probability/rate associated with each transition. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '5,probs=true' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 1 0.0011880118081395378 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 2 0.0037798355025401888 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 3 0.01029212322894221 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 4 0.023258883912578403 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 5 0.027402404026254504 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this example, the rate is 200.0 for all transitions.\nTo show the state/transition rewards for each step, use option <code>rewards=true</code>.\n</p>\n<p class='vspace'>If you are only interested in values of certain variables of your model, use the <code>vars=(...)</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '500,probs=true,vars=(a,s1,s2)' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 110 0.5025332771499665 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 111 0.5109407735244359 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 112 0.9960642154887506 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station1 0.5 130 1.0645858553472822 0 1 0</span><br/>\n<span style=\"font-style:italic;\">[loop1b] 200.0 132 1.0732572896618477 1 1 0</span><br/>\n<span style=\"font-style:italic;\">[serve1] 1.0 133 2.939742026148121 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 225 3.4311507854807677 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 227 3.434285492243098 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 228 3.553118276800078 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 250 3.6354431222941406 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 251 3.637552738997181 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 252 3.7343375346150576 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of single quotes around the path description argument to prevent the shell from misinterpreting special characters such as \"<code>(</code>\".\n</p>\n<p class='vspace'>Notice also that the above only displays states in which the values of some variable of interest changes. This is achieved with the option <code>changes=true</code>, which is automatically enabled when you use <code>vars=(...)</code>. If you want to see all steps of the path, add the option <code>changes=false</code>.\n</p>\n<p class='vspace'>An alternative way of viewing paths is to only display paths at certain fixed points in time. This is achieved with the <code>snapshot=x</code> option, where <code>x</code> is the time step. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 'time=5.0,snapshot=0.5' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">94 0.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">198 1.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">314 1.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">375 2.0 1 1 1 1</span><br/>\n<span style=\"font-style:italic;\">376 2.5 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">376 3.0 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">378 3.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">378 4.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">478 4.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">511 5.0 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use the <code>sep=...</code> option to specify the column separator. Possible values are <code>space</code> (the default), <code>tab</code> and <code>comma</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '10,vars=(a,b),sep=comma' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step,a,b,time</span><br/>\n<span style=\"font-style:italic;\">0,0,0,0.0</span><br/>\n<span style=\"font-style:italic;\">2,1,0,0.058443536856580006</span><br/>\n<span style=\"font-style:italic;\">3,1,1,0.09281024515535738</span><br/>\n<span style=\"font-style:italic;\">6,1,2,0.2556555786269585</span><br/>\n<span style=\"font-style:italic;\">7,1,3,0.284062896359802</span><br/>\n<span style=\"font-style:italic;\">8,1,4,1.1792064236954896</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When generating paths to a deadlock state, additional <code>repeat=...</code> option is available which will construct multiple paths until a deadlock is found. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath 'deadlock,repeat=100' stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, the simulator detects deterministic loops in paths (e.g. if a path reaches a state from which there is a just a single self-loop leaving that state) and stops generating the path any further. You can disable this behaviour with the <code>loopcheck=false</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">Warning: Deterministic loop detected after 6 steps (use loopcheck=false option to extend path).</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 3</span><br/>\n<span style=\"font-style:italic;\">die 4 7 3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10,loopcheck=false stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 2</span><br/>\n<span style=\"font-style:italic;\">die 4 7 2</span><br/>\n<span style=\"font-style:italic;\">die 5 7 2</span><br/>\n<span style=\"font-style:italic;\">die 6 7 2</span><br/>\n<span style=\"font-style:italic;\">die 7 7 2</span><br/>\n<span style=\"font-style:italic;\">die 8 7 2</span><br/>\n<span style=\"font-style:italic;\">die 9 7 2</span><br/>\n<span style=\"font-style:italic;\">die 10 7 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>One final note: the <code>-simpath</code> switch only generates paths up to the maximum path length setting of the simulator (the default is 10,000). If you want to generate longer paths, either change the\n<a class='wikilink' href='../ConfiguringPRISM/Main.html'>default setting</a> or override it temporarily from the command-line using the <code>-simpathlen</code> switch.\nYou might also use the latter to decrease the setting,\ne.g. to look for a path leading to a deadlock state,\nbut only within 100 steps:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath deadlock stdout -simpathlen 100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Exporting The Model</h1>\n<p>If required, once the model has been constructed, it can be exported, either for manual examination or for use in another tool. The following can all be exported:\n</p>\n<div class='vspace'></div><ul><li>the <strong>transition matrix</strong> (or function);\n</li><li>the <strong>rewards</strong> (state/transition) rewards;\n</li><li>the <strong>labels</strong> (in the <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>model</a> or <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>properties</a>) and the states that satisfy them\n</li><li>the definition of (reachable) <strong>states</strong>, i.e., their variable values\n</li><li>the definition of <strong>observations</strong>, i.e., their observable values, for partially observable models\n</li></ul><p class='vspace'>From the command-line version of PRISM, the most convenient and flexible approach is to use the <code>-exportmodel</code> switch.\nThis will, by default, use the extension of the filename(s) to determine the format.\n</p>\n<p class='vspace'>From the GUI, use the \"Model | Export\" menu to export the data to a file or, for small models, use the \"Model | View\" menu to print the details directly to the log. For the case of labels, if you want to export labels from the properties file too, use the \"Properties | Export labels\" option, rather than the \"Model | Export\" one.\n</p>\n<p class='vspace'>The main formats for model export are:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \".tra\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li><li><a class='urllink' href='https://www.graphviz.org/'>Dot</a> format, for a graphical view of the model\n</li></ul><p class='vspace'><a name='explicit' id='explicit'></a>\n</p><h3>Plain text (explicit files)</h3>\n<p>This format exports different parts of the model in different file, with the expected filename extensions being:\n</p>\n<div class='vspace'></div><ul><li><code>.tra</code> - transition matrix\n</li><li><code>.srew</code>, <code>.trew</code>, <code>.rew</code> - rewards: states, transitions or both\n</li><li><code>.lab</code> - labels\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>To export just the transition matrix in this format, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To export multiple parts, use, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you omit the file basename of the export files and the basename of the model will be used, so this is equivalent to the above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel .tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can use the shorthand <code>.all</code> to export everything, and <code>.rew</code> to export both state and transition rewards. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can always use <code>stdout</code> instead of a filename. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is a quick way to print all details (of a small model) to the terminal.\n</p>\n<p class='vspace'>The labels (<code>.lab</code>) export includes the built-in labels <code>\"init\"</code> and <code>\"deadlock\"</code>,\nproviding a way to export information about initial states and (fixed) deadlock states.\n</p>\n<p class='vspace'>When there are multiple reward structures, a separate file is created for each one and a (1-indexed) suffix is added to distinguish them.\nBy default, a header in each file (see the \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html#srew'>Explicit Model Files</a>\" appendix) also shows the name of the reward structure.\nThis can be omitted - see the options below - or via the option \"Include headers in model exports\" in the GUI.\n</p>\n<p class='vspace'><a name='umb' id='umb'></a>\n</p><h3>UMB (Unified Markov binary) format</h3>\n<p>UMB is a binary format that can incorporate all parts of the model listed above.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, everything is included. You can omit some parts with the <code>-exportmodel</code>\noptions <code>rewards</code>, <code>labels</code>, <code>states</code> and <code>obs</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb:states=false,rewards=false</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For a small model, you can also see a textual version of the UMB format\nusing file extension <code>.umbt</code> (or option <code>text</code>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock24'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.umbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=24' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also configure the compression used: <code>zip=false</code> turns it off,\n<code>zip=gzip</code> uses gzip and <code>zip=xz</code> uses xz (smaller but slower to read/write).\n</p>\n<p class='vspace'><a name='other' id='other'></a>\n</p><h3>Other formats and options</h3>\n<p>If the file extension is not recognised, PRISM defaults to plain text (explicit) format.\nYou can always override this using the @format@ option, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock25'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=umb,text</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=25' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can perform multiple model exports using several instances of <code>-exportmodel</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock26'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit -exportmodel model.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=26' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Other file formats are also available:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://www.mathworks.com/'>Matlab</a> code (extension <code>.m</code>) or <code>format=matlab</code>\n</li><li>Storm's DRN model format (extension <code>.drn</code>) or <code>format=drn</code>\n</li></ul><p class='vspace'>Other <code>-exportmodel</code> options are:\n</p>\n<div class='vspace'></div><ul><li><code>actions</code> (=<code>true</code>/<code>false</code>) - whether to  actions on choices/transitions\n</li><li><code>precision</code> (=<code>&lt;n&gt;</code>) - use <code>&lt;n&gt;</code> significant figures for floating point values (in text)\n</li><li><code>headers</code> (<code>=true/false</code>) - whether to include headers when exporting rewards\n</li><li><code>rows</code> - export matrices with one row/distribution on each line (plain text)\n</li><li><code>proplabels</code> - also export labels from a properties file into a <code>.lab</code> file\n</li></ul><p class='vspace'>For plain text export, although <code>-exportmodel</code> is now usually the best switch to use,\nother older switches still exist. For example, you can export individual files using\n<code>-exporttrans &lt;file&gt;</code>,\n<code>-exportstates &lt;file&gt;</code>,\n<code>-exportstaterewards &lt;file&gt;</code>,\n<code>-exporttransrewards &lt;file&gt;</code>,\n<code>-exportrewards &lt;file&gt; &lt;file&gt;</code>,\n<code>-exportlabels &lt;file&gt;</code>, and\n<code>-exportproplabels &lt;file&gt;</code>.\nAnd you can use switches\n<code>-exportmodelprecision &lt;x&gt;</code>,\n<code>-exportmatlab</code> and\n<code>-exportrows</code>\nto specify format options affecting all of them.\n</p>\n<p class='vspace'><a name='scc' id='scc'></a>\n</p><h3>Exporting (B)SCCs and end components</h3>\n<p>It is also possible to export the set of (bottom) strongly connected components (SCCs or BSCCs) for a model. This can only be done from the command-line currently. Use, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock27'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportsccs stdout</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportbsccs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=27' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For an MDP, you can also export the set of maximal end components (MECs):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock28'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -exportmecs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=28' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<h1>Model Checking</h1>\n<p>Typically, once a model has been constructed, it is analysed through model checking.\nProperties are specified as described in the \"<a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\" section,\nand are usually kept in files with extensions <code>.props</code>, <code>.pctl</code> or <code>.csl</code>.\nThere are properties files accompanying most of the sample PRISM models in the <code>prism-examples</code> directory.\n</p>\n<p class='vspace'>\n</p><h3>GUI</h3>\n<p>To load a file containing properties into the GUI, select menu option \"Properties | Open properties list\".\nThe file can only be loaded if there are no errors, otherwise an error is displayed.\nNote that it may be necessary to have loaded the corresponding model first,\nsince the properties will probably make reference to variables (and perhaps constants) declared in the model file.\nOnce loaded, the properties contained in the file are displayed in a list in the \"Properties\" tab of the GUI.\nConstants and labels are displayed in separate lists below.\nYou can modify or create new properties, constants and labels from the GUI,\nby right-clicking on the appropriate list and selecting from the pop-up menu which appears. Properties with errors are shaded red and marked with a warning sign.\nPositioning the mouse pointer over the property displays the corresponding error message.\n</p>\n<p class='vspace'>The pop-up menu for the properties list also contains a \"Verify\" option,\nwhich allows you instruct PRISM to model check the currently selected properties\n(hold down Ctrl/Cmd to select more than one property simultaneously).\nAll properties can be model checked at once by selecting \"Verify all\".\nPRISM verifies each property individually.\nUpon completion, the icon next to the property changes according to the result of model checking. For Boolean-valued properties, a result of true or false is indicated by a green tick or red cross, respectively. For properties which have a numerical result (e.g. <code>P=? [ ...]</code>), position the mouse pointer over the property to view the result.\nIn addition, this and further information about model checking is displayed in the log in the \"Log\" tab.\n</p>\n<p class='vspace'>\n</p><h3>Command-line</h3>\n<p>From the command-line, model checking is achieved by passing both a model file and a properties file as arguments, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock29'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=29' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The results of model checking are sent to the display and are as described above for the GUI version.\nBy default, all properties in the file are checked.\nTo model check only a single property, use the <code>-prop</code> switch.\nFor example, to check only the fourth property in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock30'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=30' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or to check only the property with <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#names'>name</a> \"safe\" in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock31'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=31' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also provide a comma-separated list of multiple properties to check,\nusing neither numerical indices or property names:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock32'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4,5,safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=32' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, the contents of a properties file can be specified directly from the command-line, using the <code>-pf</code> switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock33'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -pf 'P&gt;=0.5 [ true U&lt;=5 (s=1 &amp; a=0) ]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=33' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The switches <code>-pctl</code> and <code>-csl</code> are aliases for <code>-pf</code>.\n</p>\n<p class='vspace'>Note the use of single quotes (<code>'...'</code>) to avoid characters such as\n<code>(</code> and <code>&gt;</code> being interpreted by the command-line shell.\nSingle quotes are preferable to double quotes since PRISM properties often include double quotes, e.g. for references to labels or properties.\n</p><hr />\n<h1>Approximate Model Checking</h1>\n<p>The discrete-event simulator built into PRISM (see the section \"<a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\") can also be used to generate <em>approximate</em> results for PRISM properties, a technique often called <em>statistical model checking</em>. Essentially, this is achieved by <em>sampling</em>: generating a large number of random paths through the model, evaluating the result of the given properties on each run, and using this information to generate an approximately correct result. This approach is particularly useful on very large models when normal model checking is infeasible. This is because discrete-event simulation is performed using the PRISM language model description, without explicitly constructing the corresponding probabilistic model.\n</p>\n<p class='vspace'>Currently, statistical model checking can only be applied to <code><strong>P</strong></code> or <code><strong>R</strong></code> operators\nand does not support LTL-style path properties or <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\nThere are also a few restrictions on the modelling language features that can be used; see below for details.\n</p>\n<p class='vspace'>To use this functionality, load a model and some properties into PRISM, as described in the previous sections. To generate an approximate value for one or more properties, select them in the list, right-click and select \"Simulate\" (as opposed to \"Verify\"). As usual, it is first necessary to provide values for any undefined constants. Subsequently, a dialog appears. Here, the state from which approximate values are to be computed (i.e. from which the paths will be generated) can be selected. By default, this is the initial state of the model. The other settings in the dialog concern the methods used for simulation.\n</p>\n<p class='vspace'>PRISM supports four different methods for performing statistical model checking:\n</p>\n<div class='vspace'></div><ul><li>CI (Confidence Interval)\n</li><li>ACI (Asymptotic Confidence Interval)\n</li><li>APMC (Approximate Probabilistic Model Checking)\n</li><li>SPRT (Sequential Probability Ratio Test)\n</li></ul><p class='vspace'>The first three of these are intended primarily for \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>quantitative</a>\" properties (e.g. of the form <code><strong>P</strong>=?[...]</code>), but can also be used for \"bounded\" properties (e.g. of the form <code><strong>P</strong>&lt;p[...]</code>). The SPRT method is only applicable to \"bounded\" properties.\n</p>\n<p class='vspace'>Each method has several parameters that control its execution, i.e. the number of samples that are generated and the accuracy of the computed approximation. In most cases, these parameters are inter-related so one of them must be left unspecified and its value computed automatically based on the others. In some cases, this is done before simulation; in others, it must be done afterwards.\n</p>\n<p class='vspace'>Below, we describe each method in more detail.\nFor simplicity, we describe the case of checking a <code><strong>P</strong></code> operator.\nDetails for the case of an <code><strong>R</strong></code> operator can be found in [<a class='wikilink' href='../Main/References.html#Nim10'>Nim10</a>].\n</p>\n<div class='vspace'></div><h3>CI (Confidence Interval) Method</h3>\n<p>The CI method gives a <em>confidence interval</em> for the approximate value generated for a <code><strong>P</strong>=?</code> property, based on a given <em>confidence level</em> and the number of samples generated.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Width\" (<em>w</em>)\n</li><li>\"Confidence\" (<em>alpha</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Let <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated.\nThe confidence interval is [<em>Y-w</em>,<em>Y+w</em>], i.e. <em>w</em> gives the half-width of the interval.\nThe confidence level, which is usually stated as a percentage, is 100(1-<em>alpha</em>)%.\nThis means that the actual value <em>X</em> should fall into the confidence interval [<em>Y-w</em>,<em>Y+w</em>] 100(1-<em>alpha</em>)% of the time.\n</p>\n<p class='vspace'>To determine, for example, the width <em>w</em> for given <em>alpha</em> and <em>N</em>,\nwe use <em>w</em> = <em>q</em> * sqrt(<em>v</em> / <em>N</em>) where\n<em>q</em> is a quantile, for probability 1-<em>alpha</em>/2, from the Student's t-distribution with <em>N</em>-1 degrees of freedom and <em>v</em> is (an estimation of) the variance for <em>X</em>.\nSimilarly, we can determine the required number of iterations, from <em>w</em> and <em>alpha</em>,\nas N = (<em>v</em> * <em>q</em><sup>2</sup>)/<em>w</em><sup>2</sup>, where <em>q</em> and <em>v</em> are as before.\n</p>\n<p class='vspace'>For a bounded property  <code><strong>P</strong>~p[...]</code>, the (Boolean) result is determined according to the generated approximation for the probability. This is not the case, however, if the threshold <em>p</em> falls within the confidence interval [<em>Y-w</em>,<em>Y+w</em>], in which case no value is returned.\n</p>\n<div class='vspace'></div><h3>ACI (Asymptotic Confidence Interval) Method</h3>\n<p>The ACI method works in exactly same fashion as the CI method, except that it uses the Normal distribution to approximate the Student's t-distribution when determining the confidence interval. This is appropriate when the number of samples is large (because we can get a reliable estimation of the variance from the samples) but may be less accurate for small numbers of samples.\n</p>\n<div class='vspace'></div><h3>APMC (Approximate Probabilistic Model Checking) Method</h3>\n<p>The APMC method, based on [<a class='wikilink' href='../Main/References.html#HLMP04'>HLMP04</a>], offers a probabilistic guarantee on the accuracy of the  approximate value generated for a <code><strong>P</strong>=?</code> property, based on the Chernoff-Hoeffding bound.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Approximation\" (<em>epsilon</em>)\n</li><li>\"Confidence\" (<em>delta</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Letting <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated, we have:\n</p>\n<div class='vspace'></div><ul><li>Prob(|<em>Y</em>-<em>X</em>| &gt; <em>epsilon</em>) &lt; <em>delta</em>\n</li></ul><p class='vspace'>where the parameters are related as follows:\n<em>N</em> = ln(2/<em>delta</em>) / 2<em>epsilon</em><sup>2</sup>.\nThis imposes certain restrictions on the parameters,\nnamely that <em>N</em>(<em>epsilon</em><sup>2</sup>) &#8805; ln(2/delta)/2.\n</p>\n<p class='vspace'>In similar fashion to the CI/ACI methods, the APMC method can be also be used for bounded properties such as <code><strong>P</strong>~p[...]</code>, as long as the threshold <em>p</em> falls outside the interval [<em>Y-epsilon</em>,<em>Y+epsilon</em>].\n</p>\n<div class='vspace'></div><h3>SPRT (Sequential Probability Ratio Test) Method</h3>\n<p>The SPRT method is specifically for bounded properties, such as <code><strong>P</strong>~p[...]</code> and is based on <em>acceptance sampling</em> techniques [<a class='wikilink' href='../Main/References.html#YS02'>YS02</a>]. It uses Wald's sequential probability ratio test (SPRT), which generates a succession of samples, deciding on-the-fly when an answer can be given with a sufficiently high confidence.\n</p>\n<p class='vspace'>The parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Indifference\" (<em>delta</em>)\n</li><li>\"Type I/II error\" (<em>alpha</em>/<em>beta</em>)\n</li></ul><p class='vspace'>Consider a property of the form <code><strong>P</strong>&#8805;p[...]</code>. The parameter <em>delta</em> is used as the half-width of an <em>indifference region</em> [p-delta,p+delta]. PRISM will attempt to determine whether either the hypothesis <code><strong>P</strong>&#8805;(p+delta)[...]</code> or <code><strong>P</strong>&#8804;(p-delta)[...]</code> is true, based on which it will return either <code>true</code> or <code>false</code>, respectively. The parameters <em>alpha</em> and <em>beta</em> represent the probability of the occurrence of a <em>type I error</em> (wrongly accepting the first hypothesis) and a <em>type II error</em> (wrongly accepting the second hypothesis), respectively. For simplicity, PRISM assigns the same value to both <em>alpha</em> and <em>beta</em>.\n</p>\n<div class='vspace'></div><h3>Maximum Path Length</h3>\n<p>Another setting that can be configured from the \"Simulation Parameters\" dialog is the maximum length of paths generated by PRISM during statistical model checking. In order to perform statistical model checking, PRISM needs to evaluate the property being checked along every generated path. For example, when checking <code>P=? [ F&lt;=10 \"end\" ]</code>, PRISM must check whether <code>F&lt;=10 \"end\"</code> is true for each path. On this example (assuming a discrete-time model), this can always be done within the first 10 steps. For a property such as <code>P=? [ F \"end\" ]</code>, however, there may be paths along which no finite fragment can show <code>F \"end\"</code> to be true or false. So, PRISM imposes a maximum path length to avoid the need to generate excessively long (or infinite) paths.\nThe default maximum length is 10,000 steps.\nIf, for a given property, statistical model checking results in one or more paths on which the property cannot be evaluated, an error is reported.\n</p>\n<div class='vspace'></div><h3>Command-line Statistical Model Checking</h3>\n<p>Statistical model checking can also be enabled from the command-line version of PRISM, by including the <code>-sim</code> switch. The default methods used are CI (Confidence Interval) for \"quantitative\" properties and SPRT (Sequential Probability Ratio Test) for \"bounded\" properties. To select a particular method, use switch <code>-simmethod &lt;method&gt;</code> where <code>&lt;method&gt;</code> is one of <code>ci</code>, <code>aci</code>, <code>apmc</code> and <code>sprt</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock34'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.pctl -prop 1 -sim -simmethod aci</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=34' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM has default values for the various simulation method parameters, but these can also be specified using the switches <code>-simsamples</code>, <code>-simconf</code>, <code>-simwidth</code> and <code>-simapprox</code>. The exact meaning of these switches for each simulation method is given in the table below.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><strong>CI</strong></td><td  align='center'><strong>ACI</strong></td><td  align='center'><strong>APMC</strong></td><td  align='right'><strong>SPRT</strong></td></tr>\n<tr ><td  align='center'><code>-simsamples</code></td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='right'>n/a</td></tr>\n<tr ><td  align='center'><code>-simconf</code></td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='right'>\"Type I/II error\"</td></tr>\n<tr ><td  align='center'><code>-simwidth</code></td><td  align='center'>\"Width\"</td><td  align='center'>\"Width\"</td><td  align='center'>n/a</td><td  align='right'>\"Indifference\"</td></tr>\n<tr ><td  align='center'><code>-simapprox</code></td><td  align='center'>n/a</td><td  align='center'>n/a</td><td  align='center'>\"Approximation\"</td><td  align='right'>n/a</td></tr>\n</table>\n<p class='vspace'>The maximum length of simulation paths is set with switch <code>-simpathlen</code>.\n</p>\n<div class='vspace'></div><h3>Limitations</h3>\n<p>Currently, the simulator does not support every part of the PRISM modelling languages. For example, it does not handle models with multiple initial states or with <code><strong>system</strong>...<strong>endsystem</strong></code> definitions.\n</p>\n<p class='vspace'>It is also worth pointing out that statistical model checking techniques are not well suited to models that exhibit nondeterminism, such as MDPs. This because the techniques rely on generation of <em>random</em> paths, which are not well defined for a MDP. PRISM does allow statistical model checking to be performed on an MDP, but does so by simply resolving nondeterministic choices in a (uniformly) random fashion (and displaying a warning message). Currently PTAs are not supported by the simulator.\n</p><hr />\n<h1>Computing Steady-state And Transient Probabilities</h1>\n<p>If the model is a CTMC or DTMC, it is possible to compute corresponding vectors of\nsteady-state or transient probabilities directly\n(rather than indirectly by analysing a property which requires their computation).\nFrom the GUI, select an option from the \"Model | Compute\" menu.\nFor transient probabilities, you will be asked to supply the\ntime value for which you wish to compute probabilities.\nFrom the command-line, add the <code>-steadystate</code> (or <code>-ss</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock35'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=35' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for steady-state probabilities or the <code>-transient</code> (or <code>-tr</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock36'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=36' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for transient probabilities, again specifying a time value in the latter case.\nThe probabilities are computed for all states of the model and displayed,\neither on the screen (from the command-line) or in the log (from the GUI).\n</p>\n<p class='vspace'>To instead export the vector of computed probabilities to a file, use the \"Model | Compute/export\" option from the GUI, or the <code>-exportsteadystate</code> (or <code>-exportss</code>) and <code>-exporttransient</code> (or <code>-exporttr</code>) switches from the command-line:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock37'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss -exportss poll2-ss.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=37' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the command-line, you can request that the probability vectors exported are in Matlab format by adding the <code>-exportmatlab</code> switch.\n</p>\n<div class='vspace'></div><h3>Initial probability distributions</h3>\n<p>By default, for both steady-state and transient probability computation,\nPRISM assumes that the initial probability distribution of the model is\nan equiprobable choice over the set of initial states.\nYou can override this and provide a specific initial distribution. This is done using the <code>-importinitdist</code> switch. The format for this imported distribution is identical to the ones exported by PRISM, i.e. simply a list of probabilities for all states separated by new lines. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock38'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -exporttr poll2-tr1.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -importinitdist poll2-tr1.txt -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=38' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is (essentially) equivalent to this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock39'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=39' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Ranges of time values</h3>\n<p>Finally, you can compute transient probabilities for a range of time values, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock40'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 0.1:0.01:0.2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=40' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which computes transient probabilities for the time points 0.1, 0.11, 0.12, .., 0.2. In this case, the computation is done incrementally, with probabilities for each time point being computed from the previous point for efficiency.\n</p><hr />\n<h1>Experiments</h1>\n<p>PRISM supports <em>experiments</em>, which is a way of automating multiple instances of model checking.\nThis is done by leaving one or more <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a> undefined, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock41'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=41' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This can be done for constants in the model file, the properties file, or both.\nBefore any verification can be performed, values must be provided for any such constants. In the GUI, a dialog appears in which the user is required to enter values. From the command line, the <code>-const</code> switch must be used, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock42'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=42' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To run an experiment, provide a <em>range</em> of values for one or more of the constants. Model checking will be performed for all combinations of the constant values provided. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock43'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4:6,T=60:10:100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=43' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>N=4:6</code> means that values of 4,5 and 6 are used for <code>N</code>,\nand <code>T=60:10:100</code> means that values of 60, 70, 80, 90 and 100 (i.e. steps of 10) are used for <code>T</code>.\n</p>\n<p class='vspace'>For convenience, constant specifications can be split across separate instances of the <code>-const</code> switch, if desired.\nYou can also specify double-valued constants as fractions rather than decimals. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock44'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9 -const p=1/3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=44' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, the same thing can be achieved by selecting a single property,\nright clicking on it and selecting \"New experiment\"\n(or alternatively using the popup menu in the \"Experiments\" panel).\nValues or ranges for each undefined constant can then be supplied in the resulting dialog.\nDetails of the new experiment and its progress are shown in the panel.\nTo stop the experiment before it has completed, click the red \"Stop\" button and it will\nhalt after finishing the current iteration of model checking.\nOnce the experiment has finished, right clicking on the experiment produces a pop-up menu,\nfrom which you can view the results of the experiment or export them to a file.\n</p>\n<p class='vspace'>For experiments based on properties which return numerical results, you can also use the GUI to plot graphs of the results.\nThis can be done either before the experiment starts, by selecting the \"Create graph\" tick-box in the dialog used to create the experiment\n(in fact this box is ticked by default), or after the experiment's completion, by choosing \"Plot results\" from the pop-up menu on the experiment.\nA dialog appears, where you can choose which constant (if there are more than one) to use for the x-axis of the graph,\nand for which values of any other constants the results should be plotted.\nThe graph will appear in the panel below the list of experiments.\nRight clicking on a graph and selecting \"Graph options\" brings up a dialog from which many properties of the graph can be configured.\nFrom the pop-up menu of a graph, you can also choose to print the graph (to a printer or Postscript file)\nor export it in a variety of formats:\nas an image (PNG or JPEG),\nas an encapsulated Postscript file (EPS),\nin an XML-based format (for reloading back into PRISM),\nor as code which can be used to generate the graph in Matlab.\n</p>\n<p class='vspace'>Approximate computation of quantitive results obtained with the <a class='wikilink' href='ApproximateModelChecking.html'>simulator</a> can also be used on experiments. In the GUI, select the \"Use Simulation\" option when defining the parameters for the experiment. From the command-line, just add the <code>-sim</code> switch as usual.\n</p>\n<p class='vspace'><a name='exportresults' id='exportresults'></a>\n</p><h3>Exporting results</h3>\n<p>You can export all the results from an experiment to a file or to the screen. From the command-line, use the <code>-exportresults</code> switch, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock45'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=45' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send to output file <code>res.txt</code>, or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock46'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=46' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send the results straight to the screen. From the GUI, right click on the experiment and select \"Export results\".\n</p>\n<p class='vspace'>The default behaviour is to export a <em>list</em> of results in <em>text</em> form, using tabs to separate items. The above examples produce:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock47'>\r\n  <div class='sourceblocktext'><div class=\"text\">N &nbsp; &nbsp; &nbsp; T &nbsp; &nbsp; &nbsp; Result<br />\n4 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n4 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 4.707364688019771E-6<br />\n4 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 1.3126420636755292E-5<br />\n5 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n5 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 3.267731327728599E-6<br />\n5 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=47' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can change the format in which the results are exported by appending one or more comma-separated options to the end of the <code>-exportresults</code> switch, for example to export in CSV (comma-separated values) format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock48'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=48' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock49'>\r\n  <div class='sourceblocktext'><div class=\"text\">N, T, Result<br />\n4, 0, 0.0<br />\n4, 10, 4.707364688019771E-6<br />\n4, 20, 1.3126420636755292E-5<br />\n5, 0, 0.0<br />\n5, 10, 3.267731327728599E-6<br />\n5, 20, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=49' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock50'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:dataframe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=50' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock51'>\r\n  <div class='sourceblocktext'><div class=\"text\">N,T,Result<br />\n4,0,0<br />\n4,10,4.70736468802e-06<br />\n4,20,1.31264206368e-05<br />\n5,0,0<br />\n5,10,3.26773132773e-06<br />\n5,20,8.34357506036e-06</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=51' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also add the <code>matrix</code> option, to export the results as one or more 2D matrices, rather than a list.\nThis is particularly useful if you want to create a surface plot from results that vary over two constants.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock52'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv,matrix</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=52' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock53'>\r\n  <div class='sourceblocktext'><div class=\"text\">&quot;N\\T&quot;<br />\n, 0.0, 10.0, 20.0<br />\n4, 0.0, 4.707364688019771E-6, 1.3126420636755292E-5<br />\n5, 0.0, 3.267731327728599E-6, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=53' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>matrix</code> option is also available in normal (non-CSV) mode.\n</p>\n<p class='vspace'>You can also export results in the form of comments, used by PRISM's <a class='urllink' href='https://github.com/prismmodelchecker/prism/wiki/Regression-Testing'>regression testing</a> functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock54'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:comment</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=54' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock55'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// RESULT (N=4,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=10): 4.707364688019771E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=20): 1.3126420636755292E-5</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=10): 3.267731327728599E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=20): 8.343575060356386E-6</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=55' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, it is also possible to <em>import</em> previously exported results (in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format).\n</p>\n<p class='vspace'>A related option is the <code>-exportvector &lt;file&gt;</code> switch, useful in general contexts, not for experiments.\nThis exports the results for all states of the model\n(typically, the log just displays the result for the initial state, unless a <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> has been used)\nto the the file <code>file</code>.\n</p><hr />\n<h1>Strategies</h1>\n<p>Properties to be model checked on MDPs (and their variants, such as POMDPs or IMDPs) usually quantify over <em>strategies</em> (or <em>policies</em>) of the model, i.e., over the different possible ways that nondeterminism can be resolved in the model.\nFor example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock56'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=56' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>determines the maximum probability, over all strategies, of reaching a state satisfying the label <code>\"goal\"</code>. When checking such properties, you can also ask PRISM to generate a corresponding (optimal) strategy, which yields this maximum probability when followed. The strategy can then be viewed, exported or simulated.\n</p>\n<p class='vspace'><strong>Note:</strong> For consistency across models, PRISM now uses the terminology <em>strategy</em> (rather than alternatives such as <em>policy</em>). In older versions of the tool, these were referred to as <em>adversaries</em>. Currently, the newer (and more extensive) <em>strategy generation</em> functionality is implemented just for the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>\"explicit\"</a> model checking engine,\nwhich is used automatically if strategy generation is requested.\nThe old <em>adversary generation</em> functionality (see below) still exists for the \"sparse\" engine, but will be updated in the future.\n</p>\n<p class='vspace'><strong>Generating strategies</strong>. Optimal strategies can be generated either from the command-line or the graphical user interface (GUI). For the former, use the <code>-exportstrat</code> switch. Simple examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock57'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat stdout</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.tra</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=57' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, you can trigger strategy generation by ticking the \"Generate strategy\" box either on the popup menu that appears when you right-click a property, or from the \"Strategies\" menu at the top. As long as it is supported, a strategy will be then generated once \"Verify\" is clicked.\n</p>\n<p class='vspace'>From the same menu(s), you can then\n</p>\n<div class='vspace'></div><ul><li>export the strategy to a file\n</li><li>view the strategy by printing it in the log\n</li><li>explore the strategy in the simulator\n</li></ul><p class='vspace'><strong>Strategy export types</strong>. Strategies can be viewed or exported in several different formats:\n</p>\n<p class='vspace'>(i) <em>Action list</em>. This is a list of the action taken in each state of the model, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock58'>\r\n  <div class='sourceblocktext'><div class=\"text\">(0,0):east<br />\n(0,1):north<br />\n(0,2):north<br />\n(1,0):south<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=58' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where states, by default, are shown as a tuple of variable values.\n</p>\n<p class='vspace'>(ii) <em>Induced model</em>. This is a representation of the model that is induced when the strategy is applied. There are two \"modes\" for this export. The first (and default) is \n<em>reduce</em>, which removes the nondeterminism resolved by the strategy (e.g., an MDP becomes a DTMC). This can be useful to re-import the model back into PRISM and analyse the induced model. The second is <em>restrict</em>, which shows the original model but with a restricted set of choices (e.g., an MDP with just one choice in each state). In each case, the transitions of the induced model are presented as a <code>.tra</code> file (as for normal <a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>model export</a>), e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock59'>\r\n  <div class='sourceblocktext'><div class=\"text\">9 11<br />\n0 5 1 east<br />\n1 10 1 north<br />\n2 15 0.9 north<br />\n2 16 0.1 north<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=59' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>(iii) <em>Dot file</em>. This is, like the previous format, a view of the model induced by the strategy, but in <a class='urllink' href='http://www.graphviz.org'>Dot</a> format, which allows it to be visualised.\n</p>\n<p class='vspace'><strong>Configuring strategy export</strong>. \nAs hinted in the command-line examples above, the <code>-exportstrat</code> switch uses the file extension to determine the preferred format: if the strategy is exported to a file with extension <code>.tra</code> or <code>.dot</code>, then it uses an induced model or Dot file, respectively. Otherwise, the default is an action list. You can specify the desired format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock60'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=actions</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=60' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Further options can be added, e.g., to specify whether an induced model is exported in \"restrict\" or \"reduce\" mode:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock61'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced,mode=restrict</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=61' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A full list of available options is as follows:\n</p>\n<div class='vspace'></div><ul><li><code>type</code> (<code>actions</code>, <code>induced</code> or <code>dot</code>): the type of strategy export to use (action list, induced model or Dot file)\n</li><li><code>mode</code> (<code>restrict</code> or <code>reduce</code>): when exporting as an induced model or Dot file, whether to \"restrict\" or \"reduce\" the model (see above); the default is \"restrict\"\n</li><li><code>reach</code> (<code>true</code> or <code>false</code>): whether to restrict the strategy to states that are reachable when it is applied to the model (this is currently only used for exporting induced models and Dot files, and the default value is false and true, respectively, in these two cases)\n</li><li><code>states</code> (<code>true</code> or <code>false</code>): whether to show states, rather than state indices, for actions lists or Dot files; this is true by default\n</li><li><code>obs</code> (<code>true</code> or <code>false</code>): for partially observable models, whether to merge observationally equivalent states; this is true by default\n</li></ul><p class='vspace'><strong>Strategy types</strong>. PRISM generates several types of strategies. The simplest are <em>memoryless deterministic</em> strategies, which pick a single action in each state, as in the examples above. For some query types (e.g., step-bounded properties, or LTL-based properties), <em>finite-memory</em> strategies are generated, where an additional memory value is used. For these, induced models or Dot files are most useful since they will also show how the memory values are updated as the strategy is executed. Note that, in these cases, the state indices of the strategy will correspond to the product model constructed during model checking, not the original model. The product model can be exported using the <code>-exportprodtrans</code> and <code>-exportprodstates</code> switches.\n</p>\n<p class='vspace'><strong>Adversary generation</strong>. As mentioned above, the \"sparse\" model checking engine still includes older so-called \"adversary generation\" functionality. This can be used to export the induced model to a file using the <code>-exportadv</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock62'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadv adv.tra -s</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadvmdp adv.tra -s</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=62' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where the <code>-exportadv</code> and <code>-exportadvmdp</code> export a DTMC and an MDP, respectively, i.e., corresponding to the \"reduce\" and \"restrict\" modes described above.\nFrom the GUI, change the \"Adversary export\" option (under the \"PRISM\" settings) from \"None\" to \"DTMC\" or \"MDP\". You can also change the filename for the export adversary which, by default, is <code>adv.tra</code> as in the example above.\n</p><hr />\n<h1>Support For PEPA Models</h1>\n<p>For CTMCs, PRISM also accepts model descriptions in the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='../Main/References.html#Hil96'>Hil96</a>].\nThe tool compiles such descriptions into the PRISM language and then constructs the model as normal.\nThe language accepted by the PEPA to PRISM compiler is actually a subset of PEPA.\nThe restrictions applied to the language are firstly that component identifiers can only be bound to sequential components\n(formed using prefix and choice and references to other sequential components only).\nSecondly, each local state of a  sequential component must be named.  For example, we would rewrite:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).(b,s).P;\n</li></ul><p class='vspace'>as:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).P';\n</li><li>P' = (b,s).P;\n</li></ul><p class='vspace'>Finally, active/active synchronisations are not allowed since the PRISM \ndefinition of these differs from the PEPA definition.  Every PEPA \nsynchronisation must have exactly one active component.\nSome examples of PEPA model descriptions which can be imported into PRISM\ncan be found in the <code>prism-examples/pepa</code> directory.\n</p>\n<p class='vspace'>From the command-line version of PRISM, add the <code>-importpepa</code> switch and the model will be treated as a PEPA description.\nFrom the GUI, select \"Model | Open model\" and then choose \"PEPA models\"\non the \"Files of type\" drop-down menu.\nAlternatively, select \"Model | New | PEPA model\" and either type a description from scratch\nor paste in an existing one from elsewhere.\nOnce the PEPA model has been successfully parsed by PRISM,\nyou can view the corresponding PRISM code (as generated by the PEPA-to-PRISM compiler)\nby selecting menu option \"Model | View | Parsed PRISM model\".\n</p><hr />\n<h1>Support For SBML</h1>\n<p>PRISM includes a (prototype) tool to translate specifications in <a class='urllink' href='http://sbml.org/'>SBML</a> (Systems Biology Markup Language) to model descriptions in the PRISM language. SBML is an XML-based format for representing models of biochemical reaction networks. The translator currently works with Level 2 Version 1 of the SBML specification, details of which can be found <a class='urllink' href='http://sbml.org/documents/'>here</a>.\n</p>\n<p class='vspace'>Since PRISM is a tool for analysing discrete-state systems, the translator is designed for SBML files intended for discrete stochastic simulation. A useful set of such files can be found in the CaliBayes <a class='urllink' href='http://code.google.com/p/dsmts/'>Discrete Stochastic Model Test Suite</a>. There are also many more SBML files available in the <a class='urllink' href='http://www.ebi.ac.uk/biomodels/'>BioModels Database</a>.\n</p>\n<p class='vspace'>We first give a simple example of an SBML file and its PRISM translation. We then give some more precise details of the translation process.\n</p>\n<div class='vspace'></div><h3>Example</h3>\n<p>An SBML file comprises a set of <em>species</em> and a set of <em>reactions</em> which they undergo. Below is the SBML file for the simple reversible reaction: <strong>Na + Cl &#8596; Na<sup>+</sup> + Cl<sup>-</sup></strong>, where there are initially 100 Na and Cl atoms and no ions, and the base rates for the forwards and backwards reactions are 100 and 10, respectively.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock63'>\r\n  <div class='sourceblocktext'><div class=\"xml\"><span class=\"re1\">&lt;?xml</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1.0&quot;</span> <span class=\"re0\">encoding</span>=<span class=\"st0\">&quot;UTF-8&quot;</span><span class=\"re2\">?&gt;</span><br />\n<span class=\"re1\">&lt;sbml</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.sbml.org/sbml/level2&quot;</span> <span class=\"re0\">metaid</span>=<span class=\"st0\">&quot;_000000&quot;</span> <span class=\"re0\">level</span>=<span class=\"st0\">&quot;2&quot;</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; <span class=\"re1\">&lt;model</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;nacl&quot;</span> <span class=\"re0\">name</span>=<span class=\"st0\">&quot;Na+Cl&quot;</span><span class=\"re2\">&gt;</span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;compartment</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;compartment&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na_plus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl_minus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactions<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>forwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;100&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>backwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na_plus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl_minus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;10&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactions<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; <span class=\"re1\">&lt;/model<span class=\"re2\">&gt;</span></span><br />\n<span class=\"re1\">&lt;/sbml<span class=\"re2\">&gt;</span></span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=63' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And here is the resulting PRISM code:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock64'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// File generated by automatic SBML-to-PRISM conversion</span><br/>\n<span class=\"prismcomment\">// Original SBML file: nacl.xml</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">MAX_AMOUNT</span> = <span class=\"prismnum\">100</span>;<br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction forwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">forwards_rate</span> = <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// forwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction backwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">backwards_rate</span> = <span class=\"prismnum\">10</span>; <span class=\"prismcomment\">// backwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na</span><br/>\n<br/>\n\t<span class=\"prismident\">na</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">na</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na</span> &lt;= <span class=\"prismident\">na_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl</span><br/>\n<br/>\n\t<span class=\"prismident\">cl</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">cl</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl</span> &lt;= <span class=\"prismident\">cl_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na_plus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_plus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na_plus</span><br/>\n<br/>\n\t<span class=\"prismident\">na_plus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_plus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na_plus</span> &lt;= <span class=\"prismident\">na_plus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">na_plus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl_minus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_minus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl_minus</span><br/>\n<br/>\n\t<span class=\"prismident\">cl_minus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_minus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl_minus</span> &lt;= <span class=\"prismident\">cl_minus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">cl_minus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reaction rates</span><br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">reaction_rates</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reward structures (one per species)</span><br/>\n<br/>\n<span class=\"prismcomment\">// 1</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 2</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 3</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na_plus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na_plus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 4</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl_minus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl_minus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=64' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the latter, we can use PRISM to generate a simple plot of the expected amount of Na and Na+ over time (using both model checking and a single random trace from the simulator):\n</p>\n<div class='vspace'></div><div class='img imgcaption'><a class='urllink' href='../uploads/sbml_ex_graph.png'><img src='../uploads/sbml_ex_graph.png' alt='' /></a><br /><span class='caption'><strong>Expected amount of Na/Na+ at time T</strong></span></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Using the translator</h3>\n<p>At present, the SBML-to-PRISM translator is included in the PRISM code-base, but not integrated into the application itself.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock65'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=65' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are using a binary (rather than source code) distribution of PRISM, replace <code>classes</code> with <code>lib/prism.jar</code> in the above.\n</p>\n<p class='vspace'>Alternatively (on Linux or Mac OS X), ensure <code>prism</code> is in your path and then save the script below as an executable file called <code>sbml2prism</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock66'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#!/bin/sh</span><br />\n<br />\n<span class=\"co0\"># Startup script for SBML-to-PRISM translator</span><br />\n<br />\n<span class=\"co0\"># Launch using main PRISM script</span><br />\n<span class=\"re2\">PRISM_MAINCLASS</span>=<span class=\"st0\">&quot;prism.SBML2Prism&quot;</span><br />\n<span class=\"kw3\">export</span> PRISM_MAINCLASS<br />\nprism <span class=\"st0\">&quot;$@&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=66' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Then use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock67'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">sbml2prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=67' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The following PRISM properties file will also be useful:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock68'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">c</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismident\">c</span>}=? [<span class=\"prismkeyword\">I</span>=<span class=\"prismident\">T</span>]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=68' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This contains a single property which, based on the reward structures in the PRISM model generated by the translator, means \"the expected amount of species <em>c</em> at time <em>T</em>\". The constant <em>c</em> is an integer index which can range between 1 and <em>N</em>, where <em>N</em> is the number of species in the model. To view the expected amount of each species over time, create an <a class='wikilink' href='Experiments.html'>experiment</a> in PRISM which varies <em>c</em> from 1 to <em>N</em> and <em>T</em> over the desired time range.\n</p>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Details of the translation</h3>\n<p>The basic structure of the translation process is as follows:\n</p>\n<div class='vspace'></div><ul><li>Each <em>species</em> in the SBML file is represented by a <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>module</a> in the resulting PRISM file. This module, which (where possible) retains the SBML species id as its name, contains a single <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variable</a> whose value represents the amount of the species present. A corresponding <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structure</a> for computing the expected amount of the species at a given time instant is also created. Species for which the <code>boundaryCondition</code> flag is set to <code>true</code> in the SBML file do not have a corresponding module.\n<div class='vspace'></div></li><li>Each <em>reaction</em> in the SBML file is associated with a unique <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation action label</a>. The module for each species which takes part in the reaction will include a synchronous <a class='wikilink' href='../ThePRISMLanguage/Commands.html'>command</a> to represent this. An additional PRISM module called <code>reaction_rates</code> stores the expression representing the rate of each reaction (from the corresponding <code>kineticLaw</code> section in the SBML file). Reaction stoichiometry information is respected but must be provided in the scalar <code>stoichiometry</code> field of a <code>speciesReference</code> element, not in a separate <code>StoichiometryMath</code> element.\n<div class='vspace'></div></li><li>Each <em>parameter</em> in the SBML file, either global to the file or specific to a reaction, becomes a <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constant</a> in the PRISM file. If a value for this parameter is given, it used. If not, the constant is left as undefined.\n</li></ul><p class='vspace'>As described above, this translation process is designed for discrete systems and so the amount of each species in the model is represented by an integer variable. It is therefore assumed that the initial amount for each species specified in the SBML file is also given as an integer. If this is not the case, then the values will need to be scaled accordingly first.\n</p>\n<p class='vspace'>Furthermore, since PRISM is primarily a model checking (rather than simulation) tool, it is important that the amount of each species also has an upper bound (to ensure a finite state space). When model checking, the efficiency (or even feasibility) of the process is likely to be very sensitive to the upper bound(s) chosen. When using the discrete-event simulation functionality of PRISM, this is not the case and the bounds can can be set much higher. By default the translator uses an upper bound of 100 (which is increased if the initial amount exceeds this). A different value can specified through a second command-line argument as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock69'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml 1000 &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=69' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, upper bounds can be modified manually after the translation process.\n</p>\n<p class='vspace'>Finally, The following aspects of SBML files are not currently supported and are ignored during the translation process:\n</p>\n<div class='vspace'></div><ul><li>compartments\n</li><li>events/triggers\n</li></ul><hr />\n<h1>Explicit Model Import</h1>\n<p>It is also possible to construct models in PRISM through direct specification of their transition matrix.\nTwo formats for explicit model import are currently supported:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \"<code>.tra</code>\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li></ul><p class='vspace'>Presently, this functionality is only supported in the command-line version of the tool, usually using the <code>-importmodel</code> switch.\nIn a similar fashion to <code>-exportmodel</code> switch, the type of import is usually determined from the file extension.\n</p>\n<p class='vspace'>For UMB, all model info is contained in a single file. An example of import is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock70'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=70' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For the plain text files (<code>.tra</code> etc.), various options are possible.\nTo just import the core part of the model (the transition function) use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock71'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=71' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM tries to determine the model type from the format of the <code>.tra</code> file,\nbut if this does not work, the model type can be overwritten using the <code>-dtmc</code>, <code>-ctmc</code> and <code>-mdp</code> switches.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock72'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=72' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Using the same formats as for <a class='wikilink' href='ExportingTheModel.html'>model export</a>, other parts of the model can also be imported:\n</p>\n<div class='vspace'></div><ul><li><code>.lab</code> - labels\n</li><li><code>.srew</code>, <code>.trew</code> - rewards: states, transitions\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>Here is an example of also importing labels and states:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock73'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra,sta,lab</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=73' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If state information is not imported, a single zero-indexed variable <code>x</code> is assumed.\n</p>\n<p class='vspace'>Note also that, since details about the initial state(s) of a model are not preserved in the <code>.tra</code> file,\nbut are included in the labels file, this should also be used to designate a particular initial state for a model.\nOtherwise, state 0 is assumed to be the initial state or,\nif state information is imported, the state in which all variables take their minimum value is used.\n</p>\n<p class='vspace'>Use the extension <code>.all</code> to import from any matching files with appropriate extensions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock74'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=74' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this case, you can omit the <code>-importmodel</code> switch and just specify the <code>.all</code>-ended filename, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock75'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=75' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Efficiency</h3>\n<p>Please note, for PRISM's symbolic model construction/engines, which are often used by default,\nthis explicit method of constructing models in PRISM is typically less efficient than using the PRISM language.\nThis is because the underlying data structures used to represent the model\nfunction better when there is high-level structure and regularity to exploit.\nYou may want to switch to the \"explicit\" engine:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock76'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=76' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The situation can also be alleviated to a certain extent for the symbolic implementations by importing\nthe <code>.sta</code> file, since the composition of the states reintroduces some regularity\n(although is still typically inefficient to construct).\n</p>\n<p class='vspace'>\n</p><h3>Other options</h3>\n<p>In a similar style to PRISM's <a class='wikilink' href='ExportingTheModel.html'><code>-exportmodel</code></a> switch, while <code>-importmodel</code> is usually the most convenient, you can also specify each part separately, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock77'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importtrans poll2.tra -importstates poll2.sta -importlabels poll2.lab -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=77' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>There are also <code>-importstaterewards</code> and <code>-impottransrewards</code> switches.\nYou can import multiple reward structures using multiple instances of the these switches.\nIf present in the rewards files (see the appendix \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\"),\nthe names of the reward structures are read too.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:26 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/AllOnOnePage@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / All On One Page | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:26 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/AllOnOnePage@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / All On One Page | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:26 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/AllOnOnePage@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / AllOnOnePage </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for xml\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.xml .de1, .xml .de2 {font-family: monospace; font-weight: normal;}\n.xml  {font-family:monospace;}\n.xml .imp {font-weight: bold; color: red;}\n.xml li, .xml .li1 {font-family: monospace; color: black; font-weight: normal;}\n.xml .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.xml .li2 {font-weight: bold;}\n.xml .es0 {color: #000099; font-weight: bold;}\n.xml .br0 {color: #66cc66;}\n.xml .sy0 {color: #66cc66;}\n.xml .st0 {color: #ff0000;}\n.xml .nu0 {color: #cc66cc;}\n.xml .sc-1 {color: #808080; font-style: italic;}\n.xml .sc0 {color: #00bbdd;}\n.xml .sc1 {color: #ddbb00;}\n.xml .sc2 {color: #339933;}\n.xml .sc3 {color: #009900;}\n.xml .re0 {color: #000066;}\n.xml .re1 {color: #000000; font-weight: bold;}\n.xml .re2 {color: #000000; font-weight: bold;}\n.xml .ln-xtra, .xml li.ln-xtra, .xml div.ln-xtra {background-color: #ffc;}\n.xml span.xtra { display:block; }\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>Running PRISM</span></h1>\n<hr />\n<h1>Starting PRISM</h1>\n<p>There are two versions of PRISM, one based on a graphical user interface (GUI),\nthe other based on a command line interface. Both use the same underlying model checker.\nThe latter is useful for running large batches of jobs, leaving long-running model checking tasks in the background, or simply for running the tool quickly and easily once you are familiar with its operation. \n</p>\n<p class='vspace'>Details how how to run PRISM can be found in the <a class='wikilink' href='../InstallingPRISM/Main.html'>installation instructions</a>.\nIn short, to run the PRISM GUI:\n</p>\n<div class='vspace'></div><ul><li>(on Windows) click the short-cut (to <code>xprism.bat</code>) installed on the Desktop/Start Menu\n</li><li>(on other OSs) run the <code>xprism</code> script in the <code>bin</code> directory\n</li></ul><p class='vspace'>You can also optionally specify a model file and a properties file to load upon starting the GUI, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xprism example.prism</span><br/>\n<span style=\"font-weight:bold;\">xprism example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To use the command-line version of PRISM, run the <code>prism</code> script, also in the <code>bin</code> directory, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism example.prism example.props -prop 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-dir</code> switch can be used to specify a directory for input (and output) files.\nSo the following are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism ~/myfiles/example.prism ~/myfiles/example.props</span><br/>\n<span style=\"font-weight:bold;\">prism -dir ~/myfiles example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The remainder of this section of the manual describes the main types of functionality offered by PRISM.\nFor a more introductory guide to using the tool, try the\n<a class='urllink' href='http://www.prismmodelchecker.org/tutorial/'>tutorial</a> on the PRISM web site.\nSome screenshots of the GUI version of PRISM are shown below.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui1.gif'><img width='500' src='../uploads/gui1.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (editing a model)</strong></span></div>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui2.gif'><img width='500' src='../uploads/gui2.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (model checking)</strong></span></div>\n<div class='vspace'></div><hr />\n<h1>Loading And Building a Model</h1>\n<p>Typically, when using PRISM, the first step is to load a model that has been specified in the PRISM modelling language. If using the GUI, select menu option \"Model | Open Model\" and choose a file. There are a selection of sample PRISM model files in the <code>prism-examples</code> directory of the distribution.\nA few very small models are contained in the subdirectory <code>simple</code>;\nthe rest are in subdirectories grouped by model type.\n</p>\n<p class='vspace'>The model will then be displayed in the editor in the \"Model\" tab of the GUI window. The file is parsed upon loading. If there are no errors, information about the modules, variables, and other components of the model is displayed in the panel to the left and a green tick will be visible. If there are errors in the file, a red cross will appear instead and the errors will be highlighted in the model editor. To view details of the error, position the mouse pointer over the source of the error (or over the red cross). Alternatively, select menu option \"Model | Parse Model\" and the error mIessage will be displayed in a message box. Model descriptions can, of course, also be typed from scratch into the GUI's editor.\n</p>\n<div class='vspace'></div><h3>Building the model</h3>\n<p>In order to perform model checking, PRISM will (in most cases) need to construct the corresponding probabilistic model, i.e. convert the PRISM model description to, for example, an MDP, DTMC, etc. During this process, PRISM computes the set of states in the model which are reachable from the initial states and the transition matrix which represents the model.\n</p>\n<p class='vspace'>Model construction is done automatically when you perform <a class='wikilink' href='ModelChecking.html'>model checking</a>. However, you may always want to explicitly ask PRISM to build the model in order to test for errors or to see how large the model is. From the GUI, you can do this by by selecting \"Model | Build Model\". If there are no errors during model construction, the number of states and transitions in the model will be displayed in the bottom left corner of the window.\n</p>\n<p class='vspace'>From the command-line, simply type:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.nm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>model.nm</code> is the name of the file containing the model description.\n</p>\n<p class='vspace'>For some types of models, notably PTAs, models are not constructed in this way (because the models are infinite-state). In these cases, analysis of the model is not performed until model checking is performed.\n</p>\n<p class='vspace'><a name='deadlocks' id='deadlocks'></a>\n</p><h3>Deadlocks</h3>\n<p>You should be aware of the possibility of <em>deadlock states</em> (or <em>deadlocks</em>) in the model,\ni.e. states which are reachable but from which there are no outgoing transitions.\nPRISM will automatically search your model for deadlocks and, by default,\n\"fix\" them by adding self-loops in these states.\nSince deadlocks are sometimes caused by modelling errors,\nPRISM will display a warning message in the log when deadlocks are fixed in this way.\n</p>\n<p class='vspace'>You can control whether deadlocks are automatically fixed in this way using the \"Automatically fix deadlocks\" option (or with command-line switches <code>-nofixdl</code> and <code>-fixdl</code>). When fixing is disabled, PRISM will report and error when the model contains deadlocks (this used to be the default behaviour in older versions of PRISM).\n</p>\n<p class='vspace'>If you have unwanted or unexpected deadlocks in your model, there are several ways you can detect then. Firstly, by disabling deadlock fixing (as described above), PRISM will display a list of deadlock states in the log. Alternatively, you can model check the <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> property <code>filter(print, \"deadlock\")</code>, which has the safe effect.\n</p>\n<p class='vspace'>To find out <em>how</em> deadlocks occur, i.e. which paths through the model lead to a deadlock state, there are several possibilities. Firstly, you can model check the <a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>CTL</a> property <code>E[F \"deadlock\"]</code>. When checked from the GUI, this will provide you with the option of display a path to a deadlock in the simulator. From the command-line, for example with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -pf 'E[F \"deadlock\"]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>a path to a deadlock will be displayed in the log.\n</p>\n<p class='vspace'>Finally, in the eventuality that the model is too large to be model checked, you can still use the <a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>simulator</a> to search for deadlocks. This can be done either by manually generating random paths using the <a class='wikilink' href='DebuggingModelsWithTheSimulator.html#gui'>simulator in the GUI</a> or, <a class='wikilink' href='DebuggingModelsWithTheSimulator.html#cl'>from the command-line</a>, e.g. by running:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath deadlock stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Debugging Models With The Simulator</h1>\n<p>PRISM includes a <em>simulator</em>, a tool which can be used to generate sample paths (executions) through a PRISM model. From the GUI, the simulator allows you to explore a model by interactively generating such paths. This is particularly useful for debugging models during development and for running sanity checks on completed models. Paths can also be generated from the command-line.\n</p>\n<p class='vspace'><a name='gui' id='gui'></a>\n</p><h3>Generating a path in the GUI</h3>\n<p>Once you have loaded a model into the PRISM GUI\n(note that it is not necessary to build the model),\nselect the \"Simulator\" tab at the bottom of the main window.\nYou can now start a new path by double-clicking in the bottom half of the window\n(or right-clicking and selecting \"New path\").\nIf there are undefined constants in the\nmodel (or in any currently loaded properties files) you will be prompted to give values for these. You\ncan also specify the state from which you wish to generate a path. By default, this is the initial state of\nthe model.\n</p>\n<p class='vspace'>The main portion of the user interface (the bottom part) displays a path through the currently loaded model. Initially, this will comprise just a single state. The table above shows the list of available transitions from this state. Double-click one of these to extend the path with this transition. The process can be repeated to extend the path in an interactive fashion. Clicking on any state in the current path shows the transition which was taken at this stage. Click on the final state in the path to continue\nextending the path. Alternatively, clicking the \"Simulate\" button will select a transition randomly (according to the probabilities/rates of the available transitions). By changing the number in the box below this button, you can easily generate random paths of a given length with a single click.\nThere are also options (in the accompanying drop-down menu) to allow generation of paths up until a particular length or, for CTMCs, in terms of the time taken.\n</p>\n<p class='vspace'>The figure shows the simulator in action.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui-sim.png'><img width='500' src='../uploads/gui-sim.png' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI: exploring a model using the simulator</strong></span></div>\n<p class='vspace'>It is also possible to:\n</p>\n<div class='vspace'></div><ul><li>backtrack to an earlier point in a path\n</li><li>remove all of the states before some point in a path\n</li><li>restart a path from its first state\n</li><li>export a path to a text file\n</li></ul><p class='vspace'>Notice that the table containing the path displays not just the value of each variable in each\nstate but also the time spent in that state and any rewards accumulated there. You can configure exactly which columns appear by right-clicking on the path and selecting \"Configure view\". For rewards (and for CTMC models, for the time-values), you can can opt to display the reward/time for each individual state and/or the cumulative total up until each point in the path.\n</p>\n<p class='vspace'>At the top-right of the interface, any labels contained in the currently loaded model/properties file are displayed, along with their value in the currently selected state of the path. In addition, the built-in <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>labels</a> <code>\"init\"</code> and <code>\"deadlock\"</code> are also included. Selecting a label from the list highlights all states in the current path which satisfy it.\n</p>\n<p class='vspace'>The other tabs in this panel allow the value of path operators (taken from properties in the current file) to be viewed for the current path, as well as various other statistics.\n</p>\n<p class='vspace'>Another very useful feature for some models is to use the \"Plot new path\" option from the simulator, which generates a plot of some/all of the variable/reward values for a particular randomly generated path through the model.\n</p>\n<p class='vspace'><a name='cl' id='cl'></a>\n</p><h3>Path generation from the command-line</h3>\n<p>It is also possible to generate random paths through a model using the command-line version of PRISM. This is achieved using the <code>-simpath</code> switch, which requires two arguments, the first describing the path to be generated and the second specifying the file to which the path should be output (as usual, specifying <code>stdout</code> sends output to the terminal). The following examples illustrate the various ways of generating paths in this way:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -simpath 10 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath time=7.5 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath deadlock path.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These generate a path of 10 steps, a path of at least 7.5 time units and a path ending in deadlock, respectively.\n</p>\n<p class='vspace'>Here's an example of the output:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 1 0.007479539729154247 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 2 0.00782819795294666 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 3 0.01570585559933703 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 4 0.017061111948220263 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 5 0.026816317516034468 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 6 0.039878416276337814 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 7 0.04456566315999103 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 8 0.047368359683643765 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 9 0.04934857366557349 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 10 0.055031679365844674 1 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This shows the sequence of states in the path, i.e. the values of the variables in each state. In the example above, there are 4 variables: <code>s</code>, <code>a</code>, <code>s1</code> and <code>s2</code>.\nThe first three columns show the type of transition taken to reach that state, its index within the path (starting from 0) and the time at which it was entered. The latter is only shown for continuous time models. The type of the transition is written as <em>[act]</em> if action label <code>act</code> was taken, and as <em>module1</em> if the module named <code>module1</code> takes an unlabelled transition). \n</p>\n<p class='vspace'>Further options can also be appended to the first parameter. For example, option <code>probs=true</code> also displays the probability/rate associated with each transition. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '5,probs=true' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 1 0.0011880118081395378 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 2 0.0037798355025401888 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 3 0.01029212322894221 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 4 0.023258883912578403 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 5 0.027402404026254504 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this example, the rate is 200.0 for all transitions.\nTo show the state/transition rewards for each step, use option <code>rewards=true</code>.\n</p>\n<p class='vspace'>If you are only interested in values of certain variables of your model, use the <code>vars=(...)</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '500,probs=true,vars=(a,s1,s2)' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 110 0.5025332771499665 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 111 0.5109407735244359 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 112 0.9960642154887506 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station1 0.5 130 1.0645858553472822 0 1 0</span><br/>\n<span style=\"font-style:italic;\">[loop1b] 200.0 132 1.0732572896618477 1 1 0</span><br/>\n<span style=\"font-style:italic;\">[serve1] 1.0 133 2.939742026148121 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 225 3.4311507854807677 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 227 3.434285492243098 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 228 3.553118276800078 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 250 3.6354431222941406 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 251 3.637552738997181 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 252 3.7343375346150576 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of single quotes around the path description argument to prevent the shell from misinterpreting special characters such as \"<code>(</code>\".\n</p>\n<p class='vspace'>Notice also that the above only displays states in which the values of some variable of interest changes. This is achieved with the option <code>changes=true</code>, which is automatically enabled when you use <code>vars=(...)</code>. If you want to see all steps of the path, add the option <code>changes=false</code>.\n</p>\n<p class='vspace'>An alternative way of viewing paths is to only display paths at certain fixed points in time. This is achieved with the <code>snapshot=x</code> option, where <code>x</code> is the time step. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 'time=5.0,snapshot=0.5' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">94 0.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">198 1.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">314 1.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">375 2.0 1 1 1 1</span><br/>\n<span style=\"font-style:italic;\">376 2.5 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">376 3.0 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">378 3.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">378 4.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">478 4.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">511 5.0 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use the <code>sep=...</code> option to specify the column separator. Possible values are <code>space</code> (the default), <code>tab</code> and <code>comma</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '10,vars=(a,b),sep=comma' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step,a,b,time</span><br/>\n<span style=\"font-style:italic;\">0,0,0,0.0</span><br/>\n<span style=\"font-style:italic;\">2,1,0,0.058443536856580006</span><br/>\n<span style=\"font-style:italic;\">3,1,1,0.09281024515535738</span><br/>\n<span style=\"font-style:italic;\">6,1,2,0.2556555786269585</span><br/>\n<span style=\"font-style:italic;\">7,1,3,0.284062896359802</span><br/>\n<span style=\"font-style:italic;\">8,1,4,1.1792064236954896</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When generating paths to a deadlock state, additional <code>repeat=...</code> option is available which will construct multiple paths until a deadlock is found. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath 'deadlock,repeat=100' stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, the simulator detects deterministic loops in paths (e.g. if a path reaches a state from which there is a just a single self-loop leaving that state) and stops generating the path any further. You can disable this behaviour with the <code>loopcheck=false</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">Warning: Deterministic loop detected after 6 steps (use loopcheck=false option to extend path).</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 3</span><br/>\n<span style=\"font-style:italic;\">die 4 7 3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10,loopcheck=false stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 2</span><br/>\n<span style=\"font-style:italic;\">die 4 7 2</span><br/>\n<span style=\"font-style:italic;\">die 5 7 2</span><br/>\n<span style=\"font-style:italic;\">die 6 7 2</span><br/>\n<span style=\"font-style:italic;\">die 7 7 2</span><br/>\n<span style=\"font-style:italic;\">die 8 7 2</span><br/>\n<span style=\"font-style:italic;\">die 9 7 2</span><br/>\n<span style=\"font-style:italic;\">die 10 7 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>One final note: the <code>-simpath</code> switch only generates paths up to the maximum path length setting of the simulator (the default is 10,000). If you want to generate longer paths, either change the\n<a class='wikilink' href='../ConfiguringPRISM/Main.html'>default setting</a> or override it temporarily from the command-line using the <code>-simpathlen</code> switch.\nYou might also use the latter to decrease the setting,\ne.g. to look for a path leading to a deadlock state,\nbut only within 100 steps:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath deadlock stdout -simpathlen 100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Exporting The Model</h1>\n<p>If required, once the model has been constructed, it can be exported, either for manual examination or for use in another tool. The following can all be exported:\n</p>\n<div class='vspace'></div><ul><li>the <strong>transition matrix</strong> (or function);\n</li><li>the <strong>rewards</strong> (state/transition) rewards;\n</li><li>the <strong>labels</strong> (in the <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>model</a> or <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>properties</a>) and the states that satisfy them\n</li><li>the definition of (reachable) <strong>states</strong>, i.e., their variable values\n</li><li>the definition of <strong>observations</strong>, i.e., their observable values, for partially observable models\n</li></ul><p class='vspace'>From the command-line version of PRISM, the most convenient and flexible approach is to use the <code>-exportmodel</code> switch.\nThis will, by default, use the extension of the filename(s) to determine the format.\n</p>\n<p class='vspace'>From the GUI, use the \"Model | Export\" menu to export the data to a file or, for small models, use the \"Model | View\" menu to print the details directly to the log. For the case of labels, if you want to export labels from the properties file too, use the \"Properties | Export labels\" option, rather than the \"Model | Export\" one.\n</p>\n<p class='vspace'>The main formats for model export are:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \".tra\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li><li><a class='urllink' href='https://www.graphviz.org/'>Dot</a> format, for a graphical view of the model\n</li></ul><p class='vspace'><a name='explicit' id='explicit'></a>\n</p><h3>Plain text (explicit files)</h3>\n<p>This format exports different parts of the model in different file, with the expected filename extensions being:\n</p>\n<div class='vspace'></div><ul><li><code>.tra</code> - transition matrix\n</li><li><code>.srew</code>, <code>.trew</code>, <code>.rew</code> - rewards: states, transitions or both\n</li><li><code>.lab</code> - labels\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>To export just the transition matrix in this format, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To export multiple parts, use, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you omit the file basename of the export files and the basename of the model will be used, so this is equivalent to the above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel .tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can use the shorthand <code>.all</code> to export everything, and <code>.rew</code> to export both state and transition rewards. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can always use <code>stdout</code> instead of a filename. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is a quick way to print all details (of a small model) to the terminal.\n</p>\n<p class='vspace'>The labels (<code>.lab</code>) export includes the built-in labels <code>\"init\"</code> and <code>\"deadlock\"</code>,\nproviding a way to export information about initial states and (fixed) deadlock states.\n</p>\n<p class='vspace'>When there are multiple reward structures, a separate file is created for each one and a (1-indexed) suffix is added to distinguish them.\nBy default, a header in each file (see the \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html#srew'>Explicit Model Files</a>\" appendix) also shows the name of the reward structure.\nThis can be omitted - see the options below - or via the option \"Include headers in model exports\" in the GUI.\n</p>\n<p class='vspace'><a name='umb' id='umb'></a>\n</p><h3>UMB (Unified Markov binary) format</h3>\n<p>UMB is a binary format that can incorporate all parts of the model listed above.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, everything is included. You can omit some parts with the <code>-exportmodel</code>\noptions <code>rewards</code>, <code>labels</code>, <code>states</code> and <code>obs</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb:states=false,rewards=false</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For a small model, you can also see a textual version of the UMB format\nusing file extension <code>.umbt</code> (or option <code>text</code>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock24'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.umbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=24' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also configure the compression used: <code>zip=false</code> turns it off,\n<code>zip=gzip</code> uses gzip and <code>zip=xz</code> uses xz (smaller but slower to read/write).\n</p>\n<p class='vspace'><a name='other' id='other'></a>\n</p><h3>Other formats and options</h3>\n<p>If the file extension is not recognised, PRISM defaults to plain text (explicit) format.\nYou can always override this using the @format@ option, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock25'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=umb,text</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=25' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can perform multiple model exports using several instances of <code>-exportmodel</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock26'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit -exportmodel model.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=26' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Other file formats are also available:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://www.mathworks.com/'>Matlab</a> code (extension <code>.m</code>) or <code>format=matlab</code>\n</li><li>Storm's DRN model format (extension <code>.drn</code>) or <code>format=drn</code>\n</li></ul><p class='vspace'>Other <code>-exportmodel</code> options are:\n</p>\n<div class='vspace'></div><ul><li><code>actions</code> (=<code>true</code>/<code>false</code>) - whether to  actions on choices/transitions\n</li><li><code>precision</code> (=<code>&lt;n&gt;</code>) - use <code>&lt;n&gt;</code> significant figures for floating point values (in text)\n</li><li><code>headers</code> (<code>=true/false</code>) - whether to include headers when exporting rewards\n</li><li><code>rows</code> - export matrices with one row/distribution on each line (plain text)\n</li><li><code>proplabels</code> - also export labels from a properties file into a <code>.lab</code> file\n</li></ul><p class='vspace'>For plain text export, although <code>-exportmodel</code> is now usually the best switch to use,\nother older switches still exist. For example, you can export individual files using\n<code>-exporttrans &lt;file&gt;</code>,\n<code>-exportstates &lt;file&gt;</code>,\n<code>-exportstaterewards &lt;file&gt;</code>,\n<code>-exporttransrewards &lt;file&gt;</code>,\n<code>-exportrewards &lt;file&gt; &lt;file&gt;</code>,\n<code>-exportlabels &lt;file&gt;</code>, and\n<code>-exportproplabels &lt;file&gt;</code>.\nAnd you can use switches\n<code>-exportmodelprecision &lt;x&gt;</code>,\n<code>-exportmatlab</code> and\n<code>-exportrows</code>\nto specify format options affecting all of them.\n</p>\n<p class='vspace'><a name='scc' id='scc'></a>\n</p><h3>Exporting (B)SCCs and end components</h3>\n<p>It is also possible to export the set of (bottom) strongly connected components (SCCs or BSCCs) for a model. This can only be done from the command-line currently. Use, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock27'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportsccs stdout</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportbsccs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=27' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For an MDP, you can also export the set of maximal end components (MECs):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock28'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -exportmecs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=28' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<h1>Model Checking</h1>\n<p>Typically, once a model has been constructed, it is analysed through model checking.\nProperties are specified as described in the \"<a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\" section,\nand are usually kept in files with extensions <code>.props</code>, <code>.pctl</code> or <code>.csl</code>.\nThere are properties files accompanying most of the sample PRISM models in the <code>prism-examples</code> directory.\n</p>\n<p class='vspace'>\n</p><h3>GUI</h3>\n<p>To load a file containing properties into the GUI, select menu option \"Properties | Open properties list\".\nThe file can only be loaded if there are no errors, otherwise an error is displayed.\nNote that it may be necessary to have loaded the corresponding model first,\nsince the properties will probably make reference to variables (and perhaps constants) declared in the model file.\nOnce loaded, the properties contained in the file are displayed in a list in the \"Properties\" tab of the GUI.\nConstants and labels are displayed in separate lists below.\nYou can modify or create new properties, constants and labels from the GUI,\nby right-clicking on the appropriate list and selecting from the pop-up menu which appears. Properties with errors are shaded red and marked with a warning sign.\nPositioning the mouse pointer over the property displays the corresponding error message.\n</p>\n<p class='vspace'>The pop-up menu for the properties list also contains a \"Verify\" option,\nwhich allows you instruct PRISM to model check the currently selected properties\n(hold down Ctrl/Cmd to select more than one property simultaneously).\nAll properties can be model checked at once by selecting \"Verify all\".\nPRISM verifies each property individually.\nUpon completion, the icon next to the property changes according to the result of model checking. For Boolean-valued properties, a result of true or false is indicated by a green tick or red cross, respectively. For properties which have a numerical result (e.g. <code>P=? [ ...]</code>), position the mouse pointer over the property to view the result.\nIn addition, this and further information about model checking is displayed in the log in the \"Log\" tab.\n</p>\n<p class='vspace'>\n</p><h3>Command-line</h3>\n<p>From the command-line, model checking is achieved by passing both a model file and a properties file as arguments, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock29'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=29' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The results of model checking are sent to the display and are as described above for the GUI version.\nBy default, all properties in the file are checked.\nTo model check only a single property, use the <code>-prop</code> switch.\nFor example, to check only the fourth property in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock30'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=30' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or to check only the property with <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#names'>name</a> \"safe\" in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock31'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=31' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also provide a comma-separated list of multiple properties to check,\nusing neither numerical indices or property names:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock32'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4,5,safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=32' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, the contents of a properties file can be specified directly from the command-line, using the <code>-pf</code> switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock33'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -pf 'P&gt;=0.5 [ true U&lt;=5 (s=1 &amp; a=0) ]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=33' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The switches <code>-pctl</code> and <code>-csl</code> are aliases for <code>-pf</code>.\n</p>\n<p class='vspace'>Note the use of single quotes (<code>'...'</code>) to avoid characters such as\n<code>(</code> and <code>&gt;</code> being interpreted by the command-line shell.\nSingle quotes are preferable to double quotes since PRISM properties often include double quotes, e.g. for references to labels or properties.\n</p><hr />\n<h1>Approximate Model Checking</h1>\n<p>The discrete-event simulator built into PRISM (see the section \"<a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\") can also be used to generate <em>approximate</em> results for PRISM properties, a technique often called <em>statistical model checking</em>. Essentially, this is achieved by <em>sampling</em>: generating a large number of random paths through the model, evaluating the result of the given properties on each run, and using this information to generate an approximately correct result. This approach is particularly useful on very large models when normal model checking is infeasible. This is because discrete-event simulation is performed using the PRISM language model description, without explicitly constructing the corresponding probabilistic model.\n</p>\n<p class='vspace'>Currently, statistical model checking can only be applied to <code><strong>P</strong></code> or <code><strong>R</strong></code> operators\nand does not support LTL-style path properties or <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\nThere are also a few restrictions on the modelling language features that can be used; see below for details.\n</p>\n<p class='vspace'>To use this functionality, load a model and some properties into PRISM, as described in the previous sections. To generate an approximate value for one or more properties, select them in the list, right-click and select \"Simulate\" (as opposed to \"Verify\"). As usual, it is first necessary to provide values for any undefined constants. Subsequently, a dialog appears. Here, the state from which approximate values are to be computed (i.e. from which the paths will be generated) can be selected. By default, this is the initial state of the model. The other settings in the dialog concern the methods used for simulation.\n</p>\n<p class='vspace'>PRISM supports four different methods for performing statistical model checking:\n</p>\n<div class='vspace'></div><ul><li>CI (Confidence Interval)\n</li><li>ACI (Asymptotic Confidence Interval)\n</li><li>APMC (Approximate Probabilistic Model Checking)\n</li><li>SPRT (Sequential Probability Ratio Test)\n</li></ul><p class='vspace'>The first three of these are intended primarily for \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>quantitative</a>\" properties (e.g. of the form <code><strong>P</strong>=?[...]</code>), but can also be used for \"bounded\" properties (e.g. of the form <code><strong>P</strong>&lt;p[...]</code>). The SPRT method is only applicable to \"bounded\" properties.\n</p>\n<p class='vspace'>Each method has several parameters that control its execution, i.e. the number of samples that are generated and the accuracy of the computed approximation. In most cases, these parameters are inter-related so one of them must be left unspecified and its value computed automatically based on the others. In some cases, this is done before simulation; in others, it must be done afterwards.\n</p>\n<p class='vspace'>Below, we describe each method in more detail.\nFor simplicity, we describe the case of checking a <code><strong>P</strong></code> operator.\nDetails for the case of an <code><strong>R</strong></code> operator can be found in [<a class='wikilink' href='../Main/References.html#Nim10'>Nim10</a>].\n</p>\n<div class='vspace'></div><h3>CI (Confidence Interval) Method</h3>\n<p>The CI method gives a <em>confidence interval</em> for the approximate value generated for a <code><strong>P</strong>=?</code> property, based on a given <em>confidence level</em> and the number of samples generated.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Width\" (<em>w</em>)\n</li><li>\"Confidence\" (<em>alpha</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Let <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated.\nThe confidence interval is [<em>Y-w</em>,<em>Y+w</em>], i.e. <em>w</em> gives the half-width of the interval.\nThe confidence level, which is usually stated as a percentage, is 100(1-<em>alpha</em>)%.\nThis means that the actual value <em>X</em> should fall into the confidence interval [<em>Y-w</em>,<em>Y+w</em>] 100(1-<em>alpha</em>)% of the time.\n</p>\n<p class='vspace'>To determine, for example, the width <em>w</em> for given <em>alpha</em> and <em>N</em>,\nwe use <em>w</em> = <em>q</em> * sqrt(<em>v</em> / <em>N</em>) where\n<em>q</em> is a quantile, for probability 1-<em>alpha</em>/2, from the Student's t-distribution with <em>N</em>-1 degrees of freedom and <em>v</em> is (an estimation of) the variance for <em>X</em>.\nSimilarly, we can determine the required number of iterations, from <em>w</em> and <em>alpha</em>,\nas N = (<em>v</em> * <em>q</em><sup>2</sup>)/<em>w</em><sup>2</sup>, where <em>q</em> and <em>v</em> are as before.\n</p>\n<p class='vspace'>For a bounded property  <code><strong>P</strong>~p[...]</code>, the (Boolean) result is determined according to the generated approximation for the probability. This is not the case, however, if the threshold <em>p</em> falls within the confidence interval [<em>Y-w</em>,<em>Y+w</em>], in which case no value is returned.\n</p>\n<div class='vspace'></div><h3>ACI (Asymptotic Confidence Interval) Method</h3>\n<p>The ACI method works in exactly same fashion as the CI method, except that it uses the Normal distribution to approximate the Student's t-distribution when determining the confidence interval. This is appropriate when the number of samples is large (because we can get a reliable estimation of the variance from the samples) but may be less accurate for small numbers of samples.\n</p>\n<div class='vspace'></div><h3>APMC (Approximate Probabilistic Model Checking) Method</h3>\n<p>The APMC method, based on [<a class='wikilink' href='../Main/References.html#HLMP04'>HLMP04</a>], offers a probabilistic guarantee on the accuracy of the  approximate value generated for a <code><strong>P</strong>=?</code> property, based on the Chernoff-Hoeffding bound.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Approximation\" (<em>epsilon</em>)\n</li><li>\"Confidence\" (<em>delta</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Letting <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated, we have:\n</p>\n<div class='vspace'></div><ul><li>Prob(|<em>Y</em>-<em>X</em>| &gt; <em>epsilon</em>) &lt; <em>delta</em>\n</li></ul><p class='vspace'>where the parameters are related as follows:\n<em>N</em> = ln(2/<em>delta</em>) / 2<em>epsilon</em><sup>2</sup>.\nThis imposes certain restrictions on the parameters,\nnamely that <em>N</em>(<em>epsilon</em><sup>2</sup>) &#8805; ln(2/delta)/2.\n</p>\n<p class='vspace'>In similar fashion to the CI/ACI methods, the APMC method can be also be used for bounded properties such as <code><strong>P</strong>~p[...]</code>, as long as the threshold <em>p</em> falls outside the interval [<em>Y-epsilon</em>,<em>Y+epsilon</em>].\n</p>\n<div class='vspace'></div><h3>SPRT (Sequential Probability Ratio Test) Method</h3>\n<p>The SPRT method is specifically for bounded properties, such as <code><strong>P</strong>~p[...]</code> and is based on <em>acceptance sampling</em> techniques [<a class='wikilink' href='../Main/References.html#YS02'>YS02</a>]. It uses Wald's sequential probability ratio test (SPRT), which generates a succession of samples, deciding on-the-fly when an answer can be given with a sufficiently high confidence.\n</p>\n<p class='vspace'>The parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Indifference\" (<em>delta</em>)\n</li><li>\"Type I/II error\" (<em>alpha</em>/<em>beta</em>)\n</li></ul><p class='vspace'>Consider a property of the form <code><strong>P</strong>&#8805;p[...]</code>. The parameter <em>delta</em> is used as the half-width of an <em>indifference region</em> [p-delta,p+delta]. PRISM will attempt to determine whether either the hypothesis <code><strong>P</strong>&#8805;(p+delta)[...]</code> or <code><strong>P</strong>&#8804;(p-delta)[...]</code> is true, based on which it will return either <code>true</code> or <code>false</code>, respectively. The parameters <em>alpha</em> and <em>beta</em> represent the probability of the occurrence of a <em>type I error</em> (wrongly accepting the first hypothesis) and a <em>type II error</em> (wrongly accepting the second hypothesis), respectively. For simplicity, PRISM assigns the same value to both <em>alpha</em> and <em>beta</em>.\n</p>\n<div class='vspace'></div><h3>Maximum Path Length</h3>\n<p>Another setting that can be configured from the \"Simulation Parameters\" dialog is the maximum length of paths generated by PRISM during statistical model checking. In order to perform statistical model checking, PRISM needs to evaluate the property being checked along every generated path. For example, when checking <code>P=? [ F&lt;=10 \"end\" ]</code>, PRISM must check whether <code>F&lt;=10 \"end\"</code> is true for each path. On this example (assuming a discrete-time model), this can always be done within the first 10 steps. For a property such as <code>P=? [ F \"end\" ]</code>, however, there may be paths along which no finite fragment can show <code>F \"end\"</code> to be true or false. So, PRISM imposes a maximum path length to avoid the need to generate excessively long (or infinite) paths.\nThe default maximum length is 10,000 steps.\nIf, for a given property, statistical model checking results in one or more paths on which the property cannot be evaluated, an error is reported.\n</p>\n<div class='vspace'></div><h3>Command-line Statistical Model Checking</h3>\n<p>Statistical model checking can also be enabled from the command-line version of PRISM, by including the <code>-sim</code> switch. The default methods used are CI (Confidence Interval) for \"quantitative\" properties and SPRT (Sequential Probability Ratio Test) for \"bounded\" properties. To select a particular method, use switch <code>-simmethod &lt;method&gt;</code> where <code>&lt;method&gt;</code> is one of <code>ci</code>, <code>aci</code>, <code>apmc</code> and <code>sprt</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock34'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.pctl -prop 1 -sim -simmethod aci</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=34' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM has default values for the various simulation method parameters, but these can also be specified using the switches <code>-simsamples</code>, <code>-simconf</code>, <code>-simwidth</code> and <code>-simapprox</code>. The exact meaning of these switches for each simulation method is given in the table below.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><strong>CI</strong></td><td  align='center'><strong>ACI</strong></td><td  align='center'><strong>APMC</strong></td><td  align='right'><strong>SPRT</strong></td></tr>\n<tr ><td  align='center'><code>-simsamples</code></td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='right'>n/a</td></tr>\n<tr ><td  align='center'><code>-simconf</code></td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='right'>\"Type I/II error\"</td></tr>\n<tr ><td  align='center'><code>-simwidth</code></td><td  align='center'>\"Width\"</td><td  align='center'>\"Width\"</td><td  align='center'>n/a</td><td  align='right'>\"Indifference\"</td></tr>\n<tr ><td  align='center'><code>-simapprox</code></td><td  align='center'>n/a</td><td  align='center'>n/a</td><td  align='center'>\"Approximation\"</td><td  align='right'>n/a</td></tr>\n</table>\n<p class='vspace'>The maximum length of simulation paths is set with switch <code>-simpathlen</code>.\n</p>\n<div class='vspace'></div><h3>Limitations</h3>\n<p>Currently, the simulator does not support every part of the PRISM modelling languages. For example, it does not handle models with multiple initial states or with <code><strong>system</strong>...<strong>endsystem</strong></code> definitions.\n</p>\n<p class='vspace'>It is also worth pointing out that statistical model checking techniques are not well suited to models that exhibit nondeterminism, such as MDPs. This because the techniques rely on generation of <em>random</em> paths, which are not well defined for a MDP. PRISM does allow statistical model checking to be performed on an MDP, but does so by simply resolving nondeterministic choices in a (uniformly) random fashion (and displaying a warning message). Currently PTAs are not supported by the simulator.\n</p><hr />\n<h1>Computing Steady-state And Transient Probabilities</h1>\n<p>If the model is a CTMC or DTMC, it is possible to compute corresponding vectors of\nsteady-state or transient probabilities directly\n(rather than indirectly by analysing a property which requires their computation).\nFrom the GUI, select an option from the \"Model | Compute\" menu.\nFor transient probabilities, you will be asked to supply the\ntime value for which you wish to compute probabilities.\nFrom the command-line, add the <code>-steadystate</code> (or <code>-ss</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock35'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=35' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for steady-state probabilities or the <code>-transient</code> (or <code>-tr</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock36'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=36' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for transient probabilities, again specifying a time value in the latter case.\nThe probabilities are computed for all states of the model and displayed,\neither on the screen (from the command-line) or in the log (from the GUI).\n</p>\n<p class='vspace'>To instead export the vector of computed probabilities to a file, use the \"Model | Compute/export\" option from the GUI, or the <code>-exportsteadystate</code> (or <code>-exportss</code>) and <code>-exporttransient</code> (or <code>-exporttr</code>) switches from the command-line:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock37'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss -exportss poll2-ss.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=37' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the command-line, you can request that the probability vectors exported are in Matlab format by adding the <code>-exportmatlab</code> switch.\n</p>\n<div class='vspace'></div><h3>Initial probability distributions</h3>\n<p>By default, for both steady-state and transient probability computation,\nPRISM assumes that the initial probability distribution of the model is\nan equiprobable choice over the set of initial states.\nYou can override this and provide a specific initial distribution. This is done using the <code>-importinitdist</code> switch. The format for this imported distribution is identical to the ones exported by PRISM, i.e. simply a list of probabilities for all states separated by new lines. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock38'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -exporttr poll2-tr1.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -importinitdist poll2-tr1.txt -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=38' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is (essentially) equivalent to this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock39'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=39' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Ranges of time values</h3>\n<p>Finally, you can compute transient probabilities for a range of time values, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock40'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 0.1:0.01:0.2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=40' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which computes transient probabilities for the time points 0.1, 0.11, 0.12, .., 0.2. In this case, the computation is done incrementally, with probabilities for each time point being computed from the previous point for efficiency.\n</p><hr />\n<h1>Experiments</h1>\n<p>PRISM supports <em>experiments</em>, which is a way of automating multiple instances of model checking.\nThis is done by leaving one or more <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a> undefined, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock41'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=41' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This can be done for constants in the model file, the properties file, or both.\nBefore any verification can be performed, values must be provided for any such constants. In the GUI, a dialog appears in which the user is required to enter values. From the command line, the <code>-const</code> switch must be used, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock42'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=42' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To run an experiment, provide a <em>range</em> of values for one or more of the constants. Model checking will be performed for all combinations of the constant values provided. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock43'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4:6,T=60:10:100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=43' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>N=4:6</code> means that values of 4,5 and 6 are used for <code>N</code>,\nand <code>T=60:10:100</code> means that values of 60, 70, 80, 90 and 100 (i.e. steps of 10) are used for <code>T</code>.\n</p>\n<p class='vspace'>For convenience, constant specifications can be split across separate instances of the <code>-const</code> switch, if desired.\nYou can also specify double-valued constants as fractions rather than decimals. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock44'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9 -const p=1/3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=44' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, the same thing can be achieved by selecting a single property,\nright clicking on it and selecting \"New experiment\"\n(or alternatively using the popup menu in the \"Experiments\" panel).\nValues or ranges for each undefined constant can then be supplied in the resulting dialog.\nDetails of the new experiment and its progress are shown in the panel.\nTo stop the experiment before it has completed, click the red \"Stop\" button and it will\nhalt after finishing the current iteration of model checking.\nOnce the experiment has finished, right clicking on the experiment produces a pop-up menu,\nfrom which you can view the results of the experiment or export them to a file.\n</p>\n<p class='vspace'>For experiments based on properties which return numerical results, you can also use the GUI to plot graphs of the results.\nThis can be done either before the experiment starts, by selecting the \"Create graph\" tick-box in the dialog used to create the experiment\n(in fact this box is ticked by default), or after the experiment's completion, by choosing \"Plot results\" from the pop-up menu on the experiment.\nA dialog appears, where you can choose which constant (if there are more than one) to use for the x-axis of the graph,\nand for which values of any other constants the results should be plotted.\nThe graph will appear in the panel below the list of experiments.\nRight clicking on a graph and selecting \"Graph options\" brings up a dialog from which many properties of the graph can be configured.\nFrom the pop-up menu of a graph, you can also choose to print the graph (to a printer or Postscript file)\nor export it in a variety of formats:\nas an image (PNG or JPEG),\nas an encapsulated Postscript file (EPS),\nin an XML-based format (for reloading back into PRISM),\nor as code which can be used to generate the graph in Matlab.\n</p>\n<p class='vspace'>Approximate computation of quantitive results obtained with the <a class='wikilink' href='ApproximateModelChecking.html'>simulator</a> can also be used on experiments. In the GUI, select the \"Use Simulation\" option when defining the parameters for the experiment. From the command-line, just add the <code>-sim</code> switch as usual.\n</p>\n<p class='vspace'><a name='exportresults' id='exportresults'></a>\n</p><h3>Exporting results</h3>\n<p>You can export all the results from an experiment to a file or to the screen. From the command-line, use the <code>-exportresults</code> switch, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock45'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=45' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send to output file <code>res.txt</code>, or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock46'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=46' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send the results straight to the screen. From the GUI, right click on the experiment and select \"Export results\".\n</p>\n<p class='vspace'>The default behaviour is to export a <em>list</em> of results in <em>text</em> form, using tabs to separate items. The above examples produce:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock47'>\r\n  <div class='sourceblocktext'><div class=\"text\">N &nbsp; &nbsp; &nbsp; T &nbsp; &nbsp; &nbsp; Result<br />\n4 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n4 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 4.707364688019771E-6<br />\n4 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 1.3126420636755292E-5<br />\n5 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n5 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 3.267731327728599E-6<br />\n5 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=47' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can change the format in which the results are exported by appending one or more comma-separated options to the end of the <code>-exportresults</code> switch, for example to export in CSV (comma-separated values) format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock48'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=48' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock49'>\r\n  <div class='sourceblocktext'><div class=\"text\">N, T, Result<br />\n4, 0, 0.0<br />\n4, 10, 4.707364688019771E-6<br />\n4, 20, 1.3126420636755292E-5<br />\n5, 0, 0.0<br />\n5, 10, 3.267731327728599E-6<br />\n5, 20, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=49' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock50'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:dataframe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=50' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock51'>\r\n  <div class='sourceblocktext'><div class=\"text\">N,T,Result<br />\n4,0,0<br />\n4,10,4.70736468802e-06<br />\n4,20,1.31264206368e-05<br />\n5,0,0<br />\n5,10,3.26773132773e-06<br />\n5,20,8.34357506036e-06</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=51' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also add the <code>matrix</code> option, to export the results as one or more 2D matrices, rather than a list.\nThis is particularly useful if you want to create a surface plot from results that vary over two constants.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock52'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv,matrix</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=52' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock53'>\r\n  <div class='sourceblocktext'><div class=\"text\">&quot;N\\T&quot;<br />\n, 0.0, 10.0, 20.0<br />\n4, 0.0, 4.707364688019771E-6, 1.3126420636755292E-5<br />\n5, 0.0, 3.267731327728599E-6, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=53' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>matrix</code> option is also available in normal (non-CSV) mode.\n</p>\n<p class='vspace'>You can also export results in the form of comments, used by PRISM's <a class='urllink' href='https://github.com/prismmodelchecker/prism/wiki/Regression-Testing'>regression testing</a> functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock54'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:comment</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=54' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock55'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// RESULT (N=4,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=10): 4.707364688019771E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=20): 1.3126420636755292E-5</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=10): 3.267731327728599E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=20): 8.343575060356386E-6</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=55' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, it is also possible to <em>import</em> previously exported results (in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format).\n</p>\n<p class='vspace'>A related option is the <code>-exportvector &lt;file&gt;</code> switch, useful in general contexts, not for experiments.\nThis exports the results for all states of the model\n(typically, the log just displays the result for the initial state, unless a <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> has been used)\nto the the file <code>file</code>.\n</p><hr />\n<h1>Strategies</h1>\n<p>Properties to be model checked on MDPs (and their variants, such as POMDPs or IMDPs) usually quantify over <em>strategies</em> (or <em>policies</em>) of the model, i.e., over the different possible ways that nondeterminism can be resolved in the model.\nFor example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock56'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=56' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>determines the maximum probability, over all strategies, of reaching a state satisfying the label <code>\"goal\"</code>. When checking such properties, you can also ask PRISM to generate a corresponding (optimal) strategy, which yields this maximum probability when followed. The strategy can then be viewed, exported or simulated.\n</p>\n<p class='vspace'><strong>Note:</strong> For consistency across models, PRISM now uses the terminology <em>strategy</em> (rather than alternatives such as <em>policy</em>). In older versions of the tool, these were referred to as <em>adversaries</em>. Currently, the newer (and more extensive) <em>strategy generation</em> functionality is implemented just for the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>\"explicit\"</a> model checking engine,\nwhich is used automatically if strategy generation is requested.\nThe old <em>adversary generation</em> functionality (see below) still exists for the \"sparse\" engine, but will be updated in the future.\n</p>\n<p class='vspace'><strong>Generating strategies</strong>. Optimal strategies can be generated either from the command-line or the graphical user interface (GUI). For the former, use the <code>-exportstrat</code> switch. Simple examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock57'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat stdout</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.tra</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=57' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, you can trigger strategy generation by ticking the \"Generate strategy\" box either on the popup menu that appears when you right-click a property, or from the \"Strategies\" menu at the top. As long as it is supported, a strategy will be then generated once \"Verify\" is clicked.\n</p>\n<p class='vspace'>From the same menu(s), you can then\n</p>\n<div class='vspace'></div><ul><li>export the strategy to a file\n</li><li>view the strategy by printing it in the log\n</li><li>explore the strategy in the simulator\n</li></ul><p class='vspace'><strong>Strategy export types</strong>. Strategies can be viewed or exported in several different formats:\n</p>\n<p class='vspace'>(i) <em>Action list</em>. This is a list of the action taken in each state of the model, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock58'>\r\n  <div class='sourceblocktext'><div class=\"text\">(0,0):east<br />\n(0,1):north<br />\n(0,2):north<br />\n(1,0):south<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=58' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where states, by default, are shown as a tuple of variable values.\n</p>\n<p class='vspace'>(ii) <em>Induced model</em>. This is a representation of the model that is induced when the strategy is applied. There are two \"modes\" for this export. The first (and default) is \n<em>reduce</em>, which removes the nondeterminism resolved by the strategy (e.g., an MDP becomes a DTMC). This can be useful to re-import the model back into PRISM and analyse the induced model. The second is <em>restrict</em>, which shows the original model but with a restricted set of choices (e.g., an MDP with just one choice in each state). In each case, the transitions of the induced model are presented as a <code>.tra</code> file (as for normal <a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>model export</a>), e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock59'>\r\n  <div class='sourceblocktext'><div class=\"text\">9 11<br />\n0 5 1 east<br />\n1 10 1 north<br />\n2 15 0.9 north<br />\n2 16 0.1 north<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=59' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>(iii) <em>Dot file</em>. This is, like the previous format, a view of the model induced by the strategy, but in <a class='urllink' href='http://www.graphviz.org'>Dot</a> format, which allows it to be visualised.\n</p>\n<p class='vspace'><strong>Configuring strategy export</strong>. \nAs hinted in the command-line examples above, the <code>-exportstrat</code> switch uses the file extension to determine the preferred format: if the strategy is exported to a file with extension <code>.tra</code> or <code>.dot</code>, then it uses an induced model or Dot file, respectively. Otherwise, the default is an action list. You can specify the desired format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock60'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=actions</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=60' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Further options can be added, e.g., to specify whether an induced model is exported in \"restrict\" or \"reduce\" mode:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock61'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced,mode=restrict</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=61' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A full list of available options is as follows:\n</p>\n<div class='vspace'></div><ul><li><code>type</code> (<code>actions</code>, <code>induced</code> or <code>dot</code>): the type of strategy export to use (action list, induced model or Dot file)\n</li><li><code>mode</code> (<code>restrict</code> or <code>reduce</code>): when exporting as an induced model or Dot file, whether to \"restrict\" or \"reduce\" the model (see above); the default is \"restrict\"\n</li><li><code>reach</code> (<code>true</code> or <code>false</code>): whether to restrict the strategy to states that are reachable when it is applied to the model (this is currently only used for exporting induced models and Dot files, and the default value is false and true, respectively, in these two cases)\n</li><li><code>states</code> (<code>true</code> or <code>false</code>): whether to show states, rather than state indices, for actions lists or Dot files; this is true by default\n</li><li><code>obs</code> (<code>true</code> or <code>false</code>): for partially observable models, whether to merge observationally equivalent states; this is true by default\n</li></ul><p class='vspace'><strong>Strategy types</strong>. PRISM generates several types of strategies. The simplest are <em>memoryless deterministic</em> strategies, which pick a single action in each state, as in the examples above. For some query types (e.g., step-bounded properties, or LTL-based properties), <em>finite-memory</em> strategies are generated, where an additional memory value is used. For these, induced models or Dot files are most useful since they will also show how the memory values are updated as the strategy is executed. Note that, in these cases, the state indices of the strategy will correspond to the product model constructed during model checking, not the original model. The product model can be exported using the <code>-exportprodtrans</code> and <code>-exportprodstates</code> switches.\n</p>\n<p class='vspace'><strong>Adversary generation</strong>. As mentioned above, the \"sparse\" model checking engine still includes older so-called \"adversary generation\" functionality. This can be used to export the induced model to a file using the <code>-exportadv</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock62'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadv adv.tra -s</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadvmdp adv.tra -s</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=62' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where the <code>-exportadv</code> and <code>-exportadvmdp</code> export a DTMC and an MDP, respectively, i.e., corresponding to the \"reduce\" and \"restrict\" modes described above.\nFrom the GUI, change the \"Adversary export\" option (under the \"PRISM\" settings) from \"None\" to \"DTMC\" or \"MDP\". You can also change the filename for the export adversary which, by default, is <code>adv.tra</code> as in the example above.\n</p><hr />\n<h1>Support For PEPA Models</h1>\n<p>For CTMCs, PRISM also accepts model descriptions in the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='../Main/References.html#Hil96'>Hil96</a>].\nThe tool compiles such descriptions into the PRISM language and then constructs the model as normal.\nThe language accepted by the PEPA to PRISM compiler is actually a subset of PEPA.\nThe restrictions applied to the language are firstly that component identifiers can only be bound to sequential components\n(formed using prefix and choice and references to other sequential components only).\nSecondly, each local state of a  sequential component must be named.  For example, we would rewrite:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).(b,s).P;\n</li></ul><p class='vspace'>as:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).P';\n</li><li>P' = (b,s).P;\n</li></ul><p class='vspace'>Finally, active/active synchronisations are not allowed since the PRISM \ndefinition of these differs from the PEPA definition.  Every PEPA \nsynchronisation must have exactly one active component.\nSome examples of PEPA model descriptions which can be imported into PRISM\ncan be found in the <code>prism-examples/pepa</code> directory.\n</p>\n<p class='vspace'>From the command-line version of PRISM, add the <code>-importpepa</code> switch and the model will be treated as a PEPA description.\nFrom the GUI, select \"Model | Open model\" and then choose \"PEPA models\"\non the \"Files of type\" drop-down menu.\nAlternatively, select \"Model | New | PEPA model\" and either type a description from scratch\nor paste in an existing one from elsewhere.\nOnce the PEPA model has been successfully parsed by PRISM,\nyou can view the corresponding PRISM code (as generated by the PEPA-to-PRISM compiler)\nby selecting menu option \"Model | View | Parsed PRISM model\".\n</p><hr />\n<h1>Support For SBML</h1>\n<p>PRISM includes a (prototype) tool to translate specifications in <a class='urllink' href='http://sbml.org/'>SBML</a> (Systems Biology Markup Language) to model descriptions in the PRISM language. SBML is an XML-based format for representing models of biochemical reaction networks. The translator currently works with Level 2 Version 1 of the SBML specification, details of which can be found <a class='urllink' href='http://sbml.org/documents/'>here</a>.\n</p>\n<p class='vspace'>Since PRISM is a tool for analysing discrete-state systems, the translator is designed for SBML files intended for discrete stochastic simulation. A useful set of such files can be found in the CaliBayes <a class='urllink' href='http://code.google.com/p/dsmts/'>Discrete Stochastic Model Test Suite</a>. There are also many more SBML files available in the <a class='urllink' href='http://www.ebi.ac.uk/biomodels/'>BioModels Database</a>.\n</p>\n<p class='vspace'>We first give a simple example of an SBML file and its PRISM translation. We then give some more precise details of the translation process.\n</p>\n<div class='vspace'></div><h3>Example</h3>\n<p>An SBML file comprises a set of <em>species</em> and a set of <em>reactions</em> which they undergo. Below is the SBML file for the simple reversible reaction: <strong>Na + Cl &#8596; Na<sup>+</sup> + Cl<sup>-</sup></strong>, where there are initially 100 Na and Cl atoms and no ions, and the base rates for the forwards and backwards reactions are 100 and 10, respectively.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock63'>\r\n  <div class='sourceblocktext'><div class=\"xml\"><span class=\"re1\">&lt;?xml</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1.0&quot;</span> <span class=\"re0\">encoding</span>=<span class=\"st0\">&quot;UTF-8&quot;</span><span class=\"re2\">?&gt;</span><br />\n<span class=\"re1\">&lt;sbml</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.sbml.org/sbml/level2&quot;</span> <span class=\"re0\">metaid</span>=<span class=\"st0\">&quot;_000000&quot;</span> <span class=\"re0\">level</span>=<span class=\"st0\">&quot;2&quot;</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; <span class=\"re1\">&lt;model</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;nacl&quot;</span> <span class=\"re0\">name</span>=<span class=\"st0\">&quot;Na+Cl&quot;</span><span class=\"re2\">&gt;</span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;compartment</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;compartment&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na_plus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl_minus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactions<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>forwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;100&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>backwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na_plus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl_minus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;10&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactions<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; <span class=\"re1\">&lt;/model<span class=\"re2\">&gt;</span></span><br />\n<span class=\"re1\">&lt;/sbml<span class=\"re2\">&gt;</span></span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=63' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And here is the resulting PRISM code:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock64'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// File generated by automatic SBML-to-PRISM conversion</span><br/>\n<span class=\"prismcomment\">// Original SBML file: nacl.xml</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">MAX_AMOUNT</span> = <span class=\"prismnum\">100</span>;<br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction forwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">forwards_rate</span> = <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// forwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction backwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">backwards_rate</span> = <span class=\"prismnum\">10</span>; <span class=\"prismcomment\">// backwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na</span><br/>\n<br/>\n\t<span class=\"prismident\">na</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">na</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na</span> &lt;= <span class=\"prismident\">na_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl</span><br/>\n<br/>\n\t<span class=\"prismident\">cl</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">cl</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl</span> &lt;= <span class=\"prismident\">cl_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na_plus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_plus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na_plus</span><br/>\n<br/>\n\t<span class=\"prismident\">na_plus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_plus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na_plus</span> &lt;= <span class=\"prismident\">na_plus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">na_plus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl_minus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_minus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl_minus</span><br/>\n<br/>\n\t<span class=\"prismident\">cl_minus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_minus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl_minus</span> &lt;= <span class=\"prismident\">cl_minus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">cl_minus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reaction rates</span><br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">reaction_rates</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reward structures (one per species)</span><br/>\n<br/>\n<span class=\"prismcomment\">// 1</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 2</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 3</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na_plus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na_plus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 4</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl_minus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl_minus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=64' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the latter, we can use PRISM to generate a simple plot of the expected amount of Na and Na+ over time (using both model checking and a single random trace from the simulator):\n</p>\n<div class='vspace'></div><div class='img imgcaption'><a class='urllink' href='../uploads/sbml_ex_graph.png'><img src='../uploads/sbml_ex_graph.png' alt='' /></a><br /><span class='caption'><strong>Expected amount of Na/Na+ at time T</strong></span></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Using the translator</h3>\n<p>At present, the SBML-to-PRISM translator is included in the PRISM code-base, but not integrated into the application itself.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock65'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=65' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are using a binary (rather than source code) distribution of PRISM, replace <code>classes</code> with <code>lib/prism.jar</code> in the above.\n</p>\n<p class='vspace'>Alternatively (on Linux or Mac OS X), ensure <code>prism</code> is in your path and then save the script below as an executable file called <code>sbml2prism</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock66'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#!/bin/sh</span><br />\n<br />\n<span class=\"co0\"># Startup script for SBML-to-PRISM translator</span><br />\n<br />\n<span class=\"co0\"># Launch using main PRISM script</span><br />\n<span class=\"re2\">PRISM_MAINCLASS</span>=<span class=\"st0\">&quot;prism.SBML2Prism&quot;</span><br />\n<span class=\"kw3\">export</span> PRISM_MAINCLASS<br />\nprism <span class=\"st0\">&quot;$@&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=66' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Then use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock67'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">sbml2prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=67' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The following PRISM properties file will also be useful:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock68'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">c</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismident\">c</span>}=? [<span class=\"prismkeyword\">I</span>=<span class=\"prismident\">T</span>]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=68' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This contains a single property which, based on the reward structures in the PRISM model generated by the translator, means \"the expected amount of species <em>c</em> at time <em>T</em>\". The constant <em>c</em> is an integer index which can range between 1 and <em>N</em>, where <em>N</em> is the number of species in the model. To view the expected amount of each species over time, create an <a class='wikilink' href='Experiments.html'>experiment</a> in PRISM which varies <em>c</em> from 1 to <em>N</em> and <em>T</em> over the desired time range.\n</p>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Details of the translation</h3>\n<p>The basic structure of the translation process is as follows:\n</p>\n<div class='vspace'></div><ul><li>Each <em>species</em> in the SBML file is represented by a <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>module</a> in the resulting PRISM file. This module, which (where possible) retains the SBML species id as its name, contains a single <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variable</a> whose value represents the amount of the species present. A corresponding <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structure</a> for computing the expected amount of the species at a given time instant is also created. Species for which the <code>boundaryCondition</code> flag is set to <code>true</code> in the SBML file do not have a corresponding module.\n<div class='vspace'></div></li><li>Each <em>reaction</em> in the SBML file is associated with a unique <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation action label</a>. The module for each species which takes part in the reaction will include a synchronous <a class='wikilink' href='../ThePRISMLanguage/Commands.html'>command</a> to represent this. An additional PRISM module called <code>reaction_rates</code> stores the expression representing the rate of each reaction (from the corresponding <code>kineticLaw</code> section in the SBML file). Reaction stoichiometry information is respected but must be provided in the scalar <code>stoichiometry</code> field of a <code>speciesReference</code> element, not in a separate <code>StoichiometryMath</code> element.\n<div class='vspace'></div></li><li>Each <em>parameter</em> in the SBML file, either global to the file or specific to a reaction, becomes a <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constant</a> in the PRISM file. If a value for this parameter is given, it used. If not, the constant is left as undefined.\n</li></ul><p class='vspace'>As described above, this translation process is designed for discrete systems and so the amount of each species in the model is represented by an integer variable. It is therefore assumed that the initial amount for each species specified in the SBML file is also given as an integer. If this is not the case, then the values will need to be scaled accordingly first.\n</p>\n<p class='vspace'>Furthermore, since PRISM is primarily a model checking (rather than simulation) tool, it is important that the amount of each species also has an upper bound (to ensure a finite state space). When model checking, the efficiency (or even feasibility) of the process is likely to be very sensitive to the upper bound(s) chosen. When using the discrete-event simulation functionality of PRISM, this is not the case and the bounds can can be set much higher. By default the translator uses an upper bound of 100 (which is increased if the initial amount exceeds this). A different value can specified through a second command-line argument as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock69'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml 1000 &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=69' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, upper bounds can be modified manually after the translation process.\n</p>\n<p class='vspace'>Finally, The following aspects of SBML files are not currently supported and are ignored during the translation process:\n</p>\n<div class='vspace'></div><ul><li>compartments\n</li><li>events/triggers\n</li></ul><hr />\n<h1>Explicit Model Import</h1>\n<p>It is also possible to construct models in PRISM through direct specification of their transition matrix.\nTwo formats for explicit model import are currently supported:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \"<code>.tra</code>\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li></ul><p class='vspace'>Presently, this functionality is only supported in the command-line version of the tool, usually using the <code>-importmodel</code> switch.\nIn a similar fashion to <code>-exportmodel</code> switch, the type of import is usually determined from the file extension.\n</p>\n<p class='vspace'>For UMB, all model info is contained in a single file. An example of import is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock70'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=70' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For the plain text files (<code>.tra</code> etc.), various options are possible.\nTo just import the core part of the model (the transition function) use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock71'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=71' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM tries to determine the model type from the format of the <code>.tra</code> file,\nbut if this does not work, the model type can be overwritten using the <code>-dtmc</code>, <code>-ctmc</code> and <code>-mdp</code> switches.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock72'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=72' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Using the same formats as for <a class='wikilink' href='ExportingTheModel.html'>model export</a>, other parts of the model can also be imported:\n</p>\n<div class='vspace'></div><ul><li><code>.lab</code> - labels\n</li><li><code>.srew</code>, <code>.trew</code> - rewards: states, transitions\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>Here is an example of also importing labels and states:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock73'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra,sta,lab</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=73' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If state information is not imported, a single zero-indexed variable <code>x</code> is assumed.\n</p>\n<p class='vspace'>Note also that, since details about the initial state(s) of a model are not preserved in the <code>.tra</code> file,\nbut are included in the labels file, this should also be used to designate a particular initial state for a model.\nOtherwise, state 0 is assumed to be the initial state or,\nif state information is imported, the state in which all variables take their minimum value is used.\n</p>\n<p class='vspace'>Use the extension <code>.all</code> to import from any matching files with appropriate extensions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock74'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=74' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this case, you can omit the <code>-importmodel</code> switch and just specify the <code>.all</code>-ended filename, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock75'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=75' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Efficiency</h3>\n<p>Please note, for PRISM's symbolic model construction/engines, which are often used by default,\nthis explicit method of constructing models in PRISM is typically less efficient than using the PRISM language.\nThis is because the underlying data structures used to represent the model\nfunction better when there is high-level structure and regularity to exploit.\nYou may want to switch to the \"explicit\" engine:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock76'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=76' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The situation can also be alleviated to a certain extent for the symbolic implementations by importing\nthe <code>.sta</code> file, since the composition of the states reintroduces some regularity\n(although is still typically inefficient to construct).\n</p>\n<p class='vspace'>\n</p><h3>Other options</h3>\n<p>In a similar style to PRISM's <a class='wikilink' href='ExportingTheModel.html'><code>-exportmodel</code></a> switch, while <code>-importmodel</code> is usually the most convenient, you can also specify each part separately, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock77'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importtrans poll2.tra -importstates poll2.sta -importlabels poll2.lab -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/AllOnOnePage?action=sourceblock&amp;num=77' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>There are also <code>-importstaterewards</code> and <code>-impottransrewards</code> switches.\nYou can import multiple reward structures using multiple instances of the these switches.\nIf present in the rewards files (see the appendix \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\"),\nthe names of the reward structures are read too.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ApproximateModelChecking.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Statistical Model Checking \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ApproximateModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='StatisticalModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Statistical Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The discrete-event simulator built into PRISM (see the section \"<a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\") can also be used to generate <em>approximate</em> results for PRISM properties, a technique often called <em>statistical model checking</em>. Essentially, this is achieved by <em>sampling</em>: generating a large number of random paths through the model, evaluating the result of the given properties on each run, and using this information to generate an approximately correct result. This approach is particularly useful on very large models when normal model checking is infeasible. This is because discrete-event simulation is performed using the PRISM language model description, without explicitly constructing the corresponding probabilistic model.\n</p>\n<p class='vspace'>Currently, statistical model checking can only be applied to <code><strong>P</strong></code> or <code><strong>R</strong></code> operators\nand does not support LTL-style path properties or <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\nThere are also a few restrictions on the modelling language features that can be used; see below for details.\n</p>\n<p class='vspace'>To use this functionality, load a model and some properties into PRISM, as described in the previous sections. To generate an approximate value for one or more properties, select them in the list, right-click and select \"Simulate\" (as opposed to \"Verify\"). As usual, it is first necessary to provide values for any undefined constants. Subsequently, a dialog appears. Here, the state from which approximate values are to be computed (i.e. from which the paths will be generated) can be selected. By default, this is the initial state of the model. The other settings in the dialog concern the methods used for simulation.\n</p>\n<p class='vspace'>PRISM supports four different methods for performing statistical model checking:\n</p>\n<div class='vspace'></div><ul><li>CI (Confidence Interval)\n</li><li>ACI (Asymptotic Confidence Interval)\n</li><li>APMC (Approximate Probabilistic Model Checking)\n</li><li>SPRT (Sequential Probability Ratio Test)\n</li></ul><p class='vspace'>The first three of these are intended primarily for \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>quantitative</a>\" properties (e.g. of the form <code><strong>P</strong>=?[...]</code>), but can also be used for \"bounded\" properties (e.g. of the form <code><strong>P</strong>&lt;p[...]</code>). The SPRT method is only applicable to \"bounded\" properties.\n</p>\n<p class='vspace'>Each method has several parameters that control its execution, i.e. the number of samples that are generated and the accuracy of the computed approximation. In most cases, these parameters are inter-related so one of them must be left unspecified and its value computed automatically based on the others. In some cases, this is done before simulation; in others, it must be done afterwards.\n</p>\n<p class='vspace'>Below, we describe each method in more detail.\nFor simplicity, we describe the case of checking a <code><strong>P</strong></code> operator.\nDetails for the case of an <code><strong>R</strong></code> operator can be found in [<a class='wikilink' href='../Main/References.html#Nim10'>Nim10</a>].\n</p>\n<div class='vspace'></div><h3>CI (Confidence Interval) Method</h3>\n<p>The CI method gives a <em>confidence interval</em> for the approximate value generated for a <code><strong>P</strong>=?</code> property, based on a given <em>confidence level</em> and the number of samples generated.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Width\" (<em>w</em>)\n</li><li>\"Confidence\" (<em>alpha</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Let <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated.\nThe confidence interval is [<em>Y-w</em>,<em>Y+w</em>], i.e. <em>w</em> gives the half-width of the interval.\nThe confidence level, which is usually stated as a percentage, is 100(1-<em>alpha</em>)%.\nThis means that the actual value <em>X</em> should fall into the confidence interval [<em>Y-w</em>,<em>Y+w</em>] 100(1-<em>alpha</em>)% of the time.\n</p>\n<p class='vspace'>To determine, for example, the width <em>w</em> for given <em>alpha</em> and <em>N</em>,\nwe use <em>w</em> = <em>q</em> * sqrt(<em>v</em> / <em>N</em>) where\n<em>q</em> is a quantile, for probability 1-<em>alpha</em>/2, from the Student's t-distribution with <em>N</em>-1 degrees of freedom and <em>v</em> is (an estimation of) the variance for <em>X</em>.\nSimilarly, we can determine the required number of iterations, from <em>w</em> and <em>alpha</em>,\nas N = (<em>v</em> * <em>q</em><sup>2</sup>)/<em>w</em><sup>2</sup>, where <em>q</em> and <em>v</em> are as before.\n</p>\n<p class='vspace'>For a bounded property  <code><strong>P</strong>~p[...]</code>, the (Boolean) result is determined according to the generated approximation for the probability. This is not the case, however, if the threshold <em>p</em> falls within the confidence interval [<em>Y-w</em>,<em>Y+w</em>], in which case no value is returned.\n</p>\n<div class='vspace'></div><h3>ACI (Asymptotic Confidence Interval) Method</h3>\n<p>The ACI method works in exactly same fashion as the CI method, except that it uses the Normal distribution to approximate the Student's t-distribution when determining the confidence interval. This is appropriate when the number of samples is large (because we can get a reliable estimation of the variance from the samples) but may be less accurate for small numbers of samples.\n</p>\n<div class='vspace'></div><h3>APMC (Approximate Probabilistic Model Checking) Method</h3>\n<p>The APMC method, based on [<a class='wikilink' href='../Main/References.html#HLMP04'>HLMP04</a>], offers a probabilistic guarantee on the accuracy of the  approximate value generated for a <code><strong>P</strong>=?</code> property, based on the Chernoff-Hoeffding bound.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Approximation\" (<em>epsilon</em>)\n</li><li>\"Confidence\" (<em>delta</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Letting <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated, we have:\n</p>\n<div class='vspace'></div><ul><li>Prob(|<em>Y</em>-<em>X</em>| &gt; <em>epsilon</em>) &lt; <em>delta</em>\n</li></ul><p class='vspace'>where the parameters are related as follows:\n<em>N</em> = ln(2/<em>delta</em>) / 2<em>epsilon</em><sup>2</sup>.\nThis imposes certain restrictions on the parameters,\nnamely that <em>N</em>(<em>epsilon</em><sup>2</sup>) &#8805; ln(2/delta)/2.\n</p>\n<p class='vspace'>In similar fashion to the CI/ACI methods, the APMC method can be also be used for bounded properties such as <code><strong>P</strong>~p[...]</code>, as long as the threshold <em>p</em> falls outside the interval [<em>Y-epsilon</em>,<em>Y+epsilon</em>].\n</p>\n<div class='vspace'></div><h3>SPRT (Sequential Probability Ratio Test) Method</h3>\n<p>The SPRT method is specifically for bounded properties, such as <code><strong>P</strong>~p[...]</code> and is based on <em>acceptance sampling</em> techniques [<a class='wikilink' href='../Main/References.html#YS02'>YS02</a>]. It uses Wald's sequential probability ratio test (SPRT), which generates a succession of samples, deciding on-the-fly when an answer can be given with a sufficiently high confidence.\n</p>\n<p class='vspace'>The parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Indifference\" (<em>delta</em>)\n</li><li>\"Type I/II error\" (<em>alpha</em>/<em>beta</em>)\n</li></ul><p class='vspace'>Consider a property of the form <code><strong>P</strong>&#8805;p[...]</code>. The parameter <em>delta</em> is used as the half-width of an <em>indifference region</em> [p-delta,p+delta]. PRISM will attempt to determine whether either the hypothesis <code><strong>P</strong>&#8805;(p+delta)[...]</code> or <code><strong>P</strong>&#8804;(p-delta)[...]</code> is true, based on which it will return either <code>true</code> or <code>false</code>, respectively. The parameters <em>alpha</em> and <em>beta</em> represent the probability of the occurrence of a <em>type I error</em> (wrongly accepting the first hypothesis) and a <em>type II error</em> (wrongly accepting the second hypothesis), respectively. For simplicity, PRISM assigns the same value to both <em>alpha</em> and <em>beta</em>.\n</p>\n<div class='vspace'></div><h3>Maximum Path Length</h3>\n<p>Another setting that can be configured from the \"Simulation Parameters\" dialog is the maximum length of paths generated by PRISM during statistical model checking. In order to perform statistical model checking, PRISM needs to evaluate the property being checked along every generated path. For example, when checking <code>P=? [ F&lt;=10 \"end\" ]</code>, PRISM must check whether <code>F&lt;=10 \"end\"</code> is true for each path. On this example (assuming a discrete-time model), this can always be done within the first 10 steps. For a property such as <code>P=? [ F \"end\" ]</code>, however, there may be paths along which no finite fragment can show <code>F \"end\"</code> to be true or false. So, PRISM imposes a maximum path length to avoid the need to generate excessively long (or infinite) paths.\nThe default maximum length is 10,000 steps.\nIf, for a given property, statistical model checking results in one or more paths on which the property cannot be evaluated, an error is reported.\n</p>\n<div class='vspace'></div><h3>Command-line Statistical Model Checking</h3>\n<p>Statistical model checking can also be enabled from the command-line version of PRISM, by including the <code>-sim</code> switch. The default methods used are CI (Confidence Interval) for \"quantitative\" properties and SPRT (Sequential Probability Ratio Test) for \"bounded\" properties. To select a particular method, use switch <code>-simmethod &lt;method&gt;</code> where <code>&lt;method&gt;</code> is one of <code>ci</code>, <code>aci</code>, <code>apmc</code> and <code>sprt</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.pctl -prop 1 -sim -simmethod aci</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StatisticalModelChecking?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM has default values for the various simulation method parameters, but these can also be specified using the switches <code>-simsamples</code>, <code>-simconf</code>, <code>-simwidth</code> and <code>-simapprox</code>. The exact meaning of these switches for each simulation method is given in the table below.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><strong>CI</strong></td><td  align='center'><strong>ACI</strong></td><td  align='center'><strong>APMC</strong></td><td  align='right'><strong>SPRT</strong></td></tr>\n<tr ><td  align='center'><code>-simsamples</code></td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='right'>n/a</td></tr>\n<tr ><td  align='center'><code>-simconf</code></td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='right'>\"Type I/II error\"</td></tr>\n<tr ><td  align='center'><code>-simwidth</code></td><td  align='center'>\"Width\"</td><td  align='center'>\"Width\"</td><td  align='center'>n/a</td><td  align='right'>\"Indifference\"</td></tr>\n<tr ><td  align='center'><code>-simapprox</code></td><td  align='center'>n/a</td><td  align='center'>n/a</td><td  align='center'>\"Approximation\"</td><td  align='right'>n/a</td></tr>\n</table>\n<p class='vspace'>The maximum length of simulation paths is set with switch <code>-simpathlen</code>.\n</p>\n<div class='vspace'></div><h3>Limitations</h3>\n<p>Currently, the simulator does not support every part of the PRISM modelling languages. For example, it does not handle models with multiple initial states or with <code><strong>system</strong>...<strong>endsystem</strong></code> definitions.\n</p>\n<p class='vspace'>It is also worth pointing out that statistical model checking techniques are not well suited to models that exhibit nondeterminism, such as MDPs. This because the techniques rely on generation of <em>random</em> paths, which are not well defined for a MDP. PRISM does allow statistical model checking to be performed on an MDP, but does so by simply resolving nondeterministic choices in a (uniformly) random fashion (and displaying a warning message). Currently PTAs are not supported by the simulator.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ApproximateModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='StatisticalModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 05, 2024, at 03:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='selflink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Computing Steady-state And Transient Probabilities \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Computing Steady-state And Transient Probabilities</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>If the model is a CTMC or DTMC, it is possible to compute corresponding vectors of\nsteady-state or transient probabilities directly\n(rather than indirectly by analysing a property which requires their computation).\nFrom the GUI, select an option from the \"Model | Compute\" menu.\nFor transient probabilities, you will be asked to supply the\ntime value for which you wish to compute probabilities.\nFrom the command-line, add the <code>-steadystate</code> (or <code>-ss</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for steady-state probabilities or the <code>-transient</code> (or <code>-tr</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for transient probabilities, again specifying a time value in the latter case.\nThe probabilities are computed for all states of the model and displayed,\neither on the screen (from the command-line) or in the log (from the GUI).\n</p>\n<p class='vspace'>To instead export the vector of computed probabilities to a file, use the \"Model | Compute/export\" option from the GUI, or the <code>-exportsteadystate</code> (or <code>-exportss</code>) and <code>-exporttransient</code> (or <code>-exporttr</code>) switches from the command-line:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss -exportss poll2-ss.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the command-line, you can request that the probability vectors exported are in Matlab format by adding the <code>-exportmatlab</code> switch.\n</p>\n<div class='vspace'></div><h3>Initial probability distributions</h3>\n<p>By default, for both steady-state and transient probability computation,\nPRISM assumes that the initial probability distribution of the model is\nan equiprobable choice over the set of initial states.\nYou can override this and provide a specific initial distribution. This is done using the <code>-importinitdist</code> switch. The format for this imported distribution is identical to the ones exported by PRISM, i.e. simply a list of probabilities for all states separated by new lines. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -exporttr poll2-tr1.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -importinitdist poll2-tr1.txt -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is (essentially) equivalent to this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Ranges of time values</h3>\n<p>Finally, you can compute transient probabilities for a range of time values, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 0.1:0.01:0.2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which computes transient probabilities for the time points 0.1, 0.11, 0.12, .., 0.2. In this case, the computation is done incrementally, with probabilities for each time point being computed from the previous point for efficiency.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 11, 2013, at 09:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Computing Steady-state And Transient Probabilities | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Computing Steady-state And Transient Probabilities</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ComputingSteady-stateAndTransientProbabilities@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 11, 2013, at 09:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Computing Steady-state And Transient Probabilities | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Computing Steady-state And Transient Probabilities</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ComputingSteady-stateAndTransientProbabilities@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=edit.html'>Edit</a> - <a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ComputingSteady-stateAndTransientProbabilities@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 11, 2013, at 09:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='selflink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / ComputingSteady-stateAndTransientProbabilities </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Computing Steady-state And Transient Probabilities</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>If the model is a CTMC or DTMC, it is possible to compute corresponding vectors of\nsteady-state or transient probabilities directly\n(rather than indirectly by analysing a property which requires their computation).\nFrom the GUI, select an option from the \"Model | Compute\" menu.\nFor transient probabilities, you will be asked to supply the\ntime value for which you wish to compute probabilities.\nFrom the command-line, add the <code>-steadystate</code> (or <code>-ss</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for steady-state probabilities or the <code>-transient</code> (or <code>-tr</code>) switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>for transient probabilities, again specifying a time value in the latter case.\nThe probabilities are computed for all states of the model and displayed,\neither on the screen (from the command-line) or in the log (from the GUI).\n</p>\n<p class='vspace'>To instead export the vector of computed probabilities to a file, use the \"Model | Compute/export\" option from the GUI, or the <code>-exportsteadystate</code> (or <code>-exportss</code>) and <code>-exporttransient</code> (or <code>-exporttr</code>) switches from the command-line:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -ss -exportss poll2-ss.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the command-line, you can request that the probability vectors exported are in Matlab format by adding the <code>-exportmatlab</code> switch.\n</p>\n<div class='vspace'></div><h3>Initial probability distributions</h3>\n<p>By default, for both steady-state and transient probability computation,\nPRISM assumes that the initial probability distribution of the model is\nan equiprobable choice over the set of initial states.\nYou can override this and provide a specific initial distribution. This is done using the <code>-importinitdist</code> switch. The format for this imported distribution is identical to the ones exported by PRISM, i.e. simply a list of probabilities for all states separated by new lines. For example, this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -exporttr poll2-tr1.txt</span><br/>\n<span style=\"font-weight:bold;\">prism poll2.sm -tr 1.0 -importinitdist poll2-tr1.txt -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is (essentially) equivalent to this:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 2.0 -exporttr poll2-tr2.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Ranges of time values</h3>\n<p>Finally, you can compute transient probabilities for a range of time values, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -tr 0.1:0.01:0.2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ComputingSteady-stateAndTransientProbabilities?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which computes transient probabilities for the time points 0.1, 0.11, 0.12, .., 0.2. In this case, the computation is done incrementally, with probabilities for each time point being computed from the previous point for efficiency.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/DebuggingModelsWithTheSimulator.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Debugging Models With The Simulator \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=edit.html'>Edit</a> - <a class='wikilink' href='DebuggingModelsWithTheSimulator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Debugging Models With The Simulator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM includes a <em>simulator</em>, a tool which can be used to generate sample paths (executions) through a PRISM model. From the GUI, the simulator allows you to explore a model by interactively generating such paths. This is particularly useful for debugging models during development and for running sanity checks on completed models. Paths can also be generated from the command-line.\n</p>\n<p class='vspace'><a name='gui' id='gui'></a>\n</p><h3>Generating a path in the GUI</h3>\n<p>Once you have loaded a model into the PRISM GUI\n(note that it is not necessary to build the model),\nselect the \"Simulator\" tab at the bottom of the main window.\nYou can now start a new path by double-clicking in the bottom half of the window\n(or right-clicking and selecting \"New path\").\nIf there are undefined constants in the\nmodel (or in any currently loaded properties files) you will be prompted to give values for these. You\ncan also specify the state from which you wish to generate a path. By default, this is the initial state of\nthe model.\n</p>\n<p class='vspace'>The main portion of the user interface (the bottom part) displays a path through the currently loaded model. Initially, this will comprise just a single state. The table above shows the list of available transitions from this state. Double-click one of these to extend the path with this transition. The process can be repeated to extend the path in an interactive fashion. Clicking on any state in the current path shows the transition which was taken at this stage. Click on the final state in the path to continue\nextending the path. Alternatively, clicking the \"Simulate\" button will select a transition randomly (according to the probabilities/rates of the available transitions). By changing the number in the box below this button, you can easily generate random paths of a given length with a single click.\nThere are also options (in the accompanying drop-down menu) to allow generation of paths up until a particular length or, for CTMCs, in terms of the time taken.\n</p>\n<p class='vspace'>The figure shows the simulator in action.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui-sim.png'><img width='500' src='../uploads/gui-sim.png' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI: exploring a model using the simulator</strong></span></div>\n<p class='vspace'>It is also possible to:\n</p>\n<div class='vspace'></div><ul><li>backtrack to an earlier point in a path\n</li><li>remove all of the states before some point in a path\n</li><li>restart a path from its first state\n</li><li>export a path to a text file\n</li></ul><p class='vspace'>Notice that the table containing the path displays not just the value of each variable in each\nstate but also the time spent in that state and any rewards accumulated there. You can configure exactly which columns appear by right-clicking on the path and selecting \"Configure view\". For rewards (and for CTMC models, for the time-values), you can can opt to display the reward/time for each individual state and/or the cumulative total up until each point in the path.\n</p>\n<p class='vspace'>At the top-right of the interface, any labels contained in the currently loaded model/properties file are displayed, along with their value in the currently selected state of the path. In addition, the built-in <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>labels</a> <code>\"init\"</code> and <code>\"deadlock\"</code> are also included. Selecting a label from the list highlights all states in the current path which satisfy it.\n</p>\n<p class='vspace'>The other tabs in this panel allow the value of path operators (taken from properties in the current file) to be viewed for the current path, as well as various other statistics.\n</p>\n<p class='vspace'>Another very useful feature for some models is to use the \"Plot new path\" option from the simulator, which generates a plot of some/all of the variable/reward values for a particular randomly generated path through the model.\n</p>\n<p class='vspace'><a name='cl' id='cl'></a>\n</p><h3>Path generation from the command-line</h3>\n<p>It is also possible to generate random paths through a model using the command-line version of PRISM. This is achieved using the <code>-simpath</code> switch, which requires two arguments, the first describing the path to be generated and the second specifying the file to which the path should be output (as usual, specifying <code>stdout</code> sends output to the terminal). The following examples illustrate the various ways of generating paths in this way:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -simpath 10 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath time=7.5 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath deadlock path.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These generate a path of 10 steps, a path of at least 7.5 time units and a path ending in deadlock, respectively.\n</p>\n<p class='vspace'>Here's an example of the output:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 1 0.007479539729154247 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 2 0.00782819795294666 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 3 0.01570585559933703 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 4 0.017061111948220263 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 5 0.026816317516034468 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 6 0.039878416276337814 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 7 0.04456566315999103 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 8 0.047368359683643765 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 9 0.04934857366557349 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 10 0.055031679365844674 1 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This shows the sequence of states in the path, i.e. the values of the variables in each state. In the example above, there are 4 variables: <code>s</code>, <code>a</code>, <code>s1</code> and <code>s2</code>.\nThe first three columns show the type of transition taken to reach that state, its index within the path (starting from 0) and the time at which it was entered. The latter is only shown for continuous time models. The type of the transition is written as <em>[act]</em> if action label <code>act</code> was taken, and as <em>module1</em> if the module named <code>module1</code> takes an unlabelled transition). \n</p>\n<p class='vspace'>Further options can also be appended to the first parameter. For example, option <code>probs=true</code> also displays the probability/rate associated with each transition. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '5,probs=true' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 1 0.0011880118081395378 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 2 0.0037798355025401888 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 3 0.01029212322894221 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 4 0.023258883912578403 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 5 0.027402404026254504 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this example, the rate is 200.0 for all transitions.\nTo show the state/transition rewards for each step, use option <code>rewards=true</code>.\n</p>\n<p class='vspace'>If you are only interested in values of certain variables of your model, use the <code>vars=(...)</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '500,probs=true,vars=(a,s1,s2)' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 110 0.5025332771499665 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 111 0.5109407735244359 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 112 0.9960642154887506 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station1 0.5 130 1.0645858553472822 0 1 0</span><br/>\n<span style=\"font-style:italic;\">[loop1b] 200.0 132 1.0732572896618477 1 1 0</span><br/>\n<span style=\"font-style:italic;\">[serve1] 1.0 133 2.939742026148121 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 225 3.4311507854807677 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 227 3.434285492243098 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 228 3.553118276800078 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 250 3.6354431222941406 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 251 3.637552738997181 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 252 3.7343375346150576 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of single quotes around the path description argument to prevent the shell from misinterpreting special characters such as \"<code>(</code>\".\n</p>\n<p class='vspace'>Notice also that the above only displays states in which the values of some variable of interest changes. This is achieved with the option <code>changes=true</code>, which is automatically enabled when you use <code>vars=(...)</code>. If you want to see all steps of the path, add the option <code>changes=false</code>.\n</p>\n<p class='vspace'>An alternative way of viewing paths is to only display paths at certain fixed points in time. This is achieved with the <code>snapshot=x</code> option, where <code>x</code> is the time step. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 'time=5.0,snapshot=0.5' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">94 0.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">198 1.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">314 1.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">375 2.0 1 1 1 1</span><br/>\n<span style=\"font-style:italic;\">376 2.5 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">376 3.0 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">378 3.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">378 4.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">478 4.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">511 5.0 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use the <code>sep=...</code> option to specify the column separator. Possible values are <code>space</code> (the default), <code>tab</code> and <code>comma</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '10,vars=(a,b),sep=comma' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step,a,b,time</span><br/>\n<span style=\"font-style:italic;\">0,0,0,0.0</span><br/>\n<span style=\"font-style:italic;\">2,1,0,0.058443536856580006</span><br/>\n<span style=\"font-style:italic;\">3,1,1,0.09281024515535738</span><br/>\n<span style=\"font-style:italic;\">6,1,2,0.2556555786269585</span><br/>\n<span style=\"font-style:italic;\">7,1,3,0.284062896359802</span><br/>\n<span style=\"font-style:italic;\">8,1,4,1.1792064236954896</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When generating paths to a deadlock state, additional <code>repeat=...</code> option is available which will construct multiple paths until a deadlock is found. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath 'deadlock,repeat=100' stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, the simulator detects deterministic loops in paths (e.g. if a path reaches a state from which there is a just a single self-loop leaving that state) and stops generating the path any further. You can disable this behaviour with the <code>loopcheck=false</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">Warning: Deterministic loop detected after 6 steps (use loopcheck=false option to extend path).</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 3</span><br/>\n<span style=\"font-style:italic;\">die 4 7 3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10,loopcheck=false stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 2</span><br/>\n<span style=\"font-style:italic;\">die 4 7 2</span><br/>\n<span style=\"font-style:italic;\">die 5 7 2</span><br/>\n<span style=\"font-style:italic;\">die 6 7 2</span><br/>\n<span style=\"font-style:italic;\">die 7 7 2</span><br/>\n<span style=\"font-style:italic;\">die 8 7 2</span><br/>\n<span style=\"font-style:italic;\">die 9 7 2</span><br/>\n<span style=\"font-style:italic;\">die 10 7 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>One final note: the <code>-simpath</code> switch only generates paths up to the maximum path length setting of the simulator (the default is 10,000). If you want to generate longer paths, either change the\n<a class='wikilink' href='../ConfiguringPRISM/Main.html'>default setting</a> or override it temporarily from the command-line using the <code>-simpathlen</code> switch.\nYou might also use the latter to decrease the setting,\ne.g. to look for a path leading to a deadlock state,\nbut only within 100 steps:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath deadlock stdout -simpathlen 100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=edit.html'>Edit</a> - <a class='wikilink' href='DebuggingModelsWithTheSimulator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 07, 2013, at 09:23 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/DebuggingModelsWithTheSimulator@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Debugging Models With The Simulator | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=edit.html'>Edit</a> - <a class='wikilink' href='DebuggingModelsWithTheSimulator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Debugging Models With The Simulator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='DebuggingModelsWithTheSimulator@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=edit.html'>Edit</a> - <a class='wikilink' href='DebuggingModelsWithTheSimulator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 07, 2013, at 09:23 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/DebuggingModelsWithTheSimulator@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Debugging Models With The Simulator | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=edit.html'>Edit</a> - <a class='wikilink' href='DebuggingModelsWithTheSimulator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Debugging Models With The Simulator</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='DebuggingModelsWithTheSimulator@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>View</a> - <a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=edit.html'>Edit</a> - <a class='wikilink' href='DebuggingModelsWithTheSimulator@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='DebuggingModelsWithTheSimulator@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 07, 2013, at 09:23 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='selflink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/DebuggingModelsWithTheSimulator@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / DebuggingModelsWithTheSimulator </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Debugging Models With The Simulator</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM includes a <em>simulator</em>, a tool which can be used to generate sample paths (executions) through a PRISM model. From the GUI, the simulator allows you to explore a model by interactively generating such paths. This is particularly useful for debugging models during development and for running sanity checks on completed models. Paths can also be generated from the command-line.\n</p>\n<p class='vspace'><a name='gui' id='gui'></a>\n</p><h3>Generating a path in the GUI</h3>\n<p>Once you have loaded a model into the PRISM GUI\n(note that it is not necessary to build the model),\nselect the \"Simulator\" tab at the bottom of the main window.\nYou can now start a new path by double-clicking in the bottom half of the window\n(or right-clicking and selecting \"New path\").\nIf there are undefined constants in the\nmodel (or in any currently loaded properties files) you will be prompted to give values for these. You\ncan also specify the state from which you wish to generate a path. By default, this is the initial state of\nthe model.\n</p>\n<p class='vspace'>The main portion of the user interface (the bottom part) displays a path through the currently loaded model. Initially, this will comprise just a single state. The table above shows the list of available transitions from this state. Double-click one of these to extend the path with this transition. The process can be repeated to extend the path in an interactive fashion. Clicking on any state in the current path shows the transition which was taken at this stage. Click on the final state in the path to continue\nextending the path. Alternatively, clicking the \"Simulate\" button will select a transition randomly (according to the probabilities/rates of the available transitions). By changing the number in the box below this button, you can easily generate random paths of a given length with a single click.\nThere are also options (in the accompanying drop-down menu) to allow generation of paths up until a particular length or, for CTMCs, in terms of the time taken.\n</p>\n<p class='vspace'>The figure shows the simulator in action.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui-sim.png'><img width='500' src='../uploads/gui-sim.png' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI: exploring a model using the simulator</strong></span></div>\n<p class='vspace'>It is also possible to:\n</p>\n<div class='vspace'></div><ul><li>backtrack to an earlier point in a path\n</li><li>remove all of the states before some point in a path\n</li><li>restart a path from its first state\n</li><li>export a path to a text file\n</li></ul><p class='vspace'>Notice that the table containing the path displays not just the value of each variable in each\nstate but also the time spent in that state and any rewards accumulated there. You can configure exactly which columns appear by right-clicking on the path and selecting \"Configure view\". For rewards (and for CTMC models, for the time-values), you can can opt to display the reward/time for each individual state and/or the cumulative total up until each point in the path.\n</p>\n<p class='vspace'>At the top-right of the interface, any labels contained in the currently loaded model/properties file are displayed, along with their value in the currently selected state of the path. In addition, the built-in <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>labels</a> <code>\"init\"</code> and <code>\"deadlock\"</code> are also included. Selecting a label from the list highlights all states in the current path which satisfy it.\n</p>\n<p class='vspace'>The other tabs in this panel allow the value of path operators (taken from properties in the current file) to be viewed for the current path, as well as various other statistics.\n</p>\n<p class='vspace'>Another very useful feature for some models is to use the \"Plot new path\" option from the simulator, which generates a plot of some/all of the variable/reward values for a particular randomly generated path through the model.\n</p>\n<p class='vspace'><a name='cl' id='cl'></a>\n</p><h3>Path generation from the command-line</h3>\n<p>It is also possible to generate random paths through a model using the command-line version of PRISM. This is achieved using the <code>-simpath</code> switch, which requires two arguments, the first describing the path to be generated and the second specifying the file to which the path should be output (as usual, specifying <code>stdout</code> sends output to the terminal). The following examples illustrate the various ways of generating paths in this way:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm -simpath 10 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath time=7.5 path.txt</span><br/>\n<span style=\"font-weight:bold;\">prism model.pm -simpath deadlock path.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These generate a path of 10 steps, a path of at least 7.5 time units and a path ending in deadlock, respectively.\n</p>\n<p class='vspace'>Here's an example of the output:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 1 0.007479539729154247 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 2 0.00782819795294666 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 3 0.01570585559933703 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 4 0.017061111948220263 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 5 0.026816317516034468 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 6 0.039878416276337814 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 7 0.04456566315999103 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 8 0.047368359683643765 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 9 0.04934857366557349 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 10 0.055031679365844674 1 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This shows the sequence of states in the path, i.e. the values of the variables in each state. In the example above, there are 4 variables: <code>s</code>, <code>a</code>, <code>s1</code> and <code>s2</code>.\nThe first three columns show the type of transition taken to reach that state, its index within the path (starting from 0) and the time at which it was entered. The latter is only shown for continuous time models. The type of the transition is written as <em>[act]</em> if action label <code>act</code> was taken, and as <em>module1</em> if the module named <code>module1</code> takes an unlabelled transition). \n</p>\n<p class='vspace'>Further options can also be appended to the first parameter. For example, option <code>probs=true</code> also displays the probability/rate associated with each transition. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '5,probs=true' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 1 0.0011880118081395378 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 2 0.0037798355025401888 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 3 0.01029212322894221 2 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop2a] 200.0 4 0.023258883912578403 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">[loop1a] 200.0 5 0.027402404026254504 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this example, the rate is 200.0 for all transitions.\nTo show the state/transition rewards for each step, use option <code>rewards=true</code>.\n</p>\n<p class='vspace'>If you are only interested in values of certain variables of your model, use the <code>vars=(...)</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '500,probs=true,vars=(a,s1,s2)' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action probability step time a s1 s2</span><br/>\n<span style=\"font-style:italic;\">- - 0 0.0 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 110 0.5025332771499665 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 111 0.5109407735244359 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 112 0.9960642154887506 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station1 0.5 130 1.0645858553472822 0 1 0</span><br/>\n<span style=\"font-style:italic;\">[loop1b] 200.0 132 1.0732572896618477 1 1 0</span><br/>\n<span style=\"font-style:italic;\">[serve1] 1.0 133 2.939742026148121 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 225 3.4311507854807677 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 227 3.434285492243098 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 228 3.553118276800078 0 0 0</span><br/>\n<span style=\"font-style:italic;\">station2 0.5 250 3.6354431222941406 0 0 1</span><br/>\n<span style=\"font-style:italic;\">[loop2b] 200.0 251 3.637552738997181 1 0 1</span><br/>\n<span style=\"font-style:italic;\">[serve2] 1.0 252 3.7343375346150576 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Note the use of single quotes around the path description argument to prevent the shell from misinterpreting special characters such as \"<code>(</code>\".\n</p>\n<p class='vspace'>Notice also that the above only displays states in which the values of some variable of interest changes. This is achieved with the option <code>changes=true</code>, which is automatically enabled when you use <code>vars=(...)</code>. If you want to see all steps of the path, add the option <code>changes=false</code>.\n</p>\n<p class='vspace'>An alternative way of viewing paths is to only display paths at certain fixed points in time. This is achieved with the <code>snapshot=x</code> option, where <code>x</code> is the time step. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath 'time=5.0,snapshot=0.5' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step time s a s1 s2</span><br/>\n<span style=\"font-style:italic;\">0 0.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">94 0.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">198 1.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">314 1.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">375 2.0 1 1 1 1</span><br/>\n<span style=\"font-style:italic;\">376 2.5 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">376 3.0 2 0 0 1</span><br/>\n<span style=\"font-style:italic;\">378 3.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">378 4.0 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">478 4.5 1 0 0 0</span><br/>\n<span style=\"font-style:italic;\">511 5.0 2 0 0 0</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also use the <code>sep=...</code> option to specify the column separator. Possible values are <code>space</code> (the default), <code>tab</code> and <code>comma</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -simpath '10,vars=(a,b),sep=comma' stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">step,a,b,time</span><br/>\n<span style=\"font-style:italic;\">0,0,0,0.0</span><br/>\n<span style=\"font-style:italic;\">2,1,0,0.058443536856580006</span><br/>\n<span style=\"font-style:italic;\">3,1,1,0.09281024515535738</span><br/>\n<span style=\"font-style:italic;\">6,1,2,0.2556555786269585</span><br/>\n<span style=\"font-style:italic;\">7,1,3,0.284062896359802</span><br/>\n<span style=\"font-style:italic;\">8,1,4,1.1792064236954896</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When generating paths to a deadlock state, additional <code>repeat=...</code> option is available which will construct multiple paths until a deadlock is found. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath 'deadlock,repeat=100' stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, the simulator detects deterministic loops in paths (e.g. if a path reaches a state from which there is a just a single self-loop leaving that state) and stops generating the path any further. You can disable this behaviour with the <code>loopcheck=false</code> option. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10 stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">Warning: Deterministic loop detected after 6 steps (use loopcheck=false option to extend path).</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 3</span><br/>\n<span style=\"font-style:italic;\">die 4 7 3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath 10,loopcheck=false stdout</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">action step s d</span><br/>\n<span style=\"font-style:italic;\">- 0 0 0</span><br/>\n<span style=\"font-style:italic;\">die 1 1 0</span><br/>\n<span style=\"font-style:italic;\">die 2 4 0</span><br/>\n<span style=\"font-style:italic;\">die 3 7 2</span><br/>\n<span style=\"font-style:italic;\">die 4 7 2</span><br/>\n<span style=\"font-style:italic;\">die 5 7 2</span><br/>\n<span style=\"font-style:italic;\">die 6 7 2</span><br/>\n<span style=\"font-style:italic;\">die 7 7 2</span><br/>\n<span style=\"font-style:italic;\">die 8 7 2</span><br/>\n<span style=\"font-style:italic;\">die 9 7 2</span><br/>\n<span style=\"font-style:italic;\">die 10 7 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>One final note: the <code>-simpath</code> switch only generates paths up to the maximum path length setting of the simulator (the default is 10,000). If you want to generate longer paths, either change the\n<a class='wikilink' href='../ConfiguringPRISM/Main.html'>default setting</a> or override it temporarily from the command-line using the <code>-simpathlen</code> switch.\nYou might also use the latter to decrease the setting,\ne.g. to look for a path leading to a deadlock state,\nbut only within 100 steps:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.sm -simpath deadlock stdout -simpathlen 100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/DebuggingModelsWithTheSimulator?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Experiments.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Experiments \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Experiments.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Experiments@action=edit.html'>Edit</a> - <a class='wikilink' href='Experiments@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Experiments</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM supports <em>experiments</em>, which is a way of automating multiple instances of model checking.\nThis is done by leaving one or more <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a> undefined, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This can be done for constants in the model file, the properties file, or both.\nBefore any verification can be performed, values must be provided for any such constants. In the GUI, a dialog appears in which the user is required to enter values. From the command line, the <code>-const</code> switch must be used, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To run an experiment, provide a <em>range</em> of values for one or more of the constants. Model checking will be performed for all combinations of the constant values provided. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4:6,T=60:10:100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>N=4:6</code> means that values of 4,5 and 6 are used for <code>N</code>,\nand <code>T=60:10:100</code> means that values of 60, 70, 80, 90 and 100 (i.e. steps of 10) are used for <code>T</code>.\n</p>\n<p class='vspace'>For convenience, constant specifications can be split across separate instances of the <code>-const</code> switch, if desired.\nYou can also specify double-valued constants as fractions rather than decimals. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9 -const p=1/3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, the same thing can be achieved by selecting a single property,\nright clicking on it and selecting \"New experiment\"\n(or alternatively using the popup menu in the \"Experiments\" panel).\nValues or ranges for each undefined constant can then be supplied in the resulting dialog.\nDetails of the new experiment and its progress are shown in the panel.\nTo stop the experiment before it has completed, click the red \"Stop\" button and it will\nhalt after finishing the current iteration of model checking.\nOnce the experiment has finished, right clicking on the experiment produces a pop-up menu,\nfrom which you can view the results of the experiment or export them to a file.\n</p>\n<p class='vspace'>For experiments based on properties which return numerical results, you can also use the GUI to plot graphs of the results.\nThis can be done either before the experiment starts, by selecting the \"Create graph\" tick-box in the dialog used to create the experiment\n(in fact this box is ticked by default), or after the experiment's completion, by choosing \"Plot results\" from the pop-up menu on the experiment.\nA dialog appears, where you can choose which constant (if there are more than one) to use for the x-axis of the graph,\nand for which values of any other constants the results should be plotted.\nThe graph will appear in the panel below the list of experiments.\nRight clicking on a graph and selecting \"Graph options\" brings up a dialog from which many properties of the graph can be configured.\nFrom the pop-up menu of a graph, you can also choose to print the graph (to a printer or Postscript file)\nor export it in a variety of formats:\nas an image (PNG or JPEG),\nas an encapsulated Postscript file (EPS),\nin an XML-based format (for reloading back into PRISM),\nor as code which can be used to generate the graph in Matlab.\n</p>\n<p class='vspace'>Approximate computation of quantitive results obtained with the <a class='wikilink' href='ApproximateModelChecking.html'>simulator</a> can also be used on experiments. In the GUI, select the \"Use Simulation\" option when defining the parameters for the experiment. From the command-line, just add the <code>-sim</code> switch as usual.\n</p>\n<p class='vspace'><a name='exportresults' id='exportresults'></a>\n</p><h3>Exporting results</h3>\n<p>You can export all the results from an experiment to a file or to the screen. From the command-line, use the <code>-exportresults</code> switch, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send to output file <code>res.txt</code>, or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send the results straight to the screen. From the GUI, right click on the experiment and select \"Export results\".\n</p>\n<p class='vspace'>The default behaviour is to export a <em>list</em> of results in <em>text</em> form, using tabs to separate items. The above examples produce:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"text\">N &nbsp; &nbsp; &nbsp; T &nbsp; &nbsp; &nbsp; Result<br />\n4 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n4 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 4.707364688019771E-6<br />\n4 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 1.3126420636755292E-5<br />\n5 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n5 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 3.267731327728599E-6<br />\n5 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can change the format in which the results are exported by appending one or more comma-separated options to the end of the <code>-exportresults</code> switch, for example to export in CSV (comma-separated values) format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"text\">N, T, Result<br />\n4, 0, 0.0<br />\n4, 10, 4.707364688019771E-6<br />\n4, 20, 1.3126420636755292E-5<br />\n5, 0, 0.0<br />\n5, 10, 3.267731327728599E-6<br />\n5, 20, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:dataframe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"text\">N,T,Result<br />\n4,0,0<br />\n4,10,4.70736468802e-06<br />\n4,20,1.31264206368e-05<br />\n5,0,0<br />\n5,10,3.26773132773e-06<br />\n5,20,8.34357506036e-06</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also add the <code>matrix</code> option, to export the results as one or more 2D matrices, rather than a list.\nThis is particularly useful if you want to create a surface plot from results that vary over two constants.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv,matrix</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"text\">&quot;N\\T&quot;<br />\n, 0.0, 10.0, 20.0<br />\n4, 0.0, 4.707364688019771E-6, 1.3126420636755292E-5<br />\n5, 0.0, 3.267731327728599E-6, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>matrix</code> option is also available in normal (non-CSV) mode.\n</p>\n<p class='vspace'>You can also export results in the form of comments, used by PRISM's <a class='urllink' href='https://github.com/prismmodelchecker/prism/wiki/Regression-Testing'>regression testing</a> functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:comment</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// RESULT (N=4,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=10): 4.707364688019771E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=20): 1.3126420636755292E-5</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=10): 3.267731327728599E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=20): 8.343575060356386E-6</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, it is also possible to <em>import</em> previously exported results (in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format).\n</p>\n<p class='vspace'>A related option is the <code>-exportvector &lt;file&gt;</code> switch, useful in general contexts, not for experiments.\nThis exports the results for all states of the model\n(typically, the log just displays the result for the initial state, unless a <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> has been used)\nto the the file <code>file</code>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Experiments.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Experiments@action=edit.html'>Edit</a> - <a class='wikilink' href='Experiments@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Experiments@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 29, 2023, at 10:56 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='selflink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Experiments@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Experiments | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Experiments.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Experiments@action=edit.html'>Edit</a> - <a class='wikilink' href='Experiments@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Experiments</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Experiments@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Experiments.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Experiments@action=edit.html'>Edit</a> - <a class='wikilink' href='Experiments@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Experiments@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 29, 2023, at 10:56 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='selflink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Experiments@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Experiments | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Experiments.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Experiments@action=edit.html'>Edit</a> - <a class='wikilink' href='Experiments@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Experiments</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Experiments@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Experiments.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Experiments@action=edit.html'>Edit</a> - <a class='wikilink' href='Experiments@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Experiments@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 29, 2023, at 10:56 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='selflink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Experiments@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / Experiments </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Experiments</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM supports <em>experiments</em>, which is a way of automating multiple instances of model checking.\nThis is done by leaving one or more <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a> undefined, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This can be done for constants in the model file, the properties file, or both.\nBefore any verification can be performed, values must be provided for any such constants. In the GUI, a dialog appears in which the user is required to enter values. From the command line, the <code>-const</code> switch must be used, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To run an experiment, provide a <em>range</em> of values for one or more of the constants. Model checking will be performed for all combinations of the constant values provided. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4:6,T=60:10:100</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>N=4:6</code> means that values of 4,5 and 6 are used for <code>N</code>,\nand <code>T=60:10:100</code> means that values of 60, 70, 80, 90 and 100 (i.e. steps of 10) are used for <code>T</code>.\n</p>\n<p class='vspace'>For convenience, constant specifications can be split across separate instances of the <code>-const</code> switch, if desired.\nYou can also specify double-valued constants as fractions rather than decimals. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -const N=4,T=85.9 -const p=1/3</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, the same thing can be achieved by selecting a single property,\nright clicking on it and selecting \"New experiment\"\n(or alternatively using the popup menu in the \"Experiments\" panel).\nValues or ranges for each undefined constant can then be supplied in the resulting dialog.\nDetails of the new experiment and its progress are shown in the panel.\nTo stop the experiment before it has completed, click the red \"Stop\" button and it will\nhalt after finishing the current iteration of model checking.\nOnce the experiment has finished, right clicking on the experiment produces a pop-up menu,\nfrom which you can view the results of the experiment or export them to a file.\n</p>\n<p class='vspace'>For experiments based on properties which return numerical results, you can also use the GUI to plot graphs of the results.\nThis can be done either before the experiment starts, by selecting the \"Create graph\" tick-box in the dialog used to create the experiment\n(in fact this box is ticked by default), or after the experiment's completion, by choosing \"Plot results\" from the pop-up menu on the experiment.\nA dialog appears, where you can choose which constant (if there are more than one) to use for the x-axis of the graph,\nand for which values of any other constants the results should be plotted.\nThe graph will appear in the panel below the list of experiments.\nRight clicking on a graph and selecting \"Graph options\" brings up a dialog from which many properties of the graph can be configured.\nFrom the pop-up menu of a graph, you can also choose to print the graph (to a printer or Postscript file)\nor export it in a variety of formats:\nas an image (PNG or JPEG),\nas an encapsulated Postscript file (EPS),\nin an XML-based format (for reloading back into PRISM),\nor as code which can be used to generate the graph in Matlab.\n</p>\n<p class='vspace'>Approximate computation of quantitive results obtained with the <a class='wikilink' href='ApproximateModelChecking.html'>simulator</a> can also be used on experiments. In the GUI, select the \"Use Simulation\" option when defining the parameters for the experiment. From the command-line, just add the <code>-sim</code> switch as usual.\n</p>\n<p class='vspace'><a name='exportresults' id='exportresults'></a>\n</p><h3>Exporting results</h3>\n<p>You can export all the results from an experiment to a file or to the screen. From the command-line, use the <code>-exportresults</code> switch, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send to output file <code>res.txt</code>, or:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>to send the results straight to the screen. From the GUI, right click on the experiment and select \"Export results\".\n</p>\n<p class='vspace'>The default behaviour is to export a <em>list</em> of results in <em>text</em> form, using tabs to separate items. The above examples produce:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"text\">N &nbsp; &nbsp; &nbsp; T &nbsp; &nbsp; &nbsp; Result<br />\n4 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n4 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 4.707364688019771E-6<br />\n4 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 1.3126420636755292E-5<br />\n5 &nbsp; &nbsp; &nbsp; 0 &nbsp; &nbsp; &nbsp; 0.0<br />\n5 &nbsp; &nbsp; &nbsp; 10&nbsp; &nbsp; &nbsp; 3.267731327728599E-6<br />\n5 &nbsp; &nbsp; &nbsp; 20&nbsp; &nbsp; &nbsp; 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can change the format in which the results are exported by appending one or more comma-separated options to the end of the <code>-exportresults</code> switch, for example to export in CSV (comma-separated values) format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"text\">N, T, Result<br />\n4, 0, 0.0<br />\n4, 10, 4.707364688019771E-6<br />\n4, 20, 1.3126420636755292E-5<br />\n5, 0, 0.0<br />\n5, 10, 3.267731327728599E-6<br />\n5, 20, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:dataframe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"text\">N,T,Result<br />\n4,0,0<br />\n4,10,4.70736468802e-06<br />\n4,20,1.31264206368e-05<br />\n5,0,0<br />\n5,10,3.26773132773e-06<br />\n5,20,8.34357506036e-06</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also add the <code>matrix</code> option, to export the results as one or more 2D matrices, rather than a list.\nThis is particularly useful if you want to create a surface plot from results that vary over two constants.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:csv,matrix</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"text\">&quot;N\\T&quot;<br />\n, 0.0, 10.0, 20.0<br />\n4, 0.0, 4.707364688019771E-6, 1.3126420636755292E-5<br />\n5, 0.0, 3.267731327728599E-6, 8.343575060356386E-6</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>matrix</code> option is also available in normal (non-CSV) mode.\n</p>\n<p class='vspace'>You can also export results in the form of comments, used by PRISM's <a class='urllink' href='https://github.com/prismmodelchecker/prism/wiki/Regression-Testing'>regression testing</a> functionality:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism cluster.sm cluster.csl -prop 4 -const N=4:5,T=0:10:20 -exportresults res.txt:comment</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// RESULT (N=4,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=10): 4.707364688019771E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=4,T=20): 1.3126420636755292E-5</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=0): 0.0</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=10): 3.267731327728599E-6</span><br/>\n<span class=\"prismcomment\">// RESULT (N=5,T=20): 8.343575060356386E-6</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Experiments?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, it is also possible to <em>import</em> previously exported results (in <a class='urllink' href='https://pandas.pydata.org/docs/reference/api/pandas.DataFrame.html'>DataFrame</a> format).\n</p>\n<p class='vspace'>A related option is the <code>-exportvector &lt;file&gt;</code> switch, useful in general contexts, not for experiments.\nThis exports the results for all states of the model\n(typically, the log just displays the result for the initial state, unless a <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> has been used)\nto the the file <code>file</code>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ExplicitModelImport.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Explicit Model Import \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExplicitModelImport.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelImport@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Explicit Model Import</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>It is also possible to construct models in PRISM through direct specification of their transition matrix.\nTwo formats for explicit model import are currently supported:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \"<code>.tra</code>\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li></ul><p class='vspace'>Presently, this functionality is only supported in the command-line version of the tool, usually using the <code>-importmodel</code> switch.\nIn a similar fashion to <code>-exportmodel</code> switch, the type of import is usually determined from the file extension.\n</p>\n<p class='vspace'>For UMB, all model info is contained in a single file. An example of import is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For the plain text files (<code>.tra</code> etc.), various options are possible.\nTo just import the core part of the model (the transition function) use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM tries to determine the model type from the format of the <code>.tra</code> file,\nbut if this does not work, the model type can be overwritten using the <code>-dtmc</code>, <code>-ctmc</code> and <code>-mdp</code> switches.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Using the same formats as for <a class='wikilink' href='ExportingTheModel.html'>model export</a>, other parts of the model can also be imported:\n</p>\n<div class='vspace'></div><ul><li><code>.lab</code> - labels\n</li><li><code>.srew</code>, <code>.trew</code> - rewards: states, transitions\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>Here is an example of also importing labels and states:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra,sta,lab</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If state information is not imported, a single zero-indexed variable <code>x</code> is assumed.\n</p>\n<p class='vspace'>Note also that, since details about the initial state(s) of a model are not preserved in the <code>.tra</code> file,\nbut are included in the labels file, this should also be used to designate a particular initial state for a model.\nOtherwise, state 0 is assumed to be the initial state or,\nif state information is imported, the state in which all variables take their minimum value is used.\n</p>\n<p class='vspace'>Use the extension <code>.all</code> to import from any matching files with appropriate extensions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this case, you can omit the <code>-importmodel</code> switch and just specify the <code>.all</code>-ended filename, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Efficiency</h3>\n<p>Please note, for PRISM's symbolic model construction/engines, which are often used by default,\nthis explicit method of constructing models in PRISM is typically less efficient than using the PRISM language.\nThis is because the underlying data structures used to represent the model\nfunction better when there is high-level structure and regularity to exploit.\nYou may want to switch to the \"explicit\" engine:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The situation can also be alleviated to a certain extent for the symbolic implementations by importing\nthe <code>.sta</code> file, since the composition of the states reintroduces some regularity\n(although is still typically inefficient to construct).\n</p>\n<p class='vspace'><a name='other' id='other'></a>\n</p><h3>Other options</h3>\n<p>In a similar style to PRISM's <a class='wikilink' href='ExportingTheModel.html'><code>-exportmodel</code></a> switch, while <code>-importmodel</code> is usually the most convenient, you can also specify each part separately, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importtrans poll2.tra -importstates poll2.sta -importlabels poll2.lab -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>There are also <code>-importstaterewards</code> and <code>-impottransrewards</code> switches.\nYou can import multiple reward structures using multiple instances of the these switches.\nIf present in the rewards files (see the appendix \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\"),\nthe names of the reward structures are read too.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExplicitModelImport.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelImport@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 10:14 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='selflink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ExplicitModelImport@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Explicit Model Import | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExplicitModelImport.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelImport@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Explicit Model Import</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ExplicitModelImport@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExplicitModelImport.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelImport@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 10:14 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='selflink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ExplicitModelImport@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Explicit Model Import | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExplicitModelImport.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelImport@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Explicit Model Import</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ExplicitModelImport@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExplicitModelImport.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=edit.html'>Edit</a> - <a class='wikilink' href='ExplicitModelImport@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExplicitModelImport@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 10:14 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='selflink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ExplicitModelImport@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / ExplicitModelImport </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Explicit Model Import</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>It is also possible to construct models in PRISM through direct specification of their transition matrix.\nTwo formats for explicit model import are currently supported:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \"<code>.tra</code>\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li></ul><p class='vspace'>Presently, this functionality is only supported in the command-line version of the tool, usually using the <code>-importmodel</code> switch.\nIn a similar fashion to <code>-exportmodel</code> switch, the type of import is usually determined from the file extension.\n</p>\n<p class='vspace'>For UMB, all model info is contained in a single file. An example of import is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For the plain text files (<code>.tra</code> etc.), various options are possible.\nTo just import the core part of the model (the transition function) use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM tries to determine the model type from the format of the <code>.tra</code> file,\nbut if this does not work, the model type can be overwritten using the <code>-dtmc</code>, <code>-ctmc</code> and <code>-mdp</code> switches.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Using the same formats as for <a class='wikilink' href='ExportingTheModel.html'>model export</a>, other parts of the model can also be imported:\n</p>\n<div class='vspace'></div><ul><li><code>.lab</code> - labels\n</li><li><code>.srew</code>, <code>.trew</code> - rewards: states, transitions\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>Here is an example of also importing labels and states:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra,sta,lab</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If state information is not imported, a single zero-indexed variable <code>x</code> is assumed.\n</p>\n<p class='vspace'>Note also that, since details about the initial state(s) of a model are not preserved in the <code>.tra</code> file,\nbut are included in the labels file, this should also be used to designate a particular initial state for a model.\nOtherwise, state 0 is assumed to be the initial state or,\nif state information is imported, the state in which all variables take their minimum value is used.\n</p>\n<p class='vspace'>Use the extension <code>.all</code> to import from any matching files with appropriate extensions:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In this case, you can omit the <code>-importmodel</code> switch and just specify the <code>.all</code>-ended filename, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><h3>Efficiency</h3>\n<p>Please note, for PRISM's symbolic model construction/engines, which are often used by default,\nthis explicit method of constructing models in PRISM is typically less efficient than using the PRISM language.\nThis is because the underlying data structures used to represent the model\nfunction better when there is high-level structure and regularity to exploit.\nYou may want to switch to the \"explicit\" engine:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importmodel poll2.tra -ex</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The situation can also be alleviated to a certain extent for the symbolic implementations by importing\nthe <code>.sta</code> file, since the composition of the states reintroduces some regularity\n(although is still typically inefficient to construct).\n</p>\n<p class='vspace'><a name='other' id='other'></a>\n</p><h3>Other options</h3>\n<p>In a similar style to PRISM's <a class='wikilink' href='ExportingTheModel.html'><code>-exportmodel</code></a> switch, while <code>-importmodel</code> is usually the most convenient, you can also specify each part separately, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism -importtrans poll2.tra -importstates poll2.sta -importlabels poll2.lab -ctmc</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExplicitModelImport?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>There are also <code>-importstaterewards</code> and <code>-impottransrewards</code> switches.\nYou can import multiple reward structures using multiple instances of the these switches.\nIf present in the rewards files (see the appendix \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>Explicit Model Files</a>\"),\nthe names of the reward structures are read too.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ExportingTheModel.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Exporting The Model \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExportingTheModel.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=edit.html'>Edit</a> - <a class='wikilink' href='ExportingTheModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Exporting The Model</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>If required, once the model has been constructed, it can be exported, either for manual examination or for use in another tool. The following can all be exported:\n</p>\n<div class='vspace'></div><ul><li>the <strong>transition matrix</strong> (or function);\n</li><li>the <strong>rewards</strong> (state/transition) rewards;\n</li><li>the <strong>labels</strong> (in the <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>model</a> or <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>properties</a>) and the states that satisfy them\n</li><li>the definition of (reachable) <strong>states</strong>, i.e., their variable values\n</li><li>the definition of <strong>observations</strong>, i.e., their observable values, for partially observable models\n</li></ul><p class='vspace'>From the command-line version of PRISM, the most convenient and flexible approach is to use the <code>-exportmodel</code> switch.\nThis will, by default, use the extension of the filename(s) to determine the format.\n</p>\n<p class='vspace'>From the GUI, use the \"Model | Export\" menu to export the data to a file or, for small models, use the \"Model | View\" menu to print the details directly to the log. For the case of labels, if you want to export labels from the properties file too, use the \"Properties | Export labels\" option, rather than the \"Model | Export\" one.\n</p>\n<p class='vspace'>The main formats for model export are:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \".tra\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li><li><a class='urllink' href='https://www.graphviz.org/'>Dot</a> format, for a graphical view of the model\n</li></ul><p class='vspace'><a name='explicit' id='explicit'></a>\n</p><h3>Plain text (explicit files)</h3>\n<p>This format exports different parts of the model in different file, with the expected filename extensions being:\n</p>\n<div class='vspace'></div><ul><li><code>.tra</code> - transition matrix\n</li><li><code>.srew</code>, <code>.trew</code>, <code>.rew</code> - rewards: states, transitions or both\n</li><li><code>.lab</code> - labels\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>To export just the transition matrix in this format, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To export multiple parts, use, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you omit the file basename of the export files and the basename of the model will be used, so this is equivalent to the above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel .tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can use the shorthand <code>.all</code> to export everything, and <code>.rew</code> to export both state and transition rewards. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can always use <code>stdout</code> instead of a filename. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is a quick way to print all details (of a small model) to the terminal.\n</p>\n<p class='vspace'>The labels (<code>.lab</code>) export includes the built-in labels <code>\"init\"</code> and <code>\"deadlock\"</code>,\nproviding a way to export information about initial states and (fixed) deadlock states.\n</p>\n<p class='vspace'>When there are multiple reward structures, a separate file is created for each one and a (1-indexed) suffix is added to distinguish them.\nBy default, a header in each file (see the \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html#srew'>Explicit Model Files</a>\" appendix) also shows the name of the reward structure.\nThis can be omitted - see the options below - or via the option \"Include headers in model exports\" in the GUI.\n</p>\n<p class='vspace'><a name='umb' id='umb'></a>\n</p><h3>UMB (Unified Markov binary) format</h3>\n<p>UMB is a binary format that can incorporate all parts of the model listed above.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, everything is included. You can omit some parts with the <code>-exportmodel</code>\noptions <code>rewards</code>, <code>labels</code>, <code>states</code> and <code>obs</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb:states=false,rewards=false</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For a small model, you can also see a textual version of the UMB format\nusing file extension <code>.umbt</code> (or option <code>text</code>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.umbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also configure the compression used: <code>zip=false</code> turns it off,\n<code>zip=gzip</code> uses gzip and <code>zip=xz</code> uses xz (smaller but slower to read/write).\n</p>\n<p class='vspace'><a name='other' id='other'></a>\n</p><h3>Other formats and options</h3>\n<p>If the file extension is not recognised, PRISM defaults to plain text (explicit) format.\nYou can always override this using the @format@ option, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=umb,text</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can perform multiple model exports using several instances of <code>-exportmodel</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit -exportmodel model.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Other file formats are also available:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://www.mathworks.com/'>Matlab</a> code (extension <code>.m</code>) or <code>format=matlab</code>\n</li><li>Storm's DRN model format (extension <code>.drn</code>) or <code>format=drn</code>\n</li></ul><p class='vspace'>Other <code>-exportmodel</code> options are:\n</p>\n<div class='vspace'></div><ul><li><code>actions</code> (=<code>true</code>/<code>false</code>) - whether to  actions on choices/transitions\n</li><li><code>precision</code> (=<code>&lt;n&gt;</code>) - use <code>&lt;n&gt;</code> significant figures for floating point values (in text)\n</li><li><code>headers</code> (<code>=true/false</code>) - whether to include headers when exporting rewards\n</li><li><code>rows</code> - export matrices with one row/distribution on each line (plain text)\n</li><li><code>proplabels</code> - also export labels from a properties file into a <code>.lab</code> file\n</li></ul><p class='vspace'>For plain text export, although <code>-exportmodel</code> is now usually the best switch to use,\nother older switches still exist. For example, you can export individual files using\n<code>-exporttrans &lt;file&gt;</code>,\n<code>-exportstates &lt;file&gt;</code>,\n<code>-exportstaterewards &lt;file&gt;</code>,\n<code>-exporttransrewards &lt;file&gt;</code>,\n<code>-exportrewards &lt;file&gt; &lt;file&gt;</code>,\n<code>-exportlabels &lt;file&gt;</code>, and\n<code>-exportproplabels &lt;file&gt;</code>.\nAnd you can use switches\n<code>-exportmodelprecision &lt;x&gt;</code>,\n<code>-exportmatlab</code> and\n<code>-exportrows</code>\nto specify format options affecting all of them.\n</p>\n<p class='vspace'><a name='scc' id='scc'></a>\n</p><h3>Exporting (B)SCCs and end components</h3>\n<p>It is also possible to export the set of (bottom) strongly connected components (SCCs or BSCCs) for a model. This can only be done from the command-line currently. Use, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportsccs stdout</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportbsccs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For an MDP, you can also export the set of maximal end components (MECs):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -exportmecs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExportingTheModel.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=edit.html'>Edit</a> - <a class='wikilink' href='ExportingTheModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 08:46 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='selflink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ExportingTheModel@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Exporting The Model | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExportingTheModel.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=edit.html'>Edit</a> - <a class='wikilink' href='ExportingTheModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Exporting The Model</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ExportingTheModel@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExportingTheModel.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=edit.html'>Edit</a> - <a class='wikilink' href='ExportingTheModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 08:46 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='selflink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ExportingTheModel@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Exporting The Model | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ExportingTheModel.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=edit.html'>Edit</a> - <a class='wikilink' href='ExportingTheModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Exporting The Model</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ExportingTheModel@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ExportingTheModel.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=edit.html'>Edit</a> - <a class='wikilink' href='ExportingTheModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ExportingTheModel@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on January 25, 2026, at 08:46 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='selflink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ExportingTheModel@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / ExportingTheModel </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Exporting The Model</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>If required, once the model has been constructed, it can be exported, either for manual examination or for use in another tool. The following can all be exported:\n</p>\n<div class='vspace'></div><ul><li>the <strong>transition matrix</strong> (or function);\n</li><li>the <strong>rewards</strong> (state/transition) rewards;\n</li><li>the <strong>labels</strong> (in the <a class='wikilink' href='../ThePRISMLanguage/FormulasAndLabels.html'>model</a> or <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#labels'>properties</a>) and the states that satisfy them\n</li><li>the definition of (reachable) <strong>states</strong>, i.e., their variable values\n</li><li>the definition of <strong>observations</strong>, i.e., their observable values, for partially observable models\n</li></ul><p class='vspace'>From the command-line version of PRISM, the most convenient and flexible approach is to use the <code>-exportmodel</code> switch.\nThis will, by default, use the extension of the filename(s) to determine the format.\n</p>\n<p class='vspace'>From the GUI, use the \"Model | Export\" menu to export the data to a file or, for small models, use the \"Model | View\" menu to print the details directly to the log. For the case of labels, if you want to export labels from the properties file too, use the \"Properties | Export labels\" option, rather than the \"Model | Export\" one.\n</p>\n<p class='vspace'>The main formats for model export are:\n</p>\n<div class='vspace'></div><ul><li><a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>plain text</a> files (sometimes referred to as \"explicit\" or \".tra\" files)\n</li><li><a class='urllink' href='https://pmc-tools.github.io/umb/'>UMB</a> (Unified Markov binary) format, a binary format supported by other probabilistic model checkers\n</li><li><a class='urllink' href='https://www.graphviz.org/'>Dot</a> format, for a graphical view of the model\n</li></ul><p class='vspace'><a name='explicit' id='explicit'></a>\n</p><h3>Plain text (explicit files)</h3>\n<p>This format exports different parts of the model in different file, with the expected filename extensions being:\n</p>\n<div class='vspace'></div><ul><li><code>.tra</code> - transition matrix\n</li><li><code>.srew</code>, <code>.trew</code>, <code>.rew</code> - rewards: states, transitions or both\n</li><li><code>.lab</code> - labels\n</li><li><code>.sta</code> - states\n</li><li><code>.obs</code> - observations\n</li></ul><p class='vspace'>To export just the transition matrix in this format, use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To export multiple parts, use, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you omit the file basename of the export files and the basename of the model will be used, so this is equivalent to the above:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel .tra,sta</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can use the shorthand <code>.all</code> to export everything, and <code>.rew</code> to export both state and transition rewards. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can always use <code>stdout</code> instead of a filename. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.all</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>is a quick way to print all details (of a small model) to the terminal.\n</p>\n<p class='vspace'>The labels (<code>.lab</code>) export includes the built-in labels <code>\"init\"</code> and <code>\"deadlock\"</code>,\nproviding a way to export information about initial states and (fixed) deadlock states.\n</p>\n<p class='vspace'>When there are multiple reward structures, a separate file is created for each one and a (1-indexed) suffix is added to distinguish them.\nBy default, a header in each file (see the \"<a class='wikilink' href='../Appendices/ExplicitModelFiles.html#srew'>Explicit Model Files</a>\" appendix) also shows the name of the reward structure.\nThis can be omitted - see the options below - or via the option \"Include headers in model exports\" in the GUI.\n</p>\n<p class='vspace'><a name='umb' id='umb'></a>\n</p><h3>UMB (Unified Markov binary) format</h3>\n<p>UMB is a binary format that can incorporate all parts of the model listed above.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>By default, everything is included. You can omit some parts with the <code>-exportmodel</code>\noptions <code>rewards</code>, <code>labels</code>, <code>states</code> and <code>obs</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.umb:states=false,rewards=false</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For a small model, you can also see a textual version of the UMB format\nusing file extension <code>.umbt</code> (or option <code>text</code>):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel stdout.umbt</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also configure the compression used: <code>zip=false</code> turns it off,\n<code>zip=gzip</code> uses gzip and <code>zip=xz</code> uses xz (smaller but slower to read/write).\n</p>\n<p class='vspace'><a name='other' id='other'></a>\n</p><h3>Other formats and options</h3>\n<p>If the file extension is not recognised, PRISM defaults to plain text (explicit) format.\nYou can always override this using the @format@ option, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=umb,text</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can perform multiple model exports using several instances of <code>-exportmodel</code>, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportmodel model.txt:format=explicit -exportmodel model.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Other file formats are also available:\n</p>\n<div class='vspace'></div><ul><li><a class='urllink' href='http://www.mathworks.com/'>Matlab</a> code (extension <code>.m</code>) or <code>format=matlab</code>\n</li><li>Storm's DRN model format (extension <code>.drn</code>) or <code>format=drn</code>\n</li></ul><p class='vspace'>Other <code>-exportmodel</code> options are:\n</p>\n<div class='vspace'></div><ul><li><code>actions</code> (=<code>true</code>/<code>false</code>) - whether to  actions on choices/transitions\n</li><li><code>precision</code> (=<code>&lt;n&gt;</code>) - use <code>&lt;n&gt;</code> significant figures for floating point values (in text)\n</li><li><code>headers</code> (<code>=true/false</code>) - whether to include headers when exporting rewards\n</li><li><code>rows</code> - export matrices with one row/distribution on each line (plain text)\n</li><li><code>proplabels</code> - also export labels from a properties file into a <code>.lab</code> file\n</li></ul><p class='vspace'>For plain text export, although <code>-exportmodel</code> is now usually the best switch to use,\nother older switches still exist. For example, you can export individual files using\n<code>-exporttrans &lt;file&gt;</code>,\n<code>-exportstates &lt;file&gt;</code>,\n<code>-exportstaterewards &lt;file&gt;</code>,\n<code>-exporttransrewards &lt;file&gt;</code>,\n<code>-exportrewards &lt;file&gt; &lt;file&gt;</code>,\n<code>-exportlabels &lt;file&gt;</code>, and\n<code>-exportproplabels &lt;file&gt;</code>.\nAnd you can use switches\n<code>-exportmodelprecision &lt;x&gt;</code>,\n<code>-exportmatlab</code> and\n<code>-exportrows</code>\nto specify format options affecting all of them.\n</p>\n<p class='vspace'><a name='scc' id='scc'></a>\n</p><h3>Exporting (B)SCCs and end components</h3>\n<p>It is also possible to export the set of (bottom) strongly connected components (SCCs or BSCCs) for a model. This can only be done from the command-line currently. Use, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.prism -exportsccs stdout</span><br/>\n<span style=\"font-weight:bold;\">prism model.prism -exportbsccs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For an MDP, you can also export the set of maximal end components (MECs):\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -exportmecs stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ExportingTheModel?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/LoadingAndBuildingAModel.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Loading And Building A Model \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='LoadingAndBuildingAModel.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=edit.html'>Edit</a> - <a class='wikilink' href='LoadingAndBuildingAModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Loading And Building A Model</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Typically, when using PRISM, the first step is to load a model that has been specified in the PRISM modelling language. If using the GUI, select menu option \"Model | Open Model\" and choose a file. There are a selection of sample PRISM model files in the <code>prism-examples</code> directory of the distribution.\nA few very small models are contained in the subdirectory <code>simple</code>;\nthe rest are in subdirectories grouped by model type.\n</p>\n<p class='vspace'>The model will then be displayed in the editor in the \"Model\" tab of the GUI window. The file is parsed upon loading. If there are no errors, information about the modules, variables, and other components of the model is displayed in the panel to the left and a green tick will be visible. If there are errors in the file, a red cross will appear instead and the errors will be highlighted in the model editor. To view details of the error, position the mouse pointer over the source of the error (or over the red cross). Alternatively, select menu option \"Model | Parse Model\" and the error mIessage will be displayed in a message box. Model descriptions can, of course, also be typed from scratch into the GUI's editor.\n</p>\n<div class='vspace'></div><h3>Building the model</h3>\n<p>In order to perform model checking, PRISM will (in most cases) need to construct the corresponding probabilistic model, i.e. convert the PRISM model description to, for example, an MDP, DTMC, etc. During this process, PRISM computes the set of states in the model which are reachable from the initial states and the transition matrix which represents the model.\n</p>\n<p class='vspace'>Model construction is done automatically when you perform <a class='wikilink' href='ModelChecking.html'>model checking</a>. However, you may always want to explicitly ask PRISM to build the model in order to test for errors or to see how large the model is. From the GUI, you can do this by by selecting \"Model | Build Model\". If there are no errors during model construction, the number of states and transitions in the model will be displayed in the bottom left corner of the window.\n</p>\n<p class='vspace'>From the command-line, simply type:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.nm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/LoadingAndBuildingAModel?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>model.nm</code> is the name of the file containing the model description.\n</p>\n<p class='vspace'>For some types of models, notably PTAs, models are not constructed in this way (because the models are infinite-state). In these cases, analysis of the model is not performed until model checking is performed.\n</p>\n<p class='vspace'><a name='deadlocks' id='deadlocks'></a>\n</p><h3>Deadlocks</h3>\n<p>You should be aware of the possibility of <em>deadlock states</em> (or <em>deadlocks</em>) in the model,\ni.e. states which are reachable but from which there are no outgoing transitions.\nPRISM will automatically search your model for deadlocks and, by default,\n\"fix\" them by adding self-loops in these states.\nSince deadlocks are sometimes caused by modelling errors,\nPRISM will display a warning message in the log when deadlocks are fixed in this way.\n</p>\n<p class='vspace'>You can control whether deadlocks are automatically fixed in this way using the \"Automatically fix deadlocks\" option (or with command-line switches <code>-nofixdl</code> and <code>-fixdl</code>). When fixing is disabled, PRISM will report and error when the model contains deadlocks (this used to be the default behaviour in older versions of PRISM).\n</p>\n<p class='vspace'>If you have unwanted or unexpected deadlocks in your model, there are several ways you can detect then. Firstly, by disabling deadlock fixing (as described above), PRISM will display a list of deadlock states in the log. Alternatively, you can model check the <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> property <code>filter(print, \"deadlock\")</code>, which has the safe effect.\n</p>\n<p class='vspace'>To find out <em>how</em> deadlocks occur, i.e. which paths through the model lead to a deadlock state, there are several possibilities. Firstly, you can model check the <a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>CTL</a> property <code>E[F \"deadlock\"]</code>. When checked from the GUI, this will provide you with the option of display a path to a deadlock in the simulator. From the command-line, for example with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -pf 'E[F \"deadlock\"]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/LoadingAndBuildingAModel?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>a path to a deadlock will be displayed in the log.\n</p>\n<p class='vspace'>Finally, in the eventuality that the model is too large to be model checked, you can still use the <a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>simulator</a> to search for deadlocks. This can be done either by manually generating random paths using the <a class='wikilink' href='DebuggingModelsWithTheSimulator.html#gui'>simulator in the GUI</a> or, <a class='wikilink' href='DebuggingModelsWithTheSimulator.html#cl'>from the command-line</a>, e.g. by running:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath deadlock stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/LoadingAndBuildingAModel?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='LoadingAndBuildingAModel.html'>View</a> - <a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=edit.html'>Edit</a> - <a class='wikilink' href='LoadingAndBuildingAModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 10:58 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='selflink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/LoadingAndBuildingAModel@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Loading And Building A Model | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='LoadingAndBuildingAModel.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=edit.html'>Edit</a> - <a class='wikilink' href='LoadingAndBuildingAModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Loading And Building A Model</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='LoadingAndBuildingAModel@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='LoadingAndBuildingAModel.html'>View</a> - <a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=edit.html'>Edit</a> - <a class='wikilink' href='LoadingAndBuildingAModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 10:58 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='selflink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/LoadingAndBuildingAModel@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Loading And Building A Model | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='LoadingAndBuildingAModel.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=edit.html'>Edit</a> - <a class='wikilink' href='LoadingAndBuildingAModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Loading And Building A Model</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='LoadingAndBuildingAModel@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='LoadingAndBuildingAModel.html'>View</a> - <a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=edit.html'>Edit</a> - <a class='wikilink' href='LoadingAndBuildingAModel@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='LoadingAndBuildingAModel@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 10:58 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='selflink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/LoadingAndBuildingAModel@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / LoadingAndBuildingAModel </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Loading And Building A Model</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Typically, when using PRISM, the first step is to load a model that has been specified in the PRISM modelling language. If using the GUI, select menu option \"Model | Open Model\" and choose a file. There are a selection of sample PRISM model files in the <code>prism-examples</code> directory of the distribution.\nA few very small models are contained in the subdirectory <code>simple</code>;\nthe rest are in subdirectories grouped by model type.\n</p>\n<p class='vspace'>The model will then be displayed in the editor in the \"Model\" tab of the GUI window. The file is parsed upon loading. If there are no errors, information about the modules, variables, and other components of the model is displayed in the panel to the left and a green tick will be visible. If there are errors in the file, a red cross will appear instead and the errors will be highlighted in the model editor. To view details of the error, position the mouse pointer over the source of the error (or over the red cross). Alternatively, select menu option \"Model | Parse Model\" and the error mIessage will be displayed in a message box. Model descriptions can, of course, also be typed from scratch into the GUI's editor.\n</p>\n<div class='vspace'></div><h3>Building the model</h3>\n<p>In order to perform model checking, PRISM will (in most cases) need to construct the corresponding probabilistic model, i.e. convert the PRISM model description to, for example, an MDP, DTMC, etc. During this process, PRISM computes the set of states in the model which are reachable from the initial states and the transition matrix which represents the model.\n</p>\n<p class='vspace'>Model construction is done automatically when you perform <a class='wikilink' href='ModelChecking.html'>model checking</a>. However, you may always want to explicitly ask PRISM to build the model in order to test for errors or to see how large the model is. From the GUI, you can do this by by selecting \"Model | Build Model\". If there are no errors during model construction, the number of states and transitions in the model will be displayed in the bottom left corner of the window.\n</p>\n<p class='vspace'>From the command-line, simply type:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.nm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/LoadingAndBuildingAModel?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where <code>model.nm</code> is the name of the file containing the model description.\n</p>\n<p class='vspace'>For some types of models, notably PTAs, models are not constructed in this way (because the models are infinite-state). In these cases, analysis of the model is not performed until model checking is performed.\n</p>\n<p class='vspace'><a name='deadlocks' id='deadlocks'></a>\n</p><h3>Deadlocks</h3>\n<p>You should be aware of the possibility of <em>deadlock states</em> (or <em>deadlocks</em>) in the model,\ni.e. states which are reachable but from which there are no outgoing transitions.\nPRISM will automatically search your model for deadlocks and, by default,\n\"fix\" them by adding self-loops in these states.\nSince deadlocks are sometimes caused by modelling errors,\nPRISM will display a warning message in the log when deadlocks are fixed in this way.\n</p>\n<p class='vspace'>You can control whether deadlocks are automatically fixed in this way using the \"Automatically fix deadlocks\" option (or with command-line switches <code>-nofixdl</code> and <code>-fixdl</code>). When fixing is disabled, PRISM will report and error when the model contains deadlocks (this used to be the default behaviour in older versions of PRISM).\n</p>\n<p class='vspace'>If you have unwanted or unexpected deadlocks in your model, there are several ways you can detect then. Firstly, by disabling deadlock fixing (as described above), PRISM will display a list of deadlock states in the log. Alternatively, you can model check the <a class='wikilink' href='../PropertySpecification/Filters.html'>filter</a> property <code>filter(print, \"deadlock\")</code>, which has the safe effect.\n</p>\n<p class='vspace'>To find out <em>how</em> deadlocks occur, i.e. which paths through the model lead to a deadlock state, there are several possibilities. Firstly, you can model check the <a class='wikilink' href='../PropertySpecification/Non-probabilisticProperties.html'>CTL</a> property <code>E[F \"deadlock\"]</code>. When checked from the GUI, this will provide you with the option of display a path to a deadlock in the simulator. From the command-line, for example with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -pf 'E[F \"deadlock\"]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/LoadingAndBuildingAModel?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>a path to a deadlock will be displayed in the log.\n</p>\n<p class='vspace'>Finally, in the eventuality that the model is too large to be model checked, you can still use the <a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>simulator</a> to search for deadlocks. This can be done either by manually generating random paths using the <a class='wikilink' href='DebuggingModelsWithTheSimulator.html#gui'>simulator in the GUI</a> or, <a class='wikilink' href='DebuggingModelsWithTheSimulator.html#cl'>from the command-line</a>, e.g. by running:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism dice.pm -simpath deadlock stdout</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/LoadingAndBuildingAModel?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Main.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Starting PRISM \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='StartingPRISM@action=edit.html'>Edit</a> - <a class='wikilink' href='StartingPRISM@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Starting PRISM</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>There are two versions of PRISM, one based on a graphical user interface (GUI),\nthe other based on a command line interface. Both use the same underlying model checker.\nThe latter is useful for running large batches of jobs, leaving long-running model checking tasks in the background, or simply for running the tool quickly and easily once you are familiar with its operation. \n</p>\n<p class='vspace'>Details how how to run PRISM can be found in the <a class='wikilink' href='../InstallingPRISM/Main.html'>installation instructions</a>.\nIn short, to run the PRISM GUI:\n</p>\n<div class='vspace'></div><ul><li>(on Windows) click the short-cut (to <code>xprism.bat</code>) installed on the Desktop/Start Menu\n</li><li>(on other OSs) run the <code>xprism</code> script in the <code>bin</code> directory\n</li></ul><p class='vspace'>You can also optionally specify a model file and a properties file to load upon starting the GUI, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xprism example.prism</span><br/>\n<span style=\"font-weight:bold;\">xprism example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StartingPRISM?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To use the command-line version of PRISM, run the <code>prism</code> script, also in the <code>bin</code> directory, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism example.prism example.props -prop 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StartingPRISM?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-dir</code> switch can be used to specify a directory for input (and output) files.\nSo the following are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism ~/myfiles/example.prism ~/myfiles/example.props</span><br/>\n<span style=\"font-weight:bold;\">prism -dir ~/myfiles example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StartingPRISM?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The remainder of this section of the manual describes the main types of functionality offered by PRISM.\nFor a more introductory guide to using the tool, try the\n<a class='urllink' href='http://www.prismmodelchecker.org/tutorial/'>tutorial</a> on the PRISM web site.\nSome screenshots of the GUI version of PRISM are shown below.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui1.gif'><img width='500' src='../uploads/gui1.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (editing a model)</strong></span></div>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui2.gif'><img width='500' src='../uploads/gui2.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (model checking)</strong></span></div>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='StartingPRISM@action=edit.html'>Edit</a> - <a class='wikilink' href='StartingPRISM@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='StartingPRISM@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 12:07 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ModelChecking.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Model Checking \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Typically, once a model has been constructed, it is analysed through model checking.\nProperties are specified as described in the \"<a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\" section,\nand are usually kept in files with extensions <code>.props</code>, <code>.pctl</code> or <code>.csl</code>.\nThere are properties files accompanying most of the sample PRISM models in the <code>prism-examples</code> directory.\n</p>\n<p class='vspace'><a name='gui' id='gui'></a>\n</p><h3>GUI</h3>\n<p>To load a file containing properties into the GUI, select menu option \"Properties | Open properties list\".\nThe file can only be loaded if there are no errors, otherwise an error is displayed.\nNote that it may be necessary to have loaded the corresponding model first,\nsince the properties will probably make reference to variables (and perhaps constants) declared in the model file.\nOnce loaded, the properties contained in the file are displayed in a list in the \"Properties\" tab of the GUI.\nConstants and labels are displayed in separate lists below.\nYou can modify or create new properties, constants and labels from the GUI,\nby right-clicking on the appropriate list and selecting from the pop-up menu which appears. Properties with errors are shaded red and marked with a warning sign.\nPositioning the mouse pointer over the property displays the corresponding error message.\n</p>\n<p class='vspace'>The pop-up menu for the properties list also contains a \"Verify\" option,\nwhich allows you instruct PRISM to model check the currently selected properties\n(hold down Ctrl/Cmd to select more than one property simultaneously).\nAll properties can be model checked at once by selecting \"Verify all\".\nPRISM verifies each property individually.\nUpon completion, the icon next to the property changes according to the result of model checking. For Boolean-valued properties, a result of true or false is indicated by a green tick or red cross, respectively. For properties which have a numerical result (e.g. <code>P=? [ ...]</code>), position the mouse pointer over the property to view the result.\nIn addition, this and further information about model checking is displayed in the log in the \"Log\" tab.\n</p>\n<p class='vspace'><a name='cl' id='cl'></a>\n</p><h3>Command-line</h3>\n<p>From the command-line, model checking is achieved by passing both a model file and a properties file as arguments, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The results of model checking are sent to the display and are as described above for the GUI version.\nBy default, all properties in the file are checked.\nTo model check only a single property, use the <code>-prop</code> switch.\nFor example, to check only the fourth property in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or to check only the property with <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#names'>name</a> \"safe\" in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also provide a comma-separated list of multiple properties to check,\nusing neither numerical indices or property names:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4,5,safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, the contents of a properties file can be specified directly from the command-line, using the <code>-pf</code> switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -pf 'P&gt;=0.5 [ true U&lt;=5 (s=1 &amp; a=0) ]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The switches <code>-pctl</code> and <code>-csl</code> are aliases for <code>-pf</code>.\n</p>\n<p class='vspace'>Note the use of single quotes (<code>'...'</code>) to avoid characters such as\n<code>(</code> and <code>&gt;</code> being interpreted by the command-line shell.\nSingle quotes are preferable to double quotes since PRISM properties often include double quotes, e.g. for references to labels or properties.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 21, 2020, at 09:05 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='selflink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ModelChecking@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Model Checking | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ModelChecking@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 21, 2020, at 09:05 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='selflink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ModelChecking@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Model Checking | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ModelChecking@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 21, 2020, at 09:05 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='selflink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ModelChecking@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / ModelChecking </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Model Checking</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Typically, once a model has been constructed, it is analysed through model checking.\nProperties are specified as described in the \"<a class='wikilink' href='../PropertySpecification/Main.html'>Property Specification</a>\" section,\nand are usually kept in files with extensions <code>.props</code>, <code>.pctl</code> or <code>.csl</code>.\nThere are properties files accompanying most of the sample PRISM models in the <code>prism-examples</code> directory.\n</p>\n<p class='vspace'><a name='gui' id='gui'></a>\n</p><h3>GUI</h3>\n<p>To load a file containing properties into the GUI, select menu option \"Properties | Open properties list\".\nThe file can only be loaded if there are no errors, otherwise an error is displayed.\nNote that it may be necessary to have loaded the corresponding model first,\nsince the properties will probably make reference to variables (and perhaps constants) declared in the model file.\nOnce loaded, the properties contained in the file are displayed in a list in the \"Properties\" tab of the GUI.\nConstants and labels are displayed in separate lists below.\nYou can modify or create new properties, constants and labels from the GUI,\nby right-clicking on the appropriate list and selecting from the pop-up menu which appears. Properties with errors are shaded red and marked with a warning sign.\nPositioning the mouse pointer over the property displays the corresponding error message.\n</p>\n<p class='vspace'>The pop-up menu for the properties list also contains a \"Verify\" option,\nwhich allows you instruct PRISM to model check the currently selected properties\n(hold down Ctrl/Cmd to select more than one property simultaneously).\nAll properties can be model checked at once by selecting \"Verify all\".\nPRISM verifies each property individually.\nUpon completion, the icon next to the property changes according to the result of model checking. For Boolean-valued properties, a result of true or false is indicated by a green tick or red cross, respectively. For properties which have a numerical result (e.g. <code>P=? [ ...]</code>), position the mouse pointer over the property to view the result.\nIn addition, this and further information about model checking is displayed in the log in the \"Log\" tab.\n</p>\n<p class='vspace'><a name='cl' id='cl'></a>\n</p><h3>Command-line</h3>\n<p>From the command-line, model checking is achieved by passing both a model file and a properties file as arguments, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The results of model checking are sent to the display and are as described above for the GUI version.\nBy default, all properties in the file are checked.\nTo model check only a single property, use the <code>-prop</code> switch.\nFor example, to check only the fourth property in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>or to check only the property with <a class='wikilink' href='../PropertySpecification/PropertiesFiles.html#names'>name</a> \"safe\" in the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>You can also provide a comma-separated list of multiple properties to check,\nusing neither numerical indices or property names:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm poll.csl -prop 4,5,safe</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, the contents of a properties file can be specified directly from the command-line, using the <code>-pf</code> switch:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism poll2.sm -pf 'P&gt;=0.5 [ true U&lt;=5 (s=1 &amp; a=0) ]'</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ModelChecking?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The switches <code>-pctl</code> and <code>-csl</code> are aliases for <code>-pf</code>.\n</p>\n<p class='vspace'>Note the use of single quotes (<code>'...'</code>) to avoid characters such as\n<code>(</code> and <code>&gt;</code> being interpreted by the command-line shell.\nSingle quotes are preferable to double quotes since PRISM properties often include double quotes, e.g. for references to labels or properties.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ParametricModelChecking.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Parametric Model Checking \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ParametricModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ParametricModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Parametric Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Often, PRISM models contain <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a>, representing parameters of the system being modelled, which define for example the transition probabilities in the model. In order to perform model checking, these constants have to be assigned concrete values. PRISM also allows <a class='wikilink' href='Experiments.html'>experiments</a>, where model checking is performed for a range of different values for the constants.\n</p>\n<p class='vspace'>PRISM's <em>parametric model checking</em> [<a class='wikilink' href='../Main/References.html#HHZ11b'>HHZ11b</a>],[<a class='wikilink' href='../Main/References.html#HHZ11'>HHZ11</a>] functionality, however, provides a more powerful method for analysing probabilistic models whose transition probabilities are specified as functions over a set of parameters. Depending on the property under consideration, the result is then given as either a rational function over the parameters or as a mapping from regions of these parameters to rational functions or truth values. This function (or functions) can then be used to, for example:\n</p>\n<div class='vspace'></div><ul><li>plot a graph showing how the parameter affects the result of the property; or\n<div class='vspace'></div></li><li>use optimisation methods to find parameter values that minimise or maximise the result.\n</li></ul><p class='vspace'>PRISM's implementation of parametric model checking [<a class='wikilink' href='../Main/References.html#CHH+13'>CHH+13</a>] re-implements the techniques previously included in the <a class='urllink' href='http://depend.cs.uni-sb.de/tools/param/'>PARAM</a> tool.\n</p>\n<p class='vspace'>Parameters are specified as undefined constants in the model file, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">x</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ParametricModelChecking?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These parameters can only be used to describe probabilities (or rates). For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">x</span> : (<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">1</span>-<span class=\"prismident\">x</span> : (<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ParametricModelChecking?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>They may not be used in guards or updates. The parametric definitions of probabilities or rates (e.g. <code>x</code> and <code>1-x</code> in the above) must be rational functions (fractions of polynomials). PRISM currently supports parametric versions of discrete-time Markov chains (DTMCs), continuous-time Markov chains (CTMCs) and Markov decision processes (MDPs). The classes of properties that be checked on these models are as follows:\n</p>\n<div class='vspace'></div><ul><li>parametric DTMCs/CTMCs: unbounded until, steady-state probabilities, reachability reward and steady-state reward;\n<div class='vspace'></div></li><li>parametric MDPs: unbounded until and reachability rewards.\n</li></ul><p class='vspace'>Currently, parametric model checking can only be performed from the command-line. This is done by using the switch <code>-param &lt;vals&gt;</code>, where <code>&lt;vals&gt;</code> lists the undefined constants that should be treated as parameters. A range of possible values should also be provided for each parameter, in the form <code>&lt;parameter&gt;=&lt;lower-bound&gt;:&lt;upper-bound&gt;</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.props -param x=0.2:0.4,y=-2:2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ParametricModelChecking?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would specify a parameter <code>x</code> with lower bound 0.2 and upper bound 0.4, and a parameter <code>y</code> with values between -2 and 2. You can also omit the bounds for a parameter, in which case it will be assumed to have range 0 to 1.\n</p>\n<p class='vspace'>The result of parametric model checking will be a mapping from regions (subsets of parameter valuations) to functions over the parameters. The regions are given as hyper-rectangles, e.g. \"[ [0.2,0.3],[-2,0] ]\" would represent the region of parameter valuations in which the first parameter is between 0.2 and 0.3 and the second is between -2 and 0. The results obtained are exact, that is no rounding errors are made during computation. Here is an example of the output of model checking:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.props -param x=0:1</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">Result: ([0.0,1.0]): { 2 x - 5  | 8 x - 12  }</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ParametricModelChecking?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which indicates that, for the full range ([0,1]) of the parameter <code>x</code>, the result of model checking is the expression <code>(2x-5)/(8x-2)</code>.\n</p>\n<p class='vspace'>Parametric model checking can be configured with the following options:\n</p>\n<div class='vspace'></div><ul><li><code>-paramprecision &lt;x&gt;</code>: PRISM uses regions in the form of hyper-rectangles to subsume parameter valuations with the same rational function or truth value. Because it is not always possible to cover the whole parameter space with hyper-rectangles, this option can be used to specify a <em>precision</em>, that is, an amount of the parameter space which may remain undecided. The default is 5/100.\n<div class='vspace'></div></li><li><code>-paramsplit &lt;name&gt;</code>: During model checking, undecided regions may have to be split into several parts, because there might not exist a single rational function or truth value to which all parameter valuations of the original regions can be mapped. When a region is split, it can either be split at only its longest side (<code>&lt;name&gt;=longest</code>) or at all all sides at once (<code>&lt;name&gt;=all</code>). The default is <code>longest</code>.\n<div class='vspace'></div></li><li><code>-parambisim &lt;name&gt;</code>: The parametric analysis is costly in terms of time and memory, so it can help to perform bisimulation minimisation to speed up the analysis and use less memory. The possible options here are to use weak bisimulation (<code>&lt;name&gt;=weak</code>), strong bisimulation (<code>&lt;name&gt;=strong</code>) or none at all (<code>&lt;name&gt;=none</code>). The default is <code>weak</code>. In case an analysis is to be performed for which the current bisimulation type does not maintain validity of the results (e.g. weak bisimulation and a steady state analysis), an appropriate bisimulation engine is chosen automatically.\n<div class='vspace'></div></li><li><code>-paramfunction &lt;name&gt;</code>: Sets the way rational functions are represented. Currently, only <a class='urllink' href='http://krum.rz.uni-mannheim.de/jas/'>Java Algebra System (JAS)</a> is supported. The options are to use JAS directly (<code>&lt;name&gt;=jas</code>) or to use a version in which results of some previous mathematical operations performed during the analysis are cached (<code>&lt;name&gt;=jas-cached</code>). This can speed up computation, but also needs more memory. The default is to use the cached version.\n<div class='vspace'></div></li><li><code>-paramelimorder &lt;name&gt;</code>: In the parametric engine, computations are performed by \"eliminating\" one state after the other, that is completely treating a state together with its incoming and outgoing transitions, rather than performing iterative methods. This option sets the order in which states are eliminated. The values currently available are: arbitrary order (<code>&lt;name&gt;=arbitrary</code>), forward starting from the initial states (<code>&lt;name&gt;=forward</code>), reversed forward order (<code>&lt;name&gt;=forward-reversed</code>), starting with target/unsafe states and then going backward (<code>&lt;name&gt;=backward</code>), the reverse of this order (<code>&lt;name&gt;=backward-reversed</code>) or random order (<code>&lt;name&gt;=random</code>). The default is the backward order.\n<div class='vspace'></div></li><li><code>-paramrandompoints &lt;n&gt;</code>: Under some conditions, it has to be decided whether certain properties hold for all parameter valuations of a given region. This is the case for instance when computing truth values of properties for parametric DTMCs, CTMCs and MDPs, and also when computing any value for MDPs. At the moment, the truth values are only computed approximately, by evaluating and checking values at the edges of regions (as they are hyper-rectangles) and some random points. The exact number of random points to use is given with this option. The default is 5.\n<div class='vspace'></div></li><li><code>-paramsubsumeregions &lt;b&gt;</code>: During the parametric analysis, quite a number of different regions might be created, which have to be stored in memory. If this option is used (<code>&lt;b&gt;=true</code>), PRISM tries to subsume neighbouring regions with the same value. The default is to use it.\n</li></ul>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ParametricModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ParametricModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2015, at 08:54 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='selflink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ParametricModelChecking@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Parametric Model Checking | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ParametricModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ParametricModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Parametric Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ParametricModelChecking@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ParametricModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ParametricModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2015, at 08:54 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='selflink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ParametricModelChecking@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Parametric Model Checking | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ParametricModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ParametricModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Parametric Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ParametricModelChecking@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ParametricModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='ParametricModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ParametricModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2015, at 08:54 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='selflink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/ParametricModelChecking@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / ParametricModelChecking </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Parametric Model Checking</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Often, PRISM models contain <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constants</a>, representing parameters of the system being modelled, which define for example the transition probabilities in the model. In order to perform model checking, these constants have to be assigned concrete values. PRISM also allows <a class='wikilink' href='Experiments.html'>experiments</a>, where model checking is performed for a range of different values for the constants.\n</p>\n<p class='vspace'>PRISM's <em>parametric model checking</em> [<a class='wikilink' href='../Main/References.html#HHZ11b'>HHZ11b</a>],[<a class='wikilink' href='../Main/References.html#HHZ11'>HHZ11</a>] functionality, however, provides a more powerful method for analysing probabilistic models whose transition probabilities are specified as functions over a set of parameters. Depending on the property under consideration, the result is then given as either a rational function over the parameters or as a mapping from regions of these parameters to rational functions or truth values. This function (or functions) can then be used to, for example:\n</p>\n<div class='vspace'></div><ul><li>plot a graph showing how the parameter affects the result of the property; or\n<div class='vspace'></div></li><li>use optimisation methods to find parameter values that minimise or maximise the result.\n</li></ul><p class='vspace'>PRISM's implementation of parametric model checking [<a class='wikilink' href='../Main/References.html#CHH+13'>CHH+13</a>] re-implements the techniques previously included in the <a class='urllink' href='http://depend.cs.uni-sb.de/tools/param/'>PARAM</a> tool.\n</p>\n<p class='vspace'>Parameters are specified as undefined constants in the model file, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">x</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ParametricModelChecking?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These parameters can only be used to describe probabilities (or rates). For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">x</span> : (<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">1</span>-<span class=\"prismident\">x</span> : (<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ParametricModelChecking?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>They may not be used in guards or updates. The parametric definitions of probabilities or rates (e.g. <code>x</code> and <code>1-x</code> in the above) must be rational functions (fractions of polynomials). PRISM currently supports parametric versions of discrete-time Markov chains (DTMCs), continuous-time Markov chains (CTMCs) and Markov decision processes (MDPs). The classes of properties that be checked on these models are as follows:\n</p>\n<div class='vspace'></div><ul><li>parametric DTMCs/CTMCs: unbounded until, steady-state probabilities, reachability reward and steady-state reward;\n<div class='vspace'></div></li><li>parametric MDPs: unbounded until and reachability rewards.\n</li></ul><p class='vspace'>Currently, parametric model checking can only be performed from the command-line. This is done by using the switch <code>-param &lt;vals&gt;</code>, where <code>&lt;vals&gt;</code> lists the undefined constants that should be treated as parameters. A range of possible values should also be provided for each parameter, in the form <code>&lt;parameter&gt;=&lt;lower-bound&gt;:&lt;upper-bound&gt;</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.props -param x=0.2:0.4,y=-2:2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ParametricModelChecking?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>would specify a parameter <code>x</code> with lower bound 0.2 and upper bound 0.4, and a parameter <code>y</code> with values between -2 and 2. You can also omit the bounds for a parameter, in which case it will be assumed to have range 0 to 1.\n</p>\n<p class='vspace'>The result of parametric model checking will be a mapping from regions (subsets of parameter valuations) to functions over the parameters. The regions are given as hyper-rectangles, e.g. \"[ [0.2,0.3],[-2,0] ]\" would represent the region of parameter valuations in which the first parameter is between 0.2 and 0.3 and the second is between -2 and 0. The results obtained are exact, that is no rounding errors are made during computation. Here is an example of the output of model checking:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.props -param x=0:1</span><br/>\n<span style=\"font-style:italic;\">...</span><br/>\n<span style=\"font-style:italic;\">Result: ([0.0,1.0]): { 2 x - 5  | 8 x - 12  }</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/ParametricModelChecking?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>which indicates that, for the full range ([0,1]) of the parameter <code>x</code>, the result of model checking is the expression <code>(2x-5)/(8x-2)</code>.\n</p>\n<p class='vspace'>Parametric model checking can be configured with the following options:\n</p>\n<div class='vspace'></div><ul><li><code>-paramprecision &lt;x&gt;</code>: PRISM uses regions in the form of hyper-rectangles to subsume parameter valuations with the same rational function or truth value. Because it is not always possible to cover the whole parameter space with hyper-rectangles, this option can be used to specify a <em>precision</em>, that is, an amount of the parameter space which may remain undecided. The default is 5/100.\n<div class='vspace'></div></li><li><code>-paramsplit &lt;name&gt;</code>: During model checking, undecided regions may have to be split into several parts, because there might not exist a single rational function or truth value to which all parameter valuations of the original regions can be mapped. When a region is split, it can either be split at only its longest side (<code>&lt;name&gt;=longest</code>) or at all all sides at once (<code>&lt;name&gt;=all</code>). The default is <code>longest</code>.\n<div class='vspace'></div></li><li><code>-parambisim &lt;name&gt;</code>: The parametric analysis is costly in terms of time and memory, so it can help to perform bisimulation minimisation to speed up the analysis and use less memory. The possible options here are to use weak bisimulation (<code>&lt;name&gt;=weak</code>), strong bisimulation (<code>&lt;name&gt;=strong</code>) or none at all (<code>&lt;name&gt;=none</code>). The default is <code>weak</code>. In case an analysis is to be performed for which the current bisimulation type does not maintain validity of the results (e.g. weak bisimulation and a steady state analysis), an appropriate bisimulation engine is chosen automatically.\n<div class='vspace'></div></li><li><code>-paramfunction &lt;name&gt;</code>: Sets the way rational functions are represented. Currently, only <a class='urllink' href='http://krum.rz.uni-mannheim.de/jas/'>Java Algebra System (JAS)</a> is supported. The options are to use JAS directly (<code>&lt;name&gt;=jas</code>) or to use a version in which results of some previous mathematical operations performed during the analysis are cached (<code>&lt;name&gt;=jas-cached</code>). This can speed up computation, but also needs more memory. The default is to use the cached version.\n<div class='vspace'></div></li><li><code>-paramelimorder &lt;name&gt;</code>: In the parametric engine, computations are performed by \"eliminating\" one state after the other, that is completely treating a state together with its incoming and outgoing transitions, rather than performing iterative methods. This option sets the order in which states are eliminated. The values currently available are: arbitrary order (<code>&lt;name&gt;=arbitrary</code>), forward starting from the initial states (<code>&lt;name&gt;=forward</code>), reversed forward order (<code>&lt;name&gt;=forward-reversed</code>), starting with target/unsafe states and then going backward (<code>&lt;name&gt;=backward</code>), the reverse of this order (<code>&lt;name&gt;=backward-reversed</code>) or random order (<code>&lt;name&gt;=random</code>). The default is the backward order.\n<div class='vspace'></div></li><li><code>-paramrandompoints &lt;n&gt;</code>: Under some conditions, it has to be decided whether certain properties hold for all parameter valuations of a given region. This is the case for instance when computing truth values of properties for parametric DTMCs, CTMCs and MDPs, and also when computing any value for MDPs. At the moment, the truth values are only computed approximately, by evaluating and checking values at the edges of regions (as they are hyper-rectangles) and some random points. The exact number of random points to use is given with this option. The default is 5.\n<div class='vspace'></div></li><li><code>-paramsubsumeregions &lt;b&gt;</code>: During the parametric analysis, quite a number of different regions might be created, which have to be stored in memory. If this option is used (<code>&lt;b&gt;=true</code>), PRISM tries to subsume neighbouring regions with the same value. The default is to use it.\n</li></ul>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/StartingPRISM@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Starting PRISM | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='StartingPRISM@action=edit.html'>Edit</a> - <a class='wikilink' href='StartingPRISM@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Starting PRISM</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='StartingPRISM@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='StartingPRISM@action=edit.html'>Edit</a> - <a class='wikilink' href='StartingPRISM@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='StartingPRISM@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 12:07 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/StartingPRISM@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Starting PRISM | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='StartingPRISM@action=edit.html'>Edit</a> - <a class='wikilink' href='StartingPRISM@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Starting PRISM</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='StartingPRISM@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='StartingPRISM@action=edit.html'>Edit</a> - <a class='wikilink' href='StartingPRISM@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='StartingPRISM@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 19, 2021, at 12:07 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/StartingPRISM@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / StartingPRISM </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Starting PRISM</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>There are two versions of PRISM, one based on a graphical user interface (GUI),\nthe other based on a command line interface. Both use the same underlying model checker.\nThe latter is useful for running large batches of jobs, leaving long-running model checking tasks in the background, or simply for running the tool quickly and easily once you are familiar with its operation. \n</p>\n<p class='vspace'>Details how how to run PRISM can be found in the <a class='wikilink' href='../InstallingPRISM/Main.html'>installation instructions</a>.\nIn short, to run the PRISM GUI:\n</p>\n<div class='vspace'></div><ul><li>(on Windows) click the short-cut (to <code>xprism.bat</code>) installed on the Desktop/Start Menu\n</li><li>(on other OSs) run the <code>xprism</code> script in the <code>bin</code> directory\n</li></ul><p class='vspace'>You can also optionally specify a model file and a properties file to load upon starting the GUI, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">xprism example.prism</span><br/>\n<span style=\"font-weight:bold;\">xprism example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StartingPRISM?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>To use the command-line version of PRISM, run the <code>prism</code> script, also in the <code>bin</code> directory, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism example.prism example.props -prop 2</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StartingPRISM?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <code>-dir</code> switch can be used to specify a directory for input (and output) files.\nSo the following are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism ~/myfiles/example.prism ~/myfiles/example.props</span><br/>\n<span style=\"font-weight:bold;\">prism -dir ~/myfiles example.prism example.props</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StartingPRISM?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The remainder of this section of the manual describes the main types of functionality offered by PRISM.\nFor a more introductory guide to using the tool, try the\n<a class='urllink' href='http://www.prismmodelchecker.org/tutorial/'>tutorial</a> on the PRISM web site.\nSome screenshots of the GUI version of PRISM are shown below.\n</p>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui1.gif'><img width='500' src='../uploads/gui1.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (editing a model)</strong></span></div>\n<div class='vspace'></div><div class='img imgcaption'> <a class='urllink' href='../uploads/gui2.gif'><img width='500' src='../uploads/gui2.gif' alt='' /></a><br /><span class='caption'><strong>The PRISM GUI (model checking)</strong></span></div>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/StatisticalModelChecking.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Statistical Model Checking \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ApproximateModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='StatisticalModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Statistical Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The discrete-event simulator built into PRISM (see the section \"<a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\") can also be used to generate <em>approximate</em> results for PRISM properties, a technique often called <em>statistical model checking</em>. Essentially, this is achieved by <em>sampling</em>: generating a large number of random paths through the model, evaluating the result of the given properties on each run, and using this information to generate an approximately correct result. This approach is particularly useful on very large models when normal model checking is infeasible. This is because discrete-event simulation is performed using the PRISM language model description, without explicitly constructing the corresponding probabilistic model.\n</p>\n<p class='vspace'>Currently, statistical model checking can only be applied to <code><strong>P</strong></code> or <code><strong>R</strong></code> operators\nand does not support LTL-style path properties or <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\nThere are also a few restrictions on the modelling language features that can be used; see below for details.\n</p>\n<p class='vspace'>To use this functionality, load a model and some properties into PRISM, as described in the previous sections. To generate an approximate value for one or more properties, select them in the list, right-click and select \"Simulate\" (as opposed to \"Verify\"). As usual, it is first necessary to provide values for any undefined constants. Subsequently, a dialog appears. Here, the state from which approximate values are to be computed (i.e. from which the paths will be generated) can be selected. By default, this is the initial state of the model. The other settings in the dialog concern the methods used for simulation.\n</p>\n<p class='vspace'>PRISM supports four different methods for performing statistical model checking:\n</p>\n<div class='vspace'></div><ul><li>CI (Confidence Interval)\n</li><li>ACI (Asymptotic Confidence Interval)\n</li><li>APMC (Approximate Probabilistic Model Checking)\n</li><li>SPRT (Sequential Probability Ratio Test)\n</li></ul><p class='vspace'>The first three of these are intended primarily for \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>quantitative</a>\" properties (e.g. of the form <code><strong>P</strong>=?[...]</code>), but can also be used for \"bounded\" properties (e.g. of the form <code><strong>P</strong>&lt;p[...]</code>). The SPRT method is only applicable to \"bounded\" properties.\n</p>\n<p class='vspace'>Each method has several parameters that control its execution, i.e. the number of samples that are generated and the accuracy of the computed approximation. In most cases, these parameters are inter-related so one of them must be left unspecified and its value computed automatically based on the others. In some cases, this is done before simulation; in others, it must be done afterwards.\n</p>\n<p class='vspace'>Below, we describe each method in more detail.\nFor simplicity, we describe the case of checking a <code><strong>P</strong></code> operator.\nDetails for the case of an <code><strong>R</strong></code> operator can be found in [<a class='wikilink' href='../Main/References.html#Nim10'>Nim10</a>].\n</p>\n<div class='vspace'></div><h3>CI (Confidence Interval) Method</h3>\n<p>The CI method gives a <em>confidence interval</em> for the approximate value generated for a <code><strong>P</strong>=?</code> property, based on a given <em>confidence level</em> and the number of samples generated.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Width\" (<em>w</em>)\n</li><li>\"Confidence\" (<em>alpha</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Let <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated.\nThe confidence interval is [<em>Y-w</em>,<em>Y+w</em>], i.e. <em>w</em> gives the half-width of the interval.\nThe confidence level, which is usually stated as a percentage, is 100(1-<em>alpha</em>)%.\nThis means that the actual value <em>X</em> should fall into the confidence interval [<em>Y-w</em>,<em>Y+w</em>] 100(1-<em>alpha</em>)% of the time.\n</p>\n<p class='vspace'>To determine, for example, the width <em>w</em> for given <em>alpha</em> and <em>N</em>,\nwe use <em>w</em> = <em>q</em> * sqrt(<em>v</em> / <em>N</em>) where\n<em>q</em> is a quantile, for probability 1-<em>alpha</em>/2, from the Student's t-distribution with <em>N</em>-1 degrees of freedom and <em>v</em> is (an estimation of) the variance for <em>X</em>.\nSimilarly, we can determine the required number of iterations, from <em>w</em> and <em>alpha</em>,\nas N = (<em>v</em> * <em>q</em><sup>2</sup>)/<em>w</em><sup>2</sup>, where <em>q</em> and <em>v</em> are as before.\n</p>\n<p class='vspace'>For a bounded property  <code><strong>P</strong>~p[...]</code>, the (Boolean) result is determined according to the generated approximation for the probability. This is not the case, however, if the threshold <em>p</em> falls within the confidence interval [<em>Y-w</em>,<em>Y+w</em>], in which case no value is returned.\n</p>\n<div class='vspace'></div><h3>ACI (Asymptotic Confidence Interval) Method</h3>\n<p>The ACI method works in exactly same fashion as the CI method, except that it uses the Normal distribution to approximate the Student's t-distribution when determining the confidence interval. This is appropriate when the number of samples is large (because we can get a reliable estimation of the variance from the samples) but may be less accurate for small numbers of samples.\n</p>\n<div class='vspace'></div><h3>APMC (Approximate Probabilistic Model Checking) Method</h3>\n<p>The APMC method, based on [<a class='wikilink' href='../Main/References.html#HLMP04'>HLMP04</a>], offers a probabilistic guarantee on the accuracy of the  approximate value generated for a <code><strong>P</strong>=?</code> property, based on the Chernoff-Hoeffding bound.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Approximation\" (<em>epsilon</em>)\n</li><li>\"Confidence\" (<em>delta</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Letting <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated, we have:\n</p>\n<div class='vspace'></div><ul><li>Prob(|<em>Y</em>-<em>X</em>| &gt; <em>epsilon</em>) &lt; <em>delta</em>\n</li></ul><p class='vspace'>where the parameters are related as follows:\n<em>N</em> = ln(2/<em>delta</em>) / 2<em>epsilon</em><sup>2</sup>.\nThis imposes certain restrictions on the parameters,\nnamely that <em>N</em>(<em>epsilon</em><sup>2</sup>) &#8805; ln(2/delta)/2.\n</p>\n<p class='vspace'>In similar fashion to the CI/ACI methods, the APMC method can be also be used for bounded properties such as <code><strong>P</strong>~p[...]</code>, as long as the threshold <em>p</em> falls outside the interval [<em>Y-epsilon</em>,<em>Y+epsilon</em>].\n</p>\n<div class='vspace'></div><h3>SPRT (Sequential Probability Ratio Test) Method</h3>\n<p>The SPRT method is specifically for bounded properties, such as <code><strong>P</strong>~p[...]</code> and is based on <em>acceptance sampling</em> techniques [<a class='wikilink' href='../Main/References.html#YS02'>YS02</a>]. It uses Wald's sequential probability ratio test (SPRT), which generates a succession of samples, deciding on-the-fly when an answer can be given with a sufficiently high confidence.\n</p>\n<p class='vspace'>The parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Indifference\" (<em>delta</em>)\n</li><li>\"Type I/II error\" (<em>alpha</em>/<em>beta</em>)\n</li></ul><p class='vspace'>Consider a property of the form <code><strong>P</strong>&#8805;p[...]</code>. The parameter <em>delta</em> is used as the half-width of an <em>indifference region</em> [p-delta,p+delta]. PRISM will attempt to determine whether either the hypothesis <code><strong>P</strong>&#8805;(p+delta)[...]</code> or <code><strong>P</strong>&#8804;(p-delta)[...]</code> is true, based on which it will return either <code>true</code> or <code>false</code>, respectively. The parameters <em>alpha</em> and <em>beta</em> represent the probability of the occurrence of a <em>type I error</em> (wrongly accepting the first hypothesis) and a <em>type II error</em> (wrongly accepting the second hypothesis), respectively. For simplicity, PRISM assigns the same value to both <em>alpha</em> and <em>beta</em>.\n</p>\n<div class='vspace'></div><h3>Maximum Path Length</h3>\n<p>Another setting that can be configured from the \"Simulation Parameters\" dialog is the maximum length of paths generated by PRISM during statistical model checking. In order to perform statistical model checking, PRISM needs to evaluate the property being checked along every generated path. For example, when checking <code>P=? [ F&lt;=10 \"end\" ]</code>, PRISM must check whether <code>F&lt;=10 \"end\"</code> is true for each path. On this example (assuming a discrete-time model), this can always be done within the first 10 steps. For a property such as <code>P=? [ F \"end\" ]</code>, however, there may be paths along which no finite fragment can show <code>F \"end\"</code> to be true or false. So, PRISM imposes a maximum path length to avoid the need to generate excessively long (or infinite) paths.\nThe default maximum length is 10,000 steps.\nIf, for a given property, statistical model checking results in one or more paths on which the property cannot be evaluated, an error is reported.\n</p>\n<div class='vspace'></div><h3>Command-line Statistical Model Checking</h3>\n<p>Statistical model checking can also be enabled from the command-line version of PRISM, by including the <code>-sim</code> switch. The default methods used are CI (Confidence Interval) for \"quantitative\" properties and SPRT (Sequential Probability Ratio Test) for \"bounded\" properties. To select a particular method, use switch <code>-simmethod &lt;method&gt;</code> where <code>&lt;method&gt;</code> is one of <code>ci</code>, <code>aci</code>, <code>apmc</code> and <code>sprt</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.pctl -prop 1 -sim -simmethod aci</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StatisticalModelChecking?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM has default values for the various simulation method parameters, but these can also be specified using the switches <code>-simsamples</code>, <code>-simconf</code>, <code>-simwidth</code> and <code>-simapprox</code>. The exact meaning of these switches for each simulation method is given in the table below.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><strong>CI</strong></td><td  align='center'><strong>ACI</strong></td><td  align='center'><strong>APMC</strong></td><td  align='right'><strong>SPRT</strong></td></tr>\n<tr ><td  align='center'><code>-simsamples</code></td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='right'>n/a</td></tr>\n<tr ><td  align='center'><code>-simconf</code></td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='right'>\"Type I/II error\"</td></tr>\n<tr ><td  align='center'><code>-simwidth</code></td><td  align='center'>\"Width\"</td><td  align='center'>\"Width\"</td><td  align='center'>n/a</td><td  align='right'>\"Indifference\"</td></tr>\n<tr ><td  align='center'><code>-simapprox</code></td><td  align='center'>n/a</td><td  align='center'>n/a</td><td  align='center'>\"Approximation\"</td><td  align='right'>n/a</td></tr>\n</table>\n<p class='vspace'>The maximum length of simulation paths is set with switch <code>-simpathlen</code>.\n</p>\n<div class='vspace'></div><h3>Limitations</h3>\n<p>Currently, the simulator does not support every part of the PRISM modelling languages. For example, it does not handle models with multiple initial states or with <code><strong>system</strong>...<strong>endsystem</strong></code> definitions.\n</p>\n<p class='vspace'>It is also worth pointing out that statistical model checking techniques are not well suited to models that exhibit nondeterminism, such as MDPs. This because the techniques rely on generation of <em>random</em> paths, which are not well defined for a MDP. PRISM does allow statistical model checking to be performed on an MDP, but does so by simply resolving nondeterministic choices in a (uniformly) random fashion (and displaying a warning message). Currently PTAs are not supported by the simulator.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ApproximateModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='StatisticalModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 05, 2024, at 03:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='selflink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/StatisticalModelChecking@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Statistical Model Checking | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ApproximateModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='StatisticalModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Statistical Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='StatisticalModelChecking@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ApproximateModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='StatisticalModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 05, 2024, at 03:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='selflink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/StatisticalModelChecking@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Statistical Model Checking | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ApproximateModelChecking.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='StatisticalModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Statistical Model Checking</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='StatisticalModelChecking@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ApproximateModelChecking.html'>View</a> - <a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=edit.html'>Edit</a> - <a class='wikilink' href='StatisticalModelChecking@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='StatisticalModelChecking@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 05, 2024, at 03:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='selflink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/StatisticalModelChecking@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / StatisticalModelChecking </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Statistical Model Checking</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>The discrete-event simulator built into PRISM (see the section \"<a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\") can also be used to generate <em>approximate</em> results for PRISM properties, a technique often called <em>statistical model checking</em>. Essentially, this is achieved by <em>sampling</em>: generating a large number of random paths through the model, evaluating the result of the given properties on each run, and using this information to generate an approximately correct result. This approach is particularly useful on very large models when normal model checking is infeasible. This is because discrete-event simulation is performed using the PRISM language model description, without explicitly constructing the corresponding probabilistic model.\n</p>\n<p class='vspace'>Currently, statistical model checking can only be applied to <code><strong>P</strong></code> or <code><strong>R</strong></code> operators\nand does not support LTL-style path properties or <a class='wikilink' href='../PropertySpecification/Filters.html'>filters</a>.\nThere are also a few restrictions on the modelling language features that can be used; see below for details.\n</p>\n<p class='vspace'>To use this functionality, load a model and some properties into PRISM, as described in the previous sections. To generate an approximate value for one or more properties, select them in the list, right-click and select \"Simulate\" (as opposed to \"Verify\"). As usual, it is first necessary to provide values for any undefined constants. Subsequently, a dialog appears. Here, the state from which approximate values are to be computed (i.e. from which the paths will be generated) can be selected. By default, this is the initial state of the model. The other settings in the dialog concern the methods used for simulation.\n</p>\n<p class='vspace'>PRISM supports four different methods for performing statistical model checking:\n</p>\n<div class='vspace'></div><ul><li>CI (Confidence Interval)\n</li><li>ACI (Asymptotic Confidence Interval)\n</li><li>APMC (Approximate Probabilistic Model Checking)\n</li><li>SPRT (Sequential Probability Ratio Test)\n</li></ul><p class='vspace'>The first three of these are intended primarily for \"<a class='wikilink' href='../PropertySpecification/ThePOperator.html'>quantitative</a>\" properties (e.g. of the form <code><strong>P</strong>=?[...]</code>), but can also be used for \"bounded\" properties (e.g. of the form <code><strong>P</strong>&lt;p[...]</code>). The SPRT method is only applicable to \"bounded\" properties.\n</p>\n<p class='vspace'>Each method has several parameters that control its execution, i.e. the number of samples that are generated and the accuracy of the computed approximation. In most cases, these parameters are inter-related so one of them must be left unspecified and its value computed automatically based on the others. In some cases, this is done before simulation; in others, it must be done afterwards.\n</p>\n<p class='vspace'>Below, we describe each method in more detail.\nFor simplicity, we describe the case of checking a <code><strong>P</strong></code> operator.\nDetails for the case of an <code><strong>R</strong></code> operator can be found in [<a class='wikilink' href='../Main/References.html#Nim10'>Nim10</a>].\n</p>\n<div class='vspace'></div><h3>CI (Confidence Interval) Method</h3>\n<p>The CI method gives a <em>confidence interval</em> for the approximate value generated for a <code><strong>P</strong>=?</code> property, based on a given <em>confidence level</em> and the number of samples generated.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Width\" (<em>w</em>)\n</li><li>\"Confidence\" (<em>alpha</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Let <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated.\nThe confidence interval is [<em>Y-w</em>,<em>Y+w</em>], i.e. <em>w</em> gives the half-width of the interval.\nThe confidence level, which is usually stated as a percentage, is 100(1-<em>alpha</em>)%.\nThis means that the actual value <em>X</em> should fall into the confidence interval [<em>Y-w</em>,<em>Y+w</em>] 100(1-<em>alpha</em>)% of the time.\n</p>\n<p class='vspace'>To determine, for example, the width <em>w</em> for given <em>alpha</em> and <em>N</em>,\nwe use <em>w</em> = <em>q</em> * sqrt(<em>v</em> / <em>N</em>) where\n<em>q</em> is a quantile, for probability 1-<em>alpha</em>/2, from the Student's t-distribution with <em>N</em>-1 degrees of freedom and <em>v</em> is (an estimation of) the variance for <em>X</em>.\nSimilarly, we can determine the required number of iterations, from <em>w</em> and <em>alpha</em>,\nas N = (<em>v</em> * <em>q</em><sup>2</sup>)/<em>w</em><sup>2</sup>, where <em>q</em> and <em>v</em> are as before.\n</p>\n<p class='vspace'>For a bounded property  <code><strong>P</strong>~p[...]</code>, the (Boolean) result is determined according to the generated approximation for the probability. This is not the case, however, if the threshold <em>p</em> falls within the confidence interval [<em>Y-w</em>,<em>Y+w</em>], in which case no value is returned.\n</p>\n<div class='vspace'></div><h3>ACI (Asymptotic Confidence Interval) Method</h3>\n<p>The ACI method works in exactly same fashion as the CI method, except that it uses the Normal distribution to approximate the Student's t-distribution when determining the confidence interval. This is appropriate when the number of samples is large (because we can get a reliable estimation of the variance from the samples) but may be less accurate for small numbers of samples.\n</p>\n<div class='vspace'></div><h3>APMC (Approximate Probabilistic Model Checking) Method</h3>\n<p>The APMC method, based on [<a class='wikilink' href='../Main/References.html#HLMP04'>HLMP04</a>], offers a probabilistic guarantee on the accuracy of the  approximate value generated for a <code><strong>P</strong>=?</code> property, based on the Chernoff-Hoeffding bound.\nThe parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Approximation\" (<em>epsilon</em>)\n</li><li>\"Confidence\" (<em>delta</em>)\n</li><li>\"Number of samples\" (<em>N</em>)\n</li></ul><p class='vspace'>Letting <em>X</em> denote the true result of the query <code><strong>P</strong>=?[...]</code> and <em>Y</em> the approximation generated, we have:\n</p>\n<div class='vspace'></div><ul><li>Prob(|<em>Y</em>-<em>X</em>| &gt; <em>epsilon</em>) &lt; <em>delta</em>\n</li></ul><p class='vspace'>where the parameters are related as follows:\n<em>N</em> = ln(2/<em>delta</em>) / 2<em>epsilon</em><sup>2</sup>.\nThis imposes certain restrictions on the parameters,\nnamely that <em>N</em>(<em>epsilon</em><sup>2</sup>) &#8805; ln(2/delta)/2.\n</p>\n<p class='vspace'>In similar fashion to the CI/ACI methods, the APMC method can be also be used for bounded properties such as <code><strong>P</strong>~p[...]</code>, as long as the threshold <em>p</em> falls outside the interval [<em>Y-epsilon</em>,<em>Y+epsilon</em>].\n</p>\n<div class='vspace'></div><h3>SPRT (Sequential Probability Ratio Test) Method</h3>\n<p>The SPRT method is specifically for bounded properties, such as <code><strong>P</strong>~p[...]</code> and is based on <em>acceptance sampling</em> techniques [<a class='wikilink' href='../Main/References.html#YS02'>YS02</a>]. It uses Wald's sequential probability ratio test (SPRT), which generates a succession of samples, deciding on-the-fly when an answer can be given with a sufficiently high confidence.\n</p>\n<p class='vspace'>The parameters of the method are:\n</p>\n<div class='vspace'></div><ul><li>\"Indifference\" (<em>delta</em>)\n</li><li>\"Type I/II error\" (<em>alpha</em>/<em>beta</em>)\n</li></ul><p class='vspace'>Consider a property of the form <code><strong>P</strong>&#8805;p[...]</code>. The parameter <em>delta</em> is used as the half-width of an <em>indifference region</em> [p-delta,p+delta]. PRISM will attempt to determine whether either the hypothesis <code><strong>P</strong>&#8805;(p+delta)[...]</code> or <code><strong>P</strong>&#8804;(p-delta)[...]</code> is true, based on which it will return either <code>true</code> or <code>false</code>, respectively. The parameters <em>alpha</em> and <em>beta</em> represent the probability of the occurrence of a <em>type I error</em> (wrongly accepting the first hypothesis) and a <em>type II error</em> (wrongly accepting the second hypothesis), respectively. For simplicity, PRISM assigns the same value to both <em>alpha</em> and <em>beta</em>.\n</p>\n<div class='vspace'></div><h3>Maximum Path Length</h3>\n<p>Another setting that can be configured from the \"Simulation Parameters\" dialog is the maximum length of paths generated by PRISM during statistical model checking. In order to perform statistical model checking, PRISM needs to evaluate the property being checked along every generated path. For example, when checking <code>P=? [ F&lt;=10 \"end\" ]</code>, PRISM must check whether <code>F&lt;=10 \"end\"</code> is true for each path. On this example (assuming a discrete-time model), this can always be done within the first 10 steps. For a property such as <code>P=? [ F \"end\" ]</code>, however, there may be paths along which no finite fragment can show <code>F \"end\"</code> to be true or false. So, PRISM imposes a maximum path length to avoid the need to generate excessively long (or infinite) paths.\nThe default maximum length is 10,000 steps.\nIf, for a given property, statistical model checking results in one or more paths on which the property cannot be evaluated, an error is reported.\n</p>\n<div class='vspace'></div><h3>Command-line Statistical Model Checking</h3>\n<p>Statistical model checking can also be enabled from the command-line version of PRISM, by including the <code>-sim</code> switch. The default methods used are CI (Confidence Interval) for \"quantitative\" properties and SPRT (Sequential Probability Ratio Test) for \"bounded\" properties. To select a particular method, use switch <code>-simmethod &lt;method&gt;</code> where <code>&lt;method&gt;</code> is one of <code>ci</code>, <code>aci</code>, <code>apmc</code> and <code>sprt</code>. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism model.pm model.pctl -prop 1 -sim -simmethod aci</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/StatisticalModelChecking?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>PRISM has default values for the various simulation method parameters, but these can also be specified using the switches <code>-simsamples</code>, <code>-simconf</code>, <code>-simwidth</code> and <code>-simapprox</code>. The exact meaning of these switches for each simulation method is given in the table below.\n</p>\n<div class='vspace'></div>\n<table border='1' cellpadding='5' ><tr ><td >&nbsp;</td><td  align='center'><strong>CI</strong></td><td  align='center'><strong>ACI</strong></td><td  align='center'><strong>APMC</strong></td><td  align='right'><strong>SPRT</strong></td></tr>\n<tr ><td  align='center'><code>-simsamples</code></td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='center'>\"Num. samples\"</td><td  align='right'>n/a</td></tr>\n<tr ><td  align='center'><code>-simconf</code></td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='center'>\"Confidence\"</td><td  align='right'>\"Type I/II error\"</td></tr>\n<tr ><td  align='center'><code>-simwidth</code></td><td  align='center'>\"Width\"</td><td  align='center'>\"Width\"</td><td  align='center'>n/a</td><td  align='right'>\"Indifference\"</td></tr>\n<tr ><td  align='center'><code>-simapprox</code></td><td  align='center'>n/a</td><td  align='center'>n/a</td><td  align='center'>\"Approximation\"</td><td  align='right'>n/a</td></tr>\n</table>\n<p class='vspace'>The maximum length of simulation paths is set with switch <code>-simpathlen</code>.\n</p>\n<div class='vspace'></div><h3>Limitations</h3>\n<p>Currently, the simulator does not support every part of the PRISM modelling languages. For example, it does not handle models with multiple initial states or with <code><strong>system</strong>...<strong>endsystem</strong></code> definitions.\n</p>\n<p class='vspace'>It is also worth pointing out that statistical model checking techniques are not well suited to models that exhibit nondeterminism, such as MDPs. This because the techniques rely on generation of <em>random</em> paths, which are not well defined for a MDP. PRISM does allow statistical model checking to be performed on an MDP, but does so by simply resolving nondeterministic choices in a (uniformly) random fashion (and displaying a warning message). Currently PTAs are not supported by the simulator.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Strategies.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Strategies \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Strategies.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Strategies@action=edit.html'>Edit</a> - <a class='wikilink' href='Strategies@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Strategies</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Properties to be model checked on MDPs (and their variants, such as POMDPs or IMDPs) usually quantify over <em>strategies</em> (or <em>policies</em>) of the model, i.e., over the different possible ways that nondeterminism can be resolved in the model.\nFor example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>determines the maximum probability, over all strategies, of reaching a state satisfying the label <code>\"goal\"</code>. When checking such properties, you can also ask PRISM to generate a corresponding (optimal) strategy, which yields this maximum probability when followed. The strategy can then be viewed, exported or simulated.\n</p>\n<p class='vspace'><strong>Note:</strong> For consistency across models, PRISM now uses the terminology <em>strategy</em> (rather than alternatives such as <em>policy</em>). In older versions of the tool, these were referred to as <em>adversaries</em>. Currently, the newer (and more extensive) <em>strategy generation</em> functionality is implemented just for the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>\"explicit\"</a> model checking engine,\nwhich is used automatically if strategy generation is requested.\nThe old <em>adversary generation</em> functionality (see below) still exists for the \"sparse\" engine, but will be updated in the future.\n</p>\n<p class='vspace'><strong>Generating strategies</strong>. Optimal strategies can be generated either from the command-line or the graphical user interface (GUI). For the former, use the <code>-exportstrat</code> switch. Simple examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat stdout</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.tra</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, you can trigger strategy generation by ticking the \"Generate strategy\" box either on the popup menu that appears when you right-click a property, or from the \"Strategies\" menu at the top. As long as it is supported, a strategy will be then generated once \"Verify\" is clicked.\n</p>\n<p class='vspace'>From the same menu(s), you can then\n</p>\n<div class='vspace'></div><ul><li>export the strategy to a file\n</li><li>view the strategy by printing it in the log\n</li><li>explore the strategy in the simulator\n</li></ul><p class='vspace'><strong>Strategy export types</strong>. Strategies can be viewed or exported in several different formats:\n</p>\n<p class='vspace'>(i) <em>Action list</em>. This is a list of the action taken in each state of the model, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"text\">(0,0):east<br />\n(0,1):north<br />\n(0,2):north<br />\n(1,0):south<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where states, by default, are shown as a tuple of variable values.\n</p>\n<p class='vspace'>(ii) <em>Induced model</em>. This is a representation of the model that is induced when the strategy is applied. There are two \"modes\" for this export. The first (and default) is \n<em>reduce</em>, which removes the nondeterminism resolved by the strategy (e.g., an MDP becomes a DTMC). This can be useful to re-import the model back into PRISM and analyse the induced model. The second is <em>restrict</em>, which shows the original model but with a restricted set of choices (e.g., an MDP with just one choice in each state). In each case, the transitions of the induced model are presented as a <code>.tra</code> file (as for normal <a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>model export</a>), e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"text\">9 11<br />\n0 5 1 east<br />\n1 10 1 north<br />\n2 15 0.9 north<br />\n2 16 0.1 north<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>(iii) <em>Dot file</em>. This is, like the previous format, a view of the model induced by the strategy, but in <a class='urllink' href='http://www.graphviz.org'>Dot</a> format, which allows it to be visualised.\n</p>\n<p class='vspace'><strong>Configuring strategy export</strong>. \nAs hinted in the command-line examples above, the <code>-exportstrat</code> switch uses the file extension to determine the preferred format: if the strategy is exported to a file with extension <code>.tra</code> or <code>.dot</code>, then it uses an induced model or Dot file, respectively. Otherwise, the default is an action list. You can specify the desired format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=actions</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Further options can be added, e.g., to specify whether an induced model is exported in \"restrict\" or \"reduce\" mode:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced,mode=restrict</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A full list of available options is as follows:\n</p>\n<div class='vspace'></div><ul><li><code>type</code> (<code>actions</code>, <code>induced</code> or <code>dot</code>): the type of strategy export to use (action list, induced model or Dot file)\n</li><li><code>mode</code> (<code>restrict</code> or <code>reduce</code>): when exporting as an induced model or Dot file, whether to \"restrict\" or \"reduce\" the model (see above); the default is \"restrict\"\n</li><li><code>reach</code> (<code>true</code> or <code>false</code>): whether to restrict the strategy to states that are reachable when it is applied to the model (this is currently only used for exporting induced models and Dot files, and the default value is false and true, respectively, in these two cases)\n</li><li><code>states</code> (<code>true</code> or <code>false</code>): whether to show states, rather than state indices, for actions lists or Dot files; this is true by default\n</li><li><code>obs</code> (<code>true</code> or <code>false</code>): for partially observable models, whether to merge observationally equivalent states; this is true by default\n</li></ul><p class='vspace'><strong>Strategy types</strong>. PRISM generates several types of strategies. The simplest are <em>memoryless deterministic</em> strategies, which pick a single action in each state, as in the examples above. For some query types (e.g., step-bounded properties, or LTL-based properties), <em>finite-memory</em> strategies are generated, where an additional memory value is used. For these, induced models or Dot files are most useful since they will also show how the memory values are updated as the strategy is executed. Note that, in these cases, the state indices of the strategy will correspond to the product model constructed during model checking, not the original model. The product model can be exported using the <code>-exportprodtrans</code> and <code>-exportprodstates</code> switches.\n</p>\n<p class='vspace'><strong>Adversary generation</strong>. As mentioned above, the \"sparse\" model checking engine still includes older so-called \"adversary generation\" functionality. This can be used to export the induced model to a file using the <code>-exportadv</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadv adv.tra -s</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadvmdp adv.tra -s</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where the <code>-exportadv</code> and <code>-exportadvmdp</code> export a DTMC and an MDP, respectively, i.e., corresponding to the \"reduce\" and \"restrict\" modes described above.\nFrom the GUI, change the \"Adversary export\" option (under the \"PRISM\" settings) from \"None\" to \"DTMC\" or \"MDP\". You can also change the filename for the export adversary which, by default, is <code>adv.tra</code> as in the example above.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Strategies.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Strategies@action=edit.html'>Edit</a> - <a class='wikilink' href='Strategies@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Strategies@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 03:36 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='selflink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Strategies@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Strategies | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Strategies.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Strategies@action=edit.html'>Edit</a> - <a class='wikilink' href='Strategies@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Strategies</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Strategies@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Strategies.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Strategies@action=edit.html'>Edit</a> - <a class='wikilink' href='Strategies@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Strategies@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 03:36 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='selflink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Strategies@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Strategies | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Strategies.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Strategies@action=edit.html'>Edit</a> - <a class='wikilink' href='Strategies@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Strategies</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Strategies@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Strategies.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Strategies@action=edit.html'>Edit</a> - <a class='wikilink' href='Strategies@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Strategies@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 03:36 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='selflink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/Strategies@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / Strategies </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for text\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.text .de1, .text .de2 {font-family: monospace; font-weight: normal;}\n.text  {font-family:monospace;}\n.text .imp {font-weight: bold; color: red;}\n.text li, .text .li1 {font-family: monospace; color: black; font-weight: normal;}\n.text .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.text .li2 {font-weight: bold;}\n.text .ln-xtra, .text li.ln-xtra, .text div.ln-xtra {background-color: #ffc;}\n.text span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Strategies</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Properties to be model checked on MDPs (and their variants, such as POMDPs or IMDPs) usually quantify over <em>strategies</em> (or <em>policies</em>) of the model, i.e., over the different possible ways that nondeterminism can be resolved in the model.\nFor example, this property:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">Pmax</span>=? [ <span class=\"prismkeyword\">F</span> \"<span class=\"prismident\">goal</span>\" ]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>determines the maximum probability, over all strategies, of reaching a state satisfying the label <code>\"goal\"</code>. When checking such properties, you can also ask PRISM to generate a corresponding (optimal) strategy, which yields this maximum probability when followed. The strategy can then be viewed, exported or simulated.\n</p>\n<p class='vspace'><strong>Note:</strong> For consistency across models, PRISM now uses the terminology <em>strategy</em> (rather than alternatives such as <em>policy</em>). In older versions of the tool, these were referred to as <em>adversaries</em>. Currently, the newer (and more extensive) <em>strategy generation</em> functionality is implemented just for the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>\"explicit\"</a> model checking engine,\nwhich is used automatically if strategy generation is requested.\nThe old <em>adversary generation</em> functionality (see below) still exists for the \"sparse\" engine, but will be updated in the future.\n</p>\n<p class='vspace'><strong>Generating strategies</strong>. Optimal strategies can be generated either from the command-line or the graphical user interface (GUI). For the former, use the <code>-exportstrat</code> switch. Simple examples are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat stdout</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.tra</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat strat.dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the GUI, you can trigger strategy generation by ticking the \"Generate strategy\" box either on the popup menu that appears when you right-click a property, or from the \"Strategies\" menu at the top. As long as it is supported, a strategy will be then generated once \"Verify\" is clicked.\n</p>\n<p class='vspace'>From the same menu(s), you can then\n</p>\n<div class='vspace'></div><ul><li>export the strategy to a file\n</li><li>view the strategy by printing it in the log\n</li><li>explore the strategy in the simulator\n</li></ul><p class='vspace'><strong>Strategy export types</strong>. Strategies can be viewed or exported in several different formats:\n</p>\n<p class='vspace'>(i) <em>Action list</em>. This is a list of the action taken in each state of the model, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"text\">(0,0):east<br />\n(0,1):north<br />\n(0,2):north<br />\n(1,0):south<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where states, by default, are shown as a tuple of variable values.\n</p>\n<p class='vspace'>(ii) <em>Induced model</em>. This is a representation of the model that is induced when the strategy is applied. There are two \"modes\" for this export. The first (and default) is \n<em>reduce</em>, which removes the nondeterminism resolved by the strategy (e.g., an MDP becomes a DTMC). This can be useful to re-import the model back into PRISM and analyse the induced model. The second is <em>restrict</em>, which shows the original model but with a restricted set of choices (e.g., an MDP with just one choice in each state). In each case, the transitions of the induced model are presented as a <code>.tra</code> file (as for normal <a class='wikilink' href='../Appendices/ExplicitModelFiles.html'>model export</a>), e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"text\">9 11<br />\n0 5 1 east<br />\n1 10 1 north<br />\n2 15 0.9 north<br />\n2 16 0.1 north<br />\n...</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>(iii) <em>Dot file</em>. This is, like the previous format, a view of the model induced by the strategy, but in <a class='urllink' href='http://www.graphviz.org'>Dot</a> format, which allows it to be visualised.\n</p>\n<p class='vspace'><strong>Configuring strategy export</strong>. \nAs hinted in the command-line examples above, the <code>-exportstrat</code> switch uses the file extension to determine the preferred format: if the strategy is exported to a file with extension <code>.tra</code> or <code>.dot</code>, then it uses an induced model or Dot file, respectively. Otherwise, the default is an action list. You can specify the desired format:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=actions</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=dot</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Further options can be added, e.g., to specify whether an induced model is exported in \"restrict\" or \"reduce\" mode:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.prism -pf 'Pmax=? [ F \"goal\" ]' -exportstrat file.txt:type=induced,mode=restrict</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A full list of available options is as follows:\n</p>\n<div class='vspace'></div><ul><li><code>type</code> (<code>actions</code>, <code>induced</code> or <code>dot</code>): the type of strategy export to use (action list, induced model or Dot file)\n</li><li><code>mode</code> (<code>restrict</code> or <code>reduce</code>): when exporting as an induced model or Dot file, whether to \"restrict\" or \"reduce\" the model (see above); the default is \"restrict\"\n</li><li><code>reach</code> (<code>true</code> or <code>false</code>): whether to restrict the strategy to states that are reachable when it is applied to the model (this is currently only used for exporting induced models and Dot files, and the default value is false and true, respectively, in these two cases)\n</li><li><code>states</code> (<code>true</code> or <code>false</code>): whether to show states, rather than state indices, for actions lists or Dot files; this is true by default\n</li><li><code>obs</code> (<code>true</code> or <code>false</code>): for partially observable models, whether to merge observationally equivalent states; this is true by default\n</li></ul><p class='vspace'><strong>Strategy types</strong>. PRISM generates several types of strategies. The simplest are <em>memoryless deterministic</em> strategies, which pick a single action in each state, as in the examples above. For some query types (e.g., step-bounded properties, or LTL-based properties), <em>finite-memory</em> strategies are generated, where an additional memory value is used. For these, induced models or Dot files are most useful since they will also show how the memory values are updated as the strategy is executed. Note that, in these cases, the state indices of the strategy will correspond to the product model constructed during model checking, not the original model. The product model can be exported using the <code>-exportprodtrans</code> and <code>-exportprodstates</code> switches.\n</p>\n<p class='vspace'><strong>Adversary generation</strong>. As mentioned above, the \"sparse\" model checking engine still includes older so-called \"adversary generation\" functionality. This can be used to export the induced model to a file using the <code>-exportadv</code> switch, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadv adv.tra -s</span><br/>\n<span style=\"font-weight:bold;\">prism mdp.nm -pf 'Pmax=? [ F \"goal\" ]' -exportadvmdp adv.tra -s</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/Strategies?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>where the <code>-exportadv</code> and <code>-exportadvmdp</code> export a DTMC and an MDP, respectively, i.e., corresponding to the \"reduce\" and \"restrict\" modes described above.\nFrom the GUI, change the \"Adversary export\" option (under the \"PRISM\" settings) from \"None\" to \"DTMC\" or \"MDP\". You can also change the filename for the export adversary which, by default, is <code>adv.tra</code> as in the example above.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/SupportForPEPAModels.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Support For PEPA Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SupportForPEPAModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForPEPAModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Support For PEPA Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>For CTMCs, PRISM also accepts model descriptions in the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='../Main/References.html#Hil96'>Hil96</a>].\nThe tool compiles such descriptions into the PRISM language and then constructs the model as normal.\nThe language accepted by the PEPA to PRISM compiler is actually a subset of PEPA.\nThe restrictions applied to the language are firstly that component identifiers can only be bound to sequential components\n(formed using prefix and choice and references to other sequential components only).\nSecondly, each local state of a  sequential component must be named.  For example, we would rewrite:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).(b,s).P;\n</li></ul><p class='vspace'>as:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).P';\n</li><li>P' = (b,s).P;\n</li></ul><p class='vspace'>Finally, active/active synchronisations are not allowed since the PRISM \ndefinition of these differs from the PEPA definition.  Every PEPA \nsynchronisation must have exactly one active component.\nSome examples of PEPA model descriptions which can be imported into PRISM\ncan be found in the <code>prism-examples/pepa</code> directory.\n</p>\n<p class='vspace'>From the command-line version of PRISM, add the <code>-importpepa</code> switch and the model will be treated as a PEPA description.\nFrom the GUI, select \"Model | Open model\" and then choose \"PEPA models\"\non the \"Files of type\" drop-down menu.\nAlternatively, select \"Model | New | PEPA model\" and either type a description from scratch\nor paste in an existing one from elsewhere.\nOnce the PEPA model has been successfully parsed by PRISM,\nyou can view the corresponding PRISM code (as generated by the PEPA-to-PRISM compiler)\nby selecting menu option \"Model | View | Parsed PRISM model\".\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SupportForPEPAModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForPEPAModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 23, 2019, at 07:59 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='selflink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/SupportForPEPAModels@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Support For PEPA Models | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SupportForPEPAModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForPEPAModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Support For PEPA Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='SupportForPEPAModels@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SupportForPEPAModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForPEPAModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 23, 2019, at 07:59 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='selflink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/SupportForPEPAModels@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Support For PEPA Models | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SupportForPEPAModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForPEPAModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Support For PEPA Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='SupportForPEPAModels@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SupportForPEPAModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForPEPAModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SupportForPEPAModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 23, 2019, at 07:59 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='selflink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='wikilink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/SupportForPEPAModels@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / SupportForPEPAModels </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Support For PEPA Models</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>For CTMCs, PRISM also accepts model descriptions in the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='../Main/References.html#Hil96'>Hil96</a>].\nThe tool compiles such descriptions into the PRISM language and then constructs the model as normal.\nThe language accepted by the PEPA to PRISM compiler is actually a subset of PEPA.\nThe restrictions applied to the language are firstly that component identifiers can only be bound to sequential components\n(formed using prefix and choice and references to other sequential components only).\nSecondly, each local state of a  sequential component must be named.  For example, we would rewrite:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).(b,s).P;\n</li></ul><p class='vspace'>as:\n</p>\n<div class='vspace'></div><ul><li>P = (a,r).P';\n</li><li>P' = (b,s).P;\n</li></ul><p class='vspace'>Finally, active/active synchronisations are not allowed since the PRISM \ndefinition of these differs from the PEPA definition.  Every PEPA \nsynchronisation must have exactly one active component.\nSome examples of PEPA model descriptions which can be imported into PRISM\ncan be found in the <code>prism-examples/pepa</code> directory.\n</p>\n<p class='vspace'>From the command-line version of PRISM, add the <code>-importpepa</code> switch and the model will be treated as a PEPA description.\nFrom the GUI, select \"Model | Open model\" and then choose \"PEPA models\"\non the \"Files of type\" drop-down menu.\nAlternatively, select \"Model | New | PEPA model\" and either type a description from scratch\nor paste in an existing one from elsewhere.\nOnce the PEPA model has been successfully parsed by PRISM,\nyou can view the corresponding PRISM code (as generated by the PEPA-to-PRISM compiler)\nby selecting menu option \"Model | View | Parsed PRISM model\".\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/SupportForSBML.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Support For SBML \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for xml\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.xml .de1, .xml .de2 {font-family: monospace; font-weight: normal;}\n.xml  {font-family:monospace;}\n.xml .imp {font-weight: bold; color: red;}\n.xml li, .xml .li1 {font-family: monospace; color: black; font-weight: normal;}\n.xml .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.xml .li2 {font-weight: bold;}\n.xml .es0 {color: #000099; font-weight: bold;}\n.xml .br0 {color: #66cc66;}\n.xml .sy0 {color: #66cc66;}\n.xml .st0 {color: #ff0000;}\n.xml .nu0 {color: #cc66cc;}\n.xml .sc-1 {color: #808080; font-style: italic;}\n.xml .sc0 {color: #00bbdd;}\n.xml .sc1 {color: #ddbb00;}\n.xml .sc2 {color: #339933;}\n.xml .sc3 {color: #009900;}\n.xml .re0 {color: #000066;}\n.xml .re1 {color: #000000; font-weight: bold;}\n.xml .re2 {color: #000000; font-weight: bold;}\n.xml .ln-xtra, .xml li.ln-xtra, .xml div.ln-xtra {background-color: #ffc;}\n.xml span.xtra { display:block; }\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SupportForSBML.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SupportForSBML@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForSBML@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Support For SBML</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM includes a (prototype) tool to translate specifications in <a class='urllink' href='http://sbml.org/'>SBML</a> (Systems Biology Markup Language) to model descriptions in the PRISM language. SBML is an XML-based format for representing models of biochemical reaction networks. The translator currently works with Level 2 Version 1 of the SBML specification, details of which can be found <a class='urllink' href='http://sbml.org/documents/'>here</a>.\n</p>\n<p class='vspace'>Since PRISM is a tool for analysing discrete-state systems, the translator is designed for SBML files intended for discrete stochastic simulation. A useful set of such files can be found in the CaliBayes <a class='urllink' href='http://code.google.com/p/dsmts/'>Discrete Stochastic Model Test Suite</a>. There are also many more SBML files available in the <a class='urllink' href='http://www.ebi.ac.uk/biomodels/'>BioModels Database</a>.\n</p>\n<p class='vspace'>We first give a simple example of an SBML file and its PRISM translation. We then give some more precise details of the translation process.\n</p>\n<div class='vspace'></div><h3>Example</h3>\n<p>An SBML file comprises a set of <em>species</em> and a set of <em>reactions</em> which they undergo. Below is the SBML file for the simple reversible reaction: <strong>Na + Cl &#8596; Na<sup>+</sup> + Cl<sup>-</sup></strong>, where there are initially 100 Na and Cl atoms and no ions, and the base rates for the forwards and backwards reactions are 100 and 10, respectively.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"xml\"><span class=\"re1\">&lt;?xml</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1.0&quot;</span> <span class=\"re0\">encoding</span>=<span class=\"st0\">&quot;UTF-8&quot;</span><span class=\"re2\">?&gt;</span><br />\n<span class=\"re1\">&lt;sbml</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.sbml.org/sbml/level2&quot;</span> <span class=\"re0\">metaid</span>=<span class=\"st0\">&quot;_000000&quot;</span> <span class=\"re0\">level</span>=<span class=\"st0\">&quot;2&quot;</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; <span class=\"re1\">&lt;model</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;nacl&quot;</span> <span class=\"re0\">name</span>=<span class=\"st0\">&quot;Na+Cl&quot;</span><span class=\"re2\">&gt;</span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;compartment</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;compartment&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na_plus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl_minus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactions<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>forwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;100&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>backwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na_plus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl_minus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;10&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactions<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; <span class=\"re1\">&lt;/model<span class=\"re2\">&gt;</span></span><br />\n<span class=\"re1\">&lt;/sbml<span class=\"re2\">&gt;</span></span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And here is the resulting PRISM code:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// File generated by automatic SBML-to-PRISM conversion</span><br/>\n<span class=\"prismcomment\">// Original SBML file: nacl.xml</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">MAX_AMOUNT</span> = <span class=\"prismnum\">100</span>;<br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction forwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">forwards_rate</span> = <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// forwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction backwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">backwards_rate</span> = <span class=\"prismnum\">10</span>; <span class=\"prismcomment\">// backwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na</span><br/>\n<br/>\n\t<span class=\"prismident\">na</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">na</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na</span> &lt;= <span class=\"prismident\">na_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl</span><br/>\n<br/>\n\t<span class=\"prismident\">cl</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">cl</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl</span> &lt;= <span class=\"prismident\">cl_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na_plus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_plus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na_plus</span><br/>\n<br/>\n\t<span class=\"prismident\">na_plus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_plus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na_plus</span> &lt;= <span class=\"prismident\">na_plus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">na_plus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl_minus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_minus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl_minus</span><br/>\n<br/>\n\t<span class=\"prismident\">cl_minus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_minus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl_minus</span> &lt;= <span class=\"prismident\">cl_minus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">cl_minus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reaction rates</span><br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">reaction_rates</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reward structures (one per species)</span><br/>\n<br/>\n<span class=\"prismcomment\">// 1</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 2</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 3</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na_plus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na_plus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 4</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl_minus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl_minus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the latter, we can use PRISM to generate a simple plot of the expected amount of Na and Na+ over time (using both model checking and a single random trace from the simulator):\n</p>\n<div class='vspace'></div><div class='img imgcaption'><a class='urllink' href='../uploads/sbml_ex_graph.png'><img src='../uploads/sbml_ex_graph.png' alt='' /></a><br /><span class='caption'><strong>Expected amount of Na/Na+ at time T</strong></span></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Using the translator</h3>\n<p>At present, the SBML-to-PRISM translator is included in the PRISM code-base, but not integrated into the application itself.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are using a binary (rather than source code) distribution of PRISM, replace <code>classes</code> with <code>lib/prism.jar</code> in the above.\n</p>\n<p class='vspace'>Alternatively (on Linux or Mac OS X), ensure <code>prism</code> is in your path and then save the script below as an executable file called <code>sbml2prism</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#!/bin/sh</span><br />\n<br />\n<span class=\"co0\"># Startup script for SBML-to-PRISM translator</span><br />\n<br />\n<span class=\"co0\"># Launch using main PRISM script</span><br />\n<span class=\"re2\">PRISM_MAINCLASS</span>=<span class=\"st0\">&quot;prism.SBML2Prism&quot;</span><br />\n<span class=\"kw3\">export</span> PRISM_MAINCLASS<br />\nprism <span class=\"st0\">&quot;$@&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Then use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">sbml2prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The following PRISM properties file will also be useful:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">c</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismident\">c</span>}=? [<span class=\"prismkeyword\">I</span>=<span class=\"prismident\">T</span>]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This contains a single property which, based on the reward structures in the PRISM model generated by the translator, means \"the expected amount of species <em>c</em> at time <em>T</em>\". The constant <em>c</em> is an integer index which can range between 1 and <em>N</em>, where <em>N</em> is the number of species in the model. To view the expected amount of each species over time, create an <a class='wikilink' href='Experiments.html'>experiment</a> in PRISM which varies <em>c</em> from 1 to <em>N</em> and <em>T</em> over the desired time range.\n</p>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Details of the translation</h3>\n<p>The basic structure of the translation process is as follows:\n</p>\n<div class='vspace'></div><ul><li>Each <em>species</em> in the SBML file is represented by a <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>module</a> in the resulting PRISM file. This module, which (where possible) retains the SBML species id as its name, contains a single <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variable</a> whose value represents the amount of the species present. A corresponding <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structure</a> for computing the expected amount of the species at a given time instant is also created. Species for which the <code>boundaryCondition</code> flag is set to <code>true</code> in the SBML file do not have a corresponding module.\n<div class='vspace'></div></li><li>Each <em>reaction</em> in the SBML file is associated with a unique <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation action label</a>. The module for each species which takes part in the reaction will include a synchronous <a class='wikilink' href='../ThePRISMLanguage/Commands.html'>command</a> to represent this. An additional PRISM module called <code>reaction_rates</code> stores the expression representing the rate of each reaction (from the corresponding <code>kineticLaw</code> section in the SBML file). Reaction stoichiometry information is respected but must be provided in the scalar <code>stoichiometry</code> field of a <code>speciesReference</code> element, not in a separate <code>StoichiometryMath</code> element.\n<div class='vspace'></div></li><li>Each <em>parameter</em> in the SBML file, either global to the file or specific to a reaction, becomes a <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constant</a> in the PRISM file. If a value for this parameter is given, it used. If not, the constant is left as undefined.\n</li></ul><p class='vspace'>As described above, this translation process is designed for discrete systems and so the amount of each species in the model is represented by an integer variable. It is therefore assumed that the initial amount for each species specified in the SBML file is also given as an integer. If this is not the case, then the values will need to be scaled accordingly first.\n</p>\n<p class='vspace'>Furthermore, since PRISM is primarily a model checking (rather than simulation) tool, it is important that the amount of each species also has an upper bound (to ensure a finite state space). When model checking, the efficiency (or even feasibility) of the process is likely to be very sensitive to the upper bound(s) chosen. When using the discrete-event simulation functionality of PRISM, this is not the case and the bounds can can be set much higher. By default the translator uses an upper bound of 100 (which is increased if the initial amount exceeds this). A different value can specified through a second command-line argument as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml 1000 &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, upper bounds can be modified manually after the translation process.\n</p>\n<p class='vspace'>Finally, The following aspects of SBML files are not currently supported and are ignored during the translation process:\n</p>\n<div class='vspace'></div><ul><li>compartments\n</li><li>events/triggers\n</li></ul>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SupportForSBML.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SupportForSBML@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForSBML@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SupportForSBML@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 11, 2012, at 12:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='selflink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/SupportForSBML@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Support For SBML | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SupportForSBML.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SupportForSBML@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForSBML@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Support For SBML</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='SupportForSBML@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SupportForSBML.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SupportForSBML@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForSBML@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SupportForSBML@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 11, 2012, at 12:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='selflink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/SupportForSBML@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Running PRISM / Support For SBML | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='SupportForSBML.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='SupportForSBML@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForSBML@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Support For SBML</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='SupportForSBML@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='SupportForSBML.html'>View</a> - <a rel='nofollow'  class='wikilink' href='SupportForSBML@action=edit.html'>Edit</a> - <a class='wikilink' href='SupportForSBML@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='SupportForSBML@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 11, 2012, at 12:04 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>Running PRISM</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Starting PRISM</a>\n</li><li><a class='wikilink' href='LoadingAndBuildingAModel.html'>Loading And Building a Model</a>\n</li><li><a class='wikilink' href='DebuggingModelsWithTheSimulator.html'>Debugging Models With The Simulator</a>\n</li><li><a class='wikilink' href='ExportingTheModel.html'>Exporting The Model</a>\n</li><li><a class='wikilink' href='ModelChecking.html'>Model Checking</a>\n</li><li><a class='wikilink' href='ApproximateModelChecking.html'>Statistical Model Checking</a>\n</li><li><a class='wikilink' href='ComputingSteady-stateAndTransientProbabilities.html'>Computing Steady-state And Transient Probabilities</a>\n</li><li><a class='wikilink' href='Experiments.html'>Experiments</a>\n</li><li><a class='wikilink' href='Strategies.html'>Strategies</a>\n</li><li><a class='wikilink' href='SupportForPEPAModels.html'>Support For PEPA Models</a>\n</li><li><a class='selflink' href='SupportForSBML.html'>Support For SBML</a>\n</li><li><a class='wikilink' href='ExplicitModelImport.html'>Explicit Model Import</a>\n</li><li><a class='wikilink' href='ParametricModelChecking.html'>Parametric Model Checking</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/RunningPRISM/SupportForSBML@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | RunningPRISM / SupportForSBML </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for xml\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.xml .de1, .xml .de2 {font-family: monospace; font-weight: normal;}\n.xml  {font-family:monospace;}\n.xml .imp {font-weight: bold; color: red;}\n.xml li, .xml .li1 {font-family: monospace; color: black; font-weight: normal;}\n.xml .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.xml .li2 {font-weight: bold;}\n.xml .es0 {color: #000099; font-weight: bold;}\n.xml .br0 {color: #66cc66;}\n.xml .sy0 {color: #66cc66;}\n.xml .st0 {color: #ff0000;}\n.xml .nu0 {color: #cc66cc;}\n.xml .sc-1 {color: #808080; font-style: italic;}\n.xml .sc0 {color: #00bbdd;}\n.xml .sc1 {color: #ddbb00;}\n.xml .sc2 {color: #339933;}\n.xml .sc3 {color: #009900;}\n.xml .re0 {color: #000066;}\n.xml .re1 {color: #000000; font-weight: bold;}\n.xml .re2 {color: #000000; font-weight: bold;}\n.xml .ln-xtra, .xml li.ln-xtra, .xml div.ln-xtra {background-color: #ffc;}\n.xml span.xtra { display:block; }\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n/**\n * GeSHi Dynamically Generated Stylesheet\n * --------------------------------------\n * Dynamically generated stylesheet for bash\n * CSS class: , CSS id: \n * GeSHi (C) 2004 - 2007 Nigel McNie, 2007 - 2014 Benny Baumann\n * (http://qbnz.com/highlighter/ and http://geshi.org/)\n * --------------------------------------\n */\n.bash .de1, .bash .de2 {font-family: monospace; font-weight: normal;}\n.bash  {font-family:monospace;}\n.bash .imp {font-weight: bold; color: red;}\n.bash li, .bash .li1 {font-family: monospace; color: black; font-weight: normal;}\n.bash .ln {width:1px;text-align:right;margin:0;padding:0 2px;vertical-align:top;}\n.bash .li2 {font-weight: bold;}\n.bash .kw1 {color: #000000; font-weight: bold;}\n.bash .kw2 {color: #c20cb9; font-weight: bold;}\n.bash .kw3 {color: #7a0874; font-weight: bold;}\n.bash .co0 {color: #666666; font-style: italic;}\n.bash .co1 {color: #800000;}\n.bash .co2 {color: #cc0000; font-style: italic;}\n.bash .co3 {color: #000000; font-weight: bold;}\n.bash .co4 {color: #666666;}\n.bash .es1 {color: #000099; font-weight: bold;}\n.bash .es2 {color: #007800;}\n.bash .es3 {color: #007800;}\n.bash .es4 {color: #007800;}\n.bash .es5 {color: #780078;}\n.bash .es_h {color: #000099; font-weight: bold;}\n.bash .br0 {color: #7a0874; font-weight: bold;}\n.bash .sy0 {color: #000000; font-weight: bold;}\n.bash .st0 {color: #ff0000;}\n.bash .st_h {color: #ff0000;}\n.bash .nu0 {color: #000000;}\n.bash .re0 {color: #007800;}\n.bash .re1 {color: #007800;}\n.bash .re2 {color: #007800;}\n.bash .re4 {color: #007800;}\n.bash .re5 {color: #660033;}\n.bash .ln-xtra, .bash li.ln-xtra, .bash div.ln-xtra {background-color: #ffc;}\n.bash span.xtra { display:block; }\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>Running PRISM</a> /\n</p><h1>Support For SBML</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM includes a (prototype) tool to translate specifications in <a class='urllink' href='http://sbml.org/'>SBML</a> (Systems Biology Markup Language) to model descriptions in the PRISM language. SBML is an XML-based format for representing models of biochemical reaction networks. The translator currently works with Level 2 Version 1 of the SBML specification, details of which can be found <a class='urllink' href='http://sbml.org/documents/'>here</a>.\n</p>\n<p class='vspace'>Since PRISM is a tool for analysing discrete-state systems, the translator is designed for SBML files intended for discrete stochastic simulation. A useful set of such files can be found in the CaliBayes <a class='urllink' href='http://code.google.com/p/dsmts/'>Discrete Stochastic Model Test Suite</a>. There are also many more SBML files available in the <a class='urllink' href='http://www.ebi.ac.uk/biomodels/'>BioModels Database</a>.\n</p>\n<p class='vspace'>We first give a simple example of an SBML file and its PRISM translation. We then give some more precise details of the translation process.\n</p>\n<div class='vspace'></div><h3>Example</h3>\n<p>An SBML file comprises a set of <em>species</em> and a set of <em>reactions</em> which they undergo. Below is the SBML file for the simple reversible reaction: <strong>Na + Cl &#8596; Na<sup>+</sup> + Cl<sup>-</sup></strong>, where there are initially 100 Na and Cl atoms and no ions, and the base rates for the forwards and backwards reactions are 100 and 10, respectively.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"xml\"><span class=\"re1\">&lt;?xml</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1.0&quot;</span> <span class=\"re0\">encoding</span>=<span class=\"st0\">&quot;UTF-8&quot;</span><span class=\"re2\">?&gt;</span><br />\n<span class=\"re1\">&lt;sbml</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.sbml.org/sbml/level2&quot;</span> <span class=\"re0\">metaid</span>=<span class=\"st0\">&quot;_000000&quot;</span> <span class=\"re0\">level</span>=<span class=\"st0\">&quot;2&quot;</span> <span class=\"re0\">version</span>=<span class=\"st0\">&quot;1&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; <span class=\"re1\">&lt;model</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;nacl&quot;</span> <span class=\"re0\">name</span>=<span class=\"st0\">&quot;Na+Cl&quot;</span><span class=\"re2\">&gt;</span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;compartment</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;compartment&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfCompartments<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;100&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;na_plus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;species</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;cl_minus&quot;</span> <span class=\"re0\">initialAmount</span>=<span class=\"st0\">&quot;0&quot;</span> <span class=\"re0\">hasOnlySubstanceUnits</span>=<span class=\"st0\">&quot;true&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfSpecies<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactions<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>forwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;forwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;100&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;reaction</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards&quot;</span> <span class=\"re0\">reversible</span>=<span class=\"st0\">&quot;false&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na_plus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl_minus&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactants<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;na&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;speciesReference</span> <span class=\"re0\">species</span>=<span class=\"st0\">&quot;cl&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfProducts<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;math</span> <span class=\"re0\">xmlns</span>=<span class=\"st0\">&quot;http://www.w3.org/1998/Math/MathML&quot;</span><span class=\"re2\">&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>backwards_rate<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;times</span><span class=\"re2\">/&gt;</span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>na_plus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;ci<span class=\"re2\">&gt;</span></span>cl_minus<span class=\"re1\">&lt;/ci<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><span class=\"re1\">&lt;/apply<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/math<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;parameter</span> <span class=\"re0\">id</span>=<span class=\"st0\">&quot;backwards_rate&quot;</span> <span class=\"re0\">value</span>=<span class=\"st0\">&quot;10&quot;</span><span class=\"re2\">/&gt;</span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/listOfParameters<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/kineticLaw<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; &nbsp; <span class=\"re1\">&lt;/reaction<span class=\"re2\">&gt;</span></span><br />\n&nbsp; &nbsp; <span class=\"re1\">&lt;/listOfReactions<span class=\"re2\">&gt;</span></span><br />\n<br />\n&nbsp; <span class=\"re1\">&lt;/model<span class=\"re2\">&gt;</span></span><br />\n<span class=\"re1\">&lt;/sbml<span class=\"re2\">&gt;</span></span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>And here is the resulting PRISM code:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// File generated by automatic SBML-to-PRISM conversion</span><br/>\n<span class=\"prismcomment\">// Original SBML file: nacl.xml</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">MAX_AMOUNT</span> = <span class=\"prismnum\">100</span>;<br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction forwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">forwards_rate</span> = <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// forwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Parameters for reaction backwards</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">backwards_rate</span> = <span class=\"prismnum\">10</span>; <span class=\"prismcomment\">// backwards_rate</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na</span><br/>\n<br/>\n\t<span class=\"prismident\">na</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">na</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na</span> &lt;= <span class=\"prismident\">na_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na</span>'=<span class=\"prismident\">na</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl</span><br/>\n<br/>\n\t<span class=\"prismident\">cl</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">100</span>; <span class=\"prismcomment\">// Initial amount 100</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] <span class=\"prismident\">cl</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>-<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl</span> &lt;= <span class=\"prismident\">cl_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl</span>'=<span class=\"prismident\">cl</span>+<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species na_plus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">na_plus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">na_plus</span><br/>\n<br/>\n\t<span class=\"prismident\">na_plus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">na_plus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">na_plus</span> &lt;= <span class=\"prismident\">na_plus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">na_plus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">na_plus</span>'=<span class=\"prismident\">na_plus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Species cl_minus</span><br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">cl_minus_MAX</span> = <span class=\"prismident\">MAX_AMOUNT</span>;<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">cl_minus</span><br/>\n<br/>\n\t<span class=\"prismident\">cl_minus</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">cl_minus_MAX</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <span class=\"prismcomment\">// Initial amount 0</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>]&nbsp;&nbsp;<span class=\"prismident\">cl_minus</span> &lt;= <span class=\"prismident\">cl_minus_MAX</span>-<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>+<span class=\"prismnum\">1</span>);<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] <span class=\"prismident\">cl_minus</span> &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">cl_minus</span>'=<span class=\"prismident\">cl_minus</span>-<span class=\"prismnum\">1</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reaction rates</span><br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">reaction_rates</span><br/>\n<br/>\n\t<span class=\"prismcomment\">// forwards</span><br/>\n\t[<span class=\"prismident\">forwards</span>] (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">forwards_rate</span>*(<span class=\"prismident\">na</span>*<span class=\"prismident\">cl</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n\t<span class=\"prismcomment\">// backwards</span><br/>\n\t[<span class=\"prismident\">backwards</span>] (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) &gt; <span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">backwards_rate</span>*(<span class=\"prismident\">na_plus</span>*<span class=\"prismident\">cl_minus</span>)) : <span class=\"prismkeyword\">true</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismcomment\">// Reward structures (one per species)</span><br/>\n<br/>\n<span class=\"prismcomment\">// 1</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 2</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 3</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">na_plus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">na_plus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n<span class=\"prismcomment\">// 4</span><br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">cl_minus</span>\" <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">cl_minus</span>; <span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>From the latter, we can use PRISM to generate a simple plot of the expected amount of Na and Na+ over time (using both model checking and a single random trace from the simulator):\n</p>\n<div class='vspace'></div><div class='img imgcaption'><a class='urllink' href='../uploads/sbml_ex_graph.png'><img src='../uploads/sbml_ex_graph.png' alt='' /></a><br /><span class='caption'><strong>Expected amount of Na/Na+ at time T</strong></span></div>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Using the translator</h3>\n<p>At present, the SBML-to-PRISM translator is included in the PRISM code-base, but not integrated into the application itself.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>If you are using a binary (rather than source code) distribution of PRISM, replace <code>classes</code> with <code>lib/prism.jar</code> in the above.\n</p>\n<p class='vspace'>Alternatively (on Linux or Mac OS X), ensure <code>prism</code> is in your path and then save the script below as an executable file called <code>sbml2prism</code>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"bash\"><span class=\"co0\">#!/bin/sh</span><br />\n<br />\n<span class=\"co0\"># Startup script for SBML-to-PRISM translator</span><br />\n<br />\n<span class=\"co0\"># Launch using main PRISM script</span><br />\n<span class=\"re2\">PRISM_MAINCLASS</span>=<span class=\"st0\">&quot;prism.SBML2Prism&quot;</span><br />\n<span class=\"kw3\">export</span> PRISM_MAINCLASS<br />\nprism <span class=\"st0\">&quot;$@&quot;</span></div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Then use:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">sbml2prism sbml_file.xml &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The following PRISM properties file will also be useful:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">T</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">c</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">R</span>{<span class=\"prismident\">c</span>}=? [<span class=\"prismkeyword\">I</span>=<span class=\"prismident\">T</span>]<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This contains a single property which, based on the reward structures in the PRISM model generated by the translator, means \"the expected amount of species <em>c</em> at time <em>T</em>\". The constant <em>c</em> is an integer index which can range between 1 and <em>N</em>, where <em>N</em> is the number of species in the model. To view the expected amount of each species over time, create an <a class='wikilink' href='Experiments.html'>experiment</a> in PRISM which varies <em>c</em> from 1 to <em>N</em> and <em>T</em> over the desired time range.\n</p>\n<div class='vspace'></div><hr />\n<div class='vspace'></div><h3>Details of the translation</h3>\n<p>The basic structure of the translation process is as follows:\n</p>\n<div class='vspace'></div><ul><li>Each <em>species</em> in the SBML file is represented by a <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>module</a> in the resulting PRISM file. This module, which (where possible) retains the SBML species id as its name, contains a single <a class='wikilink' href='../ThePRISMLanguage/ModulesAndVariables.html'>variable</a> whose value represents the amount of the species present. A corresponding <a class='wikilink' href='../ThePRISMLanguage/CostsAndRewards.html'>reward structure</a> for computing the expected amount of the species at a given time instant is also created. Species for which the <code>boundaryCondition</code> flag is set to <code>true</code> in the SBML file do not have a corresponding module.\n<div class='vspace'></div></li><li>Each <em>reaction</em> in the SBML file is associated with a unique <a class='wikilink' href='../ThePRISMLanguage/Synchronisation.html'>synchronisation action label</a>. The module for each species which takes part in the reaction will include a synchronous <a class='wikilink' href='../ThePRISMLanguage/Commands.html'>command</a> to represent this. An additional PRISM module called <code>reaction_rates</code> stores the expression representing the rate of each reaction (from the corresponding <code>kineticLaw</code> section in the SBML file). Reaction stoichiometry information is respected but must be provided in the scalar <code>stoichiometry</code> field of a <code>speciesReference</code> element, not in a separate <code>StoichiometryMath</code> element.\n<div class='vspace'></div></li><li>Each <em>parameter</em> in the SBML file, either global to the file or specific to a reaction, becomes a <a class='wikilink' href='../ThePRISMLanguage/Constants.html'>constant</a> in the PRISM file. If a value for this parameter is given, it used. If not, the constant is left as undefined.\n</li></ul><p class='vspace'>As described above, this translation process is designed for discrete systems and so the amount of each species in the model is represented by an integer variable. It is therefore assumed that the initial amount for each species specified in the SBML file is also given as an integer. If this is not the case, then the values will need to be scaled accordingly first.\n</p>\n<p class='vspace'>Furthermore, since PRISM is primarily a model checking (rather than simulation) tool, it is important that the amount of each species also has an upper bound (to ensure a finite state space). When model checking, the efficiency (or even feasibility) of the process is likely to be very sensitive to the upper bound(s) chosen. When using the discrete-event simulation functionality of PRISM, this is not the case and the bounds can can be set much higher. By default the translator uses an upper bound of 100 (which is increased if the initial amount exceeds this). A different value can specified through a second command-line argument as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"shell\"><span style=\"font-weight:bold;\">cd prism</span><br/>\n<span style=\"font-weight:bold;\">java -cp classes prism.SBML2Prism sbml_file.xml 1000 &gt; prism_file.sm</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/RunningPRISM/SupportForSBML?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Alternatively, upper bounds can be modified manually after the translation process.\n</p>\n<p class='vspace'>Finally, The following aspects of SBML files are not currently supported and are ignored during the translation process:\n</p>\n<div class='vspace'></div><ul><li>compartments\n</li><li>events/triggers\n</li></ul>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/AllOnOnePage.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Real-time Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>The PRISM Language</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>In order to construct and analyse a model with PRISM,\nit must be specified in the PRISM language,\na simple, state-based language,\nbased on the Reactive Modules formalism of Alur and Henzinger [<a class='wikilink' href='../Main/References.html#AH99'>AH99</a>].\nThis is used for <a class='wikilink' href='../Main/Introduction.html'>all of the types of model</a> that PRISM supports.\n</p>\n<p class='vspace'>In this section, we describe the PRISM language and present a number of small illustrative examples.\nA precise definition of the semantics of the language is available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site. One of the best ways to learn what can be done with the PRISM language is to look at some existing examples.\nA number of these are included with the tool distribution in the <code>prism-examples</code> directory.\nMany additional examples can be found on the \"<a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a>\" section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<p class='vspace'>The fundamental components of the PRISM language are <em>modules</em> and <em>variables</em>.\nA model is composed of a number of <em>modules</em> which can interact with each other.\nA module contains a number of local <em>variables</em>.\nThe values of these variables at any given time constitute the state of the module.\nThe <em>global state</em> of the whole model is determined by the <em>local state</em> of all modules.\nThe behaviour of each module is described by a set of <em>commands</em>.\nA command takes the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[<span class=\"prismident\">action</span>] <span class=\"prismident\">guard</span> -&gt; <span class=\"prismident\">prob_1</span> : <span class=\"prismident\">update_1</span> + ... + <span class=\"prismident\">prob_n</span> : <span class=\"prismident\">update_n</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <em>guard</em> is a predicate over all the variables in the model (including those belonging to other modules). Each <em>update</em> describes a transition which the module can make if the guard is true. A transition is specified by giving the new values of the variables in the module, possibly as a function of other variables. Each update is assigned a probability (or in some cases a rate) which will be assigned to the corresponding transition. The command also optionally includes an <em>action</em>, either just to annotate it, or for <a class='wikilink' href='Synchronisation.html'>synchronisation</a>.\n</p><hr />\n<h1>Example 1</h1>\n<p>We will use the following simple example to illustrate the basic concepts of the PRISM language.\nConsider a system comprising two identical processes which must operate under mutual exclusion.\nEach process can be in one of 3 states: {0,1,2}.\nFrom state 0, a process will move to state 1 with probability 0.2\nand remain in the same state with probability 0.8.\nFrom state 1, it tries to move to the critical section: state 2.\nThis can only occur if the other process is not in its critical section.\nFinally, from state 2, a process will either remain there or move back to state 0\nwith equal probability.\nThe PRISM code to describe an MDP model of this system can be seen below.\nIn the next sections, we explain each aspect of the code in turn.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 1</span><br/>\n<span class=\"prismcomment\">// Two process mutual exclusion</span><br/>\n<br/>\n<span class=\"prismkeyword\">mdp</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M1</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">y</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 1</strong>\n</p><hr />\n<h1>Model Type</h1>\n<p>As mentioned above, the PRISM language can be used to describe several types of probabilistic models.\nTo indicate which type is being described, a PRISM model usually includes a model type keyword:\n</p>\n<div class='vspace'></div><ul><li><code><strong>dtmc</strong></code>: discrete-time Markov chain\n</li><li><code><strong>ctmc</strong></code>: continuous-time Markov chain\n</li><li><code><strong>mdp</strong></code>: Markov decision process (or probabilistic automaton)\n</li><li><code><strong>pta</strong></code>: probabilistic timed automaton\n</li><li><code><strong>pomdp</strong></code>: partially observable Markov decision process\n</li><li><code><strong>popta</strong></code>: partially observable probabilistic timed automaton\n</li></ul><p class='vspace'>This is typically at the very start of the file,\nbut can actually occur anywhere in the file (except inside modules and other declarations).\n</p>\n<p class='vspace'>If no such model type declaration is included, the model is by default assumed to be an MDP.\nPRISM also performs some auto-detection of the model type;\nfor example, an MDP with <a class='wikilink' href='Real-timeModels.html'>clock variables</a> is assumed to be a PTA,\nand an MDP with <a class='createlinktext' rel='nofollow'\n    href='POMDPs@action=edit.html'>observables</a><a rel='nofollow' \n    class='createlink' href='POMDPs@action=edit.html'>?</a> is assumed to be a POMDP.\n</p>\n<p class='vspace'><strong>Note:</strong> For compatibility with old versions of PRISM,\nthe keywords <code><strong>probabilistic</strong></code>, <code><strong>stochastic</strong></code> and <code><strong>nondeterministic</strong></code>\ncan be used as alternatives for <code><strong>dtmc</strong></code>, <code><strong>ctmc</strong></code> and <code><strong>mdp</strong></code>, respectively.\n</p>\n<div class='vspace'></div><hr />\n<h1>Modules And Variables</h1>\n<p>The <a class='wikilink' href='Example1.html'>previous example</a> uses two modules, <code>M1</code> and <code>M2</code>, one representing each process.\nA module is specified as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">name</span> ... <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The definition of a module contains two parts: its <em>variables</em> and its <em>commands</em>.\nThe variables describe the possible states that the module can be in;\nthe <a class='wikilink' href='Commands.html'>commands</a> describe its behaviour, i.e. the way in which the state changes over time.\nCurrently, PRISM supports just a few simple types of variables:\nthey can either be (finite ranges of) integers or Booleans\n(we ignore <a class='wikilink' href='Real-timeModels.html'>clocks</a> for now).\n</p>\n<p class='vspace'>In the example above, each module has one integer variable with range <code>[0..2]</code>.\nA variable declaration looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the initial value of the variable is also specified.\nA Boolean variable is declared as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">false</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It is also possible to omit the initial value of a variable,\nin which case it is assumed to be the lowest value in the range (or <code>false</code> for a Boolean).\nThus, the variable declarations shown below are equivalent to the ones above.\nAs will be described later, it is also possible to specify\n<a class='wikilink' href='MultipleInitialStates.html'>multiple initial states</a> for a model.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>];<br/>\n<span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We also mention that, for a few kinds of model analysis (typically those based on simulation, such as <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a> or <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#fau'>fast adaptive simulation</a>, it is also permissable to use integer variables with unbounded ranges, denoted as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : <span class=\"prismkeyword\">int</span>;<br/>\n<span class=\"prismident\">y</span> : <span class=\"prismkeyword\">int</span> <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">3</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Where the state space of the model remains finite, despite the presence of such unbounded variables, you can use the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>explicit engine</a> to build and analyse the model.\n</p>\n<div class='vspace'></div><h3>Identifiers</h3>\n<p>The names given to modules and variables are referred to as <em>identifiers</em>.\nIdentifiers can be made up of letters, digits and the underscore character, but cannot begin with a digit,\ni.e. they must satisfy the regular expression [A-Za-z_][A-Za-z0-9_]*, and are case-sensitive.\nFurthermore, identifiers cannot be any of the following, which are all reserved keywords in PRISM:\n<code><strong>A</strong></code>,\n<code><strong>bool</strong></code>,\n<code><strong>clock</strong></code>,\n<code><strong>const</strong></code>,\n<code><strong>ctmc</strong></code>,\n<code><strong>C</strong></code>,\n<code><strong>double</strong></code>,\n<code><strong>dtmc</strong></code>,\n<code><strong>E</strong></code>,\n<code><strong>endinit</strong></code>,\n<code><strong>endinvariant</strong></code>,\n<code><strong>endmodule</strong></code>,\n<code><strong>endobservables</strong></code>,\n<code><strong>endrewards</strong></code>,\n<code><strong>endsystem</strong></code>,\n<code><strong>false</strong></code>,\n<code><strong>formula</strong></code>,\n<code><strong>filter</strong></code>,\n<code><strong>func</strong></code>,\n<code><strong>F</strong></code>,\n<code><strong>global</strong></code>,\n<code><strong>G</strong></code>,\n<code><strong>init</strong></code>,\n<code><strong>invariant</strong></code>,\n<code><strong>I</strong></code>,\n<code><strong>int</strong></code>,\n<code><strong>label</strong></code>,\n<code><strong>max</strong></code>,\n<code><strong>mdp</strong></code>,\n<code><strong>min</strong></code>,\n<code><strong>module</strong></code>,\n<code><strong>X</strong></code>,\n<code><strong>nondeterministic</strong></code>,\n<code><strong>observable</strong></code>,\n<code><strong>observables</strong></code>,\n<code><strong>of</strong></code>,\n<code><strong>Pmax</strong></code>,\n<code><strong>Pmin</strong></code>,\n<code><strong>P</strong></code>,\n<code><strong>pomdp</strong></code>,\n<code><strong>popta</strong></code>,\n<code><strong>probabilistic</strong></code>,\n<code><strong>prob</strong></code>,\n<code><strong>pta</strong></code>,\n<code><strong>rate</strong></code>,\n<code><strong>rewards</strong></code>,\n<code><strong>Rmax</strong></code>,\n<code><strong>Rmin</strong></code>,\n<code><strong>R</strong></code>,\n<code><strong>S</strong></code>,\n<code><strong>stochastic</strong></code>,\n<code><strong>system</strong></code>,\n<code><strong>true</strong></code>,\n<code><strong>U</strong></code>,\n<code><strong>W</strong></code>.\n</p><hr />\n<h1>Commands</h1>\n<p>The behaviour of each module is described by <em>commands</em>,\ncomprising a <em>guard</em> and one or more <em>updates</em>.\nThe first command of module <code>M1</code> in our <a class='wikilink' href='Example1.html'>example</a> is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The guard <code>x=0</code> indicates that this describes the behaviour of the module when the variable <code>x</code> has value 0.\nThe updates <code>(x'=0)</code> and <code>(x'=1)</code> and their associated probabilities state that the value of <code>x</code> will\nremain at 0 with probability 0.8 and change to 1 with probability 0.2.\nNote that the inclusion of updates in parentheses, e.g. <code>(x'=1)</code>, is essential.\nWhile older versions of PRISM did not report the absence of parentheses as an error, newer versions do.\nNote also that PRISM will complain if the probabilities on the right hand side of a command do not sum to one.\n</p>\n<p class='vspace'>The second command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>illustrates that guards can contain constraints on any variable, not just the ones in that module,\ni.e. the behaviour of one module can depend on the state of another.\nUpdates, however, can only specify values for variables belonging to the module.\nIn general a module can <em>read</em> the variables of any other module, but only <em>write</em> to its own.\nWhen a command comprises a single update with probability 1, the <code>1.0:</code> can be omitted,\nas is done in the example above.\n</p>\n<p class='vspace'>If a module has more than one variable, updates describe the new value for each of them.\nFor example, if it had two variables <code>x1</code> and <code>x2</code>, a possible command would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&lt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>+<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that elements of the updates are concatenated with <code>&amp;</code> and that each element must be bracketed individually.\nIf an update does not give a new value for a local variable, it is assumed not to change.\nAs a special case, the keyword <code><strong>true</strong></code> can be used to denote an update where no variable's value changes, i.e. the following are all equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Finally, it is important to remember that the expressions on the right hand side of each update refer to the state of the model <em>before</em> the update occurs. So, for example, this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>=<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x1</span>) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>updates variable <code>x2</code> to 0, not 2.\n</p>\n<div class='vspace'></div><hr />\n<h1>Parallel Composition</h1>\n<p>The probabilistic model corresponding to a PRISM language description is constructed as the <em>parallel composition</em> of its modules. In every state of the model, there is a set of commands (belonging to any of the modules) which are enabled, i.e. whose guards are satisfied in that state. The choice between which command is performed (i.e. the <em>scheduling</em>) depends on the model type.\n</p>\n<p class='vspace'>For an MDP, as in <a class='wikilink' href='Example1.html'>Example 1</a>, the choice is <em>nondeterministic</em>. By way of example, consider state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>). There are two commands enabled, one from each module:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In state <code>(0,0)</code> of the MDP, there would be a nondeterministic choice between these two probability distributions:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.2:(1,0)</code> (module <code>M1</code> moves)\n</li><li><code>0.8:(0,0) + 0.2:(0,1)</code> (module <code>M2</code> moves)\n</li></ul><p class='vspace'>For a DTMC, the choice is <em>probabilistic</em>: each enabled command is selected with equal probability.\nIf <a class='wikilink' href='Example1.html'>Example 1</a> was a DTMC, then in state <code>(0,0)</code> of the model\nthe following probability distribution would result:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.1:(1,0) + 0.1:(0,1)</code>\n</li></ul><p class='vspace'>For a <a class='wikilink' href='CTMCs.html'>CTMC</a>, as will be discussed shortly,\nthe choice is modelled as a \"race\" between transitions.\n</p>\n<p class='vspace'>See the later sections on \"<a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\" and \"<a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\" for other topics related to parallel composition.\n</p><hr />\n<h1>Local Nondeterminism</h1>\n<p>PRISM models that support nondeterminism, such as are MDPs, can also exhibit <em>local nondeterminism</em>,\nwhich allows the modules themselves to make nondeterministic choices.\nIn <a class='wikilink' href='Example1.html'>Example 1</a>, we can make the probabilistic choice in the first state of module <code>M1</code> nondeterministic by replacing the command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>with the commands:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Assuming we do the same for module <code>M2</code>, in state <code>(0,0)</code> of the MDP\nthere will be a nondeterministic choice between the three (trivial) probability distributions listed below. (There are three, not four, distributions because two possibilities result in identical behaviour: staying with probability 1 in the state state.)\n</p>\n<div class='vspace'></div><ul><li><code>1.0:(0,0)</code>\n</li><li><code>1.0:(1,0)</code>\n</li><li><code>1.0:(0,1)</code>\n</li></ul><p class='vspace'>More generally, local nondeterminism can also arise when the guards of two commands overlap only partially, rather than completely as in the example above.\n</p>\n<p class='vspace'>PRISM also permits local nondeterminism in models which are DTMCs,\nalthough the nondeterministic choice is randomised when the parallel composition of the modules occurs.\nSince the appearance of nondeterminism in a DTMC is often the result of\na user error in the model specification, PRISM displays a warning when local nondeterminism is detected in a DTMC.\nOverlapping guards in <a class='wikilink' href='CTMCs.html'>CTMCs</a> are not treated as nondeterministic choices.\n</p>\n<div class='vspace'></div><hr />\n<h1>CTMCs</h1>\n<p class='vspace'>Specifying the behaviour of a continuous-time Markov chain (CTMC)\nis done in similar fashion to a DTMC or an MDP, as discussed so far.\nThe main difference is that updates in commands are\nlabelled with (positive-valued) <em>rates</em>, rather than probabilities.\nThe notation used in commands, however, to associate rates to transitions is identical to\nthe one used to assign probabilities:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">rate_1</span>:<span class=\"prismident\">update_1</span> + <span class=\"prismident\">rate_2</span>:<span class=\"prismident\">update_2</span> + ... <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In a CTMC, when multiple possible transitions are available in a state, a <em>race condition</em> occurs\n(see e.g. [<a class='wikilink' href='../Main/References.html#KNP07a'>KNP07a</a>] for more details).\nIn terms of PRISM commands, this can arise in several ways.\nFirstly, within in a module, multiple transitions can be specified either as several different updates in a command, or as multiple commands with overlapping guards. The following, for example. are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Furthermore, parallel composition between modules in a CTMC is modelled as a race condition,\nrather as a nondeterministic choice, like for <a class='wikilink' href='ParallelComposition.html'>MDPs</a>.\n</p><hr />\n<h1>Example 2</h1>\n<p>We now introduce a second example: a CTMC that models an <em>N</em>-place queue of jobs and\na server which removes jobs from the queue and processes them.\nThe PRISM code is as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 2</span><br/>\n<span class=\"prismcomment\">// N-place queue + server</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span> = <span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mu</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">lambda</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">2</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">gamma</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">3</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">queue</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">q</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">N</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>&lt;<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>+<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>=<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">server</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">s</span>=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismident\">gamma</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">0</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 2</strong>\n</p>\n<p class='vspace'>This example also introduces a number of other PRISM language concepts,\nincluding <a class='wikilink' href='Constants.html'>constants</a>, action labels and <a class='wikilink' href='Synchronisation.html'>synchronisation</a>.\nThese are described in the following sections.\n</p><hr />\n<h1>Constants</h1>\n<p>PRISM supports the use of <em>constants</em>, as seen in <a class='wikilink' href='Example2.html'>Example 2</a>.\nConstants can be integers, doubles or Booleans\nand can be defined using literal values or as constant expressions (including in terms of each other) using the <code><strong>const</strong></code>\nkeyword. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">radius</span> = <span class=\"prismnum\">12</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">pi</span> = <span class=\"prismnum\">3.141592</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">area</span> = <span class=\"prismident\">pi</span> * <span class=\"prismident\">radius</span> * <span class=\"prismident\">radius</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">bool</span> <span class=\"prismident\">yes</span> = <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The identifiers used for their names are subject to the same rules as <a class='wikilink' href='ModulesAndVariables.html'>variables</a>.\n</p>\n<p class='vspace'>Constants can be used anywhere that a constant value would be expected,\nsuch as the lower or upper range of a variable (e.g. <code>N</code> in <a class='wikilink' href='Example2.html'>Example 2</a>),\nthe probability or rate associated with an update (<code>mu</code> in <a class='wikilink' href='Example2.html'>Example 2</a>),\nor anywhere in a guard or update.\nAs will be described later constants can also be left undefined\nand specified later, either to a single value or a range of values, using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'><strong>Note:</strong> For the sake of backward-compatibility, the notation used in earlier versions of PRISM\n(<code><strong>const</strong></code> for <code><strong>const int</strong></code> and <code><strong>rate</strong></code> or <code><strong>prob</strong></code> for <code><strong>const double</strong></code>) is still supported.\n</p><hr />\n<h1>Expressions</h1>\n<p>The definition of the <code>area</code> constant, in the example above, uses an <em>expression</em>.\nWe now define more precisely what types of expression are supported by PRISM.\nExpressions can contain literal values (12, 3.141592, <code><strong>true</strong></code>, <code><strong>false</strong></code>, etc.),\nidentifiers (corresponding to variables, constants, etc.) and operators from the following list:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>^</code> (power)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li></ul><p class='vspace'>All of these operators except <code>?</code> and <code>=&gt;</code> are left associative\n(i.e. they are evaluated from left to right).\nThe precedence of the operators is as found in the list above,\nmost strongly binding operators first.\nOperators on the same line (e.g. <code>+</code> and <code>-</code>) are of equal precedence.\n</p>\n<p class='vspace'>Much of the notation for expressions is hence essentially equivalent to that of C/C++ or Java.\nOne notable exception to this is that  the division operator <code>/</code> always performs floating point, not integer, division,\ni.e. the result of <code>22/7</code> is 3.142857... not 3.\nAll expressions must evaluate correctly in terms of type (integer, double or Boolean).\n</p>\n<p class='vspace'><strong>Built-in Functions</strong>\n</p>\n<p class='vspace'>Expressions can make use of several built-in functions:\n</p>\n<div class='vspace'></div><ul><li><code>min(...)</code> and <code>max(...)</code>, which select the minimum and maximum value, respectively, of two or more numbers\n</li><li><code>floor(x)</code> and <code>ceil(x)</code>, which round <code>x</code> down and up, respectively, to the nearest integer\n</li><li><code>round(x)</code>, which rounds <code>x</code> to the nearest integer (note, in a tie-break, we always round <em>up</em>, e.g. <code>round(-1.5)</code> gives <code>-1</code> not <code>-2</code>)\n</li><li><code>pow(x,y)</code> which computes <code>x</code> to the power of <code>y</code> (same as <code>x^y</code>)\n</li><li><code>mod(i,n)</code> for integer modulo operations\n</li><li><code>log(x,b)</code>, which computes the logarithm of <code>x</code> to base <code>b</code>\n</li></ul><p class='vspace'>Examples of their usage are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">min</span>(<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>, <span class=\"prismident\">x_max</span>)<br/>\n<span class=\"prismkeyword\">max</span>(<span class=\"prismident\">a</span>,<span class=\"prismident\">b</span>,<span class=\"prismident\">c</span>)<br/>\n<span class=\"prismident\">floor</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">ceil</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">round</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">2</span>, <span class=\"prismnum\">8</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">9.0</span>, <span class=\"prismnum\">0.5</span>)<br/>\n<span class=\"prismident\">mod</span>(<span class=\"prismnum\">1977</span>, <span class=\"prismnum\">100</span>)<br/>\n<span class=\"prismident\">log</span>(<span class=\"prismnum\">123</span>, <span class=\"prismnum\">2.71828183</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For compatibility with older versions of PRISM, all functions can also be expressed via the <code><strong>func</strong></code> keyword, e.g. <code>func(floor, 13.5)</code>.\n</p>\n<p class='vspace'><strong>Use of Expressions</strong>\n</p>\n<p class='vspace'>Expressions can be used in a wide range of places in a PRISM language description, e.g.:\n</p>\n<div class='vspace'></div><ul><li>constant definitions\n</li><li>lower/upper bounds and initial values for variables\n</li><li>guards\n</li><li>probabilities/rates\n</li><li>updates\n</li></ul><p class='vspace'>This allows, for example, the probability in a command to be dependent on the current state:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] (<span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span>) -&gt; <span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">max</span>(<span class=\"prismnum\">1</span>,<span class=\"prismident\">x</span>-<span class=\"prismnum\">1</span>)) + <span class=\"prismnum\">1</span>-<span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">min</span>(<span class=\"prismnum\">10</span>,<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>)) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Synchronisation</h1>\n<p>Another feature of PRISM introduced in <a class='wikilink' href='Example2.html'>Example 2</a> is <em>synchronisation</em>.\nIn the style of many process algebras, we allow commands to be labelled with <em>actions</em>.\nThese are placed inside the square brackets which mark the start of the command,\nfor example <code>serve</code> in this command from <a class='wikilink' href='Example2.html'>Example 2</a>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock24'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=24' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These actions can be used to force two or more modules to make transitions simultaneously\n(i.e. to <em>synchronise</em>).\nFor example, in state <code>(3,0)</code> (i.e.  <code>q=3</code> and <code>s=0</code>),\nthe composed model can move to state <code>(2,1)</code>,\nsynchronising over the <code>serve</code> action.\nThe rate of this transition is equal to the product of the two individual rates\n(in this case, <code>lambda * 1 = lambda</code>).\nThe product of two rates does not always meaningfully represent the rate of a synchronised transition.\nA common technique, as seen here, is to make one action <em>passive</em>, with rate 1 and one action <em>active</em>,\nwhich actually defines the rate for the synchronised transition.\nBy default, all modules are combined using the standard CSP parallel composition\n(i.e. modules synchronise over all their common actions).\n</p><hr />\n<h1>Module Renaming</h1>\n<p>PRISM also supports <em>module renaming</em>, which allows duplication of modules.\nIn <a class='wikilink' href='Example1.html'>Example 1</a>, module <code>M2</code> is identical to module <code>M1</code> so we can in fact replace its entire definition with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock25'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span> = <span class=\"prismident\">M1</span> [ <span class=\"prismident\">x</span>=<span class=\"prismident\">y</span>, <span class=\"prismident\">y</span>=<span class=\"prismident\">x</span> ] <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=25' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>All of the variables in the module being renamed (in this case, just <code>x</code>) <em>must</em> be renamed to new, unused names. Optionally, it is also possible to rename other aspects of the module definition. In fact, the renaming is done at a textual level, so any identifiers (including <a class='wikilink' href='Synchronisation.html'>action labels</a>, <a class='wikilink' href='Constants.html'>constants</a> and <a class='wikilink' href='Expressions.html'>functions</a>) used in the module definition can be changed in this way.\n</p>\n<p class='vspace'><strong>Note:</strong> Care should be taken when renaming modules that make use of <a class='wikilink' href='FormulasAndLabels.html'>formulas</a>.\n</p><hr />\n<h1>Multiple Initial States</h1>\n<p>Typically, a <a class='wikilink' href='ModulesAndVariables.html'>variable</a> declaration\nspecifies the initial value for that variable.\nThe <em>initial state</em> for the model is then defined by the initial value for all variables.\nIt is possible, however, to specify that a model has <em>multiple</em> initial states.\nThis is done using the <code><strong>init</strong>...<strong>endinit</strong></code> construct,\nwhich can be placed anywhere in the file except within a module definition,\nand removing any initial values from variable declarations.\nBetween the <code><strong>init</strong></code> and <code><strong>endinit</strong></code> keywords, there should be a\npredicate over all the variables of the model.\nAny state which satisfies this predicate is an initial state.\n</p>\n<p class='vspace'>Consider again <a class='wikilink' href='Example1.html'>Example 1</a>.\nAs it stands, there is a single initial state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>).\nIf we remove the <code><strong>init</strong> 0</code> part of both variable declarations\nand add the following to the end of the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock26'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=26' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>there will be three initial states: <code>(0,0)</code>, <code>(0,1)</code> and <code>(0,2)</code>.\nSimilarly, we could instead add:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock27'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>+<span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=27' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>in which case there would be two initial states: <code>(0,1)</code> and <code>(1,0)</code>.\n</p><hr />\n<h1>Global Variables</h1>\n<p>In addition to the local variables belonging to each module, a PRISM model can also include <em>global variables</em>,\nwhich can be written to, as well as read, by all modules.\nLike local variables, these can be integers or Booleans.\nGlobal variables are declared in identical fashion to a module's local variables,\nexcept that the declaration must not be inside the definition of any module.\nSome example declarations are as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock28'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">global</span> <span class=\"prismident\">g</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismnum\">10</span>];<br/>\n<span class=\"prismkeyword\">global</span> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=28' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A global variable can be modified by any module and provides another way for modules to interact.\nAn important restriction on the use of global variables is the fact that commands which synchronise with other modules\n(i.e. those with an action label attached; see the section \"<a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\") cannot modify global variables.\nPRISM will detect this and report an error.\n</p><hr />\n<h1>Formulas And Labels</h1>\n<p>PRISM models can include <em>formulas</em> which are used to avoid duplication of code.\nA formula comprises a name (an identifier) and an <a class='wikilink' href='Expressions.html'>expression</a>.\nThe formula name can then be used as shorthand for the expression anywhere an expression might usually be accepted.\nA formula is defined as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock29'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">formula</span> <span class=\"prismident\">num_tokens</span> = <span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=29' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It can then be used anywhere within that file, as for example in this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock30'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">num_tokens</span>=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=30' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The effect is exactly as if the following had been typed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock31'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; (<span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>)=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=31' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Formulas defined in a model can also be used when specifying its properties.\n</p>\n<div class='vspace'></div><h3>Formulas and renaming</h3>\n<p>During parsing of the model, expansion of formulas is done before module renaming so, if a module which uses formulas is renamed to another module, it is the contents of the formula which will be renamed, not the formula itself.\n</p>\n<div class='vspace'></div><h3>Labels</h3>\n<p>PRISM models can also contain <em>labels</em>. These are a way of identifying sets of states that are of particular interest. Labels can only be used when specifying <a class='wikilink' href='../PropertySpecification/Main.html'>properties</a> but, for convenience, can be defined in model files as well as property files. \n</p>\n<p class='vspace'>Labels differ from formulas in two other ways: firstly, they must be of Boolean type;\nsecondly, they are written using quotation marks (<code>\"...\"</code>), as illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock32'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=32' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Costs And Rewards </h1>\n<p>PRISM supports the specification and analysis of\nproperties based on <em>costs</em> and <em>rewards</em>.\nThis means that it can be used to reason,\nnot just about the probability that a model behaves in a certain fashion,\nbut about a wider range of quantitative measures relating to model behaviour.\nFor example, PRISM can be used to compute properties such as\n\"expected time\", \"expected number of lost messages\" or \"expected power consumption\".\nThe implementation of cost- and reward-based techniques in the tool is only partially completed and is still ongoing.\nIf you have questions, comments or feature-requests relating to this functionality,\nplease feel free to contact the PRISM team about this.\n</p>\n<p class='vspace'>The basic idea is that probabilistic models (of all types) developed in PRISM\ncan be augmented with costs or rewards: real values associated with certain states or transitions of the model.\nIn fact, since there is no practical distinction between costs and rewards\n(except that costs are generally perceived to be \"bad\" and rewards to be \"good\"),\nPRISM only supports rewards.\nThe user is, however, free to interpret the values however they choose.\n</p>\n<p class='vspace'>In this section, we describe how models described in the PRISM language\ncan be augmented with rewards.\nLater, we will discuss how to express properties that relate to these rewards.\nRewards are associated with models using <code><strong>rewards</strong> ... <strong>endrewards</strong></code> constructs,\nwhich can appear anywhere in a model file except within a module definition.\nThese constructs contains one or more <em>reward items</em>.\nConsider the following simple example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock33'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r1</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=33' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This defines a reward structure with name <code>r1</code> (the name is optional)\nwhich assigns a reward of 1 to every state of the model.\nIt comprises a single reward item, the left part of which (<code><strong>true</strong></code>) is a guard\nand the right part of which (<code>1</code>) is a reward.\nStates of the model which satisfy the predicate in the guard are assigned the corresponding reward.\nMore generally, state rewards can be specified using multiple reward items,\neach of the form <code>guard : reward;</code>,\nwhere <code>guard</code> is a predicate (over all the variables of the model)\nand <code>reward</code> is an expression (containing any variables, constants, etc. from the model).\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock34'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r2</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> : <span class=\"prismnum\">100</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&lt;<span class=\"prismnum\">10</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">10</span> : <span class=\"prismnum\">100</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=34' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 100 to states satisfying <code>x=0</code> or <code>x=10</code>\nand a reward of <code>2*x</code> to states satisfying <code>x&gt;0 &amp; x&lt;10</code>.\nNote that a single reward item can assign different rewards to different states,\ndepending on the values of model variables in each one.\nAny states which do not satisfy the guard of any reward item will have no reward assigned to them.\nFor states which satisfy multiple guards, the reward assigned to the state\nis the sum of the rewards for all the corresponding reward items.\n</p>\n<p class='vspace'>Rewards can also be assigned to transitions of a model.\nThese are specified in a similar fashion to state rewards,\nwithin the <code><strong>rewards</strong> ... <strong>endrewards</strong></code> construct.\nReward items describing transition rewards are of the form <code>[action] guard : reward;</code>,\nthe interpretation being that transitions from states which satisfy the guard <code>guard</code>\nand are labelled with the action <code>action</code> acquire the reward <code>reward</code>.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock35'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r3</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">a</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=35' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 1 to all transitions in the model with no action label,\nand rewards of <code>x</code> and <code>2*x</code> to all transitions labelled with actions <code>a</code> and <code>b</code>, respectively.\n</p>\n<p class='vspace'>As is the case for states, multiple reward items can specify rewards for a single transition,\nin which case the resulting reward is the sum of all the individual rewards.\nA model description can specify rewards for both states and transitions.\nThese are all placed together in a single <code><strong>rewards</strong>...<strong>endrewards</strong></code> construct.\n</p>\n<p class='vspace'>A PRISM model will often have multiple reward structures, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock36'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">total_time</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n<br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">num_failures</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">fail</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=36' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<h1>Real-time Models</h1>\n<p class='vspace'>So far in this section, we have mainly focused on three types of models: DTMCs, MDPs and CTMCs,\nin which all the variables making up their state are finite.\nPRISM also supports <em>real-time</em> models, in particular,\n<em>probabilistic timed automata</em> (PTAs), which extend MDPs with the ability to model real-time behaviour.\nThis is done in the style of <em>timed automata</em> [<a class='wikilink' href='../Main/References.html#AD94'>AD94</a>], by adding <em>clocks</em>,\nreal-valued variables which increase with time and can be reset. For background material on PTAs, see for example [<a class='wikilink' href='../Main/References.html#NPS13'>NPS13</a>].\nYou can also find several example PTA models included in the PRISM distribution. Look in the <code>prism-examples/ptas</code> directory.\n</p>\n<p class='vspace'>Before describing how PTA features are incorporated into the PRISM modelling language, we give a simple example. Here is a small PTA:\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/pta.png' alt='' /></div>\n<p class='vspace'>and here is a corresponding PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock37'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">pta</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : <span class=\"prismkeyword\">clock</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">invariant</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">2</span>) &amp;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">3</span>)<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">endinvariant</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">send</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismnum\">0.9</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">retry</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.95</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.05</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=37' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For modelling PTAs in PRISM, there is a new datatype, <strong><code>clock</code></strong>, used for variables that are clocks. Other types of PRISM variables can be defined in the usual way. In the example above, we use just a single integer variable <code>s</code> to represent the locations of the PTAs.\n</p>\n<p class='vspace'>In a PTA, transitions can include a <em>guard</em>, which constrains when it can occur based on the current value of clocks, and <em>resets</em>, which specify that a clock's values should be set to a new (integer) value. These are both specified in PRISM commands in the usual way: see, for example, the inclusion of <code>x&gt;=1</code> in the guard for the <code>send</code>-labelled command and the updates of the form <code>(x'=0)</code> which reset the clock <code>x</code> to 0.\n</p>\n<p class='vspace'>The other new addition is an <code>invariant</code> construct, which is used to specify an expression describing the clock <em>invariants</em> for each PRISM module. These impose restrictions on the allowable values of clock variables, depending on the values of the other non-clock variables. The <code>invariant</code> construct should appear between the variable declarations and the commands of the module. Often, clock invariants are described separately for each PTA location; hence, the invariant will often take the form of a conjunction of implications, as in the example model above, but more general expressions are also permitted. In the example, the clock <code>x</code> must satisfy <code>x&lt;=2</code> or <code>x&lt;=3</code> when local variables <code>s</code> is 0 or 2, respectively. If <code>s</code> is 1, there is no restriction (since the invariant is effectively <code>true</code> in this case).\n</p>\n<p class='vspace'>Expressions that include reference to clocks, whether in guards or invariants, must satisfy certain conditions to facilitate model checking. In particular, references to clocks must appear as conjunctions of <em>simple clock constraints</em>, i.e. conjunctions of expressions of the form <code>x~c</code> or <code>x~y</code> where <code>x</code> and <code>y</code> are clocks, <code>c</code> is an integer-valued expression and <code>~</code> is one of <code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code>, <code>=</code>).\n</p>\n<p class='vspace'>There are also some additional restrictions imposed on PTA models that are dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is in use.\n</p>\n<p class='vspace'>For the <strong>stochastic games</strong> and <strong>backwards reachability</strong> engines:\n</p>\n<div class='vspace'></div><ul><li>The model must also have a single initial state (i.e. the <code>init...endinit</code> construct is not permitted).\n</li></ul><p class='vspace'>For the <strong>digital clocks</strong> engine:\n</p>\n<div class='vspace'></div><ul><li>Clock constraints cannot use strict comparison operators, e.g. <code>x&lt;=5</code> is allowed, but <code>x&lt;5</code> is not.\n<div class='vspace'></div></li><li>Diagonal clock constraints are not allowed, i.e. those containing references to two clocks, such as <code>x&lt;=y</code>.\n</li></ul><p class='vspace'>Finally, PRISM makes several assumptions about PTAs, regardless of the engine used.\n</p>\n<div class='vspace'></div><ul><li>Firstly PTAs should not exhibit <em>timelocks</em>, i.e. the possibility of reaching a state where no transitions are possible and time cannot elapse beyond a certain point (due to invariant conditions). PRISM checks for timelocks and reports an error if one is found.\n<div class='vspace'></div></li><li>Secondly, PTAs should be <em>well-formed</em> and <em>non-zeno</em> (see e.g. [<a class='wikilink' href='../Main/References.html#KNSW07'>KNSW07</a>] for details). Currently, PRISM does not check automatically that these assumptions are satisfied.\n</li></ul><div class='vspace'></div><hr />\n<h1>Partially Observable Models</h1>\n<p>PRISM supports analysis of <em>partially observable</em> probabilistic models,\nmost notably partially observable Markov decision processes (POMDPs),\nbut also partially observable probabilistic timed automata (POPTAs).\nPOMDPs are a variant of MDPs in which the strategy/policy\nwhich resolves nondeterministic choices in the model is unable to\nsee the precise state of the model, but instead just <em>observations</em> of it.\nFor background material on POMDPs and POPTAs, see for example [<a class='wikilink' href='../Main/References.html#NPZ17'>NPZ17</a>].\nYou can also find several example models included in the PRISM distribution.\nLook in the <code>prism-examples/pomdps</code> and <code>prism-examples/poptas</code> directories.\n</p>\n<p class='vspace'>PRISM currently supports state-based observations:\nthis means that, upon entering a new POMDP state,\nthe observation is determined by that state.\nIn the same way that a model state comprises the values or one or more variables,\nan observation comprises one or more <em>observables</em>.\nThere are several way to define these observables.\nThe simplest is to specify a subset of the model's variables\nthat are designated as being observable. The rest are unobservable.\n</p>\n<p class='vspace'>For example, in a POMDP with 3 variables, <code>s</code>, <code>l</code> and <code>h</code>, the following:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock38'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">observables</span> <span class=\"prismident\">s</span>, <span class=\"prismident\">l</span> <span class=\"prismkeyword\">endobservables</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=38' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>specifies that <code>s</code> and <code>l</code> are observable and <code>h</code> is not.\n</p>\n<p class='vspace'>Alternatively, observables can be specified as arbitrary expressions over variables.\nFor example, assuming the same variables <code>s</code>, <code>l</code> and <code>h</code>, this specification:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock39'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">s</span>\" = <span class=\"prismident\">s</span>;<br/>\n<span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">pos</span>\" = <span class=\"prismident\">l</span>&gt;<span class=\"prismnum\">0</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=39' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>defines 2 observables. The first is, as above, the variable <code>s</code>.\nThe second, named <code>\"pos\"</code>, determines if variable <code>l</code> is positive.\nOther than this, the values of <code>l</code> and <code>h</code> are unobservable.\nThe named observables can then be used in properties\nin the same way that <a class='wikilink' href='FormulasAndLabels.html'>labels</a> can.\n</p>\n<p class='vspace'>The above two styles of definition can also be mixed\nto specify a combined set of observables.\n</p>\n<p class='vspace'>POPTAs (partially observable PTAs) combine the features of both PTAs and POMDPs.\nThey are are currently analysed using the digital clocks engine,\nso inherit the <a class='wikilink' href='Real-timeModels.html'>restrictions for that engine</a>.\nFurthermore, for a POPTA, all clock variables must be observable.\n</p><hr />\n<h1>Uncertain models</h1>\n<p>PRISM has support for <em>uncertain</em> models, in which there is epistemic uncertainty regarding some quantitative aspects of the probabilistic models being verified. In particular, it currently supports <em>interval MDPs</em> (IMDPs) and <em>interval DTMCs</em> (IDTMCs), which are MDPs or DTMCs in which transition probabilities can be specified as intervals, indicating that the exact probability is not precisely known. This can be useful, for example, when the transition probabilities have been estimated from data.\n</p>\n<p class='vspace'>Currently, this is achieved by simply replacing the probabilities attached to updates in commands with intervals, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock40'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismnum\">0.8</span>,<span class=\"prismnum\">0.9</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.1</span>,<span class=\"prismnum\">0.2</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=40' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As usual, the probability thresholds can be expressions involving state variables or constants, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock41'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismident\">p</span>,<span class=\"prismident\">p</span>+<span class=\"prismnum\">0.1</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.9</span>-<span class=\"prismident\">p</span>,<span class=\"prismnum\">1</span>-<span class=\"prismident\">p</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=41' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When two commands in different modules <a class='wikilink' href='Synchronisation.html'>synchronise</a> and specify the probabilities for updates to variables as intervals, these are considered to be independent, i.e., the probability of each combined transition is taken to be the product of the two component intervals.\n</p>\n<p class='vspace'>See the <a class='wikilink' href='../PropertySpecification/UncertainModels.html'>property specification</a> section for details of how these models are analysed.\n</p><hr />\n<h1>Process Algebra Operators</h1>\n<p>To make the concept of synchronisation described above more powerful,\nPRISM allows you to define precisely the way in which the set of modules are composed in parallel.\nThis is specified using the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct,\nplaced at the end of the model description, which should contain a process-algebraic expression.\nThis expression should feature each module exactly once, and can use the following (CSP-based) operators:\n</p>\n<div class='vspace'></div><ul><li><code>M1 || M2</code> : alphabetised parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising on only actions appearing in both <code>M1</code> and <code>M2</code>)\n<div class='vspace'></div></li><li><code>M1 ||| M2</code> : asynchronous parallel composition of <code>M1</code> and <code>M2</code> (fully interleaved, no synchronisation)\n<div class='vspace'></div></li><li><code>M1 |[a,b,...]| M2</code> : restricted parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising only on actions from the set {<code>a</code>, <code>b</code>,...})\n<div class='vspace'></div></li><li><code>M / {a,b,...</code>} : hiding of actions {<code>a</code>, <code>b</code>, ...} in module <code>M</code>\n<div class='vspace'></div></li><li><code>M {a&lt;-b,c&lt;-d,...</code>} : renaming of actions <code>a</code> to <code>b</code>, <code>c</code> to <code>d</code>, etc. in module <code>M</code>.\n</li></ul><p class='vspace'>The first two types of parallel composition (<code>||</code> and <code>|||</code>) are associative and can be applied to more than two modules at once.\nWhen evaluating the expression, the hiding and renaming operators bind more tightly than the three parallel composition operators.\nNo other rules of precedence are defined and parentheses should be used to specify the order in which modules are composed.\n</p>\n<p class='vspace'>Some examples of expressions which could be included in the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct are as follows:\n</p>\n<div class='vspace'></div><ul><li><code>(station1 ||| station2 ||| station3) |[serve]| server</code>\n</li><li><code>((P1 |[a]| P2) / {a}) || Q</code>\n</li><li><code>((P1 |[a]| P2) {a&lt;-b}) |[b]| Q</code>\n</li></ul><p class='vspace'>When no parallel composition is specified by the user,\nPRISM implicitly assumes an expression of the form <code>M1 || M2 || ...</code> containing all of the modules in the model.\nFor a more formal definition of the process algebra operators described above, check the semantics of the PRISM language, available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site.\n</p>\n<p class='vspace'>PRISM is also able to <a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>import</a> model descriptions written in (a subset of) the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='../Main/References.html#Hil96'>Hil96</a>].\n</p><hr />\n<h1>PRISM Model Files</h1>\n<p>Files containing model descriptions written in the PRISM language\ncan contain any amount of white space (spaces, tabs, new lines, etc.),\nall of which is ignored when the file is parsed by the tool.\nComments can also be used included in files in the style of the C programming language,\nby preceding them with the characters <code>//</code>.\nThis is illustrated by the PRISM language examples from earlier in this section.\n</p>\n<p class='vspace'>We recommend that the <code>.prism</code> extension is used for PRISM model files.\nHistorically (when the tool supported fewer types of model),\ndifferent extensions were often used for each model type:\n<code>.nm</code> for MDPs or PTAs, <code>.pm</code> for DTMCs and <code>.sm</code> for CTMCs.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:54 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/AllOnOnePage@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / All On One Page | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:54 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/AllOnOnePage@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / All On One Page | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='AllOnOnePage.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>All On One Page</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='AllOnOnePage@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='AllOnOnePage.html'>View</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=edit.html'>Edit</a> - <a class='wikilink' href='AllOnOnePage@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='AllOnOnePage@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:54 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='selflink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/AllOnOnePage@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Real-time Models </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt--><!--PageText-->\n<div id='wikitext'>\n<div class='vspace'></div><h1><span class='big'>The PRISM Language</span></h1>\n<hr />\n<h1>Introduction</h1>\n<p>In order to construct and analyse a model with PRISM,\nit must be specified in the PRISM language,\na simple, state-based language,\nbased on the Reactive Modules formalism of Alur and Henzinger [<a class='wikilink' href='../Main/References.html#AH99'>AH99</a>].\nThis is used for <a class='wikilink' href='../Main/Introduction.html'>all of the types of model</a> that PRISM supports.\n</p>\n<p class='vspace'>In this section, we describe the PRISM language and present a number of small illustrative examples.\nA precise definition of the semantics of the language is available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site. One of the best ways to learn what can be done with the PRISM language is to look at some existing examples.\nA number of these are included with the tool distribution in the <code>prism-examples</code> directory.\nMany additional examples can be found on the \"<a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a>\" section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<p class='vspace'>The fundamental components of the PRISM language are <em>modules</em> and <em>variables</em>.\nA model is composed of a number of <em>modules</em> which can interact with each other.\nA module contains a number of local <em>variables</em>.\nThe values of these variables at any given time constitute the state of the module.\nThe <em>global state</em> of the whole model is determined by the <em>local state</em> of all modules.\nThe behaviour of each module is described by a set of <em>commands</em>.\nA command takes the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[<span class=\"prismident\">action</span>] <span class=\"prismident\">guard</span> -&gt; <span class=\"prismident\">prob_1</span> : <span class=\"prismident\">update_1</span> + ... + <span class=\"prismident\">prob_n</span> : <span class=\"prismident\">update_n</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <em>guard</em> is a predicate over all the variables in the model (including those belonging to other modules). Each <em>update</em> describes a transition which the module can make if the guard is true. A transition is specified by giving the new values of the variables in the module, possibly as a function of other variables. Each update is assigned a probability (or in some cases a rate) which will be assigned to the corresponding transition. The command also optionally includes an <em>action</em>, either just to annotate it, or for <a class='wikilink' href='Synchronisation.html'>synchronisation</a>.\n</p><hr />\n<h1>Example 1</h1>\n<p>We will use the following simple example to illustrate the basic concepts of the PRISM language.\nConsider a system comprising two identical processes which must operate under mutual exclusion.\nEach process can be in one of 3 states: {0,1,2}.\nFrom state 0, a process will move to state 1 with probability 0.2\nand remain in the same state with probability 0.8.\nFrom state 1, it tries to move to the critical section: state 2.\nThis can only occur if the other process is not in its critical section.\nFinally, from state 2, a process will either remain there or move back to state 0\nwith equal probability.\nThe PRISM code to describe an MDP model of this system can be seen below.\nIn the next sections, we explain each aspect of the code in turn.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 1</span><br/>\n<span class=\"prismcomment\">// Two process mutual exclusion</span><br/>\n<br/>\n<span class=\"prismkeyword\">mdp</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M1</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">y</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 1</strong>\n</p><hr />\n<h1>Model Type</h1>\n<p>As mentioned above, the PRISM language can be used to describe several types of probabilistic models.\nTo indicate which type is being described, a PRISM model usually includes a model type keyword:\n</p>\n<div class='vspace'></div><ul><li><code><strong>dtmc</strong></code>: discrete-time Markov chain\n</li><li><code><strong>ctmc</strong></code>: continuous-time Markov chain\n</li><li><code><strong>mdp</strong></code>: Markov decision process (or probabilistic automaton)\n</li><li><code><strong>pta</strong></code>: probabilistic timed automaton\n</li><li><code><strong>pomdp</strong></code>: partially observable Markov decision process\n</li><li><code><strong>popta</strong></code>: partially observable probabilistic timed automaton\n</li></ul><p class='vspace'>This is typically at the very start of the file,\nbut can actually occur anywhere in the file (except inside modules and other declarations).\n</p>\n<p class='vspace'>If no such model type declaration is included, the model is by default assumed to be an MDP.\nPRISM also performs some auto-detection of the model type;\nfor example, an MDP with <a class='wikilink' href='Real-timeModels.html'>clock variables</a> is assumed to be a PTA,\nand an MDP with <a class='createlinktext' rel='nofollow'\n    href='POMDPs@action=edit.html'>observables</a><a rel='nofollow' \n    class='createlink' href='POMDPs@action=edit.html'>?</a> is assumed to be a POMDP.\n</p>\n<p class='vspace'><strong>Note:</strong> For compatibility with old versions of PRISM,\nthe keywords <code><strong>probabilistic</strong></code>, <code><strong>stochastic</strong></code> and <code><strong>nondeterministic</strong></code>\ncan be used as alternatives for <code><strong>dtmc</strong></code>, <code><strong>ctmc</strong></code> and <code><strong>mdp</strong></code>, respectively.\n</p>\n<div class='vspace'></div><hr />\n<h1>Modules And Variables</h1>\n<p>The <a class='wikilink' href='Example1.html'>previous example</a> uses two modules, <code>M1</code> and <code>M2</code>, one representing each process.\nA module is specified as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">name</span> ... <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The definition of a module contains two parts: its <em>variables</em> and its <em>commands</em>.\nThe variables describe the possible states that the module can be in;\nthe <a class='wikilink' href='Commands.html'>commands</a> describe its behaviour, i.e. the way in which the state changes over time.\nCurrently, PRISM supports just a few simple types of variables:\nthey can either be (finite ranges of) integers or Booleans\n(we ignore <a class='wikilink' href='Real-timeModels.html'>clocks</a> for now).\n</p>\n<p class='vspace'>In the example above, each module has one integer variable with range <code>[0..2]</code>.\nA variable declaration looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the initial value of the variable is also specified.\nA Boolean variable is declared as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">false</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It is also possible to omit the initial value of a variable,\nin which case it is assumed to be the lowest value in the range (or <code>false</code> for a Boolean).\nThus, the variable declarations shown below are equivalent to the ones above.\nAs will be described later, it is also possible to specify\n<a class='wikilink' href='MultipleInitialStates.html'>multiple initial states</a> for a model.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock6'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>];<br/>\n<span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=6' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We also mention that, for a few kinds of model analysis (typically those based on simulation, such as <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a> or <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#fau'>fast adaptive simulation</a>, it is also permissable to use integer variables with unbounded ranges, denoted as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock7'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : <span class=\"prismkeyword\">int</span>;<br/>\n<span class=\"prismident\">y</span> : <span class=\"prismkeyword\">int</span> <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">3</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=7' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Where the state space of the model remains finite, despite the presence of such unbounded variables, you can use the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>explicit engine</a> to build and analyse the model.\n</p>\n<div class='vspace'></div><h3>Identifiers</h3>\n<p>The names given to modules and variables are referred to as <em>identifiers</em>.\nIdentifiers can be made up of letters, digits and the underscore character, but cannot begin with a digit,\ni.e. they must satisfy the regular expression [A-Za-z_][A-Za-z0-9_]*, and are case-sensitive.\nFurthermore, identifiers cannot be any of the following, which are all reserved keywords in PRISM:\n<code><strong>A</strong></code>,\n<code><strong>bool</strong></code>,\n<code><strong>clock</strong></code>,\n<code><strong>const</strong></code>,\n<code><strong>ctmc</strong></code>,\n<code><strong>C</strong></code>,\n<code><strong>double</strong></code>,\n<code><strong>dtmc</strong></code>,\n<code><strong>E</strong></code>,\n<code><strong>endinit</strong></code>,\n<code><strong>endinvariant</strong></code>,\n<code><strong>endmodule</strong></code>,\n<code><strong>endobservables</strong></code>,\n<code><strong>endrewards</strong></code>,\n<code><strong>endsystem</strong></code>,\n<code><strong>false</strong></code>,\n<code><strong>formula</strong></code>,\n<code><strong>filter</strong></code>,\n<code><strong>func</strong></code>,\n<code><strong>F</strong></code>,\n<code><strong>global</strong></code>,\n<code><strong>G</strong></code>,\n<code><strong>init</strong></code>,\n<code><strong>invariant</strong></code>,\n<code><strong>I</strong></code>,\n<code><strong>int</strong></code>,\n<code><strong>label</strong></code>,\n<code><strong>max</strong></code>,\n<code><strong>mdp</strong></code>,\n<code><strong>min</strong></code>,\n<code><strong>module</strong></code>,\n<code><strong>X</strong></code>,\n<code><strong>nondeterministic</strong></code>,\n<code><strong>observable</strong></code>,\n<code><strong>observables</strong></code>,\n<code><strong>of</strong></code>,\n<code><strong>Pmax</strong></code>,\n<code><strong>Pmin</strong></code>,\n<code><strong>P</strong></code>,\n<code><strong>pomdp</strong></code>,\n<code><strong>popta</strong></code>,\n<code><strong>probabilistic</strong></code>,\n<code><strong>prob</strong></code>,\n<code><strong>pta</strong></code>,\n<code><strong>rate</strong></code>,\n<code><strong>rewards</strong></code>,\n<code><strong>Rmax</strong></code>,\n<code><strong>Rmin</strong></code>,\n<code><strong>R</strong></code>,\n<code><strong>S</strong></code>,\n<code><strong>stochastic</strong></code>,\n<code><strong>system</strong></code>,\n<code><strong>true</strong></code>,\n<code><strong>U</strong></code>,\n<code><strong>W</strong></code>.\n</p><hr />\n<h1>Commands</h1>\n<p>The behaviour of each module is described by <em>commands</em>,\ncomprising a <em>guard</em> and one or more <em>updates</em>.\nThe first command of module <code>M1</code> in our <a class='wikilink' href='Example1.html'>example</a> is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock8'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=8' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The guard <code>x=0</code> indicates that this describes the behaviour of the module when the variable <code>x</code> has value 0.\nThe updates <code>(x'=0)</code> and <code>(x'=1)</code> and their associated probabilities state that the value of <code>x</code> will\nremain at 0 with probability 0.8 and change to 1 with probability 0.2.\nNote that the inclusion of updates in parentheses, e.g. <code>(x'=1)</code>, is essential.\nWhile older versions of PRISM did not report the absence of parentheses as an error, newer versions do.\nNote also that PRISM will complain if the probabilities on the right hand side of a command do not sum to one.\n</p>\n<p class='vspace'>The second command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock9'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=9' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>illustrates that guards can contain constraints on any variable, not just the ones in that module,\ni.e. the behaviour of one module can depend on the state of another.\nUpdates, however, can only specify values for variables belonging to the module.\nIn general a module can <em>read</em> the variables of any other module, but only <em>write</em> to its own.\nWhen a command comprises a single update with probability 1, the <code>1.0:</code> can be omitted,\nas is done in the example above.\n</p>\n<p class='vspace'>If a module has more than one variable, updates describe the new value for each of them.\nFor example, if it had two variables <code>x1</code> and <code>x2</code>, a possible command would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock10'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&lt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>+<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=10' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that elements of the updates are concatenated with <code>&amp;</code> and that each element must be bracketed individually.\nIf an update does not give a new value for a local variable, it is assumed not to change.\nAs a special case, the keyword <code><strong>true</strong></code> can be used to denote an update where no variable's value changes, i.e. the following are all equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock11'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=11' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Finally, it is important to remember that the expressions on the right hand side of each update refer to the state of the model <em>before</em> the update occurs. So, for example, this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock12'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>=<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x1</span>) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=12' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>updates variable <code>x2</code> to 0, not 2.\n</p>\n<div class='vspace'></div><hr />\n<h1>Parallel Composition</h1>\n<p>The probabilistic model corresponding to a PRISM language description is constructed as the <em>parallel composition</em> of its modules. In every state of the model, there is a set of commands (belonging to any of the modules) which are enabled, i.e. whose guards are satisfied in that state. The choice between which command is performed (i.e. the <em>scheduling</em>) depends on the model type.\n</p>\n<p class='vspace'>For an MDP, as in <a class='wikilink' href='Example1.html'>Example 1</a>, the choice is <em>nondeterministic</em>. By way of example, consider state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>). There are two commands enabled, one from each module:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock13'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=13' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock14'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=14' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In state <code>(0,0)</code> of the MDP, there would be a nondeterministic choice between these two probability distributions:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.2:(1,0)</code> (module <code>M1</code> moves)\n</li><li><code>0.8:(0,0) + 0.2:(0,1)</code> (module <code>M2</code> moves)\n</li></ul><p class='vspace'>For a DTMC, the choice is <em>probabilistic</em>: each enabled command is selected with equal probability.\nIf <a class='wikilink' href='Example1.html'>Example 1</a> was a DTMC, then in state <code>(0,0)</code> of the model\nthe following probability distribution would result:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.1:(1,0) + 0.1:(0,1)</code>\n</li></ul><p class='vspace'>For a <a class='wikilink' href='CTMCs.html'>CTMC</a>, as will be discussed shortly,\nthe choice is modelled as a \"race\" between transitions.\n</p>\n<p class='vspace'>See the later sections on \"<a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\" and \"<a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\" for other topics related to parallel composition.\n</p><hr />\n<h1>Local Nondeterminism</h1>\n<p>PRISM models that support nondeterminism, such as are MDPs, can also exhibit <em>local nondeterminism</em>,\nwhich allows the modules themselves to make nondeterministic choices.\nIn <a class='wikilink' href='Example1.html'>Example 1</a>, we can make the probabilistic choice in the first state of module <code>M1</code> nondeterministic by replacing the command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock15'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=15' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>with the commands:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock16'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=16' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Assuming we do the same for module <code>M2</code>, in state <code>(0,0)</code> of the MDP\nthere will be a nondeterministic choice between the three (trivial) probability distributions listed below. (There are three, not four, distributions because two possibilities result in identical behaviour: staying with probability 1 in the state state.)\n</p>\n<div class='vspace'></div><ul><li><code>1.0:(0,0)</code>\n</li><li><code>1.0:(1,0)</code>\n</li><li><code>1.0:(0,1)</code>\n</li></ul><p class='vspace'>More generally, local nondeterminism can also arise when the guards of two commands overlap only partially, rather than completely as in the example above.\n</p>\n<p class='vspace'>PRISM also permits local nondeterminism in models which are DTMCs,\nalthough the nondeterministic choice is randomised when the parallel composition of the modules occurs.\nSince the appearance of nondeterminism in a DTMC is often the result of\na user error in the model specification, PRISM displays a warning when local nondeterminism is detected in a DTMC.\nOverlapping guards in <a class='wikilink' href='CTMCs.html'>CTMCs</a> are not treated as nondeterministic choices.\n</p>\n<div class='vspace'></div><hr />\n<h1>CTMCs</h1>\n<p class='vspace'>Specifying the behaviour of a continuous-time Markov chain (CTMC)\nis done in similar fashion to a DTMC or an MDP, as discussed so far.\nThe main difference is that updates in commands are\nlabelled with (positive-valued) <em>rates</em>, rather than probabilities.\nThe notation used in commands, however, to associate rates to transitions is identical to\nthe one used to assign probabilities:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock17'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">rate_1</span>:<span class=\"prismident\">update_1</span> + <span class=\"prismident\">rate_2</span>:<span class=\"prismident\">update_2</span> + ... <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=17' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In a CTMC, when multiple possible transitions are available in a state, a <em>race condition</em> occurs\n(see e.g. [<a class='wikilink' href='../Main/References.html#KNP07a'>KNP07a</a>] for more details).\nIn terms of PRISM commands, this can arise in several ways.\nFirstly, within in a module, multiple transitions can be specified either as several different updates in a command, or as multiple commands with overlapping guards. The following, for example. are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock18'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=18' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock19'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=19' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Furthermore, parallel composition between modules in a CTMC is modelled as a race condition,\nrather as a nondeterministic choice, like for <a class='wikilink' href='ParallelComposition.html'>MDPs</a>.\n</p><hr />\n<h1>Example 2</h1>\n<p>We now introduce a second example: a CTMC that models an <em>N</em>-place queue of jobs and\na server which removes jobs from the queue and processes them.\nThe PRISM code is as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock20'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 2</span><br/>\n<span class=\"prismcomment\">// N-place queue + server</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span> = <span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mu</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">lambda</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">2</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">gamma</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">3</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">queue</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">q</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">N</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>&lt;<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>+<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>=<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">server</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">s</span>=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismident\">gamma</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">0</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=20' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 2</strong>\n</p>\n<p class='vspace'>This example also introduces a number of other PRISM language concepts,\nincluding <a class='wikilink' href='Constants.html'>constants</a>, action labels and <a class='wikilink' href='Synchronisation.html'>synchronisation</a>.\nThese are described in the following sections.\n</p><hr />\n<h1>Constants</h1>\n<p>PRISM supports the use of <em>constants</em>, as seen in <a class='wikilink' href='Example2.html'>Example 2</a>.\nConstants can be integers, doubles or Booleans\nand can be defined using literal values or as constant expressions (including in terms of each other) using the <code><strong>const</strong></code>\nkeyword. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock21'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">radius</span> = <span class=\"prismnum\">12</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">pi</span> = <span class=\"prismnum\">3.141592</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">area</span> = <span class=\"prismident\">pi</span> * <span class=\"prismident\">radius</span> * <span class=\"prismident\">radius</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">bool</span> <span class=\"prismident\">yes</span> = <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=21' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The identifiers used for their names are subject to the same rules as <a class='wikilink' href='ModulesAndVariables.html'>variables</a>.\n</p>\n<p class='vspace'>Constants can be used anywhere that a constant value would be expected,\nsuch as the lower or upper range of a variable (e.g. <code>N</code> in <a class='wikilink' href='Example2.html'>Example 2</a>),\nthe probability or rate associated with an update (<code>mu</code> in <a class='wikilink' href='Example2.html'>Example 2</a>),\nor anywhere in a guard or update.\nAs will be described later constants can also be left undefined\nand specified later, either to a single value or a range of values, using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'><strong>Note:</strong> For the sake of backward-compatibility, the notation used in earlier versions of PRISM\n(<code><strong>const</strong></code> for <code><strong>const int</strong></code> and <code><strong>rate</strong></code> or <code><strong>prob</strong></code> for <code><strong>const double</strong></code>) is still supported.\n</p><hr />\n<h1>Expressions</h1>\n<p>The definition of the <code>area</code> constant, in the example above, uses an <em>expression</em>.\nWe now define more precisely what types of expression are supported by PRISM.\nExpressions can contain literal values (12, 3.141592, <code><strong>true</strong></code>, <code><strong>false</strong></code>, etc.),\nidentifiers (corresponding to variables, constants, etc.) and operators from the following list:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>^</code> (power)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li></ul><p class='vspace'>All of these operators except <code>?</code> and <code>=&gt;</code> are left associative\n(i.e. they are evaluated from left to right).\nThe precedence of the operators is as found in the list above,\nmost strongly binding operators first.\nOperators on the same line (e.g. <code>+</code> and <code>-</code>) are of equal precedence.\n</p>\n<p class='vspace'>Much of the notation for expressions is hence essentially equivalent to that of C/C++ or Java.\nOne notable exception to this is that  the division operator <code>/</code> always performs floating point, not integer, division,\ni.e. the result of <code>22/7</code> is 3.142857... not 3.\nAll expressions must evaluate correctly in terms of type (integer, double or Boolean).\n</p>\n<p class='vspace'><strong>Built-in Functions</strong>\n</p>\n<p class='vspace'>Expressions can make use of several built-in functions:\n</p>\n<div class='vspace'></div><ul><li><code>min(...)</code> and <code>max(...)</code>, which select the minimum and maximum value, respectively, of two or more numbers\n</li><li><code>floor(x)</code> and <code>ceil(x)</code>, which round <code>x</code> down and up, respectively, to the nearest integer\n</li><li><code>round(x)</code>, which rounds <code>x</code> to the nearest integer (note, in a tie-break, we always round <em>up</em>, e.g. <code>round(-1.5)</code> gives <code>-1</code> not <code>-2</code>)\n</li><li><code>pow(x,y)</code> which computes <code>x</code> to the power of <code>y</code> (same as <code>x^y</code>)\n</li><li><code>mod(i,n)</code> for integer modulo operations\n</li><li><code>log(x,b)</code>, which computes the logarithm of <code>x</code> to base <code>b</code>\n</li></ul><p class='vspace'>Examples of their usage are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock22'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">min</span>(<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>, <span class=\"prismident\">x_max</span>)<br/>\n<span class=\"prismkeyword\">max</span>(<span class=\"prismident\">a</span>,<span class=\"prismident\">b</span>,<span class=\"prismident\">c</span>)<br/>\n<span class=\"prismident\">floor</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">ceil</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">round</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">2</span>, <span class=\"prismnum\">8</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">9.0</span>, <span class=\"prismnum\">0.5</span>)<br/>\n<span class=\"prismident\">mod</span>(<span class=\"prismnum\">1977</span>, <span class=\"prismnum\">100</span>)<br/>\n<span class=\"prismident\">log</span>(<span class=\"prismnum\">123</span>, <span class=\"prismnum\">2.71828183</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=22' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For compatibility with older versions of PRISM, all functions can also be expressed via the <code><strong>func</strong></code> keyword, e.g. <code>func(floor, 13.5)</code>.\n</p>\n<p class='vspace'><strong>Use of Expressions</strong>\n</p>\n<p class='vspace'>Expressions can be used in a wide range of places in a PRISM language description, e.g.:\n</p>\n<div class='vspace'></div><ul><li>constant definitions\n</li><li>lower/upper bounds and initial values for variables\n</li><li>guards\n</li><li>probabilities/rates\n</li><li>updates\n</li></ul><p class='vspace'>This allows, for example, the probability in a command to be dependent on the current state:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock23'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] (<span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span>) -&gt; <span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">max</span>(<span class=\"prismnum\">1</span>,<span class=\"prismident\">x</span>-<span class=\"prismnum\">1</span>)) + <span class=\"prismnum\">1</span>-<span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">min</span>(<span class=\"prismnum\">10</span>,<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>)) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=23' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Synchronisation</h1>\n<p>Another feature of PRISM introduced in <a class='wikilink' href='Example2.html'>Example 2</a> is <em>synchronisation</em>.\nIn the style of many process algebras, we allow commands to be labelled with <em>actions</em>.\nThese are placed inside the square brackets which mark the start of the command,\nfor example <code>serve</code> in this command from <a class='wikilink' href='Example2.html'>Example 2</a>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock24'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=24' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These actions can be used to force two or more modules to make transitions simultaneously\n(i.e. to <em>synchronise</em>).\nFor example, in state <code>(3,0)</code> (i.e.  <code>q=3</code> and <code>s=0</code>),\nthe composed model can move to state <code>(2,1)</code>,\nsynchronising over the <code>serve</code> action.\nThe rate of this transition is equal to the product of the two individual rates\n(in this case, <code>lambda * 1 = lambda</code>).\nThe product of two rates does not always meaningfully represent the rate of a synchronised transition.\nA common technique, as seen here, is to make one action <em>passive</em>, with rate 1 and one action <em>active</em>,\nwhich actually defines the rate for the synchronised transition.\nBy default, all modules are combined using the standard CSP parallel composition\n(i.e. modules synchronise over all their common actions).\n</p><hr />\n<h1>Module Renaming</h1>\n<p>PRISM also supports <em>module renaming</em>, which allows duplication of modules.\nIn <a class='wikilink' href='Example1.html'>Example 1</a>, module <code>M2</code> is identical to module <code>M1</code> so we can in fact replace its entire definition with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock25'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span> = <span class=\"prismident\">M1</span> [ <span class=\"prismident\">x</span>=<span class=\"prismident\">y</span>, <span class=\"prismident\">y</span>=<span class=\"prismident\">x</span> ] <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=25' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>All of the variables in the module being renamed (in this case, just <code>x</code>) <em>must</em> be renamed to new, unused names. Optionally, it is also possible to rename other aspects of the module definition. In fact, the renaming is done at a textual level, so any identifiers (including <a class='wikilink' href='Synchronisation.html'>action labels</a>, <a class='wikilink' href='Constants.html'>constants</a> and <a class='wikilink' href='Expressions.html'>functions</a>) used in the module definition can be changed in this way.\n</p>\n<p class='vspace'><strong>Note:</strong> Care should be taken when renaming modules that make use of <a class='wikilink' href='FormulasAndLabels.html'>formulas</a>.\n</p><hr />\n<h1>Multiple Initial States</h1>\n<p>Typically, a <a class='wikilink' href='ModulesAndVariables.html'>variable</a> declaration\nspecifies the initial value for that variable.\nThe <em>initial state</em> for the model is then defined by the initial value for all variables.\nIt is possible, however, to specify that a model has <em>multiple</em> initial states.\nThis is done using the <code><strong>init</strong>...<strong>endinit</strong></code> construct,\nwhich can be placed anywhere in the file except within a module definition,\nand removing any initial values from variable declarations.\nBetween the <code><strong>init</strong></code> and <code><strong>endinit</strong></code> keywords, there should be a\npredicate over all the variables of the model.\nAny state which satisfies this predicate is an initial state.\n</p>\n<p class='vspace'>Consider again <a class='wikilink' href='Example1.html'>Example 1</a>.\nAs it stands, there is a single initial state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>).\nIf we remove the <code><strong>init</strong> 0</code> part of both variable declarations\nand add the following to the end of the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock26'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=26' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>there will be three initial states: <code>(0,0)</code>, <code>(0,1)</code> and <code>(0,2)</code>.\nSimilarly, we could instead add:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock27'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>+<span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=27' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>in which case there would be two initial states: <code>(0,1)</code> and <code>(1,0)</code>.\n</p><hr />\n<h1>Global Variables</h1>\n<p>In addition to the local variables belonging to each module, a PRISM model can also include <em>global variables</em>,\nwhich can be written to, as well as read, by all modules.\nLike local variables, these can be integers or Booleans.\nGlobal variables are declared in identical fashion to a module's local variables,\nexcept that the declaration must not be inside the definition of any module.\nSome example declarations are as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock28'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">global</span> <span class=\"prismident\">g</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismnum\">10</span>];<br/>\n<span class=\"prismkeyword\">global</span> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=28' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A global variable can be modified by any module and provides another way for modules to interact.\nAn important restriction on the use of global variables is the fact that commands which synchronise with other modules\n(i.e. those with an action label attached; see the section \"<a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\") cannot modify global variables.\nPRISM will detect this and report an error.\n</p><hr />\n<h1>Formulas And Labels</h1>\n<p>PRISM models can include <em>formulas</em> which are used to avoid duplication of code.\nA formula comprises a name (an identifier) and an <a class='wikilink' href='Expressions.html'>expression</a>.\nThe formula name can then be used as shorthand for the expression anywhere an expression might usually be accepted.\nA formula is defined as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock29'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">formula</span> <span class=\"prismident\">num_tokens</span> = <span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=29' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It can then be used anywhere within that file, as for example in this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock30'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">num_tokens</span>=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=30' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The effect is exactly as if the following had been typed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock31'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; (<span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>)=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=31' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Formulas defined in a model can also be used when specifying its properties.\n</p>\n<div class='vspace'></div><h3>Formulas and renaming</h3>\n<p>During parsing of the model, expansion of formulas is done before module renaming so, if a module which uses formulas is renamed to another module, it is the contents of the formula which will be renamed, not the formula itself.\n</p>\n<div class='vspace'></div><h3>Labels</h3>\n<p>PRISM models can also contain <em>labels</em>. These are a way of identifying sets of states that are of particular interest. Labels can only be used when specifying <a class='wikilink' href='../PropertySpecification/Main.html'>properties</a> but, for convenience, can be defined in model files as well as property files. \n</p>\n<p class='vspace'>Labels differ from formulas in two other ways: firstly, they must be of Boolean type;\nsecondly, they are written using quotation marks (<code>\"...\"</code>), as illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock32'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=32' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<hr />\n<h1>Costs And Rewards </h1>\n<p>PRISM supports the specification and analysis of\nproperties based on <em>costs</em> and <em>rewards</em>.\nThis means that it can be used to reason,\nnot just about the probability that a model behaves in a certain fashion,\nbut about a wider range of quantitative measures relating to model behaviour.\nFor example, PRISM can be used to compute properties such as\n\"expected time\", \"expected number of lost messages\" or \"expected power consumption\".\nThe implementation of cost- and reward-based techniques in the tool is only partially completed and is still ongoing.\nIf you have questions, comments or feature-requests relating to this functionality,\nplease feel free to contact the PRISM team about this.\n</p>\n<p class='vspace'>The basic idea is that probabilistic models (of all types) developed in PRISM\ncan be augmented with costs or rewards: real values associated with certain states or transitions of the model.\nIn fact, since there is no practical distinction between costs and rewards\n(except that costs are generally perceived to be \"bad\" and rewards to be \"good\"),\nPRISM only supports rewards.\nThe user is, however, free to interpret the values however they choose.\n</p>\n<p class='vspace'>In this section, we describe how models described in the PRISM language\ncan be augmented with rewards.\nLater, we will discuss how to express properties that relate to these rewards.\nRewards are associated with models using <code><strong>rewards</strong> ... <strong>endrewards</strong></code> constructs,\nwhich can appear anywhere in a model file except within a module definition.\nThese constructs contains one or more <em>reward items</em>.\nConsider the following simple example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock33'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r1</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=33' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This defines a reward structure with name <code>r1</code> (the name is optional)\nwhich assigns a reward of 1 to every state of the model.\nIt comprises a single reward item, the left part of which (<code><strong>true</strong></code>) is a guard\nand the right part of which (<code>1</code>) is a reward.\nStates of the model which satisfy the predicate in the guard are assigned the corresponding reward.\nMore generally, state rewards can be specified using multiple reward items,\neach of the form <code>guard : reward;</code>,\nwhere <code>guard</code> is a predicate (over all the variables of the model)\nand <code>reward</code> is an expression (containing any variables, constants, etc. from the model).\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock34'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r2</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> : <span class=\"prismnum\">100</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&lt;<span class=\"prismnum\">10</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">10</span> : <span class=\"prismnum\">100</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=34' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 100 to states satisfying <code>x=0</code> or <code>x=10</code>\nand a reward of <code>2*x</code> to states satisfying <code>x&gt;0 &amp; x&lt;10</code>.\nNote that a single reward item can assign different rewards to different states,\ndepending on the values of model variables in each one.\nAny states which do not satisfy the guard of any reward item will have no reward assigned to them.\nFor states which satisfy multiple guards, the reward assigned to the state\nis the sum of the rewards for all the corresponding reward items.\n</p>\n<p class='vspace'>Rewards can also be assigned to transitions of a model.\nThese are specified in a similar fashion to state rewards,\nwithin the <code><strong>rewards</strong> ... <strong>endrewards</strong></code> construct.\nReward items describing transition rewards are of the form <code>[action] guard : reward;</code>,\nthe interpretation being that transitions from states which satisfy the guard <code>guard</code>\nand are labelled with the action <code>action</code> acquire the reward <code>reward</code>.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock35'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r3</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">a</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=35' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 1 to all transitions in the model with no action label,\nand rewards of <code>x</code> and <code>2*x</code> to all transitions labelled with actions <code>a</code> and <code>b</code>, respectively.\n</p>\n<p class='vspace'>As is the case for states, multiple reward items can specify rewards for a single transition,\nin which case the resulting reward is the sum of all the individual rewards.\nA model description can specify rewards for both states and transitions.\nThese are all placed together in a single <code><strong>rewards</strong>...<strong>endrewards</strong></code> construct.\n</p>\n<p class='vspace'>A PRISM model will often have multiple reward structures, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock36'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">total_time</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n<br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">num_failures</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">fail</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=36' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div><hr />\n<h1>Real-time Models</h1>\n<p class='vspace'>So far in this section, we have mainly focused on three types of models: DTMCs, MDPs and CTMCs,\nin which all the variables making up their state are finite.\nPRISM also supports <em>real-time</em> models, in particular,\n<em>probabilistic timed automata</em> (PTAs), which extend MDPs with the ability to model real-time behaviour.\nThis is done in the style of <em>timed automata</em> [<a class='wikilink' href='../Main/References.html#AD94'>AD94</a>], by adding <em>clocks</em>,\nreal-valued variables which increase with time and can be reset. For background material on PTAs, see for example [<a class='wikilink' href='../Main/References.html#NPS13'>NPS13</a>].\nYou can also find several example PTA models included in the PRISM distribution. Look in the <code>prism-examples/ptas</code> directory.\n</p>\n<p class='vspace'>Before describing how PTA features are incorporated into the PRISM modelling language, we give a simple example. Here is a small PTA:\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/pta.png' alt='' /></div>\n<p class='vspace'>and here is a corresponding PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock37'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">pta</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : <span class=\"prismkeyword\">clock</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">invariant</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">2</span>) &amp;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">3</span>)<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">endinvariant</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">send</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismnum\">0.9</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">retry</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.95</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.05</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=37' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For modelling PTAs in PRISM, there is a new datatype, <strong><code>clock</code></strong>, used for variables that are clocks. Other types of PRISM variables can be defined in the usual way. In the example above, we use just a single integer variable <code>s</code> to represent the locations of the PTAs.\n</p>\n<p class='vspace'>In a PTA, transitions can include a <em>guard</em>, which constrains when it can occur based on the current value of clocks, and <em>resets</em>, which specify that a clock's values should be set to a new (integer) value. These are both specified in PRISM commands in the usual way: see, for example, the inclusion of <code>x&gt;=1</code> in the guard for the <code>send</code>-labelled command and the updates of the form <code>(x'=0)</code> which reset the clock <code>x</code> to 0.\n</p>\n<p class='vspace'>The other new addition is an <code>invariant</code> construct, which is used to specify an expression describing the clock <em>invariants</em> for each PRISM module. These impose restrictions on the allowable values of clock variables, depending on the values of the other non-clock variables. The <code>invariant</code> construct should appear between the variable declarations and the commands of the module. Often, clock invariants are described separately for each PTA location; hence, the invariant will often take the form of a conjunction of implications, as in the example model above, but more general expressions are also permitted. In the example, the clock <code>x</code> must satisfy <code>x&lt;=2</code> or <code>x&lt;=3</code> when local variables <code>s</code> is 0 or 2, respectively. If <code>s</code> is 1, there is no restriction (since the invariant is effectively <code>true</code> in this case).\n</p>\n<p class='vspace'>Expressions that include reference to clocks, whether in guards or invariants, must satisfy certain conditions to facilitate model checking. In particular, references to clocks must appear as conjunctions of <em>simple clock constraints</em>, i.e. conjunctions of expressions of the form <code>x~c</code> or <code>x~y</code> where <code>x</code> and <code>y</code> are clocks, <code>c</code> is an integer-valued expression and <code>~</code> is one of <code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code>, <code>=</code>).\n</p>\n<p class='vspace'>There are also some additional restrictions imposed on PTA models that are dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is in use.\n</p>\n<p class='vspace'>For the <strong>stochastic games</strong> and <strong>backwards reachability</strong> engines:\n</p>\n<div class='vspace'></div><ul><li>The model must also have a single initial state (i.e. the <code>init...endinit</code> construct is not permitted).\n</li></ul><p class='vspace'>For the <strong>digital clocks</strong> engine:\n</p>\n<div class='vspace'></div><ul><li>Clock constraints cannot use strict comparison operators, e.g. <code>x&lt;=5</code> is allowed, but <code>x&lt;5</code> is not.\n<div class='vspace'></div></li><li>Diagonal clock constraints are not allowed, i.e. those containing references to two clocks, such as <code>x&lt;=y</code>.\n</li></ul><p class='vspace'>Finally, PRISM makes several assumptions about PTAs, regardless of the engine used.\n</p>\n<div class='vspace'></div><ul><li>Firstly PTAs should not exhibit <em>timelocks</em>, i.e. the possibility of reaching a state where no transitions are possible and time cannot elapse beyond a certain point (due to invariant conditions). PRISM checks for timelocks and reports an error if one is found.\n<div class='vspace'></div></li><li>Secondly, PTAs should be <em>well-formed</em> and <em>non-zeno</em> (see e.g. [<a class='wikilink' href='../Main/References.html#KNSW07'>KNSW07</a>] for details). Currently, PRISM does not check automatically that these assumptions are satisfied.\n</li></ul><div class='vspace'></div><hr />\n<h1>Partially Observable Models</h1>\n<p>PRISM supports analysis of <em>partially observable</em> probabilistic models,\nmost notably partially observable Markov decision processes (POMDPs),\nbut also partially observable probabilistic timed automata (POPTAs).\nPOMDPs are a variant of MDPs in which the strategy/policy\nwhich resolves nondeterministic choices in the model is unable to\nsee the precise state of the model, but instead just <em>observations</em> of it.\nFor background material on POMDPs and POPTAs, see for example [<a class='wikilink' href='../Main/References.html#NPZ17'>NPZ17</a>].\nYou can also find several example models included in the PRISM distribution.\nLook in the <code>prism-examples/pomdps</code> and <code>prism-examples/poptas</code> directories.\n</p>\n<p class='vspace'>PRISM currently supports state-based observations:\nthis means that, upon entering a new POMDP state,\nthe observation is determined by that state.\nIn the same way that a model state comprises the values or one or more variables,\nan observation comprises one or more <em>observables</em>.\nThere are several way to define these observables.\nThe simplest is to specify a subset of the model's variables\nthat are designated as being observable. The rest are unobservable.\n</p>\n<p class='vspace'>For example, in a POMDP with 3 variables, <code>s</code>, <code>l</code> and <code>h</code>, the following:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock38'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">observables</span> <span class=\"prismident\">s</span>, <span class=\"prismident\">l</span> <span class=\"prismkeyword\">endobservables</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=38' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>specifies that <code>s</code> and <code>l</code> are observable and <code>h</code> is not.\n</p>\n<p class='vspace'>Alternatively, observables can be specified as arbitrary expressions over variables.\nFor example, assuming the same variables <code>s</code>, <code>l</code> and <code>h</code>, this specification:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock39'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">s</span>\" = <span class=\"prismident\">s</span>;<br/>\n<span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">pos</span>\" = <span class=\"prismident\">l</span>&gt;<span class=\"prismnum\">0</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=39' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>defines 2 observables. The first is, as above, the variable <code>s</code>.\nThe second, named <code>\"pos\"</code>, determines if variable <code>l</code> is positive.\nOther than this, the values of <code>l</code> and <code>h</code> are unobservable.\nThe named observables can then be used in properties\nin the same way that <a class='wikilink' href='FormulasAndLabels.html'>labels</a> can.\n</p>\n<p class='vspace'>The above two styles of definition can also be mixed\nto specify a combined set of observables.\n</p>\n<p class='vspace'>POPTAs (partially observable PTAs) combine the features of both PTAs and POMDPs.\nThey are are currently analysed using the digital clocks engine,\nso inherit the <a class='wikilink' href='Real-timeModels.html'>restrictions for that engine</a>.\nFurthermore, for a POPTA, all clock variables must be observable.\n</p><hr />\n<h1>Uncertain models</h1>\n<p>PRISM has support for <em>uncertain</em> models, in which there is epistemic uncertainty regarding some quantitative aspects of the probabilistic models being verified. In particular, it currently supports <em>interval MDPs</em> (IMDPs) and <em>interval DTMCs</em> (IDTMCs), which are MDPs or DTMCs in which transition probabilities can be specified as intervals, indicating that the exact probability is not precisely known. This can be useful, for example, when the transition probabilities have been estimated from data.\n</p>\n<p class='vspace'>Currently, this is achieved by simply replacing the probabilities attached to updates in commands with intervals, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock40'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismnum\">0.8</span>,<span class=\"prismnum\">0.9</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.1</span>,<span class=\"prismnum\">0.2</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=40' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As usual, the probability thresholds can be expressions involving state variables or constants, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock41'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismident\">p</span>,<span class=\"prismident\">p</span>+<span class=\"prismnum\">0.1</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.9</span>-<span class=\"prismident\">p</span>,<span class=\"prismnum\">1</span>-<span class=\"prismident\">p</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/AllOnOnePage?action=sourceblock&amp;num=41' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When two commands in different modules <a class='wikilink' href='Synchronisation.html'>synchronise</a> and specify the probabilities for updates to variables as intervals, these are considered to be independent, i.e., the probability of each combined transition is taken to be the product of the two component intervals.\n</p>\n<p class='vspace'>See the <a class='wikilink' href='../PropertySpecification/UncertainModels.html'>property specification</a> section for details of how these models are analysed.\n</p><hr />\n<h1>Process Algebra Operators</h1>\n<p>To make the concept of synchronisation described above more powerful,\nPRISM allows you to define precisely the way in which the set of modules are composed in parallel.\nThis is specified using the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct,\nplaced at the end of the model description, which should contain a process-algebraic expression.\nThis expression should feature each module exactly once, and can use the following (CSP-based) operators:\n</p>\n<div class='vspace'></div><ul><li><code>M1 || M2</code> : alphabetised parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising on only actions appearing in both <code>M1</code> and <code>M2</code>)\n<div class='vspace'></div></li><li><code>M1 ||| M2</code> : asynchronous parallel composition of <code>M1</code> and <code>M2</code> (fully interleaved, no synchronisation)\n<div class='vspace'></div></li><li><code>M1 |[a,b,...]| M2</code> : restricted parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising only on actions from the set {<code>a</code>, <code>b</code>,...})\n<div class='vspace'></div></li><li><code>M / {a,b,...</code>} : hiding of actions {<code>a</code>, <code>b</code>, ...} in module <code>M</code>\n<div class='vspace'></div></li><li><code>M {a&lt;-b,c&lt;-d,...</code>} : renaming of actions <code>a</code> to <code>b</code>, <code>c</code> to <code>d</code>, etc. in module <code>M</code>.\n</li></ul><p class='vspace'>The first two types of parallel composition (<code>||</code> and <code>|||</code>) are associative and can be applied to more than two modules at once.\nWhen evaluating the expression, the hiding and renaming operators bind more tightly than the three parallel composition operators.\nNo other rules of precedence are defined and parentheses should be used to specify the order in which modules are composed.\n</p>\n<p class='vspace'>Some examples of expressions which could be included in the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct are as follows:\n</p>\n<div class='vspace'></div><ul><li><code>(station1 ||| station2 ||| station3) |[serve]| server</code>\n</li><li><code>((P1 |[a]| P2) / {a}) || Q</code>\n</li><li><code>((P1 |[a]| P2) {a&lt;-b}) |[b]| Q</code>\n</li></ul><p class='vspace'>When no parallel composition is specified by the user,\nPRISM implicitly assumes an expression of the form <code>M1 || M2 || ...</code> containing all of the modules in the model.\nFor a more formal definition of the process algebra operators described above, check the semantics of the PRISM language, available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site.\n</p>\n<p class='vspace'>PRISM is also able to <a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>import</a> model descriptions written in (a subset of) the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='../Main/References.html#Hil96'>Hil96</a>].\n</p><hr />\n<h1>PRISM Model Files</h1>\n<p>Files containing model descriptions written in the PRISM language\ncan contain any amount of white space (spaces, tabs, new lines, etc.),\nall of which is ignored when the file is parsed by the tool.\nComments can also be used included in files in the style of the C programming language,\nby preceding them with the characters <code>//</code>.\nThis is illustrated by the PRISM language examples from earlier in this section.\n</p>\n<p class='vspace'>We recommend that the <code>.prism</code> extension is used for PRISM model files.\nHistorically (when the tool supported fewer types of model),\ndifferent extensions were often used for each model type:\n<code>.nm</code> for MDPs or PTAs, <code>.pm</code> for DTMCs and <code>.sm</code> for CTMCs.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/CTMCs.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / CTMCs \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CTMCs.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CTMCs@action=edit.html'>Edit</a> - <a class='wikilink' href='CTMCs@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>CTMCs</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p class='vspace'>Specifying the behaviour of a continuous-time Markov chain (CTMC)\nis done in similar fashion to a DTMC or an MDP, as discussed so far.\nThe main difference is that updates in commands are\nlabelled with (positive-valued) <em>rates</em>, rather than probabilities.\nThe notation used in commands, however, to associate rates to transitions is identical to\nthe one used to assign probabilities:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">rate_1</span>:<span class=\"prismident\">update_1</span> + <span class=\"prismident\">rate_2</span>:<span class=\"prismident\">update_2</span> + ... <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CTMCs?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In a CTMC, when multiple possible transitions are available in a state, a <em>race condition</em> occurs\n(see e.g. [<a class='wikilink' href='../Main/References.html#KNP07a'>KNP07a</a>] for more details).\nIn terms of PRISM commands, this can arise in several ways.\nFirstly, within in a module, multiple transitions can be specified either as several different updates in a command, or as multiple commands with overlapping guards. The following, for example. are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CTMCs?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CTMCs?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Furthermore, parallel composition between modules in a CTMC is modelled as a race condition,\nrather as a nondeterministic choice, like for <a class='wikilink' href='ParallelComposition.html'>MDPs</a>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CTMCs.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CTMCs@action=edit.html'>Edit</a> - <a class='wikilink' href='CTMCs@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CTMCs@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:35 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='selflink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/CTMCs@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / CTMCs | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CTMCs.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CTMCs@action=edit.html'>Edit</a> - <a class='wikilink' href='CTMCs@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>CTMCs</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='CTMCs@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CTMCs.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CTMCs@action=edit.html'>Edit</a> - <a class='wikilink' href='CTMCs@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CTMCs@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:35 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='selflink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/CTMCs@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / CTMCs | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CTMCs.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CTMCs@action=edit.html'>Edit</a> - <a class='wikilink' href='CTMCs@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>CTMCs</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='CTMCs@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CTMCs.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CTMCs@action=edit.html'>Edit</a> - <a class='wikilink' href='CTMCs@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CTMCs@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:35 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='selflink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/CTMCs@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / CTMCs </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>CTMCs</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p class='vspace'>Specifying the behaviour of a continuous-time Markov chain (CTMC)\nis done in similar fashion to a DTMC or an MDP, as discussed so far.\nThe main difference is that updates in commands are\nlabelled with (positive-valued) <em>rates</em>, rather than probabilities.\nThe notation used in commands, however, to associate rates to transitions is identical to\nthe one used to assign probabilities:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">rate_1</span>:<span class=\"prismident\">update_1</span> + <span class=\"prismident\">rate_2</span>:<span class=\"prismident\">update_2</span> + ... <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CTMCs?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In a CTMC, when multiple possible transitions are available in a state, a <em>race condition</em> occurs\n(see e.g. [<a class='wikilink' href='../Main/References.html#KNP07a'>KNP07a</a>] for more details).\nIn terms of PRISM commands, this can arise in several ways.\nFirstly, within in a module, multiple transitions can be specified either as several different updates in a command, or as multiple commands with overlapping guards. The following, for example. are equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CTMCs?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">50</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">60</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CTMCs?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Furthermore, parallel composition between modules in a CTMC is modelled as a race condition,\nrather as a nondeterministic choice, like for <a class='wikilink' href='ParallelComposition.html'>MDPs</a>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Commands.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Commands \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Commands.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Commands@action=edit.html'>Edit</a> - <a class='wikilink' href='Commands@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Commands</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The behaviour of each module is described by <em>commands</em>,\ncomprising a <em>guard</em> and one or more <em>updates</em>.\nThe first command of module <code>M1</code> in our <a class='wikilink' href='Example1.html'>example</a> is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The guard <code>x=0</code> indicates that this describes the behaviour of the module when the variable <code>x</code> has value 0.\nThe updates <code>(x'=0)</code> and <code>(x'=1)</code> and their associated probabilities state that the value of <code>x</code> will\nremain at 0 with probability 0.8 and change to 1 with probability 0.2.\nNote that the inclusion of updates in parentheses, e.g. <code>(x'=1)</code>, is essential.\nWhile older versions of PRISM did not report the absence of parentheses as an error, newer versions do.\nNote also that PRISM will complain if the probabilities on the right hand side of a command do not sum to one.\n</p>\n<p class='vspace'>The second command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>illustrates that guards can contain constraints on any variable, not just the ones in that module,\ni.e. the behaviour of one module can depend on the state of another.\nUpdates, however, can only specify values for variables belonging to the module.\nIn general a module can <em>read</em> the variables of any other module, but only <em>write</em> to its own.\nWhen a command comprises a single update with probability 1, the <code>1.0:</code> can be omitted,\nas is done in the example above.\n</p>\n<p class='vspace'>If a module has more than one variable, updates describe the new value for each of them.\nFor example, if it had two variables <code>x1</code> and <code>x2</code>, a possible command would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&lt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>+<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that elements of the updates are concatenated with <code>&amp;</code> and that each element must be bracketed individually.\nIf an update does not give a new value for a local variable, it is assumed not to change.\nAs a special case, the keyword <code><strong>true</strong></code> can be used to denote an update where no variable's value changes, i.e. the following are all equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Finally, it is important to remember that the expressions on the right hand side of each update refer to the state of the model <em>before</em> the update occurs. So, for example, this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>=<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x1</span>) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>updates variable <code>x2</code> to 0, not 2.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Commands.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Commands@action=edit.html'>Edit</a> - <a class='wikilink' href='Commands@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Commands@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 12:57 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='selflink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Commands@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Commands | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Commands.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Commands@action=edit.html'>Edit</a> - <a class='wikilink' href='Commands@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Commands</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Commands@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Commands.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Commands@action=edit.html'>Edit</a> - <a class='wikilink' href='Commands@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Commands@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 12:57 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='selflink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Commands@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Commands | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Commands.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Commands@action=edit.html'>Edit</a> - <a class='wikilink' href='Commands@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Commands</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Commands@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Commands.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Commands@action=edit.html'>Edit</a> - <a class='wikilink' href='Commands@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Commands@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 12:57 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='selflink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Commands@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Commands </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Commands</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>The behaviour of each module is described by <em>commands</em>,\ncomprising a <em>guard</em> and one or more <em>updates</em>.\nThe first command of module <code>M1</code> in our <a class='wikilink' href='Example1.html'>example</a> is:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The guard <code>x=0</code> indicates that this describes the behaviour of the module when the variable <code>x</code> has value 0.\nThe updates <code>(x'=0)</code> and <code>(x'=1)</code> and their associated probabilities state that the value of <code>x</code> will\nremain at 0 with probability 0.8 and change to 1 with probability 0.2.\nNote that the inclusion of updates in parentheses, e.g. <code>(x'=1)</code>, is essential.\nWhile older versions of PRISM did not report the absence of parentheses as an error, newer versions do.\nNote also that PRISM will complain if the probabilities on the right hand side of a command do not sum to one.\n</p>\n<p class='vspace'>The second command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>illustrates that guards can contain constraints on any variable, not just the ones in that module,\ni.e. the behaviour of one module can depend on the state of another.\nUpdates, however, can only specify values for variables belonging to the module.\nIn general a module can <em>read</em> the variables of any other module, but only <em>write</em> to its own.\nWhen a command comprises a single update with probability 1, the <code>1.0:</code> can be omitted,\nas is done in the example above.\n</p>\n<p class='vspace'>If a module has more than one variable, updates describe the new value for each of them.\nFor example, if it had two variables <code>x1</code> and <code>x2</code>, a possible command would be:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>&lt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>+<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that elements of the updates are concatenated with <code>&amp;</code> and that each element must be bracketed individually.\nIf an update does not give a new value for a local variable, it is assumed not to change.\nAs a special case, the keyword <code><strong>true</strong></code> can be used to denote an update where no variable's value changes, i.e. the following are all equivalent:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x2</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismident\">x1</span>);<br/>\n[] <span class=\"prismident\">x1</span>&gt;<span class=\"prismnum\">10</span> | <span class=\"prismident\">x2</span>&gt;<span class=\"prismnum\">10</span> -&gt; <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Finally, it is important to remember that the expressions on the right hand side of each update refer to the state of the model <em>before</em> the update occurs. So, for example, this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x1</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x2</span>=<span class=\"prismnum\">1</span> -&gt; (<span class=\"prismident\">x1</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x2</span>'=<span class=\"prismident\">x1</span>) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Commands?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>updates variable <code>x2</code> to 0, not 2.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Constants.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Constants \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Constants.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Constants@action=edit.html'>Edit</a> - <a class='wikilink' href='Constants@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Constants</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM supports the use of <em>constants</em>, as seen in <a class='wikilink' href='Example2.html'>Example 2</a>.\nConstants can be integers, doubles or Booleans\nand can be defined using literal values or as constant expressions (including in terms of each other) using the <code><strong>const</strong></code>\nkeyword. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">radius</span> = <span class=\"prismnum\">12</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">pi</span> = <span class=\"prismnum\">3.141592</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">area</span> = <span class=\"prismident\">pi</span> * <span class=\"prismident\">radius</span> * <span class=\"prismident\">radius</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">bool</span> <span class=\"prismident\">yes</span> = <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Constants?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The identifiers used for their names are subject to the same rules as <a class='wikilink' href='ModulesAndVariables.html'>variables</a>.\n</p>\n<p class='vspace'>Constants can be used anywhere that a constant value would be expected,\nsuch as the lower or upper range of a variable (e.g. <code>N</code> in <a class='wikilink' href='Example2.html'>Example 2</a>),\nthe probability or rate associated with an update (<code>mu</code> in <a class='wikilink' href='Example2.html'>Example 2</a>),\nor anywhere in a guard or update.\nAs will be described later constants can also be left undefined\nand specified later, either to a single value or a range of values, using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'><strong>Note:</strong> For the sake of backward-compatibility, the notation used in earlier versions of PRISM\n(<code><strong>const</strong></code> for <code><strong>const int</strong></code> and <code><strong>rate</strong></code> or <code><strong>prob</strong></code> for <code><strong>const double</strong></code>) is still supported.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Constants.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Constants@action=edit.html'>Edit</a> - <a class='wikilink' href='Constants@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Constants@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:37 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='selflink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Constants@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Constants | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Constants.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Constants@action=edit.html'>Edit</a> - <a class='wikilink' href='Constants@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Constants</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Constants@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Constants.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Constants@action=edit.html'>Edit</a> - <a class='wikilink' href='Constants@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Constants@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:37 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='selflink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Constants@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Constants | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Constants.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Constants@action=edit.html'>Edit</a> - <a class='wikilink' href='Constants@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Constants</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Constants@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Constants.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Constants@action=edit.html'>Edit</a> - <a class='wikilink' href='Constants@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Constants@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:37 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='selflink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Constants@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Constants </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Constants</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM supports the use of <em>constants</em>, as seen in <a class='wikilink' href='Example2.html'>Example 2</a>.\nConstants can be integers, doubles or Booleans\nand can be defined using literal values or as constant expressions (including in terms of each other) using the <code><strong>const</strong></code>\nkeyword. For example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">radius</span> = <span class=\"prismnum\">12</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">pi</span> = <span class=\"prismnum\">3.141592</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">area</span> = <span class=\"prismident\">pi</span> * <span class=\"prismident\">radius</span> * <span class=\"prismident\">radius</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">bool</span> <span class=\"prismident\">yes</span> = <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Constants?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The identifiers used for their names are subject to the same rules as <a class='wikilink' href='ModulesAndVariables.html'>variables</a>.\n</p>\n<p class='vspace'>Constants can be used anywhere that a constant value would be expected,\nsuch as the lower or upper range of a variable (e.g. <code>N</code> in <a class='wikilink' href='Example2.html'>Example 2</a>),\nthe probability or rate associated with an update (<code>mu</code> in <a class='wikilink' href='Example2.html'>Example 2</a>),\nor anywhere in a guard or update.\nAs will be described later constants can also be left undefined\nand specified later, either to a single value or a range of values, using <a class='wikilink' href='../RunningPRISM/Experiments.html'>experiments</a>.\n</p>\n<p class='vspace'><strong>Note:</strong> For the sake of backward-compatibility, the notation used in earlier versions of PRISM\n(<code><strong>const</strong></code> for <code><strong>const int</strong></code> and <code><strong>rate</strong></code> or <code><strong>prob</strong></code> for <code><strong>const double</strong></code>) is still supported.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/CostsAndRewards.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Costs And Rewards \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CostsAndRewards.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=edit.html'>Edit</a> - <a class='wikilink' href='CostsAndRewards@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Costs And Rewards</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM supports the specification and analysis of\nproperties based on <em>costs</em> and <em>rewards</em>.\nThis means that it can be used to reason,\nnot just about the probability that a model behaves in a certain fashion,\nbut about a wider range of quantitative measures relating to model behaviour.\nFor example, PRISM can be used to compute properties such as\n\"expected time\", \"expected number of lost messages\" or \"expected power consumption\".\nThe implementation of cost- and reward-based techniques in the tool is only partially completed and is still ongoing.\nIf you have questions, comments or feature-requests relating to this functionality,\nplease feel free to contact the PRISM team about this.\n</p>\n<p class='vspace'>The basic idea is that probabilistic models (of all types) developed in PRISM\ncan be augmented with costs or rewards: real values associated with certain states or transitions of the model.\nIn fact, since there is no practical distinction between costs and rewards\n(except that costs are generally perceived to be \"bad\" and rewards to be \"good\"),\nPRISM only supports rewards.\nThe user is, however, free to interpret the values however they choose.\n</p>\n<p class='vspace'>In this section, we describe how models described in the PRISM language\ncan be augmented with rewards.\nLater, we will discuss how to express properties that relate to these rewards.\nRewards are associated with models using <code><strong>rewards</strong> ... <strong>endrewards</strong></code> constructs,\nwhich can appear anywhere in a model file except within a module definition.\nThese constructs contains one or more <em>reward items</em>.\nConsider the following simple example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r1</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CostsAndRewards?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This defines a reward structure with name <code>r1</code> (the name is optional)\nwhich assigns a reward of 1 to every state of the model.\nIt comprises a single reward item, the left part of which (<code><strong>true</strong></code>) is a guard\nand the right part of which (<code>1</code>) is a reward.\nStates of the model which satisfy the predicate in the guard are assigned the corresponding reward.\nMore generally, state rewards can be specified using multiple reward items,\neach of the form <code>guard : reward;</code>,\nwhere <code>guard</code> is a predicate (over all the variables of the model)\nand <code>reward</code> is an expression (containing any variables, constants, etc. from the model).\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r2</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> : <span class=\"prismnum\">100</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&lt;<span class=\"prismnum\">10</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">10</span> : <span class=\"prismnum\">100</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CostsAndRewards?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 100 to states satisfying <code>x=0</code> or <code>x=10</code>\nand a reward of <code>2*x</code> to states satisfying <code>x&gt;0 &amp; x&lt;10</code>.\nNote that a single reward item can assign different rewards to different states,\ndepending on the values of model variables in each one.\nAny states which do not satisfy the guard of any reward item will have no reward assigned to them.\nFor states which satisfy multiple guards, the reward assigned to the state\nis the sum of the rewards for all the corresponding reward items.\n</p>\n<p class='vspace'>Rewards can also be assigned to transitions of a model.\nThese are specified in a similar fashion to state rewards,\nwithin the <code><strong>rewards</strong> ... <strong>endrewards</strong></code> construct.\nReward items describing transition rewards are of the form <code>[action] guard : reward;</code>,\nthe interpretation being that transitions from states which satisfy the guard <code>guard</code>\nand are labelled with the action <code>action</code> acquire the reward <code>reward</code>.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r3</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">a</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CostsAndRewards?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 1 to all transitions in the model with no action label,\nand rewards of <code>x</code> and <code>2*x</code> to all transitions labelled with actions <code>a</code> and <code>b</code>, respectively.\n</p>\n<p class='vspace'>As is the case for states, multiple reward items can specify rewards for a single transition,\nin which case the resulting reward is the sum of all the individual rewards.\nA model description can specify rewards for both states and transitions.\nThese are all placed together in a single <code><strong>rewards</strong>...<strong>endrewards</strong></code> construct.\n</p>\n<p class='vspace'>A PRISM model will often have multiple reward structures, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">total_time</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n<br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">num_failures</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">fail</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CostsAndRewards?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CostsAndRewards.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=edit.html'>Edit</a> - <a class='wikilink' href='CostsAndRewards@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 11, 2025, at 04:27 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='selflink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/CostsAndRewards@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Costs And Rewards | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CostsAndRewards.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=edit.html'>Edit</a> - <a class='wikilink' href='CostsAndRewards@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Costs And Rewards</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='CostsAndRewards@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CostsAndRewards.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=edit.html'>Edit</a> - <a class='wikilink' href='CostsAndRewards@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 11, 2025, at 04:27 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='selflink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/CostsAndRewards@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Costs And Rewards | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='CostsAndRewards.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=edit.html'>Edit</a> - <a class='wikilink' href='CostsAndRewards@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Costs And Rewards</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='CostsAndRewards@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='CostsAndRewards.html'>View</a> - <a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=edit.html'>Edit</a> - <a class='wikilink' href='CostsAndRewards@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='CostsAndRewards@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 11, 2025, at 04:27 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='selflink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/CostsAndRewards@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / CostsAndRewards </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Costs And Rewards</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM supports the specification and analysis of\nproperties based on <em>costs</em> and <em>rewards</em>.\nThis means that it can be used to reason,\nnot just about the probability that a model behaves in a certain fashion,\nbut about a wider range of quantitative measures relating to model behaviour.\nFor example, PRISM can be used to compute properties such as\n\"expected time\", \"expected number of lost messages\" or \"expected power consumption\".\nThe implementation of cost- and reward-based techniques in the tool is only partially completed and is still ongoing.\nIf you have questions, comments or feature-requests relating to this functionality,\nplease feel free to contact the PRISM team about this.\n</p>\n<p class='vspace'>The basic idea is that probabilistic models (of all types) developed in PRISM\ncan be augmented with costs or rewards: real values associated with certain states or transitions of the model.\nIn fact, since there is no practical distinction between costs and rewards\n(except that costs are generally perceived to be \"bad\" and rewards to be \"good\"),\nPRISM only supports rewards.\nThe user is, however, free to interpret the values however they choose.\n</p>\n<p class='vspace'>In this section, we describe how models described in the PRISM language\ncan be augmented with rewards.\nLater, we will discuss how to express properties that relate to these rewards.\nRewards are associated with models using <code><strong>rewards</strong> ... <strong>endrewards</strong></code> constructs,\nwhich can appear anywhere in a model file except within a module definition.\nThese constructs contains one or more <em>reward items</em>.\nConsider the following simple example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r1</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CostsAndRewards?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>This defines a reward structure with name <code>r1</code> (the name is optional)\nwhich assigns a reward of 1 to every state of the model.\nIt comprises a single reward item, the left part of which (<code><strong>true</strong></code>) is a guard\nand the right part of which (<code>1</code>) is a reward.\nStates of the model which satisfy the predicate in the guard are assigned the corresponding reward.\nMore generally, state rewards can be specified using multiple reward items,\neach of the form <code>guard : reward;</code>,\nwhere <code>guard</code> is a predicate (over all the variables of the model)\nand <code>reward</code> is an expression (containing any variables, constants, etc. from the model).\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r2</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> : <span class=\"prismnum\">100</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>&gt;<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&lt;<span class=\"prismnum\">10</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span>=<span class=\"prismnum\">10</span> : <span class=\"prismnum\">100</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CostsAndRewards?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 100 to states satisfying <code>x=0</code> or <code>x=10</code>\nand a reward of <code>2*x</code> to states satisfying <code>x&gt;0 &amp; x&lt;10</code>.\nNote that a single reward item can assign different rewards to different states,\ndepending on the values of model variables in each one.\nAny states which do not satisfy the guard of any reward item will have no reward assigned to them.\nFor states which satisfy multiple guards, the reward assigned to the state\nis the sum of the rewards for all the corresponding reward items.\n</p>\n<p class='vspace'>Rewards can also be assigned to transitions of a model.\nThese are specified in a similar fashion to state rewards,\nwithin the <code><strong>rewards</strong> ... <strong>endrewards</strong></code> construct.\nReward items describing transition rewards are of the form <code>[action] guard : reward;</code>,\nthe interpretation being that transitions from states which satisfy the guard <code>guard</code>\nand are labelled with the action <code>action</code> acquire the reward <code>reward</code>.\nFor example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">r3</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">a</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismident\">x</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">b</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">2</span>*<span class=\"prismident\">x</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CostsAndRewards?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>assigns a reward of 1 to all transitions in the model with no action label,\nand rewards of <code>x</code> and <code>2*x</code> to all transitions labelled with actions <code>a</code> and <code>b</code>, respectively.\n</p>\n<p class='vspace'>As is the case for states, multiple reward items can specify rewards for a single transition,\nin which case the resulting reward is the sum of all the individual rewards.\nA model description can specify rewards for both states and transitions.\nThese are all placed together in a single <code><strong>rewards</strong>...<strong>endrewards</strong></code> construct.\n</p>\n<p class='vspace'>A PRISM model will often have multiple reward structures, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">total_time</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n<br/>\n<span class=\"prismkeyword\">rewards</span> \"<span class=\"prismident\">num_failures</span>\"<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">fail</span>] <span class=\"prismkeyword\">true</span> : <span class=\"prismnum\">1</span>;<br/>\n<span class=\"prismkeyword\">endrewards</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/CostsAndRewards?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Example1.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Example 1 \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Example1.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Example1@action=edit.html'>Edit</a> - <a class='wikilink' href='Example1@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Example 1</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>We will use the following simple example to illustrate the basic concepts of the PRISM language.\nConsider a system comprising two identical processes which must operate under mutual exclusion.\nEach process can be in one of 3 states: {0,1,2}.\nFrom state 0, a process will move to state 1 with probability 0.2\nand remain in the same state with probability 0.8.\nFrom state 1, it tries to move to the critical section: state 2.\nThis can only occur if the other process is not in its critical section.\nFinally, from state 2, a process will either remain there or move back to state 0\nwith equal probability.\nThe PRISM code to describe an MDP model of this system can be seen below.\nIn the next sections, we explain each aspect of the code in turn.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 1</span><br/>\n<span class=\"prismcomment\">// Two process mutual exclusion</span><br/>\n<br/>\n<span class=\"prismkeyword\">mdp</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M1</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">y</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Example1?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 1</strong>\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Example1.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Example1@action=edit.html'>Edit</a> - <a class='wikilink' href='Example1@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Example1@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 11:48 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Example1@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Example 1 | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Example1.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Example1@action=edit.html'>Edit</a> - <a class='wikilink' href='Example1@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Example 1</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Example1@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Example1.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Example1@action=edit.html'>Edit</a> - <a class='wikilink' href='Example1@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Example1@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 11:48 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Example1@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Example 1 | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Example1.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Example1@action=edit.html'>Edit</a> - <a class='wikilink' href='Example1@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Example 1</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Example1@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Example1.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Example1@action=edit.html'>Edit</a> - <a class='wikilink' href='Example1@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Example1@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 11:48 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='selflink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Example1@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Example1 </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Example 1</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>We will use the following simple example to illustrate the basic concepts of the PRISM language.\nConsider a system comprising two identical processes which must operate under mutual exclusion.\nEach process can be in one of 3 states: {0,1,2}.\nFrom state 0, a process will move to state 1 with probability 0.2\nand remain in the same state with probability 0.8.\nFrom state 1, it tries to move to the critical section: state 2.\nThis can only occur if the other process is not in its critical section.\nFinally, from state 2, a process will either remain there or move back to state 0\nwith equal probability.\nThe PRISM code to describe an MDP model of this system can be seen below.\nIn the next sections, we explain each aspect of the code in turn.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 1</span><br/>\n<span class=\"prismcomment\">// Two process mutual exclusion</span><br/>\n<br/>\n<span class=\"prismkeyword\">mdp</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M1</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">y</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">y</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>!=<span class=\"prismnum\">2</span> -&gt; (<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">y</span>=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">2</span>) + <span class=\"prismnum\">0.5</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Example1?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 1</strong>\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Example2.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Example 2 \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Example2.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Example2@action=edit.html'>Edit</a> - <a class='wikilink' href='Example2@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Example 2</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>We now introduce a second example: a CTMC that models an <em>N</em>-place queue of jobs and\na server which removes jobs from the queue and processes them.\nThe PRISM code is as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 2</span><br/>\n<span class=\"prismcomment\">// N-place queue + server</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span> = <span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mu</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">lambda</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">2</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">gamma</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">3</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">queue</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">q</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">N</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>&lt;<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>+<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>=<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">server</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">s</span>=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismident\">gamma</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">0</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Example2?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 2</strong>\n</p>\n<p class='vspace'>This example also introduces a number of other PRISM language concepts,\nincluding <a class='wikilink' href='Constants.html'>constants</a>, action labels and <a class='wikilink' href='Synchronisation.html'>synchronisation</a>.\nThese are described in the following sections.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Example2.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Example2@action=edit.html'>Edit</a> - <a class='wikilink' href='Example2@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Example2@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='selflink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Example2@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Example 2 | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Example2.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Example2@action=edit.html'>Edit</a> - <a class='wikilink' href='Example2@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Example 2</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Example2@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Example2.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Example2@action=edit.html'>Edit</a> - <a class='wikilink' href='Example2@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Example2@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='selflink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Example2@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Example 2 | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Example2.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Example2@action=edit.html'>Edit</a> - <a class='wikilink' href='Example2@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Example 2</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Example2@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Example2.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Example2@action=edit.html'>Edit</a> - <a class='wikilink' href='Example2@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Example2@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:26 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='selflink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Example2@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Example2 </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Example 2</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>We now introduce a second example: a CTMC that models an <em>N</em>-place queue of jobs and\na server which removes jobs from the queue and processes them.\nThe PRISM code is as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismcomment\">// Example 2</span><br/>\n<span class=\"prismcomment\">// N-place queue + server</span><br/>\n<br/>\n<span class=\"prismkeyword\">ctmc</span><br/>\n<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">int</span> <span class=\"prismident\">N</span> = <span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">mu</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">10</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">lambda</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">2</span>;<br/>\n<span class=\"prismkeyword\">const</span> <span class=\"prismkeyword\">double</span> <span class=\"prismident\">gamma</span> = <span class=\"prismnum\">1</span>/<span class=\"prismnum\">3</span>;<br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">queue</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">q</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismident\">N</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>&lt;<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>+<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">q</span>=<span class=\"prismident\">N</span> -&gt; <span class=\"prismident\">mu</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">server</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">1</span>];<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">serve</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;[] <span class=\"prismident\">s</span>=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismident\">gamma</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">0</span>);<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Example2?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'  style='text-align: center;'><strong>The PRISM Language: Example 2</strong>\n</p>\n<p class='vspace'>This example also introduces a number of other PRISM language concepts,\nincluding <a class='wikilink' href='Constants.html'>constants</a>, action labels and <a class='wikilink' href='Synchronisation.html'>synchronisation</a>.\nThese are described in the following sections.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Expressions.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Expressions \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Expressions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Expressions@action=edit.html'>Edit</a> - <a class='wikilink' href='Expressions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Expressions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The definition of the <code>area</code> constant, in the example above, uses an <em>expression</em>.\nWe now define more precisely what types of expression are supported by PRISM.\nExpressions can contain literal values (12, 3.141592, <code><strong>true</strong></code>, <code><strong>false</strong></code>, etc.),\nidentifiers (corresponding to variables, constants, etc.) and operators from the following list:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>^</code> (power)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li></ul><p class='vspace'>All of these operators except <code>?</code> and <code>=&gt;</code> are left associative\n(i.e. they are evaluated from left to right).\nThe precedence of the operators is as found in the list above,\nmost strongly binding operators first.\nOperators on the same line (e.g. <code>+</code> and <code>-</code>) are of equal precedence.\n</p>\n<p class='vspace'>Much of the notation for expressions is hence essentially equivalent to that of C/C++ or Java.\nOne notable exception to this is that  the division operator <code>/</code> always performs floating point, not integer, division,\ni.e. the result of <code>22/7</code> is 3.142857... not 3.\nAll expressions must evaluate correctly in terms of type (integer, double or Boolean).\n</p>\n<p class='vspace'><strong>Built-in Functions</strong>\n</p>\n<p class='vspace'>Expressions can make use of several built-in functions:\n</p>\n<div class='vspace'></div><ul><li><code>min(...)</code> and <code>max(...)</code>, which select the minimum and maximum value, respectively, of two or more numbers\n</li><li><code>floor(x)</code> and <code>ceil(x)</code>, which round <code>x</code> down and up, respectively, to the nearest integer\n</li><li><code>round(x)</code>, which rounds <code>x</code> to the nearest integer (note, in a tie-break, we always round <em>up</em>, e.g. <code>round(-1.5)</code> gives <code>-1</code> not <code>-2</code>)\n</li><li><code>pow(x,y)</code> which computes <code>x</code> to the power of <code>y</code> (same as <code>x^y</code>)\n</li><li><code>mod(i,n)</code> for integer modulo operations\n</li><li><code>log(x,b)</code>, which computes the logarithm of <code>x</code> to base <code>b</code>\n</li></ul><p class='vspace'>Examples of their usage are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">min</span>(<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>, <span class=\"prismident\">x_max</span>)<br/>\n<span class=\"prismkeyword\">max</span>(<span class=\"prismident\">a</span>,<span class=\"prismident\">b</span>,<span class=\"prismident\">c</span>)<br/>\n<span class=\"prismident\">floor</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">ceil</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">round</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">2</span>, <span class=\"prismnum\">8</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">9.0</span>, <span class=\"prismnum\">0.5</span>)<br/>\n<span class=\"prismident\">mod</span>(<span class=\"prismnum\">1977</span>, <span class=\"prismnum\">100</span>)<br/>\n<span class=\"prismident\">log</span>(<span class=\"prismnum\">123</span>, <span class=\"prismnum\">2.71828183</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Expressions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For compatibility with older versions of PRISM, all functions can also be expressed via the <code><strong>func</strong></code> keyword, e.g. <code>func(floor, 13.5)</code>.\n</p>\n<p class='vspace'><strong>Use of Expressions</strong>\n</p>\n<p class='vspace'>Expressions can be used in a wide range of places in a PRISM language description, e.g.:\n</p>\n<div class='vspace'></div><ul><li>constant definitions\n</li><li>lower/upper bounds and initial values for variables\n</li><li>guards\n</li><li>probabilities/rates\n</li><li>updates\n</li></ul><p class='vspace'>This allows, for example, the probability in a command to be dependent on the current state:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] (<span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span>) -&gt; <span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">max</span>(<span class=\"prismnum\">1</span>,<span class=\"prismident\">x</span>-<span class=\"prismnum\">1</span>)) + <span class=\"prismnum\">1</span>-<span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">min</span>(<span class=\"prismnum\">10</span>,<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>)) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Expressions?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Expressions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Expressions@action=edit.html'>Edit</a> - <a class='wikilink' href='Expressions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Expressions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 05:17 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='selflink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Expressions@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Expressions | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Expressions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Expressions@action=edit.html'>Edit</a> - <a class='wikilink' href='Expressions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Expressions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Expressions@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Expressions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Expressions@action=edit.html'>Edit</a> - <a class='wikilink' href='Expressions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Expressions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 05:17 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='selflink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Expressions@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Expressions | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Expressions.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Expressions@action=edit.html'>Edit</a> - <a class='wikilink' href='Expressions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Expressions</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Expressions@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Expressions.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Expressions@action=edit.html'>Edit</a> - <a class='wikilink' href='Expressions@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Expressions@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 06, 2025, at 05:17 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='selflink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Expressions@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Expressions </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Expressions</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>The definition of the <code>area</code> constant, in the example above, uses an <em>expression</em>.\nWe now define more precisely what types of expression are supported by PRISM.\nExpressions can contain literal values (12, 3.141592, <code><strong>true</strong></code>, <code><strong>false</strong></code>, etc.),\nidentifiers (corresponding to variables, constants, etc.) and operators from the following list:\n</p>\n<div class='vspace'></div><ul><li><code>-</code> (unary minus)\n</li><li><code>^</code> (power)\n</li><li><code>*</code>, <code>/</code> (multiplication, division)\n</li><li><code>+</code>, <code>-</code> (addition, subtraction)\n</li><li><code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code> (relational operators)\n</li><li><code>=</code>, <code>!=</code> (equality operators)\n</li><li><code>!</code> (negation)\n</li><li><code>&amp;</code> (conjunction)\n</li><li><code>|</code> (disjunction)\n</li><li><code>&lt;=&gt;</code> (if-and-only-if)\n</li><li><code>=&gt;</code> (implication)\n</li><li><code>?</code> (condition evaluation: <code>condition ? a : b</code> means \"if <code>condition</code> is true then <code>a</code> else <code>b</code>\")\n</li></ul><p class='vspace'>All of these operators except <code>?</code> and <code>=&gt;</code> are left associative\n(i.e. they are evaluated from left to right).\nThe precedence of the operators is as found in the list above,\nmost strongly binding operators first.\nOperators on the same line (e.g. <code>+</code> and <code>-</code>) are of equal precedence.\n</p>\n<p class='vspace'>Much of the notation for expressions is hence essentially equivalent to that of C/C++ or Java.\nOne notable exception to this is that  the division operator <code>/</code> always performs floating point, not integer, division,\ni.e. the result of <code>22/7</code> is 3.142857... not 3.\nAll expressions must evaluate correctly in terms of type (integer, double or Boolean).\n</p>\n<p class='vspace'><strong>Built-in Functions</strong>\n</p>\n<p class='vspace'>Expressions can make use of several built-in functions:\n</p>\n<div class='vspace'></div><ul><li><code>min(...)</code> and <code>max(...)</code>, which select the minimum and maximum value, respectively, of two or more numbers\n</li><li><code>floor(x)</code> and <code>ceil(x)</code>, which round <code>x</code> down and up, respectively, to the nearest integer\n</li><li><code>round(x)</code>, which rounds <code>x</code> to the nearest integer (note, in a tie-break, we always round <em>up</em>, e.g. <code>round(-1.5)</code> gives <code>-1</code> not <code>-2</code>)\n</li><li><code>pow(x,y)</code> which computes <code>x</code> to the power of <code>y</code> (same as <code>x^y</code>)\n</li><li><code>mod(i,n)</code> for integer modulo operations\n</li><li><code>log(x,b)</code>, which computes the logarithm of <code>x</code> to base <code>b</code>\n</li></ul><p class='vspace'>Examples of their usage are:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">min</span>(<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>, <span class=\"prismident\">x_max</span>)<br/>\n<span class=\"prismkeyword\">max</span>(<span class=\"prismident\">a</span>,<span class=\"prismident\">b</span>,<span class=\"prismident\">c</span>)<br/>\n<span class=\"prismident\">floor</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">ceil</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">round</span>(<span class=\"prismnum\">13.5</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">2</span>, <span class=\"prismnum\">8</span>)<br/>\n<span class=\"prismident\">pow</span>(<span class=\"prismnum\">9.0</span>, <span class=\"prismnum\">0.5</span>)<br/>\n<span class=\"prismident\">mod</span>(<span class=\"prismnum\">1977</span>, <span class=\"prismnum\">100</span>)<br/>\n<span class=\"prismident\">log</span>(<span class=\"prismnum\">123</span>, <span class=\"prismnum\">2.71828183</span>)<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Expressions?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For compatibility with older versions of PRISM, all functions can also be expressed via the <code><strong>func</strong></code> keyword, e.g. <code>func(floor, 13.5)</code>.\n</p>\n<p class='vspace'><strong>Use of Expressions</strong>\n</p>\n<p class='vspace'>Expressions can be used in a wide range of places in a PRISM language description, e.g.:\n</p>\n<div class='vspace'></div><ul><li>constant definitions\n</li><li>lower/upper bounds and initial values for variables\n</li><li>guards\n</li><li>probabilities/rates\n</li><li>updates\n</li></ul><p class='vspace'>This allows, for example, the probability in a command to be dependent on the current state:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] (<span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> &amp; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">10</span>) -&gt; <span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">max</span>(<span class=\"prismnum\">1</span>,<span class=\"prismident\">x</span>-<span class=\"prismnum\">1</span>)) + <span class=\"prismnum\">1</span>-<span class=\"prismident\">x</span>/<span class=\"prismnum\">10</span> : (<span class=\"prismident\">x</span>'=<span class=\"prismkeyword\">min</span>(<span class=\"prismnum\">10</span>,<span class=\"prismident\">x</span>+<span class=\"prismnum\">1</span>)) <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Expressions?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/FormulasAndLabels.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Formulas And Labels \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='FormulasAndLabels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=edit.html'>Edit</a> - <a class='wikilink' href='FormulasAndLabels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Formulas And Labels</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM models can include <em>formulas</em> which are used to avoid duplication of code.\nA formula comprises a name (an identifier) and an <a class='wikilink' href='Expressions.html'>expression</a>.\nThe formula name can then be used as shorthand for the expression anywhere an expression might usually be accepted.\nA formula is defined as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">formula</span> <span class=\"prismident\">num_tokens</span> = <span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/FormulasAndLabels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It can then be used anywhere within that file, as for example in this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">num_tokens</span>=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/FormulasAndLabels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The effect is exactly as if the following had been typed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; (<span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>)=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/FormulasAndLabels?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Formulas defined in a model can also be used when specifying its properties.\n</p>\n<div class='vspace'></div><h3>Formulas and renaming</h3>\n<p>During parsing of the model, expansion of formulas is done before module renaming so, if a module which uses formulas is renamed to another module, it is the contents of the formula which will be renamed, not the formula itself.\n</p>\n<div class='vspace'></div><h3>Labels</h3>\n<p>PRISM models can also contain <em>labels</em>. These are a way of identifying sets of states that are of particular interest. Labels can only be used when specifying <a class='wikilink' href='../PropertySpecification/Main.html'>properties</a> but, for convenience, can be defined in model files as well as property files. \n</p>\n<p class='vspace'>Labels differ from formulas in two other ways: firstly, they must be of Boolean type;\nsecondly, they are written using quotation marks (<code>\"...\"</code>), as illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/FormulasAndLabels?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='FormulasAndLabels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=edit.html'>Edit</a> - <a class='wikilink' href='FormulasAndLabels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 11, 2022, at 08:18 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='selflink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/FormulasAndLabels@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Formulas And Labels | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='FormulasAndLabels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=edit.html'>Edit</a> - <a class='wikilink' href='FormulasAndLabels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Formulas And Labels</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='FormulasAndLabels@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='FormulasAndLabels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=edit.html'>Edit</a> - <a class='wikilink' href='FormulasAndLabels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 11, 2022, at 08:18 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='selflink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/FormulasAndLabels@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Formulas And Labels | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='FormulasAndLabels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=edit.html'>Edit</a> - <a class='wikilink' href='FormulasAndLabels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Formulas And Labels</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='FormulasAndLabels@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='FormulasAndLabels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=edit.html'>Edit</a> - <a class='wikilink' href='FormulasAndLabels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='FormulasAndLabels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on May 11, 2022, at 08:18 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='selflink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/FormulasAndLabels@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / FormulasAndLabels </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Formulas And Labels</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM models can include <em>formulas</em> which are used to avoid duplication of code.\nA formula comprises a name (an identifier) and an <a class='wikilink' href='Expressions.html'>expression</a>.\nThe formula name can then be used as shorthand for the expression anywhere an expression might usually be accepted.\nA formula is defined as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">formula</span> <span class=\"prismident\">num_tokens</span> = <span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/FormulasAndLabels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It can then be used anywhere within that file, as for example in this command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">num_tokens</span>=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/FormulasAndLabels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The effect is exactly as if the following had been typed:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">p1</span>=<span class=\"prismnum\">2</span> &amp; (<span class=\"prismident\">q1</span>+<span class=\"prismident\">q2</span>+<span class=\"prismident\">q3</span>+<span class=\"prismident\">q</span>+<span class=\"prismident\">q5</span>)=<span class=\"prismnum\">5</span> -&gt; (<span class=\"prismident\">p1</span>'=<span class=\"prismnum\">4</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/FormulasAndLabels?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Formulas defined in a model can also be used when specifying its properties.\n</p>\n<div class='vspace'></div><h3>Formulas and renaming</h3>\n<p>During parsing of the model, expansion of formulas is done before module renaming so, if a module which uses formulas is renamed to another module, it is the contents of the formula which will be renamed, not the formula itself.\n</p>\n<div class='vspace'></div><h3>Labels</h3>\n<p>PRISM models can also contain <em>labels</em>. These are a way of identifying sets of states that are of particular interest. Labels can only be used when specifying <a class='wikilink' href='../PropertySpecification/Main.html'>properties</a> but, for convenience, can be defined in model files as well as property files. \n</p>\n<p class='vspace'>Labels differ from formulas in two other ways: firstly, they must be of Boolean type;\nsecondly, they are written using quotation marks (<code>\"...\"</code>), as illustrated in the following example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">safe</span>\" = <span class=\"prismident\">temp</span>&lt;=<span class=\"prismnum\">100</span> | <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">true</span>;<br/>\n<span class=\"prismkeyword\">label</span> \"<span class=\"prismident\">fail</span>\" = <span class=\"prismident\">temp</span>&gt;<span class=\"prismnum\">100</span> &amp; <span class=\"prismident\">alarm</span>=<span class=\"prismkeyword\">false</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/FormulasAndLabels?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/GlobalVariables.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Global Variables \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='GlobalVariables.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='GlobalVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='GlobalVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Global Variables</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>In addition to the local variables belonging to each module, a PRISM model can also include <em>global variables</em>,\nwhich can be written to, as well as read, by all modules.\nLike local variables, these can be integers or Booleans.\nGlobal variables are declared in identical fashion to a module's local variables,\nexcept that the declaration must not be inside the definition of any module.\nSome example declarations are as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">global</span> <span class=\"prismident\">g</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismnum\">10</span>];<br/>\n<span class=\"prismkeyword\">global</span> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/GlobalVariables?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A global variable can be modified by any module and provides another way for modules to interact.\nAn important restriction on the use of global variables is the fact that commands which synchronise with other modules\n(i.e. those with an action label attached; see the section \"<a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\") cannot modify global variables.\nPRISM will detect this and report an error.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='GlobalVariables.html'>View</a> - <a rel='nofollow'  class='wikilink' href='GlobalVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='GlobalVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='GlobalVariables@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 04, 2006, at 02:50 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='selflink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/GlobalVariables@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Global Variables | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='GlobalVariables.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='GlobalVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='GlobalVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Global Variables</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='GlobalVariables@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='GlobalVariables.html'>View</a> - <a rel='nofollow'  class='wikilink' href='GlobalVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='GlobalVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='GlobalVariables@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 04, 2006, at 02:50 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='selflink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/GlobalVariables@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Global Variables | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='GlobalVariables.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='GlobalVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='GlobalVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Global Variables</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='GlobalVariables@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='GlobalVariables.html'>View</a> - <a rel='nofollow'  class='wikilink' href='GlobalVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='GlobalVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='GlobalVariables@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on July 04, 2006, at 02:50 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='selflink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/GlobalVariables@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / GlobalVariables </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Global Variables</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>In addition to the local variables belonging to each module, a PRISM model can also include <em>global variables</em>,\nwhich can be written to, as well as read, by all modules.\nLike local variables, these can be integers or Booleans.\nGlobal variables are declared in identical fashion to a module's local variables,\nexcept that the declaration must not be inside the definition of any module.\nSome example declarations are as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">global</span> <span class=\"prismident\">g</span> : [<span class=\"prismnum\">1</span>..<span class=\"prismnum\">10</span>];<br/>\n<span class=\"prismkeyword\">global</span> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">true</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/GlobalVariables?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>A global variable can be modified by any module and provides another way for modules to interact.\nAn important restriction on the use of global variables is the fact that commands which synchronise with other modules\n(i.e. those with an action label attached; see the section \"<a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\") cannot modify global variables.\nPRISM will detect this and report an error.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Introduction@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Introduction | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Introduction@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 09:41 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Introduction@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Introduction | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Introduction@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 09:41 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Introduction@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Introduction </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Introduction</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>In order to construct and analyse a model with PRISM,\nit must be specified in the PRISM language,\na simple, state-based language,\nbased on the Reactive Modules formalism of Alur and Henzinger [<a class='wikilink' href='../Main/References.html#AH99'>AH99</a>].\nThis is used for <a class='wikilink' href='../Main/Introduction.html'>all of the types of model</a> that PRISM supports.\n</p>\n<p class='vspace'>In this section, we describe the PRISM language and present a number of small illustrative examples.\nA precise definition of the semantics of the language is available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site. One of the best ways to learn what can be done with the PRISM language is to look at some existing examples.\nA number of these are included with the tool distribution in the <code>prism-examples</code> directory.\nMany additional examples can be found on the \"<a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a>\" section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<p class='vspace'>The fundamental components of the PRISM language are <em>modules</em> and <em>variables</em>.\nA model is composed of a number of <em>modules</em> which can interact with each other.\nA module contains a number of local <em>variables</em>.\nThe values of these variables at any given time constitute the state of the module.\nThe <em>global state</em> of the whole model is determined by the <em>local state</em> of all modules.\nThe behaviour of each module is described by a set of <em>commands</em>.\nA command takes the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[<span class=\"prismident\">action</span>] <span class=\"prismident\">guard</span> -&gt; <span class=\"prismident\">prob_1</span> : <span class=\"prismident\">update_1</span> + ... + <span class=\"prismident\">prob_n</span> : <span class=\"prismident\">update_n</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Introduction?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <em>guard</em> is a predicate over all the variables in the model (including those belonging to other modules). Each <em>update</em> describes a transition which the module can make if the guard is true. A transition is specified by giving the new values of the variables in the module, possibly as a function of other variables. Each update is assigned a probability (or in some cases a rate) which will be assigned to the corresponding transition. The command also optionally includes an <em>action</em>, either just to annotate it, or for <a class='wikilink' href='Synchronisation.html'>synchronisation</a>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/LocalNondeterminism.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Local Nondeterminism \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='LocalNondeterminism.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=edit.html'>Edit</a> - <a class='wikilink' href='LocalNondeterminism@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Local Nondeterminism</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM models that support nondeterminism, such as are MDPs, can also exhibit <em>local nondeterminism</em>,\nwhich allows the modules themselves to make nondeterministic choices.\nIn <a class='wikilink' href='Example1.html'>Example 1</a>, we can make the probabilistic choice in the first state of module <code>M1</code> nondeterministic by replacing the command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/LocalNondeterminism?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>with the commands:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/LocalNondeterminism?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Assuming we do the same for module <code>M2</code>, in state <code>(0,0)</code> of the MDP\nthere will be a nondeterministic choice between the three (trivial) probability distributions listed below. (There are three, not four, distributions because two possibilities result in identical behaviour: staying with probability 1 in the state state.)\n</p>\n<div class='vspace'></div><ul><li><code>1.0:(0,0)</code>\n</li><li><code>1.0:(1,0)</code>\n</li><li><code>1.0:(0,1)</code>\n</li></ul><p class='vspace'>More generally, local nondeterminism can also arise when the guards of two commands overlap only partially, rather than completely as in the example above.\n</p>\n<p class='vspace'>PRISM also permits local nondeterminism in models which are DTMCs,\nalthough the nondeterministic choice is randomised when the parallel composition of the modules occurs.\nSince the appearance of nondeterminism in a DTMC is often the result of\na user error in the model specification, PRISM displays a warning when local nondeterminism is detected in a DTMC.\nOverlapping guards in <a class='wikilink' href='CTMCs.html'>CTMCs</a> are not treated as nondeterministic choices.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='LocalNondeterminism.html'>View</a> - <a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=edit.html'>Edit</a> - <a class='wikilink' href='LocalNondeterminism@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:19 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='selflink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/LocalNondeterminism@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Local Nondeterminism | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='LocalNondeterminism.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=edit.html'>Edit</a> - <a class='wikilink' href='LocalNondeterminism@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Local Nondeterminism</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='LocalNondeterminism@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='LocalNondeterminism.html'>View</a> - <a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=edit.html'>Edit</a> - <a class='wikilink' href='LocalNondeterminism@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:19 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='selflink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/LocalNondeterminism@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Local Nondeterminism | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='LocalNondeterminism.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=edit.html'>Edit</a> - <a class='wikilink' href='LocalNondeterminism@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Local Nondeterminism</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='LocalNondeterminism@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='LocalNondeterminism.html'>View</a> - <a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=edit.html'>Edit</a> - <a class='wikilink' href='LocalNondeterminism@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='LocalNondeterminism@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:19 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='selflink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/LocalNondeterminism@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / LocalNondeterminism </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Local Nondeterminism</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM models that support nondeterminism, such as are MDPs, can also exhibit <em>local nondeterminism</em>,\nwhich allows the modules themselves to make nondeterministic choices.\nIn <a class='wikilink' href='Example1.html'>Example 1</a>, we can make the probabilistic choice in the first state of module <code>M1</code> nondeterministic by replacing the command:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/LocalNondeterminism?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>with the commands:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n[] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; (<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>);<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/LocalNondeterminism?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Assuming we do the same for module <code>M2</code>, in state <code>(0,0)</code> of the MDP\nthere will be a nondeterministic choice between the three (trivial) probability distributions listed below. (There are three, not four, distributions because two possibilities result in identical behaviour: staying with probability 1 in the state state.)\n</p>\n<div class='vspace'></div><ul><li><code>1.0:(0,0)</code>\n</li><li><code>1.0:(1,0)</code>\n</li><li><code>1.0:(0,1)</code>\n</li></ul><p class='vspace'>More generally, local nondeterminism can also arise when the guards of two commands overlap only partially, rather than completely as in the example above.\n</p>\n<p class='vspace'>PRISM also permits local nondeterminism in models which are DTMCs,\nalthough the nondeterministic choice is randomised when the parallel composition of the modules occurs.\nSince the appearance of nondeterminism in a DTMC is often the result of\na user error in the model specification, PRISM displays a warning when local nondeterminism is detected in a DTMC.\nOverlapping guards in <a class='wikilink' href='CTMCs.html'>CTMCs</a> are not treated as nondeterministic choices.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Main.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Introduction \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Introduction</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>In order to construct and analyse a model with PRISM,\nit must be specified in the PRISM language,\na simple, state-based language,\nbased on the Reactive Modules formalism of Alur and Henzinger [<a class='wikilink' href='../Main/References.html#AH99'>AH99</a>].\nThis is used for <a class='wikilink' href='../Main/Introduction.html'>all of the types of model</a> that PRISM supports.\n</p>\n<p class='vspace'>In this section, we describe the PRISM language and present a number of small illustrative examples.\nA precise definition of the semantics of the language is available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site. One of the best ways to learn what can be done with the PRISM language is to look at some existing examples.\nA number of these are included with the tool distribution in the <code>prism-examples</code> directory.\nMany additional examples can be found on the \"<a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>Case Studies</a>\" section of the <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<p class='vspace'>The fundamental components of the PRISM language are <em>modules</em> and <em>variables</em>.\nA model is composed of a number of <em>modules</em> which can interact with each other.\nA module contains a number of local <em>variables</em>.\nThe values of these variables at any given time constitute the state of the module.\nThe <em>global state</em> of the whole model is determined by the <em>local state</em> of all modules.\nThe behaviour of each module is described by a set of <em>commands</em>.\nA command takes the form:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\">[<span class=\"prismident\">action</span>] <span class=\"prismident\">guard</span> -&gt; <span class=\"prismident\">prob_1</span> : <span class=\"prismident\">update_1</span> + ... + <span class=\"prismident\">prob_n</span> : <span class=\"prismident\">update_n</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Introduction?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The <em>guard</em> is a predicate over all the variables in the model (including those belonging to other modules). Each <em>update</em> describes a transition which the module can make if the guard is true. A transition is specified by giving the new values of the variables in the module, possibly as a function of other variables. Each update is assigned a probability (or in some cases a rate) which will be assigned to the corresponding transition. The command also optionally includes an <em>action</em>, either just to annotate it, or for <a class='wikilink' href='Synchronisation.html'>synchronisation</a>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=edit.html'>Edit</a> - <a class='wikilink' href='Introduction@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Introduction@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 09:41 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='selflink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModelType.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Model Type \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModelType.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModelType@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelType@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Model Type</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>As mentioned above, the PRISM language can be used to describe several types of probabilistic models.\nTo indicate which type is being described, a PRISM model usually includes a model type keyword:\n</p>\n<div class='vspace'></div><ul><li><code><strong>dtmc</strong></code>: discrete-time Markov chain\n</li><li><code><strong>ctmc</strong></code>: continuous-time Markov chain\n</li><li><code><strong>mdp</strong></code>: Markov decision process (or probabilistic automaton)\n</li><li><code><strong>pta</strong></code>: probabilistic timed automaton\n</li><li><code><strong>pomdp</strong></code>: partially observable Markov decision process\n</li><li><code><strong>popta</strong></code>: partially observable probabilistic timed automaton\n</li></ul><p class='vspace'>This is typically at the very start of the file,\nbut can actually occur anywhere in the file (except inside modules and other declarations).\n</p>\n<p class='vspace'>If no such model type declaration is included, the model is by default assumed to be an MDP.\nPRISM also performs some auto-detection of the model type;\nfor example, an MDP with <a class='wikilink' href='Real-timeModels.html'>clock variables</a> is assumed to be a PTA,\nand an MDP with <a class='createlinktext' rel='nofollow'\n    href='POMDPs@action=edit.html'>observables</a><a rel='nofollow' \n    class='createlink' href='POMDPs@action=edit.html'>?</a> is assumed to be a POMDP.\n</p>\n<p class='vspace'><strong>Note:</strong> For compatibility with old versions of PRISM,\nthe keywords <code><strong>probabilistic</strong></code>, <code><strong>stochastic</strong></code> and <code><strong>nondeterministic</strong></code>\ncan be used as alternatives for <code><strong>dtmc</strong></code>, <code><strong>ctmc</strong></code> and <code><strong>mdp</strong></code>, respectively.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModelType.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModelType@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelType@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModelType@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 10:47 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='selflink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModelType@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Model Type | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModelType.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModelType@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelType@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Model Type</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ModelType@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModelType.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModelType@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelType@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModelType@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 10:47 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='selflink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModelType@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Model Type | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModelType.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModelType@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelType@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Model Type</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ModelType@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModelType.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModelType@action=edit.html'>Edit</a> - <a class='wikilink' href='ModelType@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModelType@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 10:47 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='selflink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModelType@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / ModelType </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Model Type</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>As mentioned above, the PRISM language can be used to describe several types of probabilistic models.\nTo indicate which type is being described, a PRISM model usually includes a model type keyword:\n</p>\n<div class='vspace'></div><ul><li><code><strong>dtmc</strong></code>: discrete-time Markov chain\n</li><li><code><strong>ctmc</strong></code>: continuous-time Markov chain\n</li><li><code><strong>mdp</strong></code>: Markov decision process (or probabilistic automaton)\n</li><li><code><strong>pta</strong></code>: probabilistic timed automaton\n</li><li><code><strong>pomdp</strong></code>: partially observable Markov decision process\n</li><li><code><strong>popta</strong></code>: partially observable probabilistic timed automaton\n</li></ul><p class='vspace'>This is typically at the very start of the file,\nbut can actually occur anywhere in the file (except inside modules and other declarations).\n</p>\n<p class='vspace'>If no such model type declaration is included, the model is by default assumed to be an MDP.\nPRISM also performs some auto-detection of the model type;\nfor example, an MDP with <a class='wikilink' href='Real-timeModels.html'>clock variables</a> is assumed to be a PTA,\nand an MDP with <a class='createlinktext' rel='nofollow'\n    href='POMDPs@action=edit.html'>observables</a><a rel='nofollow' \n    class='createlink' href='POMDPs@action=edit.html'>?</a> is assumed to be a POMDP.\n</p>\n<p class='vspace'><strong>Note:</strong> For compatibility with old versions of PRISM,\nthe keywords <code><strong>probabilistic</strong></code>, <code><strong>stochastic</strong></code> and <code><strong>nondeterministic</strong></code>\ncan be used as alternatives for <code><strong>dtmc</strong></code>, <code><strong>ctmc</strong></code> and <code><strong>mdp</strong></code>, respectively.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModuleRenaming.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Module Renaming \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModuleRenaming.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=edit.html'>Edit</a> - <a class='wikilink' href='ModuleRenaming@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Module Renaming</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM also supports <em>module renaming</em>, which allows duplication of modules.\nIn <a class='wikilink' href='Example1.html'>Example 1</a>, module <code>M2</code> is identical to module <code>M1</code> so we can in fact replace its entire definition with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span> = <span class=\"prismident\">M1</span> [ <span class=\"prismident\">x</span>=<span class=\"prismident\">y</span>, <span class=\"prismident\">y</span>=<span class=\"prismident\">x</span> ] <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModuleRenaming?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>All of the variables in the module being renamed (in this case, just <code>x</code>) <em>must</em> be renamed to new, unused names. Optionally, it is also possible to rename other aspects of the module definition. In fact, the renaming is done at a textual level, so any identifiers (including <a class='wikilink' href='Synchronisation.html'>action labels</a>, <a class='wikilink' href='Constants.html'>constants</a> and <a class='wikilink' href='Expressions.html'>functions</a>) used in the module definition can be changed in this way.\n</p>\n<p class='vspace'><strong>Note:</strong> Care should be taken when renaming modules that make use of <a class='wikilink' href='FormulasAndLabels.html'>formulas</a>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModuleRenaming.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=edit.html'>Edit</a> - <a class='wikilink' href='ModuleRenaming@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:43 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='selflink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModuleRenaming@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Module Renaming | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModuleRenaming.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=edit.html'>Edit</a> - <a class='wikilink' href='ModuleRenaming@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Module Renaming</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ModuleRenaming@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModuleRenaming.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=edit.html'>Edit</a> - <a class='wikilink' href='ModuleRenaming@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:43 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='selflink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModuleRenaming@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Module Renaming | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModuleRenaming.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=edit.html'>Edit</a> - <a class='wikilink' href='ModuleRenaming@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Module Renaming</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ModuleRenaming@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModuleRenaming.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=edit.html'>Edit</a> - <a class='wikilink' href='ModuleRenaming@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModuleRenaming@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:43 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='selflink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModuleRenaming@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / ModuleRenaming </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Module Renaming</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM also supports <em>module renaming</em>, which allows duplication of modules.\nIn <a class='wikilink' href='Example1.html'>Example 1</a>, module <code>M2</code> is identical to module <code>M1</code> so we can in fact replace its entire definition with:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">M2</span> = <span class=\"prismident\">M1</span> [ <span class=\"prismident\">x</span>=<span class=\"prismident\">y</span>, <span class=\"prismident\">y</span>=<span class=\"prismident\">x</span> ] <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModuleRenaming?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>All of the variables in the module being renamed (in this case, just <code>x</code>) <em>must</em> be renamed to new, unused names. Optionally, it is also possible to rename other aspects of the module definition. In fact, the renaming is done at a textual level, so any identifiers (including <a class='wikilink' href='Synchronisation.html'>action labels</a>, <a class='wikilink' href='Constants.html'>constants</a> and <a class='wikilink' href='Expressions.html'>functions</a>) used in the module definition can be changed in this way.\n</p>\n<p class='vspace'><strong>Note:</strong> Care should be taken when renaming modules that make use of <a class='wikilink' href='FormulasAndLabels.html'>formulas</a>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModulesAndVariables.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Modules And Variables \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModulesAndVariables.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='ModulesAndVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Modules And Variables</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The <a class='wikilink' href='Example1.html'>previous example</a> uses two modules, <code>M1</code> and <code>M2</code>, one representing each process.\nA module is specified as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">name</span> ... <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The definition of a module contains two parts: its <em>variables</em> and its <em>commands</em>.\nThe variables describe the possible states that the module can be in;\nthe <a class='wikilink' href='Commands.html'>commands</a> describe its behaviour, i.e. the way in which the state changes over time.\nCurrently, PRISM supports just a few simple types of variables:\nthey can either be (finite ranges of) integers or Booleans\n(we ignore <a class='wikilink' href='Real-timeModels.html'>clocks</a> for now).\n</p>\n<p class='vspace'>In the example above, each module has one integer variable with range <code>[0..2]</code>.\nA variable declaration looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the initial value of the variable is also specified.\nA Boolean variable is declared as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">false</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It is also possible to omit the initial value of a variable,\nin which case it is assumed to be the lowest value in the range (or <code>false</code> for a Boolean).\nThus, the variable declarations shown below are equivalent to the ones above.\nAs will be described later, it is also possible to specify\n<a class='wikilink' href='MultipleInitialStates.html'>multiple initial states</a> for a model.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>];<br/>\n<span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We also mention that, for a few kinds of model analysis (typically those based on simulation, such as <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a> or <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#fau'>fast adaptive simulation</a>, it is also permissable to use integer variables with unbounded ranges, denoted as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : <span class=\"prismkeyword\">int</span>;<br/>\n<span class=\"prismident\">y</span> : <span class=\"prismkeyword\">int</span> <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">3</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Where the state space of the model remains finite, despite the presence of such unbounded variables, you can use the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>explicit engine</a> to build and analyse the model.\n</p>\n<div class='vspace'></div><h3>Identifiers</h3>\n<p>The names given to modules and variables are referred to as <em>identifiers</em>.\nIdentifiers can be made up of letters, digits and the underscore character, but cannot begin with a digit,\ni.e. they must satisfy the regular expression [A-Za-z_][A-Za-z0-9_]*, and are case-sensitive.\nFurthermore, identifiers cannot be any of the following, which are all reserved keywords in PRISM:\n<code><strong>A</strong></code>,\n<code><strong>bool</strong></code>,\n<code><strong>clock</strong></code>,\n<code><strong>const</strong></code>,\n<code><strong>ctmc</strong></code>,\n<code><strong>C</strong></code>,\n<code><strong>double</strong></code>,\n<code><strong>dtmc</strong></code>,\n<code><strong>E</strong></code>,\n<code><strong>endinit</strong></code>,\n<code><strong>endinvariant</strong></code>,\n<code><strong>endmodule</strong></code>,\n<code><strong>endobservables</strong></code>,\n<code><strong>endrewards</strong></code>,\n<code><strong>endsystem</strong></code>,\n<code><strong>false</strong></code>,\n<code><strong>formula</strong></code>,\n<code><strong>filter</strong></code>,\n<code><strong>func</strong></code>,\n<code><strong>F</strong></code>,\n<code><strong>global</strong></code>,\n<code><strong>G</strong></code>,\n<code><strong>init</strong></code>,\n<code><strong>invariant</strong></code>,\n<code><strong>I</strong></code>,\n<code><strong>int</strong></code>,\n<code><strong>label</strong></code>,\n<code><strong>max</strong></code>,\n<code><strong>mdp</strong></code>,\n<code><strong>min</strong></code>,\n<code><strong>module</strong></code>,\n<code><strong>X</strong></code>,\n<code><strong>nondeterministic</strong></code>,\n<code><strong>observable</strong></code>,\n<code><strong>observables</strong></code>,\n<code><strong>of</strong></code>,\n<code><strong>Pmax</strong></code>,\n<code><strong>Pmin</strong></code>,\n<code><strong>P</strong></code>,\n<code><strong>pomdp</strong></code>,\n<code><strong>popta</strong></code>,\n<code><strong>probabilistic</strong></code>,\n<code><strong>prob</strong></code>,\n<code><strong>pta</strong></code>,\n<code><strong>rate</strong></code>,\n<code><strong>rewards</strong></code>,\n<code><strong>Rmax</strong></code>,\n<code><strong>Rmin</strong></code>,\n<code><strong>R</strong></code>,\n<code><strong>S</strong></code>,\n<code><strong>stochastic</strong></code>,\n<code><strong>system</strong></code>,\n<code><strong>true</strong></code>,\n<code><strong>U</strong></code>,\n<code><strong>W</strong></code>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModulesAndVariables.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='ModulesAndVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='selflink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModulesAndVariables@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Modules And Variables | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModulesAndVariables.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='ModulesAndVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Modules And Variables</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ModulesAndVariables@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModulesAndVariables.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='ModulesAndVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='selflink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModulesAndVariables@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Modules And Variables | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ModulesAndVariables.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='ModulesAndVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Modules And Variables</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ModulesAndVariables@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ModulesAndVariables.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=edit.html'>Edit</a> - <a class='wikilink' href='ModulesAndVariables@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ModulesAndVariables@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:16 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='selflink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ModulesAndVariables@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / ModulesAndVariables </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Modules And Variables</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>The <a class='wikilink' href='Example1.html'>previous example</a> uses two modules, <code>M1</code> and <code>M2</code>, one representing each process.\nA module is specified as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">module</span> <span class=\"prismident\">name</span> ... <span class=\"prismkeyword\">endmodule</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>The definition of a module contains two parts: its <em>variables</em> and its <em>commands</em>.\nThe variables describe the possible states that the module can be in;\nthe <a class='wikilink' href='Commands.html'>commands</a> describe its behaviour, i.e. the way in which the state changes over time.\nCurrently, PRISM supports just a few simple types of variables:\nthey can either be (finite ranges of) integers or Booleans\n(we ignore <a class='wikilink' href='Real-timeModels.html'>clocks</a> for now).\n</p>\n<p class='vspace'>In the example above, each module has one integer variable with range <code>[0..2]</code>.\nA variable declaration looks like:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Notice that the initial value of the variable is also specified.\nA Boolean variable is declared as follows:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock3'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span> <span class=\"prismkeyword\">init</span> <span class=\"prismkeyword\">false</span>; <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=3' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>It is also possible to omit the initial value of a variable,\nin which case it is assumed to be the lowest value in the range (or <code>false</code> for a Boolean).\nThus, the variable declarations shown below are equivalent to the ones above.\nAs will be described later, it is also possible to specify\n<a class='wikilink' href='MultipleInitialStates.html'>multiple initial states</a> for a model.\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock4'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>];<br/>\n<span class=\"prismident\">b</span> : <span class=\"prismkeyword\">bool</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=4' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>We also mention that, for a few kinds of model analysis (typically those based on simulation, such as <a class='wikilink' href='../RunningPRISM/ApproximateModelChecking.html'>approximate model checking</a> or <a class='wikilink' href='../ConfiguringPRISM/SolutionMethodsAndOptions.html#fau'>fast adaptive simulation</a>, it is also permissable to use integer variables with unbounded ranges, denoted as:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock5'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismident\">x</span> : <span class=\"prismkeyword\">int</span>;<br/>\n<span class=\"prismident\">y</span> : <span class=\"prismkeyword\">int</span> <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">3</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ModulesAndVariables?action=sourceblock&amp;num=5' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>Where the state space of the model remains finite, despite the presence of such unbounded variables, you can use the <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html'>explicit engine</a> to build and analyse the model.\n</p>\n<div class='vspace'></div><h3>Identifiers</h3>\n<p>The names given to modules and variables are referred to as <em>identifiers</em>.\nIdentifiers can be made up of letters, digits and the underscore character, but cannot begin with a digit,\ni.e. they must satisfy the regular expression [A-Za-z_][A-Za-z0-9_]*, and are case-sensitive.\nFurthermore, identifiers cannot be any of the following, which are all reserved keywords in PRISM:\n<code><strong>A</strong></code>,\n<code><strong>bool</strong></code>,\n<code><strong>clock</strong></code>,\n<code><strong>const</strong></code>,\n<code><strong>ctmc</strong></code>,\n<code><strong>C</strong></code>,\n<code><strong>double</strong></code>,\n<code><strong>dtmc</strong></code>,\n<code><strong>E</strong></code>,\n<code><strong>endinit</strong></code>,\n<code><strong>endinvariant</strong></code>,\n<code><strong>endmodule</strong></code>,\n<code><strong>endobservables</strong></code>,\n<code><strong>endrewards</strong></code>,\n<code><strong>endsystem</strong></code>,\n<code><strong>false</strong></code>,\n<code><strong>formula</strong></code>,\n<code><strong>filter</strong></code>,\n<code><strong>func</strong></code>,\n<code><strong>F</strong></code>,\n<code><strong>global</strong></code>,\n<code><strong>G</strong></code>,\n<code><strong>init</strong></code>,\n<code><strong>invariant</strong></code>,\n<code><strong>I</strong></code>,\n<code><strong>int</strong></code>,\n<code><strong>label</strong></code>,\n<code><strong>max</strong></code>,\n<code><strong>mdp</strong></code>,\n<code><strong>min</strong></code>,\n<code><strong>module</strong></code>,\n<code><strong>X</strong></code>,\n<code><strong>nondeterministic</strong></code>,\n<code><strong>observable</strong></code>,\n<code><strong>observables</strong></code>,\n<code><strong>of</strong></code>,\n<code><strong>Pmax</strong></code>,\n<code><strong>Pmin</strong></code>,\n<code><strong>P</strong></code>,\n<code><strong>pomdp</strong></code>,\n<code><strong>popta</strong></code>,\n<code><strong>probabilistic</strong></code>,\n<code><strong>prob</strong></code>,\n<code><strong>pta</strong></code>,\n<code><strong>rate</strong></code>,\n<code><strong>rewards</strong></code>,\n<code><strong>Rmax</strong></code>,\n<code><strong>Rmin</strong></code>,\n<code><strong>R</strong></code>,\n<code><strong>S</strong></code>,\n<code><strong>stochastic</strong></code>,\n<code><strong>system</strong></code>,\n<code><strong>true</strong></code>,\n<code><strong>U</strong></code>,\n<code><strong>W</strong></code>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/MultipleInitialStates.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Multiple Initial States \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='MultipleInitialStates.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=edit.html'>Edit</a> - <a class='wikilink' href='MultipleInitialStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Multiple Initial States</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Typically, a <a class='wikilink' href='ModulesAndVariables.html'>variable</a> declaration\nspecifies the initial value for that variable.\nThe <em>initial state</em> for the model is then defined by the initial value for all variables.\nIt is possible, however, to specify that a model has <em>multiple</em> initial states.\nThis is done using the <code><strong>init</strong>...<strong>endinit</strong></code> construct,\nwhich can be placed anywhere in the file except within a module definition,\nand removing any initial values from variable declarations.\nBetween the <code><strong>init</strong></code> and <code><strong>endinit</strong></code> keywords, there should be a\npredicate over all the variables of the model.\nAny state which satisfies this predicate is an initial state.\n</p>\n<p class='vspace'>Consider again <a class='wikilink' href='Example1.html'>Example 1</a>.\nAs it stands, there is a single initial state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>).\nIf we remove the <code><strong>init</strong> 0</code> part of both variable declarations\nand add the following to the end of the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/MultipleInitialStates?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>there will be three initial states: <code>(0,0)</code>, <code>(0,1)</code> and <code>(0,2)</code>.\nSimilarly, we could instead add:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>+<span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/MultipleInitialStates?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>in which case there would be two initial states: <code>(0,1)</code> and <code>(1,0)</code>.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='MultipleInitialStates.html'>View</a> - <a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=edit.html'>Edit</a> - <a class='wikilink' href='MultipleInitialStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 12:45 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='selflink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/MultipleInitialStates@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Multiple Initial States | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='MultipleInitialStates.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=edit.html'>Edit</a> - <a class='wikilink' href='MultipleInitialStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Multiple Initial States</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='MultipleInitialStates@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='MultipleInitialStates.html'>View</a> - <a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=edit.html'>Edit</a> - <a class='wikilink' href='MultipleInitialStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 12:45 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='selflink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/MultipleInitialStates@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Multiple Initial States | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='MultipleInitialStates.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=edit.html'>Edit</a> - <a class='wikilink' href='MultipleInitialStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Multiple Initial States</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='MultipleInitialStates@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='MultipleInitialStates.html'>View</a> - <a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=edit.html'>Edit</a> - <a class='wikilink' href='MultipleInitialStates@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='MultipleInitialStates@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 12:45 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='selflink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/MultipleInitialStates@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / MultipleInitialStates </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Multiple Initial States</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Typically, a <a class='wikilink' href='ModulesAndVariables.html'>variable</a> declaration\nspecifies the initial value for that variable.\nThe <em>initial state</em> for the model is then defined by the initial value for all variables.\nIt is possible, however, to specify that a model has <em>multiple</em> initial states.\nThis is done using the <code><strong>init</strong>...<strong>endinit</strong></code> construct,\nwhich can be placed anywhere in the file except within a module definition,\nand removing any initial values from variable declarations.\nBetween the <code><strong>init</strong></code> and <code><strong>endinit</strong></code> keywords, there should be a\npredicate over all the variables of the model.\nAny state which satisfies this predicate is an initial state.\n</p>\n<p class='vspace'>Consider again <a class='wikilink' href='Example1.html'>Example 1</a>.\nAs it stands, there is a single initial state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>).\nIf we remove the <code><strong>init</strong> 0</code> part of both variable declarations\nand add the following to the end of the file:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/MultipleInitialStates?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>there will be three initial states: <code>(0,0)</code>, <code>(0,1)</code> and <code>(0,2)</code>.\nSimilarly, we could instead add:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">init</span> <span class=\"prismident\">x</span>+<span class=\"prismident\">y</span>=<span class=\"prismnum\">1</span> <span class=\"prismkeyword\">endinit</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/MultipleInitialStates?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>in which case there would be two initial states: <code>(0,1)</code> and <code>(1,0)</code>.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/POMDPs@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / POMD Ps | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='createlinktext' rel='nofollow'\n    href='POMDPs@action=edit.html'>View</a><a rel='nofollow' \n    class='createlink' href='POMDPs@action=edit.html'>?</a> - </span><a rel='nofollow'  class='wikilink' href='POMDPs@action=edit.html'>Edit</a> - <a class='wikilink' href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/POMDPs?action=print'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>POMD Ps</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='POMDPs@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='createlinktext' rel='nofollow'\n    href='POMDPs@action=edit.html'>View</a><a rel='nofollow' \n    class='createlink' href='POMDPs@action=edit.html'>?</a> - <a rel='nofollow'  class='wikilink' href='POMDPs@action=edit.html'>Edit</a> - <a class='wikilink' href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/POMDPs?action=print'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/POMDPs?action=login'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:57 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/PRISMModelFiles.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / PRISM Model Files \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMModelFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>PRISM Model Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Files containing model descriptions written in the PRISM language\ncan contain any amount of white space (spaces, tabs, new lines, etc.),\nall of which is ignored when the file is parsed by the tool.\nComments can also be used included in files in the style of the C programming language,\nby preceding them with the characters <code>//</code>.\nThis is illustrated by the PRISM language examples from earlier in this section.\n</p>\n<p class='vspace'>We recommend that the <code>.prism</code> extension is used for PRISM model files.\nHistorically (when the tool supported fewer types of model),\ndifferent extensions were often used for each model type:\n<code>.nm</code> for MDPs or PTAs, <code>.pm</code> for DTMCs and <code>.sm</code> for CTMCs.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMModelFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:20 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='selflink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/PRISMModelFiles@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / PRISM Model Files | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMModelFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>PRISM Model Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PRISMModelFiles@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMModelFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:20 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='selflink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/PRISMModelFiles@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / PRISM Model Files | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PRISMModelFiles.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>PRISM Model Files</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PRISMModelFiles@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PRISMModelFiles.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=edit.html'>Edit</a> - <a class='wikilink' href='PRISMModelFiles@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PRISMModelFiles@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 18, 2021, at 11:20 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='selflink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/PRISMModelFiles@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / PRISMModelFiles </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>PRISM Model Files</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Files containing model descriptions written in the PRISM language\ncan contain any amount of white space (spaces, tabs, new lines, etc.),\nall of which is ignored when the file is parsed by the tool.\nComments can also be used included in files in the style of the C programming language,\nby preceding them with the characters <code>//</code>.\nThis is illustrated by the PRISM language examples from earlier in this section.\n</p>\n<p class='vspace'>We recommend that the <code>.prism</code> extension is used for PRISM model files.\nHistorically (when the tool supported fewer types of model),\ndifferent extensions were often used for each model type:\n<code>.nm</code> for MDPs or PTAs, <code>.pm</code> for DTMCs and <code>.sm</code> for CTMCs.\n</p>\n<div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ParallelComposition.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Parallel Composition \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ParallelComposition.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ParallelComposition@action=edit.html'>Edit</a> - <a class='wikilink' href='ParallelComposition@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Parallel Composition</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>The probabilistic model corresponding to a PRISM language description is constructed as the <em>parallel composition</em> of its modules. In every state of the model, there is a set of commands (belonging to any of the modules) which are enabled, i.e. whose guards are satisfied in that state. The choice between which command is performed (i.e. the <em>scheduling</em>) depends on the model type.\n</p>\n<p class='vspace'>For an MDP, as in <a class='wikilink' href='Example1.html'>Example 1</a>, the choice is <em>nondeterministic</em>. By way of example, consider state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>). There are two commands enabled, one from each module:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ParallelComposition?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ParallelComposition?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In state <code>(0,0)</code> of the MDP, there would be a nondeterministic choice between these two probability distributions:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.2:(1,0)</code> (module <code>M1</code> moves)\n</li><li><code>0.8:(0,0) + 0.2:(0,1)</code> (module <code>M2</code> moves)\n</li></ul><p class='vspace'>For a DTMC, the choice is <em>probabilistic</em>: each enabled command is selected with equal probability.\nIf <a class='wikilink' href='Example1.html'>Example 1</a> was a DTMC, then in state <code>(0,0)</code> of the model\nthe following probability distribution would result:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.1:(1,0) + 0.1:(0,1)</code>\n</li></ul><p class='vspace'>For a <a class='wikilink' href='CTMCs.html'>CTMC</a>, as will be discussed shortly,\nthe choice is modelled as a \"race\" between transitions.\n</p>\n<p class='vspace'>See the later sections on \"<a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\" and \"<a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\" for other topics related to parallel composition.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ParallelComposition.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ParallelComposition@action=edit.html'>Edit</a> - <a class='wikilink' href='ParallelComposition@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ParallelComposition@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:12 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='selflink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ParallelComposition@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Parallel Composition | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ParallelComposition.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ParallelComposition@action=edit.html'>Edit</a> - <a class='wikilink' href='ParallelComposition@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Parallel Composition</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ParallelComposition@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ParallelComposition.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ParallelComposition@action=edit.html'>Edit</a> - <a class='wikilink' href='ParallelComposition@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ParallelComposition@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:12 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='selflink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ParallelComposition@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Parallel Composition | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ParallelComposition.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ParallelComposition@action=edit.html'>Edit</a> - <a class='wikilink' href='ParallelComposition@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Parallel Composition</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ParallelComposition@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ParallelComposition.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ParallelComposition@action=edit.html'>Edit</a> - <a class='wikilink' href='ParallelComposition@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ParallelComposition@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:12 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='selflink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ParallelComposition@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / ParallelComposition </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Parallel Composition</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>The probabilistic model corresponding to a PRISM language description is constructed as the <em>parallel composition</em> of its modules. In every state of the model, there is a set of commands (belonging to any of the modules) which are enabled, i.e. whose guards are satisfied in that state. The choice between which command is performed (i.e. the <em>scheduling</em>) depends on the model type.\n</p>\n<p class='vspace'>For an MDP, as in <a class='wikilink' href='Example1.html'>Example 1</a>, the choice is <em>nondeterministic</em>. By way of example, consider state <code>(0,0)</code> (i.e.  <code>x=0</code> and <code>y=0</code>). There are two commands enabled, one from each module:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ParallelComposition?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">y</span>=<span class=\"prismnum\">0</span> -&gt; <span class=\"prismnum\">0.8</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.2</span>:(<span class=\"prismident\">y</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/ParallelComposition?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>In state <code>(0,0)</code> of the MDP, there would be a nondeterministic choice between these two probability distributions:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.2:(1,0)</code> (module <code>M1</code> moves)\n</li><li><code>0.8:(0,0) + 0.2:(0,1)</code> (module <code>M2</code> moves)\n</li></ul><p class='vspace'>For a DTMC, the choice is <em>probabilistic</em>: each enabled command is selected with equal probability.\nIf <a class='wikilink' href='Example1.html'>Example 1</a> was a DTMC, then in state <code>(0,0)</code> of the model\nthe following probability distribution would result:\n</p>\n<div class='vspace'></div><ul><li><code>0.8:(0,0) + 0.1:(1,0) + 0.1:(0,1)</code>\n</li></ul><p class='vspace'>For a <a class='wikilink' href='CTMCs.html'>CTMC</a>, as will be discussed shortly,\nthe choice is modelled as a \"race\" between transitions.\n</p>\n<p class='vspace'>See the later sections on \"<a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\" and \"<a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\" for other topics related to parallel composition.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/PartiallyObservableModels.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Partially Observable Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PartiallyObservableModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Partially Observable Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM supports analysis of <em>partially observable</em> probabilistic models,\nmost notably partially observable Markov decision processes (POMDPs),\nbut also partially observable probabilistic timed automata (POPTAs).\nPOMDPs are a variant of MDPs in which the strategy/policy\nwhich resolves nondeterministic choices in the model is unable to\nsee the precise state of the model, but instead just <em>observations</em> of it.\nFor background material on POMDPs and POPTAs, see for example [<a class='wikilink' href='../Main/References.html#NPZ17'>NPZ17</a>].\nYou can also find several example models included in the PRISM distribution.\nLook in the <code>prism-examples/pomdps</code> and <code>prism-examples/poptas</code> directories.\n</p>\n<p class='vspace'>PRISM currently supports state-based observations:\nthis means that, upon entering a new POMDP state,\nthe observation is determined by that state.\nIn the same way that a model state comprises the values or one or more variables,\nan observation comprises one or more <em>observables</em>.\nThere are several way to define these observables.\nThe simplest is to specify a subset of the model's variables\nthat are designated as being observable. The rest are unobservable.\n</p>\n<p class='vspace'>For example, in a POMDP with 3 variables, <code>s</code>, <code>l</code> and <code>h</code>, the following:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">observables</span> <span class=\"prismident\">s</span>, <span class=\"prismident\">l</span> <span class=\"prismkeyword\">endobservables</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/PartiallyObservableModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>specifies that <code>s</code> and <code>l</code> are observable and <code>h</code> is not.\n</p>\n<p class='vspace'>Alternatively, observables can be specified as arbitrary expressions over variables.\nFor example, assuming the same variables <code>s</code>, <code>l</code> and <code>h</code>, this specification:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">s</span>\" = <span class=\"prismident\">s</span>;<br/>\n<span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">pos</span>\" = <span class=\"prismident\">l</span>&gt;<span class=\"prismnum\">0</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/PartiallyObservableModels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>defines 2 observables. The first is, as above, the variable <code>s</code>.\nThe second, named <code>\"pos\"</code>, determines if variable <code>l</code> is positive.\nOther than this, the values of <code>l</code> and <code>h</code> are unobservable.\nThe named observables can then be used in properties\nin the same way that <a class='wikilink' href='FormulasAndLabels.html'>labels</a> can.\n</p>\n<p class='vspace'>The above two styles of definition can also be mixed\nto specify a combined set of observables.\n</p>\n<p class='vspace'>POPTAs (partially observable PTAs) combine the features of both PTAs and POMDPs.\nThey are are currently analysed using the digital clocks engine,\nso inherit the <a class='wikilink' href='Real-timeModels.html'>restrictions for that engine</a>.\nFurthermore, for a POPTA, all clock variables must be observable.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PartiallyObservableModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:26 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='selflink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/PartiallyObservableModels@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Partially Observable Models | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PartiallyObservableModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Partially Observable Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PartiallyObservableModels@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PartiallyObservableModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:26 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='selflink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/PartiallyObservableModels@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Partially Observable Models | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='PartiallyObservableModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Partially Observable Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='PartiallyObservableModels@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='PartiallyObservableModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=edit.html'>Edit</a> - <a class='wikilink' href='PartiallyObservableModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='PartiallyObservableModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on June 16, 2023, at 11:26 am</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='selflink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/PartiallyObservableModels@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / PartiallyObservableModels </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Partially Observable Models</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM supports analysis of <em>partially observable</em> probabilistic models,\nmost notably partially observable Markov decision processes (POMDPs),\nbut also partially observable probabilistic timed automata (POPTAs).\nPOMDPs are a variant of MDPs in which the strategy/policy\nwhich resolves nondeterministic choices in the model is unable to\nsee the precise state of the model, but instead just <em>observations</em> of it.\nFor background material on POMDPs and POPTAs, see for example [<a class='wikilink' href='../Main/References.html#NPZ17'>NPZ17</a>].\nYou can also find several example models included in the PRISM distribution.\nLook in the <code>prism-examples/pomdps</code> and <code>prism-examples/poptas</code> directories.\n</p>\n<p class='vspace'>PRISM currently supports state-based observations:\nthis means that, upon entering a new POMDP state,\nthe observation is determined by that state.\nIn the same way that a model state comprises the values or one or more variables,\nan observation comprises one or more <em>observables</em>.\nThere are several way to define these observables.\nThe simplest is to specify a subset of the model's variables\nthat are designated as being observable. The rest are unobservable.\n</p>\n<p class='vspace'>For example, in a POMDP with 3 variables, <code>s</code>, <code>l</code> and <code>h</code>, the following:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> <span class=\"prismkeyword\">observables</span> <span class=\"prismident\">s</span>, <span class=\"prismident\">l</span> <span class=\"prismkeyword\">endobservables</span> <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/PartiallyObservableModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>specifies that <code>s</code> and <code>l</code> are observable and <code>h</code> is not.\n</p>\n<p class='vspace'>Alternatively, observables can be specified as arbitrary expressions over variables.\nFor example, assuming the same variables <code>s</code>, <code>l</code> and <code>h</code>, this specification:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">s</span>\" = <span class=\"prismident\">s</span>;<br/>\n<span class=\"prismkeyword\">observable</span> \"<span class=\"prismident\">pos</span>\" = <span class=\"prismident\">l</span>&gt;<span class=\"prismnum\">0</span>;<br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/PartiallyObservableModels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>defines 2 observables. The first is, as above, the variable <code>s</code>.\nThe second, named <code>\"pos\"</code>, determines if variable <code>l</code> is positive.\nOther than this, the values of <code>l</code> and <code>h</code> are unobservable.\nThe named observables can then be used in properties\nin the same way that <a class='wikilink' href='FormulasAndLabels.html'>labels</a> can.\n</p>\n<p class='vspace'>The above two styles of definition can also be mixed\nto specify a combined set of observables.\n</p>\n<p class='vspace'>POPTAs (partially observable PTAs) combine the features of both PTAs and POMDPs.\nThey are are currently analysed using the digital clocks engine,\nso inherit the <a class='wikilink' href='Real-timeModels.html'>restrictions for that engine</a>.\nFurthermore, for a POPTA, all clock variables must be observable.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ProcessAlgebraOperators.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Process Algebra Operators \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ProcessAlgebraOperators.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=edit.html'>Edit</a> - <a class='wikilink' href='ProcessAlgebraOperators@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Process Algebra Operators</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>To make the concept of synchronisation described above more powerful,\nPRISM allows you to define precisely the way in which the set of modules are composed in parallel.\nThis is specified using the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct,\nplaced at the end of the model description, which should contain a process-algebraic expression.\nThis expression should feature each module exactly once, and can use the following (CSP-based) operators:\n</p>\n<div class='vspace'></div><ul><li><code>M1 || M2</code> : alphabetised parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising on only actions appearing in both <code>M1</code> and <code>M2</code>)\n<div class='vspace'></div></li><li><code>M1 ||| M2</code> : asynchronous parallel composition of <code>M1</code> and <code>M2</code> (fully interleaved, no synchronisation)\n<div class='vspace'></div></li><li><code>M1 |[a,b,...]| M2</code> : restricted parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising only on actions from the set {<code>a</code>, <code>b</code>,...})\n<div class='vspace'></div></li><li><code>M / {a,b,...</code>} : hiding of actions {<code>a</code>, <code>b</code>, ...} in module <code>M</code>\n<div class='vspace'></div></li><li><code>M {a&lt;-b,c&lt;-d,...</code>} : renaming of actions <code>a</code> to <code>b</code>, <code>c</code> to <code>d</code>, etc. in module <code>M</code>.\n</li></ul><p class='vspace'>The first two types of parallel composition (<code>||</code> and <code>|||</code>) are associative and can be applied to more than two modules at once.\nWhen evaluating the expression, the hiding and renaming operators bind more tightly than the three parallel composition operators.\nNo other rules of precedence are defined and parentheses should be used to specify the order in which modules are composed.\n</p>\n<p class='vspace'>Some examples of expressions which could be included in the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct are as follows:\n</p>\n<div class='vspace'></div><ul><li><code>(station1 ||| station2 ||| station3) |[serve]| server</code>\n</li><li><code>((P1 |[a]| P2) / {a}) || Q</code>\n</li><li><code>((P1 |[a]| P2) {a&lt;-b}) |[b]| Q</code>\n</li></ul><p class='vspace'>When no parallel composition is specified by the user,\nPRISM implicitly assumes an expression of the form <code>M1 || M2 || ...</code> containing all of the modules in the model.\nFor a more formal definition of the process algebra operators described above, check the semantics of the PRISM language, available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site.\n</p>\n<p class='vspace'>PRISM is also able to <a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>import</a> model descriptions written in (a subset of) the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='../Main/References.html#Hil96'>Hil96</a>].\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ProcessAlgebraOperators.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=edit.html'>Edit</a> - <a class='wikilink' href='ProcessAlgebraOperators@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 17, 2009, at 02:01 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='selflink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ProcessAlgebraOperators@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Process Algebra Operators | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ProcessAlgebraOperators.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=edit.html'>Edit</a> - <a class='wikilink' href='ProcessAlgebraOperators@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Process Algebra Operators</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ProcessAlgebraOperators@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ProcessAlgebraOperators.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=edit.html'>Edit</a> - <a class='wikilink' href='ProcessAlgebraOperators@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 17, 2009, at 02:01 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='selflink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ProcessAlgebraOperators@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Process Algebra Operators | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='ProcessAlgebraOperators.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=edit.html'>Edit</a> - <a class='wikilink' href='ProcessAlgebraOperators@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Process Algebra Operators</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='ProcessAlgebraOperators@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='ProcessAlgebraOperators.html'>View</a> - <a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=edit.html'>Edit</a> - <a class='wikilink' href='ProcessAlgebraOperators@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='ProcessAlgebraOperators@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on November 17, 2009, at 02:01 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='selflink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/ProcessAlgebraOperators@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / ProcessAlgebraOperators </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Process Algebra Operators</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>To make the concept of synchronisation described above more powerful,\nPRISM allows you to define precisely the way in which the set of modules are composed in parallel.\nThis is specified using the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct,\nplaced at the end of the model description, which should contain a process-algebraic expression.\nThis expression should feature each module exactly once, and can use the following (CSP-based) operators:\n</p>\n<div class='vspace'></div><ul><li><code>M1 || M2</code> : alphabetised parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising on only actions appearing in both <code>M1</code> and <code>M2</code>)\n<div class='vspace'></div></li><li><code>M1 ||| M2</code> : asynchronous parallel composition of <code>M1</code> and <code>M2</code> (fully interleaved, no synchronisation)\n<div class='vspace'></div></li><li><code>M1 |[a,b,...]| M2</code> : restricted parallel composition of modules <code>M1</code> and <code>M2</code> (synchronising only on actions from the set {<code>a</code>, <code>b</code>,...})\n<div class='vspace'></div></li><li><code>M / {a,b,...</code>} : hiding of actions {<code>a</code>, <code>b</code>, ...} in module <code>M</code>\n<div class='vspace'></div></li><li><code>M {a&lt;-b,c&lt;-d,...</code>} : renaming of actions <code>a</code> to <code>b</code>, <code>c</code> to <code>d</code>, etc. in module <code>M</code>.\n</li></ul><p class='vspace'>The first two types of parallel composition (<code>||</code> and <code>|||</code>) are associative and can be applied to more than two modules at once.\nWhen evaluating the expression, the hiding and renaming operators bind more tightly than the three parallel composition operators.\nNo other rules of precedence are defined and parentheses should be used to specify the order in which modules are composed.\n</p>\n<p class='vspace'>Some examples of expressions which could be included in the <code><strong>system</strong> ... <strong>endsystem</strong></code> construct are as follows:\n</p>\n<div class='vspace'></div><ul><li><code>(station1 ||| station2 ||| station3) |[serve]| server</code>\n</li><li><code>((P1 |[a]| P2) / {a}) || Q</code>\n</li><li><code>((P1 |[a]| P2) {a&lt;-b}) |[b]| Q</code>\n</li></ul><p class='vspace'>When no parallel composition is specified by the user,\nPRISM implicitly assumes an expression of the form <code>M1 || M2 || ...</code> containing all of the modules in the model.\nFor a more formal definition of the process algebra operators described above, check the semantics of the PRISM language, available from the \"<a class='urllink' href='http://www.prismmodelchecker.org/doc/'>Documentation</a>\" section of the PRISM web site.\n</p>\n<p class='vspace'>PRISM is also able to <a class='wikilink' href='../RunningPRISM/SupportForPEPAModels.html'>import</a> model descriptions written in (a subset of) the stochastic process algebra <a class='urllink' href='http://www.dcs.ed.ac.uk/pepa/'>PEPA</a> [<a class='wikilink' href='../Main/References.html#Hil96'>Hil96</a>].\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Real-timeModels.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Real-time Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Real-timeModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Real-time Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p class='vspace'>So far in this section, we have mainly focused on three types of models: DTMCs, MDPs and CTMCs,\nin which all the variables making up their state are finite.\nPRISM also supports <em>real-time</em> models, in particular,\n<em>probabilistic timed automata</em> (PTAs), which extend MDPs with the ability to model real-time behaviour.\nThis is done in the style of <em>timed automata</em> [<a class='wikilink' href='../Main/References.html#AD94'>AD94</a>], by adding <em>clocks</em>,\nreal-valued variables which increase with time and can be reset. For background material on PTAs, see for example [<a class='wikilink' href='../Main/References.html#NPS13'>NPS13</a>].\nYou can also find several example PTA models included in the PRISM distribution. Look in the <code>prism-examples/ptas</code> directory.\n</p>\n<p class='vspace'>Before describing how PTA features are incorporated into the PRISM modelling language, we give a simple example. Here is a small PTA:\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/pta.png' alt='' /></div>\n<p class='vspace'>and here is a corresponding PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">pta</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : <span class=\"prismkeyword\">clock</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">invariant</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">2</span>) &amp;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">3</span>)<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">endinvariant</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">send</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismnum\">0.9</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">retry</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.95</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.05</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Real-timeModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For modelling PTAs in PRISM, there is a new datatype, <strong><code>clock</code></strong>, used for variables that are clocks. Other types of PRISM variables can be defined in the usual way. In the example above, we use just a single integer variable <code>s</code> to represent the locations of the PTAs.\n</p>\n<p class='vspace'>In a PTA, transitions can include a <em>guard</em>, which constrains when it can occur based on the current value of clocks, and <em>resets</em>, which specify that a clock's values should be set to a new (integer) value. These are both specified in PRISM commands in the usual way: see, for example, the inclusion of <code>x&gt;=1</code> in the guard for the <code>send</code>-labelled command and the updates of the form <code>(x'=0)</code> which reset the clock <code>x</code> to 0.\n</p>\n<p class='vspace'>The other new addition is an <code>invariant</code> construct, which is used to specify an expression describing the clock <em>invariants</em> for each PRISM module. These impose restrictions on the allowable values of clock variables, depending on the values of the other non-clock variables. The <code>invariant</code> construct should appear between the variable declarations and the commands of the module. Often, clock invariants are described separately for each PTA location; hence, the invariant will often take the form of a conjunction of implications, as in the example model above, but more general expressions are also permitted. In the example, the clock <code>x</code> must satisfy <code>x&lt;=2</code> or <code>x&lt;=3</code> when local variables <code>s</code> is 0 or 2, respectively. If <code>s</code> is 1, there is no restriction (since the invariant is effectively <code>true</code> in this case).\n</p>\n<p class='vspace'>Expressions that include reference to clocks, whether in guards or invariants, must satisfy certain conditions to facilitate model checking. In particular, references to clocks must appear as conjunctions of <em>simple clock constraints</em>, i.e. conjunctions of expressions of the form <code>x~c</code> or <code>x~y</code> where <code>x</code> and <code>y</code> are clocks, <code>c</code> is an integer-valued expression and <code>~</code> is one of <code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code>, <code>=</code>).\n</p>\n<p class='vspace'>There are also some additional restrictions imposed on PTA models that are dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is in use.\n</p>\n<p class='vspace'>For the <strong>stochastic games</strong> and <strong>backwards reachability</strong> engines:\n</p>\n<div class='vspace'></div><ul><li>The model must also have a single initial state (i.e. the <code>init...endinit</code> construct is not permitted).\n</li></ul><p class='vspace'>For the <strong>digital clocks</strong> engine:\n</p>\n<div class='vspace'></div><ul><li>Clock constraints cannot use strict comparison operators, e.g. <code>x&lt;=5</code> is allowed, but <code>x&lt;5</code> is not.\n<div class='vspace'></div></li><li>Diagonal clock constraints are not allowed, i.e. those containing references to two clocks, such as <code>x&lt;=y</code>.\n</li></ul><p class='vspace'>Finally, PRISM makes several assumptions about PTAs, regardless of the engine used.\n</p>\n<div class='vspace'></div><ul><li>Firstly PTAs should not exhibit <em>timelocks</em>, i.e. the possibility of reaching a state where no transitions are possible and time cannot elapse beyond a certain point (due to invariant conditions). PRISM checks for timelocks and reports an error if one is found.\n<div class='vspace'></div></li><li>Secondly, PTAs should be <em>well-formed</em> and <em>non-zeno</em> (see e.g. [<a class='wikilink' href='../Main/References.html#KNSW07'>KNSW07</a>] for details). Currently, PRISM does not check automatically that these assumptions are satisfied.\n</li></ul><div class='vspace'></div>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Real-timeModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 10, 2023, at 07:27 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='selflink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Real-timeModels@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Real-time Models | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Real-timeModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Real-time Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Real-timeModels@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Real-timeModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 10, 2023, at 07:27 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='selflink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Real-timeModels@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Real-time Models | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Real-timeModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Real-time Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Real-timeModels@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Real-timeModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=edit.html'>Edit</a> - <a class='wikilink' href='Real-timeModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Real-timeModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on March 10, 2023, at 07:27 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='selflink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Real-timeModels@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Real-time Models </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Real-time Models</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p class='vspace'>So far in this section, we have mainly focused on three types of models: DTMCs, MDPs and CTMCs,\nin which all the variables making up their state are finite.\nPRISM also supports <em>real-time</em> models, in particular,\n<em>probabilistic timed automata</em> (PTAs), which extend MDPs with the ability to model real-time behaviour.\nThis is done in the style of <em>timed automata</em> [<a class='wikilink' href='../Main/References.html#AD94'>AD94</a>], by adding <em>clocks</em>,\nreal-valued variables which increase with time and can be reset. For background material on PTAs, see for example [<a class='wikilink' href='../Main/References.html#NPS13'>NPS13</a>].\nYou can also find several example PTA models included in the PRISM distribution. Look in the <code>prism-examples/ptas</code> directory.\n</p>\n<p class='vspace'>Before describing how PTA features are incorporated into the PRISM modelling language, we give a simple example. Here is a small PTA:\n</p>\n<div class='vspace'></div><div class='img imgonly'><img src='../uploads/pta.png' alt='' /></div>\n<p class='vspace'>and here is a corresponding PRISM model:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"><span class=\"prismkeyword\">pta</span><br/>\n<br/>\n<span class=\"prismkeyword\">module</span> <span class=\"prismident\">M</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">s</span> : [<span class=\"prismnum\">0</span>..<span class=\"prismnum\">2</span>] <span class=\"prismkeyword\">init</span> <span class=\"prismnum\">0</span>;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismident\">x</span> : <span class=\"prismkeyword\">clock</span>;<br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">invariant</span><br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">2</span>) &amp;<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;(<span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> =&gt; <span class=\"prismident\">x</span>&lt;=<span class=\"prismnum\">3</span>)<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;<span class=\"prismkeyword\">endinvariant</span><br/>\n<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">send</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">0</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">1</span> -&gt; <span class=\"prismnum\">0.9</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + <span class=\"prismnum\">0.1</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n&nbsp;&nbsp;&nbsp;&nbsp;[<span class=\"prismident\">retry</span>] <span class=\"prismident\">s</span>=<span class=\"prismnum\">2</span> &amp; <span class=\"prismident\">x</span>&gt;=<span class=\"prismnum\">2</span> -&gt; <span class=\"prismnum\">0.95</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">1</span>) + <span class=\"prismnum\">0.05</span>:(<span class=\"prismident\">s</span>'=<span class=\"prismnum\">2</span>)&amp;(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>);<br/>\n<br/>\n<span class=\"prismkeyword\">endmodule</span><br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Real-timeModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>For modelling PTAs in PRISM, there is a new datatype, <strong><code>clock</code></strong>, used for variables that are clocks. Other types of PRISM variables can be defined in the usual way. In the example above, we use just a single integer variable <code>s</code> to represent the locations of the PTAs.\n</p>\n<p class='vspace'>In a PTA, transitions can include a <em>guard</em>, which constrains when it can occur based on the current value of clocks, and <em>resets</em>, which specify that a clock's values should be set to a new (integer) value. These are both specified in PRISM commands in the usual way: see, for example, the inclusion of <code>x&gt;=1</code> in the guard for the <code>send</code>-labelled command and the updates of the form <code>(x'=0)</code> which reset the clock <code>x</code> to 0.\n</p>\n<p class='vspace'>The other new addition is an <code>invariant</code> construct, which is used to specify an expression describing the clock <em>invariants</em> for each PRISM module. These impose restrictions on the allowable values of clock variables, depending on the values of the other non-clock variables. The <code>invariant</code> construct should appear between the variable declarations and the commands of the module. Often, clock invariants are described separately for each PTA location; hence, the invariant will often take the form of a conjunction of implications, as in the example model above, but more general expressions are also permitted. In the example, the clock <code>x</code> must satisfy <code>x&lt;=2</code> or <code>x&lt;=3</code> when local variables <code>s</code> is 0 or 2, respectively. If <code>s</code> is 1, there is no restriction (since the invariant is effectively <code>true</code> in this case).\n</p>\n<p class='vspace'>Expressions that include reference to clocks, whether in guards or invariants, must satisfy certain conditions to facilitate model checking. In particular, references to clocks must appear as conjunctions of <em>simple clock constraints</em>, i.e. conjunctions of expressions of the form <code>x~c</code> or <code>x~y</code> where <code>x</code> and <code>y</code> are clocks, <code>c</code> is an integer-valued expression and <code>~</code> is one of <code>&lt;</code>, <code>&lt;=</code>, <code>&gt;=</code>, <code>&gt;</code>, <code>=</code>).\n</p>\n<p class='vspace'>There are also some additional restrictions imposed on PTA models that are dependent on which of the PTA model checking <a class='wikilink' href='../ConfiguringPRISM/ComputationEngines.html#pta'>engines</a> is in use.\n</p>\n<p class='vspace'>For the <strong>stochastic games</strong> and <strong>backwards reachability</strong> engines:\n</p>\n<div class='vspace'></div><ul><li>The model must also have a single initial state (i.e. the <code>init...endinit</code> construct is not permitted).\n</li></ul><p class='vspace'>For the <strong>digital clocks</strong> engine:\n</p>\n<div class='vspace'></div><ul><li>Clock constraints cannot use strict comparison operators, e.g. <code>x&lt;=5</code> is allowed, but <code>x&lt;5</code> is not.\n<div class='vspace'></div></li><li>Diagonal clock constraints are not allowed, i.e. those containing references to two clocks, such as <code>x&lt;=y</code>.\n</li></ul><p class='vspace'>Finally, PRISM makes several assumptions about PTAs, regardless of the engine used.\n</p>\n<div class='vspace'></div><ul><li>Firstly PTAs should not exhibit <em>timelocks</em>, i.e. the possibility of reaching a state where no transitions are possible and time cannot elapse beyond a certain point (due to invariant conditions). PRISM checks for timelocks and reports an error if one is found.\n<div class='vspace'></div></li><li>Secondly, PTAs should be <em>well-formed</em> and <em>non-zeno</em> (see e.g. [<a class='wikilink' href='../Main/References.html#KNSW07'>KNSW07</a>] for details). Currently, PRISM does not check automatically that these assumptions are satisfied.\n</li></ul><div class='vspace'></div>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Synchronisation.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Synchronisation \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Synchronisation.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Synchronisation@action=edit.html'>Edit</a> - <a class='wikilink' href='Synchronisation@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Synchronisation</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Another feature of PRISM introduced in <a class='wikilink' href='Example2.html'>Example 2</a> is <em>synchronisation</em>.\nIn the style of many process algebras, we allow commands to be labelled with <em>actions</em>.\nThese are placed inside the square brackets which mark the start of the command,\nfor example <code>serve</code> in this command from <a class='wikilink' href='Example2.html'>Example 2</a>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Synchronisation?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These actions can be used to force two or more modules to make transitions simultaneously\n(i.e. to <em>synchronise</em>).\nFor example, in state <code>(3,0)</code> (i.e.  <code>q=3</code> and <code>s=0</code>),\nthe composed model can move to state <code>(2,1)</code>,\nsynchronising over the <code>serve</code> action.\nThe rate of this transition is equal to the product of the two individual rates\n(in this case, <code>lambda * 1 = lambda</code>).\nThe product of two rates does not always meaningfully represent the rate of a synchronised transition.\nA common technique, as seen here, is to make one action <em>passive</em>, with rate 1 and one action <em>active</em>,\nwhich actually defines the rate for the synchronised transition.\nBy default, all modules are combined using the standard CSP parallel composition\n(i.e. modules synchronise over all their common actions).\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Synchronisation.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Synchronisation@action=edit.html'>Edit</a> - <a class='wikilink' href='Synchronisation@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Synchronisation@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:39 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='selflink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Synchronisation@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Synchronisation | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Synchronisation.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Synchronisation@action=edit.html'>Edit</a> - <a class='wikilink' href='Synchronisation@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Synchronisation</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Synchronisation@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Synchronisation.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Synchronisation@action=edit.html'>Edit</a> - <a class='wikilink' href='Synchronisation@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Synchronisation@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:39 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='selflink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Synchronisation@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Synchronisation | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Synchronisation.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Synchronisation@action=edit.html'>Edit</a> - <a class='wikilink' href='Synchronisation@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Synchronisation</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='Synchronisation@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Synchronisation.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Synchronisation@action=edit.html'>Edit</a> - <a class='wikilink' href='Synchronisation@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Synchronisation@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on December 03, 2010, at 01:39 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='selflink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='wikilink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/Synchronisation@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / Synchronisation </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Synchronisation</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>Another feature of PRISM introduced in <a class='wikilink' href='Example2.html'>Example 2</a> is <em>synchronisation</em>.\nIn the style of many process algebras, we allow commands to be labelled with <em>actions</em>.\nThese are placed inside the square brackets which mark the start of the command,\nfor example <code>serve</code> in this command from <a class='wikilink' href='Example2.html'>Example 2</a>:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [<span class=\"prismident\">serve</span>] <span class=\"prismident\">q</span>&gt;<span class=\"prismnum\">0</span> -&gt; <span class=\"prismident\">lambda</span>:(<span class=\"prismident\">q</span>'=<span class=\"prismident\">q</span>-<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/Synchronisation?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>These actions can be used to force two or more modules to make transitions simultaneously\n(i.e. to <em>synchronise</em>).\nFor example, in state <code>(3,0)</code> (i.e.  <code>q=3</code> and <code>s=0</code>),\nthe composed model can move to state <code>(2,1)</code>,\nsynchronising over the <code>serve</code> action.\nThe rate of this transition is equal to the product of the two individual rates\n(in this case, <code>lambda * 1 = lambda</code>).\nThe product of two rates does not always meaningfully represent the rate of a synchronised transition.\nA common technique, as seen here, is to make one action <em>passive</em>, with rate 1 and one action <em>active</em>,\nwhich actually defines the rate for the synchronised transition.\nBy default, all modules are combined using the standard CSP parallel composition\n(i.e. modules synchronise over all their common actions).\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/UncertainModels.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Uncertain Models \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='UncertainModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Uncertain Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM has support for <em>uncertain</em> models, in which there is epistemic uncertainty regarding some quantitative aspects of the probabilistic models being verified. In particular, it currently supports <em>interval MDPs</em> (IMDPs) and <em>interval DTMCs</em> (IDTMCs), which are MDPs or DTMCs in which transition probabilities can be specified as intervals, indicating that the exact probability is not precisely known. This can be useful, for example, when the transition probabilities have been estimated from data.\n</p>\n<p class='vspace'>Currently, this is achieved by simply replacing the probabilities attached to updates in commands with intervals, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismnum\">0.8</span>,<span class=\"prismnum\">0.9</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.1</span>,<span class=\"prismnum\">0.2</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/UncertainModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As usual, the probability thresholds can be expressions involving state variables or constants, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismident\">p</span>,<span class=\"prismident\">p</span>+<span class=\"prismnum\">0.1</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.9</span>-<span class=\"prismident\">p</span>,<span class=\"prismnum\">1</span>-<span class=\"prismident\">p</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/UncertainModels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When two commands in different modules <a class='wikilink' href='Synchronisation.html'>synchronise</a> and specify the probabilities for updates to variables as intervals, these are considered to be independent, i.e., the probability of each combined transition is taken to be the product of the two component intervals.\n</p>\n<p class='vspace'>See the <a class='wikilink' href='../PropertySpecification/UncertainModels.html'>property specification</a> section for details of how these models are analysed.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='UncertainModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 11, 2023, at 04:58 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='selflink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/UncertainModels@action=edit.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Uncertain Models | Edit\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n<script type='text/javascript'\n  src='http://www.prismmodelchecker.org/manual/pub/guiedit/guiedit.js'></script>\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='UncertainModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Uncertain Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='UncertainModels@action=edit.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='UncertainModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 11, 2023, at 04:58 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='selflink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/UncertainModels@action=login.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | The PRISM Language / Uncertain Models | Login\n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"../pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"../index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"../FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='UncertainModels.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Uncertain Models</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p><strong>Password required</strong>\n</p>\n<form name='authform' action='UncertainModels@action=login.html' method='post'>\n<p>Password: <input type='password' name='authpw' class='inputbox' autofocus='autofocus' />\n<input type='submit' value='OK' class='inputbutton' />\n</p></form>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='UncertainModels.html'>View</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=edit.html'>Edit</a> - <a class='wikilink' href='UncertainModels@action=print.html'>Print</a> - <a class='wikilink' href='../Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='UncertainModels@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on August 11, 2023, at 04:58 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='wikilink' href='../Main/Main.html'>PRISM Manual</a></h3>\n<p><strong><a class='wikilink' href='Main.html'>The PRISM Language</a></strong>\n</p><ul><li><a class='wikilink' href='Main.html'>Introduction</a>\n</li><li><a class='wikilink' href='Example1.html'>Example 1</a>\n</li><li><a class='wikilink' href='ModelType.html'>Model Type</a>\n</li><li><a class='wikilink' href='ModulesAndVariables.html'>Modules And Variables</a>\n</li><li><a class='wikilink' href='Commands.html'>Commands</a>\n</li><li><a class='wikilink' href='ParallelComposition.html'>Parallel Composition</a>\n</li><li><a class='wikilink' href='LocalNondeterminism.html'>Local Nondeterminism</a>\n</li><li><a class='wikilink' href='CTMCs.html'>CTMCs</a>\n</li><li><a class='wikilink' href='Example2.html'>Example 2</a>\n</li><li><a class='wikilink' href='Constants.html'>Constants</a>\n</li><li><a class='wikilink' href='Expressions.html'>Expressions</a>\n</li><li><a class='wikilink' href='Synchronisation.html'>Synchronisation</a>\n</li><li><a class='wikilink' href='ModuleRenaming.html'>Module Renaming</a>\n</li><li><a class='wikilink' href='MultipleInitialStates.html'>Multiple Initial States</a>\n</li><li><a class='wikilink' href='GlobalVariables.html'>Global Variables</a>\n</li><li><a class='wikilink' href='FormulasAndLabels.html'>Formulas And Labels</a>\n</li><li><a class='wikilink' href='CostsAndRewards.html'>Costs And Rewards</a>\n</li><li><a class='wikilink' href='Real-timeModels.html'>Real-time Models</a>\n</li><li><a class='wikilink' href='PartiallyObservableModels.html'>Partially Observable Models</a>\n</li><li><a class='selflink' href='UncertainModels.html'>Uncertain Models</a>\n</li><li><a class='wikilink' href='ProcessAlgebraOperators.html'>Process Algebra Operators</a>\n</li><li><a class='wikilink' href='PRISMModelFiles.html'>PRISM Model Files</a>\n</li></ul><p>[ <a class='wikilink' href='AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/ThePRISMLanguage/UncertainModels@action=print.html",
    "content": "\n<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">\n\n<html>\n<head>\n\n<title>PRISM Manual | ThePRISMLanguage / UncertainModels </title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=iso-8859-1\"/>\n\n<!--HeaderText--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\r\n.sourceblocklink {\r\n  text-align: right;\r\n  font-size: smaller;\r\n}\r\n.sourceblocktext {\r\n  padding: 0.5em;\r\n  border: 1px solid #808080;\r\n  color: #000000;\r\n  background-color: #f1f0ed;\r\n}\r\n.sourceblocktext div {\r\n  font-family: monospace;\r\n  font-size: small;\r\n  line-height: 1;\r\n  height: 1%;\r\n}\r\n.sourceblocktext div.head,\r\n.sourceblocktext div.foot {\r\n  font: italic medium serif;\r\n  padding: 0.5em;\r\n}\r\n\n--></style>  <meta name='robots' content='noindex,nofollow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\"/>\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismmanual.css\"/>\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/manual/pub/skins/prismprint/css/prismprint.css\"/>\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffcc\">\n\n<!--PageTitleFmt-->\n  <p><a class='wikilink' href='Main.html'>The PRISM Language</a> /\n</p><h1>Uncertain Models</h1>\n\n<!--PageText-->\n<div id='wikitext'>\n<p>PRISM has support for <em>uncertain</em> models, in which there is epistemic uncertainty regarding some quantitative aspects of the probabilistic models being verified. In particular, it currently supports <em>interval MDPs</em> (IMDPs) and <em>interval DTMCs</em> (IDTMCs), which are MDPs or DTMCs in which transition probabilities can be specified as intervals, indicating that the exact probability is not precisely known. This can be useful, for example, when the transition probabilities have been estimated from data.\n</p>\n<p class='vspace'>Currently, this is achieved by simply replacing the probabilities attached to updates in commands with intervals, e.g.:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock1'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismnum\">0.8</span>,<span class=\"prismnum\">0.9</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.1</span>,<span class=\"prismnum\">0.2</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/UncertainModels?action=sourceblock&amp;num=1' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>As usual, the probability thresholds can be expressions involving state variables or constants, for example:\n</p>\n<div class='vspace'></div>\r\n<div class='sourceblock ' id='sourceblock2'>\r\n  <div class='sourceblocktext'><div class=\"prism\"> [] <span class=\"prismident\">x</span>=<span class=\"prismnum\">0</span> -&gt; [<span class=\"prismident\">p</span>,<span class=\"prismident\">p</span>+<span class=\"prismnum\">0.1</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">0</span>) + [<span class=\"prismnum\">0.9</span>-<span class=\"prismident\">p</span>,<span class=\"prismnum\">1</span>-<span class=\"prismident\">p</span>]:(<span class=\"prismident\">x</span>'=<span class=\"prismnum\">1</span>); <br/>\n</div></div>\r\n  <div class='sourceblocklink'><a href='http://www.prismmodelchecker.org/manual/ThePRISMLanguage/UncertainModels?action=sourceblock&amp;num=2' type='text/plain'>[&#036;[Get Code]]</a></div>\r\n</div>\r\n\n<p class='vspace'>When two commands in different modules <a class='wikilink' href='Synchronisation.html'>synchronise</a> and specify the probabilities for updates to variables as intervals, these are considered to be independent, i.e., the probability of each combined transition is taken to be the product of the two component intervals.\n</p>\n<p class='vspace'>See the <a class='wikilink' href='../PropertySpecification/UncertainModels.html'>property specification</a> section for details of how these models are analysed.\n</p>\n</div>\n\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/index.html",
    "content": "\n<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\"\n\"http://www.w3.org/TR/html4/loose.dtd\">\n\n\n<html>\n<head>\n\n<title>\nPRISM Manual | Main / Welcome \n</title>\n\n<meta http-equiv=\"Content-Type\" content=\"text/html; charset=UTF-8\">\n<meta name=\"keywords\" content=\"prism, probabilistic, symbolic, model, checker, verification, birmingham, oxford, parker, norman, kwiatkowska\">\n\n<link rel=\"icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n<link rel=\"shortcut icon\" href=\"http://www.prismmodelchecker.org/images/prism.ico\" type=\"image/x-icon\">\n\n<!--The following line is needed by PmWiki (for the manual) - don't delete-->\n<!--HTMLHeader--><style type='text/css'><!--\n  ul, ol, pre, dl, p { margin-top:0px; margin-bottom:0px; }\n  code.escaped { white-space: pre; }\n  .vspace { margin-top:1.33em; }\n  .indent { margin-left:40px; }\n  .outdent { margin-left:40px; text-indent:-40px; }\n  a.createlinktext { text-decoration:none; border-bottom:1px dotted gray; }\n  a.createlink { text-decoration:none; position:relative; top:-0.5em;\n    font-weight:bold; font-size:smaller; border-bottom:none; }\n  img { border:0px; }\n  .editconflict { color:green; \n  font-style:italic; margin-top:1.33em; margin-bottom:1.33em; }\n\n  table.markup { border:2px dotted #ccf; width:90%; }\n  td.markup1, td.markup2 { padding-left:10px; padding-right:10px; }\n  table.vert td.markup1 { border-bottom:1px solid #ccf; }\n  table.horiz td.markup1 { width:23em; border-right:1px solid #ccf; }\n  table.markup caption { text-align:left; }\n  div.faq p, div.faq pre { margin-left:2em; }\n  div.faq p.question { margin:1em 0 0.75em 0; font-weight:bold; }\n  div.faqtoc div.faq * { display:none; }\n  div.faqtoc div.faq p.question \n    { display:block; font-weight:normal; margin:0.5em 0 0.5em 20px; line-height:normal; }\n  div.faqtoc div.faq p.question * { display:inline; }\n  td.markup1 pre { white-space: pre-wrap; }\n  .noPmTOC, .PmTOCdiv:empty {display:none;}\n.PmTOCdiv { display: inline-block; font-size: 13px; overflow: auto; max-height: 500px;}\n.PmTOCdiv a { text-decoration: none; display: block; line-height: 1;}\n.PmTOCdiv a.pmtoc-indent1 { margin-left: 1em; }\n.PmTOCdiv a.pmtoc-indent2 { margin-left: 2em; }\n.PmTOCdiv a.pmtoc-indent3 { margin-left: 3em; }\n.PmTOCdiv a.pmtoc-indent4 { margin-left: 4em; }\n.PmTOCdiv a.pmtoc-indent5 { margin-left: 5em; }\n.PmTOCdiv a.pmtoc-indent6 { margin-left: 6em; }\n.back-arrow {font-size: .8rem; text-decoration: none; vertical-align: text-top;}\n#PmTOCchk + label {cursor: pointer;}\n#PmTOCchk {display: none;}\n#PmTOCchk:not(:checked) + label > .pmtoc-show {display: none;}\n#PmTOCchk:checked + label > .pmtoc-hide {display: none;}\n#PmTOCchk:checked + label + div {display: none;}table.sortable th { cursor: pointer; }\ntable.sortable th::after { color: transparent; content: \"\\00A0\\025B8\"; }\ntable.sortable th:hover::after { color: inherit; content: \"\\00A0\\025B8\"; }\ntable.sortable th.dir-u::after { color: inherit; content: \"\\00A0\\025BE\"; }\ntable.sortable th.dir-d::after { color: inherit; content: \"\\00A0\\025B4\"; } \n    .frame \n      { border:1px solid #cccccc; padding:4px; background-color:#f9f9f9; }\n    .lfloat { float:left; margin-right:0.5em; }\n    .rfloat { float:right; margin-left:0.5em; }\na.varlink { text-decoration:none;}\n\n--></style>  <meta name='robots' content='index,follow' />\n\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/base.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/prism.css\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/print.css\" media=\"print\">\n<link type=\"text/css\" rel=\"stylesheet\" href=\"http://www.prismmodelchecker.org/css/bib.css\">\n\n<link type=\"text/css\" rel=\"stylesheet\" href=\"pub/skins/prism/css/prismmanual.css\">\n\n\n<script type=\"text/javascript\" src=\"http://www.prismmodelchecker.org/includes/prism.js\"></script>\n\n\n<script type=\"text/javascript\">\n  (function(i,s,o,g,r,a,m){i['GoogleAnalyticsObject']=r;i[r]=i[r]||function(){\n  (i[r].q=i[r].q||[]).push(arguments)},i[r].l=1*new Date();a=s.createElement(o),\n  m=s.getElementsByTagName(o)[0];a.async=1;a.src=g;m.parentNode.insertBefore(a,m)\n  })(window,document,'script','//www.google-analytics.com/analytics.js','ga');\n  ga('create', 'UA-42079741-1', 'prismmodelchecker.org');\n  ga('send', 'pageview');\n</script>\n\n</head>\n\n<body text=\"#000000\" bgcolor=\"#ffffff\" onload=\"initialise()\">\n\n<div id=\"prism-banner\">\n\t<div id=\"prism-bannerlefthalf\"></div>\n\t<div id=\"prism-bannerrighthalf\"></div>\n\t<div id=\"prism-bannerurl\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/url_thin.png\" alt=\"www.prismmodelchecker.org\"></a></div>\n\t<div id=\"prism-bannerlogo\"><a href=\"http://www.prismmodelchecker.org/\"><img src=\"http://www.prismmodelchecker.org/images/p_blue.png\" alt=\"P\"></a></div>\n\t<form id=\"prism-searchbox\" title=\"Search the PRISM site with Google\" method=\"get\" action=\"https://www.google.com/search\">\n\t<input type=\"hidden\" name=\"domains\" value=\"www.prismmodelchecker.org\">\n\t<input type=\"hidden\" name=\"sitesearch\" value=\"www.prismmodelchecker.org\">\n\t<input class=\"input1\" id=\"q\" name=\"q\" type=\"text\" size=\"30\">\n\t<input class=\"input2\" id=\"submit\" type=\"submit\" value=\"Search\">\n\t</form>\n</div>\n\n<div id=\"prism-navbar\">\n<div id=\"prism-navbarinner\">\n\n<ul id=\"prism-navbarmenu\">\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/\" title=\"\">Home</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/about.php\" title=\"\">About</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/about.php\">About PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/people.php\">People</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/sponsors.php\">Sponsors</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/contact.php\">Contact</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/news.php\">News</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/screenshots.php\">Screenshots</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-tools.php\">Other tools</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/links.php\">Links</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/download.php\" title=\"\">Downloads</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/download.php\">PRISM</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/dev/\">Development versions</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/benchmarks/\">Benchmarks</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">PRISM-games</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/other-downloads.php\">Other downloads</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/doc/\" title=\"\">Documentation</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"InstallingPRISM.html\">Installation</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"index.html\">Manual</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"FrequentlyAskedQuestions.html\">FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/tutorial/\">Tutorial</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/lectures/\">Lectures</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitemsel\"><a href=\"index.html\" title=\"\">Manual</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/publ-lists.php\" title=\"\">Publications</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-selected.php\">Selected publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publications.php\">PRISM publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib.php\">PRISM bibliography</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/bib-ext.php\">External publications</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/publ-search.php\">Search</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/casestudies/index.php\" title=\"\">Case Studies</a>\n\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/support.php\" title=\"\">Support</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"InstallingPRISM/CommonProblemsAndQuestions.html\">Installation FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"FrequentlyAskedQuestions/index.html\">PRISM FAQ</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker\">Forum (Google)</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"https://github.com/prismmodelchecker/prism/wiki\" title=\"\">Developers</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"https://github.com/prismmodelchecker/prism/wiki\">Developer resources</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://groups.google.com/group/prismmodelchecker-dev\">Developer forum</a>\n\t</ul>\n<li> &nbsp;&#8226;&nbsp;\n<li class=\"prism-navitem\"><a href=\"http://www.prismmodelchecker.org/games/\" title=\"\">PRISM-games</a>\n\t<ul class=\"prism-navbarsubmenu\">\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/download.php\">Download</a>\n\t<li class=\"prism-navsubitem\">&#187; <a href=\"http://www.prismmodelchecker.org/games/publ.php\">Publications</a>\n\t</ul>\n</ul>\n<div style=\"clear:both;\"></div>\n\n</div> <!-- id=\"prism-navbarinner\" -->\n</div> <!-- id=\"prism-navbar\" -->\n\n<div id=\"layout-maincontainer\">\n<div id=\"layout-main\">\n\n<div id=\"prism-mainbox\">\n\n<!--<a href=\"http://www.ox.ac.uk/\"><img id=\"prism-unilogo\" src=\"/images/oxford_logo_pale.png\" alt=\"University of Oxford\"></a>-->\n\n<!-- ============================================================================= -->\n\n<!--PageHeaderFmt-->\n  <div id=\"prism-man-commands1\">\n    <p><span class='prism-man-commands'><a class='selflink' href='Main/Main.html'>View</a> - </span><a rel='nofollow'  class='wikilink' href='Main/Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Main/Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Main/Search.html'>Search</a>\n</p>\n\n  </div>\n<!--/PageHeaderFmt-->\n\n<!--PageTitleFmt-->\n  <div id=\"prism-man-title\">\n    <p><a class='wikilink' href='Main/Main.html'>Main</a> /\n</p><h1>Welcome</h1>\n\n  </div>\n<!--PageText-->\n<div id='wikitext'>\n<p>Welcome to the manual for <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM</a>.\nThis document is the main source of information regarding the installation and operation of the PRISM tool. For access to other resources, such as <a class='urllink' href='http://www.prismmodelchecker.org/publications.php'>related publications</a> and details of <a class='urllink' href='http://www.prismmodelchecker.org/casestudies/'>case studies</a>, or to <a class='urllink' href='http://www.prismmodelchecker.org/download.php'>download</a> the tool itself, see the main <a class='urllink' href='http://www.prismmodelchecker.org/'>PRISM website</a>.\n</p>\n<div class='vspace'></div><h3>Which version of PRISM does this manual describe?</h3>\n<p>This manual describes version <strong>4.10.1</strong>.\nIn general, the online copy of the manual corresponds to the most recent\n<a class='urllink' href='http://www.prismmodelchecker.org/download.php'>publically available</a>\nversion of PRISM (including beta versions).\nIf you need the manual for an older version of PRISM,\nuse the version included in that distribution.\n</p>\n<div class='vspace'></div><h3>How do I search the manual?</h3>\n<p>This documentation is continuously updated and is best viewed online. If you are reading this online, you can use the built-in <a class='wikilink' href='Main/Search.html'>search</a> facility (there is a link in the grey box at the top of each page). For a nicer search interface (but possibly not 100% up-to-date index), you can also search with Google, using the search box in the banner at the top of the site.\n</p>\n<p class='vspace'>If you are browsing these pages off-line, for example using the copy distributed with the tool, you can view the whole manual on <a class='wikilink' href='Main/AllOnOnePage.html'>one page</a> and use the search functionality of your browser.\n</p>\n<div class='vspace'></div><h3>How do I print the manual?</h3>\n<p>To print an individual page of the manual click on the \"Print\" link at the top-right hand corner of the page (in the online version) and print the page from your web browser. You can also print an entire section (see the \"View all\" link under the contents on the left) or the <a class='wikilink' href='Main/AllOnOnePage.html'>entire manual</a> in this way.\n</p>\n<div class='vspace'></div><h3>More questions?</h3>\n<p>If you have a question about PRISM and you cannot find the answer in this manual, please use the discussion group provided. Check the\n<a class='urllink' href='http://www.prismmodelchecker.org/support/'>support</a>\nsection of the PRISM website for details.\n</p>\n</div>\n\n\n<!--PageFooterFmt-->\n  <div id='prism-man-footer'>\n    <div id='prism-man-commands2'>\n      <p><a class='selflink' href='Main/Main.html'>View</a> - <a rel='nofollow'  class='wikilink' href='Main/Welcome@action=edit.html'>Edit</a> - <a class='wikilink' href='Main/Welcome@action=print.html'>Print</a> - <a class='wikilink' href='Main/Search.html'>Search</a> - <a rel='nofollow'  class='wikilink' href='Main/Welcome@action=login.html'>Login</a>\n</p>\n\n    </div>\n    <div id='prism-man-lastmod'>Page last modified on April 02, 2026, at 01:54 pm</div>\n  </div>\n<!--/PageFooterFmt-->\n\n\n<!-- ============================================================================= -->\n\n</div> <!-- id=\"prism-mainbox\" -->\n\n<div id=\"prism-footer\">\n<a href=\"http://validator.w3.org/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_html.png\" alt=\"Valid HTML 4.1\"/></a>\n<a href=\"http://www.php.net/\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/php_powered.png\" alt=\"Powered by PHP\"/></a>\n<a href=\"http://jigsaw.w3.org/css-validator/check/referer\"><img border=\"0\" src=\"http://www.prismmodelchecker.org/images/valid_css.png\" alt=\"Valid CSS\"/></a>\n<span style=\"color:#888888; font-size:85%; margin-left:20px;\">Site hosted at the Department of Computer Science, University of Oxford</span>\n</div> <!-- id=\"prism-footer\" -->\n\n</div> <!-- id=\"layout-main\" -->\n</div> <!-- id=\"layout-maincontainer\" -->\n\n<div id=\"layout-leftcol\">\n<div id=\"prism-navbar2\">\n\n<h3><a class='selflink' href='Main/Main.html'>PRISM Manual</a></h3>\n<ul><li><a class='wikilink' href='Main/Contents.html'>Contents</a>\n</li><li><a class='wikilink' href='Main/Introduction.html'>Introduction</a>\n</li><li><a class='wikilink' href='InstallingPRISM/Main.html'>Installing PRISM</a>\n</li><li><a class='wikilink' href='ThePRISMLanguage/Main.html'>The PRISM Language</a>\n</li><li><a class='wikilink' href='PropertySpecification/Main.html'>Property Specification</a>\n</li><li><a class='wikilink' href='RunningPRISM/Main.html'>Running PRISM</a>\n</li><li><a class='wikilink' href='ConfiguringPRISM/Main.html'>Configuring PRISM</a>\n</li><li><a class='wikilink' href='Main/References.html'>References</a>\n</li><li><a class='wikilink' href='FrequentlyAskedQuestions/index.html'>FAQ</a>\n</li><li><a class='wikilink' href='Appendices/Main.html'>Appendices</a>\n</li></ul><p>[ <a class='wikilink' href='Main/AllOnOnePage.html'>View all</a> ]\n</p>\n\n\n</div>  <!-- id=\"prism-navbar2\" -->\n</div> <!-- id=\"layout-leftcol\" -->\n\n<div id=\"layout-footer\">\n</div> <!-- id=\"layout-footer\" -->\n\n</body>\n</html>\n"
  },
  {
    "path": "manual/pub/skins/offline/images/index.html",
    "content": "<p>CSS-required images:</p>\n\n<img src=\"bullet0.png\">\n<img src=\"bullet2.png\">\n<img src=\"bullet.png\">\n<img src=\"hyphen.png\">\n<img src=\"trinity.png\">\n\n"
  },
  {
    "path": "manual/pub/skins/prism/css/prismmanual.css",
    "content": "\n/* Main box */\n\n#prism-unilogo {\n\tdisplay:none;\n}\n\n/* Command boxes */\n\n#prism-man-commands1 {\n\tfloat:right;\n\tmargin:25px;\n\tmargin-right:25px;\n\tcolor:#333333;\n}\n#prism-man-commands2 {\n\tmargin-top:30px;\n\tcolor:#333333;\n}\n#prism-man-commands1 p, #prism-man-commands2 p {\n\tmargin:0;\n\ttext-align:center;\n}\n#prism-man-commands1 a, #prism-man-commands2 a {\n\tpadding:2px 5px 2px 5px;\n\tbackground:#eeeeee;\n\tcolor:#333333;\n\tborder:solid 1px #cccccc;\n}\n\n/* Main box title */\n\n#prism-man-title p {\n\tmargin-top:1em;\n\tmargin-bottom:-1em;\n}\n\n/* Last modified */\n\n#prism-man-lastmod {\n\tmargin-top:30px;\n\ttext-align:center;\n\tfont-size:70%;\n\tcolor:#999999;\n}\n\n/* General CSS for main box content */\n\n#prism-mainbox hr {\n\tmargin-top:20px;\n\tmargin-bottom:10px;\n\theight:4px;\n}\n\n#wikiedit form { margin:0px; }\n#wikiedit textarea { width:98%; }\n\ncode { white-space: normal; }\n\n.big {\n  font-size:100%; /* already inside h1 */\n  color:#444444;\n  /*border-width:8px 0 8px 0;\n  border-color:#444444;\n  border-style:double;*/\n}\n\nh1 img {\n\tvertical-align:middle;\n}\n\npre.cl {\n  padding:10px;\n  margin-left:10px;\n  margin-right:10px;\n  border:1px dotted #808080;\n  background-color:#F1F0ED;\n}\n\n.answer {\n  padding:10px;\n  margin-left:0px;\n  margin-right:0px;\n  border:2px dotted #808080;\n  background-color:#ddddff;\n}\n\ndiv.latex2html dt {\n\tfont-weight:bold;\n}\n\ndiv.sourceblock {\n  padding:5px 10px 5px 10px;\n  margin:10px 0 10px 0;\n  border:2px dotted #808080;\n  background-color:#F1F0ED;\n  width:90%; /* Need a width or else IE6 gets upset */\n  overflow:auto;\n}\n* html div.sourceblock {\n  padding-bottom:1.5em; /* Nasty hack to fix IE6 scrollbar positioning */\n}\n.sourceblocklink {\n  /*float:right;*/\n  display:none;\n}\n.sourceblocktext {\n  border:none;\n  white-space:nowrap;\n  font-family:monospace;\n  font-size:100%;\n  line-height:1.2;\n}\n.sourceblocktext div {\n  font-family:monospace;\n  font-size:100%;\n}\n.sourceblocktext div.head,\n.sourceblocktext div.foot {\n  font:italic medium serif;\n  padding:0.5em;\n}\n"
  },
  {
    "path": "manual/uploads/lec12mdp.nm.html",
    "content": "// Simple MDPs from Lec 12 of Probabilistic Model Checking\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\ns:[0..3];\r\n\r\n[] s=0 -> 1:(s'=1);\r\n[] s=1 -> 0.7:(s'=0) + 0.3:(s'=1);\r\n[] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n[] s=2 -> 1:(s'=2);\r\n[] s=3 -> 1:(s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"heads\" = s=2;\r\nlabel \"tails\" = s=3;\r\n"
  },
  {
    "path": "manual/uploads/lec12mdpa.nm.html",
    "content": "// Simple MDPs from Lec 12 of Probabilistic Model Checking\n\nmdp\n\nmodule M\n\ns:[0..3];\n\n[a] s=0 -> 1:(s'=1);\n[b] s=1 -> 0.7:(s'=0) + 0.3:(s'=1);\n[c] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\n[a] s=2 -> 1:(s'=2);\n[a] s=3 -> 1:(s'=3);\n\nendmodule\n\nlabel \"heads\" = s=2;\nlabel \"tails\" = s=3;\n\nrewards \"r\"\n\t[b] true : 5;\n\t[c] true : 6;\nendrewards\n"
  },
  {
    "path": "manual/uploads/lec3.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"r\"\r\n\ts=0 : 2;\r\n\ts>=4 : 1;\r\n\t[] s<3 : s;\r\nendrewards\r\n"
  },
  {
    "path": "manual/uploads/poll2.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 2;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..2]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism/.classpath",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<classpath>\n\t<classpathentry kind=\"src\" path=\"src\"/>\n\t<classpathentry kind=\"src\" path=\"unit-tests\"/>\n\t<classpathentry kind=\"con\" path=\"org.eclipse.jdt.launching.JRE_CONTAINER\"/>\n\t<classpathentry kind=\"con\" path=\"org.eclipse.jdt.junit.JUNIT_CONTAINER/5\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/epsgraphics.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/jcommon.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/jfreechart.jar\" sourcepath=\"/jfreechart/source\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/jhoafparser.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/colt.jar\" sourcepath=\"/Users/dxp/colt/src\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/pepa.zip\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/lpsolve55j.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/jas.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/log4j-core.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/log4j-api.jar\"/>\n\t<classpathentry kind=\"lib\" path=\"lib/nailgun-server.jar\"/>\n\t<classpathentry kind=\"output\" path=\"classes\"/>\n</classpath>\n"
  },
  {
    "path": "prism/Makefile",
    "content": "##############################################\n#  NB: This is the main Makefile for PRISM.  #\n#      It calls all the other Makefiles in   #\n#      subdirectories, passing in all the    #\n#      options configured here.              #\n##############################################\n\n###############\n# Directories #\n###############\n\n# Note that these are all relative to the PRISM directory\n# to make the distribution more 'portable'.\n# If this is a problem, the best solution is to create symlinks.\n\nexport PRISM_SRC_DIR     = src\nexport PRISM_OBJ_DIR     = obj\nexport PRISM_LIB_DIR     = lib\nexport PRISM_BIN_DIR     = bin\nexport PRISM_INCLUDE_DIR = include\nexport PRISM_IMAGES_DIR  = images\nexport PRISM_DTDS_DIR    = dtds\n\n# Java locations, files\n\nJAVA_SRC_DIR := src\nJAVA_CLASSES_DIR := classes\nJAVA_TESTS_SRC_DIR := unit-tests\nJAVA_TESTS_CLASSES_DIR := $(JAVA_CLASSES_DIR)\n\nJAVA_SRC_FILES := $(shell find $(JAVA_SRC_DIR) -name \"*.java\")\nJAVA_SRC_FILES_LIST := $(JAVA_CLASSES_DIR)/java_sources.txt\nJAVA_COMPILED_STAMP := $(JAVA_CLASSES_DIR)/java_compiled.stamp\nJAVA_PARSER_JJ := $(JAVA_SRC_DIR)/parser/PrismParser.jj\nJAVA_PARSER_JAVA := $(JAVA_SRC_DIR)/parser/PrismParser.java\nJAVA_TESTS_SRC_FILES := $(shell find $(JAVA_TESTS_SRC_DIR) -name \"*.java\")\nJAVA_TESTS_SRC_FILES_LIST := $(JAVA_TESTS_CLASSES_DIR)/java_tests_sources.txt\nJAVA_TESTS_COMPILED_STAMP := $(JAVA_TESTS_CLASSES_DIR)/java_tests_compiled.stamp\n\n# Location of CUDD (used to be variable; now mainly fixed with the git repo layout)\n\nCUDD_DIR := ../cudd\n\n####################\n# Operating system #\n####################\n\n# OSTYPE needs to be one of: linux, solaris, cygwin, darwin\n# This makefile will try to detect which one of these is appropriate.\n# If this detection does not work, or you wish to override it,\n# either uncomment one of the lines directly below\n# or pass a value to make directly, e.g.: make OSTYPE=linux\n\n#OSTYPE = linux\n#OSTYPE = solaris\n#OSTYPE = cygwin\n#OSTYPE = darwin\n\nifneq ($(OSTYPE),)\n\t# Look for common variants, e.g. gnu-linux -> linux\n\tifneq (,$(findstring linux, $(OSTYPE)))\n\t  OSTYPE := linux\n\tendif\n\tifneq (,$(findstring solaris, $(OSTYPE)))\n\t  OSTYPE := solaris\n\tendif\n\tifneq (,$(findstring cygwin, $(OSTYPE)))\n\t  OSTYPE := cygwin\n\tendif\n\t# For Cygwin , OSTYPE is sometimes set to \"posix\"\n\tifneq (,$(findstring posix, $(OSTYPE)))\n\t  OSTYPE := cygwin\n\tendif\n\tifneq (,$(findstring darwin, $(OSTYPE)))\n\t  OSTYPE := darwin\n\tendif\nelse\n\t# If OSTYPE is not defined/available,\n\t# First try OS (on Windows), otherwise try uname\n\tifeq ($(OS),Windows_NT)\n\t\tOSTYPE := cygwin\n\telse\n\t\tUNAME_STR := $(shell uname -s 2>/dev/null || echo unknown)\n\t\tifneq (,$(findstring Linux, $(UNAME_STR)))\n\t\t\tOSTYPE := linux\n\t\tendif\n\t\tifneq (,$(findstring SunOS, $(UNAME_STR)))\n\t\t\tOSTYPE := solaris\n\t\tendif\n\t\tifneq (,$(findstring CYGWIN, $(UNAME_STR)))\n\t\t\tOSTYPE := cygwin\n\t\tendif\n\t\tifneq (,$(findstring MINGW, $(UNAME_STR)))\n\t\t\tOSTYPE := cygwin\n\t\tendif\n\t\tifneq (,$(findstring Darwin, $(UNAME_STR)))\n\t\t\tOSTYPE := darwin\n\t\tendif\n\tendif\nendif\n\n################\n# Architecture #\n################\n\n# For Linux/Mac, we use uname to check the architecture\nifeq ($(OSTYPE),linux)\n\tifneq (,$(findstring 86_64, $(shell uname -m)))\n\t\tARCH := amd64\n\tendif\n\tifneq (,$(findstring ia64, $(shell uname -m)))\n\t\tARCH := ia64\n\tendif\n\tifneq (,$(findstring aarch64, $(shell uname -m)))\n\t\tARCH := aarch64\n\tendif\nendif\nifeq ($(OSTYPE),darwin)\n\tifneq (,$(findstring x86_64, $(shell uname -m)))\n\t\tARCH := x86_64\n\tendif\n\tifneq (,$(findstring arm64, $(shell uname -m)))\n\t\tARCH := arm64\n\tendif\nendif\n# For Windows, we decide whether to build in 64-bit mode based on\n# whether java is 32/64-bit (since these need to match)\nifeq ($(OSTYPE),cygwin)\n\t# Default to 64-bit, which is most likely these days\n\tARCH := x86_64\n    ifeq ($(shell which java 2>/dev/null),)\n        $(error \"Could not find java executable. Please install Java or add it to your PATH.\")\n    endif\n    JAVA_VERSION_STRING := $(shell java -version 2>&1)\n\tifneq (,$(findstring 32-bit, $(JAVA_VERSION_STRING)))\n        ARCH := \n    endif\n    ifneq (,$(findstring Client VM, $(JAVA_VERSION_STRING)))\n        ARCH := \n    endif\nendif\n\n##################\n# Pre-processing #\n##################\n\n# Convert scripts needed for building, in case extracted with CRLF endings\nPRE_PROC := $(shell if [ \"$(OSTYPE)\" = \"cygwin\" ]; then \\\n  dos2unix \"$(PRISM_SRC_DIR)\"/scripts/*.sh; \\\n  dos2unix \"$(CUDD_DIR)\"/setup.sh; \\\nfi 2> /dev/null)\n\n########\n# Java #\n########\n\n# JAVA_DIR needs to be set to the location of your Java installation.\n# This makefile will try to detect this automatically based on the location of the javac command.\n# If this detection does not work, or you wish to override it,\n# either set the variable yourself by uncommenting and/or modifying one of the lines below\n# or pass a value to make directly, e.g.: make JAVA_DIR=/usr/java\n\n# Find javac\nDETECT_JAVAC = $(shell $(PRISM_SRC_DIR)/scripts/findjavac.sh 2> /dev/null)\n\n# Find directory containing javac\nifeq (\"$(DETECT_JAVAC)\",\"\")\n  JAVA_DIR :=\nelse\n  JAVA_DIR := $(shell dirname \"$(DETECT_JAVAC)\" | sed -e 's/\\/bin//' -e 's/\\/Commands//')\nendif\n\n# As a backup way of detecting JAVA_DIR, run java_home\nJAVA_DIR_BACKUP := $(shell \\\n\tif [ -f /usr/libexec/java_home ]; then /usr/libexec/java_home; \\\n\telse echo \"\"; fi )\n\n#JAVA_DIR =\t/usr/java\n#JAVA_DIR =\t/usr/java/j2sdk1.4.2\n#JAVA_DIR =\t/bham/java/packages/j2sdk1.4.2\n#JAVA_DIR =\t/cygdrive/c/java/j2sdk1.4.2\n#JAVA_DIR =\t/System/Library/Frameworks/JavaVM.framework\n\n# Now we locate the JNI header files jni.h and jni_md.h\n# (in fact this is the only reason we need JAVA_DIR)\nJAVA_JNI_H_DIR := $(shell \\\n\tif [ -f \"$(JAVA_DIR)\"/include/jni.h ]; then echo \"$(JAVA_DIR)\"/include; \\\n\telif [ -f \"$(JAVA_DIR)\"/Headers/jni.h ]; then echo \"$(JAVA_DIR)\"/Headers; \\\n\telif [ -f \"$(JAVA_DIR_BACKUP)\"/include/jni.h ]; then echo \"$(JAVA_DIR_BACKUP)\"/include; \\\n\telif [ -f \"$(JAVA_DIR_BACKUP)\"/Headers/jni.h ]; then echo \"$(JAVA_DIR_BACKUP)\"/Headers; \\\n\telse echo \"\"; fi )\nJAVA_JNI_MD_H_DIR := $(shell (ls \"$(JAVA_JNI_H_DIR)\"/jni_md.h \"$(JAVA_JNI_H_DIR)\"/*/jni_md.h | head -n 1 | sed 's/\\/jni_md.h//') 2>/dev/null)\nJAVA_INCLUDES := -I $(JAVA_JNI_H_DIR) -I $(JAVA_JNI_MD_H_DIR)\n\n##################\n# Compilers etc. #\n##################\n\nifeq ($(OSTYPE),cygwin)\n\tifeq ($(ARCH),x86_64)\n\t\tCC := /usr/bin/x86_64-w64-mingw32-gcc\n\t\tCXX := /usr/bin/x86_64-w64-mingw32-g++\n\telse\n\t\tCC := /usr/bin/i686-w64-mingw32-gcc\n\t\tCXX := /usr/bin/i686-w64-mingw32-g++\n\tendif\n\tJAVACC := javacc.bat\nelse\n\tCC := gcc\n\tCXX := g++\n\tJAVACC := javacc\nendif\nLD := $(CXX)\nJAVAC := javac\nJAVA := java\n\nexport CC CXX LD JAVAC JAVACC\n\n##############\n# Flags etc. #\n##############\n\n# Tell compiler to generate debug information?\n# (WARNING: must not contain a % symbol!)\nDEBUG := \n#DEBUG := -g\n\n# Compiler optimisation level:\n# (WARNING: must not contain a % symbol!)\nOPTIMISE := -O3\n#OPTIMISE :=\n\n# Compiler warnings to enable:\n# (WARNING: must not contain a % symbol!)\nWARNINGS := #-Wformat\n\n# Flags for compilation/linking\n# Flags to generate shared libraries\n# Executable/library naming conventions\n# Suffix for binary distribution directory\n# (requires GNU make for conditional evaluation)\n\n# Linux\nifeq ($(OSTYPE),linux)\n\tifeq ($(ARCH),amd64)\n\t\t# Position Independent Code required on AMD64/Itanium\n\t\tCFLAGS := -m64 -fPIC -DPIC $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 $(CFLAGS)\n\t\tLDFLAGS :=\n\t\tBINDISTSUFFIX := linux64\n\t\tBINDISTARCH := x86\n\telse\n\tifeq ($(ARCH),ia64)\n\t\t# Position Independent Code required on AMD64/Itanium\n\t\t# Note: We omit the -m64 flag from here since it seems to be unsupported by gcc on IA64\n\t\tCFLAGS := -fPIC -DPIC $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 $(CFLAGS)\n\t\tLDFLAGS :=\n\t\tBINDISTSUFFIX := linux64\n\t\tBINDISTARCH := ia64\n\telse\n\tifeq ($(ARCH),aarch64)\n\t\t# Position Independent Code required on Aarch64\n\t\tCFLAGS := -fPIC -DPIC $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 $(CFLAGS)\n\t\tLDFLAGS :=\n\t\tBINDISTSUFFIX := linux64\n\t\tBINDISTARCH := arm\n\telse\n\t\tCFLAGS := -m32 $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 $(CFLAGS)\n\t\tLDFLAGS :=\n\t\tBINDISTSUFFIX := linux32\n\t\tBINDISTARCH := x86\n\tendif\n\tendif\n\tendif\n\tBIN_TARGETS := prism.linux xprism.linux\n\tJFLAGS := -encoding UTF8\n\tSHARED := -shared\n\t#SHARED := -G\n\tEXE :=\n\tLIBPREFIX := lib\n\tLIBSUFFIX := .so\n\tLIBMATH := -lm\n\tCLASSPATHSEP := :\nendif\n# Solaris\nifeq ($(OSTYPE),solaris)\n\tCFLAGS := -mcpu=ultrasparc $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\tCXXFLAGS := --std=c++11 $(CFLAGS)\n\tLDFLAGS :=\n\tBINDISTSUFFIX := solaris\n\tBINDISTARCH := solaris\n\tBIN_TARGETS := prism.linux xprism.linux\n\tJFLAGS := -encoding UTF8\n\tSHARED := -shared -mimpure-text\n\tEXE :=\n\tLIBPREFIX := lib\n\tLIBSUFFIX := .so\n\tLIBMATH := -lm\n\tCLASSPATHSEP := :\nendif\n# Cygwin\nifeq ($(OSTYPE),cygwin)\n\t# -DWIN32 needed for lpsolve (included e.g. in sparse) - WIN32 is only defined by mingw/gcc without --std=c++11\n\t# -static-libgcc -static-libstdc+ needed to build binaries that don't rely on these libraries to be present\n\t# -Wl,--add-stdcall-alias needed so shared libraries can be read from JNI\n\t# -Wl ... -lpthread ... --no-whole-archive needed to statically include pthread in case missing\n\tifeq ($(ARCH),x86_64)\n\t\tCFLAGS := $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 -DWIN32 $(CFLAGS)\n\t\tLDFLAGS := -static-libgcc -static-libstdc++ -Wl,--add-stdcall-alias -Wl,-Bstatic,--whole-archive -lpthread -Wl,-Bdynamic,--no-whole-archive\n\t\tBINDISTSUFFIX := win64\n\t\tBINDISTARCH := x86\n\telse\n\t\tCFLAGS := -march=i686 $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 -DWIN32 $(CFLAGS)\n\t\tLDFLAGS := -static-libgcc -static-libstdc++ -Wl,--add-stdcall-alias -Wl,-Bstatic,--whole-archive -lpthread -Wl,-Bdynamic,--no-whole-archive\n\t\tBINDISTSUFFIX := win32\n\t\tBINDISTARCH := x86\n\tendif\n\tBIN_TARGETS := prism.cygwin xprism.linux prism.bat.win xprism.bat.win\n\tJFLAGS := -encoding UTF8\n\tSHARED := -shared\n\t#SHARED := -G\n\tEXE := .exe\n\tLIBPREFIX :=\n\tLIBSUFFIX := .dll\n\tLIBMATH := \n\tCLASSPATHSEP := ;\nendif\n# Darwin\nifeq ($(OSTYPE),darwin)\n\tifeq ($(ARCH),x86_64)\n\t\tCFLAGS := -arch x86_64 -fPIC -DPIC $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 $(CFLAGS)\n\t\tLDFLAGS := -arch x86_64 -Wl,-search_paths_first\n\t\tBINDISTSUFFIX := mac64\n\t\tBINDISTARCH := x86\n\t\tBIN_TARGETS := prism.darwin xprism.linux\n\telse\n\tifeq ($(ARCH),arm64)\n\t\tCFLAGS := -arch arm64 -fPIC -DPIC $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 $(CFLAGS)\n\t\tLDFLAGS := -arch arm64 -Wl,-search_paths_first\n\t\tBINDISTSUFFIX := mac64\n\t\tBINDISTARCH := arm\n\t\tBIN_TARGETS := prism.darwin xprism.linux\n\telse\n\t\tCFLAGS := -arch i386 $(DEBUG) $(OPTIMISE) $(WARNINGS)\n\t\tCXXFLAGS := --std=c++11 $(CFLAGS)\n\t\tLDFLAGS := -arch i386 -Wl,-search_paths_first\n\t\tBINDISTSUFFIX := mac32\n\t\tBINDISTARCH := x86\n\t\tBIN_TARGETS := prism.darwin xprism.linux\n\tendif\n\tendif\n\tJFLAGS := -encoding UTF8\n\tSHARED := -dynamiclib\n\tEXE :=\n\tLIBPREFIX := lib\n\tLIBSUFFIX := .dylib\n\tLIBMATH := -lm\n\tCLASSPATHSEP := :\nendif\n\n# Java flags\nJFLAGS += -proc:none # Remove annotation processing warnings due to log4j\nJFLAGS += --release 11 # Enforce Java language level\n\nexport CFLAGS CXXFLAGS LDFLAGS JFLAGS LIBPREFIX LIBSUFFIX\n\n##########################################\n# Main part of Makefile: Compiling PRISM #\n##########################################\n\nEXT_PACKAGES := lpsolve55 lp_solve_5.5_java\n\n.PHONY: clean javadoc tests release\n\n# inhibit building in parallel (-j option)\n.NOTPARALLEL:\n\ndefault: all\n\nall: cuddpackage extpackages prism\n\n# Build our customised version of CUDD\n# (let CUDD choose its own linker - problems on Cygwin if not)\n# (should be no need for linker options - we use static CUDD libraries)\n# (note CFLAGS/CXXFLAGS _are_ passed on, e.g. to preserve PIC consistency)\ncuddpackage: checks\n\t@echo Making cudd ...; cd $(CUDD_DIR) && \\\n\tLD= LDFLAGS= ./install.sh\n\n# Build various external libraries needed by PRISM\nextpackages: checks\n\t@for ext in $(EXT_PACKAGES); do \\\n\t  echo Making $$ext ...; \\\n\t  (cd ext/$$ext && \\\n\t  $(MAKE) \\\n\t  OSTYPE=\"$(OSTYPE)\" \\\n\t  ARCH=\"$(ARCH)\" \\\n\t  SHARED=\"$(SHARED)\" \\\n\t  LIBMATH=\"$(LIBMATH)\" \\\n\t  BINDISTSUFFIX=\"$(BINDISTSUFFIX)\" \\\n\t  BINDISTARCH=\"$(BINDISTARCH)\" \\\n\t  JAVA_DIR=\"$(JAVA_DIR)\" \\\n\t  JAVA_JNI_H_DIR=\"$(JAVA_JNI_H_DIR)\" \\\n\t  JAVA_JNI_MD_H_DIR=\"$(JAVA_JNI_MD_H_DIR)\" \\\n\t  ) || exit 1; \\\n\tdone\n\n# Compile main PRISM code\n# (we also do some preparatory checks, and build launch scripts afterwards)\nprism: checks prism_java prism_lib prism_ng bin_scripts\n\n# Compile all Java code, build JNI headers\nprism_java: $(JAVA_COMPILED_STAMP)\n\n$(JAVA_COMPILED_STAMP): $(JAVA_SRC_FILES)\n\t@mkdir -p $(JAVA_CLASSES_DIR) $(PRISM_INCLUDE_DIR)/jni\n\t@find $(JAVA_SRC_DIR) -name \"*.java\" > $(JAVA_SRC_FILES_LIST)\n\t@echo \"Compiling Java files...\"\n\t$(JAVAC) $(JFLAGS) -classpath \"$(PRISM_LIB_DIR)/*\" -d $(JAVA_CLASSES_DIR) -h $(PRISM_INCLUDE_DIR)/jni @$(JAVA_SRC_FILES_LIST)\n\t@touch $@\n\n# Rebuild PRISM (JavaCC) compiler if needed\n# Just emit warning if javacc not available and fall back to pre-compiled .java\n$(JAVA_PARSER_JAVA): $(JAVA_PARSER_JJ)\n\t@$(JAVACC) $< || echo \"Warning: Did not recompile $@\"\n\n# Use this to force a rebuild (with javacc) of the main parser\nparser: parser_force prism_java\n\nparser_force:\n\t@ echo \"Forcing parser rebuild\"\n\t@$(JAVACC) $(JAVA_PARSER_JJ)\n\n# On Windows, convert the generated JNI headers using dos2unix\n# and any scripts to be run from Cywgin, in case extracted with CRLF endings.\n\t@if [ \"$(OSTYPE)\" = \"cygwin\" ]; then \\\n\t  dos2unix $(PRISM_INCLUDE_DIR)/jni/*.h; \\\n\t  find .. -name '*.sh' -exec dos2unix {} \\; ; \\\n\t  dos2unix \"$(PRISM_SRC_DIR)\"/bin/prism.cygwin; \\\n\tfi\n\nPRISM_LIB_DIRS := dd jdd odd dv prism mtbdd sparse hybrid\n\nPRISM_LIB_EXCLUDE_FILES := $(PRISM_SRC_DIR)/dd/dd_test.cc\nPRISM_LIB_ALL_SRC_FILES := $(shell find $(foreach d,$(PRISM_LIB_DIRS),$(PRISM_SRC_DIR)/$(d)) -name \"*.cc\")\nPRISM_LIB_SRC_FILES := $(filter-out $(PRISM_LIB_EXCLUDE_FILES), $(PRISM_LIB_ALL_SRC_FILES))\nPRISM_LIB_OBJ_FILES := $(patsubst $(PRISM_SRC_DIR)/%.cc, $(PRISM_OBJ_DIR)/%.o, $(PRISM_LIB_SRC_FILES))\n\nOLD_SHARED_LIBS := dd jdd odd dv prismmtbdd prismsparse prismhybrid\nOLD_SHARED_LIB_FILES := $(patsubst %, $(PRISM_LIB_DIR)/$(LIBPREFIX)%$(LIBSUFFIX), $(OLD_SHARED_LIBS))\n\nINCLUDES := \\\n-I$(CUDD_DIR)/include \\\n-I\"$(JAVA_JNI_H_DIR)\" \\\n-I\"$(JAVA_JNI_MD_H_DIR)\" \\\n-I$(PRISM_INCLUDE_DIR) \\\n-Iext/lpsolve55/include\n\nLIBRARIES := \\\n-L$(PRISM_LIB_DIR) \\\n-L$(CUDD_DIR)/lib \\\n-lcudd \\\n$(LIBMATH) \\\n-llpsolve55\n\n# Setup RPATH. Use = here (not :=) so $@ is evaluated inside the recipe scope\nRPATH_LINUX   = -Wl,-soname,$(notdir $@) -Wl,-rpath,'$$ORIGIN'\nRPATH_DARWIN  = -Wl,-install_name,@rpath/$(notdir $@) -Wl,-rpath,@loader_path/.\n# Then pick the right one based on OSTYPE\n$(PRISM_LIB_DIR)/$(LIBPREFIX)prism$(LIBSUFFIX): RPATH_SETTING = \\\n    $(if $(filter linux,$(OSTYPE)),$(RPATH_LINUX), \\\n    $(if $(filter darwin,$(OSTYPE)),$(RPATH_DARWIN),))\n\n# Compile the main native shared library\nprism_lib: prism_java $(PRISM_LIB_DIR)/$(LIBPREFIX)prism$(LIBSUFFIX)\n\n$(PRISM_LIB_DIR)/$(LIBPREFIX)prism$(LIBSUFFIX): $(PRISM_LIB_OBJ_FILES)\n\t@echo \"Linking shared library $@...\"\n\t$(LD) $(SHARED) $(LDFLAGS) $(RPATH_SETTING) -o $@ $^ $(LIBRARIES)\n\n$(PRISM_OBJ_DIR)/%.o: $(PRISM_SRC_DIR)/%.cc\n\t@mkdir -p $(dir $@)\n\t$(CXX) $(CXXFLAGS) -c $< -o $@ -I$(PRISM_INCLUDE_DIR)/jni $(INCLUDES)\n\n# Compile ngprism\n# (on Windows, link winsocket library, ws2_32)\nprism_ng: $(PRISM_OBJ_DIR)/prism/ngprism$(EXE)\n\n$(PRISM_OBJ_DIR)/prism/ngprism$(EXE): $(PRISM_SRC_DIR)/prism/ngprism.c\n\t@echo \"Bilding $@...\"\n\t@if [ \"$(EXE)\" = \"\" ]; then \\\n\t  $(CC) $(LDFLAGS) $(CFLAGS) -o $@ $<; \\\n\telse \\\n\t\t$(CC) $(LDFLAGS) $(CFLAGS) -o $@ $< -lws2_32; \\\n\tfi;\n\n# Compile (Java) unit tests\n$(JAVA_TESTS_COMPILED_STAMP): $(JAVA_TESTS_SRC_FILES)\n\t@mkdir -p $(JAVA_TESTS_CLASSES_DIR)\n\t@find $(JAVA_TESTS_SRC_DIR) -name \"*.java\" > $(JAVA_TESTS_SRC_FILES_LIST)\n\t@echo \"Compiling Java unit tests...\"\n\t$(JAVAC) $(JFLAGS) -sourcepath $(JAVA_SRC_DIR) -classpath $(PRISM_CLASSPATH) -d $(JAVA_TESTS_CLASSES_DIR) -h $(PRISM_INCLUDE_DIR)/jni @$(JAVA_TESTS_SRC_FILES_LIST)\n\t@touch $@\n\n# Copy/modify the launch scripts and put in the bin directory\nbin_scripts:\n\t@mkdir -p $(PRISM_BIN_DIR)\n\t@for target in $(BIN_TARGETS); do \\\n\t  target_trunc=`echo $$target | sed 's/\\.[^.]*$$//'` && \\\n\t  echo Copying \"$(PRISM_SRC_DIR)/bin/$$target -> $(PRISM_BIN_DIR)/$$target_trunc\" && \\\n\t  cp $(PRISM_SRC_DIR)/bin/$$target \"$(PRISM_BIN_DIR)/$$target_trunc\"; \\\n\tdone;\n\t@echo Copying \"$(PRISM_OBJ_DIR)/prism/ngprism$(EXE) -> $(PRISM_BIN_DIR)/ngprism$(EXE)\" && \\\n\tcp $(PRISM_OBJ_DIR)/prism/ngprism$(EXE) $(PRISM_BIN_DIR)/ngprism$(EXE)\n\t@./install.sh silent\n\n# Some checks to make sure that the main settings are valid\nchecks:\n\t@(if [ \"$(OSTYPE)\" != \"linux\" -a \"$(OSTYPE)\" != \"solaris\" -a \"$(OSTYPE)\" != \"cygwin\" -a \"$(OSTYPE)\" != \"darwin\" ]; then \\\n\t  echo \"\\033[33mTo compile PRISM, the environment variable OSTYPE\"; \\\n\t  echo \"must be set to one of: linux, solaris, cygwin or darwin,\"; \\\n\t  echo \"depending on which operating system you are using.\"; \\\n\t  echo \"This is not the case on your system. Please specify\"; \\\n\t  echo \"the value of OSTYPE manually to make, e.g.:\"; \\\n\t  echo; \\\n\t  echo \"  make OSTYPE=linux\"; \\\n\t  echo; \\\n\t  echo \"Alternatively, if you wish, you can set the environment\"; \\\n\t  echo \"variable yourself (using setenv or export) or you\"; \\\n\t  echo \"can edit the value of OSTYPE directly in the Makefile.\"; \\\n\t  echo \"\\033[0m\"; \\\n\t  exit 1; \\\n\tfi; \\\n\tif [ \"$(JAVA_DIR)\" = \"\" ]; then \\\n\t  echo \"\\033[33mPRISM was unable to find the directory which contains\"; \\\n\t  echo \"your Java distribution. Please specify this manually to\"; \\\n\t  echo \"make, as in these examples:\"; \\\n\t  echo; \\\n\t  echo \"  make JAVA_DIR=/usr/java/j2sdk1.4.2\"; \\\n\t  echo \"  make JAVA_DIR=\\\"/cygdrive/c/Program Files/Java/jdk1.4.2\\\"\"; \\\n\t  echo; \\\n\t  echo \"See the PRISM manual for further information.\"; \\\n\t  echo; \\\n\t  echo \"Alternatively, if you wish, you can set the environment\"; \\\n\t  echo \"variable yourself (using setenv or export) or you\"; \\\n\t  echo \"can edit the value of JAVA_DIR directly in the Makefile.\"; \\\n\t  echo \"\\033[0m\"; \\\n\t  exit 1; \\\n\tfi; \\\n\tif [ ! -d \"$(JAVA_DIR)\" ]; then \\\n\t  echo \"\\033[33mJava directory \\\"$(JAVA_DIR)\\\" does not exist.\"; \\\n\t  echo \"\\033[0m\"; \\\n\t  exit 1; \\\n\tfi; \\\n\tif [ ! -f \"$(JAVA_JNI_H_DIR)\"/jni.h ]; then \\\n\t  echo \"\\033[33mCould not locate JNI header jni.h within \\\"$(JAVA_DIR)\\\".\"; \\\n\t  echo \"You may need to set JAVA_DIR by hand. See the PRISM manual for details.\"; \\\n\t  echo \"\\033[0m\"; \\\n\t  exit 1; \\\n\tfi; \\\n\tif [ ! -f \"$(JAVA_JNI_MD_H_DIR)\"/jni_md.h ]; then \\\n\t  echo \"\\033[33mCould not locate JNI header jni_md.h within \\\"$(JAVA_DIR)\\\".\"; \\\n\t  echo \"You may need to set JAVA_DIR by hand. See the PRISM manual for details.\"; \\\n\t  echo \"\\033[0m\"; \\\n\t  exit 1; \\\n\tfi; \\\n\techo \"VERSION: $(VERSION)\"; \\\n\techo \"OSTYPE/ARCH: $(OSTYPE) $(ARCH)\"; \\\n\techo \"JAVA_DIR: $(JAVA_DIR)\"; \\\n\techo \"JAVA_DIR_BACKUP: $(JAVA_DIR_BACKUP)\"; \\\n\techo \"JAVAC (which): \"`which $(JAVAC)`; \\\n\techo \"JAVAC (version): \"$(shell $(JAVAC) -version) \\\n\t)\n\n# Misc: count the number of lines of code\ncount_loc:\n\tfind $(PRISM_SRC_DIR) $(JAVA_SRC_DIR) -name '*.java' -o -name '*.cc' | xargs wc -l\n\n###########\n# Testing #\n###########\n\n# Run all unit tests\nJUNIT_JAR = $(wildcard $(PRISM_LIB_DIR)/junit-platform-console-standalone*.jar)\nunittests: $(JAVA_TESTS_COMPILED_STAMP)\n\t# Provide Regex to match our test classes. If none is given, only certain test classes are excluded by default.\n\t$(JAVA) -jar $(JUNIT_JAR) -cp classes --include-classname '^(Test.*|.+[.$$]Test.*|.+Tests?[.$$].+|.*Tests?)$$' -scan-classpath --details=summary\n\n# Run a single test case from the test suite (useful quick check that the build was ok)\ntest:\n\t$(PRISM_BIN_DIR)/prism etc/tests/dtmc_pctl.prism etc/tests/dtmc_pctl.prism.props -h -test\n\n# Run a single test case from the test suite that relies on lpsolve being properly installed\ntestlpsolve:\n\t$(PRISM_BIN_DIR)/prism etc/tests/test_lpsolve_mdpmo.prism etc/tests/test_lpsolve_mdpmo.prism.props -lp -test\n\n# Run all tests from the test suite (in ../prism-tests and ./tests)\n# Optionally, extra arguments for prism-auto are picked up via variable TESTS_ARGS\ntests: testslocal\n\t@if [ -d ../prism-tests ]; then \\\n\t  etc/scripts/prism-auto -t -m ../prism-tests -p $(PRISM_BIN_DIR)/prism --print-failures --nailgun --ngprism $(PRISM_BIN_DIR)/ngprism $(TESTS_ARGS); \\\n\telse \\\n\t  echo \"Skipping tests\"; \\\n\tfi\n\n# Just display the command to run the test suite on this version of PRISM\n# Optionally, extra arguments for prism-auto are picked up via variable TESTS_ARGS\ntestsecho:\n\t@echo etc/scripts/prism-auto -t -m ../prism-tests -p $(PRISM_BIN_DIR)/prism --print-failures --nailgun --ngprism $(PRISM_BIN_DIR)/ngprism $(TESTS_ARGS)\n\n# Run local tests (in ./tests)\n# Optionally, extra arguments for prism-auto are picked up via variable TESTS_ARGS\ntestslocal:\n\t@if [ -d tests ]; then \\\n\t  etc/scripts/prism-auto -t -m tests -p $(PRISM_BIN_DIR)/prism --print-failures --nailgun --ngprism $(PRISM_BIN_DIR)/ngprism $(TESTS_ARGS); \\\n\telse \\\n\t  echo \"Skipping local tests\"; \\\n\tfi\n\n# Run the tests from ../prism-tests (with different engine settings, picked up from ../prism-tests/all-engines.args)\n# - Export tests are disabled, as there is currently no robust test mechanism for dealing with the\n#   variations in the output of the different engines.\n# - We run with --test-all, as failures for some engines should not abort the tests\n# - We run with a timeout of 1 minute, as some engines take a long time for some properties\ntestsfull:\n\tetc/scripts/prism-auto -t -m ../prism-tests \\\n\t--skip-export-runs --skip-duplicate-runs --test-all -a ../prism-tests/all-engines.args --timeout 1m \\\n\t-p $(PRISM_BIN_DIR)/prism --print-failures --nailgun $(TESTS_ARGS);\n\n##########################\n# Building distributions #\n##########################\n\n# Build prism.jar\nbinary:\n\t@echo \"Generating JAR file ($(PRISM_LIB_DIR)/prism.jar)...\"\n\t@jar cmf $(JAVA_SRC_DIR)/manifest.txt $(PRISM_LIB_DIR)/prism.jar -C $(JAVA_CLASSES_DIR) . -C . $(PRISM_IMAGES_DIR) $(PRISM_DTDS_DIR)\n\n# Build prism-sources.jar\nsource-jar:\n\t@echo \"Generating sources JAR file ($(PRISM_LIB_DIR)/prism-sources.jar)...\"\n\t@find $(JAVA_SRC_DIR) -type f -name '*.java' -o -name '*.form' -o -name '*.jj' | sed -e \"s/^$(JAVA_SRC_DIR)./-C $(JAVA_SRC_DIR) /\" > prism-sources.txt\n\t@jar cf $(PRISM_LIB_DIR)/prism-sources.jar @prism-sources.txt\n\t@rm -f prism-sources.txt\n\n# Download a local html copy of the manual\n#PRISM_MANUAL_WEBSITE := http://prismmodelchecker.localhost/manual/\nPRISM_MANUAL_WEBSITE := http://www.prismmodelchecker.org/manual/\ndoc: clean_doc\n\t(cd .. && wget -r -np -k -E -nH --no-cookies --header \"Cookie: setskin=offline\" --restrict-file-names=windows --reject '*action=sourceblock*' $(PRISM_MANUAL_WEBSITE) $(PRISM_MANUAL_WEBSITE)/pub/skins/offline/images/)\nclean_doc:\n\trm -rf ../manual\n\n# Set up version, in particular for building releases\n# Unless VERSION has been passed in (as VERSION=xxx),\n# extract version number from Java code using printversion\nVERSION = $(shell $(PRISM_SRC_DIR)/scripts/printversion.sh $(PRISM_SRC_DIR) 2> /dev/null)\n\n# Default branch for building source releases\nBRANCH = master\n\n# File/dir names for distribution\nSRC_DIST_DIR = prism-$(VERSION)-src\nSRC_DIST_FILE = $(SRC_DIST_DIR).tar.gz\nBIN_DIST_DIR = prism-$(VERSION)-$(BINDISTSUFFIX)-$(BINDISTARCH)\nBIN_DIST_FILE = $(BIN_DIST_DIR).tar.gz\nBIN_DIST_INST = $(BIN_DIST_DIR)-installer.exe\n\n# Build a (binary) distribution in the release directory\n\nrelease: clean_all all binary release_check_version build_release clean_binary\n\nrelease_check_version:\n\t@if [ \"$(VERSION)\" = \"\" ]; then echo \"Usage: make release VERSION=4.5\"; exit 1; fi\n\nbuild_release:\n\t@if [ \"$(BINDISTSUFFIX)\" = \"win32\" -o \"$(BINDISTSUFFIX)\" = \"win64\" ]; then \\\n\t\techo Creating Windows installer in \"release/$(BIN_DIST_INST)\"... && \\\n\t\tmakensis /NOCD /DPRISM_NAME=\"PRISM $(VERSION)\" /DPRISM_BUILD=\"prism-$(VERSION)\" /DPRISM_BINDISTSUFFIX=\"$(BINDISTSUFFIX)\" /DPRISM_BINDISTARCH=\"$(BINDISTARCH)\" /DPRISM_DIR=\"..\" $(PRISM_SRC_DIR)/nsis_script.nsi && \\\n\t\tmkdir -p release && \\\n\t\tmv ../\"$(BIN_DIST_INST)\" release; \\\n\telse \\\n\t\techo Creating binary distribution in \"release/$(BIN_DIST_FILE)\"... && \\\n\t\tmkdir -p release && \\\n\t\trm -rf \"release/$(BIN_DIST_DIR)\" && \\\n\t\trm -f \"release/$(BIN_DIST_FILE)\" && \\\n\t\tmkdir -p \"release/$(BIN_DIST_DIR)\" && \\\n\t\ttar cf - bin $(PRISM_LIB_DIR) install.sh etc -C .. manual prism-examples CHANGELOG.txt COPYING.txt README.md | tar xf - -C \"release/$(BIN_DIST_DIR)\" && \\\n\t\t(cd release && tar cfz \"$(BIN_DIST_FILE)\" \"$(BIN_DIST_DIR)\") && rm -rf \"release/$(BIN_DIST_DIR)\"; \\\n\tfi\n\nrelease_source: release_check_version build_release_source\n\nbuild_release_source:\n\t@echo Creating source distribution from branch \"$(BRANCH)\" in \"release/$(SRC_DIST_FILE)\"... && \\\n\tmkdir -p release && \\\n\trm -rf \"release/$(SRC_DIST_DIR)\" && \\\n\trm -f \"release/$(SRC_DIST_FILE)\" && \\\n\tmkdir -p \"release/$(SRC_DIST_DIR)\" && \\\n\t(cd .. && git archive $(BRANCH) --format=tar) | tar xf - -C \"release/$(SRC_DIST_DIR)\" && \\\n\t(cd release && tar cfz \"$(SRC_DIST_FILE)\" \"$(SRC_DIST_DIR)\") && rm -rf \"release/$(SRC_DIST_DIR)\"\n\n# Build Javadoc (and put in javadoc directory)\n\nPRISM_CLASSPATH := \"$(JAVA_CLASSES_DIR)$(CLASSPATHSEP)$(PRISM_LIB_DIR)/*\"\n\nPRISM_JAVADOC_DIR := javadoc\n\njavadoc: prism_java\n\t@mkdir -p $(PRISM_JAVADOC_DIR)\n\t@echo \"Generating Javadoc...\"\n\tjavadoc -d $(PRISM_JAVADOC_DIR) \\\n\t        -classpath $(PRISM_CLASSPATH) \\\n\t        -quiet \\\n\t        -Xdoclint:none \\\n\t        @$(JAVA_SRC_FILES_LIST)\n\n###############\n# Cleaning up #\n###############\n\n# Clean main PRISM build (not CUDD or external libs)\nclean: checks\n\trm -rf $(JAVA_CLASSES_DIR)\n\trm -f $(JAVA_SRC_FILES_LIST) $(JAVA_COMPILED_STAMP)\n\trm -f $(JAVA_TESTS_SRC_FILES_LIST) $(JAVA_TESTS_COMPILED_STAMP)\n\trm -rf $(PRISM_OBJ_DIR)\n\trm -f $(PRISM_LIB_DIR)/$(LIBPREFIX)prism$(LIBSUFFIX)\n\trm -f $(OLD_SHARED_LIB_FILES)\n\trm -f $(PRISM_INCLUDE_DIR)/jni/*.h\n\trm -f $(PRISM_LIB_DIR)/*jnilib\n\trm -f $(PRISM_LIB_DIR)/prism.jar\n\trm -f $(PRISM_LIB_DIR)/prism-sources.jar\n\trm -f $(addprefix $(PRISM_BIN_DIR)/, $(notdir $(basename $(BIN_TARGETS)))) $(PRISM_BIN_DIR)/ngprism$(EXE)\n\ncelan: clean\n\n# Clean PRISM + CUDD and external libs\nclean_all: checks clean_cudd clean_ext clean\n\nclean_cudd:\n\t@(cd $(CUDD_DIR) && ./clean.sh)\n\nclean_ext:\n\t@(for ext in $(EXT_PACKAGES); do \\\n\t  echo Cleaning $$ext ...; \\\n\t  (cd ext/$$ext && \\\n\t  $(MAKE) -s clean) \\\n\t  || exit 1; \\\n\tdone )\n\n# Remove just the prism.jar binary\nclean_binary:\n\t@echo \"Removing JAR file ($(PRISM_LIB_DIR)/prism.jar)...\"\n\t@rm -f $(PRISM_LIB_DIR)/prism.jar\n\n###############\n# IDE support #\n###############\n\n# Set up for IntelliJ IDEA\nintellij:\n\tetc/intellij/install.sh\n\n#################################################\n"
  },
  {
    "path": "prism/dtds/chartformat.dtd",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n\n<!--\n    Document   : chartformat.dtd\n    Created on : 26 October 2004, 19:23\n    Author     : Andrew Hinton\n    Description:\n        Describes the structure of XML files used by PRISM's\n        chart package.\n\n    PUBLIC ID  : -//vendor//vocabulary//EN\n    SYSTEM ID  : http://server/path/chartformat.dtd\n-->\n\n<!ELEMENT chartFormat (layout, axis, axis, (graph)*)>\n\n<!ATTLIST chartFormat\n    versionString CDATA #IMPLIED\n    graphTitle CDATA #IMPLIED\n    titleFontName CDATA #IMPLIED\n    titleFontSize CDATA #IMPLIED\n    titleFontStyle CDATA #IMPLIED\n    titleFontColourR CDATA #IMPLIED\n    titleFontColourG CDATA #IMPLIED\n    titleFontColourB CDATA #IMPLIED\n    legendVisible (true|false) #IMPLIED\n    legendPosition (left|bottom|right|manual) #IMPLIED\n    legendPositionX CDATA #IMPLIED\n    legendPositionY CDATA #IMPLIED\n    legendFontName CDATA #IMPLIED\n    legendFontSize CDATA #IMPLIED\n    legendFontStyle CDATA #IMPLIED\n    legendFontColourR CDATA #IMPLIED\n    legendFontColourG CDATA #IMPLIED\n    legendFontColourB CDATA #IMPLIED\n    autoborder (true|false) #IMPLIED\n    >\n\n<!ELEMENT layout (#PCDATA)>\n\n<!ATTLIST layout\n    topOffset CDATA #IMPLIED\n    bottomOffset CDATA #IMPLIED\n    leftOffset CDATA #IMPLIED\n    rightOffset CDATA #IMPLIED\n    >\n\n<!ELEMENT axis (#PCDATA)>\n\n<!ATTLIST axis\n    heading CDATA #IMPLIED\n    headingFontName CDATA #IMPLIED\n    headingFontSize CDATA #IMPLIED\n    headingFontStyle CDATA #IMPLIED\n    headingFontColourR CDATA #IMPLIED\n    headingFontColourG CDATA #IMPLIED\n    headingFontColourB CDATA #IMPLIED\n    numberFontName CDATA #IMPLIED\n    numberFontSize CDATA #IMPLIED\n    numberFontStyle CDATA #IMPLIED\n    numberFontColourR CDATA #IMPLIED\n    numberFontColourG CDATA #IMPLIED\n    numberFontColourB CDATA #IMPLIED\n    showMajor (true|false) #IMPLIED\n    showMinor (true|false) #IMPLIED\n    majorColourR CDATA #IMPLIED\n    majorColourG CDATA #IMPLIED\n    majorColourB CDATA #IMPLIED\n    minorColourR CDATA #IMPLIED\n    minorColourG CDATA #IMPLIED\n    minorColourB CDATA #IMPLIED\n    logarithmic (true|false) #IMPLIED\n    autoscale (true|false) #IMPLIED\n    minValue CDATA #IMPLIED\n    maxValue CDATA #IMPLIED\n    majorGridInterval CDATA #IMPLIED\n    minorGridInterval CDATA #IMPLIED\n    maximumPower CDATA #IMPLIED\n    logBase CDATA #IMPLIED\n    logStyle CDATA #IMPLIED\n    minimumPower CDATA #IMPLIED>\n\n<!ELEMENT graph (point)*>\n\n<!ATTLIST graph\n    seriesHeading CDATA #IMPLIED\n    seriesColourR CDATA #IMPLIED\n    seriesColourG CDATA #IMPLIED\n    seriesColourB CDATA #IMPLIED\n    showPoints (true|false) #IMPLIED\n    seriesShape (circle|square|triangle|rectangle_h|rectangle_v|none) #IMPLIED\n    showLines (true|false) #IMPLIED\n    lineWidth CDATA #IMPLIED\n    lineStyle (normal|dashed|dotDashed) #IMPLIED>\n\n<!ELEMENT point (#PCDATA)>\n\n<!ATTLIST point\n    x CDATA #REQUIRED\n    y CDATA #REQUIRED>\n"
  },
  {
    "path": "prism/dtds/gmo.dtd",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n\n<!--\n    Document   : GMO.dtd\n    Created on : July 8, 2003, 1:07 PM\n    Last change: November 11, 2003, 10:08 AM\n    Author     : Andrew Hinton\n    Description:\n        Document to describe the structure of a Graphic Model File\n        Last modification to accomodate new tree structure i.e. \n        with constants and globals\n-->\n\n<!ELEMENT gmo (constants,globals,systemDescription,(module)*)>\n<!ATTLIST gmo\n    type (stochastic|probabilistic|nondeterministic|dtmc|mdp|ctmc) #REQUIRED\n    filename CDATA #IMPLIED\n    autolayout CDATA #IMPLIED\n    >\n    \n<!ELEMENT constants (integerConstant|doubleConstant|booleanConstant)*>\n<!ELEMENT integerConstant (#PCDATA)>\n<!ATTLIST integerConstant\n    name CDATA #REQUIRED\n    value CDATA #IMPLIED>\n<!ELEMENT doubleConstant (#PCDATA)>\n<!ATTLIST doubleConstant\n    name CDATA #REQUIRED\n    value CDATA #IMPLIED>\n<!ELEMENT booleanConstant (#PCDATA)>\n<!ATTLIST booleanConstant\n    name CDATA #REQUIRED\n    value CDATA #IMPLIED>\n    \n<!ELEMENT globals (variable|boolVariable)*>\n\n<!ELEMENT systemDescription (#PCDATA)>\n\n<!ELEMENT module (state|transition|variable|boolVariable|branchtrans)*>\n<!ATTLIST module\n    name CDATA #REQUIRED\n    x CDATA #IMPLIED\n    y CDATA #IMPLIED\n    width CDATA #IMPLIED\n    height CDATA #IMPLIED\n    zoom CDATA #IMPLIED\n    >\n    \n<!ELEMENT position (#PCDATA)>\n<!ATTLIST position\n    x CDATA #REQUIRED\n    y CDATA #REQUIRED>\n<!ELEMENT invariant (position)>\n<!ATTLIST invariant\n    name CDATA #REQUIRED>\n<!ELEMENT sName (position)>\n<!ATTLIST sName\n    name CDATA #REQUIRED>\n<!ELEMENT state (position,(invariant)?,(sName)?)>\n<!ATTLIST state\n    id CDATA #REQUIRED\n    initial CDATA #REQUIRED>\n\n<!ELEMENT variable (#PCDATA)>\n<!ATTLIST variable\n    name CDATA #REQUIRED\n    min CDATA #REQUIRED\n    max CDATA #REQUIRED\n    init CDATA #IMPLIED>\n    \n<!ELEMENT boolVariable (#PCDATA)>\n<!ATTLIST boolVariable\n    name CDATA #REQUIRED\n    init CDATA #IMPLIED>\n\n<!ELEMENT guard (position)>\n<!ATTLIST guard\n    value CDATA #REQUIRED>\n<!ELEMENT sync (position)>\n<!ATTLIST sync\n    value CDATA #REQUIRED>\n<!ELEMENT assign (position)>\n<!ATTLIST assign\n    value CDATA #REQUIRED>\n<!ELEMENT tranProb (position)>\n<!ATTLIST tranProb\n    value CDATA #REQUIRED>\n<!ELEMENT nail (position)>\n<!ATTLIST nail\n    from CDATA #REQUIRED\n    to CDATA #REQUIRED\n    id CDATA #REQUIRED>\n<!ELEMENT transition ((guard)?,(sync)?,(assign)?,(tranProb)?,(nail)*)>\n<!ATTLIST transition\n    from CDATA #REQUIRED\n    to CDATA #REQUIRED>\n    \n<!ELEMENT branch ((position)?,(assign)?,(tranProb)?)>\n<!ATTLIST branch\n    to CDATA #REQUIRED>\n<!ELEMENT branchtrans ((position),(branch)*,(guard)?,(sync)?,(assign)?)>\n<!ATTLIST branchtrans\n    from CDATA #REQUIRED>\n"
  },
  {
    "path": "prism/dtds/prismnetwork.dtd",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n\n<!--\n    Document   : prismnetwork.dtd\n    Created on : 11 July 2005, 12:28\n    Author     : Andrew Hinton\n    Description:\n        Describes the structure of XML files used by PRISM's\n        networking interface.\n\n    TODO define vocabulary identification data\n    PUBLIC ID  : -//vendor//vocabulary//EN\n    SYSTEM ID  : http://server/path/chartformat.dtd\n-->\n\n<!-- TODO define your own vocabulary/syntax. Example follows:  -->\n<!ELEMENT prismNetwork ((fileSystem)*)>\n<!ATTLIST prismNetwork\n\tversionString CDATA #REQUIRED\n\tsystemName CDATA #REQUIRED\n        sshCommand CDATA #REQUIRED\n        scpCommand CDATA #REQUIRED\n\t>\n\n<!ELEMENT fileSystem ((host)*)>\n<!ATTLIST fileSystem\n        name CDATA #REQUIRED\n\texecuteDir CDATA #REQUIRED\n\tbinaryDir CDATA #REQUIRED\n\tresultsDir CDATA #REQUIRED\n\t>\n\n<!ELEMENT host (#PCDATA)>\n<!ATTLIST host\n\thostName CDATA #REQUIRED\n\tuserName CDATA #REQUIRED>\n\n"
  },
  {
    "path": "prism/etc/README.txt",
    "content": "This directory contains the following files.\r\nWhere appropriate, comments/instructions are included in the files themselves.\r\n\r\n * icons/ - PRISM icons for shortcuts/etc.\r\n   - p*.png - Variously sized PNGs\r\n   - prism.ico - Windows icon file\r\n\r\n * scripts/ - Various useful scripts\r\n   - prism2html - converts PRISM models/properties to HTML\r\n   - prism2latex - converts PRISM models/properties to LaTex\r\n   - prism3to4 - fixes some common problems in old (3.x and earlier) PRISM models\r\n   - prism-statra - combines a PRISM .sta and .tra file into one file\r\n     (these scripts run on Linux/Unix/OS X and require prism to be in your path)\r\n   - prism-filler.py - automates filling a text file (e.g. latex) with results\r\n     from log files. This script requires Python, run it without arguments for\r\n     more help.\r\n   - bash-prism-completion.sh - Bash programmable completion for PRISM,\r\n     automatically completes options for PRISM when run in Bash.\r\n   - prism-auto - automates PRISM execution for testing/benchmarking\r\n   - prism-test - automates running PRISM in test mode\r\n   - prism-install-* - install scripts for building PRISM on clean OS installs\r\n\r\n * scripts/hoa/ - Scripts for attaching external LTL-to-automaton translators\r\n   to PRISM via the HOA (Hanoi Omega Automata) format. See:\r\n   https://www.prismmodelchecker.org/manual/ConfiguringPRISM/AutomataGeneration\r\n\r\n * syntax-highlighters/ - Syntax highlighting configs for various tools\r\n   - gnome/{Overrides.xml,prism.lang} - files for Gnome environment\r\n   - nedit/prism.pats - files for NEdit editor\r\n   \r\n * prism.css - CSS style file for PRISM-generated HTML code\r\n\r\n * prism.tex - LaTeX file for PRISM-generated LaTeX code\r\n \r\n * prism-eclipse-formatter.xml - Eclipse Java code formatting definitions\r\n"
  },
  {
    "path": "prism/etc/intellij/PrismCL.xml",
    "content": "<component name=\"ProjectRunConfigurationManager\">\n  <configuration default=\"false\" name=\"PrismCL\" type=\"Application\" factoryName=\"Application\">\n    <option name=\"MAIN_CLASS_NAME\" value=\"prism.PrismCL\" />\n    <module name=\"prism\" />\n    <option name=\"VM_PARAMETERS\" value=\"-Djava.library.path=$PROJECT_DIR$/prism/lib\" />\n    <option name=\"WORKING_DIRECTORY\" value=\"$PROJECT_DIR$/prism\" />\n    <method v=\"2\">\n      <option name=\"Make\" enabled=\"true\" />\n    </method>\n  </configuration>\n</component>\n"
  },
  {
    "path": "prism/etc/intellij/install.sh",
    "content": "#!/bin/bash\n\n# Path logic\nSCRIPT_DIR=\"$(cd \"$(dirname \"$0\")\" && pwd)\"\nPROJECT_ROOT=\"$(cd \"$SCRIPT_DIR/../../..\" && pwd)\"\n\n# Check for force flag\nFORCE=false\nfor arg in \"$@\"; do\n  if [ \"$arg\" == \"--force\" ] || [ \"$arg\" == \"-f\" ]; then\n    FORCE=true\n  fi\ndone\n\n# Check for symlink flag\nSYMLINK=false\nfor arg in \"$@\"; do\n  if [ \"$arg\" == \"--symlink\" ] || [ \"$arg\" == \"-s\" ]; then\n    SYMLINK=true\n  fi\ndone\n\ncopy_file() {\n    local src=\"$1\"\n    local dest=\"$2\"\n\tlocal display_path=${dest#\"$PROJECT_ROOT/\"}\n    if [ -f \"$dest\" ] && [ \"$FORCE\" = false ]; then\n        echo \"⚠️  Skipping $display_path (already exists). Use -f to overwrite.\"\n    else\n\t    if [ \"$SYMLINK\" = false ]; then\n            cp \"$src\" \"$dest\" && echo \"✅ Installed $display_path\"\n\t\telse\n\t\t    rm \"$dest\" && ln -s \"$src\" \"$dest\" && echo \"✅ Installed $display_path (symlink)\"\n    \tfi\n    fi\n}\n\necho \"🚀 Setting up IntelliJ configuration for PRISM...\"\n\n# Ensure directories exist\nmkdir -p \"$PROJECT_ROOT/.idea/libraries\"\nmkdir -p \"$PROJECT_ROOT/.idea/runConfigurations\"\n\n# Execute copies\necho \"Project root: $PROJECT_ROOT\"\ncopy_file \"$SCRIPT_DIR/prism.iml\" \"$PROJECT_ROOT/prism.iml\"\ncopy_file \"$SCRIPT_DIR/modules.xml\" \"$PROJECT_ROOT/.idea/modules.xml\"\ncopy_file \"$SCRIPT_DIR/lib.xml\" \"$PROJECT_ROOT/.idea/libraries/lib.xml\"\ncopy_file \"$SCRIPT_DIR/PrismCL.xml\" \"$PROJECT_ROOT/.idea/runConfigurations/PrismCL.xml\"\n\necho -e \"Done. Now open the project in IntelliJ IDEA.\"\n"
  },
  {
    "path": "prism/etc/intellij/lib.xml",
    "content": "<component name=\"libraryTable\">\n  <library name=\"lib\">\n    <CLASSES>\n      <root url=\"file://$PROJECT_DIR$/prism/lib\" />\n    </CLASSES>\n    <JAVADOC />\n    <NATIVE>\n      <root url=\"file://$PROJECT_DIR$/prism/lib\" />\n    </NATIVE>\n    <SOURCES>\n      <root url=\"file://$PROJECT_DIR$/prism/lib\" />\n    </SOURCES>\n    <jarDirectory url=\"file://$PROJECT_DIR$/prism/lib\" recursive=\"false\" />\n    <jarDirectory url=\"file://$PROJECT_DIR$/prism/lib\" recursive=\"false\" type=\"SOURCES\" />\n  </library>\n</component>\n"
  },
  {
    "path": "prism/etc/intellij/modules.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<project version=\"4\">\n  <component name=\"ProjectModuleManager\">\n    <modules>\n      <module fileurl=\"file://$PROJECT_DIR$/prism.iml\" filepath=\"$PROJECT_DIR$/prism.iml\" />\n    </modules>\n  </component>\n</project>"
  },
  {
    "path": "prism/etc/intellij/prism.iml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<module type=\"JAVA_MODULE\" version=\"4\">\n  <component name=\"NewModuleRootManager\">\n    <output url=\"file://$MODULE_DIR$/prism/classes\" />\n    <output-test url=\"file://$MODULE_DIR$/prism/classes\" />\n    <exclude-output />\n    <content url=\"file://$MODULE_DIR$\">\n      <sourceFolder url=\"file://$MODULE_DIR$/prism/src\" isTestSource=\"false\" />\n      <sourceFolder url=\"file://$MODULE_DIR$/prism/unit-tests\" isTestSource=\"true\" />\n      <sourceFolder url=\"file://$MODULE_DIR$/prism/images\" type=\"java-resource\" relativeOutputPath=\"images\" />\n      <excludeFolder url=\"file://$MODULE_DIR$/prism/classes\" />\n    </content>\n    <orderEntry type=\"inheritedJdk\" />\n    <orderEntry type=\"sourceFolder\" forTests=\"false\" />\n    <orderEntry type=\"library\" name=\"lib\" level=\"project\" />\n  </component>\n</module>"
  },
  {
    "path": "prism/etc/jars/README.md",
    "content": "Local (Gradle-based) management of dependent jars, kept in `lib`\n\nTo find dependencies and copy into `lib`:\n\n* `gradle -p etc/jars syncLibs`\n\nTo see what changed:\n\n* `git diff lib`\n\nTo remove files in `lib` in order to re-run:\n\n* `gradle -p etc/jars cleanLibs`\n\nTo print dependency tree:\n\n* `gradle -p etc/jars dependencies --configuration runtimeClasspath`\n\n"
  },
  {
    "path": "prism/etc/jars/build.gradle",
    "content": "// Gradle-based download of dependency jars\n\nplugins {\n    id 'java'\n}\n\njava {\n    sourceCompatibility = JavaVersion.VERSION_1_9\n    targetCompatibility = JavaVersion.VERSION_1_9\n}\n\nrepositories {\n    mavenCentral()\n}\n\nconfigurations {\n    // Bucket for the JUnit standalone runner\n    testRunner\n}\n\nconfigurations.all {\n    // Detect conflicts in JAR dependencies\n    resolutionStrategy {\n        failOnVersionConflict()\n        // Resolve JAR issue (JAS 2.7.200 may pull in too new log4j)\n        force 'org.apache.logging.log4j:log4j-api:2.24.0'\n        force 'org.apache.logging.log4j:log4j-core:2.24.0'\n    }\n}\n\n// Libraries not on Maven Central\n// Get from prismmodelchecker.org and cache in local-libs\n\ndef prismJarBaseUrl = \"https://www.prismmodelchecker.org/other/\"\ndef prismJarStashDir = file(\"local-libs\")\n\ndef customJars = [\n    \"jhoafparser-1.1.1.jar\",\n    \"epsgraphics-1.0.0.jar\",\n    \"nailgun-server-0.9.2-SNAPSHOT.jar\",\n    \"pepa.jar\"\n]\n\ntasks.register('downloadPrismJars') {\n    group = \"PRISM\"\n    description = \"Downloads non-Maven jars from the PRISM website.\"\n    \n    doLast {\n        if (!prismJarStashDir.exists()) prismJarStashDir.mkdirs()\n        \n        customJars.each { jarName ->\n            def destFile = new File(prismJarStashDir, jarName)\n            if (!destFile.exists()) {\n                println \"Downloading ${jarName}...\"\n                ant.get(src: \"${prismJarBaseUrl}${jarName}\", dest: destFile)\n            }\n        }\n    }\n}\n\n// Main dependencies\n\ndependencies {\n\n    // Colt (random number generation for simulator)\n    implementation 'colt:colt:1.2.0'\n    // JAS: Java Algebra System (parametric engine)\n    implementation(\"de.uni-mannheim.rz.krum:jas:2.7.200\")\n    // GSON (JSON reading/writing for UMB)\n    implementation 'com.google.code.gson:gson:2.11.0'\n    // Compression libraries (for import/export, e.g., UMB)\n    implementation 'org.apache.commons:commons-compress:1.24.0'\n    implementation 'org.tukaani:xz:1.10'\n    // fastutil (fast data structures, e.g., UMB import/export)\n    implementation 'it.unimi.dsi:fastutil:8.5.15'\n    // JFreeChart (graph plotting in GUI)\n    implementation 'org.jfree:jfreechart:1.0.14'\n    \n    // Log4j (needed by JAS, possibly others)\n    implementation 'org.apache.logging.log4j:log4j-api:2.24.0'\n    implementation 'org.apache.logging.log4j:log4j-core:2.24.0'\n    \n    //implementation(\"com.martiansoftware:nailgun-server:0.9.1\")\n\n    // JUnit: for simplicity, don't put in separate test group for now\n    implementation 'org.junit.platform:junit-platform-console-standalone:1.7.2'\n    //testRunner 'org.junit.platform:junit-platform-console-standalone:1.9.3'\n    \n    // Grab anything we can't find online from our local stash\n    implementation fileTree(dir: 'local-libs', include: ['*.jar'])\n}\n\ntasks.register('syncLibs', Copy) {\n    group = \"PRISM\"\n    description = \"Downloads and copies JAR dependencies into the lib/ folder.\"\n\n    dependsOn 'downloadPrismJars'\n    \n    // 1. Production Libs\n    from(configurations.runtimeClasspath) {\n        into \"lib\" \n    }\n\n    // 2. Test Libs\n    from(configurations.testRunner) {\n        into \"lib/test\"\n    }\n    \n    // 3. Clean up version numbers (Optional)\n    // If your Makefile expects 'gson.jar' instead of 'gson-2.11.0.jar', \n    // uncomment the line below:\n    // rename { it.replaceAll(/-\\d+\\..*jar$/, \".jar\") }\n\n    // Anchor this task to the parent parent directory (prism/)\n    destinationDir = file(\"../..\") \n\n    // Optional: This ensures the task always runs if you call it,\n    // preventing Gradle from saying \"Up-to-Date\" if you've manually deleted a JAR.\n    outputs.upToDateWhen { false }\n}\n\ntasks.register('cleanLibs', Delete) {\n    group = \"PRISM\"\n    description = \"Deletes all JARs in the lib/ and lib/test/ folders.\"\n    delete fileTree(\"../../lib\") { include \"*.jar\" }\n    delete \"../../lib/test\"\n}\n"
  },
  {
    "path": "prism/etc/jars/settings.gradle",
    "content": "rootProject.name = 'prism-dependency-manager'\n"
  },
  {
    "path": "prism/etc/prism-eclipse-formatter.xml",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" standalone=\"no\"?>\n<profiles version=\"11\">\n<profile kind=\"CodeFormatterProfile\" name=\"PRISM\" version=\"11\">\n<setting id=\"org.eclipse.jdt.core.formatter.comment.insert_new_line_before_root_tags\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.disabling_tag\" value=\"@formatter:off\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_annotation\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_parameters\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_type_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_arguments\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_anonymous_type_declaration\" value=\"next_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_colon_in_case\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_brace_in_array_initializer\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.new_lines_at_block_boundaries\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_in_empty_annotation_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_before_closing_brace_in_array_initializer\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_annotation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_before_field\" value=\"0\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_while\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.use_on_off_tags\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_annotation_type_member_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_before_else_in_if_statement\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_prefix_operator\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.keep_else_statement_on_same_line\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_ellipsis\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.insert_new_line_for_parameter\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_annotation_type_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_breaks_compare_to_cases\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_multiple_fields\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_expressions_in_array_initializer\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_conditional_expression\" value=\"80\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_for\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_binary_operator\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_question_in_wildcard\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_array_initializer\" value=\"end_of_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_enum_constant\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_before_finally_in_try_statement\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_local_variable\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_before_catch_in_try_statement\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_while\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_after_package\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_type_parameters\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.continuation_indentation\" value=\"2\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_postfix_operator\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_arguments_in_method_invocation\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_arguments\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_superinterfaces\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_before_new_chunk\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_binary_operator\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_before_package\" value=\"0\"/>\n<setting id=\"org.eclipse.jdt.core.compiler.source\" value=\"1.5\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_constant_arguments\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_constructor_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.format_line_comments\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_arguments\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_enum_declarations\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.join_wrapped_lines\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_block\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_arguments_in_explicit_constructor_call\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_invocation_arguments\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_before_member_type\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.align_type_members_on_columns\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_enum_constant\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_for\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_method_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_selector_in_method_invocation\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_switch\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_unary_operator\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_colon_in_case\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.indent_parameter_description\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_switch\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_parameters\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_in_empty_type_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_block_comment\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.lineSplit\" value=\"160\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_if\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_between_brackets_in_array_type_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_parenthesized_expression\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_explicitconstructorcall_arguments\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_constructor_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_before_first_class_body_declaration\" value=\"0\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indentation.size\" value=\"4\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.enabling_tag\" value=\"@formatter:on\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_enum_constant\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_superclass_in_type_declaration\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_assignment\" value=\"0\"/>\n<setting id=\"org.eclipse.jdt.core.compiler.problem.assertIdentifier\" value=\"error\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.tabulation.char\" value=\"tab\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_parameters\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_prefix_operator\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_statements_compare_to_body\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_before_method\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.wrap_outer_expressions_when_nested\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.format_guardian_clause_on_one_line\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_colon_in_for\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_cast\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_parameters_in_constructor_declaration\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_colon_in_labeled_statement\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_annotation_type_declaration\" value=\"end_of_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_in_empty_method_body\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_method_declaration\" value=\"0\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_method_invocation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_allocation_expression\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_enum_constant\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_annotation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_at_in_annotation_type_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_throws\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_if\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_switch\" value=\"end_of_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_throws\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_return\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_question_in_conditional\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_question_in_wildcard\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_allocation_expression\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_parenthesized_expression_in_throw\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_type_arguments\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.compiler.problem.enumIdentifier\" value=\"error\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_switch\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_ellipsis\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_block\" value=\"end_of_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_inits\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_method_declaration\" value=\"next_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.compact_else_if\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_array_initializer\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_increments\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.format_line_comment_starting_on_first_column\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_bracket_in_array_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_enum_constant\" value=\"end_of_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.indent_root_tags\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_declarations\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_explicitconstructorcall_arguments\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_switch\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_superinterfaces\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_method_declaration_parameters\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_allocation_expression\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.tabulation.size\" value=\"4\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_type_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_after_opening_brace_in_array_initializer\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_closing_brace_in_block\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_constant\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_arguments\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_constructor_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_if\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_throws\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.clear_blank_lines_in_javadoc_comment\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_constructor_declaration\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_assignment_operator\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_assignment_operator\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_empty_lines\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_synchronized\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_closing_paren_in_cast\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_declaration_parameters\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_block_in_case\" value=\"end_of_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.number_of_empty_lines_to_preserve\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_catch\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_constructor_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_method_invocation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_bracket_in_array_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_and_in_type_parameter\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_arguments_in_qualified_allocation_expression\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.compiler.compliance\" value=\"1.5\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.continuation_indentation_for_array_initializer\" value=\"2\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_between_empty_brackets_in_array_allocation_expression\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_at_in_annotation_type_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_arguments_in_allocation_expression\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_cast\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_unary_operator\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_parameterized_type_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_anonymous_type_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.keep_empty_array_initializer_on_one_line\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_in_empty_enum_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.keep_imple_if_on_one_line\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_constructor_declaration_parameters\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_closing_angle_bracket_in_type_parameters\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_at_end_of_file_if_missing\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_colon_in_for\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_colon_in_labeled_statement\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_parameterized_type_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_type_declaration\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_binary_expression\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_enum_declaration\" value=\"end_of_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_while\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.compiler.codegen.inlineJsrBytecode\" value=\"enabled\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.put_empty_statement_on_new_line\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_after_label\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_parameter\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_type_parameters\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_method_invocation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_before_while_in_do_statement\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_arguments_in_enum_constant\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.format_javadoc_comments\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.line_length\" value=\"120\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_between_import_groups\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_enum_constant_arguments\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_semicolon\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_constructor_declaration\" value=\"next_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.number_of_blank_lines_at_beginning_of_method_body\" value=\"0\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_colon_in_conditional\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_type_header\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_annotation_type_member_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.wrap_before_binary_operator\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_declaration_header\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_between_type_declarations\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_synchronized\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_statements_compare_to_block\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_superinterfaces_in_enum_declaration\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.join_lines_in_comments\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_question_in_conditional\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_field_declarations\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_compact_if\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_for_inits\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_switchstatements_compare_to_cases\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_array_initializer\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_colon_in_default\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_and_in_type_parameter\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_between_empty_parens_in_constructor_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_before_imports\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_colon_in_assert\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.format_html\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_throws_clause_in_method_declaration\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_angle_bracket_in_type_parameters\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_bracket_in_array_allocation_expression\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_in_empty_anonymous_type_declaration\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_colon_in_conditional\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_angle_bracket_in_parameterized_type_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_for\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_postfix_operator\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.format_source_code\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_synchronized\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_allocation_expression\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_constructor_declaration_throws\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_parameters_in_method_declaration\" value=\"16\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_brace_in_array_initializer\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.compiler.codegen.targetPlatform\" value=\"1.5\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.use_tabs_only_for_leading_indentations\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_arguments_in_annotation\" value=\"0\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_after_annotation_on_member\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.format_header\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.format_block_comments\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_enum_constant\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.alignment_for_enum_constants\" value=\"0\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_new_line_in_empty_block\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_annotation_declaration_header\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_parenthesized_expression\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_parenthesized_expression\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_catch\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_multiple_local_declarations\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_switch\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_comma_in_for_increments\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_invocation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_colon_in_assert\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.brace_position_for_type_declaration\" value=\"next_line\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_brace_in_array_initializer\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_between_empty_braces_in_array_initializer\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_opening_paren_in_method_declaration\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_semicolon_in_for\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_paren_in_catch\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_parameterized_type_reference\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_field_declarations\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_closing_paren_in_annotation\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_parameterized_type_reference\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_method_invocation_arguments\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.comment.new_lines_at_javadoc_boundaries\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.blank_lines_after_imports\" value=\"1\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_comma_in_multiple_local_declarations\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.indent_body_declarations_compare_to_enum_constant_header\" value=\"true\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_after_semicolon_in_for\" value=\"insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.never_indent_line_comments_on_first_column\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.insert_space_before_opening_angle_bracket_in_type_arguments\" value=\"do not insert\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.never_indent_block_comments_on_first_column\" value=\"false\"/>\n<setting id=\"org.eclipse.jdt.core.formatter.keep_then_statement_on_same_line\" value=\"false\"/>\n</profile>\n</profiles>\n"
  },
  {
    "path": "prism/etc/prism.css",
    "content": ".prismkeyword { font-weight:bold }\n.prismident { color:#cc0000 }\n.prismnum { color:#0000cc }\n.prismcomment { font-style:italic; color:#009900 }\n.prismpreproc { color:#a020f0; }\n\n"
  },
  {
    "path": "prism/etc/prism.tex",
    "content": "\\newcommand{\\prismcomment}[1]{\\mbox{\\em #1}}\n\\newcommand{\\prismkeyword}[1]{\\mathtt{#1}}\n\\newcommand{\\prismident}[1]{\\mathit{#1}}\n\\newcommand{\\prismtab}{\\hspace*{0.5cm}}\n"
  },
  {
    "path": "prism/etc/scripts/bash_prism_completion.sh",
    "content": "#A script with programmable completion for BASH\n#In order to apply it, put a line \"source path/to/this/script\" somewhere where it gets executed every time you start bash, e.g. in ~/.profile \n\n#Features\n#* completion of switches. Just type hyphen and hit TAB twice\n#* completion of constants. If a model name was specified, hit TAB twice when you are specifying a parameter to -const switch\n#* completion for -{pta,scc,sim}method switch parameters\n\n_prismcomplete() {\n\tlocal cur prev MODELFILE PROPFILE curconst preconst CONSTANTS PARS SWITCHES\n\tCOMPREPLY=()\n\tcur=\"${COMP_WORDS[COMP_CWORD]}\"\n\tprev=\"${COMP_WORDS[COMP_CWORD-1]}\"\n\n\tif [ \"$prev\" = -const ]; then\n\n\t\t#get the name of the model\n\t\tMODELFILE=`echo $COMP_LINE | grep -E -o \"[^ ]*[.]([psn]m|smg) \" | sed \"s/ ^//\"`\n\t\t#expand tilde\n\t\tMODELFILE=`eval echo $MODELFILE`\n\t\t#check if model has been specified and is valid\n\t\ttest -n \"$MODELFILE\"|| return 0;\n\t\ttest -e $MODELFILE || return 0; \n\n\t\t#get the parts after/before the last comma\n\t\tcurconst=`echo $cur | sed \"s/.*,\\([^,]*\\)$/\\\\1/\"`\n\t\tpreconst=`echo $cur | sed \"s/[^,]*$//\" | sed \"s/.*[=]//\"` \n\n\t\t#check if we are after = sign, which means that we don't autocomplete\n\t\t(echo $curconst | grep -q \"=\") && return 1;\n\n\t\t#get a list of constants from the model file\n\t\tCONSTANTS=`grep \"^[ \\t]*const \" $MODELFILE | sed \"s/.*const[ ]*\\([^=;]*\\)[\\=;].*/\\\\1/\" | sed \"s/[^ ]* \\([^ ]*\\)[ ]*/\\\\1=/\"`\n\n\t\tCOMPREPLY=( `compgen -W \"$CONSTANTS\" -- $curconst` )\n\t\t\n\t\tCOMPREPLY=(\"${COMPREPLY[@]/#/$preconst}\")\n\t\treturn 0;\n\tfi;\n\n\tif [ \"$prev\" = -property ]; then\n\t\n\t\tPROPFILE=`echo $COMP_LINE | grep -E -o \"[^ ]*[.](pctl|props)\" | sed \"s/ ^//\"`\n\t\tPROPFILE=`eval echo $PROPFILE`\n\t\ttest -n \"$PROPFILE\"|| return 0;\n\t\ttest -e $PROPFILE || return 0; \n\t\n\t\t#get the number of properties\n\t\tSEQUENCE=`sed \"s/\\/\\/.*//\" $PROPFILE | grep \"[a-z]\" | awk '{print NR, \" \", $0}' | sed \"s/^[0-9]*[^\\\\\"]*\\\\\"\\(.*\\)\\\\\":.*/\\\\1/\" | sed \"s/^\\([0-9][0-9]*\\).*$/\\\\1/\"`\n\t\n\t\tCOMPREPLY=( `compgen -W \"$SEQUENCE\" -- $cur` )\n\t\tCOMPREPLY=(\"${COMPREPLY[@]/%/ }\")\n\t\treturn 0;\n\tfi;\n\n\tif [ \"$prev\" = -simmethod ]; then\n\t\tPARS=\"ci aci apmc sprt\"\n\t\tCOMPREPLY=( `compgen -W \"$PARS\" -- $cur` )\n\t\tCOMPREPLY=(\"${COMPREPLY[@]/%/ }\")\n\t\treturn 0;\n\tfi;\n\n\tif [ \"$prev\" = -ptamethod ]; then\n\t\tPARS=\"games digital\"\n\t\tCOMPREPLY=( `compgen -W \"$PARS\" -- $cur` )\n\t\tCOMPREPLY=(\"${COMPREPLY[@]/%/ }\")\n\t\treturn 0;\n\tfi;\n\n\tif [ \"$prev\" = -sccmethod ]; then\n\t\tPARS=\"xiebeerel lockstep sccfind\"\n\t\tCOMPREPLY=( `compgen -W \"$PARS\" -- $cur` )\n\t\tCOMPREPLY=(\"${COMPREPLY[@]/%/ }\")\n\t\treturn 0;\n\tfi;\n\tif [[ $cur == -* ]] ; then\n\t\tSWITCHES=\"-noprob0 -noprob1 -help -version -pctl -property -const -steadystate -transient -simpath -nobuild -test -testall -importpepa -importtrans -importstates -importlabels -importinitdist -dtmc -ctmc -mdp -exportresults -exporttrans -exportstaterewards -exporttransrewards -exportrewards -exportstates -exportlabels -exportmatlab -exportmrmc -exportrows -exportordered -exportunordered -exporttransdot -exporttransdotstates -exportdot -exportbsccs -exportsteadystate -exporttransient -exportprism -exportprismconst -mtbdd -m -sparse -s -hybrid -h -ptamethod -power -jacobi -gaussseidel -bgaussseidel -pgaussseidel -bpgaussseidel -jor -sor -bsor -psor -bpsor -omega -relative -absolute -epsilon -maxiters -nopre -fair -nofair -fixdl -noprobchecks -zerorewardcheck -nossdetect -sccmethod -symm -aroptions -exportadv -exportadvmdp -verbose -extraddinfo -extrareachinfo -nocompact -sbl -sbmax -gsl -gsmax -cuddmaxmem -cuddepsilon -sim -simmethod -simsamples -simconf -simwidth -simapprox -simmanual -simvar -simmaxrwd -simpathlen\"\n\t\tCOMPREPLY=( `compgen -W \"$SWITCHES\" -- $cur` )\n\t\tCOMPREPLY=(\"${COMPREPLY[@]/%/ }\")\n\t\treturn 0;\n\tfi;\n\t#COMPREPLY=( `compgen -A file -- $cur` )\n\treturn 0;\n}\n\ncomplete -o nospace -F _prismcomplete -o default prism\n\n"
  },
  {
    "path": "prism/etc/scripts/hoa/hoa-library-for-prism",
    "content": "#! /usr/bin/perl -w\n\n# For usage notes see end of file or run hoa-library-for-prism without parameters.\n\nuse strict;\n\nuse File::Spec;\nuse Pod::Usage;\n\nif (scalar @ARGV != 2) {\n    pod2usage(2);\n}\n\nmy $formula_file = shift;\nmy $output_file = shift;\n\nmy $hoa_lib_dir = \"hoa-lib\";\nif (defined $ENV{HOA_LIB}) {\n    $hoa_lib_dir = $ENV{HOA_LIB};\n}\n\nif (!open(IN, \"<\", $formula_file)) {\n    print \"Can not file '$formula_file' for reading formula: $!\\n\"; exit(1);\n}\nmy $formula = <IN>;\nif (!defined $formula) {\n    print \"No formula read from file '$formula_file'\\n\"; exit(1);\n}\nwhile (<IN>) {\n    chomp();  # remove \\n at end of line\n    next if (/^\\s*$/);   # ok if there is only whitespace\n    print \"Garbage at end of formula file '$formula_file': $_\"; exit(1);\n}\n\nchomp($formula);\n$formula =~ s/\\s+/ /g;  # multiple whitspace -> single space\n$formula =~ s/^\\s*//;   # trim whitespace in front\n$formula =~ s/\\s*//;    # trim whitespace in back\n\nmy $filename = $formula;\n$filename =~ s/ /_/g;   # replace spaces with _\n$filename.='.hoa';      # append .hoa suffix\n\n$filename = File::Spec->catfile($hoa_lib_dir, $filename);\n\nif (-f $filename) {\n    if (!open(IN, \"<\", $filename)) {\n\tprint \"Can not open file '$filename' for formula '$formula': $!\\n\"; exit(1);\n    }\n    if (!open(OUT, \">\", $output_file)) {\n\tprint \"Can not open file '$output_file' for writing the automaton: $!\\n\"; exit(1);\n    }\n    while (<IN>) {\n\tprint OUT $_;\n    }\n    close(IN);\n    close(OUT);\n    exit(0);\n} else {\n    print \"Can not find file '$filename' corresponding to formula '$formula': $!\\n\";\n    exit(1);\n}\n\n\n\n__END__\n\n=head1 NAME\n\nhoa-library-for-prism - Script to lookup formulas from a library and return a HOA automaton\n\n=head1 SYNOPSIS\n\nhoa-library-for-prism formula-file output-file\n\nReads a single-line formula from I<formula-file>, transforms the\nformula (in LBT format) into a filename and looks for a corresponding\n.hoa file in the I<library directory>. If this file exists, the\ncontent is written to I<output-file> and the script exits with exit\nvalue 0.\n\nBy default, the I<library-directory> is I<hoa-lib>. The directory can\nbe set to a custom value by setting the environment variable HOA_LIB,\ne.g.,\n\n  export HOA_LIB=path/to/library\n\nThe formula is transformed to a filename as follows. First, all\nwhitespace in front and in the back is stripped and multiple\nwhitespace characters are combined to a single one. Then, all\nwhitespaces are replaced by underscore (_) characters. Finally, the\nsuffix '.hoa' is appended. As an example, the formula\n\n    G F U p0 p1\n\nis transformed to the filename\n\n    G_F_U_p0_p1.hoa\n\n\n"
  },
  {
    "path": "prism/etc/scripts/hoa/hoa-ltl2dstar-for-prism",
    "content": "#! /bin/bash\n\n# Interface wrapper for calling ltl2dstar\n# Invoke from PRISM with\n#  -ltl2datool hoa-ltl2dstar-for-prism -ltl2dasyntax lbt\n\n# Expects the ltl2dstar executable to be on the PATH, otherwise specify its location using\n#  export LTL2DSTAR=path/to/ltl2dstar\n\n# ---\n\n# ltl2dstar needs an LTL->NBA tool\n# We default to Spot's ltl2tgba\n# Comment/uncomment the blocks below to replace with \n# As above, specify the paths to the executables as needed\n\n# Spot's ltl2tgba as the LTL->NBA tool\n# Take the ltl2tgba executable from the LTL2TGBA environment variable\n# Otherwise, default to \"ltl2tgba\", which will search the PATH\nLTL2TGBA_BIN=${LTL2TGBA-ltl2tgba}\n# ltl2tgba args: -s -B = as Spin neverclaim, NBA output\nLTL2NBA_CMD=\"--ltl2nba=spin:${LTL2TGBA_BIN}@-s -B\"\n\n# # ltl2ba as the LTL->NBA tool\n# # Take the ltl2ba executable from the LTL2BA environment variable\n# #  export LTL2BA=path/to/ltl2ba\n# # Otherwise, default to \"ltl2ba\", which will search the PATH\n# LTL2BA_BIN=${LTL2BA-ltl2ba}\n# LTL2NBA_CMD=\"--ltl2nba=spin:$LTL2BA_BIN\"\n\n# # ltl3ba as the LTL->NBA tool\n# # Take the ltl3ba executable from the LTL3BA environment variable\n# # Otherwise, default to \"ltl3ba\", which will search the PATH\n# LTL3BA_BIN=${LTL3BA-ltl3ba}\n# LTL2NBA_CMD=\"--ltl2nba=spin:$LTL3BA_BIN\"\n\n# ---\n\n# Take ltl2dstar executable from the LTL2DSTAR environment variable\n# Otherwise, default to \"ltl2dstar\", which will search the PATH\nLTL2DSTAR_BIN=${LTL2DSTAR-ltl2dstar}\n\n# --output=automaton = we want the automaton\n# --output-format=hoa = ... in HOA\n$LTL2DSTAR_BIN --output=automaton --output-format=hoa \"$LTL2NBA_CMD\" \"$@\"\n"
  },
  {
    "path": "prism/etc/scripts/hoa/hoa-ltl2tgba-for-prism",
    "content": "#! /bin/bash\n\n# Interface wrapper for calling Spot's ltl2tgba\n# Invoke from PRISM with\n#  -ltl2datool hoa-ltl2tgba-for-prism -ltl2dasyntax lbt\n\n# Expects the ltl2tgba executable to be on the PATH, otherwise specify its location using\n#  export LTL2TGBA=path/to/ltl2tgba\n\n# Take the ltl2tgba executable from the LTL2TGBA environment variable\n# Otherwise, default to \"ltl2tgba\", which will search the PATH\nLTL2TGBA_BIN=${LTL2TGBA-ltl2tgba}\n\n# --output=automaton = we want the automaton\n# --output-format=hoa = ... in HOA\n$LTL2TGBA_BIN --file=\"$1\" --lbt-input --hoaf --output=\"$2\" --generic --deterministic --complete\n"
  },
  {
    "path": "prism/etc/scripts/hoa/hoa-ltl3dra-for-prism",
    "content": "#! /bin/bash\n\n# Interface wrapper for calling ltl3dra\n# Invoke from PRISM with\n#  -ltl2datool hoa-ltl3dra-for-prism -ltl2dasyntax spin\n#\n# Expects the ltl3dra on the PATH, otherwise specify its location using\n#  export LTL3DRA=path/to/ltl3dra\n#\n# Expects the dynamic buddy library to be in the library PATH,\n# otherwise specify its location using\n#  export BUDDY_LIB=path/to/buddy-lib-dir\n\n# Take ltl3dra executable from the LTL3DRA environment variable\n# Otherwise, default to \"ltl3dra\", which will search the PATH\nLTL3DRA_BIN=${LTL3DRA-ltl3dra}\n\n# If BUDDY_LIB environment variable is set, add to appropriate path\nif [ ! -z \"$BUDDY_LIB\" ]; then\n    if [ \"$(uname)\" == \"Darwin\" ]; then\n\texport DYLD_LIBRARY_PATH=\"$DYLD_LIBRARY_PATH\":\"$BUDDY_LIB\"\n    else\n\texport LD_LIBRARY_PATH=\"$DYLD_LIBRARY_PATH\":\"$BUDDY_LIB\"\n    fi\nfi\n\n# Change the switch accordingly to get state-based Rabin\n# or transition-based generalized-Rabin automata\n# -H2 = output deterministic transition-based generalized-Rabin in HOA format\n# -H3 = output deterministic state-based Rabin in HOA format\n$LTL3DRA_BIN -H3 -F \"$1\" > \"$2\"\n"
  },
  {
    "path": "prism/etc/scripts/hoa/hoa-rabinizer-for-prism",
    "content": "#! /bin/bash\n\n# Interface wrapper for calling Rabinizer (version 4)\n# Invoke from PRISM with\n#  -ltl2datool hoa-rabinizer-for-prism -ltl2dasyntax rabinizer\n#\n# Expects the ltl2dra executable to be on the PATH, otherwise specify its location using\n# specify its location using\n#  export RABINIZER_LTL2DRA=path/to/ltl2dra\n\n# Take the  executable from the RABINIZER_LTL2DRA environment variable\n# Otherwise, default to \"ltl2dra\", which will search the PATH\nRABINIZER_LTL2DRA_BIN=${RABINIZER_LTL2DRA-ltl2dra}\n\n$RABINIZER_LTL2DRA_BIN --filein \"$1\" --fileout=\"$2\" --complete\n"
  },
  {
    "path": "prism/etc/scripts/hoa/hoa-rabinizer-for-prism.bat",
    "content": "@echo off\n\nrem Interface wrapper for calling Rabinizer (version 4)\nrem Invoke from PRISM with\nrem   -ltl2datool hoa-rabinizer-for-prism.bat -ltl2dasyntax rabinizer\n\nrem Expects the ltl2dra executable to be on the PATH, otherwise specify its location below\n \nltl2dra.bat --filein \"%1\" --fileout=\"%2\" --complete\n"
  },
  {
    "path": "prism/etc/scripts/prism-auto",
    "content": "#!/usr/bin/env python3\n\n# The prism-auto script automatically executes PRISM on one or more\n# models/properties, for the purposes of benchmarking or testing.\n\n# The simplest usage is just \"prism-auto <target>\" where <target>\n# is a directory, model file or properties file. For a directory,\n# prism-auto finds all models and all properties files in the\n# directory and then executes PRISM on each combination of them.\n# For a model file, it runs against all properties, and vice versa.\n\n# Run \"prism-auto -h\" for details of further options.\n\nimport os,sys,re,subprocess,signal,tempfile,functools,logging,time,platform,csv\nfrom shlex import quote\nfrom optparse import OptionParser\nfrom threading import Timer\n\n#==================================================================================================\n# Global variables\n#==================================================================================================\n\n# statistics about test results\ntestStats = dict(SUCCESS = 0, FAILURE = 0, FAIL_NONCONVERGE = 0, SKIPPED = 0, SKIPPED_EXPORT = 0, SKIPPED_DUPLICATE = 0, SKIPPED_NOT_TESTED = 0, UNSUPPORTED = 0, WARNING = 0, DDWARNING = 0, TIMEOUT = 0)\n\n# colour coding for test results\n# for colour values, see https://en.wikipedia.org/wiki/ANSI_escape_code#Colors\ntestColours = dict(SUCCESS = 32, FAILURE = 31, SKIPPED = 90, UNSUPPORTED = 34, WARNING = 33)\n\n# mapping from PRISM switch shortcuts to the full version (for canonicalisation of arguments)\n# to get a list of abbreviated settings in prism, run   prism --help | grep '(or '\nswitchShortcuts = {\n                   # engines:\n                   '-ex':    '-explicit',\n                   '-m':     '-mtbdd',\n                   '-s':     '-sparse',\n                   '-h':     '-hybrid',\n                   # iteration/solver settings:\n                   '-pow':   '-power',\n                   '-pwr':   '-power',\n                   '-jac':   '-jacobi',\n                   '-gs' :   '-gaussseidel',\n                   '-bgs':   '-bgaussseidel',\n                   '-pgs':   '-pgaussseidel',\n                   '-bpgs':  '-bpgaussseidel',\n                   '-ii':    '-intervaliter',\n                   '-lp':    '-linprog',\n                   # epsilon related settings:\n                   '-rel':   '-relative',\n                   '-abs':   '-absolute',\n                   '-e':     '-epsilon',\n                   # other:\n                   '-ss':    '-steadystate',\n                   '-tr':    '-transient',\n                   '-pctl':  '-pf',\n                   '-csl':   '-pf',\n                   '-prop':  '-property',\n                   }\n\n# set of PRISM argument tuples that already ran\nalreadyRan = set()\n\n#==================================================================================================\n# Utility functions\n#==================================================================================================\n\n# returns true if we are running on Windows\ndef isWindows():\n    s = platform.system()\n    return s == 'Windows' or re.match(r'CYGWIN', s) != None\n\n# compare two files (with filenames f1,f2) for equality\ndef compareFiles(f1,f2):\n    with open(f1, 'r') as fp1, open(f2, 'r') as fp2:\n        while True:\n            s1 = fp1.readline()\n            s2 = fp2.readline()\n            if s1 != s2:  # mismatch\n                return False\n            if s1 == '':  # EOF (in both files)\n                return True\n\n# returns a sorted list of files / directories in dir\ndef sortedListDir(dir):\n    list = os.listdir(dir);\n    list.sort()\n    return list\n\ndef isPrismModelFile(file):\n    return re.match(r'.+(\\.prism|\\.nm|\\.pm|\\.sm)$', file)\n\ndef isPrismPropertiesFile(file):\n    return re.match(r'.+(\\.props|\\.pctl|\\.csl)$', file)\n\ndef isPrismModelListFile(file):\n    return re.match(r'models$', os.path.basename(file))\n\ndef isPrismPropListFile(file):\n    return re.match(r'.+(\\.txt)$', file)\n\ndef isOutFile(file):\n    return re.match(r'.+(\\.out\\.)', file) # Note that this matches anything that contains a .out anywhere in the name\n\ndef isAutoFile(file):\n    return re.match(r'.+(\\.auto)$', file)\n\n# Check whether the given (args|auto) file doesn't have an associated model\n\ndef isOrphan(dir, file):\n    return not getMatchingModelsInDir(dir, file)\n\ndef lineIsCommentedOut(line):\n    return line.startswith('#')\n\n# Get a list of models in a directory, either from a \"models\" file if present,\n# or by searching for all files in the directory with an appropriate extension.\n# A \"models\" file is a list of (relative) path names, in which lines starting with # are ignored.\n# Each item of the returned list is itself a tuple consisting of the name of the model file and\n# a possibly empty argument list, e.g. (\"model.pm\", [\"-const\", \"N=2\"])\n#\n# The name of the \"models\" file is configurable, defaults to \"models\" and is\n# stored in options.modelsFilename\n\ndef getModelsInDir(dir):\n    modelFiles = []\n    # Process \"models\" file, if present\n    if os.path.isfile(os.path.join(dir, options.modelsFilename)):\n        for line in open(os.path.join(dir, options.modelsFilename), 'r').readlines():\n            line = line.strip()\n            if len(line) == 0 or lineIsCommentedOut(line): continue\n            first = 1\n            args = []\n            for item in line.split(' '):\n                if first:\n                    modelFile = item\n                    first = 0\n                else:\n                    args.append(item)\n            modelFiles.append((modelFile, args))\n    # Otherwise look for all model files\n    else:\n        for file in sortedListDir(dir):\n            if os.path.isfile(os.path.join(dir, file)) and isPrismModelFile(file):\n                modelFiles.append((file, []))\n    #print \"Model files in \" + dir + \": \" + ' '.join( map(lambda pair: pair[0], modelFiles ))\n    \n    # If requested, filter the list of models\n    if options.filterModels:\n        modelFiles = filterModels(modelFiles, options.filterModels, dir)\n        \n    # Finally, append the dir name to all the model files\n    modelFiles = map(lambda pair: (os.path.join(dir, pair[0]),pair[1]), modelFiles)\n    \n    return modelFiles\n\n# Restrict a list of models to those satisfying a filter expressed as a string\n# Examples: \"states>100 and states<10000\" or \"model_type=='DTMC'\"\n# Model list is given as pairs of files and argument lists (see getModelsInDir() above)\n# Model data is read in from a file models.csv (or something else if specified\n# using options.modelsInfoFilename)\n\ndef filterModels(modelFiles, filterString, dir):\n    modelFilesNew = []\n    # Filter is false if the model metadata cannot be found\n    if os.path.isfile(os.path.join(dir, options.modelsInfoFilename)):\n        with open(os.path.join(dir, options.modelsInfoFilename), newline='') as csvfile:\n            # Build a list of models matching the filter\n            modelFilesFiltered = []\n            reader = csv.DictReader(csvfile)\n            for row in reader:\n                # Evaluate the filter using eval()\n                # Only provide access to the model type and number of states for now\n                #filterVarsAvailable = ['model_type', 'states']\n                #filterVarsMissing = [key for key in filterVarsAvailable if key in filterString and not row[key]]\n                eval_model_type = row['model_type'] if row['model_type'] else None\n                eval_states = int(row['states']) if row['states'] else None\n                try:\n                    if eval(filterString, {\"__builtins__\": {}}, {'model_type': eval_model_type, 'states': eval_states}):\n                        model = row['model_file']\n                        if 'model_consts' in row and row['model_consts']:\n                            model += ' -const ' + row['model_consts']\n                        modelFilesFiltered.append(model)\n                # If there are any errors evaluating the exception, the filter is false\n                except (Exception):\n                    pass\n        # Restrict models list to ones in the list of filter matches\n        for modelFile in modelFiles:\n            if modelMatches(modelFile, modelFilesFiltered):\n                modelFilesNew.append(modelFile)\n    return modelFilesNew;\n\n# Check if a model is contained in a list of possible matches\n# The model is given as a pairs of files and argument lists\n# (e.g. (\"model.pm\", [\"-const\", \"N=2\", \"-const\", \"K=3\"]))\n# The possible matches are a list of single strings\n# (e.g. \"model.pm -const K=3,N=2\")\n# Constant values are extracted and sorted for a more intelligent match\n\ndef modelMatches(modelFile, possibleMatches):\n    # Extract constant defns from modelFile and sort them\n    consts = getSortedConsts(modelFile[1])\n    # If there are no constants, just check for an exact match in possibleMatches\n    if len(consts) == 0:\n        return modelFile[0] in possibleMatches\n    # Otherwise compare to each model in possibleMatches after first sorting its constant defns\n    for possibleMatch in possibleMatches:\n        # Extract name (there will also be a \" \" since there are >0 constants)\n        possibleMatchModel = possibleMatch[:possibleMatch.index(\" \")]\n        # Extract/sort constants from argument list\n        possibleMatchConsts = getSortedConsts((\"\".join(re.findall(\"-const [^ ]+\", possibleMatch))).split(\" \"))\n        # Compare\n        if modelFile[0] == possibleMatchModel and consts == possibleMatchConsts:\n            return True\n    return False;\n\n# Extract and sort constant values form an argument list specified as a string list,\n# e.g. [\"-const\", \"N=2\", \"-const\", \"K=3\"] would return [\"K=3\", \"N=2\"]\n\ndef getSortedConsts(args):\n    consts = []\n    num_args = len(args)\n    i = 0;\n    while i < num_args:\n        if args[i] == \"-const\" and i+1 < num_args:\n            consts.extend(args[i+1].split(','))\n        i = i+1\n    consts.sort()\n    return consts\n\n# Get a list of all files in the directory that satisfy the given predicate\n\ndef getFilesInDir(dir, pred):\n    resultFiles = []\n    for file in sortedListDir(dir):\n        if os.path.isfile(os.path.join(dir, file)) and pred(file):\n            resultFiles.append(os.path.join(dir, file))\n    return resultFiles\n\n# Return true iff the basename of file in the directory dir starts with prefix\n\ndef startsWith(prefix, dir, file):\n    return os.path.basename(os.path.join(dir, file)).startswith(os.path.basename(prefix))\n\n# Get a list of models in a directory matching a (property|args|auto) file name.\n\ndef getMatchingModelsInDir(dir, fileToMatch):\n    return getFilesInDir(dir, lambda file: isPrismModelFile(file) and startsWith(file, dir, fileToMatch))\n\n# Get a list of properties in a directory, by searching for all files with an appropriate extension.\n\ndef getPropertiesInDir(dir):\n    return getFilesInDir(dir, isPrismPropertiesFile)\n\n# Get a list of properties in a directory with prefix matching a model file name.\n\ndef getMatchingPropertiesInDir(dir, modelFile):\n    return getFilesInDir(dir, lambda file: isPrismPropertiesFile(file) and startsWith(modelFile, dir, file))\n\n# Get a list of auto files in a directory\n\ndef getAutoFilesInDir(dir):\n    return getFilesInDir(dir, isAutoFile)\n\n# Get a list of auto files in a directory with prefix matching a model file name.\n\ndef getMatchingAutoFilesInDir(dir, modelFile):\n    return getFilesInDir(dir, lambda file: isAutoFile(file) and startsWith(modelFile, dir, file))\n\n# Get a list of all out files in a directory\n\ndef getOutFilesInDir(dir):\n    return getFilesInDir(dir, isOutFile)\n\n# Get a list of all out files in a directory whose prefix matches a model file name\n\ndef getMatchingOutFilesInDir(dir, modelFile):\n    return getFilesInDir(dir, lambda file: isOutFile(file) and startsWith(modelFile, dir, file))\n\n# Extract all command-line switches from an \"args\" file into a list\n# Just combine switches on all (non-commented) lines together, delimited by spaces\n# Returns an empty list if the file does not exist\n\ndef getAllArgsFromFile(file):\n    args = []\n    if not os.path.isfile(file): return args\n    for line in open(file, 'r').readlines():\n        line = line.strip()\n        if len(line) == 0 or lineIsCommentedOut(line): continue\n        items = line.split(' ')\n        for item in items:\n            if len(item) > 0: args.append(item)\n    return args\n\n# Extract command-line switches from an \"args\" file into a list of lists\n# Switches from each (non-commented) line, delimited by spaces, are in a separate list\n# Returns an empty list if the file does not exist\n\ndef getArgsListsFromFile(file):\n    argsSet = []\n    if not os.path.isfile(file): return argsSet\n    for line in open(file, 'r').readlines():\n        args = []\n        line = line.strip()\n        if len(line) == 0 or lineIsCommentedOut(line): continue\n        items = line.split(' ')\n        for item in items:\n            if len(item) > 0: args.append(item)\n        if len(args) > 0: argsSet.append(args)\n    return argsSet\n\n# Read the matching .args file for the given model/properties/auto file and return a list of lists,\n# each list corresponding to one line in the .args file, one argument per list item\n#\n# * file: name of the model/properties file (as a string)\n\ndef getMatchingArgListsForFile(file):\n    if os.path.isfile(file + \".args\"):\n        return getArgsListsFromFile(file + \".args\")\n    return [[]]\n\n# Add any extra args provided to this script to each of the given argument lists\n\ndef addExtraArgs(argLists):\n    if len(options.extraArgs) > 0:\n        result = argLists\n        for x in options.extraArgs:\n            result = result + x.split(' ')\n        return result\n    else:\n        return argLists\n\n# Returns true iff there is a possible name clash for the given filename\n\ndef possibleNameClash(fullName):\n    withoutExt = fullName.rsplit('.', 1)[0]\n    exts = ['lab','tra','sta','srew','trew','obs']\n\n    return any(map (os.path.exists, [fullName] + [withoutExt + '.' + ext for ext in exts] +  [withoutExt + '1.' + ext for ext in exts]))\n\n# Join directory and filename to obtain a full path\n# If doAddPrefix is true, a prefix is prepended to the filename as well\n\ndef expandName(dir, option):\n    splitOption = option.split(':')\n    # if the filename is 'stdout' (recognized as special by PRISM),\n    # we don't expand and simply return the input\n    if splitOption[0] == \"stdout\":\n        return option\n    fullName = os.path.join(dir, splitOption[0])\n    return fullName + (\":\" + splitOption[1] if len(splitOption) > 1 else '')\n\n# Prepend the given prefix to the given filename or filename:option string\n# e.g. prependToFile('hello.', '/some/world:here) == '/some/hello.world:here'\n\ndef prependToFile(prefix, option):\n    splitOption = option.split(':')\n    # if the filename is 'stdout' (recognized as special by PRISM),\n    # we don't expand and simply return the input\n    if splitOption[0] == \"stdout\":\n        return option\n    fullName = os.path.join(os.path.dirname(splitOption[0]), 'tmp.' + os.path.basename(splitOption[0]))\n    return fullName + (\":\" + splitOption[1] if len(splitOption) > 1 else '')\n\n# Traverses an argument list, expanding all filenames in import and export switches\n# and appending a prefix to each export filename to prevent PRISM from overriding the out file\n\ndef expandFilenames(args, dir=\"\"):\n    def isImportExportArg(arg):\n        return (arg.startswith(\"-export\") or arg.startswith(\"-import\")) and not arg==\"-exportmodelprecision\"\n    if args:\n        return [args[0]] + [expandName(dir, args[i+1]) if isImportExportArg(args[i]) else args[i+1] for i in range(len(args)-1)]\n    else:\n        return []\n\n# Rename all export files in the arguments by prepending prefix\n\ndef renameExports(prefix, args):\n    def isExportArg(arg):\n        return arg.startswith(\"-export\") and not arg==\"-exportmodelprecision\"\n    if args:\n        return [args[0]] + [prependToFile(prefix, args[i+1]) if isExportArg(args[i]) else args[i+1] for i in range(len(args)-1)]\n    else:\n        return args\n\n\n#  Return True if there are any -export... switches\n\ndef hasExportSwitches(args):\n    for i in range(len(args)-1):\n        if args[i].startswith(\"-export\"):\n            return True\n    return False\n\n# Find all files that match any -export switch file argument\n# This takes into account that a .all extension corresponds to five different files\n# and that multiple reward structures will result in filenames extended with a number\n\ndef getExpectedOutFilesFromArgs(args):\n    argsOptions = [args[i+1] for i in range(len(args)-1) if args[i].startswith(\"-export\") and not args[i]==\"-exportmodelprecision\"]\n    # Sometimes there are options appended, after a \":\" - remove these\n    files = map(lambda option: option.split(':')[0], argsOptions)\n\n    resultFiles = []\n    for file in files:\n        # Sometimes we have extra extensions appended, e.g. -exportmodel out.sta,tra\n        split = file.split(',');\n        if (len(split) > 1): moreExts = split[1:len(split)]\n        else: moreExts = []\n        # Get extension\n        split = split[0].rsplit('.', 1)\n        base = split[0]\n        if (len(split) == 1): split = split + [\"\"]\n        # Determine relevant extensions\n        if split[1] == 'all':\n            exts = ['lab','tra','sta','srew','trew','obs']\n        else:\n            exts = [split[1]]\n        if (moreExts): exts = exts + moreExts;\n        # Find all files of the form base<number>.<ext>\n        for ext in exts:\n            fullName = base + '.' + ext\n            foundFile = False\n            if os.path.exists(fullName):\n                resultFiles.append(fullName)\n                foundFile = True\n            else:\n                i = 1\n                fullName = base + str(i) + '.' + ext\n                while os.path.exists(fullName):\n                    resultFiles.append(fullName)\n                    i += 1\n                    fullName = base + str(i) + '.' + ext\n                    foundFile = True\n            if not foundFile and (options.showWarnings or options.verboseTest):\n                printColoured('WARNING', \"Warning: There is no file of the form \" + base + \"[number].\" + ext + \" to compare against -- will skip\")\n                incrementTestStat('WARNING')\n    return resultFiles\n\n# Create a valid name for a log file based on a list of benchmark arguments\n\ndef createLogFileName(args, dir=\"\"):\n    logFile = '.'.join(args)\n    if len(dir) > 0:\n        logFile = re.sub(dir+'/', '', logFile)\n    logFile = re.sub(r'/', '_', logFile)\n    logFile = re.sub(r'[^a-zA-Z0-9=_, \\.]', '', logFile)\n    logFile = re.sub(r'[ ]+', '.', logFile)\n    logFile = re.sub(r'[\\.]+', '.', logFile)\n    logFile = re.sub(r'^[\\._]+', '', logFile)\n    return logFile + \".log\"\n\n# Create a valid name for a log (sub) directory based on a list of benchmark arguments\n\ndef createLogDirName(args):\n    logDir = '.'.join(args)\n    logDir = re.sub(r'/', '_', logDir)\n    logDir = re.sub(r'[^a-zA-Z0-9=_, \\.]', '', logDir)\n    logDir = re.sub(r'[ ]+', '.', logDir)\n    logDir = re.sub(r'[\\.]+', '.', logDir)\n    logDir = re.sub(r'^[\\._]+', '', logDir)\n    return logDir\n\n# Walk a directory and execute a callback on each file\n\ndef walk(dir, meth):\n    dir = os.path.abspath(dir)\n    for file in [file for file in sortedListDir(dir) if not file in [\".\",\"..\",\".svn\"]]:\n        nfile = os.path.join(dir, file)\n        meth(nfile)\n        if os.path.isdir(nfile):\n            walk(nfile,meth)\n\n#\n# Print a message in colour, but only if isColourEnabled() is true.\n# If isColourEnabled is false, print message without colours.\n# The colour parameter is a key for the global testColours dictionary.\n#\ndef printColoured(colour, msg):\n    global testColours\n    if isColourEnabled():\n        print('\\033[' + str(testColours[colour]) + 'm' + msg + '\\033[0m')\n    else:\n        print(msg)\n    sys.stdout.flush()\n\n#\n# Given a switch (-xyz or --xyz), expand to full-length form\n# using the switchShortcuts mapping.\n# Switches can also have the form -xyz:foo=..., i.e., carrying\n# additional arguments; this is handled as well.\n# Return expanded switch or the original parameter, if not expanded.\n#\ndef expandShortcutSwitch(s):\n    xtradash = ''\n    if (s.startswith('--')):\n        xtradash = '-'\n        s = s[1:]\n    # split off extra arguments after a :\n    l = s.split(':',1)\n    # continue with the actual switch name\n    s = l[0]\n    # get entry for s; otherwise, default value is s itself\n    s = switchShortcuts.get(s,s)\n    # add back extra dash, if necessary\n    s = xtradash + s\n    # add back :arg part, if necessary\n    if len(l) == 2:\n        s += ':' + l[1]\n    return s\n\n#\n# Given an argument list, expand short-form switches (-xyz or --xyz)\n# to their full-length form using the switchShortcuts mapping.\n# Returns processed argument list.\n#\ndef expandShortcutsInArgs(args):\n    return [expandShortcutSwitch(x) for x in args]\n\n#\n# Given an argument list, remove conflicting settings,\n# e.g., if there are multiple switches for selecting\n# the PRISM engine, only keep the last one, i.e.,\n# the switch that PRISM will actually use.\n# Returns processed argument list.\n#\ndef removeConflictingArgs(args, conflicting):\n    seen = False\n    result = []\n    for x in reversed(args):\n        if x in conflicting:\n            if not seen: result.append(x)\n            seen = True\n        else:\n            result.append(x)\n    result.reverse()\n    return list(result)\n\n#\n# Given an argument list, returns a (more or less)\n# canonical version:\n#  * Performs regularisation of --switch to -switch\n#  * Expands short-form switches to long-form version\n#    (if we know about them, see switchShortcuts mapping)\n#  * Removes conflicting switches for\n#     - PRISM engine, as well as -exact and -param setting\n#     - model type override\n#\ndef canonicaliseArgs(args):\n    # canonicalise --switch to -switch\n    args = [ x[1:] if x.startswith('--') else x for x in args]\n    # expand the short cuts via switchShortcuts mapping\n    args = expandShortcutsInArgs(args)\n    # remove conflicting engine setting\n    engines = frozenset(['-explicit', '-hybrid', '-sparse', '-mtbdd'])\n    args = removeConflictingArgs(args, engines)\n    # remove conflicting model type overrides\n    args = removeConflictingArgs(args, frozenset(['-mdp', '-dtmc', '-ctmc']))\n    # handle exact / param switches\n    if '-exact' in args or '-param' in args:\n        # remove engines if we are in exact or param mode (normal engines are irrelevant)\n        args = [x for x in args if x not in engines ]\n    if '-param' in args:\n        # remove -exact if we are in param mode (param takes precedence)\n        args = [x for x in args if x != '-exact' ]\n    return args\n\n#==================================================================================================\n# Benchmarking\n#==================================================================================================\n\n# Run PRISM with a given list of command-line args\n#\n# * args: list of command-line line arguments\n# * bmArgs: further list of command-line line arguments (benchmarking ones)\n# * dir: name of the directory (as a string)\n\ndef runPrism(args, bmArgs, dir=\"\"):\n    # collate all arguments\n    args += bmArgs\n    \n    # check if we can skip\n    if options.skipDuplicates:\n        canonicalArgs = canonicaliseArgs(args)\n        if (tuple(canonicalArgs) in alreadyRan):\n            incrementTestStat('SKIPPED')\n            incrementTestStat('SKIPPED_DUPLICATE')\n            return\n        alreadyRan.add(tuple(canonicalArgs))\n\n    # keep track if we need to cleanup the log file after use\n    cleanupLogFile = False\n    if options.test:\n        if options.testAll: args.append(\"-testall\")\n        else: args.append(\"-test\")\n    if options.nailgun:\n        prismArgs = [options.ngprism] + args\n    else:\n        prismArgs = [options.prismExec] + args\n    if options.echo or options.echoFull:\n        if options.echoFull:\n            prismArgs = ['echo', quote(' '.join(prismArgs)), ';'] + prismArgs\n            if options.logDir:\n                logDir = options.logDir\n                if options.logSubdirs and bmArgs:\n                    logDir = os.path.join(logDir, createLogDirName(bmArgs))\n                logFile = os.path.relpath(os.path.join(logDir, createLogFileName(args, dir)))\n                logFile = quote(logFile)\n                if options.test:\n                    prismArgs += ['|', 'tee', logFile]\n                else:\n                    prismArgs += ['>', logFile]\n            if options.test:\n                prismArgs += ['|', 'grep \"Testing result:\"']\n        print(' '.join(prismArgs))\n        return\n    if not options.errorsOnly:\n        print(' '.join(prismArgs))\n    sys.stdout.flush()\n    if options.logDir:\n        logDir = options.logDir\n        if options.logSubdirs and bmArgs:\n            logDir = os.path.join(logDir, createLogDirName(bmArgs))\n        if not os.path.exists(logDir):\n            os.makedirs(logDir)\n        logFile = os.path.join(logDir, createLogFileName(args, dir))\n        #f = open(logFile, 'w')\n        prismArgsExec = prismArgs + ['-mainlog', logFile]\n        exitCode = execute(prismArgsExec)\n        #exitCode = subprocess.Popen(prismArgsExec, cwd=dir, stdout=f).wait()\n    elif options.test or options.ddWarnings:\n        # create logfile\n        if isWindows():\n            # On Windows, PRISM can not open a temporary file created with NamedTemporaryFile.\n            # So we use the not-as-secure mktemp...\n            # We use . as directory because PRISM / Java can not handle\n            # cygwin style paths (/tmp/...)\n            logFile = tempfile.mktemp(dir='.')\n        else:\n            # Not on Windows, use NamedTemporaryFile\n            f = tempfile.NamedTemporaryFile(delete=False)\n            logFile = f.name\n            f.close()\n        # we want cleanup when we are done, as this is a real temporary file\n        cleanupLogFile = True\n        prismArgsExec = prismArgs + ['-mainlog', logFile]\n        exitCode = execute(prismArgsExec)\n    else:\n        exitCode = execute(prismArgs)\n    # Extract DD reference count warnings\n    if options.ddWarnings:\n        for line in open(logFile, 'r').readlines():\n            if re.match(r'Warning: CUDD reports .* non-zero references', line):\n                printTestResult(line, prismArgs)\n    # Extract test results if needed\n    if options.test:\n        for line in open(logFile, 'r').readlines():\n            if re.match(r'Testing result:', line):\n                printTestResult(line, prismArgs)\n            elif re.match(r'Warning:', line):\n                if options.showWarnings or options.verboseTest:\n                    printTestResult(line, prismArgs)\n                else:\n                    # We don't print it, but we count it\n                    countTestResult(line)\n            elif options.verboseTest:\n                # in verbose mode, also print the non-matching lines\n                # rstrip to remove newline before printing\n                if re.match(r'Error:', line):\n                    # highlight lines with error messages\n                    printColoured('FAILURE', line.rstrip())\n                else:\n                    print(line.rstrip())\n                sys.stdout.flush()\n    if options.test and exitCode != 0:\n        # failure\n        if not options.verboseTest:\n            # we don't want to cleanup the log (if it was a temporary file)\n            # so that the user can inspect it\n            cleanupLogFile = False\n            for line in open(logFile, 'r').readlines():\n                if re.match(r'Error:', line):\n                    printTestResult(line, prismArgs)\n            if (options.printFailures):\n                print(\"Failing test log file:\")\n                for line in open(logFile, 'r').readlines():\n                    print(line, end=\"\")\n            else:\n                print(\"To see log file, run:\")\n                print(\"edit \" + logFile)\n            prismArgsPrint = list(prismArgs)\n            prismArgsPrint[0] = options.prismExec\n            print(\"To re-run failing test:\")\n            print(' '.join(prismArgsPrint))\n        else:\n            # in verbose test mode, print extra info and increment failure counter\n            printColoured('FAILURE', \"\\n[Exit code: \" + str(exitCode) + \"]\")\n            incrementTestStat('FAILURE')\n        if not options.testAll:\n            closeDown(1)\n    if cleanupLogFile:\n        # logFile was a temporary file and we'd like to clean it up\n        os.remove(logFile)\n\n# call-back function for expiration of the execute timer thread\ndef timeout(proc, flag):\n    printColoured('FAILURE', '\\nTimeout (' + str(options.timeout) + 's)')\n    flag.append(True)\n    proc.kill()\n\n# execute the given process, optionally setting a timeout\ndef execute(args):\n    if options.timeout is not None:\n        # run program\n        proc = subprocess.Popen(args)\n        # list to serve as indicator that a timeout has occurred\n        flag = []\n        # setup timer to call timeout function with proc and flag as arguments\n        timer = Timer(float(options.timeout), timeout, [proc, flag])\n        try:\n            # start time and wait for process to finish\n            timer.start()\n            exitCode = proc.wait()\n            # here, either the process quit by itself (flag is empty)\n            # or was killed in the timeout function (flag contains one True element)\n            hadTimeout = bool(flag)   # timeout = flag is not empty -> True\n            if hadTimeout:\n                incrementTestStat('TIMEOUT')\n                # in nailgun mode, we have to restart the nailgun server,\n                # as the VM can be in an inconsistent state\n                if options.nailgun: restartNailGunServer()\n                # if we had a timeout, fake exitCode of 0\n                return 0\n            return exitCode\n        finally:\n            timer.cancel()\n    else:\n        proc = subprocess.Popen(args)\n        exitCode = proc.wait()\n        return exitCode\n\n\n# Print a testing-related message, colour coding if needed\n\ndef printTestResult(msg, prismArgs=[]):\n    global testColours\n    if options.errorsOnly:\n        if not ('Error:' in msg or 'FAIL' in msg or ('Warning:' in msg and (options.showWarnings or options.verboseTest))):\n            return\n        else:\n            if prismArgs:\n                print(' '.join(prismArgs))\n    msg = str.rstrip(msg)\n    countTestResult(msg)\n    if not isColourEnabled():\n        print(msg)\n        sys.stdout.flush()\n        return\n    # Coloured-coded...\n    if 'Error:' in msg or 'FAIL' in msg:\n        printColoured('FAILURE', msg)\n    elif 'Warning:' in msg:\n        printColoured('WARNING', msg)\n    elif 'PASS' in msg:\n        printColoured('SUCCESS', msg)\n    elif 'SKIPPED' in msg or 'NOT TESTED' in msg:\n        printColoured('SKIPPED', msg)\n    elif 'UNSUPPORTED' in msg or 'Warning:' in msg:\n        printColoured('UNSUPPORTED', msg)\n    else:\n        print(msg)\n        sys.stdout.flush()\n\ndef incrementTestStat(stat):\n    global testStats\n    testStats[stat]+=1\n\ndef printTestStatistics():\n    if options.test and not options.echo:\n        print('\\nTest results:')\n        printColoured('SUCCESS',     ' Success:            ' + str(testStats['SUCCESS']))\n        printColoured('WARNING',     ' Warnings:           ' + str(testStats['WARNING'])\n                      + ('  (use -w to show)' if (testStats['WARNING']>0 and not options.showWarnings and not options.verboseTest) else ''))\n        if (options.ddWarnings):\n            printColoured('WARNING',     '  DD-Warnings:       ' + str(testStats['DDWARNING']))\n        printColoured('FAILURE',     ' Failure:            ' + str(testStats['FAILURE']))\n        if testStats['FAIL_NONCONVERGE']:\n            printColoured('FAILURE',     '  - Non-convergence: ' + str(testStats['FAIL_NONCONVERGE']))\n        printColoured('UNSUPPORTED', ' Unsupported:        ' + str(testStats['UNSUPPORTED']))\n        printColoured('SKIPPED',     ' Skipped:            ' + str(testStats['SKIPPED']))\n        if testStats['SKIPPED_NOT_TESTED']:\n            printColoured('SKIPPED',     '  - Not tested:      ' + str(testStats['SKIPPED_NOT_TESTED']))\n        if options.skipDuplicates:\n            printColoured('SKIPPED',     '  - Duplicates:      ' + str(testStats['SKIPPED_DUPLICATE']) + '  (due to --skip-duplicate-runs)')\n        if options.skipExportRuns:\n            printColoured('SKIPPED',     '  - Export:          ' + str(testStats['SKIPPED_EXPORT']) + '  (due to --skip-export-runs)')\n        if options.timeout is not None:\n            printColoured('FAILURE',     ' Timeouts:           ' + str(testStats['TIMEOUT']))\n\n\ndef countTestResult(msg):\n    if 'Error:' in msg or 'FAIL' in msg:\n        if 'did not converge' in msg:\n            incrementTestStat('FAIL_NONCONVERGE')\n        incrementTestStat('FAILURE')\n    elif options.ddWarnings and re.match(r'Warning: CUDD reports .* non-zero references', msg):\n        incrementTestStat('WARNING')\n        incrementTestStat('DDWARNING')\n    elif 'Warning:' in msg:\n        incrementTestStat('WARNING')\n    elif 'PASS' in msg:\n        incrementTestStat('SUCCESS')\n    elif 'SKIPPED' in msg or 'NOT TESTED' in msg:\n        if 'NOT TESTED' in msg:\n            incrementTestStat('SKIPPED_NOT_TESTED')\n        incrementTestStat('SKIPPED')\n    elif 'UNSUPPORTED' in msg:\n        incrementTestStat('UNSUPPORTED')\n\n# Is printing of colour coded messages enabled?\n\ndef isColourEnabled():\n    if options.colourEnabled == \"yes\":\n        return True\n    elif options.colourEnabled == \"no\":\n        return False\n    else:\n        # auto: yes if in terminal mode\n        return sys.stdout.isatty()\n\n# Checks for each file from the outFiles list whether there is an identical file\n# with the name exportPrefix + file. If so, said file is deleted. Otherwise, it is kept\n# Returns true iff identical files were found for each out file\n\ndef verifyAndCleanupExports(outFiles, exportPrefix):\n    result = True\n    # Check for equality with out files\n    for outFile in outFiles:\n        msg = \"Testing export \" + os.path.basename(outFile) + \": \"\n        expFile = prependToFile(exportPrefix, outFile)\n        if os.path.isfile(expFile):\n            if options.noExportTests:\n                msg = msg + \"SKIPPED\"\n                os.remove(expFile)\n            elif compareFiles(outFile, expFile):\n                # If successful, notify and delete exported file\n                msg = msg + \"PASS\"\n                os.remove(expFile)\n            else:\n                msg = msg + \"FAIL (\" + os.path.basename(expFile) + \" does not match)\"\n                print(\"To see difference, run:\")\n                print(\"diff \" + outFile + \" \" + expFile)\n                sys.stdout.flush()\n                result = False\n        else:\n            if options.noExportTests:\n                msg = msg + \"SKIPPED\"\n            else:\n                msg = msg + \"FAIL (no \" + os.path.basename(expFile) + \" to compare to)\"\n                result = False\n        printTestResult(msg)\n        if not result:\n            return result\n    return result\n\n# Run a benchmark, specified by a list of command-line args,\n# possibly iterating over further lists of args from a \"bm\" file\n\ndef benchmark(file, args, dir=\"\"):\n    logging.debug(\"Benchmarking: \" + file + \", \" + str(args))\n    # Add extra arguments from command line, if applicable\n    args = addExtraArgs(args)\n    # Expand input/output files to full paths\n    args = expandFilenames(args, dir)\n\n    if options.skipExportRuns and hasExportSwitches(args):\n        incrementTestStat('SKIPPED')\n        incrementTestStat('SKIPPED_EXPORT')\n        return\n\n    # Determine which out files apply to this benchmark from the -export switches (if required)\n    if not options.echo and options.test:\n        outFiles = getExpectedOutFilesFromArgs(args)\n        \n    # Rename export files to avoid overriding out files\n    # (if in test mode, and if not disabled)\n    exportPrefix = 'tmp.'\n    if (options.test and not options.noRenaming):\n        args = renameExports(exportPrefix, args)\n\n    # print '\\033[94m' + \"EXECUTING BENCHMARK\" + '\\033[0m'\n    # print \"File: \" + file\n    # print \"Directory: \" + dir\n    # print \"Args: \" + ' '.join(args)\n    # print \" \"\n\n    modelFileArg = [file] if (file != \"\") else []\n\n    # Loop through benchmark options, if required\n    argsLists = []\n    # May be specified in a file\n    if options.bmFile:\n        if not os.path.isfile(os.path.join(options.bmFile)):\n            print(\"Cannot read arguments from non-existing file: \" + os.path.join(options.bmFile))\n            sys.exit(1)\n        argsLists.extend(getArgsListsFromFile(options.bmFile))\n    # And/or may be specified on the command line\n    if options.bmList:\n        for bmArgsString in options.bmList.split(','):\n            argsLists.append(bmArgsString.strip().split(' '))\n            \n    # Now loop through benchmark options\n    if len(argsLists) > 0:\n        for bmArgs in argsLists:\n            runPrism(modelFileArg + args, bmArgs, dir)\n    # If none, just use existing args alone\n    else:\n        runPrism(modelFileArg + args, [], dir)\n\n    # Verify that exported files are correct (if required)\n    if not options.echo and options.test and outFiles:\n        # print \"Out files to verify exports against: \" + ' '.join(outFiles)\n        allEqual = verifyAndCleanupExports(outFiles, exportPrefix)\n        if (not allEqual) and (not options.testAll):\n            closeDown(1)\n\n# Execute benchmarking based on a directory\n# Unless requested not to (via -n/--non-recursive), the directory is searched recursively.\n# In each directory, all models are found - either those listed in a file called 'models',\n# if present, or all files with a suitable extension within the directory.\n# Each model is then treated as if it had been called with prism-auto directly\n# In addition, any \"orphan\" auto files are run (i.e. those not matching some model file).\n# This basically means calling PRISM for each line of the auto file, and passing the\n# contents of this line as the arguments. Arguments found in a matching .args file\n# (e.g. xxx.auto.args) are also appended, and if there are multiple lines in the .args file,\n# PRISM is run for each line of the auto file and each line of the .args file.\n#\n# * dir: name of the directory (as a string)\n\ndef benchmarkDir(dir):\n    logging.debug(\"Benchmarking dir \" + dir)\n    # Recurse first, unless asked not to\n    if not options.nonRec:\n        for file in [file for file in sortedListDir(dir) if not file in [\".\",\"..\",\".svn\"]]:\n            if os.path.isdir(os.path.join(dir, file)):\n                benchmarkDir(os.path.join(dir, file))\n    # Get model files in dir\n    modelFiles = getModelsInDir(dir)\n    for modelFile in modelFiles:\n        benchmarkModelFile(modelFile[0], modelFile[1], dir)\n    # Get \"orphan\" auto files\n    autoFiles = filter(functools.partial(isOrphan, dir), getAutoFilesInDir(dir))\n    for autoFile in autoFiles:\n        logging.debug(\"Orphan auto file: \" + autoFile)\n        for args in getArgsListsFromFile(autoFile):\n            benchmark(\"\", args, dir)\n\n# Execute benchmarking based on a single file (model, property, list, auto)\n#\n# * file: name of the file (as a string)\n\ndef benchmarkFile(file):\n    if isPrismModelFile(file):\n        benchmarkModelFile(file)\n    elif isPrismPropertiesFile(file):\n        benchmarkPropertiesFile(file)\n    elif isPrismPropListFile(file):\n        benchmarkPropListFile(file)\n    elif isAutoFile(file):\n        benchmarkAutoFile(file)\n\n# Execute benchmarking based on a single model file, possibly with some additional\n# arguments to pass to PRISM, passed in the list modelArgs (probably from a \"models\" file).\n# If there is a matching .args file (e.g. model.nm.args), arguments in this file\n# are also appended when calling PRISM (and multiple lines result in multiple PRISM runs).\n#\n# * modelFile: name of the model file (as a string)\n# * modelArgs: (optionally) a list of arguments attached to the model, e.g. [\"-const\", \"N=2\"]\n# * dir: (optionally) the directory containing the model (if absent, it is deduced)\n\ndef benchmarkModelFile(modelFile, modelArgs=[], dir=\"\"):\n    logging.debug(\"Benchmarking model file \" + modelFile + \" \" + str(modelArgs))\n    if dir == \"\":\n        dir = os.path.dirname(modelFile)\n        if dir == \"\": dir = \".\"\n    # Expand model file based on any .args file\n    argLists = getMatchingArgListsForFile(modelFile)\n    logging.debug(\"Arg lists: \" + str(argLists))\n    for args in argLists:\n        # Build mode: just build\n        if options.build:\n            benchmark(modelFile, modelArgs + args, dir)\n        # Otherwise, find properties\n        else:\n            # Find and benchmark properties\n            if options.matching:\n                propertiesFiles = getMatchingPropertiesInDir(dir, modelFile)\n            else:\n                propertiesFiles = getPropertiesInDir(dir)\n            logging.debug(\"Properties files: \" + str(propertiesFiles))\n            for propertiesFile in propertiesFiles:\n                logging.debug(\"Property file: \" + propertiesFile)\n                for argsp in getMatchingArgListsForFile(propertiesFile):\n                    benchmark(modelFile, modelArgs + args + [propertiesFile] + argsp, dir)\n        # Find and benchmark auto files\n        autoFiles = getMatchingAutoFilesInDir(dir, modelFile)\n        logging.debug(\"Auto files: \" + str(autoFiles))\n        for autoFile in autoFiles:\n            logging.debug(\"Auto file: \" + str(autoFile))\n            for autoArgs in getArgsListsFromFile(autoFile):\n                for argsa in getMatchingArgListsForFile(autoFile):\n                   benchmark(modelFile, modelArgs + args + autoArgs + argsa, dir)\n\n# Execute benchmarking on an auto file, i.e. a file containing one or more lines\n# of command-line arguments specifying calls to be made to PRISM.\n# If in \"matching mode, and if it is present, an associated model file (with matching name)\n# is also used. But there is no corresponding property file.\n#\n# * autoFile: name of the auto file (as a string)\n\ndef benchmarkAutoFile(autoFile):\n    logging.debug(\"Benchmarking auto file \" + autoFile)\n    dir = os.path.dirname(autoFile)\n    if dir == \"\": dir = \".\"\n    if options.matching:\n        matchingModelFiles = getMatchingModelsInDir(dir, autoFile)\n        if matchingModelFiles:\n            modelFiles = map(lambda file: [file,[]], matchingModelFiles)\n        else:\n            modelFiles = []\n    else:\n        modelFiles = getModelsInDir(dir)\n    logging.debug(\"Model files: \" + str(modelFiles))\n    for modelFile in modelFiles:\n        # Read args for the model\n        for modelArgs in getMatchingArgListsForFile(modelFile):\n            # Treat auto file like an args file\n            for argsList in getArgsListsFromFile(autoFile):\n                # Don't look for properties (corresponds to build mode)\n                for argsa in getMatchingArgListsForFile(autoFile):\n                    benchmark(modelFile, modelArgs + argsList + argsa, dir)\n    if not modelFiles:\n        # There aren't any (matching) model files, process as \"orphaned\" auto file\n        for argsList in getArgsListsFromFile(autoFile):\n            benchmark(\"\", argsList, dir)\n\n# Execute benchmarking based on a single properties file.\n#\n# * propertiesFile: name of the properties file (as a string)\n\ndef benchmarkPropertiesFile(propertiesFile):\n    logging.debug(\"Benchmarking properties file \" + propertiesFile)\n    dir = os.path.dirname(propertiesFile)\n    if dir == \"\": dir = \".\"\n    # Expand properties file based on any .args file\n    argLists = getMatchingArgListsForFile(propertiesFile)\n    for args in argLists:\n        # Find models\n        if options.matching:\n            matchingModelFiles = getMatchingModelsInDir(dir, propertiesFile)\n            modelFiles = map(lambda file: [file,[]], matchingModelFiles)\n        else:\n            modelFiles = getModelsInDir(dir)\n        logging.debug(\"Model files: \" + str(modelFiles))\n        for modelFile in modelFiles:\n            # Expand model based on any .args file, too\n            for modelArgs in getMatchingArgListsForFile(modelFile[0]):\n                benchmark(modelFile[0], modelFile[1] + modelArgs + [propertiesFile] + args, dir)\n\n# Execute benchmarking based on a property list.\n# A property list is a file containing pairs of the form <dir>, <prop> where:\n# <dir> is a directory, relative to the location of the properties file, and\n# <prop> is the name of a properties file contained within that directory.\n# Each properties file is treated as if it had been called with prism-auto directly.\n#\n# * propListFile: name of the property list file (as a string)\n\ndef benchmarkPropListFile(propListFile):\n    logging.debug(\"Benchmarking property list file \" + propListFile)\n    listDir = os.path.dirname(propListFile)\n    if listDir == \"\": listDir = \".\"\n    for line in open(propListFile, 'r').readlines():\n        line = line.strip()\n        if len(line) == 0 or lineIsCommentedOut(line): continue\n        items = line.split(',')\n        dir = os.path.join(listDir, items[0].strip())\n        dir = os.path.realpath(dir)\n        propFile = items[1].strip()\n        benchmarkPropertiesFile(os.path.join(dir, propFile))\n\n# (Re-)start the nailgun server\ndef restartNailGunServer():\n\t# First try to stop an existing server (which should fail quickly if there is none running)\n    print(\"Stopping existing nailgun server, if it's running...\")\n    sys.stdout.flush()\n    subprocess.Popen([options.ngprism, \"stop\"]).wait()\n    # For Java version >=19, running Nailgun needs a workaround\n    javaVersion = getJavaVersion()\n    if javaVersion is not None and javaVersion >= 19:\n        os.environ['PRISM_JAVA_PARAMS'] = '-Djava.security.manager=allow'\n    # Start the server and make sure it is running\n    print(\"Starting nailgun server...\")\n    sys.stdout.flush()\n    os.system(options.prismExec + \" -ng &\")\n    print(\"Checking nailgun server is running...\")\n    exitCode = 1\n    tries = 0\n    maxTries = 5;\n    while exitCode != 0 and tries < maxTries:\n        time.sleep(0.5)\n        tries = tries + 1\n        exitCode = subprocess.Popen([options.ngprism, \"-version\"]).wait()\n        \n# Get the (major) version of Java used to run PRISM, return as an integer (or None if failed)\ndef getJavaVersion():\n    try:\n        # Get the output of \"prism -javaversion\", extract version as regexp\n        result = subprocess.run([options.prismExec, '-javaversion'], stdout=subprocess.DEVNULL, stderr=subprocess.PIPE, text=True)\n        javaVersionMajor = None\n        if result.returncode == 0:\n            javaVersionString = re.search(r'\"(\\d+)', result.stderr)\n            if javaVersionString:\n                javaVersionMajor = int(javaVersionString.group(1))\n        return javaVersionMajor\n    except FileNotFoundError: # prismExec call fails\n        return None\n\n#==================================================================================================\n# Main program\n#==================================================================================================\n\ndef printUsage():\n    print(\"Usage: prism-auto ...\")\n\ndef signal_handler(signal, frame):\n    closeDown(1)\n\n# Close down neatly, stopping nailgun if needed\n\ndef closeDown(exitCode):\n    if options.nailgun:\n        if options.echo or options.echoFull:\n            print(options.ngprism + \" stop\")\n        else:\n            subprocess.Popen([options.ngprism, \"stop\"]).wait()\n    printTestStatistics()\n    sys.exit(exitCode)\n\n# Main program\n\nsignal.signal(signal.SIGINT, signal_handler)\nparser = OptionParser(usage=\"usage: %prog [options] args\")\nparser.add_option(\"-l\", \"--log\", dest=\"logDir\", metavar=\"DIR\", default=\"\", help=\"Store PRISM output in logs in DIR\")\nparser.add_option(\"-a\", \"--args\", dest=\"bmFile\", metavar=\"FILE\", default=\"\", help=\"Read argument lists for benchmarking from FILE\")\nparser.add_option(\"--args-list\", dest=\"bmList\", metavar=\"X\", default=\"\", help=\"Use X as argument lists for benchmarking (comma-separated)\")\nparser.add_option(\"-e\", \"--echo\", action=\"store_true\", dest=\"echo\", default=False, help=\"Just print out tasks, don't execute\")\nparser.add_option(\"-m\", \"--matching\", action=\"store_true\", dest=\"matching\", default=False, help=\"Only use matching models/properties, not all files\")\nparser.add_option(\"-b\", \"--build\", action=\"store_true\", dest=\"build\", default=False, help=\"Just build models, don't model check properties\")\nparser.add_option(\"-p\", \"--prog\", dest=\"prismExec\", metavar=\"FILE\", default=\"prism\", help=\"Program to execute [default=prism]\")\nparser.add_option(\"-n\", \"--non-recursive\", action=\"store_true\", dest=\"nonRec\", default=False, help=\"Don't recurse into directories\")\nparser.add_option(\"-x\", \"--extra\", action=\"append\", dest=\"extraArgs\", metavar=\"XXX\", default=[], help=\"Pass extra switches to PRISM\")\nparser.add_option(\"-t\", \"--test\", action=\"store_true\", dest=\"test\", default=False, help=\"Run in test mode\")\nparser.add_option(\"--verbose-test\", action=\"store_true\", dest=\"verboseTest\", default=False, help=\"Run in verbose test mode (implies --test)\")\nparser.add_option(\"-w\", \"--show-warnings\", action=\"store_true\", dest=\"showWarnings\", default=False, help=\"Show warnings (as well as errors) when in test mode\")\nparser.add_option(\"--errors-only\", action=\"store_true\", dest=\"errorsOnly\", default=False, help=\"Only show errors when in test mode\")\nparser.add_option(\"--nailgun\", action=\"store_true\", dest=\"nailgun\", default=False, help=\"Run PRISM in Nailgun mode\")\nparser.add_option(\"--ngprism\", dest=\"ngprism\", metavar=\"FILE\", default=None, help=\"Specify the location of ngprism (for Nailgun mode) [default: derive from --prog setting]\")\nparser.add_option(\"--test-all\", action=\"store_true\", dest=\"testAll\", default=False, help=\"In test mode, don't stop after an error\")\nparser.add_option(\"--no-renaming\", action=\"store_true\", dest=\"noRenaming\", default=False, help=\"Don't rename files to be exported\")\nparser.add_option(\"--debug\", action=\"store_true\", dest=\"debug\", default=False, help=\"Enable debug mode: display debugging info\")\nparser.add_option(\"--echo-full\", action=\"store_true\", dest=\"echoFull\", default=False, help=\"An expanded version of -e/--echo\")\nparser.add_option(\"--models-filename\", dest=\"modelsFilename\", metavar=\"X\", default=\"models\", help=\"Read in list of models/parameters for a directory from file X, if present [default=models]\")\nparser.add_option(\"--models-info\", dest=\"modelsInfoFilename\", metavar=\"X\", default=\"models.csv\", help=\"Read model details from CSV file X, if present [default=models.csv]\")\nparser.add_option(\"--filter-models\", dest=\"filterModels\", metavar=\"N\", default=\"\", help=\"Filter benchmark models...\")\nparser.add_option(\"--log-subdirs\", action=\"store_true\", dest=\"logSubdirs\" ,default=False, help=\"Organise PRISM output logs in subdirectories per benchmark argument\")\nparser.add_option(\"--no-export-tests\", action=\"store_true\", dest=\"noExportTests\", default=False, help=\"Don't check exported files when in test mode\")\nparser.add_option(\"--skip-export-runs\", action=\"store_true\", dest=\"skipExportRuns\", default=False, help=\"Skip all runs having exports\")\nparser.add_option(\"--skip-duplicate-runs\", action=\"store_true\", dest=\"skipDuplicates\", default=False, help=\"Skip PRISM runs which have the same arguments as an earlier run (with some heuristics to detect equivalent arguments)\")\nparser.add_option(\"--timeout\", dest=\"timeout\", metavar=\"N\", default=None, help='Timeout for each PRISM run (examples values for N: 5 / 5s for seconds, 5m / 5h for minutes / hours)')\nparser.add_option(\"--dd-warnings\", action=\"store_true\", dest=\"ddWarnings\", default=False, help=\"Print the DD reference count warnings\")\nparser.add_option(\"--colour\", dest=\"colourEnabled\", metavar=\"X\", type=\"choice\", choices=[\"yes\",\"no\",\"auto\"], default=\"auto\", help=\"Whether to colour test results: yes, no, auto (yes iff in terminal mode) [default=auto]\")\nparser.add_option(\"--print-failures\", action=\"store_true\", dest=\"printFailures\", default=False, help=\"Display logs for failing tests\")\n(options, args) = parser.parse_args()\nif len(args) < 1:\n    parser.print_help()\n    sys.exit(1)\nif options.debug:\n    logging.basicConfig(level=logging.DEBUG)\nif options.verboseTest:\n    # --verbose-test implies --test\n    vars(options)['test'] = True\nif options.timeout:\n    # handle time units\n    mult = 1.0\n    if options.timeout.endswith('s'):\n        vars(options)['timeout'] = options.timeout[0:-1]  # strip 's'\n    elif options.timeout.endswith('m'):\n        vars(options)['timeout'] = options.timeout[0:-1]\n        mult =  60.0;\n    elif options.timeout.endswith('h'):\n        vars(options)['timeout'] = options.timeout[0:-1]\n        mult = 3600.0;\n    try:\n        vars(options)['timeout'] = float(options.timeout) * mult\n    except ValueError:\n        print('Illegal parameter value for timeout parameter')\n        sys.exit(1)\n# if options.logDir and not os.path.isdir(options.logDir):\n#     print(\"Log directory \\\"\" + options.logDir + \"\\\" does not exist\")\n#     sys.exit(1)\nif options.nailgun:\n    if options.ngprism is None:\n        # derive ngprism location from the --prog setting\n        dir = os.path.dirname(options.prismExec)\n        base = os.path.basename(options.prismExec)\n        # we just replace the base part of prismExec by ngprism and hope for the best...\n        base = 'ngprism'\n        options.ngprism = os.path.join(dir, base)\n        print(\"Derived executable for nailgun server: \" + options.ngprism)\n    if options.echo or options.echoFull:\n        print(options.prismExec + \" -ng &\")\n    else:\n        restartNailGunServer();\n\n# process benchmarks\nfor arg in args:\n    if os.path.isdir(arg):\n        benchmarkDir(arg)\n    elif os.path.isfile(arg):\n        benchmarkFile(arg)\n    else:\n        print(\"Error: File/directory \" + arg + \" does not exist\")\n\n# shutdown\nif options.test and options.testAll and not options.echo:\n    if testStats['FAILURE'] > 0:\n        # report via the exit code that there were actual failures in test + test-all mode\n        closeDown(1)\n\ncloseDown(0)\n"
  },
  {
    "path": "prism/etc/scripts/prism-download.sh",
    "content": "#!/bin/bash\n\n# Script to download the source/binary releases of some version\n\n# Usage: ./prism-download.sh prism 4.10.2\n# Usage: ./prism-download.sh prism-games 3.2.4\n\nTOOL=$1\nVERSION=$2\n\nDISTRS=(\"src\" \"linux64-x86\" \"linux64-arm\" \"mac64-x86\" \"mac64-arm\" \"win64-x86\")\n\nif [ -z \"$TOOL\" -o -z \"$VERSION\" ]; then\n    echo \"Usage: $0 <tool> <version>\"\n    echo \"where <tool> is prism or prism-games\"\n    exit 1\nfi\n\nif [[ -n \"$TOOL\" && -n \"$VERSION\" ]]; then\n\tfor DISTR in \"${DISTRS[@]}\"; do\n\t\tif [[ \"$DISTR\" == win* ]]; then\n\t\t\tDISTR_FILE=\"${TOOL}-${VERSION}-${DISTR}-installer.exe\"\n\t\t\tDISTR_PERM=755\n\t\telse\n\t\t\tDISTR_FILE=\"${TOOL}-${VERSION}-${DISTR}.tar.gz\"\n\t\t\tDISTR_PERM=644\n\t\tfi\n\t\twget -O \"${DISTR_FILE}\" \"https://github.com/prismmodelchecker/${TOOL}/releases/download/v${VERSION}/${DISTR_FILE}\"\n\t\tchmod ${DISTR_PERM} \"${DISTR_FILE}\"\n\tdone\nfi\n"
  },
  {
    "path": "prism/etc/scripts/prism-filler.py",
    "content": "#! /usr/bin/env python3\n# coding=utf-8\n\n# run without arguments for usage info\n\nimport re\nimport sys\nimport os\nfrom optparse import OptionParser\n\nlist_of_files = []\ndirectories = []\n\ndef treat_file_names(file) : \n\tglobal list_of_files\n\t#first get the actual string if a number or None is provided\n\tif file is None : \n\t\tfile = list_of_files[-1]\n\tif type(file) is int :\n\t\tfile = list_of_files[file]\n\tlist_of_files.append(file)\n\n\t#now get a path\n\t#first try the directories\n\tfor d in directories :\n\t\tjoined = os.path.join(d, file) \n\t\tif (os.path.isfile(joined)) :\n\t\t\treturn joined\n\t#otherwise just return the file itself (note: if it does not exist, an exception will be thrown anyway)\n\treturn file\n\n#extract total computation time\ndef p_time(file = None) :\n\tfile = treat_file_names(file)\n\tlog_content = open(file).read()\n\tmatched = re.search(\"Time for model checking:[^0-9]*(?P<time>[0-9.]*)\", log_content)\n\tif matched is None :\n\t\treturn None\n\telse :\n\t\treturn matched.group(\"time\");\n\n#extract total number of states\ndef p_states(file = None) :\n\tfile = treat_file_names(file)\n\tlog_content = open(file).read()\n\tmatched = re.search(\"States:[^0-9]*(?P<states>[0-9.]*)\", log_content)\n\tif matched is None :\n\t\treturn None\n\telse :\n\t\treturn matched.group(\"states\");\n\n#extract time for LP solving (TODO does not take setup into consideration)\ndef p_lptime(file = None) :\n\tfile = treat_file_names(file)\n\tlog_content = open(file).read()\n\tmatched = re.search(\"LP problem solved in [^0-9]*(?P<time>[0-9.]*)\", log_content)\n\tif matched is None :\n\t\treturn None\n\telse :\n\t\treturn matched.group(\"time\");\n\n#extract number of variables in LP\ndef p_lpsize(file = None) :\n\tfile = treat_file_names(file)\n\tlog_content = open(file).read()\n\tmatched = re.search(\"Number of LP variables[^0-9]*(?P<vars>[0-9.]*)\", log_content)\n\tif matched is None :\n\t\treturn None\n\telse :\n\t\treturn matched.group(\"vars\");\n\n#extract time for value iteration (in multi obj)\ndef p_vitime(file = None) :\n\tfile = treat_file_names(file)\n\tlog_content = open(file).read()\n\tmatched = re.search(\"The value iteration.s. took [^0-9]*(?P<time>[0-9.]*)\", log_content)\n\tif matched is None :\n\t\treturn None\n\telse :\n\t\treturn matched.group(\"time\");\n\n#extract number of objectives (in multi obj)\ndef p_numobj(file = None) :\n\tfile = treat_file_names(file)\n\tlog_content = open(file).read()\n\tmatched = re.search(\"Number of objectives: [^0-9]*(?P<num>[0-9.]*)\", log_content)\n\tif matched is None :\n\t\treturn None\n\telse :\n\t\treturn matched.group(\"num\");\n\n#extract number of weights used (in multi obj)\ndef p_weights(file = None) :\n\tfile = treat_file_names(file)\n\tlog_content = open(file).read()\n\tmatched = re.search(\"Number of weight vectors used: [^0-9]*(?P<num>[0-9.]*)\", log_content)\n\tif matched is None :\n\t\treturn None\n\telse :\n\t\treturn matched.group(\"num\");\n\n#The program starts here\ndescrip = u\"A script that allows to fill in data from prism logs to textual files\\\n such as Latex or CSV.\\\n Usefull when writing papers with tables containing results of experiments.\\\n Basically, it searches the textual file for occurences of a pound sign (\\u00A3), \\\n interprets the text between any two pound signs as a python program, executes\\\n it and replaces it with the output of the program (removing the pound signs). \\\n Some useful functions are provided to extract information from prism logs, see end of this help.\\\n Each of the functions takes one optional argument, which is a file name, \\\n or a number n which says that the n-th log file searched should be used \\\n (repetitions do count, and negative numbers are allowed). \\\n For example, 1 stands for the second file used, -2 stands for last but one file. \\\n If the argument is omitted, '-1' is used (i.e. last file).\"\nep = \"Predefined functions: p_time (total computation time), p_states (number of states of model), \\\n p_lptime (time taken by LP solver),  p_lpsize (number of variables in linear program),\\\n p_vitime (total number for value iterations, in multi-objective queries), p_numobj (number of objectives, \\\n in multi-objective queries), p_weights (number of different weights used, in multi objective queries).\"\n\nparser = OptionParser(usage=\"usage: %prog [options] input_file\",version=\"alpha1 (2012-03-04)\",description=descrip, epilog=ep)\nparser.add_option(\"-o\", \"--output\", action=\"store\", type=\"string\", dest=\"outputfile\", default=None, help=\"Output to file (stdout is used if not present\")\nparser.add_option(\"-d\", \"--dir\", action=\"store\", type=\"string\", dest=\"dir\", default=None, help=\"(NOT SUPPORTED YET) Use directory to look for log files. Multiple directories are separated with colon ':', and the first file found is used.\")\nparser.add_option(\"-i\", \"--ignore-errors\", action=\"store_true\", dest=\"ignoreerrors\", default=False, help=\"The execution will not stop on the first error and the output file will be produced despite errors, with \\\"ERROR\\\" strings in it.\")\n(options, args) = parser.parse_args()\n\nif len(args) != 1:\n\tparser.print_help()\n\tsys.exit(1)\n\n#open input file\ntry :\n\tfile_content = open(args[0]).read()\nexcept IOError as e:\n\tprint \"Cannot read the input file '\" + e.filename + \"': \" + e.strerror >> sys.stderr\n\tsys.exit(1)\n\n#open output file\ntry :\n\tif (options.outputfile is None) :\n\t\toutput_file = sys.stdout\n\telse :\n\t\toutput_file = open(options.outputfile, \"w\")\nexcept IOError as e:\n\tprint >> sys.stderr, \"Cannot access the output file '\" + e.filename + \"': \" + e.strerror\n\tsys.exit(1)\n\n#parse directories\nif not options.dir is None :\n\tdirectories = options.dir.split(':')\n\n#do the work, first, get a string between two pound signs\nmatched = re.search(\"£(?P<cmd>[^£]*)£\", file_content)\nwhile not matched is None :\n\twas_successful = True\n\t#evaluate the user provided expression\n\treplacement = None\n\ttry :\n\t\treplacement =  eval(matched.group(\"cmd\"))\n\texcept NameError as e :\n\t\tprint >> sys.stderr, \"Cannot evaluate '\" + matched.group(\"cmd\") + \"': \" + e.args[0]\n\t\twas_successful = False\n\texcept IOError as (noerror, strerror) :\n\t\tprint >> sys.stderr, \"Cannot evaluate '\" + matched.group(\"cmd\") + \"': \" + strerror\n\t\twas_successful = False\n\texcept IndexError as e :\n\t\tprint >> sys.stderr, \"Cannot evaluate '\" + matched.group(\"cmd\") + \"', you are probably trying to open n-th last file when less than n files were opened so far.\"\n\t\tprint >> sys.stderr, \"The error message reported is: \" + e.args[0]\n\t\twas_successful = False\n\texcept SyntaxError as e :\n\t\tprint >> sys.stderr, \"Cannot evaluate '\" + matched.group(\"cmd\") + \"', invalid syntax. Have you enclosed the file name in qutation marks?\"\n\t\tprint >> sys.stderr, \"The error message reported is: \" + e.args[0]\n\t\twas_successful = False\n\n\tif replacement is None and was_successful :\n\t\tprint  >> sys.stderr, \"Evaluation of '\" + matched.group(\"cmd\") + \"' did not return any text. Possible problems are using wrong log file or calling a wrong function.\"\n\t\twas_successful = False;\n\n\t#if there was some problem, either substitute with a dummy string or exit, depending on user preferences.\n\tif (not was_successful) and options.ignoreerrors:\n\t\treplacement = \"ERROR\"\n\tif (not was_successful) and not options.ignoreerrors:\n\t\tsys.exit(1)\n\n\t#replace the text\n\tfile_content = file_content.replace(matched.group(),replacement, 1);\n\t#get next match\n\tmatched = re.search(\"£(?P<cmd>[^£]*)£\", file_content)\n#output the string with substitutions\nprint >> output_file, file_content\n"
  },
  {
    "path": "prism/etc/scripts/prism-install-cygwin",
    "content": "#!/bin/sh\n\n# Script for installation of PRISM on a clean install of Cygwin\n# already set up with required packages, e.g., via prism-install-windows.bat\n\nset -e # Abort if one of the commands fails\nset -x # Print commands as they are executed\n\n# Download the latest development version from GitHub\ngit clone https://github.com/prismmodelchecker/prism.git\n\n# Compile PRISM and run a single test (unless --nobuild passed)\n# (should ultimately display: \"Testing result: PASS\")\nif [ \"$*\" = \"${*/--nobuild}\" ]; then\n  (cd prism/prism && make && make test)\nfi\n"
  },
  {
    "path": "prism/etc/scripts/prism-install-fedora",
    "content": "#!/bin/sh\n\n# Script for installation of PRISM on a clean install of Fedora-based Linux\n# (current based on Amazon Linux, should be easy to adapt to RHEL/CentOS/etc.)\n\nset -e # Abort if one of the commands fails\nset -x # Print commands as they are executed\n\n# Install dependencies: make/gcc/Java/git\nsudo yum -y update\nsudo yum -y install make gcc gcc-c++ java-11-amazon-corretto-devel git\n\n# Install Python (only needed for testing (prism-auto) currently)\nsudo yum -y install python\n\n# Download the latest development version from GitHub\ngit clone https://github.com/prismmodelchecker/prism.git\n\n# Compile PRISM and run a single test (unless --nobuild passed)\n# (should ultimately display: \"Testing result: PASS\")\nif [ \"$*\" = \"${*/--nobuild}\" ]; then\n  (cd prism/prism && make && make test)\nfi\n"
  },
  {
    "path": "prism/etc/scripts/prism-install-ubuntu",
    "content": "#!/bin/sh\n\n# Script for installation of PRISM on a clean install of Ubuntu\n\nset -e # Abort if one of the commands fails\nset -x # Print commands as they are executed\n\n# Avoid interruptions during install\nif [ -e \"/etc/needrestart/needrestart.conf\" ]; then\n  sudo sed -i \"/#\\$nrconf{restart} = 'i';/s/.*/\\$nrconf{restart} = 'a';/\" /etc/needrestart/needrestart.conf\nfi\n\n# Install dependencies: make/gcc/Java/git\nsudo apt-get -y update\nsudo apt -y install make gcc g++ default-jdk git\n\n# Install Python (only needed for testing (prism-auto) currently)\nsudo apt -y install python3\n\n# Download the latest development version from GitHub\ngit clone https://github.com/prismmodelchecker/prism.git\n\n# Compile PRISM and run a single test (unless --nobuild passed)\n# (should ultimately display: \"Testing result: PASS\")\nif [ \"$*\" = \"${*/--nobuild}\" ]; then\n  (cd prism/prism && make && make test)\nfi\n"
  },
  {
    "path": "prism/etc/scripts/prism-install-windows.bat",
    "content": "@REM Script to prepare for installation of PRISM on a clean Windows install\n@REM Run this in a Windows Command Prompt\n@REM e.g. cmd /K prism-install-windows.bat\n@REM Then run prism-install-cygwin in a Cygwin window\n\n@REM First, install Chocolatey\n\"%SystemRoot%\\System32\\WindowsPowerShell\\v1.0\\powershell.exe\" -Command \"Set-ExecutionPolicy Bypass -Scope Process -Force; [System.Net.ServicePointManager]::SecurityProtocol = [System.Net.ServicePointManager]::SecurityProtocol -bor 3072; iex ((New-Object System.Net.WebClient).DownloadString('https://community.chocolatey.org/install.ps1'))\"\n@REM Chocolatey binaries now on path, but this avoids starting a new prompt\ncall %ALLUSERSPROFILE%\\chocolatey\\bin\\RefreshEnv.cmd\n\n@REM Install some pre-requisites\nchoco install -y wget\nchoco install -y openjdk11\nchoco install -y nsis\nsetx PATH \"%ProgramFiles(x86)%\\NSIS;%PATH%\"\n\n@REM Get and install Cygwin, with core packages needed for PRISM install\n\"%SystemRoot%\\System32\\WindowsPowerShell\\v1.0\\powershell.exe\" -Command \"wget -Uri  http://cygwin.com/setup-x86_64.exe -Outfile setup-x86_64.exe\n.\\setup-x86_64.exe -P make -P mingw64-x86_64-gcc-g++ -P binutils -P dos2unix -P git -P wget -P unzip -P python -P nano -q -s http://ftp.inf.tu-dresden.de/software/windows/cygwin/\n\n@REM Launch a Cygwin terminal\n@REM \"%HOMEDRIVE%\\cygwin64\\bin\\mintty.exe\" -\n"
  },
  {
    "path": "prism/etc/scripts/prism-log-extract",
    "content": "#!/usr/bin/env python3\n\n# The prism-log-extract script extracts and collates info from a\n# collection of PRISM log files.\n\n# The basic usage is \"prism-log-extract <targets>\" where <targets>\n# is one or more log files or directories containing log files.\n# The default behaviour is to extract all known fields from all logs\n# and then print the resulting table of values in CSV format.\n\n# Run \"prism-log-extract --help\" for details of further options.\n\nimport os,sys,re,signal\nfrom optparse import OptionParser\n\n#==================================================================================================\n# Global variables\n#==================================================================================================\n\n# Details of all the fields that can be extracted from logs\nall_fields_details = [\\\n    {'name': 'prog_name', 'descr': 'Name of program run', 'type': 'string'}, \\\n    {'name': 'prog_version', 'descr': 'Version of program run', 'type': 'string', 'regexp': 'Version: ([^ \\n]+)'}, \\\n    {'name': 'log_dir', 'descr': 'Name of directory containing log file', 'type': 'string'}, \\\n    {'name': 'log_file', 'descr': 'Name of log file', 'type': 'string'}, \\\n    {'name': 'model_file', 'descr': 'Name of PRISM model file', 'type': 'file', 'regexp': 'Parsing model file \"(.+)\"...'}, \\\n    {'name': 'model_consts', 'descr': 'Constants defined for model', 'type': 'string', 'regexp': 'Model constants: (.+)'}, \\\n    {'name': 'model_type', 'descr': 'Model type', 'regexp': 'Type: *(.+)'}, \\\n    {'name': 'states', 'descr': 'Number of states in model', 'regexp': 'States: *(.+) \\((.+) initial\\)'}, \\\n    {'name': 'dd_nodes', 'descr': 'Number of nodes in the DD for the model', 'regexp': 'Transition matrix: *(.+) nodes'}, \\\n    {'name': 'time_constr', 'descr': 'Time to construct the model', 'regexp': 'Time for model construction: *(.+) sec'}, \\\n    {'name': 'prop_file', 'descr': 'Name of PRISM property file', 'type': 'file', 'regexp': 'Parsing properties file \"(.+)\"...'}, \\\n    {'name': 'prop_consts', 'descr': 'Constants defined for property', 'type': 'string', 'regexp': 'Property constants: (.+)'}, \\\n    {'name': 'iters_check', 'descr': 'Iterations for (numerica) model checking', 'regexp': 'took ([^ \\n]+) iterations', 'match': 'last'}, \\\n    {'name': 'time_check', 'descr': 'Time to perform mode checking', 'regexp': 'Time for model checking: *(.+) sec'}, \\\n    {'name': 'result', 'descr': 'Result of mode checking', 'regexp': '^Result.*: ([^( \\n]+)'}, \\\n]\n\n# Names of all fields\nall_fields = list(map(lambda x: x['name'], all_fields_details))\n\n# Meta-fields\nmeta_fields = {\\\n    'all': all_fields, \\\n    'prog': ['prog_name', 'prog_version'], \\\n    'model': ['model_file', 'model_consts'], \\\n    'prop': ['prop_file', 'prop_consts'], \\\n    'benchmark' : ['model_file', 'model_consts', 'prop_file', 'prop_consts'], \\\n}\n\n#==================================================================================================\n# Utility functions\n#==================================================================================================\n\n# Returns a sorted list of files / directories in dir\ndef sorted_list_dir(dir):\n    list = os.listdir(dir);\n    list.sort()\n    return list\n\n#==================================================================================================\n# Functions\n#==================================================================================================\n\n# Takes a list of field names, including \"meta-fields\" (e.g. 'model'\n# is shorthand for 'model_file','model_consts') and expands the meta-fields\ndef expand_meta_fields(fields):\n    fields_expanded = []\n    for field in fields:\n        fields_expanded.extend(meta_fields[field] if field in meta_fields else [field])\n    return fields_expanded\n\n# Get the details of a field\ndef get_field_details(field):\n    return next(filter(lambda x: x['name'] == field, all_fields_details))\n\n# Extract info from a list of files/directories\ndef grep_for_info(fileOrDirs, fields):\n    infos = []\n    for fileOrDir in fileOrDirs:\n        infos += grep_for_info_file_or_dir(fileOrDir, fields)\n    return infos\n\n# Extract info from a single file/directory (recurse unless asked not to)\ndef grep_for_info_file_or_dir(fileOrDir, fields):\n    infos = []\n    if os.path.isdir(fileOrDir):\n        for file in [file for file in sorted_list_dir(fileOrDir) if not file in [\".\",\"..\",\".svn\"]]:\n            if os.path.isdir(os.path.join(fileOrDir, file)):\n                if not options.nonRec:\n                    infos += grep_for_info_file_or_dir(os.path.join(fileOrDir, file), fields)\n            else:\n                infos += grep_for_info_file(os.path.join(fileOrDir, file), fields)\n    else:\n        infos += grep_for_info_file(fileOrDir, fields)\n    return infos\n\n# Extract info from a log file\ndef grep_for_info_file(logFile, fields):\n    if options.extension and not logFile.endswith('.'+options.extension):\n        return []\n    info = {}\n    # Initialise all fields\n    for field in fields:\n        info[field] = ''\n    # For some fields, there is a specific way to define them\n    if 'log_dir' in fields:\n        info['log_dir'] = os.path.basename(os.path.dirname(logFile))\n    if 'log_file' in fields:\n        info['log_file'] = os.path.basename(logFile)\n    # For other fields, we parse the log\n    line_num = 1\n    with open(logFile, 'r') as f:\n        for line in f:\n            # We assume the first line printed out is the tool name\n            if line_num == 1:\n                info['prog_name'] = line.strip()\n            # For most fields, a regexp is used to grep the log\n            for field in fields:\n                field_details = get_field_details(field)\n                if 'regexp' in field_details and (info[field] == '' or ('match' in field_details and field_details['match'] == 'last')):\n                    regexp = field_details['regexp']\n                    m = re.search(regexp, line)\n                    if not m is None:\n                        info[field] = m.group(1)\n            line_num = line_num + 1\n    # Some field processing based on type\n    for field in info.keys():\n        field_details = get_field_details(field)\n        if 'type' in field_details and field_details['type'] == 'file':\n            info[field] = os.path.basename(info[field])\n        if 'type' in field_details and field_details['type'] in ['string', 'file']:\n            info[field] = '\"' + info[field] + '\"'\n    return [info]\n\n# Print info from a log, i.e. a list of fields, comma-separated\ndef print_info(info, fields):\n    values = []\n    for field in fields:\n        values.append(info[field])\n    print(','.join(values))\n\n#==================================================================================================\n# Main program\n#==================================================================================================\n\ndef printUsage():\n    print(\"Usage: prism-log-extract ...\")\n\ndef print_fields():\n    print('Fields:')\n    for field in all_fields_details:\n        print('*', field['name'], ':', field['descr'])\n    print('\\nMeta-fields:')\n    for meta_field, defn in meta_fields.items():\n        print('*', meta_field, ':', '<all fields>' if meta_field=='all' else ','.join(defn))\n\ndef signal_handler(signal, frame):\n    sys.exit(1)\n\n# Parse options\nsignal.signal(signal.SIGINT, signal_handler)\nparser = OptionParser(usage=\"usage: %prog [options] args\")\nparser.add_option(\"--show-fields\", action=\"store_true\", dest=\"showFields\", default=False, help=\"Show all fields that can be extracted\")\nparser.add_option(\"--fields\", dest=\"fields\", metavar=\"X\", default=\"\", help=\"Fields to extract from the log (comma-separated)\")\nparser.add_option(\"--groupby\", dest=\"groupby\", metavar=\"X\", default=\"\", help=\"Group log entries by these fields\")\nparser.add_option(\"--groupkey\", dest=\"groupkey\", metavar=\"X\", default=\"\", help=\"Key used for uniqueness of grouped log entries\")\nparser.add_option(\"--non-recursive\", action=\"store_true\", dest=\"nonRec\", default=False, help=\"Don't recurse into directories\")\nparser.add_option(\"--extension\", dest=\"extension\", metavar=\"ext\", default=\"\", help=\"Process files with name .ext\")\n(options, args) = parser.parse_args()\n\nif options.showFields:\n    print_fields()\n    sys.exit(0)\n\nif len(args) < 1:\n    parser.print_help()\n    sys.exit(1)\n\n# Determine fields to be extracted\nif options.fields:\n    fields = options.fields.split(',')\n    fields = expand_meta_fields(fields)\n    for field in fields:\n        if not field in all_fields:\n            print('Error: Unknown field \"' + field + '\" (valid fields are: ' + ', '.join(all_fields) + ')')\n            sys.exit(1)\n# Default to all fields if none specified\nelse:\n    fields = []+all_fields\n# print('Extracting fields: ' + ','.join(fields))\n\n# Process grouping info\ngroup_by = None\ngroup_key = None\nif options.groupby:\n    group_by = options.groupby\n    group_by = expand_meta_fields([group_by])[0]\n    # Check group_by fields are valid\n    if not group_by in all_fields:\n        print('Error: Unknown \"group by\" field \"' + group_by + '\" (valid fields are: ' + ', '.join(all_fields) + ')')\n        sys.exit(1)\n    # Use default group_key if not provided\n    group_key = options.groupkey.split(',') if options.groupkey else ['benchmark']\n    group_key = expand_meta_fields(group_key)\n    # Check group_key fields are valid\n    for key in group_key:\n        if not key in all_fields:\n            print('Error: Unknown \"group key\" field \"' + key + '\" (valid fields are: ' + ', '.join(all_fields) + ')')\n            sys.exit(1)\n        if key in group_by:\n            print('Error: \"group key\" field \"' + key + ' is already used in \"group by\"')\n            sys.exit(1)\n    # Add group by/key fields to overall list of fields to use\n    fields_new = []\n    fields_new.extend([group_by])\n    fields_new.extend(group_key)\n    fields_new.extend(x for x in fields if x not in fields_new)\n    fields = fields_new\n# print('Group: By: ' + ','.join([group_by]) + ', Key: ' + ','.join(group_key))\n   \n# Extract chosen fields from all files/dirs\ninfos = grep_for_info(args, fields)\n\n# Group entries if requested\nif group_by:\n\n    # Get all values for group by/key\n    group_by_vals = set(map(lambda x: x[group_by], infos))\n    group_key_vals = sorted(set(map(lambda info: '.'.join([info[key] for key in group_key if key in info]), infos)))\n    \n    # Modify list of fields for header\n    # Key fields shown once at the start; others are repeated and prefixed with group\n    fields_new = []\n    fields_new += group_key\n    for group_val in group_by_vals:\n        group_val_trim = group_val.replace('\"', '')\n        fields_new.extend([group_val_trim+':'+field for field in fields if field not in [group_by]+group_key])\n\n    # Iterate through each key/group value and find (at most 1) matching entry\n    infos_new = []\n    for group_key_val in group_key_vals:\n        info_new = {}\n        # Get first matching entry and use to fill group key fields\n        first_info_match = next(filter(lambda info: group_key_val == '.'.join([info[key] for key in group_key if key in info]), infos))\n        info_new.update({x: first_info_match[x] for x in group_key})\n        # For each group\n        for group_val in group_by_vals:\n            group_val_trim = group_val.replace('\"', '')\n            info_matches = [info for info in infos if (group_val == info[group_by] and group_key_val == '.'.join([info[key] for key in group_key if key in info]))]\n            # >1 match: error\n            if len(info_matches) > 1:\n                print('Error: multiple entries matching ' + group_key_val + ' in group ' + group_val)\n                sys.exit(1)\n            # 1 match: store field values with names prefixed with group\n            if len(info_matches) > 0:\n                info = info_matches[0]\n                info_new.update({group_val_trim+':'+field : val for field, val in info.items() if field not in [group_by]+group_key})\n            # 0 matches: store empty field values with names prefixed with group\n            else:\n                info_new.update({group_val_trim+':'+field : \"\" for field in fields if field not in [group_by]+group_key})\n        infos_new.append(info_new)\n    \n    fields = fields_new\n    infos = infos_new\n\n# Print entries (header, then rows)\nprint(','.join(fields))\nfor info in infos:\n    print_info(info, fields)\n"
  },
  {
    "path": "prism/etc/scripts/prism-pareto.py",
    "content": "#! /usr/bin/env python3\n# coding=utf-8\n\n# run without arguments for usage info\n\nimport re\nimport sys\nimport os\nfrom optparse import OptionParser\nimport matplotlib as mpl\nfrom mpl_toolkits.mplot3d import Axes3D\nfrom matplotlib.axes import Axes\nimport matplotlib.pyplot as plt\nfrom matplotlib.collections import PolyCollection\nfrom mpl_toolkits.mplot3d.art3d import Poly3DCollection\n\ndescr = \"This Python script allows to visualise a 3D Pareto curve generated by PRISM.\"\nparser = OptionParser(usage=\"usage: %prog input_file\",version=\"alpha1 (2012-03-04)\", description=descr)\n(options, args) = parser.parse_args()\n\nif len(args) != 1:\n\tparser.print_help()\n\tsys.exit(1)\n\n#open input file\ntry :\n\tfile = open(args[0])\nexcept IOError as e:\n\tprint \"Cannot read the input file '\" + e.filename + \"': \" + e.strerror >> sys.stderr\n\tsys.exit(1)\n\ncol = []\nmaxX = 0;\nmaxY = 0;\nmaxZ = 0;\nfor line in file:\n\ttile = []\n        coords = line.split(';')\n\tfor pointStr in coords:\n\t\tpoint = pointStr.split(',')\n\t\tx= float(point[0])\n\t\ty= float(point[1])\n\t\tmaxX = x if (maxX < x) else maxX  \n\t\tmaxY = y if (maxY < y) else maxY  \n\t\tif len(point) > 2:\n\t\t\tz = float(point[2])\n\t\t\tmaxZ = z if (maxZ < z) else maxZ  \n\t\t\tvert = (x,y,z)\n\t\telse:\n\t\t\tvert = (x,y)\n\t\ttile.append(vert)\n\tcol.append(tile)\n\nmpl.rcParams['legend.fontsize'] = 10\n\nfig = plt.figure()\nfig.clf()\ndim = len(col[0][0])\nif dim == 3:\n\tax = fig.add_subplot(111, projection='3d')\n\tpoly = Poly3DCollection(col)\n\tax.add_collection3d(poly)\n\tax.set_zlabel(\"objective 3\")\n\tax.set_zlim(0, maxZ * 1.1)\nelse:\n\tax = fig.add_subplot(111)\n\tpoly = PolyCollection(col)\n\tax.add_collection(poly)\n\nax.set_xlim(0, maxX * 1.1)\nax.set_ylim(0, maxY * 1.1)\nax.set_xlabel(\"objective 1\")\nax.set_ylabel(\"objective 2\")\n\nplt.show()\nplt.draw()\n"
  },
  {
    "path": "prism/etc/scripts/prism-statra",
    "content": "#!/bin/sh\n\n# Script to combine PRISM states and transitions files\n\n# Launch using main PRISM script\nPRISM_MAINCLASS=\"prism.PrismStaTra\"\nexport PRISM_MAINCLASS\nprism \"$@\"\n"
  },
  {
    "path": "prism/etc/scripts/prism-test",
    "content": "#!/bin/sh\n\nprism-auto -m -t \"$@\"\n"
  },
  {
    "path": "prism/etc/scripts/prism2html",
    "content": "#!/bin/sh\n\n# Startup script for PRISM to HTML converter (Linux/Solaris)\n\n# Launch using main PRISM script\nPRISM_MAINCLASS=\"parser.PrismSyntaxHighlighter html\"\nexport PRISM_MAINCLASS\nprism \"$@\"\n"
  },
  {
    "path": "prism/etc/scripts/prism2latex",
    "content": "#!/bin/sh\n\n# Startup script for PRISM to LaTeX converter (Linux/Solaris)\n\n# Launch using main PRISM script\nPRISM_MAINCLASS=\"parser.PrismSyntaxHighlighter latex\"\nexport PRISM_MAINCLASS\nprism \"$@\"\n"
  },
  {
    "path": "prism/etc/scripts/prism3to4",
    "content": "#!/bin/sh\n\n# Script for conversion of old PRISM files (Linux/Solaris)\n\nif [ \"$1\" = \"\" ]; then\n  echo \"Usage: prism3to4 <file> [<outfile>]\"\n  exit\nfi\n\n# Run using main PRISM script with this class\nPRISM_MAINCLASS=\"parser.Prism3To4\"\nexport PRISM_MAINCLASS\n\nif [ \"$2\" = \"\" ]; then\n  prism \"$1\"\nelse\n  if [ \"$2\" = \"$1\" ]; then\n    ( prism \"$1\" > \"$2\".new && mv \"$2\".new \"$2\" ) || rm \"$2\".new\n  else\n    prism \"$1\" > \"$2\"\n  fi\nfi\n\n"
  },
  {
    "path": "prism/etc/scripts/sbml2prism",
    "content": "#!/bin/sh\n\n# Startup script for SBML to PRISM converter (Linux/Mac/Solaris)\n\n# Launch using main PRISM script\nPRISM_MAINCLASS=\"prism.SBML2Prism\"\nexport PRISM_MAINCLASS\nprism \"$@\"\n"
  },
  {
    "path": "prism/etc/syntax-highlighters/gnome/Overrides.xml",
    "content": "<?xml version='1.0' encoding='utf-8'?>\n\n<!-- This file can be used to define a MIME type for PRISM files under the Gnome desktop -->\n<!-- Save the file as ~/.local/share/mime/packages/Overrides.xml and then run: -->\n<!--   update-mime-database ~/.local/share/mime -->\n\n<!-- Please note that this overrides the association of .pm file with Perl files -->\n<!-- If you do not want this, then comment out the .pm line below -->\n\n<mime-info xmlns=\"http://www.freedesktop.org/standards/shared-mime-info\">\n  <mime-type type=\"text/x-prism\">\n    <sub-class-of type=\"text/x-csrc\"/> <!-- just to prevent mis-detection as C -->\n    <comment>PRISM file</comment>\n    <magic priority=\"51\">\n      <match type=\"string\" value=\"dtmc\" offset=\"0\"/>\n      <match type=\"string\" value=\"ctmc\" offset=\"0\"/>\n      <match type=\"string\" value=\"mdp\" offset=\"0\"/>\n      <match type=\"string\" value=\"probabilistic\" offset=\"0\"/>\n      <match type=\"string\" value=\"nondeterministic\" offset=\"0\"/>\n      <match type=\"string\" value=\"stochastic\" offset=\"0\"/>\n    </magic>\n    <glob pattern=\"*.prism\"/>\n    <glob pattern=\"*.pm\"/>\n    <glob pattern=\"*.sm\"/>\n    <glob pattern=\"*.nm\"/>\n    <glob pattern=\"*.props\"/>\n    <glob pattern=\"*.pctl\"/>\n    <glob pattern=\"*.csl\"/>\n    <glob pattern=\"*.pp\"/>\n  </mime-type>\n</mime-info>\n"
  },
  {
    "path": "prism/etc/syntax-highlighters/gnome/prism.lang",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE language SYSTEM \"language.dtd\">\n\n<!-- Syntax highlighting patterns for Gnome editors such as gedit -->\n<!-- Save this file in ~/.gnome2/gtksourceview-1.0/language-specs/ -->\n<!-- After a restart of Gnome, \"PRISM\" should appear as a highlight mode under \"Others\" -->\n\n<!-- See the file Overrides.xml for info about adding MIME types under Gnome -->\n\n<language _name=\"PRISM\" version=\"1.0\" _section=\"Others\" mimetypes=\"text/x-prism\">\n\n\t<line-comment _name = \"Line Comment\" style= \"Comment\">\n\t\t<start-regex>//</start-regex>\n\t</line-comment>\n\n\t<syntax-item _name = \"PRISM Preprocessor\" style = \"Preprocessor\">\n\t\t<start-regex>#</start-regex><end-regex>#</end-regex>\n\t</syntax-item>\n\n\t<pattern-item _name = \"Numeric\" style = \"Decimal\">\n\t\t<regex>(\\b([1-9][0-9]*|0)\\b)|(\\b([0-9]+[Ee][+-]?[0-9]+|([0-9]*\\.[0-9]+|[0-9]+\\.)([Ee][-]?[0-9]+)?)[fFlL]?)</regex>\n\t</pattern-item>\n\t\n\t<pattern-item _name = \"Identifiers\" style = \"Data Type\">\n\t\t<regex>[a-zA-Z_][a-zA-Z0-9_]*</regex>\n\t</pattern-item>\n\t\n\t<keyword-list _name = \"Keywords\" style = \"Keyword\" case-sensitive=\"TRUE\">\n\t\t<keyword>bool</keyword>\n\t\t<keyword>C</keyword>\n\t\t<keyword>ceil</keyword>\n\t\t<keyword>const</keyword>\n\t\t<keyword>ctmc</keyword>\n\t\t<keyword>double</keyword>\n\t\t<keyword>dtmc</keyword>\n\t\t<keyword>endinit</keyword>\n\t\t<keyword>endmodule</keyword>\n\t\t<keyword>endrewards</keyword>\n\t\t<keyword>endsystem</keyword>\n\t\t<keyword>F</keyword>\n\t\t<keyword>false</keyword>\n\t\t<keyword>floor</keyword>\n\t\t<keyword>formula</keyword>\n\t\t<keyword>func</keyword>\n\t\t<keyword>G</keyword>\n\t\t<keyword>global</keyword>\n\t\t<keyword>I</keyword>\n\t\t<keyword>init</keyword>\n\t\t<keyword>int</keyword>\n\t\t<keyword>label</keyword>\n\t\t<keyword>max</keyword>\n\t\t<keyword>mdp</keyword>\n\t\t<keyword>min</keyword>\n\t\t<keyword>module</keyword>\n\t\t<keyword>nondeterministic</keyword>\n\t\t<keyword>P</keyword>\n\t\t<keyword>Pmax</keyword>\n\t\t<keyword>Pmin</keyword>\n\t\t<keyword>prob</keyword>\n\t\t<keyword>probabilistic</keyword>\n\t\t<keyword>R</keyword>\n\t\t<keyword>rate</keyword>\n\t\t<keyword>rewards</keyword>\n\t\t<keyword>Rmax</keyword>\n\t\t<keyword>Rmin</keyword>\n\t\t<keyword>S</keyword>\n\t\t<keyword>stochastic</keyword>\n\t\t<keyword>system</keyword>\n\t\t<keyword>true</keyword>\n\t\t<keyword>U</keyword>\n\t\t<keyword>X</keyword>\n\t</keyword-list>\n\n</language>\n"
  },
  {
    "path": "prism/etc/syntax-highlighters/nedit/prism.pats",
    "content": "! This file is used to provide syntax highlighting for PRISM\n! in the NEdit editor (www.nedit.org).\n!\n! To use it, close any NEdit programs and restart with:\n!\n!     nedit -import prism.pats\n!\n! Now, select \"Save Defaults\" from the \"Preferences\" menu\n! to save these changes to your personal settings.\n!\n! You can view or modify the syntax highlighting settings from:\n!\n! \t\"Preferences | Default Settings | Language Modes\"\n! \t\"Preferences | Default Settings | Syntax Highlighting\"\n!\n! In theory, the PRISM language mode should be automatically started\n! in NEdit when a file with an associated extension is loaded:\n!\n! \t.pm .nm .sm .pctl .csl\n!\n! In fact, this is not always the case since these extensions overlap\n! with those for other programs (e.g. .pm for Perl and .nm for NEdit macros).\n! To overide this at any time, select:\n!\n! \t\"Preferences | Language Mode | PRISM\"\n!\n! For a more permanent solution, select:\n!\n! \t\"Preferences | Default Settings | Language Modes\"\n!\n! and move \"PRISM\" higher up the list of modes using the \"Move ^\" button.\n\nnedit.highlightPatterns: PRISM:1:0{\\n\\\n\t\tComment:\"//\":\"$\"::PRISM Comment::\\n\\\n\t\tPreprocessor:\"#\":\"#\"::PRISM Preprocessor::\\n\\\n\t\tKeyword:\"<(bool|C|ceil|const|ctmc|double|dtmc|endinit|endmodule|endrewards|endsystem|F|false|floor|formula|func|G|global|I|init|int|label|max|mdp|min|module|nondeterministic|P|Pmax|Pmin|prob|probabilistic|R|rate|rewards|Rmax|Rmin|S|stochastic|system|true|U|X)>\":::Keyword::\\n\\\n\t\tIdentifier:\"<([A-Za-z_][A-Za-z0-9_]*)>\":::PRISM Identifier::\\n\\\n\t\tNumeric:\"<(([0-9]*(\\\\.)?[0-9]+([eE]([-+])?[0-9]+)?)|([1-9][0-9]*)|0)>\":::PRISM Numeric::\\n\\\n\t}\nnedit.languageModes: \tPRISM:.prism .pm .nm .sm .props .pctl .csl .pp::::::\"!&|->:;,.()[]{}=<+*/'?\"\"\":\nnedit.styles: \tPRISM Comment:darkGreen:Italic\\n\\\n\tPRISM Identifier:darkRed:Plain\\n\\\n\tPRISM Numeric:Blue:Plain\\n\\\n\tPRISM Preprocessor:purple:Plain\n"
  },
  {
    "path": "prism/etc/syntax-highlighters/textwrangler/prism.plist",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\"?>\n<!DOCTYPE plist PUBLIC \"-//Apple//DTD PLIST 1.0//EN\" \"http://www.apple.com/DTDs/PropertyList-1.0.dtd\">\n\n<!--\nPRISM syntax highlighting for TextWrangler.\nCopy this file into ~/Library/Application Support/TextWrangler/Language Modules/\n(creating this directory if necessary).\n-->\n\n<plist version=\"1.0\">\n<dict>\n\t<key>BBEditDocumentType</key>\n\t<string>CodelessLanguageModule</string>\n\t<key>BBLMLanguageDisplayName</key>\n\t<string>PRISM</string>\n\t<key>BBLMLanguageCode</key>\n\t<string>PRIS</string>\n\t<key>BBLMColorsSyntax</key>\n\t<true/>\n\t<key>BBLMScansFunctions</key>\n\t<false/>\n\t<key>BBLMIsCaseSensitive</key>\n\t<true/>\n\t<key>BBLMKeywordList</key>\n\t<array>\n\t\t<string>bool</string>\n\t\t<string>C</string>\n\t\t<string>ceil</string>\n\t\t<string>const</string>\n\t\t<string>ctmc</string>\n\t\t<string>double</string>\n\t\t<string>dtmc</string>\n\t\t<string>endinit</string>\n\t\t<string>endmodule</string>\n\t\t<string>endrewards</string>\n\t\t<string>endsystem</string>\n\t\t<string>F</string>\n\t\t<string>false</string>\n\t\t<string>floor</string>\n\t\t<string>formula</string>\n\t\t<string>func</string>\n\t\t<string>G</string>\n\t\t<string>global</string>\n\t\t<string>I</string>\n\t\t<string>init</string>\n\t\t<string>int</string>\n\t\t<string>label</string>\n\t\t<string>max</string>\n\t\t<string>mdp</string>\n\t\t<string>min</string>\n\t\t<string>module</string>\n\t\t<string>nondeterministic</string>\n\t\t<string>P</string>\n\t\t<string>Pmax</string>\n\t\t<string>Pmin</string>\n\t\t<string>prob</string>\n\t\t<string>probabilistic</string>\n\t\t<string>R</string>\n\t\t<string>rate</string>\n\t\t<string>rewards</string>\n\t\t<string>Rmax</string>\n\t\t<string>Rmin</string>\n\t\t<string>S</string>\n\t\t<string>stochastic</string>\n\t\t<string>system</string>\n\t\t<string>true</string>\n\t\t<string>U</string>\n\t\t<string>X</string>\n\t</array>\n\t<key>BBLMSuffixMap</key>\n\t<array>\n\t\t<dict>\n\t\t\t<key>BBLMLanguageSuffix</key>\n\t\t\t<string>.prism</string>\n\t\t</dict>\n\t\t<dict>\n\t\t\t<key>BBLMLanguageSuffix</key>\n\t\t\t<string>.pm</string>\n\t\t</dict>\n\t\t<dict>\n\t\t\t<key>BBLMLanguageSuffix</key>\n\t\t\t<string>.nm</string>\n\t\t</dict>\n\t\t<dict>\n\t\t\t<key>BBLMLanguageSuffix</key>\n\t\t\t<string>.sm</string>\n\t\t</dict>\n\t\t<dict>\n\t\t\t<key>BBLMLanguageSuffix</key>\n\t\t\t<string>.props</string>\n\t\t</dict>\n\t\t<dict>\n\t\t\t<key>BBLMLanguageSuffix</key>\n\t\t\t<string>.pctl</string>\n\t\t</dict>\n\t\t<dict>\n\t\t\t<key>BBLMLanguageSuffix</key>\n\t\t\t<string>.csl</string>\n\t\t</dict>\n\t</array>\n\t<key>Language Features</key>\n\t<dict>\n\t\t<key>Open Line Comments</key>\n\t\t<string>//</string>\n\t\t<key>Identifier and Keyword Characters</key>\n\t\t<string>0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ_abcdefghijklmnopqrstuvwxyz</string>\n\t</dict>\n</dict>\n</plist>\n"
  },
  {
    "path": "prism/etc/syntax-highlighters/vim/README",
    "content": "To install, copy the files prismmodel.vim and prismproperty.vim to a directory where syntax files reside, e.g. on Unix this can be the ~/.vim/syntax/ directory\n\nThen add the following 3 lines to your filetype.vim (on Unix, this can be in ~/.vim/filetype.vim):\n\nau BufRead,BufNewFile *.prism setfiletype prismmodel\nau BufRead,BufNewFile *.[pns]m setfiletype prismmodel\nau BufRead,BufNewFile *.smg setfiletype prismmodel\nau BufRead,BufNewFile *.props setfiletype prismproperty\nau BufRead,BufNewFile *.pctl setfiletype prismproperty\n"
  },
  {
    "path": "prism/etc/syntax-highlighters/vim/prismmodel.vim",
    "content": "\" Vim syntax file\n\" Language: PRISM model files\n\" Latest Revision: 20 October 2011\n\nif exists(\"b:current_syntax\")\n  finish\nendif\n\nsyn keyword prismStructureKeyword ctmc dtmc mdp smg module endmodule formula nondeterministic probabilistic pta stochastic invariant endinvariant rewards endrewards init endinit system endsystem player endplayer\nsyn keyword prismBool true false\nsyn keyword prismVariableType bool clock const double global int rate label filter func\nsyn keyword prismFunction max min\n\nsyn region prismString start='\"' end='\"'\n\nsyn match prismOp \"[&|<>=!+\\-*/:?]\"\nsyn match prismNumber \"[0-9][0-9]*\"\nsyn match prismVariableName \"[_a-zA-Z][_a-zA-Z0-9]*\"\nsyn match prismComment \"//.*$\"\nsyn match prismArrow \"->\"\nsyn match prismActionEmpty \"\\[\\]\"\nsyn match prismAction \"\\[[a-zA-Z][a-zA-Z0-9]*\\]\"\n\n\" A, , C  E, F, G, I, X, Pmax, Pmin, P prob,  Rmax, Rmin, R, S, U, W.\n\nhi def link prismStructureKeyword Keyword\nhi def link prismVariableType Type\nhi def link prismVariableName Identifier\nhi def link prismNumber Number\nhi def link prismBool Boolean\nhi def link prismComment Comment\nhi def link prismString String\nhi def link prismArrow Operator\nhi def link prismOp Operator\nhi def link prismActionEmpty Special\nhi def link prismAction Special\n"
  },
  {
    "path": "prism/etc/syntax-highlighters/vim/prismproperty.vim",
    "content": "\" Vim syntax file\n\" Language: PRISM property files\n\" Latest Revision: 20 October 2011\n\nif exists(\"b:current_syntax\")\n  finish\nendif\n\nsyn match prismOp \"[&|=<>]\"\nsyn keyword prismFilterParam min max count sum avg first range forall exists state argmin argmax print\nsyn keyword prismStructureKeyword filter \nsyn keyword prismBool true false\nsyn keyword prismVariableType bool  double int const\nsyn match prismVariableName \"[_a-zA-Z][_a-zA-Z0-9]*\"\nsyn match prismNumber \"[0-9][0-9]*\"\nsyn match prismComment \"//.*$\" contains=prismResult\nsyn match prismResult \"RESULT.*$\" contained\nsyn match prismStatePROperator \"[PRS]\\({[^\\}]*}\\|\\)\\(min\\|max\\|\\)[=<>?]*[0-9]*\" contains=prismNumberInOperator,prismString\nsyn match prismTemporalOperator \"[ACEFGIXUW][=<>?]*[0-9]*\" contains=prismNumberInOperator\nsyn match prismCoalition \"<<[^>]*>>\" contains=prismNumberInOperator\nsyn match prismNumberInOperator \"[0-9]*\" contained\nsyn region prismString start='\"' end='\"'\n\n\n\nhi def link prismStructureKeyword Keyword\nhi def link prismVariableType Type\nhi def link prismVariableName Identifier\nhi def link prismBool Boolean\nhi def link prismNumberInOperator Number\nhi def link prismNumber Number\nhi def link prismComment Comment\nhi def link prismString String\nhi def link prismStatePROperator Operator\nhi def link prismTemporalOperator Operator\nhi def link prismTempOperator Operator\nhi def link prismCoalition Operator\nhi def link prismFilterParam Keyword\nhi def link prismOp Operator\nhi def link prismResult PreProc\n"
  },
  {
    "path": "prism/etc/tests/dtmc_pctl.prism",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[r] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n\r\nrewards \"r\"\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism/etc/tests/dtmc_pctl.prism.props",
    "content": "// RESULT: 1/6\nP=? [ F s=2 ];\n"
  },
  {
    "path": "prism/etc/tests/dtmc_pctl.prism.props.args",
    "content": "-ex\n-h\n"
  },
  {
    "path": "prism/etc/tests/run.sh",
    "content": "#!/bin/sh\n\nset -e # Abort if one of the commands fail\nset -x # Print commands as they are executed\n\n# Tests to check key libraries/components are installed\n\n# Can be run manually from this directory, with \"prism-test .\" (or \"prism-auto -tm .\")\n\n# This script is intended to be run from from ../..\n# (the below is generated from ../.. by: \"prism-test -e etc/tests -p bin/prism\")\n\nbin/prism etc/tests/dtmc_pctl.prism etc/tests/dtmc_pctl.prism.props -ex -test\nbin/prism etc/tests/dtmc_pctl.prism etc/tests/dtmc_pctl.prism.props -h -test\nbin/prism etc/tests/test_lpsolve_mdpmo.prism etc/tests/test_lpsolve_mdpmo.prism.props -lp -test\n"
  },
  {
    "path": "prism/etc/tests/test_lpsolve_mdpmo.prism",
    "content": "// simple example where the values of y_{v,sigma} are > 1\r\n// example formula: multi(P>=0.3[F x=3],P>=0.75[F x=2])\r\n// only two points: [0.6,0.4], [0.0,1.0] \r\n\r\nmodule M\r\n\r\nx:[0..3] init 0;\r\n\r\n[] x=0 -> (x'=1);\r\n[a] x=1 -> 0.4 : (x'=2) + 0.6: (x'=3);\r\n[b] x=1 -> (x'=2);\r\n[] x=2 -> (x'=2);\r\n[] x=3 -> (x'=3);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism/etc/tests/test_lpsolve_mdpmo.prism.props",
    "content": "// RESULT: 0.25\nmulti(Pmax=? [F x=3],P>=0.75[F x=2])\n"
  },
  {
    "path": "prism/etc/tests/test_lpsolve_mdpmo.prism.props.args",
    "content": "-lp\n"
  },
  {
    "path": "prism/ext/README.md",
    "content": "This directory contains various external libraries, either in source or binary form.\n\nTo simplify maintenance of scripts and config files, we mostly omit version numbers in the filenames. For reference, they are:\n\n* lpsolve (and its Java wrapper) - modification of version 5.5.2.0 (and version 5.5.0.14)\n\nSee here for more details and links:\n\nhttps://www.prismmodelchecker.org/other-downloads.php\n\nand here for further details about compilation:\n\nhttps://github.com/prismmodelchecker/prism/wiki\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/CHANGES.txt",
    "content": "\nThis file contains the version history of the lp_solve Java wrapper.\nThe wrapper has no version numbering of its own but follows the\nversion scheme of lp_solve.\n\n5.5.0.14\n--------\n- The build scripts now also generate 64 bit versions in win64 or ux64 directories.\n- build scripts added for unix and tested on unix\n- lpsolve5j.cpp gave some warning about delete on void pointer. Modified.\n\n5.5.0.11\n--------\n- New API resizeLp for lp_solve 5.5.0.11 added\n\n5.5.0.9 (07.09.2006)\n--------------------\n- Revised unittest program because it gave some errors and warnings that it shouldn't give.\n\n\n5.5.0.8 (27.08.2006)\n--------------------\n- New API guessBasis for lp_solve 5.5.0.8 added\n\n\n5.5.0.2 beta (26.06.2005)\n--------------------\n- New API constants for lp_solve 5.5.0.2 added\n- New test cases\n\n\n5.5.0.0 beta (23.05.2005)\n--------------------\n- API changes for lp_solve 5.5.0.0 implemented\n- lp_solve 5.5.0.0 is still beta, so there are known bugs that also\n  show up in the Java wrapper\n- Some unit tests are missing for new API functions so the wrapper code\n  is to some extent untested.\n\n\n5.1.1.3 (17.03.2005)\n--------------------\n- API changes for lp_solve 5.1.1.3 implemented (read_basis, write_basis)\n- Relaxed JNI Version requirement to 1.2 in order to support also JDK 1.3\n- Tested also with JDK 1.5 (5.0): runs without changes on new Java version\n- Java classes are now precompiled with JDK 1.5, but with 1.4 as target\n  platform to ensure backward compatibility\n\n\n5.1.1.2 (05.01.2005)\n--------------------\n- API changes for lp_solve 5.1.1.1 implemented (no changes for 5.1.1.2).\n- Removed some constants which are only internally used from LpSolve class.\n\n\n5.1.1.0 (01.12.2004)\n--------------------\n- API changes for lp_solve 5.1.1.0 implemented (only two constants added).\n- Class files in demo directory are now packed in jar archives.\n- Updated build file for Mac OS X from Sean P. Kane.\n\n\n5.1.0.2 (21.09.2004)\n--------------------\n- Added a build file to compile the stub library on Mac OS X.\n  Thanks to Sean P. Kane who provided this script.\n\n\n5.1.0.1 (12.09.2004)\n--------------------\n- API changes for lp_solve 5.1.0.1 implemented (only two constants added).\n- Added a description how to call lp_solve functions from Python/Jython\n  to README.html and a Python demo program to the demo directory.\n- Tests for set_column(ex) and set_row enabled again\n\n\n5.1.0.0 (08.09.2004)\n--------------------\n- API changes for lp_solve 5.1.0.0 implemented.\n- Wrapper libraries renamed to lpsolve51j.dll (liblpsolve51.so for Linux)\n  and lpsolve51.jar to keep in sync with the naming conventions of\n  the core lp_solve distribution.\n- Tests for set_row(ex) and set_column(ex) temporarily disabled until\n  issue is resolved in lp_solve\n- Demo program now shows the use of callback functions.\n- writeLp, writeMps, writeFreeMps and writeXLI and their read* equivalents\n  now accept filenames with native (non UTF-8) characters.\n- Resetting the callback functions to default values did not work\n  correctly. Fixed.\n\n\n5.0.10.0 (24.07.2004)\n--------------------\n- API changes for lp_solve 5.0.10.0 implemented.\n- Added more test cases.\n- Some changes in doc file README.html\n\n\n5.0.9.0 (22.06.2004)\n--------------------\n- API changes for lp_solve 5.0.9.0 implemented, including new XLI functions.\n- getUpbo and getLowbo were not implemented correctly. Fixed.\n- The methods in the listener interfaces for the lp_solve callback functions\n  are now declared to throw an LpSolveException to allow implementing classes\n  to throw such an exception.\n- Added more test cases.\n- Added junit.jar and batch/shell scripts to run the JUnit testcases on\n  Windows and Linux.\n\n\n5.0.8.1 (14.06.2004)\n--------------------\n- Moved lpsolve5j.dll from lib to lib\\win32 and added a build script for\n  Microsoft Visual C++ compiler.\n- Added a Linux shared library and gcc build script to lib\\linux.\n- Minor C source modifications to make it compile on Linux.\n- Documentation modifications for Linux lib.\n- The following lp_solve functions were not implemented in the wrapper:\n  get_ptr_dual_solution, get_ptr_sensitivity_obj, get_ptr_sensitivity_rhs,\n  is_constr_type, is_piv_rule, print_str. Fixed.\n- Changed setPreferduals (Java) parameter type from int to boolean.\n- The names of the methods getLambda and getPtrLambda were reversed. Fixed.\n- Changed getRow and getColumn which now exctly follow the lp_solve API\n  and return their results in an array which must be allocated by the caller.\n- Added the methods getPtrRow and getPtrColumn (which are not in lp_solve) for\n  convenience. Their return value is an array allocated by the method.\n- Added more test cases.\n\n\n5.0.8.0 (06.06.2004)\n--------------------\n- To avoid confusion with the lp_solve version numbering and in order to be\n  consistent with the naming conventions of the other interface libraries,\n  the lpsolve4j software has been renamed. The distribution archive is now\n  called lp_solve_5.0_java.zip. The libraries have been renamed to lpsolve5j.dll\n  and lpsolve5j.jar. The package name of the LpSolve class has been renamed\n  from lpsolve4j to lpsolve. Documentation has been updated to avoid the usage\n  of lpsolve4j completely.\n- Implementation of API changes from lp_solve 5.0.7.0 and 5.0.8.0\n- Added file CHANGES.txt in docs directory for version history\n- Source files are now compiled with the header files from lp_solve5.zip\n  instead of using the sources.\n\n\n5.0.6.0 (27.05.2004)\n--------------------\n- Implementation of API changes from lp_solve 5.0.6.0\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/LGPL",
    "content": "\t\t  GNU LESSER GENERAL PUBLIC LICENSE\r\n\t\t       Version 2.1, February 1999\r\n\r\n Copyright (C) 1991, 1999 Free Software Foundation, Inc.\r\n     59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n Everyone is permitted to copy and distribute verbatim copies\r\n of this license document, but changing it is not allowed.\r\n\r\n[This is the first released version of the Lesser GPL.  It also counts\r\n as the successor of the GNU Library Public License, version 2, hence\r\n the version number 2.1.]\r\n\r\n\t\t\t    Preamble\r\n\r\n  The licenses for most software are designed to take away your\r\nfreedom to share and change it.  By contrast, the GNU General Public\r\nLicenses are intended to guarantee your freedom to share and change\r\nfree software--to make sure the software is free for all its users.\r\n\r\n  This license, the Lesser General Public License, applies to some\r\nspecially designated software packages--typically libraries--of the\r\nFree Software Foundation and other authors who decide to use it.  You\r\ncan use it too, but we suggest you first think carefully about whether\r\nthis license or the ordinary General Public License is the better\r\nstrategy to use in any particular case, based on the explanations below.\r\n\r\n  When we speak of free software, we are referring to freedom of use,\r\nnot price.  Our General Public Licenses are designed to make sure that\r\nyou have the freedom to distribute copies of free software (and charge\r\nfor this service if you wish); that you receive source code or can get\r\nit if you want it; that you can change the software and use pieces of\r\nit in new free programs; and that you are informed that you can do\r\nthese things.\r\n\r\n  To protect your rights, we need to make restrictions that forbid\r\ndistributors to deny you these rights or to ask you to surrender these\r\nrights.  These restrictions translate to certain responsibilities for\r\nyou if you distribute copies of the library or if you modify it.\r\n\r\n  For example, if you distribute copies of the library, whether gratis\r\nor for a fee, you must give the recipients all the rights that we gave\r\nyou.  You must make sure that they, too, receive or can get the source\r\ncode.  If you link other code with the library, you must provide\r\ncomplete object files to the recipients, so that they can relink them\r\nwith the library after making changes to the library and recompiling\r\nit.  And you must show them these terms so they know their rights.\r\n\r\n  We protect your rights with a two-step method: (1) we copyright the\r\nlibrary, and (2) we offer you this license, which gives you legal\r\npermission to copy, distribute and/or modify the library.\r\n\r\n  To protect each distributor, we want to make it very clear that\r\nthere is no warranty for the free library.  Also, if the library is\r\nmodified by someone else and passed on, the recipients should know\r\nthat what they have is not the original version, so that the original\r\nauthor's reputation will not be affected by problems that might be\r\nintroduced by others.\r\n\f\r\n  Finally, software patents pose a constant threat to the existence of\r\nany free program.  We wish to make sure that a company cannot\r\neffectively restrict the users of a free program by obtaining a\r\nrestrictive license from a patent holder.  Therefore, we insist that\r\nany patent license obtained for a version of the library must be\r\nconsistent with the full freedom of use specified in this license.\r\n\r\n  Most GNU software, including some libraries, is covered by the\r\nordinary GNU General Public License.  This license, the GNU Lesser\r\nGeneral Public License, applies to certain designated libraries, and\r\nis quite different from the ordinary General Public License.  We use\r\nthis license for certain libraries in order to permit linking those\r\nlibraries into non-free programs.\r\n\r\n  When a program is linked with a library, whether statically or using\r\na shared library, the combination of the two is legally speaking a\r\ncombined work, a derivative of the original library.  The ordinary\r\nGeneral Public License therefore permits such linking only if the\r\nentire combination fits its criteria of freedom.  The Lesser General\r\nPublic License permits more lax criteria for linking other code with\r\nthe library.\r\n\r\n  We call this license the \"Lesser\" General Public License because it\r\ndoes Less to protect the user's freedom than the ordinary General\r\nPublic License.  It also provides other free software developers Less\r\nof an advantage over competing non-free programs.  These disadvantages\r\nare the reason we use the ordinary General Public License for many\r\nlibraries.  However, the Lesser license provides advantages in certain\r\nspecial circumstances.\r\n\r\n  For example, on rare occasions, there may be a special need to\r\nencourage the widest possible use of a certain library, so that it becomes\r\na de-facto standard.  To achieve this, non-free programs must be\r\nallowed to use the library.  A more frequent case is that a free\r\nlibrary does the same job as widely used non-free libraries.  In this\r\ncase, there is little to gain by limiting the free library to free\r\nsoftware only, so we use the Lesser General Public License.\r\n\r\n  In other cases, permission to use a particular library in non-free\r\nprograms enables a greater number of people to use a large body of\r\nfree software.  For example, permission to use the GNU C Library in\r\nnon-free programs enables many more people to use the whole GNU\r\noperating system, as well as its variant, the GNU/Linux operating\r\nsystem.\r\n\r\n  Although the Lesser General Public License is Less protective of the\r\nusers' freedom, it does ensure that the user of a program that is\r\nlinked with the Library has the freedom and the wherewithal to run\r\nthat program using a modified version of the Library.\r\n\r\n  The precise terms and conditions for copying, distribution and\r\nmodification follow.  Pay close attention to the difference between a\r\n\"work based on the library\" and a \"work that uses the library\".  The\r\nformer contains code derived from the library, whereas the latter must\r\nbe combined with the library in order to run.\r\n\f\r\n\t\t  GNU LESSER GENERAL PUBLIC LICENSE\r\n   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION\r\n\r\n  0. This License Agreement applies to any software library or other\r\nprogram which contains a notice placed by the copyright holder or\r\nother authorized party saying it may be distributed under the terms of\r\nthis Lesser General Public License (also called \"this License\").\r\nEach licensee is addressed as \"you\".\r\n\r\n  A \"library\" means a collection of software functions and/or data\r\nprepared so as to be conveniently linked with application programs\r\n(which use some of those functions and data) to form executables.\r\n\r\n  The \"Library\", below, refers to any such software library or work\r\nwhich has been distributed under these terms.  A \"work based on the\r\nLibrary\" means either the Library or any derivative work under\r\ncopyright law: that is to say, a work containing the Library or a\r\nportion of it, either verbatim or with modifications and/or translated\r\nstraightforwardly into another language.  (Hereinafter, translation is\r\nincluded without limitation in the term \"modification\".)\r\n\r\n  \"Source code\" for a work means the preferred form of the work for\r\nmaking modifications to it.  For a library, complete source code means\r\nall the source code for all modules it contains, plus any associated\r\ninterface definition files, plus the scripts used to control compilation\r\nand installation of the library.\r\n\r\n  Activities other than copying, distribution and modification are not\r\ncovered by this License; they are outside its scope.  The act of\r\nrunning a program using the Library is not restricted, and output from\r\nsuch a program is covered only if its contents constitute a work based\r\non the Library (independent of the use of the Library in a tool for\r\nwriting it).  Whether that is true depends on what the Library does\r\nand what the program that uses the Library does.\r\n  \r\n  1. You may copy and distribute verbatim copies of the Library's\r\ncomplete source code as you receive it, in any medium, provided that\r\nyou conspicuously and appropriately publish on each copy an\r\nappropriate copyright notice and disclaimer of warranty; keep intact\r\nall the notices that refer to this License and to the absence of any\r\nwarranty; and distribute a copy of this License along with the\r\nLibrary.\r\n\r\n  You may charge a fee for the physical act of transferring a copy,\r\nand you may at your option offer warranty protection in exchange for a\r\nfee.\r\n\f\r\n  2. You may modify your copy or copies of the Library or any portion\r\nof it, thus forming a work based on the Library, and copy and\r\ndistribute such modifications or work under the terms of Section 1\r\nabove, provided that you also meet all of these conditions:\r\n\r\n    a) The modified work must itself be a software library.\r\n\r\n    b) You must cause the files modified to carry prominent notices\r\n    stating that you changed the files and the date of any change.\r\n\r\n    c) You must cause the whole of the work to be licensed at no\r\n    charge to all third parties under the terms of this License.\r\n\r\n    d) If a facility in the modified Library refers to a function or a\r\n    table of data to be supplied by an application program that uses\r\n    the facility, other than as an argument passed when the facility\r\n    is invoked, then you must make a good faith effort to ensure that,\r\n    in the event an application does not supply such function or\r\n    table, the facility still operates, and performs whatever part of\r\n    its purpose remains meaningful.\r\n\r\n    (For example, a function in a library to compute square roots has\r\n    a purpose that is entirely well-defined independent of the\r\n    application.  Therefore, Subsection 2d requires that any\r\n    application-supplied function or table used by this function must\r\n    be optional: if the application does not supply it, the square\r\n    root function must still compute square roots.)\r\n\r\nThese requirements apply to the modified work as a whole.  If\r\nidentifiable sections of that work are not derived from the Library,\r\nand can be reasonably considered independent and separate works in\r\nthemselves, then this License, and its terms, do not apply to those\r\nsections when you distribute them as separate works.  But when you\r\ndistribute the same sections as part of a whole which is a work based\r\non the Library, the distribution of the whole must be on the terms of\r\nthis License, whose permissions for other licensees extend to the\r\nentire whole, and thus to each and every part regardless of who wrote\r\nit.\r\n\r\nThus, it is not the intent of this section to claim rights or contest\r\nyour rights to work written entirely by you; rather, the intent is to\r\nexercise the right to control the distribution of derivative or\r\ncollective works based on the Library.\r\n\r\nIn addition, mere aggregation of another work not based on the Library\r\nwith the Library (or with a work based on the Library) on a volume of\r\na storage or distribution medium does not bring the other work under\r\nthe scope of this License.\r\n\r\n  3. You may opt to apply the terms of the ordinary GNU General Public\r\nLicense instead of this License to a given copy of the Library.  To do\r\nthis, you must alter all the notices that refer to this License, so\r\nthat they refer to the ordinary GNU General Public License, version 2,\r\ninstead of to this License.  (If a newer version than version 2 of the\r\nordinary GNU General Public License has appeared, then you can specify\r\nthat version instead if you wish.)  Do not make any other change in\r\nthese notices.\r\n\f\r\n  Once this change is made in a given copy, it is irreversible for\r\nthat copy, so the ordinary GNU General Public License applies to all\r\nsubsequent copies and derivative works made from that copy.\r\n\r\n  This option is useful when you wish to copy part of the code of\r\nthe Library into a program that is not a library.\r\n\r\n  4. You may copy and distribute the Library (or a portion or\r\nderivative of it, under Section 2) in object code or executable form\r\nunder the terms of Sections 1 and 2 above provided that you accompany\r\nit with the complete corresponding machine-readable source code, which\r\nmust be distributed under the terms of Sections 1 and 2 above on a\r\nmedium customarily used for software interchange.\r\n\r\n  If distribution of object code is made by offering access to copy\r\nfrom a designated place, then offering equivalent access to copy the\r\nsource code from the same place satisfies the requirement to\r\ndistribute the source code, even though third parties are not\r\ncompelled to copy the source along with the object code.\r\n\r\n  5. A program that contains no derivative of any portion of the\r\nLibrary, but is designed to work with the Library by being compiled or\r\nlinked with it, is called a \"work that uses the Library\".  Such a\r\nwork, in isolation, is not a derivative work of the Library, and\r\ntherefore falls outside the scope of this License.\r\n\r\n  However, linking a \"work that uses the Library\" with the Library\r\ncreates an executable that is a derivative of the Library (because it\r\ncontains portions of the Library), rather than a \"work that uses the\r\nlibrary\".  The executable is therefore covered by this License.\r\nSection 6 states terms for distribution of such executables.\r\n\r\n  When a \"work that uses the Library\" uses material from a header file\r\nthat is part of the Library, the object code for the work may be a\r\nderivative work of the Library even though the source code is not.\r\nWhether this is true is especially significant if the work can be\r\nlinked without the Library, or if the work is itself a library.  The\r\nthreshold for this to be true is not precisely defined by law.\r\n\r\n  If such an object file uses only numerical parameters, data\r\nstructure layouts and accessors, and small macros and small inline\r\nfunctions (ten lines or less in length), then the use of the object\r\nfile is unrestricted, regardless of whether it is legally a derivative\r\nwork.  (Executables containing this object code plus portions of the\r\nLibrary will still fall under Section 6.)\r\n\r\n  Otherwise, if the work is a derivative of the Library, you may\r\ndistribute the object code for the work under the terms of Section 6.\r\nAny executables containing that work also fall under Section 6,\r\nwhether or not they are linked directly with the Library itself.\r\n\f\r\n  6. As an exception to the Sections above, you may also combine or\r\nlink a \"work that uses the Library\" with the Library to produce a\r\nwork containing portions of the Library, and distribute that work\r\nunder terms of your choice, provided that the terms permit\r\nmodification of the work for the customer's own use and reverse\r\nengineering for debugging such modifications.\r\n\r\n  You must give prominent notice with each copy of the work that the\r\nLibrary is used in it and that the Library and its use are covered by\r\nthis License.  You must supply a copy of this License.  If the work\r\nduring execution displays copyright notices, you must include the\r\ncopyright notice for the Library among them, as well as a reference\r\ndirecting the user to the copy of this License.  Also, you must do one\r\nof these things:\r\n\r\n    a) Accompany the work with the complete corresponding\r\n    machine-readable source code for the Library including whatever\r\n    changes were used in the work (which must be distributed under\r\n    Sections 1 and 2 above); and, if the work is an executable linked\r\n    with the Library, with the complete machine-readable \"work that\r\n    uses the Library\", as object code and/or source code, so that the\r\n    user can modify the Library and then relink to produce a modified\r\n    executable containing the modified Library.  (It is understood\r\n    that the user who changes the contents of definitions files in the\r\n    Library will not necessarily be able to recompile the application\r\n    to use the modified definitions.)\r\n\r\n    b) Use a suitable shared library mechanism for linking with the\r\n    Library.  A suitable mechanism is one that (1) uses at run time a\r\n    copy of the library already present on the user's computer system,\r\n    rather than copying library functions into the executable, and (2)\r\n    will operate properly with a modified version of the library, if\r\n    the user installs one, as long as the modified version is\r\n    interface-compatible with the version that the work was made with.\r\n\r\n    c) Accompany the work with a written offer, valid for at\r\n    least three years, to give the same user the materials\r\n    specified in Subsection 6a, above, for a charge no more\r\n    than the cost of performing this distribution.\r\n\r\n    d) If distribution of the work is made by offering access to copy\r\n    from a designated place, offer equivalent access to copy the above\r\n    specified materials from the same place.\r\n\r\n    e) Verify that the user has already received a copy of these\r\n    materials or that you have already sent this user a copy.\r\n\r\n  For an executable, the required form of the \"work that uses the\r\nLibrary\" must include any data and utility programs needed for\r\nreproducing the executable from it.  However, as a special exception,\r\nthe materials to be distributed need not include anything that is\r\nnormally distributed (in either source or binary form) with the major\r\ncomponents (compiler, kernel, and so on) of the operating system on\r\nwhich the executable runs, unless that component itself accompanies\r\nthe executable.\r\n\r\n  It may happen that this requirement contradicts the license\r\nrestrictions of other proprietary libraries that do not normally\r\naccompany the operating system.  Such a contradiction means you cannot\r\nuse both them and the Library together in an executable that you\r\ndistribute.\r\n\f\r\n  7. You may place library facilities that are a work based on the\r\nLibrary side-by-side in a single library together with other library\r\nfacilities not covered by this License, and distribute such a combined\r\nlibrary, provided that the separate distribution of the work based on\r\nthe Library and of the other library facilities is otherwise\r\npermitted, and provided that you do these two things:\r\n\r\n    a) Accompany the combined library with a copy of the same work\r\n    based on the Library, uncombined with any other library\r\n    facilities.  This must be distributed under the terms of the\r\n    Sections above.\r\n\r\n    b) Give prominent notice with the combined library of the fact\r\n    that part of it is a work based on the Library, and explaining\r\n    where to find the accompanying uncombined form of the same work.\r\n\r\n  8. You may not copy, modify, sublicense, link with, or distribute\r\nthe Library except as expressly provided under this License.  Any\r\nattempt otherwise to copy, modify, sublicense, link with, or\r\ndistribute the Library is void, and will automatically terminate your\r\nrights under this License.  However, parties who have received copies,\r\nor rights, from you under this License will not have their licenses\r\nterminated so long as such parties remain in full compliance.\r\n\r\n  9. You are not required to accept this License, since you have not\r\nsigned it.  However, nothing else grants you permission to modify or\r\ndistribute the Library or its derivative works.  These actions are\r\nprohibited by law if you do not accept this License.  Therefore, by\r\nmodifying or distributing the Library (or any work based on the\r\nLibrary), you indicate your acceptance of this License to do so, and\r\nall its terms and conditions for copying, distributing or modifying\r\nthe Library or works based on it.\r\n\r\n  10. Each time you redistribute the Library (or any work based on the\r\nLibrary), the recipient automatically receives a license from the\r\noriginal licensor to copy, distribute, link with or modify the Library\r\nsubject to these terms and conditions.  You may not impose any further\r\nrestrictions on the recipients' exercise of the rights granted herein.\r\nYou are not responsible for enforcing compliance by third parties with\r\nthis License.\r\n\f\r\n  11. If, as a consequence of a court judgment or allegation of patent\r\ninfringement or for any other reason (not limited to patent issues),\r\nconditions are imposed on you (whether by court order, agreement or\r\notherwise) that contradict the conditions of this License, they do not\r\nexcuse you from the conditions of this License.  If you cannot\r\ndistribute so as to satisfy simultaneously your obligations under this\r\nLicense and any other pertinent obligations, then as a consequence you\r\nmay not distribute the Library at all.  For example, if a patent\r\nlicense would not permit royalty-free redistribution of the Library by\r\nall those who receive copies directly or indirectly through you, then\r\nthe only way you could satisfy both it and this License would be to\r\nrefrain entirely from distribution of the Library.\r\n\r\nIf any portion of this section is held invalid or unenforceable under any\r\nparticular circumstance, the balance of the section is intended to apply,\r\nand the section as a whole is intended to apply in other circumstances.\r\n\r\nIt is not the purpose of this section to induce you to infringe any\r\npatents or other property right claims or to contest validity of any\r\nsuch claims; this section has the sole purpose of protecting the\r\nintegrity of the free software distribution system which is\r\nimplemented by public license practices.  Many people have made\r\ngenerous contributions to the wide range of software distributed\r\nthrough that system in reliance on consistent application of that\r\nsystem; it is up to the author/donor to decide if he or she is willing\r\nto distribute software through any other system and a licensee cannot\r\nimpose that choice.\r\n\r\nThis section is intended to make thoroughly clear what is believed to\r\nbe a consequence of the rest of this License.\r\n\r\n  12. If the distribution and/or use of the Library is restricted in\r\ncertain countries either by patents or by copyrighted interfaces, the\r\noriginal copyright holder who places the Library under this License may add\r\nan explicit geographical distribution limitation excluding those countries,\r\nso that distribution is permitted only in or among countries not thus\r\nexcluded.  In such case, this License incorporates the limitation as if\r\nwritten in the body of this License.\r\n\r\n  13. The Free Software Foundation may publish revised and/or new\r\nversions of the Lesser General Public License from time to time.\r\nSuch new versions will be similar in spirit to the present version,\r\nbut may differ in detail to address new problems or concerns.\r\n\r\nEach version is given a distinguishing version number.  If the Library\r\nspecifies a version number of this License which applies to it and\r\n\"any later version\", you have the option of following the terms and\r\nconditions either of that version or of any later version published by\r\nthe Free Software Foundation.  If the Library does not specify a\r\nlicense version number, you may choose any version ever published by\r\nthe Free Software Foundation.\r\n\f\r\n  14. If you wish to incorporate parts of the Library into other free\r\nprograms whose distribution conditions are incompatible with these,\r\nwrite to the author to ask for permission.  For software which is\r\ncopyrighted by the Free Software Foundation, write to the Free\r\nSoftware Foundation; we sometimes make exceptions for this.  Our\r\ndecision will be guided by the two goals of preserving the free status\r\nof all derivatives of our free software and of promoting the sharing\r\nand reuse of software generally.\r\n\r\n\t\t\t    NO WARRANTY\r\n\r\n  15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO\r\nWARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.\r\nEXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR\r\nOTHER PARTIES PROVIDE THE LIBRARY \"AS IS\" WITHOUT WARRANTY OF ANY\r\nKIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE\r\nIMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR\r\nPURPOSE.  THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE\r\nLIBRARY IS WITH YOU.  SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME\r\nTHE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.\r\n\r\n  16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN\r\nWRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY\r\nAND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU\r\nFOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR\r\nCONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE\r\nLIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING\r\nRENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A\r\nFAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF\r\nSUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH\r\nDAMAGES.\r\n\r\n\t\t     END OF TERMS AND CONDITIONS\r\n\f\r\n           How to Apply These Terms to Your New Libraries\r\n\r\n  If you develop a new library, and you want it to be of the greatest\r\npossible use to the public, we recommend making it free software that\r\neveryone can redistribute and change.  You can do so by permitting\r\nredistribution under these terms (or, alternatively, under the terms of the\r\nordinary General Public License).\r\n\r\n  To apply these terms, attach the following notices to the library.  It is\r\nsafest to attach them to the start of each source file to most effectively\r\nconvey the exclusion of warranty; and each file should have at least the\r\n\"copyright\" line and a pointer to where the full notice is found.\r\n\r\n    <one line to give the library's name and a brief idea of what it does.>\r\n    Copyright (C) <year>  <name of author>\r\n\r\n    This library is free software; you can redistribute it and/or\r\n    modify it under the terms of the GNU Lesser General Public\r\n    License as published by the Free Software Foundation; either\r\n    version 2.1 of the License, or (at your option) any later version.\r\n\r\n    This library is distributed in the hope that it will be useful,\r\n    but WITHOUT ANY WARRANTY; without even the implied warranty of\r\n    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n    Lesser General Public License for more details.\r\n\r\n    You should have received a copy of the GNU Lesser General Public\r\n    License along with this library; if not, write to the Free Software\r\n    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n\r\nAlso add information on how to contact you by electronic and paper mail.\r\n\r\nYou should also get your employer (if you work as a programmer) or your\r\nschool, if any, to sign a \"copyright disclaimer\" for the library, if\r\nnecessary.  Here is a sample; alter the names:\r\n\r\n  Yoyodyne, Inc., hereby disclaims all copyright interest in the\r\n  library `Frob' (a library for tweaking knobs) written by James Random Hacker.\r\n\r\n  <signature of Ty Coon>, 1 April 1990\r\n  Ty Coon, President of Vice\r\n\r\nThat's all there is to it!\r\n\r\n\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/Makefile",
    "content": "################################################\n#  NB: This Makefile is designed to be called  #\n#      from the main PRISM Makefile. It won't  #\n#      work on its own because it needs        #\n#      various options to be passed in         #\n################################################\n\ndefault: all\n\nall: checks lpsolve55java\n\n# Try and prevent accidental makes (i.e. called manually, not from top-level Makefile)\nchecks:\n\t@if [ \"$(LIBSUFFIX)\" = \"\" ]; then \\\n\t  (echo \"Error: This Makefile is designed to be called from the main PRISM Makefile\"; exit 1) \\\n\tfi; \n\nlpsolve55java:\n\t@echo Making sure lpsolve55 Java wrapper is compatible with $(OSTYPE) $(ARCH)\n\t@(if [ \"$(OSTYPE)\" = \"linux\" ]; then \\\n\t  echo \"Rebuild lpsolve55 Java wrapper for Linux\"; \\\n\t  (cd lib ; ARCH=$(ARCH) JAVA_JNI_H_DIR=\"$(JAVA_JNI_H_DIR)\" JAVA_JNI_MD_H_DIR=\"$(JAVA_JNI_MD_H_DIR)\" sh build); \\\n\t  if [ \"$(ARCH)\" = \"\" ]; then \\\n\t    cp lib/lpsolve55j.jar lib/ux32/liblpsolve55j.so ../../$(PRISM_LIB_DIR)/ ; \\\n\t  else \\\n\t    cp lib/lpsolve55j.jar lib/ux64/liblpsolve55j.so ../../$(PRISM_LIB_DIR)/ ; \\\n\t  fi; \\\n\tfi)\n\t@(if [ \"$(OSTYPE)\" = \"darwin\" ]; then \\\n\t  echo \"Rebuild lpsolve55 Java wrapper for MacOS\"; \\\n\t  (cd lib/mac; ARCH=$(ARCH) JAVA_JNI_H_DIR=\"$(JAVA_JNI_H_DIR)\" JAVA_JNI_MD_H_DIR=\"$(JAVA_JNI_MD_H_DIR)\" sh -x build-osx); \\\n\t  cp lib/lpsolve55j.jar lib/mac/liblpsolve55j.dylib ../../$(PRISM_LIB_DIR)/ ; \\\n\tfi)\n\t@(if [ \"$(OSTYPE)\" = \"cygwin\" ]; then \\\n\t  if [ \"$(ARCH)\" = \"x86_64\" ]; then \\\n\t    cp lib/lpsolve55j.jar lib/win64/lpsolve55j.dll ../../$(PRISM_LIB_DIR)/ ; \\\n\t  else \\\n\t    cp lib/lpsolve55j.jar lib/win32/lpsolve55j.dll ../../$(PRISM_LIB_DIR)/ ; \\\n\t  fi; \\\n\tfi)\nclean: checks\n\trm -f $(LPSOLVE55JAVA_DIR)/lib/lpsolve55j.jar\n\ncelan:\tclean\n\n\n#################################################\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/README.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 3.2 Final//EN\">\r\n<html>\r\n<head>\r\n<title>Using lp_solve 5.5 in Java programs</title>\r\n<style type=\"text/css\">\r\n<!--\r\nbody  { font-family: Verdana, Arial, Helvetica, sans-serif; }\r\ntd,th\t{ text-align:left; }\r\nli\t\t{ margin-top: 3px; }\r\npre\t\t{ font-size: smaller; }\r\n-->\r\n</style>\r\n\r\n</head>\r\n\r\n<body>\r\n\r\n<h1>Using lp_solve 5.5 in Java programs</h1>\r\n\r\n<h2>Contents</h2>\r\n\r\n<a href=\"#intro\">1. Introduction</a><br/>\r\n<a href=\"#install\">2. Installation</a><br/>\r\n<a href=\"#usage\">3. Usage</a><br/>\r\n<a href=\"#impl\">4. Implementation notes</a><br/>\r\n<a href=\"#building\">5. Building from source</a><br/>\r\n<a href=\"#jython\">6. Calling lp_solve from Python/Jython</a><br/>\r\n\r\n\r\n<!--\r\n * *******************************************************************\r\n * PART 1\r\n * *******************************************************************\r\n-->\r\n<h2><a name=\"intro\">1. Introduction</a></h2>\r\n\r\n<p>lp_solve is a free (see <a href=\"LGPL\">LGPL</a> for the GNU lesser general public license) linear\r\n(integer) programming solver based on the revised simplex method and the Branch-and-bound method\r\nfor the integers. lp_solve has its own community via the Yahoo group\r\n<a href=\"http://groups.yahoo.com/group/lp_solve\">http://groups.yahoo.com/group/lp_solve</a>.\r\nThere you can find the latest sources, executables for the common platforms, examples, manuals\r\nand a message board where people can share their thoughts on lp_solve.</p>\r\n\r\n<p>lp_solve is written in ANSI C and can be compiled on many different platforms like Linux and Windows.\r\nBasically, lp_solve is a library, a set of routines, that can be called\r\neasily from programming languages like C, C++, C# and VB. Unfortunately, there is no simple and\r\nstraightforward way to use native C libraries like lp_solve in Java programs.\r\nThis library (also called <strong>&quot;Java wrapper&quot;</strong>) is designed to remedy this shortcoming. It\r\nconsists of two main parts:</p>\r\n\r\n<ul>\r\n<li>A Java class library that is used by Java client programs. It gives access to all\r\n  lp_solve routines through the <code>LpSolve</code> class.</li>\r\n\r\n<li> A native library written in C++, also called 'stub' library, that uses the JNI\r\n  (Java Native Interface) API to translate Java method calls into calls to the\r\n  corresponding routines of the lp_solve library. Java client\r\n  programs do not interact directly with the stub library.\r\n  This library must be compiled for each target platform.\r\n  Precompiled binaries are included for Windows and Linux operating systems.\r\n  There is also a build script for compiling the stub library on Mac OS X.</li>\r\n</ul>\r\n\r\n<p>This document should help you getting started using the Java wrapper and lp_solve in your\r\nJava programs. Read it in addition to the documentation that comes with lp_solve.\r\nAlways refer to the lp_solve docs as ultimate reference for\r\nusing the routines of the optimization library.\r\nBug reports, succes stories and requests for changes concerning the Java wrapper are welcome\r\nby email at <code>juergen.ebert@web.de</code> or in the lp_solve discussion group.</p>\r\n\r\n<p>The current wrapper version was written to work with lp_solve 5.5.0.9 and was tested\r\n under Windows XP and Linux.  As long as the API stays the same, other versions of lp_solve\r\n are likely to work as well. The wrapper requires a Java Runtime Environment 1.3 or later.</p>\r\n\r\n<p>The latest version of the Java wrapper can be found in the files section of the lp_solve group.\r\nThe wrapper is released under the same LGPL license conditions as lp_solve. A copy of\r\nthe LGPL text is contained in the distribution archive. </p>\r\n\r\n\r\n<!--\r\n * *******************************************************************\r\n * PART 2\r\n * *******************************************************************\r\n-->\r\n<h2><a name=\"install\">2. Installation</a></h2>\r\n\r\n<ul>\r\n<li>Copy the lp_solve dynamic libraries from the archives <code>lp_solve_5.5_dev.(zip or tar.gz)</code>\r\n  and <code>lp_solve_5.5_exe.(zip or tar.gz)</code> to a standard library directory for your target platform.\r\n  On Windows, a typical place would be <code>\\WINDOWS</code> or <code>\\WINDOWS\\SYSTEM32</code>.\r\n  On Linux, a typical place would be the directory <code>/usr/local/lib</code>.\r\n</li>\r\n\r\n<li>Unzip the Java wrapper distribution file to new directory of your choice.</li>\r\n\r\n<li>On Windows, copy the wrapper stub library <code>lpsolve55j.dll</code>\r\n  to the directory that already contains <code>lpsolve55.dll</code>.\r\n</li>\r\n\r\n<li>On Linux, copy the wrapper stub library  <code>liblpsolve55j.so</code>\r\n  to the directory that already contains <code>liblpsolve55.so</code>. Run <code>ldconfig</code> to include\r\n  the library in the shared libray cache.\r\n</li>\r\n</ul>\r\n\r\n\r\n\r\n<!--\r\n * *******************************************************************\r\n * PART 3\r\n * *******************************************************************\r\n-->\r\n<h2><a name=\"usage\">3. Usage</a></h2>\r\n\r\n<p>To create a Java application that uses lp_solve routines, you must perform the\r\nfollowing steps:</p>\r\n\r\n<ul>\r\n<li>Make sure you have a Java Runtime Environment 1.3 or later installed.</li>\r\n\r\n<li>Install lp_solve and the Java wrapper as described above.</li>\r\n\r\n<li>Copy the archive file <code>lpsolve55j.jar</code> from the Java wrapper distribution to a\r\n  directory that is included in the CLASSPATH of your java program.</li>\r\n\r\n<li>Add an import statement for the package <code>lpsolve.*</code> at the beginning of your\r\n  source file.</li>\r\n\r\n<li>Call <code>LpSolve.makeLp(...)</code> or one of the other static factory methods of the LpSolve\r\n  class to create a <code>LpSolve</code> instance. Each <code>LpSolve</code> instance represents an optimization\r\n  problem.</li>\r\n\r\n<li>Call the methods of the <code>LpSolve</code> instance to define the problem and obtain the solution.\r\n  Use the examples and implementation notes later in this documentation for further\r\n  information.</li>\r\n\r\n<li>When you run your Java file make sure to include <code>lpsolve55j.jar</code> in the CLASSPATH.\r\n  Also, on Windows, if you installed the  native stub library in a directory that is not included\r\n  in the PATH variable, you have to define the Java system variable <code>java.library.path</code>\r\n  which must point to the installation directory. On Linux, the equivalent of the Windows PATH\r\n  variable is called LD_LIBRARY_PATH.</li>\r\n</ul>\r\n\r\n\r\n<h3><a name=\"ex1\">A simple example</a></h3>\r\n\r\n<p>The following program is a very simple example that shows how to program with lp_solve in Java.\r\n</p>\r\n\r\n<pre>\r\nimport lpsolve.*;\r\n\r\npublic class Demo {\r\n\r\n  public static void main(String[] args) {\r\n    try {\r\n      // Create a problem with 4 variables and 0 constraints\r\n      LpSolve solver = LpSolve.makeLp(0, 4);\r\n\r\n      // add constraints\r\n      solver.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n      solver.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\r\n      // set objective function\r\n      solver.strSetObjFn(\"2 3 -2 3\");\r\n\r\n      // solve the problem\r\n      solver.solve();\r\n\r\n      // print solution\r\n      System.out.println(\"Value of objective function: \" + solver.getObjective());\r\n      double[] var = solver.getPtrVariables();\r\n      for (int i = 0; i < var.length; i++) {\r\n        System.out.println(\"Value of var[\" + i + \"] = \" + var[i]);\r\n      }\r\n\r\n      // delete the problem and free memory\r\n      solver.deleteLp();\r\n    }\r\n    catch (LpSolveException e) {\r\n       e.printStackTrace();\r\n    }\r\n  }\r\n\r\n}\r\n</pre>\r\n\r\n<h3><a name=\"ex2\">Using callbacks</a></h3>\r\n\r\n<p>The following code fragment shows you how to use callbacks in Java.\r\nThe example defines an anonymous inner class that implements the <code>AbortListener</code>\r\ninterface which is then passed to the <code>putAbortfunc</code> method.</p>\r\n\r\n<pre>\r\n    LpSolve solver = LpSolve.makeLp(0, 4);\r\n    AbortListener abortfunc = new AbortListener() {\r\n      public boolean abortfunc(LpSolve problem, Object handle) {\r\n        System.out.println(\"Java abortfunc called, handle = \" + handle);\r\n        return false;\r\n      }\r\n    };\r\n    solver.putAbortfunc(abortfunc, new Integer(123));\r\n</pre>\r\n\r\n\r\n<h3><a name=\"ex3\">Running the demo application</a></h3>\r\n\r\n<p>Follow these steps to run the demo application, which is a port of the C demo\r\nprogram that comes with lp_solve to the Java language. You will need a Java Runtime\r\nEnvironment (JRE) on your machine in order to run the demo. You can download the\r\nlatest JRE from <a href=\"http://java.sun.com\">http://java.sun.com</a></p>\r\n\r\n<ul>\r\n<li>Install lp_solve and the Java wrapper as described above.</li>\r\n<li>On Windows, go to the <code>demo</code> directory and\r\nstart the batch script &quot;run_demo.bat&quot;.</li>\r\n<li>On Linux, go to the <code>demo</code> directory of the wrapper distribution and\r\nrun &quot;sh run_demo&quot;.</li>\r\n</ul>\r\n\r\n<h3><a name=\"ex4\">More example code</a></h3>\r\n\r\n<p>In the <code>demo</code> directory you will find\r\nthe file <code>LpSolveTest.java</code> which contains more than 100\r\nJUnit test cases (see <a href=\"http://www.junit.org\">http://www.junit.org</a> for\r\ndetails about this highly useful software)\r\nto strengthen the faith in the Java wrapper implementation. The test cases\r\nmay also seve as examples of basic lp_solve usage in Java. You will need\r\nthe library <code>junit.jar</code> in your <code>CLASSPATH</code> to run the test cases.\r\n<code>junit.jar</code> is included in the <code>lib</code> directory of the Java wrapper. You\r\ncan run the test cases directly by starting the batch script &quot;run_unittests.bat&quot; on Windows\r\nor &quot;sh run_unittests&quot; on Linux.\r\n</p>\r\n\r\n<!--\r\n * *******************************************************************\r\n * PART 4\r\n * *******************************************************************\r\n-->\r\n<h2><a name=\"impl\">4. Implementation notes</a></h2>\r\n\r\n<ul>\r\n<li>In general, the Java API tries to follow the original C/C++ API of lp_solve as\r\n  closely as possible to make ist easier for programmers who have to write programs for\r\n  lp_solve in multiple different programming languages. However, because of fundamental\r\n  differences between the Java programming language and C/C++ this is not always strictly\r\n  possible. For example, it is not possible in Java to pass simple datatypes by reference.</li>\r\n\r\n<li>Method names have been kept, but changed to Java convention, i.e. underscores have been\r\n  removed, the following character is capitalized. For example <code>str_add_constraint</code>\r\n  becomes <code>strAddConstraint</code> in Java.</li>\r\n\r\n<li>The <code>lprec*</code> argument taken by almost all lp_solve API routines is hidden\r\n  completely inside the <code>LpSolve</code> class. All methods that create new <code>lprec\r\n  </code> structures were made static methods of the <code>LpSolve</code> class.</li>\r\n\r\n<li>Return values denoting fatal internal errors have been changed to Java Exceptions. For\r\n  example <code>set_row_name</code> returns FALSE if an error has occured. In Java, <code>\r\n  setRowName</code> is of type void and throws a <code>LpSolveException</code>.</li>\r\n\r\n<li>Routines that have arguments or return values of type unsigned char, but only allow for TRUE or\r\n  FALSE as legal values have been changed to type <code>boolean</code>. Example: <code>\r\n  set_debug(lprec *lp, unsigned char debug)</code> is <code>setDebug(boolean debug)</code> in Java.\r\n  </li>\r\n\r\n<li>Multiple problems may be solved concurrently by multiple threads, as long as a single\r\n  <code>LpSolve</code> object, which represents a problem, is only used by one thread at a\r\n  time.</li>\r\n\r\n<li>lp_solve does not require client programs to keep argument buffers allocated between calls\r\n  to different library routines, because all input arguments are copied to internal buffers.\r\n  Thus, it is easy to avoid memory leaks in the stub library. All objects returned by the\r\n  Java wrapper routines are allocated by the JVM and are subject to the standard garbage\r\n  collection process.</li>\r\n\r\n<li>The methods <code>get_ptr_sensitivity_rhs</code>, <code>get_ptr_reduced_costs</code>,\r\n  <code>get_ptr_sensitivity_obj</code>, and <code>get_ptr_sensitivity_objex</code> are not implemented,\r\n  because it is not possible in Java to pass pointers by reference to a method. Use the corresponding\r\n  methods without the <code>Ptr</code> part in the method name instead, which require allocation\r\n  of the resulting arrays by the caller.</li>\r\n\r\n<li>See the file <code>reference.html</code> for details on how the lp_solve API functions\r\nare mapped to the Java methods.</li>\r\n</ul>\r\n\r\n\r\n<!--\r\n * *******************************************************************\r\n * PART 5\r\n * *******************************************************************\r\n-->\r\n<h2><a name=\"building\">5. Building from source</a></h2>\r\n\r\n<p>The Java wrapper archive contains precompiled binary libraries for Windows and Linux.\r\nIf you just want to use the wrapper there should be no need to build the libs from the sources.\r\nBut if you absolutely have to, follow the guidelines in this chapter.</p>\r\n\r\n<h3><a name=\"build_win\">On Windows OS</a></h3>\r\n\r\nThe following prerequisites must be met in order to build the wrapper C library from source\r\non Windows operating systems:\r\n\r\n<ul>\r\n<li>Microsoft Visual C++ compiler (I used V 7, others might work)</li>\r\n<li>Visual Studio envirement variables must be set.</li>\r\n<li>Sun Java Development Kit 1.4.x installed and JAVA_HOME environment variable set</li>\r\n<li>lp_solve Windows development archive <code>lp_solve_5.5_dev.zip</code> unpacked</li>\r\n</ul>\r\n\r\nChange to the <code>lib</code> directory and edit the file <code>build.bat</code>.\r\nChange the path to the directory where you unpacked the lp_solve Windows\r\narchive. Run the script to build <code>lpsolve55j.dll</code>.\r\nThe dll will be created in directory win32 or win64 depending on the OS.\r\n\r\n\r\n<h3><a name=\"build_linux\">On Linux</a></h3>\r\n\r\nThe following prerequisites must be met in order to build the wrapper C library from source\r\non Linux operating systems:\r\n\r\n<ul>\r\n<li>gcc and g++ compiler installed (I used gcc Version 3.3.1)</li>\r\n<li>Sun Java Development Kit 1.4.x installed</li>\r\n<li>lp_solve Linux development archive <code>lp_solve_5.5_dev.tar.gz</code> unpacked</li>\r\n</ul>\r\n\r\nChange to the <code>lib</code> directory and edit the file <code>build</code>.\r\nChange the paths to the directory where you unpacked the lp_solve linux archive\r\nand where the JDK is installed.\r\nRun <code>sh build</code> to build <code>liblpsolve55j.so</code>.\r\nThe dll will be created in directory ux32 or ux64 depending on the OS.\r\n\r\n\r\n<h3><a name=\"build_mac\">On Mac OS X</a></h3>\r\n\r\n<p>Change to the <code>lib/mac</code> directory and edit the file <code>build_osx</code>.\r\nChange the directory paths as indicated in the comments.\r\nThanks to Sean P. Kane (spkane@genomatica.com) who provided this build script.</p>\r\n\r\n<!--\r\n * *******************************************************************\r\n * PART 6\r\n * *******************************************************************\r\n-->\r\n<h2><a name=\"jython\">6. Calling lp_solve from Python/Jython</a></h2>\r\n\r\n<p>\r\nJython (<a href=\"http://www.jython.org\">http://www.jython.org</a>) is a 100% Java implementation of\r\nthe popular scripting language Python.\r\nOne of the most remarkable features of Jython is the seamless interaction between Python and Java.\r\nJava programmers can add the Jython libraries to their system to allow end users to write scripts that add\r\nfunctionality to the application. On the other hand, Python/Jython programs can interact with Java packages\r\nor with running Java applications.\r\n</p>\r\n\r\n<p>lp_solve functions can be called via the Java wrapper from Python/Jython programs.\r\nSee the file <code>demo.py</code> in the <code>demo</code> directory of the Java wrapper distribution\r\nfor an example program.\r\nTo run this program, you must install lp_solve, the Java wrapper, and Jython. Don't forget\r\nto include <code>lpsolve55j.jar</code> in the Java CLASSPATH when you run Jython.\r\n</p>\r\n\r\n\r\n</body>\r\n</html>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/Build.bat",
    "content": "@echo off\r\n\r\nxcopy ..\\src\\java\\lpsolve\\*.class lpsolve\\ /y\r\nrem jar -c -f ..\\lib\\lpsolve55j.jar *.class lpsolve\r\njar cvf ..\\lib\\lpsolve55j.jar *.class lpsolve\r\n\r\njavac -classpath ..\\lib\\lpsolve55j.jar Demo.java\r\nrem jar -c -f Demo.jar Demo.class\r\njar cvf Demo.jar Demo.class\r\nrem following shows contents of jar file.\r\nrem rem jar -t -f Demo.jar\r\nrem jar tf Demo.jar\r\n\r\njavac -classpath ..\\lib\\lpsolve55j.jar;..\\lib\\junit.jar LpSolveTest.java\r\nrem jar -c -f unittests.jar LpSolveTest.class LpSolveTest$1MyListener.class LpSolveTest$2MyListener.class LpSolveTest$3MyListener.class\r\njar cvf unittests.jar LpSolveTest.class LpSolveTest$1MyListener.class LpSolveTest$2MyListener.class LpSolveTest$3MyListener.class\r\n\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/Demo.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\t\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\nimport java.io.BufferedReader;\r\nimport java.io.IOException;\r\nimport java.io.InputStreamReader;\r\n\r\nimport lpsolve.*;\r\n\r\n/**\r\n * Java version of the C Demo program that comes with the lp_solve software.\r\n * \r\n * @author Juergen Ebert\r\n */\r\npublic class Demo {\r\n\r\n\tpublic Demo() {\r\n\t}\r\n\r\n\tpublic void execute() throws LpSolveException {\r\n\t\tVersionInfo info = LpSolve.lpSolveVersion();\r\n\t\tSystem.out.println(\"This demo (Java version) will show most of the features of lp_solve \" \r\n\t\t\t+ info.getMajorversion()\r\n\t\t\t+ \".\" + info.getMinorversion()\r\n\t\t\t+ \".\" + info.getRelease()\r\n\t\t\t+ \".\" + info.getBuild());\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"We start by creating a new problem with 4 variables \"\r\n\t\t\t+ \"and 0 constraints\");\r\n\t\tSystem.out.println(\"We use: LpSolve problem = LpSolve.makeLp(0, 4);\");\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tpressRet();\r\n\t\t\r\n\t\t/* Let's first demonstrate the logfunc callback feature */\r\n\t    LogListener logfunc = new LogListener() {\r\n\t        public void logfunc(LpSolve problem, Object handle, String buf) {\r\n\t        \tSystem.out.println(buf);\r\n\t        }\r\n\t    };\r\n\t    problem.putLogfunc(logfunc, null);\r\n\t    problem.solve(); /* just to see that a message is send via the logfunc routine ... */\r\n\t    problem.putLogfunc(null, null); /* ok, that is enough, no more callback */\r\n\r\n\t    /* Set an abort function. This is optional */\r\n\t    AbortListener abortfunc = new AbortListener() {\r\n\t        public boolean abortfunc(LpSolve problem, Object handle) {\r\n\t        \t/* If set to true, then solve is aborted and returncode will indicate this. */\r\n\t        \treturn false;\r\n\t        }\r\n\t    };\r\n\t    problem.putAbortfunc(abortfunc, null);\r\n\r\n\t    /* Set a message function. Again optional */\r\n\t    MsgListener msgfunc = new MsgListener() {\r\n\t        public void msgfunc(LpSolve problem, Object handle, int msg) {\r\n\t        \t// System.out.println(\"Message = \" + msg);\r\n\t        }\r\n\t    };\r\n\t    problem.putMsgfunc(msgfunc, null, \r\n\t    \t\tLpSolve.MSG_PRESOLVE | LpSolve.MSG_LPFEASIBLE | LpSolve.MSG_LPOPTIMAL \r\n\t\t\t\t| LpSolve.MSG_MILPEQUAL | LpSolve.MSG_MILPFEASIBLE | LpSolve.MSG_MILPBETTER);\r\n\r\n\t    System.out.println(\"We can show the current problem with problem.printLp()\");\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\r\n\t\tSystem.out.println(\"Now we add some constraints:\");\r\n\t\tSystem.out.println(\"problem.strAddConstraint(\\\"3 2 2 1\\\", LpSolve.LE, 4);\");\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"problem.strAddConstraint(\\\"0 4 3 1\\\", LpSolve.GE, 3);\");\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\t\r\n\t\tSystem.out.println(\"Set the objective function:\");\r\n\t\tSystem.out.println(\"problem.strSetObjFn(\\\"2 3 -2 3\\\");\");\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"Now solve the problem with System.out.println(problem.solve());\");\r\n\t\tSystem.out.println(problem.solve());\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"The value is 0, this means we found an optimal solution.\");\r\n\t\tSystem.out.println(\"We can display the solution with problem.printObjective(), \"\r\n\t\t\t+ \"problem.printSolution(1), and problem.printConstraints(1)\");\t\t\r\n\t\tproblem.printObjective();\r\n\t\tproblem.printSolution(1);\r\n\t\tproblem.printConstraints(1);\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"The dual variables of the solution are printed with \"\r\n\t\t\t+ \"problem.printDuals()\");\r\n\t\tproblem.printDuals();\r\n\t\tpressRet();\r\n\t\t\t\t\r\n\t\tSystem.out.println(\"We can change a single element in the matix with \"\r\n\t\t\t+ \"problem.setMat(2, 1, 0.5)\");\r\n\t\tproblem.setMat(2, 1, 0.5);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"If we want to maximize the objective function use \"\r\n\t\t\t+ \"problem.setMaxim()\");\r\n\t\tproblem.setMaxim();\t\t\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\t\t\r\n\t\tSystem.out.println(\"After solving this gives us:\");\r\n\t\tproblem.solve();\r\n\t\tproblem.printObjective();\r\n\t\tproblem.printSolution(1);\r\n\t\tproblem.printConstraints(1);\r\n\t\tproblem.printDuals();\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"Change the value of a rhs element with problem.setRh(1, 7.45)\");\r\n\t\tproblem.setRh(1, 7.45);\r\n\t\tproblem.printLp();\r\n\t\tproblem.solve();\r\n\t\tproblem.printObjective();\r\n\t\tproblem.printSolution(1);\r\n\t\tproblem.printConstraints(1);\r\n\t\tpressRet();\r\n\t\r\n\t\tSystem.out.println(\"We change \" + problem.getColName(4) \r\n\t\t\t+ \" to the integer type with problem.setInt(4, true)\");\r\n\t\tproblem.setInt(4, true);\r\n\t\tproblem.printLp();\r\n\t\tSystem.out.println(\"We set branch & bound debugging on with problem.setDebug(true)\");\r\n\t\tproblem.setDebug(true);\r\n\t\tSystem.out.println(\"and solve...\");\r\n\t\tpressRet();\r\n\t\t\r\n\t\tproblem.solve();\r\n\t\tproblem.printObjective();\r\n\t\tproblem.printSolution(1);\r\n\t\tproblem.printConstraints(1);\r\n\t\tpressRet();\r\n\t\r\n\t\tSystem.out.println(\"We can set bounds on the variables with \"\r\n\t\t\t+ \"problem.setLowbo(2, 2) & problem.setUpbo(4, 5.3)\");\r\n\t\tproblem.setLowbo(2, 2);\r\n\t\tproblem.setUpbo(4, 5.3);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\r\n\t\tproblem.solve();\r\n\t\tproblem.printObjective();\r\n\t\tproblem.printSolution(1);\r\n\t\tproblem.printConstraints(1);\r\n\t\tpressRet();\r\n\t\r\n\t\tSystem.out.println(\"Now remove a constraint with problem.delConstraint(1)\");\r\n\t\tproblem.delConstraint(1);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\r\n\t\tSystem.out.println(\"Add an equality constraint:\\n\" \r\n\t\t\t+ \"problem.strAddConstraint(\\\"1 2 1 4\\\", LpSolve.EQ, 8)\");\r\n\t\tproblem.strAddConstraint(\"1 2 1 4\", LpSolve.EQ, 8);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"A column can be added with problem.strAddColumn(\\\"3 2 2\\\")\");\r\n\t\tproblem.strAddColumn(\"3 2 2\");\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\r\n\t\tSystem.out.println(\"A column can be removed with problem.delColumn(3)\");\r\n\t\tproblem.delColumn(3);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"We can use automatic scaling with problem.setScaling(LpSolve.SCALE_MEAN)\");\r\n\t\tproblem.setScaling(LpSolve.SCALE_MEAN);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\r\n\t\tSystem.out.println(\"The function matElm returns a single matrix element.\");\r\n\t\tSystem.out.println(\"problem.getMat(2, 3) returns \" + problem.getMat(2, 3));\r\n\t\tSystem.out.println(\"problem.getMat(1, 1) returns \" + problem.getMat(1, 1));\r\n\t\tSystem.out.println(\"Notice that getMat returns the value of the \"\r\n\t\t\t+ \"original unscaled problem\");\r\n\t\tpressRet();\r\n\r\n\t\tSystem.out.println(\"If there are any integer type variables, then only \"\r\n\t\t\t+ \" the rows are scaled.\");\r\n\t\tSystem.out.println(\"problem.setScaling(LpSolve.SCALE_MEAN);\");\t\t\r\n\t\tproblem.setScaling(LpSolve.SCALE_MEAN);\r\n\t\tSystem.out.println(\"problem.setInt(3, false);\");\t\t\r\n\t\tproblem.setInt(3, false);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"printObjective, printSolution gives the solution to the \"\r\n\t\t\t+ \"original problem\");\r\n\t\tproblem.solve();\r\n\t\tproblem.printObjective();\r\n\t\tproblem.printSolution(1);\r\n\t\tproblem.printConstraints(1);\r\n\t\tpressRet();\r\n\r\n\t\tSystem.out.println(\"Scaling is turned off with problem.unscale()\");\r\n\t\tproblem.unscale();\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\r\n\t\tSystem.out.println(\"Now turn B&B debugging off and simplex tracing on with\");\r\n\t\tSystem.out.println(\"problem.setDebug(false), problem.setTrace(true) and solve.\");\r\n\t\tproblem.setDebug(false);\r\n\t\tproblem.setTrace(true);\r\n\t\tpressRet();\r\n\r\n\t\tproblem.solve();\r\n\t\tSystem.out.println(\"Where possible, lp_solve will start at the last found basis.\");\r\n\t\tSystem.out.println(\"We can reset the problem to the initial basis with\");\r\n\t\tSystem.out.println(\"problem.resetBasis(). Now solve it again ...\");\r\n\t\tpressRet();\r\n\r\n\t\tproblem.resetBasis();\r\n\t\tproblem.solve();\r\n\t\tSystem.out.println(\"It is possible to give variables and constraints names.\");\r\n\t\tSystem.out.println(\"problem.setRowName(1, \\\"speed\\\") & problem.setColName(2, \\\"money\\\")\");\r\n\t\tproblem.setRowName(1, \"speed\");\r\n\t\tproblem.setColName(2, \"money\");\r\n\t\tproblem.printLp();\r\n\t\tSystem.out.println(\"As you can see, all column and rows are assigned default names\");\r\n\t\tSystem.out.println(\"If a column or constraint is deleted, the names shift place also:\");\r\n\t\tpressRet();\r\n\t\t\r\n\t\tSystem.out.println(\"problem.delColumn(1)\");\r\n\t\tproblem.delColumn(1);\r\n\t\tproblem.printLp();\r\n\t\tpressRet();\r\n\t\t\r\n\t\t// delete the problem \r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tprivate void pressRet() {\r\n\t\tSystem.out.print(\"\\n[Press return to continue or type 'q' to quit] \");\r\n\t\tBufferedReader br = new BufferedReader(new InputStreamReader(System.in));\r\n\t\ttry {\r\n\t\t\tString line = br.readLine();\r\n\t\t\tif (line == null || \"q\".equals(line.trim())) {\r\n\t\t\t\tSystem.out.println(\"Demo terminated.\");\r\n\t\t\t\tSystem.exit(0);\r\n\t\t\t}\r\n\t\t} \r\n\t\tcatch (IOException e) {\r\n\t\t\tSystem.exit(0);\r\n\t\t}\r\n\t\tSystem.out.println(\"\");\r\n\t}\r\n\r\n\tpublic static void main(String[] args) {\r\n\t\ttry {\r\n\t\t\tnew Demo().execute();\r\n\t\t} \r\n\t\tcatch (LpSolveException e) {\r\n\t\t\te.printStackTrace();\r\n\t\t}\r\n\t}\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/LpSolveTest.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\nimport java.io.File;\r\nimport java.util.Arrays;\r\n\r\nimport lpsolve.*;\r\nimport junit.framework.TestCase;\r\nimport junit.framework.TestSuite;\r\n\r\n/**\r\n * JUnit tests for methods of the LpSolve class.\r\n *\r\n * @author Juergen Ebert\r\n */\r\npublic class LpSolveTest extends TestCase {\r\n\r\n\tpublic LpSolveTest(String name) {\r\n\t\tsuper(name);\r\n\t}\r\n\r\n\tpublic static void main(String[] args) {\r\n\t\tjunit.textui.TestRunner.run(suite());\r\n\t}\r\n\r\n\tpublic static TestSuite suite() {\r\n\t\treturn new TestSuite(LpSolveTest.class);\r\n\t}\r\n\r\n\t/**\r\n\t * This test is important to check if we test against the\r\n\t * correct lp_solve version.\r\n\t */\r\n\tpublic void testVersion() throws Exception {\r\n\t\tVersionInfo info = LpSolve.lpSolveVersion();\r\n\t\tassertEquals(5, info.getMajorversion());\r\n\t\tassertEquals(5, info.getMinorversion());\r\n\t\tassertEquals(0, info.getRelease());\r\n\t\t/* assertEquals(2, info.getBuild()); */\r\n\t}\r\n\r\n\tpublic void testMakeLp() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertTrue(problem.getLp() > 0);\r\n\t\tproblem.deleteLp();\r\n\t\tassertEquals(0, problem.getLp());\r\n\t}\r\n\r\n\tpublic void testTwoProblems() throws Exception {\r\n\t\tLpSolve problem1 = LpSolve.makeLp(3, 4);\r\n\t\tLpSolve problem2 = LpSolve.makeLp(5, 6);\r\n\t\tassertTrue(problem1.getLp() > 0);\r\n\t\tassertTrue(problem2.getLp() > 0);\r\n\t\tassertTrue(problem1.getLp() != problem2.getLp());\r\n\r\n\t\tassertEquals(3, problem1.getNrows());\r\n\t\tassertEquals(5, problem2.getNrows());\r\n\t\tassertEquals(4, problem1.getNcolumns());\r\n\t\tassertEquals(6, problem2.getNcolumns());\r\n\t\tassertEquals(3, problem1.getNorigRows());\r\n\t\tassertEquals(5, problem2.getNorigRows());\r\n\t\tassertEquals(4, problem1.getNorigColumns());\r\n\t\tassertEquals(6, problem2.getNorigColumns());\r\n\r\n\t\tproblem1.deleteLp();\r\n\t\tproblem2.deleteLp();\r\n\t\tassertEquals(0, problem1.getLp());\r\n\t\tassertEquals(0, problem2.getLp());\r\n\t}\r\n\r\n\t/**\r\n\t * Set up a test model that is used in a number of test cases\r\n\t */\r\n\tprivate LpSolve setupProblem() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\treturn problem;\r\n\t}\r\n\r\n\t/**\r\n\t * Verify a test model that is used in a number of test cases\r\n\t */\r\n\tprivate void verifyProblem(LpSolve problem) throws Exception {\r\n\t\tassertEquals(2, problem.getNrows());\r\n\t\tassertEquals(4, problem.getNcolumns());\r\n\t\tdouble[] objFn = problem.getPtrRow(0);\r\n\t\tassertEquals(4+1, objFn.length);\r\n\t\tassertEquals(2, objFn[1], 1e-8);\r\n\t\tassertEquals(3, objFn[2], 1e-8);\r\n\t\tassertEquals(-2, objFn[3], 1e-8);\r\n\t\tassertEquals(3, objFn[4], 1e-8);\r\n\t}\r\n\r\n\tpublic void testReadWriteLp() throws Exception {\r\n\t\tString filename = \"testmodel.lp\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tproblem.writeLp(filename);\r\n\t\tassertTrue(file.exists());\r\n\t\tproblem.deleteLp();\r\n\r\n\t\tproblem = LpSolve.readLp(filename, LpSolve.NORMAL, \"Testmodel LP\");\r\n\t\tverifyProblem(problem);\r\n\t\tproblem.deleteLp();\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testReadWriteLpNative() throws Exception {\r\n\t\tString filename = \"model_.lp\";\t// use german native chars in filename\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tproblem.writeLp(filename);\r\n\t\tassertTrue(file.exists());\r\n\t\tproblem.deleteLp();\r\n\r\n\t\tproblem = LpSolve.readLp(filename, LpSolve.NORMAL, \"Testmodel LP\");\r\n\t\tverifyProblem(problem);\r\n\t\tproblem.deleteLp();\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testReadWriteMps() throws Exception {\r\n\t\tString filename = \"testmodel.mps\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tproblem.writeMps(filename);\r\n\t\tassertTrue(file.exists());\r\n\t\tproblem.deleteLp();\r\n\r\n\t\tproblem = LpSolve.readMps(filename, LpSolve.NORMAL);\r\n\t\tverifyProblem(problem);\r\n\t\tproblem.deleteLp();\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testReadWriteFreeMps() throws Exception {\r\n\t\tString filename = \"testmodel.fmps\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tproblem.writeFreeMps(filename);\r\n\t\tassertTrue(file.exists());\r\n\t\tproblem.deleteLp();\r\n\r\n\t\tproblem = LpSolve.readFreeMps(filename, LpSolve.NORMAL);\r\n\t\tverifyProblem(problem);\r\n\t\tproblem.deleteLp();\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n        // API call copy_lp doesn't work yet. Test is useless */\r\n        /*\r\n\tpublic void testCopyLp() throws Exception {\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tLpSolve copy = problem.copyLp();\r\n\t\tverifyProblem(problem);\r\n\t\tverifyProblem(copy);\r\n\t\tproblem.deleteLp();\r\n\t\tcopy.deleteLp();\r\n\t}\r\n        */\r\n\r\n\t// TODO: find out under what conditions to call dualizeLp\r\n\t/*\r\n\tpublic void testDualizeLp() throws Exception {\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\t// No idea what this does; just call it to see if it crashes\r\n\t\tproblem.dualizeLp();\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\t*/\r\n\r\n\r\n\t/**\r\n\t * Helper method for the various xli_* variants\r\n\t */\r\n\tprivate void readWriteXLI(String name) throws Exception {\r\n\t\tString filename = \"testmodel_\" + name + \".txt\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\r\n\t\tString xliname = \"xli_\" + name;\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tproblem.setXLI(xliname);\r\n\t\tproblem.writeXLI(filename, null, false);\r\n\t\tassertTrue(file.exists());\r\n\t\tproblem.deleteLp();\r\n\r\n\t\tproblem = LpSolve.readXLI(xliname, filename, null, null, LpSolve.NORMAL);\r\n\t\tverifyProblem(problem);\r\n\t\tproblem.deleteLp();\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testReadWriteXLI_CPLEX() throws Exception {\r\n\t\treadWriteXLI(\"CPLEX\");\r\n\t}\r\n\r\n\tpublic void testReadWriteXLI_LINDO() throws Exception {\r\n\t\treadWriteXLI(\"LINDO\");\r\n\t}\r\n\r\n\t/* Not used, because xli_LPFML is currently not available on LInux\r\n\t * and requires additional lis (Xerces , ..)\r\n\tpublic void testReadWriteXLI_LPFML() throws Exception {\r\n\t\treadWriteXLI(\"LPFML\");\r\n\t}\r\n\t*/\r\n\r\n\t/* Not used, because xli_MathProg cannot write models\r\n\tpublic void testReadWriteXLI_MathProg() throws Exception {\r\n\t\treadWriteXLI(\"MathProg\");\r\n\t}\r\n\t*/\r\n\r\n\tpublic void testSetXLI_Unknown() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\ttry {\r\n\t\t\tproblem.setXLI(\"Unknown\");\r\n\t\t\tfail(\"Setting a nonexistent XLI should throw an exception\");\r\n\t\t}\r\n\t\tcatch (LpSolveException e) {\r\n\t\t\t// OK\r\n                        System.out.println(\"setXLI failed as expected\");\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testHasXLI() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tassertFalse(problem.isNativeXLI()); \t// is always FALSE\r\n\t\tassertFalse(problem.hasXLI());\r\n\t\tproblem.setXLI(\"xli_CPLEX\");\r\n\t\tassertTrue(problem.hasXLI());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testresizeLp() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tproblem.resizeLp(4, 5);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testAddColumnex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 0);\r\n\t\tassertEquals(0, problem.getNcolumns());\r\n\t\tdouble[] column = { 1.5, 3.5 };\r\n\t\tint[] rowno = { 1, 3 };\r\n\t\tproblem.addColumnex(2, column, rowno);\r\n\t\tassertEquals(1, problem.getNcolumns());\r\n\t\tdouble[] col = problem.getPtrColumn(1);\r\n\t\tassertEquals(0, col[0], 1e-8);\r\n\t\tassertEquals(1.5, col[1], 1e-8);\r\n\t\tassertEquals(0, col[2], 1e-8);\r\n\t\tassertEquals(3.5, col[3], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetColumn() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 0);\r\n\t\tproblem.strAddColumn(\"1 2 3 4\");\r\n\t\tassertEquals(1, problem.getNcolumns());\r\n\t\tdouble[] col = problem.getPtrColumn(1);\r\n\t\tassertEquals(1, col[0], 1e-8);\r\n\t\tassertEquals(2, col[1], 1e-8);\r\n\t\tassertEquals(3, col[2], 1e-8);\r\n\t\tassertEquals(4, col[3], 1e-8);\r\n\t\tdouble[] newcol = { 5, 6, 7, 8 };\r\n\t\tproblem.setColumn(1, newcol);\r\n\t\tcol = problem.getPtrColumn(1);\r\n\t\tassertEquals(5, col[0], 1e-8);\r\n\t\tassertEquals(6, col[1], 1e-8);\r\n\t\tassertEquals(7, col[2], 1e-8);\r\n\t\tassertEquals(8, col[3], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetColumnex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 0);\r\n\t\tproblem.strAddColumn(\"1 2 3 4\");\r\n\t\tassertEquals(1, problem.getNcolumns());\r\n\t\tdouble[] col = problem.getPtrColumn(1);\r\n\t\tassertEquals(1, col[0], 1e-8);\r\n\t\tassertEquals(2, col[1], 1e-8);\r\n\t\tassertEquals(3, col[2], 1e-8);\r\n\t\tassertEquals(4, col[3], 1e-8);\r\n\t\tdouble[] newcol = { 6, 8 };\r\n\t\tint[] rowno = { 1, 3 };\r\n\t\tproblem.setColumnex(1, 2, newcol, rowno);\r\n\t\tcol = problem.getPtrColumn(1);\r\n\t\tassertEquals(0, col[0], 1e-8);\t// unspecified values are set to zero !?\r\n\t\tassertEquals(6, col[1], 1e-8);\r\n\t\tassertEquals(0, col[2], 1e-8);\r\n\t\tassertEquals(8, col[3], 1e-8);\t// unspecified values are set to zero !?\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetRow() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"1 2 3 4\", LpSolve.LE, 4);\r\n\t\tdouble[] ptrRow = problem.getPtrRow(1);\r\n\t\tassertEquals(1+4, ptrRow.length);\r\n\t\tassertEquals(1, ptrRow[1], 1e-8);\r\n\t\tassertEquals(2, ptrRow[2], 1e-8);\r\n\t\tdouble[] newRow = { 0, 5, 6, 7, 8 };\t// element 0 is unused\r\n\t\tproblem.setRow(1, newRow);\r\n\t\tptrRow = problem.getPtrRow(1);\r\n\t\tassertEquals(5, ptrRow[1], 1e-8);\r\n\t\tassertEquals(6, ptrRow[2], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetRowex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"1 2 3 4\", LpSolve.LE, 4);\r\n\t\tdouble[] ptrRow = problem.getPtrRow(1);\r\n\t\tassertEquals(1+4, ptrRow.length);\r\n\t\tassertEquals(1, ptrRow[1], 1e-8);\r\n\t\tassertEquals(2, ptrRow[2], 1e-8);\r\n\t\tassertEquals(3, ptrRow[3], 1e-8);\r\n\t\tassertEquals(4, ptrRow[4], 1e-8);\r\n\t\tdouble[] newRow = { 5, 7 };\r\n\t\tint[] colno = { 1, 3 };\r\n\t\tproblem.setRowex(1, 2, newRow, colno);\r\n\t\tptrRow = problem.getPtrRow(1);\r\n\t\tassertEquals(5, ptrRow[1], 1e-8);\r\n\t\tassertEquals(0, ptrRow[2], 1e-8);\t // unspecified values are set to 0\r\n\t\tassertEquals(7, ptrRow[3], 1e-8);\r\n\t\tassertEquals(0, ptrRow[4], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetBasiscrash() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tassertEquals(LpSolve.CRASH_NOTHING, problem.getBasiscrash());\t// default\r\n\t\tproblem.setBasiscrash(LpSolve.CRASH_MOSTFEASIBLE);\r\n\t\tassertEquals(LpSolve.CRASH_MOSTFEASIBLE, problem.getBasiscrash());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetBbDepthlimit() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tassertEquals(-50, problem.getBbDepthlimit());\t// default\r\n\t\tproblem.setBbDepthlimit(10);\r\n\t\tassertEquals(10, problem.getBbDepthlimit());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetSimplextype() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tassertEquals(LpSolve.SIMPLEX_DEFAULT, problem.getSimplextype());\t// default\r\n\t\tassertEquals(LpSolve.SIMPLEX_DUAL_PRIMAL, problem.getSimplextype());\t// default\r\n\t\tproblem.setSimplextype(LpSolve.SIMPLEX_PRIMAL_DUAL);\r\n\t\tassertEquals(LpSolve.SIMPLEX_PRIMAL_DUAL, problem.getSimplextype());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetPreferdual() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tproblem.setPreferdual(true);\r\n\t\tassertEquals(LpSolve.SIMPLEX_DUAL_DUAL, problem.getSimplextype());\r\n\t\tproblem.setPreferdual(false);\r\n\t\tassertEquals(LpSolve.SIMPLEX_PRIMAL_PRIMAL, problem.getSimplextype());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetScalelimit() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tassertEquals(5, problem.getScalelimit(), 1e-8);\t // default\r\n\t\tproblem.setScalelimit(10);\r\n\t\tassertEquals(10, problem.getScalelimit(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetStatustext() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tint status = problem.solve();\r\n\t\tString text = problem.getStatustext(status);\r\n\t\tassertNotNull(text);\r\n\t\tassertTrue(text.length() > 0);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetBFP() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tassertTrue(problem.hasBFP());\r\n\t\tassertTrue(problem.isNativeBFP());\r\n\t\t// This requires the bfp_LUSOL.dll in the path !!\r\n\t\tproblem.setBFP(\"bfp_LUSOL\");\r\n\t\tassertTrue(problem.hasBFP());\r\n\t\tassertFalse(problem.isNativeBFP());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetBFPException() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\ttry {\r\n\t\t\tproblem.setBFP(\"nonexistent\");\r\n\t\t\tfail(\"Setting a nonexistent BFP should throw an exception\");\r\n\t\t} catch (LpSolveException e) {\r\n\t\t\t// OK\r\n                        System.out.println(\"setBFP failed as expected\");\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetUnbounded() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tassertFalse(problem.isUnbounded(1));\r\n\t\tproblem.setUnbounded(1);\r\n\t\tassertTrue(problem.isUnbounded(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testIsNegative() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tassertFalse(problem.isNegative(1));\r\n\t\tproblem.setLowbo(1, -10);\r\n\t\tproblem.setUpbo(1, -1);\r\n\t\tassertTrue(problem.isNegative(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetUpbo() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tassertEquals(1E30, problem.getUpbo(1), 1e-8);\t // default\r\n\t\tproblem.setUpbo(1, 1234);\r\n\t\tassertEquals(1234, problem.getUpbo(1), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetLowbo() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tassertEquals(0.0, problem.getLowbo(1), 1e-8);\t // default\r\n\t\tproblem.setLowbo(1, -1234);\r\n\t\tassertEquals(-1234, problem.getLowbo(1), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetBounds() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tproblem.setBounds(1, -1234, 5555);\r\n\t\tassertEquals(-1234, problem.getLowbo(1), 1e-8);\r\n\t\tassertEquals(5555, problem.getUpbo(1), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testWriteDebugdump() throws Exception {\r\n\t\tString filename = \"debugdump.txt\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tproblem.printDebugdump(file.getAbsolutePath());\r\n\t\tproblem.deleteLp();\r\n\t\tassertTrue(file.exists());\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testSetOutputfile() throws Exception {\r\n\t\tString filename = \"print_file.txt\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.setOutputfile(file.getAbsolutePath());\r\n\t\tproblem.setOutputfile(null);\r\n\t\tproblem.deleteLp();\r\n\t\tassertTrue(file.exists());\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testPrintSolution() throws Exception {\r\n\t\tString filename = \"print_solution.txt\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.setOutputfile(file.getAbsolutePath());\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.printLp();\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tproblem.printSolution(1);\r\n\t\tproblem.printConstraints(1);\r\n\t\tproblem.printObjective();\r\n\t\tproblem.printDuals();\r\n\t\tproblem.printScales();\r\n\t\tproblem.setOutputfile(null);\r\n\t\tproblem.deleteLp();\r\n\t\tassertTrue(file.exists());\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testPrintTableau() throws Exception {\r\n\t\tString filename = \"print_tableau.txt\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.setOutputfile(file.getAbsolutePath());\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tproblem.printTableau();\r\n\t\tproblem.setOutputfile(null);\r\n\t\tproblem.deleteLp();\r\n\t\tassertTrue(file.exists());\r\n\t\tassertTrue(file.canRead());\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testPrintStr() throws Exception {\r\n\t\tString filename = \"print_str.txt\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.setOutputfile(file.getAbsolutePath());\r\n\t\tproblem.printStr(\"Test\");\r\n\t\tproblem.printStr(null);\r\n\t\tproblem.setOutputfile(null);\r\n\t\tproblem.deleteLp();\r\n\t\tassertTrue(file.exists());\r\n\t\tassertTrue(file.length() >= 8);\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testSetObj() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tdouble[] objFn = problem.getPtrRow(0);\r\n\t\tassertEquals(4+1, objFn.length);\r\n\t\tassertEquals(2, objFn[1], 1e-8);\r\n\t\tproblem.setObj(1, 6.6);\r\n\t\tobjFn = problem.getPtrRow(0);\r\n\t\tassertEquals(4+1, objFn.length);\r\n\t\tassertEquals(6.6, objFn[1], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetRow() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tint size = 1 + problem.getNcolumns();\r\n\t\tdouble[] row = new double[size];\r\n\t\tproblem.getRow(1, row);\r\n\t\tdouble[] ptrRow = problem.getPtrRow(1);\r\n\t\tassertEquals(size, ptrRow.length);\r\n\t\tassertEquals(3, row[1], 1e-8);\r\n\t\tfor (int i = 0; i < size; i++) {\r\n\t\t\tassertEquals(row[i], ptrRow[i], 1e-8);\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetRowex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 0 1\", LpSolve.GE, 3);\r\n\t\tint size = problem.getNcolumns();\r\n\t\tdouble[] row = new double[size];\r\n\t\tint[] nzcols = new int[size];\r\n\r\n\t\tint nzcount = problem.getRowex(1, row, nzcols);\r\n\t\tassertEquals(4, nzcount);\r\n\t\tassertEquals(3, row[0], 1e-8);\r\n\t\tassertEquals(2, row[1], 1e-8);\r\n\t\tassertEquals(2, row[2], 1e-8);\r\n\t\tassertEquals(1, row[3], 1e-8);\r\n\t\tassertEquals(1, nzcols[0]);\r\n\t\tassertEquals(2, nzcols[1]);\r\n\t\tassertEquals(3, nzcols[2]);\r\n\t\tassertEquals(4, nzcols[3]);\r\n\r\n\t\tnzcount = problem.getRowex(2, row, nzcols);\r\n\t\tassertEquals(2, nzcount);\r\n\t\tassertEquals(4, row[0], 1e-8);\r\n\t\tassertEquals(1, row[1], 1e-8);\r\n\t\tassertEquals(2, nzcols[0]);\r\n\t\tassertEquals(4, nzcols[1]);\r\n\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetColumn() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tint size = 1 + problem.getNrows();\r\n\t\tdouble[] column = new double[size];\r\n\t\tproblem.getColumn(1, column);\r\n\t\tdouble[] ptrColumn = problem.getPtrColumn(1);\r\n\t\tassertEquals(size, ptrColumn.length);\r\n\t\tassertEquals(2, column[0], 1e-8);\r\n\t\tfor (int i = 0; i < size; i++) {\r\n\t\t\tassertEquals(column[i], ptrColumn[i], 1e-8);\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetColumnex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.strAddConstraint(\"0 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"3 4 0 1\", LpSolve.GE, 3);\r\n\t\tint size = 1 + problem.getNrows();\r\n\t\tdouble[] col = new double[size];\r\n\t\tint[] nzrows = new int[size];\r\n\r\n\t\tint nzcount = problem.getColumnex(1, col, nzrows);\r\n\t\tassertEquals(2, nzcount);\r\n\t\tassertEquals(2, col[0], 1e-8);\r\n\t\tassertEquals(3, col[1], 1e-8);\r\n\t\tassertEquals(0, nzrows[0]);\r\n\t\tassertEquals(2, nzrows[1]);\r\n\r\n\t\tnzcount = problem.getColumnex(2, col, nzrows);\r\n\t\tassertEquals(3, nzcount);\r\n\t\tassertEquals(3, col[0], 1e-8);\r\n\t\tassertEquals(2, col[1], 1e-8);\r\n\t\tassertEquals(4, col[2], 1e-8);\r\n\t\tassertEquals(0, nzrows[0]);\r\n\t\tassertEquals(1, nzrows[1]);\r\n\t\tassertEquals(2, nzrows[2]);\r\n\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testMinimMaxim() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertFalse(problem.isMaxim());\t// default\r\n\t\tproblem.setMaxim();\r\n\t\tassertTrue(problem.isMaxim());\r\n\t\tproblem.setMinim();\r\n\t\tassertFalse(problem.isMaxim());\r\n\t\tproblem.setMaxim();\r\n\t\tassertTrue(problem.isMaxim());\r\n\t\tproblem.setSense(false);\r\n\t\tassertFalse(problem.isMaxim());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testAddDelConstraint() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(0, problem.getNrows());\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tassertEquals(1, problem.getNrows());\r\n\t\tdouble[] row = { 0.0, 1.0, 2.0, 3.0, 4.0 };\r\n\t\tproblem.addConstraint(row, LpSolve.GE, 5.0);\r\n\t\tassertEquals(2, problem.getNrows());\r\n\t\tproblem.delConstraint(1);\r\n\t\tassertEquals(1, problem.getNrows());\r\n\t\tproblem.delConstraint(1);\r\n\t\tassertEquals(0, problem.getNrows());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testAddConstraintex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(0, problem.getNrows());\r\n\t\tdouble[] constr = { 1.5, 3.5 };\r\n\t\tint[] colno = { 1, 3 };\r\n\t\tproblem.addConstraintex(2, constr, colno, LpSolve.GE, 10);\r\n\t\tassertEquals(1, problem.getNrows());\r\n\t\tdouble[] row = problem.getPtrRow(1);\r\n\t\tassertEquals(5, row.length);\r\n\t\tassertEquals(1.5, row[1], 1e-8);\r\n\t\tassertEquals(0.0, row[2], 1e-8);\r\n\t\tassertEquals(3.5, row[3], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetNonzeros() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(0, problem.getNonzeros());\r\n\t\tdouble[] constr = { 1.5, 3.5 };\r\n\t\tint[] colno = { 1, 3 };\r\n\t\tproblem.addConstraintex(2, constr, colno, LpSolve.GE, 10);\r\n\t\tassertEquals(2, problem.getNonzeros());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetObjFn() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strSetObjFn(\"1 -2 3 -4\");\r\n\t\tdouble[] objFn = problem.getPtrRow(0);\r\n\t\tassertEquals(5, objFn.length);\r\n\t\tassertEquals(1, objFn[1], 1e-8);\r\n\t\tassertEquals(-2, objFn[2], 1e-8);\r\n\t\tassertEquals(3, objFn[3], 1e-8);\r\n\t\tassertEquals(-4, objFn[4], 1e-8);\r\n\r\n\t\tproblem.setObjFn(new double[] {0, 9, -8, 7, -6});\r\n\t\tobjFn = problem.getPtrRow(0);\r\n\t\tassertEquals(9, objFn[1], 1e-8);\r\n\t\tassertEquals(-8, objFn[2], 1e-8);\r\n\t\tassertEquals(7, objFn[3], 1e-8);\r\n\t\tassertEquals(-6, objFn[4], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetObjFnex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tdouble[] objfn = { 1.5, 3.5 };\r\n\t\tint[] colno = { 2, 4 };\r\n\t\tproblem.setObjFnex(2, objfn, colno);\r\n\t\tdouble[] row = problem.getPtrRow(0);\r\n\t\tassertEquals(5, row.length);\r\n\t\tassertEquals(1.5, row[2], 1e-8);\r\n\t\tassertEquals(0.0, row[3], 1e-8);\r\n\t\tassertEquals(3.5, row[4], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\t/* TODO: activate if *Lag* functiona are supported again\r\n\tpublic void testAddLagConstraint() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(0, problem.getLrows());\r\n\t\tproblem.strAddLagCon(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tassertEquals(1, problem.getLrows());\r\n\t\tdouble[] row = { 0.0, 1.0, 2.0, 3.0, 4.0 };\r\n\t\tproblem.addLagCon(row, LpSolve.GE, 5.0);\r\n\t\tassertEquals(2, problem.getLrows());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\t*/\r\n\r\n\tpublic void testAddDelColumn() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 0);\r\n\t\tassertEquals(0, problem.getNcolumns());\r\n\t\tproblem.strAddColumn(\"3 2 2 1\");\r\n\t\tassertEquals(1, problem.getNcolumns());\r\n\t\tdouble[] column = { 0.0, 1.0, 2.0, 3.0, 4.0 };\r\n\t\tproblem.addColumn(column);\r\n\t\tassertEquals(2, problem.getNcolumns());\r\n\t\tproblem.delColumn(1);\r\n\t\tassertEquals(1, problem.getNcolumns());\r\n\t\tproblem.delColumn(1);\r\n\t\tassertEquals(0, problem.getNcolumns());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testDelColumnWithException() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\ttry {\r\n\t\t\tproblem.delColumn(1);\r\n\t\t\tfail(\"delColumn with nonexistent col shouold throw an Exception\");\r\n\t\t}\r\n\t\tcatch (LpSolveException e) {\r\n\t\t\t// OK\r\n                        System.out.println(\"delColumn failed as expected\");\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testColumnInLp() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 0);\r\n\t\tdouble[] column1 = { 0.0, 1.0, 2.0, 3.0, 4.0 };\r\n\t\tdouble[] column2 = { 0.0, 5.0, 6.0, 7.0, 8.0 };\r\n\t\tproblem.addColumn(column1);\r\n\t\tproblem.addColumn(column2);\r\n\t\tassertEquals(2, problem.getNcolumns());\r\n\t\tassertEquals(1, problem.columnInLp(column1));\r\n\t\tassertEquals(2, problem.columnInLp(column2));\r\n\t\tcolumn1[1] = 100.6;\r\n\t\tassertEquals(0, problem.columnInLp(column1));\r\n\t\tassertEquals(2, problem.columnInLp(column2));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetLpName() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(\"\", problem.getLpName());\r\n\t\tproblem.setLpName(\"test\");\r\n\t\tassertEquals(\"test\", problem.getLpName());\r\n\t\tproblem.setLpName(null);\r\n\t\tassertEquals(\"\", problem.getLpName());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetRowName() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(1, 0);\r\n\t\tassertEquals(\"R1\", problem.getRowName(1));\t// default\r\n\t\tproblem.setRowName(1, \"test\");\r\n\t\tassertEquals(\"test\", problem.getRowName(1));\r\n\t\tassertEquals(\"test\", problem.getOrigrowName(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetColName() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 1);\r\n\t\tassertEquals(\"C1\", problem.getColName(1));\t// default\r\n\t\tproblem.setColName(1, \"test\");\r\n\t\tassertEquals(\"test\", problem.getColName(1));\r\n\t\tassertEquals(\"test\", problem.getOrigcolName(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetMat() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(0.0, problem.getMat(1, 1), 1e-8);\t // default\r\n\t\tproblem.setMat(1, 1, 0.5);\r\n\t\tassertEquals(0.5, problem.getMat(1, 1), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetVerbose() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(LpSolve.NORMAL, problem.getVerbose());\t// default\r\n\t\tproblem.setVerbose(LpSolve.DETAILED);\r\n\t\tassertEquals(LpSolve.DETAILED, problem.getVerbose());\r\n\t\tproblem.setVerbose(LpSolve.SEVERE);\r\n\t\tassertEquals(LpSolve.SEVERE, problem.getVerbose());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetTimeout() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(0, problem.getTimeout());\t// default\r\n\t\tproblem.setTimeout(1234);\r\n\t\tassertEquals(1234, problem.getTimeout());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetPrintSol() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(LpSolve.FALSE, problem.getPrintSol());\t// default\r\n\t\tproblem.setPrintSol(LpSolve.TRUE);\r\n\t\tassertEquals(LpSolve.TRUE, problem.getPrintSol());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetDebug() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(false, problem.isDebug());\t// default\r\n\t\tproblem.setDebug(true);\r\n\t\tassertEquals(true, problem.isDebug());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetTrace() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(false, problem.isTrace());\t// default\r\n\t\tproblem.setTrace(true);\r\n\t\tassertEquals(true, problem.isTrace());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetLagTrace() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(false, problem.isLagTrace());\t// default\r\n\t\tproblem.setLagTrace(true);\r\n\t\tassertEquals(true, problem.isLagTrace());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSetAddRowmode() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(false, problem.isAddRowmode());\t// default\r\n\t\tassertEquals(false, problem.setAddRowmode(false));\r\n\t\tassertEquals(true, problem.setAddRowmode(true));\r\n\t\tassertEquals(true, problem.isAddRowmode());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\t/* Reproduces a problem reported in the mailing list */\r\n\tpublic void testSetAddRowmode2() throws Exception {\r\n\t\t// Do not predefine rows in makeLp when using addConstraint !\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.setAddRowmode(true);\r\n\t\tassertEquals(true, problem.isAddRowmode());\r\n\t\tdouble[] objFn = { 0, 2, 3, -2, 3 };\r\n\t\tproblem.setObjFn(objFn);\r\n\t\tdouble[] row = { 0.0, 1.0, 2.0, 3.0, 4.0 };\r\n\t\tproblem.addConstraint(row, LpSolve.GE, 5.0);\r\n\t\tproblem.setAddRowmode(false);\r\n\r\n\t\tobjFn = problem.getPtrRow(0);\r\n\t\tassertEquals(2, objFn[1], 1e-8);\r\n\t\tassertEquals(3, objFn[2], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetAntiDegen() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tproblem.setAntiDegen(LpSolve.ANTIDEGEN_DYNAMIC);\r\n\t\tassertEquals(true, problem.isAntiDegen(LpSolve.ANTIDEGEN_DYNAMIC));\r\n\t\tassertEquals(LpSolve.ANTIDEGEN_DYNAMIC, problem.getAntiDegen());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetPresolve() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(true, problem.isPresolve(LpSolve.PRESOLVE_NONE));\t// default\r\n\t\tproblem.setPresolve(LpSolve.PRESOLVE_ROWS | LpSolve.PRESOLVE_COLS, 2);\r\n\t\tassertTrue(problem.isPresolve(LpSolve.PRESOLVE_ROWS | LpSolve.PRESOLVE_COLS));\r\n\t\tassertTrue(problem.isPresolve(LpSolve.PRESOLVE_ROWS));\r\n\t\tassertEquals(LpSolve.PRESOLVE_ROWS | LpSolve.PRESOLVE_COLS, problem.getPresolve());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetPresolveloops() throws Exception {\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tproblem.setPresolve(LpSolve.PRESOLVE_ROWS | LpSolve.PRESOLVE_COLS, 1);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tassertEquals(1, problem.getPresolveloops());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetMaxpivot() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(250, problem.getMaxpivot());\t// default for LUSOL\r\n\t\tproblem.setMaxpivot(44);\r\n\t\tassertEquals(44, problem.getMaxpivot());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetBbRule() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tproblem.setBbRule(LpSolve.NODE_RANGESELECT);\r\n\t\tassertEquals(LpSolve.NODE_RANGESELECT, problem.getBbRule());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetObjBound() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(problem.getInfinite(), problem.getObjBound(), 1e-8);\t // default\r\n\t\tproblem.setObjBound(1234.56);\r\n\t\tassertEquals(1234.56, problem.getObjBound(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetFloorFirst() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(LpSolve.BRANCH_AUTOMATIC, problem.getBbFloorfirst());\t// default\r\n\t\tproblem.setBbFloorfirst(LpSolve.BRANCH_CEILING);\r\n\t\tassertEquals(LpSolve.BRANCH_CEILING, problem.getBbFloorfirst());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetUseNames() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 4);\r\n\t\tassertEquals(true, problem.isUseNames(true));\t// default\r\n\t\tassertEquals(true, problem.isUseNames(false));\t// default\r\n\t\tproblem.setUseNames(true, false);\r\n\t\tproblem.setUseNames(false, false);\r\n\t\tassertEquals(false, problem.isUseNames(true));\r\n\t\tassertEquals(false, problem.isUseNames(false));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetObjectiveGetSolution() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tint rc = problem.solve();\r\n\t\tassertEquals(LpSolve.OPTIMAL, rc);\r\n\t\tassertEquals(-4.0, problem.getObjective(), 1e-8);\r\n\t\tdouble[] solution = problem.getPtrPrimalSolution();\r\n\t\tint size = 1 + problem.getNrows() + problem.getNcolumns();\r\n\t\tassertEquals(size, solution.length);\r\n\t\tint firstVar = 1 + problem.getNrows();\r\n\t\tassertEquals(0.0, solution[firstVar + 0], 1e-8);\r\n\t\tassertEquals(0.0, solution[firstVar + 1], 1e-8);\r\n\t\tassertEquals(2.0, solution[firstVar + 2], 1e-8);\r\n\t\tassertEquals(0.0, solution[firstVar + 3], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testPrimalSolution() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tdouble[] objFn = { 0, 2, 3, -2, 3 };\r\n\t\tproblem.setObjFn(objFn);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tint rc = problem.solve();\r\n\t\tdouble[] solution1 = problem.getPtrPrimalSolution();\r\n\t\tdouble[] solution2 = new double[1 + 2 + 4];\r\n\t\tproblem.getPrimalSolution(solution2);\r\n\t\tArrays.equals(solution1, solution2);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testVarDualresult() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.setObjFn(new double[] { 0, 2, 3, -2, 3 });\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tassertEquals(4.0, problem.getVarPrimalresult(1), 1e-8);\r\n\t\t// TODO: the following used to be 0.0 until version 5.5 !!\r\n\t\tassertEquals(-1.0, problem.getVarDualresult(1), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetPtrVariables() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tdouble[] var = problem.getPtrVariables();\r\n\t\tassertEquals(problem.getNcolumns(), var.length);\r\n\t\tassertEquals(0.0, var[0], 1e-8);\r\n\t\tassertEquals(0.0, var[1], 1e-8);\r\n\t\tassertEquals(2.0, var[2], 1e-8);\r\n\t\tassertEquals(0.0, var[3], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetVariables() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tdouble[] var = new double[4];\r\n\t\tproblem.getVariables(var);\r\n\t\tassertEquals(problem.getNcolumns(), var.length);\r\n\t\tassertEquals(0.0, var[0], 1e-8);\r\n\t\tassertEquals(0.0, var[1], 1e-8);\r\n\t\tassertEquals(2.0, var[2], 1e-8);\r\n\t\tassertEquals(0.0, var[3], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetPtrConstraints() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tdouble[] var = problem.getPtrConstraints();\r\n\t\tassertEquals(problem.getNrows(), var.length);\r\n\t\tassertEquals(4.0, var[0], 1e-8);\r\n\t\tassertEquals(6.0, var[1], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetConstraints() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tdouble[] var = new double[2];\r\n\t\tproblem.getConstraints(var);\r\n\t\tassertEquals(problem.getNrows(), var.length);\r\n\t\tassertEquals(4.0, var[0], 1e-8);\r\n\t\tassertEquals(6.0, var[1], 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testRhVec() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tassertEquals(4.0, problem.getRh(1), 1e-8);\r\n\t\tassertEquals(3.0, problem.getRh(2), 1e-8);\r\n\t\tproblem.strSetRhVec(\"1 2\");\r\n\t\tassertEquals(1.0, problem.getRh(1), 1e-8);\r\n\t\tassertEquals(2.0, problem.getRh(2), 1e-8);\r\n\t\tproblem.setRhVec(new double[] {0.0, 6.0, 7.5});\r\n\t\tassertEquals(6.0, problem.getRh(1), 1e-8);\r\n\t\tassertEquals(7.5, problem.getRh(2), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testRh() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tassertEquals(4.0, problem.getRh(1), 1e-8);\r\n\t\tassertEquals(3.0, problem.getRh(2), 1e-8);\r\n\t\tproblem.setRh(1, 1.0);\r\n\t\tproblem.setRh(2, 2.0);\r\n\t\tassertEquals(1.0, problem.getRh(1), 1e-8);\r\n\t\tassertEquals(2.0, problem.getRh(2), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testConstrType() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tassertEquals(LpSolve.LE, problem.getConstrType(1));\r\n\t\tassertEquals(LpSolve.GE, problem.getConstrType(2));\r\n\t\tproblem.setConstrType(1, LpSolve.EQ);\r\n\t\tassertEquals(LpSolve.EQ, problem.getConstrType(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\t// TODO: enable test after problems with add_SOS are solved\r\n\t/*\r\n\tpublic void testAddSOS() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tint[] vars = { 2, 3 };\r\n\t\tdouble[] weights = { 1.0, 2.0 };\r\n\t\tproblem.addSOS(\"SOS\", 3, 1, 2, vars, weights);\r\n\t\tassertFalse(problem.isSOSVar(1));\r\n\t\tassertTrue(problem.isSOSVar(2));\r\n\t\tassertTrue(problem.isSOSVar(3));\r\n\t\tassertFalse(problem.isSOSVar(4));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\t*/\r\n\r\n\tpublic void testRhRange() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.setRhRange(1, 20.5);\r\n\t\tassertEquals(20.5, problem.getRhRange(1), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testInt() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(false, problem.isInt(1));\r\n\t\tproblem.setInt(1, true);\r\n\t\tassertEquals(true, problem.isInt(1));\r\n\t\tproblem.setInt(1, false);\r\n\t\tassertEquals(false, problem.isInt(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testBinary() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(false, problem.isBinary(1));\r\n\t\tproblem.setBinary(1, true);\r\n\t\tassertEquals(true, problem.isBinary(1));\r\n\t\tproblem.setBinary(1, false);\r\n\t\tassertEquals(false, problem.isBinary(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testSemicont() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(false, problem.isSemicont(1));\r\n\t\tproblem.setSemicont(1, true);\r\n\t\tassertEquals(true, problem.isSemicont(1));\r\n\t\tproblem.setSemicont(1, false);\r\n\t\tassertEquals(false, problem.isSemicont(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testInfinite() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(1E30, problem.getInfinite(), 1e-8); // default\r\n\t\tassertTrue(problem.isInfinite(problem.getInfinite()));\r\n\t\tassertFalse(problem.isInfinite(3E22));\r\n\t\tproblem.setInfinite(2.1E22);\r\n\t\tassertEquals(2.1E22, problem.getInfinite(), 1e-8);\r\n\t\tassertTrue(problem.isInfinite(3E22));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testEpsint() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(1E-7, problem.getEpsint(), 1e-8);\t // default\r\n\t\tproblem.setEpsint(0.0001);\r\n\t\tassertEquals(0.0001, problem.getEpsint(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testEpsb() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(1e-10, problem.getEpsb(), 1e-8);\t // default\r\n\t\tproblem.setEpsb(0.0001);\r\n\t\tassertEquals(0.0001, problem.getEpsb(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testEpsd() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(1e-9, problem.getEpsd(), 1e-8);\t // default\r\n\t\tproblem.setEpsd(0.0001);\r\n\t\tassertEquals(0.0001, problem.getEpsd(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testEpsel() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(1e-12, problem.getEpsel(), 1e-8);\t // default\r\n\t\tproblem.setEpsel(0.0001);\r\n\t\tassertEquals(0.0001, problem.getEpsel(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testEpspivot() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(2e-7, problem.getEpspivot(), 1e-8); // default\r\n\t\tproblem.setEpspivot(0.0001);\r\n\t\tassertEquals(0.0001, problem.getEpspivot(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testEpsperturb() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(1e-5, problem.getEpsperturb(), 1e-8);\t // default\r\n\t\tproblem.setEpsperturb(0.0001);\r\n\t\tassertEquals(0.0001, problem.getEpsperturb(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\t// TODO: find out under what conditions to call setEpslevel\r\n\t/*\r\n\tpublic void testEpslevel() throws Exception {\r\n\t\tLpSolve problem = setupProblem();\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\t// No idea what this method does and how to verify it.\r\n\t\t// Just call it to see if it crashes.\r\n\t\tproblem.setEpslevel(5);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\t*/\r\n\r\n\tpublic void testGetStatus() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(3, 0);\r\n\t\t// I have no idea what these status values mean\r\n\t\tassertEquals(-1, problem.getStatus());\r\n\t\ttry {\r\n\t\t\tproblem.strAddColumn(\"1 2 3\"); // should be 4 elements\r\n\t\t\tfail(\"this should throw an exception\");\r\n\t\t}\r\n\t\tcatch (LpSolveException e) {\r\n                        System.out.println(\"strAddColumn failed as expected\");\r\n                        assertEquals(-4, problem.getStatus());\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testMipGap() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.setMipGap(true, 0.0001);\r\n\t\tassertEquals(0.0001, problem.getMipGap(true), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testVarBranch() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.setVarBranch(1, LpSolve.BRANCH_AUTOMATIC);\r\n\t\tassertEquals(LpSolve.BRANCH_AUTOMATIC, problem.getVarBranch(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testVarWeights() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tassertEquals(1, problem.getVarPriority(1));\r\n\t\tassertEquals(2, problem.getVarPriority(2));\r\n\t\tdouble[] weights = { 2, 1 };\r\n\t\tproblem.setVarWeights(weights);\r\n\t\tassertEquals(2, problem.getVarPriority(1));\r\n\t\tassertEquals(1, problem.getVarPriority(2));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testBreakAtFirst() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertFalse(problem.isBreakAtFirst());\r\n\t\tproblem.setBreakAtFirst(true);\r\n\t\tassertTrue(problem.isBreakAtFirst());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testBreakAtValue() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(- problem.getInfinite(), problem.getBreakAtValue(), 1e-8);\r\n\t\tproblem.setBreakAtValue(-1.2E22);\r\n\t\tassertEquals(-1.2E22, problem.getBreakAtValue(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testScaling() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tint mode = (LpSolve.SCALE_EXTREME | LpSolve.SCALE_POWER2);\r\n\t\tproblem.setScaling(mode);\r\n\t\tassertEquals(mode, problem.getScaling());\r\n\t\tassertTrue(problem.isScalemode(mode));\r\n\t\tassertTrue(problem.isScaletype(LpSolve.SCALE_EXTREME));\r\n\t\tassertFalse(problem.isIntegerscaling());\r\n\t\tproblem.setScaling(mode | LpSolve.SCALE_INTEGERS);\r\n\t\tassertTrue(problem.isIntegerscaling());\r\n\t\tproblem.unscale();\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testImprove() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(LpSolve.IMPROVE_DUALFEAS | LpSolve.IMPROVE_THETAGAP, problem.getImprove());\r\n\t\tproblem.setImprove(LpSolve.IMPROVE_BBSIMPLEX );\r\n\t\tassertEquals(LpSolve.IMPROVE_BBSIMPLEX , problem.getImprove());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testPivoting() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals((LpSolve.PRICER_DEVEX | LpSolve.PRICE_ADAPTIVE), problem.getPivoting());  // default\r\n\t\tassertTrue(problem.isPivRule(LpSolve.PRICER_DEVEX));\t// default\r\n\t\tassertTrue(problem.isPivMode(LpSolve.PRICE_ADAPTIVE));\t// default\r\n\t\tint mask = (LpSolve.PRICER_STEEPESTEDGE | LpSolve.PRICE_PRIMALFALLBACK);\r\n\t\tproblem.setPivoting(mask);\r\n\t\tassertEquals(mask, problem.getPivoting());\r\n\t\tassertTrue(problem.isPivRule(LpSolve.PRICER_STEEPESTEDGE));\r\n\t\tassertFalse(problem.isPivRule(LpSolve.PRICER_DANTZIG));\r\n\t\tassertTrue(problem.isPivMode(LpSolve.PRICE_PRIMALFALLBACK));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testNegrange() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(-1000000, problem.getNegrange(), 1e-8); // default\r\n\t\tproblem.setNegrange(-1.234);\r\n\t\tassertEquals(-1.234, problem.getNegrange(), 1e-8);\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testBasis() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tint[] basis = new int[1+2];\r\n\t\tproblem.getBasis(basis, false);\r\n\r\n\t\tint[] newBasis = { 0, -2, -3 };\r\n\t\tproblem.setBasis(newBasis, false);\r\n\t\tproblem.getBasis(basis, false);\r\n\t\tassertEquals(-2, basis[1]);\r\n\t\tassertEquals(-3, basis[2]);\r\n\r\n\t\tproblem.defaultBasis();\r\n\t\tproblem.getBasis(basis, false);\r\n\t\tassertEquals(-1, basis[1]);\r\n\t\tassertEquals(-2, basis[2]);\r\n\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSensitivityRhs() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tproblem.strSetObjFn(\"1 1\");\r\n\t\tproblem.strAddConstraint(\"2 4\", LpSolve.GE, 10);\r\n\t\tproblem.setLowbo(1, 1);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tint size = problem.getNcolumns() + problem.getNrows();\r\n\t\tdouble[] duals = new double[size];\r\n\t\tdouble[] dualsfrom = new double[size];\r\n\t\tdouble[] dualstill = new double[size];\r\n\t\tproblem.getSensitivityRhs(duals, dualsfrom, dualstill);\r\n\t\tdouble[][] sens = problem.getPtrSensitivityRhs();\r\n\t\tassertEquals(3, sens.length);\r\n\t\tdouble[] ptrDuals = sens[0];\r\n\t\tdouble[] ptrDualsfrom = sens[1];\r\n\t\tdouble[] ptrDualstill = sens[2];\r\n\t\tassertEquals(size, ptrDuals.length);\r\n\t\tassertEquals(size, ptrDualsfrom.length);\r\n\t\tassertEquals(size, ptrDualstill.length);\r\n\t\tfor (int i = 0; i < size; i++) {\r\n\t\t\tassertEquals(duals[i], ptrDuals[i], 1e-8);\r\n\t\t\tassertEquals(dualsfrom[i], ptrDualsfrom[i], 1e-8);\r\n\t\t\tassertEquals(dualstill[i], ptrDualstill[i], 1e-8);\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetDualSolution() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tproblem.strSetObjFn(\"1 1\");\r\n\t\tproblem.strAddConstraint(\"2 4\", LpSolve.GE, 10);\r\n\t\tproblem.setLowbo(1, 1);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tint size = 1 + problem.getNcolumns() + problem.getNrows();\r\n\t\tdouble[] duals = new double[size];\r\n\t\tproblem.getDualSolution(duals);\r\n\t\tdouble[] ptrDuals = problem.getPtrDualSolution();\r\n\t\tassertEquals(size, ptrDuals.length);\r\n\t\tfor (int i = 0; i < size; i++) {\r\n\t\t\tassertEquals(duals[i], ptrDuals[i], 1e-8);\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSensitivityObj() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tproblem.strSetObjFn(\"1 1\");\r\n\t\tproblem.strAddConstraint(\"2 4\", LpSolve.GE, 10);\r\n\t\tproblem.setLowbo(1, 1);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tint size = problem.getNcolumns();\r\n\t\tdouble[] objfrom = new double[size];\r\n\t\tdouble[] objtill = new double[size];\r\n\t\tproblem.getSensitivityObj(objfrom, objtill);\r\n\t\tdouble[][] sens = problem.getPtrSensitivityObj();\r\n\t\tassertEquals(2, sens.length);\r\n\t\tdouble[] ptrObjfrom = sens[0];\r\n\t\tdouble[] ptrObjtill = sens[1];\r\n\t\tassertEquals(size, ptrObjfrom.length);\r\n\t\tassertEquals(size, ptrObjtill.length);\r\n\t\tassertEquals(0.5, objfrom[0], 1e-8);\r\n\t\tassertEquals(problem.getInfinite(), objtill[0], 1e-8);\r\n\t\tassertEquals(0.0, objfrom[1], 1e-8);\r\n\t\tassertEquals(2.0, objtill[1], 1e-8);\r\n\t\tfor (int i = 0; i < size; i++) {\r\n\t\t\tassertEquals(objfrom[i], ptrObjfrom[i], 1e-8);\r\n\t\t\tassertEquals(objtill[i], ptrObjtill[i], 1e-8);\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSensitivityObjex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 2);\r\n\t\tproblem.strSetObjFn(\"1 1\");\r\n\t\tproblem.strAddConstraint(\"2 4\", LpSolve.GE, 10);\r\n\t\tproblem.setLowbo(1, 1);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tint size = problem.getNcolumns();\r\n\t\tdouble[] objfrom = new double[size];\r\n\t\tdouble[] objtill = new double[size];\r\n\t\tdouble[] objfromvalue = new double[size];\r\n\t\tdouble[] objtillvalue = new double[size];\r\n\t\tproblem.getSensitivityObjex(objfrom, objtill, objfromvalue, objtillvalue);\r\n\t\tdouble[][] sens = problem.getPtrSensitivityObjex();\r\n\t\tassertEquals(4, sens.length);\r\n\t\tdouble[] ptrObjfrom = sens[0];\r\n\t\tdouble[] ptrObjtill = sens[1];\r\n\t\tdouble[] ptrObjfromvalue = sens[2];\r\n\t\tdouble[] ptrObjtillvalue = sens[3];\r\n\t\tassertEquals(size, ptrObjfrom.length);\r\n\t\tassertEquals(size, ptrObjtill.length);\r\n\t\tassertEquals(size, ptrObjfromvalue.length);\r\n\t\tassertEquals(size, ptrObjtillvalue.length);\r\n\t\tassertEquals(0.5, objfrom[0], 1e-8);\r\n\t\tassertEquals(problem.getInfinite(), objtill[0], 1e-8);\r\n\t\tassertEquals(0.0, objfrom[1], 1e-8);\r\n\t\tassertEquals(2.0, objtill[1], 1e-8);\r\n\t\tfor (int i = 0; i < size; i++) {\r\n\t\t\tassertEquals(objfrom[i], ptrObjfrom[i], 1e-8);\r\n\t\t\tassertEquals(objtill[i], ptrObjtill[i], 1e-8);\r\n\t\t\tassertEquals(objfromvalue[i], ptrObjfromvalue[i], 1e-8);\r\n\t\t\t/* assertEquals(objtillvalue[i], ptrObjtillvalue[i], 1e-8); */ /* Not used/filled at this time, so should not be tested */\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testIsConstrType() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tassertTrue(problem.isConstrType(1, LpSolve.LE));\r\n\t\tassertFalse(problem.isConstrType(1, LpSolve.EQ));\r\n\t\tassertFalse(problem.isConstrType(1, LpSolve.GE));\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tassertTrue(problem.isConstrType(2, LpSolve.GE));\r\n\t\tassertFalse(problem.isConstrType(2, LpSolve.LE));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSolutioncount() throws Exception {\r\n\t\t// not a real test but at least we make sure the\r\n\t\t// function exists and does not crash ..\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tassertEquals(0, problem.getSolutioncount());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSolutionlimit() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tproblem.setSolutionlimit(10);\r\n\t\tassertEquals(10, problem.getSolutionlimit());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetTotalIter() throws Exception {\r\n\t\t// not a real test but at least we make sure the\r\n\t\t// function exists and does not crash ..\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tassertEquals(0, problem.getTotalIter());\r\n\t\tassertEquals(0, problem.getTotalNodes());\r\n\t\tassertEquals(0, problem.getMaxLevel());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetSetBoundsTighter() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tassertFalse(problem.getBoundsTighter()); \t// default\r\n\t\tproblem.setBoundsTighter(true);\r\n\t\tassertTrue(problem.getBoundsTighter());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetLpIndex() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 1);\r\n\t\tassertEquals(1, problem.getLpIndex(1));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testIsFeasible() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(1, 1);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tdouble[] values = { 0.0, 1.0, 2.0 };\r\n\t\tassertTrue(problem.isFeasible(values, 0));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testTimeElapsed() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 1);\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tproblem.timeElapsed();\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetNameindexWithRows() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(2, 4);\r\n\t\tassertEquals(-1, problem.getNameindex(\"myrow1\", true));\r\n\t\tproblem.setRowName(1, \"myrow1\");\r\n\t\tassertEquals(1, problem.getNameindex(\"myrow1\", true));\r\n\t\tassertEquals(-1, problem.getNameindex(\"myrow2\", true));\r\n\t\tproblem.setRowName(2, \"myrow2\");\r\n\t\tassertEquals(2, problem.getNameindex(\"myrow2\", true));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testGetNameindexWithCols() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(2, 4);\r\n\t\tassertEquals(-1, problem.getNameindex(\"mycol1\", false));\r\n\t\tproblem.setColName(1, \"mycol1\");\r\n\t\tassertEquals(1, problem.getNameindex(\"mycol1\", false));\r\n\t\tassertEquals(-1, problem.getNameindex(\"mycol2\", false));\r\n\t\tproblem.setColName(3, \"mycol2\");\r\n\t\tassertEquals(3, problem.getNameindex(\"mycol2\", false));\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testReadNonexistentBasis() throws Exception {\r\n\t\tString filename = \"model.bas\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\ttry {\r\n\t\t\tproblem.readBasis(file.getAbsolutePath());\r\n\t\t\tfail(\"readBasis should throw an Exception on nonexistent file\");\r\n\t\t}\r\n\t\tcatch (LpSolveException e) {\r\n\t\t\t// OK\r\n                        System.out.println(\"readBasis failed as expected\");\r\n\t\t}\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\tpublic void testReadWriteBasis() throws Exception {\r\n\t\tString filename = \"model.bas\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tproblem.writeBasis(file.getAbsolutePath());\r\n\t\tassertTrue(file.exists());\r\n\r\n\t\tString info = problem.readBasis(file.getAbsolutePath());\r\n\t\tassertNotNull(info);\r\n\t\tassertTrue(info.length() > 0);\r\n\t\tproblem.deleteLp();\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testReadWriteParams() throws Exception {\r\n\t\tString filename = \"model.params\";\r\n\t\tFile file = new File(filename);\r\n\t\tif (file.exists()) file.delete();\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(250, problem.getMaxpivot());\r\n\t\tproblem.setMaxpivot(400);\r\n\t\tproblem.writeParams(file.getAbsolutePath(), \"\");\r\n\t\tassertTrue(file.exists());\r\n\t\tproblem.deleteLp();\r\n\r\n\t\tproblem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(250, problem.getMaxpivot());\r\n\t\tproblem.readParams(file.getAbsolutePath(), \"\");\r\n\t\tassertEquals(400, problem.getMaxpivot());\r\n\t\tproblem.deleteLp();\r\n\t\tif (file.exists()) file.delete();\r\n\t}\r\n\r\n\tpublic void testResetParams() throws Exception {\r\n\t\tLpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tassertEquals(250, problem.getMaxpivot());\r\n\t\tproblem.setMaxpivot(400);\r\n\t\tassertEquals(400, problem.getMaxpivot());\r\n\t\tproblem.resetParams();\r\n\t\tassertEquals(250, problem.getMaxpivot());\r\n\t\tproblem.deleteLp();\r\n\t}\r\n\r\n\t// TODO: write test case for setBasisvar after docs have been added\r\n\r\n\t// TODO: write test case for getConstrValue\r\n\r\n\t// TODO: write test case for put_bb_branchfunc\r\n\r\n\t// TODO: write test case for put_bb_nodefunc\r\n\r\n\tpublic void testAbortListener() throws Exception {\r\n\t\tfinal LpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tclass MyListener implements AbortListener {\r\n\t\t\tpublic int numCalls = 0;\r\n\t\t\tpublic boolean abortfunc(LpSolve prob, Object handle) {\r\n\t\t\t\tnumCalls++;\r\n\t\t\t\tassertEquals(problem, prob);\r\n\t\t\t\tassertEquals(new Integer(123), handle);\r\n\t\t\t\treturn false;\r\n\t\t\t}\r\n\t\t};\r\n\t\tMyListener listener = new MyListener();\r\n\t\tproblem.putAbortfunc(listener, new Integer(123));\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tproblem.deleteLp();\r\n\t\tassertTrue(listener.numCalls > 0);\r\n\t}\r\n\r\n\tpublic void testMsgListener() throws Exception {\r\n\t\tfinal LpSolve problem = LpSolve.makeLp(0, 4);\r\n\t\tclass MyListener implements MsgListener {\r\n\t\t\tpublic int  numCalls = 0;\r\n\t\t\tpublic void msgfunc(LpSolve prob, Object handle, int code) throws LpSolveException {\r\n\t\t\t\tnumCalls++;\r\n\t\t\t\tassertEquals(problem, prob);\r\n\t\t\t\tassertEquals(new Integer(123), handle);\r\n\t\t\t\tproblem.getWorkingObjective();\r\n\t\t\t}\r\n\t\t};\r\n\t\tMyListener listener = new MyListener();\r\n\t\tint mask = LpSolve.MSG_LPFEASIBLE | LpSolve.MSG_LPOPTIMAL;\r\n\t\tproblem.putMsgfunc(listener, new Integer(123), mask);\r\n\t\tproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4);\r\n\t\tproblem.strAddConstraint(\"0 4 3 1\", LpSolve.GE, 3);\r\n\t\tproblem.strSetObjFn(\"2 3 -2 3\");\r\n\t\tproblem.setVerbose(LpSolve.IMPORTANT);\r\n\t\tproblem.solve();\r\n\t\tproblem.deleteLp();\r\n\t\tassertTrue(listener.numCalls > 0);\r\n\t}\r\n\r\n\tpublic void testLogListener() throws Exception {\r\n\t\tfinal LpSolve problem = LpSolve.makeLp(0, 0);\r\n\t\tclass MyListener implements LogListener {\r\n\t\t\tpublic int  numCalls = 0;\r\n\t\t\tpublic void logfunc(LpSolve prob, Object handle, String buf) {\r\n\t\t\t\tnumCalls++;\r\n\t\t\t\tassertEquals(problem, prob);\r\n\t\t\t\tassertEquals(new Integer(123), handle);\r\n\t\t\t\tassertNotNull(buf);\r\n\t\t\t}\r\n\t\t};\r\n\t\tMyListener listener = new MyListener();\r\n\t\tproblem.putLogfunc(listener, new Integer(123));\r\n\t\ttry {\r\n\t\t\tproblem.delColumn(1);\t// should generate an error (see docs)\r\n\t\t}\r\n\t\tcatch (LpSolveException e) {\r\n                        // OK\r\n                        System.out.println(\"delColumn failed as expected\");\r\n                }\r\n\t\tproblem.deleteLp();\r\n\t\tassertTrue(listener.numCalls > 0);\r\n\t}\r\n\r\n}"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/build",
    "content": ":\n\nmkdir lpsolve >/dev/null 2>&1\ncp ../src/java/lpsolve/*.class lpsolve\njar cvf ../lib/lpsolve55j.jar *.class lpsolve\n\njavac -classpath ../lib/lpsolve55j.jar Demo.java\njar cvf Demo.jar Demo.class\n\njavac -classpath ../lib/lpsolve55j.jar:../lib/junit.jar LpSolveTest.java\njar cvf unittests.jar LpSolveTest.class 'LpSolveTest$1MyListener.class' 'LpSolveTest$2MyListener.class' 'LpSolveTest$3MyListener.class'\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/demo.py",
    "content": "# ###########################################################################\n# \n# Demo program that shows how to call lp_solve methods from a Python program\n# via the Java wrapper. See README.html on how to run this programm with Jython.\n#\n# ###########################################################################\n\nfrom lpsolve import *\n\n#\n# Define some callback methods\n#\nclass MyAbortListener(AbortListener):\n    def abortfunc(self, problem, handle):\n        # print \"In abortfunc, handle = \", handle\n        return LpSolve.FALSE\n\nclass MyLogListener(LogListener):\n    def logfunc(self, problem, handle, buf):\n        print \"logfunc:\", buf\n\n#\n# some utility methods\n#\ndef print_line():\n\tprint '-----------------------------------------------'\n\t\ndef msg(text):\n    print_line()\n    print \"\\n***\", text, \"***\\n\"\n    raw_input(\"Press RETURN to continue\")\n\n\n#\n# here we start with the demo code\n#\nv = LpSolve.lpSolveVersion()\nprint 'lp_solve %d.%d.%d.%d demo (Python version)' % (v.majorversion, v.minorversion, v.release, v.build)\n\t\nmsg(\"We start by creating a new problem with 4 variables and 0 constraints\")\nproblem = LpSolve.makeLp(0, 4)\nproblem.printLp()\n\nmsg(\"let's first demonstrate the logfunc callback feature \")\nproblem.putLogfunc(MyLogListener(), 1)\nproblem.solve()  # just to see that a message is send via the logfunc routine\nproblem.putLogfunc(None, 0) # ok, that is enough, no more callback\n\nmsg(\"Now we add a constraint with the string version of add_constraint\")\nproblem.strAddConstraint(\"3 2 2 1\", LpSolve.LE, 4)\nproblem.printLp()\n\nmsg(\"Add another constraint with the normal version\")\nproblem.addConstraint([0, 0, 4, 3, 1], LpSolve.GE, 3)\nproblem.printLp()\n\n# NOTE: the Jython docs say that Java arrays must be passed to methods\n# as PyArray objects. This would look like this:\n#\n# from jarray import array\n# problem.addConstraint(array([0, 0, 4, 3, 1]), \"d\"), LpSolve.GE, 3)\n#\n# But it seems to work also with normal Python sequences !?\n\nmsg(\"Set the objective function\")\nproblem.strSetObjFn(\"2 3 -2 3\")\nproblem.printLp()\n\nmsg(\"Now solve the problem\")\nrc = problem.solve();\n\nif rc != 0:\n    print \"ERROR\"; exit()\n   \nmsg(\"The value is 0, this means we found an optimal solution; display solution\")\nproblem.printObjective()\nproblem.printSolution(1)\nproblem.printConstraints(1)\n\nmsg(\"Print the dual variables of the solution\")\nproblem.printDuals()\n\nmsg(\"Change a single element in the matrix and set to maximize\")\nproblem.setMat(2, 1, 0.5)\nproblem.setMaxim()\nproblem.printLp()\n\nmsg(\"Now solve the problem\")\nproblem.solve();\nproblem.printObjective()\nproblem.printSolution(1)\nproblem.printConstraints(1)\nproblem.printDuals()\n\nmsg(\"Change the value of a rhs element\")\nproblem.setRh(1, 7.45);\nproblem.printLp()\n\nproblem.solve();\nproblem.printObjective()\nproblem.printSolution(1)\nproblem.printConstraints(1)\n\nmsg(\"We change column 4 to the integer type\")\nproblem.setInt(4, LpSolve.TRUE)\nproblem.printLp()\n\nmsg(\"We set branch & bound debugging on and solve\")\nproblem.setDebug(LpSolve.TRUE)\nproblem.solve();\nproblem.printObjective()\nproblem.printSolution(1)\nproblem.printConstraints(1)\n\nmsg(\"We can set bounds on the variables\")\nproblem.setLowbo(2, 2)\nproblem.setUpbo(4, 5.3)\nproblem.printLp()\n\nproblem.solve();\nproblem.printObjective()\nproblem.printSolution(1)\nproblem.printConstraints(1)\n\nmsg(\"Now remove a constraint \")\nproblem.delConstraint(1);\nproblem.printLp()\n\nmsg(\"Add an equality constraint\")\nproblem.strAddConstraint(\"1 2 1 4\", LpSolve.EQ, 8)\nproblem.printLp()\n\nmsg(\"Add a column\")\nproblem.strAddColumn(\"3 2 2\")\nproblem.printLp()\n\nmsg(\"Delete a column\")\nproblem.delColumn(3)\nproblem.printLp()\n\nmsg(\"Remove interger attributefrom  column 3\")\nproblem.setInt(3, LpSolve.FALSE) # done in scaling stuff\nproblem.printLp()\n\n# Scaling stuff from C demo program left out because in versions 4\n# and 5 of lp_solve scaling is transparent and would not produce any \n# visual change in the output\n\nmsg(\"Return a single matrix element with getMat()\")\nprint \"problem.getMat(2, 3) = \", problem.getMat(2, 3)\nprint \"problem.getMat(1, 1) = \", problem.getMat(1, 1)\n\nmsg(\"Now turn B&B debugging off and simplex tracing on and solve again\")\nproblem.setDebug(LpSolve.FALSE)\nproblem.setTrace(LpSolve.TRUE)\nproblem.solve();\n\nmsg(\"Where possible, lp_solve will start at the last found basis.\\n\"\n  \"We reset the problem to the initial basis and solve again\");\nproblem.resetBasis()\nproblem.solve();\n\nmsg(\"It is possible to give variables and constraints names\")\nproblem.setRowName(1, \"speed\")\nproblem.setColName(2, \"money\")\nproblem.printLp()\n\nmsg(\"If a column or constraint is deleted, the names shift place also\")\nproblem.delColumn(1);\nproblem.printLp()\n\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/run_demo",
    "content": ":\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\ncc /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\n# run the Demo.class file\njava -cp .:../lib/lpsolve55j.jar -Djava.library.path=../lib/$PLATFORM Demo\n\n# run the Demo.jar file\njava -cp ./Demo.jar:../lib/lpsolve55j.jar -Djava.library.path=../lib/$PLATFORM Demo # -Djava.library.path=/usr/local/lib\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/run_demo.bat",
    "content": "rem run the Demo.class file\njava -cp .;..\\lib\\lpsolve55j.jar Demo\n\nrem run the Demo.jar file\njava -cp .\\Demo.jar;..\\lib\\lpsolve55j.jar Demo"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/run_unittests",
    "content": ":\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\ncc /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nLD_LIBRARY_PATH=$LD_LIBRARY_PATH:../../../xli/xli_CPLEX/bin/$PLATFORM:../../../xli/xli_LINDO/bin/$PLATFORM:../../../bfp/bfp_LUSOL/bin/$PLATFORM\nexport LD_LIBRARY_PATH\n\njava -cp ./unittests.jar:../lib/lpsolve55j.jar:../lib/junit.jar -Djava.library.path=../lib/$PLATFORM LpSolveTest\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo/run_unittests.bat",
    "content": "@echo off\n\nset c=cl\n\nREM determine platform (win32/win64)\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\n%c% /nologo platform.c /Feplatform.exe\ndel platform.c\nplatform.exe >platform.bat\ndel platform.exe\ncall platform.bat\ndel platform.bat\n\nset patho=%path%\nset path=..\\..\\..\\xli\\xli_CPLEX\\bin\\%PLATFORM%;..\\..\\..\\xli\\xli_LINDO\\bin\\%PLATFORM%;..\\..\\..\\bfp\\bfp_LUSOL\\bin\\%PLATFORM%;%path%\n\njava -cp .\\unittests.jar;..\\lib\\lpsolve55j.jar;..\\lib\\junit.jar LpSolveTest\n\nset path=%patho%"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo2/Build.bat",
    "content": "javac -classpath ..\\lib\\lpsolve55j.jar Demo.java\r\nrem jar -c -f Demo.jar Demo.class\r\njar cvf Demo.jar Demo.class\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo2/Demo.java",
    "content": "/* demo.java */\r\n\r\nimport java.io.BufferedReader;\r\nimport java.io.IOException;\r\nimport java.io.InputStreamReader;\r\n\r\nimport lpsolve.*;\r\n\r\npublic class Demo {\r\n\r\n\tpublic Demo() {\r\n\t}\r\n\r\n\tpublic int execute() throws LpSolveException {\r\n          LpSolve lp;\r\n          int Ncol, j, ret = 0;\r\n\r\n          /* We will build the model row by row\r\n             So we start with creating a model with 0 rows and 2 columns */\r\n          Ncol = 2; /* there are two variables in the model */\r\n\r\n          /* create space large enough for one row */\r\n          int[] colno = new int[Ncol];\r\n          double[] row = new double[Ncol];\r\n\r\n          lp = LpSolve.makeLp(0, Ncol);\r\n          if(lp.getLp() == 0)\r\n            ret = 1; /* couldn't construct a new model... */\r\n\r\n          if(ret == 0) {\r\n            /* let us name our variables. Not required, but can be usefull for debugging */\r\n            lp.setColName(1, \"x\");\r\n            lp.setColName(2, \"y\");\r\n\r\n            lp.setAddRowmode(true);  /* makes building the model faster if it is done rows by row */\r\n\r\n            /* construct first row (120 x + 210 y <= 15000) */\r\n            j = 0;\r\n\r\n            colno[j] = 1; /* first column */\r\n            row[j++] = 120;\r\n\r\n            colno[j] = 2; /* second column */\r\n            row[j++] = 210;\r\n\r\n            /* add the row to lp_solve */\r\n            lp.addConstraintex(j, row, colno, LpSolve.LE, 15000);\r\n          }\r\n\r\n          if(ret == 0) {\r\n            /* construct second row (110 x + 30 y <= 4000) */\r\n            j = 0;\r\n\r\n            colno[j] = 1; /* first column */\r\n            row[j++] = 110;\r\n\r\n            colno[j] = 2; /* second column */\r\n            row[j++] = 30;\r\n\r\n            /* add the row to lp_solve */\r\n            lp.addConstraintex(j, row, colno, LpSolve.LE, 4000);\r\n          }\r\n\r\n          if(ret == 0) {\r\n            /* construct third row (x + y <= 75) */\r\n            j = 0;\r\n\r\n            colno[j] = 1; /* first column */\r\n            row[j++] = 1;\r\n\r\n            colno[j] = 2; /* second column */\r\n            row[j++] = 1;\r\n\r\n            /* add the row to lp_solve */\r\n            lp.addConstraintex(j, row, colno, LpSolve.LE, 75);\r\n          }\r\n\r\n          if(ret == 0) {\r\n            lp.setAddRowmode(false); /* rowmode should be turned off again when done building the model */\r\n\r\n            /* set the objective function (143 x + 60 y) */\r\n            j = 0;\r\n\r\n            colno[j] = 1; /* first column */\r\n            row[j++] = 143;\r\n\r\n            colno[j] = 2; /* second column */\r\n            row[j++] = 60;\r\n\r\n            /* set the objective in lp_solve */\r\n            lp.setObjFnex(j, row, colno);\r\n          }\r\n\r\n          if(ret == 0) {\r\n            /* set the object direction to maximize */\r\n            lp.setMaxim();\r\n\r\n            /* just out of curioucity, now generate the model in lp format in file model.lp */\r\n            lp.writeLp(\"model.lp\");\r\n\r\n            /* I only want to see importand messages on screen while solving */\r\n            lp.setVerbose(LpSolve.IMPORTANT);\r\n\r\n            /* Now let lp_solve calculate a solution */\r\n            ret = lp.solve();\r\n            if(ret == LpSolve.OPTIMAL)\r\n              ret = 0;\r\n            else\r\n              ret = 5;\r\n          }\r\n\r\n          if(ret == 0) {\r\n            /* a solution is calculated, now lets get some results */\r\n\r\n            /* objective value */\r\n            System.out.println(\"Objective value: \" + lp.getObjective());\r\n\r\n            /* variable values */\r\n            lp.getVariables(row);\r\n            for(j = 0; j < Ncol; j++)\r\n              System.out.println(lp.getColName(j + 1) + \": \" + row[j]);\r\n\r\n            /* we are done now */\r\n          }\r\n\r\n          /* clean up such that all used memory by lp_solve is freeed */\r\n          if(lp.getLp() != 0)\r\n            lp.deleteLp();\r\n\r\n          return(ret);\r\n        }\r\n\r\n\tpublic static void main(String[] args) {\r\n\t\ttry {\r\n\t\t\tnew Demo().execute();\r\n\t\t}\r\n\t\tcatch (LpSolveException e) {\r\n\t\t\te.printStackTrace();\r\n\t\t}\r\n\t}\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/demo2/run_demo.bat",
    "content": "rem run the Demo.class file\njava -cp .;..\\lib\\lpsolve55j.jar Demo\n\nrem run the Demo.jar file\njava -cp .\\Demo.jar;..\\lib\\lpsolve55j.jar Demo"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/allclasses-frame.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nAll Classes (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\">\r\n<FONT size=\"+1\" CLASS=\"FrameHeadingFont\">\r\n<B>All Classes</B></FONT>\r\n<BR>\r\n\n<TABLE BORDER=\"0\" WIDTH=\"100%\" SUMMARY=\"\">\r\n<TR>\r\n<TD NOWRAP><FONT CLASS=\"FrameItemFont\"><A HREF=\"lpsolve/AbortListener.html\" title=\"interface in lpsolve\" target=\"classFrame\"><I>AbortListener</I></A>\r\n<BR>\r\n<A HREF=\"lpsolve/BbListener.html\" title=\"interface in lpsolve\" target=\"classFrame\"><I>BbListener</I></A>\r\n<BR>\r\n<A HREF=\"lpsolve/LogListener.html\" title=\"interface in lpsolve\" target=\"classFrame\"><I>LogListener</I></A>\r\n<BR>\r\n<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\" target=\"classFrame\">LpSolve</A>\r\n<BR>\r\n<A HREF=\"lpsolve/LpSolveException.html\" title=\"class in lpsolve\" target=\"classFrame\">LpSolveException</A>\r\n<BR>\r\n<A HREF=\"lpsolve/MsgListener.html\" title=\"interface in lpsolve\" target=\"classFrame\"><I>MsgListener</I></A>\r\n<BR>\r\n<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\" target=\"classFrame\">VersionInfo</A>\r\n<BR>\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/allclasses-noframe.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nAll Classes (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\">\r\n<FONT size=\"+1\" CLASS=\"FrameHeadingFont\">\r\n<B>All Classes</B></FONT>\r\n<BR>\r\n\n<TABLE BORDER=\"0\" WIDTH=\"100%\" SUMMARY=\"\">\r\n<TR>\r\n<TD NOWRAP><FONT CLASS=\"FrameItemFont\"><A HREF=\"lpsolve/AbortListener.html\" title=\"interface in lpsolve\"><I>AbortListener</I></A>\r\n<BR>\r\n<A HREF=\"lpsolve/BbListener.html\" title=\"interface in lpsolve\"><I>BbListener</I></A>\r\n<BR>\r\n<A HREF=\"lpsolve/LogListener.html\" title=\"interface in lpsolve\"><I>LogListener</I></A>\r\n<BR>\r\n<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<BR>\r\n<A HREF=\"lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A>\r\n<BR>\r\n<A HREF=\"lpsolve/MsgListener.html\" title=\"interface in lpsolve\"><I>MsgListener</I></A>\r\n<BR>\r\n<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A>\r\n<BR>\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/constant-values.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:56 CEST 2005 -->\r\n<TITLE>\r\nConstant Field Values (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"Constant Field Values (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\r\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\r\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\r\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\r\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"constant-values.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\r\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\r\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<CENTER>\r\n<H1>\r\nConstant Field Values</H1>\r\n</CENTER>\r\n<HR SIZE=\"4\" NOSHADE>\r\n<B>Contents</B><UL>\r\n<LI><A HREF=\"#lpsolve\">lpsolve.*</A>\r\n</UL>\r\n\r\n<A NAME=\"lpsolve\"><!-- --></A>\r\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD ALIGN=\"left\"><FONT SIZE=\"+2\">\r\n<B>lpsolve.*</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<P>\r\n\r\n<TABLE BORDER=\"0\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#EEEEFF\" CLASS=\"TableSubHeadingColor\">\r\n<TD COLSPAN=3><B>lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A></B></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_BOUNDFLIP\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_BOUNDFLIP\">ANTIDEGEN_BOUNDFLIP</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>512</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_COLUMNCHECK\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_COLUMNCHECK\">ANTIDEGEN_COLUMNCHECK</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_DURINGBB\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_DURINGBB\">ANTIDEGEN_DURINGBB</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>128</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_DYNAMIC\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_DYNAMIC\">ANTIDEGEN_DYNAMIC</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>64</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_FIXEDVARS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_FIXEDVARS\">ANTIDEGEN_FIXEDVARS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_INFEASIBLE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_INFEASIBLE\">ANTIDEGEN_INFEASIBLE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>32</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_LOSTFEAS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_LOSTFEAS\">ANTIDEGEN_LOSTFEAS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>16</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_NONE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_NONE\">ANTIDEGEN_NONE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_NUMFAILURE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_NUMFAILURE\">ANTIDEGEN_NUMFAILURE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_RHSPERTURB\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_RHSPERTURB\">ANTIDEGEN_RHSPERTURB</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>256</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.ANTIDEGEN_STALLING\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_STALLING\">ANTIDEGEN_STALLING</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.AUTOMATIC\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#AUTOMATIC\">AUTOMATIC</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.BRANCH_AUTOMATIC\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#BRANCH_AUTOMATIC\">BRANCH_AUTOMATIC</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.BRANCH_DEFAULT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#BRANCH_DEFAULT\">BRANCH_DEFAULT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>3</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.BRANCH_CEILING\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#BRANCH_CEILING\">BRANCH_CEILING</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.BRANCH_FLOOR\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#BRANCH_FLOOR\">BRANCH_FLOOR</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.CRASH_MOSTFEASIBLE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#CRASH_MOSTFEASIBLE\">CRASH_MOSTFEASIBLE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.CRASH_NOTHING\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#CRASH_NOTHING\">CRASH_NOTHING</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.CRITICAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#CRITICAL\">CRITICAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.DATAIGNORED\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#DATAIGNORED\">DATAIGNORED</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>-4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.DEGENERATE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#DEGENERATE\">DEGENERATE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.DETAILED\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#DETAILED\">DETAILED</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>5</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.DYNAMIC\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#DYNAMIC\">DYNAMIC</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.EQ\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#EQ\">EQ</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>3</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.FALSE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#FALSE\">FALSE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.FEASFOUND\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#FEASFOUND\">FEASFOUND</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>12</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.FR\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#FR\">FR</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.FULL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#FULL\">FULL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>6</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVED\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVED\">PRESOLVED</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>9</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.GE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#GE\">GE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.IMPORTANT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#IMPORTANT\">IMPORTANT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>3</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.IMPROVE_BBSIMPLEX\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#IMPROVE_BBSIMPLEX\">IMPROVE_BBSIMPLEX</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.IMPROVE_DUALFEAS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#IMPROVE_DUALFEAS\">IMPROVE_DUALFEAS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.IMPROVE_NONE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#IMPROVE_NONE\">IMPROVE_NONE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.IMPROVE_SOLUTION\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#IMPROVE_SOLUTION\">IMPROVE_SOLUTION</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.IMPROVE_THETAGAP\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#IMPROVE_THETAGAP\">IMPROVE_THETAGAP</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.INFEASIBLE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#INFEASIBLE\">INFEASIBLE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.LE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#LE\">LE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_INITPSEUDOCOST\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_INITPSEUDOCOST\">MSG_INITPSEUDOCOST</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8192</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_INVERT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_INVERT\">MSG_INVERT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_ITERATION\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_ITERATION\">MSG_ITERATION</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_LPBETTER\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_LPBETTER\">MSG_LPBETTER</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>64</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_LPEQUAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_LPEQUAL\">MSG_LPEQUAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>32</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_LPFEASIBLE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_LPFEASIBLE\">MSG_LPFEASIBLE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_LPOPTIMAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_LPOPTIMAL\">MSG_LPOPTIMAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>16</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_MILPBETTER\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_MILPBETTER\">MSG_MILPBETTER</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>512</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_MILPEQUAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_MILPEQUAL\">MSG_MILPEQUAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>256</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_MILPFEASIBLE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_MILPFEASIBLE\">MSG_MILPFEASIBLE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>128</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_MILPOPTIMAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_MILPOPTIMAL\">MSG_MILPOPTIMAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2048</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_MILPSTRATEGY\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_MILPSTRATEGY\">MSG_MILPSTRATEGY</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1024</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_NONE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_NONE\">MSG_NONE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_PERFORMANCE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_PERFORMANCE\">MSG_PERFORMANCE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4096</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.MSG_PRESOLVE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#MSG_PRESOLVE\">MSG_PRESOLVE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NEUTRAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NEUTRAL\">NEUTRAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NOBFP\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NOBFP\">NOBFP</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>-3</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_AUTOORDER\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_AUTOORDER\">NODE_AUTOORDER</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8192</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_BRANCHREVERSEMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_BRANCHREVERSEMODE\">NODE_BRANCHREVERSEMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>16</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_BREADTHFIRSTMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_BREADTHFIRSTMODE\">NODE_BREADTHFIRSTMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4096</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_DEPTHFIRSTMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_DEPTHFIRSTMODE\">NODE_DEPTHFIRSTMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>128</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_DYNAMICMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_DYNAMICMODE\">NODE_DYNAMICMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1024</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_FIRSTSELECT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_FIRSTSELECT\">NODE_FIRSTSELECT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_FRACTIONSELECT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_FRACTIONSELECT\">NODE_FRACTIONSELECT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>3</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_GAPSELECT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_GAPSELECT\">NODE_GAPSELECT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_GREEDYMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_GREEDYMODE\">NODE_GREEDYMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>32</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_PSEUDOCOSTMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_PSEUDOCOSTMODE\">NODE_PSEUDOCOSTMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>64</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_PSEUDOCOSTSELECT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_PSEUDOCOSTSELECT\">NODE_PSEUDOCOSTSELECT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_PSEUDONONINTSELECT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_PSEUDONONINTSELECT\">NODE_PSEUDONONINTSELECT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>5</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_PSEUDORATIOSELECT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_PSEUDORATIOSELECT\">NODE_PSEUDORATIOSELECT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>6</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_RANDOMIZEMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_RANDOMIZEMODE\">NODE_RANDOMIZEMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>256</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_RANGESELECT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_RANGESELECT\">NODE_RANGESELECT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_RCOSTFIXING\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_RCOSTFIXING\">NODE_RCOSTFIXING</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>16384</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_RESTARTMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_RESTARTMODE\">NODE_RESTARTMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2048</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_STRONGINIT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_STRONGINIT\">NODE_STRONGINIT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>32768</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_USERSELECT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_USERSELECT\">NODE_USERSELECT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>7</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NODE_WEIGHTREVERSEMODE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NODE_WEIGHTREVERSEMODE\">NODE_WEIGHTREVERSEMODE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NOFEASFOUND\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NOFEASFOUND\">NOFEASFOUND</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>13</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NOMEMORY\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NOMEMORY\">NOMEMORY</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>-2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NORMAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NORMAL\">NORMAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NOTRUN\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NOTRUN\">NOTRUN</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>-1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.NUMFAILURE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#NUMFAILURE\">NUMFAILURE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>5</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.OF\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#OF\">OF</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.OPTIMAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#OPTIMAL\">OPTIMAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_BOUNDS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_BOUNDS\">PRESOLVE_BOUNDS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>262144</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_COLDOMINATE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_COLDOMINATE\">PRESOLVE_COLDOMINATE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>16384</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_COLFIXDUAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_COLFIXDUAL\">PRESOLVE_COLFIXDUAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>131072</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_COLS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_COLS\">PRESOLVE_COLS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_DUALS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_DUALS\">PRESOLVE_DUALS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>524288</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_ELIMEQ2\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_ELIMEQ2\">PRESOLVE_ELIMEQ2</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>256</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_IMPLIEDFREE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_IMPLIEDFREE\">PRESOLVE_IMPLIEDFREE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>512</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_IMPLIEDSLK\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_IMPLIEDSLK\">PRESOLVE_IMPLIEDSLK</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>65536</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_KNAPSACK\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_KNAPSACK\">PRESOLVE_KNAPSACK</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>128</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_LINDEP\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_LINDEP\">PRESOLVE_LINDEP</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_MERGEROWS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_MERGEROWS\">PRESOLVE_MERGEROWS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>32768</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_NONE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_NONE\">PRESOLVE_NONE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_PROBEFIX\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_PROBEFIX\">PRESOLVE_PROBEFIX</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2048</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_PROBEREDUCE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_PROBEREDUCE\">PRESOLVE_PROBEREDUCE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4096</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_REDUCEGCD\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_REDUCEGCD\">PRESOLVE_REDUCEGCD</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1024</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_REDUCEMIP\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_REDUCEMIP\">PRESOLVE_REDUCEMIP</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>64</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_ROWDOMINATE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_ROWDOMINATE\">PRESOLVE_ROWDOMINATE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8192</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_ROWS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_ROWS\">PRESOLVE_ROWS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_SENSDUALS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_SENSDUALS\">PRESOLVE_SENSDUALS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1048576</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRESOLVE_SOS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_SOS\">PRESOLVE_SOS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>32</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_ADAPTIVE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_ADAPTIVE\">PRICE_ADAPTIVE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>32</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_AUTOPARTIAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_AUTOPARTIAL\">PRICE_AUTOPARTIAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>512</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_HARRISTWOPASS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_HARRISTWOPASS\">PRICE_HARRISTWOPASS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4096</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_HYBRID\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_HYBRID\">PRICE_HYBRID</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>64</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_LOOPALTERNATE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_LOOPALTERNATE\">PRICE_LOOPALTERNATE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2048</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_LOOPLEFT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_LOOPLEFT\">PRICE_LOOPLEFT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1024</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_METHODDEFAULT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_METHODDEFAULT\">PRICE_METHODDEFAULT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_MULTIPLE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_MULTIPLE\">PRICE_MULTIPLE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_PARTIAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_PARTIAL\">PRICE_PARTIAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>16</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_PRIMALFALLBACK\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_PRIMALFALLBACK\">PRICE_PRIMALFALLBACK</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_RANDOMIZE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_RANDOMIZE\">PRICE_RANDOMIZE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>128</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICE_TRUENORMINIT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICE_TRUENORMINIT\">PRICE_TRUENORMINIT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>16384</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICER_DANTZIG\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICER_DANTZIG\">PRICER_DANTZIG</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICER_DEVEX\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICER_DEVEX\">PRICER_DEVEX</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICER_FIRSTINDEX\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICER_FIRSTINDEX\">PRICER_FIRSTINDEX</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PRICER_STEEPESTEDGE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PRICER_STEEPESTEDGE\">PRICER_STEEPESTEDGE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>3</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PROCBREAK\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PROCBREAK\">PROCBREAK</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>11</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.PROCFAIL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#PROCFAIL\">PROCFAIL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>10</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.RUNNING\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#RUNNING\">RUNNING</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_COLSONLY\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_COLSONLY\">SCALE_COLSONLY</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1024</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_CURTISREID\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_CURTISREID\">SCALE_CURTISREID</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>7</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_DYNUPDATE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_DYNUPDATE\">SCALE_DYNUPDATE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>256</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_EQUILIBRATE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_EQUILIBRATE\">SCALE_EQUILIBRATE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>64</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_EXTREME\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_EXTREME\">SCALE_EXTREME</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_GEOMETRIC\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_GEOMETRIC\">SCALE_GEOMETRIC</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>4</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_INTEGERS\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_INTEGERS\">SCALE_INTEGERS</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>128</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_LINEAR\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_LINEAR\">SCALE_LINEAR</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_LOGARITHMIC\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_LOGARITHMIC\">SCALE_LOGARITHMIC</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>16</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_MEAN\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_MEAN\">SCALE_MEAN</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>3</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_NONE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_NONE\">SCALE_NONE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>0</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_POWER2\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_POWER2\">SCALE_POWER2</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>32</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_QUADRATIC\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_QUADRATIC\">SCALE_QUADRATIC</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>8</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_RANGE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_RANGE\">SCALE_RANGE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_ROWSONLY\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_ROWSONLY\">SCALE_ROWSONLY</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>512</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SCALE_USERWEIGHT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SCALE_USERWEIGHT\">SCALE_USERWEIGHT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>31</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SEVERE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SEVERE\">SEVERE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>2</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SIMPLEX_DEFAULT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_DEFAULT\">SIMPLEX_DEFAULT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>6</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SIMPLEX_DUAL_DUAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_DUAL_DUAL\">SIMPLEX_DUAL_DUAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>10</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SIMPLEX_DUAL_PRIMAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_DUAL_PRIMAL\">SIMPLEX_DUAL_PRIMAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>6</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SIMPLEX_PRIMAL_DUAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_PRIMAL_DUAL\">SIMPLEX_PRIMAL_DUAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>9</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SIMPLEX_PRIMAL_PRIMAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_PRIMAL_PRIMAL\">SIMPLEX_PRIMAL_PRIMAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>5</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.SUBOPTIMAL\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#SUBOPTIMAL\">SUBOPTIMAL</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.TIMEOUT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#TIMEOUT\">TIMEOUT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>7</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.TRUE\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#TRUE\">TRUE</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>1</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.UNBOUNDED\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#UNBOUNDED\">UNBOUNDED</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>3</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.UNKNOWNERROR\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#UNKNOWNERROR\">UNKNOWNERROR</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>-5</CODE></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<A NAME=\"lpsolve.LpSolve.USERABORT\"><!-- --></A><TD ALIGN=\"right\"><FONT SIZE=\"-1\">\r\n<CODE>public&nbsp;static&nbsp;final&nbsp;int</CODE></FONT></TD>\r\n<TD ALIGN=\"left\"><CODE><A HREF=\"lpsolve/LpSolve.html#USERABORT\">USERABORT</A></CODE></TD>\r\n<TD ALIGN=\"right\"><CODE>6</CODE></TD>\r\n</TR>\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<P>\r\n\r\n<P>\r\n<HR>\r\n\r\n\r\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\r\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\r\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\r\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"constant-values.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\r\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\r\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/deprecated-list.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nDeprecated List (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"Deprecated List (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Deprecated</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"deprecated-list.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<CENTER>\r\n<H2>\r\n<B>Deprecated API</B></H2>\r\n</CENTER>\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Deprecated</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"deprecated-list.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/help-doc.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nAPI Help (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"API Help (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Help</B></FONT>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"help-doc.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<CENTER>\r\n<H1>\r\nHow This API Document Is Organized</H1>\r\n</CENTER>\r\nThis API (Application Programming Interface) document has pages corresponding to the items in the navigation bar, described as follows.<H3>\r\nPackage</H3>\r\n<BLOCKQUOTE>\r\n\r\n<P>\r\nEach package has a page that contains a list of its classes and interfaces, with a summary for each. This page can contain four categories:<UL>\r\n<LI>Interfaces (italic)<LI>Classes<LI>Exceptions<LI>Errors</UL>\r\n</BLOCKQUOTE>\r\n<H3>\r\nClass/Interface</H3>\r\n<BLOCKQUOTE>\r\n\r\n<P>\r\nEach class, interface, nested class and nested interface has its own separate page. Each of these pages has three sections consisting of a class/interface description, summary tables, and detailed member descriptions:<UL>\r\n<LI>Class inheritance diagram<LI>Direct Subclasses<LI>All Known Subinterfaces<LI>All Known Implementing Classes<LI>Class/interface declaration<LI>Class/interface description\r\n<P>\r\n<LI>Nested Class Summary<LI>Field Summary<LI>Constructor Summary<LI>Method Summary\r\n<P>\r\n<LI>Field Detail<LI>Constructor Detail<LI>Method Detail</UL>\r\nEach summary entry contains the first sentence from the detailed description for that item. The summary entries are alphabetical, while the detailed descriptions are in the order they appear in the source code. This preserves the logical groupings established by the programmer.</BLOCKQUOTE>\r\n<H3>\r\nTree (Class Hierarchy)</H3>\r\n<BLOCKQUOTE>\r\nThere is a <A HREF=\"overview-tree.html\">Class Hierarchy</A> page for all packages, plus a hierarchy for each package. Each hierarchy page contains a list of classes and a list of interfaces. The classes are organized by inheritance structure starting with <code>java.lang.Object</code>. The interfaces do not inherit from <code>java.lang.Object</code>.<UL>\r\n<LI>When viewing the Overview page, clicking on \"Tree\" displays the hierarchy for all packages.<LI>When viewing a particular package, class or interface page, clicking \"Tree\" displays the hierarchy for only that package.</UL>\r\n</BLOCKQUOTE>\r\n<H3>\r\nDeprecated API</H3>\r\n<BLOCKQUOTE>\r\nThe <A HREF=\"deprecated-list.html\">Deprecated API</A> page lists all of the API that have been deprecated. A deprecated API is not recommended for use, generally due to improvements, and a replacement API is usually given. Deprecated APIs may be removed in future implementations.</BLOCKQUOTE>\r\n<H3>\r\nIndex</H3>\r\n<BLOCKQUOTE>\r\nThe <A HREF=\"index-all.html\">Index</A> contains an alphabetic list of all classes, interfaces, constructors, methods, and fields.</BLOCKQUOTE>\r\n<H3>\r\nPrev/Next</H3>\r\nThese links take you to the next or previous class, interface, package, or related page.<H3>\r\nFrames/No Frames</H3>\r\nThese links show and hide the HTML frames.  All pages are available with or without frames.\r\n<P>\r\n<H3>\r\nSerialized Form</H3>\r\nEach serializable or externalizable class has a description of its serialization fields and methods. This information is of interest to re-implementors, not to developers using the API. While there is no link in the navigation bar, you can get to this information by going to any serialized class and clicking \"Serialized Form\" in the \"See also\" section of the class description.\r\n<P>\r\n<FONT SIZE=\"-1\">\r\n<EM>\r\nThis help file applies to API documentation generated using the standard doclet.</EM>\r\n</FONT>\r\n<BR>\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Help</B></FONT>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"help-doc.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/index-all.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:56 CEST 2005 -->\r\n<TITLE>\r\nIndex (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"Index (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\r\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\r\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\r\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\r\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Index</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"index-all.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\r\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\r\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<A HREF=\"#_A_\">A</A> <A HREF=\"#_B_\">B</A> <A HREF=\"#_C_\">C</A> <A HREF=\"#_D_\">D</A> <A HREF=\"#_E_\">E</A> <A HREF=\"#_F_\">F</A> <A HREF=\"#_G_\">G</A> <A HREF=\"#_H_\">H</A> <A HREF=\"#_I_\">I</A> <A HREF=\"#_L_\">L</A> <A HREF=\"#_M_\">M</A> <A HREF=\"#_N_\">N</A> <A HREF=\"#_O_\">O</A> <A HREF=\"#_P_\">P</A> <A HREF=\"#_R_\">R</A> <A HREF=\"#_S_\">S</A> <A HREF=\"#_T_\">T</A> <A HREF=\"#_U_\">U</A> <A HREF=\"#_V_\">V</A> <A HREF=\"#_W_\">W</A> <HR>\r\n<A NAME=\"_A_\"><!-- --></A><H2>\r\n<B>A</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_BOUNDFLIP\"><B>ANTIDEGEN_BOUNDFLIP</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_COLUMNCHECK\"><B>ANTIDEGEN_COLUMNCHECK</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_DURINGBB\"><B>ANTIDEGEN_DURINGBB</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_DYNAMIC\"><B>ANTIDEGEN_DYNAMIC</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_FIXEDVARS\"><B>ANTIDEGEN_FIXEDVARS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_INFEASIBLE\"><B>ANTIDEGEN_INFEASIBLE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_LOSTFEAS\"><B>ANTIDEGEN_LOSTFEAS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_NONE\"><B>ANTIDEGEN_NONE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_NUMFAILURE\"><B>ANTIDEGEN_NUMFAILURE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_RHSPERTURB\"><B>ANTIDEGEN_RHSPERTURB</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#ANTIDEGEN_STALLING\"><B>ANTIDEGEN_STALLING</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#AUTOMATIC\"><B>AUTOMATIC</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/AbortListener.html\" title=\"interface in lpsolve\"><B>AbortListener</B></A> - interface lpsolve.<A HREF=\"lpsolve/AbortListener.html\" title=\"interface in lpsolve\">AbortListener</A>.<DD>Classes that implement this interface may be passed\r\n to the <code>putAbortfunc</code> method of the <code>LpSolve</code> class.<DT><A HREF=\"lpsolve/AbortListener.html#abortfunc(lpsolve.LpSolve, java.lang.Object)\"><B>abortfunc(LpSolve, Object)</B></A> -\r\nMethod in interface lpsolve.<A HREF=\"lpsolve/AbortListener.html\" title=\"interface in lpsolve\">AbortListener</A>\r\n<DD>When set, the abort routine is called regularly during solve().\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#addColumn(double[])\"><B>addColumn(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a column to the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#addColumnex(int, double[], int[])\"><B>addColumnex(int, double[], int[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a column to the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#addConstraint(double[], int, double)\"><B>addConstraint(double[], int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a constraint to the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#addConstraintex(int, double[], int[], int, double)\"><B>addConstraintex(int, double[], int[], int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a constraint to the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#addLagCon(double[], int, double)\"><B>addLagCon(double[], int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a Lagrangian constraint to the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#addSOS(java.lang.String, int, int, int, int[], double[])\"><B>addSOS(String, int, int, int, int[], double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a SOS constraint.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_B_\"><!-- --></A><H2>\r\n<B>B</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#BRANCH_AUTOMATIC\"><B>BRANCH_AUTOMATIC</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#BRANCH_CEILING\"><B>BRANCH_CEILING</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#BRANCH_FLOOR\"><B>BRANCH_FLOOR</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#BRANCH_DEFAULT\"><B>BRANCH_DEFAULT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/BbListener.html\" title=\"interface in lpsolve\"><B>BbListener</B></A> - interface lpsolve.<A HREF=\"lpsolve/BbListener.html\" title=\"interface in lpsolve\">BbListener</A>.<DD>Classes that implement this interface may be passed\r\n to the <code>putbbBranchfunc</code> and <code>putbbNodefunc</code> method\r\n of the <code>LpSolve</code> class.<DT><A HREF=\"lpsolve/BbListener.html#bbfunc(lpsolve.LpSolve, java.lang.Object, int)\"><B>bbfunc(LpSolve, Object, int)</B></A> -\r\nMethod in interface lpsolve.<A HREF=\"lpsolve/BbListener.html\" title=\"interface in lpsolve\">BbListener</A>\r\n<DD>TODO: add documentation when available\r\n</DL>\r\n<HR>\r\n<A NAME=\"_C_\"><!-- --></A><H2>\r\n<B>C</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#CRASH_MOSTFEASIBLE\"><B>CRASH_MOSTFEASIBLE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#CRASH_NOTHING\"><B>CRASH_NOTHING</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#CRITICAL\"><B>CRITICAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#columnInLp(double[])\"><B>columnInLp(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Check if a column is already present in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#copyLp()\"><B>copyLp()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Copy an existing lprec structure to a new lprec structure.\r\n\r\n</DL>\r\n<HR>\r\n<A NAME=\"_D_\"><!-- --></A><H2>\r\n<B>D</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#DATAIGNORED\"><B>DATAIGNORED</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#DEGENERATE\"><B>DEGENERATE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#DETAILED\"><B>DETAILED</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#DYNAMIC\"><B>DYNAMIC</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#defaultBasis()\"><B>defaultBasis()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets the starting base to an all slack basis (the default simplex starting basis).\r\n<DT><A HREF=\"lpsolve/LpSolve.html#delColumn(int)\"><B>delColumn(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Remove a column from the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#delConstraint(int)\"><B>delConstraint(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Remove a constraint from the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#deleteLp()\"><B>deleteLp()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Frees all resources allocated to this problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#dualizeLp()\"><B>dualizeLp()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Create the dual of the current model.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_E_\"><!-- --></A><H2>\r\n<B>E</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#EQ\"><B>EQ</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n</DL>\r\n<HR>\r\n<A NAME=\"_F_\"><!-- --></A><H2>\r\n<B>F</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#FALSE\"><B>FALSE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#FEASFOUND\"><B>FEASFOUND</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#FR\"><B>FR</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#FULL\"><B>FULL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVED\"><B>PRESOLVED</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#finalize()\"><B>finalize()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n</DL>\r\n<HR>\r\n<A NAME=\"_G_\"><!-- --></A><H2>\r\n<B>G</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#GE\"><B>GE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getAntiDegen()\"><B>getAntiDegen()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the used degeneracy rule.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getBasis(int[], boolean)\"><B>getBasis(int[], boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the basis of the lp.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getBasiscrash()\"><B>getBasiscrash()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns which basis crash mode must be used.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getBbDepthlimit()\"><B>getBbDepthlimit()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the maximum branch-and-bound depth.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getBbFloorfirst()\"><B>getBbFloorfirst()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns which branch to take first in branch-and-bound algorithm.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getBbRule()\"><B>getBbRule()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the branch-and-bound rule.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getBoundsTighter()\"><B>getBoundsTighter()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if set bounds may only be tighter or also less restrictive.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getBreakAtValue()\"><B>getBreakAtValue()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value at which the branch-and-bound algorithm stops\r\n when the object value is better than this value.\r\n<DT><A HREF=\"lpsolve/VersionInfo.html#getBuild()\"><B>getBuild()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getColName(int)\"><B>getColName(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the name of a column in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getColumn(int, double[])\"><B>getColumn(int, double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get all column elements from the matrix.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getColumnex(int, double[], int[])\"><B>getColumnex(int, double[], int[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the non-zero column elements from the matrix.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getConstrType(int)\"><B>getConstrType(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the type of a constraint.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getConstrValue(int, int, double[], int[])\"><B>getConstrValue(int, int, double[], int[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the value of a constraint according to provided variable values.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getConstraints(double[])\"><B>getConstraints(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the values of the constraints.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getDualSolution(double[])\"><B>getDualSolution(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getEpsb()\"><B>getEpsb()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value that is used as a tolerance for the Right Hand Side (RHS)\r\n to determine whether a value should be considered as 0.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getEpsd()\"><B>getEpsd()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value that is used as a tolerance for the reduced costs\r\n to determine whether a value should be considered as 0.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getEpsel()\"><B>getEpsel()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value that is used as a tolerance for rounding values to zero.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getEpsint()\"><B>getEpsint()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the tolerance that is used to determine whether a floating-point\r\n number is in fact an integer\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getEpsperturb()\"><B>getEpsperturb()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value that is used as perturbation scalar for degenerative problems.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getEpspivot()\"><B>getEpspivot()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value that is used as a tolerance pivot element to determine\r\n whether a value should be considered as 0.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getImprove()\"><B>getImprove()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the iterative improvement level.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getInfinite()\"><B>getInfinite()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value of \"infinite\".\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getLambda(double[])\"><B>getLambda(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the Lamdba vectors (Lagrangian optimization).\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getLowbo(int)\"><B>getLowbo(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the lower bound of a variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getLp()\"><B>getLp()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Return the value of the lp attribute.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getLpIndex(int)\"><B>getLpIndex(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the index in the lp of the original row/column.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getLpName()\"><B>getLpName()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the name of the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getLrows()\"><B>getLrows()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the number of Lagrangian rows in the lp.\r\n<DT><A HREF=\"lpsolve/VersionInfo.html#getMajorversion()\"><B>getMajorversion()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getMat(int, int)\"><B>getMat(int, int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get a single element from the matrix.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getMaxLevel()\"><B>getMaxLevel()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the deepest Branch-and-bound level of the last solution.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getMaxpivot()\"><B>getMaxpivot()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the maximum number of pivots between a reinversion of the matrix.\r\n<DT><A HREF=\"lpsolve/VersionInfo.html#getMinorversion()\"><B>getMinorversion()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getMipGap(boolean)\"><B>getMipGap(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the MIP gap value.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getNameindex(java.lang.String, boolean)\"><B>getNameindex(String, boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the index of a given column or row name in the lp.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getNcolumns()\"><B>getNcolumns()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the number of columns (variables) in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getNegrange()\"><B>getNegrange()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the negative value below which variables are split\r\n into a negative and a positive part.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getNonzeros()\"><B>getNonzeros()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the number of non-zero elements in the matrix.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getNorigColumns()\"><B>getNorigColumns()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the number of original columns (variables) in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getNorigRows()\"><B>getNorigRows()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the number of original rows (constraints) in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getNrows()\"><B>getNrows()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the number of rows (constraints) in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getObjBound()\"><B>getObjBound()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns initial \"at least better than\" guess for objective function.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getObjective()\"><B>getObjective()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value of the objective function.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getOrigIndex(int)\"><B>getOrigIndex(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the original row/column where a constraint/variable was before presolve.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getOrigcolName(int)\"><B>getOrigcolName(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the name of a column in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getOrigrowName(int)\"><B>getOrigrowName(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the name of a constraint (row) in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPivoting()\"><B>getPivoting()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the pivot rule.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPresolve()\"><B>getPresolve()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the current presolve setting.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPresolveloops()\"><B>getPresolveloops()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the number of times presolve is done.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPrimalSolution(double[])\"><B>getPrimalSolution(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the solution of the model.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPrintSol()\"><B>getPrintSol()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns a flag if all intermediate valid solutions must be printed while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrColumn(int)\"><B>getPtrColumn(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get all column elements from the matrix.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrConstraints()\"><B>getPtrConstraints()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the values of the constraints.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrDualSolution()\"><B>getPtrDualSolution()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrLambda()\"><B>getPtrLambda()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the Lamdba vectors (Lagrangian optimization).\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrPrimalSolution()\"><B>getPtrPrimalSolution()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the solution of the model.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrRow(int)\"><B>getPtrRow(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get all row elements from the matrix.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrSensitivityObj()\"><B>getPtrSensitivityObj()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the objective function.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrSensitivityObjex()\"><B>getPtrSensitivityObjex()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the objective function.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrSensitivityRhs()\"><B>getPtrSensitivityRhs()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getPtrVariables()\"><B>getPtrVariables()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the values of the variables.\r\n\r\n<DT><A HREF=\"lpsolve/VersionInfo.html#getRelease()\"><B>getRelease()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getRh(int)\"><B>getRh(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the value of the right hand side (RHS) vector (column 0) for one row.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getRhRange(int)\"><B>getRhRange(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the range on a constraint.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getRow(int, double[])\"><B>getRow(int, double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get all row elements from the matrix.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getRowName(int)\"><B>getRowName(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the name of a constraint (row) in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getRowex(int, double[], int[])\"><B>getRowex(int, double[], int[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the non-zero row elements from the matrix.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getScalelimit()\"><B>getScalelimit()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the relative scaling convergence criterion for the active scaling mode;\r\n the integer part specifies the maximum number of iterations.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getScaling()\"><B>getScaling()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies which scaling algorithm is used.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getSensitivityObj(double[], double[])\"><B>getSensitivityObj(double[], double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the objective function.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getSensitivityObjex(double[], double[], double[], double[])\"><B>getSensitivityObjex(double[], double[], double[], double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the objective function.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getSensitivityRhs(double[], double[], double[])\"><B>getSensitivityRhs(double[], double[], double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getSimplextype()\"><B>getSimplextype()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the desired combination of primal and dual simplex algorithms.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getSolutioncount()\"><B>getSolutioncount()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the number of equal solutions.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getSolutionlimit()\"><B>getSolutionlimit()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the solution number that must be returned.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getStatus()\"><B>getStatus()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns an extra status after a call to a function.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getStatustext(int)\"><B>getStatustext(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the description of a returncode of the solve function.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getTimeout()\"><B>getTimeout()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the timout.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getTotalIter()\"><B>getTotalIter()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the total number of iterations with Branch-and-bound of the last solution.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getTotalNodes()\"><B>getTotalNodes()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the total number of nodes processed in branch-and-bound.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getUpbo(int)\"><B>getUpbo(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the upper bound of a variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getVarBranch(int)\"><B>getVarBranch(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns, for the specified variable, which branch to take first\r\n in branch-and-bound algorithm.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getVarDualresult(int)\"><B>getVarDualresult(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getVarPrimalresult(int)\"><B>getVarPrimalresult(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the solution of the model.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getVarPriority(int)\"><B>getVarPriority(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns, for the specified variable, the priority the variable has\r\n in the branch-and-bound algorithm.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getVariables(double[])\"><B>getVariables(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the values of the variables.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getVerbose()\"><B>getVerbose()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the verbose level.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#getWorkingObjective()\"><B>getWorkingObjective()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the value of the objective function.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#guessBasis(double[], int[])\"><B>guessBasis(double[], int[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Guess an initial basis of the lp.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_H_\"><!-- --></A><H2>\r\n<B>H</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#hasBFP()\"><B>hasBFP()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if there is a basis factorization package (BFP) available.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#hasXLI()\"><B>hasXLI()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if there is an external language interface (XLI) set.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_I_\"><!-- --></A><H2>\r\n<B>I</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#IMPORTANT\"><B>IMPORTANT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#IMPROVE_BBSIMPLEX\"><B>IMPROVE_BBSIMPLEX</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#IMPROVE_DUALFEAS\"><B>IMPROVE_DUALFEAS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#IMPROVE_NONE\"><B>IMPROVE_NONE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#IMPROVE_SOLUTION\"><B>IMPROVE_SOLUTION</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#IMPROVE_THETAGAP\"><B>IMPROVE_THETAGAP</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#INFEASIBLE\"><B>INFEASIBLE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isAddRowmode()\"><B>isAddRowmode()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns a flag which of the add routines perform best.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isAntiDegen(int)\"><B>isAntiDegen(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if the degeneracy rule specified in testmask is active.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isBinary(int)\"><B>isBinary(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the type of the variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isBreakAtFirst()\"><B>isBreakAtFirst()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if the branch-and-bound algorithm stops at first found solution.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isConstrType(int, int)\"><B>isConstrType(int, int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if constraint type specified in mask is active.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isDebug()\"><B>isDebug()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns a flag if all intermediate results and the branch-and-bound decisions\r\n must be printed while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isFeasible(double[], double)\"><B>isFeasible(double[], double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Checks if provided solution is a feasible solution.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isInfinite(double)\"><B>isInfinite(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Checks if the provided absolute of the value is larger or equal to \"infinite\".\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isInt(int)\"><B>isInt(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the type of the variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isIntegerscaling()\"><B>isIntegerscaling()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies which scaling algorithm is used.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isLagTrace()\"><B>isLagTrace()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns a flag if Lagrangian progression must be printed while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isMaxim()\"><B>isMaxim()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns objective function direction.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isNativeBFP()\"><B>isNativeBFP()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if the native (build-in) basis factorization package (BFP) is used,\r\n or an external package.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isNativeXLI()\"><B>isNativeXLI()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if a build-in External Language Interfaces (XLI) is available or not.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isNegative(int)\"><B>isNegative(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if the variable is negative.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isPivMode(int)\"><B>isPivMode(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if pivot strategy specified in testmask is active.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isPivRule(int)\"><B>isPivRule(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Checks if the specified pivot rule is active.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isPresolve(int)\"><B>isPresolve(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if presolve level specified in testmask is active.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isSOSVar(int)\"><B>isSOSVar(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if the variable is SOS or not.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isScalemode(int)\"><B>isScalemode(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if scaling mode specified in testmask is active.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isScaletype(int)\"><B>isScaletype(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if scaling type specified in scaletype is active.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isSemicont(int)\"><B>isSemicont(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Get the type of the variable. semi-continious or not.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isTrace()\"><B>isTrace()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns a flag if pivot selection must be printed while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isUnbounded(int)\"><B>isUnbounded(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if the variable is free.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#isUseNames(boolean)\"><B>isUseNames(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns if variable or constraint names are used.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_L_\"><!-- --></A><H2>\r\n<B>L</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#LE\"><B>LE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LogListener.html\" title=\"interface in lpsolve\"><B>LogListener</B></A> - interface lpsolve.<A HREF=\"lpsolve/LogListener.html\" title=\"interface in lpsolve\">LogListener</A>.<DD>Classes that implement this interface may be passed\r\n to the <code>putLogfunc</code> method of the <code>LpSolve</code> class.<DT><A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\"><B>LpSolve</B></A> - class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>.<DD>Object wrapper for a problem structure of the lp_solve library.\r\n <DT><A HREF=\"lpsolve/LpSolveException.html\" title=\"class in lpsolve\"><B>LpSolveException</B></A> - exception lpsolve.<A HREF=\"lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A>.<DD>Exception thrown by the native methods in the C stub DLL.<DT><A HREF=\"lpsolve/LpSolveException.html#LpSolveException()\"><B>LpSolveException()</B></A> -\r\nConstructor for class lpsolve.<A HREF=\"lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolveException.html#LpSolveException(java.lang.String)\"><B>LpSolveException(String)</B></A> -\r\nConstructor for class lpsolve.<A HREF=\"lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LogListener.html#logfunc(lpsolve.LpSolve, java.lang.Object, java.lang.String)\"><B>logfunc(LpSolve, Object, String)</B></A> -\r\nMethod in interface lpsolve.<A HREF=\"lpsolve/LogListener.html\" title=\"interface in lpsolve\">LogListener</A>\r\n<DD>When set, the log routine is called when lp_solve has someting\r\n to report (error conditions or so).\r\n<DT><A HREF=\"lpsolve/LpSolve.html#lpSolveVersion()\"><B>lpSolveVersion()</B></A> -\r\nStatic method in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Returns the full version number of the underlying lp_solve library.\r\n<DT><A HREF=\"lpsolve/package-summary.html\"><B>lpsolve</B></A> - package lpsolve<DD>This package contains the files for the Java wrapper for the lp_solve optimization library.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_M_\"><!-- --></A><H2>\r\n<B>M</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_INITPSEUDOCOST\"><B>MSG_INITPSEUDOCOST</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_INVERT\"><B>MSG_INVERT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_ITERATION\"><B>MSG_ITERATION</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_LPBETTER\"><B>MSG_LPBETTER</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_LPEQUAL\"><B>MSG_LPEQUAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_LPFEASIBLE\"><B>MSG_LPFEASIBLE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_LPOPTIMAL\"><B>MSG_LPOPTIMAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_MILPBETTER\"><B>MSG_MILPBETTER</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_MILPEQUAL\"><B>MSG_MILPEQUAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_MILPFEASIBLE\"><B>MSG_MILPFEASIBLE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_MILPOPTIMAL\"><B>MSG_MILPOPTIMAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_MILPSTRATEGY\"><B>MSG_MILPSTRATEGY</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_NONE\"><B>MSG_NONE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_PERFORMANCE\"><B>MSG_PERFORMANCE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#MSG_PRESOLVE\"><B>MSG_PRESOLVE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/MsgListener.html\" title=\"interface in lpsolve\"><B>MsgListener</B></A> - interface lpsolve.<A HREF=\"lpsolve/MsgListener.html\" title=\"interface in lpsolve\">MsgListener</A>.<DD>Classes that implement this interface may be passed\r\n to the <code>putMsgfunc</code> method of the <code>LpSolve</code> class.<DT><A HREF=\"lpsolve/LpSolve.html#makeLp(int, int)\"><B>makeLp(int, int)</B></A> -\r\nStatic method in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Creates a new problem.\r\n<DT><A HREF=\"lpsolve/MsgListener.html#msgfunc(lpsolve.LpSolve, java.lang.Object, int)\"><B>msgfunc(LpSolve, Object, int)</B></A> -\r\nMethod in interface lpsolve.<A HREF=\"lpsolve/MsgListener.html\" title=\"interface in lpsolve\">MsgListener</A>\r\n<DD>This routine is called when a situation specified in the mask parameter\r\n of putMsgfunc occurs.\r\n\r\n</DL>\r\n<HR>\r\n<A NAME=\"_N_\"><!-- --></A><H2>\r\n<B>N</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NEUTRAL\"><B>NEUTRAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NOBFP\"><B>NOBFP</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_AUTOORDER\"><B>NODE_AUTOORDER</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_BRANCHREVERSEMODE\"><B>NODE_BRANCHREVERSEMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_BREADTHFIRSTMODE\"><B>NODE_BREADTHFIRSTMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_DEPTHFIRSTMODE\"><B>NODE_DEPTHFIRSTMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_DYNAMICMODE\"><B>NODE_DYNAMICMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_FIRSTSELECT\"><B>NODE_FIRSTSELECT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_FRACTIONSELECT\"><B>NODE_FRACTIONSELECT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_GAPSELECT\"><B>NODE_GAPSELECT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_GREEDYMODE\"><B>NODE_GREEDYMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_PSEUDOCOSTMODE\"><B>NODE_PSEUDOCOSTMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_PSEUDOCOSTSELECT\"><B>NODE_PSEUDOCOSTSELECT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_PSEUDONONINTSELECT\"><B>NODE_PSEUDONONINTSELECT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_PSEUDORATIOSELECT\"><B>NODE_PSEUDORATIOSELECT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_RANDOMIZEMODE\"><B>NODE_RANDOMIZEMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_RANGESELECT\"><B>NODE_RANGESELECT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_RCOSTFIXING\"><B>NODE_RCOSTFIXING</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_RESTARTMODE\"><B>NODE_RESTARTMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_STRONGINIT\"><B>NODE_STRONGINIT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_USERSELECT\"><B>NODE_USERSELECT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NODE_WEIGHTREVERSEMODE\"><B>NODE_WEIGHTREVERSEMODE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NOFEASFOUND\"><B>NOFEASFOUND</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NOMEMORY\"><B>NOMEMORY</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NORMAL\"><B>NORMAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NOTRUN\"><B>NOTRUN</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#NUMFAILURE\"><B>NUMFAILURE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n</DL>\r\n<HR>\r\n<A NAME=\"_O_\"><!-- --></A><H2>\r\n<B>O</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#OF\"><B>OF</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#OPTIMAL\"><B>OPTIMAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n</DL>\r\n<HR>\r\n<A NAME=\"_P_\"><!-- --></A><H2>\r\n<B>P</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_BOUNDS\"><B>PRESOLVE_BOUNDS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_COLDOMINATE\"><B>PRESOLVE_COLDOMINATE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_COLFIXDUAL\"><B>PRESOLVE_COLFIXDUAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_COLS\"><B>PRESOLVE_COLS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_DUALS\"><B>PRESOLVE_DUALS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_ELIMEQ2\"><B>PRESOLVE_ELIMEQ2</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_IMPLIEDFREE\"><B>PRESOLVE_IMPLIEDFREE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_IMPLIEDSLK\"><B>PRESOLVE_IMPLIEDSLK</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_KNAPSACK\"><B>PRESOLVE_KNAPSACK</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_LINDEP\"><B>PRESOLVE_LINDEP</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_MERGEROWS\"><B>PRESOLVE_MERGEROWS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_NONE\"><B>PRESOLVE_NONE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_PROBEFIX\"><B>PRESOLVE_PROBEFIX</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_PROBEREDUCE\"><B>PRESOLVE_PROBEREDUCE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_REDUCEGCD\"><B>PRESOLVE_REDUCEGCD</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_REDUCEMIP\"><B>PRESOLVE_REDUCEMIP</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_ROWDOMINATE\"><B>PRESOLVE_ROWDOMINATE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_ROWS\"><B>PRESOLVE_ROWS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_SENSDUALS\"><B>PRESOLVE_SENSDUALS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRESOLVE_SOS\"><B>PRESOLVE_SOS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICER_DANTZIG\"><B>PRICER_DANTZIG</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICER_DEVEX\"><B>PRICER_DEVEX</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICER_FIRSTINDEX\"><B>PRICER_FIRSTINDEX</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICER_STEEPESTEDGE\"><B>PRICER_STEEPESTEDGE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_ADAPTIVE\"><B>PRICE_ADAPTIVE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_AUTOPARTIAL\"><B>PRICE_AUTOPARTIAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_HARRISTWOPASS\"><B>PRICE_HARRISTWOPASS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_HYBRID\"><B>PRICE_HYBRID</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_LOOPALTERNATE\"><B>PRICE_LOOPALTERNATE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_LOOPLEFT\"><B>PRICE_LOOPLEFT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_METHODDEFAULT\"><B>PRICE_METHODDEFAULT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_MULTIPLE\"><B>PRICE_MULTIPLE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_PARTIAL\"><B>PRICE_PARTIAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_PRIMALFALLBACK\"><B>PRICE_PRIMALFALLBACK</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_RANDOMIZE\"><B>PRICE_RANDOMIZE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PRICE_TRUENORMINIT\"><B>PRICE_TRUENORMINIT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PROCBREAK\"><B>PROCBREAK</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#PROCFAIL\"><B>PROCFAIL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printConstraints(int)\"><B>printConstraints(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Prints the values of the constraints of the lp.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printDebugdump(java.lang.String)\"><B>printDebugdump(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Do a generic readable data dump of key lp_solve model variables;\r\n principally for run difference and debugging purposes.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printDuals()\"><B>printDuals()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Prints the values of the duals of the lp.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printLp()\"><B>printLp()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Prints the lp model.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printObjective()\"><B>printObjective()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Prints the objective value of the lp.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printScales()\"><B>printScales()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Prints the scales of the lp.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printSolution(int)\"><B>printSolution(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Prints the solution (variables) of the lp.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printStr(java.lang.String)\"><B>printStr(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Prints a string.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#printTableau()\"><B>printTableau()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Prints the tableau.\r\n\r\n<DT><A HREF=\"lpsolve/LpSolve.html#putAbortfunc(lpsolve.AbortListener, java.lang.Object)\"><B>putAbortfunc(AbortListener, Object)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Register an <code>AbortListener</code> for callback.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#putBbBranchfunc(lpsolve.BbListener, java.lang.Object)\"><B>putBbBranchfunc(BbListener, Object)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Register an <code>BbBranchListener</code> for callback.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#putBbNodefunc(lpsolve.BbListener, java.lang.Object)\"><B>putBbNodefunc(BbListener, Object)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Register an <code>BbNodeListener</code> for callback.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#putLogfunc(lpsolve.LogListener, java.lang.Object)\"><B>putLogfunc(LogListener, Object)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Register an <code>LogListener</code> for callback.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#putMsgfunc(lpsolve.MsgListener, java.lang.Object, int)\"><B>putMsgfunc(MsgListener, Object, int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Register an <code>MsgListener</code> for callback.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_R_\"><!-- --></A><H2>\r\n<B>R</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#RUNNING\"><B>RUNNING</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#readBasis(java.lang.String)\"><B>readBasis(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Read basis from a file and set as default basis.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#readFreeMps(java.lang.String, int)\"><B>readFreeMps(String, int)</B></A> -\r\nStatic method in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Read a model in free MPS format from file and create a new problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#readLp(java.lang.String, int, java.lang.String)\"><B>readLp(String, int, String)</B></A> -\r\nStatic method in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Read an lp model from file and create a new problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#readMps(java.lang.String, int)\"><B>readMps(String, int)</B></A> -\r\nStatic method in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Read an mps model from file and create a new problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#readParams(java.lang.String, java.lang.String)\"><B>readParams(String, String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Read settings from a parameter file.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#readXLI(java.lang.String, java.lang.String, java.lang.String, java.lang.String, int)\"><B>readXLI(String, String, String, String, int)</B></A> -\r\nStatic method in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Read a model via the External Language Interface and create a new problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#resetBasis()\"><B>resetBasis()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Resets the basis to the initial basis.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#resetParams()\"><B>resetParams()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Resets parameters back to their default values.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#resizeLp(int, int)\"><B>resizeLp(int, int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Allocates memory for the specified size.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_S_\"><!-- --></A><H2>\r\n<B>S</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_COLSONLY\"><B>SCALE_COLSONLY</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_CURTISREID\"><B>SCALE_CURTISREID</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_DYNUPDATE\"><B>SCALE_DYNUPDATE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_EQUILIBRATE\"><B>SCALE_EQUILIBRATE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_EXTREME\"><B>SCALE_EXTREME</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_GEOMETRIC\"><B>SCALE_GEOMETRIC</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_INTEGERS\"><B>SCALE_INTEGERS</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_LINEAR\"><B>SCALE_LINEAR</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_LOGARITHMIC\"><B>SCALE_LOGARITHMIC</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_MEAN\"><B>SCALE_MEAN</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_NONE\"><B>SCALE_NONE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_POWER2\"><B>SCALE_POWER2</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_QUADRATIC\"><B>SCALE_QUADRATIC</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_RANGE\"><B>SCALE_RANGE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_ROWSONLY\"><B>SCALE_ROWSONLY</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SCALE_USERWEIGHT\"><B>SCALE_USERWEIGHT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SEVERE\"><B>SEVERE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_DEFAULT\"><B>SIMPLEX_DEFAULT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_DUAL_DUAL\"><B>SIMPLEX_DUAL_DUAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_DUAL_PRIMAL\"><B>SIMPLEX_DUAL_PRIMAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_PRIMAL_DUAL\"><B>SIMPLEX_PRIMAL_DUAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SIMPLEX_PRIMAL_PRIMAL\"><B>SIMPLEX_PRIMAL_PRIMAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#SUBOPTIMAL\"><B>SUBOPTIMAL</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setAddRowmode(boolean)\"><B>setAddRowmode(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies which add routine performs best.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setAntiDegen(int)\"><B>setAntiDegen(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies if special handling must be done to reduce degeneracy/cycling while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBFP(java.lang.String)\"><B>setBFP(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set basis factorization package.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBasis(int[], boolean)\"><B>setBasis(int[], boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets an initial basis of the lp.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBasiscrash(int)\"><B>setBasiscrash(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies which basis crash mode must be used.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBasisvar(int, int)\"><B>setBasisvar(int, int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>This is an internal function that has been published for special purposes. It should generally not be used.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBbDepthlimit(int)\"><B>setBbDepthlimit(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets the maximum branch-and-bound depth.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBbFloorfirst(int)\"><B>setBbFloorfirst(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies which branch to take first in branch-and-bound algorithm.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBbRule(int)\"><B>setBbRule(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the branch-and-bound rule.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBinary(int, boolean)\"><B>setBinary(int, boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the type of the variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBounds(int, double, double)\"><B>setBounds(int, double, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the upper and lower bound of a variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBoundsTighter(boolean)\"><B>setBoundsTighter(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies if set bounds may only be tighter or also less restrictive.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBreakAtFirst(boolean)\"><B>setBreakAtFirst(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies if the branch-and-bound algorithm stops at first found solution.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setBreakAtValue(double)\"><B>setBreakAtValue(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies if the branch-and-bound algorithm stops when the object value\r\n is better than a given value.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setColName(int, java.lang.String)\"><B>setColName(int, String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the name of a column in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setColumn(int, double[])\"><B>setColumn(int, double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set a column in the lp.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setColumnex(int, int, double[], int[])\"><B>setColumnex(int, int, double[], int[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set a column in the lp.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setConstrType(int, int)\"><B>setConstrType(int, int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the type of a constraint.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setDebug(boolean)\"><B>setDebug(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets a flag if all intermediate results and the branch-and-bound decisions\r\n must be printed while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setEpsb(double)\"><B>setEpsb(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the value that is used as a tolerance for the Right Hand Side (RHS)\r\n to determine whether a value should be considered as 0\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setEpsd(double)\"><B>setEpsd(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the value that is used as a tolerance for reduced costs\r\n to determine whether a value should be considered as 0.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setEpsel(double)\"><B>setEpsel(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the value that is used as a tolerance for rounding values to zero.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setEpsint(double)\"><B>setEpsint(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the tolerance that is used to determine whether a floating-point\r\n number is in fact an integer.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setEpslevel(int)\"><B>setEpslevel(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>This is a simplified way of specifying multiple eps thresholds that are \"logically\" consistent.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setEpsperturb(double)\"><B>setEpsperturb(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the value that is used as perturbation scalar for degenerative problems.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setEpspivot(double)\"><B>setEpspivot(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the value that is used as a tolerance pivot element to determine\r\n whether a value should be considered as 0.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setImprove(int)\"><B>setImprove(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the iterative improvement level.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setInfinite(double)\"><B>setInfinite(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the practical value for \"infinite\".\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setInt(int, boolean)\"><B>setInt(int, boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the type of the variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setLagTrace(boolean)\"><B>setLagTrace(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets a flag if Lagrangian progression must be printed while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setLowbo(int, double)\"><B>setLowbo(int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the lower bound of a variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setLpName(java.lang.String)\"><B>setLpName(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the name of the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setMat(int, int, double)\"><B>setMat(int, int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set a single element in the matrix.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setMaxim()\"><B>setMaxim()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set objective function to maximize.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setMaxpivot(int)\"><B>setMaxpivot(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets the maximum number of pivots between a reinversion of the matrix.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setMinim()\"><B>setMinim()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set objective function to minimize.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setMipGap(boolean, double)\"><B>setMipGap(boolean, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the MIP gap value.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setNegrange(double)\"><B>setNegrange(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set negative value below which variables are split into a negative\r\n and a positive part.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setObj(int, double)\"><B>setObj(int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the objective function (row 0) of the matrix.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setObjBound(double)\"><B>setObjBound(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set initial \"at least better than\" guess for objective function.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setObjFn(double[])\"><B>setObjFn(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the objective function (row 0) of the matrix.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setObjFnex(int, double[], int[])\"><B>setObjFnex(int, double[], int[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the objective function (row 0) of the matrix.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setOutputfile(java.lang.String)\"><B>setOutputfile(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Defines the output for the print_* functions.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setPivoting(int)\"><B>setPivoting(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies the pivot rule.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setPreferdual(boolean)\"><B>setPreferdual(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets the desired combination of primal and dual simplex algorithms.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setPresolve(int, int)\"><B>setPresolve(int, int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies if a presolve must be done before solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setPrintSol(int)\"><B>setPrintSol(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets a flag if all intermediate valid solutions must be printed while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setRh(int, double)\"><B>setRh(int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the value of the right hand side (RHS) vector (column 0) for one row.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setRhRange(int, double)\"><B>setRhRange(int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the range on a constraint.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setRhVec(double[])\"><B>setRhVec(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the right hand side (RHS) vector (column 0).\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setRow(int, double[])\"><B>setRow(int, double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set a constraint in the lp.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setRowName(int, java.lang.String)\"><B>setRowName(int, String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the name of a constraint (row) in the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setRowex(int, int, double[], int[])\"><B>setRowex(int, int, double[], int[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set a constraint in the lp.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setScalelimit(double)\"><B>setScalelimit(double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets the relative scaling convergence criterion for the active scaling mode;\r\n the integer part specifies the maximum number of iterations.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setScaling(int)\"><B>setScaling(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies which scaling algorithm must be used.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setSemicont(int, boolean)\"><B>setSemicont(int, boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the type of the variable. semi-continious or not.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setSense(boolean)\"><B>setSense(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set objective function sense.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setSimplextype(int)\"><B>setSimplextype(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets the desired combination of primal and dual simplex algorithms.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setSolutionlimit(int)\"><B>setSolutionlimit(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets the solution number that must be returned.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setTimeout(long)\"><B>setTimeout(long)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set a timeout.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setTrace(boolean)\"><B>setTrace(boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets a flag if pivot selection must be printed while solving.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setUnbounded(int)\"><B>setUnbounded(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets if the variable is free.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setUpbo(int, double)\"><B>setUpbo(int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the upper bound of a variable.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setUseNames(boolean, boolean)\"><B>setUseNames(boolean, boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Sets if variable or constraint names are used.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setVarBranch(int, int)\"><B>setVarBranch(int, int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Specifies, for the specified variable, which branch to take first\r\n in branch-and-bound algorithm.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setVarWeights(double[])\"><B>setVarWeights(double[])</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the weights on variables.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setVerbose(int)\"><B>setVerbose(int)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the verbose level.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#setXLI(java.lang.String)\"><B>setXLI(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set External Language Interfaces package.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#solve()\"><B>solve()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Solve the model.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#strAddColumn(java.lang.String)\"><B>strAddColumn(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a column to the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#strAddConstraint(java.lang.String, int, double)\"><B>strAddConstraint(String, int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a constraint to the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#strAddLagCon(java.lang.String, int, double)\"><B>strAddLagCon(String, int, double)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Add a Lagrangian constraint to the problem.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#strSetObjFn(java.lang.String)\"><B>strSetObjFn(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the objective function (row 0) of the matrix.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#strSetRhVec(java.lang.String)\"><B>strSetRhVec(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Set the right hand side (RHS) vector (column 0).\r\n</DL>\r\n<HR>\r\n<A NAME=\"_T_\"><!-- --></A><H2>\r\n<B>T</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#TIMEOUT\"><B>TIMEOUT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#TRUE\"><B>TRUE</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#timeElapsed()\"><B>timeElapsed()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Gets the time elapsed since start of solve.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_U_\"><!-- --></A><H2>\r\n<B>U</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#UNBOUNDED\"><B>UNBOUNDED</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#UNKNOWNERROR\"><B>UNKNOWNERROR</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#USERABORT\"><B>USERABORT</B></A> -\r\nStatic variable in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>&nbsp;\r\n<DT><A HREF=\"lpsolve/LpSolve.html#unscale()\"><B>unscale()</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Unscales the model.\r\n</DL>\r\n<HR>\r\n<A NAME=\"_V_\"><!-- --></A><H2>\r\n<B>V</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\"><B>VersionInfo</B></A> - class lpsolve.<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A>.<DD>Contains the full version info for a lp_solve library instance.<DT><A HREF=\"lpsolve/VersionInfo.html#VersionInfo(int, int, int, int)\"><B>VersionInfo(int, int, int, int)</B></A> -\r\nConstructor for class lpsolve.<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A>\r\n<DD>Creates a new instance of this class\r\n</DL>\r\n<HR>\r\n<A NAME=\"_W_\"><!-- --></A><H2>\r\n<B>W</B></H2>\r\n<DL>\r\n<DT><A HREF=\"lpsolve/LpSolve.html#writeBasis(java.lang.String)\"><B>writeBasis(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Writes current basis to a file.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#writeFreeMps(java.lang.String)\"><B>writeFreeMps(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Write a model in free MPS format to a file.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#writeLp(java.lang.String)\"><B>writeLp(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Write an lp model to a file.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#writeMps(java.lang.String)\"><B>writeMps(String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Write an mps model to a file.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#writeParams(java.lang.String, java.lang.String)\"><B>writeParams(String, String)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Write settings to a parameter file.\r\n<DT><A HREF=\"lpsolve/LpSolve.html#writeXLI(java.lang.String, java.lang.String, boolean)\"><B>writeXLI(String, String, boolean)</B></A> -\r\nMethod in class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>\r\n<DD>Write a model to a file via the External Language Interface.\r\n</DL>\r\n<HR>\r\n<A HREF=\"#_A_\">A</A> <A HREF=\"#_B_\">B</A> <A HREF=\"#_C_\">C</A> <A HREF=\"#_D_\">D</A> <A HREF=\"#_E_\">E</A> <A HREF=\"#_F_\">F</A> <A HREF=\"#_G_\">G</A> <A HREF=\"#_H_\">H</A> <A HREF=\"#_I_\">I</A> <A HREF=\"#_L_\">L</A> <A HREF=\"#_M_\">M</A> <A HREF=\"#_N_\">N</A> <A HREF=\"#_O_\">O</A> <A HREF=\"#_P_\">P</A> <A HREF=\"#_R_\">R</A> <A HREF=\"#_S_\">S</A> <A HREF=\"#_T_\">T</A> <A HREF=\"#_U_\">U</A> <A HREF=\"#_V_\">V</A> <A HREF=\"#_W_\">W</A>\r\n\r\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\r\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\r\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\r\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Index</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"index-all.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\r\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\r\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/index.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Frameset//EN\" \"http://www.w3.org/TR/html4/frameset.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc on Sun Jun 26 18:11:57 CEST 2005-->\r\n<TITLE>\r\nUsing lp_solve in Java programs\r\n</TITLE>\r\n</HEAD>\r\n<FRAMESET cols=\"20%,80%\">\r\n<FRAME src=\"allclasses-frame.html\" name=\"packageFrame\" title=\"All classes and interfaces (except non-static nested types)\">\r\n<FRAME src=\"lpsolve/package-summary.html\" name=\"classFrame\" title=\"Package, class and interface descriptions\">\r\n<NOFRAMES>\r\n<H2>\r\nFrame Alert</H2>\r\n\r\n<P>\r\nThis document is designed to be viewed using the frames feature. If you see this message, you are using a non-frame-capable web client.\r\n<BR>\r\nLink to<A HREF=\"lpsolve/package-summary.html\">Non-frame version.</A>\r\n</NOFRAMES>\r\n</FRAMESET>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/AbortListener.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nAbortListener (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve.AbortListener interface\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"AbortListener (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV CLASS&nbsp;\r\n&nbsp;<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\"><B>NEXT CLASS</B></A></FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"AbortListener.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<!-- ======== START OF CLASS DATA ======== -->\r\n<H2>\r\n<FONT SIZE=\"-1\">\r\nlpsolve</FONT>\r\n<BR>\r\nInterface AbortListener</H2>\r\n<HR>\r\n<DL>\r\n<DT>public interface <B>AbortListener</B></DL>\r\n\r\n<P>\r\nClasses that implement this interface may be passed\n to the <code>putAbortfunc</code> method of the <code>LpSolve</code> class.\r\n<P>\r\n\r\n<P>\r\n<DL>\r\n<DT><B>Author:</B></DT>\n  <DD>Juergen Ebert</DD>\n<DT><B>See Also:</B><DD><A HREF=\"../lpsolve/LpSolve.html#putAbortfunc(lpsolve.AbortListener, java.lang.Object)\"><CODE>LpSolve.putAbortfunc(lpsolve.AbortListener, java.lang.Object)</CODE></A>, \n\"lp_solve documentation for 'put_abortfunc'\"</DL>\r\n<HR>\r\n\r\n<P>\r\n<!-- ======== NESTED CLASS SUMMARY ======== -->\r\n\r\n\r\n<!-- =========== FIELD SUMMARY =========== -->\r\n\r\n\r\n<!-- ======== CONSTRUCTOR SUMMARY ======== -->\r\n\r\n\r\n<!-- ========== METHOD SUMMARY =========== -->\r\n\r\n<A NAME=\"method_summary\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Method Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/AbortListener.html#abortfunc(lpsolve.LpSolve, java.lang.Object)\">abortfunc</A></B>(<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>&nbsp;problem,\n          java.lang.Object&nbsp;userhandle)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;When set, the abort routine is called regularly during solve(). \n </TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<P>\r\n\r\n<!-- ============ FIELD DETAIL =========== -->\r\n\r\n\r\n<!-- ========= CONSTRUCTOR DETAIL ======== -->\r\n\r\n\r\n<!-- ============ METHOD DETAIL ========== -->\r\n\r\n<A NAME=\"method_detail\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Method Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"abortfunc(lpsolve.LpSolve, java.lang.Object)\"><!-- --></A><H3>\r\nabortfunc</H3>\r\n<PRE>\r\npublic boolean <B>abortfunc</B>(<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>&nbsp;problem,\n                         java.lang.Object&nbsp;userhandle)\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>When set, the abort routine is called regularly during solve(). \n The user can do whatever he wants in this routine.\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>problem</CODE> - the problem this Listener was defined for<DD><CODE>userhandle</CODE> - the userhandle object that was passed to <code>putAbortfunc</code>\n<DT><B>Returns:</B><DD>if true, then lp_solve aborts the solver and returns with an appropriate code\n<DT><B>Throws:</B>\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<!-- ========= END OF CLASS DATA ========= -->\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV CLASS&nbsp;\r\n&nbsp;<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\"><B>NEXT CLASS</B></A></FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"AbortListener.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/BbListener.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nBbListener (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve.BbListener interface\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"BbListener (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;<A HREF=\"../lpsolve/AbortListener.html\" title=\"interface in lpsolve\"><B>PREV CLASS</B></A>&nbsp;\r\n&nbsp;<A HREF=\"../lpsolve/LogListener.html\" title=\"interface in lpsolve\"><B>NEXT CLASS</B></A></FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"BbListener.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<!-- ======== START OF CLASS DATA ======== -->\r\n<H2>\r\n<FONT SIZE=\"-1\">\r\nlpsolve</FONT>\r\n<BR>\r\nInterface BbListener</H2>\r\n<HR>\r\n<DL>\r\n<DT>public interface <B>BbListener</B></DL>\r\n\r\n<P>\r\nClasses that implement this interface may be passed\n to the <code>putbbBranchfunc</code> and <code>putbbNodefunc</code> method \n of the <code>LpSolve</code> class.\r\n<P>\r\n\r\n<P>\r\n<DL>\r\n<DT><B>Author:</B></DT>\n  <DD>Juergen Ebert</DD>\n<DT><B>See Also:</B><DD><A HREF=\"../lpsolve/LpSolve.html#putBbBranchfunc(lpsolve.BbListener, java.lang.Object)\"><CODE>LpSolve.putBbBranchfunc(lpsolve.BbListener, java.lang.Object)</CODE></A>, \n<A HREF=\"../lpsolve/LpSolve.html#putBbNodefunc(lpsolve.BbListener, java.lang.Object)\"><CODE>LpSolve.putBbNodefunc(lpsolve.BbListener, java.lang.Object)</CODE></A>, \n\"lp_solve documentation for 'put_bb_branchfunc'\", \n\"lp_solve documentation for 'put_bb_nodefunc'\"</DL>\r\n<HR>\r\n\r\n<P>\r\n<!-- ======== NESTED CLASS SUMMARY ======== -->\r\n\r\n\r\n<!-- =========== FIELD SUMMARY =========== -->\r\n\r\n\r\n<!-- ======== CONSTRUCTOR SUMMARY ======== -->\r\n\r\n\r\n<!-- ========== METHOD SUMMARY =========== -->\r\n\r\n<A NAME=\"method_summary\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Method Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/BbListener.html#bbfunc(lpsolve.LpSolve, java.lang.Object, int)\">bbfunc</A></B>(<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>&nbsp;problem,\n       java.lang.Object&nbsp;userhandle,\n       int&nbsp;message)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;TODO: add documentation when available</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<P>\r\n\r\n<!-- ============ FIELD DETAIL =========== -->\r\n\r\n\r\n<!-- ========= CONSTRUCTOR DETAIL ======== -->\r\n\r\n\r\n<!-- ============ METHOD DETAIL ========== -->\r\n\r\n<A NAME=\"method_detail\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Method Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"bbfunc(lpsolve.LpSolve, java.lang.Object, int)\"><!-- --></A><H3>\r\nbbfunc</H3>\r\n<PRE>\r\npublic int <B>bbfunc</B>(<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>&nbsp;problem,\n                  java.lang.Object&nbsp;userhandle,\n                  int&nbsp;message)\n           throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>TODO: add documentation when available\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>problem</CODE> - the problem this Listener was defined for<DD><CODE>userhandle</CODE> - the userhandle object that was passed to <code>putLogfunc</code>\n<DT><B>Throws:</B>\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<!-- ========= END OF CLASS DATA ========= -->\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;<A HREF=\"../lpsolve/AbortListener.html\" title=\"interface in lpsolve\"><B>PREV CLASS</B></A>&nbsp;\r\n&nbsp;<A HREF=\"../lpsolve/LogListener.html\" title=\"interface in lpsolve\"><B>NEXT CLASS</B></A></FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"BbListener.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/LogListener.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nLogListener (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve.LogListener interface\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"LogListener (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\"><B>PREV CLASS</B></A>&nbsp;\r\n&nbsp;<A HREF=\"../lpsolve/MsgListener.html\" title=\"interface in lpsolve\"><B>NEXT CLASS</B></A></FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"LogListener.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<!-- ======== START OF CLASS DATA ======== -->\r\n<H2>\r\n<FONT SIZE=\"-1\">\r\nlpsolve</FONT>\r\n<BR>\r\nInterface LogListener</H2>\r\n<HR>\r\n<DL>\r\n<DT>public interface <B>LogListener</B></DL>\r\n\r\n<P>\r\nClasses that implement this interface may be passed\n to the <code>putLogfunc</code> method of the <code>LpSolve</code> class.\r\n<P>\r\n\r\n<P>\r\n<DL>\r\n<DT><B>Author:</B></DT>\n  <DD>Juergen Ebert</DD>\n<DT><B>See Also:</B><DD><A HREF=\"../lpsolve/LpSolve.html#putLogfunc(lpsolve.LogListener, java.lang.Object)\"><CODE>LpSolve.putLogfunc(lpsolve.LogListener, java.lang.Object)</CODE></A>, \n\"lp_solve documentation for 'put_logfunc'\"</DL>\r\n<HR>\r\n\r\n<P>\r\n<!-- ======== NESTED CLASS SUMMARY ======== -->\r\n\r\n\r\n<!-- =========== FIELD SUMMARY =========== -->\r\n\r\n\r\n<!-- ======== CONSTRUCTOR SUMMARY ======== -->\r\n\r\n\r\n<!-- ========== METHOD SUMMARY =========== -->\r\n\r\n<A NAME=\"method_summary\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Method Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LogListener.html#logfunc(lpsolve.LpSolve, java.lang.Object, java.lang.String)\">logfunc</A></B>(<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>&nbsp;problem,\n        java.lang.Object&nbsp;userhandle,\n        java.lang.String&nbsp;buf)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;When set, the log routine is called when lp_solve has someting \n to report (error conditions or so).</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<P>\r\n\r\n<!-- ============ FIELD DETAIL =========== -->\r\n\r\n\r\n<!-- ========= CONSTRUCTOR DETAIL ======== -->\r\n\r\n\r\n<!-- ============ METHOD DETAIL ========== -->\r\n\r\n<A NAME=\"method_detail\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Method Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"logfunc(lpsolve.LpSolve, java.lang.Object, java.lang.String)\"><!-- --></A><H3>\r\nlogfunc</H3>\r\n<PRE>\r\npublic void <B>logfunc</B>(<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>&nbsp;problem,\n                    java.lang.Object&nbsp;userhandle,\n                    java.lang.String&nbsp;buf)\n             throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>When set, the log routine is called when lp_solve has someting \n to report (error conditions or so).\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>problem</CODE> - the problem this Listener was defined for<DD><CODE>userhandle</CODE> - the userhandle object that was passed to <code>putLogfunc</code><DD><CODE>buf</CODE> - the log message\n<DT><B>Throws:</B>\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<!-- ========= END OF CLASS DATA ========= -->\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\"><B>PREV CLASS</B></A>&nbsp;\r\n&nbsp;<A HREF=\"../lpsolve/MsgListener.html\" title=\"interface in lpsolve\"><B>NEXT CLASS</B></A></FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"LogListener.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/LpSolve.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nLpSolve (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve.LpSolve class\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"LpSolve (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\r\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\r\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\r\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\r\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV CLASS&nbsp;\r\n&nbsp;<A HREF=\"../lpsolve/VersionInfo.html\" title=\"class in lpsolve\"><B>NEXT CLASS</B></A></FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"LpSolve.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\r\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;<A HREF=\"#field_summary\">FIELD</A>&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;<A HREF=\"#field_detail\">FIELD</A>&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\r\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<!-- ======== START OF CLASS DATA ======== -->\r\n<H2>\r\n<FONT SIZE=\"-1\">\r\nlpsolve</FONT>\r\n<BR>\r\nClass LpSolve</H2>\r\n<PRE>\r\njava.lang.Object\r\n  <IMG SRC=\"../resources/inherit.gif\" ALT=\"extended by\"><B>lpsolve.LpSolve</B>\r\n</PRE>\r\n<HR>\r\n<DL>\r\n<DT>public class <B>LpSolve</B><DT>extends java.lang.Object</DL>\r\n\r\n<P>\r\nObject wrapper for a problem structure of the lp_solve library.\r\n Offers access to all lp_solve methods.\r\n<P>\r\n\r\n<P>\r\n<DL>\r\n<DT><B>Author:</B></DT>\r\n  <DD>Juergen Ebert</DD>\r\n</DL>\r\n<HR>\r\n\r\n<P>\r\n<!-- ======== NESTED CLASS SUMMARY ======== -->\r\n\r\n\r\n<!-- =========== FIELD SUMMARY =========== -->\r\n\r\n<A NAME=\"field_summary\"><!-- --></A>\r\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Field Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_BOUNDFLIP\">ANTIDEGEN_BOUNDFLIP</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_COLUMNCHECK\">ANTIDEGEN_COLUMNCHECK</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_DURINGBB\">ANTIDEGEN_DURINGBB</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_DYNAMIC\">ANTIDEGEN_DYNAMIC</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_FIXEDVARS\">ANTIDEGEN_FIXEDVARS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_INFEASIBLE\">ANTIDEGEN_INFEASIBLE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_LOSTFEAS\">ANTIDEGEN_LOSTFEAS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_NONE\">ANTIDEGEN_NONE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_NUMFAILURE\">ANTIDEGEN_NUMFAILURE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_RHSPERTURB\">ANTIDEGEN_RHSPERTURB</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#ANTIDEGEN_STALLING\">ANTIDEGEN_STALLING</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#AUTOMATIC\">AUTOMATIC</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#BRANCH_AUTOMATIC\">BRANCH_AUTOMATIC</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#BRANCH_CEILING\">BRANCH_CEILING</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#BRANCH_FLOOR\">BRANCH_FLOOR</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#BRANCH_DEFAULT\">BRANCH_DEFAULT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#CRASH_MOSTFEASIBLE\">CRASH_MOSTFEASIBLE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#CRASH_NOTHING\">CRASH_NOTHING</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#CRITICAL\">CRITICAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#DATAIGNORED\">DATAIGNORED</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#DEGENERATE\">DEGENERATE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#DETAILED\">DETAILED</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#DYNAMIC\">DYNAMIC</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#EQ\">EQ</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#FALSE\">FALSE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#FEASFOUND\">FEASFOUND</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#FR\">FR</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#FULL\">FULL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVED\">PRESOLVED</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#GE\">GE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#IMPORTANT\">IMPORTANT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#IMPROVE_BBSIMPLEX\">IMPROVE_BBSIMPLEX</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#IMPROVE_DUALFEAS\">IMPROVE_DUALFEAS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#IMPROVE_NONE\">IMPROVE_NONE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#IMPROVE_SOLUTION\">IMPROVE_SOLUTION</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#IMPROVE_THETAGAP\">IMPROVE_THETAGAP</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#INFEASIBLE\">INFEASIBLE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#LE\">LE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_INITPSEUDOCOST\">MSG_INITPSEUDOCOST</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_INVERT\">MSG_INVERT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_ITERATION\">MSG_ITERATION</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_LPBETTER\">MSG_LPBETTER</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_LPEQUAL\">MSG_LPEQUAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_LPFEASIBLE\">MSG_LPFEASIBLE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_LPOPTIMAL\">MSG_LPOPTIMAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_MILPBETTER\">MSG_MILPBETTER</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_MILPEQUAL\">MSG_MILPEQUAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_MILPFEASIBLE\">MSG_MILPFEASIBLE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_MILPOPTIMAL\">MSG_MILPOPTIMAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_MILPSTRATEGY\">MSG_MILPSTRATEGY</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_NONE\">MSG_NONE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_PERFORMANCE\">MSG_PERFORMANCE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#MSG_PRESOLVE\">MSG_PRESOLVE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NEUTRAL\">NEUTRAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NOBFP\">NOBFP</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_AUTOORDER\">NODE_AUTOORDER</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_BRANCHREVERSEMODE\">NODE_BRANCHREVERSEMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_BREADTHFIRSTMODE\">NODE_BREADTHFIRSTMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_DEPTHFIRSTMODE\">NODE_DEPTHFIRSTMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_DYNAMICMODE\">NODE_DYNAMICMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_FIRSTSELECT\">NODE_FIRSTSELECT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_FRACTIONSELECT\">NODE_FRACTIONSELECT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_GAPSELECT\">NODE_GAPSELECT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_GREEDYMODE\">NODE_GREEDYMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_PSEUDOCOSTMODE\">NODE_PSEUDOCOSTMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_PSEUDOCOSTSELECT\">NODE_PSEUDOCOSTSELECT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_PSEUDONONINTSELECT\">NODE_PSEUDONONINTSELECT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_PSEUDORATIOSELECT\">NODE_PSEUDORATIOSELECT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_RANDOMIZEMODE\">NODE_RANDOMIZEMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_RANGESELECT\">NODE_RANGESELECT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_RCOSTFIXING\">NODE_RCOSTFIXING</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_RESTARTMODE\">NODE_RESTARTMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_STRONGINIT\">NODE_STRONGINIT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_USERSELECT\">NODE_USERSELECT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NODE_WEIGHTREVERSEMODE\">NODE_WEIGHTREVERSEMODE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NOFEASFOUND\">NOFEASFOUND</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NOMEMORY\">NOMEMORY</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NORMAL\">NORMAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NOTRUN\">NOTRUN</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#NUMFAILURE\">NUMFAILURE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#OF\">OF</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#OPTIMAL\">OPTIMAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_BOUNDS\">PRESOLVE_BOUNDS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_COLDOMINATE\">PRESOLVE_COLDOMINATE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_COLFIXDUAL\">PRESOLVE_COLFIXDUAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_COLS\">PRESOLVE_COLS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_DUALS\">PRESOLVE_DUALS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_ELIMEQ2\">PRESOLVE_ELIMEQ2</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_IMPLIEDFREE\">PRESOLVE_IMPLIEDFREE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_IMPLIEDSLK\">PRESOLVE_IMPLIEDSLK</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_KNAPSACK\">PRESOLVE_KNAPSACK</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_LINDEP\">PRESOLVE_LINDEP</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_MERGEROWS\">PRESOLVE_MERGEROWS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_NONE\">PRESOLVE_NONE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_PROBEFIX\">PRESOLVE_PROBEFIX</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_PROBEREDUCE\">PRESOLVE_PROBEREDUCE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_REDUCEGCD\">PRESOLVE_REDUCEGCD</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_REDUCEMIP\">PRESOLVE_REDUCEMIP</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_ROWDOMINATE\">PRESOLVE_ROWDOMINATE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_ROWS\">PRESOLVE_ROWS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_SENSDUALS\">PRESOLVE_SENSDUALS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRESOLVE_SOS\">PRESOLVE_SOS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_ADAPTIVE\">PRICE_ADAPTIVE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_AUTOPARTIAL\">PRICE_AUTOPARTIAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_HARRISTWOPASS\">PRICE_HARRISTWOPASS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_HYBRID\">PRICE_HYBRID</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_LOOPALTERNATE\">PRICE_LOOPALTERNATE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_LOOPLEFT\">PRICE_LOOPLEFT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_METHODDEFAULT\">PRICE_METHODDEFAULT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_MULTIPLE\">PRICE_MULTIPLE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_PARTIAL\">PRICE_PARTIAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_PRIMALFALLBACK\">PRICE_PRIMALFALLBACK</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_RANDOMIZE\">PRICE_RANDOMIZE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICE_TRUENORMINIT\">PRICE_TRUENORMINIT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICER_DANTZIG\">PRICER_DANTZIG</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICER_DEVEX\">PRICER_DEVEX</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICER_FIRSTINDEX\">PRICER_FIRSTINDEX</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PRICER_STEEPESTEDGE\">PRICER_STEEPESTEDGE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PROCBREAK\">PROCBREAK</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#PROCFAIL\">PROCFAIL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#RUNNING\">RUNNING</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_COLSONLY\">SCALE_COLSONLY</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_CURTISREID\">SCALE_CURTISREID</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_DYNUPDATE\">SCALE_DYNUPDATE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_EQUILIBRATE\">SCALE_EQUILIBRATE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_EXTREME\">SCALE_EXTREME</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_GEOMETRIC\">SCALE_GEOMETRIC</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_INTEGERS\">SCALE_INTEGERS</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_LINEAR\">SCALE_LINEAR</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_LOGARITHMIC\">SCALE_LOGARITHMIC</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_MEAN\">SCALE_MEAN</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_NONE\">SCALE_NONE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_POWER2\">SCALE_POWER2</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_QUADRATIC\">SCALE_QUADRATIC</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_RANGE\">SCALE_RANGE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_ROWSONLY\">SCALE_ROWSONLY</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SCALE_USERWEIGHT\">SCALE_USERWEIGHT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SEVERE\">SEVERE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SIMPLEX_DEFAULT\">SIMPLEX_DEFAULT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SIMPLEX_DUAL_DUAL\">SIMPLEX_DUAL_DUAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SIMPLEX_DUAL_PRIMAL\">SIMPLEX_DUAL_PRIMAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SIMPLEX_PRIMAL_DUAL\">SIMPLEX_PRIMAL_DUAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SIMPLEX_PRIMAL_PRIMAL\">SIMPLEX_PRIMAL_PRIMAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#SUBOPTIMAL\">SUBOPTIMAL</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#TIMEOUT\">TIMEOUT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#TRUE\">TRUE</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#UNBOUNDED\">UNBOUNDED</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#UNKNOWNERROR\">UNKNOWNERROR</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#USERABORT\">USERABORT</A></B></CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<!-- ======== CONSTRUCTOR SUMMARY ======== -->\r\n\r\n\r\n<!-- ========== METHOD SUMMARY =========== -->\r\n\r\n<A NAME=\"method_summary\"><!-- --></A>\r\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Method Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#addColumn(double[])\">addColumn</A></B>(double[]&nbsp;column)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a column to the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#addColumnex(int, double[], int[])\">addColumnex</A></B>(int&nbsp;count,\r\n            double[]&nbsp;column,\r\n            int[]&nbsp;rowno)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a column to the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#addConstraint(double[], int, double)\">addConstraint</A></B>(double[]&nbsp;row,\r\n              int&nbsp;constrType,\r\n              double&nbsp;rh)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a constraint to the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#addConstraintex(int, double[], int[], int, double)\">addConstraintex</A></B>(int&nbsp;count,\r\n                double[]&nbsp;row,\r\n                int[]&nbsp;colno,\r\n                int&nbsp;constrType,\r\n                double&nbsp;rh)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a constraint to the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#addLagCon(double[], int, double)\">addLagCon</A></B>(double[]&nbsp;row,\r\n          int&nbsp;constrType,\r\n          double&nbsp;rh)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a Lagrangian constraint to the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#addSOS(java.lang.String, int, int, int, int[], double[])\">addSOS</A></B>(java.lang.String&nbsp;name,\r\n       int&nbsp;sostype,\r\n       int&nbsp;priority,\r\n       int&nbsp;count,\r\n       int[]&nbsp;sosvars,\r\n       double[]&nbsp;weights)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a SOS constraint.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#columnInLp(double[])\">columnInLp</A></B>(double[]&nbsp;column)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Check if a column is already present in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A></CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#copyLp()\">copyLp</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Copy an existing lprec structure to a new lprec structure.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#defaultBasis()\">defaultBasis</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets the starting base to an all slack basis (the default simplex starting basis).</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#delColumn(int)\">delColumn</A></B>(int&nbsp;columnnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Remove a column from the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#delConstraint(int)\">delConstraint</A></B>(int&nbsp;rownr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Remove a constraint from the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#deleteLp()\">deleteLp</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Frees all resources allocated to this problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#dualizeLp()\">dualizeLp</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Create the dual of the current model.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>protected &nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#finalize()\">finalize</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getAntiDegen()\">getAntiDegen</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the used degeneracy rule.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getBasis(int[], boolean)\">getBasis</A></B>(int[]&nbsp;bascolumn,\r\n         boolean&nbsp;nonbasic)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the basis of the lp.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getBasiscrash()\">getBasiscrash</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns which basis crash mode must be used.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getBbDepthlimit()\">getBbDepthlimit</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the maximum branch-and-bound depth.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getBbFloorfirst()\">getBbFloorfirst</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns which branch to take first in branch-and-bound algorithm.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getBbRule()\">getBbRule</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the branch-and-bound rule.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getBoundsTighter()\">getBoundsTighter</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if set bounds may only be tighter or also less restrictive.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getBreakAtValue()\">getBreakAtValue</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value at which the branch-and-bound algorithm stops\r\n when the object value is better than this value.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;java.lang.String</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getColName(int)\">getColName</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the name of a column in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getColumn(int, double[])\">getColumn</A></B>(int&nbsp;colnr,\r\n          double[]&nbsp;column)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get all column elements from the matrix.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getColumnex(int, double[], int[])\">getColumnex</A></B>(int&nbsp;colnr,\r\n            double[]&nbsp;column,\r\n            int[]&nbsp;nzrows)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the non-zero column elements from the matrix.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getConstraints(double[])\">getConstraints</A></B>(double[]&nbsp;var)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the values of the constraints.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;short</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getConstrType(int)\">getConstrType</A></B>(int&nbsp;rownr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the type of a constraint.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getConstrValue(int, int, double[], int[])\">getConstrValue</A></B>(int&nbsp;rownr,\r\n               int&nbsp;count,\r\n               double[]&nbsp;primsolution,\r\n               int[]&nbsp;nzindex)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the value of a constraint according to provided variable values.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getDualSolution(double[])\">getDualSolution</A></B>(double[]&nbsp;duals)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the constraints and the variables.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getEpsb()\">getEpsb</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value that is used as a tolerance for the Right Hand Side (RHS)\r\n to determine whether a value should be considered as 0.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getEpsd()\">getEpsd</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value that is used as a tolerance for the reduced costs\r\n to determine whether a value should be considered as 0.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getEpsel()\">getEpsel</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value that is used as a tolerance for rounding values to zero.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getEpsint()\">getEpsint</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the tolerance that is used to determine whether a floating-point\r\n number is in fact an integer</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getEpsperturb()\">getEpsperturb</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value that is used as perturbation scalar for degenerative problems.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getEpspivot()\">getEpspivot</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value that is used as a tolerance pivot element to determine\r\n whether a value should be considered as 0.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getImprove()\">getImprove</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the iterative improvement level.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getInfinite()\">getInfinite</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value of \"infinite\".</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getLambda(double[])\">getLambda</A></B>(double[]&nbsp;lambda)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the Lamdba vectors (Lagrangian optimization).\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getLowbo(int)\">getLowbo</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the lower bound of a variable.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;long</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getLp()\">getLp</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Return the value of the lp attribute.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getLpIndex(int)\">getLpIndex</A></B>(int&nbsp;index)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the index in the lp of the original row/column.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;java.lang.String</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getLpName()\">getLpName</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the name of the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getLrows()\">getLrows</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the number of Lagrangian rows in the lp.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getMat(int, int)\">getMat</A></B>(int&nbsp;row,\r\n       int&nbsp;column)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get a single element from the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getMaxLevel()\">getMaxLevel</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the deepest Branch-and-bound level of the last solution.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getMaxpivot()\">getMaxpivot</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the maximum number of pivots between a reinversion of the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getMipGap(boolean)\">getMipGap</A></B>(boolean&nbsp;absolute)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the MIP gap value.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getNameindex(java.lang.String, boolean)\">getNameindex</A></B>(java.lang.String&nbsp;name,\r\n             boolean&nbsp;isRow)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the index of a given column or row name in the lp.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getNcolumns()\">getNcolumns</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the number of columns (variables) in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getNegrange()\">getNegrange</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the negative value below which variables are split\r\n into a negative and a positive part.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getNonzeros()\">getNonzeros</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the number of non-zero elements in the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getNorigColumns()\">getNorigColumns</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the number of original columns (variables) in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getNorigRows()\">getNorigRows</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the number of original rows (constraints) in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getNrows()\">getNrows</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the number of rows (constraints) in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getObjBound()\">getObjBound</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns initial \"at least better than\" guess for objective function.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getObjective()\">getObjective</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value of the objective function.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;java.lang.String</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getOrigcolName(int)\">getOrigcolName</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the name of a column in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getOrigIndex(int)\">getOrigIndex</A></B>(int&nbsp;index)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the original row/column where a constraint/variable was before presolve.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;java.lang.String</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getOrigrowName(int)\">getOrigrowName</A></B>(int&nbsp;rownr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the name of a constraint (row) in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPivoting()\">getPivoting</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the pivot rule.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPresolve()\">getPresolve</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the current presolve setting.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPresolveloops()\">getPresolveloops</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the number of times presolve is done.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPrimalSolution(double[])\">getPrimalSolution</A></B>(double[]&nbsp;pv)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the solution of the model.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPrintSol()\">getPrintSol</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns a flag if all intermediate valid solutions must be printed while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrColumn(int)\">getPtrColumn</A></B>(int&nbsp;columnrnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get all column elements from the matrix.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrConstraints()\">getPtrConstraints</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the values of the constraints.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrDualSolution()\">getPtrDualSolution</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the constraints and the variables.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrLambda()\">getPtrLambda</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the Lamdba vectors (Lagrangian optimization).\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrPrimalSolution()\">getPtrPrimalSolution</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the solution of the model.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrRow(int)\">getPtrRow</A></B>(int&nbsp;rownr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get all row elements from the matrix.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[][]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrSensitivityObj()\">getPtrSensitivityObj</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the objective function.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[][]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrSensitivityObjex()\">getPtrSensitivityObjex</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the objective function.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[][]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrSensitivityRhs()\">getPtrSensitivityRhs</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the constraints and the variables.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double[]</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getPtrVariables()\">getPtrVariables</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the values of the variables.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getRh(int)\">getRh</A></B>(int&nbsp;row)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the value of the right hand side (RHS) vector (column 0) for one row.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getRhRange(int)\">getRhRange</A></B>(int&nbsp;rownr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the range on a constraint.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getRow(int, double[])\">getRow</A></B>(int&nbsp;rownr,\r\n       double[]&nbsp;row)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get all row elements from the matrix.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getRowex(int, double[], int[])\">getRowex</A></B>(int&nbsp;rownr,\r\n         double[]&nbsp;row,\r\n         int[]&nbsp;nzcols)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the non-zero row elements from the matrix.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;java.lang.String</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getRowName(int)\">getRowName</A></B>(int&nbsp;rownr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the name of a constraint (row) in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getScalelimit()\">getScalelimit</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the relative scaling convergence criterion for the active scaling mode;\r\n the integer part specifies the maximum number of iterations.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getScaling()\">getScaling</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies which scaling algorithm is used.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getSensitivityObj(double[], double[])\">getSensitivityObj</A></B>(double[]&nbsp;objfrom,\r\n                  double[]&nbsp;objtill)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the objective function.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getSensitivityObjex(double[], double[], double[], double[])\">getSensitivityObjex</A></B>(double[]&nbsp;objfrom,\r\n                    double[]&nbsp;objtill,\r\n                    double[]&nbsp;objfromvalue,\r\n                    double[]&nbsp;objtillvalue)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the objective function.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getSensitivityRhs(double[], double[], double[])\">getSensitivityRhs</A></B>(double[]&nbsp;duals,\r\n                  double[]&nbsp;dualsfrom,\r\n                  double[]&nbsp;dualstill)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the constraints and the variables.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getSimplextype()\">getSimplextype</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the desired combination of primal and dual simplex algorithms.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getSolutioncount()\">getSolutioncount</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the number of equal solutions.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getSolutionlimit()\">getSolutionlimit</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the solution number that must be returned.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getStatus()\">getStatus</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns an extra status after a call to a function.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;java.lang.String</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getStatustext(int)\">getStatustext</A></B>(int&nbsp;statuscode)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the description of a returncode of the solve function.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;long</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getTimeout()\">getTimeout</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the timout.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;long</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getTotalIter()\">getTotalIter</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the total number of iterations with Branch-and-bound of the last solution.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;long</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getTotalNodes()\">getTotalNodes</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the total number of nodes processed in branch-and-bound.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getUpbo(int)\">getUpbo</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the upper bound of a variable.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getVarBranch(int)\">getVarBranch</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns, for the specified variable, which branch to take first\r\n in branch-and-bound algorithm.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getVarDualresult(int)\">getVarDualresult</A></B>(int&nbsp;index)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the sensitivity of the constraints and the variables.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getVariables(double[])\">getVariables</A></B>(double[]&nbsp;var)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the values of the variables.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getVarPrimalresult(int)\">getVarPrimalresult</A></B>(int&nbsp;index)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the solution of the model.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getVarPriority(int)\">getVarPriority</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns, for the specified variable, the priority the variable has\r\n in the branch-and-bound algorithm.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getVerbose()\">getVerbose</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the verbose level.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#getWorkingObjective()\">getWorkingObjective</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the value of the objective function.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#guessBasis(double[], int[])\">guessBasis</A></B>(double[] guessvector,&nbsp;int[] basisvector)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Guess a basis for the lp.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#hasBFP()\">hasBFP</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if there is a basis factorization package (BFP) available.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#hasXLI()\">hasXLI</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if there is an external language interface (XLI) set.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isAddRowmode()\">isAddRowmode</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns a flag which of the add routines perform best.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isAntiDegen(int)\">isAntiDegen</A></B>(int&nbsp;testmask)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if the degeneracy rule specified in testmask is active.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isBinary(int)\">isBinary</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the type of the variable. </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isBreakAtFirst()\">isBreakAtFirst</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if the branch-and-bound algorithm stops at first found solution.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isConstrType(int, int)\">isConstrType</A></B>(int&nbsp;row,\r\n             int&nbsp;mask)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if constraint type specified in mask is active.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isDebug()\">isDebug</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns a flag if all intermediate results and the branch-and-bound decisions\r\n must be printed while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isFeasible(double[], double)\">isFeasible</A></B>(double[]&nbsp;values,\r\n           double&nbsp;threshold)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Checks if provided solution is a feasible solution.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isInfinite(double)\">isInfinite</A></B>(double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Checks if the provided absolute of the value is larger or equal to \"infinite\".</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isInt(int)\">isInt</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the type of the variable. </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isIntegerscaling()\">isIntegerscaling</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies which scaling algorithm is used.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isLagTrace()\">isLagTrace</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns a flag if Lagrangian progression must be printed while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isMaxim()\">isMaxim</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns objective function direction.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isNativeBFP()\">isNativeBFP</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if the native (build-in) basis factorization package (BFP) is used,\r\n or an external package.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isNativeXLI()\">isNativeXLI</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if a build-in External Language Interfaces (XLI) is available or not.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isNegative(int)\">isNegative</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if the variable is negative.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isPivMode(int)\">isPivMode</A></B>(int&nbsp;testmask)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if pivot strategy specified in testmask is active.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isPivRule(int)\">isPivRule</A></B>(int&nbsp;rule)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Checks if the specified pivot rule is active.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isPresolve(int)\">isPresolve</A></B>(int&nbsp;testmask)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if presolve level specified in testmask is active.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isScalemode(int)\">isScalemode</A></B>(int&nbsp;testmask)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if scaling mode specified in testmask is active.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isScaletype(int)\">isScaletype</A></B>(int&nbsp;scaletype)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if scaling type specified in scaletype is active.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isSemicont(int)\">isSemicont</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Get the type of the variable. semi-continious or not.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isSOSVar(int)\">isSOSVar</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if the variable is SOS or not.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isTrace()\">isTrace</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns a flag if pivot selection must be printed while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isUnbounded(int)\">isUnbounded</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if the variable is free.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#isUseNames(boolean)\">isUseNames</A></B>(boolean&nbsp;isRow)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns if variable or constraint names are used.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;<A HREF=\"../lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A></CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#lpSolveVersion()\">lpSolveVersion</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Returns the full version number of the underlying lp_solve library.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A></CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#makeLp(int, int)\">makeLp</A></B>(int&nbsp;rows,\r\n       int&nbsp;columns)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Creates a new problem. </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printConstraints(int)\">printConstraints</A></B>(int&nbsp;columns)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prints the values of the constraints of the lp.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printDebugdump(java.lang.String)\">printDebugdump</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Do a generic readable data dump of key lp_solve model variables;\r\n principally for run difference and debugging purposes.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printDuals()\">printDuals</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prints the values of the duals of the lp.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printLp()\">printLp</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prints the lp model. </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printObjective()\">printObjective</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prints the objective value of the lp.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printScales()\">printScales</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prints the scales of the lp.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printSolution(int)\">printSolution</A></B>(int&nbsp;columns)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prints the solution (variables) of the lp.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printStr(java.lang.String)\">printStr</A></B>(java.lang.String&nbsp;str)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prints a string.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#printTableau()\">printTableau</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Prints the tableau.\r\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#putAbortfunc(lpsolve.AbortListener, java.lang.Object)\">putAbortfunc</A></B>(<A HREF=\"../lpsolve/AbortListener.html\" title=\"interface in lpsolve\">AbortListener</A>&nbsp;listener,\r\n             java.lang.Object&nbsp;userhandle)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Register an <code>AbortListener</code> for callback.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#putBbBranchfunc(lpsolve.BbListener, java.lang.Object)\">putBbBranchfunc</A></B>(<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\">BbListener</A>&nbsp;listener,\r\n                java.lang.Object&nbsp;userhandle)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Register an <code>BbBranchListener</code> for callback.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#putBbNodefunc(lpsolve.BbListener, java.lang.Object)\">putBbNodefunc</A></B>(<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\">BbListener</A>&nbsp;listener,\r\n              java.lang.Object&nbsp;userhandle)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Register an <code>BbNodeListener</code> for callback.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#putLogfunc(lpsolve.LogListener, java.lang.Object)\">putLogfunc</A></B>(<A HREF=\"../lpsolve/LogListener.html\" title=\"interface in lpsolve\">LogListener</A>&nbsp;listener,\r\n           java.lang.Object&nbsp;userhandle)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Register an <code>LogListener</code> for callback.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#putMsgfunc(lpsolve.MsgListener, java.lang.Object, int)\">putMsgfunc</A></B>(<A HREF=\"../lpsolve/MsgListener.html\" title=\"interface in lpsolve\">MsgListener</A>&nbsp;listener,\r\n           java.lang.Object&nbsp;userhandle,\r\n           int&nbsp;mask)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Register an <code>MsgListener</code> for callback.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;java.lang.String</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#readBasis(java.lang.String)\">readBasis</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Read basis from a file and set as default basis. </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A></CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#readFreeMps(java.lang.String, int)\">readFreeMps</A></B>(java.lang.String&nbsp;filename,\r\n            int&nbsp;verbose)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Read a model in free MPS format from file and create a new problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A></CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#readLp(java.lang.String, int, java.lang.String)\">readLp</A></B>(java.lang.String&nbsp;filename,\r\n       int&nbsp;verbose,\r\n       java.lang.String&nbsp;lpName)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Read an lp model from file and create a new problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A></CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#readMps(java.lang.String, int)\">readMps</A></B>(java.lang.String&nbsp;filename,\r\n        int&nbsp;verbose)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Read an mps model from file and create a new problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#readParams(java.lang.String, java.lang.String)\">readParams</A></B>(java.lang.String&nbsp;filename,\r\n           java.lang.String&nbsp;options)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Read settings from a parameter file.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>static&nbsp;<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A></CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#readXLI(java.lang.String, java.lang.String, java.lang.String, java.lang.String, int)\">readXLI</A></B>(java.lang.String&nbsp;xliname,\r\n        java.lang.String&nbsp;modelname,\r\n        java.lang.String&nbsp;dataname,\r\n        java.lang.String&nbsp;options,\r\n        int&nbsp;verbose)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Read a model via the External Language Interface and create a new problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#resetBasis()\">resetBasis</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Resets the basis to the initial basis.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#resetParams()\">resetParams</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Resets parameters back to their default values.</TD>\r\n</TR>\r\n\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#resizeLp(int, int)\">resizeLp</A></B>(int&nbsp;rows,\r\n             int&nbsp;columns)</CODE>\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Allocate memory for the specified size.</TD>\r\n</TR>\r\n\r\n\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;boolean</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setAddRowmode(boolean)\">setAddRowmode</A></B>(boolean&nbsp;turnon)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies which add routine performs best.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setAntiDegen(int)\">setAntiDegen</A></B>(int&nbsp;antiDegen)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies if special handling must be done to reduce degeneracy/cycling while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBasis(int[], boolean)\">setBasis</A></B>(int[]&nbsp;bascolumn,\r\n         boolean&nbsp;nonbasic)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets an initial basis of the lp.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBasiscrash(int)\">setBasiscrash</A></B>(int&nbsp;mode)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies which basis crash mode must be used.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBasisvar(int, int)\">setBasisvar</A></B>(int&nbsp;basisPos,\r\n            int&nbsp;enteringCol)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;This is an internal function that has been published for special purposes. It should generally not be used.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBbDepthlimit(int)\">setBbDepthlimit</A></B>(int&nbsp;bbMaxlevel)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets the maximum branch-and-bound depth.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBbFloorfirst(int)\">setBbFloorfirst</A></B>(int&nbsp;floorFirst)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies which branch to take first in branch-and-bound algorithm.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBbRule(int)\">setBbRule</A></B>(int&nbsp;bbRule)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the branch-and-bound rule.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBFP(java.lang.String)\">setBFP</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set basis factorization package.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBinary(int, boolean)\">setBinary</A></B>(int&nbsp;colnr,\r\n          boolean&nbsp;mustBeBin)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the type of the variable. </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBounds(int, double, double)\">setBounds</A></B>(int&nbsp;colnr,\r\n          double&nbsp;lower,\r\n          double&nbsp;upper)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the upper and lower bound of a variable.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBoundsTighter(boolean)\">setBoundsTighter</A></B>(boolean&nbsp;tighten)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies if set bounds may only be tighter or also less restrictive.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBreakAtFirst(boolean)\">setBreakAtFirst</A></B>(boolean&nbsp;breakAtFirst)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies if the branch-and-bound algorithm stops at first found solution.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setBreakAtValue(double)\">setBreakAtValue</A></B>(double&nbsp;breakAtValue)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies if the branch-and-bound algorithm stops when the object value\r\n is better than a given value.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setColName(int, java.lang.String)\">setColName</A></B>(int&nbsp;colnr,\r\n           java.lang.String&nbsp;name)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the name of a column in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setColumn(int, double[])\">setColumn</A></B>(int&nbsp;colno,\r\n          double[]&nbsp;column)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set a column in the lp.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setColumnex(int, int, double[], int[])\">setColumnex</A></B>(int&nbsp;colno,\r\n            int&nbsp;count,\r\n            double[]&nbsp;column,\r\n            int[]&nbsp;rowno)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set a column in the lp.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setConstrType(int, int)\">setConstrType</A></B>(int&nbsp;rownr,\r\n              int&nbsp;constrType)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the type of a constraint.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setDebug(boolean)\">setDebug</A></B>(boolean&nbsp;debug)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets a flag if all intermediate results and the branch-and-bound decisions\r\n must be printed while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setEpsb(double)\">setEpsb</A></B>(double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the value that is used as a tolerance for the Right Hand Side (RHS)\r\n to determine whether a value should be considered as 0</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setEpsd(double)\">setEpsd</A></B>(double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the value that is used as a tolerance for reduced costs\r\n to determine whether a value should be considered as 0.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setEpsel(double)\">setEpsel</A></B>(double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the value that is used as a tolerance for rounding values to zero.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setEpsint(double)\">setEpsint</A></B>(double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the tolerance that is used to determine whether a floating-point\r\n number is in fact an integer.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setEpslevel(int)\">setEpslevel</A></B>(int&nbsp;epslevel)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;This is a simplified way of specifying multiple eps thresholds that are \"logically\" consistent.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setEpsperturb(double)\">setEpsperturb</A></B>(double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the value that is used as perturbation scalar for degenerative problems.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setEpspivot(double)\">setEpspivot</A></B>(double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the value that is used as a tolerance pivot element to determine\r\n whether a value should be considered as 0.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setImprove(int)\">setImprove</A></B>(int&nbsp;improve)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the iterative improvement level.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setInfinite(double)\">setInfinite</A></B>(double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the practical value for \"infinite\".</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setInt(int, boolean)\">setInt</A></B>(int&nbsp;colnr,\r\n       boolean&nbsp;mustBeInteger)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the type of the variable. </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setLagTrace(boolean)\">setLagTrace</A></B>(boolean&nbsp;lagTrace)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets a flag if Lagrangian progression must be printed while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setLowbo(int, double)\">setLowbo</A></B>(int&nbsp;colnr,\r\n         double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the lower bound of a variable.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setLpName(java.lang.String)\">setLpName</A></B>(java.lang.String&nbsp;name)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the name of the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setMat(int, int, double)\">setMat</A></B>(int&nbsp;row,\r\n       int&nbsp;column,\r\n       double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set a single element in the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setMaxim()\">setMaxim</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set objective function to maximize.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setMaxpivot(int)\">setMaxpivot</A></B>(int&nbsp;maxNumInv)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets the maximum number of pivots between a reinversion of the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setMinim()\">setMinim</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set objective function to minimize.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setMipGap(boolean, double)\">setMipGap</A></B>(boolean&nbsp;absolute,\r\n          double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the MIP gap value.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setNegrange(double)\">setNegrange</A></B>(double&nbsp;negRange)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set negative value below which variables are split into a negative\r\n and a positive part.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setObj(int, double)\">setObj</A></B>(int&nbsp;column,\r\n       double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the objective function (row 0) of the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setObjBound(double)\">setObjBound</A></B>(double&nbsp;objBound)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set initial \"at least better than\" guess for objective function.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setObjFn(double[])\">setObjFn</A></B>(double[]&nbsp;row)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the objective function (row 0) of the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setObjFnex(int, double[], int[])\">setObjFnex</A></B>(int&nbsp;count,\r\n           double[]&nbsp;row,\r\n           int[]&nbsp;colno)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the objective function (row 0) of the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setOutputfile(java.lang.String)\">setOutputfile</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Defines the output for the print_* functions.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setPivoting(int)\">setPivoting</A></B>(int&nbsp;pivRule)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies the pivot rule.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setPreferdual(boolean)\">setPreferdual</A></B>(boolean&nbsp;dodual)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets the desired combination of primal and dual simplex algorithms.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setPresolve(int, int)\">setPresolve</A></B>(int&nbsp;doPresolve,\r\n            int&nbsp;maxloops)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies if a presolve must be done before solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setPrintSol(int)\">setPrintSol</A></B>(int&nbsp;printSol)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets a flag if all intermediate valid solutions must be printed while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setRh(int, double)\">setRh</A></B>(int&nbsp;row,\r\n      double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the value of the right hand side (RHS) vector (column 0) for one row.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setRhRange(int, double)\">setRhRange</A></B>(int&nbsp;rownr,\r\n           double&nbsp;range)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the range on a constraint.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setRhVec(double[])\">setRhVec</A></B>(double[]&nbsp;rh)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the right hand side (RHS) vector (column 0).</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setRow(int, double[])\">setRow</A></B>(int&nbsp;rowno,\r\n       double[]&nbsp;row)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set a constraint in the lp.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setRowex(int, int, double[], int[])\">setRowex</A></B>(int&nbsp;rowno,\r\n         int&nbsp;count,\r\n         double[]&nbsp;row,\r\n         int[]&nbsp;colno)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set a constraint in the lp.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setRowName(int, java.lang.String)\">setRowName</A></B>(int&nbsp;rownr,\r\n           java.lang.String&nbsp;name)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the name of a constraint (row) in the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setScalelimit(double)\">setScalelimit</A></B>(double&nbsp;scalelimit)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets the relative scaling convergence criterion for the active scaling mode;\r\n the integer part specifies the maximum number of iterations.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setScaling(int)\">setScaling</A></B>(int&nbsp;scalemode)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies which scaling algorithm must be used.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setSemicont(int, boolean)\">setSemicont</A></B>(int&nbsp;colnr,\r\n            boolean&nbsp;mustBeSc)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the type of the variable. semi-continious or not.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setSense(boolean)\">setSense</A></B>(boolean&nbsp;maximize)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set objective function sense.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setSimplextype(int)\">setSimplextype</A></B>(int&nbsp;simplextype)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets the desired combination of primal and dual simplex algorithms.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setSolutionlimit(int)\">setSolutionlimit</A></B>(int&nbsp;limit)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets the solution number that must be returned.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setTimeout(long)\">setTimeout</A></B>(long&nbsp;timeout)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set a timeout.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setTrace(boolean)\">setTrace</A></B>(boolean&nbsp;trace)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets a flag if pivot selection must be printed while solving.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setUnbounded(int)\">setUnbounded</A></B>(int&nbsp;colnr)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets if the variable is free.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setUpbo(int, double)\">setUpbo</A></B>(int&nbsp;colnr,\r\n        double&nbsp;value)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the upper bound of a variable.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setUseNames(boolean, boolean)\">setUseNames</A></B>(boolean&nbsp;isRow,\r\n            boolean&nbsp;useNames)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Sets if variable or constraint names are used.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setVarBranch(int, int)\">setVarBranch</A></B>(int&nbsp;colnr,\r\n             int&nbsp;branchMode)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Specifies, for the specified variable, which branch to take first\r\n in branch-and-bound algorithm.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setVarWeights(double[])\">setVarWeights</A></B>(double[]&nbsp;weights)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the weights on variables.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setVerbose(int)\">setVerbose</A></B>(int&nbsp;verbose)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the verbose level.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#setXLI(java.lang.String)\">setXLI</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set External Language Interfaces package.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#solve()\">solve</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Solve the model.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#strAddColumn(java.lang.String)\">strAddColumn</A></B>(java.lang.String&nbsp;column)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a column to the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#strAddConstraint(java.lang.String, int, double)\">strAddConstraint</A></B>(java.lang.String&nbsp;row,\r\n                 int&nbsp;constrType,\r\n                 double&nbsp;rh)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a constraint to the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#strAddLagCon(java.lang.String, int, double)\">strAddLagCon</A></B>(java.lang.String&nbsp;row,\r\n             int&nbsp;constrType,\r\n             double&nbsp;rh)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Add a Lagrangian constraint to the problem.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#strSetObjFn(java.lang.String)\">strSetObjFn</A></B>(java.lang.String&nbsp;row)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the objective function (row 0) of the matrix.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#strSetRhVec(java.lang.String)\">strSetRhVec</A></B>(java.lang.String&nbsp;rh)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Set the right hand side (RHS) vector (column 0).</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;double</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#timeElapsed()\">timeElapsed</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Gets the time elapsed since start of solve.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#unscale()\">unscale</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Unscales the model.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#writeBasis(java.lang.String)\">writeBasis</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Writes current basis to a file.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#writeFreeMps(java.lang.String)\">writeFreeMps</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Write a model in free MPS format to a file.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#writeLp(java.lang.String)\">writeLp</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Write an lp model to a file.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#writeMps(java.lang.String)\">writeMps</A></B>(java.lang.String&nbsp;filename)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Write an mps model to a file.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#writeParams(java.lang.String, java.lang.String)\">writeParams</A></B>(java.lang.String&nbsp;filename,\r\n            java.lang.String&nbsp;options)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Write settings to a parameter file.\r\n</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolve.html#writeXLI(java.lang.String, java.lang.String, boolean)\">writeXLI</A></B>(java.lang.String&nbsp;filename,\r\n         java.lang.String&nbsp;options,\r\n         boolean&nbsp;results)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Write a model to a file via the External Language Interface.</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;<A NAME=\"methods_inherited_from_class_java.lang.Object\"><!-- --></A>\r\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#EEEEFF\" CLASS=\"TableSubHeadingColor\">\r\n<TD><B>Methods inherited from class java.lang.Object</B></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD><CODE>clone, equals, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait</CODE></TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<P>\r\n\r\n<!-- ============ FIELD DETAIL =========== -->\r\n\r\n<A NAME=\"field_detail\"><!-- --></A>\r\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Field Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"FALSE\"><!-- --></A><H3>\r\nFALSE</H3>\r\n<PRE>\r\npublic static final int <B>FALSE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.FALSE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"TRUE\"><!-- --></A><H3>\r\nTRUE</H3>\r\n<PRE>\r\npublic static final int <B>TRUE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.TRUE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"AUTOMATIC\"><!-- --></A><H3>\r\nAUTOMATIC</H3>\r\n<PRE>\r\npublic static final int <B>AUTOMATIC</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.AUTOMATIC\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"DYNAMIC\"><!-- --></A><H3>\r\nDYNAMIC</H3>\r\n<PRE>\r\npublic static final int <B>DYNAMIC</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.DYNAMIC\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"FR\"><!-- --></A><H3>\r\nFR</H3>\r\n<PRE>\r\npublic static final int <B>FR</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.FR\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"LE\"><!-- --></A><H3>\r\nLE</H3>\r\n<PRE>\r\npublic static final int <B>LE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.LE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"GE\"><!-- --></A><H3>\r\nGE</H3>\r\n<PRE>\r\npublic static final int <B>GE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.GE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"EQ\"><!-- --></A><H3>\r\nEQ</H3>\r\n<PRE>\r\npublic static final int <B>EQ</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.EQ\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"OF\"><!-- --></A><H3>\r\nOF</H3>\r\n<PRE>\r\npublic static final int <B>OF</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.OF\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SIMPLEX_PRIMAL_PRIMAL\"><!-- --></A><H3>\r\nSIMPLEX_PRIMAL_PRIMAL</H3>\r\n<PRE>\r\npublic static final int <B>SIMPLEX_PRIMAL_PRIMAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SIMPLEX_PRIMAL_PRIMAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SIMPLEX_DUAL_PRIMAL\"><!-- --></A><H3>\r\nSIMPLEX_DUAL_PRIMAL</H3>\r\n<PRE>\r\npublic static final int <B>SIMPLEX_DUAL_PRIMAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SIMPLEX_DUAL_PRIMAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SIMPLEX_PRIMAL_DUAL\"><!-- --></A><H3>\r\nSIMPLEX_PRIMAL_DUAL</H3>\r\n<PRE>\r\npublic static final int <B>SIMPLEX_PRIMAL_DUAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SIMPLEX_PRIMAL_DUAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SIMPLEX_DUAL_DUAL\"><!-- --></A><H3>\r\nSIMPLEX_DUAL_DUAL</H3>\r\n<PRE>\r\npublic static final int <B>SIMPLEX_DUAL_DUAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SIMPLEX_DUAL_DUAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SIMPLEX_DEFAULT\"><!-- --></A><H3>\r\nSIMPLEX_DEFAULT</H3>\r\n<PRE>\r\npublic static final int <B>SIMPLEX_DEFAULT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SIMPLEX_DEFAULT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_NONE\"><!-- --></A><H3>\r\nPRESOLVE_NONE</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_NONE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_NONE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_ROWS\"><!-- --></A><H3>\r\nPRESOLVE_ROWS</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_ROWS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_ROWS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_COLS\"><!-- --></A><H3>\r\nPRESOLVE_COLS</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_COLS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_COLS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_LINDEP\"><!-- --></A><H3>\r\nPRESOLVE_LINDEP</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_LINDEP</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_LINDEP\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_SOS\"><!-- --></A><H3>\r\nPRESOLVE_SOS</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_SOS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_SOS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_REDUCEMIP\"><!-- --></A><H3>\r\nPRESOLVE_REDUCEMIP</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_REDUCEMIP</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_REDUCEMIP\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_KNAPSACK\"><!-- --></A><H3>\r\nPRESOLVE_KNAPSACK</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_KNAPSACK</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_KNAPSACK\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_ELIMEQ2\"><!-- --></A><H3>\r\nPRESOLVE_ELIMEQ2</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_ELIMEQ2</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_ELIMEQ2\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_IMPLIEDFREE\"><!-- --></A><H3>\r\nPRESOLVE_IMPLIEDFREE</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_IMPLIEDFREE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_IMPLIEDFREE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_REDUCEGCD\"><!-- --></A><H3>\r\nPRESOLVE_REDUCEGCD</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_REDUCEGCD</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_REDUCEGCD\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_PROBEFIX\"><!-- --></A><H3>\r\nPRESOLVE_PROBEFIX</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_PROBEFIX</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_PROBEFIX\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_PROBEREDUCE\"><!-- --></A><H3>\r\nPRESOLVE_PROBEREDUCE</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_PROBEREDUCE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_PROBEREDUCE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_ROWDOMINATE\"><!-- --></A><H3>\r\nPRESOLVE_ROWDOMINATE</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_ROWDOMINATE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_ROWDOMINATE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_COLDOMINATE\"><!-- --></A><H3>\r\nPRESOLVE_COLDOMINATE</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_COLDOMINATE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_COLDOMINATE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_MERGEROWS\"><!-- --></A><H3>\r\nPRESOLVE_MERGEROWS</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_MERGEROWS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_MERGEROWS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_IMPLIEDSLK\"><!-- --></A><H3>\r\nPRESOLVE_IMPLIEDSLK</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_IMPLIEDSLK</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_IMPLIEDSLK\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_COLFIXDUAL\"><!-- --></A><H3>\r\nPRESOLVE_COLFIXDUAL</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_COLFIXDUAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_COLFIXDUAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_BOUNDS\"><!-- --></A><H3>\r\nPRESOLVE_BOUNDS</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_BOUNDS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_BOUNDS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_DUALS\"><!-- --></A><H3>\r\nPRESOLVE_DUALS</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_DUALS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_DUALS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVE_SENSDUALS\"><!-- --></A><H3>\r\nPRESOLVE_SENSDUALS</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVE_SENSDUALS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVE_SENSDUALS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"CRASH_NOTHING\"><!-- --></A><H3>\r\nCRASH_NOTHING</H3>\r\n<PRE>\r\npublic static final int <B>CRASH_NOTHING</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.CRASH_NOTHING\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"CRASH_MOSTFEASIBLE\"><!-- --></A><H3>\r\nCRASH_MOSTFEASIBLE</H3>\r\n<PRE>\r\npublic static final int <B>CRASH_MOSTFEASIBLE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.CRASH_MOSTFEASIBLE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_NONE\"><!-- --></A><H3>\r\nANTIDEGEN_NONE</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_NONE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_NONE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_FIXEDVARS\"><!-- --></A><H3>\r\nANTIDEGEN_FIXEDVARS</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_FIXEDVARS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_FIXEDVARS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_COLUMNCHECK\"><!-- --></A><H3>\r\nANTIDEGEN_COLUMNCHECK</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_COLUMNCHECK</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_COLUMNCHECK\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_STALLING\"><!-- --></A><H3>\r\nANTIDEGEN_STALLING</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_STALLING</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_STALLING\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_NUMFAILURE\"><!-- --></A><H3>\r\nANTIDEGEN_NUMFAILURE</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_NUMFAILURE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_NUMFAILURE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_LOSTFEAS\"><!-- --></A><H3>\r\nANTIDEGEN_LOSTFEAS</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_LOSTFEAS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_LOSTFEAS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_INFEASIBLE\"><!-- --></A><H3>\r\nANTIDEGEN_INFEASIBLE</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_INFEASIBLE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_INFEASIBLE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_DYNAMIC\"><!-- --></A><H3>\r\nANTIDEGEN_DYNAMIC</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_DYNAMIC</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_DYNAMIC\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_DURINGBB\"><!-- --></A><H3>\r\nANTIDEGEN_DURINGBB</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_DURINGBB</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_DURINGBB\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_RHSPERTURB\"><!-- --></A><H3>\r\nANTIDEGEN_RHSPERTURB</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_RHSPERTURB</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_RHSPERTURB\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"ANTIDEGEN_BOUNDFLIP\"><!-- --></A><H3>\r\nANTIDEGEN_BOUNDFLIP</H3>\r\n<PRE>\r\npublic static final int <B>ANTIDEGEN_BOUNDFLIP</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.ANTIDEGEN_BOUNDFLIP\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NEUTRAL\"><!-- --></A><H3>\r\nNEUTRAL</H3>\r\n<PRE>\r\npublic static final int <B>NEUTRAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NEUTRAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"CRITICAL\"><!-- --></A><H3>\r\nCRITICAL</H3>\r\n<PRE>\r\npublic static final int <B>CRITICAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.CRITICAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SEVERE\"><!-- --></A><H3>\r\nSEVERE</H3>\r\n<PRE>\r\npublic static final int <B>SEVERE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SEVERE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"IMPORTANT\"><!-- --></A><H3>\r\nIMPORTANT</H3>\r\n<PRE>\r\npublic static final int <B>IMPORTANT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.IMPORTANT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NORMAL\"><!-- --></A><H3>\r\nNORMAL</H3>\r\n<PRE>\r\npublic static final int <B>NORMAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NORMAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"DETAILED\"><!-- --></A><H3>\r\nDETAILED</H3>\r\n<PRE>\r\npublic static final int <B>DETAILED</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.DETAILED\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"FULL\"><!-- --></A><H3>\r\nFULL</H3>\r\n<PRE>\r\npublic static final int <B>FULL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.FULL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_NONE\"><!-- --></A><H3>\r\nMSG_NONE</H3>\r\n<PRE>\r\npublic static final int <B>MSG_NONE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_NONE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_PRESOLVE\"><!-- --></A><H3>\r\nMSG_PRESOLVE</H3>\r\n<PRE>\r\npublic static final int <B>MSG_PRESOLVE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_PRESOLVE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_ITERATION\"><!-- --></A><H3>\r\nMSG_ITERATION</H3>\r\n<PRE>\r\npublic static final int <B>MSG_ITERATION</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_ITERATION\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_INVERT\"><!-- --></A><H3>\r\nMSG_INVERT</H3>\r\n<PRE>\r\npublic static final int <B>MSG_INVERT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_INVERT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_LPFEASIBLE\"><!-- --></A><H3>\r\nMSG_LPFEASIBLE</H3>\r\n<PRE>\r\npublic static final int <B>MSG_LPFEASIBLE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_LPFEASIBLE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_LPOPTIMAL\"><!-- --></A><H3>\r\nMSG_LPOPTIMAL</H3>\r\n<PRE>\r\npublic static final int <B>MSG_LPOPTIMAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_LPOPTIMAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_LPEQUAL\"><!-- --></A><H3>\r\nMSG_LPEQUAL</H3>\r\n<PRE>\r\npublic static final int <B>MSG_LPEQUAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_LPEQUAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_LPBETTER\"><!-- --></A><H3>\r\nMSG_LPBETTER</H3>\r\n<PRE>\r\npublic static final int <B>MSG_LPBETTER</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_LPBETTER\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_MILPFEASIBLE\"><!-- --></A><H3>\r\nMSG_MILPFEASIBLE</H3>\r\n<PRE>\r\npublic static final int <B>MSG_MILPFEASIBLE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_MILPFEASIBLE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_MILPEQUAL\"><!-- --></A><H3>\r\nMSG_MILPEQUAL</H3>\r\n<PRE>\r\npublic static final int <B>MSG_MILPEQUAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_MILPEQUAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_MILPBETTER\"><!-- --></A><H3>\r\nMSG_MILPBETTER</H3>\r\n<PRE>\r\npublic static final int <B>MSG_MILPBETTER</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_MILPBETTER\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_MILPSTRATEGY\"><!-- --></A><H3>\r\nMSG_MILPSTRATEGY</H3>\r\n<PRE>\r\npublic static final int <B>MSG_MILPSTRATEGY</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_MILPSTRATEGY\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_MILPOPTIMAL\"><!-- --></A><H3>\r\nMSG_MILPOPTIMAL</H3>\r\n<PRE>\r\npublic static final int <B>MSG_MILPOPTIMAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_MILPOPTIMAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_PERFORMANCE\"><!-- --></A><H3>\r\nMSG_PERFORMANCE</H3>\r\n<PRE>\r\npublic static final int <B>MSG_PERFORMANCE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_PERFORMANCE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"MSG_INITPSEUDOCOST\"><!-- --></A><H3>\r\nMSG_INITPSEUDOCOST</H3>\r\n<PRE>\r\npublic static final int <B>MSG_INITPSEUDOCOST</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.MSG_INITPSEUDOCOST\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"IMPROVE_NONE\"><!-- --></A><H3>\r\nIMPROVE_NONE</H3>\r\n<PRE>\r\npublic static final int <B>IMPROVE_NONE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.IMPROVE_NONE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"IMPROVE_SOLUTION\"><!-- --></A><H3>\r\nIMPROVE_SOLUTION</H3>\r\n<PRE>\r\npublic static final int <B>IMPROVE_SOLUTION</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.IMPROVE_SOLUTION\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"IMPROVE_DUALFEAS\"><!-- --></A><H3>\r\nIMPROVE_DUALFEAS</H3>\r\n<PRE>\r\npublic static final int <B>IMPROVE_DUALFEAS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.IMPROVE_DUALFEAS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"IMPROVE_THETAGAP\"><!-- --></A><H3>\r\nIMPROVE_THETAGAP</H3>\r\n<PRE>\r\npublic static final int <B>IMPROVE_THETAGAP</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.IMPROVE_THETAGAP\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"IMPROVE_BBSIMPLEX\"><!-- --></A><H3>\r\nIMPROVE_BBSIMPLEX</H3>\r\n<PRE>\r\npublic static final int <B>IMPROVE_BBSIMPLEX</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.IMPROVE_BBSIMPLEX\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_NONE\"><!-- --></A><H3>\r\nSCALE_NONE</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_NONE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_NONE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_EXTREME\"><!-- --></A><H3>\r\nSCALE_EXTREME</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_EXTREME</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_EXTREME\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_RANGE\"><!-- --></A><H3>\r\nSCALE_RANGE</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_RANGE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_RANGE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_MEAN\"><!-- --></A><H3>\r\nSCALE_MEAN</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_MEAN</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_MEAN\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_GEOMETRIC\"><!-- --></A><H3>\r\nSCALE_GEOMETRIC</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_GEOMETRIC</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_GEOMETRIC\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_CURTISREID\"><!-- --></A><H3>\r\nSCALE_CURTISREID</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_CURTISREID</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_CURTISREID\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_LINEAR\"><!-- --></A><H3>\r\nSCALE_LINEAR</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_LINEAR</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_LINEAR\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_QUADRATIC\"><!-- --></A><H3>\r\nSCALE_QUADRATIC</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_QUADRATIC</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_QUADRATIC\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_LOGARITHMIC\"><!-- --></A><H3>\r\nSCALE_LOGARITHMIC</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_LOGARITHMIC</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_LOGARITHMIC\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_USERWEIGHT\"><!-- --></A><H3>\r\nSCALE_USERWEIGHT</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_USERWEIGHT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_USERWEIGHT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_POWER2\"><!-- --></A><H3>\r\nSCALE_POWER2</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_POWER2</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_POWER2\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_EQUILIBRATE\"><!-- --></A><H3>\r\nSCALE_EQUILIBRATE</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_EQUILIBRATE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_EQUILIBRATE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_INTEGERS\"><!-- --></A><H3>\r\nSCALE_INTEGERS</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_INTEGERS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_INTEGERS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_DYNUPDATE\"><!-- --></A><H3>\r\nSCALE_DYNUPDATE</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_DYNUPDATE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_DYNUPDATE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_ROWSONLY\"><!-- --></A><H3>\r\nSCALE_ROWSONLY</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_ROWSONLY</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_ROWSONLY\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SCALE_COLSONLY\"><!-- --></A><H3>\r\nSCALE_COLSONLY</H3>\r\n<PRE>\r\npublic static final int <B>SCALE_COLSONLY</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SCALE_COLSONLY\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICER_FIRSTINDEX\"><!-- --></A><H3>\r\nPRICER_FIRSTINDEX</H3>\r\n<PRE>\r\npublic static final int <B>PRICER_FIRSTINDEX</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICER_FIRSTINDEX\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICER_DANTZIG\"><!-- --></A><H3>\r\nPRICER_DANTZIG</H3>\r\n<PRE>\r\npublic static final int <B>PRICER_DANTZIG</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICER_DANTZIG\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICER_DEVEX\"><!-- --></A><H3>\r\nPRICER_DEVEX</H3>\r\n<PRE>\r\npublic static final int <B>PRICER_DEVEX</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICER_DEVEX\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICER_STEEPESTEDGE\"><!-- --></A><H3>\r\nPRICER_STEEPESTEDGE</H3>\r\n<PRE>\r\npublic static final int <B>PRICER_STEEPESTEDGE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICER_STEEPESTEDGE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_METHODDEFAULT\"><!-- --></A><H3>\r\nPRICE_METHODDEFAULT</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_METHODDEFAULT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_METHODDEFAULT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_PRIMALFALLBACK\"><!-- --></A><H3>\r\nPRICE_PRIMALFALLBACK</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_PRIMALFALLBACK</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_PRIMALFALLBACK\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_MULTIPLE\"><!-- --></A><H3>\r\nPRICE_MULTIPLE</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_MULTIPLE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_MULTIPLE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_PARTIAL\"><!-- --></A><H3>\r\nPRICE_PARTIAL</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_PARTIAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_PARTIAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_ADAPTIVE\"><!-- --></A><H3>\r\nPRICE_ADAPTIVE</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_ADAPTIVE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_ADAPTIVE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_HYBRID\"><!-- --></A><H3>\r\nPRICE_HYBRID</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_HYBRID</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_HYBRID\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_RANDOMIZE\"><!-- --></A><H3>\r\nPRICE_RANDOMIZE</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_RANDOMIZE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_RANDOMIZE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_AUTOPARTIAL\"><!-- --></A><H3>\r\nPRICE_AUTOPARTIAL</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_AUTOPARTIAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_AUTOPARTIAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_LOOPLEFT\"><!-- --></A><H3>\r\nPRICE_LOOPLEFT</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_LOOPLEFT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_LOOPLEFT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_LOOPALTERNATE\"><!-- --></A><H3>\r\nPRICE_LOOPALTERNATE</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_LOOPALTERNATE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_LOOPALTERNATE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_HARRISTWOPASS\"><!-- --></A><H3>\r\nPRICE_HARRISTWOPASS</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_HARRISTWOPASS</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_HARRISTWOPASS\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRICE_TRUENORMINIT\"><!-- --></A><H3>\r\nPRICE_TRUENORMINIT</H3>\r\n<PRE>\r\npublic static final int <B>PRICE_TRUENORMINIT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRICE_TRUENORMINIT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_FIRSTSELECT\"><!-- --></A><H3>\r\nNODE_FIRSTSELECT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_FIRSTSELECT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_FIRSTSELECT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_GAPSELECT\"><!-- --></A><H3>\r\nNODE_GAPSELECT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_GAPSELECT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_GAPSELECT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_RANGESELECT\"><!-- --></A><H3>\r\nNODE_RANGESELECT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_RANGESELECT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_RANGESELECT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_FRACTIONSELECT\"><!-- --></A><H3>\r\nNODE_FRACTIONSELECT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_FRACTIONSELECT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_FRACTIONSELECT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_PSEUDOCOSTSELECT\"><!-- --></A><H3>\r\nNODE_PSEUDOCOSTSELECT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_PSEUDOCOSTSELECT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_PSEUDOCOSTSELECT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_PSEUDONONINTSELECT\"><!-- --></A><H3>\r\nNODE_PSEUDONONINTSELECT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_PSEUDONONINTSELECT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_PSEUDONONINTSELECT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_PSEUDORATIOSELECT\"><!-- --></A><H3>\r\nNODE_PSEUDORATIOSELECT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_PSEUDORATIOSELECT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_PSEUDORATIOSELECT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_USERSELECT\"><!-- --></A><H3>\r\nNODE_USERSELECT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_USERSELECT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_USERSELECT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_WEIGHTREVERSEMODE\"><!-- --></A><H3>\r\nNODE_WEIGHTREVERSEMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_WEIGHTREVERSEMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_WEIGHTREVERSEMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_BRANCHREVERSEMODE\"><!-- --></A><H3>\r\nNODE_BRANCHREVERSEMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_BRANCHREVERSEMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_BRANCHREVERSEMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_GREEDYMODE\"><!-- --></A><H3>\r\nNODE_GREEDYMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_GREEDYMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_GREEDYMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_PSEUDOCOSTMODE\"><!-- --></A><H3>\r\nNODE_PSEUDOCOSTMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_PSEUDOCOSTMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_PSEUDOCOSTMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_DEPTHFIRSTMODE\"><!-- --></A><H3>\r\nNODE_DEPTHFIRSTMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_DEPTHFIRSTMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_DEPTHFIRSTMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_RANDOMIZEMODE\"><!-- --></A><H3>\r\nNODE_RANDOMIZEMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_RANDOMIZEMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_RANDOMIZEMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_DYNAMICMODE\"><!-- --></A><H3>\r\nNODE_DYNAMICMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_DYNAMICMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_DYNAMICMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_RESTARTMODE\"><!-- --></A><H3>\r\nNODE_RESTARTMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_RESTARTMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_RESTARTMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_BREADTHFIRSTMODE\"><!-- --></A><H3>\r\nNODE_BREADTHFIRSTMODE</H3>\r\n<PRE>\r\npublic static final int <B>NODE_BREADTHFIRSTMODE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_BREADTHFIRSTMODE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_AUTOORDER\"><!-- --></A><H3>\r\nNODE_AUTOORDER</H3>\r\n<PRE>\r\npublic static final int <B>NODE_AUTOORDER</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_AUTOORDER\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_RCOSTFIXING\"><!-- --></A><H3>\r\nNODE_RCOSTFIXING</H3>\r\n<PRE>\r\npublic static final int <B>NODE_RCOSTFIXING</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_RCOSTFIXING\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NODE_STRONGINIT\"><!-- --></A><H3>\r\nNODE_STRONGINIT</H3>\r\n<PRE>\r\npublic static final int <B>NODE_STRONGINIT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NODE_STRONGINIT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"BRANCH_CEILING\"><!-- --></A><H3>\r\nBRANCH_CEILING</H3>\r\n<PRE>\r\npublic static final int <B>BRANCH_CEILING</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.BRANCH_CEILING\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"BRANCH_FLOOR\"><!-- --></A><H3>\r\nBRANCH_FLOOR</H3>\r\n<PRE>\r\npublic static final int <B>BRANCH_FLOOR</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.BRANCH_FLOOR\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"BRANCH_AUTOMATIC\"><!-- --></A><H3>\r\nBRANCH_AUTOMATIC</H3>\r\n<PRE>\r\npublic static final int <B>BRANCH_AUTOMATIC</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.BRANCH_AUTOMATIC\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"BRANCH_DEFAULT\"><!-- --></A><H3>\r\nBRANCH_DEFAULT</H3>\r\n<PRE>\r\npublic static final int <B>BRANCH_DEFAULT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.BRANCH_DEFAULT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"UNKNOWNERROR\"><!-- --></A><H3>\r\nUNKNOWNERROR</H3>\r\n<PRE>\r\npublic static final int <B>UNKNOWNERROR</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.UNKNOWNERROR\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"DATAIGNORED\"><!-- --></A><H3>\r\nDATAIGNORED</H3>\r\n<PRE>\r\npublic static final int <B>DATAIGNORED</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.DATAIGNORED\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NOBFP\"><!-- --></A><H3>\r\nNOBFP</H3>\r\n<PRE>\r\npublic static final int <B>NOBFP</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NOBFP\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NOMEMORY\"><!-- --></A><H3>\r\nNOMEMORY</H3>\r\n<PRE>\r\npublic static final int <B>NOMEMORY</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NOMEMORY\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NOTRUN\"><!-- --></A><H3>\r\nNOTRUN</H3>\r\n<PRE>\r\npublic static final int <B>NOTRUN</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NOTRUN\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"OPTIMAL\"><!-- --></A><H3>\r\nOPTIMAL</H3>\r\n<PRE>\r\npublic static final int <B>OPTIMAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.OPTIMAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"SUBOPTIMAL\"><!-- --></A><H3>\r\nSUBOPTIMAL</H3>\r\n<PRE>\r\npublic static final int <B>SUBOPTIMAL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.SUBOPTIMAL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"INFEASIBLE\"><!-- --></A><H3>\r\nINFEASIBLE</H3>\r\n<PRE>\r\npublic static final int <B>INFEASIBLE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.INFEASIBLE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"UNBOUNDED\"><!-- --></A><H3>\r\nUNBOUNDED</H3>\r\n<PRE>\r\npublic static final int <B>UNBOUNDED</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.UNBOUNDED\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"DEGENERATE\"><!-- --></A><H3>\r\nDEGENERATE</H3>\r\n<PRE>\r\npublic static final int <B>DEGENERATE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.DEGENERATE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NUMFAILURE\"><!-- --></A><H3>\r\nNUMFAILURE</H3>\r\n<PRE>\r\npublic static final int <B>NUMFAILURE</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NUMFAILURE\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"USERABORT\"><!-- --></A><H3>\r\nUSERABORT</H3>\r\n<PRE>\r\npublic static final int <B>USERABORT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.USERABORT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"TIMEOUT\"><!-- --></A><H3>\r\nTIMEOUT</H3>\r\n<PRE>\r\npublic static final int <B>TIMEOUT</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.TIMEOUT\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"RUNNING\"><!-- --></A><H3>\r\nRUNNING</H3>\r\n<PRE>\r\npublic static final int <B>RUNNING</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.RUNNING\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PRESOLVED\"><!-- --></A><H3>\r\nPRESOLVED</H3>\r\n<PRE>\r\npublic static final int <B>PRESOLVED</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PRESOLVED\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PROCFAIL\"><!-- --></A><H3>\r\nPROCFAIL</H3>\r\n<PRE>\r\npublic static final int <B>PROCFAIL</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PROCFAIL\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"PROCBREAK\"><!-- --></A><H3>\r\nPROCBREAK</H3>\r\n<PRE>\r\npublic static final int <B>PROCBREAK</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.PROCBREAK\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"FEASFOUND\"><!-- --></A><H3>\r\nFEASFOUND</H3>\r\n<PRE>\r\npublic static final int <B>FEASFOUND</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.FEASFOUND\">Constant Field Values</A></DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"NOFEASFOUND\"><!-- --></A><H3>\r\nNOFEASFOUND</H3>\r\n<PRE>\r\npublic static final int <B>NOFEASFOUND</B></PRE>\r\n<DL>\r\n<DL>\r\n<DT><B>See Also:</B><DD><A HREF=\"../constant-values.html#lpsolve.LpSolve.NOFEASFOUND\">Constant Field Values</A></DL>\r\n</DL>\r\n\r\n<!-- ========= CONSTRUCTOR DETAIL ======== -->\r\n\r\n\r\n<!-- ============ METHOD DETAIL ========== -->\r\n\r\n<A NAME=\"method_detail\"><!-- --></A>\r\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Method Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"makeLp(int, int)\"><!-- --></A><H3>\r\nmakeLp</H3>\r\n<PRE>\r\npublic static <A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A> <B>makeLp</B>(int&nbsp;rows,\r\n                             int&nbsp;columns)\r\n                      throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Creates a new problem. Upon successful completion, the lprec attribute\r\n in this class contains the value of the pointer to the <code>lprec</code>\r\n structure.\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>rows</CODE> - Initial number of rows.<DD><CODE>columns</CODE> - Initial number of columns.\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE> - if lp_solve could not create the problem</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"readLp(java.lang.String, int, java.lang.String)\"><!-- --></A><H3>\r\nreadLp</H3>\r\n<PRE>\r\npublic static <A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A> <B>readLp</B>(java.lang.String&nbsp;filename,\r\n                             int&nbsp;verbose,\r\n                             java.lang.String&nbsp;lpName)\r\n                      throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Read an lp model from file and create a new problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"readMps(java.lang.String, int)\"><!-- --></A><H3>\r\nreadMps</H3>\r\n<PRE>\r\npublic static <A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A> <B>readMps</B>(java.lang.String&nbsp;filename,\r\n                              int&nbsp;verbose)\r\n                       throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Read an mps model from file and create a new problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"readFreeMps(java.lang.String, int)\"><!-- --></A><H3>\r\nreadFreeMps</H3>\r\n<PRE>\r\npublic static <A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A> <B>readFreeMps</B>(java.lang.String&nbsp;filename,\r\n                                  int&nbsp;verbose)\r\n                           throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Read a model in free MPS format from file and create a new problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"readXLI(java.lang.String, java.lang.String, java.lang.String, java.lang.String, int)\"><!-- --></A><H3>\r\nreadXLI</H3>\r\n<PRE>\r\npublic static <A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A> <B>readXLI</B>(java.lang.String&nbsp;xliname,\r\n                              java.lang.String&nbsp;modelname,\r\n                              java.lang.String&nbsp;dataname,\r\n                              java.lang.String&nbsp;options,\r\n                              int&nbsp;verbose)\r\n                       throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Read a model via the External Language Interface and create a new problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"lpSolveVersion()\"><!-- --></A><H3>\r\nlpSolveVersion</H3>\r\n<PRE>\r\npublic static <A HREF=\"../lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A> <B>lpSolveVersion</B>()</PRE>\r\n<DL>\r\n<DD>Returns the full version number of the underlying lp_solve library.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Returns:</B><DD>VersionInfo object with full version info</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"finalize()\"><!-- --></A><H3>\r\nfinalize</H3>\r\n<PRE>\r\nprotected void <B>finalize</B>()\r\n                 throws java.lang.Throwable</PRE>\r\n<DL>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE>java.lang.Throwable</CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getLp()\"><!-- --></A><H3>\r\ngetLp</H3>\r\n<PRE>\r\npublic long <B>getLp</B>()</PRE>\r\n<DL>\r\n<DD>Return the value of the lp attribute.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Returns:</B><DD>the value of the lp attribute</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"copyLp()\"><!-- --></A><H3>\r\ncopyLp</H3>\r\n<PRE>\r\npublic <A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A> <B>copyLp</B>()\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Copy an existing lprec structure to a new lprec structure.\r\n Creates an independent new problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n\r\n<HR>\r\n\r\n<A NAME=\"resizeLp(int, int)\"><!-- --></A><H3>\r\nresizeLp</H3>\r\n<PRE>\r\npublic void <B>resizeLp</B>(int&nbsp;rows,\r\n                     int&nbsp;columns)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Allocate memory for the specified size.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n\r\n\r\n<HR>\r\n\r\n<A NAME=\"setLpName(java.lang.String)\"><!-- --></A><H3>\r\nsetLpName</H3>\r\n<PRE>\r\npublic void <B>setLpName</B>(java.lang.String&nbsp;name)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the name of the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getLpName()\"><!-- --></A><H3>\r\ngetLpName</H3>\r\n<PRE>\r\npublic java.lang.String <B>getLpName</B>()\r\n                           throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get the name of the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"addConstraint(double[], int, double)\"><!-- --></A><H3>\r\naddConstraint</H3>\r\n<PRE>\r\npublic void <B>addConstraint</B>(double[]&nbsp;row,\r\n                          int&nbsp;constrType,\r\n                          double&nbsp;rh)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a constraint to the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"strAddConstraint(java.lang.String, int, double)\"><!-- --></A><H3>\r\nstrAddConstraint</H3>\r\n<PRE>\r\npublic void <B>strAddConstraint</B>(java.lang.String&nbsp;row,\r\n                             int&nbsp;constrType,\r\n                             double&nbsp;rh)\r\n                      throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a constraint to the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"addConstraintex(int, double[], int[], int, double)\"><!-- --></A><H3>\r\naddConstraintex</H3>\r\n<PRE>\r\npublic void <B>addConstraintex</B>(int&nbsp;count,\r\n                            double[]&nbsp;row,\r\n                            int[]&nbsp;colno,\r\n                            int&nbsp;constrType,\r\n                            double&nbsp;rh)\r\n                     throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a constraint to the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"delConstraint(int)\"><!-- --></A><H3>\r\ndelConstraint</H3>\r\n<PRE>\r\npublic void <B>delConstraint</B>(int&nbsp;rownr)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Remove a constraint from the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isConstrType(int, int)\"><!-- --></A><H3>\r\nisConstrType</H3>\r\n<PRE>\r\npublic boolean <B>isConstrType</B>(int&nbsp;row,\r\n                            int&nbsp;mask)</PRE>\r\n<DL>\r\n<DD>Returns if constraint type specified in mask is active.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"addLagCon(double[], int, double)\"><!-- --></A><H3>\r\naddLagCon</H3>\r\n<PRE>\r\npublic void <B>addLagCon</B>(double[]&nbsp;row,\r\n                      int&nbsp;constrType,\r\n                      double&nbsp;rh)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a Lagrangian constraint to the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"strAddLagCon(java.lang.String, int, double)\"><!-- --></A><H3>\r\nstrAddLagCon</H3>\r\n<PRE>\r\npublic void <B>strAddLagCon</B>(java.lang.String&nbsp;row,\r\n                         int&nbsp;constrType,\r\n                         double&nbsp;rh)\r\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a Lagrangian constraint to the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"addColumn(double[])\"><!-- --></A><H3>\r\naddColumn</H3>\r\n<PRE>\r\npublic void <B>addColumn</B>(double[]&nbsp;column)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a column to the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"addColumnex(int, double[], int[])\"><!-- --></A><H3>\r\naddColumnex</H3>\r\n<PRE>\r\npublic void <B>addColumnex</B>(int&nbsp;count,\r\n                        double[]&nbsp;column,\r\n                        int[]&nbsp;rowno)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a column to the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"strAddColumn(java.lang.String)\"><!-- --></A><H3>\r\nstrAddColumn</H3>\r\n<PRE>\r\npublic void <B>strAddColumn</B>(java.lang.String&nbsp;column)\r\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a column to the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"delColumn(int)\"><!-- --></A><H3>\r\ndelColumn</H3>\r\n<PRE>\r\npublic void <B>delColumn</B>(int&nbsp;columnnr)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Remove a column from the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setRow(int, double[])\"><!-- --></A><H3>\r\nsetRow</H3>\r\n<PRE>\r\npublic void <B>setRow</B>(int&nbsp;rowno,\r\n                   double[]&nbsp;row)\r\n            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set a constraint in the lp.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setRowex(int, int, double[], int[])\"><!-- --></A><H3>\r\nsetRowex</H3>\r\n<PRE>\r\npublic void <B>setRowex</B>(int&nbsp;rowno,\r\n                     int&nbsp;count,\r\n                     double[]&nbsp;row,\r\n                     int[]&nbsp;colno)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set a constraint in the lp.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setColumn(int, double[])\"><!-- --></A><H3>\r\nsetColumn</H3>\r\n<PRE>\r\npublic void <B>setColumn</B>(int&nbsp;colno,\r\n                      double[]&nbsp;column)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set a column in the lp.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setColumnex(int, int, double[], int[])\"><!-- --></A><H3>\r\nsetColumnex</H3>\r\n<PRE>\r\npublic void <B>setColumnex</B>(int&nbsp;colno,\r\n                        int&nbsp;count,\r\n                        double[]&nbsp;column,\r\n                        int[]&nbsp;rowno)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set a column in the lp.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"columnInLp(double[])\"><!-- --></A><H3>\r\ncolumnInLp</H3>\r\n<PRE>\r\npublic int <B>columnInLp</B>(double[]&nbsp;column)</PRE>\r\n<DL>\r\n<DD>Check if a column is already present in the problem.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setRowName(int, java.lang.String)\"><!-- --></A><H3>\r\nsetRowName</H3>\r\n<PRE>\r\npublic void <B>setRowName</B>(int&nbsp;rownr,\r\n                       java.lang.String&nbsp;name)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the name of a constraint (row) in the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getRowName(int)\"><!-- --></A><H3>\r\ngetRowName</H3>\r\n<PRE>\r\npublic java.lang.String <B>getRowName</B>(int&nbsp;rownr)\r\n                            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Gets the name of a constraint (row) in the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getOrigrowName(int)\"><!-- --></A><H3>\r\ngetOrigrowName</H3>\r\n<PRE>\r\npublic java.lang.String <B>getOrigrowName</B>(int&nbsp;rownr)\r\n                                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Gets the name of a constraint (row) in the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setColName(int, java.lang.String)\"><!-- --></A><H3>\r\nsetColName</H3>\r\n<PRE>\r\npublic void <B>setColName</B>(int&nbsp;colnr,\r\n                       java.lang.String&nbsp;name)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the name of a column in the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getColName(int)\"><!-- --></A><H3>\r\ngetColName</H3>\r\n<PRE>\r\npublic java.lang.String <B>getColName</B>(int&nbsp;colnr)\r\n                            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Gets the name of a column in the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getOrigcolName(int)\"><!-- --></A><H3>\r\ngetOrigcolName</H3>\r\n<PRE>\r\npublic java.lang.String <B>getOrigcolName</B>(int&nbsp;colnr)\r\n                                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Gets the name of a column in the problem.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setRhVec(double[])\"><!-- --></A><H3>\r\nsetRhVec</H3>\r\n<PRE>\r\npublic void <B>setRhVec</B>(double[]&nbsp;rh)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the right hand side (RHS) vector (column 0).\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"strSetRhVec(java.lang.String)\"><!-- --></A><H3>\r\nstrSetRhVec</H3>\r\n<PRE>\r\npublic void <B>strSetRhVec</B>(java.lang.String&nbsp;rh)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the right hand side (RHS) vector (column 0).\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setRh(int, double)\"><!-- --></A><H3>\r\nsetRh</H3>\r\n<PRE>\r\npublic void <B>setRh</B>(int&nbsp;row,\r\n                  double&nbsp;value)\r\n           throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the value of the right hand side (RHS) vector (column 0) for one row.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getRh(int)\"><!-- --></A><H3>\r\ngetRh</H3>\r\n<PRE>\r\npublic double <B>getRh</B>(int&nbsp;row)</PRE>\r\n<DL>\r\n<DD>Get the value of the right hand side (RHS) vector (column 0) for one row.\r\n NOTE: Returns 0 even if the row index is out of bounds, in accordance\r\n to the behaviour of the lp_solve routine!\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setConstrType(int, int)\"><!-- --></A><H3>\r\nsetConstrType</H3>\r\n<PRE>\r\npublic void <B>setConstrType</B>(int&nbsp;rownr,\r\n                          int&nbsp;constrType)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the type of a constraint.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getConstrType(int)\"><!-- --></A><H3>\r\ngetConstrType</H3>\r\n<PRE>\r\npublic short <B>getConstrType</B>(int&nbsp;rownr)\r\n                    throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get the type of a constraint.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"addSOS(java.lang.String, int, int, int, int[], double[])\"><!-- --></A><H3>\r\naddSOS</H3>\r\n<PRE>\r\npublic void <B>addSOS</B>(java.lang.String&nbsp;name,\r\n                   int&nbsp;sostype,\r\n                   int&nbsp;priority,\r\n                   int&nbsp;count,\r\n                   int[]&nbsp;sosvars,\r\n                   double[]&nbsp;weights)\r\n            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Add a SOS constraint.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isSOSVar(int)\"><!-- --></A><H3>\r\nisSOSVar</H3>\r\n<PRE>\r\npublic boolean <B>isSOSVar</B>(int&nbsp;colnr)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns if the variable is SOS or not.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setObjFn(double[])\"><!-- --></A><H3>\r\nsetObjFn</H3>\r\n<PRE>\r\npublic void <B>setObjFn</B>(double[]&nbsp;row)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the objective function (row 0) of the matrix.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"strSetObjFn(java.lang.String)\"><!-- --></A><H3>\r\nstrSetObjFn</H3>\r\n<PRE>\r\npublic void <B>strSetObjFn</B>(java.lang.String&nbsp;row)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the objective function (row 0) of the matrix.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setObjFnex(int, double[], int[])\"><!-- --></A><H3>\r\nsetObjFnex</H3>\r\n<PRE>\r\npublic void <B>setObjFnex</B>(int&nbsp;count,\r\n                       double[]&nbsp;row,\r\n                       int[]&nbsp;colno)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the objective function (row 0) of the matrix.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setObj(int, double)\"><!-- --></A><H3>\r\nsetObj</H3>\r\n<PRE>\r\npublic void <B>setObj</B>(int&nbsp;column,\r\n                   double&nbsp;value)\r\n            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the objective function (row 0) of the matrix.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setMat(int, int, double)\"><!-- --></A><H3>\r\nsetMat</H3>\r\n<PRE>\r\npublic void <B>setMat</B>(int&nbsp;row,\r\n                   int&nbsp;column,\r\n                   double&nbsp;value)\r\n            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set a single element in the matrix.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getMat(int, int)\"><!-- --></A><H3>\r\ngetMat</H3>\r\n<PRE>\r\npublic double <B>getMat</B>(int&nbsp;row,\r\n                     int&nbsp;column)</PRE>\r\n<DL>\r\n<DD>Get a single element from the matrix.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getRow(int, double[])\"><!-- --></A><H3>\r\ngetRow</H3>\r\n<PRE>\r\npublic void <B>getRow</B>(int&nbsp;rownr,\r\n                   double[]&nbsp;row)\r\n            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get all row elements from the matrix.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getRowex(int, double[], int[])\"><!-- --></A><H3>\r\ngetRowex</H3>\r\n<PRE>\r\npublic int <B>getRowex</B>(int&nbsp;rownr,\r\n                    double[]&nbsp;row,\r\n                    int[]&nbsp;nzcols)\r\n             throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get the non-zero row elements from the matrix.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrRow(int)\"><!-- --></A><H3>\r\ngetPtrRow</H3>\r\n<PRE>\r\npublic double[] <B>getPtrRow</B>(int&nbsp;rownr)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get all row elements from the matrix.\r\n Returned array is allocated by the method.\r\n This is an additional method which is not implemented by lp_solve.\r\n Internally, get_row is used.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getColumn(int, double[])\"><!-- --></A><H3>\r\ngetColumn</H3>\r\n<PRE>\r\npublic void <B>getColumn</B>(int&nbsp;colnr,\r\n                      double[]&nbsp;column)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get all column elements from the matrix.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getColumnex(int, double[], int[])\"><!-- --></A><H3>\r\ngetColumnex</H3>\r\n<PRE>\r\npublic int <B>getColumnex</B>(int&nbsp;colnr,\r\n                       double[]&nbsp;column,\r\n                       int[]&nbsp;nzrows)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get the non-zero column elements from the matrix.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrColumn(int)\"><!-- --></A><H3>\r\ngetPtrColumn</H3>\r\n<PRE>\r\npublic double[] <B>getPtrColumn</B>(int&nbsp;columnrnr)\r\n                      throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get all column elements from the matrix.\r\n Returned array is allocated by the method.\r\n This is an additional method which is not implemented by lp_solve.\r\n Internally, get_column is used.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setMaxim()\"><!-- --></A><H3>\r\nsetMaxim</H3>\r\n<PRE>\r\npublic void <B>setMaxim</B>()</PRE>\r\n<DL>\r\n<DD>Set objective function to maximize.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setMinim()\"><!-- --></A><H3>\r\nsetMinim</H3>\r\n<PRE>\r\npublic void <B>setMinim</B>()</PRE>\r\n<DL>\r\n<DD>Set objective function to minimize.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setSense(boolean)\"><!-- --></A><H3>\r\nsetSense</H3>\r\n<PRE>\r\npublic void <B>setSense</B>(boolean&nbsp;maximize)</PRE>\r\n<DL>\r\n<DD>Set objective function sense.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isMaxim()\"><!-- --></A><H3>\r\nisMaxim</H3>\r\n<PRE>\r\npublic boolean <B>isMaxim</B>()</PRE>\r\n<DL>\r\n<DD>Returns objective function direction.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setLowbo(int, double)\"><!-- --></A><H3>\r\nsetLowbo</H3>\r\n<PRE>\r\npublic void <B>setLowbo</B>(int&nbsp;colnr,\r\n                     double&nbsp;value)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the lower bound of a variable.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getLowbo(int)\"><!-- --></A><H3>\r\ngetLowbo</H3>\r\n<PRE>\r\npublic double <B>getLowbo</B>(int&nbsp;colnr)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get the lower bound of a variable.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setUpbo(int, double)\"><!-- --></A><H3>\r\nsetUpbo</H3>\r\n<PRE>\r\npublic void <B>setUpbo</B>(int&nbsp;colnr,\r\n                    double&nbsp;value)\r\n             throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the upper bound of a variable.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getUpbo(int)\"><!-- --></A><H3>\r\ngetUpbo</H3>\r\n<PRE>\r\npublic double <B>getUpbo</B>(int&nbsp;colnr)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Get the upper bound of a variable.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setUnbounded(int)\"><!-- --></A><H3>\r\nsetUnbounded</H3>\r\n<PRE>\r\npublic void <B>setUnbounded</B>(int&nbsp;colnr)\r\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Sets if the variable is free.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isUnbounded(int)\"><!-- --></A><H3>\r\nisUnbounded</H3>\r\n<PRE>\r\npublic boolean <B>isUnbounded</B>(int&nbsp;colnr)</PRE>\r\n<DL>\r\n<DD>Returns if the variable is free.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isNegative(int)\"><!-- --></A><H3>\r\nisNegative</H3>\r\n<PRE>\r\npublic boolean <B>isNegative</B>(int&nbsp;colnr)</PRE>\r\n<DL>\r\n<DD>Returns if the variable is negative.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBounds(int, double, double)\"><!-- --></A><H3>\r\nsetBounds</H3>\r\n<PRE>\r\npublic void <B>setBounds</B>(int&nbsp;colnr,\r\n                      double&nbsp;lower,\r\n                      double&nbsp;upper)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the upper and lower bound of a variable.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBoundsTighter(boolean)\"><!-- --></A><H3>\r\nsetBoundsTighter</H3>\r\n<PRE>\r\npublic void <B>setBoundsTighter</B>(boolean&nbsp;tighten)</PRE>\r\n<DL>\r\n<DD>Specifies if set bounds may only be tighter or also less restrictive.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getBoundsTighter()\"><!-- --></A><H3>\r\ngetBoundsTighter</H3>\r\n<PRE>\r\npublic boolean <B>getBoundsTighter</B>()</PRE>\r\n<DL>\r\n<DD>Returns if set bounds may only be tighter or also less restrictive.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setRhRange(int, double)\"><!-- --></A><H3>\r\nsetRhRange</H3>\r\n<PRE>\r\npublic void <B>setRhRange</B>(int&nbsp;rownr,\r\n                       double&nbsp;range)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the range on a constraint.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getRhRange(int)\"><!-- --></A><H3>\r\ngetRhRange</H3>\r\n<PRE>\r\npublic double <B>getRhRange</B>(int&nbsp;rownr)\r\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Gets the range on a constraint.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setInt(int, boolean)\"><!-- --></A><H3>\r\nsetInt</H3>\r\n<PRE>\r\npublic void <B>setInt</B>(int&nbsp;colnr,\r\n                   boolean&nbsp;mustBeInteger)\r\n            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the type of the variable. Integer or floating point.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isInt(int)\"><!-- --></A><H3>\r\nisInt</H3>\r\n<PRE>\r\npublic boolean <B>isInt</B>(int&nbsp;colnr)</PRE>\r\n<DL>\r\n<DD>Get the type of the variable. Integer or floating point.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBinary(int, boolean)\"><!-- --></A><H3>\r\nsetBinary</H3>\r\n<PRE>\r\npublic void <B>setBinary</B>(int&nbsp;colnr,\r\n                      boolean&nbsp;mustBeBin)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the type of the variable. Binary or floating point.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isBinary(int)\"><!-- --></A><H3>\r\nisBinary</H3>\r\n<PRE>\r\npublic boolean <B>isBinary</B>(int&nbsp;colnr)</PRE>\r\n<DL>\r\n<DD>Gets the type of the variable. Binary integer or floating point.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setSemicont(int, boolean)\"><!-- --></A><H3>\r\nsetSemicont</H3>\r\n<PRE>\r\npublic void <B>setSemicont</B>(int&nbsp;colnr,\r\n                        boolean&nbsp;mustBeSc)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the type of the variable. semi-continious or not.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isSemicont(int)\"><!-- --></A><H3>\r\nisSemicont</H3>\r\n<PRE>\r\npublic boolean <B>isSemicont</B>(int&nbsp;colnr)</PRE>\r\n<DL>\r\n<DD>Get the type of the variable. semi-continious or not.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setInfinite(double)\"><!-- --></A><H3>\r\nsetInfinite</H3>\r\n<PRE>\r\npublic void <B>setInfinite</B>(double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Specifies the practical value for \"infinite\".\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getInfinite()\"><!-- --></A><H3>\r\ngetInfinite</H3>\r\n<PRE>\r\npublic double <B>getInfinite</B>()</PRE>\r\n<DL>\r\n<DD>Returns the value of \"infinite\".\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isInfinite(double)\"><!-- --></A><H3>\r\nisInfinite</H3>\r\n<PRE>\r\npublic boolean <B>isInfinite</B>(double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Checks if the provided absolute of the value is larger or equal to \"infinite\".\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setEpsint(double)\"><!-- --></A><H3>\r\nsetEpsint</H3>\r\n<PRE>\r\npublic void <B>setEpsint</B>(double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Specifies the tolerance that is used to determine whether a floating-point\r\n number is in fact an integer.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getEpsint()\"><!-- --></A><H3>\r\ngetEpsint</H3>\r\n<PRE>\r\npublic double <B>getEpsint</B>()</PRE>\r\n<DL>\r\n<DD>Returns the tolerance that is used to determine whether a floating-point\r\n number is in fact an integer\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setEpsb(double)\"><!-- --></A><H3>\r\nsetEpsb</H3>\r\n<PRE>\r\npublic void <B>setEpsb</B>(double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Specifies the value that is used as a tolerance for the Right Hand Side (RHS)\r\n to determine whether a value should be considered as 0\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getEpsb()\"><!-- --></A><H3>\r\ngetEpsb</H3>\r\n<PRE>\r\npublic double <B>getEpsb</B>()</PRE>\r\n<DL>\r\n<DD>Returns the value that is used as a tolerance for the Right Hand Side (RHS)\r\n to determine whether a value should be considered as 0.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setEpsd(double)\"><!-- --></A><H3>\r\nsetEpsd</H3>\r\n<PRE>\r\npublic void <B>setEpsd</B>(double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Specifies the value that is used as a tolerance for reduced costs\r\n to determine whether a value should be considered as 0.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getEpsd()\"><!-- --></A><H3>\r\ngetEpsd</H3>\r\n<PRE>\r\npublic double <B>getEpsd</B>()</PRE>\r\n<DL>\r\n<DD>Returns the value that is used as a tolerance for the reduced costs\r\n to determine whether a value should be considered as 0.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setEpsel(double)\"><!-- --></A><H3>\r\nsetEpsel</H3>\r\n<PRE>\r\npublic void <B>setEpsel</B>(double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Specifies the value that is used as a tolerance for rounding values to zero.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getEpsel()\"><!-- --></A><H3>\r\ngetEpsel</H3>\r\n<PRE>\r\npublic double <B>getEpsel</B>()</PRE>\r\n<DL>\r\n<DD>Returns the value that is used as a tolerance for rounding values to zero.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setEpspivot(double)\"><!-- --></A><H3>\r\nsetEpspivot</H3>\r\n<PRE>\r\npublic void <B>setEpspivot</B>(double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Specifies the value that is used as a tolerance pivot element to determine\r\n whether a value should be considered as 0.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getEpspivot()\"><!-- --></A><H3>\r\ngetEpspivot</H3>\r\n<PRE>\r\npublic double <B>getEpspivot</B>()</PRE>\r\n<DL>\r\n<DD>Returns the value that is used as a tolerance pivot element to determine\r\n whether a value should be considered as 0.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setEpsperturb(double)\"><!-- --></A><H3>\r\nsetEpsperturb</H3>\r\n<PRE>\r\npublic void <B>setEpsperturb</B>(double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Specifies the value that is used as perturbation scalar for degenerative problems.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getEpsperturb()\"><!-- --></A><H3>\r\ngetEpsperturb</H3>\r\n<PRE>\r\npublic double <B>getEpsperturb</B>()</PRE>\r\n<DL>\r\n<DD>Returns the value that is used as perturbation scalar for degenerative problems.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setEpslevel(int)\"><!-- --></A><H3>\r\nsetEpslevel</H3>\r\n<PRE>\r\npublic void <B>setEpslevel</B>(int&nbsp;epslevel)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>This is a simplified way of specifying multiple eps thresholds that are \"logically\" consistent.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getStatus()\"><!-- --></A><H3>\r\ngetStatus</H3>\r\n<PRE>\r\npublic int <B>getStatus</B>()</PRE>\r\n<DL>\r\n<DD>Returns an extra status after a call to a function.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setMipGap(boolean, double)\"><!-- --></A><H3>\r\nsetMipGap</H3>\r\n<PRE>\r\npublic void <B>setMipGap</B>(boolean&nbsp;absolute,\r\n                      double&nbsp;value)</PRE>\r\n<DL>\r\n<DD>Specifies the MIP gap value.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getMipGap(boolean)\"><!-- --></A><H3>\r\ngetMipGap</H3>\r\n<PRE>\r\npublic double <B>getMipGap</B>(boolean&nbsp;absolute)</PRE>\r\n<DL>\r\n<DD>Returns the MIP gap value.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setVerbose(int)\"><!-- --></A><H3>\r\nsetVerbose</H3>\r\n<PRE>\r\npublic void <B>setVerbose</B>(int&nbsp;verbose)</PRE>\r\n<DL>\r\n<DD>Set the verbose level.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getVerbose()\"><!-- --></A><H3>\r\ngetVerbose</H3>\r\n<PRE>\r\npublic int <B>getVerbose</B>()</PRE>\r\n<DL>\r\n<DD>Returns the verbose level.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setTimeout(long)\"><!-- --></A><H3>\r\nsetTimeout</H3>\r\n<PRE>\r\npublic void <B>setTimeout</B>(long&nbsp;timeout)</PRE>\r\n<DL>\r\n<DD>Set a timeout.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getTimeout()\"><!-- --></A><H3>\r\ngetTimeout</H3>\r\n<PRE>\r\npublic long <B>getTimeout</B>()</PRE>\r\n<DL>\r\n<DD>Gets the timout.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"timeElapsed()\"><!-- --></A><H3>\r\ntimeElapsed</H3>\r\n<PRE>\r\npublic double <B>timeElapsed</B>()</PRE>\r\n<DL>\r\n<DD>Gets the time elapsed since start of solve.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setPrintSol(int)\"><!-- --></A><H3>\r\nsetPrintSol</H3>\r\n<PRE>\r\npublic void <B>setPrintSol</B>(int&nbsp;printSol)</PRE>\r\n<DL>\r\n<DD>Sets a flag if all intermediate valid solutions must be printed while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPrintSol()\"><!-- --></A><H3>\r\ngetPrintSol</H3>\r\n<PRE>\r\npublic int <B>getPrintSol</B>()</PRE>\r\n<DL>\r\n<DD>Returns a flag if all intermediate valid solutions must be printed while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setDebug(boolean)\"><!-- --></A><H3>\r\nsetDebug</H3>\r\n<PRE>\r\npublic void <B>setDebug</B>(boolean&nbsp;debug)</PRE>\r\n<DL>\r\n<DD>Sets a flag if all intermediate results and the branch-and-bound decisions\r\n must be printed while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isDebug()\"><!-- --></A><H3>\r\nisDebug</H3>\r\n<PRE>\r\npublic boolean <B>isDebug</B>()</PRE>\r\n<DL>\r\n<DD>Returns a flag if all intermediate results and the branch-and-bound decisions\r\n must be printed while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setTrace(boolean)\"><!-- --></A><H3>\r\nsetTrace</H3>\r\n<PRE>\r\npublic void <B>setTrace</B>(boolean&nbsp;trace)</PRE>\r\n<DL>\r\n<DD>Sets a flag if pivot selection must be printed while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isTrace()\"><!-- --></A><H3>\r\nisTrace</H3>\r\n<PRE>\r\npublic boolean <B>isTrace</B>()</PRE>\r\n<DL>\r\n<DD>Returns a flag if pivot selection must be printed while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setLagTrace(boolean)\"><!-- --></A><H3>\r\nsetLagTrace</H3>\r\n<PRE>\r\npublic void <B>setLagTrace</B>(boolean&nbsp;lagTrace)</PRE>\r\n<DL>\r\n<DD>Sets a flag if Lagrangian progression must be printed while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isLagTrace()\"><!-- --></A><H3>\r\nisLagTrace</H3>\r\n<PRE>\r\npublic boolean <B>isLagTrace</B>()</PRE>\r\n<DL>\r\n<DD>Returns a flag if Lagrangian progression must be printed while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setAddRowmode(boolean)\"><!-- --></A><H3>\r\nsetAddRowmode</H3>\r\n<PRE>\r\npublic boolean <B>setAddRowmode</B>(boolean&nbsp;turnon)</PRE>\r\n<DL>\r\n<DD>Specifies which add routine performs best.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isAddRowmode()\"><!-- --></A><H3>\r\nisAddRowmode</H3>\r\n<PRE>\r\npublic boolean <B>isAddRowmode</B>()</PRE>\r\n<DL>\r\n<DD>Returns a flag which of the add routines perform best.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setAntiDegen(int)\"><!-- --></A><H3>\r\nsetAntiDegen</H3>\r\n<PRE>\r\npublic void <B>setAntiDegen</B>(int&nbsp;antiDegen)</PRE>\r\n<DL>\r\n<DD>Specifies if special handling must be done to reduce degeneracy/cycling while solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isAntiDegen(int)\"><!-- --></A><H3>\r\nisAntiDegen</H3>\r\n<PRE>\r\npublic boolean <B>isAntiDegen</B>(int&nbsp;testmask)</PRE>\r\n<DL>\r\n<DD>Returns if the degeneracy rule specified in testmask is active.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getAntiDegen()\"><!-- --></A><H3>\r\ngetAntiDegen</H3>\r\n<PRE>\r\npublic int <B>getAntiDegen</B>()</PRE>\r\n<DL>\r\n<DD>Returns the used degeneracy rule.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setPresolve(int, int)\"><!-- --></A><H3>\r\nsetPresolve</H3>\r\n<PRE>\r\npublic void <B>setPresolve</B>(int&nbsp;doPresolve,\r\n                        int&nbsp;maxloops)</PRE>\r\n<DL>\r\n<DD>Specifies if a presolve must be done before solving.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isPresolve(int)\"><!-- --></A><H3>\r\nisPresolve</H3>\r\n<PRE>\r\npublic boolean <B>isPresolve</B>(int&nbsp;testmask)</PRE>\r\n<DL>\r\n<DD>Returns if presolve level specified in testmask is active.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPresolve()\"><!-- --></A><H3>\r\ngetPresolve</H3>\r\n<PRE>\r\npublic int <B>getPresolve</B>()</PRE>\r\n<DL>\r\n<DD>Returns the current presolve setting.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPresolveloops()\"><!-- --></A><H3>\r\ngetPresolveloops</H3>\r\n<PRE>\r\npublic int <B>getPresolveloops</B>()</PRE>\r\n<DL>\r\n<DD>Returns the number of times presolve is done.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setMaxpivot(int)\"><!-- --></A><H3>\r\nsetMaxpivot</H3>\r\n<PRE>\r\npublic void <B>setMaxpivot</B>(int&nbsp;maxNumInv)</PRE>\r\n<DL>\r\n<DD>Sets the maximum number of pivots between a reinversion of the matrix.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getMaxpivot()\"><!-- --></A><H3>\r\ngetMaxpivot</H3>\r\n<PRE>\r\npublic int <B>getMaxpivot</B>()</PRE>\r\n<DL>\r\n<DD>Returns the maximum number of pivots between a reinversion of the matrix.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBbRule(int)\"><!-- --></A><H3>\r\nsetBbRule</H3>\r\n<PRE>\r\npublic void <B>setBbRule</B>(int&nbsp;bbRule)</PRE>\r\n<DL>\r\n<DD>Specifies the branch-and-bound rule.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getBbRule()\"><!-- --></A><H3>\r\ngetBbRule</H3>\r\n<PRE>\r\npublic int <B>getBbRule</B>()</PRE>\r\n<DL>\r\n<DD>Returns the branch-and-bound rule.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBbDepthlimit(int)\"><!-- --></A><H3>\r\nsetBbDepthlimit</H3>\r\n<PRE>\r\npublic void <B>setBbDepthlimit</B>(int&nbsp;bbMaxlevel)</PRE>\r\n<DL>\r\n<DD>Sets the maximum branch-and-bound depth.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getBbDepthlimit()\"><!-- --></A><H3>\r\ngetBbDepthlimit</H3>\r\n<PRE>\r\npublic int <B>getBbDepthlimit</B>()</PRE>\r\n<DL>\r\n<DD>Returns the maximum branch-and-bound depth.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getSolutioncount()\"><!-- --></A><H3>\r\ngetSolutioncount</H3>\r\n<PRE>\r\npublic int <B>getSolutioncount</B>()</PRE>\r\n<DL>\r\n<DD>Returns the number of equal solutions.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setSolutionlimit(int)\"><!-- --></A><H3>\r\nsetSolutionlimit</H3>\r\n<PRE>\r\npublic void <B>setSolutionlimit</B>(int&nbsp;limit)</PRE>\r\n<DL>\r\n<DD>Sets the solution number that must be returned.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getSolutionlimit()\"><!-- --></A><H3>\r\ngetSolutionlimit</H3>\r\n<PRE>\r\npublic int <B>getSolutionlimit</B>()</PRE>\r\n<DL>\r\n<DD>Returns the solution number that must be returned.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setObjBound(double)\"><!-- --></A><H3>\r\nsetObjBound</H3>\r\n<PRE>\r\npublic void <B>setObjBound</B>(double&nbsp;objBound)</PRE>\r\n<DL>\r\n<DD>Set initial \"at least better than\" guess for objective function.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getObjBound()\"><!-- --></A><H3>\r\ngetObjBound</H3>\r\n<PRE>\r\npublic double <B>getObjBound</B>()</PRE>\r\n<DL>\r\n<DD>Returns initial \"at least better than\" guess for objective function.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBbFloorfirst(int)\"><!-- --></A><H3>\r\nsetBbFloorfirst</H3>\r\n<PRE>\r\npublic void <B>setBbFloorfirst</B>(int&nbsp;floorFirst)</PRE>\r\n<DL>\r\n<DD>Specifies which branch to take first in branch-and-bound algorithm.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getBbFloorfirst()\"><!-- --></A><H3>\r\ngetBbFloorfirst</H3>\r\n<PRE>\r\npublic int <B>getBbFloorfirst</B>()</PRE>\r\n<DL>\r\n<DD>Returns which branch to take first in branch-and-bound algorithm.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setVarBranch(int, int)\"><!-- --></A><H3>\r\nsetVarBranch</H3>\r\n<PRE>\r\npublic void <B>setVarBranch</B>(int&nbsp;colnr,\r\n                         int&nbsp;branchMode)\r\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Specifies, for the specified variable, which branch to take first\r\n in branch-and-bound algorithm.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getVarBranch(int)\"><!-- --></A><H3>\r\ngetVarBranch</H3>\r\n<PRE>\r\npublic int <B>getVarBranch</B>(int&nbsp;colnr)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns, for the specified variable, which branch to take first\r\n in branch-and-bound algorithm.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setVarWeights(double[])\"><!-- --></A><H3>\r\nsetVarWeights</H3>\r\n<PRE>\r\npublic void <B>setVarWeights</B>(double[]&nbsp;weights)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set the weights on variables.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getVarPriority(int)\"><!-- --></A><H3>\r\ngetVarPriority</H3>\r\n<PRE>\r\npublic int <B>getVarPriority</B>(int&nbsp;colnr)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns, for the specified variable, the priority the variable has\r\n in the branch-and-bound algorithm.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBreakAtFirst(boolean)\"><!-- --></A><H3>\r\nsetBreakAtFirst</H3>\r\n<PRE>\r\npublic void <B>setBreakAtFirst</B>(boolean&nbsp;breakAtFirst)</PRE>\r\n<DL>\r\n<DD>Specifies if the branch-and-bound algorithm stops at first found solution.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isBreakAtFirst()\"><!-- --></A><H3>\r\nisBreakAtFirst</H3>\r\n<PRE>\r\npublic boolean <B>isBreakAtFirst</B>()</PRE>\r\n<DL>\r\n<DD>Returns if the branch-and-bound algorithm stops at first found solution.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBreakAtValue(double)\"><!-- --></A><H3>\r\nsetBreakAtValue</H3>\r\n<PRE>\r\npublic void <B>setBreakAtValue</B>(double&nbsp;breakAtValue)</PRE>\r\n<DL>\r\n<DD>Specifies if the branch-and-bound algorithm stops when the object value\r\n is better than a given value.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getBreakAtValue()\"><!-- --></A><H3>\r\ngetBreakAtValue</H3>\r\n<PRE>\r\npublic double <B>getBreakAtValue</B>()</PRE>\r\n<DL>\r\n<DD>Returns the value at which the branch-and-bound algorithm stops\r\n when the object value is better than this value.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setScaling(int)\"><!-- --></A><H3>\r\nsetScaling</H3>\r\n<PRE>\r\npublic void <B>setScaling</B>(int&nbsp;scalemode)</PRE>\r\n<DL>\r\n<DD>Specifies which scaling algorithm must be used.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getScaling()\"><!-- --></A><H3>\r\ngetScaling</H3>\r\n<PRE>\r\npublic int <B>getScaling</B>()</PRE>\r\n<DL>\r\n<DD>Specifies which scaling algorithm is used.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isScalemode(int)\"><!-- --></A><H3>\r\nisScalemode</H3>\r\n<PRE>\r\npublic boolean <B>isScalemode</B>(int&nbsp;testmask)</PRE>\r\n<DL>\r\n<DD>Returns if scaling mode specified in testmask is active.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isScaletype(int)\"><!-- --></A><H3>\r\nisScaletype</H3>\r\n<PRE>\r\npublic boolean <B>isScaletype</B>(int&nbsp;scaletype)</PRE>\r\n<DL>\r\n<DD>Returns if scaling type specified in scaletype is active.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isIntegerscaling()\"><!-- --></A><H3>\r\nisIntegerscaling</H3>\r\n<PRE>\r\npublic boolean <B>isIntegerscaling</B>()</PRE>\r\n<DL>\r\n<DD>Specifies which scaling algorithm is used.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setScalelimit(double)\"><!-- --></A><H3>\r\nsetScalelimit</H3>\r\n<PRE>\r\npublic void <B>setScalelimit</B>(double&nbsp;scalelimit)</PRE>\r\n<DL>\r\n<DD>Sets the relative scaling convergence criterion for the active scaling mode;\r\n the integer part specifies the maximum number of iterations.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getScalelimit()\"><!-- --></A><H3>\r\ngetScalelimit</H3>\r\n<PRE>\r\npublic double <B>getScalelimit</B>()</PRE>\r\n<DL>\r\n<DD>Returns the relative scaling convergence criterion for the active scaling mode;\r\n the integer part specifies the maximum number of iterations.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setImprove(int)\"><!-- --></A><H3>\r\nsetImprove</H3>\r\n<PRE>\r\npublic void <B>setImprove</B>(int&nbsp;improve)</PRE>\r\n<DL>\r\n<DD>Specifies the iterative improvement level.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getImprove()\"><!-- --></A><H3>\r\ngetImprove</H3>\r\n<PRE>\r\npublic int <B>getImprove</B>()</PRE>\r\n<DL>\r\n<DD>Returns the iterative improvement level.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setPivoting(int)\"><!-- --></A><H3>\r\nsetPivoting</H3>\r\n<PRE>\r\npublic void <B>setPivoting</B>(int&nbsp;pivRule)</PRE>\r\n<DL>\r\n<DD>Specifies the pivot rule.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPivoting()\"><!-- --></A><H3>\r\ngetPivoting</H3>\r\n<PRE>\r\npublic int <B>getPivoting</B>()</PRE>\r\n<DL>\r\n<DD>Returns the pivot rule.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isPivMode(int)\"><!-- --></A><H3>\r\nisPivMode</H3>\r\n<PRE>\r\npublic boolean <B>isPivMode</B>(int&nbsp;testmask)</PRE>\r\n<DL>\r\n<DD>Returns if pivot strategy specified in testmask is active.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isPivRule(int)\"><!-- --></A><H3>\r\nisPivRule</H3>\r\n<PRE>\r\npublic boolean <B>isPivRule</B>(int&nbsp;rule)</PRE>\r\n<DL>\r\n<DD>Checks if the specified pivot rule is active.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setPreferdual(boolean)\"><!-- --></A><H3>\r\nsetPreferdual</H3>\r\n<PRE>\r\npublic void <B>setPreferdual</B>(boolean&nbsp;dodual)</PRE>\r\n<DL>\r\n<DD>Sets the desired combination of primal and dual simplex algorithms.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setSimplextype(int)\"><!-- --></A><H3>\r\nsetSimplextype</H3>\r\n<PRE>\r\npublic void <B>setSimplextype</B>(int&nbsp;simplextype)</PRE>\r\n<DL>\r\n<DD>Sets the desired combination of primal and dual simplex algorithms.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getSimplextype()\"><!-- --></A><H3>\r\ngetSimplextype</H3>\r\n<PRE>\r\npublic int <B>getSimplextype</B>()</PRE>\r\n<DL>\r\n<DD>Returns the desired combination of primal and dual simplex algorithms.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setNegrange(double)\"><!-- --></A><H3>\r\nsetNegrange</H3>\r\n<PRE>\r\npublic void <B>setNegrange</B>(double&nbsp;negRange)</PRE>\r\n<DL>\r\n<DD>Set negative value below which variables are split into a negative\r\n and a positive part.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getNegrange()\"><!-- --></A><H3>\r\ngetNegrange</H3>\r\n<PRE>\r\npublic double <B>getNegrange</B>()</PRE>\r\n<DL>\r\n<DD>Returns the negative value below which variables are split\r\n into a negative and a positive part.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getTotalIter()\"><!-- --></A><H3>\r\ngetTotalIter</H3>\r\n<PRE>\r\npublic long <B>getTotalIter</B>()</PRE>\r\n<DL>\r\n<DD>Returns the total number of iterations with Branch-and-bound of the last solution.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getMaxLevel()\"><!-- --></A><H3>\r\ngetMaxLevel</H3>\r\n<PRE>\r\npublic int <B>getMaxLevel</B>()</PRE>\r\n<DL>\r\n<DD>Returns the deepest Branch-and-bound level of the last solution.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getTotalNodes()\"><!-- --></A><H3>\r\ngetTotalNodes</H3>\r\n<PRE>\r\npublic long <B>getTotalNodes</B>()</PRE>\r\n<DL>\r\n<DD>Returns the total number of nodes processed in branch-and-bound.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getNrows()\"><!-- --></A><H3>\r\ngetNrows</H3>\r\n<PRE>\r\npublic int <B>getNrows</B>()</PRE>\r\n<DL>\r\n<DD>Returns the number of rows (constraints) in the problem.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getNorigRows()\"><!-- --></A><H3>\r\ngetNorigRows</H3>\r\n<PRE>\r\npublic int <B>getNorigRows</B>()</PRE>\r\n<DL>\r\n<DD>Returns the number of original rows (constraints) in the problem.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getLrows()\"><!-- --></A><H3>\r\ngetLrows</H3>\r\n<PRE>\r\npublic int <B>getLrows</B>()</PRE>\r\n<DL>\r\n<DD>Returns the number of Lagrangian rows in the lp.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getNcolumns()\"><!-- --></A><H3>\r\ngetNcolumns</H3>\r\n<PRE>\r\npublic int <B>getNcolumns</B>()</PRE>\r\n<DL>\r\n<DD>Returns the number of columns (variables) in the problem.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getNorigColumns()\"><!-- --></A><H3>\r\ngetNorigColumns</H3>\r\n<PRE>\r\npublic int <B>getNorigColumns</B>()</PRE>\r\n<DL>\r\n<DD>Returns the number of original columns (variables) in the problem.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getNonzeros()\"><!-- --></A><H3>\r\ngetNonzeros</H3>\r\n<PRE>\r\npublic int <B>getNonzeros</B>()</PRE>\r\n<DL>\r\n<DD>Returns the number of non-zero elements in the matrix.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getOrigIndex(int)\"><!-- --></A><H3>\r\ngetOrigIndex</H3>\r\n<PRE>\r\npublic int <B>getOrigIndex</B>(int&nbsp;index)</PRE>\r\n<DL>\r\n<DD>Returns the original row/column where a constraint/variable was before presolve.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getLpIndex(int)\"><!-- --></A><H3>\r\ngetLpIndex</H3>\r\n<PRE>\r\npublic int <B>getLpIndex</B>(int&nbsp;index)</PRE>\r\n<DL>\r\n<DD>Returns the index in the lp of the original row/column.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBasis(int[], boolean)\"><!-- --></A><H3>\r\nsetBasis</H3>\r\n<PRE>\r\npublic void <B>setBasis</B>(int[]&nbsp;bascolumn,\r\n                     boolean&nbsp;nonbasic)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Sets an initial basis of the lp.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getBasis(int[], boolean)\"><!-- --></A><H3>\r\ngetBasis</H3>\r\n<PRE>\r\npublic void <B>getBasis</B>(int[]&nbsp;bascolumn,\r\n                     boolean&nbsp;nonbasic)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the basis of the lp.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"resetBasis()\"><!-- --></A><H3>\r\nresetBasis</H3>\r\n<PRE>\r\npublic void <B>resetBasis</B>()</PRE>\r\n<DL>\r\n<DD>Resets the basis to the initial basis.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"defaultBasis()\"><!-- --></A><H3>\r\ndefaultBasis</H3>\r\n<PRE>\r\npublic void <B>defaultBasis</B>()</PRE>\r\n<DL>\r\n<DD>Sets the starting base to an all slack basis (the default simplex starting basis).\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBasiscrash(int)\"><!-- --></A><H3>\r\nsetBasiscrash</H3>\r\n<PRE>\r\npublic void <B>setBasiscrash</B>(int&nbsp;mode)</PRE>\r\n<DL>\r\n<DD>Specifies which basis crash mode must be used.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getBasiscrash()\"><!-- --></A><H3>\r\ngetBasiscrash</H3>\r\n<PRE>\r\npublic int <B>getBasiscrash</B>()</PRE>\r\n<DL>\r\n<DD>Returns which basis crash mode must be used.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"guessBasis(double[], int[])\"><!-- --></A><H3>\r\nguessBasis</H3>\r\n<PRE>\r\npublic void <B>guessBasis</B>(double[] guessvector,&nbsp;int[] basisvector)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Guess a basis for the lp.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"unscale()\"><!-- --></A><H3>\r\nunscale</H3>\r\n<PRE>\r\npublic void <B>unscale</B>()</PRE>\r\n<DL>\r\n<DD>Unscales the model.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBFP(java.lang.String)\"><!-- --></A><H3>\r\nsetBFP</H3>\r\n<PRE>\r\npublic void <B>setBFP</B>(java.lang.String&nbsp;filename)\r\n            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set basis factorization package.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isNativeBFP()\"><!-- --></A><H3>\r\nisNativeBFP</H3>\r\n<PRE>\r\npublic boolean <B>isNativeBFP</B>()</PRE>\r\n<DL>\r\n<DD>Returns if the native (build-in) basis factorization package (BFP) is used,\r\n or an external package.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"hasBFP()\"><!-- --></A><H3>\r\nhasBFP</H3>\r\n<PRE>\r\npublic boolean <B>hasBFP</B>()</PRE>\r\n<DL>\r\n<DD>Returns if there is a basis factorization package (BFP) available.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"solve()\"><!-- --></A><H3>\r\nsolve</H3>\r\n<PRE>\r\npublic int <B>solve</B>()\r\n          throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Solve the model.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getStatustext(int)\"><!-- --></A><H3>\r\ngetStatustext</H3>\r\n<PRE>\r\npublic java.lang.String <B>getStatustext</B>(int&nbsp;statuscode)</PRE>\r\n<DL>\r\n<DD>Returns the description of a returncode of the solve function.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isFeasible(double[], double)\"><!-- --></A><H3>\r\nisFeasible</H3>\r\n<PRE>\r\npublic boolean <B>isFeasible</B>(double[]&nbsp;values,\r\n                          double&nbsp;threshold)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Checks if provided solution is a feasible solution.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getObjective()\"><!-- --></A><H3>\r\ngetObjective</H3>\r\n<PRE>\r\npublic double <B>getObjective</B>()\r\n                    throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the value of the objective function.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getWorkingObjective()\"><!-- --></A><H3>\r\ngetWorkingObjective</H3>\r\n<PRE>\r\npublic double <B>getWorkingObjective</B>()\r\n                           throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the value of the objective function.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getVariables(double[])\"><!-- --></A><H3>\r\ngetVariables</H3>\r\n<PRE>\r\npublic void <B>getVariables</B>(double[]&nbsp;var)\r\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the values of the variables.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrVariables()\"><!-- --></A><H3>\r\ngetPtrVariables</H3>\r\n<PRE>\r\npublic double[] <B>getPtrVariables</B>()\r\n                         throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the values of the variables.\r\n Returned array is allocated by the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getConstraints(double[])\"><!-- --></A><H3>\r\ngetConstraints</H3>\r\n<PRE>\r\npublic void <B>getConstraints</B>(double[]&nbsp;var)\r\n                    throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the values of the constraints.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrConstraints()\"><!-- --></A><H3>\r\ngetPtrConstraints</H3>\r\n<PRE>\r\npublic double[] <B>getPtrConstraints</B>()\r\n                           throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the values of the constraints.\r\n Returned array is allocated by the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPrimalSolution(double[])\"><!-- --></A><H3>\r\ngetPrimalSolution</H3>\r\n<PRE>\r\npublic void <B>getPrimalSolution</B>(double[]&nbsp;pv)\r\n                       throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the solution of the model.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrPrimalSolution()\"><!-- --></A><H3>\r\ngetPtrPrimalSolution</H3>\r\n<PRE>\r\npublic double[] <B>getPtrPrimalSolution</B>()\r\n                              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the solution of the model.\r\n Returned array is allocated by the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getVarPrimalresult(int)\"><!-- --></A><H3>\r\ngetVarPrimalresult</H3>\r\n<PRE>\r\npublic double <B>getVarPrimalresult</B>(int&nbsp;index)\r\n                          throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the solution of the model.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getSensitivityRhs(double[], double[], double[])\"><!-- --></A><H3>\r\ngetSensitivityRhs</H3>\r\n<PRE>\r\npublic void <B>getSensitivityRhs</B>(double[]&nbsp;duals,\r\n                              double[]&nbsp;dualsfrom,\r\n                              double[]&nbsp;dualstill)\r\n                       throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrSensitivityRhs()\"><!-- --></A><H3>\r\ngetPtrSensitivityRhs</H3>\r\n<PRE>\r\npublic double[][] <B>getPtrSensitivityRhs</B>()\r\n                                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n Returned arrays are allocated by the method.\r\n The returned array contains two elements of type double[].\r\n element [0] is the duals array, element [1] is the dualsfrom array,\r\n element [2] is the dualstill array.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getDualSolution(double[])\"><!-- --></A><H3>\r\ngetDualSolution</H3>\r\n<PRE>\r\npublic void <B>getDualSolution</B>(double[]&nbsp;duals)\r\n                     throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrDualSolution()\"><!-- --></A><H3>\r\ngetPtrDualSolution</H3>\r\n<PRE>\r\npublic double[] <B>getPtrDualSolution</B>()\r\n                            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n Returned array is allocated by the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getVarDualresult(int)\"><!-- --></A><H3>\r\ngetVarDualresult</H3>\r\n<PRE>\r\npublic double <B>getVarDualresult</B>(int&nbsp;index)\r\n                        throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the constraints and the variables.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getSensitivityObj(double[], double[])\"><!-- --></A><H3>\r\ngetSensitivityObj</H3>\r\n<PRE>\r\npublic void <B>getSensitivityObj</B>(double[]&nbsp;objfrom,\r\n                              double[]&nbsp;objtill)\r\n                       throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the objective function.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrSensitivityObj()\"><!-- --></A><H3>\r\ngetPtrSensitivityObj</H3>\r\n<PRE>\r\npublic double[][] <B>getPtrSensitivityObj</B>()\r\n                                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the objective function.\r\n Returned arrays are allocated by the method.\r\n The returned array contains two elements of type double[].\r\n element [0] is the objfrom array, element [1] is the objtill array.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getSensitivityObjex(double[], double[], double[], double[])\"><!-- --></A><H3>\r\ngetSensitivityObjex</H3>\r\n<PRE>\r\npublic void <B>getSensitivityObjex</B>(double[]&nbsp;objfrom,\r\n                                double[]&nbsp;objtill,\r\n                                double[]&nbsp;objfromvalue,\r\n                                double[]&nbsp;objtillvalue)\r\n                         throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the objective function.\r\n Passed in arrays must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrSensitivityObjex()\"><!-- --></A><H3>\r\ngetPtrSensitivityObjex</H3>\r\n<PRE>\r\npublic double[][] <B>getPtrSensitivityObjex</B>()\r\n                                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the sensitivity of the objective function.\r\n Returned arrays are allocated by the method.\r\n The returned array contains four elements of type double[].\r\n element [0] is the objfrom array, element [1] is the objtill array,\r\n element [2] is the objfromvalue array, element [3] is the objtillvalue array.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getLambda(double[])\"><!-- --></A><H3>\r\ngetLambda</H3>\r\n<PRE>\r\npublic void <B>getLambda</B>(double[]&nbsp;lambda)\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the Lamdba vectors (Lagrangian optimization).\r\n Passed in array must be allocated by the caller of the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getPtrLambda()\"><!-- --></A><H3>\r\ngetPtrLambda</H3>\r\n<PRE>\r\npublic double[] <B>getPtrLambda</B>()\r\n                      throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Returns the Lamdba vectors (Lagrangian optimization).\r\n Returned array is allocated by the method.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"deleteLp()\"><!-- --></A><H3>\r\ndeleteLp</H3>\r\n<PRE>\r\npublic void <B>deleteLp</B>()</PRE>\r\n<DL>\r\n<DD>Frees all resources allocated to this problem.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"writeLp(java.lang.String)\"><!-- --></A><H3>\r\nwriteLp</H3>\r\n<PRE>\r\npublic void <B>writeLp</B>(java.lang.String&nbsp;filename)\r\n             throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Write an lp model to a file.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"writeMps(java.lang.String)\"><!-- --></A><H3>\r\nwriteMps</H3>\r\n<PRE>\r\npublic void <B>writeMps</B>(java.lang.String&nbsp;filename)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Write an mps model to a file.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"writeFreeMps(java.lang.String)\"><!-- --></A><H3>\r\nwriteFreeMps</H3>\r\n<PRE>\r\npublic void <B>writeFreeMps</B>(java.lang.String&nbsp;filename)\r\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Write a model in free MPS format to a file.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"readBasis(java.lang.String)\"><!-- --></A><H3>\r\nreadBasis</H3>\r\n<PRE>\r\npublic java.lang.String <B>readBasis</B>(java.lang.String&nbsp;filename)\r\n                           throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Read basis from a file and set as default basis. The info text\r\n is returned as method result.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"writeBasis(java.lang.String)\"><!-- --></A><H3>\r\nwriteBasis</H3>\r\n<PRE>\r\npublic void <B>writeBasis</B>(java.lang.String&nbsp;filename)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Writes current basis to a file.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"readParams(java.lang.String, java.lang.String)\"><!-- --></A><H3>\r\nreadParams</H3>\r\n<PRE>\r\npublic void <B>readParams</B>(java.lang.String&nbsp;filename,\r\n                       java.lang.String&nbsp;options)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Read settings from a parameter file.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"writeParams(java.lang.String, java.lang.String)\"><!-- --></A><H3>\r\nwriteParams</H3>\r\n<PRE>\r\npublic void <B>writeParams</B>(java.lang.String&nbsp;filename,\r\n                        java.lang.String&nbsp;options)\r\n                 throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Write settings to a parameter file.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"resetParams()\"><!-- --></A><H3>\r\nresetParams</H3>\r\n<PRE>\r\npublic void <B>resetParams</B>()</PRE>\r\n<DL>\r\n<DD>Resets parameters back to their default values.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printLp()\"><!-- --></A><H3>\r\nprintLp</H3>\r\n<PRE>\r\npublic void <B>printLp</B>()</PRE>\r\n<DL>\r\n<DD>Prints the lp model. This function is meant for debugging purposes.\r\n By default, the output is stdout. However this can be changed via a call\r\n to setOutputfile.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printConstraints(int)\"><!-- --></A><H3>\r\nprintConstraints</H3>\r\n<PRE>\r\npublic void <B>printConstraints</B>(int&nbsp;columns)</PRE>\r\n<DL>\r\n<DD>Prints the values of the constraints of the lp.\r\n This can only be done after a successful solve.\r\n This function is meant for debugging purposes. By default, the output is stdout.\r\n However this can be changed via a call to setOutputfile.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printDuals()\"><!-- --></A><H3>\r\nprintDuals</H3>\r\n<PRE>\r\npublic void <B>printDuals</B>()</PRE>\r\n<DL>\r\n<DD>Prints the values of the duals of the lp.\r\n This can only be done after a successful solve.\r\n This function is meant for debugging purposes. By default, the output is stdout.\r\n However this can be changed via a call to setOutputfile.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printScales()\"><!-- --></A><H3>\r\nprintScales</H3>\r\n<PRE>\r\npublic void <B>printScales</B>()</PRE>\r\n<DL>\r\n<DD>Prints the scales of the lp.\r\n This can only be done after a successful solve.\r\n This function is meant for debugging purposes. By default, the output is stdout.\r\n However this can be changed via a call to setOutputfile.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printTableau()\"><!-- --></A><H3>\r\nprintTableau</H3>\r\n<PRE>\r\npublic void <B>printTableau</B>()</PRE>\r\n<DL>\r\n<DD>Prints the tableau.\r\n This can only be done after a successful solve.\r\n This function is meant for debugging purposes. By default, the output is stdout.\r\n However this can be changed via a call to setOutputfile.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printObjective()\"><!-- --></A><H3>\r\nprintObjective</H3>\r\n<PRE>\r\npublic void <B>printObjective</B>()</PRE>\r\n<DL>\r\n<DD>Prints the objective value of the lp.\r\n This can only be done after a successful solve.\r\n This function is meant for debugging purposes. By default, the output is stdout.\r\n However this can be changed via a call to setOutputfile.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printSolution(int)\"><!-- --></A><H3>\r\nprintSolution</H3>\r\n<PRE>\r\npublic void <B>printSolution</B>(int&nbsp;columns)</PRE>\r\n<DL>\r\n<DD>Prints the solution (variables) of the lp.\r\n This can only be done after a successful solve.\r\n This function is meant for debugging purposes. By default, the output is stdout.\r\n However this can be changed via a call to setOutputfile.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printStr(java.lang.String)\"><!-- --></A><H3>\r\nprintStr</H3>\r\n<PRE>\r\npublic void <B>printStr</B>(java.lang.String&nbsp;str)</PRE>\r\n<DL>\r\n<DD>Prints a string.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setOutputfile(java.lang.String)\"><!-- --></A><H3>\r\nsetOutputfile</H3>\r\n<PRE>\r\npublic void <B>setOutputfile</B>(java.lang.String&nbsp;filename)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Defines the output for the print_* functions.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"printDebugdump(java.lang.String)\"><!-- --></A><H3>\r\nprintDebugdump</H3>\r\n<PRE>\r\npublic void <B>printDebugdump</B>(java.lang.String&nbsp;filename)\r\n                    throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Do a generic readable data dump of key lp_solve model variables;\r\n principally for run difference and debugging purposes.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setXLI(java.lang.String)\"><!-- --></A><H3>\r\nsetXLI</H3>\r\n<PRE>\r\npublic void <B>setXLI</B>(java.lang.String&nbsp;filename)\r\n            throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Set External Language Interfaces package.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"writeXLI(java.lang.String, java.lang.String, boolean)\"><!-- --></A><H3>\r\nwriteXLI</H3>\r\n<PRE>\r\npublic void <B>writeXLI</B>(java.lang.String&nbsp;filename,\r\n                     java.lang.String&nbsp;options,\r\n                     boolean&nbsp;results)\r\n              throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Write a model to a file via the External Language Interface.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"hasXLI()\"><!-- --></A><H3>\r\nhasXLI</H3>\r\n<PRE>\r\npublic boolean <B>hasXLI</B>()</PRE>\r\n<DL>\r\n<DD>Returns if there is an external language interface (XLI) set.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isNativeXLI()\"><!-- --></A><H3>\r\nisNativeXLI</H3>\r\n<PRE>\r\npublic boolean <B>isNativeXLI</B>()</PRE>\r\n<DL>\r\n<DD>Returns if a build-in External Language Interfaces (XLI) is available or not.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getNameindex(java.lang.String, boolean)\"><!-- --></A><H3>\r\ngetNameindex</H3>\r\n<PRE>\r\npublic int <B>getNameindex</B>(java.lang.String&nbsp;name,\r\n                        boolean&nbsp;isRow)</PRE>\r\n<DL>\r\n<DD>Gets the index of a given column or row name in the lp.\r\n A return value of -1 indicates that the name does not exist.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"dualizeLp()\"><!-- --></A><H3>\r\ndualizeLp</H3>\r\n<PRE>\r\npublic void <B>dualizeLp</B>()\r\n               throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Create the dual of the current model.\r\n<P>\r\n<DD><DL>\r\n\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"isUseNames(boolean)\"><!-- --></A><H3>\r\nisUseNames</H3>\r\n<PRE>\r\npublic boolean <B>isUseNames</B>(boolean&nbsp;isRow)</PRE>\r\n<DL>\r\n<DD>Returns if variable or constraint names are used.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setUseNames(boolean, boolean)\"><!-- --></A><H3>\r\nsetUseNames</H3>\r\n<PRE>\r\npublic void <B>setUseNames</B>(boolean&nbsp;isRow,\r\n                        boolean&nbsp;useNames)</PRE>\r\n<DL>\r\n<DD>Sets if variable or constraint names are used.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getConstrValue(int, int, double[], int[])\"><!-- --></A><H3>\r\ngetConstrValue</H3>\r\n<PRE>\r\npublic double <B>getConstrValue</B>(int&nbsp;rownr,\r\n                             int&nbsp;count,\r\n                             double[]&nbsp;primsolution,\r\n                             int[]&nbsp;nzindex)</PRE>\r\n<DL>\r\n<DD>Gets the value of a constraint according to provided variable values.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"setBasisvar(int, int)\"><!-- --></A><H3>\r\nsetBasisvar</H3>\r\n<PRE>\r\npublic int <B>setBasisvar</B>(int&nbsp;basisPos,\r\n                       int&nbsp;enteringCol)</PRE>\r\n<DL>\r\n<DD>This is an internal function that has been published for special purposes. It should generally not be used.\r\n<P>\r\n<DD><DL>\r\n</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"putAbortfunc(lpsolve.AbortListener, java.lang.Object)\"><!-- --></A><H3>\r\nputAbortfunc</H3>\r\n<PRE>\r\npublic void <B>putAbortfunc</B>(<A HREF=\"../lpsolve/AbortListener.html\" title=\"interface in lpsolve\">AbortListener</A>&nbsp;listener,\r\n                         java.lang.Object&nbsp;userhandle)\r\n                  throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Register an <code>AbortListener</code> for callback.\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>listener</CODE> - the listener that should be called by lp_solve<DD><CODE>userhandle</CODE> - an arbitrary object that is passed to the listener on call\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"putLogfunc(lpsolve.LogListener, java.lang.Object)\"><!-- --></A><H3>\r\nputLogfunc</H3>\r\n<PRE>\r\npublic void <B>putLogfunc</B>(<A HREF=\"../lpsolve/LogListener.html\" title=\"interface in lpsolve\">LogListener</A>&nbsp;listener,\r\n                       java.lang.Object&nbsp;userhandle)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Register an <code>LogListener</code> for callback.\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>listener</CODE> - the listener that should be called by lp_solve<DD><CODE>userhandle</CODE> - an arbitrary object that is passed to the listener on call\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"putMsgfunc(lpsolve.MsgListener, java.lang.Object, int)\"><!-- --></A><H3>\r\nputMsgfunc</H3>\r\n<PRE>\r\npublic void <B>putMsgfunc</B>(<A HREF=\"../lpsolve/MsgListener.html\" title=\"interface in lpsolve\">MsgListener</A>&nbsp;listener,\r\n                       java.lang.Object&nbsp;userhandle,\r\n                       int&nbsp;mask)\r\n                throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Register an <code>MsgListener</code> for callback.\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>listener</CODE> - the listener that should be called by lp_solve<DD><CODE>userhandle</CODE> - an arbitrary object that is passed to the listener on call\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"putBbBranchfunc(lpsolve.BbListener, java.lang.Object)\"><!-- --></A><H3>\r\nputBbBranchfunc</H3>\r\n<PRE>\r\npublic void <B>putBbBranchfunc</B>(<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\">BbListener</A>&nbsp;listener,\r\n                            java.lang.Object&nbsp;userhandle)\r\n                     throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Register an <code>BbBranchListener</code> for callback.\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>listener</CODE> - the listener that should be called by lp_solve<DD><CODE>userhandle</CODE> - an arbitrary object that is passed to the listener on call\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"putBbNodefunc(lpsolve.BbListener, java.lang.Object)\"><!-- --></A><H3>\r\nputBbNodefunc</H3>\r\n<PRE>\r\npublic void <B>putBbNodefunc</B>(<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\">BbListener</A>&nbsp;listener,\r\n                          java.lang.Object&nbsp;userhandle)\r\n                   throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>Register an <code>BbNodeListener</code> for callback.\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>listener</CODE> - the listener that should be called by lp_solve<DD><CODE>userhandle</CODE> - an arbitrary object that is passed to the listener on call\r\n<DT><B>Throws:</B>\r\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<!-- ========= END OF CLASS DATA ========= -->\r\n<HR>\r\n\r\n\r\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\r\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\r\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\r\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV CLASS&nbsp;\r\n&nbsp;<A HREF=\"../lpsolve/VersionInfo.html\" title=\"class in lpsolve\"><B>NEXT CLASS</B></A></FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"LpSolve.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\r\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;<A HREF=\"#field_summary\">FIELD</A>&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;<A HREF=\"#field_detail\">FIELD</A>&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\r\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/LpSolveException.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nLpSolveException (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve.LpSolveException class\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"LpSolveException (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV CLASS&nbsp;\r\n&nbsp;NEXT CLASS</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"LpSolveException.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;<A HREF=\"#fields_inherited_from_class_java.lang.Exception\">FIELD</A>&nbsp;|&nbsp;<A HREF=\"#constructor_summary\">CONSTR</A>&nbsp;|&nbsp;<A HREF=\"#methods_inherited_from_class_java.lang.Throwable\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;<A HREF=\"#constructor_detail\">CONSTR</A>&nbsp;|&nbsp;METHOD</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<!-- ======== START OF CLASS DATA ======== -->\r\n<H2>\r\n<FONT SIZE=\"-1\">\r\nlpsolve</FONT>\r\n<BR>\r\nClass LpSolveException</H2>\r\n<PRE>\r\njava.lang.Object\r\n  <IMG SRC=\"../resources/inherit.gif\" ALT=\"extended by\">java.lang.Throwable\r\n      <IMG SRC=\"../resources/inherit.gif\" ALT=\"extended by\">java.lang.Exception\r\n          <IMG SRC=\"../resources/inherit.gif\" ALT=\"extended by\"><B>lpsolve.LpSolveException</B>\r\n</PRE>\r\n<DL>\r\n<DT><B>All Implemented Interfaces:</B> <DD>java.io.Serializable</DD>\r\n</DL>\r\n<HR>\r\n<DL>\r\n<DT>public class <B>LpSolveException</B><DT>extends java.lang.Exception</DL>\r\n\r\n<P>\r\nException thrown by the native methods in the C stub DLL.\r\n<P>\r\n\r\n<P>\r\n<DL>\r\n<DT><B>Author:</B></DT>\n  <DD>Juergen Ebert</DD>\n<DT><B>See Also:</B><DD><A HREF=\"../serialized-form.html#lpsolve.LpSolveException\">Serialized Form</A></DL>\r\n<HR>\r\n\r\n<P>\r\n<!-- ======== NESTED CLASS SUMMARY ======== -->\r\n\r\n\r\n<!-- =========== FIELD SUMMARY =========== -->\r\n\r\n<A NAME=\"field_summary\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Field Summary</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;<A NAME=\"fields_inherited_from_class_java.lang.Exception\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#EEEEFF\" CLASS=\"TableSubHeadingColor\">\r\n<TD><B>Fields inherited from class java.lang.Exception</B></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD><CODE></CODE></TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<!-- ======== CONSTRUCTOR SUMMARY ======== -->\r\n\r\n<A NAME=\"constructor_summary\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Constructor Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolveException.html#LpSolveException()\">LpSolveException</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD><CODE><B><A HREF=\"../lpsolve/LpSolveException.html#LpSolveException(java.lang.String)\">LpSolveException</A></B>(java.lang.String&nbsp;arg0)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<!-- ========== METHOD SUMMARY =========== -->\r\n\r\n<A NAME=\"methods_inherited_from_class_java.lang.Throwable\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#EEEEFF\" CLASS=\"TableSubHeadingColor\">\r\n<TD><B>Methods inherited from class java.lang.Throwable</B></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD><CODE>fillInStackTrace, getCause, getLocalizedMessage, getMessage, getStackTrace, initCause, printStackTrace, printStackTrace, printStackTrace, setStackTrace, toString</CODE></TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;<A NAME=\"methods_inherited_from_class_java.lang.Object\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#EEEEFF\" CLASS=\"TableSubHeadingColor\">\r\n<TD><B>Methods inherited from class java.lang.Object</B></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD><CODE>clone, equals, finalize, getClass, hashCode, notify, notifyAll, wait, wait, wait</CODE></TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<P>\r\n\r\n<!-- ============ FIELD DETAIL =========== -->\r\n\r\n\r\n<!-- ========= CONSTRUCTOR DETAIL ======== -->\r\n\r\n<A NAME=\"constructor_detail\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Constructor Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"LpSolveException()\"><!-- --></A><H3>\r\nLpSolveException</H3>\r\n<PRE>\r\npublic <B>LpSolveException</B>()</PRE>\r\n<DL>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"LpSolveException(java.lang.String)\"><!-- --></A><H3>\r\nLpSolveException</H3>\r\n<PRE>\r\npublic <B>LpSolveException</B>(java.lang.String&nbsp;arg0)</PRE>\r\n<DL>\r\n<DT><B>Parameters:</B><DD><CODE>arg0</CODE> - </DL>\r\n\r\n<!-- ============ METHOD DETAIL ========== -->\r\n\r\n<!-- ========= END OF CLASS DATA ========= -->\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV CLASS&nbsp;\r\n&nbsp;NEXT CLASS</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"LpSolveException.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;<A HREF=\"#fields_inherited_from_class_java.lang.Exception\">FIELD</A>&nbsp;|&nbsp;<A HREF=\"#constructor_summary\">CONSTR</A>&nbsp;|&nbsp;<A HREF=\"#methods_inherited_from_class_java.lang.Throwable\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;<A HREF=\"#constructor_detail\">CONSTR</A>&nbsp;|&nbsp;METHOD</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/MsgListener.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nMsgListener (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve.MsgListener interface\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"MsgListener (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;<A HREF=\"../lpsolve/LogListener.html\" title=\"interface in lpsolve\"><B>PREV CLASS</B></A>&nbsp;\r\n&nbsp;NEXT CLASS</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"MsgListener.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<!-- ======== START OF CLASS DATA ======== -->\r\n<H2>\r\n<FONT SIZE=\"-1\">\r\nlpsolve</FONT>\r\n<BR>\r\nInterface MsgListener</H2>\r\n<HR>\r\n<DL>\r\n<DT>public interface <B>MsgListener</B></DL>\r\n\r\n<P>\r\nClasses that implement this interface may be passed\n to the <code>putMsgfunc</code> method of the <code>LpSolve</code> class.\r\n<P>\r\n\r\n<P>\r\n<DL>\r\n<DT><B>Author:</B></DT>\n  <DD>Juergen Ebert</DD>\n<DT><B>See Also:</B><DD><A HREF=\"../lpsolve/LpSolve.html#putMsgfunc(lpsolve.MsgListener, java.lang.Object, int)\"><CODE>LpSolve.putMsgfunc(lpsolve.MsgListener, java.lang.Object, int)</CODE></A>, \n\"lp_solve documentation for 'put_msgfunc'\"</DL>\r\n<HR>\r\n\r\n<P>\r\n<!-- ======== NESTED CLASS SUMMARY ======== -->\r\n\r\n\r\n<!-- =========== FIELD SUMMARY =========== -->\r\n\r\n\r\n<!-- ======== CONSTRUCTOR SUMMARY ======== -->\r\n\r\n\r\n<!-- ========== METHOD SUMMARY =========== -->\r\n\r\n<A NAME=\"method_summary\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Method Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;void</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/MsgListener.html#msgfunc(lpsolve.LpSolve, java.lang.Object, int)\">msgfunc</A></B>(<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>&nbsp;problem,\n        java.lang.Object&nbsp;userhandle,\n        int&nbsp;msg)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;This routine is called when a situation specified in the mask parameter\n of putMsgfunc occurs. \n </TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<P>\r\n\r\n<!-- ============ FIELD DETAIL =========== -->\r\n\r\n\r\n<!-- ========= CONSTRUCTOR DETAIL ======== -->\r\n\r\n\r\n<!-- ============ METHOD DETAIL ========== -->\r\n\r\n<A NAME=\"method_detail\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Method Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"msgfunc(lpsolve.LpSolve, java.lang.Object, int)\"><!-- --></A><H3>\r\nmsgfunc</H3>\r\n<PRE>\r\npublic void <B>msgfunc</B>(<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A>&nbsp;problem,\n                    java.lang.Object&nbsp;userhandle,\n                    int&nbsp;msg)\n             throws <A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></PRE>\r\n<DL>\r\n<DD>This routine is called when a situation specified in the mask parameter\n of putMsgfunc occurs. \n Note that this routine is called while solving the model. \n This can be usefull to follow the solving progress.\r\n<P>\r\n<DD><DL>\r\n<DT><B>Parameters:</B><DD><CODE>problem</CODE> - the problem this Listener was defined for<DD><CODE>userhandle</CODE> - the userhandle object that was passed to <code>putMsgfunc</code><DD><CODE>msg</CODE> - event code why this method was called\n<DT><B>Throws:</B>\n<DD><CODE><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></CODE></DL>\r\n</DD>\r\n</DL>\r\n<!-- ========= END OF CLASS DATA ========= -->\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;<A HREF=\"../lpsolve/LogListener.html\" title=\"interface in lpsolve\"><B>PREV CLASS</B></A>&nbsp;\r\n&nbsp;NEXT CLASS</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"MsgListener.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;CONSTR&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/VersionInfo.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nVersionInfo (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve.VersionInfo class\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"VersionInfo (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\"><B>PREV CLASS</B></A>&nbsp;\r\n&nbsp;NEXT CLASS</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"VersionInfo.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;<A HREF=\"#constructor_summary\">CONSTR</A>&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;<A HREF=\"#constructor_detail\">CONSTR</A>&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<!-- ======== START OF CLASS DATA ======== -->\r\n<H2>\r\n<FONT SIZE=\"-1\">\r\nlpsolve</FONT>\r\n<BR>\r\nClass VersionInfo</H2>\r\n<PRE>\r\njava.lang.Object\r\n  <IMG SRC=\"../resources/inherit.gif\" ALT=\"extended by\"><B>lpsolve.VersionInfo</B>\r\n</PRE>\r\n<HR>\r\n<DL>\r\n<DT>public class <B>VersionInfo</B><DT>extends java.lang.Object</DL>\r\n\r\n<P>\r\nContains the full version info for a lp_solve library instance.\r\n<P>\r\n\r\n<P>\r\n<DL>\r\n<DT><B>Author:</B></DT>\n  <DD>Juergen Ebert</DD>\n</DL>\r\n<HR>\r\n\r\n<P>\r\n<!-- ======== NESTED CLASS SUMMARY ======== -->\r\n\r\n\r\n<!-- =========== FIELD SUMMARY =========== -->\r\n\r\n\r\n<!-- ======== CONSTRUCTOR SUMMARY ======== -->\r\n\r\n<A NAME=\"constructor_summary\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Constructor Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD><CODE><B><A HREF=\"../lpsolve/VersionInfo.html#VersionInfo(int, int, int, int)\">VersionInfo</A></B>(int&nbsp;major,\n            int&nbsp;minor,\n            int&nbsp;release,\n            int&nbsp;build)</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;Creates a new instance of this class</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<!-- ========== METHOD SUMMARY =========== -->\r\n\r\n<A NAME=\"method_summary\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Method Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/VersionInfo.html#getBuild()\">getBuild</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/VersionInfo.html#getMajorversion()\">getMajorversion</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/VersionInfo.html#getMinorversion()\">getMinorversion</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD ALIGN=\"right\" VALIGN=\"top\" WIDTH=\"1%\"><FONT SIZE=\"-1\">\r\n<CODE>&nbsp;int</CODE></FONT></TD>\r\n<TD><CODE><B><A HREF=\"../lpsolve/VersionInfo.html#getRelease()\">getRelease</A></B>()</CODE>\r\n\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;<A NAME=\"methods_inherited_from_class_java.lang.Object\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#EEEEFF\" CLASS=\"TableSubHeadingColor\">\r\n<TD><B>Methods inherited from class java.lang.Object</B></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD><CODE>clone, equals, finalize, getClass, hashCode, notify, notifyAll, toString, wait, wait, wait</CODE></TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n<P>\r\n\r\n<!-- ============ FIELD DETAIL =========== -->\r\n\r\n\r\n<!-- ========= CONSTRUCTOR DETAIL ======== -->\r\n\r\n<A NAME=\"constructor_detail\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Constructor Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"VersionInfo(int, int, int, int)\"><!-- --></A><H3>\r\nVersionInfo</H3>\r\n<PRE>\r\npublic <B>VersionInfo</B>(int&nbsp;major,\n                   int&nbsp;minor,\n                   int&nbsp;release,\n                   int&nbsp;build)</PRE>\r\n<DL>\r\n<DD>Creates a new instance of this class\r\n<P>\r\n</DL>\r\n\r\n<!-- ============ METHOD DETAIL ========== -->\r\n\r\n<A NAME=\"method_detail\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=1><FONT SIZE=\"+2\">\r\n<B>Method Detail</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<A NAME=\"getBuild()\"><!-- --></A><H3>\r\ngetBuild</H3>\r\n<PRE>\r\npublic int <B>getBuild</B>()</PRE>\r\n<DL>\r\n<DD><DL>\r\n\n<DT><B>Returns:</B><DD>value of the build attribute</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getMajorversion()\"><!-- --></A><H3>\r\ngetMajorversion</H3>\r\n<PRE>\r\npublic int <B>getMajorversion</B>()</PRE>\r\n<DL>\r\n<DD><DL>\r\n\n<DT><B>Returns:</B><DD>value of the majorversion attribute</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getMinorversion()\"><!-- --></A><H3>\r\ngetMinorversion</H3>\r\n<PRE>\r\npublic int <B>getMinorversion</B>()</PRE>\r\n<DL>\r\n<DD><DL>\r\n\n<DT><B>Returns:</B><DD>value of the minorversion attribute</DL>\r\n</DD>\r\n</DL>\r\n<HR>\r\n\r\n<A NAME=\"getRelease()\"><!-- --></A><H3>\r\ngetRelease</H3>\r\n<PRE>\r\npublic int <B>getRelease</B>()</PRE>\r\n<DL>\r\n<DD><DL>\r\n\n<DT><B>Returns:</B><DD>value of the release attribute</DL>\r\n</DD>\r\n</DL>\r\n<!-- ========= END OF CLASS DATA ========= -->\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Class</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\"><B>PREV CLASS</B></A>&nbsp;\r\n&nbsp;NEXT CLASS</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"VersionInfo.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n<TR>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\n  SUMMARY:&nbsp;NESTED&nbsp;|&nbsp;FIELD&nbsp;|&nbsp;<A HREF=\"#constructor_summary\">CONSTR</A>&nbsp;|&nbsp;<A HREF=\"#method_summary\">METHOD</A></FONT></TD>\r\n<TD VALIGN=\"top\" CLASS=\"NavBarCell3\"><FONT SIZE=\"-2\">\r\nDETAIL:&nbsp;FIELD&nbsp;|&nbsp;<A HREF=\"#constructor_detail\">CONSTR</A>&nbsp;|&nbsp;<A HREF=\"#method_detail\">METHOD</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/package-frame.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nlpsolve (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve package\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\">\r\n<FONT size=\"+1\" CLASS=\"FrameTitleFont\">\r\n<A HREF=\"../lpsolve/package-summary.html\" target=\"classFrame\">lpsolve</A></FONT>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" SUMMARY=\"\">\r\n<TR>\r\n<TD NOWRAP><FONT size=\"+1\" CLASS=\"FrameHeadingFont\">\r\nInterfaces</FONT>&nbsp;\r\n<FONT CLASS=\"FrameItemFont\">\r\n<BR>\r\n<A HREF=\"AbortListener.html\" title=\"interface in lpsolve\" target=\"classFrame\"><I>AbortListener</I></A>\r\n<BR>\r\n<A HREF=\"BbListener.html\" title=\"interface in lpsolve\" target=\"classFrame\"><I>BbListener</I></A>\r\n<BR>\r\n<A HREF=\"LogListener.html\" title=\"interface in lpsolve\" target=\"classFrame\"><I>LogListener</I></A>\r\n<BR>\r\n<A HREF=\"MsgListener.html\" title=\"interface in lpsolve\" target=\"classFrame\"><I>MsgListener</I></A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n\n<TABLE BORDER=\"0\" WIDTH=\"100%\" SUMMARY=\"\">\r\n<TR>\r\n<TD NOWRAP><FONT size=\"+1\" CLASS=\"FrameHeadingFont\">\r\nClasses</FONT>&nbsp;\r\n<FONT CLASS=\"FrameItemFont\">\r\n<BR>\r\n<A HREF=\"LpSolve.html\" title=\"class in lpsolve\" target=\"classFrame\">LpSolve</A>\r\n<BR>\r\n<A HREF=\"VersionInfo.html\" title=\"class in lpsolve\" target=\"classFrame\">VersionInfo</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n\n<TABLE BORDER=\"0\" WIDTH=\"100%\" SUMMARY=\"\">\r\n<TR>\r\n<TD NOWRAP><FONT size=\"+1\" CLASS=\"FrameHeadingFont\">\r\nExceptions</FONT>&nbsp;\r\n<FONT CLASS=\"FrameItemFont\">\r\n<BR>\r\n<A HREF=\"LpSolveException.html\" title=\"class in lpsolve\" target=\"classFrame\">LpSolveException</A></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/package-summary.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nlpsolve (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n<META NAME=\"keywords\" CONTENT=\"lpsolve package\">\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"lpsolve (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Package</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV PACKAGE&nbsp;\r\n&nbsp;NEXT PACKAGE</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"package-summary.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<H2>\r\nPackage lpsolve\r\n</H2>\r\nThis package contains the files for the Java wrapper for the lp_solve optimization library.\r\n\r\n<P>\r\n<B>See:</B>\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<A HREF=\"#package_description\"><B>Description</B></A>\r\n<P>\r\n\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Interface Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD WIDTH=\"15%\"><B><A HREF=\"../lpsolve/AbortListener.html\" title=\"interface in lpsolve\">AbortListener</A></B></TD>\r\n<TD>Classes that implement this interface may be passed\n to the <code>putAbortfunc</code> method of the <code>LpSolve</code> class.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD WIDTH=\"15%\"><B><A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\">BbListener</A></B></TD>\r\n<TD>Classes that implement this interface may be passed\n to the <code>putbbBranchfunc</code> and <code>putbbNodefunc</code> method \n of the <code>LpSolve</code> class.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD WIDTH=\"15%\"><B><A HREF=\"../lpsolve/LogListener.html\" title=\"interface in lpsolve\">LogListener</A></B></TD>\r\n<TD>Classes that implement this interface may be passed\n to the <code>putLogfunc</code> method of the <code>LpSolve</code> class.</TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD WIDTH=\"15%\"><B><A HREF=\"../lpsolve/MsgListener.html\" title=\"interface in lpsolve\">MsgListener</A></B></TD>\r\n<TD>Classes that implement this interface may be passed\n to the <code>putMsgfunc</code> method of the <code>LpSolve</code> class.</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n\r\n<P>\r\n\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Class Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD WIDTH=\"15%\"><B><A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\">LpSolve</A></B></TD>\r\n<TD>Object wrapper for a problem structure of the lp_solve library.\n </TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD WIDTH=\"15%\"><B><A HREF=\"../lpsolve/VersionInfo.html\" title=\"class in lpsolve\">VersionInfo</A></B></TD>\r\n<TD>Contains the full version info for a lp_solve library instance.</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n\r\n<P>\r\n\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Exception Summary</B></FONT></TD>\r\n</TR>\r\n<TR BGCOLOR=\"white\" CLASS=\"TableRowColor\">\r\n<TD WIDTH=\"15%\"><B><A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\">LpSolveException</A></B></TD>\r\n<TD>Exception thrown by the native methods in the C stub DLL.</TD>\r\n</TR>\r\n</TABLE>\r\n&nbsp;\r\n\r\n<P>\r\n<A NAME=\"package_description\"><!-- --></A><H2>\r\nPackage lpsolve Description\r\n</H2>\r\n\r\n<P>\r\n<p>This package contains the files for the Java wrapper for the lp_solve optimization library.\r\nSee the file <a href=\"..\\..\\..\\README.html\">README.html</a> in the root direcory of the distribution\r\narchive for details.</p>\r\n<P>\r\n\r\n<P>\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Package</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV PACKAGE&nbsp;\r\n&nbsp;NEXT PACKAGE</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"package-summary.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/lpsolve/package-tree.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nlpsolve Class Hierarchy (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"../stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"lpsolve Class Hierarchy (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Tree</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"package-tree.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<CENTER>\r\n<H2>\r\nHierarchy For Package lpsolve\r\n</H2>\r\n</CENTER>\r\n<H2>\r\nClass Hierarchy\r\n</H2>\r\n<UL>\r\n<LI TYPE=\"circle\">class java.lang.Object<UL>\r\n<LI TYPE=\"circle\">class lpsolve.<A HREF=\"../lpsolve/LpSolve.html\" title=\"class in lpsolve\"><B>LpSolve</B></A><LI TYPE=\"circle\">class java.lang.Throwable (implements java.io.Serializable)\r\n<UL>\r\n<LI TYPE=\"circle\">class java.lang.Exception<UL>\r\n<LI TYPE=\"circle\">class lpsolve.<A HREF=\"../lpsolve/LpSolveException.html\" title=\"class in lpsolve\"><B>LpSolveException</B></A></UL>\r\n</UL>\r\n<LI TYPE=\"circle\">class lpsolve.<A HREF=\"../lpsolve/VersionInfo.html\" title=\"class in lpsolve\"><B>VersionInfo</B></A></UL>\r\n</UL>\r\n<H2>\r\nInterface Hierarchy\r\n</H2>\r\n<UL>\r\n<LI TYPE=\"circle\">interface lpsolve.<A HREF=\"../lpsolve/AbortListener.html\" title=\"interface in lpsolve\"><B>AbortListener</B></A><LI TYPE=\"circle\">interface lpsolve.<A HREF=\"../lpsolve/BbListener.html\" title=\"interface in lpsolve\"><B>BbListener</B></A><LI TYPE=\"circle\">interface lpsolve.<A HREF=\"../lpsolve/LogListener.html\" title=\"interface in lpsolve\"><B>LogListener</B></A><LI TYPE=\"circle\">interface lpsolve.<A HREF=\"../lpsolve/MsgListener.html\" title=\"interface in lpsolve\"><B>MsgListener</B></A></UL>\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"package-summary.html\"><FONT CLASS=\"NavBarFont1\"><B>Package</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Tree</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"../help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"../index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"package-tree.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"../allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/overview-tree.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:56 CEST 2005 -->\r\n<TITLE>\r\nClass Hierarchy (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"Class Hierarchy (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Tree</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"overview-tree.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<CENTER>\r\n<H2>\r\nHierarchy For All Packages</H2>\r\n</CENTER>\r\n<DL>\r\n<DT><B>Package Hierarchies:</B><DD><A HREF=\"lpsolve/package-tree.html\">lpsolve</A></DL>\r\n<HR>\r\n<H2>\r\nClass Hierarchy\r\n</H2>\r\n<UL>\r\n<LI TYPE=\"circle\">class java.lang.Object<UL>\r\n<LI TYPE=\"circle\">class lpsolve.<A HREF=\"lpsolve/LpSolve.html\" title=\"class in lpsolve\"><B>LpSolve</B></A><LI TYPE=\"circle\">class java.lang.Throwable (implements java.io.Serializable)\r\n<UL>\r\n<LI TYPE=\"circle\">class java.lang.Exception<UL>\r\n<LI TYPE=\"circle\">class lpsolve.<A HREF=\"lpsolve/LpSolveException.html\" title=\"class in lpsolve\"><B>LpSolveException</B></A></UL>\r\n</UL>\r\n<LI TYPE=\"circle\">class lpsolve.<A HREF=\"lpsolve/VersionInfo.html\" title=\"class in lpsolve\"><B>VersionInfo</B></A></UL>\r\n</UL>\r\n<H2>\r\nInterface Hierarchy\r\n</H2>\r\n<UL>\r\n<LI TYPE=\"circle\">interface lpsolve.<A HREF=\"lpsolve/AbortListener.html\" title=\"interface in lpsolve\"><B>AbortListener</B></A><LI TYPE=\"circle\">interface lpsolve.<A HREF=\"lpsolve/BbListener.html\" title=\"interface in lpsolve\"><B>BbListener</B></A><LI TYPE=\"circle\">interface lpsolve.<A HREF=\"lpsolve/LogListener.html\" title=\"interface in lpsolve\"><B>LogListener</B></A><LI TYPE=\"circle\">interface lpsolve.<A HREF=\"lpsolve/MsgListener.html\" title=\"interface in lpsolve\"><B>MsgListener</B></A></UL>\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#FFFFFF\" CLASS=\"NavBarCell1Rev\"> &nbsp;<FONT CLASS=\"NavBarFont1Rev\"><B>Tree</B></FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"overview-tree.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/package-list",
    "content": "lpsolve\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/packages.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\n (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\" (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n<BR>\r\n\r\n<BR>\r\n\r\n<BR>\r\n<CENTER>\r\nThe front page has been relocated.Please see:\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<A HREF=\"index.html\">Frame version</A>\r\n<BR>\r\n&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;&nbsp;<A HREF=\"lpsolve/package-summary.html\">Non-frame version.</A></CENTER>\r\n\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/serialized-form.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 4.01 Transitional//EN\" \"http://www.w3.org/TR/html4/loose.dtd\">\r\n<!--NewPage-->\r\n<HTML>\r\n<HEAD>\r\n<!-- Generated by javadoc (build 1.4.2_02) on Sun Jun 26 18:11:57 CEST 2005 -->\r\n<TITLE>\r\nSerialized Form (Using lp_solve in Java programs)\r\n</TITLE>\r\n\r\n\r\n<LINK REL =\"stylesheet\" TYPE=\"text/css\" HREF=\"stylesheet.css\" TITLE=\"Style\">\r\n\r\n<SCRIPT type=\"text/javascript\">\r\nfunction windowTitle()\r\n{\r\n    parent.document.title=\"Serialized Form (Using lp_solve in Java programs)\";\r\n}\r\n</SCRIPT>\r\n\r\n</HEAD>\r\n\r\n<BODY BGCOLOR=\"white\" onload=\"windowTitle();\">\r\n\r\n\n<!-- ========= START OF TOP NAVBAR ======= -->\r\n<A NAME=\"navbar_top\"><!-- --></A>\n<A HREF=\"#skip-navbar_top\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_top_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"serialized-form.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_top\"></A>\n<!-- ========= END OF TOP NAVBAR ========= -->\r\n\r\n<HR>\r\n<CENTER>\r\n<H1>\r\nSerialized Form</H1>\r\n</CENTER>\r\n<HR SIZE=\"4\" NOSHADE>\r\n\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableSubHeadingColor\">\r\n<TD ALIGN=\"center\"><FONT SIZE=\"+2\">\r\n<B>Package</B> <B>lpsolve</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<P>\r\n<A NAME=\"lpsolve.LpSolveException\"><!-- --></A>\n<TABLE BORDER=\"1\" WIDTH=\"100%\" CELLPADDING=\"3\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR BGCOLOR=\"#CCCCFF\" CLASS=\"TableSubHeadingColor\">\r\n<TD COLSPAN=2><FONT SIZE=\"+2\">\r\n<B>Class <A HREF=\"lpsolve/LpSolveException.html\" title=\"class in lpsolve\">lpsolve.LpSolveException</A> extends java.lang.Exception implements Serializable</B></FONT></TD>\r\n</TR>\r\n</TABLE>\r\n\r\n<P>\r\n\r\n<P>\r\n<HR>\r\n\r\n\n<!-- ======= START OF BOTTOM NAVBAR ====== -->\r\n<A NAME=\"navbar_bottom\"><!-- --></A>\n<A HREF=\"#skip-navbar_bottom\" title=\"Skip navigation links\"></A>\n<TABLE BORDER=\"0\" WIDTH=\"100%\" CELLPADDING=\"1\" CELLSPACING=\"0\" SUMMARY=\"\">\r\n<TR>\r\n<TD COLSPAN=3 BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">\r\n<A NAME=\"navbar_bottom_firstrow\"><!-- --></A>\n<TABLE BORDER=\"0\" CELLPADDING=\"0\" CELLSPACING=\"3\" SUMMARY=\"\">\r\n  <TR ALIGN=\"center\" VALIGN=\"top\">\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Package</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <FONT CLASS=\"NavBarFont1\">Class</FONT>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"lpsolve/package-tree.html\"><FONT CLASS=\"NavBarFont1\"><B>Tree</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"deprecated-list.html\"><FONT CLASS=\"NavBarFont1\"><B>Deprecated</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"index-all.html\"><FONT CLASS=\"NavBarFont1\"><B>Index</B></FONT></A>&nbsp;</TD>\r\n  <TD BGCOLOR=\"#EEEEFF\" CLASS=\"NavBarCell1\">    <A HREF=\"help-doc.html\"><FONT CLASS=\"NavBarFont1\"><B>Help</B></FONT></A>&nbsp;</TD>\r\n  </TR>\r\n</TABLE>\r\n</TD>\r\n<TD ALIGN=\"right\" VALIGN=\"top\" ROWSPAN=3><EM>\r\n</EM>\r\n</TD>\r\n</TR>\r\n\r\n<TR>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n&nbsp;PREV&nbsp;\r\n&nbsp;NEXT</FONT></TD>\r\n<TD BGCOLOR=\"white\" CLASS=\"NavBarCell2\"><FONT SIZE=\"-2\">\r\n  <A HREF=\"index.html\" target=\"_top\"><B>FRAMES</B></A>  &nbsp;\r\n&nbsp;<A HREF=\"serialized-form.html\" target=\"_top\"><B>NO FRAMES</B></A>  &nbsp;\r\n&nbsp;<SCRIPT type=\"text/javascript\">\r\n  <!--\r\n  if(window==top) {\r\n    document.writeln('<A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>');\r\n  }\r\n  //-->\r\n</SCRIPT>\r\n<NOSCRIPT>\r\n  <A HREF=\"allclasses-noframe.html\"><B>All Classes</B></A>\r\n</NOSCRIPT>\n\r\n</FONT></TD>\r\n</TR>\r\n</TABLE>\r\n<A NAME=\"skip-navbar_bottom\"></A>\n<!-- ======== END OF BOTTOM NAVBAR ======= -->\r\n\r\n<HR>\r\nCopyright  2004 - Juergen Ebert\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/api/stylesheet.css",
    "content": "/* Javadoc style sheet */\r\n\r\n/* Define colors, fonts and other style attributes here to override the defaults */\r\n\r\n/* Page background color */\r\nbody { background-color: #FFFFFF }\r\n\r\n/* Headings */\r\nh1 { font-size: 145% }\r\n\r\n/* Table colors */\r\n.TableHeadingColor     { background: #CCCCFF } /* Dark mauve */\r\n.TableSubHeadingColor  { background: #EEEEFF } /* Light mauve */\r\n.TableRowColor         { background: #FFFFFF } /* White */\r\n\r\n/* Font used in left-hand frame lists */\r\n.FrameTitleFont   { font-size: 100%; font-family: Helvetica, Arial, sans-serif }\r\n.FrameHeadingFont { font-size:  90%; font-family: Helvetica, Arial, sans-serif }\r\n.FrameItemFont    { font-size:  90%; font-family: Helvetica, Arial, sans-serif }\r\n\r\n/* Navigation bar fonts and colors */\r\n.NavBarCell1    { background-color:#EEEEFF;} /* Light mauve */\r\n.NavBarCell1Rev { background-color:#00008B;} /* Dark Blue */\r\n.NavBarFont1    { font-family: Arial, Helvetica, sans-serif; color:#000000;}\r\n.NavBarFont1Rev { font-family: Arial, Helvetica, sans-serif; color:#FFFFFF;}\r\n\r\n.NavBarCell2    { font-family: Arial, Helvetica, sans-serif; background-color:#FFFFFF;}\r\n.NavBarCell3    { font-family: Arial, Helvetica, sans-serif; background-color:#FFFFFF;}\r\n\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/docs/reference.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 3.2 Final//EN\">\r\n<html>\r\n<head>\r\n<title>lp_solve 5.5 Java Wrapper - Function Reference</title>\r\n<style type=\"text/css\">\r\n<!--\r\nbody  { font-family: Verdana, Arial, Helvetica, sans-serif; }\r\ntd,th\t{ text-align:left; }\r\nli\t\t{ margin-top: 3px; }\r\npre\t\t{ font-size: smaller; }\r\n-->\r\n</style>\r\n\r\n</head>\r\n\r\n<body>\r\n\r\n<h1>Using lp_solve 5.5 in Java programs</h1>\r\n\r\n<h2>C - Java function reference</h2>\r\n\r\n<p>This file contains a reference for all methods in the lp_solve library and the Java wrapper.\r\nThe first column of the following table contains the C functions of the lp_solve library,\r\nthe second column the corresponding methods of the Java wrapper.</p>\r\n\r\n\r\n<table border=\"1\">\r\n<tr><th>C function</th><th>Java wrapper method (LpSolve class)</th></tr>\r\n<tr><td>unsigned char add_column (lprec* lp, REAL* column)</td><td>void addColumn(double[] column) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char add_columnex (lprec* lp, int count, REAL* column, int* rowno)</td><td>void addColumnex(int count, double[] column, int[] rowno) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char add_constraint (lprec* lp, REAL *row, int constr_type, REAL rh)</td><td>void addConstraint(double[] row, int constrType, double rh) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char add_constraintex (lprec *lp, int count, REAL *row, int *colno, int constr_type, REAL rh)</td><td>void addConstraintex(int count, double[] row, int[] colno, int constrType, double rh) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char add_lag_con (lprec* lp, REAL *row, int con_type, REAL rhs)</td><td>void addLagCon(double[] row, int constrType, double rh) throws LpSolveException</td></tr>\r\n<tr><td>int add_SOS (lprec* lp, char *name, int sostype, int priority, int count, int *sosvars, REAL *weights)</td><td>void addSOS(String name, int sostype, int priority, int count, int[] sosvars, double[] weights) throws LpSolveException</td></tr>\r\n<tr><td>int column_in_lp (lprec* lp, REAL *column)</td><td>int columnInLp(double[] column)</td></tr>\r\n<tr><td>void default_basis (lprec* lp)</td><td>void defaultBasis()</td></tr>\r\n<tr><td>unsigned char del_column(lprec *lp, int column)</td><td>void delColumn(int columnnr) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char del_constraint(lprec *lp, int del_row)</td><td>void delConstraint(int rownr) throws LpSolveException</td></tr>\r\n<tr><td>void delete_lp(lprec *lp)</td><td>void deleteLp()</td></tr>\r\n<tr><td>void free_lp(lprec **plp)</td><td><strong>&lt;Not implemented, use deleteLp() instead&gt;</strong></td></tr>\r\n<tr><td>int get_anti_degen(lprec *lp)</td><td>int getAntiDegen()</td></tr>\r\n<tr><td>void get_basis(lprec *lp, int *bascolumn, unsigned char nonbasic)</td><td>void getBasis(int[] bascolumn, boolean nonbasic)</td></tr>\r\n<tr><td>int get_basiscrash(lprec *lp)</td><td>int getBasiscrash()</td></tr>\r\n<tr><td>int get_bb_depthlimit(lprec *lp)</td><td>int getBbDepthlimit()</td></tr>\r\n<tr><td>int get_bb_floorfirst(lprec *lp)</td><td>int getBbFloorfirst()</td></tr>\r\n<tr><td>int get_bb_rule(lprec *lp)</td><td>int getBbRule()</td></tr>\r\n<tr><td>unsigned char get_bounds_tighter(lprec *lp)</td><td>boolean getBoundsTighter()</td></tr>\r\n<tr><td>REAL get_break_at_value(lprec *lp)</td><td>double getBreakAtValue()</td></tr>\r\n<tr><td>char *get_col_name(lprec *lp, int column)</td><td>String getColName(int colnr) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_column(lprec *lp, int col_nr, REAL *column)</td><td>void getColumn(int columnrnr, double[] column) throws LpSolveException</td></tr>\r\n<tr><td><strong>&lt;Not implemented&gt;</strong></td><td>double[] getPtrColumn(int columnrnr) throws LpSolveException</td></tr>\r\n<tr><td>int get_constr_type(lprec *lp, int row)</td><td>short getConstrType(int rownr) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_constraints(lprec *lp, REAL *constr)</td><td>void getConstraints(double[] var) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_dual_solution(lprec *lp, REAL *duals)</td><td>void getDualSolution(double[] duals) throws LpSolveException</td></tr>\r\n<tr><td>REAL get_epsb(lprec *lp)</td><td>double getEpsb()</td></tr>\r\n<tr><td>REAL get_epsd(lprec *lp)</td><td>double getEpsd()</td></tr>\r\n<tr><td>REAL get_epsel(lprec *lp)</td><td>double getEpsel()</td></tr>\r\n<tr><td>REAL get_epsint(lprec *lp)</td><td>double getEpsint()</td></tr>\r\n<tr><td>REAL get_epsperturb(lprec *lp)</td><td>double getEpsperturb()</td></tr>\r\n<tr><td>REAL get_epspivot(lprec *lp)</td><td>double getEpspivot()</td></tr>\r\n<tr><td>int get_improve(lprec *lp)</td><td>int getImprove()</td></tr>\r\n<tr><td>REAL get_infinite(lprec *lp)</td><td>double getInfinite()</td></tr>\r\n<tr><td>unsigned char get_lambda(lprec *lp, REAL *lambda)</td><td>void getLambda(double[] lambda) throws LpSolveException</td></tr>\r\n<tr><td>REAL get_lowbo(lprec *lp, int column)</td><td>double getLowbo(int colnr) throws LpSolveException</td></tr>\r\n<tr><td>int get_lp_index(lprec *lp, int orig_index)</td><td>int getLpIndex(int index)</td></tr>\r\n<tr><td>char *get_lp_name(lprec *lp)</td><td>String getLpName() throws LpSolveException</td></tr>\r\n<tr><td>int get_Lrows(lprec *lp)</td><td>int getLrows()</td></tr>\r\n<tr><td>REAL get_mat(lprec *lp, int row, int column)</td><td>double getMat(int row, int column)</td></tr>\r\n<tr><td>int get_max_level(lprec *lp)</td><td>int getMaxLevel()</td></tr>\r\n<tr><td>int get_maxpivot(lprec *lp)</td><td>int getMaxpivot()</td></tr>\r\n<tr><td>REAL get_mip_gap(lprec *lp, unsigned char absolute)</td><td>double getMipGap(boolean absolute)</td></tr>\r\n<tr><td>int get_Ncolumns(lprec *lp)</td><td>int getNcolumns()</td></tr>\r\n<tr><td>REAL get_negrange(lprec *lp)</td><td>double getNegrange()</td></tr>\r\n<tr><td>int get_nonzeros(lprec *lp)</td><td>int getNonzeros()</td></tr>\r\n<tr><td>int get_Norig_columns(lprec *lp)</td><td>int getNorigColumns()</td></tr>\r\n<tr><td>int get_Norig_rows(lprec *lp)</td><td>int getNorigRows()</td></tr>\r\n<tr><td>int get_Nrows(lprec *lp)</td><td>int getNrows()</td></tr>\r\n<tr><td>REAL get_obj_bound(lprec *lp)</td><td>double getObjBound()</td></tr>\r\n<tr><td>REAL get_objective(lprec *lp)</td><td>getObjective()</td></tr>\r\n<tr><td>int get_orig_index(lprec *lp, int lp_index)</td><td>int getOrigIndex(int index)</td></tr>\r\n<tr><td>char *get_origcol_name(lprec *lp, int column)</td><td>String getOrigcolName(int colnr) throws LpSolveException</td></tr>\r\n<tr><td>char *get_origrow_name(lprec *lp, int row)</td><td>String getOrigrowName(int rownr) throws LpSolveException</td></tr>\r\n<tr><td>int get_pivoting(lprec *lp)</td><td>int getPivoting()</td></tr>\r\n<tr><td>int get_presolve(lprec *lp)</td><td>int getPresolve()</td></tr>\r\n<tr><td>unsigned char get_primal_solution(lprec *lp, REAL *pv)</td><td>void getPrimalSolution(double[] pv) throws LpSolveException</td></tr>\r\n<tr><td>int get_print_sol(lprec *lp)</td><td>int getPrintSol()</td></tr>\r\n<tr><td>unsigned char get_ptr_constraints(lprec *lp, REAL **ptr_constr)</td><td>double[] getPtrConstraints() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_ptr_dual_solution(lprec *lp, REAL **ptr_duals)</td><td>double[] getPtrDualSolution() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_ptr_lambda(lprec *lp, REAL **ptr_lambda)</td><td>double[] getPtrLambda() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_ptr_primal_solution(lprec *lp, REAL **ptr_pv)</td><td>double[] getPtrPrimalSolution() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_ptr_sensitivity_obj(lprec *lp, REAL **ptr_objfrom, REAL **ptr_objtill)</td><td>double[][] getPtrSensitivityObj() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_ptr_sensitivity_objex(lprec *lp, REAL **ptr_objfrom, REAL **ptr_objtill, REAL *ptr_objfromvalue, REAL *ptr_objtillvalue)</td><td>double[][] getPtrSensitivityObjex() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_ptr_sensitivity_rhs(lprec *lp, REAL **ptr_duals, REAL **ptr_dualsfrom, REAL **ptr_dualstill)</td><td>double[][] getPtrSensitivityRhs() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_ptr_variables(lprec *lp, REAL **ptr_var)</td><td>double[] getPtrVariables() throws LpSolveException</td></tr>\r\n<tr><td>REAL get_rh(lprec *lp, int row)</td><td>double getRh(int row)</td></tr>\r\n<tr><td>REAL get_rh_range(lprec *lp, int row)</td><td>double getRhRange(int rownr) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_row(lprec *lp, int row_nr, REAL *row)</td><td>void getRow(int rownr, double[] row) throws LpSolveException</td></tr>\r\n<tr><td><strong>&lt;Not implemented&gt;</strong></td><td>double[] getPtrRow(int rownr) throws LpSolveException</td></tr>\r\n<tr><td>char *get_row_name(lprec *lp, int row)</td><td>String getRowName(int rownr) throws LpSolveException</td></tr>\r\n<tr><td>REAL get_scalelimit(lprec *lp)</td><td>double getScalelimit()</td></tr>\r\n<tr><td>int get_scaling(lprec *lp)</td><td>int getScaling()</td></tr>\r\n<tr><td>unsigned char get_sensitivity_obj(lprec *lp, REAL *objfrom, REAL *objtill)</td><td>void getSensitivityObj(double[] objfrom, double[] objtill) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_sensitivity_objex(lprec *lp, REAL *objfrom, REAL *objtill, REAL *objfromvalue, REAL *objtillvalue)</td><td>void getSensitivityObjex(double[] objfrom, double[] objtill, double[] objfromvalue, double[] objtillvalue) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_sensitivity_rhs(lprec *lp, REAL *duals, REAL *dualsfrom, REAL *dualstill)</td><td>void getSensitivityRhs(double[] duals, double[] dualsfrom, double[] dualstill) throws LpSolveException</td></tr>\r\n<tr><td>int get_simplextype(lprec *lp)</td><td>int getSimplextype()</td></tr>\r\n<tr><td>int get_solutioncount(lprec *lp)</td><td>int getSolutioncount()</td></tr>\r\n<tr><td>int get_solutionlimit(lprec *lp)</td><td>int getSolutionlimit()</td></tr>\r\n<tr><td>int get_status(lprec *lp)</td><td>int getStatus()</td></tr>\r\n<tr><td>char *get_statustext(lprec *lp, int statuscode)</td><td>String getStatustext(int statuscode)</td></tr>\r\n<tr><td>long get_timeout(lprec *lp)</td><td>long getTimeout()</td></tr>\r\n<tr><td>int get_total_iter(lprec *lp)</td><td>int getTotalIter()</td></tr>\r\n<tr><td>int get_total_nodes(lprec *lp)</td><td>int getTotalNodes()</td></tr>\r\n<tr><td>REAL get_upbo(lprec *lp, int column)</td><td>double getUpbo(int colnr) throws LpSolveException</td></tr>\r\n<tr><td>int get_var_branch(lprec *lp, int column)</td><td>int getVarBranch(int colnr) throws LpSolveException</td></tr>\r\n<tr><td>REAL get_var_dualresult(lprec *lp, int index)</td><td>double getVarDualresult(int index) throws LpSolveException</td></tr>\r\n<tr><td>REAL get_var_primalresult(lprec *lp, int index)</td><td>double getVarPrimalresult(int index) throws LpSolveException</td></tr>\r\n<tr><td>int get_var_priority(lprec *lp, int column)</td><td>int getVarPriority(int colnr) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char get_variables(lprec *lp, REAL *var)</td><td>void getVariables(double[] var) throws LpSolveException</td></tr>\r\n<tr><td>int get_verbose(lprec *lp)</td><td>int getVerbose()</td></tr>\r\n<tr><td>REAL get_working_objective(lprec *lp)</td><td>double getWorkingObjective() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char guess_basis(lprec *lp, double *guessvector, int *basisvector)</td><td>void guessBasis(double[] guessvector, int[] basisvector) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char has_BFP(lprec *lp)</td><td>boolean hasBFP()</td></tr>\r\n<tr><td>unsigned char has_XLI(lprec *lp)</td><td>boolean hasXLI()</td></tr>\r\n<tr><td>unsigned char is_add_rowmode(lprec *lp)</td><td>boolean isAddRowmode()</td></tr>\r\n<tr><td>unsigned char is_anti_degen(lprec *lp, int testmask)</td><td>boolean isAntiDegen(int testmask)</td></tr>\r\n<tr><td>unsigned char is_binary(lprec *lp, int column)</td><td>boolean isBinary(int colnr)</td></tr>\r\n<tr><td>unsigned char is_break_at_first(lprec *lp)</td><td>boolean isBreakAtFirst()</td></tr>\r\n<tr><td>unsigned char is_constr_type(lprec *lp, int row, int mask)</td><td>boolean isConstrType(int row, int mask)</td></tr>\r\n<tr><td>unsigned char is_debug(lprec *lp)</td><td>boolean isDebug()</td></tr>\r\n<tr><td>unsigned char is_feasible(lprec *lp, REAL *values, REAL threshold)</td><td>boolean isFeasible(double[] values, double threshold) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char is_free(lprec *lp, int column)</td><td>boolean isFree(int colnr)</td></tr>\r\n<tr><td>unsigned char is_infinite(lprec *lp, REAL value)</td><td>boolean isInfinite(double value)</td></tr>\r\n<tr><td>unsigned char is_int(lprec *lp, int column)</td><td>boolean isInt(int colnr)</td></tr>\r\n<tr><td>unsigned char is_integerscaling(lprec *lp)</td><td>boolean isIntegerscaling()</td></tr>\r\n<tr><td>unsigned char is_lag_trace(lprec *lp)</td><td>boolean isLagTrace()</td></tr>\r\n<tr><td>unsigned char is_maxim(lprec *lp)</td><td>boolean isMaxim()</td></tr>\r\n<tr><td>unsigned char is_nativeBFP(lprec *lp)</td><td>boolean isNativeBFP()</td></tr>\r\n<tr><td>unsigned char is_nativeXLI(lprec *lp)</td><td>boolean isNativeXLI()</td></tr>\r\n<tr><td>unsigned char is_negative(lprec *lp, int column)</td><td>boolean isNegative(int colnr)</td></tr>\r\n<tr><td>unsigned char is_piv_mode(lprec *lp, int testmask)</td><td>boolean isPivMode(int testmask)</td></tr>\r\n<tr><td>unsigned char is_piv_rule(lprec *lp, int rule)</td><td>boolean isPivRule(int rule)</td></tr>\r\n<tr><td>unsigned char is_presolve(lprec *lp, int testmask)</td><td>boolean isPresolve(int testmask)</td></tr>\r\n<tr><td>unsigned char is_scalemode(lprec *lp, int testmask)</td><td>boolean isScalemode(int testmask)</td></tr>\r\n<tr><td>unsigned char is_scaletype(lprec *lp, int scaletype)</td><td>boolean isScaletype(int scaletype)</td></tr>\r\n<tr><td>unsigned char is_semicont(lprec *lp, int column)</td><td>boolean isSemicont(int colnr)</td></tr>\r\n<tr><td>unsigned char is_SOS_var(lprec *lp, int column)</td><td>boolean isSOSVar(int colnr) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char is_trace(lprec *lp)</td><td>boolean isTrace()</td></tr>\r\n<tr><td>int lag_solve(lprec *lp, REAL start_bound, int num_iter, short verbose)</td><td><strong>&lt;Function is currently not exported from lp_solve dll&gt;</strong></td></tr>\r\n<tr><td>void lp_solve_version(int *majorversion, int *minorversion, int *release, int *build)</td><td>static VersionInfo lpSolveVersion()</td></tr>\r\n<tr><td>lprec *make_lp(int rows, int columns)</td><td>static LpSolve makeLp(int rows, int columns) throws LpSolveException</td></tr>\r\n<tr><td>void print_constraints(lprec *lp, int columns)</td><td>void printConstraints(int columns)</td></tr>\r\n<tr><td>unsigned char print_debugdump(lprec *lp, char *filename)</td><td>void printDebugdump(String filename) throws LpSolveException</td></tr>\r\n<tr><td>void print_duals(lprec *lp)</td><td>void printDuals()</td></tr>\r\n<tr><td>void print_lp(lprec *lp)</td><td>void printLp()</td></tr>\r\n<tr><td>void print_objective(lprec *lp)</td><td>void printObjective()</td></tr>\r\n<tr><td>void print_scales(lprec *lp)</td><td>void printScales()</td></tr>\r\n<tr><td>void print_solution(lprec *lp, int columns)</td><td>void printSolution(int columns)</td></tr>\r\n<tr><td>void print_str(lprec *lp, char *str)</td><td>void printStr(String str)</td></tr>\r\n<tr><td>void print_tableau(lprec *lp)</td><td>void printTableau()</td></tr>\r\n<tr><td>void put_abortfunc(lprec *lp, ctrlcfunc newctrlc, void *ctrlchandle)</td><td>void putAbortfunc(AbortListener listener, Object userhandle) throws LpSolveException</td></tr>\r\n<tr><td>void put_logfunc(lprec *lp, logfunc newlog, void *loghandle)</td><td>void putLogfunc(LogListener listener, Object userhandle) throws LpSolveException</td></tr>\r\n<tr><td>void put_msgfunc(lprec *lp, msgfunc newmsg, void *msghandle, int mask)</td><td>void putMsgfunc(MsgListener listener, Object userhandle, int mask) throws LpSolveException</td></tr>\r\n<tr><td>lprec *read_freeMPS(char *filename, int options)</td><td>static LpSolve readFreeMps(String filename, int options) throws LpSolveException</td></tr>\r\n<tr><td>lprec *read_freemps(FILE *stream, int options)</td><td><strong>&lt;Not implemented, use readFreeMps instead&gt;</strong></td></tr>\r\n<tr><td>lprec *read_lp(FILE *stream, int verbose, char *lp_name)</td><td><strong>&lt;Not implemented, use readLp instead&gt;</strong></td></tr>\r\n<tr><td>lprec *read_LP(char *filename, int verbose, char *lp_name)</td><td>static LpSolve readLp(String filename, int verbose, String lpName) throws LpSolveException</td></tr>\r\n<tr><td>lprec *read_lpt(FILE *stream, int verbose, char *lp_name)</td><td><strong>&lt;Not implemented, use readLpt instead&gt;</strong></td></tr>\r\n<tr><td>lprec *read_LPT(char *filename, int verbose, char *lp_name)</td><td>static LpSolve readLpt(String filename, int verbose, String lpName) throws LpSolveException</td></tr>\r\n<tr><td>lprec *read_mps(FILE *stream, int options)</td><td><strong>&lt;Not implemented, use readMps instead&gt;</strong></td></tr>\r\n<tr><td>lprec *read_MPS(char *filename, int options)</td><td>static LpSolve readMps(String filename, int options) throws LpSolveException</td></tr>\r\n<tr><td>lprec *read_XLI(char *xliname, char *modelname, char *dataname, char *options, int verbose)</td><td>static LpSolve readXLI(String xliname, String modelname, String dataname, String options, int verbose)\tthrows LpSolveException</td></tr>\r\n<tr><td>void reset_basis(lprec *lp)</td><td>void resetBasis()</td></tr>\r\n<tr><td>unsigned char resize_lp(lprec *lp, int rows, int columns)</td><td>void resizeLp(int rows, int columns) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_add_rowmode(lprec *lp, unsigned char turnon)</td><td>boolean setAddRowmode(boolean turnon)</td></tr>\r\n<tr><td>void set_anti_degen(lprec *lp, int anti_degen)</td><td>void setAntiDegen(int antiDegen)</td></tr>\r\n<tr><td>unsigned char set_basis(lprec *lp, int *bascolumn, unsigned char nonbasic)</td><td>void setBasis(int[] bascolumn, boolean nonbasic) throws LpSolveException</td></tr>\r\n<tr><td>void set_basiscrash(lprec *lp, int mode)</td><td>void setBasiscrash(int mode)</td></tr>\r\n<tr><td>void set_bb_depthlimit(lprec *lp, int bb_maxlevel)</td><td>void setBbDepthlimit(int bbMaxlevel)</td></tr>\r\n<tr><td>void set_bb_floorfirst(lprec *lp, int bb_floorfirst)</td><td>void setBbFloorfirst(int floorFirst)</td></tr>\r\n<tr><td>void set_bb_rule(lprec *lp, int bb_rule)</td><td>void setBbRule(int bbRule)</td></tr>\r\n<tr><td>unsigned char set_BFP(lprec *lp, char *filename)</td><td>void setBFP(String filename) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_XLI(lprec *lp, char *filename)</td><td>void setXLI(String filename) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_binary(lprec *lp, int column, unsigned char must_be_bin)</td><td>void setBinary(int colnr, boolean mustBeBin) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_bounds(lprec *lp, int column, REAL lower, REAL upper)</td><td>void setBounds(int colnr, double lower, double upper) throws LpSolveException</td></tr>\r\n<tr><td>void set_bounds_tighter(lprec *lp, unsigned char tighten)</td><td>void setBoundsTighter(boolean tighten)</td></tr>\r\n<tr><td>void set_break_at_first(lprec *lp, unsigned char break_at_first)</td><td>void setBreakAtFirst(boolean breakAtFirst)</td></tr>\r\n<tr><td>void set_break_at_value(lprec *lp, REAL break_at_value)</td><td>void setBreakAtValue(double breakAtValue)</td></tr>\r\n<tr><td>unsigned char set_col_name(lprec *lp, int column, char *new_name)</td><td>void setColName(int colnr, String name) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_column(lprec *lp, int col_no, REAL *column)</td><td>void setColumn(int colno, double[] column) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_columnex(lprec *lp, int col_no, int count, REAL *column, int *rowno)</td><td>void setColumnex(int colno, int count, double[] column, int[] rowno) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_constr_type(lprec *lp, int row, int con_type)</td><td>void setConstrType(int rownr, int constrType) throws LpSolveException</td></tr>\r\n<tr><td>void set_debug(lprec *lp, unsigned char debug)</td><td>void setDebug(boolean debug)</td></tr>\r\n<tr><td>void set_epsb(lprec *lp, REAL epsb)</td><td>void setEpsb(double value)</td></tr>\r\n<tr><td>void set_epsd(lprec *lp, REAL epsd)</td><td>void setEpsd(double value)</td></tr>\r\n<tr><td>void set_epsel(lprec *lp, REAL epsel)</td><td>void setEpsel(double value)</td></tr>\r\n<tr><td>void set_epsint(lprec *lp, REAL epsint)</td><td>void setEpsint(double value)</td></tr>\r\n<tr><td>void set_epsperturb(lprec *lp, REAL epsperturb)</td><td>void setEpsperturb(double value)</td></tr>\r\n<tr><td>void set_epspivot(lprec *lp, REAL epspivot)</td><td>void setEpspivot(double value)</td></tr>\r\n<tr><td>unsigned char set_free(lprec *lp, int column)</td><td>void setFree(int colnr) throws LpSolveException</td></tr>\r\n<tr><td>void set_improve(lprec *lp, int improve)</td><td>void setImprove(int improve)</td></tr>\r\n<tr><td>void set_infinite(lprec *lp, REAL infinite)</td><td>void setInfinite(double value)</td></tr>\r\n<tr><td>unsigned char set_int(lprec *lp, int column, unsigned char must_be_int)</td><td>void setInt(int colnr, boolean mustBeInteger) throws LpSolveException</td></tr>\r\n<tr><td>void set_lag_trace(lprec *lp, unsigned char lag_trace)</td><td>void setLagTrace(boolean lagTrace)</td></tr>\r\n<tr><td>unsigned char set_lowbo(lprec *lp, int column, REAL value)</td><td>void setLowbo(int colnr, double value) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_lp_name(lprec *lp, char *lpname)</td><td>void setLpName(String name) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_mat(lprec *lp, int row, int column, REAL value)</td><td>void setMat(int row, int column, double value) throws LpSolveException</td></tr>\r\n<tr><td>void set_maxim(lprec *lp)</td><td>void setMaxim()</td></tr>\r\n<tr><td>void set_maxpivot(lprec *lp, int max_num_inv)</td><td>void setMaxpivot(int maxNumInv)</td></tr>\r\n<tr><td>void set_minim(lprec *lp)</td><td>void setMinim()</td></tr>\r\n<tr><td>void set_mip_gap(lprec *lp, unsigned char absolute, REAL mip_gap)</td><td>void setMipGap(boolean absolute, double value)</td></tr>\r\n<tr><td>void set_negrange(lprec *lp, REAL negrange)</td><td>void setNegrange(double negRange)</td></tr>\r\n<tr><td>void set_obj_bound(lprec *lp, REAL obj_bound)</td><td>void setObjBound(double objBound)</td></tr>\r\n<tr><td>unsigned char set_obj_fn(lprec *lp, REAL *row)</td><td>void setObjFn(double[] row) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_obj_fnex(lprec *lp, int count, REAL *row, int *colno)</td><td>void setObjFnex(int count, double[] row, int[] colno) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_obj(lprec *lp, int column, REAL value)</td><td>void setObj(int column, double value) throws LpSolveException</td></tr>\r\n<tr><td>void set_outputstream(lprec *lp, FILE *stream)</td><td><strong>&lt;Not implemented, use setOutputfile instead&gt;</strong></td></tr>\r\n<tr><td>unsigned char set_outputfile(lprec *lp, char *filename)</td><td>void setOutputfile(String filename) throws LpSolveException</td></tr>\r\n<tr><td>void set_pivoting(lprec *lp, int pivoting)</td><td>void setPivoting(int pivRule)</td></tr>\r\n<tr><td>void set_preferdual(lprec *lp, unsigned char dodual)</td><td>void setPreferdual(int dodual)</td></tr>\r\n<tr><td>void set_presolve(lprec *lp, int do_presolve)</td><td>void setPresolve(int doPresolve)</td></tr>\r\n<tr><td>void set_print_sol(lprec *lp, int print_sol)</td><td>void setPrintSol(int printSol)</td></tr>\r\n<tr><td>unsigned char set_rh(lprec *lp, int row, REAL value)</td><td>void setRh(int row, double value) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_rh_range(lprec *lp, int row, REAL deltavalue)</td><td>void setRhRange(int rownr, double range) throws LpSolveException</td></tr>\r\n<tr><td>void set_rh_vec(lprec *lp, REAL *rh)</td><td>void setRhVec(double[] rh) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_row(lprec *lp, int row_no, REAL *row)</td><td>void setRow(int rowno, double[] row) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_rowex(lprec *lp, int row_no, int count, REAL *row, int *colno)</td><td>void setRowex(int rowno, int count, double[] row, int[] colno) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_row_name(lprec *lp, int row, char *new_name)</td><td>void setRowName(int rownr, String name) throws LpSolveException</td></tr>\r\n<tr><td>void set_scalelimit(lprec *lp, REAL scalelimit)</td><td>void setScalelimit(double scalelimit)</td></tr>\r\n<tr><td>void set_scaling(lprec *lp, int scalemode)</td><td>void setScaling(int scalemode)</td></tr>\r\n<tr><td>unsigned char set_semicont(lprec *lp, int column, unsigned char must_be_sc)</td><td>void setSemicont(int colnr, boolean mustBeSc) throws LpSolveException</td></tr>\r\n<tr><td>void set_sense(lprec *lp, unsigned char maximize)</td><td>void setSense(boolean maximize)</td></tr>\r\n<tr><td>void set_simplextype(lprec *lp, int simplextype)</td><td>void setSimplextype(int simplextype)</td></tr>\r\n<tr><td>void set_solutionlimit(lprec *lp, int limit)</td><td>void setSolutionlimit(int limit)</td></tr>\r\n<tr><td>void set_timeout(lprec *lp, long sectimeout)</td><td>void setTimeout(long timeout)</td></tr>\r\n<tr><td>void set_trace(lprec *lp, unsigned char trace)</td><td>void setTrace(boolean trace)</td></tr>\r\n<tr><td>unsigned char set_upbo(lprec *lp, int column, REAL value)</td><td>void setUpbo(int colnr, double value) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_var_branch(lprec *lp, int column, int branch_mode)</td><td>void setVarBranch(int colnr, int branchMode) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char set_var_weights(lprec *lp, REAL *weights)</td><td>void setVarWeights(double[] weights) throws LpSolveException</td></tr>\r\n<tr><td>void set_verbose(lprec *lp, int verbose)</td><td>void setVerbose(int verbose)</td></tr>\r\n<tr><td>int solve(lprec *lp)</td><td>int solve() throws LpSolveException</td></tr>\r\n<tr><td>unsigned char str_add_column (lprec* lp, char* col_string)</td><td>void strAddColumn(String column) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char str_add_constraint (lprec* lp, char *row_string, int constr_type, REAL rh)</td><td>void strAddConstraint(String row, int constrType, double rh) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char str_add_lag_con (lprec* lp, char *row_string, int con_type, REAL rhs)</td><td>void strAddLagCon(String row, int constrType, double rh) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char str_set_obj_fn(lprec *lp, char *row_string)</td><td>void strSetObjFn(String row) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char str_set_rh_vec(lprec *lp, char *rh_string)</td><td>void strSetRhVec(String rh) throws LpSolveException</td></tr>\r\n<tr><td>REAL time_elapsed(lprec *lp)</td><td>double timeElapsed()</td></tr>\r\n<tr><td>void unscale(lprec *lp)</td><td>void unscale()</td></tr>\r\n<tr><td>unsigned char write_freeMPS(lprec *lp, FILE *stream)</td><td><strong>&lt;Not implemented, use writeFreeMps instead&gt;</strong></td></tr>\r\n<tr><td>unsigned char write_freemps(lprec *lp, char *filename)</td><td>void writeFreeMps(String filename) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char write_lp(lprec *lp, char *filename)</td><td>void writeLp(String filename) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char write_LP(lprec *lp, FILE *stream)</td><td><strong>&lt;Not implemented, use writeLp instead&gt;</strong></td></tr>\r\n<tr><td>unsigned char write_mps(lprec *lp, char *filename)</td><td>void writeMps(String filename) throws LpSolveException</td></tr>\r\n<tr><td>unsigned char write_MPS(lprec *lp, FILE *stream)</td><td><strong>&lt;Not implemented, use writeMps instead&gt;</strong></td></tr>\r\n<tr><td>unsigned char write_XLI(lprec *lp, char *filename, char *options, unsigned char results)</td><td>void writeXLI(String filename, String options, boolean results) throws LpSolveException</td></tr>\r\n</table>\r\n\r\n</body>\r\n</html>\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/lib/build",
    "content": ":\n# -------------------------------------------------------------------\n# This is a build file for the lp_solve Java wrapper stub library\n# on linux platforms.\n#\n# Requirements and preconditions:\n#\n# - gcc and g++ compiler installed (I used gcc Version 3.3.1)\n# - Sun JDK 1.4 installed\n# - lp_solve archive (lp_solve_5.5_source.tar.gz) unpacked\n#\n# Change the paths below this line and you should be ready to go!\n# -------------------------------------------------------------------\n\nLPSOLVE_DIR=../../lpsolve55/src/lp_solve_5.5\nLPSOLVE_LIB_DIR=../../../lib\n#JDK_DIR=/usr/local/lib/jdk1.5.0_02\n#JDK_DIR=/usr/lib/jvm/java-6-sun-1.6.0.10\n#JDK_DIR=$JAVA_DIR\n\nc=g++\n\nif [ \"$ARCH\" = \"\" ]; then\n\tCFLAGS=\"-m32\"\nfi\nif [ \"$ARCH\" = \"amd64\" ]; then\n\tCFLAGS=\"-m64 -fPIC -DPIC\"\nfi\nif [ \"$ARCH\" = \"ia64\" ]; then\n\tCFLAGS=\"-fPIC -DPIC\"\nfi\nif [ \"$ARCH\" = \"aarch64\" ]; then\n\tCFLAGS=\"-fPIC -DPIC\"\nfi\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c $CFLAGS /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir $PLATFORM >/dev/null 2>&1\n\n# OK, here we go!\n\nSRC_DIR=../src/c\nINCL=\"-I$JAVA_JNI_H_DIR -I$JAVA_JNI_MD_H_DIR -I $LPSOLVE_DIR -I $SRC_DIR\"\n\n$c $CFLAGS $INCL -c $SRC_DIR/lpsolve5j.cpp\n$c $CFLAGS -shared -Wl,-soname,liblpsolve55j.so -Wl,-soname,liblpsolve55j.so -Wl,-rpath,'$ORIGIN' -o $PLATFORM/liblpsolve55j.so lpsolve5j.o -L$LPSOLVE_LIB_DIR -lc -llpsolve55\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/lib/build.bat",
    "content": "@echo off\r\n\r\nREM ----------------------------------------------------------------\r\nREM This is a build file for the lp_solve Java wrapper stub library\r\nREM on Windows platforms.\r\nREM\r\nREM Requirements:\r\nREM\r\nREM - Microsoft Visual C++ compiler (I used V 7, others might work)\r\nREM - Visual Studio envirement variables must be set.\r\nREM - Java Development Kit 1.4.x installed\r\nREM - JAVA_HOME environment variable set\r\nREM - lp_solve windows archive lp_solve_5.5_dev.zip\r\nREM\r\nREM Change the paths below this line and you should be ready to go!\r\nREM ----------------------------------------------------------------\r\n\r\nREM -- Set the path to the lp_solve directories here !\r\nREM --\r\n\r\nset c=cl\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% /nologo platform.c /Feplatform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif not exist %PLATFORM%\\*.* md %PLATFORM%\r\n\r\nREM -- Here we go !\r\nREM --\r\nset SRC_DIR=..\\src\\c\r\nset OPTIONS=/LD /O2 /Gz /MT\r\nset DEFINES=-DWIN32\r\nREM The 64 bit java sdk also uses win32 as folder\r\nset INCLUDES=-I \"%JAVA_HOME%\\include\" -I \"%JAVA_HOME%\\include\\win32\" -I %LPSOLVE_DIR% -I %SRC_DIR%\r\nset LIBS=%LPSOLVE_DIR%\\lpsolve55\\bin\\%PLATFORM%\\lpsolve55.lib\r\nset SRCFILES=%SRC_DIR%\\lpsolve5j.cpp\r\n\r\ncl %OPTIONS% %DEFINES% %INCLUDES% %LIBS% %SRCFILES% /Fe%PLATFORM%\\lpsolve55j.dll\r\n\r\nif exist *.obj del *.obj\r\n\r\nset PLATFORM="
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/lib/mac/build-osx",
    "content": "\n# -------------------------------------------------------------------\n# This is a build file for the lp_solve Java wrapper stub library\n# on Mac OS X platforms.\n#\n# Requirements and preconditions:\n#\n# - gcc and g++ compiler installed (I used gcc Version 3.3 20030304 )\n# - Apple JDK 1.4 installed (I have JDK 1.4.2)\n# - lp_solve archive (lp_solve_5.5_source.tar.gz) unpacked\n#\n# Change the paths below this line and you should be ready to go!\n# -------------------------------------------------------------------\nLPSOLVE_DIR=../../../lpsolve55/src/lp_solve_5.5\nLPSOLVE_LIB_DIR=../../../../lib\n#JDK_DIR=/System/Library/Frameworks/JavaVM.framework/Versions/Current/Headers\n#JDK_DIR=$JAVA_DIR\n\n# OK, here we go!\n\nSRC_DIR=../../src/c\nINCL=\"-I$JAVA_JNI_H_DIR -I$JAVA_JNI_MD_H_DIR -I $LPSOLVE_DIR -I $SRC_DIR -idirafter /usr/include/sys\"\n\nif [ \"$ARCH\" = \"\" ]; then\n\tCFLAGS=\"-arch i386 -fno-common\"\nfi\nif [ \"$ARCH\" = \"x86_64\" ]; then\n\tCFLAGS=\"-arch x86_64 -fPIC -DPIC -fno-common\"\nfi\nif [ \"$ARCH\" = \"arm64\" ]; then\n\tCFLAGS=\"-arch arm64 -fPIC -DPIC -fno-common\"\nfi\n\ng++ $CFLAGS $INCL -c $SRC_DIR/lpsolve5j.cpp\ng++ $CFLAGS -dynamiclib lpsolve5j.o -compatibility_version 5.5.0 -current_version 5.5.0 -Wl,-install_name,@rpath/liblpsolve55j.dylib -Wl,-rpath,@loader_path/. -o liblpsolve55j.dylib -lc -llpsolve55 -L$LPSOLVE_LIB_DIR\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/c/lpsolve5j.cpp",
    "content": "/*\r\n\tThis software is a java wrapper for the lp_solve optimization library.\r\n\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\n#include <stdio.h>\r\n#include <stdlib.h>\r\n#include \"lpsolve_LpSolve.h\"\r\n#include \"lp_lib.h\"\r\n\r\n\r\n// =======================================================================\r\n// -----------------  global variables  ----------------------------------\r\n// =======================================================================\r\n\r\n/* The global JavaVM object - reference is obtained in OnLoad */\r\nJavaVM *g_jvm = NULL;\r\n\r\n/* globally cached method and field IDs */\r\njmethodID MID_lpsolve_constr = NULL;\r\njmethodID MID_getLp = NULL;\r\njfieldID FID_lp = NULL;\r\njmethodID MID_abortfunc = NULL;\r\njfieldID FID_abortListener = NULL;\r\njfieldID FID_abortHandle = NULL;\r\njmethodID MID_logfunc = NULL;\r\njfieldID FID_logListener = NULL;\r\njfieldID FID_logHandle = NULL;\r\njmethodID MID_msgfunc = NULL;\r\njfieldID FID_msgListener = NULL;\r\njfieldID FID_msgHandle = NULL;\r\njmethodID MID_bbfunc = NULL;\r\njfieldID FID_bbBranchListener = NULL;\r\njfieldID FID_bbBranchHandle = NULL;\r\njfieldID FID_bbNodeListener = NULL;\r\njfieldID FID_bbNodeHandle = NULL;\r\njmethodID MID_String_getBytes = NULL;\r\njmethodID MID_String_init = NULL;\r\n\r\n\r\n// =======================================================================\r\n// -----------------  DLL initialisation and finalization methods --------\r\n// =======================================================================\r\n\r\nextern \"C\"\r\nJNIEXPORT jint JNICALL JNI_OnLoad(JavaVM* vm, void* reserved) {\r\n\t//printf(\"JNI_OnLoad\\n\");\r\n\tg_jvm = vm;\r\n\treturn JNI_VERSION_1_2;\r\n}\r\n\r\nextern \"C\"\r\nJNIEXPORT void JNICALL JNI_OnUnload(JavaVM* vm, void* reserved) {\r\n\t//printf(\"JNI_OnUnload\\n\");\r\n\tg_jvm = NULL;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    init\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_init\r\n  (JNIEnv *env, jclass cls)\r\n{\r\n\tMID_lpsolve_constr = env->GetMethodID(cls, \"<init>\", \"(J)V\");\r\n\tMID_getLp = env->GetStaticMethodID(cls, \"getLp\", \"(J)Llpsolve/LpSolve;\");\r\n\tFID_lp = env->GetFieldID(cls, \"lp\", \"J\");\r\n\r\n\tFID_abortListener = env->GetFieldID(cls, \"abortListener\", \"Llpsolve/AbortListener;\");\r\n\tFID_abortHandle = env->GetFieldID(cls, \"abortUserhandle\", \"Ljava/lang/Object;\");\r\n\tjclass abort_listener_cls = env->FindClass(\"lpsolve/AbortListener\");\r\n\tMID_abortfunc = env->GetMethodID(abort_listener_cls, \"abortfunc\", \"(Llpsolve/LpSolve;Ljava/lang/Object;)Z\");\r\n\tenv->DeleteLocalRef(abort_listener_cls);\r\n\r\n\tFID_logListener = env->GetFieldID(cls, \"logListener\", \"Llpsolve/LogListener;\");\r\n\tFID_logHandle = env->GetFieldID(cls, \"logUserhandle\", \"Ljava/lang/Object;\");\r\n\tjclass log_listener_cls = env->FindClass(\"lpsolve/LogListener\");\r\n\tMID_logfunc = env->GetMethodID(log_listener_cls, \"logfunc\", \"(Llpsolve/LpSolve;Ljava/lang/Object;Ljava/lang/String;)V\");\r\n\tenv->DeleteLocalRef(log_listener_cls);\r\n\r\n\tFID_msgListener = env->GetFieldID(cls, \"msgListener\", \"Llpsolve/MsgListener;\");\r\n\tFID_msgHandle = env->GetFieldID(cls, \"msgUserhandle\", \"Ljava/lang/Object;\");\r\n\tjclass msg_listener_cls = env->FindClass(\"lpsolve/MsgListener\");\r\n\tMID_msgfunc = env->GetMethodID(msg_listener_cls, \"msgfunc\", \"(Llpsolve/LpSolve;Ljava/lang/Object;I)V\");\r\n\tenv->DeleteLocalRef(msg_listener_cls);\r\n\r\n\tFID_bbBranchListener = env->GetFieldID(cls, \"bbBranchListener\", \"Llpsolve/BbListener;\");\r\n\tFID_bbBranchHandle = env->GetFieldID(cls, \"bbBranchUserhandle\", \"Ljava/lang/Object;\");\r\n\tFID_bbNodeListener = env->GetFieldID(cls, \"bbNodeListener\", \"Llpsolve/BbListener;\");\r\n\tFID_bbNodeHandle = env->GetFieldID(cls, \"bbNodeUserhandle\", \"Ljava/lang/Object;\");\r\n\tjclass bb_listener_cls = env->FindClass(\"lpsolve/BbListener\");\r\n\tMID_bbfunc = env->GetMethodID(bb_listener_cls, \"bbfunc\", \"(Llpsolve/LpSolve;Ljava/lang/Object;I)I\");\r\n\tenv->DeleteLocalRef(bb_listener_cls);\r\n\r\n\tjclass string_cls = env->FindClass(\"java/lang/String\");\r\n\tMID_String_getBytes = env->GetMethodID(string_cls, \"getBytes\", \"()[B\");\r\n\tMID_String_init = env->GetMethodID(string_cls, \"<init>\", \"([B)V\");\r\n\tenv->DeleteLocalRef(string_cls);\r\n}\r\n\r\n\r\n// =======================================================================\r\n// -----------------  helper methods  ------------------------------------\r\n// =======================================================================\r\n\r\nvoid put_lp(JNIEnv *env, jobject obj, lprec *lp) {\r\n\tenv->SetLongField(obj, FID_lp, reinterpret_cast<jlong>(lp));\r\n}\r\n\r\nlprec* get_lp(JNIEnv *env, jobject obj) {\r\n\treturn (reinterpret_cast<lprec*>(env->GetLongField(obj, FID_lp)));\r\n}\r\n\r\nvoid JNU_ThrowByName(JNIEnv* env, const char* name, const char* msg)\r\n{\r\n\tjclass cls = env->FindClass(name);\r\n\t/* if cls is NULL, an exception has already been thrown */\r\n\tif (cls != NULL) {\r\n\t\tenv->ThrowNew(cls, msg);\r\n\t}\r\n\t/* free local ref */\r\n\tenv->DeleteLocalRef(cls);\r\n}\r\n\r\nvoid throw_exception(JNIEnv* env, const char* msg) {\r\n\tJNU_ThrowByName(env, \"lpsolve/LpSolveException\", msg);\r\n}\r\n\r\nvoid throw_exception_with_status(JNIEnv* env, lprec* lp, const char* funcname) {\r\n\tint statuscode = get_status(lp);\r\n\tchar *statustext = get_statustext(lp, statuscode);\r\n\tchar msg[200];\r\n\tsprintf(msg, \"ERROR in %s: status = %d (%s)\", funcname, statuscode, statustext);\r\n\tJNU_ThrowByName(env, \"lpsolve/LpSolveException\", msg);\r\n}\r\n\r\n/*\r\n * Utility function that creates a jstring from a locale-specific\r\n * native C string.\r\n * See Liang, The Java Native Interface, p. 99\r\n */\r\n/*\r\njstring JNU_NewStringNative(JNIEnv* env, const char *str) {\r\n\tjstring result = NULL;\r\n\tjbyteArray bytes = 0;\r\n\tjsize len;\r\n\r\n\tif (env->EnsureLocalCapacity(2) < 0) {\r\n\t\treturn NULL;\r\n\t}\r\n\tlen = (jsize)strlen(str);\r\n\tbytes = env->NewByteArray(len);\r\n\tif (bytes != NULL) {\r\n\t\tenv->SetByteArrayRegion(bytes, 0, len, (jbyte *)str);\r\n\t\tjclass string_cls = env->FindClass(\"java/lang/String\");\r\n\t\tresult = (jstring)env->NewObject(string_cls, MID_String_init, bytes);\r\n\t\tenv->DeleteLocalRef(string_cls);\r\n\t\tenv->DeleteLocalRef(bytes);\r\n\t}\r\n\treturn result;\r\n}\r\n*/\r\n\r\n/*\r\n * Utility function that translates a jstring to a locale-specific\r\n * native C string.\r\n * See Liang, The Java Native Interface, p. 100\r\n */\r\nchar* JNU_GetStringNativeChars(JNIEnv* env, jstring jstr) {\r\n\tchar* result = 0;\r\n\tjbyteArray bytes = 0;\r\n\tjthrowable ex = 0;\r\n\r\n\tif (env->EnsureLocalCapacity(2) < 0) {\r\n\t\treturn 0;\t/* exception thrown */\r\n\t}\r\n\tbytes = (jbyteArray)env->CallObjectMethod(jstr, MID_String_getBytes);\r\n\tex = env->ExceptionOccurred();\r\n\tif (!ex) {\r\n\t\tjint len = env->GetArrayLength(bytes);\r\n\t\tresult = new char[len + 1];\r\n\t\tif (result == 0) {\r\n\t\t\tthrow_exception(env, \"out of memory\");\r\n\t\t\tenv->DeleteLocalRef(bytes);\r\n\t\t\treturn 0;\r\n\t\t}\r\n\t\tenv->GetByteArrayRegion(bytes, 0, len, (jbyte *)result);\r\n\t\tresult[len] = 0;\r\n\t}\r\n\telse {\r\n\t\tenv->DeleteLocalRef(ex);\r\n\t}\r\n\r\n\tenv->DeleteLocalRef(bytes);\r\n\treturn result;\r\n}\r\n\r\n// =======================================================================\r\n// -----------------  JNI interface methods  -----------------------------\r\n// =======================================================================\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    makeLp\r\n * Signature: (II)Llpsolve/LpSolve;\r\n */\r\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_makeLp\r\n  (JNIEnv *env, jclass cls, jint rows, jint columns)\r\n{\r\n\tjobject result = NULL;\r\n\tjclass lpsolve_cls = NULL;\r\n\r\n\tlprec* lp = make_lp(rows, columns);\r\n\tif (lp == NULL) {\r\n\t\tthrow_exception(env, \"make_lp returned NULL\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tresult = env->NewObject(lpsolve_cls, MID_lpsolve_constr, reinterpret_cast<jlong>(lp));\r\n\t/* no error checking because we're terminating anyway */\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    copyLp\r\n * Signature: ()Llpsolve/LpSolve;\r\n */\r\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_copyLp\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tjobject result = NULL;\r\n\tjclass lpsolve_cls = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tlprec* newLp = copy_lp(lp);\r\n\tif (newLp == NULL) {\r\n\t\tthrow_exception(env, \"copy_lp returned NULL\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tresult = env->NewObject(lpsolve_cls, MID_lpsolve_constr, reinterpret_cast<jlong>(newLp));\r\n\t/* no error checking because we're terminating anyway */\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    readLp\r\n * Signature: (Ljava/lang/String;ILjava/lang/String;)Llpsolve/LpSolve;\r\n */\r\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_readLp\r\n  (JNIEnv *env, jclass cls, jstring filename, jint verbose, jstring lpName)\r\n{\r\n\tlprec* lp = NULL;\r\n\tjobject result = NULL;\r\n\tjclass lpsolve_cls = NULL;\r\n\tconst char* c_filename = NULL;\r\n\tconst char* c_lpName = NULL;\r\n\r\n\tif (filename != NULL) {\r\n\t\tc_filename = JNU_GetStringNativeChars(env, filename);\r\n\t\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\tif (lpName != NULL) {\r\n\t\tif ((c_lpName = env->GetStringUTFChars(lpName, NULL)) == NULL) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlp = read_LP((char *)c_filename, verbose, (char *)c_lpName);\r\n\tif (lp == NULL) {\r\n\t\tthrow_exception(env, \"read_LP returned NULL\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tresult = env->NewObject(lpsolve_cls, MID_lpsolve_constr, reinterpret_cast<jlong>(lp));\r\n\t/* no error checking because we're terminating anyway */\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tdelete (char *)c_filename;\r\n\tenv->ReleaseStringUTFChars(lpName, c_lpName);\r\n\treturn result;\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    readMps\r\n * Signature: (Ljava/lang/String;I)Llpsolve/LpSolve;\r\n */\r\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_readMps\r\n  (JNIEnv *env, jclass cls, jstring filename, jint options)\r\n{\r\n\tlprec* lp = NULL;\r\n\tjobject result = NULL;\r\n\tjclass lpsolve_cls = NULL;\r\n\tconst char* c_filename = NULL;\r\n\r\n\tif (filename != NULL) {\r\n\t\tc_filename = JNU_GetStringNativeChars(env, filename);\r\n\t\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlp = read_MPS((char *)c_filename, options);\r\n\tif (lp == NULL) {\r\n\t\tthrow_exception(env, \"read_MPS returned NULL\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tresult = env->NewObject(lpsolve_cls, MID_lpsolve_constr, reinterpret_cast<jlong>(lp));\r\n\t/* no error checking because we're terminating anyway */\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tdelete (char *)c_filename;\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    readFreeMps\r\n * Signature: (Ljava/lang/String;I)Llpsolve/LpSolve;\r\n */\r\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_readFreeMps\r\n  (JNIEnv *env, jclass cls, jstring filename, jint options)\r\n{\r\n\tlprec* lp = NULL;\r\n\tjobject result = NULL;\r\n\tjclass lpsolve_cls = NULL;\r\n\tconst char* c_filename = NULL;\r\n\r\n\tif (filename != NULL) {\r\n\t\tc_filename = JNU_GetStringNativeChars(env, filename);\r\n\t\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlp = read_freeMPS((char *)c_filename, options);\r\n\tif (lp == NULL) {\r\n\t\tthrow_exception(env, \"read_freeMPS returned NULL\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tresult = env->NewObject(lpsolve_cls, MID_lpsolve_constr, reinterpret_cast<jlong>(lp));\r\n\t/* no error checking because we're terminating anyway */\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tdelete (char *)c_filename;\r\n\treturn result;\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    readXLI\r\n * Signature: (Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;I)Llpsolve/LpSolve;\r\n */\r\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_readXLI\r\n  (JNIEnv *env, jclass cls, jstring xliname, jstring modelname, jstring dataname, jstring options, jint verbose)\r\n{\r\n\tlprec* lp = NULL;\r\n\tjobject result = NULL;\r\n\tjclass lpsolve_cls = NULL;\r\n\tconst char* c_xliname = NULL;\r\n\tconst char* c_modelname = NULL;\r\n\tconst char* c_dataname = NULL;\r\n\tconst char* c_options = NULL;\r\n\r\n\tif (xliname != NULL) {\r\n\t\tif ((c_xliname = env->GetStringUTFChars(xliname, NULL)) == NULL) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tif (modelname != NULL) {\r\n\t\tc_modelname = JNU_GetStringNativeChars(env, modelname);\r\n\t\tif (c_modelname == 0 || env->ExceptionCheck()) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tif (dataname != NULL) {\r\n\t\tc_dataname = JNU_GetStringNativeChars(env, dataname);\r\n\t\tif (c_dataname == 0 || env->ExceptionCheck()) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tif (options != NULL) {\r\n\t\tif ((c_options = env->GetStringUTFChars(options, NULL)) == NULL) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlp = read_XLI((char *)c_xliname, (char *)c_modelname, (char *)c_dataname, (char *)c_options, verbose);\r\n\tif (lp == NULL) {\r\n\t\tthrow_exception(env, \"read_XLI returned NULL\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tresult = env->NewObject(lpsolve_cls, MID_lpsolve_constr, reinterpret_cast<jlong>(lp));\r\n\t/* no error checking because we're terminating anyway */\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tenv->ReleaseStringUTFChars(xliname, c_xliname);\r\n\tdelete (char *)c_modelname;\r\n\tdelete (char *)c_dataname;\r\n\tenv->ReleaseStringUTFChars(options, c_options);\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    resizeLp\r\n * Signature:\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_resizeLp\r\n  (JNIEnv *env, jobject obj, jint rows, jint columns)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = resize_lp(lp, rows, columns);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"resize_lp\");\r\n        }\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setLpName\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setLpName\r\n  (JNIEnv *env, jobject obj, jstring name)\r\n{\r\n\tconst char* c_name = NULL;\r\n\r\n\tif (name != NULL) {\r\n\t\tif ((c_name = env->GetStringUTFChars(name, NULL)) == NULL) {\r\n\t\t\treturn;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_lp_name(lp, (char *)c_name);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_lp_name\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(name, c_name);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getLpName\r\n * Signature: ()Ljava/lang/String;\r\n */\r\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getLpName\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tjstring name = NULL;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tchar *c_name = get_lp_name(lp);\r\n\tif (c_name != NULL) {\r\n\t\tname = env->NewStringUTF(c_name);\r\n\t\t/* no error checking because we're terminating anyway */\r\n\t}\r\n\treturn name;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    addConstraint\r\n * Signature: ([DID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addConstraint\r\n  (JNIEnv *env, jobject obj, jdoubleArray row, jint constrType, jdouble rh)\r\n{\r\n\tjdouble* c_row = env->GetDoubleArrayElements(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = add_constraint(lp, c_row, constrType, rh);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"add_constraint\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseDoubleArrayElements(row, c_row, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    addConstraintex\r\n * Signature: (I[D[IID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addConstraintex\r\n  (JNIEnv *env, jobject obj, jint count, jdoubleArray row, jintArray colno, jint constrType, jdouble rh)\r\n{\r\n\tunsigned char rc;\r\n\tjdouble* c_row = NULL;\r\n\tjint* c_colno = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\r\n\tc_row = env->GetDoubleArrayElements(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_colno = env->GetIntArrayElements(colno, NULL);\r\n\tif (c_colno == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\trc = add_constraintex(lp, count, (REAL *)c_row, (int *)c_colno, constrType, rh);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"add_constraintex\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(row, c_row, 0);\r\n\tenv->ReleaseIntArrayElements(colno, c_colno, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    strAddConstraint\r\n * Signature: (Ljava/lang/String;ID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strAddConstraint\r\n  (JNIEnv *env, jobject obj, jstring row, jint constrType, jdouble rh)\r\n{\r\n\tconst char* c_row = env->GetStringUTFChars(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = str_add_constraint(lp, (char*)c_row, constrType, rh);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"str_add_constraint\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(row, c_row);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    delConstraint\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_delConstraint\r\n  (JNIEnv *env, jobject obj, jint rownr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = del_constraint(lp, rownr);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"del_constraint\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isConstrType\r\n * Signature: (II)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isConstrType\r\n  (JNIEnv *env, jobject obj, jint row, jint mask)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_constr_type(lp, row, mask) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    addLagCon\r\n * Signature: ([DID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addLagCon\r\n  (JNIEnv *env, jobject obj, jdoubleArray row, jint constrType, jdouble rh)\r\n{\r\n\tjdouble* c_row = env->GetDoubleArrayElements(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = add_lag_con(lp, c_row, constrType, rh);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"add_lag_con\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseDoubleArrayElements(row, c_row, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    strAddLagCon\r\n * Signature: (Ljava/lang/String;ID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strAddLagCon\r\n  (JNIEnv *env, jobject obj, jstring row, jint constrType, jdouble rh)\r\n{\r\n\tconst char* c_row = env->GetStringUTFChars(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = str_add_lag_con(lp, (char*)c_row, constrType, rh);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"str_add_lag_con\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(row, c_row);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    addColumn\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addColumn\r\n  (JNIEnv *env, jobject obj, jdoubleArray column)\r\n{\r\n\tjdouble* c_column = env->GetDoubleArrayElements(column, NULL);\r\n\tif (c_column == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = add_column(lp, c_column);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"add_column\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseDoubleArrayElements(column, c_column, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    addColumnex\r\n * Signature: (I[D[I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addColumnex\r\n  (JNIEnv *env, jobject obj, jint count, jdoubleArray column, jintArray rowno)\r\n{\r\n\tunsigned char rc;\r\n\tjdouble* c_column = NULL;\r\n\tjint* c_rowno = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\r\n\tc_column = env->GetDoubleArrayElements(column, NULL);\r\n\tif (c_column == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_rowno = env->GetIntArrayElements(rowno, NULL);\r\n\tif (c_rowno == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\trc = add_columnex(lp, count, c_column, (int *)c_rowno);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"add_columnex\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(column, c_column, 0);\r\n\tenv->ReleaseIntArrayElements(rowno, c_rowno, 0);\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    strAddColumn\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strAddColumn\r\n  (JNIEnv *env, jobject obj, jstring column)\r\n{\r\n\tconst char* c_column = env->GetStringUTFChars(column, NULL);\r\n\tif (c_column == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = str_add_column(lp, (char*)c_column);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"str_add_column\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(column, c_column);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    delColumn\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_delColumn\r\n  (JNIEnv *env, jobject obj, jint columnnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = del_column(lp, columnnr);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"del_column\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setRow\r\n * Signature: (I[D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRow\r\n  (JNIEnv *env, jobject obj, jint rowno, jdoubleArray row)\r\n{\r\n\tjdouble* c_row = env->GetDoubleArrayElements(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_row(lp, rowno, c_row);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_row\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseDoubleArrayElements(row, c_row, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setRowex\r\n * Signature: (II[D[I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRowex\r\n  (JNIEnv *env, jobject obj, jint rowno, jint count, jdoubleArray row, jintArray colno)\r\n{\r\n\tunsigned char rc;\r\n\tjdouble* c_row = NULL;\r\n\tjint* c_colno = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\r\n\tc_row = env->GetDoubleArrayElements(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_colno = env->GetIntArrayElements(colno, NULL);\r\n\tif (c_colno == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\trc = set_rowex(lp, rowno, count, c_row, (int *)c_colno);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_rowex\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(row, c_row, 0);\r\n\tenv->ReleaseIntArrayElements(colno, c_colno, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setColumn\r\n * Signature: (I[D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setColumn\r\n  (JNIEnv *env, jobject obj, jint colno, jdoubleArray column)\r\n{\r\n\tjdouble* c_column = env->GetDoubleArrayElements(column, NULL);\r\n\tif (c_column == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_column(lp, colno, c_column);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_column\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseDoubleArrayElements(column, c_column, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setColumnex\r\n * Signature: (II[D[I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setColumnex\r\n  (JNIEnv *env, jobject obj, jint colno, jint count, jdoubleArray column, jintArray rowno)\r\n{\r\n\tunsigned char rc;\r\n\tjdouble* c_column = NULL;\r\n\tjint* c_rowno = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\r\n\tc_column = env->GetDoubleArrayElements(column, NULL);\r\n\tif (c_column == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_rowno = env->GetIntArrayElements(rowno, NULL);\r\n\tif (c_rowno == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\trc = set_columnex(lp, colno, count, c_column, (int *)c_rowno);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_columnex\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(column, c_column, 0);\r\n\tenv->ReleaseIntArrayElements(rowno, c_rowno, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    columnInLp\r\n * Signature: ([D)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_columnInLp\r\n  (JNIEnv *env, jobject obj, jdoubleArray column)\r\n{\r\n\tjdouble* c_column = env->GetDoubleArrayElements(column, NULL);\r\n\tif (c_column == NULL) {\r\n\t\treturn FALSE;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tjint result = column_in_lp(lp, c_column);\r\n\r\n\tenv->ReleaseDoubleArrayElements(column, c_column, 0);\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setRowName\r\n * Signature: (ILjava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRowName\r\n  (JNIEnv *env, jobject obj, jint rownr, jstring name)\r\n{\r\n\tconst char* c_name = NULL;\r\n\r\n\tif (name != NULL) {\r\n\t\tif ((c_name = env->GetStringUTFChars(name, NULL)) == NULL) {\r\n\t\t\treturn;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_row_name(lp, rownr, (char *)c_name);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_row_name\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(name, c_name);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getRowName\r\n * Signature: (I)Ljava/lang/String;\r\n */\r\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getRowName\r\n  (JNIEnv *env, jobject obj, jint rownr)\r\n{\r\n\tjstring name = NULL;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tchar *c_name = get_row_name(lp, rownr);\r\n\tif (c_name != NULL) {\r\n\t\tname = env->NewStringUTF(c_name);\r\n\t\t/* no error checking because we're terminating anyway */\r\n\t}\r\n\treturn name;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getOrigrowName\r\n * Signature: (I)Ljava/lang/String;\r\n */\r\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getOrigrowName\r\n  (JNIEnv *env, jobject obj, jint rownr)\r\n{\r\n\tjstring name = NULL;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tchar *c_name = get_origrow_name(lp, rownr);\r\n\tif (c_name != NULL) {\r\n\t\tname = env->NewStringUTF(c_name);\r\n\t\t/* no error checking because we're terminating anyway */\r\n\t}\r\n\treturn name;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setColName\r\n * Signature: (ILjava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setColName\r\n  (JNIEnv *env, jobject obj, jint colnr, jstring name)\r\n{\r\n\tconst char* c_name = NULL;\r\n\r\n\tif (name != NULL) {\r\n\t\tif ((c_name = env->GetStringUTFChars(name, NULL)) == NULL) {\r\n\t\t\treturn;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_col_name(lp, colnr, (char *)c_name);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_col_name\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(name, c_name);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getColName\r\n * Signature: (I)Ljava/lang/String;\r\n */\r\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getColName\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tjstring name = NULL;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tchar *c_name = get_col_name(lp, colnr);\r\n\tif (c_name != NULL) {\r\n\t\tname = env->NewStringUTF(c_name);\r\n\t\t/* no error checking because we're terminating anyway */\r\n\t}\r\n\treturn name;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getOrigcolName\r\n * Signature: (I)Ljava/lang/String;\r\n */\r\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getOrigcolName\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tjstring name = NULL;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tchar *c_name = get_origcol_name(lp, colnr);\r\n\tif (c_name != NULL) {\r\n\t\tname = env->NewStringUTF(c_name);\r\n\t\t/* no error checking because we're terminating anyway */\r\n\t}\r\n\treturn name;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setRhVec\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRhVec\r\n  (JNIEnv *env, jobject obj, jdoubleArray rh)\r\n{\r\n\tjdouble* c_rh = env->GetDoubleArrayElements(rh, NULL);\r\n\tif (c_rh == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\t/* Strange enough, set_rh_vec has no return value */\r\n\tset_rh_vec(lp, c_rh);\r\n\r\n\tenv->ReleaseDoubleArrayElements(rh, c_rh, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    strSetRhVec\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strSetRhVec\r\n  (JNIEnv *env, jobject obj, jstring rh)\r\n{\r\n\tconst char* c_rh = env->GetStringUTFChars(rh, NULL);\r\n\tif (c_rh == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = str_set_rh_vec(lp, (char*)c_rh);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"str_set_rh_vec\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(rh, c_rh);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setConstrType\r\n * Signature: (II)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setConstrType\r\n  (JNIEnv *env, jobject obj, jint rownr, jint constrType)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_constr_type(lp, rownr, constrType);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_constr_type\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getConstrType\r\n * Signature: (I)S\r\n */\r\nJNIEXPORT jshort JNICALL Java_lpsolve_LpSolve_getConstrType\r\n  (JNIEnv *env, jobject obj, jint rownr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint constrType = get_constr_type(lp, rownr);\r\n\tif (constrType == -1) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_constr_type\");\r\n\t}\r\n\treturn (jshort)constrType;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    addSOS\r\n * Signature: (Ljava/lang/String;III[I[D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addSOS\r\n  (JNIEnv *env, jobject obj, jstring name, jint sostype, jint priority, jint count, jintArray sosvars, jdoubleArray weights)\r\n{\r\n\tint rc;\r\n\tconst char* c_name = NULL;\r\n\tjint* c_sosvars = NULL;\r\n\tjdouble* c_weights = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\r\n\tif (name != NULL) {\r\n\t\tif ((c_name = env->GetStringUTFChars(name, NULL)) == NULL) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\tc_sosvars = env->GetIntArrayElements(sosvars, NULL);\r\n\tif (c_sosvars == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tc_weights = env->GetDoubleArrayElements(weights, NULL);\r\n\tif (c_weights == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\trc = add_SOS(lp, (char *)c_name, (short)sostype, priority, count, (int *)c_sosvars, c_weights);\r\n\tif (rc == 0) {\r\n\t\tthrow_exception_with_status(env, lp, \"add_SOS\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseStringUTFChars(name, c_name);\r\n\tenv->ReleaseIntArrayElements(sosvars, c_sosvars, 0);\r\n\tenv->ReleaseDoubleArrayElements(weights, c_weights, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isSOSVar\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isSOSVar\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_SOS_var(lp, colnr) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setObjFn\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setObjFn\r\n  (JNIEnv *env, jobject obj, jdoubleArray row)\r\n{\r\n\tjdouble* c_row = env->GetDoubleArrayElements(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_obj_fn(lp, c_row);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_obj_fn\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseDoubleArrayElements(row, c_row, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    strSetObjFn\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strSetObjFn\r\n  (JNIEnv *env, jobject obj, jstring row)\r\n{\r\n\tconst char* c_row = env->GetStringUTFChars(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = str_set_obj_fn(lp, (char*)c_row);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"str_set_obj_fn\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(row, c_row);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setObjFnex\r\n * Signature: (I[D[I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setObjFnex\r\n  (JNIEnv *env, jobject obj, jint count, jdoubleArray row, jintArray colno)\r\n{\r\n\tunsigned char rc;\r\n\tjdouble* c_row = NULL;\r\n\tjint* c_colno = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\r\n\tc_row = env->GetDoubleArrayElements(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_colno = env->GetIntArrayElements(colno, NULL);\r\n\tif (c_colno == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\trc = set_obj_fnex(lp, count, c_row, (int *)c_colno);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_obj_fnex\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(row, c_row, 0);\r\n\tenv->ReleaseIntArrayElements(colno, c_colno, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setObj\r\n * Signature: (ID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setObj\r\n  (JNIEnv *env, jobject obj, jint column, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_obj(lp, column, value);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_obj\");\r\n\t}\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setMat\r\n * Signature: (IID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMat\r\n  (JNIEnv *env, jobject obj, jint row, jint column, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_mat(lp, row, column, value);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_mat\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getMat\r\n * Signature: (II)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getMat\r\n  (JNIEnv *env, jobject obj, jint row, jint column)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_mat(lp, row, column);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getRow\r\n * Signature: (I[D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getRow\r\n  (JNIEnv *env, jobject obj, jint rownr, jdoubleArray row)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc;\r\n\tint size = (1 + get_Ncolumns(lp));\r\n\tdouble* c_row = new double[size];\r\n\tif (c_row == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_row(lp, rownr, c_row);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_row\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(row) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(row, 0, size, c_row);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_row;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrRow\r\n * Signature: (I)[D\r\n */\r\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrRow\r\n  (JNIEnv *env, jobject obj, jint rownr)\r\n{\r\n\tunsigned char rc;\r\n\tjdoubleArray row = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = (1 + get_Ncolumns(lp));\r\n\tdouble* c_row = new double[size];\r\n\tif (c_row == NULL) {\r\n\t\tthrow_exception(env, \"getRow: cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\trc = get_row(lp, rownr, c_row);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_row\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\trow = env->NewDoubleArray(size);\r\n\tif (row == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(row, 0, size, c_row);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_row;\r\n\treturn row;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getRowex\r\n * Signature: (I[D[I)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getRowex\r\n  (JNIEnv *env, jobject obj, jint rownr, jdoubleArray row, jintArray nzcols)\r\n{\r\n\tint nzcount;\r\n\tjdouble* c_row = NULL;\r\n\tjint* c_nzcols = NULL;\r\n\tlprec* lp;\r\n\r\n\tc_row = env->GetDoubleArrayElements(row, NULL);\r\n\tif (c_row == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_nzcols = env->GetIntArrayElements(nzcols, NULL);\r\n\tif (c_nzcols == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tlp = get_lp(env, obj);\r\n\tnzcount = get_rowex(lp, rownr, c_row, (int *)c_nzcols);\r\n\tif (nzcount == -1) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_rowex\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(row, c_row, 0);\r\n\tenv->ReleaseIntArrayElements(nzcols, c_nzcols, 0);\r\n\r\n\treturn nzcount;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getColumn\r\n * Signature: (I[D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getColumn\r\n  (JNIEnv *env, jobject obj, jint columnnr, jdoubleArray column)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc;\r\n\tint size = (1 + get_Nrows(lp));\r\n\tdouble* c_column = new double[size];\r\n\tif (c_column == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_column(lp, columnnr, c_column);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_column\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(column) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(column, 0, size, c_column);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_column;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrColumn\r\n * Signature: (I)[D\r\n */\r\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrColumn\r\n  (JNIEnv *env, jobject obj, jint columnnr)\r\n{\r\n\tunsigned char rc;\r\n\tjdoubleArray column = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = (1 + get_Nrows(lp));\r\n\tdouble* c_column = new double[size];\r\n\tif (c_column == NULL) {\r\n\t\tthrow_exception(env, \"getColumn: cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\trc = get_column(lp, columnnr, c_column);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_column\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tcolumn = env->NewDoubleArray(size);\r\n\tif (column == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(column, 0, size, c_column);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_column;\r\n\treturn column;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getColumnex\r\n * Signature: (I[D[I)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getColumnex\r\n  (JNIEnv *env, jobject obj, jint colnr, jdoubleArray column, jintArray nzrows)\r\n{\r\n\tint nzcount;\r\n\tjdouble* c_column = NULL;\r\n\tjint* c_nzrows = NULL;\r\n\tlprec* lp;\r\n\r\n\tc_column = env->GetDoubleArrayElements(column, NULL);\r\n\tif (c_column == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_nzrows = env->GetIntArrayElements(nzrows, NULL);\r\n\tif (c_nzrows == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tlp = get_lp(env, obj);\r\n\tnzcount = get_columnex(lp, colnr, c_column, (int *)c_nzrows);\r\n\tif (nzcount == -1) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_columnex\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(column, c_column, 0);\r\n\tenv->ReleaseIntArrayElements(nzrows, c_nzrows, 0);\r\n\r\n\treturn nzcount;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setMaxim\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMaxim\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_maxim(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setMinim\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMinim\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_minim(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setSense\r\n * Signature: (Z)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setSense\r\n  (JNIEnv *env, jobject obj, jboolean maximize)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_sense(lp, (maximize == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isMaxim\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isMaxim\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_maxim(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setLowbo\r\n * Signature: (ID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setLowbo\r\n  (JNIEnv *env, jobject obj, jint colnr, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_lowbo(lp, colnr, value);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_lowbo\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getLowbo\r\n * Signature: (I)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getLowbo\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_lowbo(lp, colnr);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setUpbo\r\n * Signature: (ID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setUpbo\r\n  (JNIEnv *env, jobject obj, jint colnr, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_upbo(lp, colnr, value);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_upbo\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getUpbo\r\n * Signature: (I)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getUpbo\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_upbo(lp, colnr);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setUnbounded\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setUnbounded\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_unbounded(lp, colnr);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_unbounded\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isUnbounded\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isUnbounded\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_unbounded(lp, colnr) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isNegative\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isNegative\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_negative(lp, colnr) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBounds\r\n * Signature: (IDD)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBounds\r\n  (JNIEnv *env, jobject obj, jint colnr, jdouble lower, jdouble upper)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_bounds(lp, colnr, lower, upper);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_bounds\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBoundsTighter\r\n * Signature: (Z)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBoundsTighter\r\n  (JNIEnv *env, jobject obj, jboolean tighten)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_bounds_tighter(lp, (tighten == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getBoundsTighter\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_getBoundsTighter\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((get_bounds_tighter(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setRhRange\r\n * Signature: (ID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRhRange\r\n  (JNIEnv *env, jobject obj, jint rownr, jdouble range)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_rh_range(lp, rownr, range);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_rh_range\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getRhRange\r\n * Signature: (I)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getRhRange\r\n  (JNIEnv *env, jobject obj, jint rownr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_rh_range(lp, rownr);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setInt\r\n * Signature: (IZ)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setInt\r\n  (JNIEnv *env, jobject obj, jint colnr, jboolean mustBeInteger)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_int(lp, colnr, (mustBeInteger == JNI_TRUE) ? TRUE : FALSE);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_int\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isInt\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isInt\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_int(lp, colnr) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBinary\r\n * Signature: (IZ)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBinary\r\n  (JNIEnv *env, jobject obj, jint colnr, jboolean mustBeBin)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_binary(lp, colnr, (mustBeBin == JNI_TRUE) ? TRUE : FALSE);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_binary\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isBinary\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isBinary\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_binary(lp, colnr) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setSemicont\r\n * Signature: (IZ)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setSemicont\r\n  (JNIEnv *env, jobject obj, jint colnr, jboolean mustBeSc)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_semicont(lp, colnr, (mustBeSc == JNI_TRUE) ? TRUE : FALSE);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_semicont\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isSemicont\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isSemicont\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_semicont(lp, colnr) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setInfinite\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setInfinite\r\n  (JNIEnv *env, jobject obj, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_infinite(lp, value);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getInfinite\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getInfinite\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_infinite(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isInfinite\r\n * Signature: (D)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isInfinite\r\n  (JNIEnv *env, jobject obj, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_infinite(lp, value) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setEpsint\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsint\r\n  (JNIEnv *env, jobject obj, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_epsint(lp, value);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getEpsint\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsint\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_epsint(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setEpsb\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsb\r\n  (JNIEnv *env, jobject obj, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_epsb(lp, value);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getEpsb\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsb\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_epsb(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setEpsd\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsd\r\n  (JNIEnv *env, jobject obj, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_epsd(lp, value);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getEpsd\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsd\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_epsd(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setEpsel\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsel\r\n  (JNIEnv *env, jobject obj, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_epsel(lp, value);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getEpsel\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsel\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_epsel(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setEpspivot\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpspivot\r\n  (JNIEnv *env, jobject obj, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_epspivot(lp, value);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getEpspivot\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpspivot\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_epspivot(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setEpsperturb\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsperturb\r\n  (JNIEnv *env, jobject obj, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_epsperturb(lp, value);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getEpsperturb\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsperturb\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_epsperturb(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setEpslevel\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpslevel\r\n  (JNIEnv *env, jobject obj, jint epslevel)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_epslevel(lp, epslevel);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_epslevel\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getStatus\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getStatus\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_status(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setMipGap\r\n * Signature: (ZD)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMipGap\r\n  (JNIEnv *env, jobject obj, jboolean absolute, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_mip_gap(lp, (absolute == JNI_TRUE) ? TRUE : FALSE, value);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getMipGap\r\n * Signature: (Z)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getMipGap\r\n  (JNIEnv *env, jobject obj, jboolean absolute)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_mip_gap(lp, (absolute == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setRh\r\n * Signature: (ID)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRh\r\n  (JNIEnv *env, jobject obj, jint row, jdouble value)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_rh(lp, row, value);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_rh\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getRh\r\n * Signature: (I)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getRh\r\n  (JNIEnv *env, jobject obj, jint row)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_rh(lp, row);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setVerbose\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setVerbose\r\n  (JNIEnv *env, jobject obj, jint verbose)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_verbose(lp, verbose);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getVerbose\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getVerbose\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_verbose(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setTimeout\r\n * Signature: (J)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setTimeout\r\n  (JNIEnv *env, jobject obj, jlong sectimeout)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_timeout(lp, (long)sectimeout);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getTimeout\r\n * Signature: ()J\r\n */\r\nJNIEXPORT jlong JNICALL Java_lpsolve_LpSolve_getTimeout\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_timeout(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    timeElapsed\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_timeElapsed\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn time_elapsed(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setPrintSol\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setPrintSol\r\n  (JNIEnv *env, jobject obj, jint printSol)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_print_sol(lp, printSol);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPrintSol\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getPrintSol\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_print_sol(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setDebug\r\n * Signature: (Z)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setDebug\r\n  (JNIEnv *env, jobject obj, jboolean debug)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_debug(lp, (debug == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isDebug\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isDebug\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_debug(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setTrace\r\n * Signature: (Z)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setTrace\r\n  (JNIEnv *env, jobject obj, jboolean trace)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_trace(lp, (trace == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isTrace\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isTrace\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_trace(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setLagTrace\r\n * Signature: (Z)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setLagTrace\r\n  (JNIEnv *env, jobject obj, jboolean lagTrace)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_lag_trace(lp, (lagTrace == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isLagTrace\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isLagTrace\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_lag_trace(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setAddRowmode\r\n * Signature: (Z)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_setAddRowmode\r\n  (JNIEnv *env, jobject obj, jboolean turnon)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_add_rowmode(lp, (turnon == JNI_TRUE) ? TRUE : FALSE);\r\n\treturn (rc == TRUE) ? JNI_TRUE : JNI_FALSE;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isAddRowmode\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isAddRowmode\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_add_rowmode(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setAntiDegen\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setAntiDegen\r\n  (JNIEnv *env, jobject obj, jint antiDegen)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_anti_degen(lp, antiDegen);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isAntiDegen\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isAntiDegen\r\n  (JNIEnv *env, jobject obj, jint testmask)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_anti_degen(lp, testmask) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getAntiDegen\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getAntiDegen\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_anti_degen(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setPresolve\r\n * Signature: (II)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setPresolve\r\n  (JNIEnv *env, jobject obj, jint doPresolve, jint maxloops)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_presolve(lp, doPresolve, maxloops);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isPresolve\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isPresolve\r\n  (JNIEnv *env, jobject obj, jint testmask)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_presolve(lp, testmask) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPresolve\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getPresolve\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_presolve(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPresolveloops\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getPresolveloops\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_presolveloops(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setMaxpivot\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMaxpivot\r\n  (JNIEnv *env, jobject obj, jint maxNumInv)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_maxpivot(lp, maxNumInv);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getMaxpivot\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getMaxpivot\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_maxpivot(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBbRule\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBbRule\r\n  (JNIEnv *env, jobject obj, jint bbRule)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_bb_rule(lp, bbRule);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getBbRule\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getBbRule\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_bb_rule(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBbDepthlimit\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBbDepthlimit\r\n  (JNIEnv *env, jobject obj, jint bbMaxlevel)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_bb_depthlimit(lp, bbMaxlevel);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getBbDepthlimit\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getBbDepthlimit\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_bb_depthlimit(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getSolutioncount\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getSolutioncount\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_solutioncount(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setSolutionlimit\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setSolutionlimit\r\n  (JNIEnv *env, jobject obj, jint limit)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_solutionlimit(lp, limit);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getSolutionlimit\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getSolutionlimit\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_solutionlimit(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setObjBound\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setObjBound\r\n  (JNIEnv *env, jobject obj, jdouble objBound)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_obj_bound(lp, objBound);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getObjBound\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getObjBound\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_obj_bound(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBbFloorfirst\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBbFloorfirst\r\n  (JNIEnv *env, jobject obj, jint floorFirst)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_bb_floorfirst(lp, floorFirst);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getBbFloorfirst\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getBbFloorfirst\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_bb_floorfirst(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setVarBranch\r\n * Signature: (II)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setVarBranch\r\n  (JNIEnv *env, jobject obj, jint colnr, jint branchMode)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_var_branch(lp, colnr, branchMode);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_var_branch\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getVarBranch\r\n * Signature: (I)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getVarBranch\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_var_branch(lp, colnr);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setVarWeights\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setVarWeights\r\n  (JNIEnv *env, jobject obj, jdoubleArray weights)\r\n{\r\n\tjdouble* c_weights = env->GetDoubleArrayElements(weights, NULL);\r\n\tif (c_weights == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_var_weights(lp, c_weights);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_var_weights\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseDoubleArrayElements(weights, c_weights, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getVarPriority\r\n * Signature: (I)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getVarPriority\r\n  (JNIEnv *env, jobject obj, jint colnr)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_var_priority(lp, colnr);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBreakAtFirst\r\n * Signature: (Z)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBreakAtFirst\r\n  (JNIEnv *env, jobject obj, jboolean breakAtFirst)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_break_at_first(lp, (breakAtFirst == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isBreakAtFirst\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isBreakAtFirst\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_break_at_first(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBreakAtValue\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBreakAtValue\r\n  (JNIEnv *env, jobject obj, jdouble breakAtValue)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_break_at_value(lp, breakAtValue);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getBreakAtValue\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getBreakAtValue\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_break_at_value(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setScaling\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setScaling\r\n  (JNIEnv *env, jobject obj, jint scalemode)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_scaling(lp, scalemode);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getScaling\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getScaling\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_scaling(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isScalemode\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isScalemode\r\n  (JNIEnv *env, jobject obj, jint testmask)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_scalemode(lp, testmask) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isScaletype\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isScaletype\r\n  (JNIEnv *env, jobject obj, jint scaletype)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_scaletype(lp, scaletype) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isIntegerscaling\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isIntegerscaling\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_integerscaling(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setScalelimit\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setScalelimit\r\n  (JNIEnv *env, jobject obj, jdouble scalelimit)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_scalelimit(lp, scalelimit);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getScalelimit\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getScalelimit\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_scalelimit(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setImprove\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setImprove\r\n  (JNIEnv *env, jobject obj, jint improve)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_improve(lp, improve);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getImprove\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getImprove\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_improve(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setPivoting\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setPivoting\r\n  (JNIEnv *env, jobject obj, jint pivRule)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_pivoting(lp, pivRule);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPivoting\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getPivoting\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_pivoting(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isPivMode\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isPivMode\r\n  (JNIEnv *env, jobject obj, jint testmask)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_piv_mode(lp, testmask) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isPivRule\r\n * Signature: (I)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isPivRule\r\n  (JNIEnv *env, jobject obj, jint rule)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_piv_rule(lp, rule) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setPreferdual\r\n * Signature: (Z)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setPreferdual\r\n  (JNIEnv *env, jobject obj, jboolean dodual)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_preferdual(lp, (dodual == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setSimplextype\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setSimplextype\r\n  (JNIEnv *env, jobject obj, jint simplextype)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_simplextype(lp, simplextype);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getSimplextype\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getSimplextype\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_simplextype(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setNegrange\r\n * Signature: (D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setNegrange\r\n  (JNIEnv *env, jobject obj, jdouble negrange)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_negrange(lp, negrange);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getNegrange\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getNegrange\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_negrange(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getTotalIter\r\n * Signature: ()J\r\n */\r\nJNIEXPORT jlong JNICALL Java_lpsolve_LpSolve_getTotalIter\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_total_iter(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getMaxLevel\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getMaxLevel\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_max_level(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getTotalNodes\r\n * Signature: ()J\r\n */\r\nJNIEXPORT jlong JNICALL Java_lpsolve_LpSolve_getTotalNodes\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_total_nodes(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    solve\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_solve\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn solve(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getStatustext\r\n * Signature: (I)Ljava/lang/String;\r\n */\r\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getStatustext\r\n  (JNIEnv *env, jobject obj, jint statuscode)\r\n{\r\n\tjstring name = NULL;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tchar *c_name = get_statustext(lp, statuscode);\r\n\tif (c_name != NULL) {\r\n\t\tname = env->NewStringUTF(c_name);\r\n\t\t/* no error checking because we're terminating anyway */\r\n\t}\r\n\treturn name;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    lagSolve\r\n * Signature: (DI)I\r\n */\r\n/*\r\n * TODO: According to Peter Notebaert, this method is temporarily unavailable\r\n * but might be added again in later versions.\r\n *\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_lagSolve\r\n  (JNIEnv *env, jobject obj, jdouble startBound, jint numIter)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn lag_solve(lp, startBound, numIter);\r\n}\r\n*/\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isFeasible\r\n * Signature: ([DD)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isFeasible\r\n  (JNIEnv *env, jobject obj, jdoubleArray values, jdouble threshold)\r\n{\r\n\tjdouble* c_values = env->GetDoubleArrayElements(values, NULL);\r\n\tif (c_values == NULL) {\r\n\t\treturn JNI_FALSE;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = is_feasible(lp, c_values, threshold);\r\n\tjboolean result =  ((rc == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n\r\n\tenv->ReleaseDoubleArrayElements(values, c_values, 0);\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getObjective\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getObjective\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_objective(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getWorkingObjective\r\n * Signature: ()D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getWorkingObjective\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_working_objective(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getVariables\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getVariables\r\n  (JNIEnv *env, jobject obj, jdoubleArray var)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc;\r\n\tint size = get_Ncolumns(lp);\r\n\tdouble* c_var = new double[size];\r\n\tif (c_var == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_variables(lp, c_var);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_variables\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(var) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(var, 0, size, c_var);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_var;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrVariables\r\n * Signature: ()[D\r\n */\r\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrVariables\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tunsigned char rc;\r\n\tjdoubleArray var = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Ncolumns(lp);\r\n\tdouble* c_var = new double[size];\r\n\tif (c_var == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\trc = get_variables(lp, c_var);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_variables\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tvar = env->NewDoubleArray(size);\r\n\tif (var == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(var, 0, size, c_var);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_var;\r\n\treturn var;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getConstraints\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getConstraints\r\n  (JNIEnv *env, jobject obj, jdoubleArray var)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc;\r\n\tint size = get_Nrows(lp);\r\n\tdouble* c_var = new double[size];\r\n\tif (c_var == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_constraints(lp, c_var);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_constraints\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(var) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(var, 0, size, c_var);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_var;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrConstraints\r\n * Signature: ()[D\r\n */\r\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrConstraints\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tunsigned char rc;\r\n\tjdoubleArray var = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Nrows(lp);\r\n\tdouble* c_var = new double[size];\r\n\tif (c_var == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\trc = get_constraints(lp, c_var);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_constraints\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tvar = env->NewDoubleArray(size);\r\n\tif (var == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(var, 0, size, c_var);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_var;\r\n\treturn var;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPrimalSolution\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getPrimalSolution\r\n  (JNIEnv *env, jobject obj, jdoubleArray pv)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc;\r\n\tint nRows = get_Nrows(lp);\r\n\tint nCols = get_Ncolumns(lp);\r\n\tint size = 1 + nRows + nCols;\r\n\tdouble* c_pv = new double[size];\r\n\tif (c_pv == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_primal_solution(lp, c_pv);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_primal_solution\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(pv) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(pv, 0, size, c_pv);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_pv;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrPrimalSolution\r\n * Signature: ()[D\r\n */\r\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrPrimalSolution\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tunsigned char rc;\r\n\tjdoubleArray solution = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint nRows = get_Nrows(lp);\r\n\tint nCols = get_Ncolumns(lp);\r\n\tint size = 1 + nRows + nCols;\r\n\tdouble* c_solution = new double[size];\r\n\tif (c_solution == NULL) {\r\n\t\tthrow_exception(env, \"getPrimalSolution: cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\trc = get_primal_solution(lp, c_solution);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_primal_solution\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tsolution = env->NewDoubleArray(size);\r\n\tif (solution == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(solution, 0, size, c_solution);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_solution;\r\n\treturn solution;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getVarPrimalresult\r\n * Signature: (I)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getVarPrimalresult\r\n  (JNIEnv *env, jobject obj, jint index)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_var_primalresult(lp, index);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getSensitivityRhs\r\n * Signature: ([D[D[D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getSensitivityRhs\r\n  (JNIEnv *env, jobject obj, jdoubleArray duals, jdoubleArray dualsfrom, jdoubleArray dualstill)\r\n{\r\n\tunsigned char rc;\r\n\tdouble *c_duals = NULL, *c_dualsfrom = NULL, *c_dualstill = NULL;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Nrows(lp) + get_Ncolumns(lp);\r\n\tif ((c_duals = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_dualsfrom = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_dualstill = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_sensitivity_rhs(lp, c_duals, c_dualsfrom, c_dualstill);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_sensitivity_rhs\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(duals) < size || env->GetArrayLength(dualsfrom) < size || env->GetArrayLength(dualstill) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(duals, 0, size, c_duals);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(dualsfrom, 0, size, c_dualsfrom);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(dualstill, 0, size, c_dualstill);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete c_duals;\r\n\tdelete c_dualsfrom;\r\n\tdelete c_dualstill;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrSensitivityRhs\r\n * Signature: ()[[D\r\n */\r\nJNIEXPORT jobjectArray JNICALL Java_lpsolve_LpSolve_getPtrSensitivityRhs\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\t// See also Liang, p. 39 for an example with two-dimensional arrays.\r\n\tunsigned char rc;\r\n\tjobjectArray result = NULL;\r\n\tjdoubleArray duals = NULL, dualsfrom = NULL, dualstill = NULL;\r\n\tdouble *c_duals = NULL, *c_dualsfrom = NULL, *c_dualstill = NULL;\r\n\r\n\tjclass doubleArr_cls = env->FindClass(\"[D\");\r\n\tif (doubleArr_cls == NULL) {\r\n\t\treturn NULL;\t/* exception thrown */\r\n\t}\r\n\r\n\tresult = env->NewObjectArray(3, doubleArr_cls, NULL);\r\n\tif (result == NULL) {\r\n\t\treturn NULL;\t/* out of memory error thrown */\r\n\t}\r\n\r\n\t// Now allocate the arrays for the lp_solve method\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Nrows(lp) + get_Ncolumns(lp);\r\n\r\n\tif ((duals = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif ((dualsfrom = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif ((dualstill = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif ((c_duals = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_dualsfrom = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_dualstill = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_sensitivity_rhs(lp, c_duals, c_dualsfrom, c_dualstill);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_sensitivity_rhs\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(duals, 0, size, c_duals);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(dualsfrom, 0, size, c_dualsfrom);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(dualstill, 0, size, c_dualstill);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t// Set the lements of the resulting array\r\n\tenv->SetObjectArrayElement(result, 0, duals);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetObjectArrayElement(result, 1, dualsfrom);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetObjectArrayElement(result, 2, dualstill);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\n\r\ncleanup:\r\n\tdelete c_duals;\r\n\tdelete c_dualsfrom;\r\n\tdelete c_dualstill;\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getDualSolution\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getDualSolution\r\n  (JNIEnv *env, jobject obj, jdoubleArray duals)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc;\r\n\tint nRows = get_Nrows(lp);\r\n\tint nCols = get_Ncolumns(lp);\r\n\tint size = 1 + nRows + nCols;\r\n\tdouble* c_duals = new double[size];\r\n\tif (c_duals == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_dual_solution(lp, c_duals);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_dual_solution\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(duals) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(duals, 0, size, c_duals);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_duals;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrDualSolution\r\n * Signature: ()[D\r\n */\r\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrDualSolution\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tunsigned char rc;\r\n\tjdoubleArray duals = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint nRows = get_Nrows(lp);\r\n\tint nCols = get_Ncolumns(lp);\r\n\tint size = 1 + nRows + nCols;\r\n\tdouble* c_duals = new double[size];\r\n\tif (c_duals == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_dual_solution(lp, c_duals);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_dual_solution\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tduals = env->NewDoubleArray(size);\r\n\tif (duals == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(duals, 0, size, c_duals);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_duals;\r\n\treturn duals;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getVarDualresult\r\n * Signature: (I)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getVarDualresult\r\n  (JNIEnv *env, jobject obj, jint index)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_var_dualresult(lp, index);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getSensitivityObj\r\n * Signature: ([D[D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getSensitivityObj\r\n  (JNIEnv *env, jobject obj, jdoubleArray objfrom, jdoubleArray objtill)\r\n{\r\n\tunsigned char rc;\r\n\tdouble *c_objfrom = NULL, *c_objtill = NULL;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Ncolumns(lp);\r\n\tif ((c_objfrom = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_objtill = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_sensitivity_obj(lp, c_objfrom, c_objtill);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_sensitivity_obj\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(objfrom) < size || env->GetArrayLength(objtill) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(objfrom, 0, size, c_objfrom);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(objtill, 0, size, c_objtill);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete c_objfrom;\r\n\tdelete c_objtill;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrSensitivityObj\r\n * Signature: ()[[D\r\n */\r\nJNIEXPORT jobjectArray JNICALL Java_lpsolve_LpSolve_getPtrSensitivityObj\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\t// See also Liang, p. 39 for an example with two-dimensional arrays.\r\n\tunsigned char rc;\r\n\tjobjectArray result = NULL;\r\n\tjdoubleArray objfrom = NULL, objtill = NULL;\r\n\tdouble *c_objfrom = NULL, *c_objtill = NULL;\r\n\r\n\tjclass doubleArr_cls = env->FindClass(\"[D\");\r\n\tif (doubleArr_cls == NULL) {\r\n\t\treturn NULL;\t/* exception thrown */\r\n\t}\r\n\r\n\t// the resulting object array will contain two double[] arrays\r\n\tresult = env->NewObjectArray(2, doubleArr_cls, NULL);\r\n\tif (result == NULL) {\r\n\t\treturn NULL;\t/* out of memory error thrown */\r\n\t}\r\n\r\n\t// Now allocate the arrays for the lp_solve method\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Ncolumns(lp);\r\n\r\n\tif ((objfrom = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif ((objtill = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif ((c_objfrom = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_objtill = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_sensitivity_obj(lp, c_objfrom, c_objtill);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_sensitivity_obj\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(objfrom, 0, size, c_objfrom);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(objtill, 0, size, c_objtill);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t// Set the lements of the resulting array\r\n\tenv->SetObjectArrayElement(result, 0, objfrom);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetObjectArrayElement(result, 1, objtill);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\n\r\ncleanup:\r\n\tdelete c_objfrom;\r\n\tdelete c_objtill;\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Common code from getSensitivityObjex and getPtrSensitivityObjex implementation\r\n */\r\nvoid getSensitivityObjex\r\n  (JNIEnv *env, jobject obj, jdoubleArray objfrom, jdoubleArray objtill, jdoubleArray objfromvalue, jdoubleArray objtillvalue)\r\n{\r\n\tdouble *c_objfrom = NULL, *c_objtill = NULL, *c_objfromvalue = NULL, *c_objtillvalue = NULL;\r\n\tunsigned char rc;\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Ncolumns(lp);\r\n\r\n\tif ((c_objfrom = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_objtill = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_objfromvalue = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tif ((c_objtillvalue = new double[size]) == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\trc = get_sensitivity_objex(lp, c_objfrom, c_objtill, c_objfromvalue, c_objtillvalue);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_sensitivity_objex\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(objfrom) < size || env->GetArrayLength(objtill) < size\r\n\t\t|| env->GetArrayLength(objfromvalue) < size || env->GetArrayLength(objtillvalue) < size)\r\n\t{\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t// copy results to the Java arrays\r\n\tenv->SetDoubleArrayRegion(objfrom, 0, size, c_objfrom);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(objtill, 0, size, c_objtill);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(objfromvalue, 0, size, c_objfromvalue);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetDoubleArrayRegion(objtillvalue, 0, size, c_objtillvalue);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete c_objfrom;\r\n\tdelete c_objtill;\r\n\tdelete c_objfromvalue;\r\n\tdelete c_objtillvalue;\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getSensitivityObjex\r\n * Signature: ([D[D[D[D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getSensitivityObjex\r\n  (JNIEnv *env, jobject obj, jdoubleArray objfrom, jdoubleArray objtill, jdoubleArray objfromvalue, jdoubleArray objtillvalue)\r\n{\r\n\tgetSensitivityObjex(env, obj, objfrom, objtill, objfromvalue, objtillvalue);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrSensitivityObjex\r\n * Signature: ()[[D\r\n */\r\nJNIEXPORT jobjectArray JNICALL Java_lpsolve_LpSolve_getPtrSensitivityObjex\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\t// See also Liang, p. 39 for an example with two-dimensional arrays.\r\n\tjobjectArray result = NULL;\r\n\tjdoubleArray objfrom = NULL, objtill = NULL, objfromvalue = NULL, objtillvalue = NULL;\r\n\tdouble *c_objfrom = NULL, *c_objtill = NULL, *c_objfromvalue = NULL, *c_objtillvalue = NULL;\r\n\r\n\tjclass doubleArr_cls = env->FindClass(\"[D\");\r\n\tif (doubleArr_cls == NULL) {\r\n\t\treturn NULL;\t/* exception thrown */\r\n\t}\r\n\r\n\t// the resulting object array will contain four double[] arrays\r\n\tresult = env->NewObjectArray(4, doubleArr_cls, NULL);\r\n\tif (result == NULL) {\r\n\t\treturn NULL;\t/* out of memory error thrown */\r\n\t}\r\n\r\n\t// Now allocate the arrays for the lp_solve method\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Ncolumns(lp);\r\n\r\n\tif ((objfrom = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif ((objtill = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif ((objfromvalue = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif ((objtillvalue = env->NewDoubleArray(size)) == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tgetSensitivityObjex(env, obj, objfrom, objtill, objfromvalue, objtillvalue);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t// Set the lements of the resulting array\r\n\tenv->SetObjectArrayElement(result, 0, objfrom);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetObjectArrayElement(result, 1, objtill);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetObjectArrayElement(result, 2, objfromvalue);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tenv->SetObjectArrayElement(result, 3, objtillvalue);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete c_objfrom;\r\n\tdelete c_objtill;\r\n\tdelete c_objfromvalue;\r\n\tdelete c_objtillvalue;\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getPtrLambda\r\n * Signature: ()[D\r\n */\r\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrLambda\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tunsigned char rc;\r\n\tjdoubleArray lambda = NULL;\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint size = get_Lrows(lp);\r\n\tdouble* c_lambda = new double[size];\r\n\tif (c_lambda == NULL) {\r\n\t\tthrow_exception(env, \"getPrimalSolution: cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\trc = get_lambda(lp, c_lambda);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_lambda\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tlambda = env->NewDoubleArray(size);\r\n\tif (lambda == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(lambda, 0, size, c_lambda);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_lambda;\r\n\treturn lambda;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getLambda\r\n * Signature: ([D)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getLambda\r\n  (JNIEnv *env, jobject obj, jdoubleArray lambda)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc;\r\n\tint size = get_Lrows(lp);\r\n\tdouble* c_lambda = new double[size];\r\n\tif (c_lambda == NULL) {\r\n\t\tthrow_exception(env, \"cannot allocate memory\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* We do not use the _ptr_variants because we want to control memory allocation */\r\n\trc = get_lambda(lp, c_lambda);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_lambda\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tif (env->GetArrayLength(lambda) < size) {\r\n\t\tthrow_exception(env, \"Target array is too short to hold values\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\tenv->SetDoubleArrayRegion(lambda, 0, size, c_lambda);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete[] c_lambda;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    deleteLp\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_deleteLp\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tdelete_lp(lp);\r\n\tput_lp(env, obj, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getNrows\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNrows\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_Nrows(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getNcolumns\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNcolumns\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_Ncolumns(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getNorigRows\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNorigRows\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_Norig_rows(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getNorigColumns\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNorigColumns\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_Norig_columns(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getNonzeros\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNonzeros\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_nonzeros(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getLrows\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getLrows\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_Lrows(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getOrigIndex\r\n * Signature: (I)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getOrigIndex\r\n  (JNIEnv *env, jobject obj, jint index)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_orig_index(lp, index);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getLpIndex\r\n * Signature: (I)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getLpIndex\r\n  (JNIEnv *env, jobject obj, jint index)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_lp_index(lp, index);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    guessBasis\r\n * Signature: ([IZ)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_guessBasis\r\n  (JNIEnv *env, jobject obj, jdoubleArray guessvector, jintArray basisvector)\r\n{\r\n\tunsigned char rc;\r\n\tjdouble* c_guessvector;\r\n\tjint* c_basisvector;\r\n        lprec* lp = get_lp(env, obj);\r\n\r\n\tc_guessvector = env->GetDoubleArrayElements(guessvector, NULL);\r\n\tif (c_guessvector == NULL) {\r\n                goto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n        c_basisvector = env->GetIntArrayElements(basisvector, NULL);\r\n\tif (c_basisvector == NULL) {\r\n                goto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\trc = guess_basis(lp, c_guessvector, (int *)c_basisvector);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"guess_basis\");\r\n\t\t/* Fall through and cleanup */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(guessvector, c_guessvector, 0);\r\n        env->ReleaseIntArrayElements(basisvector, c_basisvector, 0);\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBasis\r\n * Signature: ([IZ)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBasis\r\n  (JNIEnv *env, jobject obj, jintArray bascolumn, jboolean nonbasic)\r\n{\r\n\tunsigned char rc;\r\n\tjint* c_bascolumn = env->GetIntArrayElements(bascolumn, NULL);\r\n\tif (c_bascolumn == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\trc = set_basis(lp, (int *)c_bascolumn, (nonbasic == JNI_TRUE) ? TRUE : FALSE);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_basis\");\r\n\t\t/* Fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseIntArrayElements(bascolumn, c_bascolumn, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getBasis\r\n * Signature: ([IZ)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getBasis\r\n  (JNIEnv *env, jobject obj, jintArray bascolumn, jboolean nonbasic)\r\n{\r\n\tunsigned char rc;\r\n\tjint* c_bascolumn = env->GetIntArrayElements(bascolumn, NULL);\r\n\tif (c_bascolumn == NULL) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\t// get_basis has no return value to indicate failure !\r\n\trc = get_basis(lp, (int *)c_bascolumn, (nonbasic == JNI_TRUE) ? TRUE : FALSE);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"get_basis\");\r\n\t\t/* Fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseIntArrayElements(bascolumn, c_bascolumn, 0);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    resetBasis\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_resetBasis\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treset_basis(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    defaultBasis\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_defaultBasis\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tdefault_basis(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBasiscrash\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBasiscrash\r\n  (JNIEnv *env, jobject obj, jint mode)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_basiscrash(lp, mode);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getBasiscrash\r\n * Signature: ()I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getBasiscrash\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn get_basiscrash(lp);\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    unscale\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_unscale\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunscale(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBFP\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBFP\r\n  (JNIEnv *env, jobject obj, jstring name)\r\n{\r\n\tconst char* c_name = NULL;\r\n\r\n\tif (name != NULL) {\r\n\t\tif ((c_name = env->GetStringUTFChars(name, NULL)) == NULL) {\r\n\t\t\treturn;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_BFP(lp, (char *)c_name);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_BFP\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(name, c_name);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isNativeBFP\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isNativeBFP\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_nativeBFP(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    hasBFP\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_hasBFP\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((has_BFP(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    hasXLI\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_hasXLI\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((has_XLI(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isNativeXLI\r\n * Signature: ()Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isNativeXLI\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_nativeXLI(lp) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getNameindex\r\n * Signature: (Ljava/lang/String;Z)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNameindex\r\n  (JNIEnv *env, jobject obj, jstring name, jboolean isrow)\r\n{\r\n\tconst char* c_name = NULL;\r\n\r\n\tif (name != NULL) {\r\n\t\tif ((c_name = env->GetStringUTFChars(name, NULL)) == NULL) {\r\n\t\t\treturn -1;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tint rc = get_nameindex(lp, (char *)c_name, (isrow == JNI_TRUE) ? TRUE : FALSE);\r\n\r\n\tenv->ReleaseStringUTFChars(name, c_name);\r\n\treturn rc;\r\n}\r\n\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    lpSolveVersion\r\n * Signature: ()Llpsolve/VersionInfo;\r\n */\r\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_lpSolveVersion\r\n  (JNIEnv *env, jclass cls)\r\n{\r\n\tint major, minor, release, build;\r\n\tlp_solve_version(&major, &minor, &release, &build);\r\n\r\n\tjclass info_cls = env->FindClass(\"lpsolve/VersionInfo\");\r\n\tif (info_cls == NULL) {\r\n\t\treturn NULL;\t/* exception thrown */\r\n\t}\r\n\r\n\tjmethodID cid = env->GetMethodID(info_cls, \"<init>\", \"(IIII)V\");\r\n\tif (cid == NULL) {\r\n\t\treturn NULL;\t/* exception thrown */\r\n\t}\r\n\r\n\tjobject result = env->NewObject(info_cls, cid, major, minor, release, build);\r\n\t/* no error checking because we're terminating anyway */\r\n\r\n\tenv->DeleteLocalRef(info_cls);\r\n\treturn result;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    dualizeLp\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_dualizeLp\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec *lp = get_lp(env, obj);\r\n\tunsigned char rc = dualize_lp(lp);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"dualize_lp\");\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    isUseNames\r\n * Signature: (Z)Z\r\n */\r\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isUseNames\r\n  (JNIEnv *env, jobject obj, jboolean isRow)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn ((is_use_names(lp, (isRow == JNI_TRUE) ? TRUE : FALSE) == TRUE) ? JNI_TRUE : JNI_FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setUseNames\r\n * Signature: (ZZ)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setUseNames\r\n  (JNIEnv *env, jobject obj, jboolean isRow, jboolean useNames)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tset_use_names(lp, (isRow == JNI_TRUE) ? TRUE : FALSE, (useNames == JNI_TRUE) ? TRUE : FALSE);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    getConstrValue\r\n * Signature: (II[D[I)D\r\n */\r\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getConstrValue\r\n  (JNIEnv *env, jobject obj, jint rownr, jint count, jdoubleArray primsolution, jintArray nzindex)\r\n{\r\n\tdouble value;\r\n\tjdouble* c_primsolution = NULL;\r\n\tjint* c_nzindex = NULL;\r\n\tlprec* lp;\r\n\r\n\tc_primsolution = env->GetDoubleArrayElements(primsolution, NULL);\r\n\tif (c_primsolution == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_nzindex = env->GetIntArrayElements(nzindex, NULL);\r\n\tif (c_nzindex == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tlp = get_lp(env, obj);\r\n\tvalue = get_constr_value(lp, rownr, count, c_primsolution, (int *)c_nzindex);\r\n\r\ncleanup:\r\n\tenv->ReleaseDoubleArrayElements(primsolution, c_primsolution, 0);\r\n\tenv->ReleaseIntArrayElements(nzindex, c_nzindex, 0);\r\n\r\n\treturn value;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setBasisvar\r\n * Signature: (II)I\r\n */\r\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_setBasisvar\r\n  (JNIEnv *env, jobject obj, jint basisPos, jint enteringCol)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treturn set_basisvar(lp, (char)basisPos, (char)enteringCol);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    writeLp\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeLp\r\n  (JNIEnv *env, jobject obj, jstring filename)\r\n{\r\n\tlprec *lp = NULL;\r\n\tunsigned char rc;\r\n\tconst char *c_filename = JNU_GetStringNativeChars(env, filename);\r\n\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\tlp = get_lp(env, obj);\r\n\trc = write_lp(lp, (char*)c_filename);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"write_lp\");\r\n\t\t/* fall through and release pointer */\r\n\t}\r\n\tdelete (char *)c_filename;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    writeMps\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeMps\r\n  (JNIEnv *env, jobject obj, jstring filename)\r\n{\r\n\tlprec *lp = NULL;\r\n\tunsigned char rc;\r\n\tconst char *c_filename = JNU_GetStringNativeChars(env, filename);\r\n\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\tlp = get_lp(env, obj);\r\n\trc = write_mps(lp, (char*)c_filename);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"write_mps\");\r\n\t\t/* fall through and release pointer */\r\n\t}\r\n\tdelete (char *)c_filename;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    writeBasis\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeBasis\r\n  (JNIEnv *env, jobject obj, jstring filename)\r\n{\r\n\tlprec *lp = NULL;\r\n\tunsigned char rc;\r\n\tconst char *c_filename = JNU_GetStringNativeChars(env, filename);\r\n\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\tlp = get_lp(env, obj);\r\n\trc = write_basis(lp, (char*)c_filename);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"write_basis\");\r\n\t\t/* fall through and release pointer */\r\n\t}\r\n\tdelete (char *)c_filename;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    readParams\r\n * Signature: (Ljava/lang/String;Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_readParams\r\n  (JNIEnv *env, jobject obj, jstring filename, jstring options)\r\n{\r\n\tlprec *lp = NULL;\r\n\tunsigned char rc;\r\n\tconst char *c_filename = NULL;\r\n\tconst char *c_options = NULL;\r\n\r\n\tc_filename = JNU_GetStringNativeChars(env, filename);\r\n\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_options = JNU_GetStringNativeChars(env, options);\r\n\tif (c_options == 0 || env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\r\n\tlp = get_lp(env, obj);\r\n\trc = read_params(lp, (char*)c_filename, (char*)c_options);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"read_params\");\r\n\t\t/* fall through and release pointer */\r\n\t}\r\n\r\ncleanup:\r\n\tdelete (char *)c_filename;\r\n\tdelete (char *)c_options;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    writeParams\r\n * Signature: (Ljava/lang/String;Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeParams\r\n  (JNIEnv *env, jobject obj, jstring filename, jstring options)\r\n{\r\n\tlprec *lp = NULL;\r\n\tunsigned char rc;\r\n\tconst char *c_filename = NULL;\r\n\tconst char *c_options = NULL;\r\n\r\n\tc_filename = JNU_GetStringNativeChars(env, filename);\r\n\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\tc_options = JNU_GetStringNativeChars(env, options);\r\n\tif (c_options == 0 || env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\r\n\tlp = get_lp(env, obj);\r\n\trc = write_params(lp, (char*)c_filename, (char*)c_options);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"read_params\");\r\n\t\t/* fall through and release pointer */\r\n\t}\r\n\r\ncleanup:\r\n\tdelete (char *)c_filename;\r\n\tdelete (char *)c_options;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    resetParams\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_resetParams\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\treset_params(lp);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    writeFreeMps\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeFreeMps\r\n  (JNIEnv *env, jobject obj, jstring filename)\r\n{\r\n\tlprec *lp = NULL;\r\n\tunsigned char rc;\r\n\tconst char *c_filename = JNU_GetStringNativeChars(env, filename);\r\n\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\treturn;\t/* exception thrown */\r\n\t}\r\n\tlp = get_lp(env, obj);\r\n\trc = write_freemps(lp, (char*)c_filename);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"write_freemps\");\r\n\t\t/* fall through and release pointer */\r\n\t}\r\n\tdelete (char *)c_filename;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setXLI\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setXLI\r\n  (JNIEnv *env, jobject obj, jstring filename)\r\n{\r\n\tconst char *c_filename = env->GetStringUTFChars(filename, NULL);\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_XLI(lp, (char*)c_filename);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_XLI\");\r\n\t\t/* fall through and release pointer */\r\n\t}\r\n\tenv->ReleaseStringUTFChars(filename, c_filename);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    readBasis\r\n * Signature: (Ljava/lang/String;)Ljava/lang/String;\r\n */\r\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_readBasis\r\n  (JNIEnv *env, jobject obj, jstring filename)\r\n{\r\n\tjstring info = NULL;\r\n\tlprec *lp = NULL;\r\n\tunsigned char rc;\r\n\tconst char *c_filename = NULL;\r\n\tchar c_info[500];\r\n\r\n\tif (filename != NULL) {\r\n\t\tc_filename = JNU_GetStringNativeChars(env, filename);\r\n\t\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlp = get_lp(env, obj);\r\n\trc = read_basis(lp, (char*)c_filename, c_info);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"read_basis\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\tinfo = env->NewStringUTF(c_info);\r\n\t/* no exception check; we're terminating anyway */\r\n\r\ncleanup:\r\n\tdelete (char *)c_filename;\r\n\treturn info;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    writeXLI\r\n * Signature: (Ljava/lang/String;Ljava/lang/String;Z)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeXLI\r\n  (JNIEnv *env, jobject obj, jstring filename, jstring options, jboolean results)\r\n{\r\n\tlprec *lp = NULL;\r\n\tunsigned char rc;\r\n\tconst char *c_filename = NULL;\r\n\tconst char *c_options = NULL;\r\n\r\n\tif (filename != NULL) {\r\n\t\tc_filename = JNU_GetStringNativeChars(env, filename);\r\n\t\tif (c_filename == 0 || env->ExceptionCheck()) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tif (options != NULL) {\r\n\t\tc_options = JNU_GetStringNativeChars(env, options);\r\n\t\tif (c_options == 0 || env->ExceptionCheck()) {\r\n\t\t\tgoto cleanup;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlp = get_lp(env, obj);\r\n\trc = write_XLI(lp, (char*)c_filename, (char *)c_options, (results == JNI_TRUE) ? TRUE : FALSE);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"write_XLI\");\r\n\t\t/* fall through and release pointer */\r\n\t}\r\n\r\ncleanup:\r\n\tdelete (char *)c_filename;\r\n\tdelete (char *)c_options;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printLp\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printLp\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tprint_lp(get_lp(env, obj));\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printConstraints\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printConstraints\r\n  (JNIEnv *env, jobject obj, jint columns)\r\n{\r\n\tprint_constraints(get_lp(env, obj), columns);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printDuals\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printDuals\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tprint_duals(get_lp(env, obj));\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printScales\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printScales\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tprint_scales(get_lp(env, obj));\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printTableau\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printTableau\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tprint_tableau(get_lp(env, obj));\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printObjective\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printObjective\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tprint_objective(get_lp(env, obj));\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printSolution\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printSolution\r\n  (JNIEnv *env, jobject obj, jint columns)\r\n{\r\n\tprint_solution(get_lp(env, obj), columns);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printStr\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printStr\r\n  (JNIEnv *env, jobject obj, jstring str)\r\n{\r\n\tconst char* c_str = NULL;\r\n\r\n\tif (str != NULL) {\r\n\t\tc_str = JNU_GetStringNativeChars(env, str);\r\n\t\tif (c_str == 0 || env->ExceptionCheck()) {\r\n\t\t\treturn;\t/* exception thrown */\r\n\t\t}\r\n\r\n\t\tlprec* lp = get_lp(env, obj);\r\n\t\tprint_str(lp, (char *)c_str);\r\n\r\n\t\tdelete (char *)c_str;\r\n\t}\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    setOutputfile\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setOutputfile\r\n  (JNIEnv *env, jobject obj, jstring filename)\r\n{\r\n\tconst char* c_filename = NULL;\r\n\r\n\tif (filename != NULL) {\r\n\t\tif ((c_filename = env->GetStringUTFChars(filename, NULL)) == NULL) {\r\n\t\t\treturn;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = set_outputfile(lp, (char *)c_filename);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"set_outputfile\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(filename, c_filename);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    printDebugdump\r\n * Signature: (Ljava/lang/String;)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printDebugdump\r\n  (JNIEnv *env, jobject obj, jstring filename)\r\n{\r\n\tconst char* c_filename = NULL;\r\n\r\n\tif (filename != NULL) {\r\n\t\tif ((c_filename = env->GetStringUTFChars(filename, NULL)) == NULL) {\r\n\t\t\treturn;\t/* exception thrown */\r\n\t\t}\r\n\t}\r\n\r\n\tlprec* lp = get_lp(env, obj);\r\n\tunsigned char rc = print_debugdump(lp, (char *)c_filename);\r\n\tif (rc == FALSE) {\r\n\t\tthrow_exception_with_status(env, lp, \"print_debugdump\");\r\n\t\t/* fall through and cleanup */\r\n\t}\r\n\r\n\tenv->ReleaseStringUTFChars(filename, c_filename);\r\n}\r\n\r\n/*\r\n * Abort callback function\r\n */\r\nint abortfunction(lprec* lp, void* userhandle) {\r\n\t//printf(\"C abortfunction called ..\\n\");\r\n\tint doAbort = TRUE;\r\n\tjclass lpsolve_cls = NULL;\r\n\tjobject lpsolve_obj = NULL;\r\n\tjobject listener_obj = NULL;\r\n\tjobject handle_obj = NULL;\r\n\tjboolean rc;\r\n\r\n\t/* Get a pointer to the JNI environment from the global JavaVM object */\r\n\tJNIEnv *env;\r\n\tg_jvm->AttachCurrentThread((void **)&env, NULL);\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t/* Get the LpSolve object that contains the given lp argument */\r\n\tlpsolve_obj = env->CallStaticObjectMethod(lpsolve_cls, MID_getLp, reinterpret_cast<jlong>(lp));\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif (lpsolve_obj == NULL) {\r\n\t\tthrow_exception(env, \"abortfunction: No LpSolve object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the listener object */\r\n\tlistener_obj = env->GetObjectField(lpsolve_obj, FID_abortListener);\r\n\tif (listener_obj == NULL) {\r\n\t\tthrow_exception(env, \"abortfunction: No AbortListener object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the userhandle object */\r\n\thandle_obj = env->GetObjectField(lpsolve_obj, FID_abortHandle);\r\n\r\n\t/* Call the callback method */\r\n\trc = env->CallBooleanMethod(listener_obj, MID_abortfunc, lpsolve_obj, handle_obj);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tdoAbort = (rc == JNI_TRUE) ? TRUE : FALSE;\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(listener_obj);\r\n\tenv->DeleteLocalRef(lpsolve_obj);\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tenv->DeleteLocalRef(handle_obj);\r\n\treturn doAbort;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    registerAbortfunc\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerAbortfunc\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tjobject listener_obj = env->GetObjectField(obj, FID_abortListener);\r\n\tput_abortfunc(lp, (listener_obj != NULL) ? abortfunction : NULL, NULL);\r\n\tenv->DeleteLocalRef(listener_obj);\r\n}\r\n\r\n/*\r\n * Log callback function\r\n */\r\nvoid logfunction(lprec* lp, void* userhandle, char* buf) {\r\n\t//printf(\"C logfunction called, buf = %s ..\\n\", buf);\r\n\tjclass lpsolve_cls = NULL;\r\n\tjobject lpsolve_obj = NULL;\r\n\tjobject listener_obj = NULL;\r\n\tjobject handle_obj = NULL;\r\n\tjstring j_buf = NULL;\r\n\r\n\t/* Get a pointer to the JNI environment from the global JavaVM object */\r\n\tJNIEnv *env;\r\n\tg_jvm->AttachCurrentThread((void **)&env, NULL);\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t/* Get the LpSolve object that contains the given lp argument */\r\n\tlpsolve_obj = env->CallStaticObjectMethod(lpsolve_cls, MID_getLp, reinterpret_cast<jlong>(lp));\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif (lpsolve_obj == NULL) {\r\n\t\tthrow_exception(env, \"logfunction: No LpSolve object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the listener object */\r\n\tlistener_obj = env->GetObjectField(lpsolve_obj, FID_logListener);\r\n\tif (listener_obj == NULL) {\r\n\t\tthrow_exception(env, \"logfunction: No LogListener object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the userhandle object */\r\n\thandle_obj = env->GetObjectField(lpsolve_obj, FID_logHandle);\r\n\r\n\t/* Construct the Java string */\r\n\tj_buf = env->NewStringUTF(buf);\r\n\tif (j_buf == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t/* Call the callback method */\r\n\tenv->CallVoidMethod(listener_obj, MID_logfunc, lpsolve_obj, handle_obj, j_buf);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(listener_obj);\r\n\tenv->DeleteLocalRef(lpsolve_obj);\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tenv->DeleteLocalRef(handle_obj);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    registerLogfunc\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerLogfunc\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tjobject listener_obj = env->GetObjectField(obj, FID_logListener);\r\n\tput_logfunc(lp, (listener_obj != NULL) ? logfunction : NULL, NULL);\r\n\tenv->DeleteLocalRef(listener_obj);\r\n}\r\n\r\n/*\r\n * Msg callback function\r\n */\r\nvoid msgfunction(lprec* lp, void* userhandle, int code) {\r\n\t//printf(\"C msgfunction called, code = %d ..\\n\", code);\r\n\tjclass lpsolve_cls = NULL;\r\n\tjobject lpsolve_obj = NULL;\r\n\tjobject listener_obj = NULL;\r\n\tjobject handle_obj = NULL;\r\n\r\n\t/* Get a pointer to the JNI environment from the global JavaVM object */\r\n\tJNIEnv *env;\r\n\tg_jvm->AttachCurrentThread((void **)&env, NULL);\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t/* Get the LpSolve object that contains the given lp argument */\r\n\tlpsolve_obj = env->CallStaticObjectMethod(lpsolve_cls, MID_getLp, reinterpret_cast<jlong>(lp));\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif (lpsolve_obj == NULL) {\r\n\t\tthrow_exception(env, \"msgfunction: No LpSolve object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the listener object */\r\n\tlistener_obj = env->GetObjectField(lpsolve_obj, FID_msgListener);\r\n\tif (listener_obj == NULL) {\r\n\t\tthrow_exception(env, \"msgfunction: No MsgListener object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the userhandle object */\r\n\thandle_obj = env->GetObjectField(lpsolve_obj, FID_msgHandle);\r\n\r\n\t/* Call the callback method */\r\n\tenv->CallVoidMethod(listener_obj, MID_msgfunc, lpsolve_obj, handle_obj, code);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(listener_obj);\r\n\tenv->DeleteLocalRef(lpsolve_obj);\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tenv->DeleteLocalRef(handle_obj);\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    registerMsgfunc\r\n * Signature: (I)V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerMsgfunc\r\n  (JNIEnv *env, jobject obj, jint mask)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tjobject listener_obj = env->GetObjectField(obj, FID_msgListener);\r\n\tput_msgfunc(lp, (listener_obj != NULL) ? msgfunction : NULL, NULL, mask);\r\n\tenv->DeleteLocalRef(listener_obj);\r\n}\r\n\r\n/*\r\n * bb_branch callback function\r\n */\r\nint bb_branchfunction(lprec* lp, void* userhandle, int message) {\r\n\t//printf(\"C msgfunction called, code = %d ..\\n\", code);\r\n\tjclass lpsolve_cls = NULL;\r\n\tjobject lpsolve_obj = NULL;\r\n\tjobject listener_obj = NULL;\r\n\tjobject handle_obj = NULL;\r\n\tjint rc;\r\n\r\n\t/* Get a pointer to the JNI environment from the global JavaVM object */\r\n\tJNIEnv *env;\r\n\tg_jvm->AttachCurrentThread((void **)&env, NULL);\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t/* Get the LpSolve object that contains the given lp argument */\r\n\tlpsolve_obj = env->CallStaticObjectMethod(lpsolve_cls, MID_getLp, reinterpret_cast<jlong>(lp));\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif (lpsolve_obj == NULL) {\r\n\t\tthrow_exception(env, \"bb_branchfunction: No LpSolve object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the listener object */\r\n\tlistener_obj = env->GetObjectField(lpsolve_obj, FID_bbBranchListener);\r\n\tif (listener_obj == NULL) {\r\n\t\tthrow_exception(env, \"bb_branchfunction: No BbListener object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the userhandle object */\r\n\thandle_obj = env->GetObjectField(lpsolve_obj, FID_bbBranchHandle);\r\n\r\n\t/* Call the callback method */\r\n\trc = env->CallIntMethod(listener_obj, MID_bbfunc, lpsolve_obj, handle_obj, message);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(listener_obj);\r\n\tenv->DeleteLocalRef(lpsolve_obj);\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tenv->DeleteLocalRef(handle_obj);\r\n\r\n\treturn rc;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    registerBbBranchfunc\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerBbBranchfunc\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tjobject listener_obj = env->GetObjectField(obj, FID_bbBranchListener);\r\n\tput_bb_branchfunc(lp, (listener_obj != NULL) ? bb_branchfunction : NULL, NULL);\r\n\tenv->DeleteLocalRef(listener_obj);\r\n}\r\n\r\n/*\r\n * bb_node callback function\r\n */\r\nint bb_nodefunction(lprec* lp, void* userhandle, int message) {\r\n\t//printf(\"C msgfunction called, code = %d ..\\n\", code);\r\n\tjclass lpsolve_cls = NULL;\r\n\tjobject lpsolve_obj = NULL;\r\n\tjobject listener_obj = NULL;\r\n\tjobject handle_obj = NULL;\r\n\tjint rc;\r\n\r\n\t/* Get a pointer to the JNI environment from the global JavaVM object */\r\n\tJNIEnv *env;\r\n\tg_jvm->AttachCurrentThread((void **)&env, NULL);\r\n\r\n\tlpsolve_cls = env->FindClass(\"lpsolve/LpSolve\");\r\n\tif (lpsolve_cls == NULL) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\n\t/* Get the LpSolve object that contains the given lp argument */\r\n\tlpsolve_obj = env->CallStaticObjectMethod(lpsolve_cls, MID_getLp, reinterpret_cast<jlong>(lp));\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\tif (lpsolve_obj == NULL) {\r\n\t\tthrow_exception(env, \"bb_nodefunction: No LpSolve object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the listener object */\r\n\tlistener_obj = env->GetObjectField(lpsolve_obj, FID_bbNodeListener);\r\n\tif (listener_obj == NULL) {\r\n\t\tthrow_exception(env, \"bb_nodefunction: No BbListener object found\");\r\n\t\tgoto cleanup;\r\n\t}\r\n\r\n\t/* Get the userhandle object */\r\n\thandle_obj = env->GetObjectField(lpsolve_obj, FID_bbNodeHandle);\r\n\r\n\t/* Call the callback method */\r\n\trc = env->CallIntMethod(listener_obj, MID_bbfunc, lpsolve_obj, handle_obj, message);\r\n\tif (env->ExceptionCheck()) {\r\n\t\tgoto cleanup;\t/* exception thrown */\r\n\t}\r\n\r\ncleanup:\r\n\tenv->DeleteLocalRef(listener_obj);\r\n\tenv->DeleteLocalRef(lpsolve_obj);\r\n\tenv->DeleteLocalRef(lpsolve_cls);\r\n\tenv->DeleteLocalRef(handle_obj);\r\n\r\n\treturn rc;\r\n}\r\n\r\n/*\r\n * Class:     lpsolve_LpSolve\r\n * Method:    registerBbNodefunc\r\n * Signature: ()V\r\n */\r\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerBbNodefunc\r\n  (JNIEnv *env, jobject obj)\r\n{\r\n\tlprec* lp = get_lp(env, obj);\r\n\tjobject listener_obj = env->GetObjectField(obj, FID_bbNodeListener);\r\n\tput_bb_nodefunc(lp, (listener_obj != NULL) ? bb_nodefunction : NULL, NULL);\r\n\tenv->DeleteLocalRef(listener_obj);\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/c/lpsolve_LpSolve.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class lpsolve_LpSolve */\n\n#ifndef _Included_lpsolve_LpSolve\n#define _Included_lpsolve_LpSolve\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n#undef lpsolve_LpSolve_FALSE\n#define lpsolve_LpSolve_FALSE 0L\n#undef lpsolve_LpSolve_TRUE\n#define lpsolve_LpSolve_TRUE 1L\n#undef lpsolve_LpSolve_AUTOMATIC\n#define lpsolve_LpSolve_AUTOMATIC 2L\n#undef lpsolve_LpSolve_DYNAMIC\n#define lpsolve_LpSolve_DYNAMIC 4L\n#undef lpsolve_LpSolve_FR\n#define lpsolve_LpSolve_FR 0L\n#undef lpsolve_LpSolve_LE\n#define lpsolve_LpSolve_LE 1L\n#undef lpsolve_LpSolve_GE\n#define lpsolve_LpSolve_GE 2L\n#undef lpsolve_LpSolve_EQ\n#define lpsolve_LpSolve_EQ 3L\n#undef lpsolve_LpSolve_OF\n#define lpsolve_LpSolve_OF 4L\n#undef lpsolve_LpSolve_SIMPLEX_PRIMAL_PRIMAL\n#define lpsolve_LpSolve_SIMPLEX_PRIMAL_PRIMAL 5L\n#undef lpsolve_LpSolve_SIMPLEX_DUAL_PRIMAL\n#define lpsolve_LpSolve_SIMPLEX_DUAL_PRIMAL 6L\n#undef lpsolve_LpSolve_SIMPLEX_PRIMAL_DUAL\n#define lpsolve_LpSolve_SIMPLEX_PRIMAL_DUAL 9L\n#undef lpsolve_LpSolve_SIMPLEX_DUAL_DUAL\n#define lpsolve_LpSolve_SIMPLEX_DUAL_DUAL 10L\n#undef lpsolve_LpSolve_SIMPLEX_DEFAULT\n#define lpsolve_LpSolve_SIMPLEX_DEFAULT 6L\n#undef lpsolve_LpSolve_PRESOLVE_NONE\n#define lpsolve_LpSolve_PRESOLVE_NONE 0L\n#undef lpsolve_LpSolve_PRESOLVE_ROWS\n#define lpsolve_LpSolve_PRESOLVE_ROWS 1L\n#undef lpsolve_LpSolve_PRESOLVE_COLS\n#define lpsolve_LpSolve_PRESOLVE_COLS 2L\n#undef lpsolve_LpSolve_PRESOLVE_LINDEP\n#define lpsolve_LpSolve_PRESOLVE_LINDEP 4L\n#undef lpsolve_LpSolve_PRESOLVE_SOS\n#define lpsolve_LpSolve_PRESOLVE_SOS 32L\n#undef lpsolve_LpSolve_PRESOLVE_REDUCEMIP\n#define lpsolve_LpSolve_PRESOLVE_REDUCEMIP 64L\n#undef lpsolve_LpSolve_PRESOLVE_KNAPSACK\n#define lpsolve_LpSolve_PRESOLVE_KNAPSACK 128L\n#undef lpsolve_LpSolve_PRESOLVE_ELIMEQ2\n#define lpsolve_LpSolve_PRESOLVE_ELIMEQ2 256L\n#undef lpsolve_LpSolve_PRESOLVE_IMPLIEDFREE\n#define lpsolve_LpSolve_PRESOLVE_IMPLIEDFREE 512L\n#undef lpsolve_LpSolve_PRESOLVE_REDUCEGCD\n#define lpsolve_LpSolve_PRESOLVE_REDUCEGCD 1024L\n#undef lpsolve_LpSolve_PRESOLVE_PROBEFIX\n#define lpsolve_LpSolve_PRESOLVE_PROBEFIX 2048L\n#undef lpsolve_LpSolve_PRESOLVE_PROBEREDUCE\n#define lpsolve_LpSolve_PRESOLVE_PROBEREDUCE 4096L\n#undef lpsolve_LpSolve_PRESOLVE_ROWDOMINATE\n#define lpsolve_LpSolve_PRESOLVE_ROWDOMINATE 8192L\n#undef lpsolve_LpSolve_PRESOLVE_COLDOMINATE\n#define lpsolve_LpSolve_PRESOLVE_COLDOMINATE 16384L\n#undef lpsolve_LpSolve_PRESOLVE_MERGEROWS\n#define lpsolve_LpSolve_PRESOLVE_MERGEROWS 32768L\n#undef lpsolve_LpSolve_PRESOLVE_IMPLIEDSLK\n#define lpsolve_LpSolve_PRESOLVE_IMPLIEDSLK 65536L\n#undef lpsolve_LpSolve_PRESOLVE_COLFIXDUAL\n#define lpsolve_LpSolve_PRESOLVE_COLFIXDUAL 131072L\n#undef lpsolve_LpSolve_PRESOLVE_BOUNDS\n#define lpsolve_LpSolve_PRESOLVE_BOUNDS 262144L\n#undef lpsolve_LpSolve_PRESOLVE_DUALS\n#define lpsolve_LpSolve_PRESOLVE_DUALS 524288L\n#undef lpsolve_LpSolve_PRESOLVE_SENSDUALS\n#define lpsolve_LpSolve_PRESOLVE_SENSDUALS 1048576L\n#undef lpsolve_LpSolve_CRASH_NOTHING\n#define lpsolve_LpSolve_CRASH_NOTHING 0L\n#undef lpsolve_LpSolve_CRASH_MOSTFEASIBLE\n#define lpsolve_LpSolve_CRASH_MOSTFEASIBLE 2L\n#undef lpsolve_LpSolve_ANTIDEGEN_NONE\n#define lpsolve_LpSolve_ANTIDEGEN_NONE 0L\n#undef lpsolve_LpSolve_ANTIDEGEN_FIXEDVARS\n#define lpsolve_LpSolve_ANTIDEGEN_FIXEDVARS 1L\n#undef lpsolve_LpSolve_ANTIDEGEN_COLUMNCHECK\n#define lpsolve_LpSolve_ANTIDEGEN_COLUMNCHECK 2L\n#undef lpsolve_LpSolve_ANTIDEGEN_STALLING\n#define lpsolve_LpSolve_ANTIDEGEN_STALLING 4L\n#undef lpsolve_LpSolve_ANTIDEGEN_NUMFAILURE\n#define lpsolve_LpSolve_ANTIDEGEN_NUMFAILURE 8L\n#undef lpsolve_LpSolve_ANTIDEGEN_LOSTFEAS\n#define lpsolve_LpSolve_ANTIDEGEN_LOSTFEAS 16L\n#undef lpsolve_LpSolve_ANTIDEGEN_INFEASIBLE\n#define lpsolve_LpSolve_ANTIDEGEN_INFEASIBLE 32L\n#undef lpsolve_LpSolve_ANTIDEGEN_DYNAMIC\n#define lpsolve_LpSolve_ANTIDEGEN_DYNAMIC 64L\n#undef lpsolve_LpSolve_ANTIDEGEN_DURINGBB\n#define lpsolve_LpSolve_ANTIDEGEN_DURINGBB 128L\n#undef lpsolve_LpSolve_ANTIDEGEN_RHSPERTURB\n#define lpsolve_LpSolve_ANTIDEGEN_RHSPERTURB 256L\n#undef lpsolve_LpSolve_ANTIDEGEN_BOUNDFLIP\n#define lpsolve_LpSolve_ANTIDEGEN_BOUNDFLIP 512L\n#undef lpsolve_LpSolve_NEUTRAL\n#define lpsolve_LpSolve_NEUTRAL 0L\n#undef lpsolve_LpSolve_CRITICAL\n#define lpsolve_LpSolve_CRITICAL 1L\n#undef lpsolve_LpSolve_SEVERE\n#define lpsolve_LpSolve_SEVERE 2L\n#undef lpsolve_LpSolve_IMPORTANT\n#define lpsolve_LpSolve_IMPORTANT 3L\n#undef lpsolve_LpSolve_NORMAL\n#define lpsolve_LpSolve_NORMAL 4L\n#undef lpsolve_LpSolve_DETAILED\n#define lpsolve_LpSolve_DETAILED 5L\n#undef lpsolve_LpSolve_FULL\n#define lpsolve_LpSolve_FULL 6L\n#undef lpsolve_LpSolve_MSG_NONE\n#define lpsolve_LpSolve_MSG_NONE 0L\n#undef lpsolve_LpSolve_MSG_PRESOLVE\n#define lpsolve_LpSolve_MSG_PRESOLVE 1L\n#undef lpsolve_LpSolve_MSG_ITERATION\n#define lpsolve_LpSolve_MSG_ITERATION 2L\n#undef lpsolve_LpSolve_MSG_INVERT\n#define lpsolve_LpSolve_MSG_INVERT 4L\n#undef lpsolve_LpSolve_MSG_LPFEASIBLE\n#define lpsolve_LpSolve_MSG_LPFEASIBLE 8L\n#undef lpsolve_LpSolve_MSG_LPOPTIMAL\n#define lpsolve_LpSolve_MSG_LPOPTIMAL 16L\n#undef lpsolve_LpSolve_MSG_LPEQUAL\n#define lpsolve_LpSolve_MSG_LPEQUAL 32L\n#undef lpsolve_LpSolve_MSG_LPBETTER\n#define lpsolve_LpSolve_MSG_LPBETTER 64L\n#undef lpsolve_LpSolve_MSG_MILPFEASIBLE\n#define lpsolve_LpSolve_MSG_MILPFEASIBLE 128L\n#undef lpsolve_LpSolve_MSG_MILPEQUAL\n#define lpsolve_LpSolve_MSG_MILPEQUAL 256L\n#undef lpsolve_LpSolve_MSG_MILPBETTER\n#define lpsolve_LpSolve_MSG_MILPBETTER 512L\n#undef lpsolve_LpSolve_MSG_MILPSTRATEGY\n#define lpsolve_LpSolve_MSG_MILPSTRATEGY 1024L\n#undef lpsolve_LpSolve_MSG_MILPOPTIMAL\n#define lpsolve_LpSolve_MSG_MILPOPTIMAL 2048L\n#undef lpsolve_LpSolve_MSG_PERFORMANCE\n#define lpsolve_LpSolve_MSG_PERFORMANCE 4096L\n#undef lpsolve_LpSolve_MSG_INITPSEUDOCOST\n#define lpsolve_LpSolve_MSG_INITPSEUDOCOST 8192L\n#undef lpsolve_LpSolve_IMPROVE_NONE\n#define lpsolve_LpSolve_IMPROVE_NONE 0L\n#undef lpsolve_LpSolve_IMPROVE_SOLUTION\n#define lpsolve_LpSolve_IMPROVE_SOLUTION 1L\n#undef lpsolve_LpSolve_IMPROVE_DUALFEAS\n#define lpsolve_LpSolve_IMPROVE_DUALFEAS 2L\n#undef lpsolve_LpSolve_IMPROVE_THETAGAP\n#define lpsolve_LpSolve_IMPROVE_THETAGAP 4L\n#undef lpsolve_LpSolve_IMPROVE_BBSIMPLEX\n#define lpsolve_LpSolve_IMPROVE_BBSIMPLEX 8L\n#undef lpsolve_LpSolve_SCALE_NONE\n#define lpsolve_LpSolve_SCALE_NONE 0L\n#undef lpsolve_LpSolve_SCALE_EXTREME\n#define lpsolve_LpSolve_SCALE_EXTREME 1L\n#undef lpsolve_LpSolve_SCALE_RANGE\n#define lpsolve_LpSolve_SCALE_RANGE 2L\n#undef lpsolve_LpSolve_SCALE_MEAN\n#define lpsolve_LpSolve_SCALE_MEAN 3L\n#undef lpsolve_LpSolve_SCALE_GEOMETRIC\n#define lpsolve_LpSolve_SCALE_GEOMETRIC 4L\n#undef lpsolve_LpSolve_SCALE_CURTISREID\n#define lpsolve_LpSolve_SCALE_CURTISREID 7L\n#undef lpsolve_LpSolve_SCALE_LINEAR\n#define lpsolve_LpSolve_SCALE_LINEAR 0L\n#undef lpsolve_LpSolve_SCALE_QUADRATIC\n#define lpsolve_LpSolve_SCALE_QUADRATIC 8L\n#undef lpsolve_LpSolve_SCALE_LOGARITHMIC\n#define lpsolve_LpSolve_SCALE_LOGARITHMIC 16L\n#undef lpsolve_LpSolve_SCALE_USERWEIGHT\n#define lpsolve_LpSolve_SCALE_USERWEIGHT 31L\n#undef lpsolve_LpSolve_SCALE_POWER2\n#define lpsolve_LpSolve_SCALE_POWER2 32L\n#undef lpsolve_LpSolve_SCALE_EQUILIBRATE\n#define lpsolve_LpSolve_SCALE_EQUILIBRATE 64L\n#undef lpsolve_LpSolve_SCALE_INTEGERS\n#define lpsolve_LpSolve_SCALE_INTEGERS 128L\n#undef lpsolve_LpSolve_SCALE_DYNUPDATE\n#define lpsolve_LpSolve_SCALE_DYNUPDATE 256L\n#undef lpsolve_LpSolve_SCALE_ROWSONLY\n#define lpsolve_LpSolve_SCALE_ROWSONLY 512L\n#undef lpsolve_LpSolve_SCALE_COLSONLY\n#define lpsolve_LpSolve_SCALE_COLSONLY 1024L\n#undef lpsolve_LpSolve_PRICER_FIRSTINDEX\n#define lpsolve_LpSolve_PRICER_FIRSTINDEX 0L\n#undef lpsolve_LpSolve_PRICER_DANTZIG\n#define lpsolve_LpSolve_PRICER_DANTZIG 1L\n#undef lpsolve_LpSolve_PRICER_DEVEX\n#define lpsolve_LpSolve_PRICER_DEVEX 2L\n#undef lpsolve_LpSolve_PRICER_STEEPESTEDGE\n#define lpsolve_LpSolve_PRICER_STEEPESTEDGE 3L\n#undef lpsolve_LpSolve_PRICE_METHODDEFAULT\n#define lpsolve_LpSolve_PRICE_METHODDEFAULT 0L\n#undef lpsolve_LpSolve_PRICE_PRIMALFALLBACK\n#define lpsolve_LpSolve_PRICE_PRIMALFALLBACK 4L\n#undef lpsolve_LpSolve_PRICE_MULTIPLE\n#define lpsolve_LpSolve_PRICE_MULTIPLE 8L\n#undef lpsolve_LpSolve_PRICE_PARTIAL\n#define lpsolve_LpSolve_PRICE_PARTIAL 16L\n#undef lpsolve_LpSolve_PRICE_ADAPTIVE\n#define lpsolve_LpSolve_PRICE_ADAPTIVE 32L\n#undef lpsolve_LpSolve_PRICE_HYBRID\n#define lpsolve_LpSolve_PRICE_HYBRID 64L\n#undef lpsolve_LpSolve_PRICE_RANDOMIZE\n#define lpsolve_LpSolve_PRICE_RANDOMIZE 128L\n#undef lpsolve_LpSolve_PRICE_AUTOPARTIAL\n#define lpsolve_LpSolve_PRICE_AUTOPARTIAL 512L\n#undef lpsolve_LpSolve_PRICE_LOOPLEFT\n#define lpsolve_LpSolve_PRICE_LOOPLEFT 1024L\n#undef lpsolve_LpSolve_PRICE_LOOPALTERNATE\n#define lpsolve_LpSolve_PRICE_LOOPALTERNATE 2048L\n#undef lpsolve_LpSolve_PRICE_HARRISTWOPASS\n#define lpsolve_LpSolve_PRICE_HARRISTWOPASS 4096L\n#undef lpsolve_LpSolve_PRICE_TRUENORMINIT\n#define lpsolve_LpSolve_PRICE_TRUENORMINIT 16384L\n#undef lpsolve_LpSolve_NODE_FIRSTSELECT\n#define lpsolve_LpSolve_NODE_FIRSTSELECT 0L\n#undef lpsolve_LpSolve_NODE_GAPSELECT\n#define lpsolve_LpSolve_NODE_GAPSELECT 1L\n#undef lpsolve_LpSolve_NODE_RANGESELECT\n#define lpsolve_LpSolve_NODE_RANGESELECT 2L\n#undef lpsolve_LpSolve_NODE_FRACTIONSELECT\n#define lpsolve_LpSolve_NODE_FRACTIONSELECT 3L\n#undef lpsolve_LpSolve_NODE_PSEUDOCOSTSELECT\n#define lpsolve_LpSolve_NODE_PSEUDOCOSTSELECT 4L\n#undef lpsolve_LpSolve_NODE_PSEUDONONINTSELECT\n#define lpsolve_LpSolve_NODE_PSEUDONONINTSELECT 5L\n#undef lpsolve_LpSolve_NODE_PSEUDORATIOSELECT\n#define lpsolve_LpSolve_NODE_PSEUDORATIOSELECT 6L\n#undef lpsolve_LpSolve_NODE_USERSELECT\n#define lpsolve_LpSolve_NODE_USERSELECT 7L\n#undef lpsolve_LpSolve_NODE_WEIGHTREVERSEMODE\n#define lpsolve_LpSolve_NODE_WEIGHTREVERSEMODE 8L\n#undef lpsolve_LpSolve_NODE_BRANCHREVERSEMODE\n#define lpsolve_LpSolve_NODE_BRANCHREVERSEMODE 16L\n#undef lpsolve_LpSolve_NODE_GREEDYMODE\n#define lpsolve_LpSolve_NODE_GREEDYMODE 32L\n#undef lpsolve_LpSolve_NODE_PSEUDOCOSTMODE\n#define lpsolve_LpSolve_NODE_PSEUDOCOSTMODE 64L\n#undef lpsolve_LpSolve_NODE_DEPTHFIRSTMODE\n#define lpsolve_LpSolve_NODE_DEPTHFIRSTMODE 128L\n#undef lpsolve_LpSolve_NODE_RANDOMIZEMODE\n#define lpsolve_LpSolve_NODE_RANDOMIZEMODE 256L\n#undef lpsolve_LpSolve_NODE_DYNAMICMODE\n#define lpsolve_LpSolve_NODE_DYNAMICMODE 1024L\n#undef lpsolve_LpSolve_NODE_RESTARTMODE\n#define lpsolve_LpSolve_NODE_RESTARTMODE 2048L\n#undef lpsolve_LpSolve_NODE_BREADTHFIRSTMODE\n#define lpsolve_LpSolve_NODE_BREADTHFIRSTMODE 4096L\n#undef lpsolve_LpSolve_NODE_AUTOORDER\n#define lpsolve_LpSolve_NODE_AUTOORDER 8192L\n#undef lpsolve_LpSolve_NODE_RCOSTFIXING\n#define lpsolve_LpSolve_NODE_RCOSTFIXING 16384L\n#undef lpsolve_LpSolve_NODE_STRONGINIT\n#define lpsolve_LpSolve_NODE_STRONGINIT 32768L\n#undef lpsolve_LpSolve_BRANCH_CEILING\n#define lpsolve_LpSolve_BRANCH_CEILING 0L\n#undef lpsolve_LpSolve_BRANCH_FLOOR\n#define lpsolve_LpSolve_BRANCH_FLOOR 1L\n#undef lpsolve_LpSolve_BRANCH_AUTOMATIC\n#define lpsolve_LpSolve_BRANCH_AUTOMATIC 2L\n#undef lpsolve_LpSolve_BRANCH_DEFAULT\n#define lpsolve_LpSolve_BRANCH_DEFAULT 3L\n#undef lpsolve_LpSolve_UNKNOWNERROR\n#define lpsolve_LpSolve_UNKNOWNERROR -5L\n#undef lpsolve_LpSolve_DATAIGNORED\n#define lpsolve_LpSolve_DATAIGNORED -4L\n#undef lpsolve_LpSolve_NOBFP\n#define lpsolve_LpSolve_NOBFP -3L\n#undef lpsolve_LpSolve_NOMEMORY\n#define lpsolve_LpSolve_NOMEMORY -2L\n#undef lpsolve_LpSolve_NOTRUN\n#define lpsolve_LpSolve_NOTRUN -1L\n#undef lpsolve_LpSolve_OPTIMAL\n#define lpsolve_LpSolve_OPTIMAL 0L\n#undef lpsolve_LpSolve_SUBOPTIMAL\n#define lpsolve_LpSolve_SUBOPTIMAL 1L\n#undef lpsolve_LpSolve_INFEASIBLE\n#define lpsolve_LpSolve_INFEASIBLE 2L\n#undef lpsolve_LpSolve_UNBOUNDED\n#define lpsolve_LpSolve_UNBOUNDED 3L\n#undef lpsolve_LpSolve_DEGENERATE\n#define lpsolve_LpSolve_DEGENERATE 4L\n#undef lpsolve_LpSolve_NUMFAILURE\n#define lpsolve_LpSolve_NUMFAILURE 5L\n#undef lpsolve_LpSolve_USERABORT\n#define lpsolve_LpSolve_USERABORT 6L\n#undef lpsolve_LpSolve_TIMEOUT\n#define lpsolve_LpSolve_TIMEOUT 7L\n#undef lpsolve_LpSolve_RUNNING\n#define lpsolve_LpSolve_RUNNING 8L\n#undef lpsolve_LpSolve_PRESOLVED\n#define lpsolve_LpSolve_PRESOLVED 9L\n#undef lpsolve_LpSolve_PROCFAIL\n#define lpsolve_LpSolve_PROCFAIL 10L\n#undef lpsolve_LpSolve_PROCBREAK\n#define lpsolve_LpSolve_PROCBREAK 11L\n#undef lpsolve_LpSolve_FEASFOUND\n#define lpsolve_LpSolve_FEASFOUND 12L\n#undef lpsolve_LpSolve_NOFEASFOUND\n#define lpsolve_LpSolve_NOFEASFOUND 13L\n/* Inaccessible static: lpMap */\n/*\n * Class:     lpsolve_LpSolve\n * Method:    init\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_init\n  (JNIEnv *, jclass);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    makeLp\n * Signature: (II)Llpsolve/LpSolve;\n */\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_makeLp\n  (JNIEnv *, jclass, jint, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    readLp\n * Signature: (Ljava/lang/String;ILjava/lang/String;)Llpsolve/LpSolve;\n */\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_readLp\n  (JNIEnv *, jclass, jstring, jint, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    readMps\n * Signature: (Ljava/lang/String;I)Llpsolve/LpSolve;\n */\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_readMps\n  (JNIEnv *, jclass, jstring, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    readFreeMps\n * Signature: (Ljava/lang/String;I)Llpsolve/LpSolve;\n */\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_readFreeMps\n  (JNIEnv *, jclass, jstring, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    readXLI\n * Signature: (Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;Ljava/lang/String;I)Llpsolve/LpSolve;\n */\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_readXLI\n  (JNIEnv *, jclass, jstring, jstring, jstring, jstring, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    lpSolveVersion\n * Signature: ()Llpsolve/VersionInfo;\n */\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_lpSolveVersion\n  (JNIEnv *, jclass);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    copyLp\n * Signature: ()Llpsolve/LpSolve;\n */\nJNIEXPORT jobject JNICALL Java_lpsolve_LpSolve_copyLp\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    resizeLp\n * Signature:\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_resizeLp\n  (JNIEnv *, jobject, jint, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setLpName\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setLpName\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getLpName\n * Signature: ()Ljava/lang/String;\n */\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getLpName\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    addConstraint\n * Signature: ([DID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addConstraint\n  (JNIEnv *, jobject, jdoubleArray, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    strAddConstraint\n * Signature: (Ljava/lang/String;ID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strAddConstraint\n  (JNIEnv *, jobject, jstring, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    addConstraintex\n * Signature: (I[D[IID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addConstraintex\n  (JNIEnv *, jobject, jint, jdoubleArray, jintArray, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    delConstraint\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_delConstraint\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isConstrType\n * Signature: (II)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isConstrType\n  (JNIEnv *, jobject, jint, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    addLagCon\n * Signature: ([DID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addLagCon\n  (JNIEnv *, jobject, jdoubleArray, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    strAddLagCon\n * Signature: (Ljava/lang/String;ID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strAddLagCon\n  (JNIEnv *, jobject, jstring, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    addColumn\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addColumn\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    addColumnex\n * Signature: (I[D[I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addColumnex\n  (JNIEnv *, jobject, jint, jdoubleArray, jintArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    strAddColumn\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strAddColumn\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    delColumn\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_delColumn\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setRow\n * Signature: (I[D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRow\n  (JNIEnv *, jobject, jint, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setRowex\n * Signature: (II[D[I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRowex\n  (JNIEnv *, jobject, jint, jint, jdoubleArray, jintArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setColumn\n * Signature: (I[D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setColumn\n  (JNIEnv *, jobject, jint, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setColumnex\n * Signature: (II[D[I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setColumnex\n  (JNIEnv *, jobject, jint, jint, jdoubleArray, jintArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    columnInLp\n * Signature: ([D)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_columnInLp\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setRowName\n * Signature: (ILjava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRowName\n  (JNIEnv *, jobject, jint, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getRowName\n * Signature: (I)Ljava/lang/String;\n */\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getRowName\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getOrigrowName\n * Signature: (I)Ljava/lang/String;\n */\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getOrigrowName\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setColName\n * Signature: (ILjava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setColName\n  (JNIEnv *, jobject, jint, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getColName\n * Signature: (I)Ljava/lang/String;\n */\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getColName\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getOrigcolName\n * Signature: (I)Ljava/lang/String;\n */\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getOrigcolName\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setRhVec\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRhVec\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    strSetRhVec\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strSetRhVec\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setRh\n * Signature: (ID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRh\n  (JNIEnv *, jobject, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getRh\n * Signature: (I)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getRh\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setConstrType\n * Signature: (II)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setConstrType\n  (JNIEnv *, jobject, jint, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getConstrType\n * Signature: (I)S\n */\nJNIEXPORT jshort JNICALL Java_lpsolve_LpSolve_getConstrType\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    addSOS\n * Signature: (Ljava/lang/String;III[I[D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_addSOS\n  (JNIEnv *, jobject, jstring, jint, jint, jint, jintArray, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isSOSVar\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isSOSVar\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setObjFn\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setObjFn\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    strSetObjFn\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_strSetObjFn\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setObjFnex\n * Signature: (I[D[I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setObjFnex\n  (JNIEnv *, jobject, jint, jdoubleArray, jintArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setObj\n * Signature: (ID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setObj\n  (JNIEnv *, jobject, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setMat\n * Signature: (IID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMat\n  (JNIEnv *, jobject, jint, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getMat\n * Signature: (II)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getMat\n  (JNIEnv *, jobject, jint, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getRow\n * Signature: (I[D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getRow\n  (JNIEnv *, jobject, jint, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getRowex\n * Signature: (I[D[I)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getRowex\n  (JNIEnv *, jobject, jint, jdoubleArray, jintArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrRow\n * Signature: (I)[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrRow\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getColumn\n * Signature: (I[D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getColumn\n  (JNIEnv *, jobject, jint, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getColumnex\n * Signature: (I[D[I)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getColumnex\n  (JNIEnv *, jobject, jint, jdoubleArray, jintArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrColumn\n * Signature: (I)[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrColumn\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setMaxim\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMaxim\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setMinim\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMinim\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setSense\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setSense\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isMaxim\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isMaxim\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setLowbo\n * Signature: (ID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setLowbo\n  (JNIEnv *, jobject, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getLowbo\n * Signature: (I)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getLowbo\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setUpbo\n * Signature: (ID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setUpbo\n  (JNIEnv *, jobject, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getUpbo\n * Signature: (I)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getUpbo\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setUnbounded\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setUnbounded\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isUnbounded\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isUnbounded\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isNegative\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isNegative\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBounds\n * Signature: (IDD)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBounds\n  (JNIEnv *, jobject, jint, jdouble, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBoundsTighter\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBoundsTighter\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getBoundsTighter\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_getBoundsTighter\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setRhRange\n * Signature: (ID)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setRhRange\n  (JNIEnv *, jobject, jint, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getRhRange\n * Signature: (I)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getRhRange\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setInt\n * Signature: (IZ)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setInt\n  (JNIEnv *, jobject, jint, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isInt\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isInt\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBinary\n * Signature: (IZ)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBinary\n  (JNIEnv *, jobject, jint, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isBinary\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isBinary\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setSemicont\n * Signature: (IZ)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setSemicont\n  (JNIEnv *, jobject, jint, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isSemicont\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isSemicont\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setInfinite\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setInfinite\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getInfinite\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getInfinite\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isInfinite\n * Signature: (D)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isInfinite\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setEpsint\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsint\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getEpsint\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsint\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setEpsb\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsb\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getEpsb\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsb\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setEpsd\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsd\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getEpsd\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsd\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setEpsel\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsel\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getEpsel\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsel\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setEpspivot\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpspivot\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getEpspivot\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpspivot\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setEpsperturb\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpsperturb\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getEpsperturb\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getEpsperturb\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setEpslevel\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setEpslevel\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getStatus\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getStatus\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setMipGap\n * Signature: (ZD)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMipGap\n  (JNIEnv *, jobject, jboolean, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getMipGap\n * Signature: (Z)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getMipGap\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setVerbose\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setVerbose\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getVerbose\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getVerbose\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setTimeout\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setTimeout\n  (JNIEnv *, jobject, jlong);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getTimeout\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_lpsolve_LpSolve_getTimeout\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    timeElapsed\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_timeElapsed\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setPrintSol\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setPrintSol\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPrintSol\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getPrintSol\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setDebug\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setDebug\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isDebug\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isDebug\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setTrace\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setTrace\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isTrace\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isTrace\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setLagTrace\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setLagTrace\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isLagTrace\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isLagTrace\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setAddRowmode\n * Signature: (Z)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_setAddRowmode\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isAddRowmode\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isAddRowmode\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setAntiDegen\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setAntiDegen\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isAntiDegen\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isAntiDegen\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getAntiDegen\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getAntiDegen\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setPresolve\n * Signature: (II)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setPresolve\n  (JNIEnv *, jobject, jint, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isPresolve\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isPresolve\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPresolve\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getPresolve\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPresolveloops\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getPresolveloops\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setMaxpivot\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setMaxpivot\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getMaxpivot\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getMaxpivot\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBbRule\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBbRule\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getBbRule\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getBbRule\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBbDepthlimit\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBbDepthlimit\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getBbDepthlimit\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getBbDepthlimit\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getSolutioncount\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getSolutioncount\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setSolutionlimit\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setSolutionlimit\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getSolutionlimit\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getSolutionlimit\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setObjBound\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setObjBound\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getObjBound\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getObjBound\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBbFloorfirst\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBbFloorfirst\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getBbFloorfirst\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getBbFloorfirst\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setVarBranch\n * Signature: (II)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setVarBranch\n  (JNIEnv *, jobject, jint, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getVarBranch\n * Signature: (I)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getVarBranch\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setVarWeights\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setVarWeights\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getVarPriority\n * Signature: (I)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getVarPriority\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBreakAtFirst\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBreakAtFirst\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isBreakAtFirst\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isBreakAtFirst\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBreakAtValue\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBreakAtValue\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getBreakAtValue\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getBreakAtValue\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setScaling\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setScaling\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getScaling\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getScaling\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isScalemode\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isScalemode\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isScaletype\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isScaletype\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isIntegerscaling\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isIntegerscaling\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setScalelimit\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setScalelimit\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getScalelimit\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getScalelimit\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setImprove\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setImprove\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getImprove\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getImprove\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setPivoting\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setPivoting\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPivoting\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getPivoting\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isPivMode\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isPivMode\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isPivRule\n * Signature: (I)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isPivRule\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setPreferdual\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setPreferdual\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setSimplextype\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setSimplextype\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getSimplextype\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getSimplextype\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setNegrange\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setNegrange\n  (JNIEnv *, jobject, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getNegrange\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getNegrange\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getTotalIter\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_lpsolve_LpSolve_getTotalIter\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getMaxLevel\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getMaxLevel\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getTotalNodes\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_lpsolve_LpSolve_getTotalNodes\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getNrows\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNrows\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getNorigRows\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNorigRows\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getLrows\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getLrows\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getNcolumns\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNcolumns\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getNorigColumns\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNorigColumns\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getNonzeros\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNonzeros\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getOrigIndex\n * Signature: (I)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getOrigIndex\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getLpIndex\n * Signature: (I)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getLpIndex\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBasis\n * Signature: ([IZ)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBasis\n  (JNIEnv *, jobject, jintArray, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getBasis\n * Signature: ([IZ)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getBasis\n  (JNIEnv *, jobject, jintArray, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    guessBasis\n * Signature: ([IZ)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_guessBasis\n  (JNIEnv *, jobject, jdoubleArray, jintArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    resetBasis\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_resetBasis\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    defaultBasis\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_defaultBasis\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBasiscrash\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBasiscrash\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getBasiscrash\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getBasiscrash\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    unscale\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_unscale\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBFP\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setBFP\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isNativeBFP\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isNativeBFP\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    hasBFP\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_hasBFP\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    solve\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_solve\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getStatustext\n * Signature: (I)Ljava/lang/String;\n */\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_getStatustext\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isFeasible\n * Signature: ([DD)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isFeasible\n  (JNIEnv *, jobject, jdoubleArray, jdouble);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getObjective\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getObjective\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getWorkingObjective\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getWorkingObjective\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getVariables\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getVariables\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrVariables\n * Signature: ()[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrVariables\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getConstraints\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getConstraints\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrConstraints\n * Signature: ()[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrConstraints\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPrimalSolution\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getPrimalSolution\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrPrimalSolution\n * Signature: ()[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrPrimalSolution\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getVarPrimalresult\n * Signature: (I)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getVarPrimalresult\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getSensitivityRhs\n * Signature: ([D[D[D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getSensitivityRhs\n  (JNIEnv *, jobject, jdoubleArray, jdoubleArray, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrSensitivityRhs\n * Signature: ()[[D\n */\nJNIEXPORT jobjectArray JNICALL Java_lpsolve_LpSolve_getPtrSensitivityRhs\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getDualSolution\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getDualSolution\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrDualSolution\n * Signature: ()[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrDualSolution\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getVarDualresult\n * Signature: (I)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getVarDualresult\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getSensitivityObj\n * Signature: ([D[D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getSensitivityObj\n  (JNIEnv *, jobject, jdoubleArray, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrSensitivityObj\n * Signature: ()[[D\n */\nJNIEXPORT jobjectArray JNICALL Java_lpsolve_LpSolve_getPtrSensitivityObj\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getSensitivityObjex\n * Signature: ([D[D[D[D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getSensitivityObjex\n  (JNIEnv *, jobject, jdoubleArray, jdoubleArray, jdoubleArray, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrSensitivityObjex\n * Signature: ()[[D\n */\nJNIEXPORT jobjectArray JNICALL Java_lpsolve_LpSolve_getPtrSensitivityObjex\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getLambda\n * Signature: ([D)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_getLambda\n  (JNIEnv *, jobject, jdoubleArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getPtrLambda\n * Signature: ()[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_lpsolve_LpSolve_getPtrLambda\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    deleteLp\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_deleteLp\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    writeLp\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeLp\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    writeMps\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeMps\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    writeFreeMps\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeFreeMps\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    readBasis\n * Signature: (Ljava/lang/String;)Ljava/lang/String;\n */\nJNIEXPORT jstring JNICALL Java_lpsolve_LpSolve_readBasis\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    writeBasis\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeBasis\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    readParams\n * Signature: (Ljava/lang/String;Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_readParams\n  (JNIEnv *, jobject, jstring, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    writeParams\n * Signature: (Ljava/lang/String;Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeParams\n  (JNIEnv *, jobject, jstring, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    resetParams\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_resetParams\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printLp\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printLp\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printConstraints\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printConstraints\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printDuals\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printDuals\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printScales\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printScales\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printTableau\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printTableau\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printObjective\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printObjective\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printSolution\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printSolution\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printStr\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printStr\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setOutputfile\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setOutputfile\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    printDebugdump\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_printDebugdump\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setXLI\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setXLI\n  (JNIEnv *, jobject, jstring);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    writeXLI\n * Signature: (Ljava/lang/String;Ljava/lang/String;Z)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_writeXLI\n  (JNIEnv *, jobject, jstring, jstring, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    hasXLI\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_hasXLI\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isNativeXLI\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isNativeXLI\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getNameindex\n * Signature: (Ljava/lang/String;Z)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_getNameindex\n  (JNIEnv *, jobject, jstring, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    dualizeLp\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_dualizeLp\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    isUseNames\n * Signature: (Z)Z\n */\nJNIEXPORT jboolean JNICALL Java_lpsolve_LpSolve_isUseNames\n  (JNIEnv *, jobject, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setUseNames\n * Signature: (ZZ)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_setUseNames\n  (JNIEnv *, jobject, jboolean, jboolean);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    getConstrValue\n * Signature: (II[D[I)D\n */\nJNIEXPORT jdouble JNICALL Java_lpsolve_LpSolve_getConstrValue\n  (JNIEnv *, jobject, jint, jint, jdoubleArray, jintArray);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    setBasisvar\n * Signature: (II)I\n */\nJNIEXPORT jint JNICALL Java_lpsolve_LpSolve_setBasisvar\n  (JNIEnv *, jobject, jint, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    registerAbortfunc\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerAbortfunc\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    registerLogfunc\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerLogfunc\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    registerMsgfunc\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerMsgfunc\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    registerBbBranchfunc\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerBbBranchfunc\n  (JNIEnv *, jobject);\n\n/*\n * Class:     lpsolve_LpSolve\n * Method:    registerBbNodefunc\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_lpsolve_LpSolve_registerBbNodefunc\n  (JNIEnv *, jobject);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/AbortListener.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\t\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\npackage lpsolve;\r\n\r\n/**\r\n * Classes that implement this interface may be passed\r\n * to the <code>putAbortfunc</code> method of the <code>LpSolve</code> class.\r\n * \r\n * @author Juergen Ebert\r\n * @see LpSolve#putAbortfunc\r\n * @see \"lp_solve documentation for 'put_abortfunc'\"\r\n */\r\npublic interface AbortListener {\r\n\r\n\t/**\r\n\t * When set, the abort routine is called regularly during solve(). \r\n\t * The user can do whatever he wants in this routine.\r\n\t * \r\n\t * @param problem the problem this Listener was defined for\r\n\t * @param userhandle the userhandle object that was passed to <code>putAbortfunc</code>\r\n\t * @return if true, then lp_solve aborts the solver and returns with an appropriate code\r\n\t * @throws LpSolveException\r\n\t */\r\n\tpublic boolean abortfunc(LpSolve problem, Object userhandle) throws LpSolveException;\r\n\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/BbListener.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\t\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\npackage lpsolve;\r\n\r\n/**\r\n * Classes that implement this interface may be passed\r\n * to the <code>putbbBranchfunc</code> and <code>putbbNodefunc</code> method \r\n * of the <code>LpSolve</code> class.\r\n * \r\n * @author Juergen Ebert\r\n * @see LpSolve#putBbBranchfunc\r\n * @see LpSolve#putBbNodefunc\r\n * @see \"lp_solve documentation for 'put_bb_branchfunc'\"\r\n * @see \"lp_solve documentation for 'put_bb_nodefunc'\"\r\n */\r\npublic interface BbListener {\r\n\r\n\t/**\r\n\t * TODO: add documentation when available\r\n\t *  \r\n\t * @param problem the problem this Listener was defined for\r\n\t * @param userhandle the userhandle object that was passed to <code>putLogfunc</code>\r\n\t * @param buf the log message\r\n\t * @throws LpSolveException\r\n\t */\r\n\tpublic int bbfunc(LpSolve problem, Object userhandle, int message) throws LpSolveException;\r\n\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/LogListener.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\t\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\npackage lpsolve;\r\n\r\n/**\r\n * Classes that implement this interface may be passed\r\n * to the <code>putLogfunc</code> method of the <code>LpSolve</code> class.\r\n * \r\n * @author Juergen Ebert\r\n * @see LpSolve#putLogfunc\r\n * @see \"lp_solve documentation for 'put_logfunc'\"\r\n */\r\npublic interface LogListener {\r\n\r\n\t/**\r\n\t * When set, the log routine is called when lp_solve has someting \r\n\t * to report (error conditions or so).\r\n\t *  \r\n\t * @param problem the problem this Listener was defined for\r\n\t * @param userhandle the userhandle object that was passed to <code>putLogfunc</code>\r\n\t * @param buf the log message\r\n\t * @throws LpSolveException\r\n\t */\r\n\tpublic void logfunc(LpSolve problem, Object userhandle, String buf) throws LpSolveException;\r\n\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/LpSolve.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\npackage lpsolve;\r\n\r\nimport java.util.HashMap;\r\nimport java.util.Map;\r\n\r\n\r\n/**\r\n * Object wrapper for a problem structure of the lp_solve library.\r\n * Offers access to all lp_solve methods.\r\n *\r\n * @author Juergen Ebert\r\n */\r\npublic class LpSolve {\r\n\r\n\tpublic static final int FALSE           = 0;\r\n\tpublic static final int TRUE            = 1;\r\n\tpublic static final int AUTOMATIC       = 2;\r\n\tpublic static final int DYNAMIC         = 4;\r\n\r\n\tpublic static final int FR = 0;\r\n\tpublic static final int LE = 1;\r\n\tpublic static final int GE = 2;\r\n\tpublic static final int EQ = 3;\r\n\tpublic static final int OF = 4;\r\n\r\n\tpublic static final int SIMPLEX_PRIMAL_PRIMAL    = 5;\r\n\tpublic static final int SIMPLEX_DUAL_PRIMAL      = 6;\r\n\tpublic static final int SIMPLEX_PRIMAL_DUAL      = 9;\r\n\tpublic static final int SIMPLEX_DUAL_DUAL        = 10;\r\n\tpublic static final int SIMPLEX_DEFAULT          = SIMPLEX_DUAL_PRIMAL;\r\n\r\n\t/* Presolve defines */\r\n\tpublic static final int PRESOLVE_NONE            = 0;\r\n\tpublic static final int PRESOLVE_ROWS            = 1;\r\n\tpublic static final int PRESOLVE_COLS            = 2;\r\n\tpublic static final int PRESOLVE_LINDEP          = 4;\r\n\tpublic static final int PRESOLVE_SOS             = 32;\r\n\tpublic static final int PRESOLVE_REDUCEMIP       = 64;\r\n\tpublic static final int PRESOLVE_KNAPSACK        = 128;\r\n\tpublic static final int PRESOLVE_ELIMEQ2         = 256;\r\n\tpublic static final int PRESOLVE_IMPLIEDFREE     = 512;\r\n\tpublic static final int PRESOLVE_REDUCEGCD       = 1024;\r\n\tpublic static final int PRESOLVE_PROBEFIX        = 2048;\r\n\tpublic static final int PRESOLVE_PROBEREDUCE     = 4096;\r\n\tpublic static final int PRESOLVE_ROWDOMINATE     = 8192;\r\n\tpublic static final int PRESOLVE_COLDOMINATE     = 16384;\r\n\tpublic static final int PRESOLVE_MERGEROWS       = 32768;\r\n\tpublic static final int PRESOLVE_IMPLIEDSLK      = 65536;\r\n\tpublic static final int PRESOLVE_COLFIXDUAL      = 131072;\r\n\tpublic static final int PRESOLVE_BOUNDS          = 262144;\r\n\tpublic static final int PRESOLVE_DUALS           = 524288;\r\n\tpublic static final int PRESOLVE_SENSDUALS       = 1048576;\r\n\r\n\t/* Basis crash options */\r\n\tpublic static final int CRASH_NOTHING            = 0;\r\n\tpublic static final int CRASH_MOSTFEASIBLE       = 2;\r\n\r\n\t/* Strategy codes to avoid or recover from degenerate pivots */\r\n\tpublic static final int ANTIDEGEN_NONE           = 0;\r\n\tpublic static final int ANTIDEGEN_FIXEDVARS      = 1;\r\n\tpublic static final int ANTIDEGEN_COLUMNCHECK    = 2;\r\n\tpublic static final int ANTIDEGEN_STALLING       = 4;\r\n\tpublic static final int ANTIDEGEN_NUMFAILURE     = 8;\r\n\tpublic static final int ANTIDEGEN_LOSTFEAS      = 16;\r\n\tpublic static final int ANTIDEGEN_INFEASIBLE    = 32;\r\n\tpublic static final int ANTIDEGEN_DYNAMIC       = 64;\r\n\tpublic static final int ANTIDEGEN_DURINGBB     = 128;\r\n\tpublic static final int ANTIDEGEN_RHSPERTURB   = 256;\r\n\tpublic static final int ANTIDEGEN_BOUNDFLIP    = 512;\r\n\r\n\t/* REPORT defines */\r\n\tpublic static final int NEUTRAL      = 0;\r\n\tpublic static final int CRITICAL     = 1;\r\n\tpublic static final int SEVERE       = 2;\r\n\tpublic static final int IMPORTANT    = 3;\r\n\tpublic static final int NORMAL       = 4;\r\n\tpublic static final int DETAILED     = 5;\r\n\tpublic static final int FULL         = 6;\r\n\r\n\t/* MESSAGE defines */\r\n\tpublic static final int MSG_NONE                 = 0;\r\n\tpublic static final int MSG_PRESOLVE             = 1;\r\n\tpublic static final int MSG_ITERATION            = 2;\r\n\tpublic static final int MSG_INVERT               = 4;\r\n\tpublic static final int MSG_LPFEASIBLE           = 8;\r\n\tpublic static final int MSG_LPOPTIMAL           = 16;\r\n\tpublic static final int MSG_LPEQUAL             = 32;\r\n\tpublic static final int MSG_LPBETTER            = 64;\r\n\tpublic static final int MSG_MILPFEASIBLE       = 128;\r\n\tpublic static final int MSG_MILPEQUAL          = 256;\r\n\tpublic static final int MSG_MILPBETTER         = 512;\r\n\tpublic static final int MSG_MILPSTRATEGY      = 1024;\r\n\tpublic static final int MSG_MILPOPTIMAL       = 2048;\r\n\tpublic static final int MSG_PERFORMANCE       = 4096;\r\n\tpublic static final int MSG_INITPSEUDOCOST    = 8192;\r\n\r\n\t/* Improvement defines */\r\n\tpublic static final int IMPROVE_NONE        = 0;\r\n\tpublic static final int IMPROVE_SOLUTION    = 1;\r\n\tpublic static final int IMPROVE_DUALFEAS    = 2;\r\n\tpublic static final int IMPROVE_THETAGAP    = 4;\r\n\tpublic static final int IMPROVE_BBSIMPLEX   = 8;\r\n\r\n\t/* Scaling types */\r\n\tpublic static final int SCALE_NONE               = 0;\r\n\tpublic static final int SCALE_EXTREME            = 1;\r\n\tpublic static final int SCALE_RANGE              = 2;\r\n\tpublic static final int SCALE_MEAN               = 3;\r\n\tpublic static final int SCALE_GEOMETRIC          = 4;\r\n\tpublic static final int SCALE_CURTISREID         = 7;   /* Override to optimal Curtis-Reid scaling */\r\n\r\n\t/* Alternative scaling weights */\r\n\tpublic static final int SCALE_LINEAR             = 0;\r\n\tpublic static final int SCALE_QUADRATIC          = 8;\r\n\tpublic static final int SCALE_LOGARITHMIC       = 16;\r\n\tpublic static final int SCALE_USERWEIGHT        = 31;\r\n\tpublic static final int SCALE_POWER2            = 32;   /* As is or rounded to power of 2 */\r\n\tpublic static final int SCALE_EQUILIBRATE       = 64;   /* Make sure that no scaled number is above 1 */\r\n\tpublic static final int SCALE_INTEGERS         = 128;   /* Apply to integer column variables */\r\n\tpublic static final int SCALE_DYNUPDATE        = 256;\r\n\tpublic static final int SCALE_ROWSONLY         = 512;\r\n\tpublic static final int SCALE_COLSONLY        = 1024;\r\n\r\n\t/* Pricing methods */\r\n\tpublic static final int PRICER_FIRSTINDEX        = 0;\r\n\tpublic static final int PRICER_DANTZIG           = 1;\r\n\tpublic static final int PRICER_DEVEX             = 2;\r\n\tpublic static final int PRICER_STEEPESTEDGE      = 3;\r\n\r\n\t/* Pricing strategies */\r\n\tpublic static final int PRICE_METHODDEFAULT      = 0;\r\n\tpublic static final int PRICE_PRIMALFALLBACK     = 4;    /* In case of Steepest Edge, fall back to DEVEX in primal */\r\n\tpublic static final int PRICE_MULTIPLE           = 8;    /* Multiple pricing (as of v5 only binary) */\r\n\tpublic static final int PRICE_PARTIAL           = 16;    /* Enable partial pricing */\r\n\tpublic static final int PRICE_ADAPTIVE          = 32;    /* Temporarily use First Index if cycling is detected */\r\n\tpublic static final int PRICE_HYBRID            = 64;    /* NOT IMPLEMENTED */\r\n\tpublic static final int PRICE_RANDOMIZE        = 128;    /* Adds a small randomization effect to the selected pricer */\r\n\tpublic static final int PRICE_AUTOPARTIAL      = 512;\r\n\tpublic static final int PRICE_LOOPLEFT        = 1024;    /* Scan entering/leaving columns left rather than right */\r\n\tpublic static final int PRICE_LOOPALTERNATE   = 2048;    /* Scan entering/leaving columns alternatingly left/right */\r\n\tpublic static final int PRICE_HARRISTWOPASS   = 4096;\r\n\tpublic static final int PRICE_TRUENORMINIT   = 16384;\r\n\r\n\t/* B&B strategies */\r\n\tpublic static final int NODE_FIRSTSELECT         = 0;\r\n\tpublic static final int NODE_GAPSELECT           = 1;\r\n\tpublic static final int NODE_RANGESELECT         = 2;\r\n\tpublic static final int NODE_FRACTIONSELECT      = 3;\r\n\tpublic static final int NODE_PSEUDOCOSTSELECT    = 4;\r\n\tpublic static final int NODE_PSEUDONONINTSELECT  = 5;                /* Kjell Eikland special #1 */\r\n\tpublic static final int NODE_PSEUDORATIOSELECT   = 6;                /* Kjell Eikland special #2 */\r\n\tpublic static final int NODE_USERSELECT          = 7;\r\n\r\n\tpublic static final int NODE_WEIGHTREVERSEMODE   = 8;\r\n\tpublic static final int NODE_BRANCHREVERSEMODE   = 16;\r\n\tpublic static final int NODE_GREEDYMODE          = 32;\r\n\tpublic static final int NODE_PSEUDOCOSTMODE      = 64;\r\n\tpublic static final int NODE_DEPTHFIRSTMODE      = 128;\r\n\tpublic static final int NODE_RANDOMIZEMODE       = 256;\r\n\tpublic static final int NODE_DYNAMICMODE         = 1024;\r\n\tpublic static final int NODE_RESTARTMODE         = 2048;\r\n\tpublic static final int NODE_BREADTHFIRSTMODE    = 4096;\r\n\tpublic static final int NODE_AUTOORDER           = 8192;\r\n\tpublic static final int NODE_RCOSTFIXING         = 16384;\r\n\tpublic static final int NODE_STRONGINIT          = 32768;\r\n\r\n\tpublic static final int BRANCH_CEILING   = 0;\r\n\tpublic static final int BRANCH_FLOOR     = 1;\r\n\tpublic static final int BRANCH_AUTOMATIC = 2;\r\n        public static final int BRANCH_DEFAULT   = 3;\r\n\r\n\t/* Solver status values */\r\n\tpublic static final int UNKNOWNERROR            = -5;\r\n\tpublic static final int DATAIGNORED             = -4;\r\n\tpublic static final int NOBFP                   = -3;\r\n\tpublic static final int NOMEMORY                = -2;\r\n\tpublic static final int NOTRUN                  = -1;\r\n\tpublic static final int OPTIMAL                  = 0;\r\n\tpublic static final int SUBOPTIMAL               = 1;\r\n\tpublic static final int INFEASIBLE               = 2;\r\n\tpublic static final int UNBOUNDED                = 3;\r\n\tpublic static final int DEGENERATE               = 4;\r\n\tpublic static final int NUMFAILURE               = 5;\r\n\tpublic static final int USERABORT                = 6;\r\n\tpublic static final int TIMEOUT                  = 7;\r\n\tpublic static final int RUNNING                  = 8;\r\n\tpublic static final int PRESOLVED                = 9;\r\n\r\n\t/* Branch & Bound and Lagrangean extra status values */\r\n\tpublic static final int PROCFAIL                = 10;\r\n\tpublic static final int PROCBREAK               = 11;\r\n\tpublic static final int FEASFOUND               = 12;\r\n\tpublic static final int NOFEASFOUND             = 13;\r\n\r\n\r\n\t/**\r\n\t * Value of the pointer to the <code>lprec</code> structure in the C stub DLL.\r\n\t */\r\n\tprivate long lp = 0;\r\n\r\n\t/**\r\n\t * Callback listener set by <code>putAbortfunc</code>\r\n\t */\r\n\tprivate AbortListener abortListener = null;\r\n\r\n\t/**\r\n\t * User handle set by <code>putAbortfunc</code>\r\n\t */\r\n\tprivate Object abortUserhandle = null;\r\n\r\n\t/**\r\n\t * Callback listener set by <code>putLogfunc</code>\r\n\t */\r\n\tprivate LogListener logListener = null;\r\n\r\n\t/**\r\n\t * User handle set by <code>putLogfunc</code>\r\n\t */\r\n\tprivate Object logUserhandle = null;\r\n\r\n\t/**\r\n\t * Callback listener set by <code>putMsgfunc</code>\r\n\t */\r\n\tprivate MsgListener msgListener = null;\r\n\r\n\t/**\r\n\t * User handle set by <code>putMsgfunc</code>\r\n\t */\r\n\tprivate Object msgUserhandle = null;\r\n\r\n\t/**\r\n\t * Callback listener set by <code>putBbBranchfunc</code>\r\n\t */\r\n\tprivate BbListener bbBranchListener = null;\r\n\r\n\t/**\r\n\t * User handle set by <code>putBbBranchfunc</code>\r\n\t */\r\n\tprivate Object bbBranchUserhandle = null;\r\n\r\n\t/**\r\n\t * Callback listener set by <code>putBbNodefunc</code>\r\n\t */\r\n\tprivate BbListener bbNodeListener = null;\r\n\r\n\t/**\r\n\t * User handle set by <code>putBbNodefunc</code>\r\n\t */\r\n\tprivate Object bbNodeUserhandle = null;\r\n\r\n\t/**\r\n\t * Static initializer to load the stub library\r\n\t */\r\n\tstatic {\r\n\t\tSystem.loadLibrary(\"lpsolve55j\");\r\n\t\tinit();\r\n\t}\r\n\r\n\t/**\r\n\t * Native helper method to cache method and field IDs.\r\n\t */\r\n\tprivate static native void init();\r\n\r\n\r\n\t// ========================================================================\r\n\t// Constructors\r\n\t// ========================================================================\r\n\r\n\t/**\r\n\t * Constructs a new LpSolve instance\r\n\t */\r\n\tprivate LpSolve(long lp) {\r\n\t\tthis.lp = lp;\r\n\t}\r\n\r\n\t// ========================================================================\r\n\t// Public static factory methods\r\n\t// ========================================================================\r\n\r\n\t/**\r\n\t * Creates a new problem. Upon successful completion, the lprec attribute\r\n\t * in this class contains the value of the pointer to the <code>lprec</code>\r\n\t * structure.\r\n\t *\r\n\t * @param rows Initial number of rows.\r\n\t * @param columns Initial number of columns.\r\n\t * @throws LpSolveException if lp_solve could not create the problem\r\n\t */\r\n\tpublic static native LpSolve makeLp(int rows, int columns) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Read an lp model from file and create a new problem.\r\n\t */\r\n\tpublic static native LpSolve readLp(String filename, int verbose, String lpName)\r\n\t\tthrows LpSolveException;\r\n\r\n\t/**\r\n\t * Read an mps model from file and create a new problem.\r\n\t */\r\n\tpublic static native LpSolve readMps(String filename, int verbose)\r\n\t\tthrows LpSolveException;\r\n\r\n\t/**\r\n\t * Read a model in free MPS format from file and create a new problem.\r\n\t */\r\n\tpublic static native LpSolve readFreeMps(String filename, int verbose)\r\n\t\tthrows LpSolveException;\r\n\r\n\t/**\r\n\t * Read a model via the External Language Interface and create a new problem.\r\n\t */\r\n\tpublic static native LpSolve readXLI(String xliname, String modelname,\r\n\t\t\tString dataname, String options, int verbose) throws LpSolveException;\r\n\r\n\r\n\t// ========================================================================\r\n\t// Other static methods\r\n\t// ========================================================================\r\n\r\n\t/**\r\n\t * Returns the full version number of the underlying lp_solve library.\r\n\t *\r\n\t * @return VersionInfo object with full version info\r\n\t */\r\n\tpublic static native VersionInfo lpSolveVersion();\r\n\r\n\r\n\t// ========================================================================\r\n\t// Overridden methods of the base class\r\n\t// ========================================================================\r\n\r\n\r\n\t/* (non-Javadoc)\r\n\t * @see java.lang.Object#finalize()\r\n\t */\r\n\tprotected void finalize() throws Throwable {\r\n\t\tif (lp != 0) {\r\n\t\t\tremoveLp(lp);\r\n\t\t\tdeleteLp();\r\n\t\t}\r\n\t\tsuper.finalize();\r\n\t}\r\n\r\n\t/**\r\n\t * Return the value of the lp attribute.\r\n\t * @return the value of the lp attribute\r\n\t */\r\n\tpublic long getLp() {\r\n\t\treturn lp;\r\n\t}\r\n\r\n\r\n\t// ========================================================================\r\n\t// Native methods.\r\n\t// ========================================================================\r\n\r\n\t/**\r\n\t * Copy an existing lprec structure to a new lprec structure.\r\n\t * Creates an independent new problem.\r\n\t */\r\n\tpublic native LpSolve copyLp() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the name of the problem.\r\n\t */\r\n\tpublic native void setLpName(String name) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Allocate memory for the specified size.\r\n\t */\r\n\tpublic native void resizeLp(int rows, int columns) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the name of the problem.\r\n\t */\r\n\tpublic native String getLpName() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Add a constraint to the problem.\r\n\t */\r\n\tpublic native void addConstraint(double[] row, int constrType, double rh) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Add a constraint to the problem.\r\n\t */\r\n\tpublic native void strAddConstraint(String row, int constrType, double rh) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Add a constraint to the problem.\r\n\t */\r\n\tpublic native void addConstraintex(int count, double[] row, int[] colno, int constrType, double rh) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Remove a constraint from the problem.\r\n\t */\r\n\tpublic native void delConstraint(int rownr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns if constraint type specified in mask is active.\r\n\t */\r\n\tpublic native boolean isConstrType(int row, int mask);\r\n\r\n\t/**\r\n\t * Add a Lagrangian constraint to the problem.\r\n\t */\r\n\tpublic native void addLagCon(double[] row, int constrType, double rh) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Add a Lagrangian constraint to the problem.\r\n\t */\r\n\tpublic native void strAddLagCon(String row, int constrType, double rh) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Add a column to the problem.\r\n\t */\r\n\tpublic native void addColumn(double[] column) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Add a column to the problem.\r\n\t */\r\n\tpublic native void addColumnex(int count, double[] column, int[] rowno) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Add a column to the problem.\r\n\t */\r\n\tpublic native void strAddColumn(String column) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Remove a column from the problem.\r\n\t */\r\n\tpublic native void delColumn(int columnnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set a constraint in the lp.\r\n\t */\r\n\tpublic native void setRow(int rowno, double[] row) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set a constraint in the lp.\r\n\t */\r\n\tpublic native void setRowex(int rowno, int count, double[] row, int[] colno) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set a column in the lp.\r\n\t */\r\n\tpublic native void setColumn(int colno, double[] column) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set a column in the lp.\r\n\t */\r\n\tpublic native void setColumnex(int colno, int count, double[] column, int[] rowno) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Check if a column is already present in the problem.\r\n\t */\r\n\tpublic native int columnInLp(double[] column);\r\n\r\n\t/**\r\n\t * Set the name of a constraint (row) in the problem.\r\n\t */\r\n\tpublic native void setRowName(int rownr, String name) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Gets the name of a constraint (row) in the problem.\r\n\t */\r\n\tpublic native String getRowName(int rownr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Gets the name of a constraint (row) in the problem.\r\n\t */\r\n\tpublic native String getOrigrowName(int rownr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the name of a column in the problem.\r\n\t */\r\n\tpublic native void setColName(int colnr, String name) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Gets the name of a column in the problem.\r\n\t */\r\n\tpublic native String getColName(int colnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Gets the name of a column in the problem.\r\n\t */\r\n\tpublic native String getOrigcolName(int colnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the right hand side (RHS) vector (column 0).\r\n\t */\r\n\tpublic native void setRhVec(double[] rh) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the right hand side (RHS) vector (column 0).\r\n\t */\r\n\tpublic native void strSetRhVec(String rh) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the value of the right hand side (RHS) vector (column 0) for one row.\r\n\t */\r\n\tpublic native void setRh(int row, double value) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the value of the right hand side (RHS) vector (column 0) for one row.\r\n\t * NOTE: Returns 0 even if the row index is out of bounds, in accordance\r\n\t * to the behaviour of the lp_solve routine!\r\n\t */\r\n\tpublic native double getRh(int row);\r\n\r\n\t/**\r\n\t * Set the type of a constraint.\r\n\t */\r\n\tpublic native void setConstrType(int rownr, int constrType) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the type of a constraint.\r\n\t */\r\n\tpublic native short getConstrType(int rownr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Add a SOS constraint.\r\n\t */\r\n\tpublic native void addSOS(String name, int sostype, int priority, int count,\r\n\t\tint[] sosvars, double[] weights) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns if the variable is SOS or not.\r\n\t */\r\n\tpublic native boolean isSOSVar(int colnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the objective function (row 0) of the matrix.\r\n\t */\r\n\tpublic native void setObjFn(double[] row) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the objective function (row 0) of the matrix.\r\n\t */\r\n\tpublic native void strSetObjFn(String row) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the objective function (row 0) of the matrix.\r\n\t */\r\n\tpublic native void setObjFnex(int count, double[] row, int[] colno) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the objective function (row 0) of the matrix.\r\n\t */\r\n\tpublic native void setObj(int column, double value) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set a single element in the matrix.\r\n\t */\r\n\tpublic native void setMat(int row, int column, double value) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get a single element from the matrix.\r\n\t */\r\n\tpublic native double getMat(int row, int column);\r\n\r\n\t/**\r\n\t * Get all row elements from the matrix.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getRow(int rownr, double[] row) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the non-zero row elements from the matrix.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native int getRowex(int rownr, double[] row, int[] nzcols) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get all row elements from the matrix.\r\n\t * Returned array is allocated by the method.\r\n\t * This is an additional method which is not implemented by lp_solve.\r\n\t * Internally, get_row is used.\r\n\t */\r\n\tpublic native double[] getPtrRow(int rownr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get all column elements from the matrix.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getColumn(int colnr, double[] column) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the non-zero column elements from the matrix.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native int getColumnex(int colnr, double[] column, int[] nzrows) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get all column elements from the matrix.\r\n\t * Returned array is allocated by the method.\r\n\t * This is an additional method which is not implemented by lp_solve.\r\n\t * Internally, get_column is used.\r\n\t */\r\n\tpublic native double[] getPtrColumn(int columnrnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set objective function to maximize.\r\n\t */\r\n\tpublic native void setMaxim();\r\n\r\n\t/**\r\n\t * Set objective function to minimize.\r\n\t */\r\n\tpublic native void setMinim();\r\n\r\n\t/**\r\n\t * Set objective function sense.\r\n\t */\r\n\tpublic native void setSense(boolean maximize);\r\n\r\n\t/**\r\n\t * Returns objective function direction.\r\n\t */\r\n\tpublic native boolean isMaxim();\r\n\r\n\t/**\r\n\t * Set the lower bound of a variable.\r\n\t */\r\n\tpublic native void setLowbo(int colnr, double value) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the lower bound of a variable.\r\n\t */\r\n\tpublic native double getLowbo(int colnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the upper bound of a variable.\r\n\t */\r\n\tpublic native void setUpbo(int colnr, double value) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the upper bound of a variable.\r\n\t */\r\n\tpublic native double getUpbo(int colnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Sets if the variable is free.\r\n\t */\r\n\tpublic native void setUnbounded(int colnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns if the variable is free.\r\n\t */\r\n\tpublic native boolean isUnbounded(int colnr);\r\n\r\n\t/**\r\n\t * Returns if the variable is negative.\r\n\t */\r\n\tpublic native boolean isNegative(int colnr);\r\n\r\n\t/**\r\n\t * Set the upper and lower bound of a variable.\r\n\t */\r\n\tpublic native void setBounds(int colnr, double lower, double upper) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Specifies if set bounds may only be tighter or also less restrictive.\r\n\t */\r\n\tpublic native void setBoundsTighter(boolean tighten);\r\n\r\n\t/**\r\n\t * Returns if set bounds may only be tighter or also less restrictive.\r\n\t */\r\n\tpublic native boolean getBoundsTighter();\r\n\r\n\t/**\r\n\t * Set the range on a constraint.\r\n\t */\r\n\tpublic native void setRhRange(int rownr, double range) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Gets the range on a constraint.\r\n\t */\r\n\tpublic native double getRhRange(int rownr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the type of the variable. Integer or floating point.\r\n\t */\r\n\tpublic native void setInt(int colnr, boolean mustBeInteger) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the type of the variable. Integer or floating point.\r\n\t */\r\n\tpublic native boolean isInt(int colnr);\r\n\r\n\t/**\r\n\t * Set the type of the variable. Binary or floating point.\r\n\t */\r\n\tpublic native void setBinary(int colnr, boolean mustBeBin) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Gets the type of the variable. Binary integer or floating point.\r\n\t */\r\n\tpublic native boolean isBinary(int colnr);\r\n\r\n\t/**\r\n\t * Set the type of the variable. semi-continious or not.\r\n\t */\r\n\tpublic native void setSemicont(int colnr, boolean mustBeSc) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Get the type of the variable. semi-continious or not.\r\n\t */\r\n\tpublic native boolean isSemicont(int colnr);\r\n\r\n\t/**\r\n\t * Specifies the practical value for \"infinite\".\r\n\t */\r\n\tpublic native void setInfinite(double value);\r\n\r\n\t/**\r\n\t * Returns the value of \"infinite\".\r\n\t */\r\n\tpublic native double getInfinite();\r\n\r\n\t/**\r\n\t * Checks if the provided absolute of the value is larger or equal to \"infinite\".\r\n\t */\r\n\tpublic native boolean isInfinite(double value);\r\n\r\n\t/**\r\n\t * Specifies the tolerance that is used to determine whether a floating-point\r\n\t * number is in fact an integer.\r\n\t */\r\n\tpublic native void setEpsint(double value);\r\n\r\n\t/**\r\n\t * Returns the tolerance that is used to determine whether a floating-point\r\n\t * number is in fact an integer\r\n\t */\r\n\tpublic native double getEpsint();\r\n\r\n\t/**\r\n\t * Specifies the value that is used as a tolerance for the Right Hand Side (RHS)\r\n\t * to determine whether a value should be considered as 0\r\n\t */\r\n\tpublic native void setEpsb(double value);\r\n\r\n\t/**\r\n\t * Returns the value that is used as a tolerance for the Right Hand Side (RHS)\r\n\t * to determine whether a value should be considered as 0.\r\n\t */\r\n\tpublic native double getEpsb();\r\n\r\n\t/**\r\n\t * Specifies the value that is used as a tolerance for reduced costs\r\n\t * to determine whether a value should be considered as 0.\r\n\t */\r\n\tpublic native void setEpsd(double value);\r\n\r\n\t/**\r\n\t * Returns the value that is used as a tolerance for the reduced costs\r\n\t * to determine whether a value should be considered as 0.\r\n\t */\r\n\tpublic native double getEpsd();\r\n\r\n\t/**\r\n\t * Specifies the value that is used as a tolerance for rounding values to zero.\r\n\t */\r\n\tpublic native void setEpsel(double value);\r\n\r\n\t/**\r\n\t * Returns the value that is used as a tolerance for rounding values to zero.\r\n\t */\r\n\tpublic native double getEpsel();\r\n\r\n\t/**\r\n\t * Specifies the value that is used as a tolerance pivot element to determine\r\n\t * whether a value should be considered as 0.\r\n\t */\r\n\tpublic native void setEpspivot(double value);\r\n\r\n\t/**\r\n\t * Returns the value that is used as a tolerance pivot element to determine\r\n\t * whether a value should be considered as 0.\r\n\t */\r\n\tpublic native double getEpspivot();\r\n\r\n\t/**\r\n\t * Specifies the value that is used as perturbation scalar for degenerative problems.\r\n\t */\r\n\tpublic native void setEpsperturb(double value);\r\n\r\n\t/**\r\n\t * Returns the value that is used as perturbation scalar for degenerative problems.\r\n\t */\r\n\tpublic native double getEpsperturb();\r\n\r\n\t/**\r\n\t * This is a simplified way of specifying multiple eps thresholds that are \"logically\" consistent.\r\n\t */\r\n\tpublic native void setEpslevel(int epslevel) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns an extra status after a call to a function.\r\n\t */\r\n\tpublic native int getStatus();\r\n\r\n\t/**\r\n\t * Specifies the MIP gap value.\r\n\t */\r\n\tpublic native void setMipGap(boolean absolute, double value);\r\n\r\n\t/**\r\n\t * Returns the MIP gap value.\r\n\t */\r\n\tpublic native double getMipGap(boolean absolute);\r\n\r\n\t/**\r\n\t * Set the verbose level.\r\n\t */\r\n\tpublic native void setVerbose(int verbose);\r\n\r\n\t/**\r\n\t * Returns the verbose level.\r\n\t */\r\n\tpublic native int getVerbose();\r\n\r\n\t/**\r\n\t * Set a timeout.\r\n\t */\r\n\tpublic native void setTimeout(long timeout);\r\n\r\n\t/**\r\n\t * Gets the timout.\r\n\t */\r\n\tpublic native long getTimeout();\r\n\r\n\t/**\r\n\t * Gets the time elapsed since start of solve.\r\n\t */\r\n\tpublic native double timeElapsed();\r\n\r\n\t/**\r\n\t * Sets a flag if all intermediate valid solutions must be printed while solving.\r\n\t */\r\n\tpublic native void setPrintSol(int printSol);\r\n\r\n\t/**\r\n\t * Returns a flag if all intermediate valid solutions must be printed while solving.\r\n\t */\r\n\tpublic native int getPrintSol();\r\n\r\n\t/**\r\n\t * Sets a flag if all intermediate results and the branch-and-bound decisions\r\n\t * must be printed while solving.\r\n\t */\r\n\tpublic native void setDebug(boolean debug);\r\n\r\n\t/**\r\n\t * Returns a flag if all intermediate results and the branch-and-bound decisions\r\n\t * must be printed while solving.\r\n\t */\r\n\tpublic native boolean isDebug();\r\n\r\n\t/**\r\n\t * Sets a flag if pivot selection must be printed while solving.\r\n\t */\r\n\tpublic native void setTrace(boolean trace);\r\n\r\n\t/**\r\n\t * Returns a flag if pivot selection must be printed while solving.\r\n\t */\r\n\tpublic native boolean isTrace();\r\n\r\n\t/**\r\n\t * Sets a flag if Lagrangian progression must be printed while solving.\r\n\t */\r\n\tpublic native void setLagTrace(boolean lagTrace);\r\n\r\n\t/**\r\n\t * Returns a flag if Lagrangian progression must be printed while solving.\r\n\t */\r\n\tpublic native boolean isLagTrace();\r\n\r\n\t/**\r\n\t * Specifies which add routine performs best.\r\n\t */\r\n\tpublic native boolean setAddRowmode(boolean turnon);\r\n\r\n\t/**\r\n\t * Returns a flag which of the add routines perform best.\r\n\t */\r\n\tpublic native boolean isAddRowmode();\r\n\r\n\t/**\r\n\t * Specifies if special handling must be done to reduce degeneracy/cycling while solving.\r\n\t */\r\n\tpublic native void setAntiDegen(int antiDegen);\r\n\r\n\t/**\r\n\t * Returns if the degeneracy rule specified in testmask is active.\r\n\t */\r\n\tpublic native boolean isAntiDegen(int testmask);\r\n\r\n\t/**\r\n\t * Returns the used degeneracy rule.\r\n\t */\r\n\tpublic native int getAntiDegen();\r\n\r\n\t/**\r\n\t * Specifies if a presolve must be done before solving.\r\n\t */\r\n\tpublic native void setPresolve(int doPresolve, int maxloops);\r\n\r\n\t/**\r\n\t * Returns if presolve level specified in testmask is active.\r\n\t */\r\n\tpublic native boolean isPresolve(int testmask);\r\n\r\n\t/**\r\n\t * Returns the current presolve setting.\r\n\t */\r\n\tpublic native int getPresolve();\r\n\r\n\t/**\r\n\t * Returns the number of times presolve is done.\r\n\t */\r\n\tpublic native int getPresolveloops();\r\n\r\n\t/**\r\n\t * Sets the maximum number of pivots between a reinversion of the matrix.\r\n\t */\r\n\tpublic native void setMaxpivot(int maxNumInv);\r\n\r\n\t/**\r\n\t * Returns the maximum number of pivots between a reinversion of the matrix.\r\n\t */\r\n\tpublic native int getMaxpivot();\r\n\r\n\t/**\r\n\t * Specifies the branch-and-bound rule.\r\n\t */\r\n\tpublic native void setBbRule(int bbRule);\r\n\r\n\t/**\r\n\t * Returns the branch-and-bound rule.\r\n\t */\r\n\tpublic native int getBbRule();\r\n\r\n\t/**\r\n\t * Sets the maximum branch-and-bound depth.\r\n\t */\r\n\tpublic native void setBbDepthlimit(int bbMaxlevel);\r\n\r\n\t/**\r\n\t * Returns the maximum branch-and-bound depth.\r\n\t */\r\n\tpublic native int getBbDepthlimit();\r\n\r\n\t/**\r\n\t * Returns the number of equal solutions.\r\n\t */\r\n\tpublic native int getSolutioncount();\r\n\r\n\t/**\r\n\t * Sets the solution number that must be returned.\r\n\t */\r\n\tpublic native void setSolutionlimit(int limit);\r\n\r\n\t/**\r\n\t * Returns the solution number that must be returned.\r\n\t */\r\n\tpublic native int getSolutionlimit();\r\n\r\n\t/**\r\n\t * Set initial \"at least better than\" guess for objective function.\r\n\t */\r\n\tpublic native void setObjBound(double objBound);\r\n\r\n\t/**\r\n\t * Returns initial \"at least better than\" guess for objective function.\r\n\t */\r\n\tpublic native double getObjBound();\r\n\r\n\t/**\r\n\t * Specifies which branch to take first in branch-and-bound algorithm.\r\n\t */\r\n\tpublic native void setBbFloorfirst(int floorFirst);\r\n\r\n\t/**\r\n\t * Returns which branch to take first in branch-and-bound algorithm.\r\n\t */\r\n\tpublic native int getBbFloorfirst();\r\n\r\n\t/**\r\n\t * Specifies, for the specified variable, which branch to take first\r\n\t * in branch-and-bound algorithm.\r\n\t */\r\n\tpublic native void setVarBranch(int colnr, int branchMode) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns, for the specified variable, which branch to take first\r\n\t * in branch-and-bound algorithm.\r\n\t */\r\n\tpublic native int getVarBranch(int colnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set the weights on variables.\r\n\t */\r\n\tpublic native void setVarWeights(double[] weights) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns, for the specified variable, the priority the variable has\r\n\t * in the branch-and-bound algorithm.\r\n\t */\r\n\tpublic native int getVarPriority(int colnr) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Specifies if the branch-and-bound algorithm stops at first found solution.\r\n\t */\r\n\tpublic native void setBreakAtFirst(boolean breakAtFirst);\r\n\r\n\t/**\r\n\t * Returns if the branch-and-bound algorithm stops at first found solution.\r\n\t */\r\n\tpublic native boolean isBreakAtFirst();\r\n\r\n\t/**\r\n\t * Specifies if the branch-and-bound algorithm stops when the object value\r\n\t * is better than a given value.\r\n\t */\r\n\tpublic native void setBreakAtValue(double breakAtValue);\r\n\r\n\t/**\r\n\t * Returns the value at which the branch-and-bound algorithm stops\r\n\t * when the object value is better than this value.\r\n\t */\r\n\tpublic native double getBreakAtValue();\r\n\r\n\t/**\r\n\t * Specifies which scaling algorithm must be used.\r\n\t */\r\n\tpublic native void setScaling(int scalemode);\r\n\r\n\t/**\r\n\t * Specifies which scaling algorithm is used.\r\n\t */\r\n\tpublic native int getScaling();\r\n\r\n\t/**\r\n\t * Returns if scaling mode specified in testmask is active.\r\n\t */\r\n\tpublic native boolean isScalemode(int testmask);\r\n\r\n\t/**\r\n\t * Returns if scaling type specified in scaletype is active.\r\n\t */\r\n\tpublic native boolean isScaletype(int scaletype);\r\n\r\n\t/**\r\n\t * Specifies which scaling algorithm is used.\r\n\t */\r\n\tpublic native boolean isIntegerscaling();\r\n\r\n\t/**\r\n\t * Sets the relative scaling convergence criterion for the active scaling mode;\r\n\t * the integer part specifies the maximum number of iterations.\r\n\t */\r\n\tpublic native void setScalelimit(double scalelimit);\r\n\r\n\t/**\r\n\t * Returns the relative scaling convergence criterion for the active scaling mode;\r\n\t * the integer part specifies the maximum number of iterations.\r\n\t */\r\n\tpublic native double getScalelimit();\r\n\r\n\t/**\r\n\t * Specifies the iterative improvement level.\r\n\t */\r\n\tpublic native void setImprove(int improve);\r\n\r\n\t/**\r\n\t * Returns the iterative improvement level.\r\n\t */\r\n\tpublic native int getImprove();\r\n\r\n\t/**\r\n\t * Specifies the pivot rule.\r\n\t */\r\n\tpublic native void setPivoting(int pivRule);\r\n\r\n\t/**\r\n\t * Returns the pivot rule.\r\n\t */\r\n\tpublic native int getPivoting();\r\n\r\n\t/**\r\n\t * Returns if pivot strategy specified in testmask is active.\r\n\t */\r\n\tpublic native boolean isPivMode(int testmask);\r\n\r\n\t/**\r\n\t * Checks if the specified pivot rule is active.\r\n\t */\r\n\tpublic native boolean isPivRule(int rule);\r\n\r\n\t/**\r\n\t * Sets the desired combination of primal and dual simplex algorithms.\r\n\t */\r\n\tpublic native void setPreferdual(boolean dodual);\r\n\r\n\t/**\r\n\t * Sets the desired combination of primal and dual simplex algorithms.\r\n\t */\r\n\tpublic native void setSimplextype(int simplextype);\r\n\r\n\t/**\r\n\t * Returns the desired combination of primal and dual simplex algorithms.\r\n\t */\r\n\tpublic native int getSimplextype();\r\n\r\n\t/**\r\n\t * Set negative value below which variables are split into a negative\r\n\t * and a positive part.\r\n\t */\r\n\tpublic native void setNegrange(double negRange);\r\n\r\n\t/**\r\n\t * Returns the negative value below which variables are split\r\n\t * into a negative and a positive part.\r\n\t */\r\n\tpublic native double getNegrange();\r\n\r\n\t/**\r\n\t * Returns the total number of iterations with Branch-and-bound of the last solution.\r\n\t */\r\n\tpublic native long getTotalIter();\r\n\r\n\t/**\r\n\t * Returns the deepest Branch-and-bound level of the last solution.\r\n\t */\r\n\tpublic native int getMaxLevel();\r\n\r\n\t/**\r\n\t * Returns the total number of nodes processed in branch-and-bound.\r\n\t */\r\n\tpublic native long getTotalNodes();\r\n\r\n\t/**\r\n\t * Returns the number of rows (constraints) in the problem.\r\n\t */\r\n\tpublic native int getNrows();\r\n\r\n\t/**\r\n\t * Returns the number of original rows (constraints) in the problem.\r\n\t */\r\n\tpublic native int getNorigRows();\r\n\r\n\t/**\r\n\t * Returns the number of Lagrangian rows in the lp.\r\n\t */\r\n\tpublic native int getLrows();\r\n\r\n\t/**\r\n\t * Returns the number of columns (variables) in the problem.\r\n\t */\r\n\tpublic native int getNcolumns();\r\n\r\n\t/**\r\n\t * Returns the number of original columns (variables) in the problem.\r\n\t */\r\n\tpublic native int getNorigColumns();\r\n\r\n\t/**\r\n\t * Returns the number of non-zero elements in the matrix.\r\n\t */\r\n\tpublic native int getNonzeros();\r\n\r\n\t/**\r\n\t * Returns the original row/column where a constraint/variable was before presolve.\r\n\t */\r\n\tpublic native int getOrigIndex(int index);\r\n\r\n\t/**\r\n\t * Returns the index in the lp of the original row/column.\r\n\t */\r\n\tpublic native int getLpIndex(int index);\r\n\r\n\t/**\r\n\t * Sets an initial basis of the lp.\r\n\t */\r\n\tpublic native void setBasis(int[] bascolumn, boolean nonbasic) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Guess a basis for the lp.\r\n\t */\r\n\tpublic native void guessBasis(double[] guessvector, int[] basisvector) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the basis of the lp.\r\n\t */\r\n\tpublic native void getBasis(int[] bascolumn, boolean nonbasic) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Resets the basis to the initial basis.\r\n\t */\r\n\tpublic native void resetBasis();\r\n\r\n\t/**\r\n\t * Sets the starting base to an all slack basis (the default simplex starting basis).\r\n\t */\r\n\tpublic native void defaultBasis();\r\n\r\n\t/**\r\n\t * Specifies which basis crash mode must be used.\r\n\t */\r\n\tpublic native void setBasiscrash(int mode);\r\n\r\n\t/**\r\n\t * Returns which basis crash mode must be used.\r\n\t */\r\n\tpublic native int getBasiscrash();\r\n\r\n\t/**\r\n\t * Unscales the model.\r\n\t */\r\n\tpublic native void unscale();\r\n\r\n\t/**\r\n\t * Set basis factorization package.\r\n\t */\r\n\tpublic native void setBFP(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns if the native (build-in) basis factorization package (BFP) is used,\r\n\t * or an external package.\r\n\t */\r\n\tpublic native boolean isNativeBFP();\r\n\r\n\t/**\r\n\t * Returns if there is a basis factorization package (BFP) available.\r\n\t */\r\n\tpublic native boolean hasBFP();\r\n\r\n\t/**\r\n\t * Solve the model.\r\n\t */\r\n\tpublic native int solve() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Solve the model via Lagrangian relaxation.\r\n\t */\r\n\t/*\r\n\t * According to Peter Notebaert, this method is temporarily unavailable\r\n\t * but might be added again in later versions.\r\n\r\n\tpublic native int lagSolve(double startBound, int numIter) throws LpSolveException;\r\n\t*/\r\n\r\n\t/**\r\n\t * Returns the description of a returncode of the solve function.\r\n\t */\r\n\tpublic native String getStatustext(int statuscode);\r\n\r\n\t/**\r\n\t * Checks if provided solution is a feasible solution.\r\n\t */\r\n\tpublic native boolean isFeasible(double[] values, double threshold) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the value of the objective function.\r\n\t */\r\n\tpublic native double getObjective() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the value of the objective function.\r\n\t */\r\n\tpublic native double getWorkingObjective() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the values of the variables.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getVariables(double[] var) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the values of the variables.\r\n\t * Returned array is allocated by the method.\r\n\t */\r\n\tpublic native double[] getPtrVariables() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the values of the constraints.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getConstraints(double[] var) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the values of the constraints.\r\n\t * Returned array is allocated by the method.\r\n\t */\r\n\tpublic native double[] getPtrConstraints() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the solution of the model.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getPrimalSolution(double[] pv) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the solution of the model.\r\n\t * Returned array is allocated by the method.\r\n\t */\r\n\tpublic native double[] getPtrPrimalSolution() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the solution of the model.\r\n\t */\r\n\tpublic native double getVarPrimalresult(int index) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the constraints and the variables.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getSensitivityRhs(double[] duals, double[] dualsfrom, double[] dualstill) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the constraints and the variables.\r\n\t * Returned arrays are allocated by the method.\r\n\t * The returned array contains two elements of type double[].\r\n\t * element [0] is the duals array, element [1] is the dualsfrom array,\r\n\t * element [2] is the dualstill array.\r\n\t */\r\n\tpublic native double[][] getPtrSensitivityRhs() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the constraints and the variables.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getDualSolution(double[] duals) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the constraints and the variables.\r\n\t * Returned array is allocated by the method.\r\n\t */\r\n\tpublic native double[] getPtrDualSolution() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the constraints and the variables.\r\n\t */\r\n\tpublic native double getVarDualresult(int index) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the objective function.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getSensitivityObj(double[] objfrom, double[] objtill) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the objective function.\r\n\t * Returned arrays are allocated by the method.\r\n\t * The returned array contains two elements of type double[].\r\n\t * element [0] is the objfrom array, element [1] is the objtill array.\r\n\t */\r\n\tpublic native double[][] getPtrSensitivityObj() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the objective function.\r\n\t * Passed in arrays must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getSensitivityObjex(double[] objfrom, double[] objtill,\r\n\t\tdouble[] objfromvalue, double[] objtillvalue) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the sensitivity of the objective function.\r\n\t * Returned arrays are allocated by the method.\r\n\t * The returned array contains four elements of type double[].\r\n\t * element [0] is the objfrom array, element [1] is the objtill array,\r\n\t * element [2] is the objfromvalue array, element [3] is the objtillvalue array.\r\n\t */\r\n\tpublic native double[][] getPtrSensitivityObjex() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the Lamdba vectors (Lagrangian optimization).\r\n\t * Passed in array must be allocated by the caller of the method.\r\n\t */\r\n\tpublic native void getLambda(double[] lambda) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns the Lamdba vectors (Lagrangian optimization).\r\n\t * Returned array is allocated by the method.\r\n\t */\r\n\tpublic native double[] getPtrLambda() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Frees all resources allocated to this problem.\r\n\t */\r\n\tpublic native void deleteLp();\r\n\r\n\t/**\r\n\t * Write an lp model to a file.\r\n\t */\r\n\tpublic native void writeLp(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Write an mps model to a file.\r\n\t */\r\n\tpublic native void writeMps(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Write a model in free MPS format to a file.\r\n\t */\r\n\tpublic native void writeFreeMps(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Read basis from a file and set as default basis. The info text\r\n\t * is returned as method result.\r\n\t */\r\n\tpublic native String readBasis(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Writes current basis to a file.\r\n\t */\r\n\tpublic native void writeBasis(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Read settings from a parameter file.\r\n\t */\r\n\tpublic native void readParams(String filename, String options) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Write settings to a parameter file.\r\n\t */\r\n\tpublic native void writeParams(String filename, String options) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Resets parameters back to their default values.\r\n\t */\r\n\tpublic native void resetParams();\r\n\r\n\t/**\r\n\t * Prints the lp model. This function is meant for debugging purposes.\r\n\t * By default, the output is stdout. However this can be changed via a call\r\n\t * to setOutputfile.\r\n\t */\r\n\tpublic native void printLp();\r\n\r\n\t/**\r\n\t * Prints the values of the constraints of the lp.\r\n\t * This can only be done after a successful solve.\r\n\t * This function is meant for debugging purposes. By default, the output is stdout.\r\n\t * However this can be changed via a call to setOutputfile.\r\n\t */\r\n\tpublic native void printConstraints(int columns);\r\n\r\n\t/**\r\n\t * Prints the values of the duals of the lp.\r\n\t * This can only be done after a successful solve.\r\n\t * This function is meant for debugging purposes. By default, the output is stdout.\r\n\t * However this can be changed via a call to setOutputfile.\r\n\t */\r\n\tpublic native void printDuals();\r\n\r\n\t/**\r\n\t * Prints the scales of the lp.\r\n\t * This can only be done after a successful solve.\r\n\t * This function is meant for debugging purposes. By default, the output is stdout.\r\n\t * However this can be changed via a call to setOutputfile.\r\n\t */\r\n\tpublic native void printScales();\r\n\r\n\t/**\r\n\t * Prints the tableau.\r\n\t * This can only be done after a successful solve.\r\n\t * This function is meant for debugging purposes. By default, the output is stdout.\r\n\t * However this can be changed via a call to setOutputfile.\r\n\t */\r\n\tpublic native void printTableau();\r\n\r\n\t/**\r\n\t * Prints the objective value of the lp.\r\n\t * This can only be done after a successful solve.\r\n\t * This function is meant for debugging purposes. By default, the output is stdout.\r\n\t * However this can be changed via a call to setOutputfile.\r\n\t */\r\n\tpublic native void printObjective();\r\n\r\n\t/**\r\n\t * Prints the solution (variables) of the lp.\r\n\t * This can only be done after a successful solve.\r\n\t * This function is meant for debugging purposes. By default, the output is stdout.\r\n\t * However this can be changed via a call to setOutputfile.\r\n\t */\r\n\tpublic native void printSolution(int columns);\r\n\r\n\t/**\r\n\t * Prints a string.\r\n\t */\r\n\tpublic native void printStr(String str);\r\n\r\n\t/**\r\n\t * Defines the output for the print_* functions.\r\n\t */\r\n\tpublic native void setOutputfile(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Do a generic readable data dump of key lp_solve model variables;\r\n\t * principally for run difference and debugging purposes.\r\n\t */\r\n\tpublic native void printDebugdump(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Set External Language Interfaces package.\r\n\t */\r\n\tpublic native void setXLI(String filename) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Write a model to a file via the External Language Interface.\r\n\t */\r\n\tpublic native void writeXLI(String filename, String options, boolean results) throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns if there is an external language interface (XLI) set.\r\n\t */\r\n\tpublic native boolean hasXLI();\r\n\r\n\t/**\r\n\t * Returns if a build-in External Language Interfaces (XLI) is available or not.\r\n\t */\r\n\tpublic native boolean isNativeXLI();\r\n\r\n\t/**\r\n\t * Gets the index of a given column or row name in the lp.\r\n\t * A return value of -1 indicates that the name does not exist.\r\n\t */\r\n\tpublic native int getNameindex(String name, boolean isRow);\r\n\r\n\t/**\r\n\t * Create the dual of the current model.\r\n\t */\r\n\tpublic native void dualizeLp() throws LpSolveException;\r\n\r\n\t/**\r\n\t * Returns if variable or constraint names are used.\r\n\t */\r\n\tpublic native boolean isUseNames(boolean isRow);\r\n\r\n\t/**\r\n\t * Sets if variable or constraint names are used.\r\n\t */\r\n\tpublic native void setUseNames(boolean isRow, boolean useNames);\r\n\r\n\t/**\r\n\t * Gets the value of a constraint according to provided variable values.\r\n\t */\r\n\tpublic native double getConstrValue(int rownr, int count, double[] primsolution, int[] nzindex);\r\n\r\n\t/**\r\n\t * This is an internal function that has been published for special purposes. It should generally not be used.\r\n\t */\r\n\tpublic native int setBasisvar(int basisPos, int enteringCol);\r\n\r\n\r\n\t// ========================================================================\r\n\t// Callback methods.\r\n\t// ========================================================================\r\n\r\n\t/**\r\n\t * Calls the native lp_solve method <code>put_abortfunc</code>\r\n\t */\r\n\tprivate native void registerAbortfunc();\r\n\r\n\t/**\r\n\t * Register an <code>AbortListener</code> for callback.\r\n\t *\r\n\t * @param listener the listener that should be called by lp_solve\r\n\t * @param userhandle an arbitrary object that is passed to the listener on call\r\n\t */\r\n\tpublic void putAbortfunc(AbortListener listener, Object userhandle) throws LpSolveException {\r\n\t\tabortListener = listener;\r\n\t\tabortUserhandle = (listener != null) ? userhandle : null;\r\n\t\taddLp(this);\r\n\t\tregisterAbortfunc();\r\n\t}\r\n\r\n\t/**\r\n\t * Calls the native lp_solve method <code>put_logfunc</code>\r\n\t */\r\n\tprivate native void registerLogfunc();\r\n\r\n\t/**\r\n\t * Register an <code>LogListener</code> for callback.\r\n\t *\r\n\t * @param listener the listener that should be called by lp_solve\r\n\t * @param userhandle an arbitrary object that is passed to the listener on call\r\n\t */\r\n\tpublic void putLogfunc(LogListener listener, Object userhandle) throws LpSolveException {\r\n\t\tlogListener = listener;\r\n\t\tlogUserhandle = (listener != null) ? userhandle : null;\r\n\t\taddLp(this);\r\n\t\tregisterLogfunc();\r\n\t}\r\n\r\n\t/**\r\n\t * Calls the native lp_solve method <code>put_msgfunc</code>\r\n\t */\r\n\tprivate native void registerMsgfunc(int mask);\r\n\r\n\t/**\r\n\t * Register an <code>MsgListener</code> for callback.\r\n\t *\r\n\t * @param listener the listener that should be called by lp_solve\r\n\t * @param userhandle an arbitrary object that is passed to the listener on call\r\n\t */\r\n\tpublic void putMsgfunc(MsgListener listener, Object userhandle, int mask) throws LpSolveException {\r\n\t\tmsgListener = listener;\r\n\t\tmsgUserhandle = (listener != null) ? userhandle : null;\r\n\t\taddLp(this);\r\n\t\tregisterMsgfunc(mask);\r\n\t}\r\n\r\n\t/**\r\n\t * Calls the native lp_solve method <code>put_bb_branchfunc</code>\r\n\t */\r\n\tprivate native void registerBbBranchfunc();\r\n\r\n\t/**\r\n\t * Register an <code>BbBranchListener</code> for callback.\r\n\t *\r\n\t * @param listener the listener that should be called by lp_solve\r\n\t * @param userhandle an arbitrary object that is passed to the listener on call\r\n\t */\r\n\tpublic void putBbBranchfunc(BbListener listener, Object userhandle) throws LpSolveException {\r\n\t\tbbBranchListener = listener;\r\n\t\tbbBranchUserhandle = (listener != null) ? userhandle : null;\r\n\t\taddLp(this);\r\n\t\tregisterBbBranchfunc();\r\n\t}\r\n\r\n\t/**\r\n\t * Calls the native lp_solve method <code>put_bb_nodefunc</code>\r\n\t */\r\n\tprivate native void registerBbNodefunc();\r\n\r\n\t/**\r\n\t * Register an <code>BbNodeListener</code> for callback.\r\n\t *\r\n\t * @param listener the listener that should be called by lp_solve\r\n\t * @param userhandle an arbitrary object that is passed to the listener on call\r\n\t */\r\n\tpublic void putBbNodefunc(BbListener listener, Object userhandle) throws LpSolveException {\r\n\t\tbbNodeListener = listener;\r\n\t\tbbNodeUserhandle = (listener != null) ? userhandle : null;\r\n\t\taddLp(this);\r\n\t\tregisterBbNodefunc();\r\n\t}\r\n\r\n\t/**\r\n\t * Stores references to LpSolve objects. The key to this map\r\n\t * is the lp_solve lprec pointer value.\r\n\t */\r\n\tprivate static Map lpMap = new HashMap();\r\n\r\n\t/**\r\n\t * Adds a LpSolve object to the lpMap\r\n\t * @param problem the problem to add\r\n\t */\r\n\tprivate static synchronized void addLp(LpSolve problem) {\r\n\t\tlpMap.put(new Long(problem.lp), problem);\r\n\t}\r\n\r\n\t/**\r\n\t * Retrieves a LpSolve object from the lpMap.\r\n\t * @param lp lprec pointer value\r\n\t * @return the LpSolve object or null, if not found\r\n\t */\r\n\tprivate static synchronized LpSolve getLp(long lp) {\r\n\t\treturn (LpSolve)lpMap.get(new Long(lp));\r\n\t}\r\n\r\n\t/**\r\n\t * Removes a LpSolve object from the lpMap.\r\n\t * @param lp lprec pointer value\r\n\t */\r\n\tprivate static synchronized void removeLp(long lp) {\r\n\t\tlpMap.remove(new Long(lp));\r\n\t}\r\n\r\n\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/LpSolveException.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\t\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\npackage lpsolve;\r\n\r\n/**\r\n * Exception thrown by the native methods in the C stub DLL.\r\n * \r\n * @author Juergen Ebert\r\n */\r\npublic class LpSolveException extends Exception {\r\n\r\n\t/**\r\n\t * \r\n\t */\r\n\tpublic LpSolveException() {\r\n\t\tsuper();\r\n\t}\r\n\r\n\t/**\r\n\t * @param arg0\r\n\t */\r\n\tpublic LpSolveException(String arg0) {\r\n\t\tsuper(arg0);\r\n\t}\r\n\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/MsgListener.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\t\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\npackage lpsolve;\r\n\r\n/**\r\n * Classes that implement this interface may be passed\r\n * to the <code>putMsgfunc</code> method of the <code>LpSolve</code> class.\r\n * \r\n * @author Juergen Ebert\r\n * @see LpSolve#putMsgfunc\r\n * @see \"lp_solve documentation for 'put_msgfunc'\"\r\n */\r\npublic interface MsgListener {\r\n\r\n\t/**\r\n\t * This routine is called when a situation specified in the mask parameter\r\n\t * of putMsgfunc occurs. \r\n\t * Note that this routine is called while solving the model. \r\n\t * This can be usefull to follow the solving progress.\r\n\t *  \r\n\t * @param problem the problem this Listener was defined for\r\n\t * @param userhandle the userhandle object that was passed to <code>putMsgfunc</code>\r\n\t * @param msg event code why this method was called\r\n\t * @throws LpSolveException\r\n\t */\r\n\tpublic void msgfunc(LpSolve problem, Object userhandle, int msg) throws LpSolveException;\r\n\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/VersionInfo.java",
    "content": "/*\r\n\tThis software is a Java wrapper for the lp_solve optimization library.\r\n\t\r\n\tCopyright (C) 2004  Juergen Ebert (juergen.ebert@web.de)\r\n\r\n\tThis library is free software; you can redistribute it and/or\r\n\tmodify it under the terms of the GNU Lesser General Public\r\n\tLicense as published by the Free Software Foundation; either\r\n\tversion 2.1 of the License, or (at your option) any later version.\r\n\r\n\tThis library is distributed in the hope that it will be useful,\r\n\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n\tLesser General Public License for more details.\r\n\r\n\tYou should have received a copy of the GNU Lesser General Public\r\n\tLicense along with this library; if not, write to the Free Software\r\n\tFoundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n*/\r\n\r\npackage lpsolve;\r\n\r\n/**\r\n * Contains the full version info for a lp_solve library instance.\r\n * \r\n * @author Juergen Ebert\r\n */\r\npublic class VersionInfo {\r\n\t\r\n\tprivate int _majorversion;\r\n\tprivate int _minorversion;\r\n\tprivate int _release;\r\n\tprivate int _build;\r\n\r\n\t/**\r\n\t * Creates a new instance of this class\r\n\t */\r\n\tpublic VersionInfo(int major, int minor, int release, int build) {\r\n\t\t_majorversion = major;\r\n\t\t_minorversion = minor;\r\n\t\t_release = release;\r\n\t\t_build = build;\r\n\t}\r\n\r\n\t/**\r\n\t * @return value of the build attribute\r\n\t */\r\n\tpublic int getBuild() {\r\n\t\treturn _build;\r\n\t}\r\n\r\n\t/**\r\n\t * @return value of the majorversion attribute\r\n\t */\r\n\tpublic int getMajorversion() {\r\n\t\treturn _majorversion;\r\n\t}\r\n\r\n\t/**\r\n\t * @return value of the minorversion attribute\r\n\t */\r\n\tpublic int getMinorversion() {\r\n\t\treturn _minorversion;\r\n\t}\r\n\r\n\t/**\r\n\t * @return value of the release attribute\r\n\t */\r\n\tpublic int getRelease() {\r\n\t\treturn _release;\r\n\t}\r\n\r\n}\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/build",
    "content": ":\njavac *.java\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/build.bat",
    "content": "javac *.java\r\n"
  },
  {
    "path": "prism/ext/lp_solve_5.5_java/src/java/lpsolve/package.html",
    "content": "<!DOCTYPE HTML PUBLIC \"-//W3C//DTD HTML 3.2 Final//EN\">\r\n<HTML>\r\n<HEAD>\r\n<TITLE></TITLE>\r\n</HEAD>\r\n\r\n<BODY>\r\n<p>This package contains the files for the Java wrapper for the lp_solve optimization library.\r\nSee the file <a href=\"..\\..\\..\\README.html\">README.html</a> in the root direcory of the distribution\r\narchive for details.</p>\r\n</BODY>\r\n</HTML>\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/Makefile",
    "content": "################################################\n#  NB: This Makefile is designed to be called  #\n#      from the main PRISM Makefile. It won't  #\n#      work on its own because it needs        #\n#      various options to be passed in         #\n################################################\n\nifeq ($(OSTYPE),linux)\n\t  LPSOLVE55_BUILD=ccc\nendif\nifeq ($(OSTYPE),solaris)\n\t  LPSOLVE55_BUILD=ccc.solaris\nendif\nifeq ($(OSTYPE),cygwin)\n\t  LPSOLVE55_BUILD=ccc.cygwin\nendif\nifeq ($(OSTYPE),darwin)\n\tifeq ($(ARCH),x86_64)\n\t  LPSOLVE55_BUILD=ccc.osx64\n\telse\n\tifeq ($(ARCH),arm64)\n\t  LPSOLVE55_BUILD=ccc.osx64\n\telse\n\t  LPSOLVE55_BUILD=ccc.osx\n\tendif\n\tendif\nendif\n\ndefault: all\n\nall: checks ../../$(PRISM_LIB_DIR)/$(LIBPREFIX)lpsolve55$(LIBSUFFIX)\n\n# Try and prevent accidental makes (i.e. called manually, not from top-level Makefile)\nchecks:\n\t@if [ \"$(LIBSUFFIX)\" = \"\" ]; then \\\n\t  (echo \"Error: This Makefile is designed to be called from the main PRISM Makefile\"; exit 1) \\\n\tfi; \n\n../../$(PRISM_LIB_DIR)/$(LIBPREFIX)lpsolve55$(LIBSUFFIX):\n\tmkdir -p lib\n\t@(if [ \"$(OSTYPE)\" = \"cygwin\" ]; then \\\n\t  cp bin/$(BINDISTSUFFIX)/$(LIBPREFIX)lpsolve55$(LIBSUFFIX) ../../$(PRISM_LIB_DIR); \\\n\telse \\\n\t  (cd src/lp_solve_5.5/lpsolve55 && \\\n\t  ARCH=$(ARCH) c=$(CC) sh -x $(LPSOLVE55_BUILD) \\\n\t  ) && mv lib/$(LIBPREFIX)lpsolve55$(LIBSUFFIX) ../../$(PRISM_LIB_DIR)/; \\\n\tfi)\n\nclean: checks\n\trm -f lib/$(LIBPREFIX)lpsolve55$(LIBSUFFIX) ../../$(PRISM_LIB_DIR)/$(LIBPREFIX)lpsolve55$(LIBSUFFIX)\n\ncelan:\tclean\n\n#################################################\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/declare.h",
    "content": "#ifndef __DECLARE_H__\n#define __DECLARE_H__\n\n#if !defined ANSI_PROTOTYPES\n# if defined MSDOS || defined __BORLANDC__ || defined __HIGHC__ || defined SCO_UNIX || defined AViiON\n#  define ANSI_PROTOTYPES 1\n# endif\n#endif\n\n#if ANSI_PROTOTYPES!=0\n# define __OF(args)  args\n#else\n# define __OF(args)  ()\n#endif\n\n#if defined __HIGHC__\n# define VARARG    ...\n#else\n# define VARARG\n#endif\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/fortify.h",
    "content": "#ifndef __FORTIFY_H__\n#define __FORTIFY_H__\n/*\n * FILE:\n *   fortify.h\n *\n * DESCRIPTION:\n *     Header file for fortify.c - A fortified shell for malloc, realloc,\n *   calloc, strdup, getcwd, tempnam & free\n *\n * WRITTEN:\n *   spb 29/4/94\n *\n * VERSION:\n *   1.0 29/4/94\n */\n#include <stdlib.h>\n\n#include \"declare.h\"\n\n#if defined HP9000 || defined AViiON || defined ALPHA || defined SIGNED_UNKNOWN\n# define signed\n#endif\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n#ifdef FORTIFY\n\ntypedef void (*OutputFuncPtr) __OF((char *));\n\nextern char *_Fortify_file;\nextern int _Fortify_line;\n\n#define Fortify_FILE(file) _Fortify_file=file\n#define Fortify_LINE(line) _Fortify_line=line\n\n#define _Fortify_FILE (_Fortify_file==(char *) 0 ? __FILE__ : _Fortify_file)\n#define _Fortify_LINE (_Fortify_line==0 ? __LINE__ : _Fortify_line)\n\nvoid  _Fortify_Init __OF((char *file, unsigned long line));\nvoid *_Fortify_malloc __OF((size_t size, char *file, unsigned long line));\nvoid *_Fortify_realloc __OF((void *ptr, size_t new_size, char *file, unsigned long line));\nvoid *_Fortify_calloc __OF((size_t nitems, size_t size, char *file, unsigned long line));\nchar *_Fortify_strdup __OF((char *str, char *file, unsigned long line));\nvoid *_Fortify_memcpy __OF((void *to, void *from, size_t size, char *file, unsigned long line));\nvoid *_Fortify_memmove __OF((void *to, void *from, size_t size, char *file, unsigned long line));\nvoid *_Fortify_memccpy __OF((void *to, void *from, int c, size_t size, char *file, unsigned long line));\nvoid *_Fortify_memset __OF((void *buffer, int c, size_t size, char *file, unsigned long line));\nvoid *_Fortify_memchr __OF((void *buffer, int c, size_t size, char *file, unsigned long line));\nint   _Fortify_memcmp __OF((void *buffer1, void *buffer2, size_t size, char *file, unsigned long line));\nint   _Fortify_memicmp __OF((void *buffer1, void *buffer2, size_t size, char *file, unsigned long line));\nchar *_Fortify_strchr __OF((char *buffer, int c, char *file, unsigned long line));\nchar *_Fortify_strrchr __OF((char *buffer, int c, char *file, unsigned long line));\nchar *_Fortify_strlwr __OF((char *buffer, char *file, unsigned long line));\nchar *_Fortify_strupr __OF((char *buffer, char *file, unsigned long line));\nchar *_Fortify_strrev __OF((char *buffer, char *file, unsigned long line));\nchar *_Fortify_strset __OF((char *buffer, int c, char *file, unsigned long line));\nchar *_Fortify_strnset __OF((char *buffer, int c, size_t size, char *file, unsigned long line));\nchar *_Fortify_strstr __OF((char *to, char *from, char *file, unsigned long line));\nchar *_Fortify_strcpy __OF((char *to, char *from, char *file, unsigned long line));\nchar *_Fortify_strncpy __OF((char *to, char *from, size_t size, char *file, unsigned long line));\nint   _Fortify_strcmp __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\ndouble _Fortify_strtod __OF((char *buffer1, char **buffer2, char *file, unsigned long line));\nlong _Fortify_strtol __OF((char *buffer1, char **buffer2, int n, char *file, unsigned long line));\nint _Fortify_atoi __OF((char *buffer1, char *file, unsigned long line));\nlong _Fortify_atol __OF((char *buffer1, char *file, unsigned long line));\ndouble _Fortify_atof __OF((char *buffer1, char *file, unsigned long line));\nunsigned long _Fortify_strtoul __OF((char *buffer1, char **buffer2, int n, char *file, unsigned long line));\nsize_t _Fortify_strcspn __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nint   _Fortify_strcoll __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nint   _Fortify_strcmpi __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nint   _Fortify_strncmp __OF((char *buffer1, char *buffer2, size_t size, char *file, unsigned long line));\nint   _Fortify_strnicmp __OF((char *buffer1, char *buffer2, size_t size, char *file, unsigned long line));\nchar *_Fortify_strcat __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nchar *_Fortify_strpbrk __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nsize_t _Fortify_strlen __OF((char *buffer, char *file, unsigned long line));\nchar *_Fortify_getcwd __OF((char *buf, int size, char *file, unsigned long line));\nchar *_Fortify_tempnam __OF((char *dir, char *pfx, char *file, unsigned long line));\nvoid  _Fortify_free __OF((void *uptr, char *file, unsigned long line));\n\nint   _Fortify_OutputAllMemory __OF((char *file, unsigned long line));\nint   _Fortify_CheckAllMemory __OF((char *file, unsigned long line));\nint   _Fortify_CheckPointer __OF((void *uptr, char *file, unsigned long line));\nint   _Fortify_Disable __OF((char *file, unsigned long line, int how));\nint   _Fortify_SetMallocFailRate __OF((int Percent));\nint   _Fortify_EnterScope __OF((char *file, unsigned long line));\nint   _Fortify_LeaveScope __OF((char *file, unsigned long line));\nint   _Fortify_DumpAllMemory __OF((int scope, char *file, unsigned long line));\n\ntypedef void (*Fortify_OutputFuncPtr) __OF((/* const */ char *));\nFortify_OutputFuncPtr _Fortify_SetOutputFunc __OF((Fortify_OutputFuncPtr Output));\n\n#endif /* FORTIFY */\n\n#ifdef __cplusplus\n}\n#endif\n\n#ifndef __FORTIFY_C__ /* Only define the macros if we're NOT in fortify.c */\n\n#ifdef FORTIFY /* Add file and line information to the fortify calls */\n\n#if defined malloc\n# undef malloc\n#endif\n#if defined realloc\n# undef realloc\n#endif\n#if defined calloc\n# undef calloc\n#endif\n#if defined strdup\n# undef strdup\n#endif\n#if defined memcpy\n# undef memcpy\n#endif\n#if defined memmove\n# undef memmove\n#endif\n#if defined memccpy\n# undef memccpy\n#endif\n#if defined memset\n# undef memset\n#endif\n#if defined memchr\n# undef memchr\n#endif\n#if defined memcmp\n# undef memcmp\n#endif\n#if defined memicmp\n# undef memicmp\n#endif\n#if defined strcoll\n# undef strcoll\n#endif\n#if defined strcspn\n# undef strcspn\n#endif\n#if defined strcmp\n# undef strcmp\n#endif\n#if defined strcmpi\n# undef strcmpi\n#endif\n#if defined stricmp\n# undef stricmp\n#endif\n#if defined strncmp\n# undef strncmp\n#endif\n#if defined strnicmp\n# undef strnicmp\n#endif\n#if defined strlwr\n# undef strlwr\n#endif\n#if defined strupr\n# undef strupr\n#endif\n#if defined strrev\n# undef strrev\n#endif\n#if defined strchr\n# undef strchr\n#endif\n#if defined strrchr\n# undef strrchr\n#endif\n#if defined strcat\n# undef strcat\n#endif\n#if defined strpbrk\n# undef strpbrk\n#endif\n#if defined strcpy\n# undef strcpy\n#endif\n#if defined atoi\n# undef atoi\n#endif\n#if defined atol\n# undef atol\n#endif\n#if defined atof\n# undef atof\n#endif\n#if defined strtol\n# undef strtol\n#endif\n#if defined strtoul\n# undef strtoul\n#endif\n#if defined strtod\n# undef strtod\n#endif\n#if defined strstr\n# undef strstr\n#endif\n#if defined strncpy\n# undef strncpy\n#endif\n#if defined strset\n# undef strset\n#endif\n#if defined strnset\n# undef strnset\n#endif\n#if defined strlen\n# undef strlen\n#endif\n#if defined getcwd\n# undef getcwd\n#endif\n#if defined tempnam\n# undef tempnam\n#endif\n#if defined free\n# undef free\n#endif\n\n#define malloc(size)                  _Fortify_malloc(size, _Fortify_FILE, _Fortify_LINE)\n#define realloc(ptr,new_size)         _Fortify_realloc(ptr, new_size, _Fortify_FILE, _Fortify_LINE)\n#define calloc(num,size)              _Fortify_calloc(num, size, _Fortify_FILE, _Fortify_LINE)\n#define strdup(str)                   _Fortify_strdup(str, _Fortify_FILE, _Fortify_LINE)\n#define memcpy(to,from,size)          _Fortify_memcpy((void *)(to),(void *)(from),size, _Fortify_FILE, _Fortify_LINE)\n#define memmove(to,from,size)         _Fortify_memmove((void *)(to),(void *)(from),size, _Fortify_FILE, _Fortify_LINE)\n#define memccpy(to,from,c,size)       _Fortify_memccpy((void *)(to),(void *)(from),c,size, _Fortify_FILE, _Fortify_LINE)\n#define memset(buffer,c,size)         _Fortify_memset(buffer,c,size, _Fortify_FILE, _Fortify_LINE)\n#define memchr(buffer,c,size)         _Fortify_memchr(buffer,c,size, _Fortify_FILE, _Fortify_LINE)\n#define memcmp(buffer1,buffer2,size)  _Fortify_memcmp((void *)buffer1,(void *)buffer2,size, _Fortify_FILE, _Fortify_LINE)\n#define memicmp(buffer1,buffer2,size) _Fortify_memicmp((void *)buffer1,(void *)buffer2,size, _Fortify_FILE, _Fortify_LINE)\n#define strlwr(buffer)                _Fortify_strlwr(buffer, _Fortify_FILE, _Fortify_LINE)\n#define strupr(buffer)                _Fortify_strupr(buffer, _Fortify_FILE, _Fortify_LINE)\n#define strrev(buffer)                _Fortify_strrev(buffer, _Fortify_FILE, _Fortify_LINE)\n#define strchr(buffer,c)              _Fortify_strchr(buffer,c, _Fortify_FILE, _Fortify_LINE)\n#define strrchr(buffer,c)             _Fortify_strrchr(buffer,c, _Fortify_FILE, _Fortify_LINE)\n#define strset(buffer,c)              _Fortify_strset(buffer,c, _Fortify_FILE, _Fortify_LINE)\n#define strnset(buffer,c)             _Fortify_strnset(buffer,c, _Fortify_FILE, _Fortify_LINE)\n#define strstr(buffer1,buffer2)       _Fortify_strstr(buffer1,buffer2, _Fortify_FILE, _Fortify_LINE)\n#define atoi(buffer)                  _Fortify_atoi(buffer, _Fortify_FILE, _Fortify_LINE)\n#define atol(buffer)                  _Fortify_atol(buffer, _Fortify_FILE, _Fortify_LINE)\n#define atof(buffer)                  _Fortify_atof(buffer, _Fortify_FILE, _Fortify_LINE)\n#define strtol(buffer1,buffer2,n)     _Fortify_strtol(buffer1,buffer2,n, _Fortify_FILE, _Fortify_LINE)\n#define strtoul(buffer1,buffer2,n)    _Fortify_strtoul(buffer1,buffer2,n, _Fortify_FILE, _Fortify_LINE)\n#define strtod(buffer1,buffer2)       _Fortify_strtod(buffer1,buffer2, _Fortify_FILE, _Fortify_LINE)\n#define strcpy(to,from)               _Fortify_strcpy((char *)(to),(char *)(from), _Fortify_FILE, _Fortify_LINE)\n#define strncpy(to,from,size)         _Fortify_strncpy((char *)(to),(char *)(from),size, _Fortify_FILE, _Fortify_LINE)\n#define strcoll(buffer1,buffer2)      _Fortify_strcoll((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strcspn(buffer1,buffer2)      _Fortify_strcspn((char*)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strcmp(buffer1,buffer2)       _Fortify_strcmp((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strcmpi(buffer1,buffer2)      _Fortify_strcmpi((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define stricmp(buffer1,buffer2)      _Fortify_strcmpi((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strncmp(buffer1,buffer2,size) _Fortify_strncmp((char *)(buffer1),(char *)(buffer2),size, _Fortify_FILE, _Fortify_LINE)\n#define strnicmp(buffer1,buffer2,size) _Fortify_strnicmp((char *)(buffer1),(char *)(buffer2),size, _Fortify_FILE, _Fortify_LINE)\n#define strcat(buffer1,buffer2)       _Fortify_strcat((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strpbrk(buffer1,buffer2)      _Fortify_strpbrk((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strlen(buffer)                _Fortify_strlen((char*)(buffer), _Fortify_FILE, _Fortify_LINE)\n#define getcwd(buf,size)              _Fortify_getcwd(buf, size, _Fortify_FILE, _Fortify_LINE)\n#define tempnam(dir,pfx)              _Fortify_tempnam(dir, pfx, _Fortify_FILE, _Fortify_LINE)\n#define free(ptr)                     _Fortify_free(ptr, _Fortify_FILE, _Fortify_LINE)\n\n#define Fortify_Init()                _Fortify_Init(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_OutputAllMemory()     _Fortify_OutputAllMemory(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_CheckAllMemory()      _Fortify_CheckAllMemory(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_CheckPointer(ptr)     _Fortify_CheckPointer(ptr, _Fortify_FILE, _Fortify_LINE)\n#define Fortify_Disable(how)          _Fortify_Disable(_Fortify_FILE, _Fortify_LINE,how)\n#define Fortify_EnterScope()          _Fortify_EnterScope(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_LeaveScope()          _Fortify_LeaveScope(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_DumpAllMemory(s)      _Fortify_DumpAllMemory(s,_Fortify_FILE, _Fortify_LINE)\n\n#else /* FORTIFY Define the special fortify functions away to nothing */\n\n#define Fortify_FILE(file)\n#define Fortify_LINE(line)\n#define Fortify_Init()\n#define Fortify_OutputAllMemory()     0\n#define Fortify_CheckAllMemory()      0\n#define Fortify_CheckPointer(ptr)     1\n#define Fortify_Disable(how)          1\n#define Fortify_SetOutputFunc()       0\n#define Fortify_SetMallocFailRate(p)  0\n#define Fortify_EnterScope()          0\n#define Fortify_LeaveScope()          0\n#define Fortify_DumpAllMemory(s)      0\n\n#endif /*   FORTIFY     */\n#endif /* __FORTIFY_C__ */\n#endif /* __FORTIFY_H__ */\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/ini.h",
    "content": "#include <stdio.h>\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\nextern FILE *ini_create(char *filename);\nextern FILE *ini_open(char *filename);\nextern void ini_writecomment(FILE *fp, char *comment);\nextern void ini_writeheader(FILE *fp, char *header, int addnewline);\nextern void ini_writedata(FILE *fp, char *name, char *data);\nextern int ini_readdata(FILE *fp, char *data, int szdata, int withcomment);\nextern void ini_close(FILE *fp);\n\n#ifdef __cplusplus\n}\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_Hash.h",
    "content": "#ifndef HEADER_lp_hash\n#define HEADER_lp_hash\n\n/* For row and column name hash tables */\n\ntypedef struct _hashelem\n{\n  char             *name;\n  int               index;\n  struct _hashelem *next;\n  struct _hashelem *nextelem;\n} hashelem;\n\ntypedef struct /* _hashtable */\n{\n  hashelem         **table;\n  int              size;\n  int              base;\n  int              count;\n  struct _hashelem *first;\n  struct _hashelem *last;\n} hashtable;\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nSTATIC hashtable *create_hash_table(int size, int base);\nSTATIC void      free_hash_table(hashtable *ht);\nSTATIC hashelem  *findhash(const char *name, hashtable *ht);\nSTATIC hashelem  *puthash(const char *name, int index, hashelem **list, hashtable *ht);\nSTATIC void      drophash(const char *name, hashelem **list, hashtable *ht);\nSTATIC void      free_hash_item(hashelem **hp);\nSTATIC hashtable *copy_hash_table(hashtable *ht, hashelem **list, int newsize);\nSTATIC int find_var(lprec *lp, char *name, MYBOOL verbose);\nSTATIC int find_row(lprec *lp, char *name, MYBOOL Unconstrained_rows_found);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_hash */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_MDO.h",
    "content": "#ifndef HEADER_MDO\n#define HEADER_MDO\n\n#include \"lp_types.h\"\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nint __WINAPI getMDO(lprec *lp, MYBOOL *usedpos, int *colorder, int *size, MYBOOL symmetric);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_MDO */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_MPS.h",
    "content": "#ifndef HEADER_lp_MPS\n#define HEADER_lp_MPS\n\n#include \"lp_types.h\"\n\n/* For MPS file reading and writing */\n#define ROWNAMEMASK          \"R%d\"\n#define ROWNAMEMASK2         \"r%d\"\n#define COLNAMEMASK          \"C%d\"\n#define COLNAMEMASK2         \"c%d\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Read an MPS file */\nMYBOOL MPS_readfile(lprec **newlp, char *filename, int typeMPS, int verbose);\nMYBOOL __WINAPI MPS_readhandle(lprec **newlp, FILE *filehandle, int typeMPS, int verbose);\n\n/* Write a MPS file to output */\nMYBOOL MPS_writefile(lprec *lp, int typeMPS, char *filename);\nMYBOOL MPS_writehandle(lprec *lp, int typeMPS, FILE *output);\n\n/* Read and write BAS files */\nMYBOOL MPS_readBAS(lprec *lp, int typeMPS, char *filename, char *info);\nMYBOOL MPS_writeBAS(lprec *lp, int typeMPS, char *filename);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_MPS */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_SOS.h",
    "content": "#ifndef HEADER_lp_SOS\n#define HEADER_lp_SOS\n\n/* Specially Ordered Sets (SOS) prototypes and settings                      */\n/* ------------------------------------------------------------------------- */\n\n#include \"lp_types.h\"\n#include \"lp_utils.h\"\n#include \"lp_matrix.h\"\n\n\n/* SOS constraint defines                                                    */\n/* ------------------------------------------------------------------------- */\n#define SOS1                     1\n#define SOS2                     2\n#define SOS3                    -1\n#define SOSn                      MAXINT32\n#define SOS_START_SIZE          10  /* Start size of SOS_list array; realloced if needed */\n\n/* Define SOS_is_feasible() return values                                    */\n/* ------------------------------------------------------------------------- */\n#define SOS3_INCOMPLETE         -2\n#define SOS_INCOMPLETE          -1\n#define SOS_COMPLETE             0\n#define SOS_INFEASIBLE           1\n#define SOS_INTERNALERROR        2\n\n\ntypedef struct _SOSgroup SOSgroup;\n\ntypedef struct _SOSrec\n{\n  SOSgroup  *parent;\n  int       tagorder;\n  char      *name;\n  int       type;\n  MYBOOL    isGUB;\n  int       size;\n  int       priority;\n  int       *members;\n  REAL      *weights;\n  int       *membersSorted;\n  int       *membersMapped;\n} SOSrec;\n\n/* typedef */ struct _SOSgroup\n{\n  lprec     *lp;                /* Pointer to owner */\n  SOSrec    **sos_list;         /* Array of pointers to SOS lists */\n  int       sos_alloc;          /* Size allocated to specially ordered sets (SOS1, SOS2...) */\n  int       sos_count;          /* Number of specially ordered sets (SOS1, SOS2...) */\n  int       maxorder;           /* The highest-order SOS in the group */\n  int       sos1_count;         /* Number of the lowest order SOS in the group */\n  int       *membership;        /* Array of variable-sorted indeces to SOSes that the variable is member of */\n  int       *memberpos;         /* Starting positions of the each column's membership list */\n} /* SOSgroup */;\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* SOS storage structure */\nSTATIC SOSgroup *create_SOSgroup(lprec *lp);\nSTATIC void resize_SOSgroup(SOSgroup *group);\nSTATIC int append_SOSgroup(SOSgroup *group, SOSrec *SOS);\nSTATIC int clean_SOSgroup(SOSgroup *group, MYBOOL forceupdatemap);\nSTATIC void free_SOSgroup(SOSgroup **group);\n\nSTATIC SOSrec *create_SOSrec(SOSgroup *group, char *name, int type, int priority, int size, int *variables, REAL *weights);\nSTATIC MYBOOL delete_SOSrec(SOSgroup *group, int sosindex);\nSTATIC int append_SOSrec(SOSrec *SOS, int size, int *variables, REAL *weights);\nSTATIC void free_SOSrec(SOSrec *SOS);\n\n/* SOS utilities */\nSTATIC int make_SOSchain(lprec *lp, MYBOOL forceresort);\nSTATIC int SOS_member_updatemap(SOSgroup *group);\nSTATIC MYBOOL SOS_member_sortlist(SOSgroup *group, int sosindex);\nSTATIC MYBOOL SOS_shift_col(SOSgroup *group, int sosindex, int column, int delta, LLrec *usedmap, MYBOOL forceresort);\nint SOS_member_delete(SOSgroup *group, int sosindex, int member);\nint SOS_get_type(SOSgroup *group, int sosindex);\nint SOS_infeasible(SOSgroup *group, int sosindex);\nint SOS_member_index(SOSgroup *group, int sosindex, int member);\nint SOS_member_count(SOSgroup *group, int sosindex);\nint SOS_memberships(SOSgroup *group, int column);\nint *SOS_get_candidates(SOSgroup *group, int sosindex, int column, MYBOOL excludetarget, REAL *upbound, REAL *lobound);\nint SOS_is_member(SOSgroup *group, int sosindex, int column);\nMYBOOL SOS_is_member_of_type(SOSgroup *group, int column, int sostype);\nMYBOOL SOS_set_GUB(SOSgroup *group, int sosindex, MYBOOL state);\nMYBOOL SOS_is_GUB(SOSgroup *group, int sosindex);\nMYBOOL SOS_is_marked(SOSgroup *group, int sosindex, int column);\nMYBOOL SOS_is_active(SOSgroup *group, int sosindex, int column);\nMYBOOL SOS_is_full(SOSgroup *group, int sosindex, int column, MYBOOL activeonly);\nMYBOOL SOS_can_activate(SOSgroup *group, int sosindex, int column);\nMYBOOL SOS_set_marked(SOSgroup *group, int sosindex, int column, MYBOOL asactive);\nMYBOOL SOS_unmark(SOSgroup *group, int sosindex, int column);\nint SOS_fix_unmarked(SOSgroup *group, int sosindex, int variable, REAL *bound, REAL value,\n                     MYBOOL isupper, int *diffcount, DeltaVrec *changelog);\nint SOS_fix_list(SOSgroup *group, int sosindex, int variable, REAL *bound, \n                  int *varlist, MYBOOL isleft, DeltaVrec *changelog);\nint SOS_is_satisfied(SOSgroup *group, int sosindex, REAL *solution);\nMYBOOL SOS_is_feasible(SOSgroup *group, int sosindex, REAL *solution);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_SOS */\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_bit.h",
    "content": "#include \"lp_types.h\"\r\n\r\n#if defined INLINE\r\n# define MYINLINE INLINE\r\n#else\r\n# define MYINLINE static\r\n#endif\r\n\r\nMYINLINE void set_biton(MYBOOL *bitarray, int item)\r\n{\r\n  bitarray[item / 8] |= (1 << (item % 8));\r\n}\r\n\r\nMYINLINE void set_bitoff(MYBOOL *bitarray, int item)\r\n{\r\n  bitarray[item / 8] &= ~(1 << (item % 8));\r\n}\r\n\r\nMYINLINE MYBOOL is_biton(MYBOOL *bitarray, int item)\r\n{\r\n  return( (MYBOOL) ((bitarray[item / 8] & (1 << (item % 8))) != 0) );\r\n}\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_crash.h",
    "content": "\n#ifndef HEADER_lp_crash\n#define HEADER_lp_crash\n\n\n#include \"lp_types.h\"\n\n#define CRASH_SIMPLESCALE       /* Specify if we should use a simple absolute scaling threshold */\n\n#define CRASH_THRESHOLD  0.167\n#define CRASH_SPACER        10\n#define CRASH_WEIGHT     0.500\n\n\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\nSTATIC MYBOOL crash_basis(lprec *lp);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* HEADER_lp_crash */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_explicit.h",
    "content": "#define HEADER_lp_report\n\n#include \"lp_lib.h\"\n\n#if defined LPSOLVEAPIFROMLPRECDEF\n# define LPSOLVEAPIFROMLPREC\n# define LPSOLVEAPIDEF\n#endif\n\n#if defined LPSOLVEAPIFROMLIBDEF\n# define LPSOLVEAPIFROMLIB\n# define LPSOLVEAPIDEF\n#endif\n\n#if !defined LPSOLVEAPIDEF\n# define LPSOLVEAPIDEF extern\n#endif\n\n/* entries for lp structure */\nLPSOLVEAPIDEF add_column_func               *_add_column;\nLPSOLVEAPIDEF add_columnex_func             *_add_columnex;\nLPSOLVEAPIDEF add_constraint_func           *_add_constraint;\nLPSOLVEAPIDEF add_constraintex_func         *_add_constraintex;\nLPSOLVEAPIDEF add_lag_con_func              *_add_lag_con;\nLPSOLVEAPIDEF add_SOS_func                  *_add_SOS;\nLPSOLVEAPIDEF column_in_lp_func             *_column_in_lp;\nLPSOLVEAPIDEF copy_lp_func                  *_copy_lp;\nLPSOLVEAPIDEF default_basis_func            *_default_basis;\nLPSOLVEAPIDEF del_column_func               *_del_column;\nLPSOLVEAPIDEF del_constraint_func           *_del_constraint;\nLPSOLVEAPIDEF delete_lp_func                *_delete_lp;\nLPSOLVEAPIDEF dualize_lp_func               *_dualize_lp;\nLPSOLVEAPIDEF free_lp_func                  *_free_lp;\nLPSOLVEAPIDEF get_anti_degen_func           *_get_anti_degen;\nLPSOLVEAPIDEF get_basis_func                *_get_basis;\nLPSOLVEAPIDEF get_basiscrash_func           *_get_basiscrash;\nLPSOLVEAPIDEF get_bb_depthlimit_func        *_get_bb_depthlimit;\nLPSOLVEAPIDEF get_bb_floorfirst_func        *_get_bb_floorfirst;\nLPSOLVEAPIDEF get_bb_rule_func              *_get_bb_rule;\nLPSOLVEAPIDEF get_bounds_tighter_func       *_get_bounds_tighter;\nLPSOLVEAPIDEF get_break_at_value_func       *_get_break_at_value;\nLPSOLVEAPIDEF get_col_name_func             *_get_col_name;\nLPSOLVEAPIDEF get_column_func               *_get_column;\nLPSOLVEAPIDEF get_columnex_func             *_get_columnex;\nLPSOLVEAPIDEF get_constr_type_func          *_get_constr_type;\nLPSOLVEAPIDEF get_constr_value_func         *_get_constr_value;\nLPSOLVEAPIDEF get_constraints_func          *_get_constraints;\nLPSOLVEAPIDEF get_dual_solution_func        *_get_dual_solution;\nLPSOLVEAPIDEF get_epsb_func                 *_get_epsb;\nLPSOLVEAPIDEF get_epsd_func                 *_get_epsd;\nLPSOLVEAPIDEF get_epsel_func                *_get_epsel;\nLPSOLVEAPIDEF get_epsint_func               *_get_epsint;\nLPSOLVEAPIDEF get_epsperturb_func           *_get_epsperturb;\nLPSOLVEAPIDEF get_epspivot_func             *_get_epspivot;\nLPSOLVEAPIDEF get_improve_func              *_get_improve;\nLPSOLVEAPIDEF get_infinite_func             *_get_infinite;\nLPSOLVEAPIDEF get_lambda_func               *_get_lambda;\nLPSOLVEAPIDEF get_lowbo_func                *_get_lowbo;\nLPSOLVEAPIDEF get_lp_index_func             *_get_lp_index;\nLPSOLVEAPIDEF get_lp_name_func              *_get_lp_name;\nLPSOLVEAPIDEF get_Lrows_func                *_get_Lrows;\nLPSOLVEAPIDEF get_mat_func                  *_get_mat;\nLPSOLVEAPIDEF get_mat_byindex_func          *_get_mat_byindex;\nLPSOLVEAPIDEF get_max_level_func            *_get_max_level;\nLPSOLVEAPIDEF get_maxpivot_func             *_get_maxpivot;\nLPSOLVEAPIDEF get_mip_gap_func              *_get_mip_gap;\nLPSOLVEAPIDEF get_multiprice_func           *_get_multiprice;\nLPSOLVEAPIDEF get_nameindex_func            *_get_nameindex;\nLPSOLVEAPIDEF get_Ncolumns_func             *_get_Ncolumns;\nLPSOLVEAPIDEF get_negrange_func             *_get_negrange;\nLPSOLVEAPIDEF get_nz_func                   *_get_nonzeros;\nLPSOLVEAPIDEF get_Norig_columns_func        *_get_Norig_columns;\nLPSOLVEAPIDEF get_Norig_rows_func           *_get_Norig_rows;\nLPSOLVEAPIDEF get_Nrows_func                *_get_Nrows;\nLPSOLVEAPIDEF get_obj_bound_func            *_get_obj_bound;\nLPSOLVEAPIDEF get_objective_func            *_get_objective;\nLPSOLVEAPIDEF get_orig_index_func           *_get_orig_index;\nLPSOLVEAPIDEF get_origcol_name_func         *_get_origcol_name;\nLPSOLVEAPIDEF get_origrow_name_func         *_get_origrow_name;\nLPSOLVEAPIDEF get_partialprice_func         *_get_partialprice;\nLPSOLVEAPIDEF get_pivoting_func             *_get_pivoting;\nLPSOLVEAPIDEF get_presolve_func             *_get_presolve;\nLPSOLVEAPIDEF get_presolveloops_func        *_get_presolveloops;\nLPSOLVEAPIDEF get_primal_solution_func      *_get_primal_solution;\nLPSOLVEAPIDEF get_print_sol_func            *_get_print_sol;\nLPSOLVEAPIDEF get_pseudocosts_func          *_get_pseudocosts;\nLPSOLVEAPIDEF get_ptr_constraints_func      *_get_ptr_constraints;\nLPSOLVEAPIDEF get_ptr_dual_solution_func    *_get_ptr_dual_solution;\nLPSOLVEAPIDEF get_ptr_lambda_func           *_get_ptr_lambda;\nLPSOLVEAPIDEF get_ptr_primal_solution_func  *_get_ptr_primal_solution;\nLPSOLVEAPIDEF get_ptr_sensitivity_obj_func  *_get_ptr_sensitivity_obj;\nLPSOLVEAPIDEF get_ptr_sensitivity_objex_func *_get_ptr_sensitivity_objex;\nLPSOLVEAPIDEF get_ptr_sensitivity_rhs_func  *_get_ptr_sensitivity_rhs;\nLPSOLVEAPIDEF get_ptr_variables_func        *_get_ptr_variables;\nLPSOLVEAPIDEF get_rh_func                   *_get_rh;\nLPSOLVEAPIDEF get_rh_range_func             *_get_rh_range;\nLPSOLVEAPIDEF get_row_func                  *_get_row;\nLPSOLVEAPIDEF get_rowex_func                *_get_rowex;\nLPSOLVEAPIDEF get_row_name_func             *_get_row_name;\nLPSOLVEAPIDEF get_scalelimit_func           *_get_scalelimit;\nLPSOLVEAPIDEF get_scaling_func              *_get_scaling;\nLPSOLVEAPIDEF get_sensitivity_obj_func      *_get_sensitivity_obj;\nLPSOLVEAPIDEF get_sensitivity_objex_func    *_get_sensitivity_objex;\nLPSOLVEAPIDEF get_sensitivity_rhs_func      *_get_sensitivity_rhs;\nLPSOLVEAPIDEF get_simplextype_func          *_get_simplextype;\nLPSOLVEAPIDEF get_solutioncount_func        *_get_solutioncount;\nLPSOLVEAPIDEF get_solutionlimit_func        *_get_solutionlimit;\nLPSOLVEAPIDEF get_status_func               *_get_status;\nLPSOLVEAPIDEF get_statustext_func           *_get_statustext;\nLPSOLVEAPIDEF get_timeout_func              *_get_timeout;\nLPSOLVEAPIDEF get_total_iter_func           *_get_total_iter;\nLPSOLVEAPIDEF get_total_nodes_func          *_get_total_nodes;\nLPSOLVEAPIDEF get_upbo_func                 *_get_upbo;\nLPSOLVEAPIDEF get_var_branch_func           *_get_var_branch;\nLPSOLVEAPIDEF get_var_dualresult_func       *_get_var_dualresult;\nLPSOLVEAPIDEF get_var_primalresult_func     *_get_var_primalresult;\nLPSOLVEAPIDEF get_var_priority_func         *_get_var_priority;\nLPSOLVEAPIDEF get_variables_func            *_get_variables;\nLPSOLVEAPIDEF get_verbose_func              *_get_verbose;\nLPSOLVEAPIDEF get_working_objective_func    *_get_working_objective;\nLPSOLVEAPIDEF guess_basis_func              *_guess_basis;\nLPSOLVEAPIDEF has_BFP_func                  *_has_BFP;\nLPSOLVEAPIDEF has_XLI_func                  *_has_XLI;\nLPSOLVEAPIDEF is_add_rowmode_func           *_is_add_rowmode;\nLPSOLVEAPIDEF is_anti_degen_func            *_is_anti_degen;\nLPSOLVEAPIDEF is_binary_func                *_is_binary;\nLPSOLVEAPIDEF is_break_at_first_func        *_is_break_at_first;\nLPSOLVEAPIDEF is_constr_type_func           *_is_constr_type;\nLPSOLVEAPIDEF is_debug_func                 *_is_debug;\nLPSOLVEAPIDEF is_feasible_func              *_is_feasible;\nLPSOLVEAPIDEF is_unbounded_func             *_is_unbounded;\nLPSOLVEAPIDEF is_infinite_func              *_is_infinite;\nLPSOLVEAPIDEF is_int_func                   *_is_int;\nLPSOLVEAPIDEF is_integerscaling_func        *_is_integerscaling;\nLPSOLVEAPIDEF is_lag_trace_func             *_is_lag_trace;\nLPSOLVEAPIDEF is_maxim_func                 *_is_maxim;\nLPSOLVEAPIDEF is_nativeBFP_func             *_is_nativeBFP;\nLPSOLVEAPIDEF is_nativeXLI_func             *_is_nativeXLI;\nLPSOLVEAPIDEF is_negative_func              *_is_negative;\nLPSOLVEAPIDEF is_piv_mode_func              *_is_piv_mode;\nLPSOLVEAPIDEF is_piv_rule_func              *_is_piv_rule;\nLPSOLVEAPIDEF is_presolve_func              *_is_presolve;\nLPSOLVEAPIDEF is_scalemode_func             *_is_scalemode;\nLPSOLVEAPIDEF is_scaletype_func             *_is_scaletype;\nLPSOLVEAPIDEF is_semicont_func              *_is_semicont;\nLPSOLVEAPIDEF is_SOS_var_func               *_is_SOS_var;\nLPSOLVEAPIDEF is_trace_func                 *_is_trace;\nLPSOLVEAPIDEF is_use_names_func             *_is_use_names;\nLPSOLVEAPIDEF lp_solve_version_func         *_lp_solve_version;\nLPSOLVEAPIDEF make_lp_func                  *_make_lp;\nLPSOLVEAPIDEF print_constraints_func        *_print_constraints;\nLPSOLVEAPIDEF print_debugdump_func          *_print_debugdump;\nLPSOLVEAPIDEF print_duals_func              *_print_duals;\nLPSOLVEAPIDEF print_lp_func                 *_print_lp;\nLPSOLVEAPIDEF print_objective_func          *_print_objective;\nLPSOLVEAPIDEF print_scales_func             *_print_scales;\nLPSOLVEAPIDEF print_solution_func           *_print_solution;\nLPSOLVEAPIDEF print_str_func                *_print_str;\nLPSOLVEAPIDEF print_tableau_func            *_print_tableau;\nLPSOLVEAPIDEF put_abortfunc_func            *_put_abortfunc;\nLPSOLVEAPIDEF put_bb_nodefunc_func          *_put_bb_nodefunc;\nLPSOLVEAPIDEF put_bb_branchfunc_func        *_put_bb_branchfunc;\nLPSOLVEAPIDEF put_logfunc_func              *_put_logfunc;\nLPSOLVEAPIDEF put_msgfunc_func              *_put_msgfunc;\nLPSOLVEAPIDEF read_LP_func                  *_read_LP;\nLPSOLVEAPIDEF read_MPS_func                 *_read_MPS;\nLPSOLVEAPIDEF read_XLI_func                 *_read_XLI;\nLPSOLVEAPIDEF read_params_func              *_read_params;\nLPSOLVEAPIDEF read_basis_func               *_read_basis;\nLPSOLVEAPIDEF reset_basis_func              *_reset_basis;\nLPSOLVEAPIDEF reset_params_func             *_reset_params;\nLPSOLVEAPIDEF reportfunc                    *_report;\nLPSOLVEAPIDEF resize_lp_func                *_resize_lp;\nLPSOLVEAPIDEF set_add_rowmode_func          *_set_add_rowmode;\nLPSOLVEAPIDEF set_anti_degen_func           *_set_anti_degen;\nLPSOLVEAPIDEF set_basisvar_func             *_set_basisvar;\nLPSOLVEAPIDEF set_basis_func                *_set_basis;\nLPSOLVEAPIDEF set_basiscrash_func           *_set_basiscrash;\nLPSOLVEAPIDEF set_bb_depthlimit_func        *_set_bb_depthlimit;\nLPSOLVEAPIDEF set_bb_floorfirst_func        *_set_bb_floorfirst;\nLPSOLVEAPIDEF set_bb_rule_func              *_set_bb_rule;\nLPSOLVEAPIDEF set_BFP_func                  *_set_BFP;\nLPSOLVEAPIDEF set_binary_func               *_set_binary;\nLPSOLVEAPIDEF set_bounds_func               *_set_bounds;\nLPSOLVEAPIDEF set_bounds_tighter_func       *_set_bounds_tighter;\nLPSOLVEAPIDEF set_break_at_first_func       *_set_break_at_first;\nLPSOLVEAPIDEF set_break_at_value_func       *_set_break_at_value;\nLPSOLVEAPIDEF set_column_func               *_set_column;\nLPSOLVEAPIDEF set_columnex_func             *_set_columnex;\nLPSOLVEAPIDEF set_col_name_func             *_set_col_name;\nLPSOLVEAPIDEF set_constr_type_func          *_set_constr_type;\nLPSOLVEAPIDEF set_debug_func                *_set_debug;\nLPSOLVEAPIDEF set_epsb_func                 *_set_epsb;\nLPSOLVEAPIDEF set_epsd_func                 *_set_epsd;\nLPSOLVEAPIDEF set_epsel_func                *_set_epsel;\nLPSOLVEAPIDEF set_epsint_func               *_set_epsint;\nLPSOLVEAPIDEF set_epslevel_func             *_set_epslevel;\nLPSOLVEAPIDEF set_epsperturb_func           *_set_epsperturb;\nLPSOLVEAPIDEF set_epspivot_func             *_set_epspivot;\nLPSOLVEAPIDEF set_unbounded_func            *_set_unbounded;\nLPSOLVEAPIDEF set_improve_func              *_set_improve;\nLPSOLVEAPIDEF set_infinite_func             *_set_infinite;\nLPSOLVEAPIDEF set_int_func                  *_set_int;\nLPSOLVEAPIDEF set_lag_trace_func            *_set_lag_trace;\nLPSOLVEAPIDEF set_lowbo_func                *_set_lowbo;\nLPSOLVEAPIDEF set_lp_name_func              *_set_lp_name;\nLPSOLVEAPIDEF set_mat_func                  *_set_mat;\nLPSOLVEAPIDEF set_maxim_func                *_set_maxim;\nLPSOLVEAPIDEF set_maxpivot_func             *_set_maxpivot;\nLPSOLVEAPIDEF set_minim_func                *_set_minim;\nLPSOLVEAPIDEF set_mip_gap_func              *_set_mip_gap;\nLPSOLVEAPIDEF set_multiprice_func           *_set_multiprice;\nLPSOLVEAPIDEF set_negrange_func             *_set_negrange;\nLPSOLVEAPIDEF set_obj_bound_func            *_set_obj_bound;\nLPSOLVEAPIDEF set_obj_fn_func               *_set_obj_fn;\nLPSOLVEAPIDEF set_obj_fnex_func             *_set_obj_fnex;\nLPSOLVEAPIDEF set_obj_func                  *_set_obj;\nLPSOLVEAPIDEF set_outputfile_func           *_set_outputfile;\nLPSOLVEAPIDEF set_outputstream_func         *_set_outputstream;\nLPSOLVEAPIDEF set_partialprice_func         *_set_partialprice;\nLPSOLVEAPIDEF set_pivoting_func             *_set_pivoting;\nLPSOLVEAPIDEF set_preferdual_func           *_set_preferdual;\nLPSOLVEAPIDEF set_presolve_func             *_set_presolve;\nLPSOLVEAPIDEF set_print_sol_func            *_set_print_sol;\nLPSOLVEAPIDEF set_pseudocosts_func          *_set_pseudocosts;\nLPSOLVEAPIDEF set_rh_func                   *_set_rh;\nLPSOLVEAPIDEF set_rh_range_func             *_set_rh_range;\nLPSOLVEAPIDEF set_rh_vec_func               *_set_rh_vec;\nLPSOLVEAPIDEF set_row_func                  *_set_row;\nLPSOLVEAPIDEF set_rowex_func                *_set_rowex;\nLPSOLVEAPIDEF set_row_name_func             *_set_row_name;\nLPSOLVEAPIDEF set_scalelimit_func           *_set_scalelimit;\nLPSOLVEAPIDEF set_scaling_func              *_set_scaling;\nLPSOLVEAPIDEF set_semicont_func             *_set_semicont;\nLPSOLVEAPIDEF set_sense_func                *_set_sense;\nLPSOLVEAPIDEF set_simplextype_func          *_set_simplextype;\nLPSOLVEAPIDEF set_solutionlimit_func        *_set_solutionlimit;\nLPSOLVEAPIDEF set_timeout_func              *_set_timeout;\nLPSOLVEAPIDEF set_trace_func                *_set_trace;\nLPSOLVEAPIDEF set_upbo_func                 *_set_upbo;\nLPSOLVEAPIDEF set_var_branch_func           *_set_var_branch;\nLPSOLVEAPIDEF set_var_weights_func          *_set_var_weights;\nLPSOLVEAPIDEF set_verbose_func              *_set_verbose;\nLPSOLVEAPIDEF set_XLI_func                  *_set_XLI;\nLPSOLVEAPIDEF solve_func                    *_solve;\nLPSOLVEAPIDEF str_add_column_func           *_str_add_column;\nLPSOLVEAPIDEF str_add_constraint_func       *_str_add_constraint;\nLPSOLVEAPIDEF str_add_lag_con_func          *_str_add_lag_con;\nLPSOLVEAPIDEF str_set_obj_fn_func           *_str_set_obj_fn;\nLPSOLVEAPIDEF str_set_rh_vec_func           *_str_set_rh_vec;\nLPSOLVEAPIDEF time_elapsed_func             *_time_elapsed;\nLPSOLVEAPIDEF unscale_func                  *_unscale;\nLPSOLVEAPIDEF write_lp_func                 *_write_lp;\nLPSOLVEAPIDEF write_LP_func                 *_write_LP;\nLPSOLVEAPIDEF write_mps_func                *_write_mps;\nLPSOLVEAPIDEF write_MPS_func                *_write_MPS;\nLPSOLVEAPIDEF write_freemps_func            *_write_freemps;\nLPSOLVEAPIDEF write_freeMPS_func            *_write_freeMPS;\nLPSOLVEAPIDEF write_XLI_func                *_write_XLI;\nLPSOLVEAPIDEF write_basis_func              *_write_basis;\nLPSOLVEAPIDEF write_params_func             *_write_params;\n\n#if defined LPSOLVEAPIFROMLPREC\n\nstatic int init_lpsolve(lprec *lp)\n{\n  _add_column = lp->add_column;\n  _add_columnex = lp->add_columnex;\n  _add_constraint = lp->add_constraint;\n  _add_constraintex = lp->add_constraintex;\n  _add_lag_con = lp->add_lag_con;\n  _add_SOS = lp->add_SOS;\n  _column_in_lp = lp->column_in_lp;\n  _copy_lp = lp->copy_lp;\n  _default_basis = lp->default_basis;\n  _del_column = lp->del_column;\n  _del_constraint = lp->del_constraint;\n  _delete_lp = lp->delete_lp;\n  _dualize_lp = lp->dualize_lp;\n  _free_lp = lp->free_lp;\n  _get_anti_degen = lp->get_anti_degen;\n  _get_basis = lp->get_basis;\n  _get_basiscrash = lp->get_basiscrash;\n  _get_bb_depthlimit = lp->get_bb_depthlimit;\n  _get_bb_floorfirst = lp->get_bb_floorfirst;\n  _get_bb_rule = lp->get_bb_rule;\n  _get_bounds_tighter = lp->get_bounds_tighter;\n  _get_break_at_value = lp->get_break_at_value;\n  _get_col_name = lp->get_col_name;\n  _get_columnex = lp->get_columnex;\n  _get_constr_type = lp->get_constr_type;\n  _get_constr_value = lp->get_constr_value;\n  _get_constraints = lp->get_constraints;\n  _get_dual_solution = lp->get_dual_solution;\n  _get_epsb = lp->get_epsb;\n  _get_epsd = lp->get_epsd;\n  _get_epsel = lp->get_epsel;\n  _get_epsint = lp->get_epsint;\n  _get_epsperturb = lp->get_epsperturb;\n  _get_epspivot = lp->get_epspivot;\n  _get_improve = lp->get_improve;\n  _get_infinite = lp->get_infinite;\n  _get_lambda = lp->get_lambda;\n  _get_lowbo = lp->get_lowbo;\n  _get_lp_index = lp->get_lp_index;\n  _get_lp_name = lp->get_lp_name;\n  _get_Lrows = lp->get_Lrows;\n  _get_mat = lp->get_mat;\n  _get_mat_byindex = lp->get_mat_byindex;\n  _get_max_level = lp->get_max_level;\n  _get_maxpivot = lp->get_maxpivot;\n  _get_mip_gap = lp->get_mip_gap;\n  _get_multiprice = lp->get_multiprice;\n  _get_nameindex = lp->get_nameindex;\n  _get_Ncolumns = lp->get_Ncolumns;\n  _get_negrange = lp->get_negrange;\n  _get_nonzeros = lp->get_nonzeros;\n  _get_Norig_columns = lp->get_Norig_columns;\n  _get_Norig_rows = lp->get_Norig_rows;\n  _get_Nrows = lp->get_Nrows;\n  _get_obj_bound = lp->get_obj_bound;\n  _get_objective = lp->get_objective;\n  _get_orig_index = lp->get_orig_index;\n  _get_origcol_name = lp->get_origcol_name;\n  _get_origrow_name = lp->get_origrow_name;\n  _get_partialprice = lp->get_partialprice;\n  _get_pivoting = lp->get_pivoting;\n  _get_presolve = lp->get_presolve;\n  _get_presolveloops = lp->get_presolveloops;\n  _get_primal_solution = lp->get_primal_solution;\n  _get_print_sol = lp->get_print_sol;\n  _get_pseudocosts = lp->get_pseudocosts;\n  _get_ptr_constraints = lp->get_ptr_constraints;\n  _get_ptr_dual_solution = lp->get_ptr_dual_solution;\n  _get_ptr_lambda = lp->get_ptr_lambda;\n  _get_ptr_primal_solution = lp->get_ptr_primal_solution;\n  _get_ptr_sensitivity_obj = lp->get_ptr_sensitivity_obj;\n  _get_ptr_sensitivity_objex = lp->get_ptr_sensitivity_objex;\n  _get_ptr_sensitivity_rhs = lp->get_ptr_sensitivity_rhs;\n  _get_ptr_variables = lp->get_ptr_variables;\n  _get_rh = lp->get_rh;\n  _get_rh_range = lp->get_rh_range;\n  _get_row = lp->get_row;\n  _get_rowex = lp->get_rowex;\n  _get_row_name = lp->get_row_name;\n  _get_scalelimit = lp->get_scalelimit;\n  _get_scaling = lp->get_scaling;\n  _get_sensitivity_obj = lp->get_sensitivity_obj;\n  _get_sensitivity_objex = lp->get_sensitivity_objex;\n  _get_sensitivity_rhs = lp->get_sensitivity_rhs;\n  _get_simplextype = lp->get_simplextype;\n  _get_solutioncount = lp->get_solutioncount;\n  _get_solutionlimit = lp->get_solutionlimit;\n  _get_status = lp->get_status;\n  _get_statustext = lp->get_statustext;\n  _get_timeout = lp->get_timeout;\n  _get_total_iter = lp->get_total_iter;\n  _get_total_nodes = lp->get_total_nodes;\n  _get_upbo = lp->get_upbo;\n  _get_var_branch = lp->get_var_branch;\n  _get_var_dualresult = lp->get_var_dualresult;\n  _get_var_primalresult = lp->get_var_primalresult;\n  _get_var_priority = lp->get_var_priority;\n  _get_variables = lp->get_variables;\n  _get_verbose = lp->get_verbose;\n  _get_working_objective = lp->get_working_objective;\n  _has_BFP = lp->has_BFP;\n  _has_XLI = lp->has_XLI;\n  _is_add_rowmode = lp->is_add_rowmode;\n  _is_anti_degen = lp->is_anti_degen;\n  _is_binary = lp->is_binary;\n  _is_break_at_first = lp->is_break_at_first;\n  _is_constr_type = lp->is_constr_type;\n  _is_debug = lp->is_debug;\n  _is_feasible = lp->is_feasible;\n  _is_unbounded = lp->is_unbounded;\n  _is_infinite = lp->is_infinite;\n  _is_int = lp->is_int;\n  _is_integerscaling = lp->is_integerscaling;\n  _is_lag_trace = lp->is_lag_trace;\n  _is_maxim = lp->is_maxim;\n  _is_nativeBFP = lp->is_nativeBFP;\n  _is_nativeXLI = lp->is_nativeXLI;\n  _is_negative = lp->is_negative;\n  _is_piv_mode = lp->is_piv_mode;\n  _is_piv_rule = lp->is_piv_rule;\n  _is_presolve = lp->is_presolve;\n  _is_scalemode = lp->is_scalemode;\n  _is_scaletype = lp->is_scaletype;\n  _is_semicont = lp->is_semicont;\n  _is_SOS_var = lp->is_SOS_var;\n  _is_trace = lp->is_trace;\n  _is_use_names = lp->is_use_names;\n  _lp_solve_version = lp->lp_solve_version;\n  _make_lp = lp->make_lp;\n  _print_constraints = lp->print_constraints;\n  _print_debugdump = lp->print_debugdump;\n  _print_duals = lp->print_duals;\n  _print_lp = lp->print_lp;\n  _print_objective = lp->print_objective;\n  _print_scales = lp->print_scales;\n  _print_solution = lp->print_solution;\n  _print_str = lp->print_str;\n  _print_tableau = lp->print_tableau;\n  _put_abortfunc = lp->put_abortfunc;\n  _put_bb_nodefunc = lp->put_bb_nodefunc;\n  _put_bb_branchfunc = lp->put_bb_branchfunc;\n  _put_logfunc = lp->put_logfunc;\n  _put_msgfunc = lp->put_msgfunc;\n  _read_LP = lp->read_LP;\n  _read_MPS = lp->read_MPS;\n  _read_XLI = lp->read_XLI;\n  _read_params = lp->read_params;\n  _read_basis = lp->read_basis;\n  _reset_basis = lp->reset_basis;\n  _reset_params = lp->reset_params;\n  _report = lp->report;\n  _resize_lp = lp->resize_lp;\n  _set_add_rowmode = lp->set_add_rowmode;\n  _set_anti_degen = lp->set_anti_degen;\n  _set_basisvar = lp->set_basisvar;\n  _set_basis = lp->set_basis;\n  _set_basiscrash = lp->set_basiscrash;\n  _set_bb_depthlimit = lp->set_bb_depthlimit;\n  _set_bb_floorfirst = lp->set_bb_floorfirst;\n  _set_bb_rule = lp->set_bb_rule;\n  _set_BFP = lp->set_BFP;\n  _set_binary = lp->set_binary;\n  _set_bounds = lp->set_bounds;\n  _set_bounds_tighter = lp->set_bounds_tighter;\n  _set_break_at_first = lp->set_break_at_first;\n  _set_break_at_value = lp->set_break_at_value;\n  _set_column = lp->set_column;\n  _set_columnex = lp->set_columnex;\n  _set_col_name = lp->set_col_name;\n  _set_constr_type = lp->set_constr_type;\n  _set_debug = lp->set_debug;\n  _set_epsb = lp->set_epsb;\n  _set_epsd = lp->set_epsd;\n  _set_epsel = lp->set_epsel;\n  _set_epsint = lp->set_epsint;\n  _set_epslevel = lp->set_epslevel;\n  _set_epsperturb = lp->set_epsperturb;\n  _set_epspivot = lp->set_epspivot;\n  _set_unbounded = lp->set_unbounded;\n  _set_improve = lp->set_improve;\n  _set_infinite = lp->set_infinite;\n  _set_int = lp->set_int;\n  _set_lag_trace = lp->set_lag_trace;\n  _set_lowbo = lp->set_lowbo;\n  _set_lp_name = lp->set_lp_name;\n  _set_mat = lp->set_mat;\n  _set_maxim = lp->set_maxim;\n  _set_maxpivot = lp->set_maxpivot;\n  _set_minim = lp->set_minim;\n  _set_mip_gap = lp->set_mip_gap;\n  _set_multiprice = lp->set_multiprice;\n  _set_negrange = lp->set_negrange;\n  _set_obj_bound = lp->set_obj_bound;\n  _set_obj_fn = lp->set_obj_fn;\n  _set_obj_fnex = lp->set_obj_fnex;\n  _set_obj = lp->set_obj;\n  _set_outputfile = lp->set_outputfile;\n  _set_outputstream = lp->set_outputstream;\n  _set_partialprice = lp->set_partialprice;\n  _set_pivoting = lp->set_pivoting;\n  _set_preferdual = lp->set_preferdual;\n  _set_presolve = lp->set_presolve;\n  _set_print_sol = lp->set_print_sol;\n  _set_pseudocosts = lp->set_pseudocosts;\n  _set_rh = lp->set_rh;\n  _set_rh_range = lp->set_rh_range;\n  _set_rh_vec = lp->set_rh_vec;\n  _set_row = lp->set_row;\n  _set_rowex = lp->set_rowex;\n  _set_row_name = lp->set_row_name;\n  _set_scalelimit = lp->set_scalelimit;\n  _set_scaling = lp->set_scaling;\n  _set_semicont = lp->set_semicont;\n  _set_sense = lp->set_sense;\n  _set_simplextype = lp->set_simplextype;\n  _set_solutionlimit = lp->set_solutionlimit;\n  _set_timeout = lp->set_timeout;\n  _set_trace = lp->set_trace;\n  _set_upbo = lp->set_upbo;\n  _set_var_branch = lp->set_var_branch;\n  _set_var_weights = lp->set_var_weights;\n  _set_verbose = lp->set_verbose;\n  _set_XLI = lp->set_XLI;\n  _solve = lp->solve;\n  _str_add_column = lp->str_add_column;\n  _str_add_constraint = lp->str_add_constraint;\n  _str_add_lag_con = lp->str_add_lag_con;\n  _str_set_obj_fn = lp->str_set_obj_fn;\n  _str_set_rh_vec = lp->str_set_rh_vec;\n  _time_elapsed = lp->time_elapsed;\n  _unscale = lp->unscale;\n  _write_lp = lp->write_lp;\n  _write_LP = lp->write_LP;\n  _write_mps = lp->write_mps;\n  _write_MPS = lp->write_MPS;\n  _write_freemps = lp->write_freemps;\n  _write_freeMPS = lp->write_freeMPS;\n  _write_XLI = lp->write_XLI;\n  _write_basis = lp->write_basis;\n  _write_params = lp->write_params;\n\n  return(TRUE);\n}\n\n#elif defined LPSOLVEAPIFROMLIB\n\n#ifdef WIN32\n#  include <windows.h>\n#else\n#  include <dlfcn.h>\n#endif\n\n#if defined WIN32\n# define hlpsolve HINSTANCE\n#else\n# define hlpsolve void *\n#endif\n\nstatic hlpsolve open_lpsolve_lib(char *filename)\n{\n  hlpsolve lpsolve;\n\n# if defined WIN32\n  /* Get a handle to the Windows DLL module. */\n  lpsolve = LoadLibrary(\"lpsolve55.dll\");\n# else\n  lpsolve = dlopen(\"liblpsolve55.so\", RTLD_LAZY);;\n# endif\n  return(lpsolve);\n}\n\nstatic int close_lpsolve_lib(hlpsolve lpsolve)\n{\n#ifdef WIN32\n  FreeLibrary(lpsolve);\n#else\n  dlclose(lpsolve);\n#endif\n\n  return(TRUE);\n}\n\nstatic int init_lpsolve(hlpsolve lpsolve)\n{\n# if defined WIN32\n#   define AddressOf GetProcAddress\n# else\n#   define AddressOf dlsym\n# endif\n\n  /* assign API functions to lp structure */\n  _add_column = (add_column_func *) AddressOf(lpsolve, \"add_column\");\n  _add_columnex = (add_columnex_func *) AddressOf(lpsolve, \"add_columnex\");\n  _add_constraint = (add_constraint_func *) AddressOf(lpsolve, \"add_constraint\");\n  _add_constraintex = (add_constraintex_func *) AddressOf(lpsolve, \"add_constraintex\");\n  _add_lag_con = (add_lag_con_func *) AddressOf(lpsolve, \"add_lag_con\");\n  _add_SOS = (add_SOS_func *) AddressOf(lpsolve, \"add_SOS\");\n  _column_in_lp = (column_in_lp_func *) AddressOf(lpsolve, \"column_in_lp\");\n  _copy_lp = (copy_lp_func *) AddressOf(lpsolve, \"copy_lp\");\n  _default_basis = (default_basis_func *) AddressOf(lpsolve, \"default_basis\");\n  _del_column = (del_column_func *) AddressOf(lpsolve, \"del_column\");\n  _del_constraint = (del_constraint_func *) AddressOf(lpsolve, \"del_constraint\");\n  _delete_lp = (delete_lp_func *) AddressOf(lpsolve, \"delete_lp\");\n  _dualize_lp = (dualize_lp_func *) AddressOf(lpsolve, \"dualize_lp\");\n  _free_lp = (free_lp_func *) AddressOf(lpsolve, \"free_lp\");\n  _get_anti_degen = (get_anti_degen_func *) AddressOf(lpsolve, \"get_anti_degen\");\n  _get_basis = (get_basis_func *) AddressOf(lpsolve, \"get_basis\");\n  _get_basiscrash = (get_basiscrash_func *) AddressOf(lpsolve, \"get_basiscrash\");\n  _get_bb_depthlimit = (get_bb_depthlimit_func *) AddressOf(lpsolve, \"get_bb_depthlimit\");\n  _get_bb_floorfirst = (get_bb_floorfirst_func *) AddressOf(lpsolve, \"get_bb_floorfirst\");\n  _get_bb_rule = (get_bb_rule_func *) AddressOf(lpsolve, \"get_bb_rule\");\n  _get_bounds_tighter = (get_bounds_tighter_func *) AddressOf(lpsolve, \"get_bounds_tighter\");\n  _get_break_at_value = (get_break_at_value_func *) AddressOf(lpsolve, \"get_break_at_value\");\n  _get_col_name = (get_col_name_func *) AddressOf(lpsolve, \"get_col_name\");\n  _get_column = (get_column_func *) AddressOf(lpsolve, \"get_column\");\n  _get_columnex = (get_columnex_func *) AddressOf(lpsolve, \"get_columnex\");\n  _get_constr_type = (get_constr_type_func *) AddressOf(lpsolve, \"get_constr_type\");\n  _get_constr_value = (get_constr_value_func *) AddressOf(lpsolve, \"get_constr_value\");\n  _get_constraints = (get_constraints_func *) AddressOf(lpsolve, \"get_constraints\");\n  _get_dual_solution = (get_dual_solution_func *) AddressOf(lpsolve, \"get_dual_solution\");\n  _get_epsb = (get_epsb_func *) AddressOf(lpsolve, \"get_epsb\");\n  _get_epsd = (get_epsd_func *) AddressOf(lpsolve, \"get_epsd\");\n  _get_epsel = (get_epsel_func *) AddressOf(lpsolve, \"get_epsel\");\n  _get_epsint = (get_epsint_func *) AddressOf(lpsolve, \"get_epsint\");\n  _get_epsperturb = (get_epsperturb_func *) AddressOf(lpsolve, \"get_epsperturb\");\n  _get_epspivot = (get_epspivot_func *) AddressOf(lpsolve, \"get_epspivot\");\n  _get_improve = (get_improve_func *) AddressOf(lpsolve, \"get_improve\");\n  _get_infinite = (get_infinite_func *) AddressOf(lpsolve, \"get_infinite\");\n  _get_lambda = (get_lambda_func *) AddressOf(lpsolve, \"get_lambda\");\n  _get_lowbo = (get_lowbo_func *) AddressOf(lpsolve, \"get_lowbo\");\n  _get_lp_index = (get_lp_index_func *) AddressOf(lpsolve, \"get_lp_index\");\n  _get_lp_name = (get_lp_name_func *) AddressOf(lpsolve, \"get_lp_name\");\n  _get_Lrows = (get_Lrows_func *) AddressOf(lpsolve, \"get_Lrows\");\n  _get_mat = (get_mat_func *) AddressOf(lpsolve, \"get_mat\");\n  _get_mat_byindex = (get_mat_byindex_func *) AddressOf(lpsolve, \"get_mat_byindex\");\n  _get_max_level = (get_max_level_func *) AddressOf(lpsolve, \"get_max_level\");\n  _get_maxpivot = (get_maxpivot_func *) AddressOf(lpsolve, \"get_maxpivot\");\n  _get_mip_gap = (get_mip_gap_func *) AddressOf(lpsolve, \"get_mip_gap\");\n  _get_multiprice = (get_multiprice_func *) AddressOf(lpsolve, \"get_multiprice\");\n  _get_nameindex = (get_nameindex_func *) AddressOf(lpsolve, \"get_nameindex\");\n  _get_Ncolumns = (get_Ncolumns_func *) AddressOf(lpsolve, \"get_Ncolumns\");\n  _get_negrange = (get_negrange_func *) AddressOf(lpsolve, \"get_negrange\");\n  _get_nonzeros = (get_nz_func *) AddressOf(lpsolve, \"get_nonzeros\");\n  _get_Norig_columns = (get_Norig_columns_func *) AddressOf(lpsolve, \"get_Norig_columns\");\n  _get_Norig_rows = (get_Norig_rows_func *) AddressOf(lpsolve, \"get_Norig_rows\");\n  _get_Nrows = (get_Nrows_func *) AddressOf(lpsolve, \"get_Nrows\");\n  _get_obj_bound = (get_obj_bound_func *) AddressOf(lpsolve, \"get_obj_bound\");\n  _get_objective = (get_objective_func *) AddressOf(lpsolve, \"get_objective\");\n  _get_orig_index = (get_orig_index_func *) AddressOf(lpsolve, \"get_orig_index\");\n  _get_origcol_name = (get_origcol_name_func *) AddressOf(lpsolve, \"get_origcol_name\");\n  _get_origrow_name = (get_origrow_name_func *) AddressOf(lpsolve, \"get_origrow_name\");\n  _get_partialprice = (get_partialprice_func *) AddressOf(lpsolve, \"get_partialprice\");\n  _get_pivoting = (get_pivoting_func *) AddressOf(lpsolve, \"get_pivoting\");\n  _get_presolve = (get_presolve_func *) AddressOf(lpsolve, \"get_presolve\");\n  _get_presolveloops = (get_presolveloops_func *) AddressOf(lpsolve, \"get_presolveloops\");\n  _get_primal_solution = (get_primal_solution_func *) AddressOf(lpsolve, \"get_primal_solution\");\n  _get_print_sol = (get_print_sol_func *) AddressOf(lpsolve, \"get_print_sol\");\n  _get_pseudocosts = (get_pseudocosts_func *) AddressOf(lpsolve, \"get_pseudocosts\");\n  _get_ptr_constraints = (get_ptr_constraints_func *) AddressOf(lpsolve, \"get_ptr_constraints\");\n  _get_ptr_dual_solution = (get_ptr_dual_solution_func *) AddressOf(lpsolve, \"get_ptr_dual_solution\");\n  _get_ptr_lambda = (get_ptr_lambda_func *) AddressOf(lpsolve, \"get_ptr_lambda\");\n  _get_ptr_primal_solution = (get_ptr_primal_solution_func *) AddressOf(lpsolve, \"get_ptr_primal_solution\");\n  _get_ptr_sensitivity_obj = (get_ptr_sensitivity_obj_func *) AddressOf(lpsolve, \"get_ptr_sensitivity_obj\");\n  _get_ptr_sensitivity_objex = (get_ptr_sensitivity_objex_func *) AddressOf(lpsolve, \"get_ptr_sensitivity_objex\");\n  _get_ptr_sensitivity_rhs = (get_ptr_sensitivity_rhs_func *) AddressOf(lpsolve, \"get_ptr_sensitivity_rhs\");\n  _get_ptr_variables = (get_ptr_variables_func *) AddressOf(lpsolve, \"get_ptr_variables\");\n  _get_rh = (get_rh_func *) AddressOf(lpsolve, \"get_rh\");\n  _get_rh_range = (get_rh_range_func *) AddressOf(lpsolve, \"get_rh_range\");\n  _get_row = (get_row_func *) AddressOf(lpsolve, \"get_row\");\n  _get_rowex = (get_rowex_func *) AddressOf(lpsolve, \"get_rowex\");\n  _get_row_name = (get_row_name_func *) AddressOf(lpsolve, \"get_row_name\");\n  _get_scalelimit = (get_scalelimit_func *) AddressOf(lpsolve, \"get_scalelimit\");\n  _get_scaling = (get_scaling_func *) AddressOf(lpsolve, \"get_scaling\");\n  _get_sensitivity_obj = (get_sensitivity_obj_func *) AddressOf(lpsolve, \"get_sensitivity_obj\");\n  _get_sensitivity_objex = (get_sensitivity_objex_func *) AddressOf(lpsolve, \"get_sensitivity_objex\");\n  _get_sensitivity_rhs = (get_sensitivity_rhs_func *) AddressOf(lpsolve, \"get_sensitivity_rhs\");\n  _get_simplextype = (get_simplextype_func *) AddressOf(lpsolve, \"get_simplextype\");\n  _get_solutioncount = (get_solutioncount_func *) AddressOf(lpsolve, \"get_solutioncount\");\n  _get_solutionlimit = (get_solutionlimit_func *) AddressOf(lpsolve, \"get_solutionlimit\");\n  _get_status = (get_status_func *) AddressOf(lpsolve, \"get_status\");\n  _get_statustext = (get_statustext_func *) AddressOf(lpsolve, \"get_statustext\");\n  _get_timeout = (get_timeout_func *) AddressOf(lpsolve, \"get_timeout\");\n  _get_total_iter = (get_total_iter_func *) AddressOf(lpsolve, \"get_total_iter\");\n  _get_total_nodes = (get_total_nodes_func *) AddressOf(lpsolve, \"get_total_nodes\");\n  _get_upbo = (get_upbo_func *) AddressOf(lpsolve, \"get_upbo\");\n  _get_var_branch = (get_var_branch_func *) AddressOf(lpsolve, \"get_var_branch\");\n  _get_var_dualresult = (get_var_dualresult_func *) AddressOf(lpsolve, \"get_var_dualresult\");\n  _get_var_primalresult = (get_var_primalresult_func *) AddressOf(lpsolve, \"get_var_primalresult\");\n  _get_var_priority = (get_var_priority_func *) AddressOf(lpsolve, \"get_var_priority\");\n  _get_variables = (get_variables_func *) AddressOf(lpsolve, \"get_variables\");\n  _get_verbose = (get_verbose_func *) AddressOf(lpsolve, \"get_verbose\");\n  _get_working_objective = (get_working_objective_func *) AddressOf(lpsolve, \"get_working_objective\");\n  _guess_basis = (guess_basis_func *) AddressOf(lpsolve, \"guess_basis\");\n  _has_BFP = (has_BFP_func *) AddressOf(lpsolve, \"has_BFP\");\n  _has_XLI = (has_XLI_func *) AddressOf(lpsolve, \"has_XLI\");\n  _is_add_rowmode = (is_add_rowmode_func *) AddressOf(lpsolve, \"is_add_rowmode\");\n  _is_anti_degen = (is_anti_degen_func *) AddressOf(lpsolve, \"is_anti_degen\");\n  _is_binary = (is_binary_func *) AddressOf(lpsolve, \"is_binary\");\n  _is_break_at_first = (is_break_at_first_func *) AddressOf(lpsolve, \"is_break_at_first\");\n  _is_constr_type = (is_constr_type_func *) AddressOf(lpsolve, \"is_constr_type\");\n  _is_debug = (is_debug_func *) AddressOf(lpsolve, \"is_debug\");\n  _is_feasible = (is_feasible_func *) AddressOf(lpsolve, \"is_feasible\");\n  _is_unbounded = (is_unbounded_func *) AddressOf(lpsolve, \"is_unbounded\");\n  _is_infinite = (is_infinite_func *) AddressOf(lpsolve, \"is_infinite\");\n  _is_int = (is_int_func *) AddressOf(lpsolve, \"is_int\");\n  _is_integerscaling = (is_integerscaling_func *) AddressOf(lpsolve, \"is_integerscaling\");\n  _is_lag_trace = (is_lag_trace_func *) AddressOf(lpsolve, \"is_lag_trace\");\n  _is_maxim = (is_maxim_func *) AddressOf(lpsolve, \"is_maxim\");\n  _is_nativeBFP = (is_nativeBFP_func *) AddressOf(lpsolve, \"is_nativeBFP\");\n  _is_nativeXLI = (is_nativeXLI_func *) AddressOf(lpsolve, \"is_nativeXLI\");\n  _is_negative = (is_negative_func *) AddressOf(lpsolve, \"is_negative\");\n  _is_piv_mode = (is_piv_mode_func *) AddressOf(lpsolve, \"is_piv_mode\");\n  _is_piv_rule = (is_piv_rule_func *) AddressOf(lpsolve, \"is_piv_rule\");\n  _is_presolve = (is_presolve_func *) AddressOf(lpsolve, \"is_presolve\");\n  _is_scalemode = (is_scalemode_func *) AddressOf(lpsolve, \"is_scalemode\");\n  _is_scaletype = (is_scaletype_func *) AddressOf(lpsolve, \"is_scaletype\");\n  _is_semicont = (is_semicont_func *) AddressOf(lpsolve, \"is_semicont\");\n  _is_SOS_var = (is_SOS_var_func *) AddressOf(lpsolve, \"is_SOS_var\");\n  _is_trace = (is_trace_func *) AddressOf(lpsolve, \"is_trace\");\n  _is_use_names = (is_use_names_func *) AddressOf(lpsolve, \"is_use_names\");\n  _lp_solve_version = (lp_solve_version_func *) AddressOf(lpsolve, \"lp_solve_version\");\n  _make_lp = (make_lp_func *) AddressOf(lpsolve, \"make_lp\");\n  _print_constraints = (print_constraints_func *) AddressOf(lpsolve, \"print_constraints\");\n  _print_debugdump = (print_debugdump_func *) AddressOf(lpsolve, \"print_debugdump\");\n  _print_duals = (print_duals_func *) AddressOf(lpsolve, \"print_duals\");\n  _print_lp = (print_lp_func *) AddressOf(lpsolve, \"print_lp\");\n  _print_objective = (print_objective_func *) AddressOf(lpsolve, \"print_objective\");\n  _print_scales = (print_scales_func *) AddressOf(lpsolve, \"print_scales\");\n  _print_solution = (print_solution_func *) AddressOf(lpsolve, \"print_solution\");\n  _print_str = (print_str_func *) AddressOf(lpsolve, \"print_str\");\n  _print_tableau = (print_tableau_func *) AddressOf(lpsolve, \"print_tableau\");\n  _put_abortfunc = (put_abortfunc_func *) AddressOf(lpsolve, \"put_abortfunc\");\n  _put_bb_nodefunc = (put_bb_nodefunc_func *) AddressOf(lpsolve, \"put_bb_nodefunc\");\n  _put_bb_branchfunc = (put_bb_branchfunc_func *) AddressOf(lpsolve, \"put_bb_branchfunc\");\n  _put_logfunc = (put_logfunc_func *) AddressOf(lpsolve, \"put_logfunc\");\n  _put_msgfunc = (put_msgfunc_func *) AddressOf(lpsolve, \"put_msgfunc\");\n  _read_LP = (read_LP_func *) AddressOf(lpsolve, \"read_LP\");\n  _read_MPS = (read_MPS_func *) AddressOf(lpsolve, \"read_MPS\");\n  _read_XLI = (read_XLI_func *) AddressOf(lpsolve, \"read_XLI\");\n  _read_params = (read_params_func *) AddressOf(lpsolve, \"read_params\");\n  _read_basis = (read_basis_func *) AddressOf(lpsolve, \"read_basis\");\n  _reset_basis = (reset_basis_func *) AddressOf(lpsolve, \"reset_basis\");\n  _reset_params = (reset_params_func *) AddressOf(lpsolve, \"reset_params\");\n  _report = (reportfunc *) AddressOf(lpsolve, \"report\");\n  _resize_lp = (resize_lp_func *) AddressOf(lpsolve, \"resize_lp\");\n  _set_add_rowmode = (set_add_rowmode_func *) AddressOf(lpsolve, \"set_add_rowmode\");\n  _set_anti_degen = (set_anti_degen_func *) AddressOf(lpsolve, \"set_anti_degen\");\n  _set_basisvar = (set_basisvar_func *) AddressOf(lpsolve, \"set_basisvar\");\n  _set_basis = (set_basis_func *) AddressOf(lpsolve, \"set_basis\");\n  _set_basiscrash = (set_basiscrash_func *) AddressOf(lpsolve, \"set_basiscrash\");\n  _set_bb_depthlimit = (set_bb_depthlimit_func *) AddressOf(lpsolve, \"set_bb_depthlimit\");\n  _set_bb_floorfirst = (set_bb_floorfirst_func *) AddressOf(lpsolve, \"set_bb_floorfirst\");\n  _set_bb_rule = (set_bb_rule_func *) AddressOf(lpsolve, \"set_bb_rule\");\n  _set_BFP = (set_BFP_func *) AddressOf(lpsolve, \"set_BFP\");\n  _set_binary = (set_binary_func *) AddressOf(lpsolve, \"set_binary\");\n  _set_bounds = (set_bounds_func *) AddressOf(lpsolve, \"set_bounds\");\n  _set_bounds_tighter = (set_bounds_tighter_func *) AddressOf(lpsolve, \"set_bounds_tighter\");\n  _set_break_at_first = (set_break_at_first_func *) AddressOf(lpsolve, \"set_break_at_first\");\n  _set_break_at_value = (set_break_at_value_func *) AddressOf(lpsolve, \"set_break_at_value\");\n  _set_column = (set_column_func *) AddressOf(lpsolve, \"set_column\");\n  _set_columnex = (set_columnex_func *) AddressOf(lpsolve, \"set_columnex\");\n  _set_col_name = (set_col_name_func *) AddressOf(lpsolve, \"set_col_name\");\n  _set_constr_type = (set_constr_type_func *) AddressOf(lpsolve, \"set_constr_type\");\n  _set_debug = (set_debug_func *) AddressOf(lpsolve, \"set_debug\");\n  _set_epsb = (set_epsb_func *) AddressOf(lpsolve, \"set_epsb\");\n  _set_epsd = (set_epsd_func *) AddressOf(lpsolve, \"set_epsd\");\n  _set_epsel = (set_epsel_func *) AddressOf(lpsolve, \"set_epsel\");\n  _set_epsint = (set_epsint_func *) AddressOf(lpsolve, \"set_epsint\");\n  _set_epslevel = (set_epslevel_func *) AddressOf(lpsolve, \"set_epslevel\");\n  _set_epsperturb = (set_epsperturb_func *) AddressOf(lpsolve, \"set_epsperturb\");\n  _set_epspivot = (set_epspivot_func *) AddressOf(lpsolve, \"set_epspivot\");\n  _set_unbounded = (set_unbounded_func *) AddressOf(lpsolve, \"set_unbounded\");\n  _set_improve = (set_improve_func *) AddressOf(lpsolve, \"set_improve\");\n  _set_infinite = (set_infinite_func *) AddressOf(lpsolve, \"set_infinite\");\n  _set_int = (set_int_func *) AddressOf(lpsolve, \"set_int\");\n  _set_lag_trace = (set_lag_trace_func *) AddressOf(lpsolve, \"set_lag_trace\");\n  _set_lowbo = (set_lowbo_func *) AddressOf(lpsolve, \"set_lowbo\");\n  _set_lp_name = (set_lp_name_func *) AddressOf(lpsolve, \"set_lp_name\");\n  _set_mat = (set_mat_func *) AddressOf(lpsolve, \"set_mat\");\n  _set_maxim = (set_maxim_func *) AddressOf(lpsolve, \"set_maxim\");\n  _set_maxpivot = (set_maxpivot_func *) AddressOf(lpsolve, \"set_maxpivot\");\n  _set_minim = (set_minim_func *) AddressOf(lpsolve, \"set_minim\");\n  _set_mip_gap = (set_mip_gap_func *) AddressOf(lpsolve, \"set_mip_gap\");\n  _set_multiprice = (set_multiprice_func *) AddressOf(lpsolve, \"set_multiprice\");\n  _set_negrange = (set_negrange_func *) AddressOf(lpsolve, \"set_negrange\");\n  _set_obj_bound = (set_obj_bound_func *) AddressOf(lpsolve, \"set_obj_bound\");\n  _set_obj_fn = (set_obj_fn_func *) AddressOf(lpsolve, \"set_obj_fn\");\n  _set_obj_fnex = (set_obj_fnex_func *) AddressOf(lpsolve, \"set_obj_fnex\");\n  _set_obj = (set_obj_func *) AddressOf(lpsolve, \"set_obj\");\n  _set_outputfile = (set_outputfile_func *) AddressOf(lpsolve, \"set_outputfile\");\n  _set_outputstream = (set_outputstream_func *) AddressOf(lpsolve, \"set_outputstream\");\n  _set_partialprice = (set_partialprice_func *) AddressOf(lpsolve, \"set_partialprice\");\n  _set_pivoting = (set_pivoting_func *) AddressOf(lpsolve, \"set_pivoting\");\n  _set_preferdual = (set_preferdual_func *) AddressOf(lpsolve, \"set_preferdual\");\n  _set_presolve = (set_presolve_func *) AddressOf(lpsolve, \"set_presolve\");\n  _set_print_sol = (set_print_sol_func *) AddressOf(lpsolve, \"set_print_sol\");\n  _set_pseudocosts = (set_pseudocosts_func *) AddressOf(lpsolve, \"set_pseudocosts\");\n  _set_rh = (set_rh_func *) AddressOf(lpsolve, \"set_rh\");\n  _set_rh_range = (set_rh_range_func *) AddressOf(lpsolve, \"set_rh_range\");\n  _set_rh_vec = (set_rh_vec_func *) AddressOf(lpsolve, \"set_rh_vec\");\n  _set_row = (set_row_func *) AddressOf(lpsolve, \"set_row\");\n  _set_rowex = (set_rowex_func *) AddressOf(lpsolve, \"set_rowex\");\n  _set_row_name = (set_row_name_func *) AddressOf(lpsolve, \"set_row_name\");\n  _set_scalelimit = (set_scalelimit_func *) AddressOf(lpsolve, \"set_scalelimit\");\n  _set_scaling = (set_scaling_func *) AddressOf(lpsolve, \"set_scaling\");\n  _set_semicont = (set_semicont_func *) AddressOf(lpsolve, \"set_semicont\");\n  _set_sense = (set_sense_func *) AddressOf(lpsolve, \"set_sense\");\n  _set_simplextype = (set_simplextype_func *) AddressOf(lpsolve, \"set_simplextype\");\n  _set_solutionlimit = (set_solutionlimit_func *) AddressOf(lpsolve, \"set_solutionlimit\");\n  _set_timeout = (set_timeout_func *) AddressOf(lpsolve, \"set_timeout\");\n  _set_trace = (set_trace_func *) AddressOf(lpsolve, \"set_trace\");\n  _set_upbo = (set_upbo_func *) AddressOf(lpsolve, \"set_upbo\");\n  _set_var_branch = (set_var_branch_func *) AddressOf(lpsolve, \"set_var_branch\");\n  _set_var_weights = (set_var_weights_func *) AddressOf(lpsolve, \"set_var_weights\");\n  _set_verbose = (set_verbose_func *) AddressOf(lpsolve, \"set_verbose\");\n  _set_XLI = (set_XLI_func *) AddressOf(lpsolve, \"set_XLI\");\n  _solve = (solve_func *) AddressOf(lpsolve, \"solve\");\n  _str_add_column = (str_add_column_func *) AddressOf(lpsolve, \"str_add_column\");\n  _str_add_constraint = (str_add_constraint_func *) AddressOf(lpsolve, \"str_add_constraint\");\n  _str_add_lag_con = (str_add_lag_con_func *) AddressOf(lpsolve, \"str_add_lag_con\");\n  _str_set_obj_fn = (str_set_obj_fn_func *) AddressOf(lpsolve, \"str_set_obj_fn\");\n  _str_set_rh_vec = (str_set_rh_vec_func *) AddressOf(lpsolve, \"str_set_rh_vec\");\n  _time_elapsed = (time_elapsed_func *) AddressOf(lpsolve, \"time_elapsed\");\n  _unscale = (unscale_func *) AddressOf(lpsolve, \"unscale\");\n  _write_lp = (write_lp_func *) AddressOf(lpsolve, \"write_lp\");\n  _write_LP = (write_LP_func *) AddressOf(lpsolve, \"write_LP\");\n  _write_mps = (write_mps_func *) AddressOf(lpsolve, \"write_mps\");\n  _write_MPS = (write_MPS_func *) AddressOf(lpsolve, \"write_MPS\");\n  _write_freemps = (write_freemps_func *) AddressOf(lpsolve, \"write_freemps\");\n  _write_freeMPS = (write_freeMPS_func *) AddressOf(lpsolve, \"write_freeMPS\");\n  _write_XLI = (write_XLI_func *) AddressOf(lpsolve, \"write_XLI\");\n  _write_basis = (write_basis_func *) AddressOf(lpsolve, \"write_basis\");\n  _write_params = (write_params_func *) AddressOf(lpsolve, \"write_params\");\n\n  return(TRUE);\n# undef AddressOf\n}\n\n#else\n#  error Either LPSOLVEAPIFROMLPREC or LPSOLVEAPIFROMLIB must be defined\n#endif\n\n#define add_column _add_column\n#define add_columnex _add_columnex\n#define add_constraint _add_constraint\n#define add_constraintex _add_constraintex\n#define add_lag_con _add_lag_con\n#define add_SOS _add_SOS\n#define column_in_lp _column_in_lp\n#define copy_lp _copy_lp\n#define default_basis _default_basis\n#define del_column _del_column\n#define del_constraint _del_constraint\n#define delete_lp _delete_lp\n#define dualize_lp _dualize_lp\n#define free_lp _free_lp\n#define get_anti_degen _get_anti_degen\n#define get_basis _get_basis\n#define get_basiscrash _get_basiscrash\n#define get_bb_depthlimit _get_bb_depthlimit\n#define get_bb_floorfirst _get_bb_floorfirst\n#define get_bb_rule _get_bb_rule\n#define get_bounds_tighter _get_bounds_tighter\n#define get_break_at_value _get_break_at_value\n#define get_col_name _get_col_name\n#define get_column _get_column\n#define get_columnex _get_columnex\n#define get_constr_type _get_constr_type\n#define get_constr_value _get_constr_value\n#define get_constraints _get_constraints\n#define get_dual_solution _get_dual_solution\n#define get_epsb _get_epsb\n#define get_epsd _get_epsd\n#define get_epsel _get_epsel\n#define get_epsint _get_epsint\n#define get_epsperturb _get_epsperturb\n#define get_epspivot _get_epspivot\n#define get_improve _get_improve\n#define get_infinite _get_infinite\n#define get_lambda _get_lambda\n#define get_lowbo _get_lowbo\n#define get_lp_index _get_lp_index\n#define get_lp_name _get_lp_name\n#define get_Lrows _get_Lrows\n#define get_mat _get_mat\n#define get_mat_byindex _get_mat_byindex\n#define get_max_level _get_max_level\n#define get_maxpivot _get_maxpivot\n#define get_mip_gap _get_mip_gap\n#define get_multiprice _get_multiprice\n#define get_nameindex _get_nameindex\n#define get_Ncolumns _get_Ncolumns\n#define get_negrange _get_negrange\n#define get_nonzeros _get_nonzeros\n#define get_Norig_columns _get_Norig_columns\n#define get_Norig_rows _get_Norig_rows\n#define get_Nrows _get_Nrows\n#define get_obj_bound _get_obj_bound\n#define get_objective _get_objective\n#define get_orig_index _get_orig_index\n#define get_origcol_name _get_origcol_name\n#define get_origrow_name _get_origrow_name\n#define get_partialprice _get_partialprice\n#define get_pivoting _get_pivoting\n#define get_presolve _get_presolve\n#define get_presolveloops _get_presolveloops\n#define get_primal_solution _get_primal_solution\n#define get_print_sol _get_print_sol\n#define get_pseudocosts _get_pseudocosts\n#define get_ptr_constraints _get_ptr_constraints\n#define get_ptr_dual_solution _get_ptr_dual_solution\n#define get_ptr_lambda _get_ptr_lambda\n#define get_ptr_primal_solution _get_ptr_primal_solution\n#define get_ptr_sensitivity_obj _get_ptr_sensitivity_obj\n#define get_ptr_sensitivity_objex _get_ptr_sensitivity_objex\n#define get_ptr_sensitivity_rhs _get_ptr_sensitivity_rhs\n#define get_ptr_variables _get_ptr_variables\n#define get_rh _get_rh\n#define get_rh_range _get_rh_range\n#define get_row _get_row\n#define get_rowex _get_rowex\n#define get_row_name _get_row_name\n#define get_scalelimit _get_scalelimit\n#define get_scaling _get_scaling\n#define get_sensitivity_obj _get_sensitivity_obj\n#define get_sensitivity_objex _get_sensitivity_objex\n#define get_sensitivity_rhs _get_sensitivity_rhs\n#define get_simplextype _get_simplextype\n#define get_solutioncount _get_solutioncount\n#define get_solutionlimit _get_solutionlimit\n#define get_status _get_status\n#define get_statustext _get_statustext\n#define get_timeout _get_timeout\n#define get_total_iter _get_total_iter\n#define get_total_nodes _get_total_nodes\n#define get_upbo _get_upbo\n#define get_var_branch _get_var_branch\n#define get_var_dualresult _get_var_dualresult\n#define get_var_primalresult _get_var_primalresult\n#define get_var_priority _get_var_priority\n#define get_variables _get_variables\n#define get_verbose _get_verbose\n#define get_working_objective _get_working_objective\n#define guess_basis _guess_basis\n#define has_BFP _has_BFP\n#define has_XLI _has_XLI\n#define is_add_rowmode _is_add_rowmode\n#define is_anti_degen _is_anti_degen\n#define is_binary _is_binary\n#define is_break_at_first _is_break_at_first\n#define is_constr_type _is_constr_type\n#define is_debug _is_debug\n#define is_feasible _is_feasible\n#define is_unbounded _is_unbounded\n#define is_infinite _is_infinite\n#define is_int _is_int\n#define is_integerscaling _is_integerscaling\n#define is_lag_trace _is_lag_trace\n#define is_maxim _is_maxim\n#define is_nativeBFP _is_nativeBFP\n#define is_nativeXLI _is_nativeXLI\n#define is_negative _is_negative\n#define is_piv_mode _is_piv_mode\n#define is_piv_rule _is_piv_rule\n#define is_presolve _is_presolve\n#define is_scalemode _is_scalemode\n#define is_scaletype _is_scaletype\n#define is_semicont _is_semicont\n#define is_SOS_var _is_SOS_var\n#define is_trace _is_trace\n#define is_use_names _is_use_names\n#define lp_solve_version _lp_solve_version\n#define make_lp _make_lp\n#define print_constraints _print_constraints\n#define print_debugdump _print_debugdump\n#define print_duals _print_duals\n#define print_lp _print_lp\n#define print_objective _print_objective\n#define print_scales _print_scales\n#define print_solution _print_solution\n#define print_str _print_str\n#define print_tableau _print_tableau\n#define put_abortfunc _put_abortfunc\n#define put_bb_nodefunc _put_bb_nodefunc\n#define put_bb_branchfunc _put_bb_branchfunc\n#define put_logfunc _put_logfunc\n#define put_msgfunc _put_msgfunc\n#define read_LP _read_LP\n#define read_MPS _read_MPS\n#define read_XLI _read_XLI\n#define read_params _read_params\n#define read_basis _read_basis\n#define reset_basis _reset_basis\n#define reset_params _reset_params\n#define report _report\n#define resize_lp _resize_lp\n#define set_add_rowmode _set_add_rowmode\n#define set_anti_degen _set_anti_degen\n#define set_basisvar _set_basisvar\n#define set_basis _set_basis\n#define set_basiscrash _set_basiscrash\n#define set_bb_depthlimit _set_bb_depthlimit\n#define set_bb_floorfirst _set_bb_floorfirst\n#define set_bb_rule _set_bb_rule\n#define set_BFP _set_BFP\n#define set_binary _set_binary\n#define set_bounds _set_bounds\n#define set_bounds_tighter _set_bounds_tighter\n#define set_break_at_first _set_break_at_first\n#define set_break_at_value _set_break_at_value\n#define set_column _set_column\n#define set_columnex _set_columnex\n#define set_col_name _set_col_name\n#define set_constr_type _set_constr_type\n#define set_debug _set_debug\n#define set_epsb _set_epsb\n#define set_epsd _set_epsd\n#define set_epsel _set_epsel\n#define set_epsint _set_epsint\n#define set_epslevel _set_epslevel\n#define set_epsperturb _set_epsperturb\n#define set_epspivot _set_epspivot\n#define set_unbounded _set_unbounded\n#define set_improve _set_improve\n#define set_infinite _set_infinite\n#define set_int _set_int\n#define set_lag_trace _set_lag_trace\n#define set_lowbo _set_lowbo\n#define set_lp_name _set_lp_name\n#define set_mat _set_mat\n#define set_maxim _set_maxim\n#define set_maxpivot _set_maxpivot\n#define set_minim _set_minim\n#define set_mip_gap _set_mip_gap\n#define set_multiprice _set_multiprice\n#define set_negrange _set_negrange\n#define set_obj_bound _set_obj_bound\n#define set_obj_fn _set_obj_fn\n#define set_obj_fnex _set_obj_fnex\n#define set_obj _set_obj\n#define set_outputfile _set_outputfile\n#define set_outputstream _set_outputstream\n#define set_partialprice _set_partialprice\n#define set_pivoting _set_pivoting\n#define set_preferdual _set_preferdual\n#define set_presolve _set_presolve\n#define set_print_sol _set_print_sol\n#define set_pseudocosts _set_pseudocosts\n#define set_rh _set_rh\n#define set_rh_range _set_rh_range\n#define set_rh_vec _set_rh_vec\n#define set_row _set_row\n#define set_rowex _set_rowex\n#define set_row_name _set_row_name\n#define set_scalelimit _set_scalelimit\n#define set_scaling _set_scaling\n#define set_semicont _set_semicont\n#define set_sense _set_sense\n#define set_simplextype _set_simplextype\n#define set_solutionlimit _set_solutionlimit\n#define set_timeout _set_timeout\n#define set_trace _set_trace\n#define set_upbo _set_upbo\n#define set_var_branch _set_var_branch\n#define set_var_weights _set_var_weights\n#define set_verbose _set_verbose\n#define set_XLI _set_XLI\n#define solve _solve\n#define str_add_column _str_add_column\n#define str_add_constraint _str_add_constraint\n#define str_add_lag_con _str_add_lag_con\n#define str_set_obj_fn _str_set_obj_fn\n#define str_set_rh_vec _str_set_rh_vec\n#define time_elapsed _time_elapsed\n#define unscale _unscale\n#define write_lp _write_lp\n#define write_LP _write_LP\n#define write_mps _write_mps\n#define write_MPS _write_MPS\n#define write_freemps _write_freemps\n#define write_freeMPS _write_freeMPS\n#define write_XLI _write_XLI\n#define write_basis _write_basis\n#define write_params _write_params\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_fortify.h",
    "content": "#ifdef FORTIFY\n\n#include \"fortify.h\"\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_lib.h",
    "content": "\n#ifndef HEADER_lp_lib\n#define HEADER_lp_lib\n\n/* --------------------------------------------------------------------------\n\n  This is the main library header file for the lp_solve v5.0 release\n\n  Starting at version 3.0, LP_Solve is released under the LGPL license.\n  For full information, see the enclosed file LGPL.txt.\n\n  Original developer:   Michel Berkelaar  -  michel@ics.ele.tue.nl\n  Most changes 1.5-2.0: Jeroen Dirks      -  jeroend@tor.numetrix.com\n  Changes 3.2-4.0:      Kjell Eikland     -  kjell.eikland@broadpark.no\n                        (Simplex code, SOS, SC, code optimization)\n                        Peter Notebaert   -  lpsolve@peno.be\n                        (Sensitivity analysis, documentation)\n  Changes 5.0+:         Kjell Eikland     -  kjell.eikland@broadpark.no\n                        (BFP, XLI, simplex, B&B, code modularization)\n                        Peter Notebaert   -  lpsolve@peno.be\n                        (Sensitivity analysis, New lp parser, LINDO (XLI)\n                        parser, VB/.NET interface, documentation)\n\n  Release notes:\n\n  Version 4.0 enhances version 3.2 in terms of internal program/simplex\n  architecture, call level interfaces, data layout, features and contains\n  several bug fixes.  There is now complete support for semi-continuous\n  variables and SOS constructions.  In the process, a complete API\n  was added. The MPS parser has been amended to support this.\n  Sensitivity analysis and variouse bug fixes was provided by Peter\n  Notebaert in 4.0 sub-releases.  Peter also wrote a complete\n  documentation of the API and contributed a VB interface, both of which\n  significantly enhanced the accessibility of lp_solve.\n\n  Version 5.0 is a major rewrite and code cleanup.  The main additions that\n  drove forward this cleanup were the modular inversion logic with optimal\n  column ordering, addition of primal phase 1 and dual phase 2 logic for\n  full flexibility in the selection of primal and dual simplex modes,\n  DEVEX and steepest edge pivot selection, along with dynamic cycling\n  detection and prevention.  This cleanup made it possible to harmonize the\n  internal rounding principles, contributing to increased numerical stability.\n\n  Version 5.1 rearranges the matrix storage model by enabling both legacy\n  element record-based storage and split vector storage.  In addition the\n  lprec structure is optimized and additional routines are added, mainly for\n  sparse vector additions and enhanced XLI functionality.  Support for XML-\n  based models was added on the basis of the LPFML schema via xli_LPFML.\n\n  Version 5.2 removes the objective function from the constraint matrix,\n  adds a number of presolve options and speed them up.  Degeneracy handling\n  is significantly improved. Support for XLI_ZIMPL was added.\n  Multiple and partial pricing has been enhanced and activated.\n\n  -------------------------------------------------------------------------- */\n/* Define user program feature option switches                               */\n/* ------------------------------------------------------------------------- */\n\n# if defined _WIN32 && !defined __GNUC__\n#  define isnan _isnan\n# endif\n#if defined NOISNAN\n# define isnan(x) FALSE\n#endif\n\n#define SETMASK(variable, mask)     variable |= mask\n#define CLEARMASK(variable, mask)   variable &= ~(mask)\n#define TOGGLEMASK(variable, mask)  variable ^= mask\n#define ISMASKSET(variable, mask)   (MYBOOL) (((variable) & (mask)) != 0)\n\n/* Utility/system settings                                                   */\n/* ------------------------------------------------------------------------- */\n/*#define INTEGERTIME */                    /* Set use of lower-resolution timer */\n\n\n/* New v5.0+ simplex/optimization features and settings                      */\n/* ------------------------------------------------------------------------- */\n/*#define NoRowScaleOF */               /* Optionally skip row-scaling of the OF */\n#define DoMatrixRounding                  /* Round A matrix elements to precision */\n#define DoBorderRounding            /* Round RHS, bounds and ranges to precision */\n#define Phase1EliminateRedundant        /* Remove rows of redundant artificials  */\n#define FixViolatedOptimal\n#define ImproveSolutionPrecision                 /* Round optimal solution values */\n/*#define IncreasePivotOnReducedAccuracy */  /* Increase epspivot on instability */\n/*#define FixInaccurateDualMinit */     /* Reinvert on inaccuracy in dual minits */\n/*#define EnforcePositiveTheta */        /* Ensure that the theta range is valid */\n#define ResetMinitOnReinvert\n/*#define UsePrimalReducedCostUpdate */                            /* Not tested */\n/*#define UseDualReducedCostUpdate */      /* Seems Ok, but slower than expected */\n/*#ifdef UseLegacyExtrad */                     /* Use v3.2- style Extrad method */\n#define UseMilpExpandedRCF         /* Non-ints in reduced cost bound tightening */\n/*#define UseMilpSlacksRCF */  /* Slacks in reduced cost bound tightening (degen\n                                  prone); requires !SlackInitMinusInf */\n#define LegacySlackDefinition      /* Slack as the \"value of the constraint\" */\n\n\n/* Development features (change at own risk)                                 */\n/* ------------------------------------------------------------------------- */\n/*#define MIPboundWithOF */ /* Enable to detect OF constraint for use during B&B */\n/*#define SlackInitMinusInf */        /* Slacks have 0 LB if this is not defined */\n#define FULLYBOUNDEDSIMPLEX FALSE     /* WARNING: Activate at your own risk! */\n\n\n/* Specify use of the basic linear algebra subroutine library                */\n/* ------------------------------------------------------------------------- */\n#define libBLAS                  2        /* 0: No, 1: Internal, 2: External */\n#define libnameBLAS        \"myBLAS\"\n\n\n/* Active inverse logic (default is optimized original etaPFI)               */\n/* ------------------------------------------------------------------------- */\n#if !defined LoadInverseLib\n# define LoadInverseLib TRUE          /* Enable alternate inverse libraries */\n#endif\n/*#define ExcludeNativeInverse     */   /* Disable INVERSE_ACTIVE inverse engine */\n\n#define DEF_OBJINBASIS        TRUE  /* Additional rows inserted at the top (1 => OF) */\n\n#define INVERSE_NONE            -1\n#define INVERSE_LEGACY           0\n#define INVERSE_ETAPFI           1\n#define INVERSE_LUMOD            2\n#define INVERSE_LUSOL            3\n#define INVERSE_GLPKLU           4\n\n#ifndef RoleIsExternalInvEngine            /* Defined in inverse DLL drivers */\n  #ifdef ExcludeNativeInverse\n    #define INVERSE_ACTIVE       INVERSE_NONE       /* Disable native engine */\n  #else\n    #define INVERSE_ACTIVE       INVERSE_LEGACY      /* User or DLL-selected */\n  #endif\n#endif\n\n\n/* Active external language interface logic (default is none)                */\n/* ------------------------------------------------------------------------- */\n#if !defined LoadLanguageLib\n# define LoadLanguageLib TRUE         /* Enable alternate language libraries */\n#endif\n#define ExcludeNativeLanguage                 /* Disable LANGUAGE_ACTIVE XLI */\n\n#define LANGUAGE_NONE           -1\n#define LANGUAGE_LEGACYLP        0\n#define LANGUAGE_CPLEXLP         1\n#define LANGUAGE_MPSX            2\n#define LANGUAGE_LPFML           3\n#define LANGUAGE_MATHPROG        4\n#define LANGUAGE_AMPL            5\n#define LANGUAGE_GAMS            6\n#define LANGUAGE_ZIMPL           7\n#define LANGUAGE_S               8\n#define LANGUAGE_R               9\n#define LANGUAGE_MATLAB         10\n#define LANGUAGE_OMATRIX        11\n#define LANGUAGE_SCILAB         12\n#define LANGUAGE_OCTAVE         13\n#define LANGUAGE_EMPS           14\n\n#ifndef RoleIsExternalLanguageEngine      /* Defined in XLI driver libraries */\n  #ifdef ExcludeNativeLanguage\n    #define LANGUAGE_ACTIVE       LANGUAGE_NONE     /* Disable native engine */\n  #else\n    #define LANGUAGE_ACTIVE       LANGUAGE_CPLEXLP   /* User or DLL-selected */\n  #endif\n#endif\n\n\n/* Default parameters and tolerances                                         */\n/* ------------------------------------------------------------------------- */\n#define OriginalPARAM           0\n#define ProductionPARAM         1\n#define ChvatalPARAM            2\n#define LoosePARAM              3\n#if 1\n  #define ActivePARAM           ProductionPARAM\n#else\n  #define ActivePARAM           LoosePARAM\n#endif\n\n\n/* Miscellaneous settings                                                    */\n/* ------------------------------------------------------------------------- */\n#ifndef Paranoia\n  #ifdef _DEBUG\n    #define Paranoia\n  #endif\n#endif\n\n\n/* Program version data                                                      */\n/* ------------------------------------------------------------------------- */\n#define MAJORVERSION             5\n#define MINORVERSION             5\n#define RELEASE                  2\n#define BUILD                    0\n#define BFPVERSION              12       /* Checked against bfp_compatible() */\n#define XLIVERSION              12       /* Checked against xli_compatible() */\n/* Note that both BFPVERSION and XLIVERSION typically have to be incremented\n   in the case that the lprec structure changes.                             */\n\n\n/* Include/header files                                                      */\n/* ------------------------------------------------------------------------- */\n#include <sys/types.h>\n#include <stdlib.h>\n#include <string.h>\n#include <math.h>\n#include <stdio.h>\n\n#include \"lp_types.h\"\n#include \"lp_utils.h\"\n\n#if (LoadInverseLib == TRUE) || (LoadLanguageLib == TRUE)\n  #ifdef WIN32\n    #include <windows.h>\n  #else\n    #include <dlfcn.h>\n  #endif\n#endif\n\n#ifndef BFP_CALLMODEL\n  #ifdef WIN32\n    #define BFP_CALLMODEL __stdcall   /* \"Standard\" call model */\n  #else\n    #define BFP_CALLMODEL\n  #endif\n#endif\n#ifndef XLI_CALLMODEL\n  #define XLI_CALLMODEL BFP_CALLMODEL\n#endif\n\n#define REGISTER        register      /* Speed up certain operations */\n\n\n/* Definition of program constrants                                          */\n/* ------------------------------------------------------------------------- */\n#define SIMPLEX_UNDEFINED        0\n#define SIMPLEX_Phase1_PRIMAL    1\n#define SIMPLEX_Phase1_DUAL      2\n#define SIMPLEX_Phase2_PRIMAL    4\n#define SIMPLEX_Phase2_DUAL      8\n#define SIMPLEX_DYNAMIC         16\n#define SIMPLEX_AUTODUALIZE     32\n\n#define SIMPLEX_PRIMAL_PRIMAL   (SIMPLEX_Phase1_PRIMAL + SIMPLEX_Phase2_PRIMAL)\n#define SIMPLEX_DUAL_PRIMAL     (SIMPLEX_Phase1_DUAL   + SIMPLEX_Phase2_PRIMAL)\n#define SIMPLEX_PRIMAL_DUAL     (SIMPLEX_Phase1_PRIMAL + SIMPLEX_Phase2_DUAL)\n#define SIMPLEX_DUAL_DUAL       (SIMPLEX_Phase1_DUAL   + SIMPLEX_Phase2_DUAL)\n#define SIMPLEX_DEFAULT         (SIMPLEX_DUAL_PRIMAL)\n\n/* Variable codes (internal) */\n#define ISREAL                   0\n#define ISINTEGER                1\n#define ISSEMI                   2\n#define ISSOS                    4\n#define ISSOSTEMPINT             8\n#define ISGUB                   16\n\n/* Presolve defines */\n#define PRESOLVE_NONE            0\n#define PRESOLVE_ROWS            1\n#define PRESOLVE_COLS            2\n#define PRESOLVE_LINDEP          4\n#define PRESOLVE_AGGREGATE       8  /* Not implemented */\n#define PRESOLVE_SPARSER        16  /* Not implemented */\n#define PRESOLVE_SOS            32\n#define PRESOLVE_REDUCEMIP      64\n#define PRESOLVE_KNAPSACK      128  /* Implementation not tested completely */\n#define PRESOLVE_ELIMEQ2       256\n#define PRESOLVE_IMPLIEDFREE   512\n#define PRESOLVE_REDUCEGCD    1024\n#define PRESOLVE_PROBEFIX     2048\n#define PRESOLVE_PROBEREDUCE  4096\n#define PRESOLVE_ROWDOMINATE  8192\n#define PRESOLVE_COLDOMINATE 16384  /* Reduced functionality, should be expanded */\n#define PRESOLVE_MERGEROWS   32768\n#define PRESOLVE_IMPLIEDSLK  65536\n#define PRESOLVE_COLFIXDUAL 131072\n#define PRESOLVE_BOUNDS     262144\n#define PRESOLVE_LASTMASKMODE    (PRESOLVE_DUALS - 1)\n#define PRESOLVE_DUALS      524288\n#define PRESOLVE_SENSDUALS 1048576\n\n/* Basis crash options */\n#define CRASH_NONE               0\n#define CRASH_NONBASICBOUNDS     1\n#define CRASH_MOSTFEASIBLE       2\n#define CRASH_LEASTDEGENERATE    3\n\n/* Solution recomputation options (internal) */\n#define INITSOL_SHIFTZERO        0\n#define INITSOL_USEZERO          1\n#define INITSOL_ORIGINAL         2\n\n/* Strategy codes to avoid or recover from degenerate pivots,\n   infeasibility or numeric errors via randomized bound relaxation */\n#define ANTIDEGEN_NONE           0\n#define ANTIDEGEN_FIXEDVARS      1\n#define ANTIDEGEN_COLUMNCHECK    2\n#define ANTIDEGEN_STALLING       4\n#define ANTIDEGEN_NUMFAILURE     8\n#define ANTIDEGEN_LOSTFEAS      16\n#define ANTIDEGEN_INFEASIBLE    32\n#define ANTIDEGEN_DYNAMIC       64\n#define ANTIDEGEN_DURINGBB     128\n#define ANTIDEGEN_RHSPERTURB   256\n#define ANTIDEGEN_BOUNDFLIP    512\n#define ANTIDEGEN_DEFAULT        (ANTIDEGEN_FIXEDVARS | ANTIDEGEN_STALLING /* | ANTIDEGEN_INFEASIBLE */)\n\n/* REPORT defines */\n#define NEUTRAL                  0\n#define CRITICAL                 1\n#define SEVERE                   2\n#define IMPORTANT                3\n#define NORMAL                   4\n#define DETAILED                 5\n#define FULL                     6\n\n/* MESSAGE defines */\n#define MSG_NONE                 0\n#define MSG_PRESOLVE             1\n#define MSG_ITERATION            2\n#define MSG_INVERT               4\n#define MSG_LPFEASIBLE           8\n#define MSG_LPOPTIMAL           16\n#define MSG_LPEQUAL             32\n#define MSG_LPBETTER            64\n#define MSG_MILPFEASIBLE       128\n#define MSG_MILPEQUAL          256\n#define MSG_MILPBETTER         512\n#define MSG_MILPSTRATEGY      1024\n#define MSG_MILPOPTIMAL       2048\n#define MSG_PERFORMANCE       4096\n#define MSG_INITPSEUDOCOST    8192\n\n/* MPS file types */\n#define MPSFIXED                 1\n#define MPSFREE                  2\n#define MPSIBM                   4\n#define MPSNEGOBJCONST           8\n\n#define MPS_FREE                 (MPSFREE<<2)\n#define MPS_IBM                  (MPSIBM<<2)\n#define MPS_NEGOBJCONST          (MPSNEGOBJCONST<<2)\n\n/* MPS defines (internal) */\n#define MPSUNDEF                -4\n#define MPSNAME                 -3\n#define MPSOBJSENSE             -2\n#define MPSOBJNAME              -1\n#define MPSROWS                  0\n#define MPSCOLUMNS               1\n#define MPSRHS                   2\n#define MPSBOUNDS                3\n#define MPSRANGES                4\n#define MPSSOS                   5\n\n#define MPSVARMASK          \"%-8s\"\n#define MPSVALUEMASK        \"%12g\"\n\n/* Constraint type codes  (internal) */\n#define ROWTYPE_EMPTY            0\n#define ROWTYPE_LE               1\n#define ROWTYPE_GE               2\n#define ROWTYPE_EQ               3\n#define ROWTYPE_CONSTRAINT       ROWTYPE_EQ  /* This is the mask for modes */\n#define ROWTYPE_OF               4\n#define ROWTYPE_INACTIVE         8\n#define ROWTYPE_RELAX           16\n#define ROWTYPE_GUB             32\n#define ROWTYPE_OFMAX            (ROWTYPE_OF + ROWTYPE_GE)\n#define ROWTYPE_OFMIN            (ROWTYPE_OF + ROWTYPE_LE)\n#define ROWTYPE_CHSIGN           ROWTYPE_GE\n\n/* Public constraint codes */\n#define FR                       ROWTYPE_EMPTY\n#define LE                       ROWTYPE_LE\n#define GE                       ROWTYPE_GE\n#define EQ                       ROWTYPE_EQ\n#define OF                       ROWTYPE_OF\n\n/* MIP constraint classes */\n#define ROWCLASS_Unknown         0   /* Undefined/unknown */\n#define ROWCLASS_Objective       1   /* The objective function */\n#define ROWCLASS_GeneralREAL     2   /* General real-values constraint */\n#define ROWCLASS_GeneralMIP      3   /* General mixed integer/binary and real valued constraint */\n#define ROWCLASS_GeneralINT      4   /* General integer-only constraint */\n#define ROWCLASS_GeneralBIN      5   /* General binary-only constraint */\n#define ROWCLASS_KnapsackINT     6   /* Sum of positive integer times integer variables <= positive integer */\n#define ROWCLASS_KnapsackBIN     7   /* Sum of positive integer times binary variables <= positive integer */\n#define ROWCLASS_SetPacking      8   /* Sum of binary variables >= 1 */\n#define ROWCLASS_SetCover        9   /* Sum of binary variables <= 1 */\n#define ROWCLASS_GUB            10   /* Sum of binary variables = 1  */\n#define ROWCLASS_MAX             ROWCLASS_GUB\n\n/* Column subsets (internal) */\n#define SCAN_USERVARS            1\n#define SCAN_SLACKVARS           2\n#define SCAN_ARTIFICIALVARS      4\n#define SCAN_PARTIALBLOCK        8\n#define USE_BASICVARS           16\n#define USE_NONBASICVARS        32\n#define SCAN_NORMALVARS         (SCAN_USERVARS + SCAN_ARTIFICIALVARS)\n#define SCAN_ALLVARS            (SCAN_SLACKVARS + SCAN_USERVARS + SCAN_ARTIFICIALVARS)\n#define USE_ALLVARS             (USE_BASICVARS + USE_NONBASICVARS)\n#define OMIT_FIXED              64\n#define OMIT_NONFIXED          128\n\n/* Improvement defines */\n#define IMPROVE_NONE             0\n#define IMPROVE_SOLUTION         1\n#define IMPROVE_DUALFEAS         2\n#define IMPROVE_THETAGAP         4\n#define IMPROVE_BBSIMPLEX        8\n#define IMPROVE_DEFAULT          (IMPROVE_DUALFEAS + IMPROVE_THETAGAP)\n#define IMPROVE_INVERSE          (IMPROVE_SOLUTION + IMPROVE_THETAGAP)\n\n/* Scaling types */\n#define SCALE_NONE               0\n#define SCALE_EXTREME            1\n#define SCALE_RANGE              2\n#define SCALE_MEAN               3\n#define SCALE_GEOMETRIC          4\n#define SCALE_FUTURE1            5\n#define SCALE_FUTURE2            6\n#define SCALE_CURTISREID         7   /* Override to Curtis-Reid \"optimal\" scaling */\n\n/* Alternative scaling weights */\n#define SCALE_LINEAR             0\n#define SCALE_QUADRATIC          8\n#define SCALE_LOGARITHMIC       16\n#define SCALE_USERWEIGHT        31\n#define SCALE_MAXTYPE            (SCALE_QUADRATIC-1)\n\n/* Scaling modes */\n#define SCALE_POWER2            32   /* As is or rounded to power of 2 */\n#define SCALE_EQUILIBRATE       64   /* Make sure that no scaled number is above 1 */\n#define SCALE_INTEGERS         128   /* Apply to integer columns/variables */\n#define SCALE_DYNUPDATE        256   /* Apply incrementally every solve() */\n#define SCALE_ROWSONLY         512   /* Override any scaling to only scale the rows */\n#define SCALE_COLSONLY        1024   /* Override any scaling to only scale the rows */\n\n/* Standard defines for typical scaling models (no Lagrangeans) */\n#define SCALEMODEL_EQUILIBRATED  (SCALE_LINEAR+SCALE_EXTREME+SCALE_INTEGERS)\n#define SCALEMODEL_GEOMETRIC     (SCALE_LINEAR+SCALE_GEOMETRIC+SCALE_INTEGERS)\n#define SCALEMODEL_ARITHMETIC    (SCALE_LINEAR+SCALE_MEAN+SCALE_INTEGERS)\n#define SCALEMODEL_DYNAMIC       (SCALEMODEL_GEOMETRIC+SCALE_EQUILIBRATE)\n#define SCALEMODEL_CURTISREID    (SCALE_CURTISREID+SCALE_INTEGERS+SCALE_POWER2)\n\n/* Iteration status and strategies (internal) */\n#define ITERATE_MAJORMAJOR       0\n#define ITERATE_MINORMAJOR       1\n#define ITERATE_MINORRETRY       2\n\n/* Pricing methods */\n#define PRICER_FIRSTINDEX        0\n#define PRICER_DANTZIG           1\n#define PRICER_DEVEX             2\n#define PRICER_STEEPESTEDGE      3\n#define PRICER_LASTOPTION        PRICER_STEEPESTEDGE\n\n/* Additional settings for pricers (internal) */\n#define PRICER_RANDFACT        0.1\n#define DEVEX_RESTARTLIMIT 1.0e+09    /* Reset the norms if any value exceeds this limit */\n#define DEVEX_MINVALUE       0.000    /* Minimum weight [0..1] for entering variable, consider 0.01 */\n\n/* Pricing strategies */\n#define PRICE_PRIMALFALLBACK     4    /* In case of Steepest Edge, fall back to DEVEX in primal */\n#define PRICE_MULTIPLE           8    /* Enable multiple pricing (primal simplex) */\n#define PRICE_PARTIAL           16    /* Enable partial pricing */\n#define PRICE_ADAPTIVE          32    /* Temporarily use alternative strategy if cycling is detected */\n#define PRICE_HYBRID            64    /* NOT IMPLEMENTED */\n#define PRICE_RANDOMIZE        128    /* Adds a small randomization effect to the selected pricer */\n#define PRICE_AUTOPARTIAL      256    /* Detect and use data on the block structure of the model (primal) */\n#define PRICE_AUTOMULTIPLE     512    /* Automatically select multiple pricing (primal simplex) */\n#define PRICE_LOOPLEFT        1024    /* Scan entering/leaving columns left rather than right */\n#define PRICE_LOOPALTERNATE   2048    /* Scan entering/leaving columns alternatingly left/right */\n#define PRICE_HARRISTWOPASS   4096    /* Use Harris' primal pivot logic rather than the default */\n#define PRICE_FORCEFULL       8192    /* Non-user option to force full pricing */\n#define PRICE_TRUENORMINIT   16384    /* Use true norms for Devex and Steepest Edge initializations */\n\n/*#define _PRICE_NOBOUNDFLIP*/\n#if defined _PRICE_NOBOUNDFLIP\n#define PRICE_NOBOUNDFLIP    65536    /* Disallow automatic bound-flip during pivot */\n#endif\n\n#define PRICE_STRATEGYMASK       (PRICE_PRIMALFALLBACK + \\\n                                  PRICE_MULTIPLE + PRICE_PARTIAL + \\\n                                  PRICE_ADAPTIVE + PRICE_HYBRID + \\\n                                  PRICE_RANDOMIZE + PRICE_AUTOPARTIAL + PRICE_AUTOMULTIPLE + \\\n                                  PRICE_LOOPLEFT + PRICE_LOOPALTERNATE + \\\n                                  PRICE_HARRISTWOPASS + \\\n                                  PRICE_FORCEFULL + PRICE_TRUENORMINIT)\n\n/* B&B active variable codes (internal) */\n#define BB_REAL                  0\n#define BB_INT                   1\n#define BB_SC                    2\n#define BB_SOS                   3\n#define BB_GUB                   4\n\n/* B&B strategies */\n#define NODE_FIRSTSELECT         0\n#define NODE_GAPSELECT           1\n#define NODE_RANGESELECT         2\n#define NODE_FRACTIONSELECT      3\n#define NODE_PSEUDOCOSTSELECT    4\n#define NODE_PSEUDONONINTSELECT  5    /* Kjell Eikland #1 - Minimize B&B depth */\n#define NODE_PSEUDOFEASSELECT   (NODE_PSEUDONONINTSELECT+NODE_WEIGHTREVERSEMODE)\n#define NODE_PSEUDORATIOSELECT   6    /* Kjell Eikland #2 - Minimize a \"cost/benefit\" ratio */\n#define NODE_USERSELECT          7\n#define NODE_STRATEGYMASK        (NODE_WEIGHTREVERSEMODE-1) /* Mask for B&B strategies */\n#define NODE_WEIGHTREVERSEMODE   8\n#define NODE_BRANCHREVERSEMODE  16\n#define NODE_GREEDYMODE         32\n#define NODE_PSEUDOCOSTMODE     64\n#define NODE_DEPTHFIRSTMODE    128\n#define NODE_RANDOMIZEMODE     256\n#define NODE_GUBMODE           512\n#define NODE_DYNAMICMODE      1024\n#define NODE_RESTARTMODE      2048\n#define NODE_BREADTHFIRSTMODE 4096\n#define NODE_AUTOORDER        8192\n#define NODE_RCOSTFIXING     16384\n#define NODE_STRONGINIT      32768\n\n#define BRANCH_CEILING           0\n#define BRANCH_FLOOR             1\n#define BRANCH_AUTOMATIC         2\n#define BRANCH_DEFAULT           3\n\n/* Action constants for simplex and B&B (internal) */\n#define ACTION_NONE              0\n#define ACTION_ACTIVE            1\n#define ACTION_REBASE            2\n#define ACTION_RECOMPUTE         4\n#define ACTION_REPRICE           8\n#define ACTION_REINVERT         16\n#define ACTION_TIMEDREINVERT    32\n#define ACTION_ITERATE          64\n#define ACTION_RESTART         255\n\n/* Solver status values */\n#define UNKNOWNERROR            -5\n#define DATAIGNORED             -4\n#define NOBFP                   -3\n#define NOMEMORY                -2\n#define NOTRUN                  -1\n#define OPTIMAL                  0\n#define SUBOPTIMAL               1\n#define INFEASIBLE               2\n#define UNBOUNDED                3\n#define DEGENERATE               4\n#define NUMFAILURE               5\n#define USERABORT                6\n#define TIMEOUT                  7\n#define RUNNING                  8\n#define PRESOLVED                9\n\n/* Branch & Bound and Lagrangean extra status values (internal) */\n#define PROCFAIL                10\n#define PROCBREAK               11\n#define FEASFOUND               12\n#define NOFEASFOUND             13\n#define FATHOMED                14\n\n/* Status values internal to the solver (internal) */\n#define SWITCH_TO_PRIMAL        20\n#define SWITCH_TO_DUAL          21\n#define SINGULAR_BASIS          22\n#define LOSTFEAS                23\n#define MATRIXERROR             24\n\n/* Objective testing options for \"bb_better\" (internal) */\n#define OF_RELAXED               0\n#define OF_INCUMBENT             1\n#define OF_WORKING               2\n#define OF_USERBREAK             3\n#define OF_HEURISTIC             4\n#define OF_DUALLIMIT             5\n#define OF_DELTA                 8  /* Mode */\n#define OF_PROJECTED            16  /* Mode - future, not active */\n\n#define OF_TEST_BT               1\n#define OF_TEST_BE               2\n#define OF_TEST_NE               3\n#define OF_TEST_WE               4\n#define OF_TEST_WT               5\n#define OF_TEST_RELGAP           8  /* Mode */\n\n\n/* Name list and sparse matrix storage parameters (internal) */\n#define MAT_START_SIZE       10000\n#define DELTACOLALLOC          100\n#define DELTAROWALLOC          100\n#define RESIZEFACTOR             4  /* Fractional increase in selected memory allocations */\n\n/* Default solver parameters and tolerances (internal) */\n#define DEF_PARTIALBLOCKS       10  /* The default number of blocks for partial pricing */\n#define DEF_MAXRELAX             7  /* Maximum number of non-BB relaxations in MILP */\n#define DEF_MAXPIVOTRETRY       10  /* Maximum number of times to retry a div-0 situation */\n#define DEF_MAXSINGULARITIES    10  /* Maximum number of singularities in refactorization */\n#define MAX_MINITUPDATES        60  /* Maximum number of bound swaps between refactorizations\n                                       without recomputing the whole vector - contain errors */\n#define MIN_REFACTFREQUENCY      5  /* Refactorization frequency indicating an inherent\n                                       numerical instability of the basis */\n#define LAG_SINGULARLIMIT        5  /* Number of times the objective does not change\n                                       before it is assumed that the Lagrangean constraints\n                                       are non-binding, and therefore impossible to converge;\n                                       upper iteration limit is divided by this threshold */\n#define MIN_TIMEPIVOT      5.0e-02  /* Minimum time per pivot for reinversion optimization\n                                       purposes; use active monitoring only if a pivot\n                                       takes more than MINTIMEPIVOT seconds.  5.0e-2 is\n                                       roughly suitable for a 1GHz system.  */\n#define MAX_STALLCOUNT          12  /* The absolute upper limit to the number of stalling or\n                                       cycling iterations before switching rule */\n#define MAX_RULESWITCH           5  /* The maximum number of times to try an alternate pricing rule\n                                       to recover from stalling; set negative for no limit. */\n#define DEF_TIMEDREFACT  AUTOMATIC  /* Default for timed refactorization in BFPs;\n                                       can be FALSE, TRUE or AUTOMATIC (dynamic) */\n\n#define DEF_SCALINGLIMIT         5  /* The default maximum number of scaling iterations */\n\n#define DEF_NEGRANGE      -1.0e+06  /* Downward limit for expanded variable range before the\n                                       variable is split into positive and negative components */\n#define DEF_BB_LIMITLEVEL      -50  /* Relative B&B limit to protect against very deep,\n                                       memory-consuming trees */\n\n#define MAX_FRACSCALE            6  /* The maximum decimal scan range for simulated integers */\n#define RANDSCALE              100  /* Randomization scaling range */\n#define DOUBLEROUND        0.0e-02  /* Extra rounding scalar used in btran/ftran calculations; the\n                                       rationale for 0.0 is that prod_xA() uses rounding as well */\n#define DEF_EPSMACHINE    2.22e-16  /* Machine relative precision (doubles) */\n#define MIN_STABLEPIVOT        5.0  /* Minimum pivot magnitude assumed to be numerically stable */\n\n\n/* Precision macros                                                                       */\n/* -------------------------------------------------------------------------------------- */\n#define PREC_REDUCEDCOST        lp->epsvalue\n#define PREC_IMPROVEGAP         lp->epsdual\n#define PREC_SUBSTFEASGAP       lp->epsprimal\n#if 1\n  #define PREC_BASICSOLUTION    lp->epsvalue  /* Zero-rounding of RHS/basic solution vector */\n#else\n  #define PREC_BASICSOLUTION    lp->epsmachine  /* Zero-rounding of RHS/basic solution vector */\n#endif\n#define LIMIT_ABS_REL         10.0  /* Limit for testing using relative metric */\n\n\n/* Parameters constants for short-cut setting of tolerances                           */\n/* -------------------------------------------------------------------------------------- */\n#define EPS_TIGHT                0\n#define EPS_MEDIUM               1\n#define EPS_LOOSE                2\n#define EPS_BAGGY                3\n#define EPS_DEFAULT              EPS_TIGHT\n\n\n#if ActivePARAM==ProductionPARAM    /* PARAMETER SET FOR PRODUCTION                       */\n/* -------------------------------------------------------------------------------------- */\n#define DEF_INFINITE       1.0e+30  /* Limit for dynamic range */\n#define DEF_EPSVALUE       1.0e-12  /* High accuracy and feasibility preserving tolerance */\n#define DEF_EPSPRIMAL      1.0e-10  /* For rounding primal/RHS values to 0 */\n#define DEF_EPSDUAL        1.0e-09  /* For rounding reduced costs to 0 */\n#define DEF_EPSPIVOT       2.0e-07  /* Pivot reject threshold */\n#define DEF_PERTURB        1.0e-05  /* Perturbation scalar for degenerate problems;\n                                       must at least be RANDSCALE greater than EPSPRIMAL */\n#define DEF_EPSSOLUTION    1.0e-05  /* Margin of error for solution bounds */\n#define DEF_EPSINT         1.0e-07  /* Accuracy for considering a float value as integer */\n\n#elif ActivePARAM==OriginalPARAM    /* PARAMETER SET FOR LEGACY VERSIONS                  */\n/* -------------------------------------------------------------------------------------- */\n#define DEF_INFINITE       1.0e+24  /* Limit for dynamic range */\n#define DEF_EPSVALUE       1.0e-08  /* High accuracy and feasibility preserving tolerance */\n#define DEF_EPSPRIMAL     5.01e-07  /* For rounding primal/RHS values to 0, infeasibility */\n#define DEF_EPSDUAL        1.0e-06  /* For rounding reduced costs to 0 */\n#define DEF_EPSPIVOT       1.0e-04  /* Pivot reject threshold */\n#define DEF_PERTURB        1.0e-05  /* Perturbation scalar for degenerate problems;\n                                       must at least be RANDSCALE greater than EPSPRIMAL */\n#define DEF_EPSSOLUTION    1.0e-02  /* Margin of error for solution bounds */\n#define DEF_EPSINT         1.0e-03  /* Accuracy for considering a float value as integer */\n\n#elif ActivePARAM==ChvatalPARAM     /* PARAMETER SET EXAMPLES FROM Vacek Chvatal          */\n/* -------------------------------------------------------------------------------------- */\n#define DEF_INFINITE       1.0e+30  /* Limit for dynamic range */\n#define DEF_EPSVALUE       1.0e-10  /* High accuracy and feasibility preserving tolerance */\n#define DEF_EPSPRIMAL       10e-07  /* For rounding primal/RHS values to 0 */\n#define DEF_EPSDUAL         10e-05  /* For rounding reduced costs to 0 */\n#define DEF_EPSPIVOT        10e-05  /* Pivot reject threshold */\n#define DEF_PERTURB         10e-03  /* Perturbation scalar for degenerate problems;\n                                       must at least be RANDSCALE greater than EPSPRIMAL */\n#define DEF_EPSSOLUTION    1.0e-05  /* Margin of error for solution bounds */\n#define DEF_EPSINT         5.0e-03  /* Accuracy for considering a float value as integer */\n\n#elif ActivePARAM==LoosePARAM       /* PARAMETER SET FOR LOOSE TOLERANCES                 */\n/* -------------------------------------------------------------------------------------- */\n#define DEF_INFINITE       1.0e+30  /* Limit for dynamic range */\n#define DEF_EPSVALUE       1.0e-10  /* High accuracy and feasibility preserving tolerance */\n#define DEF_EPSPRIMAL     5.01e-08  /* For rounding primal/RHS values to 0 */\n#define DEF_EPSDUAL        1.0e-07  /* For rounding reduced costs to 0 */\n#define DEF_EPSPIVOT       1.0e-05  /* Pivot reject threshold */\n#define DEF_PERTURB        1.0e-05  /* Perturbation scalar for degenerate problems;\n                                       must at least be RANDSCALE greater than EPSPRIMAL */\n#define DEF_EPSSOLUTION    1.0e-05  /* Margin of error for solution bounds */\n#define DEF_EPSINT         1.0e-04  /* Accuracy for considering a float value as integer */\n\n#endif\n\n\n#define DEF_MIP_GAP        1.0e-11  /* The default absolute and relative MIP gap */\n#define SCALEDINTFIXRANGE      1.6  /* Epsilon range multiplier < 2 for collapsing bounds to fix */\n\n#define MIN_SCALAR         1.0e-10  /* Smallest allowed scaling adjustment */\n#define MAX_SCALAR         1.0e+10  /* Largest allowed scaling adjustment */\n#define DEF_SCALINGEPS     1.0e-02  /* Relative scaling convergence criterion for auto_scale */\n\n#define DEF_LAGACCEPT      1.0e-03  /* Default Lagrangean convergence acceptance criterion */\n#define DEF_LAGCONTRACT       0.90  /* The contraction parameter for Lagrangean iterations */\n#define DEF_LAGMAXITERATIONS   100  /* The maximum number of Lagrangean iterations */\n\n#define DEF_PSEUDOCOSTUPDATES    7  /* The default number of times pseudo-costs are recalculated;\n                                       experiments indicate that costs tend to stabilize */\n#define DEF_PSEUDOCOSTRESTART 0.15  /* The fraction of price updates required for B&B restart\n                                       when the mode is NODE_RESTARTMODE */\n#define DEF_MAXPRESOLVELOOPS     0  /* Upper limit to the number of loops during presolve,\n                                       <= 0 for no limit. */\n\n\n/* Hashing prototypes and function headers                                   */\n/* ------------------------------------------------------------------------- */\n#include \"lp_Hash.h\"\n\n\n/* Sparse matrix prototypes                                                  */\n/* ------------------------------------------------------------------------- */\n#include \"lp_matrix.h\"\n\n\n/* Basis storage (mainly for B&B) */\ntypedef struct _basisrec\n{\n  int       level;\n  int       *var_basic;\n  MYBOOL    *is_basic;\n  MYBOOL    *is_lower;\n  int       pivots;\n  struct   _basisrec *previous;\n} basisrec;\n\n/* Presolve undo data storage */\ntypedef struct _presolveundorec\n{\n  lprec     *lp;\n  int       orig_rows;\n  int       orig_columns;\n  int       orig_sum;\n  int       *var_to_orig;       /* sum_alloc+1 : Mapping of variables from solution to\n                                   best_solution to account for removed variables and\n                                   rows during presolve; a non-positive value indicates\n                                   that the constraint or variable was removed */\n  int       *orig_to_var;       /* sum_alloc+1 : Mapping from original variable index to\n                                   current / working index number */\n  REAL      *fixed_rhs;         /* rows_alloc+1 : Storage of values of presolved fixed colums */\n  REAL      *fixed_obj;         /* columns_alloc+1: Storage of values of presolved fixed rows */\n  DeltaVrec *deletedA;          /* A matrix of eliminated data from matA */\n  DeltaVrec *primalundo;        /* Affine translation vectors for eliminated primal variables */\n  DeltaVrec *dualundo;          /* Affine translation vectors for eliminated dual variables */\n  MYBOOL    OFcolsdeleted;\n} presolveundorec;\n\n/* Pseudo-cost arrays used during B&B */\ntypedef struct _BBPSrec\n{\n  lprec     *lp;\n  int       pseodotype;\n  int       updatelimit;\n  int       updatesfinished;\n  REAL      restartlimit;\n  MATitem   *UPcost;\n  MATitem   *LOcost;\n  struct   _BBPSrec *secondary;\n} BBPSrec;\n\n#include \"lp_mipbb.h\"\n\n\n/* Partial pricing block data */\ntypedef struct _partialrec {\n  lprec     *lp;\n  int       blockcount;         /* ## The number of logical blocks or stages in the model */\n  int       blocknow;           /* The currently active block */\n  int       *blockend;          /* Array of column indeces giving the start of each block */\n  int       *blockpos;          /* Array of column indeces giving the start scan position */\n  MYBOOL    isrow;\n} partialrec;\n\n\n/* Specially Ordered Sets (SOS) prototypes and settings                      */\n/* ------------------------------------------------------------------------- */\n/* SOS storage structure (LINEARSEARCH is typically in the 0-10 range)       */\n#ifndef LINEARSEARCH\n#define LINEARSEARCH 0\n#endif\n\n#include \"lp_SOS.h\"\n\n\n/* Prototypes for user call-back functions                                   */\n/* ------------------------------------------------------------------------- */\ntypedef int    (__WINAPI lphandle_intfunc)(lprec *lp, void *userhandle);\ntypedef void   (__WINAPI lphandlestr_func)(lprec *lp, void *userhandle, char *buf);\ntypedef void   (__WINAPI lphandleint_func)(lprec *lp, void *userhandle, int message);\ntypedef int    (__WINAPI lphandleint_intfunc)(lprec *lp, void *userhandle, int message);\n\n\n/* API typedef definitions                                                   */\n/* ------------------------------------------------------------------------- */\ntypedef MYBOOL (__WINAPI add_column_func)(lprec *lp, REAL *column);\ntypedef MYBOOL (__WINAPI add_columnex_func)(lprec *lp, int count, REAL *column, int *rowno);\ntypedef MYBOOL (__WINAPI add_constraint_func)(lprec *lp, REAL *row, int constr_type, REAL rh);\ntypedef MYBOOL (__WINAPI add_constraintex_func)(lprec *lp, int count, REAL *row, int *colno, int constr_type, REAL rh);\ntypedef MYBOOL (__WINAPI add_lag_con_func)(lprec *lp, REAL *row, int con_type, REAL rhs);\ntypedef int (__WINAPI add_SOS_func)(lprec *lp, char *name, int sostype, int priority, int count, int *sosvars, REAL *weights);\ntypedef int (__WINAPI column_in_lp_func)(lprec *lp, REAL *column);\ntypedef lprec * (__WINAPI copy_lp_func)(lprec *lp);\ntypedef void (__WINAPI default_basis_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI del_column_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI del_constraint_func)(lprec *lp, int rownr);\ntypedef void (__WINAPI delete_lp_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI dualize_lp_func)(lprec *lp);\ntypedef void (__WINAPI free_lp_func)(lprec **plp);\ntypedef int (__WINAPI get_anti_degen_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_basis_func)(lprec *lp, int *bascolumn, MYBOOL nonbasic);\ntypedef int (__WINAPI get_basiscrash_func)(lprec *lp);\ntypedef int (__WINAPI get_bb_depthlimit_func)(lprec *lp);\ntypedef int (__WINAPI get_bb_floorfirst_func)(lprec *lp);\ntypedef int (__WINAPI get_bb_rule_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_bounds_tighter_func)(lprec *lp);\ntypedef REAL (__WINAPI get_break_at_value_func)(lprec *lp);\ntypedef char * (__WINAPI get_col_name_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI get_column_func)(lprec *lp, int colnr, REAL *column);\ntypedef int (__WINAPI get_columnex_func)(lprec *lp, int colnr, REAL *column, int *nzrow);\ntypedef int (__WINAPI get_constr_type_func)(lprec *lp, int rownr);\ntypedef REAL (__WINAPI get_constr_value_func)(lprec *lp, int rownr, int count, REAL *primsolution, int *nzindex);\ntypedef MYBOOL (__WINAPI get_constraints_func)(lprec *lp, REAL *constr);\ntypedef MYBOOL (__WINAPI get_dual_solution_func)(lprec *lp, REAL *rc);\ntypedef REAL (__WINAPI get_epsb_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epsd_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epsel_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epsint_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epsperturb_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epspivot_func)(lprec *lp);\ntypedef int (__WINAPI get_improve_func)(lprec *lp);\ntypedef REAL (__WINAPI get_infinite_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_lambda_func)(lprec *lp, REAL *lambda);\ntypedef REAL (__WINAPI get_lowbo_func)(lprec *lp, int colnr);\ntypedef int (__WINAPI get_lp_index_func)(lprec *lp, int orig_index);\ntypedef char * (__WINAPI get_lp_name_func)(lprec *lp);\ntypedef int (__WINAPI get_Lrows_func)(lprec *lp);\ntypedef REAL (__WINAPI get_mat_func)(lprec *lp, int rownr, int colnr);\ntypedef REAL (__WINAPI get_mat_byindex_func)(lprec *lp, int matindex, MYBOOL isrow, MYBOOL adjustsign);\ntypedef int (__WINAPI get_max_level_func)(lprec *lp);\ntypedef int (__WINAPI get_maxpivot_func)(lprec *lp);\ntypedef REAL (__WINAPI get_mip_gap_func)(lprec *lp, MYBOOL absolute);\ntypedef int (__WINAPI get_multiprice_func)(lprec *lp, MYBOOL getabssize);\ntypedef MYBOOL (__WINAPI is_use_names_func)(lprec *lp, MYBOOL isrow);\ntypedef void (__WINAPI set_use_names_func)(lprec *lp, MYBOOL isrow, MYBOOL use_names);\ntypedef int (__WINAPI get_nameindex_func)(lprec *lp, char *varname, MYBOOL isrow);\ntypedef int (__WINAPI get_Ncolumns_func)(lprec *lp);\ntypedef REAL (__WINAPI get_negrange_func)(lprec *lp);\ntypedef int (__WINAPI get_nz_func)(lprec *lp);\ntypedef int (__WINAPI get_Norig_columns_func)(lprec *lp);\ntypedef int (__WINAPI get_Norig_rows_func)(lprec *lp);\ntypedef int (__WINAPI get_Nrows_func)(lprec *lp);\ntypedef REAL (__WINAPI get_obj_bound_func)(lprec *lp);\ntypedef REAL (__WINAPI get_objective_func)(lprec *lp);\ntypedef int (__WINAPI get_orig_index_func)(lprec *lp, int lp_index);\ntypedef char * (__WINAPI get_origcol_name_func)(lprec *lp, int colnr);\ntypedef char * (__WINAPI get_origrow_name_func)(lprec *lp, int rownr);\ntypedef void (__WINAPI get_partialprice_func)(lprec *lp, int *blockcount, int *blockstart, MYBOOL isrow);\ntypedef int (__WINAPI get_pivoting_func)(lprec *lp);\ntypedef int (__WINAPI get_presolve_func)(lprec *lp);\ntypedef int (__WINAPI get_presolveloops_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_primal_solution_func)(lprec *lp, REAL *pv);\ntypedef int (__WINAPI get_print_sol_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_pseudocosts_func)(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit);\ntypedef MYBOOL (__WINAPI get_ptr_constraints_func)(lprec *lp, REAL **constr);\ntypedef MYBOOL (__WINAPI get_ptr_dual_solution_func)(lprec *lp, REAL **rc);\ntypedef MYBOOL (__WINAPI get_ptr_lambda_func)(lprec *lp, REAL **lambda);\ntypedef MYBOOL (__WINAPI get_ptr_primal_solution_func)(lprec *lp, REAL **pv);\ntypedef MYBOOL (__WINAPI get_ptr_sensitivity_obj_func)(lprec *lp, REAL **objfrom, REAL **objtill);\ntypedef MYBOOL (__WINAPI get_ptr_sensitivity_objex_func)(lprec *lp, REAL **objfrom, REAL **objtill, REAL **objfromvalue, REAL **objtillvalue);\ntypedef MYBOOL (__WINAPI get_ptr_sensitivity_rhs_func)(lprec *lp, REAL **duals, REAL **dualsfrom, REAL **dualstill);\ntypedef MYBOOL (__WINAPI get_ptr_variables_func)(lprec *lp, REAL **var);\ntypedef REAL (__WINAPI get_rh_func)(lprec *lp, int rownr);\ntypedef REAL (__WINAPI get_rh_range_func)(lprec *lp, int rownr);\ntypedef int (__WINAPI get_rowex_func)(lprec *lp, int rownr, REAL *row, int *colno);\ntypedef MYBOOL (__WINAPI get_row_func)(lprec *lp, int rownr, REAL *row);\ntypedef char * (__WINAPI get_row_name_func)(lprec *lp, int rownr);\ntypedef REAL (__WINAPI get_scalelimit_func)(lprec *lp);\ntypedef int (__WINAPI get_scaling_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_sensitivity_obj_func)(lprec *lp, REAL *objfrom, REAL *objtill);\ntypedef MYBOOL (__WINAPI get_sensitivity_objex_func)(lprec *lp, REAL *objfrom, REAL *objtill, REAL *objfromvalue, REAL *objtillvalue);\ntypedef MYBOOL (__WINAPI get_sensitivity_rhs_func)(lprec *lp, REAL *duals, REAL *dualsfrom, REAL *dualstill);\ntypedef int (__WINAPI get_simplextype_func)(lprec *lp);\ntypedef int (__WINAPI get_solutioncount_func)(lprec *lp);\ntypedef int (__WINAPI get_solutionlimit_func)(lprec *lp);\ntypedef int (__WINAPI get_status_func)(lprec *lp);\ntypedef char * (__WINAPI get_statustext_func)(lprec *lp, int statuscode);\ntypedef long (__WINAPI get_timeout_func)(lprec *lp);\ntypedef COUNTER (__WINAPI get_total_iter_func)(lprec *lp);\ntypedef COUNTER (__WINAPI get_total_nodes_func)(lprec *lp);\ntypedef REAL (__WINAPI get_upbo_func)(lprec *lp, int colnr);\ntypedef int (__WINAPI get_var_branch_func)(lprec *lp, int colnr);\ntypedef REAL (__WINAPI get_var_dualresult_func)(lprec *lp, int index);\ntypedef REAL (__WINAPI get_var_primalresult_func)(lprec *lp, int index);\ntypedef int (__WINAPI get_var_priority_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI get_variables_func)(lprec *lp, REAL *var);\ntypedef int (__WINAPI get_verbose_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI guess_basis_func)(lprec *lp, REAL *guessvector, int *basisvector);\ntypedef REAL (__WINAPI get_working_objective_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI has_BFP_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI has_XLI_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_add_rowmode_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_anti_degen_func)(lprec *lp, int testmask);\ntypedef MYBOOL (__WINAPI is_binary_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_break_at_first_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_constr_type_func)(lprec *lp, int rownr, int mask);\ntypedef MYBOOL (__WINAPI is_debug_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_feasible_func)(lprec *lp, REAL *values, REAL threshold);\ntypedef MYBOOL (__WINAPI is_unbounded_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_infinite_func)(lprec *lp, REAL value);\ntypedef MYBOOL (__WINAPI is_int_func)(lprec *lp, int column);\ntypedef MYBOOL (__WINAPI is_integerscaling_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_lag_trace_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_maxim_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_nativeBFP_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_nativeXLI_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_negative_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_obj_in_basis_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_piv_mode_func)(lprec *lp, int testmask);\ntypedef MYBOOL (__WINAPI is_piv_rule_func)(lprec *lp, int rule);\ntypedef MYBOOL (__WINAPI is_presolve_func)(lprec *lp, int testmask);\ntypedef MYBOOL (__WINAPI is_scalemode_func)(lprec *lp, int testmask);\ntypedef MYBOOL (__WINAPI is_scaletype_func)(lprec *lp, int scaletype);\ntypedef MYBOOL (__WINAPI is_semicont_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_SOS_var_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_trace_func)(lprec *lp);\ntypedef void (__WINAPI lp_solve_version_func)(int *majorversion, int *minorversion, int *release, int *build);\ntypedef lprec * (__WINAPI make_lp_func)(int rows, int columns);\ntypedef void (__WINAPI print_constraints_func)(lprec *lp, int columns);\ntypedef MYBOOL (__WINAPI print_debugdump_func)(lprec *lp, char *filename);\ntypedef void (__WINAPI print_duals_func)(lprec *lp);\ntypedef void (__WINAPI print_lp_func)(lprec *lp);\ntypedef void (__WINAPI print_objective_func)(lprec *lp);\ntypedef void (__WINAPI print_scales_func)(lprec *lp);\ntypedef void (__WINAPI print_solution_func)(lprec *lp, int columns);\ntypedef void (__WINAPI print_str_func)(lprec *lp, char *str);\ntypedef void (__WINAPI print_tableau_func)(lprec *lp);\ntypedef void (__WINAPI put_abortfunc_func)(lprec *lp, lphandle_intfunc newctrlc, void *ctrlchandle);\ntypedef void (__WINAPI put_bb_nodefunc_func)(lprec *lp, lphandleint_intfunc newnode, void *bbnodehandle);\ntypedef void (__WINAPI put_bb_branchfunc_func)(lprec *lp, lphandleint_intfunc newbranch, void *bbbranchhandle);\ntypedef void (__WINAPI put_logfunc_func)(lprec *lp, lphandlestr_func newlog, void *loghandle);\ntypedef void (__WINAPI put_msgfunc_func)(lprec *lp, lphandleint_func newmsg, void *msghandle, int mask);\ntypedef lprec * (__WINAPI read_LP_func)(char *filename, int verbose, char *lp_name);\ntypedef lprec * (__WINAPI read_MPS_func)(char *filename, int options);\ntypedef lprec * (__WINAPI read_XLI_func)(char *xliname, char *modelname, char *dataname, char *options, int verbose);\ntypedef MYBOOL (__WINAPI read_basis_func)(lprec *lp, char *filename, char *info);\ntypedef void (__WINAPI reset_basis_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI read_params_func)(lprec *lp, char *filename, char *options);\ntypedef void (__WINAPI reset_params_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI resize_lp_func)(lprec *lp, int rows, int columns);\ntypedef MYBOOL (__WINAPI set_add_rowmode_func)(lprec *lp, MYBOOL turnon);\ntypedef void (__WINAPI set_anti_degen_func)(lprec *lp, int anti_degen);\ntypedef int  (__WINAPI set_basisvar_func)(lprec *lp, int basisPos, int enteringCol);\ntypedef MYBOOL (__WINAPI set_basis_func)(lprec *lp, int *bascolumn, MYBOOL nonbasic);\ntypedef void (__WINAPI set_basiscrash_func)(lprec *lp, int mode);\ntypedef void (__WINAPI set_bb_depthlimit_func)(lprec *lp, int bb_maxlevel);\ntypedef void (__WINAPI set_bb_floorfirst_func)(lprec *lp, int bb_floorfirst);\ntypedef void (__WINAPI set_bb_rule_func)(lprec *lp, int bb_rule);\ntypedef MYBOOL (__WINAPI set_BFP_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI set_binary_func)(lprec *lp, int colnr, MYBOOL must_be_bin);\ntypedef MYBOOL (__WINAPI set_bounds_func)(lprec *lp, int colnr, REAL lower, REAL upper);\ntypedef void (__WINAPI set_bounds_tighter_func)(lprec *lp, MYBOOL tighten);\ntypedef void (__WINAPI set_break_at_first_func)(lprec *lp, MYBOOL break_at_first);\ntypedef void (__WINAPI set_break_at_value_func)(lprec *lp, REAL break_at_value);\ntypedef MYBOOL (__WINAPI set_column_func)(lprec *lp, int colnr, REAL *column);\ntypedef MYBOOL (__WINAPI set_columnex_func)(lprec *lp, int colnr, int count, REAL *column, int *rowno);\ntypedef MYBOOL (__WINAPI set_col_name_func)(lprec *lp, int colnr, char *new_name);\ntypedef MYBOOL (__WINAPI set_constr_type_func)(lprec *lp, int rownr, int con_type);\ntypedef void (__WINAPI set_debug_func)(lprec *lp, MYBOOL debug);\ntypedef void (__WINAPI set_epsb_func)(lprec *lp, REAL epsb);\ntypedef void (__WINAPI set_epsd_func)(lprec *lp, REAL epsd);\ntypedef void (__WINAPI set_epsel_func)(lprec *lp, REAL epsel);\ntypedef void (__WINAPI set_epsint_func)(lprec *lp, REAL epsint);\ntypedef MYBOOL (__WINAPI set_epslevel_func)(lprec *lp, int epslevel);\ntypedef void (__WINAPI set_epsperturb_func)(lprec *lp, REAL epsperturb);\ntypedef void (__WINAPI set_epspivot_func)(lprec *lp, REAL epspivot);\ntypedef MYBOOL (__WINAPI set_unbounded_func)(lprec *lp, int colnr);\ntypedef void (__WINAPI set_improve_func)(lprec *lp, int improve);\ntypedef void (__WINAPI set_infinite_func)(lprec *lp, REAL infinite);\ntypedef MYBOOL (__WINAPI set_int_func)(lprec *lp, int colnr, MYBOOL must_be_int);\ntypedef void (__WINAPI set_lag_trace_func)(lprec *lp, MYBOOL lag_trace);\ntypedef MYBOOL (__WINAPI set_lowbo_func)(lprec *lp, int colnr, REAL value);\ntypedef MYBOOL (__WINAPI set_lp_name_func)(lprec *lp, char *lpname);\ntypedef MYBOOL (__WINAPI set_mat_func)(lprec *lp, int row, int column, REAL value);\ntypedef void (__WINAPI set_maxim_func)(lprec *lp);\ntypedef void (__WINAPI set_maxpivot_func)(lprec *lp, int max_num_inv);\ntypedef void (__WINAPI set_minim_func)(lprec *lp);\ntypedef void (__WINAPI set_mip_gap_func)(lprec *lp, MYBOOL absolute, REAL mip_gap);\ntypedef MYBOOL (__WINAPI set_multiprice_func)(lprec *lp, int multiblockdiv);\ntypedef void (__WINAPI set_negrange_func)(lprec *lp, REAL negrange);\ntypedef MYBOOL (__WINAPI set_obj_func)(lprec *lp, int colnr, REAL value);\ntypedef void (__WINAPI set_obj_bound_func)(lprec *lp, REAL obj_bound);\ntypedef MYBOOL (__WINAPI set_obj_fn_func)(lprec *lp, REAL *row);\ntypedef MYBOOL (__WINAPI set_obj_fnex_func)(lprec *lp, int count, REAL *row, int *colno);\ntypedef void (__WINAPI set_obj_in_basis_func)(lprec *lp, MYBOOL obj_in_basis);\ntypedef MYBOOL (__WINAPI set_outputfile_func)(lprec *lp, char *filename);\ntypedef void (__WINAPI set_outputstream_func)(lprec *lp, FILE *stream);\ntypedef MYBOOL (__WINAPI set_partialprice_func)(lprec *lp, int blockcount, int *blockstart, MYBOOL isrow);\ntypedef void (__WINAPI set_pivoting_func)(lprec *lp, int piv_rule);\ntypedef void (__WINAPI set_preferdual_func)(lprec *lp, MYBOOL dodual);\ntypedef void (__WINAPI set_presolve_func)(lprec *lp, int presolvemode, int maxloops);\ntypedef void (__WINAPI set_print_sol_func)(lprec *lp, int print_sol);\ntypedef MYBOOL (__WINAPI set_pseudocosts_func)(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit);\ntypedef MYBOOL (__WINAPI set_rh_func)(lprec *lp, int rownr, REAL value);\ntypedef MYBOOL (__WINAPI set_rh_range_func)(lprec *lp, int rownr, REAL deltavalue);\ntypedef void (__WINAPI set_rh_vec_func)(lprec *lp, REAL *rh);\ntypedef MYBOOL (__WINAPI set_row_func)(lprec *lp, int rownr, REAL *row);\ntypedef MYBOOL (__WINAPI set_rowex_func)(lprec *lp, int rownr, int count, REAL *row, int *colno);\ntypedef MYBOOL (__WINAPI set_row_name_func)(lprec *lp, int rownr, char *new_name);\ntypedef void (__WINAPI set_scalelimit_func)(lprec *lp, REAL scalelimit);\ntypedef void (__WINAPI set_scaling_func)(lprec *lp, int scalemode);\ntypedef MYBOOL (__WINAPI set_semicont_func)(lprec *lp, int colnr, MYBOOL must_be_sc);\ntypedef void (__WINAPI set_sense_func)(lprec *lp, MYBOOL maximize);\ntypedef void (__WINAPI set_simplextype_func)(lprec *lp, int simplextype);\ntypedef void (__WINAPI set_solutionlimit_func)(lprec *lp, int limit);\ntypedef void (__WINAPI set_timeout_func)(lprec *lp, long sectimeout);\ntypedef void (__WINAPI set_trace_func)(lprec *lp, MYBOOL trace);\ntypedef MYBOOL (__WINAPI set_upbo_func)(lprec *lp, int colnr, REAL value);\ntypedef MYBOOL (__WINAPI set_var_branch_func)(lprec *lp, int colnr, int branch_mode);\ntypedef MYBOOL (__WINAPI set_var_weights_func)(lprec *lp, REAL *weights);\ntypedef void (__WINAPI set_verbose_func)(lprec *lp, int verbose);\ntypedef MYBOOL (__WINAPI set_XLI_func)(lprec *lp, char *filename);\ntypedef int (__WINAPI solve_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI str_add_column_func)(lprec *lp, char *col_string);\ntypedef MYBOOL (__WINAPI str_add_constraint_func)(lprec *lp, char *row_string ,int constr_type, REAL rh);\ntypedef MYBOOL (__WINAPI str_add_lag_con_func)(lprec *lp, char *row_string, int con_type, REAL rhs);\ntypedef MYBOOL (__WINAPI str_set_obj_fn_func)(lprec *lp, char *row_string);\ntypedef MYBOOL (__WINAPI str_set_rh_vec_func)(lprec *lp, char *rh_string);\ntypedef REAL (__WINAPI time_elapsed_func)(lprec *lp);\ntypedef void (__WINAPI unscale_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI write_lp_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI write_LP_func)(lprec *lp, FILE *output);\ntypedef MYBOOL (__WINAPI write_mps_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI write_MPS_func)(lprec *lp, FILE *output);\ntypedef MYBOOL (__WINAPI write_freemps_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI write_freeMPS_func)(lprec *lp, FILE *output);\ntypedef MYBOOL (__WINAPI write_XLI_func)(lprec *lp, char *filename, char *options, MYBOOL results);\ntypedef MYBOOL (__WINAPI write_basis_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI write_params_func)(lprec *lp, char *filename, char *options);\n\n\n/* Prototypes for callbacks from basis inverse/factorization libraries       */\n/* ------------------------------------------------------------------------- */\ntypedef MYBOOL (__WINAPI userabortfunc)(lprec *lp, int level);\ntypedef void   (__VACALL reportfunc)(lprec *lp, int level, char *format, ...);\ntypedef char * (__VACALL explainfunc)(lprec *lp, char *format, ...);\ntypedef int    (__WINAPI getvectorfunc)(lprec *lp, int varin, REAL *pcol, int *nzlist, int *maxabs);\ntypedef int    (__WINAPI getpackedfunc)(lprec *lp, int j, int rn[], double bj[]);\ntypedef REAL    (__WINAPI get_OF_activefunc)(lprec *lp, int varnr, REAL mult);\ntypedef int    (__WINAPI getMDOfunc)(lprec *lp, MYBOOL *usedpos, int *colorder, int *size, MYBOOL symmetric);\ntypedef MYBOOL (__WINAPI invertfunc)(lprec *lp, MYBOOL shiftbounds, MYBOOL final);\ntypedef void   (__WINAPI set_actionfunc)(int *actionvar, int actionmask);\ntypedef MYBOOL (__WINAPI is_actionfunc)(int actionvar, int testmask);\ntypedef void   (__WINAPI clear_actionfunc)(int *actionvar, int actionmask);\n\n\n/* Prototypes for basis inverse/factorization libraries                      */\n/* ------------------------------------------------------------------------- */\ntypedef char   *(BFP_CALLMODEL BFPchar)(void);\ntypedef void   (BFP_CALLMODEL BFP_lp)(lprec *lp);\ntypedef void   (BFP_CALLMODEL BFP_lpint)(lprec *lp, int newsize);\ntypedef int    (BFP_CALLMODEL BFPint_lp)(lprec *lp);\ntypedef int    (BFP_CALLMODEL BFPint_lpint)(lprec *lp, int kind);\ntypedef REAL   (BFP_CALLMODEL BFPreal_lp)(lprec *lp);\ntypedef REAL   *(BFP_CALLMODEL BFPrealp_lp)(lprec *lp);\ntypedef void   (BFP_CALLMODEL BFP_lpbool)(lprec *lp, MYBOOL maximum);\ntypedef int    (BFP_CALLMODEL BFPint_lpbool)(lprec *lp, MYBOOL maximum);\ntypedef int    (BFP_CALLMODEL BFPint_lpintintboolbool)(lprec *lp, int uservars, int Bsize, MYBOOL *usedpos, MYBOOL final);\ntypedef void   (BFP_CALLMODEL BFP_lprealint)(lprec *lp, REAL *pcol, int *nzidx);\ntypedef void   (BFP_CALLMODEL BFP_lprealintrealint)(lprec *lp, REAL *prow, int *pnzidx, REAL *drow, int *dnzidx);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lp)(lprec *lp);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lpbool)(lprec *lp, MYBOOL changesign);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lpint)(lprec *lp, int size);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lpintintchar)(lprec *lp, int size, int deltasize, char *options);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lpintintint)(lprec *lp, int size, int deltasize, int sizeofvar);\ntypedef LREAL  (BFP_CALLMODEL BFPlreal_lpintintreal)(lprec *lp, int row_nr, int col_nr, REAL *pcol);\ntypedef REAL   (BFP_CALLMODEL BFPreal_lplrealreal)(lprec *lp, LREAL theta, REAL *pcol);\n\ntypedef int    (BFP_CALLMODEL getcolumnex_func)(lprec *lp, int colnr, REAL *nzvalues, int *nzrows, int *mapin);\ntypedef int    (BFP_CALLMODEL BFPint_lpintrealcbintint)(lprec *lp, int items, getcolumnex_func cb, int *maprow, int*mapcol);\n\n/* Prototypes for external language libraries                                */\n/* ------------------------------------------------------------------------- */\ntypedef char   *(XLI_CALLMODEL XLIchar)(void);\ntypedef MYBOOL (XLI_CALLMODEL XLIbool_lpintintint)(lprec* lp, int size, int deltasize, int sizevar);\ntypedef MYBOOL (XLI_CALLMODEL XLIbool_lpcharcharcharint)(lprec *lp, char *modelname, char *dataname, char *options, int verbose);\ntypedef MYBOOL (XLI_CALLMODEL XLIbool_lpcharcharbool)(lprec *lp, char *filename, char *options, MYBOOL results);\n\n\n/* Main lp_solve prototypes and function definitions                         */\n/* ------------------------------------------------------------------------- */\nstruct _lprec\n{\n  /* Full list of exported functions made available in a quasi object-oriented fashion */\n  add_column_func               *add_column;\n  add_columnex_func             *add_columnex;\n  add_constraint_func           *add_constraint;\n  add_constraintex_func         *add_constraintex;\n  add_lag_con_func              *add_lag_con;\n  add_SOS_func                  *add_SOS;\n  column_in_lp_func             *column_in_lp;\n  copy_lp_func                  *copy_lp;\n  default_basis_func            *default_basis;\n  del_column_func               *del_column;\n  del_constraint_func           *del_constraint;\n  delete_lp_func                *delete_lp;\n  dualize_lp_func               *dualize_lp;\n  free_lp_func                  *free_lp;\n  get_anti_degen_func           *get_anti_degen;\n  get_basis_func                *get_basis;\n  get_basiscrash_func           *get_basiscrash;\n  get_bb_depthlimit_func        *get_bb_depthlimit;\n  get_bb_floorfirst_func        *get_bb_floorfirst;\n  get_bb_rule_func              *get_bb_rule;\n  get_bounds_tighter_func       *get_bounds_tighter;\n  get_break_at_value_func       *get_break_at_value;\n  get_col_name_func             *get_col_name;\n  get_columnex_func             *get_columnex;\n  get_constr_type_func          *get_constr_type;\n  get_constr_value_func         *get_constr_value;\n  get_constraints_func          *get_constraints;\n  get_dual_solution_func        *get_dual_solution;\n  get_epsb_func                 *get_epsb;\n  get_epsd_func                 *get_epsd;\n  get_epsel_func                *get_epsel;\n  get_epsint_func               *get_epsint;\n  get_epsperturb_func           *get_epsperturb;\n  get_epspivot_func             *get_epspivot;\n  get_improve_func              *get_improve;\n  get_infinite_func             *get_infinite;\n  get_lambda_func               *get_lambda;\n  get_lowbo_func                *get_lowbo;\n  get_lp_index_func             *get_lp_index;\n  get_lp_name_func              *get_lp_name;\n  get_Lrows_func                *get_Lrows;\n  get_mat_func                  *get_mat;\n  get_mat_byindex_func          *get_mat_byindex;\n  get_max_level_func            *get_max_level;\n  get_maxpivot_func             *get_maxpivot;\n  get_mip_gap_func              *get_mip_gap;\n  get_multiprice_func           *get_multiprice;\n  get_nameindex_func            *get_nameindex;\n  get_Ncolumns_func             *get_Ncolumns;\n  get_negrange_func             *get_negrange;\n  get_nz_func                   *get_nonzeros;\n  get_Norig_columns_func        *get_Norig_columns;\n  get_Norig_rows_func           *get_Norig_rows;\n  get_Nrows_func                *get_Nrows;\n  get_obj_bound_func            *get_obj_bound;\n  get_objective_func            *get_objective;\n  get_orig_index_func           *get_orig_index;\n  get_origcol_name_func         *get_origcol_name;\n  get_origrow_name_func         *get_origrow_name;\n  get_partialprice_func         *get_partialprice;\n  get_pivoting_func             *get_pivoting;\n  get_presolve_func             *get_presolve;\n  get_presolveloops_func        *get_presolveloops;\n  get_primal_solution_func      *get_primal_solution;\n  get_print_sol_func            *get_print_sol;\n  get_pseudocosts_func          *get_pseudocosts;\n  get_ptr_constraints_func      *get_ptr_constraints;\n  get_ptr_dual_solution_func    *get_ptr_dual_solution;\n  get_ptr_lambda_func           *get_ptr_lambda;\n  get_ptr_primal_solution_func  *get_ptr_primal_solution;\n  get_ptr_sensitivity_obj_func  *get_ptr_sensitivity_obj;\n  get_ptr_sensitivity_objex_func *get_ptr_sensitivity_objex;\n  get_ptr_sensitivity_rhs_func  *get_ptr_sensitivity_rhs;\n  get_ptr_variables_func        *get_ptr_variables;\n  get_rh_func                   *get_rh;\n  get_rh_range_func             *get_rh_range;\n  get_row_func                  *get_row;\n  get_rowex_func                *get_rowex;\n  get_row_name_func             *get_row_name;\n  get_scalelimit_func           *get_scalelimit;\n  get_scaling_func              *get_scaling;\n  get_sensitivity_obj_func      *get_sensitivity_obj;\n  get_sensitivity_objex_func    *get_sensitivity_objex;\n  get_sensitivity_rhs_func      *get_sensitivity_rhs;\n  get_simplextype_func          *get_simplextype;\n  get_solutioncount_func        *get_solutioncount;\n  get_solutionlimit_func        *get_solutionlimit;\n  get_status_func               *get_status;\n  get_statustext_func           *get_statustext;\n  get_timeout_func              *get_timeout;\n  get_total_iter_func           *get_total_iter;\n  get_total_nodes_func          *get_total_nodes;\n  get_upbo_func                 *get_upbo;\n  get_var_branch_func           *get_var_branch;\n  get_var_dualresult_func       *get_var_dualresult;\n  get_var_primalresult_func     *get_var_primalresult;\n  get_var_priority_func         *get_var_priority;\n  get_variables_func            *get_variables;\n  get_verbose_func              *get_verbose;\n  get_working_objective_func    *get_working_objective;\n  has_BFP_func                  *has_BFP;\n  has_XLI_func                  *has_XLI;\n  is_add_rowmode_func           *is_add_rowmode;\n  is_anti_degen_func            *is_anti_degen;\n  is_binary_func                *is_binary;\n  is_break_at_first_func        *is_break_at_first;\n  is_constr_type_func           *is_constr_type;\n  is_debug_func                 *is_debug;\n  is_feasible_func              *is_feasible;\n  is_infinite_func              *is_infinite;\n  is_int_func                   *is_int;\n  is_integerscaling_func        *is_integerscaling;\n  is_lag_trace_func             *is_lag_trace;\n  is_maxim_func                 *is_maxim;\n  is_nativeBFP_func             *is_nativeBFP;\n  is_nativeXLI_func             *is_nativeXLI;\n  is_negative_func              *is_negative;\n  is_obj_in_basis_func          *is_obj_in_basis;\n  is_piv_mode_func              *is_piv_mode;\n  is_piv_rule_func              *is_piv_rule;\n  is_presolve_func              *is_presolve;\n  is_scalemode_func             *is_scalemode;\n  is_scaletype_func             *is_scaletype;\n  is_semicont_func              *is_semicont;\n  is_SOS_var_func               *is_SOS_var;\n  is_trace_func                 *is_trace;\n  is_unbounded_func             *is_unbounded;\n  is_use_names_func             *is_use_names;\n  lp_solve_version_func         *lp_solve_version;\n  make_lp_func                  *make_lp;\n  print_constraints_func        *print_constraints;\n  print_debugdump_func          *print_debugdump;\n  print_duals_func              *print_duals;\n  print_lp_func                 *print_lp;\n  print_objective_func          *print_objective;\n  print_scales_func             *print_scales;\n  print_solution_func           *print_solution;\n  print_str_func                *print_str;\n  print_tableau_func            *print_tableau;\n  put_abortfunc_func            *put_abortfunc;\n  put_bb_nodefunc_func          *put_bb_nodefunc;\n  put_bb_branchfunc_func        *put_bb_branchfunc;\n  put_logfunc_func              *put_logfunc;\n  put_msgfunc_func              *put_msgfunc;\n  read_LP_func                  *read_LP;\n  read_MPS_func                 *read_MPS;\n  read_XLI_func                 *read_XLI;\n  read_params_func              *read_params;\n  read_basis_func               *read_basis;\n  reset_basis_func              *reset_basis;\n  reset_params_func             *reset_params;\n  resize_lp_func                *resize_lp;\n  set_add_rowmode_func          *set_add_rowmode;\n  set_anti_degen_func           *set_anti_degen;\n  set_basisvar_func             *set_basisvar;\n  set_basis_func                *set_basis;\n  set_basiscrash_func           *set_basiscrash;\n  set_bb_depthlimit_func        *set_bb_depthlimit;\n  set_bb_floorfirst_func        *set_bb_floorfirst;\n  set_bb_rule_func              *set_bb_rule;\n  set_BFP_func                  *set_BFP;\n  set_binary_func               *set_binary;\n  set_bounds_func               *set_bounds;\n  set_bounds_tighter_func       *set_bounds_tighter;\n  set_break_at_first_func       *set_break_at_first;\n  set_break_at_value_func       *set_break_at_value;\n  set_column_func               *set_column;\n  set_columnex_func             *set_columnex;\n  set_col_name_func             *set_col_name;\n  set_constr_type_func          *set_constr_type;\n  set_debug_func                *set_debug;\n  set_epsb_func                 *set_epsb;\n  set_epsd_func                 *set_epsd;\n  set_epsel_func                *set_epsel;\n  set_epsint_func               *set_epsint;\n  set_epslevel_func             *set_epslevel;\n  set_epsperturb_func           *set_epsperturb;\n  set_epspivot_func             *set_epspivot;\n  set_unbounded_func            *set_unbounded;\n  set_improve_func              *set_improve;\n  set_infinite_func             *set_infinite;\n  set_int_func                  *set_int;\n  set_lag_trace_func            *set_lag_trace;\n  set_lowbo_func                *set_lowbo;\n  set_lp_name_func              *set_lp_name;\n  set_mat_func                  *set_mat;\n  set_maxim_func                *set_maxim;\n  set_maxpivot_func             *set_maxpivot;\n  set_minim_func                *set_minim;\n  set_mip_gap_func              *set_mip_gap;\n  set_multiprice_func           *set_multiprice;\n  set_negrange_func             *set_negrange;\n  set_obj_bound_func            *set_obj_bound;\n  set_obj_fn_func               *set_obj_fn;\n  set_obj_fnex_func             *set_obj_fnex;\n  set_obj_func                  *set_obj;\n  set_obj_in_basis_func         *set_obj_in_basis;\n  set_outputfile_func           *set_outputfile;\n  set_outputstream_func         *set_outputstream;\n  set_partialprice_func         *set_partialprice;\n  set_pivoting_func             *set_pivoting;\n  set_preferdual_func           *set_preferdual;\n  set_presolve_func             *set_presolve;\n  set_print_sol_func            *set_print_sol;\n  set_pseudocosts_func          *set_pseudocosts;\n  set_rh_func                   *set_rh;\n  set_rh_range_func             *set_rh_range;\n  set_rh_vec_func               *set_rh_vec;\n  set_row_func                  *set_row;\n  set_rowex_func                *set_rowex;\n  set_row_name_func             *set_row_name;\n  set_scalelimit_func           *set_scalelimit;\n  set_scaling_func              *set_scaling;\n  set_semicont_func             *set_semicont;\n  set_sense_func                *set_sense;\n  set_simplextype_func          *set_simplextype;\n  set_solutionlimit_func        *set_solutionlimit;\n  set_timeout_func              *set_timeout;\n  set_trace_func                *set_trace;\n  set_upbo_func                 *set_upbo;\n  set_use_names_func            *set_use_names;\n  set_var_branch_func           *set_var_branch;\n  set_var_weights_func          *set_var_weights;\n  set_verbose_func              *set_verbose;\n  set_XLI_func                  *set_XLI;\n  solve_func                    *solve;\n  str_add_column_func           *str_add_column;\n  str_add_constraint_func       *str_add_constraint;\n  str_add_lag_con_func          *str_add_lag_con;\n  str_set_obj_fn_func           *str_set_obj_fn;\n  str_set_rh_vec_func           *str_set_rh_vec;\n  time_elapsed_func             *time_elapsed;\n  unscale_func                  *unscale;\n  write_lp_func                 *write_lp;\n  write_LP_func                 *write_LP;\n  write_mps_func                *write_mps;\n  write_MPS_func                *write_MPS;\n  write_freemps_func            *write_freemps;\n  write_freeMPS_func            *write_freeMPS;\n  write_XLI_func                *write_XLI;\n  write_basis_func              *write_basis;\n  write_params_func             *write_params;\n\n  /* Spacer */\n  int       *alignmentspacer;\n\n  /* Problem description */\n  char      *lp_name;           /* The name of the model */\n\n  /* Problem sizes */\n  int       sum;                /* The total number of variables, including slacks */\n  int       rows;\n  int       columns;\n  int       equalities;         /* No of non-Lagrangean equality constraints in the problem */\n  int       boundedvars;        /* Count of bounded variables */\n  int       INTfuture1;\n\n  /* Memory allocation sizes */\n  int       sum_alloc;          /* The allocated memory for row+column-sized data */\n  int       rows_alloc;         /* The allocated memory for row-sized data */\n  int       columns_alloc;      /* The allocated memory for column-sized data */\n\n  /* Model status and solver result variables */\n  MYBOOL    source_is_file;     /* The base model was read from a file */\n  MYBOOL    model_is_pure;      /* The model has been built entirely from row and column additions */\n  MYBOOL    model_is_valid;     /* Has this lp pased the 'test' */\n  MYBOOL    tighten_on_set;     /* Specify if bounds will be tightened or overriden at bound setting */\n  MYBOOL    names_used;         /* Flag to indicate if names for rows and columns are used */\n  MYBOOL    use_row_names;      /* Flag to indicate if names for rows are used */\n  MYBOOL    use_col_names;      /* Flag to indicate if names for columns are used */\n\n  MYBOOL    lag_trace;          /* Print information on Lagrange progression */\n  MYBOOL    spx_trace;          /* Print information on simplex progression */\n  MYBOOL    bb_trace;           /* TRUE to print extra debug information */\n  MYBOOL    streamowned;        /* TRUE if the handle should be closed at delete_lp() */\n  MYBOOL    obj_in_basis;       /* TRUE if the objective function is in the basis matrix */\n\n  int       spx_status;         /* Simplex solver feasibility/mode code */\n  int       lag_status;         /* Extra status variable for lag_solve */\n  int       solutioncount;      /* number of equal-valued solutions found (up to solutionlimit) */\n  int       solutionlimit;      /* upper number of equal-valued solutions kept track of */\n\n  REAL      real_solution;      /* Optimal non-MIP solution base */\n  REAL      *solution;          /* sum_alloc+1 : Solution array of the next to optimal LP,\n                                   Index   0           : Objective function value,\n                                   Indeces 1..rows     : Slack variable values,\n                                   Indeced rows+1..sum : Variable values */\n  REAL      *best_solution;     /* sum_alloc+1 : Solution array of optimal 'Integer' LP,\n                                   structured as the solution array above */\n  REAL      *full_solution;     /* sum_alloc+1 : Final solution array expanded for deleted variables */\n  REAL      *edgeVector;        /* Array of reduced cost scaling norms (DEVEX and Steepest Edge) */\n\n  REAL      *drow;              /* sum+1: Reduced costs of the last simplex */\n  int       *nzdrow;            /* sum+1: Indeces of non-zero reduced costs of the last simplex */\n  REAL      *duals;             /* rows_alloc+1 : The dual variables of the last LP */\n  REAL      *full_duals;        /* sum_alloc+1: Final duals array expanded for deleted variables */\n  REAL      *dualsfrom;         /* sum_alloc+1 :The sensitivity on dual variables/reduced costs\n                                   of the last LP */\n  REAL      *dualstill;         /* sum_alloc+1 :The sensitivity on dual variables/reduced costs\n                                   of the last LP */\n  REAL      *objfrom;           /* columns_alloc+1 :The sensitivity on objective function\n                                   of the last LP */\n  REAL      *objtill;           /* columns_alloc+1 :The sensitivity on objective function\n                                   of the last LP */\n  REAL      *objfromvalue;      /* columns_alloc+1 :The value of the variables when objective value\n                                   is at its from value of the last LP */\n  REAL      *orig_obj;          /* Unused pointer - Placeholder for OF not part of B */\n  REAL      *obj;               /* Special vector used to temporarily change the OF vector */\n\n  COUNTER   current_iter;       /* Number of iterations in the current/last simplex */\n  COUNTER   total_iter;         /* Number of iterations over all B&B steps */\n  COUNTER   current_bswap;      /* Number of bound swaps in the current/last simplex */\n  COUNTER   total_bswap;        /* Number of bount swaps over all B&B steps */\n  int       solvecount;         /* The number of solve() performed in this model */\n  int       max_pivots;         /* Number of pivots between refactorizations of the basis */\n\n  /* Various execution parameters */\n  int       simplex_strategy;   /* Set desired combination of primal and dual simplex algorithms */\n  int       simplex_mode;       /* Specifies the current simplex mode during solve; see simplex_strategy */\n  int       verbose;            /* Set amount of run-time messages and results */\n  int       print_sol;          /* TRUE to print optimal solution; AUTOMATIC skips zeros */\n  FILE      *outstream;         /* Output stream, initialized to STDOUT */\n\n  /* Main Branch and Bound settings */\n  MYBOOL    *bb_varbranch;      /* Determines branching strategy at the individual variable level;\n                                   the setting here overrides the bb_floorfirst setting */\n  int       piv_strategy;       /* Strategy for selecting row and column entering/leaving */\n  int       _piv_rule_;         /* Internal working rule-part of piv_strategy above */\n  int       bb_rule;            /* Rule for selecting B&B variables */\n  MYBOOL    bb_floorfirst;      /* Set BRANCH_FLOOR for B&B to set variables to floor bound first;\n                                   conversely with BRANCH_CEILING, the ceiling value is set first */\n  MYBOOL    bb_breakfirst;      /* TRUE to stop at first feasible solution */\n  MYBOOL    _piv_left_;         /* Internal variable indicating active pricing loop order */\n  MYBOOL    BOOLfuture1;\n\n  REAL      scalelimit;         /* Relative convergence criterion for iterated scaling */\n  int       scalemode;          /* OR-ed codes for data scaling */\n  int       improve;            /* Set to non-zero for iterative improvement */\n  int       anti_degen;         /* Anti-degen strategy (or none) TRUE to avoid cycling */\n  int       do_presolve;        /* PRESOLVE_ parameters for LP presolving */\n  int       presolveloops;      /* Maximum number of presolve loops */\n\n  int       perturb_count;      /* The number of bound relaxation retries performed */\n\n  /* Row and column names storage variables */\n  hashelem  **row_name;         /* rows_alloc+1 */\n  hashelem  **col_name;         /* columns_alloc+1 */\n  hashtable *rowname_hashtab;   /* hash table to store row names */\n  hashtable *colname_hashtab;   /* hash table to store column names */\n\n  /* Optionally specify continuous rows/column blocks for partial pricing */\n  partialrec *rowblocks;\n  partialrec *colblocks;\n\n  /* Row and column type codes */\n  MYBOOL    *var_type;          /* sum_alloc+1 : TRUE if variable must be integer */\n\n  /* Data for multiple pricing */\n  multirec  *multivars;\n  int       multiblockdiv;      /* The divisor used to set or augment pricing block */\n\n  /* Variable (column) parameters */\n  int       fixedvars;          /* The current number of basic fixed variables in the model */\n  int       int_vars;           /* Number of variables required to be integer */\n\n  int       sc_vars;            /* Number of semi-continuous variables */\n  REAL      *sc_lobound;        /* sum_columns+1 : TRUE if variable is semi-continuous;\n                                   value replaced by conventional lower bound during solve */\n  int       *var_is_free;       /* columns+1: Index of twin variable if variable is free */\n  int       *var_priority;      /* columns: Priority-mapping of variables */\n\n  SOSgroup  *GUB;               /* Pointer to record containing GUBs */\n\n  int       sos_vars;           /* Number of variables in the sos_priority list */\n  int       sos_ints;           /* Number of integers in SOS'es above */\n  SOSgroup  *SOS;               /* Pointer to record containing all SOS'es */\n  int       *sos_priority;      /* Priority-sorted list of variables (no duplicates) */\n\n  /* Optionally specify list of active rows/columns used in multiple pricing */\n  REAL      *bsolveVal;         /* rows+1: bsolved solution vector for reduced costs */\n  int       *bsolveIdx;         /* rows+1: Non-zero indeces of bsolveVal */\n\n  /* RHS storage */\n  REAL      *orig_rhs;          /* rows_alloc+1 : The RHS after scaling and sign\n                                   changing, but before 'Bound transformation' */\n  LREAL     *rhs;               /* rows_alloc+1 : The RHS of the current simplex tableau */\n\n  /* Row (constraint) parameters */\n  int       *row_type;          /* rows_alloc+1 : Row/constraint type coding */\n\n  /* Optionally specify data for dual long-step */\n  multirec  *longsteps;\n\n  /* Original and working row and variable bounds */\n  REAL      *orig_upbo;         /* sum_alloc+1 : Bound before transformations */\n  REAL      *upbo;              /*  \" \" : Upper bound after transformation and B&B work */\n  REAL      *orig_lowbo;        /*  \"       \"                                 */\n  REAL      *lowbo;             /*  \" \" : Lower bound after transformation and B&B work */\n\n  /* User data and basis factorization matrices (ETA or LU, product form) */\n  MATrec    *matA;\n  INVrec    *invB;\n\n  /* Basis and bounds */\n  BBrec     *bb_bounds;         /* The linked list of B&B bounds */\n  BBrec     *rootbounds;        /* The bounds at the lowest B&B level */\n  basisrec  *bb_basis;          /* The linked list of B&B bases */\n  basisrec  *rootbasis;\n  OBJmonrec *monitor;           /* Objective monitoring record for stalling/degeneracy handling */\n\n  /* Scaling parameters */\n  REAL      *scalars;           /* sum_alloc+1:0..Rows the scaling of the rows,\n                                   Rows+1..Sum the scaling of the columns */\n  MYBOOL    scaling_used;       /* TRUE if scaling is used */\n  MYBOOL    columns_scaled;     /* TRUE if the columns are scaled too */\n  MYBOOL    varmap_locked;      /* Determines whether the var_to_orig and orig_to_var are fixed */\n\n  /* Variable state information */\n  MYBOOL    basis_valid;        /* TRUE is the basis is still valid */\n  int       crashmode;          /* Basis crashing mode (or none) */\n  int       *var_basic;         /* rows_alloc+1: The list of columns in the basis */\n  REAL      *val_nonbasic;      /* Array to store current values of non-basic variables */\n  MYBOOL    *is_basic;          /* sum_alloc+1: TRUE if the column is in the basis */\n  MYBOOL    *is_lower;          /*  \"       \" : TRUE if the variable is at its\n                                   lower bound (or in the basis), FALSE otherwise */\n\n  /* Simplex basis indicators */\n  int       *rejectpivot;       /* List of unacceptable pivot choices due to division-by-zero */\n  BBPSrec   *bb_PseudoCost;     /* Data structure for costing of node branchings */\n  int       bb_PseudoUpdates;   /* Maximum number of updates for pseudo-costs */\n  int       bb_strongbranches;  /* The number of strong B&B branches performed */\n  int       is_strongbranch;    /* Are we currently in a strong branch mode? */\n  int       bb_improvements;    /* The number of discrete B&B objective improvement steps */\n\n  /* Solver working variables */\n  REAL      rhsmax;             /* The maximum |value| of the rhs vector at any iteration */\n  REAL      suminfeas;          /* The working sum of primal and dual infeasibilities */\n  REAL      bigM;               /* Original objective weighting in primal phase 1 */\n  REAL      P1extraVal;         /* Phase 1 OF/RHS offset for feasibility */\n  int       P1extraDim;         /* Phase 1 additional columns/rows for feasibility */\n  int       spx_action;         /* ACTION_ variables for the simplex routine */\n  MYBOOL    spx_perturbed;      /* The variable bounds were relaxed/perturbed into this simplex */\n  MYBOOL    bb_break;           /* Solver working variable; signals break of the B&B */\n  MYBOOL    wasPreprocessed;    /* The solve preprocessing was performed */\n  MYBOOL    wasPresolved;       /* The solve presolver was invoked */\n  int      INTfuture2;\n\n  /* Lagragean solver storage and parameters */\n  MATrec    *matL;\n  REAL      *lag_rhs;           /* Array of Lagrangean rhs vector */\n  int       *lag_con_type;      /* Array of GT, LT or EQ */\n  REAL      *lambda;            /* Lambda values (Lagrangean multipliers) */\n  REAL      lag_bound;          /* The Lagrangian lower OF bound */\n  REAL      lag_accept;         /* The Lagrangian convergence criterion */\n\n  /* Solver thresholds */\n  REAL      infinite;           /* Limit for dynamic range */\n  REAL      negrange;           /* Limit for negative variable range */\n  REAL      epsmachine;         /* Default machine accuracy */\n  REAL      epsvalue;           /* Input data precision / rounding of data values to 0 */\n  REAL      epsprimal;          /* For rounding RHS values to 0/infeasibility */\n  REAL      epsdual;            /* For rounding reduced costs to zero */\n  REAL      epspivot;           /* Pivot reject tolerance */\n  REAL      epsperturb;         /* Perturbation scalar */\n  REAL      epssolution;        /* The solution tolerance for final validation */\n\n  /* Branch & Bound working parameters */\n  int       bb_status;          /* Indicator that the last solvelp() gave an improved B&B solution */\n  int       bb_level;           /* Solver B&B working variable (recursion depth) */\n  int       bb_maxlevel;        /* The deepest B&B level of the last solution */\n  int       bb_limitlevel;      /* The maximum B&B level allowed */\n  COUNTER   bb_totalnodes;      /* Total number of nodes processed in B&B */\n  int       bb_solutionlevel;   /* The B&B level of the last / best solution */\n  int       bb_cutpoolsize;     /* Size of the B&B cut pool */\n  int       bb_cutpoolused;     /* Currently used cut pool */\n  int       bb_constraintOF;    /* General purpose B&B parameter (typically for testing) */\n  int       *bb_cuttype;        /* The type of the currently used cuts */\n  int       *bb_varactive;      /* The B&B state of the variable; 0 means inactive */\n  DeltaVrec *bb_upperchange;    /* Changes to upper bounds during the B&B phase */\n  DeltaVrec *bb_lowerchange;    /* Changes to lower bounds during the B&B phase */\n\n  REAL      bb_deltaOF;         /* Minimum OF step value; computed at beginning of solve() */\n\n  REAL      bb_breakOF;         /* User-settable value for the objective function deemed\n                               to be sufficiently good in an integer problem */\n  REAL      bb_limitOF;         /* \"Dual\" bound / limit to final optimal MIP solution */\n  REAL      bb_heuristicOF;     /* Set initial \"at least better than\" guess for objective function\n                               (can significantly speed up B&B iterations) */\n  REAL      bb_parentOF;        /* The OF value of the previous BB simplex */\n  REAL      bb_workOF;          /* The unadjusted OF value for the current best solution */\n\n  /* Internal work arrays allocated as required */\n  presolveundorec *presolve_undo;\n  workarraysrec   *workarrays;\n\n  /* MIP parameters */\n  REAL      epsint;             /* Margin of error in determining if a float value is integer */\n  REAL      mip_absgap;         /* Absolute MIP gap */\n  REAL      mip_relgap;         /* Relative MIP gap */\n\n  /* Time/timer variables and extended status text */\n  double    timecreate;\n  double    timestart;\n  double    timeheuristic;\n  double    timepresolved;\n  double    timeend;\n  long      sectimeout;\n\n  /* Extended status message text set via explain() */\n  char      *ex_status;\n\n  /* Refactorization engine interface routines (for dynamic DLL/SO BFPs) */\n#if LoadInverseLib == TRUE\n  #ifdef WIN32\n    HINSTANCE                   hBFP;\n  #else\n    void                        *hBFP;\n  #endif\n#endif\n  BFPchar                       *bfp_name;\n  BFPbool_lpintintint           *bfp_compatible;\n  BFPbool_lpintintchar          *bfp_init;\n  BFP_lp                        *bfp_free;\n  BFPbool_lpint                 *bfp_resize;\n  BFPint_lp                     *bfp_memallocated;\n  BFPbool_lp                    *bfp_restart;\n  BFPbool_lp                    *bfp_mustrefactorize;\n  BFPint_lp                     *bfp_preparefactorization;\n  BFPint_lpintintboolbool       *bfp_factorize;\n  BFP_lp                        *bfp_finishfactorization;\n  BFP_lp                        *bfp_updaterefactstats;\n  BFPlreal_lpintintreal         *bfp_prepareupdate;\n  BFPreal_lplrealreal           *bfp_pivotRHS;\n  BFPbool_lpbool                *bfp_finishupdate;\n  BFP_lprealint                 *bfp_ftran_prepare;\n  BFP_lprealint                 *bfp_ftran_normal;\n  BFP_lprealint                 *bfp_btran_normal;\n  BFP_lprealintrealint          *bfp_btran_double;\n  BFPint_lp                     *bfp_status;\n  BFPint_lpbool                 *bfp_nonzeros;\n  BFPbool_lp                    *bfp_implicitslack;\n  BFPint_lp                     *bfp_indexbase;\n  BFPint_lp                     *bfp_rowoffset;\n  BFPint_lp                     *bfp_pivotmax;\n  BFPbool_lpint                 *bfp_pivotalloc;\n  BFPint_lp                     *bfp_colcount;\n  BFPbool_lp                    *bfp_canresetbasis;\n  BFPreal_lp                    *bfp_efficiency;\n  BFPrealp_lp                   *bfp_pivotvector;\n  BFPint_lp                     *bfp_pivotcount;\n  BFPint_lpint                  *bfp_refactcount;\n  BFPbool_lp                    *bfp_isSetI;\n  BFPint_lpintrealcbintint      *bfp_findredundant;\n\n  /* External language interface routines (for dynamic DLL/SO XLIs) */\n#if LoadLanguageLib == TRUE\n  #ifdef WIN32\n    HINSTANCE                   hXLI;\n  #else\n    void                        *hXLI;\n  #endif\n#endif\n  XLIchar                       *xli_name;\n  XLIbool_lpintintint           *xli_compatible;\n  XLIbool_lpcharcharcharint     *xli_readmodel;\n  XLIbool_lpcharcharbool        *xli_writemodel;\n\n  /* Miscellaneous internal functions made available externally */\n  userabortfunc                 *userabort;\n  reportfunc                    *report;\n  explainfunc                   *explain;\n  getvectorfunc                 *get_lpcolumn;\n  getpackedfunc                 *get_basiscolumn;\n  get_OF_activefunc             *get_OF_active;\n  getMDOfunc                    *getMDO;\n  invertfunc                    *invert;\n  set_actionfunc                *set_action;\n  is_actionfunc                 *is_action;\n  clear_actionfunc              *clear_action;\n\n  /* User program interface callbacks */\n  lphandle_intfunc              *ctrlc;\n    void                          *ctrlchandle;     /* User-specified \"owner process ID\" */\n  lphandlestr_func              *writelog;\n    void                          *loghandle;       /* User-specified \"owner process ID\" */\n  lphandlestr_func              *debuginfo;\n  lphandleint_func              *usermessage;\n    int                           msgmask;\n    void                          *msghandle;       /* User-specified \"owner process ID\" */\n  lphandleint_intfunc           *bb_usenode;\n    void                          *bb_nodehandle;   /* User-specified \"owner process ID\" */\n  lphandleint_intfunc           *bb_usebranch;\n    void                          *bb_branchhandle; /* User-specified \"owner process ID\" */\n\n  /* replacement of static variables */\n  char      *rowcol_name;       /* The name of a row/column */\n};\n\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\n\n/* User and system function interfaces                                       */\n/* ------------------------------------------------------------------------- */\n\nvoid __EXPORT_TYPE __WINAPI lp_solve_version(int *majorversion, int *minorversion, int *release, int *build);\n\nlprec __EXPORT_TYPE * __WINAPI make_lp(int rows, int columns);\nMYBOOL __EXPORT_TYPE __WINAPI resize_lp(lprec *lp, int rows, int columns);\nint __EXPORT_TYPE __WINAPI get_status(lprec *lp);\nchar __EXPORT_TYPE * __WINAPI get_statustext(lprec *lp, int statuscode);\nMYBOOL __EXPORT_TYPE __WINAPI is_obj_in_basis(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI set_obj_in_basis(lprec *lp, MYBOOL obj_in_basis);\n/* Create and initialise a lprec structure defaults */\n\nlprec __EXPORT_TYPE * __WINAPI copy_lp(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI dualize_lp(lprec *lp);\nSTATIC MYBOOL memopt_lp(lprec *lp, int rowextra, int colextra, int nzextra);\n/* Copy or dualize the lp */\n\nvoid __EXPORT_TYPE __WINAPI delete_lp(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI free_lp(lprec **plp);\n/* Remove problem from memory */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_lp_name(lprec *lp, char *lpname);\nchar __EXPORT_TYPE * __WINAPI get_lp_name(lprec *lp);\n/* Set and get the problem name */\n\nMYBOOL __EXPORT_TYPE __WINAPI has_BFP(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_nativeBFP(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI set_BFP(lprec *lp, char *filename);\n/* Set basis factorization engine */\n\nlprec __EXPORT_TYPE * __WINAPI read_XLI(char *xliname, char *modelname, char *dataname, char *options, int verbose);\nMYBOOL __EXPORT_TYPE __WINAPI write_XLI(lprec *lp, char *filename, char *options, MYBOOL results);\nMYBOOL __EXPORT_TYPE __WINAPI has_XLI(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_nativeXLI(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI set_XLI(lprec *lp, char *filename);\n/* Set external language interface */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_obj(lprec *lp, int colnr, REAL value);\nMYBOOL __EXPORT_TYPE __WINAPI set_obj_fn(lprec *lp, REAL *row);\nMYBOOL __EXPORT_TYPE __WINAPI set_obj_fnex(lprec *lp, int count, REAL *row, int *colno);\n/* set the objective function (Row 0) of the matrix */\nMYBOOL __EXPORT_TYPE __WINAPI str_set_obj_fn(lprec *lp, char *row_string);\n/* The same, but with string input */\nvoid __EXPORT_TYPE __WINAPI set_sense(lprec *lp, MYBOOL maximize);\nvoid __EXPORT_TYPE __WINAPI set_maxim(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI set_minim(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_maxim(lprec *lp);\n/* Set optimization direction for the objective function */\n\nMYBOOL __EXPORT_TYPE __WINAPI add_constraint(lprec *lp, REAL *row, int constr_type, REAL rh);\nMYBOOL __EXPORT_TYPE __WINAPI add_constraintex(lprec *lp, int count, REAL *row, int *colno, int constr_type, REAL rh);\nMYBOOL __EXPORT_TYPE __WINAPI set_add_rowmode(lprec *lp, MYBOOL turnon);\nMYBOOL __EXPORT_TYPE __WINAPI is_add_rowmode(lprec *lp);\n/* Add a constraint to the problem, row is the constraint row, rh is the right hand side,\n   constr_type is the type of constraint (LE (<=), GE(>=), EQ(=)) */\nMYBOOL __EXPORT_TYPE __WINAPI str_add_constraint(lprec *lp, char *row_string, int constr_type, REAL rh);\n/* The same, but with string input */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_row(lprec *lp, int rownr, REAL *row);\nMYBOOL __EXPORT_TYPE __WINAPI set_rowex(lprec *lp, int rownr, int count, REAL *row, int *colno);\nMYBOOL __EXPORT_TYPE __WINAPI get_row(lprec *lp, int rownr, REAL *row);\nint __EXPORT_TYPE __WINAPI get_rowex(lprec *lp, int rownr, REAL *row, int *colno);\n/* Fill row with the row row_nr from the problem */\n\nMYBOOL __EXPORT_TYPE __WINAPI del_constraint(lprec *lp, int rownr);\nSTATIC MYBOOL del_constraintex(lprec *lp, LLrec *rowmap);\n/* Remove constrain nr del_row from the problem */\n\nMYBOOL __EXPORT_TYPE __WINAPI add_lag_con(lprec *lp, REAL *row, int con_type, REAL rhs);\n/* add a Lagrangian constraint of form Row' x contype Rhs */\nMYBOOL __EXPORT_TYPE __WINAPI str_add_lag_con(lprec *lp, char *row_string, int con_type, REAL rhs);\n/* The same, but with string input */\nvoid __EXPORT_TYPE __WINAPI set_lag_trace(lprec *lp, MYBOOL lag_trace);\nMYBOOL __EXPORT_TYPE __WINAPI is_lag_trace(lprec *lp);\n/* Set debugging/tracing mode of the Lagrangean solver */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_constr_type(lprec *lp, int rownr, int con_type);\nint __EXPORT_TYPE __WINAPI get_constr_type(lprec *lp, int rownr);\nREAL __EXPORT_TYPE __WINAPI get_constr_value(lprec *lp, int rownr, int count, REAL *primsolution, int *nzindex);\nMYBOOL __EXPORT_TYPE __WINAPI is_constr_type(lprec *lp, int rownr, int mask);\nSTATIC char *get_str_constr_type(lprec *lp, int con_type);\nSTATIC int get_constr_class(lprec *lp, int rownr);\nSTATIC char *get_str_constr_class(lprec *lp, int con_class);\n/* Set the type of constraint in row Row (LE, GE, EQ) */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_rh(lprec *lp, int rownr, REAL value);\nREAL __EXPORT_TYPE __WINAPI get_rh(lprec *lp, int rownr);\n/* Set and get the right hand side of a constraint row */\nMYBOOL __EXPORT_TYPE __WINAPI set_rh_range(lprec *lp, int rownr, REAL deltavalue);\nREAL __EXPORT_TYPE __WINAPI get_rh_range(lprec *lp, int rownr);\n/* Set the RHS range; i.e. the lower and upper bounds of a constraint row */\nvoid __EXPORT_TYPE __WINAPI set_rh_vec(lprec *lp, REAL *rh);\n/* Set the right hand side vector */\nMYBOOL __EXPORT_TYPE __WINAPI str_set_rh_vec(lprec *lp, char *rh_string);\n/* The same, but with string input */\n\nMYBOOL __EXPORT_TYPE __WINAPI add_column(lprec *lp, REAL *column);\nMYBOOL __EXPORT_TYPE __WINAPI add_columnex(lprec *lp, int count, REAL *column, int *rowno);\nMYBOOL __EXPORT_TYPE __WINAPI str_add_column(lprec *lp, char *col_string);\n/* Add a column to the problem */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_column(lprec *lp, int colnr, REAL *column);\nMYBOOL __EXPORT_TYPE __WINAPI set_columnex(lprec *lp, int colnr, int count, REAL *column, int *rowno);\n/* Overwrite existing column data */\n\nint __EXPORT_TYPE __WINAPI column_in_lp(lprec *lp, REAL *column);\n/* Returns the column index if column is already present in lp, otherwise 0.\n   (Does not look at bounds and types, only looks at matrix values */\n\nint __EXPORT_TYPE __WINAPI get_columnex(lprec *lp, int colnr, REAL *column, int *nzrow);\nMYBOOL __EXPORT_TYPE __WINAPI get_column(lprec *lp, int colnr, REAL *column);\n/* Fill column with the column col_nr from the problem */\n\nMYBOOL __EXPORT_TYPE __WINAPI del_column(lprec *lp, int colnr);\nSTATIC MYBOOL del_columnex(lprec *lp, LLrec *colmap);\n/* Delete a column */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_mat(lprec *lp, int rownr, int colnr, REAL value);\n/* Fill in element (Row,Column) of the matrix\n   Row in [0..Rows] and Column in [1..Columns] */\nREAL __EXPORT_TYPE __WINAPI get_mat(lprec *lp, int rownr, int colnr);\nREAL __EXPORT_TYPE __WINAPI get_mat_byindex(lprec *lp, int matindex, MYBOOL isrow, MYBOOL adjustsign);\nint __EXPORT_TYPE __WINAPI get_nonzeros(lprec *lp);\n/* get a single element from the matrix */  /* Name changed from \"mat_elm\" by KE */\n\nvoid __EXPORT_TYPE __WINAPI set_bounds_tighter(lprec *lp, MYBOOL tighten);\nMYBOOL get_bounds(lprec *lp, int column, REAL *lower, REAL *upper);\nMYBOOL __EXPORT_TYPE __WINAPI get_bounds_tighter(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI set_upbo(lprec *lp, int colnr, REAL value);\nREAL __EXPORT_TYPE __WINAPI get_upbo(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_lowbo(lprec *lp, int colnr, REAL value);\nREAL __EXPORT_TYPE __WINAPI get_lowbo(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_bounds(lprec *lp, int colnr, REAL lower, REAL upper);\nMYBOOL __EXPORT_TYPE __WINAPI set_unbounded(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI is_unbounded(lprec *lp, int colnr);\n/* Set the upper and lower bounds of a variable */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_int(lprec *lp, int colnr, MYBOOL must_be_int);\nMYBOOL __EXPORT_TYPE __WINAPI is_int(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_binary(lprec *lp, int colnr, MYBOOL must_be_bin);\nMYBOOL __EXPORT_TYPE __WINAPI is_binary(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_semicont(lprec *lp, int colnr, MYBOOL must_be_sc);\nMYBOOL __EXPORT_TYPE __WINAPI is_semicont(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI is_negative(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_var_weights(lprec *lp, REAL *weights);\nint __EXPORT_TYPE __WINAPI get_var_priority(lprec *lp, int colnr);\n/* Set the type of variable */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_pseudocosts(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit);\nMYBOOL __EXPORT_TYPE __WINAPI get_pseudocosts(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit);\n/* Set initial values for, or get computed pseudocost vectors;\n   note that setting of pseudocosts can only happen in response to a\n   call-back function optionally requesting this */\n\nint  __EXPORT_TYPE __WINAPI add_SOS(lprec *lp, char *name, int sostype, int priority, int count, int *sosvars, REAL *weights);\nMYBOOL __EXPORT_TYPE __WINAPI is_SOS_var(lprec *lp, int colnr);\n/* Add SOS constraints */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_row_name(lprec *lp, int rownr, char *new_name);\nchar __EXPORT_TYPE * __WINAPI get_row_name(lprec *lp, int rownr);\nchar __EXPORT_TYPE * __WINAPI get_origrow_name(lprec *lp, int rownr);\n/* Set/Get the name of a constraint row */   /* Get added by KE */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_col_name(lprec *lp, int colnr, char *new_name);\nchar __EXPORT_TYPE * __WINAPI get_col_name(lprec *lp, int colnr);\nchar __EXPORT_TYPE * __WINAPI get_origcol_name(lprec *lp, int colnr);\n/* Set/Get the name of a variable column */  /* Get added by KE */\n\nvoid __EXPORT_TYPE __WINAPI unscale(lprec *lp);\n/* Undo previous scaling of the problem */\n\nvoid __EXPORT_TYPE __WINAPI set_preferdual(lprec *lp, MYBOOL dodual);\nvoid __EXPORT_TYPE __WINAPI set_simplextype(lprec *lp, int simplextype);\nint __EXPORT_TYPE __WINAPI get_simplextype(lprec *lp);\n/* Set/Get if lp_solve should prefer the dual simplex over the primal -- added by KE */\n\nvoid __EXPORT_TYPE __WINAPI default_basis(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI set_basiscrash(lprec *lp, int mode);\nint __EXPORT_TYPE __WINAPI get_basiscrash(lprec *lp);\nint __EXPORT_TYPE __WINAPI set_basisvar(lprec *lp, int basisPos, int enteringCol);\nMYBOOL __EXPORT_TYPE __WINAPI set_basis(lprec *lp, int *bascolumn, MYBOOL nonbasic);\nMYBOOL __EXPORT_TYPE __WINAPI get_basis(lprec *lp, int *bascolumn, MYBOOL nonbasic);\nvoid __EXPORT_TYPE __WINAPI reset_basis(lprec *lp);\n/* Set/Get basis for a re-solved system */  /* Added by KE */\nMYBOOL __EXPORT_TYPE __WINAPI guess_basis(lprec *lp, REAL *guessvector, int *basisvector);\n\nMYBOOL __EXPORT_TYPE __WINAPI is_feasible(lprec *lp, REAL *values, REAL threshold);\n/* returns TRUE if the vector in values is a feasible solution to the lp */\n\nint __EXPORT_TYPE __WINAPI solve(lprec *lp);\n/* Solve the problem */\n\nREAL __EXPORT_TYPE __WINAPI time_elapsed(lprec *lp);\n/* Return the number of seconds since start of solution process */\n\nvoid __EXPORT_TYPE __WINAPI put_bb_nodefunc(lprec *lp, lphandleint_intfunc newnode, void *bbnodehandle);\nvoid __EXPORT_TYPE __WINAPI put_bb_branchfunc(lprec *lp, lphandleint_intfunc newbranch, void *bbbranchhandle);\n/* Allow the user to override B&B node and branching decisions */\n\nvoid __EXPORT_TYPE __WINAPI put_abortfunc(lprec *lp, lphandle_intfunc newctrlc, void *ctrlchandle);\n/* Allow the user to define an interruption callback function */\n\nvoid __EXPORT_TYPE __WINAPI put_logfunc(lprec *lp, lphandlestr_func newlog, void *loghandle);\n/* Allow the user to define a logging function */\n\nvoid __EXPORT_TYPE __WINAPI put_msgfunc(lprec *lp, lphandleint_func newmsg, void *msghandle, int mask);\n/* Allow the user to define an event-driven message/reporting */\n\nMYBOOL __EXPORT_TYPE __WINAPI get_primal_solution(lprec *lp, REAL *pv);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_primal_solution(lprec *lp, REAL **pv);\nMYBOOL __EXPORT_TYPE __WINAPI get_dual_solution(lprec *lp, REAL *rc);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_dual_solution(lprec *lp, REAL **rc);\nMYBOOL __EXPORT_TYPE __WINAPI get_lambda(lprec *lp, REAL *lambda);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_lambda(lprec *lp, REAL **lambda);\n/* Get the primal, dual/reduced costs and Lambda vectors */\n\n/* Read an MPS file */\nlprec __EXPORT_TYPE * __WINAPI read_MPS(char *filename, int options);\nlprec __EXPORT_TYPE * __WINAPI read_mps(FILE *filename, int options);\nlprec __EXPORT_TYPE * __WINAPI read_freeMPS(char *filename, int options);\nlprec __EXPORT_TYPE * __WINAPI read_freemps(FILE *filename, int options);\n\n/* Write a MPS file to output */\nMYBOOL __EXPORT_TYPE __WINAPI write_mps(lprec *lp, char *filename);\nMYBOOL __EXPORT_TYPE __WINAPI write_MPS(lprec *lp, FILE *output);\nMYBOOL __EXPORT_TYPE __WINAPI write_freemps(lprec *lp, char *filename);\nMYBOOL __EXPORT_TYPE __WINAPI write_freeMPS(lprec *lp, FILE *output);\n\nMYBOOL __EXPORT_TYPE __WINAPI write_lp(lprec *lp, char *filename);\nMYBOOL __EXPORT_TYPE __WINAPI write_LP(lprec *lp, FILE *output);\n /* Write a LP file to output */\n\nMYBOOL __WINAPI LP_readhandle(lprec **lp, FILE *filename, int verbose, char *lp_name);\nlprec __EXPORT_TYPE * __WINAPI read_lp(FILE *filename, int verbose, char *lp_name);\nlprec __EXPORT_TYPE * __WINAPI read_LP(char *filename, int verbose, char *lp_name);\n/* Old-style lp format file parser */\n\nMYBOOL __EXPORT_TYPE __WINAPI write_basis(lprec *lp, char *filename);\nMYBOOL __EXPORT_TYPE __WINAPI read_basis(lprec *lp, char *filename, char *info);\n/* Read and write basis from/to file in CPLEX BAS format */\n\nMYBOOL __EXPORT_TYPE __WINAPI write_params(lprec *lp, char *filename, char *options);\nMYBOOL __EXPORT_TYPE __WINAPI read_params(lprec *lp, char *filename, char *options);\nvoid __EXPORT_TYPE __WINAPI reset_params(lprec *lp);\n/* Read and write parameter file */\n\nvoid __EXPORT_TYPE __WINAPI print_lp(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI print_tableau(lprec *lp);\n/* Print the current problem, only useful in very small (test) problems */\n\nvoid __EXPORT_TYPE __WINAPI print_objective(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI print_solution(lprec *lp, int columns);\nvoid __EXPORT_TYPE __WINAPI print_constraints(lprec *lp, int columns);\n/* Print the solution to stdout */\n\nvoid __EXPORT_TYPE __WINAPI print_duals(lprec *lp);\n/* Print the dual variables of the solution */\n\nvoid __EXPORT_TYPE __WINAPI print_scales(lprec *lp);\n/* If scaling is used, print the scaling factors */\n\nvoid __EXPORT_TYPE __WINAPI print_str(lprec *lp, char *str);\n\nvoid __EXPORT_TYPE __WINAPI set_outputstream(lprec *lp, FILE *stream);\nMYBOOL __EXPORT_TYPE __WINAPI set_outputfile(lprec *lp, char *filename);\n\nvoid __EXPORT_TYPE __WINAPI set_verbose(lprec *lp, int verbose);\nint __EXPORT_TYPE __WINAPI get_verbose(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_timeout(lprec *lp, long sectimeout);\nlong __EXPORT_TYPE __WINAPI get_timeout(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_print_sol(lprec *lp, int print_sol);\nint __EXPORT_TYPE __WINAPI get_print_sol(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_debug(lprec *lp, MYBOOL debug);\nMYBOOL __EXPORT_TYPE __WINAPI is_debug(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_trace(lprec *lp, MYBOOL trace);\nMYBOOL __EXPORT_TYPE __WINAPI is_trace(lprec *lp);\n\nMYBOOL __EXPORT_TYPE __WINAPI print_debugdump(lprec *lp, char *filename);\n\nvoid __EXPORT_TYPE __WINAPI set_anti_degen(lprec *lp, int anti_degen);\nint __EXPORT_TYPE __WINAPI get_anti_degen(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_anti_degen(lprec *lp, int testmask);\n\nvoid __EXPORT_TYPE __WINAPI set_presolve(lprec *lp, int presolvemode, int maxloops);\nint __EXPORT_TYPE __WINAPI get_presolve(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_presolveloops(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_presolve(lprec *lp, int testmask);\n\nint __EXPORT_TYPE __WINAPI get_orig_index(lprec *lp, int lp_index);\nint __EXPORT_TYPE __WINAPI get_lp_index(lprec *lp, int orig_index);\n\nvoid __EXPORT_TYPE __WINAPI set_maxpivot(lprec *lp, int max_num_inv);\nint __EXPORT_TYPE __WINAPI get_maxpivot(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_obj_bound(lprec *lp, REAL obj_bound);\nREAL __EXPORT_TYPE __WINAPI get_obj_bound(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_mip_gap(lprec *lp, MYBOOL absolute, REAL mip_gap);\nREAL __EXPORT_TYPE __WINAPI get_mip_gap(lprec *lp, MYBOOL absolute);\n\nvoid __EXPORT_TYPE __WINAPI set_bb_rule(lprec *lp, int bb_rule);\nint __EXPORT_TYPE __WINAPI get_bb_rule(lprec *lp);\n\nMYBOOL __EXPORT_TYPE __WINAPI set_var_branch(lprec *lp, int colnr, int branch_mode);\nint __EXPORT_TYPE __WINAPI get_var_branch(lprec *lp, int colnr);\n\nMYBOOL __EXPORT_TYPE __WINAPI is_infinite(lprec *lp, REAL value);\nvoid __EXPORT_TYPE __WINAPI set_infinite(lprec *lp, REAL infinite);\nREAL __EXPORT_TYPE __WINAPI get_infinite(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsint(lprec *lp, REAL epsint);\nREAL __EXPORT_TYPE __WINAPI get_epsint(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsb(lprec *lp, REAL epsb);\nREAL __EXPORT_TYPE __WINAPI get_epsb(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsd(lprec *lp, REAL epsd);\nREAL __EXPORT_TYPE __WINAPI get_epsd(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsel(lprec *lp, REAL epsel);\nREAL __EXPORT_TYPE __WINAPI get_epsel(lprec *lp);\n\nMYBOOL __EXPORT_TYPE __WINAPI set_epslevel(lprec *lp, int epslevel);\n\nvoid __EXPORT_TYPE __WINAPI set_scaling(lprec *lp, int scalemode);\nint __EXPORT_TYPE __WINAPI get_scaling(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_scalemode(lprec *lp, int testmask);\nMYBOOL __EXPORT_TYPE __WINAPI is_scaletype(lprec *lp, int scaletype);\nMYBOOL __EXPORT_TYPE __WINAPI is_integerscaling(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI set_scalelimit(lprec *lp, REAL scalelimit);\nREAL __EXPORT_TYPE __WINAPI get_scalelimit(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_improve(lprec *lp, int improve);\nint __EXPORT_TYPE __WINAPI get_improve(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_pivoting(lprec *lp, int piv_rule);\nint __EXPORT_TYPE __WINAPI get_pivoting(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI set_partialprice(lprec *lp, int blockcount, int *blockstart, MYBOOL isrow);\nvoid __EXPORT_TYPE __WINAPI get_partialprice(lprec *lp, int *blockcount, int *blockstart, MYBOOL isrow);\n\nMYBOOL __EXPORT_TYPE __WINAPI set_multiprice(lprec *lp, int multiblockdiv);\nint __EXPORT_TYPE __WINAPI get_multiprice(lprec *lp, MYBOOL getabssize);\n\nMYBOOL __EXPORT_TYPE __WINAPI is_use_names(lprec *lp, MYBOOL isrow);\nvoid __EXPORT_TYPE __WINAPI set_use_names(lprec *lp, MYBOOL isrow, MYBOOL use_names);\n\nint __EXPORT_TYPE __WINAPI get_nameindex(lprec *lp, char *varname, MYBOOL isrow);\n\nMYBOOL __EXPORT_TYPE __WINAPI is_piv_mode(lprec *lp, int testmask);\nMYBOOL __EXPORT_TYPE __WINAPI is_piv_rule(lprec *lp, int rule);\n\nvoid __EXPORT_TYPE __WINAPI set_break_at_first(lprec *lp, MYBOOL break_at_first);\nMYBOOL __EXPORT_TYPE __WINAPI is_break_at_first(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_bb_floorfirst(lprec *lp, int bb_floorfirst);\nint __EXPORT_TYPE __WINAPI get_bb_floorfirst(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_bb_depthlimit(lprec *lp, int bb_maxlevel);\nint __EXPORT_TYPE __WINAPI get_bb_depthlimit(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_break_at_value(lprec *lp, REAL break_at_value);\nREAL __EXPORT_TYPE __WINAPI get_break_at_value(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_negrange(lprec *lp, REAL negrange);\nREAL __EXPORT_TYPE __WINAPI get_negrange(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsperturb(lprec *lp, REAL epsperturb);\nREAL __EXPORT_TYPE __WINAPI get_epsperturb(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epspivot(lprec *lp, REAL epspivot);\nREAL __EXPORT_TYPE __WINAPI get_epspivot(lprec *lp);\n\nint __EXPORT_TYPE __WINAPI get_max_level(lprec *lp);\nCOUNTER __EXPORT_TYPE __WINAPI get_total_nodes(lprec *lp);\nCOUNTER __EXPORT_TYPE __WINAPI get_total_iter(lprec *lp);\n\nREAL __EXPORT_TYPE __WINAPI get_objective(lprec *lp);\nREAL __EXPORT_TYPE __WINAPI get_working_objective(lprec *lp);\n\nREAL __EXPORT_TYPE __WINAPI get_var_primalresult(lprec *lp, int index);\nREAL __EXPORT_TYPE __WINAPI get_var_dualresult(lprec *lp, int index);\n\nMYBOOL __EXPORT_TYPE __WINAPI get_variables(lprec *lp, REAL *var);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_variables(lprec *lp, REAL **var);\n\nMYBOOL __EXPORT_TYPE __WINAPI get_constraints(lprec *lp, REAL *constr);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_constraints(lprec *lp, REAL **constr);\n\nMYBOOL __EXPORT_TYPE __WINAPI get_sensitivity_rhs(lprec *lp, REAL *duals, REAL *dualsfrom, REAL *dualstill);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_sensitivity_rhs(lprec *lp, REAL **duals, REAL **dualsfrom, REAL **dualstill);\n\nMYBOOL __EXPORT_TYPE __WINAPI get_sensitivity_obj(lprec *lp, REAL *objfrom, REAL *objtill);\nMYBOOL __EXPORT_TYPE __WINAPI get_sensitivity_objex(lprec *lp, REAL *objfrom, REAL *objtill, REAL *objfromvalue, REAL *objtillvalue);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_sensitivity_obj(lprec *lp, REAL **objfrom, REAL **objtill);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_sensitivity_objex(lprec *lp, REAL **objfrom, REAL **objtill, REAL **objfromvalue, REAL **objtillvalue);\n\nvoid __EXPORT_TYPE __WINAPI set_solutionlimit(lprec *lp, int limit);\nint __EXPORT_TYPE __WINAPI get_solutionlimit(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_solutioncount(lprec *lp);\n\nint __EXPORT_TYPE __WINAPI get_Norig_rows(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_Nrows(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_Lrows(lprec *lp);\n\nint __EXPORT_TYPE __WINAPI get_Norig_columns(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_Ncolumns(lprec *lp);\n\ntypedef int (__WINAPI read_modeldata_func)(void *userhandle, char *buf, int max_size);\ntypedef int (__WINAPI write_modeldata_func)(void *userhandle, char *buf);\nMYBOOL __WINAPI MPS_readex(lprec **newlp, void *userhandle, read_modeldata_func read_modeldata, int typeMPS, int options);\n\n/* #if defined develop */\nlprec __EXPORT_TYPE * __WINAPI read_lpex(void *userhandle, read_modeldata_func read_modeldata, int verbose, char *lp_name);\nMYBOOL __EXPORT_TYPE __WINAPI write_lpex(lprec *lp, void *userhandle, write_modeldata_func write_modeldata);\n\nlprec __EXPORT_TYPE * __WINAPI read_mpsex(void *userhandle, read_modeldata_func read_modeldata, int options);\nlprec __EXPORT_TYPE * __WINAPI read_freempsex(void *userhandle, read_modeldata_func read_modeldata, int options);\n\nMYBOOL __EXPORT_TYPE __WINAPI MPS_writefileex(lprec *lp, int typeMPS, void *userhandle, write_modeldata_func write_modeldata);\n/* #endif */\n\n#ifdef __cplusplus\n}\n#endif\n\n\n/* Forward definitions of functions used internaly by the lp toolkit */\nMYBOOL set_callbacks(lprec *lp);\nSTATIC int yieldformessages(lprec *lp);\nMYBOOL __WINAPI userabort(lprec *lp, int message);\n/*char * __VACALL explain(lprec *lp, char *format, ...);\nvoid __VACALL report(lprec *lp, int level, char *format, ...);*/\n\n/* Memory management routines */\nSTATIC MYBOOL append_rows(lprec *lp, int deltarows);\nSTATIC MYBOOL append_columns(lprec *lp, int deltacolumns);\nSTATIC void inc_rows(lprec *lp, int delta);\nSTATIC void inc_columns(lprec *lp, int delta);\nSTATIC MYBOOL init_rowcol_names(lprec *lp);\nSTATIC MYBOOL inc_row_space(lprec *lp, int deltarows);\nSTATIC MYBOOL inc_col_space(lprec *lp, int deltacols);\nSTATIC MYBOOL shift_rowcoldata(lprec *lp, int base, int delta, LLrec *usedmap, MYBOOL isrow);\nSTATIC MYBOOL shift_basis(lprec *lp, int base, int delta, LLrec *usedmap, MYBOOL isrow);\nSTATIC MYBOOL shift_rowdata(lprec *lp, int base, int delta, LLrec *usedmap);\nSTATIC MYBOOL shift_coldata(lprec *lp, int base, int delta, LLrec *usedmap);\n\n/* INLINE */ MYBOOL is_chsign(lprec *lp, int rownr);\n\nSTATIC MYBOOL inc_lag_space(lprec *lp, int deltarows, MYBOOL ignoreMAT);\nlprec *make_lag(lprec *server);\n\nREAL get_rh_upper(lprec *lp, int rownr);\nREAL get_rh_lower(lprec *lp, int rownr);\nMYBOOL set_rh_upper(lprec *lp, int rownr, REAL value);\nMYBOOL set_rh_lower(lprec *lp, int rownr, REAL value);\nSTATIC int bin_count(lprec *lp, MYBOOL working);\nSTATIC int MIP_count(lprec *lp);\nSTATIC int SOS_count(lprec *lp);\nSTATIC int GUB_count(lprec *lp);\nSTATIC int identify_GUB(lprec *lp, MYBOOL mark);\nSTATIC int prepare_GUB(lprec *lp);\n\nSTATIC MYBOOL refactRecent(lprec *lp);\nSTATIC MYBOOL check_if_less(lprec *lp, REAL x, REAL y, int variable);\nSTATIC MYBOOL feasiblePhase1(lprec *lp, REAL epsvalue);\nSTATIC void free_duals(lprec *lp);\nSTATIC void initialize_solution(lprec *lp, MYBOOL shiftbounds);\nSTATIC void recompute_solution(lprec *lp, MYBOOL shiftbounds);\nSTATIC int verify_solution(lprec *lp, MYBOOL reinvert, char *info);\nSTATIC int check_solution(lprec *lp, int  lastcolumn, REAL *solution,\n                          REAL *upbo, REAL *lowbo, REAL tolerance);\n/* INLINE */ MYBOOL is_fixedvar(lprec *lp, int variable);\n/* INLINE */ MYBOOL is_splitvar(lprec *lp, int colnr);\n\nvoid   __WINAPI set_action(int *actionvar, int actionmask);\nvoid   __WINAPI clear_action(int *actionvar, int actionmask);\nMYBOOL __WINAPI is_action(int actionvar, int testmask);\n\n/* INLINE */ MYBOOL is_bb_rule(lprec *lp, int bb_rule);\n/* INLINE */ MYBOOL is_bb_mode(lprec *lp, int bb_mask);\n/* INLINE */ int get_piv_rule(lprec *lp);\nSTATIC char *get_str_piv_rule(int rule);\nSTATIC MYBOOL __WINAPI set_var_priority(lprec *lp);\nSTATIC int find_sc_bbvar(lprec *lp, int *count);\nSTATIC int find_sos_bbvar(lprec *lp, int *count, MYBOOL intsos);\nSTATIC int find_int_bbvar(lprec *lp, int *count, BBrec *BB, MYBOOL *isfeasible);\n\n/* Solution-related functions */\nSTATIC REAL compute_dualslacks(lprec *lp, int target, REAL **dvalues, int **nzdvalues, MYBOOL dosum);\nSTATIC MYBOOL solution_is_int(lprec *lp, int index, MYBOOL checkfixed);\nSTATIC MYBOOL bb_better(lprec *lp, int target, int mode);\nSTATIC void construct_solution(lprec *lp, REAL *target);\nSTATIC void transfer_solution_var(lprec *lp, int uservar);\nSTATIC MYBOOL construct_duals(lprec *lp);\nSTATIC MYBOOL construct_sensitivity_duals(lprec *lp);\nSTATIC MYBOOL construct_sensitivity_obj(lprec *lp);\n\nSTATIC int add_GUB(lprec *lp, char *name, int priority, int count, int *sosvars);\nSTATIC basisrec *push_basis(lprec *lp, int *basisvar, MYBOOL *isbasic, MYBOOL *islower);\nSTATIC MYBOOL compare_basis(lprec *lp);\nSTATIC MYBOOL restore_basis(lprec *lp);\nSTATIC MYBOOL pop_basis(lprec *lp, MYBOOL restore);\nSTATIC MYBOOL is_BasisReady(lprec *lp);\nSTATIC MYBOOL is_slackbasis(lprec *lp);\nSTATIC MYBOOL verify_basis(lprec *lp);\nSTATIC int unload_basis(lprec *lp, MYBOOL restorelast);\n\nSTATIC int perturb_bounds(lprec *lp, BBrec *perturbed, MYBOOL doRows, MYBOOL doCols, MYBOOL includeFIXED);\nSTATIC MYBOOL validate_bounds(lprec *lp, REAL *upbo, REAL *lowbo);\nSTATIC MYBOOL impose_bounds(lprec *lp, REAL * upbo, REAL *lowbo);\nSTATIC int unload_BB(lprec *lp);\n\nSTATIC REAL feasibilityOffset(lprec *lp, MYBOOL isdual);\nSTATIC MYBOOL isP1extra(lprec *lp);\nSTATIC REAL get_refactfrequency(lprec *lp, MYBOOL final);\nSTATIC int findBasicFixedvar(lprec *lp, int afternr, MYBOOL slacksonly);\nSTATIC MYBOOL isBasisVarFeasible(lprec *lp, REAL tol, int basis_row);\nSTATIC MYBOOL isPrimalFeasible(lprec *lp, REAL tol, int infeasibles[], REAL *feasibilitygap);\nSTATIC MYBOOL isDualFeasible(lprec *lp, REAL tol, int *boundflips, int infeasibles[], REAL *feasibilitygap);\n\n/* Main simplex driver routines */\nSTATIC int preprocess(lprec *lp);\nSTATIC void postprocess(lprec *lp);\nSTATIC MYBOOL performiteration(lprec *lp, int rownr, int varin, LREAL theta, MYBOOL primal, MYBOOL allowminit, REAL *prow, int *nzprow, REAL *pcol, int *nzpcol, int *boundswaps);\nSTATIC void transfer_solution_var(lprec *lp, int uservar);\nSTATIC void transfer_solution(lprec *lp, MYBOOL dofinal);\n\n/* Scaling utilities */\nSTATIC REAL scaled_floor(lprec *lp, int colnr, REAL value, REAL epsscale);\nSTATIC REAL scaled_ceil(lprec *lp, int colnr, REAL value, REAL epsscale);\n\n/* Variable mapping utility routines */\nSTATIC void varmap_lock(lprec *lp);\nSTATIC void varmap_clear(lprec *lp);\nSTATIC MYBOOL varmap_canunlock(lprec *lp);\nSTATIC void varmap_addconstraint(lprec *lp);\nSTATIC void varmap_addcolumn(lprec *lp);\nSTATIC void varmap_delete(lprec *lp, int base, int delta, LLrec *varmap);\nSTATIC void varmap_compact(lprec *lp, int prev_rows, int prev_cols);\nSTATIC MYBOOL varmap_validate(lprec *lp, int varno);\n/* STATIC MYBOOL del_varnameex(lprec *lp, hashelem **namelist, hashtable *ht, int varnr, LLrec *varmap); */\n STATIC MYBOOL del_varnameex(lprec *lp, hashelem **namelist, int items, hashtable *ht, int varnr, LLrec *varmap);\n\n/* Pseudo-cost routines (internal) */\nSTATIC BBPSrec *init_pseudocost(lprec *lp, int pseudotype);\nSTATIC void free_pseudocost(lprec *lp);\nSTATIC REAL get_pseudorange(BBPSrec *pc, int mipvar, int varcode);\nSTATIC void update_pseudocost(BBPSrec *pc, int mipvar, int varcode, MYBOOL capupper, REAL varsol);\nSTATIC REAL get_pseudobranchcost(BBPSrec *pc, int mipvar, MYBOOL dofloor);\nSTATIC REAL get_pseudonodecost(BBPSrec *pc, int mipvar, int vartype, REAL varsol);\n\n/* Matrix access and equation solving routines */\nSTATIC void set_OF_override(lprec *lp, REAL *ofVector);\nSTATIC void set_OF_p1extra(lprec *lp, REAL p1extra);\nSTATIC void unset_OF_p1extra(lprec *lp);\nMYBOOL modifyOF1(lprec *lp, int index, REAL *ofValue, REAL mult);\nREAL __WINAPI get_OF_active(lprec *lp, int varnr, REAL mult);\nSTATIC MYBOOL is_OF_nz(lprec *lp, int colnr);\n\nSTATIC int get_basisOF(lprec *lp, int coltarget[], REAL crow[], int colno[]);\nint    __WINAPI get_basiscolumn(lprec *lp, int j, int rn[], double bj[]);\nint    __WINAPI obtain_column(lprec *lp, int varin, REAL *pcol, int *nzlist, int *maxabs);\nSTATIC int compute_theta(lprec *lp, int rownr, LREAL *theta, int isupbound, REAL HarrisScalar, MYBOOL primal);\n\n/* Pivot utility routines */\nSTATIC int findBasisPos(lprec *lp, int notint, int *var_basic);\nSTATIC MYBOOL check_degeneracy(lprec *lp, REAL *pcol, int *degencount);\n\n#endif /* HEADER_lp_lib */\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_matrix.h",
    "content": "#ifndef HEADER_lp_matrix\n#define HEADER_lp_matrix\n\n#include \"lp_types.h\"\n#include \"lp_utils.h\"\n\n\n/* Sparse matrix element (ordered columnwise) */\ntypedef struct _MATitem\n{\n  int  rownr;\n  int  colnr;\n  REAL value;\n} MATitem;\n\n/* Constants for matrix product rounding options */\n#define MAT_ROUNDNONE             0\n#define MAT_ROUNDABS              1\n#define MAT_ROUNDREL              2\n#define MAT_ROUNDABSREL          (MAT_ROUNDABS + MAT_ROUNDREL)\n#define MAT_ROUNDRC               4\n#define MAT_ROUNDRCMIN            1.0 /* lp->epspivot */\n#if 1\n #define MAT_ROUNDDEFAULT         MAT_ROUNDREL  /* Typically increases performance */\n#else\n #define MAT_ROUNDDEFAULT         MAT_ROUNDABS  /* Probably gives more precision */\n#endif\n\n/* Compiler option development features */\n/*#define DebugInv*/               /* Report array values at factorization/inversion */\n#define NoLoopUnroll              /* Do not do loop unrolling */\n#define DirectArrayOF             /* Reference lp->obj[] array instead of function call */\n\n\n/* Matrix column access macros to be able to easily change storage model */\n#define CAM_Record                0\n#define CAM_Vector                1\n#if 0\n #define MatrixColAccess           CAM_Record\n#else\n #define MatrixColAccess           CAM_Vector\n#endif\n\n#if MatrixColAccess==CAM_Record\n#define SET_MAT_ijA(item,i,j,A)   mat->col_mat[item].rownr = i; \\\n                                  mat->col_mat[item].colnr = j; \\\n                                  mat->col_mat[item].value = A\n#define COL_MAT_COLNR(item)       (mat->col_mat[item].colnr)\n#define COL_MAT_ROWNR(item)       (mat->col_mat[item].rownr)\n#define COL_MAT_VALUE(item)       (mat->col_mat[item].value)\n#define COL_MAT_COPY(left,right)  mat->col_mat[left] = mat->col_mat[right]\n#define COL_MAT_MOVE(to,from,rec) MEMMOVE(&(mat->col_mat[to]),&(mat->col_mat[from]),rec)\n#define COL_MAT2_COLNR(item)      (mat2->col_mat[item].colnr)\n#define COL_MAT2_ROWNR(item)      (mat2->col_mat[item].rownr)\n#define COL_MAT2_VALUE(item)      (mat2->col_mat[item].value)\n#define matRowColStep             (sizeof(MATitem)/sizeof(int))\n#define matValueStep              (sizeof(MATitem)/sizeof(REAL))\n\n#else /* if MatrixColAccess==CAM_Vector */\n#define SET_MAT_ijA(item,i,j,A)   mat->col_mat_rownr[item] = i; \\\n                                  mat->col_mat_colnr[item] = j; \\\n                                  mat->col_mat_value[item] = A\n#define COL_MAT_COLNR(item)       (mat->col_mat_colnr[item])\n#define COL_MAT_ROWNR(item)       (mat->col_mat_rownr[item])\n#define COL_MAT_VALUE(item)       (mat->col_mat_value[item])\n#define COL_MAT_COPY(left,right)  COL_MAT_COLNR(left) = COL_MAT_COLNR(right); \\\n                                  COL_MAT_ROWNR(left) = COL_MAT_ROWNR(right); \\\n                                  COL_MAT_VALUE(left) = COL_MAT_VALUE(right)\n#define COL_MAT_MOVE(to,from,rec) MEMMOVE(&COL_MAT_COLNR(to),&COL_MAT_COLNR(from),rec); \\\n                                  MEMMOVE(&COL_MAT_ROWNR(to),&COL_MAT_ROWNR(from),rec); \\\n                                  MEMMOVE(&COL_MAT_VALUE(to),&COL_MAT_VALUE(from),rec)\n#define COL_MAT2_COLNR(item)      (mat2->col_mat_colnr[item])\n#define COL_MAT2_ROWNR(item)      (mat2->col_mat_rownr[item])\n#define COL_MAT2_VALUE(item)      (mat2->col_mat_value[item])\n#define matRowColStep             1\n#define matValueStep              1\n\n#endif\n\n\n/* Matrix row access macros to be able to easily change storage model */\n#define RAM_Index                 0\n#define RAM_FullCopy              1\n#define MatrixRowAccess           RAM_Index\n\n#if MatrixRowAccess==RAM_Index\n#define ROW_MAT_COLNR(item)       COL_MAT_COLNR(mat->row_mat[item])\n#define ROW_MAT_ROWNR(item)       COL_MAT_ROWNR(mat->row_mat[item])\n#define ROW_MAT_VALUE(item)       COL_MAT_VALUE(mat->row_mat[item])\n\n#elif MatrixColAccess==CAM_Record\n#define ROW_MAT_COLNR(item)       (mat->row_mat[item].colnr)\n#define ROW_MAT_ROWNR(item)       (mat->row_mat[item].rownr)\n#define ROW_MAT_VALUE(item)       (mat->row_mat[item].value)\n\n#else /* if MatrixColAccess==CAM_Vector */\n#define ROW_MAT_COLNR(item)       (mat->row_mat_colnr[item])\n#define ROW_MAT_ROWNR(item)       (mat->row_mat_rownr[item])\n#define ROW_MAT_VALUE(item)       (mat->row_mat_value[item])\n\n#endif\n\n\ntypedef struct _MATrec\n{\n  /* Owner reference */\n  lprec     *lp;\n\n  /* Active dimensions */\n  int       rows;\n  int       columns;\n\n  /* Allocated memory */\n  int       rows_alloc;\n  int       columns_alloc;\n  int       mat_alloc;          /* The allocated size for matrix sized structures */\n\n  /* Sparse problem matrix storage */\n#if MatrixColAccess==CAM_Record  \n  MATitem   *col_mat;           /* mat_alloc : The sparse data storage */\n#else /*MatrixColAccess==CAM_Vector*/\n  int       *col_mat_colnr;\n  int       *col_mat_rownr;\n  REAL      *col_mat_value;\n#endif  \n  int       *col_end;           /* columns_alloc+1 : col_end[i] is the index of the\n                                   first element after column i; column[i] is stored\n                                   in elements col_end[i-1] to col_end[i]-1 */\n  int       *col_tag;           /* user-definable tag associated with each column */\n\n#if MatrixRowAccess==RAM_Index\n  int       *row_mat;           /* mat_alloc : From index 0, row_mat contains the\n                                   row-ordered index of the elements of col_mat */\n#elif MatrixColAccess==CAM_Record\n  MATitem   *row_mat;           /* mat_alloc : From index 0, row_mat contains the\n                                   row-ordered copy of the elements in col_mat */\n#else /*if MatrixColAccess==CAM_Vector*/\n  int       *row_mat_colnr;\n  int       *row_mat_rownr;\n  REAL      *row_mat_value;\n#endif\n  int       *row_end;           /* rows_alloc+1 : row_end[i] is the index of the\n                                   first element in row_mat after row i */\n  int       *row_tag;           /* user-definable tag associated with each row */\n\n  REAL      *colmax;            /* Array of maximum values of each column */\n  REAL      *rowmax;            /* Array of maximum values of each row */\n\n  REAL      epsvalue;           /* Zero element rejection threshold */\n  REAL      infnorm;            /* The largest absolute value in the matrix */\n  REAL      dynrange;\n  MYBOOL    row_end_valid;      /* TRUE if row_end & row_mat are valid */\n  MYBOOL    is_roworder;        /* TRUE if the current (temporary) matrix order is row-wise */\n\n} MATrec;\n\ntypedef struct _DeltaVrec\n{\n  lprec     *lp;\n  int       activelevel;\n  MATrec    *tracker;\n} DeltaVrec;\n\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\n/* Sparse matrix routines */\nSTATIC MATrec *mat_create(lprec *lp, int rows, int columns, REAL epsvalue);\nSTATIC MYBOOL mat_memopt(MATrec *mat, int rowextra, int colextra, int nzextra);\nSTATIC void mat_free(MATrec **matrix);\nSTATIC MYBOOL inc_matrow_space(MATrec *mat, int deltarows);\nSTATIC int mat_mapreplace(MATrec *mat, LLrec *rowmap, LLrec *colmap, MATrec *insmat);\nSTATIC int mat_matinsert(MATrec *mat, MATrec *insmat);\nSTATIC int mat_zerocompact(MATrec *mat);\nSTATIC int mat_rowcompact(MATrec *mat, MYBOOL dozeros);\nSTATIC int mat_colcompact(MATrec *mat, int prev_rows, int prev_cols);\nSTATIC MYBOOL inc_matcol_space(MATrec *mat, int deltacols);\nSTATIC MYBOOL inc_mat_space(MATrec *mat, int mindelta);\nSTATIC int mat_shiftrows(MATrec *mat, int *bbase, int delta, LLrec *varmap);\nSTATIC int mat_shiftcols(MATrec *mat, int *bbase, int delta, LLrec *varmap);\nSTATIC MATrec *mat_extractmat(MATrec *mat, LLrec *rowmap, LLrec *colmap, MYBOOL negated);\nSTATIC int mat_appendrow(MATrec *mat, int count, REAL *row, int *colno, REAL mult, MYBOOL checkrowmode);\nSTATIC int mat_appendcol(MATrec *mat, int count, REAL *column, int *rowno, REAL mult, MYBOOL checkrowmode);\nMYBOOL mat_get_data(lprec *lp, int matindex, MYBOOL isrow, int **rownr, int **colnr, REAL **value);\nMYBOOL mat_set_rowmap(MATrec *mat, int row_mat_index, int rownr, int colnr, int col_mat_index);\nSTATIC MYBOOL mat_indexrange(MATrec *mat, int index, MYBOOL isrow, int *startpos, int *endpos);\nSTATIC MYBOOL mat_validate(MATrec *mat);\nSTATIC MYBOOL mat_equalRows(MATrec *mat, int baserow, int comprow);\nSTATIC int mat_findelm(MATrec *mat, int row, int column);\nSTATIC int mat_findins(MATrec *mat, int row, int column, int *insertpos, MYBOOL validate);\nSTATIC void mat_multcol(MATrec *mat, int col_nr, REAL mult, MYBOOL DoObj);\nSTATIC REAL mat_getitem(MATrec *mat, int row, int column);\nSTATIC MYBOOL mat_setitem(MATrec *mat, int row, int column, REAL value);\nSTATIC MYBOOL mat_additem(MATrec *mat, int row, int column, REAL delta);\nSTATIC MYBOOL mat_setvalue(MATrec *mat, int Row, int Column, REAL Value, MYBOOL doscale);\nSTATIC int mat_nonzeros(MATrec *mat);\nSTATIC int mat_collength(MATrec *mat, int colnr);\nSTATIC int mat_rowlength(MATrec *mat, int rownr);\nSTATIC void mat_multrow(MATrec *mat, int row_nr, REAL mult);\nSTATIC void mat_multadd(MATrec *mat, REAL *lhsvector, int varnr, REAL mult);\nSTATIC MYBOOL mat_setrow(MATrec *mat, int rowno, int count, REAL *row, int *colno, MYBOOL doscale, MYBOOL checkrowmode);\nSTATIC MYBOOL mat_setcol(MATrec *mat, int colno, int count, REAL *column, int *rowno, MYBOOL doscale, MYBOOL checkrowmode);\nSTATIC MYBOOL mat_mergemat(MATrec *target, MATrec *source, MYBOOL usecolmap);\nSTATIC int mat_checkcounts(MATrec *mat, int *rownum, int *colnum, MYBOOL freeonexit);\nSTATIC int mat_expandcolumn(MATrec *mat, int colnr, REAL *column, int *nzlist, MYBOOL signedA);\nSTATIC MYBOOL mat_computemax(MATrec *mat);\nSTATIC MYBOOL mat_transpose(MATrec *mat);\n\n/* Refactorization and recomputation routine */\nMYBOOL __WINAPI invert(lprec *lp, MYBOOL shiftbounds, MYBOOL final);\n\n/* Vector compression and expansion routines */\nSTATIC MYBOOL vec_compress(REAL *densevector, int startpos, int endpos, REAL epsilon, REAL *nzvector, int *nzindex);\nSTATIC MYBOOL vec_expand(REAL *nzvector, int *nzindex, REAL *densevector, int startpos, int endpos);\n\n/* Sparse matrix products */\nSTATIC MYBOOL get_colIndexA(lprec *lp, int varset, int *colindex, MYBOOL append);\nSTATIC int prod_Ax(lprec *lp, int *coltarget, REAL *input, int *nzinput, REAL roundzero, REAL ofscalar, REAL *output, int *nzoutput, int roundmode);\nSTATIC int prod_xA(lprec *lp, int *coltarget, REAL *input, int *nzinput, REAL roundzero, REAL ofscalar, REAL *output, int *nzoutput, int roundmode);\nSTATIC MYBOOL prod_xA2(lprec *lp, int *coltarget, REAL *prow, REAL proundzero, int *pnzprow,\n                                                  REAL *drow, REAL droundzero, int *dnzdrow, REAL ofscalar, int roundmode);\n\n/* Equation solution */\nSTATIC MYBOOL fimprove(lprec *lp, REAL *pcol, int *nzidx, REAL roundzero);\nSTATIC void ftran(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);\nSTATIC MYBOOL bimprove(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);\nSTATIC void btran(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);\n\n/* Combined equation solution and matrix product for simplex operations */\nSTATIC MYBOOL fsolve(lprec *lp, int varin, REAL *pcol, int *nzidx, REAL roundzero, REAL ofscalar, MYBOOL prepareupdate);\nSTATIC MYBOOL bsolve(lprec *lp, int row_nr, REAL *rhsvector, int *nzidx, REAL roundzero, REAL ofscalar);\nSTATIC void bsolve_xA2(lprec *lp, int* coltarget, \n                                  int row_nr1, REAL *vector1, REAL roundzero1, int *nzvector1,\n                                  int row_nr2, REAL *vector2, REAL roundzero2, int *nzvector2, int roundmode);\n\n/* Change-tracking routines (primarily for B&B and presolve) */\nSTATIC DeltaVrec *createUndoLadder(lprec *lp, int levelitems, int maxlevels);\nSTATIC int incrementUndoLadder(DeltaVrec *DV);\nSTATIC MYBOOL modifyUndoLadder(DeltaVrec *DV, int itemno, REAL target[], REAL newvalue);\nSTATIC int countsUndoLadder(DeltaVrec *DV);\nSTATIC int restoreUndoLadder(DeltaVrec *DV, REAL target[]);\nSTATIC int decrementUndoLadder(DeltaVrec *DV);\nSTATIC MYBOOL freeUndoLadder(DeltaVrec **DV);\n\n/* Specialized presolve undo functions */\nSTATIC MYBOOL appendUndoPresolve(lprec *lp, MYBOOL isprimal, REAL beta, int colnrDep);\nSTATIC MYBOOL addUndoPresolve(lprec *lp, MYBOOL isprimal, int colnrElim, REAL alpha, REAL beta, int colnrDep);\n\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* HEADER_lp_matrix */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_mipbb.h",
    "content": "#ifndef HEADER_lp_mipbb\n#define HEADER_lp_mipbb\n\n#include \"lp_types.h\"\n#include \"lp_utils.h\"\n\n\n/* Bounds storage for B&B routines */\ntypedef struct _BBrec\n{\n  struct    _BBrec *parent;\n  struct    _BBrec *child;\n  lprec     *lp;\n  int       varno;\n  int       vartype;\n  int       lastvarcus;            /* Count of non-int variables of the previous branch */\n  int       lastrcf;\n  int       nodesleft;\n  int       nodessolved;\n  int       nodestatus;\n  REAL      noderesult;\n  REAL      lastsolution;          /* Optimal solution of the previous branch */\n  REAL      sc_bound;\n  REAL      *upbo,   *lowbo;\n  REAL      UPbound, LObound;\n  int       UBtrack, LBtrack;      /* Signals that incoming bounds were changed */\n  MYBOOL    contentmode;           /* Flag indicating if we \"own\" the bound vectors */\n  MYBOOL    sc_canset;\n  MYBOOL    isSOS;\n  MYBOOL    isGUB;\n  int       *varmanaged;           /* Extended list of variables managed by this B&B level */\n  MYBOOL    isfloor;               /* State variable indicating the active B&B bound */\n  MYBOOL    UBzerobased;           /* State variable indicating if bounds have been rebased */\n} BBrec;\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nSTATIC BBrec *create_BB(lprec *lp, BBrec *parentBB, MYBOOL dofullcopy);\nSTATIC BBrec *push_BB(lprec *lp, BBrec *parentBB, int varno, int vartype, int varcus);\nSTATIC MYBOOL initbranches_BB(BBrec *BB);\nSTATIC MYBOOL fillbranches_BB(BBrec *BB);\nSTATIC MYBOOL nextbranch_BB(BBrec *BB);\nSTATIC MYBOOL strongbranch_BB(lprec *lp, BBrec *BB, int varno, int vartype, int varcus);\nSTATIC MYBOOL initcuts_BB(lprec *lp);\nSTATIC int updatecuts_BB(lprec *lp);\nSTATIC MYBOOL freecuts_BB(lprec *lp);\nSTATIC BBrec *findself_BB(BBrec *BB);\nSTATIC int solve_LP(lprec *lp, BBrec *BB);\nSTATIC int rcfbound_BB(BBrec *BB, int varno, MYBOOL isINT, REAL *newbound, MYBOOL *isfeasible);\nSTATIC MYBOOL findnode_BB(BBrec *BB, int *varno, int *vartype, int *varcus);\nSTATIC int solve_BB(BBrec *BB);\nSTATIC MYBOOL free_BB(BBrec **BB);\nSTATIC BBrec *pop_BB(BBrec *BB);\n\nSTATIC int run_BB(lprec *lp);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_mipbb */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_presolve.h",
    "content": "#ifndef HEADER_lp_presolve\n#define HEADER_lp_presolve\n\n#include \"lp_types.h\"\n#include \"lp_matrix.h\"\n\n/* -------------------------------------------------------------------------------------------- */\n/* Defines for various presolve options                                                         */\n/* -------------------------------------------------------------------------------------------- */\n\n#define MAX_PSMERGELOOPS                2                 /* Max loops to merge compatible constraints */\n#define MAX_PSLINDEPLOOPS               1   /* Max loops to detect linearly dependendent constraints */\n#define MAX_PSBOUNDTIGHTENLOOPS         5     /* Maximumn number of loops to allow bound tightenings */\n#define MIN_SOS1LENGTH                  4   /* Minimum length of a constraint for conversion to SOS1 */\n#if 1\n  #define PRESOLVE_EPSVALUE (0.1*lp->epsprimal)\n#else\n  #define PRESOLVE_EPSVALUE  lp->epsvalue\n#endif\n#define PRESOLVE_EPSPIVOT         1.0e-3        /* Looses robustness at values smaller than ~1.0e-3 */\n#define PRESOLVE_BOUNDSLACK           10                     /* Extra error recovery/tolerance margin */\n\n#define DoPresolveRounding              /* Use absolute and directed rounding (disable at own risk) */\n/*#define DoPresolveRelativeTest*/\n\n/*#define PresolveForceUpdateMax*/\n\n/*#define DualFeasibilityLogicEQ2*/              /* Add low-order feasibility/accuracy logic to elimEQ2 */\n#define DivisorIntegralityLogicEQ2                                   /* Always prefer integer divisors */\n#define FindImpliedEqualities                               /* Detect equalities (default is enabled) */\n#define Eq2Reldiff\n\n/*#define SavePresolveEliminated */        /* Enable to activate storage of eliminated matrix data */\n/*#define UseDualPresolve */                    /* Enable to use full dual information for presolve */\n\n\ntypedef struct _psrec\n{\n  LLrec *varmap;\n  int  **next;\n  int  *empty;\n  int  *plucount;\n  int  *negcount;\n  int  *pluneg;\n  int  *infcount;\n  REAL  *plulower;\n  REAL  *neglower;\n  REAL  *pluupper;\n  REAL  *negupper;\n  int  allocsize;\n} psrec;\n\ntypedef struct _presolverec\n{\n  psrec *rows;\n  psrec *cols;\n  LLrec *EQmap;\n  LLrec *LTmap;\n  LLrec *INTmap;\n  REAL  *pv_upbo;\n  REAL  *pv_lobo;\n  REAL  *dv_upbo;\n  REAL  *dv_lobo;\n  lprec *lp;\n  REAL  epsvalue;\n  REAL  epspivot;\n  int   innerloops;\n  int   middleloops;\n  int   outerloops;\n  int   nzdeleted;\n  MYBOOL forceupdate;\n} presolverec;\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\n\nSTATIC MYBOOL presolve_createUndo(lprec *lp);\nSTATIC MYBOOL presolve_rebuildUndo(lprec *lp, MYBOOL isprimal);\nSTATIC MYBOOL inc_presolve_space(lprec *lp, int delta, MYBOOL isrows);\nSTATIC MYBOOL presolve_setOrig(lprec *lp, int orig_rows, int orig_cols);\nSTATIC MYBOOL presolve_colfix(presolverec *psdata, int colnr, REAL newvalue, MYBOOL remove, int *tally);\nSTATIC MYBOOL presolve_fillUndo(lprec *lp, int orig_rows, int orig_cols, MYBOOL setOrig);\nSTATIC MYBOOL presolve_freeUndo(lprec *lp);\n\nSTATIC MYBOOL presolve_updatesums(presolverec *psdata);\n\nINLINE int presolve_nextrow(presolverec *psdata, int colnr, int *previtem);\nINLINE int presolve_nextcol(presolverec *psdata, int rownr, int *previtem);\n\nSTATIC presolverec *presolve_init(lprec *lp);\nSTATIC void presolve_free(presolverec **psdata);\nSTATIC int presolve_shrink(presolverec *psdata, int *nConRemove, int *nVarRemove);\nSTATIC void presolve_rowremove(presolverec *psdata, int rownr, MYBOOL allowcoldelete);\nSTATIC int presolve_colremove(presolverec *psdata, int colnr, MYBOOL allowrowdelete);\n\nSTATIC MYBOOL presolve_colfixdual(presolverec *psdata, int colnr, REAL *fixValue, int *status);\n\nINLINE int presolve_rowlength(presolverec *psdata, int rownr)\n{\n  int *items = psdata->rows->next[rownr];\n\n  if(items == NULL)\n    return( 0 );\n  else\n    return( items[0] );\n}\nINLINE int presolve_collength(presolverec *psdata, int colnr)\n{\n  int *items = psdata->cols->next[colnr];\n  if(items == NULL)\n    return( 0 );\n  else\n    return( items[0] );\n}\n\nSTATIC int presolve(lprec *lp);\nSTATIC MYBOOL postsolve(lprec *lp, int status);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_presolve */\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_price.h",
    "content": "#ifndef HEADER_lp_price\n#define HEADER_lp_price\n\n/* Local defines                                                             */\n/* ------------------------------------------------------------------------- */\n#define UseSortOnBound_Improve\n/*#define UseSortOnBound_Substitute*/\n\n#if 0 /* Stricter feasibility-preserving tolerance; use w/ *_UseRejectionList */\n  #define UseRelativeFeasibility       /* Use machine-precision and A-scale data */\n#endif\n#if 0          /* Stricter pivot-selection criteria; use w/ *UseRejectionList */\n  #define UseRelativePivot_Primal             /* In rowprim based on A-scale data */\n  #define UseRelativePivot_Dual               /* In coldual based on A-scale data */\n#endif\n\n\n/* Include required library headers                                          */\n/* ------------------------------------------------------------------------- */\n#include \"lp_types.h\"\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Comparison and validity routines */\nint CMP_CALLMODEL compareImprovementVar(const pricerec *current, const pricerec *candidate);\nint CMP_CALLMODEL compareSubstitutionVar(const pricerec *current, const pricerec *candidate);\nint CMP_CALLMODEL compareBoundFlipVar(const pricerec *current, const pricerec *candidate);\nSTATIC int addCandidateVar(pricerec *candidate, multirec *multi, findCompare_func findCompare, MYBOOL allowSortedExpand);\nSTATIC MYBOOL collectMinorVar(pricerec *candidate, multirec *longsteps, MYBOOL isphase2, MYBOOL isbatch);\nSTATIC MYBOOL validImprovementVar(pricerec *candidate);\nSTATIC MYBOOL validSubstitutionVar(pricerec *candidate);\n\n/* Row+column selection routines */\nSTATIC MYBOOL findImprovementVar(pricerec *current, pricerec *candidate, MYBOOL collectMP, int *candidatecount);\nSTATIC MYBOOL findSubstitutionVar(pricerec *current, pricerec *candidate, int *candidatecount);\nINLINE REAL normalizeEdge(lprec *lp, int item, REAL edge, MYBOOL isdual);\nSTATIC void makePriceLoop(lprec *lp, int *start, int *end, int *delta);\n\n/* Computation of reduced costs */\nSTATIC void update_reducedcosts(lprec *lp, MYBOOL isdual, int leave_nr, int enter_nr, REAL *prow, REAL *drow);\nSTATIC void compute_reducedcosts(lprec *lp, MYBOOL isdual, int row_nr, int *coltarget, MYBOOL dosolve,\n                                                            REAL *prow, int *nzprow,\n                                                            REAL *drow, int *nzdrow,\n                                                            int roundmode);\n\n/* Leaving variable selection and entering column pricing loops */\nSTATIC int find_rowReplacement(lprec *lp, int rownr, REAL *prow, int *nzprow);\nSTATIC int colprim(lprec *lp, REAL *drow, int *nzdrow,\n                              MYBOOL skipupdate, int partialloop, int *candidatecount, MYBOOL updateinfeas, REAL *xviol);\nSTATIC int rowprim(lprec *lp, int colnr, LREAL *theta, REAL *pcol, int *nzpcol, MYBOOL forceoutEQ, REAL *xviol);\nSTATIC int rowdual(lprec *lp, REAL *rhvec, MYBOOL forceoutEQ, MYBOOL updateinfeas, REAL *xviol);\nSTATIC int coldual(lprec *lp, int row_nr,\n                              REAL *prow, int *nzprow, REAL *drow, int *nzdrow,\n                              MYBOOL dualphase1, MYBOOL skipupdate,\n                              int *candidatecount, REAL *xviol);\n\n/* Partial pricing management routines */\nSTATIC partialrec *partial_createBlocks(lprec *lp, MYBOOL isrow);\nSTATIC int partial_countBlocks(lprec *lp, MYBOOL isrow);\nSTATIC int partial_activeBlocks(lprec *lp, MYBOOL isrow);\nSTATIC void partial_freeBlocks(partialrec **blockdata);\n\n/* Partial pricing utility routines */\nSTATIC int partial_findBlocks(lprec *lp, MYBOOL autodefine, MYBOOL isrow);\nSTATIC int partial_blockStart(lprec *lp, MYBOOL isrow);\nSTATIC int partial_blockEnd(lprec *lp, MYBOOL isrow);\nSTATIC int partial_blockNextPos(lprec *lp, int block, MYBOOL isrow);\n\nSTATIC MYBOOL partial_blockStep(lprec *lp, MYBOOL isrow);\nSTATIC MYBOOL partial_isVarActive(lprec *lp, int varno, MYBOOL isrow);\n\n/* Multiple pricing / dual long step management routines */\nSTATIC multirec *multi_create(lprec *lp, MYBOOL truncinf);\nSTATIC MYBOOL multi_resize(multirec *multi, int blocksize, int blockdiv, MYBOOL doVlist, MYBOOL doIset);\nSTATIC int multi_restart(multirec *multi);\nSTATIC int multi_size(multirec *multi);\nSTATIC int multi_used(multirec *multi);\nSTATIC MYBOOL multi_truncatingvar(multirec *multi, int varnr);\nSTATIC MYBOOL multi_mustupdate(multirec *multi);\nSTATIC void multi_valueInit(multirec *multi, REAL step_base, REAL obj_base);\nSTATIC REAL *multi_valueList(multirec *multi);\nSTATIC int *multi_indexSet(multirec *multi, MYBOOL regenerate);\nSTATIC int multi_getvar(multirec *multi, int item);\nSTATIC MYBOOL multi_recompute(multirec *multi, int index, MYBOOL isphase2, MYBOOL fullupdate);\nSTATIC MYBOOL multi_removevar(multirec *multi, int varnr);\nSTATIC int multi_enteringvar(multirec *multi, pricerec *current, int priority);\nSTATIC REAL multi_enteringtheta(multirec *multi);\nSTATIC void multi_free(multirec **multi);\nSTATIC int multi_populateSet(multirec *multi, int **list, int excludenr);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_price */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_pricePSE.h",
    "content": "#ifndef HEADER_lp_pricePSE\n#define HEADER_lp_pricePSE\n\n#include \"lp_types.h\"\n\n#define ApplySteepestEdgeMinimum\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Price norm management routines */\nSTATIC MYBOOL initPricer(lprec *lp);\nINLINE MYBOOL applyPricer(lprec *lp);\nSTATIC void simplexPricer(lprec *lp, MYBOOL isdual);\nSTATIC void freePricer(lprec *lp);\nSTATIC MYBOOL resizePricer(lprec *lp);\nSTATIC REAL getPricer(lprec *lp, int item, MYBOOL isdual);\nSTATIC MYBOOL restartPricer(lprec *lp, MYBOOL isdual);\nSTATIC MYBOOL updatePricer(lprec *lp, int rownr, int colnr, REAL *pcol, REAL *prow, int *nzprow);\nSTATIC MYBOOL verifyPricer(lprec *lp);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_pricePSE */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_report.h",
    "content": "#ifndef HEADER_lp_report\n#define HEADER_lp_report\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* General information functions */\nchar * __VACALL explain(lprec *lp, char *format, ...);\nvoid __VACALL report(lprec *lp, int level, char *format, ...);\n\n/* Prototypes for debugging and general data dumps */\nvoid debug_print(lprec *lp, char *format, ...);\nvoid debug_print_solution(lprec *lp);\nvoid debug_print_bounds(lprec *lp, REAL *upbo, REAL *lowbo);\nvoid blockWriteLREAL(FILE *output, char *label, LREAL *vector, int first, int last);\nvoid blockWriteAMAT(FILE *output, const char *label, lprec* lp, int first, int last);\nvoid blockWriteBMAT(FILE *output, const char *label, lprec* lp, int first, int last);\n\n\n/* Model reporting headers */\nvoid REPORT_objective(lprec *lp);\nvoid REPORT_solution(lprec *lp, int columns);\nvoid REPORT_constraints(lprec *lp, int columns);\nvoid REPORT_duals(lprec *lp);\nvoid REPORT_extended(lprec *lp);\n\n/* Other rarely used, but sometimes extremely useful reports */\nvoid REPORT_constraintinfo(lprec *lp, char *datainfo);\nvoid REPORT_modelinfo(lprec *lp, MYBOOL doName, char *datainfo);\nvoid REPORT_lp(lprec *lp);\nMYBOOL REPORT_tableau(lprec *lp);\nvoid REPORT_scales(lprec *lp);\nMYBOOL REPORT_debugdump(lprec *lp, char *filename, MYBOOL livedata);\nMYBOOL REPORT_mat_mmsave(lprec *lp, char *filename, int *colndx, MYBOOL includeOF, char *infotext);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_report */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_rlp.h",
    "content": "\n\n\n#define  YY_INT_ALIGNED short int\n\n/* A lexical scanner generated by flex */\n\n#define FLEX_SCANNER\n#define YY_FLEX_MAJOR_VERSION 2\n#define YY_FLEX_MINOR_VERSION 5\n#define YY_FLEX_SUBMINOR_VERSION 35\n#if YY_FLEX_SUBMINOR_VERSION > 0\n#define FLEX_BETA\n#endif\n\n/* First, we deal with  platform-specific or compiler-specific issues. */\n\n/* begin standard C headers. */\n#include <stdio.h>\n#include <string.h>\n#include <errno.h>\n#include <stdlib.h>\n\n/* end standard C headers. */\n\n/* flex integer type definitions */\n\n#ifndef FLEXINT_H\n#define FLEXINT_H\n\n/* C99 systems have <inttypes.h>. Non-C99 systems may or may not. */\n\n#if defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L\n\n/* C99 says to define __STDC_LIMIT_MACROS before including stdint.h,\n * if you want the limit (max/min) macros for int types. \n */\n#ifndef __STDC_LIMIT_MACROS\n#define __STDC_LIMIT_MACROS 1\n#endif\n\n#include <inttypes.h>\ntypedef int8_t flex_int8_t;\ntypedef uint8_t flex_uint8_t;\ntypedef int16_t flex_int16_t;\ntypedef uint16_t flex_uint16_t;\ntypedef int32_t flex_int32_t;\ntypedef uint32_t flex_uint32_t;\n#else\ntypedef signed char flex_int8_t;\ntypedef short int flex_int16_t;\ntypedef int flex_int32_t;\ntypedef unsigned char flex_uint8_t; \ntypedef unsigned short int flex_uint16_t;\ntypedef unsigned int flex_uint32_t;\n#endif /* ! C99 */\n\n/* Limits of integral types. */\n#ifndef INT8_MIN\n#define INT8_MIN               (-128)\n#endif\n#ifndef INT16_MIN\n#define INT16_MIN              (-32767-1)\n#endif\n#ifndef INT32_MIN\n#define INT32_MIN              (-2147483647-1)\n#endif\n#ifndef INT8_MAX\n#define INT8_MAX               (127)\n#endif\n#ifndef INT16_MAX\n#define INT16_MAX              (32767)\n#endif\n#ifndef INT32_MAX\n#define INT32_MAX              (2147483647)\n#endif\n#ifndef UINT8_MAX\n#define UINT8_MAX              (255U)\n#endif\n#ifndef UINT16_MAX\n#define UINT16_MAX             (65535U)\n#endif\n#ifndef UINT32_MAX\n#define UINT32_MAX             (4294967295U)\n#endif\n\n#endif /* ! FLEXINT_H */\n\n#ifdef __cplusplus\n\n/* The \"const\" storage-class-modifier is valid. */\n#define YY_USE_CONST\n\n#else\t/* ! __cplusplus */\n\n/* C99 requires __STDC__ to be defined as 1. */\n#if defined (__STDC__)\n\n#define YY_USE_CONST\n\n#endif\t/* defined (__STDC__) */\n#endif\t/* ! __cplusplus */\n\n#ifdef YY_USE_CONST\n#define lp_yyconst const\n#else\n#define lp_yyconst\n#endif\n\n/* Returned upon end-of-file. */\n#define YY_NULL 0\n\n/* Promotes a possibly negative, possibly signed char to an unsigned\n * integer for use as an array index.  If the signed char is negative,\n * we want to instead treat it as an 8-bit unsigned char, hence the\n * double cast.\n */\n#define YY_SC_TO_UI(c) ((unsigned int) (unsigned char) c)\n\n/* An opaque pointer. */\n#ifndef YY_TYPEDEF_YY_SCANNER_T\n#define YY_TYPEDEF_YY_SCANNER_T\ntypedef void* lp_yyscan_t;\n#endif\n\n/* For convenience, these vars (plus the bison vars far below)\n   are macros in the reentrant scanner. */\n#define lp_yyin lp_yyg->lp_yyin_r\n#define lp_yyout lp_yyg->lp_yyout_r\n#define lp_yyextra lp_yyg->lp_yyextra_r\n#define lp_yyleng lp_yyg->lp_yyleng_r\n#define lp_yytext lp_yyg->lp_yytext_r\n#define lp_yylineno (YY_CURRENT_BUFFER_LVALUE->lp_yy_bs_lineno)\n#define lp_yycolumn (YY_CURRENT_BUFFER_LVALUE->lp_yy_bs_column)\n#define lp_yy_flex_debug lp_yyg->lp_yy_flex_debug_r\n\n/* Enter a start condition.  This macro really ought to take a parameter,\n * but we do it the disgusting crufty way forced on us by the ()-less\n * definition of BEGIN.\n */\n#define BEGIN lp_yyg->lp_yy_start = 1 + 2 *\n\n/* Translate the current start state into a value that can be later handed\n * to BEGIN to return to the state.  The YYSTATE alias is for lex\n * compatibility.\n */\n#define YY_START ((lp_yyg->lp_yy_start - 1) / 2)\n#define YYSTATE YY_START\n\n/* Action number for EOF rule of a given start state. */\n#define YY_STATE_EOF(state) (YY_END_OF_BUFFER + state + 1)\n\n/* Special action meaning \"start processing a new file\". */\n#define YY_NEW_FILE lp_yyrestart(lp_yyin ,lp_yyscanner )\n\n#define YY_END_OF_BUFFER_CHAR 0\n\n/* Size of default input buffer. */\n#ifndef YY_BUF_SIZE\n#define YY_BUF_SIZE 16384\n#endif\n\n/* The state buf must be large enough to hold one state per character in the main buffer.\n */\n#define YY_STATE_BUF_SIZE   ((YY_BUF_SIZE + 2) * sizeof(lp_yy_state_type))\n\n#ifndef YY_TYPEDEF_YY_BUFFER_STATE\n#define YY_TYPEDEF_YY_BUFFER_STATE\ntypedef struct lp_yy_buffer_state *YY_BUFFER_STATE;\n#endif\n\n#define EOB_ACT_CONTINUE_SCAN 0\n#define EOB_ACT_END_OF_FILE 1\n#define EOB_ACT_LAST_MATCH 2\n\n    /* Note: We specifically omit the test for lp_yy_rule_can_match_eol because it requires\n     *       access to the local variable lp_yy_act. Since lp_yyless() is a macro, it would break\n     *       existing scanners that call lp_yyless() from OUTSIDE lp_yylex. \n     *       One obvious solution it to make lp_yy_act a global. I tried that, and saw\n     *       a 5% performance hit in a non-lp_yylineno scanner, because lp_yy_act is\n     *       normally declared as a register variable-- so it is not worth it.\n     */\n    #define  YY_LESS_LINENO(n) \\\n            do { \\\n                int lp_yyl;\\\n                for ( lp_yyl = n; lp_yyl < lp_yyleng; ++lp_yyl )\\\n                    if ( lp_yytext[lp_yyl] == '\\n' )\\\n                        --lp_yylineno;\\\n            }while(0)\n    \n/* Return all but the first \"n\" matched characters back to the input stream. */\n#define lp_yyless(n) \\\n\tdo \\\n\t\t{ \\\n\t\t/* Undo effects of setting up lp_yytext. */ \\\n        int lp_yyless_macro_arg = (n); \\\n        YY_LESS_LINENO(lp_yyless_macro_arg);\\\n\t\t*lp_yy_cp = lp_yyg->lp_yy_hold_char; \\\n\t\tYY_RESTORE_YY_MORE_OFFSET \\\n\t\tlp_yyg->lp_yy_c_buf_p = lp_yy_cp = lp_yy_bp + lp_yyless_macro_arg - YY_MORE_ADJ; \\\n\t\tYY_DO_BEFORE_ACTION; /* set up lp_yytext again */ \\\n\t\t} \\\n\twhile ( 0 )\n\n#define unput(c) lp_yyunput( c, lp_yyg->lp_yytext_ptr , lp_yyscanner )\n\n#ifndef YY_TYPEDEF_YY_SIZE_T\n#define YY_TYPEDEF_YY_SIZE_T\ntypedef size_t lp_yy_size_t;\n#endif\n\n#ifndef YY_STRUCT_YY_BUFFER_STATE\n#define YY_STRUCT_YY_BUFFER_STATE\nstruct lp_yy_buffer_state\n\t{\n\tFILE *lp_yy_input_file;\n\n\tchar *lp_yy_ch_buf;\t\t/* input buffer */\n\tchar *lp_yy_buf_pos;\t\t/* current position in input buffer */\n\n\t/* Size of input buffer in bytes, not including room for EOB\n\t * characters.\n\t */\n\tlp_yy_size_t lp_yy_buf_size;\n\n\t/* Number of characters read into lp_yy_ch_buf, not including EOB\n\t * characters.\n\t */\n\tint lp_yy_n_chars;\n\n\t/* Whether we \"own\" the buffer - i.e., we know we created it,\n\t * and can realloc() it to grow it, and should free() it to\n\t * delete it.\n\t */\n\tint lp_yy_is_our_buffer;\n\n\t/* Whether this is an \"interactive\" input source; if so, and\n\t * if we're using stdio for input, then we want to use getc()\n\t * instead of fread(), to make sure we stop fetching input after\n\t * each newline.\n\t */\n\tint lp_yy_is_interactive;\n\n\t/* Whether we're considered to be at the beginning of a line.\n\t * If so, '^' rules will be active on the next match, otherwise\n\t * not.\n\t */\n\tint lp_yy_at_bol;\n\n    int lp_yy_bs_lineno; /**< The line count. */\n    int lp_yy_bs_column; /**< The column count. */\n    \n\t/* Whether to try to fill the input buffer when we reach the\n\t * end of it.\n\t */\n\tint lp_yy_fill_buffer;\n\n\tint lp_yy_buffer_status;\n\n#define YY_BUFFER_NEW 0\n#define YY_BUFFER_NORMAL 1\n\t/* When an EOF's been seen but there's still some text to process\n\t * then we mark the buffer as YY_EOF_PENDING, to indicate that we\n\t * shouldn't try reading from the input source any more.  We might\n\t * still have a bunch of tokens to match, though, because of\n\t * possible backing-up.\n\t *\n\t * When we actually see the EOF, we change the status to \"new\"\n\t * (via lp_yyrestart()), so that the user can continue scanning by\n\t * just pointing lp_yyin at a new input file.\n\t */\n#define YY_BUFFER_EOF_PENDING 2\n\n\t};\n#endif /* !YY_STRUCT_YY_BUFFER_STATE */\n\n/* We provide macros for accessing buffer states in case in the\n * future we want to put the buffer states in a more general\n * \"scanner state\".\n *\n * Returns the top of the stack, or NULL.\n */\n#define YY_CURRENT_BUFFER ( lp_yyg->lp_yy_buffer_stack \\\n                          ? lp_yyg->lp_yy_buffer_stack[lp_yyg->lp_yy_buffer_stack_top] \\\n                          : NULL)\n\n/* Same as previous macro, but useful when we know that the buffer stack is not\n * NULL or when we need an lvalue. For internal use only.\n */\n#define YY_CURRENT_BUFFER_LVALUE lp_yyg->lp_yy_buffer_stack[lp_yyg->lp_yy_buffer_stack_top]\n\nvoid lp_yyrestart (FILE *input_file ,lp_yyscan_t lp_yyscanner );\nvoid lp_yy_switch_to_buffer (YY_BUFFER_STATE new_buffer ,lp_yyscan_t lp_yyscanner );\nYY_BUFFER_STATE lp_yy_create_buffer (FILE *file,int size ,lp_yyscan_t lp_yyscanner );\nvoid lp_yy_delete_buffer (YY_BUFFER_STATE b ,lp_yyscan_t lp_yyscanner );\nvoid lp_yy_flush_buffer (YY_BUFFER_STATE b ,lp_yyscan_t lp_yyscanner );\nvoid lp_yypush_buffer_state (YY_BUFFER_STATE new_buffer ,lp_yyscan_t lp_yyscanner );\nvoid lp_yypop_buffer_state (lp_yyscan_t lp_yyscanner );\n\nstatic void lp_yyensure_buffer_stack (lp_yyscan_t lp_yyscanner );\nstatic void lp_yy_load_buffer_state (lp_yyscan_t lp_yyscanner );\nstatic void lp_yy_init_buffer (YY_BUFFER_STATE b,FILE *file ,lp_yyscan_t lp_yyscanner );\n\n#define YY_FLUSH_BUFFER lp_yy_flush_buffer(YY_CURRENT_BUFFER ,lp_yyscanner)\n\nYY_BUFFER_STATE lp_yy_scan_buffer (char *base,lp_yy_size_t size ,lp_yyscan_t lp_yyscanner );\nYY_BUFFER_STATE lp_yy_scan_string (lp_yyconst char *lp_yy_str ,lp_yyscan_t lp_yyscanner );\nYY_BUFFER_STATE lp_yy_scan_bytes (lp_yyconst char *bytes,int len ,lp_yyscan_t lp_yyscanner );\n\nvoid *lp_yyalloc (lp_yy_size_t ,lp_yyscan_t lp_yyscanner );\nvoid *lp_yyrealloc (void *,lp_yy_size_t ,lp_yyscan_t lp_yyscanner );\nvoid lp_yyfree (void * ,lp_yyscan_t lp_yyscanner );\n\n#define lp_yy_new_buffer lp_yy_create_buffer\n\n#define lp_yy_set_interactive(is_interactive) \\\n\t{ \\\n\tif ( ! YY_CURRENT_BUFFER ){ \\\n        lp_yyensure_buffer_stack (lp_yyscanner); \\\n\t\tYY_CURRENT_BUFFER_LVALUE =    \\\n            lp_yy_create_buffer(lp_yyin,YY_BUF_SIZE ,lp_yyscanner); \\\n\t} \\\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_is_interactive = is_interactive; \\\n\t}\n\n#define lp_yy_set_bol(at_bol) \\\n\t{ \\\n\tif ( ! YY_CURRENT_BUFFER ){\\\n        lp_yyensure_buffer_stack (lp_yyscanner); \\\n\t\tYY_CURRENT_BUFFER_LVALUE =    \\\n            lp_yy_create_buffer(lp_yyin,YY_BUF_SIZE ,lp_yyscanner); \\\n\t} \\\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol = at_bol; \\\n\t}\n\n#define YY_AT_BOL() (YY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol)\n\n/* Begin user sect3 */\n\n#define lp_yywrap(n) 1\n#define YY_SKIP_YYWRAP\n\ntypedef unsigned char YY_CHAR;\n\ntypedef int lp_yy_state_type;\n\n#define lp_yytext_ptr lp_yytext_r\n\nstatic lp_yy_state_type lp_yy_get_previous_state (lp_yyscan_t lp_yyscanner );\nstatic lp_yy_state_type lp_yy_try_NUL_trans (lp_yy_state_type current_state  ,lp_yyscan_t lp_yyscanner);\nstatic int lp_yy_get_next_buffer (lp_yyscan_t lp_yyscanner );\nstatic void lp_yy_fatal_error (lp_yyconst char msg[] ,lp_yyscan_t lp_yyscanner );\n\n/* Done after the current pattern has been matched and before the\n * corresponding action - sets up lp_yytext.\n */\n#define YY_DO_BEFORE_ACTION \\\n\tlp_yyg->lp_yytext_ptr = lp_yy_bp; \\\n\tlp_yyleng = (size_t) (lp_yy_cp - lp_yy_bp); \\\n\tlp_yyg->lp_yy_hold_char = *lp_yy_cp; \\\n\t*lp_yy_cp = '\\0'; \\\n\tlp_yyg->lp_yy_c_buf_p = lp_yy_cp;\n\n#define YY_NUM_RULES 33\n#define YY_END_OF_BUFFER 34\n/* This struct is not used in this scanner,\n   but its presence is necessary. */\nstruct lp_yy_trans_info\n\t{\n\tflex_int32_t lp_yy_verify;\n\tflex_int32_t lp_yy_nxt;\n\t};\nstatic lp_yyconst flex_int16_t lp_yy_accept[144] =\n    {   0,\n        0,    0,    0,    0,    0,    0,   34,   32,   10,   10,\n       27,   17,   11,   32,   32,   14,   26,   31,   29,   28,\n       30,   25,   25,   10,   25,   25,   25,   25,    3,    4,\n        3,    3,    9,    7,    8,   10,   17,   17,    0,   15,\n        1,    6,   15,   14,    0,   29,   30,    0,   25,   24,\n        0,   25,   25,   10,    0,    0,    0,    0,   25,   25,\n       25,   25,   25,    2,    0,   15,    0,   15,   22,    0,\n       25,   25,    0,    0,    0,    0,    0,   19,   25,   18,\n       20,   25,   25,   21,    0,   25,    0,   13,   25,    0,\n       12,   25,   19,    0,   18,   20,   21,   25,   23,   25,\n\n       20,   21,   21,   16,   16,    0,   25,   25,    0,   23,\n        0,   21,   25,   25,    0,    0,   25,   25,    0,    0,\n       19,   25,    0,    0,   25,   25,   19,    0,   18,    0,\n        0,   25,   25,   18,    0,    0,    0,    0,    0,    0,\n        0,    0,    0\n    } ;\n\nstatic lp_yyconst flex_int32_t lp_yy_ec[256] =\n    {   0,\n        1,    1,    1,    1,    1,    1,    1,    1,    2,    3,\n        1,    1,    4,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    2,    1,    1,    5,    6,    5,    5,    5,    1,\n        1,    7,    8,    9,   10,   11,   12,   13,   14,   14,\n       13,   13,   13,   13,   13,   13,   13,   15,   16,   17,\n       18,   19,    1,    5,   20,   21,   22,   23,   24,   25,\n       26,   23,   27,   23,   23,   23,   28,   29,   30,   23,\n       23,   31,   32,   33,   34,   23,   23,   35,   36,   37,\n        5,    1,    5,    5,    5,    1,   20,   21,   22,   23,\n\n       24,   25,   26,   23,   27,   23,   23,   23,   28,   29,\n       30,   23,   23,   31,   32,   33,   34,   23,   23,   35,\n       36,   37,    5,    1,    5,    5,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1\n    } ;\n\nstatic lp_yyconst flex_int32_t lp_yy_meta[38] =\n    {   0,\n        1,    2,    3,    3,    4,    5,    6,    3,    6,    3,\n        5,    5,    5,    5,    7,    6,    7,    6,    6,    4,\n        4,    4,    4,    4,    4,    4,    8,    4,    4,    4,\n        4,    4,    4,    4,    4,    4,    4\n    } ;\n\nstatic lp_yyconst flex_int16_t lp_yy_base[150] =\n    {   0,\n        0,   36,   36,   38,   43,   45,  366,  388,   48,   62,\n      388,  338,  388,   40,   48,   60,  388,  388,  346,  388,\n      326,   60,   65,   91,   81,   74,   85,  102,  388,  388,\n      388,  330,  388,  388,  388,  125,  313,  134,  308,   96,\n      388,  388,  117,  132,  139,  388,  388,   88,  146,  320,\n        0,  149,  152,    0,  307,  301,  294,   83,  153,  156,\n      157,  189,  160,  388,  286,  126,   65,  108,  388,  289,\n      181,  185,  272,  273,  250,  249,  220,  199,  203,  208,\n      192,  211,  219,  227,  243,  109,  163,  225,  202,  174,\n      224,  215,  213,  207,  191,  388,  189,  227,  228,  231,\n\n      244,  240,  253,  276,  388,  170,  260,  262,  166,  388,\n      169,  179,  263,  241,  166,  159,  270,  272,  149,  155,\n      284,  288,  130,  124,  296,  303,  388,  103,  300,   96,\n       45,  324,  328,  388,   82,  311,   79,   68,   54,   56,\n       25,   12,  388,  345,  353,  360,  367,  372,  379\n    } ;\n\nstatic lp_yyconst flex_int16_t lp_yy_def[150] =\n    {   0,\n      143,    1,  144,  144,  145,  145,  143,  143,  143,  143,\n      143,  146,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  147,  147,  143,  147,  147,  147,  147,  143,  143,\n      143,  143,  143,  143,  143,  143,  146,  143,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  147,  143,\n      148,  147,  147,   24,  143,  143,  143,  143,  147,  147,\n      147,  147,  147,  143,  143,  143,  143,  143,  143,  148,\n      147,  147,  143,  143,  143,  143,  143,  147,  147,  147,\n      147,  147,  147,  147,  149,  143,  143,  143,   62,  143,\n      143,   62,  143,  143,  143,  143,  143,   62,   62,   62,\n\n       62,   62,   62,  143,  143,  143,   62,   62,  143,  143,\n      143,  143,   62,   62,  143,  143,   62,   62,  143,  143,\n       62,   62,  143,  143,   62,   62,  143,  143,   62,  143,\n      143,  147,  147,  143,  143,  149,  143,  143,  143,  143,\n      143,  143,    0,  143,  143,  143,  143,  143,  143\n    } ;\n\nstatic lp_yyconst flex_int16_t lp_yy_nxt[426] =\n    {   0,\n        8,    9,   10,    9,    8,    8,   11,   12,   13,   12,\n       14,   15,   16,   16,   17,   18,   19,   20,   21,   22,\n       22,   22,   22,   22,   22,   22,   22,   23,   22,   22,\n       22,   22,   22,   22,   22,   22,   22,   24,   30,   31,\n       30,   31,   32,   96,   32,   34,   35,   34,   35,   36,\n       36,   36,   40,   40,   41,   37,   25,   37,  142,   42,\n       26,   48,   27,   36,   36,   36,   48,   28,  136,   37,\n       43,   37,   44,   44,   50,   48,   51,   68,   68,   50,\n      136,   51,   48,   45,   52,  141,   48,  140,   50,   48,\n       51,   53,   54,   36,   36,   50,  139,   51,   37,   50,\n\n       37,   51,   50,   48,   60,  138,   76,   59,   40,   40,\n       48,   55,   77,   61,  137,   56,   50,   57,   51,   45,\n       68,   68,   58,   50,  135,   62,   36,   36,   36,   66,\n       66,   63,   37,  134,   37,   38,   38,   38,   66,   66,\n       45,   38,   43,   38,   44,   44,   67,   48,   67,   45,\n       48,   68,   68,   48,   48,   45,  131,   48,   48,  130,\n       50,   48,   51,   50,   87,   51,   50,   50,   51,   51,\n       50,   50,   51,   51,   50,   90,   51,   88,  128,   79,\n       72,   78,   87,   71,  127,  124,   90,  123,   91,   80,\n       48,   84,  112,   48,  120,   88,  119,   51,  116,   91,\n\n       48,   51,  112,   50,   48,   51,   50,   89,   51,   48,\n       81,   92,   48,   50,  111,   51,   82,   50,   98,   51,\n       48,   83,   50,   49,   51,   50,   99,   51,   48,  107,\n      110,  100,  109,   50,   49,   51,   49,  101,   69,   69,\n      103,   50,  108,   51,  104,  104,  104,   49,   49,   49,\n      102,   97,   49,  115,   49,   49,  114,  113,   49,   49,\n       49,   49,   49,   49,  122,   49,  103,   49,   49,  106,\n       96,   49,   49,   49,   49,   81,   49,  104,  104,  104,\n       49,   49,   95,   49,   49,   49,  117,   49,  118,   49,\n       49,   49,   49,   49,   49,   49,   94,   49,  121,   49,\n\n       93,  125,   49,  126,   49,   49,  125,   86,  126,   49,\n       85,   49,  104,  104,  104,   49,   49,   49,  129,  132,\n       49,   49,   75,   49,   49,   87,  133,   49,   49,   90,\n       49,   74,   49,   73,   69,   49,   65,  143,   88,   39,\n       51,   64,   91,   47,   51,   29,   29,   29,   29,   29,\n       29,   29,   29,   33,   33,   33,   33,   33,   33,   33,\n       33,   38,   38,   46,   39,  143,  143,   38,   49,  143,\n       49,   49,  143,   49,   49,   70,   70,  143,  143,   70,\n      105,  105,  143,  105,  105,  105,  105,    7,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  143,  143,  143,  143\n    } ;\n\nstatic lp_yyconst flex_int16_t lp_yy_chk[426] =\n    {   0,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    2,    3,    3,\n        4,    4,    3,  142,    4,    5,    5,    6,    6,    9,\n        9,    9,   14,   14,   15,    9,    2,    9,  141,   15,\n        2,   22,    2,   10,   10,   10,   23,    2,  131,   10,\n       16,   10,   16,   16,   22,   26,   22,   67,   67,   23,\n      131,   23,   25,   16,   23,  140,   27,  139,   26,   48,\n       26,   23,   24,   24,   24,   25,  138,   25,   24,   27,\n\n       24,   27,   48,   28,   26,  137,   58,   25,   40,   40,\n       86,   24,   58,   27,  135,   24,   28,   24,   28,   40,\n       68,   68,   24,   86,  130,   28,   36,   36,   36,   43,\n       43,   28,   36,  128,   36,   38,   38,   38,   66,   66,\n       43,   38,   44,   38,   44,   44,   45,   49,   45,   66,\n       52,   45,   45,   53,   59,   44,  124,   60,   61,  123,\n       49,   63,   49,   52,   87,   52,   53,   59,   53,   59,\n       60,   61,   60,   61,   63,   90,   63,   87,  120,   60,\n       53,   59,   71,   52,  119,  116,   72,  115,   90,   61,\n       62,   63,  112,   81,  111,   71,  109,   71,  106,   72,\n\n       78,   72,   97,   62,   79,   62,   81,   71,   81,   80,\n       62,   72,   82,   78,   95,   78,   62,   79,   78,   79,\n       83,   62,   80,   89,   80,   82,   79,   82,   84,   89,\n       94,   80,   93,   83,   89,   83,   92,   82,   91,   88,\n       84,   84,   92,   84,   85,   85,   85,   92,   98,   99,\n       83,   77,  100,  101,   98,   99,  100,   98,  100,   98,\n       99,  102,  114,  100,  114,  101,  103,  102,  114,   85,\n       76,  101,  102,  114,  103,  101,  101,  104,  104,  104,\n      103,  107,   75,  108,  113,  103,  107,  107,  108,  108,\n      113,  117,  107,  118,  108,  113,   74,  117,  113,  118,\n\n       73,  117,  117,  118,  118,  121,  117,   70,  118,  122,\n       65,  121,  136,  136,  136,  122,  121,  125,  122,  125,\n      122,  129,   57,  125,  126,  132,  126,  129,  125,  133,\n      126,   56,  129,   55,   50,  126,   39,  136,  132,   37,\n      132,   32,  133,   21,  133,  144,  144,  144,  144,  144,\n      144,  144,  144,  145,  145,  145,  145,  145,  145,  145,\n      145,  146,  146,   19,   12,    7,    0,  146,  147,    0,\n      147,  147,    0,  147,  147,  148,  148,    0,    0,  148,\n      149,  149,    0,  149,  149,  149,  149,  143,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  143,  143,  143,  143\n    } ;\n\n/* Table of booleans, true if rule could match eol. */\nstatic lp_yyconst flex_int32_t lp_yy_rule_can_match_eol[34] =\n    {   0,\n0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, \n    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,     };\n\n/* The intent behind this definition is that it'll catch\n * any uses of REJECT which flex missed.\n */\n#define REJECT reject_used_but_not_detected\n#define lp_yymore() lp_yymore_used_but_not_detected\n#define YY_MORE_ADJ 0\n#define YY_RESTORE_YY_MORE_OFFSET\n/*\n   made reentrant with help of\n   http://www.usualcoding.eu/post/2007/09/03/Building-a-reentrant-parser-in-C-with-Flex/Bison\n*/\n/*\n   Note that a minimum version of flex is needed to be able to compile this.\n   Older version don't know the reentrant code.\n   Version 2.5.4 is not enough. Probably at least v2.5.31 is needed. Tested with v2.5.35\n*/\n/*\n** We want the scanner to be reentrant, therefore generate no global variables.\n** That what the 'reentrant' option is for.\n** 'bison-bridge' is used to create a bison compatible scanner and share lp_yylval\n*/\n\n#define INITIAL 0\n#define COMMENT 1\n#define LINECOMMENT 2\n\n#ifndef YY_NO_UNISTD_H\n/* Special case for \"unistd.h\", since it is non-ANSI. We include it way\n * down here because we want the user's section 1 to have been scanned first.\n * The user has a chance to override it with an option.\n */\n#include <unistd.h>\n#endif\n\n#ifndef YY_EXTRA_TYPE\n#define YY_EXTRA_TYPE void *\n#endif\n\n/* Holds the entire state of the reentrant scanner. */\nstruct lp_yyguts_t\n    {\n\n    /* User-defined. Not touched by flex. */\n    YY_EXTRA_TYPE lp_yyextra_r;\n\n    /* The rest are the same as the globals declared in the non-reentrant scanner. */\n    FILE *lp_yyin_r, *lp_yyout_r;\n    size_t lp_yy_buffer_stack_top; /**< index of top of stack. */\n    size_t lp_yy_buffer_stack_max; /**< capacity of stack. */\n    YY_BUFFER_STATE * lp_yy_buffer_stack; /**< Stack as an array. */\n    char lp_yy_hold_char;\n    int lp_yy_n_chars;\n    int lp_yyleng_r;\n    char *lp_yy_c_buf_p;\n    int lp_yy_init;\n    int lp_yy_start;\n    int lp_yy_did_buffer_switch_on_eof;\n    int lp_yy_start_stack_ptr;\n    int lp_yy_start_stack_depth;\n    int *lp_yy_start_stack;\n    lp_yy_state_type lp_yy_last_accepting_state;\n    char* lp_yy_last_accepting_cpos;\n\n    int lp_yylineno_r;\n    int lp_yy_flex_debug_r;\n\n    char *lp_yytext_r;\n    int lp_yy_more_flag;\n    int lp_yy_more_len;\n\n    YYSTYPE * lp_yylval_r;\n\n    }; /* end struct lp_yyguts_t */\n\nstatic int lp_yy_init_globals (lp_yyscan_t lp_yyscanner );\n\n    /* This must go here because YYSTYPE and YYLTYPE are included\n     * from bison output in section 1.*/\n    #    define lp_yylval lp_yyg->lp_yylval_r\n    \nint lp_yylex_init (lp_yyscan_t* scanner);\n\nint lp_yylex_init_extra (YY_EXTRA_TYPE user_defined,lp_yyscan_t* scanner);\n\n/* Accessor methods to globals.\n   These are made visible to non-reentrant scanners for convenience. */\n\nint lp_yylex_destroy (lp_yyscan_t lp_yyscanner );\n\nint lp_yyget_debug (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_debug (int debug_flag ,lp_yyscan_t lp_yyscanner );\n\nYY_EXTRA_TYPE lp_yyget_extra (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_extra (YY_EXTRA_TYPE user_defined ,lp_yyscan_t lp_yyscanner );\n\nFILE *lp_yyget_in (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_in  (FILE * in_str ,lp_yyscan_t lp_yyscanner );\n\nFILE *lp_yyget_out (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_out  (FILE * out_str ,lp_yyscan_t lp_yyscanner );\n\nint lp_yyget_leng (lp_yyscan_t lp_yyscanner );\n\nchar *lp_yyget_text (lp_yyscan_t lp_yyscanner );\n\nint lp_yyget_lineno (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_lineno (int line_number ,lp_yyscan_t lp_yyscanner );\n\nYYSTYPE * lp_yyget_lval (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_lval (YYSTYPE * lp_yylval_param ,lp_yyscan_t lp_yyscanner );\n\n/* Macros after this point can all be overridden by user definitions in\n * section 1.\n */\n\n#ifndef YY_SKIP_YYWRAP\n#ifdef __cplusplus\nextern \"C\" int lp_yywrap (lp_yyscan_t lp_yyscanner );\n#else\nextern int lp_yywrap (lp_yyscan_t lp_yyscanner );\n#endif\n#endif\n\n    static void lp_yyunput (int c,char *buf_ptr  ,lp_yyscan_t lp_yyscanner);\n    \n#ifndef lp_yytext_ptr\nstatic void lp_yy_flex_strncpy (char *,lp_yyconst char *,int ,lp_yyscan_t lp_yyscanner);\n#endif\n\n#ifdef YY_NEED_STRLEN\nstatic int lp_yy_flex_strlen (lp_yyconst char * ,lp_yyscan_t lp_yyscanner);\n#endif\n\n#ifndef YY_NO_INPUT\n\n#ifdef __cplusplus\nstatic int lp_yyinput (lp_yyscan_t lp_yyscanner );\n#else\nstatic int input (lp_yyscan_t lp_yyscanner );\n#endif\n\n#endif\n\n/* Amount of stuff to slurp up with each read. */\n#ifndef YY_READ_BUF_SIZE\n#define YY_READ_BUF_SIZE 8192\n#endif\n\n/* Copy whatever the last rule matched to the standard output. */\n#ifndef ECHO\n/* This used to be an fputs(), but since the string might contain NUL's,\n * we now use fwrite().\n */\n#define ECHO fwrite( lp_yytext, lp_yyleng, 1, lp_yyout )\n#endif\n\n/* Gets input and stuffs it into \"buf\".  number of characters read, or YY_NULL,\n * is returned in \"result\".\n */\n#ifndef YY_INPUT\n#define YY_INPUT(buf,result,max_size) \\\n\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_is_interactive ) \\\n\t\t{ \\\n\t\tint c = '*'; \\\n\t\tint n; \\\n\t\tfor ( n = 0; n < max_size && \\\n\t\t\t     (c = getc( lp_yyin )) != EOF && c != '\\n'; ++n ) \\\n\t\t\tbuf[n] = (char) c; \\\n\t\tif ( c == '\\n' ) \\\n\t\t\tbuf[n++] = (char) c; \\\n\t\tif ( c == EOF && ferror( lp_yyin ) ) \\\n\t\t\tYY_FATAL_ERROR( \"input in flex scanner failed\" ); \\\n\t\tresult = n; \\\n\t\t} \\\n\telse \\\n\t\t{ \\\n\t\terrno=0; \\\n\t\twhile ( (result = fread(buf, 1, max_size, lp_yyin))==0 && ferror(lp_yyin)) \\\n\t\t\t{ \\\n\t\t\tif( errno != EINTR) \\\n\t\t\t\t{ \\\n\t\t\t\tYY_FATAL_ERROR( \"input in flex scanner failed\" ); \\\n\t\t\t\tbreak; \\\n\t\t\t\t} \\\n\t\t\terrno=0; \\\n\t\t\tclearerr(lp_yyin); \\\n\t\t\t} \\\n\t\t}\\\n\\\n\n#endif\n\n/* No semi-colon after return; correct usage is to write \"lp_yyterminate();\" -\n * we don't want an extra ';' after the \"return\" because that will cause\n * some compilers to complain about unreachable statements.\n */\n#ifndef lp_yyterminate\n#define lp_yyterminate() return YY_NULL\n#endif\n\n/* Number of entries by which start-condition stack grows. */\n#ifndef YY_START_STACK_INCR\n#define YY_START_STACK_INCR 25\n#endif\n\n/* Report a fatal error. */\n#ifndef YY_FATAL_ERROR\n#define YY_FATAL_ERROR(msg) lp_yy_fatal_error( msg , lp_yyscanner)\n#endif\n\n/* end tables serialization structures and prototypes */\n\n/* Default declaration of generated scanner - a define so the user can\n * easily add parameters.\n */\n#ifndef YY_DECL\n#define YY_DECL_IS_OURS 1\n\nextern int lp_yylex \\\n               (YYSTYPE * lp_yylval_param ,lp_yyscan_t lp_yyscanner);\n\n#define YY_DECL int lp_yylex \\\n               (YYSTYPE * lp_yylval_param , lp_yyscan_t lp_yyscanner)\n#endif /* !YY_DECL */\n\n/* Code executed at the beginning of each rule, after lp_yytext and lp_yyleng\n * have been set up.\n */\n#ifndef YY_USER_ACTION\n#define YY_USER_ACTION\n#endif\n\n/* Code executed at the end of each rule. */\n#ifndef YY_BREAK\n#define YY_BREAK break;\n#endif\n\n#define YY_RULE_SETUP \\\n\tif ( lp_yyleng > 0 ) \\\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol = \\\n\t\t\t\t(lp_yytext[lp_yyleng - 1] == '\\n'); \\\n\tYY_USER_ACTION\n\n/** The main scanner function which does all the work.\n */\nYY_DECL\n{\n\tregister lp_yy_state_type lp_yy_current_state;\n\tregister char *lp_yy_cp, *lp_yy_bp;\n\tregister int lp_yy_act;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n    lp_yylval = lp_yylval_param;\n\n\tif ( !lp_yyg->lp_yy_init )\n\t\t{\n\t\tlp_yyg->lp_yy_init = 1;\n\n#ifdef YY_USER_INIT\n\t\tYY_USER_INIT;\n#endif\n\n\t\tif ( ! lp_yyg->lp_yy_start )\n\t\t\tlp_yyg->lp_yy_start = 1;\t/* first start state */\n\n\t\tif ( ! lp_yyin )\n\t\t\tlp_yyin = stdin;\n\n\t\tif ( ! lp_yyout )\n\t\t\tlp_yyout = stdout;\n\n\t\tif ( ! YY_CURRENT_BUFFER ) {\n\t\t\tlp_yyensure_buffer_stack (lp_yyscanner);\n\t\t\tYY_CURRENT_BUFFER_LVALUE =\n\t\t\t\tlp_yy_create_buffer(lp_yyin,YY_BUF_SIZE ,lp_yyscanner);\n\t\t}\n\n\t\tlp_yy_load_buffer_state(lp_yyscanner );\n\t\t}\n\n\twhile ( 1 )\t\t/* loops until end-of-file is reached */\n\t\t{\n\t\tlp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\n\t\t/* Support of lp_yytext. */\n\t\t*lp_yy_cp = lp_yyg->lp_yy_hold_char;\n\n\t\t/* lp_yy_bp points to the position in lp_yy_ch_buf of the start of\n\t\t * the current run.\n\t\t */\n\t\tlp_yy_bp = lp_yy_cp;\n\n\t\tlp_yy_current_state = lp_yyg->lp_yy_start;\n\t\tlp_yy_current_state += YY_AT_BOL();\nlp_yy_match:\n\t\tdo\n\t\t\t{\n\t\t\tregister YY_CHAR lp_yy_c = lp_yy_ec[YY_SC_TO_UI(*lp_yy_cp)];\n\t\t\tif ( lp_yy_accept[lp_yy_current_state] )\n\t\t\t\t{\n\t\t\t\tlp_yyg->lp_yy_last_accepting_state = lp_yy_current_state;\n\t\t\t\tlp_yyg->lp_yy_last_accepting_cpos = lp_yy_cp;\n\t\t\t\t}\n\t\t\twhile ( lp_yy_chk[lp_yy_base[lp_yy_current_state] + lp_yy_c] != lp_yy_current_state )\n\t\t\t\t{\n\t\t\t\tlp_yy_current_state = (int) lp_yy_def[lp_yy_current_state];\n\t\t\t\tif ( lp_yy_current_state >= 144 )\n\t\t\t\t\tlp_yy_c = lp_yy_meta[(unsigned int) lp_yy_c];\n\t\t\t\t}\n\t\t\tlp_yy_current_state = lp_yy_nxt[lp_yy_base[lp_yy_current_state] + (unsigned int) lp_yy_c];\n\t\t\t++lp_yy_cp;\n\t\t\t}\n\t\twhile ( lp_yy_base[lp_yy_current_state] != 388 );\n\nlp_yy_find_action:\n\t\tlp_yy_act = lp_yy_accept[lp_yy_current_state];\n\t\tif ( lp_yy_act == 0 )\n\t\t\t{ /* have to back up */\n\t\t\tlp_yy_cp = lp_yyg->lp_yy_last_accepting_cpos;\n\t\t\tlp_yy_current_state = lp_yyg->lp_yy_last_accepting_state;\n\t\t\tlp_yy_act = lp_yy_accept[lp_yy_current_state];\n\t\t\t}\n\n\t\tYY_DO_BEFORE_ACTION;\n\n\t\tif ( lp_yy_act != YY_END_OF_BUFFER && lp_yy_rule_can_match_eol[lp_yy_act] )\n\t\t\t{\n\t\t\tint lp_yyl;\n\t\t\tfor ( lp_yyl = 0; lp_yyl < lp_yyleng; ++lp_yyl )\n\t\t\t\tif ( lp_yytext[lp_yyl] == '\\n' )\n\t\t\t\t\t   \n    do{ lp_yylineno++;\n        lp_yycolumn=0;\n    }while(0)\n;\n\t\t\t}\n\ndo_action:\t/* This label is used only to access EOF actions. */\n\n\t\tswitch ( lp_yy_act )\n\t{ /* beginning of action switch */\n\t\t\tcase 0: /* must back up */\n\t\t\t/* undo the effects of YY_DO_BEFORE_ACTION */\n\t\t\t*lp_yy_cp = lp_yyg->lp_yy_hold_char;\n\t\t\tlp_yy_cp = lp_yyg->lp_yy_last_accepting_cpos;\n\t\t\tlp_yy_current_state = lp_yyg->lp_yy_last_accepting_state;\n\t\t\tgoto lp_yy_find_action;\n\ncase 1:\nYY_RULE_SETUP\n{\n  BEGIN COMMENT;\n} /* begin skip comment */\n\tYY_BREAK\ncase 2:\nYY_RULE_SETUP\n{\n  BEGIN INITIAL;\n} /* end skip comment */\n\tYY_BREAK\ncase 3:\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 4:\n/* rule 4 can match eol */\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 5:\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 6:\nYY_RULE_SETUP\n{\n  BEGIN LINECOMMENT;\n} /* begin skip LINECOMMENT */\n\tYY_BREAK\ncase 7:\n/* rule 7 can match eol */\nYY_RULE_SETUP\n{\n  BEGIN INITIAL;\n} /* end skip LINECOMMENT */\n\tYY_BREAK\ncase 8:\nYY_RULE_SETUP\n{\n  BEGIN INITIAL;\n} /* end skip LINECOMMENT */\n\tYY_BREAK\ncase 9:\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 10:\n/* rule 10 can match eol */\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 11:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return(COMMA);\n}\n\tYY_BREAK\ncase 12:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return(MINIMISE);\n}\n\tYY_BREAK\ncase 13:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return(MAXIMISE);\n}\n\tYY_BREAK\ncase 14:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->f = atof((char *)lp_yytext);\n  return(INTCONS);\n} /* f contains the last float */\n\tYY_BREAK\ncase 15:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->f = atof((char *)lp_yytext);\n  return(CONS);\n} /* f contains the last float */\n\tYY_BREAK\ncase 16:\n/* rule 16 can match eol */\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  char *ptr, c;\n\n  pp->lineno = lp_yylineno;\n  pv->f = DEF_INFINITE;\n  pv->Sign = 0;\n  ptr = (char *)lp_yytext;\n  while (isspace(*ptr)) ptr++;\n  if(*ptr == '-')\n    pv->Sign = 1;\n  if(lp_yyleng > 0) {\n    c = lp_yytext[lp_yyleng - 1];\n    if(!isalnum(c))\n      unput(c);\n  }\n  return(INF);\n} /* f contains the last float */\n\tYY_BREAK\ncase 17:\n/* rule 17 can match eol */\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  int x;\n\n  pp->lineno = lp_yylineno;\n  pv->Sign = 0;\n  for(x = 0; x < lp_yyleng; x++)\n    if(lp_yytext[x] == '-' || lp_yytext[x] == '+')\n      pv->Sign = (pv->Sign == (lp_yytext[x] == '+'));\n  return (TOK_SIGN);\n  /* Sign is TRUE if the sign-string\n     represents a '-'. Otherwise Sign\n     is FALSE */\n}\n\tYY_BREAK\ncase 18:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_int_decl = 1;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_INT);\n}\n\tYY_BREAK\ncase 19:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_int_decl = 2;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_BIN);\n}\n\tYY_BREAK\ncase 20:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_sec_decl = TRUE;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_SEC);\n}\n\tYY_BREAK\ncase 21:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if(!pv->Within_sos_decl)\n    pv->SOStype0 = (short)atoi(((char *)lp_yytext) + 3);\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl))\n    pv->Within_sos_decl = TRUE;\n  return(SEC_SOS);\n}\n\tYY_BREAK\ncase 22:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)lp_yytext);\n  pv->Last_var[strlen(pv->Last_var) - 2] = 0;\n  return(SOSDESCR);\n}\n\tYY_BREAK\ncase 23:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_free_decl = TRUE;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_FREE);\n}\n\tYY_BREAK\ncase 24:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  char *ptr;\n\n  pp->lineno = lp_yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)lp_yytext);\n  ptr = pv->Last_var + strlen(pv->Last_var);\n  ptr[-1] = ' ';\n  while ((--ptr >= pv->Last_var) && (isspace(*ptr)))\n    *ptr = 0;\n  return(VARIABLECOLON);\n}\n\tYY_BREAK\ncase 25:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)lp_yytext);\n  return(VAR);\n}\n\tYY_BREAK\ncase 26:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return (COLON);\n}\n\tYY_BREAK\ncase 27:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return(AR_M_OP);\n}\n\tYY_BREAK\ncase 28:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->OP = *lp_yytext;\n  return(RE_OPEQ);\n}\n\tYY_BREAK\ncase 29:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->OP = *lp_yytext;\n  return(RE_OPLE);\n}\n\tYY_BREAK\ncase 30:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->OP = *lp_yytext;\n  return(RE_OPGE);\n}\n\tYY_BREAK\ncase 31:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->Within_int_decl = pv->Within_sec_decl = pv->Within_sos_decl = pv->Within_free_decl = FALSE;\n  check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, (int) pv->Within_sos_decl, (int) pv->Within_free_decl);\n  return(END_C);\n}\n\tYY_BREAK\ncase 32:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  report(NULL, CRITICAL, \"LEX ERROR : %s lineno %d\\n\", lp_yytext, lp_yylineno);\n  return(UNDEFINED);\n}\n\tYY_BREAK\ncase 33:\nYY_RULE_SETUP\nECHO;\n\tYY_BREAK\ncase YY_STATE_EOF(INITIAL):\ncase YY_STATE_EOF(COMMENT):\ncase YY_STATE_EOF(LINECOMMENT):\n\tlp_yyterminate();\n\n\tcase YY_END_OF_BUFFER:\n\t\t{\n\t\t/* Amount of text matched not including the EOB char. */\n\t\tint lp_yy_amount_of_matched_text = (int) (lp_yy_cp - lp_yyg->lp_yytext_ptr) - 1;\n\n\t\t/* Undo the effects of YY_DO_BEFORE_ACTION. */\n\t\t*lp_yy_cp = lp_yyg->lp_yy_hold_char;\n\t\tYY_RESTORE_YY_MORE_OFFSET\n\n\t\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_buffer_status == YY_BUFFER_NEW )\n\t\t\t{\n\t\t\t/* We're scanning a new file or input source.  It's\n\t\t\t * possible that this happened because the user\n\t\t\t * just pointed lp_yyin at a new source and called\n\t\t\t * lp_yylex().  If so, then we have to assure\n\t\t\t * consistency between YY_CURRENT_BUFFER and our\n\t\t\t * globals.  Here is the right place to do so, because\n\t\t\t * this is the first action (other than possibly a\n\t\t\t * back-up) that will match for the new input source.\n\t\t\t */\n\t\t\tlp_yyg->lp_yy_n_chars = YY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars;\n\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_input_file = lp_yyin;\n\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buffer_status = YY_BUFFER_NORMAL;\n\t\t\t}\n\n\t\t/* Note that here we test for lp_yy_c_buf_p \"<=\" to the position\n\t\t * of the first EOB in the buffer, since lp_yy_c_buf_p will\n\t\t * already have been incremented past the NUL character\n\t\t * (since all states make transitions on EOB to the\n\t\t * end-of-buffer state).  Contrast this with the test\n\t\t * in input().\n\t\t */\n\t\tif ( lp_yyg->lp_yy_c_buf_p <= &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars] )\n\t\t\t{ /* This was really a NUL. */\n\t\t\tlp_yy_state_type lp_yy_next_state;\n\n\t\t\tlp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yytext_ptr + lp_yy_amount_of_matched_text;\n\n\t\t\tlp_yy_current_state = lp_yy_get_previous_state( lp_yyscanner );\n\n\t\t\t/* Okay, we're now positioned to make the NUL\n\t\t\t * transition.  We couldn't have\n\t\t\t * lp_yy_get_previous_state() go ahead and do it\n\t\t\t * for us because it doesn't know how to deal\n\t\t\t * with the possibility of jamming (and we don't\n\t\t\t * want to build jamming into it because then it\n\t\t\t * will run more slowly).\n\t\t\t */\n\n\t\t\tlp_yy_next_state = lp_yy_try_NUL_trans( lp_yy_current_state , lp_yyscanner);\n\n\t\t\tlp_yy_bp = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ;\n\n\t\t\tif ( lp_yy_next_state )\n\t\t\t\t{\n\t\t\t\t/* Consume the NUL. */\n\t\t\t\tlp_yy_cp = ++lp_yyg->lp_yy_c_buf_p;\n\t\t\t\tlp_yy_current_state = lp_yy_next_state;\n\t\t\t\tgoto lp_yy_match;\n\t\t\t\t}\n\n\t\t\telse\n\t\t\t\t{\n\t\t\t\tlp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\t\t\t\tgoto lp_yy_find_action;\n\t\t\t\t}\n\t\t\t}\n\n\t\telse switch ( lp_yy_get_next_buffer( lp_yyscanner ) )\n\t\t\t{\n\t\t\tcase EOB_ACT_END_OF_FILE:\n\t\t\t\t{\n\t\t\t\tlp_yyg->lp_yy_did_buffer_switch_on_eof = 0;\n\n\t\t\t\tif ( lp_yywrap(lp_yyscanner ) )\n\t\t\t\t\t{\n\t\t\t\t\t/* Note: because we've taken care in\n\t\t\t\t\t * lp_yy_get_next_buffer() to have set up\n\t\t\t\t\t * lp_yytext, we can now set up\n\t\t\t\t\t * lp_yy_c_buf_p so that if some total\n\t\t\t\t\t * hoser (like flex itself) wants to\n\t\t\t\t\t * call the scanner after we return the\n\t\t\t\t\t * YY_NULL, it'll still work - another\n\t\t\t\t\t * YY_NULL will get returned.\n\t\t\t\t\t */\n\t\t\t\t\tlp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ;\n\n\t\t\t\t\tlp_yy_act = YY_STATE_EOF(YY_START);\n\t\t\t\t\tgoto do_action;\n\t\t\t\t\t}\n\n\t\t\t\telse\n\t\t\t\t\t{\n\t\t\t\t\tif ( ! lp_yyg->lp_yy_did_buffer_switch_on_eof )\n\t\t\t\t\t\tYY_NEW_FILE;\n\t\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t\t}\n\n\t\t\tcase EOB_ACT_CONTINUE_SCAN:\n\t\t\t\tlp_yyg->lp_yy_c_buf_p =\n\t\t\t\t\tlp_yyg->lp_yytext_ptr + lp_yy_amount_of_matched_text;\n\n\t\t\t\tlp_yy_current_state = lp_yy_get_previous_state( lp_yyscanner );\n\n\t\t\t\tlp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\t\t\t\tlp_yy_bp = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ;\n\t\t\t\tgoto lp_yy_match;\n\n\t\t\tcase EOB_ACT_LAST_MATCH:\n\t\t\t\tlp_yyg->lp_yy_c_buf_p =\n\t\t\t\t&YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars];\n\n\t\t\t\tlp_yy_current_state = lp_yy_get_previous_state( lp_yyscanner );\n\n\t\t\t\tlp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\t\t\t\tlp_yy_bp = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ;\n\t\t\t\tgoto lp_yy_find_action;\n\t\t\t}\n\t\tbreak;\n\t\t}\n\n\tdefault:\n\t\tYY_FATAL_ERROR(\n\t\t\t\"fatal flex scanner internal error--no action found\" );\n\t} /* end of action switch */\n\t\t} /* end of scanning one token */\n} /* end of lp_yylex */\n\n/* lp_yy_get_next_buffer - try to read in a new buffer\n *\n * Returns a code representing an action:\n *\tEOB_ACT_LAST_MATCH -\n *\tEOB_ACT_CONTINUE_SCAN - continue scanning from current position\n *\tEOB_ACT_END_OF_FILE - end of file\n */\nstatic int lp_yy_get_next_buffer (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tregister char *dest = YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf;\n\tregister char *source = lp_yyg->lp_yytext_ptr;\n\tregister int number_to_move, i;\n\tint ret_val;\n\n\tif ( lp_yyg->lp_yy_c_buf_p > &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars + 1] )\n\t\tYY_FATAL_ERROR(\n\t\t\"fatal flex scanner internal error--end of buffer missed\" );\n\n\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_fill_buffer == 0 )\n\t\t{ /* Don't try to fill the buffer, so this is an EOF. */\n\t\tif ( lp_yyg->lp_yy_c_buf_p - lp_yyg->lp_yytext_ptr - YY_MORE_ADJ == 1 )\n\t\t\t{\n\t\t\t/* We matched a single character, the EOB, so\n\t\t\t * treat this as a final EOF.\n\t\t\t */\n\t\t\treturn EOB_ACT_END_OF_FILE;\n\t\t\t}\n\n\t\telse\n\t\t\t{\n\t\t\t/* We matched some text prior to the EOB, first\n\t\t\t * process it.\n\t\t\t */\n\t\t\treturn EOB_ACT_LAST_MATCH;\n\t\t\t}\n\t\t}\n\n\t/* Try to read more data. */\n\n\t/* First move last chars to start of buffer. */\n\tnumber_to_move = (int) (lp_yyg->lp_yy_c_buf_p - lp_yyg->lp_yytext_ptr) - 1;\n\n\tfor ( i = 0; i < number_to_move; ++i )\n\t\t*(dest++) = *(source++);\n\n\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_buffer_status == YY_BUFFER_EOF_PENDING )\n\t\t/* don't do the read, it's not guaranteed to return an EOF,\n\t\t * just force an EOF\n\t\t */\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars = lp_yyg->lp_yy_n_chars = 0;\n\n\telse\n\t\t{\n\t\t\tint num_to_read =\n\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size - number_to_move - 1;\n\n\t\twhile ( num_to_read <= 0 )\n\t\t\t{ /* Not enough room in the buffer - grow it. */\n\n\t\t\t/* just a shorter name for the current buffer */\n\t\t\tYY_BUFFER_STATE b = YY_CURRENT_BUFFER;\n\n\t\t\tint lp_yy_c_buf_p_offset =\n\t\t\t\t(int) (lp_yyg->lp_yy_c_buf_p - b->lp_yy_ch_buf);\n\n\t\t\tif ( b->lp_yy_is_our_buffer )\n\t\t\t\t{\n\t\t\t\tint new_size = b->lp_yy_buf_size * 2;\n\n\t\t\t\tif ( new_size <= 0 )\n\t\t\t\t\tb->lp_yy_buf_size += b->lp_yy_buf_size / 8;\n\t\t\t\telse\n\t\t\t\t\tb->lp_yy_buf_size *= 2;\n\n\t\t\t\tb->lp_yy_ch_buf = (char *)\n\t\t\t\t\t/* Include room in for 2 EOB chars. */\n\t\t\t\t\tlp_yyrealloc((void *) b->lp_yy_ch_buf,b->lp_yy_buf_size + 2 ,lp_yyscanner );\n\t\t\t\t}\n\t\t\telse\n\t\t\t\t/* Can't grow it, we don't own it. */\n\t\t\t\tb->lp_yy_ch_buf = 0;\n\n\t\t\tif ( ! b->lp_yy_ch_buf )\n\t\t\t\tYY_FATAL_ERROR(\n\t\t\t\t\"fatal error - scanner input buffer overflow\" );\n\n\t\t\tlp_yyg->lp_yy_c_buf_p = &b->lp_yy_ch_buf[lp_yy_c_buf_p_offset];\n\n\t\t\tnum_to_read = YY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size -\n\t\t\t\t\t\tnumber_to_move - 1;\n\n\t\t\t}\n\n\t\tif ( num_to_read > YY_READ_BUF_SIZE )\n\t\t\tnum_to_read = YY_READ_BUF_SIZE;\n\n\t\t/* Read in more data. */\n\t\tYY_INPUT( (&YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[number_to_move]),\n\t\t\tlp_yyg->lp_yy_n_chars, (size_t) num_to_read );\n\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars = lp_yyg->lp_yy_n_chars;\n\t\t}\n\n\tif ( lp_yyg->lp_yy_n_chars == 0 )\n\t\t{\n\t\tif ( number_to_move == YY_MORE_ADJ )\n\t\t\t{\n\t\t\tret_val = EOB_ACT_END_OF_FILE;\n\t\t\tlp_yyrestart(lp_yyin  ,lp_yyscanner);\n\t\t\t}\n\n\t\telse\n\t\t\t{\n\t\t\tret_val = EOB_ACT_LAST_MATCH;\n\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buffer_status =\n\t\t\t\tYY_BUFFER_EOF_PENDING;\n\t\t\t}\n\t\t}\n\n\telse\n\t\tret_val = EOB_ACT_CONTINUE_SCAN;\n\n\tif ((lp_yy_size_t) (lp_yyg->lp_yy_n_chars + number_to_move) > YY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size) {\n\t\t/* Extend the array by 50%, plus the number we really need. */\n\t\tlp_yy_size_t new_size = lp_yyg->lp_yy_n_chars + number_to_move + (lp_yyg->lp_yy_n_chars >> 1);\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf = (char *) lp_yyrealloc((void *) YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf,new_size ,lp_yyscanner );\n\t\tif ( ! YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf )\n\t\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_get_next_buffer()\" );\n\t}\n\n\tlp_yyg->lp_yy_n_chars += number_to_move;\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars] = YY_END_OF_BUFFER_CHAR;\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars + 1] = YY_END_OF_BUFFER_CHAR;\n\n\tlp_yyg->lp_yytext_ptr = &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[0];\n\n\treturn ret_val;\n}\n\n/* lp_yy_get_previous_state - get the state just before the EOB char was reached */\n\n    static lp_yy_state_type lp_yy_get_previous_state (lp_yyscan_t lp_yyscanner)\n{\n\tregister lp_yy_state_type lp_yy_current_state;\n\tregister char *lp_yy_cp;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tlp_yy_current_state = lp_yyg->lp_yy_start;\n\tlp_yy_current_state += YY_AT_BOL();\n\n\tfor ( lp_yy_cp = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ; lp_yy_cp < lp_yyg->lp_yy_c_buf_p; ++lp_yy_cp )\n\t\t{\n\t\tregister YY_CHAR lp_yy_c = (*lp_yy_cp ? lp_yy_ec[YY_SC_TO_UI(*lp_yy_cp)] : 1);\n\t\tif ( lp_yy_accept[lp_yy_current_state] )\n\t\t\t{\n\t\t\tlp_yyg->lp_yy_last_accepting_state = lp_yy_current_state;\n\t\t\tlp_yyg->lp_yy_last_accepting_cpos = lp_yy_cp;\n\t\t\t}\n\t\twhile ( lp_yy_chk[lp_yy_base[lp_yy_current_state] + lp_yy_c] != lp_yy_current_state )\n\t\t\t{\n\t\t\tlp_yy_current_state = (int) lp_yy_def[lp_yy_current_state];\n\t\t\tif ( lp_yy_current_state >= 144 )\n\t\t\t\tlp_yy_c = lp_yy_meta[(unsigned int) lp_yy_c];\n\t\t\t}\n\t\tlp_yy_current_state = lp_yy_nxt[lp_yy_base[lp_yy_current_state] + (unsigned int) lp_yy_c];\n\t\t}\n\n\treturn lp_yy_current_state;\n}\n\n/* lp_yy_try_NUL_trans - try to make a transition on the NUL character\n *\n * synopsis\n *\tnext_state = lp_yy_try_NUL_trans( current_state );\n */\n    static lp_yy_state_type lp_yy_try_NUL_trans  (lp_yy_state_type lp_yy_current_state , lp_yyscan_t lp_yyscanner)\n{\n\tregister int lp_yy_is_jam;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner; /* This var may be unused depending upon options. */\n\tregister char *lp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\n\tregister YY_CHAR lp_yy_c = 1;\n\tif ( lp_yy_accept[lp_yy_current_state] )\n\t\t{\n\t\tlp_yyg->lp_yy_last_accepting_state = lp_yy_current_state;\n\t\tlp_yyg->lp_yy_last_accepting_cpos = lp_yy_cp;\n\t\t}\n\twhile ( lp_yy_chk[lp_yy_base[lp_yy_current_state] + lp_yy_c] != lp_yy_current_state )\n\t\t{\n\t\tlp_yy_current_state = (int) lp_yy_def[lp_yy_current_state];\n\t\tif ( lp_yy_current_state >= 144 )\n\t\t\tlp_yy_c = lp_yy_meta[(unsigned int) lp_yy_c];\n\t\t}\n\tlp_yy_current_state = lp_yy_nxt[lp_yy_base[lp_yy_current_state] + (unsigned int) lp_yy_c];\n\tlp_yy_is_jam = (lp_yy_current_state == 143);\n\n\treturn lp_yy_is_jam ? 0 : lp_yy_current_state;\n}\n\n    static void lp_yyunput (int c, register char * lp_yy_bp , lp_yyscan_t lp_yyscanner)\n{\n\tregister char *lp_yy_cp;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n    lp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\n\t/* undo effects of setting up lp_yytext */\n\t*lp_yy_cp = lp_yyg->lp_yy_hold_char;\n\n\tif ( lp_yy_cp < YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf + 2 )\n\t\t{ /* need to shift things up to make room */\n\t\t/* +2 for EOB chars. */\n\t\tregister int number_to_move = lp_yyg->lp_yy_n_chars + 2;\n\t\tregister char *dest = &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[\n\t\t\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size + 2];\n\t\tregister char *source =\n\t\t\t\t&YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[number_to_move];\n\n\t\twhile ( source > YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf )\n\t\t\t*--dest = *--source;\n\n\t\tlp_yy_cp += (int) (dest - source);\n\t\tlp_yy_bp += (int) (dest - source);\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars =\n\t\t\tlp_yyg->lp_yy_n_chars = YY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size;\n\n\t\tif ( lp_yy_cp < YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf + 2 )\n\t\t\tYY_FATAL_ERROR( \"flex scanner push-back overflow\" );\n\t\t}\n\n\t*--lp_yy_cp = (char) c;\n\n    if ( c == '\\n' ){\n        --lp_yylineno;\n    }\n\n\tlp_yyg->lp_yytext_ptr = lp_yy_bp;\n\tlp_yyg->lp_yy_hold_char = *lp_yy_cp;\n\tlp_yyg->lp_yy_c_buf_p = lp_yy_cp;\n}\n\n#ifndef YY_NO_INPUT\n#ifdef __cplusplus\n    static int lp_yyinput (lp_yyscan_t lp_yyscanner)\n#else\n    static int input  (lp_yyscan_t lp_yyscanner)\n#endif\n\n{\n\tint c;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\t*lp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yy_hold_char;\n\n\tif ( *lp_yyg->lp_yy_c_buf_p == YY_END_OF_BUFFER_CHAR )\n\t\t{\n\t\t/* lp_yy_c_buf_p now points to the character we want to return.\n\t\t * If this occurs *before* the EOB characters, then it's a\n\t\t * valid NUL; if not, then we've hit the end of the buffer.\n\t\t */\n\t\tif ( lp_yyg->lp_yy_c_buf_p < &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars] )\n\t\t\t/* This was really a NUL. */\n\t\t\t*lp_yyg->lp_yy_c_buf_p = '\\0';\n\n\t\telse\n\t\t\t{ /* need more input */\n\t\t\tint offset = lp_yyg->lp_yy_c_buf_p - lp_yyg->lp_yytext_ptr;\n\t\t\t++lp_yyg->lp_yy_c_buf_p;\n\n\t\t\tswitch ( lp_yy_get_next_buffer( lp_yyscanner ) )\n\t\t\t\t{\n\t\t\t\tcase EOB_ACT_LAST_MATCH:\n\t\t\t\t\t/* This happens because lp_yy_g_n_b()\n\t\t\t\t\t * sees that we've accumulated a\n\t\t\t\t\t * token and flags that we need to\n\t\t\t\t\t * try matching the token before\n\t\t\t\t\t * proceeding.  But for input(),\n\t\t\t\t\t * there's no matching to consider.\n\t\t\t\t\t * So convert the EOB_ACT_LAST_MATCH\n\t\t\t\t\t * to EOB_ACT_END_OF_FILE.\n\t\t\t\t\t */\n\n\t\t\t\t\t/* Reset buffer status. */\n\t\t\t\t\tlp_yyrestart(lp_yyin ,lp_yyscanner);\n\n\t\t\t\t\t/*FALLTHROUGH*/\n\n\t\t\t\tcase EOB_ACT_END_OF_FILE:\n\t\t\t\t\t{\n\t\t\t\t\tif ( lp_yywrap(lp_yyscanner ) )\n\t\t\t\t\t\treturn EOF;\n\n\t\t\t\t\tif ( ! lp_yyg->lp_yy_did_buffer_switch_on_eof )\n\t\t\t\t\t\tYY_NEW_FILE;\n#ifdef __cplusplus\n\t\t\t\t\treturn lp_yyinput(lp_yyscanner);\n#else\n\t\t\t\t\treturn input(lp_yyscanner);\n#endif\n\t\t\t\t\t}\n\n\t\t\t\tcase EOB_ACT_CONTINUE_SCAN:\n\t\t\t\t\tlp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yytext_ptr + offset;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\tc = *(unsigned char *) lp_yyg->lp_yy_c_buf_p;\t/* cast for 8-bit char's */\n\t*lp_yyg->lp_yy_c_buf_p = '\\0';\t/* preserve lp_yytext */\n\tlp_yyg->lp_yy_hold_char = *++lp_yyg->lp_yy_c_buf_p;\n\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol = (c == '\\n');\n\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol )\n\t\t   \n    do{ lp_yylineno++;\n        lp_yycolumn=0;\n    }while(0)\n;\n\n\treturn c;\n}\n#endif\t/* ifndef YY_NO_INPUT */\n\n/** Immediately switch to a different input stream.\n * @param input_file A readable stream.\n * @param lp_yyscanner The scanner object.\n * @note This function does not reset the start condition to @c INITIAL .\n */\n    void lp_yyrestart  (FILE * input_file , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tif ( ! YY_CURRENT_BUFFER ){\n        lp_yyensure_buffer_stack (lp_yyscanner);\n\t\tYY_CURRENT_BUFFER_LVALUE =\n            lp_yy_create_buffer(lp_yyin,YY_BUF_SIZE ,lp_yyscanner);\n\t}\n\n\tlp_yy_init_buffer(YY_CURRENT_BUFFER,input_file ,lp_yyscanner);\n\tlp_yy_load_buffer_state(lp_yyscanner );\n}\n\n/** Switch to a different input buffer.\n * @param new_buffer The new input buffer.\n * @param lp_yyscanner The scanner object.\n */\n    void lp_yy_switch_to_buffer  (YY_BUFFER_STATE  new_buffer , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\t/* TODO. We should be able to replace this entire function body\n\t * with\n\t *\t\tlp_yypop_buffer_state();\n\t *\t\tlp_yypush_buffer_state(new_buffer);\n     */\n\tlp_yyensure_buffer_stack (lp_yyscanner);\n\tif ( YY_CURRENT_BUFFER == new_buffer )\n\t\treturn;\n\n\tif ( YY_CURRENT_BUFFER )\n\t\t{\n\t\t/* Flush out information for old buffer. */\n\t\t*lp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yy_hold_char;\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buf_pos = lp_yyg->lp_yy_c_buf_p;\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars = lp_yyg->lp_yy_n_chars;\n\t\t}\n\n\tYY_CURRENT_BUFFER_LVALUE = new_buffer;\n\tlp_yy_load_buffer_state(lp_yyscanner );\n\n\t/* We don't actually know whether we did this switch during\n\t * EOF (lp_yywrap()) processing, but the only time this flag\n\t * is looked at is after lp_yywrap() is called, so it's safe\n\t * to go ahead and always set it.\n\t */\n\tlp_yyg->lp_yy_did_buffer_switch_on_eof = 1;\n}\n\nstatic void lp_yy_load_buffer_state  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tlp_yyg->lp_yy_n_chars = YY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars;\n\tlp_yyg->lp_yytext_ptr = lp_yyg->lp_yy_c_buf_p = YY_CURRENT_BUFFER_LVALUE->lp_yy_buf_pos;\n\tlp_yyin = YY_CURRENT_BUFFER_LVALUE->lp_yy_input_file;\n\tlp_yyg->lp_yy_hold_char = *lp_yyg->lp_yy_c_buf_p;\n}\n\n/** Allocate and initialize an input buffer state.\n * @param file A readable stream.\n * @param size The character buffer size in bytes. When in doubt, use @c YY_BUF_SIZE.\n * @param lp_yyscanner The scanner object.\n * @return the allocated buffer state.\n */\n    YY_BUFFER_STATE lp_yy_create_buffer  (FILE * file, int  size , lp_yyscan_t lp_yyscanner)\n{\n\tYY_BUFFER_STATE b;\n    \n\tb = (YY_BUFFER_STATE) lp_yyalloc(sizeof( struct lp_yy_buffer_state ) ,lp_yyscanner );\n\tif ( ! b )\n\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_create_buffer()\" );\n\n\tb->lp_yy_buf_size = size;\n\n\t/* lp_yy_ch_buf has to be 2 characters longer than the size given because\n\t * we need to put in 2 end-of-buffer characters.\n\t */\n\tb->lp_yy_ch_buf = (char *) lp_yyalloc(b->lp_yy_buf_size + 2 ,lp_yyscanner );\n\tif ( ! b->lp_yy_ch_buf )\n\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_create_buffer()\" );\n\n\tb->lp_yy_is_our_buffer = 1;\n\n\tlp_yy_init_buffer(b,file ,lp_yyscanner);\n\n\treturn b;\n}\n\n/** Destroy the buffer.\n * @param b a buffer created with lp_yy_create_buffer()\n * @param lp_yyscanner The scanner object.\n */\n    void lp_yy_delete_buffer (YY_BUFFER_STATE  b , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tif ( ! b )\n\t\treturn;\n\n\tif ( b == YY_CURRENT_BUFFER ) /* Not sure if we should pop here. */\n\t\tYY_CURRENT_BUFFER_LVALUE = (YY_BUFFER_STATE) 0;\n\n\tif ( b->lp_yy_is_our_buffer )\n\t\tlp_yyfree((void *) b->lp_yy_ch_buf ,lp_yyscanner );\n\n\tlp_yyfree((void *) b ,lp_yyscanner );\n}\n\n#ifndef __cplusplus\nextern int isatty (int );\n#endif /* __cplusplus */\n    \n/* Initializes or reinitializes a buffer.\n * This function is sometimes called more than once on the same buffer,\n * such as during a lp_yyrestart() or at EOF.\n */\n    static void lp_yy_init_buffer  (YY_BUFFER_STATE  b, FILE * file , lp_yyscan_t lp_yyscanner)\n\n{\n\tint oerrno = errno;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tlp_yy_flush_buffer(b ,lp_yyscanner);\n\n\tb->lp_yy_input_file = file;\n\tb->lp_yy_fill_buffer = 1;\n\n    /* If b is the current buffer, then lp_yy_init_buffer was _probably_\n     * called from lp_yyrestart() or through lp_yy_get_next_buffer.\n     * In that case, we don't want to reset the lineno or column.\n     */\n    if (b != YY_CURRENT_BUFFER){\n        b->lp_yy_bs_lineno = 1;\n        b->lp_yy_bs_column = 0;\n    }\n\n        b->lp_yy_is_interactive = file ? (isatty( fileno(file) ) > 0) : 0;\n    \n\terrno = oerrno;\n}\n\n/** Discard all buffered characters. On the next scan, YY_INPUT will be called.\n * @param b the buffer state to be flushed, usually @c YY_CURRENT_BUFFER.\n * @param lp_yyscanner The scanner object.\n */\n    void lp_yy_flush_buffer (YY_BUFFER_STATE  b , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tif ( ! b )\n\t\treturn;\n\n\tb->lp_yy_n_chars = 0;\n\n\t/* We always need two end-of-buffer characters.  The first causes\n\t * a transition to the end-of-buffer state.  The second causes\n\t * a jam in that state.\n\t */\n\tb->lp_yy_ch_buf[0] = YY_END_OF_BUFFER_CHAR;\n\tb->lp_yy_ch_buf[1] = YY_END_OF_BUFFER_CHAR;\n\n\tb->lp_yy_buf_pos = &b->lp_yy_ch_buf[0];\n\n\tb->lp_yy_at_bol = 1;\n\tb->lp_yy_buffer_status = YY_BUFFER_NEW;\n\n\tif ( b == YY_CURRENT_BUFFER )\n\t\tlp_yy_load_buffer_state(lp_yyscanner );\n}\n\n/** Pushes the new state onto the stack. The new state becomes\n *  the current state. This function will allocate the stack\n *  if necessary.\n *  @param new_buffer The new state.\n *  @param lp_yyscanner The scanner object.\n */\nvoid lp_yypush_buffer_state (YY_BUFFER_STATE new_buffer , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tif (new_buffer == NULL)\n\t\treturn;\n\n\tlp_yyensure_buffer_stack(lp_yyscanner);\n\n\t/* This block is copied from lp_yy_switch_to_buffer. */\n\tif ( YY_CURRENT_BUFFER )\n\t\t{\n\t\t/* Flush out information for old buffer. */\n\t\t*lp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yy_hold_char;\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buf_pos = lp_yyg->lp_yy_c_buf_p;\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars = lp_yyg->lp_yy_n_chars;\n\t\t}\n\n\t/* Only push if top exists. Otherwise, replace top. */\n\tif (YY_CURRENT_BUFFER)\n\t\tlp_yyg->lp_yy_buffer_stack_top++;\n\tYY_CURRENT_BUFFER_LVALUE = new_buffer;\n\n\t/* copied from lp_yy_switch_to_buffer. */\n\tlp_yy_load_buffer_state(lp_yyscanner );\n\tlp_yyg->lp_yy_did_buffer_switch_on_eof = 1;\n}\n\n/** Removes and deletes the top of the stack, if present.\n *  The next element becomes the new top.\n *  @param lp_yyscanner The scanner object.\n */\nvoid lp_yypop_buffer_state (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tif (!YY_CURRENT_BUFFER)\n\t\treturn;\n\n\tlp_yy_delete_buffer(YY_CURRENT_BUFFER ,lp_yyscanner);\n\tYY_CURRENT_BUFFER_LVALUE = NULL;\n\tif (lp_yyg->lp_yy_buffer_stack_top > 0)\n\t\t--lp_yyg->lp_yy_buffer_stack_top;\n\n\tif (YY_CURRENT_BUFFER) {\n\t\tlp_yy_load_buffer_state(lp_yyscanner );\n\t\tlp_yyg->lp_yy_did_buffer_switch_on_eof = 1;\n\t}\n}\n\n/* Allocates the stack if it does not exist.\n *  Guarantees space for at least one push.\n */\nstatic void lp_yyensure_buffer_stack (lp_yyscan_t lp_yyscanner)\n{\n\tint num_to_alloc;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tif (!lp_yyg->lp_yy_buffer_stack) {\n\n\t\t/* First allocation is just for 2 elements, since we don't know if this\n\t\t * scanner will even need a stack. We use 2 instead of 1 to avoid an\n\t\t * immediate realloc on the next call.\n         */\n\t\tnum_to_alloc = 1;\n\t\tlp_yyg->lp_yy_buffer_stack = (struct lp_yy_buffer_state**)lp_yyalloc\n\t\t\t\t\t\t\t\t(num_to_alloc * sizeof(struct lp_yy_buffer_state*)\n\t\t\t\t\t\t\t\t, lp_yyscanner);\n\t\tif ( ! lp_yyg->lp_yy_buffer_stack )\n\t\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yyensure_buffer_stack()\" );\n\t\t\t\t\t\t\t\t  \n\t\tmemset(lp_yyg->lp_yy_buffer_stack, 0, num_to_alloc * sizeof(struct lp_yy_buffer_state*));\n\t\t\t\t\n\t\tlp_yyg->lp_yy_buffer_stack_max = num_to_alloc;\n\t\tlp_yyg->lp_yy_buffer_stack_top = 0;\n\t\treturn;\n\t}\n\n\tif (lp_yyg->lp_yy_buffer_stack_top >= (lp_yyg->lp_yy_buffer_stack_max) - 1){\n\n\t\t/* Increase the buffer to prepare for a possible push. */\n\t\tint grow_size = 8 /* arbitrary grow size */;\n\n\t\tnum_to_alloc = lp_yyg->lp_yy_buffer_stack_max + grow_size;\n\t\tlp_yyg->lp_yy_buffer_stack = (struct lp_yy_buffer_state**)lp_yyrealloc\n\t\t\t\t\t\t\t\t(lp_yyg->lp_yy_buffer_stack,\n\t\t\t\t\t\t\t\tnum_to_alloc * sizeof(struct lp_yy_buffer_state*)\n\t\t\t\t\t\t\t\t, lp_yyscanner);\n\t\tif ( ! lp_yyg->lp_yy_buffer_stack )\n\t\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yyensure_buffer_stack()\" );\n\n\t\t/* zero only the new slots.*/\n\t\tmemset(lp_yyg->lp_yy_buffer_stack + lp_yyg->lp_yy_buffer_stack_max, 0, grow_size * sizeof(struct lp_yy_buffer_state*));\n\t\tlp_yyg->lp_yy_buffer_stack_max = num_to_alloc;\n\t}\n}\n\n/** Setup the input buffer state to scan directly from a user-specified character buffer.\n * @param base the character buffer\n * @param size the size in bytes of the character buffer\n * @param lp_yyscanner The scanner object.\n * @return the newly allocated buffer state object. \n */\nYY_BUFFER_STATE lp_yy_scan_buffer  (char * base, lp_yy_size_t  size , lp_yyscan_t lp_yyscanner)\n{\n\tYY_BUFFER_STATE b;\n    \n\tif ( size < 2 ||\n\t     base[size-2] != YY_END_OF_BUFFER_CHAR ||\n\t     base[size-1] != YY_END_OF_BUFFER_CHAR )\n\t\t/* They forgot to leave room for the EOB's. */\n\t\treturn 0;\n\n\tb = (YY_BUFFER_STATE) lp_yyalloc(sizeof( struct lp_yy_buffer_state ) ,lp_yyscanner );\n\tif ( ! b )\n\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_scan_buffer()\" );\n\n\tb->lp_yy_buf_size = size - 2;\t/* \"- 2\" to take care of EOB's */\n\tb->lp_yy_buf_pos = b->lp_yy_ch_buf = base;\n\tb->lp_yy_is_our_buffer = 0;\n\tb->lp_yy_input_file = 0;\n\tb->lp_yy_n_chars = b->lp_yy_buf_size;\n\tb->lp_yy_is_interactive = 0;\n\tb->lp_yy_at_bol = 1;\n\tb->lp_yy_fill_buffer = 0;\n\tb->lp_yy_buffer_status = YY_BUFFER_NEW;\n\n\tlp_yy_switch_to_buffer(b ,lp_yyscanner );\n\n\treturn b;\n}\n\n/** Setup the input buffer state to scan a string. The next call to lp_yylex() will\n * scan from a @e copy of @a str.\n * @param lp_yystr a NUL-terminated string to scan\n * @param lp_yyscanner The scanner object.\n * @return the newly allocated buffer state object.\n * @note If you want to scan bytes that may contain NUL values, then use\n *       lp_yy_scan_bytes() instead.\n */\nYY_BUFFER_STATE lp_yy_scan_string (lp_yyconst char * lp_yystr , lp_yyscan_t lp_yyscanner)\n{\n    \n\treturn lp_yy_scan_bytes(lp_yystr,strlen(lp_yystr) ,lp_yyscanner);\n}\n\n/** Setup the input buffer state to scan the given bytes. The next call to lp_yylex() will\n * scan from a @e copy of @a bytes.\n * @param bytes the byte buffer to scan\n * @param len the number of bytes in the buffer pointed to by @a bytes.\n * @param lp_yyscanner The scanner object.\n * @return the newly allocated buffer state object.\n */\nYY_BUFFER_STATE lp_yy_scan_bytes  (lp_yyconst char * lp_yybytes, int  _lp_yybytes_len , lp_yyscan_t lp_yyscanner)\n{\n\tYY_BUFFER_STATE b;\n\tchar *buf;\n\tlp_yy_size_t n;\n\tint i;\n    \n\t/* Get memory for full buffer, including space for trailing EOB's. */\n\tn = _lp_yybytes_len + 2;\n\tbuf = (char *) lp_yyalloc(n ,lp_yyscanner );\n\tif ( ! buf )\n\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_scan_bytes()\" );\n\n\tfor ( i = 0; i < _lp_yybytes_len; ++i )\n\t\tbuf[i] = lp_yybytes[i];\n\n\tbuf[_lp_yybytes_len] = buf[_lp_yybytes_len+1] = YY_END_OF_BUFFER_CHAR;\n\n\tb = lp_yy_scan_buffer(buf,n ,lp_yyscanner);\n\tif ( ! b )\n\t\tYY_FATAL_ERROR( \"bad buffer in lp_yy_scan_bytes()\" );\n\n\t/* It's okay to grow etc. this buffer, and we should throw it\n\t * away when we're done.\n\t */\n\tb->lp_yy_is_our_buffer = 1;\n\n\treturn b;\n}\n\n#ifndef YY_EXIT_FAILURE\n#define YY_EXIT_FAILURE 2\n#endif\n\nstatic void lp_yy_fatal_error (lp_yyconst char* msg , lp_yyscan_t lp_yyscanner)\n{\n    \t(void) fprintf( stderr, \"%s\\n\", msg );\n\texit( YY_EXIT_FAILURE );\n}\n\n/* Redefine lp_yyless() so it works in section 3 code. */\n\n#undef lp_yyless\n#define lp_yyless(n) \\\n\tdo \\\n\t\t{ \\\n\t\t/* Undo effects of setting up lp_yytext. */ \\\n        int lp_yyless_macro_arg = (n); \\\n        YY_LESS_LINENO(lp_yyless_macro_arg);\\\n\t\tlp_yytext[lp_yyleng] = lp_yyg->lp_yy_hold_char; \\\n\t\tlp_yyg->lp_yy_c_buf_p = lp_yytext + lp_yyless_macro_arg; \\\n\t\tlp_yyg->lp_yy_hold_char = *lp_yyg->lp_yy_c_buf_p; \\\n\t\t*lp_yyg->lp_yy_c_buf_p = '\\0'; \\\n\t\tlp_yyleng = lp_yyless_macro_arg; \\\n\t\t} \\\n\twhile ( 0 )\n\n/* Accessor  methods (get/set functions) to struct members. */\n\n/** Get the user-defined data for this scanner.\n * @param lp_yyscanner The scanner object.\n */\nYY_EXTRA_TYPE lp_yyget_extra  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yyextra;\n}\n\n/** Get the current line number.\n * @param lp_yyscanner The scanner object.\n */\nint lp_yyget_lineno  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    \n        if (! YY_CURRENT_BUFFER)\n            return 0;\n    \n    return lp_yylineno;\n}\n\n/** Get the current column number.\n * @param lp_yyscanner The scanner object.\n */\nint lp_yyget_column  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    \n        if (! YY_CURRENT_BUFFER)\n            return 0;\n    \n    return lp_yycolumn;\n}\n\n/** Get the input stream.\n * @param lp_yyscanner The scanner object.\n */\nFILE *lp_yyget_in  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yyin;\n}\n\n/** Get the output stream.\n * @param lp_yyscanner The scanner object.\n */\nFILE *lp_yyget_out  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yyout;\n}\n\n/** Get the length of the current token.\n * @param lp_yyscanner The scanner object.\n */\nint lp_yyget_leng  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yyleng;\n}\n\n/** Get the current token.\n * @param lp_yyscanner The scanner object.\n */\n\nchar *lp_yyget_text  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yytext;\n}\n\n/** Set the user-defined data. This data is never touched by the scanner.\n * @param user_defined The data to be associated with this scanner.\n * @param lp_yyscanner The scanner object.\n */\nvoid lp_yyset_extra (YY_EXTRA_TYPE  user_defined , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yyextra = user_defined ;\n}\n\n/** Set the current line number.\n * @param line_number\n * @param lp_yyscanner The scanner object.\n */\nvoid lp_yyset_lineno (int  line_number , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n        /* lineno is only valid if an input buffer exists. */\n        if (! YY_CURRENT_BUFFER )\n           lp_yy_fatal_error( \"lp_yyset_lineno called with no buffer\" , lp_yyscanner); \n    \n    lp_yylineno = line_number;\n}\n\n/** Set the current column.\n * @param line_number\n * @param lp_yyscanner The scanner object.\n */\nvoid lp_yyset_column (int  column_no , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n        /* column is only valid if an input buffer exists. */\n        if (! YY_CURRENT_BUFFER )\n           lp_yy_fatal_error( \"lp_yyset_column called with no buffer\" , lp_yyscanner); \n    \n    lp_yycolumn = column_no;\n}\n\n/** Set the input stream. This does not discard the current\n * input buffer.\n * @param in_str A readable stream.\n * @param lp_yyscanner The scanner object.\n * @see lp_yy_switch_to_buffer\n */\nvoid lp_yyset_in (FILE *  in_str , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yyin = in_str ;\n}\n\nvoid lp_yyset_out (FILE *  out_str , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yyout = out_str ;\n}\n\nint lp_yyget_debug  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yy_flex_debug;\n}\n\nvoid lp_yyset_debug (int  bdebug , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yy_flex_debug = bdebug ;\n}\n\n/* Accessor methods for lp_yylval and lp_yylloc */\n\nYYSTYPE * lp_yyget_lval  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yylval;\n}\n\nvoid lp_yyset_lval (YYSTYPE *  lp_yylval_param , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yylval = lp_yylval_param;\n}\n\n/* User-visible API */\n\n/* lp_yylex_init is special because it creates the scanner itself, so it is\n * the ONLY reentrant function that doesn't take the scanner as the last argument.\n * That's why we explicitly handle the declaration, instead of using our macros.\n */\n\nint lp_yylex_init(lp_yyscan_t* ptr_lp_yy_globals)\n\n{\n    if (ptr_lp_yy_globals == NULL){\n        errno = EINVAL;\n        return 1;\n    }\n\n    *ptr_lp_yy_globals = (lp_yyscan_t) lp_yyalloc ( sizeof( struct lp_yyguts_t ), NULL );\n\n    if (*ptr_lp_yy_globals == NULL){\n        errno = ENOMEM;\n        return 1;\n    }\n\n    /* By setting to 0xAA, we expose bugs in lp_yy_init_globals. Leave at 0x00 for releases. */\n    memset(*ptr_lp_yy_globals,0x00,sizeof(struct lp_yyguts_t));\n\n    return lp_yy_init_globals ( *ptr_lp_yy_globals );\n}\n\n/* lp_yylex_init_extra has the same functionality as lp_yylex_init, but follows the\n * convention of taking the scanner as the last argument. Note however, that\n * this is a *pointer* to a scanner, as it will be allocated by this call (and\n * is the reason, too, why this function also must handle its own declaration).\n * The user defined value in the first argument will be available to lp_yyalloc in\n * the lp_yyextra field.\n */\n\nint lp_yylex_init_extra(YY_EXTRA_TYPE lp_yy_user_defined,lp_yyscan_t* ptr_lp_yy_globals )\n\n{\n    struct lp_yyguts_t dummy_lp_yyguts;\n\n    lp_yyset_extra (lp_yy_user_defined, &dummy_lp_yyguts);\n\n    if (ptr_lp_yy_globals == NULL){\n        errno = EINVAL;\n        return 1;\n    }\n\t\n    *ptr_lp_yy_globals = (lp_yyscan_t) lp_yyalloc ( sizeof( struct lp_yyguts_t ), &dummy_lp_yyguts );\n\t\n    if (*ptr_lp_yy_globals == NULL){\n        errno = ENOMEM;\n        return 1;\n    }\n    \n    /* By setting to 0xAA, we expose bugs in\n    lp_yy_init_globals. Leave at 0x00 for releases. */\n    memset(*ptr_lp_yy_globals,0x00,sizeof(struct lp_yyguts_t));\n    \n    lp_yyset_extra (lp_yy_user_defined, *ptr_lp_yy_globals);\n    \n    return lp_yy_init_globals ( *ptr_lp_yy_globals );\n}\n\nstatic int lp_yy_init_globals (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    /* Initialization is the same as for the non-reentrant scanner.\n     * This function is called from lp_yylex_destroy(), so don't allocate here.\n     */\n\n    lp_yyg->lp_yy_buffer_stack = 0;\n    lp_yyg->lp_yy_buffer_stack_top = 0;\n    lp_yyg->lp_yy_buffer_stack_max = 0;\n    lp_yyg->lp_yy_c_buf_p = (char *) 0;\n    lp_yyg->lp_yy_init = 0;\n    lp_yyg->lp_yy_start = 0;\n\n    lp_yyg->lp_yy_start_stack_ptr = 0;\n    lp_yyg->lp_yy_start_stack_depth = 0;\n    lp_yyg->lp_yy_start_stack =  NULL;\n\n/* Defined in main.c */\n#ifdef YY_STDINIT\n    lp_yyin = stdin;\n    lp_yyout = stdout;\n#else\n    lp_yyin = (FILE *) 0;\n    lp_yyout = (FILE *) 0;\n#endif\n\n    /* For future reference: Set errno on error, since we are called by\n     * lp_yylex_init()\n     */\n    return 0;\n}\n\n/* lp_yylex_destroy is for both reentrant and non-reentrant scanners. */\nint lp_yylex_destroy  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n    /* Pop the buffer stack, destroying each element. */\n\twhile(YY_CURRENT_BUFFER){\n\t\tlp_yy_delete_buffer(YY_CURRENT_BUFFER ,lp_yyscanner );\n\t\tYY_CURRENT_BUFFER_LVALUE = NULL;\n\t\tlp_yypop_buffer_state(lp_yyscanner);\n\t}\n\n\t/* Destroy the stack itself. */\n\tlp_yyfree(lp_yyg->lp_yy_buffer_stack ,lp_yyscanner);\n\tlp_yyg->lp_yy_buffer_stack = NULL;\n\n    /* Destroy the start condition stack. */\n        lp_yyfree(lp_yyg->lp_yy_start_stack ,lp_yyscanner );\n        lp_yyg->lp_yy_start_stack = NULL;\n\n    /* Reset the globals. This is important in a non-reentrant scanner so the next time\n     * lp_yylex() is called, initialization will occur. */\n    lp_yy_init_globals( lp_yyscanner);\n\n    /* Destroy the main struct (reentrant only). */\n    lp_yyfree ( lp_yyscanner , lp_yyscanner );\n    lp_yyscanner = NULL;\n    return 0;\n}\n\n/*\n * Internal utility routines.\n */\n\n#ifndef lp_yytext_ptr\nstatic void lp_yy_flex_strncpy (char* s1, lp_yyconst char * s2, int n , lp_yyscan_t lp_yyscanner)\n{\n\tregister int i;\n\tfor ( i = 0; i < n; ++i )\n\t\ts1[i] = s2[i];\n}\n#endif\n\n#ifdef YY_NEED_STRLEN\nstatic int lp_yy_flex_strlen (lp_yyconst char * s , lp_yyscan_t lp_yyscanner)\n{\n\tregister int n;\n\tfor ( n = 0; s[n]; ++n )\n\t\t;\n\n\treturn n;\n}\n#endif\n\nvoid *lp_yyalloc (lp_yy_size_t  size , lp_yyscan_t lp_yyscanner)\n{\n\treturn (void *) malloc( size );\n}\n\nvoid *lp_yyrealloc  (void * ptr, lp_yy_size_t  size , lp_yyscan_t lp_yyscanner)\n{\n\t/* The cast to (char *) in the following accommodates both\n\t * implementations that use char* generic pointers, and those\n\t * that use void* generic pointers.  It works with the latter\n\t * because both ANSI C and C++ allow castless assignment from\n\t * any pointer type to void*, and deal with argument conversions\n\t * as though doing an assignment.\n\t */\n\treturn (void *) realloc( (char *) ptr, size );\n}\n\nvoid lp_yyfree (void * ptr , lp_yyscan_t lp_yyscanner)\n{\n\tfree( (char *) ptr );\t/* see lp_yyrealloc() for (char *) cast */\n}\n\n#define YYTABLES_NAME \"lp_yytables\"\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_scale.h",
    "content": "#ifndef HEADER_lp_scale\n#define HEADER_lp_scale\n\n#include \"lp_types.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\nSTATIC MYBOOL scale_updatecolumns(lprec *lp, REAL *scalechange, MYBOOL updateonly);\nSTATIC MYBOOL scale_updaterows(lprec *lp, REAL *scalechange, MYBOOL updateonly);\nSTATIC MYBOOL scale_rows(lprec *lp, REAL *scaledelta);\nSTATIC MYBOOL scale_columns(lprec *lp, REAL *scaledelta);\nSTATIC void unscale_columns(lprec *lp);\nSTATIC REAL scale(lprec *lp, REAL *scaledelta);\nSTATIC REAL scaled_mat(lprec *lp, REAL value, int rownr, int colnr);\nSTATIC REAL unscaled_mat(lprec *lp, REAL value, int rownr, int colnr);\nSTATIC REAL scaled_value(lprec *lp, REAL value, int index);\nSTATIC REAL unscaled_value(lprec *lp, REAL value, int index);\nSTATIC MYBOOL scaleCR(lprec *lp, REAL *scaledelta);\nSTATIC MYBOOL finalize_scaling(lprec *lp, REAL *scaledelta);\nSTATIC REAL auto_scale(lprec *lp);\nvoid undoscale(lprec *lp);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_scale */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_simplex.h",
    "content": "#ifndef HEADER_lp_simplex\n#define HEADER_lp_simplex\n\n#include \"lp_types.h\"\n\n#define ForceDualSimplexInBB               /* Force use/switch of dual simplex in B&B */\n#define AssumeHighAccuracyInBB    /* No iteration of simplex solves at infeasibility */\n/*#define UseLongStepPruning*/\n/*#define UseLongStepDualPhase1*/\n#define primal_UseRejectionList\n#define dual_UseRejectionList\n#define dual_RemoveBasicFixedVars\n/*#define dual_Phase1PriceEqualities */   /* Force elimination of equality slacks */\n#define AcceptMarginalAccuracy\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\nSTATIC int primloop(lprec *lp, MYBOOL primalfeasible, REAL primaloffset);\nSTATIC int dualloop(lprec *lp, MYBOOL dualfeasible, int dualinfeasibles[], REAL dualoffset);\nSTATIC int spx_run(lprec *lp, MYBOOL validInvB);\nSTATIC int spx_solve(lprec *lp);\nSTATIC int lag_solve(lprec *lp, REAL start_bound, int num_iter);\nSTATIC int heuristics(lprec *lp, int mode);\nSTATIC int lin_solve(lprec *lp);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_simplex */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_solveDLL.h",
    "content": "// stdafx.h : include file for standard system include files,\n//  or project specific include files that are used frequently, but\n//      are changed infrequently\n//\n\n#if !defined(AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_)\n#define AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_\n\n#if _MSC_VER > 1000\n#pragma once\n#endif // _MSC_VER > 1000\n\n\n// Insert your headers here\n#define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers\n\n#include <windows.h>\n\n// TODO: reference additional headers your program requires here\n\n//{{AFX_INSERT_LOCATION}}\n// Microsoft Visual C++ will insert additional declarations immediately before the previous line.\n\n#endif // !defined(AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_)\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_types.h",
    "content": "#ifndef HEADER_lp_types\n#define HEADER_lp_types\n\n#ifdef WIN32\n  #include <windows.h>\n#endif\n\n/* Define data types                                                         */\n/* ------------------------------------------------------------------------- */\n#ifndef LLONG\n  #if defined __BORLANDC__\n    #define LLONG __int64\n  #elif !defined _MSC_VER || _MSC_VER >= 1310\n    #define LLONG long long\n  #else\n    #define LLONG __int64\n  #endif\n#endif\n\n#ifndef COUNTER\n  #define COUNTER LLONG\n#endif\n\n#ifndef REAL\n  #define REAL    double\n#endif\n\n#ifndef REALXP\n  #if 1\n    #define REALXP long double  /* Set local accumulation variable as long double */\n  #else\n    #define REALXP REAL          /* Set local accumulation as default precision */\n  #endif\n#endif\n\n#ifndef LREAL\n  #if 0\n    #define LREAL long double   /* Set global solution update variable as long double */\n  #else\n    #define LREAL REAL           /* Set global solution update variable as default precision */\n  #endif\n#endif\n\n#define RESULTVALUEMASK \"%18.12g\" /* Set fixed-format real-valued output precision;\n                                  suggested width: ABS(exponent of DEF_EPSVALUE)+6. */\n#define INDEXVALUEMASK  \"%8d\"     /* Set fixed-format integer-valued output width */\n\n#ifndef DEF_STRBUFSIZE\n  #define DEF_STRBUFSIZE   512\n#endif\n#ifndef MAXINT32\n  #define MAXINT32  2147483647\n#endif\n#ifndef MAXUINT32\n  #define MAXUINT32 4294967295\n#endif\n\n#ifndef MAXINT64\n  #if defined _LONGLONG || defined __LONG_LONG_MAX__ || defined LLONG_MAX\n    #define MAXINT64   9223372036854775807ll\n  #else\n    #define MAXINT64   9223372036854775807l\n  #endif\n#endif\n#ifndef MAXUINT64\n  #if defined _LONGLONG || defined __LONG_LONG_MAX__ || defined LLONG_MAX\n    #define MAXUINT64 18446744073709551615ll\n  #else\n    #define MAXUINT64 18446744073709551615l\n  #endif\n#endif\n\n#ifndef CHAR_BIT\n  #define CHAR_BIT  8\n#endif\n#ifndef MYBOOL\n  #define MYBOOL  unsigned char    /* Conserve memory, could be unsigned int */\n#endif\n\n\n/* Constants                                                                 */\n/* ------------------------------------------------------------------------- */\n#ifndef NULL\n  #define NULL                   0\n#endif\n\n/* Byte-sized Booleans and extended options */\n#define FALSE                    0\n#define TRUE                     1\n#define AUTOMATIC                2\n#define DYNAMIC                  4\n\n/* Sorting and comparison constants */\n#define COMP_PREFERCANDIDATE     1\n#define COMP_PREFERNONE          0\n#define COMP_PREFERINCUMBENT    -1\n\n/* Library load status values */\n#define LIB_LOADED               0\n#define LIB_NOTFOUND             1\n#define LIB_NOINFO               2\n#define LIB_NOFUNCTION           3\n#define LIB_VERINVALID           4\n#define LIB_STR_LOADED           \"Successfully loaded\"\n#define LIB_STR_NOTFOUND         \"File not found\"\n#define LIB_STR_NOINFO           \"No version data\"\n#define LIB_STR_NOFUNCTION       \"Missing function header\"\n#define LIB_STR_VERINVALID       \"Incompatible version\"\n#define LIB_STR_MAXLEN           23\n\n\n/* Compiler/target settings                                                  */\n/* ------------------------------------------------------------------------- */\n#if (defined _WIN32) || (defined WIN32) || (defined _WIN64) || (defined WIN64)\n# define __WINAPI WINAPI\n#else\n# define __WINAPI\n#endif\n\n#if (defined _WIN32) || (defined WIN32) || (defined _WIN64) || (defined WIN64)\n# define __VACALL __cdecl\n#else\n# define __VACALL\n#endif\n\n#ifndef __BORLANDC__\n\n  #ifdef _USRDLL\n\n    #if 1\n      #define __EXPORT_TYPE __declspec(dllexport)\n    #else\n     /* Set up for the Microsoft compiler */\n      #ifdef LP_SOLVE_EXPORTS\n        #define __EXPORT_TYPE __declspec(dllexport)\n      #else\n        #define __EXPORT_TYPE __declspec(dllimport)\n      #endif\n    #endif\n\n  #else\n\n    #define __EXPORT_TYPE\n\n  #endif\n\n  #ifdef __cplusplus\n    #define __EXTERN_C extern \"C\"\n  #else\n    #define __EXTERN_C\n  #endif\n\n#else  /* Otherwise set up for the Borland compiler */\n\n  #ifdef __DLL__\n\n    #define _USRDLL\n    #define __EXTERN_C extern \"C\"\n\n    #ifdef __READING_THE_DLL\n      #define __EXPORT_TYPE __import\n    #else\n      #define __EXPORT_TYPE __export\n    #endif\n\n  #else\n\n    #define __EXPORT_TYPE\n    #define __EXTERN_C extern \"C\"\n\n  #endif\n\n#endif\n\n\n#if 0\n  #define STATIC static\n#else\n  #define STATIC\n#endif\n\n#if !defined INLINE\n  #if defined __cplusplus\n    #define INLINE inline\n  #elif (defined _WIN32) || (defined WIN32) || (defined _WIN64) || (defined WIN64)\n    #define INLINE __inline\n  #else\n    #define INLINE static\n  #endif\n#endif\n\n/* Function macros                                                           */\n/* ------------------------------------------------------------------------- */\n#define my_limitrange(x, lo, hi) ((x) < (lo) ? (lo) : ((x) > (hi) ? (hi) : (x)))\n#ifndef my_mod\n  #define my_mod(n, m)          ((n) % (m))\n#endif\n#define my_if(t, x, y)          ((t) ? (x) : (y))\n#define my_sign(x)              ((x) < 0 ? -1 : 1)\n#if 1\n  #define my_chsign(t, x)       ( ((t) && ((x) != 0)) ? -(x) : (x))\n#else\n  #define my_chsign(t, x)       ( (2*((t) == 0) - 1) * (x) )  /* \"Pipelined\", but problem with \"negative zero\" and possible problems on AIX  */\n#endif\n#define my_flipsign(x)          ( fabs((REAL) (x)) == 0 ? 0 : -(x) )\n#define my_roundzero(val, eps)  if (fabs((REAL) (val)) < eps) val = 0\n#define my_avoidtiny(val, eps)  (fabs((REAL) (val)) < eps ? 0 : val)\n\n#if 1\n  #define my_infinite(lp, val)  ( (MYBOOL) (fabs(val) >= lp->infinite) )\n#else\n  #define my_infinite(lp, val)  is_infinite(lp, val)\n#endif\n#define my_inflimit(lp, val)    ( my_infinite(lp, val) ? lp->infinite * my_sign(val) : (val) )\n#if 0\n  #define my_precision(val, eps) ((fabs((REAL) (val))) < (eps) ? 0 : (val))\n#else\n  #define my_precision(val, eps) restoreINT(val, eps)\n#endif\n#define my_reldiff(x, y)       (((x) - (y)) / (1.0 + fabs((REAL) (y))))\n#define my_boundstr(x)         (fabs(x) < lp->infinite ? sprintf(\"%g\",x) : ((x) < 0 ? \"-Inf\" : \"Inf\") )\n#ifndef my_boolstr\n  #define my_boolstr(x)          (!(x) ? \"FALSE\" : \"TRUE\")\n#endif\n#define my_basisstr(isbasic)     ((isbasic) ? \"BASIC\" : \"NON-BASIC\")\n#define my_simplexstr(isdual)    ((isdual) ? \"DUAL\" : \"PRIMAL\")\n#define my_plural_std(count)     (count == 1 ? \"\" : \"s\")\n#define my_plural_y(count)       (count == 1 ? \"y\" : \"ies\")\n#define my_lowbound(x)           ((FULLYBOUNDEDSIMPLEX) ? (x) : 0)\n\n\n/* Bound macros usable for both the standard and fully bounded simplex       */\n/* ------------------------------------------------------------------------- */\n/*\n#define my_lowbo(lp, varnr)      ( lp->isfullybounded ? lp->lowbo[varnr] : 0.0 )\n#define my_upbo(lp, varnr)       ( lp->isfullybounded ? lp->upbo[varnr]  : lp->lowbo[varnr] + lp->upbo[varnr] )\n#define my_rangebo(lp, varnr)    ( lp->isfullybounded ? lp->upbo[varnr] - lp->lowbo[varnr] : lp->upbo[varnr] )\n*/\n#define my_lowbo(lp, varnr)      ( 0.0 )\n#define my_upbo(lp, varnr)       ( lp->lowbo[varnr] + lp->upbo[varnr] )\n#define my_rangebo(lp, varnr)    ( lp->upbo[varnr] )\n\n#define my_unbounded(lp, varnr)  ((lp->upbo[varnr] >= lp->infinite) && (lp->lowbo[varnr] <= -lp->infinite))\n#define my_bounded(lp, varnr)    ((lp->upbo[varnr] < lp->infinite) && (lp->lowbo[varnr] > -lp->infinite))\n\n/* Forward declarations                                                      */\n/* ------------------------------------------------------------------------- */\ntypedef struct _lprec     lprec;\ntypedef struct _INVrec    INVrec;\nunion  QSORTrec;\n\n#ifndef UNIONTYPE\n  #ifdef __cplusplus\n    #define UNIONTYPE\n  #else\n    #define UNIONTYPE union\n  #endif\n#endif\n\n/* B4 factorization optimization data */\ntypedef struct _B4rec\n{\n  int  *B4_var;  /* Position of basic columns in the B4 basis */\n  int  *var_B4;  /* Variable in the B4 basis */\n  int  *B4_row;  /* B4 position of the i'th row */\n  int  *row_B4;  /* Original position of the i'th row */\n  REAL *wcol;\n  int  *nzwcol;\n} B4rec;\n\n#define OBJ_STEPS   5\ntypedef struct _OBJmonrec {\n  lprec  *lp;\n  int    oldpivstrategy,\n         oldpivrule, pivrule, ruleswitches,\n         limitstall[2], limitruleswitches,\n         idxstep[OBJ_STEPS], countstep, startstep, currentstep,\n         Rcycle, Ccycle, Ncycle, Mcycle, Icount;\n  REAL   thisobj, prevobj,\n         objstep[OBJ_STEPS],\n         thisinfeas, previnfeas,\n         epsvalue;\n  char   spxfunc[10];\n  MYBOOL pivdynamic;\n  MYBOOL isdual;\n  MYBOOL active;\n} OBJmonrec;\n\ntypedef struct _edgerec\n{\n  REAL      *edgeVector;\n} edgerec;\n\ntypedef struct _pricerec\n{\n  REAL   theta;\n  REAL   pivot;\n  REAL   epspivot;\n  int    varno;\n  lprec  *lp;\n  MYBOOL isdual;\n} pricerec;\ntypedef struct _multirec\n{\n  lprec    *lp;\n  int      size;                  /* The maximum number of multiply priced rows/columns */\n  int      used;                  /* The current / active number of multiply priced rows/columns */\n  int      limit;                 /* The active/used count at which a full update is triggered */\n  pricerec *items;                /* Array of best multiply priced rows/columns */\n  int      *freeList;             /* The indeces of available positions in \"items\" */\n  UNIONTYPE QSORTrec *sortedList; /* List of pointers to \"pricerec\" items in sorted order */\n  REAL     *stepList;             /* Working array (values in sortedList order) */\n  REAL     *valueList;            /* Working array (values in sortedList order) */\n  int      *indexSet;             /* The final exported index list of pivot variables */\n  int      active;                /* Index of currently active multiply priced row/column */\n  int      retries;\n  REAL     step_base;\n  REAL     step_last;\n  REAL     obj_base;\n  REAL     obj_last;\n  REAL     epszero;\n  REAL     maxpivot;\n  REAL     maxbound;\n  MYBOOL   sorted;\n  MYBOOL   truncinf;\n  MYBOOL   objcheck;\n  MYBOOL   dirty;\n} multirec;\n\n#endif /* HEADER_lp_types */\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_utils.h",
    "content": "#ifndef HEADER_lp_utils\n#define HEADER_lp_utils\n\n#ifdef FORTIFY\n\n#include \"lp_fortify.h\"\n\n#define allocCHAR allocCHAR_FORTIFY\n#define allocMYBOOL allocMYBOOL_FORTIFY\n#define allocINT allocINT_FORTIFY\n#define allocREAL allocREAL_FORTIFY\n#define allocLREAL allocLREAL_FORTIFY\n\n#endif\n\n#include \"lp_types.h\"\n\n/* Temporary data storage arrays */\ntypedef struct _workarraysrec\n{\n  lprec     *lp;\n  int       size;\n  int       count;\n  char      **vectorarray;\n  int       *vectorsize;\n} workarraysrec;\n\ntypedef struct _LLrec\n{\n  int       size;               /* The allocated list size */\n  int       count;              /* The current entry count */\n  int       firstitem;\n  int       lastitem;\n  int       *map;               /* The list of forward and backward-mapped entries */\n} LLrec;\n\ntypedef struct _PVrec\n{\n  int       count;              /* The allocated list item count */\n  int       *startpos;          /* Starting index of the current value */\n  REAL      *value;             /* The list of forward and backward-mapped entries */\n  struct   _PVrec *parent;     /* The parent record in a pushed chain */\n} PVrec;\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\nSTATIC MYBOOL allocCHAR(lprec *lp, char **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocMYBOOL(lprec *lp, MYBOOL **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocINT(lprec *lp, int **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocREAL(lprec *lp, REAL **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocLREAL(lprec *lp, LREAL **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocFREE(lprec *lp, void **ptr);\nREAL *cloneREAL(lprec *lp, REAL *origlist, int size);\nMYBOOL *cloneMYBOOL(lprec *lp, MYBOOL *origlist, int size);\nint *cloneINT(lprec *lp, int *origlist, int size);\n\nint comp_bits(MYBOOL *bitarray1, MYBOOL *bitarray2, int items);\n\nSTATIC workarraysrec *mempool_create(lprec *lp);\nSTATIC char *mempool_obtainVector(workarraysrec *mempool, int count, int unitsize);\nSTATIC MYBOOL mempool_releaseVector(workarraysrec *mempool, char *memvector, MYBOOL forcefree);\nSTATIC MYBOOL mempool_free(workarraysrec **mempool);\n\nSTATIC void roundVector(LREAL *myvector, int endpos, LREAL roundzero);\nSTATIC REAL normalizeVector(REAL *myvector, int endpos);\n\nSTATIC void swapINT(int *item1, int *item2);\nSTATIC void swapREAL(REAL *item1, REAL *item2);\nSTATIC void swapPTR(void **item1, void **item2);\nSTATIC REAL restoreINT(REAL valREAL, REAL epsilon);\nSTATIC REAL roundToPrecision(REAL value, REAL precision);\n\nSTATIC int searchFor(int target, int *attributes, int size, int offset, MYBOOL absolute);\n\nSTATIC MYBOOL isINT(lprec *lp, REAL value);\nSTATIC MYBOOL isOrigFixed(lprec *lp, int varno);\nSTATIC void chsign_bounds(REAL *lobound, REAL *upbound);\nSTATIC REAL rand_uniform(lprec *lp, REAL range);\n\n/* Doubly linked list routines */\nSTATIC int createLink(int size, LLrec **linkmap, MYBOOL *usedpos);\nSTATIC MYBOOL freeLink(LLrec **linkmap);\nSTATIC int sizeLink(LLrec *linkmap);\nSTATIC MYBOOL isActiveLink(LLrec *linkmap, int itemnr);\nSTATIC int countActiveLink(LLrec *linkmap);\nSTATIC int countInactiveLink(LLrec *linkmap);\nSTATIC int firstActiveLink(LLrec *linkmap);\nSTATIC int lastActiveLink(LLrec *linkmap);\nSTATIC MYBOOL appendLink(LLrec *linkmap, int newitem);\nSTATIC MYBOOL insertLink(LLrec *linkmap, int afteritem, int newitem);\nSTATIC MYBOOL setLink(LLrec *linkmap, int newitem);\nSTATIC MYBOOL fillLink(LLrec *linkmap);\nSTATIC int nextActiveLink(LLrec *linkmap, int backitemnr);\nSTATIC int prevActiveLink(LLrec *linkmap, int forwitemnr);\nSTATIC int firstInactiveLink(LLrec *linkmap);\nSTATIC int lastInactiveLink(LLrec *linkmap);\nSTATIC int nextInactiveLink(LLrec *linkmap, int backitemnr);\nSTATIC int prevInactiveLink(LLrec *linkmap, int forwitemnr);\nSTATIC int removeLink(LLrec *linkmap, int itemnr);\nSTATIC LLrec *cloneLink(LLrec *sourcemap, int newsize, MYBOOL freesource);\nSTATIC int compareLink(LLrec *linkmap1, LLrec *linkmap2);\nSTATIC MYBOOL verifyLink(LLrec *linkmap, int itemnr, MYBOOL doappend);\n\n/* Packed vector routines */\nSTATIC PVrec  *createPackedVector(int size, REAL *values, int *workvector);\nSTATIC void   pushPackedVector(PVrec *PV, PVrec *parent);\nSTATIC MYBOOL unpackPackedVector(PVrec *PV, REAL **target);\nSTATIC REAL   getvaluePackedVector(PVrec *PV, int index);\nSTATIC PVrec  *popPackedVector(PVrec *PV);\nSTATIC MYBOOL freePackedVector(PVrec **PV);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_utils */\n\n#ifdef FORTIFY\n\n#if defined CODE_lp_utils && !defined CODE_lp_utils_\nint _Fortify_ret;\n#else\nextern int _Fortify_ret;\n#endif\n\n#ifdef CODE_lp_utils\n#define CODE_lp_utils_\n#else\n# undef allocCHAR\n# undef allocMYBOOL\n# undef allocINT\n# undef allocREAL\n# undef allocLREAL\n# define allocCHAR(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocCHAR_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n# define allocMYBOOL(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocMYBOOL_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n# define allocINT(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocINT_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n# define allocREAL(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocREAL_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n# define allocLREAL(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocLREAL_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n#endif\n\n#endif\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lp_wlp.h",
    "content": "#ifndef HEADER_lp_lp\n#define HEADER_lp_lp\n\n#include \"lp_types.h\"\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\nMYBOOL LP_writefile(lprec *lp, char *filename);\nMYBOOL LP_writehandle(lprec *lp, FILE *output);\n\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_lp */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lpkit.h",
    "content": "#include \"lp_lib.h\"\n#include \"lp_report.h\"\n\n#define MALLOC(ptr, nr, type)\\\n  ((((nr) == 0) || ((ptr = (type *) malloc((size_t)((nr) * sizeof(*ptr)))) == NULL)) ? \\\n   report(NULL, CRITICAL, \"malloc of %d bytes failed on line %d of file %s\\n\",\\\n           (nr) * sizeof(*ptr), __LINE__, __FILE__), (ptr = NULL /* (void *) 0 */) : \\\n   ptr\\\n  )\n\n#define CALLOC(ptr, nr, type)\\\n  ((((nr) == 0) || ((ptr = (type *) calloc((size_t)(nr), sizeof(*ptr))) == NULL)) ? \\\n   report(NULL, CRITICAL, \"calloc of %d bytes failed on line %d of file %s\\n\",\\\n           (nr) * sizeof(*ptr), __LINE__, __FILE__), (ptr = NULL /* (void *) 0 */) : \\\n   ptr\\\n  )\n\n#define REALLOC(ptr, nr, type)\\\n  ((((nr) == 0) || ((ptr = (type *) realloc(ptr, (size_t)((nr) * sizeof(*ptr)))) == NULL)) ? \\\n   report(NULL, CRITICAL, \"realloc of %d bytes failed on line %d of file %s\\n\",\\\n           (nr) * sizeof(*ptr), __LINE__, __FILE__), (ptr = NULL /* (void *) 0 */) : \\\n   ptr\\\n  )\n\n#if defined FREE\n# undef FREE\n#endif\n\n#define FREE(ptr) if (ptr != NULL) {free(ptr), ptr = NULL;} else\n\n#define MALLOCCPY(nptr, optr, nr, type)\\\n  (MALLOC(nptr, nr, type), (nptr != NULL) ? memcpy(nptr, optr, (size_t)((nr) * sizeof(*optr))) : 0, nptr)\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/lpsolve.h",
    "content": "// stdafx.h : include file for standard system include files,\n//  or project specific include files that are used frequently, but\n//      are changed infrequently\n//\n\n#if !defined(AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_)\n#define AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_\n\n#if _MSC_VER > 1000\n#pragma once\n#endif // _MSC_VER > 1000\n\n\n// Insert your headers here\n#define WIN32_LEAN_AND_MEAN\t\t// Exclude rarely-used stuff from Windows headers\n\n#include <windows.h>\n\n// TODO: reference additional headers your program requires here\n\n//{{AFX_INSERT_LOCATION}}\n// Microsoft Visual C++ will insert additional declarations immediately before the previous line.\n\n#endif // !defined(AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_)\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/ufortify.h",
    "content": "/*\n * FILE:\n *   ufortify.h\n *\n * DESCRIPTION:\n *   User options for fortify. Changes to this file require fortify.c to be\n * recompiled, but nothing else.\n */\n\n#ifndef __UFORTIFY_H__\n#define __UFORTIFY_H__\n\n#define FORTIFY_STORAGE\n\n#if defined MSDOS || defined __BORLANDC__ || defined __HIGHC__\n# define KNOWS_POINTER_TYPE\n#endif\n\n#define FORTIFY_WAIT_FOR_KEY         /* Pause after message            */\n\n#if !defined FORTIFY_BEFORE_SIZE\n# define FORTIFY_BEFORE_SIZE     16  /* Bytes to allocate before block */\n#endif\n\n#if !defined FORTIFY_BEFORE_VALUE\n# define FORTIFY_BEFORE_VALUE  0xA3  /* Fill value before block        */\n#endif\n\n#if !defined FORTIFY_AFTER_SIZE\n# define FORTIFY_AFTER_SIZE      16  /* Bytes to allocate after block  */\n#endif\n\n#if !defined FORTIFY_AFTER_VALUE\n# define FORTIFY_AFTER_VALUE   0xA5  /* Fill value after block         */\n#endif\n\n#define FILL_ON_MALLOC               /* Nuke out malloc'd memory       */\n\n#if !defined FILL_ON_MALLOC_VALUE\n# define FILL_ON_MALLOC_VALUE  0xA7  /* Value to initialize with       */\n#endif\n\n#define FILL_ON_FREE                 /* free'd memory is cleared       */\n\n#if !defined FILL_ON_FREE_VALUE\n# define FILL_ON_FREE_VALUE    0xA9  /* Value to de-initialize with    */\n#endif\n\n#define FORTIFY_CheckInterval 1      /* seconds */\n/* #define CHECK_ALL_MEMORY_ON_MALLOC */\n#define CHECK_ALL_MEMORY_ON_FREE\n#define PARANOID_FREE\n\n#define WARN_ON_MALLOC_FAIL    /* A debug is issued on a failed malloc */\n#define WARN_ON_ZERO_MALLOC    /* A debug is issued on a malloc(0)     */\n#define WARN_ON_FALSE_FAIL     /* See Fortify_SetMallocFailRate        */\n#define WARN_ON_SIZE_T_OVERFLOW/* Watch for breaking the 64K limit in  */\n                               /* some braindead architectures...      */\n\n#define FORTIFY_LOCK()\n#define FORTIFY_UNLOCK()\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/include/yacc_read.h",
    "content": "/* prototypes of functions used in the parser */\n\n#include <setjmp.h>\n\n#ifndef __READ_H__\n#define __READ_H__\n\nstruct _tmp_store_struct\n{\n  char    *name;\n  int     row;\n  REAL    value;\n  REAL    rhs_value;\n  short   relat;\n};\n\ntypedef struct parse_parm_s\n{\n  void *scanner;\n  long lineno;\n  int Verbose;\n  jmp_buf jump_buf;\n  long Rows, Columns, Non_zeros, Lin_term_count;\n  struct rside *First_rside, *rs;\n  short SOStype;         /* SOS type */\n  char Ignore_int_decl, int_decl, Ignore_sec_decl, Ignore_free_decl, sos_decl, Maximise;\n  hashtable *Hash_tab, *Hash_constraints;\n  struct structcoldata *coldata;\n  struct structSOS *FirstSOS, *LastSOS;\n  struct _tmp_store_struct tmp_store;\n  char *title;\n  short *relat;\n  void *parse_vars;\n} parse_parm;\n\nvoid lex_fatal_error(parse_parm *, void *, char *);\nint set_title(parse_parm *pp, char *name);\nint add_constraint_name(parse_parm *pp, char *name);\nint store_re_op(parse_parm *pp, char OP, int HadConstraint, int HadVar, int Had_lineair_sum);\nvoid null_tmp_store(parse_parm *pp, int init_Lin_term_count);\nint store_bounds(parse_parm *pp, int warn);\nvoid storevarandweight(parse_parm *pp, char *name);\nint set_sos_type(parse_parm *pp, int SOStype);\nint set_sos_weight(parse_parm *pp, double weight, int sos_decl);\nint set_sec_threshold(parse_parm *pp, char *name, REAL threshold);\nint rhs_store(parse_parm *pp, REAL value, int HadConstraint, int HadVar, int Had_lineair_sum);\nint var_store(parse_parm *pp, char *var, REAL value, int HadConstraint, int HadVar, int Had_lineair_sum);\nint negate_constraint(parse_parm *pp);\nvoid add_row(parse_parm *pp);\nvoid add_sos_row(parse_parm *pp, short SOStype);\n\nvoid read_error(parse_parm *, void *, char *);\nvoid check_int_sec_sos_free_decl(parse_parm *, int, int, int, int);\nlprec *yacc_read(lprec *lp, int verbose, char *lp_name, int (*parse) (parse_parm *pp), parse_parm *pp, void (*delete_allocated_memory) (parse_parm *pp));\n\n#define set_obj_dir(pp, maximise) pp->Maximise = maximise\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/README.txt",
    "content": "Introduction\r\n------------\r\nWhat is lp_solve and what is it not?\r\nThe simple answer is, lp_solve is a Mixed Integer Linear Programming (MILP) solver.\r\n\r\nIt is a free (see LGPL for the GNU lesser general public license) linear (integer) programming solver\r\nbased on the revised simplex method and the Branch-and-bound method for the integers.\r\nIt contains full source, examples and manuals.\r\nlp_solve solves pure linear, (mixed) integer/binary, semi-continuous and\r\nspecial ordered sets (SOS) models.\r\n\r\nSee the reference guide for more information.\r\n\r\n\r\nlp_solve 5.5\r\n------------\r\n\r\nWhy a jump from version numbers 5.1 to 5.5 ?\r\nThis is done to indicate that this is more than just another update.\r\nThe solver engine was revised and optimised in such a way that performance has improved considerably.\r\nNumerical stability is also better resulting in more models that can be solved.\r\nThe LUSOL bfp is now also the default. In the past, the etaPFI bfp package was the default,\r\nbut for larger models this leads faster to numerical instabilities and performance problems.\r\n\r\nOverall, the v5.5 code is faster and more robust than v5.1.\r\nThis robustness is for example proven by the fact that many more models can now be solved even without scaling.\r\n\r\nThe API hasn't changed very much.\r\nThere are a couple of new routines and one routine has an extra argument.\r\nSome constants got new values.\r\n\r\n    * Fundamental internal change to the solver engine resulting in better performance and numerical stability.\r\n      Both the LP solver and the B&B solvers are enhanced.\r\n    * Optimised MILP branch truncation, with reduced cost fixing.\r\n    * LUSOL bfp is now the default.\r\n    * Presolve is improved in functionality and performance.\r\n    * Better handling of degeneracy, with more options.\r\n    * Store and read options from a file make it easier to set options.\r\n    * Partial pricing for the primal simplex now works.\r\n    * Full support for xli_ZIMPL v2.0.3.\r\n    * The objective function is no longer stored as part of the constraint matrix.\r\n    * Dual-long step code is in place, but not fully activated yet.\r\n    * General code cleanup.\r\n    * Added OBJSENSE and OBJNAME headers in the free MPS format (See MPS file format).\r\n    * The MathProg xli driver has now the ability to generate a model.\r\n    * New API routines\r\n\r\nStart by taking a look at 'Changes compared to version 4', 'Changes from version 5.1 to version 5.5'\r\nand 'lp_solve usage'\r\nThis gives a good starting point.\r\n\r\n\r\nBFP's\r\n-----\r\n\r\nBFP stands for Basis Factorization Package, which is a unique lp_solve feature.  Considerable\r\neffort has been put in this new feature and we have big expectations for this. BFP is a generic\r\ninterface model and users can develop their own implementations based on the provided templates.\r\nWe are very interested in providing as many different BFPs as possible to the community.\r\n\r\nlp_solve 5.5 has the LUSOL BFP built in as default engine.  In addition two other\r\nBFPs are included for both Windows and Linux: bfp_etaPFI.dll, bfp_GLPK.dll for Windows and\r\nlibbfp_etaPFI.so, libbfp_GLPK.so for Linux.  The bfp_etaPFI includes\r\nadvanced column ordering using the COLAMD library, as well as better pivot management for\r\nstability.  For complex models, however, the LU factorization approach is much better, and\r\nlp_solve now includes LUSOL as one of the most stable engines available anywhere.  LUSOL was\r\noriginally developed by Prof. Saunders at Stanford, and it has now been ported to C\r\nand enhanced by Kjell.\r\n\r\nIf you compile BFPs yourself, make sure that under Windows, you use __stdcall convention and\r\nuse 8 byte alignments.  This is needed for the BFPs to work correctly with the general\r\ndistribution of lp_solve and also to make sharing BFPs as uncomplicated as possible.\r\n\r\nSee the reference guide for more information.\r\n\r\n\r\nXLI's\r\n-----\r\n\r\nXLI stands for eXternal Language Interface, also a unique lp_solve feature. XLI's are stand-alone\r\nlibraries used as add-on to lp_solve to make it possible to read and write lp models in a format\r\nnot natively supported by lp_solve. Examples are CPLEX lp format, LINDO lp format, MathProg format,\r\nXML format...\r\n\r\nSee the reference guide for more information.\r\n\r\n\r\nlpsolve API\r\n-----------\r\n\r\nDon't forget that the API has changed compared to previous versions of lpsolve and that you just\r\ncan't use the version 5 lpsolve library with your version 4 or older code.  That is also the\r\nreason why the library is now called lpsolve55.dll/lpsolve55.a.  lpsolve55.dll or lpsolve55.a are\r\nonly needed when you call the lpsolve library via the API interface from your program.\r\nThe lp_solve program is still a stand-alone executable program.\r\n\r\nThere are examples interfaces for different language like C, VB, C#, VB.NET, Java,\r\nDelphi, and there is now also even a COM object to access the lpsolve library.  This means that\r\nthe door is wide-open for using lp_solve in many different situations.  Thus everything that is\r\navailable in version 4 is now also available in version 5 and already much more!\r\n\r\nSee the reference guide for more information.\r\n\r\n\r\nConversion between lp modeling formats\r\n--------------------------------------\r\n\r\nNote that lp2mps and mps2lp don't exist anymore. However this functionality is now implemented\r\nin lp_solve:\r\n\r\nlp2mps can be simulated as following:\r\nlp_solve -parse_only -lp infile -wmps outfile\r\n\r\nmps2lp can be simulated as following:\r\nlp_solve -parse_only -mps infile -wlp outfile\r\n\r\n\r\nvia the -rxli option, a model can be read via an XLI library and via the -wxli option, a model\r\ncan be written via an XLI library.\r\n\r\n\r\nHow to build the executables yourself.\r\n---------------------------------------\r\n\r\nAt this time, there are no Makefiles yet. However for the time being, there are batch files/scripts\r\nto build. For the Microsoft compiler under Windows, use cvc6.bat, for the gnu compiler under Windows,\r\nuse cgcc.bat and for Unix/Linux, use the ccc shell script (sh ccc).\r\n\r\nSee the reference guide for more information.\r\n\r\n\r\nIDE\r\n---\r\n\r\nUnder Windows, there is now also a very user friendly lpsolve IDE. Check out LPSolveIDE\r\n\r\nSee the reference guide for more information.\r\n\r\n\r\nDocumentation (reference guide)\r\n-------------------------------\r\n\r\nSee lp_solve55.chm for a Windows HTML help documentation file.\r\nThe html files are also in lp_solve_5.5_doc.tar.gz. Start with index.htm\r\nAlso see http://lpsolve.sourceforge.net/ for a on-line documentation\r\n\r\n\r\nChange history:\r\n---------------\r\n\r\n17/05/05 version 5.5.0.0\r\n- Beta release of version 5.5\r\n\r\n??/??/05 version 5.5.0.1\r\n- ?\r\n\r\n26/06/05 version 5.5.0.2\r\n- ?\r\n\r\n29/06/05 version 5.5.0.3\r\n- ?\r\n\r\n16/08/05 version 5.5.0.4\r\n- There are no API changes\r\n- The LUSOL message routine could generate a crash under some cicumstances. Fixed\r\n- A crash could occur when building the model in add_row_mode. Fixed.\r\n- write_params didn't write the PRESOLVE and PRESOLVELOOPS correctly. Fixed.\r\n- write_params didn't write constants with value 0. Fixed.\r\n- The library did not compile under msdev 2002 (VC 7.0 _MSC_VER 1300). Fixed.\r\n- There were some problems with printing long long variables which could generate a crash. Fixed.\r\n- An overflow error could occur because memory was sometimes overwritten. Fixed.\r\n- Presolve routines are revised. They are again improved and made faster.\r\n  Also some problems with it are fixed (possible crashes).\r\n- Solver revised. Again made faster and more stable.\r\n- get_row/get_column returned FALSE if the row/column is empty. Fixed.\r\n- get_rowex/get_columnex now returns -1 if and error is detected. This instead of 0.\r\n  This to know the distinction between an empty row/column and an error.\r\n- set_bounds had a possible problem when min and max are equal. Fixed.\r\n- A crash/damage error could occur when rows/columns are added after a solve. Fixed.\r\n- The my_chsign macro in lp_types.h gave warnings with some compilers. Fixed.\r\n- The lp_solve program now returns 255 if an unexpected error occurs. Before this was 1\r\n  But this interferes with the lpsolve library return codes.\r\n- With the lp_solve program, debug and print modes were not written correctly in a\r\n  specified parameter file. Fixed.\r\n- With the lp_solve program, presolveloops was not set correctly. Fixed.\r\n\r\n17/09/05 version 5.5.0.5\r\n- In some cases, SOS restrictions were not optimized till optimality. Fixed.\r\n- Presolve sometimes generated 'Column -xxx out of range during presolve' with a possible crash.\r\n- Presolve sometimes removed integer and/or semi-cont variables that should not be deleted. Fixed.\r\n- B&B sometimes didn't find the most optimal solution. Fixed.\r\n- Internal constant COMP_EQUAL renamed to COMP_PREFERNONE because this could interfere with a define\r\n  in the standard header files.\r\n- The lp parser had problems with variables starting with INF and there is a + or - sign just before it.\r\n  Fixed.\r\n- Added options -presolvem, -presolvefd, -presolvebnd, -presolved, -presolveslk\r\n- Updated documentation. put_bb_branchfunc, put_bb_nodefunc, set_epslevel, dualize_lp, set_basisvar\r\n\r\n16/11/05 version 5.5.0.6\r\n- set_add_rowmode should not be called after a solve. There is now a test in this routine when this is\r\n  done and it then returns FALSE.\r\n- When an empty string (\"\") as filename is provided to set_outputfile, then output is completely\r\n  ignored.\r\n- In some cases, SOS models did not solve to their most optimal solution.\r\n- There was as problem with get_sensitivity_objex. Calling it (sometimes only after multiple times)\r\n  resulted in protection errors/core dumps.\r\n- When a model has no constraints, it did not solve most of the times.\r\n- column_in_lp didn't work anymore.\r\n- Large upper bounds could make the model unstable. A change was made to fix this.\r\n- set_improve could let crash the model.\r\n- lp_params.c used the non-ANSI function unlink(). Changed to ANSI function remove().\r\n- Presolve is again revised considerably.\r\n- SOS handling is improved when there are a lot of SOS constraints.\r\n- Limited constraint-to-SOS1 presolve to constraints with at least 4 variables.\r\n- Limited bound tightening presolve loops.\r\n\r\n12/02/06 version 5.5.0.7\r\n- When SOS restrictions are added after a previous solve, a crash could occur.\r\n- Optimized renaming a variable when the new name is equal to the old name.\r\n- A possible crash could occur when presolve was enabled\r\n- The constant ANTIDEGEN_DEFAULT is changed. ANTIDEGEN_INFEASIBLE is removed from it.\r\n  This constant should not be used unless you have some very tight and hard to solve\r\n  models where the optimal solution numerically straddles infeasibility.\r\n- There was a possible problem with set_row(ex). It sometimes wrongfully changed the row.\r\n- When integer variables were scaled, it could happen that because of rounding errors,\r\n  a loop was created.\r\n- Sometimes integer models kept on looping in the B&B algorithm.\r\n- A memory overrun could occur when an initial basis is set. This when variable names\r\n  are in Rnnn format and constraint names in Cnnn format.\r\n- Some fixes are made in presolve.\r\n- On 64-bit systems, compiler warnings were given and some code worked wrong resulting in\r\n  wrong results.\r\n- lp_solve.c didn't compile with some compilers because if a very deep nested if statement.\r\n- The distributed files now have the version number include in the filename.\r\n  For example lp_solve_5.5.0.7_exe.zip\r\n  This for a possible move to SourceForge in the (near?) future.\r\n- When illegal bounds are specified in the MPS format (lower bound larger than upper bound)\r\n  then a warning was given but the illegal bound was just ignored and the model was solved.\r\n  This resulted in a solution that did not comply to the original model. Now the message is\r\n  seen as an error and solving is aborted.\r\n\r\n\r\n06/09/06 version 5.5.0.8\r\n- When presolve is active and columns are removed and there are SOS constraints, then presolve\r\n  had an error which could result in hanging while solve or maybe wrong solutions.\r\n- set_row(ex) set wrong values when used after a previous solve and scaling is active.\r\n- disabled PRESOLVE_REDUCEMIP since it is very rare that this is effective, and also that it adds\r\n  code complications and delayed presolve effects that are not captured properly.\r\n- made routine guess_basis available for all languages (now exported by the dll).\r\n  The routine is now also documented.\r\n- some bug corrections in guess_basis.\r\n- Corrected a problem with add_column(ex) when add_rowmode is enabled.\r\n- write_lp now wraps long lines over multiple lines to make it more readable.\r\n- A compilation warning/error sometimes occured on is_fixedvar in lp_lusol.c with some compilers.\r\n- Added options -wxlisol and -wxlisolopt to lp_solve program to write a solution file for those\r\n  XLIs that support it.\r\n- Updated CPLEX XLI to support constants in objective.\r\n- Added documentation on infeasible models, guess_basis, DIMACS models, CPLEX format, Zimpl, GNU Mathprog.\r\n  Corrected/updated documentation on get_col_name, get_row_name, get_nameindex, write_xli,\r\n  External Language Interfaces.\r\n- The mps reader was improved for the rarely cases where the same elements are provided multiple\r\n  times. These are now added.\r\n- Revised the java unittest example because it gave some errors that it shouldn't give.\r\n\r\n07/10/06 version 5.5.0.9\r\n- set_row(ex) could sometimes set wrong values in the model.\r\n- Sometimes models with semi-cont variables which are also integer and scaling is active, a solution\r\n  was returned that is not most optimal or it returns infeasible.\r\n- write_mps didn't write semi-cont variables with an infinite upper bound.\r\n- When presolve can solve the model on its own and objective direction is maximize then a wrong sign\r\n  was shown in the reported price on screen.\r\n- write_lp writes constraint and bounds in the same way if a constraint is not named. If a constraint\r\n  only has one variable then it looks like a bound. This can give problems because when a constraint\r\n  is interpreted as bound and it is negative then the problem definition changes.\r\n  Therefore a constraint which is not named and having only one variable in it is getting a name to\r\n  make sure it is interpreted as a constraint.\r\n- The lp_solve program didn't interprete the PRESOLVED solve return code very well. Fixed.\r\n- bfp_GLPK and xli_MathProg are now compiled against GLPK 4.11\r\n- When an integer model is aborted before the most optimal solution is found (timeout or\r\n  break at first, ...) solve returned OPTIMAL (0) instead of SUBOPTIMAL (1). This is now corrected.\r\n\r\n14/01/07 version 5.5.0.10\r\n- If a model has integer variables, but the model is already integer optimal in the simplex fase,\r\n  then it was reported as suboptimal feasible.\r\n- get_objective, get_variables, get_ptr_variables, get_constraints, get_ptr_constraints, get_primal_solution\r\n  reported 'not a valid basis' when presolve is active and the model is entirely solved by presolve.\r\n- presolve on a model with SOS variables sometimes went wrong.\r\n- presolve on a model with SOS variables where infeasibility is detected crashed.\r\n- read_bas could fail when not all constraints had names or had names like default variable names.\r\n- A crash could occur with set_row(ex) in rowmode.\r\n- The lp format has been extended with a free section to define free variables.\r\n- bfp_GLPK and xli_MathProg are now compiled against GLPK 4.13\r\n- fixed bug in the pseudocost logic that can blow up subsequent pseudocost values in that\r\n  branch and make them almost random.\r\n- In some rare cases a memory overrun could occur when constraints are added after a previous solve.\r\n- Made the copy_lp routine work. Note that information about the optimisation of the original model\r\n  is not copied (at this time). Only the model is.\r\n- Fixed a bug in the hashing routines that had only influence in some rare cases in the\r\n  MATLAB, O-Matrix, Scilab, Octave, Python drivers.\r\n- coldual sometimes worked on a uninitialised variable value with unpredictable results.\r\n\r\n27/12/07 version 5.5.0.11\r\n- Fixed a problem in presolve. Sometimes an array-index-out-of-bounds error occured.\r\n- Added a makefile for Linux.\r\n- When adding constraints, in some rare cases a memory overrun could occur resulting in a crash.\r\n- add_constraintex with count=0 and row=colno=NULL gave a protection error.\r\n  several XLIs didn't work anymore because of this.\r\n- set_constr_type sometimes set wrong signs for the coefficient matrix when add_rowmode is on.\r\n- presolve did an unnecessary extra loop. Also a test is added to stop presolve when very few\r\n  changes are done.\r\n- for very large models, a request of much more memory than is reasonable could occur. Fixed.\r\n- Modified LINDO XLI to read keywords also not at column 1 and to accept an empty objective function.\r\n  Previously this wat not possible.\r\n- In some rare cases, numbers very close to their integer values (for example 11276.999999999998)\r\n  were truncated to their ceiling value (for example 11276) instead of rounded\r\n  (for example 11277).\r\n- Solved a problem with presolve with an all-int constraint.\r\n- Solved a problem with presolve coldominate\r\n- Added stronger checking of the MPS format.\r\n  Fields that must be blank are now also tested accordingly so that if data is there that it is\r\n  not ignored as before.\r\n- FREE MPS format was not read ok if row/column name were all numbers\r\n  or a FR, MI, PL, BV bound was defined. Fixed.\r\n- The lp-format now also supports a bin(ary) section to define binary variables.\r\n- When an integer model is aborted before the most optimal solution is found\r\n  via break at first or break at value, solve returned OPTIMAL (0) instead of SUBOPTIMAL (1).\r\n  This is now corrected. Problem occured in version 5.5.0.10\r\n- Fixed a problem with del_constraint. Constraints names were not shifted and reported variable result was incorrect.\r\n- read_XLI failed with MathProg if datamodel was provided with \"\" when there is no datamodel.\r\n  NULL was expected in the past. \"\" is now also accepted.\r\n- Added an XLI to read Xpress lp files.\r\n- Added routines MPS_writefileex, write_lpex.\r\n- Added options -o0, -o1 to lp_solve command driven program to specify if objective is in basis or not.\r\n- Added new information in the reference guide:\r\n   - Linear programming basics\r\n   - Presolve\r\n   - Xpress lp files\r\n\r\n04/01/08 version 5.5.0.11\r\n- There was an error in the lp-parser resulting is misreading the model in many cases. This was fixed in the existing release and an update of following files is posted:\r\n    lp_solve_5.5.0.11_exe.tar.gz\r\n    lp_solve_5.5.0.11_dev.tar.gz\r\n    lp_solve_5.5.0.11_source.tar.gz\r\n    lp_solve_5.5.0.11_exe.zip\r\n    lp_solve_5.5.0.11_dev.zip\r\n\r\n13/03/08 version 5.5.0.12\r\n- When NODE_RCOSTFIXING (bound tightening during B&B) (enabled by default) was enabled some models were not solved\r\n  to optimality.\r\n- In following situation a (sub-optimal) solution was returned while no integer\r\n  solution isn't found yet at this time.\r\n   - The model contains integers\r\n   - A break at first is set\r\n   - A timeout is set\r\n   - The timeout occurs before a first integer solution is found\r\n   - When the timeout occurs, the simplex algorithm is in phase 2 and has a feasible (but non-integer) solution, but not optimal yet.\r\n- If an integer solution is found with the same objective value as the relaxed solution then\r\n  B&B is stopped. However this resulted in a report of a SUBOPTIMAL solution while this is not true.\r\n  The found solution is then optimal.\r\n- On 64-bit Linux systems crashes occured when information is printed via variable argument routines.\r\n- There was a warning about redefinition of MAXINT32, MAXUINT32, MAXINT64, MAXUINT64 when compiled\r\n  with MS Visual C 2008.\r\n- The reference guide now also contains the Java documentation.\r\n\r\n03/08/08 version 5.5.0.13\r\n- The code should now completely be reentrant and thread safe.\r\n  Especially the lp-parser, but also the solver code itself used static variables which made it\r\n  not reentrant.\r\n  The lp parser code has changed considerably for this. Also the lex and yacc code had to be made\r\n  reentrant. This is only tested with GNU flex and bison. Not with lex and yacc.\r\n  This should be no problem since the corresponding c files are included with the source so people\r\n  don't have to build these themselves.\r\n- commonlib.c/h were also under BFP/BFP_LUSOL/LUSOL while a more advanced version is also\r\n  under the shared directory. The one from LUSOL is removed.\r\n- If objective coefficients are all integer and the columns are integer or objective coefficients\r\n  are zero, then B&B can stop when the objective function equals ceil/floor(real objective)\r\n  which results in a faster solving process. This did not work anymore and is now fixed.\r\n- The lpsolve IDE is now also on sourceforge (previously it was a link to another site).\r\n  Also the sources are included.\r\n\r\n02/02/09 version 5.5.0.14\r\n- The lp format now allows spaces between the row label and the colon.\r\n- Added better error handling in the copy_lp API\r\n- Timeout in a MIP model sometimes resulted in an endless loop\r\n- Revised isnan call for gnu compilers\r\n- Removed some extra static variables for better reentrance support.\r\n- REPORT_Objective now reports large objective values (>1e-5) with better precision\r\n- On Windows the binaries are again compiled with compiler optimization /O2 for better performance.\r\n- Compiled and tested on Windows and Linux 64-bit. 64-bit binaries are now provided.\r\n  Changed project files and compile scripts for 64-bit compilation.\r\n  Binaries are now located in a subdirectory bin\\platform\r\n- Added PHP driver so that lpsolve can be called from PHP\r\n- When an MPS file is created, upper bounds were written before lower bounds.\r\n  Now it is the other way around. First lower bounds and then upper bounds.\r\n- The MPS reader could not handle negative lower bounds where the lower bound was specified after the upper bound.\r\n- The MPS write now writes the implicit lower bound of zero if the variable has no lower bound and it is integer.\r\n  This to make sure that other solvers (like CPLEX) interprete the variable as integer and not binary.\r\n- The LINDO XLI parser interpreted negative lower and upper bounds as positive\r\n- Added the option -stat to the lp_solve driver program. It prints statistics of the model like number of\r\n  rows/columns used and smalled and largest value in objective, RHS and coefficient matrix.\r\n- Added the option -plp to the lp_solve driver program. It prints the model via the print_lp API function.\r\n\r\n09/09/09 version 5.5.0.15\r\n- Improved guess_basis\r\n- set_row(ex) corrections. Actually completely revised the routine.\r\n  Sometimes the matrix was corrupted after the call.\r\n- When in set_add_row mode, all API calls can now be used. For example printing or writing the model,\r\n  retrieving data from the model and so on are now all possible in that mode.\r\n  Will help greatly when debugging your models.\r\n- Sometimes an integer model is reported infeasible while it isn't because the integer solution\r\n  is much different from the relaxed (real) model. Then API call set_bb_depthlimit can be used\r\n  to increase the default B&B depth. However its new value was not used for the depth limit of an\r\n  individual variabled which could result in still infeasible results.\r\n- modified the demo program not to use the str_ versions of API calls, because they are not\r\n  performant and not intended to be used in real programs.\r\n- Added an lpsolve driver to Sysquake.\r\n- Added an lpsolve driver to FreeMat.\r\n- Added an lpsolve driver to Euler.\r\n- Added an Access example.\r\n- Added documentation to use lpsolve from Sage via the existing Python driver.\r\n- Changed the second parameter to read_mps, read_MPS, read_freemps and read_freeMPS from verbose to options.\r\n  These routines now supports via this options parameter the native IBM interpretation of\r\n  integer variables and allows to negate the objective constant.\r\n  This is also supported by the lp_solve command line program via the -mps_ibm and -mps_negobjconst options.\r\n  This is also supported by the IDE in the options tab.\r\n- Removed read_LPhandle and read_MPShandle from the lprec structure.\r\n  On their place there is now read_LP and read_MPS.\r\n  The handle functions are not usable anyway under windows as dll because the FILE structure\r\n  is searched in the dll space and therefore not working.\r\n  read_LP and read_MPS work on the file name and always work.\r\n  Since these handle routines were not documented anyway and the lp structure should not be\r\n  accessed by applications (except XLI and BFP drivers) this change should not give any (compatibility) problem at all.\r\n- write_lp/write_LP write just a + or - if the factor to a variable is +1 or -1\r\n  However when the number was not exactly one, for example 1.0000000000001, then the test\r\n  on equal to one gave false, but the writing was a 1 because only 12 significant digits are written.\r\n  The result was that the 1 was written in that case. Not an error, but when lp files are compared,\r\n  this is enoying. Now this is solved. When a +1 or -1 would be written then alyways only + and -\r\n  is written and +1 or -1 will never occur again.\r\n- When a message function is set via put_msgfunc,\r\n  in message MSG_LPOPTIMAL it was not possible to get the solution. Now it is.\r\n  Also when messages MSG_MILPFEASIBLE, MSG_MILPBETTER, MSG_MILPEQUAL were catched the\r\n  returned solution was the one from the previous MIP solution. This is now also fixed.\r\n  With this fix, the IDE now also shows the relaxed solution (column LP Optimal).\r\n- Extended the MATLAB, O-Matrix, Scilab, Octave, Python, PHP and of course the new\r\n  Sysquake, FreeMat and Euler drivers to support string constants. See the reference guide.\r\n- Compiled and tested lpsolve on MAC OSX 10.4.8 (Intel). Compilation scripts for this platform\r\n  were added and revised and binaries are provided to download.\r\n- Revised the c# and vb.net lpsolve code to pass arrays back and forth to the dll to make it also work on 64 bit systems.\r\n- IDE enhancements:\r\n      - Can talk to the lpsolve55.dll large address aware version so access to 3.4G 32 bit memory.\r\n      - Can write and read lp_solve parameter files ( type .lpi) via Options, Solver params, so\r\n        it is easy to save a readable file of parameters for a particular problem class when it is found.\r\n        The file can then be collected by the -rpar exe param or the read_params() API.\r\n      - Added Options, Reset to solver defaults to go back to all lp_solve defaults.\r\n      - Added in Help a link to the online help files.\r\n      - Resized the help, main and statistics windows for Vista.\r\n      - Added the Xpress XLI to the setup.\r\n      - Use the latest dlls, especially lpsolve55.dll, in the setup.\r\n      - Added the two new MPS options for IBM integer variables and negate objective constant.\r\n      - Added the option to ignore integer restrictions.\r\n17/09/09 version 5.5.0.15b\r\n- objfrom values where not correct if scaling is active.\r\n  Routine to calculate these values and the objective from-till values is revised\r\n  and made a bit more performant.\r\n- write_lp did not write all column data. For objective function and constraints.\r\n\r\n28/10/09 version 5.5.1.0\r\n- In some cases with a model with integer variables lp_solve did not find the most optimal solution. Fixed.\r\n- The reported relative gap for the optimal solution was not always ok.\r\n- Sensitivity on a zero upper bounded variable was not calculated. Now it is.\r\n\r\n08/03/10 version 5.5.1.2\r\n- When there are integer variables in the model then sensitivity is not correct.\r\n\r\n12/08/10 version 5.5.2.0\r\n- add_SOS did a wrong test when SOS type is bigger than 2 if this SOS is allowed in lp_solve. Fixed\r\n- new and improved MIP_stepOF function to find integer solutions.\r\n- fixes in set_row.\r\n- replaces code\r\n   w *= 2*lp->is_lower[i] - 1;\r\n  by\r\n   w = my_chsign(!lp->is_lower[i], w);\r\n  because the old failed on AIX\r\n  Also changed the definition of my_chsign in lp_types.h in the same way.\r\n- Added the option -BR in the lp_solve driver program to select branch rule NODE_PSEUDORATIOSELECT\r\n- lpsolve.pas updated for Delphi 2009.\r\n- Python driver updated to allow also to provide numpy arrays to the lpsolve driver.\r\n- xli_MathProg is now compiled against glpk 4.44 meaning that it now supports the MathProg Tables feature\r\n  as described in http://www.cs.unb.ca/~bremner/docs/glpk/tables.pdf\r\n  csv, ODBC and MySQL are supported on all platforms.\r\n- Added MSF support. MSF (Microsoft Solver Foundation) is a microsoft .NET library to access solvers via an OO way\r\n  MSF has a default lpsolve driver, but the one on the sourceforge site is enhanced in functionality and performance.\r\n  There is also documentation in the lpsolve reference guide.\r\n\r\nWe are thrilled to hear from you and your experiences with this new version. The good and the bad.\r\nAlso we would be pleased to hear about your experiences with the different BFPs on your models.\r\n\r\nPlease send reactions to:\r\nPeter Notebaert: lpsolve@peno.be\r\nKjell Eikland: kjell.eikland@broadpark.no\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/LUSOL-overview.txt",
    "content": "            Notes for Contribution of LUSOL to COIN-OR\r\n                            May 2004\r\n\r\nIntroduction\r\n============\r\n\r\nLUSOL maintains sparse LU factors of a square or rectangular sparse matrix.  It includes a Basis Factorization Package (BFP) suitable for implementing simplex and reduced-gradient methods for optimization.  It is a set of  routines written in ANSI C (adapted from the original Fortran 77 version).\r\n\r\nLUSOL includes the following features:\r\n\r\n-  A Markowitz-based sparse LU factorization for square,\r\n   rectangular and possibly singular matrices.\r\n\r\n-  Three options for balancing sparsity and stability:\r\n   Threshold Partial/Rook/Complete Pivoting (TPP, TRP, TCP).\r\n\r\n-  Rank-revealing properties.  TRP and TCP are intended for detecting singularities.\r\n\r\n-  Dynamic storage allocation (C version only).\r\n\r\n-  Stable column replacement as in the method of Bartels and Golub.\r\n\r\n-  Other stable updates: add, replace, or delete row or column\r\n   (currently F77 version only).\r\n\r\n-  Implementation into an easy-to-use BFP API (C version only).\r\n\r\n\r\nImplementation\r\n==============\r\n\r\nThe Factor routine is similar to the classical Markowitz routines MA28 and LA05 in the Harwell Subroutine Library. The source matrix nonzeros are stored column-wise with the largest entry at the top of each column.  Internally, the structure is also accessible row-wise.  All entries in a particular column or row are held in contiguous storage.  Fill is accommodated by moving a column or row to the beginning of free storage. Occasional compressions recover storage.  This scheme is effective for column-oriented TPP.  When the remaining matrix reaches a specified density, the factors are completed using dense processing.\r\n\r\nTRP uses an additional vector of storage to maintain the largest element in each remaining row.\r\n\r\nTCP uses a heap structure to hold the largest element in each column.  The largest element in the remaining matrix is then available at the top of the heap.\r\n\r\nThe final L is stored column-wise (and never changed).  The final U is stored row-wise as a triangular or trapezoidal sparse matrix.\r\n\r\nColumn replacements are implemented using a forward sweep of 2-by-2 stabilized elimination matrices.  L is updated in product form.  U is updated explicitly.\r\n\r\nThe other updates use either forward or backward sweeps. They tend to generate more nonzeros than column replacement.\r\n\r\nBoth the F77 and C versions contain extensive comments, method and implementational information as part of the code.\r\n\r\nThe C version contains a record-based wrapper for the data.  Function calls have been simplified by including references to this structure.  New maintenance routines enable dynamic instance creation and destruction, and  simplifies access to the most frequently used functions.  The LUSOL C library is multi-instance and fully re-entrant.  All control and output parameters have been given long descriptive names for usability. \r\n\r\n\r\nBenefits\r\n========\r\n\r\nRank-revealing properties and rectangular factors (and updates) have not previously been available in sparse LU software.  With sensible parameter settings and reasonably scaled data, all routines are numerically stable.  The updates may be called hundreds of times, and the decision to refactorize can be based on sparsity considerations alone.\r\n\r\nIn the Factor routine, rook pivoting (TRP) gives reliable rank determination without catastrophic degradation in sparsity or speed.  Complete pivoting (TCP) is included for moderate-sized matrices and for checking pathological cases (but the factors tend to be substantially more dense).\r\n\r\nTo conserve storage, one may request only the row and column pivot orders.  The factors are discarded as they are computed.  This is useful for basis repair, or for selecting a basis from a rectangular matrix.\r\n\r\n\r\nKnown Inefficiencies\r\n====================\r\n\r\nLUSOL is usually efficient on sparse matrices with dimensions up to about 100,000 (but not millions).\r\n\r\nIn the Factor routine, row and column lists must be updated each time a row and column is eliminated.  Deleting the pivot row and column is inefficient if the original matrix contains unusually dense rows or columns.  For TPP, dense columns could be kept aside and incorporated at the end via updates (but dense rows remain a difficulty).  For TRP and TCP, all rows and columns must be present to achieve the required numerical properties.\r\n\r\nFor TRP, the current bottleneck is updating the vector containing the largest element in each row.  One solution would be to include the matrix nonzeros in the row structure (but this carries its own cost).\r\n\r\nFor TCP, the heap structure is already efficient, but the dense factors (and the extended searching for acceptable pivots) are unavoidable expenses.\r\n\r\nThe triangular Solve routines do not take full of advantage of sparse right-hand sides.  Gilbert and Peierls have shown how to solve Lx = (sparse b) efficiently if L is stored column-wise.  Their approach could therefore be implemented in LUSOL for solves with L and U(transpose).  Solves with L(transpose) and U would need a second copy of L and U. \r\n\r\n\r\nOriginal Reference\r\n==================\r\n\r\nP. E. Gill, W. Murray, M. A. Saunders and M. H. Wright, Maintaining LU factors of a general sparse matrix, Linear Algebra and its Applications 88/89, 239-270 (1987).\r\n\r\n\r\nMaintainers\r\n===========\r\n\r\nF77 version: Michael Saunders (saunders@stanford.edu).\r\nC version: Kjell Eikland (kjell.eikland@broadpark.no).\r\n\r\n\r\nContributors\r\n============\r\n\r\nPhilip Gill, Walter Murray, Margaret Wright, Michael O'Sullivan.\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/LUSOL_LGPL.txt",
    "content": "\t\t  GNU LESSER GENERAL PUBLIC LICENSE\r\n\t\t       Version 2.1, February 1999\r\n\r\n Copyright (C) 1991, 1999 Free Software Foundation, Inc.\r\n     59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n Everyone is permitted to copy and distribute verbatim copies\r\n of this license document, but changing it is not allowed.\r\n\r\n[This is the first released version of the Lesser GPL.  It also counts\r\n as the successor of the GNU Library Public License, version 2, hence\r\n the version number 2.1.]\r\n\r\n\t\t\t    Preamble\r\n\r\n  The licenses for most software are designed to take away your\r\nfreedom to share and change it.  By contrast, the GNU General Public\r\nLicenses are intended to guarantee your freedom to share and change\r\nfree software--to make sure the software is free for all its users.\r\n\r\n  This license, the Lesser General Public License, applies to some\r\nspecially designated software packages--typically libraries--of the\r\nFree Software Foundation and other authors who decide to use it.  You\r\ncan use it too, but we suggest you first think carefully about whether\r\nthis license or the ordinary General Public License is the better\r\nstrategy to use in any particular case, based on the explanations below.\r\n\r\n  When we speak of free software, we are referring to freedom of use,\r\nnot price.  Our General Public Licenses are designed to make sure that\r\nyou have the freedom to distribute copies of free software (and charge\r\nfor this service if you wish); that you receive source code or can get\r\nit if you want it; that you can change the software and use pieces of\r\nit in new free programs; and that you are informed that you can do\r\nthese things.\r\n\r\n  To protect your rights, we need to make restrictions that forbid\r\ndistributors to deny you these rights or to ask you to surrender these\r\nrights.  These restrictions translate to certain responsibilities for\r\nyou if you distribute copies of the library or if you modify it.\r\n\r\n  For example, if you distribute copies of the library, whether gratis\r\nor for a fee, you must give the recipients all the rights that we gave\r\nyou.  You must make sure that they, too, receive or can get the source\r\ncode.  If you link other code with the library, you must provide\r\ncomplete object files to the recipients, so that they can relink them\r\nwith the library after making changes to the library and recompiling\r\nit.  And you must show them these terms so they know their rights.\r\n\r\n  We protect your rights with a two-step method: (1) we copyright the\r\nlibrary, and (2) we offer you this license, which gives you legal\r\npermission to copy, distribute and/or modify the library.\r\n\r\n  To protect each distributor, we want to make it very clear that\r\nthere is no warranty for the free library.  Also, if the library is\r\nmodified by someone else and passed on, the recipients should know\r\nthat what they have is not the original version, so that the original\r\nauthor's reputation will not be affected by problems that might be\r\nintroduced by others.\r\n\f\r\n  Finally, software patents pose a constant threat to the existence of\r\nany free program.  We wish to make sure that a company cannot\r\neffectively restrict the users of a free program by obtaining a\r\nrestrictive license from a patent holder.  Therefore, we insist that\r\nany patent license obtained for a version of the library must be\r\nconsistent with the full freedom of use specified in this license.\r\n\r\n  Most GNU software, including some libraries, is covered by the\r\nordinary GNU General Public License.  This license, the GNU Lesser\r\nGeneral Public License, applies to certain designated libraries, and\r\nis quite different from the ordinary General Public License.  We use\r\nthis license for certain libraries in order to permit linking those\r\nlibraries into non-free programs.\r\n\r\n  When a program is linked with a library, whether statically or using\r\na shared library, the combination of the two is legally speaking a\r\ncombined work, a derivative of the original library.  The ordinary\r\nGeneral Public License therefore permits such linking only if the\r\nentire combination fits its criteria of freedom.  The Lesser General\r\nPublic License permits more lax criteria for linking other code with\r\nthe library.\r\n\r\n  We call this license the \"Lesser\" General Public License because it\r\ndoes Less to protect the user's freedom than the ordinary General\r\nPublic License.  It also provides other free software developers Less\r\nof an advantage over competing non-free programs.  These disadvantages\r\nare the reason we use the ordinary General Public License for many\r\nlibraries.  However, the Lesser license provides advantages in certain\r\nspecial circumstances.\r\n\r\n  For example, on rare occasions, there may be a special need to\r\nencourage the widest possible use of a certain library, so that it becomes\r\na de-facto standard.  To achieve this, non-free programs must be\r\nallowed to use the library.  A more frequent case is that a free\r\nlibrary does the same job as widely used non-free libraries.  In this\r\ncase, there is little to gain by limiting the free library to free\r\nsoftware only, so we use the Lesser General Public License.\r\n\r\n  In other cases, permission to use a particular library in non-free\r\nprograms enables a greater number of people to use a large body of\r\nfree software.  For example, permission to use the GNU C Library in\r\nnon-free programs enables many more people to use the whole GNU\r\noperating system, as well as its variant, the GNU/Linux operating\r\nsystem.\r\n\r\n  Although the Lesser General Public License is Less protective of the\r\nusers' freedom, it does ensure that the user of a program that is\r\nlinked with the Library has the freedom and the wherewithal to run\r\nthat program using a modified version of the Library.\r\n\r\n  The precise terms and conditions for copying, distribution and\r\nmodification follow.  Pay close attention to the difference between a\r\n\"work based on the library\" and a \"work that uses the library\".  The\r\nformer contains code derived from the library, whereas the latter must\r\nbe combined with the library in order to run.\r\n\f\r\n\t\t  GNU LESSER GENERAL PUBLIC LICENSE\r\n   TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION\r\n\r\n  0. This License Agreement applies to any software library or other\r\nprogram which contains a notice placed by the copyright holder or\r\nother authorized party saying it may be distributed under the terms of\r\nthis Lesser General Public License (also called \"this License\").\r\nEach licensee is addressed as \"you\".\r\n\r\n  A \"library\" means a collection of software functions and/or data\r\nprepared so as to be conveniently linked with application programs\r\n(which use some of those functions and data) to form executables.\r\n\r\n  The \"Library\", below, refers to any such software library or work\r\nwhich has been distributed under these terms.  A \"work based on the\r\nLibrary\" means either the Library or any derivative work under\r\ncopyright law: that is to say, a work containing the Library or a\r\nportion of it, either verbatim or with modifications and/or translated\r\nstraightforwardly into another language.  (Hereinafter, translation is\r\nincluded without limitation in the term \"modification\".)\r\n\r\n  \"Source code\" for a work means the preferred form of the work for\r\nmaking modifications to it.  For a library, complete source code means\r\nall the source code for all modules it contains, plus any associated\r\ninterface definition files, plus the scripts used to control compilation\r\nand installation of the library.\r\n\r\n  Activities other than copying, distribution and modification are not\r\ncovered by this License; they are outside its scope.  The act of\r\nrunning a program using the Library is not restricted, and output from\r\nsuch a program is covered only if its contents constitute a work based\r\non the Library (independent of the use of the Library in a tool for\r\nwriting it).  Whether that is true depends on what the Library does\r\nand what the program that uses the Library does.\r\n  \r\n  1. You may copy and distribute verbatim copies of the Library's\r\ncomplete source code as you receive it, in any medium, provided that\r\nyou conspicuously and appropriately publish on each copy an\r\nappropriate copyright notice and disclaimer of warranty; keep intact\r\nall the notices that refer to this License and to the absence of any\r\nwarranty; and distribute a copy of this License along with the\r\nLibrary.\r\n\r\n  You may charge a fee for the physical act of transferring a copy,\r\nand you may at your option offer warranty protection in exchange for a\r\nfee.\r\n\f\r\n  2. You may modify your copy or copies of the Library or any portion\r\nof it, thus forming a work based on the Library, and copy and\r\ndistribute such modifications or work under the terms of Section 1\r\nabove, provided that you also meet all of these conditions:\r\n\r\n    a) The modified work must itself be a software library.\r\n\r\n    b) You must cause the files modified to carry prominent notices\r\n    stating that you changed the files and the date of any change.\r\n\r\n    c) You must cause the whole of the work to be licensed at no\r\n    charge to all third parties under the terms of this License.\r\n\r\n    d) If a facility in the modified Library refers to a function or a\r\n    table of data to be supplied by an application program that uses\r\n    the facility, other than as an argument passed when the facility\r\n    is invoked, then you must make a good faith effort to ensure that,\r\n    in the event an application does not supply such function or\r\n    table, the facility still operates, and performs whatever part of\r\n    its purpose remains meaningful.\r\n\r\n    (For example, a function in a library to compute square roots has\r\n    a purpose that is entirely well-defined independent of the\r\n    application.  Therefore, Subsection 2d requires that any\r\n    application-supplied function or table used by this function must\r\n    be optional: if the application does not supply it, the square\r\n    root function must still compute square roots.)\r\n\r\nThese requirements apply to the modified work as a whole.  If\r\nidentifiable sections of that work are not derived from the Library,\r\nand can be reasonably considered independent and separate works in\r\nthemselves, then this License, and its terms, do not apply to those\r\nsections when you distribute them as separate works.  But when you\r\ndistribute the same sections as part of a whole which is a work based\r\non the Library, the distribution of the whole must be on the terms of\r\nthis License, whose permissions for other licensees extend to the\r\nentire whole, and thus to each and every part regardless of who wrote\r\nit.\r\n\r\nThus, it is not the intent of this section to claim rights or contest\r\nyour rights to work written entirely by you; rather, the intent is to\r\nexercise the right to control the distribution of derivative or\r\ncollective works based on the Library.\r\n\r\nIn addition, mere aggregation of another work not based on the Library\r\nwith the Library (or with a work based on the Library) on a volume of\r\na storage or distribution medium does not bring the other work under\r\nthe scope of this License.\r\n\r\n  3. You may opt to apply the terms of the ordinary GNU General Public\r\nLicense instead of this License to a given copy of the Library.  To do\r\nthis, you must alter all the notices that refer to this License, so\r\nthat they refer to the ordinary GNU General Public License, version 2,\r\ninstead of to this License.  (If a newer version than version 2 of the\r\nordinary GNU General Public License has appeared, then you can specify\r\nthat version instead if you wish.)  Do not make any other change in\r\nthese notices.\r\n\f\r\n  Once this change is made in a given copy, it is irreversible for\r\nthat copy, so the ordinary GNU General Public License applies to all\r\nsubsequent copies and derivative works made from that copy.\r\n\r\n  This option is useful when you wish to copy part of the code of\r\nthe Library into a program that is not a library.\r\n\r\n  4. You may copy and distribute the Library (or a portion or\r\nderivative of it, under Section 2) in object code or executable form\r\nunder the terms of Sections 1 and 2 above provided that you accompany\r\nit with the complete corresponding machine-readable source code, which\r\nmust be distributed under the terms of Sections 1 and 2 above on a\r\nmedium customarily used for software interchange.\r\n\r\n  If distribution of object code is made by offering access to copy\r\nfrom a designated place, then offering equivalent access to copy the\r\nsource code from the same place satisfies the requirement to\r\ndistribute the source code, even though third parties are not\r\ncompelled to copy the source along with the object code.\r\n\r\n  5. A program that contains no derivative of any portion of the\r\nLibrary, but is designed to work with the Library by being compiled or\r\nlinked with it, is called a \"work that uses the Library\".  Such a\r\nwork, in isolation, is not a derivative work of the Library, and\r\ntherefore falls outside the scope of this License.\r\n\r\n  However, linking a \"work that uses the Library\" with the Library\r\ncreates an executable that is a derivative of the Library (because it\r\ncontains portions of the Library), rather than a \"work that uses the\r\nlibrary\".  The executable is therefore covered by this License.\r\nSection 6 states terms for distribution of such executables.\r\n\r\n  When a \"work that uses the Library\" uses material from a header file\r\nthat is part of the Library, the object code for the work may be a\r\nderivative work of the Library even though the source code is not.\r\nWhether this is true is especially significant if the work can be\r\nlinked without the Library, or if the work is itself a library.  The\r\nthreshold for this to be true is not precisely defined by law.\r\n\r\n  If such an object file uses only numerical parameters, data\r\nstructure layouts and accessors, and small macros and small inline\r\nfunctions (ten lines or less in length), then the use of the object\r\nfile is unrestricted, regardless of whether it is legally a derivative\r\nwork.  (Executables containing this object code plus portions of the\r\nLibrary will still fall under Section 6.)\r\n\r\n  Otherwise, if the work is a derivative of the Library, you may\r\ndistribute the object code for the work under the terms of Section 6.\r\nAny executables containing that work also fall under Section 6,\r\nwhether or not they are linked directly with the Library itself.\r\n\f\r\n  6. As an exception to the Sections above, you may also combine or\r\nlink a \"work that uses the Library\" with the Library to produce a\r\nwork containing portions of the Library, and distribute that work\r\nunder terms of your choice, provided that the terms permit\r\nmodification of the work for the customer's own use and reverse\r\nengineering for debugging such modifications.\r\n\r\n  You must give prominent notice with each copy of the work that the\r\nLibrary is used in it and that the Library and its use are covered by\r\nthis License.  You must supply a copy of this License.  If the work\r\nduring execution displays copyright notices, you must include the\r\ncopyright notice for the Library among them, as well as a reference\r\ndirecting the user to the copy of this License.  Also, you must do one\r\nof these things:\r\n\r\n    a) Accompany the work with the complete corresponding\r\n    machine-readable source code for the Library including whatever\r\n    changes were used in the work (which must be distributed under\r\n    Sections 1 and 2 above); and, if the work is an executable linked\r\n    with the Library, with the complete machine-readable \"work that\r\n    uses the Library\", as object code and/or source code, so that the\r\n    user can modify the Library and then relink to produce a modified\r\n    executable containing the modified Library.  (It is understood\r\n    that the user who changes the contents of definitions files in the\r\n    Library will not necessarily be able to recompile the application\r\n    to use the modified definitions.)\r\n\r\n    b) Use a suitable shared library mechanism for linking with the\r\n    Library.  A suitable mechanism is one that (1) uses at run time a\r\n    copy of the library already present on the user's computer system,\r\n    rather than copying library functions into the executable, and (2)\r\n    will operate properly with a modified version of the library, if\r\n    the user installs one, as long as the modified version is\r\n    interface-compatible with the version that the work was made with.\r\n\r\n    c) Accompany the work with a written offer, valid for at\r\n    least three years, to give the same user the materials\r\n    specified in Subsection 6a, above, for a charge no more\r\n    than the cost of performing this distribution.\r\n\r\n    d) If distribution of the work is made by offering access to copy\r\n    from a designated place, offer equivalent access to copy the above\r\n    specified materials from the same place.\r\n\r\n    e) Verify that the user has already received a copy of these\r\n    materials or that you have already sent this user a copy.\r\n\r\n  For an executable, the required form of the \"work that uses the\r\nLibrary\" must include any data and utility programs needed for\r\nreproducing the executable from it.  However, as a special exception,\r\nthe materials to be distributed need not include anything that is\r\nnormally distributed (in either source or binary form) with the major\r\ncomponents (compiler, kernel, and so on) of the operating system on\r\nwhich the executable runs, unless that component itself accompanies\r\nthe executable.\r\n\r\n  It may happen that this requirement contradicts the license\r\nrestrictions of other proprietary libraries that do not normally\r\naccompany the operating system.  Such a contradiction means you cannot\r\nuse both them and the Library together in an executable that you\r\ndistribute.\r\n\f\r\n  7. You may place library facilities that are a work based on the\r\nLibrary side-by-side in a single library together with other library\r\nfacilities not covered by this License, and distribute such a combined\r\nlibrary, provided that the separate distribution of the work based on\r\nthe Library and of the other library facilities is otherwise\r\npermitted, and provided that you do these two things:\r\n\r\n    a) Accompany the combined library with a copy of the same work\r\n    based on the Library, uncombined with any other library\r\n    facilities.  This must be distributed under the terms of the\r\n    Sections above.\r\n\r\n    b) Give prominent notice with the combined library of the fact\r\n    that part of it is a work based on the Library, and explaining\r\n    where to find the accompanying uncombined form of the same work.\r\n\r\n  8. You may not copy, modify, sublicense, link with, or distribute\r\nthe Library except as expressly provided under this License.  Any\r\nattempt otherwise to copy, modify, sublicense, link with, or\r\ndistribute the Library is void, and will automatically terminate your\r\nrights under this License.  However, parties who have received copies,\r\nor rights, from you under this License will not have their licenses\r\nterminated so long as such parties remain in full compliance.\r\n\r\n  9. You are not required to accept this License, since you have not\r\nsigned it.  However, nothing else grants you permission to modify or\r\ndistribute the Library or its derivative works.  These actions are\r\nprohibited by law if you do not accept this License.  Therefore, by\r\nmodifying or distributing the Library (or any work based on the\r\nLibrary), you indicate your acceptance of this License to do so, and\r\nall its terms and conditions for copying, distributing or modifying\r\nthe Library or works based on it.\r\n\r\n  10. Each time you redistribute the Library (or any work based on the\r\nLibrary), the recipient automatically receives a license from the\r\noriginal licensor to copy, distribute, link with or modify the Library\r\nsubject to these terms and conditions.  You may not impose any further\r\nrestrictions on the recipients' exercise of the rights granted herein.\r\nYou are not responsible for enforcing compliance by third parties with\r\nthis License.\r\n\f\r\n  11. If, as a consequence of a court judgment or allegation of patent\r\ninfringement or for any other reason (not limited to patent issues),\r\nconditions are imposed on you (whether by court order, agreement or\r\notherwise) that contradict the conditions of this License, they do not\r\nexcuse you from the conditions of this License.  If you cannot\r\ndistribute so as to satisfy simultaneously your obligations under this\r\nLicense and any other pertinent obligations, then as a consequence you\r\nmay not distribute the Library at all.  For example, if a patent\r\nlicense would not permit royalty-free redistribution of the Library by\r\nall those who receive copies directly or indirectly through you, then\r\nthe only way you could satisfy both it and this License would be to\r\nrefrain entirely from distribution of the Library.\r\n\r\nIf any portion of this section is held invalid or unenforceable under any\r\nparticular circumstance, the balance of the section is intended to apply,\r\nand the section as a whole is intended to apply in other circumstances.\r\n\r\nIt is not the purpose of this section to induce you to infringe any\r\npatents or other property right claims or to contest validity of any\r\nsuch claims; this section has the sole purpose of protecting the\r\nintegrity of the free software distribution system which is\r\nimplemented by public license practices.  Many people have made\r\ngenerous contributions to the wide range of software distributed\r\nthrough that system in reliance on consistent application of that\r\nsystem; it is up to the author/donor to decide if he or she is willing\r\nto distribute software through any other system and a licensee cannot\r\nimpose that choice.\r\n\r\nThis section is intended to make thoroughly clear what is believed to\r\nbe a consequence of the rest of this License.\r\n\r\n  12. If the distribution and/or use of the Library is restricted in\r\ncertain countries either by patents or by copyrighted interfaces, the\r\noriginal copyright holder who places the Library under this License may add\r\nan explicit geographical distribution limitation excluding those countries,\r\nso that distribution is permitted only in or among countries not thus\r\nexcluded.  In such case, this License incorporates the limitation as if\r\nwritten in the body of this License.\r\n\r\n  13. The Free Software Foundation may publish revised and/or new\r\nversions of the Lesser General Public License from time to time.\r\nSuch new versions will be similar in spirit to the present version,\r\nbut may differ in detail to address new problems or concerns.\r\n\r\nEach version is given a distinguishing version number.  If the Library\r\nspecifies a version number of this License which applies to it and\r\n\"any later version\", you have the option of following the terms and\r\nconditions either of that version or of any later version published by\r\nthe Free Software Foundation.  If the Library does not specify a\r\nlicense version number, you may choose any version ever published by\r\nthe Free Software Foundation.\r\n\f\r\n  14. If you wish to incorporate parts of the Library into other free\r\nprograms whose distribution conditions are incompatible with these,\r\nwrite to the author to ask for permission.  For software which is\r\ncopyrighted by the Free Software Foundation, write to the Free\r\nSoftware Foundation; we sometimes make exceptions for this.  Our\r\ndecision will be guided by the two goals of preserving the free status\r\nof all derivatives of our free software and of promoting the sharing\r\nand reuse of software generally.\r\n\r\n\t\t\t    NO WARRANTY\r\n\r\n  15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO\r\nWARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW.\r\nEXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR\r\nOTHER PARTIES PROVIDE THE LIBRARY \"AS IS\" WITHOUT WARRANTY OF ANY\r\nKIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE\r\nIMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR\r\nPURPOSE.  THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE\r\nLIBRARY IS WITH YOU.  SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME\r\nTHE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION.\r\n\r\n  16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN\r\nWRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY\r\nAND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU\r\nFOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR\r\nCONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE\r\nLIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING\r\nRENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A\r\nFAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF\r\nSUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH\r\nDAMAGES.\r\n\r\n\t\t     END OF TERMS AND CONDITIONS\r\n\f\r\n           How to Apply These Terms to Your New Libraries\r\n\r\n  If you develop a new library, and you want it to be of the greatest\r\npossible use to the public, we recommend making it free software that\r\neveryone can redistribute and change.  You can do so by permitting\r\nredistribution under these terms (or, alternatively, under the terms of the\r\nordinary General Public License).\r\n\r\n  To apply these terms, attach the following notices to the library.  It is\r\nsafest to attach them to the start of each source file to most effectively\r\nconvey the exclusion of warranty; and each file should have at least the\r\n\"copyright\" line and a pointer to where the full notice is found.\r\n\r\n    <one line to give the library's name and a brief idea of what it does.>\r\n    Copyright (C) <year>  <name of author>\r\n\r\n    This library is free software; you can redistribute it and/or\r\n    modify it under the terms of the GNU Lesser General Public\r\n    License as published by the Free Software Foundation; either\r\n    version 2 of the License, or (at your option) any later version.\r\n\r\n    This library is distributed in the hope that it will be useful,\r\n    but WITHOUT ANY WARRANTY; without even the implied warranty of\r\n    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU\r\n    Lesser General Public License for more details.\r\n\r\n    You should have received a copy of the GNU Lesser General Public\r\n    License along with this library; if not, write to the Free Software\r\n    Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n\r\nAlso add information on how to contact you by electronic and paper mail.\r\n\r\nYou should also get your employer (if you work as a programmer) or your\r\nschool, if any, to sign a \"copyright disclaimer\" for the library, if\r\nnecessary.  Here is a sample; alter the names:\r\n\r\n  Yoyodyne, Inc., hereby disclaims all copyright interest in the\r\n  library `Frob' (a library for tweaking knobs) written by James Random Hacker.\r\n\r\n  <signature of Ty Coon>, 1 April 1990\r\n  Ty Coon, President of Vice\r\n\r\nThat's all there is to it!\r\n\r\n\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/LUSOL_Overview.txt",
    "content": "            Notes for Contribution of LUSOL to COIN-OR\r\n                            May 2004\r\n\r\nIntroduction\r\n============\r\n\r\nLUSOL maintains sparse LU factors of a square or rectangular sparse matrix.  It includes a Basis Factorization Package (BFP) suitable for implementing simplex and reduced-gradient methods for optimization.  It is a set of  routines written in ANSI C (adapted from the original Fortran 77 version).\r\n\r\nLUSOL includes the following features:\r\n\r\n-  A Markowitz-based sparse LU factorization for square,\r\n   rectangular and possibly singular matrices.\r\n\r\n-  Three options for balancing sparsity and stability:\r\n   Threshold Partial/Rook/Complete Pivoting (TPP, TRP, TCP).\r\n\r\n-  Rank-revealing properties.  TRP and TCP are intended for detecting singularities.\r\n\r\n-  Dynamic storage allocation (C version only).\r\n\r\n-  Stable column replacement as in the method of Bartels and Golub.\r\n\r\n-  Other stable updates: add, replace, or delete row or column\r\n   (currently F77 version only).\r\n\r\n-  Implementation into an easy-to-use BFP API (C version only).\r\n\r\n\r\nImplementation\r\n==============\r\n\r\nThe Factor routine is similar to the classical Markowitz routines MA28 and LA05 in the Harwell Subroutine Library. The source matrix nonzeros are stored column-wise with the largest entry at the top of each column.  Internally, the structure is also accessible row-wise.  All entries in a particular column or row are held in contiguous storage.  Fill is accommodated by moving a column or row to the beginning of free storage. Occasional compressions recover storage.  This scheme is effective for column-oriented TPP.  When the remaining matrix reaches a specified density, the factors are completed using dense processing.\r\n\r\nTRP uses an additional vector of storage to maintain the largest element in each remaining row.\r\n\r\nTCP uses a heap structure to hold the largest element in each column.  The largest element in the remaining matrix is then available at the top of the heap.\r\n\r\nThe final L is stored column-wise (and never changed).  The final U is stored row-wise as a triangular or trapezoidal sparse matrix.\r\n\r\nColumn replacements are implemented using a forward sweep of 2-by-2 stabilized elimination matrices.  L is updated in product form.  U is updated explicitly.\r\n\r\nThe other updates use either forward or backward sweeps. They tend to generate more nonzeros than column replacement.\r\n\r\nBoth the F77 and C versions contain extensive comments, method and implementational information as part of the code.\r\n\r\nThe C version contains a record-based wrapper for the data.  Function calls have been simplified by including references to this structure.  New maintenance routines enable dynamic instance creation and destruction, and  simplifies access to the most frequently used functions.  The LUSOL C library is multi-instance and fully re-entrant.  All control and output parameters have been given long descriptive names for usability. \r\n\r\n\r\nBenefits\r\n========\r\n\r\nRank-revealing properties and rectangular factors (and updates) have not previously been available in sparse LU software.  With sensible parameter settings and reasonably scaled data, all routines are numerically stable.  The updates may be called hundreds of times, and the decision to refactorize can be based on sparsity considerations alone.\r\n\r\nIn the Factor routine, rook pivoting (TRP) gives reliable rank determination without catastrophic degradation in sparsity or speed.  Complete pivoting (TCP) is included for moderate-sized matrices and for checking pathological cases (but the factors tend to be substantially more dense).\r\n\r\nTo conserve storage, one may request only the row and column pivot orders.  The factors are discarded as they are computed.  This is useful for basis repair, or for selecting a basis from a rectangular matrix.\r\n\r\n\r\nKnown Inefficiencies\r\n====================\r\n\r\nLUSOL is usually efficient on sparse matrices with dimensions up to about 100,000 (but not millions).\r\n\r\nIn the Factor routine, row and column lists must be updated each time a row and column is eliminated.  Deleting the pivot row and column is inefficient if the original matrix contains unusually dense rows or columns.  For TPP, dense columns could be kept aside and incorporated at the end via updates (but dense rows remain a difficulty).  For TRP and TCP, all rows and columns must be present to achieve the required numerical properties.\r\n\r\nFor TRP, the current bottleneck is updating the vector containing the largest element in each row.  One solution would be to include the matrix nonzeros in the row structure (but this carries its own cost).\r\n\r\nFor TCP, the heap structure is already efficient, but the dense factors (and the extended searching for acceptable pivots) are unavoidable expenses.\r\n\r\nThe triangular Solve routines do not take full of advantage of sparse right-hand sides.  Gilbert and Peierls have shown how to solve Lx = (sparse b) efficiently if L is stored column-wise.  Their approach could therefore be implemented in LUSOL for solves with L and U(transpose).  Solves with L(transpose) and U would need a second copy of L and U. \r\n\r\n\r\nOriginal Reference\r\n==================\r\n\r\nP. E. Gill, W. Murray, M. A. Saunders and M. H. Wright, Maintaining LU factors of a general sparse matrix, Linear Algebra and its Applications 88/89, 239-270 (1987).\r\n\r\n\r\nMaintainers\r\n===========\r\n\r\nF77 version: Michael Saunders (saunders@stanford.edu).\r\nC version: Kjell Eikland (kjell.eikland@broadpark.no).\r\n\r\n\r\nContributors\r\n============\r\n\r\nPhilip Gill, Walter Murray, Margaret Wright, Michael O'Sullivan.\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/LUSOL_README.txt",
    "content": "README.TXT for LUSOL - Advanced LU solver with enhanced numerical stability options\r\n-----------------------------------------------------------------------------------\r\n\r\nLUSOL - pronounced \"L-U-SOL\" - was developed by Prof. Michael Saunders at the \r\nStanford (University) Optimization Laboratory over a period of 2 decades of \r\nprogressive improvements.  It is a particularly capable matrix factorization system\r\nand includes sparsity-preserving column updates and equation solving.  It is\r\ntherefore particularly well suited to be part of a system to solve tough mathematical \r\nprogramming problems.  Further details can be found in the file \"LUSOL-overview.txt.\"\r\n\r\nA big step has been made in converting the original Fortran code into a much more\r\neasily accessible and modularized system based on ANSI C as part of the release of\r\nlp_solve v5.  LUSOL is fully implemented as a \"Basis Factorization Package\", BFP in \r\nlp_solve and is the BFP of choice for large and complex models, if not all.  As part\r\nof the conversion to C, processor optimized BLAS functionality has been enabled, and\r\nfuture enhancements to LUSOL may make increasing use of this, ensuring top performance. \r\n\r\nFor the lp_solve release of LUSOL, a stand-alone equation solving system has also been\r\ndeveloped.  A pre-compiled Windows command-line executable version is included in the\r\nstandard distribution of LUSOL. In addition, the program options illustrate several \r\nadvanced uses of LUSOL.  The equation solving utility features reading of standard \r\nmatrix files in the Harwell-Boeing, MatrixMarket and text formats.  Sample matrix \r\nmodels are provided for Harwell-Boeing (.RUA) and MatrixMarket (.mtx).  \r\n\r\nThe LUSOL code is released under the GNU Lesser General Public Licence.  Confer the \r\nfile \"Licence_LGPL.txt\" for the full terms of this licence.  These terms make lp_solve\r\nand LUSOL available and distributable on equal licencing terms.  It is expected that\r\nLUSOL will have an official repository in the near future, but the LUSOL archive at\r\nthe Yahoo lp_solve group will be an official copy and the formal repository until\r\nfurther notice.\r\n\r\n\r\nKjell Eikland\r\n14 July 2004\r\nOslo, Norway\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/Row-based L0.txt",
    "content": "Traditional column-based L0\r\n---------------------------\r\nV[  3] = V[  3] + L[1,3]*V[  1]\r\n0.9375 = -1.26316 + -0.789474*-2.7875\r\nV[  2] = V[  2] + L[1,2]*V[  1]\r\n-0.846875 =  -0.15 +   0.25*-2.7875\r\nV[  2] = V[  2] + L[3,2]*V[  3]\r\n-0.925 = -0.846875 + -0.0833333*0.9375\r\nV[  4] = V[  4] + L[3,4]*V[  3]\r\n-0.3125 =      0 + -0.333333*0.9375\r\n\r\nSolution vector\r\n            -2.7875             -0.925             0.9375            -0.3125\r\n\r\n\r\nNew row-based L0\r\n----------------\r\nV[  4] = V[  4] + L[3,4]*V[  3]\r\n0.421053 =      0 + -0.333333*-1.26316\r\nV[  2] = V[  2] + L[3,2]*V[  3]\r\n-0.0447368 =  -0.15 + -0.0833333*-1.26316\r\nV[  2] = V[  2] + L[1,2]*V[  1]\r\n-0.741612 = -0.0447368 +   0.25*-2.7875\r\nV[  3] = V[  3] + L[1,3]*V[  1]\r\n0.9375 = -1.26316 + -0.789474*-2.7875\r\n\r\nSolution vector\r\n            -2.7875          -0.741612             0.9375           0.421053\r\n\r\n\r\nL0 generated\r\n----------------\r\n         0         0         0         0\r\n         0         0         0         0\r\n         0      0.25 -0.789474         0\r\n         0-0.0833333         0 -0.333333"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/Victoria1850.RUA",
    "content": "1UNSYMMETRIC MATRIX             MAHINDAS ST ERTAR             24OCT84   MAHINDAS\r\n          2488           126           769          1537            56          \r\nRUA                     1258          1258          7682             0          \r\n(10I8)          (10I8)          (1P5D16.8)          (1P5D16.8)                  \r\nM                         55           162                                      \r\n       1      37      74     111     148     185     222     259     296     317\r\n     337     351     366     378     394     407     422     434     444     456\r\n     466     478     486     497     511     526     541     556     572     589\r\n     611     624     638     655     670     683     697     709     720     730\r\n     742     756     777     789     801     815     827     852     862     874\r\n     881     885     889     891     893     895     897     899     901     903\r\n     905     907     909     911     913     915     917     919     921     923\r\n     925     927     929     931     933     935     937     939     941     943\r\n     945     947     949     951     953     955     957     959     961     963\r\n     965     967     969     971     973     975     977     979     981     983\r\n     985     986     987     989     991     993     995     997     999    1001\r\n    1003    1005    1007    1009    1011    1013    1015    1017    1019    1021\r\n    1023    1025    1027    1029    1031    1033    1035    1037    1039    1041\r\n    1043    1045    1047    1049    1051    1053    1055    1057    1059    1061\r\n    1063    1065    1067    1069    1071    1073    1075    1077    1079    1081\r\n    1083    1085    1087    1089    1091    1093    1095    1097    1099    1101\r\n    1103    1105    1107    1109    1111    1113    1115    1117    1119    1121\r\n    1123    1125    1127    1129    1131    1133    1135    1137    1139    1141\r\n    1143    1145    1147    1149    1151    1153    1155    1157    1159    1161\r\n    1163    1165    1167    1169    1171    1173    1175    1177    1179    1181\r\n    1183    1185    1187    1189    1191    1193    1195    1197    1199    1201\r\n    1203    1205    1207    1209    1211    1213    1215    1217    1219    1221\r\n    1223    1225    1227    1229    1231    1233    1235    1237    1239    1241\r\n    1243    1245    1247    1249    1251    1253    1255    1257    1259    1261\r\n    1263    1265    1267    1269    1271    1273    1275    1277    1279    1281\r\n    1283    1285    1287    1289    1291    1293    1295    1297    1299    1301\r\n    1303    1305    1307    1309    1311    1313    1315    1317    1319    1321\r\n    1323    1325    1327    1329    1331    1333    1335    1337    1339    1341\r\n    1343    1345    1347    1349    1351    1353    1355    1357    1359    1361\r\n    1363    1365    1367    1369    1371    1373    1375    1377    1379    1381\r\n    1383    1385    1387    1389    1391    1393    1395    1397    1399    1401\r\n    1403    1405    1407    1409    1411    1413    1415    1417    1419    1421\r\n    1423    1425    1427    1429    1431    1433    1435    1437    1439    1441\r\n    1443    1445    1447    1448    1449    1450    1452    1454    1455    1457\r\n    1458    1460    1462    1464    1466    1468    1469    1471    1473    1475\r\n    1477    1479    1481    1483    1485    1487    1488    1489    1491    1492\r\n    1493    1494    1496    1498    1500    1502    1504    1506    1508    1510\r\n    1512    1514    1516    1518    1520    1522    1524    1525    1526    1528\r\n    1530    1531    1533    1535    1536    1537    1538    1539    1540    1541\r\n    1543    1545    1547    1549    1550    1552    1554    1556    1558    1560\r\n    1561    1562    1564    1566    1568    1570    1572    1574    1576    1578\r\n    1579    1581    1583    1584    1585    1586    1588    1590    1592    1594\r\n    1596    1598    1600    1602    1604    1605    1607    1609    1611    1613\r\n    1615    1617    1619    1621    1623    1625    1627    1629    1630    1632\r\n    1634    1637    1640    1643    1646    1649    1652    1655    1658    1661\r\n    1664    1667    1670    1673    1676    1679    1682    1685    1688    1691\r\n    1694    1697    1700    1703    1706    1709    1712    1715    1718    1721\r\n    1724    1727    1730    1733    1736    1739    1742    1745    1748    1751\r\n    1754    1757    1760    1763    1766    1769    1772    1775    1778    1781\r\n    1784    1787    1790    1793    1796    1801    1806    1811    1816    1821\r\n    1826    1831    1832    1833    1834    1835    1836    1837    1838    1839\r\n    1840    1841    1842    1843    1844    1845    1846    1847    1848    1850\r\n    1851    1852    1853    1854    1855    1856    1857    1858    1859    1860\r\n    1861    1862    1863    1865    1866    1868    1870    1871    1872    1873\r\n    1875    1876    1877    1878    1879    1881    1882    1883    1885    1887\r\n    1888    1890    1891    1892    1894    1895    1896    1897    1898    1899\r\n    1900    1901    1902    1903    1904    1905    1906    1907    1908    1909\r\n    1910    1911    1912    1914    1915    1916    1917    1918    1919    1920\r\n    1922    1923    1924    1925    1926    1927    1928    1929    1930    1931\r\n    1932    1933    1934    1935    1936    1937    1938    1939    1940    1942\r\n    1943    1944    1945    1946    1947    1948    1949    1950    1951    1952\r\n    1954    1956    1958    1960    1962    1964    1966    1968    1970    1972\r\n    1974    1976    1978    1980    1982    1984    1986    1988    1990    1992\r\n    1994    1996    1998    2000    2002    2004    2006    2008    2010    2012\r\n    2014    2016    2018    2020    2022    2024    2026    2028    2030    2032\r\n    2034    2036    2038    2040    2042    2044    2046    2048    2050    2052\r\n    2054    2056    2058    2060    2062    2064    2066    2068    2070    2071\r\n    2073    2075    2077    2079    2081    2083    2085    2087    2089    2091\r\n    2093    2095    2097    2099    2101    2103    2105    2107    2109    2111\r\n    2113    2115    2117    2119    2121    2123    2125    2127    2129    2131\r\n    2133    2135    2137    2139    2140    2142    2144    2146    2147    2148\r\n    2149    2150    2151    2152    2153    2155    2156    2157    2166    2174\r\n    2181    2196    2199    2202    2205    2208    2211    2214    2217    2220\r\n    2223    2226    2229    2232    2235    2238    2241    2244    2247    2250\r\n    2253    2256    2259    2262    2265    2268    2271    2274    2277    2280\r\n    2283    2286    2289    2292    2295    2298    2301    2304    2307    2310\r\n    2313    2316    2319    2322    2325    2328    2331    2334    2337    2340\r\n    2343    2345    2347    2348    2442    2536    2630    2727    2824    2915\r\n    3014    3110    3208    3306    3323    3329    3338    3359    3367    3374\r\n    3380    3401    3407    3413    3419    3425    3431    3438    3445    3457\r\n    3464    3469    3477    3483    3511    3551    3572    3578    3587    3601\r\n    3610    3628    3667    3682    3688    3698    3720    3757    3763    3772\r\n    3871    3971    3979    4032    4037    4041    4045    4050    4055    4067\r\n    4079    4095    4104    4106    4114    4121    4126    4131    4136    4141\r\n    4149    4155    4160    4166    4171    4179    4184    4189    4195    4200\r\n    4207    4212    4221    4232    4238    4241    4246    4252    4271    4279\r\n    4300    4305    4310    4319    4325    4349    4386    4395    4397    4405\r\n    4420    4442    4444    4446    4448    4450    4452    4454    4456    4459\r\n    4461    4463    4666    4671    4676    4681    4686    4691    4696    4701\r\n    4706    4711    4716    4721    4726    4731    4736    4741    4746    4751\r\n    4756    4761    4766    4771    4776    4781    4786    4791    4796    4801\r\n    4806    4811    4816    4821    4826    4831    4836    4841    4846    4851\r\n    4856    4861    4866    4871    4876    4881    4886    4891    4896    4901\r\n    4906    4910    4914    4916    4918    4922    4926    4930    4934    4938\r\n    4942    4946    4950    4951    4952    4953    4954    4955    4956    4957\r\n    4958    4959    4960    4961    4962    4963    4964    4965    4966    4967\r\n    4968    4969    4970    4971    4972    4973    4974    4975    4976    4977\r\n    4978    4979    4980    4981    4982    4983    4984    4985    4986    4987\r\n    4988    4989    4990    4991    4992    4993    4994    4996    4998    5000\r\n    5055    5110    5112    5167    5169    5224    5279    5334    5389    5444\r\n    5446    5501    5556    5611    5666    5721    5776    5831    5886    5941\r\n    5943    5998    6053    6055    6057    6059    6114    6169    6224    6279\r\n    6334    6389    6444    6499    6554    6609    6664    6719    6774    6829\r\n    6884    6886    6888    6943    6998    7000    7055    7110    7112    7114\r\n    7116    7119    7122    7125    7128    7131    7133    7136    7139    7142\r\n    7145    7148    7151    7154    7157    7160    7163    7166    7169    7172\r\n    7175    7178    7181    7184    7186    7189    7192    7195    7198    7201\r\n    7204    7207    7210    7213    7216    7219    7222    7225    7228    7231\r\n    7234    7236    7239    7242    7245    7247    7250    7252    7254    7256\r\n    7258    7260    7263    7265    7267    7278    7315    7321    7329    7331\r\n    7333    7335    7337    7339    7341    7343    7345    7347    7349    7351\r\n    7353    7355    7357    7359    7361    7363    7365    7367    7369    7371\r\n    7373    7375    7377    7379    7381    7383    7385    7387    7389    7391\r\n    7393    7395    7397    7399    7401    7403    7405    7407    7409    7411\r\n    7413    7415    7417    7418    7419    7420    7421    7422    7423    7424\r\n    7426    7428    7430    7432    7434    7436    7438    7440    7442    7444\r\n    7446    7448    7450    7452    7454    7456    7458    7460    7462    7464\r\n    7466    7468    7470    7472    7474    7476    7478    7480    7482    7484\r\n    7486    7488    7490    7492    7494    7496    7498    7500    7502    7504\r\n    7506    7508    7510    7512    7514    7515    7516    7517    7518    7519\r\n    7520    7521    7523    7568    7569    7571    7573    7574    7577    7579\r\n    7634    7636    7637    7638    7639    7640    7641    7642    7643    7644\r\n    7645    7646    7647    7648    7649    7650    7651    7652    7653    7654\r\n    7655    7656    7657    7658    7659    7660    7661    7662    7663    7664\r\n    7665    7666    7667    7668    7669    7670    7671    7672    7673    7674\r\n    7675    7676    7677    7678    7679    7680    7681    7682    7683        \r\n       1      53     105     157     158     159     160     161     162     163\r\n     164     165     166     986     987     988     989     991     992     996\r\n     999    1003    1016    1017    1018    1029    1032    1033    1035    1200\r\n    1201    1202    1229    1231    1236    1242       2      54     106     167\r\n     168     169     170     171     172     173     174     175     176     986\r\n     987     988     989     990     991     992     996     999    1003    1016\r\n    1017    1018    1029    1032    1033    1035    1200    1201    1202    1229\r\n    1231    1236    1242       3      55     107     177     178     179     180\r\n     181     182     183     184     185     186     986     987     988     989\r\n     990     991     992     996     999    1003    1016    1017    1018    1029\r\n    1032    1033    1035    1200    1201    1202    1229    1231    1236    1242\r\n       4      56     108     187     188     189     190     191     192     193\r\n     194     195     196     986     987     988     989     990     991     992\r\n     996     999    1003    1016    1017    1018    1029    1032    1033    1035\r\n    1200    1201    1202    1229    1231    1236    1242       5      57     109\r\n     197     198     199     200     201     202     203     204     205     206\r\n     986     987     988     989     990     991     992     996     999    1003\r\n    1016    1017    1018    1029    1032    1033    1035    1200    1201    1202\r\n    1229    1231    1236    1242       6      58     110     207     208     209\r\n     210     211     212     213     214     215     216     986     987     988\r\n     989     990     991     992     996     999    1003    1016    1017    1018\r\n    1029    1032    1033    1035    1200    1201    1202    1229    1231    1236\r\n    1242       7      59     111     217     218     219     220     221     222\r\n     223     224     225     226     986     987     988     989     990     991\r\n     992     996     999    1003    1016    1017    1018    1029    1032    1033\r\n    1035    1200    1201    1202    1229    1231    1236    1242       8      60\r\n     112     227     228     229     230     231     232     233     234     235\r\n     236     986     987     988     989     990     991     992     996     999\r\n    1003    1016    1017    1018    1029    1032    1033    1035    1200    1201\r\n    1202    1229    1231    1236    1242       9      61     113     237     986\r\n     987     989     994    1016    1017    1018    1020    1024    1029    1032\r\n    1033    1035    1199    1231    1237    1242      10      62     114     238\r\n     988     989     990     992    1021    1024    1025    1032    1033    1035\r\n    1202    1203    1234    1236    1237    1238      11      63     115     239\r\n     993     999    1016    1017    1024    1032    1033    1035    1206    1237\r\n      12      64     116     240     993     995    1001    1016    1024    1032\r\n    1033    1035    1206    1212    1237      13      65     117     241    1024\r\n    1025    1029    1031    1032    1033    1035    1237      14      66     118\r\n     242     995     999    1016    1017    1022    1024    1029    1032    1033\r\n    1035    1214    1237      15      67     119     243     992    1021    1024\r\n    1029    1032    1033    1035    1205    1237      16      68     120     244\r\n    1016    1023    1024    1029    1032    1033    1035    1229    1236    1237\r\n    1242      17      69     121     245    1017    1023    1024    1028    1032\r\n    1033    1035    1237      18      70     122     246    1003    1016    1017\r\n    1032    1033    1035      19      71     123     247    1017    1023    1024\r\n    1032    1033    1035    1219    1237      20      72     124     248    1016\r\n    1024    1032    1033    1035    1237      21      73     125     249    1025\r\n    1027    1028    1029    1032    1033    1035    1221      22      74     126\r\n     250    1028    1032    1033    1035      23      75     127     251    1024\r\n    1028    1032    1033    1035    1223    1237      24      76     128     252\r\n    1017    1024    1028    1029    1032    1033    1035    1231    1237    1241\r\n      25      77     129     253     999    1017    1023    1024    1028    1029\r\n    1032    1033    1035    1225    1237      26      78     130     254    1017\r\n    1018    1023    1024    1028    1029    1032    1033    1035    1226    1237\r\n      27      79     131     255    1017    1023    1024    1025    1028    1029\r\n    1031    1032    1033    1035    1237      28      80     132     256     999\r\n    1017    1023    1024    1028    1032    1033    1035    1228    1229    1236\r\n    1237      29      81     133     257     999    1016    1017    1021    1024\r\n    1028    1029    1032    1033    1035    1229    1236    1237      30      82\r\n     134     258     993     995     998     999    1016    1017    1022    1024\r\n    1032    1033    1035    1206    1211    1212    1230    1231    1236    1237\r\n      31      83     135     259    1017    1018    1024    1029    1032    1033\r\n    1035    1231    1237      32      84     136     260     994     995    1017\r\n    1021    1024    1029    1032    1033    1035    1237      33      85     137\r\n     261     990     992     994     996    1003    1017    1020    1021    1024\r\n    1032    1033    1035    1237      34      86     138     262     992     994\r\n    1020    1024    1026    1032    1033    1035    1203    1234    1237      35\r\n      87     139     263     995     999    1017    1024    1032    1033    1035\r\n    1235    1237      36      88     140     264     996    1017    1023    1024\r\n    1029    1032    1033    1035    1236    1237      37      89     141     265\r\n    1023    1024    1029    1031    1032    1033    1035    1237      38      90\r\n     142     266    1024    1025    1029    1032    1033    1035    1237      39\r\n      91     143     267    1024    1026    1032    1033    1035    1237      40\r\n      92     144     268    1025    1027    1029    1031    1032    1033    1035\r\n    1240      41      93     145     269    1016    1024    1028    1029    1031\r\n    1032    1033    1035    1237    1241      42      94     146     270     994\r\n     996    1003    1016    1017    1018    1020    1021    1022    1024    1027\r\n    1028    1032    1033    1035    1237    1242      43      95     147     271\r\n    1010    1024    1029    1032    1033    1035    1223    1237      44      96\r\n     148     272    1017    1024    1032    1033    1035    1039    1223    1237\r\n      45      97     149     273    1017    1024    1028    1029    1032    1033\r\n    1035    1237    1241    1242      46      98     150     274    1003    1017\r\n    1018    1023    1032    1033    1035    1236      47      99     151     275\r\n    1000    1010    1014    1016    1017    1018    1023    1025    1028    1029\r\n    1030    1032    1033    1035    1213    1227    1229    1231    1236    1238\r\n    1241      48     100     152     276    1003    1017    1032    1033    1216\r\n    1236      49     101     153     277    1014    1016    1017    1025    1030\r\n    1032    1033    1035      50     102     154     278    1032    1033    1250\r\n      51     103     155     279      52     104     156     280       1    1094\r\n       2    1094       3    1094       4    1094       5    1094       6    1094\r\n       7    1094       8    1094       9    1094      10    1094      11    1094\r\n      12    1094      13    1094      14    1094      15    1094      16    1094\r\n      17    1094      18    1094      19    1094      20    1094      21    1094\r\n      22    1094      23    1094      24    1094      25    1094      26    1094\r\n      27    1094      28    1094      29    1094      30    1094      31    1094\r\n      32    1094      33    1094      34    1094      35    1094      36    1094\r\n      37    1094      38    1094      39    1094      40    1094      41    1094\r\n      42    1094      43    1094      44    1094      45    1094      46    1094\r\n      47    1094      48    1094      49      50      51    1094      52    1094\r\n      53    1095      54    1096      55    1097      56    1098      57    1099\r\n      58    1100      59    1101      60    1102      61    1103      62    1104\r\n      63    1105      64    1106      65    1107      66    1108      67    1109\r\n      68    1110      69    1111      70    1112      71    1113      72    1114\r\n      73    1115      74    1116      75    1117      76    1118      77    1119\r\n      78    1120      79    1121      80    1122      81    1123      82    1124\r\n      83    1125      84    1126      85    1127      86    1128      87    1129\r\n      88    1130      89    1131      90    1132      91    1133      92    1134\r\n      93    1135      94    1136      95    1137      96    1138      97    1139\r\n      98    1140      99    1141     100    1142     101    1143     102    1144\r\n     103    1145     104    1146     105    1147     106    1148     107    1149\r\n     108    1150     109    1151     110    1152     111    1153     112    1154\r\n     113    1155     114    1156     115    1157     116    1158     117    1159\r\n     118    1160     119    1161     120    1162     121    1163     122    1164\r\n     123    1165     124    1166     125    1167     126    1168     127    1169\r\n     128    1170     129    1171     130    1172     131    1173     132    1174\r\n     133    1175     134    1176     135    1177     136    1178     137    1179\r\n     138    1180     139    1181     140    1182     141    1183     142    1184\r\n     143    1185     144    1186     145    1187     146    1188     147    1189\r\n     148    1190     149    1191     150    1192     151    1193     152    1194\r\n     153    1195     154    1196     155    1197     156    1198     157    1040\r\n     158    1041     159    1042     160    1043     161    1044     162    1045\r\n     163    1046     164    1047     165    1048     166    1049     167    1040\r\n     168    1041     169    1042     170    1043     171    1044     172    1045\r\n     173    1046     174    1047     175    1048     176    1049     177    1040\r\n     178    1041     179    1042     180    1043     181    1044     182    1045\r\n     183    1046     184    1047     185    1048     186    1049     187    1040\r\n     188    1041     189    1042     190    1043     191    1044     192    1045\r\n     193    1046     194    1047     195    1048     196    1049     197    1040\r\n     198    1041     199    1042     200    1043     201    1044     202    1045\r\n     203    1046     204    1047     205    1048     206    1049     207    1040\r\n     208    1041     209    1042     210    1043     211    1044     212    1045\r\n     213    1046     214    1047     215    1048     216    1049     217    1040\r\n     218    1041     219    1042     220    1043     221    1044     222    1045\r\n     223    1046     224    1047     225    1048     226    1049     227    1040\r\n     228    1041     229    1042     230    1043     231    1044     232    1045\r\n     233    1046     234    1047     235    1048     236    1049     237    1050\r\n     238    1051     239    1052     240    1053     241    1054     242    1055\r\n     243    1056     244    1057     245    1058     246    1059     247    1060\r\n     248    1061     249    1062     250    1063     251    1064     252    1065\r\n     253    1066     254    1067     255    1068     256    1069     257    1070\r\n     258    1071     259    1072     260    1073     261    1074     262    1075\r\n     263    1076     264    1077     265    1078     266    1079     267    1080\r\n     268    1081     269    1082     270    1083     271    1084     272    1085\r\n     273    1086     274    1087     275    1088     276    1089     277    1090\r\n     278    1091     279    1092     280    1093     285     286     287     288\r\n     989     289     990     290     291     992     292     293     994     294\r\n     995     295     996     296     997     297     998     298     299    1000\r\n     300    1001     301    1002     302    1003     303    1004     304    1005\r\n     305    1006     306    1007     307    1008     308     309     310    1011\r\n     311     312     313     314    1015     315    1016     316    1017     317\r\n    1018     318    1019     319    1020     320    1021     321    1022     322\r\n    1023     323    1024     324    1025     325    1026     326    1027     327\r\n    1028     328    1029     329     330     331    1032     332    1033     333\r\n     334    1035     335    1036     336     337     338     339     340     341\r\n     342    1202     343    1203     344    1204     345    1205     346     347\r\n    1207     348    1208     349    1209     350    1210     351    1211     352\r\n     353     354    1214     355    1215     356    1216     357    1217     358\r\n    1218     359    1219     360    1220     361    1221     362     363    1223\r\n     364    1224     365     366     367     368    1228     369    1229     370\r\n    1230     371    1231     372    1232     373    1233     374    1234     375\r\n    1235     376    1236     377     378    1238     379    1239     380    1240\r\n     381    1241     382    1242     383    1243     384    1244     385    1245\r\n     386    1246     387    1247     388    1248     389    1249     390     391\r\n    1251     392    1252     285     339     447     286     340     448     287\r\n     341     449     288     342     450     289     343     451     290     344\r\n     452     291     345     453     292     346     454     293     347     455\r\n     294     348     456     295     349     457     296     350     458     297\r\n     351     459     298     352     460     299     353     461     300     354\r\n     462     301     355     463     302     356     464     303     357     465\r\n     304     358     466     305     359     467     306     360     468     307\r\n     361     469     308     362     470     309     363     471     310     364\r\n     472     311     365     473     312     366     474     313     367     475\r\n     314     368     476     315     369     477     316     370     478     317\r\n     371     479     318     372     480     319     373     481     320     374\r\n     482     321     375     483     322     376     484     323     377     485\r\n     324     378     486     325     379     487     326     380     488     327\r\n     381     489     328     382     490     329     383     491     330     384\r\n     492     331     385     493     332     386     494     333     387     495\r\n     334     388     496     335     389     497     336     390     498     337\r\n     391     499     338     392     500     501     986    1032    1033    1254\r\n     505     990    1032    1033    1254     508     993    1032    1033    1254\r\n     514     999    1032    1033    1254     516    1001    1032    1033    1254\r\n     534    1019    1032    1033    1254     546    1031    1032    1033    1254\r\n     555     556     557     558     559     560     561     562     563     564\r\n     565     566     567     568     569     570     571     572    1003     573\r\n     574     575     576     577     578     579     580     581     582     583\r\n     584     585     586    1017     587     588    1019     589    1020     590\r\n     591     592     593    1024     594     595     596     597     598    1029\r\n     599     600     601    1032     602    1033     603     604    1035     605\r\n     606     607    1038     608     609     610     611     612     613     614\r\n     615     616     617     618     619     620     621     622     623     624\r\n     625     626    1216     627     628     629     630     631     632     633\r\n    1223     634     635     636     637     638     639     640     641     642\r\n     643     644     645     646     647     648     649     650     651     652\r\n    1242     653     654     655     656     657     658     659     660     661\r\n     662     986    1040     987    1041     988    1042     989    1043     990\r\n    1044     991    1045     992    1046     993    1047     994    1048     995\r\n    1049     996    1050     997    1051     998    1052     999    1053    1000\r\n    1054    1001    1055    1002    1056    1003    1057    1004    1058    1005\r\n    1059    1006    1060    1007    1061    1008    1062    1009    1063    1010\r\n    1064    1011    1065    1012    1066    1013    1067    1014    1068    1015\r\n    1069    1016    1070    1017    1071    1018    1072    1019    1073    1020\r\n    1074    1021    1075    1022    1076    1023    1077    1024    1078    1025\r\n    1079    1026    1080    1027    1081    1028    1082    1029    1083    1030\r\n    1084    1031    1085    1032    1086    1033    1087    1034    1088    1035\r\n    1089    1036    1090    1037    1091    1038    1092    1039    1093    1199\r\n    1253    1200    1253    1201    1253    1202    1253    1203    1253    1204\r\n    1205    1253    1206    1253    1207    1253    1208    1253    1209    1253\r\n    1210    1253    1211    1253    1212    1253    1213    1253    1214    1253\r\n    1215    1253    1216    1253    1217    1253    1218    1253    1219    1253\r\n    1220    1253    1221    1253    1222    1253    1223    1253    1224    1253\r\n    1225    1253    1226    1253    1227    1253    1228    1253    1229    1253\r\n    1230    1253    1231    1253    1232    1253    1233    1253    1234    1253\r\n    1235    1253    1236    1253    1237    1253    1238    1253    1239    1240\r\n    1253    1241    1253    1242    1253    1243    1244    1245    1246    1247\r\n    1248    1249    1250    1253    1251    1252     281    1011    1032    1033\r\n    1034    1224    1231    1241    1242     282    1011    1032    1033    1034\r\n    1224    1241    1242     283    1011    1032    1033    1034    1224    1241\r\n     284    1009    1011    1012    1013    1028    1032    1033    1034    1221\r\n    1222    1224    1225    1241    1242     281     925     977     281     926\r\n     977     281     927     977     281     928     977     281     929     977\r\n     281     930     977     281     931     977     281     932     977     282\r\n     933     977     282     934     977     282     935     977     282     936\r\n     977     282     937     977     282     938     977     282     939     977\r\n     282     940     977     282     941     977     282     942     977     282\r\n     943     977     282     944     977     282     945     977     282     946\r\n     977     282     947     977     282     948     977     282     949     977\r\n     282     950     977     282     951     977     282     952     977     282\r\n     953     977     282     954     977     282     955     977     282     956\r\n     977     282     957     977     282     958     977     282     959     977\r\n     282     960     977     282     961     977     282     962     977     282\r\n     963     977     282     964     977     282     965     977     282     966\r\n     977     283     967     977     283     968     977     284     969     978\r\n     284     970     979     284     971     980     284     972     981     284\r\n     973     982     974     983     975     984     976     157     158     159\r\n     160     161     162     163     164     165     166     167     168     169\r\n     170     171     172     173     174     175     176     177     178     179\r\n     180     181     182     183     184     185     186     187     188     189\r\n     190     191     192     193     194     195     196     197     198     199\r\n     200     201     202     203     204     205     206     207     208     209\r\n     210     211     212     213     214     215     216     217     218     219\r\n     220     221     222     223     224     225     226     227     228     229\r\n     230     231     232     233     234     235     236     339     393     664\r\n     665     666     667     668     669     670     671     672     774     986\r\n    1199     157     158     159     160     161     162     163     164     165\r\n     166     167     168     169     170     171     172     173     174     175\r\n     176     177     178     179     180     181     182     183     184     185\r\n     186     187     188     189     190     191     192     193     194     195\r\n     196     197     198     199     200     201     202     203     204     205\r\n     206     207     208     209     210     211     212     213     214     215\r\n     216     217     218     219     220     221     222     223     224     225\r\n     226     227     228     229     230     231     232     233     234     235\r\n     236     340     394     664     665     666     667     668     669     670\r\n     671     672     775     987    1200     157     158     159     160     161\r\n     162     163     164     165     166     167     168     169     170     171\r\n     172     173     174     175     176     177     178     179     180     181\r\n     182     183     184     185     186     187     188     189     190     191\r\n     192     193     194     195     196     197     198     199     200     201\r\n     202     203     204     205     206     207     208     209     210     211\r\n     212     213     214     215     216     217     218     219     220     221\r\n     222     223     224     225     226     227     228     229     230     231\r\n     232     233     234     235     236     341     395     664     665     666\r\n     667     668     669     670     671     673     776     988    1201     157\r\n     158     159     160     161     162     163     164     165     166     167\r\n     168     169     170     171     172     173     174     175     176     177\r\n     178     179     180     181     182     183     184     185     186     187\r\n     188     189     190     191     192     193     194     195     196     197\r\n     198     199     200     201     202     203     204     205     206     207\r\n     208     209     210     211     212     213     214     215     216     217\r\n     218     219     220     221     222     223     224     225     226     227\r\n     228     229     230     231     232     233     234     235     236     288\r\n     342     396     664     665     666     667     668     669     670     671\r\n     672     673     777     989    1202    1256     157     158     159     160\r\n     161     162     163     164     165     166     167     168     169     170\r\n     171     172     173     174     175     176     177     178     179     180\r\n     181     182     183     184     185     186     187     188     189     190\r\n     191     192     193     194     195     196     197     198     199     200\r\n     201     202     203     204     205     206     207     208     209     210\r\n     211     212     213     214     215     216     217     218     219     220\r\n     221     222     223     224     225     226     227     228     229     230\r\n     231     232     233     234     235     236     289     343     397     664\r\n     665     666     667     668     669     670     671     673     696     778\r\n     990    1203    1256     157     158     159     160     161     162     163\r\n     164     165     166     167     168     169     170     171     172     173\r\n     174     175     176     177     178     179     180     181     182     183\r\n     184     185     186     187     188     189     190     191     192     193\r\n     194     195     196     197     198     199     200     201     202     203\r\n     204     205     206     207     208     209     210     211     212     213\r\n     214     215     216     217     218     219     220     221     222     223\r\n     224     225     226     227     228     229     230     231     232     233\r\n     234     235     236     344     398     664     665     666     667     668\r\n     669     670     671     779     157     158     159     160     161     162\r\n     163     164     165     166     167     168     169     170     171     172\r\n     173     174     175     176     177     178     179     180     181     182\r\n     183     184     185     186     187     188     189     190     191     192\r\n     193     194     195     196     197     198     199     200     201     202\r\n     203     204     205     206     207     208     209     210     211     212\r\n     213     214     215     216     217     218     219     220     221     222\r\n     223     224     225     226     227     228     229     230     231     232\r\n     233     234     235     236     291     345     399     664     665     666\r\n     667     668     669     670     671     673     678     696     697     780\r\n     992    1205    1256     157     158     159     160     161     162     163\r\n     164     165     166     167     168     169     170     171     172     173\r\n     174     175     176     177     178     179     180     181     182     183\r\n     184     185     186     187     188     189     190     191     192     193\r\n     194     195     196     197     198     199     200     201     202     203\r\n     204     205     206     207     208     209     210     211     212     213\r\n     214     215     216     217     218     219     220     221     222     223\r\n     224     225     226     227     228     229     230     231     232     233\r\n     234     235     236     346     400     664     665     666     667     668\r\n     669     670     671     674     675     693     781     993    1206     157\r\n     158     159     160     161     162     163     164     165     166     167\r\n     168     169     170     171     172     173     174     175     176     177\r\n     178     179     180     181     182     183     184     185     186     187\r\n     188     189     190     191     192     193     194     195     196     197\r\n     198     199     200     201     202     203     204     205     206     207\r\n     208     209     210     211     212     213     214     215     216     217\r\n     218     219     220     221     222     223     224     225     226     227\r\n     228     229     230     231     232     233     234     235     236     293\r\n     347     401     664     665     666     667     668     669     670     671\r\n     672     695     696     697     705     782    1256     157     158     159\r\n     160     161     162     163     164     165     166     167     168     169\r\n     170     171     172     173     174     175     176     177     178     179\r\n     180     181     182     183     184     185     186     187     188     189\r\n     190     191     192     193     194     195     196     197     198     199\r\n     200     201     202     203     204     205     206     207     208     209\r\n     210     211     212     213     214     215     216     217     218     219\r\n     220     221     222     223     224     225     226     227     228     229\r\n     230     231     232     233     234     235     236     294     348     402\r\n     664     665     666     667     668     669     670     671     675     677\r\n     693     695     698     783    1256     295     349     403     664     665\r\n     666     667     668     669     670     671     672     696     699     705\r\n     784    1256     296     350     404     673     785    1256     297     351\r\n     405     674     693     786     998    1211    1256     352     406     664\r\n     665     666     667     668     669     670     671     674     675     677\r\n     688     691     692     693     698     787     999    1212     353     407\r\n     676     710     788    1000    1213    1256     300     354     408     675\r\n     677     789    1256     301     355     409     678     790    1256     302\r\n     356     410     664     665     666     667     668     669     670     671\r\n     679     681     696     705     709     711     791    1003    1216    1256\r\n     303     357     411     680     792    1256     304     358     412     681\r\n     793    1256     305     359     413     682     794    1256     306     360\r\n     414     683     795    1256     307     361     415     684     796    1256\r\n     362     416     685     719     797    1009    1222     309     686     706\r\n     710     798    1010    1223     310     364     418     687     716     717\r\n     718     719     799    1011    1224    1256     365     419     688     719\r\n     800    1012    1225     366     420     689     719     801     367     421\r\n     690     710     712     802    1014    1227     314     368     422     691\r\n     803    1256     315     369     423     664     665     666     667     668\r\n     669     670     671     672     674     675     677     679     681     683\r\n     692     693     704     705     710     712     804    1016    1229    1256\r\n     316     370     424     664     665     666     667     668     669     670\r\n     671     672     674     677     680     681     682     687     688     689\r\n     690     691     692     693     694     695     696     698     699     705\r\n     707     708     709     710     711     712     805    1017    1230    1256\r\n     317     371     425     664     665     666     667     668     669     670\r\n     671     672     689     694     705     709     710     806    1018    1231\r\n    1256     318     372     426     695     807    1256     319     373     427\r\n     672     696     697     705     808    1256     320     374     428     673\r\n     678     692     695     696     697     705     809    1021    1234    1256\r\n     321     375     429     677     693     698     705     810    1256     322\r\n     376     430     679     680     682     688     689     690     691     699\r\n     700     709     710     811    1023    1236    1256     377     431     672\r\n     673     674     675     676     677     678     679     680     682     683\r\n     686     687     688     689     690     691     692     693     694     695\r\n     696     697     698     699     700     701     702     704     705     706\r\n     707     708     812    1024    1237    1256     324     378     432     673\r\n     676     684     690     701     703     710     712     813    1025    1238\r\n    1256     379     433     697     702     814    1256     326     380     434\r\n     684     703     705     815    1027    1240    1256     327     381     435\r\n     680     684     685     686     687     688     689     690     691     692\r\n     704     705     708     710     719     816    1028    1241    1256     328\r\n     382     436     664     665     666     667     668     669     670     671\r\n     672     676     677     678     679     684     687     688     689     690\r\n     692     694     695     699     700     701     703     704     705     706\r\n     708     710     817    1029    1242    1256     383     437     706     710\r\n     712     818     384     438     676     690     700     703     704     707\r\n     819     385     439     664     665     666     667     668     669     670\r\n     671     672     673     674     675     676     677     678     679     680\r\n     681     682     683     684     685     686     687     688     689     690\r\n     691     692     693     694     695     696     697     698     699     700\r\n     701     702     703     704     705     706     707     708     709     710\r\n     711     712     713     716     717     718     719     774     775     776\r\n     777     778     780     781     782     783     784     785     786     787\r\n     788     789     790     791     792     793     794     796     798     799\r\n     800     801     802     803     804     805     806     807     808     809\r\n     810     811     812     813     815     816     817     819     820    1256\r\n     386     440     664     665     666     667     668     669     670     671\r\n     672     673     674     675     676     677     678     679     680     681\r\n     682     683     684     685     686     687     688     689     690     691\r\n     692     693     694     695     696     697     698     699     700     701\r\n     702     703     704     705     706     707     708     709     710     711\r\n     712     713     716     717     718     719     774     775     776     777\r\n     778     780     781     782     783     784     785     786     787     788\r\n     789     790     791     792     793     794     795     796     798     799\r\n     800     801     802     803     804     805     806     807     808     809\r\n     810     811     812     813     815     816     817     819     821    1256\r\n     387     441     710     716     717     718     719     822     388     442\r\n     664     665     666     667     668     669     670     671     672     673\r\n     674     675     676     677     678     679     680     681     682     683\r\n     684     685     686     687     688     689     690     691     692     693\r\n     694     695     696     697     698     699     700     701     702     703\r\n     704     705     706     707     708     709     710     711     712     823\r\n    1256     389     443     712     824    1256     390     444     713     825\r\n     391     445     714     826     392     446     707     715     827     339\r\n     672     720     986    1199     340     664     665     666     667     668\r\n     669     670     671     721     987    1200     341     664     665     666\r\n     667     668     669     670     671     722     988    1201     288     342\r\n     396     664     665     666     667     668     669     670     671     673\r\n     723     989    1202    1256     289     343     397     673     697     724\r\n     990    1203    1256     344     725     291     345     399     678     726\r\n     992    1205    1256     346     674     675     693     727     993    1206\r\n     293     347     401     728    1256     294     348     402     729    1256\r\n     295     349     403     730    1256     296     350     404     731    1256\r\n     297     351     405     693     732     998    1211    1256     352     675\r\n     693     733     999    1212     353     710     734    1000    1213     300\r\n     354     408     677     735    1256     301     355     409     736    1256\r\n     302     356     410     711     737    1003    1216    1256     303     357\r\n     411     738    1256     304     358     412     739    1256     305     359\r\n     413     682     740    1256     306     360     414     741    1256     307\r\n     361     415     684     719     742    1256     362     719     743    1009\r\n    1222     309     417     686     706     707     744    1010    1223    1256\r\n     310     364     418     716     717     718     719     745    1011    1224\r\n    1256     365     688     719     746    1012    1225     366     689     747\r\n     367     710     748    1014    1227     314     368     422     691     749\r\n    1256     315     369     423     664     665     666     667     668     669\r\n     670     671     679     691     692     710     750    1016    1229    1256\r\n     316     370     424     693     751    1017    1230    1256     317     371\r\n     425     664     665     666     667     668     669     670     671     672\r\n     687     693     694     710     716     752    1018    1231    1256     318\r\n     372     426     753    1256     319     373     427     754    1256     320\r\n     374     428     673     697     755    1021    1234    1256     321     375\r\n     429     698     756    1256     322     376     430     664     665     666\r\n     667     668     669     670     671     673     679     691     692     693\r\n     699     709     710     711     757    1023    1236    1256     377     672\r\n     673     674     675     676     677     678     679     680     682     683\r\n     686     687     688     689     690     691     692     693     694     695\r\n     696     697     698     699     700     701     702     704     705     706\r\n     707     708     758    1024    1237     324     378     432     673     710\r\n     759    1025    1238    1256     379     760     326     380     434     703\r\n     761    1027    1240    1256     327     381     435     687     704     708\r\n     710     716     717     718     719     762    1028    1241    1256     328\r\n     382     436     664     665     666     667     668     669     670     671\r\n     672     679     705     708     716     717     719     763    1029    1242\r\n    1256     383     764     384     765     385     766     386     767     387\r\n     768     388     769     389     770     390     713     771     391     772\r\n     392     773       1       2       3       4       5       6       7       8\r\n       9      10      11      12      13      14      15      16      17      18\r\n      19      20      21      22      23      24      25      26      27      28\r\n      29      30      31      32      33      34      35      36      37      38\r\n      39      40      41      42      43      44      45      46      47      48\r\n      49      50      53      54      55      56      57      58      59      60\r\n      61      62      63      64      65      66      67      68      69      70\r\n      71      72      73      74      75      76      77      78      79      80\r\n      81      82      83      84      85      86      87      88      89      90\r\n      91      92      93      94      95      96      97      98      99     100\r\n     102     103     104     105     106     107     108     109     110     111\r\n     112     113     114     115     116     117     118     119     120     121\r\n     122     123     124     125     126     127     128     129     130     131\r\n     132     133     134     135     136     137     138     139     140     141\r\n     142     143     144     145     146     147     148     149     150     151\r\n     152     154     155     156     664     665     666     667     668     669\r\n     670     671     672     673     674     675     676     677     678     679\r\n     680     681     682     683     684     685     686     687     688     689\r\n     690     691     692     693     694     695     696     697     698     699\r\n     700     701     702     703     704     705     706     707     708     709\r\n     710     711     714     715    1258       1      53     105     664     828\r\n       2      54     106     665     829       3      55     107     666     830\r\n       4      56     108     667     831       5      57     109     668     832\r\n       6      58     110     669     833       7      59     111     670     834\r\n       8      60     112     671     835       9      61     113     672     836\r\n      10      62     114     673     837      11      63     115     674     838\r\n      12      64     116     675     839      13      65     117     676     840\r\n      14      66     118     677     841      15      67     119     678     842\r\n      16      68     120     679     843      17      69     121     680     844\r\n      18      70     122     681     845      19      71     123     682     846\r\n      20      72     124     683     847      21      73     125     684     848\r\n      22      74     126     685     849      23      75     127     686     850\r\n      24      76     128     687     851      25      77     129     688     852\r\n      26      78     130     689     853      27      79     131     690     854\r\n      28      80     132     691     855      29      81     133     692     856\r\n      30      82     134     693     857      31      83     135     694     858\r\n      32      84     136     695     859      33      85     137     696     860\r\n      34      86     138     697     861      35      87     139     698     862\r\n      36      88     140     699     863      37      89     141     700     864\r\n      38      90     142     701     865      39      91     143     702     866\r\n      40      92     144     703     867      41      93     145     704     868\r\n      42      94     146     705     869      43      95     147     706     870\r\n      44      96     148     707     871      45      97     149     708     872\r\n      46      98     150     709     873      47      99     151     710     874\r\n      48     100     152     711     875      49     153     712     876      50\r\n     102     154     877     103     878     104     879       1      53     105\r\n     664       2      54     106     665       3      55     107     666       4\r\n      56     108     667       5      57     109     668       6      58     110\r\n     669       7      59     111     670       8      60     112     671     113\r\n     114     115     116     117     118     119     120     121     122     123\r\n     124     125     126     127     128     129     130     131     132     133\r\n     134     135     136     137     138     139     140     141     142     143\r\n     144     145     146     147     148     149     150     151     152     153\r\n     154     155     156     393     447     394     448     395     449     396\r\n     447     448     449     450     451     452     453     454     455     456\r\n     457     458     459     460     461     462     463     464     465     466\r\n     467     468     469     470     471     472     473     474     475     476\r\n     477     478     479     480     481     482     483     484     485     486\r\n     487     488     489     490     491     492     493     494     495     496\r\n     497     498     499     500     397     447     448     449     450     451\r\n     452     453     454     455     456     457     458     459     460     461\r\n     462     463     464     465     466     467     468     469     470     471\r\n     472     473     474     475     476     477     478     479     480     481\r\n     482     483     484     485     486     487     488     489     490     491\r\n     492     493     494     495     496     497     498     499     500     398\r\n     452     399     447     448     449     450     451     452     453     454\r\n     455     456     457     458     459     460     461     462     463     464\r\n     465     466     467     468     469     470     471     472     473     474\r\n     475     476     477     478     479     480     481     482     483     484\r\n     485     486     487     488     489     490     491     492     493     494\r\n     495     496     497     498     499     500     400     454     401     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     402     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     403     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     404     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     405     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     406     460     407     447     448     449     450\r\n     451     452     453     454     455     456     457     458     459     460\r\n     461     462     463     464     465     466     467     468     469     470\r\n     471     472     473     474     475     476     477     478     479     480\r\n     481     482     483     484     485     486     487     488     489     490\r\n     491     492     493     494     495     496     497     498     499     500\r\n     408     447     448     449     450     451     452     453     454     455\r\n     456     457     458     459     460     461     462     463     464     465\r\n     466     467     468     469     470     471     472     473     474     475\r\n     476     477     478     479     480     481     482     483     484     485\r\n     486     487     488     489     490     491     492     493     494     495\r\n     496     497     498     499     500     409     447     448     449     450\r\n     451     452     453     454     455     456     457     458     459     460\r\n     461     462     463     464     465     466     467     468     469     470\r\n     471     472     473     474     475     476     477     478     479     480\r\n     481     482     483     484     485     486     487     488     489     490\r\n     491     492     493     494     495     496     497     498     499     500\r\n     410     447     448     449     450     451     452     453     454     455\r\n     456     457     458     459     460     461     462     463     464     465\r\n     466     467     468     469     470     471     472     473     474     475\r\n     476     477     478     479     480     481     482     483     484     485\r\n     486     487     488     489     490     491     492     493     494     495\r\n     496     497     498     499     500     411     447     448     449     450\r\n     451     452     453     454     455     456     457     458     459     460\r\n     461     462     463     464     465     466     467     468     469     470\r\n     471     472     473     474     475     476     477     478     479     480\r\n     481     482     483     484     485     486     487     488     489     490\r\n     491     492     493     494     495     496     497     498     499     500\r\n     412     447     448     449     450     451     452     453     454     455\r\n     456     457     458     459     460     461     462     463     464     465\r\n     466     467     468     469     470     471     472     473     474     475\r\n     476     477     478     479     480     481     482     483     484     485\r\n     486     487     488     489     490     491     492     493     494     495\r\n     496     497     498     499     500     413     447     448     449     450\r\n     451     452     453     454     455     456     457     458     459     460\r\n     461     462     463     464     465     466     467     468     469     470\r\n     471     472     473     474     475     476     477     478     479     480\r\n     481     482     483     484     485     486     487     488     489     490\r\n     491     492     493     494     495     496     497     498     499     500\r\n     414     447     448     449     450     451     452     453     454     455\r\n     456     457     458     459     460     461     462     463     464     465\r\n     466     467     468     469     470     471     472     473     474     475\r\n     476     477     478     479     480     481     482     483     484     485\r\n     486     487     488     489     490     491     492     493     494     495\r\n     496     497     498     499     500     415     447     448     449     450\r\n     451     452     453     454     455     456     457     458     459     460\r\n     461     462     463     464     465     466     467     468     469     470\r\n     471     472     473     474     475     476     477     478     479     480\r\n     481     482     483     484     485     486     487     488     489     490\r\n     491     492     493     494     495     496     497     498     499     500\r\n     416     470     417     447     448     449     450     451     452     453\r\n     454     455     456     457     458     459     460     461     462     463\r\n     464     465     466     467     468     469     470     471     472     473\r\n     474     475     476     477     478     479     480     481     482     483\r\n     484     485     486     487     488     489     490     491     492     493\r\n     494     495     496     497     498     499     500     418     447     448\r\n     449     450     451     452     453     454     455     456     457     458\r\n     459     460     461     462     463     464     465     466     467     468\r\n     469     470     471     472     473     474     475     476     477     478\r\n     479     480     481     482     483     484     485     486     487     488\r\n     489     490     491     492     493     494     495     496     497     498\r\n     499     500     419     473     420     474     421     475     422     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     423     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     424     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     425     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     426     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     427     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     428     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     429     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     430     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     431     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     432     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     433     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     434     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     435     447     448     449     450     451     452\r\n     453     454     455     456     457     458     459     460     461     462\r\n     463     464     465     466     467     468     469     470     471     472\r\n     473     474     475     476     477     478     479     480     481     482\r\n     483     484     485     486     487     488     489     490     491     492\r\n     493     494     495     496     497     498     499     500     436     447\r\n     448     449     450     451     452     453     454     455     456     457\r\n     458     459     460     461     462     463     464     465     466     467\r\n     468     469     470     471     472     473     474     475     476     477\r\n     478     479     480     481     482     483     484     485     486     487\r\n     488     489     490     491     492     493     494     495     496     497\r\n     498     499     500     437     491     438     492     439     447     448\r\n     449     450     451     452     453     454     455     456     457     458\r\n     459     460     461     462     463     464     465     466     467     468\r\n     469     470     471     472     473     474     475     476     477     478\r\n     479     480     481     482     483     484     485     486     487     488\r\n     489     490     491     492     493     494     495     496     497     498\r\n     499     500     440     447     448     449     450     451     452     453\r\n     454     455     456     457     458     459     460     461     462     463\r\n     464     465     466     467     468     469     470     471     472     473\r\n     474     475     476     477     478     479     480     481     482     483\r\n     484     485     486     487     488     489     490     491     492     493\r\n     494     495     496     497     498     499     500     441     495     442\r\n     447     448     449     450     451     452     453     454     455     456\r\n     457     458     459     460     461     462     463     464     465     466\r\n     467     468     469     470     471     472     473     474     475     476\r\n     477     478     479     480     481     482     483     484     485     486\r\n     487     488     489     490     491     492     493     494     495     496\r\n     497     498     499     500     443     447     448     449     450     451\r\n     452     453     454     455     456     457     458     459     460     461\r\n     462     463     464     465     466     467     468     469     470     471\r\n     472     473     474     475     476     477     478     479     480     481\r\n     482     483     484     485     486     487     488     489     490     491\r\n     492     493     494     495     496     497     498     499     500     444\r\n     498     445     499     446     500     501     774    1254     502     775\r\n    1254     503     776    1254     504     777    1254     505     778    1254\r\n     506     779     507     780    1254     508     781    1254     509     782\r\n    1254     510     783    1254     511     784    1254     512     785    1254\r\n     513     786    1254     514     787    1254     515     788    1254     516\r\n     789    1254     517     790    1254     518     791    1254     519     792\r\n    1254     520     793    1254     521     794    1254     522     795    1254\r\n     523     796    1254     524     797     525     798    1254     526     799\r\n    1254     527     800    1254     528     801    1254     529     802    1254\r\n     530     803    1254     531     804    1254     532     805    1254     533\r\n     806    1254     534     807    1254     535     808    1254     536     809\r\n    1254     537     810    1254     538     811    1254     539     812    1254\r\n     540     813    1254     541     814     542     815    1254     543     816\r\n    1254     544     817    1254     545     818     546     819    1254     547\r\n     820     548     821     549     822     550     823     551     824     552\r\n     825    1254     553     826     554     827     716     828     829     830\r\n     831     832     833     834     835     977    1257     717     836     837\r\n     838     839     840     841     842     843     844     845     846     847\r\n     848     849     850     851     852     853     854     855     856     857\r\n     858     859     860     861     862     863     864     865     866     867\r\n     868     869     977    1257     718     870     871     879     977    1257\r\n     719     872     873     874     875     876     877     878     880     925\r\n     881     926     882     927     883     928     884     929     885     930\r\n     886     931     887     932     888     933     889     934     890     935\r\n     891     936     892     937     893     938     894     939     895     940\r\n     896     941     897     942     898     943     899     944     900     945\r\n     901     946     902     947     903     948     904     949     905     950\r\n     906     951     907     952     908     953     909     954     910     955\r\n     911     956     912     957     913     958     914     959     915     960\r\n     916     961     917     962     918     963     919     964     920     965\r\n     921     966     922     967     923     968     969     970     971     972\r\n     973     974     975     924     976     828     880     829     881     830\r\n     882     831     883     832     884     833     885     834     886     835\r\n     887     836     888     837     889     838     890     839     891     840\r\n     892     841     893     842     894     843     895     844     896     845\r\n     897     846     898     847     899     848     900     849     901     850\r\n     902     851     903     852     904     853     905     854     906     855\r\n     907     856     908     857     909     858     910     859     911     860\r\n     912     861     913     862     914     863     915     864     916     865\r\n     917     866     918     867     919     868     920     869     921     870\r\n     922     871     923     872     873     874     875     876     877     878\r\n     879     924     880     881     882     883     884     885     886     887\r\n     888     889     890     891     892     893     894     895     896     897\r\n     898     899     900     901     902     903     904     905     906     907\r\n     908     909     910     911     912     913     914     915     916     917\r\n     918     919     920     921     922     923     924    1094    1253    1255\r\n    1254    1255    1255     663    1256    1258     985    1257     447     448\r\n     449     450     451     452     453     454     455     456     457     458\r\n     459     460     461     462     463     464     465     466     467     468\r\n     469     470     471     472     473     474     475     476     477     478\r\n     479     480     481     482     483     484     485     486     487     488\r\n     489     490     491     492     493     494     495     496     497     498\r\n     499     500     663     977     985     775     776     777     779     780\r\n     782     783     784     785     786     788     790     791     792     793\r\n     794     795     796     797     798     799     800     801     802     803\r\n     804     805     806     808     809     810     811     812     813     814\r\n     815     816     817     818     820     821     822     823     824     825\r\n     826     827                                                                \r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -5.93589153D-03 -8.27388279D-03\r\n -8.60892702D-03 -1.37353456D-03 -4.92890272D-03 -1.55171787D-04 -1.30801986D-04\r\n -8.56874278D-04 -1.83234370D-04 -1.37678441D-03 -9.81827034D-04 -3.93233960D-03\r\n -3.73784045D-04 -6.89376247D-05 -1.66634141D-04 -1.05326253D-04 -1.00132599D-02\r\n -9.98593494D-03 -5.46094589D-03 -7.06019695D-04 -2.78090150D-03 -2.38090535D-04\r\n -1.64178631D-03 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -6.19863123D-02\r\n -7.16687143D-02 -6.68680817D-02 -1.15005681D-02 -1.90558087D-04 -7.38000050D-02\r\n -2.59988802D-03 -1.93114602D-03 -3.63798230D-03 -1.55267026D-03 -9.03802924D-03\r\n -6.42052805D-03 -3.30437534D-02 -3.13421409D-03 -5.57913794D-04 -1.34995126D-03\r\n -6.88492961D-04 -7.00013712D-02 -7.00070336D-02 -3.82313095D-02 -8.13334715D-03\r\n -1.48213431D-02 -2.86629447D-03 -5.33711677D-03 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -6.43365784D-03 -1.46014765D-01 -1.32799476D-01 -4.80291620D-02\r\n -1.27418283D-02 -2.09978819D-01 -6.17644563D-03 -3.45171918D-03 -9.97103006D-03\r\n -2.30328832D-03 -1.80562958D-02 -1.28339566D-02 -4.90272008D-02 -4.65024495D-03\r\n -8.43684305D-04 -2.04204884D-03 -1.37659872D-03 -1.69996798D-01 -1.70007035D-01\r\n -9.28501487D-02 -3.88781494D-03 -4.44640294D-02 -6.44817576D-03 -9.85071808D-03\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -9.52748433D-02 -1.84948742D-01\r\n -2.01589674D-01 -2.73518991D-02 -4.88014601D-04 -1.38668075D-01 -6.40007528D-03\r\n -4.22320887D-03 -2.66946550D-03 -2.67779361D-03 -1.42026180D-02 -1.00969886D-02\r\n -5.69765754D-02 -5.40477782D-03 -9.67531581D-04 -2.34273169D-03 -1.08307914D-03\r\n -1.80010065D-01 -1.79992974D-01 -9.83157754D-02 -1.23726027D-02 -1.11134751D-02\r\n -4.53819009D-03 -7.38803856D-03 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -8.71037971D-03 -1.18917592D-01 -1.02624908D-01 -3.30613479D-02 -6.81361323D-03\r\n -1.36338934D-01 -3.95535911D-03 -2.64995149D-03 -1.38095417D-03 -1.48837746D-03\r\n -6.73240982D-03 -4.78634099D-03 -3.16886082D-02 -3.00652371D-03 -5.41481015D-04\r\n -1.31053664D-03 -5.13465493D-04 -1.29989490D-01 -1.29992962D-01 -7.10063577D-02\r\n -3.18179536D-03 -6.48370478D-03 -2.38879793D-03 -4.10446571D-03 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -2.51121563D-03 -2.03185737D-01 -1.92379743D-01\r\n -5.52012399D-02 -2.22557895D-02 -2.92612076D-01 -2.19613705D-02 -5.13518928D-03\r\n -1.95196667D-03 -2.93014268D-03 -1.19892228D-02 -8.52459297D-03 -6.23729564D-02\r\n -5.91553887D-03 -1.05771166D-03 -2.56029260D-03 -9.14247415D-04 -2.39998177D-01\r\n -2.40014061D-01 -1.31086141D-01 -3.88781494D-03 -8.33763927D-03 -4.29878384D-03\r\n -7.38803856D-03 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -9.12127737D-03\r\n -9.66502652D-02 -8.96248892D-02 -1.80861093D-02 -2.58647744D-03 -3.19746435D-02\r\n -8.87065381D-03 -2.36170273D-03 -8.52607656D-04 -6.57393481D-04 -4.91426373D-03\r\n -3.49397887D-03 -1.39749302D-02 -1.32565643D-03 -2.53706501D-04 -6.14048797D-04\r\n -3.74643947D-04 -1.10008687D-01 -1.09985933D-01 -6.00797832D-02 -1.76975597D-03\r\n -3.70280328D-03 -1.67189550D-03 -2.46267952D-03 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.72779313D-03 -7.32349306D-02 -6.92287683D-02 -3.76125723D-02\r\n -6.32327469D-03 -1.11695595D-01 -2.23021419D-03 -1.86090055D-03 -2.39640358D-04\r\n -1.08172570D-03 -4.17646533D-03 -2.96730525D-03 -2.30374597D-02 -2.18466320D-03\r\n -3.89978552D-04 -9.44000029D-04 -3.18302133D-04 -8.99821669D-02 -9.00140628D-02\r\n -4.91578877D-02 -1.41517725D-03 -9.26967128D-04 -1.43248949D-03 -2.87443749D-03\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -5.39141834D-01\r\n -7.24108219D-02 -2.70749658D-01 -1.21773174D-02 -4.69028950D-03 -1.54549666D-02\r\n -1.32671088D-01 -5.41632026D-02 -2.29070000D-02 -1.02059292D-02 -2.30139447D-03\r\n -5.57160983D-03 -7.13856425D-04 -1.00000000D+00 -4.73746061D-01 -3.32121551D-02\r\n -4.78609577D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.28765732D-01 -3.11814636D-01 -2.33154781D-02 -7.09880516D-02 -4.69889343D-02\r\n -3.15410877D-03 -1.07982764D-02 -5.53905789D-04 -1.34165853D-03 -2.59249733D-04\r\n -1.31625205D-01 -1.44391209D-01 -5.64676113D-02 -2.39616428D-02 -5.95942466D-03\r\n -1.50985867D-01 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -6.88045193D-03 -1.94378905D-02 -4.44655260D-03 -2.45325267D-04 -5.37030539D-03\r\n -1.53506466D-04 -3.71707312D-04 -7.68649334D-05 -9.63710174D-02 -7.38798082D-03\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -9.01386291D-02\r\n -1.22320458D-01 -3.04286312D-02 -8.37532878D-02 -4.68578050D-03 -1.73666712D-03\r\n -4.20468301D-03 -6.42606348D-04 -6.97601080D-01 -3.87774557D-01 -6.43205643D-03\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -5.67285763D-03\r\n -8.43898356D-02 -7.12952465D-02 -2.18436681D-03 -2.09217687D-04 -5.06146345D-04\r\n -1.28947213D-04 -3.80237587D-03 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -2.41041323D-03 -1.25423633D-02 -1.31881451D-02 -1.33477459D-02\r\n -5.36979139D-01 -5.27575752D-03 -1.30613148D-01 -6.97793090D-04 -1.68956094D-03\r\n -2.89647200D-04 -3.43984067D-01 -5.14919870D-03 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.01745531D-01 -2.69539990D-02 -4.38700983D-04\r\n -3.81027572D-02 -2.16832879D-04 -5.24975592D-04 -9.08051734D-05 -4.47068959D-02\r\n -6.04115834D-04 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.70154739D-02 -5.44804186D-02 -2.94610416D-03 -3.52424942D-03 -5.30659396D-04\r\n -1.28507311D-03 -3.73675866D-04 -1.34332012D-02 -1.33385956D-01 -3.07743694D-03\r\n -3.23741399D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -5.22729533D-04 -4.91144974D-03 -1.17239055D-04 -4.91660368D-03 -4.84968186D-05\r\n -1.17170734D-04 -3.02038534D-05 -1.20823162D-04 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.84873845D-02 -9.48597852D-04 -1.18245208D-03\r\n -3.76752141D-05 -9.16097561D-05 -2.07167450D-05 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -7.71998952D-04 -1.67202950D-02 -6.54269592D-04\r\n -8.01600327D-05 -1.94536580D-04 -4.97589099D-05 -2.03145415D-01 -7.49814324D-04\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -3.93997468D-02\r\n -3.02552417D-05 -1.28256052D-05 -3.05365866D-05 -9.09987830D-06 -3.55362245D-05\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -4.90518920D-02\r\n -3.67200300D-02 -2.71796845D-02 -3.59273776D-02 -2.38876892D-04 -5.77658531D-04\r\n -1.04939027D-04 -5.05565293D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.21411122D-03 -6.01200236D-06 -1.42439021D-05 -3.67867437D-06\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -3.47935274D-04\r\n -2.35384447D-03 -3.32664131D-05 -7.99024419D-05 -1.47146975D-05 -1.36343017D-01\r\n -3.37594131D-04 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.82508340D-03 -9.35265142D-03 -3.97599563D-02 -5.92482509D-03 -5.05008211D-04\r\n -1.22273166D-03 -7.55212503D-03 -3.74332629D-03 -9.20388196D-03 -9.66170877D-02\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -5.53583428D-02\r\n -1.56889856D-02 -1.50773702D-02 -8.01763905D-04 -3.58140953D-02 -3.03902687D-03\r\n -5.37873828D-04 -1.30273169D-03 -3.15010693D-04 -7.46915162D-01 -9.20388207D-04\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.96155044D-03\r\n -2.13435292D-02 -3.22694657D-03 -3.08981654D-03 -8.41127534D-04 -1.17707148D-03\r\n -4.40880176D-05 -1.06243904D-04 -6.73778268D-05 -1.00000000D+00 -3.56072956D-03\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -6.53464487D-03\r\n -4.78093931D-03 -2.98770494D-04 -1.25943303D-01 -7.90266134D-03 -1.20934229D-02\r\n -8.96510552D-04 -1.88376071D-04 -4.56000009D-04 -1.34755654D-04 -3.02057917D-04\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -3.42344381D-02\r\n -7.49491062D-03 -5.08867763D-02 -1.53167162D-03 -4.46431991D-03 -4.15228977D-04\r\n -1.00536586D-03 -2.18397094D-04 -1.15931267D-02 -1.34739932D-02 -2.05113031D-02\r\n -1.80524017D-03 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -2.25418378D-04 -3.57041694D-03 -2.39277597D-05 -1.42107746D-02 -2.45445641D-03\r\n -6.50260481D-04 -9.39567667D-03 -1.57514456D-04 -3.81170743D-04 -7.84138465D-05\r\n -1.52073503D-01 -1.34146260D-02 -2.97793560D-03 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.39835760D-01 -5.19003533D-02 -4.34840858D-01\r\n -3.61280963D-02 -8.04134309D-02 -1.93728089D-01 -1.11547887D-01 -1.16482680D-03\r\n -3.34107014D-03 -8.08946323D-03 -1.76595734D-03 -2.06027895D-01 -3.05439346D-03\r\n -6.12225473D-01 -1.51701225D-02 -9.47329998D-02 -3.37812342D-02 -1.57425471D-03\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -2.20819050D-03\r\n -2.20815986D-02 -1.26315630D-03 -6.98581478D-03 -1.08616841D-04 -2.63512193D-04\r\n -4.74355365D-05 -1.68003932D-01 -1.38235907D-03 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -3.79240662D-02 -3.79112288D-02 -3.78637087D-05\r\n -2.06161980D-02 -1.18751824D-03 -9.24244896D-03 -3.09818512D-04 -7.49756116D-04\r\n -1.13651680D-04 -1.90118793D-03 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.03008263D-01 -3.86701792D-01 -2.99895387D-02 -5.25375903D-02\r\n -1.23860007D-02 -5.47971984D-04 -8.51425901D-02 -6.35736883D-02 -1.41821441D-03\r\n -8.42481910D-04 -2.03999993D-03 -3.50635761D-04 -2.42357049D-03 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.66872039D-01 -3.37420292D-02\r\n -8.80064443D-02 -3.89158027D-03 -6.62715316D-01 -5.41481015D-04 -1.31102442D-03\r\n -2.28077814D-04 -1.27128080D-01 -8.09310284D-03 -7.43773161D-03 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -2.97079161D-02 -5.42924087D-03\r\n -2.06804206D-03 -3.53608117D-03 -2.03606483D-04 -4.92780469D-04 -9.89369801D-05\r\n -3.20892364D-01 -4.84358752D-03 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.22674100D-01 -1.09305168D-02 -2.05520347D-01 -4.30607721D-02\r\n -4.88937367D-03 -2.13786797D-03 -5.17551228D-03 -9.38836427D-04 -4.67726886D-01\r\n -4.98075709D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -2.56573432D-03 -9.37912439D-04 -9.42864418D-02 -1.70647688D-02 -3.70740134D-04\r\n -8.98439030D-04 -2.28465040D-04 -6.78741897D-04 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -2.07248400D-03 -2.02045768D-01 -6.14770278D-02\r\n -2.10019280D-04 -5.07902412D-04 -1.28366373D-04 -1.47830695D-03 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -3.40371451D-04 -2.59070516D-01\r\n -6.81360279D-06 -1.66829268D-05 -6.38927668D-06 -6.04115834D-04 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.57857910D-02 -4.08238396D-02\r\n -5.86399846D-02 -1.60451792D-02 -3.32263327D-04 -8.04975629D-04 -1.56246853D-04\r\n -7.34207183D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -4.65537570D-02 -1.24538131D-02 -4.12854701D-01 -3.76570015D-03 -4.29942692D-03\r\n -2.45209527D-03 -5.93648758D-03 -1.22170709D-03 -2.08562091D-02 -1.58014163D-01\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -3.14314887D-02\r\n -3.47981751D-02 -4.16617095D-03 -1.12184873D-02 -1.80052444D-02 -2.45015007D-02\r\n -1.56204402D-02 -2.99912523D-02 -2.06400584D-02 -3.67979356D-03 -4.41914909D-02\r\n -4.77933232D-03 -4.08415362D-04 -9.88682965D-04 -1.65540347D-04 -6.01272890D-03\r\n -3.15532461D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.85339358D-02 -1.16104481D-03 -4.73614549D-04 -9.61920341D-06 -2.31219510D-05\r\n -4.22079465D-05 -3.23306620D-02 -1.04121130D-03 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -4.53286432D-03 -1.78381115D-01 -3.97593743D-04\r\n -9.62439051D-04 -1.75821269D-03 -1.00000000D+00 -4.71103936D-01 -3.14317912D-01\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -4.37515154D-02\r\n -5.10670662D-01 -1.60897091D-01 -7.86571670D-03 -2.05049361D-03 -4.96419519D-03\r\n -1.57118123D-03 -5.00001788D-01 -6.21112846D-02 -4.10499051D-02 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -6.98079586D-01 -1.94451973D-01\r\n -8.52652192D-02 -3.07986289D-02 -7.04887230D-03 -1.70657560D-02 -2.77327120D-01\r\n -1.43419951D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -7.45730400D-01 -6.41808689D-01 -9.49445844D-01 -1.16051726D-01 -7.41642267D-02\r\n -1.46283031D-01 -1.69224694D-01 -1.78926215D-01 -1.40577674D-01 -1.35398041D-02\r\n -9.27194357D-01 -4.80118487D-03 -1.16230240D-02 -3.06480043D-02 -1.00000000D+00\r\n -1.00000000D+00 -1.75491393D-01 -1.90357510D-02 -2.82683177D-03 -2.79957622D-01\r\n -4.48854752D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.33129418D-01 -1.00396676D-02 -3.90780158D-04 -9.46048764D-04 -6.60542548D-02\r\n -1.13310050D-02 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -3.76148261D-02 -4.02495340D-02 -2.78500728D-02 -4.21503261D-02 -7.28056729D-02\r\n -2.98596104D-04 -7.22439028D-04 -2.63993279D-03 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -8.09095241D-03 -9.52975638D-03 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -3.56158568D-03\r\n  1.00000000D+00 -3.36924791D-02  1.00000000D+00 -9.01731327D-02  1.00000000D+00\r\n -5.66755012D-02  1.00000000D+00 -2.80031972D-02  1.00000000D+00 -4.98667546D-02\r\n  1.00000000D+00 -2.37598270D-02  1.00000000D+00 -1.64391100D-02  1.00000000D+00\r\n -2.31136009D-03  1.00000000D+00 -2.48041283D-03  1.00000000D+00 -1.27226813D-03\r\n  1.00000000D+00 -5.37730055D-03  1.00000000D+00 -2.57951277D-03  1.00000000D+00\r\n -1.56978657D-03  1.00000000D+00 -2.18602782D-03  1.00000000D+00 -8.61218385D-03\r\n  1.00000000D+00 -6.97780051D-04  1.00000000D+00 -5.19145164D-04  1.00000000D+00\r\n -1.32793898D-03  1.00000000D+00 -2.91506789D-04  1.00000000D+00 -1.51601026D-03\r\n  1.00000000D+00 -9.04286790D-05  1.00000000D+00 -1.42273973D-04  1.00000000D+00\r\n -7.39766378D-03  1.00000000D+00 -8.19738582D-03  1.00000000D+00 -2.08459608D-03\r\n  1.00000000D+00 -3.65354470D-03  1.00000000D+00 -4.88446048D-03  1.00000000D+00\r\n -1.22504996D-03  1.00000000D+00 -4.36096154D-02  1.00000000D+00 -6.93262264D-04\r\n  1.00000000D+00 -1.65846641D-03  1.00000000D+00 -8.10870528D-03  1.00000000D+00\r\n -3.22366226D-03  1.00000000D+00 -1.27204950D-03  1.00000000D+00 -1.30607868D-02\r\n  1.00000000D+00 -1.65249128D-03  1.00000000D+00 -1.77341502D-03  1.00000000D+00\r\n -3.16500373D-04  1.00000000D+00 -2.04896391D-03  1.00000000D+00 -2.36979984D-02\r\n  1.00000000D+00 -1.35482708D-03  1.00000000D+00 -1.56581530D-03  1.00000000D+00\r\n -5.38427010D-02  1.00000000D+00 -2.21645720D-02  1.00000000D+00 -1.42507151D-01\r\n  1.00000000D+00 -4.82241735D-02  1.00000000D+00 -1.79205015D-01  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00 -5.76346964D-02  1.00000000D+00 -3.17968652D-02\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.78465787D-02\r\n  1.00000000D+00 -5.69905678D-04  1.00000000D+00 -4.49396856D-03  1.00000000D+00\r\n -5.19715795D-05  1.00000000D+00 -1.39432741D-05  1.00000000D+00 -3.59829981D-03\r\n  1.00000000D+00 -2.16023461D-03  1.00000000D+00 -2.96454262D-02  1.00000000D+00\r\n -4.90016444D-03  1.00000000D+00 -1.30853141D-02  1.00000000D+00 -2.92256594D-01\r\n  1.00000000D+00 -4.58589569D-02  1.00000000D+00 -2.51878798D-02  1.00000000D+00\r\n -7.07555935D-03  1.00000000D+00 -3.27899330D-03  1.00000000D+00 -6.71901256D-02\r\n  1.00000000D+00 -4.52964678D-02  1.00000000D+00 -1.56934559D-01  1.00000000D+00\r\n -5.25400750D-02  1.00000000D+00 -8.18570703D-02  1.00000000D+00 -3.68810818D-02\r\n  1.00000000D+00 -1.44300938D-01  1.00000000D+00 -7.79947191D-02  1.00000000D+00\r\n -2.54118741D-01  1.00000000D+00 -2.48348296D-01  1.00000000D+00 -2.14205191D-01\r\n  1.00000000D+00 -1.20531969D-01  1.00000000D+00 -4.81847942D-01  1.00000000D+00\r\n -1.67683020D-01  1.00000000D+00 -2.87884384D-01  1.00000000D+00 -5.31182885D-01\r\n  1.00000000D+00 -3.48290294D-01  1.00000000D+00 -6.13069355D-01  1.00000000D+00\r\n -2.59709395D-02  1.00000000D+00 -8.81912094D-03  1.00000000D+00 -1.31283581D-01\r\n  1.00000000D+00 -1.15888983D-01  1.00000000D+00 -1.19731724D-01  1.00000000D+00\r\n -1.63664266D-01  1.00000000D+00 -1.43314779D-01  1.00000000D+00 -4.88956943D-02\r\n  1.00000000D+00 -1.82706028D-01  1.00000000D+00 -6.37331307D-02  1.00000000D+00\r\n -1.64185643D-01  1.00000000D+00 -1.31180644D-01  1.00000000D+00 -1.37433782D-01\r\n  1.00000000D+00 -7.62486756D-02  1.00000000D+00 -6.59873635D-02  1.00000000D+00\r\n -1.53722018D-01  1.00000000D+00 -1.00952752D-01  1.00000000D+00 -1.59418490D-02\r\n  1.00000000D+00 -1.75022557D-01  1.00000000D+00 -1.48241401D-01  1.00000000D+00\r\n -2.95332223D-01  1.00000000D+00 -4.35067326D-01  1.00000000D+00 -2.99447656D-01\r\n  1.00000000D+00 -4.29889739D-01  1.00000000D+00 -9.46358740D-02  1.00000000D+00\r\n -2.62589782D-01  1.00000000D+00 -1.57239005D-01  1.00000000D+00 -4.79257405D-02\r\n  1.00000000D+00 -6.81549832D-02  1.00000000D+00 -4.14365530D-02  1.00000000D+00\r\n -3.13165896D-02  1.00000000D+00 -4.82902043D-02  1.00000000D+00 -3.12532112D-02\r\n  1.00000000D+00 -1.65843651D-01  1.00000000D+00 -3.94780114D-02  1.00000000D+00\r\n -1.06069766D-01  1.00000000D+00 -1.06182404D-01  1.00000000D+00 -9.06958152D-03\r\n  1.00000000D+00 -3.50963511D-02  1.00000000D+00 -2.58430243D-02  1.00000000D+00\r\n -2.21948341D-01  1.00000000D+00 -1.25001445D-01  1.00000000D+00 -1.15588143D-01\r\n  1.00000000D+00 -4.41402867D-02  1.00000000D+00 -1.17391003D-02  1.00000000D+00\r\n -8.88309106D-02  1.00000000D+00 -1.09484315D-01  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n -3.03959493D-02  1.00000000D+00 -3.56015950D-01  1.00000000D+00  1.00000000D+00\r\n -2.09159389D-01  1.00000000D+00  1.00000000D+00 -8.19865763D-01  1.00000000D+00\r\n -6.45634174D-01  1.00000000D+00 -6.39332294D-01  1.00000000D+00 -9.97142851D-01\r\n  1.00000000D+00 -5.00000000D-01  1.00000000D+00  1.00000000D+00 -2.51026601D-01\r\n  1.00000000D+00 -5.73770761D-01  1.00000000D+00 -9.99197245D-01  1.00000000D+00\r\n -6.12838604D-02  1.00000000D+00 -9.79579866D-01  1.00000000D+00 -9.41222906D-01\r\n  1.00000000D+00 -9.82795656D-01  1.00000000D+00 -9.99544799D-01  1.00000000D+00\r\n -9.98440027D-01  1.00000000D+00  1.00000000D+00  1.00000000D+00 -6.87208250D-02\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00 -9.37243104D-01\r\n  1.00000000D+00 -3.05369467D-01  1.00000000D+00 -2.44393930D-01  1.00000000D+00\r\n -5.99167570D-02  1.00000000D+00 -4.09031749D-01  1.00000000D+00 -6.54813766D-01\r\n  1.00000000D+00 -7.75436103D-01  1.00000000D+00 -5.67775071D-02  1.00000000D+00\r\n -3.49151224D-01  1.00000000D+00 -1.00001134D-01  1.00000000D+00 -6.01657480D-02\r\n  1.00000000D+00 -7.82141462D-02  1.00000000D+00 -8.72963190D-01  1.00000000D+00\r\n -7.58721083D-02  1.00000000D+00 -6.22733496D-02  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00 -7.42725551D-01  1.00000000D+00 -7.90000021D-01  1.00000000D+00\r\n  1.00000000D+00 -6.62945509D-01  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00 -3.22186440D-01  1.00000000D+00 -7.28480697D-01  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -9.55293119D-01  1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -9.96945620D-01  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00 -6.56015933D-01  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -8.67891490D-01  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -7.96854556D-01  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -8.03196490D-01  1.00000000D+00  1.00000000D+00 -2.34577850D-01\r\n  1.00000000D+00 -1.01583153D-01  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00 -9.88406897D-01  1.00000000D+00 -6.10173583D-01  1.00000000D+00\r\n -9.84829903D-01  1.00000000D+00 -1.45812437D-01  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -9.35439289D-01  1.00000000D+00\r\n -6.79107606D-01  1.00000000D+00 -2.54835814D-01  1.00000000D+00  1.00000000D+00\r\n -5.69056511D-01  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -9.26579297D-01\r\n  1.00000000D+00 -3.86048704D-02  1.00000000D+00 -4.91169512D-01  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n  5.00000007D-02 -2.69156814D-01 -4.65328991D-03 -6.22985372D-03 -3.80239636D-02\r\n  5.00000007D-02 -4.66260761D-01 -1.84849033D-03 -2.47492688D-03 -1.51058435D-02\r\n  5.60000002D-01 -7.63145924D-01 -1.06123865D-01 -9.68712196D-03 -2.16793314D-01\r\n  2.39999995D-01 -8.15083683D-01 -1.05610844D-02 -1.41391223D-02 -8.62984210D-02\r\n  5.00000007D-02 -3.95800620D-01 -1.64448307D-03 -2.20156088D-03 -1.34372637D-02\r\n  5.00000007D-02 -5.11013329D-01 -1.36712939D-03 -1.83034141D-03 -1.11717703D-02\r\n  5.00000007D-02 -9.59510028D-01 -2.95934808D-02 -3.96195129D-02 -2.41819128D-01\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00 -2.76298150D-02  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00 -3.40405246D-03  1.00000000D+00\r\n  1.00000000D+00 -7.99549520D-02  1.00000000D+00 -3.64257284D-02  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00 -6.36040792D-02  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00 -1.25452146D-01\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00 -1.37514537D-02  1.00000000D+00\r\n -2.57521961D-03  1.00000000D+00  1.00000000D+00 -1.06875168D-03  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00 -1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00 -6.60542548D-02  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n -1.25644520D-01  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n -7.15435967D-02  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n -2.12379946D-05  1.00000000D+00 -1.38877379D-03  1.00000000D+00 -1.69529160D-03\r\n  1.00000000D+00 -1.30305747D-02  1.00000000D+00 -7.15932772D-02  1.00000000D+00\r\n  1.00000000D+00 -1.56391002D-02  1.00000000D+00 -1.96913686D-02  1.00000000D+00\r\n -4.65031248D-04  1.00000000D+00 -6.46045059D-02  1.00000000D+00 -1.41096707D-05\r\n  1.00000000D+00 -2.13194918D-02  1.00000000D+00 -4.82018702D-02  1.00000000D+00\r\n -1.17546050D-02  1.00000000D+00 -7.12832334D-05  1.00000000D+00 -2.90225632D-03\r\n  1.00000000D+00 -4.32887627D-03  1.00000000D+00 -1.61347762D-02  1.00000000D+00\r\n -3.65646253D-03  1.00000000D+00 -1.12061657D-03  1.00000000D+00 -1.28508243D-03\r\n  1.00000000D+00 -7.21944845D-04  1.00000000D+00 -3.12227919D-03  1.00000000D+00\r\n -4.79361363D-04  1.00000000D+00 -3.76875186D-03  1.00000000D+00 -9.84223001D-03\r\n  1.00000000D+00 -1.19829318D-03  1.00000000D+00 -8.72301025D-05  1.00000000D+00\r\n -2.48197932D-03  1.00000000D+00 -2.69700470D-03  1.00000000D+00 -2.04223525D-02\r\n  1.00000000D+00 -1.21343024D-01  1.00000000D+00 -1.30022084D-02  1.00000000D+00\r\n -6.75853249D-03  1.00000000D+00 -1.29593657D-02  1.00000000D+00 -4.72033173D-02\r\n  1.00000000D+00 -2.85191718D-03  1.00000000D+00 -5.33207394D-02  1.00000000D+00\r\n -2.06797067D-02  1.00000000D+00 -9.44649801D-03  1.00000000D+00  1.00000000D+00\r\n -3.70004075D-03  1.00000000D+00 -5.03387488D-02  1.00000000D+00 -2.59307083D-02\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00 -2.88725168D-01  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00 -5.48067629D-01 -7.43604545D-03 -4.82097548D-03\r\n -1.31497085D-01 -2.47637033D-01 -2.29462353D-03 -1.01192757D-01 -2.62266193D-02\r\n  1.00000000D+00 -2.13327646D-01 -3.71461594D-03 -3.46439029D-03 -1.28691241D-01\r\n -3.02950412D-01 -8.93040746D-03 -2.01682709D-02  1.00000000D+00 -8.31404980D-03\r\n -2.52504105D-04 -1.63707315D-04 -3.93955124D-04 -6.25510290D-02 -1.97172053D-02\r\n  1.00000000D+00 -1.00000000D+00 -4.02082577D-02 -9.67077792D-01 -9.97612417D-01\r\n -5.00000529D-02 -4.88695642D-03 -2.11219513D-03 -7.39417732D-01 -1.46247000D-01\r\n -1.00000000D+00 -2.85278380D-01 -2.53084838D-01 -4.69926745D-01 -1.97006494D-01\r\n -3.99474278D-02 -5.00000007D-02  6.67069061D-03 -1.31836802D-01 -9.00000036D-02\r\n  2.20149979D-02 -2.42864177D-01 -5.00000007D-02  4.05550972D-02 -1.81239873D-01\r\n -9.00000036D-02  3.02646551D-02 -9.38324183D-02 -7.00000003D-02  1.56687703D-02\r\n -1.79161012D-01 -7.00000003D-02  2.99175121D-02 -6.24370202D-02 -7.00000003D-02\r\n  1.04261544D-02 -6.86812699D-02 -7.00000003D-02  1.14688613D-02 -6.83486238D-02\r\n -1.29999995D-01  8.17558262D-03 -5.05733937D-02 -7.99999982D-02  6.04938250D-03\r\n -3.38348635D-02 -1.00000001D-01  4.04718798D-03 -4.25351672D-02 -7.99999982D-02\r\n  5.08788275D-03 -1.93547402D-02 -1.09999999D-01  2.31513497D-03 -2.32370030D-02\r\n -1.80000007D-01  2.77951523D-03 -9.78440326D-03 -1.40000001D-01  1.17037038D-03\r\n -6.17706440D-02 -1.29999995D-01  7.38875149D-03 -7.21712539D-04 -1.29999995D-01\r\n  8.63283058D-05 -1.98470941D-03 -1.29999995D-01  2.37402841D-04 -2.72782869D-03\r\n -1.29999995D-01  3.26291716D-04 -1.98165141D-03 -1.00000001D-01  2.37037035D-04\r\n -7.97706377D-03 -1.40000001D-01  9.54183808D-04 -9.46483167D-04 -1.40000001D-01\r\n  1.13214446D-04 -1.12079515D-03 -1.29999995D-01  1.34064932D-04 -5.94709478D-02\r\n -9.00000036D-02  7.11367186D-03 -2.49847099D-02 -1.09999999D-01  2.98856874D-03\r\n -7.44204894D-02 -1.09999999D-01  8.90187453D-03 -1.95565750D-03 -1.50000006D-01\r\n  2.33927756D-04 -1.74281336D-02 -1.29999995D-01  2.08468223D-03 -1.33516816D-02\r\n -1.40000001D-01  1.59707363D-03 -4.67324145D-02 -1.09999999D-01  5.58994059D-03\r\n -6.00917451D-03 -1.40000001D-01  7.18792842D-04 -1.12645263D-02 -1.00000001D-01\r\n  1.34741655D-03 -1.53486235D-02 -1.19999997D-01  1.83593959D-03 -4.24143746D-02\r\n -1.40000001D-01  5.07343374D-03 -1.16284406D-02 -7.99999982D-02  1.39094645D-03\r\n -8.41406733D-02 -1.09999999D-01  1.00645637D-02 -1.31145254D-01 -2.00000003D-01\r\n  1.56870596D-02 -8.49541277D-03 -1.19999997D-01  1.01618655D-03 -3.09327221D-03\r\n -5.99999987D-02  3.70004564D-04 -7.79969431D-03 -1.50000006D-01  9.32967523D-04\r\n -7.35229328D-02 -1.19999997D-01  8.79451260D-03 -3.98944952D-02 -1.29999995D-01\r\n  4.77201631D-03 -1.77741945D-02 -2.00000003D-01  1.00777317D-04 -9.82225835D-01\r\n -2.00000003D-01  5.56909014D-03 -7.99999982D-02 -1.59999996D-01  1.00000000D+00\r\n -3.60000014D-01 -1.09999999D-01  1.00000000D+00 -7.99999982D-02 -2.00000003D-01\r\n  1.00000000D+00 -2.39999995D-01 -1.50000006D-01  1.00000000D+00 -2.39999995D-01\r\n -1.50000006D-01  1.00000000D+00 -1.59999996D-01  1.00000000D+00 -1.19999997D-01\r\n  1.00000000D+00 -2.00000003D-01 -2.03827190D+00  2.50722790D+00  2.50722790D+00\r\n  2.50722790D+00  2.50722790D+00  2.50722790D+00  2.50722790D+00  5.74199595D-02\r\n  8.89650881D-01  8.89650881D-01 -6.84651732D-01  7.57262707D-01  7.57262707D-01\r\n  7.57262707D-01  7.57262707D-01  7.57262707D-01  7.57262707D-01  1.71273291D-01\r\n  7.57262707D-01  2.98174381D-01 -1.73215106D-01 -1.73215106D-01 -1.73215106D-01\r\n -1.73215106D-01 -1.73215106D-01 -1.73215106D-01 -1.73215106D-01  6.30014949D-03\r\n  9.76129770D-02  9.76129770D-02 -7.40123630D-01  7.12008893D-01  2.81816572D-01\r\n  7.12008893D-01  7.12008893D-01  7.12008893D-01  7.12008893D-01  1.61038041D-01\r\n  7.12008893D-01  2.80355543D-01 -2.82574105D+00  1.02045894D+00  1.02045894D+00\r\n  1.02045894D+00  1.02045894D+00  3.05909496D-02  1.02045894D+00  1.67414490D-02\r\n  9.93608907D-02  9.93608907D-02 -3.01978122D-02 -3.01978122D-02 -3.01978122D-02\r\n -3.01978122D-02 -3.01978122D-02  4.75290697D-03 -3.01978122D-02  2.60111387D-03\r\n  1.54376719D-02  1.54376719D-02 -1.69090942D-01 -1.69090942D-01 -1.69090942D-01\r\n -1.69090942D-01 -1.69090942D-01 -1.69090942D-01 -1.69090942D-01  1.60707850D-02\r\n  9.53804851D-02  9.53804851D-02 -1.24394380D-01 -1.24394380D-01 -1.24394380D-01\r\n -1.24394380D-01 -1.24394380D-01  9.98765975D-03 -1.24394380D-01  5.46592707D-03\r\n  3.24404053D-02  3.24404053D-02 -5.00000000D-01 -1.00000000D+00  1.10741682D-01\r\n  2.62503922D-01  1.54968342D-02  3.03868353D-01  5.55011146D-02  1.02592101D-02\r\n  7.57173747D-02  1.59322936D-02 -6.12610757D-01 -8.69999826D-01  8.81728047D-05\r\n -4.99836445D-01  1.04071647D-02 -6.39951527D-02 -6.39951527D-02 -6.39951527D-02\r\n -6.39951527D-02 -6.39951527D-02 -6.39951527D-02  2.38342502D-04  3.69282067D-03\r\n  3.69282067D-03  1.54453237D-02 -7.84192756D-02 -7.84192756D-02 -7.84192756D-02\r\n -7.84192756D-02 -7.84192756D-02 -7.84192756D-02  2.84985313D-03  1.26002580D-02\r\n  4.96138772D-03 -8.80930871D-02 -8.80930871D-02 -8.80930871D-02 -8.80930871D-02\r\n -8.80930871D-02 -8.80930871D-02 -8.80930871D-02  3.20410589D-03  4.96436357D-02\r\n  4.96436357D-02  6.06838651D-02 -2.36646697D-01  1.95946172D-02 -2.36646697D-01\r\n -2.36646697D-01 -2.36646697D-01 -2.36646697D-01  1.11969244D-02  4.95057516D-02\r\n  1.94930322D-02  4.95642304D-01 -4.30728585D-01 -4.30728585D-01 -4.30728585D-01\r\n -4.30728585D-01  1.48581862D-02 -4.30728585D-01  8.13141000D-03  4.82601114D-02\r\n  4.82601114D-02 -4.30944450D-02 -4.30944450D-02 -4.30944450D-02 -4.30944450D-02\r\n -4.30944450D-02  6.78273896D-03 -4.30944450D-02  3.71197611D-03  2.20306665D-02\r\n  2.20306665D-02 -3.12564522D-02 -3.12564522D-02 -3.12564522D-02 -3.12564522D-02\r\n -3.12564522D-02 -3.12564522D-02 -3.12564522D-02  2.97068362D-03  1.76310781D-02\r\n  1.76310781D-02 -6.25699833D-02 -6.25699833D-02 -6.25699833D-02 -6.25699833D-02\r\n -6.25699833D-02  5.02376119D-03 -6.25699833D-02  2.74934387D-03  1.63174197D-02\r\n  1.63174197D-02 -5.00000000D-01 -1.00000000D+00 -9.31064598D-03 -3.82446544D-03\r\n -1.13382936D-04  1.48005467D-02  1.14515871D-02 -2.79633701D-03 -7.22729228D-03\r\n -1.07579976D-02 -1.06948726D-02 -8.69891703D-01  4.07628454D-02 -4.54577208D-01\r\n  6.21434972D-02 -3.82129312D-01 -3.82129312D-01 -3.82129312D-01 -3.82129312D-01\r\n -3.82129312D-01 -3.82129312D-01  1.42319617D-03  2.20506545D-02  2.20506545D-02\r\n  6.42392877D-03 -3.26156914D-02 -3.26156914D-02 -3.26156914D-02 -3.26156914D-02\r\n -3.26156914D-02 -3.26156914D-02  1.18529436D-03  5.24062570D-03  2.06351141D-03\r\n -3.60557176D-02 -3.60557176D-02 -3.60557176D-02 -3.60557176D-02 -3.60557176D-02\r\n -3.60557176D-02 -3.60557176D-02  1.31141208D-03  2.03187000D-02  2.03187000D-02\r\n  3.20153944D-02  2.61180811D-02 -5.10462344D-01  2.61180811D-02  2.61180811D-02\r\n  2.61180811D-02  2.61180811D-02  5.90723613D-03  2.61180811D-02  1.02840699D-02\r\n  1.30923346D-01 -1.13776460D-01 -1.13776460D-01 -1.13776460D-01 -1.13776460D-01\r\n  3.92477307D-03 -1.13776460D-01  2.14790273D-03  1.27478531D-02  1.27478531D-02\r\n -2.76396852D-02 -2.76396852D-02 -2.76396852D-02 -2.76396852D-02 -2.76396852D-02\r\n  4.35027713D-03 -2.76396852D-02  2.38076760D-03  1.41299125D-02  1.41299125D-02\r\n -1.43900374D-02 -1.43900374D-02 -1.43900374D-02 -1.43900374D-02 -1.43900374D-02\r\n -1.43900374D-02 -1.43900374D-02  1.36766164D-03  8.11710395D-03  8.11710395D-03\r\n -3.48886102D-02 -3.48886102D-02 -3.48886102D-02 -3.48886102D-02 -3.48886102D-02\r\n  2.80121644D-03 -3.48886102D-02  1.53301610D-03  9.09848697D-03  9.09848697D-03\r\n -5.00000000D-01 -1.00000000D+00 -3.76588060D-03 -4.67685144D-03 -2.74560135D-03\r\n  2.82335691D-02 -5.28713875D-03 -3.31864133D-03 -9.25511029D-03 -9.26723704D-03\r\n -3.04701719D-02 -8.70137990D-01  6.51841611D-02 -4.23311949D-01  5.24101779D-04\r\n -3.22277728D-03 -3.22277728D-03 -3.22277728D-03 -3.22277728D-03 -3.22277728D-03\r\n -3.22277728D-03  1.20028599D-05  1.85969388D-04  1.85969388D-04  1.31599407D-03\r\n -6.68158941D-03 -6.68158941D-03 -6.68158941D-03 -6.68158941D-03 -6.68158941D-03\r\n -6.68158941D-03  2.42817172D-04  1.07358478D-03  4.22727084D-04 -8.56701881D-02\r\n -8.56701881D-02 -8.56701881D-02 -8.56701881D-02 -8.56701881D-02 -8.56701881D-02\r\n -8.56701881D-02  3.11598089D-03  4.82782498D-02  4.82782498D-02  2.49884813D-03\r\n -9.74466838D-03  8.06869706D-04 -9.74466838D-03 -9.74466838D-03 -9.74466838D-03\r\n -9.74466838D-03  4.61068412D-04  2.03855429D-03  8.02686671D-04  2.45963693D-01\r\n -2.13750109D-01 -2.13750109D-01 -2.13750109D-01 -2.13750109D-01  7.37341121D-03\r\n -2.13750109D-01  4.03523212D-03  2.39491984D-02  2.39491984D-02 -4.01567370D-02\r\n -4.01567370D-02 -4.01567370D-02 -4.01567370D-02 -4.01567370D-02  6.32036664D-03\r\n -4.01567370D-02  3.45893437D-03  2.05288567D-02  2.05288567D-02 -7.93116167D-03\r\n -7.93116167D-03 -7.93116167D-03 -7.93116167D-03 -7.93116167D-03 -7.93116167D-03\r\n -7.93116167D-03  7.53795495D-04  4.47379425D-03  4.47379425D-03 -2.18512505D-01\r\n -2.18512505D-01 -2.18512505D-01 -2.18512505D-01 -2.18512505D-01  1.75444297D-02\r\n -2.18512505D-01  9.60150547D-03  5.69851622D-02  5.69851622D-02  4.71892297D-01\r\n -2.81077065D-02 -5.62154129D-02 -8.82008986D-04 -3.62094084D-04  7.52938213D-03\r\n -6.91006426D-05  1.29995495D-02  1.31666847D-02  1.85310841D-03  2.87142098D-02\r\n -2.20831167D-02 -5.38090281D-02 -8.70029628D-01  1.52490258D-01 -9.62755829D-02\r\n -1.12710521D-04  4.49230138D-04 -2.76238052D-03 -2.76238052D-03 -2.76238052D-03\r\n -2.76238052D-03 -2.76238052D-03 -2.76238052D-03  1.02881659D-05  1.59402334D-04\r\n  1.59402334D-04  1.94844441D-03 -9.89267789D-03 -9.89267789D-03 -9.89267789D-03\r\n -9.89267789D-03 -9.89267789D-03 -9.89267789D-03  3.59512109D-04  1.58953632D-03\r\n  6.25884510D-04 -2.67490625D-01 -2.67490625D-01 -2.67490625D-01 -2.67490625D-01\r\n -2.67490625D-01 -2.67490625D-01 -2.67490625D-01  9.72912088D-03  1.50740623D-01\r\n  1.50740623D-01  2.71101436D-03 -1.05720451D-02  8.75377445D-04 -1.05720451D-02\r\n -1.05720451D-02 -1.05720451D-02 -1.05720451D-02  5.00215683D-04  2.21163896D-03\r\n  8.70839227D-04  6.27855837D-01 -5.45626283D-01 -5.45626283D-01 -5.45626283D-01\r\n -5.45626283D-01  1.88216381D-02 -5.45626283D-01  1.03004798D-02  6.11335933D-02\r\n  6.11335933D-02 -1.88998535D-01 -1.88998535D-01 -1.88998535D-01 -1.88998535D-01\r\n -1.88998535D-01  2.97469385D-02 -1.88998535D-01  1.62795484D-02  9.66195017D-02\r\n  9.66195017D-02 -3.90729122D-02 -3.90729122D-02 -3.90729122D-02 -3.90729122D-02\r\n -3.90729122D-02 -3.90729122D-02 -3.90729122D-02  3.71357752D-03  2.20401697D-02\r\n  2.20401697D-02 -3.93182158D-01 -3.93182158D-01 -3.93182158D-01 -3.93182158D-01\r\n -3.93182158D-01  3.15687060D-02 -3.93182158D-01  1.72765423D-02  1.02536693D-01\r\n  1.02536693D-01  1.67131245D+00 -3.28687608D-01 -1.64343804D-01  2.97306397D-05\r\n  8.07423727D-04  2.75007710D-02  1.33185962D-03  3.93917151D-02  7.23160058D-02\r\n  2.04517543D-02  5.90625890D-02 -1.28545640D-02 -4.63634431D-02 -8.70002031D-01\r\n  4.37857695D-02 -1.76200569D-02 -4.21766937D-03  4.55968589D-01 -2.80381632D+00\r\n -2.80381632D+00 -2.80381632D+00 -2.80381632D+00 -2.80381632D+00 -2.80381632D+00\r\n  1.04424879D-02  1.61793381D-01  1.61793381D-01  1.57031372D-01 -7.97282577D-01\r\n -7.97282577D-01 -7.97282577D-01 -7.97282577D-01 -7.97282577D-01 -7.97282577D-01\r\n  2.89742295D-02  1.28105819D-01  5.04420325D-02 -9.07425106D-01 -9.07425106D-01\r\n -9.07425106D-01 -9.07425106D-01 -9.07425106D-01 -9.07425106D-01 -9.07425106D-01\r\n  3.30047049D-02  5.11366904D-01  5.11366904D-01  1.58726871D-01 -6.18981421D-01\r\n  5.12523726D-02 -6.18981421D-01 -6.18981421D-01 -6.18981421D-01 -6.18981421D-01\r\n  2.92870700D-02  1.29488990D-01  5.09866662D-02  7.75558501D-02  7.75558501D-02\r\n  7.75558501D-02  7.75558501D-02  7.75558501D-02 -1.12975061D-01  7.75558501D-02\r\n  1.27236603D-03  7.55152293D-03  7.55152293D-03  8.05267543D-02  8.05267543D-02\r\n  8.05267543D-02  8.05267543D-02  8.05267543D-02 -1.12885997D-01  8.05267543D-02\r\n  1.32110610D-03  7.84079637D-03  7.84079637D-03 -9.94591713D-02 -9.94591713D-02\r\n -9.94591713D-02 -9.94591713D-02 -9.94591713D-02 -9.94591713D-02 -9.94591713D-02\r\n  9.45282448D-03  5.61027341D-02  5.61027341D-02  1.14812307D-01  1.14812307D-01\r\n  1.14812307D-01  1.14812307D-01  1.14812307D-01 -1.11858197D-01  1.14812307D-01\r\n  1.88358827D-03  1.11791408D-02  1.11791408D-02 -2.00000000D+00 -1.00000000D+00\r\n -1.11589003D-02 -6.79647923D-03  1.94025785D-03 -4.64311987D-03  1.36367977D-03\r\n  4.70969081D-03 -1.26966089D-03  7.61918724D-03 -1.00000000D+00  1.06317788D-01\r\n -6.53763413D-01 -6.53763413D-01 -6.53763413D-01 -6.53763413D-01 -6.53763413D-01\r\n -6.53763413D-01  2.43486557D-03  3.77252176D-02  3.77252176D-02  4.11161855D-02\r\n -2.08755851D-01 -2.08755851D-01 -2.08755851D-01 -2.08755851D-01 -2.08755851D-01\r\n -2.08755851D-01  7.58644473D-03  3.35424840D-02  1.32074496D-02 -1.98312685D-01\r\n -1.98312685D-01 -1.98312685D-01 -1.98312685D-01 -1.98312685D-01 -1.98312685D-01\r\n -1.98312685D-01  7.21299369D-03  1.11756369D-01  1.11756369D-01  5.44188842D-02\r\n -2.12215364D-01  1.75716747D-02 -2.12215364D-01 -2.12215364D-01 -2.12215364D-01\r\n -2.12215364D-01  1.00409575D-02  4.43947949D-02  1.74805783D-02  5.57472408D-01\r\n -4.84460890D-01 -4.84460890D-01 -4.84460890D-01 -4.84460890D-01  1.67117082D-02\r\n -4.84460890D-01  9.14578326D-03  5.42804413D-02  5.42804413D-02 -2.85272539D-01\r\n -2.85272539D-01 -2.85272539D-01 -2.85272539D-01 -2.85272539D-01  4.48997393D-02\r\n -2.85272539D-01  2.45721899D-02  1.45836532D-01  1.45836532D-01 -2.04982370D-01\r\n -2.04982370D-01 -2.04982370D-01 -2.04982370D-01 -2.04982370D-01 -2.04982370D-01\r\n -2.04982370D-01  1.94819868D-02  1.15626052D-01  1.15626052D-01 -2.12087378D-01\r\n -2.12087378D-01 -2.12087378D-01 -2.12087378D-01 -2.12087378D-01  1.70285534D-02\r\n -2.12087378D-01  9.31918249D-03  5.53095713D-02  5.53095713D-02  1.46780527D+00\r\n -5.32194793D-01 -2.66097397D-01  6.53083064D-03  1.70512833D-02  2.03899294D-02\r\n  2.67378725D-02  3.49783003D-02  1.09160982D-01  1.07301265D-01  3.18611152D-02\r\n -5.97859584D-02 -3.35545868D-01 -2.65876949D-01 -1.57820597D-01 -8.70056510D-01\r\n  4.26713973D-02 -7.06640184D-02 -3.78513522D-03  1.96210727D-01  1.96210727D-01\r\n  1.96210727D-01  1.96210727D-01  1.96210727D-01  1.96210727D-01  1.96210727D-01\r\n -9.96064246D-02  6.96223304D-02  6.96223304D-02  1.89191252D-01  1.54341772D-01\r\n  1.54341772D-01  1.54341772D-01  1.54341772D-01  1.54341772D-01  1.54341772D-01\r\n -2.62691885D-01  1.54341772D-01  6.07725158D-02  1.69322357D-01  1.69322357D-01\r\n  1.69322357D-01  1.69322357D-01  1.69322357D-01  1.69322357D-01  1.69322357D-01\r\n -1.00222215D-01  6.00814112D-02  6.00814112D-02  7.46707991D-02  6.09162562D-02\r\n  2.41109487D-02  6.09162562D-02  6.09162562D-02  6.09162562D-02  6.09162562D-02\r\n -2.83822298D-01  6.09162562D-02  2.39859503D-02  4.64772396D-02  4.64772396D-02\r\n  4.64772396D-02  4.64772396D-02  4.64772396D-02  1.39327801D-03  4.64772396D-02\r\n -6.23375066D-02  4.52543469D-03  4.52543469D-03  3.17638852D-02  3.17638852D-02\r\n  3.17638852D-02  3.17638852D-02  3.17638852D-02  9.52206377D-04  3.17638852D-02\r\n -6.25788867D-02  3.09281261D-03  3.09281261D-03  2.72320695D-02  2.72320695D-02\r\n  2.72320695D-02  2.72320695D-02  2.72320695D-02  2.72320695D-02  2.72320695D-02\r\n -6.26532361D-02  2.65155477D-03  2.65155477D-03  1.45535357D-02  1.45535357D-02\r\n  1.45535357D-02  1.45535357D-02  1.45535357D-02  4.36280679D-04  1.45535357D-02\r\n -6.28612414D-02  1.41706085D-03  1.41706085D-03 -5.00000000D-01 -1.00000000D+00\r\n  5.67007899D-01  3.68021756D-01  5.04498124D-01  1.71694726D-01  1.87478885D-01\r\n  1.48706645D-01  1.58462361D-01  5.24044745D-02 -1.57417119D-01 -2.47411415D-01\r\n -1.41924486D-01 -8.90000045D-01  2.39348169D-02 -3.44784945D-01  2.74278283D-01\r\n  2.74278283D-01  2.74278283D-01  2.74278283D-01  2.74278283D-01  2.74278283D-01\r\n  2.74278283D-01  6.28145831D-03 -2.69419193D-01 -2.69419193D-01  1.52858287D-01\r\n  1.24701418D-01  1.24701418D-01  1.24701418D-01  1.24701418D-01  1.24701418D-01\r\n  1.24701418D-01  2.82042436D-02 -1.19109857D+00  4.91015427D-02  4.98320878D-01\r\n  4.98320878D-01  4.98320878D-01  4.98320878D-01  4.98320878D-01  4.98320878D-01\r\n  4.98320878D-01  1.14124306D-02 -3.29651117D-01 -3.29651117D-01  2.46326566D-01\r\n  2.00952619D-01  7.95380175D-02  2.00952619D-01  2.00952619D-01  2.00952619D-01\r\n  2.00952619D-01  4.54503000D-02 -1.11484730D+00  7.91256726D-02  3.50749463D-01\r\n  3.50749463D-01  3.50749463D-01  3.50749463D-01  3.50749463D-01  1.05146412D-02\r\n  3.50749463D-01  5.75432694D-03 -3.40347946D-01  3.41520645D-02  2.85520315D-01\r\n  2.85520315D-01  2.85520315D-01  2.85520315D-01  2.85520315D-01  8.55922513D-03\r\n  2.85520315D-01  4.68419027D-03 -3.46699238D-01  2.78007798D-02  2.37027302D-01\r\n  2.37027302D-01  2.37027302D-01  2.37027302D-01  2.37027302D-01  2.37027302D-01\r\n  2.37027302D-01  3.88862356D-03 -3.51420939D-01  2.30790731D-02  3.56762469D-01\r\n  3.56762469D-01  3.56762469D-01  3.56762469D-01  3.56762469D-01  1.06948968D-02\r\n  3.56762469D-01  5.85297495D-03 -3.39762479D-01  3.47375460D-02  7.39657879D-03\r\n -1.99260342D+00 -9.96301711D-01  5.11565208D-02  6.72518909D-02  9.58291367D-02\r\n  1.28103361D-01  2.38389209D-01  2.25222245D-01  2.32392117D-01  2.16449484D-01\r\n -1.55363604D-02 -2.75162965D-01 -6.60882518D-02 -1.02282472D-01 -1.53743282D-01\r\n -8.90000701D-01 -4.75550555D-02  9.31972265D-01  9.31972265D-01  9.31972265D-01\r\n  9.31972265D-01  9.31972265D-01  9.31972265D-01  9.31972265D-01  2.13438161D-02\r\n -9.15461600D-01 -9.15461600D-01  1.19320869D-01  9.73416790D-02  9.73416790D-02\r\n  9.73416790D-02  9.73416790D-02  9.73416790D-02  9.73416790D-02  2.20161770D-02\r\n  9.73416790D-02 -4.79771465D-01  1.08861959D+00  1.08861959D+00  1.08861959D+00\r\n  1.08861959D+00  1.08861959D+00  1.08861959D+00  1.08861959D+00  2.49313172D-02\r\n -7.20147789D-01 -7.20147789D-01  1.08071260D-01  8.81642774D-02  3.48958485D-02\r\n  8.81642774D-02  8.81642774D-02  8.81642774D-02  8.81642774D-02  1.99404843D-02\r\n  8.81642774D-02 -4.83385086D-01  2.93100953D-01  2.93100953D-01  2.93100953D-01\r\n  2.93100953D-01  2.93100953D-01  8.78647529D-03  2.93100953D-01  4.80855675D-03\r\n  2.85388995D-02 -3.45961124D-01  2.17549220D-01  2.17549220D-01  2.17549220D-01\r\n  2.17549220D-01  2.17549220D-01  6.52161241D-03  2.17549220D-01  3.56906978D-03\r\n  2.11825129D-02 -3.53317499D-01  3.01923811D-01  3.01923811D-01  3.01923811D-01\r\n  3.01923811D-01  3.01923811D-01  3.01923811D-01  3.01923811D-01  4.95330291D-03\r\n  2.93979701D-02 -3.45102042D-01  5.59506476D-01  5.59506476D-01  5.59506476D-01\r\n  5.59506476D-01  5.59506476D-01  1.67726837D-02  5.59506476D-01  9.17915348D-03\r\n  5.44784926D-02 -3.20021540D-01  6.95431352D-01 -1.30456865D+00 -6.52284324D-01\r\n  1.73825145D-01  1.33323938D-01  2.09345996D-01  1.42736718D-01  1.99208006D-01\r\n  1.71605751D-01  2.96019554D-01  3.39455217D-01 -2.33187303D-01 -1.43305426D-02\r\n -3.65852825D-02 -3.50010514D-01 -3.68325382D-01 -8.90000045D-01 -4.76517156D-02\r\n  4.57370246D-04 -2.09954262D+00 -9.99782205D-01 -1.07030303D-03 -1.93744991D-03\r\n -1.54613005D-03 -2.59090355D-03 -3.22100311D-03 -3.45216854D-03 -4.05561412D-03\r\n -3.55400215D-03  1.00000000D+00 -9.07458216D-02 -1.16984315D-01 -1.33410409D-01\r\n -8.70000362D-01 -2.90658250D-02  9.00660157D-01 -1.19933975D+00 -5.71114182D-01\r\n  1.00000000D+00 -8.70074153D-01 -2.14263145D-02  2.60216546D+00 -2.97834694D-01\r\n -1.02701619D-01  1.00000000D+00 -1.92899816D-02 -8.69974673D-01  3.76543887D-02\r\n -8.59325007D-03 -2.32234877D-03 -2.00000000D+00 -1.00000000D+00 -5.97090367D-03\r\n -3.10818246D-03 -3.80347972D-03 -1.39464473D-03 -1.42943056D-03 -1.11747673D-03\r\n -1.24684128D-03 -3.89749010D-04 -1.62022635D-01  1.00000000D+00 -3.91151533D-02\r\n -1.34885684D-01 -1.17574222D-01 -2.08823266D-03 -1.33590531D-02 -3.53096239D-02\r\n -8.69999945D-01  4.84563895D-02 -4.03310657D-01 -1.39999998D+00 -1.00000000D+00\r\n  1.00000000D+00 -2.96438169D-02 -8.69649827D-01  1.07462266D-02 -1.38558960D+00\r\n -9.52560804D-04  1.24517657D-01 -1.07548237D+00 -8.96235287D-01 -9.75699630D-03\r\n  1.00000000D+00 -8.69999290D-01 -7.12292502D-03  7.48468280D-01 -1.25153172D+00\r\n -6.25765860D-01  1.00000000D+00 -8.69565189D-01 -5.48300613D-03  1.67540276D+00\r\n -3.24597210D-01 -1.62298605D-01 -5.64882183D-04 -5.86885144D-04 -3.88702523D-04\r\n -6.18933933D-04 -6.81592501D-04 -7.42134813D-04 -4.25319507D-04 -7.78341491D-04\r\n  1.00000000D+00 -3.24237466D-01 -8.06020573D-03 -6.01767702D-03 -4.23720069D-02\r\n -1.60365067D-02 -8.70012224D-01  4.07752655D-02 -1.11877225D-01 -1.04968902D-03\r\n  6.68755710D-01 -5.31244338D-01 -4.42703605D-01  1.00000000D+00 -8.70578110D-01\r\n -1.33256649D-03  6.27053499D-01 -1.37294650D+00 -6.86473250D-01  1.00000000D+00\r\n -8.69837284D-01 -9.19193670D-04  1.86955050D-01 -1.01304495D+00 -8.44204128D-01\r\n  1.00000000D+00 -8.69710445D-01 -2.45653326D-03  7.21822023D-01 -1.27817798D+00\r\n -6.39088988D-01  1.00000000D+00 -8.88888896D-01 -4.83603566D-04  1.05930507D-01\r\n -3.94069493D-01 -7.88138986D-01  1.00000000D+00 -8.70722413D-01 -4.03519627D-03\r\n -5.00000000D-01 -1.00000000D+00  1.00000000D+00 -1.44721544D-03 -1.00000000D+00\r\n  2.69034058D-01 -2.30965927D-01  1.20000005D+00  1.00000000D+00 -6.98827021D-03\r\n -4.22448991D-03 -8.70033681D-01  1.82339847D-02 -6.98937196D-03  1.51235133D-01\r\n -3.48764867D-01 -6.97529733D-01  1.00000000D+00 -2.95740426D-01 -1.60700306D-01\r\n -1.32129028D-01 -5.11926599D-03 -8.70001733D-01  7.98794478D-02 -2.72300512D-01\r\n -9.32077994D-04 -5.00000000D-01 -1.00000000D+00  1.00000000D+00 -1.44242674D-01\r\n -8.69969308D-01  4.20977129D-03 -1.25440717D-01 -5.00000000D-01 -1.00000000D+00\r\n  1.00000000D+00 -3.19625288D-02 -8.68035197D-01 -1.29999995D+00 -1.00000000D+00\r\n  1.00000000D+00 -5.91685250D-02 -1.59905537D-03 -8.69984448D-01  1.75757363D-01\r\n -1.11488414D+00  2.00484842D-01 -1.69951510D+00 -8.94481659D-01  1.00000000D+00\r\n -8.69993567D-01 -1.05654960D-02  1.61500096D+00 -3.84999037D-01 -1.92499518D-01\r\n -1.03561732D-03 -8.33546976D-04 -7.43498676D-04 -8.00973328D-04 -7.52254389D-04\r\n -7.40913558D-04 -7.75766151D-04 -7.33237015D-04 -4.31161869D-04 -4.00092453D-03\r\n -9.04091913D-03 -4.43976279D-03 -4.15170519D-03 -4.05931100D-03 -3.40312958D-01\r\n  9.96429563D-01 -3.20973806D-03 -3.86491860D-03 -3.95374373D-03 -5.08075068D-03\r\n -1.20204582D-03 -8.69974256D-01  2.71766007D-01 -1.29452288D-01 -1.27621123D-03\r\n  2.23066592D+00 -1.16933417D+00 -3.43921810D-01 -1.85023677D-02 -1.48349488D-02\r\n -1.32394843D-02 -1.42659442D-02 -1.33985188D-02 -1.31980311D-02 -1.38182044D-02\r\n -1.30513879D-02 -3.55932601D-02 -5.53016691D-03 -1.12575263D-01 -4.02331427D-02\r\n -1.26768902D-01 -3.23383622D-02 -1.40888244D-02 -1.03382498D-01 -6.01734221D-02\r\n -1.15011364D-01 -6.96121082D-02 -5.99461142D-04  8.06271911D-01 -1.01612881D-01\r\n -4.95907036D-04 -2.17979099D-03 -3.63733061D-02 -2.40057558D-02 -1.58976257D-01\r\n -5.14993165D-03 -6.66899681D-02 -7.21485987D-02 -8.13447908D-02 -7.39258807D-03\r\n -2.08374932D-02 -8.69999588D-01  2.35442594D-02 -4.97347564D-02 -2.55885925D-02\r\n  2.04773259D+00 -3.52267474D-01 -1.46778107D-01 -1.61040970D-03 -1.65919599D-03\r\n -1.09910860D-03 -1.74943579D-03 -1.92774378D-03 -2.09857640D-03 -1.20108563D-03\r\n -2.20202422D-03 -6.64001377D-03 -1.42286755D-02  9.77918148D-01 -4.70131030D-03\r\n -6.87512336D-04 -3.48676136D-03 -8.70021164D-01  6.68438077D-01 -2.79838085D-01\r\n -1.36331830D-04  2.33849168D-01 -2.66150832D-01 -5.32301664D-01  1.00000000D+00\r\n -8.70003164D-01 -3.26989894D-03  2.91807085D-01 -8.08192909D-01 -7.34720826D-01\r\n -3.13579403D-02  9.14857388D-01 -1.21057041D-01 -3.46712917D-02 -8.69999170D-01\r\n -1.72352381D-02  1.14481020D+00 -8.55189800D-01 -4.27594900D-01 -4.18436378D-02\r\n -9.39895660D-02 -6.50645867D-02 -4.93461937D-02 -4.62170057D-02  1.00000000D+00\r\n -4.83944751D-02 -8.69988739D-01  5.37051633D-02 -4.83965762D-02 -1.48378145D-02\r\n  1.42642903D+00 -5.73570967D-01 -2.86785483D-01 -2.57495135D-01 -6.34217123D-03\r\n  1.00000000D+00 -1.03614554D-02 -8.70010138D-01 -3.37993901D-04  4.85329628D-01\r\n -1.51467037D+00 -7.57335186D-01 -1.51637703D-01 -1.72124177D-01 -3.18911761D-01\r\n -4.52379622D-02 -4.50736023D-02 -3.83139811D-02 -2.15203106D-01  7.94479668D-01\r\n -1.68030038D-02 -5.20322053D-03 -8.45131576D-02 -8.70004654D-01  2.90093929D-01\r\n -6.60795033D-01 -1.66454222D-02 -5.00000000D-01 -1.00000000D+00 -3.66790360D-03\r\n -1.06854446D-03 -8.41675978D-03 -8.81052285D-04 -1.08826561D-02 -3.09364079D-03\r\n -5.81978704D-04 -1.25210162D-03 -6.27377944D-04 -1.90549623D-03 -4.55192028D-04\r\n -4.03084466D-03 -5.01968898D-03 -3.67323461D-04 -6.59003854D-03 -3.65600252D-04\r\n -9.89085878D-04 -4.27527772D-03 -8.09862686D-05 -4.04128386D-03 -1.08135282D-03\r\n -3.92236834D-04 -1.48049882D-03 -4.32409951D-03 -6.57516345D-03  9.99062061D-01\r\n -3.75950173D-03 -4.98532085D-03 -1.80093071D-03 -2.25895038D-03 -5.07186539D-03\r\n -1.40905408D-02 -5.41200675D-02 -8.70759308D-01  2.29801148D-01 -2.15929925D-01\r\n -7.27965671D-04  1.27107942D+00 -1.28920481D-01 -9.20860618D-02 -2.01665331D-03\r\n -8.92450362D-02 -4.87057231D-02 -8.49580914D-02  7.97954261D-01 -1.26410509D-02\r\n -7.52177229D-03 -1.20873482D-03 -8.69994819D-01  1.69435248D-01 -1.62539542D-01\r\n -2.41443879D-04 -2.00000000D+00 -1.00000000D+00 -1.72134973D-02  7.40929484D-01\r\n -1.00000000D+00 -3.88732915D-05  3.33289057D-01 -9.66710925D-01 -7.43623793D-01\r\n -4.55313362D-02  9.59176183D-01 -1.86752286D-02 -8.70153308D-01  1.95702668D-02\r\n -6.02502711D-02 -4.37467685D-03  8.34249258D-02 -4.16575074D-01 -8.33150148D-01\r\n -1.81939617D-01 -3.38542223D-01 -3.96428585D-01 -1.88573435D-01 -1.47568300D-01\r\n -1.13464832D-01 -1.24057271D-02 -6.68724552D-02 -1.99355744D-02 -7.83251971D-03\r\n  5.87145507D-01 -2.02887654D-02 -1.17915452D-01 -7.41321817D-02 -2.36270837D-02\r\n -8.69995236D-01  7.48817250D-02 -1.90253779D-01 -3.81938345D-03  1.04966235D+00\r\n -1.50337696D-01 -1.25281408D-01 -7.97772198D-04 -8.20181100D-04 -5.43315487D-04\r\n -8.64872884D-04 -9.53199051D-04 -1.03727891D-03 -5.93783450D-04 -1.08829024D-03\r\n -2.66206125D-03 -2.22796991D-01 -1.24763541D-01 -8.23399574D-02 -2.43991031D-03\r\n -1.05415531D-01 -5.18004317D-03 -2.26804917D-03 -4.08953428D-03 -2.41064783D-02\r\n -2.66595520D-02 -3.64078544D-02 -1.37097631D-02 -1.21616852D-03 -1.53590724D-01\r\n -1.81663513D-01 -1.38760403D-01 -8.87066359D-04  1.00000000D+00 -3.37022962D-03\r\n -1.35791150D-03 -1.68195146D-03 -8.69997799D-01  3.93045694D-02 -4.44007665D-02\r\n -7.38454866D-04 -2.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.61861870D-02\r\n -8.67007475D-04 -1.00000000D+00 -5.00000000D-01 -1.00000000D+00 -5.30493185D-02\r\n -1.38881821D-02 -2.16033772D-01 -2.95067728D-01 -7.87093677D-03  1.00000000D+00\r\n -8.70000243D-01 -2.00000000D+00 -1.00000000D+00 -8.52278376D-04 -8.45697825D-04\r\n -5.70983102D-04 -8.96822661D-04 -9.94418398D-04 -1.07432459D-03 -6.58257341D-04\r\n -1.12529914D-03 -3.47715081D-03 -1.77065760D-03 -2.27015419D-03 -3.08119413D-03\r\n -3.78716434D-03 -3.86095257D-03 -2.71422835D-03 -2.12809048D-03 -2.44879792D-03\r\n -2.64982809D-03 -2.20288569D-03 -1.82076811D-03 -4.05994570D-03 -2.67857150D-03\r\n -3.63652292D-03 -2.55754474D-03 -2.32522679D-03 -8.87275673D-04 -2.17509014D-03\r\n -2.53010611D-03 -2.58888165D-03 -2.19188794D-03 -3.27900588D-03 -2.66205659D-03\r\n -2.19861837D-03 -1.94378418D-03 -2.34935014D-03 -3.08026723D-03 -3.49826226D-03\r\n -3.59485205D-03 -9.41671722D-04 -4.55429452D-03 -3.34591372D-03 -2.36574560D-03\r\n -3.96497606D-04 -2.96347367D-04  9.97949481D-01 -1.71580527D-03 -3.45474901D-03\r\n -1.88774109D-04 -1.46566963D-04 -4.98844869D-03 -2.03209203D-02 -1.41712539D-02\r\n -2.03225799D-02 -3.15105310D-03 -1.99997593D-02 -2.00722013D-02 -2.00752821D-02\r\n -1.99858136D-02 -1.99983530D-02 -1.99913085D-02 -7.99998567D-02 -8.00038800D-02\r\n -7.99991563D-02 -2.00005732D-02 -1.98985543D-02 -2.00221576D-02 -1.99998934D-02\r\n -1.94552504D-02 -2.00004857D-02 -2.17391308D-02 -1.99947488D-02 -1.98446941D-02\r\n -2.00250316D-02 -2.00445447D-02 -1.90114081D-02 -1.99775547D-02 -1.99930165D-02\r\n -2.00082418D-02 -2.05278583D-02 -1.99066866D-02 -2.00088024D-02 -2.00148020D-02\r\n -2.00016722D-02 -1.99828986D-02 -1.99990626D-02 -2.00033169D-02 -1.99887399D-02\r\n -1.99961830D-02 -1.99976135D-02 -1.93861071D-02 -1.99948251D-02 -1.98376905D-02\r\n -2.00031791D-02 -1.99988130D-02 -1.99998822D-02 -1.00000000D+00 -5.10172583D-02\r\n -2.00000000D+00 -1.00000000D+00 -8.46332218D-03 -8.40655249D-03 -5.67755196D-03\r\n -8.92104488D-03 -9.88750812D-03 -1.06834034D-02 -6.54513668D-03 -1.11905383D-02\r\n -3.45831774D-02 -1.76194515D-02 -2.25829966D-02 -3.06469649D-02 -3.76394801D-02\r\n -3.84055004D-02 -2.69967895D-02 -2.11716071D-02 -2.43058372D-02 -2.64700912D-02\r\n -2.19627712D-02 -1.78093892D-02 -4.03337888D-02 -2.60714293D-02 -3.58832814D-02\r\n -2.54394505D-02 -2.31361799D-02 -8.78402870D-03 -2.16305777D-02 -2.51667406D-02\r\n -2.57373042D-02 -2.18023974D-02 -3.26811634D-02 -2.64655948D-02 -2.18711272D-02\r\n -1.93342511D-02 -2.33593863D-02 -3.06346249D-02 -3.48275639D-02 -3.57152671D-02\r\n -9.47211031D-03 -4.53286879D-02 -3.32781151D-02 -2.35274453D-02 -3.91541375D-03\r\n -2.94704316D-03 -2.03939229D-02  9.82934237D-01 -3.43588740D-02 -1.87747960D-03\r\n -1.45681656D-03 -2.41378937D-02 -5.41237667D-02 -5.42966351D-02 -5.41290306D-02\r\n -5.59503818D-03 -1.10000402D-01 -1.10036097D-01 -1.09786704D-01 -1.09984562D-01\r\n -1.09999612D-01 -1.09952196D-01 -3.00000962D-02 -2.99953986D-02 -3.00008152D-02\r\n -1.09999068D-01 -1.10027306D-01 -1.10003166D-01 -1.10000178D-01 -1.10894933D-01\r\n -1.10000238D-01 -1.08695649D-01 -1.09992996D-01 -1.09577231D-01 -1.10137671D-01\r\n -1.10244997D-01 -1.11111112D-01 -1.10266164D-01 -1.09988779D-01 -1.10005237D-01\r\n -1.10022433D-01 -1.11436948D-01 -1.10108867D-01 -1.09997630D-01 -1.10010929D-01\r\n -1.09998740D-01 -1.09995946D-01 -1.09997772D-01 -1.09997511D-01 -1.10022523D-01\r\n -1.09993681D-01 -1.09997720D-01 -1.09854601D-01 -1.10010341D-01 -1.10009015D-01\r\n -1.10001586D-01 -1.10003375D-01 -1.09999895D-01 -1.00000000D+00 -2.22929522D-01\r\n -2.00000000D+00 -1.00000000D+00  1.00000000D+00 -4.99400884D-01 -6.82299674D-01\r\n -4.40645143D-02 -6.62580967D-01 -1.00000000D+00 -2.00000000D+00 -1.00000000D+00\r\n -2.69557815D-03 -2.16041761D-03 -1.92859373D-03 -2.07822118D-03 -1.95203384D-03\r\n -1.92230428D-03 -2.01220834D-03 -1.90132763D-03 -2.23271595D-03 -1.71556475D-03\r\n -2.35313643D-03 -2.36013927D-03 -4.83189942D-03 -3.31762480D-03 -2.35300022D-03\r\n -3.10212583D-03 -3.15712788D-03 -3.01629351D-03 -2.83070817D-03 -2.67425319D-03\r\n -3.69209819D-03 -3.39285703D-03 -3.32982815D-03 -7.91742802D-02 -2.81903427D-03\r\n -2.80701765D-03 -3.22098448D-03 -2.75478722D-03 -2.66793137D-03 -2.39829789D-03\r\n -2.96441489D-03 -2.02150992D-03 -1.89424248D-03 -1.69487623D-03 -2.36322428D-03\r\n -2.80019036D-03 -4.46264818D-03 -4.54844814D-03 -1.82795106D-03 -4.43343259D-03\r\n -3.45091801D-03 -1.98499765D-03 -3.60151986D-03 -2.71283323D-03 -3.25249461D-03\r\n -1.39743254D-01 -4.56520617D-02  1.00000000D+00 -2.68247048D-03 -1.00000000D+00\r\n -9.42663550D-02 -2.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.39938340D-01 -2.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -2.00000000D+00 -1.00000000D+00  1.00000000D+00 -1.00000000D+00 -2.00000000D+00\r\n -1.00000000D+00 -2.60716975D-01  1.00000000D+00 -1.00000000D+00  5.00000000D-01\r\n -2.00441820D-04  1.00000000D+00 -8.81728047D-05  4.99836445D-01  5.00000000D-01\r\n -1.08516833D-03 -9.30146081D-04 -1.00851082D-03 -1.46263081D-03 -2.09262152D-03\r\n -2.13684351D-03 -2.50200182D-03 -2.27604178D-03  1.00000000D+00 -4.07628454D-02\r\n  4.54577208D-01  5.00000000D-01 -1.40725030D-03 -1.20961515D-03 -1.31149800D-03\r\n -1.90175441D-03 -2.72121769D-03 -2.77883280D-03 -3.25281033D-03 -2.96070473D-03\r\n  1.00000000D+00 -6.51841611D-02  4.23311949D-01 -4.71892297D-01  2.81077027D-02\r\n -9.43784595D-01 -5.77269914D-03 -4.95510874D-03 -5.37293730D-03 -7.79202906D-03\r\n -1.11498525D-02 -1.13844210D-02 -1.33284107D-02 -1.21284807D-02 -3.59768905D-02\r\n  1.00000000D+00 -1.52490258D-01  9.62755829D-02 -1.89226482D-03 -1.67131233D+00\r\n  3.28687668D-01 -8.35656166D-01 -1.97824225D-01 -1.95589870D-01  1.00000000D+00\r\n -4.37857695D-02  1.76200569D-02 -2.14460250D-02  2.00000000D+00  1.00000000D+00\r\n -1.46780527D+00  5.32194734D-01 -7.33902633D-01 -8.90327096D-02  1.00000000D+00\r\n -4.26713973D-02  7.06640184D-02 -1.04394881D-02  5.00000000D-01 -1.53060555D-01\r\n -1.32922277D-01 -1.45159997D-02  1.00000000D+00 -2.39348169D-02  3.44784945D-01\r\n -7.39663653D-03  1.99260342D+00 -3.69831827D-03  1.00000000D+00 -1.76526592D-04\r\n -6.95431292D-01  1.30456877D+00 -3.47715646D-01  1.00000000D+00 -2.54018791D-02\r\n -4.57389804D-04  2.09954262D+00 -2.17804685D-04  1.00000000D+00 -6.33205173D-06\r\n -9.00660157D-01  1.19933975D+00 -4.28885818D-01  1.00000000D+00 -1.60903763D-02\r\n -2.60216546D+00  2.97834665D-01 -8.97298396D-01 -5.93723962D-04  1.00000000D+00\r\n -3.76543887D-02  8.59325007D-03 -2.02902332D-02  2.00000000D+00 -4.65898141D-02\r\n -2.71990262D-02  1.00000000D+00 -4.84563895D-02  4.03310657D-01  1.39999998D+00\r\n -3.08300077D-04  1.00000000D+00 -1.07462266D-02  1.38558960D+00 -1.24517642D-01\r\n  1.07548237D+00 -1.03764698D-01 -3.48328426D-02  1.00000000D+00 -8.24680901D-04\r\n -7.48468280D-01  1.25153172D+00 -3.74234140D-01  1.00000000D+00 -3.27906664D-03\r\n -1.67540276D+00  3.24597239D-01 -8.37701380D-01 -2.89995759D-03  1.00000000D+00\r\n -4.07752655D-02  1.11877225D-01 -5.41795138D-03 -6.68755710D-01  5.31244338D-01\r\n -5.57296395D-01  1.00000000D+00 -1.67749810D-03 -6.27053499D-01  1.37294650D+00\r\n -3.13526750D-01  1.00000000D+00 -4.19815013D-04 -1.86955050D-01  1.01304495D+00\r\n -1.55795872D-01 -4.62385714D-02  1.00000000D+00 -4.53347369D-04 -7.21822023D-01\r\n  1.27817798D+00 -3.60911012D-01  1.00000000D+00 -2.73104146D-04 -1.05930492D-01\r\n  3.94069523D-01 -2.11860985D-01 -1.68937333D-02 -1.85398629D-03  1.00000000D+00\r\n -1.08470803D-03  5.00000000D-01 -1.68574753D-03  1.00000000D+00 -2.69034058D-01\r\n  2.30965927D-01 -1.20000005D+00 -1.00000000D+00 -3.55678231D-01 -3.18024121D-02\r\n -8.37958045D-03  1.00000000D+00 -1.82339847D-02  6.98937196D-03 -3.84520710D-04\r\n -1.51235133D-01  3.48764867D-01 -3.02470267D-01 -3.91993411D-02 -6.69464841D-02\r\n -2.91612893D-01 -1.06548648D-02  1.00000000D+00 -7.98794478D-02  2.72300512D-01\r\n -4.04177612D-04  5.00000000D-01 -2.50663608D-02 -1.26683037D-03  1.00000000D+00\r\n -4.20977129D-03  1.25440717D-01  5.00000000D-01 -9.76003241D-03  1.00000000D+00\r\n  1.29999995D+00 -9.82436165D-03  1.00000000D+00 -1.75757363D-01  1.11488414D+00\r\n -2.00484797D-01  1.69951510D+00 -1.05518319D-01 -1.29680149D-03  1.00000000D+00\r\n -1.24636805D-03 -1.61500096D+00  3.84999037D-01 -8.07500482D-01 -1.11489906D-03\r\n -1.57474761D-03 -3.36079829D-04 -1.46485993D-03 -7.46365869D-04 -5.04391151D-04\r\n -5.86504175D-04 -5.21592912D-04 -6.88093295D-03 -1.04867527D-02 -3.19255888D-01\r\n -1.61293726D-02  1.00000000D+00 -2.71766007D-01  1.29452288D-01 -5.35347452D-03\r\n -2.23066592D+00  1.16933429D+00 -6.56078160D-01 -7.18148332D-03  1.00000000D+00\r\n -2.35442594D-02  4.97347564D-02 -4.88137603D-02 -2.04773259D+00  3.52267474D-01\r\n -8.53221893D-01 -2.72035366D-03 -1.77766650D-03 -2.38104025D-03 -8.15090723D-04\r\n -9.42158105D-04 -6.70078967D-04 -7.60167604D-04 -2.11644132D-04 -5.66360168D-02\r\n -1.50002027D-03 -4.91754897D-03 -4.01309192D-01 -1.08380883D-03 -4.96166467D-04\r\n  1.00000000D+00 -6.68438077D-01  2.79838085D-01 -7.92497536D-04 -2.33849168D-01\r\n  2.66150832D-01 -4.67698336D-01  1.00000000D+00 -2.87304446D-03 -2.91807055D-01\r\n  8.08192968D-01 -2.65279144D-01  1.00000000D+00 -6.22297544D-03 -1.14481020D+00\r\n  8.55189800D-01 -5.72405100D-01 -5.58000579D-02 -8.98083020D-03  1.00000000D+00\r\n -5.37051633D-02  4.83965762D-02 -1.98628195D-02 -1.42642903D+00  5.73570967D-01\r\n -7.13214517D-01 -6.67206198D-02  1.00000000D+00 -8.40566121D-04 -4.85329628D-01\r\n  1.51467037D+00 -2.42664814D-01 -8.96874291D-04 -1.32383301D-03 -1.32967182D-03\r\n -1.28170592D-03 -1.33668678D-03 -1.33038755D-03 -1.32171414D-03 -1.25945604D-03\r\n -2.33388562D-02 -1.62985370D-01 -3.80810276D-02 -6.71791732D-02 -6.75262418D-03\r\n -2.05335543D-01 -1.06370752D-03 -6.19772589D-04 -1.66779512D-03  1.00000000D+00\r\n -2.90093929D-01  6.60795033D-01 -5.33351488D-03  5.00000000D-01 -5.65960491D-03\r\n -2.14861985D-03 -1.23228477D-02 -1.28709001D-03 -7.76296109D-03 -3.21339467D-03\r\n -8.52899859D-04 -1.39193831D-03 -6.88091968D-04 -2.32404447D-03 -5.68990072D-04\r\n -4.16228548D-03 -5.25717530D-03 -4.48758365D-04 -8.08227435D-03 -3.93367372D-04\r\n -1.24063122D-03 -5.52031258D-03 -1.16483490D-04 -4.70676506D-03 -1.84243242D-03\r\n -7.13348098D-04 -3.01135471D-03 -6.30347338D-03 -8.09392985D-03 -7.22343859D-04\r\n -2.85392837D-03 -9.41671710D-03 -3.20973643D-03 -3.92820593D-03 -4.84057469D-03\r\n -2.64233109D-02 -5.63934073D-02  1.00000000D+00 -2.29801148D-01  2.15929925D-01\r\n -1.27107942D+00  1.28920510D-01 -9.07913923D-01 -2.93939412D-02 -1.22682666D-02\r\n  1.00000000D+00 -1.69435248D-01  1.62539542D-01 -2.38049356D-03  2.00000000D+00\r\n  1.00000000D+00 -3.33289027D-01  9.66710985D-01 -2.56376177D-01 -2.38482412D-02\r\n  1.00000000D+00 -1.95702668D-02  6.02502711D-02 -1.50823966D-03 -8.34249184D-02\r\n  4.16575074D-01 -1.66849837D-01 -1.41137898D-01 -6.21925406D-02 -1.79157741D-02\r\n -9.31619946D-03 -7.97656104D-02 -9.82721709D-03 -4.57741946D-01 -8.74001831D-02\r\n  1.00000000D+00 -7.48817250D-02  1.90253779D-01 -7.64884287D-04 -1.04966235D+00\r\n  1.50337681D-01 -8.74718606D-01 -3.10189673D-03 -1.23634702D-03 -1.01881835D-03\r\n -1.04654080D-03 -1.15193555D-03 -1.14678754D-03 -9.76467039D-04 -1.26755168D-03\r\n -1.10509451D-02 -1.98407471D-02 -2.79315859D-02 -6.27332646D-03 -1.09529030D-02\r\n -1.17584094D-02 -1.94125865D-02  1.00000000D+00 -3.93045694D-02  4.44007665D-02\r\n -5.15591446D-03  2.00000000D+00  1.00000000D+00  5.00000000D-01  1.00000000D+00\r\n  2.00000000D+00  1.00000000D+00  2.00000000D+00  1.00000000D+00  2.00000000D+00\r\n  1.00000000D+00  2.00000000D+00  1.00000000D+00  2.00000000D+00  1.00000000D+00\r\n  2.00000000D+00 -9.70873654D-01  1.00000000D+00  2.00000000D+00  1.00000000D+00\r\n  2.00000000D+00  1.00000000D+00  2.06969410D-01  1.42192304D-01  9.91375148D-02\r\n  1.21215612D-01  1.07199252D-01  9.79955196D-02  8.66832137D-02  1.13363981D-01\r\n  5.14388204D-01  3.99175406D-01  2.79817909D-01  3.77357244D-01  4.94234264D-02\r\n  3.67496192D-01  8.83079469D-02  2.73117274D-01  1.62650615D-01  1.08350277D-01\r\n  1.78367764D-01  1.42301500D-01  1.99999988D-01  1.57062501D-01  3.46346229D-01\r\n  1.68499485D-01  1.43396467D-01  2.21011877D-01  1.31137341D-01  2.03243569D-01\r\n  2.62830466D-01  2.20662773D-01  2.05521852D-01  3.04139465D-01  2.50172228D-01\r\n  3.27778846D-01  3.86875868D-01  2.86146790D-01  3.49301606D-01  2.04914153D-01\r\n  1.63164020D-01  1.44504279D-01  1.19339019D-01  4.49773788D-01  1.22339576D-01\r\n  1.75039321D-01  3.13483953D-01  2.35000014D-01  1.18269891D-01  9.08070803D-03\r\n  5.00000000D-01  2.50000000D-01 -2.93030590D-01 -3.57807696D-01 -4.00862485D-01\r\n -3.78784388D-01 -3.92800748D-01 -4.02004480D-01 -4.13316786D-01 -3.86636019D-01\r\n -1.85611829D-01 -1.00824602D-01 -2.20182091D-01 -2.22642779D-01 -4.50576574D-01\r\n -1.32503808D-01 -4.11692053D-01 -4.26882714D-01 -3.37349385D-01 -3.91649723D-01\r\n -4.21632260D-01 -3.57698500D-01 -5.00000000D-01 -5.42937458D-01 -2.53653795D-01\r\n -4.31500524D-01 -3.56603533D-01 -2.78988123D-01 -3.68862659D-01 -3.96756440D-01\r\n -2.37169534D-01 -3.79337251D-01 -2.94478148D-01 -3.95860523D-01 -4.49827760D-01\r\n -1.72221169D-01 -2.13124171D-01 -3.13853234D-01 -1.50698408D-01 -2.95085847D-01\r\n -3.36835980D-01 -3.55495721D-01 -3.80660981D-01 -1.50226235D-01 -3.77660424D-01\r\n -3.24960679D-01 -1.86516061D-01 -2.64999986D-01 -3.81730109D-01 -4.90919292D-01\r\n -2.50000000D-01 -5.00000000D-01 -5.00000000D-01 -2.93030590D-01 -3.57807696D-01\r\n -4.00862485D-01 -3.78784388D-01 -3.92800748D-01 -4.02004480D-01 -4.13316786D-01\r\n -3.86636019D-01 -1.85611829D-01 -1.00824602D-01 -2.20182091D-01 -2.22642779D-01\r\n -4.50576574D-01 -1.32503808D-01 -4.11692053D-01 -4.26882714D-01 -3.37349385D-01\r\n -3.91649723D-01 -4.21632260D-01 -3.57698500D-01 -5.00000000D-01 -5.42937458D-01\r\n -2.53653795D-01 -4.31500524D-01 -3.56603533D-01 -2.78988123D-01 -3.68862659D-01\r\n -3.96756440D-01 -2.37169534D-01 -3.79337251D-01 -2.94478148D-01 -3.95860523D-01\r\n -4.49827760D-01 -1.72221169D-01 -2.13124171D-01 -3.13853234D-01 -1.50698408D-01\r\n -2.95085847D-01 -3.36835980D-01 -3.55495721D-01 -3.80660981D-01 -1.50226235D-01\r\n -3.77660424D-01 -3.24960679D-01 -1.86516061D-01 -2.64999986D-01 -3.81730109D-01\r\n -4.90919292D-01 -2.50000000D-01 -5.00000000D-01 -5.00000000D-01 -4.84386444D-01\r\n -5.61829507D-01 -6.71342134D-01 -5.77910066D-01 -5.65740168D-01 -5.57189345D-01\r\n -6.78157926D-01 -5.21830022D-01 -3.84170078D-02 -8.72260258D-02 -2.06981167D-01\r\n -1.04951881D-01 -5.13661385D-01 -9.55502614D-02 -3.01023483D-01 -3.79936486D-01\r\n -3.87598157D-01 -4.01674479D-01 -4.01453912D-01 -4.55248922D-01 -2.83446878D-01\r\n -4.43214297D-01 -1.71091840D-01 -4.12138194D-01 -3.89837623D-01 -4.61512387D-01\r\n -4.64076310D-01 -3.27409387D-01 -2.21497595D-01 -3.14730257D-01 -2.30232194D-01\r\n -1.56761721D-01 -2.32789949D-01 -1.27302766D-01 -1.61466956D-01 -2.07014278D-01\r\n -1.71532094D-01 -3.33930194D-01 -4.81194258D-01 -3.08955878D-01 -3.55723470D-01\r\n -8.63323063D-02 -7.10011542D-01 -4.41480815D-01 -2.43827671D-01 -3.81600082D-01\r\n -3.81729990D-01 -9.52321470D-01 -1.00000000D+00 -1.00000000D+00  1.00000000D+00\r\n -1.75656468D-01  3.24343532D-01 -1.75656468D-01 -2.90364295D-01 -2.50000000D+00\r\n -7.48264492D-02  4.25173551D-01 -7.48264492D-02 -1.17492460D-01 -2.70000005D+00\r\n -5.77010401D-02  4.42298949D-01 -5.77010401D-02 -9.66344848D-02 -2.50000000D+00\r\n -6.47369847D-02  4.35263008D-01 -6.47369847D-02 -9.87690017D-02 -2.70000005D+00\r\n -7.03428686D-02  4.29657131D-01 -7.03428686D-02 -1.01312913D-01 -2.90000010D+00\r\n -7.71906078D-02  4.22809392D-01 -7.71906078D-02 -1.06988318D-01 -2.90000010D+00\r\n -5.80480322D-02  4.41951960D-01 -5.80480322D-02 -9.52434912D-02 -2.90000010D+00\r\n -8.63306150D-02  4.13669378D-01 -8.63306150D-02 -1.16517611D-01 -2.90000010D+00\r\n -5.14388204D-01  1.85611799D-01 -5.14388204D-01 -1.06465489D-01 -2.40000010D+00\r\n -3.99175406D-01  1.00824594D-01 -3.99175406D-01 -3.45337152D-01 -1.50000000D+00\r\n -2.79817909D-01  2.20182091D-01 -2.79817909D-01 -2.63041526D-01 -2.40000010D+00\r\n -3.77357244D-01  2.22642779D-01 -3.77357244D-01 -1.77882954D-01 -1.89999998D+00\r\n -4.94234152D-02  4.50576574D-01 -4.94234152D-02 -5.63431382D-02 -1.60000002D+00\r\n -3.67496192D-01  1.32503808D-01 -3.67496192D-01 -2.65006363D-01 -2.09999990D+00\r\n -8.83079469D-02  4.11692053D-01 -8.83079469D-02 -6.45695329D-02 -1.79999995D+00\r\n -2.73117244D-01  4.26882774D-01 -2.73117244D-01 -2.43081301D-01 -1.79999995D+00\r\n -1.62650600D-01  3.37349415D-01 -1.62650600D-01 -1.86877683D-01 -1.79999995D+00\r\n -1.08350284D-01  3.91649723D-01 -1.08350284D-01 -1.11123636D-01 -1.79999995D+00\r\n -1.78367749D-01  4.21632290D-01 -1.78367749D-01 -1.69831485D-01 -1.79999995D+00\r\n -1.42301500D-01  3.57698500D-01 -1.42301500D-01 -1.81109533D-01 -1.79999995D+00\r\n -2.00000003D-01  5.00000000D-01 -2.00000003D-01 -1.13378748D-01 -1.89999998D+00\r\n -1.57062501D-01  5.42937458D-01 -1.57062501D-01 -1.28214285D-01 -1.89999998D+00\r\n -3.46346229D-01  2.53653795D-01 -3.46346229D-01 -2.33613744D-01 -1.79999995D+00\r\n -1.68499500D-01  4.31500524D-01 -1.68499500D-01 -1.60938576D-01 -2.20000005D+00\r\n -1.43396482D-01  3.56603533D-01 -1.43396482D-01 -1.56760484D-01 -2.59999990D+00\r\n -2.21011877D-01  2.78988123D-01 -2.21011877D-01 -3.65605980D-01 -2.59999990D+00\r\n -1.31137356D-01  3.68862659D-01 -1.31137356D-01 -1.64987534D-01 -2.20000005D+00\r\n -2.03243569D-01  3.96756440D-01 -2.03243569D-01 -1.67719662D-01 -1.50000000D+00\r\n -2.62830466D-01  2.37169534D-01 -2.62830466D-01 -2.45462865D-01 -3.00000000D+00\r\n -2.20662788D-01  3.79337251D-01 -2.20662788D-01 -1.83080494D-01 -1.89999998D+00\r\n -2.05521852D-01  2.94478148D-01 -2.05521852D-01 -1.60683393D-01 -2.40000010D+00\r\n -3.04139495D-01  3.95860523D-01 -3.04139495D-01 -1.20439976D-01 -2.40000010D+00\r\n -2.50172228D-01  4.49827760D-01 -2.50172228D-01 -1.29466400D-01 -2.40000010D+00\r\n -3.27778846D-01  1.72221154D-01 -3.27778846D-01 -2.42288172D-01 -2.40000010D+00\r\n -3.86875868D-01  2.13124156D-01 -3.86875868D-01 -2.93104559D-01 -1.89999998D+00\r\n -2.86146790D-01  3.13853234D-01 -2.86146790D-01 -1.88739419D-01 -2.20000005D+00\r\n -3.49301606D-01  1.50698394D-01 -3.49301606D-01 -3.97591680D-01 -1.70000005D+00\r\n -2.04914153D-01  2.95085847D-01 -2.04914153D-01 -2.31888533D-01 -2.20000005D+00\r\n -1.63164020D-01  3.36835980D-01 -1.63164020D-01 -2.33091459D-01 -2.90000010D+00\r\n -1.44504279D-01  3.55495721D-01 -1.44504279D-01 -1.25586450D-01 -2.20000005D+00\r\n -1.19339012D-01  3.80660981D-01 -1.19339012D-01 -1.11520983D-01 -2.59999990D+00\r\n -4.49773788D-01  1.50226235D-01 -4.49773788D-01 -2.58476883D-01 -1.79999995D+00\r\n -1.22339584D-01  3.77660424D-01 -1.22339584D-01 -2.30001658D-01 -1.70000005D+00\r\n -1.75039321D-01  3.24960679D-01 -1.75039321D-01 -2.37802625D-01 -1.70000005D+00\r\n -3.13483924D-01  1.86516076D-01 -3.13483924D-01 -4.09809500D-01 -1.60000002D+00\r\n -2.34999999D-01  2.65000015D-01 -2.34999999D-01 -3.38400066D-01 -1.60000002D+00\r\n -1.18269883D-01  3.81730109D-01 -1.18269883D-01 -1.18269853D-01 -1.60000002D+00\r\n -9.08071082D-03  4.90919292D-01 -9.08071082D-03 -1.76154319D-02 -1.50000000D+00\r\n -5.00000000D-01 -5.00000000D-01 -9.69999790D-01 -1.50000000D+00 -2.50000000D-01\r\n  2.50000000D-01 -2.50000000D-01 -1.60000002D+00  5.00000000D-01 -1.70000005D+00\r\n  5.00000000D-01 -1.70000005D+00 -3.13129500D-02 -3.13129500D-02  4.68687057D-01\r\n -5.17610461D-02 -6.73658550D-02 -6.73658550D-02  4.32634145D-01 -1.05777845D-01\r\n -4.14364599D-02 -4.14364599D-02  4.58563536D-01 -6.93954676D-02 -5.64786419D-02\r\n -5.64786419D-02  4.43521351D-01 -8.61692801D-02 -3.68563868D-02 -3.68563868D-02\r\n  4.63143617D-01 -5.30832484D-02 -2.08049174D-02 -2.08049174D-02  4.79195088D-01\r\n -2.88361926D-02 -2.86351871D-02 -2.86351871D-02  4.71364826D-01 -4.69837673D-02\r\n -2.70333719D-02 -2.70333719D-02  4.72966641D-01 -3.64860594D-02  6.99999988D-01\r\n  5.00000000D-01  5.00000000D-01  6.00000024D-01  5.00000000D-01  5.00000000D-01\r\n  5.00000000D-01  6.99999988D-01  5.00000000D-01  5.00000000D-01  6.00000024D-01\r\n  5.00000000D-01  6.99999988D-01  6.99999988D-01  6.00000024D-01  6.00000024D-01\r\n  5.00000000D-01  5.00000000D-01  5.00000000D-01  6.00000024D-01  5.00000000D-01\r\n  6.00000024D-01  5.00000000D-01  6.99999988D-01  6.99999988D-01  5.00000000D-01\r\n  6.00000024D-01  6.00000024D-01  5.00000000D-01  5.00000000D-01  5.00000000D-01\r\n  5.00000000D-01  5.00000000D-01  6.00000024D-01  5.00000000D-01  5.00000000D-01\r\n  5.00000000D-01  5.00000000D-01  5.00000000D-01  5.00000000D-01  5.00000000D-01\r\n  5.00000000D-01  5.00000000D-01  5.00000000D-01  1.00000000D+00  2.17519850D-01\r\n  1.00000000D+00  2.17519850D-01  1.00000000D+00  2.17519850D-01  1.00000000D+00\r\n  7.78065412D-04  7.78065412D-04  7.78065412D-04  2.18297914D-01  7.78065412D-04\r\n  1.94401259D-03  7.78065412D-04  2.30427063D-03  1.10379385D-03  1.24306313D-03\r\n  7.78065412D-04  7.78065412D-04  2.30427063D-03  1.64245476D-03  1.48016575D-03\r\n  1.94401259D-03  7.78065412D-04  1.48016575D-03  1.48016575D-03  1.48016575D-03\r\n  1.94401259D-03  1.94401259D-03  1.48016575D-03  1.94401259D-03  1.94401259D-03\r\n  1.48016575D-03  1.94401259D-03  1.94401259D-03  1.94401259D-03  1.48016575D-03\r\n  1.94401259D-03  2.30427063D-03  1.48016575D-03  1.24306313D-03  7.78065412D-04\r\n  7.78065412D-04  1.64245476D-03  9.62222868D-04  9.62222868D-04  1.48016575D-03\r\n  7.78065412D-04  1.94401259D-03  1.48016575D-03  1.94401259D-03  1.94401259D-03\r\n  1.94401259D-03  1.94401259D-03  1.94401259D-03  1.94401259D-03  1.94401259D-03\r\n  1.44678715D-03  1.94401259D-03  1.94401259D-03  1.94401259D-03  1.00000000D+00\r\n  9.95924044D-03  9.95924044D-03  9.95924044D-03  9.95924044D-03  2.27479085D-01\r\n  2.48833690D-02  9.95924044D-03  2.94946730D-02  1.41285667D-02  1.59112141D-02\r\n  9.95924044D-03  9.95924044D-03  2.94946730D-02  2.10234281D-02  1.89461298D-02\r\n  2.48833690D-02  9.95924044D-03  1.89461298D-02  1.89461298D-02  1.89461298D-02\r\n  2.48833690D-02  2.48833690D-02  1.89461298D-02  2.48833690D-02  2.48833690D-02\r\n  1.89461298D-02  2.48833690D-02  2.48833690D-02  2.48833690D-02  1.89461298D-02\r\n  2.48833690D-02  2.94946730D-02  1.89461298D-02  1.59112141D-02  9.95924044D-03\r\n  9.95924044D-03  2.10234281D-02  1.23164579D-02  1.23164579D-02  1.89461298D-02\r\n  9.95924044D-03  2.48833690D-02  1.89461298D-02  2.48833690D-02  2.48833690D-02\r\n  2.48833690D-02  2.48833690D-02  2.48833690D-02  2.48833690D-02  2.48833690D-02\r\n  1.85188837D-02  2.48833690D-02  2.48833690D-02  2.48833690D-02  1.00000000D+00\r\n  5.43477893D-01  1.00000000D+00  5.52011142D-03  5.52011142D-03  5.52011142D-03\r\n  5.52011142D-03  5.52011142D-03  1.37921125D-02  2.23039955D-01  1.63480211D-02\r\n  7.83104450D-03  8.81911349D-03  5.52011142D-03  5.52011142D-03  1.63480211D-02\r\n  1.16526615D-02  1.05012767D-02  1.37921125D-02  5.52011142D-03  1.05012767D-02\r\n  1.05012767D-02  1.05012767D-02  1.37921125D-02  1.37921125D-02  1.05012767D-02\r\n  1.37921125D-02  1.37921125D-02  1.05012767D-02  1.37921125D-02  1.37921125D-02\r\n  1.37921125D-02  1.05012767D-02  1.37921125D-02  1.63480211D-02  1.05012767D-02\r\n  8.81911349D-03  5.52011142D-03  5.52011142D-03  1.16526615D-02  6.82664663D-03\r\n  6.82664663D-03  1.05012767D-02  5.52011142D-03  1.37921125D-02  1.05012767D-02\r\n  1.37921125D-02  1.37921125D-02  1.37921125D-02  1.37921125D-02  1.37921125D-02\r\n  1.37921125D-02  1.37921125D-02  1.02644665D-02  1.37921125D-02  1.37921125D-02\r\n  1.37921125D-02  1.00000000D+00  6.44193411D-01  1.00000000D+00  1.63674168D-02\r\n  1.63674168D-02  1.63674168D-02  1.63674168D-02  1.63674168D-02  4.08943295D-02\r\n  1.63674168D-02  4.84727360D-02  3.31801593D-01  2.61491276D-02  1.63674168D-02\r\n  1.63674168D-02  4.84727360D-02  3.45507450D-02  3.11368294D-02  4.08943295D-02\r\n  1.63674168D-02  3.11368294D-02  3.11368294D-02  3.11368294D-02  4.08943295D-02\r\n  4.08943295D-02  3.11368294D-02  4.08943295D-02  4.08943295D-02  3.11368294D-02\r\n  4.08943295D-02  4.08943295D-02  4.08943295D-02  3.11368294D-02  4.08943295D-02\r\n  4.84727360D-02  3.11368294D-02  2.61491276D-02  1.63674168D-02  1.63674168D-02\r\n  3.45507450D-02  2.02413611D-02  2.02413611D-02  3.11368294D-02  1.63674168D-02\r\n  4.08943295D-02  3.11368294D-02  4.08943295D-02  4.08943295D-02  4.08943295D-02\r\n  4.08943295D-02  4.08943295D-02  4.08943295D-02  4.08943295D-02  3.04346774D-02\r\n  4.08943295D-02  4.08943295D-02  4.08943295D-02  1.00000000D+00  2.36398429D-02\r\n  2.36398429D-02  2.36398429D-02  2.36398429D-02  2.36398429D-02  5.90646379D-02\r\n  2.36398429D-02  7.00103045D-02  3.35364044D-02  3.85284722D-01  2.36398429D-02\r\n  2.36398429D-02  7.00103045D-02  4.99024540D-02  4.49716561D-02  5.90646379D-02\r\n  2.36398429D-02  4.49716561D-02  4.49716561D-02  4.49716561D-02  5.90646379D-02\r\n  5.90646379D-02  4.49716561D-02  5.90646379D-02  5.90646379D-02  4.49716561D-02\r\n  5.90646379D-02  5.90646379D-02  5.90646379D-02  4.49716561D-02  5.90646379D-02\r\n  7.00103045D-02  4.49716561D-02  3.77677977D-02  2.36398429D-02  2.36398429D-02\r\n  4.99024540D-02  2.92350724D-02  2.92350724D-02  4.49716561D-02  2.36398429D-02\r\n  5.90646379D-02  4.49716561D-02  5.90646379D-02  5.90646379D-02  5.90646379D-02\r\n  5.90646379D-02  5.90646379D-02  5.90646379D-02  5.90646379D-02  4.39575128D-02\r\n  5.90646379D-02  5.90646379D-02  5.90646379D-02  1.00000000D+00  1.12819523D-02\r\n  1.12819523D-02  1.12819523D-02  1.12819523D-02  1.12819523D-02  2.81881951D-02\r\n  1.12819523D-02  3.34119350D-02  1.60050169D-02  1.80244222D-02  2.28801802D-01\r\n  1.12819523D-02  3.34119350D-02  2.38156039D-02  2.14624126D-02  2.81881951D-02\r\n  1.12819523D-02  2.14624126D-02  2.14624126D-02  2.14624126D-02  2.81881951D-02\r\n  2.81881951D-02  2.14624126D-02  2.81881951D-02  2.81881951D-02  2.14624126D-02\r\n  2.81881951D-02  2.81881951D-02  2.81881951D-02  2.14624126D-02  2.81881951D-02\r\n  3.34119350D-02  2.14624126D-02  1.80244222D-02  1.12819523D-02  1.12819523D-02\r\n  2.38156039D-02  1.39522376D-02  1.39522376D-02  2.14624126D-02  1.12819523D-02\r\n  2.81881951D-02  2.14624126D-02  2.81881951D-02  2.81881951D-02  2.81881951D-02\r\n  2.81881951D-02  2.81881951D-02  2.81881951D-02  2.81881951D-02  2.09784228D-02\r\n  2.81881951D-02  2.81881951D-02  2.81881951D-02  1.00000000D+00  1.45590007D-02\r\n  1.45590007D-02  1.45590007D-02  1.45590007D-02  1.45590007D-02  3.63759659D-02\r\n  1.45590007D-02  4.31170389D-02  2.06539650D-02  2.32599434D-02  1.45590007D-02\r\n  2.32078850D-01  4.31170389D-02  3.07332780D-02  2.76965592D-02  3.63759659D-02\r\n  1.45590007D-02  2.76965592D-02  2.76965592D-02  2.76965592D-02  3.63759659D-02\r\n  3.63759659D-02  2.76965592D-02  3.63759659D-02  3.63759659D-02  2.76965592D-02\r\n  3.63759659D-02  3.63759659D-02  3.63759659D-02  2.76965592D-02  3.63759659D-02\r\n  4.31170389D-02  2.76965592D-02  2.32599434D-02  1.45590007D-02  1.45590007D-02\r\n  3.07332780D-02  1.80049166D-02  1.80049166D-02  2.76965592D-02  1.45590007D-02\r\n  3.63759659D-02  2.76965592D-02  3.63759659D-02  3.63759659D-02  3.63759659D-02\r\n  3.63759659D-02  3.63759659D-02  3.63759659D-02  3.63759659D-02  2.70719863D-02\r\n  3.63759659D-02  3.63759659D-02  3.63759659D-02  1.00000000D+00  3.99022875D-03\r\n  3.99022875D-03  3.99022875D-03  3.99022875D-03  3.99022875D-03  9.96967033D-03\r\n  3.99022875D-03  1.18172178D-02  5.66069456D-03  6.37492212D-03  3.99022875D-03\r\n  3.99022875D-03  6.56010628D-01  8.42316169D-03  7.59087969D-03  9.96967033D-03\r\n  3.99022875D-03  7.59087969D-03  7.59087969D-03  7.59087969D-03  9.96967033D-03\r\n  9.96967033D-03  7.59087969D-03  9.96967033D-03  9.96967033D-03  7.59087969D-03\r\n  9.96967033D-03  9.96967033D-03  9.96967033D-03  7.59087969D-03  9.96967033D-03\r\n  1.18172178D-02  7.59087969D-03  6.37492212D-03  3.99022875D-03  3.99022875D-03\r\n  8.42316169D-03  4.93466202D-03  4.93466202D-03  7.59087969D-03  3.99022875D-03\r\n  9.96967033D-03  7.59087969D-03  9.96967033D-03  9.96967033D-03  9.96967033D-03\r\n  9.96967033D-03  9.96967033D-03  9.96967033D-03  9.96967033D-03  7.41970027D-03\r\n  9.96967033D-03  9.96967033D-03  9.96967033D-03  1.00000000D+00  4.59172845D-01\r\n  1.00000000D+00  2.76930194D-04  2.76930194D-04  2.76930194D-04  2.76930194D-04\r\n  2.76930194D-04  6.91915862D-04  2.76930194D-04  8.20139423D-04  3.92863934D-04\r\n  4.42432880D-04  2.76930194D-04  2.76930194D-04  8.20139423D-04  5.84584952D-04\r\n  4.14329380D-01  6.91915862D-04  2.76930194D-04  5.26822812D-04  5.26822812D-04\r\n  5.26822812D-04  6.91915862D-04  6.91915862D-04  5.26822812D-04  6.91915862D-04\r\n  6.91915862D-04  5.26822812D-04  6.91915862D-04  6.91915862D-04  6.91915862D-04\r\n  5.26822812D-04  6.91915862D-04  8.20139423D-04  5.26822812D-04  4.42432880D-04\r\n  2.76930194D-04  2.76930194D-04  5.84584952D-04  3.42475803D-04  3.42475803D-04\r\n  5.26822812D-04  2.76930194D-04  6.91915862D-04  5.26822812D-04  6.91915862D-04\r\n  6.91915862D-04  6.91915862D-04  6.91915862D-04  6.91915862D-04  6.91915862D-04\r\n  6.91915862D-04  5.14942629D-04  6.91915862D-04  6.91915862D-04  6.91915862D-04\r\n  1.00000000D+00  1.79941696D-03  1.79941696D-03  1.79941696D-03  1.79941696D-03\r\n  1.79941696D-03  4.49588103D-03  1.79941696D-03  5.32904267D-03  2.55272305D-03\r\n  2.87480839D-03  1.79941696D-03  1.79941696D-03  5.32904267D-03  3.79847386D-03\r\n  3.42315156D-03  5.47973752D-01  1.79941696D-03  3.42315156D-03  3.42315156D-03\r\n  3.42315156D-03  4.49588103D-03  4.49588103D-03  3.42315156D-03  4.49588103D-03\r\n  4.49588103D-03  3.42315156D-03  4.49588103D-03  4.49588103D-03  4.49588103D-03\r\n  3.42315156D-03  4.49588103D-03  5.32904267D-03  3.42315156D-03  2.87480839D-03\r\n  1.79941696D-03  1.79941696D-03  3.79847386D-03  2.22531473D-03  2.22531473D-03\r\n  3.42315156D-03  1.79941696D-03  4.49588103D-03  3.42315156D-03  4.49588103D-03\r\n  4.49588103D-03  4.49588103D-03  4.49588103D-03  4.49588103D-03  4.49588103D-03\r\n  4.49588103D-03  3.34595726D-03  4.49588103D-03  4.49588103D-03  4.49588103D-03\r\n  1.00000000D+00  3.40027385D-03  3.40027385D-03  3.40027385D-03  3.40027385D-03\r\n  3.40027385D-03  8.49565491D-03  3.40027385D-03  1.00700418D-02  4.82376106D-03\r\n  5.43239061D-03  3.40027385D-03  3.40027385D-03  1.00700418D-02  7.17779715D-03\r\n  6.46856846D-03  8.49565491D-03  2.20920131D-01  6.46856846D-03  6.46856846D-03\r\n  6.46856846D-03  8.49565491D-03  8.49565491D-03  6.46856846D-03  8.49565491D-03\r\n  8.49565491D-03  6.46856846D-03  8.49565491D-03  8.49565491D-03  8.49565491D-03\r\n  6.46856846D-03  8.49565491D-03  1.00700418D-02  6.46856846D-03  5.43239061D-03\r\n  3.40027385D-03  3.40027385D-03  7.17779715D-03  4.20507230D-03  4.20507230D-03\r\n  6.46856846D-03  3.40027385D-03  8.49565491D-03  6.46856846D-03  8.49565491D-03\r\n  8.49565491D-03  8.49565491D-03  8.49565491D-03  8.49565491D-03  8.49565491D-03\r\n  8.49565491D-03  6.32269774D-03  8.49565491D-03  8.49565491D-03  8.49565491D-03\r\n  1.00000000D+00  1.88028405D-03  1.88028405D-03  1.88028405D-03  1.88028405D-03\r\n  1.88028405D-03  4.69792867D-03  1.88028405D-03  5.56853367D-03  2.66744406D-03\r\n  3.00400425D-03  1.88028405D-03  1.88028405D-03  5.56853367D-03  3.96917993D-03\r\n  3.57698998D-03  4.69792867D-03  1.88028405D-03  4.17379558D-01  3.57698998D-03\r\n  3.57698998D-03  4.69792867D-03  4.69792867D-03  3.57698998D-03  4.69792867D-03\r\n  4.69792867D-03  3.57698998D-03  4.69792867D-03  4.69792867D-03  4.69792867D-03\r\n  3.57698998D-03  4.69792867D-03  5.56853367D-03  3.57698998D-03  3.00400425D-03\r\n  1.88028405D-03  1.88028405D-03  3.96917993D-03  2.32532178D-03  2.32532178D-03\r\n  3.57698998D-03  1.88028405D-03  4.69792867D-03  3.57698998D-03  4.69792867D-03\r\n  4.69792867D-03  4.69792867D-03  4.69792867D-03  4.69792867D-03  4.69792867D-03\r\n  4.69792867D-03  3.49632674D-03  4.69792867D-03  4.69792867D-03  4.69792867D-03\r\n  1.00000000D+00  8.75091413D-04  8.75091413D-04  8.75091413D-04  8.75091413D-04\r\n  8.75091413D-04  2.18643411D-03  8.75091413D-04  2.59161694D-03  1.24143891D-03\r\n  1.39807514D-03  8.75091413D-04  8.75091413D-04  2.59161694D-03  1.84727146D-03\r\n  1.66474504D-03  2.18643411D-03  8.75091413D-04  1.66474504D-03  4.15467322D-01\r\n  1.66474504D-03  2.18643411D-03  2.18643411D-03  1.66474504D-03  2.18643411D-03\r\n  2.18643411D-03  1.66474504D-03  2.18643411D-03  2.18643411D-03  2.18643411D-03\r\n  1.66474504D-03  2.18643411D-03  2.59161694D-03  1.66474504D-03  1.39807514D-03\r\n  8.75091413D-04  8.75091413D-04  1.84727146D-03  1.08221371D-03  1.08221371D-03\r\n  1.66474504D-03  8.75091413D-04  2.18643411D-03  1.66474504D-03  2.18643411D-03\r\n  2.18643411D-03  2.18643411D-03  2.18643411D-03  2.18643411D-03  2.18643411D-03\r\n  2.18643411D-03  1.62720389D-03  2.18643411D-03  2.18643411D-03  2.18643411D-03\r\n  1.00000000D+00  3.89279012D-04  3.89279012D-04  3.89279012D-04  3.89279012D-04\r\n  3.89279012D-04  9.72621783D-04  3.89279012D-04  1.15286477D-03  5.52246405D-04\r\n  6.21925166D-04  3.89279012D-04  3.89279012D-04  1.15286477D-03  8.21747351D-04\r\n  7.40551506D-04  9.72621783D-04  3.89279012D-04  7.40551506D-04  7.40551506D-04\r\n  4.14543122D-01  9.72621783D-04  9.72621783D-04  7.40551506D-04  9.72621783D-04\r\n  9.72621783D-04  7.40551506D-04  9.72621783D-04  9.72621783D-04  9.72621783D-04\r\n  7.40551506D-04  9.72621783D-04  1.15286477D-03  7.40551506D-04  6.21925166D-04\r\n  3.89279012D-04  3.89279012D-04  8.21747351D-04  4.81416093D-04  4.81416093D-04\r\n  7.40551506D-04  3.89279012D-04  9.72621783D-04  7.40551506D-04  9.72621783D-04\r\n  9.72621783D-04  9.72621783D-04  9.72621783D-04  9.72621783D-04  9.72621783D-04\r\n  9.72621783D-04  7.23851670D-04  9.72621783D-04  9.72621783D-04  9.72621783D-04\r\n  1.00000000D+00  6.58825913D-04  6.58825913D-04  6.58825913D-04  6.58825913D-04\r\n  6.58825913D-04  1.64609030D-03  6.58825913D-04  1.95113849D-03  9.34636162D-04\r\n  1.05256215D-03  6.58825913D-04  6.58825913D-04  1.95113849D-03  1.39074656D-03\r\n  1.25332864D-03  1.64609030D-03  6.58825913D-04  1.25332864D-03  1.25332864D-03\r\n  1.25332864D-03  5.45123994D-01  1.64609030D-03  1.25332864D-03  1.64609030D-03\r\n  1.64609030D-03  1.25332864D-03  1.64609030D-03  1.64609030D-03  1.64609030D-03\r\n  1.25332864D-03  1.64609030D-03  1.95113849D-03  1.25332864D-03  1.05256215D-03\r\n  6.58825913D-04  6.58825913D-04  1.39074656D-03  8.14761093D-04  8.14761093D-04\r\n  1.25332864D-03  6.58825913D-04  1.64609030D-03  1.25332864D-03  1.64609030D-03\r\n  1.64609030D-03  1.64609030D-03  1.64609030D-03  1.64609030D-03  1.64609030D-03\r\n  1.64609030D-03  1.22506532D-03  1.64609030D-03  1.64609030D-03  1.64609030D-03\r\n  1.00000000D+00  1.71326144D-04  1.71326144D-04  1.71326144D-04  1.71326144D-04\r\n  1.71326144D-04  4.28061961D-04  1.71326144D-04  5.07389021D-04  2.43049974D-04\r\n  2.73716345D-04  1.71326144D-04  1.71326144D-04  5.07389021D-04  3.61660408D-04\r\n  3.25925212D-04  4.28061961D-04  1.71326144D-04  3.25925212D-04  3.25925212D-04\r\n  3.25925212D-04  4.28061961D-04  5.43905973D-01  3.25925212D-04  4.28061961D-04\r\n  4.28061961D-04  3.25925212D-04  4.28061961D-04  4.28061961D-04  4.28061961D-04\r\n  3.25925212D-04  4.28061961D-04  5.07389021D-04  3.25925212D-04  2.73716345D-04\r\n  1.71326144D-04  1.71326144D-04  3.61660408D-04  2.11876730D-04  2.11876730D-04\r\n  3.25925212D-04  1.71326144D-04  4.28061961D-04  3.25925212D-04  4.28061961D-04\r\n  4.28061961D-04  4.28061961D-04  4.28061961D-04  4.28061961D-04  4.28061961D-04\r\n  4.28061961D-04  3.18575389D-04  4.28061961D-04  4.28061961D-04  4.28061961D-04\r\n  1.00000000D+00  1.48846791D-03  1.48846791D-03  1.48846791D-03  1.48846791D-03\r\n  1.48846791D-03  3.71896802D-03  1.48846791D-03  4.40815510D-03  2.11159862D-03\r\n  2.37802579D-03  1.48846791D-03  1.48846791D-03  4.40815510D-03  3.14207654D-03\r\n  2.83161202D-03  3.71896802D-03  1.48846791D-03  2.83161202D-03  2.83161202D-03\r\n  2.83161202D-03  3.71896802D-03  3.71896802D-03  4.16634172D-01  3.71896802D-03\r\n  3.71896802D-03  2.83161202D-03  3.71896802D-03  3.71896802D-03  3.71896802D-03\r\n  2.83161202D-03  3.71896802D-03  4.40815510D-03  2.83161202D-03  2.37802579D-03\r\n  1.48846791D-03  1.48846791D-03  3.14207654D-03  1.84076803D-03  1.84076803D-03\r\n  2.83161202D-03  1.48846791D-03  3.71896802D-03  2.83161202D-03  3.71896802D-03\r\n  3.71896802D-03  3.71896802D-03  3.71896802D-03  3.71896802D-03  3.71896802D-03\r\n  3.71896802D-03  2.76775728D-03  3.71896802D-03  3.71896802D-03  3.71896802D-03\r\n  1.00000000D+00  5.43477893D-01  1.00000000D+00  8.70593140D-05  8.70593140D-05\r\n  8.70593140D-05  8.70593140D-05  8.70593140D-05  2.17519526D-04  8.70593140D-05\r\n  2.57829524D-04  1.23505743D-04  1.39088850D-04  8.70593140D-05  8.70593140D-05\r\n  2.57829524D-04  1.83777607D-04  1.65618767D-04  2.17519526D-04  8.70593140D-05\r\n  1.65618767D-04  1.65618767D-04  1.65618767D-04  2.17519526D-04  2.17519526D-04\r\n  1.65618767D-04  2.17519526D-04  5.43695390D-01  1.65618767D-04  2.17519526D-04\r\n  2.17519526D-04  2.17519526D-04  1.65618767D-04  2.17519526D-04  2.57829524D-04\r\n  1.65618767D-04  1.39088850D-04  8.70593140D-05  8.70593140D-05  1.83777607D-04\r\n  1.07665073D-04  1.07665073D-04  1.65618767D-04  8.70593140D-05  2.17519526D-04\r\n  1.65618767D-04  2.17519526D-04  2.17519526D-04  2.17519526D-04  2.17519526D-04\r\n  2.17519526D-04  2.17519526D-04  2.17519526D-04  1.61883960D-04  2.17519526D-04\r\n  2.17519526D-04  2.17519526D-04  1.00000000D+00  3.88478627D-04  3.88478627D-04\r\n  3.88478627D-04  3.88478627D-04  3.88478627D-04  9.70622001D-04  3.88478627D-04\r\n  1.15049444D-03  5.51110948D-04  6.20646402D-04  3.88478627D-04  3.88478627D-04\r\n  1.15049444D-03  8.20057758D-04  7.39028910D-04  9.70622001D-04  3.88478627D-04\r\n  7.39028910D-04  7.39028910D-04  7.39028910D-04  9.70622001D-04  9.70622001D-04\r\n  7.39028910D-04  9.70622001D-04  9.70622001D-04  4.14541602D-01  9.70622001D-04\r\n  9.70622001D-04  9.70622001D-04  7.39028910D-04  9.70622001D-04  1.15049444D-03\r\n  7.39028910D-04  6.20646402D-04  3.88478627D-04  3.88478627D-04  8.20057758D-04\r\n  4.80426272D-04  4.80426272D-04  7.39028910D-04  3.88478627D-04  9.70622001D-04\r\n  7.39028910D-04  9.70622001D-04  9.70622001D-04  9.70622001D-04  9.70622001D-04\r\n  9.70622001D-04  9.70622001D-04  9.70622001D-04  7.22363358D-04  9.70622001D-04\r\n  9.70622001D-04  9.70622001D-04  1.00000000D+00  5.43477893D-01  1.00000000D+00\r\n  5.43477893D-01  1.00000000D+00  5.43477893D-01  1.00000000D+00  3.43396631D-03\r\n  3.43396631D-03  3.43396631D-03  3.43396631D-03  3.43396631D-03  8.57983623D-03\r\n  3.43396631D-03  1.01698246D-02  4.87155840D-03  5.48621872D-03  3.43396631D-03\r\n  3.43396631D-03  1.01698246D-02  7.24892039D-03  6.53266395D-03  8.57983623D-03\r\n  3.43396631D-03  6.53266395D-03  6.53266395D-03  6.53266395D-03  8.57983623D-03\r\n  8.57983623D-03  6.53266395D-03  8.57983623D-03  8.57983623D-03  6.53266395D-03\r\n  8.57983623D-03  8.57983623D-03  8.57983623D-03  4.20335233D-01  8.57983623D-03\r\n  1.01698246D-02  6.53266395D-03  5.48621872D-03  3.43396631D-03  3.43396631D-03\r\n  7.24892039D-03  4.24673967D-03  4.24673967D-03  6.53266395D-03  3.43396631D-03\r\n  8.57983623D-03  6.53266395D-03  8.57983623D-03  8.57983623D-03  8.57983623D-03\r\n  8.57983623D-03  8.57983623D-03  8.57983623D-03  8.57983623D-03  6.38534827D-03\r\n  8.57983623D-03  8.57983623D-03  8.57983623D-03  1.00000000D+00  1.50102680D-03\r\n  1.50102680D-03  1.50102680D-03  1.50102680D-03  1.50102680D-03  3.75034660D-03\r\n  1.50102680D-03  4.44534887D-03  2.12941528D-03  2.39809020D-03  1.50102680D-03\r\n  1.50102680D-03  4.44534887D-03  3.16858804D-03  2.85550370D-03  3.75034660D-03\r\n  1.50102680D-03  2.85550370D-03  2.85550370D-03  2.85550370D-03  3.75034660D-03\r\n  3.75034660D-03  2.85550370D-03  3.75034660D-03  3.75034660D-03  2.85550370D-03\r\n  3.75034660D-03  3.75034660D-03  3.75034660D-03  2.85550370D-03  5.47228217D-01\r\n  4.44534887D-03  2.85550370D-03  2.39809020D-03  1.50102680D-03  1.50102680D-03\r\n  3.16858804D-03  1.85629935D-03  1.85629935D-03  2.85550370D-03  1.50102680D-03\r\n  3.75034660D-03  2.85550370D-03  3.75034660D-03  3.75034660D-03  3.75034660D-03\r\n  3.75034660D-03  3.75034660D-03  3.75034660D-03  3.75034660D-03  2.79111019D-03\r\n  3.75034660D-03  3.75034660D-03  3.75034660D-03  1.00000000D+00  1.31290816D-02\r\n  1.31290816D-02  1.31290816D-02  1.31290816D-02  1.31290816D-02  3.28032821D-02\r\n  1.31290816D-02  3.88822779D-02  1.86254252D-02  2.09754556D-02  1.31290816D-02\r\n  1.31290816D-02  3.88822779D-02  2.77147945D-02  2.49763280D-02  3.28032821D-02\r\n  1.31290816D-02  2.49763280D-02  2.49763280D-02  2.49763280D-02  3.28032821D-02\r\n  3.28032821D-02  2.49763280D-02  3.28032821D-02  3.28032821D-02  2.49763280D-02\r\n  3.28032821D-02  3.28032821D-02  3.28032821D-02  2.49763280D-02  3.28032821D-02\r\n  6.83075666D-01  2.49763280D-02  2.09754556D-02  1.31290816D-02  1.31290816D-02\r\n  2.77147945D-02  1.62365567D-02  1.62365567D-02  2.49763280D-02  1.31290816D-02\r\n  3.28032821D-02  2.49763280D-02  3.28032821D-02  3.28032821D-02  3.28032821D-02\r\n  3.28032821D-02  3.28032821D-02  3.28032821D-02  3.28032821D-02  2.44130976D-02\r\n  3.28032821D-02  3.28032821D-02  3.28032821D-02  1.00000000D+00  2.70030956D-04\r\n  2.70030956D-04  2.70030956D-04  2.70030956D-04  2.70030956D-04  6.74678013D-04\r\n  2.70030956D-04  7.99707079D-04  3.83076462D-04  4.31410444D-04  2.70030956D-04\r\n  2.70030956D-04  7.99707079D-04  5.70021046D-04  5.13697974D-04  6.74678013D-04\r\n  2.70030956D-04  5.13697974D-04  5.13697974D-04  5.13697974D-04  6.74678013D-04\r\n  6.74678013D-04  5.13697974D-04  6.74678013D-04  6.74678013D-04  5.13697974D-04\r\n  6.74678013D-04  6.74678013D-04  6.74678013D-04  5.13697974D-04  6.74678013D-04\r\n  7.99707079D-04  4.14316267D-01  4.31410444D-04  2.70030956D-04  2.70030956D-04\r\n  5.70021046D-04  3.33943637D-04  3.33943637D-04  5.13697974D-04  2.70030956D-04\r\n  6.74678013D-04  5.13697974D-04  6.74678013D-04  6.74678013D-04  6.74678013D-04\r\n  6.74678013D-04  6.74678013D-04  6.74678013D-04  6.74678013D-04  5.02113777D-04\r\n  6.74678013D-04  6.74678013D-04  6.74678013D-04  1.00000000D+00  1.98783097D-03\r\n  1.98783097D-03  1.98783097D-03  1.98783097D-03  1.98783097D-03  4.96663759D-03\r\n  1.98783097D-03  5.88703807D-03  2.82001449D-03  3.17582488D-03  1.98783097D-03\r\n  1.98783097D-03  5.88703807D-03  4.19620611D-03  3.78158386D-03  4.96663759D-03\r\n  1.98783097D-03  3.78158386D-03  3.78158386D-03  3.78158386D-03  4.96663759D-03\r\n  4.96663759D-03  3.78158386D-03  4.96663759D-03  4.96663759D-03  3.78158386D-03\r\n  4.96663759D-03  4.96663759D-03  4.96663759D-03  3.78158386D-03  4.96663759D-03\r\n  5.88703807D-03  3.78158386D-03  3.50692749D-01  1.98783097D-03  1.98783097D-03\r\n  4.19620611D-03  2.45832372D-03  2.45832372D-03  3.78158386D-03  1.98783097D-03\r\n  4.96663759D-03  3.78158386D-03  4.96663759D-03  4.96663759D-03  4.96663759D-03\r\n  4.96663759D-03  4.96663759D-03  4.96663759D-03  4.96663759D-03  3.69630684D-03\r\n  4.96663759D-03  4.96663759D-03  4.96663759D-03  1.00000000D+00  9.10336524D-03\r\n  9.10336524D-03  9.10336524D-03  9.10336524D-03  9.10336524D-03  2.27449480D-02\r\n  9.10336524D-03  2.69599687D-02  1.29143884D-02  1.45438388D-02  9.10336524D-03\r\n  9.10336524D-03  2.69599687D-02  1.92167219D-02  1.73179395D-02  2.27449480D-02\r\n  9.10336524D-03  1.73179395D-02  1.73179395D-02  1.73179395D-02  2.27449480D-02\r\n  2.27449480D-02  1.73179395D-02  2.27449480D-02  2.27449480D-02  1.73179395D-02\r\n  2.27449480D-02  2.27449480D-02  2.27449480D-02  1.73179395D-02  2.27449480D-02\r\n  2.69599687D-02  1.73179395D-02  1.45438388D-02  2.26623222D-01  9.10336524D-03\r\n  1.92167219D-02  1.12580080D-02  1.12580080D-02  1.73179395D-02  9.10336524D-03\r\n  2.27449480D-02  1.73179395D-02  2.27449480D-02  2.27449480D-02  2.27449480D-02\r\n  2.27449480D-02  2.27449480D-02  2.27449480D-02  2.27449480D-02  1.69274099D-02\r\n  2.27449480D-02  2.27449480D-02  2.27449480D-02  1.00000000D+00  1.34661812D-02\r\n  1.34661812D-02  1.34661812D-02  1.34661812D-02  1.34661812D-02  3.36455368D-02\r\n  1.34661812D-02  3.98806147D-02  1.91036500D-02  2.15140190D-02  1.34661812D-02\r\n  1.34661812D-02  3.98806147D-02  2.84263939D-02  2.56176181D-02  3.36455368D-02\r\n  1.34661812D-02  2.56176181D-02  2.56176181D-02  2.56176181D-02  3.36455368D-02\r\n  3.36455368D-02  2.56176181D-02  3.36455368D-02  3.36455368D-02  2.56176181D-02\r\n  3.36455368D-02  3.36455368D-02  3.36455368D-02  2.56176181D-02  3.36455368D-02\r\n  3.98806147D-02  2.56176181D-02  2.15140190D-02  1.34661812D-02  2.30986029D-01\r\n  2.84263939D-02  1.66534446D-02  1.66534446D-02  2.56176181D-02  1.34661812D-02\r\n  3.36455368D-02  2.56176181D-02  3.36455368D-02  3.36455368D-02  3.36455368D-02\r\n  3.36455368D-02  3.36455368D-02  3.36455368D-02  3.36455368D-02  2.50399243D-02\r\n  3.36455368D-02  3.36455368D-02  3.36455368D-02  1.00000000D+00  3.16114078D-04\r\n  3.16114078D-04  3.16114078D-04  3.16114078D-04  3.16114078D-04  7.89817655D-04\r\n  3.16114078D-04  9.36184078D-04  4.48451785D-04  5.05034404D-04  3.16114078D-04\r\n  3.16114078D-04  9.36184078D-04  6.67300075D-04  6.01364998D-04  7.89817655D-04\r\n  3.16114078D-04  6.01364998D-04  6.01364998D-04  6.01364998D-04  7.89817655D-04\r\n  7.89817655D-04  6.01364998D-04  7.89817655D-04  7.89817655D-04  6.01364998D-04\r\n  7.89817655D-04  7.89817655D-04  7.89817655D-04  6.01364998D-04  7.89817655D-04\r\n  9.36184078D-04  6.01364998D-04  5.05034404D-04  3.16114078D-04  3.16114078D-04\r\n  4.59840149D-01  3.90934001D-04  3.90934001D-04  6.01364998D-04  3.16114078D-04\r\n  7.89817655D-04  6.01364998D-04  7.89817655D-04  7.89817655D-04  7.89817655D-04\r\n  7.89817655D-04  7.89817655D-04  7.89817655D-04  7.89817655D-04  5.87803836D-04\r\n  7.89817655D-04  7.89817655D-04  7.89817655D-04  1.00000000D+00  7.96811283D-03\r\n  7.96811283D-03  7.96811283D-03  7.96811283D-03  7.96811283D-03  1.99084971D-02\r\n  7.96811283D-03  2.35978737D-02  1.13038765D-02  1.27301235D-02  7.96811283D-03\r\n  7.96811283D-03  2.35978737D-02  1.68202631D-02  1.51582742D-02  1.99084971D-02\r\n  7.96811283D-03  1.51582742D-02  1.51582742D-02  1.51582742D-02  1.99084971D-02\r\n  1.99084971D-02  1.51582742D-02  1.99084971D-02  1.99084971D-02  1.51582742D-02\r\n  1.99084971D-02  1.99084971D-02  1.99084971D-02  1.51582742D-02  1.99084971D-02\r\n  2.35978737D-02  1.51582742D-02  1.27301235D-02  7.96811283D-03  7.96811283D-03\r\n  1.68202631D-02  2.78857887D-01  9.85405780D-03  1.51582742D-02  7.96811283D-03\r\n  1.99084971D-02  1.51582742D-02  1.99084971D-02  1.99084971D-02  1.99084971D-02\r\n  1.99084971D-02  1.99084971D-02  1.99084971D-02  1.99084971D-02  1.48164472D-02\r\n  1.99084971D-02  1.99084971D-02  1.99084971D-02  1.00000000D+00  2.63912370D-04\r\n  2.63912370D-04  2.63912370D-04  2.63912370D-04  2.63912370D-04  6.59390527D-04\r\n  2.63912370D-04  7.81586568D-04  3.74396332D-04  4.21635137D-04  2.63912370D-04\r\n  2.63912370D-04  7.81586568D-04  5.57104941D-04  5.02058130D-04  6.59390527D-04\r\n  2.63912370D-04  5.02058130D-04  5.02058130D-04  5.02058130D-04  6.59390527D-04\r\n  6.59390527D-04  5.02058130D-04  6.59390527D-04  6.59390527D-04  5.02058130D-04\r\n  6.59390527D-04  6.59390527D-04  6.59390527D-04  5.02058130D-04  6.59390527D-04\r\n  7.81586568D-04  5.02058130D-04  4.21635137D-04  2.63912370D-04  2.63912370D-04\r\n  5.57104941D-04  3.26376816D-04  2.69330204D-01  5.02058130D-04  2.63912370D-04\r\n  6.59390527D-04  5.02058130D-04  6.59390527D-04  6.59390527D-04  6.59390527D-04\r\n  6.59390527D-04  6.59390527D-04  6.59390527D-04  6.59390527D-04  4.90736391D-04\r\n  6.59390527D-04  6.59390527D-04  6.59390527D-04  1.00000000D+00  7.62254349D-04\r\n  7.62254349D-04  7.62254349D-04  7.62254349D-04  7.62254349D-04  1.90450845D-03\r\n  7.62254349D-04  2.25744559D-03  1.08136376D-03  1.21780287D-03  7.62254349D-04\r\n  7.62254349D-04  2.25744559D-03  1.60907849D-03  1.45008741D-03  1.90450845D-03\r\n  7.62254349D-04  1.45008741D-03  1.45008741D-03  1.45008741D-03  1.90450845D-03\r\n  1.90450845D-03  1.45008741D-03  1.90450845D-03  1.90450845D-03  1.45008741D-03\r\n  1.90450845D-03  1.90450845D-03  1.90450845D-03  1.45008741D-03  1.90450845D-03\r\n  2.25744559D-03  1.45008741D-03  1.21780287D-03  7.62254349D-04  7.62254349D-04\r\n  1.60907849D-03  9.42669634D-04  9.42669634D-04  4.15252656D-01  7.62254349D-04\r\n  1.90450845D-03  1.45008741D-03  1.90450845D-03  1.90450845D-03  1.90450845D-03\r\n  1.90450845D-03  1.90450845D-03  1.90450845D-03  1.90450845D-03  1.41738704D-03\r\n  1.90450845D-03  1.90450845D-03  1.90450845D-03  1.00000000D+00  1.50854530D-05\r\n  1.50854530D-05  1.50854530D-05  1.50854530D-05  1.50854530D-05  3.76913194D-05\r\n  1.50854530D-05  4.46761514D-05  2.14008123D-05  2.41010202D-05  1.50854530D-05\r\n  1.50854530D-05  4.46761514D-05  3.18445891D-05  2.86980667D-05  3.76913194D-05\r\n  1.50854530D-05  2.86980667D-05  2.86980667D-05  2.86980667D-05  3.76913194D-05\r\n  3.76913194D-05  2.86980667D-05  3.76913194D-05  3.76913194D-05  2.86980667D-05\r\n  3.76913194D-05  3.76913194D-05  3.76913194D-05  2.86980667D-05  3.76913194D-05\r\n  4.46761514D-05  2.86980667D-05  2.41010202D-05  1.50854530D-05  1.50854530D-05\r\n  3.18445891D-05  1.86559755D-05  1.86559755D-05  2.86980667D-05  2.17534930D-01\r\n  3.76913194D-05  2.86980667D-05  3.76913194D-05  3.76913194D-05  3.76913194D-05\r\n  3.76913194D-05  3.76913194D-05  3.76913194D-05  3.76913194D-05  2.80509066D-05\r\n  3.76913194D-05  3.76913194D-05  3.76913194D-05  1.00000000D+00  1.33195089D-03\r\n  1.33195089D-03  1.33195089D-03  1.33195089D-03  1.33195089D-03  3.32790706D-03\r\n  1.33195089D-03  3.94462375D-03  1.88955734D-03  2.12796894D-03  1.33195089D-03\r\n  1.33195089D-03  3.94462375D-03  2.81167752D-03  2.53385911D-03  3.32790706D-03\r\n  1.33195089D-03  2.53385911D-03  2.53385911D-03  2.53385911D-03  3.32790706D-03\r\n  3.32790706D-03  2.53385911D-03  3.32790706D-03  3.32790706D-03  2.53385911D-03\r\n  3.32790706D-03  3.32790706D-03  3.32790706D-03  2.53385911D-03  3.32790706D-03\r\n  3.94462375D-03  2.53385911D-03  2.12796894D-03  1.33195089D-03  1.33195089D-03\r\n  2.81167752D-03  1.64720556D-03  1.64720556D-03  2.53385911D-03  1.33195089D-03\r\n  5.46805799D-01  2.53385911D-03  3.32790706D-03  3.32790706D-03  3.32790706D-03\r\n  3.32790706D-03  3.32790706D-03  3.32790706D-03  3.32790706D-03  2.47671921D-03\r\n  3.32790706D-03  3.32790706D-03  3.32790706D-03  1.00000000D+00  1.33274659D-03\r\n  1.33274659D-03  1.33274659D-03  1.33274659D-03  1.33274659D-03  3.32989520D-03\r\n  1.33274659D-03  3.94698046D-03  1.89068634D-03  2.12924019D-03  1.33274659D-03\r\n  1.33274659D-03  3.94698046D-03  2.81335716D-03  2.53537297D-03  3.32989520D-03\r\n  1.33274659D-03  2.53537297D-03  2.53537297D-03  2.53537297D-03  3.32989520D-03\r\n  3.32989520D-03  2.53537297D-03  3.32989520D-03  3.32989520D-03  2.53537297D-03\r\n  3.32989520D-03  3.32989520D-03  3.32989520D-03  2.53537297D-03  3.32989520D-03\r\n  3.94698046D-03  2.53537297D-03  2.12924019D-03  1.33274659D-03  1.33274659D-03\r\n  2.81335716D-03  1.64818950D-03  1.64818950D-03  2.53537297D-03  1.33274659D-03\r\n  3.32989520D-03  4.16337937D-01  3.32989520D-03  3.32989520D-03  3.32989520D-03\r\n  3.32989520D-03  3.32989520D-03  3.32989520D-03  3.32989520D-03  2.47819885D-03\r\n  3.32989520D-03  3.32989520D-03  3.32989520D-03  1.00000000D+00  1.33454381D-03\r\n  1.33454381D-03  1.33454381D-03  1.33454381D-03  1.33454381D-03  3.33438558D-03\r\n  1.33454381D-03  3.95230297D-03  1.89323595D-03  2.13211169D-03  1.33454381D-03\r\n  1.33454381D-03  3.95230297D-03  2.81715114D-03  2.53879209D-03  3.33438558D-03\r\n  1.33454381D-03  2.53879209D-03  2.53879209D-03  2.53879209D-03  3.33438558D-03\r\n  3.33438558D-03  2.53879209D-03  3.33438558D-03  3.33438558D-03  2.53879209D-03\r\n  3.33438558D-03  3.33438558D-03  3.33438558D-03  2.53879209D-03  3.33438558D-03\r\n  3.95230297D-03  2.53879209D-03  2.13211169D-03  1.33454381D-03  1.33454381D-03\r\n  2.81715114D-03  1.65041210D-03  1.65041210D-03  2.53879209D-03  1.33454381D-03\r\n  3.33438558D-03  2.53879209D-03  5.46812296D-01  3.33438558D-03  3.33438558D-03\r\n  3.33438558D-03  3.33438558D-03  3.33438558D-03  3.33438558D-03  2.48154067D-03\r\n  3.33438558D-03  3.33438558D-03  3.33438558D-03  1.00000000D+00  5.43477893D-01\r\n  1.00000000D+00  5.43477893D-01  1.00000000D+00  1.15508148D-02  1.15508148D-02\r\n  1.15508148D-02  1.15508148D-02  1.15508148D-02  2.88599506D-02  1.15508148D-02\r\n  3.42081785D-02  1.63864344D-02  1.84539650D-02  1.15508148D-02  1.15508148D-02\r\n  3.42081785D-02  2.43831556D-02  2.19738856D-02  2.88599506D-02  1.15508148D-02\r\n  2.19738856D-02  2.19738856D-02  2.19738856D-02  2.88599506D-02  2.88599506D-02\r\n  2.19738856D-02  2.88599506D-02  2.88599506D-02  2.19738856D-02  2.88599506D-02\r\n  2.88599506D-02  2.88599506D-02  2.19738856D-02  2.88599506D-02  3.42081785D-02\r\n  2.19738856D-02  1.84539650D-02  1.15508148D-02  1.15508148D-02  2.43831556D-02\r\n  1.42847355D-02  1.42847355D-02  2.19738856D-02  1.15508148D-02  2.88599506D-02\r\n  2.19738856D-02  2.88599506D-02  2.88599506D-02  2.88599506D-02  5.72337866D-01\r\n  2.88599506D-02  2.88599506D-02  2.88599506D-02  2.14783605D-02  2.88599506D-02\r\n  2.88599506D-02  2.88599506D-02  1.00000000D+00  5.04734591D-02  5.04734591D-02\r\n  5.04734591D-02  5.04734591D-02  5.04734591D-02  1.26108989D-01  5.04734591D-02\r\n  1.49479091D-01  7.16036186D-02  8.06380734D-02  5.04734591D-02  5.04734591D-02\r\n  1.49479091D-01  1.06546797D-01  9.60190371D-02  1.26108989D-01  5.04734591D-02\r\n  9.60190371D-02  9.60190371D-02  9.60190371D-02  1.26108989D-01  1.26108989D-01\r\n  9.60190371D-02  1.26108989D-01  1.26108989D-01  9.60190371D-02  1.26108989D-01\r\n  1.26108989D-01  1.26108989D-01  9.60190371D-02  1.26108989D-01  1.49479091D-01\r\n  9.60190371D-02  8.06380734D-02  5.04734591D-02  5.04734591D-02  1.06546797D-01\r\n  6.24198392D-02  6.24198392D-02  9.60190371D-02  5.04734591D-02  1.26108989D-01\r\n  9.60190371D-02  1.26108989D-01  1.26108989D-01  1.26108989D-01  1.26108989D-01\r\n  6.69586897D-01  1.26108989D-01  1.26108989D-01  9.38537493D-02  1.26108989D-01\r\n  1.26108989D-01  1.26108989D-01  1.00000000D+00  5.43477893D-01  1.00000000D+00\r\n  2.13428419D-02  2.13428419D-02  2.13428419D-02  2.13428419D-02  2.13428419D-02\r\n  5.33255301D-02  2.13428419D-02  6.32076487D-02  3.02777849D-02  3.40980291D-02\r\n  2.13428419D-02  2.13428419D-02  6.32076487D-02  4.50536050D-02  4.06019129D-02\r\n  5.33255301D-02  2.13428419D-02  4.06019129D-02  4.06019129D-02  4.06019129D-02\r\n  5.33255301D-02  5.33255301D-02  4.06019129D-02  5.33255301D-02  5.33255301D-02\r\n  4.06019129D-02  5.33255301D-02  5.33255301D-02  5.33255301D-02  4.06019129D-02\r\n  5.33255301D-02  6.32076487D-02  4.06019129D-02  3.40980291D-02  2.13428419D-02\r\n  2.13428419D-02  4.50536050D-02  2.63944026D-02  2.63944026D-02  4.06019129D-02\r\n  2.13428419D-02  5.33255301D-02  4.06019129D-02  5.33255301D-02  5.33255301D-02\r\n  5.33255301D-02  5.33255301D-02  5.33255301D-02  5.33255301D-02  5.96803427D-01\r\n  3.96863185D-02  5.33255301D-02  5.33255301D-02  5.33255301D-02  1.00000000D+00\r\n  4.13307510D-02  4.13307510D-02  4.13307510D-02  4.13307510D-02  4.13307510D-02\r\n  1.03265740D-01  4.13307510D-02  1.22402608D-01  5.86334132D-02  6.60313815D-02\r\n  4.13307510D-02  4.13307510D-02  1.22402608D-01  8.72470215D-02  7.86262453D-02\r\n  1.03265740D-01  4.13307510D-02  7.86262453D-02  7.86262453D-02  7.86262453D-02\r\n  1.03265740D-01  1.03265740D-01  7.86262453D-02  1.03265740D-01  1.03265740D-01\r\n  7.86262453D-02  1.03265740D-01  1.03265740D-01  1.03265740D-01  7.86262453D-02\r\n  1.03265740D-01  1.22402608D-01  7.86262453D-02  6.60313815D-02  4.13307510D-02\r\n  4.13307510D-02  8.72470215D-02  5.11131771D-02  5.11131771D-02  7.86262453D-02\r\n  4.13307510D-02  1.03265740D-01  7.86262453D-02  1.03265740D-01  1.03265740D-01\r\n  1.03265740D-01  1.03265740D-01  1.03265740D-01  1.03265740D-01  1.03265740D-01\r\n  4.81324255D-01  1.03265740D-01  1.03265740D-01  1.03265740D-01  1.00000000D+00\r\n  5.43477893D-01  1.00000000D+00  5.43477893D-01  1.00000000D+00  5.43477893D-01\r\n  1.00000000D+00  1.00000000D+00 -3.80239636D-02  1.00000000D+00  1.00000000D+00\r\n -4.53596498D-04  1.00000000D+00  1.00000000D+00 -1.04409068D-04  1.00000000D+00\r\n  1.00000000D+00 -1.56986958D-03  1.00000000D+00  1.00000000D+00 -1.51058435D-02\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00 -6.02873974D-04\r\n  1.00000000D+00  1.00000000D+00 -2.16793314D-01  1.00000000D+00  1.00000000D+00\r\n -5.40687004D-03  1.00000000D+00  1.00000000D+00 -2.17261910D-02  1.00000000D+00\r\n  1.00000000D+00 -1.60277095D-02  1.00000000D+00  1.00000000D+00 -1.67879829D-04\r\n  1.00000000D+00  1.00000000D+00 -8.27674405D-04  1.00000000D+00  1.00000000D+00\r\n -8.62984210D-02  1.00000000D+00  1.00000000D+00 -3.36676676D-05  1.00000000D+00\r\n  1.00000000D+00 -1.34372637D-02  1.00000000D+00  1.00000000D+00 -1.20522391D-05\r\n  1.00000000D+00  1.00000000D+00 -1.49709766D-03  1.00000000D+00  1.00000000D+00\r\n -7.59160030D-05  1.00000000D+00  1.00000000D+00 -1.57006609D-04  1.00000000D+00\r\n  1.00000000D+00 -1.17640331D-04  1.00000000D+00  1.00000000D+00 -5.89511671D-07\r\n  1.00000000D+00  1.00000000D+00 -1.72268410D-05  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00 -5.83616551D-04  1.00000000D+00  1.00000000D+00\r\n -4.50151134D-03  1.00000000D+00  1.00000000D+00 -1.43061380D-03  1.00000000D+00\r\n  1.00000000D+00 -2.23359420D-05  1.00000000D+00  1.00000000D+00 -2.10586673D-04\r\n  1.00000000D+00  1.00000000D+00 -1.93471182D-03  1.00000000D+00  1.00000000D+00\r\n -1.85886130D-03  1.00000000D+00  1.00000000D+00 -1.56698748D-02  1.00000000D+00\r\n  1.00000000D+00 -1.45537336D-03  1.00000000D+00  1.00000000D+00 -1.11717703D-02\r\n  1.00000000D+00  1.00000000D+00 -4.73823305D-03  1.00000000D+00  1.00000000D+00\r\n -1.16330304D-03  1.00000000D+00  1.00000000D+00 -4.46149008D-03  1.00000000D+00\r\n  1.00000000D+00 -1.20798806D-02  1.00000000D+00  1.00000000D+00 -4.05453029D-05\r\n  1.00000000D+00  1.00000000D+00 -2.53228028D-03  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00 -7.26409417D-05  1.00000000D+00  1.00000000D+00\r\n -4.11937665D-03  1.00000000D+00  1.00000000D+00 -6.60947384D-03  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00 -2.41819128D-01  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00 -2.65067309D-01  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  2.50000000D+00  2.70000005D+00  2.50000000D+00\r\n  2.70000005D+00  2.90000010D+00  2.90000010D+00  2.90000010D+00  2.90000010D+00\r\n  1.66986734D-01 -5.71339190D-01  1.00000000D+00  2.40000010D+00  1.50000000D+00\r\n  2.40000010D+00  1.89999998D+00  1.60000002D+00  2.09999990D+00  1.79999995D+00\r\n  1.79999995D+00  1.79999995D+00  1.79999995D+00  1.79999995D+00  1.79999995D+00\r\n  1.89999998D+00  1.89999998D+00  1.79999995D+00  2.20000005D+00  2.59999990D+00\r\n  2.59999990D+00  2.20000005D+00  1.50000000D+00  3.00000000D+00  1.89999998D+00\r\n  2.40000010D+00  2.40000010D+00  2.40000010D+00  2.40000010D+00  1.89999998D+00\r\n  2.20000005D+00  1.70000005D+00  2.20000005D+00  2.90000010D+00  2.20000005D+00\r\n  2.59999990D+00  1.79999995D+00  1.19615935D-01 -4.09261674D-01  1.00000000D+00\r\n  1.70000005D+00  1.70000005D+00  1.70000005D+00  5.66986762D-03 -1.93992499D-02\r\n  1.00000000D+00  1.60000002D+00  1.60000002D+00  1.60000002D+00  1.50000000D+00\r\n  1.50000000D+00  1.60000002D+00  1.70000005D+00 -6.00000000D+01  1.00000000D+00\r\n -3.60000000D+01  1.00000000D+00 -6.00000000D+01  1.00000000D+00 -3.60000000D+01\r\n  1.00000000D+00 -4.10000000D+01  1.00000000D+00 -4.10000000D+01  1.00000000D+00\r\n -4.10000000D+01  1.00000000D+00 -4.10000000D+01  1.00000000D+00 -1.90000000D+01\r\n  1.00000000D+00 -3.30000000D+01  1.00000000D+00 -6.00000000D+01  1.00000000D+00\r\n -6.00000000D+01  1.00000000D+00 -3.20000000D+01  1.00000000D+00 -2.60000000D+01\r\n  1.00000000D+00 -6.00000000D+01  1.00000000D+00 -3.10000000D+01  1.00000000D+00\r\n -3.00000000D+01  1.00000000D+00 -3.10000000D+01  1.00000000D+00 -3.00000000D+01\r\n  1.00000000D+00 -4.10000000D+01  1.00000000D+00 -3.00000000D+01  1.00000000D+00\r\n -3.00000000D+01  1.00000000D+00 -3.00000000D+01  1.00000000D+00 -6.00000000D+01\r\n  1.00000000D+00 -2.80000000D+01  1.00000000D+00 -2.80000000D+01  1.00000000D+00\r\n -3.10000000D+01  1.00000000D+00 -2.30000000D+01  1.00000000D+00 -1.50000000D+01\r\n  1.00000000D+00 -4.50000000D+01  1.00000000D+00 -1.50000000D+01  1.00000000D+00\r\n -4.90000000D+01  1.00000000D+00 -2.60000000D+01  1.00000000D+00 -1.50000000D+01\r\n  1.00000000D+00 -6.00000000D+01  1.00000000D+00 -6.00000000D+01  1.00000000D+00\r\n -8.00000000D+00  1.00000000D+00 -2.50000000D+01  1.00000000D+00 -9.00000000D+00\r\n  1.00000000D+00 -3.10000000D+01  1.00000000D+00 -2.10000000D+01  1.00000000D+00\r\n -3.00000000D+01  1.00000000D+00 -8.00000000D+00  1.00000000D+00 -8.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00 -8.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00  1.00000000D+00  1.00000000D+00  1.36076880D+07\r\n  1.00000000D+00 -1.52668730D+07  1.00000000D+02  1.00000000D+00  1.00000000D+00\r\n -1.00000000D+00  1.00000000D+00  1.00000000D+00 -4.95945245D-01 -4.95945245D-01\r\n -4.95945245D-01 -4.95945245D-01 -4.95945245D-01 -1.23912954D+00 -4.95945245D-01\r\n -1.46876097D+00 -7.03567266D-01 -7.92338610D-01 -4.95945245D-01 -4.95945245D-01\r\n -1.46876097D+00 -1.04691410D+00 -9.43469822D-01 -1.23912954D+00 -4.95945245D-01\r\n -9.43469822D-01 -9.43469822D-01 -9.43469822D-01 -1.23912954D+00 -1.23912954D+00\r\n -9.43469822D-01 -1.23912954D+00 -1.23912954D+00 -9.43469822D-01 -1.23912954D+00\r\n -1.23912954D+00 -1.23912954D+00 -9.43469822D-01 -1.23912954D+00 -1.46876097D+00\r\n -9.43469822D-01 -7.92338610D-01 -4.95945245D-01 -4.95945245D-01 -1.04691410D+00\r\n -6.13328755D-01 -6.13328755D-01 -9.43469822D-01 -4.95945245D-01 -1.23912954D+00\r\n -9.43469822D-01 -1.23912954D+00 -1.23912954D+00 -1.23912954D+00 -1.23912954D+00\r\n -1.23912954D+00 -1.23912954D+00 -1.23912954D+00 -9.22194004D-01 -1.23912954D+00\r\n -1.23912954D+00 -1.23912954D+00 -1.00000000D+00 -2.92272508D-01 -1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00                                                \r\n       1     109     110     111     112     113     114     115     116     117\r\n     118     119     120     121     122     123     124     125     126     127\r\n     128     129     130     131     132     133     134     135     136     137\r\n     138     139     140     141     142     143     144     145     146     147\r\n     148     149     150     151     152     153     154     155     156     157\r\n     158     159     160     161     162     163                                \r\n     720     721     722     723     724     725     726     727     728     729\r\n     730     731     732     733     734     735     736     737     738     739\r\n     740     741     742     743     744     745     746     747     748     749\r\n     750     751     752     753     754     755     756     757     758     759\r\n     760     761     762     763     764     765     766     767     768     769\r\n     770     771     772     773     774     775     776     777     778     779\r\n     780     781     782     783     784     785     786     787     788     789\r\n     790     791     792     793     794     795     796     797     798     799\r\n     800     801     802     803     804     805     806     807     808     809\r\n     810     811     812     813     814     815     816     817     818     819\r\n     820     821     822     823     824     825     826     827     720     721\r\n     722     723     724     725     726     727     728     729     730     731\r\n     732     733     734     735     736     737     738     739     740     741\r\n     742     743     744     745     746     747     748     749     750     751\r\n     752     753     754     755     756     757     758     759     760     761\r\n     762     763     764     765     766     767     768     769     770     771\r\n     772     773                                                                \r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00 -1.00000000D+00\r\n -1.00000000D+00 -1.00000000D+00 -1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00  1.00000000D+00\r\n  1.00000000D+00  1.00000000D+00                                                \r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/bfile3.txt",
    "content": "       -0.187248E+05\r\n        0.112479E+05\r\n        0.132356E+05\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/hbio.c",
    "content": "\n/*                    Harwell-Boeing File I/O in C\n                                V. 1.0\n\n           National Institute of Standards and Technology, MD.\n                             K.A. Remington\n\n++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n                                NOTICE\n\n Permission to use, copy, modify, and distribute this software and\n its documentation for any purpose and without fee is hereby granted\n provided that the above copyright notice appear in all copies and\n that both the copyright notice and this permission notice appear in\n supporting documentation.\n\n Neither the Author nor the Institution (National Institute of Standards\n and Technology) make any representations about the suitability of this\n software for any purpose. This software is provided \"as is\" without\n expressed or implied warranty.\n++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n\n                         ---------------------\n                         INTERFACE DESCRIPTION\n                         ---------------------\n  ---------------\n  QUERY FUNCTIONS\n  ---------------\n\n  FUNCTION:\n\n  int readHB_info(const char *filename, int *M, int *N, int *nz,\n  char **Type, int *Nrhs)\n\n  DESCRIPTION:\n\n  The readHB_info function opens and reads the header information from\n  the specified Harwell-Boeing file, and reports back the number of rows\n  and columns in the stored matrix (M and N), the number of nonzeros in\n  the matrix (nz), the 3-character matrix type(Type), and the number of\n  right-hand-sides stored along with the matrix (Nrhs).  This function\n  is designed to retrieve basic size information which can be used to\n  allocate arrays.\n\n  FUNCTION:\n\n  int  readHB_header(FILE* in_file, char* Title, char* Key, char* Type,\n                    int* Nrow, int* Ncol, int* Nnzero, int* Nrhs, int* Nrhsix, \n                    char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                    int* Ptrcrd, int* Indcrd, int* Valcrd, int* Rhscrd,\n                    char *Rhstype)\n\n  DESCRIPTION:\n\n  More detailed than the readHB_info function, readHB_header() reads from\n  the specified Harwell-Boeing file all of the header information.\n\n\n  ------------------------------\n  DOUBLE PRECISION I/O FUNCTIONS\n  ------------------------------\n  FUNCTION:\n\n  int readHB_newmat_double(const char *filename, int *M, int *N, *int nz,\n  int **colptr, int **rowind,  double**val)\n\n  int readHB_mat_double(const char *filename, int *colptr, int *rowind,\n  double*val)\n\n\n  DESCRIPTION:\n\n  This function opens and reads the specified file, interpreting its\n  contents as a sparse matrix stored in the Harwell/Boeing standard\n  format.  (See readHB_aux_double to read auxillary vectors.)\n        -- Values are interpreted as double precision numbers. --\n\n  The \"mat\" function uses _pre-allocated_ vectors to hold the index and\n  nonzero value information.\n\n  The \"newmat\" function allocates vectors to hold the index and nonzero\n  value information, and returns pointers to these vectors along with\n  matrix dimension and number of nonzeros.\n\n  FUNCTION:\n\n  int readHB_aux_double(const char* filename, const char AuxType, double b[])\n\n  int readHB_newaux_double(const char* filename, const char AuxType, double** b)\n\n  DESCRIPTION:\n\n  This function opens and reads from the specified file auxillary vector(s).\n  The char argument Auxtype determines which type of auxillary vector(s)\n  will be read (if present in the file).\n\n                  AuxType = 'F'   right-hand-side\n                  AuxType = 'G'   initial estimate (Guess)\n                  AuxType = 'X'   eXact solution\n\n  If Nrhs > 1, all of the Nrhs vectors of the given type are read and\n  stored in column-major order in the vector b.\n\n  The \"newaux\" function allocates a vector to hold the values retrieved.\n  The \"mat\" function uses a _pre-allocated_ vector to hold the values.\n\n  FUNCTION:\n\n  int writeHB_mat_double(const char* filename, int M, int N,\n                        int nz, const int colptr[], const int rowind[],\n                        const double val[], int Nrhs, const double rhs[],\n                        const double guess[], const double exact[],\n                        const char* Title, const char* Key, const char* Type,\n                        char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                        const char* Rhstype)\n\n  DESCRIPTION:\n\n  The writeHB_mat_double function opens the named file and writes the specified\n  matrix and optional auxillary vector(s) to that file in Harwell-Boeing\n  format.  The format arguments (Ptrfmt,Indfmt,Valfmt, and Rhsfmt) are\n  character strings specifying \"Fortran-style\" output formats -- as they\n  would appear in a Harwell-Boeing file.  They are used to produce output\n  which is as close as possible to what would be produced by Fortran code,\n  but note that \"D\" and \"P\" edit descriptors are not supported.\n  If NULL, the following defaults will be used:\n                    Ptrfmt = Indfmt = \"(8I10)\"\n                    Valfmt = Rhsfmt = \"(4E20.13)\"\n\n  -----------------------\n  CHARACTER I/O FUNCTIONS\n  -----------------------\n  FUNCTION:\n\n  int readHB_mat_char(const char* filename, int colptr[], int rowind[],\n                                           char val[], char* Valfmt)\n  int readHB_newmat_char(const char* filename, int* M, int* N, int* nonzeros,\n                          int** colptr, int** rowind, char** val, char** Valfmt)\n\n  DESCRIPTION:\n\n  This function opens and reads the specified file, interpreting its\n  contents as a sparse matrix stored in the Harwell/Boeing standard\n  format.  (See readHB_aux_char to read auxillary vectors.)\n              -- Values are interpreted as char strings.     --\n  (Used to translate exact values from the file into a new storage format.)\n\n  The \"mat\" function uses _pre-allocated_ arrays to hold the index and\n  nonzero value information.\n\n  The \"newmat\" function allocates char arrays to hold the index\n  and nonzero value information, and returns pointers to these arrays\n  along with matrix dimension and number of nonzeros.\n\n  FUNCTION:\n\n  int readHB_aux_char(const char* filename, const char AuxType, char b[])\n  int readHB_newaux_char(const char* filename, const char AuxType, char** b,\n                         char** Rhsfmt)\n\n  DESCRIPTION:\n\n  This function opens and reads from the specified file auxillary vector(s).\n  The char argument Auxtype determines which type of auxillary vector(s)\n  will be read (if present in the file).\n\n                  AuxType = 'F'   right-hand-side\n                  AuxType = 'G'   initial estimate (Guess)\n                  AuxType = 'X'   eXact solution\n\n  If Nrhs > 1, all of the Nrhs vectors of the given type are read and\n  stored in column-major order in the vector b.\n\n  The \"newaux\" function allocates a character array to hold the values\n                retrieved.\n  The \"mat\" function uses a _pre-allocated_ array to hold the values.\n\n  FUNCTION:\n\n  int writeHB_mat_char(const char* filename, int M, int N,\n                        int nz, const int colptr[], const int rowind[],\n                        const char val[], int Nrhs, const char rhs[],\n                        const char guess[], const char exact[],\n                        const char* Title, const char* Key, const char* Type,\n                        char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                        const char* Rhstype)\n\n  DESCRIPTION:\n\n  The writeHB_mat_char function opens the named file and writes the specified\n  matrix and optional auxillary vector(s) to that file in Harwell-Boeing\n  format.  The format arguments (Ptrfmt,Indfmt,Valfmt, and Rhsfmt) are\n  character strings specifying \"Fortran-style\" output formats -- as they\n  would appear in a Harwell-Boeing file.  Valfmt and Rhsfmt must accurately\n  represent the character representation of the values stored in val[]\n  and rhs[].\n\n  If NULL, the following defaults will be used for the integer vectors:\n                    Ptrfmt = Indfmt = \"(8I10)\"\n                    Valfmt = Rhsfmt = \"(4E20.13)\"\n\n\n*/\n\n/*---------------------------------------------------------------------*/\n/* If zero-based indexing is desired, _SP_base should be set to 0      */\n/* This will cause indices read from H-B files to be decremented by 1  */\n/*             and indices written to H-B files to be incremented by 1 */\n/*            <<<  Standard usage is _SP_base = 1  >>>                 */\n#ifndef _SP_base\n#define _SP_base 1\n#endif\n/*---------------------------------------------------------------------*/\n\n#include \"hbio.h\"\n#include <string.h>\n#include <math.h>\n\nchar *substr(const char* S, const int pos, const int len);\nvoid upcase(char* S);\nvoid IOHBTerminate(char* message);\n\nint readHB_info(const char* filename, int* M, int* N, int* nz, char** Type,\n                                                      int* Nrhs)\n{\n/****************************************************************************/\n/*  The readHB_info function opens and reads the header information from    */\n/*  the specified Harwell-Boeing file, and reports back the number of rows  */\n/*  and columns in the stored matrix (M and N), the number of nonzeros in   */\n/*  the matrix (nz), and the number of right-hand-sides stored along with   */\n/*  the matrix (Nrhs).                                                      */\n/*                                                                          */\n/*  For a description of the Harwell Boeing standard, see:                  */\n/*            Duff, et al.,  ACM TOMS Vol.15, No.1, March 1989              */\n/*                                                                          */\n/*    ----------                                                            */\n/*    **CAVEAT**                                                            */\n/*    ----------                                                            */\n/*  **  If the input file does not adhere to the H/B format, the  **        */\n/*  **             results will be unpredictable.                 **        */\n/*                                                                          */\n/****************************************************************************/\n    FILE *in_file;\n    int Ptrcrd, Indcrd, Valcrd, Rhscrd;\n    int Nrow, Ncol, Nnzero, Nrhsix;\n    char *mat_type;\n    char Title[73], Key[9], Rhstype[4];\n    char Ptrfmt[17], Indfmt[17], Valfmt[21], Rhsfmt[21];\n\n    mat_type = (char *) malloc(4);\n    if ( mat_type == NULL ) IOHBTerminate(\"Insufficient memory for mat_typen\");\n\n    if ( (in_file = fopen( filename, \"r\")) == NULL ) {\n       fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n       return 0;\n    }\n\n    readHB_header(in_file, Title, Key, mat_type, &Nrow, &Ncol, &Nnzero, \n                  Nrhs,  &Nrhsix,\n                  Ptrfmt, Indfmt, Valfmt, Rhsfmt,\n                  &Ptrcrd, &Indcrd, &Valcrd, &Rhscrd, Rhstype);\n    fclose(in_file);\n    *Type = mat_type;\n    *(*Type+3) = (char) NULL;\n    *M    = Nrow;\n    *N    = Ncol;\n    *nz   = Nnzero;\n    if (Rhscrd == 0) {*Nrhs = 0;}\n\n/*  In verbose mode, print some of the header information:   */\n/*\n    if (verbose == 1)\n    {\n        printf(\"Reading from Harwell-Boeing file %s (verbose on)...\\n\",filename);\n        printf(\"  Title: %s\\n\",Title);\n        printf(\"  Key:   %s\\n\",Key);\n        printf(\"  The stored matrix is %i by %i with %i nonzeros.\\n\",\n                *M, *N, *nz );\n        printf(\"  %i right-hand--side(s) stored.\\n\",*Nrhs);\n    }\n*/\n\n    return 1;\n\n}\n\n\n\nint readHB_header(FILE* in_file, char* Title, char* Key, char* Type,\n                    int* Nrow, int* Ncol, int* Nnzero, int* Nrhs, int* Nrhsix,\n                    char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                    int* Ptrcrd, int* Indcrd, int* Valcrd, int* Rhscrd,\n                    char *Rhstype)\n{\n/*************************************************************************/\n/*  Read header information from the named H/B file...                   */\n/*************************************************************************/\n    int Totcrd,Neltvl;\n    char line[BUFSIZ];\n\n/*  First line:   */\n    fgets(line, BUFSIZ, in_file);\n    if ( sscanf(line,\"%*s\") < 0 )\n        IOHBTerminate(\"iohb.c: Null (or blank) first line of HB file.\\n\");\n    (void) sscanf(line, \"%72c%8[^\\n]\", Title, Key);\n    *(Key+8) = (char) NULL;\n    *(Title+72) = (char) NULL;\n\n/*  Second line:  */\n    fgets(line, BUFSIZ, in_file);\n    if ( sscanf(line,\"%*s\") < 0 )\n        IOHBTerminate(\"iohb.c: Null (or blank) second line of HB file.\\n\");\n    if ( sscanf(line,\"%i\",&Totcrd) != 1) Totcrd = 0;\n    if ( sscanf(line,\"%*i%i\",Ptrcrd) != 1) *Ptrcrd = 0;\n    if ( sscanf(line,\"%*i%*i%i\",Indcrd) != 1) *Indcrd = 0;\n    if ( sscanf(line,\"%*i%*i%*i%i\",Valcrd) != 1) *Valcrd = 0;\n    if ( sscanf(line,\"%*i%*i%*i%*i%i\",Rhscrd) != 1) *Rhscrd = 0;\n\n/*  Third line:   */\n    fgets(line, BUFSIZ, in_file);\n    if ( sscanf(line,\"%*s\") < 0 )\n        IOHBTerminate(\"iohb.c: Null (or blank) third line of HB file.\\n\");\n    if ( sscanf(line, \"%3c\", Type) != 1)\n        IOHBTerminate(\"iohb.c: Invalid Type info, line 3 of Harwell-Boeing file.\\n\");\n    upcase(Type);\n    if ( sscanf(line,\"%*3c%i\",Nrow) != 1) *Nrow = 0 ;\n    if ( sscanf(line,\"%*3c%*i%i\",Ncol) != 1) *Ncol = 0 ;\n    if ( sscanf(line,\"%*3c%*i%*i%i\",Nnzero) != 1) *Nnzero = 0 ;\n    if ( sscanf(line,\"%*3c%*i%*i%*i%i\",&Neltvl) != 1) Neltvl = 0 ;\n\n/*  Fourth line:  */\n    fgets(line, BUFSIZ, in_file);\n    if ( sscanf(line,\"%*s\") < 0 )\n        IOHBTerminate(\"iohb.c: Null (or blank) fourth line of HB file.\\n\");\n    if ( sscanf(line, \"%16c\",Ptrfmt) != 1)\n        IOHBTerminate(\"iohb.c: Invalid format info, line 4 of Harwell-Boeing file.\\n\");\n    if ( sscanf(line, \"%*16c%16c\",Indfmt) != 1)\n        IOHBTerminate(\"iohb.c: Invalid format info, line 4 of Harwell-Boeing file.\\n\");\n    if ( sscanf(line, \"%*16c%*16c%20c\",Valfmt) != 1)\n        IOHBTerminate(\"iohb.c: Invalid format info, line 4 of Harwell-Boeing file.\\n\");\n    sscanf(line, \"%*16c%*16c%*20c%20c\",Rhsfmt);\n    *(Ptrfmt+16) = (char) NULL;\n    *(Indfmt+16) = (char) NULL;\n    *(Valfmt+20) = (char) NULL;\n    *(Rhsfmt+20) = (char) NULL;\n\n/*  (Optional) Fifth line: */\n    if (*Rhscrd != 0 )\n    {\n       fgets(line, BUFSIZ, in_file);\n       if ( sscanf(line,\"%*s\") < 0 )\n           IOHBTerminate(\"iohb.c: Null (or blank) fifth line of HB file.\\n\");\n       if ( sscanf(line, \"%3c\", Rhstype) != 1)\n         IOHBTerminate(\"iohb.c: Invalid RHS type information, line 5 of Harwell-Boeing file.\\n\");\n       if ( sscanf(line, \"%*3c%i\", Nrhs) != 1) *Nrhs = 0;\n       if ( sscanf(line, \"%*3c%*i%i\", Nrhsix) != 1) *Nrhsix = 0;\n    }\n    return 1;\n}\n\n\nint readHB_mat_double(const char* filename, int colptr[], int rowind[],\n                                                                 double val[])\n{\n/****************************************************************************/\n/*  This function opens and reads the specified file, interpreting its      */\n/*  contents as a sparse matrix stored in the Harwell/Boeing standard       */\n/*  format and creating compressed column storage scheme vectors to hold    */\n/*  the index and nonzero value information.                                */\n/*                                                                          */\n/*    ----------                                                            */\n/*    **CAVEAT**                                                            */\n/*    ----------                                                            */\n/*  Parsing real formats from Fortran is tricky, and this file reader       */\n/*  does not claim to be foolproof.   It has been tested for cases when     */\n/*  the real values are printed consistently and evenly spaced on each      */\n/*  line, with Fixed (F), and Exponential (E or D) formats.                 */\n/*                                                                          */\n/*  **  If the input file does not adhere to the H/B format, the  **        */\n/*  **             results will be unpredictable.                 **        */\n/*                                                                          */\n/****************************************************************************/\n    FILE *in_file;\n    int i,j,ind,col,offset,count,last,Nrhs,Nrhsix;\n    int Ptrcrd, Indcrd, Valcrd, Rhscrd;\n    int Nrow, Ncol, Nnzero, Nentries;\n    int Ptrperline, Ptrwidth, Indperline, Indwidth;\n    int Valperline, Valwidth, Valprec;\n    int Valflag;           /* Indicates 'E','D', or 'F' float format */\n    char* ThisElement;\n    char Title[73], Key[9], Type[4], Rhstype[4];\n    char Ptrfmt[17], Indfmt[17], Valfmt[21], Rhsfmt[21];\n    char line[BUFSIZ];\n\n    if ( (in_file = fopen( filename, \"r\")) == NULL ) {\n       fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n       return 0;\n    }\n\n    readHB_header(in_file, Title, Key, Type, &Nrow, &Ncol, &Nnzero, \n                  &Nrhs, &Nrhsix,\n                  Ptrfmt, Indfmt, Valfmt, Rhsfmt,\n                  &Ptrcrd, &Indcrd, &Valcrd, &Rhscrd, Rhstype);\n\n/*  Parse the array input formats from Line 3 of HB file  */\n    ParseIfmt(Ptrfmt,&Ptrperline,&Ptrwidth);\n    ParseIfmt(Indfmt,&Indperline,&Indwidth);\n    if ( Type[0] != 'P' ) {          /* Skip if pattern only  */\n    ParseRfmt(Valfmt,&Valperline,&Valwidth,&Valprec,&Valflag);\n    }\n\n/*  Read column pointer array:   */\n\n    offset = 1-_SP_base;  /* if base 0 storage is declared (via macro definition), */\n                          /* then storage entries are offset by 1                  */\n\n    ThisElement = (char *) malloc(Ptrwidth+1);\n    if ( ThisElement == NULL ) IOHBTerminate(\"Insufficient memory for ThisElement.\");\n    *(ThisElement+Ptrwidth) = (char) NULL;\n    count=0;\n    for (i=0;i<Ptrcrd;i++)\n    {\n       fgets(line, BUFSIZ, in_file);\n       if ( sscanf(line,\"%*s\") < 0 )\n         IOHBTerminate(\"iohb.c: Null (or blank) line in pointer data region of HB file.\\n\");\n       col =  0;\n       for (ind = 0;ind<Ptrperline;ind++)\n       {\n          if (count > Ncol) break;\n          strncpy(ThisElement,line+col,Ptrwidth);\n  /* ThisElement = substr(line,col,Ptrwidth); */\n          colptr[count] = atoi(ThisElement)-offset;\n          count++; col += Ptrwidth;\n       }\n    }\n    free(ThisElement);\n\n/*  Read row index array:  */\n\n    ThisElement = (char *) malloc(Indwidth+1);\n    if ( ThisElement == NULL ) IOHBTerminate(\"Insufficient memory for ThisElement.\");\n    *(ThisElement+Indwidth) = (char) NULL;\n    count = 0;\n    for (i=0;i<Indcrd;i++)\n    {\n       fgets(line, BUFSIZ, in_file);\n       if ( sscanf(line,\"%*s\") < 0 )\n         IOHBTerminate(\"iohb.c: Null (or blank) line in index data region of HB file.\\n\");\n       col =  0;\n       for (ind = 0;ind<Indperline;ind++)\n       {\n          if (count == Nnzero) break;\n          strncpy(ThisElement,line+col,Indwidth);\n/*        ThisElement = substr(line,col,Indwidth); */\n          rowind[count] = atoi(ThisElement)-offset;\n          count++; col += Indwidth;\n       }\n    }\n    free(ThisElement);\n\n/*  Read array of values:  */\n\n    if ( Type[0] != 'P' ) {          /* Skip if pattern only  */\n\n       if ( Type[0] == 'C' ) Nentries = 2*Nnzero;\n           else Nentries = Nnzero;\n\n    ThisElement = (char *) malloc(Valwidth+1);\n    if ( ThisElement == NULL )\n      IOHBTerminate(\"Insufficient memory for ThisElement.\");\n    *(ThisElement+Valwidth) = (char) NULL;\n    count = 0;\n    for (i=0;i<Valcrd;i++)\n    {\n       fgets(line, BUFSIZ, in_file);\n       if ( sscanf(line,\"%*s\") < 0 )\n         IOHBTerminate(\"iohb.c: Null (or blank) line in value data region of HB file.\\n\");\n       if (Valflag == 'D')  {\n          while( strchr(line,'D') ) *strchr(line,'D') = 'E';\n/*           *strchr(Valfmt,'D') = 'E'; */\n       }\n       col =  0;\n       for (ind = 0;ind<Valperline;ind++)\n       {\n          if (count == Nentries) break;\n          strncpy(ThisElement,line+col,Valwidth);\n          /*ThisElement = substr(line,col,Valwidth);*/\n          if ( Valflag != 'F' && strchr(ThisElement,'E') == NULL ) {\n             /* insert a char prefix for exp */\n             last = strlen(ThisElement);\n             for (j=last+1;j>=0;j--) {\n                ThisElement[j] = ThisElement[j-1];\n                if ( ThisElement[j] == '+' || ThisElement[j] == '-' ) {\n                   ThisElement[j-1] = Valflag;\n                   break;\n                }\n             }\n          }\n          val[count] = atof(ThisElement);\n          count++; col += Valwidth;\n       }\n    }\n    free(ThisElement);\n    }\n\n    fclose(in_file);\n    return 1;\n}\n\nint readHB_newmat_double(const char* filename, int* M, int* N, int* nonzeros,\n                         int** colptr, int** rowind, double** val)\n{\n  int Nrhs;\n        char *Type;\n\n  readHB_info(filename, M, N, nonzeros, &Type, &Nrhs);\n\n        *colptr = (int *)malloc((*N+1)*sizeof(int));\n        if ( *colptr == NULL ) IOHBTerminate(\"Insufficient memory for colptr.\\n\");\n        *rowind = (int *)malloc(*nonzeros*sizeof(int));\n        if ( *rowind == NULL ) IOHBTerminate(\"Insufficient memory for rowind.\\n\");\n        if ( Type[0] == 'C' ) {\n/*\n   fprintf(stderr, \"Warning: Reading complex data from HB file %s.\\n\",filename);\n   fprintf(stderr, \"         Real and imaginary parts will be interlaced in val[].\\n\");\n*/\n           /* Malloc enough space for real AND imaginary parts of val[] */\n           *val = (double *)malloc(*nonzeros*sizeof(double)*2);\n           if ( *val == NULL ) IOHBTerminate(\"Insufficient memory for val.\\n\");\n        } else {\n           if ( Type[0] != 'P' ) {\n             /* Malloc enough space for real array val[] */\n             *val = (double *)malloc(*nonzeros*sizeof(double));\n             if ( *val == NULL ) IOHBTerminate(\"Insufficient memory for val.\\n\");\n           }\n        }  /* No val[] space needed if pattern only */\n  return readHB_mat_double(filename, *colptr, *rowind, *val);\n\n}\n\nint readHB_aux_double(const char* filename, const char AuxType, double b[])\n{\n/****************************************************************************/\n/*  This function opens and reads the specified file, placing auxillary     */\n/*  vector(s) of the given type (if available) in b.                        */\n/*  Return value is the number of vectors successfully read.                */\n/*                                                                          */\n/*                AuxType = 'F'   full right-hand-side vector(s)            */\n/*                AuxType = 'G'   initial Guess vector(s)                   */\n/*                AuxType = 'X'   eXact solution vector(s)                  */\n/*                                                                          */\n/*    ----------                                                            */\n/*    **CAVEAT**                                                            */\n/*    ----------                                                            */\n/*  Parsing real formats from Fortran is tricky, and this file reader       */\n/*  does not claim to be foolproof.   It has been tested for cases when     */\n/*  the real values are printed consistently and evenly spaced on each      */\n/*  line, with Fixed (F), and Exponential (E or D) formats.                 */\n/*                                                                          */\n/*  **  If the input file does not adhere to the H/B format, the  **        */\n/*  **             results will be unpredictable.                 **        */\n/*                                                                          */\n/****************************************************************************/\n    FILE *in_file;\n    int i,j,n,maxcol,start,stride,col,last,linel;\n    int Ptrcrd, Indcrd, Valcrd, Rhscrd;\n    int Nrow, Ncol, Nnzero, Nentries;\n    int Nrhs, Nrhsix, nvecs, rhsi;\n    int Rhsperline, Rhswidth, Rhsprec;\n    int Rhsflag;\n    char *ThisElement;\n    char Title[73], Key[9], Type[4], Rhstype[4];\n    char Ptrfmt[17], Indfmt[17], Valfmt[21], Rhsfmt[21];\n    char line[BUFSIZ];\n\n    if ((in_file = fopen( filename, \"r\")) == NULL) {\n      fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n      return 0;\n    }\n\n    readHB_header(in_file, Title, Key, Type, &Nrow, &Ncol, &Nnzero, \n                  &Nrhs, &Nrhsix,\n                  Ptrfmt, Indfmt, Valfmt, Rhsfmt,\n                  &Ptrcrd, &Indcrd, &Valcrd, &Rhscrd, Rhstype);\n\n    if (Nrhs <= 0)\n    {\n      fprintf(stderr, \"Warn: Attempt to read auxillary vector(s) when none are present.\\n\");\n      return 0;\n    }\n    if (Rhstype[0] != 'F' )\n    {\n      fprintf(stderr,\"Warn: Attempt to read auxillary vector(s) which are not stored in Full form.\\n\");\n      fprintf(stderr,\"       Rhs must be specified as full. \\n\");\n      return 0;\n    }\n\n/* If reading complex data, allow for interleaved real and imaginary values. */\n    if ( Type[0] == 'C' ) {\n       Nentries = 2*Nrow;\n     } else {\n       Nentries = Nrow;\n    }\n\n    nvecs = 1;\n\n    if ( Rhstype[1] == 'G' ) nvecs++;\n    if ( Rhstype[2] == 'X' ) nvecs++;\n\n    if ( AuxType == 'G' && Rhstype[1] != 'G' ) {\n      fprintf(stderr, \"Warn: Attempt to read auxillary Guess vector(s) when none are present.\\n\");\n      return 0;\n    }\n    if ( AuxType == 'X' && Rhstype[2] != 'X' ) {\n      fprintf(stderr, \"Warn: Attempt to read auxillary eXact solution vector(s) when none are present.\\n\");\n      return 0;\n    }\n\n    ParseRfmt(Rhsfmt, &Rhsperline, &Rhswidth, &Rhsprec,&Rhsflag);\n    maxcol = Rhsperline*Rhswidth;\n\n/*  Lines to skip before starting to read RHS values... */\n    n = Ptrcrd + Indcrd + Valcrd;\n\n    for (i = 0; i < n; i++)\n      fgets(line, BUFSIZ, in_file);\n\n/*  start  - number of initial aux vector entries to skip   */\n/*           to reach first  vector requested               */\n/*  stride - number of aux vector entries to skip between   */\n/*           requested vectors                              */\n    if ( AuxType == 'F' ) start = 0;\n    else if ( AuxType == 'G' ) start = Nentries;\n    else start = (nvecs-1)*Nentries;\n    stride = (nvecs-1)*Nentries;\n\n    fgets(line, BUFSIZ, in_file);\n    linel= strchr(line,'\\n')-line;\n    col = 0;\n/*  Skip to initial offset */\n\n    for (i=0;i<start;i++) {\n       if ( col >=  ( maxcol<linel?maxcol:linel ) ) {\n           fgets(line, BUFSIZ, in_file);\n           linel= strchr(line,'\\n')-line;\n           col = 0;\n       }\n       col += Rhswidth;\n    }\n    if (Rhsflag == 'D')  {\n       while( strchr(line,'D') ) *strchr(line,'D') = 'E';\n    }\n\n/*  Read a vector of desired type, then skip to next */\n/*  repeating to fill Nrhs vectors                   */\n\n  ThisElement = (char *) malloc(Rhswidth+1);\n  if ( ThisElement == NULL ) IOHBTerminate(\"Insufficient memory for ThisElement.\");\n  *(ThisElement+Rhswidth) = (char) NULL;\n  for (rhsi=0;rhsi<Nrhs;rhsi++) {\n\n    for (i=0;i<Nentries;i++) {\n       if ( col >= ( maxcol<linel?maxcol:linel ) ) {\n           fgets(line, BUFSIZ, in_file);\n           linel= strchr(line,'\\n')-line;\n           if (Rhsflag == 'D')  {\n              while( strchr(line,'D') ) *strchr(line,'D') = 'E';\n           }\n           col = 0;\n       }\n       strncpy(ThisElement,line+col,Rhswidth);\n       /*ThisElement = substr(line, col, Rhswidth);*/\n          if ( Rhsflag != 'F' && strchr(ThisElement,'E') == NULL ) {\n             /* insert a char prefix for exp */\n             last = strlen(ThisElement);\n             for (j=last+1;j>=0;j--) {\n                ThisElement[j] = ThisElement[j-1];\n                if ( ThisElement[j] == '+' || ThisElement[j] == '-' ) {\n                   ThisElement[j-1] = Rhsflag;\n                   break;\n                }\n             }\n          }\n       b[i] = atof(ThisElement);\n       col += Rhswidth;\n    }\n\n/*  Skip any interleaved Guess/eXact vectors */\n\n    for (i=0;i<stride;i++) {\n       if ( col >= ( maxcol<linel?maxcol:linel ) ) {\n           fgets(line, BUFSIZ, in_file);\n           linel= strchr(line,'\\n')-line;\n           col = 0;\n       }\n       col += Rhswidth;\n    }\n\n  }\n  free(ThisElement);\n\n\n    fclose(in_file);\n    return Nrhs;\n}\n\nint readHB_newaux_double(const char* filename, const char AuxType, double** b)\n{\n        int Nrhs,M,N,nonzeros;\n        char *Type;\n\n  readHB_info(filename, &M, &N, &nonzeros, &Type, &Nrhs);\n        if ( Nrhs <= 0 ) {\n          fprintf(stderr,\"Warn: Requested read of aux vector(s) when none are present.\\n\");\n          return 0;\n        } else {\n          if ( Type[0] == 'C' ) {\n            fprintf(stderr, \"Warning: Reading complex aux vector(s) from HB file %s.\",filename);\n            fprintf(stderr, \"         Real and imaginary parts will be interlaced in b[].\");\n            *b = (double *)malloc(M*Nrhs*sizeof(double)*2);\n            if ( *b == NULL ) IOHBTerminate(\"Insufficient memory for rhs.\\n\");\n            return readHB_aux_double(filename, AuxType, *b);\n          } else {\n            *b = (double *)malloc(M*Nrhs*sizeof(double));\n            if ( *b == NULL ) IOHBTerminate(\"Insufficient memory for rhs.\\n\");\n      return readHB_aux_double(filename, AuxType, *b);\n          }\n        }\n}\n\nint writeHB_mat_double(const char* filename, int M, int N,\n                        int nz, const int colptr[], const int rowind[],\n                        const double val[], int Nrhs, const double rhs[],\n                        const double guess[], const double exact[],\n                        const char* Title, const char* Key, const char* Type,\n                        char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                        const char* Rhstype)\n{\n/****************************************************************************/\n/*  The writeHB function opens the named file and writes the specified      */\n/*  matrix and optional right-hand-side(s) to that file in Harwell-Boeing   */\n/*  format.                                                                 */\n/*                                                                          */\n/*  For a description of the Harwell Boeing standard, see:                  */\n/*            Duff, et al.,  ACM TOMS Vol.15, No.1, March 1989              */\n/*                                                                          */\n/****************************************************************************/\n    FILE *out_file;\n    int i,j,entry,offset,acount,linemod;\n    int totcrd, ptrcrd, indcrd, valcrd, rhscrd;\n    int nvalentries, nrhsentries;\n    int Ptrperline, Ptrwidth, Indperline, Indwidth;\n    int Rhsperline, Rhswidth, Rhsprec;\n    int Rhsflag;\n    int Valperline, Valwidth, Valprec;\n    int Valflag;           /* Indicates 'E','D', or 'F' float format */\n    char pformat[16],iformat[16],vformat[19],rformat[19];\n\n    if ( Type[0] == 'C' ) {\n         nvalentries = 2*nz;\n         nrhsentries = 2*M;\n    } else {\n         nvalentries = nz;\n         nrhsentries = M;\n    }\n\n    if ( filename != NULL ) {\n       if ( (out_file = fopen( filename, \"w\")) == NULL ) {\n         fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n         return 0;\n       }\n    } else out_file = stdout;\n\n    if ( Ptrfmt == NULL ) Ptrfmt = \"(8I10)\";\n    ParseIfmt(Ptrfmt,&Ptrperline,&Ptrwidth);\n    sprintf(pformat,\"%%%dd\",Ptrwidth);\n    ptrcrd = (N+1)/Ptrperline;\n    if ( (N+1)%Ptrperline != 0) ptrcrd++;\n\n    if ( Indfmt == NULL ) Indfmt =  Ptrfmt;\n    ParseIfmt(Indfmt,&Indperline,&Indwidth);\n    sprintf(iformat,\"%%%dd\",Indwidth);\n    indcrd = nz/Indperline;\n    if ( nz%Indperline != 0) indcrd++;\n\n    if ( Type[0] != 'P' ) {          /* Skip if pattern only  */\n      if ( Valfmt == NULL ) Valfmt = \"(4E20.13)\";\n      ParseRfmt(Valfmt,&Valperline,&Valwidth,&Valprec,&Valflag);\n      if (Valflag == 'D') *strchr(Valfmt,'D') = 'E';\n      if (Valflag == 'F')\n         sprintf(vformat,\"%% %d.%df\",Valwidth,Valprec);\n      else\n         sprintf(vformat,\"%% %d.%dE\",Valwidth,Valprec);\n      valcrd = nvalentries/Valperline;\n      if ( nvalentries%Valperline != 0) valcrd++;\n    } else valcrd = 0;\n\n    if ( Nrhs > 0 ) {\n       if ( Rhsfmt == NULL ) Rhsfmt = Valfmt;\n       ParseRfmt(Rhsfmt,&Rhsperline,&Rhswidth,&Rhsprec, &Rhsflag);\n       if (Rhsflag == 'F')\n          sprintf(rformat,\"%% %d.%df\",Rhswidth,Rhsprec);\n       else\n          sprintf(rformat,\"%% %d.%dE\",Rhswidth,Rhsprec);\n       if (Rhsflag == 'D') *strchr(Rhsfmt,'D') = 'E';\n       rhscrd = nrhsentries/Rhsperline;\n       if ( nrhsentries%Rhsperline != 0) rhscrd++;\n       if ( Rhstype[1] == 'G' ) rhscrd+=rhscrd;\n       if ( Rhstype[2] == 'X' ) rhscrd+=rhscrd;\n       rhscrd*=Nrhs;\n    } else rhscrd = 0;\n\n    totcrd = 4+ptrcrd+indcrd+valcrd+rhscrd;\n\n\n/*  Print header information:  */\n\n    fprintf(out_file,\"%-72s%-8s\\n%14d%14d%14d%14d%14d\\n\",Title, Key, totcrd,\n            ptrcrd, indcrd, valcrd, rhscrd);\n    fprintf(out_file,\"%3s%11s%14d%14d%14d\\n\",Type,\"          \", M, N, nz);\n    fprintf(out_file,\"%-16s%-16s%-20s\", Ptrfmt, Indfmt, Valfmt);\n    if ( Nrhs != 0 ) {\n/*     Print Rhsfmt on fourth line and                                    */\n/*           optional fifth header line for auxillary vector information: */\n       fprintf(out_file,\"%-20s\\n%-14s%d\\n\",Rhsfmt,Rhstype,Nrhs);\n    } else fprintf(out_file,\"\\n\");\n\n    offset = 1-_SP_base;  /* if base 0 storage is declared (via macro definition), */\n                          /* then storage entries are offset by 1                  */\n\n/*  Print column pointers:   */\n    for (i=0;i<N+1;i++)\n    {\n       entry = colptr[i]+offset;\n       fprintf(out_file,pformat,entry);\n       if ( (i+1)%Ptrperline == 0 ) fprintf(out_file,\"\\n\");\n    }\n\n   if ( (N+1) % Ptrperline != 0 ) fprintf(out_file,\"\\n\");\n\n/*  Print row indices:       */\n    for (i=0;i<nz;i++)\n    {\n       entry = rowind[i]+offset;\n       fprintf(out_file,iformat,entry);\n       if ( (i+1)%Indperline == 0 ) fprintf(out_file,\"\\n\");\n    }\n\n   if ( nz % Indperline != 0 ) fprintf(out_file,\"\\n\");\n\n/*  Print values:            */\n\n    if ( Type[0] != 'P' ) {          /* Skip if pattern only  */\n\n    for (i=0;i<nvalentries;i++)\n    {\n       fprintf(out_file,vformat,val[i]);\n       if ( (i+1)%Valperline == 0 ) fprintf(out_file,\"\\n\");\n    }\n\n    if ( nvalentries % Valperline != 0 ) fprintf(out_file,\"\\n\");\n\n/*  If available,  print right hand sides,\n           guess vectors and exact solution vectors:  */\n    acount = 1;\n    linemod = 0;\n    if ( Nrhs > 0 ) {\n       for (i=0;i<Nrhs;i++)\n       {\n          for ( j=0;j<nrhsentries;j++ ) {\n            fprintf(out_file,rformat,rhs[j]);\n            if ( acount++%Rhsperline == linemod ) fprintf(out_file,\"\\n\");\n          }\n          if ( acount%Rhsperline != linemod ) {\n            fprintf(out_file,\"\\n\");\n            linemod = (acount-1)%Rhsperline;\n          }\n          rhs += nrhsentries;\n          if ( Rhstype[1] == 'G' ) {\n            for ( j=0;j<nrhsentries;j++ ) {\n              fprintf(out_file,rformat,guess[j]);\n              if ( acount++%Rhsperline == linemod ) fprintf(out_file,\"\\n\");\n            }\n            if ( acount%Rhsperline != linemod ) {\n              fprintf(out_file,\"\\n\");\n              linemod = (acount-1)%Rhsperline;\n            }\n            guess += nrhsentries;\n          }\n          if ( Rhstype[2] == 'X' ) {\n            for ( j=0;j<nrhsentries;j++ ) {\n              fprintf(out_file,rformat,exact[j]);\n              if ( acount++%Rhsperline == linemod ) fprintf(out_file,\"\\n\");\n            }\n            if ( acount%Rhsperline != linemod ) {\n              fprintf(out_file,\"\\n\");\n              linemod = (acount-1)%Rhsperline;\n            }\n            exact += nrhsentries;\n          }\n       }\n    }\n\n    }\n\n    if ( fclose(out_file) != 0){\n      fprintf(stderr,\"Error closing file in writeHB_mat_double().\\n\");\n      return 0;\n    } else return 1;\n\n}\n\nint readHB_mat_char(const char* filename, int colptr[], int rowind[],\n                                           char val[], char* Valfmt)\n{\n/****************************************************************************/\n/*  This function opens and reads the specified file, interpreting its      */\n/*  contents as a sparse matrix stored in the Harwell/Boeing standard       */\n/*  format and creating compressed column storage scheme vectors to hold    */\n/*  the index and nonzero value information.                                */\n/*                                                                          */\n/*    ----------                                                            */\n/*    **CAVEAT**                                                            */\n/*    ----------                                                            */\n/*  Parsing real formats from Fortran is tricky, and this file reader       */\n/*  does not claim to be foolproof.   It has been tested for cases when     */\n/*  the real values are printed consistently and evenly spaced on each      */\n/*  line, with Fixed (F), and Exponential (E or D) formats.                 */\n/*                                                                          */\n/*  **  If the input file does not adhere to the H/B format, the  **        */\n/*  **             results will be unpredictable.                 **        */\n/*                                                                          */\n/****************************************************************************/\n    FILE *in_file;\n    int i,j,ind,col,offset,count,last;\n    int Nrow,Ncol,Nnzero,Nentries,Nrhs,Nrhsix;\n    int Ptrcrd, Indcrd, Valcrd, Rhscrd;\n    int Ptrperline, Ptrwidth, Indperline, Indwidth;\n    int Valperline, Valwidth, Valprec;\n    int Valflag;           /* Indicates 'E','D', or 'F' float format */\n    char* ThisElement;\n    char line[BUFSIZ];\n    char Title[73], Key[9], Type[4], Rhstype[4];\n    char Ptrfmt[17], Indfmt[17], Rhsfmt[21];\n\n    if ( (in_file = fopen( filename, \"r\")) == NULL ) {\n       fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n       return 0;\n    }\n\n    readHB_header(in_file, Title, Key, Type, &Nrow, &Ncol, &Nnzero, \n                  &Nrhs, &Nrhsix,\n                  Ptrfmt, Indfmt, Valfmt, Rhsfmt,\n                  &Ptrcrd, &Indcrd, &Valcrd, &Rhscrd, Rhstype);\n\n/*  Parse the array input formats from Line 3 of HB file  */\n    ParseIfmt(Ptrfmt,&Ptrperline,&Ptrwidth);\n    ParseIfmt(Indfmt,&Indperline,&Indwidth);\n    if ( Type[0] != 'P' ) {          /* Skip if pattern only  */\n       ParseRfmt(Valfmt,&Valperline,&Valwidth,&Valprec,&Valflag);\n       if (Valflag == 'D') {\n          *strchr(Valfmt,'D') = 'E';\n       }\n    }\n\n/*  Read column pointer array:   */\n\n    offset = 1-_SP_base;  /* if base 0 storage is declared (via macro definition), */\n                          /* then storage entries are offset by 1                  */\n\n    ThisElement = (char *) malloc(Ptrwidth+1);\n    if ( ThisElement == NULL ) IOHBTerminate(\"Insufficient memory for ThisElement.\");\n    *(ThisElement+Ptrwidth) = (char) NULL;\n    count=0;\n    for (i=0;i<Ptrcrd;i++)\n    {\n       fgets(line, BUFSIZ, in_file);\n       if ( sscanf(line,\"%*s\") < 0 )\n         IOHBTerminate(\"iohb.c: Null (or blank) line in pointer data region of HB file.\\n\");\n       col =  0;\n       for (ind = 0;ind<Ptrperline;ind++)\n       {\n          if (count > Ncol) break;\n          strncpy(ThisElement,line+col,Ptrwidth);\n          /*ThisElement = substr(line,col,Ptrwidth);*/\n          colptr[count] = atoi(ThisElement)-offset;\n          count++; col += Ptrwidth;\n       }\n    }\n    free(ThisElement);\n\n/*  Read row index array:  */\n\n    ThisElement = (char *) malloc(Indwidth+1);\n    if ( ThisElement == NULL ) IOHBTerminate(\"Insufficient memory for ThisElement.\");\n    *(ThisElement+Indwidth) = (char) NULL;\n    count = 0;\n    for (i=0;i<Indcrd;i++)\n    {\n       fgets(line, BUFSIZ, in_file);\n       if ( sscanf(line,\"%*s\") < 0 )\n         IOHBTerminate(\"iohb.c: Null (or blank) line in index data region of HB file.\\n\");\n       col =  0;\n       for (ind = 0;ind<Indperline;ind++)\n       {\n          if (count == Nnzero) break;\n          strncpy(ThisElement,line+col,Indwidth);\n          /*ThisElement = substr(line,col,Indwidth);*/\n          rowind[count] = atoi(ThisElement)-offset;\n          count++; col += Indwidth;\n       }\n    }\n    free(ThisElement);\n\n/*  Read array of values:  AS CHARACTERS*/\n\n    if ( Type[0] != 'P' ) {          /* Skip if pattern only  */\n\n       if ( Type[0] == 'C' ) Nentries = 2*Nnzero;\n           else Nentries = Nnzero;\n\n    ThisElement = (char *) malloc(Valwidth+1);\n    if ( ThisElement == NULL ) IOHBTerminate(\"Insufficient memory for ThisElement.\");\n    *(ThisElement+Valwidth) = (char) NULL;\n    count = 0;\n    for (i=0;i<Valcrd;i++)\n    {\n       fgets(line, BUFSIZ, in_file);\n       if ( sscanf(line,\"%*s\") < 0 )\n         IOHBTerminate(\"iohb.c: Null (or blank) line in value data region of HB file.\\n\");\n       if (Valflag == 'D') {\n          while( strchr(line,'D') ) *strchr(line,'D') = 'E';\n       }\n       col =  0;\n       for (ind = 0;ind<Valperline;ind++)\n       {\n          if (count == Nentries) break;\n          ThisElement = &val[count*Valwidth];\n          strncpy(ThisElement,line+col,Valwidth);\n          /*strncpy(ThisElement,substr(line,col,Valwidth),Valwidth);*/\n          if ( Valflag != 'F' && strchr(ThisElement,'E') == NULL ) {\n             /* insert a char prefix for exp */\n             last = strlen(ThisElement);\n             for (j=last+1;j>=0;j--) {\n                ThisElement[j] = ThisElement[j-1];\n                if ( ThisElement[j] == '+' || ThisElement[j] == '-' ) {\n                   ThisElement[j-1] = Valflag;\n                   break;\n                }\n             }\n          }\n          count++; col += Valwidth;\n       }\n    }\n    }\n\n    return 1;\n}\n\nint readHB_newmat_char(const char* filename, int* M, int* N, int* nonzeros, int** colptr,\n                          int** rowind, char** val, char** Valfmt)\n{\n    FILE *in_file;\n    int Nrhs,Nrhsix;\n    int Ptrcrd, Indcrd, Valcrd, Rhscrd;\n    int Valperline, Valwidth, Valprec;\n    int Valflag;           /* Indicates 'E','D', or 'F' float format */\n    char Title[73], Key[9], Type[4], Rhstype[4];\n    char Ptrfmt[17], Indfmt[17], Rhsfmt[21];\n\n    if ((in_file = fopen( filename, \"r\")) == NULL) {\n      fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n      return 0;\n     }\n\n    *Valfmt = (char *)malloc(21*sizeof(char));\n    if ( *Valfmt == NULL ) IOHBTerminate(\"Insufficient memory for Valfmt.\");\n    readHB_header(in_file, Title, Key, Type, M, N, nonzeros, \n                  &Nrhs, &Nrhsix,\n                  Ptrfmt, Indfmt, (*Valfmt), Rhsfmt,\n                  &Ptrcrd, &Indcrd, &Valcrd, &Rhscrd, Rhstype);\n    fclose(in_file);\n    ParseRfmt(*Valfmt,&Valperline,&Valwidth,&Valprec,&Valflag);\n\n        *colptr = (int *)malloc((*N+1)*sizeof(int));\n        if ( *colptr == NULL ) IOHBTerminate(\"Insufficient memory for colptr.\\n\");\n        *rowind = (int *)malloc(*nonzeros*sizeof(int));\n        if ( *rowind == NULL ) IOHBTerminate(\"Insufficient memory for rowind.\\n\");\n        if ( Type[0] == 'C' ) {\n/*\n   fprintf(stderr, \"Warning: Reading complex data from HB file %s.\\n\",filename);\n   fprintf(stderr, \"         Real and imaginary parts will be interlaced in val[].\\n\");\n*/\n           /* Malloc enough space for real AND imaginary parts of val[] */\n           *val = (char *)malloc(*nonzeros*Valwidth*sizeof(char)*2);\n           if ( *val == NULL ) IOHBTerminate(\"Insufficient memory for val.\\n\");\n        } else {\n           if ( Type[0] != 'P' ) {\n             /* Malloc enough space for real array val[] */\n             *val = (char *)malloc(*nonzeros*Valwidth*sizeof(char));\n             if ( *val == NULL ) IOHBTerminate(\"Insufficient memory for val.\\n\");\n           }\n        }  /* No val[] space needed if pattern only */\n  return readHB_mat_char(filename, *colptr, *rowind, *val, *Valfmt);\n\n}\n\nint readHB_aux_char(const char* filename, const char AuxType, char b[])\n{\n/****************************************************************************/\n/*  This function opens and reads the specified file, placing auxilary      */\n/*  vector(s) of the given type (if available) in b :                       */\n/*  Return value is the number of vectors successfully read.                */\n/*                                                                          */\n/*                AuxType = 'F'   full right-hand-side vector(s)            */\n/*                AuxType = 'G'   initial Guess vector(s)                   */\n/*                AuxType = 'X'   eXact solution vector(s)                  */\n/*                                                                          */\n/*    ----------                                                            */\n/*    **CAVEAT**                                                            */\n/*    ----------                                                            */\n/*  Parsing real formats from Fortran is tricky, and this file reader       */\n/*  does not claim to be foolproof.   It has been tested for cases when     */\n/*  the real values are printed consistently and evenly spaced on each      */\n/*  line, with Fixed (F), and Exponential (E or D) formats.                 */\n/*                                                                          */\n/*  **  If the input file does not adhere to the H/B format, the  **        */\n/*  **             results will be unpredictable.                 **        */\n/*                                                                          */\n/****************************************************************************/\n    FILE *in_file;\n    int i,j,n,maxcol,start,stride,col,last,linel,nvecs,rhsi;\n    int Nrow, Ncol, Nnzero, Nentries,Nrhs,Nrhsix;\n    int Ptrcrd, Indcrd, Valcrd, Rhscrd;\n    int Rhsperline, Rhswidth, Rhsprec;\n    int Rhsflag;\n    char Title[73], Key[9], Type[4], Rhstype[4];\n    char Ptrfmt[17], Indfmt[17], Valfmt[21], Rhsfmt[21];\n    char line[BUFSIZ];\n    char *ThisElement;\n\n    if ((in_file = fopen( filename, \"r\")) == NULL) {\n      fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n      return 0;\n     }\n\n    readHB_header(in_file, Title, Key, Type, &Nrow, &Ncol, &Nnzero, \n                  &Nrhs, &Nrhsix,\n                  Ptrfmt, Indfmt, Valfmt, Rhsfmt,\n                  &Ptrcrd, &Indcrd, &Valcrd, &Rhscrd, Rhstype);\n\n    if (Nrhs <= 0)\n    {\n      fprintf(stderr, \"Warn: Attempt to read auxillary vector(s) when none are present.\\n\");\n      return 0;\n    }\n    if (Rhstype[0] != 'F' )\n    {\n      fprintf(stderr,\"Warn: Attempt to read auxillary vector(s) which are not stored in Full form.\\n\");\n      fprintf(stderr,\"       Rhs must be specified as full. \\n\");\n      return 0;\n    }\n\n/* If reading complex data, allow for interleaved real and imaginary values. */\n    if ( Type[0] == 'C' ) {\n       Nentries = 2*Nrow;\n     } else {\n       Nentries = Nrow;\n    }\n\n    nvecs = 1;\n\n    if ( Rhstype[1] == 'G' ) nvecs++;\n    if ( Rhstype[2] == 'X' ) nvecs++;\n\n    if ( AuxType == 'G' && Rhstype[1] != 'G' ) {\n      fprintf(stderr, \"Warn: Attempt to read auxillary Guess vector(s) when none are present.\\n\");\n      return 0;\n    }\n    if ( AuxType == 'X' && Rhstype[2] != 'X' ) {\n      fprintf(stderr, \"Warn: Attempt to read auxillary eXact solution vector(s) when none are present.\\n\");\n      return 0;\n    }\n\n    ParseRfmt(Rhsfmt, &Rhsperline, &Rhswidth, &Rhsprec,&Rhsflag);\n    maxcol = Rhsperline*Rhswidth;\n\n/*  Lines to skip before starting to read RHS values... */\n    n = Ptrcrd + Indcrd + Valcrd;\n\n    for (i = 0; i < n; i++)\n      fgets(line, BUFSIZ, in_file);\n\n/*  start  - number of initial aux vector entries to skip   */\n/*           to reach first  vector requested               */\n/*  stride - number of aux vector entries to skip between   */\n/*           requested vectors                              */\n    if ( AuxType == 'F' ) start = 0;\n    else if ( AuxType == 'G' ) start = Nentries;\n    else start = (nvecs-1)*Nentries;\n    stride = (nvecs-1)*Nentries;\n\n    fgets(line, BUFSIZ, in_file);\n    linel= strchr(line,'\\n')-line;\n    if ( sscanf(line,\"%*s\") < 0 )\n       IOHBTerminate(\"iohb.c: Null (or blank) line in auxillary vector data region of HB file.\\n\");\n    col = 0;\n/*  Skip to initial offset */\n\n    for (i=0;i<start;i++) {\n       col += Rhswidth;\n       if ( col >= ( maxcol<linel?maxcol:linel ) ) {\n           fgets(line, BUFSIZ, in_file);\n           linel= strchr(line,'\\n')-line;\n       if ( sscanf(line,\"%*s\") < 0 )\n       IOHBTerminate(\"iohb.c: Null (or blank) line in auxillary vector data region of HB file.\\n\");\n           col = 0;\n       }\n    }\n\n    if (Rhsflag == 'D')  {\n      while( strchr(line,'D') ) *strchr(line,'D') = 'E';\n    }\n/*  Read a vector of desired type, then skip to next */\n/*  repeating to fill Nrhs vectors                   */\n\n  for (rhsi=0;rhsi<Nrhs;rhsi++) {\n\n    for (i=0;i<Nentries;i++) {\n       if ( col >= ( maxcol<linel?maxcol:linel ) ) {\n           fgets(line, BUFSIZ, in_file);\n           linel= strchr(line,'\\n')-line;\n       if ( sscanf(line,\"%*s\") < 0 )\n       IOHBTerminate(\"iohb.c: Null (or blank) line in auxillary vector data region of HB file.\\n\");\n           if (Rhsflag == 'D')  {\n              while( strchr(line,'D') ) *strchr(line,'D') = 'E';\n           }\n           col = 0;\n       }\n       ThisElement = &b[i*Rhswidth];\n       strncpy(ThisElement,line+col,Rhswidth);\n          if ( Rhsflag != 'F' && strchr(ThisElement,'E') == NULL ) {\n             /* insert a char prefix for exp */\n             last = strlen(ThisElement);\n             for (j=last+1;j>=0;j--) {\n                ThisElement[j] = ThisElement[j-1];\n                if ( ThisElement[j] == '+' || ThisElement[j] == '-' ) {\n                   ThisElement[j-1] = Rhsflag;\n                   break;\n                }\n             }\n          }\n       col += Rhswidth;\n    }\n    b+=Nentries*Rhswidth;\n\n/*  Skip any interleaved Guess/eXact vectors */\n\n    for (i=0;i<stride;i++) {\n       col += Rhswidth;\n       if ( col >= ( maxcol<linel?maxcol:linel ) ) {\n           fgets(line, BUFSIZ, in_file);\n           linel= strchr(line,'\\n')-line;\n       if ( sscanf(line,\"%*s\") < 0 )\n       IOHBTerminate(\"iohb.c: Null (or blank) line in auxillary vector data region of HB file.\\n\");\n           col = 0;\n       }\n    }\n\n  }\n\n\n    fclose(in_file);\n    return Nrhs;\n}\n\nint readHB_newaux_char(const char* filename, const char AuxType, char** b, char** Rhsfmt)\n{\n    FILE *in_file;\n    int Ptrcrd, Indcrd, Valcrd, Rhscrd;\n    int Nrow,Ncol,Nnzero,Nrhs,Nrhsix;\n    int Rhsperline, Rhswidth, Rhsprec;\n    int Rhsflag;\n    char Title[73], Key[9], Type[4], Rhstype[4];\n    char Ptrfmt[17], Indfmt[17], Valfmt[21];\n\n    if ((in_file = fopen( filename, \"r\")) == NULL) {\n      fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n      return 0;\n     }\n\n    *Rhsfmt = (char *)malloc(21*sizeof(char));\n    if ( *Rhsfmt == NULL ) IOHBTerminate(\"Insufficient memory for Rhsfmt.\");\n    readHB_header(in_file, Title, Key, Type, &Nrow, &Ncol, &Nnzero, \n                  &Nrhs, &Nrhsix,\n                  Ptrfmt, Indfmt, Valfmt, (*Rhsfmt),\n                  &Ptrcrd, &Indcrd, &Valcrd, &Rhscrd, Rhstype);\n     fclose(in_file);\n        if ( Nrhs == 0 ) {\n          fprintf(stderr,\"Warn: Requested read of aux vector(s) when none are present.\\n\");\n          return 0;\n        } else {\n          ParseRfmt(*Rhsfmt,&Rhsperline,&Rhswidth,&Rhsprec,&Rhsflag);\n          if ( Type[0] == 'C' ) {\n            fprintf(stderr, \"Warning: Reading complex aux vector(s) from HB file %s.\",filename);\n            fprintf(stderr, \"         Real and imaginary parts will be interlaced in b[].\");\n            *b = (char *)malloc(Nrow*Nrhs*Rhswidth*sizeof(char)*2);\n            if ( *b == NULL ) IOHBTerminate(\"Insufficient memory for rhs.\\n\");\n      return readHB_aux_char(filename, AuxType, *b);\n          } else {\n            *b = (char *)malloc(Nrow*Nrhs*Rhswidth*sizeof(char));\n            if ( *b == NULL ) IOHBTerminate(\"Insufficient memory for rhs.\\n\");\n      return readHB_aux_char(filename, AuxType, *b);\n          }\n        }\n}\n\nint writeHB_mat_char(const char* filename, int M, int N,\n                        int nz, const int colptr[], const int rowind[],\n                        const char val[], int Nrhs, const char rhs[],\n                        const char guess[], const char exact[],\n                        const char* Title, const char* Key, const char* Type,\n                        char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                        const char* Rhstype)\n{\n/****************************************************************************/\n/*  The writeHB function opens the named file and writes the specified      */\n/*  matrix and optional right-hand-side(s) to that file in Harwell-Boeing   */\n/*  format.                                                                 */\n/*                                                                          */\n/*  For a description of the Harwell Boeing standard, see:                  */\n/*            Duff, et al.,  ACM TOMS Vol.15, No.1, March 1989              */\n/*                                                                          */\n/****************************************************************************/\n    FILE *out_file;\n    int i,j,acount,linemod,entry,offset;\n    int totcrd, ptrcrd, indcrd, valcrd, rhscrd;\n    int nvalentries, nrhsentries;\n    int Ptrperline, Ptrwidth, Indperline, Indwidth;\n    int Rhsperline, Rhswidth, Rhsprec;\n    int Rhsflag;\n    int Valperline, Valwidth, Valprec;\n    int Valflag;           /* Indicates 'E','D', or 'F' float format */\n    char pformat[16],iformat[16],vformat[19],rformat[19];\n\n    if ( Type[0] == 'C' ) {\n         nvalentries = 2*nz;\n         nrhsentries = 2*M;\n    } else {\n         nvalentries = nz;\n         nrhsentries = M;\n    }\n\n    if ( filename != NULL ) {\n       if ( (out_file = fopen( filename, \"w\")) == NULL ) {\n         fprintf(stderr,\"Error: Cannot open file: %s\\n\",filename);\n         return 0;\n       }\n    } else out_file = stdout;\n\n    if ( Ptrfmt == NULL ) Ptrfmt = \"(8I10)\";\n    ParseIfmt(Ptrfmt,&Ptrperline,&Ptrwidth);\n    sprintf(pformat,\"%%%dd\",Ptrwidth);\n\n    if ( Indfmt == NULL ) Indfmt =  Ptrfmt;\n    ParseIfmt(Indfmt,&Indperline,&Indwidth);\n    sprintf(iformat,\"%%%dd\",Indwidth);\n\n    if ( Type[0] != 'P' ) {          /* Skip if pattern only  */\n      if ( Valfmt == NULL ) Valfmt = \"(4E20.13)\";\n      ParseRfmt(Valfmt,&Valperline,&Valwidth,&Valprec,&Valflag);\n      sprintf(vformat,\"%%%ds\",Valwidth);\n    }\n\n    ptrcrd = (N+1)/Ptrperline;\n    if ( (N+1)%Ptrperline != 0) ptrcrd++;\n\n    indcrd = nz/Indperline;\n    if ( nz%Indperline != 0) indcrd++;\n\n    valcrd = nvalentries/Valperline;\n    if ( nvalentries%Valperline != 0) valcrd++;\n\n    if ( Nrhs > 0 ) {\n       if ( Rhsfmt == NULL ) Rhsfmt = Valfmt;\n       ParseRfmt(Rhsfmt,&Rhsperline,&Rhswidth,&Rhsprec, &Rhsflag);\n       sprintf(rformat,\"%%%ds\",Rhswidth);\n       rhscrd = nrhsentries/Rhsperline;\n       if ( nrhsentries%Rhsperline != 0) rhscrd++;\n       if ( Rhstype[1] == 'G' ) rhscrd+=rhscrd;\n       if ( Rhstype[2] == 'X' ) rhscrd+=rhscrd;\n       rhscrd*=Nrhs;\n    } else rhscrd = 0;\n\n    totcrd = 4+ptrcrd+indcrd+valcrd+rhscrd;\n\n\n/*  Print header information:  */\n\n    fprintf(out_file,\"%-72s%-8s\\n%14d%14d%14d%14d%14d\\n\",Title, Key, totcrd,\n            ptrcrd, indcrd, valcrd, rhscrd);\n    fprintf(out_file,\"%3s%11s%14d%14d%14d\\n\",Type,\"          \", M, N, nz);\n    fprintf(out_file,\"%-16s%-16s%-20s\", Ptrfmt, Indfmt, Valfmt);\n    if ( Nrhs != 0 ) {\n/*     Print Rhsfmt on fourth line and                                    */\n/*           optional fifth header line for auxillary vector information: */\n       fprintf(out_file,\"%-20s\\n%-14s%d\\n\",Rhsfmt,Rhstype,Nrhs);\n    } else fprintf(out_file,\"\\n\");\n\n    offset = 1-_SP_base;  /* if base 0 storage is declared (via macro definition), */\n                          /* then storage entries are offset by 1                  */\n\n/*  Print column pointers:   */\n    for (i=0;i<N+1;i++)\n    {\n       entry = colptr[i]+offset;\n       fprintf(out_file,pformat,entry);\n       if ( (i+1)%Ptrperline == 0 ) fprintf(out_file,\"\\n\");\n    }\n\n   if ( (N+1) % Ptrperline != 0 ) fprintf(out_file,\"\\n\");\n\n/*  Print row indices:       */\n    for (i=0;i<nz;i++)\n    {\n       entry = rowind[i]+offset;\n       fprintf(out_file,iformat,entry);\n       if ( (i+1)%Indperline == 0 ) fprintf(out_file,\"\\n\");\n    }\n\n   if ( nz % Indperline != 0 ) fprintf(out_file,\"\\n\");\n\n/*  Print values:            */\n\n    if ( Type[0] != 'P' ) {          /* Skip if pattern only  */\n    for (i=0;i<nvalentries;i++)\n    {\n       fprintf(out_file,vformat,val+i*Valwidth);\n       if ( (i+1)%Valperline == 0 ) fprintf(out_file,\"\\n\");\n    }\n\n    if ( nvalentries % Valperline != 0 ) fprintf(out_file,\"\\n\");\n\n/*  Print right hand sides:  */\n    acount = 1;\n    linemod=0;\n    if ( Nrhs > 0 ) {\n      for (j=0;j<Nrhs;j++) {\n       for (i=0;i<nrhsentries;i++)\n       {\n          fprintf(out_file,rformat,rhs+i*Rhswidth);\n          if ( acount++%Rhsperline == linemod ) fprintf(out_file,\"\\n\");\n       }\n       if ( acount%Rhsperline != linemod ) {\n          fprintf(out_file,\"\\n\");\n          linemod = (acount-1)%Rhsperline;\n       }\n       if ( Rhstype[1] == 'G' ) {\n         for (i=0;i<nrhsentries;i++)\n         {\n           fprintf(out_file,rformat,guess+i*Rhswidth);\n           if ( acount++%Rhsperline == linemod ) fprintf(out_file,\"\\n\");\n         }\n         if ( acount%Rhsperline != linemod ) {\n            fprintf(out_file,\"\\n\");\n            linemod = (acount-1)%Rhsperline;\n         }\n       }\n       if ( Rhstype[2] == 'X' ) {\n         for (i=0;i<nrhsentries;i++)\n         {\n           fprintf(out_file,rformat,exact+i*Rhswidth);\n           if ( acount++%Rhsperline == linemod ) fprintf(out_file,\"\\n\");\n         }\n         if ( acount%Rhsperline != linemod ) {\n            fprintf(out_file,\"\\n\");\n            linemod = (acount-1)%Rhsperline;\n         }\n       }\n      }\n    }\n\n    }\n\n    if ( fclose(out_file) != 0){\n      fprintf(stderr,\"Error closing file in writeHB_mat_char().\\n\");\n      return 0;\n    } else return 1;\n\n}\n\nint ParseIfmt(char* fmt, int* perline, int* width)\n{\n/*************************************************/\n/*  Parse an *integer* format field to determine */\n/*  width and number of elements per line.       */\n/*************************************************/\n    char *tmp;\n    if (fmt == NULL ) {\n      *perline = 0; *width = 0; return 0;\n    }\n    upcase(fmt);\n    tmp = strchr(fmt,'(');\n    tmp = substr(fmt,tmp - fmt + 1, strchr(fmt,'I') - tmp - 1);\n    *perline = atoi(tmp);\n    tmp = strchr(fmt,'I');\n    tmp = substr(fmt,tmp - fmt + 1, strchr(fmt,')') - tmp - 1);\n    return *width = atoi(tmp);\n}\n\nint ParseRfmt(char* fmt, int* perline, int* width, int* prec, int* flag)\n{\n/*************************************************/\n/*  Parse a *real* format field to determine     */\n/*  width and number of elements per line.       */\n/*  Also sets flag indicating 'E' 'F' 'P' or 'D' */\n/*  format.                                      */\n/*************************************************/\n    char* tmp;\n    char* tmp2;\n    char* tmp3;\n    int len;\n\n    if (fmt == NULL ) {\n      *perline = 0;\n      *width = 0;\n      flag = NULL;\n      return 0;\n    }\n\n    upcase(fmt);\n    if (strchr(fmt,'(') != NULL)  fmt = strchr(fmt,'(');\n    if (strchr(fmt,')') != NULL)  {\n       tmp2 = strchr(fmt,')');\n       while ( strchr(tmp2+1,')') != NULL ) {\n          tmp2 = strchr(tmp2+1,')');\n       }\n       *(tmp2+1) = (int) NULL;\n    }\n    if (strchr(fmt,'P') != NULL)  /* Remove any scaling factor, which */\n    {                             /* affects output only, not input */\n      if (strchr(fmt,'(') != NULL) {\n        tmp = strchr(fmt,'P');\n        if ( *(++tmp) == ',' ) tmp++;\n        tmp3 = strchr(fmt,'(')+1;\n        len = tmp-tmp3;\n        tmp2 = tmp3;\n        while ( *(tmp2+len) != (int) NULL ) {\n           *tmp2=*(tmp2+len);\n           tmp2++;\n        }\n        *(strchr(fmt,')')+1) = (int) NULL;\n      }\n    }\n    if (strchr(fmt,'E') != NULL) {\n       *flag = 'E';\n    } else if (strchr(fmt,'D') != NULL) {\n       *flag = 'D';\n    } else if (strchr(fmt,'F') != NULL) {\n       *flag = 'F';\n    } else {\n      fprintf(stderr,\"Real format %s in H/B file not supported.\\n\",fmt);\n      return 0;\n    }\n    tmp = strchr(fmt,'(');\n    tmp = substr(fmt,tmp - fmt + 1, strchr(fmt,*flag) - tmp - 1);\n    *perline = atoi(tmp);\n    tmp = strchr(fmt,*flag);\n    if ( strchr(fmt,'.') ) {\n      *prec = atoi( substr( fmt, strchr(fmt,'.') - fmt + 1, strchr(fmt,')') - strchr(fmt,'.')-1) );\n      tmp = substr(fmt,tmp - fmt + 1, strchr(fmt,'.') - tmp - 1);\n    } else {\n      tmp = substr(fmt,tmp - fmt + 1, strchr(fmt,')') - tmp - 1);\n    }\n    return *width = atoi(tmp);\n}\n\nchar* substr(const char* S, const int pos, const int len)\n{\n    int i;\n    char *SubS;\n    if ( pos+len <= strlen(S)) {\n    SubS = (char *)malloc(len+1);\n    if ( SubS == NULL ) IOHBTerminate(\"Insufficient memory for SubS.\");\n    for (i=0;i<len;i++) SubS[i] = S[pos+i];\n    SubS[len] = (char) NULL;\n    } else {\n      SubS = NULL;\n    }\n    return SubS;\n}\n\n#include<ctype.h>\nvoid upcase(char* S)\n{\n/*  Convert S to uppercase     */\n    int i,len;\n    len = strlen(S);\n    for (i=0;i< len;i++)\n       S[i] = toupper(S[i]);\n}\n\nvoid IOHBTerminate(char* message)\n{\n   fprintf(stderr,message);\n   exit(1);\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/hbio.h",
    "content": "#ifndef IOHB_H\n#define IOHB_H\n\n#include<stdio.h>\n#include<stdlib.h>\n#include<sys/types.h>\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nint readHB_info(const char* filename, int* M, int* N, int* nz, char** Type,\n                                                      int* Nrhs);\n\nint readHB_header(FILE* in_file, char* Title, char* Key, char* Type,\n                    int* Nrow, int* Ncol, int* Nnzero, int* Nrhs, int* Nrhsix,\n                    char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                    int* Ptrcrd, int* Indcrd, int* Valcrd, int* Rhscrd,\n                    char *Rhstype);\n\nint readHB_mat_double(const char* filename, int colptr[], int rowind[],\n                                                                 double val[]);\n\nint readHB_newmat_double(const char* filename, int* M, int* N, int* nonzeros,\n                         int** colptr, int** rowind, double** val);\n\nint readHB_aux_double(const char* filename, const char AuxType, double b[]);\n\nint readHB_newaux_double(const char* filename, const char AuxType, double** b);\n\nint writeHB_mat_double(const char* filename, int M, int N,\n                        int nz, const int colptr[], const int rowind[],\n                        const double val[], int Nrhs, const double rhs[],\n                        const double guess[], const double exact[],\n                        const char* Title, const char* Key, const char* Type,\n                        char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                        const char* Rhstype);\n\nint readHB_mat_char(const char* filename, int colptr[], int rowind[],\n                                           char val[], char* Valfmt);\n\nint readHB_newmat_char(const char* filename, int* M, int* N, int* nonzeros, int** colptr,\n                          int** rowind, char** val, char** Valfmt);\n\nint readHB_aux_char(const char* filename, const char AuxType, char b[]);\n\nint readHB_newaux_char(const char* filename, const char AuxType, char** b, char** Rhsfmt);\n\nint writeHB_mat_char(const char* filename, int M, int N,\n                        int nz, const int colptr[], const int rowind[],\n                        const char val[], int Nrhs, const char rhs[],\n                        const char guess[], const char exact[],\n                        const char* Title, const char* Key, const char* Type,\n                        char* Ptrfmt, char* Indfmt, char* Valfmt, char* Rhsfmt,\n                        const char* Rhstype);\n\nint ParseIfmt(char* fmt, int* perline, int* width);\n\nint ParseRfmt(char* fmt, int* perline, int* width, int* prec, int* flag);\n\nvoid IOHBTerminate(char* message);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol.c",
    "content": "\n/* ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   LUSOL routines from the Stanford Optimization Laboratory\n   The parts included are:\n    lusol1      Factor a given matrix A from scratch (lu1fac).\n    lusol2      Heap-management routines for lu1fac.\n    lusol6      Solve with the current LU factors.\n    lusol7      Utilities for all update routines.\n    lusol8      Replace a column (Bartels-Golub update).\n   ------------------------------------------------------------------\n   26 Apr 2002: TCP implemented using heap data structure.\n   01 May 2002: lu1DCP implemented.\n   07 May 2002: lu1mxc must put 0.0 at top of empty columns.\n   09 May 2002: lu1mCP implements Markowitz with cols searched\n                in heap order.\n                Often faster (searching 20 or 40 cols) but more dense.\n   11 Jun 2002: TRP implemented.\n                lu1mRP implements Markowitz with Threshold Rook\n                Pivoting.\n                lu1mxc maintains max col elements  (was lu1max.)\n                lu1mxr maintains max row elements.\n   12 Jun 2002: lu1mCP seems too slow on big problems (e.g. memplus).\n                Disabled it for the moment.  (Use lu1mar + TCP.)\n   14 Dec 2002: TSP implemented.\n                lu1mSP implements Markowitz with TSP.\n   07 Mar 2003: character*1, character*2 changed to f90 form.\n                Comments changed from * in column to ! in column 1.\n                Comments kept within column 72 to avoid compiler\n                warning.\n   06 Mar 2004: Translation to C by Kjell Eikland with the addition\n                of data wrappers, parametric constants, various\n                helper routines, and dynamic memory reallocation.\n   26 May 2004: Added LUSOL_IP_UPDATELIMIT parameter and provided\n                for dynamic memory expansion based on possible\n                forward requirements.\n   08 Jul 2004: Revised logic in lu6chk based on new code from\n                Michael Saunders.\n   01 Dec 2005: Add support for CMEX interface (disable by undef MATLAB)\n                Also include various bug fixes (disable by undef YZHANG)\n                Yin Zhang <yzhang@cs.utexas.edu>\n   01 Jan 2006: Added storage of singular indeces, not only the last.\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */\n\n#include <stdlib.h>\n#include <stdio.h>\n#include <stdarg.h>\n#include <string.h>\n#include <float.h>\n#include <math.h>\n#include \"lusol.h\"\n#include \"myblas.h\"\n#ifdef MATLAB\n  #include \"mex.h\"\n#endif\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* LUSOL Object creation and destruction */\n\nvoid *clean_realloc(void *oldptr, int width, int newsize, int oldsize)\n{\n  newsize *= width;\n  oldsize *= width;\n  oldptr = LUSOL_REALLOC(oldptr, newsize);\n  if(newsize > oldsize)\n/*    MEMCLEAR(oldptr+oldsize, newsize-oldsize); */\n    memset((char *)oldptr+oldsize, '\\0', newsize-oldsize);\n  return(oldptr);\n}\n\nMYBOOL LUSOL_realloc_a(LUSOLrec *LUSOL, int newsize)\n{\n  int oldsize;\n\n  if(newsize < 0)\n    newsize = LUSOL->lena + MAX(abs(newsize), LUSOL_MINDELTA_a);\n\n  oldsize = LUSOL->lena;\n  LUSOL->lena = newsize;\n  if(newsize > 0)\n    newsize++;\n  if(oldsize > 0)\n    oldsize++;\n\n  LUSOL->a    = (REAL *) clean_realloc(LUSOL->a,    sizeof(*(LUSOL->a)),\n                                                    newsize, oldsize);\n  LUSOL->indc = (int *)  clean_realloc(LUSOL->indc, sizeof(*(LUSOL->indc)),\n                                                    newsize, oldsize);\n  LUSOL->indr = (int *)  clean_realloc(LUSOL->indr, sizeof(*(LUSOL->indr)),\n                                                    newsize, oldsize);\n  if((newsize == 0) ||\n     ((LUSOL->a != NULL) && (LUSOL->indc != NULL) && (LUSOL->indr != NULL)))\n    return( TRUE );\n  else\n    return( FALSE );\n}\n\nMYBOOL LUSOL_expand_a(LUSOLrec *LUSOL, int *delta_lena, int *right_shift)\n{\n#ifdef StaticMemAlloc\n  return( FALSE );\n#else\n  int LENA, NFREE, LFREE;\n\n  /* Add expansion factor to avoid having to resize too often/too much;\n     (exponential formula suggested by Michael A. Saunders) */\n  LENA = LUSOL->lena;\n  *delta_lena = DELTA_SIZE(*delta_lena, LENA);\n\n  /* Expand it! */\n  if((*delta_lena <= 0) || !LUSOL_realloc_a(LUSOL, LENA+(*delta_lena)))\n    return( FALSE );\n\n  /* Make sure we return the actual memory increase of a */\n  *delta_lena = LUSOL->lena-LENA;\n\n  /* Shift the used memory area to the right */\n  LFREE = *right_shift;\n  NFREE = LFREE+*delta_lena;\n  LENA  -= LFREE-1;\n  MEMMOVE(LUSOL->a+NFREE,    LUSOL->a+LFREE,    LENA);\n  MEMMOVE(LUSOL->indr+NFREE, LUSOL->indr+LFREE, LENA);\n  MEMMOVE(LUSOL->indc+NFREE, LUSOL->indc+LFREE, LENA);\n\n  /* Also return the new starting position for the used memory area of a */\n  *right_shift  = NFREE;\n\n  LUSOL->expanded_a++;\n  return( TRUE );\n#endif\n}\n\nMYBOOL LUSOL_realloc_r(LUSOLrec *LUSOL, int newsize)\n{\n  int oldsize;\n\n  if(newsize < 0)\n    newsize = LUSOL->maxm + MAX(abs(newsize), LUSOL_MINDELTA_rc);\n\n  oldsize = LUSOL->maxm;\n  LUSOL->maxm = newsize;\n  if(newsize > 0)\n    newsize++;\n  if(oldsize > 0)\n    oldsize++;\n\n  LUSOL->lenr  = (int *) clean_realloc(LUSOL->lenr,  sizeof(*(LUSOL->lenr)),\n                                                     newsize, oldsize);\n  LUSOL->ip    = (int *) clean_realloc(LUSOL->ip,    sizeof(*(LUSOL->ip)),\n                                                     newsize, oldsize);\n  LUSOL->iqloc = (int *) clean_realloc(LUSOL->iqloc, sizeof(*(LUSOL->iqloc)),\n                                                     newsize, oldsize);\n  LUSOL->ipinv = (int *) clean_realloc(LUSOL->ipinv, sizeof(*(LUSOL->ipinv)),\n                                                     newsize, oldsize);\n  LUSOL->locr  = (int *) clean_realloc(LUSOL->locr,  sizeof(*(LUSOL->locr)),\n                                                     newsize, oldsize);\n\n  if((newsize == 0) ||\n     ((LUSOL->lenr != NULL) &&\n      (LUSOL->ip != NULL) && (LUSOL->iqloc != NULL) &&\n      (LUSOL->ipinv != NULL) && (LUSOL->locr != NULL))) {\n\n#ifndef ClassicHamaxR\n#ifdef AlwaysSeparateHamaxR\n    if(LUSOL->luparm[LUSOL_IP_PIVOTTYPE] == LUSOL_PIVMOD_TRP)\n#endif\n    {\n      LUSOL->amaxr = (REAL *) clean_realloc(LUSOL->amaxr, sizeof(*(LUSOL->amaxr)),\n                                                          newsize, oldsize);\n      if((newsize > 0) && (LUSOL->amaxr == NULL))\n        return( FALSE );\n    }\n#endif\n    return( TRUE );\n  }\n  else\n    return( FALSE );\n}\n\nMYBOOL LUSOL_realloc_c(LUSOLrec *LUSOL, int newsize)\n{\n  int oldsize;\n\n  if(newsize < 0)\n    newsize = LUSOL->maxn + MAX(abs(newsize), LUSOL_MINDELTA_rc);\n\n  oldsize = LUSOL->maxn;\n  LUSOL->maxn = newsize;\n  if(newsize > 0)\n    newsize++;\n  if(oldsize > 0)\n    oldsize++;\n\n  LUSOL->lenc  = (int *)  clean_realloc(LUSOL->lenc,  sizeof(*(LUSOL->lenc)),\n                                                      newsize, oldsize);\n  LUSOL->iq    = (int *)  clean_realloc(LUSOL->iq,    sizeof(*(LUSOL->iq)),\n                                                      newsize, oldsize);\n  LUSOL->iploc = (int *)  clean_realloc(LUSOL->iploc, sizeof(*(LUSOL->iploc)),\n                                                      newsize, oldsize);\n  LUSOL->iqinv = (int *)  clean_realloc(LUSOL->iqinv, sizeof(*(LUSOL->iqinv)),\n                                                      newsize, oldsize);\n  LUSOL->locc  = (int *)  clean_realloc(LUSOL->locc,  sizeof(*(LUSOL->locc)),\n                                                      newsize, oldsize);\n  LUSOL->w     = (REAL *) clean_realloc(LUSOL->w,     sizeof(*(LUSOL->w)),\n                                                      newsize, oldsize);\n#ifdef LUSOLSafeFastUpdate\n  LUSOL->vLU6L = (REAL *) clean_realloc(LUSOL->vLU6L, sizeof(*(LUSOL->vLU6L)),\n                                                      newsize, oldsize);\n#else\n  LUSOL->vLU6L = LUSOL->w;\n#endif\n\n  if((newsize == 0) ||\n     ((LUSOL->w != NULL) && (LUSOL->lenc != NULL) &&\n      (LUSOL->iq != NULL) && (LUSOL->iploc != NULL) &&\n      (LUSOL->iqinv != NULL) && (LUSOL->locc != NULL))) {\n\n#ifndef ClassicHamaxR\n    if(LUSOL->luparm[LUSOL_IP_PIVOTTYPE] == LUSOL_PIVMOD_TCP) {\n      LUSOL->Ha = (REAL *) clean_realloc(LUSOL->Ha,   sizeof(*(LUSOL->Ha)),\n                                                      newsize, oldsize);\n      LUSOL->Hj = (int *)  clean_realloc(LUSOL->Hj,   sizeof(*(LUSOL->Hj)),\n                                                      newsize, oldsize);\n      LUSOL->Hk = (int *)  clean_realloc(LUSOL->Hk,   sizeof(*(LUSOL->Hk)),\n                                                      newsize, oldsize);\n      if((newsize > 0) &&\n         ((LUSOL->Ha == NULL) || (LUSOL->Hj == NULL) || (LUSOL->Hk == NULL)))\n        return( FALSE );\n    }\n#endif\n#ifndef ClassicdiagU\n    if(LUSOL->luparm[LUSOL_IP_KEEPLU] == FALSE) {\n      LUSOL->diagU = (REAL *) clean_realloc(LUSOL->diagU, sizeof(*(LUSOL->diagU)),\n                                                          newsize, oldsize);\n      if((newsize > 0) && (LUSOL->diagU == NULL))\n        return( FALSE );\n    }\n#endif\n\n    return( TRUE );\n  }\n  else\n    return( FALSE );\n}\n\nLUSOLrec *LUSOL_create(FILE *outstream, int msgfil, int pivotmodel, int updatelimit)\n{\n  LUSOLrec *newLU;\n\n  newLU = (LUSOLrec *) LUSOL_CALLOC(1, sizeof(*newLU));\n  if(newLU == NULL)\n    return( newLU );\n\n  newLU->luparm[LUSOL_IP_SCALAR_NZA]       = LUSOL_MULT_nz_a;\n  newLU->outstream = outstream;\n  newLU->luparm[LUSOL_IP_PRINTUNIT]        = msgfil;\n  newLU->luparm[LUSOL_IP_PRINTLEVEL]       = LUSOL_MSG_SINGULARITY;\n\n  LUSOL_setpivotmodel(newLU, pivotmodel, LUSOL_PIVTOL_DEFAULT);\n\n  newLU->parmlu[LUSOL_RP_GAMMA]            = LUSOL_DEFAULT_GAMMA;\n\n  newLU->parmlu[LUSOL_RP_ZEROTOLERANCE]    = 3.0e-13;\n\n  newLU->parmlu[LUSOL_RP_SMALLDIAG_U]      = /*3.7e-11;*/\n  newLU->parmlu[LUSOL_RP_EPSDIAG_U]        = 3.7e-11;\n\n  newLU->parmlu[LUSOL_RP_COMPSPACE_U]      = 3.0e+0;\n\n  newLU->luparm[LUSOL_IP_MARKOWITZ_MAXCOL] = 5;\n  newLU->parmlu[LUSOL_RP_MARKOWITZ_CONLY]  = 0.3e+0;\n  newLU->parmlu[LUSOL_RP_MARKOWITZ_DENSE]  = 0.5e+0;\n\n  newLU->parmlu[LUSOL_RP_SMARTRATIO]       = LUSOL_DEFAULT_SMARTRATIO;\n#ifdef ForceRowBasedL0\n  newLU->luparm[LUSOL_IP_ACCELERATION]     = LUSOL_BASEORDER;\n#endif\n  newLU->luparm[LUSOL_IP_KEEPLU]           = TRUE;\n  newLU->luparm[LUSOL_IP_UPDATELIMIT]      = updatelimit;\n\n  init_BLAS();\n\n  return( newLU );\n}\n\nMYBOOL LUSOL_sizeto(LUSOLrec *LUSOL, int init_r, int init_c, int init_a)\n{\n  if(init_c == 0)\n    LUSOL_FREE(LUSOL->isingular);\n  if(LUSOL_realloc_a(LUSOL, init_a) &&\n     LUSOL_realloc_r(LUSOL, init_r) &&\n     LUSOL_realloc_c(LUSOL, init_c))\n    return( TRUE );\n  else\n    return( FALSE );\n}\n\nchar *LUSOL_pivotLabel(LUSOLrec *LUSOL)\n{\n  static /*const*/ char *pivotText[LUSOL_PIVMOD_MAX+1] =\n  {\"TPP\", \"TRP\", \"TCP\", \"TSP\"};\n  return(pivotText[LUSOL->luparm[LUSOL_IP_PIVOTTYPE]]);\n}\n\nvoid LUSOL_setpivotmodel(LUSOLrec *LUSOL, int pivotmodel, int initlevel)\n{\n  REAL newFM, newUM;\n\n  /* Set pivotmodel if specified */\n  if(pivotmodel > LUSOL_PIVMOD_NOCHANGE) {\n    if((pivotmodel <= LUSOL_PIVMOD_DEFAULT) || (pivotmodel > LUSOL_PIVMOD_MAX))\n      pivotmodel = LUSOL_PIVMOD_TPP;\n    LUSOL->luparm[LUSOL_IP_PIVOTTYPE]        = pivotmodel;\n  }\n\n  /* Check if we need bother about changing tolerances */\n  if((initlevel <= LUSOL_PIVTOL_NOCHANGE) || (initlevel > LUSOL_PIVTOL_MAX))\n    return;\n\n  /* Set default pivot tolerances\n     (note that UPDATEMAX should always be <= FACTORMAX) */\n  if(initlevel == LUSOL_PIVTOL_BAGGY) {        /* Extra-loose pivot thresholds */\n    newFM = 500.0;\n    newUM = newFM / 20;\n  }\n  else if(initlevel == LUSOL_PIVTOL_LOOSE) {  /* Moderately tight pivot tolerances */\n    newFM = 100.0;\n    newUM = newFM / 10;\n  }\n  else if(initlevel == LUSOL_PIVTOL_NORMAL) { /* Standard pivot tolerances */\n    newFM = 28.0;\n    newUM = newFM / 4;\n  }\n  else if(initlevel == LUSOL_PIVTOL_SLIM) {   /* Better accuracy pivot tolerances */\n    newFM = 10.0;\n    newUM = newFM / 2;\n  }\n  else if(initlevel == LUSOL_PIVTOL_TIGHT) {  /* Enhanced accuracy pivot tolerances */\n    newFM = 5.0;\n    newUM = newFM / 2;\n  }\n  else if(initlevel == LUSOL_PIVTOL_SUPER) {  /* Very tight pivot tolerances for extra accuracy */\n    newFM = 2.5;\n    newUM = 1.99;\n  }\n  else {                                      /* Extremely tight pivot tolerances for extra accuracy */\n    newFM = 1.99;\n    newUM = newFM / 1.49;\n  }\n\n  /* Set the tolerances */\n  LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij] = newFM;\n  LUSOL->parmlu[LUSOL_RP_UPDATEMAX_Lij] = newUM;\n}\n\nMYBOOL LUSOL_tightenpivot(LUSOLrec *LUSOL)\n{\n#if 0\n  REAL newvalue;\n#endif\n\n  /* Give up tightening if we are already less than limit and we cannot change strategy */\n  if(MIN(LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij],\n         LUSOL->parmlu[LUSOL_RP_UPDATEMAX_Lij]) < 1.1) {\n    if(LUSOL->luparm[LUSOL_IP_PIVOTTYPE] >= LUSOL_PIVMOD_TRP)\n      return( FALSE );\n    LUSOL_setpivotmodel(LUSOL, LUSOL->luparm[LUSOL_IP_PIVOTTYPE]+1, LUSOL_PIVTOL_DEFAULT+1);\n    return( 2 );\n  }\n\n  /* Otherwise tighten according to defined schedule */\n#if 0   /* This is Michael Saunder's proposed tightening procedure */\n  newvalue = sqrt(LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij]);\n  LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij] = newvalue;\n  SETMIN(LUSOL->parmlu[LUSOL_RP_UPDATEMAX_Lij], newvalue);\n#elif 0 /* This is Kjell Eikland's schedule #1 */\n  newvalue = sqrt(LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij]);\n  LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij] = newvalue;\n  LUSOL->parmlu[LUSOL_RP_UPDATEMAX_Lij] = 1.0 + (newvalue - 1.0) / 2;\n#else   /* This was Kjell Eikland's schedule #2 */\n  LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij] = 1.0 + LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij]/3.0;\n  LUSOL->parmlu[LUSOL_RP_UPDATEMAX_Lij] = 1.0 + LUSOL->parmlu[LUSOL_RP_UPDATEMAX_Lij]/3.0;\n#endif\n  return( TRUE );\n}\n\nMYBOOL LUSOL_addSingularity(LUSOLrec *LUSOL, int singcol, int *inform)\n{\n  int NSING = LUSOL->luparm[LUSOL_IP_SINGULARITIES],\n      ASING = LUSOL->luparm[LUSOL_IP_SINGULARLISTSIZE];\n\n  /* Check if we need to allocated list memory to store multiple singularities */\n  if((NSING > 0) && (NSING >= ASING)) {\n\n    /* Increase list in \"reasonable\" steps */\n    ASING += (int) (10.0 * (log10((REAL) LUSOL->m)+1.0));\n    LUSOL->isingular = (int *) LUSOL_REALLOC(LUSOL->isingular, sizeof(*LUSOL->isingular)*(ASING+1));\n    if(LUSOL->isingular == NULL) {\n      LUSOL->luparm[LUSOL_IP_SINGULARLISTSIZE] = 0;\n      *inform = LUSOL_INFORM_NOMEMLEFT;\n      return( FALSE );\n    }\n    LUSOL->luparm[LUSOL_IP_SINGULARLISTSIZE] = ASING;\n\n    /* Transfer the first singularity if the list was just created */\n    if(NSING == 1)\n      LUSOL->isingular[NSING] = LUSOL->luparm[LUSOL_IP_SINGULARINDEX];\n  }\n\n  /* Update singularity count and store its index */\n  NSING++;\n  if(NSING > 1) {\n    LUSOL->isingular[0] = NSING;\n    LUSOL->isingular[NSING] = singcol;\n  }\n  LUSOL->luparm[LUSOL_IP_SINGULARITIES] = NSING;\n\n  /* Mimic old logic by keeping the last singularity stored */\n  LUSOL->luparm[LUSOL_IP_SINGULARINDEX] = singcol;\n\n  return( TRUE );\n}\n\nint LUSOL_getSingularity(LUSOLrec *LUSOL, int singitem)\n{\n  if((singitem > LUSOL->luparm[LUSOL_IP_SINGULARITIES]) || (singitem < 0))\n    singitem = -1;\n  else if(singitem == 0)\n    singitem = LUSOL->luparm[LUSOL_IP_SINGULARITIES];\n  else if(singitem > 1)\n    singitem = LUSOL->isingular[singitem];\n  else\n    singitem = LUSOL->luparm[LUSOL_IP_SINGULARINDEX];\n  return( singitem );\n}\n\nint LUSOL_findSingularityPosition(LUSOLrec *LUSOL, int singcol)\n/* The purpose of this routine is to find the slack row/column in\n   user-index that was singular in the last unsuccessful column\n   update; zero is returned if the search was unsuccessful.\n   By adding a slack at this position this particular singularity\n   should disappear.\n   (Source: Michael A. Saunders; private communication to KE) */\n{\n#if 0 /* Michael Saunders version */\n  int j;\n  for(j = LUSOL->m; j > 0; j--)\n    if(LUSOL->iq[j] == singcol)\n      break;\n  singcol = j;\n#else /* Kjell Eikland version (note that iqinv could be invalid in early versions of LUSOL) */\n  singcol = LUSOL->iqinv[singcol];\n#endif\n  return( LUSOL->ip[singcol] );\n}\n\nchar *LUSOL_informstr(LUSOLrec *LUSOL, int inform)\n{\n  static char *informText[LUSOL_INFORM_MAX-LUSOL_INFORM_MIN+1] =\n  {\"LUSOL_RANKLOSS: Lost rank\",\n   \"LUSOL_LUSUCCESS: Success\",\n   \"LUSOL_LUSINGULAR: Singular A\",\n   \"LUSOL_LUUNSTABLE: Unstable factorization\",\n   \"LUSOL_ADIMERR: Row or column count exceeded\",\n   \"LUSOL_ADUPLICATE: Duplicate A matrix entry found\",\n   \"(Undefined message)\",\n   \"(Undefined message)\",\n   \"LUSOL_ANEEDMEM: Insufficient memory for factorization\",\n   \"LUSOL_FATALERR: Fatal internal error\",\n   \"LUSOL_NOPIVOT: Found no suitable pivot\",\n   \"LUSOL_NOMEMLEFT: Could not obtain more memory\"};\n  if((inform < LUSOL_INFORM_MIN) || (inform > LUSOL_INFORM_MAX))\n    inform = LUSOL->luparm[LUSOL_IP_INFORM];\n  return(informText[inform-LUSOL_INFORM_MIN]);\n}\n\nvoid LUSOL_clear(LUSOLrec *LUSOL, MYBOOL nzonly)\n{\n  int len;\n\n  LUSOL->nelem = 0;\n  if(!nzonly) {\n\n   /* lena arrays */\n    len = LUSOL->lena + LUSOL_ARRAYOFFSET;\n    MEMCLEAR(LUSOL->a,    len);\n    MEMCLEAR(LUSOL->indc, len);\n    MEMCLEAR(LUSOL->indr, len);\n\n   /* maxm arrays */\n    len = LUSOL->maxm + LUSOL_ARRAYOFFSET;\n    MEMCLEAR(LUSOL->lenr,  len);\n    MEMCLEAR(LUSOL->ip,    len);\n    MEMCLEAR(LUSOL->iqloc, len);\n    MEMCLEAR(LUSOL->ipinv, len);\n    MEMCLEAR(LUSOL->locr,  len);\n\n#ifndef ClassicHamaxR\n    if((LUSOL->amaxr != NULL)\n#ifdef AlwaysSeparateHamaxR\n       && (LUSOL->luparm[LUSOL_IP_PIVOTTYPE] == LUSOL_PIVMOD_TRP)\n#endif\n      )\n      MEMCLEAR(LUSOL->amaxr, len);\n#endif\n\n   /* maxn arrays */\n    len = LUSOL->maxn + LUSOL_ARRAYOFFSET;\n    MEMCLEAR(LUSOL->lenc,  len);\n    MEMCLEAR(LUSOL->iq,    len);\n    MEMCLEAR(LUSOL->iploc, len);\n    MEMCLEAR(LUSOL->iqinv, len);\n    MEMCLEAR(LUSOL->locc,  len);\n    MEMCLEAR(LUSOL->w,     len);\n\n    if(LUSOL->luparm[LUSOL_IP_PIVOTTYPE] == LUSOL_PIVMOD_TCP) {\n      MEMCLEAR(LUSOL->Ha,  len);\n      MEMCLEAR(LUSOL->Hj,  len);\n      MEMCLEAR(LUSOL->Hk,  len);\n    }\n#ifndef ClassicdiagU\n    if(LUSOL->luparm[LUSOL_IP_KEEPLU] == FALSE) {\n      MEMCLEAR(LUSOL->diagU, len);\n    }\n#endif\n\n  }\n}\n\nMYBOOL LUSOL_assign(LUSOLrec *LUSOL, int iA[], int jA[], REAL Aij[], int nzcount, MYBOOL istriplet)\n{\n  int k, m, n, ij, kol;\n\n  /* Adjust the size of the a structure */\n  if(nzcount > (LUSOL->lena/LUSOL->luparm[LUSOL_IP_SCALAR_NZA]) &&\n     !LUSOL_realloc_a(LUSOL, nzcount*LUSOL->luparm[LUSOL_IP_SCALAR_NZA]))\n    return( FALSE );\n\n  m = 0;\n  n = 0;\n  kol = 1;\n  for(k = 1; k <= nzcount; k++) {\n    /* First the row indicator */\n    ij = iA[k];\n    if(ij > m) {\n      m = ij;\n      if(m > LUSOL->maxm &&\n         !LUSOL_realloc_r(LUSOL, -(m / LUSOL_MINDELTA_FACTOR + 1)))\n        return( FALSE );\n    }\n    LUSOL->indc[k] = ij;\n\n    /* Then the column indicator;\n       Handle both triplet and column count formats */\n    if(istriplet)\n      ij = jA[k];\n    else {\n      if(k >= jA[kol])\n        kol++;\n      ij = kol;\n    }\n    if(ij > n) {\n      n = ij;\n      if(n > LUSOL->maxn &&\n         !LUSOL_realloc_c(LUSOL, -(n / LUSOL_MINDELTA_FACTOR + 1)))\n        return( FALSE );\n    }\n    LUSOL->indr[k] = ij;\n\n    /* Lastly the matrix value itself */\n    LUSOL->a[k] = Aij[k];\n  }\n  LUSOL->m = m;\n  LUSOL->n = n;\n  LUSOL->nelem = nzcount;\n  return( TRUE );\n}\n\nint LUSOL_loadColumn(LUSOLrec *LUSOL, int iA[], int jA, REAL Aij[], int nzcount, int offset1)\n{\n  int i, ii, nz, k;\n\n  nz = LUSOL->nelem;\n  i = nz + nzcount;\n  if(i > (LUSOL->lena/LUSOL->luparm[LUSOL_IP_SCALAR_NZA]) &&\n     !LUSOL_realloc_a(LUSOL, i*LUSOL->luparm[LUSOL_IP_SCALAR_NZA]))\n  return( -1 );\n\n  k = 0;\n  for(ii = 1; ii <= nzcount; ii++) {\n    i = ii + offset1;\n    if(Aij[i] == 0)\n      continue;\n    if(iA[i] <= 0 || iA[i] > LUSOL->m ||\n       jA <= 0 || jA > LUSOL->n) {\n      LUSOL_report(LUSOL, 0, \"Variable index outside of set bounds (r:%d/%d, c:%d/%d)\\n\",\n                             iA[i], LUSOL->m, jA, LUSOL->n);\n      continue;\n    }\n    k++;\n    nz++;\n    LUSOL->a[nz]    = Aij[i];\n    LUSOL->indc[nz] = iA[i];\n    LUSOL->indr[nz] = jA;\n  }\n  LUSOL->nelem = nz;\n  return( k );\n}\n\nvoid LUSOL_free(LUSOLrec *LUSOL)\n{\n  LUSOL_realloc_a(LUSOL, 0);\n  LUSOL_realloc_r(LUSOL, 0);\n  LUSOL_realloc_c(LUSOL, 0);\n  if(LUSOL->L0 != NULL)\n    LUSOL_matfree(&(LUSOL->L0));\n  if(LUSOL->U != NULL)\n    LUSOL_matfree(&(LUSOL->U));\n  if(!is_nativeBLAS())\n    unload_BLAS();\n  LUSOL_FREE(LUSOL);\n}\n\nvoid LUSOL_report(LUSOLrec *LUSOL, int msglevel, char *format, ...)\n{\n  va_list ap;\n\n  if(LUSOL == NULL) {\n    va_start(ap, format);\n    vfprintf(stderr, format, ap);\n    va_end(ap);\n  }\n  else if(msglevel >= 0  /*LUSOL->luparm[2]*/) {\n    if(LUSOL->writelog != NULL) {\n      char buff[255];\n\n      va_start(ap, format);\n      vsprintf(buff, format, ap);\n      va_end(ap);\n      LUSOL->writelog(LUSOL, LUSOL->loghandle, buff);\n    }\n    if(LUSOL->outstream != NULL) {\n      va_start(ap, format);\n      vfprintf(LUSOL->outstream, format, ap);\n      va_end(ap);\n      fflush(LUSOL->outstream);\n    }\n  }\n}\n\nvoid LUSOL_timer(LUSOLrec *LUSOL, int timerid, char *text)\n{\n  LUSOL_report(LUSOL, -1, \"TimerID %d at %s - %s\\n\",\n                          timerid, \"\", text);\n}\n\nint LUSOL_factorize(LUSOLrec *LUSOL)\n{\n  int inform;\n\n  LU1FAC( LUSOL, &inform );\n  return( inform );\n}\n\nint LUSOL_ftran(LUSOLrec *LUSOL, REAL b[], int NZidx[], MYBOOL prepareupdate)\n{\n  int  inform;\n  REAL *vector;\n\n  if(prepareupdate)\n    vector = LUSOL->vLU6L;\n  else\n    vector = LUSOL->w;\n\n  /* Copy RHS vector, but make adjustment for offset since this\n     can create a memory error when the calling program uses\n     a 0-base vector offset back to comply with LUSOL. */\n  MEMCOPY(vector+1, b+1, LUSOL->n);\n  if (vector != NULL)\n    vector[0] = 0;\n\n  LU6SOL(LUSOL, LUSOL_SOLVE_Aw_v, vector, b, NZidx, &inform);\n  LUSOL->luparm[LUSOL_IP_FTRANCOUNT]++;\n\n  return(inform);\n}\n\n\nint LUSOL_btran(LUSOLrec *LUSOL, REAL b[], int NZidx[])\n{\n  int inform;\n\n  /* Copy RHS vector, but make adjustment for offset since this\n     can create a memory error when the calling program uses\n     a 0-base vector offset back to comply with LUSOL. */\n  MEMCOPY(LUSOL->w+1, b+1, LUSOL->m);\n  if (LUSOL->w != NULL)\n    LUSOL->w[0] = 0;\n\n  LU6SOL(LUSOL, LUSOL_SOLVE_Atv_w, b, LUSOL->w, NZidx, &inform);\n  LUSOL->luparm[LUSOL_IP_BTRANCOUNT]++;\n\n  return(inform);\n}\n\n\nint LUSOL_replaceColumn(LUSOLrec *LUSOL, int jcol, REAL v[])\n{\n  int  inform;\n  REAL DIAG, VNORM;\n\n  LU8RPC(LUSOL, LUSOL_UPDATE_OLDNONEMPTY, LUSOL_UPDATE_NEWNONEMPTY,\n                jcol, v, NULL,\n                &inform, &DIAG, &VNORM);\n\n  LUSOL->replaced_c++;\n  return( inform );\n}\n\nREAL LUSOL_vecdensity(LUSOLrec *LUSOL, REAL V[])\n{\n  int I, N = 0;\n\n  for(I = 1; I <= LUSOL->m; I++)\n    if(fabs(V[I]) > 0)\n      N++;\n  return( (REAL) N / (REAL) LUSOL->m );\n}\n\nchar relationChar(REAL left, REAL right)\n{\n  if(left > right)\n    return('>');\n  else if(left == right)\n    return('=');\n  else\n    return('<');\n}\n\n/* Retrieve the core modules ordered by order of dependency */\n\n#include \"lusol2.c\"      /* Heap management */\n#include \"lusol6a.c\"     /* Singularity checking and equation solving */\n#include \"lusol1.c\"      /* Factorization and core components */\n#include \"lusol7a.c\"     /* Utility routines for updates */\n#include \"lusol8a.c\"     /* Column update */\n\n\nvoid LUSOL_dump(FILE *output, LUSOLrec *LUSOL)\n{\n  MYBOOL userfile = (MYBOOL) (output != NULL);\n\n  if(!userfile)\n    output = fopen(\"LUSOL.dbg\", \"w\");\n\n  blockWriteREAL(output, \"a\", LUSOL->a, 1, LUSOL->lena);\n  blockWriteINT(output, \"indc\", LUSOL->indc, 1, LUSOL->lena);\n  blockWriteINT(output, \"indr\", LUSOL->indr, 1, LUSOL->lena);\n\n  blockWriteINT(output, \"ip\", LUSOL->ip, 1, LUSOL->m);\n  blockWriteINT(output, \"iq\", LUSOL->iq, 1, LUSOL->n);\n  blockWriteINT(output, \"lenc\", LUSOL->lenc, 1, LUSOL->n);\n  blockWriteINT(output, \"lenr\", LUSOL->lenr, 1, LUSOL->m);\n\n  blockWriteINT(output, \"locc\", LUSOL->locc, 1, LUSOL->n);\n  blockWriteINT(output, \"locr\", LUSOL->locr, 1, LUSOL->m);\n  blockWriteINT(output, \"iploc\", LUSOL->iploc, 1, LUSOL->n);\n  blockWriteINT(output, \"iqloc\", LUSOL->iqloc, 1, LUSOL->m);\n\n  blockWriteINT(output, \"ipinv\", LUSOL->ipinv, 1, LUSOL->m);\n  blockWriteINT(output, \"iqinv\", LUSOL->iqinv, 1, LUSOL->n);\n\n  if(!userfile)\n    fclose(output);\n}\n\nLUSOLmat *LUSOL_matcreate(int dim, int nz)\n{\n  LUSOLmat *newm;\n\n  newm = (LUSOLmat *) LUSOL_CALLOC(1, sizeof(*newm));\n  if(newm != NULL) {\n    newm->a    = (REAL *) LUSOL_MALLOC((nz+1)*sizeof(REAL));\n    newm->lenx = (int *)  LUSOL_MALLOC((dim+1)*sizeof(int));\n    newm->indx = (int *)  LUSOL_MALLOC((dim+1)*sizeof(int));\n    newm->indr = (int *)  LUSOL_MALLOC((nz+1)*sizeof(int));\n    newm->indc = (int *)  LUSOL_MALLOC((nz+1)*sizeof(int));\n    if((newm->a == NULL) ||\n       (newm->lenx == NULL) || (newm->indx == NULL) ||\n       (newm->indr == NULL) || (newm->indc == NULL))\n      LUSOL_matfree(&newm);\n  }\n  return(newm);\n}\nvoid LUSOL_matfree(LUSOLmat **mat)\n{\n  if((mat == NULL) || (*mat == NULL))\n    return;\n  LUSOL_FREE((*mat)->a);\n  LUSOL_FREE((*mat)->indc);\n  LUSOL_FREE((*mat)->indr);\n  LUSOL_FREE((*mat)->lenx);\n  LUSOL_FREE((*mat)->indx);\n  LUSOL_FREE(*mat);\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol.h",
    "content": "#ifndef HEADER_LUSOL\n#define HEADER_LUSOL\n\n/* Include necessary libraries                                               */\n/* ------------------------------------------------------------------------- */\n#include <stdio.h>\n#include \"commonlib.h\"\n\n/* Version information                                                       */\n/* ------------------------------------------------------------------------- */\n#define LUSOL_VERMAJOR   2\n#define LUSOL_VERMINOR   2\n#define LUSOL_RELEASE    2\n#define LUSOL_BUILD      0\n\n/* Dynamic memory management macros                                          */\n/* ------------------------------------------------------------------------- */\n#ifdef MATLAB\n  #define LUSOL_MALLOC(bytesize)        mxMalloc(bytesize)\n  #define LUSOL_CALLOC(count, recsize)  mxCalloc(count, recsize)\n  #define LUSOL_REALLOC(ptr, bytesize)  mxRealloc((void *) ptr, bytesize)\n  #define LUSOL_FREE(ptr)               {mxFree(ptr); ptr=NULL;}\n#else\n  #define LUSOL_MALLOC(bytesize)        malloc(bytesize)\n  #define LUSOL_CALLOC(count, recsize)  calloc(count, recsize)\n  #define LUSOL_REALLOC(ptr, bytesize)  realloc((void *) ptr, bytesize)\n  #define LUSOL_FREE(ptr)               {free(ptr); ptr=NULL;}\n#endif\n\n/* Performance compiler options                                              */\n/* ------------------------------------------------------------------------- */\n#if 1\n  #define ForceInitialization      /* Satisfy compilers, check during debugging! */\n  #define LUSOLFastDenseIndex           /* Increment the linearized dense address */\n  #define LUSOLFastClear           /* Use intrinsic functions for memory zeroing */\n  #define LUSOLFastMove              /* Use intrinsic functions for memory moves */\n  #define LUSOLFastCopy               /* Use intrinsic functions for memory copy */\n  #define LUSOLFastSolve           /* Use pointer operations in equation solving */\n  #define LUSOLSafeFastUpdate      /* Use separate array for LU6L result storage */\n/*#define UseOld_LU6CHK_20040510 */\n/*#define AlwaysSeparateHamaxR */       /* Enabled when the pivot model is fixed */\n  #if 0\n    #define ForceRowBasedL0                  /* Create a row-sorted version of L0 */\n  #endif\n/*  #define SetSmallToZero*/\n/*  #define DoTraceL0 */\n#endif\n/*#define UseTimer */\n\n\n/* Legacy compatibility and testing options (Fortran-LUSOL)                  */\n/* ------------------------------------------------------------------------- */\n#if 0\n  #define LegacyTesting\n  #define StaticMemAlloc           /* Preallocated vs. dynamic memory allocation */\n  #define ClassicdiagU                                  /* Store diagU at end of a */\n  #define ClassicHamaxR                    /* Store H+AmaxR at end of a/indc/indr */\n#endif\n\n\n/* General constants and data type definitions                               */\n/* ------------------------------------------------------------------------- */\n#define LUSOL_ARRAYOFFSET            1\n#ifndef ZERO\n  #define ZERO                       0\n#endif\n#ifndef ONE\n  #define ONE                        1\n#endif\n#ifndef FALSE\n  #define FALSE                      0\n#endif\n#ifndef TRUE\n  #define TRUE                       1\n#endif\n#ifndef NULL\n  #define NULL                       0\n#endif\n#ifndef REAL\n  #define REAL double\n#endif\n#ifndef REALXP\n  #define REALXP long double\n#endif\n#ifndef MYBOOL\n  #define MYBOOL unsigned char\n#endif\n\n\n/* User-settable default parameter values                                    */\n/* ------------------------------------------------------------------------- */\n#define LUSOL_DEFAULT_GAMMA        2.0\n#define LUSOL_SMALLNUM         1.0e-20  /* IAEE doubles have precision 2.22e-16 */\n#define LUSOL_BIGNUM           1.0e+20\n#define LUSOL_MINDELTA_FACTOR        4\n#define LUSOL_MINDELTA_a         10000\n#if 1\n  #define LUSOL_MULT_nz_a            2  /* Suggested by Yin Zhang */\n#else\n  #define LUSOL_MULT_nz_a            5  /* Could consider 6 or 7 */\n#endif\n#define LUSOL_MINDELTA_rc         1000\n#define LUSOL_DEFAULT_SMARTRATIO 0.667\n\n/* Fixed system parameters (changeable only by developers)                   */\n/* ------------------------------------------------------------------------- */\n\n/* parmlu INPUT parameters: */\n#define LUSOL_RP_SMARTRATIO          0\n#define LUSOL_RP_FACTORMAX_Lij       1\n#define LUSOL_RP_UPDATEMAX_Lij       2\n#define LUSOL_RP_ZEROTOLERANCE       3\n#define LUSOL_RP_SMALLDIAG_U         4\n#define LUSOL_RP_EPSDIAG_U           5\n#define LUSOL_RP_COMPSPACE_U         6\n#define LUSOL_RP_MARKOWITZ_CONLY     7\n#define LUSOL_RP_MARKOWITZ_DENSE     8\n#define LUSOL_RP_GAMMA               9\n\n/* parmlu OUPUT parameters: */\n#define LUSOL_RP_MAXELEM_A          10\n#define LUSOL_RP_MAXMULT_L          11\n#define LUSOL_RP_MAXELEM_U          12\n#define LUSOL_RP_MAXELEM_DIAGU      13\n#define LUSOL_RP_MINELEM_DIAGU      14\n#define LUSOL_RP_MAXELEM_TCP        15\n#define LUSOL_RP_GROWTHRATE         16\n#define LUSOL_RP_USERDATA_1         17\n#define LUSOL_RP_USERDATA_2         18\n#define LUSOL_RP_USERDATA_3         19\n#define LUSOL_RP_RESIDUAL_U         20\n#define LUSOL_RP_LASTITEM            LUSOL_RP_RESIDUAL_U\n\n/* luparm INPUT parameters: */\n#define LUSOL_IP_USERDATA_0          0\n#define LUSOL_IP_PRINTUNIT           1\n#define LUSOL_IP_PRINTLEVEL          2\n#define LUSOL_IP_MARKOWITZ_MAXCOL    3\n#define LUSOL_IP_SCALAR_NZA          4\n#define LUSOL_IP_UPDATELIMIT         5\n#define LUSOL_IP_PIVOTTYPE           6\n#define LUSOL_IP_ACCELERATION        7\n#define LUSOL_IP_KEEPLU              8\n#define LUSOL_IP_SINGULARLISTSIZE    9\n\n/* luparm OUTPUT parameters: */\n#define LUSOL_IP_INFORM             10\n#define LUSOL_IP_SINGULARITIES      11\n#define LUSOL_IP_SINGULARINDEX      12\n#define LUSOL_IP_MINIMUMLENA        13\n#define LUSOL_IP_MAXLEN             14\n#define LUSOL_IP_UPDATECOUNT        15\n#define LUSOL_IP_RANK_U             16\n#define LUSOL_IP_COLCOUNT_DENSE1    17\n#define LUSOL_IP_COLCOUNT_DENSE2    18\n#define LUSOL_IP_COLINDEX_DUMIN     19\n#define LUSOL_IP_COLCOUNT_L0        20\n#define LUSOL_IP_NONZEROS_L0        21\n#define LUSOL_IP_NONZEROS_U0        22\n#define LUSOL_IP_NONZEROS_L         23\n#define LUSOL_IP_NONZEROS_U         24\n#define LUSOL_IP_NONZEROS_ROW       25\n#define LUSOL_IP_COMPRESSIONS_LU    26\n#define LUSOL_IP_MARKOWITZ_MERIT    27\n#define LUSOL_IP_TRIANGROWS_U       28\n#define LUSOL_IP_TRIANGROWS_L       29\n#define LUSOL_IP_FTRANCOUNT         30\n#define LUSOL_IP_BTRANCOUNT         31\n#define LUSOL_IP_ROWCOUNT_L0        32\n#define LUSOL_IP_LASTITEM            LUSOL_IP_ROWCOUNT_L0\n\n\n/* Macros for matrix-based access for dense part of A and timer mapping      */\n/* ------------------------------------------------------------------------- */\n#define DAPOS(row, col)   (row + (col-1)*LDA)\n#define timer(text, id)   LUSOL_timer(LUSOL, id, text)\n\n\n/* Parameter/option defines                                                  */\n/* ------------------------------------------------------------------------- */\n#define LUSOL_MSG_NONE              -1\n#define LUSOL_MSG_SINGULARITY        0\n#define LUSOL_MSG_STATISTICS        10\n#define LUSOL_MSG_PIVOT             50\n\n#define LUSOL_BASEORDER              0\n#define LUSOL_OTHERORDER             1\n#define LUSOL_AUTOORDER              2\n#define LUSOL_ACCELERATE_L0          4\n#define LUSOL_ACCELERATE_U           8\n\n#define LUSOL_PIVMOD_NOCHANGE       -2  /* Don't change active pivoting model */\n#define LUSOL_PIVMOD_DEFAULT        -1  /* Set pivoting model to default */\n#define LUSOL_PIVMOD_TPP             0  /* Threshold Partial   pivoting (normal) */\n#define LUSOL_PIVMOD_TRP             1  /* Threshold Rook      pivoting */\n#define LUSOL_PIVMOD_TCP             2  /* Threshold Complete  pivoting */\n#define LUSOL_PIVMOD_TSP             3  /* Threshold Symmetric pivoting */\n#define LUSOL_PIVMOD_MAX             LUSOL_PIVMOD_TSP\n\n#define LUSOL_PIVTOL_NOCHANGE        0\n#define LUSOL_PIVTOL_BAGGY           1\n#define LUSOL_PIVTOL_LOOSE           2\n#define LUSOL_PIVTOL_NORMAL          3\n#define LUSOL_PIVTOL_SLIM            4\n#define LUSOL_PIVTOL_TIGHT           5\n#define LUSOL_PIVTOL_SUPER           6\n#define LUSOL_PIVTOL_CORSET          7\n#define LUSOL_PIVTOL_DEFAULT         LUSOL_PIVTOL_SLIM\n#define LUSOL_PIVTOL_MAX             LUSOL_PIVTOL_CORSET\n\n#define LUSOL_UPDATE_OLDEMPTY        0  /* No/empty current column. */\n#define LUSOL_UPDATE_OLDNONEMPTY     1  /* Current column need not have been empty. */\n#define LUSOL_UPDATE_NEWEMPTY        0  /* New column is taken to be zero. */\n#define LUSOL_UPDATE_NEWNONEMPTY     1  /* v(*) contains the new column;\n                                           on exit,  v(*)  satisfies  L*v = a(new). */\n#define LUSOL_UPDATE_USEPREPARED     2  /* v(*)  must satisfy  L*v = a(new). */\n\n#define LUSOL_SOLVE_Lv_v             1  /* v  solves   L v = v(input). w  is not touched. */\n#define LUSOL_SOLVE_Ltv_v            2  /* v  solves   L'v = v(input). w  is not touched. */\n#define LUSOL_SOLVE_Uw_v             3  /* w  solves   U w = v.        v  is not altered. */\n#define LUSOL_SOLVE_Utv_w            4  /* v  solves   U'v = w.        w  is destroyed. */\n#define LUSOL_SOLVE_Aw_v             5  /* w  solves   A w = v.        v  is altered as in 1. */\n#define LUSOL_FTRAN   LUSOL_SOLVE_Aw_v\n#define LUSOL_SOLVE_Atv_w            6  /* v  solves   A'v = w.        w  is destroyed. */\n#define LUSOL_BTRAN  LUSOL_SOLVE_Atv_w\n\n/* If mode = 3,4,5,6, v and w must not be the same arrays.\n   If lu1fac has just been used to factorize a symmetric matrix A\n   (which must be definite or quasi-definite), the factors A = L U\n   may be regarded as A = LDL', where D = diag(U).  In such cases,\n   the following (faster) solve codes may be used:                  */\n#define LUSOL_SOLVE_Av_v             7  /* v  solves   A v = L D L'v = v(input). w  is not touched. */\n#define LUSOL_SOLVE_LDLtv_v          8  /* v  solves       L |D| L'v = v(input). w  is not touched. */\n\n#define LUSOL_INFORM_RANKLOSS       -1\n#define LUSOL_INFORM_LUSUCCESS       0\n#define LUSOL_INFORM_LUSINGULAR      1\n#define LUSOL_INFORM_LUUNSTABLE      2\n#define LUSOL_INFORM_ADIMERR         3\n#define LUSOL_INFORM_ADUPLICATE      4\n#define LUSOL_INFORM_ANEEDMEM        7  /* Set lena >= luparm[LUSOL_IP_MINIMUMLENA] */\n#define LUSOL_INFORM_FATALERR        8\n#define LUSOL_INFORM_NOPIVOT         9  /* No diagonal pivot found with TSP or TDP. */\n#define LUSOL_INFORM_NOMEMLEFT      10\n\n#define LUSOL_INFORM_MIN             LUSOL_INFORM_RANKLOSS\n#define LUSOL_INFORM_MAX             LUSOL_INFORM_NOMEMLEFT\n\n#define LUSOL_INFORM_GETLAST        10  /* Code for LUSOL_informstr. */\n#define LUSOL_INFORM_SERIOUS         LUSOL_INFORM_LUUNSTABLE\n\n\n/* Prototypes for call-back functions                                        */\n/* ------------------------------------------------------------------------- */\ntypedef void LUSOLlogfunc(void *lp, void *userhandle, char *buf);\n\n\n/* Sparse matrix data */\ntypedef struct _LUSOLmat {\n  REAL *a;\n  int  *lenx, *indr, *indc, *indx;\n} LUSOLmat;\n\n\n/* The main LUSOL data record */\n/* ------------------------------------------------------------------------- */\ntypedef struct _LUSOLrec {\n\n  /* General data */\n  FILE         *outstream;           /* Output stream, initialized to STDOUT */\n  LUSOLlogfunc *writelog;\n    void       *loghandle;\n  LUSOLlogfunc *debuginfo;\n\n  /* Parameter storage arrays */\n  int    luparm[LUSOL_IP_LASTITEM + 1];\n  REAL   parmlu[LUSOL_RP_LASTITEM + 1];\n\n  /* Arrays of length lena+1 */\n  int    lena, nelem;\n  int    *indc, *indr;\n  REAL   *a;\n\n  /* Arrays of length maxm+1 (row storage) */\n  int    maxm, m;\n  int    *lenr, *ip, *iqloc, *ipinv, *locr;\n\n  /* Arrays of length maxn+1 (column storage) */\n  int    maxn, n;\n  int    *lenc, *iq, *iploc, *iqinv, *locc;\n  REAL   *w, *vLU6L;\n\n  /* List of singular columns, with dynamic size allocation */\n  int    *isingular;\n\n  /* Extra arrays of length n for TCP and keepLU == FALSE */\n  REAL   *Ha, *diagU;\n  int    *Hj, *Hk;\n\n  /* Extra arrays of length m for TRP*/\n  REAL   *amaxr;\n\n  /* Extra array for L0 and U stored by row/column for faster btran/ftran */\n  LUSOLmat *L0;\n  LUSOLmat *U;\n\n  /* Miscellaneous data */\n  int    expanded_a;\n  int    replaced_c;\n  int    replaced_r;\n\n} LUSOLrec;\n\n\nLUSOLrec *LUSOL_create(FILE *outstream, int msgfil, int pivotmodel, int updatelimit);\nMYBOOL LUSOL_sizeto(LUSOLrec *LUSOL, int init_r, int init_c, int init_a);\nMYBOOL LUSOL_assign(LUSOLrec *LUSOL, int iA[], int jA[], REAL Aij[],\n                                     int nzcount, MYBOOL istriplet);\nvoid LUSOL_clear(LUSOLrec *LUSOL, MYBOOL nzonly);\nvoid LUSOL_free(LUSOLrec *LUSOL);\n\nLUSOLmat *LUSOL_matcreate(int dim, int nz);\nvoid LUSOL_matfree(LUSOLmat **mat);\n\nint LUSOL_loadColumn(LUSOLrec *LUSOL, int iA[], int jA, REAL Aij[], int nzcount, int offset1);\nvoid LUSOL_setpivotmodel(LUSOLrec *LUSOL, int pivotmodel, int initlevel);\nint LUSOL_factorize(LUSOLrec *LUSOL);\nint LUSOL_replaceColumn(LUSOLrec *LUSOL, int jcol, REAL v[]);\n\nMYBOOL LUSOL_tightenpivot(LUSOLrec *LUSOL);\nMYBOOL LUSOL_addSingularity(LUSOLrec *LUSOL, int singcol, int *inform);\nint LUSOL_getSingularity(LUSOLrec *LUSOL, int singitem);\nint LUSOL_findSingularityPosition(LUSOLrec *LUSOL, int singcol);\n\nchar *LUSOL_pivotLabel(LUSOLrec *LUSOL);\nchar *LUSOL_informstr(LUSOLrec *LUSOL, int inform);\nREAL LUSOL_vecdensity(LUSOLrec *LUSOL, REAL V[]);\nvoid LUSOL_report(LUSOLrec *LUSOL, int msglevel, char *format, ...);\nvoid LUSOL_timer(LUSOLrec *LUSOL, int timerid, char *text);\n\nint LUSOL_ftran(LUSOLrec *LUSOL, REAL b[], int NZidx[], MYBOOL prepareupdate);\nint LUSOL_btran(LUSOLrec *LUSOL, REAL b[], int NZidx[]);\n\nvoid LU1FAC(LUSOLrec *LUSOL, int *INFORM);\nMYBOOL LU1L0(LUSOLrec *LUSOL, LUSOLmat **mat, int *inform);\nvoid LU6SOL(LUSOLrec *LUSOL, int MODE, REAL V[], REAL W[], int NZidx[], int *INFORM);\nvoid LU8RPC(LUSOLrec *LUSOL, int MODE1, int MODE2,\n            int JREP, REAL V[], REAL W[],\n            int *INFORM, REAL *DIAG, REAL *VNORM);\n\nvoid LUSOL_dump(FILE *output, LUSOLrec *LUSOL);\n\n\nvoid print_L0(LUSOLrec *LUSOL);\n\n\n#endif /* HEADER_LUSOL */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol1.c",
    "content": "\n/* ==================================================================\n   lu1DCP factors a dense m x n matrix A by Gaussian elimination,\n   using Complete Pivoting (row and column interchanges) for stability.\n   This version also uses column interchanges if all elements in a\n   pivot column are smaller than (or equal to) \"small\".  Such columns\n   are changed to zero and permuted to the right-hand end.\n   As in LINPACK's dgefa, ipvt(!) keeps track of pivot rows.\n   Rows of U are interchanged, but we don't have to physically\n   permute rows of L.  In contrast, column interchanges are applied\n   directly to the columns of both L and U, and to the column\n   permutation vector iq(*).\n   ------------------------------------------------------------------\n   On entry:\n      a       Array holding the matrix A to be factored.\n      lda     The leading dimension of the array  a.\n      m       The number of rows    in  A.\n      n       The number of columns in  A.\n      small   A drop tolerance.  Must be zero or positive.\n\n   On exit:\n      a       An upper triangular matrix and the multipliers\n              which were used to obtain it.\n              The factorization can be written  A = L*U  where\n              L  is a product of permutation and unit lower\n              triangular matrices and  U  is upper triangular.\n      nsing   Number of singularities detected.\n      ipvt    Records the pivot rows.\n      iq      A vector to which column interchanges are applied.\n   ------------------------------------------------------------------\n   01 May 2002: First dense Complete Pivoting, derived from lu1DPP.\n   07 May 2002: Another break needed at end of first loop.\n   07 May 2002: Current version of lu1DCP.\n   ================================================================== */\nvoid LU1DCP(LUSOLrec *LUSOL, REAL DA[], int LDA, int M, int N, REAL SMALL,\n            int *NSING, int IPVT[], int IX[])\n{\n\n  int       I, J, K, KP1, L, LAST, LENCOL, IMAX, JMAX, JLAST, JNEW;\n  REAL      AIJMAX, AJMAX;\n  register REAL T;\n#ifdef LUSOLFastDenseIndex\n  register REAL *DA1, *DA2;\n  int IDA1, IDA2;\n#else\n  register int IDA1, IDA2;\n#endif\n\n  *NSING = 0;\n  LENCOL = M+1;\n  LAST = N;\n/*     -----------------------------------------------------------------\n        Start of elimination loop.\n       ----------------------------------------------------------------- */\n  for(K = 1; K <= N; K++) {\n    KP1 = K+1;\n    LENCOL--;\n/*      Find the biggest aij in row imax and column jmax. */\n    AIJMAX = ZERO;\n    IMAX = K;\n    JMAX = K;\n    JLAST = LAST;\n    for(J = K; J <= JLAST; J++) {\nx10:\n      L = idamax(LENCOL,DA+DAPOS(K,J)-LUSOL_ARRAYOFFSET,1)+K-1;\n      AJMAX = fabs(DA[DAPOS(L,J)]);\n      if(AJMAX<=SMALL) {\n/*     ========================================================\n        Do column interchange, changing old column to zero.\n        Reduce  \"last\"  and try again with same j.\n       ======================================================== */\n        (*NSING)++;\n        JNEW = IX[LAST];\n        IX[LAST] = IX[J];\n        IX[J] = JNEW;\n#ifdef LUSOLFastDenseIndex\n        DA1 = DA+DAPOS(0,LAST);\n        DA2 = DA+DAPOS(0,J);\n        for(I = 1; I <= K-1; I++) {\n          DA1++;\n          DA2++;\n          T = *DA1;\n          *DA1 = *DA2;\n          *DA2 = T;\n#else\n        for(I = 1; I <= K-1; I++) {\n          IDA1 = DAPOS(I,LAST);\n          IDA2 = DAPOS(I,J);\n          T = DA[IDA1];\n          DA[IDA1] = DA[IDA2];\n          DA[IDA2] = T;\n#endif\n        }\n#ifdef LUSOLFastDenseIndex\n        for(I = K; I <= M; I++) {\n          DA1++;\n          DA2++;\n          T = *DA1;\n          *DA1 = ZERO;\n          *DA2 = T;\n#else\n        for(I = K; I <= M; I++) {\n          IDA1 = DAPOS(I,LAST);\n          IDA2 = DAPOS(I,J);\n          T = DA[IDA1];\n          DA[IDA1] = ZERO;\n          DA[IDA2] = T;\n#endif\n        }\n        LAST--;\n        if(J<=LAST)\n          goto x10;\n        break;\n      }\n/*      Check if this column has biggest aij so far. */\n      if(AIJMAX<AJMAX) {\n        AIJMAX = AJMAX;\n        IMAX = L;\n        JMAX = J;\n      }\n      if(J>=LAST)\n        break;\n    }\n    IPVT[K] = IMAX;\n    if(JMAX!=K) {\n/*     ==========================================================\n        Do column interchange (k and jmax).\n       ========================================================== */\n      JNEW = IX[JMAX];\n      IX[JMAX] = IX[K];\n      IX[K] = JNEW;\n#ifdef LUSOLFastDenseIndex\n      DA1 = DA+DAPOS(0,JMAX);\n      DA2 = DA+DAPOS(0,K);\n      for(I = 1; I <= M; I++) {\n        DA1++;\n        DA2++;\n        T = *DA1;\n        *DA1 = *DA2;\n        *DA2 = T;\n#else\n      for(I = 1; I <= M; I++) {\n        IDA1 = DAPOS(I,JMAX);\n        IDA2 = DAPOS(I,K);\n        T = DA[IDA1];\n        DA[IDA1] = DA[IDA2];\n        DA[IDA2] = T;\n#endif\n      }\n    }\n    if(M>K) {\n/*     ===========================================================\n        Do row interchange if necessary.\n       =========================================================== */\n      if(IMAX!=K) {\n        IDA1 = DAPOS(IMAX,K);\n        IDA2 = DAPOS(K,K);\n        T = DA[IDA1];\n        DA[IDA1] = DA[IDA2];\n        DA[IDA2] = T;\n      }\n/*     ===========================================================\n        Compute multipliers.\n        Do row elimination with column indexing.\n       =========================================================== */\n      T = -ONE/DA[DAPOS(K,K)];\n      dscal(M-K,T,DA+DAPOS(KP1,K)-LUSOL_ARRAYOFFSET,1);\n      for(J = KP1; J <= LAST; J++) {\n        IDA1 = DAPOS(IMAX,J);\n        T = DA[IDA1];\n        if(IMAX!=K) {\n          IDA2 = DAPOS(K,J);\n          DA[IDA1] = DA[IDA2];\n          DA[IDA2] = T;\n        }\n        daxpy(M-K,T,DA+DAPOS(KP1,K)-LUSOL_ARRAYOFFSET,1,\n                    DA+DAPOS(KP1,J)-LUSOL_ARRAYOFFSET,1);\n      }\n    }\n    else\n      break;\n    if(K>=LAST)\n      break;\n  }\n/*      Set ipvt(*) for singular rows. */\n  for(K = LAST+1; K <= M; K++)\n    IPVT[K] = K;\n\n}\n\n/* ==================================================================\n   lu1DPP factors a dense m x n matrix A by Gaussian elimination,\n   using row interchanges for stability, as in dgefa from LINPACK.\n   This version also uses column interchanges if all elements in a\n   pivot column are smaller than (or equal to) \"small\".  Such columns\n   are changed to zero and permuted to the right-hand end.\n   As in LINPACK, ipvt(*) keeps track of pivot rows.\n   Rows of U are interchanged, but we don't have to physically\n   permute rows of L.  In contrast, column interchanges are applied\n   directly to the columns of both L and U, and to the column\n   permutation vector iq(*).\n   ------------------------------------------------------------------\n   On entry:\n        a       Array holding the matrix A to be factored.\n        lda     The leading dimension of the array  a.\n        m       The number of rows    in  A.\n        n       The number of columns in  A.\n        small   A drop tolerance.  Must be zero or positive.\n\n   On exit:\n        a       An upper triangular matrix and the multipliers\n                which were used to obtain it.\n                The factorization can be written  A = L*U  where\n                L  is a product of permutation and unit lower\n                triangular matrices and  U  is upper triangular.\n        nsing   Number of singularities detected.\n        ipvt    Records the pivot rows.\n        iq      A vector to which column interchanges are applied.\n   ------------------------------------------------------------------\n   02 May 1989: First version derived from dgefa\n                in LINPACK (version dated 08/14/78).\n   05 Feb 1994: Generalized to treat rectangular matrices\n                and use column interchanges when necessary.\n                ipvt is retained, but column permutations are applied\n                directly to iq(*).\n   21 Dec 1994: Bug found via example from Steve Dirkse.\n                Loop 100 added to set ipvt(*) for singular rows.\n   ================================================================== */\nvoid LU1DPP(LUSOLrec *LUSOL, REAL DA[], int LDA, int M, int N, REAL SMALL,\n            int *NSING, int IPVT[], int IX[])\n{\n  int            I, J, K, KP1, L, LAST, LENCOL;\n  register REAL T;\n#ifdef LUSOLFastDenseIndex\n  register REAL *DA1, *DA2;\n  int IDA1, IDA2;\n#else\n  register int IDA1, IDA2;\n#endif\n\n  *NSING = 0;\n  K = 1;\n  LAST = N;\n/*      ------------------------------------------------------------------\n        Start of elimination loop.\n        ------------------------------------------------------------------ */\nx10:\n  KP1 = K+1;\n  LENCOL = (M-K)+1;\n/*      Find l, the pivot row. */\n  L = (idamax(LENCOL,DA+DAPOS(K,K)-LUSOL_ARRAYOFFSET,1)+K)-1;\n  IPVT[K] = L;\n  if(fabs(DA[DAPOS(L,K)])<=SMALL) {\n/*         ===============================================================\n           Do column interchange, changing old pivot column to zero.\n           Reduce  \"last\"  and try again with same k.\n           =============================================================== */\n    (*NSING)++;\n    J = IX[LAST];\n    IX[LAST] = IX[K];\n    IX[K] = J;\n#ifdef LUSOLFastDenseIndex\n    DA1 = DA+DAPOS(0,LAST);\n    DA2 = DA+DAPOS(0,K);\n    for(I = 1; I <= K-1; I++) {\n      DA1++;\n      DA2++;\n      T = *DA1;\n      *DA1 = *DA2;\n      *DA2 = T;\n#else\n    for(I = 1; I <= K-1; I++) {\n      IDA1 = DAPOS(I,LAST);\n      IDA2 = DAPOS(I,K);\n      T = DA[IDA1];\n      DA[IDA1] = DA[IDA2];\n      DA[IDA2] = T;\n#endif\n    }\n#ifdef LUSOLFastDenseIndex\n    for(I = K; I <= M; I++) {\n      DA1++;\n      DA2++;\n      T = *DA1;\n      *DA1 = ZERO;\n      *DA2 = T;\n#else\n    for(I = K; I <= M; I++) {\n      IDA1 = DAPOS(I,LAST);\n      IDA2 = DAPOS(I,K);\n      T = DA[IDA1];\n      DA[IDA1] = ZERO;\n      DA[IDA2] = T;\n#endif\n    }\n    LAST = LAST-1;\n    if(K<=LAST)\n      goto x10;\n  }\n  else if(M>K) {\n/*         ===============================================================\n           Do row interchange if necessary.\n           =============================================================== */\n    if(L!=K) {\n      IDA1 = DAPOS(L,K);\n      IDA2 = DAPOS(K,K);\n      T = DA[IDA1];\n      DA[IDA1] = DA[IDA2];\n      DA[IDA2] = T;\n    }\n/*         ===============================================================\n           Compute multipliers.\n           Do row elimination with column indexing.\n           =============================================================== */\n    T = -ONE/DA[DAPOS(K,K)];\n    dscal(M-K,T,DA+DAPOS(KP1,K)-LUSOL_ARRAYOFFSET,1);\n    for(J = KP1; J <= LAST; J++) {\n      IDA1 = DAPOS(L,J);\n      T = DA[IDA1];\n      if(L!=K) {\n        IDA2 = DAPOS(K,J);\n        DA[IDA1] = DA[IDA2];\n        DA[IDA2] = T;\n      }\n      daxpy(M-K,T,DA+DAPOS(KP1,K)-LUSOL_ARRAYOFFSET,1,\n                  DA+DAPOS(KP1,J)-LUSOL_ARRAYOFFSET,1);\n    }\n    K++;\n    if(K<=LAST)\n      goto x10;\n  }\n/*      Set ipvt(*) for singular rows. */\n  for(K = LAST+1; K <= M; K++)\n    IPVT[K] = K;\n\n}\n\n\n/* ==================================================================\n   lu1pq1  constructs a permutation  iperm  from the array  len.\n   ------------------------------------------------------------------\n   On entry:\n   len(i)  holds the number of nonzeros in the i-th row (say)\n           of an m by n matrix.\n   num(*)  can be anything (workspace).\n\n   On exit:\n   iperm   contains a list of row numbers in the order\n           rows of length 0,  rows of length 1,..., rows of length n.\n   loc(nz) points to the first row containing  nz  nonzeros,\n           nz = 1, n.\n   inv(i)  points to the position of row i within iperm(*).\n   ================================================================== */\nvoid LU1PQ1(LUSOLrec *LUSOL, int M, int N, int LEN[],\n            int IPERM[], int LOC[], int INV[], int NUM[])\n{\n  int NZEROS, NZ, I, L;\n\n/*      Count the number of rows of each length. */\n  NZEROS = 0;\n  for(NZ = 1; NZ <= N; NZ++) {\n    NUM[NZ] = 0;\n    LOC[NZ] = 0;\n  }\n  for(I = 1; I <= M; I++) {\n    NZ = LEN[I];\n    if(NZ==0)\n      NZEROS++;\n    else\n      NUM[NZ]++;\n  }\n/*      Set starting locations for each length. */\n  L = NZEROS+1;\n  for(NZ = 1; NZ <= N; NZ++) {\n    LOC[NZ] = L;\n    L += NUM[NZ];\n    NUM[NZ] = 0;\n  }\n/*      Form the list. */\n  NZEROS = 0;\n  for(I = 1; I <= M; I++) {\n    NZ = LEN[I];\n    if(NZ==0) {\n      NZEROS++;\n      IPERM[NZEROS] = I;\n    }\n    else {\n      L = LOC[NZ]+NUM[NZ];\n      IPERM[L] = I;\n      NUM[NZ]++;\n    }\n  }\n/*      Define the inverse of iperm. */\n  for(L = 1; L <= M; L++) {\n    I = IPERM[L];\n    INV[I] = L;\n  }\n}\n\n/* ==================================================================\n   lu1pq2 frees the space occupied by the pivot row,\n   and updates the column permutation iq.\n   Also used to free the pivot column and update the row perm ip.\n   ------------------------------------------------------------------\n   nzpiv   (input)    is the length of the pivot row (or column).\n   nzchng  (output)   is the net change in total nonzeros.\n   ------------------------------------------------------------------\n   14 Apr 1989  First version.\n   ================================================================== */\nvoid LU1PQ2(LUSOLrec *LUSOL, int NZPIV, int *NZCHNG,\n            int IND[], int LENOLD[], int LENNEW[], int IXLOC[], int IX[], int IXINV[])\n{\n  int LR, J, NZ, NZNEW, L, NEXT, LNEW, JNEW;\n\n  *NZCHNG = 0;\n  for(LR = 1; LR <= NZPIV; LR++) {\n    J = IND[LR];\n    IND[LR] = 0;\n    NZ = LENOLD[LR];\n    NZNEW = LENNEW[J];\n    if(NZ!=NZNEW) {\n      L = IXINV[J];\n      *NZCHNG = (*NZCHNG+NZNEW)-NZ;\n/*            l above is the position of column j in iq  (so j = iq(l)). */\n      if(NZ<NZNEW) {\n/*               Column  j  has to move towards the end of  iq. */\nx110:\n        NEXT = NZ+1;\n        LNEW = IXLOC[NEXT]-1;\n        if(LNEW!=L) {\n          JNEW = IX[LNEW];\n          IX[L] = JNEW;\n          IXINV[JNEW] = L;\n        }\n        L = LNEW;\n        IXLOC[NEXT] = LNEW;\n        NZ = NEXT;\n        if(NZ<NZNEW)\n          goto x110;\n      }\n      else {\n/*               Column  j  has to move towards the front of  iq. */\nx120:\n        LNEW = IXLOC[NZ];\n        if(LNEW!=L) {\n          JNEW = IX[LNEW];\n          IX[L] = JNEW;\n          IXINV[JNEW] = L;\n        }\n        L = LNEW;\n        IXLOC[NZ] = LNEW+1;\n        NZ = NZ-1;\n        if(NZ>NZNEW)\n          goto x120;\n      }\n      IX[LNEW] = J;\n      IXINV[J] = LNEW;\n    }\n  }\n}\n\n/* ==================================================================\n   lu1pq3  looks at the permutation  iperm(*)  and moves any entries\n   to the end whose corresponding length  len(*)  is zero.\n   ------------------------------------------------------------------\n   09 Feb 1994: Added work array iw(*) to improve efficiency.\n   ================================================================== */\nvoid LU1PQ3(LUSOLrec *LUSOL, int MN, int LEN[], int IPERM[], int IW[], int *NRANK)\n{\n  int NZEROS, K, I;\n\n  *NRANK = 0;\n  NZEROS = 0;\n  for(K = 1; K <= MN; K++) {\n    I = IPERM[K];\n    if(LEN[I]==0) {\n      NZEROS++;\n      IW[NZEROS] = I;\n    }\n    else {\n      (*NRANK)++;\n      IPERM[*NRANK] = I;\n    }\n  }\n  for(K = 1; K <= NZEROS; K++)\n    IPERM[(*NRANK)+K] = IW[K];\n}\n\n/* ==================================================================\n   lu1rec\n   ------------------------------------------------------------------\n   On exit:\n   ltop         is the length of useful entries in ind(*), a(*).\n   ind(ltop+1)  is \"i\" such that len(i), loc(i) belong to the last\n                item in ind(*), a(*).\n   ------------------------------------------------------------------\n   00 Jun 1983: Original version of lu1rec followed John Reid's\n                compression routine in LA05.  It recovered\n                space in ind(*) and optionally a(*)\n                by eliminating entries with ind(l) = 0.\n                The elements of ind(*) could not be negative.\n                If len(i) was positive, entry i contained\n                that many elements, starting at  loc(i).\n                Otherwise, entry i was eliminated.\n   23 Mar 2001: Realised we could have len(i) = 0 in rare cases!\n                (Mostly during TCP when the pivot row contains\n                a column of length 1 that couldn't be a pivot.)\n                Revised storage scheme to\n                   keep        entries with       ind(l) >  0,\n                   squeeze out entries with -n <= ind(l) <= 0,\n                and to allow len(i) = 0.\n                Empty items are moved to the end of the compressed\n                ind(*) and/or a(*) arrays are given one empty space.\n                Items with len(i) < 0 are still eliminated.\n   27 Mar 2001: Decided to use only ind(l) > 0 and = 0 in lu1fad.\n                Still have to keep entries with len(i) = 0.\n   ================================================================== */\nvoid LU1REC(LUSOLrec *LUSOL, int N, MYBOOL REALS, int *LTOP,\n                             int IND[], int LEN[], int LOC[])\n{\n  int  NEMPTY, I, LENI, L, LEND, K, KLAST, ILAST, LPRINT;\n\n  NEMPTY = 0;\n  for(I = 1; I <= N; I++) {\n    LENI = LEN[I];\n    if(LENI>0) {\n      L = (LOC[I]+LENI)-1;\n      LEN[I] = IND[L];\n      IND[L] = -(N+I);\n    }\n    else if(LENI==0)\n      NEMPTY++;\n  }\n  K = 0;\n/*      Previous k */\n  KLAST = 0;\n/*      Last entry moved. */\n  ILAST = 0;\n  LEND = *LTOP;\n  for(L = 1; L <= LEND; L++) {\n    I = IND[L];\n    if(I>0) {\n      K++;\n      IND[K] = I;\n      if(REALS)\n        LUSOL->a[K] = LUSOL->a[L];\n    }\n    else if(I<-N) {\n/*            This is the end of entry  i. */\n      I = -(N+I);\n      ILAST = I;\n      K++;\n      IND[K] = LEN[I];\n      if(REALS)\n        LUSOL->a[K] = LUSOL->a[L];\n      LOC[I] = KLAST+1;\n      LEN[I] = K-KLAST;\n      KLAST = K;\n    }\n  }\n/*      Move any empty items to the end, adding 1 free entry for each. */\n  if(NEMPTY>0) {\n    for(I = 1; I <= N; I++) {\n      if(LEN[I]==0) {\n        K++;\n        LOC[I] = K;\n        IND[K] = 0;\n        ILAST = I;\n      }\n    }\n  }\n  LPRINT = LUSOL->luparm[LUSOL_IP_PRINTLEVEL];\n  if(LPRINT>=LUSOL_MSG_PIVOT)\n    LUSOL_report(LUSOL, 0, \"lu1rec.  File compressed from %d to %d\\n\",\n                        *LTOP,K,REALS,NEMPTY);\n/*      ncp */\n  LUSOL->luparm[LUSOL_IP_COMPRESSIONS_LU]++;\n/*      Return ilast in ind(ltop + 1). */\n  *LTOP = K;\n  IND[(*LTOP)+1] = ILAST;\n}\n\n/* ==================================================================\n   lu1slk  sets w(j) > 0 if column j is a unit vector.\n   ------------------------------------------------------------------\n   21 Nov 2000: First version.  lu1fad needs it for TCP.\n                Note that w(*) is nominally an integer array,\n                but the only spare space is the double array w(*).\n   ================================================================== */\nvoid LU1SLK(LUSOLrec *LUSOL)\n{\n  int J, LC1, LQ, LQ1, LQ2;\n\n  for(J = 1; J <= LUSOL->n; J++) {\n    LUSOL->w[J] = 0;\n  }\n  LQ1 = (LUSOL->iqloc ? LUSOL->iqloc[1] : LUSOL->n+1);\n/*  LQ1 = LUSOL->iqloc[1];   This is the original version; correction above by Yin Zhang */\n  LQ2 = LUSOL->n;\n  if(LUSOL->m>1)\n    LQ2 = LUSOL->iqloc[2]-1;\n  for(LQ = LQ1; LQ <= LQ2; LQ++) {\n    J = LUSOL->iq[LQ];\n    LC1 = LUSOL->locc[J];\n    if(fabs(LUSOL->a[LC1])==1) {\n      LUSOL->w[J] = 1;\n    }\n  }\n}\n\n/* ==================================================================\n   lu1gau does most of the work for each step of Gaussian elimination.\n   A multiple of the pivot column is added to each other column j\n   in the pivot row.  The column list is fully updated.\n   The row list is updated if there is room, but some fill-ins may\n   remain, as indicated by ifill and jfill.\n   ------------------------------------------------------------------\n   Input:\n      ilast    is the row    at the end of the row    list.\n      jlast    is the column at the end of the column list.\n      lfirst   is the first column to be processed.\n      lu + 1   is the corresponding element of U in au(*).\n      nfill    keeps track of pending fill-in.\n      a(*)     contains the nonzeros for each column j.\n      indc(*)  contains the row indices for each column j.\n      al(*)    contains the new column of L.  A multiple of it is\n               used to modify each column.\n      mark(*)  has been set to -1, -2, -3, ... in the rows\n               corresponding to nonzero 1, 2, 3, ... of the col of L.\n      au(*)    contains the new row of U.  Each nonzero gives the\n               required multiple of the column of L.\n\n   Workspace:\n      markl(*) marks the nonzeros of L actually used.\n               (A different mark, namely j, is used for each column.)\n\n   Output:\n      ilast     New last row    in the row    list.\n      jlast     New last column in the column list.\n      lfirst    = 0 if all columns were completed,\n                > 0 otherwise.\n      lu        returns the position of the last nonzero of U\n                actually used, in case we come back in again.\n      nfill     keeps track of the total extra space needed in the\n                row file.\n      ifill(ll) counts pending fill-in for rows involved in the new\n                column of L.\n      jfill(lu) marks the first pending fill-in stored in columns\n                involved in the new row of U.\n   ------------------------------------------------------------------\n   16 Apr 1989: First version of lu1gau.\n   23 Apr 1989: lfirst, lu, nfill are now input and output\n                to allow re-entry if elimination is interrupted.\n   23 Mar 2001: Introduced ilast, jlast.\n   27 Mar 2001: Allow fill-in \"in situ\" if there is already room\n                up to but NOT INCLUDING the end of the\n                row or column file.\n                Seems safe way to avoid overwriting empty rows/cols\n                at the end.  (May not be needed though, now that we\n                have ilast and jlast.)\n   ================================================================== */\nvoid LU1GAU(LUSOLrec *LUSOL, int MELIM, int NSPARE,\n            REAL SMALL, int LPIVC1, int LPIVC2, int *LFIRST, int LPIVR2,\n            int LFREE, int MINFRE, int ILAST, int *JLAST, int *LROW, int *LCOL,\n            int *LU, int *NFILL,\n            int MARK[],  REAL AL[], int MARKL[], REAL AU[], int IFILL[], int JFILL[])\n{\n  MYBOOL ATEND;\n  int    LR, J, LENJ, NFREE, LC1, LC2, NDONE, NDROP, L, I, LL, K,\n         LR1, LAST, LREP, L1, L2, LC, LENI;\n  register REAL UJ;\n  REAL   AIJ;\n\n  for(LR = *LFIRST; LR <= LPIVR2; LR++) {\n    J = LUSOL->indr[LR];\n    LENJ = LUSOL->lenc[J];\n    NFREE = LFREE - *LCOL;\n    if(NFREE<MINFRE)\n      goto x900;\n/*         ---------------------------------------------------------------\n           Inner loop to modify existing nonzeros in column  j.\n           Loop 440 performs most of the arithmetic involved in the\n           whole LU factorization.\n           ndone counts how many multipliers were used.\n           ndrop counts how many modified nonzeros are negligibly small.\n           --------------------------------------------------------------- */\n    (*LU)++;\n    UJ = AU[*LU];\n    LC1 = LUSOL->locc[J];\n    LC2 = (LC1+LENJ)-1;\n    ATEND = (MYBOOL) (J==*JLAST);\n    NDONE = 0;\n    if(LENJ==0)\n      goto x500;\n    NDROP = 0;\n    for(L = LC1; L <= LC2; L++) {\n      I = LUSOL->indc[L];\n      LL = -MARK[I];\n      if(LL>0) {\n        NDONE++;\n        MARKL[LL] = J;\n        LUSOL->a[L] += AL[LL]*UJ;\n        if(fabs(LUSOL->a[L])<=SMALL) {\n          NDROP++;\n        }\n      }\n    }\n/*         ---------------------------------------------------------------\n           Remove any negligible modified nonzeros from both\n           the column file and the row file.\n           --------------------------------------------------------------- */\n    if(NDROP==0)\n      goto x500;\n    K = LC1;\n    for(L = LC1; L <= LC2; L++) {\n      I = LUSOL->indc[L];\n      if(fabs(LUSOL->a[L])<=SMALL)\n        goto x460;\n      LUSOL->a[K] = LUSOL->a[L];\n      LUSOL->indc[K] = I;\n      K++;\n      continue;\n/*            Delete the nonzero from the row file. */\nx460:\n      LENJ--;\n      LUSOL->lenr[I]--;\n      LR1 = LUSOL->locr[I];\n      LAST = LR1+LUSOL->lenr[I];\n      for(LREP = LR1; LREP <= LAST; LREP++) {\n        if(LUSOL->indr[LREP]==J)\n          break;\n      }\n      LUSOL->indr[LREP] = LUSOL->indr[LAST];\n      LUSOL->indr[LAST] = 0;\n      if(I==ILAST)\n        (*LROW)--;\n    }\n/*         Free the deleted elements from the column file. */\n#ifdef LUSOLFastClear\n    MEMCLEAR(LUSOL->indc+K, LC2-K+1);\n#else\n    for(L = K; L <= LC2; L++)\n      LUSOL->indc[L] = ZERO;\n#endif\n    if(ATEND)\n      *LCOL = K-1;\n/*         ---------------------------------------------------------------\n           Deal with the fill-in in column j.\n           --------------------------------------------------------------- */\nx500:\n    if(NDONE==MELIM)\n      goto x590;\n/*         See if column j already has room for the fill-in. */\n    if(ATEND)\n      goto x540;\n    LAST = (LC1+LENJ)-1;\n    L1 = LAST+1;\n    L2 = (LAST+MELIM)-NDONE;\n/*      27 Mar 2001: Be sure it's not at or past end of the col file. */\n    if(L2>=*LCOL)\n      goto x520;\n    for(L = L1; L <= L2; L++) {\n      if(LUSOL->indc[L]!=0)\n        goto x520;\n    }\n    goto x540;\n/*         We must move column j to the end of the column file.\n           First, leave some spare room at the end of the\n           current last column. */\nx520:\n#if 1\n    L1 = (*LCOL)+1;\n    L2 = (*LCOL)+NSPARE;\n    *LCOL = L2;\n    for(L = L1; L <= L2; L++) {\n#else\n    for(L = (*LCOL)+1; L <= (*LCOL)+NSPARE; L++) {\n      *LCOL = L;  /* ****** ERROR ???? */\n#endif\n/*      Spare space is free. */\n      LUSOL->indc[L] = 0;\n    }\n    ATEND = TRUE;\n    *JLAST = J;\n    L1 = LC1;\n    L2 = *LCOL;\n    LC1 = L2+1;\n    LUSOL->locc[J] = LC1;\n    for(L = L1; L <= LAST; L++) {\n      L2++;\n      LUSOL->a[L2] = LUSOL->a[L];\n      LUSOL->indc[L2] = LUSOL->indc[L];\n/*      Free space. */\n      LUSOL->indc[L] = 0;\n    }\n    *LCOL = L2;\n/*         ---------------------------------------------------------------\n           Inner loop for the fill-in in column j.\n           This is usually not very expensive.\n           --------------------------------------------------------------- */\nx540:\n    LAST = (LC1+LENJ)-1;\n    LL = 0;\n    for(LC = LPIVC1; LC <= LPIVC2; LC++) {\n      LL++;\n      if(MARKL[LL]==J)\n        continue;\n      AIJ = AL[LL]*UJ;\n      if(fabs(AIJ)<=SMALL)\n        continue;\n      LENJ++;\n      LAST++;\n      LUSOL->a[LAST] = AIJ;\n      I = LUSOL->indc[LC];\n      LUSOL->indc[LAST] = I;\n      LENI = LUSOL->lenr[I];\n/*            Add 1 fill-in to row i if there is already room.\n              27 Mar 2001: Be sure it's not at or past the }\n                           of the row file. */\n      L = LUSOL->locr[I]+LENI;\n      if(L>=*LROW)\n        goto x550;\n      if(LUSOL->indr[L]>0)\n        goto x550;\n      LUSOL->indr[L] = J;\n      LUSOL->lenr[I] = LENI+1;\n      continue;\n/*            Row i does not have room for the fill-in.\n              Increment ifill(ll) to count how often this has\n              happened to row i.  Also, add m to the row index\n              indc(last) in column j to mark it as a fill-in that is\n              still pending.\n              If this is the first pending fill-in for row i,\n              nfill includes the current length of row i\n              (since the whole row has to be moved later).\n              If this is the first pending fill-in for column j,\n              jfill(lu) records the current length of column j\n              (to shorten the search for pending fill-ins later). */\nx550:\n      if(IFILL[LL]==0)\n        (*NFILL) += LENI+NSPARE;\n      if(JFILL[*LU]==0)\n        JFILL[*LU] = LENJ;\n      (*NFILL)++;\n      IFILL[LL]++;\n      LUSOL->indc[LAST] = LUSOL->m+I;\n    }\n    if(ATEND)\n      *LCOL = LAST;\n/*         End loop for column  j.  Store its final length. */\nx590:\n    LUSOL->lenc[J] = LENJ;\n  }\n/*      Successful completion. */\n  *LFIRST = 0;\n  return;\n/*      Interruption.  We have to come back in after the\n        column file is compressed.  Give lfirst a new value.\n        lu and nfill will retain their current values. */\nx900:\n  *LFIRST = LR;\n}\n\n/* ==================================================================\n   lu1mar  uses a Markowitz criterion to select a pivot element\n   for the next stage of a sparse LU factorization,\n   subject to a Threshold Partial Pivoting stability criterion (TPP)\n   that bounds the elements of L.\n   ------------------------------------------------------------------\n   gamma  is \"gamma\" in the tie-breaking rule TB4 in the LUSOL paper.\n   ------------------------------------------------------------------\n   Search cols of length nz = 1, then rows of length nz = 1,\n   then   cols of length nz = 2, then rows of length nz = 2, etc.\n   ------------------------------------------------------------------\n   00 Jan 1986  Version documented in LUSOL paper:\n                Gill, Murray, Saunders and Wright (1987),\n                Maintaining LU factors of a general sparse matrix,\n                Linear algebra and its applications 88/89, 239-270.\n   02 Feb 1989  Following Suhl and Aittoniemi (1987), the largest\n                element in each column is now kept at the start of\n                the column, i.e. in position locc(j) of a and indc.\n                This should speed up the Markowitz searches.\n   26 Apr 1989  Both columns and rows searched during spars1 phase.\n                Only columns searched during spars2 phase.\n                maxtie replaced by maxcol and maxrow.\n   05 Nov 1993  Initializing  \"mbest = m * n\"  wasn't big enough when\n                m = 10, n = 3, and last column had 7 nonzeros.\n   09 Feb 1994  Realised that \"mbest = maxmn * maxmn\" might overflow.\n                Changed to    \"mbest = maxmn * 1000\".\n   27 Apr 2000  On large example from Todd Munson,\n                that allowed  \"if (mbest .le. nz1**2) go to 900\"\n                to exit before any pivot had been found.\n                Introduced kbest = mbest / nz1.\n                Most pivots can be rejected with no integer multiply.\n                TRUE merit is evaluated only if it's as good as the\n                best so far (or better).  There should be no danger\n                of integer overflow unless A is incredibly\n                large and dense.\n   10 Sep 2000  TCP, aijtol added for Threshold Complete Pivoting.\n   ================================================================== */\nvoid LU1MAR(LUSOLrec *LUSOL, int MAXMN, MYBOOL TCP, REAL AIJTOL, REAL LTOL,\n            int MAXCOL, int MAXROW, int *IBEST, int *JBEST, int *MBEST)\n{\n  int  KBEST, NCOL, NROW, NZ1, NZ, LQ1, LQ2, LQ, J, LC1, LC2, LC, I, LEN1, MERIT, LP1,\n       LP2, LP, LR1, LR2, LR;\n  REAL ABEST, LBEST, AMAX, AIJ, CMAX;\n\n  ABEST = ZERO;\n  LBEST = ZERO;\n  *IBEST = 0;\n  *MBEST = -1;\n  KBEST = MAXMN+1;\n  NCOL = 0;\n  NROW = 0;\n  NZ1 = 0;\n  for(NZ = 1; NZ <= MAXMN; NZ++) {\n/*         nz1    = nz - 1\n           if (mbest .le. nz1**2) go to 900 */\n    if(KBEST<=NZ1)\n      goto x900;\n    if(*IBEST>0) {\n      if(NCOL>=MAXCOL)\n        goto x200;\n    }\n    if(NZ>LUSOL->m)\n      goto x200;\n/*         ---------------------------------------------------------------\n           Search the set of columns of length  nz.\n           --------------------------------------------------------------- */\n    LQ1 = LUSOL->iqloc[NZ];\n    LQ2 = LUSOL->n;\n    if(NZ<LUSOL->m)\n      LQ2 = LUSOL->iqloc[NZ+1]-1;\n    for(LQ = LQ1; LQ <= LQ2; LQ++) {\n      NCOL = NCOL+1;\n      J = LUSOL->iq[LQ];\n      LC1 = LUSOL->locc[J];\n      LC2 = LC1+NZ1;\n      AMAX = fabs(LUSOL->a[LC1]);\n/*            Test all aijs in this column.\n              amax is the largest element (the first in the column).\n              cmax is the largest multiplier if aij becomes pivot. */\n      if(TCP) {\n/*      Nothing in whole column */\n        if(AMAX<AIJTOL)\n          continue;\n      }\n      for(LC = LC1; LC <= LC2; LC++) {\n        I = LUSOL->indc[LC];\n        LEN1 = LUSOL->lenr[I]-1;\n/*               merit  = nz1 * len1\n                 if (merit > mbest) continue; */\n        if(LEN1>KBEST)\n          continue;\n/*               aij  has a promising merit.\n                 Apply the stability test.\n                 We require  aij  to be sufficiently large compared to\n                 all other nonzeros in column  j.  This is equivalent\n                 to requiring cmax to be bounded by Ltol. */\n        if(LC==LC1) {\n/*                  This is the maximum element, amax.\n                    Find the biggest element in the rest of the column\n                    and hence get cmax.  We know cmax .le. 1, but\n                    we still want it exactly in order to break ties.\n                    27 Apr 2002: Settle for cmax = 1. */\n          AIJ = AMAX;\n          CMAX = ONE;\n/*                  cmax   = zero\n                    for (l = lc1 + 1; l <= lc2; l++)\n                       cmax  = max( cmax, abs( a(l) ) );\n                    cmax   = cmax / amax; */\n        }\n        else {\n/*                  aij is not the biggest element, so cmax .ge. 1.\n                    Bail out if cmax will be too big. */\n          AIJ = fabs(LUSOL->a[LC]);\n/*      Absolute test for Complete Pivoting */\n          if(TCP) {\n            if(AIJ<AIJTOL)\n              continue;\n/*      TPP */\n          }\n          else {\n            if(AIJ*LTOL<AMAX)\n              continue;\n          }\n          CMAX = AMAX/AIJ;\n        }\n/*               aij  is big enough.  Its maximum multiplier is cmax. */\n        MERIT = NZ1*LEN1;\n        if(MERIT==*MBEST) {\n/*                  Break ties.\n                    (Initializing mbest < 0 prevents getting here if\n                    nothing has been found yet.)\n                    In this version we minimize cmax\n                    but if it is already small we maximize the pivot. */\n          if(LBEST<=LUSOL->parmlu[LUSOL_RP_GAMMA] &&\n             CMAX<=LUSOL->parmlu[LUSOL_RP_GAMMA]) {\n            if(ABEST>=AIJ)\n              continue;\n          }\n          else {\n            if(LBEST<=CMAX)\n              continue;\n          }\n        }\n/*               aij  is the best pivot so far. */\n        *IBEST = I;\n        *JBEST = J;\n        KBEST = LEN1;\n        *MBEST = MERIT;\n        ABEST = AIJ;\n        LBEST = CMAX;\n        if(NZ==1)\n          goto x900;\n      }\n/*            Finished with that column. */\n      if(*IBEST>0) {\n        if(NCOL>=MAXCOL)\n          goto x200;\n      }\n    }\n/*         ---------------------------------------------------------------\n           Search the set of rows of length  nz.\n           --------------------------------------------------------------- */\nx200:\n/*    if (mbest .le. nz*nz1) go to 900 */\n    if(KBEST<=NZ)\n      goto x900;\n    if(*IBEST>0) {\n      if(NROW>=MAXROW)\n        goto x290;\n    }\n    if(NZ>LUSOL->n)\n      goto x290;\n    LP1 = LUSOL->iploc[NZ];\n    LP2 = LUSOL->m;\n    if(NZ<LUSOL->n)\n      LP2 = LUSOL->iploc[NZ+1]-1;\n    for(LP = LP1; LP <= LP2; LP++) {\n      NROW++;\n      I = LUSOL->ip[LP];\n      LR1 = LUSOL->locr[I];\n      LR2 = LR1+NZ1;\n      for(LR = LR1; LR <= LR2; LR++) {\n        J = LUSOL->indr[LR];\n        LEN1 = LUSOL->lenc[J]-1;\n/*               merit  = nz1 * len1\n                 if (merit .gt. mbest) continue */\n        if(LEN1>KBEST)\n          continue;\n/*               aij  has a promising merit.\n                 Find where  aij  is in column  j. */\n        LC1 = LUSOL->locc[J];\n        LC2 = LC1+LEN1;\n        AMAX = fabs(LUSOL->a[LC1]);\n        for(LC = LC1; LC <= LC2; LC++) {\n          if(LUSOL->indc[LC]==I)\n            break;\n        }\n/*               Apply the same stability test as above. */\n        AIJ = fabs(LUSOL->a[LC]);\n/*      Absolute test for Complete Pivoting */\n        if(TCP) {\n          if(AIJ<AIJTOL)\n            continue;\n        }\n        if(LC==LC1) {\n/*                  This is the maximum element, amax.\n                    Find the biggest element in the rest of the column\n                    and hence get cmax.  We know cmax .le. 1, but\n                    we still want it exactly in order to break ties.\n                    27 Apr 2002: Settle for cmax = 1. */\n          CMAX = ONE;\n/*                  cmax   = zero\n                    for(l = lc1 + 1; l <= lc2; l++)\n                       cmax  = max( cmax, fabs( a(l) ) )\n                    cmax   = cmax / amax */\n        }\n        else {\n/*                  aij is not the biggest element, so cmax .ge. 1.\n                    Bail out if cmax will be too big. */\n          if(TCP) {\n/*      relax */\n          }\n          else {\n            if(AIJ*LTOL<AMAX)\n              continue;\n          }\n          CMAX = AMAX/AIJ;\n        }\n/*               aij  is big enough.  Its maximum multiplier is cmax. */\n        MERIT = NZ1*LEN1;\n        if(MERIT==*MBEST) {\n/*                  Break ties as before.\n                    (Initializing mbest < 0 prevents getting here if\n                    nothing has been found yet.) */\n          if(LBEST<=LUSOL->parmlu[LUSOL_RP_GAMMA] &&\n             CMAX<=LUSOL->parmlu[LUSOL_RP_GAMMA]) {\n            if(ABEST>=AIJ)\n              continue;\n          }\n          else {\n            if(LBEST<=CMAX)\n              continue;\n          }\n        }\n/*               aij  is the best pivot so far. */\n        *IBEST = I;\n        *JBEST = J;\n        *MBEST = MERIT;\n        KBEST = LEN1;\n        ABEST = AIJ;\n        LBEST = CMAX;\n        if(NZ==1)\n          goto x900;\n      }\n/*            Finished with that row. */\n      if(*IBEST>0) {\n        if(NROW>=MAXROW)\n          goto x290;\n      }\n    }\n/*         See if it's time to quit. */\nx290:\n    if(*IBEST>0) {\n      if(NROW>=MAXROW && NCOL>=MAXCOL)\n        goto x900;\n    }\n/*         Press on with next nz. */\n    NZ1 = NZ;\n    if(*IBEST>0)\n      KBEST = *MBEST/NZ1;\n  }\nx900:\n;\n}\n\n/* ==================================================================\n   lu1mCP  uses a Markowitz criterion to select a pivot element\n   for the next stage of a sparse LU factorization,\n   subject to a Threshold Complete Pivoting stability criterion (TCP)\n   that bounds the elements of L and U.\n   ------------------------------------------------------------------\n   gamma  is \"gamma\" in the tie-breaking rule TB4 in the LUSOL paper.\n   ------------------------------------------------------------------\n   09 May 2002: First version of lu1mCP.\n                It searches columns only, using the heap that\n                holds the largest element in each column.\n   09 May 2002: Current version of lu1mCP.\n   ================================================================== */\nvoid LU1MCP(LUSOLrec *LUSOL, REAL AIJTOL, int *IBEST, int *JBEST, int *MBEST,\n            int HLEN, REAL HA[], int HJ[])\n{\n  int  J, KHEAP, LC, LC1, LC2, LENJ, MAXCOL, NCOL, NZ1, I, LEN1, MERIT;\n  REAL ABEST, AIJ, AMAX, CMAX, LBEST;\n\n/*      ------------------------------------------------------------------\n        Search up to maxcol columns stored at the top of the heap.\n        The very top column helps initialize mbest.\n        ------------------------------------------------------------------ */\n  ABEST = ZERO;\n  LBEST = ZERO;\n  *IBEST = 0;\n/*      Column at the top of the heap */\n  *JBEST = HJ[1];\n  LENJ = LUSOL->lenc[*JBEST];\n/*      Bigger than any possible merit */\n  *MBEST = LENJ*HLEN;\n/*      ??? Big question */\n  MAXCOL = 40;\n/*      No. of columns searched */\n  NCOL = 0;\n  for(KHEAP = 1; KHEAP <= HLEN; KHEAP++) {\n    AMAX = HA[KHEAP];\n    if(AMAX<AIJTOL)\n      continue;\n    NCOL++;\n    J = HJ[KHEAP];\n/*         ---------------------------------------------------------------\n           This column has at least one entry big enough (the top one).\n           Search the column for other possibilities.\n           --------------------------------------------------------------- */\n    LENJ = LUSOL->lenc[J];\n    NZ1 = LENJ-1;\n    LC1 = LUSOL->locc[J];\n    LC2 = LC1+NZ1;\n/* --      amax   = abs( a(lc1) )\n           Test all aijs in this column.\n           amax is the largest element (the first in the column).\n           cmax is the largest multiplier if aij becomes pivot. */\n    for(LC = LC1; LC <= LC2; LC++) {\n      I = LUSOL->indc[LC];\n      LEN1 = LUSOL->lenr[I]-1;\n      MERIT = NZ1*LEN1;\n      if(MERIT>*MBEST)\n        continue;\n/*            aij  has a promising merit. */\n      if(LC==LC1) {\n/*               This is the maximum element, amax.\n                 Find the biggest element in the rest of the column\n                 and hence get cmax.  We know cmax .le. 1, but\n                 we still want it exactly in order to break ties.\n                 27 Apr 2002: Settle for cmax = 1. */\n        AIJ = AMAX;\n        CMAX = ONE;\n/*               cmax   = ZERO;\n                 for(l = lc1 + 1; l <= lc2; l++)\n                    cmax  = max( cmax, abs( a(l) ) )\n                 cmax   = cmax / amax; */\n      }\n      else {\n/*               aij is not the biggest element, so cmax .ge. 1.\n                 Bail out if cmax will be too big. */\n        AIJ = fabs(LUSOL->a[LC]);\n        if(AIJ<AIJTOL)\n          continue;\n        CMAX = AMAX/AIJ;\n      }\n/*            aij  is big enough.  Its maximum multiplier is cmax. */\n      if(MERIT==*MBEST) {\n/*               Break ties.\n                 (Initializing mbest \"too big\" prevents getting here if\n                 nothing has been found yet.)\n                 In this version we minimize cmax\n                 but if it is already small we maximize the pivot. */\n        if(LBEST<=LUSOL->parmlu[LUSOL_RP_GAMMA] &&\n           CMAX<=LUSOL->parmlu[LUSOL_RP_GAMMA]) {\n          if(ABEST>=AIJ)\n            continue;\n        }\n        else {\n          if(LBEST<=CMAX)\n            continue;\n        }\n      }\n/*            aij  is the best pivot so far. */\n      *IBEST = I;\n      *JBEST = J;\n      *MBEST = MERIT;\n      ABEST = AIJ;\n      LBEST = CMAX;\n/*      Col or row of length 1 */\n      if(MERIT==0)\n        goto x900;\n    }\n    if(NCOL>=MAXCOL)\n      goto x900;\n  }\nx900:\n;\n}\n\n/* ==================================================================\n   lu1mRP  uses a Markowitz criterion to select a pivot element\n   for the next stage of a sparse LU factorization,\n   subject to a Threshold Rook Pivoting stability criterion (TRP)\n   that bounds the elements of L and U.\n   ------------------------------------------------------------------\n   11 Jun 2002: First version of lu1mRP derived from lu1mar.\n   11 Jun 2002: Current version of lu1mRP.\n   ================================================================== */\nvoid LU1MRP(LUSOLrec *LUSOL, int MAXMN, REAL LTOL, int MAXCOL, int MAXROW,\n  int *IBEST, int *JBEST, int *MBEST, REAL AMAXR[])\n{\n  int  I, J, KBEST, LC, LC1, LC2, LEN1, LP, LP1, LP2, LQ, LQ1,\n       LQ2, LR, LR1, LR2, MERIT, NCOL, NROW, NZ, NZ1;\n  REAL ABEST, AIJ, AMAX, ATOLI, ATOLJ;\n\n/*      ------------------------------------------------------------------\n        Search cols of length nz = 1, then rows of length nz = 1,\n        then   cols of length nz = 2, then rows of length nz = 2, etc.\n        ------------------------------------------------------------------ */\n  ABEST = ZERO;\n  *IBEST = 0;\n  KBEST = MAXMN+1;\n  *MBEST = -1;\n  NCOL = 0;\n  NROW = 0;\n  NZ1 = 0;\n  for(NZ = 1; NZ <= MAXMN; NZ++) {\n/*         nz1    = nz - 1\n           if (mbest .le. nz1**2) go to 900 */\n    if(KBEST<=NZ1)\n      goto x900;\n    if(*IBEST>0) {\n      if(NCOL>=MAXCOL)\n        goto x200;\n    }\n    if(NZ>LUSOL->m)\n      goto x200;\n/*         ---------------------------------------------------------------\n           Search the set of columns of length  nz.\n           --------------------------------------------------------------- */\n    LQ1 = LUSOL->iqloc[NZ];\n    LQ2 = LUSOL->n;\n    if(NZ<LUSOL->m)\n      LQ2 = LUSOL->iqloc[NZ+1]-1;\n    for(LQ = LQ1; LQ <= LQ2; LQ++) {\n      NCOL = NCOL+1;\n      J = LUSOL->iq[LQ];\n      LC1 = LUSOL->locc[J];\n      LC2 = LC1+NZ1;\n      AMAX = fabs(LUSOL->a[LC1]);\n/*      Min size of pivots in col j */\n      ATOLJ = AMAX/LTOL;\n/*            Test all aijs in this column. */\n      for(LC = LC1; LC <= LC2; LC++) {\n        I = LUSOL->indc[LC];\n        LEN1 = LUSOL->lenr[I]-1;\n/*               merit  = nz1 * len1\n                 if (merit .gt. mbest) continue; */\n        if(LEN1>KBEST)\n          continue;\n/*               aij  has a promising merit.\n                 Apply the Threshold Rook Pivoting stability test.\n                 First we require aij to be sufficiently large\n                 compared to other nonzeros in column j.\n                 Then  we require aij to be sufficiently large\n                 compared to other nonzeros in row    i. */\n        AIJ = fabs(LUSOL->a[LC]);\n        if(AIJ<ATOLJ)\n          continue;\n        if(AIJ*LTOL<AMAXR[I])\n          continue;\n/*               aij  is big enough. */\n        MERIT = NZ1*LEN1;\n        if(MERIT==*MBEST) {\n/*                  Break ties.\n                    (Initializing mbest < 0 prevents getting here if\n                    nothing has been found yet.) */\n          if(ABEST>=AIJ)\n            continue;\n        }\n/*               aij  is the best pivot so far. */\n        *IBEST = I;\n        *JBEST = J;\n        KBEST = LEN1;\n        *MBEST = MERIT;\n        ABEST = AIJ;\n        if(NZ==1)\n          goto x900;\n      }\n/*            Finished with that column. */\n      if(*IBEST>0) {\n        if(NCOL>=MAXCOL)\n          goto x200;\n      }\n    }\n/*         ---------------------------------------------------------------\n           Search the set of rows of length  nz.\n           --------------------------------------------------------------- */\nx200:\n/*    if (mbest .le. nz*nz1) go to 900 */\n    if(KBEST<=NZ)\n      goto x900;\n    if(*IBEST>0) {\n      if(NROW>=MAXROW)\n        goto x290;\n    }\n    if(NZ>LUSOL->n)\n      goto x290;\n    LP1 = LUSOL->iploc[NZ];\n    LP2 = LUSOL->m;\n    if(NZ<LUSOL->n)\n      LP2 = LUSOL->iploc[NZ+1]-1;\n    for(LP = LP1; LP <= LP2; LP++) {\n      NROW = NROW+1;\n      I = LUSOL->ip[LP];\n      LR1 = LUSOL->locr[I];\n      LR2 = LR1+NZ1;\n/*      Min size of pivots in row i */\n      ATOLI = AMAXR[I]/LTOL;\n      for(LR = LR1; LR <= LR2; LR++) {\n        J = LUSOL->indr[LR];\n        LEN1 = LUSOL->lenc[J]-1;\n/*               merit  = nz1 * len1\n                 if (merit .gt. mbest) continue; */\n        if(LEN1>KBEST)\n          continue;\n/*               aij  has a promising merit.\n                 Find where  aij  is in column j. */\n        LC1 = LUSOL->locc[J];\n        LC2 = LC1+LEN1;\n        AMAX = fabs(LUSOL->a[LC1]);\n        for(LC = LC1; LC <= LC2; LC++) {\n          if(LUSOL->indc[LC]==I)\n            break;\n        }\n/*               Apply the Threshold Rook Pivoting stability test.\n                 First we require aij to be sufficiently large\n                 compared to other nonzeros in row    i.\n                 Then  we require aij to be sufficiently large\n                 compared to other nonzeros in column j. */\n        AIJ = fabs(LUSOL->a[LC]);\n        if(AIJ<ATOLI)\n          continue;\n        if(AIJ*LTOL<AMAX)\n          continue;\n/*               aij  is big enough. */\n        MERIT = NZ1*LEN1;\n        if(MERIT==*MBEST) {\n/*                  Break ties as before.\n                    (Initializing mbest < 0 prevents getting here if\n                    nothing has been found yet.) */\n          if(ABEST>=AIJ)\n            continue;\n        }\n/*               aij  is the best pivot so far. */\n        *IBEST = I;\n        *JBEST = J;\n        KBEST = LEN1;\n        *MBEST = MERIT;\n        ABEST = AIJ;\n        if(NZ==1)\n          goto x900;\n      }\n/*            Finished with that row. */\n      if(*IBEST>0) {\n        if(NROW>=MAXROW)\n          goto x290;\n      }\n    }\n/*         See if it's time to quit. */\nx290:\n    if(*IBEST>0) {\n      if(NROW>=MAXROW && NCOL>=MAXCOL)\n        goto x900;\n    }\n/*         Press on with next nz. */\n    NZ1 = NZ;\n    if(*IBEST>0)\n      KBEST = *MBEST/NZ1;\n  }\nx900:\n;\n}\n\n/* ==================================================================\n   lu1mSP  is intended for symmetric matrices that are either\n   definite or quasi-definite.\n   lu1mSP  uses a Markowitz criterion to select a pivot element for\n   the next stage of a sparse LU factorization of a symmetric matrix,\n   subject to a Threshold Symmetric Pivoting stability criterion\n   (TSP) restricted to diagonal elements to preserve symmetry.\n   This bounds the elements of L and U and should have rank-revealing\n   properties analogous to Threshold Rook Pivoting for unsymmetric\n   matrices.\n   ------------------------------------------------------------------\n   14 Dec 2002: First version of lu1mSP derived from lu1mRP.\n                There is no safeguard to ensure that A is symmetric.\n   14 Dec 2002: Current version of lu1mSP.\n   ================================================================== */\nvoid LU1MSP(LUSOLrec *LUSOL, int MAXMN, REAL LTOL, int MAXCOL,\n            int *IBEST, int *JBEST, int *MBEST)\n{\n  int  I, J, KBEST, LC, LC1, LC2, LQ, LQ1, LQ2, MERIT, NCOL, NZ, NZ1;\n  REAL ABEST, AIJ, AMAX, ATOLJ;\n\n/*      ------------------------------------------------------------------\n        Search cols of length nz = 1, then cols of length nz = 2, etc.\n        ------------------------------------------------------------------ */\n  ABEST = ZERO;\n  *IBEST = 0;\n  *MBEST = -1;\n  KBEST = MAXMN+1;\n  NCOL = 0;\n  NZ1 = 0;\n  for(NZ = 1; NZ <= MAXMN; NZ++) {\n/*         nz1    = nz - 1\n           if (mbest .le. nz1**2) go to 900 */\n    if(KBEST<=NZ1)\n      goto x900;\n    if(*IBEST>0) {\n      if(NCOL>=MAXCOL)\n        goto x200;\n    }\n    if(NZ>LUSOL->m)\n      goto x200;\n/*         ---------------------------------------------------------------\n           Search the set of columns of length  nz.\n           --------------------------------------------------------------- */\n    LQ1 = LUSOL->iqloc[NZ];\n    LQ2 = LUSOL->n;\n    if(NZ<LUSOL->m)\n      LQ2 = LUSOL->iqloc[NZ+1]-1;\n    for(LQ = LQ1; LQ <= LQ2; LQ++) {\n      NCOL++;\n      J = LUSOL->iq[LQ];\n      LC1 = LUSOL->locc[J];\n      LC2 = LC1+NZ1;\n      AMAX = fabs(LUSOL->a[LC1]);\n/*      Min size of pivots in col j */\n      ATOLJ = AMAX/LTOL;\n/*            Test all aijs in this column.\n              Ignore everything except the diagonal. */\n      for(LC = LC1; LC <= LC2; LC++) {\n        I = LUSOL->indc[LC];\n/*      Skip off-diagonals. */\n        if(I!=J)\n          continue;\n/*               merit  = nz1 * nz1\n                 if (merit .gt. mbest) continue; */\n        if(NZ1>KBEST)\n          continue;\n/*               aij  has a promising merit.\n                 Apply the Threshold Partial Pivoting stability test\n                 (which is equivalent to Threshold Rook Pivoting for\n                 symmetric matrices).\n                 We require aij to be sufficiently large\n                 compared to other nonzeros in column j. */\n        AIJ = fabs(LUSOL->a[LC]);\n        if(AIJ<ATOLJ)\n          continue;\n/*               aij  is big enough. */\n        MERIT = NZ1*NZ1;\n        if(MERIT==*MBEST) {\n/*                  Break ties.\n                    (Initializing mbest < 0 prevents getting here if\n                    nothing has been found yet.) */\n          if(ABEST>=AIJ)\n            continue;\n        }\n/*               aij  is the best pivot so far. */\n        *IBEST = I;\n        *JBEST = J;\n        KBEST = NZ1;\n        *MBEST = MERIT;\n        ABEST = AIJ;\n        if(NZ==1)\n          goto x900;\n      }\n/*            Finished with that column. */\n      if(*IBEST>0) {\n        if(NCOL>=MAXCOL)\n          goto x200;\n      }\n    }\n/*         See if it's time to quit. */\nx200:\n    if(*IBEST>0) {\n      if(NCOL>=MAXCOL)\n        goto x900;\n    }\n/*         Press on with next nz. */\n    NZ1 = NZ;\n    if(*IBEST>0)\n      KBEST = *MBEST/NZ1;\n  }\nx900:\n;\n}\n\n/* ==================================================================\n   lu1mxc  moves the largest element in each of columns iq(k1:k2)\n   to the top of its column.\n   If k1 > k2, nothing happens.\n   ------------------------------------------------------------------\n   06 May 2002: (and earlier)\n                All columns k1:k2 must have one or more elements.\n   07 May 2002: Allow for empty columns.  The heap routines need to\n                find 0.0 as the \"largest element\".\n   29 Nov 2005: Bug fix - avoiding overwriting the next column when\n                the current column is empty (i.e. LENJ==0)\n                Yin Zhang <yzhang@cs.utexas.edu>\n   ================================================================== */\nvoid LU1MXC(LUSOLrec *LUSOL, int K1, int K2, int IX[])\n{\n  int  I, J, K, L, LC, LENJ;\n  REAL AMAX;\n\n  for(K = K1; K <= K2; K++) {\n    J = IX[K];\n    LC = LUSOL->locc[J];\n    LENJ = LUSOL->lenc[J];\n    if(LENJ==0)\n/*      LUSOL->a[LC] = ZERO;  Removal suggested by Yin Zhang to avoid overwriting next column when current is empty */\n      ;\n    else {\n      L = idamax(LUSOL->lenc[J], LUSOL->a + LC - LUSOL_ARRAYOFFSET,1) + LC - 1;\n      if(L>LC) {\n        AMAX = LUSOL->a[L];\n        LUSOL->a[L] = LUSOL->a[LC];\n        LUSOL->a[LC] = AMAX;\n        I = LUSOL->indc[L];\n        LUSOL->indc[L] = LUSOL->indc[LC];\n        LUSOL->indc[LC] = I;\n      }\n    }\n  }\n}\n\n/* ==================================================================\n   lu1mxr  finds the largest element in each of row ip(k1:k2)\n   and stores it in Amaxr(*).  The nonzeros are stored column-wise\n   in (a,indc,lenc,locc) and their structure is row-wise\n   in (  indr,lenr,locr).\n   If k1 > k2, nothing happens.\n   ------------------------------------------------------------------\n   11 Jun 2002: First version of lu1mxr.\n                Allow for empty columns.\n   ================================================================== */\nvoid LU1MXR(LUSOLrec *LUSOL, int K1, int K2, int IX[], REAL AMAXR[])\n{\n#define FastMXR\n#ifdef FastMXR\n  static int  I, *J, *IC, K, LC, LC1, LC2, LR, LR1, LR2;\n  static REAL AMAX;\n#else\n  int  I, J, K, LC, LC1, LC2, LR, LR1, LR2;\n  REAL AMAX;\n#endif\n\n  for(K = K1; K <= K2; K++) {\n    AMAX = ZERO;\n    I = IX[K];\n/*      Find largest element in row i. */\n    LR1 = LUSOL->locr[I];\n    LR2 = (LR1+LUSOL->lenr[I])-1;\n#ifdef FastMXR\n    for(LR = LR1, J = LUSOL->indr + LR1;\n        LR <= LR2; LR++, J++) {\n/*      Find where  aij  is in column  j. */\n      LC1 = LUSOL->locc[*J];\n      LC2 = LC1+LUSOL->lenc[*J];\n      for(LC = LC1, IC = LUSOL->indc + LC1;\n          LC < LC2; LC++, IC++) {\n        if(*IC==I)\n          break;\n      }\n      SETMAX(AMAX,fabs(LUSOL->a[LC]));\n    }\n#else\n    for(LR = LR1; LR <= LR2; LR++) {\n      J = LUSOL->indr[LR];\n/*      Find where  aij  is in column  j. */\n      LC1 = LUSOL->locc[J];\n      LC2 = (LC1+LUSOL->lenc[J])-1;\n      for(LC = LC1; LC <= LC2; LC++) {\n        if(LUSOL->indc[LC]==I)\n          break;\n      }\n      SETMAX(AMAX,fabs(LUSOL->a[LC]));\n    }\n#endif\n    AMAXR[I] = AMAX;\n  }\n}\n\n\n/* ==================================================================\n   lu1ful computes a dense (full) LU factorization of the\n   mleft by nleft matrix that remains to be factored at the\n   beginning of the nrowu-th pass through the main loop of lu1fad.\n   ------------------------------------------------------------------\n   02 May 1989: First version.\n   05 Feb 1994: Column interchanges added to lu1DPP.\n   08 Feb 1994: ipinv reconstructed, since lu1pq3 may alter ip.\n   ================================================================== */\nvoid LU1FUL(LUSOLrec *LUSOL, int LEND, int LU1, MYBOOL TPP,\n            int MLEFT, int NLEFT, int NRANK, int NROWU,\n            int *LENL, int *LENU, int *NSING,\n            MYBOOL KEEPLU, REAL SMALL, REAL D[], int IPVT[])\n{\n  int  L, I, J, IPBASE, LDBASE, LQ, LC1, LC2, LC, LD, LKK, LKN, LU, K, L1,\n       L2, IBEST, JBEST, LA, LL, NROWD, NCOLD;\n  REAL AI, AJ;\n\n/*      ------------------------------------------------------------------\n        If lu1pq3 moved any empty rows, reset ipinv = inverse of ip.\n        ------------------------------------------------------------------ */\n  if(NRANK<LUSOL->m) {\n    for(L = 1; L <= LUSOL->m; L++) {\n      I = LUSOL->ip[L];\n      LUSOL->ipinv[I] = L;\n    }\n  }\n/*      ------------------------------------------------------------------\n        Copy the remaining matrix into the dense matrix D.\n         ------------------------------------------------------------------ */\n#ifdef LUSOLFastClear\n  MEMCLEAR((D+1), LEND);\n#else\n/*   dload(LEND, ZERO, D, 1); */\n  for(J = 1; J <= LEND; J++)\n    D[J] = ZERO;\n#endif\n\n  IPBASE = NROWU-1;\n  LDBASE = 1-NROWU;\n  for(LQ = NROWU; LQ <= LUSOL->n; LQ++) {\n    J = LUSOL->iq[LQ];\n    LC1 = LUSOL->locc[J];\n    LC2 = (LC1+LUSOL->lenc[J])-1;\n    for(LC = LC1; LC <= LC2; LC++) {\n      I = LUSOL->indc[LC];\n      LD = LDBASE+LUSOL->ipinv[I];\n      D[LD] = LUSOL->a[LC];\n    }\n    LDBASE += MLEFT;\n  }\n/*      ------------------------------------------------------------------\n        Call our favorite dense LU factorizer.\n        ------------------------------------------------------------------ */\n  if(TPP)\n    LU1DPP(LUSOL, D,MLEFT,MLEFT,NLEFT,SMALL,NSING,IPVT,LUSOL->iq+NROWU-LUSOL_ARRAYOFFSET);\n  else\n    LU1DCP(LUSOL, D,MLEFT,MLEFT,NLEFT,SMALL,NSING,IPVT,LUSOL->iq+NROWU-LUSOL_ARRAYOFFSET);\n\n/*      ------------------------------------------------------------------\n        Move D to the beginning of A,\n        and pack L and U at the top of a, indc, indr.\n        In the process, apply the row permutation to ip.\n        lkk points to the diagonal of U.\n        ------------------------------------------------------------------ */\n#ifdef LUSOLFastCopy\n  MEMCOPY(LUSOL->a+1,D+1,LEND);\n#else\n  dcopy(LEND,D,1,LUSOL->a,1);\n#endif\n#ifdef ClassicdiagU\n  LUSOL->diagU = LUSOL->a + (LUSOL->lena-LUSOL->n);\n#endif\n  LKK = 1;\n  LKN = (LEND-MLEFT)+1;\n  LU = LU1;\n  for(K = 1; K <= MIN(MLEFT,NLEFT); K++) {\n    L1 = IPBASE+K;\n    L2 = IPBASE+IPVT[K];\n    if(L1!=L2) {\n      I = LUSOL->ip[L1];\n      LUSOL->ip[L1] = LUSOL->ip[L2];\n      LUSOL->ip[L2] = I;\n    }\n    IBEST = LUSOL->ip[L1];\n    JBEST = LUSOL->iq[L1];\n    if(KEEPLU) {\n/*            ===========================================================\n              Pack the next column of L.\n              =========================================================== */\n      LA = LKK;\n      LL = LU;\n      NROWD = 1;\n      for(I = K+1; I <= MLEFT; I++) {\n        LA++;\n        AI = LUSOL->a[LA];\n        if(fabs(AI)>SMALL) {\n          NROWD = NROWD+1;\n          LL--;\n          LUSOL->a[LL] = AI;\n          LUSOL->indc[LL] = LUSOL->ip[IPBASE+I];\n          LUSOL->indr[LL] = IBEST;\n        }\n      }\n/*            ===========================================================\n              Pack the next row of U.\n              We go backwards through the row of D\n              so the diagonal ends up at the front of the row of  U.\n              Beware -- the diagonal may be zero.\n              =========================================================== */\n      LA = LKN+MLEFT;\n      LU = LL;\n      NCOLD = 0;\n      for(J = NLEFT; J >= K; J--) {\n        LA = LA-MLEFT;\n        AJ = LUSOL->a[LA];\n        if(fabs(AJ)>SMALL || J==K) {\n          NCOLD++;\n          LU--;\n          LUSOL->a[LU] = AJ;\n          LUSOL->indr[LU] = LUSOL->iq[IPBASE+J];\n        }\n      }\n      LUSOL->lenr[IBEST] = -NCOLD;\n      LUSOL->lenc[JBEST] = -NROWD;\n      *LENL = ((*LENL)+NROWD)-1;\n      *LENU = (*LENU)+NCOLD;\n      LKN++;\n    }\n    else {\n/*            ===========================================================\n              Store just the diagonal of U, in natural order.\n              =========================================================== */\n      LUSOL->diagU[JBEST] = LUSOL->a[LKK];\n    }\n    LKK += MLEFT+1;\n  }\n}\n\n\n/* ==================================================================\n   lu1or1  organizes the elements of an  m by n  matrix  A  as\n   follows.  On entry, the parallel arrays   a, indc, indr,\n   contain  nelem  entries of the form     aij,    i,    j,\n   in any order.  nelem  must be positive.\n   Entries not larger than the input parameter  small  are treated as\n   zero and removed from   a, indc, indr.  The remaining entries are\n   defined to be nonzero.  numnz  returns the number of such nonzeros\n   and  Amax  returns the magnitude of the largest nonzero.\n   The arrays  lenc, lenr  return the number of nonzeros in each\n   column and row of  A.\n   inform = 0  on exit, except  inform = 1  if any of the indices in\n   indc, indr  imply that the element  aij  lies outside the  m by n\n   dimensions of  A.\n   ------------------------------------------------------------------\n   xx Feb 1985: Original version.\n   17 Oct 2000: a, indc, indr now have size lena to allow nelem = 0.\n   ================================================================== */\nvoid LU1OR1(LUSOLrec *LUSOL, REAL SMALL,\n            REAL *AMAX, int *NUMNZ, int *LERR, int *INFORM)\n{\n  int I, J, L, LDUMMY;\n\n#ifdef LUSOLFastClear\n  MEMCLEAR((LUSOL->lenr+1), LUSOL->m);\n  MEMCLEAR((LUSOL->lenc+1), LUSOL->n);\n#else\n  for(I = 1; I <= LUSOL->m; I++)\n    LUSOL->lenr[I] = ZERO;\n  for(I = 1; I <= LUSOL->n; I++)\n    LUSOL->lenc[I] = ZERO;\n#endif\n\n  *AMAX = 0;\n  *NUMNZ = LUSOL->nelem;\n  L = LUSOL->nelem+1;\n  for(LDUMMY = 1; LDUMMY <= LUSOL->nelem; LDUMMY++) {\n    L--;\n    if(fabs(LUSOL->a[L])>SMALL) {\n      I = LUSOL->indc[L];\n      J = LUSOL->indr[L];\n      SETMAX(*AMAX,fabs(LUSOL->a[L]));\n      if(I<1 || I>LUSOL->m)\n        goto x910;\n      if(J<1 || J>LUSOL->n)\n        goto x910;\n      LUSOL->lenr[I]++;\n      LUSOL->lenc[J]++;\n    }\n    else {\n/*            Replace a negligible element by last element.  Since\n              we are going backwards, we know the last element is ok. */\n      LUSOL->a[L] = LUSOL->a[*NUMNZ];\n      LUSOL->indc[L] = LUSOL->indc[*NUMNZ];\n      LUSOL->indr[L] = LUSOL->indr[*NUMNZ];\n      (*NUMNZ)--;\n    }\n  }\n  *LERR = 0;\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  return;\n\nx910:\n  *LERR = L;\n  *INFORM = LUSOL_INFORM_LUSINGULAR;\n}\n\n/* ==================================================================\n   lu1or2  sorts a list of matrix elements  a(i,j)  into column\n   order, given  numa  entries  a(i,j),  i,  j  in the parallel\n   arrays  a, inum, jnum  respectively.  The matrix is assumed\n   to have  n  columns and an arbitrary number of rows.\n   On entry,  len(*)  must contain the length of each column.\n   On exit,  a(*) and inum(*)  are sorted,  jnum(*) = 0,  and\n   loc(j)  points to the start of column j.\n   lu1or2  is derived from  mc20ad,  a routine in the Harwell\n   Subroutine Library, author J. K. Reid.\n   ------------------------------------------------------------------\n   xx Feb 1985: Original version.\n   17 Oct 2000: a, inum, jnum now have size lena to allow nelem = 0.\n   ================================================================== */\nvoid LU1OR2(LUSOLrec *LUSOL)\n{\n  REAL ACE, ACEP;\n  int  L, J, I, JCE, ICE, ICEP, JCEP, JA, JB;\n\n/*      Set  loc(j)  to point to the beginning of column  j. */\n  L = 1;\n  for(J = 1; J <= LUSOL->n; J++) {\n    LUSOL->locc[J] = L;\n    L += LUSOL->lenc[J];\n  }\n/*      Sort the elements into column order.\n        The algorithm is an in-place sort and is of order  numa. */\n  for(I = 1; I <= LUSOL->nelem; I++) {\n/*         Establish the current entry. */\n    JCE = LUSOL->indr[I];\n    if(JCE==0)\n      continue;\n    ACE = LUSOL->a[I];\n    ICE = LUSOL->indc[I];\n    LUSOL->indr[I] = 0;\n/*         Chain from current entry. */\n    for(J = 1; J <= LUSOL->nelem; J++) {\n/*            The current entry is not in the correct position.\n              Determine where to store it. */\n      L = LUSOL->locc[JCE];\n      LUSOL->locc[JCE]++;\n/*            Save the contents of that location. */\n      ACEP = LUSOL->a[L];\n      ICEP = LUSOL->indc[L];\n      JCEP = LUSOL->indr[L];\n/*            Store current entry. */\n      LUSOL->a[L] = ACE;\n      LUSOL->indc[L] = ICE;\n      LUSOL->indr[L] = 0;\n/*            If next current entry needs to be processed,\n              copy it into current entry. */\n      if(JCEP==0)\n        break;\n      ACE = ACEP;\n      ICE = ICEP;\n      JCE = JCEP;\n    }\n  }\n/*      Reset loc(j) to point to the start of column j. */\n  JA = 1;\n  for(J = 1; J <= LUSOL->n; J++) {\n    JB = LUSOL->locc[J];\n    LUSOL->locc[J] = JA;\n    JA = JB;\n  }\n}\n\n/* ==================================================================\n   lu1or3  looks for duplicate elements in an  m by n  matrix  A\n   defined by the column list  indc, lenc, locc.\n   iw  is used as a work vector of length  m.\n   ------------------------------------------------------------------\n   xx Feb 1985: Original version.\n   17 Oct 2000: indc, indr now have size lena to allow nelem = 0.\n   ================================================================== */\nvoid LU1OR3(LUSOLrec *LUSOL, int *LERR, int *INFORM)\n{\n  int I, J, L1, L2, L;\n\n#ifdef LUSOLFastClear\n  MEMCLEAR((LUSOL->ip+1), LUSOL->m);\n#else\n  for(I = 1; I <= LUSOL->m; I++)\n    LUSOL->ip[I] = ZERO;\n#endif\n\n  for(J = 1; J <= LUSOL->n; J++) {\n    if(LUSOL->lenc[J]>0) {\n      L1 = LUSOL->locc[J];\n      L2 = (L1+LUSOL->lenc[J])-1;\n      for(L = L1; L <= L2; L++) {\n        I = LUSOL->indc[L];\n        if(LUSOL->ip[I]==J)\n          goto x910;\n        LUSOL->ip[I] = J;\n      }\n    }\n  }\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  return;\nx910:\n  *LERR = L;\n  *INFORM = LUSOL_INFORM_LUSINGULAR;\n}\n\n/* ==================================================================\n   lu1or4 constructs a row list  indr, locr\n   from a corresponding column list  indc, locc,\n   given the lengths of both columns and rows in  lenc, lenr.\n   ------------------------------------------------------------------\n   xx Feb 1985: Original version.\n   17 Oct 2000: indc, indr now have size lena to allow nelem = 0.\n   ================================================================== */\nvoid LU1OR4(LUSOLrec *LUSOL)\n{\n  int L, I, L2, J, JDUMMY, L1, LR;\n\n/*      Initialize  locr(i)  to point just beyond where the\n        last component of row  i  will be stored. */\n  L = 1;\n  for(I = 1; I <= LUSOL->m; I++) {\n    L += LUSOL->lenr[I];\n    LUSOL->locr[I] = L;\n  }\n/*      By processing the columns backwards and decreasing  locr(i)\n        each time it is accessed, it will end up pointing to the\n        beginning of row  i  as required. */\n  L2 = LUSOL->nelem;\n  J = LUSOL->n+1;\n  for(JDUMMY = 1; JDUMMY <= LUSOL->n; JDUMMY++) {\n    J = J-1;\n    if(LUSOL->lenc[J]>0) {\n      L1 = LUSOL->locc[J];\n      for(L = L1; L <= L2; L++) {\n        I = LUSOL->indc[L];\n        LR = LUSOL->locr[I]-1;\n        LUSOL->locr[I] = LR;\n        LUSOL->indr[LR] = J;\n      }\n      L2 = L1-1;\n    }\n  }\n}\n\n/* ==================================================================\n   lu1pen deals with pending fill-in in the row file.\n   ------------------------------------------------------------------\n   ifill(ll) says if a row involved in the new column of L\n             has to be updated.  If positive, it is the total\n             length of the final updated row.\n   jfill(lu) says if a column involved in the new row of U\n             contains any pending fill-ins.  If positive, it points\n             to the first fill-in in the column that has yet to be\n             added to the row file.\n   ------------------------------------------------------------------\n   16 Apr 1989: First version of lu1pen.\n   23 Mar 2001: ilast used and updated.\n   ================================================================== */\nvoid LU1PEN(LUSOLrec *LUSOL, int NSPARE, int *ILAST,\n            int LPIVC1, int LPIVC2, int LPIVR1, int LPIVR2,\n            int *LROW, int IFILL[], int JFILL[])\n{\n  int  LL, LC, L, I, LR1, LR2, LR, LU, J, LC1, LC2, LAST;\n\n  LL = 0;\n  for(LC = LPIVC1; LC <= LPIVC2; LC++) {\n    LL++;\n    if(IFILL[LL]==0)\n      continue;\n/*      Another row has pending fill.\n        First, add some spare space at the }\n        of the current last row. */\n#if 1\n    LC1 = (*LROW)+1;\n    LC2 = (*LROW)+NSPARE;\n    *LROW = LC2;\n    for(L = LC1; L <= LC2; L++) {\n#else\n    for(L = (*LROW)+1; L <= (*LROW)+NSPARE; L++) {\n      *LROW = L;  /* ******* ERROR ???? */\n#endif\n      LUSOL->indr[L] = 0;\n    }\n/*      Now move row i to the end of the row file. */\n    I = LUSOL->indc[LC];\n    *ILAST = I;\n    LR1 = LUSOL->locr[I];\n    LR2 = (LR1+LUSOL->lenr[I])-1;\n    LUSOL->locr[I] = (*LROW)+1;\n    for(LR = LR1; LR <= LR2; LR++) {\n      (*LROW)++;\n      LUSOL->indr[*LROW] = LUSOL->indr[LR];\n      LUSOL->indr[LR] = 0;\n    }\n    (*LROW) += IFILL[LL];\n  }\n/*         Scan all columns of  D  and insert the pending fill-in\n           into the row file. */\n  LU = 1;\n  for(LR = LPIVR1; LR <= LPIVR2; LR++) {\n    LU++;\n    if(JFILL[LU]==0)\n      continue;\n    J = LUSOL->indr[LR];\n    LC1 = (LUSOL->locc[J]+JFILL[LU])-1;\n    LC2 = (LUSOL->locc[J]+LUSOL->lenc[J])-1;\n    for(LC = LC1; LC <= LC2; LC++) {\n      I = LUSOL->indc[LC]-LUSOL->m;\n      if(I>0) {\n        LUSOL->indc[LC] = I;\n        LAST = LUSOL->locr[I]+LUSOL->lenr[I];\n        LUSOL->indr[LAST] = J;\n        LUSOL->lenr[I]++;\n      }\n    }\n  }\n}\n\n\n/* ==================================================================\n   lu1fad  is a driver for the numerical phase of lu1fac.\n   At each stage it computes a column of  L  and a row of  U,\n   using a Markowitz criterion to select the pivot element,\n   subject to a stability criterion that bounds the elements of  L.\n   ------------------------------------------------------------------\n   Local variables\n   ---------------\n   lcol   is the length of the column file.  It points to the last\n          nonzero in the column list.\n   lrow   is the analogous quantity for the row file.\n   lfile  is the file length (lcol or lrow) after the most recent\n          compression of the column list or row list.\n   nrowd  and  ncold  are the number of rows and columns in the\n          matrix defined by the pivot column and row.  They are the\n          dimensions of the submatrix D being altered at this stage.\n   melim  and  nelim  are the number of rows and columns in the\n          same matrix D, excluding the pivot column and row.\n   mleft  and  nleft  are the number of rows and columns\n          still left to be factored.\n   nzchng is the increase in nonzeros in the matrix that remains\n          to be factored after the current elimination\n          (usually negative).\n   nzleft is the number of nonzeros still left to be factored.\n   nspare is the space we leave at the end of the last row or\n          column whenever a row or column is being moved to the }\n          of its file.  nspare = 1 or 2 might help reduce the\n          number of file compressions when storage is tight.\n   The row and column ordering permutes A into the form\n                      ------------------------\n                       \\                     |\n                        \\         U1         |\n                         \\                   |\n                          --------------------\n                          |\\\n                          | \\\n                          |  \\\n          P A Q   =       |   \\\n                          |    \\\n                          |     --------------\n                          |     |            |\n                          |     |            |\n                          | L1  |     A2     |\n                          |     |            |\n                          |     |            |\n                          --------------------\n   where the block A2 is factored as  A2 = L2 U2.\n   The phases of the factorization are as follows.\n   Utri   is true when U1 is being determined.\n          Any column of length 1 is accepted immediately (if TPP).\n   Ltri   is true when L1 is being determined.\n          lu1mar exits as soon as an acceptable pivot is found\n          in a row of length 1.\n   spars1 is true while the density of the (modified) A2 is less\n          than the parameter dens1 = parmlu(7) = 0.3 say.\n          lu1mar searches maxcol columns and maxrow rows,\n          where  maxcol = luparm(3),  maxrow = maxcol - 1.\n          lu1mxc is used to keep the biggest element at the top\n          of all remaining columns.\n   spars2 is true while the density of the modified A2 is less\n          than the parameter dens2 = parmlu(8) = 0.6 say.\n          lu1mar searches maxcol columns and no rows.\n          lu1mxc could fix up only the first maxcol cols (with TPP).\n          22 Sep 2000:  For simplicity, lu1mxc fixes all\n                        modified cols.\n   dense  is true once the density of A2 reaches dens2.\n          lu1mar searches only 1 column (the shortest).\n          lu1mxc could fix up only the first column (with TPP).\n   ------------------------------------------------------------------\n   00 Jan 1986  Version documented in LUSOL paper:\n                Gill, Murray, Saunders and Wright (1987),\n                Maintaining LU factors of a general sparse matrix,\n                Linear algebra and its applications 88/89, 239-270.\n   02 Feb 1989  Following Suhl and Aittoniemi (1987), the largest\n                element in each column is now kept at the start of\n                the column, i.e. in position locc(j) of a and indc.\n                This should speed up the Markowitz searches.\n                To save time on highly triangular matrices, we wait\n                until there are no further columns of length 1\n                before setting and maintaining that property.\n   12 Apr 1989  ipinv and iqinv added (inverses of ip and iq)\n                to save searching ip and iq for rows and columns\n                altered in each elimination step.  (Used in lu1pq2)\n   19 Apr 1989  Code segmented to reduce its size.\n                lu1gau does most of the Gaussian elimination work.\n                lu1mar does just the Markowitz search.\n                lu1mxc moves biggest elements to top of columns.\n                lu1pen deals with pending fill-in in the row list.\n                lu1pq2 updates the row and column permutations.\n   26 Apr 1989  maxtie replaced by maxcol, maxrow in the Markowitz\n                search.  maxcol, maxrow change as density increases.\n   25 Oct 1993  keepLU implemented.\n   07 Feb 1994  Exit main loop early to finish off with a dense LU.\n                densLU tells lu1fad whether to do it.\n   21 Dec 1994  Bug fixed.  nrank was wrong after the call to lu1ful.\n   12 Nov 1999  A parallel version of dcopy gave trouble in lu1ful\n                during left-shift of dense matrix D within a(*).\n                Fixed this unexpected problem here in lu1fad\n                by making sure the first and second D don't overlap.\n   13 Sep 2000  TCP (Threshold Complete Pivoting) implemented.\n                lu2max added\n                (finds aijmax from biggest elems in each col).\n                Utri, Ltri and Spars1 phases apply.\n                No switch to Dense CP yet.  (Only TPP switches.)\n   14 Sep 2000  imax needed to remember row containing aijmax.\n   22 Sep 2000  For simplicity, lu1mxc always fixes all modified cols.\n                (TPP spars2 used to fix just the first maxcol cols.)\n   08 Nov 2000: Speed up search for aijmax.\n                Don't need to search all columns if the elimination\n                didn't alter the col containing the current aijmax.\n   21 Nov 2000: lu1slk implemented for Utri phase with TCP\n                to guard against deceptive triangular matrices.\n                (Utri used to have aijtol >= 0.9999 to include\n                slacks, but this allows other 1s to be accepted.)\n                Utri now accepts slacks, but applies normal aijtol\n                test to other pivots.\n   28 Nov 2000: TCP with empty cols must call lu1mxc and lu2max\n                with ( lq1, n, ... ), not just ( 1, n, ... ).\n   23 Mar 2001: lu1fad bug with TCP.\n                A col of length 1 might not be accepted as a pivot.\n                Later it appears in a pivot row and temporarily\n                has length 0 (when pivot row is removed\n                but before the column is filled in).  If it is the\n                last column in storage, the preceding col also thinks\n                it is \"last\".  Trouble arises when the preceding col\n                needs fill-in -- it overlaps the real \"last\" column.\n                (Very rarely, same trouble might have happened if\n                the drop tolerance caused columns to have length 0.)\n                Introduced ilast to record the last row in row file,\n                           jlast to record the last col in col file.\n                lu1rec returns ilast = indr(lrow + 1)\n                            or jlast = indc(lcol + 1).\n                (Should be an output parameter, but didn't want to\n                alter lu1rec's parameter list.)\n                lu1rec also treats empty rows or cols safely.\n                (Doesn't eliminate them!)\n   26 Apr 2002: Heap routines added for TCP.\n                lu2max no longer needed.\n                imax, jmax used only for printing.\n   01 May 2002: lu1DCP implemented (dense complete pivoting).\n                Both TPP and TCP now switch to dense LU\n                when density exceeds dens2.\n   06 May 2002: In dense mode, store diag(U) in natural order.\n   09 May 2002: lu1mCP implemented (Markowitz TCP via heap).\n   11 Jun 2002: lu1mRP implemented (Markowitz TRP).\n   28 Jun 2002: Fixed call to lu1mxr.\n   14 Dec 2002: lu1mSP implemented (Markowitz TSP).\n   15 Dec 2002: Both TPP and TSP can grab cols of length 1\n                during Utri.\n   ================================================================== */\nvoid LU1FAD(LUSOLrec *LUSOL,\n#ifdef ClassicHamaxR\n            int LENA2, int LENH, REAL HA[], int HJ[], int HK[], REAL AMAXR[],\n#endif\n            int *INFORM, int *LENL, int *LENU, int *MINLEN,\n            int *MERSUM, int *NUTRI, int *NLTRI,\n            int *NDENS1, int *NDENS2, int *NRANK,\n            REAL *LMAX, REAL *UMAX, REAL *DUMAX, REAL *DUMIN, REAL *AKMAX)\n{\n  MYBOOL UTRI, LTRI, SPARS1, SPARS2, DENSE, DENSLU, KEEPLU, TCP, TPP, TRP,TSP;\n  int    HLEN, HOPS, H, LPIV, LPRINT, MAXCOL, MAXROW, ILAST, JLAST, LFILE, LROW, LCOL,\n         MINMN, MAXMN, NZLEFT, NSPARE, LU1, KK, J, LC, MLEFT, NLEFT, NROWU,\n         LQ1, LQ2, JBEST, LQ, I, IBEST, MBEST, LEND, NFREE, LD, NCOLD, NROWD,\n         MELIM, NELIM, JMAX, IMAX, LL1, LSAVE, LFREE, LIMIT, MINFRE, LPIVR, LPIVR1, LPIVR2,\n         L, LPIVC, LPIVC1, LPIVC2, KBEST, LU, LR, LENJ, LC1, LAST, LL, LS,\n         LENI, LR1, LFIRST, NFILL, NZCHNG, K, MRANK, NSING;\n  REAL   LIJ, LTOL, SMALL, USPACE, DENS1, DENS2, AIJMAX, AIJTOL, AMAX, ABEST, DIAG, V;\n#ifdef ClassicHamaxR\n  int    LDIAGU;\n#else\n  int    LENA2 = LUSOL->lena;\n#endif\n\n#ifdef UseTimer\n  int    eltime, mktime, ntime;\n  timer ( \"start\", 3 );\n  ntime = LUSOL->n / 4;\n#endif\n\n#ifdef ForceInitialization\n  AIJMAX = 0;\n  AIJTOL = 0;\n  HLEN   = 0;\n  JBEST  = 0;\n  IBEST  = 0;\n  MBEST  = 0;\n  LEND   = 0;\n  LD     = 0;\n#endif\n\n  LPRINT = LUSOL->luparm[LUSOL_IP_PRINTLEVEL];\n  MAXCOL = LUSOL->luparm[LUSOL_IP_MARKOWITZ_MAXCOL];\n  LPIV   = LUSOL->luparm[LUSOL_IP_PIVOTTYPE];\n  KEEPLU = (MYBOOL) (LUSOL->luparm[LUSOL_IP_KEEPLU]!=FALSE);\n/*      Threshold Partial   Pivoting (normal). */\n  TPP = (MYBOOL) (LPIV==LUSOL_PIVMOD_TPP);\n/*      Threshold Rook      Pivoting */\n  TRP = (MYBOOL) (LPIV==LUSOL_PIVMOD_TRP);\n/*      Threshold Complete  Pivoting. */\n  TCP = (MYBOOL) (LPIV==LUSOL_PIVMOD_TCP);\n/*      Threshold Symmetric Pivoting. */\n  TSP = (MYBOOL) (LPIV==LUSOL_PIVMOD_TSP);\n  DENSLU = FALSE;\n  MAXROW = MAXCOL-1;\n/*      Assume row m is last in the row file. */\n  ILAST = LUSOL->m;\n/*      Assume col n is last in the col file. */\n  JLAST = LUSOL->n;\n  LFILE = LUSOL->nelem;\n  LROW = LUSOL->nelem;\n  LCOL = LUSOL->nelem;\n  MINMN = MIN(LUSOL->m,LUSOL->n);\n  MAXMN = MAX(LUSOL->m,LUSOL->n);\n  NZLEFT = LUSOL->nelem;\n  NSPARE = 1;\n\n  if(KEEPLU)\n    LU1 = LENA2+1;\n  else {\n/*         Store only the diagonals of U in the top of memory. */\n#ifdef ClassicdiagU\n    LDIAGU = LENA2-LUSOL->n;\n    LU1 = LDIAGU+1;\n    LUSOL->diagU = LUSOL->a+LDIAGU;\n#else\n    LU1 = LENA2+1;\n#endif\n  }\n\n  LTOL = LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij];\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  USPACE = LUSOL->parmlu[LUSOL_RP_COMPSPACE_U];\n  DENS1 = LUSOL->parmlu[LUSOL_RP_MARKOWITZ_CONLY];\n  DENS2 = LUSOL->parmlu[LUSOL_RP_MARKOWITZ_DENSE];\n  UTRI = TRUE;\n  LTRI = FALSE;\n  SPARS1 = FALSE;\n  SPARS2 = FALSE;\n  DENSE = FALSE;\n/*      Check parameters. */\n  SETMAX(LTOL,1.0001E+0);\n  SETMIN(DENS1,DENS2);\n/*      Initialize output parameters.\n        lenL, lenU, minlen, mersum, nUtri, nLtri, ndens1, ndens2, nrank\n        are already initialized by lu1fac. */\n  *LMAX  = ZERO;\n  *UMAX  = ZERO;\n  *DUMAX = ZERO;\n  *DUMIN = LUSOL_BIGNUM;\n  if(LUSOL->nelem==0)\n    *DUMIN = ZERO;\n  *AKMAX = ZERO;\n  HOPS = 0;\n/*      More initialization.\n        Don't worry yet about lu1mxc. */\n  if(TPP || TSP) {\n    AIJMAX = ZERO;\n    AIJTOL = ZERO;\n    HLEN = 1;\n/*      TRP or TCP */\n  }\n  else {\n/*      Move biggest element to top of each column.\n        Set w(*) to mark slack columns (unit vectors). */\n    LU1MXC(LUSOL, 1,LUSOL->n,LUSOL->iq);\n    LU1SLK(LUSOL);\n  }\n  if(TRP)\n/*      Find biggest element in each row. */\n#ifdef ClassicHamaxR\n    LU1MXR(LUSOL, 1,LUSOL->m,LUSOL->ip,AMAXR);\n#else\n    LU1MXR(LUSOL, 1,LUSOL->m,LUSOL->ip,LUSOL->amaxr);\n#endif\n\n  if(TCP) {\n/*      Set Ha(1:Hlen) = biggest element in each column,\n            Hj(1:Hlen) = corresponding column indices. */\n    HLEN = 0;\n    for(KK = 1; KK <= LUSOL->n; KK++) {\n      HLEN++;\n      J = LUSOL->iq[KK];\n      LC = LUSOL->locc[J];\n#ifdef ClassicHamaxR\n      HA[HLEN] = fabs(LUSOL->a[LC]);\n      HJ[HLEN] = J;\n      HK[J] = HLEN;\n#else\n      LUSOL->Ha[HLEN] = fabs(LUSOL->a[LC]);\n      LUSOL->Hj[HLEN] = J;\n      LUSOL->Hk[J] = HLEN;\n#endif\n    }\n/*      Build the heap, creating new Ha, Hj and setting Hk(1:Hlen). */\n#ifdef ClassicHamaxR\n    HBUILD(HA,HJ,HK,HLEN,&HOPS);\n#else\n    HBUILD(LUSOL->Ha,LUSOL->Hj,LUSOL->Hk,HLEN,&HOPS);\n#endif\n  }\n/*      ------------------------------------------------------------------\n        Start of main loop.\n        ------------------------------------------------------------------ */\n  MLEFT = LUSOL->m+1;\n  NLEFT = LUSOL->n+1;\n  for(NROWU = 1; NROWU <= MINMN; NROWU++) {\n#ifdef UseTimer\n    mktime = (nrowu / ntime) + 4;\n    eltime = (nrowu / ntime) + 9;\n#endif\n    MLEFT--;\n    NLEFT--;\n/*         Bail out if there are no nonzero rows left. */\n    if(LUSOL->iploc[1]>LUSOL->m)\n      goto x900;\n/*      For TCP, the largest Aij is at the top of the heap. */\n   if(TCP) {\n/*\n              Marvelously easy */\n#ifdef ClassicHamaxR\n      AIJMAX = HA[1];\n#else\n      AIJMAX = LUSOL->Ha[1];\n#endif\n      SETMAX(*AKMAX,AIJMAX);\n      AIJTOL = AIJMAX/LTOL;\n    }\n/*         ===============================================================\n           Find a suitable pivot element.\n           =============================================================== */\n    if(UTRI) {\n/*            ------------------------------------------------------------\n              So far all columns have had length 1.\n              We are still looking for the (backward) triangular part of A\n              that forms the first rows and columns of U.\n              ------------------------------------------------------------ */\n      LQ1 = LUSOL->iqloc[1];\n      LQ2 = LUSOL->n;\n      if(LUSOL->m>1)\n        LQ2 = LUSOL->iqloc[2]-1;\n/*      There are more cols of length 1. */\n      if(LQ1<=LQ2) {\n        if(TPP || TSP) {\n/*      Grab the first one. */\n          JBEST = LUSOL->iq[LQ1];\n/*      Scan all columns of length 1 ... TRP or TCP */\n        }\n        else {\n          JBEST = 0;\n          for(LQ = LQ1; LQ <= LQ2; LQ++) {\n            J = LUSOL->iq[LQ];\n/*      Accept a slack */\n            if(LUSOL->w[J]>ZERO) {\n              JBEST = J;\n              goto x250;\n            }\n            LC = LUSOL->locc[J];\n            AMAX = fabs(LUSOL->a[LC]);\n            if(TRP) {\n              I = LUSOL->indc[LC];\n#ifdef ClassicHamaxR\n              AIJTOL = AMAXR[I]/LTOL;\n#else\n              AIJTOL = LUSOL->amaxr[I]/LTOL;\n#endif\n            }\n            if(AMAX>=AIJTOL) {\n              JBEST = J;\n              goto x250;\n            }\n          }\n        }\nx250:\n        if(JBEST>0) {\n          LC = LUSOL->locc[JBEST];\n          IBEST = LUSOL->indc[LC];\n          MBEST = 0;\n          goto x300;\n        }\n      }\n/*            This is the end of the U triangle.\n              We will not return to this part of the code.\n              TPP and TSP call lu1mxc for the first time\n              (to move biggest element to top of each column). */\n      if(LPRINT>=LUSOL_MSG_PIVOT)\n        LUSOL_report(LUSOL, 0, \"Utri ended.  spars1 = TRUE\\n\");\n      UTRI = FALSE;\n      LTRI = TRUE;\n      SPARS1 = TRUE;\n      *NUTRI = NROWU-1;\n      if(TPP || TSP)\n        LU1MXC(LUSOL, LQ1,LUSOL->n,LUSOL->iq);\n    }\n    if(SPARS1) {\n/*            ------------------------------------------------------------\n              Perform a Markowitz search.\n              Search cols of length 1, then rows of length 1,\n              then   cols of length 2, then rows of length 2, etc.\n              ------------------------------------------------------------ */\n#ifdef UseTimer\n        timer ( \"start\", mktime );\n#endif\n/*      12 Jun 2002: Next line disables lu1mCP below\n              if (TPP) then */\n      if(TPP || TCP) {\n        LU1MAR(LUSOL, MAXMN,TCP,AIJTOL,LTOL,MAXCOL,MAXROW,&IBEST,&JBEST,&MBEST);\n      }\n      else if(TRP) {\n#ifdef ClassicHamaxR\n        LU1MRP(LUSOL, MAXMN,LTOL,MAXCOL,MAXROW,&IBEST,&JBEST,&MBEST,AMAXR);\n#else\n        LU1MRP(LUSOL, MAXMN,LTOL,MAXCOL,MAXROW,&IBEST,&JBEST,&MBEST,LUSOL->amaxr);\n#endif\n/*      else if (TCP) {\n        lu1mCP( m    , n     , lena  , aijtol,\n                      ibest, jbest , mbest ,\n                      a    , indc  , indr  ,\n                      lenc , lenr  , locc  ,\n                      Hlen , Ha    , Hj    ) */\n      }\n      else if(TSP) {\n        LU1MSP(LUSOL, MAXMN,LTOL,MAXCOL,&IBEST,&JBEST,&MBEST);\n        if(IBEST==0)\n          goto x990;\n      }\n#ifdef UseTimer\n      timer ( \"finish\", mktime );\n#endif\n      if(LTRI) {\n/*               So far all rows have had length 1.\n                 We are still looking for the (forward) triangle of A\n                 that forms the first rows and columns of L. */\n        if(MBEST>0) {\n          LTRI = FALSE;\n          *NLTRI = NROWU-1-*NUTRI;\n          if(LPRINT>=LUSOL_MSG_PIVOT)\n            LUSOL_report(LUSOL, 0, \"Ltri ended.\\n\");\n        }\n      }\n      else {\n/*               See if what's left is as dense as dens1. */\n        if(NZLEFT>=(DENS1*MLEFT)*NLEFT) {\n          SPARS1 = FALSE;\n          SPARS2 = TRUE;\n          *NDENS1 = NLEFT;\n          MAXROW = 0;\n          if(LPRINT>=LUSOL_MSG_PIVOT)\n            LUSOL_report(LUSOL, 0, \"spars1 ended.  spars2 = TRUE\\n\");\n        }\n      }\n    }\n    else if(SPARS2 || DENSE) {\n/*            ------------------------------------------------------------\n              Perform a restricted Markowitz search,\n              looking at only the first maxcol columns.  (maxrow = 0.)\n              ------------------------------------------------------------ */\n#ifdef UseTimer\n      timer ( \"start\", mktime );\n#endif\n/*      12 Jun 2002: Next line disables lu1mCP below\n              if (TPP) then */\n      if(TPP || TCP) {\n        LU1MAR(LUSOL, MAXMN,TCP,AIJTOL,LTOL,MAXCOL,MAXROW,&IBEST,&JBEST,&MBEST);\n      }\n      else if(TRP) {\n#ifdef ClassicHamaxR\n        LU1MRP(LUSOL, MAXMN,LTOL,MAXCOL,MAXROW,&IBEST,&JBEST,&MBEST,AMAXR);\n#else\n        LU1MRP(LUSOL, MAXMN,LTOL,MAXCOL,MAXROW,&IBEST,&JBEST,&MBEST,LUSOL->amaxr);\n#endif\n/*      else if (TCP) {\n        lu1mCP( m    , n     , lena  , aijtol,\n                      ibest, jbest , mbest ,\n                      a    , indc  , indr  ,\n                      lenc , lenr  , locc  ,\n                      Hlen , Ha    , Hj    ) */\n      }\n      else if(TSP) {\n        LU1MSP(LUSOL, MAXMN,LTOL,MAXCOL,&IBEST,&JBEST,&MBEST);\n        if(IBEST==0)\n          goto x985;\n      }\n#ifdef UseTimer\n      timer ( \"finish\", mktime );\n#endif\n/*            See if what's left is as dense as dens2. */\n      if(SPARS2) {\n        if(NZLEFT>=(DENS2*MLEFT)*NLEFT) {\n          SPARS2 = FALSE;\n          DENSE = TRUE;\n          *NDENS2 = NLEFT;\n          MAXCOL = 1;\n          if(LPRINT>=LUSOL_MSG_PIVOT)\n            LUSOL_report(LUSOL, 0, \"spars2 ended.  dense = TRUE\\n\");\n        }\n      }\n    }\n/*         ---------------------------------------------------------------\n           See if we can finish quickly.\n           --------------------------------------------------------------- */\n    if(DENSE) {\n      LEND = MLEFT*NLEFT;\n      NFREE = LU1-1;\n      if(NFREE>=2*LEND) {\n/*               There is room to treat the remaining matrix as\n                 a dense matrix D.\n                 We may have to compress the column file first.\n                 12 Nov 1999: D used to be put at the\n                              beginning of free storage (lD = lcol + 1).\n                              Now put it at the end     (lD = lu1 - lenD)\n                              so the left-shift in lu1ful will not\n                              involve overlapping storage\n                              (fatal with parallel dcopy).\n   */\n        DENSLU = TRUE;\n        *NDENS2 = NLEFT;\n        LD = LU1-LEND;\n        if(LCOL>=LD) {\n          LU1REC(LUSOL, LUSOL->n,TRUE,&LCOL,\n                        LUSOL->indc,LUSOL->lenc,LUSOL->locc);\n          LFILE = LCOL;\n          JLAST = LUSOL->indc[LCOL+1];\n        }\n        goto x900;\n      }\n    }\n/*         ===============================================================\n           The best  aij  has been found.\n           The pivot row  ibest  and the pivot column  jbest\n           Define a dense matrix  D  of size  nrowd  by  ncold.\n           =============================================================== */\nx300:\n    NCOLD = LUSOL->lenr[IBEST];\n    NROWD = LUSOL->lenc[JBEST];\n    MELIM = NROWD-1;\n    NELIM = NCOLD-1;\n    (*MERSUM) += MBEST;\n    (*LENL) += MELIM;\n    (*LENU) += NCOLD;\n    if(LPRINT>=LUSOL_MSG_PIVOT) {\n      if(NROWU==1)\n        LUSOL_report(LUSOL, 0, \"lu1fad debug:\\n\");\n      if(TPP || TRP || TSP) {\n        LUSOL_report(LUSOL, 0, \"nrowu:%7d   i,jbest:%7d,%7d   nrowd,ncold:%6d,%6d\\n\",\n                            NROWU, IBEST,JBEST, NROWD,NCOLD);\n/*      TCP */\n      }\n      else {\n#ifdef ClassicHamaxR\n        JMAX = HJ[1];\n#else\n        JMAX = LUSOL->Hj[1];\n#endif\n        IMAX = LUSOL->indc[LUSOL->locc[JMAX]];\n        LUSOL_report(LUSOL, 0, \"nrowu:%7d   i,jbest:%7d,%7d   nrowd,ncold:%6d,%6d   i,jmax:%7d,%7d   aijmax:%g\\n\",\n                            NROWU, IBEST,JBEST, NROWD,NCOLD, IMAX,JMAX, AIJMAX);\n      }\n    }\n/*         ===============================================================\n           Allocate storage for the next column of  L  and next row of  U.\n           Initially the top of a, indc, indr are used as follows:\n                      ncold       melim       ncold        melim\n           a      |...........|...........|ujbest..ujn|li1......lim|\n           indc   |...........|  lenr(i)  |  lenc(j)  |  markl(i)  |\n           indr   |...........| iqloc(i)  |  jfill(j) |  ifill(i)  |\n                 ^           ^             ^           ^            ^\n                 lfree   lsave             lu1         ll1          oldlu1\n           Later the correct indices are inserted:\n           indc   |           |           |           |i1........im|\n           indr   |           |           |jbest....jn|ibest..ibest|\n           =============================================================== */\n    if(!KEEPLU) {\n/*            Always point to the top spot.\n              Only the current column of L and row of U will\n              take up space, overwriting the previous ones. */\n#ifdef ClassicHamaxR\n      LU1 = LDIAGU+1;\n#else\n      LU1 = LENA2+1;\n#endif\n    }\n    /* Update (left-shift) pointers to make room for the new data */\n    LL1 = LU1-MELIM;\n    LU1 = LL1-NCOLD;\n    LSAVE = LU1-NROWD;\n    LFREE = LSAVE-NCOLD;\n\n    /* Check if we need to allocate more memory, and allocate if necessary */\n#if 0  /* Proposal by Michael A. Saunders (logic based on Markowitz' rule) */\n    L = NROWD*NCOLD;\n\n    /* Try to avoid future expansions by anticipating further updates - KE extension */\n    if(LUSOL->luparm[LUSOL_IP_UPDATELIMIT] > 0)\n#if 1\n      L *= (int) (log(LUSOL->luparm[LUSOL_IP_UPDATELIMIT]-LUSOL->luparm[LUSOL_IP_UPDATECOUNT]+2.0) + 1);\n#else\n      L *= (LUSOL->luparm[LUSOL_IP_UPDATELIMIT]-LUSOL->luparm[LUSOL_IP_UPDATECOUNT]) / 2 + 1;\n#endif\n\n#else  /* Version by Kjell Eikland (from luparm[LUSOL_IP_MINIMUMLENA] and safety margin) */\n    L  = (KEEPLU ? MAX(LROW, LCOL) + 2*(LUSOL->m+LUSOL->n) : 0);\n    L *= LUSOL_MULT_nz_a;\n    SETMAX(L, NROWD*NCOLD);\n#endif\n\n    /* Do the memory expansion */\n    if((L > LFREE-LCOL) && LUSOL_expand_a(LUSOL, &L, &LFREE)) {\n      LL1   += L;\n      LU1   += L;\n      LSAVE += L;\n#ifdef ClassicdiagU\n      LUSOL->diagU += L;\n#endif\n#ifdef ClassicHamaxR\n      HA    += L;\n      HJ    += L;\n      HK    += L;\n      AMAXR += L;\n#endif\n    }\n    LIMIT = (int) (USPACE*LFILE)+LUSOL->m+LUSOL->n+1000;\n\n/*         Make sure the column file has room.\n           Also force a compression if its length exceeds a certain limit. */\n#ifdef StaticMemAlloc\n    MINFRE = NCOLD+MELIM;\n#else\n    MINFRE = NROWD*NCOLD;\n#endif\n    NFREE = LFREE-LCOL;\n    if(NFREE<MINFRE || LCOL>LIMIT) {\n      LU1REC(LUSOL, LUSOL->n,TRUE,&LCOL,\n                    LUSOL->indc,LUSOL->lenc,LUSOL->locc);\n      LFILE = LCOL;\n      JLAST = LUSOL->indc[LCOL+1];\n      NFREE = LFREE-LCOL;\n      if(NFREE<MINFRE)\n        goto x970;\n    }\n/*         Make sure the row file has room. */\n#ifdef StaticMemAlloc\n    MINFRE = NCOLD+MELIM;\n#else\n    MINFRE = NROWD*NCOLD;\n#endif\n    NFREE = LFREE-LROW;\n    if(NFREE<MINFRE || LROW>LIMIT) {\n      LU1REC(LUSOL, LUSOL->m,FALSE,&LROW,\n                    LUSOL->indr,LUSOL->lenr,LUSOL->locr);\n      LFILE = LROW;\n      ILAST = LUSOL->indr[LROW+1];\n      NFREE = LFREE-LROW;\n      if(NFREE<MINFRE)\n        goto x970;\n    }\n/*         ===============================================================\n           Move the pivot element to the front of its row\n           and to the top of its column.\n           =============================================================== */\n    LPIVR = LUSOL->locr[IBEST];\n    LPIVR1 = LPIVR+1;\n    LPIVR2 = LPIVR+NELIM;\n    for(L = LPIVR; L <= LPIVR2; L++) {\n      if(LUSOL->indr[L]==JBEST)\n        break;\n    }\n\n    LUSOL->indr[L] = LUSOL->indr[LPIVR];\n    LUSOL->indr[LPIVR] = JBEST;\n    LPIVC = LUSOL->locc[JBEST];\n    LPIVC1 = LPIVC+1;\n    LPIVC2 = LPIVC+MELIM;\n    for(L = LPIVC; L <= LPIVC2; L++) {\n      if(LUSOL->indc[L]==IBEST)\n        break;\n    }\n    LUSOL->indc[L] = LUSOL->indc[LPIVC];\n    LUSOL->indc[LPIVC] = IBEST;\n    ABEST = LUSOL->a[L];\n    LUSOL->a[L] = LUSOL->a[LPIVC];\n    LUSOL->a[LPIVC] = ABEST;\n    if(!KEEPLU)\n/*            Store just the diagonal of U, in natural order.\n   !!         a[ldiagU + nrowu] = abest ! This was in pivot order. */\n      LUSOL->diagU[JBEST] = ABEST;\n\n/*     ==============================================================\n        Delete pivot col from heap.\n        Hk tells us where it is in the heap.\n       ============================================================== */\n    if(TCP) {\n#ifdef ClassicHamaxR\n      KBEST = HK[JBEST];\n      HDELETE(HA,HJ,HK,&HLEN,KBEST,&H);\n#else\n      KBEST = LUSOL->Hk[JBEST];\n      HDELETE(LUSOL->Ha,LUSOL->Hj,LUSOL->Hk,&HLEN,KBEST,&H);\n#endif\n      HOPS += H;\n    }\n/*         ===============================================================\n           Delete the pivot row from the column file\n           and store it as the next row of  U.\n           set  indr(lu) = 0     to initialize jfill ptrs on columns of D,\n                indc(lu) = lenj  to save the original column lengths.\n           =============================================================== */\n    LUSOL->a[LU1] = ABEST;\n    LUSOL->indr[LU1] = JBEST;\n    LUSOL->indc[LU1] = NROWD;\n    LU = LU1;\n    DIAG = fabs(ABEST);\n    SETMAX(*UMAX,DIAG);\n    SETMAX(*DUMAX,DIAG);\n    SETMIN(*DUMIN,DIAG);\n    for(LR = LPIVR1; LR <= LPIVR2; LR++) {\n      LU++;\n      J = LUSOL->indr[LR];\n      LENJ = LUSOL->lenc[J];\n      LUSOL->lenc[J] = LENJ-1;\n      LC1 = LUSOL->locc[J];\n      LAST = LC1+LUSOL->lenc[J];\n      for(L = LC1; L <= LAST; L++) {\n        if(LUSOL->indc[L]==IBEST)\n          break;\n      }\n      LUSOL->a[LU] = LUSOL->a[L];\n      LUSOL->indr[LU] = 0;\n      LUSOL->indc[LU] = LENJ;\n      SETMAX(*UMAX,fabs(LUSOL->a[LU]));\n      LUSOL->a[L] = LUSOL->a[LAST];\n      LUSOL->indc[L] = LUSOL->indc[LAST];\n/*      Free entry */\n      LUSOL->indc[LAST] = 0;\n/* ???        if (j .eq. jlast) lcol = lcol - 1 */\n    }\n/*         ===============================================================\n           Delete the pivot column from the row file\n           and store the nonzeros of the next column of  L.\n           Set  indc(ll) = 0     to initialize markl(*) markers,\n                indr(ll) = 0     to initialize ifill(*) row fill-in cntrs,\n                indc(ls) = leni  to save the original row lengths,\n                indr(ls) = iqloc(i)    to save parts of  iqloc(*),\n                iqloc(i) = lsave - ls  to point to the nonzeros of  L\n                         = -1, -2, -3, ... in mark(*).\n           =============================================================== */\n    LUSOL->indc[LSAVE] = NCOLD;\n    if(MELIM==0)\n      goto x700;\n    LL = LL1-1;\n    LS = LSAVE;\n    ABEST = ONE/ABEST;\n    for(LC = LPIVC1; LC <= LPIVC2; LC++) {\n      LL++;\n      LS++;\n      I = LUSOL->indc[LC];\n      LENI = LUSOL->lenr[I];\n      LUSOL->lenr[I] = LENI-1;\n      LR1 = LUSOL->locr[I];\n      LAST = LR1+LUSOL->lenr[I];\n      for(L = LR1; L <= LAST; L++) {\n        if(LUSOL->indr[L]==JBEST)\n          break;\n      }\n      LUSOL->indr[L] = LUSOL->indr[LAST];\n/*      Free entry */\n      LUSOL->indr[LAST] = 0;\n      LUSOL->a[LL] = -LUSOL->a[LC]*ABEST;\n      LIJ = fabs(LUSOL->a[LL]);\n      SETMAX(*LMAX,LIJ);\n      LUSOL->indc[LL] = 0;\n      LUSOL->indr[LL] = 0;\n      LUSOL->indc[LS] = LENI;\n      LUSOL->indr[LS] = LUSOL->iqloc[I];\n      LUSOL->iqloc[I] = LSAVE-LS;\n    }\n/*         ===============================================================\n           Do the Gaussian elimination.\n           This involves adding a multiple of the pivot column\n           to all other columns in the pivot row.\n           Sometimes more than one call to lu1gau is needed to allow\n           compression of the column file.\n           lfirst  says which column the elimination should start with.\n           minfre  is a bound on the storage needed for any one column.\n           lu      points to off-diagonals of u.\n           nfill   keeps track of pending fill-in in the row file.\n           =============================================================== */\n    if(NELIM==0)\n      goto x700;\n    LFIRST = LPIVR1;\n    MINFRE = MLEFT+NSPARE;\n    LU = 1;\n    NFILL = 0;\n\nx400:\n#ifdef UseTimer\n    timer ( \"start\", eltime );\n#endif\n    LU1GAU(LUSOL, MELIM,NSPARE,SMALL,LPIVC1,LPIVC2,&LFIRST,LPIVR2,\n           LFREE,MINFRE,ILAST,&JLAST,&LROW,&LCOL,&LU,&NFILL,\n           LUSOL->iqloc, LUSOL->a+LL1-LUSOL_ARRAYOFFSET,\n           LUSOL->indc+LL1-LUSOL_ARRAYOFFSET, LUSOL->a+LU1-LUSOL_ARRAYOFFSET,\n           LUSOL->indr+LL1-LUSOL_ARRAYOFFSET, LUSOL->indr+LU1-LUSOL_ARRAYOFFSET);\n#ifdef UseTimer\n    timer ( \"finish\", eltime );\n#endif\n    if(LFIRST>0) {\n/*            The elimination was interrupted.\n              Compress the column file and try again.\n              lfirst, lu and nfill have appropriate new values. */\n      LU1REC(LUSOL, LUSOL->n,TRUE,&LCOL,\n                    LUSOL->indc,LUSOL->lenc,LUSOL->locc);\n      LFILE = LCOL;\n      JLAST = LUSOL->indc[LCOL+1];\n      LPIVC = LUSOL->locc[JBEST];\n      LPIVC1 = LPIVC+1;\n      LPIVC2 = LPIVC+MELIM;\n      NFREE = LFREE-LCOL;\n      if(NFREE<MINFRE) {\n          goto x970;\n      }\n      goto x400;\n    }\n/*         ===============================================================\n           The column file has been fully updated.\n           Deal with any pending fill-in in the row file.\n           =============================================================== */\n    if(NFILL>0) {\n/*            Compress the row file if necessary.\n              lu1gau has set nfill to be the number of pending fill-ins\n              plus the current length of any rows that need to be moved. */\n      MINFRE = NFILL;\n      NFREE = LFREE-LROW;\n      if(NFREE<MINFRE) {\n        LU1REC(LUSOL, LUSOL->m,FALSE,&LROW,\n                      LUSOL->indr,LUSOL->lenr,LUSOL->locr);\n        LFILE = LROW;\n        ILAST = LUSOL->indr[LROW+1];\n        LPIVR = LUSOL->locr[IBEST];\n        LPIVR1 = LPIVR+1;\n        LPIVR2 = LPIVR+NELIM;\n        NFREE = LFREE-LROW;\n        if(NFREE<MINFRE) {\n            goto x970;\n        }\n      }\n/*            Move rows that have pending fill-in to end of the row file.\n              Then insert the fill-in. */\n      LU1PEN(LUSOL, NSPARE,&ILAST,\n             LPIVC1,LPIVC2,LPIVR1,LPIVR2,\n             &LROW,LUSOL->indr+LL1-LUSOL_ARRAYOFFSET,LUSOL->indr+LU1-LUSOL_ARRAYOFFSET);\n    }\n/*         ===============================================================\n           Restore the saved values of  iqloc.\n           Insert the correct indices for the col of L and the row of U.\n           =============================================================== */\nx700:\n    LUSOL->lenr[IBEST] = 0;\n    LUSOL->lenc[JBEST] = 0;\n    LL = LL1-1;\n    LS = LSAVE;\n    for(LC = LPIVC1; LC <= LPIVC2; LC++) {\n      LL++;\n      LS++;\n      I = LUSOL->indc[LC];\n      LUSOL->iqloc[I] = LUSOL->indr[LS];\n      LUSOL->indc[LL] = I;\n      LUSOL->indr[LL] = IBEST;\n    }\n    LU = LU1-1;\n    for(LR = LPIVR; LR <= LPIVR2; LR++) {\n      LU++;\n      LUSOL->indr[LU] = LUSOL->indr[LR];\n    }\n/*         ===============================================================\n           Free the space occupied by the pivot row\n           and update the column permutation.\n           Then free the space occupied by the pivot column\n           and update the row permutation.\n           nzchng is found in both calls to lu1pq2, but we use it only\n           after the second.\n           =============================================================== */\n    LU1PQ2(LUSOL, NCOLD, &NZCHNG,\n           LUSOL->indr+LPIVR-LUSOL_ARRAYOFFSET,\n           LUSOL->indc+LU1-LUSOL_ARRAYOFFSET, LUSOL->lenc,\n           LUSOL->iqloc, LUSOL->iq, LUSOL->iqinv);\n    LU1PQ2(LUSOL, NROWD, &NZCHNG,\n           LUSOL->indc+LPIVC-LUSOL_ARRAYOFFSET,\n           LUSOL->indc+LSAVE-LUSOL_ARRAYOFFSET, LUSOL->lenr,\n           LUSOL->iploc, LUSOL->ip, LUSOL->ipinv);\n    NZLEFT += NZCHNG;\n\n/*         ===============================================================\n           lu1mxr resets Amaxr(i) in each modified row i.\n           lu1mxc moves the largest aij to the top of each modified col j.\n           28 Jun 2002: Note that cols of L have an implicit diag of 1.0,\n                        so lu1mxr is called with ll1, not ll1+1, whereas\n                           lu1mxc is called with          lu1+1.\n           =============================================================== */\n    if(UTRI && TPP) {\n/*      Relax -- we're not keeping big elements at the top yet. */\n    }\n    else {\n      if(TRP && MELIM>0)\n#ifdef ClassicHamaxR\n        LU1MXR(LUSOL, LL1,LL,LUSOL->indc,AMAXR);\n#else\n        LU1MXR(LUSOL, LL1,LL,LUSOL->indc,LUSOL->amaxr);\n#endif\n\n      if(NELIM>0) {\n        LU1MXC(LUSOL, LU1+1,LU,LUSOL->indr);\n/*      Update modified columns in heap */\n        if(TCP) {\n          for(KK = LU1+1; KK <= LU; KK++) {\n            J = LUSOL->indr[KK];\n#ifdef ClassicHamaxR\n            K = HK[J];\n#else\n            K = LUSOL->Hk[J];\n#endif\n/*      Biggest aij in column j */\n            V = fabs(LUSOL->a[LUSOL->locc[J]]);\n#ifdef ClassicHamaxR\n            HCHANGE(HA,HJ,HK,HLEN,K,V,J,&H);\n#else\n            HCHANGE(LUSOL->Ha,LUSOL->Hj,LUSOL->Hk,HLEN,K,V,J,&H);\n#endif\n            HOPS += H;\n          }\n        }\n      }\n    }\n/*         ===============================================================\n           Negate lengths of pivot row and column so they will be\n           eliminated during compressions.\n           =============================================================== */\n    LUSOL->lenr[IBEST] = -NCOLD;\n    LUSOL->lenc[JBEST] = -NROWD;\n\n/*         Test for fatal bug: row or column lists overwriting L and U. */\n    if(LROW>LSAVE || LCOL>LSAVE)\n      goto x980;\n\n/*         Reset the file lengths if pivot row or col was at the end. */\n    if(IBEST==ILAST)\n      LROW = LUSOL->locr[IBEST];\n\n    if(JBEST==JLAST)\n      LCOL = LUSOL->locc[JBEST];\n\n  }\n/*      ------------------------------------------------------------------\n        End of main loop.\n        ------------------------------------------------------------------\n        ------------------------------------------------------------------\n        Normal exit.\n        Move empty rows and cols to the end of ip, iq.\n        Then finish with a dense LU if necessary.\n        ------------------------------------------------------------------ */\nx900:\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  LU1PQ3(LUSOL, LUSOL->m,LUSOL->lenr,LUSOL->ip,LUSOL->ipinv,&MRANK);\n  LU1PQ3(LUSOL, LUSOL->n,LUSOL->lenc,LUSOL->iq,LUSOL->iqinv,NRANK);\n  SETMIN(*NRANK, MRANK);\n  if(DENSLU) {\n#ifdef UseTimer\n    timer ( \"start\", 17 );\n#endif\n    LU1FUL(LUSOL, LEND,LU1,TPP,MLEFT,NLEFT,*NRANK,NROWU,LENL,LENU,\n           &NSING,KEEPLU,SMALL,LUSOL->a+LD-LUSOL_ARRAYOFFSET,LUSOL->locr);\n/* ***     21 Dec 1994: Bug in next line.\n   ***     nrank  = nrank - nsing */\n    *NRANK = MINMN-NSING;\n#ifdef UseTimer\n    timer ( \"finish\", 17 );\n#endif\n  }\n  *MINLEN = (*LENL)+(*LENU)+2*(LUSOL->m+LUSOL->n);\n  goto x990;\n/*      Not enough space free after a compress.\n        Set  minlen  to an estimate of the necessary value of  lena. */\nx970:\n  *INFORM = LUSOL_INFORM_ANEEDMEM;\n  *MINLEN = LENA2+LFILE+2*(LUSOL->m+LUSOL->n);\n  goto x990;\n/*      Fatal error.  This will never happen!\n       (Famous last words.) */\nx980:\n  *INFORM = LUSOL_INFORM_FATALERR;\n  goto x990;\n/*      Fatal error with TSP.  Diagonal pivot not found. */\nx985:\n  *INFORM = LUSOL_INFORM_NOPIVOT;\n/*      Exit. */\nx990:\n#ifdef UseTimer\n  timer ( \"finish\", 3 );\n#endif\n;\n}\n\n\n/* ==================================================================\n   lu1fac computes a factorization A = L*U, where A is a sparse\n   matrix with m rows and n columns, P*L*P' is lower triangular\n   and P*U*Q is upper triangular for certain permutations P, Q\n   (which are returned in the arrays ip, iq).\n   Stability is ensured by limiting the size of the elements of L.\n   The nonzeros of A are input via the parallel arrays a, indc, indr,\n   which should contain nelem entries of the form    aij,    i,    j\n   in any order.  There should be no duplicate pairs         i,    j.\n\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   +        Beware !!!   The row indices i must be in indc,         +\n   +              and the column indices j must be in indr.         +\n   +              (Not the other way round!)                        +\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n\n   It does not matter if some of the entries in a(*) are zero.\n   Entries satisfying  abs( a(i) ) .le. parmlu(3)  are ignored.\n   Other parameters in luparm and parmlu are described below.\n   The matrix A may be singular.  On exit, nsing = luparm(11) gives\n   the number of apparent singularities.  This is the number of\n   \"small\" diagonals of the permuted factor U, as judged by\n   the input tolerances Utol1 = parmlu(4) and  Utol2 = parmlu(5).\n   The diagonal element diagj associated with column j of A is\n   \"small\" if\n               abs( diagj ) .le. Utol1\n   or\n               abs( diagj ) .le. Utol2 * max( uj ),\n   where max( uj ) is the maximum element in the j-th column of U.\n   The position of such elements is returned in w(*).  In general,\n   w(j) = + max( uj ),  but if column j is a singularity,\n   w(j) = - max( uj ).  Thus, w(j) .le. 0 if column j appears to be\n   dependent on the other columns of A.\n   NOTE: lu1fac (like certain other sparse LU packages) does not\n   treat dense columns efficiently.  This means it will be slow\n   on \"arrow matrices\" of the form\n                A = (x       a)\n                    (  x     b)\n                    (    x   c)\n                    (      x d)\n                    (x x x x e)\n   if the numerical values in the dense column allow it to be\n   chosen LATE in the pivot order.\n   With TPP (Threshold Partial Pivoting), the dense column is\n   likely to be chosen late.\n   With TCP (Threshold Complete Pivoting), if any of a,b,c,d\n   is significantly larger than other elements of A, it will\n   be chosen as the first pivot and the dense column will be\n   eliminated, giving reasonably sparse factors.\n   However, if element e is so big that TCP chooses it, the factors\n   will become dense.  (It's hard to win on these examples!)\n   ------------------------------------------------------------------\n\n   Notes on the array names\n   ------------------------\n   During the LU factorization, the sparsity pattern of the matrix\n   being factored is stored twice: in a column list and a row list.\n   The column list is ( a, indc, locc, lenc )\n   where\n         a(*)    holds the nonzeros,\n         indc(*) holds the indices for the column list,\n         locc(j) points to the start of column j in a(*) and indc(*),\n         lenc(j) is the number of nonzeros in column j.\n   The row list is    (    indr, locr, lenr )\n   where\n         indr(*) holds the indices for the row list,\n         locr(i) points to the start of row i in indr(*),\n         lenr(i) is the number of nonzeros in row i.\n   At all stages of the LU factorization, ip contains a complete\n   row permutation.  At the start of stage k,  ip(1), ..., ip(k-1)\n   are the first k-1 rows of the final row permutation P.\n   The remaining rows are stored in an ordered list\n                        ( ip, iploc, ipinv )\n   where\n         iploc(nz) points to the start in ip(*) of the set of rows\n                   that currently contain nz nonzeros,\n         ipinv(i)  points to the position of row i in ip(*).\n   For example,\n         iploc(1) = k   (and this is where rows of length 1 {),\n         iploc(2) = k+p  if there are p rows of length 1\n                        (and this is where rows of length 2 {).\n   Similarly for iq, iqloc, iqinv.\n   ---------------------------------------------------------------------\n   INPUT PARAMETERS\n   m      (not altered) is the number of rows in A.\n   n      (not altered) is the number of columns in A.\n   nelem  (not altered) is the number of matrix entries given in\n          the arrays a, indc, indr.\n   lena   (not altered) is the dimension of  a, indc, indr.\n          This should be significantly larger than nelem.\n          Typically one should have\n             lena > max( 2*nelem, 10*m, 10*n, 10000 )\n          but some applications may need more.\n          On machines with virtual memory it is safe to have\n          lena \"far bigger than necessary\", since not all of the\n          arrays will be used.\n   a      (overwritten) contains entries   Aij  in   a(1:nelem).\n   indc   (overwritten) contains the indices i in indc(1:nelem).\n   indr   (overwritten) contains the indices j in indr(1:nelem).\n   luparm input parameters:                                Typical value\n   luparm( 1) = nout     File number for printed messages.         6\n   luparm( 2) = lprint   Print level.                              0\n                    <  0 suppresses output.\n                    =  0 gives error messages.\n                   >= 10 gives statistics about the LU factors.\n                   >= 50 gives debug output from lu1fac\n                         (the pivot row and column and the\n                         no. of rows and columns involved at\n                         each elimination step).\n   luparm( 3) = maxcol   lu1fac: maximum number of columns         5\n                         searched allowed in a Markowitz-type\n                         search for the next pivot element.\n                         For some of the factorization, the\n                         number of rows searched is\n                         maxrow = maxcol - 1.\n   luparm( 6) = 0    =>  TPP: Threshold Partial   Pivoting.        0\n              = 1    =>  TRP: Threshold Rook      Pivoting.\n              = 2    =>  TCP: Threshold Complete  Pivoting.\n              = 3    =>  TSP: Threshold Symmetric Pivoting.\n              = 4    =>  TDP: Threshold Diagonal  Pivoting.\n                              (TDP not yet implemented).\n                         TRP and TCP are more expensive than TPP but\n                         more stable and better at revealing rank.\n                         Take care with setting parmlu(1), especially\n                         with TCP.\n                         NOTE: TSP and TDP are for symmetric matrices\n                         that are either definite or quasi-definite.\n                         TSP is effectively TRP for symmetric matrices.\n                         TDP is effectively TCP for symmetric matrices.\n   luparm( 8) = keepLU   lu1fac: keepLU = 1 means the numerical    1\n                         factors will be computed if possible.\n                         keepLU = 0 means L and U will be discarded\n                         but other information such as the row and\n                         column permutations will be returned.\n                         The latter option requires less storage.\n   parmlu input parameters:                                Typical value\n   parmlu( 1) = Ltol1    Max Lij allowed during Factor.\n                                                   TPP     10.0 or 100.0\n                                                   TRP      4.0 or  10.0\n                                                   TCP      5.0 or  10.0\n                                                   TSP      4.0 or  10.0\n                         With TRP and TCP (Rook and Complete Pivoting),\n                         values less than 25.0 may be expensive\n                         on badly scaled data.  However,\n                         values less than 10.0 may be needed\n                         to obtain a reliable rank-revealing\n                         factorization.\n   parmlu( 2) = Ltol2    Max Lij allowed during Updates.            10.0\n                         during updates.\n   parmlu( 3) = small    Absolute tolerance for       eps**0.8 = 3.0d-13\n                         treating reals as zero.\n   parmlu( 4) = Utol1    Absolute tol for flagging    eps**0.67= 3.7d-11\n                         small diagonals of U.\n   parmlu( 5) = Utol2    Relative tol for flagging    eps**0.67= 3.7d-11\n                         small diagonals of U.\n                         (eps = machine precision)\n   parmlu( 6) = Uspace   Factor limiting waste space in  U.      3.0\n                         In lu1fac, the row or column lists\n                         are compressed if their length\n                         exceeds Uspace times the length of\n                         either file after the last compression.\n   parmlu( 7) = dens1    The density at which the Markowitz      0.3\n                         pivot strategy should search maxcol\n                         columns and no rows.\n                         (Use 0.3 unless you are experimenting\n                         with the pivot strategy.)\n   parmlu( 8) = dens2    the density at which the Markowitz      0.5\n                         strategy should search only 1 column,\n                         or (if storage is available)\n                         the density at which all remaining\n                         rows and columns will be processed\n                         by a dense LU code.\n                         For example, if dens2 = 0.1 and lena is\n                         large enough, a dense LU will be used\n                         once more than 10 per cent of the\n                         remaining matrix is nonzero.\n\n   OUTPUT PARAMETERS\n   a, indc, indr     contain the nonzero entries in the LU factors of A.\n          If keepLU = 1, they are in a form suitable for use\n          by other parts of the LUSOL package, such as lu6sol.\n          U is stored by rows at the start of a, indr.\n          L is stored by cols at the end   of a, indc.\n          If keepLU = 0, only the diagonals of U are stored, at the\n          end of a.\n   ip, iq    are the row and column permutations defining the\n          pivot order.  For example, row ip(1) and column iq(1)\n          defines the first diagonal of U.\n   lenc(1:numl0) contains the number of entries in nontrivial\n          columns of L (in pivot order).\n   lenr(1:m) contains the number of entries in each row of U\n          (in original order).\n   locc(1:n) = 0 (ready for the LU update routines).\n   locr(1:m) points to the beginning of the rows of U in a, indr.\n   iploc, iqloc, ipinv, iqinv  are undefined.\n   w      indicates singularity as described above.\n   inform = 0 if the LU factors were obtained successfully.\n          = 1 if U appears to be singular, as judged by lu6chk.\n          = 3 if some index pair indc(l), indr(l) lies outside\n              the matrix dimensions 1:m , 1:n.\n          = 4 if some index pair indc(l), indr(l) duplicates\n              another such pair.\n          = 7 if the arrays a, indc, indr were not large enough.\n              Their length \"lena\" should be increase to at least\n              the value \"minlen\" given in luparm(13).\n          = 8 if there was some other fatal error.  (Shouldn't happen!)\n          = 9 if no diagonal pivot could be found with TSP or TDP.\n              The matrix must not be sufficiently definite\n              or quasi-definite.\n   luparm output parameters:\n   luparm(10) = inform   Return code from last call to any LU routine.\n   luparm(11) = nsing    No. of singularities marked in the\n                         output array w(*).\n   luparm(12) = jsing    Column index of last singularity.\n   luparm(13) = minlen   Minimum recommended value for  lena.\n   luparm(14) = maxlen   ?\n   luparm(15) = nupdat   No. of updates performed by the lu8 routines.\n   luparm(16) = nrank    No. of nonempty rows of U.\n   luparm(17) = ndens1   No. of columns remaining when the density of\n                         the matrix being factorized reached dens1.\n   luparm(18) = ndens2   No. of columns remaining when the density of\n                         the matrix being factorized reached dens2.\n   luparm(19) = jumin    The column index associated with DUmin.\n   luparm(20) = numL0    No. of columns in initial  L.\n   luparm(21) = lenL0    Size of initial  L  (no. of nonzeros).\n   luparm(22) = lenU0    Size of initial  U.\n   luparm(23) = lenL     Size of current  L.\n   luparm(24) = lenU     Size of current  U.\n   luparm(25) = lrow     Length of row file.\n   luparm(26) = ncp      No. of compressions of LU data structures.\n   luparm(27) = mersum   lu1fac: sum of Markowitz merit counts.\n   luparm(28) = nUtri    lu1fac: triangular rows in U.\n   luparm(29) = nLtri    lu1fac: triangular rows in L.\n   luparm(30) =\n   parmlu output parameters:\n   parmlu(10) = Amax     Maximum element in  A.\n   parmlu(11) = Lmax     Maximum multiplier in current  L.\n   parmlu(12) = Umax     Maximum element in current  U.\n   parmlu(13) = DUmax    Maximum diagonal in  U.\n   parmlu(14) = DUmin    Minimum diagonal in  U.\n   parmlu(15) = Akmax    Maximum element generated at any stage\n                         during TCP factorization.\n   parmlu(16) = growth   TPP: Umax/Amax    TRP, TCP, TSP: Akmax/Amax\n   parmlu(17) =\n   parmlu(18) =\n   parmlu(19) =\n   parmlu(20) = resid    lu6sol: residual after solve with U or U'.\n   ...\n   parmlu(30) =\n   ------------------------------------------------------------------\n   00 Jun 1983  Original version.\n   00 Jul 1987  nrank  saved in luparm(16).\n   12 Apr 1989  ipinv, iqinv added as workspace.\n   26 Apr 1989  maxtie replaced by maxcol in Markowitz search.\n   16 Mar 1992  jumin  saved in luparm(19).\n   10 Jun 1992  lu1fad has to move empty rows and cols to the bottom\n                (via lu1pq3) before doing the dense LU.\n   12 Jun 1992  Deleted dense LU (lu1ful, lu1vlu).\n   25 Oct 1993  keepLU implemented.\n   07 Feb 1994  Added new dense LU (lu1ful, lu1den).\n   21 Dec 1994  Bugs fixed in lu1fad (nrank) and lu1ful (ipvt).\n   08 Aug 1995  Use ip instead of w as parameter to lu1or3 (for F90).\n   13 Sep 2000  TPP and TCP options implemented.\n   17 Oct 2000  Fixed troubles due to A = empty matrix (Todd Munson).\n   01 Dec 2000  Save Lmax, Umax, etc. after both lu1fad and lu6chk.\n                lu1fad sets them when keepLU = false.\n                lu6chk sets them otherwise, and includes items\n                from the dense LU.\n   11 Mar 2001  lu6chk now looks at diag(U) when keepLU = false.\n   26 Apr 2002  New TCP implementation using heap routines to\n                store largest element in each column.\n                New workspace arrays Ha, Hj, Hk required.\n                For compatibility, borrow space from a, indc, indr\n                rather than adding new input parameters.\n   01 May 2002  lu1den changed to lu1DPP (dense partial  pivoting).\n                lu1DCP implemented       (dense complete pivoting).\n                Both TPP and TCP now switch to dense mode and end.\n   ================================================================== */\nvoid LU1FAC(LUSOLrec *LUSOL, int *INFORM)\n{\n  MYBOOL  KEEPLU, TCP, TPP, TRP, TSP;\n  int     LPIV, NELEM0, LPRINT, MINLEN, NUML0, LENL, LENU, LROW, MERSUM,\n          NUTRI, NLTRI, NDENS1, NDENS2, NRANK, NSING, JSING, JUMIN, NUMNZ, LERR,\n          LU, LL, LM, LTOPL, K, I, LENUK, J, LENLK, IDUMMY, LLSAVE, NMOVE, L2, L, NCP, NBUMP;\n#ifdef ClassicHamaxR\n  int     LENH, LENA2, LOCH, LMAXR;\n#endif\n\n  REAL    LMAX, LTOL, SMALL, AMAX, UMAX, DUMAX, DUMIN, AKMAX, DM, DN, DELEM, DENSTY,\n          AGRWTH, UGRWTH, GROWTH, CONDU, DINCR, AVGMER;\n\n/*      Free row-based version of L0 (regenerated by LUSOL_btran). */\n  if(LUSOL->L0 != NULL)\n    LUSOL_matfree(&(LUSOL->L0));\n\n/*      Grab relevant input parameters. */\n  NELEM0 = LUSOL->nelem;\n  LPRINT = LUSOL->luparm[LUSOL_IP_PRINTLEVEL];\n  LPIV   = LUSOL->luparm[LUSOL_IP_PIVOTTYPE];\n  KEEPLU = (MYBOOL) (LUSOL->luparm[LUSOL_IP_KEEPLU]!=FALSE);\n/*      Limit on size of Lij */\n  LTOL   = LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij];\n/*      Drop tolerance */\n  SMALL  = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  TPP = (MYBOOL) (LPIV==LUSOL_PIVMOD_TPP);\n  TRP = (MYBOOL) (LPIV==LUSOL_PIVMOD_TRP);\n  TCP = (MYBOOL) (LPIV==LUSOL_PIVMOD_TCP);\n  TSP = (MYBOOL) (LPIV==LUSOL_PIVMOD_TSP);\n/*      Initialize output parameters. */\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  LERR   = 0;\n  MINLEN = LUSOL->nelem + 2*(LUSOL->m+LUSOL->n);\n  NUML0  = 0;\n  LENL   = 0;\n  LENU   = 0;\n  LROW   = 0;\n  MERSUM = 0;\n  NUTRI  = LUSOL->m;\n  NLTRI  = 0;\n  NDENS1 = 0;\n  NDENS2 = 0;\n  NRANK  = 0;\n  NSING  = 0;\n  JSING  = 0;\n  JUMIN  = 0;\n  AMAX   = ZERO;\n  LMAX   = ZERO;\n  UMAX   = ZERO;\n  DUMAX  = ZERO;\n  DUMIN  = ZERO;\n  AKMAX  = ZERO;\n\n/*      Float version of dimensions. */\n  DM = LUSOL->m;\n  DN = LUSOL->n;\n  DELEM = LUSOL->nelem;\n\n/*      Initialize workspace parameters. */\n  LUSOL->luparm[LUSOL_IP_COMPRESSIONS_LU] = 0;\n  if(LUSOL->lena < MINLEN) {\n    if(!LUSOL_realloc_a(LUSOL, MINLEN))\n      goto x970;\n  }\n\n/*      ------------------------------------------------------------------\n        Organize the  aij's  in  a, indc, indr.\n        lu1or1  deletes small entries, tests for illegal  i,j's,\n                and counts the nonzeros in each row and column.\n        lu1or2  reorders the elements of  A  by columns.\n        lu1or3  uses the column list to test for duplicate entries\n                (same indices  i,j).\n        lu1or4  constructs a row list from the column list.\n        ------------------------------------------------------------------ */\n  LU1OR1(LUSOL, SMALL,&AMAX,&NUMNZ,&LERR,INFORM);\n  if(LPRINT>=LUSOL_MSG_STATISTICS) {\n    DENSTY = (100*DELEM)/(DM*DN);\n    LUSOL_report(LUSOL, 0, \"m:%6d %c n:%6d  nzcount:%9d  Amax:%g  Density:%g\\n\",\n                           LUSOL->m, relationChar(LUSOL->m, LUSOL->n), LUSOL->n,\n                           LUSOL->nelem, AMAX, DENSTY);\n  }\n  if(*INFORM!=LUSOL_INFORM_LUSUCCESS)\n    goto x930;\n  LUSOL->nelem = NUMNZ;\n  LU1OR2(LUSOL);\n  LU1OR3(LUSOL, &LERR,INFORM);\n  if(*INFORM!=LUSOL_INFORM_LUSUCCESS)\n    goto x940;\n  LU1OR4(LUSOL);\n/*      ------------------------------------------------------------------\n        Set up lists of rows and columns with equal numbers of nonzeros,\n        using  indc(*)  as workspace.\n        ------------------------------------------------------------------ */\n  LU1PQ1(LUSOL, LUSOL->m,LUSOL->n,LUSOL->lenr,\n         LUSOL->ip,LUSOL->iploc,LUSOL->ipinv,\n         LUSOL->indc+LUSOL->nelem); /* LUSOL_ARRAYOFFSET implied */\n  LU1PQ1(LUSOL, LUSOL->n,LUSOL->m,LUSOL->lenc,\n         LUSOL->iq,LUSOL->iqloc,LUSOL->iqinv,\n         LUSOL->indc+LUSOL->nelem); /* LUSOL_ARRAYOFFSET implied */\n/*      ------------------------------------------------------------------\n        For TCP, Ha, Hj, Hk are allocated separately, similarly amaxr\n        for TRP. Then compute the factorization  A = L*U.\n        ------------------------------------------------------------------ */\n#ifdef ClassicHamaxR\n  if(TPP || TSP) {\n    LENH  = 1;\n    LENA2 = LUSOL->lena;\n    LOCH  = LUSOL->lena;\n    LMAXR = 1;\n  }\n  else if(TRP) {\n    LENH  = 1;                     /* Dummy                                */\n    LENA2 = LUSOL->lena-LUSOL->m;  /* Reduced length of      a             */\n    LOCH  = LUSOL->lena;           /* Dummy                                */\n    LMAXR = LENA2+1;               /* Start of Amaxr      in a             */\n  }\n  else if(TCP) {\n    LENH  = LUSOL->n;              /* Length of heap                       */\n    LENA2 = LUSOL->lena-LENH;      /* Reduced length of      a, indc, indr */\n    LOCH  = LENA2+1;               /* Start of Ha, Hj, Hk in a, indc, indr */\n    LMAXR = 1;                     /* Dummy                                */\n  }\n  LU1FAD(LUSOL,\n         LENA2,LENH,\n         LUSOL->a+LOCH-LUSOL_ARRAYOFFSET,\n         LUSOL->indc+LOCH-LUSOL_ARRAYOFFSET,\n         LUSOL->indr+LOCH-LUSOL_ARRAYOFFSET,\n         LUSOL->a+LMAXR-LUSOL_ARRAYOFFSET,\n         INFORM,&LENL,&LENU,\n         &MINLEN,&MERSUM,&NUTRI,&NLTRI,&NDENS1,&NDENS2,\n         &NRANK,&LMAX,&UMAX,&DUMAX,&DUMIN,&AKMAX);\n#else\n  LU1FAD(LUSOL,\n         INFORM,&LENL,&LENU,\n         &MINLEN,&MERSUM,&NUTRI,&NLTRI,&NDENS1,&NDENS2,\n         &NRANK,&LMAX,&UMAX,&DUMAX,&DUMIN,&AKMAX);\n#endif\n  LUSOL->luparm[LUSOL_IP_RANK_U]     = NRANK;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_L] = LENL;\n  if(*INFORM==LUSOL_INFORM_ANEEDMEM)\n    goto x970;\n  if(*INFORM==LUSOL_INFORM_NOPIVOT)\n    goto x985;\n  if(*INFORM>LUSOL_INFORM_LUSUCCESS)\n    goto x980;\n  if(KEEPLU) {\n/*         ---------------------------------------------------------------\n           The LU factors are at the top of  a, indc, indr,\n           with the columns of  L  and the rows of  U  in the order\n           ( free )   ... ( u3 ) ( l3 ) ( u2 ) ( l2 ) ( u1 ) ( l1 ).\n           Starting with ( l1 ) and ( u1 ), move the rows of  U  to the\n           left and the columns of  L  to the right, giving\n           ( u1 ) ( u2 ) ( u3 ) ...   ( free )   ... ( l3 ) ( l2 ) ( l1 ).\n           Also, set  numl0 = the number of nonempty columns of  U.\n           --------------------------------------------------------------- */\n    LU = 0;\n    LL = LUSOL->lena+1;\n#ifdef ClassicHamaxR\n    LM = LENA2+1;\n#else\n    LM = LL;\n#endif\n    LTOPL = LL-LENL-LENU;\n    LROW = LENU;\n    for(K = 1; K <= NRANK; K++) {\n      I = LUSOL->ip[K];\n      LENUK = -LUSOL->lenr[I];\n      LUSOL->lenr[I] = LENUK;\n      J = LUSOL->iq[K];\n      LENLK = -LUSOL->lenc[J]-1;\n      if(LENLK>0) {\n        NUML0++;\n        LUSOL->iqloc[NUML0] = LENLK;\n      }\n      if(LU+LENUK<LTOPL) {\n/*               =========================================================\n                 There is room to move ( uk ).  Just right-shift ( lk ).\n                 ========================================================= */\n        for(IDUMMY = 1; IDUMMY <= LENLK; IDUMMY++) {\n          LL--;\n          LM--;\n          LUSOL->a[LL] = LUSOL->a[LM];\n          LUSOL->indc[LL] = LUSOL->indc[LM];\n          LUSOL->indr[LL] = LUSOL->indr[LM];\n        }\n      }\n      else {\n/*               =========================================================\n                 There is no room for ( uk ) yet.  We have to\n                 right-shift the whole of the remaining LU file.\n                 Note that ( lk ) ends up in the correct place.\n                 ========================================================= */\n        LLSAVE = LL-LENLK;\n        NMOVE = LM-LTOPL;\n        for(IDUMMY = 1; IDUMMY <= NMOVE; IDUMMY++) {\n          LL--;\n          LM--;\n          LUSOL->a[LL] = LUSOL->a[LM];\n          LUSOL->indc[LL] = LUSOL->indc[LM];\n          LUSOL->indr[LL] = LUSOL->indr[LM];\n        }\n        LTOPL = LL;\n        LL = LLSAVE;\n        LM = LL;\n      }\n/*            ======================================================\n              Left-shift ( uk ).\n              ====================================================== */\n      LUSOL->locr[I] = LU+1;\n      L2 = LM-1;\n      LM = LM-LENUK;\n      for(L = LM; L <= L2; L++) {\n        LU = LU+1;\n        LUSOL->a[LU] = LUSOL->a[L];\n        LUSOL->indr[LU] = LUSOL->indr[L];\n      }\n    }\n/*         ---------------------------------------------------------------\n           Save the lengths of the nonempty columns of  L,\n           and initialize  locc(j)  for the LU update routines.\n           --------------------------------------------------------------- */\n    for(K = 1; K <= NUML0; K++) {\n      LUSOL->lenc[K] = LUSOL->iqloc[K];\n    }\n    for(J = 1; J <= LUSOL->n; J++) {\n      LUSOL->locc[J] = 0;\n    }\n/*         ---------------------------------------------------------------\n           Test for singularity.\n           lu6chk  sets  nsing, jsing, jumin, Lmax, Umax, DUmax, DUmin\n           (including entries from the dense LU).\n           inform = 1  if there are singularities (nsing gt 0).\n           --------------------------------------------------------------- */\n    LU6CHK(LUSOL, 1,LUSOL->lena,INFORM);\n    NSING = LUSOL->luparm[LUSOL_IP_SINGULARITIES];\n    JSING = LUSOL->luparm[LUSOL_IP_SINGULARINDEX];\n    JUMIN = LUSOL->luparm[LUSOL_IP_COLINDEX_DUMIN];\n    LMAX  = LUSOL->parmlu[LUSOL_RP_MAXMULT_L];\n    UMAX  = LUSOL->parmlu[LUSOL_RP_MAXELEM_U];\n    DUMAX = LUSOL->parmlu[LUSOL_RP_MAXELEM_DIAGU];\n    DUMIN = LUSOL->parmlu[LUSOL_RP_MINELEM_DIAGU];\n  }\n  else {\n/*         ---------------------------------------------------------------\n           keepLU = 0.  L and U were not kept, just the diagonals of U.\n           lu1fac will probably be called again soon with keepLU = .true.\n           11 Mar 2001: lu6chk revised.  We can call it with keepLU = 0,\n                        but we want to keep Lmax, Umax from lu1fad.\n           05 May 2002: Allow for TCP with new lu1DCP.  Diag(U) starts\n                        below lena2, not lena.  Need lena2 in next line.\n           --------------------------------------------------------------- */\n#ifdef ClassicHamaxR\n    LU6CHK(LUSOL, 1,LENA2,INFORM);\n#else\n    LU6CHK(LUSOL, 1,LUSOL->lena,INFORM);\n#endif\n    NSING = LUSOL->luparm[LUSOL_IP_SINGULARITIES];\n    JSING = LUSOL->luparm[LUSOL_IP_SINGULARINDEX];\n    JUMIN = LUSOL->luparm[LUSOL_IP_COLINDEX_DUMIN];\n    DUMAX = LUSOL->parmlu[LUSOL_RP_MAXELEM_DIAGU];\n    DUMIN = LUSOL->parmlu[LUSOL_RP_MINELEM_DIAGU];\n  }\n  goto x990;\n/*      ------------\n        Error exits.\n        ------------ */\nx930:\n  *INFORM = LUSOL_INFORM_ADIMERR;\n  if(LPRINT>=LUSOL_MSG_SINGULARITY)\n    LUSOL_report(LUSOL, 0, \"lu1fac  error...\\nentry  a[%d]  has an illegal row (%d) or column (%d) index\\n\",\n                        LERR,LUSOL->indc[LERR],LUSOL->indr[LERR]);\n  goto x990;\nx940:\n  *INFORM = LUSOL_INFORM_ADUPLICATE;\n  if(LPRINT>=LUSOL_MSG_SINGULARITY)\n    LUSOL_report(LUSOL, 0, \"lu1fac  error...\\nentry  a[%d]  is a duplicate with indeces indc=%d, indr=%d\\n\",\n                        LERR,LUSOL->indc[LERR],LUSOL->indr[LERR]);\n  goto x990;\nx970:\n  *INFORM = LUSOL_INFORM_ANEEDMEM;\n  if(LPRINT>=LUSOL_MSG_SINGULARITY)\n    LUSOL_report(LUSOL, 0, \"lu1fac  error...\\ninsufficient storage; increase  lena  from %d to at least %d\\n\",\n                        LUSOL->lena, MINLEN);\n  goto x990;\nx980:\n  *INFORM = LUSOL_INFORM_FATALERR;\n  if(LPRINT>=LUSOL_MSG_SINGULARITY)\n    LUSOL_report(LUSOL, 0, \"lu1fac  error...\\nfatal bug   (sorry --- this should never happen)\\n\");\n  goto x990;\nx985:\n  *INFORM = LUSOL_INFORM_NOPIVOT;\n  if(LPRINT>=LUSOL_MSG_SINGULARITY)\n    LUSOL_report(LUSOL, 0, \"lu1fac  error...\\nTSP used but diagonal pivot could not be found\\n\");\n\n/*      Finalize and store output parameters. */\nx990:\n  LUSOL->nelem = NELEM0;\n  LUSOL->luparm[LUSOL_IP_SINGULARITIES]   = NSING;\n  LUSOL->luparm[LUSOL_IP_SINGULARINDEX]   = JSING;\n  LUSOL->luparm[LUSOL_IP_MINIMUMLENA]     = MINLEN;\n  LUSOL->luparm[LUSOL_IP_UPDATECOUNT]     = 0;\n  LUSOL->luparm[LUSOL_IP_RANK_U]          = NRANK;\n  LUSOL->luparm[LUSOL_IP_COLCOUNT_DENSE1] = NDENS1;\n  LUSOL->luparm[LUSOL_IP_COLCOUNT_DENSE2] = NDENS2;\n  LUSOL->luparm[LUSOL_IP_COLINDEX_DUMIN]  = JUMIN;\n  LUSOL->luparm[LUSOL_IP_COLCOUNT_L0]     = NUML0;\n  LUSOL->luparm[LUSOL_IP_ROWCOUNT_L0]     = 0;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_L0]     = LENL;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_U0]     = LENU;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_L]      = LENL;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_U]      = LENU;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_ROW]    = LROW;\n  LUSOL->luparm[LUSOL_IP_MARKOWITZ_MERIT] = MERSUM;\n  LUSOL->luparm[LUSOL_IP_TRIANGROWS_U]    = NUTRI;\n  LUSOL->luparm[LUSOL_IP_TRIANGROWS_L]    = NLTRI;\n  LUSOL->parmlu[LUSOL_RP_MAXELEM_A]       = AMAX;\n  LUSOL->parmlu[LUSOL_RP_MAXMULT_L]       = LMAX;\n  LUSOL->parmlu[LUSOL_RP_MAXELEM_U]       = UMAX;\n  LUSOL->parmlu[LUSOL_RP_MAXELEM_DIAGU]   = DUMAX;\n  LUSOL->parmlu[LUSOL_RP_MINELEM_DIAGU]   = DUMIN;\n  LUSOL->parmlu[LUSOL_RP_MAXELEM_TCP]     = AKMAX;\n  AGRWTH = AKMAX/(AMAX+LUSOL_SMALLNUM);\n  UGRWTH = UMAX/(AMAX+LUSOL_SMALLNUM);\n  if(TPP)\n    GROWTH = UGRWTH;\n/*      TRP or TCP or TSP */\n  else\n    GROWTH = AGRWTH;\n  LUSOL->parmlu[LUSOL_RP_GROWTHRATE]      = GROWTH;\n\n  LUSOL->luparm[LUSOL_IP_FTRANCOUNT]      = 0;\n  LUSOL->luparm[LUSOL_IP_BTRANCOUNT]      = 0;\n\n/*      ------------------------------------------------------------------\n        Set overall status variable.\n        ------------------------------------------------------------------ */\n  LUSOL->luparm[LUSOL_IP_INFORM]          = *INFORM;\n  if(*INFORM == LUSOL_INFORM_NOMEMLEFT)\n    LUSOL_report(LUSOL, 0, \"lu1fac  error...\\ninsufficient memory available\\n\");\n\n/*      ------------------------------------------------------------------\n        Print statistics for the LU factors.\n        ------------------------------------------------------------------ */\n  NCP   = LUSOL->luparm[LUSOL_IP_COMPRESSIONS_LU];\n  CONDU = DUMAX/MAX(DUMIN,LUSOL_SMALLNUM);\n  DINCR = (LENL+LENU)-LUSOL->nelem;\n  DINCR = (DINCR*100)/MAX(DELEM,ONE);\n  AVGMER = MERSUM;\n  AVGMER = AVGMER/DM;\n  NBUMP = LUSOL->m-NUTRI-NLTRI;\n  if(LPRINT>=LUSOL_MSG_STATISTICS) {\n    if(TPP) {\n      LUSOL_report(LUSOL, 0, \"Merit %g %d %d %d %g %d %d %g %g %d %d %d\\n\",\n                          AVGMER,LENL,LENL+LENU,NCP,DINCR,NUTRI,LENU,\n                          LTOL,UMAX,UGRWTH,NLTRI,NDENS1,LMAX);\n    }\n    else {\n      LUSOL_report(LUSOL, 0, \"Merit %s %g %d %d %d %g %d %d %g %g %d %d %d %g %g\\n\",\n                          LUSOL_pivotLabel(LUSOL),\n                          AVGMER,LENL,LENL+LENU,NCP,DINCR,NUTRI,LENU,\n                          LTOL,UMAX,UGRWTH,NLTRI,NDENS1,LMAX,AKMAX,AGRWTH);\n    }\n    LUSOL_report(LUSOL, 0, \"bump%9d  dense2%7d  DUmax%g DUmin%g  conDU%g\\n\",\n                          NBUMP,NDENS2,DUMAX,DUMIN,CONDU);\n  }\n}\n\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol2.c",
    "content": "\n/* ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   File  lusol2 LUSOL heap management routines\n   Hbuild   Hchange  Hdelete  Hdown    Hinsert  Hup\n   Heap-management routines for LUSOL's lu1fac.\n   May be useful for other applications.\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   For LUSOL, the heap structure involves three arrays of length N.\n   N        is the current number of entries in the heap.\n   Ha(1:N)  contains the values that the heap is partially sorting.\n            For LUSOL they are double precision values -- the largest\n            element in each remaining column of the updated matrix.\n            The biggest entry is in Ha(1), the top of the heap.\n   Hj(1:N)  contains column numbers j.\n            Ha(k) is the biggest entry in column j = Hj(k).\n   Hk(1:N)  contains indices within the heap.  It is the\n            inverse of Hj(1:N), so  k = Hk(j)  <=>  j = Hj(k).\n            Column j is entry k in the heap.\n   hops     is the number of heap operations,\n            i.e., the number of times an entry is moved\n            (the number of \"hops\" up or down the heap).\n   Together, Hj and Hk let us find values inside the heap\n   whenever we want to change one of the values in Ha.\n   For other applications, Ha may need to be some other data type,\n   like the keys that sort routines operate on.\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   11 Feb 2002: MATLAB  version derived from \"Algorithms\" by\n                R. Sedgewick\n   03 Mar 2002: F77     version derived from MATLAB version.\n   07 May 2002: Safeguard input parameters k, N, Nk.\n                We don't want them to be output!\n   07 May 2002: Current version of lusol2.f.\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */\n\n/* ==================================================================\n   Hdown  updates heap by moving down tree from node k.\n   ------------------------------------------------------------------\n   01 May 2002: Need Nk for length of Hk.\n   05 May 2002: Change input paramter k to kk to stop k being output.\n   05 May 2002: Current version of Hdown.\n   ================================================================== */\nvoid HDOWN(REAL HA[], int HJ[], int HK[], int N, int K, int *HOPS)\n{\n  int  J, JJ, JV, N2;\n  REAL V;\n\n  *HOPS = 0;\n  V = HA[K];\n  JV = HJ[K];\n N2 = N/2;\n/*      while 1\n        break */\nx100:\n  if(K>N2)\n    goto x200;\n  (*HOPS)++;\n  J = K+K;\n  if(J<N) {\n    if(HA[J]<HA[J+1])\n      J++;\n  }\n/*      break */\n  if(V>=HA[J])\n    goto x200;\n  HA[K] = HA[J];\n  JJ = HJ[J];\n  HJ[K] = JJ;\n  HK[JJ] = K;\n  K = J;\n  goto x100;\n/*      end while */\nx200:\n  HA[K] = V;\n  HJ[K] = JV;\n  HK[JV] = K;\n}\n\n/* ==================================================================\n   Hup updates heap by moving up tree from node k.\n   ------------------------------------------------------------------\n   01 May 2002: Need Nk for length of Hk.\n   05 May 2002: Change input paramter k to kk to stop k being output.\n   05 May 2002: Current version of Hup.\n   ================================================================== */\nvoid HUP(REAL HA[], int HJ[], int HK[], int K, int *HOPS)\n{\n  int  J, JV, K2;\n  REAL V;\n\n  *HOPS = 0;\n  V = HA[K];\n JV = HJ[K];\n/*      while 1\n        break */\nx100:\n  if(K<2)\n    goto x200;\n  K2 = K/2;\n/*      break */\n  if(V<HA[K2])\n    goto x200;\n  (*HOPS)++;\n  HA[K] = HA[K2];\n  J = HJ[K2];\n  HJ[K] = J;\n  HK[J] = K;\n  K = K2;\n  goto x100;\n/*      end while */\nx200:\n  HA[K] = V;\n  HJ[K] = JV;\n  HK[JV] = K;\n}\n\n/* ==================================================================\n   Hinsert inserts (v,jv) into heap of length N-1\n   to make heap of length N.\n   ------------------------------------------------------------------\n   03 Apr 2002: First version of Hinsert.\n   01 May 2002: Require N to be final length, not old length.\n                Need Nk for length of Hk.\n   07 May 2002: Protect input parameters N, Nk.\n   07 May 2002: Current version of Hinsert.\n   ================================================================== */\nvoid HINSERT(REAL HA[], int HJ[], int HK[], int N,\n             REAL V, int JV, int *HOPS)\n{\n  HA[N] = V;\n  HJ[N] = JV;\n  HK[JV] = N;\n  HUP(HA,HJ,HK,N,HOPS);\n}\n\n/* ==================================================================\n   Hchange changes Ha(k) to v in heap of length N.\n   ------------------------------------------------------------------\n   01 May 2002: Need Nk for length of Hk.\n   07 May 2002: Protect input parameters N, Nk, k.\n   07 May 2002: Current version of Hchange.\n   ================================================================== */\nvoid HCHANGE(REAL HA[], int HJ[], int HK[], int N, int K,\n             REAL V, int JV, int *HOPS)\n{\n  REAL V1;\n\n  V1 = HA[K];\n  HA[K] = V;\n  HJ[K] = JV;\n  HK[JV] = K;\n  if(V1<V)\n    HUP  (HA,HJ,HK,  K,HOPS);\n  else\n    HDOWN(HA,HJ,HK,N,K,HOPS);\n}\n\n/* ==================================================================\n   Hdelete deletes Ha(k) from heap of length N.\n   ------------------------------------------------------------------\n   03 Apr 2002: Current version of Hdelete.\n   01 May 2002: Need Nk for length of Hk.\n   07 May 2002: Protect input parameters N, Nk, k.\n   07 May 2002: Current version of Hdelete.\n   ================================================================== */\nvoid HDELETE(REAL HA[], int HJ[], int HK[], int *N, int K, int *HOPS)\n{\n\n  int  JV, NX;\n  REAL V;\n\n  NX = *N;\n  V = HA[NX];\n  JV = HJ[NX];\n  (*N)--;\n  *HOPS = 0;\n  if(K<NX)\n    HCHANGE(HA,HJ,HK,NX,K,V,JV,HOPS);\n}\n\n/* ==================================================================\n   Hbuild initializes the heap by inserting each element of Ha.\n   Input:  Ha, Hj.\n   Output: Ha, Hj, Hk, hops.\n   ------------------------------------------------------------------\n   01 May 2002: Use k for new length of heap, not k-1 for old length.\n   05 May 2002: Use kk in call to stop loop variable k being altered.\n                (Actually Hinsert no longer alters that parameter.)\n   07 May 2002: ftnchek wants us to protect Nk, Ha(k), Hj(k) too.\n   07 May 2002: Current version of Hbuild.\n   ================================================================== */\nvoid HBUILD(REAL HA[], int HJ[], int HK[], int N, int *HOPS)\n{\n  int  H, JV, K, KK;\n  REAL V;\n\n  *HOPS = 0;\n  for(K = 1; K <= N; K++) {\n    KK = K;\n    V = HA[K];\n    JV = HJ[K];\n    HINSERT(HA,HJ,HK,KK,V,JV,&H);\n    (*HOPS) += H;\n  }\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol6a.c",
    "content": "\n/* ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   File  lusol6a\n      lu6sol   lu6L     lu6Lt     lu6U     Lu6Ut   lu6LD   lu6chk\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   26 Apr 2002: lu6 routines put into a separate file.\n   15 Dec 2002: lu6sol modularized via lu6L, lu6Lt, lu6U, lu6Ut.\n                lu6LD implemented to allow solves with LDL' or L|D|L'.\n   15 Dec 2002: Current version of lusol6a.f.\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */\n\n/* ==================================================================\n   lu6chk  looks at the LU factorization  A = L*U.\n   If mode = 1, lu6chk is being called by lu1fac.\n   (Other modes not yet implemented.)\n   ------------------------------------------------------------------\n   The important input parameters are\n\n                  lprint = luparm(2)\n                  keepLU = luparm(8)\n                  Utol1  = parmlu(4)\n                  Utol2  = parmlu(5)\n\n   and the significant output parameters are\n\n                  inform = luparm(10)\n                  nsing  = luparm(11)\n                  jsing  = luparm(12)\n                  jumin  = luparm(19)\n                  Lmax   = parmlu(11)\n                  Umax   = parmlu(12)\n                  DUmax  = parmlu(13)\n                  DUmin  = parmlu(14)\n                  and      w(*).\n\n   Lmax  and Umax  return the largest elements in L and U.\n   DUmax and DUmin return the largest and smallest diagonals of U\n                   (excluding diagonals that are exactly zero).\n   In general, w(j) is set to the maximum absolute element in\n   the j-th column of U.  However, if the corresponding diagonal\n   of U is small in absolute terms or relative to w(j)\n   (as judged by the parameters Utol1, Utol2 respectively),\n   then w(j) is changed to - w(j).\n   Thus, if w(j) is not positive, the j-th column of A\n   appears to be dependent on the other columns of A.\n   The number of such columns, and the position of the last one,\n   are returned as nsing and jsing.\n   Note that nrank is assumed to be set already, and is not altered.\n   Typically, nsing will satisfy      nrank + nsing = n,  but if\n   Utol1 and Utol2 are rather large,  nsing > n - nrank   may occur.\n   If keepLU = 0,\n   Lmax  and Umax  are already set by lu1fac.\n   The diagonals of U are in the top of A.\n   Only Utol1 is used in the singularity test to set w(*).\n   inform = 0  if  A  appears to have full column rank  (nsing = 0).\n   inform = 1  otherwise  (nsing .gt. 0).\n   ------------------------------------------------------------------\n   00 Jul 1987: Early version.\n   09 May 1988: f77 version.\n   11 Mar 2001: Allow for keepLU = 0.\n   17 Nov 2001: Briefer output for singular factors.\n   05 May 2002: Comma needed in format 1100 (via Kenneth Holmstrom).\n   06 May 2002: With keepLU = 0, diags of U are in natural order.\n                They were not being extracted correctly.\n   23 Apr 2004: TRP can judge singularity better by comparing\n                all diagonals to DUmax.\n   27 Jun 2004: (PEG) Allow write only if nout .gt. 0.\n   ================================================================== */\n#ifdef UseOld_LU6CHK_20040510\nvoid LU6CHK(LUSOLrec *LUSOL, int MODE, int LENA2, int *INFORM)\n{\n  MYBOOL KEEPLU;\n  int    I, J, JUMIN, K, L, L1, L2, LENL, LPRINT, NDEFIC, NRANK;\n  REAL   AIJ, DIAG, DUMAX, DUMIN, LMAX, UMAX, UTOL1, UTOL2;\n\n  LPRINT = LUSOL->luparm[LUSOL_IP_PRINTLEVEL];\n  KEEPLU = (MYBOOL) (LUSOL->luparm[LUSOL_IP_KEEPLU]!=0);\n  NRANK = LUSOL->luparm[LUSOL_IP_RANK_U];\n  LENL  = LUSOL->luparm[LUSOL_IP_NONZEROS_L];\n  UTOL1 = LUSOL->parmlu[LUSOL_RP_SMALLDIAG_U];\n  UTOL2 = LUSOL->parmlu[LUSOL_RP_EPSDIAG_U];\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  LMAX  = ZERO;\n  UMAX  = ZERO;\n  LUSOL->luparm[LUSOL_IP_SINGULARITIES]  = 0;\n  LUSOL->luparm[LUSOL_IP_SINGULARINDEX]  = 0;\n  JUMIN = 0;\n  DUMAX = ZERO;\n  DUMIN = LUSOL_BIGNUM;\n\n#ifdef LUSOLFastClear\n  MEMCLEAR(LUSOL->w+1, LUSOL->n);\n#else\n  for(I = 1; I <= LUSOL->n; I++)\n    LUSOL->w[I] = ZERO;\n#endif\n\n  if(KEEPLU) {\n/*     --------------------------------------------------------------\n        Find  Lmax.\n       -------------------------------------------------------------- */\n    for(L = (LENA2+1)-LENL; L <= LENA2; L++) {\n      SETMAX(LMAX,fabs(LUSOL->a[L]));\n    }\n/*     --------------------------------------------------------------\n        Find Umax and set w(j) = maximum element in j-th column of U.\n       -------------------------------------------------------------- */\n    for(K = 1; K <= NRANK; K++) {\n      I = LUSOL->ip[K];\n      L1 = LUSOL->locr[I];\n      L2 = (L1+LUSOL->lenr[I])-1;\n      for(L = L1; L <= L2; L++) {\n        J = LUSOL->indr[L];\n        AIJ = fabs(LUSOL->a[L]);\n        SETMAX(LUSOL->w[J],AIJ);\n        SETMAX(UMAX,AIJ);\n      }\n    }\n/*     --------------------------------------------------------------\n        Negate w(j) if the corresponding diagonal of U is\n        too small in absolute terms or relative to the other elements\n        in the same column of  U.\n        Also find DUmax and DUmin, the extreme diagonals of U.\n       -------------------------------------------------------------- */\n    for(K = 1; K <= LUSOL->n; K++) {\n      J = LUSOL->iq[K];\n      if(K>NRANK)\n        DIAG = ZERO;\n      else {\n        I = LUSOL->ip[K];\n        L1 = LUSOL->locr[I];\n        DIAG = fabs(LUSOL->a[L1]);\n        SETMAX(DUMAX,DIAG);\n        if(DUMIN>DIAG) {\n          DUMIN = DIAG;\n          JUMIN = J;\n        }\n      }\n      if((DIAG<=UTOL1) || (DIAG<=UTOL2*LUSOL->w[J])) {\n        LUSOL_addSingularity(LUSOL, J, INFORM);\n        LUSOL->w[J] = -LUSOL->w[J];\n      }\n    }\n    LUSOL->parmlu[LUSOL_RP_MAXMULT_L] = LMAX;\n    LUSOL->parmlu[LUSOL_RP_MAXELEM_U] = UMAX;\n  }\n   else {\n/*     --------------------------------------------------------------\n        keepLU = 0.\n        Only diag(U) is stored.  Set w(*) accordingly.\n       -------------------------------------------------------------- */\n    for(K = 1; K <= LUSOL->n; K++) {\n      J = LUSOL->iq[K];\n      if(K>NRANK)\n        DIAG = ZERO;\n      else {\n/* !             diag   = abs( diagU(k) ) ! 06 May 2002: Diags are in natural order */\n        DIAG = fabs(LUSOL->diagU[J]);\n        LUSOL->w[J] = DIAG;\n        SETMAX(DUMAX,DIAG);\n        if(DUMIN>DIAG) {\n          DUMIN = DIAG;\n          JUMIN = J;\n        }\n      }\n      if(DIAG<=UTOL1) {\n        LUSOL_addSingularity(LUSOL, J, INFORM);\n        LUSOL->w[J] = -LUSOL->w[J];\n      }\n    }\n  }\n/*     -----------------------------------------------------------------\n        Set output parameters.\n       ----------------------------------------------------------------- */\n  if(JUMIN==0)\n    DUMIN = ZERO;\n  LUSOL->luparm[LUSOL_IP_COLINDEX_DUMIN] = JUMIN;\n  LUSOL->parmlu[LUSOL_RP_MAXELEM_DIAGU]  = DUMAX;\n  LUSOL->parmlu[LUSOL_RP_MINELEM_DIAGU]  = DUMIN;\n/*      The matrix has been judged singular. */\n  if(LUSOL->luparm[LUSOL_IP_SINGULARITIES]>0) {\n    *INFORM = LUSOL_INFORM_LUSINGULAR;\n    NDEFIC = LUSOL->n-NRANK;\n    if(LPRINT>=LUSOL_MSG_SINGULARITY) {\n      LUSOL_report(LUSOL, 0, \"Singular(m%cn)  rank:%9d  n-rank:%8d  nsing:%9d\\n\",\n                             relationChar(LUSOL->m, LUSOL->n),NRANK,NDEFIC,\n                             LUSOL->luparm[LUSOL_IP_SINGULARITIES]);\n    }\n  }\n/*      Exit. */\n  LUSOL->luparm[LUSOL_IP_INFORM] = *INFORM;\n}\n#else\nvoid LU6CHK(LUSOLrec *LUSOL, int MODE, int LENA2, int *INFORM)\n{\n  MYBOOL KEEPLU, TRP;\n  int    I, J, JUMIN, K, L, L1, L2, LENL, LDIAGU, LPRINT, NDEFIC, NRANK;\n  REAL   AIJ, DIAG, DUMAX, DUMIN, LMAX, UMAX, UTOL1, UTOL2;\n\n  LPRINT = LUSOL->luparm[LUSOL_IP_PRINTLEVEL];\n  KEEPLU = (MYBOOL) (LUSOL->luparm[LUSOL_IP_KEEPLU] != 0);\n  TRP    = (MYBOOL) (LUSOL->luparm[LUSOL_IP_PIVOTTYPE] == LUSOL_PIVMOD_TRP);\n  NRANK  = LUSOL->luparm[LUSOL_IP_RANK_U];\n  LENL   = LUSOL->luparm[LUSOL_IP_NONZEROS_L];\n  UTOL1  = LUSOL->parmlu[LUSOL_RP_SMALLDIAG_U];\n  UTOL2  = LUSOL->parmlu[LUSOL_RP_EPSDIAG_U];\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  LMAX   = ZERO;\n  UMAX   = ZERO;\n  LUSOL->luparm[LUSOL_IP_SINGULARITIES] = 0;\n  LUSOL->luparm[LUSOL_IP_SINGULARINDEX] = 0;\n  JUMIN  = 0;\n  DUMAX  = ZERO;\n  DUMIN  = LUSOL_BIGNUM;\n\n#ifdef LUSOLFastClear\n  MEMCLEAR(LUSOL->w+1, LUSOL->n);\n#else\n  for(I = 1; I <= LUSOL->n; I++)\n    LUSOL->w[I] = ZERO;\n#endif\n\n  if(KEEPLU) {\n/*     --------------------------------------------------------------\n        Find  Lmax.\n       -------------------------------------------------------------- */\n    for(L = (LENA2+1)-LENL; L <= LENA2; L++) {\n      SETMAX(LMAX,fabs(LUSOL->a[L]));\n     }\n/*     --------------------------------------------------------------\n        Find Umax and set w(j) = maximum element in j-th column of U.\n       -------------------------------------------------------------- */\n    for(K = 1; K <= NRANK; K++) {\n      I = LUSOL->ip[K];\n      L1 = LUSOL->locr[I];\n      L2 = (L1+LUSOL->lenr[I])-1;\n      for(L = L1; L <= L2; L++) {\n        J = LUSOL->indr[L];\n        AIJ = fabs(LUSOL->a[L]);\n        SETMAX(LUSOL->w[J],AIJ);\n        SETMAX(UMAX,AIJ);\n      }\n    }\n    LUSOL->parmlu[LUSOL_RP_MAXMULT_L] = LMAX;\n    LUSOL->parmlu[LUSOL_RP_MAXELEM_U] = UMAX;\n/*     --------------------------------------------------------------\n       Find DUmax and DUmin, the extreme diagonals of U.\n       -------------------------------------------------------------- */\n    for(K = 1; K <= NRANK; K++) {\n      J     = LUSOL->iq[K];\n      I     = LUSOL->ip[K];\n      L1    = LUSOL->locr[I];\n      DIAG  = fabs(LUSOL->a[L1]);\n      SETMAX( DUMAX, DIAG );\n      if(DUMIN > DIAG) {\n        DUMIN  = DIAG;\n        JUMIN  = J;\n      }\n    }\n  }\n  else {\n/*     --------------------------------------------------------------\n       keepLU = 0.\n       Only diag(U) is stored.  Set w(*) accordingly.\n       Find DUmax and DUmin, the extreme diagonals of U.\n       -------------------------------------------------------------- */\n    LDIAGU = LENA2 - LUSOL->n;\n    for(K = 1; K <= NRANK; K++) {\n      J           = LUSOL->iq[K];\n      DIAG        = fabs( LUSOL->a[LDIAGU + J] ); /* are in natural order */\n      LUSOL->w[J] = DIAG;\n      SETMAX( DUMAX, DIAG );\n      if(DUMIN > DIAG) {\n        DUMIN = DIAG;\n        JUMIN = J;\n      }\n    }\n  }\n/*     --------------------------------------------------------------\n       Negate w(j) if the corresponding diagonal of U is\n       too small in absolute terms or relative to the other elements\n       in the same column of  U.\n\n       23 Apr 2004: TRP ensures that diags are NOT small relative to\n                    other elements in their own column.\n                    Much better, we can compare all diags to DUmax.\n      -------------------------------------------------------------- */\n  if((MODE == 1) && TRP) {\n    SETMAX( UTOL1, UTOL2*DUMAX );\n  }\n\n  if(KEEPLU) {\n    for(K = 1; K <= LUSOL->n; K++) {\n      J = LUSOL->iq[K];\n      if(K>NRANK)\n        DIAG = ZERO;\n      else {\n        I = LUSOL->ip[K];\n        L1 = LUSOL->locr[I];\n        DIAG = fabs(LUSOL->a[L1]);\n      }\n      if((DIAG<=UTOL1) || (DIAG<=UTOL2*LUSOL->w[J])) {\n        LUSOL_addSingularity(LUSOL, J, INFORM);\n        LUSOL->w[J] = -LUSOL->w[J];\n      }\n    }\n  }\n  else { /* keepLU = FALSE */\n    for(K = 1; K <= LUSOL->n; K++) {\n      J = LUSOL->iq[K];\n      DIAG = LUSOL->w[J];\n      if(DIAG<=UTOL1) {\n        LUSOL_addSingularity(LUSOL, J, INFORM);\n        LUSOL->w[J] = -LUSOL->w[J];\n      }\n    }\n  }\n/*     -----------------------------------------------------------------\n        Set output parameters.\n       ----------------------------------------------------------------- */\n  if(JUMIN==0)\n    DUMIN = ZERO;\n  LUSOL->luparm[LUSOL_IP_COLINDEX_DUMIN] = JUMIN;\n  LUSOL->parmlu[LUSOL_RP_MAXELEM_DIAGU]  = DUMAX;\n  LUSOL->parmlu[LUSOL_RP_MINELEM_DIAGU]  = DUMIN;\n/*      The matrix has been judged singular. */\n  if(LUSOL->luparm[LUSOL_IP_SINGULARITIES]>0) {\n    *INFORM = LUSOL_INFORM_LUSINGULAR;\n    NDEFIC = LUSOL->n-NRANK;\n    if((LUSOL->outstream!=NULL) && (LPRINT>=LUSOL_MSG_SINGULARITY)) {\n      LUSOL_report(LUSOL, 0, \"Singular(m%cn)  rank:%9d  n-rank:%8d  nsing:%9d\\n\",\n                             relationChar(LUSOL->m, LUSOL->n),NRANK,NDEFIC,\n                             LUSOL->luparm[LUSOL_IP_SINGULARITIES]);\n    }\n  }\n/*      Exit. */\n  LUSOL->luparm[LUSOL_IP_INFORM] = *INFORM;\n}\n#endif\n\n\n/* ------------------------------------------------------------------\n   Include routines for row-based L0.\n   20 Apr 2005 Current version - KE.\n   ------------------------------------------------------------------ */\n#include \"lusol6l0.c\"\n\n\n/* ------------------------------------------------------------------\n   lu6L   solves   L v = v(input).\n   ------------------------------------------------------------------\n   15 Dec 2002: First version derived from lu6sol.\n   15 Dec 2002: Current version.\n   ------------------------------------------------------------------ */\nvoid LU6L(LUSOLrec *LUSOL, int *INFORM, REAL V[], int NZidx[])\n{\n  int  JPIV, K, L, L1, LEN, LENL, LENL0, NUML, NUML0;\n  REAL SMALL;\n  register REAL VPIV;\n#ifdef LUSOLFastSolve\n  REAL *aptr;\n  int  *iptr, *jptr;\n#else\n  int  I, J;\n#endif\n\n  NUML0 = LUSOL->luparm[LUSOL_IP_COLCOUNT_L0];\n  LENL0 = LUSOL->luparm[LUSOL_IP_NONZEROS_L0];\n  LENL  = LUSOL->luparm[LUSOL_IP_NONZEROS_L];\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  L1 = LUSOL->lena+1;\n  for(K = 1; K <= NUML0; K++) {\n    LEN = LUSOL->lenc[K];\n    L = L1;\n    L1 -= LEN;\n    JPIV = LUSOL->indr[L1];\n    VPIV = V[JPIV];\n    if(fabs(VPIV)>SMALL) {\n/*     ***** This loop could be coded specially. */\n#ifdef LUSOLFastSolve\n      L--;\n      for(aptr = LUSOL->a+L, iptr = LUSOL->indc+L;\n          LEN > 0; LEN--, aptr--, iptr--)\n        V[*iptr] += (*aptr) * VPIV;\n#else\n      for(; LEN > 0; LEN--) {\n        L--;\n        I = LUSOL->indc[L];\n        V[I] += LUSOL->a[L]*VPIV;\n      }\n#endif\n    }\n#ifdef SetSmallToZero\n    else\n      V[JPIV] = 0;\n#endif\n  }\n  L = (LUSOL->lena-LENL0)+1;\n  NUML = LENL-LENL0;\n/*     ***** This loop could be coded specially. */\n#ifdef LUSOLFastSolve\n  L--;\n  for(aptr = LUSOL->a+L, jptr = LUSOL->indr+L, iptr = LUSOL->indc+L;\n      NUML > 0; NUML--, aptr--, jptr--, iptr--) {\n    if(fabs(V[*jptr])>SMALL)\n      V[*iptr] += (*aptr) * V[*jptr];\n#ifdef SetSmallToZero\n    else\n      V[*jptr] = 0;\n#endif\n  }\n#else\n  for(; NUML > 0; NUML--) {\n    L--;\n    J = LUSOL->indr[L];\n    if(fabs(V[J])>SMALL) {\n      I = LUSOL->indc[L];\n      V[I] += LUSOL->a[L]*V[J];\n    }\n#ifdef SetSmallToZero\n    else\n      V[J] = 0;\n#endif\n  }\n#endif\n/*      Exit. */\n  LUSOL->luparm[LUSOL_IP_INFORM] = *INFORM;\n}\n\n/* ==================================================================\n   lu6LD  assumes lu1fac has computed factors A = LU of a\n   symmetric definite or quasi-definite matrix A,\n   using Threshold Symmetric Pivoting (TSP),   luparm(6) = 3,\n   or    Threshold Diagonal  Pivoting (TDP),   luparm(6) = 4.\n   It also assumes that no updates have been performed.\n   In such cases,  U = D L', where D = diag(U).\n   lu6LDL returns v as follows:\n\n   mode\n    1    v  solves   L D v = v(input).\n    2    v  solves   L|D|v = v(input).\n   ------------------------------------------------------------------\n   15 Dec 2002: First version of lu6LD.\n   15 Dec 2002: Current version.\n   ================================================================== */\nvoid LU6LD(LUSOLrec *LUSOL, int *INFORM, int MODE, REAL V[], int NZidx[])\n{\n  int  IPIV, K, L, L1, LEN, NUML0;\n  REAL DIAG, SMALL;\n  register REAL VPIV;\n#ifdef LUSOLFastSolve\n  REAL *aptr;\n  int  *jptr;\n#else\n  int  J;\n#endif\n\n/*      Solve L D v(new) = v  or  L|D|v(new) = v, depending on mode.\n        The code for L is the same as in lu6L,\n        but when a nonzero entry of v arises, we divide by\n        the corresponding entry of D or |D|. */\n  NUML0 = LUSOL->luparm[LUSOL_IP_COLCOUNT_L0];\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  L1 = LUSOL->lena+1;\n  for(K = 1; K <= NUML0; K++) {\n    LEN = LUSOL->lenc[K];\n    L = L1;\n    L1 -= LEN;\n    IPIV = LUSOL->indr[L1];\n    VPIV = V[IPIV];\n    if(fabs(VPIV)>SMALL) {\n/*     ***** This loop could be coded specially. */\n#ifdef LUSOLFastSolve\n      L--;\n      for(aptr = LUSOL->a+L, jptr = LUSOL->indc+L;\n          LEN > 0; LEN--, aptr--, jptr--)\n        V[*jptr] += (*aptr)*VPIV;\n#else\n      for(; LEN > 0; LEN--) {\n        L--;\n        J = LUSOL->indc[L];\n        V[J] += LUSOL->a[L]*VPIV;\n      }\n#endif\n/*      Find diag = U(ipiv,ipiv) and divide by diag or |diag|. */\n      L = LUSOL->locr[IPIV];\n      DIAG = LUSOL->a[L];\n      if(MODE==2)\n        DIAG = fabs(DIAG);\n      V[IPIV] = VPIV/DIAG;\n    }\n#ifdef SetSmallToZero\n    else\n      V[IPIV] = 0;\n#endif\n  }\n}\n\n\n/* ==================================================================\n   lu6Lt  solves   L'v = v(input).\n   ------------------------------------------------------------------\n   15 Dec 2002: First version derived from lu6sol.\n   15 Dec 2002: Current version.\n   ================================================================== */\nvoid LU6LT(LUSOLrec *LUSOL, int *INFORM, REAL V[], int NZidx[])\n{\n#ifdef DoTraceL0\n  REAL    TEMP;\n#endif\n  int     K, L, L1, L2, LEN, LENL, LENL0, NUML0;\n  REAL    SMALL;\n  register REALXP SUM;\n  register REAL HOLD;\n#if (defined LUSOLFastSolve) && !(defined DoTraceL0)\n  REAL    *aptr;\n  int     *iptr, *jptr;\n#else\n  int     I, J;\n#endif\n\n  NUML0 = LUSOL->luparm[LUSOL_IP_COLCOUNT_L0];\n  LENL0 = LUSOL->luparm[LUSOL_IP_NONZEROS_L0];\n  LENL  = LUSOL->luparm[LUSOL_IP_NONZEROS_L];\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  L1 = (LUSOL->lena-LENL)+1;\n  L2 = LUSOL->lena-LENL0;\n\n/*     ***** This loop could be coded specially. */\n#if (defined LUSOLFastSolve) && !(defined DoTraceL0)\n  for(L = L1, aptr = LUSOL->a+L1, iptr = LUSOL->indr+L1, jptr = LUSOL->indc+L1;\n      L <= L2; L++, aptr++, iptr++, jptr++) {\n    HOLD = V[*jptr];\n    if(fabs(HOLD)>SMALL)\n      V[*iptr] += (*aptr)*HOLD;\n#ifdef SetSmallToZero\n    else\n      V[*jptr] = 0;\n#endif\n  }\n#else\n  for(L = L1; L <= L2; L++) {\n    J = LUSOL->indc[L];\n    HOLD = V[J];\n    if(fabs(HOLD)>SMALL) {\n      I = LUSOL->indr[L];\n      V[I] += LUSOL->a[L]*HOLD;\n    }\n#ifdef SetSmallToZero\n    else\n      V[J] = 0;\n#endif\n  }\n#endif\n\n  /* Do row-based L0 version, if available */\n  if((LUSOL->L0 != NULL) ||\n     ((LUSOL->luparm[LUSOL_IP_BTRANCOUNT] == 0) && LU1L0(LUSOL, &(LUSOL->L0), INFORM))) {\n    LU6L0T_v(LUSOL, LUSOL->L0, V, NZidx, INFORM);\n  }\n\n  /* Alternatively, do the standard column-based L0 version */\n  else  {\n    /* Perform loop over columns */\n    for(K = NUML0; K >= 1; K--) {\n      SUM = ZERO;\n      LEN = LUSOL->lenc[K];\n      L1 = L2+1;\n      L2 += LEN;\n/*     ***** This loop could be coded specially. */\n#if (defined LUSOLFastSolve) && !(defined DoTraceL0)\n      for(L = L1, aptr = LUSOL->a+L1, jptr = LUSOL->indc+L1;\n          L <= L2; L++, aptr++, jptr++)\n        SUM += (*aptr) * V[*jptr];\n#else\n      for(L = L1; L <= L2; L++) {\n        J = LUSOL->indc[L];\n#ifndef DoTraceL0\n        SUM += LUSOL->a[L]*V[J];\n#else\n        TEMP = V[LUSOL->indr[L1]] + SUM;\n        SUM += LUSOL->a[L]*V[J];\n        printf(\"V[%3d] = V[%3d] + L[%d,%d]*V[%3d]\\n\", LUSOL->indr[L1], LUSOL->indr[L1], J,LUSOL->indr[L1], J);\n        printf(\"%6g = %6g + %6g*%6g\\n\", V[LUSOL->indr[L1]] + SUM, TEMP, LUSOL->a[L], V[J]);\n#endif\n      }\n#endif\n      V[LUSOL->indr[L1]] += (REAL) SUM;\n    }\n  }\n\n/*      Exit. */\n  LUSOL->luparm[LUSOL_IP_INFORM] = *INFORM;\n}\n\nvoid print_L0(LUSOLrec *LUSOL)\n{\n  int  I, J, K, L, L1, L2, LEN, LENL0, NUML0;\n  REAL *denseL0 = (REAL*) calloc(LUSOL->m+1, (LUSOL->n+1)*sizeof(*denseL0));\n\n  NUML0 = LUSOL->luparm[LUSOL_IP_COLCOUNT_L0];\n  LENL0 = LUSOL->luparm[LUSOL_IP_NONZEROS_L0];\n\n  L2 = LUSOL->lena-LENL0;\n  for(K = NUML0; K >= 1; K--) {\n    LEN = LUSOL->lenc[K];\n    L1 = L2+1;\n    L2 += LEN;\n    for(L = L1; L <= L2; L++) {\n      I = LUSOL->indc[L];\n      I = LUSOL->ipinv[I]; /* Undo row mapping */\n      J = LUSOL->indr[L];\n      denseL0[(LUSOL->n+1)*(J-1) + I] = LUSOL->a[L];\n    }\n  }\n\n  for(I = 1; I <= LUSOL->n; I++) {\n    for(J = 1; J <= LUSOL->m; J++)\n      fprintf(stdout, \"%10g\", denseL0[(LUSOL->n+1)*(J-1) + I]);\n    fprintf(stdout, \"\\n\");\n  }\n  LUSOL_FREE(denseL0);\n}\n\n\n/* ------------------------------------------------------------------\n   Include routines for column-based U.\n   5 Feb 2006 Current version - KE.\n   ------------------------------------------------------------------ */\n#include \"lusol6u.c\"\n\n\n/* ==================================================================\n   lu6U   solves   U w = v.          v  is not altered.\n   ------------------------------------------------------------------\n   15 Dec 2002: First version derived from lu6sol.\n   15 Dec 2002: Current version.\n   ================================================================== */\nvoid LU6U(LUSOLrec *LUSOL, int *INFORM, REAL V[], REAL W[], int NZidx[])\n{\n  /* Do column-based U version, if available */\n  if((LUSOL->U != NULL) ||\n     ((LUSOL->luparm[LUSOL_IP_FTRANCOUNT] == 0) && LU1U0(LUSOL, &(LUSOL->U), INFORM))) {\n    LU6U0_v(LUSOL, LUSOL->U, V, W, NZidx, INFORM);\n  }\n  /* Alternatively, do the standard column-based L0 version */\n  else {\n    int  I, J, K, KLAST, L, L1, L2, L3, NRANK, NRANK1;\n    REAL SMALL;\n    register REALXP T;\n#ifdef LUSOLFastSolve\n    REAL *aptr;\n    int  *jptr;\n#endif\n    NRANK = LUSOL->luparm[LUSOL_IP_RANK_U];\n    SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n    *INFORM = LUSOL_INFORM_LUSUCCESS;\n    NRANK1 = NRANK+1;\n/*      Find the first nonzero in v(1:nrank), counting backwards. */\n    for(KLAST = NRANK; KLAST >= 1; KLAST--) {\n      I = LUSOL->ip[KLAST];\n      if(fabs(V[I])>SMALL)\n        break;\n    }\n    L = LUSOL->n;\n#ifdef LUSOLFastSolve\n    for(K = KLAST+1, jptr = LUSOL->iq+K; K <= L; K++, jptr++)\n      W[*jptr] = ZERO;\n#else\n    for(K = KLAST+1; K <= L; K++) {\n      J = LUSOL->iq[K];\n      W[J] = ZERO;\n    }\n#endif\n/*      Do the back-substitution, using rows 1:klast of U. */\n    for(K = KLAST; K >= 1; K--) {\n      I = LUSOL->ip[K];\n      T = V[I];\n      L1 = LUSOL->locr[I];\n      L2 = L1+1;\n      L3 = (L1+LUSOL->lenr[I])-1;\n/*     ***** This loop could be coded specially. */\n#ifdef LUSOLFastSolve\n      for(L = L2, aptr = LUSOL->a+L2, jptr = LUSOL->indr+L2;\n          L <= L3; L++, aptr++, jptr++)\n        T -= (*aptr) * W[*jptr];\n#else\n      for(L = L2; L <= L3; L++) {\n        J = LUSOL->indr[L];\n        T -= LUSOL->a[L]*W[J];\n      }\n#endif\n      J = LUSOL->iq[K];\n      if(fabs((REAL) T)<=SMALL)\n        T = ZERO;\n      else\n        T /= LUSOL->a[L1];\n      W[J] = (REAL) T;\n    }\n/*      Compute residual for overdetermined systems. */\n    T = ZERO;\n    for(K = NRANK1; K <= LUSOL->m; K++) {\n      I = LUSOL->ip[K];\n      T += fabs(V[I]);\n    }\n/*      Exit. */\n    if(T>ZERO)\n      *INFORM = LUSOL_INFORM_LUSINGULAR;\n    LUSOL->luparm[LUSOL_IP_INFORM]     = *INFORM;\n    LUSOL->parmlu[LUSOL_RP_RESIDUAL_U] = (REAL) T;\n  }\n}\n\n/* ==================================================================\n   lu6Ut  solves   U'v = w.          w  is destroyed.\n   ------------------------------------------------------------------\n   15 Dec 2002: First version derived from lu6sol.\n   15 Dec 2002: Current version.\n   ================================================================== */\nvoid LU6UT(LUSOLrec *LUSOL, int *INFORM, REAL V[], REAL W[], int NZidx[])\n{\n  int  I, J, K, L, L1, L2, NRANK, NRANK1,\n       *ip = LUSOL->ip + 1, *iq = LUSOL->iq + 1;\n  REAL SMALL;\n  register REAL T;\n#ifdef LUSOLFastSolve\n  REAL *aptr;\n  int  *jptr;\n#endif\n\n  NRANK = LUSOL->luparm[LUSOL_IP_RANK_U];\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  NRANK1 = NRANK+1;\n  L = LUSOL->m;\n#ifdef LUSOLFastSolve\n  for(K = NRANK1, jptr = LUSOL->ip+K; K <= L; K++, jptr++)\n    V[*jptr] = ZERO;\n#else\n  for(K = NRANK1; K <= L; K++) {\n    I = LUSOL->ip[K];\n    V[I] = ZERO;\n  }\n#endif\n/*      Do the forward-substitution, skipping columns of U(transpose)\n        when the associated element of w(*) is negligible. */\n#if 0\n  for(K = 1; K <= NRANK; K++) {\n    I = LUSOL->ip[K];\n    J = LUSOL->iq[K];\n#else\n  for(K = 1; K <= NRANK; K++, ip++, iq++) {\n    I = *ip;\n    J = *iq;\n#endif\n    T = W[J];\n    if(fabs(T)<=SMALL) {\n      V[I] = ZERO;\n      continue;\n    }\n    L1 = LUSOL->locr[I];\n    T /= LUSOL->a[L1];\n    V[I] = T;\n    L2 = (L1+LUSOL->lenr[I])-1;\n    L1++;\n/*     ***** This loop could be coded specially. */\n#ifdef LUSOLFastSolve\n    for(L = L1, aptr = LUSOL->a+L1, jptr = LUSOL->indr+L1;\n        L <= L2; L++, aptr++, jptr++)\n      W[*jptr] -= T * (*aptr);\n#else\n    for(L = L1; L <= L2; L++) {\n      J = LUSOL->indr[L];\n      W[J] -= T*LUSOL->a[L];\n    }\n#endif\n  }\n/*      Compute residual for overdetermined systems. */\n  T = ZERO;\n  for(K = NRANK1; K <= LUSOL->n; K++) {\n    J = LUSOL->iq[K];\n    T += fabs(W[J]);\n  }\n/*      Exit. */\n  if(T>ZERO)\n    *INFORM = LUSOL_INFORM_LUSINGULAR;\n  LUSOL->luparm[LUSOL_IP_INFORM]     = *INFORM;\n  LUSOL->parmlu[LUSOL_RP_RESIDUAL_U] = T;\n}\n\n/* ==================================================================\n   lu6sol  uses the factorization  A = L U  as follows:\n   ------------------------------------------------------------------\n   mode\n    1    v  solves   L v = v(input).   w  is not touched.\n    2    v  solves   L'v = v(input).   w  is not touched.\n    3    w  solves   U w = v.          v  is not altered.\n    4    v  solves   U'v = w.          w  is destroyed.\n    5    w  solves   A w = v.          v  is altered as in 1.\n    6    v  solves   A'v = w.          w  is destroyed.\n\n   If mode = 3,4,5,6, v and w must not be the same arrays.\n   If lu1fac has just been used to factorize a symmetric matrix A\n   (which must be definite or quasi-definite), the factors A = L U\n   may be regarded as A = LDL', where D = diag(U).  In such cases,\n\n   mode\n    7    v  solves   A v = L D L'v = v(input).   w  is not touched.\n    8    v  solves       L |D| L'v = v(input).   w  is not touched.\n\n   ip(*), iq(*)      hold row and column numbers in pivotal order.\n   lenc(k)           is the length of the k-th column of initial L.\n   lenr(i)           is the length of the i-th row of U.\n   locc(*)           is not used.\n   locr(i)           is the start  of the i-th row of U.\n\n   U is assumed to be in upper-trapezoidal form (nrank by n).\n   The first entry for each row is the diagonal element\n   (according to the permutations  ip, iq).  It is stored at\n   location locr(i) in a(*), indr(*).\n\n   On exit, inform = 0 except as follows.\n     if(mode = 3,4,5,6 and if U (and hence A) is singular,)\n     inform = 1 if there is a nonzero residual in solving the system\n     involving U.  parmlu(20) returns the norm of the residual.\n   ------------------------------------------------------------------\n     July 1987: Early version.\n   09 May 1988: f77 version.\n   27 Apr 2000: Abolished the dreaded \"computed go to\".\n                But hard to change other \"go to\"s to \"if then else\".\n   15 Dec 2002: lu6L, lu6Lt, lu6U, lu6Ut added to modularize lu6sol.\n   ================================================================== */\nvoid LU6SOL(LUSOLrec *LUSOL, int MODE, REAL V[], REAL W[], int NZidx[], int *INFORM)\n{\n  if(MODE==LUSOL_SOLVE_Lv_v) {          /* Solve  L v(new) = v. */\n    LU6L(LUSOL, INFORM,V, NZidx);\n  }\n  else if(MODE==LUSOL_SOLVE_Ltv_v) {    /* Solve  L'v(new) = v. */\n    LU6LT(LUSOL, INFORM,V, NZidx);\n  }\n  else if(MODE==LUSOL_SOLVE_Uw_v) {     /* Solve  U w = v. */\n    LU6U(LUSOL, INFORM,V,W, NZidx);\n  }\n  else if(MODE==LUSOL_SOLVE_Utv_w) {    /* Solve  U'v = w. */\n    LU6UT(LUSOL, INFORM,V,W, NZidx);\n  }\n  else if(MODE==LUSOL_SOLVE_Aw_v) {     /* Solve  A w      = v (i.e. FTRAN) */\n    LU6L(LUSOL, INFORM,V, NZidx);        /* via     L v(new) = v */\n    LU6U(LUSOL, INFORM,V,W, NULL);       /* ... and U w = v(new). */\n  }\n  else if(MODE==LUSOL_SOLVE_Atv_w) {    /* Solve  A'v = w (i.e. BTRAN) */\n    LU6UT(LUSOL, INFORM,V,W, NZidx);     /* via      U'v = w */\n    LU6LT(LUSOL, INFORM,V, NULL);        /* ... and  L'v(new) = v. */\n  }\n  else if(MODE==LUSOL_SOLVE_Av_v) {     /* Solve  LDv(bar) = v */\n    LU6LD(LUSOL, INFORM,1,V, NZidx);     /* and    L'v(new) = v(bar). */\n    LU6LT(LUSOL, INFORM,V, NULL);\n  }\n  else if(MODE==LUSOL_SOLVE_LDLtv_v) {  /* Solve  L|D|v(bar) = v */\n    LU6LD(LUSOL, INFORM,2,V, NZidx);     /* and    L'v(new) = v(bar). */\n    LU6LT(LUSOL, INFORM,V, NULL);\n  }\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol6l0.c",
    "content": "\n/* Create a row-based version of L0.\n   This makes it possible to solve L0'x=h (btran) faster for sparse h,\n   since we only run down the columns of L0' (rows of LO) for which\n   the corresponding entry in h is non-zero. */\nMYBOOL LU1L0(LUSOLrec *LUSOL, LUSOLmat **mat, int *inform)\n{\n  MYBOOL status = FALSE;\n  int    K, L, LL, L1, L2, LENL0, NUML0, I;\n  int    *lsumr;\n\n  /* Assume success */\n  *inform = LUSOL_INFORM_LUSUCCESS;\n\n  /* Check if there is anything worth doing */\n  if(mat == NULL)\n    return( status );\n  if(*mat != NULL)\n    LUSOL_matfree(mat);\n  NUML0 = LUSOL->luparm[LUSOL_IP_COLCOUNT_L0];\n  LENL0 = LUSOL->luparm[LUSOL_IP_NONZEROS_L0];\n  if((NUML0 == 0) || (LENL0 == 0) ||\n     (LUSOL->luparm[LUSOL_IP_ACCELERATION] == LUSOL_BASEORDER) ||\n     ((LUSOL->luparm[LUSOL_IP_ACCELERATION] & LUSOL_ACCELERATE_L0) == 0))\n    return( status );\n\n  /* Allocate temporary array */\n  lsumr = (int *) LUSOL_CALLOC((LUSOL->m+1), sizeof(*lsumr));\n  if(lsumr == NULL) {\n    *inform = LUSOL_INFORM_NOMEMLEFT;\n    return( status );\n  }\n\n  /* Compute non-zero counts by permuted row index (order is unimportant) */\n  K = 0;\n  L2 = LUSOL->lena;\n  L1 = L2-LENL0+1;\n  for(L = L1; L <= L2; L++) {\n    I = LUSOL->indc[L];\n    lsumr[I]++;\n    if(lsumr[I] == 1)\n      K++;\n  }\n  LUSOL->luparm[LUSOL_IP_ROWCOUNT_L0] = K;\n\n  /* Check if we should apply \"smarts\" before proceeding to the row matrix creation */\n  if((LUSOL->luparm[LUSOL_IP_ACCELERATION] & LUSOL_AUTOORDER) &&\n     ((REAL) LUSOL->luparm[LUSOL_IP_ROWCOUNT_L0] /\n#if 0\n             LUSOL->luparm[LUSOL_IP_COLCOUNT_L0]\n#else\n             LUSOL->m\n#endif\n      > LUSOL->parmlu[LUSOL_RP_SMARTRATIO]))\n    goto Finish;\n\n  /* We are Ok to create the new matrix object */\n  *mat = LUSOL_matcreate(LUSOL->m, LENL0);\n  if(*mat == NULL) {\n    *inform = LUSOL_INFORM_NOMEMLEFT;\n    goto Finish;\n  }\n\n  /* Cumulate row counts to get vector offsets; first row is leftmost\n     (stick with Fortran array offset for consistency) */\n  (*mat)->lenx[0] = 1;\n  for(K = 1; K <= LUSOL->m; K++) {\n    (*mat)->lenx[K] = (*mat)->lenx[K-1] + lsumr[K];\n    lsumr[K] = (*mat)->lenx[K-1];\n  }\n\n  /* Map the matrix into row order by permuted index;\n     Note: The first permuted row is located leftmost in the array.\n           The column order is irrelevant, since the indeces will\n           refer to constant / resolved values of V[] during solve. */\n  L2 = LUSOL->lena;\n  L1 = L2-LENL0+1;\n  for(L = L1; L <= L2; L++) {\n    I = LUSOL->indc[L];\n    LL = lsumr[I]++;\n    (*mat)->a[LL] = LUSOL->a[L];\n    (*mat)->indr[LL] = LUSOL->indr[L];\n    (*mat)->indc[LL] = I;\n  }\n\n  /* Pack row starting positions, and set mapper from original index to packed */\n  I = 0;\n  for(L = 1; L <= LUSOL->m; L++) {\n    K = LUSOL->ip[L];\n    if((*mat)->lenx[K] > (*mat)->lenx[K-1]) {\n      I++;\n      (*mat)->indx[I] = K;\n    }\n  }\n\n  /* Confirm that everything went well */\n  status = TRUE;\n\n  /* Clean up */\nFinish:\n  FREE(lsumr);\n  return( status );\n}\n\n/* Solve L0' v = v based on row-based version of L0, constructed by LU1L0 */\nvoid LU6L0T_v(LUSOLrec *LUSOL, LUSOLmat *mat, REAL V[], int NZidx[], int *INFORM)\n{\n#ifdef DoTraceL0\n  REAL TEMP;\n#endif\n  int  LEN, K, KK, L, L1, NUML0;\n  REAL SMALL;\n  register REAL VPIV;\n#if (defined LUSOLFastSolve) && !(defined DoTraceL0)\n  REAL *aptr;\n  int  *jptr;\n#else\n  int  J;\n#endif\n\n  NUML0 = LUSOL->luparm[LUSOL_IP_ROWCOUNT_L0];\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n\n  /* Loop over the nz columns of L0' - from the end, going forward. */\n  for(K = NUML0; K > 0; K--) {\n    KK = mat->indx[K];\n    L  = mat->lenx[KK];\n    L1 = mat->lenx[KK-1];\n    LEN = L - L1;\n    if(LEN == 0)\n      continue;\n    /* Get value of the corresponding active entry of V[] */\n    VPIV = V[KK];\n    /* Only process the column of L0' if the value of V[] is non-zero */\n    if(fabs(VPIV)>SMALL) {\n/*     ***** This loop could be coded specially. */\n#if (defined LUSOLFastSolve) && !(defined DoTraceL0)\n      L--;\n      for(aptr = mat->a+L, jptr = mat->indr+L;\n          LEN > 0; LEN--, aptr--, jptr--)\n        V[*jptr] += VPIV * (*aptr);\n#else\n      for(; LEN > 0; LEN--) {\n        L--;\n        J = mat->indr[L];\n#ifndef DoTraceL0\n        V[J] += VPIV * mat->a[L];\n#else\n        TEMP = V[J];\n        V[J] += VPIV * mat->a[L];\n        printf(\"V[%3d] = V[%3d] + L[%d,%d]*V[%3d]\\n\", J, J, KK,J, KK);\n        printf(\"%6g = %6g + %6g*%6g\\n\", V[J], TEMP, mat->a[L], VPIV);\n#endif\n      }\n#endif\n    }\n#ifdef SetSmallToZero\n    else\n      V[KK] = 0;\n#endif\n  }\n\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol6u.c",
    "content": "\n/* Create a column-based version of U.\n   This makes it possible to solve Ux=h (ftran) faster for sparse h,\n   since we only run down the rows of U (columns of U') for which\n   the corresponding entry in h is non-zero. */\nMYBOOL LU1U0(LUSOLrec *LUSOL, LUSOLmat **mat, int *inform)\n{\n  MYBOOL status = FALSE;\n  int    K, L, LL, LENU, NUMU, J;\n  int    *lsumc;\n\n  /* Assume success */\n  *inform = LUSOL_INFORM_LUSUCCESS;\n\n  /* Check if there is anything worth doing */\n  if(mat == NULL)\n    return( status );\n  if(*mat != NULL)\n    LUSOL_matfree(mat);\n  NUMU = LUSOL->luparm[LUSOL_IP_RANK_U];\n  LENU = LUSOL->luparm[LUSOL_IP_NONZEROS_U];\n  if((NUMU == 0) || (LENU == 0) ||\n     (LUSOL->luparm[LUSOL_IP_ACCELERATION] == LUSOL_BASEORDER) ||\n     ((LUSOL->luparm[LUSOL_IP_ACCELERATION] & LUSOL_ACCELERATE_U) == 0))\n    return( status );\n\n  /* Allocate temporary array */\n  lsumc = (int *) LUSOL_CALLOC((LUSOL->n+1), sizeof(*lsumc));\n  if(lsumc == NULL) {\n    *inform = LUSOL_INFORM_NOMEMLEFT;\n    return( status );\n  }\n\n  /* Compute non-zero counts by permuted column index (order is unimportant) */\n  for(L = 1; L <= LENU; L++) {\n    J = LUSOL->indr[L];\n    lsumc[J]++;\n  }\n\n  /* Check if we should apply \"smarts\" before proceeding to the column matrix creation */\n  if((LUSOL->luparm[LUSOL_IP_ACCELERATION] & LUSOL_AUTOORDER) &&\n     ((REAL) sqrt((REAL) NUMU/LENU) > LUSOL->parmlu[LUSOL_RP_SMARTRATIO]))\n    goto Finish;\n\n  /* We are Ok to create the new matrix object */\n  *mat = LUSOL_matcreate(LUSOL->n, LENU);\n  if(*mat == NULL) {\n    *inform = LUSOL_INFORM_NOMEMLEFT;\n    goto Finish;\n  }\n\n  /* Cumulate row counts to get vector offsets; first column is leftmost\n     (stick with Fortran array offset for consistency) */\n  (*mat)->lenx[0] = 1;\n  for(K = 1; K <= LUSOL->n; K++) {\n    (*mat)->lenx[K] = (*mat)->lenx[K-1] + lsumc[K];\n    lsumc[K] = (*mat)->lenx[K-1];\n  }\n\n  /* Map the matrix into column order by permuted index;\n     Note: The first permuted column is located leftmost in the array.\n           The row order is irrelevant, since the indeces will\n           refer to constant / resolved values of V[] during solve. */\n  for(L = 1; L <= LENU; L++) {\n    J = LUSOL->indr[L];\n    LL = lsumc[J]++;\n    (*mat)->a[LL] = LUSOL->a[L];\n    (*mat)->indr[LL] = J;\n    (*mat)->indc[LL] = LUSOL->indc[L];\n  }\n\n  /* Pack column starting positions, and set mapper from original index to packed */\n  J = 0;\n  for(L = 1; L <= LUSOL->n; L++) {\n    K = LUSOL->iq[L];\n#if 1  /* Deactivate to produce a full-rank version (implicit unit diagonals) */\n    if((*mat)->lenx[K] > (*mat)->lenx[K-1])\n#endif\n    {\n      J++;\n     (*mat)->indx[J] = K;\n    }\n  }\n\n  /* Confirm that everything went well */\n  status = TRUE;\n\n  /* Clean up */\nFinish:\n  FREE(lsumc);\n  return( status );\n}\n\n/* Solve U w = v based on column-based version of U, constructed by LU1U0 */\nvoid LU6U0_v(LUSOLrec *LUSOL, LUSOLmat *mat, REAL V[], REAL W[], int NZidx[], int *INFORM)\n{\n#ifdef DoTraceU0\n  REAL TEMP;\n#endif\n  int  LEN, I, K, L, L1, NRANK, NRANK1, KLAST;\n  REAL SMALL;\n  register REAL T;\n#if (defined xxLUSOLFastSolve) && !(defined DoTraceU0)\n  REAL *aptr;\n  int  *jptr;\n#else\n  int  J;\n#endif\n\n  NRANK = LUSOL->luparm[LUSOL_IP_RANK_U];\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  NRANK1 = NRANK+1;\n/*      Find the first nonzero in v(1:nrank), counting backwards. */\n  for(KLAST = NRANK; KLAST >= 1; KLAST--) {\n    I = LUSOL->ip[KLAST];\n    if(fabs(V[I])>SMALL)\n      break;\n  }\n  L = LUSOL->n;\n#ifdef xxLUSOLFastSolve\n  for(K = KLAST+1, jptr = LUSOL->iq+K; K <= L; K++, jptr++)\n    W[*jptr] = ZERO;\n#else\n  for(K = KLAST+1; K <= L; K++) {\n    J = LUSOL->iq[K];\n    W[J] = ZERO;\n  }\n#endif\n  /* Loop over the nz columns of U - from the right, going left. */\n  for(K = NRANK; K > 0; K--) {\n    I = mat->indx[K];\n    L = mat->lenx[I];\n    L1 = mat->lenx[I-1];\n    LEN = L - L1;\n    T = V[I];\n    if(fabs(T)<=SMALL) {\n      W[K] = ZERO;\n      continue;\n    }\n    T /= mat->a[L1];  /* Should it be L or L1 ? */\n    W[K] = T;\n    LEN--;\n/*     ***** This loop could be coded specially. */\n#ifdef xxLUSOLFastSolve\n    L--;\n    for(aptr = mat->a+L, jptr = mat->indc+L;\n        LEN > 0; LEN--, aptr--, jptr--)\n      V[*jptr] -= T * (*aptr);\n#else\n    for(; LEN > 0; LEN--) {\n      L--;\n      J = mat->indc[L];\n#ifndef DoTraceL0\n      V[J] -= T * mat->a[L];\n#else\n      TEMP = V[J];\n      V[J] += T * mat->a[L];\n      printf(\"V[%3d] = V[%3d] + L[%d,%d]*V[%3d]\\n\", J, J, I,J, I);\n      printf(\"%6g = %6g + %6g*%6g\\n\", V[J], TEMP, mat->a[L], T);\n#endif\n    }\n#endif\n  }\n/*      Compute residual for overdetermined systems. */\n  T = ZERO;\n  for(K = NRANK1; K <= LUSOL->m; K++) {\n    I = LUSOL->ip[K];\n    T += fabs(V[I]);\n  }\n/*      Exit. */\n  if(T>ZERO)\n    *INFORM = LUSOL_INFORM_LUSINGULAR;\n  LUSOL->luparm[LUSOL_IP_INFORM]     = *INFORM;\n  LUSOL->parmlu[LUSOL_RP_RESIDUAL_U] = (REAL) T;\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol7a.c",
    "content": "\n/* ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   File  lusol7a\n      lu7add   lu7cyc   lu7elm   lu7for   lu7rnk   lu7zap\n      Utilities for LUSOL's update routines.\n      lu7for is the most important -- the forward sweep.\n  01 May 2002: Derived from LUSOL's original lu7a.f file.\n  01 May 2002: Current version of lusol7a.f.\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */\n\n/* ==================================================================\n   lu7add  inserts the first nrank elements of the vector v(*)\n   as column  jadd  of  U.  We assume that  U  does not yet have any\n   entries in this column.\n   Elements no larger than  parmlu(3)  are treated as zero.\n   klast  will be set so that the last row to be affected\n   (in pivotal order) is row  ip(klast).\n   ------------------------------------------------------------------\n   09 May 1988: First f77 version.\n   ================================================================== */\nvoid LU7ADD(LUSOLrec *LUSOL, int JADD, REAL V[], int LENL, int *LENU,\n  int *LROW, int NRANK, int *INFORM, int *KLAST, REAL *VNORM)\n{\n  REAL SMALL;\n  int  K, I, LENI, MINFRE, NFREE, LR1, LR2, L;\n#ifndef LUSOLFastMove\n  int J;\n#endif\n\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  *VNORM = ZERO;\n  *KLAST = 0;\n  for(K = 1; K <= NRANK; K++) {\n    I = LUSOL->ip[K];\n    if(fabs(V[I])<=SMALL)\n      continue;\n    *KLAST = K;\n    (*VNORM) += fabs(V[I]);\n    LENI = LUSOL->lenr[I];\n/*         Compress row file if necessary. */\n    MINFRE = LENI+1;\n    NFREE = LUSOL->lena - LENL - *LROW;\n    if(NFREE<MINFRE) {\n      LU1REC(LUSOL, LUSOL->m, TRUE,LROW,LUSOL->indr,LUSOL->lenr,LUSOL->locr);\n      NFREE = LUSOL->lena - LENL - *LROW;\n      if(NFREE<MINFRE)\n        goto x970;\n    }\n/*         Move row  i  to the end of the row file,\n           unless it is already there.\n           No need to move if there is a gap already. */\n    if(LENI==0)\n      LUSOL->locr[I] = (*LROW) + 1;\n    LR1 = LUSOL->locr[I];\n    LR2 = (LR1+LENI)-1;\n    if(LR2==*LROW)\n      goto x150;\n    if(LUSOL->indr[LR2+1]==0)\n      goto x180;\n    LUSOL->locr[I] = (*LROW) + 1;\n#ifdef LUSOLFastMove\n    L = LR2-LR1+1;\n    if(L > 0) {\n      LR2 = (*LROW)+1;\n      MEMMOVE(LUSOL->a+LR2,    LUSOL->a+LR1, L);\n      MEMMOVE(LUSOL->indr+LR2, LUSOL->indr+LR1, L);\n      MEMCLEAR(LUSOL->indr+LR1, L);\n      *LROW += L;\n    }\n#else\n    for(L = LR1; L <= LR2; L++) {\n      (*LROW)++;\n      LUSOL->a[*LROW] = LUSOL->a[L];\n      J = LUSOL->indr[L];\n      LUSOL->indr[L] = 0;\n      LUSOL->indr[*LROW] = J;\n    }\n#endif\nx150:\n    LR2 = *LROW;\n    (*LROW)++;\n/*         Add the element of  v. */\nx180:\n    LR2++;\n    LUSOL->a[LR2] = V[I];\n    LUSOL->indr[LR2] = JADD;\n    LUSOL->lenr[I] = LENI+1;\n    (*LENU)++;\n  }\n/*      Normal exit. */\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  goto x990;\n/*      Not enough storage. */\nx970:\n  *INFORM = LUSOL_INFORM_ANEEDMEM;\nx990:\n;\n}\n\n/* ==================================================================\n   lu7cyc performs a cyclic permutation on the row or column ordering\n   stored in ip, moving entry kfirst down to klast.\n   If kfirst .ge. klast, lu7cyc should not be called.\n   Sometimes klast = 0 and nothing should happen.\n   ------------------------------------------------------------------\n   09 May 1988: First f77 version.\n   ================================================================== */\nvoid LU7CYC(LUSOLrec *LUSOL, int KFIRST, int KLAST, int IX[])\n{\n  if(KFIRST<KLAST) {\n    int IFIRST, K;\n#ifdef LUSOLFastMove\n#if 1\n    IFIRST = IX[KFIRST];\n    K = KLAST-KFIRST;\n    MEMMOVE(IX+KFIRST, IX+KFIRST+1, K);\n    IX[KLAST] = IFIRST;\n#else\n    int *IXK, *IXK1;\n    IXK = IX+KFIRST;\n    IFIRST = *IXK;\n    for(K = KFIRST, IXK1 = IXK+1; K <= KLAST-1; K++, IXK++, IXK1++) {\n      *IXK = *IXK1;\n    }\n    *IXK = IFIRST;\n#endif\n#else\n    IFIRST = IX[KFIRST];\n    for(K = KFIRST; K <= KLAST-1; K++) {\n      IX[K] = IX[K+1];\n    }\n    IX[KLAST] = IFIRST;\n#endif\n  }\n}\n\n/* ==================================================================\n   lu7elm  eliminates the subdiagonal elements of a vector  v(*),\n   where  L*v = y  for some vector y.\n   If  jelm > 0,  y  has just become column  jelm  of the matrix  A.\n   lu7elm  should not be called unless  m  is greater than  nrank.\n   inform = 0 if y contained no subdiagonal nonzeros to eliminate.\n   inform = 1 if y contained at least one nontrivial subdiagonal.\n   inform = 7 if there is insufficient storage.\n   ------------------------------------------------------------------\n   09 May 1988: First f77 version.\n                No longer calls lu7for at end.  lu8rpc, lu8mod do so.\n   ================================================================== */\nvoid LU7ELM(LUSOLrec *LUSOL, int JELM, REAL V[], int *LENL,\n            int *LROW, int NRANK, int *INFORM, REAL *DIAG)\n{\n  REAL VI, VMAX, SMALL;\n  int  NRANK1, MINFRE, NFREE, KMAX, L, K, I, LMAX, IMAX, L1, L2;\n\n#ifdef ForceInitialization\n  LMAX = 0;\n#endif\n\n  SMALL = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  NRANK1 = NRANK+1;\n  *DIAG = ZERO;\n/*      Compress row file if necessary. */\n  MINFRE = LUSOL->m-NRANK;\n  NFREE = LUSOL->lena-(*LENL)-(*LROW);\n  if(NFREE>=MINFRE)\n    goto x100;\n  LU1REC(LUSOL, LUSOL->m,TRUE,LROW,LUSOL->indr,LUSOL->lenr,LUSOL->locr);\n  NFREE = LUSOL->lena-(*LENL)-(*LROW);\n  if(NFREE<MINFRE)\n    goto x970;\n    \n/*      Pack the subdiagonals of  v  into  L,  and find the largest. */\nx100:\n  VMAX = ZERO;\n  KMAX = 0;\n  L = (LUSOL->lena-(*LENL))+1;\n  for(K = NRANK1; K <= LUSOL->m; K++) {\n    I = LUSOL->ip[K];\n    VI = fabs(V[I]);\n    if(VI<=SMALL)\n      continue;\n    L--;\n    LUSOL->a[L] = V[I];\n    LUSOL->indc[L] = I;\n    if(VMAX>=VI)\n      continue;\n    VMAX = VI;\n    KMAX = K;\n    LMAX = L;\n  }\n  if(KMAX==0)\n    goto x900;\n/*      ------------------------------------------------------------------\n        Remove  vmax  by overwriting it with the last packed  v(i).\n        Then set the multipliers in  L  for the other elements.\n        ------------------------------------------------------------------ */\n  IMAX = LUSOL->ip[KMAX];\n  VMAX = LUSOL->a[LMAX];\n  LUSOL->a[LMAX] = LUSOL->a[L];\n  LUSOL->indc[LMAX] = LUSOL->indc[L];\n  L1 = L+1;\n  L2 = LUSOL->lena-(*LENL);\n  *LENL = ((*LENL)+L2)-L;\n  for(L = L1; L <= L2; L++) {\n    LUSOL->a[L] /= -VMAX;\n    LUSOL->indr[L] = IMAX;\n  }\n/*      Move the row containing vmax to pivotal position nrank + 1. */\n  LUSOL->ip[KMAX] = LUSOL->ip[NRANK1];\n  LUSOL->ip[NRANK1] = IMAX;\n  *DIAG = VMAX;\n/*      ------------------------------------------------------------------\n        If jelm is positive, insert  vmax  into a new row of  U.\n        This is now the only subdiagonal element.\n        ------------------------------------------------------------------ */\n  if(JELM>0) {\n    (*LROW)++;\n    LUSOL->locr[IMAX] = *LROW;\n    LUSOL->lenr[IMAX] = 1;\n    LUSOL->a[*LROW] = VMAX;\n    LUSOL->indr[*LROW] = JELM;\n  }\n  *INFORM = LUSOL_INFORM_LUSINGULAR;\n  goto x990;\n/*      No elements to eliminate. */\nx900:\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  goto x990;\n/*      Not enough storage. */\nx970:\n  *INFORM = LUSOL_INFORM_ANEEDMEM;\nx990:\n;\n}\n\n/* ==================================================================\n   lu7for  (forward sweep) updates the LU factorization  A = L*U\n   when row  iw = ip(klast)  of  U  is eliminated by a forward\n   sweep of stabilized row operations, leaving  ip * U * iq  upper\n   triangular.\n   The row permutation  ip  is updated to preserve stability and/or\n   sparsity.  The column permutation  iq  is not altered.\n   kfirst  is such that row  ip(kfirst)  is the first row involved\n   in eliminating row  iw.  (Hence,  kfirst  marks the first nonzero\n   in row  iw  in pivotal order.)  If  kfirst  is unknown it may be\n   input as  1.\n   klast   is such that row  ip(klast)  is the row being eliminated.\n   klast   is not altered.\n   lu7for  should be called only if  kfirst .le. klast.\n   If  kfirst = klast,  there are no nonzeros to eliminate, but the\n   diagonal element of row  ip(klast)  may need to be moved to the\n   front of the row.\n   ------------------------------------------------------------------\n   On entry,  locc(*)  must be zero.\n\n   On exit:\n   inform = 0  if row iw has a nonzero diagonal (could be small).\n   inform = 1  if row iw has no diagonal.\n   inform = 7  if there is not enough storage to finish the update.\n\n   On a successful exit (inform le 1),  locc(*)  will again be zero.\n   ------------------------------------------------------------------\n      Jan 1985: Final f66 version.\n   09 May 1988: First f77 version.\n   ================================================================== */\nvoid LU7FOR(LUSOLrec *LUSOL, int KFIRST, int KLAST, int *LENL, int *LENU,\n                     int *LROW, int *INFORM, REAL *DIAG)\n{\n  MYBOOL SWAPPD;\n  int    KBEGIN, IW, LENW, LW1, LW2, JFIRST, MINFRE, NFREE, L, J, KSTART, KSTOP, K,\n         LFIRST, IV, LENV, LV1, JLAST, LV2, LV3, LV, JV, LW, LDIAG, LIMIT;\n  REAL   AMULT, LTOL, USPACE, SMALL, VJ, WJ;\n\n  LTOL   = LUSOL->parmlu[LUSOL_RP_UPDATEMAX_Lij];\n  SMALL  = LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE];\n  USPACE = LUSOL->parmlu[LUSOL_RP_COMPSPACE_U];\n  KBEGIN = KFIRST;\n  SWAPPD = FALSE;\n\n/*      We come back here from below if a row interchange is performed. */\nx100:\n  IW = LUSOL->ip[KLAST];\n  LENW = LUSOL->lenr[IW];\n  if(LENW==0)\n    goto x910;\n  LW1 = LUSOL->locr[IW];\n  LW2 = (LW1+LENW)-1;\n  JFIRST = LUSOL->iq[KBEGIN];\n  if(KBEGIN>=KLAST)\n    goto x700;\n/*      Make sure there is room at the end of the row file\n        in case row  iw  is moved there and fills in completely. */\n  MINFRE = LUSOL->n+1;\n  NFREE = LUSOL->lena-(*LENL)-(*LROW);\n  if(NFREE<MINFRE) {\n    LU1REC(LUSOL, LUSOL->m,TRUE,LROW,LUSOL->indr,LUSOL->lenr,LUSOL->locr);\n    LW1 = LUSOL->locr[IW];\n    LW2 = (LW1+LENW)-1;\n    NFREE = LUSOL->lena-(*LENL)-(*LROW);\n    if(NFREE<MINFRE)\n      goto x970;\n\n  }\n/*      Set markers on row  iw. */\n  for(L = LW1; L <= LW2; L++) {\n    J = LUSOL->indr[L];\n    LUSOL->locc[J] = L;\n  }\n/*      ==================================================================\n        Main elimination loop.\n        ================================================================== */\n  KSTART = KBEGIN;\n  KSTOP = MIN(KLAST,LUSOL->n);\n  for(K = KSTART; K <= KSTOP; K++) {\n    JFIRST = LUSOL->iq[K];\n    LFIRST = LUSOL->locc[JFIRST];\n    if(LFIRST==0)\n      goto x490;\n/*         Row  iw  has its first element in column  jfirst. */\n    WJ = LUSOL->a[LFIRST];\n    if(K==KLAST)\n      goto x490;\n/*         ---------------------------------------------------------------\n           We are about to use the first element of row  iv\n                  to eliminate the first element of row  iw.\n           However, we may wish to interchange the rows instead,\n           to preserve stability and/or sparsity.\n           --------------------------------------------------------------- */\n    IV = LUSOL->ip[K];\n    LENV = LUSOL->lenr[IV];\n    LV1 = LUSOL->locr[IV];\n    VJ = ZERO;\n    if(LENV==0)\n      goto x150;\n    if(LUSOL->indr[LV1]!=JFIRST)\n      goto x150;\n    VJ = LUSOL->a[LV1];\n    if(SWAPPD)\n      goto x200;\n    if(LTOL*fabs(WJ)<fabs(VJ))\n      goto x200;\n    if(LTOL*fabs(VJ)<fabs(WJ))\n      goto x150;\n    if(LENV<=LENW)\n      goto x200;\n/*         ---------------------------------------------------------------\n           Interchange rows  iv  and  iw.\n           --------------------------------------------------------------- */\nx150:\n    LUSOL->ip[KLAST] = IV;\n    LUSOL->ip[K] = IW;\n    KBEGIN = K;\n    SWAPPD = TRUE;\n    goto x600;\n/*         ---------------------------------------------------------------\n           Delete the eliminated element from row  iw\n           by overwriting it with the last element.\n           --------------------------------------------------------------- */\nx200:\n    LUSOL->a[LFIRST] = LUSOL->a[LW2];\n    JLAST = LUSOL->indr[LW2];\n    LUSOL->indr[LFIRST] = JLAST;\n    LUSOL->indr[LW2] = 0;\n    LUSOL->locc[JLAST] = LFIRST;\n    LUSOL->locc[JFIRST] = 0;\n    LENW--;\n    (*LENU)--;\n    if(*LROW==LW2)\n      (*LROW)--;\n    LW2 = LW2-1;\n/*         ---------------------------------------------------------------\n           Form the multiplier and store it in the  L  file.\n           --------------------------------------------------------------- */\n    if(fabs(WJ)<=SMALL)\n      goto x490;\n    AMULT = -WJ/VJ;\n    L = LUSOL->lena-(*LENL);\n    LUSOL->a[L] = AMULT;\n    LUSOL->indr[L] = IV;\n    LUSOL->indc[L] = IW;\n    (*LENL)++;\n/*         ---------------------------------------------------------------\n           Add the appropriate multiple of row  iv  to row  iw.\n           We use two different inner loops.  The first one is for the\n           case where row  iw  is not at the end of storage.\n           --------------------------------------------------------------- */\n    if(LENV==1)\n      goto x490;\n    LV2 = LV1+1;\n    LV3 = (LV1+LENV)-1;\n    if(LW2==*LROW)\n      goto x400;\n/*         ...............................................................\n           This inner loop will be interrupted only if\n           fill-in occurs enough to bump into the next row.\n           ............................................................... */\n    for(LV = LV2; LV <= LV3; LV++) {\n      JV = LUSOL->indr[LV];\n      LW = LUSOL->locc[JV];\n      if(LW>0) {\n/*               No fill-in. */\n        LUSOL->a[LW] += AMULT*LUSOL->a[LV];\n        if(fabs(LUSOL->a[LW])<=SMALL) {\n/*                  Delete small computed element. */\n          LUSOL->a[LW] = LUSOL->a[LW2];\n          J = LUSOL->indr[LW2];\n          LUSOL->indr[LW] = J;\n          LUSOL->indr[LW2] = 0;\n          LUSOL->locc[J] = LW;\n          LUSOL->locc[JV] = 0;\n          (*LENU)--;\n          LENW--;\n          LW2--;\n        }\n      }\n      else {\n/*               Row  iw  doesn't have an element in column  jv  yet\n                 so there is a fill-in. */\n        if(LUSOL->indr[LW2+1]!=0)\n          goto x360;\n        (*LENU)++;\n        LENW++;\n        LW2++;\n        LUSOL->a[LW2] = AMULT*LUSOL->a[LV];\n        LUSOL->indr[LW2] = JV;\n        LUSOL->locc[JV] = LW2;\n      }\n    }\n    goto x490;\n/*         Fill-in interrupted the previous loop.\n           Move row  iw  to the end of the row file. */\nx360:\n    LV2 = LV;\n    LUSOL->locr[IW] = (*LROW)+1;\n\n#ifdef LUSOLFastMove\n    L = LW2-LW1+1;\n    if(L > 0) {\n      int loci, *locp;\n      for(loci = LW1, locp = LUSOL->indr+LW1;\n          loci <= LW2; loci++, locp++) {\n        (*LROW)++;\n        LUSOL->locc[*locp] = *LROW;\n      }\n      LW2 = (*LROW)-L+1;\n      MEMMOVE(LUSOL->a+LW2,    LUSOL->a+LW1, L);\n      MEMMOVE(LUSOL->indr+LW2, LUSOL->indr+LW1, L);\n      MEMCLEAR(LUSOL->indr+LW1, L);\n    }\n#else\n    for(L = LW1; L <= LW2; L++) {\n      (*LROW)++;\n      LUSOL->a[*LROW] = LUSOL->a[L];\n      J = LUSOL->indr[L];\n      LUSOL->indr[L] = 0;\n      LUSOL->indr[*LROW] = J;\n      LUSOL->locc[J] = *LROW;\n    }\n#endif\n    LW1 = LUSOL->locr[IW];\n    LW2 = *LROW;\n/*         ...............................................................\n           Inner loop with row  iw  at the end of storage.\n           ............................................................... */\nx400:\n    for(LV = LV2; LV <= LV3; LV++) {\n      JV = LUSOL->indr[LV];\n      LW = LUSOL->locc[JV];\n      if(LW>0) {\n/*               No fill-in. */\n        LUSOL->a[LW] += AMULT*LUSOL->a[LV];\n        if(fabs(LUSOL->a[LW])<=SMALL) {\n/*                  Delete small computed element. */\n          LUSOL->a[LW] = LUSOL->a[LW2];\n          J = LUSOL->indr[LW2];\n          LUSOL->indr[LW] = J;\n          LUSOL->indr[LW2] = 0;\n          LUSOL->locc[J] = LW;\n          LUSOL->locc[JV] = 0;\n          (*LENU)--;\n          LENW--;\n          LW2--;\n        }\n      }\n      else {\n/*               Row  iw  doesn't have an element in column  jv  yet\n                 so there is a fill-in. */\n        (*LENU)++;\n        LENW++;\n        LW2++;\n        LUSOL->a[LW2] = AMULT*LUSOL->a[LV];\n        LUSOL->indr[LW2] = JV;\n        LUSOL->locc[JV] = LW2;\n      }\n    }\n    *LROW = LW2;\n/*         The  k-th  element of row  iw  has been processed.\n           Reset  swappd  before looking at the next element. */\nx490:\n    SWAPPD = FALSE;\n  }\n/*      ==================================================================\n        End of main elimination loop.\n        ==================================================================\n\n        Cancel markers on row  iw. */\nx600:\n  LUSOL->lenr[IW] = LENW;\n  if(LENW==0)\n    goto x910;\n  for(L = LW1; L <= LW2; L++) {\n    J = LUSOL->indr[L];\n    LUSOL->locc[J] = 0;\n  }\n/*      Move the diagonal element to the front of row  iw.\n        At this stage,  lenw gt 0  and  klast le n. */\nx700:\n  for(L = LW1; L <= LW2; L++) {\n    LDIAG = L;\n    if(LUSOL->indr[L]==JFIRST)\n      goto x730;\n  }\n  goto x910;\n\nx730:\n  *DIAG = LUSOL->a[LDIAG];\n  LUSOL->a[LDIAG] = LUSOL->a[LW1];\n  LUSOL->a[LW1] = *DIAG;\n  LUSOL->indr[LDIAG] = LUSOL->indr[LW1];\n  LUSOL->indr[LW1] = JFIRST;\n/*      If an interchange is needed, repeat from the beginning with the\n        new row  iw,  knowing that the opposite interchange cannot occur. */\n  if(SWAPPD)\n    goto x100;\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  goto x950;\n/*      Singular. */\nx910:\n  *DIAG = ZERO;\n  *INFORM = LUSOL_INFORM_LUSINGULAR;\n/*      Force a compression if the file for  U  is much longer than the\n        no. of nonzeros in  U  (i.e. if  lrow  is much bigger than  lenU).\n        This should prevent memory fragmentation when there is far more\n        memory than necessary  (i.e. when  lena  is huge). */\nx950:\n  LIMIT = (int) (USPACE*(*LENU))+LUSOL->m+LUSOL->n+1000;\n  if(*LROW>LIMIT)\n    LU1REC(LUSOL, LUSOL->m,TRUE,LROW,LUSOL->indr,LUSOL->lenr,LUSOL->locr);\n  goto x990;\n/*      Not enough storage. */\nx970:\n  *INFORM = LUSOL_INFORM_ANEEDMEM;\n/*      Exit. */\nx990:\n;\n}\n\n/* ==================================================================\n   lu7rnk (check rank) assumes U is currently nrank by n\n   and determines if row nrank contains an acceptable pivot.\n   If not, the row is deleted and nrank is decreased by 1.\n   jsing is an input parameter (not altered).  If jsing is positive,\n   column jsing has already been judged dependent.  A substitute\n   (if any) must be some other column.\n   ------------------------------------------------------------------\n   -- Jul 1987: First version.\n   09 May 1988: First f77 version.\n   ================================================================== */\nvoid LU7RNK(LUSOLrec *LUSOL, int JSING, int *LENU,\n            int *LROW, int *NRANK, int *INFORM, REAL *DIAG)\n{\n  REAL UTOL1, UMAX;\n  int  IW, LENW, L1, L2, LMAX, L, JMAX, KMAX;\n\n#ifdef ForceInitialization\n  L1 = 0;\n  L2 = 0;\n#endif\n\n  UTOL1 = LUSOL->parmlu[LUSOL_RP_SMALLDIAG_U];\n  *DIAG = ZERO;\n/*      Find Umax, the largest element in row nrank. */\n  IW = LUSOL->ip[*NRANK];\n  LENW = LUSOL->lenr[IW];\n  if(LENW==0)\n    goto x400;\n  L1 = LUSOL->locr[IW];\n  L2 = (L1+LENW)-1;\n  UMAX = ZERO;\n  LMAX = L1;\n  for(L = L1; L <= L2; L++) {\n    if(UMAX<fabs(LUSOL->a[L])) {\n      UMAX = fabs(LUSOL->a[L]);\n      LMAX = L;\n    }\n  }\n/*      Find which column that guy is in (in pivotal order).\n        Interchange him with column nrank, then move him to be\n        the new diagonal at the front of row nrank. */\n  *DIAG = LUSOL->a[LMAX];\n  JMAX = LUSOL->indr[LMAX];\n  for(KMAX = *NRANK; KMAX <= LUSOL->n; KMAX++) {\n    if(LUSOL->iq[KMAX]==JMAX)\n      break;\n  }\n  LUSOL->iq[KMAX] = LUSOL->iq[*NRANK];\n  LUSOL->iq[*NRANK] = JMAX;\n  LUSOL->a[LMAX] = LUSOL->a[L1];\n  LUSOL->a[L1] = *DIAG;\n  LUSOL->indr[LMAX] = LUSOL->indr[L1];\n  LUSOL->indr[L1] = JMAX;\n/*      See if the new diagonal is big enough. */\n  if(UMAX<=UTOL1)\n    goto x400;\n  if(JMAX==JSING)\n    goto x400;\n/*      ------------------------------------------------------------------\n        The rank stays the same.\n        ------------------------------------------------------------------ */\n  *INFORM = LUSOL_INFORM_LUSUCCESS;\n  return;\n/*      ------------------------------------------------------------------\n        The rank decreases by one.\n        ------------------------------------------------------------------ */\nx400:\n  *INFORM = LUSOL_INFORM_RANKLOSS;\n  (*NRANK)--;\n  if(LENW>0) {\n/*         Delete row nrank from U. */\n    LENU = LENU-LENW;\n    LUSOL->lenr[IW] = 0;\n    for(L = L1; L <= L2; L++) {\n      LUSOL->indr[L] = 0;\n    }\n    if(L2==*LROW) {\n/*            This row was at the end of the data structure.\n              We have to reset lrow.\n              Preceding rows might already have been deleted, so we\n              have to be prepared to go all the way back to 1. */\n      for(L = 1; L <= L2; L++) {\n        if(LUSOL->indr[*LROW]>0)\n          goto x900;\n        (*LROW)--;\n      }\n    }\n  }\nx900:\n;\n}\n\n/* ==================================================================\n   lu7zap  eliminates all nonzeros in column  jzap  of  U.\n   It also sets  kzap  to the position of  jzap  in pivotal order.\n   Thus, on exit we have  iq(kzap) = jzap.\n   ------------------------------------------------------------------\n   -- Jul 1987: nrank added.\n   10 May 1988: First f77 version.\n   ================================================================== */\nvoid LU7ZAP(LUSOLrec *LUSOL, int JZAP, int *KZAP, int *LENU, int *LROW,\n            int NRANK)\n{\n  int K, I, LENI, LR1, LR2, L;\n\n  for(K = 1; K <= NRANK; K++) {\n    I = LUSOL->ip[K];\n    LENI = LUSOL->lenr[I];\n    if(LENI==0)\n      goto x90;\n    LR1 = LUSOL->locr[I];\n    LR2 = (LR1+LENI)-1;\n    for(L = LR1; L <= LR2; L++) {\n      if(LUSOL->indr[L]==JZAP)\n        goto x60;\n    }\n    goto x90;\n/*         Delete the old element. */\nx60:\n    LUSOL->a[L] = LUSOL->a[LR2];\n    LUSOL->indr[L] = LUSOL->indr[LR2];\n    LUSOL->indr[LR2] = 0;\n    LUSOL->lenr[I] = LENI-1;\n    (*LENU)--;\n/*         Stop if we know there are no more rows containing  jzap. */\nx90:\n    *KZAP = K;\n    if(LUSOL->iq[K]==JZAP)\n      goto x800;\n  }\n/*      nrank must be smaller than n because we haven't found kzap yet. */\n  L = LUSOL->n;\n  for(K = NRANK+1; K <= L; K++) {\n    *KZAP = K;\n    if(LUSOL->iq[K]==JZAP)\n      break;\n  }\n/*      See if we zapped the last element in the file. */\nx800:\n  if(*LROW>0) {\n    if(LUSOL->indr[*LROW]==0)\n      (*LROW)--;\n  }\n\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusol8a.c",
    "content": "\n/* ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\n   File  lusol8a\n      lu8rpc\n      Sparse LU update: Replace Column\n      LUSOL's sparse implementation of the Bartels-Golub update.\n\n   01 May 2002: Derived from LUSOL's original lu8a.f file.\n   01 May 2002: Current version of lusol8a.f.\n   ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */\n\n/* ==================================================================\n   lu8rpc  updates the LU factorization  A = L*U  when column  jrep\n   is replaced by some vector  a(new).\n   lu8rpc  is an implementation of the Bartels-Golub update,\n   designed for the case where A is rectangular and/or singular.\n   L is a product of stabilized eliminations (m x m, nonsingular).\n   P U Q is upper trapezoidal (m x n, rank nrank).\n\n   If  mode1 = 0,  the old column is taken to be zero\n                   (so it does not have to be removed from  U).\n   If  mode1 = 1,  the old column need not have been zero.\n   If  mode2 = 0,  the new column is taken to be zero.\n                   v(*)  is not used or altered.\n   If  mode2 = 1,  v(*)  must contain the new column  a(new).\n                   On exit,  v(*)  will satisfy  L*v = a(new).\n   If  mode2 = 2,  v(*)  must satisfy  L*v = a(new).\n\n   The array  w(*)  is not used or altered.\n   On entry, all elements of  locc  are assumed to be zero.\n   On a successful exit (inform != 7), this will again be true.\n   On exit:\n\n   inform = -1  if the rank of U decreased by 1.\n   inform =  0  if the rank of U stayed the same.\n   inform =  1  if the rank of U increased by 1.\n   inform =  2  if the update seemed to be unstable\n                (diag much bigger than vnorm).\n   inform =  7  if the update was not completed (lack of storage).\n   inform =  8  if jrep is not between 1 and n.\n   ------------------------------------------------------------------\n   -- Jan 1985: Original F66 version.\n   -- Jul 1987: Modified to maintain U in trapezoidal form.\n   10 May 1988: First f77 version.\n   16 Oct 2000: Added test for instability (inform = 2).\n   ================================================================== */\nvoid LU8RPC(LUSOLrec *LUSOL, int MODE1, int MODE2,\n            int JREP, REAL V[], REAL W[],\n            int *INFORM, REAL *DIAG, REAL *VNORM)\n{\n  MYBOOL SINGLR;\n  int    LPRINT, NRANK, LENL, LENU, LROW, NRANK0, KREP, KLAST, IW, L1, J1, JSING;\n  REAL   UTOL1, UTOL2;\n\n  LPRINT = LUSOL->luparm[LUSOL_IP_PRINTLEVEL];\n  NRANK  = LUSOL->luparm[LUSOL_IP_RANK_U];\n  LENL   = LUSOL->luparm[LUSOL_IP_NONZEROS_L];\n  LENU   = LUSOL->luparm[LUSOL_IP_NONZEROS_U];\n  LROW   = LUSOL->luparm[LUSOL_IP_NONZEROS_ROW];\n  UTOL1  = LUSOL->parmlu[LUSOL_RP_SMALLDIAG_U];\n  UTOL2  = LUSOL->parmlu[LUSOL_RP_EPSDIAG_U];\n  NRANK0 = NRANK;\n  *DIAG  = ZERO;\n  *VNORM = ZERO;\n  if(JREP<1)\n    goto x980;\n  if(JREP>LUSOL->n)\n    goto x980;\n\n/*      ------------------------------------------------------------------\n        If mode1 = 0, there are no elements to be removed from  U\n        but we still have to set  krep  (using a backward loop).\n        Otherwise, use lu7zap to remove column  jrep  from  U\n        and set  krep  at the same time.\n        ------------------------------------------------------------------ */\n  if(MODE1==LUSOL_UPDATE_OLDEMPTY) {\n    KREP = LUSOL->n+1;\nx10:\n    KREP--;\n    if(LUSOL->iq[KREP]!=JREP)\n      goto x10;\n  }\n  else\n    LU7ZAP(LUSOL, JREP,&KREP,&LENU,&LROW,NRANK);\n\n/*      ------------------------------------------------------------------\n        Insert a new column of u and find klast.\n        ------------------------------------------------------------------ */\n  if(MODE2==LUSOL_UPDATE_NEWEMPTY) {\n    KLAST = 0;\n  }\n  else {\n    if(MODE2==LUSOL_UPDATE_NEWNONEMPTY) {\n/*            Transform v = a(new) to satisfy  L*v = a(new). */\n      LU6SOL(LUSOL, LUSOL_SOLVE_Lv_v, V,W, NULL, INFORM);\n    }\n    else if(V==NULL)\n/* Otherwise, the V vector is taken to satisfy this already, or stored earlier. */\n      V=LUSOL->vLU6L;\n      \n\n/*         Insert into  U  any nonzeros in the top of  v.\n           row  ip(klast)  will contain the last nonzero in pivotal order.\n           Note that  klast  will be in the range  ( 0, nrank ). */\n    LU7ADD(LUSOL, JREP,V,LENL,&LENU,&LROW,NRANK,INFORM,&KLAST,VNORM);\n    if(*INFORM==LUSOL_INFORM_ANEEDMEM)\n      goto x970;\n  }\n/*      ------------------------------------------------------------------\n        In general, the new column causes U to look like this:\n                    krep        n                 krep  n\n                   ....a.........          ..........a...\n                    .  a        .           .        a  .\n                     . a        .            .       a  .\n                      .a        .             .      a  .\n           P U Q =     a        .    or        .     a  .\n                       b.       .               .    a  .\n                       b .      .                .   a  .\n                       b  .     .                 .  a  .\n                       b   ......                  ..a...  nrank\n                       c                             c\n                       c                             c\n                       c                             c     m\n        klast points to the last nonzero \"a\" or \"b\".\n        klast = 0 means all \"a\" and \"b\" entries are zero.\n        ------------------------------------------------------------------ */\n  if(MODE2==LUSOL_UPDATE_NEWEMPTY) {\n    if(KREP>NRANK)\n      goto x900;\n  }\n  else if(NRANK<LUSOL->m) {\n/*         Eliminate any \"c\"s (in either case).\n           Row nrank + 1 may end up containing one nonzero. */\n    LU7ELM(LUSOL, JREP,V,&LENL,&LROW,NRANK,INFORM,DIAG);\n    if(*INFORM==LUSOL_INFORM_ANEEDMEM)\n      goto x970;\n    if(*INFORM==LUSOL_INFORM_LUSINGULAR) {\n/*            The nonzero is apparently significant.\n              Increase nrank by 1 and make klast point to the bottom. */\n      NRANK++;\n      KLAST = NRANK;\n    }\n  }\n  if(NRANK<LUSOL->n) {\n/*         The column rank is low.\n           In the first case, we want the new column to end up in\n           position nrank, so the trapezoidal columns will have a chance\n           later on (in lu7rnk) to pivot in that position.\n           Otherwise the new column is not part of the triangle.  We\n           swap it into position nrank so we can judge it for singularity.\n           lu7rnk might choose some other trapezoidal column later. */\n    if(KREP<NRANK)\n      KLAST = NRANK;\n    else {\n      LUSOL->iq[KREP] = LUSOL->iq[NRANK];\n      LUSOL->iq[NRANK] = JREP;\n      KREP = NRANK;\n    }\n  }\n/*      ------------------------------------------------------------------\n        If krep .lt. klast, there are some \"b\"s to eliminate:\n                     krep\n                   ....a.........\n                    .  a        .\n                     . a        .\n                      .a        .\n           P U Q =     a        .  krep\n                       b.       .\n                       b .      .\n                       b  .     .\n                       b   ......  nrank\n        If krep .eq. klast, there are no \"b\"s, but the last \"a\" still\n        has to be moved to the front of row krep (by lu7for).\n        ------------------------------------------------------------------ */\n  if(KREP<=KLAST) {\n/*         Perform a cyclic permutation on the current pivotal order,\n           and eliminate the resulting row spike.  krep becomes klast.\n           The final diagonal (if any) will be correctly positioned at\n           the front of the new krep-th row.  nrank stays the same. */\n    LU7CYC(LUSOL, KREP,KLAST,LUSOL->ip);\n    LU7CYC(LUSOL, KREP,KLAST,LUSOL->iq);\n    LU7FOR(LUSOL, KREP,KLAST,&LENL,&LENU,&LROW,INFORM,DIAG);\n    if(*INFORM==LUSOL_INFORM_ANEEDMEM)\n      goto x970;\n    KREP = KLAST;\n/*         Test for instability (diag much bigger than vnorm). */\n    SINGLR = (MYBOOL) ((*VNORM)<UTOL2*fabs(*DIAG));\n    if(SINGLR)\n      goto x920;\n  }\n/*      ------------------------------------------------------------------\n        Test for singularity in column krep (where krep<=nrank).\n        ------------------------------------------------------------------ */\n  *DIAG = ZERO;\n  IW = LUSOL->ip[KREP];\n  SINGLR = (MYBOOL) (LUSOL->lenr[IW]==0);\n  if(!SINGLR) {\n    L1 = LUSOL->locr[IW];\n    J1 = LUSOL->indr[L1];\n    SINGLR = (MYBOOL) (J1!=JREP);\n    if(!SINGLR) {\n      *DIAG = LUSOL->a[L1];\n      SINGLR = (MYBOOL) (fabs(*DIAG)<=UTOL1 || fabs(*DIAG)<=UTOL2*(*VNORM));\n    }\n  }\n  if(SINGLR && (KREP<NRANK)) {\n/*         Perform cyclic permutations to move column jrep to the end.\n           Move the corresponding row to position nrank\n           then eliminate the resulting row spike. */\n    LU7CYC(LUSOL, KREP,NRANK,LUSOL->ip);\n    LU7CYC(LUSOL, KREP,LUSOL->n,LUSOL->iq);\n    LU7FOR(LUSOL, KREP,NRANK,&LENL,&LENU,&LROW,INFORM,DIAG);\n    if(*INFORM==LUSOL_INFORM_ANEEDMEM)\n      goto x970;\n  }\n/*      Find the best column to be in position nrank.\n        If singlr, it can't be the new column, jrep.\n        If nothing satisfactory exists, nrank will be decreased. */\n  if(SINGLR || (NRANK<LUSOL->n)) {\n    JSING = 0;\n    if(SINGLR)\n      JSING = JREP;\n    LU7RNK(LUSOL, JSING,&LENU,&LROW,&NRANK,INFORM,DIAG);\n  }\n\n/*      ------------------------------------------------------------------\n        Update indeces of optional row-based version of L0.\n        ------------------------------------------------------------------ */\n#if 0\n  if(LUSOL->L0 != NULL)\n    LU1L0UPD(LUSOL, INFORM);\n#endif\n\n/*      ------------------------------------------------------------------\n        Set inform for exit.\n        ------------------------------------------------------------------ */\nx900:\n  if(NRANK==NRANK0)\n    *INFORM = LUSOL_INFORM_LUSUCCESS;\n  else if(NRANK<NRANK0) {\n    *INFORM = LUSOL_INFORM_RANKLOSS;\n    if(NRANK0==LUSOL->n) {\n      if(LPRINT>=LUSOL_MSG_SINGULARITY)\n        LUSOL_report(LUSOL, 0, \"lu8rpc  warning...\\nSingularity after replacing column.    jrep=%8d    diag=%g\\n\",\n                            JREP,DIAG);\n    }\n  }\n  else\n    *INFORM = LUSOL_INFORM_LUSINGULAR;\n  goto x990;\n/*      Instability. */\nx920:\n  *INFORM = LUSOL_INFORM_LUUNSTABLE;\n  if(LPRINT>=LUSOL_MSG_SINGULARITY)\n    LUSOL_report(LUSOL, 0, \"lu8rpc  warning...\\nInstability after replacing column.    jrep=%8d    diag=%g\\n\",\n                        JREP,DIAG);\n  goto x990;\n/*      Not enough storage. */\nx970:\n  *INFORM = LUSOL_INFORM_ANEEDMEM;\n  if(LPRINT>=LUSOL_MSG_SINGULARITY)\n    LUSOL_report(LUSOL, 0, \"lu8rpc  error...\\nInsufficient memory.    lena=%8d\\n\",\n                        LUSOL->lena);\n  goto x990;\n/*      jrep  is out of range. */\nx980:\n  *INFORM = LUSOL_INFORM_FATALERR;\n  if(LPRINT>=LUSOL_MSG_SINGULARITY)\n    LUSOL_report(LUSOL, 0, \"lu8rpc  error...\\njrep  is out of range.    m=%8d    n=%8d    jrep=%8d\\n\",\n                        LUSOL->m,LUSOL->n,JREP);\n/*      Exit. */\nx990:\n  LUSOL->luparm[LUSOL_IP_UPDATECOUNT]++;\n  LUSOL->luparm[LUSOL_IP_RANK_U]       = NRANK;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_L]   = LENL;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_U]   = LENU;\n  LUSOL->luparm[LUSOL_IP_NONZEROS_ROW] = LROW;\n  LUSOL->luparm[LUSOL_IP_INFORM]       = *INFORM;\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusolio.c",
    "content": "\n#include <stdio.h>\n#include <string.h>\n#include \"mmio.h\"\n#include \"hbio.h\"\n#include \"lusolio.h\"\n\n/* Utility routines to read matrix files in the Coordinate Text File format*/\n\nMYBOOL ctf_read_A(char *filename, int maxm, int maxn, int maxnz,\n                  int *m, int *n, int *nnzero, int *iA, int *jA, REAL *Aij)\n{\n  FILE *iofile;\n  int  eof;\n  char buffer[100];\n  int  k, i, j;\n  REAL Ak;\n  MYBOOL filldata;\n\n  *nnzero = 0;\n  *m      = 0;\n  *n      = 0;\n\n  iofile = fopen(filename, \"r\" );\n  if(iofile == NULL) {\n    printf(\"A file %s does not exist\\n\", filename);\n    return( FALSE );\n  }\n\n  filldata = (MYBOOL) !((iA == NULL) && (jA == NULL) && (Aij == NULL));\n  eof = TRUE;\n  for (k = 1; k <= maxnz; k++) {\n    eof = feof(iofile);\n    if(eof)\n      break;\n    eof = fscanf(iofile, \"%d %d %s\", &i, &j, buffer);\n    if(eof == 0 || eof == EOF || i <= 0 || j <= 0 || strlen(buffer) == 0)\n      break;\n    Ak = atof(buffer);\n    (*nnzero)++;\n    if (filldata) {\n      iA[k]  = i;\n      jA[k]  = j;\n      Aij[k] = Ak;\n    }\n    if (i > *m) *m = i;\n    if (j > *n) *n = j;\n  }\n  fclose( iofile );\n  if(!eof) {\n    printf(\"Too much data in A file.  Increase maxnz\\n\");\n    printf(\"Current maxnz = %d\\n\", maxnz);\n    return( FALSE );\n  }\n  printf(\"A  read successfully\\n\");\n  printf(\"m      = %d   n      = %d   nnzero = %d\\n\",\n          *m, *n, *nnzero);\n  if (*m > maxm  ||  *n > maxn) {\n    printf(\"However, matrix dimensions exceed maxm or maxn\\n\");\n    return( FALSE );\n  }\n  return( TRUE );\n}\n\nMYBOOL ctf_size_A(char *filename, int *m, int *n, int *nnzero)\n{\n  int maxint = 200000000;\n\n  return( ctf_read_A(filename, maxint, maxint, maxint,\n                     m, n, nnzero, NULL, NULL, NULL) );\n}\n\nMYBOOL ctf_read_b(char *filename, int m, REAL *b)\n{\n  FILE *iofile;\n  int  eof;\n  char buffer[100];\n  int  i;\n\n  iofile = fopen(filename, \"r\");\n  if(iofile == NULL) {\n    printf(\"b file %s does not exist\\n\", filename);\n    return( FALSE );\n  }\n\n  for (i = 1; i <= m; i++) {\n    if(feof(iofile))\n      goto x350;\n    eof = fscanf(iofile, \"%s\", buffer);\n    if(eof == 0 || eof == EOF)\n      goto x350;\n    b[i] = atof(buffer);\n  }\n\n  fclose( iofile );\n  printf(\"b  read successfully\\n\");\n  return( TRUE );\n\nx350:\n  fclose( iofile );\n  printf(\"Not enough data in b file.\\n\");\n  return( FALSE );\n}\n\n\n/* Utility routines to read matrix files in the MatrixMarket format*/\n#define mmf_recsize 255\nMYBOOL mmf_read_A(char *filename, int maxM, int maxN, int maxnz,\n                  int *M, int *N, int *nz, int *iA, int *jA, REAL *Aij)\n{\n  MM_typecode matcode;\n  FILE   *f;\n  int    i, k, ret_code, ival, jval;\n  REAL   Aval;\n  MYBOOL status = FALSE, ispat, filldata;\n  char   buf[mmf_recsize];\n\n  f = fopen(filename, \"r\");\n  if(f == NULL) \n    return( status );\n\n  if(mm_read_banner(f, &matcode) != 0) {\n    printf(\"Could not process Matrix Market banner.\\n\");\n    goto x900;\n  }\n\n  /*  Screen matrix types since LUSOL only supports a \n      subset of the Matrix Market data types. */\n  if(mm_is_complex(matcode) || mm_is_pattern(matcode)) {\n    printf(\"Sorry, this application does not support \");\n    printf(\"Market Market type: [%s]\\n\", mm_typecode_to_str(matcode));\n    goto x900;\n  }\n\n  /* Verify that we have sufficient array storage */\n  filldata = (MYBOOL) !((iA == NULL) && (jA == NULL) && (Aij == NULL));\n  if(filldata && maxN > 1 && jA == NULL) {\n    printf(\"Market Market insufficient array storage specified\\n\");\n    goto x900;\n  }\n\n  /* Find out size of sparse matrix .... */\n  ret_code = mm_read_mtx_crd_size(f, M, N, nz);\n  if(ret_code != 0 || !filldata || (*M > maxM) || (*N > maxN) || (*nz > maxnz)) {\n    status = !filldata;\n    goto x900;\n  }\n\n\n  /* NOTE: when reading in doubles, ANSI C requires the use of the \"l\"  */\n  /* specifier as in \"%lg\", \"%lf\", \"%le\", otherwise errors will occur   */\n  /*  (ANSI C X3.159-1989, Sec. 4.9.6.2, p. 136 lines 13-15)            */\n\n  /* Read dense matrix in column order */\n  ispat = (MYBOOL) mm_is_pattern(matcode);\n  k = 1;\n  if(mm_is_dense(matcode)) {\n    maxN = MIN(maxN, *N);\n    for (jval = 1; jval <= maxN; jval++) {\n      for (i = 1; i <= *M; i++) {\n        if(fgets(buf, mmf_recsize-1, f) == NULL)\n          break;\n        if(sscanf(buf, \"%lg\\n\", &Aval) == 0)\n          break;\n        if(Aval != 0) {\n          if(iA != NULL)\n            iA[k] = i;\n          if(jA != NULL)\n            jA[k] = jval;\n\n          /* Make sure we handle dense vector reading properly */\n          if(iA == NULL && jA == NULL)\n            Aij[i] = Aval;\n          else\n            Aij[k] = Aval;\n          k++;\n        }\n      }\n    }\n  }\n  /* Read sparse matrix by coordinate */\n  else {\n    for (i = 1; i <= *nz; i++) {\n      if(fgets(buf, mmf_recsize-1, f) == NULL)\n        break;\n      if(buf[0] == '%')\n        continue;\n      if(ispat) {\n        if(sscanf(buf, \"%d %d\\n\", &ival, &jval) == 0)\n          continue;\n        Aij[k] = 1.0;\n      }\n      else\n        if(sscanf(buf, \"%d %d %lg\\n\", &ival, &jval, &Aval) == 0)\n          continue;\n\n      /* Check if it is a nonzero and we are within column dimension */\n      if(Aval != 0 && jval <= maxN) {\n        Aij[k] = Aval;\n        if(iA != NULL)\n          iA[k] = ival;\n        if(jA != NULL)\n          jA[k] = jval;\n        k++;\n      }\n    }\n  }\n  *nz = k - 1;\n\n  /* Handle case where only the lower triangular parts are given */\n  if(!mm_is_general(matcode)) {\n    if((M != N) || (maxN != maxM) || (2*(*nz) > maxnz)) {\n      printf(\"Market Market cannot fill in symmetry data\\n\");\n      goto x900;\n    }\n    ispat = mm_is_skew(matcode);\n    for(i = 1; i <= *nz; i++) {\n      iA[k] = jA[i];\n      jA[k] = iA[i];\n      if(ispat)\n        Aij[k] = -Aij[i];\n      else\n        Aij[k] = Aij[i];\n      k++;\n    }\n    *nz = k - 1;\n  }\n  status = TRUE;\n\n  /* Finish up */\nx900:\n  fclose( f );\n  return( status );\n}\n\nMYBOOL mmf_size_A(char *filename, int *M, int *N, int *nz)\n{\n  int maxint = 200000000;\n\n  return( mmf_read_A(filename, maxint, maxint, maxint,\n                     M, N, nz, NULL, NULL, NULL) );\n}\n\nMYBOOL mmf_read_b(char *filename, int m, REAL *b)\n{\n  int im, jn, nnzero;\n\n  return( mmf_read_A(filename, m, 1, m,\n                     &im, &jn, &nnzero, NULL, NULL, b));\n}\n\n\n/* Utility routines to read matrix files in Harwell-Boeing format*/\n\nMYBOOL hbf_read_A(char *filename, int maxM, int maxN, int maxnz,\n                  int *M, int *N, int *nz, int *iA, int *jA, REAL *Aij)\n{\n  MYBOOL success;\n\n  success = hbf_size_A(filename, M, N, nz);\n  if(!success)\n    return( success );\n\n  Aij[1] = 0;\n  success = (MYBOOL) readHB_mat_double(filename, jA, iA-1, Aij-1);\n\n  /* Test if we have a pattern matrix and fill it with all zeros */\n  if(Aij[1] == 0) {\n    int i;\n    for(i = 1; i <= *nz; i++)\n      Aij[i] = 1;\n  }\n\n  /* Expand the column nz counts to triplet format */\n  if(success) {\n    int i, j, ii, k;\n    k = *nz;\n    for(j = *N; j > 0; j--) {\n      ii = jA[j];\n      for(i = jA[j-1]; i < ii; i++, k--)\n        jA[k] = j;\n    }\n  }\n  return( success );\n}\n\nMYBOOL hbf_size_A(char *filename, int *M, int *N, int *nz)\n{\n  int  Nrhs;\n  char *Type;\n\n  return( (MYBOOL) readHB_info(filename, M, N, nz, &Type, &Nrhs) );\n}\n\nMYBOOL hbf_read_b(char *filename, int m, REAL *b)\n{\n  return( (MYBOOL) readHB_aux_double(filename, 'F', b) ); /* Same format as matrix */\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusolio.h",
    "content": "#ifndef HEADER_lusolio\n#define HEADER_lusolio\n\n/* Include necessary libraries                                               */\n/* ------------------------------------------------------------------------- */\n#include \"lusol.h\"\n\nMYBOOL ctf_read_A(char *filename, int maxm, int maxn, int maxnz,\n                  int *m, int *n, int *nnzero, int *iA, int *jA, REAL *Aij);\nMYBOOL ctf_size_A(char *filename, int *m, int *n, int *nnzero);\nMYBOOL ctf_read_b(char *filename, int m, REAL *b);\n\nMYBOOL mmf_read_A(char *filename, int maxM, int maxN, int maxnz,\n                  int *M, int *N, int *nz, int *iA, int *jA, REAL *Aij);\nMYBOOL mmf_size_A(char *filename, int *M, int *N, int *nz);\nMYBOOL mmf_read_b(char *filename, int m, REAL *b);\n\nMYBOOL hbf_read_A(char *filename, int maxM, int maxN, int maxnz,\n                  int *M, int *N, int *nz, int *iA, int *jA, REAL *Aij);\nMYBOOL hbf_size_A(char *filename, int *M, int *N, int *nz);\nMYBOOL hbf_read_b(char *filename, int m, REAL *b);\n\n\n#endif /* HEADER_lusolio */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusolmain.c",
    "content": "\n/*     This program solves a sparse linear system Ax = b using LUSOL. */\n\n#include <stdlib.h>\n#include <stdio.h>\n#include <math.h>\n#include <string.h>\n#include <time.h>\n#include \"commonlib.h\"\n#include \"myblas.h\"\n#include \"lusol.h\"\n#include \"lusolio.h\"\n#include \"lusolmain.h\"\n\n#if (defined WIN32) || (defined WIN64)\nvoid _strupr_(char *s)\n{\n  _strupr(s);\n}\n#else\n/* Yin Zhang noted that _strupr() is not available on many Unix platforms */\nvoid _strupr_(char *s)\n{\n  int  i;\n  char c;\n  for (i = 0; i < strlen(s); i++) {\n    c = s[i];\n    if (c <= 'z' && c >= 'a') {\n      s[i] = c - 'a' + 'A';\n    }\n  }\n}\n#endif\n\nMYBOOL getFileName(char *filename, char *test)\n{\n  MYBOOL status;\n  status = (MYBOOL) (('-' != test[0]) && (strlen(test) > 1));\n  if(status)\n    strcpy(filename, test);\n  return(status);\n}\nMYBOOL isNum(char val)\n{\n  int ord;\n  ord = (int) val - 48;\n  return( (MYBOOL) ((ord >= 0) && (ord <= 9)) );\n}\n\nvoid main( int argc, char *argv[], char *envp[] )\n{\n/* Output device */\n  FILE *outunit = stdout;\n\n/* Overall dimensions allocated */\n  int    maxm = MAXROWS, maxn = MAXCOLS, maxnz = MAXNZ,\n         replace = 0, randcol = 0;\n  MYBOOL ftran = TRUE;\n\n/* Storage for A, b */\n  REAL   *Aij = NULL, *b = NULL, *xexact = NULL;\n  int    *iA = NULL, *jA = NULL;\n\n/* Storage for LUSOL */\n  LUSOLrec *LUSOL = NULL;\n\n/* Define local storage variables */\n  int  i     , inform, j     , k     , i1   ,\n       m     , useropt, lenb, lenx,\n       n     , nelem , nnzero;\n  REAL Amax  , test  ,\n       bnorm , rnorm , xnorm,\n       *rhs = NULL, *r = NULL, *x = NULL;\n  char fileext[50], filename[255], blasname[255];\n  MYBOOL printsolution = FALSE, success = FALSE;\n\n/* Check if we have input parameters */\n  useropt = argc;\n  if(useropt < 2) {\n    printf(\"LUSOL v%d.%d.%d.%d - Linear equation solver - Development edition.\\n\",\n           LUSOL_VERMAJOR, LUSOL_VERMINOR, LUSOL_RELEASE, LUSOL_BUILD);\n    printf(\"Usage:   lusol [-p <type>] [-t <tolerance>] [-m <memscalar>]\\n\");\n    printf(\"               [-s] <MatrixFile> [<RhsFile>]\\n\");\n    printf(\"Options: -p <type>        <0..3>    Selects pivot type.\\n\");\n    printf(\"         -t <tolerance>   <1..100>  Selects diagonal tolerance.\\n\");\n    printf(\"         -m <memscalar>   <%d..100> Memory allocation scalar.\\n\", LUSOL_MULT_nz_a);\n    printf(\"         -b               Solves using btran (rather than ftran).\\n\");\n    printf(\"         -r <times>       Randomly replace a column and resolve.\\n\");\n    printf(\"         -s               Show the computed solution.\\n\");\n    printf(\"         -blas <lib>      Activates external optimized BLAS library.\\n\");\n    printf(\"Formats: Conventional RCV .TXT, MatrixMarket .MTX, or Harwell-Boeing .RUA\\n\");\n    printf(\"Author:  Michael A. Saunders (original Fortran version)\\n\");\n    printf(\"         Kjell Eikland       (modified C version)\\n\");\n    return;\n  }\n\n/* Create the LUSOL object and set user options */\n  LUSOL = LUSOL_create(outunit, 0, LUSOL_PIVMOD_TPP, 0);\n#if 1\n  LUSOL->luparm[LUSOL_IP_ACCELERATION] = LUSOL_OTHERORDER | LUSOL_ACCELERATE_L0;\n#elif 0\n  LUSOL->luparm[LUSOL_IP_ACCELERATION] = LUSOL_AUTOORDER | LUSOL_ACCELERATE_L0;\n#endif\n  LUSOL->luparm[LUSOL_IP_SCALAR_NZA] = 10;\n  i = 1;\n  n = 0;\n  filename[0] = '\\0';\n  blasname[0] = '\\0';\n  while((n == 0) && (i < argc)) {\n    if(strcmp(\"-p\", argv[i]) == 0) {\n      i1 = i+1;\n      if((i1 < argc) && isNum(argv[i1][0])) {\n        i = i1;\n        m = atoi(argv[i]);\n        if(m < 0 || m > LUSOL_PIVMOD_MAX)\n          continue;\n        LUSOL->luparm[LUSOL_IP_PIVOTTYPE] = m;\n      }\n    }\n    else if(strcmp(\"-t\", argv[i]) == 0) {\n      i1 = i+1;\n      if((i1 < argc) && isNum(argv[i1][0])) {\n        i = i1;\n        Amax = atof(argv[i]);\n        if(Amax < 1 || Amax > 100)\n          continue;\n        LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij] = Amax;\n      }\n    }\n    else if(strcmp(\"-m\", argv[i]) == 0) {\n      i1 = i+1;\n      if((i1 < argc) && isNum(argv[i1][0])) {\n        i = i1;\n        m = atoi(argv[i]);\n        if(m < LUSOL_MULT_nz_a || m > 100)\n          continue;\n        LUSOL->luparm[LUSOL_IP_SCALAR_NZA] = atoi(argv[i]);\n      }\n    }\n    else if(strcmp(\"-s\", argv[i]) == 0)\n      printsolution = TRUE;\n    else if(strcmp(\"-b\", argv[i]) == 0)\n      ftran = FALSE;\n    else if(strcmp(\"-r\", argv[i]) == 0) {\n      i1 = i+1;\n      if((i1 < argc) && isNum(argv[i1][0])) {\n        i = i1;\n        m = atoi(argv[i]);\n        if(m < 0 || m > 10)\n          continue;\n      }\n      else\n        m = 1;\n      srand((unsigned) time( NULL ));\n      replace = 2*m;\n    }\n    else if(strcmp(\"-blas\", argv[i]) == 0) {\n      i1 = i+1;\n      if((i1 < argc) && getFileName(blasname, argv[i1])) {\n        if(!load_BLAS(blasname))\n          fprintf(outunit, \"Could not load external BLAS library '%s'\\n\", blasname);\n        i = i1;\n      }\n      else\n        fprintf(outunit, \"Ignoring incomplete parameter %d '%s'\\n\", i, argv[i]);\n    }\n    else {\n      if(getFileName(filename, argv[i])) {\n        useropt = i;\n        break;\n      }\n      else\n        fprintf(outunit, \"Ignoring unknown parameter %d '%s'\\n\", i, argv[i]);\n    }\n    i++;\n  }\n\n/* Obtain file extension and see if we must estimate matrix data size */\n  strcpy(fileext, strchr(argv[useropt], '.'));\n  /* Yin Zhang noted that _strupr() is not available on many Unix platforms. */\n  _strupr_(fileext);\n/*  _strupr(fileext);*/\n\n  /* Read conventional text file format */\n  if(strcmp(fileext, \".TXT\") == 0) {\n    if(!ctf_size_A(filename, &maxm, &maxn, &maxnz))\n      goto x900;\n  }\n  /* Read MatrixMarket file format */\n  else if(strcmp(fileext, \".MTX\") == 0) {\n    if(!mmf_size_A(filename, &maxm, &maxn, &maxnz))\n      goto x900;\n  }\n  /* Read Harwell-Boeing file format */\n  else if(strcmp(fileext, \".RUA\") == 0) {\n    if(!hbf_size_A(filename, &maxm, &maxn, &maxnz))\n      goto x900;\n  }\n  else {\n    fprintf(outunit, \"Unrecognized matrix file extension %s\\n\", fileext);\n    goto x900;\n  }\n\n/* Create the arrays */\n\n  Aij = (REAL *) LUSOL_CALLOC(maxnz + BLAS_BASE, sizeof(REAL));\n  iA = (int *)   LUSOL_CALLOC(maxnz + BLAS_BASE, sizeof(int));\n  jA = (int *)   LUSOL_CALLOC(maxnz + BLAS_BASE, sizeof(int));\n  if(ftran)\n    lenb = maxm;\n  else\n    lenb = maxn;\n  b   = (REAL *) LUSOL_CALLOC(lenb+BLAS_BASE, sizeof(REAL));\n  rhs = (REAL *) LUSOL_CALLOC(lenb+BLAS_BASE, sizeof(REAL));\n\n  if(ftran)\n    lenx = maxn;\n  else\n    lenx = maxm;\n  xexact = (REAL *) LUSOL_CALLOC(lenx+BLAS_BASE, sizeof(REAL));\n  r = (REAL *) LUSOL_CALLOC(lenx+BLAS_BASE, sizeof(REAL));\n  x = (REAL *) LUSOL_CALLOC(lenx+BLAS_BASE, sizeof(REAL));\n\n/* -----------------------------------------------------------------\n   Read data files.\n   ----------------------------------------------------------------- */\n  fprintf(stdout, \"\\n========================================\\n\");\n  fprintf(stdout,   \"LUSOL v%d.%d.%d.%d - Linear equation solver\",\n                    LUSOL_VERMAJOR, LUSOL_VERMINOR, LUSOL_RELEASE, LUSOL_BUILD);\n  fprintf(stdout, \"\\n========================================\\n\");\n\n/* -----------------------------------------------------------------\n   Read data for A\n   ----------------------------------------------------------------- */\n  /* Read conventional text file format */\n  if(strcmp(fileext, \".TXT\") == 0) {\n    if(!ctf_read_A(argv[useropt], maxm, maxn, maxnz,\n                   &m, &n, &nnzero, iA, jA, Aij))\n      goto x900;\n  }\n  /* Read MatrixMarket file format */\n  else if(strcmp(fileext, \".MTX\") == 0) {\n    if(!mmf_read_A(argv[useropt], maxm, maxn, maxnz,\n                   &m, &n, &nnzero, iA, jA, Aij))\n      goto x900;\n  }\n  /* Read Harwell-Boeing file format */\n  else if(strcmp(fileext, \".RUA\") == 0) {\n    if(!hbf_read_A(argv[useropt], maxm, maxn, maxnz,\n                   &m, &n, &nnzero, iA, jA, Aij))\n      goto x900;\n  }\n  else {\n    fprintf(outunit, \"Error: Unrecognized matrix file extension %s\\n\", fileext);\n    goto x900;\n  }\n\n/* -----------------------------------------------------------------\n   Read data for b\n   ----------------------------------------------------------------- */\n  /* Handle Harwell-Boeing case where the file contains a RHS */\n  i = strcmp(fileext, \".RUA\");\n\n  if((useropt == argc-1) && (i != 0)) {\n    srand(timeNow());\n    i1 = m;\n    while(i1 > 0) {\n      test = rand();\n      i = RAND_MAX;\n      i = (int) ((test/i)*(m-1));\n/*      b[i+1] = 1.0; */\n      b[i+1] = i - 5;\n      i1--;\n    }\n    if(printsolution)\n      blockWriteREAL(outunit, \"\\nGenerated RHS vector\", b, 1, lenb);\n  }\n  else {\n    if(i != 0)\n      useropt++;\n    strcpy(fileext, strchr(argv[useropt], '.'));\n    _strupr_(fileext);\n\n    /* Read conventional text file format */\n    if(strcmp(fileext, \".TXT\") == 0) {\n      if(!ctf_read_b(argv[useropt], lenb, b))\n        goto x900;\n    }\n    /* Read MatrixMarket file format */\n    else if(strcmp(fileext, \".MTX\") == 0) {\n      if(!mmf_read_b(argv[useropt], lenb, b))\n        goto x900;\n    }\n  /* Read Harwell-Boeing file format */\n    else if(strcmp(fileext, \".RUA\") == 0) {\n      if(!hbf_read_b(argv[useropt], lenb, b))\n        goto x900;\n    }\n    else {\n      fprintf(outunit, \"Error: Unrecognized vector file extension %s\\n\", fileext);\n      goto x900;\n    }\n  }\n  success = TRUE;\n\n/* -----------------------------------------------------------------\n   Show data on input\n   ----------------------------------------------------------------- */\n  fprintf(outunit, \"\\nData read from:\\n%s\\n\", filename);\n  test = (double) nnzero / ((double) m * (double) n);\n  test *= 100.0;\n  fprintf(outunit, \"Rows = %d   Columns = %d   Non-zeros = %d  Density =%8.4f%%\\n\",\n                   m, n, nnzero, test);\n\n/* -----------------------------------------------------------------\n   Load A into (a, indc, indr).\n   ----------------------------------------------------------------- */\n#if 0 /* BUG !!! */\n  if(n != m)\n    LUSOL->luparm[LUSOL_IP_KEEPLU] = FALSE;\n#endif\n#ifdef LegacyTesting\n  LUSOL->luparm[LUSOL_IP_SCALAR_NZA] = LUSOL_MULT_nz_a;\n  LUSOL_sizeto(LUSOL, MAXROWS, MAXCOLS, MAXNZ*LUSOL_MULT_nz_a);\n#endif\n\n  if(!LUSOL_assign(LUSOL, iA, jA, Aij, nnzero, TRUE)) {\n    fprintf(outunit, \"Error: LUSOL failed due to insufficient memory.\\n\");\n    goto x900;\n  }\n\n/* ------------------------------------------------------------------\n   Factor  A = L U.\n   ------------------------------------------------------------------ */\n  nelem = nnzero;\n  inform = LUSOL_factorize( LUSOL);\n  if(inform > LUSOL_INFORM_SERIOUS) {\n    fprintf(outunit, \"Error:\\n%s\\n\", LUSOL_informstr(LUSOL, inform));\n    goto x900;\n  }\n  if(n != m)\n    goto x800;\n\n  /* Get the largest element in A; we use it below as an estimate\n     of ||A||_inf, even though it isn't a proper norm. */\n  Amax = LUSOL->parmlu[LUSOL_RP_MAXELEM_A];\n\n/* ------------------------------------------------------------------\n   SOLVE  A x = b  or  x'A = b'.\n   Save b first because lu6sol() overwrites the rhs.\n   ------------------------------------------------------------------ */\n  MEMCOPY(x, b, lenb+BLAS_BASE);\n\nResolve:\n  if(ftran)\n    inform = LUSOL_ftran(LUSOL, x, NULL, FALSE);\n  else\n    inform = LUSOL_btran(LUSOL, x, NULL);\n  if(inform > LUSOL_INFORM_SERIOUS) {\n    fprintf(outunit, \"Error:\\n%s\\n\", LUSOL_informstr(LUSOL, inform));\n    goto x900;\n  }\n  if(printsolution)\n    blockWriteREAL(outunit, \"\\nSolution vector\", x, 1, lenb);\n\n/* ------------------------------------------------------------------\n   Set r = b - Ax.\n   Find norm of r and x.\n   ------------------------------------------------------------------ */\n  MEMCOPY(r, b, lenb+BLAS_BASE);\n  for(k = 1; k <= nnzero; k++) {\n    i    = iA[k];  /* Row number    */\n    j    = jA[k];  /* Column number */\n    if(ftran)\n      r[i] -= Aij[k]*x[j];\n    else\n      r[j] -= Aij[k]*x[i];\n  }\n/*  blockWriteREAL(outunit, \"\\nResidual vector\", r, 1, lenb);*/\n  bnorm  = dnormi( lenb, b );\n  rnorm  = dnormi( lenb, r );\n  xnorm  = dnormi( lenx, x );\n\n/* ------------------------------------------------------------------\n   Report the findings.\n   ------------------------------------------------------------------ */\n  if(randcol > 0)\n    fprintf(outunit, \"\\n\\nColumn %d was %s\\n\",\n                      randcol,\n                      (mod(replace,2) == 1 ? \"replaced with random data\" : \"restored\"));\n\nx800:\n  fprintf(outunit, \"\\nLU size statistics (%d reallocations):\\n\",\n                   LUSOL->expanded_a);\n  test = LUSOL->luparm[LUSOL_IP_NONZEROS_U0]+LUSOL->luparm[LUSOL_IP_NONZEROS_L0];\n  fprintf(outunit, \"L0-size = %d   U0-size = %d   LU-nonzeros = %d   Fill-in = %.1fx\\n\",\n                   LUSOL->luparm[LUSOL_IP_NONZEROS_L0],\n                   LUSOL->luparm[LUSOL_IP_NONZEROS_U0],\n                   (int) test, test/nnzero);\n  if(n != m) {\n    fprintf(outunit, \"%s with a factor tol. of %g identified %d singularities.\\n\",\n                     LUSOL_pivotLabel(LUSOL), LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij],\n                     LUSOL->luparm[LUSOL_IP_SINGULARITIES]);\n    goto x900;\n  }\n\n  test   = rnorm / (Amax*xnorm);\n  fprintf(outunit, \"\\nAccuracy statistics:\\n\");\n  fprintf(outunit, \"%s with a factor tol. of %g gave a rel.error of %g and %d singularities.\\n\",\n                   LUSOL_pivotLabel(LUSOL), LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij], test,\n                   LUSOL->luparm[LUSOL_IP_SINGULARITIES]);\n  fprintf(outunit, \"Amax = %g   bnorm = %g   rnorm = %g   xnorm = %g\\n\",\n                   Amax, bnorm, rnorm, xnorm);\n\n  fprintf(outunit, \"\\n\");\n\n  if (test <= 1.0e-8)\n    fprintf(outunit, \"The equations were solved with very high accuracy.\\n\");\n  else if (test <= 1.0e-6)\n    fprintf(outunit, \"The equations were solved with reasonably good accuracy.\\n\");\n  else {\n    if (test <= 1.0e-4)\n      fprintf(outunit, \"Questionable accuracy; the LU factors may not be good enough.\\n\");\n    else\n      fprintf(outunit, \"Poor accuracy; the LU factorization probably failed.\\n\");\n    if(LUSOL->luparm[LUSOL_IP_PIVOTTYPE] == LUSOL_PIVMOD_TRP)\n      fprintf(outunit, \"Try a smaller factor tolerance (current is %g).\\n\",\n                       LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij]);\n    else\n      fprintf(outunit, \"Try a smaller factor tolerance and/or TRP pivoting.\\n\");\n  }\n\n /* Check if we should replace a column and resolve */\n  if(replace > 0) {\n    replace--;\n    MEMCLEAR(x, lenb+BLAS_BASE);\n    if(mod(replace, 2) == 1) {\n      /* Randomly find a column and replace the column values with random data */\n      rnorm   = rand();\n      randcol = (int) (n * rnorm / (RAND_MAX+1.0)) + 1;\n      for(i = 1; i < m; i++)\n        x[i] = Amax * rand() / RAND_MAX;\n    }\n    else {\n      /* Put the previously replaced column back and resolve */\n      for (k = 1; k <= nnzero; k++) {\n        i    = iA[k];\n        j    = jA[k];\n        if(j == randcol)\n          x[i] = Aij[k];\n      }\n    }\n    inform = LUSOL_replaceColumn(LUSOL, randcol, x);\n    MEMCOPY(b, x, lenb+BLAS_BASE);\n    if(inform != LUSOL_INFORM_LUSUCCESS)\n      fprintf(outunit, \"Error:\\n%s\\n\", LUSOL_informstr(LUSOL, inform));\n    else\n      goto Resolve;\n  }\n\n\n/* Free memory */\nx900:\n  if(!success)\n    fprintf(outunit, \"Insufficient memory or data file not found.\\n\");\n\n  LUSOL_FREE(Aij);\n  LUSOL_FREE(b);\n  LUSOL_FREE(xexact);\n  LUSOL_FREE(iA);\n  LUSOL_FREE(jA);\n\n  LUSOL_FREE(rhs);\n  LUSOL_FREE(r);\n  LUSOL_FREE(x);\n\n#if 0\n  LUSOL_dump(NULL, LUSOL);\n -blas \"atlas_AXP_512_360.dll\" -b -p 1 \"STP3D_A.MTX\"\n \"C:\\Shared Files\\Visual Studio Projects\\LU\\MatrixMarket\\sherman5.mtx\" \"C:\\Shared Files\\Visual Studio Projects\\LU\\MatrixMarket\\sherman5_rhs1.mtx\"\n A6805.txt b6805.txt\n A10009.txt b10009.txt\n fidap005.mtx fidap005_rhs1.mtx\n fidapm05.mtx fidapm05_rhs1.mtx\n -b -p 1 \"basis.mtx\"\n -b -p 1 \"LU-test3.mtx\"\n#endif\n\n  LUSOL_free(LUSOL);\n\n/*     End of main program for Test of LUSOL */\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/lusolmain.h",
    "content": "\n#ifdef StaticMemAlloc\n\n#if 0\n  #define MAXNZ        300000\n  #define MAXROWS       15000\n#elif 0\n  #define MAXNZ         60000\n  #define MAXROWS       12500\n#elif 1\n  #define MAXNZ         40000\n  #define MAXROWS        3500\n#else\n  #define MAXNZ          1000\n  #define MAXROWS          50\n#endif\n\n#else\n\n  #define MAXNZ          1000\n  #define MAXROWS          50\n\n#endif\n\n#define MAXCOLS     MAXROWS\n#define MAXLU      (LUSOL_MULT_nz_a*MAXNZ)\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/mmio.c",
    "content": "/* \n*   Matrix Market I/O library for ANSI C\n*\n*   See http://math.nist.gov/MatrixMarket for details.\n*\n*   (Version 1.01, 5/2003)\n*/\n\n\n#include <stdlib.h>\n#include <stdio.h>\n#include <string.h>\n#include <ctype.h>\n\n#include \"mmio.h\"\n\nint mm_read_unsymmetric_sparse(const char *fname, int *M_, int *N_, int *nz_,\n                double **val_, int **I_, int **J_)\n{\n    FILE *f;\n    MM_typecode matcode;\n    int M, N, nz;\n    int i;\n    double *val;\n    int *I, *J;\n \n    if ((f = fopen(fname, \"r\")) == NULL)\n            return -1;\n \n \n    if (mm_read_banner(f, &matcode) != 0)\n    {\n        printf(\"mm_read_unsymetric: Could not process Matrix Market banner \");\n        printf(\" in file [%s]\\n\", fname);\n        return -1;\n    }\n \n \n \n    if ( !(mm_is_real(matcode) && mm_is_matrix(matcode) &&\n            mm_is_sparse(matcode)))\n    {\n        fprintf(stderr, \"Sorry, this application does not support \");\n        fprintf(stderr, \"Market Market type: [%s]\\n\",\n                mm_typecode_to_str(matcode));\n        return -1;\n    }\n \n    /* find out size of sparse matrix: M, N, nz .... */\n \n    if (mm_read_mtx_crd_size(f, &M, &N, &nz) !=0)\n    {\n        fprintf(stderr, \"read_unsymmetric_sparse(): could not parse matrix size.\\n\");\n        return -1;\n    }\n \n    *M_ = M;\n    *N_ = N;\n    *nz_ = nz;\n \n    /* reseve memory for matrices */\n \n    I = (int *) malloc(nz * sizeof(int));\n    J = (int *) malloc(nz * sizeof(int));\n    val = (double *) malloc(nz * sizeof(double));\n \n    *val_ = val;\n    *I_ = I;\n    *J_ = J;\n \n    /* NOTE: when reading in doubles, ANSI C requires the use of the \"l\"  */\n    /*   specifier as in \"%lg\", \"%lf\", \"%le\", otherwise errors will occur */\n    /*  (ANSI C X3.159-1989, Sec. 4.9.6.2, p. 136 lines 13-15)            */\n \n    for (i=0; i<nz; i++)\n    {\n        fscanf(f, \"%d %d %lg\\n\", &I[i], &J[i], &val[i]);\n        I[i]--;  /* adjust from 1-based to 0-based */\n        J[i]--;\n    }\n    fclose(f);\n \n    return 0;\n}\n\nint mm_is_valid(MM_typecode matcode)\n{\n    if (!mm_is_matrix(matcode)) return 0;\n    if (mm_is_dense(matcode) && mm_is_pattern(matcode)) return 0;\n    if (mm_is_real(matcode) && mm_is_hermitian(matcode)) return 0;\n    if (mm_is_pattern(matcode) && (mm_is_hermitian(matcode) || \n                mm_is_skew(matcode))) return 0;\n    return 1;\n}\n\nint mm_read_banner(FILE *f, MM_typecode *matcode)\n{\n    char line[MM_MAX_LINE_LENGTH];\n    char banner[MM_MAX_TOKEN_LENGTH];\n    char mtx[MM_MAX_TOKEN_LENGTH]; \n    char crd[MM_MAX_TOKEN_LENGTH];\n    char data_type[MM_MAX_TOKEN_LENGTH];\n    char storage_scheme[MM_MAX_TOKEN_LENGTH];\n    char *p;\n\n\n    mm_clear_typecode(matcode);  \n\n    if (fgets(line, MM_MAX_LINE_LENGTH, f) == NULL) \n        return MM_PREMATURE_EOF;\n\n    if (sscanf(line, \"%s %s %s %s %s\", banner, mtx, crd, data_type, \n        storage_scheme) != 5)\n        return MM_PREMATURE_EOF;\n\n\t/* convert to lower case */\n    for (p=mtx; *p!='\\0'; *p= (char) tolower(*p),p++);  \n    for (p=crd; *p!='\\0'; *p= (char) tolower(*p),p++);  \n    for (p=data_type; *p!='\\0'; *p= (char) tolower(*p),p++);\n    for (p=storage_scheme; *p!='\\0'; *p= (char) tolower(*p),p++);\n\n    /* check for banner */\n    if (strncmp(banner, MatrixMarketBanner, strlen(MatrixMarketBanner)) != 0)\n        return MM_NO_HEADER;\n\n    /* first field should be \"mtx\" */\n    if (strcmp(mtx, MM_MTX_STR) != 0)\n        return  MM_UNSUPPORTED_TYPE;\n    mm_set_matrix(matcode);\n\n\n    /* second field describes whether this is a sparse matrix (in coordinate\n            storgae) or a dense array */\n\n\n    if (strcmp(crd, MM_SPARSE_STR) == 0)\n        mm_set_sparse(matcode);\n    else\n    if (strcmp(crd, MM_DENSE_STR) == 0)\n            mm_set_dense(matcode);\n    else\n        return MM_UNSUPPORTED_TYPE;\n    \n\n    /* third field */\n\n    if (strcmp(data_type, MM_REAL_STR) == 0)\n        mm_set_real(matcode);\n    else\n    if (strcmp(data_type, MM_COMPLEX_STR) == 0)\n        mm_set_complex(matcode);\n    else\n    if (strcmp(data_type, MM_PATTERN_STR) == 0)\n        mm_set_pattern(matcode);\n    else\n    if (strcmp(data_type, MM_INT_STR) == 0)\n        mm_set_integer(matcode);\n    else\n        return MM_UNSUPPORTED_TYPE;\n    \n\n    /* fourth field */\n\n    if (strcmp(storage_scheme, MM_GENERAL_STR) == 0)\n        mm_set_general(matcode);\n    else\n    if (strcmp(storage_scheme, MM_SYMM_STR) == 0)\n        mm_set_symmetric(matcode);\n    else\n    if (strcmp(storage_scheme, MM_HERM_STR) == 0)\n        mm_set_hermitian(matcode);\n    else\n    if (strcmp(storage_scheme, MM_SKEW_STR) == 0)\n        mm_set_skew(matcode);\n    else\n        return MM_UNSUPPORTED_TYPE;\n        \n\n    return 0;\n}\n\nint mm_write_mtx_crd_size(FILE *f, int M, int N, int nz)\n{\n    if (fprintf(f, \"%d %d %d\\n\", M, N, nz) < 0)\n        return MM_COULD_NOT_WRITE_FILE;\n    else \n        return 0;\n}\n\nint mm_read_mtx_crd_size(FILE *f, int *M, int *N, int *nz )\n{\n    char line[MM_MAX_LINE_LENGTH];\n    int num_items_read;\n\n    /* set return null parameter values, in case we exit with errors */\n    *M = *N = *nz = 0;\n\n    /* now continue scanning until you reach the end-of-comments */\n    do {\n      if (fgets(line,MM_MAX_LINE_LENGTH,f) == NULL) \n          return MM_PREMATURE_EOF;\n    } while (line[0] == '%');\n\n    /* line[] is either blank, har M,N or M,N,nz */\n    if (sscanf(line, \"%d %d %d\", M, N, nz) >= 2)\n      return 0;\n        \n    else\n    do { \n        num_items_read = fscanf(f, \"%d %d %d\", M, N, nz); \n        if (num_items_read == EOF) return MM_PREMATURE_EOF;\n    } while (num_items_read < 2);\n\n    return 0;\n}\n\n\nint mm_read_mtx_array_size(FILE *f, int *M, int *N)\n{\n    char line[MM_MAX_LINE_LENGTH];\n    int num_items_read;\n    /* set return null parameter values, in case we exit with errors */\n    *M = *N = 0;\n\t\n    /* now continue scanning until you reach the end-of-comments */\n    do \n    {\n        if (fgets(line,MM_MAX_LINE_LENGTH,f) == NULL) \n            return MM_PREMATURE_EOF;\n    }while (line[0] == '%');\n\n    /* line[] is either blank or has M,N, nz */\n    if (sscanf(line, \"%d %d\", M, N) == 2)\n        return 0;\n        \n    else /* we have a blank line */\n    do\n    { \n        num_items_read = fscanf(f, \"%d %d\", M, N); \n        if (num_items_read == EOF) return MM_PREMATURE_EOF;\n    }\n    while (num_items_read != 2);\n\n    return 0;\n}\n\nint mm_write_mtx_array_size(FILE *f, int M, int N)\n{\n    if (fprintf(f, \"%d %d\\n\", M, N) < 0)\n        return MM_COULD_NOT_WRITE_FILE;\n    else \n        return 0;\n}\n\n\n\n/*-------------------------------------------------------------------------*/\n\n/******************************************************************/\n/* use when I[], J[], and val[]J, and val[] are already allocated */\n/******************************************************************/\n\nint mm_read_mtx_crd_data(FILE *f, int M, int N, int nz, int I[], int J[],\n        double val[], MM_typecode matcode)\n{\n    int i;\n    if (mm_is_complex(matcode))\n    {\n        for (i=0; i<nz; i++)\n            if (fscanf(f, \"%d %d %lg %lg\", &I[i], &J[i], &val[2*i], &val[2*i+1])\n                != 4) return MM_PREMATURE_EOF;\n    }\n    else if (mm_is_real(matcode))\n    {\n        for (i=0; i<nz; i++)\n        {\n            if (fscanf(f, \"%d %d %lg\\n\", &I[i], &J[i], &val[i])\n                != 3) return MM_PREMATURE_EOF;\n\n        }\n    }\n\n    else if (mm_is_pattern(matcode))\n    {\n        for (i=0; i<nz; i++)\n            if (fscanf(f, \"%d %d\", &I[i], &J[i])\n                != 2) return MM_PREMATURE_EOF;\n    }\n    else\n        return MM_UNSUPPORTED_TYPE;\n\n    return 0;\n        \n}\n\nint mm_read_mtx_crd_entry(FILE *f, int *I, int *J,\n        double *real, double *imag, MM_typecode matcode)\n{\n    if (mm_is_complex(matcode))\n    {\n            if (fscanf(f, \"%d %d %lg %lg\", I, J, real, imag)\n                != 4) return MM_PREMATURE_EOF;\n    }\n    else if (mm_is_real(matcode))\n    {\n            if (fscanf(f, \"%d %d %lg\\n\", I, J, real)\n                != 3) return MM_PREMATURE_EOF;\n\n    }\n\n    else if (mm_is_pattern(matcode))\n    {\n            if (fscanf(f, \"%d %d\", I, J) != 2) return MM_PREMATURE_EOF;\n    }\n    else\n        return MM_UNSUPPORTED_TYPE;\n\n    return 0;\n        \n}\n\n\n/************************************************************************\n    mm_read_mtx_crd()  fills M, N, nz, array of values, and return\n                        type code, e.g. 'MCRS'\n\n                        if matrix is complex, values[] is of size 2*nz,\n                            (nz pairs of real/imaginary values)\n************************************************************************/\n\nint mm_read_mtx_crd(char *fname, int *M, int *N, int *nz, int **I, int **J, \n        double **val, MM_typecode *matcode)\n{\n    int ret_code;\n    FILE *f;\n\n    if (strcmp(fname, \"stdin\") == 0) f=stdin;\n    else\n    if ((f = fopen(fname, \"r\")) == NULL)\n        return MM_COULD_NOT_READ_FILE;\n\n\n    if ((ret_code = mm_read_banner(f, matcode)) != 0)\n        return ret_code;\n\n    if (!(mm_is_valid(*matcode) && mm_is_sparse(*matcode) && \n            mm_is_matrix(*matcode)))\n        return MM_UNSUPPORTED_TYPE;\n\n    if ((ret_code = mm_read_mtx_crd_size(f, M, N, nz)) != 0)\n        return ret_code;\n\n\n    *I = (int *)  malloc(*nz * sizeof(int));\n    *J = (int *)  malloc(*nz * sizeof(int));\n    *val = NULL;\n\n    if (mm_is_complex(*matcode))\n    {\n        *val = (double *) malloc(*nz * 2 * sizeof(double));\n        ret_code = mm_read_mtx_crd_data(f, *M, *N, *nz, *I, *J, *val, \n                *matcode);\n        if (ret_code != 0) return ret_code;\n    }\n    else if (mm_is_real(*matcode))\n    {\n        *val = (double *) malloc(*nz * sizeof(double));\n        ret_code = mm_read_mtx_crd_data(f, *M, *N, *nz, *I, *J, *val, \n                *matcode);\n        if (ret_code != 0) return ret_code;\n    }\n\n    else if (mm_is_pattern(*matcode))\n    {\n        ret_code = mm_read_mtx_crd_data(f, *M, *N, *nz, *I, *J, *val, \n                *matcode);\n        if (ret_code != 0) return ret_code;\n    }\n\n    if (f != stdin) fclose(f);\n    return 0;\n}\n\nint mm_write_banner(FILE *f, MM_typecode matcode)\n{\n    char *str = mm_typecode_to_str(matcode);\n    int ret_code;\n\n    ret_code = fprintf(f, \"%s %s\\n\", MatrixMarketBanner, str);\n/*    free(str);  This is a bug from the official distribution - KE fixed */\n    if (ret_code < 0 )\n        return MM_COULD_NOT_WRITE_FILE;\n    else\n        return 0;\n}\n\nint mm_write_mtx_crd(char fname[], int M, int N, int nz, int I[], int J[],\n        double val[], MM_typecode matcode)\n{\n    FILE *f;\n    int i;\n\n    if (strcmp(fname, \"stdout\") == 0) \n        f = stdout;\n    else\n    if ((f = fopen(fname, \"w\")) == NULL)\n        return MM_COULD_NOT_WRITE_FILE;\n    \n    /* print banner followed by typecode */\n    fprintf(f, \"%s \", MatrixMarketBanner);\n    fprintf(f, \"%s\\n\", mm_typecode_to_str(matcode));\n\n    /* print matrix sizes and nonzeros */\n    fprintf(f, \"%d %d %d\\n\", M, N, nz);\n\n    /* print values */\n    if (mm_is_pattern(matcode))\n        for (i=0; i<nz; i++)\n            fprintf(f, \"%d %d\\n\", I[i], J[i]);\n    else\n    if (mm_is_real(matcode))\n        for (i=0; i<nz; i++)\n            fprintf(f, \"%d %d %20.16g\\n\", I[i], J[i], val[i]);\n    else\n    if (mm_is_complex(matcode))\n        for (i=0; i<nz; i++)\n            fprintf(f, \"%d %d %20.16g %20.16g\\n\", I[i], J[i], val[2*i], \n                        val[2*i+1]);\n    else\n    {\n        if (f != stdout) fclose(f);\n        return MM_UNSUPPORTED_TYPE;\n    }\n\n    if (f !=stdout) fclose(f);\n\n    return 0;\n}\n    \n\nchar  *mm_typecode_to_str(MM_typecode matcode)\n{\n    static char buffer[MM_MAX_LINE_LENGTH];\n    char *types[4];\n\n    /* check for MTX type */\n    if (mm_is_matrix(matcode)) \n        types[0] = MM_MTX_STR;\n    else\n        return NULL;\n\n    /* check for CRD or ARR matrix */\n    if (mm_is_sparse(matcode))\n        types[1] = MM_SPARSE_STR;\n    else\n    if (mm_is_dense(matcode))\n        types[1] = MM_DENSE_STR;\n    else\n        return NULL;\n\n    /* check for element data type */\n    if (mm_is_real(matcode))\n        types[2] = MM_REAL_STR;\n    else\n    if (mm_is_complex(matcode))\n        types[2] = MM_COMPLEX_STR;\n    else\n    if (mm_is_pattern(matcode))\n        types[2] = MM_PATTERN_STR;\n    else\n    if (mm_is_integer(matcode))\n        types[2] = MM_INT_STR;\n    else\n        return NULL;\n\n\n    /* check for symmetry type */\n    if (mm_is_general(matcode))\n        types[3] = MM_GENERAL_STR;\n    else\n    if (mm_is_symmetric(matcode))\n        types[3] = MM_SYMM_STR;\n    else \n    if (mm_is_hermitian(matcode))\n        types[3] = MM_HERM_STR;\n    else \n    if (mm_is_skew(matcode))\n        types[3] = MM_SKEW_STR;\n    else\n        return NULL;\n\n    sprintf(buffer,\"%s %s %s %s\", types[0], types[1], types[2], types[3]);\n    return & buffer[0];\n\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/mmio.h",
    "content": "/*\n*   Matrix Market I/O library for ANSI C\n*\n*   See http://math.nist.gov/MatrixMarket for details.\n*\n*\n*/\n\n#ifndef MM_IO_H\n#define MM_IO_H\n\n#define MM_MAX_LINE_LENGTH 1025\n#define MatrixMarketBanner \"%%MatrixMarket\"\n#define MM_MAX_TOKEN_LENGTH 64\n\ntypedef char MM_typecode[4];\n\nchar *mm_typecode_to_str(MM_typecode matcode);\n\nint mm_read_banner(FILE *f, MM_typecode *matcode);\nint mm_read_mtx_crd_size(FILE *f, int *M, int *N, int *nz);\nint mm_read_mtx_array_size(FILE *f, int *M, int *N);\n\nint mm_write_banner(FILE *f, MM_typecode matcode);\nint mm_write_mtx_crd_size(FILE *f, int M, int N, int nz);\nint mm_write_mtx_array_size(FILE *f, int M, int N);\n\n\n/********************* MM_typecode query fucntions ***************************/\n\n#define mm_is_matrix(typecode)  ((typecode)[0]=='M')\n\n#define mm_is_sparse(typecode)  ((typecode)[1]=='C')\n#define mm_is_coordinate(typecode)((typecode)[1]=='C')\n#define mm_is_dense(typecode) ((typecode)[1]=='A')\n#define mm_is_array(typecode) ((typecode)[1]=='A')\n\n#define mm_is_complex(typecode) ((typecode)[2]=='C')\n#define mm_is_real(typecode)    ((typecode)[2]=='R')\n#define mm_is_pattern(typecode) ((typecode)[2]=='P')\n#define mm_is_integer(typecode) ((typecode)[2]=='I')\n\n#define mm_is_symmetric(typecode)((typecode)[3]=='S')\n#define mm_is_general(typecode) ((typecode)[3]=='G')\n#define mm_is_skew(typecode)  ((typecode)[3]=='K')\n#define mm_is_hermitian(typecode)((typecode)[3]=='H')\n\nint mm_is_valid(MM_typecode matcode);   /* too complex for a macro */\n\n\n/********************* MM_typecode modify fucntions ***************************/\n\n#define mm_set_matrix(typecode) ((*typecode)[0]='M')\n#define mm_set_coordinate(typecode) ((*typecode)[1]='C')\n#define mm_set_array(typecode)  ((*typecode)[1]='A')\n#define mm_set_dense(typecode)  mm_set_array(typecode)\n#define mm_set_sparse(typecode) mm_set_coordinate(typecode)\n\n#define mm_set_complex(typecode)((*typecode)[2]='C')\n#define mm_set_real(typecode) ((*typecode)[2]='R')\n#define mm_set_pattern(typecode)((*typecode)[2]='P')\n#define mm_set_integer(typecode)((*typecode)[2]='I')\n\n\n#define mm_set_symmetric(typecode)((*typecode)[3]='S')\n#define mm_set_general(typecode)((*typecode)[3]='G')\n#define mm_set_skew(typecode) ((*typecode)[3]='K')\n#define mm_set_hermitian(typecode)((*typecode)[3]='H')\n\n#define mm_clear_typecode(typecode) ((*typecode)[0]=(*typecode)[1]= \\\n                  (*typecode)[2]=' ',(*typecode)[3]='G')\n\n#define mm_initialize_typecode(typecode) mm_clear_typecode(typecode)\n\n\n/********************* Matrix Market error codes ***************************/\n\n\n#define MM_COULD_NOT_READ_FILE  11\n#define MM_PREMATURE_EOF        12\n#define MM_NOT_MTX              13\n#define MM_NO_HEADER            14\n#define MM_UNSUPPORTED_TYPE     15\n#define MM_LINE_TOO_LONG        16\n#define MM_COULD_NOT_WRITE_FILE 17\n\n\n/******************** Matrix Market internal definitions ********************\n\n   MM_matrix_typecode: 4-character sequence\n\n            ojbect    sparse/     data        storage\n                  dense       type        scheme\n\n   string position:  [0]        [1]     [2]         [3]\n\n   Matrix typecode:  M(atrix)  C(oord)    R(eal)    G(eneral)\n                    A(array)  C(omplex)   H(ermitian)\n                      P(attern)   S(ymmetric)\n                        I(nteger) K(kew)\n\n ***********************************************************************/\n\n#define MM_MTX_STR    \"matrix\"\n#define MM_ARRAY_STR  \"array\"\n#define MM_DENSE_STR  \"array\"\n#define MM_COORDINATE_STR \"coordinate\"\n#define MM_SPARSE_STR \"coordinate\"\n#define MM_COMPLEX_STR  \"complex\"\n#define MM_REAL_STR   \"real\"\n#define MM_INT_STR    \"integer\"\n#define MM_GENERAL_STR  \"general\"\n#define MM_SYMM_STR   \"symmetric\"\n#define MM_HERM_STR   \"hermitian\"\n#define MM_SKEW_STR   \"skew-symmetric\"\n#define MM_PATTERN_STR  \"pattern\"\n\n\n/*  high level routines */\n\nint mm_write_mtx_crd(char fname[], int M, int N, int nz, int I[], int J[],\n     double val[], MM_typecode matcode);\nint mm_read_mtx_crd_data(FILE *f, int M, int N, int nz, int I[], int J[],\n    double val[], MM_typecode matcode);\nint mm_read_mtx_crd_entry(FILE *f, int *I, int *J, double *real, double *img,\n      MM_typecode matcode);\n\nint mm_read_unsymmetric_sparse(const char *fname, int *M_, int *N_, int *nz_,\n                double **val_, int **I_, int **J_);\n\n\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/myblas.c",
    "content": "\n#include <stdlib.h>\n#include <stdio.h>\n/*#include <memory.h>*/\n#include <string.h>\n#include <math.h>\n#include \"myblas.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* ************************************************************************ */\n/* Initialize BLAS interfacing routines                                     */\n/* ************************************************************************ */\nMYBOOL mustinitBLAS = TRUE;\n#if (defined WIN32) || (defined WIN64)\n  HINSTANCE hBLAS = NULL;\n#else\n  void     *hBLAS = NULL;\n#endif\n\n\n/* ************************************************************************ */\n/* Function pointers for external BLAS library (C base 0)                   */\n/* ************************************************************************ */\nBLAS_dscal_func  *BLAS_dscal;\nBLAS_dcopy_func  *BLAS_dcopy;\nBLAS_daxpy_func  *BLAS_daxpy;\nBLAS_dswap_func  *BLAS_dswap;\nBLAS_ddot_func   *BLAS_ddot;\nBLAS_idamax_func *BLAS_idamax;\nBLAS_idamin_func *BLAS_idamin;\nBLAS_dload_func  *BLAS_dload;\nBLAS_dnormi_func *BLAS_dnormi;\n\n\n/* ************************************************************************ */\n/* Define the BLAS interfacing routines                                     */\n/* ************************************************************************ */\n\nvoid init_BLAS(void)\n{\n  if(mustinitBLAS) {\n    load_BLAS(NULL);\n    mustinitBLAS = FALSE;\n  }\n}\n\nMYBOOL is_nativeBLAS(void)\n{\n#ifdef LoadableBlasLib\n  return( (MYBOOL) (hBLAS == NULL) );\n#else\n  return( TRUE );\n#endif\n}\n\nMYBOOL load_BLAS(char *libname)\n{\n  MYBOOL result = TRUE;\n\n#ifdef LoadableBlasLib\n  if(hBLAS != NULL) {\n    my_FreeLibrary(hBLAS);\n  }\n#endif\n\n  if(libname == NULL) {\n    if(!mustinitBLAS && is_nativeBLAS())\n      return( FALSE );\n    BLAS_dscal = my_dscal;\n    BLAS_dcopy = my_dcopy;\n    BLAS_daxpy = my_daxpy;\n    BLAS_dswap = my_dswap;\n    BLAS_ddot  = my_ddot;\n    BLAS_idamax = my_idamax;\n    BLAS_idamin = my_idamin;\n    BLAS_dload = my_dload;\n    BLAS_dnormi = my_dnormi;\n    if(mustinitBLAS)\n      mustinitBLAS = FALSE;\n  }\n  else {\n#ifdef LoadableBlasLib\n  #if (defined WIN32) || (defined WIN64)\n    char *blasname = libname;\n  #else\n   /* First standardize UNIX .SO library name format. */\n    char blasname[260];\n    if(!so_stdname(blasname, libname, 260))\n      return( FALSE );\n  #endif\n   /* Get a handle to the Windows DLL module. */\n    hBLAS = my_LoadLibrary(blasname);\n\n   /* If the handle is valid, try to get the function addresses. */\n    result = (MYBOOL) (hBLAS != NULL);\n    if(result) {\n      BLAS_dscal  = (BLAS_dscal_func *)  my_GetProcAddress(hBLAS, BLAS_prec \"scal\");\n      BLAS_dcopy  = (BLAS_dcopy_func *)  my_GetProcAddress(hBLAS, BLAS_prec \"copy\");\n      BLAS_daxpy  = (BLAS_daxpy_func *)  my_GetProcAddress(hBLAS, BLAS_prec \"axpy\");\n      BLAS_dswap  = (BLAS_dswap_func *)  my_GetProcAddress(hBLAS, BLAS_prec \"swap\");\n      BLAS_ddot   = (BLAS_ddot_func *)   my_GetProcAddress(hBLAS, BLAS_prec \"dot\");\n      BLAS_idamax = (BLAS_idamax_func *) my_GetProcAddress(hBLAS, \"i\" BLAS_prec \"amax\");\n      BLAS_idamin = (BLAS_idamin_func *) my_GetProcAddress(hBLAS, \"i\" BLAS_prec \"amin\");\n#if 0      \n      BLAS_dload  = (BLAS_dload_func *)  my_GetProcAddress(hBLAS, BLAS_prec \"load\");\n      BLAS_dnormi = (BLAS_dnormi_func *) my_GetProcAddress(hBLAS, BLAS_prec \"normi\");\n#endif      \n    }\n#endif\n    /* Do validation */\n    if(!result ||\n       ((BLAS_dscal  == NULL) ||\n        (BLAS_dcopy  == NULL) ||\n        (BLAS_daxpy  == NULL) ||\n        (BLAS_dswap  == NULL) ||\n        (BLAS_ddot   == NULL) ||\n        (BLAS_idamax == NULL) ||\n        (BLAS_idamin == NULL) ||\n        (BLAS_dload  == NULL) ||\n        (BLAS_dnormi == NULL))\n      ) {\n      load_BLAS(NULL);\n      result = FALSE;\n    }\n  }\n  return( result );\n}\nMYBOOL unload_BLAS(void)\n{\n  return( load_BLAS(NULL) );\n}\n\n\n/* ************************************************************************ */\n/* Now define the unoptimized local BLAS functions                          */\n/* ************************************************************************ */\nvoid daxpy( int n, REAL da, REAL *dx, int incx, REAL *dy, int incy)\n{\n  dx++;\n  dy++;\n  BLAS_daxpy( &n, &da, dx, &incx, dy, &incy);\n}\nvoid BLAS_CALLMODEL my_daxpy( int *_n, REAL *_da, REAL *dx, int *_incx, REAL *dy, int *_incy)\n{\n\n/* constant times a vector plus a vector.\n   uses unrolled loops for increments equal to one.\n   jack dongarra, linpack, 3/11/78.\n   modified 12/3/93, array[1] declarations changed to array[*] */\n\n  int      i, ix, iy; \n#ifndef DOFASTMATH\n  int      m, mp1;\n#endif\n  register REAL rda;\n  REAL     da = *_da;\n  int      n = *_n, incx = *_incx, incy = *_incy;\n\n  if (n <= 0) return;\n  if (da == 0.0) return;\n\n  dx--;\n  dy--;\n  ix = 1;\n  iy = 1;\n  if (incx < 0)\n     ix = (-n+1)*incx + 1;\n  if (incy < 0)\n     iy = (-n+1)*incy + 1;\n  rda = da;\n\n/* CPU intensive loop; option to do pointer arithmetic */\n#if defined DOFASTMATH\n  {\n    REAL *xptr, *yptr;\n    for (i = 1, xptr = dx + ix, yptr = dy + iy;\n         i <= n; i++, xptr += incx, yptr += incy)\n      (*yptr) += rda*(*xptr);\n  }\n#else\n\n  if (incx==1 && incy==1) goto x20;\n\n/* code for unequal increments or equal increments not equal to 1 */\n  for (i = 1; i<=n; i++) {\n     dy[iy]+= rda*dx[ix];\n     ix+= incx;\n     iy+= incy;\n  }\n  return;\n\n/*  code for both increments equal to 1 */\n\n/*  clean-up loop */\nx20:\n  m = n % 4;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++)\n     dy[i]+= rda*dx[i];\n  if(n < 4) return;\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+4) {\n    dy[i]+= rda*dx[i];\n    dy[i + 1]+= rda*dx[i + 1];\n    dy[i + 2]+= rda*dx[i + 2];\n    dy[i + 3]+= rda*dx[i + 3];\n  }\n#endif  \n}\n\n\n/* ************************************************************************ */\nvoid dcopy( int n, REAL *dx, int incx, REAL *dy, int incy)\n{\n  dx++;\n  dy++;\n  BLAS_dcopy( &n, dx, &incx, dy, &incy);\n}\n\nvoid BLAS_CALLMODEL my_dcopy (int *_n, REAL *dx, int *_incx, REAL *dy, int *_incy)\n{\n\n/* copies a vector, x, to a vector, y.\n   uses unrolled loops for increments equal to one.\n   jack dongarra, linpack, 3/11/78.\n   modified 12/3/93, array[1] declarations changed to array[*] */\n\n  int      i, ix, iy;\n#ifndef DOFASTMATH\n  int      m, mp1;\n#endif\n  int      n = *_n, incx = *_incx, incy = *_incy;\n\n  if(n<=0) \n    return;\n\n  dx--;\n  dy--;\n  ix = 1;\n  iy = 1;\n  if(incx<0)\n    ix = (-n+1)*incx + 1;\n  if(incy<0)\n    iy = (-n+1)*incy + 1;\n\n\n/* CPU intensive loop; option to do pointer arithmetic */\n#if defined DOFASTMATH\n  {\n    REAL *xptr, *yptr;\n    for (i = 1, xptr = dx + ix, yptr = dy + iy;\n         i <= n; i++, xptr += incx, yptr += incy)\n      (*yptr) = (*xptr);\n  }\n#else\n\n  if(incx==1 && incy==1) \n    goto x20;\n\n/* code for unequal increments or equal increments not equal to 1 */\n\n  for(i = 1; i<=n; i++) {\n    dy[iy] = dx[ix];\n    ix+= incx;\n    iy+= incy;\n  }\n  return;\n\n/* code for both increments equal to 1 */\n\n/* version with fast machine copy logic (requires memory.h or string.h) */\nx20:\n  m = n % 7;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++)\n     dy[i] = dx[i];\n  if (n < 7) return;\n\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+7) {\n     dy[i] = dx[i];\n     dy[i + 1] = dx[i + 1];\n     dy[i + 2] = dx[i + 2];\n     dy[i + 3] = dx[i + 3];\n     dy[i + 4] = dx[i + 4];\n     dy[i + 5] = dx[i + 5];\n     dy[i + 6] = dx[i + 6];\n  }\n#endif\n}\n\n\n/* ************************************************************************ */\n\nvoid dscal (int n, REAL da, REAL *dx, int incx)\n{\n  dx++;\n  BLAS_dscal (&n, &da, dx, &incx);\n}\n\nvoid BLAS_CALLMODEL my_dscal (int *_n, REAL *_da, REAL *dx, int *_incx)\n{\n\n/* Multiply a vector by a constant.\n\n     --Input--\n        N  number of elements in input vector(s)\n       DA  double precision scale factor\n       DX  double precision vector with N elements\n     INCX  storage spacing between elements of DX\n\n     --Output--\n       DX  double precision result (unchanged if N.LE.0)\n\n     Replace double precision DX by double precision DA*DX.\n     For I = 0 to N-1, replace DX(IX+I*INCX) with  DA * DX(IX+I*INCX),\n     where IX = 1 if INCX .GE. 0, else IX = 1+(1-N)*INCX. */\n\n  int      i;\n#ifndef DOFASTMATH\n  int      m, mp1, ix;\n#endif\n  register REAL rda;\n  REAL      da = *_da;\n  int      n = *_n, incx = *_incx;\n\n  if (n <= 0)\n    return;\n  rda = da;  \n  \n  dx--;\n\n/* Optionally do fast pointer arithmetic */\n#if defined DOFASTMATH\n  {\n    REAL *xptr;\n    for (i = 1, xptr = dx + 1; i <= n; i++, xptr += incx)\n      (*xptr) *= rda;\n  }\n#else\n\n  if (incx == 1)\n    goto x20;\n\n/* Code for increment not equal to 1 */\n  ix = 1;\n  if (incx < 0)\n    ix = (-n+1)*incx + 1;\n  for(i = 1; i <= n; i++, ix += incx)\n    dx[ix] *= rda;\n  return;\n\n/* Code for increment equal to 1. */\n/* Clean-up loop so remaining vector length is a multiple of 5. */\nx20:\n  m = n % 5;\n  if (m == 0) goto x40;\n  for( i = 1; i <= m; i++)\n    dx[i] *= rda;\n  if (n < 5)\n    return;\nx40:\n  mp1 = m + 1;\n  for(i = mp1; i <= n; i += 5) {\n    dx[i]   *= rda;\n    dx[i+1] *= rda;\n    dx[i+2] *= rda;\n    dx[i+3] *= rda;\n    dx[i+4] *= rda;\n  }\n#endif\n}\n\n\n/* ************************************************************************ */\n\nREAL ddot(int n, REAL *dx, int incx, REAL *dy, int incy)\n{\n  dx++;\n  dy++;\n  return( BLAS_ddot (&n, dx, &incx, dy, &incy) );\n}\n\nREAL BLAS_CALLMODEL my_ddot(int *_n, REAL *dx, int *_incx, REAL *dy, int *_incy)\n{\n\n/* forms the dot product of two vectors.\n   uses unrolled loops for increments equal to one.\n   jack dongarra, linpack, 3/11/78.\n   modified 12/3/93, array[1] declarations changed to array[*] */\n\n  register REAL dtemp;\n  int      i, ix, iy;\n#ifndef DOFASTMATH\n  int      m, mp1;\n#endif\n  int      n = *_n, incx = *_incx, incy = *_incy;\n\n  dtemp = 0.0;\n  if (n<=0)\n    return( (REAL) dtemp);\n\n  dx--;\n  dy--;\n  ix = 1;\n  iy = 1;\n  if (incx<0)\n     ix = (-n+1)*incx + 1;\n  if (incy<0)\n     iy = (-n+1)*incy + 1;\n\n/* CPU intensive loop; option to do pointer arithmetic */\n\n#if defined DOFASTMATH\n  {\n    REAL *xptr, *yptr;\n    for (i = 1, xptr = dx + ix, yptr = dy + iy;\n         i <= n; i++, xptr += incx, yptr += incy)\n      dtemp+= (*yptr)*(*xptr);\n  }\n#else\n\n  if (incx==1 && incy==1) goto x20;\n\n/* code for unequal increments or equal increments not equal to 1 */\n\n  for (i = 1; i<=n; i++) {\n     dtemp+= dx[ix]*dy[iy];\n     ix+= incx;\n     iy+= incy;\n  }\n  return(dtemp);\n\n/* code for both increments equal to 1 */\n\n/* clean-up loop */\n\nx20:\n  m = n % 5;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++)\n     dtemp+= dx[i]*dy[i];\n  if (n < 5) goto x60;\n\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+5)\n     dtemp+= dx[i]*dy[i] + dx[i + 1]*dy[i + 1] +\n             dx[i + 2]*dy[i + 2] + dx[i + 3]*dy[i + 3] + dx[i + 4]*dy[i + 4];\n\nx60:\n#endif\n  return(dtemp);\n}\n\n\n/* ************************************************************************ */\n\nvoid dswap( int n, REAL *dx, int incx, REAL *dy, int incy )\n{\n  dx++;\n  dy++;\n  BLAS_dswap( &n, dx, &incx, dy, &incy );\n}\n\nvoid BLAS_CALLMODEL my_dswap( int *_n, REAL *dx, int *_incx, REAL *dy, int *_incy )\n{\n  int   i, ix, iy;\n#ifndef DOFASTMATH\n  int   m, mp1, ns;\n  REAL  dtemp2, dtemp3;\n#endif\n  register REAL  dtemp1;\n  int   n = *_n, incx = *_incx, incy = *_incy;\n\n  if (n <= 0) return;\n\n  dx--;\n  dy--;\n  ix = 1;\n  iy = 1;\n  if (incx < 0)\n    ix = (-n+1)*incx + 1;\n  if (incy < 0)\n    iy = (-n+1)*incy + 1;\n\n/* CPU intensive loop; option to do pointer arithmetic */\n#if defined DOFASTMATH\n  {\n    REAL *xptr, *yptr;\n    for (i = 1, xptr = dx + ix, yptr = dy + iy;\n         i <= n; i++, xptr += incx, yptr += incy) {\n      dtemp1 = (*xptr);\n     (*xptr) = (*yptr);\n     (*yptr) = dtemp1;\n    }\n  }\n#else\n\n  if (incx == incy) {\n    if (incx <= 0) goto x5;\n    if (incx == 1) goto x20;\n    goto x60;\n  }\n\n/* code for unequal or nonpositive increments. */\nx5:\n  for (i = 1; i<=n; i++) {\n     dtemp1 = dx[ix];\n     dx[ix] = dy[iy];\n     dy[iy] = dtemp1;\n     ix+= incx;\n     iy+= incy;\n  }\n  return;\n\n/* code for both increments equal to 1.\n   clean-up loop so remaining vector length is a multiple of 3. */\nx20:\n  m = n % 3;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++) {\n     dtemp1 = dx[i];\n     dx[i] = dy[i];\n     dy[i] = dtemp1;\n  }\n  if (n < 3) return;\n\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+3) {\n     dtemp1 = dx[i];\n     dtemp2 = dx[i+1];\n     dtemp3 = dx[i+2];\n     dx[i] = dy[i];\n     dx[i+1] = dy[i+1];\n     dx[i+2] = dy[i+2];\n     dy[i] = dtemp1;\n     dy[i+1] = dtemp2;\n     dy[i+2] = dtemp3;\n  }\n  return;\n\n/* code for equal, positive, non-unit increments. */\nx60:\n  ns = n*incx;\n  for (i = 1; i<=ns; i=i+incx) {\n     dtemp1 = dx[i];\n     dx[i] = dy[i];\n     dy[i] = dtemp1;\n  }\n#endif\n\n}\n\n\n/* ************************************************************************ */\n\nvoid dload(int n, REAL da, REAL *dx, int incx)\n{\n  dx++;\n  BLAS_dload (&n, &da, dx, &incx);\n}\n\nvoid BLAS_CALLMODEL my_dload (int *_n, REAL *_da, REAL *dx, int *_incx)\n{\n/* copies a scalar, a, to a vector, x.\n   uses unrolled loops when incx equals one.\n\n   To change the precision of this program, run the change\n   program on dload.f\n   Alternatively, to make a single precision version append a\n   comment character to the start of all lines between sequential\n      precision > double\n   and\n      end precision > double\n   comments and delete the comment character at the start of all\n   lines between sequential\n      precision > single\n   and\n      end precision > single\n   comments.  To make a double precision version interchange\n    the append and delete operations in these instructions. */\n\n  int    i, ix, m, mp1;\n  REAL   da = *_da;\n  int    n = *_n, incx = *_incx;\n\n  if (n<=0) return;\n  dx--;\n  if (incx==1) goto x20;\n\n/* code for incx not equal to 1 */\n\n  ix = 1;\n  if (incx<0)\n     ix = (-n+1)*incx + 1;\n  for (i = 1; i<=n; i++) {\n     dx[ix] = da;\n     ix+= incx;\n  }\n  return;\n\n/* code for incx equal to 1 and clean-up loop */\n\nx20:\n  m = n % 7;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++)\n     dx[i] = da;\n  if (n < 7) return;\n\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+7) {\n     dx[i] = da;\n     dx[i + 1] = da;\n     dx[i + 2] = da;\n     dx[i + 3] = da;\n     dx[i + 4] = da;\n     dx[i + 5] = da;\n     dx[i + 6] = da;\n  }\n}\n\n/* ************************************************************************ */\nint idamax( int n, REAL *x, int is )\n{\n  x++;\n  return ( BLAS_idamax( &n, x, &is ) );\n}\n\nint idamin( int n, REAL *x, int is )\n{\n  x++;\n  return ( BLAS_idamin( &n, x, &is ) );\n}\n\nint BLAS_CALLMODEL my_idamax( int *_n, REAL *x, int *_is )\n{\n  register REAL xmax, xtest;\n  int    i, imax = 0;\n#if !defined DOFASTMATH\n  int    ii;\n#endif\n  int    n = *_n, is = *_is;\n\n  if((n < 1) || (is <= 0))\n    return(imax);\n  imax = 1;\n  if(n == 1)\n    return(imax);\n\n#if defined DOFASTMATH\n  xmax = fabs(*x);\n  for (i = 2, x += is; i <= n; i++, x += is) {\n    xtest = fabs(*x);\n    if(xtest > xmax) {\n      xmax = xtest;\n      imax = i;\n    }\n  }\n#else\n  x--;\n  ii = 1;\n  xmax = fabs(x[ii]);\n  for(i = 2, ii+ = is; i <= n; i++, ii+ = is) {\n    xtest = fabs(x[ii]);\n    if(xtest > xmax) {\n      xmax = xtest;\n      imax = i;\n    }\n  }\n#endif  \n  return(imax);\n}\n\nint BLAS_CALLMODEL my_idamin( int *_n, REAL *x, int *_is )\n{\n  register REAL xmin, xtest;\n  int    i, imin = 0;\n#if !defined DOFASTMATH\n  int    ii;\n#endif\n  int    n = *_n, is = *_is;\n\n  if((n < 1) || (is <= 0))\n    return(imin);\n  imin = 1;\n  if(n == 1)\n    return(imin);\n\n#if defined DOFASTMATH\n  xmin = fabs(*x);\n  for (i = 2, x += is; i <= n; i++, x += is) {\n    xtest = fabs(*x);\n    if(xtest < xmin) {\n      xmin = xtest;\n      imin = i;\n    }\n  }\n#else\n  x--;\n  ii = 1;\n  xmin = fabs(x[ii]);\n  for(i = 2, ii+ = is; i <= n; i++, ii+ = is) {\n    xtest = fabs(x[ii]);\n    if(xtest < xmin) {\n      xmin = xtest;\n      imin = i;\n    }\n  }\n#endif  \n  return(imin);\n}\n\n/* ************************************************************************ */\nREAL dnormi( int n, REAL *x )\n{\n  x++;\n  return( BLAS_dnormi( &n, x ) );\n}\n\nREAL BLAS_CALLMODEL my_dnormi( int *_n, REAL *x )\n{\n/* ===============================================================\n   dnormi  returns the infinity-norm of the vector x.\n   =============================================================== */\n   int      j;\n   register REAL hold, absval;\n   int      n = *_n;\n\n   x--;\n   hold = 0.0;\n/*   for(j = 1; j <= n; j++) */\n   for(j = n; j > 0; j--) {\n     absval = fabs(x[j]);\n     hold = MAX( hold, absval );\n   }\n\n   return( hold );\n}\n\n\n/* ************************************************************************ */\n/* Subvector and submatrix access routines (Fortran compatibility)          */\n/* ************************************************************************ */\n\n#ifndef UseMacroVector\nint  subvec( int item)\n{\n  return( item-1 );\n}\n#endif\n\nint submat( int nrowb, int row, int col)\n{\n  return( nrowb*(col-1) + subvec(row) );\n}\n\nint posmat( int nrowb, int row, int col)\n{\n  return( submat(nrowb, row, col)+BLAS_BASE );\n}\n\n/* ************************************************************************ */\n/* Randomization functions                                                  */\n/* ************************************************************************ */\n\nvoid randomseed(int seeds[])\n/* Simply create some default seed values */\n{\n  seeds[1] = 123456;\n  seeds[2] = 234567;\n  seeds[3] = 345678;\n}\n\nvoid randomdens( int n, REAL *x, REAL r1, REAL r2, REAL densty, int *seeds )\n{\n/* ------------------------------------------------------------------\n   random  generates a vector x[*] of random numbers\n   in the range (r1, r2) with (approximate) specified density.\n   seeds[*] must be initialized before the first call.\n   ------------------------------------------------------------------ */\n\n  int   i;\n  REAL  *y;\n\n  y = (REAL *) malloc(sizeof(*y) * (n+1));\n  ddrand( n, x, 1, seeds );\n  ddrand( n, y, 1, seeds );\n\n  for (i = 1; i<=n; i++) {\n     if (y[i] < densty)\n        x[i] = r1  +  (r2 - r1) * x[i];\n     else\n        x[i] = 0.0;\n  }\n  free(y);\n}\n\n\n/* ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */\n\nvoid ddrand( int n, REAL *x, int incx, int *seeds )\n{\n\n/* ------------------------------------------------------------------\n   ddrand fills a vector x with uniformly distributed random numbers\n   in the interval (0, 1) using a method due to  Wichman and Hill.\n\n   seeds[1..3] should be set to integer values\n   between 1 and 30000 before the first entry.\n\n   Integer arithmetic up to 30323 is required.\n\n   Blatantly copied from Wichman and Hill 19-January-1987.\n   14-Feb-94. Original version.\n   30 Jun 1999. seeds stored in an array.\n   30 Jun 1999. This version of ddrand.\n   ------------------------------------------------------------------ */\n\n  int    ix, xix;\n\n  if (n < 1) return;\n\n  for (ix = 1; ix<=1+(n-1)*incx; ix=ix+incx) {\n     seeds[1]     = 171*(seeds[1] % 177) -  2*(seeds[1]/177);\n     seeds[2]     = 172*(seeds[2] % 176) - 35*(seeds[2]/176);\n     seeds[3]     = 170*(seeds[3] % 178) - 63*(seeds[3]/178);\n\n     if (seeds[1] < 0) seeds[1] = seeds[1] + 30269;\n     if (seeds[2] < 0) seeds[2] = seeds[2] + 30307;\n     if (seeds[3] < 0) seeds[3] = seeds[3] + 30323;\n\n\t x[ix]  = ((REAL) seeds[1])/30269.0 +\n              ((REAL) seeds[2])/30307.0 +\n              ((REAL) seeds[3])/30323.0;\n     xix    = (int) x[ix];\n\t x[ix]  = fabs(x[ix] - xix);\n   }\n\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/myblas.h",
    "content": "#ifndef HEADER_myblas\n#define HEADER_myblas\n\n/* ************************************************************************ */\n/* BLAS function interface with local and external loadable versions        */\n/* Author:  Kjell Eikland                                                   */\n/* Version: Initial version spring 2004                                     */\n/* Licence: LGPL                                                            */\n/* ************************************************************************ */\n/* Changes: 19 September 2004   Moved function pointer variable             */\n/*                              declarations from myblas.h to myblas.c      */\n/*                              to avoid linker problems with the Mac.      */\n/*          20 April 2005       Modified all double types to REAL to self-  */\n/*                              adjust to global settings.  Note that BLAS  */\n/*                              as of now does not have double double.      */\n/*          15 December 2005    Added idamin()                              */\n/* ************************************************************************ */\n\n#define BLAS_BASE         1\n#define UseMacroVector\n#define LoadableBlasLib\n\n\n/* ************************************************************************ */\n/* Include necessary libraries                                              */\n/* ************************************************************************ */\n#include \"commonlib.h\"\n#ifdef LoadableBlasLib\n  #if (defined WIN32) || (defined WIN64)\n    #include <windows.h>\n  #else\n    #include <dlfcn.h>\n  #endif\n#endif\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n\n/* ************************************************************************ */\n/* BLAS functions                                                           */\n/* ************************************************************************ */\n\n#ifndef BLAS_CALLMODEL\n  #if (defined WIN32) || (defined WIN64)\n    #define BLAS_CALLMODEL _cdecl\n  #else\n    #define BLAS_CALLMODEL\n  #endif\n#endif\n\ntypedef void   (BLAS_CALLMODEL BLAS_dscal_func) (int *n, REAL *da, REAL *dx, int *incx);\ntypedef void   (BLAS_CALLMODEL BLAS_dcopy_func) (int *n, REAL *dx, int *incx,  REAL *dy, int *incy);\ntypedef void   (BLAS_CALLMODEL BLAS_daxpy_func) (int *n, REAL *da, REAL *dx, int *incx,  REAL *dy, int *incy);\ntypedef void   (BLAS_CALLMODEL BLAS_dswap_func) (int *n, REAL *dx, int *incx,  REAL *dy, int *incy);\ntypedef double (BLAS_CALLMODEL BLAS_ddot_func)  (int *n, REAL *dx, int *incx,  REAL *dy, int *incy);\ntypedef int    (BLAS_CALLMODEL BLAS_idamax_func)(int *n, REAL *x,  int *is);\ntypedef int    (BLAS_CALLMODEL BLAS_idamin_func)(int *n, REAL *x,  int *is);\ntypedef void   (BLAS_CALLMODEL BLAS_dload_func) (int *n, REAL *da, REAL *dx, int *incx);\ntypedef double (BLAS_CALLMODEL BLAS_dnormi_func)(int *n, REAL *x);\n\n#ifndef __WINAPI\n  #if (defined WIN32) || (defined WIN64)\n    #define __WINAPI WINAPI\n  #else\n    #define __WINAPI\n  #endif\n#endif\n\nvoid init_BLAS(void);\nMYBOOL is_nativeBLAS(void);\nMYBOOL load_BLAS(char *libname);\nMYBOOL unload_BLAS(void);\n\n/* ************************************************************************ */\n/* User-callable BLAS definitions (C base 1)                                */\n/* ************************************************************************ */\nvoid dscal ( int n, REAL da,  REAL *dx, int incx );\nvoid dcopy ( int n, REAL *dx, int incx, REAL *dy, int incy );\nvoid daxpy ( int n, REAL da,  REAL *dx, int incx,   REAL *dy, int incy );\nvoid dswap ( int n, REAL *dx, int incx, REAL *dy, int incy );\nREAL ddot  ( int n, REAL *dx, int incx, REAL *dy, int incy );\nint  idamax( int n, REAL *x,  int is );\nint  idamin( int n, REAL *x,  int is );\nvoid dload ( int n, REAL da,  REAL *dx, int incx );\nREAL dnormi( int n, REAL *x );\n\n\n/* ************************************************************************ */\n/* Locally implemented BLAS functions (C base 0)                            */\n/* ************************************************************************ */\nvoid BLAS_CALLMODEL my_dscal ( int *n, REAL *da, REAL *dx,  int *incx );\nvoid BLAS_CALLMODEL my_dcopy ( int *n, REAL *dx, int *incx, REAL *dy, int *incy );\nvoid BLAS_CALLMODEL my_daxpy ( int *n, REAL *da, REAL *dx,  int *incx,  REAL *dy, int *incy );\nvoid BLAS_CALLMODEL my_dswap ( int *n, REAL *dx, int *incx, REAL *dy, int *incy );\nREAL BLAS_CALLMODEL my_ddot  ( int *n, REAL *dx, int *incx,  REAL *dy, int *incy );\nint  BLAS_CALLMODEL my_idamax( int *n, REAL *x,  int *is );\nint  BLAS_CALLMODEL my_idamin( int *n, REAL *x,  int *is );\nvoid BLAS_CALLMODEL my_dload ( int *n, REAL *da, REAL *dx, int *incx );\nREAL BLAS_CALLMODEL my_dnormi( int *n, REAL *x );\n\n\n/* ************************************************************************ */\n/* Subvector and submatrix access routines (Fortran compatibility)          */\n/* ************************************************************************ */\n#ifdef UseMacroVector\n  #define subvec(item) (item - 1)\n#else\n  int subvec( int item );\n#endif\n\nint submat( int nrowb, int row, int col );\nint posmat( int nrowb, int row, int col );\n\n\n/* ************************************************************************ */\n/* Randomization functions                                                  */\n/* ************************************************************************ */\nvoid randomseed(int *seeds);\nvoid randomdens( int n, REAL *x, REAL r1, REAL r2, REAL densty, int *seeds);\nvoid ddrand( int n, REAL *x, int incx, int *seeds );\n\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/sherman5.mtx",
    "content": "%%MatrixMarket matrix coordinate real general\r\n3312 3312 20793\r\n1 1  1.0000000000000e+00\r\n2 2  1.0000000000000e+00\r\n3 3  1.0000000000000e+00\r\n4 4  1.0000000000000e+00\r\n5 5  1.0000000000000e+00\r\n6 6  1.0000000000000e+00\r\n7 7  1.0000000000000e+00\r\n8 8  1.0000000000000e+00\r\n9 9  1.0000000000000e+00\r\n10 10  1.0000000000000e+00\r\n11 11  1.0000000000000e+00\r\n12 12  1.0000000000000e+00\r\n13 13  1.0000000000000e+00\r\n14 14  1.0000000000000e+00\r\n15 15  1.0000000000000e+00\r\n16 16  1.0000000000000e+00\r\n17 17  1.0000000000000e+00\r\n18 18  1.0000000000000e+00\r\n19 19  1.0000000000000e+00\r\n20 20  1.0000000000000e+00\r\n21 21  1.0000000000000e+00\r\n22 22  1.0000000000000e+00\r\n23 23  1.0000000000000e+00\r\n24 24  1.0000000000000e+00\r\n25 25  1.0000000000000e+00\r\n26 26  1.0000000000000e+00\r\n27 27  1.0000000000000e+00\r\n28 28  1.0000000000000e+00\r\n29 29  1.0000000000000e+00\r\n30 30  1.0000000000000e+00\r\n31 31  1.0000000000000e+00\r\n32 32  1.0000000000000e+00\r\n33 33  1.0000000000000e+00\r\n34 34  1.0000000000000e+00\r\n35 35  1.0000000000000e+00\r\n36 36  1.0000000000000e+00\r\n37 37  1.0000000000000e+00\r\n38 38  1.0000000000000e+00\r\n39 39  1.0000000000000e+00\r\n40 40  1.0000000000000e+00\r\n41 41  1.0000000000000e+00\r\n42 42  1.0000000000000e+00\r\n43 43  1.0000000000000e+00\r\n44 44  1.0000000000000e+00\r\n45 45  1.0000000000000e+00\r\n46 46  1.0000000000000e+00\r\n47 47  1.0000000000000e+00\r\n48 48  1.0000000000000e+00\r\n49 49  1.0000000000000e+00\r\n50 50  1.0000000000000e+00\r\n51 51  1.0000000000000e+00\r\n52 52  1.0000000000000e+00\r\n53 53  1.0000000000000e+00\r\n54 54  1.0000000000000e+00\r\n55 55  1.0000000000000e+00\r\n56 56  1.0000000000000e+00\r\n57 57  1.0000000000000e+00\r\n58 58  1.0000000000000e+00\r\n59 59  1.0000000000000e+00\r\n60 60  1.0000000000000e+00\r\n61 61  1.0000000000000e+00\r\n62 62  1.0000000000000e+00\r\n63 63  1.0000000000000e+00\r\n64 64  1.0000000000000e+00\r\n65 65  1.0000000000000e+00\r\n66 66  1.0000000000000e+00\r\n67 67  1.0000000000000e+00\r\n68 68  1.0000000000000e+00\r\n69 69  1.0000000000000e+00\r\n70 70  1.0000000000000e+00\r\n71 71  1.0000000000000e+00\r\n72 72  1.0000000000000e+00\r\n73 73  1.0000000000000e+00\r\n74 74  1.0000000000000e+00\r\n75 75  1.0000000000000e+00\r\n76 76  1.0000000000000e+00\r\n77 77  1.0000000000000e+00\r\n78 78  1.0000000000000e+00\r\n79 79  1.0000000000000e+00\r\n80 80  1.0000000000000e+00\r\n81 81  1.0000000000000e+00\r\n82 82  1.0000000000000e+00\r\n83 83  1.0000000000000e+00\r\n84 84  1.0000000000000e+00\r\n85 85  1.0000000000000e+00\r\n86 86  1.0000000000000e+00\r\n87 87  1.0000000000000e+00\r\n88 88  1.0000000000000e+00\r\n89 89  1.0000000000000e+00\r\n90 90  1.0000000000000e+00\r\n91 91  1.0000000000000e+00\r\n92 92  1.0000000000000e+00\r\n93 93  1.0000000000000e+00\r\n94 94  1.0000000000000e+00\r\n95 95  1.0000000000000e+00\r\n96 96  1.0000000000000e+00\r\n97 97  1.0000000000000e+00\r\n98 98  1.0000000000000e+00\r\n99 99  1.0000000000000e+00\r\n100 100  1.0000000000000e+00\r\n101 101  1.0000000000000e+00\r\n102 102  1.0000000000000e+00\r\n103 103  1.0000000000000e+00\r\n104 104  1.0000000000000e+00\r\n105 105  1.0000000000000e+00\r\n106 106  1.0000000000000e+00\r\n107 107  1.0000000000000e+00\r\n108 108  1.0000000000000e+00\r\n109 109  1.0000000000000e+00\r\n110 110  1.0000000000000e+00\r\n111 111  1.0000000000000e+00\r\n112 112  5.8231501000000e+02\r\n114 112  5.2492442000000e-01\r\n115 112 -2.0203364000000e+00\r\n117 112 -2.7550543000000e-01\r\n160 112 -5.6252230000000e+00\r\n162 112 -1.6807221000000e-01\r\n112 113 -3.5663180000000e+02\r\n113 113 -8.8662401000000e+01\r\n114 113  4.3323260000000e+00\r\n117 113 -1.9094766000000e+00\r\n160 113  2.6312807000000e+01\r\n162 113 -2.4130042000000e+00\r\n112 114 -6.0285039000000e+02\r\n113 114  7.5193603000000e+01\r\n114 114  7.3233615000000e+00\r\n117 114 -3.2277769000000e+00\r\n160 114  4.4479169000000e+01\r\n161 114 -5.0183851000000e+00\r\n162 114 -4.0789423000000e+00\r\n112 115 -1.6998248000000e+00\r\n114 115 -2.7550543000000e-01\r\n115 115  5.8372624000000e+02\r\n117 115  6.3124101000000e-01\r\n163 115 -7.3516016000000e+00\r\n165 115 -2.7406444000000e-01\r\n112 116  1.4215287000000e+00\r\n114 116 -1.9094766000000e+00\r\n115 116 -3.5731519000000e+02\r\n116 116 -8.2875303000000e+01\r\n117 116  3.8183672000000e+00\r\n163 116  2.5567757000000e+01\r\n165 116 -1.8996892000000e+00\r\n112 117  2.4029503000000e+00\r\n113 117 -2.3924408000000e-01\r\n114 117 -3.2277769000000e+00\r\n115 117 -6.0400514000000e+02\r\n116 117  7.0151506000000e+01\r\n117 117  6.4545628000000e+00\r\n163 117  4.3219704000000e+01\r\n164 117 -4.3030678000000e+00\r\n165 117 -3.2112320000000e+00\r\n118 118  1.0000000000000e+00\r\n119 119  1.0000000000000e+00\r\n120 120  1.0000000000000e+00\r\n121 121  1.0000000000000e+00\r\n122 122  1.0000000000000e+00\r\n123 123  1.0000000000000e+00\r\n124 124  5.3832442000000e+02\r\n126 124  5.3782022000000e-01\r\n127 124 -6.3733512000000e-01\r\n129 124 -1.5517509000000e-01\r\n172 124 -8.9792671000000e+00\r\n174 124 -3.0109811000000e-01\r\n124 125 -3.3089489000000e+02\r\n125 125 -7.4442006000000e+01\r\n126 125  3.7903600000000e+00\r\n129 125 -2.1251184000000e+00\r\n172 125  2.6986678000000e+01\r\n174 125 -1.6569781000000e+00\r\n124 126 -5.5934473000000e+02\r\n125 126  6.3483385000000e+01\r\n126 126  6.4072219000000e+00\r\n129 126 -3.5922975000000e+00\r\n172 126  4.5618281000000e+01\r\n173 126 -4.5334382000000e+00\r\n174 126 -2.8009558000000e+00\r\n124 127 -1.3980131000000e+00\r\n126 127 -1.5517509000000e-01\r\n127 127  5.0198176000000e+02\r\n129 127  4.7689354000000e-01\r\n130 127 -6.3224679000000e-01\r\n132 127 -8.6217037000000e-02\r\n175 127 -5.7287189000000e+00\r\n177 127 -1.5448592000000e-01\r\n124 128  1.3851396000000e+00\r\n126 128 -2.1251184000000e+00\r\n127 128 -3.1288440000000e+02\r\n128 128 -7.5938657000000e+01\r\n129 128  6.6177709000000e+00\r\n132 128 -2.3682623000000e+00\r\n175 128  2.7415937000000e+01\r\n177 128 -2.1159596000000e+00\r\n124 129  2.3414383000000e+00\r\n125 129 -2.6047842000000e-01\r\n126 129 -3.5922975000000e+00\r\n127 129 -5.2889940000000e+02\r\n128 129  6.5540651000000e+01\r\n129 129  1.1186675000000e+01\r\n132 129 -4.0033106000000e+00\r\n175 129  4.6343867000000e+01\r\n176 129 -5.1556247000000e+00\r\n177 129 -3.5768156000000e+00\r\n127 130 -1.4107303000000e+00\r\n129 130 -8.6217037000000e-02\r\n130 130  4.6586228000000e+02\r\n132 130  2.9383283000000e-01\r\n133 130 -3.8013097000000e-01\r\n135 130 -4.2128177000000e-02\r\n178 130 -4.3311389000000e+00\r\n180 130 -8.4835819000000e-02\r\n127 131  4.3689315000000e+00\r\n129 131 -2.3682623000000e+00\r\n130 131 -2.9407852000000e+02\r\n131 131 -7.4441522000000e+01\r\n132 131  7.2325006000000e+00\r\n135 131 -2.5253587000000e+00\r\n178 131  2.5448551000000e+01\r\n180 131 -2.3306147000000e+00\r\n127 132  7.3852418000000e+00\r\n128 132 -9.3201429000000e-01\r\n129 132 -4.0033106000000e+00\r\n130 132 -4.9711033000000e+02\r\n131 132  6.5294128000000e+01\r\n132 132  1.2225815000000e+01\r\n135 132 -4.2688625000000e+00\r\n178 132  4.3018230000000e+01\r\n179 132 -5.4288819000000e+00\r\n180 132 -3.9396711000000e+00\r\n130 133 -1.4010699000000e+00\r\n132 133 -4.2128177000000e-02\r\n133 133  4.2014767000000e+02\r\n135 133  2.8664674000000e-01\r\n136 133 -4.5043645000000e-01\r\n138 133 -2.8088374000000e-02\r\n181 133 -3.0132612000000e+00\r\n183 133 -4.1440337000000e-02\r\n1237 133 -1.5185682000000e+00\r\n1239 133 -9.4695072000000e-02\r\n130 134  8.3901469000000e+00\r\n132 134 -2.5253587000000e+00\r\n133 134 -2.7386615000000e+02\r\n134 134 -7.0163194000000e+01\r\n135 134  8.4045939000000e+00\r\n138 134 -2.4770889000000e+00\r\n181 134  2.7643276000000e+01\r\n183 134 -2.4844433000000e+00\r\n1239 134 -9.0991269000000e-01\r\n130 135  1.4182692000000e+01\r\n131 135 -1.8692398000000e+00\r\n132 135 -4.2688625000000e+00\r\n133 135 -4.6294292000000e+02\r\n134 135  6.3568717000000e+01\r\n135 135  1.4207117000000e+01\r\n138 135 -4.1872710000000e+00\r\n181 135  4.6728152000000e+01\r\n182 135 -6.1586425000000e+00\r\n183 135 -4.1996989000000e+00\r\n1239 135 -1.5381153000000e+00\r\n133 136 -1.1205588000000e+00\r\n135 136 -2.8088374000000e-02\r\n136 136  3.9605626000000e+02\r\n138 136  2.1289817000000e-01\r\n139 136 -4.3256755000000e-01\r\n141 136 -1.9131946000000e-02\r\n184 136 -2.4236070000000e+00\r\n186 136 -2.7943549000000e-02\r\n1240 136 -1.3020729000000e+00\r\n1242 136 -5.7589129000000e-02\r\n133 137  7.3902619000000e+00\r\n135 137 -2.4770889000000e+00\r\n136 137 -2.5965366000000e+02\r\n137 137 -6.7508510000000e+01\r\n138 137  8.6129243000000e+00\r\n141 137 -2.4530265000000e+00\r\n184 137  2.7643725000000e+01\r\n186 137 -2.4646498000000e+00\r\n1242 137 -1.2106635000000e+00\r\n133 138  1.2492498000000e+01\r\n134 138 -1.6776607000000e+00\r\n135 138 -4.1872710000000e+00\r\n136 138 -4.3891854000000e+02\r\n137 138  6.1392103000000e+01\r\n138 138  1.4559283000000e+01\r\n141 138 -4.1465920000000e+00\r\n184 138  4.6728953000000e+01\r\n185 138 -6.2753919000000e+00\r\n186 138 -4.1662440000000e+00\r\n1242 138 -2.0465056000000e+00\r\n136 139 -8.1089445000000e-01\r\n138 139 -1.9131946000000e-02\r\n139 139  3.7180667000000e+02\r\n141 139  1.6790239000000e-01\r\n142 139 -2.7576248000000e-01\r\n144 139 -1.2196645000000e-02\r\n187 139 -2.0755418000000e+00\r\n189 139 -1.8758993000000e-02\r\n1243 139 -8.5465113000000e-01\r\n1245 139 -3.7800198000000e-02\r\n136 140  5.6903327000000e+00\r\n138 140 -2.4530265000000e+00\r\n139 140 -2.4225577000000e+02\r\n140 140 -6.4514006000000e+01\r\n141 140  8.7655485000000e+00\r\n144 140 -2.4257603000000e+00\r\n187 140  2.5159407000000e+01\r\n189 140 -2.4055380000000e+00\r\n1245 140 -1.4740605000000e+00\r\n136 141  9.6189292000000e+00\r\n137 141 -1.3569623000000e+00\r\n138 141 -4.1465920000000e+00\r\n139 141 -4.0950877000000e+02\r\n140 141  5.8423373000000e+01\r\n141 141  1.4817273000000e+01\r\n144 141 -4.1005051000000e+00\r\n187 141  4.2529422000000e+01\r\n188 141 -5.9997136000000e+00\r\n189 141 -4.0663174000000e+00\r\n1245 141 -2.4917501000000e+00\r\n139 142 -5.8379831000000e-01\r\n141 142 -1.2196645000000e-02\r\n142 142  3.4769930000000e+02\r\n144 142  1.2785204000000e-01\r\n190 142 -1.5025582000000e+00\r\n192 142 -1.1948511000000e-02\r\n1246 142 -8.1286985000000e-01\r\n1248 142 -2.3819524000000e-02\r\n139 143  3.4445751000000e+00\r\n141 143 -2.4257603000000e+00\r\n142 143 -2.2507085000000e+02\r\n143 143 -6.1460330000000e+01\r\n144 143  6.5646306000000e+00\r\n190 143  2.3436855000000e+01\r\n192 143 -2.3767260000000e+00\r\n1248 143 -1.7553192000000e+00\r\n139 144  5.8227096000000e+00\r\n140 144 -8.3153640000000e-01\r\n141 144 -4.1005051000000e+00\r\n142 144 -3.8045976000000e+02\r\n143 144  5.5129317000000e+01\r\n144 144  1.1096852000000e+01\r\n190 144  3.9617660000000e+01\r\n191 144 -5.6577656000000e+00\r\n192 144 -4.0176177000000e+00\r\n1248 144 -2.9671916000000e+00\r\n145 145  1.0000000000000e+00\r\n146 146  1.0000000000000e+00\r\n147 147  1.0000000000000e+00\r\n148 148  1.0000000000000e+00\r\n149 149  1.0000000000000e+00\r\n150 150  1.0000000000000e+00\r\n151 151  1.0000000000000e+00\r\n152 152  1.0000000000000e+00\r\n153 153  1.0000000000000e+00\r\n154 154  1.0000000000000e+00\r\n155 155  1.0000000000000e+00\r\n156 156  1.0000000000000e+00\r\n157 157  1.0000000000000e+00\r\n158 158  1.0000000000000e+00\r\n159 159  1.0000000000000e+00\r\n112 160 -9.5033409000000e+00\r\n114 160 -1.6807221000000e-01\r\n160 160  5.8715640000000e+02\r\n162 160  2.0768709000000e-01\r\n163 160 -6.6263142000000e-01\r\n165 160 -1.1226122000000e-02\r\n208 160 -1.4917882000000e+00\r\n210 160 -1.1178095000000e-02\r\n1264 160 -8.8143285000000e-01\r\n1266 160 -1.5588662000000e-02\r\n114 161 -2.4130042000000e+00\r\n160 161 -3.6403964000000e+02\r\n161 161 -1.0420357000000e+02\r\n162 161  1.1702675000000e+01\r\n163 161  1.0112293000000e+00\r\n165 161 -4.1288435000000e+00\r\n208 161  3.2774276000000e+01\r\n210 161 -4.1117354000000e+00\r\n1266 161 -1.0375061000000e+00\r\n114 162 -4.0789423000000e+00\r\n160 162 -6.1537261000000e+02\r\n161 162  9.0595331000000e+01\r\n162 162  1.9782202000000e+01\r\n163 162  1.7093819000000e+00\r\n164 162 -2.4808822000000e-01\r\n165 162 -6.9793971000000e+00\r\n208 162  5.5401636000000e+01\r\n209 162 -8.0406217000000e+00\r\n210 162 -6.9504776000000e+00\r\n1266 162 -1.7538002000000e+00\r\n115 163 -9.3527780000000e+00\r\n117 163 -2.7406444000000e-01\r\n160 163 -3.8310490000000e-01\r\n162 163 -1.1226122000000e-02\r\n163 163  5.8877517000000e+02\r\n165 163  3.7583663000000e-01\r\n166 163 -9.7621276000000e-01\r\n168 163 -2.8605960000000e-02\r\n211 163 -2.1579866000000e+00\r\n213 163 -2.2766993000000e-02\r\n1267 163 -1.2770249000000e+00\r\n1269 163 -3.7420658000000e-02\r\n117 164 -1.8996892000000e+00\r\n162 164 -4.1288435000000e+00\r\n163 164 -3.6275210000000e+02\r\n164 164 -1.0186561000000e+02\r\n165 164  1.4544988000000e+01\r\n166 164  7.2034968000000e-01\r\n168 164 -3.8446595000000e+00\r\n211 164  3.1763844000000e+01\r\n213 164 -3.8235852000000e+00\r\n1269 164 -8.3688804000000e-01\r\n117 165 -3.2112320000000e+00\r\n162 165 -6.9793971000000e+00\r\n163 165 -6.1319572000000e+02\r\n164 165  8.8189741000000e+01\r\n165 165  2.4586836000000e+01\r\n166 165  1.2176783000000e+00\r\n167 165 -1.7063358000000e-01\r\n168 165 -6.4990078000000e+00\r\n211 165  5.3693564000000e+01\r\n212 165 -7.5240940000000e+00\r\n213 165 -6.4633840000000e+00\r\n1269 165 -1.4146747000000e+00\r\n163 166 -6.9261266000000e-01\r\n165 166 -2.8605960000000e-02\r\n166 166  5.7964280000000e+02\r\n168 166  2.1236083000000e-01\r\n169 166 -6.4659514000000e-01\r\n171 166 -2.8598130000000e-02\r\n214 166 -2.6326900000000e+00\r\n216 166 -2.8465858000000e-02\r\n1270 166 -1.0407070000000e+00\r\n1272 166 -4.6029227000000e-02\r\n165 167 -3.8446595000000e+00\r\n166 167 -3.6080559000000e+02\r\n167 167 -9.2549851000000e+01\r\n168 167  1.2072043000000e+01\r\n171 167 -3.7281591000000e+00\r\n214 167  3.0535283000000e+01\r\n216 167 -3.7102441000000e+00\r\n1272 167 -7.7776517000000e-01\r\n165 168 -6.4990078000000e+00\r\n166 168 -6.0990576000000e+02\r\n167 168  1.0113849000000e+02\r\n168 168  2.0406572000000e+01\r\n171 168 -6.3020758000000e+00\r\n214 168  5.1616842000000e+01\r\n215 168 -7.2946364000000e+00\r\n216 168 -6.2717966000000e+00\r\n1272 168 -1.3147342000000e+00\r\n166 169 -7.4936863000000e-01\r\n168 169 -2.8598130000000e-02\r\n169 169  5.7960782000000e+02\r\n171 169  2.0612325000000e-01\r\n172 169 -5.0660252000000e-01\r\n174 169 -2.2406424000000e-02\r\n217 169 -2.6813113000000e+00\r\n219 169 -2.8468338000000e-02\r\n1273 169 -1.0397916000000e+00\r\n1275 169 -4.5988738000000e-02\r\n166 170  1.6519968000000e+00\r\n168 170 -3.7281591000000e+00\r\n169 170 -3.6323852000000e+02\r\n170 170 -1.0089664000000e+02\r\n171 170  1.2039996000000e+01\r\n174 170 -3.8116668000000e+00\r\n217 170  3.1315243000000e+01\r\n219 170 -3.7116769000000e+00\r\n1275 170 -7.7727817000000e-01\r\n166 171  2.7925334000000e+00\r\n167 171 -3.9466218000000e-01\r\n168 171 -6.3020758000000e+00\r\n169 171 -6.1401798000000e+02\r\n170 171  8.7613858000000e+01\r\n171 171  2.0352399000000e+01\r\n174 171 -6.4432415000000e+00\r\n217 171  5.2935250000000e+01\r\n218 171 -7.4812153000000e+00\r\n219 171 -6.2742143000000e+00\r\n1275 171 -1.3139100000000e+00\r\n124 172 -1.0275334000000e+01\r\n126 172 -3.0109811000000e-01\r\n169 172 -9.2027711000000e-01\r\n171 172 -2.2406424000000e-02\r\n172 172  5.7841498000000e+02\r\n174 172  4.0105527000000e-01\r\n175 172 -6.0633936000000e-01\r\n177 172 -1.7767561000000e-02\r\n220 172 -2.2549502000000e+00\r\n222 172 -2.2319387000000e-02\r\n1276 172 -1.2199801000000e+00\r\n1278 172 -3.5749077000000e-02\r\n126 173 -1.6569781000000e+00\r\n169 173  4.9808187000000e+00\r\n171 173 -3.8116668000000e+00\r\n172 173 -3.6291867000000e+02\r\n173 173 -9.9874183000000e+01\r\n174 173  1.3885676000000e+01\r\n177 173 -3.7395622000000e+00\r\n220 173  3.4272320000000e+01\r\n222 173 -3.7973032000000e+00\r\n1278 173 -8.6906437000000e-01\r\n126 174 -2.8009558000000e+00\r\n169 174  8.4195758000000e+00\r\n170 174 -1.1816716000000e+00\r\n171 174 -6.4432415000000e+00\r\n172 174 -6.1347772000000e+02\r\n173 174  8.8241532000000e+01\r\n174 174  2.3472342000000e+01\r\n177 174 -6.3213517000000e+00\r\n220 174  5.7933929000000e+01\r\n221 174 -8.1309186000000e+00\r\n222 174 -6.4189614000000e+00\r\n1278 174 -1.4690664000000e+00\r\n127 175 -5.2720176000000e+00\r\n129 175 -1.5448592000000e-01\r\n172 175 -8.8376592000000e-01\r\n174 175 -1.7767561000000e-02\r\n175 175  5.3819049000000e+02\r\n177 175  2.2860480000000e-01\r\n178 175 -3.6629296000000e-01\r\n180 175 -1.0733482000000e-02\r\n223 175 -2.1028053000000e+00\r\n225 175 -1.7511047000000e-02\r\n1279 175 -9.0554114000000e-01\r\n1281 175 -2.6535070000000e-02\r\n129 176 -2.1159596000000e+00\r\n172 176  6.4992267000000e+00\r\n174 176 -3.7395622000000e+00\r\n175 176 -3.4501964000000e+02\r\n176 176 -9.4437882000000e+01\r\n177 176  1.4167430000000e+01\r\n180 176 -3.5930102000000e+00\r\n223 176  3.4671114000000e+01\r\n225 176 -3.6860291000000e+00\r\n1281 176 -1.0223718000000e+00\r\n129 177 -3.5768156000000e+00\r\n172 177  1.0986285000000e+01\r\n173 177 -1.5779046000000e+00\r\n174 177 -6.3213517000000e+00\r\n175 177 -5.8322082000000e+02\r\n176 177  8.4628322000000e+01\r\n177 177  2.3948610000000e+01\r\n180 177 -6.0736243000000e+00\r\n223 177  5.8608013000000e+01\r\n224 177 -8.4175711000000e+00\r\n225 177 -6.2308592000000e+00\r\n1281 177 -1.7282160000000e+00\r\n130 178 -4.7968887000000e+00\r\n132 178 -8.4835819000000e-02\r\n175 178 -8.0210585000000e-01\r\n177 178 -1.0733482000000e-02\r\n178 178  4.9120539000000e+02\r\n180 178  1.3248632000000e-01\r\n181 178 -3.9934254000000e-01\r\n183 178 -7.0626095000000e-03\r\n226 178 -1.5065650000000e+00\r\n228 178 -1.0573342000000e-02\r\n1282 178 -1.0123748000000e+00\r\n1284 178 -1.7904448000000e-02\r\n132 179 -2.3306147000000e+00\r\n175 179  7.4001667000000e+00\r\n177 179 -3.5930102000000e+00\r\n178 179 -3.1953541000000e+02\r\n179 179 -8.7270037000000e+01\r\n180 179  1.4135047000000e+01\r\n183 179 -3.4167533000000e+00\r\n226 179  3.4709746000000e+01\r\n228 179 -3.5398843000000e+00\r\n1284 179 -1.2450844000000e+00\r\n132 180 -3.9396711000000e+00\r\n175 180  1.2509242000000e+01\r\n176 180 -1.7988232000000e+00\r\n177 180 -6.0736243000000e+00\r\n178 180 -5.4014266000000e+02\r\n179 180  7.9198658000000e+01\r\n180 180  2.3893881000000e+01\r\n183 180 -5.7756766000000e+00\r\n226 180  5.8673355000000e+01\r\n227 180 -8.4372023000000e+00\r\n228 180 -5.9838204000000e+00\r\n1284 180 -2.1046906000000e+00\r\n133 181 -2.3431693000000e+00\r\n135 181 -4.1440337000000e-02\r\n178 181 -6.0882022000000e-01\r\n180 181 -7.0626095000000e-03\r\n181 181  4.5308736000000e+02\r\n183 181  6.8671832000000e-02\r\n184 181 -1.7952822000000e-01\r\n186 181 -3.1750629000000e-03\r\n229 181 -1.2500289000000e+00\r\n231 181 -6.9509890000000e-03\r\n1285 181 -4.9817901000000e-01\r\n1287 181 -8.8105909000000e-03\r\n135 182 -2.4844433000000e+00\r\n178 182  8.0397464000000e+00\r\n180 182 -3.4167533000000e+00\r\n181 182 -2.9842278000000e+02\r\n182 182 -8.1860502000000e+01\r\n183 182  1.4079488000000e+01\r\n186 182 -3.2915798000000e+00\r\n229 182  3.2776872000000e+01\r\n231 182 -3.3632083000000e+00\r\n1287 182 -1.5144038000000e+00\r\n135 183 -4.1996989000000e+00\r\n178 183  1.3590380000000e+01\r\n179 183 -2.0179013000000e+00\r\n180 183 -5.7756766000000e+00\r\n181 183 -5.0445359000000e+02\r\n182 183  7.4924081000000e+01\r\n183 183  2.3799955000000e+01\r\n186 183 -5.5640865000000e+00\r\n229 183  5.5405994000000e+01\r\n230 183 -8.2266890000000e+00\r\n231 183 -5.6851642000000e+00\r\n1287 183 -2.5599466000000e+00\r\n136 184 -1.5800177000000e+00\r\n138 184 -2.7943549000000e-02\r\n181 184 -3.8085523000000e-01\r\n183 184 -3.1750629000000e-03\r\n184 184  4.1704012000000e+02\r\n186 184  4.2224667000000e-02\r\n187 184 -1.2247098000000e-01\r\n189 184 -2.1659719000000e-03\r\n232 184 -9.6282021000000e-01\r\n234 184 -3.1237309000000e-03\r\n1288 184 -2.6765315000000e-01\r\n1290 184 -4.7336046000000e-03\r\n138 185 -2.4646498000000e+00\r\n181 185  7.6865494000000e+00\r\n183 185 -3.2915798000000e+00\r\n184 185 -2.7554457000000e+02\r\n185 185 -7.6543503000000e+01\r\n186 185  1.3835576000000e+01\r\n189 185 -3.0734057000000e+00\r\n232 185  3.0072650000000e+01\r\n234 185 -3.2388179000000e+00\r\n1290 185 -1.7586124000000e+00\r\n138 186 -4.1662440000000e+00\r\n181 186  1.2993343000000e+01\r\n182 186 -2.0075327000000e+00\r\n183 186 -5.5640865000000e+00\r\n184 186 -4.6578054000000e+02\r\n185 186  7.0327031000000e+01\r\n186 186  2.3387654000000e+01\r\n189 186 -5.1952822000000e+00\r\n232 186  5.0834807000000e+01\r\n233 186 -7.8542169000000e+00\r\n234 186 -5.4748978000000e+00\r\n1290 186 -2.9727583000000e+00\r\n139 187 -1.7974492000000e+00\r\n141 187 -1.8758993000000e-02\r\n184 187 -2.8221387000000e-01\r\n186 187 -2.1659719000000e-03\r\n187 187  3.8232845000000e+02\r\n189 187  2.9595214000000e-02\r\n190 187 -1.7389934000000e-01\r\n192 187 -1.8148921000000e-03\r\n235 187 -4.6688455000000e-01\r\n237 187 -2.1283901000000e-03\r\n1291 187 -3.5963947000000e-01\r\n1293 187 -3.7533603000000e-03\r\n141 188 -2.4055380000000e+00\r\n184 188  7.2573020000000e+00\r\n186 188 -3.0734057000000e+00\r\n187 188 -2.5249098000000e+02\r\n188 188 -7.0502971000000e+01\r\n189 188  1.3352024000000e+01\r\n192 188 -2.8726571000000e+00\r\n235 188  2.7264523000000e+01\r\n237 188 -3.0204609000000e+00\r\n1293 188 -1.9721237000000e+00\r\n141 189 -4.0663174000000e+00\r\n184 189  1.2267737000000e+01\r\n185 189 -1.8598161000000e+00\r\n186 189 -5.1952822000000e+00\r\n187 189 -4.2681054000000e+02\r\n188 189  6.4538446000000e+01\r\n189 189  2.2570249000000e+01\r\n192 189 -4.8559394000000e+00\r\n235 189  4.6087927000000e+01\r\n236 189 -6.9870316000000e+00\r\n237 189 -5.1057843000000e+00\r\n1293 189 -3.3336753000000e+00\r\n142 190 -1.1448824000000e+00\r\n144 190 -1.1948511000000e-02\r\n187 190 -2.2552177000000e-01\r\n189 190 -1.8148921000000e-03\r\n190 190  3.5827852000000e+02\r\n192 190  1.9645213000000e-02\r\n238 190 -3.4041326000000e-01\r\n240 190 -1.8063119000000e-03\r\n1294 190 -3.0363694000000e-01\r\n1296 190 -3.1688925000000e-03\r\n144 191 -2.3767260000000e+00\r\n187 191  5.0814602000000e+00\r\n189 191 -2.8726571000000e+00\r\n190 191 -2.3237971000000e+02\r\n191 191 -6.6372454000000e+01\r\n192 191  1.0250425000000e+01\r\n238 191  2.2538935000000e+01\r\n240 191 -2.8594450000000e+00\r\n1296 191 -2.1342173000000e+00\r\n144 192 -4.0176177000000e+00\r\n187 192  8.5897002000000e+00\r\n188 192 -1.3110006000000e+00\r\n189 192 -4.8559394000000e+00\r\n190 192 -3.9281466000000e+02\r\n191 192  5.9555841000000e+01\r\n192 192  1.7327318000000e+01\r\n238 192  3.8099815000000e+01\r\n239 192 -5.8149738000000e+00\r\n240 192 -4.8336058000000e+00\r\n1296 192 -3.6076809000000e+00\r\n193 193  1.0000000000000e+00\r\n194 194  1.0000000000000e+00\r\n195 195  1.0000000000000e+00\r\n196 196  1.0000000000000e+00\r\n197 197  1.0000000000000e+00\r\n198 198  1.0000000000000e+00\r\n199 199  1.0000000000000e+00\r\n200 200  1.0000000000000e+00\r\n201 201  1.0000000000000e+00\r\n202 202  1.0000000000000e+00\r\n203 203  1.0000000000000e+00\r\n204 204  1.0000000000000e+00\r\n205 205  1.0000000000000e+00\r\n206 206  1.0000000000000e+00\r\n207 207  1.0000000000000e+00\r\n160 208 -1.0710627000000e+00\r\n162 208 -1.1178095000000e-02\r\n208 208  5.7664083000000e+02\r\n210 208  2.0060363000000e-02\r\n211 208 -2.4673275000000e-01\r\n213 208 -2.4431051000000e-03\r\n256 208 -5.0275251000000e-01\r\n258 208 -2.4344383000000e-03\r\n1312 208 -2.4521007000000e-01\r\n1314 208 -2.5591232000000e-03\r\n162 209 -4.1117354000000e+00\r\n208 209 -3.6951689000000e+02\r\n209 209 -1.0739081000000e+02\r\n210 209  1.4473053000000e+01\r\n211 209  1.2598142000000e+00\r\n213 209 -4.5324730000000e+00\r\n256 209  3.8055507000000e+01\r\n258 209 -4.5169952000000e+00\r\n1314 209 -1.2998960000000e+00\r\n162 210 -6.9504776000000e+00\r\n208 210 -6.2463134000000e+02\r\n209 210  9.4914364000000e+01\r\n210 210  2.4465248000000e+01\r\n211 210  2.1295899000000e+00\r\n212 210 -3.2783572000000e-01\r\n213 210 -7.6616923000000e+00\r\n256 210  6.4329029000000e+01\r\n257 210 -9.9030117000000e+00\r\n258 210 -7.6355288000000e+00\r\n1314 210 -2.1973442000000e+00\r\n163 211 -2.1814878000000e+00\r\n165 211 -2.2766993000000e-02\r\n208 211 -2.3409345000000e-01\r\n210 211 -2.4431051000000e-03\r\n211 211  5.7810629000000e+02\r\n213 211  3.4919008000000e-02\r\n214 211 -2.6512178000000e-01\r\n216 211 -2.6886511000000e-03\r\n259 211 -5.7254940000000e-01\r\n261 211 -2.6800805000000e-03\r\n1315 211 -2.7636288000000e-01\r\n1317 211 -2.8842481000000e-03\r\n165 212 -3.8235852000000e+00\r\n210 212 -4.5324730000000e+00\r\n211 212 -3.6896133000000e+02\r\n212 212 -1.0720477000000e+02\r\n213 212  1.8657388000000e+01\r\n214 212  7.4248961000000e-01\r\n216 212 -4.5082972000000e+00\r\n259 212  3.8015026000000e+01\r\n261 212 -4.4945266000000e+00\r\n1317 212 -1.2865738000000e+00\r\n165 213 -6.4633840000000e+00\r\n210 213 -7.6616923000000e+00\r\n211 213 -6.2369183000000e+02\r\n212 213  9.4574832000000e+01\r\n213 213  3.1538432000000e+01\r\n214 213  1.2551036000000e+00\r\n215 213 -1.9218681000000e-01\r\n216 213 -7.6208205000000e+00\r\n259 213  6.4260557000000e+01\r\n260 213 -9.8398496000000e+00\r\n261 213 -7.5975428000000e+00\r\n1317 213 -2.1748226000000e+00\r\n166 214 -2.7275416000000e+00\r\n168 214 -2.8465858000000e-02\r\n211 214 -2.5762117000000e-01\r\n213 214 -2.6886511000000e-03\r\n214 214  5.7892699000000e+02\r\n216 214  4.2732943000000e-02\r\n217 214 -3.2769397000000e-01\r\n219 214 -3.4199625000000e-03\r\n262 214 -6.9620582000000e-01\r\n264 214 -3.1666804000000e-03\r\n1318 214 -3.3683290000000e-01\r\n1320 214 -3.5153406000000e-03\r\n168 215 -3.7102441000000e+00\r\n213 215 -4.5082972000000e+00\r\n214 215 -3.6893026000000e+02\r\n215 215 -9.8002191000000e+01\r\n216 215  1.8375718000000e+01\r\n219 215 -4.4366481000000e+00\r\n262 215  3.8721161000000e+01\r\n264 215 -4.4472212000000e+00\r\n1320 215 -1.2614183000000e+00\r\n168 216 -6.2717966000000e+00\r\n213 216 -7.6208205000000e+00\r\n214 216 -6.2363972000000e+02\r\n215 216  1.0911105000000e+02\r\n216 216  3.1062304000000e+01\r\n219 216 -7.4997050000000e+00\r\n262 216  6.5454250000000e+01\r\n263 216 -9.9161438000000e+00\r\n264 216 -7.5175827000000e+00\r\n1320 216 -2.1323014000000e+00\r\n169 217 -2.7277792000000e+00\r\n171 217 -2.8468338000000e-02\r\n214 217 -3.3767214000000e-01\r\n216 217 -3.4199625000000e-03\r\n217 217  5.7908054000000e+02\r\n219 217  4.4058334000000e-02\r\n220 217 -3.2755690000000e-01\r\n222 217 -3.4185321000000e-03\r\n265 217 -7.3488848000000e-01\r\n267 217 -3.4093212000000e-03\r\n1321 217 -3.6942559000000e-01\r\n1323 217 -3.8554926000000e-03\r\n171 218 -3.7116769000000e+00\r\n214 218  9.8147627000000e-01\r\n216 218 -4.4366481000000e+00\r\n217 218 -3.7128234000000e+02\r\n218 218 -1.0664909000000e+02\r\n219 218  1.8269537000000e+01\r\n222 218 -4.4365683000000e+00\r\n265 218  4.0088522000000e+01\r\n267 218 -4.4233411000000e+00\r\n1323 218 -1.2494341000000e+00\r\n171 219 -6.2742143000000e+00\r\n214 219  1.6590864000000e+00\r\n215 219 -2.5000051000000e-01\r\n216 219 -7.4997050000000e+00\r\n217 219 -6.2761527000000e+02\r\n218 219  9.4589072000000e+01\r\n219 219  3.0882809000000e+01\r\n222 219 -7.4995750000000e+00\r\n265 219  6.7765594000000e+01\r\n266 219 -1.0211302000000e+01\r\n267 219 -7.4772107000000e+00\r\n1323 219 -2.1120419000000e+00\r\n172 220 -2.1385990000000e+00\r\n174 220 -2.2319387000000e-02\r\n217 220 -3.6012857000000e-01\r\n219 220 -3.4185321000000e-03\r\n220 220  5.7847280000000e+02\r\n222 220  3.7287746000000e-02\r\n223 220 -2.6939197000000e-01\r\n225 220 -2.8114965000000e-03\r\n268 220 -7.5130318000000e-01\r\n270 220 -3.4090856000000e-03\r\n1324 220 -3.6819108000000e-01\r\n1326 220 -3.8426087000000e-03\r\n174 221 -3.7973032000000e+00\r\n217 221  3.2107202000000e+00\r\n219 221 -4.4365683000000e+00\r\n220 221 -3.7513644000000e+02\r\n221 221 -1.0664886000000e+02\r\n222 221  1.8317866000000e+01\r\n225 221 -4.3982700000000e+00\r\n268 221  4.1711503000000e+01\r\n270 221 -4.4248029000000e+00\r\n1326 221 -1.2490543000000e+00\r\n174 222 -6.4189614000000e+00\r\n217 222  5.4274013000000e+00\r\n218 222 -8.1785463000000e-01\r\n219 222 -7.4995750000000e+00\r\n220 222 -6.3413063000000e+02\r\n221 222  9.5574845000000e+01\r\n222 222  3.0964516000000e+01\r\n225 222 -7.4348304000000e+00\r\n268 222  7.0509125000000e+01\r\n269 222 -1.0625014000000e+01\r\n270 222 -7.4796868000000e+00\r\n1326 222 -2.1114013000000e+00\r\n175 223 -1.6778735000000e+00\r\n177 223 -1.7511047000000e-02\r\n220 223 -3.1793598000000e-01\r\n222 223 -2.8114965000000e-03\r\n223 223  5.5474903000000e+02\r\n225 223  2.9553440000000e-02\r\n226 223 -1.8227636000000e-01\r\n228 223 -1.9023186000000e-03\r\n271 223 -6.7335162000000e-01\r\n273 223 -2.8042008000000e-03\r\n1327 223 -2.9888915000000e-01\r\n1329 223 -3.1193424000000e-03\r\n177 224 -3.6860291000000e+00\r\n220 224  4.7680567000000e+00\r\n222 224 -4.3982700000000e+00\r\n223 224 -3.6390682000000e+02\r\n224 224 -1.0278084000000e+02\r\n225 224  1.8064403000000e+01\r\n228 224 -4.2463847000000e+00\r\n271 224  4.2136737000000e+01\r\n273 224 -4.3874214000000e+00\r\n1329 224 -1.3348595000000e+00\r\n177 225 -6.2308592000000e+00\r\n220 225  8.0599173000000e+00\r\n221 225 -1.2292842000000e+00\r\n222 225 -7.4348304000000e+00\r\n223 225 -6.1514765000000e+02\r\n224 225  9.3163769000000e+01\r\n225 225  3.0536050000000e+01\r\n228 225 -7.1780887000000e+00\r\n271 225  7.1227889000000e+01\r\n272 225 -1.0863549000000e+01\r\n273 225 -7.4164918000000e+00\r\n1329 225 -2.2564449000000e+00\r\n178 226 -1.0131165000000e+00\r\n180 226 -1.0573342000000e-02\r\n223 226 -2.4825922000000e-01\r\n225 226 -1.9023186000000e-03\r\n226 226  5.1920487000000e+02\r\n228 226  1.8823489000000e-02\r\n229 226 -1.1827383000000e-01\r\n231 226 -1.2343592000000e-03\r\n274 226 -5.1884683000000e-01\r\n276 226 -1.8782924000000e-03\r\n1330 226 -1.8675856000000e-01\r\n1332 226 -1.9490968000000e-03\r\n180 227 -3.5398843000000e+00\r\n223 227  6.4838811000000e+00\r\n225 227 -4.2463847000000e+00\r\n226 227 -3.4419200000000e+02\r\n227 227 -9.6916962000000e+01\r\n228 227  1.7439049000000e+01\r\n231 227 -3.9733548000000e+00\r\n274 227  4.0524145000000e+01\r\n276 227 -4.1932912000000e+00\r\n1332 227 -1.4753468000000e+00\r\n180 228 -5.9838204000000e+00\r\n223 228  1.0960352000000e+01\r\n224 228 -1.7017208000000e+00\r\n225 228 -7.1780887000000e+00\r\n226 228 -5.8182216000000e+02\r\n227 228  8.8768635000000e+01\r\n228 228  2.9478962000000e+01\r\n231 228 -6.7165536000000e+00\r\n274 228  6.8502014000000e+01\r\n275 228 -1.0635726000000e+01\r\n276 228 -7.0883394000000e+00\r\n1332 228 -2.4939263000000e+00\r\n181 229 -6.6602986000000e-01\r\n183 229 -6.9509890000000e-03\r\n226 229 -1.9858635000000e-01\r\n228 229 -1.2343592000000e-03\r\n229 229  4.7252958000000e+02\r\n231 229  1.2074909000000e-02\r\n232 229 -2.8192377000000e-02\r\n234 229 -2.9422840000000e-04\r\n277 229 -3.6741877000000e-01\r\n279 229 -1.2175774000000e-03\r\n1333 229 -1.1756918000000e-01\r\n1335 229 -1.2270051000000e-03\r\n183 230 -3.3632083000000e+00\r\n226 230  7.8886303000000e+00\r\n228 230 -3.9733548000000e+00\r\n229 230 -3.1651079000000e+02\r\n230 230 -8.8678619000000e+01\r\n231 230  1.6662947000000e+01\r\n234 230 -3.7352263000000e+00\r\n277 230  3.7856342000000e+01\r\n279 230 -3.9198308000000e+00\r\n1335 230 -1.6614562000000e+00\r\n183 231 -5.6851642000000e+00\r\n226 231  1.3334930000000e+01\r\n227 231 -2.0974954000000e+00\r\n228 231 -6.7165536000000e+00\r\n229 231 -5.3502944000000e+02\r\n230 231  8.2092491000000e+01\r\n231 231  2.8167030000000e+01\r\n234 231 -6.3140265000000e+00\r\n277 231  6.3992312000000e+01\r\n278 231 -1.0065562000000e+01\r\n279 231 -6.6260765000000e+00\r\n1335 231 -2.8085241000000e+00\r\n184 232 -2.9930964000000e-01\r\n186 232 -3.1237309000000e-03\r\n229 232 -1.1643972000000e-01\r\n231 232 -2.9422840000000e-04\r\n232 232  4.3738055000000e+02\r\n234 232  5.5958296000000e-03\r\n235 232 -1.6217394000000e-03\r\n237 232 -1.6925206000000e-05\r\n280 232 -2.0947241000000e-01\r\n282 232 -2.8999742000000e-04\r\n1336 232 -8.0340221000000e-02\r\n1338 232 -8.3846689000000e-04\r\n186 233 -3.2388179000000e+00\r\n229 233  8.6664178000000e+00\r\n231 233 -3.7352263000000e+00\r\n232 233 -2.9406254000000e+02\r\n233 233 -8.2802041000000e+01\r\n234 233  1.5978837000000e+01\r\n237 233 -3.4760355000000e+00\r\n280 233  3.4447542000000e+01\r\n282 233 -3.6819706000000e+00\r\n1338 233 -1.8375694000000e+00\r\n186 234 -5.4748978000000e+00\r\n229 234  1.4649713000000e+01\r\n230 234 -2.3563697000000e+00\r\n231 234 -6.3140265000000e+00\r\n232 234 -4.9708331000000e+02\r\n233 234  7.7003990000000e+01\r\n234 234  2.7010623000000e+01\r\n237 234 -5.8758874000000e+00\r\n280 234  5.8230126000000e+01\r\n281 234 -9.3661703000000e+00\r\n282 234 -6.2240031000000e+00\r\n1338 234 -3.1062273000000e+00\r\n187 235 -2.0393809000000e-01\r\n189 235 -2.1283901000000e-03\r\n232 235 -1.1023481000000e-01\r\n234 235 -1.6925206000000e-05\r\n235 235  4.0269551000000e+02\r\n237 235  3.7167283000000e-03\r\n238 235 -1.4737675000000e-03\r\n240 235 -1.5380905000000e-05\r\n283 235 -1.2353727000000e-01\r\n285 235 -1.6665148000000e-05\r\n1339 235 -5.7366022000000e-02\r\n1341 235 -5.9869776000000e-04\r\n189 236 -3.0204609000000e+00\r\n232 236  9.0983861000000e+00\r\n234 236 -3.4760355000000e+00\r\n235 236 -2.6989504000000e+02\r\n236 236 -7.6449015000000e+01\r\n237 236  1.5194425000000e+01\r\n240 236 -3.2404837000000e+00\r\n283 236  2.9659902000000e+01\r\n285 236 -3.4229940000000e+00\r\n1341 236 -2.0259409000000e+00\r\n189 237 -5.1057843000000e+00\r\n232 237  1.5379904000000e+01\r\n233 237 -2.4917653000000e+00\r\n234 237 -5.8758874000000e+00\r\n235 237 -4.5623034000000e+02\r\n236 237  7.0887220000000e+01\r\n237 237  2.5684645000000e+01\r\n240 237 -5.4777135000000e+00\r\n283 237  5.0137073000000e+01\r\n284 237 -8.1229254000000e+00\r\n285 237 -5.7862261000000e+00\r\n1341 237 -3.4246482000000e+00\r\n190 238 -1.7307719000000e-01\r\n192 238 -1.8063119000000e-03\r\n235 238 -1.4162830000000e-01\r\n237 238 -1.5380905000000e-05\r\n238 238  3.7956711000000e+02\r\n240 238  2.7342053000000e-03\r\n286 238 -1.8468844000000e-03\r\n288 238 -1.5122013000000e-05\r\n1342 238 -3.5584583000000e-02\r\n1344 238 -1.0490999000000e-05\r\n192 239 -2.8594450000000e+00\r\n235 239  8.7075681000000e+00\r\n237 239 -3.2404837000000e+00\r\n238 239 -2.4332481000000e+02\r\n239 239 -7.2082031000000e+01\r\n240 239  1.1483163000000e+01\r\n286 239  1.6689927000000e+01\r\n288 239 -3.1862433000000e+00\r\n1344 239 -2.1889664000000e+00\r\n192 240 -4.8336058000000e+00\r\n235 240  1.4719273000000e+01\r\n236 240 -2.3847611000000e+00\r\n237 240 -5.4777135000000e+00\r\n238 240 -4.1131626000000e+02\r\n239 240  6.3780781000000e+01\r\n240 240  1.9411139000000e+01\r\n286 240  2.8212653000000e+01\r\n287 240 -4.5709076000000e+00\r\n288 240 -5.3860258000000e+00\r\n1344 240 -3.7002288000000e+00\r\n241 241  1.0000000000000e+00\r\n242 242  1.0000000000000e+00\r\n243 243  1.0000000000000e+00\r\n244 244  1.0000000000000e+00\r\n245 245  1.0000000000000e+00\r\n246 246  1.0000000000000e+00\r\n247 247  1.0000000000000e+00\r\n248 248  1.0000000000000e+00\r\n249 249  1.0000000000000e+00\r\n250 250  1.0000000000000e+00\r\n251 251  1.0000000000000e+00\r\n252 252  1.0000000000000e+00\r\n253 253  1.0000000000000e+00\r\n254 254  1.0000000000000e+00\r\n255 255  1.0000000000000e+00\r\n208 256 -2.3326301000000e-01\r\n210 256 -2.4344383000000e-03\r\n256 256  5.7507916000000e+02\r\n258 256  3.8357379000000e-03\r\n259 256 -6.1330853000000e-02\r\n261 256 -2.4941367000000e-05\r\n304 256 -2.4053318000000e-01\r\n306 256 -2.4894191000000e-05\r\n1360 256 -1.9741121000000e-02\r\n1362 256 -7.6162909000000e-06\r\n210 257 -4.5169952000000e+00\r\n256 257 -3.7305396000000e+02\r\n257 257 -1.0022923000000e+02\r\n258 257  1.5487904000000e+01\r\n259 257  1.2056910000000e+00\r\n261 257 -4.7705675000000e+00\r\n304 257  4.1710395000000e+01\r\n306 257 -4.7620287000000e+00\r\n1362 257 -1.4261365000000e+00\r\n210 258 -7.6355288000000e+00\r\n256 258 -6.3061041000000e+02\r\n257 258  1.1299210000000e+02\r\n258 258  2.6180753000000e+01\r\n259 258  2.0381001000000e+00\r\n260 258 -3.3018964000000e-01\r\n261 258 -8.0641672000000e+00\r\n304 258  7.0507252000000e+01\r\n305 258 -1.1422778000000e+01\r\n306 258 -8.0497333000000e+00\r\n1362 258 -2.4107412000000e+00\r\n211 259 -2.5679995000000e-01\r\n213 259 -2.6800805000000e-03\r\n256 259 -2.3898319000000e-03\r\n258 259 -2.4941367000000e-05\r\n259 259  5.7512775000000e+02\r\n261 259  4.1066606000000e-03\r\n262 259 -8.7123907000000e-02\r\n264 259 -2.5087633000000e-05\r\n307 259 -2.4811441000000e-01\r\n309 259 -2.5032665000000e-05\r\n1363 259 -5.1195054000000e-03\r\n1365 259 -7.6616229000000e-06\r\n213 260 -4.4945266000000e+00\r\n258 260 -4.7705675000000e+00\r\n259 260 -3.7403651000000e+02\r\n260 260 -1.0925131000000e+02\r\n261 260  2.0220255000000e+01\r\n262 260  1.4464879000000e+00\r\n264 260 -4.7706176000000e+00\r\n307 260  4.2446987000000e+01\r\n309 260 -4.7606802000000e+00\r\n1365 260 -1.4116883000000e+00\r\n213 261 -7.5975428000000e+00\r\n258 261 -8.0641672000000e+00\r\n259 261 -6.3227092000000e+02\r\n260 261  9.8012889000000e+01\r\n261 261  3.4180302000000e+01\r\n262 261  2.4451416000000e+00\r\n263 261 -3.9613289000000e-01\r\n264 261 -8.0642470000000e+00\r\n307 261  7.1752342000000e+01\r\n308 261 -1.1624465000000e+01\r\n309 261 -8.0474488000000e+00\r\n1365 261 -2.3863159000000e+00\r\n214 262 -3.0342498000000e-01\r\n216 262 -3.1666804000000e-03\r\n259 262 -2.4038469000000e-03\r\n261 262 -2.5087633000000e-05\r\n262 262  5.7515641000000e+02\r\n264 262  5.2770057000000e-03\r\n265 262 -7.9344378000000e-03\r\n267 262 -2.5382928000000e-05\r\n310 262 -2.4183986000000e-01\r\n312 262 -2.5312166000000e-05\r\n1366 262 -6.6178409000000e-02\r\n1368 262 -6.9066782000000e-04\r\n216 263 -4.4472212000000e+00\r\n261 263 -4.7706176000000e+00\r\n262 263 -3.7464345000000e+02\r\n263 263 -1.0924511000000e+02\r\n264 263  2.0149213000000e+01\r\n265 263  3.9033555000000e-01\r\n267 263 -4.7709720000000e+00\r\n310 263  4.4102251000000e+01\r\n312 263 -4.7581730000000e+00\r\n1368 263 -1.3900576000000e+00\r\n216 264 -7.5175827000000e+00\r\n261 264 -8.0642470000000e+00\r\n262 264 -6.3329729000000e+02\r\n263 264  9.8193118000000e+01\r\n264 264  3.4060225000000e+01\r\n265 264  6.5982322000000e-01\r\n266 264 -1.0689604000000e-01\r\n267 264 -8.0648511000000e+00\r\n310 264  7.4550445000000e+01\r\n311 264 -1.2077701000000e+01\r\n312 264 -8.0432156000000e+00\r\n1368 264 -2.3497534000000e+00\r\n217 265 -3.2667434000000e-01\r\n219 265 -3.4093212000000e-03\r\n262 265 -2.4321414000000e-03\r\n264 265 -2.5382928000000e-05\r\n265 265  5.7529329000000e+02\r\n267 265  6.3019063000000e-03\r\n268 265 -4.7552521000000e-02\r\n270 265 -4.9627962000000e-04\r\n313 265 -3.0674308000000e-01\r\n315 265 -2.5241294000000e-04\r\n1369 265 -7.3306335000000e-02\r\n1371 265 -7.6505808000000e-04\r\n219 266 -4.4233411000000e+00\r\n264 266 -4.7709720000000e+00\r\n265 266 -3.7636258000000e+02\r\n266 266 -1.0907205000000e+02\r\n267 266  2.0050582000000e+01\r\n270 266 -4.7241863000000e+00\r\n313 266  4.6208999000000e+01\r\n315 266 -4.7371923000000e+00\r\n1371 266 -1.3827379000000e+00\r\n219 267 -7.4772107000000e+00\r\n264 267 -8.0648511000000e+00\r\n265 267 -6.3620291000000e+02\r\n266 267  9.8474973000000e+01\r\n267 267  3.3893491000000e+01\r\n270 267 -7.9857645000000e+00\r\n313 267  7.8111643000000e+01\r\n314 267 -1.2595337000000e+01\r\n315 267 -8.0077441000000e+00\r\n1371 267 -2.3373788000000e+00\r\n220 268 -3.2665177000000e-01\r\n222 268 -3.4090856000000e-03\r\n265 268 -6.3767677000000e-02\r\n267 268 -4.9627962000000e-04\r\n268 268  5.7538353000000e+02\r\n270 268  6.6288635000000e-03\r\n271 268 -2.4141033000000e-03\r\n273 268 -2.5194674000000e-05\r\n316 268 -3.7051672000000e-01\r\n318 268 -4.9508786000000e-04\r\n1372 268 -8.0441990000000e-02\r\n1374 268 -8.3952900000000e-04\r\n222 269 -4.4248029000000e+00\r\n265 269  1.5957294000000e+00\r\n267 269 -4.7241863000000e+00\r\n268 269 -3.7965795000000e+02\r\n269 269 -1.0888646000000e+02\r\n270 269  2.0020417000000e+01\r\n273 269 -4.7703035000000e+00\r\n316 269  4.7904941000000e+01\r\n318 269 -4.7132973000000e+00\r\n1374 269 -1.3756968000000e+00\r\n222 270 -7.4796868000000e+00\r\n265 270  2.6974210000000e+00\r\n266 270 -4.3276435000000e-01\r\n267 270 -7.9857645000000e+00\r\n268 270 -6.4177380000000e+02\r\n269 270  9.9168081000000e+01\r\n270 270  3.3842508000000e+01\r\n273 270 -8.0637164000000e+00\r\n316 270  8.0978512000000e+01\r\n317 270 -1.2991897000000e+01\r\n318 270 -7.9673577000000e+00\r\n1374 270 -2.3254778000000e+00\r\n223 271 -2.6869291000000e-01\r\n225 271 -2.8042008000000e-03\r\n268 271 -6.3581913000000e-02\r\n270 271 -2.5194674000000e-05\r\n271 271  5.7525873000000e+02\r\n273 271  4.8382758000000e-03\r\n274 271 -2.3029972000000e-03\r\n276 271 -2.4035121000000e-05\r\n319 271 -3.3088133000000e-01\r\n321 271 -2.5145119000000e-05\r\n1375 271 -5.9007951000000e-02\r\n1377 271 -6.1583367000000e-04\r\n225 272 -4.3874214000000e+00\r\n268 272  3.5641332000000e+00\r\n270 272 -4.7703035000000e+00\r\n271 272 -3.8200388000000e+02\r\n272 272 -1.0924551000000e+02\r\n273 272  1.9950620000000e+01\r\n276 272 -4.6228863000000e+00\r\n319 272  4.8289200000000e+01\r\n321 272 -4.7614281000000e+00\r\n1377 272 -1.3964088000000e+00\r\n225 273 -7.4164918000000e+00\r\n268 273  6.0248073000000e+00\r\n269 273 -9.7606576000000e-01\r\n270 273 -8.0637164000000e+00\r\n271 273 -6.4573900000000e+02\r\n272 273  1.0020851000000e+02\r\n273 273  3.3724511000000e+01\r\n276 273 -7.8145269000000e+00\r\n319 273  8.1628018000000e+01\r\n320 273 -1.3224376000000e+01\r\n321 273 -8.0487133000000e+00\r\n1377 273 -2.3604874000000e+00\r\n226 274 -1.7997422000000e-01\r\n228 274 -1.8782924000000e-03\r\n271 274 -1.1448077000000e-01\r\n273 274 -2.4035121000000e-05\r\n274 274  5.4067833000000e+02\r\n276 274  3.2197793000000e-03\r\n277 274 -2.1259208000000e-03\r\n279 274 -2.2187071000000e-05\r\n322 274 -3.0833229000000e-01\r\n324 274 -2.3990032000000e-05\r\n1378 274 -1.3839797000000e-02\r\n1380 274 -8.0577291000000e-06\r\n228 275 -4.1932912000000e+00\r\n271 275  5.7457621000000e+00\r\n273 275 -4.6228863000000e+00\r\n274 275 -3.6306423000000e+02\r\n275 275 -1.0269365000000e+02\r\n276 275  1.9287736000000e+01\r\n279 275 -4.3364913000000e+00\r\n322 275  4.6980387000000e+01\r\n324 275 -4.6146947000000e+00\r\n1380 275 -1.5089297000000e+00\r\n228 276 -7.0883394000000e+00\r\n271 276  9.7126360000000e+00\r\n272 276 -1.5735346000000e+00\r\n273 276 -7.8145269000000e+00\r\n274 276 -6.1372377000000e+02\r\n275 276  9.5280061000000e+01\r\n276 276  3.2603984000000e+01\r\n279 276 -7.3304000000000e+00\r\n322 276  7.9415645000000e+01\r\n323 276 -1.2866050000000e+01\r\n324 276 -7.8006799000000e+00\r\n1380 276 -2.5506948000000e+00\r\n229 277 -1.1666583000000e-01\r\n231 277 -1.2175774000000e-03\r\n274 277 -1.5370768000000e-01\r\n276 277 -2.2187071000000e-05\r\n277 277  5.0616727000000e+02\r\n279 277  2.4728039000000e-03\r\n280 277 -1.9243063000000e-03\r\n282 277 -2.0082931000000e-05\r\n325 277 -2.6547366000000e-01\r\n327 277 -2.1915232000000e-05\r\n1381 277 -4.5514360000000e-02\r\n1383 277 -8.4730171000000e-06\r\n231 278 -3.9198308000000e+00\r\n274 278  7.8590684000000e+00\r\n276 278 -4.3364913000000e+00\r\n277 278 -3.4227959000000e+02\r\n278 278 -9.6142388000000e+01\r\n279 278  1.8194383000000e+01\r\n282 278 -3.9985084000000e+00\r\n325 278  4.3895681000000e+01\r\n327 278 -4.2838474000000e+00\r\n1383 278 -1.6449913000000e+00\r\n231 279 -6.6260765000000e+00\r\n274 279  1.3284960000000e+01\r\n275 279 -2.1523019000000e+00\r\n276 279 -7.3304000000000e+00\r\n277 279 -5.7858903000000e+02\r\n278 279  8.9845061000000e+01\r\n279 279  3.0755768000000e+01\r\n282 279 -6.7590784000000e+00\r\n325 279  7.4201208000000e+01\r\n326 279 -1.2021368000000e+01\r\n327 279 -7.2414106000000e+00\r\n1383 279 -2.7806916000000e+00\r\n232 280 -2.7786973000000e-02\r\n234 280 -2.8999742000000e-04\r\n277 280 -1.4812760000000e-01\r\n279 280 -2.0082931000000e-05\r\n280 280  4.6009423000000e+02\r\n282 280  1.4319779000000e-03\r\n283 280 -1.7349305000000e-03\r\n285 280 -1.8106519000000e-05\r\n328 280 -2.3696305000000e-01\r\n330 280 -1.9590447000000e-05\r\n1384 280 -5.8360867000000e-02\r\n1386 280 -9.1538248000000e-06\r\n234 281 -3.6819706000000e+00\r\n277 281  9.5606028000000e+00\r\n279 281 -3.9985084000000e+00\r\n280 281 -3.1505563000000e+02\r\n281 281 -8.7403089000000e+01\r\n282 281  1.7081396000000e+01\r\n285 281 -3.6678429000000e+00\r\n328 281  4.1382436000000e+01\r\n330 281 -3.9008968000000e+00\r\n1386 281 -1.8224369000000e+00\r\n234 282 -6.2240031000000e+00\r\n277 282  1.6161243000000e+01\r\n278 282 -2.6183124000000e+00\r\n279 282 -6.7590784000000e+00\r\n280 282 -5.3257003000000e+02\r\n281 282  8.2741962000000e+01\r\n282 282  2.8874387000000e+01\r\n285 282 -6.2001176000000e+00\r\n328 282  6.9952869000000e+01\r\n329 282 -1.1333192000000e+01\r\n330 282 -6.5940759000000e+00\r\n1386 282 -3.0806474000000e+00\r\n235 283 -1.5968212000000e-03\r\n237 283 -1.6665148000000e-05\r\n280 283 -1.6533186000000e-01\r\n282 283 -1.8106519000000e-05\r\n283 283  4.2564353000000e+02\r\n285 283  1.0727203000000e-03\r\n286 283 -1.5518553000000e-03\r\n288 283 -1.6195864000000e-05\r\n331 283 -2.6510563000000e-01\r\n333 283 -1.7618593000000e-05\r\n1387 283 -5.9577134000000e-02\r\n1389 283 -9.7283995000000e-06\r\n237 284 -3.4229940000000e+00\r\n280 284  1.1886166000000e+01\r\n282 284 -3.6678429000000e+00\r\n283 284 -2.9901873000000e+02\r\n284 284 -8.0847251000000e+01\r\n285 284  1.6020787000000e+01\r\n288 284 -3.3809302000000e+00\r\n331 284  4.2827330000000e+01\r\n333 284 -3.5694188000000e+00\r\n1389 284 -1.9705921000000e+00\r\n237 285 -5.7862261000000e+00\r\n280 285  2.0092362000000e+01\r\n281 285 -3.2552296000000e+00\r\n282 285 -6.2001176000000e+00\r\n283 285 -5.0546093000000e+02\r\n284 285  7.8617985000000e+01\r\n285 285  2.7081526000000e+01\r\n288 285 -5.7151243000000e+00\r\n331 285  7.2395271000000e+01\r\n332 285 -1.1728997000000e+01\r\n333 285 -6.0337414000000e+00\r\n1389 285 -3.3310866000000e+00\r\n238 286 -1.4489610000000e-03\r\n240 286 -1.5122013000000e-05\r\n283 286 -2.6775677000000e-01\r\n285 286 -1.6195864000000e-05\r\n286 286  3.9101108000000e+02\r\n288 286  9.5535783000000e-04\r\n1390 286 -5.9779534000000e-02\r\n1392 286 -1.0278589000000e-05\r\n240 287 -3.1862433000000e+00\r\n283 287  2.0669061000000e+01\r\n285 287 -3.3809302000000e+00\r\n286 287 -2.4516982000000e+02\r\n287 287 -7.4289358000000e+01\r\n288 287  8.7210274000000e+00\r\n1392 287 -2.1455762000000e+00\r\n240 288 -5.3860258000000e+00\r\n283 288  3.4938980000000e+01\r\n284 288 -5.6606570000000e+00\r\n285 288 -5.7151243000000e+00\r\n286 288 -4.1443506000000e+02\r\n287 288  6.4143619000000e+01\r\n288 288  1.4742025000000e+01\r\n1392 288 -3.6268820000000e+00\r\n289 289  1.0000000000000e+00\r\n290 290  1.0000000000000e+00\r\n291 291  1.0000000000000e+00\r\n292 292  1.0000000000000e+00\r\n293 293  1.0000000000000e+00\r\n294 294  1.0000000000000e+00\r\n295 295  1.0000000000000e+00\r\n296 296  1.0000000000000e+00\r\n297 297  1.0000000000000e+00\r\n298 298  1.0000000000000e+00\r\n299 299  1.0000000000000e+00\r\n300 300  1.0000000000000e+00\r\n301 301  1.0000000000000e+00\r\n302 302  1.0000000000000e+00\r\n303 303  1.0000000000000e+00\r\n256 304 -2.3853116000000e-03\r\n258 304 -2.4894191000000e-05\r\n304 304  5.7485382000000e+02\r\n306 304  1.4276539000000e-03\r\n307 304 -6.9040852000000e-02\r\n309 304 -2.5585438000000e-05\r\n352 304 -2.3914903000000e-01\r\n354 304 -2.5509959000000e-05\r\n1408 304 -5.5206415000000e-02\r\n1410 304 -7.8195004000000e-06\r\n258 305 -4.7620287000000e+00\r\n304 305 -3.7818800000000e+02\r\n305 305 -1.0026451000000e+02\r\n306 305  1.5762163000000e+01\r\n307 305  1.9554283000000e+00\r\n309 305 -4.7716102000000e+00\r\n352 305  4.6140393000000e+01\r\n354 305 -4.7580907000000e+00\r\n1410 305 -1.4582423000000e+00\r\n258 306 -8.0497333000000e+00\r\n304 306 -6.3928900000000e+02\r\n305 306  1.1431216000000e+02\r\n306 306  2.6644360000000e+01\r\n307 306  3.3054560000000e+00\r\n308 306 -5.3550504000000e-01\r\n309 306 -8.0659299000000e+00\r\n352 306  7.7995721000000e+01\r\n353 306 -1.2635806000000e+01\r\n354 306 -8.0430765000000e+00\r\n1410 306 -2.4650128000000e+00\r\n259 307 -2.3985799000000e-03\r\n261 307 -2.5032665000000e-05\r\n304 307 -2.4515455000000e-03\r\n306 307 -2.5585438000000e-05\r\n307 307  5.7486458000000e+02\r\n309 307  1.4534908000000e-03\r\n310 307 -8.0982370000000e-02\r\n312 307 -2.5634127000000e-05\r\n355 307 -2.3200970000000e-01\r\n357 307 -2.5550840000000e-05\r\n1411 307 -5.5119630000000e-02\r\n1413 307 -7.8381908000000e-06\r\n261 308 -4.7606802000000e+00\r\n306 308 -4.7716102000000e+00\r\n307 308 -3.8094393000000e+02\r\n308 308 -1.0928573000000e+02\r\n309 308  2.0531953000000e+01\r\n310 308  3.1282473000000e+00\r\n312 308 -4.7717070000000e+00\r\n355 308  4.7718748000000e+01\r\n357 308 -4.7567900000000e+00\r\n1413 308 -1.4589760000000e+00\r\n261 309 -8.0474488000000e+00\r\n306 309 -8.0659299000000e+00\r\n307 309 -6.4394718000000e+02\r\n308 309  9.9820041000000e+01\r\n309 309  3.4707196000000e+01\r\n310 309  5.2879856000000e+00\r\n311 309 -8.5668723000000e-01\r\n312 309 -8.0660879000000e+00\r\n355 309  8.0663716000000e+01\r\n356 309 -1.3068034000000e+01\r\n357 309 -8.0408723000000e+00\r\n1413 309 -2.4662515000000e+00\r\n262 310 -2.4253612000000e-03\r\n264 310 -2.5312166000000e-05\r\n307 310 -2.4562108000000e-03\r\n309 310 -2.5634127000000e-05\r\n310 310  5.7484861000000e+02\r\n312 310  1.4539954000000e-03\r\n313 310 -5.1146276000000e-02\r\n315 310 -2.5710072000000e-05\r\n358 310 -2.4387167000000e-01\r\n360 310 -2.5618235000000e-05\r\n1414 310 -5.3671820000000e-02\r\n1416 310 -7.8650378000000e-06\r\n264 311 -4.7581730000000e+00\r\n309 311 -4.7717070000000e+00\r\n310 311 -3.8375362000000e+02\r\n311 311 -1.0928258000000e+02\r\n312 311  2.0527605000000e+01\r\n313 311  2.4899798000000e+00\r\n315 311 -4.7718289000000e+00\r\n358 311  5.1162626000000e+01\r\n360 311 -4.7553911000000e+00\r\n1416 311 -1.4583174000000e+00\r\n264 312 -8.0432156000000e+00\r\n309 312 -8.0660879000000e+00\r\n310 312 -6.4869713000000e+02\r\n311 312  1.0059674000000e+02\r\n312 312  3.4699859000000e+01\r\n313 312  4.2090618000000e+00\r\n314 312 -6.8189325000000e-01\r\n315 312 -8.0662996000000e+00\r\n358 312  8.6485303000000e+01\r\n359 312 -1.4011138000000e+01\r\n360 312 -8.0385130000000e+00\r\n1416 312 -2.4651397000000e+00\r\n265 313 -2.4185703000000e-02\r\n267 313 -2.5241294000000e-04\r\n310 313 -2.4634877000000e-03\r\n312 313 -2.5710072000000e-05\r\n313 313  5.7490045000000e+02\r\n315 313  1.6813887000000e-03\r\n316 313 -2.6877149000000e-02\r\n318 313 -2.5804428000000e-05\r\n361 313 -3.0468985000000e-01\r\n363 313 -2.5711604000000e-05\r\n1417 313 -4.6162916000000e-02\r\n1419 313 -7.8893794000000e-06\r\n267 314 -4.7371923000000e+00\r\n312 314 -4.7718289000000e+00\r\n313 314 -3.8505782000000e+02\r\n314 314 -1.0928134000000e+02\r\n315 314  2.0498379000000e+01\r\n316 314  1.0447785000000e-01\r\n318 314 -4.7717809000000e+00\r\n361 314  5.4850702000000e+01\r\n363 314 -4.7552271000000e+00\r\n1419 314 -1.4501622000000e+00\r\n267 315 -8.0077441000000e+00\r\n312 315 -8.0662996000000e+00\r\n313 315 -6.5090125000000e+02\r\n314 315  1.0095682000000e+02\r\n315 315  3.4650441000000e+01\r\n316 315  1.7660924000000e-01\r\n317 315 -2.8611716000000e-02\r\n318 315 -8.0662125000000e+00\r\n361 315  9.2719559000000e+01\r\n362 315 -1.5021105000000e+01\r\n363 315 -8.0382301000000e+00\r\n1419 315 -2.4513525000000e+00\r\n268 316 -4.7438329000000e-02\r\n270 316 -4.9508786000000e-04\r\n313 316 -2.4725287000000e-03\r\n315 316 -2.5804428000000e-05\r\n316 316  5.7491829000000e+02\r\n318 316  1.9241236000000e-03\r\n319 316 -2.4623592000000e-03\r\n321 316 -2.5698295000000e-05\r\n364 316 -3.2828139000000e-01\r\n366 316 -2.5763098000000e-05\r\n1420 316 -3.9116784000000e-02\r\n1422 316 -7.9051779000000e-06\r\n270 317 -4.7132973000000e+00\r\n315 317 -4.7717809000000e+00\r\n316 317 -3.8727296000000e+02\r\n317 317 -1.0025400000000e+02\r\n318 317  2.0466586000000e+01\r\n321 317 -4.7712987000000e+00\r\n364 317  5.7167553000000e+01\r\n366 317 -4.7551848000000e+00\r\n1422 317 -1.4428372000000e+00\r\n270 318 -7.9673577000000e+00\r\n315 318 -8.0662125000000e+00\r\n316 318 -6.5464621000000e+02\r\n317 318  1.1682452000000e+02\r\n318 318  3.4596706000000e+01\r\n321 318 -8.0653990000000e+00\r\n364 318  9.6636031000000e+01\r\n365 318 -1.5655569000000e+01\r\n366 318 -8.0381643000000e+00\r\n1422 318 -2.4389721000000e+00\r\n271 319 -2.4093550000000e-03\r\n273 319 -2.5145119000000e-05\r\n316 319 -5.8354240000000e-02\r\n318 319 -2.5698295000000e-05\r\n319 319  5.7493642000000e+02\r\n321 319  1.4537194000000e-03\r\n322 319 -2.4482718000000e-03\r\n324 319 -2.5551272000000e-05\r\n367 319 -3.2882232000000e-01\r\n369 319 -2.5608416000000e-05\r\n1423 319 -4.6988259000000e-02\r\n1425 319 -7.8592885000000e-06\r\n273 320 -4.7614281000000e+00\r\n316 320  3.1989950000000e+00\r\n318 320 -4.7712987000000e+00\r\n319 320 -3.9052649000000e+02\r\n320 320 -1.0928015000000e+02\r\n321 320  2.0521060000000e+01\r\n324 320 -4.7704788000000e+00\r\n367 320  5.7223219000000e+01\r\n369 320 -4.7552192000000e+00\r\n1425 320 -1.4504481000000e+00\r\n273 321 -8.0487133000000e+00\r\n316 321  5.4075782000000e+00\r\n317 321 -8.7606062000000e-01\r\n318 321 -8.0653990000000e+00\r\n319 321 -6.6014561000000e+02\r\n320 321  1.0245752000000e+02\r\n321 321  3.4688785000000e+01\r\n324 321 -8.0640173000000e+00\r\n367 321  9.6730076000000e+01\r\n368 321 -1.5670861000000e+01\r\n369 321 -8.0382181000000e+00\r\n1425 321 -2.4518359000000e+00\r\n274 322 -2.2986769000000e-03\r\n276 322 -2.3990032000000e-05\r\n319 322 -1.3090690000000e-01\r\n321 322 -2.5551272000000e-05\r\n322 322  5.7501910000000e+02\r\n324 322  1.4509787000000e-03\r\n325 322 -2.3278464000000e-03\r\n327 322 -2.4294459000000e-05\r\n370 322 -3.3392357000000e-01\r\n372 322 -2.5481281000000e-05\r\n1426 322 -5.6475911000000e-02\r\n1428 322 -7.8137698000000e-06\r\n276 323 -4.6146947000000e+00\r\n319 323  5.7425527000000e+00\r\n321 323 -4.7704788000000e+00\r\n322 323 -3.9129491000000e+02\r\n323 323 -1.0928448000000e+02\r\n324 323  2.0186025000000e+01\r\n327 323 -4.5718624000000e+00\r\n370 323  5.5453699000000e+01\r\n372 323 -4.7580243000000e+00\r\n1428 323 -1.4587762000000e+00\r\n276 324 -7.8006799000000e+00\r\n319 324  9.7072109000000e+00\r\n320 324 -1.5726313000000e+00\r\n321 324 -8.0640173000000e+00\r\n322 324 -6.6144491000000e+02\r\n323 324  1.0265780000000e+02\r\n324 324  3.4122453000000e+01\r\n327 324 -7.7282720000000e+00\r\n370 324  9.3738933000000e+01\r\n371 324 -1.5186317000000e+01\r\n372 324 -8.0429643000000e+00\r\n1428 324 -2.4659153000000e+00\r\n277 325 -2.0998737000000e-03\r\n279 325 -2.1915232000000e-05\r\n322 325 -1.8420454000000e-01\r\n324 325 -2.4294459000000e-05\r\n325 325  5.2909333000000e+02\r\n327 325  1.3365414000000e-03\r\n328 325 -2.1140734000000e-03\r\n330 325 -2.2063427000000e-05\r\n373 325 -3.2053148000000e-01\r\n375 325 -2.3521242000000e-05\r\n1429 325 -5.7097011000000e-02\r\n1431 325 -8.4205212000000e-06\r\n279 326 -4.2838474000000e+00\r\n322 326  7.9814062000000e+00\r\n324 326 -4.5718624000000e+00\r\n325 326 -3.6183494000000e+02\r\n326 326 -1.0054776000000e+02\r\n327 326  1.9068643000000e+01\r\n330 326 -4.1902376000000e+00\r\n373 326  5.0170634000000e+01\r\n375 326 -4.4269149000000e+00\r\n1431 326 -1.5845640000000e+00\r\n279 327 -7.2414106000000e+00\r\n322 327  1.3491762000000e+01\r\n323 327 -2.1857632000000e+00\r\n324 327 -7.7282720000000e+00\r\n325 327 -6.1164545000000e+02\r\n326 327  9.4936056000000e+01\r\n327 327  3.2233618000000e+01\r\n330 327 -7.0831776000000e+00\r\n373 327  8.4808394000000e+01\r\n374 327 -1.3739575000000e+01\r\n375 327 -7.4832529000000e+00\r\n1431 327 -2.6785451000000e+00\r\n280 328 -1.8771175000000e-03\r\n282 328 -1.9590447000000e-05\r\n325 328 -1.6038550000000e-01\r\n327 328 -2.2063427000000e-05\r\n328 328  4.8305359000000e+02\r\n330 328  1.2210278000000e-03\r\n331 328 -1.9047534000000e-03\r\n333 328 -1.9878868000000e-05\r\n376 328 -2.6610429000000e-01\r\n378 328 -2.1544321000000e-05\r\n1432 328 -5.7996357000000e-02\r\n1434 328 -9.1411352000000e-06\r\n282 329 -3.9008968000000e+00\r\n325 329  8.5022034000000e+00\r\n327 329 -4.1902376000000e+00\r\n328 329 -3.3090803000000e+02\r\n329 329 -9.1807741000000e+01\r\n330 329  1.7737475000000e+01\r\n333 329 -3.8079455000000e+00\r\n376 329  4.5134249000000e+01\r\n378 329 -4.0921523000000e+00\r\n1434 329 -1.7360007000000e+00\r\n282 330 -6.5940759000000e+00\r\n325 330  1.4372125000000e+01\r\n326 330 -2.3283983000000e+00\r\n327 330 -7.0831776000000e+00\r\n328 330 -5.5936694000000e+02\r\n329 330  8.6820392000000e+01\r\n330 330  2.9983424000000e+01\r\n333 330 -6.4369470000000e+00\r\n376 330  7.6294935000000e+01\r\n377 330 -1.2360385000000e+01\r\n378 330 -6.9173742000000e+00\r\n1434 330 -2.9345355000000e+00\r\n283 331 -1.6881784000000e-03\r\n285 331 -1.7618593000000e-05\r\n328 331 -1.2017962000000e-01\r\n330 331 -1.9878868000000e-05\r\n331 331  4.3702283000000e+02\r\n333 331  1.0881647000000e-03\r\n379 331 -2.3734229000000e-01\r\n381 331 -1.9354806000000e-05\r\n1435 331 -5.8560585000000e-02\r\n1437 331 -1.0017061000000e-05\r\n285 332 -3.5694188000000e+00\r\n328 332  7.0459977000000e+00\r\n330 332 -3.8079455000000e+00\r\n331 332 -2.9843639000000e+02\r\n332 332 -8.3065671000000e+01\r\n333 332  1.3013397000000e+01\r\n379 332  4.0527498000000e+01\r\n381 332 -3.7079928000000e+00\r\n1437 332 -1.9187718000000e+00\r\n285 333 -6.0337414000000e+00\r\n328 333  1.1910547000000e+01\r\n329 333 -1.9296126000000e+00\r\n330 333 -6.4369470000000e+00\r\n331 333 -5.0447656000000e+02\r\n332 333  7.8286656000000e+01\r\n333 333  2.1997831000000e+01\r\n379 333  6.8507639000000e+01\r\n380 333 -1.1098836000000e+01\r\n381 333 -6.2679871000000e+00\r\n1437 333 -3.2434895000000e+00\r\n334 334  1.0000000000000e+00\r\n335 335  1.0000000000000e+00\r\n336 336  1.0000000000000e+00\r\n337 337  1.0000000000000e+00\r\n338 338  1.0000000000000e+00\r\n339 339  1.0000000000000e+00\r\n340 340  1.0000000000000e+00\r\n341 341  1.0000000000000e+00\r\n342 342  1.0000000000000e+00\r\n343 343  1.0000000000000e+00\r\n344 344  1.0000000000000e+00\r\n345 345  1.0000000000000e+00\r\n346 346  1.0000000000000e+00\r\n347 347  1.0000000000000e+00\r\n348 348  1.0000000000000e+00\r\n349 349  1.0000000000000e+00\r\n350 350  1.0000000000000e+00\r\n351 351  1.0000000000000e+00\r\n304 352 -2.4443132000000e-03\r\n306 352 -2.5509959000000e-05\r\n352 352  5.7478946000000e+02\r\n354 352  1.4296456000000e-03\r\n355 352 -6.2044278000000e-02\r\n357 352 -2.6688160000000e-05\r\n400 352 -2.2352072000000e-01\r\n402 352 -2.5425414000000e-05\r\n1456 352 -5.6169102000000e-02\r\n1458 352 -8.1663047000000e-06\r\n306 353 -4.7580907000000e+00\r\n352 353 -3.8266089000000e+02\r\n353 353 -1.0030582000000e+02\r\n354 353  1.5551099000000e+01\r\n355 353  3.5517256000000e+00\r\n357 353 -4.7728386000000e+00\r\n400 353  4.9071106000000e+01\r\n402 353 -4.5475998000000e+00\r\n1458 353 -1.4603618000000e+00\r\n306 354 -8.0430765000000e+00\r\n352 354 -6.4684997000000e+02\r\n353 354  1.1543532000000e+02\r\n354 354  2.6287578000000e+01\r\n355 354  6.0038370000000e+00\r\n356 354 -9.7263799000000e-01\r\n357 354 -8.0680064000000e+00\r\n400 354  8.2949797000000e+01\r\n401 354 -1.3438094000000e+01\r\n402 354 -7.6872627000000e+00\r\n1458 354 -2.4685955000000e+00\r\n307 355 -2.4482304000000e-03\r\n309 355 -2.5550840000000e-05\r\n352 355 -2.5572061000000e-03\r\n354 355 -2.6688160000000e-05\r\n355 355  5.7484386000000e+02\r\n357 355  1.4571430000000e-03\r\n358 355 -9.3051196000000e-02\r\n360 355 -2.6770459000000e-05\r\n403 355 -2.4476972000000e-01\r\n405 355 -2.6083358000000e-05\r\n1459 355 -5.5215162000000e-02\r\n1461 355 -8.1907446000000e-06\r\n309 356 -4.7567900000000e+00\r\n354 356 -4.7728386000000e+00\r\n355 356 -3.8785209000000e+02\r\n356 356 -1.0932835000000e+02\r\n357 356  2.0425388000000e+01\r\n358 356  6.5986580000000e+00\r\n360 356 -4.7726485000000e+00\r\n403 356  5.1214427000000e+01\r\n405 356 -4.6507363000000e+00\r\n1461 356 -1.4601662000000e+00\r\n309 357 -8.0408723000000e+00\r\n354 357 -8.0680064000000e+00\r\n355 357 -6.5562483000000e+02\r\n356 357  1.0160568000000e+02\r\n357 357  3.4527060000000e+01\r\n358 357  1.1154366000000e+01\r\n359 357 -1.8070354000000e+00\r\n360 357 -8.0676805000000e+00\r\n403 357  8.6572821000000e+01\r\n404 357 -1.4025016000000e+01\r\n405 357 -7.8616002000000e+00\r\n1461 357 -2.4682635000000e+00\r\n310 358 -2.4546880000000e-03\r\n312 358 -2.5618235000000e-05\r\n355 358 -2.5650918000000e-03\r\n357 358 -2.6770459000000e-05\r\n358 358  5.7493309000000e+02\r\n360 358  1.4582277000000e-03\r\n361 358 -1.1228963000000e-01\r\n363 358 -2.6928272000000e-05\r\n406 358 -3.1656758000000e-01\r\n408 358 -2.6806025000000e-05\r\n1462 358 -5.3682695000000e-02\r\n1464 358 -8.2386264000000e-06\r\n312 359 -4.7553911000000e+00\r\n357 359 -4.7726485000000e+00\r\n358 359 -3.9452018000000e+02\r\n359 359 -1.0932875000000e+02\r\n360 359  2.0524561000000e+01\r\n361 359  6.1930383000000e+00\r\n363 359 -4.7726177000000e+00\r\n406 359  5.8288778000000e+01\r\n408 359 -4.7516012000000e+00\r\n1464 359 -1.4600938000000e+00\r\n312 360 -8.0385130000000e+00\r\n357 360 -8.0676805000000e+00\r\n358 360 -6.6689692000000e+02\r\n359 360  1.0343025000000e+02\r\n360 360  3.4694713000000e+01\r\n361 360  1.0468712000000e+01\r\n362 360 -1.6959515000000e+00\r\n363 360 -8.0676330000000e+00\r\n406 360  9.8531351000000e+01\r\n407 360 -1.5962269000000e+01\r\n408 360 -8.0321067000000e+00\r\n1464 360 -2.4681426000000e+00\r\n313 361 -2.4636345000000e-03\r\n315 361 -2.5711604000000e-05\r\n358 361 -2.5802131000000e-03\r\n360 361 -2.6928272000000e-05\r\n361 361  5.7492132000000e+02\r\n363 361  1.4588529000000e-03\r\n364 361 -5.0668791000000e-02\r\n366 361 -2.7077998000000e-05\r\n409 361 -3.6617143000000e-01\r\n411 361 -2.6972819000000e-05\r\n1465 361 -5.2128653000000e-02\r\n1467 361 -8.2886627000000e-06\r\n315 362 -4.7552271000000e+00\r\n360 362 -4.7726177000000e+00\r\n361 362 -3.9794035000000e+02\r\n362 362 -1.0932680000000e+02\r\n363 362  2.0528588000000e+01\r\n364 362  2.4299921000000e+00\r\n366 362 -4.7727468000000e+00\r\n409 362  6.5469467000000e+01\r\n411 362 -4.7549139000000e+00\r\n1467 362 -1.4608747000000e+00\r\n315 363 -8.0382301000000e+00\r\n360 363 -8.0676330000000e+00\r\n361 363 -6.7267788000000e+02\r\n362 363  1.0437131000000e+02\r\n363 363  3.4701505000000e+01\r\n364 363  4.1076556000000e+00\r\n365 363 -6.6544656000000e-01\r\n366 363 -8.0678453000000e+00\r\n409 363  1.1066951000000e+02\r\n410 363 -1.7928632000000e+01\r\n411 363 -8.0377006000000e+00\r\n1467 363 -2.4694602000000e+00\r\n316 364 -2.4685685000000e-03\r\n318 364 -2.5763098000000e-05\r\n361 364 -2.5945596000000e-03\r\n363 364 -2.7077998000000e-05\r\n364 364  5.7491705000000e+02\r\n366 364  1.4591127000000e-03\r\n367 364 -2.5925027000000e-03\r\n369 364 -2.7056531000000e-05\r\n412 364 -4.0929373000000e-01\r\n414 364 -2.7031042000000e-05\r\n1468 364 -5.1377246000000e-02\r\n1470 364 -8.3065546000000e-06\r\n318 365 -4.7551848000000e+00\r\n363 365 -4.7727468000000e+00\r\n364 365 -3.9975022000000e+02\r\n365 365 -1.0932556000000e+02\r\n366 365  2.0528470000000e+01\r\n369 365 -4.7725660000000e+00\r\n412 365  6.9707805000000e+01\r\n414 365 -4.7549027000000e+00\r\n1470 365 -1.4608630000000e+00\r\n318 366 -8.0381643000000e+00\r\n363 366 -8.0678453000000e+00\r\n364 366 -6.7573777000000e+02\r\n365 366  1.0486962000000e+02\r\n366 366  3.4701317000000e+01\r\n369 366 -8.0675420000000e+00\r\n412 366  1.1783407000000e+02\r\n413 366 -1.9089266000000e+01\r\n414 366 -8.0376875000000e+00\r\n1470 366 -2.4694428000000e+00\r\n319 367 -2.4537472000000e-03\r\n321 367 -2.5608416000000e-05\r\n364 367 -5.7927708000000e-02\r\n366 367 -2.7056531000000e-05\r\n367 367  5.7495935000000e+02\r\n369 367  1.4586587000000e-03\r\n370 367 -2.5753546000000e-03\r\n372 367 -2.6877566000000e-05\r\n415 367 -3.9677260000000e-01\r\n417 367 -2.6960165000000e-05\r\n1471 367 -5.1990619000000e-02\r\n1473 367 -8.2830240000000e-06\r\n321 368 -4.7552192000000e+00\r\n364 368  3.1437670000000e+00\r\n366 368 -4.7725660000000e+00\r\n367 368 -4.0167152000000e+02\r\n368 368 -1.0932652000000e+02\r\n369 368  2.0529394000000e+01\r\n372 368 -4.7721327000000e+00\r\n415 368  6.8486522000000e+01\r\n417 368 -4.7562860000000e+00\r\n1473 368 -1.4609828000000e+00\r\n321 369 -8.0382181000000e+00\r\n364 369  5.3142214000000e+00\r\n365 369 -8.6091209000000e-01\r\n366 369 -8.0675420000000e+00\r\n367 369 -6.7898527000000e+02\r\n368 369  1.0539374000000e+02\r\n369 369  3.4702875000000e+01\r\n372 369 -8.0668130000000e+00\r\n415 369  1.1576957000000e+02\r\n416 369 -1.8754848000000e+01\r\n417 369 -8.0400223000000e+00\r\n1473 369 -2.4696437000000e+00\r\n322 370 -2.4415654000000e-03\r\n324 370 -2.5481281000000e-05\r\n367 370 -1.2610705000000e-01\r\n369 370 -2.6877566000000e-05\r\n370 370  5.7500724000000e+02\r\n372 370  1.4570466000000e-03\r\n373 370 -2.4732826000000e-03\r\n375 370 -2.5812297000000e-05\r\n418 370 -3.7633253000000e-01\r\n420 370 -2.6785208000000e-05\r\n1474 370 -5.3475055000000e-02\r\n1476 370 -8.2253849000000e-06\r\n324 371 -4.7580243000000e+00\r\n367 371  7.5519975000000e+00\r\n369 371 -4.7721327000000e+00\r\n370 371 -4.0178322000000e+02\r\n371 371 -1.0932794000000e+02\r\n372 371  2.0383029000000e+01\r\n375 371 -4.6239093000000e+00\r\n418 371  6.4191733000000e+01\r\n420 371 -4.7564077000000e+00\r\n1476 371 -1.4603466000000e+00\r\n324 372 -8.0429643000000e+00\r\n367 372  1.2765896000000e+01\r\n368 372 -2.0681019000000e+00\r\n369 372 -8.0668130000000e+00\r\n370 372 -6.7917436000000e+02\r\n371 372  1.0542131000000e+02\r\n372 372  3.4455466000000e+01\r\n375 372 -7.8162509000000e+00\r\n418 372  1.0850970000000e+02\r\n419 372 -1.7578799000000e+01\r\n420 372 -8.0402315000000e+00\r\n1476 372 -2.4685699000000e+00\r\n325 373 -2.2537584000000e-03\r\n327 373 -2.3521242000000e-05\r\n370 373 -1.7606838000000e-01\r\n372 373 -2.5812297000000e-05\r\n373 373  5.4055330000000e+02\r\n375 373  1.3706714000000e-03\r\n376 373 -2.2970968000000e-03\r\n378 373 -2.3973542000000e-05\r\n421 373 -3.4175937000000e-01\r\n423 373 -2.5475303000000e-05\r\n1477 373 -5.4844342000000e-02\r\n1479 373 -8.6688503000000e-06\r\n327 374 -4.4269149000000e+00\r\n370 374  9.5580479000000e+00\r\n372 374 -4.6239093000000e+00\r\n373 374 -3.7674337000000e+02\r\n374 374 -1.0277157000000e+02\r\n375 374  1.9517038000000e+01\r\n378 374 -4.3377454000000e+00\r\n421 374  5.6952369000000e+01\r\n423 374 -4.5641563000000e+00\r\n1479 374 -1.5528349000000e+00\r\n327 375 -7.4832529000000e+00\r\n370 375  1.6156913000000e+01\r\n371 375 -2.6174681000000e+00\r\n372 375 -7.8162509000000e+00\r\n373 375 -6.3684655000000e+02\r\n374 375  9.8833318000000e+01\r\n375 375  3.2991584000000e+01\r\n378 375 -7.3325248000000e+00\r\n421 375  9.6272217000000e+01\r\n422 375 -1.5596386000000e+01\r\n423 375 -7.7152444000000e+00\r\n1479 375 -2.6249103000000e+00\r\n328 376 -2.0643337000000e-03\r\n330 376 -2.1544321000000e-05\r\n373 376 -1.9807344000000e-01\r\n375 376 -2.3973542000000e-05\r\n376 376  5.0605598000000e+02\r\n378 376  1.2828126000000e-03\r\n379 376 -2.1007017000000e-03\r\n381 376 -2.1923874000000e-05\r\n424 376 -2.9231577000000e-01\r\n426 376 -2.3634552000000e-05\r\n1480 376 -5.6318974000000e-02\r\n1482 376 -9.1602712000000e-06\r\n330 377 -4.0921523000000e+00\r\n373 377  1.0116997000000e+01\r\n375 377 -4.3377454000000e+00\r\n376 377 -3.4911006000000e+02\r\n377 377 -9.6216272000000e+01\r\n378 377  1.8374990000000e+01\r\n381 377 -4.0000020000000e+00\r\n424 377  4.8568136000000e+01\r\n426 377 -4.2769539000000e+00\r\n1482 377 -1.6573901000000e+00\r\n330 378 -6.9173742000000e+00\r\n373 378  1.7101772000000e+01\r\n374 378 -2.7705515000000e+00\r\n375 378 -7.3325248000000e+00\r\n376 378 -5.9013565000000e+02\r\n377 378  9.1532256000000e+01\r\n378 378  3.1061078000000e+01\r\n381 378 -6.7615985000000e+00\r\n424 378  8.2099576000000e+01\r\n425 378 -1.3300440000000e+01\r\n426 378 -7.2297629000000e+00\r\n1482 378 -2.8016522000000e+00\r\n331 379 -1.8545388000000e-03\r\n333 379 -1.9354806000000e-05\r\n376 379 -1.3037112000000e-01\r\n378 379 -2.1923874000000e-05\r\n379 379  4.5988358000000e+02\r\n381 379  1.1474481000000e-03\r\n427 379 -1.4544903000000e-01\r\n429 379 -2.1098457000000e-05\r\n1483 379 -5.7318543000000e-02\r\n1485 379 -1.0010604000000e-05\r\n333 380 -3.7079928000000e+00\r\n376 380  7.7991083000000e+00\r\n378 380 -4.0000020000000e+00\r\n379 380 -3.0975874000000e+02\r\n380 380 -8.7470802000000e+01\r\n381 380  1.3394024000000e+01\r\n427 380  3.7938706000000e+01\r\n429 380 -3.8499013000000e+00\r\n1485 380 -1.8263584000000e+00\r\n333 381 -6.2679871000000e+00\r\n376 381  1.3183603000000e+01\r\n377 381 -2.1358043000000e+00\r\n378 381 -6.7615985000000e+00\r\n379 381 -5.2361580000000e+02\r\n380 381  8.1123098000000e+01\r\n381 381  2.2641243000000e+01\r\n427 381  6.4131542000000e+01\r\n428 381 -1.0389604000000e+01\r\n429 381 -6.5078683000000e+00\r\n1485 381 -3.0872741000000e+00\r\n382 382  1.0000000000000e+00\r\n383 383  1.0000000000000e+00\r\n384 384  1.0000000000000e+00\r\n385 385  1.0000000000000e+00\r\n386 386  1.0000000000000e+00\r\n387 387  1.0000000000000e+00\r\n388 388  1.0000000000000e+00\r\n389 389  1.0000000000000e+00\r\n390 390  1.0000000000000e+00\r\n391 391  1.0000000000000e+00\r\n392 392  1.0000000000000e+00\r\n393 393  1.0000000000000e+00\r\n394 394  1.0000000000000e+00\r\n395 395  1.0000000000000e+00\r\n396 396  1.0000000000000e+00\r\n397 397  5.0551705000000e+02\r\n399 397  1.2406478000000e-03\r\n400 397 -2.4057914000000e-03\r\n402 397 -2.5107928000000e-05\r\n445 397 -2.2066738000000e-03\r\n447 397 -2.3029846000000e-05\r\n1501 397 -5.7686407000000e-02\r\n1503 397 -9.9051999000000e-06\r\n397 398 -3.1019601000000e+02\r\n398 398 -9.6262683000000e+01\r\n399 398  9.7862578000000e+00\r\n402 398 -4.2940391000000e+00\r\n445 398  1.9835020000000e+01\r\n447 398 -3.8097221000000e+00\r\n1503 398 -1.6717298000000e+00\r\n397 399 -5.2435500000000e+02\r\n398 399  8.0758997000000e+01\r\n399 399  1.6542684000000e+01\r\n402 399 -7.2586437000000e+00\r\n445 399  3.3529096000000e+01\r\n446 399 -5.4316301000000e+00\r\n447 399 -6.4399502000000e+00\r\n1503 399 -2.8258900000000e+00\r\n352 400 -2.4362123000000e-03\r\n354 400 -2.5425414000000e-05\r\n397 400 -7.4876051000000e-02\r\n399 400 -2.5107928000000e-05\r\n400 400  5.2865880000000e+02\r\n402 400  1.3461324000000e-03\r\n403 400 -7.3997074000000e-02\r\n405 400 -2.6227671000000e-05\r\n448 400 -8.4434598000000e-03\r\n450 400 -2.3686270000000e-05\r\n1504 400 -5.6046068000000e-02\r\n1506 400 -9.3289205000000e-06\r\n354 401 -4.5475998000000e+00\r\n397 401  1.3837884000000e+01\r\n399 401 -4.2940391000000e+00\r\n400 401 -3.5889487000000e+02\r\n401 401 -1.0062627000000e+02\r\n402 401  1.8984973000000e+01\r\n403 401  4.3310283000000e+00\r\n405 401 -4.4853735000000e+00\r\n448 401  3.7150315000000e+01\r\n450 401 -4.0513848000000e+00\r\n1506 401 -1.5953249000000e+00\r\n354 402 -7.6872627000000e+00\r\n397 402  2.3391558000000e+01\r\n398 402 -3.7894005000000e+00\r\n399 402 -7.2586437000000e+00\r\n400 402 -6.0667588000000e+02\r\n401 402  9.3934360000000e+01\r\n402 402  3.2092198000000e+01\r\n403 402  7.3211702000000e+00\r\n404 402 -1.1860196000000e+00\r\n405 402 -7.5820754000000e+00\r\n448 402  6.2798893000000e+01\r\n449 402 -1.0173335000000e+01\r\n450 402 -6.8484609000000e+00\r\n1506 402 -2.6967372000000e+00\r\n355 403 -2.4992552000000e-03\r\n357 403 -2.6083358000000e-05\r\n400 403 -2.5130830000000e-03\r\n402 403 -2.6227671000000e-05\r\n403 403  5.5177232000000e+02\r\n405 403  1.4044010000000e-03\r\n406 403 -1.5668612000000e-01\r\n408 403 -2.7455381000000e-05\r\n451 403 -1.3782599000000e-01\r\n453 403 -2.5552152000000e-05\r\n1507 403 -5.3265675000000e-02\r\n1509 403 -8.9667033000000e-06\r\n357 404 -4.6507363000000e+00\r\n402 404 -4.4853735000000e+00\r\n403 404 -3.7906662000000e+02\r\n404 404 -1.0500044000000e+02\r\n405 404  1.9704360000000e+01\r\n406 404  1.2333979000000e+01\r\n408 404 -4.6764159000000e+00\r\n451 404  4.9956892000000e+01\r\n453 404 -4.3529070000000e+00\r\n1509 404 -1.5271880000000e+00\r\n357 405 -7.8616002000000e+00\r\n402 405 -7.5820754000000e+00\r\n403 405 -6.4077381000000e+02\r\n404 405  9.9271279000000e+01\r\n405 405  3.3308234000000e+01\r\n406 405  2.0849344000000e+01\r\n407 405 -3.3775593000000e+00\r\n408 405 -7.9050080000000e+00\r\n451 405  8.4447076000000e+01\r\n452 405 -1.3680288000000e+01\r\n453 405 -7.3581490000000e+00\r\n1509 405 -2.5815568000000e+00\r\n358 406 -2.5684997000000e-03\r\n360 406 -2.6806025000000e-05\r\n403 406 -2.6307197000000e-03\r\n405 406 -2.7455381000000e-05\r\n406 406  5.7492296000000e+02\r\n408 406  1.4624084000000e-03\r\n409 406 -1.6198256000000e-01\r\n411 406 -2.8322849000000e-05\r\n454 406 -3.1386583000000e-01\r\n456 406 -2.7259136000000e-05\r\n1510 406 -4.8974647000000e-02\r\n1512 406 -8.6838251000000e-06\r\n360 407 -4.7516012000000e+00\r\n405 407 -4.6764159000000e+00\r\n406 407 -4.0792812000000e+02\r\n407 407 -1.0937761000000e+02\r\n408 407  2.0272988000000e+01\r\n409 407  1.3362148000000e+01\r\n411 407 -4.7738776000000e+00\r\n454 407  6.4594518000000e+01\r\n456 407 -4.5952814000000e+00\r\n1512 407 -1.4635822000000e+00\r\n360 408 -8.0321067000000e+00\r\n405 408 -7.9050080000000e+00\r\n406 408 -6.8956168000000e+02\r\n407 408  1.0697965000000e+02\r\n408 408  3.4269454000000e+01\r\n409 408  2.2587375000000e+01\r\n410 408 -3.6590933000000e+00\r\n411 408 -8.0697626000000e+00\r\n454 408  1.0919057000000e+02\r\n455 408 -1.7688576000000e+01\r\n456 408 -7.7678636000000e+00\r\n1512 408 -2.4740393000000e+00\r\n361 409 -2.5844816000000e-03\r\n363 409 -2.6972819000000e-05\r\n406 409 -2.7138387000000e-03\r\n408 409 -2.8322849000000e-05\r\n409 409  5.7507018000000e+02\r\n411 409  1.4650380000000e-03\r\n412 409 -9.4098850000000e-02\r\n414 409 -2.8635332000000e-05\r\n457 409 -5.3819792000000e-01\r\n459 409 -2.8456061000000e-05\r\n1513 409 -4.3304230000000e-02\r\n1515 409 -8.7599193000000e-06\r\n363 410 -4.7549139000000e+00\r\n408 410 -4.7738776000000e+00\r\n409 410 -4.1669717000000e+02\r\n410 410 -1.0938061000000e+02\r\n411 410  2.0519955000000e+01\r\n412 410  6.6853787000000e+00\r\n414 410 -4.7738909000000e+00\r\n457 410  8.0044732000000e+01\r\n459 410 -4.7447320000000e+00\r\n1515 410 -1.4603090000000e+00\r\n363 411 -8.0377006000000e+00\r\n408 411 -8.0697626000000e+00\r\n409 411 -7.0438450000000e+02\r\n410 411  1.0937287000000e+02\r\n411 411  3.4686913000000e+01\r\n412 411  1.1300958000000e+01\r\n413 411 -1.8307135000000e+00\r\n414 411 -8.0697798000000e+00\r\n457 411  1.3530754000000e+02\r\n458 411 -2.1919324000000e+01\r\n459 411 -8.0204896000000e+00\r\n1515 411 -2.4685050000000e+00\r\n364 412 -2.5900604000000e-03\r\n366 412 -2.7031042000000e-05\r\n409 412 -2.7437802000000e-03\r\n411 412 -2.8635332000000e-05\r\n412 412  5.7506595000000e+02\r\n414 412  1.4657043000000e-03\r\n415 412 -2.7497649000000e-03\r\n417 412 -2.8697790000000e-05\r\n460 412 -6.2907866000000e-01\r\n462 412 -2.8632140000000e-05\r\n1516 412 -3.9838055000000e-02\r\n1518 412 -8.8100746000000e-06\r\n366 413 -4.7549027000000e+00\r\n411 413 -4.7738909000000e+00\r\n412 413 -4.1895970000000e+02\r\n413 413 -1.0938104000000e+02\r\n414 413  2.0522181000000e+01\r\n417 413 -4.7738956000000e+00\r\n460 413  8.8993349000000e+01\r\n462 413 -4.7469534000000e+00\r\n1518 413 -1.4603067000000e+00\r\n366 414 -8.0376875000000e+00\r\n411 414 -8.0697798000000e+00\r\n412 414 -7.0820948000000e+02\r\n413 414  1.0999085000000e+02\r\n414 414  3.4690686000000e+01\r\n417 414 -8.0697896000000e+00\r\n460 414  1.5043436000000e+02\r\n461 414 -2.4369717000000e+01\r\n462 414 -8.0242501000000e+00\r\n1518 414 -2.4685025000000e+00\r\n367 415 -2.5832691000000e-03\r\n369 415 -2.6960165000000e-05\r\n412 415 -7.0760107000000e-02\r\n414 415 -2.8697790000000e-05\r\n415 415  5.7510738000000e+02\r\n417 415  1.4652996000000e-03\r\n418 415 -2.7223071000000e-03\r\n420 415 -2.8411228000000e-05\r\n463 415 -6.0098619000000e-01\r\n465 415 -2.8563549000000e-05\r\n1519 415 -4.1964468000000e-02\r\n1521 415 -8.7739954000000e-06\r\n369 416 -4.7562860000000e+00\r\n412 416  4.3901562000000e+00\r\n414 416 -4.7738956000000e+00\r\n415 416 -4.1833130000000e+02\r\n416 416 -1.0938150000000e+02\r\n417 416  2.0527906000000e+01\r\n420 416 -4.7737187000000e+00\r\n463 416  8.3975321000000e+01\r\n465 416 -4.7522972000000e+00\r\n1521 416 -1.4594767000000e+00\r\n369 417 -8.0400223000000e+00\r\n412 417  7.4211168000000e+00\r\n413 417 -1.2021920000000e+00\r\n414 417 -8.0697896000000e+00\r\n415 417 -7.0714692000000e+02\r\n416 417  1.0981801000000e+02\r\n417 417  3.4700360000000e+01\r\n420 417 -8.0694940000000e+00\r\n463 417  1.4195182000000e+02\r\n464 417 -2.2995641000000e+01\r\n465 417 -8.0332795000000e+00\r\n1521 417 -2.4670980000000e+00\r\n370 418 -2.5665051000000e-03\r\n372 418 -2.6785208000000e-05\r\n415 418 -1.4676595000000e-01\r\n417 418 -2.8411228000000e-05\r\n418 418  5.7507029000000e+02\r\n420 418  1.4638510000000e-03\r\n421 418 -2.6614878000000e-03\r\n423 418 -2.7776491000000e-05\r\n466 418 -4.8044860000000e-01\r\n468 418 -2.8301956000000e-05\r\n1522 418 -4.6530041000000e-02\r\n1524 418 -8.6924355000000e-06\r\n372 419 -4.7564077000000e+00\r\n415 419  1.1865530000000e+01\r\n417 419 -4.7737187000000e+00\r\n418 419 -4.1626645000000e+02\r\n419 419 -1.0937908000000e+02\r\n420 419  2.0483830000000e+01\r\n423 419 -4.7250120000000e+00\r\n466 419  7.4431540000000e+01\r\n468 419 -4.7560321000000e+00\r\n1524 419 -1.4604292000000e+00\r\n372 420 -8.0402315000000e+00\r\n415 420  2.0057491000000e+01\r\n416 420 -3.2492529000000e+00\r\n417 420 -8.0694940000000e+00\r\n418 420 -7.0365680000000e+02\r\n419 420  1.0925919000000e+02\r\n420 420  3.4625861000000e+01\r\n423 420 -7.9871544000000e+00\r\n466 420  1.2581907000000e+02\r\n467 420 -2.0382310000000e+01\r\n468 420 -8.0395966000000e+00\r\n1524 420 -2.4687096000000e+00\r\n373 421 -2.4409926000000e-03\r\n375 421 -2.5475303000000e-05\r\n418 421 -2.0002262000000e-01\r\n420 421 -2.7776491000000e-05\r\n421 421  5.6352835000000e+02\r\n423 421  1.4329259000000e-03\r\n424 421 -2.5152802000000e-03\r\n426 421 -2.6250602000000e-05\r\n469 421 -3.6799836000000e-01\r\n471 421 -2.7663830000000e-05\r\n1525 421 -5.0662846000000e-02\r\n1527 421 -8.7673732000000e-06\r\n375 422 -4.5641563000000e+00\r\n418 422  1.4573841000000e+01\r\n420 422 -4.7250120000000e+00\r\n421 422 -4.0302041000000e+02\r\n422 422 -1.0719043000000e+02\r\n423 422  2.0027838000000e+01\r\n426 422 -4.5288581000000e+00\r\n469 422  6.5074723000000e+01\r\n471 422 -4.7065101000000e+00\r\n1527 422 -1.4913157000000e+00\r\n375 423 -7.7152444000000e+00\r\n418 423  2.4635603000000e+01\r\n419 423 -3.9909248000000e+00\r\n420 423 -7.9871544000000e+00\r\n421 423 -6.8126520000000e+02\r\n422 423  1.0573024000000e+02\r\n423 423  3.3855038000000e+01\r\n426 423 -7.6555817000000e+00\r\n469 423  1.1000223000000e+02\r\n470 423 -1.7820172000000e+01\r\n471 423 -7.9558789000000e+00\r\n1527 423 -2.5209182000000e+00\r\n376 424 -2.2646155000000e-03\r\n378 424 -2.3634552000000e-05\r\n421 424 -2.3641910000000e-01\r\n423 424 -2.6250602000000e-05\r\n424 424  5.2896125000000e+02\r\n426 424  1.3447081000000e-03\r\n427 424 -2.2650799000000e-03\r\n429 424 -2.3639399000000e-05\r\n472 424 -2.2590056000000e-01\r\n474 424 -2.5613009000000e-05\r\n1528 424 -5.3706823000000e-02\r\n1530 424 -9.2257162000000e-06\r\n378 425 -4.2769539000000e+00\r\n421 425  1.5644070000000e+01\r\n423 425 -4.5288581000000e+00\r\n424 425 -3.7281321000000e+02\r\n425 425 -1.0062862000000e+02\r\n426 425  1.8965360000000e+01\r\n429 425 -4.1372028000000e+00\r\n472 425  5.3596444000000e+01\r\n474 425 -4.4195152000000e+00\r\n1530 425 -1.5915783000000e+00\r\n378 426 -7.2297629000000e+00\r\n421 426  2.6444736000000e+01\r\n422 426 -4.2840328000000e+00\r\n423 426 -7.6555817000000e+00\r\n424 426 -6.3020345000000e+02\r\n425 426  9.7740717000000e+01\r\n426 426  3.2059040000000e+01\r\n429 426 -6.9935225000000e+00\r\n472 426  9.0599428000000e+01\r\n473 426 -1.4677058000000e+01\r\n474 426 -7.4707486000000e+00\r\n1530 426 -2.6904039000000e+00\r\n379 427 -2.0216120000000e-03\r\n381 427 -2.1098457000000e-05\r\n424 427 -2.6132781000000e-01\r\n426 427 -2.3639399000000e-05\r\n427 427  4.7136634000000e+02\r\n429 427  1.1796732000000e-03\r\n475 427 -5.1081988000000e-02\r\n477 427 -2.2804627000000e-05\r\n1531 427 -5.5373045000000e-02\r\n1533 427 -1.0189061000000e-05\r\n381 428 -3.8499013000000e+00\r\n424 428  1.4276224000000e+01\r\n426 428 -4.1372028000000e+00\r\n427 428 -3.1413612000000e+02\r\n428 428 -8.9695520000000e+01\r\n429 428  1.3771905000000e+01\r\n475 428  2.9290310000000e+01\r\n477 428 -3.9916066000000e+00\r\n1533 428 -1.7831636000000e+00\r\n381 429 -6.5078683000000e+00\r\n424 429  2.4132512000000e+01\r\n425 429 -3.9094881000000e+00\r\n426 429 -6.9935225000000e+00\r\n427 429 -5.3101534000000e+02\r\n428 429  8.2134742000000e+01\r\n429 429  2.3280012000000e+01\r\n475 429  4.9512306000000e+01\r\n476 429 -8.0210370000000e+00\r\n477 429 -6.7474068000000e+00\r\n1533 429 -3.0142581000000e+00\r\n430 430  1.0000000000000e+00\r\n431 431  1.0000000000000e+00\r\n432 432  1.0000000000000e+00\r\n433 433  1.0000000000000e+00\r\n434 434  1.0000000000000e+00\r\n435 435  1.0000000000000e+00\r\n436 436  1.0000000000000e+00\r\n437 437  1.0000000000000e+00\r\n438 438  1.0000000000000e+00\r\n439 439  1.0000000000000e+00\r\n440 440  1.0000000000000e+00\r\n441 441  1.0000000000000e+00\r\n442 442  1.0000000000000e+00\r\n443 443  1.0000000000000e+00\r\n444 444  1.0000000000000e+00\r\n397 445 -1.8958112000000e-01\r\n399 445 -2.3029846000000e-05\r\n445 445  4.2537296000000e+02\r\n447 445  1.0715340000000e-03\r\n448 445 -1.2628141000000e-01\r\n450 445 -2.2183240000000e-05\r\n493 445 -1.9073349000000e-03\r\n495 445 -1.9905810000000e-05\r\n1549 445 -5.7003955000000e-02\r\n1551 445 -1.1969802000000e-05\r\n399 446 -3.8097221000000e+00\r\n445 446 -2.6914069000000e+02\r\n446 446 -8.0988821000000e+01\r\n447 446  1.2675962000000e+01\r\n448 446  2.7187583000000e+00\r\n450 446 -3.6700656000000e+00\r\n493 446  2.2310249000000e+01\r\n495 446 -3.2068077000000e+00\r\n1551 446 -1.9802948000000e+00\r\n399 447 -6.4399502000000e+00\r\n445 447 -4.5495508000000e+02\r\n446 447  7.0082321000000e+01\r\n447 447  2.1427431000000e+01\r\n448 447  4.5957857000000e+00\r\n449 447 -7.4449701000000e-01\r\n450 447 -6.2038744000000e+00\r\n493 447  3.7713218000000e+01\r\n494 447 -6.1093750000000e+00\r\n495 447 -5.4207838000000e+00\r\n1551 447 -3.3474880000000e+00\r\n400 448 -2.2695710000000e-03\r\n402 448 -2.3686270000000e-05\r\n445 448 -2.1255537000000e-03\r\n447 448 -2.2183240000000e-05\r\n448 448  4.5971170000000e+02\r\n450 448  1.1786059000000e-03\r\n451 448 -1.8440792000000e-01\r\n453 448 -2.4261411000000e-05\r\n496 448 -2.1320279000000e-03\r\n498 448 -2.2250808000000e-05\r\n1552 448 -5.4499852000000e-02\r\n1554 448 -1.1137754000000e-05\r\n402 449 -4.0513848000000e+00\r\n447 449 -3.6700656000000e+00\r\n448 449 -3.0965220000000e+02\r\n449 449 -8.7547250000000e+01\r\n450 449  1.7112696000000e+01\r\n451 449  1.3093529000000e+01\r\n453 449 -4.0014572000000e+00\r\n496 449  3.2643080000000e+01\r\n498 449 -3.5431100000000e+00\r\n1554 449 -1.8368744000000e+00\r\n402 450 -6.8484609000000e+00\r\n447 450 -6.2038744000000e+00\r\n448 450 -5.2343607000000e+02\r\n449 450  8.0902187000000e+01\r\n450 450  2.8927296000000e+01\r\n451 450  2.2133302000000e+01\r\n452 450 -3.5854881000000e+00\r\n453 450 -6.7640633000000e+00\r\n496 450  5.5179862000000e+01\r\n497 450 -8.9388715000000e+00\r\n498 450 -5.9892731000000e+00\r\n1554 450 -3.1050525000000e+00\r\n403 451 -2.4483561000000e-03\r\n405 451 -2.5552152000000e-05\r\n448 451 -2.3246798000000e-03\r\n450 451 -2.4261411000000e-05\r\n451 451  5.0591618000000e+02\r\n453 451  1.2930679000000e-03\r\n454 451 -3.0440354000000e-01\r\n456 451 -2.6645486000000e-05\r\n499 451 -1.4649951000000e-01\r\n501 451 -2.3763460000000e-05\r\n1555 451 -4.8561085000000e-02\r\n1557 451 -1.0237645000000e-05\r\n405 452 -4.3529070000000e+00\r\n450 452 -4.0014572000000e+00\r\n451 452 -3.6019235000000e+02\r\n452 452 -9.6302513000000e+01\r\n453 452  1.8242362000000e+01\r\n454 452  2.2638721000000e+01\r\n456 452 -4.3393966000000e+00\r\n499 452  4.7247510000000e+01\r\n501 452 -3.8706427000000e+00\r\n1557 452 -1.6671745000000e+00\r\n405 453 -7.3581490000000e+00\r\n450 453 -6.7640633000000e+00\r\n451 453 -6.0886882000000e+02\r\n452 453  9.4350579000000e+01\r\n453 453  3.0836875000000e+01\r\n454 453  3.8268474000000e+01\r\n455 453 -6.1992643000000e+00\r\n456 453 -7.3353123000000e+00\r\n499 453  7.9867150000000e+01\r\n500 453 -1.2938001000000e+01\r\n501 453 -6.5429310000000e+00\r\n1557 453 -2.8181894000000e+00\r\n406 454 -2.6119159000000e-03\r\n408 454 -2.7259136000000e-05\r\n451 454 -2.5531172000000e-03\r\n453 454 -2.6645486000000e-05\r\n454 454  5.4060151000000e+02\r\n456 454  1.3826741000000e-03\r\n457 454 -3.6581696000000e-01\r\n459 454 -2.8986084000000e-05\r\n502 454 -3.2336120000000e-01\r\n504 454 -2.6733988000000e-05\r\n1558 454 -3.7939151000000e-02\r\n1560 454 -9.7877547000000e-06\r\n408 455 -4.5952814000000e+00\r\n453 455 -4.3393966000000e+00\r\n454 455 -4.0561228000000e+02\r\n455 455 -1.0287077000000e+02\r\n456 455  1.9402726000000e+01\r\n457 455  2.5964243000000e+01\r\n459 455 -4.6265250000000e+00\r\n502 455  6.9551885000000e+01\r\n504 455 -4.2678508000000e+00\r\n1560 455 -1.5621511000000e+00\r\n408 456 -7.7678636000000e+00\r\n453 456 -7.3353123000000e+00\r\n454 456 -6.8564699000000e+02\r\n455 456  1.0648907000000e+02\r\n456 456  3.2798363000000e+01\r\n457 456  4.3889957000000e+01\r\n458 456 -7.1098200000000e+00\r\n459 456 -7.8206778000000e+00\r\n502 456  1.1757051000000e+02\r\n503 456 -1.9045476000000e+01\r\n504 456 -7.2143749000000e+00\r\n1560 456 -2.6406602000000e+00\r\n409 457 -2.7266028000000e-03\r\n411 457 -2.8456061000000e-05\r\n454 457 -2.7773886000000e-03\r\n456 457 -2.8986084000000e-05\r\n457 457  5.7512809000000e+02\r\n459 457  1.4710524000000e-03\r\n460 457 -1.8542539000000e-01\r\n462 457 -3.0563854000000e-05\r\n505 457 -5.8596145000000e-01\r\n507 457 -2.9723276000000e-05\r\n1561 457 -2.3834622000000e-02\r\n1563 457 -9.4021289000000e-06\r\n411 458 -4.7447320000000e+00\r\n456 458 -4.6265250000000e+00\r\n457 458 -4.4592885000000e+02\r\n458 458 -1.0943785000000e+02\r\n459 458  2.0272320000000e+01\r\n460 458  1.5650290000000e+01\r\n462 458 -4.7751626000000e+00\r\n505 458  1.0039086000000e+02\r\n507 458 -4.6448017000000e+00\r\n1563 458 -1.4688418000000e+00\r\n411 459 -8.0204896000000e+00\r\n456 459 -7.8206778000000e+00\r\n457 459 -7.5379764000000e+02\r\n458 459  1.1723273000000e+02\r\n459 459  3.4268312000000e+01\r\n460 459  2.6455233000000e+01\r\n461 459 -4.2854807000000e+00\r\n462 459 -8.0719295000000e+00\r\n505 459  1.6970060000000e+02\r\n506 459 -2.7489782000000e+01\r\n507 459 -7.8515677000000e+00\r\n1563 459 -2.4829287000000e+00\r\n412 460 -2.7434744000000e-03\r\n414 460 -2.8632140000000e-05\r\n457 460 -2.9285674000000e-03\r\n459 460 -3.0563854000000e-05\r\n460 460  5.7520322000000e+02\r\n462 460  1.4740832000000e-03\r\n463 460 -2.9416280000000e-03\r\n465 460 -3.0700161000000e-05\r\n508 460 -8.5968395000000e-01\r\n510 460 -3.0749960000000e-05\r\n1564 460 -1.1791679000000e-02\r\n1566 460 -9.5039760000000e-06\r\n414 461 -4.7469534000000e+00\r\n459 461 -4.7751626000000e+00\r\n460 461 -4.5529778000000e+02\r\n461 461 -1.0944174000000e+02\r\n462 461  2.0525033000000e+01\r\n465 461 -4.7749737000000e+00\r\n508 461  1.2541576000000e+02\r\n510 461 -4.7484940000000e+00\r\n1566 461 -1.4671910000000e+00\r\n414 462 -8.0242501000000e+00\r\n459 462 -8.0719295000000e+00\r\n460 462 -7.6963537000000e+02\r\n461 462  1.1978744000000e+02\r\n462 462  3.4695505000000e+01\r\n465 462 -8.0716104000000e+00\r\n508 462  2.1200280000000e+02\r\n509 462 -3.4342032000000e+01\r\n510 462 -8.0268543000000e+00\r\n1566 462 -2.4801396000000e+00\r\n415 463 -2.7369021000000e-03\r\n417 463 -2.8563549000000e-05\r\n460 463 -9.9876087000000e-02\r\n462 463 -3.0700161000000e-05\r\n463 463  5.7516494000000e+02\r\n465 463  1.4732997000000e-03\r\n466 463 -2.8922477000000e-03\r\n468 463 -3.0184806000000e-05\r\n511 463 -7.1220218000000e-01\r\n513 463 -3.0505978000000e-05\r\n1567 463 -2.0158733000000e-02\r\n1569 463 -9.4187340000000e-06\r\n417 464 -4.7522972000000e+00\r\n460 464  9.5332522000000e+00\r\n462 464 -4.7749737000000e+00\r\n463 464 -4.4573274000000e+02\r\n464 464 -1.0943806000000e+02\r\n465 464  2.0524459000000e+01\r\n468 464 -4.7743924000000e+00\r\n511 464  1.0631215000000e+02\r\n513 464 -4.7456943000000e+00\r\n1569 464 -1.4648449000000e+00\r\n417 465 -8.0332795000000e+00\r\n460 465  1.6114999000000e+01\r\n461 465 -2.6104598000000e+00\r\n462 465 -8.0716104000000e+00\r\n463 465 -7.5346616000000e+02\r\n464 465  1.1717810000000e+02\r\n465 465  3.4694530000000e+01\r\n468 465 -8.0706327000000e+00\r\n511 465  1.7970995000000e+02\r\n512 465 -2.9111112000000e+01\r\n513 465 -8.0221160000000e+00\r\n1569 465 -2.4761723000000e+00\r\n418 466 -2.7118368000000e-03\r\n420 466 -2.8301956000000e-05\r\n463 466 -2.6835624000000e-01\r\n465 466 -3.0184806000000e-05\r\n466 466  5.7520815000000e+02\r\n468 466  1.4712649000000e-03\r\n469 466 -2.8382956000000e-03\r\n471 466 -2.9621737000000e-05\r\n514 466 -5.6931617000000e-01\r\n516 466 -3.0004439000000e-05\r\n1570 466 -3.3098183000000e-02\r\n1572 466 -9.2428001000000e-06\r\n420 467 -4.7560321000000e+00\r\n463 467  2.1512569000000e+01\r\n465 467 -4.7743924000000e+00\r\n466 467 -4.3681580000000e+02\r\n467 467 -1.0943408000000e+02\r\n468 467  2.0524231000000e+01\r\n471 467 -4.7731085000000e+00\r\n514 467  8.5410030000000e+01\r\n516 467 -4.7465937000000e+00\r\n1572 467 -1.4618491000000e+00\r\n420 468 -8.0395966000000e+00\r\n463 468  3.6364846000000e+01\r\n464 468 -5.8907798000000e+00\r\n465 468 -8.0706327000000e+00\r\n466 468 -7.3839342000000e+02\r\n467 468  1.1474748000000e+02\r\n468 468  3.4694155000000e+01\r\n471 468 -8.0684581000000e+00\r\n514 468  1.4437711000000e+02\r\n515 468 -2.3387800000000e+01\r\n516 468 -8.0236419000000e+00\r\n1572 468 -2.4711096000000e+00\r\n421 469 -2.6506929000000e-03\r\n423 469 -2.7663830000000e-05\r\n466 469 -3.1107453000000e-01\r\n468 469 -2.9621737000000e-05\r\n469 469  5.7514268000000e+02\r\n471 469  1.4678365000000e-03\r\n472 469 -2.6956843000000e-03\r\n474 469 -2.8133381000000e-05\r\n517 469 -4.4832657000000e-01\r\n519 469 -2.9452477000000e-05\r\n1573 469 -4.3135835000000e-02\r\n1575 469 -9.0771279000000e-06\r\n423 470 -4.7065101000000e+00\r\n466 470  2.3423199000000e+01\r\n468 470 -4.7731085000000e+00\r\n469 470 -4.2683226000000e+02\r\n470 470 -1.0943152000000e+02\r\n471 470  2.0326504000000e+01\r\n474 470 -4.6255575000000e+00\r\n517 470  7.3511831000000e+01\r\n519 470 -4.7465231000000e+00\r\n1575 470 -1.4625507000000e+00\r\n423 471 -7.9558789000000e+00\r\n466 471  3.9594554000000e+01\r\n467 471 -6.4140399000000e+00\r\n468 471 -8.0684581000000e+00\r\n469 471 -7.2151684000000e+02\r\n470 471  1.1202164000000e+02\r\n471 471  3.4359905000000e+01\r\n474 471 -7.8190422000000e+00\r\n517 471  1.2426433000000e+02\r\n518 471 -2.0129948000000e+01\r\n519 471 -8.0235181000000e+00\r\n1575 471 -2.4722944000000e+00\r\n424 472 -2.4541873000000e-03\r\n426 472 -2.5613009000000e-05\r\n469 472 -3.6670428000000e-01\r\n471 472 -2.8133381000000e-05\r\n472 472  5.4076809000000e+02\r\n474 472  1.3791015000000e-03\r\n475 472 -2.4187469000000e-03\r\n477 472 -2.5243137000000e-05\r\n520 472 -4.7462177000000e-01\r\n522 472 -2.7428044000000e-05\r\n1576 472 -4.8717647000000e-02\r\n1578 472 -9.4536151000000e-06\r\n426 473 -4.4195152000000e+00\r\n469 473  2.3835402000000e+01\r\n471 473 -4.6255575000000e+00\r\n472 473 -4.0613436000000e+02\r\n473 473 -1.0286765000000e+02\r\n474 473  1.9409339000000e+01\r\n477 473 -4.2882222000000e+00\r\n520 473  7.2197736000000e+01\r\n522 473 -4.5102819000000e+00\r\n1578 473 -1.5542434000000e+00\r\n426 474 -7.4707486000000e+00\r\n469 474  4.0291363000000e+01\r\n470 474 -6.5269939000000e+00\r\n471 474 -7.8190422000000e+00\r\n472 474 -6.8652953000000e+02\r\n473 474  1.0664209000000e+02\r\n474 474  3.2809543000000e+01\r\n477 474 -7.2488069000000e+00\r\n520 474  1.2204305000000e+02\r\n521 474 -1.9770349000000e+01\r\n522 474 -7.6241805000000e+00\r\n1578 474 -2.6272931000000e+00\r\n427 475 -2.1850937000000e-03\r\n429 475 -2.2804627000000e-05\r\n472 475 -4.3512517000000e-01\r\n474 475 -2.5243137000000e-05\r\n475 475  4.9442470000000e+02\r\n477 475  1.2137476000000e-03\r\n1579 475 -5.3505942000000e-02\r\n1581 475 -1.0006409000000e-05\r\n429 476 -3.9916066000000e+00\r\n472 476  3.5331745000000e+01\r\n474 476 -4.2882222000000e+00\r\n475 476 -3.1905106000000e+02\r\n476 476 -9.4106391000000e+01\r\n477 476  9.9901027000000e+00\r\n1581 476 -1.6997381000000e+00\r\n429 477 -6.7474068000000e+00\r\n472 477  5.9724749000000e+01\r\n473 477 -9.6752944000000e+00\r\n474 477 -7.2488069000000e+00\r\n475 477 -5.3932361000000e+02\r\n476 477  8.3202806000000e+01\r\n477 477  1.6887259000000e+01\r\n1581 477 -2.8732354000000e+00\r\n478 478  1.0000000000000e+00\r\n479 479  1.0000000000000e+00\r\n480 480  1.0000000000000e+00\r\n481 481  1.0000000000000e+00\r\n482 482  1.0000000000000e+00\r\n483 483  1.0000000000000e+00\r\n484 484  1.0000000000000e+00\r\n485 485  1.0000000000000e+00\r\n486 486  1.0000000000000e+00\r\n487 487  1.0000000000000e+00\r\n488 488  1.0000000000000e+00\r\n489 489  1.0000000000000e+00\r\n490 490  1.0000000000000e+00\r\n491 491  1.0000000000000e+00\r\n492 492  1.0000000000000e+00\r\n445 493 -2.2188495000000e-02\r\n447 493 -1.9905810000000e-05\r\n493 493  3.5624958000000e+02\r\n495 493  9.0470568000000e-04\r\n496 493 -1.2056436000000e-01\r\n498 493 -1.9490644000000e-05\r\n541 493 -1.6758613000000e-03\r\n543 493 -1.7490047000000e-05\r\n1597 493 -5.6812041000000e-02\r\n1599 493 -1.4640770000000e-05\r\n447 494 -3.2068077000000e+00\r\n493 494 -2.3145383000000e+02\r\n494 494 -6.7884610000000e+01\r\n495 494  1.1464227000000e+01\r\n496 494  9.4096397000000e+00\r\n498 494 -3.1402877000000e+00\r\n541 494  1.7558430000000e+01\r\n543 494 -2.7507270000000e+00\r\n1599 494 -2.3587909000000e+00\r\n447 495 -5.4207838000000e+00\r\n493 495 -3.9124930000000e+02\r\n494 495  6.0276811000000e+01\r\n495 495  1.9379115000000e+01\r\n496 495  1.5906044000000e+01\r\n497 495 -2.5766673000000e+00\r\n498 495 -5.3083387000000e+00\r\n541 495  2.9680750000000e+01\r\n542 495 -4.8080725000000e+00\r\n543 495 -4.6498258000000e+00\r\n1599 495 -3.9872974000000e+00\r\n448 496 -1.0442122000000e-02\r\n450 496 -2.2250808000000e-05\r\n493 496 -1.8675545000000e-03\r\n495 496 -1.9490644000000e-05\r\n496 496  4.0240967000000e+02\r\n498 496  1.0367382000000e-03\r\n499 496 -2.9821239000000e-01\r\n501 496 -2.1851909000000e-05\r\n544 496 -5.8779169000000e-02\r\n546 496 -1.9325226000000e-05\r\n1600 496 -5.2065558000000e-02\r\n1602 496 -1.3125358000000e-05\r\n450 497 -3.5431100000000e+00\r\n495 497 -3.1402877000000e+00\r\n496 497 -2.7845932000000e+02\r\n497 497 -7.6645502000000e+01\r\n498 497  1.5340356000000e+01\r\n499 497  2.1802822000000e+01\r\n501 497 -3.4800929000000e+00\r\n544 497  2.5787942000000e+01\r\n546 497 -3.0780453000000e+00\r\n1602 497 -2.0902235000000e+00\r\n450 498 -5.9892731000000e+00\r\n495 498 -5.3083387000000e+00\r\n496 498 -4.7070763000000e+02\r\n497 498  7.2743432000000e+01\r\n498 498  2.5931334000000e+01\r\n499 498  3.6855490000000e+01\r\n500 498 -5.9702838000000e+00\r\n501 498 -5.8827489000000e+00\r\n544 498  4.3591937000000e+01\r\n545 498 -7.0615323000000e+00\r\n546 498 -5.2031278000000e+00\r\n1602 498 -3.5333138000000e+00\r\n451 499 -2.2769672000000e-03\r\n453 499 -2.3763460000000e-05\r\n496 499 -2.0938062000000e-03\r\n498 499 -2.1851909000000e-05\r\n499 499  4.3705599000000e+02\r\n501 499  1.1260789000000e-03\r\n502 499 -4.1640767000000e-01\r\n504 499 -2.4773945000000e-05\r\n547 499 -1.5382048000000e-01\r\n549 499 -2.1953293000000e-05\r\n1603 499 -3.9166332000000e-02\r\n1605 499 -1.2390340000000e-05\r\n453 500 -3.8706427000000e+00\r\n498 500 -3.4800929000000e+00\r\n499 500 -3.2692845000000e+02\r\n500 500 -8.3216692000000e+01\r\n501 500  1.6556385000000e+01\r\n502 500  3.5863226000000e+01\r\n504 500 -3.8537242000000e+00\r\n547 500  4.0410594000000e+01\r\n549 500 -3.4153510000000e+00\r\n1605 500 -1.9272396000000e+00\r\n453 501 -6.5429310000000e+00\r\n498 501 -5.8827489000000e+00\r\n499 501 -5.5263943000000e+02\r\n500 501  8.5709818000000e+01\r\n501 501  2.7986897000000e+01\r\n502 501  6.0623151000000e+01\r\n503 501 -9.8203101000000e+00\r\n504 501 -6.5143303000000e+00\r\n547 501  6.8310016000000e+01\r\n548 501 -1.1065501000000e+01\r\n549 501 -5.7733048000000e+00\r\n1605 501 -3.2578037000000e+00\r\n454 502 -2.5615973000000e-03\r\n456 502 -2.6733988000000e-05\r\n499 502 -2.3737899000000e-03\r\n501 502 -2.4773945000000e-05\r\n502 502  4.9493426000000e+02\r\n504 502  1.2728968000000e-03\r\n505 502 -5.6088406000000e-01\r\n507 502 -2.8811357000000e-05\r\n550 502 -4.9629986000000e-01\r\n552 502 -2.5522785000000e-05\r\n1606 502 -1.4348107000000e-02\r\n1608 502 -1.1291817000000e-05\r\n456 503 -4.2678508000000e+00\r\n501 503 -3.8537242000000e+00\r\n502 503 -3.9920173000000e+02\r\n503 503 -9.4176106000000e+01\r\n504 503  1.8002224000000e+01\r\n505 503  4.7350486000000e+01\r\n507 503 -4.3330727000000e+00\r\n550 503  6.8230276000000e+01\r\n552 503 -3.8389315000000e+00\r\n1608 503 -1.6980784000000e+00\r\n456 504 -7.2143749000000e+00\r\n501 504 -6.5143303000000e+00\r\n502 504 -6.7481061000000e+02\r\n503 504  1.0497153000000e+02\r\n504 504  3.0430955000000e+01\r\n505 504  8.0041261000000e+01\r\n506 504 -1.2965548000000e+01\r\n507 504 -7.3246260000000e+00\r\n550 504  1.1533646000000e+02\r\n551 504 -1.8682869000000e+01\r\n552 504 -6.4893297000000e+00\r\n1608 504 -2.8704318000000e+00\r\n457 505 -2.8480249000000e-03\r\n459 505 -2.9723276000000e-05\r\n502 505 -2.7606466000000e-03\r\n504 505 -2.8811357000000e-05\r\n505 505  5.5265280000000e+02\r\n507 505  1.4215661000000e-03\r\n508 505 -4.3860921000000e-01\r\n510 505 -3.2333973000000e-05\r\n553 505 -9.3809341000000e-01\r\n555 505 -3.0174259000000e-05\r\n1609 505 -9.8984396000000e-04\r\n1611 505 -1.0330459000000e-05\r\n459 506 -4.6448017000000e+00\r\n504 506 -4.3330727000000e+00\r\n505 506 -4.7899523000000e+02\r\n506 506 -1.0513858000000e+02\r\n507 506  1.9561832000000e+01\r\n508 506  3.7782580000000e+01\r\n510 506 -4.6790249000000e+00\r\n553 506  1.2462987000000e+02\r\n555 506 -4.3673821000000e+00\r\n1611 506 -1.5257493000000e+00\r\n459 507 -7.8515677000000e+00\r\n504 507 -7.3246260000000e+00\r\n505 507 -8.0969294000000e+02\r\n506 507  1.2628357000000e+02\r\n507 507  3.3067302000000e+01\r\n508 507  6.3867626000000e+01\r\n509 507 -1.0345390000000e+01\r\n510 507 -7.9094179000000e+00\r\n553 507  2.1067418000000e+02\r\n554 507 -3.4125373000000e+01\r\n555 507 -7.3826173000000e+00\r\n1611 507 -2.5791245000000e+00\r\n460 508 -2.9463997000000e-03\r\n462 508 -3.0749960000000e-05\r\n505 508 -3.0981766000000e-03\r\n507 508 -3.2333973000000e-05\r\n508 508  5.7610393000000e+02\r\n510 508  1.4841410000000e-03\r\n511 508 -3.1852221000000e-03\r\n513 508 -3.3242419000000e-05\r\n556 508 -1.8658174000000e+00\r\n558 508 -3.3766112000000e-05\r\n1612 508 -9.6472465000000e-04\r\n1614 508 -1.0068303000000e-05\r\n462 509 -4.7484940000000e+00\r\n507 509 -4.6790249000000e+00\r\n508 509 -5.4056621000000e+02\r\n509 509 -1.0952935000000e+02\r\n510 509  2.0434084000000e+01\r\n513 509 -4.7765998000000e+00\r\n556 509  2.1080725000000e+02\r\n558 509 -4.7563521000000e+00\r\n1614 509 -1.4613155000000e+00\r\n462 510 -8.0268543000000e+00\r\n507 510 -7.9094179000000e+00\r\n508 510 -9.1377311000000e+02\r\n509 510  1.4291169000000e+02\r\n510 510  3.4541762000000e+01\r\n513 510 -8.0743576000000e+00\r\n556 510  3.5634858000000e+02\r\n557 510 -5.7720843000000e+01\r\n558 510 -8.0401375000000e+00\r\n1614 510 -2.4702077000000e+00\r\n463 511 -2.9230218000000e-03\r\n465 511 -3.0505978000000e-05\r\n508 511 -2.4803450000000e-01\r\n510 511 -3.3242419000000e-05\r\n511 511  5.7550887000000e+02\r\n513 511  1.4829856000000e-03\r\n514 511 -3.0883055000000e-03\r\n516 511 -3.2230953000000e-05\r\n559 511 -1.0092726000000e+00\r\n561 511 -3.3068305000000e-05\r\n1615 511 -9.5556070000000e-04\r\n1617 511 -9.9726638000000e-06\r\n465 512 -4.7456943000000e+00\r\n508 512  2.8689754000000e+01\r\n510 512 -4.7765998000000e+00\r\n511 512 -4.9409341000000e+02\r\n512 512 -1.0951398000000e+02\r\n513 512  2.0528275000000e+01\r\n516 512 -4.7759952000000e+00\r\n559 512  1.3562274000000e+02\r\n561 512 -4.7524962000000e+00\r\n1617 512 -1.4651993000000e+00\r\n465 513 -8.0221160000000e+00\r\n508 513  4.8497120000000e+01\r\n509 513 -7.8556109000000e+00\r\n510 513 -8.0743576000000e+00\r\n511 513 -8.3521480000000e+02\r\n512 513  1.3022704000000e+02\r\n513 513  3.4700975000000e+01\r\n516 513 -8.0733421000000e+00\r\n559 513  2.2925650000000e+02\r\n560 513 -3.7135191000000e+01\r\n561 513 -8.0336129000000e+00\r\n1617 513 -2.4767708000000e+00\r\n466 514 -2.8749653000000e-03\r\n468 514 -3.0004439000000e-05\r\n511 514 -4.1241729000000e-01\r\n513 514 -3.2230953000000e-05\r\n514 514  5.7519069000000e+02\r\n516 514  1.4795120000000e-03\r\n517 514 -3.0069859000000e-03\r\n519 514 -3.1382266000000e-05\r\n562 514 -4.9911312000000e-01\r\n564 514 -3.2047129000000e-05\r\n1618 514 -8.0139423000000e-03\r\n1620 514 -9.9070950000000e-06\r\n468 515 -4.7465937000000e+00\r\n511 515  4.2569293000000e+01\r\n513 515 -4.7759952000000e+00\r\n514 515 -4.6234161000000e+02\r\n515 515 -1.0949542000000e+02\r\n516 515  2.0527064000000e+01\r\n519 515 -4.7748703000000e+00\r\n562 515  8.9964943000000e+01\r\n564 515 -4.7494534000000e+00\r\n1620 515 -1.4678694000000e+00\r\n468 516 -8.0236419000000e+00\r\n511 516  7.1959131000000e+01\r\n512 516 -1.1656244000000e+01\r\n513 516 -8.0733421000000e+00\r\n514 516 -7.8154226000000e+02\r\n515 516  1.2158133000000e+02\r\n516 516  3.4698943000000e+01\r\n519 516 -8.0714349000000e+00\r\n562 516  1.5207674000000e+02\r\n563 516 -2.4634033000000e+01\r\n564 516 -8.0284759000000e+00\r\n1620 516 -2.4812864000000e+00\r\n469 517 -2.8220775000000e-03\r\n471 517 -2.9452477000000e-05\r\n514 517 -4.3290524000000e-01\r\n516 517 -3.1382266000000e-05\r\n517 517  5.7503149000000e+02\r\n519 517  1.4758353000000e-03\r\n520 517 -2.8957310000000e-03\r\n522 517 -3.0221159000000e-05\r\n565 517 -2.8886261000000e-01\r\n567 517 -3.1218023000000e-05\r\n1621 517 -3.0579909000000e-02\r\n1623 517 -9.6501086000000e-06\r\n471 518 -4.7465231000000e+00\r\n514 518  3.5396470000000e+01\r\n516 518 -4.7748703000000e+00\r\n517 518 -4.3450468000000e+02\r\n518 518 -1.0948827000000e+02\r\n519 518  2.0429436000000e+01\r\n522 518 -4.6769808000000e+00\r\n565 518  6.9290058000000e+01\r\n567 518 -4.7506181000000e+00\r\n1623 518 -1.4681648000000e+00\r\n471 519 -8.0235181000000e+00\r\n514 519  5.9834150000000e+01\r\n515 519 -9.6923637000000e+00\r\n516 519 -8.0714349000000e+00\r\n517 519 -7.3448618000000e+02\r\n518 519  1.1397923000000e+02\r\n519 519  3.4533900000000e+01\r\n522 519 -7.9059682000000e+00\r\n565 519  1.1712783000000e+02\r\n566 519 -1.8973202000000e+01\r\n567 519 -8.0304389000000e+00\r\n1623 519 -2.4817839000000e+00\r\n472 520 -2.6281004000000e-03\r\n474 520 -2.7428044000000e-05\r\n517 520 -3.2038204000000e-01\r\n519 520 -3.0221159000000e-05\r\n520 520  5.5186282000000e+02\r\n522 520  1.3874395000000e-03\r\n568 520 -1.9750234000000e-01\r\n570 520 -2.9774965000000e-05\r\n1624 520 -3.9997528000000e-02\r\n1626 520 -9.8819052000000e-06\r\n474 521 -4.5102819000000e+00\r\n517 521  2.1665194000000e+01\r\n519 521 -4.6769808000000e+00\r\n520 521 -3.9709700000000e+02\r\n521 521 -9.6452757000000e+01\r\n522 521  1.5336972000000e+01\r\n568 521  5.8806825000000e+01\r\n570 521 -4.6086963000000e+00\r\n1626 521 -1.5292250000000e+00\r\n474 522 -7.6241805000000e+00\r\n517 522  3.6622843000000e+01\r\n518 522 -5.9324904000000e+00\r\n519 522 -7.9059682000000e+00\r\n520 522 -6.7125278000000e+02\r\n521 522  1.1856897000000e+02\r\n522 522  2.5925617000000e+01\r\n568 522  9.9407057000000e+01\r\n569 522 -1.6102830000000e+01\r\n570 522 -7.7905402000000e+00\r\n1626 522 -2.5850020000000e+00\r\n523 523  1.0000000000000e+00\r\n524 524  1.0000000000000e+00\r\n525 525  1.0000000000000e+00\r\n526 526  1.0000000000000e+00\r\n527 527  1.0000000000000e+00\r\n528 528  1.0000000000000e+00\r\n529 529  1.0000000000000e+00\r\n530 530  1.0000000000000e+00\r\n531 531  1.0000000000000e+00\r\n532 532  1.0000000000000e+00\r\n533 533  1.0000000000000e+00\r\n534 534  1.0000000000000e+00\r\n535 535  1.0000000000000e+00\r\n536 536  1.0000000000000e+00\r\n537 537  1.0000000000000e+00\r\n538 538  1.0000000000000e+00\r\n539 539  1.0000000000000e+00\r\n540 540  1.0000000000000e+00\r\n493 541 -4.8867607000000e-03\r\n495 541 -1.7490047000000e-05\r\n541 541  3.1031167000000e+02\r\n543 541  7.9300686000000e-04\r\n544 541 -1.5765390000000e-01\r\n546 541 -1.7263735000000e-05\r\n589 541 -9.1135186000000e-03\r\n591 541 -1.5422818000000e-05\r\n1645 541 -5.7152102000000e-02\r\n1647 541 -1.7161875000000e-05\r\n495 542 -2.7507270000000e+00\r\n541 542 -1.9981890000000e+02\r\n542 542 -5.9147403000000e+01\r\n543 542  1.0598055000000e+01\r\n544 542  1.3552430000000e+01\r\n546 542 -2.7154363000000e+00\r\n589 542  8.1967632000000e+00\r\n591 542 -2.4259626000000e+00\r\n1647 542 -2.6992882000000e+00\r\n495 543 -4.6498258000000e+00\r\n541 543 -3.3777366000000e+02\r\n542 543  5.1959485000000e+01\r\n543 543  1.7914941000000e+01\r\n544 543  2.2909013000000e+01\r\n545 543 -3.7110429000000e+00\r\n546 543 -4.5901706000000e+00\r\n589 543  1.3855800000000e+01\r\n590 543 -2.2445083000000e+00\r\n591 543 -4.1008446000000e+00\r\n1647 543 -4.5628743000000e+00\r\n496 544 -1.8517045000000e-03\r\n498 544 -1.9325226000000e-05\r\n541 544 -1.6541766000000e-03\r\n543 544 -1.7263735000000e-05\r\n544 544  3.4496899000000e+02\r\n546 544  8.9592176000000e-04\r\n547 544 -3.3972665000000e-01\r\n549 544 -1.9714003000000e-05\r\n592 544 -4.4239529000000e-02\r\n594 544 -1.7560687000000e-05\r\n1648 544 -4.9122130000000e-02\r\n1650 544 -1.5748757000000e-05\r\n498 545 -3.0780453000000e+00\r\n543 545 -2.7154363000000e+00\r\n544 545 -2.4255089000000e+02\r\n545 545 -6.5723061000000e+01\r\n546 545  1.3987573000000e+01\r\n547 545  2.9580329000000e+01\r\n549 545 -3.0438226000000e+00\r\n592 545  1.5120848000000e+01\r\n594 545 -2.7114628000000e+00\r\n1650 545 -2.4314260000000e+00\r\n498 546 -5.2031278000000e+00\r\n543 546 -4.5901706000000e+00\r\n544 546 -4.1000802000000e+02\r\n545 546  6.3344299000000e+01\r\n546 546  2.3644591000000e+01\r\n547 546  5.0002588000000e+01\r\n548 546 -8.0998458000000e+00\r\n549 546 -5.1452776000000e+00\r\n592 546  2.5560282000000e+01\r\n593 546 -4.1404725000000e+00\r\n594 546 -4.5834567000000e+00\r\n1650 546 -4.1100826000000e+00\r\n499 547 -2.1035206000000e-03\r\n501 547 -2.1953293000000e-05\r\n544 547 -1.8889563000000e-03\r\n546 547 -1.9714003000000e-05\r\n547 547  3.9125737000000e+02\r\n549 547  1.0133153000000e-03\r\n550 547 -6.5888912000000e-01\r\n552 547 -2.2988498000000e-05\r\n595 547 -1.0794534000000e-01\r\n597 547 -2.0394295000000e-05\r\n1651 547 -2.6226452000000e-02\r\n1653 547 -1.4424569000000e-05\r\n501 548 -3.4153510000000e+00\r\n546 548 -3.0438226000000e+00\r\n547 548 -3.0226887000000e+02\r\n548 548 -7.4494601000000e+01\r\n549 548  1.5085272000000e+01\r\n550 548  5.2248365000000e+01\r\n552 548 -3.4270315000000e+00\r\n595 548  2.5803312000000e+01\r\n597 548 -3.0405040000000e+00\r\n1653 548 -2.1501943000000e+00\r\n501 549 -5.7733048000000e+00\r\n546 549 -5.1452776000000e+00\r\n547 549 -5.1095495000000e+02\r\n548 549  7.9264038000000e+01\r\n549 549  2.5500128000000e+01\r\n550 549  8.8320577000000e+01\r\n551 549 -1.4306604000000e+01\r\n552 549 -5.7930501000000e+00\r\n595 549  4.3617890000000e+01\r\n596 549 -7.0654417000000e+00\r\n597 549 -5.1396644000000e+00\r\n1653 549 -3.6346854000000e+00\r\n502 550 -2.4455422000000e-03\r\n504 550 -2.5522785000000e-05\r\n547 550 -2.2027119000000e-03\r\n549 550 -2.2988498000000e-05\r\n550 550  4.3748058000000e+02\r\n552 550  1.1357538000000e-03\r\n553 550 -8.3735753000000e-01\r\n555 550 -2.7548317000000e-05\r\n598 550 -2.5091805000000e-01\r\n600 550 -2.4896148000000e-05\r\n1654 550 -1.2839192000000e-03\r\n1656 550 -1.3399561000000e-05\r\n504 551 -3.8389315000000e+00\r\n549 551 -3.4270315000000e+00\r\n550 551 -3.8540336000000e+02\r\n551 551 -8.3267654000000e+01\r\n552 551  1.6619424000000e+01\r\n553 551  8.4500754000000e+01\r\n555 551 -3.8958941000000e+00\r\n598 551  5.0320737000000e+01\r\n600 551 -3.5209698000000e+00\r\n1656 551 -1.9272400000000e+00\r\n504 552 -6.4893297000000e+00\r\n549 552 -5.7930501000000e+00\r\n550 552 -6.5148583000000e+02\r\n551 552  1.0158914000000e+02\r\n552 552  2.8093470000000e+01\r\n553 552  1.4284007000000e+02\r\n554 552 -2.3137098000000e+01\r\n555 552 -6.5856193000000e+00\r\n598 552  8.5062173000000e+01\r\n599 552 -1.3778289000000e+01\r\n600 552 -5.9518472000000e+00\r\n1656 552 -3.2578065000000e+00\r\n505 553 -2.8912371000000e-03\r\n507 553 -3.0174259000000e-05\r\n550 553 -2.6396247000000e-03\r\n552 553 -2.7548317000000e-05\r\n553 553  5.0753119000000e+02\r\n555 553  1.3171729000000e-03\r\n556 553 -1.2129343000000e+00\r\n558 553 -3.3917203000000e-05\r\n601 553 -1.0637215000000e+00\r\n603 553 -3.0689517000000e-05\r\n1657 553 -1.1608889000000e-03\r\n1659 553 -1.2115562000000e-05\r\n507 554 -4.3673821000000e+00\r\n552 554 -3.8958941000000e+00\r\n553 554 -5.2536138000000e+02\r\n554 554 -9.6452559000000e+01\r\n555 554  1.8456140000000e+01\r\n556 554  1.0669878000000e+02\r\n558 554 -4.4722193000000e+00\r\n601 554  1.2856937000000e+02\r\n603 554 -4.0471967000000e+00\r\n1659 554 -1.6625969000000e+00\r\n507 555 -7.3826173000000e+00\r\n552 555 -6.5856193000000e+00\r\n553 555 -8.8807032000000e+02\r\n554 555  1.3918923000000e+02\r\n555 555  3.1198243000000e+01\r\n556 555  1.8036351000000e+02\r\n557 555 -2.9213649000000e+01\r\n558 555 -7.5598347000000e+00\r\n601 555  2.1733352000000e+02\r\n602 555 -3.5201717000000e+01\r\n603 555 -6.8413770000000e+00\r\n1659 555 -2.8104518000000e+00\r\n508 556 -3.2354013000000e-03\r\n510 556 -3.3766112000000e-05\r\n553 556 -3.2498785000000e-03\r\n555 556 -3.3917203000000e-05\r\n556 556  5.7849567000000e+02\r\n558 556  1.4973431000000e-03\r\n559 556 -3.4951579000000e-03\r\n561 556 -3.6477050000000e-05\r\n604 556 -4.3747313000000e+00\r\n606 556 -3.8023947000000e-05\r\n1660 556 -1.0601736000000e-03\r\n1662 556 -1.1064451000000e-05\r\n510 557 -4.7563521000000e+00\r\n555 557 -4.4722193000000e+00\r\n556 557 -7.9450407000000e+02\r\n557 557 -1.0963647000000e+02\r\n558 557  2.0151920000000e+01\r\n561 557 -4.7785850000000e+00\r\n604 557  4.6489940000000e+02\r\n606 557 -4.6673536000000e+00\r\n1662 557 -1.4650651000000e+00\r\n510 558 -8.0401375000000e+00\r\n555 558 -7.5598347000000e+00\r\n556 558 -1.3430296000000e+03\r\n557 558  2.1215420000000e+02\r\n558 558  3.4064795000000e+01\r\n561 558 -8.0777140000000e+00\r\n604 558  7.8586592000000e+02\r\n605 558 -1.2728026000000e+02\r\n606 558 -7.8896943000000e+00\r\n1662 558 -2.4765460000000e+00\r\n511 559 -3.1685388000000e-03\r\n513 559 -3.3068305000000e-05\r\n556 559 -1.1079898000000e+00\r\n558 559 -3.6477050000000e-05\r\n559 559  5.7644819000000e+02\r\n561 559  1.4950011000000e-03\r\n562 559 -3.2937125000000e-03\r\n564 559 -3.4374674000000e-05\r\n607 559 -1.1830743000000e+00\r\n609 559 -3.6365310000000e-05\r\n1663 559 -1.0245894000000e-03\r\n1665 559 -1.0693079000000e-05\r\n513 560 -4.7524962000000e+00\r\n556 560  1.0412546000000e+02\r\n558 560 -4.7785850000000e+00\r\n559 560 -5.7975761000000e+02\r\n560 560 -1.0960089000000e+02\r\n561 560  2.0548189000000e+01\r\n564 560 -4.7776800000000e+00\r\n607 560  1.4597505000000e+02\r\n609 560 -4.7645572000000e+00\r\n1665 560 -1.4625411000000e+00\r\n513 561 -8.0336129000000e+00\r\n556 561  1.7601354000000e+02\r\n557 561 -2.8508945000000e+01\r\n558 561 -8.0777140000000e+00\r\n559 561 -9.8002155000000e+02\r\n560 561  1.5345788000000e+02\r\n561 561  3.4734637000000e+01\r\n564 561 -8.0761900000000e+00\r\n607 561  2.4675605000000e+02\r\n608 561 -3.9967119000000e+01\r\n609 561 -8.0540009000000e+00\r\n1665 561 -2.4722779000000e+00\r\n514 562 -3.0706918000000e-03\r\n516 562 -3.2047129000000e-05\r\n559 562 -9.2503375000000e-01\r\n561 562 -3.4374674000000e-05\r\n562 562  5.7558862000000e+02\r\n564 562  1.4879754000000e-03\r\n565 562 -3.1647136000000e-03\r\n567 562 -3.3028383000000e-05\r\n610 562 -4.7106134000000e-01\r\n612 562 -3.4274280000000e-05\r\n1666 562 -9.8565306000000e-04\r\n1668 562 -1.0286721000000e-05\r\n516 563 -4.7494534000000e+00\r\n559 563  8.8420532000000e+01\r\n561 563 -4.7776800000000e+00\r\n562 563 -4.9169918000000e+02\r\n563 563 -1.0956911000000e+02\r\n564 563  2.0541572000000e+01\r\n567 563 -4.7763472000000e+00\r\n610 563  7.3575168000000e+01\r\n612 563 -4.7640016000000e+00\r\n1668 563 -1.4617749000000e+00\r\n516 564 -8.0284759000000e+00\r\n559 564  1.4946606000000e+02\r\n560 564 -2.4210075000000e+01\r\n561 564 -8.0761900000000e+00\r\n562 564 -8.3116828000000e+02\r\n563 564  1.2943272000000e+02\r\n564 564  3.4723467000000e+01\r\n567 564 -8.0739316000000e+00\r\n610 564  1.2437146000000e+02\r\n611 564 -2.0145325000000e+01\r\n612 564 -8.0530681000000e+00\r\n1668 564 -2.4709843000000e+00\r\n517 565 -2.9912485000000e-03\r\n519 565 -3.1218023000000e-05\r\n562 565 -6.4445134000000e-01\r\n564 565 -3.3028383000000e-05\r\n565 565  5.7516975000000e+02\r\n567 565  1.4832013000000e-03\r\n568 565 -3.0629382000000e-03\r\n570 565 -3.1966208000000e-05\r\n613 565 -3.0291400000000e-01\r\n615 565 -3.2962271000000e-05\r\n1669 565 -1.4067534000000e-02\r\n1671 565 -1.0104963000000e-05\r\n519 566 -4.7506181000000e+00\r\n562 566  5.6210454000000e+01\r\n564 566 -4.7763472000000e+00\r\n565 566 -4.4068899000000e+02\r\n566 566 -1.0955398000000e+02\r\n567 566  2.0495125000000e+01\r\n570 566 -4.7275361000000e+00\r\n613 566  5.4752635000000e+01\r\n615 566 -4.7671558000000e+00\r\n1671 566 -1.4611605000000e+00\r\n519 567 -8.0304389000000e+00\r\n562 567  9.5018084000000e+01\r\n563 567 -1.5391186000000e+01\r\n564 567 -8.0739316000000e+00\r\n565 567 -7.4494017000000e+02\r\n566 567  1.1550708000000e+02\r\n567 567  3.4644941000000e+01\r\n570 567 -7.9914270000000e+00\r\n613 567  9.2553790000000e+01\r\n614 567 -1.4992013000000e+01\r\n615 567 -8.0583944000000e+00\r\n1671 567 -2.4699439000000e+00\r\n520 568 -2.8529776000000e-03\r\n522 568 -2.9774965000000e-05\r\n565 568 -4.0867176000000e-01\r\n567 568 -3.1966208000000e-05\r\n568 568  5.6332193000000e+02\r\n570 568  1.4207330000000e-03\r\n616 568 -1.5716562000000e-01\r\n618 568 -3.1899025000000e-05\r\n1672 568 -3.1166100000000e-02\r\n1674 568 -1.0076485000000e-05\r\n522 569 -4.6086963000000e+00\r\n565 569  3.0525309000000e+01\r\n567 569 -4.7275361000000e+00\r\n568 569 -3.9126151000000e+02\r\n569 569 -1.0736000000000e+02\r\n570 569  1.5556430000000e+01\r\n616 569  3.7600113000000e+01\r\n618 569 -4.7180090000000e+00\r\n1674 569 -1.4901284000000e+00\r\n522 570 -7.7905402000000e+00\r\n565 570  5.1599982000000e+01\r\n566 570 -8.3583710000000e+00\r\n567 570 -7.9914270000000e+00\r\n568 570 -6.6138846000000e+02\r\n569 570  1.0208534000000e+02\r\n570 570  2.6296589000000e+01\r\n616 570  6.3559232000000e+01\r\n617 570 -1.0295578000000e+01\r\n618 570 -7.9753225000000e+00\r\n1674 570 -2.5189130000000e+00\r\n571 571  1.0000000000000e+00\r\n572 572  1.0000000000000e+00\r\n573 573  1.0000000000000e+00\r\n574 574  1.0000000000000e+00\r\n575 575  1.0000000000000e+00\r\n576 576  1.0000000000000e+00\r\n577 577  1.0000000000000e+00\r\n578 578  1.0000000000000e+00\r\n579 579  1.0000000000000e+00\r\n580 580  1.0000000000000e+00\r\n581 581  1.0000000000000e+00\r\n582 582  1.0000000000000e+00\r\n583 583  1.0000000000000e+00\r\n584 584  1.0000000000000e+00\r\n585 585  1.0000000000000e+00\r\n586 586  2.2978609000000e+02\r\n588 586  5.8613218000000e-04\r\n589 586 -3.5185103000000e-02\r\n591 586 -1.3283667000000e-05\r\n634 586 -1.1599025000000e-03\r\n636 586 -1.2105267000000e-05\r\n1690 586 -6.2688382000000e-02\r\n1692 586 -2.3213044000000e-05\r\n586 587 -1.3774419000000e+02\r\n587 587 -4.3816660000000e+01\r\n588 587  7.6424481000000e+00\r\n589 587  5.8459524000000e+00\r\n591 587 -2.0845371000000e+00\r\n636 587 -1.9104687000000e+00\r\n1692 587 -3.6425216000000e+00\r\n586 588 -2.3284278000000e+02\r\n587 588  3.5667017000000e+01\r\n588 588  1.2918794000000e+01\r\n589 588  9.8819980000000e+00\r\n590 588 -1.6007868000000e+00\r\n591 588 -3.5237015000000e+00\r\n636 588 -3.2294562000000e+00\r\n1692 588 -6.1573185000000e+00\r\n541 589 -1.4777835000000e-03\r\n543 589 -1.5422818000000e-05\r\n586 589 -1.2728144000000e-03\r\n588 589 -1.3283667000000e-05\r\n589 589  2.7585334000000e+02\r\n591 589  7.2235850000000e-04\r\n592 589 -1.7145267000000e-01\r\n594 589 -1.5635827000000e-05\r\n637 589 -1.2860444000000e-03\r\n639 589 -1.3421741000000e-05\r\n1693 589 -5.8961975000000e-02\r\n1695 589 -1.9556480000000e-05\r\n543 590 -2.4259626000000e+00\r\n588 590 -2.0845371000000e+00\r\n589 590 -1.7607907000000e+02\r\n590 590 -5.2585057000000e+01\r\n591 590  1.2065069000000e+01\r\n592 590  1.7455773000000e+01\r\n594 590 -2.4283018000000e+00\r\n637 590  3.5253523000000e-01\r\n639 590 -2.0833663000000e+00\r\n1695 590 -3.0369940000000e+00\r\n543 591 -4.1008446000000e+00\r\n588 591 -3.5237015000000e+00\r\n589 591 -2.9764387000000e+02\r\n590 591  4.5741228000000e+01\r\n591 591  2.0394783000000e+01\r\n592 591  2.9507220000000e+01\r\n593 591 -4.7798516000000e+00\r\n594 591 -4.1047987000000e+00\r\n637 591  5.9592515000000e-01\r\n638 591 -9.6533443000000e-02\r\n639 591 -3.5217201000000e+00\r\n1695 591 -5.1337324000000e+00\r\n544 592 -1.6826299000000e-03\r\n546 592 -1.7560687000000e-05\r\n589 592 -1.4981936000000e-03\r\n591 592 -1.5635827000000e-05\r\n592 592  3.1047109000000e+02\r\n594 592  8.1079021000000e-04\r\n595 592 -3.5516694000000e-01\r\n597 592 -1.7948696000000e-05\r\n640 592 -1.5437154000000e-03\r\n642 592 -1.6110912000000e-05\r\n1696 592 -4.8563239000000e-02\r\n1698 592 -1.7854924000000e-05\r\n546 593 -2.7114628000000e+00\r\n591 593 -2.4283018000000e+00\r\n592 593 -2.1574654000000e+02\r\n593 593 -5.9166043000000e+01\r\n594 593  1.2989807000000e+01\r\n595 593  3.4295519000000e+01\r\n597 593 -2.7159780000000e+00\r\n640 593  3.4077931000000e+00\r\n642 593 -2.4258745000000e+00\r\n1698 593 -2.7015410000000e+00\r\n546 594 -4.5834567000000e+00\r\n591 594 -4.1047987000000e+00\r\n592 594 -3.6469795000000e+02\r\n593 594  5.6273456000000e+01\r\n594 594  2.1957967000000e+01\r\n595 594  5.7973145000000e+01\r\n596 594 -9.3908619000000e+00\r\n597 594 -4.5910892000000e+00\r\n640 594  5.7605335000000e+00\r\n641 594 -9.3312816000000e-01\r\n642 594 -4.1006982000000e+00\r\n1698 594 -4.5666848000000e+00\r\n547 595 -1.9541406000000e-03\r\n549 595 -2.0394295000000e-05\r\n592 595 -1.7198082000000e-03\r\n594 595 -1.7948696000000e-05\r\n595 595  3.4523209000000e+02\r\n597 595  9.0225060000000e-04\r\n598 595 -7.1300240000000e-01\r\n600 595 -2.1604671000000e-05\r\n643 595 -1.8373648000000e-03\r\n645 595 -1.9175571000000e-05\r\n1699 595 -1.4615176000000e-02\r\n1701 595 -1.6793702000000e-05\r\n549 596 -3.0405040000000e+00\r\n594 596 -2.7159780000000e+00\r\n595 596 -2.6674948000000e+02\r\n596 596 -6.5753455000000e+01\r\n597 596  1.4087562000000e+01\r\n598 596  6.5837486000000e+01\r\n600 596 -3.1277751000000e+00\r\n643 596  3.1057057000000e+00\r\n645 596 -2.7649448000000e+00\r\n1701 596 -2.4309664000000e+00\r\n549 597 -5.1396644000000e+00\r\n594 597 -4.5910892000000e+00\r\n595 597 -4.5091303000000e+02\r\n596 597  6.9892338000000e+01\r\n597 597  2.3813602000000e+01\r\n598 597  1.1129162000000e+02\r\n599 597 -1.8027209000000e+01\r\n600 597 -5.2871876000000e+00\r\n643 597  5.2498816000000e+00\r\n644 597 -8.5038494000000e-01\r\n645 597 -4.6738596000000e+00\r\n1701 597 -4.1093030000000e+00\r\n550 598 -2.3854991000000e-03\r\n552 598 -2.4896148000000e-05\r\n595 598 -2.0701163000000e-03\r\n597 598 -2.1604671000000e-05\r\n598 598  4.1487000000000e+02\r\n600 598  1.0797161000000e-03\r\n601 598 -1.4893747000000e+00\r\n603 598 -2.7142091000000e-05\r\n646 598 -2.2757736000000e-03\r\n648 598 -2.3751003000000e-05\r\n1702 598 -1.4057315000000e-03\r\n1704 598 -1.4670850000000e-05\r\n552 599 -3.5209698000000e+00\r\n597 599 -3.1277751000000e+00\r\n598 599 -3.8085355000000e+02\r\n599 599 -7.8927659000000e+01\r\n600 599  1.5582531000000e+01\r\n601 599  1.4352064000000e+02\r\n603 599 -3.6647369000000e+00\r\n648 599 -3.2334390000000e+00\r\n1704 599 -2.0267265000000e+00\r\n552 600 -5.9518472000000e+00\r\n597 600 -5.2871876000000e+00\r\n598 600 -6.4379484000000e+02\r\n599 600  1.0044229000000e+02\r\n600 600  2.6340706000000e+01\r\n601 600  2.4260728000000e+02\r\n602 600 -3.9295989000000e+01\r\n603 600 -6.1948711000000e+00\r\n648 600 -5.4658053000000e+00\r\n1704 600 -3.4259784000000e+00\r\n553 601 -2.9406082000000e-03\r\n555 601 -3.0689517000000e-05\r\n598 601 -2.6007009000000e-03\r\n600 601 -2.7142091000000e-05\r\n601 601  4.7473149000000e+02\r\n603 601  1.2383838000000e-03\r\n604 601 -3.9991868000000e+00\r\n606 601 -3.5238816000000e-05\r\n649 601 -2.8115951000000e-03\r\n651 601 -2.9343079000000e-05\r\n1705 601 -1.3243924000000e-03\r\n1707 601 -1.3821958000000e-05\r\n555 602 -4.0471967000000e+00\r\n600 602 -3.6647369000000e+00\r\n601 602 -6.5802809000000e+02\r\n602 602 -8.9945654000000e+01\r\n603 602  1.7444635000000e+01\r\n604 602  3.8781468000000e+02\r\n606 602 -4.2295457000000e+00\r\n651 602 -3.7128363000000e+00\r\n1707 602 -1.7801773000000e+00\r\n555 603 -6.8413770000000e+00\r\n600 603 -6.1948711000000e+00\r\n601 603 -1.1123300000000e+03\r\n602 603  1.7564428000000e+02\r\n603 603  2.9488395000000e+01\r\n604 603  6.5556152000000e+02\r\n605 603 -1.0617404000000e+02\r\n606 603 -7.1496192000000e+00\r\n651 603 -6.2761737000000e+00\r\n1707 603 -3.0092095000000e+00\r\n556 604 -3.6433786000000e-03\r\n558 604 -3.8023947000000e-05\r\n601 604 -3.3765129000000e-03\r\n603 604 -3.5238816000000e-05\r\n604 604  5.6907973000000e+02\r\n606 604  1.5789273000000e-03\r\n607 604 -3.7515504000000e-03\r\n609 604 -3.9152878000000e-05\r\n652 604 -3.6096880000000e-03\r\n654 604 -3.7672337000000e-05\r\n1708 604 -1.2329110000000e-03\r\n1710 604 -1.2867217000000e-05\r\n558 605 -4.6673536000000e+00\r\n603 605 -4.2295457000000e+00\r\n604 605 -2.1044274000000e+03\r\n605 605 -1.0545640000000e+02\r\n606 605  3.1506343000000e+01\r\n609 605 -4.6844756000000e+00\r\n654 605 -4.4348850000000e+00\r\n1710 605 -1.5208751000000e+00\r\n558 606 -7.8896943000000e+00\r\n603 606 -7.1496192000000e+00\r\n604 606 -3.5573237000000e+03\r\n605 606  5.7035342000000e+02\r\n606 606  5.3258311000000e+01\r\n609 606 -7.9186335000000e+00\r\n654 606 -7.4967294000000e+00\r\n1710 606 -2.5708872000000e+00\r\n559 607 -3.4844513000000e-03\r\n561 607 -3.6365310000000e-05\r\n604 607 -4.3132374000000e+00\r\n606 607 -3.9152878000000e-05\r\n607 607  5.7838196000000e+02\r\n609 607  1.5051761000000e-03\r\n610 607 -3.4620455000000e-03\r\n612 607 -3.6131473000000e-05\r\n655 607 -3.6521160000000e-03\r\n657 607 -3.8115135000000e-05\r\n1711 607 -1.0845381000000e-03\r\n1713 607 -1.1318731000000e-05\r\n561 608 -4.7645572000000e+00\r\n604 608  4.2514024000000e+02\r\n606 608 -4.6844756000000e+00\r\n607 608 -7.5467552000000e+02\r\n608 608 -1.0968478000000e+02\r\n609 608  2.0472160000000e+01\r\n612 608 -4.7794951000000e+00\r\n657 608 -4.7715009000000e+00\r\n1713 608 -1.4597647000000e+00\r\n561 609 -8.0540009000000e+00\r\n604 609  7.1865668000000e+02\r\n605 609 -1.1639256000000e+02\r\n606 609 -7.9186335000000e+00\r\n607 609 -1.2757028000000e+03\r\n608 609  2.0112619000000e+02\r\n609 609  3.4606123000000e+01\r\n612 609 -8.0792585000000e+00\r\n657 609 -8.0657406000000e+00\r\n1713 609 -2.4675848000000e+00\r\n562 610 -3.2840929000000e-03\r\n564 610 -3.4274280000000e-05\r\n607 610 -1.6392645000000e+00\r\n609 610 -3.6131473000000e-05\r\n610 610  5.7577660000000e+02\r\n612 610  1.4956980000000e-03\r\n613 610 -3.2907314000000e-03\r\n615 610 -3.4343562000000e-05\r\n658 610 -3.4728984000000e-03\r\n660 610 -3.6244739000000e-05\r\n1714 610 -1.0266717000000e-03\r\n1716 610 -1.0714810000000e-05\r\n564 611 -4.7640016000000e+00\r\n607 611  1.6106208000000e+02\r\n609 611 -4.7794951000000e+00\r\n610 611 -4.9827023000000e+02\r\n611 611 -1.0962325000000e+02\r\n612 611  2.0564645000000e+01\r\n615 611 -4.7780980000000e+00\r\n658 611  7.5819676000000e+00\r\n660 611 -4.7703929000000e+00\r\n1716 611 -1.4603184000000e+00\r\n564 612 -8.0530681000000e+00\r\n607 612  2.7225934000000e+02\r\n608 612 -4.4098175000000e+01\r\n609 612 -8.0792585000000e+00\r\n610 612 -8.4227598000000e+02\r\n611 612  1.3109326000000e+02\r\n612 612  3.4762469000000e+01\r\n615 612 -8.0768906000000e+00\r\n658 612  1.2816558000000e+01\r\n659 612 -2.0759135000000e+00\r\n660 612 -8.0638721000000e+00\r\n1716 612 -2.4685221000000e+00\r\n565 613 -3.1583789000000e-03\r\n567 613 -3.2962271000000e-05\r\n610 613 -8.1337681000000e-01\r\n612 613 -3.4343562000000e-05\r\n613 613  5.7519600000000e+02\r\n615 613  1.4890724000000e-03\r\n616 613 -3.1813009000000e-03\r\n618 613 -3.3201496000000e-05\r\n661 613 -2.2166944000000e-01\r\n663 613 -3.4294215000000e-05\r\n1717 613 -9.9022856000000e-04\r\n1719 613 -1.0334473000000e-05\r\n567 614 -4.7671558000000e+00\r\n610 614  7.5140097000000e+01\r\n612 614 -4.7780980000000e+00\r\n613 614 -4.4468461000000e+02\r\n614 614 -1.0959875000000e+02\r\n615 614  2.0565455000000e+01\r\n618 614 -4.7774699000000e+00\r\n661 614  3.9882149000000e+01\r\n663 614 -4.7713253000000e+00\r\n1719 614 -1.4590786000000e+00\r\n567 615 -8.0583944000000e+00\r\n610 615  1.2701672000000e+02\r\n611 615 -2.0573825000000e+01\r\n612 615 -8.0768906000000e+00\r\n613 615 -7.5169429000000e+02\r\n614 615  1.1648750000000e+02\r\n615 615  3.4763825000000e+01\r\n618 615 -8.0758350000000e+00\r\n661 615  6.7416734000000e+01\r\n662 615 -1.0919981000000e+01\r\n663 615 -8.0654413000000e+00\r\n1719 615 -2.4664250000000e+00\r\n568 616 -3.0565007000000e-03\r\n570 616 -3.1899025000000e-05\r\n613 616 -5.5733083000000e-01\r\n615 616 -3.3201496000000e-05\r\n616 616  5.7475318000000e+02\r\n618 616  1.4191498000000e-03\r\n1720 616 -2.5510073000000e-02\r\n1722 616 -1.0149217000000e-05\r\n570 617 -4.7180090000000e+00\r\n613 617  4.7641436000000e+01\r\n615 617 -4.7774699000000e+00\r\n616 617 -3.7732136000000e+02\r\n617 617 -1.0958694000000e+02\r\n618 617  1.0968069000000e+01\r\n1722 617 -1.4602675000000e+00\r\n570 618 -7.9753225000000e+00\r\n613 618  8.0533082000000e+01\r\n614 618 -1.3044827000000e+01\r\n615 618 -8.0758350000000e+00\r\n616 618 -6.3782403000000e+02\r\n617 618  9.8074874000000e+01\r\n618 618  1.8540423000000e+01\r\n1722 618 -2.4684361000000e+00\r\n619 619  1.0000000000000e+00\r\n620 620  1.0000000000000e+00\r\n621 621  1.0000000000000e+00\r\n622 622  1.0000000000000e+00\r\n623 623  1.0000000000000e+00\r\n624 624  1.0000000000000e+00\r\n625 625  1.0000000000000e+00\r\n626 626  1.0000000000000e+00\r\n627 627  1.0000000000000e+00\r\n628 628  1.0000000000000e+00\r\n629 629  1.0000000000000e+00\r\n630 630  1.0000000000000e+00\r\n631 631  1.0000000000000e+00\r\n632 632  1.0000000000000e+00\r\n633 633  1.0000000000000e+00\r\n586 634 -6.7886457000000e-02\r\n588 634 -1.2105267000000e-05\r\n634 634  2.2985844000000e+02\r\n636 634  5.9672425000000e-04\r\n637 634 -4.1488017000000e-02\r\n639 634 -1.2103840000000e-05\r\n682 634 -1.1404836000000e-03\r\n684 634 -1.1902603000000e-05\r\n1738 634 -6.3308042000000e-02\r\n1740 634 -2.3087268000000e-05\r\n586 635  2.8870110000000e+00\r\n588 635 -1.9104687000000e+00\r\n634 635 -1.4334945000000e+02\r\n635 635 -4.3819004000000e+01\r\n636 635  9.3800710000000e+00\r\n637 635  8.5673652000000e+00\r\n639 635 -1.9103693000000e+00\r\n684 635 -1.9106725000000e+00\r\n1740 635 -3.6436389000000e+00\r\n586 636  4.8802034000000e+00\r\n587 636 -7.9054791000000e-01\r\n588 636 -3.2294562000000e+00\r\n634 636 -2.4231791000000e+02\r\n635 636  3.7196344000000e+01\r\n636 636  1.5856072000000e+01\r\n637 636  1.4482274000000e+01\r\n638 636 -2.3459947000000e+00\r\n639 636 -3.2292883000000e+00\r\n684 636 -3.2298007000000e+00\r\n1740 636 -6.1592072000000e+00\r\n589 637 -6.3956856000000e-02\r\n591 637 -1.3421741000000e-05\r\n634 637 -1.1597657000000e-03\r\n636 637 -1.2103840000000e-05\r\n637 637  2.2995780000000e+02\r\n639 637  6.1212934000000e-04\r\n640 637 -1.5422862000000e-01\r\n642 637 -1.3429905000000e-05\r\n685 637 -1.1663975000000e-03\r\n687 637 -1.2173052000000e-05\r\n1741 637 -6.0973523000000e-02\r\n1743 637 -2.3473926000000e-05\r\n591 638 -2.0833663000000e+00\r\n636 638 -1.9103693000000e+00\r\n637 638 -1.4944624000000e+02\r\n638 638 -4.3826616000000e+01\r\n639 638  1.1637723000000e+01\r\n640 638  1.7561895000000e+01\r\n642 638 -2.0848288000000e+00\r\n687 638 -1.9104756000000e+00\r\n1743 638 -3.6437574000000e+00\r\n591 639 -3.5217201000000e+00\r\n636 639 -3.2292883000000e+00\r\n637 639 -2.5262376000000e+02\r\n638 639  3.8846729000000e+01\r\n639 639  1.9672395000000e+01\r\n640 639  2.9686608000000e+01\r\n641 639 -4.8089082000000e+00\r\n642 639 -3.5241921000000e+00\r\n687 639 -3.2294658000000e+00\r\n1743 639 -6.1594038000000e+00\r\n592 640 -6.6318298000000e-02\r\n594 640 -1.6110912000000e-05\r\n637 640 -1.2868267000000e-03\r\n639 640 -1.3429905000000e-05\r\n640 640  2.7605201000000e+02\r\n642 640  7.2487228000000e-04\r\n643 640 -3.2951707000000e-01\r\n645 640 -1.6403515000000e-05\r\n688 640 -1.3144753000000e-03\r\n690 640 -1.3718459000000e-05\r\n1744 640 -5.2938282000000e-02\r\n1746 640 -2.0166959000000e-05\r\n594 641 -2.4258745000000e+00\r\n639 641 -2.0848288000000e+00\r\n640 641 -1.8874184000000e+02\r\n641 641 -5.2601941000000e+01\r\n642 641  1.2107669000000e+01\r\n643 641  3.0495022000000e+01\r\n645 641 -2.4701913000000e+00\r\n690 641 -2.0841773000000e+00\r\n1746 641 -3.0366821000000e+00\r\n594 642 -4.1006982000000e+00\r\n639 642 -3.5241921000000e+00\r\n640 642 -3.1904920000000e+02\r\n641 642  4.9165927000000e+01\r\n642 642  2.0466800000000e+01\r\n643 642  5.1548785000000e+01\r\n644 642 -8.3501761000000e+00\r\n645 642 -4.1756113000000e+00\r\n690 642 -3.5230932000000e+00\r\n1746 642 -5.1332074000000e+00\r\n595 643 -6.8362792000000e-02\r\n597 643 -1.9175571000000e-05\r\n640 643 -1.5717520000000e-03\r\n642 643 -1.6403515000000e-05\r\n643 643  3.2214757000000e+02\r\n645 643  8.4329072000000e-04\r\n646 643 -5.2465201000000e-01\r\n648 643 -1.9795671000000e-05\r\n691 643 -1.6557416000000e-03\r\n693 643 -1.7280069000000e-05\r\n1747 643 -2.9494763000000e-02\r\n1749 643 -1.8063337000000e-05\r\n597 644 -2.7649448000000e+00\r\n642 644 -2.4701913000000e+00\r\n643 644 -2.3400402000000e+02\r\n644 644 -6.1379794000000e+01\r\n645 644  1.3221950000000e+01\r\n646 644  4.9398648000000e+01\r\n648 644 -2.8547062000000e+00\r\n693 644 -2.5206038000000e+00\r\n1749 644 -2.6045985000000e+00\r\n597 645 -4.6738596000000e+00\r\n642 645 -4.1756113000000e+00\r\n643 645 -3.9556015000000e+02\r\n644 645  6.1111547000000e+01\r\n645 645  2.2350372000000e+01\r\n646 645  8.3503422000000e+01\r\n647 645 -1.3525992000000e+01\r\n648 645 -4.8255923000000e+00\r\n693 645 -4.2608252000000e+00\r\n1749 645 -4.4028107000000e+00\r\n598 646 -2.2283947000000e-01\r\n600 646 -2.3751003000000e-05\r\n643 646 -1.8967816000000e-03\r\n645 646 -1.9795671000000e-05\r\n646 646  3.6847470000000e+02\r\n648 646  9.6544672000000e-04\r\n649 646 -8.1318431000000e-01\r\n651 646 -2.4093738000000e-05\r\n694 646 -2.0286485000000e-03\r\n696 646 -2.1171893000000e-05\r\n1750 646 -1.5824708000000e-03\r\n1752 646 -1.6515382000000e-05\r\n598 647  8.4749399000000e+00\r\n600 647 -3.2334390000000e+00\r\n645 647 -2.8547062000000e+00\r\n646 647 -2.9669662000000e+02\r\n647 647 -7.0166544000000e+01\r\n648 647  1.4612125000000e+01\r\n649 647  7.7270965000000e+01\r\n651 647 -3.2805685000000e+00\r\n696 647 -2.9554628000000e+00\r\n1752 647 -2.2800486000000e+00\r\n598 648  1.4326038000000e+01\r\n599 648 -2.3204550000000e+00\r\n600 648 -5.4658053000000e+00\r\n645 648 -4.8255923000000e+00\r\n646 648 -5.0153595000000e+02\r\n647 648  7.7805696000000e+01\r\n648 648  2.4700333000000e+01\r\n649 648  1.3061884000000e+02\r\n650 648 -2.1156940000000e+01\r\n651 648 -5.5454729000000e+00\r\n696 648 -4.9959143000000e+00\r\n1752 648 -3.8541941000000e+00\r\n601 649 -8.4451639000000e-01\r\n603 649 -2.9343079000000e-05\r\n646 649 -2.3086138000000e-03\r\n648 649 -2.4093738000000e-05\r\n649 649  4.2671000000000e+02\r\n651 649  1.1198369000000e-03\r\n652 649 -1.0475849000000e+00\r\n654 649 -3.0681625000000e-05\r\n697 649 -2.5012740000000e-03\r\n699 649 -2.6104427000000e-05\r\n1753 649 -1.4416386000000e-03\r\n1755 649 -1.5045593000000e-05\r\n601 650  6.7680332000000e+01\r\n603 650 -3.7128363000000e+00\r\n648 650 -3.2805685000000e+00\r\n649 650 -4.0881465000000e+02\r\n650 650 -8.1159344000000e+01\r\n651 650  1.6340623000000e+01\r\n652 650  9.7265790000000e+01\r\n654 650 -3.8824558000000e+00\r\n699 650 -3.4832142000000e+00\r\n1755 650 -1.9724001000000e+00\r\n601 651  1.1440675000000e+02\r\n602 651 -1.8529986000000e+01\r\n603 651 -6.2761737000000e+00\r\n648 651 -5.5454729000000e+00\r\n649 651 -6.9105976000000e+02\r\n650 651  1.0788868000000e+02\r\n651 651  2.7622172000000e+01\r\n652 651  1.6441797000000e+02\r\n653 651 -2.6630093000000e+01\r\n654 651 -6.5628982000000e+00\r\n699 651 -5.8880212000000e+00\r\n1755 651 -3.3341428000000e+00\r\n604 652 -4.0053101000000e+00\r\n606 652 -3.7672337000000e-05\r\n649 652 -2.9398520000000e-03\r\n651 652 -3.0681625000000e-05\r\n652 652  5.2063920000000e+02\r\n654 652  1.3599029000000e-03\r\n655 652 -3.4660619000000e-03\r\n657 652 -3.6173390000000e-05\r\n700 652 -3.1482507000000e-03\r\n702 652 -3.2856569000000e-05\r\n1756 652 -1.2296929000000e-03\r\n1758 652 -1.2833632000000e-05\r\n604 653  3.7637479000000e+02\r\n606 653 -4.4348850000000e+00\r\n651 653 -3.8824558000000e+00\r\n652 653 -6.7291882000000e+02\r\n653 653 -9.8742650000000e+01\r\n654 653  1.8725128000000e+01\r\n657 653 -4.5287714000000e+00\r\n702 653 -4.2455944000000e+00\r\n1758 653 -1.6222799000000e+00\r\n604 654  6.3622393000000e+02\r\n605 654 -1.0304043000000e+02\r\n606 654 -7.4967294000000e+00\r\n651 654 -6.5628982000000e+00\r\n652 654 -1.1375019000000e+03\r\n653 654  1.7922403000000e+02\r\n654 654  3.1652947000000e+01\r\n657 654 -7.6554309000000e+00\r\n702 654 -7.1767526000000e+00\r\n1758 654 -2.7423019000000e+00\r\n607 655 -9.7162808000000e-01\r\n609 655 -3.8115135000000e-05\r\n652 655 -1.0016969000000e+00\r\n654 655 -3.6173390000000e-05\r\n655 655  5.7604994000000e+02\r\n657 655  1.5023318000000e-03\r\n658 655 -3.4792827000000e-03\r\n660 655 -3.6311369000000e-05\r\n703 655 -3.4989709000000e-03\r\n705 655 -3.6516844000000e-05\r\n1759 655 -1.0719859000000e-03\r\n1761 655 -1.1187730000000e-05\r\n607 656  7.4628540000000e+01\r\n609 656 -4.7715009000000e+00\r\n652 656  9.7489376000000e+01\r\n654 656 -4.5287714000000e+00\r\n655 656 -5.0166834000000e+02\r\n656 656 -1.0967559000000e+02\r\n657 656  2.0323078000000e+01\r\n660 656 -4.7798171000000e+00\r\n705 656 -4.7714255000000e+00\r\n1761 656 -1.4592005000000e+00\r\n607 657  1.2615201000000e+02\r\n608 657 -2.0432140000000e+01\r\n609 657 -8.0657406000000e+00\r\n652 657  1.6479595000000e+02\r\n653 657 -2.6691085000000e+01\r\n654 657 -7.6554309000000e+00\r\n655 657 -8.4801969000000e+02\r\n656 657  1.3188810000000e+02\r\n657 657  3.4354116000000e+01\r\n660 657 -8.0798027000000e+00\r\n705 657 -8.0656140000000e+00\r\n1761 657 -2.4666309000000e+00\r\n610 658 -1.5987333000000e-01\r\n612 658 -3.6244739000000e-05\r\n655 658 -8.2628466000000e-01\r\n657 658 -3.6311369000000e-05\r\n658 658  5.7509413000000e+02\r\n660 658  1.4986357000000e-03\r\n661 658 -3.3828411000000e-03\r\n663 658 -3.5304860000000e-05\r\n706 658 -3.4459143000000e-03\r\n708 658 -3.5963121000000e-05\r\n1762 658 -1.0383418000000e-03\r\n1764 658 -1.0836605000000e-05\r\n612 659 -4.7703929000000e+00\r\n655 659  7.8714003000000e+01\r\n657 659 -4.7798171000000e+00\r\n658 659 -4.0830577000000e+02\r\n659 659 -1.0964765000000e+02\r\n660 659  2.0571294000000e+01\r\n663 659 -4.7794430000000e+00\r\n708 659 -4.7708020000000e+00\r\n1764 659 -1.4584898000000e+00\r\n612 660 -8.0638721000000e+00\r\n655 660  1.3305815000000e+02\r\n656 660 -2.1551510000000e+01\r\n657 660 -8.0798027000000e+00\r\n658 660 -6.9020007000000e+02\r\n659 660  1.0640089000000e+02\r\n660 660  3.4773710000000e+01\r\n663 660 -8.0791644000000e+00\r\n708 660 -8.0645636000000e+00\r\n1764 660 -2.4654311000000e+00\r\n613 661 -3.2860031000000e-03\r\n615 661 -3.4294215000000e-05\r\n658 661 -4.3816125000000e-01\r\n660 661 -3.5304860000000e-05\r\n661 661  5.7456493000000e+02\r\n663 661  1.4597886000000e-03\r\n709 661 -3.3981475000000e-03\r\n711 661 -3.5464605000000e-05\r\n1765 661 -2.1262248000000e-03\r\n1767 661 -1.0778205000000e-05\r\n615 662 -4.7713253000000e+00\r\n658 662  4.2804789000000e+01\r\n660 662 -4.7794430000000e+00\r\n661 662 -3.8206304000000e+02\r\n662 662 -1.0963121000000e+02\r\n663 662  1.5793919000000e+01\r\n709 662  9.6425004000000e+00\r\n711 662 -4.7718529000000e+00\r\n1767 662 -1.4589556000000e+00\r\n615 663 -8.0654413000000e+00\r\n658 663  7.2357161000000e+01\r\n659 663 -1.1719986000000e+01\r\n660 663 -8.0791644000000e+00\r\n661 663 -6.4583890000000e+02\r\n662 663  9.9258914000000e+01\r\n663 663  2.6698019000000e+01\r\n709 663  1.6299671000000e+01\r\n710 663 -2.6401245000000e+00\r\n711 663 -8.0663336000000e+00\r\n1767 663 -2.4662167000000e+00\r\n664 664  1.0000000000000e+00\r\n665 665  1.0000000000000e+00\r\n666 666  1.0000000000000e+00\r\n667 667  1.0000000000000e+00\r\n668 668  1.0000000000000e+00\r\n669 669  1.0000000000000e+00\r\n670 670  1.0000000000000e+00\r\n671 671  1.0000000000000e+00\r\n672 672  1.0000000000000e+00\r\n673 673  1.0000000000000e+00\r\n674 674  1.0000000000000e+00\r\n675 675  1.0000000000000e+00\r\n676 676  1.0000000000000e+00\r\n677 677  1.0000000000000e+00\r\n678 678  1.0000000000000e+00\r\n679 679  2.4128114000000e+02\r\n681 679  6.1053060000000e-04\r\n682 679 -3.6745224000000e-02\r\n684 679 -1.1963890000000e-05\r\n727 679 -1.2401056000000e-03\r\n729 679 -1.2942303000000e-05\r\n1783 679 -6.3456979000000e-02\r\n1785 679 -2.1232487000000e-05\r\n679 680 -1.4777267000000e+02\r\n680 680 -4.6000009000000e+01\r\n681 680  7.5709913000000e+00\r\n682 680  9.2686398000000e+00\r\n684 680 -1.9555350000000e+00\r\n729 680 -2.1400582000000e+00\r\n1785 680 -3.4702348000000e+00\r\n679 681 -2.4979476000000e+02\r\n680 681  3.8330186000000e+01\r\n681 681  1.2797995000000e+01\r\n682 681  1.5667699000000e+01\r\n683 681 -2.5380787000000e+00\r\n684 681 -3.3056342000000e+00\r\n729 681 -3.6175519000000e+00\r\n1785 681 -5.8660810000000e+00\r\n634 682 -1.1595734000000e-01\r\n636 682 -1.1902603000000e-05\r\n679 682 -1.1463560000000e-03\r\n681 682 -1.1963890000000e-05\r\n682 682  2.2992078000000e+02\r\n684 682  6.0799291000000e-04\r\n685 682 -5.3412268000000e-02\r\n687 682 -1.1896592000000e-05\r\n730 682 -1.1498448000000e-03\r\n732 682 -1.2000301000000e-05\r\n1786 682 -6.3594462000000e-02\r\n1788 682 -2.2712078000000e-05\r\n634 683  8.5387112000000e+00\r\n636 683 -1.9106725000000e+00\r\n681 683 -1.9555350000000e+00\r\n682 683 -1.5201540000000e+02\r\n683 683 -4.3818310000000e+01\r\n684 683  1.1383840000000e+01\r\n685 683  1.1580450000000e+01\r\n687 683 -1.9098309000000e+00\r\n732 683 -1.9571084000000e+00\r\n1788 683 -3.6457717000000e+00\r\n634 684  1.4433837000000e+01\r\n635 684 -2.3381730000000e+00\r\n636 684 -3.2298007000000e+00\r\n681 684 -3.3056342000000e+00\r\n682 684 -2.5696684000000e+02\r\n683 684  3.9571585000000e+01\r\n684 684  1.9243241000000e+01\r\n685 684  1.9575592000000e+01\r\n686 684 -3.1710985000000e+00\r\n687 684 -3.2283782000000e+00\r\n732 684 -3.3082960000000e+00\r\n1788 684 -6.1628125000000e+00\r\n637 685 -1.0399828000000e-01\r\n639 685 -1.2173052000000e-05\r\n682 685 -1.1399077000000e-03\r\n684 685 -1.1896592000000e-05\r\n685 685  2.2998800000000e+02\r\n687 685  6.0896425000000e-04\r\n688 685 -1.4493342000000e-01\r\n690 685 -1.2176631000000e-05\r\n733 685 -1.1487335000000e-03\r\n735 685 -1.1988703000000e-05\r\n1789 685 -6.2686689000000e-02\r\n1791 685 -2.3209883000000e-05\r\n637 686  5.5208100000000e+00\r\n639 686 -1.9104756000000e+00\r\n684 686 -1.9098309000000e+00\r\n685 686 -1.5431280000000e+02\r\n686 686 -4.3828808000000e+01\r\n687 686  1.1289908000000e+01\r\n688 686  1.6910541000000e+01\r\n690 686 -1.9111809000000e+00\r\n735 686 -1.9108935000000e+00\r\n1791 686 -3.6426013000000e+00\r\n637 687  9.3323711000000e+00\r\n638 687 -1.5117534000000e+00\r\n639 687 -3.2294658000000e+00\r\n684 687 -3.2283782000000e+00\r\n685 687 -2.6085019000000e+02\r\n686 687  4.0174310000000e+01\r\n687 687  1.9084451000000e+01\r\n688 687  2.8585561000000e+01\r\n689 687 -4.6305832000000e+00\r\n690 687 -3.2306580000000e+00\r\n735 687 -3.2301723000000e+00\r\n1791 687 -6.1574493000000e+00\r\n640 688 -1.0959146000000e-01\r\n642 688 -1.3718459000000e-05\r\n685 688 -1.1667404000000e-03\r\n687 688 -1.2176631000000e-05\r\n688 688  2.3007758000000e+02\r\n690 688  6.1374558000000e-04\r\n691 688 -2.4328091000000e-01\r\n693 688 -1.3979237000000e-05\r\n736 688 -1.1848147000000e-03\r\n738 688 -1.2365262000000e-05\r\n1792 688 -5.8185297000000e-02\r\n1794 688 -2.3977760000000e-05\r\n640 689  5.1372413000000e+00\r\n642 689 -2.0841773000000e+00\r\n687 689 -1.9111809000000e+00\r\n688 689 -1.6120435000000e+02\r\n689 689 -4.3837882000000e+01\r\n690 689  1.1678161000000e+01\r\n691 689  2.4198730000000e+01\r\n693 689 -2.1239615000000e+00\r\n738 689 -1.9111011000000e+00\r\n1794 689 -3.6428105000000e+00\r\n640 690  8.6839927000000e+00\r\n641 690 -1.4066924000000e+00\r\n642 690 -3.5230932000000e+00\r\n687 690 -3.2306580000000e+00\r\n688 690 -2.7249984000000e+02\r\n689 690  4.2037981000000e+01\r\n690 690  1.9740762000000e+01\r\n691 690  4.0905532000000e+01\r\n692 690 -6.6261574000000e+00\r\n693 690 -3.5903445000000e+00\r\n738 690 -3.2305253000000e+00\r\n1794 690 -6.1578069000000e+00\r\n643 691 -1.8009043000000e-01\r\n645 691 -1.7280069000000e-05\r\n688 691 -1.3394625000000e-03\r\n690 691 -1.3979237000000e-05\r\n691 691  2.8765248000000e+02\r\n693 691  7.5606631000000e-04\r\n694 691 -3.5662905000000e-01\r\n696 691 -1.7870173000000e-05\r\n739 691 -1.4366905000000e-03\r\n741 691 -1.4993952000000e-05\r\n1795 691 -4.5081617000000e-02\r\n1797 691 -2.0015607000000e-05\r\n643 692  8.6115155000000e+00\r\n645 692 -2.5206038000000e+00\r\n690 692 -2.1239615000000e+00\r\n691 692 -2.0758615000000e+02\r\n692 692 -5.4808161000000e+01\r\n693 692  1.2411776000000e+01\r\n694 692  3.4155028000000e+01\r\n696 692 -2.6069066000000e+00\r\n741 692 -2.2345164000000e+00\r\n1797 692 -2.9196208000000e+00\r\n643 693  1.4556894000000e+01\r\n644 693 -2.3579633000000e+00\r\n645 693 -4.2608252000000e+00\r\n690 693 -3.5903445000000e+00\r\n691 693 -3.5090337000000e+02\r\n692 693  5.4184103000000e+01\r\n693 693  2.0980854000000e+01\r\n694 693  5.7735619000000e+01\r\n695 693 -9.3521645000000e+00\r\n696 693 -4.4067113000000e+00\r\n741 693 -3.7772243000000e+00\r\n1797 693 -4.9353235000000e+00\r\n646 694 -3.5002965000000e-01\r\n648 694 -2.1171893000000e-05\r\n691 694 -1.7122843000000e-03\r\n693 694 -1.7870173000000e-05\r\n694 694  3.4530721000000e+02\r\n696 694  9.0444207000000e-04\r\n697 694 -4.7150985000000e-01\r\n699 694 -2.2409953000000e-05\r\n742 694 -1.8424100000000e-03\r\n744 694 -1.9228224000000e-05\r\n1798 694 -1.5534761000000e-02\r\n1800 694 -1.7423765000000e-05\r\n646 695  2.2515897000000e+01\r\n648 695 -2.9554628000000e+00\r\n693 695 -2.6069066000000e+00\r\n694 695 -2.6385430000000e+02\r\n695 695 -6.5783412000000e+01\r\n696 695  1.3891176000000e+01\r\n697 695  4.3574756000000e+01\r\n699 695 -3.1285009000000e+00\r\n744 695 -2.7607207000000e+00\r\n1800 695 -2.4321780000000e+00\r\n646 696  3.8060872000000e+01\r\n647 696 -6.1650064000000e+00\r\n648 696 -4.9959143000000e+00\r\n693 696 -4.4067113000000e+00\r\n694 696 -4.4601930000000e+02\r\n695 696  6.9023803000000e+01\r\n696 696  2.3481640000000e+01\r\n697 696  7.3658766000000e+01\r\n698 696 -1.1931066000000e+01\r\n699 696 -5.2884179000000e+00\r\n744 696 -4.6667223000000e+00\r\n1800 696 -4.1113536000000e+00\r\n649 697 -7.5095722000000e-01\r\n651 697 -2.6104427000000e-05\r\n694 697 -2.1472769000000e-03\r\n696 697 -2.2409953000000e-05\r\n697 697  4.1453605000000e+02\r\n699 697  1.0835157000000e-03\r\n700 697 -4.3707748000000e-01\r\n702 697 -2.8371765000000e-05\r\n745 697 -2.3028751000000e-03\r\n747 697 -2.4033846000000e-05\r\n1801 697 -1.4331548000000e-03\r\n1803 697 -1.4957052000000e-05\r\n649 698  6.0063016000000e+01\r\n651 698 -3.4832142000000e+00\r\n696 698 -3.1285009000000e+00\r\n697 698 -3.3647841000000e+02\r\n698 698 -7.8955712000000e+01\r\n699 698  1.5770532000000e+01\r\n700 698  3.9122168000000e+01\r\n702 698 -3.7857528000000e+00\r\n747 698 -3.3371646000000e+00\r\n1803 698 -2.0270036000000e+00\r\n649 699  1.0153045000000e+02\r\n650 699 -1.6445125000000e+01\r\n651 699 -5.8880212000000e+00\r\n696 699 -5.2884179000000e+00\r\n697 699 -5.6878271000000e+02\r\n698 699  8.8222558000000e+01\r\n699 699  2.6658491000000e+01\r\n700 699  6.6132068000000e+01\r\n701 699 -1.0711566000000e+01\r\n702 699 -6.3994322000000e+00\r\n747 699 -5.6411381000000e+00\r\n1803 699 -3.4264445000000e+00\r\n652 700 -1.5705797000000e+00\r\n654 700 -3.2856569000000e-05\r\n697 700 -2.7185258000000e-03\r\n699 700 -2.8371765000000e-05\r\n700 700  5.0676230000000e+02\r\n702 700  1.3209824000000e-03\r\n703 700 -3.2815703000000e-03\r\n705 700 -3.4247952000000e-05\r\n748 700 -2.9025049000000e-03\r\n750 700 -3.0291855000000e-05\r\n1804 700 -1.1989549000000e-03\r\n1806 700 -1.2512836000000e-05\r\n652 701  1.3569495000000e+02\r\n654 701 -4.2455944000000e+00\r\n699 701 -3.7857528000000e+00\r\n700 701 -4.2570079000000e+02\r\n701 701 -9.6514271000000e+01\r\n702 701  1.8276708000000e+01\r\n705 701 -4.4749500000000e+00\r\n750 701 -4.1004355000000e+00\r\n1806 701 -1.6590973000000e+00\r\n652 702  2.2937874000000e+02\r\n653 702 -3.7152092000000e+01\r\n654 702 -7.1767526000000e+00\r\n699 702 -6.3994322000000e+00\r\n700 702 -7.1960461000000e+02\r\n701 702  1.1174866000000e+02\r\n702 702  3.0894940000000e+01\r\n705 702 -7.5644520000000e+00\r\n750 702 -6.9313760000000e+00\r\n1806 702 -2.8045381000000e+00\r\n655 703 -8.7393253000000e-01\r\n657 703 -3.6516844000000e-05\r\n700 703 -1.5378390000000e-01\r\n702 703 -3.4247952000000e-05\r\n703 703  5.7511438000000e+02\r\n705 703  1.4971549000000e-03\r\n706 703 -3.4522739000000e-03\r\n708 703 -3.6029493000000e-05\r\n751 703 -3.3966575000000e-03\r\n753 703 -3.5449055000000e-05\r\n1807 703 -1.0485927000000e-03\r\n1809 703 -1.0943588000000e-05\r\n655 704  6.7319482000000e+01\r\n657 704 -4.7714255000000e+00\r\n700 704  1.6436817000000e+01\r\n702 704 -4.4749500000000e+00\r\n703 704 -4.1332039000000e+02\r\n704 704 -1.0966693000000e+02\r\n705 704  2.0268791000000e+01\r\n708 704 -4.7798503000000e+00\r\n753 704 -4.7704216000000e+00\r\n1809 704 -1.4597855000000e+00\r\n655 705  1.1379680000000e+02\r\n656 705 -1.8431643000000e+01\r\n657 705 -8.0656140000000e+00\r\n700 705  2.7784783000000e+01\r\n701 705 -4.5002953000000e+00\r\n702 705 -7.5644520000000e+00\r\n703 705 -6.9867647000000e+02\r\n704 705  1.0772560000000e+02\r\n705 705  3.4262351000000e+01\r\n708 705 -8.0798587000000e+00\r\n753 705 -8.0639167000000e+00\r\n1809 705 -2.4676190000000e+00\r\n658 706 -2.8639730000000e-01\r\n660 706 -3.5963121000000e-05\r\n703 706 -2.3772233000000e-01\r\n705 706 -3.6029493000000e-05\r\n706 706  5.7461766000000e+02\r\n708 706  1.4623046000000e-03\r\n709 706 -3.4034794000000e-03\r\n711 706 -3.5520251000000e-05\r\n1810 706 -1.0384528000000e-03\r\n1812 706 -1.0837763000000e-05\r\n658 707  1.1770645000000e+01\r\n660 707 -4.7708020000000e+00\r\n703 707  2.3067276000000e+01\r\n705 707 -4.7798503000000e+00\r\n706 707 -3.6441519000000e+02\r\n707 707 -1.0965817000000e+02\r\n708 707  1.5803139000000e+01\r\n711 707 -4.7796613000000e+00\r\n1812 707 -1.4604714000000e+00\r\n658 708  1.9897097000000e+01\r\n659 708 -3.2227639000000e+00\r\n660 708 -8.0645636000000e+00\r\n703 708  3.8992923000000e+01\r\n704 708 -6.3157445000000e+00\r\n705 708 -8.0798587000000e+00\r\n706 708 -6.1600743000000e+02\r\n707 708  9.4358729000000e+01\r\n708 708  2.6713622000000e+01\r\n711 708 -8.0795357000000e+00\r\n1812 708 -2.4687808000000e+00\r\n661 709 -9.2241827000000e-02\r\n663 709 -3.5464605000000e-05\r\n706 709 -2.4367706000000e-01\r\n708 709 -3.5520251000000e-05\r\n709 709  5.7444270000000e+02\r\n711 709  1.4257672000000e-03\r\n1813 709 -1.1013347000000e-02\r\n1815 709 -1.0844475000000e-05\r\n663 710 -4.7718529000000e+00\r\n706 710  2.1354776000000e+01\r\n708 710 -4.7796613000000e+00\r\n709 710 -3.5094102000000e+02\r\n710 710 -1.0965215000000e+02\r\n711 710  1.1023000000000e+01\r\n1815 710 -1.4591348000000e+00\r\n663 711 -8.0663336000000e+00\r\n706 711  3.6098097000000e+01\r\n707 711 -5.8469286000000e+00\r\n708 711 -8.0795357000000e+00\r\n709 711 -5.9323041000000e+02\r\n710 711  9.0685708000000e+01\r\n711 711  1.8633268000000e+01\r\n1815 711 -2.4665199000000e+00\r\n712 712  1.0000000000000e+00\r\n713 713  1.0000000000000e+00\r\n714 714  1.0000000000000e+00\r\n715 715  1.0000000000000e+00\r\n716 716  1.0000000000000e+00\r\n717 717  1.0000000000000e+00\r\n718 718  1.0000000000000e+00\r\n719 719  1.0000000000000e+00\r\n720 720  1.0000000000000e+00\r\n721 721  1.0000000000000e+00\r\n722 722  1.0000000000000e+00\r\n723 723  1.0000000000000e+00\r\n724 724  1.0000000000000e+00\r\n725 725  1.0000000000000e+00\r\n726 726  1.0000000000000e+00\r\n679 727 -5.0524872000000e-02\r\n681 727 -1.2942303000000e-05\r\n727 727  2.7575451000000e+02\r\n729 727  7.0388324000000e-04\r\n730 727 -1.2552775000000e-03\r\n732 727 -1.3100644000000e-05\r\n775 727 -1.3823857000000e-03\r\n777 727 -1.4427202000000e-05\r\n1831 727 -6.3023480000000e-02\r\n1833 727 -1.8396914000000e-05\r\n679 728  6.2654400000000e+00\r\n681 728 -2.1400582000000e+00\r\n727 728 -1.7223406000000e+02\r\n728 728 -5.2567430000000e+01\r\n729 728  9.7508953000000e+00\r\n730 728  7.6726354000000e+00\r\n732 728 -2.1364055000000e+00\r\n777 728 -2.4266808000000e+00\r\n1833 728 -3.0418515000000e+00\r\n679 729  1.0591093000000e+01\r\n680 729 -1.7157092000000e+00\r\n681 729 -3.6175519000000e+00\r\n727 729 -2.9114430000000e+02\r\n728 729  4.4733734000000e+01\r\n729 729  1.6482902000000e+01\r\n730 729  1.2969815000000e+01\r\n731 729 -2.1010516000000e+00\r\n732 729 -3.6113775000000e+00\r\n777 729 -4.1020580000000e+00\r\n1833 729 -5.1419423000000e+00\r\n682 730 -1.0974181000000e-01\r\n684 730 -1.2000301000000e-05\r\n727 730 -3.1715043000000e-02\r\n729 730 -1.3100644000000e-05\r\n730 730  2.4142916000000e+02\r\n732 730  6.3568310000000e-04\r\n733 730 -5.2575007000000e-02\r\n735 730 -1.1994335000000e-05\r\n778 730 -1.2365576000000e-03\r\n780 730 -1.2905275000000e-05\r\n1834 730 -6.3367554000000e-02\r\n1836 730 -2.1296887000000e-05\r\n682 731  7.9768355000000e+00\r\n684 731 -1.9571084000000e+00\r\n729 731 -2.1364055000000e+00\r\n730 731 -1.5824006000000e+02\r\n731 731 -4.6008688000000e+01\r\n732 731  1.1667628000000e+01\r\n733 731  1.1771221000000e+01\r\n735 731 -1.9562652000000e+00\r\n780 731 -2.1395018000000e+00\r\n1836 731 -3.4731796000000e+00\r\n682 732  1.3484043000000e+01\r\n683 732 -2.1843344000000e+00\r\n684 732 -3.3082960000000e+00\r\n729 732 -3.6113775000000e+00\r\n730 732 -2.6748900000000e+02\r\n731 732  4.1175183000000e+01\r\n732 732  1.9722955000000e+01\r\n733 732  1.9898073000000e+01\r\n734 732 -3.2233689000000e+00\r\n735 732 -3.3068706000000e+00\r\n780 732 -3.6166139000000e+00\r\n1836 732 -5.8710629000000e+00\r\n685 733 -1.0923002000000e-01\r\n687 733 -1.1988703000000e-05\r\n730 733 -1.1492732000000e-03\r\n732 733 -1.1994335000000e-05\r\n733 733  2.2997364000000e+02\r\n735 733  6.0811355000000e-04\r\n736 733 -1.2408179000000e-01\r\n738 733 -1.1983552000000e-05\r\n781 733 -1.1284540000000e-03\r\n783 733 -1.1777057000000e-05\r\n1837 733 -6.3341723000000e-02\r\n1839 733 -2.2857855000000e-05\r\n685 734  7.8766213000000e+00\r\n687 734 -1.9108935000000e+00\r\n732 734 -1.9562652000000e+00\r\n733 734 -1.5553723000000e+02\r\n734 734 -4.3828367000000e+01\r\n735 734  1.1336191000000e+01\r\n736 734  1.5778360000000e+01\r\n738 734 -1.9101879000000e+00\r\n783 734 -1.9106690000000e+00\r\n1839 734 -3.6432492000000e+00\r\n685 735  1.3314632000000e+01\r\n686 735 -2.1568618000000e+00\r\n687 735 -3.2301723000000e+00\r\n732 735 -3.3068706000000e+00\r\n733 735 -2.6291996000000e+02\r\n734 735  4.0511193000000e+01\r\n735 735  1.9162684000000e+01\r\n736 735  2.6671722000000e+01\r\n737 735 -4.3206013000000e+00\r\n738 735 -3.2289795000000e+00\r\n783 735 -3.2297921000000e+00\r\n1839 735 -6.1585434000000e+00\r\n688 736 -1.3003196000000e-01\r\n690 736 -1.2365262000000e-05\r\n733 736 -1.1482400000000e-03\r\n735 736 -1.1983552000000e-05\r\n736 736  2.3001051000000e+02\r\n738 736  6.1051613000000e-04\r\n739 736 -1.5214170000000e-01\r\n741 736 -1.2950488000000e-05\r\n784 736 -1.1609537000000e-03\r\n786 736 -1.2116238000000e-05\r\n1840 736 -6.1680865000000e-02\r\n1842 736 -2.3581201000000e-05\r\n688 737  9.0008987000000e+00\r\n690 737 -1.9111011000000e+00\r\n735 737 -1.9101879000000e+00\r\n736 737 -1.6126652000000e+02\r\n737 737 -4.3837874000000e+01\r\n738 737  1.1383674000000e+01\r\n739 737  2.0397004000000e+01\r\n741 737 -2.0017149000000e+00\r\n786 737 -1.9112524000000e+00\r\n1842 737 -3.6444874000000e+00\r\n688 738  1.5215119000000e+01\r\n689 738 -2.4646760000000e+00\r\n690 738 -3.2305253000000e+00\r\n735 738 -3.2289795000000e+00\r\n736 738 -2.7260493000000e+02\r\n737 738  4.2055632000000e+01\r\n738 738  1.9242960000000e+01\r\n739 738  3.4479096000000e+01\r\n740 738 -5.5852208000000e+00\r\n741 738 -3.3836988000000e+00\r\n786 738 -3.2307810000000e+00\r\n1842 738 -6.1606414000000e+00\r\n691 739 -2.3814062000000e-01\r\n693 739 -1.4993952000000e-05\r\n736 739 -1.2408899000000e-03\r\n738 739 -1.2950488000000e-05\r\n739 739  2.5318809000000e+02\r\n741 739  6.7070663000000e-04\r\n742 739 -2.7655441000000e-01\r\n744 739 -1.5803473000000e-05\r\n787 739 -1.2889535000000e-03\r\n789 739 -1.3452102000000e-05\r\n1843 739 -5.5112544000000e-02\r\n1845 739 -2.2226569000000e-05\r\n691 740  1.3212071000000e+01\r\n693 740 -2.2345164000000e+00\r\n738 740 -2.0017149000000e+00\r\n739 740 -1.8333979000000e+02\r\n740 740 -4.8235318000000e+01\r\n741 740  1.1962878000000e+01\r\n742 740  2.5091868000000e+01\r\n744 740 -2.3553143000000e+00\r\n789 740 -2.0535280000000e+00\r\n1845 740 -3.3123752000000e+00\r\n691 741  2.2333672000000e+01\r\n692 741 -3.6177164000000e+00\r\n693 741 -3.7772243000000e+00\r\n738 741 -3.3836988000000e+00\r\n739 741 -3.0991742000000e+02\r\n740 741  4.7854592000000e+01\r\n741 741  2.0222038000000e+01\r\n742 741  4.2415271000000e+01\r\n743 741 -6.8706306000000e+00\r\n744 741 -3.9814210000000e+00\r\n789 741 -3.4712812000000e+00\r\n1845 741 -5.5992353000000e+00\r\n694 742 -3.4772057000000e-01\r\n696 742 -1.9228224000000e-05\r\n739 742 -1.5142572000000e-03\r\n741 742 -1.5803473000000e-05\r\n742 742  3.2221786000000e+02\r\n744 742  8.4364185000000e-04\r\n745 742 -3.2405406000000e-01\r\n747 742 -2.0445989000000e-05\r\n790 742 -1.6677751000000e-03\r\n792 742 -1.7405656000000e-05\r\n1846 742 -4.1786403000000e-02\r\n1848 742 -1.8199507000000e-05\r\n694 743  2.3081303000000e+01\r\n696 743 -2.7607207000000e+00\r\n741 743 -2.3553143000000e+00\r\n742 743 -2.3689682000000e+02\r\n743 743 -6.1399215000000e+01\r\n744 743  1.3243956000000e+01\r\n745 743  2.9237469000000e+01\r\n747 743 -2.9356936000000e+00\r\n792 743 -2.5723639000000e+00\r\n1848 743 -2.6129498000000e+00\r\n694 744  3.9016635000000e+01\r\n695 744 -6.3199419000000e+00\r\n696 744 -4.6667223000000e+00\r\n741 744 -3.9814210000000e+00\r\n742 744 -4.0045039000000e+02\r\n743 744  6.1855639000000e+01\r\n744 744  2.2387581000000e+01\r\n745 744  4.9423017000000e+01\r\n746 744 -8.0055750000000e+00\r\n747 744 -4.9624965000000e+00\r\n792 744 -4.3483240000000e+00\r\n1848 744 -4.4169304000000e+00\r\n697 745 -5.5488178000000e-01\r\n699 745 -2.4033846000000e-05\r\n742 745 -1.9590937000000e-03\r\n744 745 -2.0445989000000e-05\r\n745 745  3.9127008000000e+02\r\n747 745  1.0222417000000e-03\r\n748 745 -3.0670813000000e-01\r\n750 745 -2.5872768000000e-05\r\n793 745 -2.1638333000000e-03\r\n795 745 -2.2582743000000e-05\r\n1849 745 -2.1586607000000e-02\r\n1851 745 -1.5462216000000e-05\r\n697 746  4.1144406000000e+01\r\n699 746 -3.3371646000000e+00\r\n744 746 -2.9356936000000e+00\r\n745 746 -2.9348485000000e+02\r\n746 746 -7.4565981000000e+01\r\n747 746  1.5258691000000e+01\r\n748 746  2.8224648000000e+01\r\n750 746 -3.5925698000000e+00\r\n795 746 -3.2380134000000e+00\r\n1851 746 -2.1468502000000e+00\r\n697 747  6.9550444000000e+01\r\n698 747 -1.1265575000000e+01\r\n699 747 -5.6411381000000e+00\r\n744 747 -4.9624965000000e+00\r\n745 747 -4.9610636000000e+02\r\n746 747  7.6678890000000e+01\r\n747 747  2.5793274000000e+01\r\n748 747  4.7710903000000e+01\r\n749 747 -7.7280713000000e+00\r\n750 747 -6.0728747000000e+00\r\n795 747 -5.4735325000000e+00\r\n1851 747 -3.6290334000000e+00\r\n700 748 -8.0505229000000e-01\r\n702 748 -3.0291855000000e-05\r\n745 748 -2.4790769000000e-03\r\n747 748 -2.5872768000000e-05\r\n748 748  4.8314666000000e+02\r\n750 748  1.2586842000000e-03\r\n751 748 -1.0306687000000e-01\r\n753 748 -3.2242448000000e-05\r\n796 748 -2.7353350000000e-03\r\n798 748 -2.8547194000000e-05\r\n1852 748 -6.9197351000000e-03\r\n1854 748 -1.2840853000000e-05\r\n700 749  6.0712756000000e+01\r\n702 749 -4.1004355000000e+00\r\n747 749 -3.5925698000000e+00\r\n748 749 -3.4528836000000e+02\r\n749 749 -9.2121217000000e+01\r\n750 749  1.7763898000000e+01\r\n751 749  7.7418258000000e+00\r\n753 749 -4.3643937000000e+00\r\n798 749 -3.9580552000000e+00\r\n1854 749 -1.7380630000000e+00\r\n700 750  1.0262884000000e+02\r\n701 750 -1.6623199000000e+01\r\n702 750 -6.9313760000000e+00\r\n747 750 -6.0728747000000e+00\r\n748 750 -5.8367545000000e+02\r\n749 750  8.9969790000000e+01\r\n750 750  3.0028088000000e+01\r\n751 750  1.3086782000000e+01\r\n752 750 -2.1197178000000e+00\r\n753 750 -7.3775710000000e+00\r\n798 750 -6.6906964000000e+00\r\n1854 750 -2.9380216000000e+00\r\n703 751 -6.6691780000000e-01\r\n705 751 -3.5449055000000e-05\r\n748 751 -3.0894068000000e-03\r\n750 751 -3.2242448000000e-05\r\n751 751  5.7476523000000e+02\r\n753 751  1.4569444000000e-03\r\n799 751 -3.3038625000000e-03\r\n801 751 -3.4480604000000e-05\r\n1855 751 -1.4370886000000e-02\r\n1857 751 -1.0849465000000e-05\r\n703 752  4.4649890000000e+01\r\n705 752 -4.7704216000000e+00\r\n750 752 -4.3643937000000e+00\r\n751 752 -3.7421213000000e+02\r\n752 752 -1.0966919000000e+02\r\n753 752  1.5329533000000e+01\r\n801 752 -4.7224174000000e+00\r\n1857 752 -1.4599415000000e+00\r\n703 753  7.5476138000000e+01\r\n704 753 -1.2225121000000e+01\r\n705 753 -8.0639167000000e+00\r\n750 753 -7.3775710000000e+00\r\n751 753 -6.3256788000000e+02\r\n752 753  9.7015417000000e+01\r\n753 753  2.5913031000000e+01\r\n801 753 -7.9827685000000e+00\r\n1857 753 -2.4678833000000e+00\r\n754 754  1.0000000000000e+00\r\n755 755  1.0000000000000e+00\r\n756 756  1.0000000000000e+00\r\n757 757  1.0000000000000e+00\r\n758 758  1.0000000000000e+00\r\n759 759  1.0000000000000e+00\r\n760 760  1.0000000000000e+00\r\n761 761  1.0000000000000e+00\r\n762 762  1.0000000000000e+00\r\n763 763  1.0000000000000e+00\r\n764 764  1.0000000000000e+00\r\n765 765  1.0000000000000e+00\r\n766 766  1.0000000000000e+00\r\n767 767  1.0000000000000e+00\r\n768 768  1.0000000000000e+00\r\n769 769  1.0000000000000e+00\r\n770 770  1.0000000000000e+00\r\n771 771  1.0000000000000e+00\r\n772 772  3.4465067000000e+02\r\n774 772  8.5349529000000e-04\r\n775 772 -1.5446407000000e-03\r\n777 772 -1.6120569000000e-05\r\n820 772 -1.6955321000000e-02\r\n822 772 -1.6827433000000e-05\r\n1876 772 -6.1746864000000e-02\r\n1878 772 -1.4279239000000e-05\r\n772 773 -2.0606605000000e+02\r\n773 773 -6.5688502000000e+01\r\n774 773  8.0134569000000e+00\r\n775 773  8.1670580000000e+00\r\n777 773 -2.7112761000000e+00\r\n822 773 -2.8642856000000e+00\r\n1878 773 -2.4305303000000e+00\r\n772 774 -3.4833405000000e+02\r\n773 774  5.3442501000000e+01\r\n774 774  1.3545947000000e+01\r\n775 774  1.3805595000000e+01\r\n776 774 -2.2364809000000e+00\r\n777 774 -4.5831412000000e+00\r\n822 774 -4.8417883000000e+00\r\n1878 774 -4.1085685000000e+00\r\n727 775 -8.0360452000000e-02\r\n729 775 -1.4427202000000e-05\r\n772 775 -1.6347658000000e-02\r\n774 775 -1.6120569000000e-05\r\n775 775  3.1027071000000e+02\r\n777 775  8.0301749000000e-04\r\n778 775 -1.4011493000000e-03\r\n780 775 -1.4623028000000e-05\r\n823 775 -9.4939016000000e-03\r\n825 775 -1.6134123000000e-05\r\n1879 775 -6.2288830000000e-02\r\n1881 775 -1.6074153000000e-05\r\n727 776  1.0544002000000e+01\r\n729 776 -2.4266808000000e+00\r\n774 776 -2.7112761000000e+00\r\n775 776 -1.9758860000000e+02\r\n776 776 -5.9131265000000e+01\r\n777 776  1.2985718000000e+01\r\n778 776  8.9515889000000e+00\r\n780 776 -2.4240280000000e+00\r\n825 776 -2.7135730000000e+00\r\n1881 776 -2.7035268000000e+00\r\n727 777  1.7823566000000e+01\r\n728 777 -2.8873665000000e+00\r\n729 777 -4.1020580000000e+00\r\n774 777 -4.5831412000000e+00\r\n775 777 -3.3400353000000e+02\r\n776 777  5.1391010000000e+01\r\n777 777  2.1951045000000e+01\r\n778 777  1.5131755000000e+01\r\n779 777 -2.4513007000000e+00\r\n780 777 -4.0975736000000e+00\r\n825 777 -4.5870206000000e+00\r\n1881 777 -4.5700380000000e+00\r\n730 778 -4.7710277000000e-02\r\n732 778 -1.2905275000000e-05\r\n775 778 -9.7353670000000e-03\r\n777 778 -1.4623028000000e-05\r\n778 778  2.7578622000000e+02\r\n780 778  7.1734272000000e-04\r\n781 778 -3.2091054000000e-02\r\n783 778 -1.2554981000000e-05\r\n826 778 -1.3328196000000e-03\r\n828 778 -1.3909909000000e-05\r\n1882 778 -6.2920115000000e-02\r\n1884 778 -1.8339563000000e-05\r\n730 779  9.0787260000000e+00\r\n732 779 -2.1395018000000e+00\r\n777 779 -2.4240280000000e+00\r\n778 779 -1.7892355000000e+02\r\n779 779 -5.2573077000000e+01\r\n780 779  1.2029808000000e+01\r\n781 779  1.1556585000000e+01\r\n783 779 -2.0814907000000e+00\r\n828 779 -2.3386791000000e+00\r\n1884 779 -3.0402072000000e+00\r\n730 780  1.5346678000000e+01\r\n731 780 -2.4860947000000e+00\r\n732 780 -3.6166139000000e+00\r\n777 780 -4.0975736000000e+00\r\n778 780 -3.0245236000000e+02\r\n779 780  4.6551825000000e+01\r\n780 780  2.0335185000000e+01\r\n781 780  1.9535251000000e+01\r\n782 780 -3.1646251000000e+00\r\n783 780 -3.5185518000000e+00\r\n828 780 -3.9533031000000e+00\r\n1884 780 -5.1391662000000e+00\r\n733 781 -6.4501178000000e-02\r\n735 781 -1.1777057000000e-05\r\n778 781 -1.2029931000000e-03\r\n780 781 -1.2554981000000e-05\r\n781 781  2.2988296000000e+02\r\n783 781  6.0793532000000e-04\r\n784 781 -7.1293148000000e-02\r\n786 781 -1.1759384000000e-05\r\n829 781 -1.1352142000000e-03\r\n831 781 -1.1847609000000e-05\r\n1885 781 -6.3524363000000e-02\r\n1887 781 -2.2487696000000e-05\r\n733 782  8.9962395000000e+00\r\n735 782 -1.9106690000000e+00\r\n780 782 -2.0814907000000e+00\r\n781 782 -1.5514131000000e+02\r\n782 782 -4.3822323000000e+01\r\n783 782  1.1509553000000e+01\r\n784 782  1.4254211000000e+01\r\n786 782 -1.9078821000000e+00\r\n831 782 -1.9564876000000e+00\r\n1887 782 -3.6481002000000e+00\r\n733 783  1.5207231000000e+01\r\n734 783 -2.4634745000000e+00\r\n735 783 -3.2297921000000e+00\r\n780 783 -3.5185518000000e+00\r\n781 783 -2.6225068000000e+02\r\n782 783  4.0418167000000e+01\r\n783 783  1.9455737000000e+01\r\n784 783  2.4095299000000e+01\r\n785 783 -3.9032848000000e+00\r\n786 783 -3.2250813000000e+00\r\n831 783 -3.3072448000000e+00\r\n1887 783 -6.1667448000000e+00\r\n736 784 -1.1725771000000e-01\r\n738 784 -1.2116238000000e-05\r\n781 784 -1.1267607000000e-03\r\n783 784 -1.1759384000000e-05\r\n784 784  2.2994354000000e+02\r\n786 784  6.0877046000000e-04\r\n787 784 -9.2996664000000e-02\r\n789 784 -1.2390710000000e-05\r\n832 784 -1.1361215000000e-03\r\n834 784 -1.1857078000000e-05\r\n1888 784 -6.3099117000000e-02\r\n1890 784 -2.3135219000000e-05\r\n736 785  1.0506499000000e+01\r\n738 785 -1.9112524000000e+00\r\n783 785 -1.9078821000000e+00\r\n784 785 -1.5977102000000e+02\r\n785 785 -4.3834704000000e+01\r\n786 785  1.1338339000000e+01\r\n787 785  1.7391223000000e+01\r\n789 785 -1.9546905000000e+00\r\n834 785 -1.9103239000000e+00\r\n1890 785 -3.6492619000000e+00\r\n736 786  1.7760186000000e+01\r\n737 786 -2.8769849000000e+00\r\n738 786 -3.2307810000000e+00\r\n783 786 -3.2250813000000e+00\r\n784 786 -2.7007692000000e+02\r\n785 786  4.1654598000000e+01\r\n786 786  1.9166326000000e+01\r\n787 786  2.9398124000000e+01\r\n788 786 -4.7622225000000e+00\r\n789 786 -3.3042088000000e+00\r\n834 786 -3.2292116000000e+00\r\n1890 786 -6.1687123000000e+00\r\n739 787 -1.8435981000000e-01\r\n741 787 -1.3452102000000e-05\r\n784 787 -1.1872531000000e-03\r\n786 787 -1.2390710000000e-05\r\n787 787  2.4151139000000e+02\r\n789 787  6.4034340000000e-04\r\n790 787 -1.2935698000000e-01\r\n792 787 -1.4531498000000e-05\r\n835 787 -1.2285658000000e-03\r\n837 787 -1.2821869000000e-05\r\n1891 787 -6.0194981000000e-02\r\n1893 787 -2.2755466000000e-05\r\n739 788  1.3942145000000e+01\r\n741 788 -2.0535280000000e+00\r\n786 788 -1.9546905000000e+00\r\n787 788 -1.7286665000000e+02\r\n788 788 -4.6041311000000e+01\r\n789 788  1.1712269000000e+01\r\n790 788  2.0478718000000e+01\r\n792 788 -2.2184736000000e+00\r\n837 788 -2.0067788000000e+00\r\n1893 788 -3.4736169000000e+00\r\n739 789  2.3567784000000e+01\r\n740 789 -3.8176844000000e+00\r\n741 789 -3.4712812000000e+00\r\n786 789 -3.3042088000000e+00\r\n787 789 -2.9221357000000e+02\r\n788 789  4.5098157000000e+01\r\n789 789  1.9798408000000e+01\r\n790 789  3.4617200000000e+01\r\n791 789 -5.6075503000000e+00\r\n792 789 -3.7501050000000e+00\r\n837 789 -3.3922563000000e+00\r\n1893 789 -5.8717972000000e+00\r\n742 790 -3.8295568000000e-01\r\n744 790 -1.7405656000000e-05\r\n787 790 -1.3923791000000e-03\r\n789 790 -1.4531498000000e-05\r\n790 790  2.9929629000000e+02\r\n792 790  7.8507417000000e-04\r\n793 790 -3.2737127000000e-01\r\n795 790 -1.9053771000000e-05\r\n838 790 -1.5647942000000e-03\r\n840 790 -1.6330900000000e-05\r\n1894 790 -5.3320545000000e-02\r\n1896 790 -1.8974124000000e-05\r\n742 791  2.1121733000000e+01\r\n744 791 -2.5723639000000e+00\r\n789 791 -2.2184736000000e+00\r\n790 791 -2.1642027000000e+02\r\n791 791 -5.7020556000000e+01\r\n792 791  1.2900552000000e+01\r\n793 791  2.3913941000000e+01\r\n795 791 -2.8160557000000e+00\r\n840 791 -2.4830562000000e+00\r\n1896 791 -2.8041797000000e+00\r\n742 792  3.5704177000000e+01\r\n743 792 -5.7835004000000e+00\r\n744 792 -4.3483240000000e+00\r\n789 792 -3.7501050000000e+00\r\n790 792 -3.6583682000000e+02\r\n791 792  5.6448122000000e+01\r\n792 792  2.1807090000000e+01\r\n793 792  4.0424126000000e+01\r\n794 792 -6.5480560000000e+00\r\n795 792 -4.7602606000000e+00\r\n840 792 -4.1973582000000e+00\r\n1896 792 -4.7401854000000e+00\r\n745 793 -4.6302039000000e-01\r\n747 793 -2.2582743000000e-05\r\n790 793 -1.8256942000000e-03\r\n792 793 -1.9053771000000e-05\r\n793 793  3.9127995000000e+02\r\n795 793  1.0169382000000e-03\r\n796 793 -3.8635653000000e-01\r\n798 793 -2.4784809000000e-05\r\n841 793 -2.0770616000000e-03\r\n843 793 -2.1677154000000e-05\r\n1897 793 -4.4529385000000e-02\r\n1899 793 -1.5027311000000e-05\r\n745 794  3.1337242000000e+01\r\n747 794 -3.2380134000000e+00\r\n792 794 -2.8160557000000e+00\r\n793 794 -2.9176279000000e+02\r\n794 794 -7.4567079000000e+01\r\n795 794  1.5008424000000e+01\r\n796 794  3.6310525000000e+01\r\n798 794 -3.5539269000000e+00\r\n843 794 -3.2374225000000e+00\r\n1899 794 -2.1546054000000e+00\r\n745 795  5.2972422000000e+01\r\n746 795 -8.5805093000000e+00\r\n747 795 -5.4735325000000e+00\r\n792 795 -4.7602606000000e+00\r\n793 795 -4.9319535000000e+02\r\n794 795  7.6206877000000e+01\r\n795 795  2.5370222000000e+01\r\n796 795  6.1379251000000e+01\r\n797 795 -9.9422529000000e+00\r\n798 795 -6.0075522000000e+00\r\n843 795 -5.4725347000000e+00\r\n1899 795 -3.6421424000000e+00\r\n748 796 -4.7355919000000e-01\r\n750 796 -2.8547194000000e-05\r\n793 796 -2.3748308000000e-03\r\n795 796 -2.4784809000000e-05\r\n796 796  4.7143383000000e+02\r\n798 796  1.1989427000000e-03\r\n799 796 -1.8473176000000e-01\r\n801 796 -3.0784169000000e-05\r\n1900 796 -3.3230226000000e-02\r\n1902 796 -1.2848602000000e-05\r\n748 797  2.8960471000000e+01\r\n750 797 -3.9580552000000e+00\r\n795 797 -3.5539269000000e+00\r\n796 797 -3.1504032000000e+02\r\n797 797 -8.9932956000000e+01\r\n798 797  1.3571840000000e+01\r\n799 797  1.5843805000000e+01\r\n801 797 -4.2683282000000e+00\r\n1902 797 -1.7813940000000e+00\r\n748 798  4.8954780000000e+01\r\n749 798 -7.9295357000000e+00\r\n750 798 -6.6906964000000e+00\r\n795 798 -6.0075522000000e+00\r\n796 798 -5.3254415000000e+02\r\n797 798  8.1786007000000e+01\r\n798 798  2.2941832000000e+01\r\n799 798  2.6782368000000e+01\r\n800 798 -4.3381207000000e+00\r\n801 798 -7.2151819000000e+00\r\n1902 798 -3.0112683000000e+00\r\n751 799 -4.7209570000000e-01\r\n753 799 -3.4480604000000e-05\r\n796 799 -2.9496775000000e-03\r\n798 799 -3.0784169000000e-05\r\n799 799  5.6309388000000e+02\r\n801 799  1.3931534000000e-03\r\n1903 799 -3.2800322000000e-02\r\n1905 799 -1.0878457000000e-05\r\n751 800  2.5400288000000e+01\r\n753 800 -4.7224174000000e+00\r\n798 800 -4.2683282000000e+00\r\n799 800 -3.4835832000000e+02\r\n800 800 -1.0748533000000e+02\r\n801 800  1.0492712000000e+01\r\n1905 800 -1.4898504000000e+00\r\n751 801  4.2936615000000e+01\r\n752 801 -6.9546765000000e+00\r\n753 801 -7.9827685000000e+00\r\n798 801 -7.2151819000000e+00\r\n799 801 -5.8886449000000e+02\r\n800 801  9.0023638000000e+01\r\n801 801  1.7736873000000e+01\r\n1905 801 -2.5184421000000e+00\r\n802 802  1.0000000000000e+00\r\n803 803  1.0000000000000e+00\r\n804 804  1.0000000000000e+00\r\n805 805  1.0000000000000e+00\r\n806 806  1.0000000000000e+00\r\n807 807  1.0000000000000e+00\r\n808 808  1.0000000000000e+00\r\n809 809  1.0000000000000e+00\r\n810 810  1.0000000000000e+00\r\n811 811  1.0000000000000e+00\r\n812 812  1.0000000000000e+00\r\n813 813  1.0000000000000e+00\r\n814 814  1.0000000000000e+00\r\n815 815  1.0000000000000e+00\r\n816 816  1.0000000000000e+00\r\n817 817  1.0000000000000e+00\r\n818 818  1.0000000000000e+00\r\n819 819  1.0000000000000e+00\r\n772 820 -1.6123710000000e-03\r\n774 820 -1.6827433000000e-05\r\n820 820  3.4466858000000e+02\r\n822 820  8.7085051000000e-04\r\n823 820 -1.6123285000000e-03\r\n825 820 -1.6826990000000e-05\r\n868 820 -2.6112782000000e-02\r\n870 820 -1.6734138000000e-05\r\n1924 820 -6.1603359000000e-02\r\n1926 820 -1.4191919000000e-05\r\n772 821  4.0042888000000e+00\r\n774 821 -2.8642856000000e+00\r\n820 821 -2.0657734000000e+02\r\n821 821 -6.0270803000000e+01\r\n822 821  1.1026543000000e+01\r\n823 821  4.6647492000000e+00\r\n825 821 -2.8613005000000e+00\r\n870 821 -2.8643717000000e+00\r\n1926 821 -2.4292229000000e+00\r\n772 822  6.7688497000000e+00\r\n773 822 -1.0965447000000e+00\r\n774 822 -4.8417883000000e+00\r\n820 822 -3.4919834000000e+02\r\n821 822  6.2745862000000e+01\r\n822 822  1.8639267000000e+01\r\n823 822  7.8852921000000e+00\r\n824 822 -1.2774069000000e+00\r\n825 822 -4.8367423000000e+00\r\n870 822 -4.8419339000000e+00\r\n1926 822 -4.1063585000000e+00\r\n775 823 -1.5459394000000e-03\r\n777 823 -1.6134123000000e-05\r\n820 823 -2.4181174000000e-02\r\n822 823 -1.6826990000000e-05\r\n823 823  3.4465958000000e+02\r\n825 823  8.8570179000000e-04\r\n826 823 -1.4820698000000e-03\r\n828 823 -1.5467551000000e-05\r\n871 823 -1.5995969000000e-03\r\n873 823 -1.6694117000000e-05\r\n1927 823 -6.2083342000000e-02\r\n1929 823 -1.4311777000000e-05\r\n775 824  7.5436455000000e+00\r\n777 824 -2.7135730000000e+00\r\n822 824 -2.8613005000000e+00\r\n823 824 -2.1303816000000e+02\r\n824 824 -6.5690055000000e+01\r\n825 824  1.3480709000000e+01\r\n826 824  7.5976270000000e+00\r\n828 824 -2.6002803000000e+00\r\n873 824 -2.8645800000000e+00\r\n1929 824 -2.4336098000000e+00\r\n775 825  1.2751770000000e+01\r\n776 825 -2.0657632000000e+00\r\n777 825 -4.5870206000000e+00\r\n822 825 -4.8367423000000e+00\r\n823 825 -3.6011950000000e+02\r\n824 825  5.5347981000000e+01\r\n825 825  2.2787778000000e+01\r\n826 825  1.2843021000000e+01\r\n827 825 -2.0805458000000e+00\r\n828 825 -4.3955109000000e+00\r\n873 825 -4.8422821000000e+00\r\n1929 825 -4.1137712000000e+00\r\n778 826 -3.8541788000000e-02\r\n780 826 -1.3909909000000e-05\r\n823 826 -5.9415082000000e-02\r\n825 826 -1.5467551000000e-05\r\n826 826  2.8730014000000e+02\r\n828 826  7.4559879000000e-04\r\n829 826 -1.2714392000000e-02\r\n831 826 -1.2947817000000e-05\r\n874 826 -1.3440434000000e-03\r\n876 826 -1.4027045000000e-05\r\n1930 826 -6.2647550000000e-02\r\n1932 826 -1.7362667000000e-05\r\n778 827  8.3044124000000e+00\r\n780 827 -2.3386791000000e+00\r\n825 827 -2.6002803000000e+00\r\n826 827 -1.8323488000000e+02\r\n827 827 -5.4755899000000e+01\r\n828 827  1.2428043000000e+01\r\n829 827  1.0036045000000e+01\r\n831 827 -2.1769877000000e+00\r\n876 827 -2.3869578000000e+00\r\n1932 827 -2.9189937000000e+00\r\n778 828  1.4037779000000e+01\r\n779 828 -2.2740776000000e+00\r\n780 828 -3.9533031000000e+00\r\n825 828 -4.3955109000000e+00\r\n826 828 -3.0974023000000e+02\r\n827 828  4.7649979000000e+01\r\n828 828  2.1008360000000e+01\r\n829 828  1.6964930000000e+01\r\n830 828 -2.7482673000000e+00\r\n831 828 -3.6799801000000e+00\r\n876 828 -4.0349134000000e+00\r\n1932 828 -4.9342670000000e+00\r\n781 829 -5.0980577000000e-02\r\n783 829 -1.1847609000000e-05\r\n826 829 -1.2406339000000e-03\r\n828 829 -1.2947817000000e-05\r\n829 829  2.4133039000000e+02\r\n831 829  6.3401457000000e-04\r\n832 829 -4.0353251000000e-02\r\n834 829 -1.1828373000000e-05\r\n877 829 -1.1450563000000e-03\r\n879 829 -1.1950326000000e-05\r\n1933 829 -6.3485672000000e-02\r\n1935 829 -2.1059135000000e-05\r\n781 830  8.7901707000000e+00\r\n783 830 -1.9564876000000e+00\r\n828 830 -2.1769877000000e+00\r\n829 830 -1.5972654000000e+02\r\n830 830 -4.6006226000000e+01\r\n831 830  1.1574441000000e+01\r\n832 830  1.2440799000000e+01\r\n834 830 -1.9533845000000e+00\r\n879 830 -2.0049953000000e+00\r\n1935 830 -3.4774202000000e+00\r\n781 831  1.4858896000000e+01\r\n782 831 -2.4070718000000e+00\r\n783 831 -3.3072448000000e+00\r\n828 831 -3.6799801000000e+00\r\n829 831 -2.7000159000000e+02\r\n830 831  4.1588697000000e+01\r\n831 831  1.9565427000000e+01\r\n832 831  2.1029915000000e+01\r\n833 831 -3.4067479000000e+00\r\n834 831 -3.3019994000000e+00\r\n879 831 -3.3892421000000e+00\r\n1935 831 -5.8782276000000e+00\r\n784 832 -8.1700425000000e-02\r\n786 832 -1.1857078000000e-05\r\n829 832 -1.1333710000000e-03\r\n831 832 -1.1828373000000e-05\r\n832 832  2.2988232000000e+02\r\n834 832  6.0759939000000e-04\r\n835 832 -5.9511872000000e-02\r\n837 832 -1.2122750000000e-05\r\n880 832 -1.1122322000000e-03\r\n882 832 -1.1607759000000e-05\r\n1936 832 -6.3616243000000e-02\r\n1938 832 -2.2676231000000e-05\r\n784 833  1.0688462000000e+01\r\n786 833 -1.9103239000000e+00\r\n831 833 -1.9533845000000e+00\r\n832 833 -1.5760196000000e+02\r\n833 833 -4.3828011000000e+01\r\n834 833  1.1384557000000e+01\r\n835 833  1.5030646000000e+01\r\n837 833 -1.9532233000000e+00\r\n882 833 -1.9095173000000e+00\r\n1938 833 -3.6531824000000e+00\r\n784 834  1.8067775000000e+01\r\n785 834 -2.9268498000000e+00\r\n786 834 -3.2292116000000e+00\r\n831 834 -3.3019994000000e+00\r\n832 834 -2.6641036000000e+02\r\n833 834  4.1077746000000e+01\r\n834 834  1.9244453000000e+01\r\n835 834  2.5407804000000e+01\r\n836 834 -4.1158816000000e+00\r\n837 834 -3.3017287000000e+00\r\n882 834 -3.2278480000000e+00\r\n1938 834 -6.1753395000000e+00\r\n787 835 -1.2015405000000e-01\r\n789 835 -1.2821869000000e-05\r\n832 835 -1.1615777000000e-03\r\n834 835 -1.2122750000000e-05\r\n835 835  2.4140711000000e+02\r\n837 835  6.3818803000000e-04\r\n838 835 -7.9495381000000e-02\r\n840 835 -1.4154005000000e-05\r\n883 835 -1.1963318000000e-03\r\n885 835 -1.2485460000000e-05\r\n1939 835 -6.2279773000000e-02\r\n1941 835 -2.2219399000000e-05\r\n787 836  1.3639587000000e+01\r\n789 836 -2.0067788000000e+00\r\n834 836 -1.9532233000000e+00\r\n835 836 -1.6979047000000e+02\r\n836 836 -4.6034272000000e+01\r\n837 836  1.1661624000000e+01\r\n838 836  1.7694926000000e+01\r\n840 836 -2.2153792000000e+00\r\n885 836 -2.0036945000000e+00\r\n1941 836 -3.4773703000000e+00\r\n787 837  2.3056342000000e+01\r\n788 837 -3.7348969000000e+00\r\n789 837 -3.3922563000000e+00\r\n834 837 -3.3017287000000e+00\r\n835 837 -2.8701362000000e+02\r\n836 837  4.4274019000000e+01\r\n837 837  1.9712798000000e+01\r\n838 837  2.9911484000000e+01\r\n839 837 -4.8453611000000e+00\r\n840 837 -3.7448743000000e+00\r\n885 837 -3.3870428000000e+00\r\n1941 837 -5.8781421000000e+00\r\n790 838 -2.0433902000000e-01\r\n792 838 -1.6330900000000e-05\r\n835 838 -1.3562085000000e-03\r\n837 838 -1.4154005000000e-05\r\n838 838  2.9882746000000e+02\r\n840 838  7.8228312000000e-04\r\n841 838 -2.2783386000000e-02\r\n843 838 -1.8495824000000e-05\r\n886 838 -1.5362482000000e-03\r\n888 838 -1.6032981000000e-05\r\n1942 838 -5.9223097000000e-02\r\n1944 838 -1.8503913000000e-05\r\n790 839  1.9964062000000e+01\r\n792 839 -2.4830562000000e+00\r\n837 839 -2.2153792000000e+00\r\n838 839 -2.0562103000000e+02\r\n839 839 -5.7012907000000e+01\r\n840 839  1.2812149000000e+01\r\n841 839  1.4261129000000e+01\r\n843 839 -2.8123255000000e+00\r\n888 839 -2.4817049000000e+00\r\n1944 839 -2.8132636000000e+00\r\n790 840  3.3747250000000e+01\r\n791 840 -5.4666118000000e+00\r\n792 840 -4.1973582000000e+00\r\n837 840 -3.7448743000000e+00\r\n838 840 -3.4758178000000e+02\r\n839 840  5.3511216000000e+01\r\n840 840  2.1657654000000e+01\r\n841 840  2.4107012000000e+01\r\n842 840 -3.9050196000000e+00\r\n843 840 -4.7539550000000e+00\r\n888 840 -4.1950740000000e+00\r\n1944 840 -4.7555408000000e+00\r\n793 841 -6.1648801000000e-01\r\n795 841 -2.1677154000000e-05\r\n838 841 -1.7722328000000e-03\r\n840 841 -1.8495824000000e-05\r\n841 841  3.9105156000000e+02\r\n843 841  9.8930809000000e-04\r\n889 841 -2.0095705000000e-03\r\n891 841 -2.0972787000000e-05\r\n1945 841 -5.6386148000000e-02\r\n1947 841 -1.4393578000000e-05\r\n793 842  3.7103314000000e+01\r\n795 842 -3.2374225000000e+00\r\n840 842 -2.8123255000000e+00\r\n841 842 -2.6120857000000e+02\r\n842 842 -7.4574783000000e+01\r\n843 842  1.1401721000000e+01\r\n891 842 -3.1939497000000e+00\r\n1947 842 -2.1496197000000e+00\r\n793 843  6.2719392000000e+01\r\n794 843 -1.0159607000000e+01\r\n795 843 -5.4725347000000e+00\r\n840 843 -4.7539550000000e+00\r\n841 843 -4.4154665000000e+02\r\n842 843  6.7824365000000e+01\r\n843 843  1.9273457000000e+01\r\n891 843 -5.3990486000000e+00\r\n1947 843 -3.6337143000000e+00\r\n844 844  1.0000000000000e+00\r\n845 845  1.0000000000000e+00\r\n846 846  1.0000000000000e+00\r\n847 847  1.0000000000000e+00\r\n848 848  1.0000000000000e+00\r\n849 849  1.0000000000000e+00\r\n850 850  1.0000000000000e+00\r\n851 851  1.0000000000000e+00\r\n852 852  1.0000000000000e+00\r\n853 853  1.0000000000000e+00\r\n854 854  1.0000000000000e+00\r\n855 855  1.0000000000000e+00\r\n856 856  1.0000000000000e+00\r\n857 857  1.0000000000000e+00\r\n858 858  1.0000000000000e+00\r\n859 859  1.0000000000000e+00\r\n860 860  1.0000000000000e+00\r\n861 861  1.0000000000000e+00\r\n862 862  1.0000000000000e+00\r\n863 863  1.0000000000000e+00\r\n864 864  1.0000000000000e+00\r\n865 865  1.0000000000000e+00\r\n866 866  1.0000000000000e+00\r\n867 867  1.0000000000000e+00\r\n820 868 -1.6034316000000e-03\r\n822 868 -1.6734138000000e-05\r\n868 868  3.4466303000000e+02\r\n870 868  8.7042247000000e-04\r\n871 868 -1.5980291000000e-03\r\n873 868 -1.6677755000000e-05\r\n916 868 -1.1800204000000e-02\r\n918 868 -1.6632213000000e-05\r\n1972 868 -6.1592932000000e-02\r\n1974 868 -1.4105490000000e-05\r\n820 869  4.4809201000000e+00\r\n822 869 -2.8643717000000e+00\r\n868 869 -2.0522846000000e+02\r\n869 869 -6.0262267000000e+01\r\n870 869  1.1027649000000e+01\r\n871 869  2.8279019000000e+00\r\n873 869 -2.8615690000000e+00\r\n918 869 -2.8647960000000e+00\r\n1974 869 -2.4295537000000e+00\r\n820 870  7.5745473000000e+00\r\n821 870 -1.2270711000000e+00\r\n822 870 -4.8419339000000e+00\r\n868 870 -3.4691819000000e+02\r\n869 870  6.2397303000000e+01\r\n870 870  1.8641137000000e+01\r\n871 870  4.7802854000000e+00\r\n872 870 -7.7440273000000e-01\r\n873 870 -4.8371963000000e+00\r\n918 870 -4.8426511000000e+00\r\n1974 870 -4.1069176000000e+00\r\n823 871 -2.3809981000000e-02\r\n825 871 -1.6694117000000e-05\r\n868 871 -7.0844374000000e-02\r\n870 871 -1.6677755000000e-05\r\n871 871  3.4475336000000e+02\r\n873 871  8.8551476000000e-04\r\n874 871 -1.4651131000000e-03\r\n876 871 -1.5290583000000e-05\r\n919 871 -1.9760735000000e-02\r\n921 871 -1.6411306000000e-05\r\n1975 871 -6.1994042000000e-02\r\n1977 871 -1.4174587000000e-05\r\n823 872  6.3203559000000e+00\r\n825 872 -2.8645800000000e+00\r\n870 872 -2.8615690000000e+00\r\n871 872 -2.0969684000000e+02\r\n872 872 -6.5683722000000e+01\r\n873 872  1.3583208000000e+01\r\n874 872  5.4707735000000e+00\r\n876 872 -2.6017154000000e+00\r\n921 872 -2.8158806000000e+00\r\n1977 872 -2.4321006000000e+00\r\n823 873  1.0683921000000e+01\r\n824 873 -1.7307849000000e+00\r\n825 873 -4.8422821000000e+00\r\n870 873 -4.8371963000000e+00\r\n871 873 -3.5447129000000e+02\r\n872 873  5.4448839000000e+01\r\n873 873  2.2961043000000e+01\r\n874 873  9.2477889000000e+00\r\n875 873 -1.4981326000000e+00\r\n876 873 -4.3979361000000e+00\r\n921 873 -4.7599617000000e+00\r\n1977 873 -4.1112205000000e+00\r\n826 874 -1.6360339000000e-02\r\n828 874 -1.4027045000000e-05\r\n871 874 -5.5631807000000e-02\r\n873 874 -1.5290583000000e-05\r\n874 874  2.8727143000000e+02\r\n876 874  7.4492479000000e-04\r\n877 874 -1.2435232000000e-03\r\n879 874 -1.2977970000000e-05\r\n922 874 -1.3030250000000e-03\r\n924 874 -1.3598958000000e-05\r\n1978 874 -6.2596797000000e-02\r\n1980 874 -1.7146335000000e-05\r\n826 875  7.2214688000000e+00\r\n828 875 -2.3869578000000e+00\r\n873 875 -2.6017154000000e+00\r\n874 875 -1.7984791000000e+02\r\n875 875 -5.4747707000000e+01\r\n876 875  1.2427625000000e+01\r\n877 875  7.7206051000000e+00\r\n879 875 -2.1771781000000e+00\r\n924 875 -2.3380768000000e+00\r\n1980 875 -2.9175561000000e+00\r\n826 876  1.2207171000000e+01\r\n827 876 -1.9775386000000e+00\r\n828 876 -4.0349134000000e+00\r\n873 876 -4.3979361000000e+00\r\n874 876 -3.0401491000000e+02\r\n875 876  4.6742926000000e+01\r\n876 876  2.1007653000000e+01\r\n877 876  1.3050911000000e+01\r\n878 876 -2.1142229000000e+00\r\n879 876 -3.6803018000000e+00\r\n924 876 -3.9522850000000e+00\r\n1980 876 -4.9318369000000e+00\r\n829 877 -2.5620619000000e-02\r\n831 877 -1.1950326000000e-05\r\n874 877 -2.6518293000000e-03\r\n876 877 -1.2977970000000e-05\r\n877 877  2.4128914000000e+02\r\n879 877  6.3315052000000e-04\r\n880 877 -1.3810981000000e-02\r\n882 877 -1.1634779000000e-05\r\n925 877 -1.1006289000000e-03\r\n927 877 -1.1486661000000e-05\r\n1981 877 -6.3481695000000e-02\r\n1983 877 -2.0719887000000e-05\r\n829 878  8.1989485000000e+00\r\n831 878 -2.0049953000000e+00\r\n876 878 -2.1771781000000e+00\r\n877 878 -1.5653041000000e+02\r\n878 878 -4.5997623000000e+01\r\n879 878  1.1571691000000e+01\r\n880 878  9.8238567000000e+00\r\n882 878 -1.9520974000000e+00\r\n927 878 -1.9561967000000e+00\r\n1983 878 -3.4760615000000e+00\r\n829 879  1.3859495000000e+01\r\n830 879 -2.2451946000000e+00\r\n831 879 -3.3892421000000e+00\r\n876 879 -3.6803018000000e+00\r\n877 879 -2.6459887000000e+02\r\n878 879  4.0735007000000e+01\r\n879 879  1.9560777000000e+01\r\n880 879  1.6606239000000e+01\r\n881 879 -2.6901584000000e+00\r\n882 879 -3.2998235000000e+00\r\n927 879 -3.3067529000000e+00\r\n1983 879 -5.8759299000000e+00\r\n832 880 -5.0339268000000e-02\r\n834 880 -1.1607759000000e-05\r\n877 880 -1.1148212000000e-03\r\n879 880 -1.1634779000000e-05\r\n880 880  2.2981958000000e+02\r\n882 880  6.0621082000000e-04\r\n883 880 -1.8023531000000e-02\r\n885 880 -1.1876018000000e-05\r\n928 880 -1.0881183000000e-03\r\n930 880 -1.1356095000000e-05\r\n1984 880 -6.3837177000000e-02\r\n1986 880 -2.2231077000000e-05\r\n832 881  1.0360255000000e+01\r\n834 881 -1.9095173000000e+00\r\n879 881 -1.9520974000000e+00\r\n880 881 -1.5508784000000e+02\r\n881 881 -4.3818848000000e+01\r\n882 881  1.1386064000000e+01\r\n883 881  1.2831785000000e+01\r\n885 881 -1.9537229000000e+00\r\n930 881 -1.9090161000000e+00\r\n1986 881 -3.6567886000000e+00\r\n832 882  1.7512975000000e+01\r\n833 882 -2.8370121000000e+00\r\n834 882 -3.2278480000000e+00\r\n879 882 -3.2998235000000e+00\r\n880 882 -2.6216048000000e+02\r\n881 882  4.0412391000000e+01\r\n882 882  1.9247000000000e+01\r\n883 882  2.1690848000000e+01\r\n884 882 -3.5138060000000e+00\r\n885 882 -3.3025732000000e+00\r\n930 882 -3.2270008000000e+00\r\n1986 882 -6.1814354000000e+00\r\n835 883 -9.5382011000000e-02\r\n837 883 -1.2485460000000e-05\r\n880 883 -1.1379363000000e-03\r\n882 883 -1.1876018000000e-05\r\n883 883  2.4148168000000e+02\r\n885 883  6.3659101000000e-04\r\n886 883 -1.6867021000000e-01\r\n888 883 -1.3820054000000e-05\r\n931 883 -1.1826096000000e-03\r\n933 883 -1.2342249000000e-05\r\n1987 883 -6.3020186000000e-02\r\n1989 883 -2.1688252000000e-05\r\n835 884  1.3129917000000e+01\r\n837 884 -2.0036945000000e+00\r\n882 884 -1.9537229000000e+00\r\n883 884 -1.7274263000000e+02\r\n884 884 -4.6025611000000e+01\r\n885 884  1.1710275000000e+01\r\n886 884  2.1144376000000e+01\r\n888 884 -2.2179112000000e+00\r\n933 884 -2.0494640000000e+00\r\n1989 884 -3.4803075000000e+00\r\n835 885  2.2194797000000e+01\r\n836 885 -3.5953912000000e+00\r\n837 885 -3.3870428000000e+00\r\n882 885 -3.3025732000000e+00\r\n883 885 -2.9200397000000e+02\r\n884 885  4.5104546000000e+01\r\n885 885  1.9795037000000e+01\r\n886 885  3.5742431000000e+01\r\n887 885 -5.7900063000000e+00\r\n888 885 -3.7491545000000e+00\r\n933 885 -3.4644117000000e+00\r\n1989 885 -5.8831074000000e+00\r\n838 886 -1.8480862000000e-02\r\n840 886 -1.6032981000000e-05\r\n883 886 -1.3242099000000e-03\r\n885 886 -1.3820054000000e-05\r\n886 886  2.9865514000000e+02\r\n888 886  7.6469165000000e-04\r\n889 886 -2.0105532000000e-02\r\n891 886 -1.7925139000000e-05\r\n1990 886 -6.0966350000000e-02\r\n1992 886 -1.8146949000000e-05\r\n838 887  1.2425388000000e+01\r\n840 887 -2.4817049000000e+00\r\n885 887 -2.2179112000000e+00\r\n886 887 -1.9650986000000e+02\r\n887 887 -5.6998073000000e+01\r\n888 887  1.0289227000000e+01\r\n889 887  1.2667573000000e+01\r\n891 887 -2.7745677000000e+00\r\n1992 887 -2.8086301000000e+00\r\n838 888  2.1003875000000e+01\r\n839 888 -3.4023914000000e+00\r\n840 888 -4.1950740000000e+00\r\n885 888 -3.7491545000000e+00\r\n886 888 -3.3218027000000e+02\r\n887 888  5.1053573000000e+01\r\n888 888  1.7392906000000e+01\r\n889 888  2.1413265000000e+01\r\n890 888 -3.4687080000000e+00\r\n891 888 -4.6901292000000e+00\r\n1992 888 -4.7477083000000e+00\r\n841 889 -2.6512448000000e-02\r\n843 889 -2.0972787000000e-05\r\n886 889 -1.7175510000000e-03\r\n888 889 -1.7925139000000e-05\r\n889 889  3.7900353000000e+02\r\n891 889  9.4034887000000e-04\r\n1993 889 -5.9610596000000e-02\r\n1995 889 -1.4556352000000e-05\r\n841 890  1.7605472000000e+01\r\n843 890 -3.1939497000000e+00\r\n888 890 -2.7745677000000e+00\r\n889 890 -2.3514888000000e+02\r\n890 890 -7.2360764000000e+01\r\n891 890  8.1931919000000e+00\r\n1995 890 -2.2165275000000e+00\r\n841 891  2.9760267000000e+01\r\n842 891 -4.8207812000000e+00\r\n843 891 -5.3990486000000e+00\r\n888 891 -4.6901292000000e+00\r\n889 891 -3.9749538000000e+02\r\n890 891  6.0849346000000e+01\r\n891 891  1.3849764000000e+01\r\n1995 891 -3.7468149000000e+00\r\n892 892  1.0000000000000e+00\r\n893 893  1.0000000000000e+00\r\n894 894  1.0000000000000e+00\r\n895 895  1.0000000000000e+00\r\n896 896  1.0000000000000e+00\r\n897 897  1.0000000000000e+00\r\n898 898  1.0000000000000e+00\r\n899 899  1.0000000000000e+00\r\n900 900  1.0000000000000e+00\r\n901 901  1.0000000000000e+00\r\n902 902  1.0000000000000e+00\r\n903 903  1.0000000000000e+00\r\n904 904  1.0000000000000e+00\r\n905 905  1.0000000000000e+00\r\n906 906  1.0000000000000e+00\r\n907 907  1.0000000000000e+00\r\n908 908  1.0000000000000e+00\r\n909 909  1.0000000000000e+00\r\n910 910  1.0000000000000e+00\r\n911 911  1.0000000000000e+00\r\n912 912  1.0000000000000e+00\r\n913 913  1.0000000000000e+00\r\n914 914  1.0000000000000e+00\r\n915 915  1.0000000000000e+00\r\n868 916 -1.5936654000000e-03\r\n870 916 -1.6632213000000e-05\r\n916 916  3.4465667000000e+02\r\n918 916  8.5322576000000e-04\r\n919 916 -1.5603987000000e-03\r\n921 916 -1.6285026000000e-05\r\n2020 916 -6.1605779000000e-02\r\n2022 916 -1.4034255000000e-05\r\n868 917  3.1315115000000e+00\r\n870 917 -2.8647960000000e+00\r\n916 917 -2.0210141000000e+02\r\n917 917 -6.5668414000000e+01\r\n918 917  8.1139592000000e+00\r\n919 917  1.0432158000000e+00\r\n921 917 -2.8137417000000e+00\r\n2022 917 -2.4280655000000e+00\r\n868 918  5.2935070000000e+00\r\n869 918 -8.5754645000000e-01\r\n870 918 -4.8426511000000e+00\r\n916 918 -3.4163222000000e+02\r\n917 918  5.2406411000000e+01\r\n918 918  1.3715837000000e+01\r\n919 918  1.7634519000000e+00\r\n920 918 -2.8567865000000e-01\r\n921 918 -4.7563489000000e+00\r\n2022 918 -4.1044020000000e+00\r\n871 919 -1.5724985000000e-03\r\n873 919 -1.6411306000000e-05\r\n916 919 -6.1502372000000e-02\r\n918 919 -1.6285026000000e-05\r\n919 919  3.3323007000000e+02\r\n921 919  8.5636298000000e-04\r\n922 919 -1.3963692000000e-03\r\n924 919 -1.4573141000000e-05\r\n967 919 -5.3339692000000e-03\r\n969 919 -1.5145699000000e-05\r\n2023 919 -6.2108993000000e-02\r\n2025 919 -1.4554666000000e-05\r\n871 920  4.8166846000000e+00\r\n873 920 -2.8158806000000e+00\r\n918 920 -2.8137417000000e+00\r\n919 920 -1.9928675000000e+02\r\n920 920 -6.3486307000000e+01\r\n921 920  1.3273757000000e+01\r\n922 920  3.1502848000000e+00\r\n924 920 -2.5053347000000e+00\r\n969 920 -2.6169199000000e+00\r\n2025 920 -2.5147666000000e+00\r\n871 921  8.1421188000000e+00\r\n872 921 -1.3190203000000e+00\r\n873 921 -4.7599617000000e+00\r\n918 921 -4.7563489000000e+00\r\n919 921 -3.3687412000000e+02\r\n920 921  5.1716900000000e+01\r\n921 921  2.2437948000000e+01\r\n922 921  5.3252382000000e+00\r\n923 921 -8.6268678000000e-01\r\n924 921 -4.2350152000000e+00\r\n969 921 -4.4236383000000e+00\r\n2025 921 -4.2509584000000e+00\r\n874 922 -6.2867949000000e-03\r\n876 922 -1.3598958000000e-05\r\n919 922 -7.5083445000000e-02\r\n921 922 -1.4573141000000e-05\r\n922 922  2.7580705000000e+02\r\n924 922  7.1551982000000e-04\r\n925 922 -1.1711663000000e-03\r\n927 922 -1.2222822000000e-05\r\n970 922 -4.9045070000000e-03\r\n972 922 -1.2440083000000e-05\r\n2026 922 -6.2807060000000e-02\r\n2028 922 -1.7675613000000e-05\r\n874 923  5.9756739000000e+00\r\n876 923 -2.3380768000000e+00\r\n921 923 -2.5053347000000e+00\r\n922 923 -1.6923485000000e+02\r\n923 923 -5.2550474000000e+01\r\n924 923  1.2108122000000e+01\r\n925 923  4.9393941000000e+00\r\n927 923 -2.0813670000000e+00\r\n972 923 -2.1386753000000e+00\r\n2028 923 -3.0387763000000e+00\r\n874 924  1.0101279000000e+01\r\n875 924 -1.6363979000000e+00\r\n876 924 -3.9522850000000e+00\r\n921 924 -4.2350152000000e+00\r\n922 924 -2.8607459000000e+02\r\n923 924  4.3955116000000e+01\r\n924 924  2.0467567000000e+01\r\n925 924  8.3495517000000e+00\r\n926 924 -1.3526197000000e+00\r\n927 924 -3.5183427000000e+00\r\n972 924 -3.6152167000000e+00\r\n2028 924 -5.1367475000000e+00\r\n877 925 -2.8587000000000e-02\r\n879 925 -1.1486661000000e-05\r\n922 925 -2.7329265000000e-02\r\n924 925 -1.2222822000000e-05\r\n925 925  2.2982680000000e+02\r\n927 925  6.0506617000000e-04\r\n928 925 -1.0877487000000e-03\r\n930 925 -1.1352238000000e-05\r\n973 925 -1.0614415000000e-03\r\n975 925 -1.1077684000000e-05\r\n2029 925 -6.3624211000000e-02\r\n2031 925 -2.1422054000000e-05\r\n877 926  7.2941785000000e+00\r\n879 926 -1.9561967000000e+00\r\n924 926 -2.0813670000000e+00\r\n925 926 -1.4544989000000e+02\r\n926 926 -4.3800301000000e+01\r\n927 926  1.1508061000000e+01\r\n928 926  6.2339408000000e+00\r\n930 926 -1.9081462000000e+00\r\n975 926 -1.9094757000000e+00\r\n2031 926 -3.6479617000000e+00\r\n877 927  1.2330072000000e+01\r\n878 927 -1.9974504000000e+00\r\n879 927 -3.3067529000000e+00\r\n924 927 -3.5183427000000e+00\r\n925 927 -2.4586833000000e+02\r\n926 927  3.7819564000000e+01\r\n927 927  1.9453216000000e+01\r\n928 927  1.0537847000000e+01\r\n929 927 -1.7071130000000e+00\r\n930 927 -3.2255284000000e+00\r\n975 927 -3.2277759000000e+00\r\n2031 927 -6.1665103000000e+00\r\n880 928 -5.1644733000000e-02\r\n882 928 -1.1356095000000e-05\r\n925 928 -1.2405304000000e-02\r\n927 928 -1.1352238000000e-05\r\n928 928  2.2982524000000e+02\r\n930 928  6.0513208000000e-04\r\n931 928 -1.1533051000000e-03\r\n933 928 -1.2036414000000e-05\r\n976 928 -1.0709075000000e-03\r\n978 928 -1.1176475000000e-05\r\n2032 928 -6.3794897000000e-02\r\n2034 928 -2.1708012000000e-05\r\n880 929  1.0488328000000e+01\r\n882 929 -1.9090161000000e+00\r\n927 929 -1.9081462000000e+00\r\n928 929 -1.4859170000000e+02\r\n929 929 -4.3809625000000e+01\r\n930 929  1.1378192000000e+01\r\n931 929  6.1945942000000e+00\r\n933 929 -1.9983706000000e+00\r\n978 929 -1.9088204000000e+00\r\n2034 929 -3.6489216000000e+00\r\n880 930  1.7729469000000e+01\r\n881 930 -2.8721199000000e+00\r\n882 930 -3.2270008000000e+00\r\n927 930 -3.2255284000000e+00\r\n928 930 -2.5117942000000e+02\r\n929 930  3.8656718000000e+01\r\n930 930  1.9233694000000e+01\r\n931 930  1.0471342000000e+01\r\n932 930 -1.6963254000000e+00\r\n933 930 -3.3780457000000e+00\r\n978 930 -3.2266700000000e+00\r\n2034 930 -6.1681371000000e+00\r\n883 931 -7.6275901000000e-02\r\n885 931 -1.2342249000000e-05\r\n928 931 -4.1889144000000e-03\r\n930 931 -1.2036414000000e-05\r\n931 931  2.5280021000000e+02\r\n933 931  6.4834342000000e-04\r\n979 931 -1.2183070000000e-03\r\n981 931 -1.2714803000000e-05\r\n2035 931 -6.3493138000000e-02\r\n2037 931 -1.9998318000000e-05\r\n883 932  1.8367232000000e+01\r\n885 932 -2.0494640000000e+00\r\n930 932 -1.9983706000000e+00\r\n931 932 -1.6345444000000e+02\r\n932 932 -4.8199513000000e+01\r\n933 932  9.5205031000000e+00\r\n981 932 -2.1469161000000e+00\r\n2037 932 -3.3203392000000e+00\r\n883 933  3.1047948000000e+01\r\n884 933 -5.0296385000000e+00\r\n885 933 -3.4644117000000e+00\r\n930 933 -3.3780457000000e+00\r\n931 933 -2.7630321000000e+02\r\n932 933  4.2501223000000e+01\r\n933 933  1.6093452000000e+01\r\n981 933 -3.6291456000000e+00\r\n2037 933 -5.6126982000000e+00\r\n934 934  1.0000000000000e+00\r\n935 935  1.0000000000000e+00\r\n936 936  1.0000000000000e+00\r\n937 937  1.0000000000000e+00\r\n938 938  1.0000000000000e+00\r\n939 939  1.0000000000000e+00\r\n940 940  1.0000000000000e+00\r\n941 941  1.0000000000000e+00\r\n942 942  1.0000000000000e+00\r\n943 943  1.0000000000000e+00\r\n944 944  1.0000000000000e+00\r\n945 945  1.0000000000000e+00\r\n946 946  1.0000000000000e+00\r\n947 947  1.0000000000000e+00\r\n948 948  1.0000000000000e+00\r\n949 949  1.0000000000000e+00\r\n950 950  1.0000000000000e+00\r\n951 951  1.0000000000000e+00\r\n952 952  1.0000000000000e+00\r\n953 953  1.0000000000000e+00\r\n954 954  1.0000000000000e+00\r\n955 955  1.0000000000000e+00\r\n956 956  1.0000000000000e+00\r\n957 957  1.0000000000000e+00\r\n958 958  1.0000000000000e+00\r\n959 959  1.0000000000000e+00\r\n960 960  1.0000000000000e+00\r\n961 961  1.0000000000000e+00\r\n962 962  1.0000000000000e+00\r\n963 963  1.0000000000000e+00\r\n964 964  1.0000000000000e+00\r\n965 965  1.0000000000000e+00\r\n966 966  1.0000000000000e+00\r\n919 967 -1.4512306000000e-03\r\n921 967 -1.5145699000000e-05\r\n967 967  2.9870923000000e+02\r\n969 967  7.4286310000000e-04\r\n970 967 -1.2253255000000e-03\r\n972 967 -1.2788052000000e-05\r\n2071 967 -6.2497635000000e-02\r\n2073 967 -1.6162266000000e-05\r\n919 968  2.9235106000000e+00\r\n921 968 -2.6169199000000e+00\r\n967 968 -1.7516579000000e+02\r\n968 968 -5.6914730000000e+01\r\n969 968  7.6454607000000e+00\r\n970 968  7.0861485000000e-01\r\n972 968 -2.2168790000000e+00\r\n2073 968 -2.8052857000000e+00\r\n919 969  4.9418988000000e+00\r\n920 969 -8.0058804000000e-01\r\n921 969 -4.4236383000000e+00\r\n967 969 -2.9610005000000e+02\r\n968 969  4.5417038000000e+01\r\n969 969  1.2923878000000e+01\r\n970 969  1.1978417000000e+00\r\n971 969 -1.9405045000000e-01\r\n972 969 -3.7474097000000e+00\r\n2073 969 -4.7420516000000e+00\r\n922 970 -1.1919839000000e-03\r\n924 970 -1.2440083000000e-05\r\n967 970 -6.5872756000000e-02\r\n969 970 -1.2788052000000e-05\r\n970 970  2.4133995000000e+02\r\n972 970  6.3226544000000e-04\r\n973 970 -1.0868674000000e-03\r\n975 970 -1.1343040000000e-05\r\n1018 970 -2.6363345000000e-03\r\n1020 970 -1.1284175000000e-05\r\n2074 970 -6.3248693000000e-02\r\n2076 970 -2.0025997000000e-05\r\n922 971  4.3947349000000e+00\r\n924 971 -2.1386753000000e+00\r\n969 971 -2.2168790000000e+00\r\n970 971 -1.4570455000000e+02\r\n971 971 -4.2188136000000e+01\r\n972 971  1.1743620000000e+01\r\n973 971  2.7719884000000e+00\r\n975 971 -1.9550432000000e+00\r\n1020 971 -1.9561966000000e+00\r\n2076 971 -3.4716727000000e+00\r\n922 972  7.4288598000000e+00\r\n923 972 -1.2034742000000e+00\r\n924 972 -3.6152167000000e+00\r\n969 972 -3.7474097000000e+00\r\n970 972 -2.4629897000000e+02\r\n971 972  4.4227243000000e+01\r\n972 972  1.9851412000000e+01\r\n973 972  4.6857691000000e+00\r\n974 972 -7.5909392000000e-01\r\n975 972 -3.3048051000000e+00\r\n1020 972 -3.3067548000000e+00\r\n2076 972 -5.8685156000000e+00\r\n925 973 -1.2781218000000e-02\r\n927 973 -1.1077684000000e-05\r\n970 973 -4.1053693000000e-02\r\n972 973 -1.1343040000000e-05\r\n973 973  2.2983246000000e+02\r\n975 973  6.0332626000000e-04\r\n976 973 -1.0707159000000e-03\r\n978 973 -1.1174475000000e-05\r\n1021 973 -1.6420732000000e-03\r\n1023 973 -1.1077758000000e-05\r\n2077 973 -6.3744100000000e-02\r\n2079 973 -2.1148424000000e-05\r\n925 974  5.7477390000000e+00\r\n927 974 -1.9094757000000e+00\r\n972 974 -1.9550432000000e+00\r\n973 974 -1.4206599000000e+02\r\n974 974 -4.3793757000000e+01\r\n975 974  1.1332200000000e+01\r\n976 974  4.3873821000000e+00\r\n978 974 -1.9082874000000e+00\r\n1023 974 -1.9093383000000e+00\r\n2079 974 -3.6451450000000e+00\r\n925 975  9.7159725000000e+00\r\n926 975 -1.5739818000000e+00\r\n927 975 -3.2277759000000e+00\r\n972 975 -3.3048051000000e+00\r\n973 975 -2.4014821000000e+02\r\n974 975  3.6909200000000e+01\r\n975 975  1.9155942000000e+01\r\n976 975  7.4164266000000e+00\r\n977 975 -1.2014568000000e+00\r\n978 975 -3.2257672000000e+00\r\n1023 975 -3.2275438000000e+00\r\n2079 975 -6.1617491000000e+00\r\n928 976 -1.2881402000000e-02\r\n930 976 -1.1176475000000e-05\r\n973 976 -1.2486327000000e-02\r\n975 976 -1.1174475000000e-05\r\n976 976  2.2979623000000e+02\r\n978 976  6.0487171000000e-04\r\n979 976 -1.1582667000000e-03\r\n981 976 -1.2088195000000e-05\r\n1024 976 -1.1079653000000e-03\r\n1026 976 -1.1563228000000e-05\r\n2080 976 -6.3757781000000e-02\r\n2082 976 -2.1366055000000e-05\r\n928 977  7.5932097000000e+00\r\n930 977 -1.9088204000000e+00\r\n975 977 -1.9082874000000e+00\r\n976 977 -1.4534879000000e+02\r\n977 977 -4.3800643000000e+01\r\n978 977  1.1511560000000e+01\r\n979 977  5.8342629000000e+00\r\n981 977 -2.0408938000000e+00\r\n1026 977 -1.9998514000000e+00\r\n2082 977 -3.6487932000000e+00\r\n928 978  1.2835562000000e+01\r\n929 978 -2.0793411000000e+00\r\n930 978 -3.2266700000000e+00\r\n975 978 -3.2257672000000e+00\r\n976 978 -2.4569759000000e+02\r\n977 978  3.7791073000000e+01\r\n978 978  1.9459139000000e+01\r\n979 978  9.8622379000000e+00\r\n980 978 -1.5976672000000e+00\r\n981 978 -3.4499269000000e+00\r\n1026 978 -3.3805488000000e+00\r\n2082 978 -6.1679201000000e+00\r\n931 979 -2.8942638000000e-02\r\n933 979 -1.2714803000000e-05\r\n976 979 -1.7989387000000e-02\r\n978 979 -1.2088195000000e-05\r\n979 979  2.6426011000000e+02\r\n981 979  6.6172256000000e-04\r\n2083 979 -6.3402179000000e-02\r\n2085 979 -1.8793556000000e-05\r\n931 980  9.0579294000000e+00\r\n933 980 -2.1469161000000e+00\r\n978 980 -2.0408938000000e+00\r\n979 980 -1.6075354000000e+02\r\n980 980 -5.0380740000000e+01\r\n981 980  7.3665337000000e+00\r\n2085 980 -3.1730689000000e+00\r\n931 981  1.5311518000000e+01\r\n932 981 -2.4804263000000e+00\r\n933 981 -3.6291456000000e+00\r\n978 981 -3.4499269000000e+00\r\n979 981 -2.7173768000000e+02\r\n980 981  4.1683042000000e+01\r\n981 981  1.2452383000000e+01\r\n2085 981 -5.3637519000000e+00\r\n982 982  1.0000000000000e+00\r\n983 983  1.0000000000000e+00\r\n984 984  1.0000000000000e+00\r\n985 985  1.0000000000000e+00\r\n986 986  1.0000000000000e+00\r\n987 987  1.0000000000000e+00\r\n988 988  1.0000000000000e+00\r\n989 989  1.0000000000000e+00\r\n990 990  1.0000000000000e+00\r\n991 991  1.0000000000000e+00\r\n992 992  1.0000000000000e+00\r\n993 993  1.0000000000000e+00\r\n994 994  1.0000000000000e+00\r\n995 995  1.0000000000000e+00\r\n996 996  1.0000000000000e+00\r\n997 997  1.0000000000000e+00\r\n998 998  1.0000000000000e+00\r\n999 999  1.0000000000000e+00\r\n1000 1000  1.0000000000000e+00\r\n1001 1001  1.0000000000000e+00\r\n1002 1002  1.0000000000000e+00\r\n1003 1003  1.0000000000000e+00\r\n1004 1004  1.0000000000000e+00\r\n1005 1005  1.0000000000000e+00\r\n1006 1006  1.0000000000000e+00\r\n1007 1007  1.0000000000000e+00\r\n1008 1008  1.0000000000000e+00\r\n1009 1009  1.0000000000000e+00\r\n1010 1010  1.0000000000000e+00\r\n1011 1011  1.0000000000000e+00\r\n1012 1012  1.0000000000000e+00\r\n1013 1013  1.0000000000000e+00\r\n1014 1014  1.0000000000000e+00\r\n1015 1015  1.0000000000000e+00\r\n1016 1016  1.0000000000000e+00\r\n1017 1017  1.0000000000000e+00\r\n970 1018 -1.0812271000000e-03\r\n972 1018 -1.1284175000000e-05\r\n1018 1018  2.2980627000000e+02\r\n1020 1018  5.9156273000000e-04\r\n1021 1018 -1.0508456000000e-03\r\n1023 1018 -1.0967101000000e-05\r\n1066 1018 -1.5430391000000e-02\r\n1068 1018 -1.0935180000000e-05\r\n2122 1018 -6.3775482000000e-02\r\n2124 1018 -2.0866851000000e-05\r\n970 1019  3.4945548000000e+00\r\n972 1019 -1.9561966000000e+00\r\n1018 1019 -1.3702239000000e+02\r\n1019 1019 -4.3781862000000e+01\r\n1020 1019  9.4233865000000e+00\r\n1021 1019  1.5805871000000e+00\r\n1023 1019 -1.9089412000000e+00\r\n1068 1019 -1.9095203000000e+00\r\n2124 1019 -3.6438231000000e+00\r\n970 1020  5.9071955000000e+00\r\n971 1020 -9.5696878000000e-01\r\n972 1020 -3.3067548000000e+00\r\n1018 1020 -2.3162265000000e+02\r\n1019 1020  3.5557344000000e+01\r\n1020 1020  1.5929293000000e+01\r\n1021 1020  2.6718245000000e+00\r\n1022 1020 -4.3283697000000e-01\r\n1023 1020 -3.2268743000000e+00\r\n1068 1020 -3.2278531000000e+00\r\n2124 1020 -6.1595186000000e+00\r\n973 1021 -1.0614486000000e-03\r\n975 1021 -1.1077758000000e-05\r\n1018 1021 -4.1015050000000e-02\r\n1020 1021 -1.0967101000000e-05\r\n1021 1021  2.2983972000000e+02\r\n1023 1021  6.0301883000000e-04\r\n1024 1021 -1.1082774000000e-03\r\n1026 1021 -1.1566485000000e-05\r\n1069 1021 -1.4084164000000e-02\r\n1071 1021 -1.0968606000000e-05\r\n2125 1021 -6.3794062000000e-02\r\n2127 1021 -2.0933286000000e-05\r\n973 1022  4.5370145000000e+00\r\n975 1022 -1.9093383000000e+00\r\n1020 1022 -1.9089412000000e+00\r\n1021 1022 -1.3962158000000e+02\r\n1022 1022 -4.3787669000000e+01\r\n1023 1022  1.1376364000000e+01\r\n1024 1022  3.1452839000000e+00\r\n1026 1022 -2.0002494000000e+00\r\n1071 1022 -1.9092098000000e+00\r\n2127 1022 -3.6437176000000e+00\r\n973 1023  7.6693654000000e+00\r\n974 1023 -1.2424395000000e+00\r\n975 1023 -3.2275438000000e+00\r\n1020 1023 -3.2268743000000e+00\r\n1021 1023 -2.3601620000000e+02\r\n1022 1023  3.6254915000000e+01\r\n1023 1023  1.9230594000000e+01\r\n1024 1023  5.3167851000000e+00\r\n1025 1023 -8.6132074000000e-01\r\n1026 1023 -3.3812198000000e+00\r\n1071 1023 -3.2273259000000e+00\r\n2127 1023 -6.1593344000000e+00\r\n976 1024 -3.0386974000000e-03\r\n978 1024 -1.1563228000000e-05\r\n1021 1024 -1.5614702000000e-02\r\n1023 1024 -1.1566485000000e-05\r\n1024 1024  2.5276665000000e+02\r\n1026 1024  6.3354621000000e-04\r\n2128 1024 -6.3580760000000e-02\r\n2130 1024 -1.9161880000000e-05\r\n976 1025  6.2052888000000e+00\r\n978 1025 -1.9998514000000e+00\r\n1023 1025 -2.0002494000000e+00\r\n1024 1025 -1.5133049000000e+02\r\n1025 1025 -4.8172242000000e+01\r\n1026 1025  7.3192863000000e+00\r\n2130 1025 -3.3137845000000e+00\r\n976 1026  1.0489420000000e+01\r\n977 1026 -1.6992821000000e+00\r\n978 1026 -3.3805488000000e+00\r\n1023 1026 -3.3812198000000e+00\r\n1024 1026 -2.5580907000000e+02\r\n1025 1026  3.9248992000000e+01\r\n1026 1026  1.2372520000000e+01\r\n2130 1026 -5.6016213000000e+00\r\n1027 1027  1.0000000000000e+00\r\n1028 1028  1.0000000000000e+00\r\n1029 1029  1.0000000000000e+00\r\n1030 1030  1.0000000000000e+00\r\n1031 1031  1.0000000000000e+00\r\n1032 1032  1.0000000000000e+00\r\n1033 1033  1.0000000000000e+00\r\n1034 1034  1.0000000000000e+00\r\n1035 1035  1.0000000000000e+00\r\n1036 1036  1.0000000000000e+00\r\n1037 1037  1.0000000000000e+00\r\n1038 1038  1.0000000000000e+00\r\n1039 1039  1.0000000000000e+00\r\n1040 1040  1.0000000000000e+00\r\n1041 1041  1.0000000000000e+00\r\n1042 1042  1.0000000000000e+00\r\n1043 1043  1.0000000000000e+00\r\n1044 1044  1.0000000000000e+00\r\n1045 1045  1.0000000000000e+00\r\n1046 1046  1.0000000000000e+00\r\n1047 1047  1.0000000000000e+00\r\n1048 1048  1.0000000000000e+00\r\n1049 1049  1.0000000000000e+00\r\n1050 1050  1.0000000000000e+00\r\n1051 1051  1.0000000000000e+00\r\n1052 1052  1.0000000000000e+00\r\n1053 1053  1.0000000000000e+00\r\n1054 1054  1.0000000000000e+00\r\n1055 1055  1.0000000000000e+00\r\n1056 1056  1.0000000000000e+00\r\n1057 1057  1.0000000000000e+00\r\n1058 1058  1.0000000000000e+00\r\n1059 1059  1.0000000000000e+00\r\n1060 1060  1.0000000000000e+00\r\n1061 1061  1.0000000000000e+00\r\n1062 1062  1.0000000000000e+00\r\n1063 1063  1.0000000000000e+00\r\n1064 1064  1.0000000000000e+00\r\n1065 1065  1.0000000000000e+00\r\n1018 1066 -1.0477870000000e-03\r\n1020 1066 -1.0935180000000e-05\r\n1066 1066  2.2979553000000e+02\r\n1068 1066  5.8009517000000e-04\r\n1069 1066 -1.0433945000000e-03\r\n1071 1066 -1.0889337000000e-05\r\n2170 1066 -6.3870563000000e-02\r\n2172 1066 -2.0759632000000e-05\r\n1018 1067  2.2605796000000e+00\r\n1020 1067 -1.9095203000000e+00\r\n1066 1067 -1.3474317000000e+02\r\n1067 1067 -4.3777519000000e+01\r\n1068 1067  7.4661549000000e+00\r\n1069 1067  5.2937606000000e-01\r\n1071 1067 -1.9090927000000e+00\r\n2172 1067 -3.6426386000000e+00\r\n1018 1068  3.8212837000000e+00\r\n1019 1068 -6.1905167000000e-01\r\n1020 1068 -3.2278531000000e+00\r\n1066 1068 -2.2776985000000e+02\r\n1067 1068  3.4943889000000e+01\r\n1068 1068  1.2620788000000e+01\r\n1069 1068  8.9485729000000e-01\r\n1070 1068 -1.4496775000000e-01\r\n1071 1068 -3.2271302000000e+00\r\n2172 1068 -6.1575162000000e+00\r\n1021 1069 -1.0509899000000e-03\r\n1023 1069 -1.0968606000000e-05\r\n1066 1069 -4.2359559000000e-02\r\n1068 1069 -1.0889337000000e-05\r\n1069 1069  2.2983197000000e+02\r\n1071 1069  5.8014818000000e-04\r\n2173 1069 -6.3888929000000e-02\r\n2175 1069 -2.0783011000000e-05\r\n1021 1070  3.3115470000000e+00\r\n1023 1070 -1.9092098000000e+00\r\n1068 1070 -1.9090927000000e+00\r\n1069 1070 -1.3525858000000e+02\r\n1070 1070 -4.3782057000000e+01\r\n1071 1070  7.4668641000000e+00\r\n2175 1070 -3.6436564000000e+00\r\n1021 1071  5.5978351000000e+00\r\n1022 1071 -9.0685487000000e-01\r\n1023 1071 -3.2273259000000e+00\r\n1068 1071 -3.2271302000000e+00\r\n1069 1071 -2.2864096000000e+02\r\n1070 1071  3.5074011000000e+01\r\n1071 1071  1.2621981000000e+01\r\n2175 1071 -6.1592331000000e+00\r\n1072 1072  1.0000000000000e+00\r\n1073 1073  1.0000000000000e+00\r\n1074 1074  1.0000000000000e+00\r\n1075 1075  1.0000000000000e+00\r\n1076 1076  1.0000000000000e+00\r\n1077 1077  1.0000000000000e+00\r\n1078 1078  1.0000000000000e+00\r\n1079 1079  1.0000000000000e+00\r\n1080 1080  1.0000000000000e+00\r\n1081 1081  1.0000000000000e+00\r\n1082 1082  1.0000000000000e+00\r\n1083 1083  1.0000000000000e+00\r\n1084 1084  1.0000000000000e+00\r\n1085 1085  1.0000000000000e+00\r\n1086 1086  1.0000000000000e+00\r\n1087 1087  1.0000000000000e+00\r\n1088 1088  1.0000000000000e+00\r\n1089 1089  1.0000000000000e+00\r\n1090 1090  1.0000000000000e+00\r\n1091 1091  1.0000000000000e+00\r\n1092 1092  1.0000000000000e+00\r\n1093 1093  1.0000000000000e+00\r\n1094 1094  1.0000000000000e+00\r\n1095 1095  1.0000000000000e+00\r\n1096 1096  1.0000000000000e+00\r\n1097 1097  1.0000000000000e+00\r\n1098 1098  1.0000000000000e+00\r\n1099 1099  1.0000000000000e+00\r\n1100 1100  1.0000000000000e+00\r\n1101 1101  1.0000000000000e+00\r\n1102 1102  1.0000000000000e+00\r\n1103 1103  1.0000000000000e+00\r\n1104 1104  1.0000000000000e+00\r\n1105 1105  1.0000000000000e+00\r\n1106 1106  1.0000000000000e+00\r\n1107 1107  1.0000000000000e+00\r\n1108 1108  1.0000000000000e+00\r\n1109 1109  1.0000000000000e+00\r\n1110 1110  1.0000000000000e+00\r\n1111 1111  1.0000000000000e+00\r\n1112 1112  1.0000000000000e+00\r\n1113 1113  1.0000000000000e+00\r\n1114 1114  1.0000000000000e+00\r\n1115 1115  1.0000000000000e+00\r\n1116 1116  1.0000000000000e+00\r\n1117 1117  1.0000000000000e+00\r\n1118 1118  1.0000000000000e+00\r\n1119 1119  1.0000000000000e+00\r\n1120 1120  1.0000000000000e+00\r\n1121 1121  1.0000000000000e+00\r\n1122 1122  1.0000000000000e+00\r\n1123 1123  1.0000000000000e+00\r\n1124 1124  1.0000000000000e+00\r\n1125 1125  1.0000000000000e+00\r\n1126 1126  1.0000000000000e+00\r\n1127 1127  1.0000000000000e+00\r\n1128 1128  1.0000000000000e+00\r\n1129 1129  1.0000000000000e+00\r\n1130 1130  1.0000000000000e+00\r\n1131 1131  1.0000000000000e+00\r\n1132 1132  1.0000000000000e+00\r\n1133 1133  1.0000000000000e+00\r\n1134 1134  1.0000000000000e+00\r\n1135 1135  1.0000000000000e+00\r\n1136 1136  1.0000000000000e+00\r\n1137 1137  1.0000000000000e+00\r\n1138 1138  1.0000000000000e+00\r\n1139 1139  1.0000000000000e+00\r\n1140 1140  1.0000000000000e+00\r\n1141 1141  1.0000000000000e+00\r\n1142 1142  1.0000000000000e+00\r\n1143 1143  1.0000000000000e+00\r\n1144 1144  1.0000000000000e+00\r\n1145 1145  1.0000000000000e+00\r\n1146 1146  1.0000000000000e+00\r\n1147 1147  1.0000000000000e+00\r\n1148 1148  1.0000000000000e+00\r\n1149 1149  1.0000000000000e+00\r\n1150 1150  1.0000000000000e+00\r\n1151 1151  1.0000000000000e+00\r\n1152 1152  1.0000000000000e+00\r\n1153 1153  1.0000000000000e+00\r\n1154 1154  1.0000000000000e+00\r\n1155 1155  1.0000000000000e+00\r\n1156 1156  1.0000000000000e+00\r\n1157 1157  1.0000000000000e+00\r\n1158 1158  1.0000000000000e+00\r\n1159 1159  1.0000000000000e+00\r\n1160 1160  1.0000000000000e+00\r\n1161 1161  1.0000000000000e+00\r\n1162 1162  1.0000000000000e+00\r\n1163 1163  1.0000000000000e+00\r\n1164 1164  1.0000000000000e+00\r\n1165 1165  1.0000000000000e+00\r\n1166 1166  1.0000000000000e+00\r\n1167 1167  1.0000000000000e+00\r\n1168 1168  1.0000000000000e+00\r\n1169 1169  1.0000000000000e+00\r\n1170 1170  1.0000000000000e+00\r\n1171 1171  1.0000000000000e+00\r\n1172 1172  1.0000000000000e+00\r\n1173 1173  1.0000000000000e+00\r\n1174 1174  1.0000000000000e+00\r\n1175 1175  1.0000000000000e+00\r\n1176 1176  1.0000000000000e+00\r\n1177 1177  1.0000000000000e+00\r\n1178 1178  1.0000000000000e+00\r\n1179 1179  1.0000000000000e+00\r\n1180 1180  1.0000000000000e+00\r\n1181 1181  1.0000000000000e+00\r\n1182 1182  1.0000000000000e+00\r\n1183 1183  1.0000000000000e+00\r\n1184 1184  1.0000000000000e+00\r\n1185 1185  1.0000000000000e+00\r\n1186 1186  1.0000000000000e+00\r\n1187 1187  1.0000000000000e+00\r\n1188 1188  1.0000000000000e+00\r\n1189 1189  1.0000000000000e+00\r\n1190 1190  1.0000000000000e+00\r\n1191 1191  1.0000000000000e+00\r\n1192 1192  1.0000000000000e+00\r\n1193 1193  1.0000000000000e+00\r\n1194 1194  1.0000000000000e+00\r\n1195 1195  1.0000000000000e+00\r\n1196 1196  1.0000000000000e+00\r\n1197 1197  1.0000000000000e+00\r\n1198 1198  1.0000000000000e+00\r\n1199 1199  1.0000000000000e+00\r\n1200 1200  1.0000000000000e+00\r\n1201 1201  1.0000000000000e+00\r\n1202 1202  1.0000000000000e+00\r\n1203 1203  1.0000000000000e+00\r\n1204 1204  1.0000000000000e+00\r\n1205 1205  1.0000000000000e+00\r\n1206 1206  1.0000000000000e+00\r\n1207 1207  1.0000000000000e+00\r\n1208 1208  1.0000000000000e+00\r\n1209 1209  1.0000000000000e+00\r\n1210 1210  1.0000000000000e+00\r\n1211 1211  1.0000000000000e+00\r\n1212 1212  1.0000000000000e+00\r\n1213 1213  1.0000000000000e+00\r\n1214 1214  1.0000000000000e+00\r\n1215 1215  1.0000000000000e+00\r\n1216 1216  1.0000000000000e+00\r\n1217 1217  1.0000000000000e+00\r\n1218 1218  1.0000000000000e+00\r\n1219 1219  1.0000000000000e+00\r\n1220 1220  1.0000000000000e+00\r\n1221 1221  1.0000000000000e+00\r\n1222 1222  1.0000000000000e+00\r\n1223 1223  1.0000000000000e+00\r\n1224 1224  1.0000000000000e+00\r\n1225 1225  1.0000000000000e+00\r\n1226 1226  1.0000000000000e+00\r\n1227 1227  1.0000000000000e+00\r\n1228 1228  1.0000000000000e+00\r\n1229 1229  1.0000000000000e+00\r\n1230 1230  1.0000000000000e+00\r\n1231 1231  1.0000000000000e+00\r\n1232 1232  1.0000000000000e+00\r\n1233 1233  1.0000000000000e+00\r\n1234 1234  1.0000000000000e+00\r\n1235 1235  1.0000000000000e+00\r\n1236 1236  1.0000000000000e+00\r\n133 1237 -2.5994143000000e+00\r\n135 1237 -9.4695072000000e-02\r\n1237 1237  1.9983945000000e+02\r\n1239 1237  2.6103739000000e-01\r\n1240 1237 -1.8307631000000e-01\r\n1242 1237 -3.0282569000000e-02\r\n1285 1237 -2.6654401000000e+00\r\n1287 1237 -5.6301327000000e-02\r\n133 1238  1.0350072000000e+01\r\n135 1238 -9.0991269000000e-01\r\n1237 1238 -1.3370690000000e+02\r\n1238 1238 -2.8933988000000e+01\r\n1239 1238  2.0907142000000e+00\r\n1242 1238 -6.3656354000000e-01\r\n1285 1238  1.1613324000000e+01\r\n1287 1238 -5.4102785000000e-01\r\n133 1239  1.7495750000000e+01\r\n134 1239 -1.8416690000000e+00\r\n135 1239 -1.5381153000000e+00\r\n1237 1239 -2.2601800000000e+02\r\n1238 1239  2.6839463000000e+01\r\n1239 1239  3.5341416000000e+00\r\n1242 1239 -1.0760470000000e+00\r\n1285 1239  1.9631152000000e+01\r\n1286 1239 -2.0664493000000e+00\r\n1287 1239 -9.1455284000000e-01\r\n136 1240 -2.0304410000000e+00\r\n138 1240 -5.7589129000000e-02\r\n1237 1240 -5.0296613000000e-01\r\n1239 1240 -3.0282569000000e-02\r\n1240 1240  1.8993261000000e+02\r\n1242 1240  3.9513066000000e-01\r\n1243 1240 -1.5909447000000e-01\r\n1245 1240 -1.7631713000000e-02\r\n1288 1240 -2.0257365000000e+00\r\n1290 1240 -3.0138742000000e-02\r\n2344 1240 -1.6231279000000e+00\r\n2346 1240 -1.7988385000000e-01\r\n136 1241  1.1063571000000e+01\r\n138 1241 -1.2106635000000e+00\r\n1237 1241  1.5421811000000e+00\r\n1239 1241 -6.3656354000000e-01\r\n1240 1241 -1.3058767000000e+02\r\n1241 1241 -2.9175140000000e+01\r\n1242 1241  4.0757323000000e+00\r\n1245 1241 -6.8751686000000e-01\r\n1288 1241  1.2447368000000e+01\r\n1290 1241 -6.3364510000000e-01\r\n2346 1241 -9.0410623000000e-01\r\n136 1242  1.8701860000000e+01\r\n137 1242 -2.2185372000000e+00\r\n138 1242 -2.0465056000000e+00\r\n1237 1242  2.6069029000000e+00\r\n1238 1242 -3.0924792000000e-01\r\n1239 1242 -1.0760470000000e+00\r\n1240 1242 -2.2074539000000e+02\r\n1241 1242  2.8144064000000e+01\r\n1242 1242  6.8896171000000e+00\r\n1245 1242 -1.1621777000000e+00\r\n1288 1242  2.1041031000000e+01\r\n1289 1242 -2.4960249000000e+00\r\n1290 1242 -1.0711137000000e+00\r\n2346 1242 -1.5283012000000e+00\r\n139 1243 -1.5798380000000e+00\r\n141 1243 -3.7800198000000e-02\r\n1240 1243 -3.0421249000000e-01\r\n1242 1243 -1.7631713000000e-02\r\n1243 1243  1.7737888000000e+02\r\n1245 1243  2.5785878000000e-01\r\n1246 1243 -1.0992009000000e-01\r\n1248 1243 -9.7964493000000e-03\r\n1291 1243 -1.5190962000000e+00\r\n1293 1243 -1.7293696000000e-02\r\n2347 1243 -1.0753633000000e+00\r\n2349 1243 -9.5840005000000e-02\r\n139 1244  1.0271379000000e+01\r\n141 1244 -1.4740605000000e+00\r\n1240 1244  7.6804050000000e-01\r\n1242 1244 -6.8751686000000e-01\r\n1243 1244 -1.2169148000000e+02\r\n1244 1244 -2.8598581000000e+01\r\n1245 1244  4.9391117000000e+00\r\n1248 1244 -7.2186927000000e-01\r\n1291 1244  1.1326966000000e+01\r\n1293 1244 -6.7444889000000e-01\r\n2349 1244 -1.3780428000000e+00\r\n139 1245  1.7362727000000e+01\r\n140 1245 -2.2457823000000e+00\r\n141 1245 -2.4917501000000e+00\r\n1240 1245  1.2982948000000e+00\r\n1241 1245 -1.6792798000000e-01\r\n1242 1245 -1.1621777000000e+00\r\n1243 1245 -2.0570714000000e+02\r\n1244 1245  2.7549954000000e+01\r\n1245 1245  8.3490693000000e+00\r\n1248 1245 -1.2202478000000e+00\r\n1291 1245  1.9147090000000e+01\r\n1292 1245 -2.4765803000000e+00\r\n1293 1245 -1.1400876000000e+00\r\n2349 1245 -2.3294416000000e+00\r\n142 1246 -1.2449286000000e+00\r\n144 1246 -2.3819524000000e-02\r\n1243 1246 -2.1725091000000e-01\r\n1245 1246 -9.7964493000000e-03\r\n1246 1246  1.6530078000000e+02\r\n1248 1246  1.7101052000000e-01\r\n1294 1246 -1.0736056000000e+00\r\n1296 1246 -9.6005376000000e-03\r\n2350 1246 -7.7598780000000e-01\r\n2352 1246 -4.8389152000000e-02\r\n142 1247  9.9607313000000e+00\r\n144 1247 -1.7553192000000e+00\r\n1243 1247  3.9035433000000e-01\r\n1245 1247 -7.2186927000000e-01\r\n1246 1247 -1.1383567000000e+02\r\n1247 1247 -2.7734053000000e+01\r\n1248 1247  5.0443281000000e+00\r\n1294 1247  1.0369892000000e+01\r\n1296 1247 -7.0754460000000e-01\r\n2352 1247 -1.8565169000000e+00\r\n142 1248  1.6837620000000e+01\r\n143 1248 -2.2908186000000e+00\r\n144 1248 -2.9671916000000e+00\r\n1243 1248  6.5985496000000e-01\r\n1244 1248 -8.9775633000000e-02\r\n1245 1248 -1.2202478000000e+00\r\n1246 1248 -1.9242782000000e+02\r\n1247 1248  2.6733771000000e+01\r\n1248 1248  8.5269322000000e+00\r\n1294 1248  1.7529266000000e+01\r\n1295 1248 -2.3849195000000e+00\r\n1296 1248 -1.1960334000000e+00\r\n2352 1248 -3.1382562000000e+00\r\n1249 1249  1.0000000000000e+00\r\n1250 1250  1.0000000000000e+00\r\n1251 1251  1.0000000000000e+00\r\n1252 1252  1.0000000000000e+00\r\n1253 1253  1.0000000000000e+00\r\n1254 1254  1.0000000000000e+00\r\n1255 1255  1.0000000000000e+00\r\n1256 1256  1.0000000000000e+00\r\n1257 1257  1.0000000000000e+00\r\n1258 1258  1.0000000000000e+00\r\n1259 1259  1.0000000000000e+00\r\n1260 1260  1.0000000000000e+00\r\n1261 1261  1.0000000000000e+00\r\n1262 1262  1.0000000000000e+00\r\n1263 1263  1.0000000000000e+00\r\n160 1264 -9.4341750000000e-01\r\n162 1264 -1.5588662000000e-02\r\n1264 1264  2.7372638000000e+02\r\n1266 1264  1.8675300000000e-01\r\n1267 1264 -3.1063380000000e-01\r\n1269 1264 -1.7255584000000e-02\r\n1312 1264 -1.5953616000000e+00\r\n1314 1264 -1.7181733000000e-02\r\n2368 1264 -9.1320914000000e-01\r\n2370 1264 -5.6946019000000e-02\r\n160 1265  7.7871889000000e+00\r\n162 1265 -1.0375061000000e+00\r\n1264 1265 -1.7821273000000e+02\r\n1265 1265 -4.6024490000000e+01\r\n1266 1265  4.0170978000000e+00\r\n1269 1265 -9.2429644000000e-01\r\n1312 1265  1.5256565000000e+01\r\n1314 1265 -1.1435802000000e+00\r\n2370 1265 -9.0660211000000e-01\r\n160 1266  1.3163464000000e+01\r\n161 1266 -1.7642359000000e+00\r\n162 1266 -1.7538002000000e+00\r\n1264 1266 -3.0125080000000e+02\r\n1265 1266  4.1622307000000e+01\r\n1266 1266  6.7905012000000e+00\r\n1269 1266 -1.5624298000000e+00\r\n1312 1266  2.5789698000000e+01\r\n1313 1266 -3.4564694000000e+00\r\n1314 1266 -1.9331079000000e+00\r\n2370 1266 -1.5325202000000e+00\r\n163 1267 -1.3679222000000e+00\r\n165 1267 -3.7420658000000e-02\r\n1264 1267 -1.5570059000000e-01\r\n1266 1267 -1.7255584000000e-02\r\n1267 1267  2.7429668000000e+02\r\n1269 1267  2.2662886000000e-01\r\n1270 1267 -4.5924620000000e-01\r\n1272 1267 -5.0896157000000e-02\r\n1315 1267 -2.3447556000000e+00\r\n1317 1267 -4.1112199000000e-02\r\n163 1268  7.2414355000000e+00\r\n165 1268 -8.3688804000000e-01\r\n1264 1268  6.6831393000000e-03\r\n1266 1268 -9.2429644000000e-01\r\n1267 1268 -1.7646757000000e+02\r\n1268 1268 -4.3113782000000e+01\r\n1269 1268  3.5454112000000e+00\r\n1272 1268 -8.5993164000000e-01\r\n1315 1268  1.4043798000000e+01\r\n1317 1268 -9.1950682000000e-01\r\n163 1269  1.2240915000000e+01\r\n164 1269 -1.4746526000000e+00\r\n165 1269 -1.4146747000000e+00\r\n1264 1269  1.1297172000000e-02\r\n1265 1269 -1.3609606000000e-03\r\n1266 1269 -1.5624298000000e+00\r\n1267 1269 -2.9830062000000e+02\r\n1268 1269  3.8450812000000e+01\r\n1269 1269  5.9931604000000e+00\r\n1272 1269 -1.4536284000000e+00\r\n1315 1269  2.3739623000000e+01\r\n1316 1269 -2.8598919000000e+00\r\n1317 1269 -1.5543334000000e+00\r\n166 1270 -1.5307554000000e+00\r\n168 1270 -4.6029227000000e-02\r\n1267 1270 -4.2528600000000e-01\r\n1269 1270 -5.0896157000000e-02\r\n1270 1270  2.7499971000000e+02\r\n1272 1270  2.7845349000000e-01\r\n1273 1270 -3.7315851000000e-01\r\n1275 1270 -5.0886177000000e-02\r\n1318 1270 -2.6999874000000e+00\r\n1320 1270 -5.0646805000000e-02\r\n166 1271  7.3587639000000e+00\r\n168 1271 -7.7776517000000e-01\r\n1267 1271  3.5203495000000e-01\r\n1269 1271 -8.5993164000000e-01\r\n1270 1271 -1.7669933000000e+02\r\n1271 1271 -4.2206845000000e+01\r\n1272 1271  3.3582000000000e+00\r\n1275 1271 -8.5997629000000e-01\r\n1318 1271  1.3811176000000e+01\r\n1320 1271 -8.5583973000000e-01\r\n166 1272  1.2439255000000e+01\r\n167 1272 -1.4685408000000e+00\r\n168 1272 -1.3147342000000e+00\r\n1267 1272  5.9507987000000e-01\r\n1268 1272 -7.0253332000000e-02\r\n1269 1272 -1.4536284000000e+00\r\n1270 1272 -2.9869255000000e+02\r\n1271 1272  3.7696049000000e+01\r\n1272 1272  5.6767002000000e+00\r\n1275 1272 -1.4537028000000e+00\r\n1318 1272  2.3346412000000e+01\r\n1319 1272 -2.7562069000000e+00\r\n1320 1272 -1.4467115000000e+00\r\n169 1273 -1.5171271000000e+00\r\n171 1273 -4.5988738000000e-02\r\n1270 1273 -4.3522813000000e-01\r\n1272 1273 -5.0886177000000e-02\r\n1273 1273  2.7494106000000e+02\r\n1275 1273  2.6592512000000e-01\r\n1276 1273 -2.8159209000000e-01\r\n1278 1273 -3.8399619000000e-02\r\n1321 1273 -2.7363301000000e+00\r\n1323 1273 -5.0655485000000e-02\r\n169 1274  7.2782798000000e+00\r\n171 1274 -7.7727817000000e-01\r\n1270 1274  3.7276885000000e-01\r\n1272 1274 -8.5997629000000e-01\r\n1273 1274 -1.7682748000000e+02\r\n1274 1274 -4.2207454000000e+01\r\n1275 1274  3.4315562000000e+00\r\n1278 1274 -9.3341499000000e-01\r\n1321 1274  1.3998636000000e+01\r\n1323 1274 -8.5619956000000e-01\r\n169 1275  1.2303195000000e+01\r\n170 1275 -1.4525767000000e+00\r\n171 1275 -1.3139100000000e+00\r\n1270 1275  6.3012799000000e-01\r\n1271 1275 -7.4396062000000e-02\r\n1272 1275 -1.4537028000000e+00\r\n1273 1275 -2.9890894000000e+02\r\n1274 1275  3.7723230000000e+01\r\n1275 1275  5.8006993000000e+00\r\n1278 1275 -1.5778447000000e+00\r\n1321 1275  2.3663276000000e+01\r\n1322 1275 -2.7938047000000e+00\r\n1323 1275 -1.4473186000000e+00\r\n172 1276 -1.3225046000000e+00\r\n174 1276 -3.5749077000000e-02\r\n1273 1276 -4.2846889000000e-01\r\n1275 1276 -3.8399619000000e-02\r\n1276 1276  2.6894547000000e+02\r\n1278 1276  2.1794486000000e-01\r\n1279 1276 -2.3129015000000e-01\r\n1281 1276 -2.5632829000000e-02\r\n1324 1276 -2.3927782000000e+00\r\n1326 1276 -3.8254744000000e-02\r\n172 1277  7.0173118000000e+00\r\n174 1277 -8.6906437000000e-01\r\n1273 1277  5.3178770000000e-01\r\n1275 1277 -9.3341499000000e-01\r\n1276 1277 -1.7415171000000e+02\r\n1277 1277 -4.2499768000000e+01\r\n1278 1277  3.7247494000000e+00\r\n1281 1277 -9.8752534000000e-01\r\n1324 1277  1.4529641000000e+01\r\n1326 1277 -9.3002484000000e-01\r\n172 1278  1.1862064000000e+01\r\n173 1278 -1.4575026000000e+00\r\n174 1278 -1.4690664000000e+00\r\n1273 1278  8.9893392000000e-01\r\n1274 1278 -1.1045283000000e-01\r\n1275 1278 -1.5778447000000e+00\r\n1276 1278 -2.9438605000000e+02\r\n1277 1278  3.8216679000000e+01\r\n1278 1278  6.2963151000000e+00\r\n1281 1278 -1.6693115000000e+00\r\n1324 1278  2.4560905000000e+01\r\n1325 1278 -3.0178208000000e+00\r\n1326 1278 -1.5721140000000e+00\r\n175 1279 -1.1990370000000e+00\r\n177 1279 -2.6535070000000e-02\r\n1276 1279 -4.8675089000000e-01\r\n1278 1279 -2.5632829000000e-02\r\n1279 1279  2.5345377000000e+02\r\n1281 1279  2.7783541000000e-01\r\n1282 1279 -1.6380963000000e-01\r\n1284 1279 -1.4599267000000e-02\r\n1327 1279 -2.0431895000000e+00\r\n1329 1279 -2.5273315000000e-02\r\n2383 1279 -1.1895630000000e+00\r\n2385 1279 -1.0601787000000e-01\r\n175 1280  7.5441924000000e+00\r\n177 1280 -1.0223718000000e+00\r\n1276 1280  1.6053408000000e+00\r\n1278 1280 -9.8752534000000e-01\r\n1279 1280 -1.6708346000000e+02\r\n1280 1280 -4.1094302000000e+01\r\n1281 1280  4.7692005000000e+00\r\n1284 1280 -1.0151535000000e+00\r\n1327 1280  1.5172454000000e+01\r\n1329 1280 -9.7381837000000e-01\r\n2385 1280 -7.6576743000000e-01\r\n175 1281  1.2752693000000e+01\r\n176 1281 -1.6457484000000e+00\r\n177 1281 -1.7282160000000e+00\r\n1276 1281  2.7136660000000e+00\r\n1277 1281 -3.5020145000000e-01\r\n1278 1281 -1.6693115000000e+00\r\n1279 1281 -2.8243766000000e+02\r\n1280 1281  3.7822306000000e+01\r\n1281 1281  8.0618517000000e+00\r\n1284 1281 -1.7160154000000e+00\r\n1327 1281  2.5647495000000e+01\r\n1328 1281 -3.3098362000000e+00\r\n1329 1281 -1.6461413000000e+00\r\n2385 1281 -1.2944525000000e+00\r\n178 1282 -9.4429877000000e-01\r\n180 1282 -1.7904448000000e-02\r\n1279 1282 -3.2832762000000e-01\r\n1281 1282 -1.4599267000000e-02\r\n1282 1282  2.3061226000000e+02\r\n1284 1282  1.9055436000000e-01\r\n1285 1282 -2.7684053000000e-01\r\n1287 1282 -1.3444978000000e-02\r\n1330 1282 -1.4800182000000e+00\r\n1332 1282 -1.4389328000000e-02\r\n2386 1282 -8.1124421000000e-01\r\n2388 1282 -5.0587676000000e-02\r\n178 1283  7.0004257000000e+00\r\n180 1283 -1.2450844000000e+00\r\n1279 1283  7.7100684000000e-01\r\n1281 1283 -1.0151535000000e+00\r\n1282 1283 -1.5247358000000e+02\r\n1283 1283 -3.8737952000000e+01\r\n1284 1283  5.3963467000000e+00\r\n1285 1283  3.3671755000000e-02\r\n1287 1283 -9.3492686000000e-01\r\n1330 1283  1.4324093000000e+01\r\n1332 1283 -1.0007156000000e+00\r\n2388 1283 -1.1961635000000e+00\r\n178 1284  1.1833520000000e+01\r\n179 1284 -1.5965280000000e+00\r\n180 1284 -2.1046906000000e+00\r\n1279 1284  1.3033100000000e+00\r\n1280 1284 -1.7583702000000e-01\r\n1281 1284 -1.7160154000000e+00\r\n1282 1284 -2.5774134000000e+02\r\n1283 1284  3.5691370000000e+01\r\n1284 1284  9.1219845000000e+00\r\n1285 1284  5.6918735000000e-02\r\n1286 1284 -7.6792327000000e-03\r\n1287 1284 -1.5804004000000e+00\r\n1330 1284  2.4213447000000e+01\r\n1331 1284 -3.2667749000000e+00\r\n1332 1284 -1.6916096000000e+00\r\n2388 1284 -2.0219947000000e+00\r\n181 1285 -4.9113639000000e-01\r\n183 1285 -8.8105909000000e-03\r\n1237 1285 -1.9213504000000e+00\r\n1239 1285 -5.6301327000000e-02\r\n1282 1285 -4.5882599000000e-01\r\n1284 1285 -1.3444978000000e-02\r\n1285 1285  2.1517023000000e+02\r\n1287 1285  1.1397561000000e-01\r\n1288 1285 -9.6336002000000e-02\r\n1290 1285 -2.8229337000000e-03\r\n1333 1285 -7.4843137000000e-01\r\n1335 1285 -6.0525091000000e-03\r\n2389 1285 -8.8396792000000e-01\r\n2391 1285 -2.5902910000000e-02\r\n181 1286  4.3571752000000e+00\r\n183 1286 -1.5144038000000e+00\r\n1239 1286 -5.4102785000000e-01\r\n1284 1286 -9.3492686000000e-01\r\n1285 1286 -1.3784731000000e+02\r\n1286 1286 -3.7353073000000e+01\r\n1287 1286  6.6361713000000e+00\r\n1290 1286 -1.0486939000000e+00\r\n1333 1286  1.2460168000000e+01\r\n1335 1286 -1.0404125000000e+00\r\n2391 1286 -1.5525563000000e+00\r\n181 1287  7.3653644000000e+00\r\n182 1287 -1.0349868000000e+00\r\n183 1287 -2.5599466000000e+00\r\n1239 1287 -9.1455284000000e-01\r\n1284 1287 -1.5804004000000e+00\r\n1285 1287 -2.3301694000000e+02\r\n1286 1287  3.3533235000000e+01\r\n1287 1287  1.1217779000000e+01\r\n1290 1287 -1.7727122000000e+00\r\n1333 1287  2.1062655000000e+01\r\n1334 1287 -2.9597410000000e+00\r\n1335 1287 -1.7587122000000e+00\r\n2391 1287 -2.6244395000000e+00\r\n184 1288 -3.5135249000000e-01\r\n186 1288 -4.7336046000000e-03\r\n1240 1288 -1.7041409000000e+00\r\n1242 1288 -3.0138742000000e-02\r\n1285 1288 -2.0094568000000e-01\r\n1287 1288 -2.8229337000000e-03\r\n1288 1288  1.9779559000000e+02\r\n1290 1288  5.3736241000000e-02\r\n1291 1288 -1.0674129000000e-01\r\n1293 1288 -1.8877829000000e-03\r\n1336 1288 -4.5062396000000e-01\r\n1338 1288 -2.7784901000000e-03\r\n2392 1288 -6.1217237000000e-01\r\n2394 1288 -1.0826631000000e-02\r\n184 1289  3.1476727000000e+00\r\n186 1289 -1.7586124000000e+00\r\n1242 1289 -6.3364510000000e-01\r\n1285 1289  1.5631499000000e+00\r\n1287 1289 -1.0486939000000e+00\r\n1288 1289 -1.2762179000000e+02\r\n1289 1289 -3.5250430000000e+01\r\n1290 1289  7.4250632000000e+00\r\n1293 1289 -9.9184626000000e-01\r\n1336 1289  1.1194629000000e+01\r\n1338 1289 -1.0323390000000e+00\r\n2394 1289 -1.9560092000000e+00\r\n184 1290  5.3208259000000e+00\r\n185 1290 -7.7296038000000e-01\r\n186 1290 -2.9727583000000e+00\r\n1242 1290 -1.0711137000000e+00\r\n1285 1290  2.6423486000000e+00\r\n1286 1290 -3.8385597000000e-01\r\n1287 1290 -1.7727122000000e+00\r\n1288 1290 -2.1573187000000e+02\r\n1289 1290  3.1772134000000e+01\r\n1290 1290  1.2551325000000e+01\r\n1293 1290 -1.6766156000000e+00\r\n1336 1290  1.8923400000000e+01\r\n1337 1290 -2.7490166000000e+00\r\n1338 1290 -1.7450659000000e+00\r\n2394 1290 -3.3064380000000e+00\r\n187 1291 -2.8222379000000e-01\r\n189 1291 -3.7533603000000e-03\r\n1243 1291 -9.7784090000000e-01\r\n1245 1291 -1.7293696000000e-02\r\n1288 1291 -1.5896989000000e-01\r\n1290 1291 -1.8877829000000e-03\r\n1291 1291  1.8041258000000e+02\r\n1293 1291  3.3488050000000e-02\r\n1294 1291 -7.8484528000000e-02\r\n1296 1291 -1.3880454000000e-03\r\n1339 1291 -3.5805095000000e-01\r\n1341 1291 -1.8557042000000e-03\r\n2395 1291 -3.8579490000000e-01\r\n2397 1291 -6.8230113000000e-03\r\n187 1292  2.7004002000000e+00\r\n189 1292 -1.9721237000000e+00\r\n1245 1292 -6.7444889000000e-01\r\n1288 1292  2.0088489000000e+00\r\n1290 1292 -9.9184626000000e-01\r\n1291 1292 -1.1678376000000e+02\r\n1292 1292 -3.2598054000000e+01\r\n1293 1292  7.8000515000000e+00\r\n1296 1292 -9.3479640000000e-01\r\n1339 1292  9.6689609000000e+00\r\n1341 1292 -9.7512180000000e-01\r\n2397 1292 -2.2480915000000e+00\r\n187 1293  4.5647529000000e+00\r\n188 1293 -6.8172614000000e-01\r\n189 1293 -3.3336753000000e+00\r\n1245 1293 -1.1400876000000e+00\r\n1288 1293  3.3957556000000e+00\r\n1289 1293 -5.0714144000000e-01\r\n1290 1293 -1.6766156000000e+00\r\n1291 1293 -1.9741111000000e+02\r\n1292 1293  2.9396479000000e+01\r\n1293 1293  1.3185199000000e+01\r\n1296 1293 -1.5801798000000e+00\r\n1339 1293  1.6344398000000e+01\r\n1340 1293 -2.4409657000000e+00\r\n1341 1293 -1.6483446000000e+00\r\n2397 1293 -3.8001718000000e+00\r\n190 1294 -2.4677947000000e-01\r\n192 1294 -3.1688925000000e-03\r\n1246 1294 -5.4284512000000e-01\r\n1248 1294 -9.6005376000000e-03\r\n1291 1294 -1.1892199000000e-01\r\n1293 1294 -1.3880454000000e-03\r\n1294 1294  1.6891509000000e+02\r\n1296 1294  2.2088858000000e-02\r\n1342 1294 -2.8875352000000e-01\r\n1344 1294 -1.3818955000000e-03\r\n2398 1294 -3.4495919000000e-01\r\n2400 1294 -6.1008077000000e-03\r\n190 1295  2.6224513000000e+00\r\n192 1295 -2.1342173000000e+00\r\n1248 1295 -7.0754460000000e-01\r\n1291 1295  1.5524766000000e+00\r\n1293 1295 -9.3479640000000e-01\r\n1294 1295 -1.0842997000000e+02\r\n1295 1295 -3.0770477000000e+01\r\n1296 1295  7.1518116000000e+00\r\n1342 1295  8.0561138000000e+00\r\n1344 1295 -9.3077878000000e-01\r\n2400 1295 -2.4410548000000e+00\r\n190 1296  4.4329917000000e+00\r\n191 1296 -6.7205137000000e-01\r\n192 1296 -3.6076809000000e+00\r\n1248 1296 -1.1960334000000e+00\r\n1291 1296  2.6243064000000e+00\r\n1292 1296 -3.9785068000000e-01\r\n1293 1296 -1.5801798000000e+00\r\n1294 1296 -1.8329003000000e+02\r\n1295 1296  2.7455917000000e+01\r\n1296 1296  1.2089422000000e+01\r\n1342 1296  1.3618055000000e+01\r\n1343 1296 -2.0645273000000e+00\r\n1344 1296 -1.5733884000000e+00\r\n2400 1296 -4.1263590000000e+00\r\n1297 1297  1.0000000000000e+00\r\n1298 1298  1.0000000000000e+00\r\n1299 1299  1.0000000000000e+00\r\n1300 1300  1.0000000000000e+00\r\n1301 1301  1.0000000000000e+00\r\n1302 1302  1.0000000000000e+00\r\n1303 1303  1.0000000000000e+00\r\n1304 1304  1.0000000000000e+00\r\n1305 1305  1.0000000000000e+00\r\n1306 1306  1.0000000000000e+00\r\n1307 1307  1.0000000000000e+00\r\n1308 1308  1.0000000000000e+00\r\n1309 1309  1.0000000000000e+00\r\n1310 1310  1.0000000000000e+00\r\n1311 1311  1.0000000000000e+00\r\n208 1312 -2.2967574000000e-01\r\n210 1312 -2.5591232000000e-03\r\n1264 1312 -9.7151014000000e-01\r\n1266 1312 -1.7181733000000e-02\r\n1312 1312  2.7223071000000e+02\r\n1314 1312  3.2932197000000e-02\r\n1315 1312 -1.7210740000000e-01\r\n1317 1312 -2.8294990000000e-03\r\n1360 1312 -5.3250509000000e-01\r\n1362 1312 -2.8194601000000e-03\r\n2416 1312 -3.8467931000000e-01\r\n2418 1312 -6.8032816000000e-03\r\n208 1313  3.2697759000000e+00\r\n210 1313 -1.2998960000000e+00\r\n1266 1313 -1.1435802000000e+00\r\n1312 1313 -1.7317694000000e+02\r\n1313 1313 -4.9368972000000e+01\r\n1314 1313  6.7511947000000e+00\r\n1315 1313  4.9197405000000e-01\r\n1317 1313 -1.4371314000000e+00\r\n1360 1313  1.4275476000000e+01\r\n1362 1313 -1.4322317000000e+00\r\n2418 1313 -1.4328639000000e+00\r\n208 1314  5.5272291000000e+00\r\n209 1314 -8.2353642000000e-01\r\n210 1314 -2.1973442000000e+00\r\n1266 1314 -1.9331079000000e+00\r\n1312 1314 -2.9273829000000e+02\r\n1313 1314  4.3512859000000e+01\r\n1314 1314  1.1412219000000e+01\r\n1315 1314  8.3163294000000e-01\r\n1316 1314 -1.2391019000000e-01\r\n1317 1314 -2.4293269000000e+00\r\n1360 1314  2.4131264000000e+01\r\n1361 1314 -3.5954678000000e+00\r\n1362 1314 -2.4210445000000e+00\r\n2418 1314 -2.4221131000000e+00\r\n211 1315 -2.4668124000000e-01\r\n213 1315 -2.8842481000000e-03\r\n1267 1315 -2.3246153000000e+00\r\n1269 1315 -4.1112199000000e-02\r\n1312 1315 -1.5998893000000e-01\r\n1314 1315 -2.8294990000000e-03\r\n1315 1315  2.7395310000000e+02\r\n1317 1315  6.3605256000000e-02\r\n1318 1315 -1.8438923000000e-01\r\n1320 1315 -3.1910365000000e-03\r\n1363 1315 -5.5027657000000e-01\r\n1365 1315 -3.1808633000000e-03\r\n2419 1315 -5.4619795000000e-01\r\n2421 1315 -9.6598344000000e-03\r\n211 1316  3.1960331000000e+00\r\n213 1316 -1.2865738000000e+00\r\n1269 1316 -9.1950682000000e-01\r\n1314 1316 -1.4371314000000e+00\r\n1315 1316 -1.7264244000000e+02\r\n1316 1316 -4.9216982000000e+01\r\n1317 1316  7.8573807000000e+00\r\n1318 1316  1.6264263000000e-01\r\n1320 1316 -1.4233134000000e+00\r\n1363 1316  1.4143033000000e+01\r\n1365 1316 -1.4189740000000e+00\r\n2421 1316 -1.3664069000000e+00\r\n211 1317  5.4025700000000e+00\r\n212 1317 -7.9723475000000e-01\r\n213 1317 -2.1748226000000e+00\r\n1269 1317 -1.5543334000000e+00\r\n1314 1317 -2.4293269000000e+00\r\n1315 1317 -2.9183455000000e+02\r\n1316 1317  4.3218287000000e+01\r\n1317 1317  1.3282108000000e+01\r\n1318 1317  2.7493090000000e-01\r\n1319 1317 -4.0570407000000e-02\r\n1320 1317 -2.4059670000000e+00\r\n1363 1317  2.3907365000000e+01\r\n1364 1317 -3.5279108000000e+00\r\n1365 1317 -2.3986317000000e+00\r\n2421 1317 -2.3097726000000e+00\r\n214 1318 -2.8443899000000e-01\r\n216 1318 -3.5153406000000e-03\r\n1270 1318 -2.8637324000000e+00\r\n1272 1318 -5.0646805000000e-02\r\n1315 1318 -1.8043142000000e-01\r\n1317 1318 -3.1910365000000e-03\r\n1318 1318  2.7481093000000e+02\r\n1320 1318  7.8662068000000e-02\r\n1321 1318 -2.4138800000000e-01\r\n1323 1318 -4.2690898000000e-03\r\n1366 1318 -5.9699022000000e-01\r\n1368 1318 -3.8802399000000e-03\r\n2422 1318 -7.0088362000000e-01\r\n2424 1318 -1.2395542000000e-02\r\n214 1319  3.2664290000000e+00\r\n216 1319 -1.2614183000000e+00\r\n1272 1319 -8.5583973000000e-01\r\n1317 1319 -1.4233134000000e+00\r\n1318 1319 -1.7281288000000e+02\r\n1319 1319 -4.8921717000000e+01\r\n1320 1319  7.6431732000000e+00\r\n1323 1319 -1.3833851000000e+00\r\n1366 1319  1.4403206000000e+01\r\n1368 1319 -1.3924364000000e+00\r\n2424 1319 -1.3213394000000e+00\r\n214 1320  5.5215716000000e+00\r\n215 1320 -7.9947677000000e-01\r\n216 1320 -2.1323014000000e+00\r\n1272 1320 -1.4467115000000e+00\r\n1317 1320 -2.4059670000000e+00\r\n1318 1320 -2.9212289000000e+02\r\n1319 1320  4.2950807000000e+01\r\n1320 1320  1.2920016000000e+01\r\n1323 1320 -2.3384726000000e+00\r\n1366 1320  2.4347179000000e+01\r\n1367 1320 -3.5252652000000e+00\r\n1368 1320 -2.3537745000000e+00\r\n2424 1320 -2.2335922000000e+00\r\n217 1321 -2.6456607000000e-01\r\n219 1321 -3.8554926000000e-03\r\n1273 1321 -1.7286792000000e+00\r\n1275 1321 -5.0655485000000e-02\r\n1318 1321 -1.5451154000000e-01\r\n1320 1321 -4.2690898000000e-03\r\n1321 1321  2.7349579000000e+02\r\n1323 1321  8.2507420000000e-02\r\n1324 1321 -1.4526412000000e-01\r\n1326 1321 -4.2566742000000e-03\r\n1369 1321 -7.6581908000000e-01\r\n1371 1321 -4.2558043000000e-03\r\n2425 1321 -4.9287455000000e-01\r\n2427 1321 -1.4442702000000e-02\r\n217 1322  3.0876061000000e+00\r\n219 1322 -1.2494341000000e+00\r\n1275 1322 -8.5619956000000e-01\r\n1318 1322  2.4181193000000e-01\r\n1320 1322 -1.3833851000000e+00\r\n1321 1322 -1.7276544000000e+02\r\n1322 1322 -4.8774953000000e+01\r\n1323 1322  7.5456821000000e+00\r\n1326 1322 -1.3835616000000e+00\r\n1369 1322  1.4291331000000e+01\r\n1371 1322 -1.3792433000000e+00\r\n2427 1322 -1.2884342000000e+00\r\n217 1323  5.2192858000000e+00\r\n218 1323 -7.7639466000000e-01\r\n219 1323 -2.1120419000000e+00\r\n1275 1323 -1.4473186000000e+00\r\n1318 1323  4.0875861000000e-01\r\n1319 1323 -6.0804872000000e-02\r\n1320 1323 -2.3384726000000e+00\r\n1321 1323 -2.9204251000000e+02\r\n1322 1323  4.2945063000000e+01\r\n1323 1323  1.2755213000000e+01\r\n1326 1323 -2.3387725000000e+00\r\n1369 1323  2.4158050000000e+01\r\n1370 1323 -3.5936298000000e+00\r\n1371 1323 -2.3314713000000e+00\r\n2427 1323 -2.1779671000000e+00\r\n220 1324 -2.5348871000000e-01\r\n222 1324 -3.8426087000000e-03\r\n1276 1324 -1.3054890000000e+00\r\n1278 1324 -3.8254744000000e-02\r\n1321 1324 -1.7752046000000e-01\r\n1323 1324 -4.2566742000000e-03\r\n1324 1324  2.7306577000000e+02\r\n1326 1324  6.9051934000000e-02\r\n1327 1324 -1.1080353000000e-01\r\n1329 1324 -3.2468757000000e-03\r\n1372 1324 -7.8112229000000e-01\r\n1374 1324 -4.2450288000000e-03\r\n2428 1324 -4.9257780000000e-01\r\n2430 1324 -1.4434007000000e-02\r\n220 1325  2.8481953000000e+00\r\n222 1325 -1.2490543000000e+00\r\n1278 1325 -9.3002484000000e-01\r\n1321 1325  7.5067591000000e-01\r\n1323 1325 -1.3835616000000e+00\r\n1324 1325 -1.7340412000000e+02\r\n1325 1325 -4.8777713000000e+01\r\n1326 1325  7.6252238000000e+00\r\n1329 1325 -1.3893338000000e+00\r\n1372 1325  1.4659879000000e+01\r\n1374 1325 -1.3799393000000e+00\r\n2430 1325 -1.2878855000000e+00\r\n220 1326  4.8145894000000e+00\r\n221 1326 -7.1633806000000e-01\r\n222 1326 -2.1114013000000e+00\r\n1278 1326 -1.5721140000000e+00\r\n1321 1326  1.2689425000000e+00\r\n1322 1326 -1.8879944000000e-01\r\n1323 1326 -2.3387725000000e+00\r\n1324 1326 -2.9312233000000e+02\r\n1325 1326  4.3110071000000e+01\r\n1326 1326  1.2889677000000e+01\r\n1329 1326 -2.3485284000000e+00\r\n1372 1326  2.4781060000000e+01\r\n1373 1326 -3.6870468000000e+00\r\n1374 1326 -2.3326495000000e+00\r\n2430 1326 -2.1770417000000e+00\r\n223 1327 -2.4545835000000e-01\r\n225 1327 -3.1193424000000e-03\r\n1279 1327 -1.4290341000000e+00\r\n1281 1327 -2.5273315000000e-02\r\n1324 1327 -2.1351350000000e-01\r\n1326 1327 -3.2468757000000e-03\r\n1327 1327  2.6218126000000e+02\r\n1329 1327  4.5701364000000e-02\r\n1330 1327 -1.0206592000000e-01\r\n1332 1327 -1.8050962000000e-03\r\n1375 1327 -5.7719046000000e-01\r\n1377 1327 -3.2392722000000e-03\r\n2431 1327 -4.6913868000000e-01\r\n2433 1327 -8.2969956000000e-03\r\n223 1328  2.6556692000000e+00\r\n225 1328 -1.3348595000000e+00\r\n1281 1328 -9.7381837000000e-01\r\n1324 1328  1.1211317000000e+00\r\n1326 1328 -1.3893338000000e+00\r\n1327 1328 -1.6777298000000e+02\r\n1328 1328 -4.7196986000000e+01\r\n1329 1328  7.9181472000000e+00\r\n1332 1328 -1.3662471000000e+00\r\n1375 1328  1.5059125000000e+01\r\n1377 1328 -1.3862673000000e+00\r\n2433 1328 -1.4623719000000e+00\r\n223 1329  4.4891401000000e+00\r\n224 1329 -6.6023896000000e-01\r\n225 1329 -2.2564449000000e+00\r\n1281 1329 -1.6461413000000e+00\r\n1324 1329  1.8951598000000e+00\r\n1325 1329 -2.7873005000000e-01\r\n1326 1329 -2.3485284000000e+00\r\n1327 1329 -2.8360325000000e+02\r\n1328 1329  4.1945986000000e+01\r\n1329 1329  1.3384829000000e+01\r\n1332 1329 -2.3095040000000e+00\r\n1375 1329  2.5455928000000e+01\r\n1376 1329 -3.7439226000000e+00\r\n1377 1329 -2.3433446000000e+00\r\n2433 1329 -2.4719924000000e+00\r\n226 1330 -1.6964017000000e-01\r\n228 1330 -1.9490968000000e-03\r\n1282 1330 -8.1361864000000e-01\r\n1284 1330 -1.4389328000000e-02\r\n1327 1330 -1.4452863000000e-01\r\n1329 1330 -1.8050962000000e-03\r\n1330 1330  2.4486254000000e+02\r\n1332 1330  2.6182592000000e-02\r\n1333 1330 -5.4021312000000e-02\r\n1335 1330 -9.5539891000000e-04\r\n1378 1330 -4.7203252000000e-01\r\n1380 1330 -1.7830369000000e-03\r\n2434 1330 -2.6316000000000e-01\r\n2436 1330 -4.6541406000000e-03\r\n226 1331  2.2969720000000e+00\r\n228 1331 -1.4753468000000e+00\r\n1284 1331 -1.0007156000000e+00\r\n1327 1331  1.6297685000000e+00\r\n1329 1331 -1.3662471000000e+00\r\n1330 1331 -1.5774793000000e+02\r\n1331 1331 -4.1064603000000e+01\r\n1332 1331  8.1507424000000e+00\r\n1335 1331 -1.2936026000000e+00\r\n1378 1331  1.4196280000000e+01\r\n1380 1331 -1.3497327000000e+00\r\n2436 1331 -1.6601180000000e+00\r\n226 1332  3.8828015000000e+00\r\n227 1332 -5.9213620000000e-01\r\n228 1332 -2.4939263000000e+00\r\n1284 1332 -1.6916096000000e+00\r\n1327 1332  2.7549606000000e+00\r\n1328 1332 -4.2013785000000e-01\r\n1329 1332 -2.3095040000000e+00\r\n1330 1332 -2.6665710000000e+02\r\n1331 1332  4.6264109000000e+01\r\n1332 1332  1.3778014000000e+01\r\n1335 1332 -2.1867046000000e+00\r\n1378 1332  2.3997392000000e+01\r\n1379 1332 -3.6596577000000e+00\r\n1380 1332 -2.2815881000000e+00\r\n2436 1332 -2.8062634000000e+00\r\n229 1333 -1.3642991000000e-01\r\n231 1333 -1.2270051000000e-03\r\n1285 1333 -5.7993932000000e-01\r\n1287 1333 -6.0525091000000e-03\r\n1330 1333 -1.1300694000000e-01\r\n1332 1333 -9.5539891000000e-04\r\n1333 1333  2.2278356000000e+02\r\n1335 1333  1.3701012000000e-02\r\n1336 1333 -5.3377101000000e-02\r\n1338 1333 -5.5706758000000e-04\r\n1381 1333 -2.2680976000000e-01\r\n1383 1333 -9.4287598000000e-04\r\n2437 1333 -3.2536038000000e-01\r\n2439 1333 -3.3956081000000e-03\r\n229 1334  1.8522376000000e+00\r\n231 1334 -1.6614562000000e+00\r\n1287 1334 -1.0404125000000e+00\r\n1330 1334  2.0830028000000e+00\r\n1332 1334 -1.2936026000000e+00\r\n1333 1334 -1.4455120000000e+02\r\n1334 1334 -4.1118626000000e+01\r\n1335 1334  8.3866352000000e+00\r\n1338 1334 -1.2207824000000e+00\r\n1381 1334  1.3404257000000e+01\r\n1383 1334 -1.2768153000000e+00\r\n2439 1334 -1.8889917000000e+00\r\n229 1335  3.1310206000000e+00\r\n230 1335 -4.7319693000000e-01\r\n231 1335 -2.8085241000000e+00\r\n1287 1335 -1.7587122000000e+00\r\n1330 1335  3.5211060000000e+00\r\n1331 1335 -5.3215124000000e-01\r\n1332 1335 -2.1867046000000e+00\r\n1333 1335 -2.4434921000000e+02\r\n1334 1335  3.6879671000000e+01\r\n1335 1335  1.4176761000000e+01\r\n1338 1335 -2.0636106000000e+00\r\n1381 1335  2.2658544000000e+01\r\n1382 1335 -3.4244273000000e+00\r\n1383 1335 -2.1583274000000e+00\r\n2439 1335 -3.1931494000000e+00\r\n232 1336 -9.4691775000000e-02\r\n234 1336 -8.3846689000000e-04\r\n1288 1336 -2.6622936000000e-01\r\n1290 1336 -2.7784901000000e-03\r\n1333 1336 -7.9317551000000e-02\r\n1335 1336 -5.5706758000000e-04\r\n1336 1336  2.0593401000000e+02\r\n1338 1336  7.1190537000000e-03\r\n1339 1336 -3.2430064000000e-02\r\n1341 1336 -3.3845482000000e-04\r\n1384 1336 -1.6328562000000e-01\r\n1386 1336 -5.4926603000000e-04\r\n2440 1336 -1.4818824000000e-01\r\n2442 1336 -1.5465596000000e-03\r\n232 1337  1.4134890000000e+00\r\n234 1337 -1.8375694000000e+00\r\n1290 1337 -1.0323390000000e+00\r\n1333 1337  2.5500288000000e+00\r\n1335 1337 -1.2207824000000e+00\r\n1336 1337 -1.3389236000000e+02\r\n1337 1337 -3.8434575000000e+01\r\n1338 1337  8.5689023000000e+00\r\n1341 1337 -1.1452500000000e+00\r\n1384 1337  1.2028529000000e+01\r\n1386 1337 -1.2038403000000e+00\r\n2442 1337 -2.1248446000000e+00\r\n232 1338  2.3893618000000e+00\r\n233 1338 -3.7068624000000e-01\r\n234 1338 -3.1062273000000e+00\r\n1290 1338 -1.7450659000000e+00\r\n1333 1338  4.3105686000000e+00\r\n1334 1338 -6.6874278000000e-01\r\n1335 1338 -2.0636106000000e+00\r\n1336 1338 -2.2633164000000e+02\r\n1337 1338  3.4516930000000e+01\r\n1338 1338  1.4484871000000e+01\r\n1341 1338 -1.9359292000000e+00\r\n1384 1338  2.0333025000000e+01\r\n1385 1338 -3.1544711000000e+00\r\n1386 1338 -2.0349717000000e+00\r\n2442 1338 -3.5918374000000e+00\r\n235 1339 -5.9815559000000e-02\r\n237 1339 -5.9869776000000e-04\r\n1291 1339 -1.7780986000000e-01\r\n1293 1339 -1.8557042000000e-03\r\n1336 1339 -6.1814214000000e-02\r\n1338 1339 -3.3845482000000e-04\r\n1339 1339  1.8949353000000e+02\r\n1341 1339  4.9610741000000e-03\r\n1342 1339 -1.0790809000000e-02\r\n1344 1339 -1.1261776000000e-04\r\n1387 1339 -1.0917736000000e-01\r\n1389 1339 -3.3334856000000e-04\r\n2443 1339 -1.2089323000000e-01\r\n2445 1339 -1.2616964000000e-03\r\n235 1340  1.1849396000000e+00\r\n237 1340 -2.0259409000000e+00\r\n1293 1340 -9.7512180000000e-01\r\n1336 1340  2.8854936000000e+00\r\n1338 1340 -1.1452500000000e+00\r\n1339 1340 -1.2295136000000e+02\r\n1340 1340 -3.5577035000000e+01\r\n1341 1340  8.7141966000000e+00\r\n1344 1340 -1.0875644000000e+00\r\n1387 1340  1.0289212000000e+01\r\n1389 1340 -1.1280965000000e+00\r\n2445 1340 -2.3482642000000e+00\r\n235 1341  2.0030206000000e+00\r\n236 1341 -3.1551711000000e-01\r\n237 1341 -3.4246482000000e+00\r\n1293 1341 -1.6483446000000e+00\r\n1336 1341  4.8776351000000e+00\r\n1337 1341 -7.6832827000000e-01\r\n1338 1341 -1.9359292000000e+00\r\n1339 1341 -2.0783683000000e+02\r\n1340 1341  3.1890305000000e+01\r\n1341 1341  1.4730469000000e+01\r\n1344 1341 -1.8384188000000e+00\r\n1387 1341  1.7392873000000e+01\r\n1388 1341 -2.7397367000000e+00\r\n1389 1341 -1.9069330000000e+00\r\n2445 1341 -3.9695031000000e+00\r\n238 1342 -1.0052266000000e-03\r\n240 1342 -1.0490999000000e-05\r\n1294 1342 -1.3241047000000e-01\r\n1296 1342 -1.3818955000000e-03\r\n1339 1342 -3.9817283000000e-02\r\n1341 1342 -1.1261776000000e-04\r\n1342 1342  1.7843031000000e+02\r\n1344 1342  2.8591254000000e-03\r\n1390 1342 -2.3448881000000e-02\r\n1392 1342 -1.1074615000000e-04\r\n2446 1342 -7.8631371000000e-02\r\n2448 1342 -8.2063256000000e-04\r\n238 1343  1.0530149000000e+00\r\n240 1343 -2.1889664000000e+00\r\n1296 1343 -9.3077878000000e-01\r\n1339 1343  2.8496034000000e+00\r\n1341 1343 -1.0875644000000e+00\r\n1342 1343 -1.1210207000000e+02\r\n1343 1343 -3.3750151000000e+01\r\n1344 1343  7.8225303000000e+00\r\n1390 1343  5.8141667000000e+00\r\n1392 1343 -1.0695946000000e+00\r\n2448 1343 -2.5418704000000e+00\r\n238 1344  1.7800163000000e+00\r\n239 1344 -2.8562166000000e-01\r\n240 1344 -3.7002288000000e+00\r\n1296 1344 -1.5733884000000e+00\r\n1339 1344  4.8169695000000e+00\r\n1340 1344 -7.7293156000000e-01\r\n1341 1344 -1.8384188000000e+00\r\n1342 1344 -1.8949733000000e+02\r\n1343 1344  2.9257887000000e+01\r\n1344 1344  1.3223205000000e+01\r\n1390 1344  9.8282675000000e+00\r\n1391 1344 -1.5770451000000e+00\r\n1392 1344 -1.8080426000000e+00\r\n2448 1344 -4.2967777000000e+00\r\n1345 1345  1.0000000000000e+00\r\n1346 1346  1.0000000000000e+00\r\n1347 1347  1.0000000000000e+00\r\n1348 1348  1.0000000000000e+00\r\n1349 1349  1.0000000000000e+00\r\n1350 1350  1.0000000000000e+00\r\n1351 1351  1.0000000000000e+00\r\n1352 1352  1.0000000000000e+00\r\n1353 1353  1.0000000000000e+00\r\n1354 1354  1.0000000000000e+00\r\n1355 1355  1.0000000000000e+00\r\n1356 1356  1.0000000000000e+00\r\n1357 1357  1.0000000000000e+00\r\n1358 1358  1.0000000000000e+00\r\n1359 1359  1.0000000000000e+00\r\n256 1360 -7.2977776000000e-04\r\n258 1360 -7.6162909000000e-06\r\n1312 1360 -2.7015503000000e-01\r\n1314 1360 -2.8194601000000e-03\r\n1360 1360  2.7046663000000e+02\r\n1362 1360  5.1151597000000e-03\r\n1363 1360 -3.7651590000000e-02\r\n1365 1360 -3.5388657000000e-04\r\n1408 1360 -1.5377477000000e-01\r\n1410 1360 -3.5321712000000e-04\r\n2464 1360 -8.9063470000000e-02\r\n2466 1360 -9.2950667000000e-04\r\n256 1361  1.6788203000000e+00\r\n258 1361 -1.4261365000000e+00\r\n1314 1361 -1.4322317000000e+00\r\n1360 1361 -1.7189519000000e+02\r\n1361 1361 -4.6745499000000e+01\r\n1362 1361  7.6639625000000e+00\r\n1363 1361  3.6624285000000e-01\r\n1365 1361 -1.5827589000000e+00\r\n1408 1361  1.4741648000000e+01\r\n1410 1361 -1.5799292000000e+00\r\n2466 1361 -1.6372305000000e+00\r\n256 1362  2.8378778000000e+00\r\n257 1362 -4.5011231000000e-01\r\n258 1362 -2.4107412000000e+00\r\n1314 1362 -2.4210445000000e+00\r\n1360 1362 -2.9057162000000e+02\r\n1361 1362  5.1757860000000e+01\r\n1362 1362  1.2955162000000e+01\r\n1363 1362  6.1909691000000e-01\r\n1364 1362 -9.8194198000000e-02\r\n1365 1362 -2.6754957000000e+00\r\n1408 1362  2.4919282000000e+01\r\n1409 1362 -3.9524166000000e+00\r\n1410 1362 -2.6707124000000e+00\r\n2466 1362 -2.7675744000000e+00\r\n259 1363 -7.3412139000000e-04\r\n261 1363 -7.6616229000000e-06\r\n1315 1363 -3.0478396000000e-01\r\n1317 1363 -3.1808633000000e-03\r\n1360 1363 -3.3908703000000e-02\r\n1362 1363 -3.5388657000000e-04\r\n1363 1363  2.7060496000000e+02\r\n1365 1363  6.3467067000000e-03\r\n1366 1363 -5.4179127000000e-02\r\n1368 1363 -5.1886286000000e-04\r\n1411 1363 -1.8816192000000e-01\r\n1413 1363 -5.1772590000000e-04\r\n2467 1363 -1.0603352000000e-01\r\n2469 1363 -1.1066138000000e-03\r\n259 1364  1.7171980000000e+00\r\n261 1364 -1.4116883000000e+00\r\n1317 1364 -1.4189740000000e+00\r\n1362 1364 -1.5827589000000e+00\r\n1363 1364 -1.7228586000000e+02\r\n1364 1364 -5.0782874000000e+01\r\n1365 1364  9.1689950000000e+00\r\n1366 1364  4.3654628000000e-01\r\n1368 1364 -1.5665785000000e+00\r\n1411 1364  1.5021144000000e+01\r\n1413 1364 -1.5633187000000e+00\r\n2469 1364 -1.6200209000000e+00\r\n259 1365  2.9027491000000e+00\r\n260 1365 -4.5568920000000e-01\r\n261 1365 -2.3863159000000e+00\r\n1317 1365 -2.3986317000000e+00\r\n1362 1365 -2.6754957000000e+00\r\n1363 1365 -2.9123177000000e+02\r\n1364 1365  4.4566443000000e+01\r\n1365 1365  1.5499259000000e+01\r\n1366 1365  7.3793721000000e-01\r\n1367 1365 -1.1584536000000e-01\r\n1368 1365 -2.6481421000000e+00\r\n1411 1365  2.5391720000000e+01\r\n1412 1365 -3.9861297000000e+00\r\n1413 1365 -2.6426316000000e+00\r\n2469 1365 -2.7384818000000e+00\r\n262 1366 -8.3648948000000e-02\r\n264 1366 -6.9066782000000e-04\r\n1318 1366 -3.7179683000000e-01\r\n1320 1366 -3.8802399000000e-03\r\n1363 1366 -4.9716401000000e-02\r\n1365 1366 -5.1886286000000e-04\r\n1366 1366  2.7088887000000e+02\r\n1368 1366  8.9254441000000e-03\r\n1369 1366 -7.5229391000000e-02\r\n1371 1366 -7.6641004000000e-04\r\n1414 1366 -2.3217630000000e-01\r\n1416 1366 -7.6427333000000e-04\r\n2470 1366 -1.5613218000000e-01\r\n2472 1366 -1.6294661000000e-03\r\n262 1367  1.7659413000000e+00\r\n264 1367 -1.3900576000000e+00\r\n1320 1367 -1.3924364000000e+00\r\n1365 1367 -1.5665785000000e+00\r\n1366 1367 -1.7267578000000e+02\r\n1367 1367 -5.0522390000000e+01\r\n1368 1367  9.0250451000000e+00\r\n1369 1367  1.7603575000000e-01\r\n1371 1367 -1.5423978000000e+00\r\n1414 1367  1.5619168000000e+01\r\n1416 1367 -1.5382633000000e+00\r\n2472 1367 -1.5896856000000e+00\r\n262 1368  2.9851472000000e+00\r\n263 1368 -4.6135374000000e-01\r\n264 1368 -2.3497534000000e+00\r\n1320 1368 -2.3537745000000e+00\r\n1365 1368 -2.6481421000000e+00\r\n1366 1368 -2.9189114000000e+02\r\n1367 1368  4.4401261000000e+01\r\n1368 1368  1.5255934000000e+01\r\n1369 1368  2.9757084000000e-01\r\n1370 1368 -4.5989498000000e-02\r\n1371 1368 -2.6072693000000e+00\r\n1414 1368  2.6402642000000e+01\r\n1415 1368 -4.0805217000000e+00\r\n1416 1368 -2.6002803000000e+00\r\n2472 1368 -2.6872046000000e+00\r\n265 1369 -9.0841256000000e-02\r\n267 1369 -7.6505808000000e-04\r\n1321 1369 -4.0778265000000e-01\r\n1323 1369 -4.2558043000000e-03\r\n1366 1369 -7.3435877000000e-02\r\n1368 1369 -7.6641004000000e-04\r\n1369 1369  2.7102069000000e+02\r\n1371 1369  1.0247861000000e-02\r\n1372 1369 -8.9236815000000e-02\r\n1374 1369 -9.3131578000000e-04\r\n1417 1369 -2.4653057000000e-01\r\n1419 1369 -8.4683365000000e-04\r\n2473 1369 -1.9183742000000e-01\r\n2475 1369 -2.0021021000000e-03\r\n265 1370  1.7265057000000e+00\r\n267 1370 -1.3827379000000e+00\r\n1323 1370 -1.3792433000000e+00\r\n1368 1370 -1.5423978000000e+00\r\n1369 1370 -1.7309385000000e+02\r\n1370 1370 -5.0435532000000e+01\r\n1371 1370  8.9420690000000e+00\r\n1374 1370 -1.5260234000000e+00\r\n1417 1370  1.6251500000000e+01\r\n1419 1370 -1.5306042000000e+00\r\n2475 1370 -1.5754464000000e+00\r\n265 1371  2.9184835000000e+00\r\n266 1371 -4.4868031000000e-01\r\n267 1371 -2.3373788000000e+00\r\n1323 1371 -2.3314713000000e+00\r\n1368 1371 -2.6072693000000e+00\r\n1369 1371 -2.9259767000000e+02\r\n1370 1371  4.4420332000000e+01\r\n1371 1371  1.5115667000000e+01\r\n1374 1371 -2.5795900000000e+00\r\n1417 1371  2.7471520000000e+01\r\n1418 1371 -4.2234023000000e+00\r\n1419 1371 -2.5873318000000e+00\r\n2475 1371 -2.6631324000000e+00\r\n268 1372 -9.6814191000000e-02\r\n270 1372 -8.3952900000000e-04\r\n1324 1372 -4.0675017000000e-01\r\n1326 1372 -4.2450288000000e-03\r\n1369 1372 -9.3438877000000e-02\r\n1371 1372 -9.3131578000000e-04\r\n1372 1372  2.7107150000000e+02\r\n1374 1372  1.0687625000000e-02\r\n1375 1372 -6.5512219000000e-02\r\n1377 1372 -6.8371516000000e-04\r\n1420 1372 -2.5906107000000e-01\r\n1422 1372 -9.2907918000000e-04\r\n2476 1372 -2.2745387000000e-01\r\n2478 1372 -2.3738115000000e-03\r\n268 1373  1.6122468000000e+00\r\n270 1373 -1.3756968000000e+00\r\n1326 1373 -1.3799393000000e+00\r\n1369 1373  4.1368427000000e-01\r\n1371 1373 -1.5260234000000e+00\r\n1372 1373 -1.7385172000000e+02\r\n1373 1373 -5.0348460000000e+01\r\n1374 1373  8.9215598000000e+00\r\n1377 1373 -1.5502175000000e+00\r\n1420 1373  1.6708277000000e+01\r\n1422 1373 -1.5225090000000e+00\r\n2478 1373 -1.5615681000000e+00\r\n268 1374  2.7253420000000e+00\r\n269 1374 -4.1677580000000e-01\r\n270 1374 -2.3254778000000e+00\r\n1326 1374 -2.3326495000000e+00\r\n1369 1374  6.9929187000000e-01\r\n1370 1374 -1.0693995000000e-01\r\n1371 1374 -2.5795900000000e+00\r\n1372 1374 -2.9387895000000e+02\r\n1373 1374  4.4526891000000e+01\r\n1374 1374  1.5081003000000e+01\r\n1377 1374 -2.6204856000000e+00\r\n1420 1374  2.8243671000000e+01\r\n1421 1374 -4.3191932000000e+00\r\n1422 1374 -2.5736492000000e+00\r\n2478 1374 -2.6396747000000e+00\r\n271 1375 -6.5999328000000e-02\r\n273 1375 -6.1583367000000e-04\r\n1327 1375 -3.1038059000000e-01\r\n1329 1375 -3.2392722000000e-03\r\n1372 1375 -7.5844300000000e-02\r\n1374 1375 -6.8371516000000e-04\r\n1375 1375  2.7077148000000e+02\r\n1377 1375  7.6019344000000e-03\r\n1378 1375 -4.1026695000000e-02\r\n1380 1375 -4.2817315000000e-04\r\n1423 1375 -2.3560074000000e-01\r\n1425 1375 -6.8240063000000e-04\r\n2479 1375 -1.2282236000000e-01\r\n2481 1375 -1.2818297000000e-03\r\n271 1376  1.4359568000000e+00\r\n273 1376 -1.3964088000000e+00\r\n1329 1376 -1.3862673000000e+00\r\n1372 1376  1.0137104000000e+00\r\n1374 1376 -1.5502175000000e+00\r\n1375 1376 -1.7428890000000e+02\r\n1376 1376 -5.0608681000000e+01\r\n1377 1376  9.0132706000000e+00\r\n1380 1376 -1.5252253000000e+00\r\n1423 1376  1.6724953000000e+01\r\n1425 1376 -1.5474048000000e+00\r\n2481 1376 -1.6021115000000e+00\r\n271 1377  2.4273393000000e+00\r\n272 1377 -3.7711731000000e-01\r\n273 1377 -2.3604874000000e+00\r\n1329 1377 -2.3433446000000e+00\r\n1372 1377  1.7135748000000e+00\r\n1373 1377 -2.6622512000000e-01\r\n1374 1377 -2.6204856000000e+00\r\n1375 1377 -2.9461773000000e+02\r\n1376 1377  4.4916084000000e+01\r\n1377 1377  1.5236023000000e+01\r\n1380 1377 -2.5782408000000e+00\r\n1423 1377  2.8271838000000e+01\r\n1424 1377 -4.3923811000000e+00\r\n1425 1377 -2.6157309000000e+00\r\n2481 1377 -2.7082075000000e+00\r\n274 1378 -7.7207549000000e-04\r\n276 1378 -8.0577291000000e-06\r\n1330 1378 -1.7084703000000e-01\r\n1332 1378 -1.7830369000000e-03\r\n1375 1378 -5.8311841000000e-02\r\n1377 1378 -4.2817315000000e-04\r\n1378 1378  2.5425503000000e+02\r\n1380 1378  4.4242257000000e-03\r\n1381 1378 -1.0246567000000e-02\r\n1383 1378 -1.0693781000000e-04\r\n1426 1378 -1.9127099000000e-01\r\n1428 1378 -4.2747906000000e-04\r\n2482 1378 -1.0092811000000e-01\r\n2484 1378 -1.0533314000000e-03\r\n274 1379  1.2813488000000e+00\r\n276 1379 -1.5089297000000e+00\r\n1332 1379 -1.3497327000000e+00\r\n1375 1379  1.6975120000000e+00\r\n1377 1379 -1.5252253000000e+00\r\n1378 1379 -1.6491776000000e+02\r\n1379 1379 -4.7810756000000e+01\r\n1380 1379  9.1070254000000e+00\r\n1383 1379 -1.4596526000000e+00\r\n1426 1379  1.6134038000000e+01\r\n1428 1379 -1.5229139000000e+00\r\n2484 1379 -1.7352467000000e+00\r\n274 1380  2.1659920000000e+00\r\n275 1380 -3.4166937000000e-01\r\n276 1380 -2.5506948000000e+00\r\n1332 1380 -2.2815881000000e+00\r\n1375 1380  2.8694743000000e+00\r\n1376 1380 -4.5263855000000e-01\r\n1377 1380 -2.5782408000000e+00\r\n1378 1380 -2.7877699000000e+02\r\n1379 1380  4.2765198000000e+01\r\n1380 1380  1.5394514000000e+01\r\n1383 1380 -2.4673954000000e+00\r\n1426 1380  2.7272978000000e+01\r\n1427 1380 -4.3021124000000e+00\r\n1428 1380 -2.5743337000000e+00\r\n2484 1380 -2.9332610000000e+00\r\n277 1381 -8.1186756000000e-04\r\n279 1381 -8.4730171000000e-06\r\n1333 1381 -9.0344491000000e-02\r\n1335 1381 -9.4287598000000e-04\r\n1378 1381 -3.4337972000000e-02\r\n1380 1381 -1.0693781000000e-04\r\n1381 1381  2.3782966000000e+02\r\n1383 1381  2.4260529000000e-03\r\n1384 1381 -6.5885284000000e-04\r\n1386 1381 -6.8760863000000e-06\r\n1429 1381 -1.1179913000000e-01\r\n1431 1381 -1.0565836000000e-04\r\n2485 1381 -6.6503128000000e-02\r\n2487 1381 -6.9405673000000e-04\r\n277 1382  1.0325500000000e+00\r\n279 1382 -1.6449913000000e+00\r\n1335 1382 -1.2768153000000e+00\r\n1378 1382  2.3644677000000e+00\r\n1380 1382 -1.4596526000000e+00\r\n1381 1382 -1.5480489000000e+02\r\n1382 1382 -4.5058371000000e+01\r\n1383 1382  9.0804599000000e+00\r\n1386 1382 -1.3549230000000e+00\r\n1429 1382  1.4912651000000e+01\r\n1431 1382 -1.4423564000000e+00\r\n2487 1382 -1.8967026000000e+00\r\n277 1383  1.7454215000000e+00\r\n278 1383 -2.8089742000000e-01\r\n279 1383 -2.7806916000000e+00\r\n1335 1383 -2.1583274000000e+00\r\n1378 1383  3.9968939000000e+00\r\n1379 1383 -6.4323556000000e-01\r\n1380 1383 -2.4673954000000e+00\r\n1381 1383 -2.6168204000000e+02\r\n1382 1383  4.0473282000000e+01\r\n1383 1383  1.5349602000000e+01\r\n1386 1383 -2.2903617000000e+00\r\n1429 1383  2.5208332000000e+01\r\n1430 1383 -4.0568740000000e+00\r\n1431 1383 -2.4381578000000e+00\r\n2487 1383 -3.2061840000000e+00\r\n280 1384 -8.7710119000000e-04\r\n282 1384 -9.1538248000000e-06\r\n1336 1384 -5.2629573000000e-02\r\n1338 1384 -5.4926603000000e-04\r\n1381 1384 -4.4043340000000e-02\r\n1383 1384 -6.8760863000000e-06\r\n1384 1384  2.1612747000000e+02\r\n1386 1384  1.0941948000000e-03\r\n1387 1384 -5.9104318000000e-04\r\n1389 1384 -6.1683940000000e-06\r\n1432 1384 -8.2149322000000e-02\r\n1434 1384 -6.7098090000000e-06\r\n2488 1384 -1.6242420000000e-02\r\n2490 1384 -1.0967924000000e-05\r\n280 1385  8.3364392000000e-01\r\n282 1385 -1.8224369000000e+00\r\n1338 1385 -1.2038403000000e+00\r\n1381 1385  3.0148106000000e+00\r\n1383 1385 -1.3549230000000e+00\r\n1384 1385 -1.4190275000000e+02\r\n1385 1385 -4.1054366000000e+01\r\n1386 1385  9.0787282000000e+00\r\n1389 1385 -1.2428850000000e+00\r\n1432 1385  1.3969117000000e+01\r\n1434 1385 -1.3223121000000e+00\r\n2490 1385 -2.1277579000000e+00\r\n280 1386  1.4091917000000e+00\r\n281 1386 -2.2830455000000e-01\r\n282 1386 -3.0806474000000e+00\r\n1338 1386 -2.0349717000000e+00\r\n1381 1386  5.0962357000000e+00\r\n1382 1386 -8.2564623000000e-01\r\n1383 1386 -2.2903617000000e+00\r\n1384 1386 -2.3987241000000e+02\r\n1385 1386  3.7214192000000e+01\r\n1386 1386  1.5346681000000e+01\r\n1389 1386 -2.1009714000000e+00\r\n1432 1386  2.3613395000000e+01\r\n1433 1386 -3.8256296000000e+00\r\n1434 1386 -2.2352363000000e+00\r\n2490 1386 -3.5967619000000e+00\r\n283 1387 -9.3215578000000e-04\r\n285 1387 -9.7283995000000e-06\r\n1339 1387 -3.1940792000000e-02\r\n1341 1387 -3.3334856000000e-04\r\n1384 1387 -5.8247628000000e-02\r\n1386 1387 -6.1683940000000e-06\r\n1387 1387  1.9996790000000e+02\r\n1389 1387  8.3949727000000e-04\r\n1390 1387 -5.2533485000000e-04\r\n1392 1387 -5.4826322000000e-06\r\n1435 1387 -9.0193798000000e-02\r\n1437 1387 -6.0039162000000e-06\r\n2491 1387 -5.0112401000000e-02\r\n2493 1387 -1.1599637000000e-05\r\n283 1388  7.2120326000000e-01\r\n285 1388 -1.9705921000000e+00\r\n1341 1388 -1.1280965000000e+00\r\n1384 1388  3.9142685000000e+00\r\n1386 1388 -1.2428850000000e+00\r\n1387 1388 -1.3385425000000e+02\r\n1388 1388 -3.7975522000000e+01\r\n1389 1388  9.0385088000000e+00\r\n1392 1388 -1.1456522000000e+00\r\n1435 1388  1.4440091000000e+01\r\n1437 1388 -1.2098873000000e+00\r\n2493 1388 -2.3371655000000e+00\r\n283 1389  1.2191212000000e+00\r\n284 1389 -1.9751333000000e-01\r\n285 1389 -3.3310866000000e+00\r\n1341 1389 -1.9069330000000e+00\r\n1384 1389  6.6166751000000e+00\r\n1385 1389 -1.0719866000000e+00\r\n1386 1389 -2.1009714000000e+00\r\n1387 1389 -2.2626707000000e+02\r\n1388 1389  3.5133565000000e+01\r\n1389 1389  1.5278686000000e+01\r\n1392 1389 -1.9366105000000e+00\r\n1435 1389  2.4409514000000e+01\r\n1436 1389 -3.9546552000000e+00\r\n1437 1389 -2.0451922000000e+00\r\n2493 1389 -3.9507414000000e+00\r\n286 1390 -9.8487380000000e-04\r\n288 1390 -1.0278589000000e-05\r\n1342 1390 -1.0611475000000e-02\r\n1344 1390 -1.1074615000000e-04\r\n1387 1390 -9.3439445000000e-02\r\n1389 1390 -5.4826322000000e-06\r\n1390 1390  1.8369762000000e+02\r\n1392 1390  5.6796279000000e-04\r\n2494 1390 -5.0293461000000e-02\r\n2496 1390 -1.2178326000000e-05\r\n286 1391  7.1032899000000e-01\r\n288 1391 -2.1455762000000e+00\r\n1344 1391 -1.0695946000000e+00\r\n1387 1391  6.9641265000000e+00\r\n1389 1391 -1.1456522000000e+00\r\n1390 1391 -1.1314811000000e+02\r\n1391 1391 -3.4895594000000e+01\r\n1392 1391  6.9094057000000e+00\r\n2496 1391 -2.5446960000000e+00\r\n286 1392  1.2007401000000e+00\r\n287 1392 -1.9453863000000e-01\r\n288 1392 -3.6268820000000e+00\r\n1344 1392 -1.8080426000000e+00\r\n1387 1392  1.1772159000000e+01\r\n1388 1392 -1.9072734000000e+00\r\n1389 1392 -1.9366105000000e+00\r\n1390 1392 -1.9126556000000e+02\r\n1391 1392  2.9589117000000e+01\r\n1392 1392  1.1679659000000e+01\r\n2496 1392 -4.3015541000000e+00\r\n1393 1393  1.0000000000000e+00\r\n1394 1394  1.0000000000000e+00\r\n1395 1395  1.0000000000000e+00\r\n1396 1396  1.0000000000000e+00\r\n1397 1397  1.0000000000000e+00\r\n1398 1398  1.0000000000000e+00\r\n1399 1399  1.0000000000000e+00\r\n1400 1400  1.0000000000000e+00\r\n1401 1401  1.0000000000000e+00\r\n1402 1402  1.0000000000000e+00\r\n1403 1403  1.0000000000000e+00\r\n1404 1404  1.0000000000000e+00\r\n1405 1405  1.0000000000000e+00\r\n1406 1406  1.0000000000000e+00\r\n1407 1407  1.0000000000000e+00\r\n304 1408 -7.4924889000000e-04\r\n306 1408 -7.8195004000000e-06\r\n1360 1408 -3.3844558000000e-02\r\n1362 1408 -3.5321712000000e-04\r\n1408 1408  2.7006466000000e+02\r\n1410 1408  1.0190183000000e-03\r\n1411 1408 -2.3272008000000e-02\r\n1413 1408 -8.6914551000000e-06\r\n1456 1408 -8.1983186000000e-02\r\n1458 1408 -8.6631152000000e-06\r\n2512 1408 -2.6950785000000e-02\r\n2514 1408 -9.2959444000000e-06\r\n304 1409  1.1331974000000e+00\r\n306 1409 -1.4582423000000e+00\r\n1362 1409 -1.5799292000000e+00\r\n1408 1409 -1.7259416000000e+02\r\n1409 1409 -4.7092408000000e+01\r\n1410 1409  7.9812487000000e+00\r\n1411 1409  6.5042611000000e-01\r\n1413 1409 -1.6170433000000e+00\r\n1456 1409  1.5723926000000e+01\r\n1458 1409 -1.6119602000000e+00\r\n2514 1409 -1.7083509000000e+00\r\n304 1410  1.9155568000000e+00\r\n305 1410 -3.1033210000000e-01\r\n306 1410 -2.4650128000000e+00\r\n1362 1410 -2.6707124000000e+00\r\n1408 1410 -2.9175317000000e+02\r\n1409 1410  5.2338123000000e+01\r\n1410 1410  1.3491503000000e+01\r\n1411 1410  1.0994803000000e+00\r\n1412 1410 -1.7812263000000e-01\r\n1413 1410 -2.7334499000000e+00\r\n1456 1410  2.6579724000000e+01\r\n1457 1410 -4.3060803000000e+00\r\n1458 1410 -2.7248575000000e+00\r\n2514 1410 -2.8877963000000e+00\r\n307 1411 -7.5103977000000e-04\r\n309 1411 -7.8381908000000e-06\r\n1363 1411 -4.9607460000000e-02\r\n1365 1411 -5.1772590000000e-04\r\n1408 1411 -8.3279784000000e-04\r\n1410 1411 -8.6914551000000e-06\r\n1411 1411  2.7006462000000e+02\r\n1413 1411  1.1924069000000e-03\r\n1414 1411 -2.5815780000000e-02\r\n1416 1411 -8.7442691000000e-06\r\n1459 1411 -7.8661667000000e-02\r\n1461 1411 -8.7145283000000e-06\r\n2515 1411 -9.3601400000000e-03\r\n2517 1411 -9.3569795000000e-06\r\n307 1412  1.1448642000000e+00\r\n309 1412 -1.4589760000000e+00\r\n1365 1412 -1.5633187000000e+00\r\n1410 1412 -1.6170433000000e+00\r\n1411 1412 -1.7344824000000e+02\r\n1412 1412 -5.1330777000000e+01\r\n1413 1412  9.5657797000000e+00\r\n1414 1412  1.0439707000000e+00\r\n1416 1412 -1.6170724000000e+00\r\n1459 1412  1.6170540000000e+01\r\n1461 1412 -1.6117717000000e+00\r\n2517 1412 -1.6918757000000e+00\r\n307 1413  1.9352772000000e+00\r\n308 1413 -3.1352611000000e-01\r\n309 1413 -2.4662515000000e+00\r\n1365 1413 -2.6426316000000e+00\r\n1410 1413 -2.7334499000000e+00\r\n1411 1413 -2.9319672000000e+02\r\n1412 1413  4.5408629000000e+01\r\n1413 1413  1.6169985000000e+01\r\n1414 1413  1.7647269000000e+00\r\n1415 1413 -2.8589598000000e-01\r\n1416 1413 -2.7334974000000e+00\r\n1459 1413  2.7334664000000e+01\r\n1460 1413 -4.4283740000000e+00\r\n1461 1413 -2.7245372000000e+00\r\n2517 1413 -2.8599448000000e+00\r\n310 1414 -7.5361219000000e-04\r\n312 1414 -7.8650378000000e-06\r\n1366 1414 -7.3231142000000e-02\r\n1368 1414 -7.6427333000000e-04\r\n1411 1414 -8.3785838000000e-04\r\n1413 1414 -8.7442691000000e-06\r\n1414 1414  2.7012596000000e+02\r\n1416 1414  2.0389723000000e-03\r\n1417 1414 -1.0518080000000e-02\r\n1419 1414 -2.4119375000000e-05\r\n1462 1414 -8.4096921000000e-02\r\n1464 1414 -2.4033219000000e-05\r\n2518 1414 -5.5354421000000e-02\r\n2520 1414 -5.7770378000000e-04\r\n310 1415  1.1600652000000e+00\r\n312 1415 -1.4583174000000e+00\r\n1368 1415 -1.5382633000000e+00\r\n1413 1415 -1.6170724000000e+00\r\n1414 1415 -1.7424625000000e+02\r\n1415 1415 -5.1313295000000e+01\r\n1416 1415  9.5203559000000e+00\r\n1417 1415  8.0556735000000e-01\r\n1419 1415 -1.6156055000000e+00\r\n1462 1415  1.7189845000000e+01\r\n1464 1415 -1.6100400000000e+00\r\n2520 1415 -1.6753377000000e+00\r\n310 1416  1.9609742000000e+00\r\n311 1416 -3.1739229000000e-01\r\n312 1416 -2.4651397000000e+00\r\n1368 1416 -2.6002803000000e+00\r\n1413 1416 -2.7334974000000e+00\r\n1414 1416 -2.9454586000000e+02\r\n1415 1416  4.5613128000000e+01\r\n1416 1416  1.6093208000000e+01\r\n1417 1416  1.3617310000000e+00\r\n1418 1416 -2.2040215000000e-01\r\n1419 1416 -2.7310196000000e+00\r\n1462 1416  2.9057715000000e+01\r\n1463 1416 -4.7031187000000e+00\r\n1464 1416 -2.7216116000000e+00\r\n2520 1416 -2.8319909000000e+00\r\n313 1417 -7.5594456000000e-04\r\n315 1417 -7.8893794000000e-06\r\n1369 1417 -8.1141907000000e-02\r\n1371 1417 -8.4683365000000e-04\r\n1414 1417 -2.3110703000000e-03\r\n1416 1417 -2.4119375000000e-05\r\n1417 1417  2.7017949000000e+02\r\n1419 1417  2.3944515000000e-03\r\n1420 1417 -1.0675461000000e-02\r\n1422 1417 -1.0662713000000e-04\r\n1465 1417 -1.1909565000000e-01\r\n1467 1417 -1.0624358000000e-04\r\n2521 1417 -6.3785526000000e-02\r\n2523 1417 -6.6569460000000e-04\r\n313 1418  1.1939511000000e+00\r\n315 1418 -1.4501622000000e+00\r\n1371 1418 -1.5306042000000e+00\r\n1416 1418 -1.6156055000000e+00\r\n1417 1418 -1.7463575000000e+02\r\n1418 1418 -5.1226801000000e+01\r\n1419 1418  9.4771723000000e+00\r\n1420 1418  4.4261743000000e-02\r\n1422 1418 -1.6074876000000e+00\r\n1465 1418  1.8305960000000e+01\r\n1467 1418 -1.6019100000000e+00\r\n2523 1418 -1.6656929000000e+00\r\n313 1419  2.0182535000000e+00\r\n314 1419 -3.2502469000000e-01\r\n315 1419 -2.4513525000000e+00\r\n1371 1419 -2.5873318000000e+00\r\n1416 1419 -2.7310196000000e+00\r\n1417 1419 -2.9520408000000e+02\r\n1418 1419  4.5626707000000e+01\r\n1419 1419  1.6020203000000e+01\r\n1420 1419  7.4820002000000e-02\r\n1421 1419 -1.2049203000000e-02\r\n1422 1419 -2.7172951000000e+00\r\n1465 1419  3.0944375000000e+01\r\n1466 1419 -4.9833605000000e+00\r\n1467 1419 -2.7078668000000e+00\r\n2523 1419 -2.8156854000000e+00\r\n316 1420 -7.5745833000000e-04\r\n318 1420 -7.9051779000000e-06\r\n1372 1420 -8.9022509000000e-02\r\n1374 1420 -9.2907918000000e-04\r\n1417 1420 -1.0216799000000e-02\r\n1419 1420 -1.0662713000000e-04\r\n1420 1420  2.7022719000000e+02\r\n1422 1420  2.7344592000000e-03\r\n1423 1420 -1.0210680000000e-02\r\n1425 1420 -1.0656327000000e-04\r\n1468 1420 -1.4191900000000e-01\r\n1470 1420 -1.8843431000000e-04\r\n2524 1420 -7.2246429000000e-02\r\n2526 1420 -7.5399642000000e-04\r\n316 1421  1.1859610000000e+00\r\n318 1421 -1.4428372000000e+00\r\n1374 1421 -1.5225090000000e+00\r\n1419 1421 -1.6074876000000e+00\r\n1420 1421 -1.7527966000000e+02\r\n1421 1421 -5.1139888000000e+01\r\n1422 1421  9.4366858000000e+00\r\n1425 1421 -1.6073277000000e+00\r\n1468 1421  1.9000849000000e+01\r\n1470 1421 -1.5938227000000e+00\r\n2526 1421 -1.6570018000000e+00\r\n316 1422  2.0047484000000e+00\r\n317 1422 -3.2122225000000e-01\r\n318 1422 -2.4389721000000e+00\r\n1374 1422 -2.5736492000000e+00\r\n1419 1422 -2.7172951000000e+00\r\n1420 1422 -2.9629274000000e+02\r\n1421 1422  4.5709042000000e+01\r\n1422 1422  1.5951770000000e+01\r\n1425 1422 -2.7170249000000e+00\r\n1468 1422  3.2119036000000e+01\r\n1469 1422 -5.1464557000000e+00\r\n1470 1422 -2.6941978000000e+00\r\n2526 1422 -2.8009959000000e+00\r\n319 1423 -7.5306130000000e-04\r\n321 1423 -7.8592885000000e-06\r\n1375 1423 -6.5386264000000e-02\r\n1377 1423 -6.8240063000000e-04\r\n1420 1423 -2.0434374000000e-02\r\n1422 1423 -1.0656327000000e-04\r\n1423 1423  2.7017970000000e+02\r\n1425 1423  2.2144193000000e-03\r\n1426 1423 -8.3475666000000e-04\r\n1428 1423 -8.7118981000000e-06\r\n1471 1423 -1.2621266000000e-01\r\n1473 1423 -1.0619059000000e-04\r\n2527 1423 -6.3781487000000e-02\r\n2529 1423 -6.6565245000000e-04\r\n319 1424  1.1138329000000e+00\r\n321 1424 -1.4504481000000e+00\r\n1377 1424 -1.5474048000000e+00\r\n1420 1424  1.0039705000000e+00\r\n1422 1424 -1.6073277000000e+00\r\n1423 1424 -1.7621607000000e+02\r\n1424 1424 -5.1226311000000e+01\r\n1425 1424  9.4953093000000e+00\r\n1428 1424 -1.6164755000000e+00\r\n1471 1424  1.9005981000000e+01\r\n1473 1424 -1.6019098000000e+00\r\n2529 1424 -1.6660338000000e+00\r\n319 1425  1.8828219000000e+00\r\n320 1425 -3.0321541000000e-01\r\n321 1425 -2.4518359000000e+00\r\n1377 1425 -2.6157309000000e+00\r\n1420 1425  1.6971106000000e+00\r\n1421 1425 -2.7330792000000e-01\r\n1422 1425 -2.7170249000000e+00\r\n1423 1425 -2.9787545000000e+02\r\n1424 1425  4.6058279000000e+01\r\n1425 1425  1.6050862000000e+01\r\n1428 1425 -2.7324901000000e+00\r\n1471 1425  3.2127690000000e+01\r\n1472 1425 -5.1739417000000e+00\r\n1473 1425 -2.7078666000000e+00\r\n2529 1425 -2.8162617000000e+00\r\n322 1426 -7.4869979000000e-04\r\n324 1426 -7.8137698000000e-06\r\n1378 1426 -4.0960189000000e-02\r\n1380 1426 -4.2747906000000e-04\r\n1423 1426 -3.3836202000000e-02\r\n1425 1426 -8.7118981000000e-06\r\n1426 1426  2.7009668000000e+02\r\n1428 1426  1.1015790000000e-03\r\n1429 1426 -7.8804909000000e-04\r\n1431 1426 -8.2244368000000e-06\r\n1474 1426 -1.0977257000000e-01\r\n1476 1426 -8.6890117000000e-06\r\n2530 1426 -1.0376518000000e-02\r\n2532 1426 -9.3263373000000e-06\r\n322 1427  1.0105250000000e+00\r\n324 1427 -1.4587762000000e+00\r\n1380 1427 -1.5229139000000e+00\r\n1423 1427  1.8318018000000e+00\r\n1425 1427 -1.6164755000000e+00\r\n1426 1427 -1.7638804000000e+02\r\n1427 1427 -5.1330268000000e+01\r\n1428 1427  9.4573617000000e+00\r\n1431 1427 -1.5490538000000e+00\r\n1474 1427  1.8456170000000e+01\r\n1476 1427 -1.6124359000000e+00\r\n2532 1427 -1.6919846000000e+00\r\n322 1428  1.7081915000000e+00\r\n323 1428 -2.7673724000000e-01\r\n324 1428 -2.4659153000000e+00\r\n1380 1428 -2.5743337000000e+00\r\n1423 1428  3.0964777000000e+00\r\n1424 1428 -5.0164789000000e-01\r\n1425 1428 -2.7324901000000e+00\r\n1426 1428 -2.9816634000000e+02\r\n1427 1428  4.6214953000000e+01\r\n1428 1428  1.5986723000000e+01\r\n1431 1428 -2.6185188000000e+00\r\n1474 1428  3.1198310000000e+01\r\n1475 1428 -5.0543129000000e+00\r\n1476 1428 -2.7256617000000e+00\r\n2532 1428 -2.8601308000000e+00\r\n325 1429 -8.0683750000000e-04\r\n327 1429 -8.4205212000000e-06\r\n1381 1429 -1.0123973000000e-02\r\n1383 1429 -1.0565836000000e-04\r\n1426 1429 -6.6563982000000e-02\r\n1428 1429 -8.2244368000000e-06\r\n1429 1429  2.4853926000000e+02\r\n1431 1429  7.2852564000000e-04\r\n1432 1429 -7.1484597000000e-04\r\n1434 1429 -7.4604560000000e-06\r\n1477 1429 -1.0755802000000e-01\r\n1479 1429 -7.9657624000000e-06\r\n2533 1429 -4.9089751000000e-02\r\n2535 1429 -9.9785368000000e-06\r\n325 1430  9.5135559000000e-01\r\n327 1430 -1.5845640000000e+00\r\n1383 1430 -1.4423564000000e+00\r\n1426 1430  2.5614310000000e+00\r\n1428 1430 -1.5490538000000e+00\r\n1429 1430 -1.6295395000000e+02\r\n1430 1430 -4.7227537000000e+01\r\n1431 1430  9.3810030000000e+00\r\n1434 1430 -1.4198346000000e+00\r\n1477 1430  1.6763446000000e+01\r\n1479 1430 -1.5005276000000e+00\r\n2535 1430 -1.8794010000000e+00\r\n325 1431  1.6081704000000e+00\r\n326 1431 -2.6053543000000e-01\r\n327 1431 -2.6785451000000e+00\r\n1383 1431 -2.4381578000000e+00\r\n1426 1431  4.3298401000000e+00\r\n1427 1431 -7.0146590000000e-01\r\n1428 1431 -2.6185188000000e+00\r\n1429 1431 -2.7545719000000e+02\r\n1430 1431  4.2694757000000e+01\r\n1431 1431  1.5857638000000e+01\r\n1434 1431 -2.4000884000000e+00\r\n1477 1431  2.8336913000000e+01\r\n1478 1431 -4.5907875000000e+00\r\n1479 1431 -2.5364900000000e+00\r\n2535 1431 -3.1769365000000e+00\r\n328 1432 -8.7588529000000e-04\r\n330 1432 -9.1411352000000e-06\r\n1384 1432 -6.4292048000000e-04\r\n1386 1432 -6.7098090000000e-06\r\n1429 1432 -5.8069268000000e-02\r\n1431 1432 -7.4604560000000e-06\r\n1432 1432  2.2691115000000e+02\r\n1434 1432  5.7844776000000e-04\r\n1435 1432 -6.4440876000000e-04\r\n1437 1432 -6.7253413000000e-06\r\n1480 1432 -9.0980477000000e-02\r\n1482 1432 -7.2877828000000e-06\r\n2536 1432 -4.9472007000000e-02\r\n2538 1432 -1.0817669000000e-05\r\n328 1433  8.7183274000000e-01\r\n330 1433 -1.7360007000000e+00\r\n1386 1433 -1.3223121000000e+00\r\n1429 1433  2.7416608000000e+00\r\n1431 1433 -1.4198346000000e+00\r\n1432 1433 -1.4900934000000e+02\r\n1433 1433 -4.3123039000000e+01\r\n1434 1433  9.2191644000000e+00\r\n1437 1433 -1.2903395000000e+00\r\n1480 1433  1.5127805000000e+01\r\n1482 1433 -1.3871457000000e+00\r\n2538 1433 -2.0587232000000e+00\r\n328 1434  1.4737461000000e+00\r\n329 1434 -2.3875883000000e-01\r\n330 1434 -2.9345355000000e+00\r\n1386 1434 -2.2352363000000e+00\r\n1429 1434  4.6345034000000e+00\r\n1430 1434 -7.5082716000000e-01\r\n1431 1434 -2.4000884000000e+00\r\n1432 1434 -2.5188539000000e+02\r\n1433 1434  3.9038658000000e+01\r\n1434 1434  1.5584074000000e+01\r\n1437 1434 -2.1811882000000e+00\r\n1480 1434  2.5572042000000e+01\r\n1481 1434 -4.1428785000000e+00\r\n1482 1434 -2.3448311000000e+00\r\n2538 1434 -3.4800657000000e+00\r\n331 1435 -9.5981471000000e-04\r\n333 1435 -1.0017061000000e-05\r\n1387 1435 -5.7528325000000e-04\r\n1389 1435 -6.0039162000000e-06\r\n1432 1435 -4.4446802000000e-02\r\n1434 1435 -6.7253413000000e-06\r\n1435 1435  2.0529453000000e+02\r\n1437 1435  5.2095283000000e-04\r\n1483 1435 -8.1520667000000e-02\r\n1485 1435 -6.5501878000000e-06\r\n2539 1435 -4.9415207000000e-02\r\n2541 1435 -1.1860249000000e-05\r\n331 1436  8.2470459000000e-01\r\n333 1436 -1.9187718000000e+00\r\n1389 1436 -1.2098873000000e+00\r\n1432 1436  2.2942588000000e+00\r\n1434 1436 -1.2903395000000e+00\r\n1435 1436 -1.3459675000000e+02\r\n1436 1436 -3.9017438000000e+01\r\n1437 1436  7.9557264000000e+00\r\n1483 1436  1.3617892000000e+01\r\n1485 1436 -1.2568843000000e+00\r\n2541 1436 -2.2754922000000e+00\r\n331 1437  1.3940796000000e+00\r\n332 1437 -2.2585332000000e-01\r\n333 1437 -3.2434895000000e+00\r\n1389 1437 -2.0451922000000e+00\r\n1432 1437  3.8782123000000e+00\r\n1433 1437 -6.2830496000000e-01\r\n1434 1437 -2.1811882000000e+00\r\n1435 1437 -2.2752218000000e+02\r\n1436 1437  3.5257103000000e+01\r\n1437 1437  1.3448350000000e+01\r\n1483 1437  2.3019668000000e+01\r\n1484 1437 -3.7293910000000e+00\r\n1485 1437 -2.1246357000000e+00\r\n2541 1437 -3.8464892000000e+00\r\n1438 1438  1.0000000000000e+00\r\n1439 1439  1.0000000000000e+00\r\n1440 1440  1.0000000000000e+00\r\n1441 1441  1.0000000000000e+00\r\n1442 1442  1.0000000000000e+00\r\n1443 1443  1.0000000000000e+00\r\n1444 1444  1.0000000000000e+00\r\n1445 1445  1.0000000000000e+00\r\n1446 1446  1.0000000000000e+00\r\n1447 1447  1.0000000000000e+00\r\n1448 1448  1.0000000000000e+00\r\n1449 1449  1.0000000000000e+00\r\n1450 1450  1.0000000000000e+00\r\n1451 1451  1.0000000000000e+00\r\n1452 1452  1.0000000000000e+00\r\n1453 1453  1.0000000000000e+00\r\n1454 1454  1.0000000000000e+00\r\n1455 1455  1.0000000000000e+00\r\n352 1456 -7.8247898000000e-04\r\n354 1456 -8.1663047000000e-06\r\n1408 1456 -8.3008238000000e-04\r\n1410 1456 -8.6631152000000e-06\r\n1456 1456  2.7001834000000e+02\r\n1458 1456  6.7542648000000e-04\r\n1459 1456 -1.9974614000000e-02\r\n1461 1456 -9.0183575000000e-06\r\n1504 1456 -7.0525855000000e-02\r\n1506 1456 -8.5828473000000e-06\r\n2560 1456 -4.8509484000000e-02\r\n2562 1456 -9.6623255000000e-06\r\n352 1457  1.0519100000000e+00\r\n354 1457 -1.4603618000000e+00\r\n1410 1457 -1.6119602000000e+00\r\n1456 1457 -1.7386680000000e+02\r\n1457 1457 -4.7111932000000e+01\r\n1458 1457  7.9679799000000e+00\r\n1459 1457  1.1004158000000e+00\r\n1461 1457 -1.6174652000000e+00\r\n1504 1457  1.6653300000000e+01\r\n1506 1457 -1.5395618000000e+00\r\n2562 1457 -1.7328999000000e+00\r\n352 1458  1.7781486000000e+00\r\n353 1458 -2.8806540000000e-01\r\n354 1458 -2.4685955000000e+00\r\n1410 1458 -2.7248575000000e+00\r\n1456 1458 -2.9390444000000e+02\r\n1457 1458  5.2638811000000e+01\r\n1458 1458  1.3469073000000e+01\r\n1459 1458  1.8601429000000e+00\r\n1460 1458 -3.0134873000000e-01\r\n1461 1458 -2.7341631000000e+00\r\n1504 1458  2.8150739000000e+01\r\n1505 1458 -4.5605041000000e+00\r\n1506 1458 -2.6024753000000e+00\r\n2562 1458 -2.9292939000000e+00\r\n355 1459 -7.8482076000000e-04\r\n357 1459 -8.1907446000000e-06\r\n1411 1459 -8.3500867000000e-04\r\n1413 1459 -8.7145283000000e-06\r\n1456 1459 -8.6412098000000e-04\r\n1458 1459 -9.0183575000000e-06\r\n1459 1459  2.7003674000000e+02\r\n1461 1459  6.8480065000000e-04\r\n1462 1459 -2.9835450000000e-02\r\n1464 1459 -9.0455668000000e-06\r\n1507 1459 -7.8257894000000e-02\r\n1509 1459 -8.8081726000000e-06\r\n2563 1459 -4.8060852000000e-02\r\n2565 1459 -9.6879349000000e-06\r\n355 1460  1.1450184000000e+00\r\n357 1460 -1.4601662000000e+00\r\n1413 1460 -1.6117717000000e+00\r\n1458 1460 -1.6174652000000e+00\r\n1459 1460 -1.7544405000000e+02\r\n1460 1460 -5.1350908000000e+01\r\n1461 1460  9.6198756000000e+00\r\n1462 1460  2.0692633000000e+00\r\n1464 1460 -1.6173997000000e+00\r\n1507 1460  1.7168040000000e+01\r\n1509 1460 -1.5751537000000e+00\r\n2565 1460 -1.7321883000000e+00\r\n355 1461  1.9355381000000e+00\r\n356 1461 -3.1356263000000e-01\r\n357 1461 -2.4682635000000e+00\r\n1413 1461 -2.7245372000000e+00\r\n1458 1461 -2.7341631000000e+00\r\n1459 1461 -2.9657046000000e+02\r\n1460 1461  4.5905440000000e+01\r\n1461 1461  1.6261429000000e+01\r\n1462 1461  3.4978806000000e+00\r\n1463 1461 -5.6666650000000e-01\r\n1464 1461 -2.7340508000000e+00\r\n1507 1461  2.9020837000000e+01\r\n1508 1461 -4.7014575000000e+00\r\n1509 1461 -2.6626383000000e+00\r\n2565 1461 -2.9280891000000e+00\r\n358 1462 -7.8940871000000e-04\r\n360 1462 -8.2386264000000e-06\r\n1414 1462 -2.3028150000000e-03\r\n1416 1462 -2.4033219000000e-05\r\n1459 1462 -8.6672812000000e-04\r\n1461 1462 -9.0455668000000e-06\r\n1462 1462  2.7006740000000e+02\r\n1464 1462  7.0053882000000e-04\r\n1465 1462 -3.6297248000000e-02\r\n1467 1462 -9.0947386000000e-06\r\n1510 1462 -1.0191037000000e-01\r\n1512 1462 -9.0508544000000e-06\r\n2566 1462 -4.7232910000000e-02\r\n2568 1462 -9.7375877000000e-06\r\n358 1463  1.2957864000000e+00\r\n360 1463 -1.4600938000000e+00\r\n1416 1463 -1.6100400000000e+00\r\n1461 1463 -1.6173997000000e+00\r\n1462 1463 -1.7750451000000e+02\r\n1463 1463 -5.1350998000000e+01\r\n1464 1463  9.6521019000000e+00\r\n1465 1463  1.9262750000000e+00\r\n1467 1463 -1.6173879000000e+00\r\n1510 1463  1.9220924000000e+01\r\n1512 1463 -1.6098024000000e+00\r\n2568 1463 -1.7316471000000e+00\r\n358 1464  2.1903974000000e+00\r\n359 1464 -3.5484929000000e-01\r\n360 1464 -2.4681426000000e+00\r\n1416 1464 -2.7216116000000e+00\r\n1461 1464 -2.7340508000000e+00\r\n1462 1464 -3.0005362000000e+02\r\n1463 1464  4.6469243000000e+01\r\n1464 1464  1.6315911000000e+01\r\n1465 1464  3.2561752000000e+00\r\n1466 1464 -5.2750769000000e-01\r\n1467 1464 -2.7340325000000e+00\r\n1510 1464  3.2491049000000e+01\r\n1511 1464 -5.2636228000000e+00\r\n1512 1464 -2.7212100000000e+00\r\n2568 1464 -2.9271763000000e+00\r\n361 1465 -7.9420309000000e-04\r\n363 1465 -8.2886627000000e-06\r\n1417 1465 -1.0180047000000e-02\r\n1419 1465 -1.0624358000000e-04\r\n1462 1465 -8.7143967000000e-04\r\n1464 1465 -9.0947386000000e-06\r\n1465 1465  2.7006765000000e+02\r\n1467 1465  7.8304509000000e-04\r\n1468 1465 -1.6336949000000e-02\r\n1470 1465 -9.1531613000000e-06\r\n1513 1465 -1.1435344000000e-01\r\n1515 1465 -9.1176109000000e-06\r\n2569 1465 -4.6196229000000e-02\r\n2571 1465 -9.8051430000000e-06\r\n361 1466  1.4523774000000e+00\r\n363 1466 -1.4608747000000e+00\r\n1419 1466 -1.6019100000000e+00\r\n1464 1466 -1.6173879000000e+00\r\n1465 1466 -1.7848422000000e+02\r\n1466 1466 -5.1349972000000e+01\r\n1467 1466  9.6472855000000e+00\r\n1468 1466  7.4175981000000e-01\r\n1470 1466 -1.6174298000000e+00\r\n1513 1466  2.1227252000000e+01\r\n1515 1466 -1.6113827000000e+00\r\n2571 1466 -1.7325699000000e+00\r\n361 1467  2.4550965000000e+00\r\n362 1467 -3.9773011000000e-01\r\n363 1467 -2.4694602000000e+00\r\n1419 1467 -2.7078668000000e+00\r\n1464 1467 -2.7340325000000e+00\r\n1465 1467 -3.0170946000000e+02\r\n1466 1467  4.6739878000000e+01\r\n1467 1467  1.6307760000000e+01\r\n1468 1467  1.2538697000000e+00\r\n1469 1467 -2.0312916000000e-01\r\n1470 1467 -2.7341007000000e+00\r\n1513 1467  3.5882516000000e+01\r\n1514 1467 -5.8130322000000e+00\r\n1515 1467 -2.7238788000000e+00\r\n2571 1467 -2.9287341000000e+00\r\n364 1468 -7.9591745000000e-04\r\n366 1468 -8.3065546000000e-06\r\n1420 1468 -1.8055398000000e-02\r\n1422 1468 -1.8843431000000e-04\r\n1465 1468 -8.7703761000000e-04\r\n1467 1468 -9.1531613000000e-06\r\n1468 1468  2.7007190000000e+02\r\n1470 1468  8.6537164000000e-04\r\n1471 1468 -8.7636085000000e-04\r\n1473 1468 -9.1460984000000e-06\r\n1516 1468 -1.2596991000000e-01\r\n1518 1468 -9.1484399000000e-06\r\n2572 1468 -4.5679259000000e-02\r\n2574 1468 -9.8382960000000e-06\r\n364 1469  1.5262413000000e+00\r\n366 1469 -1.4608630000000e+00\r\n1422 1469 -1.5938227000000e+00\r\n1467 1469 -1.6174298000000e+00\r\n1468 1469 -1.7895839000000e+02\r\n1469 1469 -5.1349336000000e+01\r\n1470 1469  9.6391433000000e+00\r\n1473 1469 -1.6173685000000e+00\r\n1516 1469  2.2368532000000e+01\r\n1518 1469 -1.6113755000000e+00\r\n2574 1469 -1.7325536000000e+00\r\n364 1470  2.5799584000000e+00\r\n365 1470 -4.1795678000000e-01\r\n366 1470 -2.4694428000000e+00\r\n1422 1470 -2.6941978000000e+00\r\n1467 1470 -2.7341007000000e+00\r\n1468 1470 -3.0251126000000e+02\r\n1469 1470  4.6871070000000e+01\r\n1470 1470  1.6294003000000e+01\r\n1473 1470 -2.7339979000000e+00\r\n1516 1470  3.7811766000000e+01\r\n1517 1470 -6.1255577000000e+00\r\n1518 1470 -2.7238692000000e+00\r\n2574 1470 -2.9287086000000e+00\r\n367 1471 -7.9366279000000e-04\r\n369 1471 -8.2830240000000e-06\r\n1423 1471 -1.0174970000000e-02\r\n1425 1471 -1.0619059000000e-04\r\n1468 1471 -1.8953762000000e-02\r\n1470 1471 -9.1460984000000e-06\r\n1471 1471  2.7007945000000e+02\r\n1473 1471  7.8294893000000e-04\r\n1474 1471 -8.6954137000000e-04\r\n1476 1471 -9.0749271000000e-06\r\n1519 1471 -1.2342382000000e-01\r\n1521 1471 -9.1135260000000e-06\r\n2575 1471 -4.6118381000000e-02\r\n2577 1471 -9.7986799000000e-06\r\n367 1472  1.4663627000000e+00\r\n369 1472 -1.4609828000000e+00\r\n1425 1472 -1.6019098000000e+00\r\n1468 1472  9.9902844000000e-01\r\n1470 1472 -1.6173685000000e+00\r\n1471 1472 -1.7965018000000e+02\r\n1472 1472 -5.1349843000000e+01\r\n1473 1472  9.6476569000000e+00\r\n1476 1472 -1.6171212000000e+00\r\n1519 1472  2.2121760000000e+01\r\n1521 1472 -1.6118470000000e+00\r\n2577 1472 -1.7326971000000e+00\r\n367 1473  2.4787378000000e+00\r\n368 1473 -4.0156009000000e-01\r\n369 1473 -2.4696437000000e+00\r\n1425 1473 -2.7078666000000e+00\r\n1468 1473  1.6887565000000e+00\r\n1469 1473 -2.7358167000000e-01\r\n1470 1473 -2.7339979000000e+00\r\n1471 1473 -3.0368046000000e+02\r\n1472 1473  4.7059527000000e+01\r\n1473 1473  1.6308390000000e+01\r\n1476 1473 -2.7335816000000e+00\r\n1519 1473  3.7394598000000e+01\r\n1520 1473 -6.0579939000000e+00\r\n1521 1473 -2.7246643000000e+00\r\n2577 1473 -2.9289491000000e+00\r\n370 1474 -7.8813993000000e-04\r\n372 1474 -8.2253849000000e-06\r\n1426 1474 -8.3256372000000e-04\r\n1428 1474 -8.6890117000000e-06\r\n1471 1474 -4.1060224000000e-02\r\n1473 1474 -9.0749271000000e-06\r\n1474 1474  2.7008865000000e+02\r\n1476 1474  6.8481087000000e-04\r\n1477 1474 -8.3543184000000e-04\r\n1479 1474 -8.7189446000000e-06\r\n1522 1474 -1.1984362000000e-01\r\n1524 1474 -9.0443172000000e-06\r\n2578 1474 -4.6864971000000e-02\r\n2580 1474 -9.7207651000000e-06\r\n370 1475  1.3171960000000e+00\r\n372 1475 -1.4603466000000e+00\r\n1428 1475 -1.6124359000000e+00\r\n1471 1475  2.3948027000000e+00\r\n1473 1475 -1.6171212000000e+00\r\n1474 1475 -1.7976978000000e+02\r\n1475 1475 -5.1350607000000e+01\r\n1476 1475  9.6064392000000e+00\r\n1479 1475 -1.5667697000000e+00\r\n1522 1475  2.0995709000000e+01\r\n1524 1475 -1.6118921000000e+00\r\n2580 1475 -1.7321429000000e+00\r\n370 1476  2.2265881000000e+00\r\n371 1476 -3.6071267000000e-01\r\n372 1476 -2.4685699000000e+00\r\n1428 1476 -2.7256617000000e+00\r\n1471 1476  4.0481744000000e+00\r\n1472 1476 -6.5581405000000e-01\r\n1473 1476 -2.7335816000000e+00\r\n1474 1476 -3.0388283000000e+02\r\n1475 1476  4.7090596000000e+01\r\n1476 1476  1.6238723000000e+01\r\n1479 1476 -2.6484659000000e+00\r\n1522 1476  3.5491147000000e+01\r\n1523 1476 -5.7496518000000e+00\r\n1524 1476 -2.7247424000000e+00\r\n2580 1476 -2.9280144000000e+00\r\n373 1477 -8.3063190000000e-04\r\n375 1477 -8.6688503000000e-06\r\n1429 1477 -7.6326343000000e-04\r\n1431 1477 -7.9657624000000e-06\r\n1474 1477 -6.1690204000000e-02\r\n1476 1477 -8.7189446000000e-06\r\n1477 1477  2.5390840000000e+02\r\n1479 1477  6.4576394000000e-04\r\n1480 1477 -7.7640669000000e-04\r\n1482 1477 -8.1029315000000e-06\r\n1525 1477 -1.1373980000000e-01\r\n1527 1477 -8.6082212000000e-06\r\n2581 1477 -4.7159864000000e-02\r\n2583 1477 -1.0248069000000e-05\r\n373 1478  1.1837465000000e+00\r\n375 1478 -1.5528349000000e+00\r\n1431 1478 -1.5005276000000e+00\r\n1474 1478  3.0200314000000e+00\r\n1476 1478 -1.5667697000000e+00\r\n1477 1478 -1.6878018000000e+02\r\n1478 1478 -4.8271778000000e+01\r\n1479 1478  9.4839287000000e+00\r\n1482 1478 -1.4698187000000e+00\r\n1525 1478  1.8820856000000e+01\r\n1527 1478 -1.5470819000000e+00\r\n2583 1478 -1.8415082000000e+00\r\n373 1479  2.0010037000000e+00\r\n374 1479 -3.2416910000000e-01\r\n375 1479 -2.6249103000000e+00\r\n1431 1479 -2.5364900000000e+00\r\n1474 1479  5.1050579000000e+00\r\n1475 1479 -8.2703595000000e-01\r\n1476 1479 -2.6484659000000e+00\r\n1477 1479 -2.8530584000000e+02\r\n1478 1479  4.4204439000000e+01\r\n1479 1479  1.6031624000000e+01\r\n1482 1479 -2.4845815000000e+00\r\n1525 1479  3.1814754000000e+01\r\n1526 1479 -5.1540934000000e+00\r\n1527 1479 -2.6151855000000e+00\r\n2583 1479 -3.1128835000000e+00\r\n376 1480 -8.7771886000000e-04\r\n378 1480 -9.1602712000000e-06\r\n1432 1480 -6.9830077000000e-04\r\n1434 1480 -7.2877828000000e-06\r\n1477 1480 -6.9078878000000e-02\r\n1479 1480 -8.1029315000000e-06\r\n1480 1480  2.3770616000000e+02\r\n1482 1480  6.0635441000000e-04\r\n1483 1480 -7.1017836000000e-04\r\n1485 1480 -7.4117426000000e-06\r\n1528 1480 -9.8724622000000e-02\r\n1530 1480 -7.9912181000000e-06\r\n2584 1480 -4.7971359000000e-02\r\n2586 1480 -1.0835706000000e-05\r\n376 1481  1.0382496000000e+00\r\n378 1481 -1.6573901000000e+00\r\n1434 1481 -1.3871457000000e+00\r\n1477 1481  3.2285571000000e+00\r\n1479 1481 -1.4698187000000e+00\r\n1480 1481 -1.5688330000000e+02\r\n1481 1481 -4.5193359000000e+01\r\n1482 1481  9.2900489000000e+00\r\n1485 1481 -1.3554128000000e+00\r\n1528 1481  1.6168101000000e+01\r\n1530 1481 -1.4497408000000e+00\r\n2586 1481 -1.9654957000000e+00\r\n376 1482  1.7550571000000e+00\r\n377 1482 -2.8432625000000e-01\r\n378 1482 -2.8016522000000e+00\r\n1434 1482 -2.3448311000000e+00\r\n1477 1482  5.4575529000000e+00\r\n1478 1482 -8.8414531000000e-01\r\n1479 1482 -2.4845815000000e+00\r\n1480 1482 -2.6519553000000e+02\r\n1481 1482  4.1068716000000e+01\r\n1482 1482  1.5703897000000e+01\r\n1485 1482 -2.2911882000000e+00\r\n1528 1482  2.7330557000000e+01\r\n1529 1482 -4.4276594000000e+00\r\n1530 1482 -2.4506419000000e+00\r\n2586 1482 -3.3224740000000e+00\r\n379 1483 -9.5919609000000e-04\r\n381 1483 -1.0010604000000e-05\r\n1435 1483 -6.2762590000000e-04\r\n1437 1483 -6.5501878000000e-06\r\n1480 1483 -4.7692092000000e-02\r\n1482 1483 -7.4117426000000e-06\r\n1483 1483  2.1604354000000e+02\r\n1485 1483  5.4800677000000e-04\r\n1531 1483 -4.8856002000000e-02\r\n1533 1483 -7.1352826000000e-06\r\n2587 1483 -4.8565204000000e-02\r\n2589 1483 -1.1844695000000e-05\r\n379 1484  9.5949762000000e-01\r\n381 1484 -1.8263584000000e+00\r\n1437 1484 -1.2568843000000e+00\r\n1480 1484  2.5058817000000e+00\r\n1482 1484 -1.3554128000000e+00\r\n1483 1484 -1.4020691000000e+02\r\n1484 1484 -4.1086240000000e+01\r\n1485 1484  7.9143095000000e+00\r\n1531 1484  1.2699265000000e+01\r\n1533 1484 -1.3050280000000e+00\r\n2589 1484 -2.1660390000000e+00\r\n379 1485  1.6219336000000e+00\r\n380 1485 -2.6276103000000e-01\r\n381 1485 -3.0872741000000e+00\r\n1437 1485 -2.1246357000000e+00\r\n1480 1485  4.2359396000000e+00\r\n1481 1485 -6.8624254000000e-01\r\n1482 1485 -2.2911882000000e+00\r\n1483 1485 -2.3700561000000e+02\r\n1484 1485  3.6671012000000e+01\r\n1485 1485  1.3378339000000e+01\r\n1531 1485  2.1466823000000e+01\r\n1532 1485 -3.4777282000000e+00\r\n1533 1485 -2.2060178000000e+00\r\n2589 1485 -3.6614697000000e+00\r\n1486 1486  1.0000000000000e+00\r\n1487 1487  1.0000000000000e+00\r\n1488 1488  1.0000000000000e+00\r\n1489 1489  1.0000000000000e+00\r\n1490 1490  1.0000000000000e+00\r\n1491 1491  1.0000000000000e+00\r\n1492 1492  1.0000000000000e+00\r\n1493 1493  1.0000000000000e+00\r\n1494 1494  1.0000000000000e+00\r\n1495 1495  1.0000000000000e+00\r\n1496 1496  1.0000000000000e+00\r\n1497 1497  1.0000000000000e+00\r\n1498 1498  1.0000000000000e+00\r\n1499 1499  1.0000000000000e+00\r\n1500 1500  1.0000000000000e+00\r\n397 1501 -9.4909644000000e-04\r\n399 1501 -9.9051999000000e-06\r\n1501 1501  2.3751600000000e+02\r\n1503 1501  5.9348746000000e-04\r\n1504 1501 -8.1308798000000e-04\r\n1506 1501 -8.4857540000000e-06\r\n1549 1501 -7.4546262000000e-04\r\n1551 1501 -7.7799852000000e-06\r\n2605 1501 -4.9070637000000e-02\r\n2607 1501 -1.1738265000000e-05\r\n397 1502  9.6736796000000e-01\r\n399 1502 -1.6717298000000e+00\r\n1501 1502 -1.4417444000000e+02\r\n1502 1502 -4.5215223000000e+01\r\n1503 1502  6.4070392000000e+00\r\n1506 1502 -1.4551388000000e+00\r\n1549 1502  6.7886956000000e+00\r\n1551 1502 -1.2892139000000e+00\r\n2607 1502 -1.9859020000000e+00\r\n397 1503  1.6352377000000e+00\r\n398 1503 -2.6490482000000e-01\r\n399 1503 -2.8258900000000e+00\r\n1501 1503 -2.4371230000000e+02\r\n1502 1503  3.7533536000000e+01\r\n1503 1503  1.0830453000000e+01\r\n1506 1503 -2.4597666000000e+00\r\n1549 1503  1.1475603000000e+01\r\n1550 1503 -1.8590219000000e+00\r\n1551 1503 -2.1792857000000e+00\r\n2607 1503 -3.3569658000000e+00\r\n400 1504 -8.9387850000000e-04\r\n402 1504 -9.3289205000000e-06\r\n1456 1504 -8.2239126000000e-04\r\n1458 1504 -8.5828473000000e-06\r\n1501 1504 -2.4458134000000e-02\r\n1503 1504 -8.4857540000000e-06\r\n1504 1504  2.4836450000000e+02\r\n1506 1504  6.3543396000000e-04\r\n1507 1504 -2.4687892000000e-02\r\n1509 1504 -8.8644260000000e-06\r\n1552 1504 -7.9467502000000e-04\r\n1554 1504 -8.2935881000000e-06\r\n2608 1504 -4.8017324000000e-02\r\n2610 1504 -1.1047996000000e-05\r\n400 1505  1.1078724000000e+00\r\n402 1505 -1.5953249000000e+00\r\n1458 1505 -1.5395618000000e+00\r\n1501 1505  4.8579944000000e+00\r\n1503 1505 -1.4551388000000e+00\r\n1504 1505 -1.6231943000000e+02\r\n1505 1505 -4.7264376000000e+01\r\n1506 1505  9.3809026000000e+00\r\n1507 1505  1.1591144000000e+00\r\n1509 1505 -1.5200077000000e+00\r\n1552 1505  1.2566956000000e+01\r\n1554 1505 -1.3712112000000e+00\r\n2610 1505 -1.8943762000000e+00\r\n400 1506  1.8727475000000e+00\r\n401 1506 -3.0338303000000e-01\r\n402 1506 -2.6967372000000e+00\r\n1458 1506 -2.6024753000000e+00\r\n1501 1506  8.2119536000000e+00\r\n1502 1506 -1.3303274000000e+00\r\n1503 1506 -2.4597666000000e+00\r\n1504 1506 -2.7438477000000e+02\r\n1505 1506  4.2428957000000e+01\r\n1506 1506  1.5857478000000e+01\r\n1507 1506  1.9593670000000e+00\r\n1508 1506 -3.1741530000000e-01\r\n1509 1506 -2.5694210000000e+00\r\n1552 1506  2.1243182000000e+01\r\n1553 1506 -3.4413720000000e+00\r\n1554 1506 -2.3178955000000e+00\r\n2610 1506 -3.2022536000000e+00\r\n403 1507 -8.5917158000000e-04\r\n405 1507 -8.9667033000000e-06\r\n1459 1507 -8.4398148000000e-04\r\n1461 1507 -8.8081726000000e-06\r\n1504 1507 -8.4937157000000e-04\r\n1506 1507 -8.8644260000000e-06\r\n1507 1507  2.5919759000000e+02\r\n1509 1507  6.6122729000000e-04\r\n1510 1507 -5.0848390000000e-02\r\n1512 1507 -9.2733182000000e-06\r\n1555 1507 -3.8161872000000e-02\r\n1557 1507 -8.6210888000000e-06\r\n2611 1507 -4.6123540000000e-02\r\n2613 1507 -1.0607112000000e-05\r\n403 1508  1.3706750000000e+00\r\n405 1508 -1.5271880000000e+00\r\n1461 1508 -1.5751537000000e+00\r\n1506 1508 -1.5200077000000e+00\r\n1507 1508 -1.7047620000000e+02\r\n1508 1508 -4.9318400000000e+01\r\n1509 1508  9.4987930000000e+00\r\n1510 1508  3.6763866000000e+00\r\n1512 1508 -1.5847634000000e+00\r\n1555 1508  1.6599150000000e+01\r\n1557 1508 -1.4735359000000e+00\r\n2613 1508 -1.8126331000000e+00\r\n403 1509  2.3169875000000e+00\r\n404 1509 -3.7534895000000e-01\r\n405 1509 -2.5815568000000e+00\r\n1461 1509 -2.6626383000000e+00\r\n1506 1509 -2.5694210000000e+00\r\n1507 1509 -2.8817279000000e+02\r\n1508 1509  4.4577014000000e+01\r\n1509 1509  1.6056750000000e+01\r\n1510 1509  6.2145599000000e+00\r\n1511 1509 -1.0067506000000e+00\r\n1512 1509 -2.6788823000000e+00\r\n1555 1509  2.8059187000000e+01\r\n1556 1509 -4.5455510000000e+00\r\n1557 1509 -2.4908634000000e+00\r\n2613 1509 -3.0640727000000e+00\r\n406 1510 -8.3206675000000e-04\r\n408 1510 -8.6838251000000e-06\r\n1462 1510 -8.6723476000000e-04\r\n1464 1510 -9.0508544000000e-06\r\n1507 1510 -8.8855081000000e-04\r\n1509 1510 -9.2733182000000e-06\r\n1510 1510  2.7004009000000e+02\r\n1512 1510  6.8734928000000e-04\r\n1513 1510 -4.8725905000000e-02\r\n1515 1510 -9.5533495000000e-06\r\n1558 1510 -9.1979919000000e-02\r\n1560 1510 -9.1876557000000e-06\r\n2614 1510 -4.3192237000000e-02\r\n2616 1510 -1.0255506000000e-05\r\n406 1511  1.7787051000000e+00\r\n408 1511 -1.4635822000000e+00\r\n1464 1511 -1.6098024000000e+00\r\n1509 1511 -1.5847634000000e+00\r\n1510 1511 -1.8161181000000e+02\r\n1511 1511 -5.1373691000000e+01\r\n1512 1511  9.5744591000000e+00\r\n1513 1511  3.9218115000000e+00\r\n1515 1511 -1.6178102000000e+00\r\n1558 1511  2.0880731000000e+01\r\n1560 1511 -1.5561203000000e+00\r\n2616 1511 -1.7366396000000e+00\r\n406 1512  3.0067231000000e+00\r\n407 1512 -4.8708231000000e-01\r\n408 1512 -2.4740393000000e+00\r\n1464 1512 -2.7212100000000e+00\r\n1509 1512 -2.6788823000000e+00\r\n1510 1512 -3.0699661000000e+02\r\n1511 1512  4.7537372000000e+01\r\n1512 1512  1.6184664000000e+01\r\n1513 1512  6.6294301000000e+00\r\n1514 1512 -1.0739526000000e+00\r\n1515 1512 -2.7347463000000e+00\r\n1558 1512  3.5296787000000e+01\r\n1559 1512 -5.7179994000000e+00\r\n1560 1512 -2.6304658000000e+00\r\n2616 1512 -2.9356156000000e+00\r\n409 1513 -8.3935795000000e-04\r\n411 1513 -8.7599193000000e-06\r\n1465 1513 -8.7363124000000e-04\r\n1467 1513 -9.1176109000000e-06\r\n1510 1513 -9.1538284000000e-04\r\n1512 1513 -9.5533495000000e-06\r\n1513 1513  2.7008309000000e+02\r\n1515 1513  6.8833418000000e-04\r\n1516 1513 -2.8041727000000e-02\r\n1518 1513 -9.6454470000000e-06\r\n1561 1513 -1.6072546000000e-01\r\n1563 1513 -9.5827761000000e-06\r\n2617 1513 -3.9367327000000e-02\r\n2619 1513 -1.0326069000000e-05\r\n409 1514  2.3223633000000e+00\r\n411 1514 -1.4603090000000e+00\r\n1467 1514 -1.6113827000000e+00\r\n1512 1514 -1.6178102000000e+00\r\n1513 1514 -1.8423016000000e+02\r\n1514 1514 -5.1374787000000e+01\r\n1515 1514  9.6524961000000e+00\r\n1516 1514  1.8876594000000e+00\r\n1518 1514 -1.6178115000000e+00\r\n1561 1514  2.4991137000000e+01\r\n1563 1514 -1.6075376000000e+00\r\n2619 1514 -1.7319037000000e+00\r\n409 1515  3.9257207000000e+00\r\n410 1515 -6.3595464000000e-01\r\n411 1515 -2.4685050000000e+00\r\n1467 1515 -2.7238788000000e+00\r\n1512 1515 -2.7347463000000e+00\r\n1513 1515 -3.1142250000000e+02\r\n1514 1515  4.8251452000000e+01\r\n1515 1515  1.6316571000000e+01\r\n1516 1515  3.1908977000000e+00\r\n1517 1515 -5.1691558000000e-01\r\n1518 1515 -2.7347471000000e+00\r\n1561 1515  4.2244995000000e+01\r\n1562 1515 -6.8435583000000e+00\r\n1563 1515 -2.7173801000000e+00\r\n2619 1515 -2.9276085000000e+00\r\n412 1516 -8.4416373000000e-04\r\n414 1516 -8.8100746000000e-06\r\n1468 1516 -8.7658522000000e-04\r\n1470 1516 -9.1484399000000e-06\r\n1513 1516 -9.2420744000000e-04\r\n1515 1516 -9.6454470000000e-06\r\n1516 1516  2.7007521000000e+02\r\n1518 1516  6.8862876000000e-04\r\n1519 1516 -9.2584909000000e-04\r\n1521 1516 -9.6625799000000e-06\r\n1564 1516 -1.8218975000000e-01\r\n1566 1516 -9.6351775000000e-06\r\n2620 1516 -3.7136019000000e-02\r\n2622 1516 -1.0375283000000e-05\r\n412 1517  2.6636120000000e+00\r\n414 1517 -1.4603067000000e+00\r\n1470 1517 -1.6113755000000e+00\r\n1515 1517 -1.6178115000000e+00\r\n1516 1517 -1.8480023000000e+02\r\n1517 1517 -5.1374772000000e+01\r\n1518 1517  9.6536146000000e+00\r\n1521 1517 -1.6178126000000e+00\r\n1564 1517  2.7107692000000e+01\r\n1566 1517 -1.6086679000000e+00\r\n2622 1517 -1.7318990000000e+00\r\n412 1518  4.5025698000000e+00\r\n413 1518 -7.2939997000000e-01\r\n414 1518 -2.4685025000000e+00\r\n1470 1518 -2.7238692000000e+00\r\n1515 1518 -2.7347471000000e+00\r\n1516 1518 -3.1238630000000e+02\r\n1517 1518  4.8407342000000e+01\r\n1518 1518  1.6318467000000e+01\r\n1521 1518 -2.7347488000000e+00\r\n1564 1518  4.5822842000000e+01\r\n1565 1518 -7.4231342000000e+00\r\n1566 1518 -2.7192922000000e+00\r\n2622 1518 -2.9276020000000e+00\r\n415 1519 -8.4070669000000e-04\r\n417 1519 -8.7739954000000e-06\r\n1471 1519 -8.7323983000000e-04\r\n1473 1519 -9.1135260000000e-06\r\n1516 1519 -2.1590804000000e-02\r\n1518 1519 -9.6625799000000e-06\r\n1519 1519  2.7009410000000e+02\r\n1521 1519  6.8843280000000e-04\r\n1522 1519 -9.1766119000000e-04\r\n1524 1519 -9.5771274000000e-06\r\n1567 1519 -1.7948756000000e-01\r\n1569 1519 -9.6173852000000e-06\r\n2623 1519 -3.8450156000000e-02\r\n2625 1519 -1.0338482000000e-05\r\n415 1520  2.4505236000000e+00\r\n417 1520 -1.4594767000000e+00\r\n1473 1520 -1.6118470000000e+00\r\n1516 1520  1.2533309000000e+00\r\n1518 1520 -1.6178126000000e+00\r\n1519 1520 -1.8481019000000e+02\r\n1520 1520 -5.1375126000000e+01\r\n1521 1520  9.6540106000000e+00\r\n1524 1520 -1.6177334000000e+00\r\n1567 1520  2.6077818000000e+01\r\n1569 1520 -1.6104834000000e+00\r\n2625 1520 -1.7309160000000e+00\r\n415 1521  4.1423626000000e+00\r\n416 1521 -6.7104929000000e-01\r\n417 1521 -2.4670980000000e+00\r\n1473 1521 -2.7246643000000e+00\r\n1516 1521  2.1186294000000e+00\r\n1517 1521 -3.4321107000000e-01\r\n1518 1521 -2.7347488000000e+00\r\n1519 1521 -3.1240296000000e+02\r\n1520 1521  4.8409390000000e+01\r\n1521 1521  1.6319131000000e+01\r\n1524 1521 -2.7346166000000e+00\r\n1567 1521  4.4081918000000e+01\r\n1568 1521 -7.1411270000000e+00\r\n1569 1521 -2.7223596000000e+00\r\n2625 1521 -2.9259386000000e+00\r\n418 1522 -8.3289178000000e-04\r\n420 1522 -8.6924355000000e-06\r\n1474 1522 -8.6660839000000e-04\r\n1476 1522 -9.0443172000000e-06\r\n1519 1522 -4.4701745000000e-02\r\n1521 1522 -9.5771274000000e-06\r\n1522 1522  2.7008965000000e+02\r\n1524 1522  6.8782746000000e-04\r\n1525 1522 -8.9809299000000e-04\r\n1527 1522 -9.3729048000000e-06\r\n1570 1522 -1.4792916000000e-01\r\n1572 1522 -9.5404218000000e-06\r\n2626 1522 -4.1432319000000e-02\r\n2628 1522 -1.0254566000000e-05\r\n418 1523  2.0051029000000e+00\r\n420 1523 -1.4604292000000e+00\r\n1476 1523 -1.6118921000000e+00\r\n1519 1523  3.5260769000000e+00\r\n1521 1523 -1.6177334000000e+00\r\n1522 1523 -1.8431844000000e+02\r\n1523 1523 -5.1374246000000e+01\r\n1524 1523  9.6407722000000e+00\r\n1527 1523 -1.6011305000000e+00\r\n1570 1523  2.3757471000000e+01\r\n1572 1523 -1.6117570000000e+00\r\n2628 1523 -1.7320887000000e+00\r\n418 1524  3.3894259000000e+00\r\n419 1524 -5.4907849000000e-01\r\n420 1524 -2.4687096000000e+00\r\n1476 1524 -2.7247424000000e+00\r\n1519 1524  5.9604802000000e+00\r\n1520 1524 -9.6558282000000e-01\r\n1521 1524 -2.7346166000000e+00\r\n1522 1524 -3.1157189000000e+02\r\n1523 1524  4.8277121000000e+01\r\n1524 1524  1.6296759000000e+01\r\n1527 1524 -2.7065491000000e+00\r\n1570 1524  4.0159629000000e+01\r\n1571 1524 -6.5057592000000e+00\r\n1572 1524 -2.7245140000000e+00\r\n2628 1524 -2.9279228000000e+00\r\n421 1525 -8.4007217000000e-04\r\n423 1525 -8.7673732000000e-06\r\n1477 1525 -8.2482254000000e-04\r\n1479 1525 -8.6082212000000e-06\r\n1522 1525 -6.4392667000000e-02\r\n1524 1525 -9.3729048000000e-06\r\n1525 1525  2.6468463000000e+02\r\n1527 1525  6.7401653000000e-04\r\n1528 1525 -8.4943775000000e-04\r\n1530 1525 -8.8651167000000e-06\r\n1573 1525 -1.1755223000000e-01\r\n1575 1525 -9.3363636000000e-06\r\n2629 1525 -4.4120055000000e-02\r\n2631 1525 -1.0353917000000e-05\r\n421 1526  1.6041890000000e+00\r\n423 1526 -1.4913157000000e+00\r\n1479 1526 -1.5470819000000e+00\r\n1522 1526  4.4628450000000e+00\r\n1524 1526 -1.6011305000000e+00\r\n1525 1526 -1.7920248000000e+02\r\n1526 1526 -5.0346702000000e+01\r\n1527 1526  9.5433280000000e+00\r\n1530 1526 -1.5344165000000e+00\r\n1573 1526  2.1205997000000e+01\r\n1575 1526 -1.5951116000000e+00\r\n2631 1526 -1.7686457000000e+00\r\n421 1527  2.7117191000000e+00\r\n422 1527 -4.3929488000000e-01\r\n423 1527 -2.5209182000000e+00\r\n1479 1527 -2.6151855000000e+00\r\n1522 1527  7.5439876000000e+00\r\n1523 1527 -1.2221159000000e+00\r\n1524 1527 -2.7065491000000e+00\r\n1525 1527 -3.0292365000000e+02\r\n1526 1527  4.6920720000000e+01\r\n1527 1527  1.6132032000000e+01\r\n1530 1527 -2.5937775000000e+00\r\n1573 1527  3.5846591000000e+01\r\n1574 1527 -5.8070999000000e+00\r\n1575 1527 -2.6963746000000e+00\r\n2631 1527 -2.9897163000000e+00\r\n424 1528 -8.8398968000000e-04\r\n426 1528 -9.2257162000000e-06\r\n1480 1528 -7.6570254000000e-04\r\n1482 1528 -7.9912181000000e-06\r\n1525 1528 -8.0443630000000e-02\r\n1527 1528 -8.8651167000000e-06\r\n1528 1528  2.4846584000000e+02\r\n1530 1528  6.3445574000000e-04\r\n1531 1528 -7.6536868000000e-04\r\n1533 1528 -7.9877338000000e-06\r\n1576 1528 -7.2952815000000e-02\r\n1578 1528 -8.6533326000000e-06\r\n2632 1528 -4.6164921000000e-02\r\n2634 1528 -1.0907693000000e-05\r\n424 1529  1.3215054000000e+00\r\n426 1529 -1.5915783000000e+00\r\n1482 1529 -1.4497408000000e+00\r\n1525 1529  4.9241295000000e+00\r\n1527 1529 -1.5344165000000e+00\r\n1528 1529 -1.6654788000000e+02\r\n1529 1529 -4.7265374000000e+01\r\n1530 1529  9.3684860000000e+00\r\n1533 1529 -1.4015808000000e+00\r\n1576 1529  1.7675979000000e+01\r\n1578 1529 -1.4979855000000e+00\r\n2634 1529 -1.8879020000000e+00\r\n424 1530  2.2338727000000e+00\r\n425 1530 -3.6188685000000e-01\r\n426 1530 -2.6904039000000e+00\r\n1482 1530 -2.4506419000000e+00\r\n1525 1530  8.3237484000000e+00\r\n1526 1530 -1.3484453000000e+00\r\n1527 1530 -2.5937775000000e+00\r\n1528 1530 -2.8153254000000e+02\r\n1529 1530  4.3584773000000e+01\r\n1530 1530  1.5836487000000e+01\r\n1533 1530 -2.3692308000000e+00\r\n1576 1530  2.9879475000000e+01\r\n1577 1530 -4.8404679000000e+00\r\n1578 1530 -2.5321947000000e+00\r\n2634 1530 -3.1913095000000e+00\r\n427 1531 -9.7629545000000e-04\r\n429 1531 -1.0189061000000e-05\r\n1483 1531 -6.8368851000000e-04\r\n1485 1531 -7.1352826000000e-06\r\n1528 1531 -9.2297563000000e-02\r\n1530 1531 -7.9877338000000e-06\r\n1531 1531  2.2143450000000e+02\r\n1533 1531  5.6275922000000e-04\r\n1579 1531 -1.7879426000000e-02\r\n1581 1531 -7.7108176000000e-06\r\n2635 1531 -4.7265566000000e-02\r\n2637 1531 -1.2053366000000e-05\r\n427 1532  1.1575908000000e+00\r\n429 1532 -1.7831636000000e+00\r\n1485 1532 -1.3050280000000e+00\r\n1528 1532  4.5828135000000e+00\r\n1530 1532 -1.4015808000000e+00\r\n1531 1532 -1.4260298000000e+02\r\n1532 1532 -4.2130994000000e+01\r\n1533 1532  7.9625911000000e+00\r\n1579 1532  9.7432456000000e+00\r\n1581 1532 -1.3531654000000e+00\r\n2637 1532 -2.1149439000000e+00\r\n427 1533  1.9567904000000e+00\r\n428 1533 -3.1700217000000e-01\r\n429 1533 -3.0142581000000e+00\r\n1485 1533 -2.2060178000000e+00\r\n1528 1533  7.7467837000000e+00\r\n1529 1533 -1.2549874000000e+00\r\n1530 1533 -2.3692308000000e+00\r\n1531 1533 -2.4105594000000e+02\r\n1532 1533  3.7240289000000e+01\r\n1533 1533  1.3459956000000e+01\r\n1579 1533  1.6469973000000e+01\r\n1580 1533 -2.6681535000000e+00\r\n1581 1533 -2.2873895000000e+00\r\n2637 1533 -3.5750987000000e+00\r\n1534 1534  1.0000000000000e+00\r\n1535 1535  1.0000000000000e+00\r\n1536 1536  1.0000000000000e+00\r\n1537 1537  1.0000000000000e+00\r\n1538 1538  1.0000000000000e+00\r\n1539 1539  1.0000000000000e+00\r\n1540 1540  1.0000000000000e+00\r\n1541 1541  1.0000000000000e+00\r\n1542 1542  1.0000000000000e+00\r\n1543 1543  1.0000000000000e+00\r\n1544 1544  1.0000000000000e+00\r\n1545 1545  1.0000000000000e+00\r\n1546 1546  1.0000000000000e+00\r\n1547 1547  1.0000000000000e+00\r\n1548 1548  1.0000000000000e+00\r\n445 1549 -1.1469225000000e-03\r\n447 1549 -1.1969802000000e-05\r\n1501 1549 -7.1538059000000e-02\r\n1503 1549 -7.7799852000000e-06\r\n1549 1549  1.9983026000000e+02\r\n1551 1549  5.1535618000000e-04\r\n1552 1549 -4.3887336000000e-02\r\n1554 1549 -7.5037232000000e-06\r\n1597 1549 -6.4507151000000e-04\r\n1599 1549 -6.7322581000000e-06\r\n2653 1549 -4.8488816000000e-02\r\n2655 1549 -1.4188647000000e-05\r\n445 1550  1.0287243000000e+00\r\n447 1550 -1.9802948000000e+00\r\n1503 1550 -1.2892139000000e+00\r\n1549 1550 -1.2404451000000e+02\r\n1550 1550 -3.8042021000000e+01\r\n1551 1550  7.9546088000000e+00\r\n1552 1550  6.9714899000000e-01\r\n1554 1550 -1.2435723000000e+00\r\n1597 1550  7.6305992000000e+00\r\n1599 1550 -1.0858122000000e+00\r\n2655 1550 -2.3514563000000e+00\r\n445 1551  1.7389544000000e+00\r\n446 1551 -2.8170320000000e-01\r\n447 1551 -3.3474880000000e+00\r\n1503 1551 -2.1792857000000e+00\r\n1549 1551 -2.0968470000000e+02\r\n1550 1551  3.2281529000000e+01\r\n1551 1551  1.3446461000000e+01\r\n1552 1551  1.1784598000000e+00\r\n1553 1551 -1.9090548000000e-01\r\n1554 1551 -2.1021332000000e+00\r\n1597 1551  1.2898756000000e+01\r\n1598 1551 -2.0895436000000e+00\r\n1599 1551 -1.8354556000000e+00\r\n2655 1551 -3.9748983000000e+00\r\n448 1552 -1.0671973000000e-03\r\n450 1552 -1.1137754000000e-05\r\n1504 1552 -6.2085766000000e-03\r\n1506 1552 -8.2935881000000e-06\r\n1549 1552 -7.1899175000000e-04\r\n1551 1552 -7.5037232000000e-06\r\n1552 1552  2.1597555000000e+02\r\n1554 1552  5.6090580000000e-04\r\n1555 1552 -6.1745967000000e-02\r\n1557 1552 -8.1998813000000e-06\r\n1600 1552 -7.1997856000000e-04\r\n1602 1552 -7.5140220000000e-06\r\n2656 1552 -4.6791177000000e-02\r\n2658 1552 -1.3190472000000e-05\r\n448 1553  1.2852983000000e+00\r\n450 1553 -1.8368744000000e+00\r\n1506 1553 -1.3712112000000e+00\r\n1551 1553 -1.2435723000000e+00\r\n1552 1553 -1.4018058000000e+02\r\n1553 1553 -4.1122058000000e+01\r\n1554 1553  9.1927650000000e+00\r\n1555 1553  3.8809383000000e+00\r\n1557 1553 -1.3559021000000e+00\r\n1600 1553  1.1021295000000e+01\r\n1602 1553 -1.1995306000000e+00\r\n2658 1553 -2.1810716000000e+00\r\n448 1554  2.1726682000000e+00\r\n449 1554 -3.5196233000000e-01\r\n450 1554 -3.1050525000000e+00\r\n1506 1554 -2.3178955000000e+00\r\n1551 1554 -2.1021332000000e+00\r\n1552 1554 -2.3696125000000e+02\r\n1553 1554  3.6574131000000e+01\r\n1554 1554  1.5539449000000e+01\r\n1555 1554  6.5603381000000e+00\r\n1556 1554 -1.0627448000000e+00\r\n1557 1554 -2.2920168000000e+00\r\n1600 1554  1.8630397000000e+01\r\n1601 1554 -3.0180392000000e+00\r\n1602 1554 -2.0276865000000e+00\r\n2658 1554 -3.6868835000000e+00\r\n451 1555 -9.8095071000000e-04\r\n453 1555 -1.0237645000000e-05\r\n1507 1555 -8.2605548000000e-04\r\n1509 1555 -8.6210888000000e-06\r\n1552 1555 -7.8569623000000e-04\r\n1554 1555 -8.1998813000000e-06\r\n1555 1555  2.3762407000000e+02\r\n1557 1555  6.1174842000000e-04\r\n1558 1555 -9.6016617000000e-02\r\n1560 1555 -8.9917060000000e-06\r\n1603 1555 -3.8034348000000e-02\r\n1605 1555 -8.0120757000000e-06\r\n2659 1555 -4.2697007000000e-02\r\n2661 1555 -1.2107049000000e-05\r\n451 1556  1.8502484000000e+00\r\n453 1556 -1.6671745000000e+00\r\n1509 1556 -1.4735359000000e+00\r\n1554 1556 -1.3559021000000e+00\r\n1555 1556 -1.6037733000000e+02\r\n1556 1556 -4.5233550000000e+01\r\n1557 1556  9.2621788000000e+00\r\n1558 1556  6.5768912000000e+00\r\n1560 1556 -1.4703690000000e+00\r\n1603 1556  1.5556959000000e+01\r\n1605 1556 -1.3103950000000e+00\r\n2661 1556 -1.9797396000000e+00\r\n451 1557  3.1276573000000e+00\r\n452 1557 -5.0666325000000e-01\r\n453 1557 -2.8181894000000e+00\r\n1509 1557 -2.4908634000000e+00\r\n1554 1557 -2.2920168000000e+00\r\n1555 1557 -2.7110161000000e+02\r\n1556 1557  4.1924961000000e+01\r\n1557 1557  1.5656777000000e+01\r\n1558 1557  1.1117568000000e+01\r\n1559 1557 -1.8009847000000e+00\r\n1560 1557 -2.4855097000000e+00\r\n1603 1557  2.6297461000000e+01\r\n1604 1557 -4.2600436000000e+00\r\n1605 1557 -2.2150898000000e+00\r\n2661 1557 -3.3465496000000e+00\r\n454 1558 -9.3784308000000e-04\r\n456 1558 -9.7877547000000e-06\r\n1510 1558 -8.8034279000000e-04\r\n1512 1558 -9.1876557000000e-06\r\n1555 1558 -8.6156728000000e-04\r\n1557 1558 -8.9917060000000e-06\r\n1558 1558  2.5387027000000e+02\r\n1560 1558  6.5172112000000e-04\r\n1561 1558 -1.1131295000000e-01\r\n1563 1558 -9.7550158000000e-06\r\n1606 1558 -8.6572045000000e-02\r\n1608 1558 -8.9907933000000e-06\r\n2662 1558 -3.5557201000000e-02\r\n2664 1558 -1.1539199000000e-05\r\n454 1559  2.8964717000000e+00\r\n456 1559 -1.5621511000000e+00\r\n1512 1559 -1.5561203000000e+00\r\n1557 1559 -1.4703690000000e+00\r\n1558 1559 -1.7753410000000e+02\r\n1559 1559 -4.8317530000000e+01\r\n1560 1559  9.4613899000000e+00\r\n1561 1559  7.1354518000000e+00\r\n1563 1559 -1.5677348000000e+00\r\n1606 1559  2.1809515000000e+01\r\n1608 1559 -1.4451929000000e+00\r\n2664 1559 -1.8544138000000e+00\r\n454 1560  4.8961958000000e+00\r\n455 1560 -7.9314774000000e-01\r\n456 1560 -2.6406602000000e+00\r\n1512 1560 -2.6304658000000e+00\r\n1557 1560 -2.4855097000000e+00\r\n1558 1560 -3.0010364000000e+02\r\n1559 1560  4.6486840000000e+01\r\n1560 1560  1.5993531000000e+01\r\n1561 1560  1.2061768000000e+01\r\n1562 1560 -1.9539178000000e+00\r\n1563 1560 -2.6500988000000e+00\r\n1606 1560  3.6866804000000e+01\r\n1607 1560 -5.9721515000000e+00\r\n1608 1560 -2.4429541000000e+00\r\n2664 1560 -3.1347010000000e+00\r\n457 1561 -9.0089319000000e-04\r\n459 1561 -9.4021289000000e-06\r\n1513 1561 -9.1820244000000e-04\r\n1515 1561 -9.5827761000000e-06\r\n1558 1561 -9.3470610000000e-04\r\n1560 1561 -9.7550158000000e-06\r\n1561 1561  2.7005098000000e+02\r\n1563 1561  6.9134172000000e-04\r\n1564 1561 -4.9570185000000e-02\r\n1566 1561 -1.0246668000000e-05\r\n1609 1561 -1.4764679000000e-01\r\n1611 1561 -9.9586297000000e-06\r\n2665 1561 -2.6542630000000e-02\r\n2667 1561 -1.1035480000000e-05\r\n457 1562  4.2818111000000e+00\r\n459 1562 -1.4688418000000e+00\r\n1515 1562 -1.6075376000000e+00\r\n1560 1562 -1.5677348000000e+00\r\n1561 1562 -1.9255353000000e+02\r\n1562 1562 -5.1400549000000e+01\r\n1563 1562  9.5838566000000e+00\r\n1564 1562  3.9993039000000e+00\r\n1566 1562 -1.6182239000000e+00\r\n1609 1562  2.9278995000000e+01\r\n1611 1562 -1.5730491000000e+00\r\n2667 1562 -1.7427167000000e+00\r\n457 1563  7.2379693000000e+00\r\n458 1563 -1.1724858000000e+00\r\n459 1563 -2.4829287000000e+00\r\n1515 1563 -2.7173801000000e+00\r\n1560 1563 -2.6500988000000e+00\r\n1561 1563 -3.2549230000000e+02\r\n1562 1563  5.0465801000000e+01\r\n1563 1563  1.6200543000000e+01\r\n1564 1563  6.7604194000000e+00\r\n1565 1563 -1.0951270000000e+00\r\n1566 1563 -2.7354441000000e+00\r\n1609 1563  4.9493185000000e+01\r\n1610 1563 -8.0174499000000e+00\r\n1611 1563 -2.6590806000000e+00\r\n2667 1563 -2.9458861000000e+00\r\n460 1564 -9.1065197000000e-04\r\n462 1564 -9.5039760000000e-06\r\n1516 1564 -9.2322343000000e-04\r\n1518 1564 -9.6351775000000e-06\r\n1561 1564 -9.8181522000000e-04\r\n1563 1564 -1.0246668000000e-05\r\n1564 1564  2.7005242000000e+02\r\n1566 1564  6.9243691000000e-04\r\n1567 1564 -9.8558489000000e-04\r\n1569 1564 -1.0286010000000e-05\r\n1612 1564 -2.0590679000000e-01\r\n1614 1564 -1.0280249000000e-05\r\n2668 1564 -1.9502765000000e-02\r\n2670 1564 -1.1119317000000e-05\r\n460 1565  5.4598407000000e+00\r\n462 1565 -1.4671910000000e+00\r\n1518 1565 -1.6086679000000e+00\r\n1563 1565 -1.6182239000000e+00\r\n1564 1565 -1.9454466000000e+02\r\n1565 1565 -5.1401676000000e+01\r\n1566 1565  9.6671848000000e+00\r\n1569 1565 -1.6181589000000e+00\r\n1612 1565  3.4093072000000e+01\r\n1614 1565 -1.6091451000000e+00\r\n2670 1565 -1.7400448000000e+00\r\n460 1566  9.2293147000000e+00\r\n461 1566 -1.4950565000000e+00\r\n462 1566 -2.4801396000000e+00\r\n1518 1566 -2.7192922000000e+00\r\n1563 1566 -2.7354441000000e+00\r\n1564 1566 -3.2885829000000e+02\r\n1565 1566  5.1007865000000e+01\r\n1566 1566  1.6341406000000e+01\r\n1569 1566 -2.7353340000000e+00\r\n1612 1566  5.7630928000000e+01\r\n1613 1566 -9.3356331000000e+00\r\n1614 1566 -2.7200988000000e+00\r\n2670 1566 -2.9413717000000e+00\r\n463 1567 -9.0248425000000e-04\r\n465 1567 -9.4187340000000e-06\r\n1519 1567 -9.2151861000000e-04\r\n1521 1567 -9.6173852000000e-06\r\n1564 1567 -2.4568362000000e-02\r\n1566 1567 -1.0286010000000e-05\r\n1567 1567  2.7006275000000e+02\r\n1569 1567  6.9209336000000e-04\r\n1570 1567 -9.7191607000000e-04\r\n1572 1567 -1.0143356000000e-05\r\n1615 1567 -1.8675828000000e-01\r\n1617 1567 -1.0220960000000e-05\r\n2671 1567 -2.4154394000000e-02\r\n2673 1567 -1.1043669000000e-05\r\n463 1568  4.6256579000000e+00\r\n465 1568 -1.4648449000000e+00\r\n1521 1568 -1.6104834000000e+00\r\n1564 1568  2.3189631000000e+00\r\n1566 1568 -1.6181589000000e+00\r\n1567 1568 -1.9259145000000e+02\r\n1568 1568 -5.1400420000000e+01\r\n1569 1568  9.6626938000000e+00\r\n1572 1568 -1.6179695000000e+00\r\n1615 1568  3.0653316000000e+01\r\n1617 1568 -1.6082163000000e+00\r\n2673 1568 -1.7372681000000e+00\r\n463 1569  7.8192072000000e+00\r\n464 1569 -1.2666381000000e+00\r\n465 1569 -2.4761723000000e+00\r\n1521 1569 -2.7223596000000e+00\r\n1564 1569  3.9199728000000e+00\r\n1565 1569 -6.3499882000000e-01\r\n1566 1569 -2.7353340000000e+00\r\n1567 1569 -3.2555639000000e+02\r\n1568 1569  5.0476322000000e+01\r\n1569 1569  1.6333809000000e+01\r\n1572 1569 -2.7350156000000e+00\r\n1615 1569  5.1816332000000e+01\r\n1616 1569 -8.3937590000000e+00\r\n1617 1569 -2.7185272000000e+00\r\n2673 1569 -2.9366758000000e+00\r\n466 1570 -8.8562662000000e-04\r\n468 1570 -9.2428001000000e-06\r\n1522 1570 -9.1414414000000e-04\r\n1524 1570 -9.5404218000000e-06\r\n1567 1570 -7.6561930000000e-02\r\n1569 1570 -1.0143356000000e-05\r\n1570 1570  2.7010278000000e+02\r\n1572 1570  6.9121367000000e-04\r\n1573 1570 -9.5611433000000e-04\r\n1575 1570 -9.9784417000000e-06\r\n1618 1570 -1.6525313000000e-01\r\n1620 1570 -1.0082749000000e-05\r\n2674 1570 -3.2290073000000e-02\r\n2676 1570 -1.0869548000000e-05\r\n466 1571  3.3381173000000e+00\r\n468 1571 -1.4618491000000e+00\r\n1524 1571 -1.6117570000000e+00\r\n1567 1571  5.8761202000000e+00\r\n1569 1571 -1.6179695000000e+00\r\n1570 1571 -1.9042826000000e+02\r\n1571 1571 -5.1399319000000e+01\r\n1572 1571  9.6569757000000e+00\r\n1575 1571 -1.6173807000000e+00\r\n1618 1571  2.6218808000000e+01\r\n1620 1571 -1.6085433000000e+00\r\n2676 1571 -1.7337240000000e+00\r\n466 1572  5.6427535000000e+00\r\n467 1572 -9.1408041000000e-01\r\n468 1572 -2.4711096000000e+00\r\n1524 1572 -2.7245140000000e+00\r\n1567 1572  9.9329935000000e+00\r\n1568 1572 -1.6090646000000e+00\r\n1569 1572 -2.7350156000000e+00\r\n1570 1572 -3.2189992000000e+02\r\n1571 1572  4.9887176000000e+01\r\n1572 1572  1.6324150000000e+01\r\n1575 1572 -2.7340189000000e+00\r\n1618 1572  4.4320273000000e+01\r\n1619 1572 -7.1795256000000e+00\r\n1620 1572 -2.7190816000000e+00\r\n2676 1572 -2.9306871000000e+00\r\n469 1573 -8.6975225000000e-04\r\n471 1573 -9.0771279000000e-06\r\n1525 1573 -8.9459169000000e-04\r\n1527 1573 -9.3363636000000e-06\r\n1570 1573 -9.4315298000000e-02\r\n1572 1573 -9.9784417000000e-06\r\n1573 1573  2.7010058000000e+02\r\n1575 1573  6.8985677000000e-04\r\n1576 1573 -9.0942543000000e-04\r\n1578 1573 -9.4911753000000e-06\r\n1621 1573 -1.3796283000000e-01\r\n1623 1573 -9.9224252000000e-06\r\n2677 1573 -3.8943053000000e-02\r\n2679 1573 -1.0703731000000e-05\r\n469 1574  2.3525033000000e+00\r\n471 1574 -1.4625507000000e+00\r\n1527 1574 -1.5951116000000e+00\r\n1570 1574  6.8457526000000e+00\r\n1572 1574 -1.6173807000000e+00\r\n1573 1574 -1.8773039000000e+02\r\n1574 1574 -5.1398707000000e+01\r\n1575 1574  9.5914529000000e+00\r\n1578 1574 -1.5672576000000e+00\r\n1621 1574  2.3535825000000e+01\r\n1623 1574 -1.6085332000000e+00\r\n2679 1574 -1.7348672000000e+00\r\n469 1575  3.9766696000000e+00\r\n470 1575 -6.4419486000000e-01\r\n471 1575 -2.4722944000000e+00\r\n1527 1575 -2.6963746000000e+00\r\n1570 1575  1.1572054000000e+01\r\n1571 1575 -1.8745984000000e+00\r\n1572 1575 -2.7340189000000e+00\r\n1573 1575 -3.1733928000000e+02\r\n1574 1575  4.9150588000000e+01\r\n1575 1575  1.6213383000000e+01\r\n1578 1575 -2.6492923000000e+00\r\n1621 1575  3.9784937000000e+01\r\n1622 1575 -6.4449045000000e+00\r\n1623 1575 -2.7190631000000e+00\r\n2679 1575 -2.9326171000000e+00\r\n472 1576 -9.0582650000000e-04\r\n474 1576 -9.4536151000000e-06\r\n1528 1576 -8.2914502000000e-04\r\n1530 1576 -8.6533326000000e-06\r\n1573 1576 -1.2133851000000e-01\r\n1575 1576 -9.4911753000000e-06\r\n1576 1576  2.5395488000000e+02\r\n1578 1576  6.4999981000000e-04\r\n1579 1576 -8.1695519000000e-04\r\n1581 1576 -8.5261140000000e-06\r\n1624 1576 -1.5291237000000e-01\r\n1626 1576 -9.2566637000000e-06\r\n2680 1576 -4.2703690000000e-02\r\n2682 1576 -1.1163654000000e-05\r\n472 1577  1.8001589000000e+00\r\n474 1577 -1.5542434000000e+00\r\n1530 1577 -1.4979855000000e+00\r\n1573 1577  7.3708350000000e+00\r\n1575 1577 -1.5672576000000e+00\r\n1576 1577 -1.7841532000000e+02\r\n1577 1577 -4.8316631000000e+01\r\n1578 1577  9.4500405000000e+00\r\n1581 1577 -1.4529925000000e+00\r\n1624 1577  2.3550095000000e+01\r\n1626 1577 -1.5287703000000e+00\r\n2682 1577 -1.8433836000000e+00\r\n472 1578  3.0429885000000e+00\r\n473 1578 -4.9294985000000e-01\r\n474 1578 -2.6272931000000e+00\r\n1530 1578 -2.5321947000000e+00\r\n1573 1578  1.2459659000000e+01\r\n1574 1578 -2.0184063000000e+00\r\n1575 1578 -2.6492923000000e+00\r\n1576 1578 -3.0159326000000e+02\r\n1577 1578  4.6731329000000e+01\r\n1578 1578  1.5974347000000e+01\r\n1581 1578 -2.4561369000000e+00\r\n1624 1578  3.9809080000000e+01\r\n1625 1578 -6.4488840000000e+00\r\n1626 1578 -2.5842333000000e+00\r\n2682 1578 -3.1160556000000e+00\r\n475 1579 -9.5879409000000e-04\r\n477 1579 -1.0006409000000e-05\r\n1531 1579 -7.3883512000000e-04\r\n1533 1579 -7.7108176000000e-06\r\n1576 1579 -1.4722774000000e-01\r\n1578 1579 -8.5261140000000e-06\r\n1579 1579  2.3224678000000e+02\r\n1581 1579  5.8100696000000e-04\r\n2683 1579 -4.5977340000000e-02\r\n2685 1579 -1.1828495000000e-05\r\n475 1580  1.3378595000000e+00\r\n477 1580 -1.6997381000000e+00\r\n1533 1580 -1.3531654000000e+00\r\n1576 1580  1.1432940000000e+01\r\n1578 1580 -1.4529925000000e+00\r\n1579 1580 -1.4606883000000e+02\r\n1580 1580 -4.4202421000000e+01\r\n1581 1580  6.5265189000000e+00\r\n2685 1580 -2.0156766000000e+00\r\n475 1581  2.2615161000000e+00\r\n476 1581 -3.6636200000000e-01\r\n477 1581 -2.8732354000000e+00\r\n1533 1581 -2.2873895000000e+00\r\n1576 1581  1.9326230000000e+01\r\n1577 1581 -3.1308183000000e+00\r\n1578 1581 -2.4561369000000e+00\r\n1579 1581 -2.4691459000000e+02\r\n1580 1581  3.8060785000000e+01\r\n1581 1581  1.1032421000000e+01\r\n2685 1581 -3.4072979000000e+00\r\n1582 1582  1.0000000000000e+00\r\n1583 1583  1.0000000000000e+00\r\n1584 1584  1.0000000000000e+00\r\n1585 1585  1.0000000000000e+00\r\n1586 1586  1.0000000000000e+00\r\n1587 1587  1.0000000000000e+00\r\n1588 1588  1.0000000000000e+00\r\n1589 1589  1.0000000000000e+00\r\n1590 1590  1.0000000000000e+00\r\n1591 1591  1.0000000000000e+00\r\n1592 1592  1.0000000000000e+00\r\n1593 1593  1.0000000000000e+00\r\n1594 1594  1.0000000000000e+00\r\n1595 1595  1.0000000000000e+00\r\n1596 1596  1.0000000000000e+00\r\n493 1597 -1.4028493000000e-03\r\n495 1597 -1.4640770000000e-05\r\n1549 1597 -1.2626206000000e-02\r\n1551 1597 -6.7322581000000e-06\r\n1597 1597  1.6737565000000e+02\r\n1599 1597  4.4266306000000e-04\r\n1600 1597 -4.1726548000000e-02\r\n1602 1597 -6.5970170000000e-06\r\n1645 1597 -5.6705978000000e-04\r\n1647 1597 -5.9180924000000e-06\r\n2701 1597 -4.8243544000000e-02\r\n2703 1597 -1.7355340000000e-05\r\n493 1598  1.0597904000000e+00\r\n495 1598 -2.3587909000000e+00\r\n1551 1598 -1.0858122000000e+00\r\n1597 1598 -1.0603673000000e+02\r\n1598 1598 -3.1887467000000e+01\r\n1599 1598  8.2435414000000e+00\r\n1600 1598  2.8951741000000e+00\r\n1602 1598 -1.0641238000000e+00\r\n1645 1598  6.0116601000000e+00\r\n1647 1598 -9.3182338000000e-01\r\n2703 1598 -2.7994161000000e+00\r\n493 1599  1.7914685000000e+00\r\n494 1599 -2.9020548000000e-01\r\n495 1599 -3.9872974000000e+00\r\n1551 1599 -1.8354556000000e+00\r\n1597 1599 -1.7924437000000e+02\r\n1598 1599  2.7588098000000e+01\r\n1599 1599  1.3934873000000e+01\r\n1600 1599  4.8939990000000e+00\r\n1601 1599 -7.9279391000000e-01\r\n1602 1599 -1.7987936000000e+00\r\n1645 1599  1.0162103000000e+01\r\n1646 1599 -1.6461903000000e+00\r\n1647 1599 -1.5751531000000e+00\r\n2703 1599 -4.7321305000000e+00\r\n496 1600 -1.2576456000000e-03\r\n498 1600 -1.3125358000000e-05\r\n1552 1600 -9.2589174000000e-03\r\n1554 1600 -7.5140220000000e-06\r\n1597 1600 -6.3211298000000e-04\r\n1599 1600 -6.5970170000000e-06\r\n1600 1600  1.8902105000000e+02\r\n1602 1600  4.9862145000000e-04\r\n1603 1600 -9.5628774000000e-02\r\n1605 1600 -7.3856317000000e-06\r\n1648 1600 -1.4988432000000e-02\r\n1650 1600 -6.5290539000000e-06\r\n2704 1600 -4.4944929000000e-02\r\n2706 1600 -1.5540863000000e-05\r\n496 1601  1.5156651000000e+00\r\n498 1601 -2.0902235000000e+00\r\n1554 1601 -1.1995306000000e+00\r\n1599 1601 -1.0641238000000e+00\r\n1600 1601 -1.2523525000000e+02\r\n1601 1601 -3.6002030000000e+01\r\n1602 1601  9.0609038000000e+00\r\n1603 1601  6.5392851000000e+00\r\n1605 1601 -1.1792028000000e+00\r\n1648 1601  8.7142602000000e+00\r\n1650 1601 -1.0425703000000e+00\r\n2706 1601 -2.4812165000000e+00\r\n496 1602  2.5620804000000e+00\r\n497 1602 -4.1503644000000e-01\r\n498 1602 -3.5333138000000e+00\r\n1554 1602 -2.0276865000000e+00\r\n1599 1602 -1.7987936000000e+00\r\n1600 1602 -2.1169766000000e+02\r\n1601 1602  3.2657959000000e+01\r\n1602 1602  1.5316551000000e+01\r\n1603 1602  1.1054008000000e+01\r\n1604 1602 -1.7906604000000e+00\r\n1605 1602 -1.9933245000000e+00\r\n1648 1602  1.4730585000000e+01\r\n1649 1602 -2.3862365000000e+00\r\n1650 1602 -1.7623608000000e+00\r\n2706 1602 -4.1942484000000e+00\r\n499 1603 -1.1872176000000e-03\r\n501 1603 -1.2390340000000e-05\r\n1555 1603 -7.6770106000000e-04\r\n1557 1603 -8.0120757000000e-06\r\n1600 1603 -7.0767646000000e-04\r\n1602 1603 -7.3856317000000e-06\r\n1603 1603  2.0524886000000e+02\r\n1605 1603  5.3797809000000e-04\r\n1606 1603 -1.2557096000000e-01\r\n1608 1603 -8.3489597000000e-06\r\n1651 1603 -4.2672522000000e-02\r\n1653 1603 -7.3950702000000e-06\r\n2707 1603 -3.6136438000000e-02\r\n2709 1603 -1.4627561000000e-05\r\n499 1604  2.7846523000000e+00\r\n501 1604 -1.9272396000000e+00\r\n1557 1604 -1.3103950000000e+00\r\n1602 1604 -1.1792028000000e+00\r\n1603 1604 -1.4376079000000e+02\r\n1604 1604 -3.9087761000000e+01\r\n1605 1604  9.1712597000000e+00\r\n1606 1604  1.0042669000000e+01\r\n1608 1604 -1.3057448000000e+00\r\n1651 1604  1.3170317000000e+01\r\n1653 1604 -1.1567119000000e+00\r\n2709 1604 -2.2875832000000e+00\r\n499 1605  4.7071732000000e+00\r\n500 1605 -7.6251491000000e-01\r\n501 1605 -3.2578037000000e+00\r\n1557 1605 -2.2150898000000e+00\r\n1602 1605 -1.9933245000000e+00\r\n1603 1605 -2.4301308000000e+02\r\n1604 1605  3.7590468000000e+01\r\n1605 1605  1.5503089000000e+01\r\n1606 1605  1.6976116000000e+01\r\n1607 1605 -2.7499606000000e+00\r\n1608 1605 -2.2072296000000e+00\r\n1651 1605  2.2263089000000e+01\r\n1652 1605 -3.6063975000000e+00\r\n1653 1605 -1.9553045000000e+00\r\n2709 1605 -3.8669288000000e+00\r\n502 1606 -1.0819594000000e-03\r\n504 1606 -1.1291817000000e-05\r\n1558 1606 -8.6147983000000e-04\r\n1560 1606 -8.9907933000000e-06\r\n1603 1606 -7.9998062000000e-04\r\n1605 1606 -8.3489597000000e-06\r\n1606 1606  2.3233074000000e+02\r\n1608 1606  6.0306568000000e-04\r\n1609 1606 -1.5408543000000e-01\r\n1611 1606 -9.6579554000000e-06\r\n1654 1606 -1.3601395000000e-01\r\n1656 1606 -8.5524443000000e-06\r\n2710 1606 -1.9913327000000e-02\r\n2712 1606 -1.3258716000000e-05\r\n502 1607  5.1966535000000e+00\r\n504 1607 -1.6980784000000e+00\r\n1560 1607 -1.4451929000000e+00\r\n1605 1607 -1.3057448000000e+00\r\n1606 1607 -1.7083276000000e+02\r\n1607 1607 -4.4233502000000e+01\r\n1608 1607  9.2379422000000e+00\r\n1609 1607  1.1851465000000e+01\r\n1611 1607 -1.4681910000000e+00\r\n1654 1607  2.0530332000000e+01\r\n1656 1607 -1.3003019000000e+00\r\n2712 1607 -2.0154729000000e+00\r\n502 1608  8.7844231000000e+00\r\n503 1608 -1.4229619000000e+00\r\n504 1608 -2.8704318000000e+00\r\n1560 1608 -2.4429541000000e+00\r\n1605 1608 -2.2072296000000e+00\r\n1606 1608 -2.8877570000000e+02\r\n1607 1608  4.4762455000000e+01\r\n1608 1608  1.5615816000000e+01\r\n1609 1608  2.0033716000000e+01\r\n1610 1608 -3.2452005000000e+00\r\n1611 1608 -2.4818300000000e+00\r\n1654 1608  3.4704472000000e+01\r\n1655 1608 -5.6216716000000e+00\r\n1656 1608 -2.1980304000000e+00\r\n2712 1608 -3.4069554000000e+00\r\n505 1609 -2.6456252000000e-02\r\n507 1609 -1.0330459000000e-05\r\n1561 1609 -9.5421598000000e-04\r\n1563 1609 -9.9586297000000e-06\r\n1606 1609 -9.2540597000000e-04\r\n1608 1609 -9.6579554000000e-06\r\n1609 1609  2.5933862000000e+02\r\n1611 1609  6.6893971000000e-04\r\n1612 1609 -1.0266790000000e-01\r\n1614 1609 -1.0736130000000e-05\r\n1657 1609 -2.1242437000000e-01\r\n1659 1609 -1.0013213000000e-05\r\n2713 1609 -1.1620610000000e-03\r\n2715 1609 -1.2127795000000e-05\r\n505 1610  9.0270468000000e+00\r\n507 1610 -1.5257493000000e+00\r\n1563 1610 -1.5730491000000e+00\r\n1608 1610 -1.4681910000000e+00\r\n1609 1610 -1.9814194000000e+02\r\n1610 1610 -4.9379196000000e+01\r\n1611 1610  9.4479177000000e+00\r\n1612 1610  7.9992192000000e+00\r\n1614 1610 -1.5855539000000e+00\r\n1657 1610  3.2370162000000e+01\r\n1659 1610 -1.4790745000000e+00\r\n2715 1610 -1.8107620000000e+00\r\n505 1611  1.5259307000000e+01\r\n506 1611 -2.4717635000000e+00\r\n507 1611 -2.5791245000000e+00\r\n1563 1611 -2.6590806000000e+00\r\n1608 1611 -2.4818300000000e+00\r\n1609 1611 -3.3493888000000e+02\r\n1610 1611  5.1999266000000e+01\r\n1611 1611  1.5970750000000e+01\r\n1612 1611  1.3521870000000e+01\r\n1613 1611 -2.1903262000000e+00\r\n1614 1611 -2.6802181000000e+00\r\n1657 1611  5.4718480000000e+01\r\n1658 1611 -8.8635174000000e+00\r\n1659 1611 -2.5002256000000e+00\r\n2715 1611 -3.0609100000000e+00\r\n508 1612 -6.7715004000000e-02\r\n510 1612 -1.0068303000000e-05\r\n1564 1612 -9.8503287000000e-04\r\n1566 1612 -1.0280249000000e-05\r\n1609 1612 -1.0287145000000e-03\r\n1611 1612 -1.0736130000000e-05\r\n1612 1612  2.7021955000000e+02\r\n1614 1612  6.9634780000000e-04\r\n1615 1612 -1.0557024000000e-03\r\n1617 1612 -1.1017788000000e-05\r\n1660 1612 -3.6415174000000e-01\r\n1662 1612 -1.1100880000000e-05\r\n2716 1612 -1.1272357000000e-03\r\n2718 1612 -1.1764342000000e-05\r\n508 1613  1.3074018000000e+01\r\n510 1613 -1.4613155000000e+00\r\n1566 1613 -1.6091451000000e+00\r\n1611 1613 -1.5855539000000e+00\r\n1612 1613 -2.1305004000000e+02\r\n1613 1613 -5.1438365000000e+01\r\n1614 1613  9.6248333000000e+00\r\n1617 1613 -1.6186598000000e+00\r\n1660 1613  4.5035434000000e+01\r\n1662 1613 -1.6113632000000e+00\r\n2718 1613 -1.7330264000000e+00\r\n508 1614  2.2100320000000e+01\r\n509 1614 -3.5798534000000e+00\r\n510 1614 -2.4702077000000e+00\r\n1566 1614 -2.7200988000000e+00\r\n1611 1614 -2.6802181000000e+00\r\n1612 1614 -3.6013979000000e+02\r\n1613 1614  5.5982322000000e+01\r\n1614 1614  1.6269814000000e+01\r\n1617 1614 -2.7361804000000e+00\r\n1660 1614  7.6127896000000e+01\r\n1661 1614 -1.2331347000000e+01\r\n1662 1614 -2.7238483000000e+00\r\n2718 1614 -2.9295078000000e+00\r\n511 1615 -3.1451497000000e-02\r\n513 1615 -9.9726638000000e-06\r\n1567 1615 -9.7935191000000e-04\r\n1569 1615 -1.0220960000000e-05\r\n1612 1615 -4.3788619000000e-02\r\n1614 1615 -1.1017788000000e-05\r\n1615 1615  2.7009141000000e+02\r\n1617 1615  6.9600893000000e-04\r\n1618 1615 -1.0320963000000e-03\r\n1620 1615 -1.0771424000000e-05\r\n1663 1615 -2.2408230000000e-01\r\n1665 1615 -1.0960101000000e-05\r\n2719 1615 -1.1200582000000e-03\r\n2721 1615 -1.1689435000000e-05\r\n511 1616  9.5237157000000e+00\r\n513 1616 -1.4651993000000e+00\r\n1569 1616 -1.6082163000000e+00\r\n1612 1616  5.7618926000000e+00\r\n1614 1616 -1.6186598000000e+00\r\n1615 1616 -2.0458147000000e+02\r\n1616 1616 -5.1433248000000e+01\r\n1617 1616  9.6644380000000e+00\r\n1620 1616 -1.6184823000000e+00\r\n1663 1616  3.4348042000000e+01\r\n1665 1616 -1.6104571000000e+00\r\n2721 1616 -1.7376559000000e+00\r\n511 1617  1.6098875000000e+01\r\n512 1617 -2.6077513000000e+00\r\n513 1617 -2.4767708000000e+00\r\n1569 1617 -2.7185272000000e+00\r\n1612 1617  9.7398956000000e+00\r\n1613 1617 -1.5777018000000e+00\r\n1614 1617 -2.7361804000000e+00\r\n1615 1617 -3.4582425000000e+02\r\n1616 1617  5.3676628000000e+01\r\n1617 1617  1.6336756000000e+01\r\n1620 1617 -2.7358825000000e+00\r\n1663 1617  5.8061886000000e+01\r\n1664 1617 -9.4050628000000e+00\r\n1665 1617 -2.7223145000000e+00\r\n2721 1617 -2.9373322000000e+00\r\n514 1618 -9.4927803000000e-04\r\n516 1618 -9.9070950000000e-06\r\n1570 1618 -9.6610888000000e-04\r\n1572 1618 -1.0082749000000e-05\r\n1615 1618 -9.8287232000000e-02\r\n1617 1618 -1.0771424000000e-05\r\n1618 1618  2.7003821000000e+02\r\n1620 1618  6.9496775000000e-04\r\n1621 1618 -1.0100503000000e-03\r\n1623 1618 -1.0541342000000e-05\r\n1666 1618 -1.2446857000000e-01\r\n1668 1618 -1.0709992000000e-05\r\n2722 1618 -1.6260742000000e-02\r\n2724 1618 -1.1586719000000e-05\r\n514 1619  5.8398884000000e+00\r\n516 1619 -1.4678694000000e+00\r\n1572 1619 -1.6085433000000e+00\r\n1615 1619  1.0345519000000e+01\r\n1617 1619 -1.6184823000000e+00\r\n1618 1619 -1.9723158000000e+02\r\n1619 1619 -5.1426699000000e+01\r\n1620 1619  9.6690332000000e+00\r\n1623 1619 -1.6180395000000e+00\r\n1666 1619  2.6089067000000e+01\r\n1668 1619 -1.6094869000000e+00\r\n2724 1619 -1.7408475000000e+00\r\n514 1620  9.8717472000000e+00\r\n515 1620 -1.5990822000000e+00\r\n516 1620 -2.4812864000000e+00\r\n1572 1620 -2.7190816000000e+00\r\n1615 1620  1.7488065000000e+01\r\n1616 1620 -2.8328170000000e+00\r\n1617 1620 -2.7358825000000e+00\r\n1618 1620 -3.3340025000000e+02\r\n1619 1620  5.1680985000000e+01\r\n1620 1620  1.6344532000000e+01\r\n1623 1620 -2.7351320000000e+00\r\n1666 1620  4.4100959000000e+01\r\n1667 1620 -7.1437259000000e+00\r\n1668 1620 -2.7206767000000e+00\r\n2724 1620 -2.9427286000000e+00\r\n517 1621 -9.2465410000000e-04\r\n519 1621 -9.6501086000000e-06\r\n1573 1621 -9.5074694000000e-04\r\n1575 1621 -9.9224252000000e-06\r\n1618 1621 -1.2181232000000e-01\r\n1620 1621 -1.0541342000000e-05\r\n1621 1621  2.7003369000000e+02\r\n1623 1621  6.9347917000000e-04\r\n1624 1621 -9.7504882000000e-04\r\n1626 1621 -1.0176051000000e-05\r\n1669 1621 -7.9817295000000e-02\r\n1671 1621 -1.0486731000000e-05\r\n2725 1621 -3.0551219000000e-02\r\n2727 1621 -1.1345441000000e-05\r\n517 1622  3.6187819000000e+00\r\n519 1622 -1.4681648000000e+00\r\n1575 1622 -1.6085332000000e+00\r\n1618 1622  9.5462132000000e+00\r\n1620 1622 -1.6180395000000e+00\r\n1621 1622 -1.8982629000000e+02\r\n1622 1622 -5.1424648000000e+01\r\n1623 1622  9.6365862000000e+00\r\n1626 1622 -1.5848009000000e+00\r\n1669 1622  2.1701004000000e+01\r\n1671 1622 -1.6099108000000e+00\r\n2727 1622 -1.7413736000000e+00\r\n517 1623  6.1171845000000e+00\r\n518 1623 -9.9091094000000e-01\r\n519 1623 -2.4817839000000e+00\r\n1575 1623 -2.7190631000000e+00\r\n1618 1623  1.6136907000000e+01\r\n1619 1623 -2.6139865000000e+00\r\n1620 1623 -2.7351320000000e+00\r\n1621 1623 -3.2088212000000e+02\r\n1622 1623  4.9659240000000e+01\r\n1623 1623  1.6289676000000e+01\r\n1626 1623 -2.6789474000000e+00\r\n1669 1623  3.6683350000000e+01\r\n1670 1623 -5.9422651000000e+00\r\n1671 1623 -2.7213913000000e+00\r\n2727 1623 -2.9436164000000e+00\r\n520 1624 -9.4686439000000e-04\r\n522 1624 -9.8819052000000e-06\r\n1576 1624 -8.8695501000000e-04\r\n1578 1624 -9.2566637000000e-06\r\n1621 1624 -1.0010991000000e-01\r\n1623 1624 -1.0176051000000e-05\r\n1624 1624  2.5920303000000e+02\r\n1626 1624  6.5708136000000e-04\r\n1672 1624 -5.8725439000000e-02\r\n1674 1624 -1.0028607000000e-05\r\n2728 1624 -3.6772028000000e-02\r\n2730 1624 -1.1644704000000e-05\r\n520 1625  2.6940643000000e+00\r\n522 1625 -1.5292250000000e+00\r\n1578 1625 -1.5287703000000e+00\r\n1621 1625  6.2274337000000e+00\r\n1623 1625 -1.5848009000000e+00\r\n1624 1625 -1.7666489000000e+02\r\n1625 1625 -4.9368903000000e+01\r\n1626 1625  8.0239023000000e+00\r\n1672 1625  1.8983067000000e+01\r\n1674 1625 -1.5621015000000e+00\r\n2730 1625 -1.8134713000000e+00\r\n520 1626  4.5540463000000e+00\r\n521 1626 -7.3770750000000e-01\r\n522 1626 -2.5850020000000e+00\r\n1578 1626 -2.5842333000000e+00\r\n1621 1626  1.0526854000000e+01\r\n1622 1626 -1.7052394000000e+00\r\n1623 1626 -2.6789474000000e+00\r\n1624 1626 -2.9863434000000e+02\r\n1625 1626  4.6145579000000e+01\r\n1626 1626  1.3563604000000e+01\r\n1672 1626  3.2088976000000e+01\r\n1673 1626 -5.1980760000000e+00\r\n1674 1626 -2.6405763000000e+00\r\n2730 1626 -3.0654918000000e+00\r\n1627 1627  1.0000000000000e+00\r\n1628 1628  1.0000000000000e+00\r\n1629 1629  1.0000000000000e+00\r\n1630 1630  1.0000000000000e+00\r\n1631 1631  1.0000000000000e+00\r\n1632 1632  1.0000000000000e+00\r\n1633 1633  1.0000000000000e+00\r\n1634 1634  1.0000000000000e+00\r\n1635 1635  1.0000000000000e+00\r\n1636 1636  1.0000000000000e+00\r\n1637 1637  1.0000000000000e+00\r\n1638 1638  1.0000000000000e+00\r\n1639 1639  1.0000000000000e+00\r\n1640 1640  1.0000000000000e+00\r\n1641 1641  1.0000000000000e+00\r\n1642 1642  1.0000000000000e+00\r\n1643 1643  1.0000000000000e+00\r\n1644 1644  1.0000000000000e+00\r\n541 1645 -1.6444165000000e-03\r\n543 1645 -1.7161875000000e-05\r\n1597 1645 -4.3774437000000e-03\r\n1599 1645 -5.9180924000000e-06\r\n1645 1645  1.4578467000000e+02\r\n1647 1645  3.9539125000000e-04\r\n1648 1645 -5.2525336000000e-02\r\n1650 1645 -5.8435869000000e-06\r\n1693 1645 -1.6373276000000e-03\r\n1695 1645 -5.2194194000000e-06\r\n2749 1645 -4.8402572000000e-02\r\n2751 1645 -2.0336349000000e-05\r\n541 1646  1.0288629000000e+00\r\n543 1646 -2.6992882000000e+00\r\n1599 1646 -9.3182338000000e-01\r\n1645 1646 -9.1799685000000e+01\r\n1646 1646 -2.7783778000000e+01\r\n1647 1646  8.5786460000000e+00\r\n1648 1646  4.2579789000000e+00\r\n1650 1646 -9.2019439000000e-01\r\n1693 1646  2.8539434000000e+00\r\n1695 1646 -8.2194276000000e-01\r\n2751 1646 -3.2022787000000e+00\r\n541 1647  1.7391889000000e+00\r\n542 1647 -2.8173234000000e-01\r\n543 1647 -4.5628743000000e+00\r\n1599 1647 -1.5751531000000e+00\r\n1645 1647 -1.5517811000000e+02\r\n1646 1647  2.3849486000000e+01\r\n1647 1647  1.4501334000000e+01\r\n1648 1647  7.1976838000000e+00\r\n1649 1647 -1.1659574000000e+00\r\n1650 1647 -1.5554957000000e+00\r\n1693 1647  4.8243035000000e+00\r\n1694 1647 -7.8149195000000e-01\r\n1695 1647 -1.3894113000000e+00\r\n2751 1647 -5.4131281000000e+00\r\n544 1648 -1.5090144000000e-03\r\n546 1648 -1.5748757000000e-05\r\n1600 1648 -6.2560088000000e-04\r\n1602 1648 -6.5290539000000e-06\r\n1645 1648 -5.5992081000000e-04\r\n1647 1648 -5.8435869000000e-06\r\n1648 1648  1.6202622000000e+02\r\n1650 1648  4.3815254000000e-04\r\n1651 1648 -1.0683496000000e-01\r\n1653 1648 -6.6625540000000e-06\r\n1696 1648 -1.2933066000000e-02\r\n1698 1648 -5.9343868000000e-06\r\n2752 1648 -4.2824486000000e-02\r\n2754 1648 -1.8637995000000e-05\r\n544 1649  1.8112808000000e+00\r\n546 1649 -2.4314260000000e+00\r\n1602 1649 -1.0425703000000e+00\r\n1647 1649 -9.2019439000000e-01\r\n1648 1649 -1.0877024000000e+02\r\n1649 1649 -3.0872090000000e+01\r\n1650 1649  9.2324532000000e+00\r\n1651 1649  8.8405414000000e+00\r\n1653 1649 -1.0313028000000e+00\r\n1696 1649  5.1659370000000e+00\r\n1698 1649 -9.1863870000000e-01\r\n2754 1649 -2.8848554000000e+00\r\n544 1650  3.0617890000000e+00\r\n545 1650 -4.9597554000000e-01\r\n546 1650 -4.1100826000000e+00\r\n1602 1650 -1.7623608000000e+00\r\n1647 1650 -1.5554957000000e+00\r\n1648 1650 -1.8386522000000e+02\r\n1649 1650  2.8349994000000e+01\r\n1650 1650  1.5606538000000e+01\r\n1651 1650  1.4944051000000e+01\r\n1652 1650 -2.4207689000000e+00\r\n1653 1650 -1.7433142000000e+00\r\n1696 1650  8.7324999000000e+00\r\n1697 1650 -1.4145672000000e+00\r\n1698 1650 -1.5528669000000e+00\r\n2754 1650 -4.8765596000000e+00\r\n547 1651 -1.3821334000000e-03\r\n549 1651 -1.4424569000000e-05\r\n1603 1651 -7.0858084000000e-04\r\n1605 1651 -7.3950702000000e-06\r\n1648 1651 -6.3839260000000e-04\r\n1650 1651 -6.6625540000000e-06\r\n1651 1651  1.8368970000000e+02\r\n1653 1651  4.8940519000000e-04\r\n1654 1651 -1.9026575000000e-01\r\n1656 1651 -7.7383422000000e-06\r\n1699 1651 -3.0179617000000e-02\r\n1701 1651 -6.8637821000000e-06\r\n2755 1651 -2.7383811000000e-02\r\n2757 1651 -1.7008204000000e-05\r\n547 1652  4.0665688000000e+00\r\n549 1652 -2.1501943000000e+00\r\n1605 1652 -1.1567119000000e+00\r\n1650 1652 -1.0313028000000e+00\r\n1651 1652 -1.3193041000000e+02\r\n1652 1652 -3.4991172000000e+01\r\n1653 1652  9.0855690000000e+00\r\n1654 1652  1.4042325000000e+01\r\n1656 1652 -1.1612148000000e+00\r\n1699 1652  8.4795271000000e+00\r\n1701 1652 -1.0300719000000e+00\r\n2757 1652 -2.5521445000000e+00\r\n547 1653  6.8741223000000e+00\r\n548 1653 -1.1135093000000e+00\r\n549 1653 -3.6346854000000e+00\r\n1605 1653 -1.9553045000000e+00\r\n1650 1653 -1.7433142000000e+00\r\n1651 1653 -2.2301501000000e+02\r\n1652 1653  3.4492949000000e+01\r\n1653 1653  1.5358235000000e+01\r\n1654 1653  2.3737128000000e+01\r\n1655 1653 -3.8450744000000e+00\r\n1656 1653 -1.9629160000000e+00\r\n1699 1653  1.4333783000000e+01\r\n1700 1653 -2.3218674000000e+00\r\n1701 1653 -1.7412321000000e+00\r\n2757 1653 -4.3141417000000e+00\r\n550 1654 -3.3803668000000e-02\r\n552 1654 -1.3399561000000e-05\r\n1606 1654 -8.1947810000000e-04\r\n1608 1654 -8.5524443000000e-06\r\n1651 1654 -7.4147247000000e-04\r\n1653 1654 -7.7383422000000e-06\r\n1654 1654  2.0530217000000e+02\r\n1656 1654  5.4275019000000e-04\r\n1657 1654 -1.9002003000000e-01\r\n1659 1654 -9.1776761000000e-06\r\n1702 1654 -5.7100965000000e-02\r\n1704 1654 -8.2919913000000e-06\r\n2758 1654 -1.5092283000000e-03\r\n2760 1654 -1.5750990000000e-05\r\n550 1655  9.7233247000000e+00\r\n552 1655 -1.9272400000000e+00\r\n1608 1655 -1.3003019000000e+00\r\n1653 1655 -1.1612148000000e+00\r\n1654 1655 -1.6066937000000e+02\r\n1655 1655 -3.9109356000000e+01\r\n1656 1655  9.1921782000000e+00\r\n1657 1655  1.8701559000000e+01\r\n1659 1655 -1.3200215000000e+00\r\n1702 1655  1.4512037000000e+01\r\n1704 1655 -1.1927259000000e+00\r\n2760 1655 -2.2862821000000e+00\r\n550 1656  1.6436308000000e+01\r\n551 1656 -2.6623687000000e+00\r\n552 1656 -3.2578065000000e+00\r\n1608 1656 -2.1980304000000e+00\r\n1653 1656 -1.9629160000000e+00\r\n1654 1656 -2.7159550000000e+02\r\n1655 1656  4.2164769000000e+01\r\n1656 1656  1.5538456000000e+01\r\n1657 1656  3.1613115000000e+01\r\n1658 1656 -5.1207224000000e+00\r\n1659 1656 -2.2313643000000e+00\r\n1702 1656  2.4531147000000e+01\r\n1703 1656 -3.9735786000000e+00\r\n1704 1656 -2.0161839000000e+00\r\n2760 1656 -3.8647313000000e+00\r\n553 1657 -1.4724815000000e-01\r\n555 1657 -1.2115562000000e-05\r\n1609 1657 -9.5944604000000e-04\r\n1611 1657 -1.0013213000000e-05\r\n1654 1657 -8.7938657000000e-04\r\n1656 1657 -9.1776761000000e-06\r\n1657 1657  2.3794610000000e+02\r\n1659 1657  6.2205494000000e-04\r\n1660 1657 -2.2289853000000e-01\r\n1662 1657 -1.1041321000000e-05\r\n1705 1657 -1.9544122000000e-01\r\n1707 1657 -9.9884456000000e-06\r\n2761 1657 -1.3508199000000e-03\r\n2763 1657 -1.4097767000000e-05\r\n553 1658  2.0895887000000e+01\r\n555 1658 -1.6625969000000e+00\r\n1611 1658 -1.4790745000000e+00\r\n1656 1658 -1.3200215000000e+00\r\n1657 1658 -2.0170899000000e+02\r\n1658 1658 -4.5295405000000e+01\r\n1659 1658  9.3258634000000e+00\r\n1660 1658  1.6827796000000e+01\r\n1662 1658 -1.5150411000000e+00\r\n1705 1658  2.7679249000000e+01\r\n1707 1658 -1.3707856000000e+00\r\n2763 1658 -1.9732535000000e+00\r\n553 1659  3.5322382000000e+01\r\n554 1659 -5.7213681000000e+00\r\n555 1659 -2.8104518000000e+00\r\n1611 1659 -2.5002256000000e+00\r\n1656 1659 -2.2313643000000e+00\r\n1657 1659 -3.4096864000000e+02\r\n1658 1659  5.3084456000000e+01\r\n1659 1659  1.5764430000000e+01\r\n1660 1659  2.8445687000000e+01\r\n1661 1659 -4.6075103000000e+00\r\n1662 1659 -2.5610236000000e+00\r\n1705 1659  4.6788972000000e+01\r\n1706 1659 -7.5786762000000e+00\r\n1707 1659 -2.3171744000000e+00\r\n2763 1659 -3.3355854000000e+00\r\n556 1660 -3.1161847000000e-01\r\n558 1660 -1.1064451000000e-05\r\n1612 1660 -1.0636641000000e-03\r\n1614 1660 -1.1100880000000e-05\r\n1657 1660 -1.0579573000000e-03\r\n1659 1660 -1.1041321000000e-05\r\n1660 1660  2.7055967000000e+02\r\n1662 1660  7.0111889000000e-04\r\n1663 1660 -1.1344195000000e-03\r\n1665 1660 -1.1839315000000e-05\r\n1708 1660 -4.9982639000000e-01\r\n1710 1660 -1.1934851000000e-05\r\n2764 1660 -1.2195763000000e-03\r\n2766 1660 -1.2728050000000e-05\r\n556 1661  3.7096615000000e+01\r\n558 1661 -1.4650651000000e+00\r\n1614 1661 -1.6113632000000e+00\r\n1659 1661 -1.5150411000000e+00\r\n1660 1661 -2.5296939000000e+02\r\n1661 1661 -5.1474670000000e+01\r\n1662 1661  9.5348012000000e+00\r\n1665 1661 -1.6191856000000e+00\r\n1708 1661  6.0983824000000e+01\r\n1710 1661 -1.5804774000000e+00\r\n2766 1661 -1.7378832000000e+00\r\n556 1662  6.2708117000000e+01\r\n557 1662 -1.0156920000000e+01\r\n558 1662 -2.4765460000000e+00\r\n1614 1662 -2.7238483000000e+00\r\n1659 1662 -2.5610236000000e+00\r\n1660 1662 -4.2761945000000e+02\r\n1661 1662  6.6818708000000e+01\r\n1662 1662  1.6117624000000e+01\r\n1665 1662 -2.7370696000000e+00\r\n1708 1662  1.0308706000000e+02\r\n1709 1662 -1.6697151000000e+01\r\n1710 1662 -2.6716390000000e+00\r\n2766 1662 -2.9377177000000e+00\r\n559 1663 -1.3855821000000e-01\r\n561 1663 -1.0693079000000e-05\r\n1615 1663 -1.0501750000000e-03\r\n1617 1663 -1.0960101000000e-05\r\n1660 1663 -1.8446945000000e-01\r\n1662 1663 -1.1839315000000e-05\r\n1663 1663  2.7028462000000e+02\r\n1665 1663  7.0049918000000e-04\r\n1666 1663 -1.0916982000000e-03\r\n1668 1663 -1.1393456000000e-05\r\n1711 1663 -2.0698907000000e-01\r\n1713 1663 -1.1803048000000e-05\r\n2767 1663 -1.1897661000000e-03\r\n2769 1663 -1.2416937000000e-05\r\n559 1664  2.0050906000000e+01\r\n561 1664 -1.4625411000000e+00\r\n1617 1664 -1.6104571000000e+00\r\n1660 1664  1.6483139000000e+01\r\n1662 1664 -1.6191856000000e+00\r\n1663 1664 -2.2180181000000e+02\r\n1664 1664 -5.1467914000000e+01\r\n1665 1664  9.6658244000000e+00\r\n1668 1664 -1.6189908000000e+00\r\n1711 1664  3.0368874000000e+01\r\n1713 1664 -1.6144318000000e+00\r\n2769 1664 -1.7344354000000e+00\r\n559 1665  3.3894031000000e+01\r\n560 1665 -5.4899961000000e+00\r\n561 1665 -2.4722779000000e+00\r\n1617 1665 -2.7223145000000e+00\r\n1660 1665  2.7863080000000e+01\r\n1661 1665 -4.5131313000000e+00\r\n1662 1665 -2.7370696000000e+00\r\n1663 1665 -3.7493354000000e+02\r\n1664 1665  5.8303482000000e+01\r\n1665 1665  1.6339100000000e+01\r\n1668 1665 -2.7367420000000e+00\r\n1711 1665  5.1335512000000e+01\r\n1712 1665 -8.3150859000000e+00\r\n1713 1665 -2.7290339000000e+00\r\n2769 1665 -2.9318876000000e+00\r\n562 1666 -3.4524809000000e-02\r\n564 1666 -1.0286721000000e-05\r\n1618 1666 -1.0262100000000e-03\r\n1620 1666 -1.0709992000000e-05\r\n1663 1666 -1.9838020000000e-01\r\n1665 1666 -1.1393456000000e-05\r\n1666 1666  2.7011203000000e+02\r\n1668 1666  6.9824186000000e-04\r\n1669 1666 -1.0595532000000e-03\r\n1671 1666 -1.1057976000000e-05\r\n1714 1666 -1.1455620000000e-01\r\n1716 1666 -1.1360162000000e-05\r\n2770 1666 -1.1553500000000e-03\r\n2772 1666 -1.2057755000000e-05\r\n562 1667  9.8107963000000e+00\r\n564 1667 -1.4617749000000e+00\r\n1620 1667 -1.6094869000000e+00\r\n1663 1667  1.8634428000000e+01\r\n1665 1667 -1.6189908000000e+00\r\n1666 1667 -2.0385159000000e+02\r\n1667 1667 -5.1459003000000e+01\r\n1668 1667  9.6625734000000e+00\r\n1671 1667 -1.6185609000000e+00\r\n1714 1667  2.0494516000000e+01\r\n1716 1667 -1.6143877000000e+00\r\n2772 1667 -1.7335935000000e+00\r\n562 1668  1.6584170000000e+01\r\n563 1668 -2.6862973000000e+00\r\n564 1668 -2.4709843000000e+00\r\n1620 1668 -2.7206767000000e+00\r\n1663 1668  3.1499637000000e+01\r\n1664 1668 -5.1022988000000e+00\r\n1665 1668 -2.7367420000000e+00\r\n1666 1668 -3.4459073000000e+02\r\n1667 1668  5.3412258000000e+01\r\n1668 1668  1.6333612000000e+01\r\n1671 1668 -2.7360136000000e+00\r\n1714 1668  3.4643930000000e+01\r\n1715 1668 -5.6116100000000e+00\r\n1716 1668 -2.7289610000000e+00\r\n2772 1668 -2.9304664000000e+00\r\n565 1669 -9.6823731000000e-04\r\n567 1669 -1.0104963000000e-05\r\n1621 1669 -1.0048176000000e-03\r\n1623 1669 -1.0486731000000e-05\r\n1666 1669 -1.6675602000000e-01\r\n1668 1669 -1.1057976000000e-05\r\n1669 1669  2.7004389000000e+02\r\n1671 1669  6.9663137000000e-04\r\n1672 1669 -1.0295369000000e-03\r\n1674 1669 -1.0744713000000e-05\r\n1717 1669 -8.7898661000000e-02\r\n1719 1669 -1.1036116000000e-05\r\n2773 1669 -1.9894113000000e-02\r\n2775 1669 -1.1840431000000e-05\r\n565 1670  5.2180375000000e+00\r\n567 1670 -1.4611605000000e+00\r\n1623 1670 -1.6099108000000e+00\r\n1666 1670  1.3966226000000e+01\r\n1668 1670 -1.6185609000000e+00\r\n1669 1670 -1.9120414000000e+02\r\n1670 1670 -5.1454603000000e+01\r\n1671 1670  9.6458946000000e+00\r\n1674 1670 -1.6020081000000e+00\r\n1717 1670  1.7101421000000e+01\r\n1719 1670 -1.6155050000000e+00\r\n2775 1670 -1.7329727000000e+00\r\n565 1671  8.8205643000000e+00\r\n566 1671 -1.4287813000000e+00\r\n567 1671 -2.4699439000000e+00\r\n1623 1671 -2.7213913000000e+00\r\n1666 1671  2.3608493000000e+01\r\n1667 1671 -3.8241739000000e+00\r\n1668 1671 -2.7360136000000e+00\r\n1669 1671 -3.2321126000000e+02\r\n1670 1671  4.9961416000000e+01\r\n1671 1671  1.6305411000000e+01\r\n1674 1671 -2.7080345000000e+00\r\n1717 1671  2.8908223000000e+01\r\n1718 1671 -4.6826404000000e+00\r\n1719 1671 -2.7308478000000e+00\r\n2775 1671 -2.9294150000000e+00\r\n568 1672 -9.6550868000000e-04\r\n570 1672 -1.0076485000000e-05\r\n1624 1672 -9.6092110000000e-04\r\n1626 1672 -1.0028607000000e-05\r\n1669 1672 -1.2038901000000e-01\r\n1671 1672 -1.0744713000000e-05\r\n1672 1672  2.6457226000000e+02\r\n1674 1672  6.7214879000000e-04\r\n1720 1672 -4.7733116000000e-02\r\n1722 1672 -1.0724002000000e-05\r\n2776 1672 -3.0770786000000e-02\r\n2778 1672 -1.1852882000000e-05\r\n568 1673  3.5314347000000e+00\r\n570 1673 -1.4901284000000e+00\r\n1626 1673 -1.5621015000000e+00\r\n1669 1673  8.4202293000000e+00\r\n1671 1673 -1.6020081000000e+00\r\n1672 1673 -1.7582806000000e+02\r\n1673 1673 -5.0425341000000e+01\r\n1674 1673  8.0261255000000e+00\r\n1720 1673  1.2055848000000e+01\r\n1722 1673 -1.5990651000000e+00\r\n2778 1673 -1.7671616000000e+00\r\n568 1674  5.9695372000000e+00\r\n569 1674 -9.6697473000000e-01\r\n570 1674 -2.5189130000000e+00\r\n1626 1674 -2.6405763000000e+00\r\n1669 1674  1.4233556000000e+01\r\n1670 1674 -2.3056207000000e+00\r\n1671 1674 -2.7080345000000e+00\r\n1672 1674 -2.9721975000000e+02\r\n1673 1674  4.5800144000000e+01\r\n1674 1674  1.3567363000000e+01\r\n1720 1674  2.0379205000000e+01\r\n1721 1674 -3.3011229000000e+00\r\n1722 1674 -2.7030597000000e+00\r\n2778 1674 -2.9872100000000e+00\r\n1675 1675  1.0000000000000e+00\r\n1676 1676  1.0000000000000e+00\r\n1677 1677  1.0000000000000e+00\r\n1678 1678  1.0000000000000e+00\r\n1679 1679  1.0000000000000e+00\r\n1680 1680  1.0000000000000e+00\r\n1681 1681  1.0000000000000e+00\r\n1682 1682  1.0000000000000e+00\r\n1683 1683  1.0000000000000e+00\r\n1684 1684  1.0000000000000e+00\r\n1685 1685  1.0000000000000e+00\r\n1686 1686  1.0000000000000e+00\r\n1687 1687  1.0000000000000e+00\r\n1688 1688  1.0000000000000e+00\r\n1689 1689  1.0000000000000e+00\r\n586 1690 -2.2242274000000e-03\r\n588 1690 -2.3213044000000e-05\r\n1690 1690  1.0797413000000e+02\r\n1692 1690  3.1185895000000e-04\r\n1693 1690 -1.3479570000000e-02\r\n1695 1690 -4.5005320000000e-06\r\n1738 1690 -3.9297606000000e-04\r\n1740 1690 -4.1012760000000e-06\r\n2794 1690 -5.2332926000000e-02\r\n2796 1690 -2.7518009000000e-05\r\n586 1691  5.3852628000000e-01\r\n588 1691 -3.6425216000000e+00\r\n1690 1691 -6.4387337000000e+01\r\n1691 1691 -1.8888764000000e+01\r\n1692 1691  9.3186480000000e+00\r\n1693 1691  1.8825568000000e+00\r\n1695 1691 -7.0652571000000e-01\r\n1740 1691 -6.4747945000000e-01\r\n2796 1691 -4.3198103000000e+00\r\n586 1692  9.1032483000000e-01\r\n587 1692 -1.4746373000000e-01\r\n588 1692 -6.1573185000000e+00\r\n1690 1692 -1.0884036000000e+02\r\n1691 1692  1.9535090000000e+01\r\n1692 1692  1.5752243000000e+01\r\n1693 1692  3.1822740000000e+00\r\n1694 1692 -5.1549731000000e-01\r\n1695 1692 -1.1943111000000e+00\r\n1740 1692 -1.0944993000000e+00\r\n2796 1692 -7.3022073000000e+00\r\n589 1693 -1.8738628000000e-03\r\n591 1693 -1.9556480000000e-05\r\n1645 1693 -5.0011433000000e-04\r\n1647 1693 -5.2194194000000e-06\r\n1690 1693 -4.3123198000000e-04\r\n1692 1693 -4.5005320000000e-06\r\n1693 1693  1.2959451000000e+02\r\n1695 1693  3.6533244000000e-04\r\n1696 1693 -5.6913742000000e-02\r\n1698 1693 -5.2950538000000e-06\r\n1741 1693 -4.3554724000000e-04\r\n1743 1693 -4.5455680000000e-06\r\n2797 1693 -4.9675742000000e-02\r\n2799 1693 -2.3182994000000e-05\r\n589 1694  8.7410339000000e-01\r\n591 1694 -3.0369940000000e+00\r\n1647 1694 -8.2194276000000e-01\r\n1692 1694 -7.0652571000000e-01\r\n1693 1694 -8.0993831000000e+01\r\n1694 1694 -2.4701508000000e+01\r\n1695 1694  9.7001595000000e+00\r\n1696 1694  5.5783043000000e+00\r\n1698 1694 -8.2297257000000e-01\r\n1741 1694  1.8469536000000e-01\r\n1743 1694 -7.0596904000000e-01\r\n2799 1694 -3.6029813000000e+00\r\n589 1695  1.4775837000000e+00\r\n590 1695 -2.3935269000000e-01\r\n591 1695 -5.1337324000000e+00\r\n1647 1695 -1.3894113000000e+00\r\n1692 1695 -1.1943111000000e+00\r\n1693 1695 -1.3691191000000e+02\r\n1694 1695  2.1021639000000e+01\r\n1695 1695  1.6397142000000e+01\r\n1696 1695  9.4295614000000e+00\r\n1697 1695 -1.5274876000000e+00\r\n1698 1695 -1.3911522000000e+00\r\n1741 1695  3.1220889000000e-01\r\n1742 1695 -5.0574491000000e-02\r\n1743 1695 -1.1933695000000e+00\r\n2799 1695 -6.0904761000000e+00\r\n592 1696 -1.7108231000000e-03\r\n594 1696 -1.7854924000000e-05\r\n1648 1696 -5.6862107000000e-04\r\n1650 1696 -5.9343868000000e-06\r\n1693 1696 -5.0736147000000e-04\r\n1695 1696 -5.2950538000000e-06\r\n1696 1696  1.4582182000000e+02\r\n1698 1696  4.0265233000000e-04\r\n1699 1696 -1.0932543000000e-01\r\n1701 1696 -6.0680834000000e-06\r\n1744 1696 -5.2222217000000e-04\r\n1746 1696 -5.4501468000000e-06\r\n2800 1696 -4.2453271000000e-02\r\n2802 1696 -2.1133029000000e-05\r\n592 1697  1.8863610000000e+00\r\n594 1697 -2.7015410000000e+00\r\n1650 1697 -9.1863870000000e-01\r\n1695 1697 -8.2297257000000e-01\r\n1696 1697 -9.7152630000000e+01\r\n1697 1697 -2.7792393000000e+01\r\n1698 1697  9.3935802000000e+00\r\n1699 1697  1.0289578000000e+01\r\n1701 1697 -9.2035445000000e-01\r\n1744 1697  1.3299976000000e+00\r\n1746 1697 -8.2190450000000e-01\r\n2802 1697 -3.2050468000000e+00\r\n592 1698  3.1887047000000e+00\r\n593 1698 -5.1652764000000e-01\r\n594 1698 -4.5666848000000e+00\r\n1650 1698 -1.5528669000000e+00\r\n1695 1698 -1.3911522000000e+00\r\n1696 1698 -1.6422681000000e+02\r\n1697 1698  2.5293396000000e+01\r\n1698 1698  1.5878907000000e+01\r\n1699 1698  1.7393503000000e+01\r\n1700 1698 -2.8175155000000e+00\r\n1701 1698 -1.5557672000000e+00\r\n1744 1698  2.2482280000000e+00\r\n1745 1698 -3.6418296000000e-01\r\n1746 1698 -1.3893474000000e+00\r\n2802 1698 -5.4178110000000e+00\r\n595 1699 -1.6091390000000e-03\r\n597 1699 -1.6793702000000e-05\r\n1651 1699 -6.5767387000000e-04\r\n1653 1699 -6.8637821000000e-06\r\n1696 1699 -5.8143161000000e-04\r\n1698 1699 -6.0680834000000e-06\r\n1699 1699  1.6206276000000e+02\r\n1701 1699  4.4204789000000e-04\r\n1702 1699 -1.9328197000000e-01\r\n1704 1699 -7.2681221000000e-06\r\n1747 1699 -6.1959745000000e-04\r\n1749 1699 -6.4663993000000e-06\r\n2803 1699 -1.9960069000000e-02\r\n2805 1699 -1.9781345000000e-05\r\n595 1700  5.2167878000000e+00\r\n597 1700 -2.4309664000000e+00\r\n1653 1700 -1.0300719000000e+00\r\n1698 1700 -9.2035445000000e-01\r\n1699 1700 -1.1684341000000e+02\r\n1700 1700 -3.0885659000000e+01\r\n1701 1700  9.2656855000000e+00\r\n1702 1700  1.6984846000000e+01\r\n1704 1700 -1.0598049000000e+00\r\n1747 1700  1.7085869000000e+00\r\n1749 1700 -9.3682947000000e-01\r\n2805 1700 -2.8841868000000e+00\r\n595 1701  8.8184523000000e+00\r\n596 1701 -1.4284351000000e+00\r\n597 1701 -4.1093030000000e+00\r\n1653 1701 -1.7412321000000e+00\r\n1698 1701 -1.5557672000000e+00\r\n1699 1701 -1.9751197000000e+02\r\n1700 1701  3.0525937000000e+01\r\n1701 1701  1.5662705000000e+01\r\n1702 1701  2.8711166000000e+01\r\n1703 1701 -4.6507071000000e+00\r\n1704 1701 -1.7914930000000e+00\r\n1747 1701  2.8881934000000e+00\r\n1748 1701 -4.6783688000000e-01\r\n1749 1701 -1.5836155000000e+00\r\n2805 1701 -4.8754260000000e+00\r\n598 1702 -8.2984683000000e-02\r\n600 1702 -1.4670850000000e-05\r\n1654 1702 -7.9452202000000e-04\r\n1656 1702 -8.2919913000000e-06\r\n1699 1702 -6.9641692000000e-04\r\n1701 1702 -7.2681221000000e-06\r\n1702 1702  1.9459037000000e+02\r\n1704 1702  5.1894309000000e-04\r\n1705 1702 -2.9625002000000e-01\r\n1707 1702 -8.9874061000000e-06\r\n1750 1702 -7.6037108000000e-04\r\n1752 1702 -7.9355766000000e-06\r\n2806 1702 -1.6482663000000e-03\r\n2808 1702 -1.7202053000000e-05\r\n598 1703  1.4531280000000e+01\r\n600 1703 -2.0267265000000e+00\r\n1656 1703 -1.1927259000000e+00\r\n1701 1703 -1.0598049000000e+00\r\n1702 1703 -1.5383473000000e+02\r\n1703 1703 -3.7069915000000e+01\r\n1704 1703  9.0252440000000e+00\r\n1705 1703  2.7552567000000e+01\r\n1707 1703 -1.2416079000000e+00\r\n1750 1703  2.4164380000000e-01\r\n1752 1703 -1.0954366000000e+00\r\n2808 1703 -2.4047730000000e+00\r\n598 1704  2.4563675000000e+01\r\n599 1704 -3.9787347000000e+00\r\n600 1704 -3.4259784000000e+00\r\n1656 1704 -2.0161839000000e+00\r\n1701 1704 -1.7914930000000e+00\r\n1702 1704 -2.6004222000000e+02\r\n1703 1704  4.0341763000000e+01\r\n1704 1704  1.5256271000000e+01\r\n1705 1704  4.6574860000000e+01\r\n1706 1704 -7.5440262000000e+00\r\n1707 1704 -2.0988139000000e+00\r\n1750 1704  4.0847468000000e-01\r\n1751 1704 -6.6163242000000e-02\r\n1752 1704 -1.8517261000000e+00\r\n2808 1704 -4.0650283000000e+00\r\n601 1705 -3.7175945000000e-01\r\n603 1705 -1.3821958000000e-05\r\n1657 1705 -9.5707288000000e-04\r\n1659 1705 -9.9884456000000e-06\r\n1702 1705 -8.6115528000000e-04\r\n1704 1705 -8.9874061000000e-06\r\n1705 1705  2.2200070000000e+02\r\n1707 1705  5.8719055000000e-04\r\n1708 1705 -4.5948004000000e-01\r\n1710 1705 -1.1123200000000e-05\r\n1753 1705 -9.1943302000000e-04\r\n1755 1705 -9.5956190000000e-06\r\n2809 1705 -1.5255790000000e-03\r\n2811 1705 -1.5921633000000e-05\r\n601 1706  4.2979748000000e+01\r\n603 1706 -1.7801773000000e+00\r\n1659 1706 -1.3707856000000e+00\r\n1704 1706 -1.2416079000000e+00\r\n1705 1706 -2.1221385000000e+02\r\n1706 1706 -4.2232058000000e+01\r\n1707 1706  9.1999729000000e+00\r\n1708 1706  4.2257388000000e+01\r\n1710 1706 -1.4325391000000e+00\r\n1755 1706 -1.2577860000000e+00\r\n2811 1706 -2.1123227000000e+00\r\n601 1707  7.2652915000000e+01\r\n602 1707 -1.1767451000000e+01\r\n603 1707 -3.0092095000000e+00\r\n1659 1707 -2.3171744000000e+00\r\n1704 1707 -2.0988139000000e+00\r\n1705 1707 -3.5872605000000e+02\r\n1706 1707  5.6042433000000e+01\r\n1707 1707  1.5551625000000e+01\r\n1708 1707  7.1431844000000e+01\r\n1709 1707 -1.1569677000000e+01\r\n1710 1707 -2.4215624000000e+00\r\n1755 1707 -2.1261600000000e+00\r\n2811 1707 -3.5706677000000e+00\r\n604 1708 -1.2680469000000e+00\r\n606 1708 -1.2867217000000e-05\r\n1660 1708 -1.1435735000000e-03\r\n1662 1708 -1.1934851000000e-05\r\n1705 1708 -1.0658028000000e-03\r\n1707 1708 -1.1123200000000e-05\r\n1708 1708  2.6110786000000e+02\r\n1710 1708  6.8404619000000e-04\r\n1711 1708 -1.1789649000000e-03\r\n1713 1708 -1.2304211000000e-05\r\n1756 1708 -1.1386170000000e-03\r\n1758 1708 -1.1883122000000e-05\r\n2812 1708 -1.3844402000000e-03\r\n2814 1708 -1.4448644000000e-05\r\n604 1709  1.3131564000000e+02\r\n606 1709 -1.5208751000000e+00\r\n1662 1709 -1.5804774000000e+00\r\n1707 1709 -1.4325391000000e+00\r\n1708 1709 -3.7165501000000e+02\r\n1709 1709 -4.9462685000000e+01\r\n1710 1709  9.8205637000000e+00\r\n1713 1709 -1.5868194000000e+00\r\n1758 1709 -1.5019716000000e+00\r\n2814 1709 -1.8034786000000e+00\r\n604 1710  2.2197596000000e+02\r\n605 1710 -3.5950514000000e+01\r\n606 1710 -2.5708872000000e+00\r\n1662 1710 -2.6716390000000e+00\r\n1707 1710 -2.4215624000000e+00\r\n1708 1710 -6.2824561000000e+02\r\n1709 1710  9.9286469000000e+01\r\n1710 1710  1.6600677000000e+01\r\n1713 1710 -2.6823581000000e+00\r\n1758 1710 -2.5389328000000e+00\r\n2814 1710 -3.0486002000000e+00\r\n607 1711 -3.1361874000000e-01\r\n609 1711 -1.1318731000000e-05\r\n1663 1711 -1.1309445000000e-03\r\n1665 1711 -1.1803048000000e-05\r\n1708 1711 -4.7911884000000e-01\r\n1710 1711 -1.2304211000000e-05\r\n1711 1711  2.7051663000000e+02\r\n1713 1711  7.0413969000000e-04\r\n1714 1711 -1.1386034000000e-03\r\n1716 1711 -1.1882980000000e-05\r\n1759 1711 -1.1879351000000e-03\r\n1761 1711 -1.2397828000000e-05\r\n2815 1711 -1.2479521000000e-03\r\n2817 1711 -1.3024193000000e-05\r\n607 1712  3.7277203000000e+01\r\n609 1712 -1.4597647000000e+00\r\n1665 1712 -1.6144318000000e+00\r\n1708 1712  4.7530409000000e+01\r\n1710 1712 -1.5868194000000e+00\r\n1711 1712 -2.3966453000000e+02\r\n1712 1712 -5.1497262000000e+01\r\n1713 1712  9.6341451000000e+00\r\n1716 1712 -1.6195096000000e+00\r\n1761 1712 -1.6167865000000e+00\r\n2817 1712 -1.7310373000000e+00\r\n607 1713  6.3013350000000e+01\r\n608 1713 -1.0206158000000e+01\r\n609 1713 -2.4675848000000e+00\r\n1665 1713 -2.7290339000000e+00\r\n1708 1713  8.0345359000000e+01\r\n1709 1713 -1.3013393000000e+01\r\n1710 1713 -2.6823581000000e+00\r\n1711 1713 -4.0512869000000e+02\r\n1712 1713  6.3118938000000e+01\r\n1713 1713  1.6285550000000e+01\r\n1716 1713 -2.7376190000000e+00\r\n1761 1713 -2.7330142000000e+00\r\n2817 1713 -2.9261433000000e+00\r\n610 1714 -7.5290694000000e-02\r\n612 1714 -1.0714810000000e-05\r\n1666 1714 -1.0885080000000e-03\r\n1668 1714 -1.1360162000000e-05\r\n1711 1714 -2.9111676000000e-01\r\n1713 1714 -1.1882980000000e-05\r\n1714 1714  2.7010717000000e+02\r\n1716 1714  7.0134261000000e-04\r\n1717 1714 -1.0989148000000e-03\r\n1719 1714 -1.1468772000000e-05\r\n1762 1714 -1.1510559000000e-03\r\n1764 1714 -1.2012940000000e-05\r\n2818 1714 -1.1995862000000e-03\r\n2820 1714 -1.2519425000000e-05\r\n610 1715  1.3815885000000e+01\r\n612 1715 -1.4603184000000e+00\r\n1668 1715 -1.6143877000000e+00\r\n1711 1715  2.8543428000000e+01\r\n1713 1715 -1.6195096000000e+00\r\n1714 1715 -2.0363473000000e+02\r\n1715 1715 -5.1482107000000e+01\r\n1716 1715  9.6675806000000e+00\r\n1719 1715 -1.6191732000000e+00\r\n1762 1715  6.3963030000000e+00\r\n1764 1715 -1.6165621000000e+00\r\n2820 1715 -1.7318408000000e+00\r\n610 1716  2.3354372000000e+01\r\n611 1716 -3.7828194000000e+00\r\n612 1716 -2.4685221000000e+00\r\n1668 1716 -2.7289610000000e+00\r\n1711 1716  4.8249810000000e+01\r\n1712 1716 -7.8152526000000e+00\r\n1713 1716 -2.7376190000000e+00\r\n1714 1716 -3.4422415000000e+02\r\n1715 1716  5.3294295000000e+01\r\n1716 1716  1.6342077000000e+01\r\n1719 1716 -2.7370489000000e+00\r\n1762 1716  1.0812310000000e+01\r\n1763 1716 -1.7513217000000e+00\r\n1764 1716 -2.7326365000000e+00\r\n2820 1716 -2.9275037000000e+00\r\n613 1717 -1.2372172000000e-03\r\n615 1717 -1.0334473000000e-05\r\n1669 1717 -1.0574586000000e-03\r\n1671 1717 -1.1036116000000e-05\r\n1714 1717 -1.9358587000000e-01\r\n1716 1717 -1.1468772000000e-05\r\n1717 1717  2.7002973000000e+02\r\n1719 1717  6.9906204000000e-04\r\n1720 1717 -1.0680400000000e-03\r\n1722 1717 -1.1146549000000e-05\r\n1765 1717 -7.6600454000000e-02\r\n1767 1717 -1.1452271000000e-05\r\n2821 1717 -1.1850076000000e-02\r\n2823 1717 -1.2257771000000e-05\r\n613 1718  6.5236915000000e+00\r\n615 1718 -1.4590786000000e+00\r\n1671 1718 -1.6155050000000e+00\r\n1714 1718  1.7385177000000e+01\r\n1716 1718 -1.6191732000000e+00\r\n1717 1718 -1.9245925000000e+02\r\n1718 1718 -5.1474884000000e+01\r\n1719 1718  9.6658804000000e+00\r\n1722 1718 -1.6190032000000e+00\r\n1765 1718  1.3660612000000e+01\r\n1767 1718 -1.6169162000000e+00\r\n2823 1718 -1.7304186000000e+00\r\n613 1719  1.1027642000000e+01\r\n614 1719 -1.7862458000000e+00\r\n615 1719 -2.4664250000000e+00\r\n1671 1719 -2.7308478000000e+00\r\n1714 1719  2.9387887000000e+01\r\n1715 1719 -4.7602190000000e+00\r\n1716 1719 -2.7370489000000e+00\r\n1717 1719 -3.2533292000000e+02\r\n1718 1719  5.0253828000000e+01\r\n1719 1719  1.6339196000000e+01\r\n1722 1719 -2.7367630000000e+00\r\n1765 1719  2.3091886000000e+01\r\n1766 1719 -3.7403991000000e+00\r\n1767 1719 -2.7332335000000e+00\r\n2823 1719 -2.9250977000000e+00\r\n616 1720 -9.7247768000000e-04\r\n618 1720 -1.0149217000000e-05\r\n1672 1720 -1.0275524000000e-03\r\n1674 1720 -1.0724002000000e-05\r\n1717 1720 -1.6140711000000e-01\r\n1719 1720 -1.1146549000000e-05\r\n1720 1720  2.6993957000000e+02\r\n1722 1720  6.7529411000000e-04\r\n2824 1720 -2.7057739000000e-02\r\n2826 1720 -1.1922981000000e-05\r\n616 1721  4.0892497000000e+00\r\n618 1721 -1.4602675000000e+00\r\n1674 1721 -1.5990651000000e+00\r\n1717 1721  1.3440870000000e+01\r\n1719 1721 -1.6190032000000e+00\r\n1720 1721 -1.7242606000000e+02\r\n1721 1721 -5.1470763000000e+01\r\n1722 1721  6.4157856000000e+00\r\n2826 1721 -1.7316662000000e+00\r\n616 1722  6.9124677000000e+00\r\n617 1722 -1.1196955000000e+00\r\n618 1722 -2.4684361000000e+00\r\n1674 1722 -2.7030597000000e+00\r\n1717 1722  2.2720447000000e+01\r\n1718 1722 -3.6803039000000e+00\r\n1719 1722 -2.7367630000000e+00\r\n1720 1722 -2.9146900000000e+02\r\n1721 1722  4.4779759000000e+01\r\n1722 1722  1.0845244000000e+01\r\n2826 1722 -2.9272085000000e+00\r\n1723 1723  1.0000000000000e+00\r\n1724 1724  1.0000000000000e+00\r\n1725 1725  1.0000000000000e+00\r\n1726 1726  1.0000000000000e+00\r\n1727 1727  1.0000000000000e+00\r\n1728 1728  1.0000000000000e+00\r\n1729 1729  1.0000000000000e+00\r\n1730 1730  1.0000000000000e+00\r\n1731 1731  1.0000000000000e+00\r\n1732 1732  1.0000000000000e+00\r\n1733 1733  1.0000000000000e+00\r\n1734 1734  1.0000000000000e+00\r\n1735 1735  1.0000000000000e+00\r\n1736 1736  1.0000000000000e+00\r\n1737 1737  1.0000000000000e+00\r\n634 1738 -2.2121759000000e-03\r\n636 1738 -2.3087268000000e-05\r\n1690 1738 -2.2899062000000e-02\r\n1692 1738 -4.1012760000000e-06\r\n1738 1738  1.0799645000000e+02\r\n1740 1738  3.1521981000000e-04\r\n1741 1738 -1.3641424000000e-02\r\n1743 1738 -4.1010484000000e-06\r\n1786 1738 -3.8641520000000e-04\r\n1788 1738 -4.0328039000000e-06\r\n2842 1738 -5.2763589000000e-02\r\n2844 1738 -2.7373634000000e-05\r\n634 1739  4.7833739000000e-01\r\n636 1739 -3.6436389000000e+00\r\n1690 1739  9.6773944000000e-01\r\n1692 1739 -6.4747945000000e-01\r\n1738 1739 -6.6273133000000e+01\r\n1739 1739 -2.0584062000000e+01\r\n1740 1739  9.9100283000000e+00\r\n1741 1739  2.8622958000000e+00\r\n1743 1739 -6.4748607000000e-01\r\n1788 1739 -6.4756021000000e-01\r\n2844 1739 -4.3215522000000e+00\r\n634 1740  8.0858152000000e-01\r\n635 1740 -1.3098277000000e-01\r\n636 1740 -6.1592072000000e+00\r\n1690 1740  1.6358668000000e+00\r\n1691 1740 -2.6499537000000e-01\r\n1692 1740 -1.0944993000000e+00\r\n1738 1740 -1.1202810000000e+02\r\n1739 1740  1.7184991000000e+01\r\n1740 1740  1.6751912000000e+01\r\n1741 1740  4.8384248000000e+00\r\n1742 1740 -7.8378034000000e-01\r\n1743 1740 -1.0945105000000e+00\r\n1788 1740 -1.0946358000000e+00\r\n2844 1740 -7.3051519000000e+00\r\n637 1741 -2.2492247000000e-03\r\n639 1741 -2.3473926000000e-05\r\n1693 1741 -2.3565069000000e-02\r\n1695 1741 -4.5455680000000e-06\r\n1738 1741 -3.9295426000000e-04\r\n1740 1741 -4.1010484000000e-06\r\n1741 1741  1.0803119000000e+02\r\n1743 1741  3.2114201000000e-04\r\n1744 1741 -5.2755570000000e-02\r\n1746 1741 -4.5491599000000e-06\r\n1789 1741 -3.9523853000000e-04\r\n1791 1741 -4.1248881000000e-06\r\n2845 1741 -5.1145261000000e-02\r\n2847 1741 -2.7822909000000e-05\r\n637 1742  7.1202527000000e-01\r\n639 1742 -3.6437574000000e+00\r\n1695 1742 -7.0596904000000e-01\r\n1740 1742 -6.4748607000000e-01\r\n1741 1742 -6.8419519000000e+01\r\n1742 1742 -2.0587619000000e+01\r\n1743 1742  1.0674876000000e+01\r\n1744 1742  5.7477272000000e+00\r\n1746 1742 -7.0659250000000e-01\r\n1791 1742 -6.4748172000000e-01\r\n2847 1742 -4.3212757000000e+00\r\n637 1743  1.2036068000000e+00\r\n638 1743 -1.9497134000000e-01\r\n639 1743 -6.1594038000000e+00\r\n1695 1743 -1.1933695000000e+00\r\n1740 1743 -1.0945105000000e+00\r\n1741 1743 -1.1565628000000e+02\r\n1742 1743  1.7763824000000e+01\r\n1743 1743  1.8044799000000e+01\r\n1744 1743  9.7159521000000e+00\r\n1745 1743 -1.5738796000000e+00\r\n1746 1743 -1.1944232000000e+00\r\n1791 1743 -1.0945024000000e+00\r\n2847 1743 -7.3046794000000e+00\r\n640 1744 -1.9323577000000e-03\r\n642 1744 -2.0166959000000e-05\r\n1696 1744 -2.2917029000000e-02\r\n1698 1744 -5.4501468000000e-06\r\n1741 1744 -4.3589141000000e-04\r\n1743 1744 -4.5491599000000e-06\r\n1744 1744  1.2965391000000e+02\r\n1746 1744  3.6728552000000e-04\r\n1747 1744 -1.0653696000000e-01\r\n1749 1744 -5.5503435000000e-06\r\n1792 1744 -4.4507975000000e-04\r\n1794 1744 -4.6450536000000e-06\r\n2848 1744 -4.5466010000000e-02\r\n2850 1744 -2.3889507000000e-05\r\n640 1745  1.4723184000000e+00\r\n642 1745 -3.0366821000000e+00\r\n1698 1745 -8.2190450000000e-01\r\n1743 1745 -7.0659250000000e-01\r\n1744 1745 -8.5348337000000e+01\r\n1745 1745 -2.4709362000000e+01\r\n1746 1745  9.7140832000000e+00\r\n1747 1745  9.5303947000000e+00\r\n1749 1745 -8.3709780000000e-01\r\n1794 1745 -7.0625909000000e-01\r\n2850 1745 -3.6027696000000e+00\r\n640 1746  2.4888069000000e+00\r\n641 1746 -4.0315204000000e-01\r\n642 1746 -5.1332074000000e+00\r\n1698 1746 -1.3893474000000e+00\r\n1743 1746 -1.1944232000000e+00\r\n1744 1746 -1.4427283000000e+02\r\n1745 1746  2.2194201000000e+01\r\n1746 1746  1.6420685000000e+01\r\n1747 1746  1.6110179000000e+01\r\n1748 1746 -2.6096245000000e+00\r\n1749 1746 -1.4150301000000e+00\r\n1794 1746 -1.1938604000000e+00\r\n2850 1746 -6.0901217000000e+00\r\n643 1747 -1.7307928000000e-03\r\n645 1747 -1.8063337000000e-05\r\n1699 1747 -1.8186795000000e-02\r\n1701 1747 -6.4663993000000e-06\r\n1744 1747 -5.3182282000000e-04\r\n1746 1747 -5.5503435000000e-06\r\n1747 1747  1.5125413000000e+02\r\n1749 1747  4.1747288000000e-04\r\n1750 1747 -1.5298080000000e-01\r\n1752 1747 -6.6764701000000e-06\r\n1795 1747 -5.5931807000000e-04\r\n1797 1747 -5.8372964000000e-06\r\n2851 1747 -2.9380086000000e-02\r\n2853 1747 -2.1328591000000e-05\r\n643 1748  3.7646537000000e+00\r\n645 1748 -2.6045985000000e+00\r\n1701 1748 -9.3682947000000e-01\r\n1746 1748 -8.3709780000000e-01\r\n1747 1748 -1.0444681000000e+02\r\n1748 1748 -2.8831816000000e+01\r\n1749 1748  9.2932034000000e+00\r\n1750 1748  1.3951809000000e+01\r\n1752 1748 -9.6736793000000e-01\r\n1797 1748 -8.5397505000000e-01\r\n2853 1748 -3.0900922000000e+00\r\n643 1749  6.3637670000000e+00\r\n644 1749 -1.0308146000000e+00\r\n645 1749 -4.4028107000000e+00\r\n1701 1749 -1.5836155000000e+00\r\n1746 1749 -1.4150301000000e+00\r\n1747 1749 -1.7655678000000e+02\r\n1748 1749  2.7216494000000e+01\r\n1749 1749  1.5709222000000e+01\r\n1750 1749  2.3584125000000e+01\r\n1751 1749 -3.8201994000000e+00\r\n1752 1749 -1.6352378000000e+00\r\n1797 1749 -1.4435584000000e+00\r\n2853 1749 -5.2234888000000e+00\r\n646 1750 -3.5777127000000e-02\r\n648 1750 -1.6515382000000e-05\r\n1702 1750 -4.7829871000000e-02\r\n1704 1750 -7.9355766000000e-06\r\n1747 1750 -6.3972601000000e-04\r\n1749 1750 -6.6764701000000e-06\r\n1750 1750  1.7290657000000e+02\r\n1752 1750  4.6981893000000e-04\r\n1753 1750 -1.9763276000000e-01\r\n1755 1750 -8.0510325000000e-06\r\n1798 1750 -6.8268354000000e-04\r\n1800 1750 -7.1247943000000e-06\r\n2854 1750 -1.8630208000000e-03\r\n2856 1750 -1.9443328000000e-05\r\n646 1751  9.8677828000000e+00\r\n648 1751 -2.2800486000000e+00\r\n1704 1751 -1.0954366000000e+00\r\n1749 1751 -9.6736793000000e-01\r\n1750 1751 -1.2699346000000e+02\r\n1751 1751 -3.2957137000000e+01\r\n1752 1751  9.1643487000000e+00\r\n1753 1751  1.8014880000000e+01\r\n1755 1751 -1.1115071000000e+00\r\n1800 1751 -1.0013891000000e+00\r\n2856 1751 -2.7048907000000e+00\r\n646 1752  1.6680500000000e+01\r\n647 1752 -2.7018452000000e+00\r\n648 1752 -3.8541941000000e+00\r\n1704 1752 -1.8517261000000e+00\r\n1749 1752 -1.6352378000000e+00\r\n1750 1752 -2.1466975000000e+02\r\n1751 1752  3.3175169000000e+01\r\n1752 1752  1.5491414000000e+01\r\n1753 1752  3.0452353000000e+01\r\n1754 1752 -4.9325587000000e+00\r\n1755 1752 -1.8788916000000e+00\r\n1800 1752 -1.6927482000000e+00\r\n2856 1752 -4.5723473000000e+00\r\n649 1753 -1.6926658000000e-01\r\n651 1753 -1.5045593000000e-05\r\n1705 1753 -1.3140085000000e-01\r\n1707 1753 -9.5956190000000e-06\r\n1750 1753 -7.7143383000000e-04\r\n1752 1753 -8.0510325000000e-06\r\n1753 1753  2.0007792000000e+02\r\n1755 1753  5.3619780000000e-04\r\n1756 1753 -1.8912705000000e-01\r\n1758 1753 -1.0034359000000e-05\r\n1801 1753 -8.3448985000000e-04\r\n1803 1753 -8.7091136000000e-06\r\n2857 1753 -1.6801156000000e-03\r\n2859 1753 -1.7534446000000e-05\r\n649 1754  2.3028724000000e+01\r\n651 1754 -1.9724001000000e+00\r\n1705 1754  7.2474017000000e+00\r\n1707 1754 -1.2577860000000e+00\r\n1752 1754 -1.1115071000000e+00\r\n1753 1754 -1.6054765000000e+02\r\n1754 1754 -3.8115097000000e+01\r\n1755 1754  9.1815998000000e+00\r\n1756 1754  1.5687094000000e+01\r\n1758 1754 -1.3153713000000e+00\r\n1803 1754 -1.1802067000000e+00\r\n2859 1754 -2.3400367000000e+00\r\n649 1755  3.8927728000000e+01\r\n650 1755 -6.3051332000000e+00\r\n651 1755 -3.3341428000000e+00\r\n1705 1755  1.2251000000000e+01\r\n1706 1755 -1.9842972000000e+00\r\n1707 1755 -2.1261600000000e+00\r\n1752 1755 -1.8788916000000e+00\r\n1753 1755 -2.7138957000000e+02\r\n1754 1755  4.2090424000000e+01\r\n1755 1755  1.5520567000000e+01\r\n1756 1755  2.6517446000000e+01\r\n1757 1755 -4.2950369000000e+00\r\n1758 1755 -2.2235022000000e+00\r\n1803 1755 -1.9950201000000e+00\r\n2859 1755 -3.9555957000000e+00\r\n652 1756 -3.4375572000000e-01\r\n654 1756 -1.2833632000000e-05\r\n1708 1756 -4.2269746000000e-01\r\n1710 1756 -1.1883122000000e-05\r\n1753 1756 -9.6147224000000e-04\r\n1755 1756 -1.0034359000000e-05\r\n1756 1756  2.4350342000000e+02\r\n1758 1756  6.4041493000000e-04\r\n1759 1756 -1.1274298000000e-03\r\n1761 1756 -1.1766367000000e-05\r\n1804 1756 -1.0395140000000e-03\r\n1806 1756 -1.0848838000000e-05\r\n2860 1756 -1.4161375000000e-03\r\n2862 1756 -1.4779451000000e-05\r\n652 1757  4.0238110000000e+01\r\n654 1757 -1.6222799000000e+00\r\n1708 1757  3.5046687000000e+01\r\n1710 1757 -1.5019716000000e+00\r\n1755 1757 -1.3153713000000e+00\r\n1756 1757 -2.1463638000000e+02\r\n1757 1757 -4.6361346000000e+01\r\n1758 1757  9.3417448000000e+00\r\n1761 1757 -1.5345715000000e+00\r\n1806 1757 -1.4383759000000e+00\r\n2862 1757 -1.9239522000000e+00\r\n652 1758  6.8018501000000e+01\r\n653 1758 -1.1016657000000e+01\r\n654 1758 -2.7423019000000e+00\r\n1708 1758  5.9242920000000e+01\r\n1709 1758 -9.5953152000000e+00\r\n1710 1758 -2.5389328000000e+00\r\n1755 1758 -2.2235022000000e+00\r\n1756 1758 -3.6282133000000e+02\r\n1757 1758  5.6481337000000e+01\r\n1758 1758  1.5791282000000e+01\r\n1761 1758 -2.5940381000000e+00\r\n1806 1758 -2.4314307000000e+00\r\n2862 1758 -3.2522488000000e+00\r\n655 1759 -1.3674684000000e-01\r\n657 1759 -1.1187730000000e-05\r\n1711 1759 -1.3342204000000e-01\r\n1713 1759 -1.2397828000000e-05\r\n1756 1759 -1.5808714000000e-01\r\n1758 1759 -1.1766367000000e-05\r\n1759 1759  2.7014495000000e+02\r\n1761 1759  7.0391015000000e-04\r\n1762 1759 -1.1531738000000e-03\r\n1764 1759 -1.2035044000000e-05\r\n1807 1759 -1.1615426000000e-03\r\n1809 1759 -1.2122384000000e-05\r\n2863 1759 -1.2461293000000e-03\r\n2865 1759 -1.3005170000000e-05\r\n655 1760  1.9861190000000e+01\r\n657 1760 -1.4592005000000e+00\r\n1711 1760  6.0085957000000e+00\r\n1713 1760 -1.6167865000000e+00\r\n1756 1760  1.5859809000000e+01\r\n1758 1760 -1.5345715000000e+00\r\n1759 1760 -1.9657855000000e+02\r\n1760 1760 -5.1503173000000e+01\r\n1761 1760  9.5834246000000e+00\r\n1764 1760 -1.6197167000000e+00\r\n1809 1760 -1.6168748000000e+00\r\n2865 1760 -1.7304764000000e+00\r\n655 1761  3.3573335000000e+01\r\n656 1761 -5.4378591000000e+00\r\n657 1761 -2.4666309000000e+00\r\n1711 1761  1.0156924000000e+01\r\n1712 1761 -1.6451127000000e+00\r\n1713 1761 -2.7330142000000e+00\r\n1756 1761  2.6809404000000e+01\r\n1757 1761 -4.3423080000000e+00\r\n1758 1761 -2.5940381000000e+00\r\n1759 1761 -3.3229618000000e+02\r\n1760 1761  5.1308508000000e+01\r\n1761 1761  1.6199811000000e+01\r\n1764 1761 -2.7379691000000e+00\r\n1809 1761 -2.7331625000000e+00\r\n2865 1761 -2.9251949000000e+00\r\n658 1762 -4.0112686000000e-02\r\n660 1762 -1.0836605000000e-05\r\n1714 1762 -1.5265340000000e-02\r\n1716 1762 -1.2012940000000e-05\r\n1759 1762 -1.7280484000000e-01\r\n1761 1762 -1.2035044000000e-05\r\n1762 1762  2.6995334000000e+02\r\n1764 1762  7.0276120000000e-04\r\n1765 1762 -1.1303636000000e-03\r\n1767 1762 -1.1796986000000e-05\r\n1810 1762 -1.1496815000000e-03\r\n1812 1762 -1.1998596000000e-05\r\n2866 1762 -1.2169571000000e-03\r\n2868 1762 -1.2700715000000e-05\r\n658 1763  1.0345366000000e+01\r\n660 1763 -1.4584898000000e+00\r\n1716 1763 -1.6165621000000e+00\r\n1759 1763  1.6117870000000e+01\r\n1761 1763 -1.6197167000000e+00\r\n1762 1763 -1.8132328000000e+02\r\n1763 1763 -5.1495627000000e+01\r\n1764 1763  9.6666238000000e+00\r\n1767 1763 -1.6196478000000e+00\r\n1812 1763 -1.6167175000000e+00\r\n2868 1763 -1.7296952000000e+00\r\n658 1764  1.7487807000000e+01\r\n659 1764 -2.8325578000000e+00\r\n660 1764 -2.4654311000000e+00\r\n1716 1764 -2.7326365000000e+00\r\n1759 1764  2.7245647000000e+01\r\n1760 1764 -4.4130674000000e+00\r\n1761 1764 -2.7379691000000e+00\r\n1762 1764 -3.0650887000000e+02\r\n1763 1764  4.7151643000000e+01\r\n1764 1764  1.6340459000000e+01\r\n1767 1764 -2.7378505000000e+00\r\n1812 1764 -2.7328993000000e+00\r\n2868 1764 -2.9238767000000e+00\r\n661 1765 -1.0327461000000e-03\r\n663 1765 -1.0778205000000e-05\r\n1717 1765 -1.0973337000000e-03\r\n1719 1765 -1.1452271000000e-05\r\n1762 1765 -1.0388055000000e-01\r\n1764 1765 -1.1796986000000e-05\r\n1765 1765  2.6984629000000e+02\r\n1767 1765  6.8987731000000e-04\r\n1813 1765 -1.1378693000000e-03\r\n1815 1765 -1.1875319000000e-05\r\n2869 1765 -1.1707371000000e-02\r\n2871 1765 -1.2603672000000e-05\r\n661 1766  6.3924356000000e+00\r\n663 1766 -1.4589556000000e+00\r\n1719 1766 -1.6169162000000e+00\r\n1762 1766  1.0114327000000e+01\r\n1764 1766 -1.6196478000000e+00\r\n1765 1766 -1.7561032000000e+02\r\n1766 1766 -5.1490230000000e+01\r\n1767 1766  8.0486866000000e+00\r\n1813 1766  4.2357121000000e+00\r\n1815 1766 -1.6171003000000e+00\r\n2871 1766 -1.7302744000000e+00\r\n661 1767  1.0805765000000e+01\r\n662 1767 -1.7502718000000e+00\r\n663 1767 -2.4662167000000e+00\r\n1719 1767 -2.7332335000000e+00\r\n1762 1767  1.7097245000000e+01\r\n1763 1767 -2.7693391000000e+00\r\n1764 1767 -2.7378505000000e+00\r\n1765 1767 -2.9685147000000e+02\r\n1766 1767  4.5601587000000e+01\r\n1767 1767  1.3605490000000e+01\r\n1813 1767  7.1600424000000e+00\r\n1814 1767 -1.1597532000000e+00\r\n1815 1767 -2.7335442000000e+00\r\n2871 1767 -2.9248541000000e+00\r\n1768 1768  1.0000000000000e+00\r\n1769 1769  1.0000000000000e+00\r\n1770 1770  1.0000000000000e+00\r\n1771 1771  1.0000000000000e+00\r\n1772 1772  1.0000000000000e+00\r\n1773 1773  1.0000000000000e+00\r\n1774 1774  1.0000000000000e+00\r\n1775 1775  1.0000000000000e+00\r\n1776 1776  1.0000000000000e+00\r\n1777 1777  1.0000000000000e+00\r\n1778 1778  1.0000000000000e+00\r\n1779 1779  1.0000000000000e+00\r\n1780 1780  1.0000000000000e+00\r\n1781 1781  1.0000000000000e+00\r\n1782 1782  1.0000000000000e+00\r\n679 1783 -2.0344545000000e-03\r\n681 1783 -2.1232487000000e-05\r\n1783 1783  1.1337215000000e+02\r\n1785 1783  3.1999143000000e-04\r\n1786 1783 -1.1889087000000e-02\r\n1788 1783 -4.0530144000000e-06\r\n1831 1783 -4.2009502000000e-04\r\n1833 1783 -4.3843017000000e-06\r\n2887 1783 -5.2840465000000e-02\r\n2889 1783 -2.5176046000000e-05\r\n679 1784  4.4623239000000e-01\r\n681 1784 -3.4702348000000e+00\r\n1783 1784 -6.8660562000000e+01\r\n1784 1784 -2.1608517000000e+01\r\n1785 1784  8.9769714000000e+00\r\n1786 1784  3.1445519000000e+00\r\n1788 1784 -6.6272767000000e-01\r\n1833 1784 -7.2523623000000e-01\r\n2889 1784 -4.1163478000000e+00\r\n679 1785  7.5431073000000e-01\r\n680 1785 -1.2219412000000e-01\r\n681 1785 -5.8660810000000e+00\r\n1783 1785 -1.1606375000000e+02\r\n1784 1785  1.7802766000000e+01\r\n1785 1785  1.5174662000000e+01\r\n1786 1785  5.3155474000000e+00\r\n1787 1785 -8.6108879000000e-01\r\n1788 1785 -1.1202741000000e+00\r\n1833 1785 -1.2259385000000e+00\r\n2889 1785 -6.9582695000000e+00\r\n682 1786 -2.1762259000000e-03\r\n684 1786 -2.2712078000000e-05\r\n1738 1786 -3.9250766000000e-02\r\n1740 1786 -4.0328039000000e-06\r\n1783 1786 -3.8835173000000e-04\r\n1785 1786 -4.0530144000000e-06\r\n1786 1786  1.0801808000000e+02\r\n1788 1786  3.1834302000000e-04\r\n1789 1786 -1.7943929000000e-02\r\n1791 1786 -4.0306948000000e-06\r\n1834 1786 -3.8955156000000e-04\r\n1836 1786 -4.0655363000000e-06\r\n2890 1786 -5.2961635000000e-02\r\n2892 1786 -2.6928775000000e-05\r\n682 1787  4.5034387000000e-01\r\n684 1787 -3.6457717000000e+00\r\n1738 1787  2.8889618000000e+00\r\n1740 1787 -6.4756021000000e-01\r\n1785 1787 -6.6272767000000e-01\r\n1786 1787 -6.9213653000000e+01\r\n1787 1787 -2.0583738000000e+01\r\n1788 1787  1.0592832000000e+01\r\n1789 1787  3.9090414000000e+00\r\n1791 1787 -6.4726334000000e-01\r\n1836 1787 -6.6324472000000e-01\r\n2892 1787 -4.3239533000000e+00\r\n682 1788  7.6126127000000e-01\r\n683 1788 -1.2331862000000e-01\r\n684 1788 -6.1628125000000e+00\r\n1738 1788  4.8835010000000e+00\r\n1739 1788 -7.9109055000000e-01\r\n1740 1788 -1.0946358000000e+00\r\n1785 1788 -1.1202741000000e+00\r\n1786 1788 -1.1699876000000e+02\r\n1787 1788  1.7991234000000e+01\r\n1788 1788  1.7906123000000e+01\r\n1789 1788  6.6078435000000e+00\r\n1790 1788 -1.0704211000000e+00\r\n1791 1788 -1.0941339000000e+00\r\n1836 1788 -1.1211489000000e+00\r\n2892 1788 -7.3092107000000e+00\r\n685 1789 -2.2239246000000e-03\r\n687 1789 -2.3209883000000e-05\r\n1741 1789 -3.4935035000000e-02\r\n1743 1789 -4.1248881000000e-06\r\n1786 1789 -3.8621311000000e-04\r\n1788 1789 -4.0306948000000e-06\r\n1789 1789  1.0803820000000e+02\r\n1791 1789  3.1959802000000e-04\r\n1792 1789 -4.8309404000000e-02\r\n1794 1789 -4.1261489000000e-06\r\n1837 1789 -3.8920994000000e-04\r\n1839 1789 -4.0619711000000e-06\r\n2893 1789 -5.2331484000000e-02\r\n2895 1789 -2.7523332000000e-05\r\n685 1790  5.3879822000000e-01\r\n687 1790 -3.6426013000000e+00\r\n1741 1790  1.8403586000000e+00\r\n1743 1790 -6.4748172000000e-01\r\n1788 1790 -6.4726334000000e-01\r\n1789 1790 -6.9988742000000e+01\r\n1790 1790 -2.0588667000000e+01\r\n1791 1790  1.0555334000000e+01\r\n1792 1790  5.6511986000000e+00\r\n1794 1790 -6.4772801000000e-01\r\n1839 1790 -6.4762352000000e-01\r\n2895 1790 -4.3203223000000e+00\r\n685 1791  9.1078393000000e-01\r\n686 1791 -1.4753817000000e-01\r\n687 1791 -6.1574493000000e+00\r\n1741 1791  3.1109401000000e+00\r\n1742 1791 -5.0394217000000e-01\r\n1743 1791 -1.0945024000000e+00\r\n1788 1791 -1.0941339000000e+00\r\n1789 1791 -1.1830889000000e+02\r\n1790 1791  1.8191121000000e+01\r\n1791 1791  1.7842726000000e+01\r\n1792 1791  9.5527798000000e+00\r\n1793 1791 -1.5474577000000e+00\r\n1794 1791 -1.0949187000000e+00\r\n1839 1791 -1.0947419000000e+00\r\n2895 1791 -7.3030692000000e+00\r\n688 1792 -2.2975010000000e-03\r\n690 1792 -2.3977760000000e-05\r\n1744 1792 -3.8165343000000e-02\r\n1746 1792 -4.6450536000000e-06\r\n1789 1792 -3.9535934000000e-04\r\n1791 1792 -4.1261489000000e-06\r\n1792 1792  1.0806751000000e+02\r\n1794 1792  3.2261263000000e-04\r\n1795 1792 -8.2053303000000e-02\r\n1797 1792 -4.7339249000000e-06\r\n1840 1792 -4.0135963000000e-04\r\n1842 1792 -4.1887707000000e-06\r\n2896 1792 -4.9200501000000e-02\r\n2898 1792 -2.8415874000000e-05\r\n688 1793  9.8968364000000e-01\r\n690 1793 -3.6428105000000e+00\r\n1744 1793  1.5903447000000e+00\r\n1746 1793 -7.0625909000000e-01\r\n1791 1793 -6.4772801000000e-01\r\n1792 1793 -7.2373388000000e+01\r\n1793 1793 -2.0592885000000e+01\r\n1794 1793  1.0687176000000e+01\r\n1795 1793  7.8410561000000e+00\r\n1797 1793 -7.1982591000000e-01\r\n1842 1793 -6.4769346000000e-01\r\n2898 1793 -4.3205436000000e+00\r\n688 1794  1.6729612000000e+00\r\n689 1794 -2.7099783000000e-01\r\n690 1794 -6.1578069000000e+00\r\n1744 1794  2.6883187000000e+00\r\n1745 1794 -4.3547246000000e-01\r\n1746 1794 -1.1938604000000e+00\r\n1791 1794 -1.0949187000000e+00\r\n1792 1794 -1.2233997000000e+02\r\n1793 1794  1.8833227000000e+01\r\n1794 1794  1.8065601000000e+01\r\n1795 1794  1.3254521000000e+01\r\n1796 1794 -2.1470590000000e+00\r\n1797 1794 -1.2167937000000e+00\r\n1842 1794 -1.0948610000000e+00\r\n2898 1794 -7.3034469000000e+00\r\n691 1795 -1.9178555000000e-03\r\n693 1795 -2.0015607000000e-05\r\n1747 1795 -5.7493821000000e-02\r\n1749 1795 -5.8372964000000e-06\r\n1792 1795 -4.5359522000000e-04\r\n1794 1795 -4.7339249000000e-06\r\n1795 1795  1.3507698000000e+02\r\n1797 1795  3.8104181000000e-04\r\n1798 1795 -1.1283663000000e-01\r\n1800 1795 -6.0380577000000e-06\r\n1843 1795 -4.8625713000000e-04\r\n1845 1795 -5.0747994000000e-06\r\n2899 1795 -4.0000201000000e-02\r\n2901 1795 -2.3677654000000e-05\r\n691 1796  2.2545016000000e+00\r\n693 1796 -2.9196208000000e+00\r\n1747 1796  2.3427932000000e+00\r\n1749 1796 -8.5397505000000e-01\r\n1794 1796 -7.1982591000000e-01\r\n1795 1796 -9.2422249000000e+01\r\n1796 1796 -2.5745523000000e+01\r\n1797 1796  9.6008817000000e+00\r\n1798 1796  1.0391003000000e+01\r\n1800 1796 -8.8341743000000e-01\r\n1845 1796 -7.5715025000000e-01\r\n2901 1796 -3.4639961000000e+00\r\n691 1797  3.8110069000000e+00\r\n692 1797 -6.1731790000000e-01\r\n693 1797 -4.9353235000000e+00\r\n1747 1797  3.9602548000000e+00\r\n1748 1797 -6.4149352000000e-01\r\n1749 1797 -1.4435584000000e+00\r\n1794 1797 -1.2167937000000e+00\r\n1795 1797 -1.5623046000000e+02\r\n1796 1797  2.4065408000000e+01\r\n1797 1797  1.6229320000000e+01\r\n1798 1797  1.7564939000000e+01\r\n1799 1797 -2.8452196000000e+00\r\n1800 1797 -1.4933278000000e+00\r\n1845 1797 -1.2798859000000e+00\r\n2901 1797 -5.8555350000000e+00\r\n694 1798 -1.6695103000000e-03\r\n696 1798 -1.7423765000000e-05\r\n1750 1798 -9.7878816000000e-02\r\n1752 1798 -7.1247943000000e-06\r\n1795 1798 -5.7855462000000e-04\r\n1797 1798 -6.0380577000000e-06\r\n1798 1798  1.6208701000000e+02\r\n1800 1798  4.4396095000000e-04\r\n1801 1798 -1.3546725000000e-01\r\n1803 1798 -7.5417599000000e-06\r\n1846 1798 -6.2223328000000e-04\r\n1848 1798 -6.4939081000000e-06\r\n2902 1798 -1.9986854000000e-02\r\n2904 1798 -2.0530161000000e-05\r\n694 1799  5.1369605000000e+00\r\n696 1799 -2.4321780000000e+00\r\n1750 1799  5.4105136000000e+00\r\n1752 1799 -1.0013891000000e+00\r\n1797 1799 -8.8341743000000e-01\r\n1798 1799 -1.1526550000000e+02\r\n1799 1799 -3.0899754000000e+01\r\n1800 1799  9.2013852000000e+00\r\n1801 1799  1.1804877000000e+01\r\n1803 1799 -1.0600584000000e+00\r\n1848 1799 -9.3536084000000e-01\r\n2904 1799 -2.8855036000000e+00\r\n694 1800  8.6835180000000e+00\r\n695 1800 -1.4065417000000e+00\r\n696 1800 -4.1113536000000e+00\r\n1750 1800  9.1459321000000e+00\r\n1751 1800 -1.4814428000000e+00\r\n1752 1800 -1.6927482000000e+00\r\n1797 1800 -1.4933278000000e+00\r\n1798 1800 -1.9484480000000e+02\r\n1799 1800  3.0058278000000e+01\r\n1800 1800  1.5554020000000e+01\r\n1801 1800  1.9954964000000e+01\r\n1802 1800 -3.2322717000000e+00\r\n1803 1800 -1.7919227000000e+00\r\n1848 1800 -1.5811340000000e+00\r\n2904 1800 -4.8776553000000e+00\r\n697 1801 -3.6361006000000e-02\r\n699 1801 -1.4957052000000e-05\r\n1753 1801 -1.7438127000000e-01\r\n1755 1801 -8.7091136000000e-06\r\n1798 1801 -7.2263635000000e-04\r\n1800 1801 -7.5417599000000e-06\r\n1801 1801  1.9451755000000e+02\r\n1803 1801  5.2093730000000e-04\r\n1804 1801 -1.1214604000000e-01\r\n1806 1801 -9.4657299000000e-06\r\n1849 1801 -7.7490891000000e-04\r\n1851 1801 -8.0873000000000e-06\r\n2905 1801 -1.6856987000000e-03\r\n2907 1801 -1.7592714000000e-05\r\n697 1802  9.9422740000000e+00\r\n699 1802 -2.0270036000000e+00\r\n1753 1802  1.2361556000000e+01\r\n1755 1802 -1.1802067000000e+00\r\n1800 1802 -1.0600584000000e+00\r\n1801 1802 -1.4259383000000e+02\r\n1802 1802 -3.7084526000000e+01\r\n1803 1802  9.0899510000000e+00\r\n1804 1802  8.8013890000000e+00\r\n1806 1802 -1.2827506000000e+00\r\n1851 1802 -1.1308285000000e+00\r\n2907 1802 -2.4049276000000e+00\r\n697 1803  1.6806408000000e+01\r\n698 1803 -2.7222043000000e+00\r\n699 1803 -3.4264445000000e+00\r\n1753 1803  2.0895960000000e+01\r\n1754 1803 -3.3846061000000e+00\r\n1755 1803 -1.9950201000000e+00\r\n1800 1803 -1.7919227000000e+00\r\n1801 1803 -2.4104046000000e+02\r\n1802 1803  3.7227496000000e+01\r\n1803 1803  1.5365644000000e+01\r\n1804 1803  1.4877859000000e+01\r\n1805 1803 -2.4098289000000e+00\r\n1806 1803 -2.1683601000000e+00\r\n1851 1803 -1.9115514000000e+00\r\n2907 1803 -4.0652867000000e+00\r\n700 1804 -7.6291503000000e-02\r\n702 1804 -1.2512836000000e-05\r\n1756 1804 -2.9356815000000e-01\r\n1758 1804 -1.0848838000000e-05\r\n1801 1804 -9.0698731000000e-04\r\n1803 1804 -9.4657299000000e-06\r\n1804 1804  2.3771689000000e+02\r\n1806 1804  6.2461449000000e-04\r\n1807 1804 -1.0893372000000e-03\r\n1809 1804 -1.1368816000000e-05\r\n1852 1804 -9.7283384000000e-04\r\n1854 1804 -1.0152934000000e-05\r\n2908 1804 -1.4038815000000e-03\r\n2910 1804 -1.4651543000000e-05\r\n700 1805  1.3900146000000e+01\r\n702 1805 -1.6590973000000e+00\r\n1756 1805  2.2350159000000e+01\r\n1758 1805 -1.4383759000000e+00\r\n1803 1805 -1.2827506000000e+00\r\n1804 1805 -1.7251084000000e+02\r\n1805 1805 -4.5327617000000e+01\r\n1806 1805  9.2591950000000e+00\r\n1809 1805 -1.5164090000000e+00\r\n1854 1805 -1.3893235000000e+00\r\n2910 1805 -1.9681342000000e+00\r\n700 1806  2.3496806000000e+01\r\n701 1806 -3.8058128000000e+00\r\n702 1806 -2.8045381000000e+00\r\n1756 1806  3.7780708000000e+01\r\n1757 1806 -6.1193978000000e+00\r\n1758 1806 -2.4314307000000e+00\r\n1803 1806 -2.1683601000000e+00\r\n1804 1806 -2.9161233000000e+02\r\n1805 1806  4.5009350000000e+01\r\n1806 1806  1.5651739000000e+01\r\n1809 1806 -2.5633354000000e+00\r\n1854 1806 -2.3485125000000e+00\r\n2910 1806 -3.3269340000000e+00\r\n703 1807 -3.3713512000000e-02\r\n705 1807 -1.0943588000000e-05\r\n1759 1807 -1.8201594000000e-01\r\n1761 1807 -1.2122384000000e-05\r\n1804 1807 -1.7390544000000e-02\r\n1806 1807 -1.1368816000000e-05\r\n1807 1807  2.6994798000000e+02\r\n1809 1807  7.0255065000000e-04\r\n1810 1807 -1.1518031000000e-03\r\n1812 1807 -1.2020739000000e-05\r\n1855 1807 -1.1382751000000e-03\r\n1857 1807 -1.1879554000000e-05\r\n2911 1807 -1.2300748000000e-03\r\n2913 1807 -1.2837617000000e-05\r\n703 1808  9.7211886000000e+00\r\n705 1808 -1.4597855000000e+00\r\n1759 1808  1.1574085000000e+01\r\n1761 1808 -1.6168748000000e+00\r\n1804 1808  2.9635679000000e+00\r\n1806 1808 -1.5164090000000e+00\r\n1807 1808 -1.7910548000000e+02\r\n1808 1808 -5.1505101000000e+01\r\n1809 1808  9.5663979000000e+00\r\n1812 1808 -1.6197874000000e+00\r\n1857 1808 -1.6165056000000e+00\r\n2913 1808 -1.7312366000000e+00\r\n703 1809  1.6432681000000e+01\r\n704 1809 -2.6616403000000e+00\r\n705 1809 -2.4676190000000e+00\r\n1759 1809  1.9564815000000e+01\r\n1760 1809 -3.1689595000000e+00\r\n1761 1809 -2.7331625000000e+00\r\n1804 1809  5.0096107000000e+00\r\n1805 1809 -8.1141850000000e-01\r\n1806 1809 -2.5633354000000e+00\r\n1807 1809 -3.0275963000000e+02\r\n1808 1809  4.6520833000000e+01\r\n1809 1809  1.6171028000000e+01\r\n1812 1809 -2.7380886000000e+00\r\n1857 1809 -2.7325391000000e+00\r\n2913 1809 -2.9264805000000e+00\r\n706 1810 -8.8675252000000e-03\r\n708 1810 -1.0837763000000e-05\r\n1762 1810 -6.2403481000000e-02\r\n1764 1810 -1.1998596000000e-05\r\n1807 1810 -5.2988615000000e-02\r\n1809 1810 -1.2020739000000e-05\r\n1810 1810  2.6984590000000e+02\r\n1812 1810  6.9097931000000e-04\r\n1813 1810 -1.1396550000000e-03\r\n1815 1810 -1.1893955000000e-05\r\n2914 1810 -6.0311753000000e-03\r\n2916 1810 -1.2854729000000e-05\r\n706 1811  7.2786198000000e+00\r\n708 1811 -1.4604714000000e+00\r\n1762 1811  5.7891668000000e-01\r\n1764 1811 -1.6167175000000e+00\r\n1807 1811  5.1032672000000e+00\r\n1809 1811 -1.6197874000000e+00\r\n1810 1811 -1.6781140000000e+02\r\n1811 1811 -5.1502392000000e+01\r\n1812 1811  8.0545803000000e+00\r\n1815 1811 -1.6197401000000e+00\r\n2916 1811 -1.7320662000000e+00\r\n706 1812  1.2303779000000e+01\r\n707 1812 -1.9928854000000e+00\r\n708 1812 -2.4687808000000e+00\r\n1762 1812  9.7860075000000e-01\r\n1763 1812 -1.5850733000000e-01\r\n1764 1812 -2.7328993000000e+00\r\n1807 1812  8.6265627000000e+00\r\n1808 1812 -1.3972740000000e+00\r\n1809 1812 -2.7380886000000e+00\r\n1810 1812 -2.8366839000000e+02\r\n1811 1812  4.3435542000000e+01\r\n1812 1812  1.3615461000000e+01\r\n1815 1812 -2.7380070000000e+00\r\n2916 1812 -2.9278847000000e+00\r\n709 1813 -1.0390959000000e-03\r\n711 1813 -1.0844475000000e-05\r\n1765 1813 -2.1406402000000e-02\r\n1767 1813 -1.1875319000000e-05\r\n1810 1813 -6.2819843000000e-02\r\n1812 1813 -1.1893955000000e-05\r\n1813 1813  2.6981877000000e+02\r\n1815 1813  6.7868937000000e-04\r\n2917 1813 -1.7018529000000e-02\r\n2919 1813 -1.2707884000000e-05\r\n709 1814  5.5196546000000e+00\r\n711 1814 -1.4591348000000e+00\r\n1767 1814 -1.6171003000000e+00\r\n1810 1814  5.2919592000000e+00\r\n1812 1814 -1.6197401000000e+00\r\n1813 1814 -1.6566496000000e+02\r\n1814 1814 -5.1500595000000e+01\r\n1815 1814  6.4322654000000e+00\r\n2919 1814 -1.7304932000000e+00\r\n709 1815  9.3304182000000e+00\r\n710 1815 -1.5112923000000e+00\r\n711 1815 -2.4665199000000e+00\r\n1767 1815 -2.7335442000000e+00\r\n1810 1815  8.9455222000000e+00\r\n1811 1815 -1.4489489000000e+00\r\n1812 1815 -2.7380070000000e+00\r\n1813 1815 -2.8003986000000e+02\r\n1814 1815  4.2852774000000e+01\r\n1815 1815  1.0873094000000e+01\r\n2919 1815 -2.9252241000000e+00\r\n1816 1816  1.0000000000000e+00\r\n1817 1817  1.0000000000000e+00\r\n1818 1818  1.0000000000000e+00\r\n1819 1819  1.0000000000000e+00\r\n1820 1820  1.0000000000000e+00\r\n1821 1821  1.0000000000000e+00\r\n1822 1822  1.0000000000000e+00\r\n1823 1823  1.0000000000000e+00\r\n1824 1824  1.0000000000000e+00\r\n1825 1825  1.0000000000000e+00\r\n1826 1826  1.0000000000000e+00\r\n1827 1827  1.0000000000000e+00\r\n1828 1828  1.0000000000000e+00\r\n1829 1829  1.0000000000000e+00\r\n1830 1830  1.0000000000000e+00\r\n727 1831 -1.7627555000000e-03\r\n729 1831 -1.8396914000000e-05\r\n1783 1831 -1.5354290000000e-02\r\n1785 1831 -4.3843017000000e-06\r\n1831 1831  1.2956429000000e+02\r\n1833 1831  3.5694669000000e-04\r\n1834 1831 -4.2519978000000e-04\r\n1836 1831 -4.4375773000000e-06\r\n1879 1831 -4.6811103000000e-04\r\n1881 1831 -4.8854185000000e-06\r\n2935 1831 -5.2523826000000e-02\r\n2937 1831 -2.1820208000000e-05\r\n727 1832  4.7361598000000e-01\r\n729 1832 -3.0418515000000e+00\r\n1783 1832  2.1429853000000e+00\r\n1785 1832 -7.2523623000000e-01\r\n1831 1832 -7.9601512000000e+01\r\n1832 1832 -2.4693282000000e+01\r\n1833 1832  8.9252988000000e+00\r\n1834 1832  2.6163863000000e+00\r\n1836 1832 -7.2388289000000e-01\r\n1881 1832 -8.2228962000000e-01\r\n2937 1832 -3.6092681000000e+00\r\n727 1833  8.0059990000000e-01\r\n728 1833 -1.2969360000000e-01\r\n729 1833 -5.1419423000000e+00\r\n1783 1833  3.6224997000000e+00\r\n1784 1833 -5.8682873000000e-01\r\n1785 1833 -1.2259385000000e+00\r\n1831 1833 -1.3455832000000e+02\r\n1832 1833  2.0661564000000e+01\r\n1833 1833  1.5087315000000e+01\r\n1834 1833  4.4227367000000e+00\r\n1835 1833 -7.1646354000000e-01\r\n1836 1833 -1.2236508000000e+00\r\n1881 1833 -1.3899972000000e+00\r\n2937 1833 -6.1011032000000e+00\r\n730 1834 -2.0406251000000e-03\r\n732 1834 -2.1296887000000e-05\r\n1786 1834 -3.6654252000000e-02\r\n1788 1834 -4.0655363000000e-06\r\n1831 1834 -1.2541000000000e-02\r\n1833 1834 -4.4375773000000e-06\r\n1834 1834  1.1342234000000e+02\r\n1836 1834  3.2863431000000e-04\r\n1837 1834 -1.7241399000000e-02\r\n1839 1834 -4.0635890000000e-06\r\n1882 1834 -4.1884696000000e-04\r\n1884 1834 -4.3712764000000e-06\r\n2938 1834 -5.2799427000000e-02\r\n2940 1834 -2.5256853000000e-05\r\n730 1835  4.6115962000000e-01\r\n732 1835 -3.4731796000000e+00\r\n1786 1835  2.7094703000000e+00\r\n1788 1835 -6.6324472000000e-01\r\n1833 1835 -7.2388289000000e-01\r\n1834 1835 -7.2226180000000e+01\r\n1835 1835 -2.1612590000000e+01\r\n1836 1835  1.0370998000000e+01\r\n1837 1835  3.9914205000000e+00\r\n1839 1835 -6.6297106000000e-01\r\n1884 1835 -7.2501701000000e-01\r\n2940 1835 -4.1202759000000e+00\r\n730 1836  7.7954422000000e-01\r\n731 1836 -1.2628154000000e-01\r\n732 1836 -5.8710629000000e+00\r\n1786 1836  4.5800887000000e+00\r\n1787 1836 -7.4194717000000e-01\r\n1788 1836 -1.1211489000000e+00\r\n1833 1836 -1.2236508000000e+00\r\n1834 1836 -1.2209113000000e+02\r\n1835 1836  1.8769138000000e+01\r\n1836 1836  1.7531134000000e+01\r\n1837 1836  6.7470971000000e+00\r\n1838 1836 -1.0929897000000e+00\r\n1839 1836 -1.1206863000000e+00\r\n1884 1836 -1.2255687000000e+00\r\n2940 1836 -6.9649144000000e+00\r\n733 1837 -2.1901939000000e-03\r\n735 1837 -2.2857855000000e-05\r\n1789 1837 -3.6900348000000e-02\r\n1791 1837 -4.0619711000000e-06\r\n1834 1837 -3.8936497000000e-04\r\n1836 1837 -4.0635890000000e-06\r\n1837 1837  1.0803430000000e+02\r\n1839 1837  3.1865465000000e-04\r\n1840 1837 -4.1747791000000e-02\r\n1842 1837 -4.0605177000000e-06\r\n1885 1837 -3.8233605000000e-04\r\n1887 1837 -3.9902320000000e-06\r\n2941 1837 -5.2785699000000e-02\r\n2943 1837 -2.7102875000000e-05\r\n733 1838  4.7214194000000e-01\r\n735 1838 -3.6432492000000e+00\r\n1789 1838  2.6576715000000e+00\r\n1791 1838 -6.4762352000000e-01\r\n1836 1838 -6.6297106000000e-01\r\n1837 1838 -7.0405894000000e+01\r\n1838 1838 -2.0588468000000e+01\r\n1839 1838  1.0572209000000e+01\r\n1840 1838  5.3173207000000e+00\r\n1842 1838 -6.4743079000000e-01\r\n1887 1838 -6.4753076000000e-01\r\n2943 1838 -4.3210899000000e+00\r\n733 1839  7.9810807000000e-01\r\n734 1839 -1.2928706000000e-01\r\n735 1839 -6.1585434000000e+00\r\n1789 1839  4.4925241000000e+00\r\n1790 1839 -7.2775254000000e-01\r\n1791 1839 -1.0947419000000e+00\r\n1836 1839 -1.1206863000000e+00\r\n1837 1839 -1.1901402000000e+02\r\n1838 1839  1.8306083000000e+01\r\n1839 1839  1.7871250000000e+01\r\n1840 1839  8.9883915000000e+00\r\n1841 1839 -1.4560467000000e+00\r\n1842 1839 -1.0944161000000e+00\r\n1887 1839 -1.0945853000000e+00\r\n2943 1839 -7.3043660000000e+00\r\n736 1840 -2.2595035000000e-03\r\n738 1840 -2.3581201000000e-05\r\n1792 1840 -4.3447644000000e-02\r\n1794 1840 -4.1887707000000e-06\r\n1837 1840 -3.8907069000000e-04\r\n1839 1840 -4.0605177000000e-06\r\n1840 1840  1.0804453000000e+02\r\n1842 1840  3.2079552000000e-04\r\n1843 1840 -5.1357459000000e-02\r\n1845 1840 -4.3870749000000e-06\r\n1888 1840 -3.9332922000000e-04\r\n1890 1840 -4.1049617000000e-06\r\n2944 1840 -5.1639411000000e-02\r\n2946 1840 -2.7951990000000e-05\r\n736 1841  6.4480901000000e-01\r\n738 1841 -3.6444874000000e+00\r\n1792 1841  2.9892049000000e+00\r\n1794 1841 -6.4769346000000e-01\r\n1839 1841 -6.4743079000000e-01\r\n1840 1841 -7.2357808000000e+01\r\n1841 1841 -2.0592914000000e+01\r\n1842 1841  1.0590126000000e+01\r\n1843 1841  6.7714276000000e+00\r\n1845 1841 -6.7841061000000e-01\r\n1890 1841 -6.4774506000000e-01\r\n2946 1841 -4.3220435000000e+00\r\n736 1842  1.0899851000000e+00\r\n737 1842 -1.7656524000000e-01\r\n738 1842 -6.1606414000000e+00\r\n1792 1842  5.0529519000000e+00\r\n1793 1842 -8.1852092000000e-01\r\n1794 1842 -1.0948610000000e+00\r\n1839 1842 -1.0944161000000e+00\r\n1840 1842 -1.2231364000000e+02\r\n1841 1842  1.8829160000000e+01\r\n1842 1842  1.7901548000000e+01\r\n1843 1842  1.1446421000000e+01\r\n1844 1842 -1.8541905000000e+00\r\n1845 1842 -1.1467853000000e+00\r\n1890 1842 -1.0949482000000e+00\r\n2946 1842 -7.3059823000000e+00\r\n739 1843 -2.1297054000000e-03\r\n741 1843 -2.2226569000000e-05\r\n1795 1843 -7.9778375000000e-02\r\n1797 1843 -5.0747994000000e-06\r\n1840 1843 -4.2036074000000e-04\r\n1842 1843 -4.3870749000000e-06\r\n1843 1843  1.1890076000000e+02\r\n1845 1843  3.4570613000000e-04\r\n1846 1843 -9.3184508000000e-02\r\n1848 1843 -5.3491131000000e-06\r\n1891 1843 -4.3647705000000e-04\r\n1893 1843 -4.5552719000000e-06\r\n2947 1843 -4.7033577000000e-02\r\n2949 1843 -2.6336006000000e-05\r\n739 1844  1.2772920000000e+00\r\n741 1844 -3.3123752000000e+00\r\n1795 1844  4.1842642000000e+00\r\n1797 1844 -7.5715025000000e-01\r\n1842 1844 -6.7841061000000e-01\r\n1843 1844 -8.1623769000000e+01\r\n1844 1844 -2.2658386000000e+01\r\n1845 1844  1.0173885000000e+01\r\n1846 1844  8.0234414000000e+00\r\n1848 1844 -7.9812720000000e-01\r\n1893 1844 -6.9594388000000e-01\r\n2949 1844 -3.9293287000000e+00\r\n739 1845  2.1591329000000e+00\r\n740 1845 -3.4974716000000e-01\r\n741 1845 -5.5992353000000e+00\r\n1795 1845  7.0730753000000e+00\r\n1796 1845 -1.1457322000000e+00\r\n1797 1845 -1.2798859000000e+00\r\n1842 1845 -1.1467853000000e+00\r\n1843 1845 -1.3797673000000e+02\r\n1844 1845  2.1252222000000e+01\r\n1845 1845  1.7197926000000e+01\r\n1846 1845  1.3562817000000e+01\r\n1847 1845 -2.1969729000000e+00\r\n1848 1845 -1.3491533000000e+00\r\n1893 1845 -1.1764226000000e+00\r\n2949 1845 -6.6421333000000e+00\r\n742 1846 -1.7438404000000e-03\r\n744 1846 -1.8199507000000e-05\r\n1798 1846 -1.0881623000000e-01\r\n1800 1846 -6.4939081000000e-06\r\n1843 1846 -5.1254132000000e-04\r\n1845 1846 -5.3491131000000e-06\r\n1846 1846  1.5129408000000e+02\r\n1848 1846  4.1790688000000e-04\r\n1849 1846 -1.0388809000000e-01\r\n1851 1846 -6.9062408000000e-06\r\n1894 1846 -5.6426636000000e-04\r\n1896 1846 -5.8889390000000e-06\r\n2950 1846 -3.7777033000000e-02\r\n2952 1846 -2.1524741000000e-05\r\n742 1847  2.5773871000000e+00\r\n744 1847 -2.6129498000000e+00\r\n1798 1847  6.7675836000000e+00\r\n1800 1847 -9.3536084000000e-01\r\n1845 1847 -7.9812720000000e-01\r\n1846 1847 -1.0485422000000e+02\r\n1847 1847 -2.8841163000000e+01\r\n1848 1847  9.3164495000000e+00\r\n1849 1847  8.7920353000000e+00\r\n1851 1847 -9.9479200000000e-01\r\n1896 1847 -8.7164905000000e-01\r\n2952 1847 -3.1003240000000e+00\r\n742 1848  4.3568151000000e+00\r\n743 1848 -7.0572155000000e-01\r\n744 1848 -4.4169304000000e+00\r\n1798 1848  1.1439923000000e+01\r\n1799 1848 -1.8530510000000e+00\r\n1800 1848 -1.5811340000000e+00\r\n1845 1848 -1.3491533000000e+00\r\n1846 1848 -1.7724558000000e+02\r\n1847 1848  2.7304935000000e+01\r\n1848 1848  1.5748525000000e+01\r\n1849 1848  1.4862056000000e+01\r\n1850 1848 -2.4073717000000e+00\r\n1851 1848 -1.6815964000000e+00\r\n1896 1848 -1.4734355000000e+00\r\n2952 1848 -5.2407877000000e+00\r\n745 1849 -1.4815586000000e-03\r\n747 1849 -1.5462216000000e-05\r\n1801 1849 -1.5796506000000e-01\r\n1803 1849 -8.0873000000000e-06\r\n1846 1849 -6.6174218000000e-04\r\n1848 1849 -6.9062408000000e-06\r\n1849 1849  1.8368457000000e+02\r\n1851 1849  4.9431217000000e-04\r\n1852 1849 -9.6520723000000e-02\r\n1854 1849 -8.7060903000000e-06\r\n1897 1849 -7.3050679000000e-04\r\n1899 1849 -7.6238993000000e-06\r\n2953 1849 -2.4271380000000e-02\r\n2955 1849 -1.8212201000000e-05\r\n745 1850  4.5255625000000e+00\r\n747 1850 -2.1468502000000e+00\r\n1801 1850  1.0780072000000e+01\r\n1803 1850 -1.1308285000000e+00\r\n1848 1850 -9.9479200000000e-01\r\n1849 1850 -1.2856659000000e+02\r\n1850 1850 -3.5024614000000e+01\r\n1851 1850  9.1376521000000e+00\r\n1852 1850  7.9663073000000e+00\r\n1854 1850 -1.2173762000000e+00\r\n1899 1850 -1.0973587000000e+00\r\n2955 1850 -2.5465029000000e+00\r\n745 1851  7.6500063000000e+00\r\n746 1851 -1.2391313000000e+00\r\n747 1851 -3.6290334000000e+00\r\n1801 1851  1.8222623000000e+01\r\n1802 1851 -2.9516605000000e+00\r\n1803 1851 -1.9115514000000e+00\r\n1848 1851 -1.6815964000000e+00\r\n1849 1851 -2.1732884000000e+02\r\n1850 1851  3.3487759000000e+01\r\n1851 1851  1.5446279000000e+01\r\n1852 1851  1.3466238000000e+01\r\n1853 1851 -2.1812317000000e+00\r\n1854 1851 -2.0578516000000e+00\r\n1899 1851 -1.8549738000000e+00\r\n2955 1851 -4.3046060000000e+00\r\n748 1852 -1.2303848000000e-03\r\n750 1852 -1.2840853000000e-05\r\n1804 1852 -2.0536677000000e-01\r\n1806 1852 -1.0152934000000e-05\r\n1849 1852 -8.3420016000000e-04\r\n1851 1852 -8.7060903000000e-06\r\n1852 1852  2.2682106000000e+02\r\n1854 1852  5.9753006000000e-04\r\n1855 1852 -4.3583597000000e-02\r\n1857 1852 -1.0807959000000e-05\r\n1900 1852 -9.2131834000000e-04\r\n1902 1852 -9.6152951000000e-06\r\n2956 1852 -1.5524926000000e-02\r\n2958 1852 -1.5067541000000e-05\r\n748 1853  5.9457629000000e+00\r\n750 1853 -1.7380630000000e+00\r\n1804 1853  1.3685122000000e+01\r\n1806 1853 -1.3893235000000e+00\r\n1851 1853 -1.2173762000000e+00\r\n1852 1853 -1.5211895000000e+02\r\n1853 1853 -4.3268319000000e+01\r\n1854 1853  9.2315550000000e+00\r\n1855 1853  2.4221967000000e+00\r\n1857 1853 -1.4789555000000e+00\r\n1902 1853 -1.3411889000000e+00\r\n2958 1853 -2.0617751000000e+00\r\n748 1854  1.0050718000000e+01\r\n749 1854 -1.6279674000000e+00\r\n750 1854 -2.9380216000000e+00\r\n1804 1854  2.3133330000000e+01\r\n1805 1854 -3.7470265000000e+00\r\n1806 1854 -2.3485125000000e+00\r\n1851 1854 -2.0578516000000e+00\r\n1852 1854 -2.5714188000000e+02\r\n1853 1854  3.9525830000000e+01\r\n1854 1854  1.5605019000000e+01\r\n1855 1854  4.0944812000000e+00\r\n1856 1854 -6.6320456000000e-01\r\n1857 1854 -2.5000264000000e+00\r\n1902 1854 -2.2671456000000e+00\r\n2958 1854 -3.4852246000000e+00\r\n751 1855 -1.0395741000000e-03\r\n753 1855 -1.0849465000000e-05\r\n1807 1855 -1.7507871000000e-01\r\n1809 1855 -1.1879554000000e-05\r\n1852 1855 -1.0355970000000e-03\r\n1854 1855 -1.0807959000000e-05\r\n1855 1855  2.6990596000000e+02\r\n1857 1855  6.8922445000000e-04\r\n1903 1855 -1.1115532000000e-03\r\n1905 1855 -1.1600672000000e-05\r\n2959 1855 -1.9985788000000e-02\r\n2961 1855 -1.2725786000000e-05\r\n751 1856  5.1931919000000e+00\r\n753 1856 -1.4599415000000e+00\r\n1807 1856  1.0116538000000e+01\r\n1809 1856 -1.6165056000000e+00\r\n1854 1856 -1.4789555000000e+00\r\n1855 1856 -1.7015155000000e+02\r\n1856 1856 -5.1508807000000e+01\r\n1857 1856  7.8930001000000e+00\r\n1905 1856 -1.6001767000000e+00\r\n2961 1856 -1.7316203000000e+00\r\n751 1857  8.7785651000000e+00\r\n752 1857 -1.4219055000000e+00\r\n753 1857 -2.4678833000000e+00\r\n1807 1857  1.7100984000000e+01\r\n1808 1857 -2.7699267000000e+00\r\n1809 1857 -2.7325391000000e+00\r\n1854 1857 -2.5000264000000e+00\r\n1855 1857 -2.8762397000000e+02\r\n1856 1857  4.4061014000000e+01\r\n1857 1857  1.3342320000000e+01\r\n1905 1857 -2.7049376000000e+00\r\n2961 1857 -2.9271289000000e+00\r\n1858 1858  1.0000000000000e+00\r\n1859 1859  1.0000000000000e+00\r\n1860 1860  1.0000000000000e+00\r\n1861 1861  1.0000000000000e+00\r\n1862 1862  1.0000000000000e+00\r\n1863 1863  1.0000000000000e+00\r\n1864 1864  1.0000000000000e+00\r\n1865 1865  1.0000000000000e+00\r\n1866 1866  1.0000000000000e+00\r\n1867 1867  1.0000000000000e+00\r\n1868 1868  1.0000000000000e+00\r\n1869 1869  1.0000000000000e+00\r\n1870 1870  1.0000000000000e+00\r\n1871 1871  1.0000000000000e+00\r\n1872 1872  1.0000000000000e+00\r\n1873 1873  1.0000000000000e+00\r\n1874 1874  1.0000000000000e+00\r\n1875 1875  1.0000000000000e+00\r\n772 1876 -1.3682081000000e-03\r\n774 1876 -1.4279239000000e-05\r\n1876 1876  1.6193772000000e+02\r\n1878 1876  4.2113976000000e-04\r\n1879 1876 -5.2298365000000e-04\r\n1881 1876 -5.4580940000000e-06\r\n1924 1876 -5.7036811000000e-03\r\n1926 1876 -5.6985528000000e-06\r\n2980 1876 -5.1615507000000e-02\r\n2982 1876 -1.6926631000000e-05\r\n772 1877  5.5238695000000e-01\r\n774 1877 -2.4305303000000e+00\r\n1876 1877 -9.6325749000000e+01\r\n1877 1877 -3.0856113000000e+01\r\n1878 1877  7.2066814000000e+00\r\n1879 1877  2.7981439000000e+00\r\n1881 1877 -9.1859475000000e-01\r\n1926 1877 -9.7071914000000e-01\r\n2982 1877 -2.8833788000000e+00\r\n772 1878  9.3375490000000e-01\r\n773 1878 -1.5126664000000e-01\r\n774 1878 -4.1085685000000e+00\r\n1876 1878 -1.6282905000000e+02\r\n1877 1878  2.4983323000000e+01\r\n1878 1878  1.2182174000000e+01\r\n1879 1878  4.7299825000000e+00\r\n1880 1878 -7.6624879000000e-01\r\n1881 1878 -1.5527926000000e+00\r\n1926 1878 -1.6409036000000e+00\r\n2982 1878 -4.8740636000000e+00\r\n775 1879 -1.5401932000000e-03\r\n777 1879 -1.6074153000000e-05\r\n1831 1879 -2.5316249000000e-02\r\n1833 1879 -4.8854185000000e-06\r\n1876 1879 -7.7146665000000e-03\r\n1878 1879 -5.4580940000000e-06\r\n1879 1879  1.4577699000000e+02\r\n1881 1879  3.9679183000000e-04\r\n1882 1879 -4.7447408000000e-04\r\n1884 1879 -4.9518262000000e-06\r\n1927 1879 -5.4925528000000e-03\r\n1929 1879 -5.4636132000000e-06\r\n2983 1879 -5.2014773000000e-02\r\n2985 1879 -1.9060727000000e-05\r\n775 1880  5.2312342000000e-01\r\n777 1880 -2.7035268000000e+00\r\n1831 1880  3.6040503000000e+00\r\n1833 1880 -8.2228962000000e-01\r\n1878 1880 -9.1859475000000e-01\r\n1879 1880 -9.0858930000000e+01\r\n1880 1880 -2.7776287000000e+01\r\n1881 1880  9.3962922000000e+00\r\n1882 1880  3.0620254000000e+00\r\n1884 1880 -8.2121591000000e-01\r\n1929 1880 -9.1952951000000e-01\r\n2985 1880 -3.2080206000000e+00\r\n775 1881  8.8428709000000e-01\r\n776 1881 -1.4325203000000e-01\r\n777 1881 -4.5700380000000e+00\r\n1831 1881  6.0922817000000e+00\r\n1832 1881 -9.8693260000000e-01\r\n1833 1881 -1.3899972000000e+00\r\n1878 1881 -1.5527926000000e+00\r\n1879 1881 -1.5358782000000e+02\r\n1880 1881  2.3611475000000e+01\r\n1881 1881  1.5883482000000e+01\r\n1882 1881  5.1760440000000e+00\r\n1883 1881 -8.3850459000000e-01\r\n1884 1881 -1.3881823000000e+00\r\n1929 1881 -1.5543716000000e+00\r\n2985 1881 -5.4228342000000e+00\r\n778 1882 -1.7572603000000e-03\r\n780 1882 -1.8339563000000e-05\r\n1834 1882 -1.4385499000000e-02\r\n1836 1882 -4.3712764000000e-06\r\n1879 1882 -5.2273750000000e-03\r\n1881 1882 -4.9518262000000e-06\r\n1882 1882  1.2957379000000e+02\r\n1884 1882  3.6139659000000e-04\r\n1885 1882 -8.5518109000000e-03\r\n1887 1882 -4.2522785000000e-06\r\n1930 1882 -4.5146567000000e-04\r\n1932 1882 -4.7117000000000e-06\r\n2986 1882 -5.2447066000000e-02\r\n2988 1882 -2.1750669000000e-05\r\n778 1883  4.7974413000000e-01\r\n780 1883 -3.0402072000000e+00\r\n1834 1883  3.0947403000000e+00\r\n1836 1883 -7.2501701000000e-01\r\n1881 1883 -8.2121591000000e-01\r\n1882 1883 -8.1877839000000e+01\r\n1883 1883 -2.4695931000000e+01\r\n1884 1883  9.6944012000000e+00\r\n1885 1883  3.9384884000000e+00\r\n1887 1883 -7.0530200000000e-01\r\n1932 1883 -7.9257688000000e-01\r\n2988 1883 -3.6073107000000e+00\r\n778 1884  8.1095948000000e-01\r\n779 1884 -1.3137192000000e-01\r\n780 1884 -5.1391662000000e+00\r\n1834 1884  5.2313490000000e+00\r\n1835 1884 -8.4745588000000e-01\r\n1836 1884 -1.2255687000000e+00\r\n1881 1884 -1.3881823000000e+00\r\n1882 1884 -1.3840630000000e+02\r\n1883 1884  2.1278445000000e+01\r\n1884 1884  1.6387415000000e+01\r\n1885 1884  6.6576208000000e+00\r\n1886 1884 -1.0785057000000e+00\r\n1887 1884 -1.1922425000000e+00\r\n1932 1884 -1.3397720000000e+00\r\n2988 1884 -6.0977979000000e+00\r\n781 1885 -2.1547261000000e-03\r\n783 1885 -2.2487696000000e-05\r\n1837 1885 -2.1837092000000e-02\r\n1839 1885 -3.9902320000000e-06\r\n1882 1885 -4.0744482000000e-04\r\n1884 1885 -4.2522785000000e-06\r\n1885 1885  1.0800479000000e+02\r\n1887 1885  3.1791075000000e-04\r\n1888 1885 -2.4076337000000e-02\r\n1890 1885 -3.9845664000000e-06\r\n1933 1885 -3.8464484000000e-04\r\n1935 1885 -4.0143276000000e-06\r\n2989 1885 -5.2925043000000e-02\r\n2991 1885 -2.6665641000000e-05\r\n781 1886  4.5923005000000e-01\r\n783 1886 -3.6481002000000e+00\r\n1837 1886  3.0465115000000e+00\r\n1839 1886 -6.4753076000000e-01\r\n1884 1886 -7.0530200000000e-01\r\n1885 1886 -7.0290947000000e+01\r\n1886 1886 -2.0585626000000e+01\r\n1887 1886  1.0639977000000e+01\r\n1888 1886  4.8224163000000e+00\r\n1890 1886 -6.4663870000000e-01\r\n1935 1886 -6.6305749000000e-01\r\n2991 1886 -4.3270355000000e+00\r\n781 1887  7.7628199000000e-01\r\n782 1887 -1.2575274000000e-01\r\n783 1887 -6.1667448000000e+00\r\n1837 1887  5.1498198000000e+00\r\n1838 1887 -8.3423801000000e-01\r\n1839 1887 -1.0945853000000e+00\r\n1884 1887 -1.1922425000000e+00\r\n1885 1887 -1.1881974000000e+02\r\n1886 1887  1.8281811000000e+01\r\n1887 1887  1.7985806000000e+01\r\n1888 1887  8.1518075000000e+00\r\n1889 1887 -1.3205409000000e+00\r\n1890 1887 -1.0930774000000e+00\r\n1935 1887 -1.1208317000000e+00\r\n2991 1887 -7.3144156000000e+00\r\n784 1888 -2.2167704000000e-03\r\n786 1888 -2.3135219000000e-05\r\n1840 1888 -3.9496526000000e-02\r\n1842 1888 -4.1049617000000e-06\r\n1885 1888 -3.8179319000000e-04\r\n1887 1888 -3.9845664000000e-06\r\n1888 1888  1.0802336000000e+02\r\n1890 1888  3.1938638000000e-04\r\n1891 1888 -3.1541777000000e-02\r\n1893 1888 -4.1991334000000e-06\r\n1936 1888 -3.8492957000000e-04\r\n1938 1888 -4.0172991000000e-06\r\n2992 1888 -5.2634792000000e-02\r\n2994 1888 -2.7427728000000e-05\r\n784 1889  5.0941971000000e-01\r\n786 1889 -3.6492619000000e+00\r\n1840 1889  3.5366700000000e+00\r\n1842 1889 -6.4774506000000e-01\r\n1887 1889 -6.4663870000000e-01\r\n1888 1889 -7.1838586000000e+01\r\n1889 1889 -2.0591437000000e+01\r\n1890 1889  1.0583862000000e+01\r\n1891 1889  5.8379544000000e+00\r\n1893 1889 -6.6265230000000e-01\r\n1938 1889 -6.4743050000000e-01\r\n2994 1889 -4.3278193000000e+00\r\n784 1890  8.6112308000000e-01\r\n785 1890 -1.3949396000000e-01\r\n786 1890 -6.1687123000000e+00\r\n1840 1890  5.9783870000000e+00\r\n1841 1890 -9.6844330000000e-01\r\n1842 1890 -1.0949482000000e+00\r\n1887 1890 -1.0930774000000e+00\r\n1888 1890 -1.2143595000000e+02\r\n1889 1890  1.8690919000000e+01\r\n1890 1890  1.7890960000000e+01\r\n1891 1890  9.8684780000000e+00\r\n1892 1890 -1.5986020000000e+00\r\n1893 1890 -1.1201474000000e+00\r\n1938 1890 -1.0944165000000e+00\r\n2994 1890 -7.3157458000000e+00\r\n787 1891 -2.1803832000000e-03\r\n789 1891 -2.2755466000000e-05\r\n1843 1891 -6.1991313000000e-02\r\n1845 1891 -4.5552719000000e-06\r\n1888 1891 -4.0235257000000e-04\r\n1890 1891 -4.1991334000000e-06\r\n1891 1891  1.1344473000000e+02\r\n1893 1891  3.3287716000000e-04\r\n1894 1891 -4.5095527000000e-02\r\n1896 1891 -4.9208480000000e-06\r\n1939 1891 -4.1622535000000e-04\r\n1941 1891 -4.3439161000000e-06\r\n2995 1891 -5.0597208000000e-02\r\n2997 1891 -2.6957113000000e-05\r\n787 1892  7.8845270000000e-01\r\n789 1892 -3.4736169000000e+00\r\n1843 1892  4.6147383000000e+00\r\n1845 1892 -6.9594388000000e-01\r\n1890 1892 -6.6265230000000e-01\r\n1891 1892 -7.7174379000000e+01\r\n1892 1892 -2.1627893000000e+01\r\n1893 1892  1.0384961000000e+01\r\n1894 1892  6.7286829000000e+00\r\n1896 1892 -7.5184989000000e-01\r\n1941 1892 -6.8011853000000e-01\r\n2997 1892 -4.1183464000000e+00\r\n787 1893  1.3327994000000e+00\r\n788 1893 -2.1589688000000e-01\r\n789 1893 -5.8717972000000e+00\r\n1843 1893  7.8007472000000e+00\r\n1844 1893 -1.2636238000000e+00\r\n1845 1893 -1.1764226000000e+00\r\n1890 1893 -1.1201474000000e+00\r\n1891 1893 -1.3045548000000e+02\r\n1892 1893  2.0085606000000e+01\r\n1893 1893  1.7554727000000e+01\r\n1894 1893  1.1374157000000e+01\r\n1895 1893 -1.8424714000000e+00\r\n1896 1893 -1.2709260000000e+00\r\n1941 1893 -1.1496714000000e+00\r\n2997 1893 -6.9616488000000e+00\r\n790 1894 -1.8180626000000e-03\r\n792 1894 -1.8974124000000e-05\r\n1846 1894 -1.2712021000000e-01\r\n1848 1894 -5.8889390000000e-06\r\n1891 1894 -4.7150582000000e-04\r\n1893 1894 -4.9208480000000e-06\r\n1894 1894  1.4053661000000e+02\r\n1896 1894  3.9251933000000e-04\r\n1897 1894 -1.1247037000000e-01\r\n1899 1894 -6.4451798000000e-06\r\n1942 1894 -5.2983208000000e-04\r\n1944 1894 -5.5295673000000e-06\r\n2998 1894 -4.5817235000000e-02\r\n3000 1894 -2.2481667000000e-05\r\n790 1895  1.4265019000000e+00\r\n792 1895 -2.8041797000000e+00\r\n1846 1895  6.7410271000000e+00\r\n1848 1895 -8.7164905000000e-01\r\n1893 1895 -7.5184989000000e-01\r\n1894 1895 -9.6260607000000e+01\r\n1895 1895 -2.6784777000000e+01\r\n1896 1895  9.5539122000000e+00\r\n1897 1895  7.5749029000000e+00\r\n1899 1895 -9.5401471000000e-01\r\n1944 1895 -8.4152480000000e-01\r\n3000 1895 -3.3276778000000e+00\r\n790 1896  2.4113587000000e+00\r\n791 1896 -3.9060161000000e-01\r\n792 1896 -4.7401854000000e+00\r\n1846 1896  1.1395032000000e+01\r\n1847 1896 -1.8458133000000e+00\r\n1848 1896 -1.4734355000000e+00\r\n1893 1896 -1.2709260000000e+00\r\n1894 1896 -1.6271893000000e+02\r\n1895 1896  2.5043815000000e+01\r\n1896 1896  1.6149932000000e+01\r\n1897 1896  1.2804616000000e+01\r\n1898 1896 -2.0741433000000e+00\r\n1899 1896 -1.6126664000000e+00\r\n1944 1896 -1.4225135000000e+00\r\n3000 1896 -5.6251066000000e+00\r\n793 1897 -1.4398869000000e-03\r\n795 1897 -1.5027311000000e-05\r\n1849 1897 -1.4525831000000e-01\r\n1851 1897 -7.6238993000000e-06\r\n1894 1897 -6.1756424000000e-04\r\n1896 1897 -6.4451798000000e-06\r\n1897 1897  1.8371826000000e+02\r\n1899 1897  4.9185286000000e-04\r\n1900 1897 -1.2848283000000e-01\r\n1902 1897 -8.3665884000000e-06\r\n1945 1897 -7.0272142000000e-04\r\n1947 1897 -7.3339187000000e-06\r\n3001 1897 -3.9784889000000e-02\r\n3003 1897 -1.7755663000000e-05\r\n793 1898  2.2860263000000e+00\r\n795 1898 -2.1546054000000e+00\r\n1849 1898  9.4717085000000e+00\r\n1851 1898 -1.0973587000000e+00\r\n1896 1898 -9.5401471000000e-01\r\n1897 1898 -1.2836321000000e+02\r\n1898 1898 -3.5025750000000e+01\r\n1899 1898  9.0671103000000e+00\r\n1900 1898  1.1312072000000e+01\r\n1902 1898 -1.2043097000000e+00\r\n1947 1898 -1.0972324000000e+00\r\n3003 1898 -2.5556453000000e+00\r\n793 1899  3.8642962000000e+00\r\n794 1899 -6.2594283000000e-01\r\n795 1899 -3.6421424000000e+00\r\n1849 1899  1.6010965000000e+01\r\n1850 1899 -2.5934732000000e+00\r\n1851 1899 -1.8549738000000e+00\r\n1896 1899 -1.6126664000000e+00\r\n1897 1899 -2.1698503000000e+02\r\n1898 1899  3.3430196000000e+01\r\n1899 1899  1.5327034000000e+01\r\n1900 1899  1.9121914000000e+01\r\n1901 1899 -3.0973879000000e+00\r\n1902 1899 -2.0357636000000e+00\r\n1947 1899 -1.8547602000000e+00\r\n3003 1899 -4.3200606000000e+00\r\n796 1900 -1.2311274000000e-03\r\n798 1900 -1.2848602000000e-05\r\n1852 1900 -1.4077561000000e-01\r\n1854 1900 -9.6152951000000e-06\r\n1897 1900 -8.0166977000000e-04\r\n1899 1900 -8.3665884000000e-06\r\n1900 1900  2.2139825000000e+02\r\n1902 1900  5.7404826000000e-04\r\n1903 1900 -6.7449494000000e-02\r\n1905 1900 -1.0368966000000e-05\r\n3004 1900 -3.2199498000000e-02\r\n3006 1900 -1.5150297000000e-05\r\n796 1901  3.3587507000000e+00\r\n798 1901 -1.7813940000000e+00\r\n1852 1901  7.7545697000000e+00\r\n1854 1901 -1.3411889000000e+00\r\n1899 1901 -1.2043097000000e+00\r\n1900 1901 -1.4289282000000e+02\r\n1901 1901 -4.2241754000000e+01\r\n1902 1901  7.8912239000000e+00\r\n1903 1901  4.8152646000000e+00\r\n1905 1901 -1.4463522000000e+00\r\n3006 1901 -2.1132209000000e+00\r\n796 1902  5.6776321000000e+00\r\n797 1902 -9.1964831000000e-01\r\n798 1902 -3.0112683000000e+00\r\n1852 1902  1.3108325000000e+01\r\n1853 1902 -2.1232529000000e+00\r\n1854 1902 -2.2671456000000e+00\r\n1899 1902 -2.0357636000000e+00\r\n1900 1902 -2.4154602000000e+02\r\n1901 1902  3.7042029000000e+01\r\n1902 1902  1.3339323000000e+01\r\n1903 1902  8.1397233000000e+00\r\n1904 1902 -1.3184515000000e+00\r\n1905 1902 -2.4449138000000e+00\r\n3006 1902 -3.5721885000000e+00\r\n799 1903 -1.0423520000000e-03\r\n801 1903 -1.0878457000000e-05\r\n1855 1903 -1.4048118000000e-01\r\n1857 1903 -1.1600672000000e-05\r\n1900 1903 -9.9353355000000e-04\r\n1902 1903 -1.0368966000000e-05\r\n1903 1903  2.6448201000000e+02\r\n1905 1903  6.6438031000000e-04\r\n3007 1903 -3.1922291000000e-02\r\n3009 1903 -1.2812511000000e-05\r\n799 1904  3.3795222000000e+00\r\n801 1904 -1.4898504000000e+00\r\n1855 1904  6.5452608000000e+00\r\n1857 1904 -1.6001767000000e+00\r\n1902 1904 -1.4463522000000e+00\r\n1903 1904 -1.6166186000000e+02\r\n1904 1904 -5.0484398000000e+01\r\n1905 1904  6.3093915000000e+00\r\n3009 1904 -1.7673253000000e+00\r\n799 1905  5.7127422000000e+00\r\n800 1905 -9.2532827000000e-01\r\n801 1905 -2.5184421000000e+00\r\n1855 1905  1.1064105000000e+01\r\n1856 1905 -1.7921216000000e+00\r\n1857 1905 -2.7049376000000e+00\r\n1902 1905 -2.4449138000000e+00\r\n1903 1905 -2.7327311000000e+02\r\n1904 1905  4.1773412000000e+01\r\n1905 1905  1.0665392000000e+01\r\n3009 1905 -2.9874848000000e+00\r\n1906 1906  1.0000000000000e+00\r\n1907 1907  1.0000000000000e+00\r\n1908 1908  1.0000000000000e+00\r\n1909 1909  1.0000000000000e+00\r\n1910 1910  1.0000000000000e+00\r\n1911 1911  1.0000000000000e+00\r\n1912 1912  1.0000000000000e+00\r\n1913 1913  1.0000000000000e+00\r\n1914 1914  1.0000000000000e+00\r\n1915 1915  1.0000000000000e+00\r\n1916 1916  1.0000000000000e+00\r\n1917 1917  1.0000000000000e+00\r\n1918 1918  1.0000000000000e+00\r\n1919 1919  1.0000000000000e+00\r\n1920 1920  1.0000000000000e+00\r\n1921 1921  1.0000000000000e+00\r\n1922 1922  1.0000000000000e+00\r\n1923 1923  1.0000000000000e+00\r\n820 1924 -1.3598413000000e-03\r\n822 1924 -1.4191919000000e-05\r\n1876 1924 -5.4602393000000e-04\r\n1878 1924 -5.6985528000000e-06\r\n1924 1924  1.6194470000000e+02\r\n1926 1924  4.2684968000000e-04\r\n1927 1924 -5.4574734000000e-04\r\n1929 1924 -5.6956662000000e-06\r\n1972 1924 -8.8439480000000e-03\r\n1974 1924 -5.6667857000000e-06\r\n3028 1924 -5.1505774000000e-02\r\n3030 1924 -1.6818596000000e-05\r\n820 1925  5.6215850000000e-01\r\n822 1925 -2.4292229000000e+00\r\n1876 1925  1.3611340000000e+00\r\n1878 1925 -9.7071914000000e-01\r\n1924 1925 -9.6497379000000e+01\r\n1925 1925 -3.0852941000000e+01\r\n1926 1925  8.2246738000000e+00\r\n1927 1925  1.5944959000000e+00\r\n1929 1925 -9.6938615000000e-01\r\n1974 1925 -9.7074826000000e-01\r\n3030 1925 -2.8811403000000e+00\r\n820 1926  9.5027273000000e-01\r\n821 1926 -1.5394300000000e-01\r\n822 1926 -4.1063585000000e+00\r\n1876 1926  2.3008609000000e+00\r\n1877 1926 -3.7273661000000e-01\r\n1878 1926 -1.6409036000000e+00\r\n1924 1926 -1.6311917000000e+02\r\n1925 1926  2.5038158000000e+01\r\n1926 1926  1.3902989000000e+01\r\n1927 1926  2.6953358000000e+00\r\n1928 1926 -4.3664106000000e-01\r\n1929 1926 -1.6386503000000e+00\r\n1974 1926 -1.6409528000000e+00\r\n3030 1926 -4.8702796000000e+00\r\n823 1927 -1.3713259000000e-03\r\n825 1927 -1.4311777000000e-05\r\n1879 1927 -5.2351249000000e-04\r\n1881 1927 -5.4636132000000e-06\r\n1924 1927 -8.0473167000000e-03\r\n1926 1927 -5.6956662000000e-06\r\n1927 1927  1.6194053000000e+02\r\n1929 1927  4.3210605000000e-04\r\n1930 1927 -5.0176739000000e-04\r\n1932 1927 -5.2366715000000e-06\r\n1975 1927 -5.4167195000000e-04\r\n1977 1927 -5.6531335000000e-06\r\n3031 1927 -5.1855591000000e-02\r\n3033 1927 -1.6968364000000e-05\r\n823 1928  5.2784843000000e-01\r\n825 1928 -2.4336098000000e+00\r\n1879 1928  2.5778537000000e+00\r\n1881 1928 -9.1952951000000e-01\r\n1926 1928 -9.6938615000000e-01\r\n1927 1928 -9.8694245000000e+01\r\n1928 1928 -3.0856855000000e+01\r\n1929 1928  9.0656151000000e+00\r\n1930 1928  2.6143063000000e+00\r\n1932 1928 -8.8078221000000e-01\r\n1977 1928 -9.7084846000000e-01\r\n3033 1928 -2.8880003000000e+00\r\n823 1929  8.9227438000000e-01\r\n824 1929 -1.4454689000000e-01\r\n825 1929 -4.1137712000000e+00\r\n1879 1929  4.3576008000000e+00\r\n1880 1929 -7.0592372000000e-01\r\n1881 1929 -1.5543716000000e+00\r\n1926 1929 -1.6386503000000e+00\r\n1927 1929 -1.6683264000000e+02\r\n1928 1929  2.5630146000000e+01\r\n1929 1929  1.5324507000000e+01\r\n1930 1929  4.4192202000000e+00\r\n1931 1929 -7.1590595000000e-01\r\n1932 1929 -1.4888732000000e+00\r\n1977 1929 -1.6411213000000e+00\r\n3033 1929 -4.8818723000000e+00\r\n826 1930 -1.6636560000000e-03\r\n828 1930 -1.7362667000000e-05\r\n1882 1930 -1.2450066000000e-02\r\n1884 1930 -4.7117000000000e-06\r\n1927 1930 -2.3695041000000e-02\r\n1929 1930 -5.2366715000000e-06\r\n1930 1930  1.3498291000000e+02\r\n1932 1930  3.7268180000000e-04\r\n1933 1930 -1.9379559000000e-03\r\n1935 1930 -4.3848042000000e-06\r\n1978 1930 -4.5528563000000e-04\r\n1980 1930 -4.7515669000000e-06\r\n3034 1930 -5.2252131000000e-02\r\n3036 1930 -2.0589990000000e-05\r\n826 1931  4.9816244000000e-01\r\n828 1931 -2.9189937000000e+00\r\n1882 1931  2.8246275000000e+00\r\n1884 1931 -7.9257688000000e-01\r\n1929 1931 -8.8078221000000e-01\r\n1930 1931 -8.4221274000000e+01\r\n1931 1931 -2.5721199000000e+01\r\n1932 1931  9.6051625000000e+00\r\n1933 1931  3.4298592000000e+00\r\n1935 1931 -7.3761286000000e-01\r\n1980 1931 -8.0898352000000e-01\r\n3036 1931 -3.4633279000000e+00\r\n826 1932  8.4209378000000e-01\r\n827 1932 -1.3641669000000e-01\r\n828 1932 -4.9342670000000e+00\r\n1882 1932  4.7747504000000e+00\r\n1883 1932 -7.7349535000000e-01\r\n1884 1932 -1.3397720000000e+00\r\n1929 1932 -1.4888732000000e+00\r\n1930 1932 -1.4236764000000e+02\r\n1931 1932  2.1881898000000e+01\r\n1932 1932  1.6236566000000e+01\r\n1933 1932  5.7978341000000e+00\r\n1934 1932 -9.3923186000000e-01\r\n1935 1932 -1.2468608000000e+00\r\n1980 1932 -1.3675057000000e+00\r\n3036 1932 -5.8544095000000e+00\r\n829 1933 -2.0178442000000e-03\r\n831 1933 -2.1059135000000e-05\r\n1885 1933 -1.6712968000000e-02\r\n1887 1933 -4.0143276000000e-06\r\n1930 1933 -4.2014317000000e-04\r\n1932 1933 -4.3848042000000e-06\r\n1933 1933  1.1338744000000e+02\r\n1935 1933  3.2763065000000e-04\r\n1936 1933 -1.3111279000000e-02\r\n1938 1933 -4.0079459000000e-06\r\n1981 1933 -3.8802292000000e-04\r\n1983 1933 -4.0495827000000e-06\r\n3037 1933 -5.2868056000000e-02\r\n3039 1933 -2.4974195000000e-05\r\n829 1934  4.5515115000000e-01\r\n831 1934 -3.4774202000000e+00\r\n1885 1934  2.9823913000000e+00\r\n1887 1934 -6.6305749000000e-01\r\n1932 1934 -7.3761286000000e-01\r\n1933 1934 -7.2722891000000e+01\r\n1934 1934 -2.1611440000000e+01\r\n1935 1934  1.0346880000000e+01\r\n1936 1934  4.2195423000000e+00\r\n1938 1934 -6.6202847000000e-01\r\n1983 1934 -6.7953492000000e-01\r\n3039 1934 -4.1247997000000e+00\r\n829 1935  7.6938705000000e-01\r\n830 1935 -1.2463713000000e-01\r\n831 1935 -5.8782276000000e+00\r\n1885 1935  5.0414313000000e+00\r\n1886 1935 -8.1668844000000e-01\r\n1887 1935 -1.1208317000000e+00\r\n1932 1935 -1.2468608000000e+00\r\n1933 1935 -1.2293071000000e+02\r\n1934 1935  1.8908185000000e+01\r\n1935 1935  1.7490356000000e+01\r\n1936 1935  7.1327105000000e+00\r\n1937 1935 -1.1554659000000e+00\r\n1938 1935 -1.1190923000000e+00\r\n1983 1935 -1.1486850000000e+00\r\n3039 1935 -6.9725578000000e+00\r\n832 1936 -2.1727911000000e-03\r\n834 1936 -2.2676231000000e-05\r\n1888 1936 -2.7603420000000e-02\r\n1890 1936 -4.0172991000000e-06\r\n1933 1936 -3.8403337000000e-04\r\n1935 1936 -4.0079459000000e-06\r\n1936 1936  1.0800416000000e+02\r\n1938 1936  3.1814256000000e-04\r\n1939 1936 -2.0496111000000e-02\r\n1941 1936 -4.1087426000000e-06\r\n1984 1936 -3.7683306000000e-04\r\n1986 1936 -3.9328003000000e-06\r\n3040 1936 -5.2989792000000e-02\r\n3042 1936 -2.6884237000000e-05\r\n832 1937  4.6107399000000e-01\r\n834 1937 -3.6531824000000e+00\r\n1888 1937  3.6138554000000e+00\r\n1890 1937 -6.4743050000000e-01\r\n1935 1937 -6.6202847000000e-01\r\n1936 1937 -7.1102064000000e+01\r\n1937 1937 -2.0588297000000e+01\r\n1938 1937  1.0606735000000e+01\r\n1939 1937  5.0681113000000e+00\r\n1941 1937 -6.6219948000000e-01\r\n1986 1937 -6.4715713000000e-01\r\n3042 1937 -4.3324235000000e+00\r\n832 1938  7.7939948000000e-01\r\n833 1938 -1.2625714000000e-01\r\n834 1938 -6.1753395000000e+00\r\n1888 1938  6.1088611000000e+00\r\n1889 1938 -9.8959181000000e-01\r\n1890 1938 -1.0944165000000e+00\r\n1935 1938 -1.1190923000000e+00\r\n1936 1938 -1.2019093000000e+02\r\n1937 1938  1.8497248000000e+01\r\n1938 1938  1.7929624000000e+01\r\n1939 1938  8.5671354000000e+00\r\n1940 1938 -1.3878147000000e+00\r\n1941 1938 -1.1193820000000e+00\r\n1986 1938 -1.0939544000000e+00\r\n3042 1938 -7.3235287000000e+00\r\n835 1939 -2.1290183000000e-03\r\n837 1939 -2.2219399000000e-05\r\n1891 1939 -4.0318724000000e-02\r\n1893 1939 -4.3439161000000e-06\r\n1936 1939 -3.9369150000000e-04\r\n1938 1939 -4.1087426000000e-06\r\n1939 1939  1.1341229000000e+02\r\n1941 1939  3.3117479000000e-04\r\n1942 1939 -2.9311834000000e-02\r\n1944 1939 -4.7987089000000e-06\r\n1987 1939 -4.0538554000000e-04\r\n1989 1939 -4.2307869000000e-06\r\n3043 1939 -5.2052241000000e-02\r\n3045 1939 -2.6331117000000e-05\r\n835 1940  5.8499962000000e-01\r\n837 1940 -3.4773703000000e+00\r\n1891 1940  4.5827496000000e+00\r\n1893 1940 -6.8011853000000e-01\r\n1938 1940 -6.6219948000000e-01\r\n1939 1940 -7.6112701000000e+01\r\n1940 1940 -2.1624608000000e+01\r\n1941 1940  1.0374867000000e+01\r\n1942 1940  5.8976992000000e+00\r\n1944 1940 -7.5135589000000e-01\r\n1989 1940 -6.7902624000000e-01\r\n3045 1940 -4.1223643000000e+00\r\n835 1941  9.8888256000000e-01\r\n836 1941 -1.6018912000000e-01\r\n837 1941 -5.8781421000000e+00\r\n1891 1941  7.7466736000000e+00\r\n1892 1941 -1.2548840000000e+00\r\n1893 1941 -1.1496714000000e+00\r\n1938 1941 -1.1193820000000e+00\r\n1939 1941 -1.2866081000000e+02\r\n1940 1941  1.9803364000000e+01\r\n1941 1941  1.7537663000000e+01\r\n1942 1941  9.9694632000000e+00\r\n1943 1941 -1.6149535000000e+00\r\n1944 1941 -1.2700910000000e+00\r\n1989 1941 -1.1478251000000e+00\r\n3045 1941 -6.9684400000000e+00\r\n838 1942 -1.7730079000000e-03\r\n840 1942 -1.8503913000000e-05\r\n1894 1942 -6.7527563000000e-02\r\n1896 1942 -5.5295673000000e-06\r\n1939 1942 -4.5980269000000e-04\r\n1941 1942 -4.7987089000000e-06\r\n1942 1942  1.4038514000000e+02\r\n1944 1942  3.9070966000000e-04\r\n1945 1942 -1.2654397000000e-02\r\n1947 1942 -6.2646258000000e-06\r\n1990 1942 -5.2024449000000e-04\r\n1992 1942 -5.4295069000000e-06\r\n3046 1942 -4.9917517000000e-02\r\n3048 1942 -2.1910194000000e-05\r\n838 1943  8.6180402000000e-01\r\n840 1943 -2.8132636000000e+00\r\n1894 1943  6.5958573000000e+00\r\n1896 1943 -8.4152480000000e-01\r\n1941 1943 -7.5135589000000e-01\r\n1942 1943 -9.2621167000000e+01\r\n1943 1943 -2.6781272000000e+01\r\n1944 1943  9.5378830000000e+00\r\n1945 1943  4.6401891000000e+00\r\n1947 1943 -9.5341677000000e-01\r\n1992 1943 -8.4106769000000e-01\r\n3048 1943 -3.3342396000000e+00\r\n838 1944  1.4567935000000e+00\r\n839 1944 -2.3598159000000e-01\r\n840 1944 -4.7555408000000e+00\r\n1894 1944  1.1149637000000e+01\r\n1895 1944 -1.8060961000000e+00\r\n1896 1944 -1.4225135000000e+00\r\n1941 1944 -1.2700910000000e+00\r\n1942 1944 -1.5656682000000e+02\r\n1943 1944  2.4056464000000e+01\r\n1944 1944  1.6122836000000e+01\r\n1945 1944  7.8437756000000e+00\r\n1946 1944 -1.2705895000000e+00\r\n1947 1944 -1.6116557000000e+00\r\n1992 1944 -1.4217408000000e+00\r\n3048 1944 -5.6361987000000e+00\r\n841 1945 -1.3791639000000e-03\r\n843 1945 -1.4393578000000e-05\r\n1897 1945 -2.0282098000000e-01\r\n1899 1945 -7.3339187000000e-06\r\n1942 1945 -6.0026392000000e-04\r\n1944 1945 -6.2646258000000e-06\r\n1945 1945  1.8365159000000e+02\r\n1947 1945  4.8141925000000e-04\r\n1993 1945 -6.8042328000000e-04\r\n1995 1945 -7.1012052000000e-06\r\n3049 1945 -4.7987493000000e-02\r\n3051 1945 -1.7045630000000e-05\r\n841 1946  1.0974181000000e+00\r\n843 1946 -2.1496197000000e+00\r\n1897 1946  1.1971675000000e+01\r\n1899 1946 -1.0972324000000e+00\r\n1944 1946 -9.5341677000000e-01\r\n1945 1946 -1.1835743000000e+02\r\n1946 1946 -3.5029675000000e+01\r\n1947 1946  7.8370049000000e+00\r\n1995 1946 -1.0825693000000e+00\r\n3051 1946 -2.5502210000000e+00\r\n841 1947  1.8550741000000e+00\r\n842 1947 -3.0049472000000e-01\r\n843 1947 -3.6337143000000e+00\r\n1897 1947  2.0236903000000e+01\r\n1898 1947 -3.2780807000000e+00\r\n1899 1947 -1.8547602000000e+00\r\n1944 1947 -1.6116557000000e+00\r\n1945 1947 -2.0007125000000e+02\r\n1946 1947  3.0681916000000e+01\r\n1947 1947  1.3247663000000e+01\r\n1995 1947 -1.8299736000000e+00\r\n3051 1947 -4.3108899000000e+00\r\n1948 1948  1.0000000000000e+00\r\n1949 1949  1.0000000000000e+00\r\n1950 1950  1.0000000000000e+00\r\n1951 1951  1.0000000000000e+00\r\n1952 1952  1.0000000000000e+00\r\n1953 1953  1.0000000000000e+00\r\n1954 1954  1.0000000000000e+00\r\n1955 1955  1.0000000000000e+00\r\n1956 1956  1.0000000000000e+00\r\n1957 1957  1.0000000000000e+00\r\n1958 1958  1.0000000000000e+00\r\n1959 1959  1.0000000000000e+00\r\n1960 1960  1.0000000000000e+00\r\n1961 1961  1.0000000000000e+00\r\n1962 1962  1.0000000000000e+00\r\n1963 1963  1.0000000000000e+00\r\n1964 1964  1.0000000000000e+00\r\n1965 1965  1.0000000000000e+00\r\n1966 1966  1.0000000000000e+00\r\n1967 1967  1.0000000000000e+00\r\n1968 1968  1.0000000000000e+00\r\n1969 1969  1.0000000000000e+00\r\n1970 1970  1.0000000000000e+00\r\n1971 1971  1.0000000000000e+00\r\n868 1972 -1.3515598000000e-03\r\n870 1972 -1.4105490000000e-05\r\n1924 1972 -5.4298008000000e-04\r\n1926 1972 -5.6667857000000e-06\r\n1972 1972  1.6194398000000e+02\r\n1974 1972  4.2654555000000e-04\r\n1975 1972 -5.4097895000000e-04\r\n1977 1972 -5.6459011000000e-06\r\n2020 1972 -4.0204471000000e-03\r\n2022 1972 -5.6321296000000e-06\r\n3076 1972 -5.1494177000000e-02\r\n3078 1972 -1.6715752000000e-05\r\n868 1973  5.6322181000000e-01\r\n870 1973 -2.4295537000000e+00\r\n1924 1973  1.5190409000000e+00\r\n1926 1973 -9.7074826000000e-01\r\n1972 1973 -9.6038303000000e+01\r\n1973 1973 -3.0849071000000e+01\r\n1974 1973  8.2257191000000e+00\r\n1975 1973  9.7113107000000e-01\r\n1977 1973 -9.6953747000000e-01\r\n2022 1973 -9.7089198000000e-01\r\n3078 1973 -2.8815324000000e+00\r\n868 1974  9.5207014000000e-01\r\n869 1974 -1.5423474000000e-01\r\n870 1974 -4.1069176000000e+00\r\n1924 1974  2.5677867000000e+00\r\n1925 1974 -4.1597978000000e-01\r\n1926 1974 -1.6409528000000e+00\r\n1972 1974 -1.6234315000000e+02\r\n1973 1974  2.4921984000000e+01\r\n1974 1974  1.3904756000000e+01\r\n1975 1974  1.6416000000000e+00\r\n1976 1974 -2.6593812000000e-01\r\n1977 1974 -1.6389061000000e+00\r\n2022 1974 -1.6411958000000e+00\r\n3078 1974 -4.8709424000000e+00\r\n871 1975 -1.3581805000000e-03\r\n873 1975 -1.4174587000000e-05\r\n1927 1975 -8.0863543000000e-03\r\n1929 1975 -5.6531335000000e-06\r\n1972 1975 -2.3869829000000e-02\r\n1974 1975 -5.6459011000000e-06\r\n1975 1975  1.6197244000000e+02\r\n1977 1975  4.3178912000000e-04\r\n1978 1975 -4.9605957000000e-04\r\n1980 1975 -5.1771021000000e-06\r\n2023 1975 -5.9434076000000e-03\r\n2025 1975 -5.5576398000000e-06\r\n3079 1975 -5.1778327000000e-02\r\n3081 1975 -1.6804275000000e-05\r\n871 1976  5.3125815000000e-01\r\n873 1976 -2.4321006000000e+00\r\n1927 1976  2.1436200000000e+00\r\n1929 1976 -9.7084846000000e-01\r\n1974 1976 -9.6953747000000e-01\r\n1975 1976 -9.7548639000000e+01\r\n1976 1976 -3.0853874000000e+01\r\n1977 1976  9.0974374000000e+00\r\n1978 1976  1.8954181000000e+00\r\n1980 1976 -8.8134172000000e-01\r\n2025 1976 -9.5439186000000e-01\r\n3081 1976 -2.8857599000000e+00\r\n871 1977  8.9803826000000e-01\r\n872 1977 -1.4548135000000e-01\r\n873 1977 -4.1112205000000e+00\r\n1927 1977  3.6235731000000e+00\r\n1928 1977 -5.8701546000000e-01\r\n1929 1977 -1.6411213000000e+00\r\n1974 1977 -1.6389061000000e+00\r\n1975 1977 -1.6489613000000e+02\r\n1976 1977  2.5323854000000e+01\r\n1977 1977  1.5378299000000e+01\r\n1978 1977  3.2040130000000e+00\r\n1979 1977 -5.1904706000000e-01\r\n1980 1977 -1.4898192000000e+00\r\n2025 1977 -1.6133028000000e+00\r\n3081 1977 -4.8780844000000e+00\r\n874 1978 -1.6429276000000e-03\r\n876 1978 -1.7146335000000e-05\r\n1930 1978 -5.5463550000000e-03\r\n1932 1978 -4.7515669000000e-06\r\n1975 1978 -2.2403983000000e-02\r\n1977 1978 -5.1771021000000e-06\r\n1978 1978  1.3497725000000e+02\r\n1980 1978  3.7205450000000e-04\r\n1981 1978 -4.2127940000000e-04\r\n1983 1978 -4.3966624000000e-06\r\n2026 1978 -4.4144999000000e-04\r\n2028 1978 -4.6071718000000e-06\r\n3082 1978 -5.2196358000000e-02\r\n3084 1978 -2.0331213000000e-05\r\n874 1979  4.9785899000000e-01\r\n876 1979 -2.9175561000000e+00\r\n1930 1979  2.4475345000000e+00\r\n1932 1979 -8.0898352000000e-01\r\n1977 1979 -8.8134172000000e-01\r\n1978 1979 -8.3065857000000e+01\r\n1979 1979 -2.5717348000000e+01\r\n1980 1979  9.6022467000000e+00\r\n1981 1979  2.6464787000000e+00\r\n1983 1979 -7.3769417000000e-01\r\n2028 1979 -7.9248720000000e-01\r\n3084 1979 -3.4613003000000e+00\r\n874 1980  8.4158084000000e-01\r\n875 1980 -1.3633455000000e-01\r\n876 1980 -4.9318369000000e+00\r\n1930 1980  4.1373122000000e+00\r\n1931 1980 -6.7023700000000e-01\r\n1932 1980 -1.3675057000000e+00\r\n1977 1980 -1.4898192000000e+00\r\n1978 1980 -1.4041452000000e+02\r\n1979 1980  2.1575094000000e+01\r\n1980 1980  1.6231637000000e+01\r\n1981 1980  4.4736076000000e+00\r\n1982 1980 -7.2471622000000e-01\r\n1983 1980 -1.2469982000000e+00\r\n2028 1980 -1.3396204000000e+00\r\n3084 1980 -5.8509821000000e+00\r\n877 1981 -1.9853381000000e-03\r\n879 1981 -2.0719887000000e-05\r\n1933 1981 -8.6747483000000e-03\r\n1935 1981 -4.0495827000000e-06\r\n1978 1981 -3.2578681000000e-03\r\n1980 1981 -4.3966624000000e-06\r\n1981 1981  1.1337756000000e+02\r\n1983 1981  3.2671386000000e-04\r\n1984 1981 -4.1423520000000e-03\r\n1986 1981 -3.9426131000000e-06\r\n2029 1981 -3.7298957000000e-04\r\n2031 1981 -3.8926879000000e-06\r\n3085 1981 -5.2842909000000e-02\r\n3087 1981 -2.4571963000000e-05\r\n877 1982  4.4971537000000e-01\r\n879 1982 -3.4760615000000e+00\r\n1933 1982  2.7778289000000e+00\r\n1935 1982 -6.7953492000000e-01\r\n1980 1982 -7.3769417000000e-01\r\n1981 1982 -7.1634305000000e+01\r\n1982 1982 -2.1607397000000e+01\r\n1983 1982  1.0343291000000e+01\r\n1984 1982  3.3352763000000e+00\r\n1986 1982 -6.6160067000000e-01\r\n2031 1982 -6.6299625000000e-01\r\n3087 1982 -4.1229794000000e+00\r\n877 1983  7.6019829000000e-01\r\n878 1983 -1.2314977000000e-01\r\n879 1983 -5.8759299000000e+00\r\n1933 1983  4.6956385000000e+00\r\n1934 1983 -7.6067890000000e-01\r\n1935 1983 -1.1486850000000e+00\r\n1980 1983 -1.2469982000000e+00\r\n1981 1983 -1.2109054000000e+02\r\n1982 1983  1.8620214000000e+01\r\n1983 1983  1.7484288000000e+01\r\n1984 1983  5.6379468000000e+00\r\n1985 1983 -9.1332988000000e-01\r\n1986 1983 -1.1183689000000e+00\r\n2031 1983 -1.1207281000000e+00\r\n3087 1983 -6.9694796000000e+00\r\n880 1984 -2.1301373000000e-03\r\n882 1984 -2.2231077000000e-05\r\n1936 1984 -1.7026601000000e-02\r\n1938 1984 -3.9328003000000e-06\r\n1981 1984 -3.7777331000000e-04\r\n1983 1984 -3.9426131000000e-06\r\n1984 1984  1.0798437000000e+02\r\n1986 1984  3.1684869000000e-04\r\n1987 1984 -6.5332251000000e-03\r\n1989 1984 -4.0245300000000e-06\r\n2032 1984 -3.6867044000000e-04\r\n2034 1984 -3.8476115000000e-06\r\n3088 1984 -5.3129053000000e-02\r\n3090 1984 -2.6355745000000e-05\r\n880 1985  4.4145583000000e-01\r\n882 1985 -3.6567886000000e+00\r\n1936 1985  3.5077310000000e+00\r\n1938 1985 -6.4715713000000e-01\r\n1983 1985 -6.6160067000000e-01\r\n1984 1985 -7.0246557000000e+01\r\n1985 1985 -2.0583992000000e+01\r\n1986 1985  1.0613731000000e+01\r\n1987 1985  4.3322745000000e+00\r\n1989 1985 -6.6227664000000e-01\r\n2034 1985 -6.4698723000000e-01\r\n3090 1985 -4.3366092000000e+00\r\n880 1986  7.4623694000000e-01\r\n881 1986 -1.2088658000000e-01\r\n882 1986 -6.1814354000000e+00\r\n1936 1986  5.9294684000000e+00\r\n1937 1986 -9.6054362000000e-01\r\n1938 1986 -1.0939544000000e+00\r\n1983 1986 -1.1183689000000e+00\r\n1984 1986 -1.1874478000000e+02\r\n1985 1986  1.8273817000000e+01\r\n1986 1986  1.7941450000000e+01\r\n1987 1986  7.3232768000000e+00\r\n1988 1986 -1.1863335000000e+00\r\n1989 1986 -1.1195124000000e+00\r\n2034 1986 -1.0936672000000e+00\r\n3090 1986 -7.3306042000000e+00\r\n883 1987 -2.0781249000000e-03\r\n885 1987 -2.1688252000000e-05\r\n1939 1987 -3.2182024000000e-02\r\n1941 1987 -4.2307869000000e-06\r\n1984 1987 -3.8562242000000e-04\r\n1986 1987 -4.0245300000000e-06\r\n1987 1987  1.1343962000000e+02\r\n1989 1987  3.2966748000000e-04\r\n1990 1987 -5.9885713000000e-02\r\n1992 1987 -4.6855457000000e-06\r\n2035 1987 -4.0055791000000e-04\r\n2037 1987 -4.1804036000000e-06\r\n3091 1987 -5.2581036000000e-02\r\n3093 1987 -2.5718390000000e-05\r\n883 1988  5.1242768000000e-01\r\n885 1988 -3.4803075000000e+00\r\n1939 1988  4.4354063000000e+00\r\n1941 1988 -6.7902624000000e-01\r\n1986 1988 -6.6227664000000e-01\r\n1987 1988 -7.7100192000000e+01\r\n1988 1988 -2.1620543000000e+01\r\n1989 1988  1.0397991000000e+01\r\n1990 1988  7.0993032000000e+00\r\n1992 1988 -7.5202197000000e-01\r\n2037 1988 -6.9450959000000e-01\r\n3093 1988 -4.1274186000000e+00\r\n883 1989  8.6620710000000e-01\r\n884 1989 -1.4031909000000e-01\r\n885 1989 -5.8831074000000e+00\r\n1939 1989  7.4976051000000e+00\r\n1940 1989 -1.2145561000000e+00\r\n1941 1989 -1.1478251000000e+00\r\n1986 1989 -1.1195124000000e+00\r\n1987 1989 -1.3033007000000e+02\r\n1988 1989  2.0084135000000e+01\r\n1989 1989  1.7576753000000e+01\r\n1990 1989  1.2000653000000e+01\r\n1991 1989 -1.9440162000000e+00\r\n1992 1989 -1.2712170000000e+00\r\n2037 1989 -1.1739984000000e+00\r\n3093 1989 -6.9769843000000e+00\r\n886 1990 -1.7388043000000e-03\r\n888 1990 -1.8146949000000e-05\r\n1942 1990 -5.7052761000000e-03\r\n1944 1990 -5.4295069000000e-06\r\n1987 1990 -4.4895961000000e-04\r\n1989 1990 -4.6855457000000e-06\r\n1990 1990  1.4033051000000e+02\r\n1992 1990  3.8410423000000e-04\r\n1993 1990 -1.1692933000000e-02\r\n1995 1990 -6.0745924000000e-06\r\n3094 1990 -5.1128589000000e-02\r\n3096 1990 -2.1493975000000e-05\r\n886 1991  6.7593607000000e-01\r\n888 1991 -2.8086301000000e+00\r\n1942 1991  4.1559287000000e+00\r\n1944 1991 -8.4106769000000e-01\r\n1989 1991 -7.5202197000000e-01\r\n1990 1991 -8.9553894000000e+01\r\n1991 1991 -2.6774330000000e+01\r\n1992 1991  8.6749636000000e+00\r\n1993 1991  4.1888701000000e+00\r\n1995 1991 -9.4098208000000e-01\r\n3096 1991 -3.3292502000000e+00\r\n886 1992  1.1426023000000e+00\r\n887 1992 -1.8508882000000e-01\r\n888 1992 -4.7477083000000e+00\r\n1942 1992  7.0251819000000e+00\r\n1943 1992 -1.1380010000000e+00\r\n1944 1992 -1.4217408000000e+00\r\n1989 1992 -1.2712170000000e+00\r\n1990 1992 -1.5138190000000e+02\r\n1991 1992  2.3233965000000e+01\r\n1992 1992  1.4664157000000e+01\r\n1993 1992  7.0808660000000e+00\r\n1994 1992 -1.1470212000000e+00\r\n1995 1992 -1.5906361000000e+00\r\n3096 1992 -5.6277646000000e+00\r\n889 1993 -1.3947605000000e-03\r\n891 1993 -1.4556352000000e-05\r\n1945 1993 -8.2597725000000e-03\r\n1947 1993 -7.1012052000000e-06\r\n1990 1993 -5.8205529000000e-04\r\n1992 1993 -6.0745924000000e-06\r\n1993 1993  1.7807479000000e+02\r\n1995 1993  4.6162173000000e-04\r\n3097 1993 -5.0210142000000e-02\r\n3099 1993 -1.7234427000000e-05\r\n889 1994  7.8644259000000e-01\r\n891 1994 -2.2165275000000e+00\r\n1945 1994  5.7988949000000e+00\r\n1947 1994 -1.0825693000000e+00\r\n1992 1994 -9.4098208000000e-01\r\n1993 1994 -1.0879048000000e+02\r\n1994 1994 -3.3989894000000e+01\r\n1995 1994  6.8709941000000e+00\r\n3099 1994 -2.6270897000000e+00\r\n889 1995  1.3294014000000e+00\r\n890 1995 -2.1534613000000e-01\r\n891 1995 -3.7468149000000e+00\r\n1945 1995  9.8024438000000e+00\r\n1946 1995 -1.5878712000000e+00\r\n1947 1995 -1.8299736000000e+00\r\n1992 1995 -1.5906361000000e+00\r\n1993 1995 -1.8389928000000e+02\r\n1994 1995  2.8136886000000e+01\r\n1995 1995  1.1614721000000e+01\r\n3099 1995 -4.4408299000000e+00\r\n1996 1996  1.0000000000000e+00\r\n1997 1997  1.0000000000000e+00\r\n1998 1998  1.0000000000000e+00\r\n1999 1999  1.0000000000000e+00\r\n2000 2000  1.0000000000000e+00\r\n2001 2001  1.0000000000000e+00\r\n2002 2002  1.0000000000000e+00\r\n2003 2003  1.0000000000000e+00\r\n2004 2004  1.0000000000000e+00\r\n2005 2005  1.0000000000000e+00\r\n2006 2006  1.0000000000000e+00\r\n2007 2007  1.0000000000000e+00\r\n2008 2008  1.0000000000000e+00\r\n2009 2009  1.0000000000000e+00\r\n2010 2010  1.0000000000000e+00\r\n2011 2011  1.0000000000000e+00\r\n2012 2012  1.0000000000000e+00\r\n2013 2013  1.0000000000000e+00\r\n2014 2014  1.0000000000000e+00\r\n2015 2015  1.0000000000000e+00\r\n2016 2016  1.0000000000000e+00\r\n2017 2017  1.0000000000000e+00\r\n2018 2018  1.0000000000000e+00\r\n2019 2019  1.0000000000000e+00\r\n916 2020 -1.3447343000000e-03\r\n918 2020 -1.4034255000000e-05\r\n1972 2020 -5.3965939000000e-04\r\n1974 2020 -5.6321296000000e-06\r\n2020 2020  1.6194250000000e+02\r\n2022 2020  4.2059232000000e-04\r\n2023 2020 -5.2827979000000e-04\r\n2025 2020 -5.5133669000000e-06\r\n3124 2020 -5.1491502000000e-02\r\n3126 2020 -1.6632414000000e-05\r\n916 2021  5.5729081000000e-01\r\n918 2021 -2.4280655000000e+00\r\n1972 2021  1.0590800000000e+00\r\n1974 2021 -9.7089198000000e-01\r\n2020 2021 -9.4979557000000e+01\r\n2021 2021 -3.0846670000000e+01\r\n2022 2021  7.2356360000000e+00\r\n2023 2021  3.7497811000000e-01\r\n2025 2021 -9.5329954000000e-01\r\n3126 2021 -2.8799247000000e+00\r\n916 2022  9.4204439000000e-01\r\n917 2022 -1.5261097000000e-01\r\n918 2022 -4.1044020000000e+00\r\n1972 2022  1.7902689000000e+00\r\n1973 2022 -2.9002313000000e-01\r\n1974 2022 -1.6411958000000e+00\r\n2020 2022 -1.6055344000000e+02\r\n2021 2022  2.4637981000000e+01\r\n2022 2022  1.2231119000000e+01\r\n2023 2022  6.3386300000000e-01\r\n2024 2022 -1.0268565000000e-01\r\n2025 2022 -1.6114575000000e+00\r\n3126 2022 -4.8682248000000e+00\r\n919 2023 -1.3945990000000e-03\r\n921 2023 -1.4554666000000e-05\r\n1975 2023 -5.3252193000000e-04\r\n1977 2023 -5.5576398000000e-06\r\n2020 2023 -2.1480390000000e-02\r\n2022 2023 -5.5133669000000e-06\r\n2023 2023  1.5656494000000e+02\r\n2025 2023  4.1907539000000e-04\r\n2026 2023 -4.7280605000000e-04\r\n2028 2023 -4.9344178000000e-06\r\n2071 2023 -4.8938068000000e-04\r\n2073 2023 -5.1073982000000e-06\r\n3127 2023 -5.1839685000000e-02\r\n3129 2023 -1.7256323000000e-05\r\n919 2024  5.2039201000000e-01\r\n921 2024 -2.5147666000000e+00\r\n1975 2024  1.6215986000000e+00\r\n1977 2024 -9.5439186000000e-01\r\n2022 2024 -9.5329954000000e-01\r\n2023 2024 -9.3134441000000e+01\r\n2024 2024 -2.9821783000000e+01\r\n2025 2024  9.1453456000000e+00\r\n2026 2024  1.1083786000000e+00\r\n2028 2024 -8.4869448000000e-01\r\n2073 2024 -8.8708335000000e-01\r\n3129 2024 -2.9837693000000e+00\r\n919 2025  8.7967001000000e-01\r\n920 2025 -1.4250631000000e-01\r\n921 2025 -4.2509584000000e+00\r\n1975 2025  2.7411483000000e+00\r\n1976 2025 -4.4406532000000e-01\r\n1977 2025 -1.6133028000000e+00\r\n2022 2025 -1.6114575000000e+00\r\n2023 2025 -1.5743434000000e+02\r\n2024 2025  2.4170331000000e+01\r\n2025 2025  1.5459282000000e+01\r\n2026 2025  1.8736018000000e+00\r\n2027 2025 -3.0352301000000e-01\r\n2028 2025 -1.4346321000000e+00\r\n2073 2025 -1.4995246000000e+00\r\n3129 2025 -5.0437600000000e+00\r\n922 2026 -1.6936419000000e-03\r\n924 2026 -1.7675613000000e-05\r\n1978 2026 -2.7509738000000e-03\r\n1980 2026 -4.6071718000000e-06\r\n2023 2026 -2.8855918000000e-02\r\n2025 2026 -4.9344178000000e-06\r\n2026 2026  1.2958883000000e+02\r\n2028 2026  3.5951497000000e-04\r\n2029 2026 -3.9681458000000e-04\r\n2031 2026 -4.1413365000000e-06\r\n2074 2026 -4.0048567000000e-04\r\n2076 2026 -4.1796496000000e-06\r\n3130 2026 -5.2323006000000e-02\r\n3132 2026 -2.0957870000000e-05\r\n922 2027  4.8137961000000e-01\r\n924 2027 -3.0387763000000e+00\r\n1978 2027  2.0158029000000e+00\r\n1980 2027 -7.9248720000000e-01\r\n2025 2027 -8.4869448000000e-01\r\n2026 2027 -7.8577491000000e+01\r\n2027 2027 -2.4685307000000e+01\r\n2028 2027  9.7176880000000e+00\r\n2029 2027  1.7006406000000e+00\r\n2031 2027 -7.0527590000000e-01\r\n2076 2027 -7.2489488000000e-01\r\n3132 2027 -3.6047923000000e+00\r\n922 2028  8.1372409000000e-01\r\n923 2028 -1.3182259000000e-01\r\n924 2028 -5.1367475000000e+00\r\n1978 2028  3.4075133000000e+00\r\n1979 2028 -5.5201418000000e-01\r\n1980 2028 -1.3396204000000e+00\r\n2025 2028 -1.4346321000000e+00\r\n2026 2028 -1.3282739000000e+02\r\n2027 2028  2.0401186000000e+01\r\n2028 2028  1.6426779000000e+01\r\n2029 2028  2.8747629000000e+00\r\n2030 2028 -4.6570909000000e-01\r\n2031 2028 -1.1921984000000e+00\r\n2076 2028 -1.2253623000000e+00\r\n3132 2028 -6.0935410000000e+00\r\n925 2029 -2.0526183000000e-03\r\n927 2029 -2.1422054000000e-05\r\n1981 2029 -1.0229231000000e-02\r\n1983 2029 -3.8926879000000e-06\r\n2026 2029 -1.1539562000000e-02\r\n2028 2029 -4.1413365000000e-06\r\n2029 2029  1.0799165000000e+02\r\n2031 2029  3.1497476000000e-04\r\n2032 2029 -3.6857629000000e-04\r\n2034 2029 -3.8466289000000e-06\r\n2077 2029 -3.5959229000000e-04\r\n2079 2029 -3.7528679000000e-06\r\n3133 2029 -5.2937329000000e-02\r\n3135 2029 -2.5405001000000e-05\r\n925 2030  4.3884976000000e-01\r\n927 2030 -3.6479617000000e+00\r\n1981 2030  2.4661872000000e+00\r\n1983 2030 -6.6299625000000e-01\r\n2028 2030 -7.0527590000000e-01\r\n2029 2030 -6.6997482000000e+01\r\n2030 2030 -2.0575274000000e+01\r\n2031 2030  1.0639110000000e+01\r\n2032 2030  2.1151711000000e+00\r\n2034 2030 -6.4674675000000e-01\r\n2079 2030 -6.4714282000000e-01\r\n3135 2030 -4.3266793000000e+00\r\n925 2031  7.4183114000000e-01\r\n926 2031 -1.2017539000000e-01\r\n927 2031 -6.1665103000000e+00\r\n1981 2031  4.1688401000000e+00\r\n1982 2031 -6.7534503000000e-01\r\n1983 2031 -1.1207281000000e+00\r\n2028 2031 -1.1921984000000e+00\r\n2029 2031 -1.1325247000000e+02\r\n2030 2031  1.7405884000000e+01\r\n2031 2031  1.7984341000000e+01\r\n2032 2031  3.5754831000000e+00\r\n2033 2031 -5.7922216000000e-01\r\n2034 2031 -1.0932600000000e+00\r\n2079 2031 -1.0939295000000e+00\r\n3135 2031 -7.3138141000000e+00\r\n928 2032 -2.0800183000000e-03\r\n930 2032 -2.1708012000000e-05\r\n1984 2032 -1.7480067000000e-02\r\n1986 2032 -3.8476115000000e-06\r\n2029 2032 -4.1808220000000e-03\r\n2031 2032 -3.8466289000000e-06\r\n2032 2032  1.0798712000000e+02\r\n2034 2032  3.1546660000000e-04\r\n2035 2032 -4.6396661000000e-04\r\n2037 2032 -4.0290025000000e-06\r\n2080 2032 -3.6280034000000e-04\r\n2082 2032 -3.7863485000000e-06\r\n3136 2032 -5.3056770000000e-02\r\n3138 2032 -2.5735744000000e-05\r\n928 2033  4.2656881000000e-01\r\n930 2033 -3.6489216000000e+00\r\n1984 2033  3.5522180000000e+00\r\n1986 2033 -6.4698723000000e-01\r\n2031 2033 -6.4674675000000e-01\r\n2032 2033 -6.8038213000000e+01\r\n2033 2033 -2.0579659000000e+01\r\n2034 2033  1.0596529000000e+01\r\n2035 2033  2.0882388000000e+00\r\n2037 2033 -6.7748189000000e-01\r\n2082 2033 -6.4687038000000e-01\r\n3138 2033 -4.3272116000000e+00\r\n928 2034  7.2107192000000e-01\r\n929 2034 -1.1681147000000e-01\r\n930 2034 -6.1681371000000e+00\r\n1984 2034  6.0046692000000e+00\r\n1985 2034 -9.7273828000000e-01\r\n1986 2034 -1.0936672000000e+00\r\n2031 2034 -1.0932600000000e+00\r\n2032 2034 -1.1501180000000e+02\r\n2033 2034  1.7679983000000e+01\r\n2034 2034  1.7912372000000e+01\r\n2035 2034  3.5299588000000e+00\r\n2036 2034 -5.7184267000000e-01\r\n2037 2034 -1.1452154000000e+00\r\n2082 2034 -1.0934697000000e+00\r\n3138 2034 -7.3147185000000e+00\r\n931 2035 -1.9161989000000e-03\r\n933 2035 -1.9998318000000e-05\r\n1987 2035 -2.5132937000000e-02\r\n1989 2035 -4.1804036000000e-06\r\n2032 2035 -3.8605096000000e-04\r\n2034 2035 -4.0290025000000e-06\r\n2035 2035  1.1877676000000e+02\r\n2037 2035  3.3397726000000e-04\r\n2083 2035 -4.1260535000000e-04\r\n2085 2035 -4.3061361000000e-06\r\n3139 2035 -5.2823657000000e-02\r\n3141 2035 -2.3699441000000e-05\r\n931 2036  4.4637846000000e-01\r\n933 2036 -3.3203392000000e+00\r\n1987 2036  6.2154245000000e+00\r\n1989 2036 -6.9450959000000e-01\r\n2034 2036 -6.7748189000000e-01\r\n2035 2036 -7.4824506000000e+01\r\n2036 2036 -2.2641647000000e+01\r\n2037 2036  9.3592333000000e+00\r\n2085 2036 -7.2755535000000e-01\r\n3141 2036 -3.9368051000000e+00\r\n931 2037  7.5455772000000e-01\r\n932 2037 -1.2223526000000e-01\r\n933 2037 -5.6126982000000e+00\r\n1987 2037  1.0506548000000e+01\r\n1988 2037 -1.7020177000000e+00\r\n1989 2037 -1.1739984000000e+00\r\n2034 2037 -1.1452154000000e+00\r\n2035 2037 -1.2648328000000e+02\r\n2036 2037  1.9433192000000e+01\r\n2037 2037  1.5820839000000e+01\r\n2085 2037 -1.2298587000000e+00\r\n3141 2037 -6.6547709000000e+00\r\n2038 2038  1.0000000000000e+00\r\n2039 2039  1.0000000000000e+00\r\n2040 2040  1.0000000000000e+00\r\n2041 2041  1.0000000000000e+00\r\n2042 2042  1.0000000000000e+00\r\n2043 2043  1.0000000000000e+00\r\n2044 2044  1.0000000000000e+00\r\n2045 2045  1.0000000000000e+00\r\n2046 2046  1.0000000000000e+00\r\n2047 2047  1.0000000000000e+00\r\n2048 2048  1.0000000000000e+00\r\n2049 2049  1.0000000000000e+00\r\n2050 2050  1.0000000000000e+00\r\n2051 2051  1.0000000000000e+00\r\n2052 2052  1.0000000000000e+00\r\n2053 2053  1.0000000000000e+00\r\n2054 2054  1.0000000000000e+00\r\n2055 2055  1.0000000000000e+00\r\n2056 2056  1.0000000000000e+00\r\n2057 2057  1.0000000000000e+00\r\n2058 2058  1.0000000000000e+00\r\n2059 2059  1.0000000000000e+00\r\n2060 2060  1.0000000000000e+00\r\n2061 2061  1.0000000000000e+00\r\n2062 2062  1.0000000000000e+00\r\n2063 2063  1.0000000000000e+00\r\n2064 2064  1.0000000000000e+00\r\n2065 2065  1.0000000000000e+00\r\n2066 2066  1.0000000000000e+00\r\n2067 2067  1.0000000000000e+00\r\n2068 2068  1.0000000000000e+00\r\n2069 2069  1.0000000000000e+00\r\n2070 2070  1.0000000000000e+00\r\n967 2071 -1.5486360000000e-03\r\n969 2071 -1.6162266000000e-05\r\n2023 2071 -1.3177635000000e-03\r\n2025 2071 -5.1073982000000e-06\r\n2071 2071  1.4035733000000e+02\r\n2073 2071  3.7303392000000e-04\r\n2074 2071 -4.1502002000000e-04\r\n2076 2071 -4.3313367000000e-06\r\n3175 2071 -5.2088389000000e-02\r\n3177 2071 -1.9158914000000e-05\r\n967 2072  4.9811720000000e-01\r\n969 2072 -2.8052857000000e+00\r\n2023 2072  9.6498412000000e-01\r\n2025 2072 -8.8708335000000e-01\r\n2071 2072 -8.2325452000000e+01\r\n2072 2072 -2.6735187000000e+01\r\n2073 2072  7.7740211000000e+00\r\n2074 2072  2.7443005000000e-01\r\n2076 2072 -7.5114428000000e-01\r\n3177 2072 -3.3275135000000e+00\r\n967 2073  8.4201672000000e-01\r\n968 2073 -1.3640684000000e-01\r\n969 2073 -4.7420516000000e+00\r\n2023 2073  1.6312080000000e+00\r\n2024 2073 -2.6425593000000e-01\r\n2025 2073 -1.4995246000000e+00\r\n2071 2073 -1.3916285000000e+02\r\n2072 2073  2.1352282000000e+01\r\n2073 2073  1.3141196000000e+01\r\n2074 2073  4.6389624000000e-01\r\n2075 2073 -7.5151254000000e-02\r\n2076 2073 -1.2697334000000e+00\r\n3177 2073 -5.6248248000000e+00\r\n970 2074 -1.9188510000000e-03\r\n972 2074 -2.0025997000000e-05\r\n2026 2074 -9.1575328000000e-04\r\n2028 2074 -4.1796496000000e-06\r\n2071 2074 -2.5369610000000e-02\r\n2073 2074 -4.3313367000000e-06\r\n2074 2074  1.1339891000000e+02\r\n2076 2074  3.2508782000000e-04\r\n2077 2074 -3.6819004000000e-04\r\n2079 2074 -3.8425978000000e-06\r\n2122 2074 -4.2051555000000e-04\r\n2124 2074 -3.8229533000000e-06\r\n3178 2074 -5.2643162000000e-02\r\n3180 2074 -2.3743447000000e-05\r\n970 2075  4.5778494000000e-01\r\n972 2075 -3.4716727000000e+00\r\n2026 2075  1.4703649000000e+00\r\n2028 2075 -7.2489488000000e-01\r\n2073 2075 -7.5114428000000e-01\r\n2074 2075 -6.7964341000000e+01\r\n2075 2075 -2.1597166000000e+01\r\n2076 2075  1.0393410000000e+01\r\n2077 2075  9.5055489000000e-01\r\n2079 2075 -6.6255674000000e-01\r\n2124 2075 -6.6299206000000e-01\r\n3180 2075 -4.1177292000000e+00\r\n970 2076  7.7383966000000e-01\r\n971 2076 -1.2536194000000e-01\r\n972 2076 -5.8685156000000e+00\r\n2026 2076  2.4855048000000e+00\r\n2027 2076 -4.0265152000000e-01\r\n2028 2076 -1.2253623000000e+00\r\n2073 2076 -1.2697334000000e+00\r\n2074 2076 -1.1488692000000e+02\r\n2075 2076  1.7640585000000e+01\r\n2076 2076  1.7569019000000e+01\r\n2077 2076  1.6068180000000e+00\r\n2078 2076 -2.6030434000000e-01\r\n2079 2076 -1.1199859000000e+00\r\n2124 2076 -1.1207218000000e+00\r\n3180 2076 -6.9606094000000e+00\r\n973 2077 -2.0263996000000e-03\r\n975 2077 -2.1148424000000e-05\r\n2029 2077 -4.2983185000000e-03\r\n2031 2077 -3.7528679000000e-06\r\n2074 2077 -1.4398817000000e-02\r\n2076 2077 -3.8425978000000e-06\r\n2077 2077  1.0799211000000e+02\r\n2079 2077  3.1387052000000e-04\r\n2080 2077 -3.6281552000000e-04\r\n2082 2077 -3.7865069000000e-06\r\n2125 2077 -5.7231082000000e-04\r\n2127 2077 -3.7528929000000e-06\r\n3181 2077 -5.2986287000000e-02\r\n3183 2077 -2.5073077000000e-05\r\n973 2078  4.1947629000000e-01\r\n975 2078 -3.6451450000000e+00\r\n2029 2078  1.9446345000000e+00\r\n2031 2078 -6.4714282000000e-01\r\n2076 2078 -6.6255674000000e-01\r\n2077 2078 -6.5831628000000e+01\r\n2078 2078 -2.0572200000000e+01\r\n2079 2078  1.0574418000000e+01\r\n2080 2078  1.4859701000000e+00\r\n2082 2078 -6.4683245000000e-01\r\n2127 2078 -6.4709638000000e-01\r\n3183 2078 -4.3233388000000e+00\r\n973 2079  7.0908224000000e-01\r\n974 2079 -1.1487093000000e-01\r\n975 2079 -6.1617491000000e+00\r\n2029 2079  3.2872081000000e+00\r\n2030 2079 -5.3252586000000e-01\r\n2031 2079 -1.0939295000000e+00\r\n2076 2079 -1.1199859000000e+00\r\n2077 2079 -1.1128171000000e+02\r\n2078 2079  1.7094281000000e+01\r\n2079 2079  1.7874985000000e+01\r\n2080 2079  2.5118822000000e+00\r\n2081 2079 -4.0692347000000e-01\r\n2082 2079 -1.0934048000000e+00\r\n2127 2079 -1.0938507000000e+00\r\n3183 2079 -7.3081667000000e+00\r\n976 2080 -2.0472526000000e-03\r\n978 2080 -2.1366055000000e-05\r\n2032 2080 -4.3670855000000e-03\r\n2034 2080 -3.7863485000000e-06\r\n2077 2080 -4.2436261000000e-03\r\n2079 2080 -3.7865069000000e-06\r\n2080 2080  1.0797900000000e+02\r\n2082 2080  3.1484536000000e-04\r\n2083 2080 -3.9241329000000e-04\r\n2085 2080 -4.0954026000000e-06\r\n2128 2080 -8.9023778000000e-04\r\n2130 2080 -3.9670213000000e-06\r\n3184 2080 -5.3021985000000e-02\r\n3186 2080 -2.5330574000000e-05\r\n976 2081  4.2670123000000e-01\r\n978 2081 -3.6487932000000e+00\r\n2032 2081  2.5733037000000e+00\r\n2034 2081 -6.4687038000000e-01\r\n2079 2081 -6.4683245000000e-01\r\n2080 2081 -6.6940390000000e+01\r\n2081 2081 -2.0575438000000e+01\r\n2082 2081  1.0641571000000e+01\r\n2083 2081  1.9633149000000e+00\r\n2085 2081 -6.9187750000000e-01\r\n2130 2081 -6.7766514000000e-01\r\n3186 2081 -4.3272245000000e+00\r\n976 2082  7.2129575000000e-01\r\n977 2082 -1.1684882000000e-01\r\n978 2082 -6.1679201000000e+00\r\n2032 2082  4.3499125000000e+00\r\n2033 2082 -7.0467922000000e-01\r\n2034 2082 -1.0934697000000e+00\r\n2079 2082 -1.0934048000000e+00\r\n2080 2082 -1.1315604000000e+02\r\n2081 2082  1.7389873000000e+01\r\n2082 2082  1.7988511000000e+01\r\n2083 2082  3.3187875000000e+00\r\n2084 2082 -5.3763854000000e-01\r\n2085 2082 -1.1695497000000e+00\r\n2130 2082 -1.1455251000000e+00\r\n3186 2082 -7.3147403000000e+00\r\n979 2083 -1.8007609000000e-03\r\n981 2083 -1.8793556000000e-05\r\n2035 2083 -9.1781122000000e-03\r\n2037 2083 -4.3061361000000e-06\r\n2080 2083 -4.3665315000000e-03\r\n2082 2083 -4.0954026000000e-06\r\n2083 2083  1.2416444000000e+02\r\n2085 2083  3.3985653000000e-04\r\n3187 2083 -5.2728554000000e-02\r\n3189 2083 -2.2272105000000e-05\r\n979 2084  4.3795089000000e-01\r\n981 2084 -3.1730689000000e+00\r\n2035 2084  3.0722658000000e+00\r\n2037 2084 -7.2755535000000e-01\r\n2082 2084 -6.9187750000000e-01\r\n2083 2084 -7.4777714000000e+01\r\n2084 2084 -2.3666192000000e+01\r\n2085 2084  8.3579258000000e+00\r\n3189 2084 -3.7627684000000e+00\r\n979 2085  7.4031168000000e-01\r\n980 2085 -1.1992867000000e-01\r\n981 2085 -5.3637519000000e+00\r\n2035 2085  5.1933545000000e+00\r\n2036 2085 -8.4131068000000e-01\r\n2037 2085 -1.2298587000000e+00\r\n2082 2085 -1.1695497000000e+00\r\n2083 2085 -1.2640416000000e+02\r\n2084 2085  1.9383922000000e+01\r\n2085 2085  1.4128229000000e+01\r\n3189 2085 -6.3605797000000e+00\r\n2086 2086  1.0000000000000e+00\r\n2087 2087  1.0000000000000e+00\r\n2088 2088  1.0000000000000e+00\r\n2089 2089  1.0000000000000e+00\r\n2090 2090  1.0000000000000e+00\r\n2091 2091  1.0000000000000e+00\r\n2092 2092  1.0000000000000e+00\r\n2093 2093  1.0000000000000e+00\r\n2094 2094  1.0000000000000e+00\r\n2095 2095  1.0000000000000e+00\r\n2096 2096  1.0000000000000e+00\r\n2097 2097  1.0000000000000e+00\r\n2098 2098  1.0000000000000e+00\r\n2099 2099  1.0000000000000e+00\r\n2100 2100  1.0000000000000e+00\r\n2101 2101  1.0000000000000e+00\r\n2102 2102  1.0000000000000e+00\r\n2103 2103  1.0000000000000e+00\r\n2104 2104  1.0000000000000e+00\r\n2105 2105  1.0000000000000e+00\r\n2106 2106  1.0000000000000e+00\r\n2107 2107  1.0000000000000e+00\r\n2108 2108  1.0000000000000e+00\r\n2109 2109  1.0000000000000e+00\r\n2110 2110  1.0000000000000e+00\r\n2111 2111  1.0000000000000e+00\r\n2112 2112  1.0000000000000e+00\r\n2113 2113  1.0000000000000e+00\r\n2114 2114  1.0000000000000e+00\r\n2115 2115  1.0000000000000e+00\r\n2116 2116  1.0000000000000e+00\r\n2117 2117  1.0000000000000e+00\r\n2118 2118  1.0000000000000e+00\r\n2119 2119  1.0000000000000e+00\r\n2120 2120  1.0000000000000e+00\r\n2121 2121  1.0000000000000e+00\r\n1018 2122 -1.9994199000000e-03\r\n1020 2122 -2.0866851000000e-05\r\n2074 2122 -3.6630774000000e-04\r\n2076 2122 -3.8229533000000e-06\r\n2122 2122  1.0798444000000e+02\r\n2124 2122  3.0936880000000e-04\r\n2125 2122 -3.5610536000000e-04\r\n2127 2122 -3.7164766000000e-06\r\n2170 2122 -5.2512808000000e-03\r\n2172 2122 -3.7048953000000e-06\r\n3226 2122 -5.2989099000000e-02\r\n3228 2122 -2.4741284000000e-05\r\n1018 2123  4.1131826000000e-01\r\n1020 2123 -3.6438231000000e+00\r\n2074 2123  1.1718104000000e+00\r\n2076 2123 -6.6299206000000e-01\r\n2122 2123 -6.4108336000000e+01\r\n2123 2123 -2.0566613000000e+01\r\n2124 2123  9.9250470000000e+00\r\n2125 2123  5.3596728000000e-01\r\n2127 2123 -6.4700011000000e-01\r\n2172 2123 -6.4715796000000e-01\r\n3228 2123 -4.3217700000000e+00\r\n1018 2124  6.9529239000000e-01\r\n1019 2124 -1.1263776000000e-01\r\n1020 2124 -6.1595186000000e+00\r\n2074 2124  1.9808284000000e+00\r\n2075 2124 -3.2089530000000e-01\r\n2076 2124 -1.1207218000000e+00\r\n2122 2124 -1.0836873000000e+02\r\n2123 2124  1.6636125000000e+01\r\n2124 2124  1.6777299000000e+01\r\n2125 2124  9.0599909000000e-01\r\n2126 2124 -1.4677236000000e-01\r\n2127 2124 -1.0936890000000e+00\r\n2172 2124 -1.0939558000000e+00\r\n3228 2124 -7.3055200000000e+00\r\n1021 2125 -2.0057856000000e-03\r\n1023 2125 -2.0933286000000e-05\r\n2077 2125 -3.5959469000000e-04\r\n2079 2125 -3.7528929000000e-06\r\n2122 2125 -1.3898480000000e-02\r\n2124 2125 -3.7164766000000e-06\r\n2125 2125  1.0799500000000e+02\r\n2127 2125  3.1337447000000e-04\r\n2128 2125 -3.7552166000000e-04\r\n2130 2125 -3.9191139000000e-06\r\n2173 2125 -4.7921739000000e-03\r\n2175 2125 -3.7167668000000e-06\r\n3229 2125 -5.3004344000000e-02\r\n3231 2125 -2.4821271000000e-05\r\n1021 2126  4.0990778000000e-01\r\n1023 2126 -3.6437176000000e+00\r\n2077 2126  1.5360070000000e+00\r\n2079 2126 -6.4709638000000e-01\r\n2124 2126 -6.4700011000000e-01\r\n2125 2126 -6.4988562000000e+01\r\n2126 2126 -2.0569350000000e+01\r\n2127 2126  1.0586380000000e+01\r\n2128 2126  1.0571098000000e+00\r\n2130 2126 -6.7798617000000e-01\r\n2175 2126 -6.4705268000000e-01\r\n3231 2126 -4.3212217000000e+00\r\n1021 2127  6.9290745000000e-01\r\n1022 2127 -1.1225128000000e-01\r\n1023 2127 -6.1593344000000e+00\r\n2077 2127  2.5964637000000e+00\r\n2078 2127 -4.2062815000000e-01\r\n2079 2127 -1.0938507000000e+00\r\n2124 2127 -1.0936890000000e+00\r\n2125 2127 -1.0985656000000e+02\r\n2126 2127  1.6870519000000e+01\r\n2127 2127  1.7895203000000e+01\r\n2128 2127  1.7869368000000e+00\r\n2129 2127 -2.8948447000000e-01\r\n2130 2127 -1.1460667000000e+00\r\n2175 2127 -1.0937772000000e+00\r\n3231 2127 -7.3045892000000e+00\r\n1024 2128 -1.8360530000000e-03\r\n1026 2128 -1.9161880000000e-05\r\n2080 2128 -3.8011205000000e-04\r\n2082 2128 -3.9670213000000e-06\r\n2125 2128 -4.1560972000000e-03\r\n2127 2128 -3.9191139000000e-06\r\n2128 2128  1.1876910000000e+02\r\n2130 2128  3.2753322000000e-04\r\n3232 2128 -5.2835255000000e-02\r\n3234 2128 -2.2719784000000e-05\r\n1024 2129  4.1682311000000e-01\r\n1026 2129 -3.3137845000000e+00\r\n2080 2129  2.1087471000000e+00\r\n2082 2129 -6.7766514000000e-01\r\n2127 2129 -6.7798617000000e-01\r\n2128 2129 -7.0706098000000e+01\r\n2129 2129 -2.2628834000000e+01\r\n2130 2129  8.6024284000000e+00\r\n3234 2129 -3.9304561000000e+00\r\n1024 2130  7.0459778000000e-01\r\n1025 2130 -1.1414460000000e-01\r\n1026 2130 -5.6016213000000e+00\r\n2080 2130  3.5646261000000e+00\r\n2081 2130 -5.7746821000000e-01\r\n2082 2130 -1.1455251000000e+00\r\n2127 2130 -1.1460667000000e+00\r\n2128 2130 -1.1952159000000e+02\r\n2129 2130  1.8337250000000e+01\r\n2130 2130  1.4541544000000e+01\r\n3234 2130 -6.6440430000000e+00\r\n2131 2131  1.0000000000000e+00\r\n2132 2132  1.0000000000000e+00\r\n2133 2133  1.0000000000000e+00\r\n2134 2134  1.0000000000000e+00\r\n2135 2135  1.0000000000000e+00\r\n2136 2136  1.0000000000000e+00\r\n2137 2137  1.0000000000000e+00\r\n2138 2138  1.0000000000000e+00\r\n2139 2139  1.0000000000000e+00\r\n2140 2140  1.0000000000000e+00\r\n2141 2141  1.0000000000000e+00\r\n2142 2142  1.0000000000000e+00\r\n2143 2143  1.0000000000000e+00\r\n2144 2144  1.0000000000000e+00\r\n2145 2145  1.0000000000000e+00\r\n2146 2146  1.0000000000000e+00\r\n2147 2147  1.0000000000000e+00\r\n2148 2148  1.0000000000000e+00\r\n2149 2149  1.0000000000000e+00\r\n2150 2150  1.0000000000000e+00\r\n2151 2151  1.0000000000000e+00\r\n2152 2152  1.0000000000000e+00\r\n2153 2153  1.0000000000000e+00\r\n2154 2154  1.0000000000000e+00\r\n2155 2155  1.0000000000000e+00\r\n2156 2156  1.0000000000000e+00\r\n2157 2157  1.0000000000000e+00\r\n2158 2158  1.0000000000000e+00\r\n2159 2159  1.0000000000000e+00\r\n2160 2160  1.0000000000000e+00\r\n2161 2161  1.0000000000000e+00\r\n2162 2162  1.0000000000000e+00\r\n2163 2163  1.0000000000000e+00\r\n2164 2164  1.0000000000000e+00\r\n2165 2165  1.0000000000000e+00\r\n2166 2166  1.0000000000000e+00\r\n2167 2167  1.0000000000000e+00\r\n2168 2168  1.0000000000000e+00\r\n2169 2169  1.0000000000000e+00\r\n1066 2170 -1.9891465000000e-03\r\n1068 2170 -2.0759632000000e-05\r\n2122 2170 -3.5499566000000e-04\r\n2124 2170 -3.7048953000000e-06\r\n2170 2170  1.0798140000000e+02\r\n2172 2170  3.0528560000000e-04\r\n2173 2170 -3.5354396000000e-04\r\n2175 2170 -3.6897447000000e-06\r\n3274 2170 -5.3043057000000e-02\r\n3276 2170 -2.4614233000000e-05\r\n1066 2171  3.9883469000000e-01\r\n1068 2171 -3.6426386000000e+00\r\n2122 2171  7.6395676000000e-01\r\n2124 2171 -6.4715796000000e-01\r\n2170 2171 -6.3334227000000e+01\r\n2171 2171 -2.0564573000000e+01\r\n2172 2171  9.2594774000000e+00\r\n2173 2171  1.7939655000000e-01\r\n2175 2171 -6.4701297000000e-01\r\n3276 2171 -4.3203650000000e+00\r\n1066 2172  6.7419016000000e-01\r\n1067 2172 -1.0921948000000e-01\r\n1068 2172 -6.1575162000000e+00\r\n2122 2172  1.2913925000000e+00\r\n2123 2172 -2.0920688000000e-01\r\n2124 2172 -1.0939558000000e+00\r\n2170 2172 -1.0706018000000e+02\r\n2171 2172  1.6429162000000e+01\r\n2172 2172  1.5652221000000e+01\r\n2173 2172  3.0325193000000e-01\r\n2174 2172 -4.9127116000000e-02\r\n2175 2172 -1.0937107000000e+00\r\n3276 2172 -7.3031450000000e+00\r\n1069 2173 -1.9913866000000e-03\r\n1071 2173 -2.0783011000000e-05\r\n2125 2173 -3.5613316000000e-04\r\n2127 2173 -3.7167668000000e-06\r\n2170 2173 -1.4356213000000e-02\r\n2172 2173 -3.6897447000000e-06\r\n2173 2173  1.0799313000000e+02\r\n2175 2173  3.0534932000000e-04\r\n3277 2173 -5.3060893000000e-02\r\n3279 2173 -2.4644423000000e-05\r\n1069 2174  3.9904024000000e-01\r\n1071 2174 -3.6436564000000e+00\r\n2125 2174  1.1204141000000e+00\r\n2127 2174 -6.4705268000000e-01\r\n2172 2174 -6.4701297000000e-01\r\n2173 2174 -6.3508591000000e+01\r\n2174 2174 -2.0566709000000e+01\r\n2175 2174  9.2615989000000e+00\r\n3279 2174 -4.3215731000000e+00\r\n1069 2175  6.7453723000000e-01\r\n1070 2175 -1.0927570000000e-01\r\n1071 2175 -6.1592331000000e+00\r\n2125 2175  1.8939468000000e+00\r\n2126 2175 -3.0682126000000e-01\r\n2127 2175 -1.0937772000000e+00\r\n2172 2175 -1.0937107000000e+00\r\n2173 2175 -1.0735486000000e+02\r\n2174 2175  1.6471721000000e+01\r\n2175 2175  1.5655799000000e+01\r\n3279 2175 -7.3051832000000e+00\r\n2176 2176  1.0000000000000e+00\r\n2177 2177  1.0000000000000e+00\r\n2178 2178  1.0000000000000e+00\r\n2179 2179  1.0000000000000e+00\r\n2180 2180  1.0000000000000e+00\r\n2181 2181  1.0000000000000e+00\r\n2182 2182  1.0000000000000e+00\r\n2183 2183  1.0000000000000e+00\r\n2184 2184  1.0000000000000e+00\r\n2185 2185  1.0000000000000e+00\r\n2186 2186  1.0000000000000e+00\r\n2187 2187  1.0000000000000e+00\r\n2188 2188  1.0000000000000e+00\r\n2189 2189  1.0000000000000e+00\r\n2190 2190  1.0000000000000e+00\r\n2191 2191  1.0000000000000e+00\r\n2192 2192  1.0000000000000e+00\r\n2193 2193  1.0000000000000e+00\r\n2194 2194  1.0000000000000e+00\r\n2195 2195  1.0000000000000e+00\r\n2196 2196  1.0000000000000e+00\r\n2197 2197  1.0000000000000e+00\r\n2198 2198  1.0000000000000e+00\r\n2199 2199  1.0000000000000e+00\r\n2200 2200  1.0000000000000e+00\r\n2201 2201  1.0000000000000e+00\r\n2202 2202  1.0000000000000e+00\r\n2203 2203  1.0000000000000e+00\r\n2204 2204  1.0000000000000e+00\r\n2205 2205  1.0000000000000e+00\r\n2206 2206  1.0000000000000e+00\r\n2207 2207  1.0000000000000e+00\r\n2208 2208  1.0000000000000e+00\r\n2209 2209  1.0000000000000e+00\r\n2210 2210  1.0000000000000e+00\r\n2211 2211  1.0000000000000e+00\r\n2212 2212  1.0000000000000e+00\r\n2213 2213  1.0000000000000e+00\r\n2214 2214  1.0000000000000e+00\r\n2215 2215  1.0000000000000e+00\r\n2216 2216  1.0000000000000e+00\r\n2217 2217  1.0000000000000e+00\r\n2218 2218  1.0000000000000e+00\r\n2219 2219  1.0000000000000e+00\r\n2220 2220  1.0000000000000e+00\r\n2221 2221  1.0000000000000e+00\r\n2222 2222  1.0000000000000e+00\r\n2223 2223  1.0000000000000e+00\r\n2224 2224  1.0000000000000e+00\r\n2225 2225  1.0000000000000e+00\r\n2226 2226  1.0000000000000e+00\r\n2227 2227  1.0000000000000e+00\r\n2228 2228  1.0000000000000e+00\r\n2229 2229  1.0000000000000e+00\r\n2230 2230  1.0000000000000e+00\r\n2231 2231  1.0000000000000e+00\r\n2232 2232  1.0000000000000e+00\r\n2233 2233  1.0000000000000e+00\r\n2234 2234  1.0000000000000e+00\r\n2235 2235  1.0000000000000e+00\r\n2236 2236  1.0000000000000e+00\r\n2237 2237  1.0000000000000e+00\r\n2238 2238  1.0000000000000e+00\r\n2239 2239  1.0000000000000e+00\r\n2240 2240  1.0000000000000e+00\r\n2241 2241  1.0000000000000e+00\r\n2242 2242  1.0000000000000e+00\r\n2243 2243  1.0000000000000e+00\r\n2244 2244  1.0000000000000e+00\r\n2245 2245  1.0000000000000e+00\r\n2246 2246  1.0000000000000e+00\r\n2247 2247  1.0000000000000e+00\r\n2248 2248  1.0000000000000e+00\r\n2249 2249  1.0000000000000e+00\r\n2250 2250  1.0000000000000e+00\r\n2251 2251  1.0000000000000e+00\r\n2252 2252  1.0000000000000e+00\r\n2253 2253  1.0000000000000e+00\r\n2254 2254  1.0000000000000e+00\r\n2255 2255  1.0000000000000e+00\r\n2256 2256  1.0000000000000e+00\r\n2257 2257  1.0000000000000e+00\r\n2258 2258  1.0000000000000e+00\r\n2259 2259  1.0000000000000e+00\r\n2260 2260  1.0000000000000e+00\r\n2261 2261  1.0000000000000e+00\r\n2262 2262  1.0000000000000e+00\r\n2263 2263  1.0000000000000e+00\r\n2264 2264  1.0000000000000e+00\r\n2265 2265  1.0000000000000e+00\r\n2266 2266  1.0000000000000e+00\r\n2267 2267  1.0000000000000e+00\r\n2268 2268  1.0000000000000e+00\r\n2269 2269  1.0000000000000e+00\r\n2270 2270  1.0000000000000e+00\r\n2271 2271  1.0000000000000e+00\r\n2272 2272  1.0000000000000e+00\r\n2273 2273  1.0000000000000e+00\r\n2274 2274  1.0000000000000e+00\r\n2275 2275  1.0000000000000e+00\r\n2276 2276  1.0000000000000e+00\r\n2277 2277  1.0000000000000e+00\r\n2278 2278  1.0000000000000e+00\r\n2279 2279  1.0000000000000e+00\r\n2280 2280  1.0000000000000e+00\r\n2281 2281  1.0000000000000e+00\r\n2282 2282  1.0000000000000e+00\r\n2283 2283  1.0000000000000e+00\r\n2284 2284  1.0000000000000e+00\r\n2285 2285  1.0000000000000e+00\r\n2286 2286  1.0000000000000e+00\r\n2287 2287  1.0000000000000e+00\r\n2288 2288  1.0000000000000e+00\r\n2289 2289  1.0000000000000e+00\r\n2290 2290  1.0000000000000e+00\r\n2291 2291  1.0000000000000e+00\r\n2292 2292  1.0000000000000e+00\r\n2293 2293  1.0000000000000e+00\r\n2294 2294  1.0000000000000e+00\r\n2295 2295  1.0000000000000e+00\r\n2296 2296  1.0000000000000e+00\r\n2297 2297  1.0000000000000e+00\r\n2298 2298  1.0000000000000e+00\r\n2299 2299  1.0000000000000e+00\r\n2300 2300  1.0000000000000e+00\r\n2301 2301  1.0000000000000e+00\r\n2302 2302  1.0000000000000e+00\r\n2303 2303  1.0000000000000e+00\r\n2304 2304  1.0000000000000e+00\r\n2305 2305  1.0000000000000e+00\r\n2306 2306  1.0000000000000e+00\r\n2307 2307  1.0000000000000e+00\r\n2308 2308  1.0000000000000e+00\r\n2309 2309  1.0000000000000e+00\r\n2310 2310  1.0000000000000e+00\r\n2311 2311  1.0000000000000e+00\r\n2312 2312  1.0000000000000e+00\r\n2313 2313  1.0000000000000e+00\r\n2314 2314  1.0000000000000e+00\r\n2315 2315  1.0000000000000e+00\r\n2316 2316  1.0000000000000e+00\r\n2317 2317  1.0000000000000e+00\r\n2318 2318  1.0000000000000e+00\r\n2319 2319  1.0000000000000e+00\r\n2320 2320  1.0000000000000e+00\r\n2321 2321  1.0000000000000e+00\r\n2322 2322  1.0000000000000e+00\r\n2323 2323  1.0000000000000e+00\r\n2324 2324  1.0000000000000e+00\r\n2325 2325  1.0000000000000e+00\r\n2326 2326  1.0000000000000e+00\r\n2327 2327  1.0000000000000e+00\r\n2328 2328  1.0000000000000e+00\r\n2329 2329  1.0000000000000e+00\r\n2330 2330  1.0000000000000e+00\r\n2331 2331  1.0000000000000e+00\r\n2332 2332  1.0000000000000e+00\r\n2333 2333  1.0000000000000e+00\r\n2334 2334  1.0000000000000e+00\r\n2335 2335  1.0000000000000e+00\r\n2336 2336  1.0000000000000e+00\r\n2337 2337  1.0000000000000e+00\r\n2338 2338  1.0000000000000e+00\r\n2339 2339  1.0000000000000e+00\r\n2340 2340  1.0000000000000e+00\r\n2341 2341  1.0000000000000e+00\r\n2342 2342  1.0000000000000e+00\r\n2343 2343  1.0000000000000e+00\r\n1240 2344 -2.5971423000000e+00\r\n1242 2344 -1.7988385000000e-01\r\n2344 2344  2.0608732000000e+02\r\n2346 2344  4.2725065000000e-01\r\n2347 2344 -4.3744598000000e-01\r\n2349 2344 -8.1460968000000e-02\r\n2392 2344 -4.1557028000000e+00\r\n2394 2344 -8.6020643000000e-02\r\n1240 2345  6.7813736000000e+00\r\n1242 2345 -9.0410623000000e-01\r\n2344 2345 -1.3475629000000e+02\r\n2345 2345 -2.7720556000000e+01\r\n2346 2345  1.7489967000000e+00\r\n2347 2345  4.4770925000000e-01\r\n2349 2345 -4.0941591000000e-01\r\n2392 2345  1.3190091000000e+01\r\n2394 2345 -4.3240035000000e-01\r\n1240 2346  1.1463234000000e+01\r\n1241 2346 -1.0989584000000e+00\r\n1242 2346 -1.5283012000000e+00\r\n2344 2346 -2.2779204000000e+02\r\n2345 2346  2.5292823000000e+01\r\n2346 2346  2.9565041000000e+00\r\n2347 2346  7.5680772000000e-01\r\n2348 2346 -7.2553717000000e-02\r\n2349 2346 -6.9207666000000e-01\r\n2392 2346  2.2296530000000e+01\r\n2393 2346 -2.1375259000000e+00\r\n2394 2346 -7.3092956000000e-01\r\n1243 2347 -1.5646243000000e+00\r\n1245 2347 -9.5840005000000e-02\r\n2344 2347 -5.9736957000000e-01\r\n2346 2347 -8.1460968000000e-02\r\n2347 2347  1.9213530000000e+02\r\n2349 2347  3.3537638000000e-01\r\n2350 2347 -2.9022544000000e-01\r\n2352 2347 -3.8350367000000e-02\r\n2395 2347 -2.4885005000000e+00\r\n2397 2347 -4.0056499000000e-02\r\n1243 2348  5.7342234000000e+00\r\n1245 2348 -1.3780428000000e+00\r\n2346 2348 -4.0941591000000e-01\r\n2347 2348 -1.2662709000000e+02\r\n2348 2348 -2.8872728000000e+01\r\n2349 2348  2.9181068000000e+00\r\n2350 2348  2.5214740000000e-01\r\n2352 2348 -5.5141574000000e-01\r\n2395 2348  1.3032447000000e+01\r\n2397 2348 -5.7602974000000e-01\r\n1243 2349  9.6931234000000e+00\r\n1244 2349 -1.0942175000000e+00\r\n1245 2349 -2.3294416000000e+00\r\n2346 2349 -6.9207666000000e-01\r\n2347 2349 -2.1405027000000e+02\r\n2348 2349  2.6519672000000e+01\r\n2349 2349  4.9327643000000e+00\r\n2350 2349  4.2622967000000e-01\r\n2351 2349 -4.8115337000000e-02\r\n2352 2349 -9.3211241000000e-01\r\n2395 2349  2.2030033000000e+01\r\n2396 2349 -2.4868810000000e+00\r\n2397 2349 -9.7371988000000e-01\r\n1246 2350 -9.9109871000000e-01\r\n1248 2350 -4.8389152000000e-02\r\n2347 2350 -4.3030649000000e-01\r\n2349 2350 -3.8350367000000e-02\r\n2350 2350  1.7850343000000e+02\r\n2352 2350  1.8406498000000e-01\r\n2398 2350 -1.5899806000000e+00\r\n2400 2350 -1.7817074000000e-02\r\n1246 2351  4.9601271000000e+00\r\n1248 2351 -1.8565169000000e+00\r\n2349 2351 -5.5141574000000e-01\r\n2350 2351 -1.1776387000000e+02\r\n2351 2351 -2.9017221000000e+01\r\n2352 2351  3.0948062000000e+00\r\n2398 2351  1.1924609000000e+01\r\n2400 2351 -6.8365407000000e-01\r\n1246 2352  8.3845988000000e+00\r\n1247 2352 -1.0812350000000e+00\r\n1248 2352 -3.1382562000000e+00\r\n2349 2352 -9.3211241000000e-01\r\n2350 2352 -1.9906804000000e+02\r\n2351 2352  2.6676978000000e+01\r\n2352 2352  5.2314596000000e+00\r\n2398 2352  2.0157360000000e+01\r\n2399 2352 -2.5993900000000e+00\r\n2400 2352 -1.1556488000000e+00\r\n2353 2353  1.0000000000000e+00\r\n2354 2354  1.0000000000000e+00\r\n2355 2355  1.0000000000000e+00\r\n2356 2356  1.0000000000000e+00\r\n2357 2357  1.0000000000000e+00\r\n2358 2358  1.0000000000000e+00\r\n2359 2359  1.0000000000000e+00\r\n2360 2360  1.0000000000000e+00\r\n2361 2361  1.0000000000000e+00\r\n2362 2362  1.0000000000000e+00\r\n2363 2363  1.0000000000000e+00\r\n2364 2364  1.0000000000000e+00\r\n2365 2365  1.0000000000000e+00\r\n2366 2366  1.0000000000000e+00\r\n2367 2367  1.0000000000000e+00\r\n1264 2368 -1.0598457000000e+00\r\n1266 2368 -5.6946019000000e-02\r\n2368 2368  2.9681124000000e+02\r\n2370 2368  1.9437580000000e-01\r\n2416 2368 -3.2797939000000e+00\r\n2418 2368 -5.7327535000000e-02\r\n1264 2369  4.3202257000000e+00\r\n1266 2369 -9.0660211000000e-01\r\n2368 2369 -1.8942500000000e+02\r\n2369 2369 -4.5507683000000e+01\r\n2370 2369  1.8244089000000e+00\r\n2416 2369  1.6991600000000e+01\r\n2418 2369 -9.1275390000000e-01\r\n1264 2370  7.3029095000000e+00\r\n1265 2370 -8.4853454000000e-01\r\n1266 2370 -1.5325202000000e+00\r\n2368 2370 -3.2020402000000e+02\r\n2369 2370  4.0208884000000e+01\r\n2370 2370  3.0839808000000e+00\r\n2416 2370  2.8722601000000e+01\r\n2417 2370 -3.3373163000000e+00\r\n2418 2370 -1.5429192000000e+00\r\n2371 2371  1.0000000000000e+00\r\n2372 2372  1.0000000000000e+00\r\n2373 2373  1.0000000000000e+00\r\n2374 2374  1.0000000000000e+00\r\n2375 2375  1.0000000000000e+00\r\n2376 2376  1.0000000000000e+00\r\n2377 2377  1.0000000000000e+00\r\n2378 2378  1.0000000000000e+00\r\n2379 2379  1.0000000000000e+00\r\n2380 2380  1.0000000000000e+00\r\n2381 2381  1.0000000000000e+00\r\n2382 2382  1.0000000000000e+00\r\n1279 2383 -1.6396503000000e+00\r\n1281 2383 -1.0601787000000e-01\r\n2383 2383  2.7574247000000e+02\r\n2385 2383  3.6499262000000e-01\r\n2386 2383 -6.1507789000000e-01\r\n2388 2383 -8.6551270000000e-02\r\n2431 2383 -4.4085565000000e+00\r\n2433 2383 -9.2258094000000e-02\r\n1279 2384  5.0504538000000e+00\r\n1281 2384 -7.6576743000000e-01\r\n2383 2384 -1.7744806000000e+02\r\n2384 2384 -3.8965438000000e+01\r\n2385 2384  2.0616847000000e+00\r\n2386 2384  9.0536898000000e-01\r\n2388 2384 -6.2514227000000e-01\r\n2431 2384  1.6821468000000e+01\r\n2433 2384 -6.6644976000000e-01\r\n1279 2385  8.5372823000000e+00\r\n1280 2385 -8.6332697000000e-01\r\n1281 2385 -1.2944525000000e+00\r\n2383 2385 -2.9995803000000e+02\r\n2384 2385  3.4751750000000e+01\r\n2385 2385  3.4850699000000e+00\r\n2386 2385  1.5304349000000e+00\r\n2387 2385 -1.5476419000000e-01\r\n2388 2385 -1.0567399000000e+00\r\n2431 2385  2.8434994000000e+01\r\n2432 2385 -2.8754695000000e+00\r\n2433 2385 -1.1265661000000e+00\r\n1282 2386 -9.3051390000000e-01\r\n1284 2386 -5.0587676000000e-02\r\n2383 2386 -7.8096942000000e-01\r\n2385 2386 -8.6551270000000e-02\r\n2386 2386  2.5031789000000e+02\r\n2388 2386  2.8883617000000e-01\r\n2389 2386 -3.2579693000000e-01\r\n2391 2386 -3.4705689000000e-02\r\n2434 2386 -2.6040483000000e+00\r\n2436 2386 -3.7153598000000e-02\r\n1282 2387  4.0955182000000e+00\r\n1284 2387 -1.1961635000000e+00\r\n2385 2387 -6.2514227000000e-01\r\n2386 2387 -1.6186823000000e+02\r\n2387 2387 -3.9385424000000e+01\r\n2388 2387  3.5248979000000e+00\r\n2389 2387  3.9373351000000e-01\r\n2391 2387 -8.2061419000000e-01\r\n2434 2387  1.6163394000000e+01\r\n2436 2387 -8.7860497000000e-01\r\n1282 2388  6.9230640000000e+00\r\n1283 2388 -8.4521630000000e-01\r\n1284 2388 -2.0219947000000e+00\r\n2385 2388 -1.0567399000000e+00\r\n2386 2388 -2.7362206000000e+02\r\n2387 2388  3.5440174000000e+01\r\n2388 2388  5.9584868000000e+00\r\n2389 2388  6.6556713000000e-01\r\n2390 2388 -8.1257112000000e-02\r\n2391 2388 -1.3871662000000e+00\r\n2434 2388  2.7322602000000e+01\r\n2435 2388 -3.3357352000000e+00\r\n2436 2388 -1.4851938000000e+00\r\n1285 2389 -8.4718938000000e-01\r\n1287 2389 -2.5902910000000e-02\r\n2386 2389 -5.5655431000000e-01\r\n2388 2389 -3.4705689000000e-02\r\n2389 2389  2.3133653000000e+02\r\n2391 2389  1.7179654000000e-01\r\n2392 2389 -2.9991573000000e-01\r\n2394 2389 -1.5280895000000e-02\r\n2437 2389 -1.5088876000000e+00\r\n2439 2389 -1.6257926000000e-02\r\n1285 2390  4.2913868000000e+00\r\n1287 2390 -1.5525563000000e+00\r\n2388 2390 -8.2061419000000e-01\r\n2389 2390 -1.5005877000000e+02\r\n2390 2390 -3.8687284000000e+01\r\n2391 2390  4.2679152000000e+00\r\n2392 2390  1.5790958000000e-01\r\n2394 2390 -9.1589138000000e-01\r\n2437 2390  1.4485912000000e+01\r\n2439 2390 -9.7455670000000e-01\r\n1285 2391  7.2541553000000e+00\r\n1286 2391 -9.5604276000000e-01\r\n1287 2391 -2.6244395000000e+00\r\n2388 2391 -1.3871662000000e+00\r\n2389 2391 -2.5365918000000e+02\r\n2390 2391  3.4830996000000e+01\r\n2391 2391  7.2144801000000e+00\r\n2392 2391  2.6693018000000e-01\r\n2393 2391 -3.5179377000000e-02\r\n2394 2391 -1.5482218000000e+00\r\n2437 2391  2.4486970000000e+01\r\n2438 2391 -3.2271970000000e+00\r\n2439 2391 -1.6473896000000e+00\r\n1288 2392 -4.4712793000000e-01\r\n1290 2392 -1.0826631000000e-02\r\n2344 2392 -2.9355577000000e+00\r\n2346 2392 -8.6020643000000e-02\r\n2389 2392 -5.2147888000000e-01\r\n2391 2392 -1.5280895000000e-02\r\n2392 2392  2.1531326000000e+02\r\n2394 2392  1.2170622000000e-01\r\n2395 2392 -1.0698811000000e-01\r\n2397 2392 -3.1350724000000e-03\r\n2440 2392 -7.3065393000000e-01\r\n2442 2392 -5.8063662000000e-03\r\n1288 2393  1.7302139000000e+00\r\n1290 2393 -1.9560092000000e+00\r\n2346 2393 -4.3240035000000e-01\r\n2391 2393 -9.1589138000000e-01\r\n2392 2393 -1.3496158000000e+02\r\n2393 2393 -3.7418826000000e+01\r\n2394 2393  5.3905033000000e+00\r\n2397 2393 -1.0329256000000e+00\r\n2440 2393  1.2199921000000e+01\r\n2442 2393 -1.0491197000000e+00\r\n1288 2394  2.9247536000000e+00\r\n1289 2394 -4.1335937000000e-01\r\n1290 2394 -3.3064380000000e+00\r\n2346 2394 -7.3092956000000e-01\r\n2391 2394 -1.5482218000000e+00\r\n2392 2394 -2.2813906000000e+02\r\n2393 2394  3.2922321000000e+01\r\n2394 2394  9.1121048000000e+00\r\n2397 2394 -1.7460565000000e+00\r\n2440 2394  2.0622746000000e+01\r\n2441 2394 -2.9146405000000e+00\r\n2442 2394 -1.7734320000000e+00\r\n1291 2395 -2.9366187000000e-01\r\n1293 2395 -6.8230113000000e-03\r\n2347 2395 -1.3669761000000e+00\r\n2349 2395 -4.0056499000000e-02\r\n2392 2395 -1.8661935000000e-01\r\n2394 2395 -3.1350724000000e-03\r\n2395 2395  1.9551180000000e+02\r\n2397 2395  5.6089800000000e-02\r\n2398 2395 -8.3317449000000e-02\r\n2400 2395 -2.4414511000000e-03\r\n2443 2395 -5.5883715000000e-01\r\n2445 2395 -3.0823466000000e-03\r\n1291 2396  1.3289956000000e+00\r\n1293 2396 -2.2480915000000e+00\r\n2349 2396 -5.7602974000000e-01\r\n2392 2396  1.8415965000000e+00\r\n2394 2396 -1.0329256000000e+00\r\n2395 2396 -1.2451462000000e+02\r\n2396 2396 -3.4875408000000e+01\r\n2397 2396  5.8534598000000e+00\r\n2400 2396 -9.7684548000000e-01\r\n2443 2396  1.0400277000000e+01\r\n2445 2396 -1.0156925000000e+00\r\n1291 2397  2.2465328000000e+00\r\n1292 2397 -3.3455223000000e-01\r\n1293 2397 -3.8001718000000e+00\r\n2349 2397 -9.7371988000000e-01\r\n2392 2397  3.1130329000000e+00\r\n2393 2397 -4.6359086000000e-01\r\n2394 2397 -1.7460565000000e+00\r\n2395 2397 -2.1047939000000e+02\r\n2396 2397  3.0994421000000e+01\r\n2397 2397  9.8946836000000e+00\r\n2400 2397 -1.6512596000000e+00\r\n2443 2397  1.7580618000000e+01\r\n2444 2397 -2.6180942000000e+00\r\n2445 2397 -1.7169257000000e+00\r\n1294 2398 -3.8461282000000e-01\r\n1296 2398 -6.1008077000000e-03\r\n2350 2398 -1.0074344000000e+00\r\n2352 2398 -1.7817074000000e-02\r\n2395 2398 -1.8152092000000e-01\r\n2397 2398 -2.4414511000000e-03\r\n2398 2398  1.8327200000000e+02\r\n2400 2398  2.9297710000000e-02\r\n2446 2398 -3.7470591000000e-01\r\n2448 2398 -2.4309867000000e-03\r\n1294 2399  1.4905014000000e+00\r\n1296 2399 -2.4410548000000e+00\r\n2352 2399 -6.8365407000000e-01\r\n2395 2399  1.6902004000000e+00\r\n2397 2399 -9.7684548000000e-01\r\n2398 2399 -1.1646374000000e+02\r\n2399 2399 -3.2951383000000e+01\r\n2400 2399  5.0780055000000e+00\r\n2446 2399  9.0636068000000e+00\r\n2448 2399 -9.7278993000000e-01\r\n1294 2400  2.5195436000000e+00\r\n1295 2400 -3.6847132000000e-01\r\n1296 2400 -4.1263590000000e+00\r\n2352 2400 -1.1556488000000e+00\r\n2395 2400  2.8571148000000e+00\r\n2396 2400 -4.1783950000000e-01\r\n2397 2400 -1.6512596000000e+00\r\n2398 2400 -1.9687031000000e+02\r\n2399 2400  2.9082529000000e+01\r\n2400 2400  8.5838604000000e+00\r\n2446 2400  1.5321121000000e+01\r\n2447 2400 -2.2406414000000e+00\r\n2448 2400 -1.6444041000000e+00\r\n2401 2401  1.0000000000000e+00\r\n2402 2402  1.0000000000000e+00\r\n2403 2403  1.0000000000000e+00\r\n2404 2404  1.0000000000000e+00\r\n2405 2405  1.0000000000000e+00\r\n2406 2406  1.0000000000000e+00\r\n2407 2407  1.0000000000000e+00\r\n2408 2408  1.0000000000000e+00\r\n2409 2409  1.0000000000000e+00\r\n2410 2410  1.0000000000000e+00\r\n2411 2411  1.0000000000000e+00\r\n2412 2412  1.0000000000000e+00\r\n2413 2413  1.0000000000000e+00\r\n2414 2414  1.0000000000000e+00\r\n2415 2415  1.0000000000000e+00\r\n1312 2416 -3.0967807000000e-01\r\n1314 2416 -6.8032816000000e-03\r\n2368 2416 -1.9563709000000e+00\r\n2370 2416 -5.7327535000000e-02\r\n2416 2416  2.9596269000000e+02\r\n2418 2416  8.1607565000000e-02\r\n2419 2416 -3.3311843000000e-01\r\n2421 2416 -9.7613690000000e-03\r\n2464 2416 -9.1982911000000e-01\r\n2466 2416 -6.8459793000000e-03\r\n1312 2417  1.7834780000000e+00\r\n1314 2417 -1.4328639000000e+00\r\n2370 2417 -9.1275390000000e-01\r\n2416 2417 -1.8566944000000e+02\r\n2417 2417 -5.2249143000000e+01\r\n2418 2417  5.1741385000000e+00\r\n2421 2417 -1.3807167000000e+00\r\n2464 2417  1.5807417000000e+01\r\n2466 2417 -1.4419946000000e+00\r\n1312 2418  3.0147912000000e+00\r\n1313 2418 -4.3302307000000e-01\r\n1314 2418 -2.4221131000000e+00\r\n2370 2418 -1.5429192000000e+00\r\n2416 2418 -3.1385562000000e+02\r\n2417 2418  4.5541410000000e+01\r\n2418 2418  8.7463620000000e+00\r\n2421 2418 -2.3339618000000e+00\r\n2464 2418  2.6720858000000e+01\r\n2465 2418 -3.8379931000000e+00\r\n2466 2418 -2.4375476000000e+00\r\n1315 2419 -4.7974428000000e-01\r\n1317 2419 -9.6598344000000e-03\r\n2416 2419 -3.4809373000000e-01\r\n2418 2419 -9.7613690000000e-03\r\n2419 2419  2.9481710000000e+02\r\n2421 2419  1.1867912000000e-01\r\n2422 2419 -2.3723633000000e-01\r\n2424 2419 -9.7613843000000e-03\r\n2467 2419 -1.3068024000000e+00\r\n2469 2419 -9.7302577000000e-03\r\n1315 2420  2.8271925000000e+00\r\n1317 2420 -1.3664069000000e+00\r\n2416 2420  6.3114563000000e-01\r\n2418 2420 -1.3807167000000e+00\r\n2419 2420 -1.8761480000000e+02\r\n2420 2420 -5.1494702000000e+01\r\n2421 2420  5.4655191000000e+00\r\n2424 2420 -1.3361793000000e+00\r\n2467 2420  1.6075890000000e+01\r\n2469 2420 -1.3764911000000e+00\r\n1315 2421  4.7790828000000e+00\r\n1316 2421 -6.8126319000000e-01\r\n1317 2421 -2.3097726000000e+00\r\n2416 2421  1.0668878000000e+00\r\n2417 2421 -1.5208596000000e-01\r\n2418 2421 -2.3339618000000e+00\r\n2419 2421 -3.1714383000000e+02\r\n2420 2421  4.5386677000000e+01\r\n2421 2421  9.2389084000000e+00\r\n2424 2421 -2.2586774000000e+00\r\n2467 2421  2.7174665000000e+01\r\n2468 2421 -3.8737766000000e+00\r\n2469 2421 -2.3268189000000e+00\r\n1318 2422 -5.3440022000000e-01\r\n1320 2422 -1.2395542000000e-02\r\n2419 2422 -2.2070197000000e-01\r\n2421 2422 -9.7613843000000e-03\r\n2422 2422  2.9491118000000e+02\r\n2424 2422  1.2905618000000e-01\r\n2425 2422 -3.3024883000000e-01\r\n2427 2422 -1.4606511000000e-02\r\n2470 2422 -1.3780511000000e+00\r\n2472 2422 -1.2496808000000e-02\r\n1318 2423  3.2197658000000e+00\r\n1320 2423 -1.3213394000000e+00\r\n2419 2423  2.3582194000000e-01\r\n2421 2423 -1.3361793000000e+00\r\n2422 2423 -1.8821336000000e+02\r\n2423 2423 -5.0966088000000e+01\r\n2424 2423  5.2984249000000e+00\r\n2427 2423 -1.3029946000000e+00\r\n2470 2423  1.6674148000000e+01\r\n2472 2423 -1.3322460000000e+00\r\n1318 2424  5.4426922000000e+00\r\n1319 2424 -7.5084820000000e-01\r\n1320 2424 -2.2335922000000e+00\r\n2419 2424  3.9863340000000e-01\r\n2420 2424 -5.4993585000000e-02\r\n2421 2424 -2.2586774000000e+00\r\n2422 2424 -3.1815586000000e+02\r\n2423 2424  4.4963881000000e+01\r\n2424 2424  8.9564554000000e+00\r\n2427 2424 -2.2025800000000e+00\r\n2470 2424  2.8185979000000e+01\r\n2471 2424 -3.8884051000000e+00\r\n2472 2424 -2.2520286000000e+00\r\n1321 2425 -5.8237589000000e-01\r\n1323 2425 -1.4442702000000e-02\r\n2422 2425 -3.4512318000000e-01\r\n2424 2425 -1.4606511000000e-02\r\n2425 2425  2.9515983000000e+02\r\n2427 2425  1.3803140000000e-01\r\n2428 2425 -3.3017192000000e-01\r\n2430 2425 -1.4603109000000e-02\r\n2473 2425 -1.4531784000000e+00\r\n2475 2425 -1.4561047000000e-02\r\n1321 2426  3.2091214000000e+00\r\n1323 2426 -1.2884342000000e+00\r\n2422 2426  2.4120100000000e-01\r\n2424 2426 -1.3029946000000e+00\r\n2425 2426 -1.8867034000000e+02\r\n2426 2426 -5.0571975000000e+01\r\n2427 2426  5.1990686000000e+00\r\n2430 2426 -1.3029156000000e+00\r\n2473 2426  1.7134703000000e+01\r\n2475 2426 -1.2991028000000e+00\r\n1321 2427  5.4246936000000e+00\r\n1322 2427 -7.2975635000000e-01\r\n1323 2427 -2.1779671000000e+00\r\n2422 2427  4.0772578000000e-01\r\n2423 2427 -5.4849268000000e-02\r\n2424 2427 -2.2025800000000e+00\r\n2425 2427 -3.1892805000000e+02\r\n2426 2427  4.4643506000000e+01\r\n2427 2427  8.7884993000000e+00\r\n2430 2427 -2.2024485000000e+00\r\n2473 2427  2.8964476000000e+01\r\n2474 2427 -3.8964426000000e+00\r\n2475 2427 -2.1960012000000e+00\r\n1324 2428 -5.4870071000000e-01\r\n1326 2428 -1.4434007000000e-02\r\n2425 2428 -3.4452271000000e-01\r\n2427 2428 -1.4603109000000e-02\r\n2428 2428  2.9519042000000e+02\r\n2430 2428  1.3772053000000e-01\r\n2431 2428 -3.9655657000000e-01\r\n2433 2428 -1.4302015000000e-02\r\n2476 2428 -1.4513846000000e+00\r\n2478 2428 -1.4563380000000e-02\r\n1324 2429  2.6632591000000e+00\r\n1326 2429 -1.2878855000000e+00\r\n2425 2429  2.3108844000000e-01\r\n2427 2429 -1.3029156000000e+00\r\n2428 2429 -1.8840910000000e+02\r\n2429 2429 -5.0572276000000e+01\r\n2430 2429  5.1720305000000e+00\r\n2431 2429  3.2512559000000e-01\r\n2433 2429 -1.2760733000000e+00\r\n2476 2429  1.7104165000000e+01\r\n2478 2429 -1.2995346000000e+00\r\n1324 2430  4.5019731000000e+00\r\n1325 2430 -6.0564353000000e-01\r\n1326 2430 -2.1770417000000e+00\r\n2425 2430  3.9063189000000e-01\r\n2426 2430 -5.2551108000000e-02\r\n2427 2430 -2.2024485000000e+00\r\n2428 2430 -3.1848675000000e+02\r\n2429 2430  4.4584784000000e+01\r\n2430 2430  8.7428003000000e+00\r\n2431 2430  5.4959229000000e-01\r\n2432 2430 -7.3935807000000e-02\r\n2433 2430 -2.1570743000000e+00\r\n2476 2430  2.8912880000000e+01\r\n2477 2430 -3.8896053000000e+00\r\n2478 2430 -2.1967333000000e+00\r\n1327 2431 -3.4095124000000e-01\r\n1329 2431 -8.2969956000000e-03\r\n2383 2431 -3.1484183000000e+00\r\n2385 2431 -9.2258094000000e-02\r\n2428 2431 -4.8807342000000e-01\r\n2430 2431 -1.4302015000000e-02\r\n2431 2431  2.8583675000000e+02\r\n2433 2431  1.2751677000000e-01\r\n2434 2431 -1.3435734000000e-01\r\n2436 2431 -3.9370728000000e-03\r\n2479 2431 -9.7714131000000e-01\r\n2481 2431 -7.8713173000000e-03\r\n1327 2432  1.2994774000000e+00\r\n1329 2432 -1.4623719000000e+00\r\n2385 2432 -6.6644976000000e-01\r\n2430 2432 -1.2760733000000e+00\r\n2431 2432 -1.7893272000000e+02\r\n2432 2432 -4.9860319000000e+01\r\n2433 2432  6.2021635000000e+00\r\n2436 2432 -1.4042632000000e+00\r\n2479 2432  1.6275427000000e+01\r\n2481 2432 -1.3874621000000e+00\r\n1327 2433  2.1966357000000e+00\r\n1328 2433 -3.0957355000000e-01\r\n1329 2433 -2.4719924000000e+00\r\n2385 2433 -1.1265661000000e+00\r\n2430 2433 -2.1570743000000e+00\r\n2431 2433 -3.0246773000000e+02\r\n2432 2433  4.3576472000000e+01\r\n2433 2433  1.0484134000000e+01\r\n2436 2433 -2.3737664000000e+00\r\n2479 2433  2.7511970000000e+01\r\n2480 2433 -3.8772832000000e+00\r\n2481 2433 -2.3453649000000e+00\r\n1330 2434 -2.9504895000000e-01\r\n1332 2434 -4.6541406000000e-03\r\n2386 2434 -2.1007833000000e+00\r\n2388 2434 -3.7153598000000e-02\r\n2431 2434 -2.6304068000000e-01\r\n2433 2434 -3.9370728000000e-03\r\n2434 2434  2.6662637000000e+02\r\n2436 2434  5.2795262000000e-02\r\n2437 2434 -1.3656872000000e-01\r\n2439 2434 -2.4152988000000e-03\r\n2482 2434 -6.3341179000000e-01\r\n2484 2434 -3.8897599000000e-03\r\n1330 2435  1.1842029000000e+00\r\n1332 2435 -1.6601180000000e+00\r\n2388 2435 -8.7860497000000e-01\r\n2431 2435  1.5518434000000e+00\r\n2433 2435 -1.4042632000000e+00\r\n2434 2435 -1.6978536000000e+02\r\n2435 2435 -4.7687417000000e+01\r\n2436 2435  6.6794454000000e+00\r\n2439 2435 -1.3435779000000e+00\r\n2482 2435  1.5780879000000e+01\r\n2484 2435 -1.3875787000000e+00\r\n1330 2436  2.0017766000000e+00\r\n1331 2436 -2.8967534000000e-01\r\n1332 2436 -2.8062634000000e+00\r\n2388 2436 -1.4851938000000e+00\r\n2431 2436  2.6232360000000e+00\r\n2432 2436 -3.7960619000000e-01\r\n2433 2436 -2.3737664000000e+00\r\n2434 2436 -2.8700517000000e+02\r\n2435 2436  4.2190864000000e+01\r\n2436 2436  1.1290933000000e+01\r\n2439 2436 -2.2711827000000e+00\r\n2482 2436  2.6675998000000e+01\r\n2483 2436 -3.8602604000000e+00\r\n2484 2436 -2.3455630000000e+00\r\n1333 2437 -2.2019369000000e-01\r\n1335 2437 -3.3956081000000e-03\r\n2389 2437 -9.1927516000000e-01\r\n2391 2437 -1.6257926000000e-02\r\n2434 2437 -1.8953279000000e-01\r\n2436 2437 -2.4152988000000e-03\r\n2437 2437  2.4169261000000e+02\r\n2439 2437  2.6043391000000e-02\r\n2440 2437 -5.3069369000000e-02\r\n2442 2437 -9.3856322000000e-04\r\n2485 2437 -5.1077148000000e-01\r\n2487 2437 -2.3842212000000e-03\r\n1333 2438  1.1119848000000e+00\r\n1335 2438 -1.8889917000000e+00\r\n2391 2438 -9.7455670000000e-01\r\n2434 2438  2.0469679000000e+00\r\n2436 2438 -1.3435779000000e+00\r\n2437 2438 -1.5535403000000e+02\r\n2438 2438 -4.3939068000000e+01\r\n2439 2438  6.8279238000000e+00\r\n2442 2438 -1.2894421000000e+00\r\n2485 2438  1.4375670000000e+01\r\n2487 2438 -1.3264689000000e+00\r\n1333 2439  1.8796978000000e+00\r\n1334 2439 -2.8178126000000e-01\r\n1335 2439 -3.1931494000000e+00\r\n2391 2439 -1.6473896000000e+00\r\n2434 2439  3.4601925000000e+00\r\n2435 2439 -5.1870963000000e-01\r\n2436 2439 -2.2711827000000e+00\r\n2437 2439 -2.6261028000000e+02\r\n2438 2439  3.9136646000000e+01\r\n2439 2439  1.1541916000000e+01\r\n2442 2439 -2.1796728000000e+00\r\n2485 2439  2.4300617000000e+01\r\n2486 2439 -3.6428508000000e+00\r\n2487 2439 -2.2422615000000e+00\r\n1336 2440 -1.5634686000000e-01\r\n1338 2440 -1.5465596000000e-03\r\n2392 2440 -5.5635440000000e-01\r\n2394 2440 -5.8063662000000e-03\r\n2437 2440 -1.1556991000000e-01\r\n2439 2440 -9.3856322000000e-04\r\n2440 2440  2.2336393000000e+02\r\n2442 2440  1.0440761000000e-02\r\n2443 2440 -6.2428621000000e-02\r\n2445 2440 -6.5153333000000e-04\r\n2488 2440 -2.2303952000000e-01\r\n2490 2440 -9.2559310000000e-04\r\n1336 2441  7.9859598000000e-01\r\n1338 2441 -2.1248446000000e+00\r\n2394 2441 -1.0491197000000e+00\r\n2437 2441  2.4947264000000e+00\r\n2439 2441 -1.2894421000000e+00\r\n2440 2441 -1.4421959000000e+02\r\n2441 2441 -4.1297090000000e+01\r\n2442 2441  6.9523798000000e+00\r\n2445 2441 -1.2125901000000e+00\r\n2488 2441  1.3195320000000e+01\r\n2490 2441 -1.2717896000000e+00\r\n1336 2442  1.3499466000000e+00\r\n1337 2442 -2.0421983000000e-01\r\n1338 2442 -3.5918374000000e+00\r\n2394 2442 -1.7734320000000e+00\r\n2437 2442  4.2170855000000e+00\r\n2438 2442 -6.3796040000000e-01\r\n2439 2442 -2.1796728000000e+00\r\n2440 2442 -2.4378879000000e+02\r\n2441 2442  3.6812861000000e+01\r\n2442 2442  1.1752301000000e+01\r\n2445 2442 -2.0497609000000e+00\r\n2488 2442  2.2305368000000e+01\r\n2489 2442 -3.3743546000000e+00\r\n2490 2442 -2.1498331000000e+00\r\n1339 2443 -1.2770622000000e-01\r\n1341 2443 -1.2616964000000e-03\r\n2395 2443 -2.9534429000000e-01\r\n2397 2443 -3.0823466000000e-03\r\n2440 2443 -9.3203764000000e-02\r\n2442 2443 -6.5153333000000e-04\r\n2443 2443  2.0543003000000e+02\r\n2445 2443  6.5246799000000e-03\r\n2446 2443 -3.5684063000000e-02\r\n2448 2443 -3.7241503000000e-04\r\n2491 2443 -1.7500042000000e-01\r\n2493 2443 -6.4179336000000e-04\r\n1339 2444  6.7186696000000e-01\r\n1341 2444 -2.3482642000000e+00\r\n2397 2444 -1.0156925000000e+00\r\n2440 2444  3.0248844000000e+00\r\n2442 2444 -1.2125901000000e+00\r\n2443 2444 -1.3262705000000e+02\r\n2444 2444 -3.8253343000000e+01\r\n2445 2444  6.9288974000000e+00\r\n2448 2444 -1.1534979000000e+00\r\n2491 2444  1.1284571000000e+01\r\n2493 2444 -1.1945971000000e+00\r\n1339 2445  1.1357231000000e+00\r\n1340 2445 -1.7486584000000e-01\r\n1341 2445 -3.9695031000000e+00\r\n2397 2445 -1.7169257000000e+00\r\n2440 2445  5.1132610000000e+00\r\n2441 2445 -7.8728226000000e-01\r\n2442 2445 -2.0497609000000e+00\r\n2443 2445 -2.2419261000000e+02\r\n2444 2445  3.4089825000000e+01\r\n2445 2445  1.1712602000000e+01\r\n2448 2445 -1.9498729000000e+00\r\n2491 2445  1.9075426000000e+01\r\n2492 2445 -2.9370187000000e+00\r\n2493 2445 -2.0193456000000e+00\r\n1342 2446 -8.5011201000000e-02\r\n1344 2446 -8.2063256000000e-04\r\n2398 2446 -2.3293228000000e-01\r\n2400 2446 -2.4309867000000e-03\r\n2443 2446 -6.6743872000000e-02\r\n2445 2446 -3.7241503000000e-04\r\n2446 2446  1.9346372000000e+02\r\n2448 2446  4.4624599000000e-03\r\n2494 2446 -7.4440291000000e-02\r\n2496 2446 -3.6626510000000e-04\r\n1342 2447  6.2918306000000e-01\r\n1344 2447 -2.5418704000000e+00\r\n2400 2447 -9.7278993000000e-01\r\n2443 2447  3.0489591000000e+00\r\n2445 2447 -1.1534979000000e+00\r\n2446 2447 -1.2100872000000e+02\r\n2447 2447 -3.6306218000000e+01\r\n2448 2447  5.8067595000000e+00\r\n2494 2447  6.4090076000000e+00\r\n2496 2447 -1.1345621000000e+00\r\n1342 2448  1.0635711000000e+00\r\n1343 2448 -1.6709874000000e-01\r\n1344 2448 -4.2967777000000e+00\r\n2400 2448 -1.6444041000000e+00\r\n2443 2448  5.1539605000000e+00\r\n2444 2448 -8.0974397000000e-01\r\n2445 2448 -1.9498729000000e+00\r\n2446 2448 -2.0455313000000e+02\r\n2447 2448  3.1328710000000e+01\r\n2448 2448  9.8157463000000e+00\r\n2494 2448  1.0833787000000e+01\r\n2495 2448 -1.7021073000000e+00\r\n2496 2448 -1.9178638000000e+00\r\n2449 2449  1.0000000000000e+00\r\n2450 2450  1.0000000000000e+00\r\n2451 2451  1.0000000000000e+00\r\n2452 2452  1.0000000000000e+00\r\n2453 2453  1.0000000000000e+00\r\n2454 2454  1.0000000000000e+00\r\n2455 2455  1.0000000000000e+00\r\n2456 2456  1.0000000000000e+00\r\n2457 2457  1.0000000000000e+00\r\n2458 2458  1.0000000000000e+00\r\n2459 2459  1.0000000000000e+00\r\n2460 2460  1.0000000000000e+00\r\n2461 2461  1.0000000000000e+00\r\n2462 2462  1.0000000000000e+00\r\n2463 2463  1.0000000000000e+00\r\n1360 2464 -9.8766101000000e-02\r\n1362 2464 -9.2950667000000e-04\r\n2416 2464 -6.5596805000000e-01\r\n2418 2464 -6.8459793000000e-03\r\n2464 2464  2.9352001000000e+02\r\n2466 2464  1.0396617000000e-02\r\n2467 2464 -9.3000819000000e-02\r\n2469 2464 -9.4227837000000e-04\r\n2512 2464 -2.5620509000000e-01\r\n2514 2464 -9.4049579000000e-04\r\n1360 2465  9.5313717000000e-01\r\n1362 2465 -1.6372305000000e+00\r\n2418 2465 -1.4419946000000e+00\r\n2464 2465 -1.8558381000000e+02\r\n2465 2465 -5.0099419000000e+01\r\n2466 2465  6.4016278000000e+00\r\n2467 2465  2.7167489000000e-01\r\n2469 2465 -1.6596434000000e+00\r\n2512 2465  1.6314945000000e+01\r\n2514 2465 -1.6566787000000e+00\r\n1360 2466  1.6111831000000e+00\r\n1361 2466 -2.4736688000000e-01\r\n1362 2466 -2.7675744000000e+00\r\n2418 2466 -2.4375476000000e+00\r\n2464 2466 -3.1371087000000e+02\r\n2465 2466  5.5228420000000e+01\r\n2466 2466  1.0821312000000e+01\r\n2467 2466  4.5923923000000e-01\r\n2468 2466 -7.0507554000000e-02\r\n2469 2466 -2.8054613000000e+00\r\n2512 2466  2.7578783000000e+01\r\n2513 2466 -4.2342038000000e+00\r\n2514 2466 -2.8004497000000e+00\r\n1363 2467 -1.1706066000000e-01\r\n1365 2467 -1.1066138000000e-03\r\n2419 2467 -9.3233383000000e-01\r\n2421 2467 -9.7302577000000e-03\r\n2464 2467 -9.0287229000000e-02\r\n2466 2467 -9.4227837000000e-04\r\n2467 2467  2.9394698000000e+02\r\n2469 2467  1.4768954000000e-02\r\n2470 2467 -1.1206181000000e-01\r\n2472 2467 -1.1217214000000e-03\r\n2515 2467 -2.7705098000000e-01\r\n2517 2467 -1.1192633000000e-03\r\n1363 2468  1.0766425000000e+00\r\n1365 2468 -1.6200209000000e+00\r\n2421 2468 -1.3764911000000e+00\r\n2466 2468 -1.6596434000000e+00\r\n2467 2468 -1.8620080000000e+02\r\n2468 2468 -5.4424641000000e+01\r\n2469 2468  7.9428916000000e+00\r\n2470 2468  4.0444868000000e-01\r\n2472 2468 -1.6420458000000e+00\r\n2515 2468  1.6672940000000e+01\r\n2517 2468 -1.6386315000000e+00\r\n1363 2469  1.8199554000000e+00\r\n1364 2469 -2.7645389000000e-01\r\n1365 2469 -2.7384818000000e+00\r\n2421 2469 -2.3268189000000e+00\r\n2466 2469 -2.8054613000000e+00\r\n2467 2469 -3.1475365000000e+02\r\n2468 2469  4.7565742000000e+01\r\n2469 2469  1.3426657000000e+01\r\n2470 2469  6.8367964000000e-01\r\n2471 2469 -1.0385194000000e-01\r\n2472 2469 -2.7757126000000e+00\r\n2515 2469  2.8183922000000e+01\r\n2516 2469 -4.2811790000000e+00\r\n2517 2469 -2.7699410000000e+00\r\n1366 2470 -1.2019010000000e-01\r\n1368 2470 -1.6294661000000e-03\r\n2422 2470 -7.0660953000000e-01\r\n2424 2470 -1.2496808000000e-02\r\n2467 2470 -6.3425720000000e-02\r\n2469 2470 -1.1217214000000e-03\r\n2470 2470  2.9394226000000e+02\r\n2472 2470  1.9313937000000e-02\r\n2473 2470 -9.9581074000000e-02\r\n2475 2470 -1.6515049000000e-03\r\n2518 2470 -5.3094432000000e-01\r\n2520 2470 -1.6469005000000e-03\r\n1366 2471  1.1063236000000e+00\r\n1368 2471 -1.5896856000000e+00\r\n2424 2471 -1.3322460000000e+00\r\n2469 2471 -1.6420458000000e+00\r\n2470 2471 -1.8614785000000e+02\r\n2471 2471 -5.4087451000000e+01\r\n2472 2471  7.7879090000000e+00\r\n2473 2471  2.3826939000000e-01\r\n2475 2471 -1.6111141000000e+00\r\n2518 2471  1.6752403000000e+01\r\n2520 2471 -1.6067971000000e+00\r\n1366 2472  1.8701294000000e+00\r\n1367 2472 -2.8829951000000e-01\r\n1368 2472 -2.6872046000000e+00\r\n2424 2472 -2.2520286000000e+00\r\n2469 2472 -2.7757126000000e+00\r\n2470 2472 -3.1466433000000e+02\r\n2471 2472  4.7365100000000e+01\r\n2472 2472  1.3164680000000e+01\r\n2473 2472  4.0277057000000e-01\r\n2474 2472 -6.2091190000000e-02\r\n2475 2472 -2.7234273000000e+00\r\n2518 2472  2.8318262000000e+01\r\n2519 2472 -4.3655487000000e+00\r\n2520 2472 -2.7161298000000e+00\r\n1369 2473 -1.3991115000000e-01\r\n1371 2473 -2.0021021000000e-03\r\n2425 2473 -8.2332821000000e-01\r\n2427 2473 -1.4561047000000e-02\r\n2470 2473 -9.3381374000000e-02\r\n2472 2473 -1.6515049000000e-03\r\n2473 2473  2.9418307000000e+02\r\n2475 2473  2.3420341000000e-02\r\n2476 2473 -1.3599737000000e-01\r\n2478 2473 -2.4051940000000e-03\r\n2521 2473 -5.6806606000000e-01\r\n2523 2473 -2.0241031000000e-03\r\n1369 2474  1.0531180000000e+00\r\n1371 2474 -1.5754464000000e+00\r\n2427 2474 -1.2991028000000e+00\r\n2472 2474 -1.6111141000000e+00\r\n2473 2474 -1.8645872000000e+02\r\n2474 2474 -5.3928425000000e+01\r\n2475 2474  7.6666907000000e+00\r\n2478 2474 -1.5821610000000e+00\r\n2521 2474  1.7353461000000e+01\r\n2523 2474 -1.5928640000000e+00\r\n1369 2475  1.7801893000000e+00\r\n1370 2475 -2.7197895000000e-01\r\n1371 2475 -2.6631324000000e+00\r\n2427 2475 -2.1960012000000e+00\r\n2472 2475 -2.7234273000000e+00\r\n2473 2475 -3.1518956000000e+02\r\n2474 2475  4.7280929000000e+01\r\n2475 2475  1.2959767000000e+01\r\n2478 2475 -2.6744850000000e+00\r\n2521 2475  2.9334266000000e+01\r\n2522 2475 -4.4817162000000e+00\r\n2523 2475 -2.6925751000000e+00\r\n1372 2476 -1.5717120000000e-01\r\n1374 2476 -2.3738115000000e-03\r\n2428 2476 -8.2346008000000e-01\r\n2430 2476 -1.4563380000000e-02\r\n2473 2476 -1.4350652000000e-01\r\n2475 2476 -2.4051940000000e-03\r\n2476 2476  2.9422033000000e+02\r\n2478 2476  2.3826699000000e-02\r\n2479 2476 -7.3488376000000e-02\r\n2481 2476 -1.2996855000000e-03\r\n2524 2476 -5.9882884000000e-01\r\n2526 2476 -2.3994175000000e-03\r\n1372 2477  9.1004946000000e-01\r\n1374 2477 -1.5615681000000e+00\r\n2430 2477 -1.2995346000000e+00\r\n2473 2477  2.8805878000000e-01\r\n2475 2477 -1.5821610000000e+00\r\n2476 2477 -1.8697054000000e+02\r\n2477 2477 -5.3769714000000e+01\r\n2478 2477  7.6521091000000e+00\r\n2481 2477 -1.6243419000000e+00\r\n2524 2477  1.7718613000000e+01\r\n2526 2477 -1.5785190000000e+00\r\n1372 2478  1.5383476000000e+00\r\n1373 2478 -2.3291596000000e-01\r\n1374 2478 -2.6396747000000e+00\r\n2430 2478 -2.1967333000000e+00\r\n2473 2478  4.8693456000000e-01\r\n2474 2478 -7.3725097000000e-02\r\n2475 2478 -2.6744850000000e+00\r\n2476 2478 -3.1605500000000e+02\r\n2477 2478  4.7247887000000e+01\r\n2478 2478  1.2935123000000e+01\r\n2481 2478 -2.7457858000000e+00\r\n2524 2478  2.9951544000000e+01\r\n2525 2478 -4.5348610000000e+00\r\n2526 2478 -2.6683286000000e+00\r\n1375 2479 -1.3041278000000e-01\r\n1377 2479 -1.2818297000000e-03\r\n2431 2479 -7.5421388000000e-01\r\n2433 2479 -7.8713173000000e-03\r\n2476 2479 -1.3407438000000e-01\r\n2478 2479 -1.2996855000000e-03\r\n2479 2479  2.9384226000000e+02\r\n2481 2479  1.3481846000000e-02\r\n2482 2479 -9.3191329000000e-02\r\n2484 2479 -9.7258687000000e-04\r\n2527 2479 -3.0950011000000e-01\r\n2529 2479 -1.2972209000000e-03\r\n1375 2480  7.4406680000000e-01\r\n1377 2480 -1.6021115000000e+00\r\n2433 2480 -1.3874621000000e+00\r\n2476 2480  8.9881285000000e-01\r\n2478 2480 -1.6243419000000e+00\r\n2479 2480 -1.8788211000000e+02\r\n2480 2480 -5.4236743000000e+01\r\n2481 2480  7.8435408000000e+00\r\n2484 2480 -1.6021489000000e+00\r\n2527 2480  1.8189066000000e+01\r\n2529 2480 -1.6214392000000e+00\r\n1375 2481  1.2577697000000e+00\r\n1376 2481 -1.8902202000000e-01\r\n1377 2481 -2.7082075000000e+00\r\n2433 2481 -2.3453649000000e+00\r\n2476 2481  1.5193522000000e+00\r\n2477 2481 -2.2833356000000e-01\r\n2478 2481 -2.7457858000000e+00\r\n2479 2481 -3.1759570000000e+02\r\n2480 2481  4.7803050000000e+01\r\n2481 2481  1.3258715000000e+01\r\n2484 2481 -2.7082724000000e+00\r\n2527 2481  3.0746777000000e+01\r\n2528 2481 -4.6207335000000e+00\r\n2529 2481 -2.7408791000000e+00\r\n1378 2482 -1.0800179000000e-01\r\n1380 2482 -1.0533314000000e-03\r\n2434 2482 -3.7270901000000e-01\r\n2436 2482 -3.8897599000000e-03\r\n2479 2482 -1.1099011000000e-01\r\n2481 2482 -9.7258687000000e-04\r\n2482 2482  2.7579034000000e+02\r\n2484 2482  8.1467754000000e-03\r\n2485 2482 -5.3900889000000e-02\r\n2487 2482 -5.6253407000000e-04\r\n2530 2482 -2.7171014000000e-01\r\n2532 2482 -9.7113407000000e-04\r\n1378 2483  6.9758497000000e-01\r\n1380 2483 -1.7352467000000e+00\r\n2436 2483 -1.3875787000000e+00\r\n2479 2483  1.7518766000000e+00\r\n2481 2483 -1.6021489000000e+00\r\n2482 2483 -1.7796595000000e+02\r\n2483 2483 -5.1274641000000e+01\r\n2484 2483  7.8678110000000e+00\r\n2487 2483 -1.5372026000000e+00\r\n2530 2483  1.7552672000000e+01\r\n2532 2483 -1.5999259000000e+00\r\n1378 2484  1.1791976000000e+00\r\n1379 2484 -1.8038458000000e-01\r\n1380 2484 -2.9332610000000e+00\r\n2436 2484 -2.3455630000000e+00\r\n2479 2484  2.9613722000000e+00\r\n2480 2484 -4.5300793000000e-01\r\n2481 2484 -2.7082724000000e+00\r\n2482 2484 -3.0083364000000e+02\r\n2483 2484  4.5592825000000e+01\r\n2484 2484  1.3299746000000e+01\r\n2487 2484 -2.5984856000000e+00\r\n2530 2484  2.9671036000000e+01\r\n2531 2484 -4.5388468000000e+00\r\n2532 2484 -2.7045147000000e+00\r\n1381 2485 -7.2669536000000e-02\r\n1383 2485 -6.9405673000000e-04\r\n2437 2485 -2.2845131000000e-01\r\n2439 2485 -2.3842212000000e-03\r\n2482 2485 -7.8869753000000e-02\r\n2484 2485 -5.6253407000000e-04\r\n2485 2485  2.5793638000000e+02\r\n2487 2485  5.0683106000000e-03\r\n2488 2485 -2.2847552000000e-02\r\n2490 2485 -2.3844739000000e-04\r\n2533 2485 -2.0865268000000e-01\r\n2535 2485 -5.5588756000000e-04\r\n1381 2486  6.0934250000000e-01\r\n1383 2486 -1.8967026000000e+00\r\n2439 2486 -1.3264689000000e+00\r\n2482 2486  2.4509331000000e+00\r\n2484 2486 -1.5372026000000e+00\r\n2485 2486 -1.6719294000000e+02\r\n2486 2486 -4.8357234000000e+01\r\n2487 2486  7.7299432000000e+00\r\n2490 2486 -1.4449656000000e+00\r\n2533 2486  1.6255375000000e+01\r\n2535 2486 -1.5192191000000e+00\r\n1381 2487  1.0300319000000e+00\r\n1382 2487 -1.6116763000000e-01\r\n1383 2487 -3.2061840000000e+00\r\n2439 2487 -2.2422615000000e+00\r\n2482 2487  4.1430546000000e+00\r\n2483 2487 -6.4825788000000e-01\r\n2484 2487 -2.5984856000000e+00\r\n2485 2487 -2.8262276000000e+02\r\n2486 2487  4.3219585000000e+01\r\n2487 2487  1.3066689000000e+01\r\n2490 2487 -2.4425698000000e+00\r\n2533 2487  2.7478068000000e+01\r\n2534 2487 -4.2994544000000e+00\r\n2535 2487 -2.5680863000000e+00\r\n1384 2488 -1.0509246000000e-03\r\n1386 2488 -1.0967924000000e-05\r\n2440 2488 -8.8688480000000e-02\r\n2442 2488 -9.2559310000000e-04\r\n2485 2488 -5.4919468000000e-02\r\n2487 2488 -2.3844739000000e-04\r\n2488 2488  2.3420959000000e+02\r\n2490 2488  1.9744794000000e-03\r\n2491 2488 -6.4639159000000e-04\r\n2493 2488 -6.7460351000000e-06\r\n2536 2488 -1.3424802000000e-01\r\n2538 2488 -2.3272242000000e-04\r\n1384 2489  4.9940552000000e-01\r\n1386 2489 -2.1277579000000e+00\r\n2442 2489 -1.2717896000000e+00\r\n2485 2489  3.1495184000000e+00\r\n2487 2489 -1.4449656000000e+00\r\n2488 2489 -1.5324261000000e+02\r\n2489 2489 -4.4241303000000e+01\r\n2490 2489  7.6061764000000e+00\r\n2493 2489 -1.3462969000000e+00\r\n2536 2489  1.5161974000000e+01\r\n2538 2489 -1.4104398000000e+00\r\n1384 2490  8.4419509000000e-01\r\n1385 2490 -1.3465477000000e-01\r\n1386 2490 -3.5967619000000e+00\r\n2442 2490 -2.1498331000000e+00\r\n2485 2490  5.3239458000000e+00\r\n2486 2490 -8.4920502000000e-01\r\n2487 2490 -2.4425698000000e+00\r\n2488 2490 -2.5904131000000e+02\r\n2489 2490  3.9933058000000e+01\r\n2490 2490  1.2857479000000e+01\r\n2493 2490 -2.2757787000000e+00\r\n2536 2490  2.5629800000000e+01\r\n2537 2490 -4.0881248000000e+00\r\n2538 2490 -2.3842075000000e+00\r\n1387 2491 -1.1114540000000e-03\r\n1389 2491 -1.1599637000000e-05\r\n2443 2491 -6.1495356000000e-02\r\n2445 2491 -6.4179336000000e-04\r\n2488 2491 -4.4340814000000e-02\r\n2490 2491 -6.7460351000000e-06\r\n2491 2491  2.1659033000000e+02\r\n2493 2491  1.1787646000000e-03\r\n2494 2491 -5.7061594000000e-04\r\n2496 2491 -5.9552061000000e-06\r\n2539 2491 -9.8060401000000e-02\r\n2541 2491 -6.5671194000000e-06\r\n1387 2492  3.8041292000000e-01\r\n1389 2492 -2.3371655000000e+00\r\n2445 2492 -1.1945971000000e+00\r\n2488 2492  4.1481179000000e+00\r\n2490 2492 -1.3462969000000e+00\r\n2491 2492 -1.4447455000000e+02\r\n2492 2492 -4.1136159000000e+01\r\n2493 2492  7.4343623000000e+00\r\n2496 2492 -1.2409730000000e+00\r\n2539 2492  1.5597252000000e+01\r\n2541 2492 -1.3107487000000e+00\r\n1387 2493  6.4304949000000e-01\r\n1388 2493 -1.0418182000000e-01\r\n1389 2493 -3.9507414000000e+00\r\n2445 2493 -2.0193456000000e+00\r\n2488 2493  7.0119733000000e+00\r\n2489 2493 -1.1360247000000e+00\r\n2490 2493 -2.2757787000000e+00\r\n2491 2493 -2.4421959000000e+02\r\n2492 2493  3.7924460000000e+01\r\n2493 2493  1.2567038000000e+01\r\n2496 2493 -2.0977408000000e+00\r\n2539 2493  2.6365575000000e+01\r\n2540 2493 -4.2715430000000e+00\r\n2541 2493 -2.2156878000000e+00\r\n1390 2494 -1.1669028000000e-03\r\n1392 2494 -1.2178326000000e-05\r\n2446 2494 -3.5094789000000e-02\r\n2448 2494 -3.6626510000000e-04\r\n2491 2494 -1.0328185000000e-01\r\n2493 2494 -5.9552061000000e-06\r\n2494 2494  1.9898050000000e+02\r\n2496 2494  8.4945259000000e-04\r\n1390 2495  3.7138614000000e-01\r\n1392 2495 -2.5446960000000e+00\r\n2448 2495 -1.1345621000000e+00\r\n2491 2495  7.5228875000000e+00\r\n2493 2495 -1.2409730000000e+00\r\n2494 2495 -1.2216176000000e+02\r\n2495 2495 -3.7800226000000e+01\r\n2496 2495  4.9244403000000e+00\r\n1390 2496  6.2779113000000e-01\r\n1391 2496 -1.0171182000000e-01\r\n1392 2496 -4.3015541000000e+00\r\n2448 2496 -1.9178638000000e+00\r\n2491 2496  1.2716689000000e+01\r\n2492 2496 -2.0602993000000e+00\r\n2493 2496 -2.0977408000000e+00\r\n2494 2496 -2.0650224000000e+02\r\n2495 2496  3.1949098000000e+01\r\n2496 2496  8.3242739000000e+00\r\n2497 2497  1.0000000000000e+00\r\n2498 2498  1.0000000000000e+00\r\n2499 2499  1.0000000000000e+00\r\n2500 2500  1.0000000000000e+00\r\n2501 2501  1.0000000000000e+00\r\n2502 2502  1.0000000000000e+00\r\n2503 2503  1.0000000000000e+00\r\n2504 2504  1.0000000000000e+00\r\n2505 2505  1.0000000000000e+00\r\n2506 2506  1.0000000000000e+00\r\n2507 2507  1.0000000000000e+00\r\n2508 2508  1.0000000000000e+00\r\n2509 2509  1.0000000000000e+00\r\n2510 2510  1.0000000000000e+00\r\n2511 2511  1.0000000000000e+00\r\n1408 2512 -8.9071880000000e-04\r\n1410 2512 -9.2959444000000e-06\r\n2464 2512 -9.0116425000000e-02\r\n2466 2512 -9.4049579000000e-04\r\n2512 2512  2.9264749000000e+02\r\n2514 2512  2.0997959000000e-03\r\n2515 2512 -2.8238988000000e-02\r\n2517 2512 -2.2707097000000e-04\r\n2560 2512 -1.3122752000000e-01\r\n2562 2512 -2.2629472000000e-04\r\n1408 2513  6.1242007000000e-01\r\n1410 2513 -1.7083509000000e+00\r\n2466 2513 -1.6566787000000e+00\r\n2512 2513 -1.8638173000000e+02\r\n2513 2513 -5.0801262000000e+01\r\n2514 2513  6.8260786000000e+00\r\n2515 2513  6.3495161000000e-01\r\n2517 2513 -1.7302944000000e+00\r\n2560 2513  1.7114212000000e+01\r\n2562 2513 -1.7245833000000e+00\r\n1408 2514  1.0352349000000e+00\r\n1409 2514 -1.6566752000000e-01\r\n1410 2514 -2.8877963000000e+00\r\n2466 2514 -2.8004497000000e+00\r\n2512 2514 -3.1505967000000e+02\r\n2513 2514  5.6283224000000e+01\r\n2514 2514  1.1538803000000e+01\r\n2515 2514  1.0733222000000e+00\r\n2516 2514 -1.7176259000000e-01\r\n2517 2514 -2.9248897000000e+00\r\n2560 2514  2.8929865000000e+01\r\n2561 2514 -4.6296150000000e+00\r\n2562 2514 -2.9152356000000e+00\r\n1411 2515 -8.9656706000000e-04\r\n1413 2515 -9.3569795000000e-06\r\n2467 2515 -1.0724558000000e-01\r\n2469 2515 -1.1192633000000e-03\r\n2512 2515 -2.1757486000000e-02\r\n2514 2515 -2.2707097000000e-04\r\n2515 2515  2.9274063000000e+02\r\n2517 2515  2.8729248000000e-03\r\n2518 2515 -4.9798591000000e-02\r\n2520 2515 -4.0579256000000e-04\r\n2563 2515 -1.6202618000000e-01\r\n2565 2515 -4.0438183000000e-04\r\n1411 2516  6.8153890000000e-01\r\n1413 2516 -1.6918757000000e+00\r\n2469 2516 -1.6386315000000e+00\r\n2514 2516 -1.7302944000000e+00\r\n2515 2516 -1.8740171000000e+02\r\n2516 2516 -5.5188260000000e+01\r\n2517 2516  8.4867624000000e+00\r\n2518 2516  1.0712380000000e+00\r\n2520 2516 -1.7127767000000e+00\r\n2563 2516  1.7626293000000e+01\r\n2565 2516 -1.7070344000000e+00\r\n1411 2517  1.1520726000000e+00\r\n1412 2517 -1.8249471000000e-01\r\n1413 2517 -2.8599448000000e+00\r\n2469 2517 -2.7699410000000e+00\r\n2514 2517 -2.9248897000000e+00\r\n2515 2517 -3.1678364000000e+02\r\n2516 2517  4.8630497000000e+01\r\n2517 2517  1.4346016000000e+01\r\n2518 2517  1.8108195000000e+00\r\n2519 2517 -2.8684389000000e-01\r\n2520 2517 -2.8952758000000e+00\r\n2563 2517  2.9795467000000e+01\r\n2564 2517 -4.7197678000000e+00\r\n2565 2517 -2.8855691000000e+00\r\n1414 2518 -6.2840163000000e-02\r\n1416 2518 -5.7770378000000e-04\r\n2470 2518 -1.5780271000000e-01\r\n2472 2518 -1.6469005000000e-03\r\n2515 2518 -3.8882232000000e-02\r\n2517 2518 -4.0579256000000e-04\r\n2518 2518  2.9292368000000e+02\r\n2520 2518  4.5149893000000e-03\r\n2521 2518 -6.4822814000000e-02\r\n2523 2518 -5.8459832000000e-04\r\n2566 2518 -1.9865773000000e-01\r\n2568 2518 -5.8251011000000e-04\r\n1414 2519  7.4086655000000e-01\r\n1416 2519 -1.6753377000000e+00\r\n2472 2519 -1.6067971000000e+00\r\n2517 2519 -1.7127767000000e+00\r\n2518 2519 -1.8834113000000e+02\r\n2519 2519 -5.5000471000000e+01\r\n2520 2519  8.3857228000000e+00\r\n2521 2519  8.6492273000000e-01\r\n2523 2519 -1.6952612000000e+00\r\n2566 2519  1.8710595000000e+01\r\n2568 2519 -1.6894219000000e+00\r\n1414 2520  1.2523608000000e+00\r\n1415 2520 -1.9634685000000e-01\r\n1416 2520 -2.8319909000000e+00\r\n2472 2520 -2.7161298000000e+00\r\n2517 2520 -2.8952758000000e+00\r\n2518 2520 -3.1837184000000e+02\r\n2519 2520  4.8683506000000e+01\r\n2520 2520  1.4175224000000e+01\r\n2521 2520  1.4620654000000e+00\r\n2522 2520 -2.2922462000000e-01\r\n2523 2520 -2.8656695000000e+00\r\n2566 2520  3.1628390000000e+01\r\n2567 2520 -4.9587423000000e+00\r\n2568 2520 -2.8557988000000e+00\r\n1417 2521 -7.1349256000000e-02\r\n1419 2521 -6.6569460000000e-04\r\n2473 2521 -1.9394551000000e-01\r\n2475 2521 -2.0241031000000e-03\r\n2518 2521 -5.6015042000000e-02\r\n2520 2521 -5.8459832000000e-04\r\n2521 2521  2.9302351000000e+02\r\n2523 2521  5.3427201000000e-03\r\n2524 2521 -6.5409750000000e-02\r\n2526 2521 -6.7402542000000e-04\r\n2569 2521 -2.3558105000000e-01\r\n2571 2521 -6.7160093000000e-04\r\n1417 2522  7.4808903000000e-01\r\n1419 2522 -1.6656929000000e+00\r\n2475 2522 -1.5928640000000e+00\r\n2520 2522 -1.6952612000000e+00\r\n2521 2522 -1.8867626000000e+02\r\n2522 2522 -5.4906725000000e+01\r\n2523 2522  8.3270121000000e+00\r\n2524 2522  8.0747099000000e-02\r\n2526 2522 -1.6864639000000e+00\r\n2569 2522  1.9821857000000e+01\r\n2571 2522 -1.6806124000000e+00\r\n1417 2523  1.2645688000000e+00\r\n1418 2523 -1.9723372000000e-01\r\n1419 2523 -2.8156854000000e+00\r\n2475 2523 -2.6925751000000e+00\r\n2520 2523 -2.8656695000000e+00\r\n2521 2523 -3.1893814000000e+02\r\n2522 2523  4.8672218000000e+01\r\n2523 2523  1.4075973000000e+01\r\n2524 2523  1.3649481000000e-01\r\n2525 2523 -2.1288979000000e-02\r\n2526 2523 -2.8507966000000e+00\r\n2569 2523  3.3506847000000e+01\r\n2570 2523 -5.2260336000000e+00\r\n2571 2523 -2.8409053000000e+00\r\n1420 2524 -7.9485143000000e-02\r\n1422 2524 -7.5399642000000e-04\r\n2476 2524 -2.2990739000000e-01\r\n2478 2524 -2.3994175000000e-03\r\n2521 2524 -6.4583768000000e-02\r\n2523 2524 -6.7402542000000e-04\r\n2524 2524  2.9310045000000e+02\r\n2526 2524  5.9898177000000e-03\r\n2527 2524 -6.4560309000000e-02\r\n2529 2524 -6.7378059000000e-04\r\n2572 2524 -2.5945883000000e-01\r\n2574 2524 -7.6068636000000e-04\r\n1420 2525  7.1569311000000e-01\r\n1422 2525 -1.6570018000000e+00\r\n2478 2525 -1.5785190000000e+00\r\n2523 2525 -1.6864639000000e+00\r\n2524 2525 -1.8923331000000e+02\r\n2525 2525 -5.4812579000000e+01\r\n2526 2525  8.2862473000000e+00\r\n2529 2525 -1.6863082000000e+00\r\n2572 2525  2.0490641000000e+01\r\n2574 2525 -1.6718474000000e+00\r\n1420 2526  1.2098076000000e+00\r\n1421 2526 -1.8770999000000e-01\r\n1422 2526 -2.8009959000000e+00\r\n2478 2526 -2.6683286000000e+00\r\n2523 2526 -2.8507966000000e+00\r\n2524 2526 -3.1987998000000e+02\r\n2525 2526  4.8719147000000e+01\r\n2526 2526  1.4007069000000e+01\r\n2529 2526 -2.8505336000000e+00\r\n2572 2526  3.4637380000000e+01\r\n2573 2526 -5.3742280000000e+00\r\n2574 2526 -2.8260909000000e+00\r\n1423 2527 -7.0592166000000e-02\r\n1425 2527 -6.6565245000000e-04\r\n2479 2527 -1.2429711000000e-01\r\n2481 2527 -1.2972209000000e-03\r\n2524 2527 -7.5201414000000e-02\r\n2526 2527 -6.7378059000000e-04\r\n2527 2527  2.9295322000000e+02\r\n2529 2527  4.4363327000000e-03\r\n2530 2527 -3.8860587000000e-02\r\n2532 2527 -4.0556666000000e-04\r\n2575 2527 -2.4243745000000e-01\r\n2577 2527 -6.7142407000000e-04\r\n1423 2528  6.7520554000000e-01\r\n1425 2528 -1.6660338000000e+00\r\n2481 2528 -1.6214392000000e+00\r\n2524 2528  1.0464732000000e+00\r\n2526 2528 -1.6863082000000e+00\r\n2527 2528 -1.9024661000000e+02\r\n2528 2528 -5.4906377000000e+01\r\n2529 2528  8.3725627000000e+00\r\n2532 2528 -1.7120399000000e+00\r\n2575 2528  2.0498619000000e+01\r\n2577 2528 -1.6806242000000e+00\r\n1423 2529  1.1413667000000e+00\r\n1424 2529 -1.7801982000000e-01\r\n1425 2529 -2.8162617000000e+00\r\n2481 2529 -2.7408791000000e+00\r\n2524 2529  1.7689573000000e+00\r\n2525 2529 -2.7590558000000e-01\r\n2526 2529 -2.8505336000000e+00\r\n2527 2529 -3.2159269000000e+02\r\n2528 2529  4.9087749000000e+01\r\n2529 2529  1.4152973000000e+01\r\n2532 2529 -2.8940321000000e+00\r\n2575 2529  3.4650845000000e+01\r\n2576 2529 -5.4045176000000e+00\r\n2577 2529 -2.8409252000000e+00\r\n1426 2530 -8.9363099000000e-04\r\n1428 2530 -9.3263373000000e-06\r\n2482 2530 -9.3052124000000e-02\r\n2484 2530 -9.7113407000000e-04\r\n2527 2530 -5.8123209000000e-02\r\n2529 2530 -4.0556666000000e-04\r\n2530 2530  2.9274599000000e+02\r\n2532 2530  2.5066052000000e-03\r\n2533 2530 -8.6187384000000e-04\r\n2535 2530 -8.9949054000000e-06\r\n2578 2530 -1.9353555000000e-01\r\n2580 2530 -4.0452664000000e-04\r\n1426 2531  5.8169256000000e-01\r\n1428 2531 -1.6919846000000e+00\r\n2484 2531 -1.5999259000000e+00\r\n2527 2531  1.8896683000000e+00\r\n2529 2531 -1.7120399000000e+00\r\n2530 2531 -1.9037896000000e+02\r\n2531 2531 -5.5187799000000e+01\r\n2532 2531  8.3957998000000e+00\r\n2535 2531 -1.6778310000000e+00\r\n2578 2531  1.9884307000000e+01\r\n2580 2531 -1.7078690000000e+00\r\n1426 2532  9.8329310000000e-01\r\n1427 2532 -1.5575948000000e-01\r\n1428 2532 -2.8601308000000e+00\r\n2484 2532 -2.7045147000000e+00\r\n2527 2532  3.1942953000000e+00\r\n2528 2532 -5.0599540000000e-01\r\n2529 2532 -2.8940321000000e+00\r\n2530 2532 -3.2181660000000e+02\r\n2531 2532  4.9428946000000e+01\r\n2532 2532  1.4192258000000e+01\r\n2535 2532 -2.8362030000000e+00\r\n2578 2532  3.3612433000000e+01\r\n2579 2532 -5.3244095000000e+00\r\n2580 2532 -2.8869818000000e+00\r\n1429 2533 -9.5612344000000e-04\r\n1431 2533 -9.9785368000000e-06\r\n2485 2533 -5.3264034000000e-02\r\n2487 2533 -5.5588756000000e-04\r\n2530 2533 -3.8332653000000e-02\r\n2532 2533 -8.9949054000000e-06\r\n2533 2533  2.6921187000000e+02\r\n2535 2533  1.2209128000000e-03\r\n2536 2533 -7.7697458000000e-04\r\n2538 2533 -8.1088582000000e-06\r\n2581 2533 -1.1567965000000e-01\r\n2583 2533 -8.7137452000000e-06\r\n1429 2534  4.6451832000000e-01\r\n1431 2534 -1.8794010000000e+00\r\n2487 2534 -1.5192191000000e+00\r\n2530 2534  2.6251845000000e+00\r\n2532 2534 -1.6778310000000e+00\r\n2533 2534 -1.7564264000000e+02\r\n2534 2534 -5.1156974000000e+01\r\n2535 2534  8.2456741000000e+00\r\n2538 2534 -1.5379209000000e+00\r\n2581 2534  1.7977306000000e+01\r\n2583 2534 -1.6256003000000e+00\r\n1429 2535  7.8522103000000e-01\r\n1430 2535 -1.2721097000000e-01\r\n1431 2535 -3.1769365000000e+00\r\n2487 2535 -2.5680863000000e+00\r\n2530 2535  4.4376080000000e+00\r\n2531 2535 -7.1892165000000e-01\r\n2532 2535 -2.8362030000000e+00\r\n2533 2535 -2.9690607000000e+02\r\n2534 2535  4.6023370000000e+01\r\n2535 2535  1.3938478000000e+01\r\n2538 2535 -2.5997015000000e+00\r\n2581 2535  3.0388813000000e+01\r\n2582 2535 -4.9231871000000e+00\r\n2583 2535 -2.7479122000000e+00\r\n1432 2536 -1.0365274000000e-03\r\n1434 2536 -1.0817669000000e-05\r\n2488 2536 -2.2298997000000e-02\r\n2490 2536 -2.3272242000000e-04\r\n2533 2536 -6.6109854000000e-02\r\n2535 2536 -8.1088582000000e-06\r\n2536 2536  2.4579760000000e+02\r\n2538 2536  8.4135438000000e-04\r\n2539 2536 -6.9746052000000e-04\r\n2541 2536 -7.2790136000000e-06\r\n2584 2536 -9.9112757000000e-02\r\n2586 2536 -7.9227719000000e-06\r\n1432 2537  4.3621853000000e-01\r\n1434 2537 -2.0587232000000e+00\r\n2490 2537 -1.4104398000000e+00\r\n2533 2537  2.9155404000000e+00\r\n2535 2537 -1.5379209000000e+00\r\n2536 2537 -1.6074289000000e+02\r\n2537 2537 -4.6711518000000e+01\r\n2538 2537  7.9127908000000e+00\r\n2541 2537 -1.3976821000000e+00\r\n2584 2537  1.6260700000000e+01\r\n2586 2537 -1.5028176000000e+00\r\n1432 2538  7.3738381000000e-01\r\n1433 2538 -1.1946196000000e-01\r\n1434 2538 -3.4800657000000e+00\r\n2490 2538 -2.3842075000000e+00\r\n2533 2538  4.9284294000000e+00\r\n2534 2538 -7.9844421000000e-01\r\n2535 2538 -2.5997015000000e+00\r\n2536 2538 -2.7171979000000e+02\r\n2537 2538  4.2116819000000e+01\r\n2538 2538  1.3375780000000e+01\r\n2541 2538 -2.3626400000000e+00\r\n2584 2538  2.7487088000000e+01\r\n2585 2538 -4.4531237000000e+00\r\n2586 2538 -2.5403629000000e+00\r\n1435 2539 -1.1364253000000e-03\r\n1437 2539 -1.1860249000000e-05\r\n2491 2539 -6.2924825000000e-04\r\n2493 2539 -6.5671194000000e-06\r\n2536 2539 -5.1374736000000e-02\r\n2538 2539 -7.2790136000000e-06\r\n2539 2539  2.2235750000000e+02\r\n2541 2539  5.5257934000000e-04\r\n2587 2539 -8.9255292000000e-02\r\n2589 2539 -7.0906607000000e-06\r\n1435 2540  4.5215280000000e-01\r\n1437 2540 -2.2754922000000e+00\r\n2493 2540 -1.3107487000000e+00\r\n2536 2540  2.4667704000000e+00\r\n2538 2540 -1.3976821000000e+00\r\n2539 2540 -1.4528699000000e+02\r\n2540 2540 -4.2264729000000e+01\r\n2541 2540  6.3503151000000e+00\r\n2587 2540  1.4681026000000e+01\r\n2589 2540 -1.3616800000000e+00\r\n1435 2541  7.6431855000000e-01\r\n1436 2541 -1.2382645000000e-01\r\n1437 2541 -3.8464892000000e+00\r\n2493 2541 -2.2156878000000e+00\r\n2536 2541  4.1698256000000e+00\r\n2537 2541 -6.7554911000000e-01\r\n2538 2541 -2.3626400000000e+00\r\n2539 2541 -2.4559295000000e+02\r\n2540 2541  3.8061162000000e+01\r\n2541 2541  1.0734565000000e+01\r\n2587 2541  2.4816788000000e+01\r\n2588 2541 -4.0205418000000e+00\r\n2589 2541 -2.3017823000000e+00\r\n2542 2542  1.0000000000000e+00\r\n2543 2543  1.0000000000000e+00\r\n2544 2544  1.0000000000000e+00\r\n2545 2545  1.0000000000000e+00\r\n2546 2546  1.0000000000000e+00\r\n2547 2547  1.0000000000000e+00\r\n2548 2548  1.0000000000000e+00\r\n2549 2549  1.0000000000000e+00\r\n2550 2550  1.0000000000000e+00\r\n2551 2551  1.0000000000000e+00\r\n2552 2552  1.0000000000000e+00\r\n2553 2553  1.0000000000000e+00\r\n2554 2554  1.0000000000000e+00\r\n2555 2555  1.0000000000000e+00\r\n2556 2556  1.0000000000000e+00\r\n2557 2557  1.0000000000000e+00\r\n2558 2558  1.0000000000000e+00\r\n2559 2559  1.0000000000000e+00\r\n1456 2560 -9.2582470000000e-04\r\n1458 2560 -9.6623255000000e-06\r\n2512 2560 -2.1683108000000e-02\r\n2514 2560 -2.2629472000000e-04\r\n2560 2560  2.9249089000000e+02\r\n2562 2560  9.3899797000000e-04\r\n2563 2560 -2.1203776000000e-02\r\n2565 2560 -9.7832424000000e-06\r\n2608 2560 -7.1925308000000e-02\r\n2610 2560 -9.3059444000000e-06\r\n1456 2561  5.3099880000000e-01\r\n1458 2561 -1.7328999000000e+00\r\n2514 2561 -1.7245833000000e+00\r\n2560 2561 -1.8766696000000e+02\r\n2561 2561 -5.1030416000000e+01\r\n2562 2561  6.8826972000000e+00\r\n2563 2561  1.1494059000000e+00\r\n2565 2561 -1.7521309000000e+00\r\n2608 2561  1.7993985000000e+01\r\n2610 2561 -1.6668777000000e+00\r\n1456 2562  8.9760037000000e-01\r\n1457 2562 -1.4541384000000e-01\r\n1458 2562 -2.9292939000000e+00\r\n2514 2562 -2.9152356000000e+00\r\n2560 2562 -3.1723224000000e+02\r\n2561 2562  5.6854685000000e+01\r\n2562 2562  1.1634511000000e+01\r\n2563 2562  1.9429557000000e+00\r\n2564 2562 -3.1476442000000e-01\r\n2565 2562 -2.9618020000000e+00\r\n2608 2562  3.0417032000000e+01\r\n2609 2562 -4.9276468000000e+00\r\n2610 2562 -2.8176901000000e+00\r\n1459 2563 -9.2827855000000e-04\r\n1461 2563 -9.6879349000000e-06\r\n2515 2563 -3.8747058000000e-02\r\n2517 2563 -4.0438183000000e-04\r\n2560 2563 -9.3741072000000e-04\r\n2562 2563 -9.7832424000000e-06\r\n2563 2563  2.9252851000000e+02\r\n2565 2563  1.1272212000000e-03\r\n2566 2563 -3.1497905000000e-02\r\n2568 2563 -9.8369999000000e-06\r\n2611 2563 -8.0804250000000e-02\r\n2613 2563 -9.5760031000000e-06\r\n1459 2564  5.7296891000000e-01\r\n1461 2564 -1.7321883000000e+00\r\n2517 2564 -1.7070344000000e+00\r\n2562 2564 -1.7521309000000e+00\r\n2563 2564 -1.8913401000000e+02\r\n2564 2564 -5.5622843000000e+01\r\n2565 2564  8.6554071000000e+00\r\n2566 2564  2.1606308000000e+00\r\n2568 2564 -1.7520569000000e+00\r\n2611 2564  1.8407184000000e+01\r\n2613 2564 -1.7057913000000e+00\r\n1459 2565  9.6854598000000e-01\r\n1460 2565 -1.5690687000000e-01\r\n1461 2565 -2.9280891000000e+00\r\n2517 2565 -2.8855691000000e+00\r\n2562 2565 -2.9618020000000e+00\r\n2563 2565 -3.1971192000000e+02\r\n2564 2565  4.9493657000000e+01\r\n2565 2565  1.4631092000000e+01\r\n2566 2565  3.6523280000000e+00\r\n2567 2565 -5.9168619000000e-01\r\n2568 2565 -2.9616750000000e+00\r\n2611 2565  3.1115484000000e+01\r\n2612 2565 -5.0407855000000e+00\r\n2613 2565 -2.8834677000000e+00\r\n1462 2566 -9.3303617000000e-04\r\n1464 2566 -9.7375877000000e-06\r\n2518 2566 -5.5814953000000e-02\r\n2520 2566 -5.8251011000000e-04\r\n2563 2566 -9.4256166000000e-04\r\n2565 2566 -9.8369999000000e-06\r\n2566 2566  2.9257763000000e+02\r\n2568 2566  1.3058487000000e-03\r\n2569 2566 -3.8248922000000e-02\r\n2571 2566 -9.9264522000000e-06\r\n2614 2566 -1.0616624000000e-01\r\n2616 2566 -9.8771465000000e-06\r\n1462 2567  6.5284766000000e-01\r\n1464 2567 -1.7316471000000e+00\r\n2520 2567 -1.6894219000000e+00\r\n2565 2567 -1.7520569000000e+00\r\n2566 2567 -1.9102779000000e+02\r\n2567 2567 -5.5622856000000e+01\r\n2568 2567  8.6749437000000e+00\r\n2569 2567  1.9808075000000e+00\r\n2571 2567 -1.7520397000000e+00\r\n2614 2567  2.0401092000000e+01\r\n2616 2567 -1.7435727000000e+00\r\n1462 2568  1.1035737000000e+00\r\n1463 2568 -1.7878067000000e-01\r\n1464 2568 -2.9271763000000e+00\r\n2520 2568 -2.8557988000000e+00\r\n2565 2568 -2.9616750000000e+00\r\n2566 2568 -3.2291338000000e+02\r\n2567 2568  5.0011819000000e+01\r\n2568 2568  1.4664123000000e+01\r\n2569 2568  3.3483570000000e+00\r\n2570 2568 -5.4243911000000e-01\r\n2571 2568 -2.9616479000000e+00\r\n2614 2568  3.4486006000000e+01\r\n2615 2568 -5.5867871000000e+00\r\n2616 2568 -2.9473353000000e+00\r\n1465 2569 -9.3950919000000e-04\r\n1467 2569 -9.8051430000000e-06\r\n2521 2569 -6.4351458000000e-02\r\n2523 2569 -6.7160093000000e-04\r\n2566 2569 -9.5113280000000e-04\r\n2568 2569 -9.9264522000000e-06\r\n2569 2569  2.9257699000000e+02\r\n2571 2569  1.3952789000000e-03\r\n2572 2569 -1.7181466000000e-02\r\n2574 2569 -1.0009662000000e-05\r\n2617 2569 -1.1698968000000e-01\r\n2619 2569 -9.9707864000000e-06\r\n1465 2570  7.5794506000000e-01\r\n1467 2570 -1.7325699000000e+00\r\n2523 2570 -1.6806124000000e+00\r\n2568 2570 -1.7520397000000e+00\r\n2569 2570 -1.9181884000000e+02\r\n2570 2570 -5.5621662000000e+01\r\n2571 2570  8.6690385000000e+00\r\n2572 2570  7.5206056000000e-01\r\n2574 2570 -1.7520824000000e+00\r\n2617 2570  2.2314308000000e+01\r\n2619 2570 -1.7455292000000e+00\r\n1465 2571  1.2812295000000e+00\r\n1466 2571 -2.0756036000000e-01\r\n1467 2571 -2.9287341000000e+00\r\n2523 2571 -2.8409053000000e+00\r\n2568 2571 -2.9616479000000e+00\r\n2569 2571 -3.2425036000000e+02\r\n2570 2571  5.0231084000000e+01\r\n2571 2571  1.4654135000000e+01\r\n2572 2571  1.2712824000000e+00\r\n2573 2571 -2.0594892000000e-01\r\n2574 2571 -2.9617180000000e+00\r\n2617 2571  3.7720082000000e+01\r\n2618 2571 -6.1106878000000e+00\r\n2619 2571 -2.9506406000000e+00\r\n1468 2572 -9.4268585000000e-04\r\n1470 2572 -9.8382960000000e-06\r\n2524 2572 -7.2887446000000e-02\r\n2526 2572 -7.6068636000000e-04\r\n2569 2572 -9.5910582000000e-04\r\n2571 2572 -1.0009662000000e-05\r\n2572 2572  2.9258100000000e+02\r\n2574 2572  1.4845354000000e-03\r\n2575 2572 -9.5913579000000e-04\r\n2577 2572 -1.0009975000000e-05\r\n2620 2572 -1.2784603000000e-01\r\n2622 2572 -1.0021305000000e-05\r\n1468 2573  8.0885568000000e-01\r\n1470 2573 -1.7325536000000e+00\r\n2526 2573 -1.6718474000000e+00\r\n2571 2573 -1.7520824000000e+00\r\n2572 2573 -1.9218464000000e+02\r\n2573 2573 -5.5620927000000e+01\r\n2574 2573  8.6602214000000e+00\r\n2577 2573 -1.7520151000000e+00\r\n2620 2573  2.3380365000000e+01\r\n2622 2573 -1.7455184000000e+00\r\n1468 2574  1.3672896000000e+00\r\n1469 2574 -2.2150141000000e-01\r\n1470 2574 -2.9287086000000e+00\r\n2526 2574 -2.8260909000000e+00\r\n2571 2574 -2.9617180000000e+00\r\n2572 2574 -3.2486892000000e+02\r\n2573 2574  5.0332785000000e+01\r\n2574 2574  1.4639234000000e+01\r\n2577 2574 -2.9616042000000e+00\r\n2620 2574  3.9522169000000e+01\r\n2621 2574 -6.4026056000000e+00\r\n2622 2574 -2.9506243000000e+00\r\n1471 2575 -9.3888991000000e-04\r\n1473 2575 -9.7986799000000e-06\r\n2527 2575 -6.4334512000000e-02\r\n2529 2575 -6.7142407000000e-04\r\n2572 2575 -2.0098704000000e-02\r\n2574 2575 -1.0009975000000e-05\r\n2575 2575  2.9258909000000e+02\r\n2577 2575  1.3950558000000e-03\r\n2578 2575 -9.4692422000000e-04\r\n2580 2575 -9.8825296000000e-06\r\n2623 2575 -1.2599173000000e-01\r\n2625 2575 -9.9743272000000e-06\r\n1471 2576  7.6584105000000e-01\r\n1473 2576 -1.7326971000000e+00\r\n2529 2576 -1.6806242000000e+00\r\n2572 2576  1.0386881000000e+00\r\n2574 2576 -1.7520151000000e+00\r\n2575 2576 -1.9300135000000e+02\r\n2576 2576 -5.5621503000000e+01\r\n2577 2576  8.6692625000000e+00\r\n2580 2576 -1.7516908000000e+00\r\n2623 2576  2.3202076000000e+01\r\n2625 2576 -1.7460305000000e+00\r\n1471 2577  1.2945768000000e+00\r\n1472 2577 -2.0972263000000e-01\r\n1473 2577 -2.9289491000000e+00\r\n2529 2577 -2.8409252000000e+00\r\n2572 2577  1.7557971000000e+00\r\n2573 2577 -2.8444074000000e-01\r\n2574 2577 -2.9616042000000e+00\r\n2575 2577 -3.2624926000000e+02\r\n2576 2577  5.0555316000000e+01\r\n2577 2577  1.4654513000000e+01\r\n2580 2577 -2.9610581000000e+00\r\n2623 2577  3.9220762000000e+01\r\n2624 2577 -6.3537996000000e+00\r\n2625 2577 -2.9514879000000e+00\r\n1474 2578 -9.3142427000000e-04\r\n1476 2578 -9.7207651000000e-06\r\n2530 2578 -3.8760933000000e-02\r\n2532 2578 -4.0452664000000e-04\r\n2575 2578 -4.3707890000000e-02\r\n2577 2578 -9.8825296000000e-06\r\n2578 2578  2.9258464000000e+02\r\n2580 2578  1.1273703000000e-03\r\n2581 2578 -9.0379544000000e-04\r\n2583 2578 -9.4324181000000e-06\r\n2626 2578 -1.2432188000000e-01\r\n2628 2578 -9.8495447000000e-06\r\n1474 2579  6.9052184000000e-01\r\n1476 2579 -1.7321429000000e+00\r\n2532 2579 -1.7078690000000e+00\r\n2575 2579  2.5182774000000e+00\r\n2577 2579 -1.7516908000000e+00\r\n2578 2579 -1.9340288000000e+02\r\n2579 2579 -5.5622434000000e+01\r\n2580 2579  8.6410780000000e+00\r\n2583 2579 -1.6970838000000e+00\r\n2626 2579  2.2200415000000e+01\r\n2628 2579 -1.7460864000000e+00\r\n1474 2580  1.1672581000000e+00\r\n1475 2580 -1.8909809000000e-01\r\n1476 2580 -2.9280144000000e+00\r\n2532 2580 -2.8869818000000e+00\r\n2575 2580  4.2568961000000e+00\r\n2576 2580 -6.8962550000000e-01\r\n2577 2580 -2.9610581000000e+00\r\n2578 2580 -3.2692822000000e+02\r\n2579 2580  5.0663406000000e+01\r\n2580 2580  1.4606876000000e+01\r\n2583 2580 -2.8687486000000e+00\r\n2626 2580  3.7527582000000e+01\r\n2627 2580 -6.0795416000000e+00\r\n2628 2580 -2.9515844000000e+00\r\n1477 2581 -9.8194949000000e-04\r\n1479 2581 -1.0248069000000e-05\r\n2533 2581 -8.3493364000000e-04\r\n2535 2581 -8.7137452000000e-06\r\n2578 2581 -6.9271226000000e-02\r\n2580 2581 -9.4324181000000e-06\r\n2581 2581  2.7502451000000e+02\r\n2583 2581  6.8938559000000e-04\r\n2584 2581 -8.4001290000000e-04\r\n2586 2581 -8.7667547000000e-06\r\n2629 2581 -1.2208159000000e-01\r\n2631 2581 -9.3143151000000e-06\r\n1477 2582  6.6369623000000e-01\r\n1479 2582 -1.8415082000000e+00\r\n2535 2582 -1.6256003000000e+00\r\n2578 2582  3.2064503000000e+00\r\n2580 2582 -1.6970838000000e+00\r\n2581 2582 -1.8185558000000e+02\r\n2582 2582 -5.2287970000000e+01\r\n2583 2582  8.4381586000000e+00\r\n2586 2582 -1.5920711000000e+00\r\n2629 2582  2.0074998000000e+01\r\n2631 2582 -1.6760612000000e+00\r\n1477 2583  1.1219114000000e+00\r\n1478 2583 -1.8175342000000e-01\r\n1479 2583 -3.1128835000000e+00\r\n2535 2583 -2.7479122000000e+00\r\n2578 2583  5.4201800000000e+00\r\n2579 2583 -8.7808747000000e-01\r\n2580 2583 -2.8687486000000e+00\r\n2581 2583 -3.0740847000000e+02\r\n2582 2583  4.7632801000000e+01\r\n2583 2583  1.4263855000000e+01\r\n2586 2583 -2.6912369000000e+00\r\n2629 2583  3.3934755000000e+01\r\n2630 2583 -5.4975455000000e+00\r\n2631 2583 -2.8332120000000e+00\r\n1480 2584 -1.0382557000000e-03\r\n1482 2584 -1.0835706000000e-05\r\n2536 2584 -7.5914416000000e-04\r\n2538 2584 -7.9227719000000e-06\r\n2581 2584 -7.6734055000000e-02\r\n2583 2584 -8.7667547000000e-06\r\n2584 2584  2.5747100000000e+02\r\n2586 2584  6.4606008000000e-04\r\n2587 2584 -7.6858040000000e-04\r\n2589 2584 -8.0212528000000e-06\r\n2632 2584 -1.0700336000000e-01\r\n2634 2584 -8.6474752000000e-06\r\n1480 2585  5.8532222000000e-01\r\n1482 2585 -1.9654957000000e+00\r\n2538 2585 -1.5028176000000e+00\r\n2581 2585  3.3975388000000e+00\r\n2583 2585 -1.5920711000000e+00\r\n2584 2585 -1.6914037000000e+02\r\n2585 2585 -4.8953851000000e+01\r\n2586 2585  8.1046240000000e+00\r\n2589 2585 -1.4681644000000e+00\r\n2632 2585  1.7330914000000e+01\r\n2634 2585 -1.5706120000000e+00\r\n1480 2586  9.8942868000000e-01\r\n1481 2586 -1.6029150000000e-01\r\n1482 2586 -3.3224740000000e+00\r\n2538 2586 -2.5403629000000e+00\r\n2581 2586  5.7431995000000e+00\r\n2582 2586 -9.3042188000000e-01\r\n2583 2586 -2.6912369000000e+00\r\n2584 2586 -2.8591488000000e+02\r\n2585 2586  4.4281127000000e+01\r\n2586 2586  1.3700055000000e+01\r\n2589 2586 -2.4817834000000e+00\r\n2632 2586  2.9296178000000e+01\r\n2633 2586 -4.7461009000000e+00\r\n2634 2586 -2.6549625000000e+00\r\n1483 2587 -1.1349350000000e-03\r\n1485 2587 -1.1844695000000e-05\r\n2539 2587 -6.7941293000000e-04\r\n2541 2587 -7.0906607000000e-06\r\n2584 2587 -5.4570200000000e-02\r\n2586 2587 -8.0212528000000e-06\r\n2587 2587  2.3400232000000e+02\r\n2589 2587  5.8182586000000e-04\r\n2635 2587 -5.2806300000000e-02\r\n2637 2587 -7.7235182000000e-06\r\n1483 2588  5.4602781000000e-01\r\n1485 2588 -2.1660390000000e+00\r\n2541 2588 -1.3616800000000e+00\r\n2584 2588  2.6473125000000e+00\r\n2586 2588 -1.4681644000000e+00\r\n2587 2588 -1.5123902000000e+02\r\n2588 2588 -4.4505464000000e+01\r\n2589 2588  6.4147095000000e+00\r\n2635 2588  1.3660367000000e+01\r\n2637 2588 -1.4138587000000e+00\r\n1483 2589  9.2300475000000e-01\r\n1484 2589 -1.4953127000000e-01\r\n1485 2589 -3.6614697000000e+00\r\n2541 2589 -2.3017823000000e+00\r\n2584 2589  4.4750140000000e+00\r\n2585 2589 -7.2497412000000e-01\r\n2586 2589 -2.4817834000000e+00\r\n2587 2589 -2.5565427000000e+02\r\n2588 2589  3.9559654000000e+01\r\n2589 2589  1.0843417000000e+01\r\n2635 2589  2.3091469000000e+01\r\n2636 2589 -3.7409303000000e+00\r\n2637 2589 -2.3899851000000e+00\r\n2590 2590  1.0000000000000e+00\r\n2591 2591  1.0000000000000e+00\r\n2592 2592  1.0000000000000e+00\r\n2593 2593  1.0000000000000e+00\r\n2594 2594  1.0000000000000e+00\r\n2595 2595  1.0000000000000e+00\r\n2596 2596  1.0000000000000e+00\r\n2597 2597  1.0000000000000e+00\r\n2598 2598  1.0000000000000e+00\r\n2599 2599  1.0000000000000e+00\r\n2600 2600  1.0000000000000e+00\r\n2601 2601  1.0000000000000e+00\r\n2602 2602  1.0000000000000e+00\r\n2603 2603  1.0000000000000e+00\r\n2604 2604  1.0000000000000e+00\r\n1501 2605 -1.1247371000000e-03\r\n1503 2605 -1.1738265000000e-05\r\n2605 2605  2.5726183000000e+02\r\n2607 2605  6.3121360000000e-04\r\n2608 2605 -8.7969584000000e-04\r\n2610 2605 -9.1809038000000e-06\r\n2653 2605 -8.0616683000000e-04\r\n2655 2605 -8.4135217000000e-06\r\n1501 2606  5.3992581000000e-01\r\n1503 2606 -1.9859020000000e+00\r\n2605 2606 -1.5570736000000e+02\r\n2606 2606 -4.8977572000000e+01\r\n2607 2606  4.9631555000000e+00\r\n2610 2606 -1.5762532000000e+00\r\n2653 2606  7.3733402000000e+00\r\n2655 2606 -1.3955268000000e+00\r\n1501 2607  9.1268979000000e-01\r\n1502 2607 -1.4785378000000e-01\r\n1503 2607 -3.3569658000000e+00\r\n2605 2607 -2.6320750000000e+02\r\n2606 2607  4.0543038000000e+01\r\n2607 2607  8.3897130000000e+00\r\n2610 2607 -2.6644983000000e+00\r\n2653 2607  1.2463884000000e+01\r\n2654 2607 -2.0191221000000e+00\r\n2655 2607 -2.3589964000000e+00\r\n1504 2608 -1.0585969000000e-03\r\n1506 2608 -1.1047996000000e-05\r\n2560 2608 -8.9167698000000e-04\r\n2562 2608 -9.3059444000000e-06\r\n2605 2608 -2.5480273000000e-02\r\n2607 2608 -9.1809038000000e-06\r\n2608 2608  2.6901524000000e+02\r\n2610 2608  6.7733017000000e-04\r\n2611 2608 -2.6901940000000e-02\r\n2613 2608 -9.5907170000000e-06\r\n2656 2608 -8.5919741000000e-04\r\n2658 2608 -8.9669729000000e-06\r\n1504 2609  6.2262536000000e-01\r\n1506 2609 -1.8943762000000e+00\r\n2562 2609 -1.6668777000000e+00\r\n2605 2609  5.3520116000000e+00\r\n2607 2609 -1.5762532000000e+00\r\n2608 2609 -1.7513816000000e+02\r\n2609 2609 -5.1196925000000e+01\r\n2610 2609  8.2741795000000e+00\r\n2611 2609  1.0732459000000e+00\r\n2613 2609 -1.6465357000000e+00\r\n2656 2609  1.3568905000000e+01\r\n2658 2609 -1.4844173000000e+00\r\n1504 2610  1.0524859000000e+00\r\n1505 2610 -1.7050168000000e-01\r\n1506 2610 -3.2022536000000e+00\r\n2562 2610 -2.8176901000000e+00\r\n2605 2610  9.0470403000000e+00\r\n2606 2610 -1.4656116000000e+00\r\n2607 2610 -2.6644983000000e+00\r\n2608 2610 -2.9605355000000e+02\r\n2609 2610  4.5785790000000e+01\r\n2610 2610  1.3986673000000e+01\r\n2611 2610  1.8142149000000e+00\r\n2612 2610 -2.9390103000000e-01\r\n2613 2610 -2.7833040000000e+00\r\n2656 2610  2.2936876000000e+01\r\n2657 2610 -3.7157514000000e+00\r\n2658 2610 -2.5092590000000e+00\r\n1507 2611 -1.0163523000000e-03\r\n1509 2611 -1.0607112000000e-05\r\n2563 2611 -9.1755346000000e-04\r\n2565 2611 -9.5760031000000e-06\r\n2608 2611 -9.1896332000000e-04\r\n2610 2611 -9.5907170000000e-06\r\n2611 2611  2.8074737000000e+02\r\n2613 2611  7.0571194000000e-04\r\n2614 2611 -5.4088750000000e-02\r\n2616 2611 -1.0025034000000e-05\r\n2659 2611 -3.5101311000000e-02\r\n2661 2611 -9.3148164000000e-06\r\n1507 2612  7.9655881000000e-01\r\n1509 2612 -1.8126331000000e+00\r\n2565 2612 -1.7057913000000e+00\r\n2610 2612 -1.6465357000000e+00\r\n2611 2612 -1.8345941000000e+02\r\n2612 2612 -5.3421482000000e+01\r\n2613 2612  8.4829556000000e+00\r\n2614 2612  3.6783861000000e+00\r\n2616 2612 -1.7166919000000e+00\r\n2659 2612  1.7742896000000e+01\r\n2661 2612 -1.5953361000000e+00\r\n1507 2613  1.3465020000000e+00\r\n1508 2613 -2.1813184000000e-01\r\n1509 2613 -3.0640727000000e+00\r\n2565 2613 -2.8834677000000e+00\r\n2610 2613 -2.7833040000000e+00\r\n2611 2613 -3.1011955000000e+02\r\n2612 2613  4.7973334000000e+01\r\n2613 2613  1.4339579000000e+01\r\n2614 2613  6.2179390000000e+00\r\n2615 2613 -1.0072993000000e+00\r\n2616 2613 -2.9018937000000e+00\r\n2659 2613  2.9992569000000e+01\r\n2660 2613 -4.8587629000000e+00\r\n2661 2613 -2.6967541000000e+00\r\n1510 2614 -9.8266211000000e-04\r\n1512 2614 -1.0255506000000e-05\r\n2566 2614 -9.4640842000000e-04\r\n2568 2614 -9.8771465000000e-06\r\n2611 2614 -9.6057866000000e-04\r\n2613 2614 -1.0025034000000e-05\r\n2614 2614  2.9249122000000e+02\r\n2616 2614  7.3436965000000e-04\r\n2617 2614 -4.9024073000000e-02\r\n2619 2614 -1.0324474000000e-05\r\n2662 2614 -8.9967129000000e-02\r\n2664 2614 -9.9255482000000e-06\r\n1510 2615  1.0708972000000e+00\r\n1512 2615 -1.7366396000000e+00\r\n2568 2615 -1.7435727000000e+00\r\n2613 2615 -1.7166919000000e+00\r\n2614 2615 -1.9487570000000e+02\r\n2615 2615 -5.5647323000000e+01\r\n2616 2615  8.6406706000000e+00\r\n2617 2615  3.8787961000000e+00\r\n2619 2615 -1.7525021000000e+00\r\n2662 2615  2.1966129000000e+01\r\n2664 2615 -1.6850482000000e+00\r\n1510 2616  1.8102447000000e+00\r\n1511 2616 -2.9325594000000e-01\r\n1512 2616 -2.9356156000000e+00\r\n2568 2616 -2.9473353000000e+00\r\n2613 2616 -2.9018937000000e+00\r\n2614 2616 -3.2941788000000e+02\r\n2615 2616  5.1004900000000e+01\r\n2616 2616  1.4606187000000e+01\r\n2617 2616  6.5567169000000e+00\r\n2618 2616 -1.0621747000000e+00\r\n2619 2616 -2.9624295000000e+00\r\n2662 2616  3.7131544000000e+01\r\n2663 2616 -6.0152344000000e+00\r\n2664 2616 -2.8484055000000e+00\r\n1513 2617 -9.8942330000000e-04\r\n1515 2617 -1.0326069000000e-05\r\n2569 2617 -9.5538081000000e-04\r\n2571 2617 -9.9707864000000e-06\r\n2614 2617 -9.8927044000000e-04\r\n2616 2617 -1.0324474000000e-05\r\n2617 2617  2.9254014000000e+02\r\n2619 2617  7.3535632000000e-04\r\n2620 2617 -2.8113285000000e-02\r\n2622 2617 -1.0418811000000e-05\r\n2665 2617 -1.6098640000000e-01\r\n2667 2617 -1.0349907000000e-05\r\n1513 2618  1.4333144000000e+00\r\n1515 2618 -1.7319037000000e+00\r\n2571 2618 -1.7455292000000e+00\r\n2616 2618 -1.7525021000000e+00\r\n2617 2618 -1.9699295000000e+02\r\n2618 2618 -5.5648296000000e+01\r\n2619 2618  8.7298165000000e+00\r\n2620 2618  1.8224452000000e+00\r\n2622 2618 -1.7525012000000e+00\r\n2665 2618  2.5778745000000e+01\r\n2667 2618 -1.7411638000000e+00\r\n1513 2619  2.4228734000000e+00\r\n1514 2619 -3.9249862000000e-01\r\n1515 2619 -2.9276085000000e+00\r\n2571 2619 -2.9506406000000e+00\r\n2616 2619 -2.9624295000000e+00\r\n2617 2619 -3.3299670000000e+02\r\n2618 2619  5.1582022000000e+01\r\n2619 2619  1.4756875000000e+01\r\n2620 2619  3.0806597000000e+00\r\n2621 2619 -4.9905816000000e-01\r\n2622 2619 -2.9624265000000e+00\r\n2665 2619  4.3576367000000e+01\r\n2666 2619 -7.0592488000000e+00\r\n2667 2619 -2.9432618000000e+00\r\n1516 2620 -9.9413888000000e-04\r\n1518 2620 -1.0375283000000e-05\r\n2572 2620 -9.6022143000000e-04\r\n2574 2620 -1.0021305000000e-05\r\n2617 2620 -9.9830961000000e-04\r\n2619 2620 -1.0418811000000e-05\r\n2620 2620  2.9253173000000e+02\r\n2622 2620  7.3561402000000e-04\r\n2623 2620 -9.9942208000000e-04\r\n2625 2620 -1.0430421000000e-05\r\n2668 2620 -1.7947806000000e-01\r\n2670 2620 -1.0399223000000e-05\r\n1516 2621  1.6531461000000e+00\r\n1518 2621 -1.7318990000000e+00\r\n2574 2621 -1.7455184000000e+00\r\n2619 2621 -1.7525012000000e+00\r\n2620 2621 -1.9721627000000e+02\r\n2621 2621 -5.5648176000000e+01\r\n2622 2621  8.7312260000000e+00\r\n2625 2621 -1.7525027000000e+00\r\n2668 2621  2.7604579000000e+01\r\n2670 2621 -1.7425884000000e+00\r\n1516 2622  2.7944782000000e+00\r\n1517 2622 -4.5269632000000e-01\r\n1518 2622 -2.9276020000000e+00\r\n2574 2622 -2.9506243000000e+00\r\n2619 2622 -2.9624265000000e+00\r\n2620 2622 -3.3337438000000e+02\r\n2621 2622  5.1643267000000e+01\r\n2622 2622  1.4759261000000e+01\r\n2625 2622 -2.9624289000000e+00\r\n2668 2622  4.6662780000000e+01\r\n2669 2622 -7.5592177000000e+00\r\n2670 2622 -2.9456714000000e+00\r\n1519 2623 -9.9061269000000e-04\r\n1521 2623 -1.0338482000000e-05\r\n2575 2623 -9.5572009000000e-04\r\n2577 2623 -9.9743272000000e-06\r\n2620 2623 -2.2031607000000e-02\r\n2622 2623 -1.0430421000000e-05\r\n2623 2623  2.9255261000000e+02\r\n2625 2623  7.3543773000000e-04\r\n2626 2623 -9.9135378000000e-04\r\n2628 2623 -1.0346217000000e-05\r\n2671 2623 -1.7989024000000e-01\r\n2673 2623 -1.0381639000000e-05\r\n1519 2624  1.5206748000000e+00\r\n1521 2624 -1.7309160000000e+00\r\n2577 2624 -1.7460305000000e+00\r\n2620 2624  1.2245586000000e+00\r\n2622 2624 -1.7525027000000e+00\r\n2623 2624 -1.9752059000000e+02\r\n2624 2624 -5.5648621000000e+01\r\n2625 2624  8.7326296000000e+00\r\n2628 2624 -1.7524060000000e+00\r\n2671 2624  2.6817401000000e+01\r\n2673 2624 -1.7445577000000e+00\r\n1519 2625  2.5705472000000e+00\r\n1520 2625 -4.1642114000000e-01\r\n1521 2625 -2.9259386000000e+00\r\n2577 2625 -2.9514879000000e+00\r\n2620 2625  2.0699926000000e+00\r\n2621 2625 -3.3533278000000e-01\r\n2622 2625 -2.9624289000000e+00\r\n2623 2625 -3.3388862000000e+02\r\n2624 2625  5.1725673000000e+01\r\n2625 2625  1.4761630000000e+01\r\n2628 2625 -2.9622671000000e+00\r\n2671 2625  4.5332109000000e+01\r\n2672 2625 -7.3436692000000e+00\r\n2673 2625 -2.9489986000000e+00\r\n1522 2626 -9.8257199000000e-04\r\n1524 2626 -1.0254566000000e-05\r\n2578 2626 -9.4376367000000e-04\r\n2580 2626 -9.8495447000000e-06\r\n2623 2626 -4.5424895000000e-02\r\n2625 2626 -1.0346217000000e-05\r\n2626 2626  2.9254806000000e+02\r\n2628 2626  7.3485204000000e-04\r\n2629 2626 -9.7085662000000e-04\r\n2631 2626 -1.0132299000000e-05\r\n2674 2626 -1.5096113000000e-01\r\n2676 2626 -1.0306636000000e-05\r\n1522 2627  1.2302176000000e+00\r\n1524 2627 -1.7320887000000e+00\r\n2580 2627 -1.7460864000000e+00\r\n2623 2627  3.5248492000000e+00\r\n2625 2627 -1.7524060000000e+00\r\n2626 2627 -1.9753514000000e+02\r\n2627 2627 -5.5647836000000e+01\r\n2628 2627  8.7171013000000e+00\r\n2631 2627 -1.7343623000000e+00\r\n2674 2627  2.4820915000000e+01\r\n2676 2627 -1.7459416000000e+00\r\n1522 2628  2.0795599000000e+00\r\n1523 2628 -3.3688403000000e-01\r\n1524 2628 -2.9279228000000e+00\r\n2580 2628 -2.9515844000000e+00\r\n2623 2628  5.9584050000000e+00\r\n2624 2628 -9.6524821000000e-01\r\n2625 2628 -2.9622671000000e+00\r\n2626 2628 -3.3391340000000e+02\r\n2627 2628  5.1731839000000e+01\r\n2628 2628  1.4735386000000e+01\r\n2631 2628 -2.9317638000000e+00\r\n2674 2628  4.1957275000000e+01\r\n2675 2628 -6.7969844000000e+00\r\n2676 2628 -2.9513397000000e+00\r\n1525 2629 -9.9209166000000e-04\r\n1527 2629 -1.0353917000000e-05\r\n2581 2629 -8.9247904000000e-04\r\n2583 2629 -9.3143151000000e-06\r\n2626 2629 -6.7965128000000e-02\r\n2628 2629 -1.0132299000000e-05\r\n2629 2629  2.8669542000000e+02\r\n2631 2629  7.1975809000000e-04\r\n2632 2629 -9.1858604000000e-04\r\n2634 2629 -9.5867796000000e-06\r\n2677 2629 -1.2299397000000e-01\r\n2679 2629 -1.0093614000000e-05\r\n1525 2630  9.7046859000000e-01\r\n1527 2630 -1.7686457000000e+00\r\n2583 2630 -1.6760612000000e+00\r\n2626 2630  4.5542143000000e+00\r\n2628 2630 -1.7343623000000e+00\r\n2629 2630 -1.9256389000000e+02\r\n2630 2630 -5.4535101000000e+01\r\n2631 2630  8.5750910000000e+00\r\n2634 2630 -1.6619487000000e+00\r\n2677 2630  2.2439305000000e+01\r\n2679 2630 -1.7279811000000e+00\r\n1525 2631  1.6404788000000e+00\r\n1526 2631 -2.6575571000000e-01\r\n1527 2631 -2.9897163000000e+00\r\n2583 2631 -2.8332120000000e+00\r\n2626 2631  7.6984380000000e+00\r\n2627 2631 -1.2471382000000e+00\r\n2628 2631 -2.9317638000000e+00\r\n2629 2631 -3.2550975000000e+02\r\n2630 2631  5.0417700000000e+01\r\n2631 2631  1.4495325000000e+01\r\n2634 2631 -2.8093580000000e+00\r\n2677 2631  3.7931372000000e+01\r\n2678 2631 -6.1448394000000e+00\r\n2679 2631 -2.9209771000000e+00\r\n1528 2632 -1.0451533000000e-03\r\n1530 2632 -1.0907693000000e-05\r\n2584 2632 -8.2858378000000e-04\r\n2586 2632 -8.6474752000000e-06\r\n2629 2632 -8.7940613000000e-02\r\n2631 2632 -9.5867796000000e-06\r\n2632 2632  2.6912665000000e+02\r\n2634 2632  6.7637135000000e-04\r\n2635 2632 -8.2768535000000e-04\r\n2637 2632 -8.6380988000000e-06\r\n2680 2632 -7.6916466000000e-02\r\n2682 2632 -9.3597604000000e-06\r\n1528 2633  7.8546443000000e-01\r\n1530 2633 -1.8879020000000e+00\r\n2586 2633 -1.5706120000000e+00\r\n2629 2633  5.1131268000000e+00\r\n2631 2633 -1.6619487000000e+00\r\n2632 2633 -1.7926113000000e+02\r\n2633 2633 -5.1197932000000e+01\r\n2634 2633  8.2670121000000e+00\r\n2637 2633 -1.5179900000000e+00\r\n2680 2633  1.8842384000000e+01\r\n2682 2633 -1.6228397000000e+00\r\n1528 2634  1.3277491000000e+00\r\n1529 2634 -2.1509523000000e-01\r\n1530 2634 -3.1913095000000e+00\r\n2586 2634 -2.6549625000000e+00\r\n2629 2634  8.6432294000000e+00\r\n2630 2634 -1.4002024000000e+00\r\n2631 2634 -2.8093580000000e+00\r\n2632 2634 -3.0302301000000e+02\r\n2633 2634  4.6912740000000e+01\r\n2634 2634  1.3974555000000e+01\r\n2637 2634 -2.5660085000000e+00\r\n2680 2634  3.1851165000000e+01\r\n2681 2634 -5.1598860000000e+00\r\n2682 2634 -2.7432483000000e+00\r\n1531 2635 -1.1549294000000e-03\r\n1533 2635 -1.2053366000000e-05\r\n2587 2635 -7.4005207000000e-04\r\n2589 2635 -7.7235182000000e-06\r\n2632 2635 -1.0315068000000e-01\r\n2634 2635 -8.6380988000000e-06\r\n2635 2635  2.3984529000000e+02\r\n2637 2635  5.9758328000000e-04\r\n2683 2635 -2.0030928000000e-02\r\n2685 2635 -8.3415062000000e-06\r\n1531 2636  6.8019859000000e-01\r\n1533 2636 -2.1149439000000e+00\r\n2589 2636 -1.4138587000000e+00\r\n2632 2636  4.8202674000000e+00\r\n2634 2636 -1.5179900000000e+00\r\n2635 2636 -1.5366395000000e+02\r\n2636 2636 -4.5637013000000e+01\r\n2637 2636  6.5179537000000e+00\r\n2683 2636  1.0444244000000e+01\r\n2685 2636 -1.4660613000000e+00\r\n1531 2637  1.1498069000000e+00\r\n1532 2637 -1.8627016000000e-01\r\n1533 2637 -3.5750987000000e+00\r\n2589 2637 -2.3899851000000e+00\r\n2632 2637  8.1481742000000e+00\r\n2633 2637 -1.3200144000000e+00\r\n2634 2637 -2.5660085000000e+00\r\n2635 2637 -2.5975337000000e+02\r\n2636 2637  4.0130338000000e+01\r\n2637 2637  1.1017941000000e+01\r\n2683 2637  1.7654939000000e+01\r\n2684 2637 -2.8601219000000e+00\r\n2685 2637 -2.4782283000000e+00\r\n2638 2638  1.0000000000000e+00\r\n2639 2639  1.0000000000000e+00\r\n2640 2640  1.0000000000000e+00\r\n2641 2641  1.0000000000000e+00\r\n2642 2642  1.0000000000000e+00\r\n2643 2643  1.0000000000000e+00\r\n2644 2644  1.0000000000000e+00\r\n2645 2645  1.0000000000000e+00\r\n2646 2646  1.0000000000000e+00\r\n2647 2647  1.0000000000000e+00\r\n2648 2648  1.0000000000000e+00\r\n2649 2649  1.0000000000000e+00\r\n2650 2650  1.0000000000000e+00\r\n2651 2651  1.0000000000000e+00\r\n2652 2652  1.0000000000000e+00\r\n1549 2653 -1.3595278000000e-03\r\n1551 2653 -1.4188647000000e-05\r\n2605 2653 -8.3154072000000e-02\r\n2607 2653 -8.4135217000000e-06\r\n2653 2653  2.1644135000000e+02\r\n2655 2653  5.4412163000000e-04\r\n2656 2653 -4.8657587000000e-02\r\n2658 2653 -8.1200792000000e-06\r\n2701 2653 -6.9781846000000e-04\r\n2703 2653 -7.2827492000000e-06\r\n1549 2654  5.9776879000000e-01\r\n1551 2654 -2.3514563000000e+00\r\n2607 2654 -1.3955268000000e+00\r\n2653 2654 -1.3376399000000e+02\r\n2654 2654 -4.1208238000000e+01\r\n2655 2654  6.2743035000000e+00\r\n2656 2654  6.2226571000000e-01\r\n2658 2654 -1.3470069000000e+00\r\n2701 2654  8.2931739000000e+00\r\n2703 2654 -1.1757010000000e+00\r\n1549 2655  1.0104675000000e+00\r\n1550 2655 -1.6369156000000e-01\r\n1551 2655 -3.9748983000000e+00\r\n2607 2655 -2.3589964000000e+00\r\n2653 2655 -2.2611446000000e+02\r\n2654 2655  3.4812190000000e+01\r\n2655 2655  1.0606074000000e+01\r\n2656 2655  1.0518771000000e+00\r\n2657 2655 -1.7039975000000e-01\r\n2658 2655 -2.2769786000000e+00\r\n2701 2655  1.4018770000000e+01\r\n2702 2655 -2.2709827000000e+00\r\n2703 2655 -1.9874033000000e+00\r\n1552 2656 -1.2638846000000e-03\r\n1554 2656 -1.3190472000000e-05\r\n2608 2656 -1.2520418000000e-02\r\n2610 2656 -8.9669729000000e-06\r\n2653 2656 -7.7804975000000e-04\r\n2655 2656 -8.1200792000000e-06\r\n2656 2656  2.3393384000000e+02\r\n2658 2656  5.9443179000000e-04\r\n2659 2656 -6.7042905000000e-02\r\n2661 2656 -8.8708119000000e-06\r\n2704 2656 -7.7850049000000e-04\r\n2706 2656 -8.1247834000000e-06\r\n1552 2657  7.6965209000000e-01\r\n1554 2657 -2.1810716000000e+00\r\n2610 2657 -1.4844173000000e+00\r\n2655 2657 -1.3470069000000e+00\r\n2656 2657 -1.5086242000000e+02\r\n2657 2657 -4.4544210000000e+01\r\n2658 2657  7.7849314000000e+00\r\n2659 2657  3.8661218000000e+00\r\n2661 2657 -1.4686982000000e+00\r\n2704 2657  1.1894484000000e+01\r\n2706 2657 -1.2987530000000e+00\r\n1552 2658  1.3010199000000e+00\r\n1553 2658 -2.1075945000000e-01\r\n1554 2658 -3.6868835000000e+00\r\n2610 2658 -2.5092590000000e+00\r\n2655 2658 -2.2769786000000e+00\r\n2656 2658 -2.5501783000000e+02\r\n2657 2658  3.9359599000000e+01\r\n2658 2658  1.3159646000000e+01\r\n2659 2658  6.5352923000000e+00\r\n2660 2658 -1.0586883000000e+00\r\n2661 2658 -2.4826874000000e+00\r\n2704 2658  2.0106436000000e+01\r\n2705 2658 -3.2571535000000e+00\r\n2706 2658 -2.1954121000000e+00\r\n1555 2659 -1.1600733000000e-03\r\n1557 2659 -1.2107049000000e-05\r\n2611 2659 -8.9252708000000e-04\r\n2613 2659 -9.3148164000000e-06\r\n2656 2659 -8.4998345000000e-04\r\n2658 2659 -8.8708119000000e-06\r\n2659 2659  2.5737405000000e+02\r\n2661 2659  6.5055223000000e-04\r\n2662 2659 -1.0018150000000e-01\r\n2664 2659 -9.7205287000000e-06\r\n2707 2659 -3.2965212000000e-02\r\n2709 2659 -8.6576764000000e-06\r\n1555 2660  1.1539528000000e+00\r\n1557 2660 -1.9797396000000e+00\r\n2613 2660 -1.5953361000000e+00\r\n2658 2660 -1.4686982000000e+00\r\n2659 2660 -1.7192855000000e+02\r\n2660 2660 -4.8997177000000e+01\r\n2661 2660  8.0606971000000e+00\r\n2662 2660  6.4604988000000e+00\r\n2664 2660 -1.5926681000000e+00\r\n2707 2660  1.6546834000000e+01\r\n2709 2660 -1.4187729000000e+00\r\n1555 2661  1.9506405000000e+00\r\n1556 2661 -3.1599334000000e-01\r\n1557 2661 -3.3465496000000e+00\r\n2613 2661 -2.6967541000000e+00\r\n2658 2661 -2.4826874000000e+00\r\n2659 2661 -2.9062782000000e+02\r\n2660 2661  4.4936312000000e+01\r\n2661 2661  1.3625795000000e+01\r\n2662 2661  1.0920820000000e+01\r\n2663 2661 -1.7691144000000e+00\r\n2664 2661 -2.6922443000000e+00\r\n2707 2661  2.7970749000000e+01\r\n2708 2661 -4.5311117000000e+00\r\n2709 2661 -2.3982922000000e+00\r\n1558 2662 -1.1056630000000e-03\r\n1560 2662 -1.1539199000000e-05\r\n2614 2662 -9.5104618000000e-04\r\n2616 2662 -9.9255482000000e-06\r\n2659 2662 -9.3140161000000e-04\r\n2661 2662 -9.7205287000000e-06\r\n2662 2662  2.7497376000000e+02\r\n2664 2662  6.9434127000000e-04\r\n2665 2662 -1.1386525000000e-01\r\n2667 2662 -1.0527775000000e-05\r\n2710 2662 -7.9156590000000e-02\r\n2712 2662 -9.6995821000000e-06\r\n1558 2663  1.8536711000000e+00\r\n1560 2663 -1.8544138000000e+00\r\n2616 2663 -1.6850482000000e+00\r\n2661 2663 -1.5926681000000e+00\r\n2662 2663 -1.8901619000000e+02\r\n2663 2663 -5.2337002000000e+01\r\n2664 2663  8.4010547000000e+00\r\n2665 2663  6.7628026000000e+00\r\n2667 2663 -1.6981766000000e+00\r\n2710 2663  2.2556493000000e+01\r\n2712 2663 -1.5648924000000e+00\r\n1558 2664  3.1334456000000e+00\r\n1559 2664 -5.0759633000000e-01\r\n1560 2664 -3.1347010000000e+00\r\n2616 2664 -2.8484055000000e+00\r\n2661 2664 -2.6922443000000e+00\r\n2662 2664 -3.1951296000000e+02\r\n2663 2664  4.9470820000000e+01\r\n2664 2664  1.4201141000000e+01\r\n2665 2664  1.1431841000000e+01\r\n2666 2664 -1.8518786000000e+00\r\n2667 2664 -2.8705978000000e+00\r\n2710 2664  3.8129496000000e+01\r\n2711 2664 -6.1767123000000e+00\r\n2712 2664 -2.6452942000000e+00\r\n1561 2665 -1.0573977000000e-03\r\n1563 2665 -1.1035480000000e-05\r\n2617 2665 -9.9170737000000e-04\r\n2619 2665 -1.0349907000000e-05\r\n2662 2665 -1.0087504000000e-03\r\n2664 2665 -1.0527775000000e-05\r\n2665 2665  2.9249969000000e+02\r\n2667 2665  7.3764742000000e-04\r\n2668 2665 -4.6634590000000e-02\r\n2670 2665 -1.1034998000000e-05\r\n2713 2665 -1.3131832000000e-01\r\n2715 2665 -1.0721463000000e-05\r\n1561 2666  2.7340495000000e+00\r\n1563 2666 -1.7427167000000e+00\r\n2619 2666 -1.7411638000000e+00\r\n2664 2666 -1.6981766000000e+00\r\n2665 2666 -2.0339245000000e+02\r\n2666 2666 -5.5675534000000e+01\r\n2667 2666  8.6446883000000e+00\r\n2668 2666  3.6380749000000e+00\r\n2670 2666 -1.7529377000000e+00\r\n2713 2666  2.9099360000000e+01\r\n2715 2666 -1.7034650000000e+00\r\n1561 2667  4.6216337000000e+00\r\n1562 2667 -7.4866592000000e-01\r\n1563 2667 -2.9458861000000e+00\r\n2619 2667 -2.9432618000000e+00\r\n2664 2667 -2.8705978000000e+00\r\n2665 2667 -3.4381433000000e+02\r\n2666 2667  5.3266037000000e+01\r\n2667 2667  1.4612973000000e+01\r\n2668 2667  6.1497971000000e+00\r\n2669 2667 -9.9621561000000e-01\r\n2670 2667 -2.9631636000000e+00\r\n2713 2667  4.9189521000000e+01\r\n2714 2667 -7.9682905000000e+00\r\n2715 2667 -2.8795349000000e+00\r\n1564 2668 -1.0654307000000e-03\r\n1566 2668 -1.1119317000000e-05\r\n2620 2668 -9.9643280000000e-04\r\n2622 2668 -1.0399223000000e-05\r\n2665 2668 -1.0573514000000e-03\r\n2667 2668 -1.1034998000000e-05\r\n2668 2668  2.9250316000000e+02\r\n2670 2668  7.3866338000000e-04\r\n2671 2668 -1.0608347000000e-03\r\n2673 2668 -1.1071350000000e-05\r\n2716 2668 -1.8115654000000e-01\r\n2718 2668 -1.1056198000000e-05\r\n1564 2669  3.4190776000000e+00\r\n1566 2669 -1.7400448000000e+00\r\n2622 2669 -1.7425884000000e+00\r\n2667 2669 -1.7529377000000e+00\r\n2668 2669 -2.0414700000000e+02\r\n2669 2669 -5.5676391000000e+01\r\n2670 2669  8.7377492000000e+00\r\n2673 2669 -1.7528667000000e+00\r\n2716 2669  3.2808237000000e+01\r\n2718 2669 -1.7430828000000e+00\r\n1564 2670  5.7796087000000e+00\r\n1565 2670 -9.3624299000000e-01\r\n1566 2670 -2.9413717000000e+00\r\n2622 2670 -2.9456714000000e+00\r\n2667 2670 -2.9631636000000e+00\r\n2668 2670 -3.4509008000000e+02\r\n2669 2670  5.3470185000000e+01\r\n2670 2670  1.4770287000000e+01\r\n2673 2670 -2.9630436000000e+00\r\n2716 2670  5.5459044000000e+01\r\n2717 2670 -8.9838507000000e+00\r\n2718 2670 -2.9465071000000e+00\r\n1567 2671 -1.0581823000000e-03\r\n1569 2671 -1.1043669000000e-05\r\n2623 2671 -9.9474788000000e-04\r\n2625 2671 -1.0381639000000e-05\r\n2668 2671 -2.1878828000000e-02\r\n2670 2671 -1.1071350000000e-05\r\n2671 2671  2.9251661000000e+02\r\n2673 2671  7.3841610000000e-04\r\n2674 2671 -1.0480451000000e-03\r\n2676 2671 -1.0937873000000e-05\r\n2719 2671 -1.7267209000000e-01\r\n2721 2671 -1.1001340000000e-05\r\n1567 2672  2.9525885000000e+00\r\n1569 2672 -1.7372681000000e+00\r\n2625 2672 -1.7445577000000e+00\r\n2668 2672  2.0469226000000e+00\r\n2670 2672 -1.7528667000000e+00\r\n2671 2672 -2.0320912000000e+02\r\n2672 2672 -5.5675291000000e+01\r\n2673 2672  8.7356720000000e+00\r\n2676 2672 -1.7526655000000e+00\r\n2719 2672  3.0288338000000e+01\r\n2721 2672 -1.7420857000000e+00\r\n1567 2673  4.9910519000000e+00\r\n1568 2673 -8.0850686000000e-01\r\n1569 2673 -2.9366758000000e+00\r\n2625 2673 -2.9489986000000e+00\r\n2668 2673  3.4601153000000e+00\r\n2669 2673 -5.6050850000000e-01\r\n2670 2673 -2.9630436000000e+00\r\n2671 2673 -3.4350445000000e+02\r\n2672 2673  5.3216309000000e+01\r\n2673 2673  1.4766772000000e+01\r\n2676 2673 -2.9627057000000e+00\r\n2719 2673  5.1199370000000e+01\r\n2720 2673 -8.2938510000000e+00\r\n2721 2673 -2.9448195000000e+00\r\n1570 2674 -1.0414984000000e-03\r\n1572 2674 -1.0869548000000e-05\r\n2626 2674 -9.8756126000000e-04\r\n2628 2674 -1.0306636000000e-05\r\n2671 2674 -7.4649095000000e-02\r\n2673 2674 -1.0937873000000e-05\r\n2674 2674  2.9256049000000e+02\r\n2676 2674  7.3773362000000e-04\r\n2677 2674 -1.0322977000000e-03\r\n2679 2674 -1.0773526000000e-05\r\n2722 2674 -1.6278700000000e-01\r\n2724 2674 -1.0872520000000e-05\r\n1570 2675  2.1402522000000e+00\r\n1572 2675 -1.7337240000000e+00\r\n2628 2675 -1.7459416000000e+00\r\n2671 2675  5.5504345000000e+00\r\n2673 2675 -1.7526655000000e+00\r\n2674 2675 -2.0241726000000e+02\r\n2675 2675 -5.5674523000000e+01\r\n2676 2675  8.7329503000000e+00\r\n2679 2675 -1.7519398000000e+00\r\n2722 2675  2.6804110000000e+01\r\n2724 2675 -1.7424514000000e+00\r\n1570 2676  3.6178823000000e+00\r\n1571 2676 -5.8606934000000e-01\r\n1572 2676 -2.9306871000000e+00\r\n2628 2676 -2.9513397000000e+00\r\n2671 2676  9.3824543000000e+00\r\n2672 2676 -1.5198860000000e+00\r\n2673 2676 -2.9627057000000e+00\r\n2674 2676 -3.4216613000000e+02\r\n2675 2676  5.3001769000000e+01\r\n2676 2676  1.4762177000000e+01\r\n2679 2676 -2.9614766000000e+00\r\n2722 2676  4.5309667000000e+01\r\n2723 2676 -7.3398205000000e+00\r\n2724 2676 -2.9454398000000e+00\r\n1573 2677 -1.0256101000000e-03\r\n1575 2677 -1.0703731000000e-05\r\n2629 2677 -9.6714994000000e-04\r\n2631 2677 -1.0093614000000e-05\r\n2674 2677 -9.5453332000000e-02\r\n2676 2677 -1.0773526000000e-05\r\n2677 2677  2.9255970000000e+02\r\n2679 2677  7.3650612000000e-04\r\n2680 2677 -9.8283089000000e-04\r\n2682 2677 -1.0257268000000e-05\r\n2725 2677 -1.4086685000000e-01\r\n2727 2677 -1.0713617000000e-05\r\n1573 2678  1.4879109000000e+00\r\n1575 2678 -1.7348672000000e+00\r\n2631 2678 -1.7279811000000e+00\r\n2674 2678  6.7553990000000e+00\r\n2676 2678 -1.7519398000000e+00\r\n2677 2678 -2.0081608000000e+02\r\n2678 2678 -5.5674209000000e+01\r\n2679 2678  8.6610325000000e+00\r\n2682 2678 -1.6975677000000e+00\r\n2725 2678  2.4649625000000e+01\r\n2727 2678 -1.7424488000000e+00\r\n1573 2679  2.5151624000000e+00\r\n1574 2679 -4.0744107000000e-01\r\n1575 2679 -2.9326171000000e+00\r\n2631 2679 -2.9209771000000e+00\r\n2674 2679  1.1419317000000e+01\r\n2675 2679 -1.8498602000000e+00\r\n2676 2679 -2.9614766000000e+00\r\n2677 2679 -3.3945922000000e+02\r\n2678 2679  5.2564782000000e+01\r\n2679 2679  1.4640600000000e+01\r\n2682 2679 -2.8695684000000e+00\r\n2725 2679  4.1667691000000e+01\r\n2726 2679 -6.7499140000000e+00\r\n2727 2679 -2.9454330000000e+00\r\n1576 2680 -1.0696790000000e-03\r\n1578 2680 -1.1163654000000e-05\r\n2632 2680 -8.9683352000000e-04\r\n2634 2680 -9.3597604000000e-06\r\n2677 2680 -1.3019587000000e-01\r\n2679 2680 -1.0257268000000e-05\r\n2680 2680  2.7507258000000e+02\r\n2682 2680  6.9292462000000e-04\r\n2683 2680 -8.8381229000000e-04\r\n2685 2680 -9.2238649000000e-06\r\n2728 2680 -1.6083653000000e-01\r\n2730 2680 -1.0005744000000e-05\r\n1576 2681  1.1161550000000e+00\r\n1578 2681 -1.8433836000000e+00\r\n2634 2681 -1.6228397000000e+00\r\n2677 2681  7.5559522000000e+00\r\n2679 2681 -1.6975677000000e+00\r\n2680 2681 -1.9145418000000e+02\r\n2681 2681 -5.2336375000000e+01\r\n2682 2681  8.3996613000000e+00\r\n2685 2681 -1.5738155000000e+00\r\n2728 2681  2.4937640000000e+01\r\n2730 2681 -1.6561995000000e+00\r\n1576 2682  1.8867484000000e+00\r\n1577 2682 -3.0564480000000e-01\r\n1578 2682 -3.1160556000000e+00\r\n2634 2682 -2.7432483000000e+00\r\n2677 2682  1.2772581000000e+01\r\n2678 2682 -2.0691010000000e+00\r\n2679 2682 -2.8695684000000e+00\r\n2680 2682 -3.2363415000000e+02\r\n2681 2682  5.0140954000000e+01\r\n2682 2682  1.4198786000000e+01\r\n2685 2682 -2.6603763000000e+00\r\n2728 2682  4.2154587000000e+01\r\n2729 2682 -6.8288545000000e+00\r\n2730 2682 -2.7996396000000e+00\r\n1579 2683 -1.1333827000000e-03\r\n1581 2683 -1.1828495000000e-05\r\n2635 2683 -7.9926644000000e-04\r\n2637 2683 -8.3415062000000e-06\r\n2680 2683 -1.6001362000000e-01\r\n2682 2683 -9.2238649000000e-06\r\n2683 2683  2.5155729000000e+02\r\n2685 2683  6.1757781000000e-04\r\n1579 2684  8.0249788000000e-01\r\n1581 2684 -2.0156766000000e+00\r\n2637 2684 -1.4660613000000e+00\r\n2680 2684  1.2057719000000e+01\r\n2682 2684 -1.5738155000000e+00\r\n2683 2684 -1.5727378000000e+02\r\n2684 2684 -4.7880521000000e+01\r\n2685 2684  5.0609096000000e+00\r\n1579 2685  1.3565417000000e+00\r\n1580 2685 -2.1975770000000e-01\r\n1581 2685 -3.4072979000000e+00\r\n2637 2685 -2.4782283000000e+00\r\n2680 2685  2.0382357000000e+01\r\n2681 2685 -3.3019111000000e+00\r\n2682 2685 -2.6603763000000e+00\r\n2683 2685 -2.6585545000000e+02\r\n2684 2685  4.0980820000000e+01\r\n2685 2685  8.5549565000000e+00\r\n2686 2686  1.0000000000000e+00\r\n2687 2687  1.0000000000000e+00\r\n2688 2688  1.0000000000000e+00\r\n2689 2689  1.0000000000000e+00\r\n2690 2690  1.0000000000000e+00\r\n2691 2691  1.0000000000000e+00\r\n2692 2692  1.0000000000000e+00\r\n2693 2693  1.0000000000000e+00\r\n2694 2694  1.0000000000000e+00\r\n2695 2695  1.0000000000000e+00\r\n2696 2696  1.0000000000000e+00\r\n2697 2697  1.0000000000000e+00\r\n2698 2698  1.0000000000000e+00\r\n2699 2699  1.0000000000000e+00\r\n2700 2700  1.0000000000000e+00\r\n1597 2701 -1.6629540000000e-03\r\n1599 2701 -1.7355340000000e-05\r\n2653 2701 -1.7666840000000e-02\r\n2655 2701 -7.2827492000000e-06\r\n2701 2701  1.8127945000000e+02\r\n2703 2701  4.6222261000000e-04\r\n2704 2701 -4.6208187000000e-02\r\n2706 2701 -7.1392325000000e-06\r\n2749 2701 -6.1374639000000e-04\r\n2751 2701 -6.4053350000000e-06\r\n1597 2702  6.3855364000000e-01\r\n1599 2702 -2.7994161000000e+00\r\n2655 2702 -1.1757010000000e+00\r\n2701 2702 -1.1421835000000e+02\r\n2702 2702 -3.4541974000000e+01\r\n2703 2702  6.1408649000000e+00\r\n2704 2702  2.9579518000000e+00\r\n2706 2702 -1.1526676000000e+00\r\n2749 2702  6.5420961000000e+00\r\n2751 2702 -1.0092086000000e+00\r\n1597 2703  1.0794105000000e+00\r\n1598 2703 -1.7485713000000e-01\r\n1599 2703 -4.7321305000000e+00\r\n2655 2703 -1.9874033000000e+00\r\n2701 2703 -1.9307461000000e+02\r\n2702 2703  2.9714594000000e+01\r\n2703 2703  1.0380512000000e+01\r\n2704 2703  5.0001190000000e+00\r\n2705 2703 -8.0998503000000e-01\r\n2706 2703 -1.9484682000000e+00\r\n2749 2703  1.1058753000000e+01\r\n2750 2703 -1.7914423000000e+00\r\n2751 2703 -1.7059653000000e+00\r\n1600 2704 -1.4890944000000e-03\r\n1602 2704 -1.5540863000000e-05\r\n2656 2704 -1.4379690000000e-02\r\n2658 2704 -8.1247834000000e-06\r\n2701 2704 -6.8406698000000e-04\r\n2703 2704 -7.1392325000000e-06\r\n2704 2704  2.0472575000000e+02\r\n2706 2704  5.2461509000000e-04\r\n2707 2704 -1.0061139000000e-01\r\n2709 2704 -7.9893061000000e-06\r\n2752 2704 -1.2523663000000e-02\r\n2754 2704 -7.0613706000000e-06\r\n1600 2705  9.4957271000000e-01\r\n1602 2705 -2.4812165000000e+00\r\n2658 2705 -1.2987530000000e+00\r\n2703 2705 -1.1526676000000e+00\r\n2704 2705 -1.3443133000000e+02\r\n2705 2705 -3.8998572000000e+01\r\n2706 2705  7.3433625000000e+00\r\n2707 2705  6.5601441000000e+00\r\n2709 2705 -1.2772784000000e+00\r\n2752 2705  9.4117655000000e+00\r\n2754 2705 -1.1290759000000e+00\r\n1600 2706  1.6051577000000e+00\r\n1601 2706 -2.6002288000000e-01\r\n1602 2706 -4.1942484000000e+00\r\n2658 2706 -2.1954121000000e+00\r\n2703 2706 -1.9484682000000e+00\r\n2704 2706 -2.2724272000000e+02\r\n2705 2706  3.5048730000000e+01\r\n2706 2706  1.2413219000000e+01\r\n2707 2706  1.1089268000000e+01\r\n2708 2706 -1.7963738000000e+00\r\n2709 2706 -2.1591114000000e+00\r\n2752 2706  1.5909648000000e+01\r\n2753 2706 -2.5772374000000e+00\r\n2754 2706 -1.9085899000000e+00\r\n1603 2707 -1.4015836000000e-03\r\n1605 2707 -1.4627561000000e-05\r\n2659 2707 -8.2956124000000e-04\r\n2661 2707 -8.6576764000000e-06\r\n2704 2707 -7.6551933000000e-04\r\n2706 2707 -7.9893061000000e-06\r\n2707 2707  2.2230395000000e+02\r\n2709 2707  5.6808927000000e-04\r\n2710 2707 -1.2762543000000e-01\r\n2712 2707 -9.0204335000000e-06\r\n2755 2707 -3.9837085000000e-02\r\n2757 2707 -7.9881879000000e-06\r\n1603 2708  1.8125664000000e+00\r\n1605 2708 -2.2875832000000e+00\r\n2661 2708 -1.4187729000000e+00\r\n2706 2708 -1.2772784000000e+00\r\n2707 2708 -1.5295853000000e+02\r\n2708 2708 -4.2340527000000e+01\r\n2709 2708  7.6553068000000e+00\r\n2710 2708  9.6268453000000e+00\r\n2712 2708 -1.4142972000000e+00\r\n2755 2708  1.3936147000000e+01\r\n2757 2708 -1.2526296000000e+00\r\n1603 2709  3.0639608000000e+00\r\n1604 2709 -4.9633165000000e-01\r\n1605 2709 -3.8669288000000e+00\r\n2661 2709 -2.3982922000000e+00\r\n2706 2709 -2.1591114000000e+00\r\n2707 2709 -2.5856097000000e+02\r\n2708 2709  3.9972265000000e+01\r\n2709 2709  1.2940525000000e+01\r\n2710 2709  1.6273212000000e+01\r\n2711 2709 -2.6361010000000e+00\r\n2712 2709 -2.3907268000000e+00\r\n2755 2709  2.3557652000000e+01\r\n2756 2709 -3.8161090000000e+00\r\n2757 2709 -2.1174440000000e+00\r\n1606 2710 -1.2704236000000e-03\r\n1608 2710 -1.3258716000000e-05\r\n2662 2710 -9.2939455000000e-04\r\n2664 2710 -9.6995821000000e-06\r\n2707 2710 -8.6431990000000e-04\r\n2709 2710 -9.0204335000000e-06\r\n2710 2710  2.5163973000000e+02\r\n2712 2710  6.3979946000000e-04\r\n2713 2710 -1.4877012000000e-01\r\n2715 2710 -1.0399190000000e-05\r\n2758 2710 -1.2819117000000e-01\r\n2760 2710 -9.2072237000000e-06\r\n1606 2711  3.3798375000000e+00\r\n1608 2711 -2.0154729000000e+00\r\n2664 2711 -1.5648924000000e+00\r\n2709 2711 -1.4142972000000e+00\r\n2710 2711 -1.7909886000000e+02\r\n2711 2711 -4.7913181000000e+01\r\n2712 2711  7.9985067000000e+00\r\n2713 2711  1.0574914000000e+01\r\n2715 2711 -1.5902782000000e+00\r\n2758 2711  2.0776367000000e+01\r\n2760 2711 -1.4081953000000e+00\r\n1606 2712  5.7132773000000e+00\r\n1607 2712 -9.2547996000000e-01\r\n1608 2712 -3.4069554000000e+00\r\n2664 2712 -2.6452942000000e+00\r\n2709 2712 -2.3907268000000e+00\r\n2710 2712 -3.0274871000000e+02\r\n2711 2712  4.6873893000000e+01\r\n2712 2712  1.3520675000000e+01\r\n2713 2712  1.7875834000000e+01\r\n2714 2712 -2.8956631000000e+00\r\n2715 2712 -2.6882062000000e+00\r\n2758 2712  3.5120371000000e+01\r\n2759 2712 -5.6890638000000e+00\r\n2760 2712 -2.3804134000000e+00\r\n1609 2713 -5.0642588000000e-03\r\n1611 2713 -1.2127795000000e-05\r\n2665 2713 -1.0273091000000e-03\r\n2667 2713 -1.0721463000000e-05\r\n2710 2713 -9.9642962000000e-04\r\n2712 2713 -1.0399190000000e-05\r\n2713 2713  2.8086435000000e+02\r\n2715 2713  7.1210420000000e-04\r\n2716 2713 -9.1822370000000e-02\r\n2718 2713 -1.1503691000000e-05\r\n2761 2713 -1.7873749000000e-01\r\n2763 2713 -1.0725980000000e-05\r\n1609 2714  5.6128305000000e+00\r\n1611 2714 -1.8107620000000e+00\r\n2667 2714 -1.7034650000000e+00\r\n2712 2714 -1.5902782000000e+00\r\n2713 2714 -2.0370738000000e+02\r\n2714 2714 -5.3485001000000e+01\r\n2715 2714  8.4296870000000e+00\r\n2716 2714  6.5513147000000e+00\r\n2718 2714 -1.7174988000000e+00\r\n2761 2714  3.0389582000000e+01\r\n2763 2714 -1.6016877000000e+00\r\n1609 2715  9.4879220000000e+00\r\n1610 2715 -1.5369025000000e+00\r\n1611 2715 -3.0609100000000e+00\r\n2667 2715 -2.8795349000000e+00\r\n2712 2715 -2.6882062000000e+00\r\n2713 2715 -3.4434672000000e+02\r\n2714 2715  5.3357989000000e+01\r\n2715 2715  1.4249535000000e+01\r\n2716 2715  1.1074335000000e+01\r\n2717 2715 -1.7938779000000e+00\r\n2718 2715 -2.9032579000000e+00\r\n2761 2715  5.1370514000000e+01\r\n2762 2715 -8.3212602000000e+00\r\n2763 2715 -2.7074910000000e+00\r\n1612 2716 -2.4425209000000e-02\r\n1614 2716 -1.1764342000000e-05\r\n2668 2716 -1.0593828000000e-03\r\n2670 2716 -1.1056198000000e-05\r\n2713 2716 -1.1022607000000e-03\r\n2715 2716 -1.1503691000000e-05\r\n2716 2716  2.9260413000000e+02\r\n2718 2716  7.4196018000000e-04\r\n2719 2716 -1.1302282000000e-03\r\n2721 2716 -1.1795573000000e-05\r\n2764 2716 -2.9916952000000e-01\r\n2766 2716 -1.1845982000000e-05\r\n1612 2717  7.5049402000000e+00\r\n1614 2717 -1.7330264000000e+00\r\n2670 2717 -1.7430828000000e+00\r\n2715 2717 -1.7174988000000e+00\r\n2716 2717 -2.1477488000000e+02\r\n2717 2717 -5.5713949000000e+01\r\n2718 2717  8.6985085000000e+00\r\n2721 2717 -1.7533842000000e+00\r\n2764 2717  3.9402394000000e+01\r\n2766 2717 -1.7452709000000e+00\r\n1612 2718  1.2686351000000e+01\r\n1613 2718 -2.0549809000000e+00\r\n1614 2718 -2.9295078000000e+00\r\n2670 2718 -2.9465071000000e+00\r\n2715 2718 -2.9032579000000e+00\r\n2716 2718 -3.6305546000000e+02\r\n2717 2718  5.6285871000000e+01\r\n2718 2718  1.4703956000000e+01\r\n2721 2718 -2.9639196000000e+00\r\n2764 2718  6.6605807000000e+01\r\n2765 2718 -1.0789049000000e+01\r\n2766 2718 -2.9502058000000e+00\r\n1615 2719 -7.5910558000000e-03\r\n1617 2719 -1.1689435000000e-05\r\n2671 2719 -1.0541264000000e-03\r\n2673 2719 -1.1001340000000e-05\r\n2716 2719 -3.0381201000000e-02\r\n2718 2719 -1.1795573000000e-05\r\n2719 2719  2.9251143000000e+02\r\n2721 2719  7.4179220000000e-04\r\n2722 2719 -1.1095801000000e-03\r\n2724 2719 -1.1580080000000e-05\r\n2767 2719 -1.8912806000000e-01\r\n2769 2719 -1.1733822000000e-05\r\n1615 2720  5.8632704000000e+00\r\n1617 2720 -1.7376559000000e+00\r\n2673 2720 -1.7420857000000e+00\r\n2716 2720  4.5648266000000e+00\r\n2718 2720 -1.7533842000000e+00\r\n2719 2720 -2.1023215000000e+02\r\n2720 2720 -5.5709291000000e+01\r\n2721 2720  8.7370563000000e+00\r\n2724 2720 -1.7532047000000e+00\r\n2767 2720  3.1930030000000e+01\r\n2769 2720 -1.7444824000000e+00\r\n1615 2721  9.9112681000000e+00\r\n1616 2721 -1.6054733000000e+00\r\n1617 2721 -2.9373322000000e+00\r\n2673 2721 -2.9448195000000e+00\r\n2716 2721  7.7163801000000e+00\r\n2717 2721 -1.2499351000000e+00\r\n2718 2721 -2.9639196000000e+00\r\n2719 2721 -3.5537629000000e+02\r\n2720 2721  5.5053787000000e+01\r\n2721 2721  1.4769114000000e+01\r\n2724 2721 -2.9636172000000e+00\r\n2767 2721  5.3974502000000e+01\r\n2768 2721 -8.7430406000000e+00\r\n2769 2721 -2.9488718000000e+00\r\n1618 2722 -1.1102163000000e-03\r\n1620 2722 -1.1586719000000e-05\r\n2674 2722 -1.0417831000000e-03\r\n2676 2722 -1.0872520000000e-05\r\n2719 2722 -8.4683273000000e-02\r\n2721 2722 -1.1580080000000e-05\r\n2722 2722  2.9248778000000e+02\r\n2724 2722  7.4090287000000e-04\r\n2725 2722 -1.0889092000000e-03\r\n2727 2722 -1.1364349000000e-05\r\n2770 2722 -1.1103176000000e-01\r\n2772 2722 -1.1514036000000e-05\r\n1618 2723  3.7457762000000e+00\r\n1620 2723 -1.7408475000000e+00\r\n2676 2723 -1.7424514000000e+00\r\n2719 2723  9.0636672000000e+00\r\n2721 2723 -1.7532047000000e+00\r\n2722 2723 -2.0660967000000e+02\r\n2723 2723 -5.5703345000000e+01\r\n2724 2723  8.7388936000000e+00\r\n2727 2723 -1.7526895000000e+00\r\n2770 2723  2.5917748000000e+01\r\n2772 2723 -1.7434598000000e+00\r\n1618 2724  6.3318601000000e+00\r\n1619 2724 -1.0256761000000e+00\r\n1620 2724 -2.9427286000000e+00\r\n2676 2724 -2.9454398000000e+00\r\n2719 2724  1.5321223000000e+01\r\n2720 2724 -2.4818319000000e+00\r\n2721 2724 -2.9636172000000e+00\r\n2722 2724 -3.4925298000000e+02\r\n2723 2724  5.4077195000000e+01\r\n2724 2724  1.4772224000000e+01\r\n2727 2724 -2.9627448000000e+00\r\n2770 2724  4.3811362000000e+01\r\n2771 2724 -7.0968508000000e+00\r\n2772 2724 -2.9471445000000e+00\r\n1621 2725 -1.0870975000000e-03\r\n1623 2725 -1.1345441000000e-05\r\n2677 2725 -1.0265574000000e-03\r\n2679 2725 -1.0713617000000e-05\r\n2722 2725 -1.1755392000000e-01\r\n2724 2725 -1.1364349000000e-05\r\n2725 2725  2.9248715000000e+02\r\n2727 2725  7.3968854000000e-04\r\n2728 2725 -1.0525810000000e-03\r\n2730 2725 -1.0985212000000e-05\r\n2773 2725 -7.5843231000000e-02\r\n2775 2725 -1.1305784000000e-05\r\n1621 2726  2.3393978000000e+00\r\n1623 2726 -1.7413736000000e+00\r\n2679 2726 -1.7424488000000e+00\r\n2722 2726  8.9243960000000e+00\r\n2724 2726 -1.7526895000000e+00\r\n2725 2726 -2.0161014000000e+02\r\n2726 2726 -5.5701882000000e+01\r\n2727 2726  8.7033340000000e+00\r\n2730 2726 -1.7166474000000e+00\r\n2773 2726  2.2461520000000e+01\r\n2775 2726 -1.7439346000000e+00\r\n1621 2727  3.9545158000000e+00\r\n1622 2727 -6.4058624000000e-01\r\n1623 2727 -2.9436164000000e+00\r\n2679 2727 -2.9454330000000e+00\r\n2722 2727  1.5085791000000e+01\r\n2723 2727 -2.4437253000000e+00\r\n2724 2727 -2.9627448000000e+00\r\n2725 2727 -3.4080161000000e+02\r\n2726 2727  5.2712667000000e+01\r\n2727 2727  1.4712108000000e+01\r\n2730 2727 -2.9018208000000e+00\r\n2773 2727  3.7968935000000e+01\r\n2774 2727 -6.1505323000000e+00\r\n2775 2727 -2.9479454000000e+00\r\n1624 2728 -1.1157723000000e-03\r\n1626 2728 -1.1644704000000e-05\r\n2680 2728 -9.5873036000000e-04\r\n2682 2728 -1.0005744000000e-05\r\n2725 2728 -1.0373638000000e-01\r\n2727 2728 -1.0985212000000e-05\r\n2728 2728  2.8076162000000e+02\r\n2730 2728  7.0006857000000e-04\r\n2776 2728 -5.8737235000000e-02\r\n2778 2728 -1.0827533000000e-05\r\n1624 2729  1.7290239000000e+00\r\n1626 2729 -1.8134713000000e+00\r\n2682 2729 -1.6561995000000e+00\r\n2725 2729  6.0763390000000e+00\r\n2727 2729 -1.7166474000000e+00\r\n2728 2729 -1.8895409000000e+02\r\n2729 2729 -5.3475766000000e+01\r\n2730 2729  6.8846034000000e+00\r\n2776 2729  1.9981820000000e+01\r\n2778 2729 -1.6922940000000e+00\r\n1624 2730  2.9227420000000e+00\r\n1625 2730 -4.7345444000000e-01\r\n1626 2730 -3.0654918000000e+00\r\n2682 2730 -2.7996396000000e+00\r\n2725 2730  1.0271443000000e+01\r\n2726 2730 -1.6638692000000e+00\r\n2727 2730 -2.9018208000000e+00\r\n2728 2730 -3.1940800000000e+02\r\n2729 2730  4.9342559000000e+01\r\n2730 2730  1.1637733000000e+01\r\n2776 2730  3.3777269000000e+01\r\n2777 2730 -5.4715737000000e+00\r\n2778 2730 -2.8606537000000e+00\r\n2731 2731  1.0000000000000e+00\r\n2732 2732  1.0000000000000e+00\r\n2733 2733  1.0000000000000e+00\r\n2734 2734  1.0000000000000e+00\r\n2735 2735  1.0000000000000e+00\r\n2736 2736  1.0000000000000e+00\r\n2737 2737  1.0000000000000e+00\r\n2738 2738  1.0000000000000e+00\r\n2739 2739  1.0000000000000e+00\r\n2740 2740  1.0000000000000e+00\r\n2741 2741  1.0000000000000e+00\r\n2742 2742  1.0000000000000e+00\r\n2743 2743  1.0000000000000e+00\r\n2744 2744  1.0000000000000e+00\r\n2745 2745  1.0000000000000e+00\r\n2746 2746  1.0000000000000e+00\r\n2747 2747  1.0000000000000e+00\r\n2748 2748  1.0000000000000e+00\r\n1645 2749 -1.9485883000000e-03\r\n1647 2749 -2.0336349000000e-05\r\n2701 2749 -6.8896215000000e-03\r\n2703 2749 -6.4053350000000e-06\r\n2749 2749  1.5788405000000e+02\r\n2751 2749  4.0803991000000e-04\r\n2752 2749 -5.6619370000000e-02\r\n2754 2749 -6.3257706000000e-06\r\n2797 2749 -5.8544193000000e-04\r\n2799 2749 -5.6495585000000e-06\r\n1645 2750  6.3186954000000e-01\r\n1647 2750 -3.2022787000000e+00\r\n2703 2750 -1.0092086000000e+00\r\n2749 2750 -9.8805163000000e+01\r\n2750 2750 -3.0096993000000e+01\r\n2751 2750  6.1019210000000e+00\r\n2752 2750  4.4049677000000e+00\r\n2754 2750 -9.9678295000000e-01\r\n2797 2750  3.1349304000000e+00\r\n2799 2750 -8.9027329000000e-01\r\n1645 2751  1.0681115000000e+00\r\n1646 2751 -1.7302417000000e-01\r\n1647 2751 -5.4131281000000e+00\r\n2703 2751 -1.7059653000000e+00\r\n2749 2751 -1.6702013000000e+02\r\n2750 2751  2.5665630000000e+01\r\n2751 2751  1.0314680000000e+01\r\n2752 2751  7.4461520000000e+00\r\n2753 2751 -1.2062076000000e+00\r\n2754 2751 -1.6849607000000e+00\r\n2797 2751  5.2992825000000e+00\r\n2798 2751 -8.5843462000000e-01\r\n2799 2751 -1.5049169000000e+00\r\n1648 2752 -1.7858554000000e-03\r\n1650 2752 -1.8637995000000e-05\r\n2704 2752 -6.7660641000000e-04\r\n2706 2752 -7.0613706000000e-06\r\n2749 2752 -6.0612268000000e-04\r\n2751 2752 -6.3257706000000e-06\r\n2752 2752  1.7547880000000e+02\r\n2754 2752  4.5601491000000e-04\r\n2755 2752 -1.1110441000000e-01\r\n2757 2752 -7.2066013000000e-06\r\n2800 2752 -1.2406400000000e-02\r\n2802 2752 -6.4187999000000e-06\r\n1648 2753  1.1698018000000e+00\r\n1650 2753 -2.8848554000000e+00\r\n2706 2753 -1.1290759000000e+00\r\n2751 2753 -9.9678295000000e-01\r\n2752 2753 -1.1634166000000e+02\r\n2753 2753 -3.3442061000000e+01\r\n2754 2753  7.1265019000000e+00\r\n2755 2753  8.8524187000000e+00\r\n2757 2753 -1.1170418000000e+00\r\n2800 2753  5.6171805000000e+00\r\n2802 2753 -9.9499262000000e-01\r\n1648 2754  1.9774329000000e+00\r\n1649 2754 -3.2032228000000e-01\r\n1650 2754 -4.8765596000000e+00\r\n2706 2754 -1.9085899000000e+00\r\n2751 2754 -1.6849607000000e+00\r\n2752 2754 -1.9666394000000e+02\r\n2753 2754  3.0310371000000e+01\r\n2754 2754  1.2046637000000e+01\r\n2755 2754  1.4964129000000e+01\r\n2756 2754 -2.4240235000000e+00\r\n2757 2754 -1.8882474000000e+00\r\n2800 2754  9.4952819000000e+00\r\n2801 2754 -1.5381307000000e+00\r\n2802 2754 -1.6819355000000e+00\r\n1651 2755 -1.6296921000000e-03\r\n1653 2755 -1.7008204000000e-05\r\n2707 2755 -7.6541219000000e-04\r\n2709 2755 -7.9881879000000e-06\r\n2752 2755 -6.9052212000000e-04\r\n2754 2755 -7.2066013000000e-06\r\n2755 2755  1.9894931000000e+02\r\n2757 2755  5.1304880000000e-04\r\n2758 2755 -1.8796678000000e-01\r\n2760 2755 -8.3498387000000e-06\r\n2803 2755 -2.8417687000000e-02\r\n2805 2755 -7.4056227000000e-06\r\n1651 2756  2.6875379000000e+00\r\n1653 2756 -2.5521445000000e+00\r\n2709 2756 -1.2526296000000e+00\r\n2754 2756 -1.1170418000000e+00\r\n2755 2756 -1.3896930000000e+02\r\n2756 2756 -3.7903255000000e+01\r\n2757 2756  7.2995082000000e+00\r\n2758 2756  1.3123630000000e+01\r\n2760 2756 -1.2577767000000e+00\r\n2803 2756  9.0322981000000e+00\r\n2805 2756 -1.1156610000000e+00\r\n1651 2757  4.5430105000000e+00\r\n1652 2757 -7.3590446000000e-01\r\n1653 2757 -4.3141417000000e+00\r\n2709 2757 -2.1174440000000e+00\r\n2754 2757 -1.8882474000000e+00\r\n2755 2757 -2.3491353000000e+02\r\n2756 2757  3.6293837000000e+01\r\n2757 2757  1.2339081000000e+01\r\n2758 2757  2.2184168000000e+01\r\n2759 2757 -3.5935266000000e+00\r\n2760 2757 -2.1261440000000e+00\r\n2803 2757  1.5268185000000e+01\r\n2804 2757 -2.4732336000000e+00\r\n2805 2757 -1.8859120000000e+00\r\n1654 2758 -1.1397067000000e-02\r\n1656 2758 -1.5750990000000e-05\r\n2710 2758 -8.8221776000000e-04\r\n2712 2758 -9.2072237000000e-06\r\n2755 2758 -8.0006484000000e-04\r\n2757 2758 -8.3498387000000e-06\r\n2758 2758  2.2233358000000e+02\r\n2760 2758  5.7188245000000e-04\r\n2761 2758 -1.6313315000000e-01\r\n2763 2758 -9.8498578000000e-06\r\n2806 2758 -4.7986726000000e-02\r\n2808 2758 -8.8984680000000e-06\r\n1654 2759  6.2010410000000e+00\r\n1656 2759 -2.2862821000000e+00\r\n2712 2759 -1.4081953000000e+00\r\n2757 2759 -1.2577767000000e+00\r\n2758 2759 -1.6380015000000e+02\r\n2759 2759 -4.2362572000000e+01\r\n2760 2759  7.6785119000000e+00\r\n2761 2759  1.5538893000000e+01\r\n2763 2759 -1.4297386000000e+00\r\n2806 2759  1.4508479000000e+01\r\n2808 2759 -1.2917639000000e+00\r\n1654 2760  1.0482240000000e+01\r\n1655 2760 -1.6979338000000e+00\r\n1656 2760 -3.8647313000000e+00\r\n2712 2760 -2.3804134000000e+00\r\n2757 2760 -2.1261440000000e+00\r\n2758 2760 -2.7688778000000e+02\r\n2759 2760  4.2884400000000e+01\r\n2760 2760  1.2979755000000e+01\r\n2761 2760  2.6266945000000e+01\r\n2762 2760 -4.2547715000000e+00\r\n2763 2760 -2.4168301000000e+00\r\n2806 2760  2.4525133000000e+01\r\n2807 2760 -3.9726294000000e+00\r\n2808 2760 -2.1835977000000e+00\r\n1657 2761 -6.8801674000000e-02\r\n1659 2761 -1.4097767000000e-05\r\n2713 2761 -1.0277419000000e-03\r\n2715 2761 -1.0725980000000e-05\r\n2758 2761 -9.4379367000000e-04\r\n2760 2761 -9.8498578000000e-06\r\n2761 2761  2.5758060000000e+02\r\n2763 2761  6.5892147000000e-04\r\n2764 2761 -1.8589673000000e-01\r\n2766 2761 -1.1723957000000e-05\r\n2809 2761 -1.5404578000000e-01\r\n2811 2761 -1.0604971000000e-05\r\n1657 2762  1.1863207000000e+01\r\n1659 2762 -1.9732535000000e+00\r\n2715 2762 -1.6016877000000e+00\r\n2760 2762 -1.4297386000000e+00\r\n2761 2762 -1.9628414000000e+02\r\n2762 2762 -4.9059757000000e+01\r\n2763 2762  8.1355860000000e+00\r\n2764 2762  1.2169841000000e+01\r\n2766 2762 -1.6408829000000e+00\r\n2809 2762  2.4571690000000e+01\r\n2811 2762 -1.4845134000000e+00\r\n1657 2763  2.0053552000000e+01\r\n1658 2763 -3.2482342000000e+00\r\n1659 2763 -3.3355854000000e+00\r\n2715 2763 -2.7074910000000e+00\r\n2760 2763 -2.4168301000000e+00\r\n2761 2763 -3.3179848000000e+02\r\n2762 2763  5.1446462000000e+01\r\n2763 2763  1.3752387000000e+01\r\n2764 2763  2.0571884000000e+01\r\n2765 2763 -3.3321924000000e+00\r\n2766 2763 -2.7737464000000e+00\r\n2809 2763  4.1535956000000e+01\r\n2810 2763 -6.7279109000000e+00\r\n2811 2763 -2.5094197000000e+00\r\n1660 2764 -1.1943183000000e-01\r\n1662 2764 -1.2728050000000e-05\r\n2716 2764 -1.1350583000000e-03\r\n2718 2764 -1.1845982000000e-05\r\n2761 2764 -1.1233661000000e-03\r\n2763 2764 -1.1723957000000e-05\r\n2764 2764  2.9273776000000e+02\r\n2766 2764  7.4540679000000e-04\r\n2767 2764 -1.2031711000000e-03\r\n2769 2764 -1.2556838000000e-05\r\n2812 2764 -3.7509276000000e-01\r\n2814 2764 -1.2533584000000e-05\r\n1660 2765  1.6863026000000e+01\r\n1662 2765 -1.7378832000000e+00\r\n2718 2765 -1.7452709000000e+00\r\n2763 2765 -1.6408829000000e+00\r\n2764 2765 -2.3456261000000e+02\r\n2765 2765 -5.5748297000000e+01\r\n2766 2765  8.5957874000000e+00\r\n2769 2765 -1.7538992000000e+00\r\n2812 2765  4.9880579000000e+01\r\n2814 2765 -1.7115905000000e+00\r\n1660 2766  2.8505260000000e+01\r\n1661 2766 -4.6171404000000e+00\r\n1662 2766 -2.9377177000000e+00\r\n2718 2766 -2.9502058000000e+00\r\n2763 2766 -2.7737464000000e+00\r\n2764 2766 -3.9650463000000e+02\r\n2765 2766  6.1616126000000e+01\r\n2766 2766  1.4530315000000e+01\r\n2769 2766 -2.9647895000000e+00\r\n2812 2766  8.4318130000000e+01\r\n2813 2766 -1.3657432000000e+01\r\n2814 2766 -2.8932726000000e+00\r\n1663 2767 -6.0944376000000e-02\r\n1665 2767 -1.2416937000000e-05\r\n2719 2767 -1.1243114000000e-03\r\n2721 2767 -1.1733822000000e-05\r\n2764 2767 -1.4093544000000e-01\r\n2766 2767 -1.2556838000000e-05\r\n2767 2767  2.9261218000000e+02\r\n2769 2767  7.4542913000000e-04\r\n2770 2767 -1.1687854000000e-03\r\n2772 2767 -1.2197973000000e-05\r\n2815 2767 -1.6354702000000e-01\r\n2817 2767 -1.2518373000000e-05\r\n1663 2768  1.1099187000000e+01\r\n1665 2768 -1.7344354000000e+00\r\n2721 2768 -1.7444824000000e+00\r\n2764 2768  1.2060554000000e+01\r\n2766 2768 -1.7538992000000e+00\r\n2767 2768 -2.1790806000000e+02\r\n2768 2768 -5.5744062000000e+01\r\n2769 2768  8.7415519000000e+00\r\n2772 2768 -1.7537264000000e+00\r\n2815 2768  2.6923069000000e+01\r\n2817 2768 -1.7487497000000e+00\r\n1663 2769  1.8762053000000e+01\r\n1664 2769 -3.0390354000000e+00\r\n1665 2769 -2.9318876000000e+00\r\n2721 2769 -2.9488718000000e+00\r\n2764 2769  2.0387148000000e+01\r\n2765 2769 -3.3022646000000e+00\r\n2766 2769 -2.9647895000000e+00\r\n2767 2769 -3.6835155000000e+02\r\n2768 2769  5.7067662000000e+01\r\n2769 2769  1.4776712000000e+01\r\n2772 2769 -2.9644990000000e+00\r\n2815 2769  4.5510728000000e+01\r\n2816 2769 -7.3717256000000e+00\r\n2817 2769 -2.9560846000000e+00\r\n1666 2770 -9.7364176000000e-03\r\n1668 2770 -1.2057755000000e-05\r\n2722 2770 -1.1032519000000e-03\r\n2724 2770 -1.1514036000000e-05\r\n2767 2770 -1.6315817000000e-01\r\n2769 2770 -1.2197973000000e-05\r\n2770 2770  2.9253163000000e+02\r\n2772 2770  7.4382185000000e-04\r\n2773 2770 -1.1401135000000e-03\r\n2775 2770 -1.1898740000000e-05\r\n2818 2770 -1.0412500000000e-01\r\n2820 2770 -1.2162317000000e-05\r\n1666 2771  6.0604122000000e+00\r\n1668 2771 -1.7335935000000e+00\r\n2724 2771 -1.7434598000000e+00\r\n2767 2771  1.5094148000000e+01\r\n2769 2771 -1.7537264000000e+00\r\n2770 2771 -2.0922440000000e+02\r\n2771 2771 -5.5737111000000e+01\r\n2772 2771  8.7390582000000e+00\r\n2775 2771 -1.7532679000000e+00\r\n2818 2771  2.0234483000000e+01\r\n2820 2771 -1.7487549000000e+00\r\n1666 2772  1.0244521000000e+01\r\n1667 2772 -1.6594169000000e+00\r\n1668 2772 -2.9304664000000e+00\r\n2724 2772 -2.9471445000000e+00\r\n2767 2772  2.5515148000000e+01\r\n2768 2772 -4.1329672000000e+00\r\n2769 2772 -2.9644990000000e+00\r\n2770 2772 -3.5367293000000e+02\r\n2771 2772  5.4708381000000e+01\r\n2772 2772  1.4772502000000e+01\r\n2775 2772 -2.9637219000000e+00\r\n2818 2772  3.4204370000000e+01\r\n2819 2772 -5.5404554000000e+00\r\n2820 2772 -2.9560952000000e+00\r\n1669 2773 -1.1345264000000e-03\r\n1671 2773 -1.1840431000000e-05\r\n2725 2773 -1.0832977000000e-03\r\n2727 2773 -1.1305784000000e-05\r\n2770 2773 -1.5298635000000e-01\r\n2772 2773 -1.1898740000000e-05\r\n2773 2773  2.9249952000000e+02\r\n2775 2773  7.4248403000000e-04\r\n2776 2773 -1.1102413000000e-03\r\n2778 2773 -1.1586981000000e-05\r\n2821 2773 -8.7072756000000e-02\r\n2823 2773 -1.1875363000000e-05\r\n1669 2774  3.3681829000000e+00\r\n1671 2774 -1.7329727000000e+00\r\n2727 2774 -1.7439346000000e+00\r\n2770 2774  1.2407653000000e+01\r\n2772 2774 -1.7532679000000e+00\r\n2773 2774 -2.0133903000000e+02\r\n2774 2774 -5.5733785000000e+01\r\n2775 2774  8.7217496000000e+00\r\n2778 2774 -1.7353310000000e+00\r\n2821 2774  1.7722819000000e+01\r\n2823 2774 -1.7499893000000e+00\r\n1669 2775  5.6935723000000e+00\r\n1670 2775 -9.2226603000000e-01\r\n1671 2775 -2.9294150000000e+00\r\n2727 2775 -2.9479454000000e+00\r\n2770 2775  2.0973881000000e+01\r\n2771 2775 -3.3974275000000e+00\r\n2772 2775 -2.9637219000000e+00\r\n2773 2775 -3.4034325000000e+02\r\n2774 2775  5.2558623000000e+01\r\n2775 2775  1.4743237000000e+01\r\n2778 2775 -2.9334035000000e+00\r\n2821 2775  2.9958631000000e+01\r\n2822 2775 -4.8528105000000e+00\r\n2823 2775 -2.9581798000000e+00\r\n1672 2776 -1.1357195000000e-03\r\n1674 2776 -1.1852882000000e-05\r\n2728 2776 -1.0374725000000e-03\r\n2730 2776 -1.0827533000000e-05\r\n2773 2776 -1.2009796000000e-01\r\n2775 2776 -1.1586981000000e-05\r\n2776 2776  2.8658158000000e+02\r\n2778 2776  7.1611912000000e-04\r\n2824 2776 -4.8588756000000e-02\r\n2826 2776 -1.1565613000000e-05\r\n1672 2777  2.2946266000000e+00\r\n1674 2777 -1.7671616000000e+00\r\n2730 2777 -1.6922940000000e+00\r\n2773 2777  8.0019043000000e+00\r\n2775 2777 -1.7353310000000e+00\r\n2776 2777 -1.8742792000000e+02\r\n2777 2777 -5.4619660000000e+01\r\n2778 2777  6.9332076000000e+00\r\n2824 2777  1.2648323000000e+01\r\n2826 2777 -1.7322918000000e+00\r\n1672 2778  3.8788368000000e+00\r\n1673 2778 -6.2831477000000e-01\r\n1674 2778 -2.9872100000000e+00\r\n2730 2778 -2.8606537000000e+00\r\n2773 2778  1.3526419000000e+01\r\n2774 2778 -2.1910817000000e+00\r\n2775 2778 -2.9334035000000e+00\r\n2776 2778 -3.1682815000000e+02\r\n2777 2778  4.8800221000000e+01\r\n2778 2778  1.1719894000000e+01\r\n2824 2778  2.1380725000000e+01\r\n2825 2778 -3.4633644000000e+00\r\n2826 2778 -2.9282661000000e+00\r\n2779 2779  1.0000000000000e+00\r\n2780 2780  1.0000000000000e+00\r\n2781 2781  1.0000000000000e+00\r\n2782 2782  1.0000000000000e+00\r\n2783 2783  1.0000000000000e+00\r\n2784 2784  1.0000000000000e+00\r\n2785 2785  1.0000000000000e+00\r\n2786 2786  1.0000000000000e+00\r\n2787 2787  1.0000000000000e+00\r\n2788 2788  1.0000000000000e+00\r\n2789 2789  1.0000000000000e+00\r\n2790 2790  1.0000000000000e+00\r\n2791 2791  1.0000000000000e+00\r\n2792 2792  1.0000000000000e+00\r\n2793 2793  1.0000000000000e+00\r\n1690 2794 -2.6367206000000e-03\r\n1692 2794 -2.7518009000000e-05\r\n2794 2794  1.1691798000000e+02\r\n2796 2794  3.1040631000000e-04\r\n2797 2794 -1.5879240000000e-02\r\n2799 2794 -4.8749114000000e-06\r\n2842 2794 -4.2567276000000e-04\r\n2844 2794 -4.4425135000000e-06\r\n1690 2795  3.0894644000000e-01\r\n1692 2795 -4.3198103000000e+00\r\n2794 2795 -6.9421330000000e+01\r\n2795 2795 -2.2297074000000e+01\r\n2796 2795  5.7891290000000e+00\r\n2797 2795  1.9807205000000e+00\r\n2799 2795 -7.6539824000000e-01\r\n2844 2795 -7.0141742000000e-01\r\n1690 2796  5.2224306000000e-01\r\n1691 2796 -8.4598286000000e-02\r\n1692 2796 -7.3022073000000e+00\r\n2794 2796 -1.1734982000000e+02\r\n2795 2796  1.7972447000000e+01\r\n2796 2796  9.7859437000000e+00\r\n2797 2796  3.3482100000000e+00\r\n2798 2796 -5.4237739000000e-01\r\n2799 2796 -1.2938292000000e+00\r\n2844 2796 -1.1856760000000e+00\r\n1693 2797 -2.2213481000000e-03\r\n1695 2797 -2.3182994000000e-05\r\n2749 2797 -5.4132940000000e-04\r\n2751 2797 -5.6495585000000e-06\r\n2794 2797 -4.6710426000000e-04\r\n2796 2797 -4.8749114000000e-06\r\n2797 2797  1.4034169000000e+02\r\n2799 2797  3.7264749000000e-04\r\n2800 2797 -6.1160249000000e-02\r\n2802 2797 -5.7321406000000e-06\r\n2845 2797 -4.7157255000000e-04\r\n2847 2797 -4.9215445000000e-06\r\n1693 2798  5.3417080000000e-01\r\n1695 2798 -3.6029813000000e+00\r\n2751 2798 -8.9027329000000e-01\r\n2796 2798 -7.6539824000000e-01\r\n2797 2798 -8.7160026000000e+01\r\n2798 2798 -2.6758321000000e+01\r\n2799 2798  6.9178904000000e+00\r\n2800 2798  5.8331968000000e+00\r\n2802 2798 -8.9151591000000e-01\r\n2845 2798  2.3724452000000e-01\r\n2847 2798 -7.6471706000000e-01\r\n1693 2799  9.0296180000000e-01\r\n1694 2799 -1.4627021000000e-01\r\n1695 2799 -6.0904761000000e+00\r\n2751 2799 -1.5049169000000e+00\r\n2796 2799 -1.2938292000000e+00\r\n2797 2799 -1.4733522000000e+02\r\n2798 2799  2.2617766000000e+01\r\n2799 2799  1.1693996000000e+01\r\n2800 2799  9.8604302000000e+00\r\n2801 2799 -1.5972850000000e+00\r\n2802 2799 -1.5070176000000e+00\r\n2845 2799  4.0103791000000e-01\r\n2846 2799 -6.4963886000000e-02\r\n2847 2799 -1.2926770000000e+00\r\n1696 2800 -2.0249245000000e-03\r\n1698 2800 -2.1133029000000e-05\r\n2752 2800 -6.1503657000000e-04\r\n2754 2800 -6.4187999000000e-06\r\n2797 2800 -5.4924225000000e-04\r\n2799 2800 -5.7321406000000e-06\r\n2800 2800  1.5792382000000e+02\r\n2802 2800  4.1507500000000e-04\r\n2803 2800 -1.1209667000000e-01\r\n2805 2800 -6.5647585000000e-06\r\n2848 2800 -5.6517062000000e-04\r\n2850 2800 -5.8983763000000e-06\r\n1696 2801  1.2295079000000e+00\r\n1698 2801 -3.2050468000000e+00\r\n2754 2801 -9.9499262000000e-01\r\n2799 2801 -8.9151591000000e-01\r\n2800 2801 -1.0373876000000e+02\r\n2801 2801 -3.0106230000000e+01\r\n2802 2801  6.9820971000000e+00\r\n2803 2801  1.0342836000000e+01\r\n2805 2801 -9.9693289000000e-01\r\n2848 2801  1.5461141000000e+00\r\n2850 2801 -8.9022740000000e-01\r\n1696 2802  2.0783602000000e+00\r\n1697 2802 -3.3666692000000e-01\r\n1698 2802 -5.4178110000000e+00\r\n2754 2802 -1.6819355000000e+00\r\n2799 2802 -1.5070176000000e+00\r\n2800 2802 -1.7536000000000e+02\r\n2801 2802  2.6993128000000e+01\r\n2802 2802  1.1802536000000e+01\r\n2803 2802  1.7483529000000e+01\r\n2804 2802 -2.8321010000000e+00\r\n2805 2802 -1.6852153000000e+00\r\n2848 2802  2.6135512000000e+00\r\n2849 2802 -4.2336080000000e-01\r\n2850 2802 -1.5048404000000e+00\r\n1699 2803 -1.8954089000000e-03\r\n1701 2803 -1.9781345000000e-05\r\n2755 2803 -7.0959196000000e-04\r\n2757 2803 -7.4056227000000e-06\r\n2800 2803 -6.2902203000000e-04\r\n2802 2803 -6.5647585000000e-06\r\n2803 2803  1.7552542000000e+02\r\n2805 2803  4.5895273000000e-04\r\n2806 2803 -1.8490299000000e-01\r\n2808 2803 -7.8425031000000e-06\r\n2851 2803 -6.6915747000000e-04\r\n2853 2803 -6.9836301000000e-06\r\n1699 2804  3.4299646000000e+00\r\n1701 2804 -2.8841868000000e+00\r\n2757 2804 -1.1156610000000e+00\r\n2802 2804 -9.9693289000000e-01\r\n2803 2804 -1.2191790000000e+02\r\n2804 2804 -3.3456331000000e+01\r\n2805 2804  7.1631975000000e+00\r\n2806 2804  1.5575259000000e+01\r\n2808 2804 -1.1479232000000e+00\r\n2851 2804  2.2306585000000e+00\r\n2853 2804 -1.0147341000000e+00\r\n1699 2805  5.7980083000000e+00\r\n1700 2805 -9.3917852000000e-01\r\n1701 2805 -4.8754260000000e+00\r\n2757 2805 -1.8859120000000e+00\r\n2802 2805 -1.6852153000000e+00\r\n2803 2805 -2.0608989000000e+02\r\n2804 2805  3.1800895000000e+01\r\n2805 2805  1.2108662000000e+01\r\n2806 2805  2.6328400000000e+01\r\n2807 2805 -4.2647520000000e+00\r\n2808 2805 -1.9404481000000e+00\r\n2851 2805  3.7707026000000e+00\r\n2852 2805 -6.1078954000000e-01\r\n2853 2805 -1.7153054000000e+00\r\n1702 2806 -3.7829768000000e-02\r\n1704 2806 -1.7202053000000e-05\r\n2758 2806 -8.5263341000000e-04\r\n2760 2806 -8.8984680000000e-06\r\n2803 2806 -7.5145296000000e-04\r\n2805 2806 -7.8425031000000e-06\r\n2806 2806  2.1068091000000e+02\r\n2808 2806  5.4456009000000e-04\r\n2809 2806 -2.4297827000000e-01\r\n2811 2806 -9.6193652000000e-06\r\n2854 2806 -8.1726223000000e-04\r\n2856 2806 -8.5293184000000e-06\r\n1702 2807  8.7724127000000e+00\r\n1704 2807 -2.4047730000000e+00\r\n2760 2807 -1.2917639000000e+00\r\n2805 2807 -1.1479232000000e+00\r\n2806 2807 -1.5312802000000e+02\r\n2807 2807 -4.0153071000000e+01\r\n2808 2807  7.3802059000000e+00\r\n2809 2807  2.1768511000000e+01\r\n2811 2807 -1.3447723000000e+00\r\n2854 2807  1.7769103000000e+00\r\n2856 2807 -1.1864595000000e+00\r\n1702 2808  1.4828886000000e+01\r\n1703 2808 -2.4019494000000e+00\r\n1704 2808 -4.0650283000000e+00\r\n2760 2808 -2.1835977000000e+00\r\n2805 2808 -1.9404481000000e+00\r\n2806 2808 -2.5884760000000e+02\r\n2807 2808  4.0015170000000e+01\r\n2808 2808  1.2475499000000e+01\r\n2809 2808  3.6797491000000e+01\r\n2810 2808 -5.9603741000000e+00\r\n2811 2808 -2.2732032000000e+00\r\n2854 2808  3.0036892000000e+00\r\n2855 2808 -4.8653076000000e-01\r\n2856 2808 -2.0055911000000e+00\r\n1705 2809 -1.5567512000000e-01\r\n1707 2809 -1.5921633000000e-05\r\n2761 2809 -1.0161471000000e-03\r\n2763 2809 -1.0604971000000e-05\r\n2806 2809 -9.2170833000000e-04\r\n2808 2809 -9.6193652000000e-06\r\n2809 2809  2.4012212000000e+02\r\n2811 2809  6.1893949000000e-04\r\n2812 2809 -3.5472890000000e-01\r\n2814 2809 -1.1694541000000e-05\r\n2857 2809 -9.7819414000000e-04\r\n2859 2809 -1.0208877000000e-05\r\n1705 2810  2.0388768000000e+01\r\n1707 2810 -2.1123227000000e+00\r\n2763 2810 -1.4845134000000e+00\r\n2808 2810 -1.3447723000000e+00\r\n2809 2810 -1.8900300000000e+02\r\n2810 2810 -4.5739429000000e+01\r\n2811 2810  7.8605356000000e+00\r\n2812 2810  3.1038869000000e+01\r\n2814 2810 -1.5515063000000e+00\r\n2859 2810 -1.3622756000000e+00\r\n1705 2811  3.4465149000000e+01\r\n1706 2811 -5.5823791000000e+00\r\n1707 2811 -3.5706677000000e+00\r\n2763 2811 -2.5094197000000e+00\r\n2808 2811 -2.2732032000000e+00\r\n2809 2811 -3.1949044000000e+02\r\n2810 2811  4.9546697000000e+01\r\n2811 2811  1.3287442000000e+01\r\n2812 2811  5.2468065000000e+01\r\n2813 2811 -8.4983418000000e+00\r\n2814 2811 -2.6226644000000e+00\r\n2859 2811 -2.3027894000000e+00\r\n1708 2812 -2.9914070000000e-01\r\n1710 2812 -1.4448644000000e-05\r\n2764 2812 -1.2009430000000e-03\r\n2766 2812 -1.2533584000000e-05\r\n2809 2812 -1.1205475000000e-03\r\n2811 2812 -1.1694541000000e-05\r\n2812 2812  2.8189826000000e+02\r\n2814 2812  7.2416564000000e-04\r\n2815 2812 -1.2390640000000e-03\r\n2817 2812 -1.2931432000000e-05\r\n2860 2812 -1.1974085000000e-03\r\n2862 2812 -1.2496697000000e-05\r\n1708 2813  3.4530089000000e+01\r\n1710 2813 -1.8034786000000e+00\r\n2766 2813 -1.7115905000000e+00\r\n2811 2813 -1.5515063000000e+00\r\n2812 2813 -3.0295866000000e+02\r\n2813 2813 -5.3561180000000e+01\r\n2814 2813  8.8391322000000e+00\r\n2817 2813 -1.7187497000000e+00\r\n2862 2813 -1.6266867000000e+00\r\n1708 2814  5.8369661000000e+01\r\n1709 2814 -9.4537851000000e+00\r\n1710 2814 -3.0486002000000e+00\r\n2766 2814 -2.8932726000000e+00\r\n2811 2814 -2.6226644000000e+00\r\n2812 2814 -5.1212130000000e+02\r\n2813 2814  8.0335994000000e+01\r\n2814 2814  1.4941665000000e+01\r\n2817 2814 -2.9053725000000e+00\r\n2862 2814 -2.7497511000000e+00\r\n1711 2815 -1.2091038000000e-01\r\n1713 2815 -1.3024193000000e-05\r\n2767 2815 -1.1994854000000e-03\r\n2769 2815 -1.2518373000000e-05\r\n2812 2815 -3.5400654000000e-01\r\n2814 2815 -1.2931432000000e-05\r\n2815 2815  2.9269180000000e+02\r\n2817 2815  7.4833530000000e-04\r\n2818 2815 -1.2151085000000e-03\r\n2820 2815 -1.2681422000000e-05\r\n2863 2815 -1.2612720000000e-03\r\n2865 2815 -1.3163206000000e-05\r\n1711 2816  1.6989522000000e+01\r\n1713 2816 -1.7310373000000e+00\r\n2769 2816 -1.7487497000000e+00\r\n2812 2816  3.5445146000000e+01\r\n2814 2816 -1.7187497000000e+00\r\n2815 2816 -2.2021925000000e+02\r\n2816 2816 -5.5772693000000e+01\r\n2817 2816  8.7103667000000e+00\r\n2820 2816 -1.7542574000000e+00\r\n2865 2816 -1.7513011000000e+00\r\n1711 2817  2.8719068000000e+01\r\n1712 2817 -4.6516829000000e+00\r\n1713 2817 -2.9261433000000e+00\r\n2769 2817 -2.9560846000000e+00\r\n2812 2817  5.9916433000000e+01\r\n2813 2817 -9.7047802000000e+00\r\n2814 2817 -2.9053725000000e+00\r\n2815 2817 -3.7225837000000e+02\r\n2816 2817  5.7627715000000e+01\r\n2817 2817  1.4723995000000e+01\r\n2820 2817 -2.9653966000000e+00\r\n2865 2817 -2.9603970000000e+00\r\n1714 2818 -2.9539221000000e-02\r\n1716 2818 -1.2519425000000e-05\r\n2770 2818 -1.1653689000000e-03\r\n2772 2818 -1.2162317000000e-05\r\n2815 2818 -2.2278842000000e-01\r\n2817 2818 -1.2681422000000e-05\r\n2818 2818  2.9248278000000e+02\r\n2820 2818  7.4634292000000e-04\r\n2821 2818 -1.1808282000000e-03\r\n2823 2818 -1.2323657000000e-05\r\n2866 2818 -1.7655237000000e-03\r\n2868 2818 -1.2658465000000e-05\r\n1714 2819  8.0014028000000e+00\r\n1716 2819 -1.7318408000000e+00\r\n2772 2819 -1.7487549000000e+00\r\n2815 2819  2.1807030000000e+01\r\n2817 2819 -1.7542574000000e+00\r\n2818 2819 -2.0609693000000e+02\r\n2819 2819 -5.5761113000000e+01\r\n2820 2819  8.7461764000000e+00\r\n2823 2819 -1.7539435000000e+00\r\n2866 2819  8.4869924000000e+00\r\n2868 2819 -1.7511135000000e+00\r\n1714 2820  1.3525571000000e+01\r\n1715 2820 -2.1908251000000e+00\r\n1716 2820 -2.9275037000000e+00\r\n2772 2820 -2.9560952000000e+00\r\n2815 2820  3.6862603000000e+01\r\n2816 2820 -5.9708767000000e+00\r\n2817 2820 -2.9653966000000e+00\r\n2818 2820 -3.4838625000000e+02\r\n2819 2820  5.3791450000000e+01\r\n2820 2820  1.4784534000000e+01\r\n2823 2820 -2.9648641000000e+00\r\n2866 2820  1.4346412000000e+01\r\n2867 2820 -2.3237821000000e+00\r\n2868 2820 -2.9600823000000e+00\r\n1717 2821 -1.1745151000000e-03\r\n1719 2821 -1.2257771000000e-05\r\n2773 2821 -1.1378735000000e-03\r\n2775 2821 -1.1875363000000e-05\r\n2818 2821 -1.7018751000000e-01\r\n2820 2821 -1.2323657000000e-05\r\n2821 2821  2.9248926000000e+02\r\n2823 2821  7.4475699000000e-04\r\n2824 2821 -1.1509821000000e-03\r\n2826 2821 -1.2012170000000e-05\r\n2869 2821 -8.2800114000000e-02\r\n2871 2821 -1.2305913000000e-05\r\n1717 2822  4.1569139000000e+00\r\n1719 2822 -1.7304186000000e+00\r\n2775 2822 -1.7499893000000e+00\r\n2818 2822  1.4942885000000e+01\r\n2820 2822 -1.7539435000000e+00\r\n2821 2822 -2.0168972000000e+02\r\n2822 2822 -5.5755356000000e+01\r\n2823 2822  8.7459120000000e+00\r\n2826 2822 -1.7537806000000e+00\r\n2869 2822  1.4779875000000e+01\r\n2871 2822 -1.7515163000000e+00\r\n1717 2823  7.0268425000000e+00\r\n1718 2823 -1.1382070000000e+00\r\n1719 2823 -2.9250977000000e+00\r\n2775 2823 -2.9581798000000e+00\r\n2818 2823  2.5259436000000e+01\r\n2819 2823 -4.0915200000000e+00\r\n2820 2823 -2.9648641000000e+00\r\n2821 2823 -3.4093608000000e+02\r\n2822 2823  5.2600284000000e+01\r\n2823 2823  1.4784082000000e+01\r\n2826 2823 -2.9645908000000e+00\r\n2869 2823  2.4983885000000e+01\r\n2870 2823 -4.0468861000000e+00\r\n2871 2823 -2.9607612000000e+00\r\n1720 2824 -1.1424362000000e-03\r\n1722 2824 -1.1922981000000e-05\r\n2776 2824 -1.1081939000000e-03\r\n2778 2824 -1.1565613000000e-05\r\n2821 2824 -1.5942759000000e-01\r\n2823 2824 -1.2012170000000e-05\r\n2824 2824  2.9239877000000e+02\r\n2826 2824  7.1946840000000e-04\r\n1720 2825  2.6606893000000e+00\r\n1722 2825 -1.7316662000000e+00\r\n2778 2825 -1.7322918000000e+00\r\n2821 2825  1.3042016000000e+01\r\n2823 2825 -1.7537806000000e+00\r\n2824 2825 -1.8351822000000e+02\r\n2825 2825 -5.5751694000000e+01\r\n2826 2825  5.2240006000000e+00\r\n1720 2826  4.4976292000000e+00\r\n1721 2826 -7.2853764000000e-01\r\n1722 2826 -2.9272085000000e+00\r\n2778 2826 -2.9282661000000e+00\r\n2821 2826  2.2046224000000e+01\r\n2822 2826 -3.5711044000000e+00\r\n2823 2826 -2.9645908000000e+00\r\n2824 2826 -3.1021919000000e+02\r\n2825 2826  4.7634733000000e+01\r\n2826 2826  8.8306505000000e+00\r\n2827 2827  1.0000000000000e+00\r\n2828 2828  1.0000000000000e+00\r\n2829 2829  1.0000000000000e+00\r\n2830 2830  1.0000000000000e+00\r\n2831 2831  1.0000000000000e+00\r\n2832 2832  1.0000000000000e+00\r\n2833 2833  1.0000000000000e+00\r\n2834 2834  1.0000000000000e+00\r\n2835 2835  1.0000000000000e+00\r\n2836 2836  1.0000000000000e+00\r\n2837 2837  1.0000000000000e+00\r\n2838 2838  1.0000000000000e+00\r\n2839 2839  1.0000000000000e+00\r\n2840 2840  1.0000000000000e+00\r\n2841 2841  1.0000000000000e+00\r\n1738 2842 -2.6228869000000e-03\r\n1740 2842 -2.7373634000000e-05\r\n2794 2842 -2.4738193000000e-02\r\n2796 2842 -4.4425135000000e-06\r\n2842 2842  1.1694008000000e+02\r\n2844 2842  3.1419533000000e-04\r\n2845 2842 -1.4510170000000e-02\r\n2847 2842 -4.4423605000000e-06\r\n2890 2842 -4.1857439000000e-04\r\n2892 2842 -4.3684318000000e-06\r\n1738 2843  2.6728897000000e-01\r\n1740 2843 -4.3215522000000e+00\r\n2794 2843  1.0415918000000e+00\r\n2796 2843 -7.0141742000000e-01\r\n2842 2843 -7.1513262000000e+01\r\n2843 2843 -2.2298278000000e+01\r\n2844 2843  6.4284232000000e+00\r\n2845 2843  3.0743413000000e+00\r\n2847 2843 -7.0143927000000e-01\r\n2892 2843 -7.0151062000000e-01\r\n1738 2844  4.5182528000000e-01\r\n1739 2844 -7.3191547000000e-02\r\n1740 2844 -7.3051519000000e+00\r\n2794 2844  1.7607067000000e+00\r\n2795 2844 -2.8521833000000e-01\r\n2796 2844 -1.1856760000000e+00\r\n2842 2844 -1.2088602000000e+02\r\n2843 2844  1.8542426000000e+01\r\n2844 2844  1.0866607000000e+01\r\n2845 2844  5.1968665000000e+00\r\n2846 2844 -8.4184466000000e-01\r\n2847 2844 -1.1857129000000e+00\r\n2892 2844 -1.1858335000000e+00\r\n1741 2845 -2.6659355000000e-03\r\n1743 2845 -2.7822909000000e-05\r\n2797 2845 -2.7018673000000e-02\r\n2799 2845 -4.9215445000000e-06\r\n2842 2845 -4.2565810000000e-04\r\n2844 2845 -4.4423605000000e-06\r\n2845 2845  1.1698186000000e+02\r\n2847 2845  3.2014905000000e-04\r\n2848 2845 -5.7738694000000e-02\r\n2850 2845 -4.9258151000000e-06\r\n2893 2845 -4.2805601000000e-04\r\n2895 2845 -4.4673862000000e-06\r\n1741 2846  4.3056606000000e-01\r\n1743 2846 -4.3212757000000e+00\r\n2799 2846 -7.6471706000000e-01\r\n2844 2846 -7.0143927000000e-01\r\n2845 2846 -7.3655198000000e+01\r\n2846 2846 -2.2302114000000e+01\r\n2847 2846  7.2568081000000e+00\r\n2848 2846  6.0999914000000e+00\r\n2850 2846 -7.6545108000000e-01\r\n2895 2846 -7.0141963000000e-01\r\n1741 2847  7.2782837000000e-01\r\n1742 2847 -1.1790039000000e-01\r\n1743 2847 -7.3046794000000e+00\r\n2799 2847 -1.2926770000000e+00\r\n2844 2847 -1.1857129000000e+00\r\n2845 2847 -1.2450666000000e+02\r\n2846 2847  1.9119340000000e+01\r\n2847 2847  1.2266901000000e+01\r\n2848 2847  1.0311418000000e+01\r\n2849 2847 -1.6703392000000e+00\r\n2850 2847 -1.2939176000000e+00\r\n2895 2847 -1.1856792000000e+00\r\n1744 2848 -2.2890448000000e-03\r\n1746 2848 -2.3889507000000e-05\r\n2800 2848 -2.5381719000000e-02\r\n2802 2848 -5.8983763000000e-06\r\n2845 2848 -4.7198175000000e-04\r\n2847 2848 -4.9258151000000e-06\r\n2848 2848  1.4040886000000e+02\r\n2850 2848  3.7403923000000e-04\r\n2851 2848 -1.1256435000000e-01\r\n2853 2848 -6.0074212000000e-06\r\n2896 2848 -4.8193290000000e-04\r\n2898 2848 -5.0296698000000e-06\r\n1744 2849  9.5493991000000e-01\r\n1746 2849 -3.6027696000000e+00\r\n2802 2849 -8.9022740000000e-01\r\n2847 2849 -7.6545108000000e-01\r\n2848 2849 -9.1323808000000e+01\r\n2849 2849 -2.6766776000000e+01\r\n2850 2849  6.9332679000000e+00\r\n2851 2849  9.8254101000000e+00\r\n2853 2849 -9.0677263000000e-01\r\n2898 2849 -7.6503890000000e-01\r\n1744 2850  1.6142304000000e+00\r\n1745 2850 -2.6148297000000e-01\r\n1746 2850 -6.0901217000000e+00\r\n2802 2850 -1.5048404000000e+00\r\n2847 2850 -1.2939176000000e+00\r\n2848 2850 -1.5437376000000e+02\r\n2849 2850  2.3736591000000e+01\r\n2850 2850  1.1719995000000e+01\r\n2851 2850  1.6608873000000e+01\r\n2852 2850 -2.6904074000000e+00\r\n2853 2850 -1.5328084000000e+00\r\n2898 2850 -1.2932218000000e+00\r\n1747 2851 -2.0436630000000e-03\r\n1749 2851 -2.1328591000000e-05\r\n2803 2851 -1.7076097000000e-02\r\n2805 2851 -6.9836301000000e-06\r\n2848 2851 -5.7561908000000e-04\r\n2850 2851 -6.0074212000000e-06\r\n2851 2851  1.6381310000000e+02\r\n2853 2851  4.3085910000000e-04\r\n2854 2851 -1.5171947000000e-01\r\n2856 2851 -7.2108945000000e-06\r\n2899 2851 -6.0504245000000e-04\r\n2901 2851 -6.3144968000000e-06\r\n1747 2852  2.5176735000000e+00\r\n1749 2852 -3.0900922000000e+00\r\n2805 2852 -1.0147341000000e+00\r\n2850 2852 -9.0677263000000e-01\r\n2851 2852 -1.0996184000000e+02\r\n2852 2852 -3.1231894000000e+01\r\n2853 2852  6.9879250000000e+00\r\n2854 2852  1.3482684000000e+01\r\n2856 2852 -1.0478604000000e+00\r\n2901 2852 -9.2495411000000e-01\r\n1747 2853  4.2558728000000e+00\r\n1748 2853 -6.8937538000000e-01\r\n1749 2853 -5.2234888000000e+00\r\n2805 2853 -1.7153054000000e+00\r\n2850 2853 -1.5328084000000e+00\r\n2851 2853 -1.8587939000000e+02\r\n2852 2853  2.8617763000000e+01\r\n2853 2853  1.1812382000000e+01\r\n2854 2853  2.2791115000000e+01\r\n2855 2853 -3.6917533000000e+00\r\n2856 2853 -1.7713021000000e+00\r\n2901 2853 -1.5635414000000e+00\r\n1750 2854 -1.4069406000000e-02\r\n1752 2854 -1.9443328000000e-05\r\n2806 2854 -3.9305704000000e-02\r\n2808 2854 -8.5293184000000e-06\r\n2851 2854 -6.9093349000000e-04\r\n2853 2854 -7.2108945000000e-06\r\n2854 2854  1.8724325000000e+02\r\n2856 2854  4.8926994000000e-04\r\n2857 2854 -1.7655716000000e-01\r\n2859 2854 -8.6535764000000e-06\r\n2902 2854 -7.3661529000000e-04\r\n2904 2854 -7.6876504000000e-06\r\n1750 2855  6.4125036000000e+00\r\n1752 2855 -2.7048907000000e+00\r\n2808 2855 -1.1864595000000e+00\r\n2853 2855 -1.0478604000000e+00\r\n2854 2855 -1.2924567000000e+02\r\n2855 2855 -3.5699346000000e+01\r\n2856 2855  7.2317654000000e+00\r\n2857 2855  1.5457157000000e+01\r\n2859 2855 -1.2038711000000e+00\r\n2904 2855 -1.0846679000000e+00\r\n1750 2856  1.0839696000000e+01\r\n1751 2856 -1.7557832000000e+00\r\n1752 2856 -4.5723473000000e+00\r\n2808 2856 -2.0055911000000e+00\r\n2853 2856 -1.7713021000000e+00\r\n2854 2856 -2.1847689000000e+02\r\n2855 2856  3.3669408000000e+01\r\n2856 2856  1.2224575000000e+01\r\n2857 2856  2.6128778000000e+01\r\n2858 2856 -4.2322654000000e+00\r\n2859 2856 -2.0350237000000e+00\r\n2904 2856 -1.8335227000000e+00\r\n1753 2857 -8.5146637000000e-02\r\n1755 2857 -1.7534446000000e-05\r\n2809 2857 -9.1496839000000e-02\r\n2811 2857 -1.0208877000000e-05\r\n2854 2857 -8.2916838000000e-04\r\n2856 2857 -8.6535764000000e-06\r\n2857 2857  2.1655768000000e+02\r\n2859 2857  5.6258459000000e-04\r\n2860 2857 -1.5399105000000e-01\r\n2862 2857 -1.0675720000000e-05\r\n2905 2857 -8.9608978000000e-04\r\n2907 2857 -9.3519983000000e-06\r\n1753 2858  1.3430198000000e+01\r\n1755 2858 -2.3400367000000e+00\r\n2809 2858  2.5196135000000e+00\r\n2811 2858 -1.3622756000000e+00\r\n2856 2858 -1.2038711000000e+00\r\n2857 2858 -1.5139205000000e+02\r\n2858 2858 -4.1283654000000e+01\r\n2859 2858  7.6138360000000e+00\r\n2860 2858  1.1298069000000e+01\r\n2862 2858 -1.4246489000000e+00\r\n2907 2858 -1.2783576000000e+00\r\n1753 2859  2.2702394000000e+01\r\n1754 2859 -3.6771606000000e+00\r\n1755 2859 -3.9555957000000e+00\r\n2809 2859  4.2591523000000e+00\r\n2810 2859 -6.8986500000000e-01\r\n2811 2859 -2.3027894000000e+00\r\n2856 2859 -2.0350237000000e+00\r\n2857 2859 -2.5591297000000e+02\r\n2858 2859  3.9447704000000e+01\r\n2859 2859  1.2870422000000e+01\r\n2860 2859  1.9098244000000e+01\r\n2861 2859 -3.0933880000000e+00\r\n2862 2859 -2.4082250000000e+00\r\n2907 2859 -2.1609341000000e+00\r\n1756 2860 -1.3871496000000e-01\r\n1758 2860 -1.4779451000000e-05\r\n2812 2860 -3.0534456000000e-01\r\n2814 2860 -1.2496697000000e-05\r\n2857 2860 -1.0229261000000e-03\r\n2859 2860 -1.0675720000000e-05\r\n2860 2860  2.6342252000000e+02\r\n2862 2860  6.7765910000000e-04\r\n2863 2860 -1.1970207000000e-03\r\n2865 2860 -1.2492650000000e-05\r\n2908 2860 -1.1113436000000e-03\r\n2910 2860 -1.1598485000000e-05\r\n1756 2861  1.8730508000000e+01\r\n1758 2861 -1.9239522000000e+00\r\n2812 2861  2.2650621000000e+01\r\n2814 2861 -1.6266867000000e+00\r\n2859 2861 -1.4246489000000e+00\r\n2860 2861 -1.9236509000000e+02\r\n2861 2861 -5.0211097000000e+01\r\n2862 2861  8.2011099000000e+00\r\n2865 2861 -1.6622378000000e+00\r\n2910 2861 -1.5579331000000e+00\r\n1756 2862  3.1662050000000e+01\r\n1757 2862 -5.1282795000000e+00\r\n1758 2862 -3.2522488000000e+00\r\n2812 2862  3.8288610000000e+01\r\n2813 2862 -6.2015787000000e+00\r\n2814 2862 -2.7497511000000e+00\r\n2859 2862 -2.4082250000000e+00\r\n2860 2862 -3.2517394000000e+02\r\n2861 2862  5.0228609000000e+01\r\n2862 2862  1.3863152000000e+01\r\n2865 2862 -2.8098445000000e+00\r\n2910 2862 -2.6335301000000e+00\r\n1759 2863 -6.1195760000000e-02\r\n1761 2863 -1.3005170000000e-05\r\n2815 2863 -8.4129370000000e-02\r\n2817 2863 -1.3163206000000e-05\r\n2860 2863 -1.1019069000000e-01\r\n2862 2863 -1.2492650000000e-05\r\n2863 2863  2.9246116000000e+02\r\n2865 2863  7.4854041000000e-04\r\n2866 2863 -1.2344464000000e-03\r\n2868 2863 -1.2883241000000e-05\r\n2911 2863 -1.2445215000000e-03\r\n2913 2863 -1.2988390000000e-05\r\n1759 2864  1.1111017000000e+01\r\n1761 2864 -1.7304764000000e+00\r\n2815 2864  5.6564743000000e-01\r\n2817 2864 -1.7513011000000e+00\r\n2860 2864  1.1669962000000e+01\r\n2862 2864 -1.6622378000000e+00\r\n2863 2864 -1.9111799000000e+02\r\n2864 2864 -5.5782280000000e+01\r\n2865 2864  8.6562392000000e+00\r\n2868 2864 -1.7545128000000e+00\r\n2913 2864 -1.7514355000000e+00\r\n1759 2865  1.8782047000000e+01\r\n1760 2865 -3.0421668000000e+00\r\n1761 2865 -2.9251949000000e+00\r\n2815 2865  9.5616964000000e-01\r\n2816 2865 -1.5487277000000e-01\r\n2817 2865 -2.9603970000000e+00\r\n2860 2865  1.9726888000000e+01\r\n2861 2865 -3.1952047000000e+00\r\n2862 2865 -2.8098445000000e+00\r\n2863 2865 -3.2306559000000e+02\r\n2864 2865  4.9636495000000e+01\r\n2865 2865  1.4632498000000e+01\r\n2868 2865 -2.9658283000000e+00\r\n2913 2865 -2.9606246000000e+00\r\n1762 2866 -1.3869516000000e-02\r\n1764 2866 -1.2700715000000e-05\r\n2818 2866 -1.2129088000000e-03\r\n2820 2866 -1.2658465000000e-05\r\n2863 2866 -1.3924076000000e-01\r\n2865 2866 -1.2883241000000e-05\r\n2866 2866  2.9236641000000e+02\r\n2868 2866  7.4779983000000e-04\r\n2869 2866 -1.2146362000000e-03\r\n2871 2866 -1.2676493000000e-05\r\n2914 2866 -1.2346491000000e-03\r\n2916 2866 -1.2885356000000e-05\r\n1762 2867  6.4520954000000e+00\r\n1764 2867 -1.7296952000000e+00\r\n2820 2867 -1.7511135000000e+00\r\n2863 2867  1.2739216000000e+01\r\n2865 2867 -1.7545128000000e+00\r\n2866 2867 -1.8808195000000e+02\r\n2867 2867 -5.5776604000000e+01\r\n2868 2867  8.7473522000000e+00\r\n2871 2867 -1.7544652000000e+00\r\n2914 2867  1.1109602000000e+00\r\n2916 2867 -1.7512923000000e+00\r\n1762 2868  1.0906622000000e+01\r\n1763 2868 -1.7665969000000e+00\r\n1764 2868 -2.9238767000000e+00\r\n2820 2868 -2.9600823000000e+00\r\n2863 2868  2.1534371000000e+01\r\n2864 2868 -3.4880233000000e+00\r\n2865 2868 -2.9658283000000e+00\r\n2866 2868 -3.1793373000000e+02\r\n2867 2868  4.8820171000000e+01\r\n2868 2868  1.4786522000000e+01\r\n2871 2868 -2.9657462000000e+00\r\n2914 2868  1.8779672000000e+00\r\n2915 2868 -3.0418317000000e-01\r\n2916 2868 -2.9603845000000e+00\r\n1765 2869 -1.2076586000000e-03\r\n1767 2869 -1.2603672000000e-05\r\n2821 2869 -1.1791280000000e-03\r\n2823 2869 -1.2305913000000e-05\r\n2866 2869 -8.9047699000000e-02\r\n2868 2869 -1.2676493000000e-05\r\n2869 2869  2.9230729000000e+02\r\n2871 2869  7.3435172000000e-04\r\n2917 2869 -1.2243854000000e-03\r\n2919 2869 -1.2778240000000e-05\r\n1765 2870  4.1746113000000e+00\r\n1767 2870 -1.7302744000000e+00\r\n2823 2870 -1.7515163000000e+00\r\n2866 2870  8.6450985000000e+00\r\n2868 2870 -1.7544652000000e+00\r\n2869 2870 -1.8572204000000e+02\r\n2870 2870 -5.5771995000000e+01\r\n2871 2870  6.9942460000000e+00\r\n2917 2870  5.1159495000000e+00\r\n2919 2870 -1.7517190000000e+00\r\n1765 2871  7.0567586000000e+00\r\n1766 2871 -1.1430303000000e+00\r\n1767 2871 -2.9248541000000e+00\r\n2823 2871 -2.9607612000000e+00\r\n2866 2871  1.4613665000000e+01\r\n2867 2871 -2.3670729000000e+00\r\n2868 2871 -2.9657462000000e+00\r\n2869 2871 -3.1394434000000e+02\r\n2870 2871  4.8186100000000e+01\r\n2871 2871  1.1823066000000e+01\r\n2917 2871  8.6479957000000e+00\r\n2918 2871 -1.4007736000000e+00\r\n2919 2871 -2.9611039000000e+00\r\n2872 2872  1.0000000000000e+00\r\n2873 2873  1.0000000000000e+00\r\n2874 2874  1.0000000000000e+00\r\n2875 2875  1.0000000000000e+00\r\n2876 2876  1.0000000000000e+00\r\n2877 2877  1.0000000000000e+00\r\n2878 2878  1.0000000000000e+00\r\n2879 2879  1.0000000000000e+00\r\n2880 2880  1.0000000000000e+00\r\n2881 2881  1.0000000000000e+00\r\n2882 2882  1.0000000000000e+00\r\n2883 2883  1.0000000000000e+00\r\n2884 2884  1.0000000000000e+00\r\n2885 2885  1.0000000000000e+00\r\n2886 2886  1.0000000000000e+00\r\n1783 2887 -2.4123184000000e-03\r\n1785 2887 -2.5176046000000e-05\r\n2887 2887  1.2276367000000e+02\r\n2889 2887  3.2155676000000e-04\r\n2890 2887 -1.2450511000000e-02\r\n2892 2887 -4.3893722000000e-06\r\n2935 2887 -4.5507138000000e-04\r\n2937 2887 -4.7493308000000e-06\r\n1783 2888  2.3967335000000e-01\r\n1785 2888 -4.1163478000000e+00\r\n2887 2888 -7.4141000000000e+01\r\n2888 2888 -2.3407988000000e+01\r\n2889 2888  5.6225115000000e+00\r\n2890 2888  3.4073757000000e+00\r\n2892 2888 -7.1792217000000e-01\r\n2937 2888 -7.8561509000000e-01\r\n1783 2889  4.0514354000000e-01\r\n1784 2889 -6.5630999000000e-02\r\n1785 2889 -6.9582695000000e+00\r\n2887 2889 -1.2532787000000e+02\r\n2888 2889  1.9223281000000e+01\r\n2889 2889  9.5042871000000e+00\r\n2890 2889  5.7598242000000e+00\r\n2891 2889 -9.3305935000000e-01\r\n2892 2889 -1.2135748000000e+00\r\n2937 2889 -1.3280030000000e+00\r\n1786 2890 -2.5802613000000e-03\r\n1788 2890 -2.6928775000000e-05\r\n2842 2890 -4.2487643000000e-02\r\n2844 2890 -4.3684318000000e-06\r\n2887 2890 -4.2058086000000e-04\r\n2889 2890 -4.3893722000000e-06\r\n2890 2890  1.1696348000000e+02\r\n2892 2890  3.1802070000000e-04\r\n2893 2890 -1.9335764000000e-02\r\n2895 2890 -4.3661119000000e-06\r\n2938 2890 -4.2194337000000e-04\r\n2940 2890 -4.4035919000000e-06\r\n1786 2891  2.4644381000000e-01\r\n1788 2891 -4.3239533000000e+00\r\n2842 2891  3.1262924000000e+00\r\n2844 2891 -7.0151062000000e-01\r\n2889 2891 -7.1792217000000e-01\r\n2890 2891 -7.4727793000000e+01\r\n2891 2891 -2.2297929000000e+01\r\n2892 2891  7.1655433000000e+00\r\n2893 2891  4.2244279000000e+00\r\n2895 2891 -7.0118328000000e-01\r\n2940 2891 -7.1847045000000e-01\r\n1786 2892  4.1658861000000e-01\r\n1787 2892 -6.7484236000000e-02\r\n1788 2892 -7.3092107000000e+00\r\n2842 2892  5.2846847000000e+00\r\n2843 2892 -8.5607937000000e-01\r\n2844 2892 -1.1858335000000e+00\r\n2889 2892 -1.2135748000000e+00\r\n2890 2892 -1.2631986000000e+02\r\n2891 2892  1.9423783000000e+01\r\n2892 2892  1.2112634000000e+01\r\n2893 2892  7.1409730000000e+00\r\n2894 2892 -1.1567842000000e+00\r\n2895 2892 -1.1852802000000e+00\r\n2940 2892 -1.2145024000000e+00\r\n1789 2893 -2.6372306000000e-03\r\n1791 2893 -2.7523332000000e-05\r\n2845 2893 -3.7647060000000e-02\r\n2847 2893 -4.4673862000000e-06\r\n2890 2893 -4.1835211000000e-04\r\n2892 2893 -4.3661119000000e-06\r\n2893 2893  1.1698538000000e+02\r\n2895 2893  3.1879142000000e-04\r\n2896 2893 -5.1812949000000e-02\r\n2898 2893 -4.4687159000000e-06\r\n2941 2893 -4.2164408000000e-04\r\n2943 2893 -4.4004684000000e-06\r\n1789 2894  3.0979913000000e-01\r\n1791 2894 -4.3203223000000e+00\r\n2845 2894  1.9741084000000e+00\r\n2847 2894 -7.0141963000000e-01\r\n2892 2894 -7.0118328000000e-01\r\n2893 2894 -7.5477566000000e+01\r\n2894 2894 -2.2303262000000e+01\r\n2895 2894  7.1286849000000e+00\r\n2896 2894  6.0705380000000e+00\r\n2898 2894 -7.0168061000000e-01\r\n2943 2894 -7.0157335000000e-01\r\n1789 2895  5.2368419000000e-01\r\n1790 2895 -8.4831764000000e-02\r\n1791 2895 -7.3030692000000e+00\r\n2845 2895  3.3370312000000e+00\r\n2846 2895 -5.4056672000000e-01\r\n2847 2895 -1.1856792000000e+00\r\n2892 2895 -1.1852802000000e+00\r\n2893 2895 -1.2758722000000e+02\r\n2894 2895  1.9615711000000e+01\r\n2895 2895  1.2050324000000e+01\r\n2896 2895  1.0261632000000e+01\r\n2897 2895 -1.6622850000000e+00\r\n2898 2895 -1.1861203000000e+00\r\n2943 2895 -1.1859389000000e+00\r\n1792 2896 -2.7227522000000e-03\r\n1794 2896 -2.8415874000000e-05\r\n2848 2896 -4.2281181000000e-02\r\n2850 2896 -5.0296698000000e-06\r\n2893 2896 -4.2818342000000e-04\r\n2895 2896 -4.4687159000000e-06\r\n2896 2896  1.1702233000000e+02\r\n2898 2896  3.2114696000000e-04\r\n2899 2896 -8.8994729000000e-02\r\n2901 2896 -5.1260958000000e-06\r\n2944 2896 -4.3471186000000e-04\r\n2946 2896 -4.5368496000000e-06\r\n1792 2897  6.2673462000000e-01\r\n1794 2897 -4.3205436000000e+00\r\n2848 2897  1.6309355000000e+00\r\n2850 2897 -7.6503890000000e-01\r\n2895 2897 -7.0168061000000e-01\r\n2896 2897 -7.7644013000000e+01\r\n2897 2897 -2.2307808000000e+01\r\n2898 2897  7.2711835000000e+00\r\n2899 2897  8.2697436000000e+00\r\n2901 2897 -7.7976354000000e-01\r\n2946 2897 -7.0164907000000e-01\r\n1792 2898  1.0594322000000e+00\r\n1793 2898 -1.7161420000000e-01\r\n1794 2898 -7.3034469000000e+00\r\n2848 2898  2.7569334000000e+00\r\n2849 2898 -4.4658727000000e-01\r\n2850 2898 -1.2932218000000e+00\r\n2895 2898 -1.1861203000000e+00\r\n2896 2898 -1.3124944000000e+02\r\n2897 2898  2.0197250000000e+01\r\n2898 2898  1.2291208000000e+01\r\n2899 2898  1.3979175000000e+01\r\n2900 2898 -2.2644440000000e+00\r\n2901 2898 -1.3181123000000e+00\r\n2946 2898 -1.1860676000000e+00\r\n1795 2899 -2.2687455000000e-03\r\n1797 2899 -2.3677654000000e-05\r\n2851 2899 -6.0381371000000e-02\r\n2853 2899 -6.3144968000000e-06\r\n2896 2899 -4.9117225000000e-04\r\n2898 2899 -5.1260958000000e-06\r\n2899 2899  1.4628593000000e+02\r\n2901 2899  3.8911555000000e-04\r\n2902 2899 -1.1778417000000e-01\r\n2904 2899 -6.5322551000000e-06\r\n2947 2899 -5.2642474000000e-04\r\n2949 2899 -5.4940068000000e-06\r\n1795 2900  1.4991793000000e+00\r\n1797 2900 -3.4639961000000e+00\r\n2851 2900  2.1842910000000e+00\r\n2853 2900 -9.2495411000000e-01\r\n2898 2900 -7.7976354000000e-01\r\n2899 2900 -9.8102872000000e+01\r\n2900 2900 -2.7889063000000e+01\r\n2901 2900  6.9489161000000e+00\r\n2902 2900  1.0529944000000e+01\r\n2904 2900 -9.5692617000000e-01\r\n2949 2900 -8.2013940000000e-01\r\n1795 2901  2.5342110000000e+00\r\n1796 2901 -4.1049921000000e-01\r\n1797 2901 -5.8555350000000e+00\r\n2851 2901  3.6923229000000e+00\r\n2852 2901 -5.9809366000000e-01\r\n2853 2901 -1.5635414000000e+00\r\n2898 2901 -1.3181123000000e+00\r\n2899 2901 -1.6583299000000e+02\r\n2900 2901  2.5522133000000e+01\r\n2901 2901  1.1746441000000e+01\r\n2902 2901  1.7799806000000e+01\r\n2903 2901 -2.8832664000000e+00\r\n2904 2901 -1.6175869000000e+00\r\n2949 2901 -1.3863628000000e+00\r\n1798 2902 -1.9671590000000e-03\r\n1800 2902 -2.0530161000000e-05\r\n2854 2902 -9.4353779000000e-02\r\n2856 2902 -7.6876504000000e-06\r\n2899 2902 -6.2590762000000e-04\r\n2901 2902 -6.5322551000000e-06\r\n2902 2902  1.7555154000000e+02\r\n2904 2902  4.6028580000000e-04\r\n2905 2902 -1.3385002000000e-01\r\n2907 2902 -8.1373237000000e-06\r\n2950 2902 -6.7278096000000e-04\r\n2952 2902 -7.0214465000000e-06\r\n1798 2903  3.4378157000000e+00\r\n1800 2903 -2.8855036000000e+00\r\n2854 2903  4.5815569000000e+00\r\n2856 2903 -1.0846679000000e+00\r\n2901 2903 -9.5692617000000e-01\r\n2902 2903 -1.1978282000000e+02\r\n2903 2903 -3.3471603000000e+01\r\n2904 2903  7.0921696000000e+00\r\n2905 2903  1.1103122000000e+01\r\n2907 2903 -1.1481787000000e+00\r\n2952 2903 -1.0131270000000e+00\r\n1798 2904  5.8112836000000e+00\r\n1799 2904 -9.4130456000000e-01\r\n1800 2904 -4.8776553000000e+00\r\n2854 2904  7.7446637000000e+00\r\n2855 2904 -1.2544711000000e+00\r\n2856 2904 -1.8335227000000e+00\r\n2901 2904 -1.6175869000000e+00\r\n2902 2904 -2.0248088000000e+02\r\n2903 2904  3.1177756000000e+01\r\n2904 2904  1.1988602000000e+01\r\n2905 2904  1.8768717000000e+01\r\n2906 2904 -3.0401336000000e+00\r\n2907 2904 -1.9408812000000e+00\r\n2952 2904 -1.7125898000000e+00\r\n1801 2905 -1.3655556000000e-02\r\n1803 2905 -1.7592714000000e-05\r\n2857 2905 -1.4965754000000e-01\r\n2859 2905 -9.3519983000000e-06\r\n2902 2905 -7.7970208000000e-04\r\n2904 2905 -8.1373237000000e-06\r\n2905 2905  2.1065174000000e+02\r\n2907 2905  5.4643995000000e-04\r\n2908 2905 -1.0697527000000e-01\r\n2910 2905 -1.0164005000000e-05\r\n2953 2905 -8.3633053000000e-04\r\n2955 2905 -8.7283238000000e-06\r\n1801 2906  6.3913273000000e+00\r\n1803 2906 -2.4049276000000e+00\r\n2857 2906  9.4506934000000e+00\r\n2859 2906 -1.2783576000000e+00\r\n2904 2906 -1.1481787000000e+00\r\n2905 2906 -1.4406601000000e+02\r\n2906 2906 -4.0169576000000e+01\r\n2907 2906  7.4502841000000e+00\r\n2908 2906  7.4370771000000e+00\r\n2910 2906 -1.3893702000000e+00\r\n2955 2906 -1.2249288000000e+00\r\n1801 2907  1.0803892000000e+01\r\n1802 2907 -1.7499627000000e+00\r\n1803 2907 -4.0652867000000e+00\r\n2857 2907  1.5975441000000e+01\r\n2858 2907 -2.5876255000000e+00\r\n2859 2907 -2.1609341000000e+00\r\n2904 2907 -1.9408812000000e+00\r\n2905 2907 -2.4352901000000e+02\r\n2906 2907  3.7492727000000e+01\r\n2907 2907  1.2593953000000e+01\r\n2908 2907  1.2571626000000e+01\r\n2909 2907 -2.0362919000000e+00\r\n2910 2907 -2.3485896000000e+00\r\n2955 2907 -2.0706186000000e+00\r\n1804 2908 -3.1731369000000e-02\r\n1806 2908 -1.4651543000000e-05\r\n2860 2908 -2.3081970000000e-01\r\n2862 2908 -1.1598485000000e-05\r\n2905 2908 -9.7389460000000e-04\r\n2907 2908 -1.0164005000000e-05\r\n2908 2908  2.5739641000000e+02\r\n2910 2908  6.6144089000000e-04\r\n2911 2908 -1.1671148000000e-03\r\n2913 2908 -1.2180538000000e-05\r\n2956 2908 -1.0475229000000e-03\r\n2958 2908 -1.0932423000000e-05\r\n1804 2909  8.1999829000000e+00\r\n1806 2909 -1.9681342000000e+00\r\n2860 2909  1.5533079000000e+01\r\n2862 2909 -1.5579331000000e+00\r\n2907 2909 -1.3893702000000e+00\r\n2908 2909 -1.7136108000000e+02\r\n2909 2909 -4.9096209000000e+01\r\n2910 2909  8.0683912000000e+00\r\n2913 2909 -1.6425735000000e+00\r\n2958 2909 -1.5048543000000e+00\r\n1804 2910  1.3861251000000e+01\r\n1805 2910 -2.2451493000000e+00\r\n1806 2910 -3.3269340000000e+00\r\n2860 2910  2.6257116000000e+01\r\n2861 2910 -4.2529456000000e+00\r\n2862 2910 -2.6335301000000e+00\r\n2907 2910 -2.3485896000000e+00\r\n2908 2910 -2.8966876000000e+02\r\n2909 2910  4.4531218000000e+01\r\n2910 2910  1.3638805000000e+01\r\n2913 2910 -2.7766044000000e+00\r\n2958 2910 -2.5438056000000e+00\r\n1807 2911 -9.9412422000000e-03\r\n1809 2911 -1.2837617000000e-05\r\n2863 2911 -1.4530947000000e-01\r\n2865 2911 -1.2988390000000e-05\r\n2908 2911 -1.7789741000000e-03\r\n2910 2911 -1.2180538000000e-05\r\n2911 2911  2.9235758000000e+02\r\n2913 2911  7.4769519000000e-04\r\n2914 2911 -1.2369273000000e-03\r\n2916 2911 -1.2909133000000e-05\r\n2959 2911 -1.2251659000000e-03\r\n2961 2911 -1.2786386000000e-05\r\n1807 2912  6.0694391000000e+00\r\n1809 2912 -1.7312366000000e+00\r\n2863 2912  7.4327847000000e+00\r\n2865 2912 -1.7514355000000e+00\r\n2908 2912  2.1251653000000e+00\r\n2910 2912 -1.6425735000000e+00\r\n2911 2912 -1.8339221000000e+02\r\n2912 2912 -5.5787051000000e+01\r\n2913 2912  8.6371571000000e+00\r\n2916 2912 -1.7546171000000e+00\r\n2961 2912 -1.7510167000000e+00\r\n1807 2913  1.0259773000000e+01\r\n1808 2913 -1.6618126000000e+00\r\n1809 2913 -2.9264805000000e+00\r\n2863 2913  1.2564371000000e+01\r\n2864 2913 -2.0350968000000e+00\r\n2865 2913 -2.9606246000000e+00\r\n2908 2913  3.5923771000000e+00\r\n2909 2913 -5.8187035000000e-01\r\n2910 2913 -2.7766044000000e+00\r\n2911 2913 -3.1000599000000e+02\r\n2912 2913  4.7510016000000e+01\r\n2913 2913  1.4600243000000e+01\r\n2916 2913 -2.9660047000000e+00\r\n2961 2913 -2.9599166000000e+00\r\n1810 2914 -1.2317144000000e-03\r\n1812 2914 -1.2854729000000e-05\r\n2866 2914 -4.9930138000000e-02\r\n2868 2914 -1.2885356000000e-05\r\n2911 2914 -4.3702887000000e-02\r\n2913 2914 -1.2909133000000e-05\r\n2914 2914  2.9229690000000e+02\r\n2916 2914  7.3543728000000e-04\r\n2917 2914 -1.2263071000000e-03\r\n2919 2914 -1.2798296000000e-05\r\n1810 2915  4.7417388000000e+00\r\n1812 2915 -1.7320662000000e+00\r\n2868 2915 -1.7512923000000e+00\r\n2911 2915  4.1803082000000e+00\r\n2913 2915 -1.7546171000000e+00\r\n2914 2915 -1.7669016000000e+02\r\n2915 2915 -5.5784865000000e+01\r\n2916 2915  6.9988269000000e+00\r\n2919 2915 -1.7545746000000e+00\r\n1810 2916  8.0154353000000e+00\r\n1811 2916 -1.2982959000000e+00\r\n1812 2916 -2.9278847000000e+00\r\n2868 2916 -2.9603845000000e+00\r\n2911 2916  7.0663930000000e+00\r\n2912 2916 -1.1445752000000e+00\r\n2913 2916 -2.9660047000000e+00\r\n2914 2916 -2.9867705000000e+02\r\n2915 2916  4.5680730000000e+01\r\n2916 2916  1.1830815000000e+01\r\n2919 2916 -2.9659313000000e+00\r\n1813 2917 -1.2176441000000e-03\r\n1815 2917 -1.2707884000000e-05\r\n2869 2917 -1.7815582000000e-02\r\n2871 2917 -1.2778240000000e-05\r\n2914 2917 -5.6888197000000e-02\r\n2916 2917 -1.2798296000000e-05\r\n2917 2917  2.9227822000000e+02\r\n2919 2917  7.2226879000000e-04\r\n1813 2918  3.6538981000000e+00\r\n1815 2918 -1.7304932000000e+00\r\n2871 2918 -1.7517190000000e+00\r\n2914 2918  4.6340972000000e+00\r\n2916 2918 -1.7545746000000e+00\r\n2917 2918 -1.7605817000000e+02\r\n2918 2918 -5.5783494000000e+01\r\n2919 2918  5.2430629000000e+00\r\n1813 2919  6.1765459000000e+00\r\n1814 2919 -1.0004495000000e+00\r\n1815 2919 -2.9252241000000e+00\r\n2871 2919 -2.9611039000000e+00\r\n2914 2919  7.8334735000000e+00\r\n2915 2919 -1.2688313000000e+00\r\n2916 2919 -2.9659313000000e+00\r\n2917 2919 -2.9760857000000e+02\r\n2918 2919  4.5511484000000e+01\r\n2919 2919  8.8628684000000e+00\r\n2920 2920  1.0000000000000e+00\r\n2921 2921  1.0000000000000e+00\r\n2922 2922  1.0000000000000e+00\r\n2923 2923  1.0000000000000e+00\r\n2924 2924  1.0000000000000e+00\r\n2925 2925  1.0000000000000e+00\r\n2926 2926  1.0000000000000e+00\r\n2927 2927  1.0000000000000e+00\r\n2928 2928  1.0000000000000e+00\r\n2929 2929  1.0000000000000e+00\r\n2930 2930  1.0000000000000e+00\r\n2931 2931  1.0000000000000e+00\r\n2932 2932  1.0000000000000e+00\r\n2933 2933  1.0000000000000e+00\r\n2934 2934  1.0000000000000e+00\r\n1831 2935 -2.0907687000000e-03\r\n1833 2935 -2.1820208000000e-05\r\n2887 2935 -1.5280454000000e-02\r\n2889 2935 -4.7493308000000e-06\r\n2935 2935  1.4030494000000e+02\r\n2937 2935  3.6494319000000e-04\r\n2938 2935 -4.6051907000000e-04\r\n2940 2935 -4.8061854000000e-06\r\n2983 2935 -5.0706768000000e-04\r\n2985 2935 -5.2919878000000e-06\r\n1831 2936  2.4986659000000e-01\r\n1833 2936 -3.6092681000000e+00\r\n2887 2936  2.3300809000000e+00\r\n2889 2936 -7.8561509000000e-01\r\n2935 2936 -8.5988916000000e+01\r\n2936 2936 -2.6749432000000e+01\r\n2937 2936  6.0726827000000e+00\r\n2938 2936  2.8408732000000e+00\r\n2940 2936 -7.8409278000000e-01\r\n2985 2936 -8.9070618000000e-01\r\n1831 2937  4.2237423000000e-01\r\n1832 2937 -6.8422734000000e-02\r\n1833 2937 -6.1011032000000e+00\r\n2887 2937  3.9387665000000e+00\r\n2888 2937 -6.3806251000000e-01\r\n2889 2937 -1.3280030000000e+00\r\n2935 2937 -1.4535558000000e+02\r\n2936 2937  2.2319922000000e+01\r\n2937 2937  1.0265257000000e+01\r\n2938 2937  4.8022092000000e+00\r\n2939 2937 -7.7793632000000e-01\r\n2940 2937 -1.3254297000000e+00\r\n2985 2937 -1.5056487000000e+00\r\n1834 2938 -2.4200611000000e-03\r\n1836 2938 -2.5256853000000e-05\r\n2890 2938 -3.9294061000000e-02\r\n2892 2938 -4.4035919000000e-06\r\n2935 2938 -1.4951867000000e-02\r\n2937 2938 -4.8061854000000e-06\r\n2938 2938  1.2281904000000e+02\r\n2940 2938  3.3084145000000e-04\r\n2941 2938 -1.8239248000000e-02\r\n2943 2938 -4.4015426000000e-06\r\n2986 2938 -4.5364268000000e-04\r\n2988 2938 -4.7344203000000e-06\r\n1834 2939  2.4940594000000e-01\r\n1836 2939 -4.1202759000000e+00\r\n2890 2939  2.9376635000000e+00\r\n2892 2939 -7.1847045000000e-01\r\n2937 2939 -7.8409278000000e-01\r\n2938 2939 -7.7998744000000e+01\r\n2939 2939 -2.3412403000000e+01\r\n2940 2939  7.1290163000000e+00\r\n2941 2939  4.3238292000000e+00\r\n2943 2939 -7.1818374000000e-01\r\n2988 2939 -7.8536504000000e-01\r\n1834 2940  4.2159580000000e-01\r\n1835 2940 -6.8296022000000e-02\r\n1836 2940 -6.9649144000000e+00\r\n2890 2940  4.9658263000000e+00\r\n2891 2940 -8.0443445000000e-01\r\n2892 2940 -1.2145024000000e+00\r\n2937 2940 -1.3254297000000e+00\r\n2938 2940 -1.3184908000000e+02\r\n2939 2940  2.0268814000000e+01\r\n2940 2940  1.2050888000000e+01\r\n2941 2940  7.3090009000000e+00\r\n2942 2940 -1.1840149000000e+00\r\n2943 2940 -1.2140178000000e+00\r\n2988 2940 -1.3275811000000e+00\r\n1837 2941 -2.5969432000000e-03\r\n1839 2941 -2.7102875000000e-05\r\n2893 2941 -3.9896689000000e-02\r\n2895 2941 -4.4004684000000e-06\r\n2938 2941 -4.2174700000000e-04\r\n2940 2941 -4.4015426000000e-06\r\n2941 2941  1.1698109000000e+02\r\n2943 2941  3.1818732000000e-04\r\n2944 2941 -4.5028381000000e-02\r\n2946 2941 -4.3990367000000e-06\r\n2989 2941 -4.1409852000000e-04\r\n2991 2941 -4.3217195000000e-06\r\n1837 2942  2.6194740000000e-01\r\n1839 2942 -4.3210899000000e+00\r\n2893 2942  2.8713325000000e+00\r\n2895 2942 -7.0157335000000e-01\r\n2940 2942 -7.1818374000000e-01\r\n2941 2942 -7.5997533000000e+01\r\n2942 2942 -2.2303045000000e+01\r\n2943 2942  7.1462039000000e+00\r\n2944 2942  5.7407411000000e+00\r\n2946 2942 -7.0138732000000e-01\r\n2991 2942 -7.0146394000000e-01\r\n1837 2943  4.4279562000000e-01\r\n1838 2943 -7.1729294000000e-02\r\n1839 2943 -7.3043660000000e+00\r\n2893 2943  4.8536977000000e+00\r\n2894 2943 -7.8625959000000e-01\r\n2895 2943 -1.1859389000000e+00\r\n2940 2943 -1.2140178000000e+00\r\n2941 2943 -1.2846615000000e+02\r\n2942 2943  1.9758867000000e+01\r\n2943 2943  1.2079937000000e+01\r\n2944 2943  9.7041432000000e+00\r\n2945 2943 -1.5719925000000e+00\r\n2946 2943 -1.1856244000000e+00\r\n2991 2943 -1.1857538000000e+00\r\n1840 2944 -2.6783038000000e-03\r\n1842 2944 -2.7951990000000e-05\r\n2896 2944 -4.6667797000000e-02\r\n2898 2944 -4.5368496000000e-06\r\n2941 2944 -4.2150690000000e-04\r\n2943 2944 -4.3990367000000e-06\r\n2944 2944  1.1699333000000e+02\r\n2946 2944  3.1965121000000e-04\r\n2947 2944 -5.5637401000000e-02\r\n2949 2944 -4.7515607000000e-06\r\n2992 2944 -4.2604735000000e-04\r\n2994 2944 -4.4464229000000e-06\r\n1840 2945  3.8406668000000e-01\r\n1842 2945 -4.3220435000000e+00\r\n2896 2945  3.1988388000000e+00\r\n2898 2945 -7.0164907000000e-01\r\n2943 2945 -7.0138732000000e-01\r\n2944 2945 -7.7946499000000e+01\r\n2945 2945 -2.2307860000000e+01\r\n2946 2945  7.1642056000000e+00\r\n2947 2945  7.2469567000000e+00\r\n2949 2945 -7.3491268000000e-01\r\n2994 2945 -7.0170517000000e-01\r\n1840 2946  6.4922631000000e-01\r\n1841 2946 -1.0516732000000e-01\r\n1842 2946 -7.3059823000000e+00\r\n2896 2946  5.4073170000000e+00\r\n2897 2946 -8.7592417000000e-01\r\n2898 2946 -1.1860676000000e+00\r\n2943 2946 -1.1856244000000e+00\r\n2944 2946 -1.3176076000000e+02\r\n2945 2946  2.0280237000000e+01\r\n2946 2946  1.2110372000000e+01\r\n2947 2946  1.2250255000000e+01\r\n2948 2946 -1.9844028000000e+00\r\n2949 2946 -1.2422964000000e+00\r\n2994 2946 -1.1861624000000e+00\r\n1843 2947 -2.5234634000000e-03\r\n1845 2947 -2.6336006000000e-05\r\n2899 2947 -8.6060744000000e-02\r\n2901 2947 -5.4940068000000e-06\r\n2944 2947 -4.5528504000000e-04\r\n2946 2947 -4.7515607000000e-06\r\n2947 2947  1.2875970000000e+02\r\n2949 2947  3.4823164000000e-04\r\n2950 2947 -1.0110620000000e-01\r\n2952 2947 -5.7909466000000e-06\r\n2995 2947 -4.7264122000000e-04\r\n2997 2947 -4.9326976000000e-06\r\n1843 2948  8.2261853000000e-01\r\n1845 2948 -3.9293287000000e+00\r\n2899 2948  4.3492109000000e+00\r\n2901 2948 -8.2013940000000e-01\r\n2946 2948 -7.3491268000000e-01\r\n2947 2948 -8.7385812000000e+01\r\n2948 2948 -2.4545170000000e+01\r\n2949 2948  7.1055679000000e+00\r\n2950 2948  8.3950323000000e+00\r\n2952 2948 -8.6451796000000e-01\r\n2997 2948 -7.5390765000000e-01\r\n1843 2949  1.3905535000000e+00\r\n1844 2949 -2.2524889000000e-01\r\n1845 2949 -6.6421333000000e+00\r\n2899 2949  7.3519017000000e+00\r\n2900 2949 -1.1908982000000e+00\r\n2901 2949 -1.3863628000000e+00\r\n2946 2949 -1.2422964000000e+00\r\n2947 2949 -1.4771689000000e+02\r\n2948 2949  2.2741959000000e+01\r\n2949 2949  1.2011246000000e+01\r\n2950 2949  1.4190954000000e+01\r\n2951 2949 -2.2987224000000e+00\r\n2952 2949 -1.4613803000000e+00\r\n2997 2949 -1.2744047000000e+00\r\n1846 2950 -2.0624577000000e-03\r\n1848 2950 -2.1524741000000e-05\r\n2902 2950 -1.1252369000000e-01\r\n2904 2950 -7.0214465000000e-06\r\n2947 2950 -5.5487692000000e-04\r\n2949 2950 -5.7909466000000e-06\r\n2950 2950  1.6385552000000e+02\r\n2952 2950  4.3118608000000e-04\r\n2953 2950 -1.0965209000000e-01\r\n2955 2950 -7.4674546000000e-06\r\n2998 2950 -6.1070402000000e-04\r\n3000 2950 -6.3735834000000e-06\r\n1846 2951  1.7105763000000e+00\r\n1848 2951 -3.1003240000000e+00\r\n2902 2951  6.6823870000000e+00\r\n2904 2951 -1.0131270000000e+00\r\n2949 2951 -8.6451796000000e-01\r\n2950 2951 -1.1119055000000e+02\r\n2951 2951 -3.1242159000000e+01\r\n2952 2951  7.0031835000000e+00\r\n2953 2951  8.8505135000000e+00\r\n2955 2951 -1.0775222000000e+00\r\n3000 2951 -9.4417640000000e-01\r\n1846 2952  2.8915581000000e+00\r\n1847 2952 -4.6837824000000e-01\r\n1848 2952 -5.2407877000000e+00\r\n2902 2952  1.1295907000000e+01\r\n2903 2952 -1.8297253000000e+00\r\n2904 2952 -1.7125898000000e+00\r\n2949 2952 -1.4613803000000e+00\r\n2950 2952 -1.8795651000000e+02\r\n2951 2952  2.8928800000000e+01\r\n2952 2952  1.1838180000000e+01\r\n2953 2952  1.4960908000000e+01\r\n2954 2952 -2.4233868000000e+00\r\n2955 2952 -1.8214435000000e+00\r\n3000 2952 -1.5960358000000e+00\r\n1849 2953 -1.7450567000000e-03\r\n1851 2953 -1.8212201000000e-05\r\n2905 2953 -1.5418602000000e-01\r\n2907 2953 -8.7283238000000e-06\r\n2950 2953 -7.1551657000000e-04\r\n2952 2953 -7.4674546000000e-06\r\n2953 2953  1.9895003000000e+02\r\n2955 2953  5.1713859000000e-04\r\n2956 2953 -1.0189083000000e-01\r\n2958 2953 -9.3955150000000e-06\r\n3001 2953 -7.8983668000000e-04\r\n3003 2953 -8.2430930000000e-06\r\n1849 2954  2.9953742000000e+00\r\n1851 2954 -2.5465029000000e+00\r\n2905 2954  9.8630409000000e+00\r\n2907 2954 -1.2249288000000e+00\r\n2952 2954 -1.0775222000000e+00\r\n2953 2954 -1.3466501000000e+02\r\n2954 2954 -3.7939422000000e+01\r\n2955 2954  7.3605572000000e+00\r\n2956 2954  7.7318862000000e+00\r\n2958 2954 -1.3185876000000e+00\r\n3003 2954 -1.1887451000000e+00\r\n1849 2955  5.0633777000000e+00\r\n1850 2955 -8.2015700000000e-01\r\n1851 2955 -4.3046060000000e+00\r\n2905 2955  1.6672475000000e+01\r\n2906 2955 -2.7005780000000e+00\r\n2907 2955 -2.0706186000000e+00\r\n2952 2955 -1.8214435000000e+00\r\n2953 2955 -2.2763761000000e+02\r\n2954 2955  3.5024388000000e+01\r\n2955 2955  1.2442280000000e+01\r\n2956 2955  1.3069973000000e+01\r\n2957 2955 -2.1170510000000e+00\r\n2958 2955 -2.2289392000000e+00\r\n3003 2955 -2.0094537000000e+00\r\n1852 2956 -1.4437416000000e-03\r\n1854 2956 -1.5067541000000e-05\r\n2908 2956 -1.8899141000000e-01\r\n2910 2956 -1.0932423000000e-05\r\n2953 2956 -9.0025946000000e-04\r\n2955 2956 -9.3955150000000e-06\r\n2956 2956  2.4568578000000e+02\r\n2958 2956  6.3195050000000e-04\r\n2959 2956 -5.3626918000000e-02\r\n2961 2956 -1.1637965000000e-05\r\n3004 2956 -9.9467506000000e-04\r\n3006 2956 -1.0380879000000e-05\r\n1852 2957  3.8277950000000e+00\r\n1854 2957 -2.0617751000000e+00\r\n2908 2957  1.1347922000000e+01\r\n2910 2957 -1.5048543000000e+00\r\n2955 2957 -1.3185876000000e+00\r\n2956 2957 -1.5857358000000e+02\r\n2957 2957 -4.6867737000000e+01\r\n2958 2957  7.9452507000000e+00\r\n2959 2957  2.4842690000000e+00\r\n2961 2957 -1.6019820000000e+00\r\n3006 2957 -1.4527757000000e+00\r\n1852 2958  6.4705046000000e+00\r\n1853 2958 -1.0480660000000e+00\r\n1854 2958 -3.4852246000000e+00\r\n2908 2958  1.9182526000000e+01\r\n2909 2958 -3.1071076000000e+00\r\n2910 2958 -2.5438056000000e+00\r\n2955 2958 -2.2289392000000e+00\r\n2956 2958 -2.6805278000000e+02\r\n2957 2958  4.1131714000000e+01\r\n2958 2958  1.3430650000000e+01\r\n2959 2958  4.1994083000000e+00\r\n2960 2958 -6.8020307000000e-01\r\n2961 2958 -2.7079903000000e+00\r\n3006 2958 -2.4557720000000e+00\r\n1855 2959 -1.2193593000000e-03\r\n1857 2959 -1.2725786000000e-05\r\n2911 2959 -1.6186938000000e-01\r\n2913 2959 -1.2786386000000e-05\r\n2956 2959 -1.1151265000000e-03\r\n2958 2959 -1.1637965000000e-05\r\n2959 2959  2.9235799000000e+02\r\n2961 2959  7.3364169000000e-04\r\n3007 2959 -1.1991036000000e-03\r\n3009 2959 -1.2514388000000e-05\r\n1855 2960  3.3656994000000e+00\r\n1857 2960 -1.7316203000000e+00\r\n2911 2960  8.2236014000000e+00\r\n2913 2960 -1.7510167000000e+00\r\n2958 2960 -1.6019820000000e+00\r\n2959 2960 -1.7934679000000e+02\r\n2960 2960 -5.5792557000000e+01\r\n2961 2960  6.8241964000000e+00\r\n3009 2960 -1.7332974000000e+00\r\n1855 2961  5.6893743000000e+00\r\n1856 2961 -9.2153890000000e-01\r\n1857 2961 -2.9271289000000e+00\r\n2911 2961  1.3901166000000e+01\r\n2912 2961 -2.2516474000000e+00\r\n2913 2961 -2.9599166000000e+00\r\n2958 2961 -2.7079903000000e+00\r\n2959 2961 -3.0316761000000e+02\r\n2960 2961  4.6389658000000e+01\r\n2961 2961  1.1535616000000e+01\r\n3009 2961 -2.9299642000000e+00\r\n2962 2962  1.0000000000000e+00\r\n2963 2963  1.0000000000000e+00\r\n2964 2964  1.0000000000000e+00\r\n2965 2965  1.0000000000000e+00\r\n2966 2966  1.0000000000000e+00\r\n2967 2967  1.0000000000000e+00\r\n2968 2968  1.0000000000000e+00\r\n2969 2969  1.0000000000000e+00\r\n2970 2970  1.0000000000000e+00\r\n2971 2971  1.0000000000000e+00\r\n2972 2972  1.0000000000000e+00\r\n2973 2973  1.0000000000000e+00\r\n2974 2974  1.0000000000000e+00\r\n2975 2975  1.0000000000000e+00\r\n2976 2976  1.0000000000000e+00\r\n2977 2977  1.0000000000000e+00\r\n2978 2978  1.0000000000000e+00\r\n2979 2979  1.0000000000000e+00\r\n1876 2980 -1.6218760000000e-03\r\n1878 2980 -1.6926631000000e-05\r\n2980 2980  1.7537941000000e+02\r\n2982 2980  4.3935417000000e-04\r\n2983 2980 -5.6647007000000e-04\r\n2985 2980 -5.9119379000000e-06\r\n3028 2980 -6.1556137000000e-03\r\n3030 2980 -6.1714783000000e-06\r\n1876 2981  2.8576449000000e-01\r\n1878 2981 -2.8833788000000e+00\r\n2980 2981 -1.0405696000000e+02\r\n2981 2981 -3.3424919000000e+01\r\n2982 2981  4.9336497000000e+00\r\n2983 2981  3.0445818000000e+00\r\n2985 2981 -9.9495519000000e-01\r\n3030 2981 -1.0515702000000e+00\r\n1876 2982  4.8305630000000e-01\r\n1877 2982 -7.8254280000000e-02\r\n1878 2982 -4.8740636000000e+00\r\n2980 2982 -1.7589789000000e+02\r\n2981 2982  2.6990414000000e+01\r\n2982 2982  8.3398415000000e+00\r\n2983 2982  5.1465611000000e+00\r\n2984 2982 -8.3373394000000e-01\r\n2985 2982 -1.6818723000000e+00\r\n3030 2982 -1.7775743000000e+00\r\n1879 2983 -1.8263607000000e-03\r\n1881 2983 -1.9060727000000e-05\r\n2935 2983 -2.5935914000000e-02\r\n2937 2983 -5.2919878000000e-06\r\n2980 2983 -1.0039632000000e-02\r\n2982 2983 -5.9119379000000e-06\r\n2983 2983  1.5787298000000e+02\r\n2985 2983  4.1085346000000e-04\r\n2986 2983 -5.1382266000000e-04\r\n2988 2983 -5.3624858000000e-06\r\n3031 2983 -7.6890951000000e-03\r\n3033 2983 -5.9184280000000e-06\r\n1879 2984  2.7351888000000e-01\r\n1881 2984 -3.2080206000000e+00\r\n2935 2984  3.9182695000000e+00\r\n2937 2984 -8.9070618000000e-01\r\n2982 2984 -9.9495519000000e-01\r\n2983 2984 -9.8166516000000e+01\r\n2984 2984 -3.0088923000000e+01\r\n2985 2984  6.9825585000000e+00\r\n2986 2984  3.3297181000000e+00\r\n2988 2984 -8.8944881000000e-01\r\n3033 2984 -9.9605394000000e-01\r\n1879 2985  4.6235599000000e-01\r\n1880 2985 -7.4900371000000e-02\r\n1881 2985 -5.4228342000000e+00\r\n2935 2985  6.6234381000000e+00\r\n2936 2985 -1.0729783000000e+00\r\n2937 2985 -1.5056487000000e+00\r\n2982 2985 -1.6818723000000e+00\r\n2983 2985 -1.6594056000000e+02\r\n2984 2985  2.5511811000000e+01\r\n2985 2985  1.1803310000000e+01\r\n2986 2985  5.6285516000000e+00\r\n2987 2985 -9.1180951000000e-01\r\n2988 2985 -1.5035232000000e+00\r\n3033 2985 -1.6837284000000e+00\r\n1882 2986 -2.0841056000000e-03\r\n1884 2986 -2.1750669000000e-05\r\n2938 2986 -1.4222408000000e-02\r\n2940 2986 -4.7344203000000e-06\r\n2983 2986 -7.1571804000000e-03\r\n2985 2986 -5.3624858000000e-06\r\n2986 2986  1.4031504000000e+02\r\n2988 2986  3.6982836000000e-04\r\n2989 2986 -7.4921983000000e-03\r\n2991 2986 -4.6053461000000e-06\r\n3034 2986 -4.8897810000000e-04\r\n3036 2986 -5.1031967000000e-06\r\n1882 2987  2.5395958000000e-01\r\n1884 2987 -3.6073107000000e+00\r\n2938 2987  3.3601425000000e+00\r\n2940 2987 -7.8536504000000e-01\r\n2985 2987 -8.8944881000000e-01\r\n2986 2987 -8.8453895000000e+01\r\n2987 2987 -2.6752309000000e+01\r\n2988 2987  6.9076900000000e+00\r\n2989 2987  4.2756307000000e+00\r\n2991 2987 -7.6397796000000e-01\r\n3036 2987 -8.5858568000000e-01\r\n1882 2988  4.2929328000000e-01\r\n1883 2988 -6.9543659000000e-02\r\n1884 2988 -6.0977979000000e+00\r\n2938 2988  5.6799849000000e+00\r\n2939 2988 -9.2013306000000e-01\r\n2940 2988 -1.3275811000000e+00\r\n2985 2988 -1.5035232000000e+00\r\n2986 2988 -1.4952246000000e+02\r\n2987 2988  2.2987933000000e+01\r\n2988 2988  1.1676758000000e+01\r\n2989 2988  7.2275262000000e+00\r\n2990 2988 -1.1708281000000e+00\r\n2991 2988 -1.2914283000000e+00\r\n3036 2988 -1.4513532000000e+00\r\n1885 2989 -2.5550484000000e-03\r\n1887 2989 -2.6665641000000e-05\r\n2941 2989 -2.3639000000000e-02\r\n2943 2989 -4.3217195000000e-06\r\n2986 2989 -4.4127505000000e-04\r\n2988 2989 -4.6053461000000e-06\r\n2989 2989  1.1694917000000e+02\r\n2991 2989  3.1781661000000e-04\r\n2992 2989 -2.6024437000000e-02\r\n2994 2989 -4.3157520000000e-06\r\n3037 2989 -4.1664047000000e-04\r\n3039 2989 -4.3482484000000e-06\r\n1885 2990  2.5126827000000e-01\r\n1887 2990 -4.3270355000000e+00\r\n2941 2990  3.2985162000000e+00\r\n2943 2990 -7.0146394000000e-01\r\n2988 2990 -7.6397796000000e-01\r\n2989 2990 -7.5896088000000e+01\r\n2990 2990 -2.2299969000000e+01\r\n2991 2990  7.2137900000000e+00\r\n2992 2990  5.2184149000000e+00\r\n2994 2990 -7.0052491000000e-01\r\n3039 2990 -7.1828335000000e-01\r\n1885 2991  4.2474358000000e-01\r\n1886 2991 -6.8805773000000e-02\r\n1887 2991 -7.3144156000000e+00\r\n2941 2991  5.5758076000000e+00\r\n2942 2991 -9.0324552000000e-01\r\n2943 2991 -1.1857538000000e+00\r\n2988 2991 -1.2914283000000e+00\r\n2989 2991 -1.2829465000000e+02\r\n2990 2991  1.9738918000000e+01\r\n2991 2991  1.2194183000000e+01\r\n2992 2991  8.8212022000000e+00\r\n2993 2991 -1.4289789000000e+00\r\n2994 2991 -1.1841664000000e+00\r\n3039 2991 -1.2141856000000e+00\r\n1888 2992 -2.6280701000000e-03\r\n1890 2992 -2.7427728000000e-05\r\n2944 2992 -4.2629391000000e-02\r\n2946 2992 -4.4464229000000e-06\r\n2989 2992 -4.1352672000000e-04\r\n2991 2992 -4.3157520000000e-06\r\n2992 2992  1.1696963000000e+02\r\n2994 2992  3.1865200000000e-04\r\n2995 2992 -3.4250593000000e-02\r\n2997 2992 -4.5489783000000e-06\r\n3040 2992 -4.1695912000000e-04\r\n3042 2992 -4.3515740000000e-06\r\n1888 2993  2.8803691000000e-01\r\n1890 2993 -4.3278193000000e+00\r\n2944 2993  3.8156956000000e+00\r\n2946 2993 -7.0170517000000e-01\r\n2991 2993 -7.0052491000000e-01\r\n2992 2993 -7.7511946000000e+01\r\n2993 2993 -2.2306268000000e+01\r\n2994 2993  7.1518615000000e+00\r\n2995 2993  6.2892341000000e+00\r\n2997 2993 -7.1794048000000e-01\r\n3042 2993 -7.0136448000000e-01\r\n1888 2994  4.8689758000000e-01\r\n1889 2994 -7.8872904000000e-02\r\n1890 2994 -7.3157458000000e+00\r\n2944 2994  6.4500519000000e+00\r\n2945 2994 -1.0448487000000e+00\r\n2946 2994 -1.1861624000000e+00\r\n2991 2994 -1.1841664000000e+00\r\n2992 2994 -1.3102619000000e+02\r\n2993 2994  2.0165486000000e+01\r\n2994 2994  1.2089506000000e+01\r\n2995 2994  1.0631321000000e+01\r\n2996 2994 -1.7221757000000e+00\r\n2997 2994 -1.2136066000000e+00\r\n3042 2994 -1.1855865000000e+00\r\n1891 2995 -2.5829767000000e-03\r\n1893 2995 -2.6957113000000e-05\r\n2947 2995 -6.6907064000000e-02\r\n2949 2995 -4.9326976000000e-06\r\n2992 2995 -4.3587400000000e-04\r\n2994 2995 -4.5489783000000e-06\r\n2995 2995  1.2284613000000e+02\r\n2997 2995  3.3371446000000e-04\r\n2998 2995 -5.0043636000000e-02\r\n3000 2995 -5.3283485000000e-06\r\n3043 2995 -4.5087345000000e-04\r\n3045 2995 -4.7055193000000e-06\r\n1891 2996  4.8005106000000e-01\r\n1893 2996 -4.1183464000000e+00\r\n2947 2996  4.9292198000000e+00\r\n2949 2996 -7.5390765000000e-01\r\n2994 2996 -7.1794048000000e-01\r\n2995 2996 -8.3034678000000e+01\r\n2996 2996 -2.3428959000000e+01\r\n2997 2996  7.1440394000000e+00\r\n2998 2996  7.1609685000000e+00\r\n3000 2996 -8.1443468000000e-01\r\n3045 2996 -7.3677436000000e-01\r\n1891 2997  8.1147783000000e-01\r\n1892 2997 -1.3144930000000e-01\r\n1893 2997 -6.9616488000000e+00\r\n2947 2997  8.3323483000000e+00\r\n2948 2997 -1.3497365000000e+00\r\n2949 2997 -1.2744047000000e+00\r\n2994 2997 -1.2136066000000e+00\r\n2995 2997 -1.4036174000000e+02\r\n2996 2997  2.1606154000000e+01\r\n2997 2997  1.2076278000000e+01\r\n2998 2997  1.2104894000000e+01\r\n2999 2997 -1.9608419000000e+00\r\n3000 2997 -1.3767196000000e+00\r\n3045 2997 -1.2454426000000e+00\r\n1894 2998 -2.1541484000000e-03\r\n1896 2998 -2.2481667000000e-05\r\n2950 2998 -1.3618978000000e-01\r\n2952 2998 -6.3735834000000e-06\r\n2995 2998 -5.1055170000000e-04\r\n2997 2998 -5.3283485000000e-06\r\n2998 2998  1.5220095000000e+02\r\n3000 2998  4.0278264000000e-04\r\n3001 2998 -1.2365296000000e-01\r\n3003 2998 -6.9744586000000e-06\r\n3046 2998 -5.7371574000000e-04\r\n3048 2998 -5.9875571000000e-06\r\n1894 2999  9.1064474000000e-01\r\n1896 2999 -3.3276778000000e+00\r\n2950 2999  7.0395525000000e+00\r\n2952 2999 -9.4417640000000e-01\r\n2997 2999 -8.1443468000000e-01\r\n2998 2999 -1.0306843000000e+02\r\n2999 2999 -2.9014860000000e+01\r\n3000 2999  7.0343971000000e+00\r\n3001 2999  7.8874247000000e+00\r\n3003 2999 -1.0332217000000e+00\r\n3048 2999 -9.1161978000000e-01\r\n1894 3000  1.5393539000000e+00\r\n1895 3000 -2.4935089000000e-01\r\n1896 3000 -5.6251066000000e+00\r\n2950 3000  1.1899659000000e+01\r\n2951 3000 -1.9275560000000e+00\r\n2952 3000 -1.5960358000000e+00\r\n2997 3000 -1.3767196000000e+00\r\n2998 3000 -1.7422688000000e+02\r\n2999 3000  2.6803302000000e+01\r\n3000 3000  1.1890944000000e+01\r\n3001 3000  1.3332903000000e+01\r\n3002 3000 -2.1597186000000e+00\r\n3003 3000 -1.7465580000000e+00\r\n3048 3000 -1.5410021000000e+00\r\n1897 3001 -1.7013121000000e-03\r\n1899 3001 -1.7755663000000e-05\r\n2953 3001 -1.5016361000000e-01\r\n2955 3001 -8.2430930000000e-06\r\n2998 3001 -6.6827867000000e-04\r\n3000 3001 -6.9744586000000e-06\r\n3001 3001  1.9898128000000e+02\r\n3003 3001  5.1503403000000e-04\r\n3004 3001 -1.3871730000000e-01\r\n3006 3001 -9.0451660000000e-06\r\n3049 3001 -7.6061183000000e-04\r\n3051 3001 -7.9380892000000e-06\r\n1897 3002  1.4824585000000e+00\r\n1899 3002 -2.5556453000000e+00\r\n2953 3002  9.5520967000000e+00\r\n2955 3002 -1.1887451000000e+00\r\n3000 3002 -1.0332217000000e+00\r\n3001 3002 -1.3676547000000e+02\r\n3002 3002 -3.7941031000000e+01\r\n3003 3002  7.2749930000000e+00\r\n3004 3002  1.1658090000000e+01\r\n3006 3002 -1.3044628000000e+00\r\n3051 3002 -1.1886468000000e+00\r\n1897 3003  2.5059465000000e+00\r\n1898 3003 -4.0591642000000e-01\r\n1899 3003 -4.3200606000000e+00\r\n2953 3003  1.6146856000000e+01\r\n2954 3003 -2.6154883000000e+00\r\n2955 3003 -2.0094537000000e+00\r\n3000 3003 -1.7465580000000e+00\r\n3001 3003 -2.3118823000000e+02\r\n3002 3003  3.5596443000000e+01\r\n3003 3003  1.2297642000000e+01\r\n3004 3003  1.9706825000000e+01\r\n3005 3003 -3.1921367000000e+00\r\n3006 3003 -2.2050628000000e+00\r\n3051 3003 -2.0092868000000e+00\r\n1900 3004 -1.4516712000000e-03\r\n1902 3004 -1.5150297000000e-05\r\n2956 3004 -1.4127870000000e-01\r\n2958 3004 -1.0380879000000e-05\r\n3001 3004 -8.6668972000000e-04\r\n3003 3004 -9.0451660000000e-06\r\n3004 3004  2.3981230000000e+02\r\n3006 3004  6.0661304000000e-04\r\n3007 3004 -7.7472854000000e-02\r\n3009 3004 -1.1193885000000e-05\r\n1900 3005  2.1898569000000e+00\r\n1902 3005 -2.1132209000000e+00\r\n2956 3005  7.2084319000000e+00\r\n2958 3005 -1.4527757000000e+00\r\n3003 3005 -1.3044628000000e+00\r\n3004 3005 -1.5184615000000e+02\r\n3005 3005 -4.5756514000000e+01\r\n3006 3005  6.4422035000000e+00\r\n3007 3005  4.8956587000000e+00\r\n3009 3005 -1.5665916000000e+00\r\n1900 3006  3.7017341000000e+00\r\n1901 3006 -5.9959884000000e-01\r\n1902 3006 -3.5721885000000e+00\r\n2956 3006  1.2185133000000e+01\r\n2957 3006 -1.9737214000000e+00\r\n2958 3006 -2.4557720000000e+00\r\n3003 3006 -2.2050628000000e+00\r\n3004 3006 -2.5668073000000e+02\r\n3005 3006  3.9333292000000e+01\r\n3006 3006  1.0889900000000e+01\r\n3007 3006  8.2756215000000e+00\r\n3008 3006 -1.3404672000000e+00\r\n3009 3006 -2.6481665000000e+00\r\n1903 3007 -1.2276692000000e-03\r\n1905 3007 -1.2812511000000e-05\r\n2959 3007 -1.4085507000000e-01\r\n2961 3007 -1.2514388000000e-05\r\n3004 3007 -1.0725757000000e-03\r\n3006 3007 -1.1193885000000e-05\r\n3007 3007  2.8648462000000e+02\r\n3009 3007  7.0680430000000e-04\r\n1903 3008  2.1925545000000e+00\r\n1905 3008 -1.7673253000000e+00\r\n2959 3008  5.8715541000000e+00\r\n2961 3008 -1.7332974000000e+00\r\n3006 3008 -1.5665916000000e+00\r\n3007 3008 -1.7245683000000e+02\r\n3008 3008 -5.4683742000000e+01\r\n3009 3008  5.0733718000000e+00\r\n1903 3009  3.7062920000000e+00\r\n1904 3009 -6.0033301000000e-01\r\n1905 3009 -2.9874848000000e+00\r\n2959 3009  9.9252692000000e+00\r\n2960 3009 -1.6076626000000e+00\r\n2961 3009 -2.9299642000000e+00\r\n3006 3009 -2.6481665000000e+00\r\n3007 3009 -2.9152085000000e+02\r\n3008 3009  4.4540689000000e+01\r\n3009 3009  8.5760242000000e+00\r\n3010 3010  1.0000000000000e+00\r\n3011 3011  1.0000000000000e+00\r\n3012 3012  1.0000000000000e+00\r\n3013 3013  1.0000000000000e+00\r\n3014 3014  1.0000000000000e+00\r\n3015 3015  1.0000000000000e+00\r\n3016 3016  1.0000000000000e+00\r\n3017 3017  1.0000000000000e+00\r\n3018 3018  1.0000000000000e+00\r\n3019 3019  1.0000000000000e+00\r\n3020 3020  1.0000000000000e+00\r\n3021 3021  1.0000000000000e+00\r\n3022 3022  1.0000000000000e+00\r\n3023 3023  1.0000000000000e+00\r\n3024 3024  1.0000000000000e+00\r\n3025 3025  1.0000000000000e+00\r\n3026 3026  1.0000000000000e+00\r\n3027 3027  1.0000000000000e+00\r\n1924 3028 -1.6115242000000e-03\r\n1926 3028 -1.6818596000000e-05\r\n2980 3028 -5.9133870000000e-04\r\n2982 3028 -6.1714783000000e-06\r\n3028 3028  1.7538712000000e+02\r\n3030 3028  4.4563921000000e-04\r\n3031 3028 -5.9091291000000e-04\r\n3033 3028 -6.1670345000000e-06\r\n3076 3028 -9.5763281000000e-03\r\n3078 3028 -6.1369889000000e-06\r\n1924 3029  2.9148652000000e-01\r\n1926 3029 -2.8811403000000e+00\r\n2980 3029  1.4767022000000e+00\r\n2982 3029 -1.0515702000000e+00\r\n3028 3029 -1.0423432000000e+02\r\n3029 3029 -3.3421480000000e+01\r\n3030 3029  6.0380010000000e+00\r\n3031 3029  1.7347769000000e+00\r\n3033 3029 -1.0499448000000e+00\r\n3078 3029 -1.0516017000000e+00\r\n1924 3030  4.9272882000000e-01\r\n1925 3030 -7.9821473000000e-02\r\n1926 3030 -4.8702796000000e+00\r\n2980 3030  2.4962175000000e+00\r\n2981 3030 -4.0438421000000e-01\r\n2982 3030 -1.7775743000000e+00\r\n3028 3030 -1.7619769000000e+02\r\n3029 3030  2.7047472000000e+01\r\n3030 3030  1.0206637000000e+01\r\n3031 3030  2.9324669000000e+00\r\n3032 3030 -4.7505609000000e-01\r\n3033 3030 -1.7748266000000e+00\r\n3078 3030 -1.7776276000000e+00\r\n1927 3031 -1.6258747000000e-03\r\n1929 3031 -1.6968364000000e-05\r\n2983 3031 -5.6709193000000e-04\r\n2985 3031 -5.9184280000000e-06\r\n3028 3031 -8.6361060000000e-03\r\n3030 3031 -6.1670345000000e-06\r\n3031 3031  1.7538214000000e+02\r\n3033 3031  4.5119202000000e-04\r\n3034 3031 -5.4331590000000e-04\r\n3036 3031 -5.6702906000000e-06\r\n3079 3031 -5.8681485000000e-04\r\n3081 3031 -6.1242653000000e-06\r\n1927 3032  2.7089122000000e-01\r\n1929 3032 -2.8880003000000e+00\r\n2983 3032  2.8009460000000e+00\r\n2985 3032 -9.9605394000000e-01\r\n3030 3032 -1.0499448000000e+00\r\n3031 3032 -1.0664585000000e+02\r\n3032 3032 -3.3425726000000e+01\r\n3033 3032  6.9433508000000e+00\r\n3034 3032  2.8484679000000e+00\r\n3036 3032 -9.5388098000000e-01\r\n3081 3032 -1.0517250000000e+00\r\n1927 3033  4.5791421000000e-01\r\n1928 3033 -7.4181320000000e-02\r\n1929 3033 -4.8818723000000e+00\r\n2983 3033  4.7347159000000e+00\r\n2984 3033 -7.6701587000000e-01\r\n2985 3033 -1.6837284000000e+00\r\n3030 3033 -1.7748266000000e+00\r\n3031 3033 -1.8027402000000e+02\r\n3032 3033  2.7697435000000e+01\r\n3033 3033  1.1737033000000e+01\r\n3034 3033  4.8150467000000e+00\r\n3035 3033 -7.8002927000000e-01\r\n3036 3033 -1.6124393000000e+00\r\n3081 3033 -1.7778344000000e+00\r\n1930 3034 -1.9728916000000e-03\r\n1932 3034 -2.0589990000000e-05\r\n2986 3034 -1.3010801000000e-02\r\n2988 3034 -5.1031967000000e-06\r\n3031 3034 -2.8402342000000e-02\r\n3033 3034 -5.6702906000000e-06\r\n3034 3034  1.4617753000000e+02\r\n3036 3034  3.8329670000000e-04\r\n3037 3034 -4.6348563000000e-04\r\n3039 3034 -4.8371457000000e-06\r\n3082 3034 -4.9312692000000e-04\r\n3084 3034 -5.1464957000000e-06\r\n1930 3035  2.6262155000000e-01\r\n1932 3035 -3.4633279000000e+00\r\n2986 3035  3.0645876000000e+00\r\n2988 3035 -8.5858568000000e-01\r\n3033 3035 -9.5388098000000e-01\r\n3034 3035 -9.0982103000000e+01\r\n3035 3035 -2.7862876000000e+01\r\n3036 3035  6.9542530000000e+00\r\n3037 3035  3.7281401000000e+00\r\n3039 3035 -7.9895138000000e-01\r\n3084 3035 -8.7638198000000e-01\r\n1930 3036  4.4393547000000e-01\r\n1931 3036 -7.1916234000000e-02\r\n1932 3036 -5.8544095000000e+00\r\n2986 3036  5.1803789000000e+00\r\n2987 3036 -8.3920606000000e-01\r\n2988 3036 -1.4513532000000e+00\r\n3033 3036 -1.6124393000000e+00\r\n3034 3036 -1.5379615000000e+02\r\n3035 3036  2.3639133000000e+01\r\n3036 3036  1.1755468000000e+01\r\n3037 3036  6.3020480000000e+00\r\n3038 3036 -1.0209131000000e+00\r\n3039 3036 -1.3505474000000e+00\r\n3084 3036 -1.4814361000000e+00\r\n1933 3037 -2.3929774000000e-03\r\n1935 3037 -2.4974195000000e-05\r\n2989 3037 -1.7678043000000e-02\r\n2991 3037 -4.3482484000000e-06\r\n3034 3037 -6.3985924000000e-04\r\n3036 3037 -4.8371457000000e-06\r\n3037 3037  1.2277994000000e+02\r\n3039 3037  3.3012322000000e-04\r\n3040 3037 -1.3774656000000e-02\r\n3042 3037 -4.3414042000000e-06\r\n3085 3037 -4.2021413000000e-04\r\n3087 3037 -4.3855448000000e-06\r\n1933 3038  2.4566396000000e-01\r\n1935 3038 -4.1247997000000e+00\r\n2989 3038  3.2319114000000e+00\r\n2991 3038 -7.1828335000000e-01\r\n3036 3038 -7.9895138000000e-01\r\n3037 3038 -7.8539113000000e+01\r\n3038 3038 -2.3411151000000e+01\r\n3039 3038  7.0979949000000e+00\r\n3040 3038  4.5718862000000e+00\r\n3042 3038 -7.1717987000000e-01\r\n3087 3038 -7.3615276000000e-01\r\n1933 3039  4.1527015000000e-01\r\n1934 3039 -6.7271826000000e-02\r\n1935 3039 -6.9725578000000e+00\r\n2989 3039  5.4632203000000e+00\r\n2990 3039 -8.8501622000000e-01\r\n2991 3039 -1.2141856000000e+00\r\n3036 3039 -1.3505474000000e+00\r\n3037 3039 -1.3276245000000e+02\r\n3038 3039  2.0420065000000e+01\r\n3039 3039  1.1998445000000e+01\r\n3040 3039  7.7283124000000e+00\r\n3041 3039 -1.2519506000000e+00\r\n3042 3039 -1.2123202000000e+00\r\n3087 3039 -1.2443918000000e+00\r\n1936 3040 -2.5759938000000e-03\r\n1938 3040 -2.6884237000000e-05\r\n2992 3040 -2.9847192000000e-02\r\n2994 3040 -4.3515740000000e-06\r\n3037 3040 -4.1598466000000e-04\r\n3039 3040 -4.3414042000000e-06\r\n3040 3040  1.1694874000000e+02\r\n3042 3040  3.1784780000000e-04\r\n3043 3040 -2.2480601000000e-02\r\n3045 3040 -4.4513079000000e-06\r\n3088 3040 -4.0819198000000e-04\r\n3090 3040 -4.2600762000000e-06\r\n1936 3041  2.5344182000000e-01\r\n1938 3041 -4.3324235000000e+00\r\n2992 3041  3.9093144000000e+00\r\n2994 3041 -7.0136448000000e-01\r\n3039 3041 -7.1717987000000e-01\r\n3040 3041 -7.6761331000000e+01\r\n3041 3041 -2.2302868000000e+01\r\n3042 3041  7.1720149000000e+00\r\n3043 3041  5.4747474000000e+00\r\n3045 3041 -7.1747312000000e-01\r\n3090 3041 -7.0106833000000e-01\r\n1936 3042  4.2841805000000e-01\r\n1937 3042 -6.9400666000000e-02\r\n1938 3042 -7.3235287000000e+00\r\n2992 3042  6.6083050000000e+00\r\n2993 3042 -1.0704982000000e+00\r\n2994 3042 -1.1855865000000e+00\r\n3039 3042 -1.2123202000000e+00\r\n3040 3042 -1.2975735000000e+02\r\n3041 3042  1.9968614000000e+01\r\n3042 3042  1.2123573000000e+01\r\n3043 3042  9.2545130000000e+00\r\n3044 3042 -1.4991650000000e+00\r\n3045 3042 -1.2128166000000e+00\r\n3090 3042 -1.1850859000000e+00\r\n1939 3043 -2.5229950000000e-03\r\n1941 3043 -2.6331117000000e-05\r\n2995 3043 -4.3417094000000e-02\r\n2997 3043 -4.7055193000000e-06\r\n3040 3043 -4.2651542000000e-04\r\n3042 3043 -4.4513079000000e-06\r\n3043 3043  1.2281008000000e+02\r\n3045 3043  3.3250862000000e-04\r\n3046 3043 -3.3660399000000e-02\r\n3048 3043 -5.1997375000000e-06\r\n3091 3043 -4.3909792000000e-04\r\n3093 3043 -4.5826245000000e-06\r\n1939 3044  3.3584186000000e-01\r\n1941 3044 -4.1223643000000e+00\r\n2995 3044  4.9387264000000e+00\r\n2997 3044 -7.3677436000000e-01\r\n3042 3044 -7.1747312000000e-01\r\n3043 3044 -8.2076518000000e+01\r\n3044 3044 -2.3425410000000e+01\r\n3045 3044  7.1290006000000e+00\r\n3046 3044  6.3323798000000e+00\r\n3048 3044 -8.1418837000000e-01\r\n3093 3044 -7.3556628000000e-01\r\n1939 3045  5.6770671000000e-01\r\n1940 3045 -9.1962831000000e-02\r\n1941 3045 -6.9684400000000e+00\r\n2995 3045  8.3484175000000e+00\r\n2996 3045 -1.3523605000000e+00\r\n2997 3045 -1.2454426000000e+00\r\n3042 3045 -1.2128166000000e+00\r\n3043 3045 -1.3874205000000e+02\r\n3044 3045  2.1352934000000e+01\r\n3045 3045  1.2050855000000e+01\r\n3046 3045  1.0704248000000e+01\r\n3047 3045 -1.7339814000000e+00\r\n3048 3045 -1.3763031000000e+00\r\n3093 3045 -1.2434005000000e+00\r\n1942 3046 -2.0993909000000e-03\r\n1944 3046 -2.1910194000000e-05\r\n2998 3046 -7.2043370000000e-02\r\n3000 3046 -5.9875571000000e-06\r\n3043 3046 -4.9822845000000e-04\r\n3045 3046 -5.1997375000000e-06\r\n3046 3046  1.5203491000000e+02\r\n3048 3046  4.0139243000000e-04\r\n3049 3046 -1.7673544000000e-02\r\n3051 3046 -6.7841610000000e-06\r\n3094 3046 -5.6341016000000e-04\r\n3096 3046 -5.8800034000000e-06\r\n1942 3047  5.1172148000000e-01\r\n1944 3047 -3.3342396000000e+00\r\n2998 3047  7.0358413000000e+00\r\n3000 3047 -9.1161978000000e-01\r\n3045 3047 -8.1418837000000e-01\r\n3046 3047 -9.9703530000000e+01\r\n3047 3047 -2.9011120000000e+01\r\n3048 3047  7.0073651000000e+00\r\n3049 3047  4.9196764000000e+00\r\n3051 3047 -1.0329272000000e+00\r\n3096 3047 -9.1112511000000e-01\r\n1942 3048  8.6501399000000e-01\r\n1943 3048 -1.4012105000000e-01\r\n1944 3048 -5.6361987000000e+00\r\n2998 3048  1.1893386000000e+01\r\n2999 3048 -1.9265743000000e+00\r\n3000 3048 -1.5410021000000e+00\r\n3045 3048 -1.3763031000000e+00\r\n3046 3048 -1.6853885000000e+02\r\n3047 3048  2.5891734000000e+01\r\n3048 3048  1.1845249000000e+01\r\n3049 3048  8.3162210000000e+00\r\n3050 3048 -1.3471200000000e+00\r\n3051 3048 -1.7460601000000e+00\r\n3096 3048 -1.5401659000000e+00\r\n1945 3049 -1.6332782000000e-03\r\n1947 3049 -1.7045630000000e-05\r\n3001 3049 -2.1583579000000e-01\r\n3003 3049 -7.9380892000000e-06\r\n3046 3049 -6.5004474000000e-04\r\n3048 3049 -6.7841610000000e-06\r\n3049 3049  1.9890370000000e+02\r\n3051 3049  5.0451300000000e-04\r\n3097 3049 -7.3674286000000e-04\r\n3099 3049 -7.6889818000000e-06\r\n1945 3050  6.5701978000000e-01\r\n1947 3050 -2.5502210000000e+00\r\n3001 3050  1.2586195000000e+01\r\n3003 3050 -1.1886468000000e+00\r\n3048 3050 -1.0329272000000e+00\r\n3049 3050 -1.2731025000000e+02\r\n3050 3050 -3.7945497000000e+01\r\n3051 3050  5.9488665000000e+00\r\n3099 3050 -1.1727986000000e+00\r\n1945 3051  1.1106253000000e+00\r\n1946 3051 -1.7990509000000e-01\r\n1947 3051 -4.3108899000000e+00\r\n3001 3051  2.1275686000000e+01\r\n3002 3051 -3.4463504000000e+00\r\n3003 3051 -2.0092868000000e+00\r\n3048 3051 -1.7460601000000e+00\r\n3049 3051 -2.1520507000000e+02\r\n3050 3051  3.2997687000000e+01\r\n3051 3051  1.0055958000000e+01\r\n3099 3051 -1.9824976000000e+00\r\n3052 3052  1.0000000000000e+00\r\n3053 3053  1.0000000000000e+00\r\n3054 3054  1.0000000000000e+00\r\n3055 3055  1.0000000000000e+00\r\n3056 3056  1.0000000000000e+00\r\n3057 3057  1.0000000000000e+00\r\n3058 3058  1.0000000000000e+00\r\n3059 3059  1.0000000000000e+00\r\n3060 3060  1.0000000000000e+00\r\n3061 3061  1.0000000000000e+00\r\n3062 3062  1.0000000000000e+00\r\n3063 3063  1.0000000000000e+00\r\n3064 3064  1.0000000000000e+00\r\n3065 3065  1.0000000000000e+00\r\n3066 3066  1.0000000000000e+00\r\n3067 3067  1.0000000000000e+00\r\n3068 3068  1.0000000000000e+00\r\n3069 3069  1.0000000000000e+00\r\n3070 3070  1.0000000000000e+00\r\n3071 3071  1.0000000000000e+00\r\n3072 3072  1.0000000000000e+00\r\n3073 3073  1.0000000000000e+00\r\n3074 3074  1.0000000000000e+00\r\n3075 3075  1.0000000000000e+00\r\n1972 3076 -1.6016700000000e-03\r\n1974 3076 -1.6715752000000e-05\r\n3028 3076 -5.8803400000000e-04\r\n3030 3076 -6.1369889000000e-06\r\n3076 3076  1.7538637000000e+02\r\n3078 3076  4.4541420000000e-04\r\n3079 3076 -5.8597202000000e-04\r\n3081 3076 -6.1154691000000e-06\r\n3124 3076 -4.3665739000000e-03\r\n3126 3076 -6.0994334000000e-06\r\n1972 3077  2.9235146000000e-01\r\n1974 3077 -2.8815324000000e+00\r\n3028 3077  1.6458959000000e+00\r\n3030 3077 -1.0516017000000e+00\r\n3076 3077 -1.0373450000000e+02\r\n3077 3077 -3.3417286000000e+01\r\n3078 3077  6.0387736000000e+00\r\n3079 3077  1.0591455000000e+00\r\n3081 3077 -1.0501400000000e+00\r\n3126 3077 -1.0517574000000e+00\r\n1972 3078  4.9419092000000e-01\r\n1973 3078 -8.0058621000000e-02\r\n1974 3078 -4.8709424000000e+00\r\n3028 3078  2.7822224000000e+00\r\n3029 3078 -4.5071831000000e-01\r\n3030 3078 -1.7776276000000e+00\r\n3076 3078 -1.7535280000000e+02\r\n3077 3078  2.6920936000000e+01\r\n3078 3078  1.0207943000000e+01\r\n3079 3078  1.7903796000000e+00\r\n3080 3078 -2.9004039000000e-01\r\n3081 3078 -1.7751567000000e+00\r\n3126 3078 -1.7778907000000e+00\r\n1975 3079 -1.6101520000000e-03\r\n1977 3079 -1.6804275000000e-05\r\n3031 3079 -8.7696541000000e-03\r\n3033 3079 -6.1242653000000e-06\r\n3076 3079 -2.5780045000000e-02\r\n3078 3079 -6.1154691000000e-06\r\n3079 3079  1.7541622000000e+02\r\n3081 3079  4.5101433000000e-04\r\n3082 3079 -5.3715474000000e-04\r\n3084 3079 -5.6059899000000e-06\r\n3127 3079 -5.8534991000000e-03\r\n3129 3079 -6.0209255000000e-06\r\n1975 3080  2.7282565000000e-01\r\n1977 3080 -2.8857599000000e+00\r\n3031 3080  2.3230251000000e+00\r\n3033 3080 -1.0517250000000e+00\r\n3078 3080 -1.0501400000000e+00\r\n3079 3080 -1.0539655000000e+02\r\n3080 3080 -3.3422495000000e+01\r\n3081 3080  6.9798114000000e+00\r\n3082 3080  2.0706710000000e+00\r\n3084 3080 -9.5452483000000e-01\r\n3129 3080 -1.0339173000000e+00\r\n1975 3081  4.6118410000000e-01\r\n1976 3081 -7.4711409000000e-02\r\n1977 3081 -4.8780844000000e+00\r\n3031 3081  3.9268383000000e+00\r\n3032 3081 -6.3614422000000e-01\r\n3033 3081 -1.7778344000000e+00\r\n3078 3081 -1.7751567000000e+00\r\n3079 3081 -1.7816218000000e+02\r\n3080 3081  2.7363394000000e+01\r\n3081 3081  1.1798665000000e+01\r\n3082 3081  3.5002593000000e+00\r\n3083 3081 -5.6703886000000e-01\r\n3084 3081 -1.6135274000000e+00\r\n3129 3081 -1.7477327000000e+00\r\n1978 3082 -1.9480962000000e-03\r\n1980 3082 -2.0331213000000e-05\r\n3034 3082 -6.0100663000000e-03\r\n3036 3082 -5.1464957000000e-06\r\n3079 3082 -2.7000336000000e-02\r\n3081 3082 -5.6059899000000e-06\r\n3082 3082  1.4617357000000e+02\r\n3084 3082  3.8278450000000e-04\r\n3085 3082 -4.5616848000000e-04\r\n3087 3082 -4.7607806000000e-06\r\n3130 3082 -4.7816925000000e-04\r\n3132 3082 -4.9903907000000e-06\r\n1978 3083  2.6258576000000e-01\r\n1980 3083 -3.4613003000000e+00\r\n3034 3083  2.6515217000000e+00\r\n3036 3083 -8.7638198000000e-01\r\n3081 3083 -9.5452483000000e-01\r\n3082 3083 -8.9727004000000e+01\r\n3083 3083 -2.7858703000000e+01\r\n3084 3083  6.9529221000000e+00\r\n3085 3083  2.8803403000000e+00\r\n3087 3083 -7.9904805000000e-01\r\n3132 3083 -8.5854366000000e-01\r\n1978 3084  4.4387497000000e-01\r\n1979 3084 -7.1906941000000e-02\r\n1980 3084 -5.8509821000000e+00\r\n3034 3084  4.4821323000000e+00\r\n3035 3084 -7.2609731000000e-01\r\n3036 3084 -1.4814361000000e+00\r\n3081 3084 -1.6135274000000e+00\r\n3082 3084 -1.5167453000000e+02\r\n3083 3084  2.3305832000000e+01\r\n3084 3084  1.1753218000000e+01\r\n3085 3084  4.8689272000000e+00\r\n3086 3084 -7.8875738000000e-01\r\n3087 3084 -1.3507108000000e+00\r\n3132 3084 -1.4512822000000e+00\r\n1981 3085 -2.3544364000000e-03\r\n1983 3085 -2.4571963000000e-05\r\n3037 3085 -9.3922807000000e-03\r\n3039 3085 -4.3855448000000e-06\r\n3082 3085 -5.3424284000000e-03\r\n3084 3085 -4.7607806000000e-06\r\n3085 3085  1.2277133000000e+02\r\n3087 3085  3.2944068000000e-04\r\n3088 3085 -4.0755025000000e-03\r\n3090 3085 -4.2696781000000e-06\r\n3133 3085 -4.0399608000000e-04\r\n3135 3085 -4.2162858000000e-06\r\n1981 3086  2.4204843000000e-01\r\n1983 3086 -4.1229794000000e+00\r\n3037 3086  3.0086929000000e+00\r\n3039 3086 -7.3615276000000e-01\r\n3084 3086 -7.9904805000000e-01\r\n3085 3086 -7.7362189000000e+01\r\n3086 3086 -2.3406774000000e+01\r\n3087 3086  7.0957632000000e+00\r\n3088 3086  3.6156603000000e+00\r\n3090 3086 -7.1672088000000e-01\r\n3135 3086 -7.1823623000000e-01\r\n1981 3087  4.0915839000000e-01\r\n1982 3087 -6.6282403000000e-02\r\n1983 3087 -6.9694796000000e+00\r\n3037 3087  5.0858910000000e+00\r\n3038 3087 -8.2389872000000e-01\r\n3039 3087 -1.2443918000000e+00\r\n3084 3087 -1.3507108000000e+00\r\n3085 3087 -1.3077296000000e+02\r\n3086 3087  2.0108738000000e+01\r\n3087 3087  1.1994671000000e+01\r\n3088 3087  6.1119084000000e+00\r\n3089 3087 -9.9011034000000e-01\r\n3090 3087 -1.2115442000000e+00\r\n3135 3087 -1.2141058000000e+00\r\n1984 3088 -2.5253548000000e-03\r\n1986 3088 -2.6355745000000e-05\r\n3040 3088 -1.8423678000000e-02\r\n3042 3088 -4.2600762000000e-06\r\n3085 3088 -4.0911202000000e-04\r\n3087 3088 -4.2696781000000e-06\r\n3088 3088  1.1692724000000e+02\r\n3090 3088  3.1697125000000e-04\r\n3091 3088 -7.4196533000000e-03\r\n3093 3088 -4.3598154000000e-06\r\n3136 3088 -3.9935147000000e-04\r\n3138 3088 -4.1678126000000e-06\r\n1984 3089  2.3972266000000e-01\r\n1986 3089 -4.3366092000000e+00\r\n3040 3089  3.7977394000000e+00\r\n3042 3089 -7.0106833000000e-01\r\n3087 3089 -7.1672088000000e-01\r\n3088 3089 -7.5851741000000e+01\r\n3089 3089 -2.2298205000000e+01\r\n3090 3089  7.1752949000000e+00\r\n3091 3089  4.6838793000000e+00\r\n3093 3089 -7.1750870000000e-01\r\n3138 3089 -7.0088425000000e-01\r\n1984 3090  4.0522718000000e-01\r\n1985 3090 -6.5644740000000e-02\r\n1986 3090 -7.3306042000000e+00\r\n3040 3090  6.4196986000000e+00\r\n3041 3090 -1.0399585000000e+00\r\n3042 3090 -1.1850859000000e+00\r\n3087 3090 -1.2115442000000e+00\r\n3088 3090 -1.2821978000000e+02\r\n3089 3090  1.9731273000000e+01\r\n3090 3090  1.2129118000000e+01\r\n3091 3090  7.9176295000000e+00\r\n3092 3090 -1.2826157000000e+00\r\n3093 3090 -1.2128767000000e+00\r\n3138 3090 -1.1847747000000e+00\r\n1987 3091 -2.4642846000000e-03\r\n1989 3091 -2.5718390000000e-05\r\n3043 3091 -3.4769833000000e-02\r\n3045 3091 -4.5826245000000e-06\r\n3088 3091 -4.1774879000000e-04\r\n3090 3091 -4.3598154000000e-06\r\n3091 3091  1.2283951000000e+02\r\n3093 3091  3.3150008000000e-04\r\n3094 3091 -6.7005388000000e-02\r\n3096 3091 -5.0763157000000e-06\r\n3139 3091 -4.3380501000000e-04\r\n3141 3091 -4.5273854000000e-06\r\n1987 3092  2.8433118000000e-01\r\n1989 3092 -4.1274186000000e+00\r\n3043 3092  4.7955485000000e+00\r\n3045 3092 -7.3556628000000e-01\r\n3090 3092 -7.1750870000000e-01\r\n3091 3092 -8.3210913000000e+01\r\n3092 3092 -2.3421014000000e+01\r\n3093 3092  7.1502657000000e+00\r\n3094 3092  7.6551978000000e+00\r\n3096 3092 -8.1481601000000e-01\r\n3141 3092 -7.5232399000000e-01\r\n1987 3093  4.8063314000000e-01\r\n1988 3093 -7.7858981000000e-02\r\n1989 3093 -6.9769843000000e+00\r\n3043 3093  8.1063905000000e+00\r\n3044 3093 -1.3131747000000e+00\r\n3045 3093 -1.2434005000000e+00\r\n3090 3093 -1.2128767000000e+00\r\n3091 3093 -1.4065965000000e+02\r\n3092 3093  2.1674765000000e+01\r\n3093 3093  1.2086803000000e+01\r\n3094 3093  1.2940339000000e+01\r\n3095 3093 -2.0962386000000e+00\r\n3096 3093 -1.3773642000000e+00\r\n3141 3093 -1.2717276000000e+00\r\n1990 3094 -2.0595097000000e-03\r\n1992 3094 -2.1493975000000e-05\r\n3046 3094 -5.8206311000000e-03\r\n3048 3094 -5.8800034000000e-06\r\n3091 3094 -4.8640242000000e-04\r\n3093 3094 -5.0763157000000e-06\r\n3094 3094  1.5197500000000e+02\r\n3096 3094  3.9466216000000e-04\r\n3097 3094 -1.6491555000000e-02\r\n3099 3094 -6.5805009000000e-06\r\n1990 3095  3.8066337000000e-01\r\n1992 3095 -3.3292502000000e+00\r\n3046 3095  4.4665247000000e+00\r\n3048 3095 -9.1112511000000e-01\r\n3093 3095 -8.1481601000000e-01\r\n3094 3095 -9.6579452000000e+01\r\n3095 3095 -2.9003616000000e+01\r\n3096 3095  6.0781023000000e+00\r\n3097 3095  4.4853469000000e+00\r\n3099 3095 -1.0196493000000e+00\r\n1990 3096  6.4347336000000e-01\r\n1991 3096 -1.0423552000000e-01\r\n1992 3096 -5.6277646000000e+00\r\n3046 3096  7.5502134000000e+00\r\n3047 3096 -1.2230505000000e+00\r\n3048 3096 -1.5401659000000e+00\r\n3093 3096 -1.3773642000000e+00\r\n3094 3096 -1.6325790000000e+02\r\n3095 3096  2.5055078000000e+01\r\n3096 3096  1.0274423000000e+01\r\n3097 3096  7.5820305000000e+00\r\n3098 3096 -1.2282045000000e+00\r\n3099 3096 -1.7236152000000e+00\r\n1993 3097 -1.6513683000000e-03\r\n1995 3097 -1.7234427000000e-05\r\n3049 3097 -8.5913082000000e-03\r\n3051 3097 -7.6889818000000e-06\r\n3094 3097 -6.3053043000000e-04\r\n3096 3097 -6.5805009000000e-06\r\n3097 3097  1.9286305000000e+02\r\n3099 3097  4.8288283000000e-04\r\n1993 3098  4.3902760000000e-01\r\n1995 3098 -2.6270897000000e+00\r\n3049 3098  6.1762049000000e+00\r\n3051 3098 -1.1727986000000e+00\r\n3096 3098 -1.0196493000000e+00\r\n3097 3098 -1.1734177000000e+02\r\n3098 3098 -3.6819304000000e+01\r\n3099 3098  4.8236805000000e+00\r\n1993 3099  7.4213181000000e-01\r\n1994 3099 -1.2021593000000e-01\r\n1995 3099 -4.4408299000000e+00\r\n3049 3099  1.0440251000000e+01\r\n3050 3099 -1.6911879000000e+00\r\n3051 3099 -1.9824976000000e+00\r\n3096 3099 -1.7236152000000e+00\r\n3097 3099 -1.9835441000000e+02\r\n3098 3099  3.0348281000000e+01\r\n3099 3099  8.1539458000000e+00\r\n3100 3100  1.0000000000000e+00\r\n3101 3101  1.0000000000000e+00\r\n3102 3102  1.0000000000000e+00\r\n3103 3103  1.0000000000000e+00\r\n3104 3104  1.0000000000000e+00\r\n3105 3105  1.0000000000000e+00\r\n3106 3106  1.0000000000000e+00\r\n3107 3107  1.0000000000000e+00\r\n3108 3108  1.0000000000000e+00\r\n3109 3109  1.0000000000000e+00\r\n3110 3110  1.0000000000000e+00\r\n3111 3111  1.0000000000000e+00\r\n3112 3112  1.0000000000000e+00\r\n3113 3113  1.0000000000000e+00\r\n3114 3114  1.0000000000000e+00\r\n3115 3115  1.0000000000000e+00\r\n3116 3116  1.0000000000000e+00\r\n3117 3117  1.0000000000000e+00\r\n3118 3118  1.0000000000000e+00\r\n3119 3119  1.0000000000000e+00\r\n3120 3120  1.0000000000000e+00\r\n3121 3121  1.0000000000000e+00\r\n3122 3122  1.0000000000000e+00\r\n3123 3123  1.0000000000000e+00\r\n2020 3124 -1.5936846000000e-03\r\n2022 3124 -1.6632414000000e-05\r\n3076 3124 -5.8443551000000e-04\r\n3078 3124 -6.0994334000000e-06\r\n3124 3124  1.7538475000000e+02\r\n3126 3124  4.3905139000000e-04\r\n3127 3124 -5.7225107000000e-04\r\n3129 3124 -5.9722711000000e-06\r\n2020 3125  2.8891914000000e-01\r\n2022 3125 -2.8799247000000e+00\r\n3076 3125  1.1461200000000e+00\r\n3078 3125 -1.0517574000000e+00\r\n3124 3125 -1.0259257000000e+02\r\n3125 3125 -3.3414684000000e+01\r\n3126 3125  4.9679571000000e+00\r\n3127 3125  4.1685342000000e-01\r\n3129 3125 -1.0325340000000e+00\r\n2020 3126  4.8838892000000e-01\r\n2021 3126 -7.9118903000000e-02\r\n2022 3126 -4.8682248000000e+00\r\n3076 3126  1.9374013000000e+00\r\n3077 3126 -3.1385861000000e-01\r\n3078 3126 -1.7778907000000e+00\r\n3124 3126 -1.7342248000000e+02\r\n3125 3126  2.6614646000000e+01\r\n3126 3126  8.3978347000000e+00\r\n3127 3126  7.0464903000000e-01\r\n3128 3126 -1.1415300000000e-01\r\n3129 3126 -1.7453955000000e+00\r\n2023 3127 -1.6534664000000e-03\r\n2025 3127 -1.7256323000000e-05\r\n3079 3127 -5.7691304000000e-04\r\n3081 3127 -6.0209255000000e-06\r\n3124 3127 -2.3788469000000e-02\r\n3126 3127 -5.9722711000000e-06\r\n3127 3127  1.6955904000000e+02\r\n3129 3127  4.3679250000000e-04\r\n3130 3127 -5.1198579000000e-04\r\n3132 3127 -5.3433153000000e-06\r\n3175 3127 -5.3019016000000e-04\r\n3177 3127 -5.5333043000000e-06\r\n2023 3128  2.6840621000000e-01\r\n2025 3128 -2.9837693000000e+00\r\n3079 3128  1.7520136000000e+00\r\n3081 3128 -1.0339173000000e+00\r\n3126 3128 -1.0325340000000e+00\r\n3127 3128 -1.0061618000000e+02\r\n3128 3128 -3.2304568000000e+01\r\n3129 3128  6.9340649000000e+00\r\n3130 3128  1.2181112000000e+00\r\n3132 3128 -9.1916787000000e-01\r\n3177 3128 -9.6105850000000e-01\r\n2023 3129  4.5371354000000e-01\r\n2024 3129 -7.3501466000000e-02\r\n2025 3129 -5.0437600000000e+00\r\n3079 3129  2.9616017000000e+00\r\n3080 3129 -4.7977864000000e-01\r\n3081 3129 -1.7477327000000e+00\r\n3126 3129 -1.7453955000000e+00\r\n3127 3129 -1.7008148000000e+02\r\n3128 3129  2.6113754000000e+01\r\n3129 3129  1.1721336000000e+01\r\n3130 3129  2.0590938000000e+00\r\n3131 3129 -3.3357259000000e-01\r\n3132 3129 -1.5537603000000e+00\r\n3177 3129 -1.6245722000000e+00\r\n2026 3130 -2.0081412000000e-03\r\n2028 3130 -2.0957870000000e-05\r\n3082 3130 -3.4615309000000e-03\r\n3084 3130 -4.9903907000000e-06\r\n3127 3130 -3.3882048000000e-02\r\n3129 3130 -5.3433153000000e-06\r\n3130 3130  1.4033621000000e+02\r\n3132 3130  3.6857606000000e-04\r\n3133 3130 -4.2975731000000e-04\r\n3135 3130 -4.4851417000000e-06\r\n3178 3130 -4.3381469000000e-04\r\n3180 3130 -4.5274864000000e-06\r\n2026 3131  2.5495473000000e-01\r\n2028 3131 -3.6047923000000e+00\r\n3082 3131  2.1794546000000e+00\r\n3084 3131 -8.5854366000000e-01\r\n3129 3131 -9.1916787000000e-01\r\n3130 3131 -8.4868844000000e+01\r\n3131 3131 -2.6740796000000e+01\r\n3132 3131  6.9347739000000e+00\r\n3133 3131  1.8542489000000e+00\r\n3135 3131 -7.6395798000000e-01\r\n3180 3131 -7.8531531000000e-01\r\n2026 3132  4.3097547000000e-01\r\n2027 3132 -6.9817658000000e-02\r\n2028 3132 -6.0935410000000e+00\r\n3082 3132  3.6841500000000e+00\r\n3083 3132 -5.9682916000000e-01\r\n3084 3132 -1.4512822000000e+00\r\n3129 3132 -1.5537603000000e+00\r\n3130 3132 -1.4346229000000e+02\r\n3131 3132  2.2034918000000e+01\r\n3132 3132  1.1722541000000e+01\r\n3133 3132  3.1344224000000e+00\r\n3134 3132 -5.0777376000000e-01\r\n3135 3132 -1.2913946000000e+00\r\n3180 3132 -1.3274970000000e+00\r\n2029 3133 -2.4342564000000e-03\r\n2031 3133 -2.5405001000000e-05\r\n3085 3133 -1.1494214000000e-02\r\n3087 3133 -4.2162858000000e-06\r\n3130 3133 -1.4244710000000e-02\r\n3132 3133 -4.4851417000000e-06\r\n3133 3133  1.1693718000000e+02\r\n3135 3133  3.1589702000000e-04\r\n3136 3133 -3.9926474000000e-04\r\n3138 3133 -4.1669075000000e-06\r\n3181 3133 -3.8956671000000e-04\r\n3183 3133 -4.0656945000000e-06\r\n2029 3134  2.3759323000000e-01\r\n2031 3134 -4.3266793000000e+00\r\n3085 3134  2.6689809000000e+00\r\n3087 3134 -7.1823623000000e-01\r\n3132 3134 -7.6395798000000e-01\r\n3133 3134 -7.2342964000000e+01\r\n3134 3134 -2.2288761000000e+01\r\n3135 3134  7.2130763000000e+00\r\n3136 3134  2.2927909000000e+00\r\n3138 3134 -7.0065061000000e-01\r\n3183 3134 -7.0105282000000e-01\r\n2029 3135  4.0162735000000e-01\r\n2030 3135 -6.5062949000000e-02\r\n2031 3135 -7.3138141000000e+00\r\n3085 3135  4.5116426000000e+00\r\n3086 3135 -7.3087850000000e-01\r\n3087 3135 -1.2141058000000e+00\r\n3132 3135 -1.2913946000000e+00\r\n3133 3135 -1.2228847000000e+02\r\n3134 3135  1.8794041000000e+01\r\n3135 3135  1.2192977000000e+01\r\n3136 3135  3.8757313000000e+00\r\n3137 3135 -6.2786194000000e-01\r\n3138 3135 -1.1843791000000e+00\r\n3183 3135 -1.1850588000000e+00\r\n2032 3136 -2.4659475000000e-03\r\n2034 3136 -2.5735744000000e-05\r\n3088 3136 -1.8922096000000e-02\r\n3090 3136 -4.1678126000000e-06\r\n3133 3136 -4.5151370000000e-03\r\n3135 3136 -4.1669075000000e-06\r\n3136 3136  1.1693079000000e+02\r\n3138 3136  3.1609362000000e-04\r\n3139 3136 -1.3475450000000e-03\r\n3141 3136 -4.3649100000000e-06\r\n3184 3136 -3.9297458000000e-04\r\n3186 3136 -4.1012605000000e-06\r\n2032 3137  2.2961507000000e-01\r\n2034 3137 -4.3272116000000e+00\r\n3088 3137  3.8466372000000e+00\r\n3090 3137 -7.0088425000000e-01\r\n3135 3137 -7.0065061000000e-01\r\n3136 3137 -7.3470486000000e+01\r\n3137 3137 -2.2293510000000e+01\r\n3138 3137  7.1659987000000e+00\r\n3139 3137  2.2572397000000e+00\r\n3141 3137 -7.3402094000000e-01\r\n3186 3137 -7.0072984000000e-01\r\n2032 3138  3.8814131000000e-01\r\n2033 3138 -6.2877724000000e-02\r\n2034 3138 -7.3147185000000e+00\r\n3088 3138  6.5023555000000e+00\r\n3089 3138 -1.0533620000000e+00\r\n3090 3138 -1.1847747000000e+00\r\n3135 3138 -1.1843791000000e+00\r\n3136 3138 -1.2419451000000e+02\r\n3137 3138  1.9090994000000e+01\r\n3138 3138  1.2113403000000e+01\r\n3139 3138  3.8156380000000e+00\r\n3140 3138 -6.1812187000000e-01\r\n3141 3138 -1.2407890000000e+00\r\n3186 3138 -1.1845137000000e+00\r\n2035 3139 -2.2708331000000e-03\r\n2037 3139 -2.3699441000000e-05\r\n3091 3139 -2.6702316000000e-02\r\n3093 3139 -4.5273854000000e-06\r\n3136 3139 -4.1823695000000e-04\r\n3138 3139 -4.3649100000000e-06\r\n3139 3139  1.2861869000000e+02\r\n3141 3139  3.3816896000000e-04\r\n3187 3139 -4.4700789000000e-04\r\n3189 3139 -4.6651766000000e-06\r\n2035 3140  2.3735622000000e-01\r\n2037 3140 -3.9368051000000e+00\r\n3091 3140  6.7264661000000e+00\r\n3093 3140 -7.5232399000000e-01\r\n3138 3140 -7.3402094000000e-01\r\n3139 3140 -8.0808617000000e+01\r\n3140 3140 -2.4527093000000e+01\r\n3141 3140  6.2140349000000e+00\r\n3189 3140 -7.8813147000000e-01\r\n2035 3141  4.0122669000000e-01\r\n2036 3141 -6.4997097000000e-02\r\n2037 3141 -6.6547709000000e+00\r\n3091 3141  1.1370411000000e+01\r\n3092 3141 -1.8419604000000e+00\r\n3093 3141 -1.2717276000000e+00\r\n3138 3141 -1.2407890000000e+00\r\n3139 3141 -1.3659880000000e+02\r\n3140 3141  2.0987143000000e+01\r\n3141 3141  1.0504199000000e+01\r\n3189 3141 -1.3322566000000e+00\r\n3142 3142  1.0000000000000e+00\r\n3143 3143  1.0000000000000e+00\r\n3144 3144  1.0000000000000e+00\r\n3145 3145  1.0000000000000e+00\r\n3146 3146  1.0000000000000e+00\r\n3147 3147  1.0000000000000e+00\r\n3148 3148  1.0000000000000e+00\r\n3149 3149  1.0000000000000e+00\r\n3150 3150  1.0000000000000e+00\r\n3151 3151  1.0000000000000e+00\r\n3152 3152  1.0000000000000e+00\r\n3153 3153  1.0000000000000e+00\r\n3154 3154  1.0000000000000e+00\r\n3155 3155  1.0000000000000e+00\r\n3156 3156  1.0000000000000e+00\r\n3157 3157  1.0000000000000e+00\r\n3158 3158  1.0000000000000e+00\r\n3159 3159  1.0000000000000e+00\r\n3160 3160  1.0000000000000e+00\r\n3161 3161  1.0000000000000e+00\r\n3162 3162  1.0000000000000e+00\r\n3163 3163  1.0000000000000e+00\r\n3164 3164  1.0000000000000e+00\r\n3165 3165  1.0000000000000e+00\r\n3166 3166  1.0000000000000e+00\r\n3167 3167  1.0000000000000e+00\r\n3168 3168  1.0000000000000e+00\r\n3169 3169  1.0000000000000e+00\r\n3170 3170  1.0000000000000e+00\r\n3171 3171  1.0000000000000e+00\r\n3172 3172  1.0000000000000e+00\r\n3173 3173  1.0000000000000e+00\r\n3174 3174  1.0000000000000e+00\r\n2071 3175 -1.8357689000000e-03\r\n2073 3175 -1.9158914000000e-05\r\n3127 3175 -3.0789269000000e-03\r\n3129 3175 -5.5333043000000e-06\r\n3175 3175  1.5200117000000e+02\r\n3177 3175  3.8501504000000e-04\r\n3178 3175 -4.4948165000000e-04\r\n3180 3175 -4.6909939000000e-06\r\n2071 3176  2.6104710000000e-01\r\n2073 3176 -3.3275135000000e+00\r\n3127 3176  1.0344195000000e+00\r\n3129 3176 -9.6105850000000e-01\r\n3175 3176 -8.8913889000000e+01\r\n3176 3176 -2.8961215000000e+01\r\n3177 3176  5.1054270000000e+00\r\n3178 3176  3.1225563000000e-01\r\n3180 3176 -8.1361201000000e-01\r\n2071 3177  4.4127371000000e-01\r\n2072 3177 -7.1486405000000e-02\r\n2073 3177 -5.6248248000000e+00\r\n3127 3177  1.7485815000000e+00\r\n3128 3177 -2.8327046000000e-01\r\n3129 3177 -1.6245722000000e+00\r\n3175 3177 -1.5029994000000e+02\r\n3176 3177  2.3061769000000e+01\r\n3177 3177  8.6302077000000e+00\r\n3178 3177  5.2783656000000e-01\r\n3179 3177 -8.5509590000000e-02\r\n3180 3177 -1.3753288000000e+00\r\n2074 3178 -2.2750497000000e-03\r\n2076 3178 -2.3743447000000e-05\r\n3130 3178 -2.3480074000000e-03\r\n3132 3178 -4.5274864000000e-06\r\n3175 3178 -2.9814492000000e-02\r\n3177 3178 -4.6909939000000e-06\r\n3178 3178  1.2279692000000e+02\r\n3180 3178  3.2847402000000e-04\r\n3181 3178 -3.9887265000000e-04\r\n3183 3178 -4.1628155000000e-06\r\n3226 3178 -3.9392972000000e-04\r\n3228 3178 -4.1112288000000e-06\r\n2074 3179  2.4712686000000e-01\r\n2076 3179 -4.1177292000000e+00\r\n3130 3179  1.5845342000000e+00\r\n3132 3179 -7.8531531000000e-01\r\n3177 3179 -8.1361201000000e-01\r\n3178 3179 -7.3378153000000e+01\r\n3179 3179 -2.3395689000000e+01\r\n3180 3179  7.1552419000000e+00\r\n3181 3179  1.0353616000000e+00\r\n3183 3179 -7.1773490000000e-01\r\n3228 3179 -7.1822949000000e-01\r\n2074 3180  4.1774324000000e-01\r\n2075 3180 -6.7674367000000e-02\r\n2076 3180 -6.9606094000000e+00\r\n3130 3180  2.6784966000000e+00\r\n3131 3180 -4.3391621000000e-01\r\n3132 3180 -1.3274970000000e+00\r\n3177 3180 -1.3753288000000e+00\r\n3178 3180 -1.2403843000000e+02\r\n3179 3180  1.9045226000000e+01\r\n3180 3180  1.2095220000000e+01\r\n3181 3180  1.7501753000000e+00\r\n3182 3180 -2.8352823000000e-01\r\n3183 3180 -1.2132591000000e+00\r\n3228 3180 -1.2140951000000e+00\r\n2077 3181 -2.4024521000000e-03\r\n2079 3181 -2.5073077000000e-05\r\n3133 3181 -4.6378412000000e-03\r\n3135 3181 -4.0656945000000e-06\r\n3178 3181 -1.5979302000000e-02\r\n3180 3181 -4.1628155000000e-06\r\n3181 3181  1.1693584000000e+02\r\n3183 3181  3.1502718000000e-04\r\n3184 3181 -3.9303164000000e-04\r\n3186 3181 -4.1018560000000e-06\r\n3229 3181 -6.3020376000000e-04\r\n3231 3181 -4.0657214000000e-06\r\n2077 3182  2.2554864000000e-01\r\n2079 3182 -4.3233388000000e+00\r\n3133 3182  2.1047377000000e+00\r\n3135 3182 -7.0105282000000e-01\r\n3180 3182 -7.1773490000000e-01\r\n3181 3182 -7.1087844000000e+01\r\n3182 3182 -2.2285431000000e+01\r\n3183 3182  7.1463879000000e+00\r\n3184 3182  1.6093254000000e+00\r\n3186 3182 -7.0076116000000e-01\r\n3231 3182 -7.0100227000000e-01\r\n2077 3183  3.8126714000000e-01\r\n2078 3183 -6.1765073000000e-02\r\n2079 3183 -7.3081667000000e+00\r\n3133 3183  3.5578461000000e+00\r\n3134 3183 -5.7636917000000e-01\r\n3135 3183 -1.1850588000000e+00\r\n3180 3183 -1.2132591000000e+00\r\n3181 3183 -1.2016681000000e+02\r\n3182 3183  1.8458632000000e+01\r\n3183 3183  1.2080246000000e+01\r\n3184 3183  2.7204018000000e+00\r\n3185 3183 -4.4070362000000e-01\r\n3186 3183 -1.1845658000000e+00\r\n3231 3183 -1.1849736000000e+00\r\n2080 3184 -2.4271249000000e-03\r\n2082 3184 -2.5330574000000e-05\r\n3136 3184 -4.7311540000000e-03\r\n3138 3184 -4.1012605000000e-06\r\n3181 3184 -4.6023346000000e-03\r\n3183 3184 -4.1018560000000e-06\r\n3184 3184  1.1692209000000e+02\r\n3186 3184  3.1582529000000e-04\r\n3187 3184 -4.2520237000000e-04\r\n3189 3184 -4.4376044000000e-06\r\n3232 3184 -1.8415784000000e-03\r\n3234 3184 -4.2967900000000e-06\r\n2080 3185  2.2919201000000e-01\r\n2082 3185 -4.3272245000000e+00\r\n3136 3185  2.7875323000000e+00\r\n3138 3185 -7.0072984000000e-01\r\n3183 3185 -7.0076116000000e-01\r\n3184 3185 -7.2281303000000e+01\r\n3185 3185 -2.2288936000000e+01\r\n3186 3185  7.2148813000000e+00\r\n3187 3185  2.1212159000000e+00\r\n3189 3185 -7.4960785000000e-01\r\n3234 3185 -7.3405848000000e-01\r\n2080 3186  3.8742616000000e-01\r\n2081 3186 -6.2762455000000e-02\r\n2082 3186 -7.3147403000000e+00\r\n3136 3186  4.7120446000000e+00\r\n3137 3186 -7.6334412000000e-01\r\n3138 3186 -1.1845137000000e+00\r\n3183 3186 -1.1845658000000e+00\r\n3184 3186 -1.2218432000000e+02\r\n3185 3186  1.8776741000000e+01\r\n3186 3186  1.2196034000000e+01\r\n3187 3186  3.5857033000000e+00\r\n3188 3186 -5.8087853000000e-01\r\n3189 3186 -1.2671371000000e+00\r\n3234 3186 -1.2408525000000e+00\r\n2083 3187 -2.1340685000000e-03\r\n2085 3187 -2.2272105000000e-05\r\n3139 3187 -9.4670244000000e-03\r\n3141 3187 -4.6651766000000e-06\r\n3184 3187 -3.4153136000000e-03\r\n3186 3187 -4.4376044000000e-06\r\n3187 3187  1.3445432000000e+02\r\n3189 3187  3.4596464000000e-04\r\n2083 3188  2.2916280000000e-01\r\n2085 3188 -3.7627684000000e+00\r\n3139 3188  3.3285979000000e+00\r\n3141 3188 -7.8813147000000e-01\r\n3186 3188 -7.4960785000000e-01\r\n3187 3188 -8.0766249000000e+01\r\n3188 3188 -2.5636890000000e+01\r\n3189 3188  5.3033841000000e+00\r\n2083 3189  3.8737656000000e-01\r\n2084 3189 -6.2754044000000e-02\r\n2085 3189 -6.3605797000000e+00\r\n3139 3189  5.6266585000000e+00\r\n3140 3189 -9.1150468000000e-01\r\n3141 3189 -1.3322566000000e+00\r\n3186 3189 -1.2671371000000e+00\r\n3187 3189 -1.3652718000000e+02\r\n3188 3189  2.0936337000000e+01\r\n3189 3189  8.9648357000000e+00\r\n3190 3190  1.0000000000000e+00\r\n3191 3191  1.0000000000000e+00\r\n3192 3192  1.0000000000000e+00\r\n3193 3193  1.0000000000000e+00\r\n3194 3194  1.0000000000000e+00\r\n3195 3195  1.0000000000000e+00\r\n3196 3196  1.0000000000000e+00\r\n3197 3197  1.0000000000000e+00\r\n3198 3198  1.0000000000000e+00\r\n3199 3199  1.0000000000000e+00\r\n3200 3200  1.0000000000000e+00\r\n3201 3201  1.0000000000000e+00\r\n3202 3202  1.0000000000000e+00\r\n3203 3203  1.0000000000000e+00\r\n3204 3204  1.0000000000000e+00\r\n3205 3205  1.0000000000000e+00\r\n3206 3206  1.0000000000000e+00\r\n3207 3207  1.0000000000000e+00\r\n3208 3208  1.0000000000000e+00\r\n3209 3209  1.0000000000000e+00\r\n3210 3210  1.0000000000000e+00\r\n3211 3211  1.0000000000000e+00\r\n3212 3212  1.0000000000000e+00\r\n3213 3213  1.0000000000000e+00\r\n3214 3214  1.0000000000000e+00\r\n3215 3215  1.0000000000000e+00\r\n3216 3216  1.0000000000000e+00\r\n3217 3217  1.0000000000000e+00\r\n3218 3218  1.0000000000000e+00\r\n3219 3219  1.0000000000000e+00\r\n3220 3220  1.0000000000000e+00\r\n3221 3221  1.0000000000000e+00\r\n3222 3222  1.0000000000000e+00\r\n3223 3223  1.0000000000000e+00\r\n3224 3224  1.0000000000000e+00\r\n3225 3225  1.0000000000000e+00\r\n2122 3226 -2.3706604000000e-03\r\n2124 3226 -2.4741284000000e-05\r\n3178 3226 -7.0890245000000e-04\r\n3180 3226 -4.1112288000000e-06\r\n3226 3226  1.1692746000000e+02\r\n3228 3226  3.1045107000000e-04\r\n3229 3226 -3.8566782000000e-04\r\n3231 3226 -4.0250039000000e-06\r\n3274 3226 -5.7017845000000e-03\r\n3276 3226 -4.0132230000000e-06\r\n2122 3227  2.2026949000000e-01\r\n2124 3227 -4.3217700000000e+00\r\n3178 3227  1.2629601000000e+00\r\n3180 3227 -7.1822949000000e-01\r\n3226 3227 -6.9220622000000e+01\r\n3227 3227 -2.2279374000000e+01\r\n3228 3227  6.4444803000000e+00\r\n3229 3227  5.8085413000000e-01\r\n3231 3227 -7.0091648000000e-01\r\n3276 3227 -7.0106907000000e-01\r\n2122 3228  3.7234355000000e-01\r\n2123 3228 -6.0319866000000e-02\r\n2124 3228 -7.3055200000000e+00\r\n3178 3228  2.1349078000000e+00\r\n3179 3228 -3.4585627000000e-01\r\n3180 3228 -1.2140951000000e+00\r\n3226 3228 -1.1701054000000e+02\r\n3227 3228  1.7962197000000e+01\r\n3228 3228  1.0893749000000e+01\r\n3229 3228  9.8187582000000e-01\r\n3230 3228 -1.5906444000000e-01\r\n3231 3228 -1.1848292000000e+00\r\n3276 3228 -1.1850872000000e+00\r\n2125 3229 -2.3783246000000e-03\r\n2127 3229 -2.4821271000000e-05\r\n3181 3229 -3.8956930000000e-04\r\n3183 3229 -4.0657214000000e-06\r\n3226 3229 -1.5054090000000e-02\r\n3228 3229 -4.0250039000000e-06\r\n3229 3229  1.1693855000000e+02\r\n3231 3229  3.1474105000000e-04\r\n3232 3229 -4.0678672000000e-04\r\n3234 3229 -4.2454102000000e-06\r\n3277 3229 -5.2020450000000e-03\r\n3279 3229 -4.0252116000000e-06\r\n2125 3230  2.1891350000000e-01\r\n2127 3230 -4.3212217000000e+00\r\n3181 3230  1.6629280000000e+00\r\n3183 3230 -7.0100227000000e-01\r\n3228 3230 -7.0091648000000e-01\r\n3229 3230 -7.0175975000000e+01\r\n3230 3230 -2.2282337000000e+01\r\n3231 3230  7.1610951000000e+00\r\n3232 3230  1.1416356000000e+00\r\n3234 3230 -7.3450310000000e-01\r\n3279 3230 -7.0095502000000e-01\r\n2125 3231  3.7005118000000e-01\r\n2126 3231 -5.9948420000000e-02\r\n2127 3231 -7.3045892000000e+00\r\n3181 3231  2.8110119000000e+00\r\n3182 3231 -4.5538492000000e-01\r\n3183 3231 -1.1849736000000e+00\r\n3228 3231 -1.1848292000000e+00\r\n3229 3231 -1.1862540000000e+02\r\n3230 3231  1.8216588000000e+01\r\n3231 3231  1.2105109000000e+01\r\n3232 3231  1.9298198000000e+00\r\n3233 3231 -3.1263150000000e-01\r\n3234 3231 -1.2416034000000e+00\r\n3279 3231 -1.1848937000000e+00\r\n2128 3232 -2.1769643000000e-03\r\n2130 3232 -2.2719784000000e-05\r\n3184 3232 -4.1170983000000e-04\r\n3186 3232 -4.2967900000000e-06\r\n3229 3232 -3.6404805000000e-03\r\n3231 3232 -4.2454102000000e-06\r\n3232 3232  1.2861005000000e+02\r\n3234 3232  3.3217568000000e-04\r\n2128 3233  2.1844699000000e-01\r\n2130 3233 -3.9304561000000e+00\r\n3184 3233  2.2861829000000e+00\r\n3186 3233 -7.3405848000000e-01\r\n3231 3233 -7.3450310000000e-01\r\n3232 3233 -7.6368722000000e+01\r\n3233 3233 -2.4513213000000e+01\r\n3234 3233  5.4017650000000e+00\r\n2128 3234  3.6926279000000e-01\r\n2129 3234 -5.9820451000000e-02\r\n2130 3234 -6.6440430000000e+00\r\n3184 3234  3.8645636000000e+00\r\n3185 3234 -6.2605803000000e-01\r\n3186 3234 -1.2408525000000e+00\r\n3231 3234 -1.2416034000000e+00\r\n3232 3234 -1.2909369000000e+02\r\n3233 3234  1.9805802000000e+01\r\n3234 3234  9.1311429000000e+00\r\n3235 3235  1.0000000000000e+00\r\n3236 3236  1.0000000000000e+00\r\n3237 3237  1.0000000000000e+00\r\n3238 3238  1.0000000000000e+00\r\n3239 3239  1.0000000000000e+00\r\n3240 3240  1.0000000000000e+00\r\n3241 3241  1.0000000000000e+00\r\n3242 3242  1.0000000000000e+00\r\n3243 3243  1.0000000000000e+00\r\n3244 3244  1.0000000000000e+00\r\n3245 3245  1.0000000000000e+00\r\n3246 3246  1.0000000000000e+00\r\n3247 3247  1.0000000000000e+00\r\n3248 3248  1.0000000000000e+00\r\n3249 3249  1.0000000000000e+00\r\n3250 3250  1.0000000000000e+00\r\n3251 3251  1.0000000000000e+00\r\n3252 3252  1.0000000000000e+00\r\n3253 3253  1.0000000000000e+00\r\n3254 3254  1.0000000000000e+00\r\n3255 3255  1.0000000000000e+00\r\n3256 3256  1.0000000000000e+00\r\n3257 3257  1.0000000000000e+00\r\n3258 3258  1.0000000000000e+00\r\n3259 3259  1.0000000000000e+00\r\n3260 3260  1.0000000000000e+00\r\n3261 3261  1.0000000000000e+00\r\n3262 3262  1.0000000000000e+00\r\n3263 3263  1.0000000000000e+00\r\n3264 3264  1.0000000000000e+00\r\n3265 3265  1.0000000000000e+00\r\n3266 3266  1.0000000000000e+00\r\n3267 3267  1.0000000000000e+00\r\n3268 3268  1.0000000000000e+00\r\n3269 3269  1.0000000000000e+00\r\n3270 3270  1.0000000000000e+00\r\n3271 3271  1.0000000000000e+00\r\n3272 3272  1.0000000000000e+00\r\n3273 3273  1.0000000000000e+00\r\n2170 3274 -2.3584866000000e-03\r\n2172 3274 -2.4614233000000e-05\r\n3226 3274 -3.8453900000000e-04\r\n3228 3274 -4.0132230000000e-06\r\n3274 3274  1.1692377000000e+02\r\n3276 3274  3.0618521000000e-04\r\n3277 3274 -3.8294690000000e-04\r\n3279 3274 -3.9966072000000e-06\r\n2170 3275  2.1207041000000e-01\r\n2172 3275 -4.3203650000000e+00\r\n3226 3275  8.2629021000000e-01\r\n3228 3275 -7.0106907000000e-01\r\n3274 3275 -6.8392282000000e+01\r\n3275 3275 -2.2277164000000e+01\r\n3276 3275  5.7248404000000e+00\r\n3277 3275  1.9435409000000e-01\r\n3279 3275 -7.0091203000000e-01\r\n2170 3276  3.5848382000000e-01\r\n2171 3276 -5.8074741000000e-02\r\n2172 3276 -7.3031450000000e+00\r\n3226 3276  1.3967610000000e+00\r\n3227 3276 -2.2627669000000e-01\r\n3228 3276 -1.1850872000000e+00\r\n3274 3276 -1.1561031000000e+02\r\n3275 3276  1.7740800000000e+01\r\n3276 3276  9.6772702000000e+00\r\n3277 3276  3.2853615000000e-01\r\n3278 3276 -5.3223188000000e-02\r\n3279 3276 -1.1848217000000e+00\r\n2173 3277 -2.3613793000000e-03\r\n2175 3277 -2.4644423000000e-05\r\n3229 3277 -3.8568773000000e-04\r\n3231 3277 -4.0252116000000e-06\r\n3274 3277 -1.5551920000000e-02\r\n3276 3277 -3.9966072000000e-06\r\n3277 3277  1.1693647000000e+02\r\n3279 3277  3.0622550000000e-04\r\n2173 3278  2.1205822000000e-01\r\n2175 3278 -4.3215731000000e+00\r\n3229 3278  1.2126517000000e+00\r\n3231 3278 -7.0095502000000e-01\r\n3276 3278 -7.0091203000000e-01\r\n3277 3278 -6.8581138000000e+01\r\n3278 3278 -2.2279477000000e+01\r\n3279 3278  5.7259355000000e+00\r\n2173 3279  3.5846302000000e-01\r\n2174 3279 -5.8071371000000e-02\r\n2175 3279 -7.3051832000000e+00\r\n3229 3279  2.0498654000000e+00\r\n3230 3279 -3.3208026000000e-01\r\n3231 3279 -1.1848937000000e+00\r\n3276 3279 -1.1848217000000e+00\r\n3277 3279 -1.1592949000000e+02\r\n3278 3279  1.7786906000000e+01\r\n3279 3279  9.6791167000000e+00\r\n3280 3280  1.0000000000000e+00\r\n3281 3281  1.0000000000000e+00\r\n3282 3282  1.0000000000000e+00\r\n3283 3283  1.0000000000000e+00\r\n3284 3284  1.0000000000000e+00\r\n3285 3285  1.0000000000000e+00\r\n3286 3286  1.0000000000000e+00\r\n3287 3287  1.0000000000000e+00\r\n3288 3288  1.0000000000000e+00\r\n3289 3289  1.0000000000000e+00\r\n3290 3290  1.0000000000000e+00\r\n3291 3291  1.0000000000000e+00\r\n3292 3292  1.0000000000000e+00\r\n3293 3293  1.0000000000000e+00\r\n3294 3294  1.0000000000000e+00\r\n3295 3295  1.0000000000000e+00\r\n3296 3296  1.0000000000000e+00\r\n3297 3297  1.0000000000000e+00\r\n3298 3298  1.0000000000000e+00\r\n3299 3299  1.0000000000000e+00\r\n3300 3300  1.0000000000000e+00\r\n3301 3301  1.0000000000000e+00\r\n3302 3302  1.0000000000000e+00\r\n3303 3303  1.0000000000000e+00\r\n3304 3304  1.0000000000000e+00\r\n3305 3305  1.0000000000000e+00\r\n3306 3306  1.0000000000000e+00\r\n3307 3307  1.0000000000000e+00\r\n3308 3308  1.0000000000000e+00\r\n3309 3309  1.0000000000000e+00\r\n3310 3310  1.0000000000000e+00\r\n3311 3311  1.0000000000000e+00\r\n3312 3312  1.0000000000000e+00\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/sherman5_rhs1.mtx",
    "content": "%%MatrixMarket matrix array real general\r\n% RBTitle: 1U FULLY IMPLICIT BLACK OIL SIMULATOR   16 BY 23 BY  3 GRID, THREE UNK  \r\n% RBKey:   SHERMAN5\r\n% Right-hand-side: 1\r\n3312 1\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.73007589E+00\r\n -0.47791410E+01\r\n -0.80786603E+01\r\n -0.10735529E+01\r\n -0.45423119E+01\r\n -0.76783303E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.12875379E+01\r\n -0.42729598E+01\r\n -0.72230115E+01\r\n -0.86232178E+00\r\n -0.44841105E+01\r\n -0.75799067E+01\r\n -0.73193270E+00\r\n -0.44916564E+01\r\n -0.75926988E+01\r\n -0.51603338E+00\r\n -0.45085547E+01\r\n -0.76212363E+01\r\n -0.61948008E+00\r\n -0.43775531E+01\r\n -0.73998181E+01\r\n -0.68304074E+00\r\n -0.42793760E+01\r\n -0.72338543E+01\r\n -0.71426769E+00\r\n -0.41984834E+01\r\n -0.70971163E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.35601016E+00\r\n -0.15060889E+01\r\n -0.25458927E+01\r\n  0.64500903E+00\r\n -0.16689431E+01\r\n -0.28211711E+01\r\n -0.21215130E+00\r\n -0.52607998E+01\r\n -0.88928567E+01\r\n -0.22257718E+00\r\n -0.52416289E+01\r\n -0.88604592E+01\r\n  0.83707514E+00\r\n -0.17437449E+01\r\n -0.29476284E+01\r\n  0.38187663E+00\r\n -0.13952795E+01\r\n -0.23586135E+01\r\n  0.19964828E+00\r\n -0.11927143E+01\r\n -0.20161661E+01\r\n  0.92284651E-01\r\n -0.10434371E+01\r\n -0.17638169E+01\r\n  0.67937173E-01\r\n -0.95358111E+00\r\n -0.16119355E+01\r\n  0.45402680E-01\r\n -0.85441984E+00\r\n -0.14443376E+01\r\n  0.28001318E-01\r\n -0.79615742E+00\r\n -0.13458247E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.19607089E-01\r\n -0.13666893E+01\r\n -0.23102515E+01\r\n  0.41824926E-01\r\n -0.13828718E+01\r\n -0.23376242E+01\r\n  0.54009602E-01\r\n -0.13798434E+01\r\n -0.23324877E+01\r\n  0.54886968E-01\r\n -0.13858378E+01\r\n -0.23426572E+01\r\n  0.41994337E-01\r\n -0.13663276E+01\r\n -0.23096417E+01\r\n  0.34842476E-01\r\n -0.13133247E+01\r\n -0.22200348E+01\r\n  0.21929996E-01\r\n -0.12106125E+01\r\n -0.20464221E+01\r\n  0.14816440E-01\r\n -0.11068098E+01\r\n -0.18709649E+01\r\n  0.71735406E-02\r\n -0.10058716E+01\r\n -0.17003275E+01\r\n  0.46638650E-02\r\n -0.92740099E+00\r\n -0.15676581E+01\r\n  0.26555312E-02\r\n -0.85507323E+00\r\n -0.14454159E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.36676090E-02\r\n -0.13998433E+01\r\n -0.23662951E+01\r\n  0.47453482E-02\r\n -0.13948700E+01\r\n -0.23579180E+01\r\n  0.72339044E-02\r\n -0.14109662E+01\r\n -0.23850976E+01\r\n  0.77620945E-02\r\n -0.13957068E+01\r\n -0.23593177E+01\r\n  0.74975053E-02\r\n -0.14068059E+01\r\n -0.23780657E+01\r\n  0.65886737E-02\r\n -0.13862602E+01\r\n -0.23433394E+01\r\n  0.38731180E-02\r\n -0.13098881E+01\r\n -0.22142374E+01\r\n  0.19912716E-02\r\n -0.12089198E+01\r\n -0.20435172E+01\r\n  0.34457596E-03\r\n -0.11017995E+01\r\n -0.18624857E+01\r\n -0.17084600E-04\r\n -0.10031355E+01\r\n -0.16956826E+01\r\n -0.41829973E-04\r\n -0.89521077E+00\r\n -0.15132649E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.18117608E-04\r\n -0.14382016E+01\r\n -0.24311360E+01\r\n -0.19541025E-04\r\n -0.14512249E+01\r\n -0.24531659E+01\r\n -0.41104053E-05\r\n -0.14412508E+01\r\n -0.24362913E+01\r\n  0.35810686E-03\r\n -0.14474765E+01\r\n -0.24468168E+01\r\n  0.86262602E-03\r\n -0.14377778E+01\r\n -0.24304205E+01\r\n  0.61385471E-05\r\n -0.14467032E+01\r\n -0.24455055E+01\r\n -0.55054371E-05\r\n -0.14303970E+01\r\n -0.24179451E+01\r\n -0.18857532E-04\r\n -0.13150356E+01\r\n -0.22229503E+01\r\n -0.19545600E-04\r\n -0.11872204E+01\r\n -0.20068795E+01\r\n -0.26680571E-04\r\n -0.10736020E+01\r\n -0.18148355E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.16404615E-04\r\n -0.14868600E+01\r\n -0.25133882E+01\r\n -0.92369949E-05\r\n -0.14778511E+01\r\n -0.24981171E+01\r\n -0.23710578E-04\r\n -0.14851980E+01\r\n -0.25105803E+01\r\n -0.10057016E-04\r\n -0.14792956E+01\r\n -0.25006310E+01\r\n -0.66869617E-05\r\n -0.14893809E+01\r\n -0.25176509E+01\r\n -0.49755106E-05\r\n -0.14752451E+01\r\n -0.24937695E+01\r\n -0.95114750E-05\r\n -0.14824034E+01\r\n -0.25058580E+01\r\n -0.64772759E-05\r\n -0.13795586E+01\r\n -0.23320204E+01\r\n -0.24176065E-04\r\n -0.12904761E+01\r\n -0.21814234E+01\r\n -0.17189726E-04\r\n -0.11638123E+01\r\n -0.19673279E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.28471641E-04\r\n -0.13773314E+01\r\n -0.23282318E+01\r\n  0.95816722E-06\r\n -0.14072786E+01\r\n -0.23788637E+01\r\n -0.12076326E-04\r\n -0.14714681E+01\r\n -0.24874129E+01\r\n -0.10807086E-04\r\n -0.15207585E+01\r\n -0.25706943E+01\r\n -0.11161304E-04\r\n -0.15263816E+01\r\n -0.25801916E+01\r\n -0.20055691E-04\r\n -0.15181462E+01\r\n -0.25662770E+01\r\n -0.26852077E-04\r\n -0.15227043E+01\r\n -0.25739554E+01\r\n -0.19050641E-04\r\n -0.15127609E+01\r\n -0.25571761E+01\r\n -0.19715413E-04\r\n -0.14913835E+01\r\n -0.25210167E+01\r\n  0.33878064E-05\r\n -0.13892753E+01\r\n -0.23484356E+01\r\n -0.34576010E-04\r\n -0.12239378E+01\r\n -0.20689494E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.56398446E-04\r\n -0.11405498E+01\r\n -0.19279831E+01\r\n -0.15864107E-04\r\n -0.12545651E+01\r\n -0.21207178E+01\r\n -0.34396076E-04\r\n -0.13648443E+01\r\n -0.23071364E+01\r\n -0.21986729E-04\r\n -0.14743089E+01\r\n -0.24921774E+01\r\n  0.52056130E-05\r\n -0.15736459E+01\r\n -0.26600491E+01\r\n -0.13752350E-05\r\n -0.15813178E+01\r\n -0.26730676E+01\r\n -0.46498680E-05\r\n -0.15685133E+01\r\n -0.26514487E+01\r\n -0.19054566E-04\r\n -0.15681498E+01\r\n -0.26508067E+01\r\n -0.12723450E-04\r\n -0.15526272E+01\r\n -0.26245537E+01\r\n -0.41287490E-04\r\n -0.14520409E+01\r\n -0.24545388E+01\r\n -0.67649937E-04\r\n -0.12879069E+01\r\n -0.21771004E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.33357966E-04\r\n -0.98516893E+00\r\n -0.16653495E+01\r\n -0.49860107E-04\r\n -0.11012408E+01\r\n -0.18615406E+01\r\n -0.29121356E-04\r\n -0.12150149E+01\r\n -0.20538326E+01\r\n -0.64973913E-04\r\n -0.13596684E+01\r\n -0.22983959E+01\r\n -0.47182663E-04\r\n -0.15436715E+01\r\n -0.26094265E+01\r\n -0.67505641E-04\r\n -0.15979560E+01\r\n -0.27012088E+01\r\n -0.28856358E-04\r\n -0.16156942E+01\r\n -0.27311742E+01\r\n  0.66711107E-05\r\n -0.16110310E+01\r\n -0.27232994E+01\r\n -0.88580379E-05\r\n -0.16122189E+01\r\n -0.27252734E+01\r\n -0.18625635E-04\r\n -0.15272640E+01\r\n -0.25816878E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.41683819E-04\r\n -0.86574634E+00\r\n -0.14634723E+01\r\n -0.38333279E-04\r\n -0.97176765E+00\r\n -0.16426802E+01\r\n -0.57507505E-04\r\n -0.10931890E+01\r\n -0.18479170E+01\r\n  0.68280592E-05\r\n -0.12635463E+01\r\n -0.21359138E+01\r\n -0.10174167E-03\r\n -0.14315321E+01\r\n -0.24198258E+01\r\n -0.66316080E-04\r\n -0.16799063E+01\r\n -0.28397741E+01\r\n -0.74049959E-04\r\n -0.16408147E+01\r\n -0.27736115E+01\r\n -0.53376426E-04\r\n -0.16438845E+01\r\n -0.27788402E+01\r\n -0.48810071E-04\r\n -0.16228442E+01\r\n -0.27432591E+01\r\n -0.73584354E-04\r\n -0.15841441E+01\r\n -0.26778375E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.48118420E-05\r\n -0.66277511E+00\r\n -0.11203550E+01\r\n -0.18260330E-04\r\n -0.79174586E+00\r\n -0.13383640E+01\r\n -0.22777606E-04\r\n -0.88713826E+00\r\n -0.14996240E+01\r\n -0.42816896E-04\r\n -0.99285880E+00\r\n -0.16783249E+01\r\n -0.57540209E-04\r\n -0.11913010E+01\r\n -0.20137940E+01\r\n -0.12622011E-03\r\n -0.13789037E+01\r\n -0.23308702E+01\r\n -0.10976066E-02\r\n -0.65360711E+00\r\n -0.11050275E+01\r\n -0.13944407E-03\r\n -0.16889513E+01\r\n -0.28550835E+01\r\n -0.39006204E-04\r\n -0.16721192E+01\r\n -0.28265820E+01\r\n -0.49153549E-04\r\n -0.16707199E+01\r\n -0.28242130E+01\r\n -0.80289801E-04\r\n -0.16295539E+01\r\n -0.27545982E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.94335240E-05\r\n -0.66738691E+00\r\n -0.11281508E+01\r\n -0.24013672E-04\r\n -0.65966426E+00\r\n -0.11151072E+01\r\n -0.33650011E-04\r\n -0.79829526E+00\r\n -0.13494442E+01\r\n -0.25928102E-04\r\n -0.93667321E+00\r\n -0.15833201E+01\r\n -0.32623966E-04\r\n -0.10845518E+01\r\n -0.18333416E+01\r\n -0.55343833E-04\r\n -0.12528916E+01\r\n -0.21178357E+01\r\n -0.79205561E-04\r\n -0.15505039E+01\r\n -0.26210261E+01\r\n -0.38003714E-04\r\n -0.17022137E+01\r\n -0.28773975E+01\r\n -0.48634295E-04\r\n -0.17002884E+01\r\n -0.28741819E+01\r\n -0.10361308E-04\r\n -0.16898889E+01\r\n -0.28566784E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.59119322E-05\r\n -0.70017737E+00\r\n -0.11835785E+01\r\n -0.14543802E-04\r\n -0.66353971E+00\r\n -0.11216505E+01\r\n -0.27038167E-04\r\n -0.66683954E+00\r\n -0.11272254E+01\r\n -0.24881679E-04\r\n -0.66659284E+00\r\n -0.11268136E+01\r\n -0.22336300E-04\r\n -0.84891238E+00\r\n -0.14349973E+01\r\n -0.29986663E-04\r\n -0.10174238E+01\r\n -0.17198650E+01\r\n -0.30273510E-04\r\n -0.12378458E+01\r\n -0.20924453E+01\r\n -0.33218393E-04\r\n -0.15112191E+01\r\n -0.25545802E+01\r\n -0.12291160E-04\r\n -0.17294887E+01\r\n -0.29234863E+01\r\n -0.55390439E-04\r\n -0.16986944E+01\r\n -0.28714782E+01\r\n -0.67921277E-04\r\n -0.16955332E+01\r\n -0.28660843E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.22892619E-05\r\n -0.79970068E+00\r\n -0.13518220E+01\r\n -0.34042565E-04\r\n -0.69427548E+00\r\n -0.11736054E+01\r\n -0.29322870E-04\r\n -0.66133833E+00\r\n -0.11179188E+01\r\n -0.18520892E-04\r\n -0.67574534E+00\r\n -0.11422847E+01\r\n -0.44095333E-04\r\n -0.73570177E+00\r\n -0.12436208E+01\r\n -0.13631124E-04\r\n -0.96566424E+00\r\n -0.16323655E+01\r\n -0.18403631E-04\r\n -0.11684261E+01\r\n -0.19751242E+01\r\n -0.30182810E-04\r\n -0.14573423E+01\r\n -0.24635024E+01\r\n -0.21977258E-04\r\n -0.17288422E+01\r\n -0.29224149E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.96096956E-05\r\n -0.98866951E+00\r\n -0.16712469E+01\r\n -0.25788017E-04\r\n -0.89318277E+00\r\n -0.15098393E+01\r\n -0.17901886E-04\r\n -0.79396960E+00\r\n -0.13421295E+01\r\n -0.15515695E-04\r\n -0.66932056E+00\r\n -0.11314188E+01\r\n -0.20788614E-04\r\n -0.66957888E+00\r\n -0.11318615E+01\r\n -0.29950432E-04\r\n -0.71221837E+00\r\n -0.12039388E+01\r\n -0.79763861E-04\r\n -0.86679264E+00\r\n -0.14652332E+01\r\n  0.62146229E-05\r\n -0.11891561E+01\r\n -0.20101667E+01\r\n -0.60913855E-04\r\n -0.14057552E+01\r\n -0.23763045E+01\r\n -0.59914479E-04\r\n -0.16912205E+01\r\n -0.28588373E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.73316461E-05\r\n -0.99293752E+00\r\n -0.16784616E+01\r\n -0.65075077E-05\r\n -0.99357334E+00\r\n -0.16795566E+01\r\n -0.24474551E-04\r\n -0.82784379E+00\r\n -0.13993893E+01\r\n -0.18857208E-04\r\n -0.69572056E+00\r\n -0.11760444E+01\r\n -0.19047106E-04\r\n -0.67271434E+00\r\n -0.11371597E+01\r\n -0.19226591E-04\r\n -0.70880567E+00\r\n -0.11981386E+01\r\n -0.33449801E-04\r\n -0.88789729E+00\r\n -0.15009068E+01\r\n -0.11609816E-03\r\n -0.11333208E+01\r\n -0.19157639E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.37105963E-05\r\n -0.98969264E+00\r\n -0.16729764E+01\r\n -0.14729875E-04\r\n -0.99001307E+00\r\n -0.16735492E+01\r\n -0.19591296E-04\r\n -0.82089647E+00\r\n -0.13876453E+01\r\n -0.93112312E-05\r\n -0.70053389E+00\r\n -0.11841959E+01\r\n -0.10793624E-04\r\n -0.66765328E+00\r\n -0.11286039E+01\r\n -0.40392857E-04\r\n -0.70163762E+00\r\n -0.11860383E+01\r\n  0.11634927E-04\r\n -0.89600441E+00\r\n -0.15146117E+01\r\n -0.99461805E-05\r\n -0.11367258E+01\r\n -0.19215158E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.15589030E-05\r\n -0.99061413E+00\r\n -0.16745341E+01\r\n -0.25002085E-06\r\n -0.95293809E+00\r\n -0.16108464E+01\r\n -0.18340935E-04\r\n -0.79103403E+00\r\n -0.13371649E+01\r\n -0.12199068E-04\r\n -0.65779221E+00\r\n -0.11119297E+01\r\n -0.17449818E-04\r\n -0.66517975E+00\r\n -0.11244218E+01\r\n -0.15437209E-04\r\n -0.73064797E+00\r\n -0.12350862E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.15361566E-05\r\n -0.85824196E+00\r\n -0.14507853E+01\r\n -0.12983907E-04\r\n -0.68618697E+00\r\n -0.11599307E+01\r\n -0.12926853E-04\r\n -0.65903822E+00\r\n -0.11140329E+01\r\n -0.10409705E-04\r\n -0.65942056E+00\r\n -0.11146858E+01\r\n -0.12116367E-04\r\n -0.76283043E+00\r\n -0.12895077E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.53194151E-05\r\n -0.65811632E+00\r\n -0.11124798E+01\r\n -0.16225085E-04\r\n -0.65181712E+00\r\n -0.11018309E+01\r\n -0.12175012E-04\r\n -0.72381679E+00\r\n -0.12235406E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.93218916E-06\r\n -0.65479993E+00\r\n -0.11068738E+01\r\n -0.11427151E-04\r\n -0.65261348E+00\r\n -0.11031850E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.11374207E+01\r\n -0.35988748E+01\r\n -0.60835282E+01\r\n -0.81269119E+00\r\n -0.37569236E+01\r\n -0.63507039E+01\r\n -0.86204067E+00\r\n -0.37062973E+01\r\n -0.62651237E+01\r\n -0.86132270E+00\r\n -0.36842788E+01\r\n -0.62279049E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.41876580E+00\r\n -0.43708098E+01\r\n -0.73884170E+01\r\n -0.57469749E+00\r\n -0.42656638E+01\r\n -0.72106682E+01\r\n -0.63737822E+00\r\n -0.42206050E+01\r\n -0.71345108E+01\r\n -0.64582562E+00\r\n -0.42103360E+01\r\n -0.71171524E+01\r\n -0.58794794E+00\r\n -0.42355747E+01\r\n -0.71598159E+01\r\n -0.46057242E+00\r\n -0.42666316E+01\r\n -0.72122914E+01\r\n -0.49824978E+00\r\n -0.42016028E+01\r\n -0.71023894E+01\r\n  0.21671793E+00\r\n -0.58070052E+00\r\n -0.98161902E+00\r\n  0.11361062E+00\r\n -0.48930719E+00\r\n -0.82712555E+00\r\n  0.60520075E-01\r\n -0.42085475E+00\r\n -0.71141235E+00\r\n  0.30968605E-01\r\n -0.38103848E+00\r\n -0.64410745E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.47423322E-01\r\n -0.65342197E+00\r\n -0.11045445E+01\r\n  0.12746087E+00\r\n -0.70065447E+00\r\n -0.11843766E+01\r\n  0.16209582E+00\r\n -0.71631155E+00\r\n -0.12108532E+01\r\n  0.16496496E+00\r\n -0.71845553E+00\r\n -0.12144852E+01\r\n  0.12210256E+00\r\n -0.68999000E+00\r\n -0.11663594E+01\r\n  0.79605960E-01\r\n -0.64335472E+00\r\n -0.10875327E+01\r\n  0.44568974E-01\r\n -0.58333030E+00\r\n -0.98606204E+00\r\n  0.14726045E-01\r\n -0.51951564E+00\r\n -0.87819327E+00\r\n  0.60058456E-02\r\n -0.47233539E+00\r\n -0.79843672E+00\r\n  0.39690732E-02\r\n -0.43482169E+00\r\n -0.73502610E+00\r\n  0.30008818E-02\r\n -0.40397232E+00\r\n -0.68287481E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.64757041E-02\r\n -0.65788842E+00\r\n -0.11120946E+01\r\n  0.68846046E-02\r\n -0.65510621E+00\r\n -0.11073899E+01\r\n  0.78823979E-02\r\n -0.65845485E+00\r\n -0.11130522E+01\r\n  0.89068724E-02\r\n -0.65354439E+00\r\n -0.11047603E+01\r\n  0.88172434E-02\r\n -0.65672103E+00\r\n -0.11101216E+01\r\n  0.68877520E-02\r\n -0.65015083E+00\r\n -0.10989916E+01\r\n  0.37512450E-02\r\n -0.61314243E+00\r\n -0.10364566E+01\r\n  0.23534657E-02\r\n -0.56977568E+00\r\n -0.96315275E+00\r\n  0.12966358E-02\r\n -0.51846792E+00\r\n -0.87641939E+00\r\n  0.59107988E-03\r\n -0.47296938E+00\r\n -0.79951156E+00\r\n  0.24698769E-04\r\n -0.42305505E+00\r\n -0.71513230E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.69521364E-03\r\n -0.67645089E+00\r\n -0.11434726E+01\r\n  0.11916901E-02\r\n -0.68104524E+00\r\n -0.11512495E+01\r\n  0.20687820E-02\r\n -0.67814869E+00\r\n -0.11463429E+01\r\n  0.22345994E-02\r\n -0.67940676E+00\r\n -0.11484613E+01\r\n  0.23542486E-02\r\n -0.67541762E+00\r\n -0.11417263E+01\r\n  0.17995186E-02\r\n -0.67841717E+00\r\n -0.11467999E+01\r\n  0.11005083E-02\r\n -0.67336022E+00\r\n -0.11382489E+01\r\n  0.18317815E-03\r\n -0.61788539E+00\r\n -0.10444794E+01\r\n -0.23565402E-05\r\n -0.55906796E+00\r\n -0.94504933E+00\r\n -0.22613593E-05\r\n -0.50507304E+00\r\n -0.85377435E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.39444853E-06\r\n -0.69842407E+00\r\n -0.11806161E+01\r\n -0.11278175E-05\r\n -0.69505700E+00\r\n -0.11749439E+01\r\n  0.17555177E-04\r\n -0.69741390E+00\r\n -0.11789090E+01\r\n  0.17626733E-03\r\n -0.69548116E+00\r\n -0.11756298E+01\r\n  0.37656054E-03\r\n -0.69884659E+00\r\n -0.11813309E+01\r\n  0.18953378E-03\r\n -0.69366649E+00\r\n -0.11725707E+01\r\n  0.19224752E-05\r\n -0.69573161E+00\r\n -0.11760656E+01\r\n  0.72776430E-07\r\n -0.64863065E+00\r\n -0.10964368E+01\r\n -0.37043390E-05\r\n -0.60671845E+00\r\n -0.10255977E+01\r\n -0.36241908E-05\r\n -0.54781537E+00\r\n -0.92601912E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.19012713E-04\r\n -0.64575511E+00\r\n -0.10915739E+01\r\n  0.51958204E-05\r\n -0.66149195E+00\r\n -0.11181860E+01\r\n  0.41671327E-05\r\n -0.69065903E+00\r\n -0.11674826E+01\r\n  0.20589718E-05\r\n -0.71540506E+00\r\n -0.12093218E+01\r\n -0.41078028E-05\r\n -0.71694651E+00\r\n -0.12119179E+01\r\n -0.19347201E-05\r\n -0.71415345E+00\r\n -0.12072059E+01\r\n -0.23046668E-05\r\n -0.71538948E+00\r\n -0.12093029E+01\r\n -0.15559414E-05\r\n -0.71176873E+00\r\n -0.12031754E+01\r\n -0.73063887E-07\r\n -0.70022290E+00\r\n -0.11836332E+01\r\n  0.62054871E-05\r\n -0.65305800E+00\r\n -0.11039304E+01\r\n -0.72453857E-05\r\n -0.57615041E+00\r\n -0.97392807E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.16038825E-04\r\n -0.53943966E+00\r\n -0.91187777E+00\r\n -0.10430093E-05\r\n -0.58970937E+00\r\n -0.99684495E+00\r\n -0.49696521E-05\r\n -0.64340420E+00\r\n -0.10876054E+01\r\n -0.22329447E-05\r\n -0.69263650E+00\r\n -0.11708354E+01\r\n  0.10760681E-04\r\n -0.73892071E+00\r\n -0.12490696E+01\r\n  0.50173076E-05\r\n -0.74118669E+00\r\n -0.12529037E+01\r\n  0.68646709E-05\r\n -0.73670040E+00\r\n -0.12453183E+01\r\n -0.13448756E-05\r\n -0.73624371E+00\r\n -0.12445482E+01\r\n  0.40206064E-05\r\n -0.73075910E+00\r\n -0.12352771E+01\r\n -0.90326372E-05\r\n -0.68330929E+00\r\n -0.11550697E+01\r\n -0.19861518E-04\r\n -0.60926912E+00\r\n -0.10299216E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.46458303E-05\r\n -0.46478996E+00\r\n -0.78568709E+00\r\n -0.11749638E-04\r\n -0.52107741E+00\r\n -0.88083010E+00\r\n -0.27788905E-05\r\n -0.57184261E+00\r\n -0.96663572E+00\r\n -0.16167461E-04\r\n -0.64224198E+00\r\n -0.10856490E+01\r\n -0.41299555E-05\r\n -0.72606644E+00\r\n -0.12273160E+01\r\n -0.13886318E-04\r\n -0.75255815E+00\r\n -0.12721290E+01\r\n -0.92050466E-05\r\n -0.75848577E+00\r\n -0.12821369E+01\r\n  0.79349533E-05\r\n -0.75643700E+00\r\n -0.12786842E+01\r\n -0.24503081E-05\r\n -0.75643239E+00\r\n -0.12786750E+01\r\n -0.17133109E-05\r\n -0.71868438E+00\r\n -0.12148642E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.87522032E-05\r\n -0.40997152E+00\r\n -0.69301945E+00\r\n -0.81547734E-05\r\n -0.45879548E+00\r\n -0.77554885E+00\r\n -0.13747454E-04\r\n -0.51738513E+00\r\n -0.87459035E+00\r\n  0.77440868E-05\r\n -0.59198985E+00\r\n -0.10007045E+01\r\n -0.21312925E-04\r\n -0.67509196E+00\r\n -0.11411619E+01\r\n  0.56932475E-05\r\n -0.78494207E+00\r\n -0.13268755E+01\r\n -0.13946572E-04\r\n -0.77182693E+00\r\n -0.13046697E+01\r\n -0.11045417E-04\r\n -0.77288926E+00\r\n -0.13064968E+01\r\n -0.11674239E-04\r\n -0.76545634E+00\r\n -0.12939092E+01\r\n -0.19866208E-04\r\n -0.74732760E+00\r\n -0.12632829E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.34535457E-05\r\n -0.31336739E+00\r\n -0.52971623E+00\r\n  0.24296697E-06\r\n -0.37415911E+00\r\n -0.63247865E+00\r\n -0.22256012E-05\r\n -0.41950437E+00\r\n -0.70913135E+00\r\n -0.10299729E-04\r\n -0.46842439E+00\r\n -0.79182793E+00\r\n -0.11236372E-04\r\n -0.56268915E+00\r\n -0.95117478E+00\r\n -0.17455445E-04\r\n -0.64775557E+00\r\n -0.10949579E+01\r\n -0.50071338E-04\r\n -0.72985406E+00\r\n -0.12337681E+01\r\n -0.10169126E-04\r\n -0.79241794E+00\r\n -0.13395053E+01\r\n -0.54241855E-05\r\n -0.78673965E+00\r\n -0.13299096E+01\r\n -0.27368962E-05\r\n -0.78572068E+00\r\n -0.13281721E+01\r\n -0.21514621E-04\r\n -0.77033882E+00\r\n -0.13021807E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.22923616E-05\r\n -0.31547640E+00\r\n -0.53328130E+00\r\n -0.40516783E-05\r\n -0.31265450E+00\r\n -0.52851059E+00\r\n -0.57661815E-05\r\n -0.37775848E+00\r\n -0.63856463E+00\r\n -0.25586938E-05\r\n -0.44268374E+00\r\n -0.74831429E+00\r\n -0.49584183E-05\r\n -0.51081530E+00\r\n -0.86348621E+00\r\n -0.66552786E-05\r\n -0.59014282E+00\r\n -0.99756439E+00\r\n -0.39262067E-05\r\n -0.72695048E+00\r\n -0.12288458E+01\r\n  0.21200911E-05\r\n -0.80108884E+00\r\n -0.13541672E+01\r\n -0.10099852E-04\r\n -0.79986012E+00\r\n -0.13520873E+01\r\n  0.49990834E-05\r\n -0.79593480E+00\r\n -0.13454764E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.21803910E-05\r\n -0.33082342E+00\r\n -0.55923432E+00\r\n  0.27233588E-06\r\n -0.31431008E+00\r\n -0.53131064E+00\r\n -0.19962890E-05\r\n -0.31593264E+00\r\n -0.53405116E+00\r\n -0.37438644E-05\r\n -0.31593646E+00\r\n -0.53406066E+00\r\n -0.61062647E-06\r\n -0.40074212E+00\r\n -0.67742088E+00\r\n -0.43291055E-05\r\n -0.48068105E+00\r\n -0.81254646E+00\r\n -0.50593711E-05\r\n -0.58274882E+00\r\n -0.98507711E+00\r\n -0.29719517E-05\r\n -0.71178735E+00\r\n -0.12032092E+01\r\n -0.94859199E-06\r\n -0.81300493E+00\r\n -0.13743075E+01\r\n -0.12937396E-04\r\n -0.80142190E+00\r\n -0.13547251E+01\r\n -0.17955245E-04\r\n -0.80004249E+00\r\n -0.13523941E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.34550382E-05\r\n -0.37763105E+00\r\n -0.63835282E+00\r\n -0.66919980E-05\r\n -0.32900294E+00\r\n -0.55614735E+00\r\n -0.28111336E-05\r\n -0.31413021E+00\r\n -0.53100365E+00\r\n -0.88323442E-06\r\n -0.31961926E+00\r\n -0.54028648E+00\r\n -0.10614214E-04\r\n -0.34939198E+00\r\n -0.59060352E+00\r\n  0.10594819E-05\r\n -0.45497981E+00\r\n -0.76910013E+00\r\n -0.46984886E-05\r\n -0.55102613E+00\r\n -0.93145259E+00\r\n -0.48102490E-05\r\n -0.68564782E+00\r\n -0.11590213E+01\r\n -0.95605717E-06\r\n -0.81497777E+00\r\n -0.13776385E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.19850434E-05\r\n -0.46652454E+00\r\n -0.78861308E+00\r\n -0.34539835E-05\r\n -0.42162136E+00\r\n -0.71271825E+00\r\n -0.68278058E-06\r\n -0.37578995E+00\r\n -0.63523639E+00\r\n -0.98047378E-06\r\n -0.31653168E+00\r\n -0.53506158E+00\r\n -0.16492219E-05\r\n -0.31753365E+00\r\n -0.53676042E+00\r\n -0.51517036E-05\r\n -0.33705691E+00\r\n -0.56976425E+00\r\n -0.22231837E-04\r\n -0.41263982E+00\r\n -0.69752866E+00\r\n  0.84971603E-05\r\n -0.55866818E+00\r\n -0.94437437E+00\r\n -0.15677310E-04\r\n -0.66436600E+00\r\n -0.11230482E+01\r\n -0.13341378E-04\r\n -0.79867406E+00\r\n -0.13500775E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.23323241E-05\r\n -0.46751943E+00\r\n -0.79029484E+00\r\n  0.10315786E-04\r\n -0.46854070E+00\r\n -0.79201667E+00\r\n -0.33532295E-05\r\n -0.39108471E+00\r\n -0.66109043E+00\r\n -0.16521591E-06\r\n -0.32960973E+00\r\n -0.55717415E+00\r\n -0.12620752E-05\r\n -0.31825347E+00\r\n -0.53797677E+00\r\n -0.22622202E-05\r\n -0.33569787E+00\r\n -0.56745673E+00\r\n -0.64161669E-05\r\n -0.41959159E+00\r\n -0.70927964E+00\r\n -0.31584037E-04\r\n -0.54021088E+00\r\n -0.91317481E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.60439200E-05\r\n -0.46607089E+00\r\n -0.78784623E+00\r\n -0.20541069E-05\r\n -0.46682901E+00\r\n -0.78912858E+00\r\n -0.17550235E-05\r\n -0.38831959E+00\r\n -0.65641592E+00\r\n  0.19694874E-05\r\n -0.33082038E+00\r\n -0.55921016E+00\r\n  0.14344787E-05\r\n -0.31605076E+00\r\n -0.53425337E+00\r\n -0.84770233E-05\r\n -0.33268918E+00\r\n -0.56236811E+00\r\n  0.89194562E-05\r\n -0.42185938E+00\r\n -0.71311363E+00\r\n  0.26511716E-06\r\n -0.53598003E+00\r\n -0.90603132E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.54260049E-05\r\n -0.46620085E+00\r\n -0.78806591E+00\r\n  0.27218236E-05\r\n -0.44965874E+00\r\n -0.76011034E+00\r\n -0.12675630E-05\r\n -0.37355368E+00\r\n -0.63145550E+00\r\n  0.86251805E-06\r\n -0.31144821E+00\r\n -0.52647519E+00\r\n -0.94779313E-06\r\n -0.31461331E+00\r\n -0.53182295E+00\r\n -0.12677737E-05\r\n -0.34610251E+00\r\n -0.58504794E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.77216518E-05\r\n -0.40432863E+00\r\n -0.68347667E+00\r\n -0.65683610E-07\r\n -0.32459688E+00\r\n -0.54869865E+00\r\n  0.38143907E-06\r\n -0.31162344E+00\r\n -0.52676415E+00\r\n  0.10659711E-05\r\n -0.31201245E+00\r\n -0.52742629E+00\r\n -0.31393068E-07\r\n -0.36084677E+00\r\n -0.60998104E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.30716571E-05\r\n -0.31077867E+00\r\n -0.52534027E+00\r\n -0.43111039E-06\r\n -0.30882335E+00\r\n -0.52203278E+00\r\n  0.12214547E-05\r\n -0.34230789E+00\r\n -0.57863771E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.46257771E-05\r\n -0.30947873E+00\r\n -0.52314285E+00\r\n  0.11230187E-05\r\n -0.30889848E+00\r\n -0.52216158E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.15262064E+01\r\n -0.33090381E+01\r\n -0.55935980E+01\r\n -0.10995579E+01\r\n -0.35566602E+01\r\n -0.60121910E+01\r\n -0.95196898E+00\r\n -0.36325096E+01\r\n -0.61403943E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.71494664E+00\r\n -0.41858508E+01\r\n -0.70757623E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.10504815E+01\r\n -0.38935606E+01\r\n -0.65816757E+01\r\n -0.65785838E+00\r\n -0.41074444E+01\r\n -0.69432242E+01\r\n -0.57144652E+00\r\n -0.41371735E+01\r\n -0.69934691E+01\r\n  0.41099112E+00\r\n -0.69170369E+00\r\n -0.11692564E+01\r\n  0.16529191E+00\r\n -0.51152301E+00\r\n -0.86468364E+00\r\n  0.62338300E-01\r\n -0.42756221E+00\r\n -0.72275117E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.19487414E+00\r\n -0.78161394E+00\r\n -0.13212404E+01\r\n -0.21719217E+00\r\n -0.46521428E+01\r\n -0.78639731E+01\r\n -0.22592071E+00\r\n -0.46393976E+01\r\n -0.78424377E+01\r\n -0.23935866E+00\r\n -0.46285000E+01\r\n -0.78240151E+01\r\n -0.24464477E+00\r\n -0.46217358E+01\r\n -0.78125822E+01\r\n  0.37947245E+00\r\n -0.85786354E+00\r\n -0.14501260E+01\r\n  0.13127482E+00\r\n -0.67509707E+00\r\n -0.11411847E+01\r\n  0.48557227E-01\r\n -0.57819252E+00\r\n -0.97736893E+00\r\n  0.13526292E-01\r\n -0.51461205E+00\r\n -0.86990111E+00\r\n  0.61471090E-02\r\n -0.47132774E+00\r\n -0.79673015E+00\r\n  0.49468496E-02\r\n -0.43830867E+00\r\n -0.74091705E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.15593223E-01\r\n -0.71408510E+00\r\n -0.12070895E+01\r\n  0.26556009E-01\r\n -0.71720185E+00\r\n -0.12123663E+01\r\n  0.33724910E-01\r\n -0.72368244E+00\r\n -0.12233129E+01\r\n  0.40136961E-01\r\n -0.72143388E+00\r\n -0.12195293E+01\r\n  0.38753434E-01\r\n -0.72356315E+00\r\n -0.12231114E+01\r\n  0.18237140E-01\r\n -0.70780665E+00\r\n -0.11964704E+01\r\n  0.79213715E-02\r\n -0.66372107E+00\r\n -0.11219548E+01\r\n  0.49058533E-02\r\n -0.61682435E+00\r\n -0.10426771E+01\r\n  0.18340632E-02\r\n -0.56160525E+00\r\n -0.94933894E+00\r\n  0.15584380E-02\r\n -0.51443330E+00\r\n -0.86959745E+00\r\n  0.32433237E-03\r\n -0.45990383E+00\r\n -0.77742144E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.20026106E-02\r\n -0.73284130E+00\r\n -0.12387949E+01\r\n  0.21106504E-02\r\n -0.73617889E+00\r\n -0.12444157E+01\r\n  0.31036832E-02\r\n -0.73192112E+00\r\n -0.12372398E+01\r\n  0.39019721E-02\r\n -0.73361373E+00\r\n -0.12401391E+01\r\n  0.47250335E-02\r\n -0.72988246E+00\r\n -0.12337936E+01\r\n  0.17903180E-02\r\n -0.73172469E+00\r\n -0.12369094E+01\r\n  0.16765488E-02\r\n -0.72839585E+00\r\n -0.12312815E+01\r\n  0.14747603E-02\r\n -0.67142582E+00\r\n -0.11349873E+01\r\n  0.47992153E-03\r\n -0.60735601E+00\r\n -0.10266754E+01\r\n -0.21995421E-05\r\n -0.54837970E+00\r\n -0.92698122E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.37540469E-03\r\n -0.75821003E+00\r\n -0.12816782E+01\r\n  0.75929842E-03\r\n -0.75484646E+00\r\n -0.12760103E+01\r\n  0.12721476E-02\r\n -0.75757842E+00\r\n -0.12806112E+01\r\n  0.17610847E-02\r\n -0.75572739E+00\r\n -0.12774873E+01\r\n  0.21797866E-02\r\n -0.75948931E+00\r\n -0.12838413E+01\r\n  0.18340514E-02\r\n -0.75382956E+00\r\n -0.12742610E+01\r\n  0.95625940E-03\r\n -0.75576823E+00\r\n -0.12775516E+01\r\n  0.95307621E-05\r\n -0.70377734E+00\r\n -0.11896828E+01\r\n  0.18464373E-05\r\n -0.65871648E+00\r\n -0.11134952E+01\r\n  0.44716180E-05\r\n -0.59489957E+00\r\n -0.10056409E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.17576459E-04\r\n -0.70136215E+00\r\n -0.11855891E+01\r\n  0.12008442E-04\r\n -0.71811897E+00\r\n -0.12139083E+01\r\n  0.12018808E-04\r\n -0.74951824E+00\r\n -0.12669860E+01\r\n  0.93681519E-05\r\n -0.77657870E+00\r\n -0.13127299E+01\r\n  0.16778629E-05\r\n -0.77794654E+00\r\n -0.13150384E+01\r\n  0.44673968E-05\r\n -0.77491752E+00\r\n -0.13099213E+01\r\n  0.15071943E-05\r\n -0.77637248E+00\r\n -0.13124036E+01\r\n  0.48165762E-05\r\n -0.77243688E+00\r\n -0.13057289E+01\r\n  0.10478180E-04\r\n -0.75998537E+00\r\n -0.12846952E+01\r\n  0.13107010E-04\r\n -0.70906833E+00\r\n -0.11986107E+01\r\n -0.50722414E-05\r\n -0.62548585E+00\r\n -0.10573175E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.12419986E-04\r\n -0.58595184E+00\r\n -0.99048779E+00\r\n  0.48147855E-05\r\n -0.64045010E+00\r\n -0.10826171E+01\r\n -0.25142174E-05\r\n -0.69877984E+00\r\n -0.11812119E+01\r\n  0.43019547E-05\r\n -0.75183846E+00\r\n -0.12709097E+01\r\n  0.16630537E-04\r\n -0.80204649E+00\r\n -0.13557728E+01\r\n  0.12346482E-04\r\n -0.80415182E+00\r\n -0.13593403E+01\r\n  0.67621486E-05\r\n -0.79931157E+00\r\n -0.13511575E+01\r\n  0.51967287E-05\r\n -0.79893118E+00\r\n -0.13505158E+01\r\n  0.89498202E-05\r\n -0.79328363E+00\r\n -0.13409688E+01\r\n -0.33266488E-05\r\n -0.74180317E+00\r\n -0.12539472E+01\r\n -0.15233154E-04\r\n -0.66154749E+00\r\n -0.11182700E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.19223968E-05\r\n -0.50530184E+00\r\n -0.85416090E+00\r\n -0.61814809E-05\r\n -0.56649563E+00\r\n -0.95760501E+00\r\n -0.22013850E-05\r\n -0.62106131E+00\r\n -0.10498414E+01\r\n -0.10310776E-04\r\n -0.69739357E+00\r\n -0.11788763E+01\r\n -0.23673627E-05\r\n -0.78808910E+00\r\n -0.13321802E+01\r\n -0.63241010E-05\r\n -0.81636590E+00\r\n -0.13799877E+01\r\n  0.41924869E-05\r\n -0.82277577E+00\r\n -0.13908122E+01\r\n  0.15804959E-04\r\n -0.82081299E+00\r\n -0.13875044E+01\r\n  0.17387077E-04\r\n -0.82106924E+00\r\n -0.13879656E+01\r\n  0.45349850E-05\r\n -0.78004278E+00\r\n -0.13185844E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n -0.51280017E-05\r\n -0.44622403E+00\r\n -0.75429165E+00\r\n -0.25244722E-05\r\n -0.49903143E+00\r\n -0.84356416E+00\r\n -0.88417906E-05\r\n -0.56253212E+00\r\n -0.95090892E+00\r\n  0.15206261E-04\r\n -0.64274428E+00\r\n -0.10864996E+01\r\n -0.19964766E-04\r\n -0.73232426E+00\r\n -0.12379073E+01\r\n  0.19901317E-04\r\n -0.85106672E+00\r\n -0.14386503E+01\r\n -0.65841589E-05\r\n -0.83701939E+00\r\n -0.14148842E+01\r\n -0.39377926E-05\r\n -0.83856117E+00\r\n -0.14175079E+01\r\n -0.74456242E-05\r\n -0.83089133E+00\r\n -0.14045317E+01\r\n -0.14641721E-04\r\n -0.81118722E+00\r\n -0.13712309E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.10031318E-04\r\n -0.34175735E+00\r\n -0.57770662E+00\r\n  0.52204219E-05\r\n -0.40770908E+00\r\n -0.68918729E+00\r\n  0.43838974E-05\r\n -0.45671306E+00\r\n -0.77202937E+00\r\n -0.12448984E-05\r\n -0.50938593E+00\r\n -0.86107302E+00\r\n -0.35282645E-05\r\n -0.61147283E+00\r\n -0.10336386E+01\r\n -0.92237562E-05\r\n -0.70257277E+00\r\n -0.11876224E+01\r\n -0.19790747E-04\r\n -0.79155376E+00\r\n -0.13380632E+01\r\n -0.12311129E-04\r\n -0.85899104E+00\r\n -0.14520437E+01\r\n  0.24987754E-05\r\n -0.85350853E+00\r\n -0.14427760E+01\r\n -0.48216252E-05\r\n -0.85269814E+00\r\n -0.14414079E+01\r\n -0.15858060E-04\r\n -0.83627770E+00\r\n -0.14136442E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.90615401E-05\r\n -0.34417517E+00\r\n -0.58179372E+00\r\n -0.22372602E-07\r\n -0.34086435E+00\r\n -0.57619304E+00\r\n  0.62647501E-06\r\n -0.41160313E+00\r\n -0.69577591E+00\r\n  0.47173876E-05\r\n -0.48184793E+00\r\n -0.81451995E+00\r\n  0.20263113E-05\r\n -0.55529347E+00\r\n -0.93867174E+00\r\n -0.31757637E-05\r\n -0.64052595E+00\r\n -0.10827418E+01\r\n  0.76586851E-05\r\n -0.78831985E+00\r\n -0.13325834E+01\r\n  0.14396884E-05\r\n -0.86912419E+00\r\n -0.14691915E+01\r\n -0.29478576E-05\r\n -0.86794837E+00\r\n -0.14671827E+01\r\n  0.31289099E-06\r\n -0.86401590E+00\r\n -0.14605308E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.87405669E-05\r\n -0.36063124E+00\r\n -0.60961186E+00\r\n  0.66210980E-05\r\n -0.34285397E+00\r\n -0.57956141E+00\r\n  0.16397731E-05\r\n -0.34464530E+00\r\n -0.58258152E+00\r\n  0.20268795E-05\r\n -0.34443634E+00\r\n -0.58223663E+00\r\n  0.45575515E-05\r\n -0.43651951E+00\r\n -0.73788988E+00\r\n  0.26015813E-05\r\n -0.52291758E+00\r\n -0.88394325E+00\r\n  0.53487280E-06\r\n -0.63317006E+00\r\n -0.10702990E+01\r\n  0.56459683E-05\r\n -0.77282508E+00\r\n -0.13063867E+01\r\n  0.62247018E-05\r\n -0.88255714E+00\r\n -0.14919108E+01\r\n -0.61726221E-05\r\n -0.86985659E+00\r\n -0.14704068E+01\r\n -0.17331946E-04\r\n -0.86850716E+00\r\n -0.14681238E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.14162502E-04\r\n -0.41144323E+00\r\n -0.69550083E+00\r\n -0.11975233E-05\r\n -0.35867596E+00\r\n -0.60630658E+00\r\n  0.22588616E-05\r\n -0.34272098E+00\r\n -0.57933422E+00\r\n  0.56065710E-05\r\n -0.34865306E+00\r\n -0.58936467E+00\r\n -0.48043723E-05\r\n -0.38072807E+00\r\n -0.64358021E+00\r\n  0.82632406E-05\r\n -0.49521199E+00\r\n -0.83710889E+00\r\n  0.37626127E-05\r\n -0.59891220E+00\r\n -0.10124041E+01\r\n  0.21057070E-05\r\n -0.74460432E+00\r\n -0.12586812E+01\r\n  0.12678650E-04\r\n -0.88531777E+00\r\n -0.14965587E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.85396360E-05\r\n -0.50760401E+00\r\n -0.85805382E+00\r\n -0.18473856E-05\r\n -0.45894137E+00\r\n -0.77579345E+00\r\n  0.57245816E-05\r\n -0.40948922E+00\r\n -0.69220165E+00\r\n  0.42157353E-05\r\n -0.34518905E+00\r\n -0.58350421E+00\r\n  0.47307198E-05\r\n -0.34642022E+00\r\n -0.58559044E+00\r\n -0.70538838E-06\r\n -0.36749160E+00\r\n -0.62120511E+00\r\n -0.17704109E-04\r\n -0.44920918E+00\r\n -0.75934523E+00\r\n  0.14319676E-04\r\n -0.60747806E+00\r\n -0.10268680E+01\r\n -0.10025376E-04\r\n -0.72165070E+00\r\n -0.12198814E+01\r\n -0.29572064E-05\r\n -0.86753038E+00\r\n -0.14664712E+01\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.85821419E-05\r\n -0.50854347E+00\r\n -0.85964188E+00\r\n  0.16493335E-04\r\n -0.51003093E+00\r\n -0.86216342E+00\r\n  0.24876358E-05\r\n -0.42590887E+00\r\n -0.71995724E+00\r\n  0.59709092E-05\r\n -0.35943482E+00\r\n -0.60758471E+00\r\n  0.49496341E-05\r\n -0.34715486E+00\r\n -0.58683164E+00\r\n  0.42827298E-05\r\n -0.36596509E+00\r\n -0.61862629E+00\r\n -0.57452087E-06\r\n -0.45678338E+00\r\n -0.77214869E+00\r\n -0.26366656E-04\r\n -0.58794746E+00\r\n -0.99385686E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.12565208E-04\r\n -0.50695871E+00\r\n -0.85696300E+00\r\n  0.46891907E-05\r\n -0.50808141E+00\r\n -0.85886385E+00\r\n  0.41420104E-05\r\n -0.42289361E+00\r\n -0.71486018E+00\r\n  0.80703502E-05\r\n -0.36065842E+00\r\n -0.60965826E+00\r\n  0.77446881E-05\r\n -0.34474650E+00\r\n -0.58276050E+00\r\n -0.25735036E-05\r\n -0.36269755E+00\r\n -0.61310652E+00\r\n  0.16030019E-04\r\n -0.45925201E+00\r\n -0.77632187E+00\r\n  0.99968945E-05\r\n -0.58320085E+00\r\n -0.98583832E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.11964946E-04\r\n -0.50713051E+00\r\n -0.85725341E+00\r\n  0.99516441E-05\r\n -0.48943012E+00\r\n -0.82733309E+00\r\n  0.46683721E-05\r\n -0.40693178E+00\r\n -0.68787787E+00\r\n  0.39080770E-05\r\n -0.33966027E+00\r\n -0.57416086E+00\r\n  0.50132371E-05\r\n -0.34315556E+00\r\n -0.58007083E+00\r\n  0.78247889E-05\r\n -0.37733096E+00\r\n -0.63783911E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.99089532E-05\r\n -0.44026646E+00\r\n -0.74422855E+00\r\n  0.54465978E-05\r\n -0.35375295E+00\r\n -0.59798408E+00\r\n  0.48361284E-05\r\n -0.33992768E+00\r\n -0.57461634E+00\r\n  0.68805448E-05\r\n -0.34022345E+00\r\n -0.57511425E+00\r\n  0.98595301E-05\r\n -0.39338020E+00\r\n -0.66496888E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.92026895E-05\r\n -0.33896389E+00\r\n -0.57298455E+00\r\n  0.35225491E-05\r\n -0.33682498E+00\r\n -0.56935837E+00\r\n  0.76078588E-05\r\n -0.37324699E+00\r\n -0.63093700E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.10923226E-04\r\n -0.33757462E+00\r\n -0.57063614E+00\r\n  0.59470629E-05\r\n -0.33692929E+00\r\n -0.56954298E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n  0.00000000E+00\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/sparselib.c",
    "content": "\n#include <stdlib.h>\n#include <stdio.h>\n#include <string.h>\n#include <math.h>\n#include \"commonlib.h\"\n#include \"myblas.h\"\n#include \"sparselib.h\"\n\n\nsparseMatrix *createMatrix(int dimLimit, int lenLimit, int initVectors)\n{\n  int          initsize;\n  sparseMatrix *matrix;\n\n  if(initVectors < 0)\n    initVectors = 0;\n  if(initVectors == 0)\n    initsize = MIN(INITIALSIZE, dimLimit);\n  else\n    initsize = MAX(INITIALSIZE, initVectors);\n\n  CALLOC(matrix, 1);\n  matrix->limit = dimLimit;\n  matrix->limitVector = lenLimit;\n  resizeMatrix(matrix, initsize);\n  while(initVectors > 0) {\n    initVectors--;\n    appendMatrix(matrix, createVector(lenLimit, 2));\n  }\n  return(matrix);\n}\n\n\nvoid resizeMatrix(sparseMatrix *matrix, int newSize)\n{\n  int oldSize;\n\n  if(matrix == NULL)\n    oldSize = 0;\n  else\n    oldSize = matrix->size;\n  while(oldSize>newSize) {\n\t  oldSize--;\n\t  freeVector(matrix->list[oldSize]);\n    return;\n  }\n  REALLOC(matrix->list, newSize);\n  while(oldSize<newSize) {\n\t  matrix->list[oldSize] = NULL;\n\t  oldSize++;\n  }\n  if(newSize>0)\n    matrix->size = newSize;\n}\n\nint appendMatrix(sparseMatrix *matrix, sparseVector *newVector)\n{\n   if(matrix->count == matrix->size)\n     resizeMatrix(matrix, matrix->size + 10);\n   matrix->list[matrix->count] = newVector;\n   matrix->count++;\n   putDiagonalIndex(newVector, matrix->count);\n   return(matrix->count);\n}\n\n\nint NZcountMatrix(sparseMatrix *matrix)\n{\n  int i, nz;\n\n  nz = 0;\n  for(i = 0; i < matrix->count; i++)\n    nz += matrix->list[i]->count;\n\n  return( nz );\n}\n\n\nvoid freeMatrix(sparseMatrix *matrix)\n{\n  resizeMatrix(matrix, 0);\n  FREE(matrix);\n}\n\n\nvoid printMatrix(int n, sparseMatrix *matrix, int modulo, MYBOOL showEmpty)\n{\n   int i;\n   for(i = 1; i<=matrix->count; i++) \n     if(matrix->list[i-1] != NULL) { \n       if(showEmpty || matrix->list[i-1]->count>0)\n         printVector(n, matrix->list[i-1], modulo);\n   }\n}\n\n\nsparseVector *createVector(int dimLimit, int initSize)\n{\n  sparseVector *newitem;\n  CALLOC(newitem, 1);\n  newitem->limit = dimLimit;\n  initSize = resizeVector(newitem, initSize);\n  return(newitem);\n}\n\n\nsparseVector *cloneVector(sparseVector *sparse)\n{\n  sparseVector *hold;\n  hold = createVector(sparse->limit, sparse->count);\n  hold->count = sparse->count;\n  MEMCOPY(&hold->value[0], &sparse->value[0], (sparse->count+1));\n  MEMCOPY(&hold->index[0], &sparse->index[0], (sparse->count+1));\n  return(hold);\n}\n\nint redimensionVector(sparseVector *sparse, int newDim)\n{\n  int olddim, i;\n\n  olddim = sparse->limit;\n  sparse->limit = newDim;\n  if(lastIndex(sparse)>newDim) {\n    i = sparse->count;\n    while(i>0 && sparse->index[i]>newDim) i--;\n    sparse->count = i;\n    resizeVector(sparse, sparse->count);\n  }\n  return(olddim);\n}\n\n\nint resizeVector(sparseVector *sparse, int newSize)\n{\n  int oldsize;\n\n  oldsize = sparse->size;\n  REALLOC(sparse->value, (newSize+1));\n  REALLOC(sparse->index, (newSize+1));\n  sparse->size = newSize;\n  return(oldsize);\n}\n\n\nvoid moveVector(sparseVector *sparse, int destPos, int sourcePos, int itemCount)\n{\n  int i;\n  \n  if(itemCount <= 0 || sourcePos == destPos)\n    return;\n\n#if defined DOFASTMATH\n  if(TRUE) {\n    MEMMOVE(&sparse->value[destPos], &sparse->value[sourcePos], itemCount);\n    MEMMOVE(&sparse->index[destPos], &sparse->index[sourcePos], itemCount);\n  }\n  else {\n    int    *idxPtr1, *idxPtr2;\n    double *valPtr1, *valPtr2;\n\n    for(i = 1, idxPtr1 = sparse->index+destPos, idxPtr2 = sparse->index+sourcePos,\n               valPtr1 = sparse->value+destPos, valPtr2 = sparse->value+sourcePos; \n        i<=itemCount; i++, idxPtr1++, idxPtr2++, valPtr1++, valPtr2++) {\n      *idxPtr1 = *idxPtr2;\n      *valPtr1 = *valPtr2;\n    }\n  }\n#else\n  for(i = 1; i<=itemCount; i++) {\n    sparse->value[destPos] = sparse->value[sourcePos];\n    sparse->index[destPos] = sparse->index[sourcePos];\n    destPos++;\n    sourcePos++;\n  }\n#endif\n}\n\n\nvoid rotateVector(sparseVector *sparse, int startPos, int chainSize, int stepDelta)\n{\n/*  int idxHold; */\n/*  double valHold; */\n\n}\n\n\nvoid swapVector(sparseVector *sparse1, sparseVector *sparse2)\n{\n  int n, m, *idx;\n  REAL *val;\n\n  n = sparse1->count;\n  sparse1->count = sparse2->count;\n  sparse2->count = n;\n\n  n = sparse1->size;\n  sparse1->size = sparse2->size;\n  sparse2->size = n;\n\n  n = sparse1->limit;\n  sparse1->limit = sparse2->limit;\n  sparse2->limit = n;\n\n  idx = sparse1->index;\n  sparse1->index = sparse2->index;\n  sparse2->index = idx;\n\n  val = sparse1->value;\n  sparse1->value = sparse2->value;\n  sparse2->value = val;\n\n  n = getDiagonalIndex(sparse1);\n  m = getDiagonalIndex(sparse2);\n  putDiagonalIndex(sparse1, m);\n  putDiagonalIndex(sparse2, n);\n\n}\n\n\nvoid freeVector(sparseVector *sparse)\n{\n\tif(sparse != NULL) {\n    FREE(sparse->value);\n    FREE(sparse->index);\n    FREE(sparse);\n  }\n}\n\n\nMYBOOL verifyVector(sparseVector *sparse)\n{\n  int i, n, k1, k2, kd; \n  int  err = 0;\n  double vd;\n\n  n = sparse->count;\n  kd = sparse->index[0];\n  vd = sparse->value[0];\n  if(n <= 1)\n    return(TRUE);\n  k1 = 0;\n  k2 = sparse->index[1];\n  if(k2 == kd && sparse->value[1] != vd) \n    err = 2;\n\n  for(i = 2; i <= n && err == 0; i++) {\n    k1 = k2;\n    k2 = sparse->index[i];\n    if(k1 >= k2) err = 1;\n    if(k2 == kd && sparse->value[i] != vd) err = 2;\n  }\n  if(err == 0)\n    return(TRUE);\n  else if(err == 1)\n    printf(\"Invalid sparse vector index order\");\n  else if(err == 2)\n    printf(\"Invalid sparse vector diagonal value\");\n  return(FALSE);\n}\n\n\nint firstIndex(sparseVector *sparse)\n{\n  return(sparse->index[1]);\n}\n\n\nint lastIndex(sparseVector *sparse)\n{\n  return(sparse->index[sparse->count]);\n}\n\n\nint getDiagonalIndex(sparseVector *sparse)\n{\n  return(sparse->index[0]);\n}\n\n\nint putDiagonalIndex(sparseVector *sparse, int index)\n{\n  int oldindex;\n  oldindex = sparse->index[0];\n  if(index > 0) {\n    sparse->index[0] = 0; /* Must temporarily set to zero to force vector search in getItem */\n    sparse->value[0] = getItem(sparse, index);\n  }\n  else\n    sparse->value[0] = 0;\n  sparse->index[0] = index;\n  return(oldindex);\n}\n\n\nMYBOOL putDiagonal(sparseVector *sparse, REAL value)\n{\n  if(sparse->index[0]>0) {\n    putItem(sparse, sparse->index[0], value); \n    return(TRUE);\n  }\n  else\n    return(FALSE);\n}\n\n\nREAL getDiagonal(sparseVector *sparse)\n{\n   return(sparse->value[0]);\n}\n\n\nREAL getItem(sparseVector *sparse, int targetIndex)\n{\n  /* First check if we want the diagonal element */ \n  if(targetIndex == sparse->index[0])\n    return(sparse->value[0]);\n\n  /* If not, search for the variable's position in the index list */\n  targetIndex = findIndex(targetIndex, sparse->index, sparse->count, BLAS_BASE);\n  if(targetIndex < 0)\n    return(0);\n  else\n    return(sparse->value[targetIndex]);\n}\n\n\nREAL addtoItem(sparseVector *sparse, int targetIndex, REAL value)\n{\n  int idx;\n\n  if(targetIndex > 0) \n    idx = findIndex(targetIndex, sparse->index, sparse->count, BLAS_BASE);\n  else {\n    idx = -targetIndex;\n    if(idx > sparse->count)\n      /* Index error; ignore item */\n      return(0.0);\n  }\n\n  if(idx <=0 )\n    value = putItem(sparse, targetIndex, value);\n  else {\n    value += sparse->value[idx];\n    putItem(sparse, -idx, value);\n  }\n  return(value);\n}\n\n\nREAL putItem(sparseVector *sparse, int targetIndex, REAL value)\n{\n  REAL last = 0.0;\n  int  posIndex;\n\n  if(targetIndex < 0) {\n    posIndex = -targetIndex;\n    if(posIndex > sparse->count)\n      return(last);\n    targetIndex = sparse->index[posIndex];\n  }\n  else\n    posIndex = findIndex(targetIndex, sparse->index, sparse->count, BLAS_BASE);\n\n  if(fabs(value) < MACHINEPREC)\n    value = 0;\n\n  if(targetIndex == sparse->index[0]) \n    sparse->value[0] = value;\n\n  if(posIndex < 0) {\n    if(value != 0) {\n      if(sparse->count == sparse->size)\n        resizeVector(sparse, sparse->size + RESIZEDELTA);\n      posIndex = -posIndex;\n      sparse->count++;\n      if(posIndex < sparse->count) \n        moveVector(sparse, posIndex+1, posIndex, sparse->count-posIndex);\n      sparse->value[posIndex] = value;\n      sparse->index[posIndex] = targetIndex;\n    }\n  }\n  else {\n    if(value == 0) {\n      last = sparse->value[posIndex];\n      if(sparse->count > posIndex) \n        moveVector(sparse, posIndex, posIndex+1, sparse->count-posIndex);\n      sparse->count--;\n    }\n    else {\n      sparse->value[posIndex] = value;\n      sparse->index[posIndex] = targetIndex;\n    }\n  }\n\n#ifdef DEBUG_SPARSELIB\n  verifyVector(sparse);\n#endif\n\n  return(last);\n}\n\n\nvoid swapItems(sparseVector *sparse, int firstIndex, int secondIndex)\n{\n  int i,j,ki,kj;\n  REAL hold;\n\n  if(firstIndex == secondIndex)\n    return;\n  if(firstIndex > secondIndex) {\n    i = firstIndex;\n    firstIndex = secondIndex;\n    secondIndex = i;\n  }\n\n  if(FALSE) {\n    i = 1;\n    ki = 0;\n    while(i <= sparse->count && (ki = sparse->index[i])<firstIndex) i++;\n    j = i;\n    kj = 0;\n    while(j <= sparse->count && (kj = sparse->index[j])<secondIndex) j++;\n  }\n  else {\n    i = findIndex(firstIndex, sparse->index, sparse->count, BLAS_BASE);\n    if(i < 0)\n      i = -i;\n    j = findIndex(secondIndex, sparse->index, sparse->count, BLAS_BASE);\n    if(j < 0)\n      j = -j;\n  }\n\n  if(i > sparse->count)\n    ki = 0;\n  else\n    ki = sparse->index[i];\n  if(j > sparse->count)\n    kj = 0;\n  else\n    kj = sparse->index[j];\n\n  if(ki == firstIndex && kj == secondIndex) {   /* Found both -> swap in place */\n    hold = sparse->value[i];\n    sparse->value[i] = sparse->value[j];\n    sparse->value[j] = hold;\n\n    if(sparse->index[0] == firstIndex)\n      sparse->value[0] = sparse->value[i];\n    else if(sparse->index[0] == secondIndex)\n      sparse->value[0] = sparse->value[j];\n  }\n  else if(ki == firstIndex) {                   /* Found first, but not the second -> shift left */\n    j--;\n    if(i < j) {\n      hold = sparse->value[i];\n      moveVector(sparse, i, i+1, j-i);\n      sparse->value[j] = hold;\n    }\n    sparse->index[j] = secondIndex;\n\n    if(sparse->index[0] == firstIndex)\n      sparse->value[0] = 0;\n    else if(sparse->index[0] == secondIndex)\n      sparse->value[0] = sparse->value[j];\n\n  }\n  else if(kj == secondIndex) {                  /* Found second, but not the first -> shift right */\n    if(i < j) {\n      hold = sparse->value[j];\n      moveVector(sparse, i+1, i, j-i);\n      sparse->value[i] = hold;\n    }\n    sparse->index[i] = firstIndex;\n\n    if(sparse->index[0] == firstIndex)\n      sparse->value[0] = sparse->value[i];\n    else if(sparse->index[0] == secondIndex)\n      sparse->value[0] = 0;\n  }\n\n#ifdef DEBUG_SPARSELIB\n  verifyVector(sparse);\n#endif\n\n}\n\n\nvoid clearVector(sparseVector *sparse, int indexStart, int indexEnd)\n{\n  int i;\n\n  i = sparse->count;\n  if(i==0) return;\n\n  if(indexStart<=0)\n    indexStart=sparse->index[1];\n  if(indexEnd<=0)\n    indexEnd=sparse->index[i];\n\n  if(indexStart>indexEnd) return;\n\n  if(sparse->index[0]>=indexStart && sparse->index[0]<=indexEnd) {\n    sparse->value[0] = 0;\n  }\n  if(indexStart<=sparse->index[1] && indexEnd>=sparse->index[i]) \n    sparse->count = 0;\n  else {\n    while(i>0 && sparse->index[i]>indexEnd) i--;\n    indexEnd = i;\n    while(i>0 && sparse->index[i]>=indexStart) i--;\n    indexStart = i+1;\n    if(indexEnd>=indexStart) {\n      i = sparse->count-indexEnd;\n      moveVector(sparse, indexStart, indexEnd+1, i);\n      sparse->count -= indexEnd-indexStart+1;\n    }\n  }\n\n#ifdef DEBUG_SPARSELIB\n  verifyVector(sparse);\n#endif\n\n}\n\n\nint getVector(sparseVector *sparse, REAL *dense, int indexStart, int indexEnd, MYBOOL doClear)\n{\n  int i,k;\n\n  i = 1;\n  while(i<=sparse->count && sparse->index[i]<indexStart) i++;\n\n  while(i<=sparse->count && (k=sparse->index[i])<=indexEnd) {\n    while(indexStart<k) {\n      dense[indexStart] = 0;\n      indexStart++;\n    }\n    dense[indexStart] = sparse->value[i];\n    indexStart++;\n    i++;\n  }\n\n  while(indexStart<=indexEnd) {\n    dense[indexStart] = 0;\n    indexStart++;\n  }\n\n  k = sparse->count;\n  if(doClear) {\n    sparse->count = 0;\n    sparse->value[0] = 0;\n  }\n  return(k);\n}\n\nvoid putVector(sparseVector *sparse, REAL *dense, int indexStart, int indexEnd)\n{\n  int i,n;\n\n  n = sparse->count;\n  if(indexStart<=0)\n    indexStart=sparse->index[1];\n  if(indexEnd<=0)\n    indexEnd=sparse->index[n];\n\n  if(n==0 || sparse->index[n]<indexStart) {\n    i = sparse->index[0];\n    if(i>=indexStart && i<=indexEnd)\n      sparse->value[0] = 0;\n    for(i = indexStart; i<=indexEnd; i++) {\n      if(dense[i] == 0) continue;\n      if(sparse->size == sparse->count)\n        resizeVector(sparse, sparse->size + RESIZEDELTA);\n      sparse->count++;\n      sparse->value[sparse->count] = dense[i];\n      sparse->index[sparse->count] = i;\n      if(i == sparse->index[0]) \n        sparse->value[0] = dense[i];\n    }\n  }\n  else {\n    while(indexStart <= indexEnd) {\n      putItem(sparse, indexStart, dense[indexStart]);\n      indexStart++;\n    }\n  }\n\n#ifdef DEBUG_SPARSELIB\n  verifyVector(sparse);\n#endif\n\n}\n\n\nvoid fillVector(sparseVector *sparse, int count, REAL value)\n{\n  int i;\n\n  if(sparse->count > 0) \n    clearVector(sparse, 0, 0);\n  for(i = 1; i<=count; i++)\n    putItem(sparse, i, value);\n}\n\n\nREAL dotVector(sparseVector *sparse, REAL *dense, int indexStart, int indexEnd)\n{\n  int  i, n;\n  long REAL sum;\n  \n  n = sparse->count;\n  sum = 0;\n\n  if(n > 0) {\n    if(indexStart<=0)\n      indexStart=sparse->index[1];\n    if(indexEnd<=0)\n      indexEnd=sparse->index[n];\n\n    if(indexStart > 1) {\n      i = findIndex(indexStart, sparse->index, sparse->count, BLAS_BASE);\n      if(i < 0) {\n        i = -i;\n        if(i > n) \n          return(sum);\n      }\n    }\n    else\n      i = 1;\n\n    /* CPU intensive loop; provide alternative evaluation models */\n#if defined DOFASTMATH\n    {\n      /* Do fast pointer arithmetic */\n      int  *indexptr;\n      REAL *valueptr;\n/*      for(i = 1, indexptr = sparse->index + 1;\n          i <= n && (*indexptr) < indexStart; i++, indexptr++); */\n      indexptr = sparse->index + i;\n      for(valueptr = sparse->value + i;\n          i <= n && (*indexptr) <= indexEnd;  i++, indexptr++, valueptr++) \n        sum += (*valueptr) * dense[(*indexptr)];\n    }\n#else\n    {\n      /* Do traditional indexed access */\n      int k;\n/*      i = 1; */\n/*      while(i<=n && sparse->index[i]<indexStart) i++; */\n      while(i<=n && (k = sparse->index[i])<=indexEnd) {\n        sum += sparse->value[i] * dense[k];\n        i++;\n      }\n    }\n#endif    \n  }\n\n  return(sum);\n}\n\n\nvoid daxpyVector1(sparseVector *sparse, REAL scalar, REAL *dense, int indexStart, int indexEnd)\n{\n  int i, n;\n\n  if(scalar == 0) return;\n\n  n = sparse->count;\n  if(indexStart<=0)\n    indexStart=sparse->index[1];\n  if(indexEnd<=0)\n    indexEnd=sparse->index[n];\n\n  /* CPU intensive loop; provide alternative evaluation models */\n#if defined DOFASTMATH\n  {\n    /* Do fast pointer arithmetic */\n    int    *indexptr;\n    REAL *valueptr;\n    for(i = 1, indexptr = sparse->index + 1;\n        i <= n && (*indexptr) < indexStart; i++, indexptr++);\n    for(valueptr = sparse->value + i;\n        i <= n && (*indexptr) <= indexEnd;  i++, indexptr++, valueptr++) \n      dense[(*indexptr)] += (*valueptr) * scalar;\n  }\n#else\n  {\n    /* Do traditional indexed access */\n    int k;\n    for(i = 1; i<= n; i++) {\n      k = sparse->index[i];\n      if(k<indexStart) continue;\n      if(k>indexEnd) break;\n      dense[k] += sparse->value[i] * scalar;\n    }\n  }\n#endif  \n}\nvoid daxpyVector2(REAL *dense, REAL scalar, sparseVector *sparse, int indexStart, int indexEnd)\n{\n  sparseVector *hold;\n\n  hold = createVector(sparse->limit, sparse->count);\n  putDiagonalIndex(hold, getDiagonalIndex(sparse));\n  putVector(hold, dense, indexStart, indexEnd);\n  daxpyVector3(hold, scalar, sparse, indexStart, indexEnd);\n  freeVector(hold);\n}\nvoid daxpyVector3(sparseVector *sparse1, REAL scalar, sparseVector *sparse2, int indexStart, int indexEnd)\n{\n  int i1, i2, k, p1, p2, c1, c2;\n  sparseVector *hold;\n\n  if(sparse1->count == 0) return;\n\n /* Spool to start positions */\n  i1 = 1;\n  c1 = sparse1->count;\n  while(i1 <= c1 && sparse1->index[i1] < indexStart) i1++;\n  if(i1 <= c1)\n    p1 = sparse1->index[i1];\n  else\n    p1 = indexEnd+1;\n\n  i2 = 1;\n  c2 = sparse2->count;\n  while(i2 <= c2 && sparse2->index[i2] < indexStart) i2++;\n  if(i2 <= c2)\n    p2 = sparse2->index[i2];\n  else\n    p2 = indexEnd+1;\n\n /* Create a temporary vector */\n  k = c1+c2;\n  if(k > 0) {\n    hold = createVector(MAX(sparse1->limit, sparse2->limit), k);\n    putDiagonalIndex(hold, getDiagonalIndex(sparse2));\n  }\n  else\n    hold = sparse2;\n\n /* Loop over all items in both vectors */\n  while((i1 <= c1 && p1 <= indexEnd) || \n        (i2 <= c2 && p2 <= indexEnd)) {\n\n    k = 0;\n\n   /* Add/spool exclusive right-vector items */\n    while(i2 <= c2 && p2 < p1) {\n      if(hold != sparse2)\n        putItem(hold, p2, sparse2->value[i2]);\n      i2++;\n      if(i2 <= c2)\n        p2 = sparse2->index[i2];\n      else\n        p2 = indexEnd+1;\n      k++;\n    }\n   /* Add equal-indexed items */\n    while(i1 <= c1 && i2 <= c2 && p1 == p2) {\n/*      if(hold != sparse2) */\n        putItem(hold, p1, scalar*sparse1->value[i1]+sparse2->value[i2]);\n/*      else\n          addtoItem(sparse2, -i2, scalar*sparse1->value[i1]); */\n      i1++;\n      if(i1 <= c1)\n        p1 = sparse1->index[i1];\n      else\n        p1 = indexEnd+1;\n      i2++;\n      if(i2 <= c2)\n        p2 = sparse2->index[i2];\n      else\n        p2 = indexEnd+1;\n      k++;\n    }\n   /* Add exclusive left-vector items */\n    while(i1 <= c1 && p1 < p2) {\n      putItem(hold, p1, scalar*sparse1->value[i1]);\n/*      if(hold == sparse2) c2++; */\n      i1++;\n      if(i1 <= c1)\n        p1 = sparse1->index[i1];\n      else\n        p1 = indexEnd+1;\n      k++;\n    }\n\n    if(k == 0) break;\n  }\n\n/*  if(hold != sparse2) */\n  {\n    swapVector(hold, sparse2);\n    freeVector(hold);\n  }\n\n#ifdef DEBUG_SPARSELIB\n  verifyVector(sparse2);\n#endif\n\n}\n\n\nvoid dswapVector1(sparseVector *sparse, REAL *dense, int indexStart, int indexEnd)\n{\n  int i, d, n;\n  REAL *x;\n\n  if(indexStart <= 0)\n    indexStart = 1;\n  n = lastIndex(sparse);\n  if(indexEnd <= 0) \n    indexEnd = n;\n  CALLOC(x, (MAX(indexEnd,n)+1));\n\n  getVector(sparse, x, indexStart, n, FALSE);\n  d = getDiagonalIndex(sparse);\n  clearVector(sparse, indexStart, n);\n  for(i = indexStart; i<=indexEnd; i++) {\n    if(dense[i] != 0)\n      putItem(sparse, i, dense[i]);\n  }\n  for(i = indexEnd+1; i<=n; i++) {\n    if(x[i] != 0)\n      putItem(sparse, i, x[i]);\n  }\n  MEMCOPY(&dense[indexStart], &x[indexStart], (indexEnd-indexStart+1));\n\n#ifdef DEBUG_SPARSELIB\n  verifyVector(sparse);\n#endif\n  \n  FREE(x);\n}\nvoid dswapVector2(REAL *dense, sparseVector *sparse, int indexStart, int indexEnd)\n{\n  dswapVector1(sparse, dense, indexStart, indexEnd);\n}\n\n\nvoid dswapVector3(sparseVector *sparse1, sparseVector *sparse2, int indexStart, int indexEnd)\n{\n\n  REAL *dense1, *dense2;\n\n  if(indexStart<=0)\n    indexStart = 1;\n  if(indexEnd<=0)\n    indexEnd = MAX(lastIndex(sparse1), lastIndex(sparse2));\n\n  if(indexStart <= firstIndex(sparse1) && indexStart <= firstIndex(sparse2) && \n     indexEnd >= lastIndex(sparse1) && indexEnd >= lastIndex(sparse2)) {\n    swapVector(sparse1, sparse2);\n  }\n  else {\n\n    CALLOC(dense1, (indexEnd+1));\n    CALLOC(dense2, (indexEnd+1));\n    getVector(sparse1, dense1, indexStart, indexEnd, TRUE);\n    getVector(sparse2, dense2, indexStart, indexEnd, TRUE);\n    clearVector(sparse1, indexStart, indexEnd);\n    clearVector(sparse2, indexStart, indexEnd);\n    putVector(sparse1, dense2, indexStart, indexEnd);\n    putVector(sparse2, dense1, indexStart, indexEnd);\n    FREE(dense1);\n    FREE(dense2);\n  }\n}\n\n\nint idamaxVector(sparseVector *sparse, int is, REAL *maxValue)\n{\n  int    i, n, imax;\n  REAL xmax;\n\n  n = sparse->count;\n  imax = 1;\n  if(n == 0)\n    xmax = 0;\n  else {\n    xmax = fabs(sparse->value[imax]);\n\n    /* CPU intensive loop; provide alternative evaluation models */\n#if defined DOFASTMATH\n    {\n      /* Do fast pointer arithmetic */\n      int  *indexptr;\n      REAL *valueptr;\n      for(i = 1, indexptr = sparse->index + 1;\n          i <= n && (*indexptr) <= is; i++, indexptr++);\n      for(valueptr = sparse->value + i;\n          i <= n; i++, indexptr++, valueptr++) {\n\t      if((*valueptr)>xmax) {\n\t\t      xmax = (*valueptr);\n\t\t      imax = (*indexptr);\n        }\n      }\n    }\n#else\n    {\n      REAL xtest;\n      /* Do traditional indexed access */\n      i = 1;\n      while(i <= n && sparse->index[i] <= is) i++;\n      for(; i<=n; i++) {\n        xtest = fabs(sparse->value[i]);\n\t      if(xtest>xmax) {\n\t\t      xmax = xtest;\n\t\t      imax = sparse->index[i];\n        }\n      }\n    }\n#endif    \n  }\n  if(maxValue != NULL)\n    (*maxValue) = sparse->index[imax];\n  return(imax);\n}\n\n\nvoid printVector(int n, sparseVector *sparse, int modulo )\n{\n  int i,j,k;\n\n  if(sparse == NULL) return;\n\n  if (modulo <= 0) modulo = 5;\n  for (i = 1, j = 1; j<=n; i++, j++) {\n    if(i<=sparse->count)\n      k = sparse->index[i];\n    else\n      k = n+1;\n    while (j < k) {\n      if(mod(j, modulo) == 1) \n        printf(\"\\n%2d:%12g\", j, 0.0);\n      else\n        printf(\" %2d:%12g\", j, 0.0);\n      j++;\n    }\n    if(k<=n) {\n      if(mod(j, modulo) == 1) \n        printf(\"\\n%2d:%12g\", k, sparse->value[i]);\n      else\n        printf(\" %2d:%12g\", k, sparse->value[i]);\n    }\n  }\n  if(mod(j, modulo) != 0) printf(\"\\n\");\n}\n\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/LUSOL/sparselib.h",
    "content": "\n#include \"commonlib.h\"\n\n/*#define DEBUG_SPARSELIB*/\n\n#define INITIALSIZE 10\n#define RESIZEDELTA  4\n\n#ifndef SPARSELIB\n\n#define SPARSELIB\n\ntypedef struct _sparseVector {\n  int    limit;\n  int    size;\n  int    count;\n  int    *index;\n  REAL *value;\n} sparseVector;\n\ntypedef struct _sparseMatrix {\n  int    limit;\n  int    size;\n  int    count;\n  int    limitVector;\n  sparseVector **list;\n} sparseMatrix;\n\n#endif\n\n\n#ifdef __cplusplus\n  extern \"C\" {\n#endif\n\nsparseMatrix *createMatrix(int dimLimit, int lenLimit, int initVectors);\nvoid resizeMatrix(sparseMatrix *matrix, int newSize);\nint appendMatrix(sparseMatrix *matrix, sparseVector *newVector);\nint NZcountMatrix(sparseMatrix *matrix);\nvoid freeMatrix(sparseMatrix *matrix);\nvoid printMatrix(int n, sparseMatrix *matrix, int modulo, MYBOOL showEmpty);\n\nsparseVector *createVector(int dimLimit, int initSize);\nsparseVector *cloneVector(sparseVector *sparse);\nint  redimensionVector(sparseVector *sparse, int newDim);\nint  resizeVector(sparseVector *sparse, int newSize);\nvoid moveVector(sparseVector *sparse, int destPos, int sourcePos, int itemCount);\nvoid rotateVector(sparseVector *sparse, int startPos, int chainSize, int stepDelta);\nvoid swapVector(sparseVector *sparse1, sparseVector *sparse2);\nvoid freeVector(sparseVector *sparse);\nvoid printVector(int n, sparseVector *sparse, int modulo);\nMYBOOL verifyVector(sparseVector *sparse);\n\nint firstIndex(sparseVector *sparse);\nint lastIndex(sparseVector *sparse);\nint getDiagonalIndex(sparseVector *sparse);\nint putDiagonalIndex(sparseVector *sparse, int index);\nMYBOOL putDiagonal(sparseVector *sparse, REAL value);\nREAL getDiagonal(sparseVector *sparse);\nREAL getItem(sparseVector *sparse, int targetIndex);\nREAL putItem(sparseVector *sparse, int targetIndex, REAL value);\nREAL addtoItem(sparseVector *sparse, int targetIndex, REAL value);\nvoid swapItems(sparseVector *sparse, int firstIndex, int secondIndex);\nvoid clearVector(sparseVector *sparse, int indexStart, int indexEnd);\nint getVector(sparseVector *sparse, REAL *dense, int indexStart, int indexEnd, MYBOOL doClear);\nvoid putVector(sparseVector *sparse, REAL *dense, int indexStart, int indexEnd);\nvoid fillVector(sparseVector *sparse, int count, REAL value);\n\nREAL dotVector(sparseVector *sparse, REAL *dense, int indexStart, int indexEnd);\n\nvoid daxpyVector1(sparseVector *sparse, REAL scalar, REAL *dense, int indexStart, int indexEnd);\nvoid daxpyVector2(REAL *dense, REAL scalar, sparseVector *sparse, int indexStart, int indexEnd);\nvoid daxpyVector3(sparseVector *sparse1, REAL scalar, sparseVector *sparse2, int indexStart, int indexEnd);\n\nvoid dswapVector1(sparseVector *sparse, REAL *dense, int indexStart, int indexEnd);\nvoid dswapVector2(REAL *dense, sparseVector *sparse, int indexStart, int indexEnd);\nvoid dswapVector3(sparseVector *sparse1, sparseVector *sparse2, int indexStart, int indexEnd);\n\nint idamaxVector(sparseVector *sparse, int is, REAL *maxValue);\n\n#ifdef __cplusplus\n  }\n#endif\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/bfp_LUSOL.c",
    "content": "\n#include \"bfp_LUSOL.h\"\n#include \"lp_lib.h\"\n#include \"lp_LUSOL.h\"\n\nBOOL APIENTRY DllMain( HANDLE hModule, \n                       DWORD  ul_reason_for_call, \n                       LPVOID lpReserved\n\t\t\t\t\t )\n{\n\tswitch (ul_reason_for_call)\n\t{\n\tcase DLL_PROCESS_ATTACH:\n\tcase DLL_THREAD_ATTACH:\n\tcase DLL_THREAD_DETACH:\n\tcase DLL_PROCESS_DETACH:\n\t\tbreak;\n\t}\n    return TRUE;\n}\n\n#if defined FORTIFY\nint EndOfPgr(int i)\n{\n    exit(i);\n}\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/bfp_LUSOL.h",
    "content": "// stdafx.h : include file for standard system include files,\n// or project specific include files that are used frequently, but\n// are changed infrequently\n//\n\n//#pragma once\n\n//RoleIsExternalInvEngine;INVERSE_ACTIVE=INVERSE_LUSOL\n\n#define WIN32_LEAN_AND_MEAN\t\t// Exclude rarely-used stuff from Windows headers\n// Windows Header Files:\n#include <windows.h>\n\n// TODO: reference additional headers your program requires here\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/lp_LUSOL.c",
    "content": "\n/*  Modularized simplex basis factorization module - w/interface for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Kjell Eikland\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      lusol.h, lp_lib.h, myblas.h\n\n    Release notes:\n    v2.0.0  1 March 2004        First implementation of the LUSOL v2.0 C translation.\n    v2.0.1  1 April 2004        Added singularity recovery and fast/reuse update logic.\n    v2.0.2  23 May 2004         Moved mustrefact() function into the BFP structure.\n    v2.0.3  5 September 2004    Reworked pivot threshold tightening logic and default\n                                values.\n    v2.1.0  18 June 2005        Made changes to allow for \"pure\" factorization;\n                                i.e. without the objective function included.\n\n   ---------------------------------------------------------------------------------- */\n\n/* Generic include libraries */\n#include <stdlib.h>\n#include <string.h>\n#include \"lp_lib.h\"\n\n/* Include libraries for this factorization system */\n#include \"myblas.h\"\n#include \"commonlib.h\"\n#include \"lp_LUSOL.h\"\n#include \"lusol.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* Include routines common to factorization engine implementations */\n#include \"lp_BFP1.c\"\n#include \"lp_BFP2.c\"\n\n\n/* MUST MODIFY */\nchar * BFP_CALLMODEL bfp_name(void)\n{\n  return( \"LUSOL v2.2.1.0\" );\n}\n\n\n/* MUST MODIFY */\nMYBOOL BFP_CALLMODEL bfp_resize(lprec *lp, int newsize)\n{\n  INVrec *lu;\n\n  lu = lp->invB;\n\n  /* Increment dimensionality since we put the objective row at the top */\n  newsize = newsize + bfp_rowoffset(lp);\n  lu->dimalloc = newsize;\n\n  /* Allocate index tracker arrays, LU matrices and various work vectors */\n  if(!allocREAL(lp, &(lu->value), newsize+MATINDEXBASE, AUTOMATIC))\n    return( FALSE );\n\n  /* Data specific to the factorization engine */\n  if(lu->LUSOL != NULL) {\n    if(newsize > 0 || 1)\n      LUSOL_sizeto(lu->LUSOL, newsize, newsize, 0);\n    else {\n      LUSOL_free(lu->LUSOL);\n      lu->LUSOL = NULL;\n    }\n  }\n  else if(newsize > 0 || 1) {\n    int  asize;\n    REAL bsize;\n\n    lu->LUSOL = LUSOL_create(NULL, 0, LUSOL_PIVMOD_TPP, bfp_pivotmax(lp)*0);\n\n#if 1\n    lu->LUSOL->luparm[LUSOL_IP_ACCELERATION]  = LUSOL_AUTOORDER;\n    lu->LUSOL->parmlu[LUSOL_RP_SMARTRATIO]    = 0.50;\n#endif\n#if 0\n    lu->timed_refact = DEF_TIMEDREFACT;\n#else\n    lu->timed_refact = FALSE;\n#endif\n\n    /* The following adjustments seem necessary to make the really tough NETLIB\n       models perform reliably and still performant (e.g. cycle.mps) */\n#if 0\n    lu->LUSOL->parmlu[LUSOL_RP_SMALLDIAG_U]   =\n    lu->LUSOL->parmlu[LUSOL_RP_EPSDIAG_U]     = lp->epsprimal;\n#endif\n#if 0\n    lu->LUSOL->parmlu[LUSOL_RP_ZEROTOLERANCE] = lp->epsvalue;\n#endif\n\n#if 1\n    LUSOL_setpivotmodel(lu->LUSOL, LUSOL_PIVMOD_NOCHANGE, LUSOL_PIVTOL_SLIM);\n#else\n    LUSOL_setpivotmodel(lu->LUSOL, LUSOL_PIVMOD_NOCHANGE, LUSOL_PIVTOL_TIGHT);\n#endif\n\n#ifdef LUSOL_UseBLAS\n/*    if(fileSearchPath(\"PATH\", \"myBLAS.DLL\", NULL) && load_BLAS(\"myBLAS\")) */\n    if(is_nativeBLAS() && load_BLAS(libnameBLAS))\n      lp->report(lp, NORMAL, \"Optimized BLAS was successfully loaded for bfp_LUSOL.\\n\");\n#endif\n\n    /* Try to minimize memory allocation if we have a large number of unit columns */\n    bsize = (REAL) lp->get_nonzeros(lp);\n    if(newsize > lp->columns)\n      bsize += newsize;\n    else\n      bsize = bsize/lp->columns*newsize;\n    /* Add a \"reasonable\" delta to allow for B and associated factorizations\n       that are denser than average; this makes reallocations less frequent.\n       Values between 1.2 and 1.5 appear to be reasonable. */\n    asize = (int) (bsize*MAX_DELTAFILLIN*1.3333);\n    if(!LUSOL_sizeto(lu->LUSOL, newsize, newsize, asize))\n      return( FALSE );\n  }\n  lu->dimcount = newsize;\n  return( TRUE );\n}\n\n\n/* MUST MODIFY */\nvoid BFP_CALLMODEL bfp_free(lprec *lp)\n{\n  INVrec *lu;\n\n  lu = lp->invB;\n  if(lu == NULL)\n    return;\n\n  /* General arrays */\n  FREE(lu->opts);\n  FREE(lu->value);\n\n  /* Data specific to the factorization engine */\n  LUSOL_free(lu->LUSOL);\n\n  FREE(lu);\n  lp->invB = NULL;\n}\n\n\n/* MUST MODIFY */\nint BFP_CALLMODEL bfp_nonzeros(lprec *lp, MYBOOL maximum)\n{\n  INVrec *lu;\n\n  lu = lp->invB;\n  if(maximum == TRUE)\n    return(lu->max_LUsize);\n  else if(maximum == AUTOMATIC)\n    return(lu->max_Bsize);\n  else\n    return(lu->LUSOL->luparm[LUSOL_IP_NONZEROS_L0]+lu->LUSOL->luparm[LUSOL_IP_NONZEROS_U0]);\n/*    return(lu->LUSOL->luparm[LUSOL_IP_NONZEROS_ROW]); */\n}\n\n\n/* MUST MODIFY (or ignore) */\nint BFP_CALLMODEL bfp_memallocated(lprec *lp)\n{\n  int      mem;\n  LUSOLrec *LUSOL = lp->invB->LUSOL;\n\n  mem = sizeof(REAL) * (LUSOL->lena+LUSOL->maxm+LUSOL_RP_LASTITEM);\n  mem += sizeof(int) * (2*LUSOL->lena+5*LUSOL->maxm+5*LUSOL->maxn+LUSOL_IP_LASTITEM);\n  if(LUSOL->luparm[LUSOL_IP_PIVOTTYPE] == LUSOL_PIVMOD_TCP)\n    mem += sizeof(REAL) * LUSOL->maxn + 2*sizeof(REAL)*LUSOL->maxn;\n  else if(LUSOL->luparm[LUSOL_IP_PIVOTTYPE] == LUSOL_PIVMOD_TRP)\n    mem += sizeof(REAL) * LUSOL->maxn;\n  if(!LUSOL->luparm[LUSOL_IP_KEEPLU])\n    mem += sizeof(REAL) * LUSOL->maxn;\n  return( mem );\n}\n\n\n/* MUST MODIFY */\nint BFP_CALLMODEL bfp_preparefactorization(lprec *lp)\n{\n  INVrec *lu = lp->invB;\n\n  /* Finish any outstanding business */\n  if(lu->is_dirty == AUTOMATIC)\n    lp->bfp_finishfactorization(lp);\n\n  /* Clear or resize the existing LU matrices - specific for the factorization engine */\n  LUSOL_clear(lu->LUSOL, TRUE);\n  if(lu->dimcount != lp->rows + bfp_rowoffset(lp))\n    lp->bfp_resize(lp, lp->rows);\n\n  /* Reset additional indicators */\n  lp->bfp_updaterefactstats(lp);\n  lu->col_pos = 0;\n\n  return(0);\n\n}\n\n\n/* LOCAL HELPER ROUTINE - Replace a basis column with corresponding slack */\nint bfp_LUSOLsetcolumn(lprec *lp, int posnr, int colnr)\n{\n  int nz, inform;\n\n  nz = lp->get_lpcolumn(lp, colnr, lp->invB->LUSOL->w + bfp_rowoffset(lp), NULL, NULL);\n  inform = LUSOL_replaceColumn(lp->invB->LUSOL, posnr, lp->invB->LUSOL->w);\n  return( inform );\n}\n\n\n/* LOCAL HELPER ROUTINE - force the basis to be the identity matrix */\nint bfp_LUSOLidentity(lprec *lp, int *rownum)\n{\n  int    i, nz;\n  INVrec *invB = lp->invB;\n\n  /* Reset the factorization engine */\n  LUSOL_clear(invB->LUSOL, TRUE);\n\n  /* Add the basis columns */\n  lp->invB->set_Bidentity = TRUE;\n  for(i = 1; i <= invB->dimcount; i++) {\n    nz = lp->get_basiscolumn(lp, i, rownum, invB->value);\n    LUSOL_loadColumn(invB->LUSOL, rownum, i, invB->value, nz, 0);\n  }\n  lp->invB->set_Bidentity = FALSE;\n\n  /* Factorize */\n  i = LUSOL_factorize(invB->LUSOL);\n\n  return( i );\n}\n\n\n/* LOCAL HELPER ROUTINE */\nint bfp_LUSOLfactorize(lprec *lp, MYBOOL *usedpos, int *rownum, int *singular)\n{\n  int    i, j, nz, deltarows = bfp_rowoffset(lp);\n  INVrec *invB = lp->invB;\n\n  /* Handle normal, presumed nonsingular case */\n  if(singular == NULL) {\n\n  /* Optionally do a symbolic minimum degree ordering;\n     not that slack variables should not be processed */\n/*#define UsePreprocessMDO*/\n#ifdef UsePreprocessMDO\n    int *mdo;\n    mdo = lp->bfp_createMDO(lp, usedpos, lp->rows, TRUE);\n    if(mdo != NULL) {\n      for(i = 1; i <= lp->rows; i++)\n        lp->set_basisvar(lp, i, mdo[i]);\n      FREE(mdo);\n    }\n#endif\n\n    /* Reset the factorization engine */\n    LUSOL_clear(invB->LUSOL, TRUE);\n\n    /* Add the basis columns in the original order */\n    for(i = 1; i <= invB->dimcount; i++) {\n      nz = lp->get_basiscolumn(lp, i, rownum, invB->value);\n      LUSOL_loadColumn(invB->LUSOL, rownum, i, invB->value, nz, 0);\n      if((i > deltarows) && (lp->var_basic[i-deltarows] > lp->rows))\n        lp->invB->user_colcount++;\n    }\n\n    /* Factorize */\n    i = LUSOL_factorize(invB->LUSOL);\n  }\n\n  /* Handle case where a column may be singular */\n  else {\n    LLrec *map;\n\n    /* Reset the factorization engine */\n    i = bfp_LUSOLidentity(lp, rownum);\n\n    /* Build map of available columns */\n    nz = createLink(lp->rows, &map, NULL);\n    for(i = 1; i <= lp->rows; i++) {\n      if(lp->var_basic[i] <= lp->rows)\n        removeLink(map, i);\n    }\n\n    /* Rebuild the basis, column by column, while skipping slack columns */\n    j = firstActiveLink(map);\n    for(i = 1; i <= lp->rows; i++) {\n      if(lp->var_basic[i] <= lp->rows)\n        continue;\n      nz = bfp_LUSOLsetcolumn(lp, j+deltarows, lp->var_basic[i]);\n      if(nz == LUSOL_INFORM_LUSUCCESS)\n        lp->invB->user_colcount++;\n      else {\n        nz = bfp_LUSOLsetcolumn(lp, j+deltarows, i);\n        lp->set_basisvar(lp, i, i);\n      }\n      j = nextActiveLink(map, j);\n    }\n\n    /* Sort the basis list */\n    MEMCOPY(rownum, lp->var_basic, lp->rows+1);\n    sortByINT(lp->var_basic, rownum, lp->rows, 1, TRUE);\n\n  }\n\n  return( i );\n}\n/* LOCAL HELPER ROUTINE */\nvoid bfp_LUSOLtighten(lprec *lp)\n{\n  int infolevel = DETAILED;\n\n  switch(LUSOL_tightenpivot(lp->invB->LUSOL)) {\n    case FALSE: lp->report(lp, infolevel, \"bfp_factorize: Very hard numerics, but cannot tighten LUSOL thresholds further.\\n\");\n                 break;\n    case TRUE:  lp->report(lp, infolevel, \"bfp_factorize: Frequent refact pivot count %d at iter %.0f; tightened thresholds.\\n\",\n                                           lp->invB->num_pivots, (REAL) lp->get_total_iter(lp));\n                 break;\n    default:    lp->report(lp, infolevel, \"bfp_factorize: LUSOL switched to %s pivoting model to enhance stability.\\n\",\n                                           LUSOL_pivotLabel(lp->invB->LUSOL));\n  }\n}\n\n#define is_fixedvar is_fixedvar_ /* resolves a compiler warning/error conflict with lp_lib.h */\n\nstatic MYBOOL is_fixedvar(lprec *lp, int variable)\n{\n  if((lp->bb_bounds != NULL && lp->bb_bounds->UBzerobased) || (variable <= lp->rows))\n    return( (MYBOOL) (lp->upbo[variable] < lp->epsprimal) );\n  else\n    return( (MYBOOL) (lp->upbo[variable]-lp->lowbo[variable] < lp->epsprimal) );\n} /* is_fixedvar */\n\n/* MUST MODIFY */\nint BFP_CALLMODEL bfp_factorize(lprec *lp, int uservars, int Bsize, MYBOOL *usedpos, MYBOOL final)\n{\n  int      kcol, inform,\n           *rownum = NULL,\n           singularities = 0,\n           dimsize = lp->invB->dimcount;\n  LUSOLrec *LUSOL = lp->invB->LUSOL;\n\n /* Set dimensions and create work array */\n  SETMAX(lp->invB->max_Bsize, Bsize+(1+lp->rows-uservars));\n  kcol = lp->invB->dimcount;\n  LUSOL->m = kcol;\n  LUSOL->n = kcol;\n  allocINT(lp, &rownum, kcol+1, FALSE);\n\n /* Check if the refactorization frequency is low;\n    tighten pivot thresholds if appropriate */\n  inform = lp->bfp_pivotcount(lp);\n  if(!final &&                        /* No solution update-based refactorization */\n     !lp->invB->force_refact &&       /* No sparsity-based refactorization */\n     !lp->is_action(lp->spx_action,\n          ACTION_TIMEDREINVERT) &&    /* No optimal time-based refactorization */\n     (inform > 5) && (inform < 0.25*lp->bfp_pivotmax(lp)))\n    bfp_LUSOLtighten(lp);\n\n\n /* Reload B and factorize */\n  inform = bfp_LUSOLfactorize(lp, usedpos, rownum, NULL);\n\n /* Do some checks */\n#ifdef Paranoia\n  if(uservars != lp->invB->user_colcount) {\n    lp->report(lp, SEVERE, \"bfp_factorize: User variable count reconciliation failed\\n\");\n    return( singularities );\n  }\n#endif\n\n  /* Check result and do further remedial action if necessary */\n  if(inform != LUSOL_INFORM_LUSUCCESS) {\n    int  singularcols,\n         replacedcols = 0;\n    REAL hold;\n\n    /* Make sure we do not tighten factorization pivot criteria too often, and simply\n       accept the substitution of slack columns into the basis */\n    if((lp->invB->num_singular+1) % TIGHTENAFTER == 0)\n      bfp_LUSOLtighten(lp);\n\n    /* Try to restore a non-singular basis by substituting singular columns with slacks */\n    while((inform == LUSOL_INFORM_LUSINGULAR) && (replacedcols < dimsize)) {\n      int    iLeave, jLeave, iEnter;\n      MYBOOL isfixed;\n\n      singularities++;\n      singularcols = LUSOL->luparm[LUSOL_IP_SINGULARITIES];\n      hold = (REAL) lp->get_total_iter(lp);\n      lp->report(lp, NORMAL, \"bfp_factorize: Resolving %d singularit%s at refact %d, iter %.0f\\n\",\n                             singularcols, my_plural_y(singularcols), lp->invB->num_refact, hold);\n\n      /* Find the failing / singular column(s) and make slack substitutions */\n      for(kcol = 1; kcol <= singularcols; kcol++) {\n\n        /* Determine leaving and entering columns. */\n        iLeave = LUSOL_getSingularity(LUSOL, kcol);        /* This is the singular column as natural index */\n        iEnter = iLeave;                                   /* This is the target replacement slack         */\n#if 1\n        iEnter = LUSOL->iqinv[iEnter];\n        iEnter = LUSOL->ip[iEnter];\n#endif\n        iLeave-= bfp_rowextra(lp);                         /* This is the original B column/basis index    */\n        jLeave = lp->var_basic[iLeave];                    /* This is the IA column index in lp_solve      */\n\n        /* Express the slack index in original lp_solve [1..rows] reference and check validity */\n /*       if(B4 != NULL) iEnter = B4->B4_row[iEnter]; v6 FUNCTIONALITY */\n        iEnter -=  bfp_rowextra(lp);\n        if(lp->is_basic[iEnter]) {\n          lp->report(lp, DETAILED, \"bfp_factorize: Replacement slack %d is already basic!\\n\", iEnter);\n\n          /* See if we can find a good alternative slack variable to enter */\n          iEnter = 0;\n          for(inform = 1; inform <= lp->rows; inform++)\n            if(!lp->is_basic[inform]) {\n              if((iEnter == 0) || (lp->upbo[inform] > lp->upbo[iEnter])) {\n                iEnter = inform;\n                if(my_infinite(lp, lp->upbo[iEnter]))\n                  break;\n              }\n            }\n          if(iEnter == 0) {\n            lp->report(lp, SEVERE, \"bfp_factorize: Could not find replacement slack variable!\\n\");\n            break;\n          }\n        }\n\n        /* We should update bound states for both the entering and leaving variables.\n           Note that this may cause (primal or dual) infeasibility, but I assume that\n           lp_solve traps this and takes necessary corrective action. */\n        isfixed = is_fixedvar(lp, iEnter);\n        if(isfixed)\n          lp->fixedvars++;\n        hold = lp->upbo[jLeave];\n        lp->is_lower[jLeave] = isfixed || (fabs(hold)>=lp->infinite) || (lp->rhs[iLeave] < hold);\n        lp->is_lower[iEnter] = TRUE;\n\n        /* Do the basis replacement */\n        lp->set_basisvar(lp, iLeave, iEnter);\n\n      }\n\n      /* Refactorize with slack substitutions */\n      inform = bfp_LUSOLfactorize(lp, NULL, rownum, NULL);\n      replacedcols += singularcols;\n    }\n\n    /* Check if we had a fundamental problem */\n    if(singularities >= dimsize) {\n      lp->report(lp, IMPORTANT, \"bfp_factorize: LUSOL was unable to recover from a singular basis\\n\");\n      lp->spx_status = NUMFAILURE;\n    }\n  }\n\n  /* Clean up before returning */\n  FREE(rownum);\n\n  /* Update statistics */\n  /* SETMAX(lp->invB->max_Bsize, (*Bsize)); */\n  lp->invB->num_singular += singularities;    /* The total number of singular updates */\n\n  return( singularities );\n}\n\n/* MUST MODIFY */\nMYBOOL BFP_CALLMODEL bfp_finishupdate(lprec *lp, MYBOOL changesign)\n/* Was addetacol() in versions of lp_solve before 4.0.1.8 - KE */\n{\n  int      i, k, kcol, deltarows = bfp_rowoffset(lp);\n  REAL     DIAG, VNORM;\n  INVrec   *lu = lp->invB;\n  LUSOLrec *LUSOL = lu->LUSOL;\n\n  if(!lu->is_dirty)\n    return( FALSE );\n  if(lu->is_dirty != AUTOMATIC)\n    lu->is_dirty = FALSE;\n\n  /* Perform the update */\n  k = lu->col_pos+deltarows;\n  lu->num_pivots++;\n  if(lu->col_leave > lu->dimcount-deltarows)\n    lu->user_colcount--;\n  if(lu->col_enter > lu->dimcount-deltarows)\n    lu->user_colcount++;\n  kcol = lu->col_pos;\n  lu->col_pos = 0;\n\n  /* Do standard update */\n#ifdef LUSOLSafeFastUpdate      /* NB! Defined in lusol.h */\n  if(TRUE || !changesign) {\n    if(changesign) {\n      REAL *temp = LUSOL->vLU6L;\n      for(i = 1, temp++; i <= lp->rows+deltarows; i++, temp++)\n        if(*temp != 0)\n          *temp = -(*temp);\n    }\n    /* Execute the update using data prepared earlier */\n    LU8RPC(LUSOL, LUSOL_UPDATE_OLDNONEMPTY, LUSOL_UPDATE_USEPREPARED,\n           k, NULL, NULL, &i, &DIAG, &VNORM);\n  }\n  else\n#endif\n  {\n    /* Retrieve the data for the entering column (base 0) */\n    i = lp->get_lpcolumn(lp, lu->col_enter, lu->value+deltarows, NULL, NULL);\n    lu->value[0] = 0;\n    /* Execute the update */\n    LU8RPC(LUSOL, LUSOL_UPDATE_OLDNONEMPTY, LUSOL_UPDATE_NEWNONEMPTY,\n           k, lu->value, NULL, &i, &DIAG, &VNORM);\n  }\n\n  if(i == LUSOL_INFORM_LUSUCCESS) {\n\n    /* Check if we should refactorize based on accumulation of fill-in */\n    DIAG  = LUSOL->luparm[LUSOL_IP_NONZEROS_L]+LUSOL->luparm[LUSOL_IP_NONZEROS_U];\n    VNORM = LUSOL->luparm[LUSOL_IP_NONZEROS_L0]+LUSOL->luparm[LUSOL_IP_NONZEROS_U0];\n#if 0\n    /* This is Michael Saunder's fixed parameter */\n    VNORM *= MAX_DELTAFILLIN;\n#else\n    /* This is Kjell Eikland's dynamic error accumulation measure */\n    VNORM *= pow(MAX_DELTAFILLIN, pow((0.5*LUSOL->nelem/VNORM), 0.25));\n#endif\n    lu->force_refact = (MYBOOL) ((DIAG > VNORM) && (lu->num_pivots > 20));\n\n#if 0\n    /* Additional KE logic to reduce maximum pivot count based on the density of B */\n    if(!lu->force_refact) {\n      VNORM = lp->rows+1;\n      VNORM = 1.0 - pow((REAL) LUSOL->nelem/VNORM/VNORM, 0.2);\n      lu->force_refact = (MYBOOL) (lu->num_pivots > VNORM*lp->bfp_pivotmax(lp));\n    }\n#endif\n  }\n\n  /* Handle errors */\n  else {\n/*    int infolevel = NORMAL; */\n    int infolevel = DETAILED;\n    lp->report(lp, infolevel, \"bfp_finishupdate: Failed at iter %.0f, pivot %d;\\n%s\\n\",\n                   (REAL) (lp->total_iter+lp->current_iter), lu->num_pivots, LUSOL_informstr(LUSOL, i));\n    if(i == LUSOL_INFORM_ANEEDMEM) {       /* To compress used memory and realloc, if necessary */\n      lp->invert(lp, INITSOL_USEZERO, FALSE);\n      if(i != LUSOL_INFORM_LUSUCCESS)\n        lp->report(lp, NORMAL, \"bfp_finishupdate: Insufficient memory at iter %.0f;\\n%s\\n\",\n                       (REAL) (lp->total_iter+lp->current_iter), LUSOL_informstr(LUSOL, i));\n    }\n    else if(i == LUSOL_INFORM_RANKLOSS) {  /* To fix rank loss and clear cumulative errors */\n#if 0\n      /* This is test code to do pivot in slack BEFORE refactorization (pessimistic approach);\n        assumes that LUSOL returns correct information about the source of the singularity */\n      kcol = LUSOL->luparm[LUSOL_IP_SINGULARINDEX];\n#ifdef MAPSINGULARCOLUMN\n      kcol = LUSOL_findColumnPosition(LUSOL, kcol);\n#endif\n      lp->set_basisvar(lp, kcol-deltarows, kcol-deltarows);\n#endif\n      lp->invert(lp, INITSOL_USEZERO, FALSE);\n      i = LUSOL->luparm[LUSOL_IP_INFORM];\n      if(i != LUSOL_INFORM_LUSUCCESS)\n        lp->report(lp, NORMAL, \"bfp_finishupdate: Recovery attempt unsuccessful at iter %.0f;\\n%s\\n\",\n                       (REAL) (lp->total_iter+lp->current_iter), LUSOL_informstr(LUSOL, i));\n      else\n        lp->report(lp, infolevel, \"bfp_finishupdate: Correction or recovery was successful.\\n\");\n    }\n  }\n  return( (MYBOOL) (i == LUSOL_INFORM_LUSUCCESS) );\n\n} /* bfp_finishupdate */\n\n\n/* MUST MODIFY */\nvoid BFP_CALLMODEL bfp_ftran_normal(lprec *lp, REAL *pcol, int *nzidx)\n{\n  int    i;\n  INVrec *lu;\n\n  lu = lp->invB;\n\n  /* Do the LUSOL ftran */\n  i = LUSOL_ftran(lu->LUSOL, pcol-bfp_rowoffset(lp), nzidx, FALSE);\n  if(i != LUSOL_INFORM_LUSUCCESS) {\n    lu->status = BFP_STATUS_ERROR;\n    lp->report(lp, NORMAL, \"bfp_ftran_normal: Failed at iter %.0f, pivot %d;\\n%s\\n\",\n                   (REAL) (lp->total_iter+lp->current_iter), lu->num_pivots, LUSOL_informstr(lu->LUSOL, i));\n  }\n}\n\n\n/* MAY MODIFY */\nvoid BFP_CALLMODEL bfp_ftran_prepare(lprec *lp, REAL *pcol, int *nzidx)\n{\n  int    i;\n  INVrec *lu;\n\n  lu = lp->invB;\n\n  /* Do the LUSOL ftran */\n  i = LUSOL_ftran(lu->LUSOL, pcol-bfp_rowoffset(lp), nzidx, TRUE);\n  if(i != LUSOL_INFORM_LUSUCCESS) {\n    lu->status = BFP_STATUS_ERROR;\n    lp->report(lp, NORMAL, \"bfp_ftran_prepare: Failed at iter %.0f, pivot %d;\\n%s\\n\",\n                   (REAL) (lp->total_iter+lp->current_iter), lu->num_pivots, LUSOL_informstr(lu->LUSOL, i));\n  }\n}\n\n\n/* MUST MODIFY */\nvoid BFP_CALLMODEL bfp_btran_normal(lprec *lp, REAL *prow, int *nzidx)\n{\n  int    i;\n  INVrec *lu;\n\n  lu = lp->invB;\n\n  /* Do the LUSOL btran */\n  i = LUSOL_btran(lu->LUSOL, prow-bfp_rowoffset(lp), nzidx);\n  if(i != LUSOL_INFORM_LUSUCCESS) {\n    lu->status = BFP_STATUS_ERROR;\n    lp->report(lp, NORMAL, \"bfp_btran_normal: Failed at iter %.0f, pivot %d;\\n%s\\n\",\n                   (REAL) (lp->total_iter+lp->current_iter), lu->num_pivots, LUSOL_informstr(lu->LUSOL, i));\n  }\n\n  /* Check performance data */\n#if 0\n  if(lu->num_pivots == 1) {\n    if(lu->LUSOL->luparm[LUSOL_IP_ACCELERATION] > 0)\n      lp->report(lp, NORMAL, \"RowL0 R:%10.7f  C:%10.7f  NZ:%10.7f\\n\",\n                             (REAL) lu->LUSOL->luparm[LUSOL_IP_ROWCOUNT_L0] / lu->LUSOL->m,\n                             (REAL) lu->LUSOL->luparm[LUSOL_IP_COLCOUNT_L0] / lu->LUSOL->m,\n                             (REAL) lu->LUSOL->luparm[LUSOL_IP_NONZEROS_L0] / pow((REAL) lu->LUSOL->m, 2));\n    else\n      lp->report(lp, NORMAL, \"ColL0 C:%10.7f  NZ:%10.7f\\n\",\n                             (REAL) lu->LUSOL->luparm[LUSOL_IP_COLCOUNT_L0] / lu->LUSOL->m,\n                             (REAL) lu->LUSOL->luparm[LUSOL_IP_NONZEROS_L0] / pow((REAL) lu->LUSOL->m, 2));\n  }\n#endif\n\n}\n\n/* MUST MODIFY - Routine to find maximum rank of equality constraints */\nint BFP_CALLMODEL bfp_findredundant(lprec *lp, int items, getcolumnex_func cb, int *maprow, int *mapcol)\n{\n  int       i, j, nz = 0, m = 0, n = 0, *nzrows = NULL;\n  REAL      *nzvalues = NULL, *arraymax = NULL;\n  LUSOLrec  *LUSOL;\n\n  /* Are we capable of finding redundancy with this BFP? */\n  if((maprow == NULL) && (mapcol == NULL))\n    return( n );\n\n  /* If so, initialize memory structures */\n  if(!allocINT(lp, &nzrows, items, FALSE) ||\n     !allocREAL(lp, &nzvalues, items, FALSE))\n    return( n );\n\n  /* Compute the number of non-empty columns */\n  m = 0;\n  for(j = 1; j <= mapcol[0]; j++) {\n    n = cb(lp, mapcol[j], NULL, NULL, maprow);\n    if(n > 0) {\n      m++;\n      mapcol[m] = mapcol[j];\n      nz += n;\n    }\n  }\n  mapcol[0] = m;\n\n  /* Instantiate a LUSOL object */\n  LUSOL = LUSOL_create(NULL, 0, LUSOL_PIVMOD_TRP, 0);\n  if((LUSOL == NULL) || !LUSOL_sizeto(LUSOL, items, m, nz*LUSOL_MULT_nz_a))\n    goto Finish;\n\n  /* Modify relevant LUSOL parameters */\n  LUSOL->m = items;\n  LUSOL->n = m;\n#if 0\n  LUSOL->luparm[LUSOL_IP_KEEPLU]        = FALSE;\n  LUSOL->luparm[LUSOL_IP_PIVOTTYPE]     = LUSOL_PIVMOD_TRP;\n  LUSOL->parmlu[LUSOL_RP_FACTORMAX_Lij] = 2.0;\n#endif\n\n  /* Load the columns into LUSOL */\n  for(j = 1; j <= m; j++) {\n    n = cb(lp, mapcol[j], nzvalues, nzrows, maprow);\n    i = LUSOL_loadColumn(LUSOL, nzrows, j, nzvalues, n, -1);\n    if(n != i) {\n      lp->report(lp, IMPORTANT, \"bfp_findredundant: Error %d while loading column %d with %d nz\\n\",\n                                i, j, n);\n      n = 0;\n      goto Finish;\n    }\n  }\n\n  /* Scale rows to prevent numerical problems */\n  if((lp->scalemode != SCALE_NONE) && allocREAL(lp, &arraymax, items+1, TRUE)) {\n    for(i = 1; i <= nz; i++) {\n      SETMAX(arraymax[LUSOL->indc[i]], fabs(LUSOL->a[i]));\n    }\n    for(i = 1; i <= nz; i++)\n      LUSOL->a[i] /= arraymax[LUSOL->indc[i]];\n    FREE(arraymax);\n  }\n\n  /* Factorize for maximum rank */\n  n = 0;\n  i = LUSOL_factorize(LUSOL);\n  /*  lp->report(lp, NORMAL, \"bfp_findredundant: r=%d c=%d - %s\\n\", items, m, LUSOL_informstr(LUSOL, i));*/\n  if((i == LUSOL_INFORM_LUSUCCESS) || (i != LUSOL_INFORM_LUSINGULAR))\n    goto Finish;\n\n  /* We have a singular matrix, obtain the indeces of the singular rows */\n  for(i = LUSOL->luparm[LUSOL_IP_RANK_U] + 1; i <= items; i++) {\n    n++;\n    maprow[n] = LUSOL->ip[i];\n  }\n  maprow[0] = n;\n\n  /* Clean up */\nFinish:\n  LUSOL_free(LUSOL);\n  FREE(nzrows);\n  FREE(nzvalues);\n\n  return( n );\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/bfp_LUSOL/lp_LUSOL.h",
    "content": "#ifndef HEADER_lp_LUSOL\n#define HEADER_lp_LUSOL\n\n/* Include libraries for this inverse system */\n#include \"lp_types.h\"\n#include \"lusol.h\"\n\n/* LUSOL defines */\n#ifdef WIN32\n# define LUSOL_UseBLAS\n#endif\n/*#define MAPSINGULARCOLUMN*/\n#define MATINDEXBASE LUSOL_ARRAYOFFSET /* Inversion engine index start for arrays */\n#define LU_START_SIZE           10000  /* Start size of LU; realloc'ed if needed */\n#define DEF_MAXPIVOT              250  /* Maximum number of pivots before refactorization */\n#define MAX_DELTAFILLIN           2.0  /* Do refactorizations based on sparsity considerations */\n#define TIGHTENAFTER               10  /* Tighten LU pivot criteria only after this number of singularities */\n\n/* typedef */ struct _INVrec\n{\n  int       status;                 /* Last operation status code */\n  int       dimcount;               /* The actual number of LU rows/columns */\n  int       dimalloc;               /* The allocated LU rows/columns size */\n  int       user_colcount;          /* The number of user LU columns */\n  LUSOLrec  *LUSOL;\n  int       col_enter;              /* The full index of the entering column */\n  int       col_leave;              /* The full index of the leaving column */\n  int       col_pos;                /* The B column to be changed at the next update using data in value[.]*/\n  REAL      *value;\n  REAL      *pcol;                  /* Reference to the elimination vector */\n  REAL      theta_enter;            /* Value of the entering column theta */\n\n  int       max_Bsize;              /* The largest B matrix of user variables */\n  int       max_colcount;           /* The maximum number of user columns in LU */\n  int       max_LUsize;             /* The largest NZ-count of LU-files generated */\n  int       num_refact;             /* Number of times the basis was refactored */\n  int       num_timed_refact;\n  int       num_dense_refact;\n  double    time_refactstart;       /* Time since start of last refactorization-pivots cyle */\n  double    time_refactnext;        /* Time estimated to next refactorization */\n  int       num_pivots;             /* Number of pivots since last refactorization */\n  int       num_singular;           /* The total number of singular updates */\n  char      *opts;\n  MYBOOL    is_dirty;               /* Specifies if a column is incompletely processed */\n  MYBOOL    force_refact;           /* Force refactorization at the next opportunity */\n  MYBOOL    timed_refact;           /* Set if timer-driven refactorization should be active */\n  MYBOOL    set_Bidentity;          /* Force B to be the identity matrix at the next refactorization */\n} /* INVrec */;\n\n\n#ifdef __cplusplus\n/* namespace LUSOL */\nextern \"C\" {\n#endif\n\n/* Put function headers here */\n#include \"lp_BFP.h\"\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_LUSOL */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/lp_BFP.h",
    "content": "\n/* ---------------------------------------------------------------------------------- */\n/* lp_solve v5+ headers for basis inversion / factorization libraries                 */\n/* ---------------------------------------------------------------------------------- */\n#define BFP_STATUS_RANKLOSS     -1\n#define BFP_STATUS_SUCCESS       0\n#define BFP_STATUS_SINGULAR      1\n#define BFP_STATUS_UNSTABLE      2\n#define BFP_STATUS_NOPIVOT       3\n#define BFP_STATUS_DIMERROR      4\n#define BFP_STATUS_DUPLICATE     5\n#define BFP_STATUS_NOMEMORY      6\n#define BFP_STATUS_ERROR         7             /* Unspecified, command-related error */\n#define BFP_STATUS_FATAL         8\n\n#define BFP_STAT_ERROR          -1\n#define BFP_STAT_REFACT_TOTAL    0\n#define BFP_STAT_REFACT_TIMED    1\n#define BFP_STAT_REFACT_DENSE    2\n\n#ifndef BFP_CALLMODEL\n  #ifdef WIN32\n    #define BFP_CALLMODEL __stdcall   /* \"Standard\" call model */\n  #else\n    #define BFP_CALLMODEL\n  #endif\n#endif\n\n#ifdef RoleIsExternalInvEngine\n  #define __BFP_EXPORT_TYPE __EXPORT_TYPE\n#else\n  #define __BFP_EXPORT_TYPE\n#endif\n\n\n/* Routines with UNIQUE implementations for each inversion engine                     */\n/* ---------------------------------------------------------------------------------- */\nchar   __BFP_EXPORT_TYPE *(BFP_CALLMODEL bfp_name)(void);\nvoid   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_free)(lprec *lp);\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_resize)(lprec *lp, int newsize);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_nonzeros)(lprec *lp, MYBOOL maximum);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_memallocated)(lprec *lp);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_preparefactorization)(lprec *lp);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_factorize)(lprec *lp, int uservars, int Bsize, MYBOOL *usedpos, MYBOOL final);\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_finishupdate)(lprec *lp, MYBOOL changesign);\nvoid   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_ftran_normal)(lprec *lp, REAL *pcol, int *nzidx);\nvoid   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_ftran_prepare)(lprec *lp, REAL *pcol, int *nzidx);\nvoid   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_btran_normal)(lprec *lp, REAL *prow, int *nzidx);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_status)(lprec *lp);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_findredundant)(lprec *lp, int items, getcolumnex_func cb, int *maprow, int*mapcol);\n\n\n/* Routines SHARED for all inverse implementations; located in lp_BFP1.c              */\n/* ---------------------------------------------------------------------------------- */\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_compatible)(lprec *lp, int bfpversion, int lpversion, int sizeofvar);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_indexbase)(lprec *lp);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_rowoffset)(lprec *lp);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_pivotmax)(lprec *lp);\nREAL   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_efficiency)(lprec *lp);\nREAL   __BFP_EXPORT_TYPE *(BFP_CALLMODEL bfp_pivotvector)(lprec *lp);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_pivotcount)(lprec *lp);\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_mustrefactorize)(lprec *lp);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_refactcount)(lprec *lp, int kind);\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_isSetI)(lprec *lp);\nint    *bfp_createMDO(lprec *lp, MYBOOL *usedpos, int count, MYBOOL doMDO);\nvoid   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_updaterefactstats)(lprec *lp);\nint    BFP_CALLMODEL bfp_rowextra(lprec *lp);\n\n/* Routines with OPTIONAL SHARED code; template routines suitable for canned          */\n/* inverse engines are located in lp_BFP2.c                                           */\n/* ---------------------------------------------------------------------------------- */\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_init)(lprec *lp, int size, int deltasize, char *options);\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_restart)(lprec *lp);\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_implicitslack)(lprec *lp);\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_pivotalloc)(lprec *lp, int newsize);\nint    __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_colcount)(lprec *lp);\nMYBOOL __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_canresetbasis)(lprec *lp);\nvoid   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_finishfactorization)(lprec *lp);\nLREAL  __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_prepareupdate)(lprec *lp, int row_nr, int col_nr, REAL *pcol);\nREAL   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_pivotRHS)(lprec *lp, LREAL theta, REAL *pcol);\nvoid   __BFP_EXPORT_TYPE (BFP_CALLMODEL bfp_btran_double)(lprec *lp, REAL *prow, int *pnzidx, REAL *drow, int *dnzidx);\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/lp_BFP1.c",
    "content": "\n/* Routines located in lp_BFP1.cpp; common for all factorization engines              */\n/* Cfr. lp_BFP.h for definitions                                                      */\n/* ---------------------------------------------------------------------------------- */\n/* Changes:                                                                           */\n/* 29 May 2004       Corrected calculation of bfp_efficiency(), which required        */\n/*                   modifying the max_Bsize to include slack variables. KE.          */\n/* 16 June 2004      Make the symbolic minimum degree ordering routine available      */\n/*                   to BFPs as a routine internal to the library. KE                 */\n/* 1  July 2004      Change due to change in MDO naming.                              */\n/* ---------------------------------------------------------------------------------- */\n\n\n/* MUST MODIFY */\nMYBOOL BFP_CALLMODEL bfp_compatible(lprec *lp, int bfpversion, int lpversion, int sizeofvar)\n{\n  MYBOOL status = FALSE;\n\n  if((lp != NULL) && (bfpversion == BFPVERSION) && (sizeof(REAL) == sizeofvar)) {\n#if 0\n    if(lpversion == MAJORVERSION)  /* Forces BFP renewal at lp_solve major version changes */\n#endif\n      status = TRUE;\n  }\n  return( status );\n}\n\n/* DON'T MODIFY */\nint BFP_CALLMODEL bfp_status(lprec *lp)\n{\n  return(lp->invB->status);\n}\n\n/* DON'T MODIFY */\nint BFP_CALLMODEL bfp_indexbase(lprec *lp)\n{\n  return( MATINDEXBASE );\n}\n\n/* DON'T MODIFY */\nint BFP_CALLMODEL bfp_rowoffset(lprec *lp)\n{\n  if(lp->obj_in_basis)\n    return( 1 );\n  else\n    return( 0 );\n}\n\n/* DON'T MODIFY */\nint BFP_CALLMODEL bfp_pivotmax(lprec *lp)\n{\n  if(lp->max_pivots > 0)\n    return( lp->max_pivots );\n  else\n    return( DEF_MAXPIVOT );\n}\n\n/* DON'T MODIFY */\nREAL * BFP_CALLMODEL bfp_pivotvector(lprec *lp)\n{\n  return( lp->invB->pcol );\n}\n\n/* DON'T MODIFY */\nREAL BFP_CALLMODEL bfp_efficiency(lprec *lp)\n{\n  REAL hold;\n\n  hold = lp->bfp_nonzeros(lp, AUTOMATIC);\n  if(hold == 0)\n    hold = 1 + lp->rows;\n  hold = lp->bfp_nonzeros(lp, TRUE)/hold;\n\n  return(hold);\n}\n\n/* DON'T MODIFY */\nint BFP_CALLMODEL bfp_pivotcount(lprec *lp)\n{\n  return(lp->invB->num_pivots);\n}\n\n\n/* DON'T MODIFY */\nint BFP_CALLMODEL bfp_refactcount(lprec *lp, int kind)\n{\n  if(kind == BFP_STAT_REFACT_TOTAL)\n    return(lp->invB->num_refact);\n  else if(kind == BFP_STAT_REFACT_TIMED)\n    return(lp->invB->num_timed_refact);\n  else if(kind == BFP_STAT_REFACT_DENSE)\n    return(lp->invB->num_dense_refact);\n  else\n    return( BFP_STAT_ERROR );\n}\n\n/* DON'T MODIFY */\nMYBOOL BFP_CALLMODEL bfp_mustrefactorize(lprec *lp)\n{\n  MYBOOL test = lp->is_action(lp->spx_action, ACTION_REINVERT | ACTION_TIMEDREINVERT);\n  if(!test) {\n    REAL   f;\n    INVrec *lu = lp->invB;\n\n    if(lu->num_pivots > 0)\n      f = (timeNow()-lu->time_refactstart) / (REAL) lu->num_pivots;\n    else\n      f = 0;\n\n    /* Always refactorize if we are above the set pivot limit */\n    if(lu->force_refact ||\n       (lu->num_pivots >= lp->bfp_pivotmax(lp)))\n      lp->set_action(&lp->spx_action, ACTION_REINVERT);\n\n    /* Check if we should do an optimal time-based refactorization */\n    else if(lu->timed_refact && (lu->num_pivots > 1) &&\n            (f > MIN_TIMEPIVOT) && (f > lu->time_refactnext)) {\n      /* If we have excessive time usage in automatic mode then\n         treat as untimed case and update optimal time metric, ... */\n      if((lu->timed_refact == AUTOMATIC) &&\n         (lu->num_pivots < 0.4*lp->bfp_pivotmax(lp)))\n        lu->time_refactnext = f;\n      /* ... otherwise set flag for the optimal time-based refactorization */\n      else\n        lp->set_action(&lp->spx_action, ACTION_TIMEDREINVERT);\n    }\n\n    /* Otherwise simply update the optimal time metric */\n    else\n      lu->time_refactnext = f;\n#if 0\n    if(lu->num_pivots % 10 == 0)\n      lp->report(lp, NORMAL, \"bfp pivot %d - start %f - timestat %f\",\n                             lu->num_pivots, lu->time_refactstart, f);\n#endif\n  }\n\n  test = lp->is_action(lp->spx_action, ACTION_REINVERT | ACTION_TIMEDREINVERT);\n  return(test);\n}\n\n/* DON'T MODIFY */\nMYBOOL BFP_CALLMODEL bfp_isSetI(lprec *lp)\n{\n  return( (MYBOOL) lp->invB->set_Bidentity );\n}\n\n/* DON'T MODIFY */\nint *bfp_createMDO(lprec *lp, MYBOOL *usedpos, int count, MYBOOL doMDO)\n{\n  int *mdo, i, j, kk;\n\n  mdo = (int *) malloc((count + 1)*sizeof(*mdo));\n/*  allocINT(lp, &mdo, count + 1, FALSE); */\n\n /* Fill the mdo[] array with remaining full-pivot basic user variables */\n  kk = 0;\n  for(j = 1; j <= lp->columns; j++) {\n    i = lp->rows + j;\n    if(usedpos[i] == TRUE) {\n      kk++;\n      mdo[kk] = i;\n    }\n  }\n  mdo[0] = kk;\n  if(kk == 0)\n    goto Process;\n\n /* Calculate the approximate minimum degree column ordering */\n  if(doMDO) {\n    i = lp->getMDO(lp, usedpos, mdo, NULL, FALSE);\n    if(i != 0) {\n      lp->report(lp, CRITICAL, \"bfp_createMDO: Internal error %d in minimum degree ordering routine\", i);\n      FREE(mdo);\n    }\n  }\nProcess:\n  return( mdo );\n}\nvoid BFP_CALLMODEL bfp_updaterefactstats(lprec *lp)\n{\n  INVrec *lu = lp->invB;\n\n  /* Signal that we are refactorizing */\n  lu->is_dirty = AUTOMATIC;\n\n  /* Set time of start of current refactorization cycle */\n  lu->time_refactstart = timeNow();\n  lu->time_refactnext  = 0;\n  lu->user_colcount = 0;\n\n  /* Do the numbers */\n  if(lu->force_refact)\n    lu->num_dense_refact++;\n  else if(lu->timed_refact && lp->is_action(lp->spx_action, ACTION_TIMEDREINVERT))\n    lu->num_timed_refact++;\n  lu->num_refact++;\n}\n\nint BFP_CALLMODEL bfp_rowextra(lprec *lp)\n{\n  if(lp->is_obj_in_basis(lp))\n    return( 1 );\n  else\n    return( 0 );\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/bfp/lp_BFP2.c",
    "content": "\n\n/* Routines located in lp_BFP2.cpp; optional shared for canned implementations        */\n/* Cfr. lp_BFP.h for definitions                                                      */\n/* ---------------------------------------------------------------------------------- */\n\n\n/* DON'T MODIFY */\nMYBOOL BFP_CALLMODEL bfp_init(lprec *lp, int size, int delta, char *options)\n{\n  INVrec *lu;\n\n  lp->invB = (INVrec *) calloc(1, sizeof(*(lp->invB)));\n  lu = lp->invB;\n  if((lu == NULL) || \n     !lp->bfp_resize(lp, size) ||\n     !lp->bfp_restart(lp))\n    return( FALSE );\n\n  /* Store any passed options */\n  if(options != NULL) {\n    size_t len = strlen(options);\n    lu->opts = (char *) malloc(len + 1);\n    strcpy(lu->opts, options);\n  }\n\n  /* Prepare for factorization and undo values reset by bfp_preparefactorization */\n  lp->bfp_preparefactorization(lp);\n  lu->num_refact = 0;\n\n  return( TRUE );\n}\n\n/* DON'T MODIFY */\nMYBOOL BFP_CALLMODEL bfp_restart(lprec *lp)\n{\n  INVrec *lu;\n\n  lu = lp->invB;\n  if(lu == NULL)\n    return( FALSE );\n\n  lu->status = BFP_STATUS_SUCCESS;\n  lu->max_Bsize = 0;          /* The largest NZ-count of the B matrix            */\n  lu->max_colcount = 0;       /* The maximum number of user columns in B         */\n  lu->max_LUsize = 0;         /* The largest NZ-count of LU-files generated      */\n  lu->num_refact = 0;         /* The number of times the basis has been factored */\n  lu->num_timed_refact = 0;\n  lu->num_dense_refact = 0;\n  lu->num_pivots = 0;         /* The number of pivots since last factorization   */\n  lu->pcol = NULL;\n  lu->set_Bidentity = FALSE;\n\n  return( TRUE );\n}\n\n/* DON'T MODIFY */\nMYBOOL BFP_CALLMODEL bfp_implicitslack(lprec *lp)\n{\n  return( FALSE );\n}\n\n/* DON'T MODIFY */\nint BFP_CALLMODEL bfp_colcount(lprec *lp)\n{\n  return(lp->invB->user_colcount);\n}\n\n\n/* DON'T MODIFY */\nMYBOOL BFP_CALLMODEL bfp_canresetbasis(lprec *lp)\n{\n  return( FALSE );\n}\n\n\n/* DON'T MODIFY */\nMYBOOL BFP_CALLMODEL bfp_pivotalloc(lprec *lp, int newsize)\n{\n  /* Does nothing in the default implementation */\n  return( TRUE );\n}\n\n\n/* DON'T MODIFY */\nvoid BFP_CALLMODEL bfp_finishfactorization(lprec *lp)\n{\n  INVrec *lu;\n\n  lu = lp->invB;\n\n  SETMAX(lu->max_colcount, lp->bfp_colcount(lp));\n  SETMAX(lu->max_LUsize, lp->bfp_nonzeros(lp, FALSE));\n\n  /* Signal that we done factorizing/reinverting */\n  lu->is_dirty = FALSE;\n  lp->clear_action(&lp->spx_action, ACTION_REINVERT | ACTION_TIMEDREINVERT);\n  lu->force_refact = FALSE;\n\n  /* Store information about the current inverse */\n  lu->num_pivots = 0;\n\n}\n\n\n/* DON'T MODIFY */\nLREAL BFP_CALLMODEL bfp_prepareupdate(lprec *lp, int row_nr, int col_nr, REAL *pcol)\n/* Was condensecol() in versions of lp_solve before 4.0.1.8 - KE */\n{\n  LREAL  pivValue;\n  INVrec *lu;\n\n  lu = lp->invB;\n\n  /* Store the incoming pivot value for RHS update purposes */\n  lu->col_enter = col_nr;  /* The index of the new data column */\n  lu->col_pos   = row_nr;  /* The basis column to be replaced */\n  lu->col_leave = lp->var_basic[row_nr];\n  if(pcol == NULL)\n    pivValue = 0;\n  else\n    pivValue = pcol[row_nr];\n  lu->theta_enter = pivValue;\n\n  /* Save reference to the elimination vector */\n  lu->pcol = pcol;\n\n  /* Set completion status; but hold if we are reinverting */\n  if(lu->is_dirty != AUTOMATIC)\n    lu->is_dirty = TRUE;\n\n  return( pivValue );\n}\n\n\n/* DON'T MODIFY */\nREAL BFP_CALLMODEL bfp_pivotRHS(lprec *lp, LREAL theta, REAL *pcol)\n/* This function is used to adjust the RHS in bound swap operations as\n   well as handling the updating of the RHS for normal basis changes.\n   Was rhsmincol(), ie. \"rhs minus column\" in versions of lp_solve before 4.0.1.8 - KE */\n{\n  INVrec    *lu;\n\n  lu = lp->invB;\n\n  if(pcol == NULL)\n    pcol = lu->pcol;\n\n  if(theta != 0) {\n    register int    i, n = lp->rows;\n    register LREAL  roundzero = lp->epsvalue;\n    register LREAL  *rhs = lp->rhs, rhsmax = 0;\n\n    for(i = 0; i <= n; i++, rhs++, pcol++) {\n      (*rhs) -= theta * (*pcol);\n      my_roundzero(*rhs, roundzero);\n      SETMAX(rhsmax, fabs(*rhs));\n    }\n    lp->rhsmax = rhsmax;\n  }\n\n  if(pcol == lu->pcol)\n    return( lu->theta_enter );\n  else\n    return( 0.0 );\n}\n\n\n/* DON'T MODIFY */\nvoid BFP_CALLMODEL bfp_btran_double(lprec *lp, REAL *prow, int *pnzidx, REAL *drow, int *dnzidx)\n{\n  if(prow != NULL)\n    lp->bfp_btran_normal(lp, prow, pnzidx);\n  if(drow != NULL)\n    lp->bfp_btran_normal(lp, drow, dnzidx);\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/c",
    "content": "distribution_5.5.0.15.htm\r\nlp_solve_5.5.0.15.chm\r\nlp_solve_5.5.0.15_access.zip\r\nlp_solve_5.5.0.15_AMPL_exe_osx32.tar.gz\r\nlp_solve_5.5.0.15_AMPL_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_AMPL_exe_win32.zip\r\nlp_solve_5.5.0.15_AMPL_source.tar.gz\r\nlp_solve_5.5.0.15_bfp_etaPFI_source.tar.gz\r\nlp_solve_5.5.0.15_bfp_GLPK_source.tar.gz\r\nlp_solve_5.5.0.15_bfp_LUSOL_source.tar.gz\r\nlp_solve_5.5.0.15_c.tar.gz\r\nlp_solve_5.5.0.15_COM.zip\r\nlp_solve_5.5.0.15_cs.net.zip\r\nlp_solve_5.5.0.15_Delphi.zip\r\nlp_solve_5.5.0.15_dev_osx32.tar.gz\r\nlp_solve_5.5.0.15_dev_ux32.tar.gz\r\nlp_solve_5.5.0.15_dev_ux64.tar.gz\r\nlp_solve_5.5.0.15_dev_win32.zip\r\nlp_solve_5.5.0.15_dev_win64.zip\r\nlp_solve_5.5.0.15_doc.tar.gz\r\nlp_solve_5.5.0.15_Euler_exe_win32.zip\r\nlp_solve_5.5.0.15_Euler_source.tar.gz\r\nlp_solve_5.5.0.15_excel.zip\r\nlp_solve_5.5.0.15_exe_osx32.tar.gz\r\nlp_solve_5.5.0.15_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_exe_ux64.tar.gz\r\nlp_solve_5.5.0.15_exe_win32.zip\r\nlp_solve_5.5.0.15_exe_win64.zip\r\nlp_solve_5.5.0.15_FreeMat_exe_osx32.tar.gz\r\nlp_solve_5.5.0.15_FreeMat_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_FreeMat_exe_ux64.tar.gz\r\nlp_solve_5.5.0.15_FreeMat_exe_win32.zip\r\nlp_solve_5.5.0.15_FreeMat_source.tar.gz\r\nlp_solve_5.5.0.15_IDE_Setup.exe\r\nlp_solve_5.5.0.15_IDE_source.zip\r\nlp_solve_5.5.0.15_java.zip\r\nlp_solve_5.5.0.15_MATLAB_exe_osx32.tar.gz\r\nlp_solve_5.5.0.15_MATLAB_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_MATLAB_exe_ux64.tar.gz\r\nlp_solve_5.5.0.15_MATLAB_exe_win32.zip\r\nlp_solve_5.5.0.15_MATLAB_exe_win64.zip\r\nlp_solve_5.5.0.15_MATLAB_source.tar.gz\r\nlp_solve_5.5.0.15_octave_exe_osx32.tar.gz\r\nlp_solve_5.5.0.15_octave_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_octave_exe_ux64.tar.gz\r\nlp_solve_5.5.0.15_octave_exe_win32.zip\r\nlp_solve_5.5.0.15_octave_source.tar.gz\r\nlp_solve_5.5.0.15_OMATRIX_exe_win32.zip\r\nlp_solve_5.5.0.15_OMATRIX_source.tar.gz\r\nlp_solve_5.5.0.15_PHP_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_PHP_exe_ux64.tar.gz\r\nlp_solve_5.5.0.15_PHP_exe_win32.zip\r\nlp_solve_5.5.0.15_PHP_source.tar.gz\r\nlp_solve_5.5.0.15_Python_source.tar.gz\r\nlp_solve_5.5.0.15_Python2.4_exe_win32.zip\r\nlp_solve_5.5.0.15_Python2.5_exe_win32.zip\r\nlp_solve_5.5.0.15_Python2.6_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_Python2.6_exe_ux64.tar.gz\r\nlp_solve_5.5.0.15_Python2.6_exe_win32.zip\r\nlp_solve_5.5.0.15_Python2.6_exe_win64.zip\r\nlp_solve_5.5.0.15_scilab_exe_osx32.tar.gz\r\nlp_solve_5.5.0.15_scilab_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_scilab_exe_ux64.tar.gz\r\nlp_solve_5.5.0.15_scilab_exe_win32.zip\r\nlp_solve_5.5.0.15_scilab_exe_win64.zip\r\nlp_solve_5.5.0.15_scilab_source.tar.gz\r\nlp_solve_5.5.0.15_source.tar.gz\r\nlp_solve_5.5.0.15_Sysquake_exe_osx32.tar.gz\r\nlp_solve_5.5.0.15_Sysquake_exe_ux32.tar.gz\r\nlp_solve_5.5.0.15_Sysquake_exe_win32.zip\r\nlp_solve_5.5.0.15_Sysquake_source.tar.gz\r\nlp_solve_5.5.0.15_vb.net.zip\r\nlp_solve_5.5.0.15_vb.zip\r\nlp_solve_5.5.0.15_xli_CPLEX_source.tar.gz\r\nlp_solve_5.5.0.15_xli_DIMACS_source.tar.gz\r\nlp_solve_5.5.0.15_xli_LINDO_source.tar.gz\r\nlp_solve_5.5.0.15_xli_LPFML_source.tar.gz\r\nlp_solve_5.5.0.15_xli_MathProg_source.tar.gz\r\nlp_solve_5.5.0.15_xli_XPRESS_source.tar.gz\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/colamd/colamd.c",
    "content": "/* ========================================================================== */\n/* === colamd/symamd - a sparse matrix column ordering algorithm ============ */\n/* ========================================================================== */\n\n/*\n    colamd:  an approximate minimum degree column ordering algorithm,\n    \tfor LU factorization of symmetric or unsymmetric matrices,\n\tQR factorization, least squares, interior point methods for\n\tlinear programming problems, and other related problems.\n\n    symamd:  an approximate minimum degree ordering algorithm for Cholesky\n    \tfactorization of symmetric matrices.\n\n    Purpose:\n\n\tColamd computes a permutation Q such that the Cholesky factorization of\n\t(AQ)'(AQ) has less fill-in and requires fewer floating point operations\n\tthan A'A.  This also provides a good ordering for sparse partial\n\tpivoting methods, P(AQ) = LU, where Q is computed prior to numerical\n\tfactorization, and P is computed during numerical factorization via\n\tconventional partial pivoting with row interchanges.  Colamd is the\n\tcolumn ordering method used in SuperLU, part of the ScaLAPACK library.\n\tIt is also available as built-in function in Matlab Version 6,\n\tavailable from MathWorks, Inc. (http://www.mathworks.com).  This\n\troutine can be used in place of colmmd in Matlab.  By default, the \\\n\tand / operators in Matlab perform a column ordering (using colmmd\n\tor colamd) prior to LU factorization using sparse partial pivoting,\n\tin the built-in Matlab lu(A) routine.\n\n    \tSymamd computes a permutation P of a symmetric matrix A such that the\n\tCholesky factorization of PAP' has less fill-in and requires fewer\n\tfloating point operations than A.  Symamd constructs a matrix M such\n\tthat M'M has the same nonzero pattern of A, and then orders the columns\n\tof M using colmmd.  The column ordering of M is then returned as the\n\trow and column ordering P of A. \n\n    Authors:\n\n\tThe authors of the code itself are Stefan I. Larimore and Timothy A.\n\tDavis (davis@cise.ufl.edu), University of Florida.  The algorithm was\n\tdeveloped in collaboration with John Gilbert, Xerox PARC, and Esmond\n\tNg, Oak Ridge National Laboratory.\n\n    Date:\n\n\tMay 4, 2001.  Version 2.1.\n\n    Acknowledgements:\n\n\tThis work was supported by the National Science Foundation, under\n\tgrants DMS-9504974 and DMS-9803599.\n\n    Notice:\n\n\tCopyright (c) 1998-2001 by the University of Florida.\n\tAll Rights Reserved.\n\n\tTHIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY\n\tEXPRESSED OR IMPLIED.  ANY USE IS AT YOUR OWN RISK.\n\n\tPermission is hereby granted to use or copy this program for any\n\tpurpose, provided the above notices are retained on all copies.\n\tUser documentation of any code that uses this code must cite the\n\tAuthors, the Copyright, and \"Used by permission.\"  If this code is\n\taccessible from within Matlab, then typing \"help colamd\" and \"help\n\tsymamd\" must cite the Authors.  Permission to modify the code and to\n\tdistribute modified code is granted, provided the above notices are\n\tretained, and a notice that the code was modified is included with the\n\tabove copyright notice.  You must also retain the Availability\n\tinformation below, of the original version.\n\n\tThis software is provided free of charge.\n\n    Availability:\n\n\tThe colamd/symamd library is available at\n\n\t    http://www.cise.ufl.edu/research/sparse/colamd/\n\n\tThis is the http://www.cise.ufl.edu/research/sparse/colamd/colamd.c\n\tfile.  It requires the colamd.h file.  It is required by the colamdmex.c\n\tand symamdmex.c files, for the Matlab interface to colamd and symamd.\n\n    Changes to the colamd library since Version 1.0 and 1.1:\n\n\tNo bugs were found in version 1.1.  These changes merely add new\n\tfunctionality.\n\n    \t* added the COLAMD_RECOMMENDED (nnz, n_row, n_col) macro.\n\n\t* moved the output statistics, from A, to a separate output argument.\n\t\tThe arguments changed for the C-callable routines.\n\n\t* added colamd_report and symamd_report.\n\n\t* added a C-callable symamd routine.  Formerly, symamd was only\n\t\tavailable as a mexFunction from Matlab.\n\n\t* added error-checking to symamd.  Formerly, it assumed its input\n\t\twas error-free.\n\n\t* added the optional stats and knobs arguments to the symamd mexFunction\n\n\t* deleted colamd_help.  A help message is still available from\n\t\t\"help colamd\" and \"help symamd\" in Matlab.\n\n\t* deleted colamdtree.m and symamdtree.m.  Now, colamd.m and symamd.m\n\t\talso do the elimination tree post-ordering.  The Version 1.1\n\t\tcolamd and symamd mexFunctions, which do not do the post-\n\t\tordering, are now visible as colamdmex and symamdmex from\n\t\tMatlab.  Essentialy, the post-ordering is now the default\n\t\tbehavior of colamd.m and symamd.m, to match the behavior of\n\t\tcolmmd and symmmd.  The post-ordering is only available in the\n\t\tMatlab interface, not the C-callable interface.\n\n\t* made a slight change to the dense row/column detection in symamd,\n\t\tto match the stated specifications.\n\n    Changes from Version 2.0 to 2.1:\n\n\t* TRUE and FALSE are predefined on some systems, so they are defined\n\t\there only if not already defined.\n\t\n\t* web site changed\n\n\t* UNIX Makefile modified, to handle the case if \".\" is not in your path.\n\n*/\n\n/* ========================================================================== */\n/* === Description of user-callable routines ================================ */\n/* ========================================================================== */\n\n/*\n    ----------------------------------------------------------------------------\n    colamd_recommended:\n    ----------------------------------------------------------------------------\n\n\tC syntax:\n\n\t    #include \"colamd.h\"\n\t    int colamd_recommended (int nnz, int n_row, int n_col) ;\n\n\t    or as a C macro\n\n\t    #include \"colamd.h\"\n\t    Alen = COLAMD_RECOMMENDED (int nnz, int n_row, int n_col) ;\n\n\tPurpose:\n\n\t    Returns recommended value of Alen for use by colamd.  Returns -1\n\t    if any input argument is negative.  The use of this routine\n\t    or macro is optional.  Note that the macro uses its arguments\n\t    more than once, so be careful for side effects, if you pass\n\t    expressions as arguments to COLAMD_RECOMMENDED.  Not needed for\n\t    symamd, which dynamically allocates its own memory.\n\n\tArguments (all input arguments):\n\n\t    int nnz ;\t\tNumber of nonzeros in the matrix A.  This must\n\t\t\t\tbe the same value as p [n_col] in the call to\n\t\t\t\tcolamd - otherwise you will get a wrong value\n\t\t\t\tof the recommended memory to use.\n\n\t    int n_row ;\t\tNumber of rows in the matrix A.\n\n\t    int n_col ;\t\tNumber of columns in the matrix A.\n\n    ----------------------------------------------------------------------------\n    colamd_set_defaults:\n    ----------------------------------------------------------------------------\n\n\tC syntax:\n\n\t    #include \"colamd.h\"\n\t    colamd_set_defaults (int knobs [COLAMD_KNOBS]) ;\n\n\tPurpose:\n\n\t    Sets the default parameters.  The use of this routine is optional.\n\n\tArguments:\n\n\t    double knobs [COLAMD_KNOBS] ;\tOutput only.\n\n\t\tColamd: rows with more than (knobs [COLAMD_DENSE_ROW] * n_col)\n\t\tentries are removed prior to ordering.  Columns with more than\n\t\t(knobs [COLAMD_DENSE_COL] * n_row) entries are removed prior to\n\t\tordering, and placed last in the output column ordering. \n\n\t\tSymamd: uses only knobs [COLAMD_DENSE_ROW], which is knobs [0].\n\t\tRows and columns with more than (knobs [COLAMD_DENSE_ROW] * n)\n\t\tentries are removed prior to ordering, and placed last in the\n\t\toutput ordering.\n\n\t\tCOLAMD_DENSE_ROW and COLAMD_DENSE_COL are defined as 0 and 1,\n\t\trespectively, in colamd.h.  Default values of these two knobs\n\t\tare both 0.5.  Currently, only knobs [0] and knobs [1] are\n\t\tused, but future versions may use more knobs.  If so, they will\n\t\tbe properly set to their defaults by the future version of\n\t\tcolamd_set_defaults, so that the code that calls colamd will\n\t\tnot need to change, assuming that you either use\n\t\tcolamd_set_defaults, or pass a (double *) NULL pointer as the\n\t\tknobs array to colamd or symamd.\n\n    ----------------------------------------------------------------------------\n    colamd:\n    ----------------------------------------------------------------------------\n\n\tC syntax:\n\n\t    #include \"colamd.h\"\n\t    int colamd (int n_row, int n_col, int Alen, int *A, int *p,\n\t    \tdouble knobs [COLAMD_KNOBS], int stats [COLAMD_STATS]) ;\n\n\tPurpose:\n\n\t    Computes a column ordering (Q) of A such that P(AQ)=LU or\n\t    (AQ)'AQ=LL' have less fill-in and require fewer floating point\n\t    operations than factorizing the unpermuted matrix A or A'A,\n\t    respectively.\n\t    \n\tReturns:\n\n\t    TRUE (1) if successful, FALSE (0) otherwise.\n\n\tArguments:\n\n\t    int n_row ;\t\tInput argument.\n\n\t\tNumber of rows in the matrix A.\n\t\tRestriction:  n_row >= 0.\n\t\tColamd returns FALSE if n_row is negative.\n\n\t    int n_col ;\t\tInput argument.\n\n\t\tNumber of columns in the matrix A.\n\t\tRestriction:  n_col >= 0.\n\t\tColamd returns FALSE if n_col is negative.\n\n\t    int Alen ;\t\tInput argument.\n\n\t\tRestriction (see note):\n\t\tAlen >= 2*nnz + 6*(n_col+1) + 4*(n_row+1) + n_col\n\t\tColamd returns FALSE if these conditions are not met.\n\n\t\tNote:  this restriction makes an modest assumption regarding\n\t\tthe size of the two typedef's structures in colamd.h.\n\t\tWe do, however, guarantee that\n\n\t\t\tAlen >= colamd_recommended (nnz, n_row, n_col)\n\t\t\n\t\tor equivalently as a C preprocessor macro: \n\n\t\t\tAlen >= COLAMD_RECOMMENDED (nnz, n_row, n_col)\n\n\t\twill be sufficient.\n\n\t    int A [Alen] ;\tInput argument, undefined on output.\n\n\t\tA is an integer array of size Alen.  Alen must be at least as\n\t\tlarge as the bare minimum value given above, but this is very\n\t\tlow, and can result in excessive run time.  For best\n\t\tperformance, we recommend that Alen be greater than or equal to\n\t\tcolamd_recommended (nnz, n_row, n_col), which adds\n\t\tnnz/5 to the bare minimum value given above.\n\n\t\tOn input, the row indices of the entries in column c of the\n\t\tmatrix are held in A [(p [c]) ... (p [c+1]-1)].  The row indices\n\t\tin a given column c need not be in ascending order, and\n\t\tduplicate row indices may be be present.  However, colamd will\n\t\twork a little faster if both of these conditions are met\n\t\t(Colamd puts the matrix into this format, if it finds that the\n\t\tthe conditions are not met).\n\n\t\tThe matrix is 0-based.  That is, rows are in the range 0 to\n\t\tn_row-1, and columns are in the range 0 to n_col-1.  Colamd\n\t\treturns FALSE if any row index is out of range.\n\n\t\tThe contents of A are modified during ordering, and are\n\t\tundefined on output.\n\n\t    int p [n_col+1] ;\tBoth input and output argument.\n\n\t\tp is an integer array of size n_col+1.  On input, it holds the\n\t\t\"pointers\" for the column form of the matrix A.  Column c of\n\t\tthe matrix A is held in A [(p [c]) ... (p [c+1]-1)].  The first\n\t\tentry, p [0], must be zero, and p [c] <= p [c+1] must hold\n\t\tfor all c in the range 0 to n_col-1.  The value p [n_col] is\n\t\tthus the total number of entries in the pattern of the matrix A.\n\t\tColamd returns FALSE if these conditions are not met.\n\n\t\tOn output, if colamd returns TRUE, the array p holds the column\n\t\tpermutation (Q, for P(AQ)=LU or (AQ)'(AQ)=LL'), where p [0] is\n\t\tthe first column index in the new ordering, and p [n_col-1] is\n\t\tthe last.  That is, p [k] = j means that column j of A is the\n\t\tkth pivot column, in AQ, where k is in the range 0 to n_col-1\n\t\t(p [0] = j means that column j of A is the first column in AQ).\n\n\t\tIf colamd returns FALSE, then no permutation is returned, and\n\t\tp is undefined on output.\n\n\t    double knobs [COLAMD_KNOBS] ;\tInput argument.\n\n\t\tSee colamd_set_defaults for a description.\n\n\t    int stats [COLAMD_STATS] ;\t\tOutput argument.\n\n\t\tStatistics on the ordering, and error status.\n\t\tSee colamd.h for related definitions.\n\t\tColamd returns FALSE if stats is not present.\n\n\t\tstats [0]:  number of dense or empty rows ignored.\n\n\t\tstats [1]:  number of dense or empty columns ignored (and\n\t\t\t\tordered last in the output permutation p)\n\t\t\t\tNote that a row can become \"empty\" if it\n\t\t\t\tcontains only \"dense\" and/or \"empty\" columns,\n\t\t\t\tand similarly a column can become \"empty\" if it\n\t\t\t\tonly contains \"dense\" and/or \"empty\" rows.\n\n\t\tstats [2]:  number of garbage collections performed.\n\t\t\t\tThis can be excessively high if Alen is close\n\t\t\t\tto the minimum required value.\n\n\t\tstats [3]:  status code.  < 0 is an error code.\n\t\t\t    > 1 is a warning or notice.\n\n\t\t\t0\tOK.  Each column of the input matrix contained\n\t\t\t\trow indices in increasing order, with no\n\t\t\t\tduplicates.\n\n\t\t\t1\tOK, but columns of input matrix were jumbled\n\t\t\t\t(unsorted columns or duplicate entries).  Colamd\n\t\t\t\thad to do some extra work to sort the matrix\n\t\t\t\tfirst and remove duplicate entries, but it\n\t\t\t\tstill was able to return a valid permutation\n\t\t\t\t(return value of colamd was TRUE).\n\n\t\t\t\t\tstats [4]: highest numbered column that\n\t\t\t\t\t\tis unsorted or has duplicate\n\t\t\t\t\t\tentries.\n\t\t\t\t\tstats [5]: last seen duplicate or\n\t\t\t\t\t\tunsorted row index.\n\t\t\t\t\tstats [6]: number of duplicate or\n\t\t\t\t\t\tunsorted row indices.\n\n\t\t\t-1\tA is a null pointer\n\n\t\t\t-2\tp is a null pointer\n\n\t\t\t-3 \tn_row is negative\n\n\t\t\t\t\tstats [4]: n_row\n\n\t\t\t-4\tn_col is negative\n\n\t\t\t\t\tstats [4]: n_col\n\n\t\t\t-5\tnumber of nonzeros in matrix is negative\n\n\t\t\t\t\tstats [4]: number of nonzeros, p [n_col]\n\n\t\t\t-6\tp [0] is nonzero\n\n\t\t\t\t\tstats [4]: p [0]\n\n\t\t\t-7\tA is too small\n\n\t\t\t\t\tstats [4]: required size\n\t\t\t\t\tstats [5]: actual size (Alen)\n\n\t\t\t-8\ta column has a negative number of entries\n\n\t\t\t\t\tstats [4]: column with < 0 entries\n\t\t\t\t\tstats [5]: number of entries in col\n\n\t\t\t-9\ta row index is out of bounds\n\n\t\t\t\t\tstats [4]: column with bad row index\n\t\t\t\t\tstats [5]: bad row index\n\t\t\t\t\tstats [6]: n_row, # of rows of matrx\n\n\t\t\t-10\t(unused; see symamd.c)\n\n\t\t\t-999\t(unused; see symamd.c)\n\n\t\tFuture versions may return more statistics in the stats array.\n\n\tExample:\n\t\n\t    See http://www.cise.ufl.edu/research/sparse/colamd/example.c\n\t    for a complete example.\n\n\t    To order the columns of a 5-by-4 matrix with 11 nonzero entries in\n\t    the following nonzero pattern\n\n\t    \tx 0 x 0\n\t\tx 0 x x\n\t\t0 x x 0\n\t\t0 0 x x\n\t\tx x 0 0\n\n\t    with default knobs and no output statistics, do the following:\n\n\t\t#include \"colamd.h\"\n\t\t#define ALEN COLAMD_RECOMMENDED (11, 5, 4)\n\t\tint A [ALEN] = {1, 2, 5, 3, 5, 1, 2, 3, 4, 2, 4} ;\n\t\tint p [ ] = {0, 3, 5, 9, 11} ;\n\t\tint stats [COLAMD_STATS] ;\n\t\tcolamd (5, 4, ALEN, A, p, (double *) NULL, stats) ;\n\n\t    The permutation is returned in the array p, and A is destroyed.\n\n    ----------------------------------------------------------------------------\n    symamd:\n    ----------------------------------------------------------------------------\n\n\tC syntax:\n\n\t    #include \"colamd.h\"\n\t    int symamd (int n, int *A, int *p, int *perm,\n\t    \tint knobs [COLAMD_KNOBS], int stats [COLAMD_STATS],\n\t\tvoid (*allocate) (size_t, size_t), void (*release) (void *)) ;\n\n\tPurpose:\n\n    \t    The symamd routine computes an ordering P of a symmetric sparse\n\t    matrix A such that the Cholesky factorization PAP' = LL' remains\n\t    sparse.  It is based on a column ordering of a matrix M constructed\n\t    so that the nonzero pattern of M'M is the same as A.  The matrix A\n\t    is assumed to be symmetric; only the strictly lower triangular part\n\t    is accessed.  You must pass your selected memory allocator (usually\n\t    calloc/free or mxCalloc/mxFree) to symamd, for it to allocate\n\t    memory for the temporary matrix M.\n\n\tReturns:\n\n\t    TRUE (1) if successful, FALSE (0) otherwise.\n\n\tArguments:\n\n\t    int n ;\t\tInput argument.\n\n\t    \tNumber of rows and columns in the symmetrix matrix A.\n\t\tRestriction:  n >= 0.\n\t\tSymamd returns FALSE if n is negative.\n\n\t    int A [nnz] ;\tInput argument.\n\n\t    \tA is an integer array of size nnz, where nnz = p [n].\n\t\t\n\t\tThe row indices of the entries in column c of the matrix are\n\t\theld in A [(p [c]) ... (p [c+1]-1)].  The row indices in a\n\t\tgiven column c need not be in ascending order, and duplicate\n\t\trow indices may be present.  However, symamd will run faster\n\t\tif the columns are in sorted order with no duplicate entries. \n\n\t\tThe matrix is 0-based.  That is, rows are in the range 0 to\n\t\tn-1, and columns are in the range 0 to n-1.  Symamd\n\t\treturns FALSE if any row index is out of range.\n\n\t\tThe contents of A are not modified.\n\n\t    int p [n+1] ;   \tInput argument.\n\n\t\tp is an integer array of size n+1.  On input, it holds the\n\t\t\"pointers\" for the column form of the matrix A.  Column c of\n\t\tthe matrix A is held in A [(p [c]) ... (p [c+1]-1)].  The first\n\t\tentry, p [0], must be zero, and p [c] <= p [c+1] must hold\n\t\tfor all c in the range 0 to n-1.  The value p [n] is\n\t\tthus the total number of entries in the pattern of the matrix A.\n\t\tSymamd returns FALSE if these conditions are not met.\n\n\t\tThe contents of p are not modified.\n\n\t    int perm [n+1] ;   \tOutput argument.\n\n\t\tOn output, if symamd returns TRUE, the array perm holds the\n\t\tpermutation P, where perm [0] is the first index in the new\n\t\tordering, and perm [n-1] is the last.  That is, perm [k] = j\n\t\tmeans that row and column j of A is the kth column in PAP',\n\t\twhere k is in the range 0 to n-1 (perm [0] = j means\n\t\tthat row and column j of A are the first row and column in\n\t\tPAP').  The array is used as a workspace during the ordering,\n\t\twhich is why it must be of length n+1, not just n.\n\n\t    double knobs [COLAMD_KNOBS] ;\tInput argument.\n\n\t\tSee colamd_set_defaults for a description.\n\n\t    int stats [COLAMD_STATS] ;\t\tOutput argument.\n\n\t\tStatistics on the ordering, and error status.\n\t\tSee colamd.h for related definitions.\n\t\tSymamd returns FALSE if stats is not present.\n\n\t\tstats [0]:  number of dense or empty row and columns ignored\n\t\t\t\t(and ordered last in the output permutation \n\t\t\t\tperm).  Note that a row/column can become\n\t\t\t\t\"empty\" if it contains only \"dense\" and/or\n\t\t\t\t\"empty\" columns/rows.\n\n\t\tstats [1]:  (same as stats [0])\n\n\t\tstats [2]:  number of garbage collections performed.\n\n\t\tstats [3]:  status code.  < 0 is an error code.\n\t\t\t    > 1 is a warning or notice.\n\n\t\t\t0\tOK.  Each column of the input matrix contained\n\t\t\t\trow indices in increasing order, with no\n\t\t\t\tduplicates.\n\n\t\t\t1\tOK, but columns of input matrix were jumbled\n\t\t\t\t(unsorted columns or duplicate entries).  Symamd\n\t\t\t\thad to do some extra work to sort the matrix\n\t\t\t\tfirst and remove duplicate entries, but it\n\t\t\t\tstill was able to return a valid permutation\n\t\t\t\t(return value of symamd was TRUE).\n\n\t\t\t\t\tstats [4]: highest numbered column that\n\t\t\t\t\t\tis unsorted or has duplicate\n\t\t\t\t\t\tentries.\n\t\t\t\t\tstats [5]: last seen duplicate or\n\t\t\t\t\t\tunsorted row index.\n\t\t\t\t\tstats [6]: number of duplicate or\n\t\t\t\t\t\tunsorted row indices.\n\n\t\t\t-1\tA is a null pointer\n\n\t\t\t-2\tp is a null pointer\n\n\t\t\t-3\t(unused, see colamd.c)\n\n\t\t\t-4 \tn is negative\n\n\t\t\t\t\tstats [4]: n\n\n\t\t\t-5\tnumber of nonzeros in matrix is negative\n\n\t\t\t\t\tstats [4]: # of nonzeros (p [n]).\n\n\t\t\t-6\tp [0] is nonzero\n\n\t\t\t\t\tstats [4]: p [0]\n\n\t\t\t-7\t(unused)\n\n\t\t\t-8\ta column has a negative number of entries\n\n\t\t\t\t\tstats [4]: column with < 0 entries\n\t\t\t\t\tstats [5]: number of entries in col\n\n\t\t\t-9\ta row index is out of bounds\n\n\t\t\t\t\tstats [4]: column with bad row index\n\t\t\t\t\tstats [5]: bad row index\n\t\t\t\t\tstats [6]: n_row, # of rows of matrx\n\n\t\t\t-10\tout of memory (unable to allocate temporary\n\t\t\t\tworkspace for M or count arrays using the\n\t\t\t\t\"allocate\" routine passed into symamd).\n\n\t\t\t-999\tinternal error.  colamd failed to order the\n\t\t\t\tmatrix M, when it should have succeeded.  This\n\t\t\t\tindicates a bug.  If this (and *only* this)\n\t\t\t\terror code occurs, please contact the authors.\n\t\t\t\tDon't contact the authors if you get any other\n\t\t\t\terror code.\n\n\t\tFuture versions may return more statistics in the stats array.\n\n\t    void * (*allocate) (size_t, size_t)\n\n\t    \tA pointer to a function providing memory allocation.  The\n\t\tallocated memory must be returned initialized to zero.  For a\n\t\tC application, this argument should normally be a pointer to\n\t\tcalloc.  For a Matlab mexFunction, the routine mxCalloc is\n\t\tpassed instead.\n\n\t    void (*release) (size_t, size_t)\n\n\t    \tA pointer to a function that frees memory allocated by the\n\t\tmemory allocation routine above.  For a C application, this\n\t\targument should normally be a pointer to free.  For a Matlab\n\t\tmexFunction, the routine mxFree is passed instead.\n\n\n    ----------------------------------------------------------------------------\n    colamd_report:\n    ----------------------------------------------------------------------------\n\n\tC syntax:\n\n\t    #include \"colamd.h\"\n\t    colamd_report (int stats [COLAMD_STATS]) ;\n\n\tPurpose:\n\n\t    Prints the error status and statistics recorded in the stats\n\t    array on the standard error output (for a standard C routine)\n\t    or on the Matlab output (for a mexFunction).\n\n\tArguments:\n\n\t    int stats [COLAMD_STATS] ;\tInput only.  Statistics from colamd.\n\n\n    ----------------------------------------------------------------------------\n    symamd_report:\n    ----------------------------------------------------------------------------\n\n\tC syntax:\n\n\t    #include \"colamd.h\"\n\t    symamd_report (int stats [COLAMD_STATS]) ;\n\n\tPurpose:\n\n\t    Prints the error status and statistics recorded in the stats\n\t    array on the standard error output (for a standard C routine)\n\t    or on the Matlab output (for a mexFunction).\n\n\tArguments:\n\n\t    int stats [COLAMD_STATS] ;\tInput only.  Statistics from symamd.\n\n\n*/\n\n/* ========================================================================== */\n/* === Scaffolding code definitions  ======================================== */\n/* ========================================================================== */\n\n/* Ensure that debugging is turned off: */\n#ifndef NDEBUG\n#define NDEBUG\n#endif /* NDEBUG */\n\n/*\n   Our \"scaffolding code\" philosophy:  In our opinion, well-written library\n   code should keep its \"debugging\" code, and just normally have it turned off\n   by the compiler so as not to interfere with performance.  This serves\n   several purposes:\n\n   (1) assertions act as comments to the reader, telling you what the code\n\texpects at that point.  All assertions will always be true (unless\n\tthere really is a bug, of course).\n\n   (2) leaving in the scaffolding code assists anyone who would like to modify\n\tthe code, or understand the algorithm (by reading the debugging output,\n\tone can get a glimpse into what the code is doing).\n\n   (3) (gasp!) for actually finding bugs.  This code has been heavily tested\n\tand \"should\" be fully functional and bug-free ... but you never know...\n\n    To enable debugging, comment out the \"#define NDEBUG\" above.  For a Matlab\n    mexFunction, you will also need to modify mexopts.sh to remove the -DNDEBUG\n    definition.  The code will become outrageously slow when debugging is\n    enabled.  To control the level of debugging output, set an environment\n    variable D to 0 (little), 1 (some), 2, 3, or 4 (lots).  When debugging,\n    you should see the following message on the standard output:\n\n    \tcolamd: debug version, D = 1 (THIS WILL BE SLOW!)\n\n    or a similar message for symamd.  If you don't, then debugging has not\n    been enabled.\n\n*/\n\n/* ========================================================================== */\n/* === Include files ======================================================== */\n/* ========================================================================== */\n\n#include \"colamd.h\"\n#include <limits.h>\n\n#ifdef MATLAB_MEX_FILE\n#include \"mex.h\"\n#include \"matrix.h\"\n#else\n#include <stdio.h>\n#include <assert.h>\n#endif /* MATLAB_MEX_FILE */\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n/* ========================================================================== */\n/* === Definitions ========================================================== */\n/* ========================================================================== */\n\n/* Routines are either PUBLIC (user-callable) or PRIVATE (not user-callable) */\n#define PUBLIC\n#define PRIVATE static\n\n#define MAX(a,b) (((a) > (b)) ? (a) : (b))\n#define MIN(a,b) (((a) < (b)) ? (a) : (b))\n\n#define ONES_COMPLEMENT(r) (-(r)-1)\n\n/* -------------------------------------------------------------------------- */\n/* Change for version 2.1:  define TRUE and FALSE only if not yet defined */  \n/* -------------------------------------------------------------------------- */\n\n#ifndef TRUE\n#define TRUE (1)\n#endif\n\n#ifndef FALSE\n#define FALSE (0)\n#endif\n\n/* -------------------------------------------------------------------------- */\n\n#define EMPTY\t(-1)\n\n/* Row and column status */\n#define ALIVE\t(0)\n#define DEAD\t(-1)\n\n/* Column status */\n#define DEAD_PRINCIPAL\t\t(-1)\n#define DEAD_NON_PRINCIPAL\t(-2)\n\n/* Macros for row and column status update and checking. */\n#define ROW_IS_DEAD(r)\t\t\tROW_IS_MARKED_DEAD (Row[r].shared2.mark)\n#define ROW_IS_MARKED_DEAD(row_mark)\t(row_mark < ALIVE)\n#define ROW_IS_ALIVE(r)\t\t\t(Row [r].shared2.mark >= ALIVE)\n#define COL_IS_DEAD(c)\t\t\t(Col [c].start < ALIVE)\n#define COL_IS_ALIVE(c)\t\t\t(Col [c].start >= ALIVE)\n#define COL_IS_DEAD_PRINCIPAL(c)\t(Col [c].start == DEAD_PRINCIPAL)\n#define KILL_ROW(r)\t\t\t{ Row [r].shared2.mark = DEAD ; }\n#define KILL_PRINCIPAL_COL(c)\t\t{ Col [c].start = DEAD_PRINCIPAL ; }\n#define KILL_NON_PRINCIPAL_COL(c)\t{ Col [c].start = DEAD_NON_PRINCIPAL ; }\n\n/* ========================================================================== */\n/* === Colamd reporting mechanism =========================================== */\n/* ========================================================================== */\n\n#ifdef MATLAB_MEX_FILE\n\n/* use mexPrintf in a Matlab mexFunction, for debugging and statistics output */\n#define PRINTF mexPrintf\n\n/* In Matlab, matrices are 1-based to the user, but 0-based internally */\n#define INDEX(i) ((i)+1)\n\n#else\n\n/* Use printf in standard C environment, for debugging and statistics output. */\n/* Output is generated only if debugging is enabled at compile time, or if */\n/* the caller explicitly calls colamd_report or symamd_report. */\n#define PRINTF printf\n\n/* In C, matrices are 0-based and indices are reported as such in *_report */\n#define INDEX(i) (i)\n\n#endif /* MATLAB_MEX_FILE */\n\n/* ========================================================================== */\n/* === Prototypes of PRIVATE routines ======================================= */\n/* ========================================================================== */\n\nPRIVATE int init_rows_cols\n(\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int A [],\n    int p [],\n    int stats [COLAMD_STATS]\n) ;\n\nPRIVATE void init_scoring\n(\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int A [],\n    int head [],\n    double knobs [COLAMD_KNOBS],\n    int *p_n_row2,\n    int *p_n_col2,\n    int *p_max_deg\n) ;\n\nPRIVATE int find_ordering\n(\n    int n_row,\n    int n_col,\n    int Alen,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int A [],\n    int head [],\n    int n_col2,\n    int max_deg,\n    int pfree\n) ;\n\nPRIVATE void order_children\n(\n    int n_col,\n    Colamd_Col Col [],\n    int p []\n) ;\n\nPRIVATE void detect_super_cols\n(\n\n#ifndef NDEBUG\n    int n_col,\n    Colamd_Row Row [],\n#endif /* NDEBUG */\n\n    Colamd_Col Col [],\n    int A [],\n    int head [],\n    int row_start,\n    int row_length\n) ;\n\nPRIVATE int garbage_collection\n(\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int A [],\n    int *pfree\n) ;\n\nPRIVATE int clear_mark\n(\n    int n_row,\n    Colamd_Row Row []\n) ;\n\nPRIVATE void print_report\n(\n    char *method,\n    int stats [COLAMD_STATS]\n) ;\n\n/* ========================================================================== */\n/* === Debugging prototypes and definitions ================================= */\n/* ========================================================================== */\n\n#ifndef NDEBUG\n\n/* colamd_debug is the *ONLY* global variable, and is only */\n/* present when debugging */\n\nPRIVATE int colamd_debug ;\t/* debug print level */\n\n#define DEBUG0(params) { (void) PRINTF params ; }\n#define DEBUG1(params) { if (colamd_debug >= 1) (void) PRINTF params ; }\n#define DEBUG2(params) { if (colamd_debug >= 2) (void) PRINTF params ; }\n#define DEBUG3(params) { if (colamd_debug >= 3) (void) PRINTF params ; }\n#define DEBUG4(params) { if (colamd_debug >= 4) (void) PRINTF params ; }\n\n#ifdef MATLAB_MEX_FILE\n#define ASSERT(expression) (mxAssert ((expression), \"\"))\n#else\n#define ASSERT(expression) (assert (expression))\n#endif /* MATLAB_MEX_FILE */\n\nPRIVATE void colamd_get_debug\t/* gets the debug print level from getenv */\n(\n    char *method\n) ;\n\nPRIVATE void debug_deg_lists\n(\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int head [],\n    int min_score,\n    int should,\n    int max_deg\n) ;\n\nPRIVATE void debug_mark\n(\n    int n_row,\n    Colamd_Row Row [],\n    int tag_mark,\n    int max_mark\n) ;\n\nPRIVATE void debug_matrix\n(\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int A []\n) ;\n\nPRIVATE void debug_structures\n(\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int A [],\n    int n_col2\n) ;\n\n#else /* NDEBUG */\n\n/* === No debugging ========================================================= */\n\n#define DEBUG0(params) ;\n#define DEBUG1(params) ;\n#define DEBUG2(params) ;\n#define DEBUG3(params) ;\n#define DEBUG4(params) ;\n\n#define ASSERT(expression) ((void) 0)\n\n#endif /* NDEBUG */\n\n/* ========================================================================== */\n\n\n\n/* ========================================================================== */\n/* === USER-CALLABLE ROUTINES: ============================================== */\n/* ========================================================================== */\n\n\n/* ========================================================================== */\n/* === colamd_recommended =================================================== */\n/* ========================================================================== */\n\n/*\n    The colamd_recommended routine returns the suggested size for Alen.  This\n    value has been determined to provide good balance between the number of\n    garbage collections and the memory requirements for colamd.  If any\n    argument is negative, a -1 is returned as an error condition.  This\n    function is also available as a macro defined in colamd.h, so that you\n    can use it for a statically-allocated array size.\n*/\n\nPUBLIC int colamd_recommended\t/* returns recommended value of Alen. */\n(\n    /* === Parameters ======================================================= */\n\n    int nnz,\t\t\t/* number of nonzeros in A */\n    int n_row,\t\t\t/* number of rows in A */\n    int n_col\t\t\t/* number of columns in A */\n)\n{\n    return (COLAMD_RECOMMENDED (nnz, n_row, n_col)) ; \n}\n\n\n/* ========================================================================== */\n/* === colamd_set_defaults ================================================== */\n/* ========================================================================== */\n\n/*\n    The colamd_set_defaults routine sets the default values of the user-\n    controllable parameters for colamd:\n\n\tknobs [0]\trows with knobs[0]*n_col entries or more are removed\n\t\t\tprior to ordering in colamd.  Rows and columns with\n\t\t\tknobs[0]*n_col entries or more are removed prior to\n\t\t\tordering in symamd and placed last in the output\n\t\t\tordering.\n\n\tknobs [1]\tcolumns with knobs[1]*n_row entries or more are removed\n\t\t\tprior to ordering in colamd, and placed last in the\n\t\t\tcolumn permutation.  Symamd ignores this knob.\n\n\tknobs [2..19]\tunused, but future versions might use this\n*/\n\nPUBLIC void colamd_set_defaults\n(\n    /* === Parameters ======================================================= */\n\n    double knobs [COLAMD_KNOBS]\t\t/* knob array */\n)\n{\n    /* === Local variables ================================================== */\n\n    int i ;\n\n    if (!knobs)\n    {\n\treturn ;\t\t\t/* no knobs to initialize */\n    }\n    for (i = 0 ; i < COLAMD_KNOBS ; i++)\n    {\n\tknobs [i] = 0 ;\n    }\n    knobs [COLAMD_DENSE_ROW] = 0.5 ;\t/* ignore rows over 50% dense */\n    knobs [COLAMD_DENSE_COL] = 0.5 ;\t/* ignore columns over 50% dense */\n}\n\n\n/* ========================================================================== */\n/* === symamd =============================================================== */\n/* ========================================================================== */\n\nPUBLIC int symamd\t\t\t/* return TRUE if OK, FALSE otherwise */\n(\n    /* === Parameters ======================================================= */\n\n    int n,\t\t\t\t/* number of rows and columns of A */\n    int A [],\t\t\t\t/* row indices of A */\n    int p [],\t\t\t\t/* column pointers of A */\n    int perm [],\t\t\t/* output permutation, size n+1 */\n    double knobs [COLAMD_KNOBS],\t/* parameters (uses defaults if NULL) */\n    int stats [COLAMD_STATS],\t\t/* output statistics and error codes */\n    void * (*allocate) (size_t, size_t),\n    \t\t\t\t\t/* pointer to calloc (ANSI C) or */\n\t\t\t\t\t/* mxCalloc (for Matlab mexFunction) */\n    void (*release) (void *)\n    \t\t\t\t\t/* pointer to free (ANSI C) or */\n    \t\t\t\t\t/* mxFree (for Matlab mexFunction) */\n)\n{\n    /* === Local variables ================================================== */\n\n    int *count ;\t\t/* length of each column of M, and col pointer*/\n    int *mark ;\t\t\t/* mark array for finding duplicate entries */\n    int *M ;\t      /* row indices of matrix M */\n    int Mlen ;\t\t\t/* length of M */\n    int n_row ;\t\t\t/* number of rows in M */\n    int nnz ;\t\t\t/* number of entries in A */\n    int i ;\t\t\t/* row index of A */\n    int j ;\t\t\t/* column index of A */\n    int k ;\t\t\t/* row index of M */ \n    int mnz ;\t\t\t/* number of nonzeros in M */\n    int pp ;\t\t\t/* index into a column of A */\n    int last_row ;\t\t/* last row seen in the current column */\n    int length ;\t\t/* number of nonzeros in a column */\n\n    double cknobs [COLAMD_KNOBS] ;\t\t/* knobs for colamd */\n    double default_knobs [COLAMD_KNOBS] ;\t/* default knobs for colamd */\n    int cstats [COLAMD_STATS] ;\t\t\t/* colamd stats */\n\n#ifndef NDEBUG\n    colamd_get_debug (\"symamd\") ;\n#endif /* NDEBUG */\n\n    /* === Check the input arguments ======================================== */\n\n    if (!stats)\n    {\n\tDEBUG0 ((\"symamd: stats not present\\n\")) ;\n\treturn (FALSE) ;\n    }\n    for (i = 0 ; i < COLAMD_STATS ; i++)\n    {\n\tstats [i] = 0 ;\n    }\n    stats [COLAMD_STATUS] = COLAMD_OK ;\n    stats [COLAMD_INFO1] = -1 ;\n    stats [COLAMD_INFO2] = -1 ;\n\n    if (!A)\n    {\n    \tstats [COLAMD_STATUS] = COLAMD_ERROR_A_not_present ;\n\tDEBUG0 ((\"symamd: A not present\\n\")) ;\n\treturn (FALSE) ;\n    }\n\n    if (!p)\t\t/* p is not present */\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_p_not_present ;\n\tDEBUG0 ((\"symamd: p not present\\n\")) ;\n    \treturn (FALSE) ;\n    }\n\n    if (n < 0)\t\t/* n must be >= 0 */\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_ncol_negative ;\n\tstats [COLAMD_INFO1] = n ;\n\tDEBUG0 ((\"symamd: n negative %d\\n\", n)) ;\n    \treturn (FALSE) ;\n    }\n\n    nnz = p [n] ;\n    if (nnz < 0)\t/* nnz must be >= 0 */\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_nnz_negative ;\n\tstats [COLAMD_INFO1] = nnz ;\n\tDEBUG0 ((\"symamd: number of entries negative %d\\n\", nnz)) ;\n\treturn (FALSE) ;\n    }\n\n    if (p [0] != 0)\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_p0_nonzero ;\n\tstats [COLAMD_INFO1] = p [0] ;\n\tDEBUG0 ((\"symamd: p[0] not zero %d\\n\", p [0])) ;\n\treturn (FALSE) ;\n    }\n\n    /* === If no knobs, set default knobs =================================== */\n\n    if (!knobs)\n    {\n\tcolamd_set_defaults (default_knobs) ;\n\tknobs = default_knobs ;\n    }\n\n    /* === Allocate count and mark ========================================== */\n\n    count = (int *) ((*allocate) (n+1, sizeof (int))) ;\n    if (!count)\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_out_of_memory ;\n\tDEBUG0 ((\"symamd: allocate count (size %d) failed\\n\", n+1)) ;\n\treturn (FALSE) ;\n    }\n\n    mark = (int *) ((*allocate) (n+1, sizeof (int))) ;\n    if (!mark)\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_out_of_memory ;\n\t(*release) ((void *) count) ;\n\tDEBUG0 ((\"symamd: allocate mark (size %d) failed\\n\", n+1)) ;\n\treturn (FALSE) ;\n    }\n\n    /* === Compute column counts of M, check if A is valid ================== */\n\n    stats [COLAMD_INFO3] = 0 ;  /* number of duplicate or unsorted row indices*/\n\n    for (i = 0 ; i < n ; i++)\n    {\n    \tmark [i] = -1 ;\n    }\n\n    for (j = 0 ; j < n ; j++)\n    {\n\tlast_row = -1 ;\n\n\tlength = p [j+1] - p [j] ;\n\tif (length < 0)\n\t{\n\t    /* column pointers must be non-decreasing */\n\t    stats [COLAMD_STATUS] = COLAMD_ERROR_col_length_negative ;\n\t    stats [COLAMD_INFO1] = j ;\n\t    stats [COLAMD_INFO2] = length ;\n\t    (*release) ((void *) count) ;\n\t    (*release) ((void *) mark) ;\n\t    DEBUG0 ((\"symamd: col %d negative length %d\\n\", j, length)) ;\n\t    return (FALSE) ;\n\t}\n\n\tfor (pp = p [j] ; pp < p [j+1] ; pp++)\n\t{\n\t    i = A [pp] ;\n\t    if (i < 0 || i >= n)\n\t    {\n\t\t/* row index i, in column j, is out of bounds */\n\t\tstats [COLAMD_STATUS] = COLAMD_ERROR_row_index_out_of_bounds ;\n\t\tstats [COLAMD_INFO1] = j ;\n\t\tstats [COLAMD_INFO2] = i ;\n\t\tstats [COLAMD_INFO3] = n ;\n\t\t(*release) ((void *) count) ;\n\t\t(*release) ((void *) mark) ;\n\t\tDEBUG0 ((\"symamd: row %d col %d out of bounds\\n\", i, j)) ;\n\t\treturn (FALSE) ;\n\t    }\n\n\t    if (i <= last_row || mark [i] == j)\n\t    {\n\t\t/* row index is unsorted or repeated (or both), thus col */\n\t\t/* is jumbled.  This is a notice, not an error condition. */\n\t\tstats [COLAMD_STATUS] = COLAMD_OK_BUT_JUMBLED ;\n\t\tstats [COLAMD_INFO1] = j ;\n\t\tstats [COLAMD_INFO2] = i ;\n\t\t(stats [COLAMD_INFO3]) ++ ;\n\t\tDEBUG1 ((\"symamd: row %d col %d unsorted/duplicate\\n\", i, j)) ;\n\t    }\n\n\t    if (i > j && mark [i] != j)\n\t    {\n\t\t/* row k of M will contain column indices i and j */\n\t\tcount [i]++ ;\n\t\tcount [j]++ ;\n\t    }\n\n\t    /* mark the row as having been seen in this column */\n\t    mark [i] = j ;\n\n\t    last_row = i ;\n\t}\n    }\n\n    if (stats [COLAMD_STATUS] == COLAMD_OK)\n    {\n\t/* if there are no duplicate entries, then mark is no longer needed */\n\t(*release) ((void *) mark) ;\n    }\n\n    /* === Compute column pointers of M ===================================== */\n\n    /* use output permutation, perm, for column pointers of M */\n    perm [0] = 0 ;\n    for (j = 1 ; j <= n ; j++)\n    {\n\tperm [j] = perm [j-1] + count [j-1] ;\n    }\n    for (j = 0 ; j < n ; j++)\n    {\n\tcount [j] = perm [j] ;\n    }\n\n    /* === Construct M ====================================================== */\n\n    mnz = perm [n] ;\n    n_row = mnz / 2 ;\n    Mlen = colamd_recommended (mnz, n_row, n) ;\n    M = (int *) ((*allocate) (Mlen, sizeof (int))) ;\n    DEBUG0 ((\"symamd: M is %d-by-%d with %d entries, Mlen = %d\\n\",\n    \tn_row, n, mnz, Mlen)) ;\n\n    if (!M)\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_out_of_memory ;\n\t(*release) ((void *) count) ;\n\t(*release) ((void *) mark) ;\n\tDEBUG0 ((\"symamd: allocate M (size %d) failed\\n\", Mlen)) ;\n\treturn (FALSE) ;\n    }\n\n    k = 0 ;\n\n    if (stats [COLAMD_STATUS] == COLAMD_OK)\n    {\n\t/* Matrix is OK */\n\tfor (j = 0 ; j < n ; j++)\n\t{\n\t    ASSERT (p [j+1] - p [j] >= 0) ;\n\t    for (pp = p [j] ; pp < p [j+1] ; pp++)\n\t    {\n\t\ti = A [pp] ;\n\t\tASSERT (i >= 0 && i < n) ;\n\t\tif (i > j)\n\t\t{\n\t\t    /* row k of M contains column indices i and j */\n\t\t    M [count [i]++] = k ;\n\t\t    M [count [j]++] = k ;\n\t\t    k++ ;\n\t\t}\n\t    }\n\t}\n    }\n    else\n    {\n\t/* Matrix is jumbled.  Do not add duplicates to M.  Unsorted cols OK. */\n\tDEBUG0 ((\"symamd: Duplicates in A.\\n\")) ;\n\tfor (i = 0 ; i < n ; i++)\n\t{\n\t    mark [i] = -1 ;\n\t}\n\tfor (j = 0 ; j < n ; j++)\n\t{\n\t    ASSERT (p [j+1] - p [j] >= 0) ;\n\t    for (pp = p [j] ; pp < p [j+1] ; pp++)\n\t    {\n\t\ti = A [pp] ;\n\t\tASSERT (i >= 0 && i < n) ;\n\t\tif (i > j && mark [i] != j)\n\t\t{\n\t\t    /* row k of M contains column indices i and j */\n\t\t    M [count [i]++] = k ;\n\t\t    M [count [j]++] = k ;\n\t\t    k++ ;\n\t\t    mark [i] = j ;\n\t\t}\n\t    }\n\t}\n\t(*release) ((void *) mark) ;\n    }\n\n    /* count and mark no longer needed */\n    (*release) ((void *) count) ;\n    ASSERT (k == n_row) ;\n\n    /* === Adjust the knobs for M =========================================== */\n\n    for (i = 0 ; i < COLAMD_KNOBS ; i++)\n    {\n\tcknobs [i] = knobs [i] ;\n    }\n\n    /* there are no dense rows in M */\n    cknobs [COLAMD_DENSE_ROW] = 1.0 ;\n\n    if (n_row != 0 && n < n_row)\n    {\n\t/* On input, the knob is a fraction of 1..n, the number of rows of A. */\n\t/* Convert it to a fraction of 1..n_row, of the number of rows of M. */\n    \tcknobs [COLAMD_DENSE_COL] = (knobs [COLAMD_DENSE_ROW] * n) / n_row ;\n    }\n    else\n    {\n\t/* no dense columns in M */\n    \tcknobs [COLAMD_DENSE_COL] = 1.0 ;\n    }\n\n    DEBUG0 ((\"symamd: dense col knob for M: %g\\n\", cknobs [COLAMD_DENSE_COL])) ;\n\n    /* === Order the columns of M =========================================== */\n\n    if (!colamd (n_row, n, Mlen, M, perm, cknobs, cstats))\n    {\n\t/* This \"cannot\" happen, unless there is a bug in the code. */\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_internal_error ;\n\t(*release) ((void *) M) ;\n\tDEBUG0 ((\"symamd: internal error!\\n\")) ;\n\treturn (FALSE) ;\n    }\n\n    /* Note that the output permutation is now in perm */\n\n    /* === get the statistics for symamd from colamd ======================== */\n\n    /* note that a dense column in colamd means a dense row and col in symamd */\n    stats [COLAMD_DENSE_ROW]    = cstats [COLAMD_DENSE_COL] ;\n    stats [COLAMD_DENSE_COL]    = cstats [COLAMD_DENSE_COL] ;\n    stats [COLAMD_DEFRAG_COUNT] = cstats [COLAMD_DEFRAG_COUNT] ;\n\n    /* === Free M =========================================================== */\n\n    (*release) ((void *) M) ;\n    DEBUG0 ((\"symamd: done.\\n\")) ;\n    return (TRUE) ;\n\n}\n\n/* ========================================================================== */\n/* === colamd =============================================================== */\n/* ========================================================================== */\n\n/*\n    The colamd routine computes a column ordering Q of a sparse matrix\n    A such that the LU factorization P(AQ) = LU remains sparse, where P is\n    selected via partial pivoting.   The routine can also be viewed as\n    providing a permutation Q such that the Cholesky factorization\n    (AQ)'(AQ) = LL' remains sparse.\n*/\n\nPUBLIC int colamd\t\t/* returns TRUE if successful, FALSE otherwise*/\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\t\t\t/* number of rows in A */\n    int n_col,\t\t\t/* number of columns in A */\n    int Alen,\t\t\t/* length of A */\n    int A [],\t\t\t/* row indices of A */\n    int p [],\t\t\t/* pointers to columns in A */\n    double knobs [COLAMD_KNOBS],/* parameters (uses defaults if NULL) */\n    int stats [COLAMD_STATS]\t/* output statistics and error codes */\n)\n{\n    /* === Local variables ================================================== */\n\n    int i ;\t\t\t/* loop index */\n    int nnz ;\t\t\t/* nonzeros in A */\n    int Row_size ;\t\t/* size of Row [], in integers */\n    int Col_size ;\t\t/* size of Col [], in integers */\n    int need ;\t\t\t/* minimum required length of A */\n    Colamd_Row *Row ;\t\t/* pointer into A of Row [0..n_row] array */\n    Colamd_Col *Col ;\t\t/* pointer into A of Col [0..n_col] array */\n    int n_col2 ;\t\t/* number of non-dense, non-empty columns */\n    int n_row2 ;\t\t/* number of non-dense, non-empty rows */\n    int ngarbage ;\t\t/* number of garbage collections performed */\n    int max_deg ;\t\t/* maximum row degree */\n    double default_knobs [COLAMD_KNOBS] ;\t/* default knobs array */\n\n#ifndef NDEBUG\n    colamd_get_debug (\"colamd\") ;\n#endif /* NDEBUG */\n\n    /* === Check the input arguments ======================================== */\n\n    if (!stats)\n    {\n\tDEBUG0 ((\"colamd: stats not present\\n\")) ;\n\treturn (FALSE) ;\n    }\n    for (i = 0 ; i < COLAMD_STATS ; i++)\n    {\n\tstats [i] = 0 ;\n    }\n    stats [COLAMD_STATUS] = COLAMD_OK ;\n    stats [COLAMD_INFO1] = -1 ;\n    stats [COLAMD_INFO2] = -1 ;\n\n    if (!A)\t\t/* A is not present */\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_A_not_present ;\n\tDEBUG0 ((\"colamd: A not present\\n\")) ;\n\treturn (FALSE) ;\n    }\n\n    if (!p)\t\t/* p is not present */\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_p_not_present ;\n\tDEBUG0 ((\"colamd: p not present\\n\")) ;\n    \treturn (FALSE) ;\n    }\n\n    if (n_row < 0)\t/* n_row must be >= 0 */\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_nrow_negative ;\n\tstats [COLAMD_INFO1] = n_row ;\n\tDEBUG0 ((\"colamd: nrow negative %d\\n\", n_row)) ;\n    \treturn (FALSE) ;\n    }\n\n    if (n_col < 0)\t/* n_col must be >= 0 */\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_ncol_negative ;\n\tstats [COLAMD_INFO1] = n_col ;\n\tDEBUG0 ((\"colamd: ncol negative %d\\n\", n_col)) ;\n    \treturn (FALSE) ;\n    }\n\n    nnz = p [n_col] ;\n    if (nnz < 0)\t/* nnz must be >= 0 */\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_nnz_negative ;\n\tstats [COLAMD_INFO1] = nnz ;\n\tDEBUG0 ((\"colamd: number of entries negative %d\\n\", nnz)) ;\n\treturn (FALSE) ;\n    }\n\n    if (p [0] != 0)\n    {\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_p0_nonzero\t;\n\tstats [COLAMD_INFO1] = p [0] ;\n\tDEBUG0 ((\"colamd: p[0] not zero %d\\n\", p [0])) ;\n\treturn (FALSE) ;\n    }\n\n    /* === If no knobs, set default knobs =================================== */\n\n    if (!knobs)\n    {\n\tcolamd_set_defaults (default_knobs) ;\n\tknobs = default_knobs ;\n    }\n\n    /* === Allocate the Row and Col arrays from array A ===================== */\n\n    Col_size = COLAMD_C (n_col) ;\n    Row_size = COLAMD_R (n_row) ;\n    need = 2*nnz + n_col + Col_size + Row_size ;\n\n    if (need > Alen)\n    {\n\t/* not enough space in array A to perform the ordering */\n\tstats [COLAMD_STATUS] = COLAMD_ERROR_A_too_small ;\n\tstats [COLAMD_INFO1] = need ;\n\tstats [COLAMD_INFO2] = Alen ;\n\tDEBUG0 ((\"colamd: Need Alen >= %d, given only Alen = %d\\n\", need,Alen));\n\treturn (FALSE) ;\n    }\n\n    Alen -= Col_size + Row_size ;\n    Col = (Colamd_Col *) &A [Alen] ;\n    Row = (Colamd_Row *) &A [Alen + Col_size] ;\n\n    /* === Construct the row and column data structures ===================== */\n\n    if (!init_rows_cols (n_row, n_col, Row, Col, A, p, stats))\n    {\n\t/* input matrix is invalid */\n\tDEBUG0 ((\"colamd: Matrix invalid\\n\")) ;\n\treturn (FALSE) ;\n    }\n\n    /* === Initialize scores, kill dense rows/columns ======================= */\n\n    init_scoring (n_row, n_col, Row, Col, A, p, knobs,\n\t&n_row2, &n_col2, &max_deg) ;\n\n    /* === Order the supercolumns =========================================== */\n\n    ngarbage = find_ordering (n_row, n_col, Alen, Row, Col, A, p,\n\tn_col2, max_deg, 2*nnz) ;\n\n    /* === Order the non-principal columns ================================== */\n\n    order_children (n_col, Col, p) ;\n\n    /* === Return statistics in stats ======================================= */\n\n    stats [COLAMD_DENSE_ROW] = n_row - n_row2 ;\n    stats [COLAMD_DENSE_COL] = n_col - n_col2 ;\n    stats [COLAMD_DEFRAG_COUNT] = ngarbage ;\n    DEBUG0 ((\"colamd: done.\\n\")) ; \n    return (TRUE) ;\n}\n\n\n/* ========================================================================== */\n/* === colamd_report ======================================================== */\n/* ========================================================================== */\n\nPUBLIC void colamd_report\n(\n    int stats [COLAMD_STATS]\n)\n{\n    print_report (\"colamd\", stats) ;\n}\n\n\n/* ========================================================================== */\n/* === symamd_report ======================================================== */\n/* ========================================================================== */\n\nPUBLIC void symamd_report\n(\n    int stats [COLAMD_STATS]\n)\n{\n    print_report (\"symamd\", stats) ;\n}\n\n\n\n/* ========================================================================== */\n/* === NON-USER-CALLABLE ROUTINES: ========================================== */\n/* ========================================================================== */\n\n/* There are no user-callable routines beyond this point in the file */\n\n\n/* ========================================================================== */\n/* === init_rows_cols ======================================================= */\n/* ========================================================================== */\n\n/*\n    Takes the column form of the matrix in A and creates the row form of the\n    matrix.  Also, row and column attributes are stored in the Col and Row\n    structs.  If the columns are un-sorted or contain duplicate row indices,\n    this routine will also sort and remove duplicate row indices from the\n    column form of the matrix.  Returns FALSE if the matrix is invalid,\n    TRUE otherwise.  Not user-callable.\n*/\n\nPRIVATE int init_rows_cols\t/* returns TRUE if OK, or FALSE otherwise */\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\t\t\t/* number of rows of A */\n    int n_col,\t\t\t/* number of columns of A */\n    Colamd_Row Row [],\t\t/* of size n_row+1 */\n    Colamd_Col Col [],\t\t/* of size n_col+1 */\n    int A [],\t\t\t/* row indices of A, of size Alen */\n    int p [],\t\t\t/* pointers to columns in A, of size n_col+1 */\n    int stats [COLAMD_STATS]\t/* colamd statistics */ \n)\n{\n    /* === Local variables ================================================== */\n\n    int col ;\t\t\t/* a column index */\n    int row ;\t\t\t/* a row index */\n    int *cp ;\t\t\t/* a column pointer */\n    int *cp_end ;\t\t/* a pointer to the end of a column */\n    int *rp ;\t\t\t/* a row pointer */\n    int *rp_end ;\t\t/* a pointer to the end of a row */\n    int last_row ;\t\t/* previous row */\n\n    /* === Initialize columns, and check column pointers ==================== */\n\n    for (col = 0 ; col < n_col ; col++)\n    {\n\tCol [col].start = p [col] ;\n\tCol [col].length = p [col+1] - p [col] ;\n\n\tif (Col [col].length < 0)\n\t{\n\t    /* column pointers must be non-decreasing */\n\t    stats [COLAMD_STATUS] = COLAMD_ERROR_col_length_negative ;\n\t    stats [COLAMD_INFO1] = col ;\n\t    stats [COLAMD_INFO2] = Col [col].length ;\n\t    DEBUG0 ((\"colamd: col %d length %d < 0\\n\", col, Col [col].length)) ;\n\t    return (FALSE) ;\n\t}\n\n\tCol [col].shared1.thickness = 1 ;\n\tCol [col].shared2.score = 0 ;\n\tCol [col].shared3.prev = EMPTY ;\n\tCol [col].shared4.degree_next = EMPTY ;\n    }\n\n    /* p [0..n_col] no longer needed, used as \"head\" in subsequent routines */\n\n    /* === Scan columns, compute row degrees, and check row indices ========= */\n\n    stats [COLAMD_INFO3] = 0 ;\t/* number of duplicate or unsorted row indices*/\n\n    for (row = 0 ; row < n_row ; row++)\n    {\n\tRow [row].length = 0 ;\n\tRow [row].shared2.mark = -1 ;\n    }\n\n    for (col = 0 ; col < n_col ; col++)\n    {\n\tlast_row = -1 ;\n\n\tcp = &A [p [col]] ;\n\tcp_end = &A [p [col+1]] ;\n\n\twhile (cp < cp_end)\n\t{\n\t    row = *cp++ ;\n\n\t    /* make sure row indices within range */\n\t    if (row < 0 || row >= n_row)\n\t    {\n\t\tstats [COLAMD_STATUS] = COLAMD_ERROR_row_index_out_of_bounds ;\n\t\tstats [COLAMD_INFO1] = col ;\n\t\tstats [COLAMD_INFO2] = row ;\n\t\tstats [COLAMD_INFO3] = n_row ;\n\t\tDEBUG0 ((\"colamd: row %d col %d out of bounds\\n\", row, col)) ;\n\t\treturn (FALSE) ;\n\t    }\n\n\t    if (row <= last_row || Row [row].shared2.mark == col)\n\t    {\n\t\t/* row index are unsorted or repeated (or both), thus col */\n\t\t/* is jumbled.  This is a notice, not an error condition. */\n\t\tstats [COLAMD_STATUS] = COLAMD_OK_BUT_JUMBLED ;\n\t\tstats [COLAMD_INFO1] = col ;\n\t\tstats [COLAMD_INFO2] = row ;\n\t\t(stats [COLAMD_INFO3]) ++ ;\n\t\tDEBUG1 ((\"colamd: row %d col %d unsorted/duplicate\\n\",row,col));\n\t    }\n\n\t    if (Row [row].shared2.mark != col)\n\t    {\n\t\tRow [row].length++ ;\n\t    }\n\t    else\n\t    {\n\t\t/* this is a repeated entry in the column, */\n\t\t/* it will be removed */\n\t\tCol [col].length-- ;\n\t    }\n\n\t    /* mark the row as having been seen in this column */\n\t    Row [row].shared2.mark = col ;\n\n\t    last_row = row ;\n\t}\n    }\n\n    /* === Compute row pointers ============================================= */\n\n    /* row form of the matrix starts directly after the column */\n    /* form of matrix in A */\n    Row [0].start = p [n_col] ;\n    Row [0].shared1.p = Row [0].start ;\n    Row [0].shared2.mark = -1 ;\n    for (row = 1 ; row < n_row ; row++)\n    {\n\tRow [row].start = Row [row-1].start + Row [row-1].length ;\n\tRow [row].shared1.p = Row [row].start ;\n\tRow [row].shared2.mark = -1 ;\n    }\n\n    /* === Create row form ================================================== */\n\n    if (stats [COLAMD_STATUS] == COLAMD_OK_BUT_JUMBLED)\n    {\n\t/* if cols jumbled, watch for repeated row indices */\n\tfor (col = 0 ; col < n_col ; col++)\n\t{\n\t    cp = &A [p [col]] ;\n\t    cp_end = &A [p [col+1]] ;\n\t    while (cp < cp_end)\n\t    {\n\t\trow = *cp++ ;\n\t\tif (Row [row].shared2.mark != col)\n\t\t{\n\t\t    A [(Row [row].shared1.p)++] = col ;\n\t\t    Row [row].shared2.mark = col ;\n\t\t}\n\t    }\n\t}\n    }\n    else\n    {\n\t/* if cols not jumbled, we don't need the mark (this is faster) */\n\tfor (col = 0 ; col < n_col ; col++)\n\t{\n\t    cp = &A [p [col]] ;\n\t    cp_end = &A [p [col+1]] ;\n\t    while (cp < cp_end)\n\t    {\n\t\tA [(Row [*cp++].shared1.p)++] = col ;\n\t    }\n\t}\n    }\n\n    /* === Clear the row marks and set row degrees ========================== */\n\n    for (row = 0 ; row < n_row ; row++)\n    {\n\tRow [row].shared2.mark = 0 ;\n\tRow [row].shared1.degree = Row [row].length ;\n    }\n\n    /* === See if we need to re-create columns ============================== */\n\n    if (stats [COLAMD_STATUS] == COLAMD_OK_BUT_JUMBLED)\n    {\n    \tDEBUG0 ((\"colamd: reconstructing column form, matrix jumbled\\n\")) ;\n\n#ifndef NDEBUG\n\t/* make sure column lengths are correct */\n\tfor (col = 0 ; col < n_col ; col++)\n\t{\n\t    p [col] = Col [col].length ;\n\t}\n\tfor (row = 0 ; row < n_row ; row++)\n\t{\n\t    rp = &A [Row [row].start] ;\n\t    rp_end = rp + Row [row].length ;\n\t    while (rp < rp_end)\n\t    {\n\t\tp [*rp++]-- ;\n\t    }\n\t}\n\tfor (col = 0 ; col < n_col ; col++)\n\t{\n\t    ASSERT (p [col] == 0) ;\n\t}\n\t/* now p is all zero (different than when debugging is turned off) */\n#endif /* NDEBUG */\n\n\t/* === Compute col pointers ========================================= */\n\n\t/* col form of the matrix starts at A [0]. */\n\t/* Note, we may have a gap between the col form and the row */\n\t/* form if there were duplicate entries, if so, it will be */\n\t/* removed upon the first garbage collection */\n\tCol [0].start = 0 ;\n\tp [0] = Col [0].start ;\n\tfor (col = 1 ; col < n_col ; col++)\n\t{\n\t    /* note that the lengths here are for pruned columns, i.e. */\n\t    /* no duplicate row indices will exist for these columns */\n\t    Col [col].start = Col [col-1].start + Col [col-1].length ;\n\t    p [col] = Col [col].start ;\n\t}\n\n\t/* === Re-create col form =========================================== */\n\n\tfor (row = 0 ; row < n_row ; row++)\n\t{\n\t    rp = &A [Row [row].start] ;\n\t    rp_end = rp + Row [row].length ;\n\t    while (rp < rp_end)\n\t    {\n\t\tA [(p [*rp++])++] = row ;\n\t    }\n\t}\n    }\n\n    /* === Done.  Matrix is not (or no longer) jumbled ====================== */\n\n    return (TRUE) ;\n}\n\n\n/* ========================================================================== */\n/* === init_scoring ========================================================= */\n/* ========================================================================== */\n\n/*\n    Kills dense or empty columns and rows, calculates an initial score for\n    each column, and places all columns in the degree lists.  Not user-callable.\n*/\n\nPRIVATE void init_scoring\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\t\t\t/* number of rows of A */\n    int n_col,\t\t\t/* number of columns of A */\n    Colamd_Row Row [],\t\t/* of size n_row+1 */\n    Colamd_Col Col [],\t\t/* of size n_col+1 */\n    int A [],\t\t\t/* column form and row form of A */\n    int head [],\t\t/* of size n_col+1 */\n    double knobs [COLAMD_KNOBS],/* parameters */\n    int *p_n_row2,\t\t/* number of non-dense, non-empty rows */\n    int *p_n_col2,\t\t/* number of non-dense, non-empty columns */\n    int *p_max_deg\t\t/* maximum row degree */\n)\n{\n    /* === Local variables ================================================== */\n\n    int c ;         /* a column index */\n    int r, row ;\t\t/* a row index */\n    int *cp ;\t\t    /* a column pointer */\n    int deg ;\t      /* degree of a row or column */\n    int *cp_end ;\t  /* a pointer to the end of a column */\n    int *new_cp ;\t  /* new column pointer */\n    int col_length ;\t\t/* length of pruned column */\n    int score ;\t    /* current column score */\n    int n_col2 ;    /* number of non-dense, non-empty columns */\n    int n_row2 ;    /* number of non-dense, non-empty rows */\n    int dense_row_count ;\t/* remove rows with more entries than this */\n    int dense_col_count ;\t/* remove cols with more entries than this */\n    int min_score ; /* smallest column score */\n    int max_deg ;\t  /* maximum row degree */\n    int next_col ;  /* Used to add to degree list.*/\n\n#ifndef NDEBUG\n    int debug_count ;\t\t/* debug only. */\n#endif /* NDEBUG */\n\n    /* === Extract knobs ==================================================== */\n\n    dense_row_count = (int) MAX (0, MIN (knobs [COLAMD_DENSE_ROW] * n_col, n_col)) ;\n    dense_col_count = (int) MAX (0, MIN (knobs [COLAMD_DENSE_COL] * n_row, n_row)) ;\n    DEBUG1 ((\"colamd: densecount: %d %d\\n\", dense_row_count, dense_col_count)) ;\n    max_deg = 0 ;\n    n_col2 = n_col ;\n    n_row2 = n_row ;\n\n    /* === Kill empty columns =============================================== */\n\n    /* Put the empty columns at the end in their natural order, so that LU */\n    /* factorization can proceed as far as possible. */\n    for (c = n_col-1 ; c >= 0 ; c--)\n    {\n\tdeg = Col [c].length ;\n\tif (deg == 0)\n\t{\n\t    /* this is a empty column, kill and order it last */\n\t    Col [c].shared2.order = --n_col2 ;\n\t    KILL_PRINCIPAL_COL (c) ;\n\t}\n    }\n    DEBUG1 ((\"colamd: null columns killed: %d\\n\", n_col - n_col2)) ;\n\n    /* === Kill dense columns =============================================== */\n\n    /* Put the dense columns at the end, in their natural order */\n    for (c = n_col-1 ; c >= 0 ; c--)\n    {\n\t/* skip any dead columns */\n\tif (COL_IS_DEAD (c))\n\t{\n\t    continue ;\n\t}\n\tdeg = Col [c].length ;\n\tif (deg > dense_col_count)\n\t{\n\t    /* this is a dense column, kill and order it last */\n\t    Col [c].shared2.order = --n_col2 ;\n\t    /* decrement the row degrees */\n\t    cp = &A [Col [c].start] ;\n\t    cp_end = cp + Col [c].length ;\n\t    while (cp < cp_end)\n\t    {\n\t\tRow [*cp++].shared1.degree-- ;\n\t    }\n\t    KILL_PRINCIPAL_COL (c) ;\n\t}\n    }\n    DEBUG1 ((\"colamd: Dense and null columns killed: %d\\n\", n_col - n_col2)) ;\n\n    /* === Kill dense and empty rows ======================================== */\n\n    for (r = 0 ; r < n_row ; r++)\n    {\n\tdeg = Row [r].shared1.degree ;\n\tASSERT (deg >= 0 && deg <= n_col) ;\n\tif (deg > dense_row_count || deg == 0)\n\t{\n\t    /* kill a dense or empty row */\n\t    KILL_ROW (r) ;\n\t    --n_row2 ;\n\t}\n\telse\n\t{\n\t    /* keep track of max degree of remaining rows */\n\t    max_deg = MAX (max_deg, deg) ;\n\t}\n    }\n    DEBUG1 ((\"colamd: Dense and null rows killed: %d\\n\", n_row - n_row2)) ;\n\n    /* === Compute initial column scores ==================================== */\n\n    /* At this point the row degrees are accurate.  They reflect the number */\n    /* of \"live\" (non-dense) columns in each row.  No empty rows exist. */\n    /* Some \"live\" columns may contain only dead rows, however.  These are */\n    /* pruned in the code below. */\n\n    /* now find the initial matlab score for each column */\n    for (c = n_col-1 ; c >= 0 ; c--)\n    {\n\t/* skip dead column */\n\tif (COL_IS_DEAD (c))\n\t{\n\t    continue ;\n\t}\n\tscore = 0 ;\n\tcp = &A [Col [c].start] ;\n\tnew_cp = cp ;\n\tcp_end = cp + Col [c].length ;\n\twhile (cp < cp_end)\n\t{\n\t    /* get a row */\n\t    row = *cp++ ;\n\t    /* skip if dead */\n\t    if (ROW_IS_DEAD (row))\n\t    {\n\t\tcontinue ;\n\t    }\n\t    /* compact the column */\n\t    *new_cp++ = row ;\n\t    /* add row's external degree */\n\t    score += Row [row].shared1.degree - 1 ;\n\t    /* guard against integer overflow */\n\t    score = MIN (score, n_col) ;\n\t}\n\t/* determine pruned column length */\n\tcol_length = (int) (new_cp - &A [Col [c].start]) ;\n\tif (col_length == 0)\n\t{\n\t    /* a newly-made null column (all rows in this col are \"dense\" */\n\t    /* and have already been killed) */\n\t    DEBUG2 ((\"Newly null killed: %d\\n\", c)) ;\n\t    Col [c].shared2.order = --n_col2 ;\n\t    KILL_PRINCIPAL_COL (c) ;\n\t}\n\telse\n\t{\n\t    /* set column length and set score */\n\t    ASSERT (score >= 0) ;\n\t    ASSERT (score <= n_col) ;\n\t    Col [c].length = col_length ;\n\t    Col [c].shared2.score = score ;\n\t}\n    }\n    DEBUG1 ((\"colamd: Dense, null, and newly-null columns killed: %d\\n\",\n    \tn_col-n_col2)) ;\n\n    /* At this point, all empty rows and columns are dead.  All live columns */\n    /* are \"clean\" (containing no dead rows) and simplicial (no supercolumns */\n    /* yet).  Rows may contain dead columns, but all live rows contain at */\n    /* least one live column. */\n\n#ifndef NDEBUG\n    debug_structures (n_row, n_col, Row, Col, A, n_col2) ;\n#endif /* NDEBUG */\n\n    /* === Initialize degree lists ========================================== */\n\n#ifndef NDEBUG\n    debug_count = 0 ;\n#endif /* NDEBUG */\n\n    /* clear the hash buckets */\n    for (c = 0 ; c <= n_col ; c++)\n    {\n\thead [c] = EMPTY ;\n    }\n    min_score = n_col ;\n    /* place in reverse order, so low column indices are at the front */\n    /* of the lists.  This is to encourage natural tie-breaking */\n    for (c = n_col-1 ; c >= 0 ; c--)\n    {\n\t/* only add principal columns to degree lists */\n\tif (COL_IS_ALIVE (c))\n\t{\n\t    DEBUG4 ((\"place %d score %d minscore %d ncol %d\\n\",\n\t\tc, Col [c].shared2.score, min_score, n_col)) ;\n\n\t    /* === Add columns score to DList =============================== */\n\n\t    score = Col [c].shared2.score ;\n\n\t    ASSERT (min_score >= 0) ;\n\t    ASSERT (min_score <= n_col) ;\n\t    ASSERT (score >= 0) ;\n\t    ASSERT (score <= n_col) ;\n\t    ASSERT (head [score] >= EMPTY) ;\n\n\t    /* now add this column to dList at proper score location */\n\t    next_col = head [score] ;\n\t    Col [c].shared3.prev = EMPTY ;\n\t    Col [c].shared4.degree_next = next_col ;\n\n\t    /* if there already was a column with the same score, set its */\n\t    /* previous pointer to this new column */\n\t    if (next_col != EMPTY)\n\t    {\n\t\tCol [next_col].shared3.prev = c ;\n\t    }\n\t    head [score] = c ;\n\n\t    /* see if this score is less than current min */\n\t    min_score = MIN (min_score, score) ;\n\n#ifndef NDEBUG\n\t    debug_count++ ;\n#endif /* NDEBUG */\n\n\t}\n    }\n\n#ifndef NDEBUG\n    DEBUG1 ((\"colamd: Live cols %d out of %d, non-princ: %d\\n\",\n\tdebug_count, n_col, n_col-debug_count)) ;\n    ASSERT (debug_count == n_col2) ;\n    debug_deg_lists (n_row, n_col, Row, Col, head, min_score, n_col2, max_deg) ;\n#endif /* NDEBUG */\n\n    /* === Return number of remaining columns, and max row degree =========== */\n\n    *p_n_col2 = n_col2 ;\n    *p_n_row2 = n_row2 ;\n    *p_max_deg = max_deg ;\n}\n\n\n/* ========================================================================== */\n/* === find_ordering ======================================================== */\n/* ========================================================================== */\n\n/*\n    Order the principal columns of the supercolumn form of the matrix\n    (no supercolumns on input).  Uses a minimum approximate column minimum\n    degree ordering method.  Not user-callable.\n*/\n\nPRIVATE int find_ordering\t/* return the number of garbage collections */\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\t\t\t/* number of rows of A */\n    int n_col,\t\t\t/* number of columns of A */\n    int Alen,\t\t\t/* size of A, 2*nnz + n_col or larger */\n    Colamd_Row Row [],\t\t/* of size n_row+1 */\n    Colamd_Col Col [],\t\t/* of size n_col+1 */\n    int A [],\t\t\t/* column form and row form of A */\n    int head [],\t\t/* of size n_col+1 */\n    int n_col2,\t\t\t/* Remaining columns to order */\n    int max_deg,\t\t/* Maximum row degree */\n    int pfree\t\t\t/* index of first free slot (2*nnz on entry) */\n)\n{\n    /* === Local variables ================================================== */\n\n    int k ;\t\t\t/* current pivot ordering step */\n    int pivot_col ;\t\t/* current pivot column */\n    int *cp ;\t\t\t/* a column pointer */\n    int *rp ;\t\t\t/* a row pointer */\n    int pivot_row ;\t\t/* current pivot row */\n    int *new_cp ;\t\t/* modified column pointer */\n    int *new_rp ;\t\t/* modified row pointer */\n    int pivot_row_start ;\t/* pointer to start of pivot row */\n    int pivot_row_degree ;\t/* number of columns in pivot row */\n    int pivot_row_length ;\t/* number of supercolumns in pivot row */\n    int pivot_col_score ;\t/* score of pivot column */\n    int needed_memory ;\t\t/* free space needed for pivot row */\n    int *cp_end ;\t\t/* pointer to the end of a column */\n    int *rp_end ;\t\t/* pointer to the end of a row */\n    int row ;\t\t\t/* a row index */\n    int col ;\t\t\t/* a column index */\n    int max_score ;\t\t/* maximum possible score */\n    int cur_score ;\t\t/* score of current column */\n    unsigned int hash ;\t\t/* hash value for supernode detection */\n    int head_column ;\t\t/* head of hash bucket */\n    int first_col ;\t\t/* first column in hash bucket */\n    int tag_mark ;\t\t/* marker value for mark array */\n    int row_mark ;\t\t/* Row [row].shared2.mark */\n    int set_difference ;\t/* set difference size of row with pivot row */\n    int min_score ;\t\t/* smallest column score */\n    int col_thickness ;\t\t/* \"thickness\" (no. of columns in a supercol) */\n    int max_mark ;\t\t/* maximum value of tag_mark */\n    int pivot_col_thickness ;\t/* number of columns represented by pivot col */\n    int prev_col ;\t\t/* Used by Dlist operations. */\n    int next_col ;\t\t/* Used by Dlist operations. */\n    int ngarbage ;\t\t/* number of garbage collections performed */\n\n#ifndef NDEBUG\n    int debug_d ;\t\t/* debug loop counter */\n    int debug_step = 0 ;\t/* debug loop counter */\n#endif /* NDEBUG */\n\n    /* === Initialization and clear mark ==================================== */\n\n    max_mark = INT_MAX - n_col ;\t/* INT_MAX defined in <limits.h> */\n    tag_mark = clear_mark (n_row, Row) ;\n    min_score = 0 ;\n    ngarbage = 0 ;\n    DEBUG1 ((\"colamd: Ordering, n_col2=%d\\n\", n_col2)) ;\n\n    /* === Order the columns ================================================ */\n\n    for (k = 0 ; k < n_col2 ; /* 'k' is incremented below */)\n    {\n\n#ifndef NDEBUG\n\tif (debug_step % 100 == 0)\n\t{\n\t    DEBUG2 ((\"\\n...       Step k: %d out of n_col2: %d\\n\", k, n_col2)) ;\n\t}\n\telse\n\t{\n\t    DEBUG3 ((\"\\n----------Step k: %d out of n_col2: %d\\n\", k, n_col2)) ;\n\t}\n\tdebug_step++ ;\n\tdebug_deg_lists (n_row, n_col, Row, Col, head,\n\t\tmin_score, n_col2-k, max_deg) ;\n\tdebug_matrix (n_row, n_col, Row, Col, A) ;\n#endif /* NDEBUG */\n\n\t/* === Select pivot column, and order it ============================ */\n\n\t/* make sure degree list isn't empty */\n\tASSERT (min_score >= 0) ;\n\tASSERT (min_score <= n_col) ;\n\tASSERT (head [min_score] >= EMPTY) ;\n\n#ifndef NDEBUG\n\tfor (debug_d = 0 ; debug_d < min_score ; debug_d++)\n\t{\n\t    ASSERT (head [debug_d] == EMPTY) ;\n\t}\n#endif /* NDEBUG */\n\n\t/* get pivot column from head of minimum degree list */\n\twhile (head [min_score] == EMPTY && min_score < n_col)\n\t{\n\t    min_score++ ;\n\t}\n\tpivot_col = head [min_score] ;\n\tASSERT (pivot_col >= 0 && pivot_col <= n_col) ;\n\tnext_col = Col [pivot_col].shared4.degree_next ;\n\thead [min_score] = next_col ;\n\tif (next_col != EMPTY)\n\t{\n\t    Col [next_col].shared3.prev = EMPTY ;\n\t}\n\n\tASSERT (COL_IS_ALIVE (pivot_col)) ;\n\tDEBUG3 ((\"Pivot col: %d\\n\", pivot_col)) ;\n\n\t/* remember score for defrag check */\n\tpivot_col_score = Col [pivot_col].shared2.score ;\n\n\t/* the pivot column is the kth column in the pivot order */\n\tCol [pivot_col].shared2.order = k ;\n\n\t/* increment order count by column thickness */\n\tpivot_col_thickness = Col [pivot_col].shared1.thickness ;\n\tk += pivot_col_thickness ;\n\tASSERT (pivot_col_thickness > 0) ;\n\n\t/* === Garbage_collection, if necessary ============================= */\n\n\tneeded_memory = MIN (pivot_col_score, n_col - k) ;\n\tif (pfree + needed_memory >= Alen)\n\t{\n\t    pfree = garbage_collection (n_row, n_col, Row, Col, A, &A [pfree]) ;\n\t    ngarbage++ ;\n\t    /* after garbage collection we will have enough */\n\t    ASSERT (pfree + needed_memory < Alen) ;\n\t    /* garbage collection has wiped out the Row[].shared2.mark array */\n\t    tag_mark = clear_mark (n_row, Row) ;\n\n#ifndef NDEBUG\n\t    debug_matrix (n_row, n_col, Row, Col, A) ;\n#endif /* NDEBUG */\n\t}\n\n\t/* === Compute pivot row pattern ==================================== */\n\n\t/* get starting location for this new merged row */\n\tpivot_row_start = pfree ;\n\n\t/* initialize new row counts to zero */\n\tpivot_row_degree = 0 ;\n\n\t/* tag pivot column as having been visited so it isn't included */\n\t/* in merged pivot row */\n\tCol [pivot_col].shared1.thickness = -pivot_col_thickness ;\n\n\t/* pivot row is the union of all rows in the pivot column pattern */\n\tcp = &A [Col [pivot_col].start] ;\n\tcp_end = cp + Col [pivot_col].length ;\n\twhile (cp < cp_end)\n\t{\n\t    /* get a row */\n\t    row = *cp++ ;\n\t    DEBUG4 ((\"Pivot col pattern %d %d\\n\", ROW_IS_ALIVE (row), row)) ;\n\t    /* skip if row is dead */\n\t    if (ROW_IS_DEAD (row))\n\t    {\n\t\tcontinue ;\n\t    }\n\t    rp = &A [Row [row].start] ;\n\t    rp_end = rp + Row [row].length ;\n\t    while (rp < rp_end)\n\t    {\n\t\t/* get a column */\n\t\tcol = *rp++ ;\n\t\t/* add the column, if alive and untagged */\n\t\tcol_thickness = Col [col].shared1.thickness ;\n\t\tif (col_thickness > 0 && COL_IS_ALIVE (col))\n\t\t{\n\t\t    /* tag column in pivot row */\n\t\t    Col [col].shared1.thickness = -col_thickness ;\n\t\t    ASSERT (pfree < Alen) ;\n\t\t    /* place column in pivot row */\n\t\t    A [pfree++] = col ;\n\t\t    pivot_row_degree += col_thickness ;\n\t\t}\n\t    }\n\t}\n\n\t/* clear tag on pivot column */\n\tCol [pivot_col].shared1.thickness = pivot_col_thickness ;\n\tmax_deg = MAX (max_deg, pivot_row_degree) ;\n\n#ifndef NDEBUG\n\tDEBUG3 ((\"check2\\n\")) ;\n\tdebug_mark (n_row, Row, tag_mark, max_mark) ;\n#endif /* NDEBUG */\n\n\t/* === Kill all rows used to construct pivot row ==================== */\n\n\t/* also kill pivot row, temporarily */\n\tcp = &A [Col [pivot_col].start] ;\n\tcp_end = cp + Col [pivot_col].length ;\n\twhile (cp < cp_end)\n\t{\n\t    /* may be killing an already dead row */\n\t    row = *cp++ ;\n\t    DEBUG3 ((\"Kill row in pivot col: %d\\n\", row)) ;\n\t    KILL_ROW (row) ;\n\t}\n\n\t/* === Select a row index to use as the new pivot row =============== */\n\n\tpivot_row_length = pfree - pivot_row_start ;\n\tif (pivot_row_length > 0)\n\t{\n\t    /* pick the \"pivot\" row arbitrarily (first row in col) */\n\t    pivot_row = A [Col [pivot_col].start] ;\n\t    DEBUG3 ((\"Pivotal row is %d\\n\", pivot_row)) ;\n\t}\n\telse\n\t{\n\t    /* there is no pivot row, since it is of zero length */\n\t    pivot_row = EMPTY ;\n\t    ASSERT (pivot_row_length == 0) ;\n\t}\n\tASSERT (Col [pivot_col].length > 0 || pivot_row_length == 0) ;\n\n\t/* === Approximate degree computation =============================== */\n\n\t/* Here begins the computation of the approximate degree.  The column */\n\t/* score is the sum of the pivot row \"length\", plus the size of the */\n\t/* set differences of each row in the column minus the pattern of the */\n\t/* pivot row itself.  The column (\"thickness\") itself is also */\n\t/* excluded from the column score (we thus use an approximate */\n\t/* external degree). */\n\n\t/* The time taken by the following code (compute set differences, and */\n\t/* add them up) is proportional to the size of the data structure */\n\t/* being scanned - that is, the sum of the sizes of each column in */\n\t/* the pivot row.  Thus, the amortized time to compute a column score */\n\t/* is proportional to the size of that column (where size, in this */\n\t/* context, is the column \"length\", or the number of row indices */\n\t/* in that column).  The number of row indices in a column is */\n\t/* monotonically non-decreasing, from the length of the original */\n\t/* column on input to colamd. */\n\n\t/* === Compute set differences ====================================== */\n\n\tDEBUG3 ((\"** Computing set differences phase. **\\n\")) ;\n\n\t/* pivot row is currently dead - it will be revived later. */\n\n\tDEBUG3 ((\"Pivot row: \")) ;\n\t/* for each column in pivot row */\n\trp = &A [pivot_row_start] ;\n\trp_end = rp + pivot_row_length ;\n\twhile (rp < rp_end)\n\t{\n\t    col = *rp++ ;\n\t    ASSERT (COL_IS_ALIVE (col) && col != pivot_col) ;\n\t    DEBUG3 ((\"Col: %d\\n\", col)) ;\n\n\t    /* clear tags used to construct pivot row pattern */\n\t    col_thickness = -Col [col].shared1.thickness ;\n\t    ASSERT (col_thickness > 0) ;\n\t    Col [col].shared1.thickness = col_thickness ;\n\n\t    /* === Remove column from degree list =========================== */\n\n\t    cur_score = Col [col].shared2.score ;\n\t    prev_col = Col [col].shared3.prev ;\n\t    next_col = Col [col].shared4.degree_next ;\n\t    ASSERT (cur_score >= 0) ;\n\t    ASSERT (cur_score <= n_col) ;\n\t    ASSERT (cur_score >= EMPTY) ;\n\t    if (prev_col == EMPTY)\n\t    {\n\t\thead [cur_score] = next_col ;\n\t    }\n\t    else\n\t    {\n\t\tCol [prev_col].shared4.degree_next = next_col ;\n\t    }\n\t    if (next_col != EMPTY)\n\t    {\n\t\tCol [next_col].shared3.prev = prev_col ;\n\t    }\n\n\t    /* === Scan the column ========================================== */\n\n\t    cp = &A [Col [col].start] ;\n\t    cp_end = cp + Col [col].length ;\n\t    while (cp < cp_end)\n\t    {\n\t\t/* get a row */\n\t\trow = *cp++ ;\n\t\trow_mark = Row [row].shared2.mark ;\n\t\t/* skip if dead */\n\t\tif (ROW_IS_MARKED_DEAD (row_mark))\n\t\t{\n\t\t    continue ;\n\t\t}\n\t\tASSERT (row != pivot_row) ;\n\t\tset_difference = row_mark - tag_mark ;\n\t\t/* check if the row has been seen yet */\n\t\tif (set_difference < 0)\n\t\t{\n\t\t    ASSERT (Row [row].shared1.degree <= max_deg) ;\n\t\t    set_difference = Row [row].shared1.degree ;\n\t\t}\n\t\t/* subtract column thickness from this row's set difference */\n\t\tset_difference -= col_thickness ;\n\t\tASSERT (set_difference >= 0) ;\n\t\t/* absorb this row if the set difference becomes zero */\n\t\tif (set_difference == 0)\n\t\t{\n\t\t    DEBUG3 ((\"aggressive absorption. Row: %d\\n\", row)) ;\n\t\t    KILL_ROW (row) ;\n\t\t}\n\t\telse\n\t\t{\n\t\t    /* save the new mark */\n\t\t    Row [row].shared2.mark = set_difference + tag_mark ;\n\t\t}\n\t    }\n\t}\n\n#ifndef NDEBUG\n\tdebug_deg_lists (n_row, n_col, Row, Col, head,\n\t\tmin_score, n_col2-k-pivot_row_degree, max_deg) ;\n#endif /* NDEBUG */\n\n\t/* === Add up set differences for each column ======================= */\n\n\tDEBUG3 ((\"** Adding set differences phase. **\\n\")) ;\n\n\t/* for each column in pivot row */\n\trp = &A [pivot_row_start] ;\n\trp_end = rp + pivot_row_length ;\n\twhile (rp < rp_end)\n\t{\n\t    /* get a column */\n\t    col = *rp++ ;\n\t    ASSERT (COL_IS_ALIVE (col) && col != pivot_col) ;\n\t    hash = 0 ;\n\t    cur_score = 0 ;\n\t    cp = &A [Col [col].start] ;\n\t    /* compact the column */\n\t    new_cp = cp ;\n\t    cp_end = cp + Col [col].length ;\n\n\t    DEBUG4 ((\"Adding set diffs for Col: %d.\\n\", col)) ;\n\n\t    while (cp < cp_end)\n\t    {\n\t\t/* get a row */\n\t\trow = *cp++ ;\n\t\tASSERT(row >= 0 && row < n_row) ;\n\t\trow_mark = Row [row].shared2.mark ;\n\t\t/* skip if dead */\n\t\tif (ROW_IS_MARKED_DEAD (row_mark))\n\t\t{\n\t\t    continue ;\n\t\t}\n\t\tASSERT (row_mark > tag_mark) ;\n\t\t/* compact the column */\n\t\t*new_cp++ = row ;\n\t\t/* compute hash function */\n\t\thash += row ;\n\t\t/* add set difference */\n\t\tcur_score += row_mark - tag_mark ;\n\t\t/* integer overflow... */\n\t\tcur_score = MIN (cur_score, n_col) ;\n\t    }\n\n\t    /* recompute the column's length */\n\t    Col [col].length = (int) (new_cp - &A [Col [col].start]) ;\n\n\t    /* === Further mass elimination ================================= */\n\n\t    if (Col [col].length == 0)\n\t    {\n\t\tDEBUG4 ((\"further mass elimination. Col: %d\\n\", col)) ;\n\t\t/* nothing left but the pivot row in this column */\n\t\tKILL_PRINCIPAL_COL (col) ;\n\t\tpivot_row_degree -= Col [col].shared1.thickness ;\n\t\tASSERT (pivot_row_degree >= 0) ;\n\t\t/* order it */\n\t\tCol [col].shared2.order = k ;\n\t\t/* increment order count by column thickness */\n\t\tk += Col [col].shared1.thickness ;\n\t    }\n\t    else\n\t    {\n\t\t/* === Prepare for supercolumn detection ==================== */\n\n\t\tDEBUG4 ((\"Preparing supercol detection for Col: %d.\\n\", col)) ;\n\n\t\t/* save score so far */\n\t\tCol [col].shared2.score = cur_score ;\n\n\t\t/* add column to hash table, for supercolumn detection */\n\t\thash %= n_col + 1 ;\n\n\t\tDEBUG4 ((\" Hash = %d, n_col = %d.\\n\", hash, n_col)) ;\n\t\tASSERT (hash <= n_col) ;\n\n\t\thead_column = head [hash] ;\n\t\tif (head_column > EMPTY)\n\t\t{\n\t\t    /* degree list \"hash\" is non-empty, use prev (shared3) of */\n\t\t    /* first column in degree list as head of hash bucket */\n\t\t    first_col = Col [head_column].shared3.headhash ;\n\t\t    Col [head_column].shared3.headhash = col ;\n\t\t}\n\t\telse\n\t\t{\n\t\t    /* degree list \"hash\" is empty, use head as hash bucket */\n\t\t    first_col = - (head_column + 2) ;\n\t\t    head [hash] = - (col + 2) ;\n\t\t}\n\t\tCol [col].shared4.hash_next = first_col ;\n\n\t\t/* save hash function in Col [col].shared3.hash */\n\t\tCol [col].shared3.hash = (int) hash ;\n\t\tASSERT (COL_IS_ALIVE (col)) ;\n\t    }\n\t}\n\n\t/* The approximate external column degree is now computed.  */\n\n\t/* === Supercolumn detection ======================================== */\n\n\tDEBUG3 ((\"** Supercolumn detection phase. **\\n\")) ;\n\n\tdetect_super_cols (\n\n#ifndef NDEBUG\n\t\tn_col, Row,\n#endif /* NDEBUG */\n\n\t\tCol, A, head, pivot_row_start, pivot_row_length) ;\n\n\t/* === Kill the pivotal column ====================================== */\n\n\tKILL_PRINCIPAL_COL (pivot_col) ;\n\n\t/* === Clear mark =================================================== */\n\n\ttag_mark += (max_deg + 1) ;\n\tif (tag_mark >= max_mark)\n\t{\n\t    DEBUG2 ((\"clearing tag_mark\\n\")) ;\n\t    tag_mark = clear_mark (n_row, Row) ;\n\t}\n\n#ifndef NDEBUG\n\tDEBUG3 ((\"check3\\n\")) ;\n\tdebug_mark (n_row, Row, tag_mark, max_mark) ;\n#endif /* NDEBUG */\n\n\t/* === Finalize the new pivot row, and column scores ================ */\n\n\tDEBUG3 ((\"** Finalize scores phase. **\\n\")) ;\n\n\t/* for each column in pivot row */\n\trp = &A [pivot_row_start] ;\n\t/* compact the pivot row */\n\tnew_rp = rp ;\n\trp_end = rp + pivot_row_length ;\n\twhile (rp < rp_end)\n\t{\n\t    col = *rp++ ;\n\t    /* skip dead columns */\n\t    if (COL_IS_DEAD (col))\n\t    {\n\t\tcontinue ;\n\t    }\n\t    *new_rp++ = col ;\n\t    /* add new pivot row to column */\n\t    A [Col [col].start + (Col [col].length++)] = pivot_row ;\n\n\t    /* retrieve score so far and add on pivot row's degree. */\n\t    /* (we wait until here for this in case the pivot */\n\t    /* row's degree was reduced due to mass elimination). */\n\t    cur_score = Col [col].shared2.score + pivot_row_degree ;\n\n\t    /* calculate the max possible score as the number of */\n\t    /* external columns minus the 'k' value minus the */\n\t    /* columns thickness */\n\t    max_score = n_col - k - Col [col].shared1.thickness ;\n\n\t    /* make the score the external degree of the union-of-rows */\n\t    cur_score -= Col [col].shared1.thickness ;\n\n\t    /* make sure score is less or equal than the max score */\n\t    cur_score = MIN (cur_score, max_score) ;\n\t    ASSERT (cur_score >= 0) ;\n\n\t    /* store updated score */\n\t    Col [col].shared2.score = cur_score ;\n\n\t    /* === Place column back in degree list ========================= */\n\n\t    ASSERT (min_score >= 0) ;\n\t    ASSERT (min_score <= n_col) ;\n\t    ASSERT (cur_score >= 0) ;\n\t    ASSERT (cur_score <= n_col) ;\n\t    ASSERT (head [cur_score] >= EMPTY) ;\n\t    next_col = head [cur_score] ;\n\t    Col [col].shared4.degree_next = next_col ;\n\t    Col [col].shared3.prev = EMPTY ;\n\t    if (next_col != EMPTY)\n\t    {\n\t\tCol [next_col].shared3.prev = col ;\n\t    }\n\t    head [cur_score] = col ;\n\n\t    /* see if this score is less than current min */\n\t    min_score = MIN (min_score, cur_score) ;\n\n\t}\n\n#ifndef NDEBUG\n\tdebug_deg_lists (n_row, n_col, Row, Col, head,\n\t\tmin_score, n_col2-k, max_deg) ;\n#endif /* NDEBUG */\n\n\t/* === Resurrect the new pivot row ================================== */\n\n\tif (pivot_row_degree > 0)\n\t{\n\t    /* update pivot row length to reflect any cols that were killed */\n\t    /* during super-col detection and mass elimination */\n\t    Row [pivot_row].start  = pivot_row_start ;\n\t    Row [pivot_row].length = (int) (new_rp - &A[pivot_row_start]) ;\n\t    Row [pivot_row].shared1.degree = pivot_row_degree ;\n\t    Row [pivot_row].shared2.mark = 0 ;\n\t    /* pivot row is no longer dead */\n\t}\n    }\n\n    /* === All principal columns have now been ordered ====================== */\n\n    return (ngarbage) ;\n}\n\n\n/* ========================================================================== */\n/* === order_children ======================================================= */\n/* ========================================================================== */\n\n/*\n    The find_ordering routine has ordered all of the principal columns (the\n    representatives of the supercolumns).  The non-principal columns have not\n    yet been ordered.  This routine orders those columns by walking up the\n    parent tree (a column is a child of the column which absorbed it).  The\n    final permutation vector is then placed in p [0 ... n_col-1], with p [0]\n    being the first column, and p [n_col-1] being the last.  It doesn't look\n    like it at first glance, but be assured that this routine takes time linear\n    in the number of columns.  Although not immediately obvious, the time\n    taken by this routine is O (n_col), that is, linear in the number of\n    columns.  Not user-callable.\n*/\n\nPRIVATE void order_children\n(\n    /* === Parameters ======================================================= */\n\n    int n_col,\t\t\t/* number of columns of A */\n    Colamd_Col Col [],\t\t/* of size n_col+1 */\n    int p []\t\t\t/* p [0 ... n_col-1] is the column permutation*/\n)\n{\n    /* === Local variables ================================================== */\n\n    int i ;\t\t\t/* loop counter for all columns */\n    int c ;\t\t\t/* column index */\n    int parent ;\t\t/* index of column's parent */\n    int order ;\t\t\t/* column's order */\n\n    /* === Order each non-principal column ================================== */\n\n    for (i = 0 ; i < n_col ; i++)\n    {\n\t/* find an un-ordered non-principal column */\n\tASSERT (COL_IS_DEAD (i)) ;\n\tif (!COL_IS_DEAD_PRINCIPAL (i) && Col [i].shared2.order == EMPTY)\n\t{\n\t    parent = i ;\n\t    /* once found, find its principal parent */\n\t    do\n\t    {\n\t\tparent = Col [parent].shared1.parent ;\n\t    } while (!COL_IS_DEAD_PRINCIPAL (parent)) ;\n\n\t    /* now, order all un-ordered non-principal columns along path */\n\t    /* to this parent.  collapse tree at the same time */\n\t    c = i ;\n\t    /* get order of parent */\n\t    order = Col [parent].shared2.order ;\n\n\t    do\n\t    {\n\t\tASSERT (Col [c].shared2.order == EMPTY) ;\n\n\t\t/* order this column */\n\t\tCol [c].shared2.order = order++ ;\n\t\t/* collaps tree */\n\t\tCol [c].shared1.parent = parent ;\n\n\t\t/* get immediate parent of this column */\n\t\tc = Col [c].shared1.parent ;\n\n\t\t/* continue until we hit an ordered column.  There are */\n\t\t/* guarranteed not to be anymore unordered columns */\n\t\t/* above an ordered column */\n\t    } while (Col [c].shared2.order == EMPTY) ;\n\n\t    /* re-order the super_col parent to largest order for this group */\n\t    Col [parent].shared2.order = order ;\n\t}\n    }\n\n    /* === Generate the permutation ========================================= */\n\n    for (c = 0 ; c < n_col ; c++)\n    {\n\tp [Col [c].shared2.order] = c ;\n    }\n}\n\n\n/* ========================================================================== */\n/* === detect_super_cols ==================================================== */\n/* ========================================================================== */\n\n/*\n    Detects supercolumns by finding matches between columns in the hash buckets.\n    Check amongst columns in the set A [row_start ... row_start + row_length-1].\n    The columns under consideration are currently *not* in the degree lists,\n    and have already been placed in the hash buckets.\n\n    The hash bucket for columns whose hash function is equal to h is stored\n    as follows:\n\n\tif head [h] is >= 0, then head [h] contains a degree list, so:\n\n\t\thead [h] is the first column in degree bucket h.\n\t\tCol [head [h]].headhash gives the first column in hash bucket h.\n\n\totherwise, the degree list is empty, and:\n\n\t\t-(head [h] + 2) is the first column in hash bucket h.\n\n    For a column c in a hash bucket, Col [c].shared3.prev is NOT a \"previous\n    column\" pointer.  Col [c].shared3.hash is used instead as the hash number\n    for that column.  The value of Col [c].shared4.hash_next is the next column\n    in the same hash bucket.\n\n    Assuming no, or \"few\" hash collisions, the time taken by this routine is\n    linear in the sum of the sizes (lengths) of each column whose score has\n    just been computed in the approximate degree computation.\n    Not user-callable.\n*/\n\nPRIVATE void detect_super_cols\n(\n    /* === Parameters ======================================================= */\n\n#ifndef NDEBUG\n    /* these two parameters are only needed when debugging is enabled: */\n    int n_col,\t\t\t/* number of columns of A */\n    Colamd_Row Row [],\t\t/* of size n_row+1 */\n#endif /* NDEBUG */\n\n    Colamd_Col Col [],\t\t/* of size n_col+1 */\n    int A [],\t\t\t/* row indices of A */\n    int head [],\t\t/* head of degree lists and hash buckets */\n    int row_start,\t\t/* pointer to set of columns to check */\n    int row_length\t\t/* number of columns to check */\n)\n{\n    /* === Local variables ================================================== */\n\n    int hash ;\t\t\t/* hash value for a column */\n    int *rp ;\t\t\t/* pointer to a row */\n    int c ;\t\t\t/* a column index */\n    int super_c ;\t\t/* column index of the column to absorb into */\n    int *cp1 ;\t\t\t/* column pointer for column super_c */\n    int *cp2 ;\t\t\t/* column pointer for column c */\n    int length ;\t\t/* length of column super_c */\n    int prev_c ;\t\t/* column preceding c in hash bucket */\n    int i ;\t\t\t/* loop counter */\n    int *rp_end ;\t\t/* pointer to the end of the row */\n    int col ;\t\t\t/* a column index in the row to check */\n    int head_column ;\t\t/* first column in hash bucket or degree list */\n    int first_col ;\t\t/* first column in hash bucket */\n\n    /* === Consider each column in the row ================================== */\n\n    rp = &A [row_start] ;\n    rp_end = rp + row_length ;\n    while (rp < rp_end)\n    {\n\tcol = *rp++ ;\n\tif (COL_IS_DEAD (col))\n\t{\n\t    continue ;\n\t}\n\n\t/* get hash number for this column */\n\thash = Col [col].shared3.hash ;\n\tASSERT (hash <= n_col) ;\n\n\t/* === Get the first column in this hash bucket ===================== */\n\n\thead_column = head [hash] ;\n\tif (head_column > EMPTY)\n\t{\n\t    first_col = Col [head_column].shared3.headhash ;\n\t}\n\telse\n\t{\n\t    first_col = - (head_column + 2) ;\n\t}\n\n\t/* === Consider each column in the hash bucket ====================== */\n\n\tfor (super_c = first_col ; super_c != EMPTY ;\n\t    super_c = Col [super_c].shared4.hash_next)\n\t{\n\t    ASSERT (COL_IS_ALIVE (super_c)) ;\n\t    ASSERT (Col [super_c].shared3.hash == hash) ;\n\t    length = Col [super_c].length ;\n\n\t    /* prev_c is the column preceding column c in the hash bucket */\n\t    prev_c = super_c ;\n\n\t    /* === Compare super_c with all columns after it ================ */\n\n\t    for (c = Col [super_c].shared4.hash_next ;\n\t\t c != EMPTY ; c = Col [c].shared4.hash_next)\n\t    {\n\t\tASSERT (c != super_c) ;\n\t\tASSERT (COL_IS_ALIVE (c)) ;\n\t\tASSERT (Col [c].shared3.hash == hash) ;\n\n\t\t/* not identical if lengths or scores are different */\n\t\tif (Col [c].length != length ||\n\t\t    Col [c].shared2.score != Col [super_c].shared2.score)\n\t\t{\n\t\t    prev_c = c ;\n\t\t    continue ;\n\t\t}\n\n\t\t/* compare the two columns */\n\t\tcp1 = &A [Col [super_c].start] ;\n\t\tcp2 = &A [Col [c].start] ;\n\n\t\tfor (i = 0 ; i < length ; i++)\n\t\t{\n\t\t    /* the columns are \"clean\" (no dead rows) */\n\t\t    ASSERT (ROW_IS_ALIVE (*cp1))  ;\n\t\t    ASSERT (ROW_IS_ALIVE (*cp2))  ;\n\t\t    /* row indices will same order for both supercols, */\n\t\t    /* no gather scatter nessasary */\n\t\t    if (*cp1++ != *cp2++)\n\t\t    {\n\t\t\tbreak ;\n\t\t    }\n\t\t}\n\n\t\t/* the two columns are different if the for-loop \"broke\" */\n\t\tif (i != length)\n\t\t{\n\t\t    prev_c = c ;\n\t\t    continue ;\n\t\t}\n\n\t\t/* === Got it!  two columns are identical =================== */\n\n\t\tASSERT (Col [c].shared2.score == Col [super_c].shared2.score) ;\n\n\t\tCol [super_c].shared1.thickness += Col [c].shared1.thickness ;\n\t\tCol [c].shared1.parent = super_c ;\n\t\tKILL_NON_PRINCIPAL_COL (c) ;\n\t\t/* order c later, in order_children() */\n\t\tCol [c].shared2.order = EMPTY ;\n\t\t/* remove c from hash bucket */\n\t\tCol [prev_c].shared4.hash_next = Col [c].shared4.hash_next ;\n\t    }\n\t}\n\n\t/* === Empty this hash bucket ======================================= */\n\n\tif (head_column > EMPTY)\n\t{\n\t    /* corresponding degree list \"hash\" is not empty */\n\t    Col [head_column].shared3.headhash = EMPTY ;\n\t}\n\telse\n\t{\n\t    /* corresponding degree list \"hash\" is empty */\n\t    head [hash] = EMPTY ;\n\t}\n    }\n}\n\n\n/* ========================================================================== */\n/* === garbage_collection =================================================== */\n/* ========================================================================== */\n\n/*\n    Defragments and compacts columns and rows in the workspace A.  Used when\n    all avaliable memory has been used while performing row merging.  Returns\n    the index of the first free position in A, after garbage collection.  The\n    time taken by this routine is linear is the size of the array A, which is\n    itself linear in the number of nonzeros in the input matrix.\n    Not user-callable.\n*/\n\nPRIVATE int garbage_collection  /* returns the new value of pfree */\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\t\t\t/* number of rows */\n    int n_col,\t\t\t/* number of columns */\n    Colamd_Row Row [],\t\t/* row info */\n    Colamd_Col Col [],\t\t/* column info */\n    int A [],\t\t\t/* A [0 ... Alen-1] holds the matrix */\n    int *pfree\t\t\t/* &A [0] ... pfree is in use */\n)\n{\n    /* === Local variables ================================================== */\n\n    int *psrc ;\t\t\t/* source pointer */\n    int *pdest ;\t\t/* destination pointer */\n    int j ;\t\t\t/* counter */\n    int r ;\t\t\t/* a row index */\n    int c ;\t\t\t/* a column index */\n    int length ;\t\t/* length of a row or column */\n\n#ifndef NDEBUG\n    int debug_rows ;\n    DEBUG2 ((\"Defrag..\\n\")) ;\n    for (psrc = &A[0] ; psrc < pfree ; psrc++) ASSERT (*psrc >= 0) ;\n    debug_rows = 0 ;\n#endif /* NDEBUG */\n\n    /* === Defragment the columns =========================================== */\n\n    pdest = &A[0] ;\n    for (c = 0 ; c < n_col ; c++)\n    {\n\tif (COL_IS_ALIVE (c))\n\t{\n\t    psrc = &A [Col [c].start] ;\n\n\t    /* move and compact the column */\n\t    ASSERT (pdest <= psrc) ;\n\t    Col [c].start = (int) (pdest - &A [0]) ;\n\t    length = Col [c].length ;\n\t    for (j = 0 ; j < length ; j++)\n\t    {\n\t\tr = *psrc++ ;\n\t\tif (ROW_IS_ALIVE (r))\n\t\t{\n\t\t    *pdest++ = r ;\n\t\t}\n\t    }\n\t    Col [c].length = (int) (pdest - &A [Col [c].start]) ;\n\t}\n    }\n\n    /* === Prepare to defragment the rows =================================== */\n\n    for (r = 0 ; r < n_row ; r++)\n    {\n\tif (ROW_IS_ALIVE (r))\n\t{\n\t    if (Row [r].length == 0)\n\t    {\n\t\t/* this row is of zero length.  cannot compact it, so kill it */\n\t\tDEBUG3 ((\"Defrag row kill\\n\")) ;\n\t\tKILL_ROW (r) ;\n\t    }\n\t    else\n\t    {\n\t\t/* save first column index in Row [r].shared2.first_column */\n\t\tpsrc = &A [Row [r].start] ;\n\t\tRow [r].shared2.first_column = *psrc ;\n\t\tASSERT (ROW_IS_ALIVE (r)) ;\n\t\t/* flag the start of the row with the one's complement of row */\n\t\t*psrc = ONES_COMPLEMENT (r) ;\n\n#ifndef NDEBUG\n\t\tdebug_rows++ ;\n#endif /* NDEBUG */\n\n\t    }\n\t}\n    }\n\n    /* === Defragment the rows ============================================== */\n\n    psrc = pdest ;\n    while (psrc < pfree)\n    {\n\t/* find a negative number ... the start of a row */\n\tif (*psrc++ < 0)\n\t{\n\t    psrc-- ;\n\t    /* get the row index */\n\t    r = ONES_COMPLEMENT (*psrc) ;\n\t    ASSERT (r >= 0 && r < n_row) ;\n\t    /* restore first column index */\n\t    *psrc = Row [r].shared2.first_column ;\n\t    ASSERT (ROW_IS_ALIVE (r)) ;\n\n\t    /* move and compact the row */\n\t    ASSERT (pdest <= psrc) ;\n\t    Row [r].start = (int) (pdest - &A [0]) ;\n\t    length = Row [r].length ;\n\t    for (j = 0 ; j < length ; j++)\n\t    {\n\t\tc = *psrc++ ;\n\t\tif (COL_IS_ALIVE (c))\n\t\t{\n\t\t    *pdest++ = c ;\n\t\t}\n\t    }\n\t    Row [r].length = (int) (pdest - &A [Row [r].start]) ;\n\n#ifndef NDEBUG\n\t    debug_rows-- ;\n#endif /* NDEBUG */\n\n\t}\n    }\n    /* ensure we found all the rows */\n    ASSERT (debug_rows == 0) ;\n\n    /* === Return the new value of pfree ==================================== */\n\n    return ((int) (pdest - &A [0])) ;\n}\n\n\n/* ========================================================================== */\n/* === clear_mark =========================================================== */\n/* ========================================================================== */\n\n/*\n    Clears the Row [].shared2.mark array, and returns the new tag_mark.\n    Return value is the new tag_mark.  Not user-callable.\n*/\n\nPRIVATE int clear_mark\t/* return the new value for tag_mark */\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\t\t/* number of rows in A */\n    Colamd_Row Row []\t/* Row [0 ... n_row-1].shared2.mark is set to zero */\n)\n{\n    /* === Local variables ================================================== */\n\n    int r ;\n\n    for (r = 0 ; r < n_row ; r++)\n    {\n\tif (ROW_IS_ALIVE (r))\n\t{\n\t    Row [r].shared2.mark = 0 ;\n\t}\n    }\n    return (1) ;\n}\n\n\n/* ========================================================================== */\n/* === print_report ========================================================= */\n/* ========================================================================== */\n\nPRIVATE void print_report\n(\n    char *method,\n    int stats [COLAMD_STATS]\n)\n{\n\n    int i1, i2, i3 ;\n\n    if (!stats)\n    {\n    \tPRINTF (\"%s: No statistics available.\\n\", method) ;\n\treturn ;\n    }\n\n    i1 = stats [COLAMD_INFO1] ;\n    i2 = stats [COLAMD_INFO2] ;\n    i3 = stats [COLAMD_INFO3] ;\n\n    if (stats [COLAMD_STATUS] >= 0)\n    {\n    \tPRINTF (\"%s: OK.  \", method) ;\n    }\n    else\n    {\n    \tPRINTF (\"%s: ERROR.  \", method) ;\n    }\n\n    switch (stats [COLAMD_STATUS])\n    {\n\n\tcase COLAMD_OK_BUT_JUMBLED:\n\n\t    PRINTF (\"Matrix has unsorted or duplicate row indices.\\n\") ;\n\n\t    PRINTF (\"%s: number of duplicate or out-of-order row indices: %d\\n\",\n\t    method, i3) ;\n\n\t    PRINTF (\"%s: last seen duplicate or out-of-order row index:   %d\\n\",\n\t    method, INDEX (i2)) ;\n\n\t    PRINTF (\"%s: last seen in column:                             %d\",\n\t    method, INDEX (i1)) ;\n\n\t    /* no break - fall through to next case instead */\n\n\tcase COLAMD_OK:\n\n\t    PRINTF (\"\\n\") ;\n\n \t    PRINTF (\"%s: number of dense or empty rows ignored:           %d\\n\",\n\t    method, stats [COLAMD_DENSE_ROW]) ;\n\n\t    PRINTF (\"%s: number of dense or empty columns ignored:        %d\\n\",\n\t    method, stats [COLAMD_DENSE_COL]) ;\n\n\t    PRINTF (\"%s: number of garbage collections performed:         %d\\n\",\n\t    method, stats [COLAMD_DEFRAG_COUNT]) ;\n\t    break ;\n\n\tcase COLAMD_ERROR_A_not_present:\n\n\t    PRINTF (\"Array A (row indices of matrix) not present.\\n\") ;\n\t    break ;\n\n\tcase COLAMD_ERROR_p_not_present:\n\n\t    PRINTF (\"Array p (column pointers for matrix) not present.\\n\") ;\n\t    break ;\n\n\tcase COLAMD_ERROR_nrow_negative:\n\n\t    PRINTF (\"Invalid number of rows (%d).\\n\", i1) ;\n\t    break ;\n\n\tcase COLAMD_ERROR_ncol_negative:\n\n\t    PRINTF (\"Invalid number of columns (%d).\\n\", i1) ;\n\t    break ;\n\n\tcase COLAMD_ERROR_nnz_negative:\n\n\t    PRINTF (\"Invalid number of nonzero entries (%d).\\n\", i1) ;\n\t    break ;\n\n\tcase COLAMD_ERROR_p0_nonzero:\n\n\t    PRINTF (\"Invalid column pointer, p [0] = %d, must be zero.\\n\", i1) ;\n\t    break ;\n\n\tcase COLAMD_ERROR_A_too_small:\n\n\t    PRINTF (\"Array A too small.\\n\") ;\n\t    PRINTF (\"        Need Alen >= %d, but given only Alen = %d.\\n\",\n\t    i1, i2) ;\n\t    break ;\n\n\tcase COLAMD_ERROR_col_length_negative:\n\n\t    PRINTF\n\t    (\"Column %d has a negative number of nonzero entries (%d).\\n\",\n\t    INDEX (i1), i2) ;\n\t    break ;\n\n\tcase COLAMD_ERROR_row_index_out_of_bounds:\n\n\t    PRINTF\n\t    (\"Row index (row %d) out of bounds (%d to %d) in column %d.\\n\",\n\t    INDEX (i2), INDEX (0), INDEX (i3-1), INDEX (i1)) ;\n\t    break ;\n\n\tcase COLAMD_ERROR_out_of_memory:\n\n\t    PRINTF (\"Out of memory.\\n\") ;\n\t    break ;\n\n\tcase COLAMD_ERROR_internal_error:\n\n\t    /* if this happens, there is a bug in the code */\n\t    PRINTF\n\t    (\"Internal error! Please contact authors (davis@cise.ufl.edu).\\n\") ;\n\t    break ;\n    }\n}\n\n\n\n\n/* ========================================================================== */\n/* === colamd debugging routines ============================================ */\n/* ========================================================================== */\n\n/* When debugging is disabled, the remainder of this file is ignored. */\n\n#ifndef NDEBUG\n\n\n/* ========================================================================== */\n/* === debug_structures ===================================================== */\n/* ========================================================================== */\n\n/*\n    At this point, all empty rows and columns are dead.  All live columns\n    are \"clean\" (containing no dead rows) and simplicial (no supercolumns\n    yet).  Rows may contain dead columns, but all live rows contain at\n    least one live column.\n*/\n\nPRIVATE void debug_structures\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int A [],\n    int n_col2\n)\n{\n    /* === Local variables ================================================== */\n\n    int i ;\n    int c ;\n    int *cp ;\n    int *cp_end ;\n    int len ;\n    int score ;\n    int r ;\n    int *rp ;\n    int *rp_end ;\n    int deg ;\n\n    /* === Check A, Row, and Col ============================================ */\n\n    for (c = 0 ; c < n_col ; c++)\n    {\n\tif (COL_IS_ALIVE (c))\n\t{\n\t    len = Col [c].length ;\n\t    score = Col [c].shared2.score ;\n\t    DEBUG4 ((\"initial live col %5d %5d %5d\\n\", c, len, score)) ;\n\t    ASSERT (len > 0) ;\n\t    ASSERT (score >= 0) ;\n\t    ASSERT (Col [c].shared1.thickness == 1) ;\n\t    cp = &A [Col [c].start] ;\n\t    cp_end = cp + len ;\n\t    while (cp < cp_end)\n\t    {\n\t\tr = *cp++ ;\n\t\tASSERT (ROW_IS_ALIVE (r)) ;\n\t    }\n\t}\n\telse\n\t{\n\t    i = Col [c].shared2.order ;\n\t    ASSERT (i >= n_col2 && i < n_col) ;\n\t}\n    }\n\n    for (r = 0 ; r < n_row ; r++)\n    {\n\tif (ROW_IS_ALIVE (r))\n\t{\n\t    i = 0 ;\n\t    len = Row [r].length ;\n\t    deg = Row [r].shared1.degree ;\n\t    ASSERT (len > 0) ;\n\t    ASSERT (deg > 0) ;\n\t    rp = &A [Row [r].start] ;\n\t    rp_end = rp + len ;\n\t    while (rp < rp_end)\n\t    {\n\t\tc = *rp++ ;\n\t\tif (COL_IS_ALIVE (c))\n\t\t{\n\t\t    i++ ;\n\t\t}\n\t    }\n\t    ASSERT (i > 0) ;\n\t}\n    }\n}\n\n\n/* ========================================================================== */\n/* === debug_deg_lists ====================================================== */\n/* ========================================================================== */\n\n/*\n    Prints the contents of the degree lists.  Counts the number of columns\n    in the degree list and compares it to the total it should have.  Also\n    checks the row degrees.\n*/\n\nPRIVATE void debug_deg_lists\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int head [],\n    int min_score,\n    int should,\n    int max_deg\n)\n{\n    /* === Local variables ================================================== */\n\n    int deg ;\n    int col ;\n    int have ;\n    int row ;\n\n    /* === Check the degree lists =========================================== */\n\n    if (n_col > 10000 && colamd_debug <= 0)\n    {\n\treturn ;\n    }\n    have = 0 ;\n    DEBUG4 ((\"Degree lists: %d\\n\", min_score)) ;\n    for (deg = 0 ; deg <= n_col ; deg++)\n    {\n\tcol = head [deg] ;\n\tif (col == EMPTY)\n\t{\n\t    continue ;\n\t}\n\tDEBUG4 ((\"%d:\", deg)) ;\n\twhile (col != EMPTY)\n\t{\n\t    DEBUG4 ((\" %d\", col)) ;\n\t    have += Col [col].shared1.thickness ;\n\t    ASSERT (COL_IS_ALIVE (col)) ;\n\t    col = Col [col].shared4.degree_next ;\n\t}\n\tDEBUG4 ((\"\\n\")) ;\n    }\n    DEBUG4 ((\"should %d have %d\\n\", should, have)) ;\n    ASSERT (should == have) ;\n\n    /* === Check the row degrees ============================================ */\n\n    if (n_row > 10000 && colamd_debug <= 0)\n    {\n\treturn ;\n    }\n    for (row = 0 ; row < n_row ; row++)\n    {\n\tif (ROW_IS_ALIVE (row))\n\t{\n\t    ASSERT (Row [row].shared1.degree <= max_deg) ;\n\t}\n    }\n}\n\n\n/* ========================================================================== */\n/* === debug_mark =========================================================== */\n/* ========================================================================== */\n\n/*\n    Ensures that the tag_mark is less that the maximum and also ensures that\n    each entry in the mark array is less than the tag mark.\n*/\n\nPRIVATE void debug_mark\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\n    Colamd_Row Row [],\n    int tag_mark,\n    int max_mark\n)\n{\n    /* === Local variables ================================================== */\n\n    int r ;\n\n    /* === Check the Row marks ============================================== */\n\n    ASSERT (tag_mark > 0 && tag_mark <= max_mark) ;\n    if (n_row > 10000 && colamd_debug <= 0)\n    {\n\treturn ;\n    }\n    for (r = 0 ; r < n_row ; r++)\n    {\n\tASSERT (Row [r].shared2.mark < tag_mark) ;\n    }\n}\n\n\n/* ========================================================================== */\n/* === debug_matrix ========================================================= */\n/* ========================================================================== */\n\n/*\n    Prints out the contents of the columns and the rows.\n*/\n\nPRIVATE void debug_matrix\n(\n    /* === Parameters ======================================================= */\n\n    int n_row,\n    int n_col,\n    Colamd_Row Row [],\n    Colamd_Col Col [],\n    int A []\n)\n{\n    /* === Local variables ================================================== */\n\n    int r ;\n    int c ;\n    int *rp ;\n    int *rp_end ;\n    int *cp ;\n    int *cp_end ;\n\n    /* === Dump the rows and columns of the matrix ========================== */\n\n    if (colamd_debug < 3)\n    {\n\treturn ;\n    }\n    DEBUG3 ((\"DUMP MATRIX:\\n\")) ;\n    for (r = 0 ; r < n_row ; r++)\n    {\n\tDEBUG3 ((\"Row %d alive? %d\\n\", r, ROW_IS_ALIVE (r))) ;\n\tif (ROW_IS_DEAD (r))\n\t{\n\t    continue ;\n\t}\n\tDEBUG3 ((\"start %d length %d degree %d\\n\",\n\t\tRow [r].start, Row [r].length, Row [r].shared1.degree)) ;\n\trp = &A [Row [r].start] ;\n\trp_end = rp + Row [r].length ;\n\twhile (rp < rp_end)\n\t{\n\t    c = *rp++ ;\n\t    DEBUG4 ((\"\t%d col %d\\n\", COL_IS_ALIVE (c), c)) ;\n\t}\n    }\n\n    for (c = 0 ; c < n_col ; c++)\n    {\n\tDEBUG3 ((\"Col %d alive? %d\\n\", c, COL_IS_ALIVE (c))) ;\n\tif (COL_IS_DEAD (c))\n\t{\n\t    continue ;\n\t}\n\tDEBUG3 ((\"start %d length %d shared1 %d shared2 %d\\n\",\n\t\tCol [c].start, Col [c].length,\n\t\tCol [c].shared1.thickness, Col [c].shared2.score)) ;\n\tcp = &A [Col [c].start] ;\n\tcp_end = cp + Col [c].length ;\n\twhile (cp < cp_end)\n\t{\n\t    r = *cp++ ;\n\t    DEBUG4 ((\"\t%d row %d\\n\", ROW_IS_ALIVE (r), r)) ;\n\t}\n    }\n}\n\nPRIVATE void colamd_get_debug\n(\n    char *method\n)\n{\n    colamd_debug = 0 ;\t\t/* no debug printing */\n\n    /* get \"D\" environment variable, which gives the debug printing level */\n    if (getenv (\"D\"))\n    {\n    \tcolamd_debug = atoi (getenv (\"D\")) ;\n    }\n\n    DEBUG0 ((\"%s: debug version, D = %d (THIS WILL BE SLOW!)\\n\",\n    \tmethod, colamd_debug)) ;\n}\n\n#endif /* NDEBUG */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/colamd/colamd.h",
    "content": "/* ========================================================================== */\n/* === colamd/symamd prototypes and definitions ============================= */\n/* ========================================================================== */\n\n/*\n    You must include this file (colamd.h) in any routine that uses colamd,\n    symamd, or the related macros and definitions.\n\n    Authors:\n\n\tThe authors of the code itself are Stefan I. Larimore and Timothy A.\n\tDavis (davis@cise.ufl.edu), University of Florida.  The algorithm was\n\tdeveloped in collaboration with John Gilbert, Xerox PARC, and Esmond\n\tNg, Oak Ridge National Laboratory.\n\n    Date:\n\n\tMay 4, 2001.  Version 2.1.\n\n    Acknowledgements:\n\n\tThis work was supported by the National Science Foundation, under\n\tgrants DMS-9504974 and DMS-9803599.\n\n    Notice:\n\n\tCopyright (c) 1998-2001 by the University of Florida.\n\tAll Rights Reserved.\n\n\tTHIS MATERIAL IS PROVIDED AS IS, WITH ABSOLUTELY NO WARRANTY\n\tEXPRESSED OR IMPLIED.  ANY USE IS AT YOUR OWN RISK.\n\n\tPermission is hereby granted to use or copy this program for any\n\tpurpose, provided the above notices are retained on all copies.\n\tUser documentation of any code that uses this code must cite the\n\tAuthors, the Copyright, and \"Used by permission.\"  If this code is\n\taccessible from within Matlab, then typing \"help colamd\" and \"help\n\tsymamd\" must cite the Authors.  Permission to modify the code and to\n\tdistribute modified code is granted, provided the above notices are\n\tretained, and a notice that the code was modified is included with the\n\tabove copyright notice.  You must also retain the Availability\n\tinformation below, of the original version.\n\n\tThis software is provided free of charge.\n\n    Availability:\n\n\tThe colamd/symamd library is available at\n\n\t    http://www.cise.ufl.edu/research/sparse/colamd\n\n\tThis is the http://www.cise.ufl.edu/research/sparse/colamd/colamd.h\n\tfile.  It is required by the colamd.c, colamdmex.c, and symamdmex.c\n\tfiles, and by any C code that calls the routines whose prototypes are\n\tlisted below, or that uses the colamd/symamd definitions listed below.\n\n*/\n\n#ifndef COLAMD_H\n#define COLAMD_H\n\n/* ========================================================================== */\n/* === Include files ======================================================== */\n/* ========================================================================== */\n\n#include <stdlib.h>\n\n/* ========================================================================== */\n/* === Knob and statistics definitions ====================================== */\n/* ========================================================================== */\n\n/* size of the knobs [ ] array.  Only knobs [0..1] are currently used. */\n#define COLAMD_KNOBS 20\n\n/* number of output statistics.  Only stats [0..6] are currently used. */\n#define COLAMD_STATS 20\n\n/* knobs [0] and stats [0]: dense row knob and output statistic. */\n#define COLAMD_DENSE_ROW 0\n\n/* knobs [1] and stats [1]: dense column knob and output statistic. */\n#define COLAMD_DENSE_COL 1\n\n/* stats [2]: memory defragmentation count output statistic */\n#define COLAMD_DEFRAG_COUNT 2\n\n/* stats [3]: colamd status:  zero OK, > 0 warning or notice, < 0 error */\n#define COLAMD_STATUS 3\n\n/* stats [4..6]: error info, or info on jumbled columns */\n#define COLAMD_INFO1 4\n#define COLAMD_INFO2 5\n#define COLAMD_INFO3 6\n\n/* error codes returned in stats [3]: */\n#define COLAMD_OK\t\t\t\t(0)\n#define COLAMD_OK_BUT_JUMBLED\t\t\t(1)\n#define COLAMD_ERROR_A_not_present\t\t(-1)\n#define COLAMD_ERROR_p_not_present\t\t(-2)\n#define COLAMD_ERROR_nrow_negative\t\t(-3)\n#define COLAMD_ERROR_ncol_negative\t\t(-4)\n#define COLAMD_ERROR_nnz_negative\t\t(-5)\n#define COLAMD_ERROR_p0_nonzero\t\t\t(-6)\n#define COLAMD_ERROR_A_too_small\t\t(-7)\n#define COLAMD_ERROR_col_length_negative\t(-8)\n#define COLAMD_ERROR_row_index_out_of_bounds\t(-9)\n#define COLAMD_ERROR_out_of_memory\t\t(-10)\n#define COLAMD_ERROR_internal_error\t\t(-999)\n\n\n\n/* ========================================================================== */\n/* === Row and Column structures ============================================ */\n/* ========================================================================== */\n\n/* User code that makes use of the colamd/symamd routines need not directly */\n/* reference these structures.  They are used only for the COLAMD_RECOMMENDED */\n/* macro. */\n\ntypedef struct Colamd_Col_struct\n{\n    int start ;\t\t/* index for A of first row in this column, or DEAD */\n\t\t\t/* if column is dead */\n    int length ;\t/* number of rows in this column */\n    union\n    {\n\tint thickness ;\t/* number of original columns represented by this */\n\t\t\t/* col, if the column is alive */\n\tint parent ;\t/* parent in parent tree super-column structure, if */\n\t\t\t/* the column is dead */\n    } shared1 ;\n    union\n    {\n\tint score ;\t/* the score used to maintain heap, if col is alive */\n\tint order ;\t/* pivot ordering of this column, if col is dead */\n    } shared2 ;\n    union\n    {\n\tint headhash ;\t/* head of a hash bucket, if col is at the head of */\n\t\t\t/* a degree list */\n\tint hash ;\t/* hash value, if col is not in a degree list */\n\tint prev ;\t/* previous column in degree list, if col is in a */\n\t\t\t/* degree list (but not at the head of a degree list) */\n    } shared3 ;\n    union\n    {\n\tint degree_next ;\t/* next column, if col is in a degree list */\n\tint hash_next ;\t\t/* next column, if col is in a hash list */\n    } shared4 ;\n\n} Colamd_Col ;\n\ntypedef struct Colamd_Row_struct\n{\n    int start ;\t\t/* index for A of first col in this row */\n    int length ;\t/* number of principal columns in this row */\n    union\n    {\n\tint degree ;\t/* number of principal & non-principal columns in row */\n\tint p ;\t\t/* used as a row pointer in init_rows_cols () */\n    } shared1 ;\n    union\n    {\n\tint mark ;\t/* for computing set differences and marking dead rows*/\n\tint first_column ;/* first column in row (used in garbage collection) */\n    } shared2 ;\n\n} Colamd_Row ;\n\n/* ========================================================================== */\n/* === Colamd recommended memory size ======================================= */\n/* ========================================================================== */\n\n/*\n    The recommended length Alen of the array A passed to colamd is given by\n    the COLAMD_RECOMMENDED (nnz, n_row, n_col) macro.  It returns -1 if any\n    argument is negative.  2*nnz space is required for the row and column\n    indices of the matrix. COLAMD_C (n_col) + COLAMD_R (n_row) space is\n    required for the Col and Row arrays, respectively, which are internal to\n    colamd.  An additional n_col space is the minimal amount of \"elbow room\",\n    and nnz/5 more space is recommended for run time efficiency.\n\n    This macro is not needed when using symamd.\n*/\n\n#define COLAMD_C(n_col) (((n_col) + 1) * sizeof (Colamd_Col) / sizeof (int))\n#define COLAMD_R(n_row) (((n_row) + 1) * sizeof (Colamd_Row) / sizeof (int))\n\n#define COLAMD_RECOMMENDED(nnz, n_row, n_col)                                 \\\n(                                                                             \\\n((nnz) < 0 || (n_row) < 0 || (n_col) < 0)                                     \\\n?                                                                             \\\n    (-1)                                                                      \\\n:                                                                             \\\n    (int) (2 * (nnz) + COLAMD_C (n_col) + COLAMD_R (n_row) + (n_col) + ((nnz) / 5)) \\\n)\n\n/* ========================================================================== */\n/* === Prototypes of user-callable routines ================================= */\n/* ========================================================================== */\n\n/*\n#ifdef __cplusplus\n  #define __EXTERN_C extern \"C\"\n#else\n  #define __EXTERN_C\n#endif\n*/\n\n#ifndef __BORLANDC__\n\n  #ifdef __cplusplus\n    #define __EXTERN_C extern \"C\"\n  #else\n    #define __EXTERN_C\n  #endif\n\n#else  /* Otherwise set up for the Borland compiler */\n\n  #define __EXTERN_C extern \"C\"\n\n#endif\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\n\n\nint colamd_recommended\t\t/* returns recommended value of Alen, */\n\t\t\t\t/* or (-1) if input arguments are erroneous */\n(\n    int nnz,\t\t\t/* nonzeros in A */\n    int n_row,\t\t/* number of rows in A */\n    int n_col\t\t\t/* number of columns in A */\n) ;\n\nvoid colamd_set_defaults\t/* sets default parameters */\n(\t\t\t\t/* knobs argument is modified on output */\n    double knobs [COLAMD_KNOBS]\t/* parameter settings for colamd */\n) ;\n\nint colamd\t\t\t/* returns (1) if successful, (0) otherwise*/\n(\t\t\t\t/* A and p arguments are modified on output */\n    int n_row,\t\t/* number of rows in A */\n    int n_col,\t\t/* number of columns in A */\n    int Alen,\t\t\t/* size of the array A */\n    int A [],\t\t\t/* row indices of A, of size Alen */\n    int p [],\t\t\t/* column pointers of A, of size n_col+1 */\n    double knobs [COLAMD_KNOBS],/* parameter settings for colamd */\n    int stats [COLAMD_STATS]\t/* colamd output statistics and error codes */\n) ;\n\nint symamd\t\t\t\t/* return (1) if OK, (0) otherwise */\n(\n    int n,\t\t\t\t/* number of rows and columns of A */\n    int A [],\t\t\t/* row indices of A */\n    int p [],\t\t\t/* column pointers of A */\n    int perm [],\t/* output permutation, size n_col+1 */\n    double knobs [COLAMD_KNOBS],\t/* parameters (uses defaults if NULL) */\n    int stats [COLAMD_STATS],\t\t/* output statistics and error codes */\n    void * (*allocate) (size_t, size_t),\n    \t\t\t\t\t/* pointer to calloc (ANSI C) or */\n\t\t\t\t\t/* mxCalloc (for Matlab mexFunction) */\n    void (*release) (void *)\n    \t\t\t\t\t/* pointer to free (ANSI C) or */\n    \t\t\t\t\t/* mxFree (for Matlab mexFunction) */\n) ;\n\nvoid colamd_report\n(\n    int stats [COLAMD_STATS]\n) ;\n\nvoid symamd_report\n(\n    int stats [COLAMD_STATS]\n) ;\n\n#endif /* COLAMD_H */\n\n\n#ifdef __cplusplus\n}\n#endif\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/configure",
    "content": "#! /bin/sh\n# Guess values for system-dependent variables and create Makefiles.\n# Generated by GNU Autoconf 2.59 for lpsolve 5.5.2.0.\n#\n# Copyright (C) 2003 Free Software Foundation, Inc.\n# This configure script is free software; the Free Software Foundation\n# gives unlimited permission to copy, distribute and modify it.\n## --------------------- ##\n## M4sh Initialization.  ##\n## --------------------- ##\n\n# Be Bourne compatible\nif test -n \"${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then\n  emulate sh\n  NULLCMD=:\n  # Zsh 3.x and 4.x performs word splitting on ${1+\"$@\"}, which\n  # is contrary to our usage.  Disable this feature.\n  alias -g '${1+\"$@\"}'='\"$@\"'\nelif test -n \"${BASH_VERSION+set}\" && (set -o posix) >/dev/null 2>&1; then\n  set -o posix\nfi\nDUALCASE=1; export DUALCASE # for MKS sh\n\n# Support unset when possible.\nif ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then\n  as_unset=unset\nelse\n  as_unset=false\nfi\n\n\n# Work around bugs in pre-3.0 UWIN ksh.\n$as_unset ENV MAIL MAILPATH\nPS1='$ '\nPS2='> '\nPS4='+ '\n\n# NLS nuisances.\nfor as_var in \\\n  LANG LANGUAGE LC_ADDRESS LC_ALL LC_COLLATE LC_CTYPE LC_IDENTIFICATION \\\n  LC_MEASUREMENT LC_MESSAGES LC_MONETARY LC_NAME LC_NUMERIC LC_PAPER \\\n  LC_TELEPHONE LC_TIME\ndo\n  if (set +x; test -z \"`(eval $as_var=C; export $as_var) 2>&1`\"); then\n    eval $as_var=C; export $as_var\n  else\n    $as_unset $as_var\n  fi\ndone\n\n# Required to use basename.\nif expr a : '\\(a\\)' >/dev/null 2>&1; then\n  as_expr=expr\nelse\n  as_expr=false\nfi\n\nif (basename /) >/dev/null 2>&1 && test \"X`basename / 2>&1`\" = \"X/\"; then\n  as_basename=basename\nelse\n  as_basename=false\nfi\n\n\n# Name of the executable.\nas_me=`$as_basename \"$0\" ||\n$as_expr X/\"$0\" : '.*/\\([^/][^/]*\\)/*$' \\| \\\n\t X\"$0\" : 'X\\(//\\)$' \\| \\\n\t X\"$0\" : 'X\\(/\\)$' \\| \\\n\t .     : '\\(.\\)' 2>/dev/null ||\necho X/\"$0\" |\n    sed '/^.*\\/\\([^/][^/]*\\)\\/*$/{ s//\\1/; q; }\n  \t  /^X\\/\\(\\/\\/\\)$/{ s//\\1/; q; }\n  \t  /^X\\/\\(\\/\\).*/{ s//\\1/; q; }\n  \t  s/.*/./; q'`\n\n\n# PATH needs CR, and LINENO needs CR and PATH.\n# Avoid depending upon Character Ranges.\nas_cr_letters='abcdefghijklmnopqrstuvwxyz'\nas_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'\nas_cr_Letters=$as_cr_letters$as_cr_LETTERS\nas_cr_digits='0123456789'\nas_cr_alnum=$as_cr_Letters$as_cr_digits\n\n# The user is always right.\nif test \"${PATH_SEPARATOR+set}\" != set; then\n  echo \"#! /bin/sh\" >conf$$.sh\n  echo  \"exit 0\"   >>conf$$.sh\n  chmod +x conf$$.sh\n  if (PATH=\"/nonexistent;.\"; conf$$.sh) >/dev/null 2>&1; then\n    PATH_SEPARATOR=';'\n  else\n    PATH_SEPARATOR=:\n  fi\n  rm -f conf$$.sh\nfi\n\n\n  as_lineno_1=$LINENO\n  as_lineno_2=$LINENO\n  as_lineno_3=`(expr $as_lineno_1 + 1) 2>/dev/null`\n  test \"x$as_lineno_1\" != \"x$as_lineno_2\" &&\n  test \"x$as_lineno_3\"  = \"x$as_lineno_2\"  || {\n  # Find who we are.  Look in the path if we contain no path at all\n  # relative or not.\n  case $0 in\n    *[\\\\/]* ) as_myself=$0 ;;\n    *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  test -r \"$as_dir/$0\" && as_myself=$as_dir/$0 && break\ndone\n\n       ;;\n  esac\n  # We did not find ourselves, most probably we were run as `sh COMMAND'\n  # in which case we are not to be found in the path.\n  if test \"x$as_myself\" = x; then\n    as_myself=$0\n  fi\n  if test ! -f \"$as_myself\"; then\n    { echo \"$as_me: error: cannot find myself; rerun with an absolute path\" >&2\n   { (exit 1); exit 1; }; }\n  fi\n  case $CONFIG_SHELL in\n  '')\n    as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for as_base in sh bash ksh sh5; do\n\t case $as_dir in\n\t /*)\n\t   if (\"$as_dir/$as_base\" -c '\n  as_lineno_1=$LINENO\n  as_lineno_2=$LINENO\n  as_lineno_3=`(expr $as_lineno_1 + 1) 2>/dev/null`\n  test \"x$as_lineno_1\" != \"x$as_lineno_2\" &&\n  test \"x$as_lineno_3\"  = \"x$as_lineno_2\" ') 2>/dev/null; then\n\t     $as_unset BASH_ENV || test \"${BASH_ENV+set}\" != set || { BASH_ENV=; export BASH_ENV; }\n\t     $as_unset ENV || test \"${ENV+set}\" != set || { ENV=; export ENV; }\n\t     CONFIG_SHELL=$as_dir/$as_base\n\t     export CONFIG_SHELL\n\t     exec \"$CONFIG_SHELL\" \"$0\" ${1+\"$@\"}\n\t   fi;;\n\t esac\n       done\ndone\n;;\n  esac\n\n  # Create $as_me.lineno as a copy of $as_myself, but with $LINENO\n  # uniformly replaced by the line number.  The first 'sed' inserts a\n  # line-number line before each line; the second 'sed' does the real\n  # work.  The second script uses 'N' to pair each line-number line\n  # with the numbered line, and appends trailing '-' during\n  # substitution so that $LINENO is not a special case at line end.\n  # (Raja R Harinath suggested sed '=', and Paul Eggert wrote the\n  # second 'sed' script.  Blame Lee E. McMahon for sed's syntax.  :-)\n  sed '=' <$as_myself |\n    sed '\n      N\n      s,$,-,\n      : loop\n      s,^\\(['$as_cr_digits']*\\)\\(.*\\)[$]LINENO\\([^'$as_cr_alnum'_]\\),\\1\\2\\1\\3,\n      t loop\n      s,-$,,\n      s,^['$as_cr_digits']*\\n,,\n    ' >$as_me.lineno &&\n  chmod +x $as_me.lineno ||\n    { echo \"$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell\" >&2\n   { (exit 1); exit 1; }; }\n\n  # Don't try to exec as it changes $[0], causing all sort of problems\n  # (the dirname of $[0] is not the place where we might find the\n  # original and so on.  Autoconf is especially sensible to this).\n  . ./$as_me.lineno\n  # Exit status is that of the last command.\n  exit\n}\n\n\ncase `echo \"testing\\c\"; echo 1,2,3`,`echo -n testing; echo 1,2,3` in\n  *c*,-n*) ECHO_N= ECHO_C='\n' ECHO_T='\t' ;;\n  *c*,*  ) ECHO_N=-n ECHO_C= ECHO_T= ;;\n  *)       ECHO_N= ECHO_C='\\c' ECHO_T= ;;\nesac\n\nif expr a : '\\(a\\)' >/dev/null 2>&1; then\n  as_expr=expr\nelse\n  as_expr=false\nfi\n\nrm -f conf$$ conf$$.exe conf$$.file\necho >conf$$.file\nif ln -s conf$$.file conf$$ 2>/dev/null; then\n  # We could just check for DJGPP; but this test a) works b) is more generic\n  # and c) will remain valid once DJGPP supports symlinks (DJGPP 2.04).\n  if test -f conf$$.exe; then\n    # Don't use ln at all; we don't have any links\n    as_ln_s='cp -p'\n  else\n    as_ln_s='ln -s'\n  fi\nelif ln conf$$.file conf$$ 2>/dev/null; then\n  as_ln_s=ln\nelse\n  as_ln_s='cp -p'\nfi\nrm -f conf$$ conf$$.exe conf$$.file\n\nif mkdir -p . 2>/dev/null; then\n  as_mkdir_p=:\nelse\n  test -d ./-p && rmdir ./-p\n  as_mkdir_p=false\nfi\n\nas_executable_p=\"test -f\"\n\n# Sed expression to map a string onto a valid CPP name.\nas_tr_cpp=\"eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'\"\n\n# Sed expression to map a string onto a valid variable name.\nas_tr_sh=\"eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'\"\n\n\n# IFS\n# We need space, tab and new line, in precisely that order.\nas_nl='\n'\nIFS=\" \t$as_nl\"\n\n# CDPATH.\n$as_unset CDPATH\n\n\n# Name of the host.\n# hostname on some systems (SVR3.2, Linux) returns a bogus exit status,\n# so uname gets run too.\nac_hostname=`(hostname || uname -n) 2>/dev/null | sed 1q`\n\nexec 6>&1\n\n#\n# Initializations.\n#\nac_default_prefix=/usr/local\nac_config_libobj_dir=.\ncross_compiling=no\nsubdirs=\nMFLAGS=\nMAKEFLAGS=\nSHELL=${CONFIG_SHELL-/bin/sh}\n\n# Maximum number of lines to put in a shell here document.\n# This variable seems obsolete.  It should probably be removed, and\n# only ac_max_sed_lines should be used.\n: ${ac_max_here_lines=38}\n\n# Identity of this package.\nPACKAGE_NAME='lpsolve'\nPACKAGE_TARNAME='lpsolve'\nPACKAGE_VERSION='5.5.2.0'\nPACKAGE_STRING='lpsolve 5.5.2.0'\nPACKAGE_BUGREPORT=''\n\nac_unique_file=\"lp_simplex.c\"\nac_subst_vars='SHELL PATH_SEPARATOR PACKAGE_NAME PACKAGE_TARNAME PACKAGE_VERSION PACKAGE_STRING PACKAGE_BUGREPORT exec_prefix prefix program_transform_name bindir sbindir libexecdir datadir sysconfdir sharedstatedir localstatedir libdir includedir oldincludedir infodir mandir build_alias host_alias target_alias DEFS ECHO_C ECHO_N ECHO_T LIBS build build_cpu build_vendor build_os host host_cpu host_vendor host_os SO CCSHARED DEF SHARED_LIB CC CFLAGS LDFLAGS CPPFLAGS ac_ct_CC EXEEXT OBJEXT INSTALL_PROGRAM INSTALL_SCRIPT INSTALL_DATA LIBOBJS LTLIBOBJS'\nac_subst_files=''\n\n# Initialize some variables set by options.\nac_init_help=\nac_init_version=false\n# The variables have the same names as the options, with\n# dashes changed to underlines.\ncache_file=/dev/null\nexec_prefix=NONE\nno_create=\nno_recursion=\nprefix=NONE\nprogram_prefix=NONE\nprogram_suffix=NONE\nprogram_transform_name=s,x,x,\nsilent=\nsite=\nsrcdir=\nverbose=\nx_includes=NONE\nx_libraries=NONE\n\n# Installation directory options.\n# These are left unexpanded so users can \"make install exec_prefix=/foo\"\n# and all the variables that are supposed to be based on exec_prefix\n# by default will actually change.\n# Use braces instead of parens because sh, perl, etc. also accept them.\nbindir='${exec_prefix}/bin'\nsbindir='${exec_prefix}/sbin'\nlibexecdir='${exec_prefix}/libexec'\ndatadir='${prefix}/share'\nsysconfdir='${prefix}/etc'\nsharedstatedir='${prefix}/com'\nlocalstatedir='${prefix}/var'\nlibdir='${exec_prefix}/lib'\nincludedir='${prefix}/include'\noldincludedir='/usr/include'\ninfodir='${prefix}/info'\nmandir='${prefix}/man'\n\nac_prev=\nfor ac_option\ndo\n  # If the previous option needs an argument, assign it.\n  if test -n \"$ac_prev\"; then\n    eval \"$ac_prev=\\$ac_option\"\n    ac_prev=\n    continue\n  fi\n\n  ac_optarg=`expr \"x$ac_option\" : 'x[^=]*=\\(.*\\)'`\n\n  # Accept the important Cygnus configure options, so we can diagnose typos.\n\n  case $ac_option in\n\n  -bindir | --bindir | --bindi | --bind | --bin | --bi)\n    ac_prev=bindir ;;\n  -bindir=* | --bindir=* | --bindi=* | --bind=* | --bin=* | --bi=*)\n    bindir=$ac_optarg ;;\n\n  -build | --build | --buil | --bui | --bu)\n    ac_prev=build_alias ;;\n  -build=* | --build=* | --buil=* | --bui=* | --bu=*)\n    build_alias=$ac_optarg ;;\n\n  -cache-file | --cache-file | --cache-fil | --cache-fi \\\n  | --cache-f | --cache- | --cache | --cach | --cac | --ca | --c)\n    ac_prev=cache_file ;;\n  -cache-file=* | --cache-file=* | --cache-fil=* | --cache-fi=* \\\n  | --cache-f=* | --cache-=* | --cache=* | --cach=* | --cac=* | --ca=* | --c=*)\n    cache_file=$ac_optarg ;;\n\n  --config-cache | -C)\n    cache_file=config.cache ;;\n\n  -datadir | --datadir | --datadi | --datad | --data | --dat | --da)\n    ac_prev=datadir ;;\n  -datadir=* | --datadir=* | --datadi=* | --datad=* | --data=* | --dat=* \\\n  | --da=*)\n    datadir=$ac_optarg ;;\n\n  -disable-* | --disable-*)\n    ac_feature=`expr \"x$ac_option\" : 'x-*disable-\\(.*\\)'`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_feature\" : \".*[^-_$as_cr_alnum]\" >/dev/null &&\n      { echo \"$as_me: error: invalid feature name: $ac_feature\" >&2\n   { (exit 1); exit 1; }; }\n    ac_feature=`echo $ac_feature | sed 's/-/_/g'`\n    eval \"enable_$ac_feature=no\" ;;\n\n  -enable-* | --enable-*)\n    ac_feature=`expr \"x$ac_option\" : 'x-*enable-\\([^=]*\\)'`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_feature\" : \".*[^-_$as_cr_alnum]\" >/dev/null &&\n      { echo \"$as_me: error: invalid feature name: $ac_feature\" >&2\n   { (exit 1); exit 1; }; }\n    ac_feature=`echo $ac_feature | sed 's/-/_/g'`\n    case $ac_option in\n      *=*) ac_optarg=`echo \"$ac_optarg\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"`;;\n      *) ac_optarg=yes ;;\n    esac\n    eval \"enable_$ac_feature='$ac_optarg'\" ;;\n\n  -exec-prefix | --exec_prefix | --exec-prefix | --exec-prefi \\\n  | --exec-pref | --exec-pre | --exec-pr | --exec-p | --exec- \\\n  | --exec | --exe | --ex)\n    ac_prev=exec_prefix ;;\n  -exec-prefix=* | --exec_prefix=* | --exec-prefix=* | --exec-prefi=* \\\n  | --exec-pref=* | --exec-pre=* | --exec-pr=* | --exec-p=* | --exec-=* \\\n  | --exec=* | --exe=* | --ex=*)\n    exec_prefix=$ac_optarg ;;\n\n  -gas | --gas | --ga | --g)\n    # Obsolete; use --with-gas.\n    with_gas=yes ;;\n\n  -help | --help | --hel | --he | -h)\n    ac_init_help=long ;;\n  -help=r* | --help=r* | --hel=r* | --he=r* | -hr*)\n    ac_init_help=recursive ;;\n  -help=s* | --help=s* | --hel=s* | --he=s* | -hs*)\n    ac_init_help=short ;;\n\n  -host | --host | --hos | --ho)\n    ac_prev=host_alias ;;\n  -host=* | --host=* | --hos=* | --ho=*)\n    host_alias=$ac_optarg ;;\n\n  -includedir | --includedir | --includedi | --included | --include \\\n  | --includ | --inclu | --incl | --inc)\n    ac_prev=includedir ;;\n  -includedir=* | --includedir=* | --includedi=* | --included=* | --include=* \\\n  | --includ=* | --inclu=* | --incl=* | --inc=*)\n    includedir=$ac_optarg ;;\n\n  -infodir | --infodir | --infodi | --infod | --info | --inf)\n    ac_prev=infodir ;;\n  -infodir=* | --infodir=* | --infodi=* | --infod=* | --info=* | --inf=*)\n    infodir=$ac_optarg ;;\n\n  -libdir | --libdir | --libdi | --libd)\n    ac_prev=libdir ;;\n  -libdir=* | --libdir=* | --libdi=* | --libd=*)\n    libdir=$ac_optarg ;;\n\n  -libexecdir | --libexecdir | --libexecdi | --libexecd | --libexec \\\n  | --libexe | --libex | --libe)\n    ac_prev=libexecdir ;;\n  -libexecdir=* | --libexecdir=* | --libexecdi=* | --libexecd=* | --libexec=* \\\n  | --libexe=* | --libex=* | --libe=*)\n    libexecdir=$ac_optarg ;;\n\n  -localstatedir | --localstatedir | --localstatedi | --localstated \\\n  | --localstate | --localstat | --localsta | --localst \\\n  | --locals | --local | --loca | --loc | --lo)\n    ac_prev=localstatedir ;;\n  -localstatedir=* | --localstatedir=* | --localstatedi=* | --localstated=* \\\n  | --localstate=* | --localstat=* | --localsta=* | --localst=* \\\n  | --locals=* | --local=* | --loca=* | --loc=* | --lo=*)\n    localstatedir=$ac_optarg ;;\n\n  -mandir | --mandir | --mandi | --mand | --man | --ma | --m)\n    ac_prev=mandir ;;\n  -mandir=* | --mandir=* | --mandi=* | --mand=* | --man=* | --ma=* | --m=*)\n    mandir=$ac_optarg ;;\n\n  -nfp | --nfp | --nf)\n    # Obsolete; use --without-fp.\n    with_fp=no ;;\n\n  -no-create | --no-create | --no-creat | --no-crea | --no-cre \\\n  | --no-cr | --no-c | -n)\n    no_create=yes ;;\n\n  -no-recursion | --no-recursion | --no-recursio | --no-recursi \\\n  | --no-recurs | --no-recur | --no-recu | --no-rec | --no-re | --no-r)\n    no_recursion=yes ;;\n\n  -oldincludedir | --oldincludedir | --oldincludedi | --oldincluded \\\n  | --oldinclude | --oldinclud | --oldinclu | --oldincl | --oldinc \\\n  | --oldin | --oldi | --old | --ol | --o)\n    ac_prev=oldincludedir ;;\n  -oldincludedir=* | --oldincludedir=* | --oldincludedi=* | --oldincluded=* \\\n  | --oldinclude=* | --oldinclud=* | --oldinclu=* | --oldincl=* | --oldinc=* \\\n  | --oldin=* | --oldi=* | --old=* | --ol=* | --o=*)\n    oldincludedir=$ac_optarg ;;\n\n  -prefix | --prefix | --prefi | --pref | --pre | --pr | --p)\n    ac_prev=prefix ;;\n  -prefix=* | --prefix=* | --prefi=* | --pref=* | --pre=* | --pr=* | --p=*)\n    prefix=$ac_optarg ;;\n\n  -program-prefix | --program-prefix | --program-prefi | --program-pref \\\n  | --program-pre | --program-pr | --program-p)\n    ac_prev=program_prefix ;;\n  -program-prefix=* | --program-prefix=* | --program-prefi=* \\\n  | --program-pref=* | --program-pre=* | --program-pr=* | --program-p=*)\n    program_prefix=$ac_optarg ;;\n\n  -program-suffix | --program-suffix | --program-suffi | --program-suff \\\n  | --program-suf | --program-su | --program-s)\n    ac_prev=program_suffix ;;\n  -program-suffix=* | --program-suffix=* | --program-suffi=* \\\n  | --program-suff=* | --program-suf=* | --program-su=* | --program-s=*)\n    program_suffix=$ac_optarg ;;\n\n  -program-transform-name | --program-transform-name \\\n  | --program-transform-nam | --program-transform-na \\\n  | --program-transform-n | --program-transform- \\\n  | --program-transform | --program-transfor \\\n  | --program-transfo | --program-transf \\\n  | --program-trans | --program-tran \\\n  | --progr-tra | --program-tr | --program-t)\n    ac_prev=program_transform_name ;;\n  -program-transform-name=* | --program-transform-name=* \\\n  | --program-transform-nam=* | --program-transform-na=* \\\n  | --program-transform-n=* | --program-transform-=* \\\n  | --program-transform=* | --program-transfor=* \\\n  | --program-transfo=* | --program-transf=* \\\n  | --program-trans=* | --program-tran=* \\\n  | --progr-tra=* | --program-tr=* | --program-t=*)\n    program_transform_name=$ac_optarg ;;\n\n  -q | -quiet | --quiet | --quie | --qui | --qu | --q \\\n  | -silent | --silent | --silen | --sile | --sil)\n    silent=yes ;;\n\n  -sbindir | --sbindir | --sbindi | --sbind | --sbin | --sbi | --sb)\n    ac_prev=sbindir ;;\n  -sbindir=* | --sbindir=* | --sbindi=* | --sbind=* | --sbin=* \\\n  | --sbi=* | --sb=*)\n    sbindir=$ac_optarg ;;\n\n  -sharedstatedir | --sharedstatedir | --sharedstatedi \\\n  | --sharedstated | --sharedstate | --sharedstat | --sharedsta \\\n  | --sharedst | --shareds | --shared | --share | --shar \\\n  | --sha | --sh)\n    ac_prev=sharedstatedir ;;\n  -sharedstatedir=* | --sharedstatedir=* | --sharedstatedi=* \\\n  | --sharedstated=* | --sharedstate=* | --sharedstat=* | --sharedsta=* \\\n  | --sharedst=* | --shareds=* | --shared=* | --share=* | --shar=* \\\n  | --sha=* | --sh=*)\n    sharedstatedir=$ac_optarg ;;\n\n  -site | --site | --sit)\n    ac_prev=site ;;\n  -site=* | --site=* | --sit=*)\n    site=$ac_optarg ;;\n\n  -srcdir | --srcdir | --srcdi | --srcd | --src | --sr)\n    ac_prev=srcdir ;;\n  -srcdir=* | --srcdir=* | --srcdi=* | --srcd=* | --src=* | --sr=*)\n    srcdir=$ac_optarg ;;\n\n  -sysconfdir | --sysconfdir | --sysconfdi | --sysconfd | --sysconf \\\n  | --syscon | --sysco | --sysc | --sys | --sy)\n    ac_prev=sysconfdir ;;\n  -sysconfdir=* | --sysconfdir=* | --sysconfdi=* | --sysconfd=* | --sysconf=* \\\n  | --syscon=* | --sysco=* | --sysc=* | --sys=* | --sy=*)\n    sysconfdir=$ac_optarg ;;\n\n  -target | --target | --targe | --targ | --tar | --ta | --t)\n    ac_prev=target_alias ;;\n  -target=* | --target=* | --targe=* | --targ=* | --tar=* | --ta=* | --t=*)\n    target_alias=$ac_optarg ;;\n\n  -v | -verbose | --verbose | --verbos | --verbo | --verb)\n    verbose=yes ;;\n\n  -version | --version | --versio | --versi | --vers | -V)\n    ac_init_version=: ;;\n\n  -with-* | --with-*)\n    ac_package=`expr \"x$ac_option\" : 'x-*with-\\([^=]*\\)'`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_package\" : \".*[^-_$as_cr_alnum]\" >/dev/null &&\n      { echo \"$as_me: error: invalid package name: $ac_package\" >&2\n   { (exit 1); exit 1; }; }\n    ac_package=`echo $ac_package| sed 's/-/_/g'`\n    case $ac_option in\n      *=*) ac_optarg=`echo \"$ac_optarg\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"`;;\n      *) ac_optarg=yes ;;\n    esac\n    eval \"with_$ac_package='$ac_optarg'\" ;;\n\n  -without-* | --without-*)\n    ac_package=`expr \"x$ac_option\" : 'x-*without-\\(.*\\)'`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_package\" : \".*[^-_$as_cr_alnum]\" >/dev/null &&\n      { echo \"$as_me: error: invalid package name: $ac_package\" >&2\n   { (exit 1); exit 1; }; }\n    ac_package=`echo $ac_package | sed 's/-/_/g'`\n    eval \"with_$ac_package=no\" ;;\n\n  --x)\n    # Obsolete; use --with-x.\n    with_x=yes ;;\n\n  -x-includes | --x-includes | --x-include | --x-includ | --x-inclu \\\n  | --x-incl | --x-inc | --x-in | --x-i)\n    ac_prev=x_includes ;;\n  -x-includes=* | --x-includes=* | --x-include=* | --x-includ=* | --x-inclu=* \\\n  | --x-incl=* | --x-inc=* | --x-in=* | --x-i=*)\n    x_includes=$ac_optarg ;;\n\n  -x-libraries | --x-libraries | --x-librarie | --x-librari \\\n  | --x-librar | --x-libra | --x-libr | --x-lib | --x-li | --x-l)\n    ac_prev=x_libraries ;;\n  -x-libraries=* | --x-libraries=* | --x-librarie=* | --x-librari=* \\\n  | --x-librar=* | --x-libra=* | --x-libr=* | --x-lib=* | --x-li=* | --x-l=*)\n    x_libraries=$ac_optarg ;;\n\n  -*) { echo \"$as_me: error: unrecognized option: $ac_option\nTry \\`$0 --help' for more information.\" >&2\n   { (exit 1); exit 1; }; }\n    ;;\n\n  *=*)\n    ac_envvar=`expr \"x$ac_option\" : 'x\\([^=]*\\)='`\n    # Reject names that are not valid shell variable names.\n    expr \"x$ac_envvar\" : \".*[^_$as_cr_alnum]\" >/dev/null &&\n      { echo \"$as_me: error: invalid variable name: $ac_envvar\" >&2\n   { (exit 1); exit 1; }; }\n    ac_optarg=`echo \"$ac_optarg\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"`\n    eval \"$ac_envvar='$ac_optarg'\"\n    export $ac_envvar ;;\n\n  *)\n    # FIXME: should be removed in autoconf 3.0.\n    echo \"$as_me: WARNING: you should use --build, --host, --target\" >&2\n    expr \"x$ac_option\" : \".*[^-._$as_cr_alnum]\" >/dev/null &&\n      echo \"$as_me: WARNING: invalid host type: $ac_option\" >&2\n    : ${build_alias=$ac_option} ${host_alias=$ac_option} ${target_alias=$ac_option}\n    ;;\n\n  esac\ndone\n\nif test -n \"$ac_prev\"; then\n  ac_option=--`echo $ac_prev | sed 's/_/-/g'`\n  { echo \"$as_me: error: missing argument to $ac_option\" >&2\n   { (exit 1); exit 1; }; }\nfi\n\n# Be sure to have absolute paths.\nfor ac_var in exec_prefix prefix\ndo\n  eval ac_val=$`echo $ac_var`\n  case $ac_val in\n    [\\\\/$]* | ?:[\\\\/]* | NONE | '' ) ;;\n    *)  { echo \"$as_me: error: expected an absolute directory name for --$ac_var: $ac_val\" >&2\n   { (exit 1); exit 1; }; };;\n  esac\ndone\n\n# Be sure to have absolute paths.\nfor ac_var in bindir sbindir libexecdir datadir sysconfdir sharedstatedir \\\n\t      localstatedir libdir includedir oldincludedir infodir mandir\ndo\n  eval ac_val=$`echo $ac_var`\n  case $ac_val in\n    [\\\\/$]* | ?:[\\\\/]* ) ;;\n    *)  { echo \"$as_me: error: expected an absolute directory name for --$ac_var: $ac_val\" >&2\n   { (exit 1); exit 1; }; };;\n  esac\ndone\n\n# There might be people who depend on the old broken behavior: `$host'\n# used to hold the argument of --host etc.\n# FIXME: To remove some day.\nbuild=$build_alias\nhost=$host_alias\ntarget=$target_alias\n\n# FIXME: To remove some day.\nif test \"x$host_alias\" != x; then\n  if test \"x$build_alias\" = x; then\n    cross_compiling=maybe\n    echo \"$as_me: WARNING: If you wanted to set the --build type, don't use --host.\n    If a cross compiler is detected then cross compile mode will be used.\" >&2\n  elif test \"x$build_alias\" != \"x$host_alias\"; then\n    cross_compiling=yes\n  fi\nfi\n\nac_tool_prefix=\ntest -n \"$host_alias\" && ac_tool_prefix=$host_alias-\n\ntest \"$silent\" = yes && exec 6>/dev/null\n\n\n# Find the source files, if location was not specified.\nif test -z \"$srcdir\"; then\n  ac_srcdir_defaulted=yes\n  # Try the directory containing this script, then its parent.\n  ac_confdir=`(dirname \"$0\") 2>/dev/null ||\n$as_expr X\"$0\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$0\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$0\" : 'X\\(//\\)$' \\| \\\n\t X\"$0\" : 'X\\(/\\)' \\| \\\n\t .     : '\\(.\\)' 2>/dev/null ||\necho X\"$0\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\/\\)[^/].*/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\/\\)$/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\).*/{ s//\\1/; q; }\n  \t  s/.*/./; q'`\n  srcdir=$ac_confdir\n  if test ! -r $srcdir/$ac_unique_file; then\n    srcdir=..\n  fi\nelse\n  ac_srcdir_defaulted=no\nfi\nif test ! -r $srcdir/$ac_unique_file; then\n  if test \"$ac_srcdir_defaulted\" = yes; then\n    { echo \"$as_me: error: cannot find sources ($ac_unique_file) in $ac_confdir or ..\" >&2\n   { (exit 1); exit 1; }; }\n  else\n    { echo \"$as_me: error: cannot find sources ($ac_unique_file) in $srcdir\" >&2\n   { (exit 1); exit 1; }; }\n  fi\nfi\n(cd $srcdir && test -r ./$ac_unique_file) 2>/dev/null ||\n  { echo \"$as_me: error: sources are in $srcdir, but \\`cd $srcdir' does not work\" >&2\n   { (exit 1); exit 1; }; }\nsrcdir=`echo \"$srcdir\" | sed 's%\\([^\\\\/]\\)[\\\\/]*$%\\1%'`\nac_env_build_alias_set=${build_alias+set}\nac_env_build_alias_value=$build_alias\nac_cv_env_build_alias_set=${build_alias+set}\nac_cv_env_build_alias_value=$build_alias\nac_env_host_alias_set=${host_alias+set}\nac_env_host_alias_value=$host_alias\nac_cv_env_host_alias_set=${host_alias+set}\nac_cv_env_host_alias_value=$host_alias\nac_env_target_alias_set=${target_alias+set}\nac_env_target_alias_value=$target_alias\nac_cv_env_target_alias_set=${target_alias+set}\nac_cv_env_target_alias_value=$target_alias\nac_env_CC_set=${CC+set}\nac_env_CC_value=$CC\nac_cv_env_CC_set=${CC+set}\nac_cv_env_CC_value=$CC\nac_env_CFLAGS_set=${CFLAGS+set}\nac_env_CFLAGS_value=$CFLAGS\nac_cv_env_CFLAGS_set=${CFLAGS+set}\nac_cv_env_CFLAGS_value=$CFLAGS\nac_env_LDFLAGS_set=${LDFLAGS+set}\nac_env_LDFLAGS_value=$LDFLAGS\nac_cv_env_LDFLAGS_set=${LDFLAGS+set}\nac_cv_env_LDFLAGS_value=$LDFLAGS\nac_env_CPPFLAGS_set=${CPPFLAGS+set}\nac_env_CPPFLAGS_value=$CPPFLAGS\nac_cv_env_CPPFLAGS_set=${CPPFLAGS+set}\nac_cv_env_CPPFLAGS_value=$CPPFLAGS\n\n#\n# Report the --help message.\n#\nif test \"$ac_init_help\" = \"long\"; then\n  # Omit some internal or obsolete options to make the list less imposing.\n  # This message is too long to be a string in the A/UX 3.1 sh.\n  cat <<_ACEOF\n\\`configure' configures lpsolve 5.5.2.0 to adapt to many kinds of systems.\n\nUsage: $0 [OPTION]... [VAR=VALUE]...\n\nTo assign environment variables (e.g., CC, CFLAGS...), specify them as\nVAR=VALUE.  See below for descriptions of some of the useful variables.\n\nDefaults for the options are specified in brackets.\n\nConfiguration:\n  -h, --help              display this help and exit\n      --help=short        display options specific to this package\n      --help=recursive    display the short help of all the included packages\n  -V, --version           display version information and exit\n  -q, --quiet, --silent   do not print \\`checking...' messages\n      --cache-file=FILE   cache test results in FILE [disabled]\n  -C, --config-cache      alias for \\`--cache-file=config.cache'\n  -n, --no-create         do not create output files\n      --srcdir=DIR        find the sources in DIR [configure dir or \\`..']\n\n_ACEOF\n\n  cat <<_ACEOF\nInstallation directories:\n  --prefix=PREFIX         install architecture-independent files in PREFIX\n\t\t\t  [$ac_default_prefix]\n  --exec-prefix=EPREFIX   install architecture-dependent files in EPREFIX\n\t\t\t  [PREFIX]\n\nBy default, \\`make install' will install all the files in\n\\`$ac_default_prefix/bin', \\`$ac_default_prefix/lib' etc.  You can specify\nan installation prefix other than \\`$ac_default_prefix' using \\`--prefix',\nfor instance \\`--prefix=\\$HOME'.\n\nFor better control, use the options below.\n\nFine tuning of the installation directories:\n  --bindir=DIR           user executables [EPREFIX/bin]\n  --sbindir=DIR          system admin executables [EPREFIX/sbin]\n  --libexecdir=DIR       program executables [EPREFIX/libexec]\n  --datadir=DIR          read-only architecture-independent data [PREFIX/share]\n  --sysconfdir=DIR       read-only single-machine data [PREFIX/etc]\n  --sharedstatedir=DIR   modifiable architecture-independent data [PREFIX/com]\n  --localstatedir=DIR    modifiable single-machine data [PREFIX/var]\n  --libdir=DIR           object code libraries [EPREFIX/lib]\n  --includedir=DIR       C header files [PREFIX/include]\n  --oldincludedir=DIR    C header files for non-gcc [/usr/include]\n  --infodir=DIR          info documentation [PREFIX/info]\n  --mandir=DIR           man documentation [PREFIX/man]\n_ACEOF\n\n  cat <<\\_ACEOF\n\nSystem types:\n  --build=BUILD     configure for building on BUILD [guessed]\n  --host=HOST       cross-compile to build programs to run on HOST [BUILD]\n_ACEOF\nfi\n\nif test -n \"$ac_init_help\"; then\n  case $ac_init_help in\n     short | recursive ) echo \"Configuration of lpsolve 5.5.2.0:\";;\n   esac\n  cat <<\\_ACEOF\n\nSome influential environment variables:\n  CC          C compiler command\n  CFLAGS      C compiler flags\n  LDFLAGS     linker flags, e.g. -L<lib dir> if you have libraries in a\n              nonstandard directory <lib dir>\n  CPPFLAGS    C/C++ preprocessor flags, e.g. -I<include dir> if you have\n              headers in a nonstandard directory <include dir>\n\nUse these variables to override the choices made by `configure' or to help\nit to find libraries and programs with nonstandard names/locations.\n\n_ACEOF\nfi\n\nif test \"$ac_init_help\" = \"recursive\"; then\n  # If there are subdirs, report their specific --help.\n  ac_popdir=`pwd`\n  for ac_dir in : $ac_subdirs_all; do test \"x$ac_dir\" = x: && continue\n    test -d $ac_dir || continue\n    ac_builddir=.\n\nif test \"$ac_dir\" != .; then\n  ac_dir_suffix=/`echo \"$ac_dir\" | sed 's,^\\.[\\\\/],,'`\n  # A \"../\" for each directory in $ac_dir_suffix.\n  ac_top_builddir=`echo \"$ac_dir_suffix\" | sed 's,/[^\\\\/]*,../,g'`\nelse\n  ac_dir_suffix= ac_top_builddir=\nfi\n\ncase $srcdir in\n  .)  # No --srcdir option.  We are building in place.\n    ac_srcdir=.\n    if test -z \"$ac_top_builddir\"; then\n       ac_top_srcdir=.\n    else\n       ac_top_srcdir=`echo $ac_top_builddir | sed 's,/$,,'`\n    fi ;;\n  [\\\\/]* | ?:[\\\\/]* )  # Absolute path.\n    ac_srcdir=$srcdir$ac_dir_suffix;\n    ac_top_srcdir=$srcdir ;;\n  *) # Relative path.\n    ac_srcdir=$ac_top_builddir$srcdir$ac_dir_suffix\n    ac_top_srcdir=$ac_top_builddir$srcdir ;;\nesac\n\n# Do not use `cd foo && pwd` to compute absolute paths, because\n# the directories may not exist.\ncase `pwd` in\n.) ac_abs_builddir=\"$ac_dir\";;\n*)\n  case \"$ac_dir\" in\n  .) ac_abs_builddir=`pwd`;;\n  [\\\\/]* | ?:[\\\\/]* ) ac_abs_builddir=\"$ac_dir\";;\n  *) ac_abs_builddir=`pwd`/\"$ac_dir\";;\n  esac;;\nesac\ncase $ac_abs_builddir in\n.) ac_abs_top_builddir=${ac_top_builddir}.;;\n*)\n  case ${ac_top_builddir}. in\n  .) ac_abs_top_builddir=$ac_abs_builddir;;\n  [\\\\/]* | ?:[\\\\/]* ) ac_abs_top_builddir=${ac_top_builddir}.;;\n  *) ac_abs_top_builddir=$ac_abs_builddir/${ac_top_builddir}.;;\n  esac;;\nesac\ncase $ac_abs_builddir in\n.) ac_abs_srcdir=$ac_srcdir;;\n*)\n  case $ac_srcdir in\n  .) ac_abs_srcdir=$ac_abs_builddir;;\n  [\\\\/]* | ?:[\\\\/]* ) ac_abs_srcdir=$ac_srcdir;;\n  *) ac_abs_srcdir=$ac_abs_builddir/$ac_srcdir;;\n  esac;;\nesac\ncase $ac_abs_builddir in\n.) ac_abs_top_srcdir=$ac_top_srcdir;;\n*)\n  case $ac_top_srcdir in\n  .) ac_abs_top_srcdir=$ac_abs_builddir;;\n  [\\\\/]* | ?:[\\\\/]* ) ac_abs_top_srcdir=$ac_top_srcdir;;\n  *) ac_abs_top_srcdir=$ac_abs_builddir/$ac_top_srcdir;;\n  esac;;\nesac\n\n    cd $ac_dir\n    # Check for guested configure; otherwise get Cygnus style configure.\n    if test -f $ac_srcdir/configure.gnu; then\n      echo\n      $SHELL $ac_srcdir/configure.gnu  --help=recursive\n    elif test -f $ac_srcdir/configure; then\n      echo\n      $SHELL $ac_srcdir/configure  --help=recursive\n    elif test -f $ac_srcdir/configure.ac ||\n\t   test -f $ac_srcdir/configure.in; then\n      echo\n      $ac_configure --help\n    else\n      echo \"$as_me: WARNING: no configuration information is in $ac_dir\" >&2\n    fi\n    cd $ac_popdir\n  done\nfi\n\ntest -n \"$ac_init_help\" && exit 0\nif $ac_init_version; then\n  cat <<\\_ACEOF\nlpsolve configure 5.5.2.0\ngenerated by GNU Autoconf 2.59\n\nCopyright (C) 2003 Free Software Foundation, Inc.\nThis configure script is free software; the Free Software Foundation\ngives unlimited permission to copy, distribute and modify it.\n_ACEOF\n  exit 0\nfi\nexec 5>config.log\ncat >&5 <<_ACEOF\nThis file contains any messages produced by compilers while\nrunning configure, to aid debugging if configure makes a mistake.\n\nIt was created by lpsolve $as_me 5.5.2.0, which was\ngenerated by GNU Autoconf 2.59.  Invocation command line was\n\n  $ $0 $@\n\n_ACEOF\n{\ncat <<_ASUNAME\n## --------- ##\n## Platform. ##\n## --------- ##\n\nhostname = `(hostname || uname -n) 2>/dev/null | sed 1q`\nuname -m = `(uname -m) 2>/dev/null || echo unknown`\nuname -r = `(uname -r) 2>/dev/null || echo unknown`\nuname -s = `(uname -s) 2>/dev/null || echo unknown`\nuname -v = `(uname -v) 2>/dev/null || echo unknown`\n\n/usr/bin/uname -p = `(/usr/bin/uname -p) 2>/dev/null || echo unknown`\n/bin/uname -X     = `(/bin/uname -X) 2>/dev/null     || echo unknown`\n\n/bin/arch              = `(/bin/arch) 2>/dev/null              || echo unknown`\n/usr/bin/arch -k       = `(/usr/bin/arch -k) 2>/dev/null       || echo unknown`\n/usr/convex/getsysinfo = `(/usr/convex/getsysinfo) 2>/dev/null || echo unknown`\nhostinfo               = `(hostinfo) 2>/dev/null               || echo unknown`\n/bin/machine           = `(/bin/machine) 2>/dev/null           || echo unknown`\n/usr/bin/oslevel       = `(/usr/bin/oslevel) 2>/dev/null       || echo unknown`\n/bin/universe          = `(/bin/universe) 2>/dev/null          || echo unknown`\n\n_ASUNAME\n\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  echo \"PATH: $as_dir\"\ndone\n\n} >&5\n\ncat >&5 <<_ACEOF\n\n\n## ----------- ##\n## Core tests. ##\n## ----------- ##\n\n_ACEOF\n\n\n# Keep a trace of the command line.\n# Strip out --no-create and --no-recursion so they do not pile up.\n# Strip out --silent because we don't want to record it for future runs.\n# Also quote any args containing shell meta-characters.\n# Make two passes to allow for proper duplicate-argument suppression.\nac_configure_args=\nac_configure_args0=\nac_configure_args1=\nac_sep=\nac_must_keep_next=false\nfor ac_pass in 1 2\ndo\n  for ac_arg\n  do\n    case $ac_arg in\n    -no-create | --no-c* | -n | -no-recursion | --no-r*) continue ;;\n    -q | -quiet | --quiet | --quie | --qui | --qu | --q \\\n    | -silent | --silent | --silen | --sile | --sil)\n      continue ;;\n    *\" \"*|*\"\t\"*|*[\\[\\]\\~\\#\\$\\^\\&\\*\\(\\)\\{\\}\\\\\\|\\;\\<\\>\\?\\\"\\']*)\n      ac_arg=`echo \"$ac_arg\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"` ;;\n    esac\n    case $ac_pass in\n    1) ac_configure_args0=\"$ac_configure_args0 '$ac_arg'\" ;;\n    2)\n      ac_configure_args1=\"$ac_configure_args1 '$ac_arg'\"\n      if test $ac_must_keep_next = true; then\n\tac_must_keep_next=false # Got value, back to normal.\n      else\n\tcase $ac_arg in\n\t  *=* | --config-cache | -C | -disable-* | --disable-* \\\n\t  | -enable-* | --enable-* | -gas | --g* | -nfp | --nf* \\\n\t  | -q | -quiet | --q* | -silent | --sil* | -v | -verb* \\\n\t  | -with-* | --with-* | -without-* | --without-* | --x)\n\t    case \"$ac_configure_args0 \" in\n\t      \"$ac_configure_args1\"*\" '$ac_arg' \"* ) continue ;;\n\t    esac\n\t    ;;\n\t  -* ) ac_must_keep_next=true ;;\n\tesac\n      fi\n      ac_configure_args=\"$ac_configure_args$ac_sep'$ac_arg'\"\n      # Get rid of the leading space.\n      ac_sep=\" \"\n      ;;\n    esac\n  done\ndone\n$as_unset ac_configure_args0 || test \"${ac_configure_args0+set}\" != set || { ac_configure_args0=; export ac_configure_args0; }\n$as_unset ac_configure_args1 || test \"${ac_configure_args1+set}\" != set || { ac_configure_args1=; export ac_configure_args1; }\n\n# When interrupted or exit'd, cleanup temporary files, and complete\n# config.log.  We remove comments because anyway the quotes in there\n# would cause problems or look ugly.\n# WARNING: Be sure not to use single quotes in there, as some shells,\n# such as our DU 5.0 friend, will then `close' the trap.\ntrap 'exit_status=$?\n  # Save into config.log some information that might help in debugging.\n  {\n    echo\n\n    cat <<\\_ASBOX\n## ---------------- ##\n## Cache variables. ##\n## ---------------- ##\n_ASBOX\n    echo\n    # The following way of writing the cache mishandles newlines in values,\n{\n  (set) 2>&1 |\n    case `(ac_space='\"'\"' '\"'\"'; set | grep ac_space) 2>&1` in\n    *ac_space=\\ *)\n      sed -n \\\n\t\"s/'\"'\"'/'\"'\"'\\\\\\\\'\"'\"''\"'\"'/g;\n\t  s/^\\\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\\\)=\\\\(.*\\\\)/\\\\1='\"'\"'\\\\2'\"'\"'/p\"\n      ;;\n    *)\n      sed -n \\\n\t\"s/^\\\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\\\)=\\\\(.*\\\\)/\\\\1=\\\\2/p\"\n      ;;\n    esac;\n}\n    echo\n\n    cat <<\\_ASBOX\n## ----------------- ##\n## Output variables. ##\n## ----------------- ##\n_ASBOX\n    echo\n    for ac_var in $ac_subst_vars\n    do\n      eval ac_val=$`echo $ac_var`\n      echo \"$ac_var='\"'\"'$ac_val'\"'\"'\"\n    done | sort\n    echo\n\n    if test -n \"$ac_subst_files\"; then\n      cat <<\\_ASBOX\n## ------------- ##\n## Output files. ##\n## ------------- ##\n_ASBOX\n      echo\n      for ac_var in $ac_subst_files\n      do\n\teval ac_val=$`echo $ac_var`\n\techo \"$ac_var='\"'\"'$ac_val'\"'\"'\"\n      done | sort\n      echo\n    fi\n\n    if test -s confdefs.h; then\n      cat <<\\_ASBOX\n## ----------- ##\n## confdefs.h. ##\n## ----------- ##\n_ASBOX\n      echo\n      sed \"/^$/d\" confdefs.h | sort\n      echo\n    fi\n    test \"$ac_signal\" != 0 &&\n      echo \"$as_me: caught signal $ac_signal\"\n    echo \"$as_me: exit $exit_status\"\n  } >&5\n  rm -f core *.core &&\n  rm -rf conftest* confdefs* conf$$* $ac_clean_files &&\n    exit $exit_status\n     ' 0\nfor ac_signal in 1 2 13 15; do\n  trap 'ac_signal='$ac_signal'; { (exit 1); exit 1; }' $ac_signal\ndone\nac_signal=0\n\n# confdefs.h avoids OS command line length limits that DEFS can exceed.\nrm -rf conftest* confdefs.h\n# AIX cpp loses on an empty file, so make sure it contains at least a newline.\necho >confdefs.h\n\n# Predefined preprocessor variables.\n\ncat >>confdefs.h <<_ACEOF\n#define PACKAGE_NAME \"$PACKAGE_NAME\"\n_ACEOF\n\n\ncat >>confdefs.h <<_ACEOF\n#define PACKAGE_TARNAME \"$PACKAGE_TARNAME\"\n_ACEOF\n\n\ncat >>confdefs.h <<_ACEOF\n#define PACKAGE_VERSION \"$PACKAGE_VERSION\"\n_ACEOF\n\n\ncat >>confdefs.h <<_ACEOF\n#define PACKAGE_STRING \"$PACKAGE_STRING\"\n_ACEOF\n\n\ncat >>confdefs.h <<_ACEOF\n#define PACKAGE_BUGREPORT \"$PACKAGE_BUGREPORT\"\n_ACEOF\n\n\n# Let the site file select an alternate cache file if it wants to.\n# Prefer explicitly selected file to automatically selected ones.\nif test -z \"$CONFIG_SITE\"; then\n  if test \"x$prefix\" != xNONE; then\n    CONFIG_SITE=\"$prefix/share/config.site $prefix/etc/config.site\"\n  else\n    CONFIG_SITE=\"$ac_default_prefix/share/config.site $ac_default_prefix/etc/config.site\"\n  fi\nfi\nfor ac_site_file in $CONFIG_SITE; do\n  if test -r \"$ac_site_file\"; then\n    { echo \"$as_me:$LINENO: loading site script $ac_site_file\" >&5\necho \"$as_me: loading site script $ac_site_file\" >&6;}\n    sed 's/^/| /' \"$ac_site_file\" >&5\n    . \"$ac_site_file\"\n  fi\ndone\n\nif test -r \"$cache_file\"; then\n  # Some versions of bash will fail to source /dev/null (special\n  # files actually), so we avoid doing that.\n  if test -f \"$cache_file\"; then\n    { echo \"$as_me:$LINENO: loading cache $cache_file\" >&5\necho \"$as_me: loading cache $cache_file\" >&6;}\n    case $cache_file in\n      [\\\\/]* | ?:[\\\\/]* ) . $cache_file;;\n      *)                      . ./$cache_file;;\n    esac\n  fi\nelse\n  { echo \"$as_me:$LINENO: creating cache $cache_file\" >&5\necho \"$as_me: creating cache $cache_file\" >&6;}\n  >$cache_file\nfi\n\n# Check that the precious variables saved in the cache have kept the same\n# value.\nac_cache_corrupted=false\nfor ac_var in `(set) 2>&1 |\n\t       sed -n 's/^ac_env_\\([a-zA-Z_0-9]*\\)_set=.*/\\1/p'`; do\n  eval ac_old_set=\\$ac_cv_env_${ac_var}_set\n  eval ac_new_set=\\$ac_env_${ac_var}_set\n  eval ac_old_val=\"\\$ac_cv_env_${ac_var}_value\"\n  eval ac_new_val=\"\\$ac_env_${ac_var}_value\"\n  case $ac_old_set,$ac_new_set in\n    set,)\n      { echo \"$as_me:$LINENO: error: \\`$ac_var' was set to \\`$ac_old_val' in the previous run\" >&5\necho \"$as_me: error: \\`$ac_var' was set to \\`$ac_old_val' in the previous run\" >&2;}\n      ac_cache_corrupted=: ;;\n    ,set)\n      { echo \"$as_me:$LINENO: error: \\`$ac_var' was not set in the previous run\" >&5\necho \"$as_me: error: \\`$ac_var' was not set in the previous run\" >&2;}\n      ac_cache_corrupted=: ;;\n    ,);;\n    *)\n      if test \"x$ac_old_val\" != \"x$ac_new_val\"; then\n\t{ echo \"$as_me:$LINENO: error: \\`$ac_var' has changed since the previous run:\" >&5\necho \"$as_me: error: \\`$ac_var' has changed since the previous run:\" >&2;}\n\t{ echo \"$as_me:$LINENO:   former value:  $ac_old_val\" >&5\necho \"$as_me:   former value:  $ac_old_val\" >&2;}\n\t{ echo \"$as_me:$LINENO:   current value: $ac_new_val\" >&5\necho \"$as_me:   current value: $ac_new_val\" >&2;}\n\tac_cache_corrupted=:\n      fi;;\n  esac\n  # Pass precious variables to config.status.\n  if test \"$ac_new_set\" = set; then\n    case $ac_new_val in\n    *\" \"*|*\"\t\"*|*[\\[\\]\\~\\#\\$\\^\\&\\*\\(\\)\\{\\}\\\\\\|\\;\\<\\>\\?\\\"\\']*)\n      ac_arg=$ac_var=`echo \"$ac_new_val\" | sed \"s/'/'\\\\\\\\\\\\\\\\''/g\"` ;;\n    *) ac_arg=$ac_var=$ac_new_val ;;\n    esac\n    case \" $ac_configure_args \" in\n      *\" '$ac_arg' \"*) ;; # Avoid dups.  Use of quotes ensures accuracy.\n      *) ac_configure_args=\"$ac_configure_args '$ac_arg'\" ;;\n    esac\n  fi\ndone\nif $ac_cache_corrupted; then\n  { echo \"$as_me:$LINENO: error: changes in the environment can compromise the build\" >&5\necho \"$as_me: error: changes in the environment can compromise the build\" >&2;}\n  { { echo \"$as_me:$LINENO: error: run \\`make distclean' and/or \\`rm $cache_file' and start over\" >&5\necho \"$as_me: error: run \\`make distclean' and/or \\`rm $cache_file' and start over\" >&2;}\n   { (exit 1); exit 1; }; }\nfi\n\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\n\nac_aux_dir=\nfor ac_dir in $srcdir $srcdir/.. $srcdir/../..; do\n  if test -f $ac_dir/install-sh; then\n    ac_aux_dir=$ac_dir\n    ac_install_sh=\"$ac_aux_dir/install-sh -c\"\n    break\n  elif test -f $ac_dir/install.sh; then\n    ac_aux_dir=$ac_dir\n    ac_install_sh=\"$ac_aux_dir/install.sh -c\"\n    break\n  elif test -f $ac_dir/shtool; then\n    ac_aux_dir=$ac_dir\n    ac_install_sh=\"$ac_aux_dir/shtool install -c\"\n    break\n  fi\ndone\nif test -z \"$ac_aux_dir\"; then\n  { { echo \"$as_me:$LINENO: error: cannot find install-sh or install.sh in $srcdir $srcdir/.. $srcdir/../..\" >&5\necho \"$as_me: error: cannot find install-sh or install.sh in $srcdir $srcdir/.. $srcdir/../..\" >&2;}\n   { (exit 1); exit 1; }; }\nfi\nac_config_guess=\"$SHELL $ac_aux_dir/config.guess\"\nac_config_sub=\"$SHELL $ac_aux_dir/config.sub\"\nac_configure=\"$SHELL $ac_aux_dir/configure\" # This should be Cygnus configure.\n\n# Make sure we can run config.sub.\n$ac_config_sub sun4 >/dev/null 2>&1 ||\n  { { echo \"$as_me:$LINENO: error: cannot run $ac_config_sub\" >&5\necho \"$as_me: error: cannot run $ac_config_sub\" >&2;}\n   { (exit 1); exit 1; }; }\n\necho \"$as_me:$LINENO: checking build system type\" >&5\necho $ECHO_N \"checking build system type... $ECHO_C\" >&6\nif test \"${ac_cv_build+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  ac_cv_build_alias=$build_alias\ntest -z \"$ac_cv_build_alias\" &&\n  ac_cv_build_alias=`$ac_config_guess`\ntest -z \"$ac_cv_build_alias\" &&\n  { { echo \"$as_me:$LINENO: error: cannot guess build type; you must specify one\" >&5\necho \"$as_me: error: cannot guess build type; you must specify one\" >&2;}\n   { (exit 1); exit 1; }; }\nac_cv_build=`$ac_config_sub $ac_cv_build_alias` ||\n  { { echo \"$as_me:$LINENO: error: $ac_config_sub $ac_cv_build_alias failed\" >&5\necho \"$as_me: error: $ac_config_sub $ac_cv_build_alias failed\" >&2;}\n   { (exit 1); exit 1; }; }\n\nfi\necho \"$as_me:$LINENO: result: $ac_cv_build\" >&5\necho \"${ECHO_T}$ac_cv_build\" >&6\nbuild=$ac_cv_build\nbuild_cpu=`echo $ac_cv_build | sed 's/^\\([^-]*\\)-\\([^-]*\\)-\\(.*\\)$/\\1/'`\nbuild_vendor=`echo $ac_cv_build | sed 's/^\\([^-]*\\)-\\([^-]*\\)-\\(.*\\)$/\\2/'`\nbuild_os=`echo $ac_cv_build | sed 's/^\\([^-]*\\)-\\([^-]*\\)-\\(.*\\)$/\\3/'`\n\n\necho \"$as_me:$LINENO: checking host system type\" >&5\necho $ECHO_N \"checking host system type... $ECHO_C\" >&6\nif test \"${ac_cv_host+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  ac_cv_host_alias=$host_alias\ntest -z \"$ac_cv_host_alias\" &&\n  ac_cv_host_alias=$ac_cv_build_alias\nac_cv_host=`$ac_config_sub $ac_cv_host_alias` ||\n  { { echo \"$as_me:$LINENO: error: $ac_config_sub $ac_cv_host_alias failed\" >&5\necho \"$as_me: error: $ac_config_sub $ac_cv_host_alias failed\" >&2;}\n   { (exit 1); exit 1; }; }\n\nfi\necho \"$as_me:$LINENO: result: $ac_cv_host\" >&5\necho \"${ECHO_T}$ac_cv_host\" >&6\nhost=$ac_cv_host\nhost_cpu=`echo $ac_cv_host | sed 's/^\\([^-]*\\)-\\([^-]*\\)-\\(.*\\)$/\\1/'`\nhost_vendor=`echo $ac_cv_host | sed 's/^\\([^-]*\\)-\\([^-]*\\)-\\(.*\\)$/\\2/'`\nhost_os=`echo $ac_cv_host | sed 's/^\\([^-]*\\)-\\([^-]*\\)-\\(.*\\)$/\\3/'`\n\n\n\nSHARED_LIB=liblpsolve55.so\nSO=.so\ncase $host_os in\n  hp*|HP*)\n    DEF=-ldld\n    case `uname -m` in\n      ia64) SO=.so;;\n      *)    SO=.sl;;\n    esac\n    if test \"$GCC\" = yes;\n      then CCSHARED=\"-fPIC\";\n      else CCSHARED=\"+z\";\n    fi;;\n  CYGWIN*)\n    SO=.dll;;\n  linux)\n    CCSHARED=\"-fPIC\";;\n  apple-darwin)\n    DEF=-ldl -idirafter /usr/include/sys -DINTEGERTIME -Wno-long-double\n    ;;\n  OpenUNIX*|UnixWare*)\n    DEF='-dy -DNOLONGLONG'\n    if test \"$GCC\" = \"yes\"\n      then CCSHARED=\"-fPIC\"\n      else CCSHARED=\"-K PIC\"\n    fi;;\n  SCO_SV*)\n    DEF='-dy -DNOLONGLONG'\n    if test \"$GCC\" = \"yes\"\n      then CCSHARED=\"-fPIC\"\n      else CCSHARED=\"-Kpic -belf\"\n    fi;;\n *)\nesac\n\n\n\n\n\n\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\nif test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}gcc\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}gcc; ac_word=$2\necho \"$as_me:$LINENO: checking for $ac_word\" >&5\necho $ECHO_N \"checking for $ac_word... $ECHO_C\" >&6\nif test \"${ac_cv_prog_CC+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for ac_exec_ext in '' $ac_executable_extensions; do\n  if $as_executable_p \"$as_dir/$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_CC=\"${ac_tool_prefix}gcc\"\n    echo \"$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\ndone\n\nfi\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  echo \"$as_me:$LINENO: result: $CC\" >&5\necho \"${ECHO_T}$CC\" >&6\nelse\n  echo \"$as_me:$LINENO: result: no\" >&5\necho \"${ECHO_T}no\" >&6\nfi\n\nfi\nif test -z \"$ac_cv_prog_CC\"; then\n  ac_ct_CC=$CC\n  # Extract the first word of \"gcc\", so it can be a program name with args.\nset dummy gcc; ac_word=$2\necho \"$as_me:$LINENO: checking for $ac_word\" >&5\necho $ECHO_N \"checking for $ac_word... $ECHO_C\" >&6\nif test \"${ac_cv_prog_ac_ct_CC+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  if test -n \"$ac_ct_CC\"; then\n  ac_cv_prog_ac_ct_CC=\"$ac_ct_CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for ac_exec_ext in '' $ac_executable_extensions; do\n  if $as_executable_p \"$as_dir/$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_CC=\"gcc\"\n    echo \"$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\ndone\n\nfi\nfi\nac_ct_CC=$ac_cv_prog_ac_ct_CC\nif test -n \"$ac_ct_CC\"; then\n  echo \"$as_me:$LINENO: result: $ac_ct_CC\" >&5\necho \"${ECHO_T}$ac_ct_CC\" >&6\nelse\n  echo \"$as_me:$LINENO: result: no\" >&5\necho \"${ECHO_T}no\" >&6\nfi\n\n  CC=$ac_ct_CC\nelse\n  CC=\"$ac_cv_prog_CC\"\nfi\n\nif test -z \"$CC\"; then\n  if test -n \"$ac_tool_prefix\"; then\n  # Extract the first word of \"${ac_tool_prefix}cc\", so it can be a program name with args.\nset dummy ${ac_tool_prefix}cc; ac_word=$2\necho \"$as_me:$LINENO: checking for $ac_word\" >&5\necho $ECHO_N \"checking for $ac_word... $ECHO_C\" >&6\nif test \"${ac_cv_prog_CC+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for ac_exec_ext in '' $ac_executable_extensions; do\n  if $as_executable_p \"$as_dir/$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_CC=\"${ac_tool_prefix}cc\"\n    echo \"$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\ndone\n\nfi\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  echo \"$as_me:$LINENO: result: $CC\" >&5\necho \"${ECHO_T}$CC\" >&6\nelse\n  echo \"$as_me:$LINENO: result: no\" >&5\necho \"${ECHO_T}no\" >&6\nfi\n\nfi\nif test -z \"$ac_cv_prog_CC\"; then\n  ac_ct_CC=$CC\n  # Extract the first word of \"cc\", so it can be a program name with args.\nset dummy cc; ac_word=$2\necho \"$as_me:$LINENO: checking for $ac_word\" >&5\necho $ECHO_N \"checking for $ac_word... $ECHO_C\" >&6\nif test \"${ac_cv_prog_ac_ct_CC+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  if test -n \"$ac_ct_CC\"; then\n  ac_cv_prog_ac_ct_CC=\"$ac_ct_CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for ac_exec_ext in '' $ac_executable_extensions; do\n  if $as_executable_p \"$as_dir/$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_CC=\"cc\"\n    echo \"$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\ndone\n\nfi\nfi\nac_ct_CC=$ac_cv_prog_ac_ct_CC\nif test -n \"$ac_ct_CC\"; then\n  echo \"$as_me:$LINENO: result: $ac_ct_CC\" >&5\necho \"${ECHO_T}$ac_ct_CC\" >&6\nelse\n  echo \"$as_me:$LINENO: result: no\" >&5\necho \"${ECHO_T}no\" >&6\nfi\n\n  CC=$ac_ct_CC\nelse\n  CC=\"$ac_cv_prog_CC\"\nfi\n\nfi\nif test -z \"$CC\"; then\n  # Extract the first word of \"cc\", so it can be a program name with args.\nset dummy cc; ac_word=$2\necho \"$as_me:$LINENO: checking for $ac_word\" >&5\necho $ECHO_N \"checking for $ac_word... $ECHO_C\" >&6\nif test \"${ac_cv_prog_CC+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\n  ac_prog_rejected=no\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for ac_exec_ext in '' $ac_executable_extensions; do\n  if $as_executable_p \"$as_dir/$ac_word$ac_exec_ext\"; then\n    if test \"$as_dir/$ac_word$ac_exec_ext\" = \"/usr/ucb/cc\"; then\n       ac_prog_rejected=yes\n       continue\n     fi\n    ac_cv_prog_CC=\"cc\"\n    echo \"$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\ndone\n\nif test $ac_prog_rejected = yes; then\n  # We found a bogon in the path, so make sure we never use it.\n  set dummy $ac_cv_prog_CC\n  shift\n  if test $# != 0; then\n    # We chose a different compiler from the bogus one.\n    # However, it has the same basename, so the bogon will be chosen\n    # first if we set CC to just the basename; use the full file name.\n    shift\n    ac_cv_prog_CC=\"$as_dir/$ac_word${1+' '}$@\"\n  fi\nfi\nfi\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  echo \"$as_me:$LINENO: result: $CC\" >&5\necho \"${ECHO_T}$CC\" >&6\nelse\n  echo \"$as_me:$LINENO: result: no\" >&5\necho \"${ECHO_T}no\" >&6\nfi\n\nfi\nif test -z \"$CC\"; then\n  if test -n \"$ac_tool_prefix\"; then\n  for ac_prog in cl\n  do\n    # Extract the first word of \"$ac_tool_prefix$ac_prog\", so it can be a program name with args.\nset dummy $ac_tool_prefix$ac_prog; ac_word=$2\necho \"$as_me:$LINENO: checking for $ac_word\" >&5\necho $ECHO_N \"checking for $ac_word... $ECHO_C\" >&6\nif test \"${ac_cv_prog_CC+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  if test -n \"$CC\"; then\n  ac_cv_prog_CC=\"$CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for ac_exec_ext in '' $ac_executable_extensions; do\n  if $as_executable_p \"$as_dir/$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_CC=\"$ac_tool_prefix$ac_prog\"\n    echo \"$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\ndone\n\nfi\nfi\nCC=$ac_cv_prog_CC\nif test -n \"$CC\"; then\n  echo \"$as_me:$LINENO: result: $CC\" >&5\necho \"${ECHO_T}$CC\" >&6\nelse\n  echo \"$as_me:$LINENO: result: no\" >&5\necho \"${ECHO_T}no\" >&6\nfi\n\n    test -n \"$CC\" && break\n  done\nfi\nif test -z \"$CC\"; then\n  ac_ct_CC=$CC\n  for ac_prog in cl\ndo\n  # Extract the first word of \"$ac_prog\", so it can be a program name with args.\nset dummy $ac_prog; ac_word=$2\necho \"$as_me:$LINENO: checking for $ac_word\" >&5\necho $ECHO_N \"checking for $ac_word... $ECHO_C\" >&6\nif test \"${ac_cv_prog_ac_ct_CC+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  if test -n \"$ac_ct_CC\"; then\n  ac_cv_prog_ac_ct_CC=\"$ac_ct_CC\" # Let the user override the test.\nelse\nas_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for ac_exec_ext in '' $ac_executable_extensions; do\n  if $as_executable_p \"$as_dir/$ac_word$ac_exec_ext\"; then\n    ac_cv_prog_ac_ct_CC=\"$ac_prog\"\n    echo \"$as_me:$LINENO: found $as_dir/$ac_word$ac_exec_ext\" >&5\n    break 2\n  fi\ndone\ndone\n\nfi\nfi\nac_ct_CC=$ac_cv_prog_ac_ct_CC\nif test -n \"$ac_ct_CC\"; then\n  echo \"$as_me:$LINENO: result: $ac_ct_CC\" >&5\necho \"${ECHO_T}$ac_ct_CC\" >&6\nelse\n  echo \"$as_me:$LINENO: result: no\" >&5\necho \"${ECHO_T}no\" >&6\nfi\n\n  test -n \"$ac_ct_CC\" && break\ndone\n\n  CC=$ac_ct_CC\nfi\n\nfi\n\n\ntest -z \"$CC\" && { { echo \"$as_me:$LINENO: error: no acceptable C compiler found in \\$PATH\nSee \\`config.log' for more details.\" >&5\necho \"$as_me: error: no acceptable C compiler found in \\$PATH\nSee \\`config.log' for more details.\" >&2;}\n   { (exit 1); exit 1; }; }\n\n# Provide some information about the compiler.\necho \"$as_me:$LINENO:\" \\\n     \"checking for C compiler version\" >&5\nac_compiler=`set X $ac_compile; echo $2`\n{ (eval echo \"$as_me:$LINENO: \\\"$ac_compiler --version </dev/null >&5\\\"\") >&5\n  (eval $ac_compiler --version </dev/null >&5) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }\n{ (eval echo \"$as_me:$LINENO: \\\"$ac_compiler -v </dev/null >&5\\\"\") >&5\n  (eval $ac_compiler -v </dev/null >&5) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }\n{ (eval echo \"$as_me:$LINENO: \\\"$ac_compiler -V </dev/null >&5\\\"\") >&5\n  (eval $ac_compiler -V </dev/null >&5) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }\n\ncat >conftest.$ac_ext <<_ACEOF\n/* confdefs.h.  */\n_ACEOF\ncat confdefs.h >>conftest.$ac_ext\ncat >>conftest.$ac_ext <<_ACEOF\n/* end confdefs.h.  */\n\nint\nmain ()\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nac_clean_files_save=$ac_clean_files\nac_clean_files=\"$ac_clean_files a.out a.exe b.out\"\n# Try to create an executable without -o first, disregard a.out.\n# It will help us diagnose broken compilers, and finding out an intuition\n# of exeext.\necho \"$as_me:$LINENO: checking for C compiler default output file name\" >&5\necho $ECHO_N \"checking for C compiler default output file name... $ECHO_C\" >&6\nac_link_default=`echo \"$ac_link\" | sed 's/ -o *conftest[^ ]*//'`\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_link_default\\\"\") >&5\n  (eval $ac_link_default) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; then\n  # Find the output, starting from the most likely.  This scheme is\n# not robust to junk in `.', hence go to wildcards (a.*) only as a last\n# resort.\n\n# Be careful to initialize this variable, since it used to be cached.\n# Otherwise an old cache value of `no' led to `EXEEXT = no' in a Makefile.\nac_cv_exeext=\n# b.out is created by i960 compilers.\nfor ac_file in a_out.exe a.exe conftest.exe a.out conftest a.* conftest.* b.out\ndo\n  test -f \"$ac_file\" || continue\n  case $ac_file in\n    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.o | *.obj )\n\t;;\n    conftest.$ac_ext )\n\t# This is the source file.\n\t;;\n    [ab].out )\n\t# We found the default executable, but exeext='' is most\n\t# certainly right.\n\tbreak;;\n    *.* )\n\tac_cv_exeext=`expr \"$ac_file\" : '[^.]*\\(\\..*\\)'`\n\t# FIXME: I believe we export ac_cv_exeext for Libtool,\n\t# but it would be cool to find out if it's true.  Does anybody\n\t# maintain Libtool? --akim.\n\texport ac_cv_exeext\n\tbreak;;\n    * )\n\tbreak;;\n  esac\ndone\nelse\n  echo \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n{ { echo \"$as_me:$LINENO: error: C compiler cannot create executables\nSee \\`config.log' for more details.\" >&5\necho \"$as_me: error: C compiler cannot create executables\nSee \\`config.log' for more details.\" >&2;}\n   { (exit 77); exit 77; }; }\nfi\n\nac_exeext=$ac_cv_exeext\necho \"$as_me:$LINENO: result: $ac_file\" >&5\necho \"${ECHO_T}$ac_file\" >&6\n\n# Check the compiler produces executables we can run.  If not, either\n# the compiler is broken, or we cross compile.\necho \"$as_me:$LINENO: checking whether the C compiler works\" >&5\necho $ECHO_N \"checking whether the C compiler works... $ECHO_C\" >&6\n# FIXME: These cross compiler hacks should be removed for Autoconf 3.0\n# If not cross compiling, check that we can run a simple program.\nif test \"$cross_compiling\" != yes; then\n  if { ac_try='./$ac_file'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; }; then\n    cross_compiling=no\n  else\n    if test \"$cross_compiling\" = maybe; then\n\tcross_compiling=yes\n    else\n\t{ { echo \"$as_me:$LINENO: error: cannot run C compiled programs.\nIf you meant to cross compile, use \\`--host'.\nSee \\`config.log' for more details.\" >&5\necho \"$as_me: error: cannot run C compiled programs.\nIf you meant to cross compile, use \\`--host'.\nSee \\`config.log' for more details.\" >&2;}\n   { (exit 1); exit 1; }; }\n    fi\n  fi\nfi\necho \"$as_me:$LINENO: result: yes\" >&5\necho \"${ECHO_T}yes\" >&6\n\nrm -f a.out a.exe conftest$ac_cv_exeext b.out\nac_clean_files=$ac_clean_files_save\n# Check the compiler produces executables we can run.  If not, either\n# the compiler is broken, or we cross compile.\necho \"$as_me:$LINENO: checking whether we are cross compiling\" >&5\necho $ECHO_N \"checking whether we are cross compiling... $ECHO_C\" >&6\necho \"$as_me:$LINENO: result: $cross_compiling\" >&5\necho \"${ECHO_T}$cross_compiling\" >&6\n\necho \"$as_me:$LINENO: checking for suffix of executables\" >&5\necho $ECHO_N \"checking for suffix of executables... $ECHO_C\" >&6\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_link\\\"\") >&5\n  (eval $ac_link) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; then\n  # If both `conftest.exe' and `conftest' are `present' (well, observable)\n# catch `conftest.exe'.  For instance with Cygwin, `ls conftest' will\n# work properly (i.e., refer to `conftest.exe'), while it won't with\n# `rm'.\nfor ac_file in conftest.exe conftest conftest.*; do\n  test -f \"$ac_file\" || continue\n  case $ac_file in\n    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg | *.o | *.obj ) ;;\n    *.* ) ac_cv_exeext=`expr \"$ac_file\" : '[^.]*\\(\\..*\\)'`\n\t  export ac_cv_exeext\n\t  break;;\n    * ) break;;\n  esac\ndone\nelse\n  { { echo \"$as_me:$LINENO: error: cannot compute suffix of executables: cannot compile and link\nSee \\`config.log' for more details.\" >&5\necho \"$as_me: error: cannot compute suffix of executables: cannot compile and link\nSee \\`config.log' for more details.\" >&2;}\n   { (exit 1); exit 1; }; }\nfi\n\nrm -f conftest$ac_cv_exeext\necho \"$as_me:$LINENO: result: $ac_cv_exeext\" >&5\necho \"${ECHO_T}$ac_cv_exeext\" >&6\n\nrm -f conftest.$ac_ext\nEXEEXT=$ac_cv_exeext\nac_exeext=$EXEEXT\necho \"$as_me:$LINENO: checking for suffix of object files\" >&5\necho $ECHO_N \"checking for suffix of object files... $ECHO_C\" >&6\nif test \"${ac_cv_objext+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  cat >conftest.$ac_ext <<_ACEOF\n/* confdefs.h.  */\n_ACEOF\ncat confdefs.h >>conftest.$ac_ext\ncat >>conftest.$ac_ext <<_ACEOF\n/* end confdefs.h.  */\n\nint\nmain ()\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nrm -f conftest.o conftest.obj\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_compile\\\"\") >&5\n  (eval $ac_compile) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; then\n  for ac_file in `(ls conftest.o conftest.obj; ls conftest.*) 2>/dev/null`; do\n  case $ac_file in\n    *.$ac_ext | *.xcoff | *.tds | *.d | *.pdb | *.xSYM | *.bb | *.bbg ) ;;\n    *) ac_cv_objext=`expr \"$ac_file\" : '.*\\.\\(.*\\)'`\n       break;;\n  esac\ndone\nelse\n  echo \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\n{ { echo \"$as_me:$LINENO: error: cannot compute suffix of object files: cannot compile\nSee \\`config.log' for more details.\" >&5\necho \"$as_me: error: cannot compute suffix of object files: cannot compile\nSee \\`config.log' for more details.\" >&2;}\n   { (exit 1); exit 1; }; }\nfi\n\nrm -f conftest.$ac_cv_objext conftest.$ac_ext\nfi\necho \"$as_me:$LINENO: result: $ac_cv_objext\" >&5\necho \"${ECHO_T}$ac_cv_objext\" >&6\nOBJEXT=$ac_cv_objext\nac_objext=$OBJEXT\necho \"$as_me:$LINENO: checking whether we are using the GNU C compiler\" >&5\necho $ECHO_N \"checking whether we are using the GNU C compiler... $ECHO_C\" >&6\nif test \"${ac_cv_c_compiler_gnu+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  cat >conftest.$ac_ext <<_ACEOF\n/* confdefs.h.  */\n_ACEOF\ncat confdefs.h >>conftest.$ac_ext\ncat >>conftest.$ac_ext <<_ACEOF\n/* end confdefs.h.  */\n\nint\nmain ()\n{\n#ifndef __GNUC__\n       choke me\n#endif\n\n  ;\n  return 0;\n}\n_ACEOF\nrm -f conftest.$ac_objext\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_compile\\\"\") >&5\n  (eval $ac_compile) 2>conftest.er1\n  ac_status=$?\n  grep -v '^ *+' conftest.er1 >conftest.err\n  rm -f conftest.er1\n  cat conftest.err >&5\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); } &&\n\t { ac_try='test -z \"$ac_c_werror_flag\"\n\t\t\t || test ! -s conftest.err'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; } &&\n\t { ac_try='test -s conftest.$ac_objext'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; }; then\n  ac_compiler_gnu=yes\nelse\n  echo \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\nac_compiler_gnu=no\nfi\nrm -f conftest.err conftest.$ac_objext conftest.$ac_ext\nac_cv_c_compiler_gnu=$ac_compiler_gnu\n\nfi\necho \"$as_me:$LINENO: result: $ac_cv_c_compiler_gnu\" >&5\necho \"${ECHO_T}$ac_cv_c_compiler_gnu\" >&6\nGCC=`test $ac_compiler_gnu = yes && echo yes`\nac_test_CFLAGS=${CFLAGS+set}\nac_save_CFLAGS=$CFLAGS\nCFLAGS=\"-g\"\necho \"$as_me:$LINENO: checking whether $CC accepts -g\" >&5\necho $ECHO_N \"checking whether $CC accepts -g... $ECHO_C\" >&6\nif test \"${ac_cv_prog_cc_g+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  cat >conftest.$ac_ext <<_ACEOF\n/* confdefs.h.  */\n_ACEOF\ncat confdefs.h >>conftest.$ac_ext\ncat >>conftest.$ac_ext <<_ACEOF\n/* end confdefs.h.  */\n\nint\nmain ()\n{\n\n  ;\n  return 0;\n}\n_ACEOF\nrm -f conftest.$ac_objext\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_compile\\\"\") >&5\n  (eval $ac_compile) 2>conftest.er1\n  ac_status=$?\n  grep -v '^ *+' conftest.er1 >conftest.err\n  rm -f conftest.er1\n  cat conftest.err >&5\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); } &&\n\t { ac_try='test -z \"$ac_c_werror_flag\"\n\t\t\t || test ! -s conftest.err'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; } &&\n\t { ac_try='test -s conftest.$ac_objext'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; }; then\n  ac_cv_prog_cc_g=yes\nelse\n  echo \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\nac_cv_prog_cc_g=no\nfi\nrm -f conftest.err conftest.$ac_objext conftest.$ac_ext\nfi\necho \"$as_me:$LINENO: result: $ac_cv_prog_cc_g\" >&5\necho \"${ECHO_T}$ac_cv_prog_cc_g\" >&6\nif test \"$ac_test_CFLAGS\" = set; then\n  CFLAGS=$ac_save_CFLAGS\nelif test $ac_cv_prog_cc_g = yes; then\n  if test \"$GCC\" = yes; then\n    CFLAGS=\"-g -O2\"\n  else\n    CFLAGS=\"-g\"\n  fi\nelse\n  if test \"$GCC\" = yes; then\n    CFLAGS=\"-O2\"\n  else\n    CFLAGS=\n  fi\nfi\necho \"$as_me:$LINENO: checking for $CC option to accept ANSI C\" >&5\necho $ECHO_N \"checking for $CC option to accept ANSI C... $ECHO_C\" >&6\nif test \"${ac_cv_prog_cc_stdc+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  ac_cv_prog_cc_stdc=no\nac_save_CC=$CC\ncat >conftest.$ac_ext <<_ACEOF\n/* confdefs.h.  */\n_ACEOF\ncat confdefs.h >>conftest.$ac_ext\ncat >>conftest.$ac_ext <<_ACEOF\n/* end confdefs.h.  */\n#include <stdarg.h>\n#include <stdio.h>\n#include <sys/types.h>\n#include <sys/stat.h>\n/* Most of the following tests are stolen from RCS 5.7's src/conf.sh.  */\nstruct buf { int x; };\nFILE * (*rcsopen) (struct buf *, struct stat *, int);\nstatic char *e (p, i)\n     char **p;\n     int i;\n{\n  return p[i];\n}\nstatic char *f (char * (*g) (char **, int), char **p, ...)\n{\n  char *s;\n  va_list v;\n  va_start (v,p);\n  s = g (p, va_arg (v,int));\n  va_end (v);\n  return s;\n}\n\n/* OSF 4.0 Compaq cc is some sort of almost-ANSI by default.  It has\n   function prototypes and stuff, but not '\\xHH' hex character constants.\n   These don't provoke an error unfortunately, instead are silently treated\n   as 'x'.  The following induces an error, until -std1 is added to get\n   proper ANSI mode.  Curiously '\\x00'!='x' always comes out true, for an\n   array size at least.  It's necessary to write '\\x00'==0 to get something\n   that's true only with -std1.  */\nint osf4_cc_array ['\\x00' == 0 ? 1 : -1];\n\nint test (int i, double x);\nstruct s1 {int (*f) (int a);};\nstruct s2 {int (*f) (double a);};\nint pairnames (int, char **, FILE *(*)(struct buf *, struct stat *, int), int, int);\nint argc;\nchar **argv;\nint\nmain ()\n{\nreturn f (e, argv, 0) != argv[0]  ||  f (e, argv, 1) != argv[1];\n  ;\n  return 0;\n}\n_ACEOF\n# Don't try gcc -ansi; that turns off useful extensions and\n# breaks some systems' header files.\n# AIX\t\t\t-qlanglvl=ansi\n# Ultrix and OSF/1\t-std1\n# HP-UX 10.20 and later\t-Ae\n# HP-UX older versions\t-Aa -D_HPUX_SOURCE\n# SVR4\t\t\t-Xc -D__EXTENSIONS__\nfor ac_arg in \"\" -qlanglvl=ansi -std1 -Ae \"-Aa -D_HPUX_SOURCE\" \"-Xc -D__EXTENSIONS__\"\ndo\n  CC=\"$ac_save_CC $ac_arg\"\n  rm -f conftest.$ac_objext\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_compile\\\"\") >&5\n  (eval $ac_compile) 2>conftest.er1\n  ac_status=$?\n  grep -v '^ *+' conftest.er1 >conftest.err\n  rm -f conftest.er1\n  cat conftest.err >&5\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); } &&\n\t { ac_try='test -z \"$ac_c_werror_flag\"\n\t\t\t || test ! -s conftest.err'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; } &&\n\t { ac_try='test -s conftest.$ac_objext'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; }; then\n  ac_cv_prog_cc_stdc=$ac_arg\nbreak\nelse\n  echo \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\nfi\nrm -f conftest.err conftest.$ac_objext\ndone\nrm -f conftest.$ac_ext conftest.$ac_objext\nCC=$ac_save_CC\n\nfi\n\ncase \"x$ac_cv_prog_cc_stdc\" in\n  x|xno)\n    echo \"$as_me:$LINENO: result: none needed\" >&5\necho \"${ECHO_T}none needed\" >&6 ;;\n  *)\n    echo \"$as_me:$LINENO: result: $ac_cv_prog_cc_stdc\" >&5\necho \"${ECHO_T}$ac_cv_prog_cc_stdc\" >&6\n    CC=\"$CC $ac_cv_prog_cc_stdc\" ;;\nesac\n\n# Some people use a C++ compiler to compile C.  Since we use `exit',\n# in C++ we need to declare it.  In case someone uses the same compiler\n# for both compiling C and C++ we need to have the C++ compiler decide\n# the declaration of exit, since it's the most demanding environment.\ncat >conftest.$ac_ext <<_ACEOF\n#ifndef __cplusplus\n  choke me\n#endif\n_ACEOF\nrm -f conftest.$ac_objext\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_compile\\\"\") >&5\n  (eval $ac_compile) 2>conftest.er1\n  ac_status=$?\n  grep -v '^ *+' conftest.er1 >conftest.err\n  rm -f conftest.er1\n  cat conftest.err >&5\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); } &&\n\t { ac_try='test -z \"$ac_c_werror_flag\"\n\t\t\t || test ! -s conftest.err'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; } &&\n\t { ac_try='test -s conftest.$ac_objext'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; }; then\n  for ac_declaration in \\\n   '' \\\n   'extern \"C\" void std::exit (int) throw (); using std::exit;' \\\n   'extern \"C\" void std::exit (int); using std::exit;' \\\n   'extern \"C\" void exit (int) throw ();' \\\n   'extern \"C\" void exit (int);' \\\n   'void exit (int);'\ndo\n  cat >conftest.$ac_ext <<_ACEOF\n/* confdefs.h.  */\n_ACEOF\ncat confdefs.h >>conftest.$ac_ext\ncat >>conftest.$ac_ext <<_ACEOF\n/* end confdefs.h.  */\n$ac_declaration\n#include <stdlib.h>\nint\nmain ()\n{\nexit (42);\n  ;\n  return 0;\n}\n_ACEOF\nrm -f conftest.$ac_objext\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_compile\\\"\") >&5\n  (eval $ac_compile) 2>conftest.er1\n  ac_status=$?\n  grep -v '^ *+' conftest.er1 >conftest.err\n  rm -f conftest.er1\n  cat conftest.err >&5\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); } &&\n\t { ac_try='test -z \"$ac_c_werror_flag\"\n\t\t\t || test ! -s conftest.err'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; } &&\n\t { ac_try='test -s conftest.$ac_objext'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; }; then\n  :\nelse\n  echo \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\ncontinue\nfi\nrm -f conftest.err conftest.$ac_objext conftest.$ac_ext\n  cat >conftest.$ac_ext <<_ACEOF\n/* confdefs.h.  */\n_ACEOF\ncat confdefs.h >>conftest.$ac_ext\ncat >>conftest.$ac_ext <<_ACEOF\n/* end confdefs.h.  */\n$ac_declaration\nint\nmain ()\n{\nexit (42);\n  ;\n  return 0;\n}\n_ACEOF\nrm -f conftest.$ac_objext\nif { (eval echo \"$as_me:$LINENO: \\\"$ac_compile\\\"\") >&5\n  (eval $ac_compile) 2>conftest.er1\n  ac_status=$?\n  grep -v '^ *+' conftest.er1 >conftest.err\n  rm -f conftest.er1\n  cat conftest.err >&5\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); } &&\n\t { ac_try='test -z \"$ac_c_werror_flag\"\n\t\t\t || test ! -s conftest.err'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; } &&\n\t { ac_try='test -s conftest.$ac_objext'\n  { (eval echo \"$as_me:$LINENO: \\\"$ac_try\\\"\") >&5\n  (eval $ac_try) 2>&5\n  ac_status=$?\n  echo \"$as_me:$LINENO: \\$? = $ac_status\" >&5\n  (exit $ac_status); }; }; then\n  break\nelse\n  echo \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\nfi\nrm -f conftest.err conftest.$ac_objext conftest.$ac_ext\ndone\nrm -f conftest*\nif test -n \"$ac_declaration\"; then\n  echo '#ifdef __cplusplus' >>confdefs.h\n  echo $ac_declaration      >>confdefs.h\n  echo '#endif'             >>confdefs.h\nfi\n\nelse\n  echo \"$as_me: failed program was:\" >&5\nsed 's/^/| /' conftest.$ac_ext >&5\n\nfi\nrm -f conftest.err conftest.$ac_objext conftest.$ac_ext\nac_ext=c\nac_cpp='$CPP $CPPFLAGS'\nac_compile='$CC -c $CFLAGS $CPPFLAGS conftest.$ac_ext >&5'\nac_link='$CC -o conftest$ac_exeext $CFLAGS $CPPFLAGS $LDFLAGS conftest.$ac_ext $LIBS >&5'\nac_compiler_gnu=$ac_cv_c_compiler_gnu\n\nif test \"x$GCC\" != \"xyes\"\nthen\n  echo \"*** non GNU CC compiler detected.\"\n  echo \"*** This package has not been tested very well with non GNU compilers\"\nfi\n\n# Find a good install program.  We prefer a C program (faster),\n# so one script is as good as another.  But avoid the broken or\n# incompatible versions:\n# SysV /etc/install, /usr/sbin/install\n# SunOS /usr/etc/install\n# IRIX /sbin/install\n# AIX /bin/install\n# AmigaOS /C/install, which installs bootblocks on floppy discs\n# AIX 4 /usr/bin/installbsd, which doesn't work without a -g flag\n# AFS /usr/afsws/bin/install, which mishandles nonexistent args\n# SVR4 /usr/ucb/install, which tries to use the nonexistent group \"staff\"\n# OS/2's system install, which has a completely different semantic\n# ./install, which can be erroneously created by make from ./install.sh.\necho \"$as_me:$LINENO: checking for a BSD-compatible install\" >&5\necho $ECHO_N \"checking for a BSD-compatible install... $ECHO_C\" >&6\nif test -z \"$INSTALL\"; then\nif test \"${ac_cv_path_install+set}\" = set; then\n  echo $ECHO_N \"(cached) $ECHO_C\" >&6\nelse\n  as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  # Account for people who put trailing slashes in PATH elements.\ncase $as_dir/ in\n  ./ | .// | /cC/* | \\\n  /etc/* | /usr/sbin/* | /usr/etc/* | /sbin/* | /usr/afsws/bin/* | \\\n  ?:\\\\/os2\\\\/install\\\\/* | ?:\\\\/OS2\\\\/INSTALL\\\\/* | \\\n  /usr/ucb/* ) ;;\n  *)\n    # OSF1 and SCO ODT 3.0 have their own names for install.\n    # Don't use installbsd from OSF since it installs stuff as root\n    # by default.\n    for ac_prog in ginstall scoinst install; do\n      for ac_exec_ext in '' $ac_executable_extensions; do\n\tif $as_executable_p \"$as_dir/$ac_prog$ac_exec_ext\"; then\n\t  if test $ac_prog = install &&\n\t    grep dspmsg \"$as_dir/$ac_prog$ac_exec_ext\" >/dev/null 2>&1; then\n\t    # AIX install.  It has an incompatible calling convention.\n\t    :\n\t  elif test $ac_prog = install &&\n\t    grep pwplus \"$as_dir/$ac_prog$ac_exec_ext\" >/dev/null 2>&1; then\n\t    # program-specific install script used by HP pwplus--don't use.\n\t    :\n\t  else\n\t    ac_cv_path_install=\"$as_dir/$ac_prog$ac_exec_ext -c\"\n\t    break 3\n\t  fi\n\tfi\n      done\n    done\n    ;;\nesac\ndone\n\n\nfi\n  if test \"${ac_cv_path_install+set}\" = set; then\n    INSTALL=$ac_cv_path_install\n  else\n    # As a last resort, use the slow shell script.  We don't cache a\n    # path for INSTALL within a source directory, because that will\n    # break other packages using the cache if that directory is\n    # removed, or if the path is relative.\n    INSTALL=$ac_install_sh\n  fi\nfi\necho \"$as_me:$LINENO: result: $INSTALL\" >&5\necho \"${ECHO_T}$INSTALL\" >&6\n\n# Use test -z because SunOS4 sh mishandles braces in ${var-val}.\n# It thinks the first close brace ends the variable substitution.\ntest -z \"$INSTALL_PROGRAM\" && INSTALL_PROGRAM='${INSTALL}'\n\ntest -z \"$INSTALL_SCRIPT\" && INSTALL_SCRIPT='${INSTALL}'\n\ntest -z \"$INSTALL_DATA\" && INSTALL_DATA='${INSTALL} -m 644'\n\n          ac_config_files=\"$ac_config_files Makefile\"\n\ncat >confcache <<\\_ACEOF\n# This file is a shell script that caches the results of configure\n# tests run on this system so they can be shared between configure\n# scripts and configure runs, see configure's option --config-cache.\n# It is not useful on other systems.  If it contains results you don't\n# want to keep, you may remove or edit it.\n#\n# config.status only pays attention to the cache file if you give it\n# the --recheck option to rerun configure.\n#\n# `ac_cv_env_foo' variables (set or unset) will be overridden when\n# loading this file, other *unset* `ac_cv_foo' will be assigned the\n# following values.\n\n_ACEOF\n\n# The following way of writing the cache mishandles newlines in values,\n# but we know of no workaround that is simple, portable, and efficient.\n# So, don't put newlines in cache variables' values.\n# Ultrix sh set writes to stderr and can't be redirected directly,\n# and sets the high bit in the cache file unless we assign to the vars.\n{\n  (set) 2>&1 |\n    case `(ac_space=' '; set | grep ac_space) 2>&1` in\n    *ac_space=\\ *)\n      # `set' does not quote correctly, so add quotes (double-quote\n      # substitution turns \\\\\\\\ into \\\\, and sed turns \\\\ into \\).\n      sed -n \\\n\t\"s/'/'\\\\\\\\''/g;\n\t  s/^\\\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\\\)=\\\\(.*\\\\)/\\\\1='\\\\2'/p\"\n      ;;\n    *)\n      # `set' quotes correctly as required by POSIX, so do not add quotes.\n      sed -n \\\n\t\"s/^\\\\([_$as_cr_alnum]*_cv_[_$as_cr_alnum]*\\\\)=\\\\(.*\\\\)/\\\\1=\\\\2/p\"\n      ;;\n    esac;\n} |\n  sed '\n     t clear\n     : clear\n     s/^\\([^=]*\\)=\\(.*[{}].*\\)$/test \"${\\1+set}\" = set || &/\n     t end\n     /^ac_cv_env/!s/^\\([^=]*\\)=\\(.*\\)$/\\1=${\\1=\\2}/\n     : end' >>confcache\nif diff $cache_file confcache >/dev/null 2>&1; then :; else\n  if test -w $cache_file; then\n    test \"x$cache_file\" != \"x/dev/null\" && echo \"updating cache $cache_file\"\n    cat confcache >$cache_file\n  else\n    echo \"not updating unwritable cache $cache_file\"\n  fi\nfi\nrm -f confcache\n\ntest \"x$prefix\" = xNONE && prefix=$ac_default_prefix\n# Let make expand exec_prefix.\ntest \"x$exec_prefix\" = xNONE && exec_prefix='${prefix}'\n\n# VPATH may cause trouble with some makes, so we remove $(srcdir),\n# ${srcdir} and @srcdir@ from VPATH if srcdir is \".\", strip leading and\n# trailing colons and then remove the whole line if VPATH becomes empty\n# (actually we leave an empty line to preserve line numbers).\nif test \"x$srcdir\" = x.; then\n  ac_vpsub='/^[\t ]*VPATH[\t ]*=/{\ns/:*\\$(srcdir):*/:/;\ns/:*\\${srcdir}:*/:/;\ns/:*@srcdir@:*/:/;\ns/^\\([^=]*=[\t ]*\\):*/\\1/;\ns/:*$//;\ns/^[^=]*=[\t ]*$//;\n}'\nfi\n\n# Transform confdefs.h into DEFS.\n# Protect against shell expansion while executing Makefile rules.\n# Protect against Makefile macro expansion.\n#\n# If the first sed substitution is executed (which looks for macros that\n# take arguments), then we branch to the quote section.  Otherwise,\n# look for a macro that doesn't take arguments.\ncat >confdef2opt.sed <<\\_ACEOF\nt clear\n: clear\ns,^[\t ]*#[\t ]*define[\t ][\t ]*\\([^\t (][^\t (]*([^)]*)\\)[\t ]*\\(.*\\),-D\\1=\\2,g\nt quote\ns,^[\t ]*#[\t ]*define[\t ][\t ]*\\([^\t ][^\t ]*\\)[\t ]*\\(.*\\),-D\\1=\\2,g\nt quote\nd\n: quote\ns,[\t `~#$^&*(){}\\\\|;'\"<>?],\\\\&,g\ns,\\[,\\\\&,g\ns,\\],\\\\&,g\ns,\\$,$$,g\np\n_ACEOF\n# We use echo to avoid assuming a particular line-breaking character.\n# The extra dot is to prevent the shell from consuming trailing\n# line-breaks from the sub-command output.  A line-break within\n# single-quotes doesn't work because, if this script is created in a\n# platform that uses two characters for line-breaks (e.g., DOS), tr\n# would break.\nac_LF_and_DOT=`echo; echo .`\nDEFS=`sed -n -f confdef2opt.sed confdefs.h | tr \"$ac_LF_and_DOT\" ' .'`\nrm -f confdef2opt.sed\n\n\nac_libobjs=\nac_ltlibobjs=\nfor ac_i in : $LIBOBJS; do test \"x$ac_i\" = x: && continue\n  # 1. Remove the extension, and $U if already installed.\n  ac_i=`echo \"$ac_i\" |\n\t sed 's/\\$U\\././;s/\\.o$//;s/\\.obj$//'`\n  # 2. Add them.\n  ac_libobjs=\"$ac_libobjs $ac_i\\$U.$ac_objext\"\n  ac_ltlibobjs=\"$ac_ltlibobjs $ac_i\"'$U.lo'\ndone\nLIBOBJS=$ac_libobjs\n\nLTLIBOBJS=$ac_ltlibobjs\n\n\n\n: ${CONFIG_STATUS=./config.status}\nac_clean_files_save=$ac_clean_files\nac_clean_files=\"$ac_clean_files $CONFIG_STATUS\"\n{ echo \"$as_me:$LINENO: creating $CONFIG_STATUS\" >&5\necho \"$as_me: creating $CONFIG_STATUS\" >&6;}\ncat >$CONFIG_STATUS <<_ACEOF\n#! $SHELL\n# Generated by $as_me.\n# Run this file to recreate the current configuration.\n# Compiler output produced by configure, useful for debugging\n# configure, is in config.log if it exists.\n\ndebug=false\nac_cs_recheck=false\nac_cs_silent=false\nSHELL=\\${CONFIG_SHELL-$SHELL}\n_ACEOF\n\ncat >>$CONFIG_STATUS <<\\_ACEOF\n## --------------------- ##\n## M4sh Initialization.  ##\n## --------------------- ##\n\n# Be Bourne compatible\nif test -n \"${ZSH_VERSION+set}\" && (emulate sh) >/dev/null 2>&1; then\n  emulate sh\n  NULLCMD=:\n  # Zsh 3.x and 4.x performs word splitting on ${1+\"$@\"}, which\n  # is contrary to our usage.  Disable this feature.\n  alias -g '${1+\"$@\"}'='\"$@\"'\nelif test -n \"${BASH_VERSION+set}\" && (set -o posix) >/dev/null 2>&1; then\n  set -o posix\nfi\nDUALCASE=1; export DUALCASE # for MKS sh\n\n# Support unset when possible.\nif ( (MAIL=60; unset MAIL) || exit) >/dev/null 2>&1; then\n  as_unset=unset\nelse\n  as_unset=false\nfi\n\n\n# Work around bugs in pre-3.0 UWIN ksh.\n$as_unset ENV MAIL MAILPATH\nPS1='$ '\nPS2='> '\nPS4='+ '\n\n# NLS nuisances.\nfor as_var in \\\n  LANG LANGUAGE LC_ADDRESS LC_ALL LC_COLLATE LC_CTYPE LC_IDENTIFICATION \\\n  LC_MEASUREMENT LC_MESSAGES LC_MONETARY LC_NAME LC_NUMERIC LC_PAPER \\\n  LC_TELEPHONE LC_TIME\ndo\n  if (set +x; test -z \"`(eval $as_var=C; export $as_var) 2>&1`\"); then\n    eval $as_var=C; export $as_var\n  else\n    $as_unset $as_var\n  fi\ndone\n\n# Required to use basename.\nif expr a : '\\(a\\)' >/dev/null 2>&1; then\n  as_expr=expr\nelse\n  as_expr=false\nfi\n\nif (basename /) >/dev/null 2>&1 && test \"X`basename / 2>&1`\" = \"X/\"; then\n  as_basename=basename\nelse\n  as_basename=false\nfi\n\n\n# Name of the executable.\nas_me=`$as_basename \"$0\" ||\n$as_expr X/\"$0\" : '.*/\\([^/][^/]*\\)/*$' \\| \\\n\t X\"$0\" : 'X\\(//\\)$' \\| \\\n\t X\"$0\" : 'X\\(/\\)$' \\| \\\n\t .     : '\\(.\\)' 2>/dev/null ||\necho X/\"$0\" |\n    sed '/^.*\\/\\([^/][^/]*\\)\\/*$/{ s//\\1/; q; }\n  \t  /^X\\/\\(\\/\\/\\)$/{ s//\\1/; q; }\n  \t  /^X\\/\\(\\/\\).*/{ s//\\1/; q; }\n  \t  s/.*/./; q'`\n\n\n# PATH needs CR, and LINENO needs CR and PATH.\n# Avoid depending upon Character Ranges.\nas_cr_letters='abcdefghijklmnopqrstuvwxyz'\nas_cr_LETTERS='ABCDEFGHIJKLMNOPQRSTUVWXYZ'\nas_cr_Letters=$as_cr_letters$as_cr_LETTERS\nas_cr_digits='0123456789'\nas_cr_alnum=$as_cr_Letters$as_cr_digits\n\n# The user is always right.\nif test \"${PATH_SEPARATOR+set}\" != set; then\n  echo \"#! /bin/sh\" >conf$$.sh\n  echo  \"exit 0\"   >>conf$$.sh\n  chmod +x conf$$.sh\n  if (PATH=\"/nonexistent;.\"; conf$$.sh) >/dev/null 2>&1; then\n    PATH_SEPARATOR=';'\n  else\n    PATH_SEPARATOR=:\n  fi\n  rm -f conf$$.sh\nfi\n\n\n  as_lineno_1=$LINENO\n  as_lineno_2=$LINENO\n  as_lineno_3=`(expr $as_lineno_1 + 1) 2>/dev/null`\n  test \"x$as_lineno_1\" != \"x$as_lineno_2\" &&\n  test \"x$as_lineno_3\"  = \"x$as_lineno_2\"  || {\n  # Find who we are.  Look in the path if we contain no path at all\n  # relative or not.\n  case $0 in\n    *[\\\\/]* ) as_myself=$0 ;;\n    *) as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in $PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  test -r \"$as_dir/$0\" && as_myself=$as_dir/$0 && break\ndone\n\n       ;;\n  esac\n  # We did not find ourselves, most probably we were run as `sh COMMAND'\n  # in which case we are not to be found in the path.\n  if test \"x$as_myself\" = x; then\n    as_myself=$0\n  fi\n  if test ! -f \"$as_myself\"; then\n    { { echo \"$as_me:$LINENO: error: cannot find myself; rerun with an absolute path\" >&5\necho \"$as_me: error: cannot find myself; rerun with an absolute path\" >&2;}\n   { (exit 1); exit 1; }; }\n  fi\n  case $CONFIG_SHELL in\n  '')\n    as_save_IFS=$IFS; IFS=$PATH_SEPARATOR\nfor as_dir in /bin$PATH_SEPARATOR/usr/bin$PATH_SEPARATOR$PATH\ndo\n  IFS=$as_save_IFS\n  test -z \"$as_dir\" && as_dir=.\n  for as_base in sh bash ksh sh5; do\n\t case $as_dir in\n\t /*)\n\t   if (\"$as_dir/$as_base\" -c '\n  as_lineno_1=$LINENO\n  as_lineno_2=$LINENO\n  as_lineno_3=`(expr $as_lineno_1 + 1) 2>/dev/null`\n  test \"x$as_lineno_1\" != \"x$as_lineno_2\" &&\n  test \"x$as_lineno_3\"  = \"x$as_lineno_2\" ') 2>/dev/null; then\n\t     $as_unset BASH_ENV || test \"${BASH_ENV+set}\" != set || { BASH_ENV=; export BASH_ENV; }\n\t     $as_unset ENV || test \"${ENV+set}\" != set || { ENV=; export ENV; }\n\t     CONFIG_SHELL=$as_dir/$as_base\n\t     export CONFIG_SHELL\n\t     exec \"$CONFIG_SHELL\" \"$0\" ${1+\"$@\"}\n\t   fi;;\n\t esac\n       done\ndone\n;;\n  esac\n\n  # Create $as_me.lineno as a copy of $as_myself, but with $LINENO\n  # uniformly replaced by the line number.  The first 'sed' inserts a\n  # line-number line before each line; the second 'sed' does the real\n  # work.  The second script uses 'N' to pair each line-number line\n  # with the numbered line, and appends trailing '-' during\n  # substitution so that $LINENO is not a special case at line end.\n  # (Raja R Harinath suggested sed '=', and Paul Eggert wrote the\n  # second 'sed' script.  Blame Lee E. McMahon for sed's syntax.  :-)\n  sed '=' <$as_myself |\n    sed '\n      N\n      s,$,-,\n      : loop\n      s,^\\(['$as_cr_digits']*\\)\\(.*\\)[$]LINENO\\([^'$as_cr_alnum'_]\\),\\1\\2\\1\\3,\n      t loop\n      s,-$,,\n      s,^['$as_cr_digits']*\\n,,\n    ' >$as_me.lineno &&\n  chmod +x $as_me.lineno ||\n    { { echo \"$as_me:$LINENO: error: cannot create $as_me.lineno; rerun with a POSIX shell\" >&5\necho \"$as_me: error: cannot create $as_me.lineno; rerun with a POSIX shell\" >&2;}\n   { (exit 1); exit 1; }; }\n\n  # Don't try to exec as it changes $[0], causing all sort of problems\n  # (the dirname of $[0] is not the place where we might find the\n  # original and so on.  Autoconf is especially sensible to this).\n  . ./$as_me.lineno\n  # Exit status is that of the last command.\n  exit\n}\n\n\ncase `echo \"testing\\c\"; echo 1,2,3`,`echo -n testing; echo 1,2,3` in\n  *c*,-n*) ECHO_N= ECHO_C='\n' ECHO_T='\t' ;;\n  *c*,*  ) ECHO_N=-n ECHO_C= ECHO_T= ;;\n  *)       ECHO_N= ECHO_C='\\c' ECHO_T= ;;\nesac\n\nif expr a : '\\(a\\)' >/dev/null 2>&1; then\n  as_expr=expr\nelse\n  as_expr=false\nfi\n\nrm -f conf$$ conf$$.exe conf$$.file\necho >conf$$.file\nif ln -s conf$$.file conf$$ 2>/dev/null; then\n  # We could just check for DJGPP; but this test a) works b) is more generic\n  # and c) will remain valid once DJGPP supports symlinks (DJGPP 2.04).\n  if test -f conf$$.exe; then\n    # Don't use ln at all; we don't have any links\n    as_ln_s='cp -p'\n  else\n    as_ln_s='ln -s'\n  fi\nelif ln conf$$.file conf$$ 2>/dev/null; then\n  as_ln_s=ln\nelse\n  as_ln_s='cp -p'\nfi\nrm -f conf$$ conf$$.exe conf$$.file\n\nif mkdir -p . 2>/dev/null; then\n  as_mkdir_p=:\nelse\n  test -d ./-p && rmdir ./-p\n  as_mkdir_p=false\nfi\n\nas_executable_p=\"test -f\"\n\n# Sed expression to map a string onto a valid CPP name.\nas_tr_cpp=\"eval sed 'y%*$as_cr_letters%P$as_cr_LETTERS%;s%[^_$as_cr_alnum]%_%g'\"\n\n# Sed expression to map a string onto a valid variable name.\nas_tr_sh=\"eval sed 'y%*+%pp%;s%[^_$as_cr_alnum]%_%g'\"\n\n\n# IFS\n# We need space, tab and new line, in precisely that order.\nas_nl='\n'\nIFS=\" \t$as_nl\"\n\n# CDPATH.\n$as_unset CDPATH\n\nexec 6>&1\n\n# Open the log real soon, to keep \\$[0] and so on meaningful, and to\n# report actual input values of CONFIG_FILES etc. instead of their\n# values after options handling.  Logging --version etc. is OK.\nexec 5>>config.log\n{\n  echo\n  sed 'h;s/./-/g;s/^.../## /;s/...$/ ##/;p;x;p;x' <<_ASBOX\n## Running $as_me. ##\n_ASBOX\n} >&5\ncat >&5 <<_CSEOF\n\nThis file was extended by lpsolve $as_me 5.5.2.0, which was\ngenerated by GNU Autoconf 2.59.  Invocation command line was\n\n  CONFIG_FILES    = $CONFIG_FILES\n  CONFIG_HEADERS  = $CONFIG_HEADERS\n  CONFIG_LINKS    = $CONFIG_LINKS\n  CONFIG_COMMANDS = $CONFIG_COMMANDS\n  $ $0 $@\n\n_CSEOF\necho \"on `(hostname || uname -n) 2>/dev/null | sed 1q`\" >&5\necho >&5\n_ACEOF\n\n# Files that config.status was made for.\nif test -n \"$ac_config_files\"; then\n  echo \"config_files=\\\"$ac_config_files\\\"\" >>$CONFIG_STATUS\nfi\n\nif test -n \"$ac_config_headers\"; then\n  echo \"config_headers=\\\"$ac_config_headers\\\"\" >>$CONFIG_STATUS\nfi\n\nif test -n \"$ac_config_links\"; then\n  echo \"config_links=\\\"$ac_config_links\\\"\" >>$CONFIG_STATUS\nfi\n\nif test -n \"$ac_config_commands\"; then\n  echo \"config_commands=\\\"$ac_config_commands\\\"\" >>$CONFIG_STATUS\nfi\n\ncat >>$CONFIG_STATUS <<\\_ACEOF\n\nac_cs_usage=\"\\\n\\`$as_me' instantiates files from templates according to the\ncurrent configuration.\n\nUsage: $0 [OPTIONS] [FILE]...\n\n  -h, --help       print this help, then exit\n  -V, --version    print version number, then exit\n  -q, --quiet      do not print progress messages\n  -d, --debug      don't remove temporary files\n      --recheck    update $as_me by reconfiguring in the same conditions\n  --file=FILE[:TEMPLATE]\n\t\t   instantiate the configuration file FILE\n\nConfiguration files:\n$config_files\n\nReport bugs to <bug-autoconf@gnu.org>.\"\n_ACEOF\n\ncat >>$CONFIG_STATUS <<_ACEOF\nac_cs_version=\"\\\\\nlpsolve config.status 5.5.2.0\nconfigured by $0, generated by GNU Autoconf 2.59,\n  with options \\\\\"`echo \"$ac_configure_args\" | sed 's/[\\\\\"\"\\`\\$]/\\\\\\\\&/g'`\\\\\"\n\nCopyright (C) 2003 Free Software Foundation, Inc.\nThis config.status script is free software; the Free Software Foundation\ngives unlimited permission to copy, distribute and modify it.\"\nsrcdir=$srcdir\nINSTALL=\"$INSTALL\"\n_ACEOF\n\ncat >>$CONFIG_STATUS <<\\_ACEOF\n# If no file are specified by the user, then we need to provide default\n# value.  By we need to know if files were specified by the user.\nac_need_defaults=:\nwhile test $# != 0\ndo\n  case $1 in\n  --*=*)\n    ac_option=`expr \"x$1\" : 'x\\([^=]*\\)='`\n    ac_optarg=`expr \"x$1\" : 'x[^=]*=\\(.*\\)'`\n    ac_shift=:\n    ;;\n  -*)\n    ac_option=$1\n    ac_optarg=$2\n    ac_shift=shift\n    ;;\n  *) # This is not an option, so the user has probably given explicit\n     # arguments.\n     ac_option=$1\n     ac_need_defaults=false;;\n  esac\n\n  case $ac_option in\n  # Handling of the options.\n_ACEOF\ncat >>$CONFIG_STATUS <<\\_ACEOF\n  -recheck | --recheck | --rechec | --reche | --rech | --rec | --re | --r)\n    ac_cs_recheck=: ;;\n  --version | --vers* | -V )\n    echo \"$ac_cs_version\"; exit 0 ;;\n  --he | --h)\n    # Conflict between --help and --header\n    { { echo \"$as_me:$LINENO: error: ambiguous option: $1\nTry \\`$0 --help' for more information.\" >&5\necho \"$as_me: error: ambiguous option: $1\nTry \\`$0 --help' for more information.\" >&2;}\n   { (exit 1); exit 1; }; };;\n  --help | --hel | -h )\n    echo \"$ac_cs_usage\"; exit 0 ;;\n  --debug | --d* | -d )\n    debug=: ;;\n  --file | --fil | --fi | --f )\n    $ac_shift\n    CONFIG_FILES=\"$CONFIG_FILES $ac_optarg\"\n    ac_need_defaults=false;;\n  --header | --heade | --head | --hea )\n    $ac_shift\n    CONFIG_HEADERS=\"$CONFIG_HEADERS $ac_optarg\"\n    ac_need_defaults=false;;\n  -q | -quiet | --quiet | --quie | --qui | --qu | --q \\\n  | -silent | --silent | --silen | --sile | --sil | --si | --s)\n    ac_cs_silent=: ;;\n\n  # This is an error.\n  -*) { { echo \"$as_me:$LINENO: error: unrecognized option: $1\nTry \\`$0 --help' for more information.\" >&5\necho \"$as_me: error: unrecognized option: $1\nTry \\`$0 --help' for more information.\" >&2;}\n   { (exit 1); exit 1; }; } ;;\n\n  *) ac_config_targets=\"$ac_config_targets $1\" ;;\n\n  esac\n  shift\ndone\n\nac_configure_extra_args=\n\nif $ac_cs_silent; then\n  exec 6>/dev/null\n  ac_configure_extra_args=\"$ac_configure_extra_args --silent\"\nfi\n\n_ACEOF\ncat >>$CONFIG_STATUS <<_ACEOF\nif \\$ac_cs_recheck; then\n  echo \"running $SHELL $0 \" $ac_configure_args \\$ac_configure_extra_args \" --no-create --no-recursion\" >&6\n  exec $SHELL $0 $ac_configure_args \\$ac_configure_extra_args --no-create --no-recursion\nfi\n\n_ACEOF\n\n\n\n\n\ncat >>$CONFIG_STATUS <<\\_ACEOF\nfor ac_config_target in $ac_config_targets\ndo\n  case \"$ac_config_target\" in\n  # Handling of arguments.\n  \"Makefile\" ) CONFIG_FILES=\"$CONFIG_FILES Makefile\" ;;\n  *) { { echo \"$as_me:$LINENO: error: invalid argument: $ac_config_target\" >&5\necho \"$as_me: error: invalid argument: $ac_config_target\" >&2;}\n   { (exit 1); exit 1; }; };;\n  esac\ndone\n\n# If the user did not use the arguments to specify the items to instantiate,\n# then the envvar interface is used.  Set only those that are not.\n# We use the long form for the default assignment because of an extremely\n# bizarre bug on SunOS 4.1.3.\nif $ac_need_defaults; then\n  test \"${CONFIG_FILES+set}\" = set || CONFIG_FILES=$config_files\nfi\n\n# Have a temporary directory for convenience.  Make it in the build tree\n# simply because there is no reason to put it here, and in addition,\n# creating and moving files from /tmp can sometimes cause problems.\n# Create a temporary directory, and hook for its removal unless debugging.\n$debug ||\n{\n  trap 'exit_status=$?; rm -rf $tmp && exit $exit_status' 0\n  trap '{ (exit 1); exit 1; }' 1 2 13 15\n}\n\n# Create a (secure) tmp directory for tmp files.\n\n{\n  tmp=`(umask 077 && mktemp -d -q \"./confstatXXXXXX\") 2>/dev/null` &&\n  test -n \"$tmp\" && test -d \"$tmp\"\n}  ||\n{\n  tmp=./confstat$$-$RANDOM\n  (umask 077 && mkdir $tmp)\n} ||\n{\n   echo \"$me: cannot create a temporary directory in .\" >&2\n   { (exit 1); exit 1; }\n}\n\n_ACEOF\n\ncat >>$CONFIG_STATUS <<_ACEOF\n\n#\n# CONFIG_FILES section.\n#\n\n# No need to generate the scripts if there are no CONFIG_FILES.\n# This happens for instance when ./config.status config.h\nif test -n \"\\$CONFIG_FILES\"; then\n  # Protect against being on the right side of a sed subst in config.status.\n  sed 's/,@/@@/; s/@,/@@/; s/,;t t\\$/@;t t/; /@;t t\\$/s/[\\\\\\\\&,]/\\\\\\\\&/g;\n   s/@@/,@/; s/@@/@,/; s/@;t t\\$/,;t t/' >\\$tmp/subs.sed <<\\\\CEOF\ns,@SHELL@,$SHELL,;t t\ns,@PATH_SEPARATOR@,$PATH_SEPARATOR,;t t\ns,@PACKAGE_NAME@,$PACKAGE_NAME,;t t\ns,@PACKAGE_TARNAME@,$PACKAGE_TARNAME,;t t\ns,@PACKAGE_VERSION@,$PACKAGE_VERSION,;t t\ns,@PACKAGE_STRING@,$PACKAGE_STRING,;t t\ns,@PACKAGE_BUGREPORT@,$PACKAGE_BUGREPORT,;t t\ns,@exec_prefix@,$exec_prefix,;t t\ns,@prefix@,$prefix,;t t\ns,@program_transform_name@,$program_transform_name,;t t\ns,@bindir@,$bindir,;t t\ns,@sbindir@,$sbindir,;t t\ns,@libexecdir@,$libexecdir,;t t\ns,@datadir@,$datadir,;t t\ns,@sysconfdir@,$sysconfdir,;t t\ns,@sharedstatedir@,$sharedstatedir,;t t\ns,@localstatedir@,$localstatedir,;t t\ns,@libdir@,$libdir,;t t\ns,@includedir@,$includedir,;t t\ns,@oldincludedir@,$oldincludedir,;t t\ns,@infodir@,$infodir,;t t\ns,@mandir@,$mandir,;t t\ns,@build_alias@,$build_alias,;t t\ns,@host_alias@,$host_alias,;t t\ns,@target_alias@,$target_alias,;t t\ns,@DEFS@,$DEFS,;t t\ns,@ECHO_C@,$ECHO_C,;t t\ns,@ECHO_N@,$ECHO_N,;t t\ns,@ECHO_T@,$ECHO_T,;t t\ns,@LIBS@,$LIBS,;t t\ns,@build@,$build,;t t\ns,@build_cpu@,$build_cpu,;t t\ns,@build_vendor@,$build_vendor,;t t\ns,@build_os@,$build_os,;t t\ns,@host@,$host,;t t\ns,@host_cpu@,$host_cpu,;t t\ns,@host_vendor@,$host_vendor,;t t\ns,@host_os@,$host_os,;t t\ns,@SO@,$SO,;t t\ns,@CCSHARED@,$CCSHARED,;t t\ns,@DEF@,$DEF,;t t\ns,@SHARED_LIB@,$SHARED_LIB,;t t\ns,@CC@,$CC,;t t\ns,@CFLAGS@,$CFLAGS,;t t\ns,@LDFLAGS@,$LDFLAGS,;t t\ns,@CPPFLAGS@,$CPPFLAGS,;t t\ns,@ac_ct_CC@,$ac_ct_CC,;t t\ns,@EXEEXT@,$EXEEXT,;t t\ns,@OBJEXT@,$OBJEXT,;t t\ns,@INSTALL_PROGRAM@,$INSTALL_PROGRAM,;t t\ns,@INSTALL_SCRIPT@,$INSTALL_SCRIPT,;t t\ns,@INSTALL_DATA@,$INSTALL_DATA,;t t\ns,@LIBOBJS@,$LIBOBJS,;t t\ns,@LTLIBOBJS@,$LTLIBOBJS,;t t\nCEOF\n\n_ACEOF\n\n  cat >>$CONFIG_STATUS <<\\_ACEOF\n  # Split the substitutions into bite-sized pieces for seds with\n  # small command number limits, like on Digital OSF/1 and HP-UX.\n  ac_max_sed_lines=48\n  ac_sed_frag=1 # Number of current file.\n  ac_beg=1 # First line for current file.\n  ac_end=$ac_max_sed_lines # Line after last line for current file.\n  ac_more_lines=:\n  ac_sed_cmds=\n  while $ac_more_lines; do\n    if test $ac_beg -gt 1; then\n      sed \"1,${ac_beg}d; ${ac_end}q\" $tmp/subs.sed >$tmp/subs.frag\n    else\n      sed \"${ac_end}q\" $tmp/subs.sed >$tmp/subs.frag\n    fi\n    if test ! -s $tmp/subs.frag; then\n      ac_more_lines=false\n    else\n      # The purpose of the label and of the branching condition is to\n      # speed up the sed processing (if there are no `@' at all, there\n      # is no need to browse any of the substitutions).\n      # These are the two extra sed commands mentioned above.\n      (echo ':t\n  /@[a-zA-Z_][a-zA-Z_0-9]*@/!b' && cat $tmp/subs.frag) >$tmp/subs-$ac_sed_frag.sed\n      if test -z \"$ac_sed_cmds\"; then\n\tac_sed_cmds=\"sed -f $tmp/subs-$ac_sed_frag.sed\"\n      else\n\tac_sed_cmds=\"$ac_sed_cmds | sed -f $tmp/subs-$ac_sed_frag.sed\"\n      fi\n      ac_sed_frag=`expr $ac_sed_frag + 1`\n      ac_beg=$ac_end\n      ac_end=`expr $ac_end + $ac_max_sed_lines`\n    fi\n  done\n  if test -z \"$ac_sed_cmds\"; then\n    ac_sed_cmds=cat\n  fi\nfi # test -n \"$CONFIG_FILES\"\n\n_ACEOF\ncat >>$CONFIG_STATUS <<\\_ACEOF\nfor ac_file in : $CONFIG_FILES; do test \"x$ac_file\" = x: && continue\n  # Support \"outfile[:infile[:infile...]]\", defaulting infile=\"outfile.in\".\n  case $ac_file in\n  - | *:- | *:-:* ) # input from stdin\n\tcat >$tmp/stdin\n\tac_file_in=`echo \"$ac_file\" | sed 's,[^:]*:,,'`\n\tac_file=`echo \"$ac_file\" | sed 's,:.*,,'` ;;\n  *:* ) ac_file_in=`echo \"$ac_file\" | sed 's,[^:]*:,,'`\n\tac_file=`echo \"$ac_file\" | sed 's,:.*,,'` ;;\n  * )   ac_file_in=$ac_file.in ;;\n  esac\n\n  # Compute @srcdir@, @top_srcdir@, and @INSTALL@ for subdirectories.\n  ac_dir=`(dirname \"$ac_file\") 2>/dev/null ||\n$as_expr X\"$ac_file\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$ac_file\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$ac_file\" : 'X\\(//\\)$' \\| \\\n\t X\"$ac_file\" : 'X\\(/\\)' \\| \\\n\t .     : '\\(.\\)' 2>/dev/null ||\necho X\"$ac_file\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\/\\)[^/].*/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\/\\)$/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\).*/{ s//\\1/; q; }\n  \t  s/.*/./; q'`\n  { if $as_mkdir_p; then\n    mkdir -p \"$ac_dir\"\n  else\n    as_dir=\"$ac_dir\"\n    as_dirs=\n    while test ! -d \"$as_dir\"; do\n      as_dirs=\"$as_dir $as_dirs\"\n      as_dir=`(dirname \"$as_dir\") 2>/dev/null ||\n$as_expr X\"$as_dir\" : 'X\\(.*[^/]\\)//*[^/][^/]*/*$' \\| \\\n\t X\"$as_dir\" : 'X\\(//\\)[^/]' \\| \\\n\t X\"$as_dir\" : 'X\\(//\\)$' \\| \\\n\t X\"$as_dir\" : 'X\\(/\\)' \\| \\\n\t .     : '\\(.\\)' 2>/dev/null ||\necho X\"$as_dir\" |\n    sed '/^X\\(.*[^/]\\)\\/\\/*[^/][^/]*\\/*$/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\/\\)[^/].*/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\/\\)$/{ s//\\1/; q; }\n  \t  /^X\\(\\/\\).*/{ s//\\1/; q; }\n  \t  s/.*/./; q'`\n    done\n    test ! -n \"$as_dirs\" || mkdir $as_dirs\n  fi || { { echo \"$as_me:$LINENO: error: cannot create directory \\\"$ac_dir\\\"\" >&5\necho \"$as_me: error: cannot create directory \\\"$ac_dir\\\"\" >&2;}\n   { (exit 1); exit 1; }; }; }\n\n  ac_builddir=.\n\nif test \"$ac_dir\" != .; then\n  ac_dir_suffix=/`echo \"$ac_dir\" | sed 's,^\\.[\\\\/],,'`\n  # A \"../\" for each directory in $ac_dir_suffix.\n  ac_top_builddir=`echo \"$ac_dir_suffix\" | sed 's,/[^\\\\/]*,../,g'`\nelse\n  ac_dir_suffix= ac_top_builddir=\nfi\n\ncase $srcdir in\n  .)  # No --srcdir option.  We are building in place.\n    ac_srcdir=.\n    if test -z \"$ac_top_builddir\"; then\n       ac_top_srcdir=.\n    else\n       ac_top_srcdir=`echo $ac_top_builddir | sed 's,/$,,'`\n    fi ;;\n  [\\\\/]* | ?:[\\\\/]* )  # Absolute path.\n    ac_srcdir=$srcdir$ac_dir_suffix;\n    ac_top_srcdir=$srcdir ;;\n  *) # Relative path.\n    ac_srcdir=$ac_top_builddir$srcdir$ac_dir_suffix\n    ac_top_srcdir=$ac_top_builddir$srcdir ;;\nesac\n\n# Do not use `cd foo && pwd` to compute absolute paths, because\n# the directories may not exist.\ncase `pwd` in\n.) ac_abs_builddir=\"$ac_dir\";;\n*)\n  case \"$ac_dir\" in\n  .) ac_abs_builddir=`pwd`;;\n  [\\\\/]* | ?:[\\\\/]* ) ac_abs_builddir=\"$ac_dir\";;\n  *) ac_abs_builddir=`pwd`/\"$ac_dir\";;\n  esac;;\nesac\ncase $ac_abs_builddir in\n.) ac_abs_top_builddir=${ac_top_builddir}.;;\n*)\n  case ${ac_top_builddir}. in\n  .) ac_abs_top_builddir=$ac_abs_builddir;;\n  [\\\\/]* | ?:[\\\\/]* ) ac_abs_top_builddir=${ac_top_builddir}.;;\n  *) ac_abs_top_builddir=$ac_abs_builddir/${ac_top_builddir}.;;\n  esac;;\nesac\ncase $ac_abs_builddir in\n.) ac_abs_srcdir=$ac_srcdir;;\n*)\n  case $ac_srcdir in\n  .) ac_abs_srcdir=$ac_abs_builddir;;\n  [\\\\/]* | ?:[\\\\/]* ) ac_abs_srcdir=$ac_srcdir;;\n  *) ac_abs_srcdir=$ac_abs_builddir/$ac_srcdir;;\n  esac;;\nesac\ncase $ac_abs_builddir in\n.) ac_abs_top_srcdir=$ac_top_srcdir;;\n*)\n  case $ac_top_srcdir in\n  .) ac_abs_top_srcdir=$ac_abs_builddir;;\n  [\\\\/]* | ?:[\\\\/]* ) ac_abs_top_srcdir=$ac_top_srcdir;;\n  *) ac_abs_top_srcdir=$ac_abs_builddir/$ac_top_srcdir;;\n  esac;;\nesac\n\n\n  case $INSTALL in\n  [\\\\/$]* | ?:[\\\\/]* ) ac_INSTALL=$INSTALL ;;\n  *) ac_INSTALL=$ac_top_builddir$INSTALL ;;\n  esac\n\n  if test x\"$ac_file\" != x-; then\n    { echo \"$as_me:$LINENO: creating $ac_file\" >&5\necho \"$as_me: creating $ac_file\" >&6;}\n    rm -f \"$ac_file\"\n  fi\n  # Let's still pretend it is `configure' which instantiates (i.e., don't\n  # use $as_me), people would be surprised to read:\n  #    /* config.h.  Generated by config.status.  */\n  if test x\"$ac_file\" = x-; then\n    configure_input=\n  else\n    configure_input=\"$ac_file.  \"\n  fi\n  configure_input=$configure_input\"Generated from `echo $ac_file_in |\n\t\t\t\t     sed 's,.*/,,'` by configure.\"\n\n  # First look for the input files in the build tree, otherwise in the\n  # src tree.\n  ac_file_inputs=`IFS=:\n    for f in $ac_file_in; do\n      case $f in\n      -) echo $tmp/stdin ;;\n      [\\\\/$]*)\n\t # Absolute (can't be DOS-style, as IFS=:)\n\t test -f \"$f\" || { { echo \"$as_me:$LINENO: error: cannot find input file: $f\" >&5\necho \"$as_me: error: cannot find input file: $f\" >&2;}\n   { (exit 1); exit 1; }; }\n\t echo \"$f\";;\n      *) # Relative\n\t if test -f \"$f\"; then\n\t   # Build tree\n\t   echo \"$f\"\n\t elif test -f \"$srcdir/$f\"; then\n\t   # Source tree\n\t   echo \"$srcdir/$f\"\n\t else\n\t   # /dev/null tree\n\t   { { echo \"$as_me:$LINENO: error: cannot find input file: $f\" >&5\necho \"$as_me: error: cannot find input file: $f\" >&2;}\n   { (exit 1); exit 1; }; }\n\t fi;;\n      esac\n    done` || { (exit 1); exit 1; }\n_ACEOF\ncat >>$CONFIG_STATUS <<_ACEOF\n  sed \"$ac_vpsub\n$extrasub\n_ACEOF\ncat >>$CONFIG_STATUS <<\\_ACEOF\n:t\n/@[a-zA-Z_][a-zA-Z_0-9]*@/!b\ns,@configure_input@,$configure_input,;t t\ns,@srcdir@,$ac_srcdir,;t t\ns,@abs_srcdir@,$ac_abs_srcdir,;t t\ns,@top_srcdir@,$ac_top_srcdir,;t t\ns,@abs_top_srcdir@,$ac_abs_top_srcdir,;t t\ns,@builddir@,$ac_builddir,;t t\ns,@abs_builddir@,$ac_abs_builddir,;t t\ns,@top_builddir@,$ac_top_builddir,;t t\ns,@abs_top_builddir@,$ac_abs_top_builddir,;t t\ns,@INSTALL@,$ac_INSTALL,;t t\n\" $ac_file_inputs | (eval \"$ac_sed_cmds\") >$tmp/out\n  rm -f $tmp/stdin\n  if test x\"$ac_file\" != x-; then\n    mv $tmp/out $ac_file\n  else\n    cat $tmp/out\n    rm -f $tmp/out\n  fi\n\ndone\n_ACEOF\n\ncat >>$CONFIG_STATUS <<\\_ACEOF\n\n{ (exit 0); exit 0; }\n_ACEOF\nchmod +x $CONFIG_STATUS\nac_clean_files=$ac_clean_files_save\n\n\n# configure is writing to config.log, and then calls config.status.\n# config.status does its own redirection, appending to config.log.\n# Unfortunately, on DOS this fails, as config.log is still kept open\n# by configure, so config.status won't be able to write to it; its\n# output is simply discarded.  So we exec the FD to /dev/null,\n# effectively closing config.log, so it can be properly (re)opened and\n# appended to by config.status.  When coming back to configure, we\n# need to make the FD available again.\nif test \"$no_create\" != yes; then\n  ac_cs_success=:\n  ac_config_status_args=\n  test \"$silent\" = yes &&\n    ac_config_status_args=\"$ac_config_status_args --quiet\"\n  exec 5>/dev/null\n  $SHELL $CONFIG_STATUS $ac_config_status_args || ac_cs_success=false\n  exec 5>>config.log\n  # Use ||, not &&, to avoid exiting from the if with $? = 1, which\n  # would make configure fail if this is the last instruction.\n  $ac_cs_success || { (exit 1); exit 1; }\nfi\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/configure.ac",
    "content": "AC_PREREQ(2.52)\nAC_INIT([lpsolve],5.5.0.14,[], [])\nAC_CONFIG_SRCDIR(lp_simplex.c)\nAC_CANONICAL_HOST\n\nSHARED_LIB=liblpsolve55.so\nSO=.so\ncase $host_os in\n  hp*|HP*)\n    DEF=-ldld\n    case `uname -m` in\n      ia64) SO=.so;;\n      *)    SO=.sl;;\n    esac\n    if test \"$GCC\" = yes;\n      then CCSHARED=\"-fPIC\";\n      else CCSHARED=\"+z\";\n    fi;;\n  CYGWIN*)\n    SO=.dll;;\n  linux)\n    CCSHARED=\"-fPIC\";;\n  apple-darwin)\n    DEF=-ldl -idirafter /usr/include/sys -DINTEGERTIME -Wno-long-double\n    ;;\n  OpenUNIX*|UnixWare*)\n    DEF='-dy -DNOLONGLONG'\n    if test \"$GCC\" = \"yes\"\n      then CCSHARED=\"-fPIC\"\n      else CCSHARED=\"-K PIC\"\n    fi;;\n  SCO_SV*)\n    DEF='-dy -DNOLONGLONG'\n    if test \"$GCC\" = \"yes\"\n      then CCSHARED=\"-fPIC\"\n      else CCSHARED=\"-Kpic -belf\"\n    fi;;\n *)\nesac\n\nAC_SUBST(SO)\nAC_SUBST(CCSHARED)\nAC_SUBST(DEF)\nAC_SUBST(SHARED_LIB)\n\nAC_PROG_CC\nif test \"x$GCC\" != \"xyes\"\nthen\n  echo \"*** non GNU CC compiler detected.\"\n  echo \"*** This package has not been tested very well with non GNU compilers\"\nfi\n\nAC_PROG_INSTALL\nAC_CONFIG_FILES([ \\\n\tMakefile \\\n])\nAC_OUTPUT\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/declare.h",
    "content": "#ifndef __DECLARE_H__\n#define __DECLARE_H__\n\n#if !defined ANSI_PROTOTYPES\n# if defined MSDOS || defined __BORLANDC__ || defined __HIGHC__ || defined SCO_UNIX || defined AViiON\n#  define ANSI_PROTOTYPES 1\n# endif\n#endif\n\n#if ANSI_PROTOTYPES!=0\n# define __OF(args)  args\n#else\n# define __OF(args)  ()\n#endif\n\n#if defined __HIGHC__\n# define VARARG    ...\n#else\n# define VARARG\n#endif\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/cbcc32.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the demo program with the Borland C++ 5.5 compiler for Windows\r\n\r\nset src=../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c ../lp_MDO.c ../colamd/colamd.c\r\n\r\nset c=bcc32 -w-8004 -w-8057\r\n\r\nset PLATFORM=win32\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\n%c% -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared -a8 -DWIN32 -DYY_NEVER_INTERACTIVE=1 -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine demo.c -ebin\\%PLATFORM%\\demo.exe %src%\r\n\r\nif exist *.obj del *.obj\r\n\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/ccc",
    "content": "src='../lp_MDO.c ../shared/commonlib.c ../colamd/colamd.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\nc=cc\n\nmath=-lm\n\ndef=\nif [ \"$PLATFORM\" = \"SCO_UNIX\" ]\nthen def='-dy -K PIC -DNOLONGLONG'\n     dl=-lc\nelse dl=-ldl\nfi\n\nopts='-O3'\n\n$c -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared $opts $def -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine demo.c $src -o demo $math $dl\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/ccc.osx",
    "content": "src='../bfp/lp_MDO.c ../commonlib.c ../myblas.c ../colamd/colamd.c ../ini.c ../fortify.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_etaPFI/lp_etaPFI.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c demo.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\nc=cc\n\nmath=-lm\n\ndef=\nif [ \"$PLATFORM\" = \"SCO_UNIX\" ]\nthen def='-DLoadInverseLib=0 -DLoadLanguageLib=0 -D__HYPER=long'\nelse dl=-ldl\nfi\n\nopts='-idirafter /usr/include/sys -O3 -DINTEGERTIME -Wno-long-double'\n\n$c -I.. -I../bfp -I../bfp/bfp_etaPFI -I../colamd $opts $def -DYY_NEVER_INTERACTIVE -DPARSER_LP $src -o demo $math $dl\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/cgcc.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the demo program with the gnu gcc compiler under DOS/Windows\r\n\r\nREM There are two ways to do that: use the lpsolve code directly or use that static library.\r\n\r\nset c=gcc\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% platform.c -o platform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nrem link lpsolve code with application\r\nset src=../lp_MDO.c ../shared/commonlib.c ../colamd/colamd.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c\r\n\r\nrem statically link lpsolve library\r\nrem set src=../lpsolve55/bin/%PLATFORM%/liblpsolve55.a\r\n\r\n%c% -DINLINE=static -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared -O3 -DBFP_CALLMODEL=__stdcall -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine demo.c %src% -o bin\\%PLATFORM%\\demo.exe\r\n\r\nif exist *.o del *.o\r\n\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/cvc6.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the demo program with the Microsoft Visual C/C++ compiler under Windows\r\n\r\nset src=../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c ../lp_MDO.c ../colamd/colamd.c\r\n\r\nset c=cl\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% /nologo platform.c /Feplatform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif \"%PLATFORM%\" == \"win32\" goto ok1\r\necho.\r\necho This batch file is entended for 32 bit compilation with MS Visual C 6\r\necho For newer versions use cvc8*.bat\r\ngoto done\r\n:ok1\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\n%c% -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared /O2 /Zp8 /Gd -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine demo.c %src% -o bin\\%PLATFORM%\\demo.exe\r\n\r\nif exist *.obj del *.obj\r\n:done\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/cvc8.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the demo program with the Microsoft Visual C/C++ compiler under Windows\r\n\r\nset src=../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c ../lp_MDO.c ../colamd/colamd.c\r\n\r\nset c=cl\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% /nologo platform.c /Feplatform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\n%c% -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared /O2 /Zp8 /Gd -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE demo.c %src% /Febin\\%PLATFORM%\\demo.exe\r\n\r\nif exist *.obj del *.obj\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/demo.c",
    "content": "/*\n This program is originally made by by Jeroen J. Dirks (jeroend@tor.numetrix.com)\n Adapted by Peter Notebaert (lpsolve@peno.be)\n*/\n\n#include <stdio.h>\n\n#include \"lp_lib.h\"\n\n#if defined FORTIFY\n#include \"lp_fortify.h\"\n\nint EndOfPgr(int i)\n{\n    exit(i);\n}\n#endif\n\nvoid press_ret(void)\n{\n#if !defined NORETURN\n  printf(\"[return]\");\n  getchar();\n#endif\n}\n\nint main(void)\n{\n# if defined ERROR\n#  undef ERROR\n# endif\n# define ERROR() { fprintf(stderr, \"Error\\n\"); exit(1); }\n  lprec *lp;\n  int majorversion, minorversion, release, build;\n\n#if defined FORTIFY\n  Fortify_EnterScope();\n#endif\n\n  lp_solve_version(&majorversion, &minorversion, &release, &build);\n  printf(\"lp_solve %d.%d.%d.%d demo\\n\\n\", majorversion, minorversion, release, build);\n  printf(\"This demo will show most of the features of lp_solve %d.%d.%d.%d\\n\", majorversion, minorversion, release, build);\n  press_ret();\n  printf(\"\\nWe start by creating a new problem with 4 variables and 0 constraints\\n\");\n  printf(\"We use: lp=make_lp(0,4);\\n\");\n  if ((lp = make_lp(0,4)) == NULL)\n    ERROR();\n  press_ret();\n\n  printf(\"We can show the current problem with print_lp(lp)\\n\");\n  print_lp(lp);\n  press_ret();\n  printf(\"Now we add some constraints\\n\");\n  printf(\"add_constraint(lp, {0, 3, 2, 2, 1}, LE, 4)\\n\");\n  {\n    double row[] = {0, 3, 2, 2, 1};\n    if (!add_constraint(lp, row, LE, 4))\n      ERROR();\n  }\n  print_lp(lp);\n  press_ret();\n  printf(\"add_constraintex is now used to add a row. Only the npn-zero values must be specfied with this call.\\n\");\n  printf(\"add_constraintex(lp, 3, {4, 3, 1}, {2, 3, 4}, GE, 3)\\n\");\n  {\n    int colno[] = {2, 3, 4};\n    double row[] = {4, 3, 1};\n    if (!add_constraintex(lp, sizeof(colno) / sizeof(*colno), row, colno, GE, 3))\n      ERROR();\n  }\n  print_lp(lp);\n  press_ret();\n  printf(\"Set the objective function\\n\");\n  printf(\"set_obj_fn(lp, {0, 2, 3, -2, 3})\\n\");\n  {\n    double row[] = {0, 2, 3, -2, 3};\n    if (!set_obj_fn(lp, row))\n      ERROR();\n  }\n  print_lp(lp);\n  press_ret();\n  printf(\"Now solve the problem with printf(solve(lp));\\n\");\n  printf(\"%d\",solve(lp));\n  press_ret();\n  printf(\"The value is 0, this means we found an optimal solution\\n\");\n  printf(\"We can display this solution with print_objective(lp) and print_solution(lp)\\n\");\n  print_objective(lp);\n  print_solution(lp, 1);\n  print_constraints(lp, 1);\n\n  press_ret();\n  printf(\"The dual variables of the solution are printed with\\n\");\n  printf(\"print_duals(lp);\\n\");\n  print_duals(lp);\n  press_ret();\n  printf(\"We can change a single element in the matrix with\\n\");\n  printf(\"set_mat(lp,2,1,0.5)\\n\");\n  if (!set_mat(lp,2,1,0.5))\n    ERROR();\n  print_lp(lp);\n  press_ret();\n  printf(\"If we want to maximize the objective function use set_maxim(lp);\\n\");\n  set_maxim(lp);\n  print_lp(lp);\n  press_ret();\n  printf(\"after solving this gives us:\\n\");\n  solve(lp);\n  print_objective(lp);\n  print_solution(lp, 1);\n  print_constraints(lp, 1);\n  print_duals(lp);\n  press_ret();\n  printf(\"Change the value of a rhs element with set_rh(lp,1,7.45)\\n\");\n  set_rh(lp,1,7.45);\n  print_lp(lp);\n  solve(lp);\n  print_objective(lp);\n  print_solution(lp, 1);\n  print_constraints(lp, 1);\n  press_ret();\n  printf(\"We change %s to the integer type with\\n\", get_col_name(lp, 4));\n  printf(\"set_int(lp, 4, TRUE)\\n\");\n  set_int(lp, 4, TRUE);\n  print_lp(lp);\n  printf(\"We set branch & bound debugging on with set_debug(lp, TRUE)\\n\");\n  set_debug(lp, TRUE);\n  printf(\"and solve...\\n\");\n  press_ret();\n  solve(lp);\n  print_objective(lp);\n  print_solution(lp, 1);\n  print_constraints(lp, 1);\n  press_ret();\n  printf(\"We can set bounds on the variables with\\n\");\n  printf(\"set_lowbo(lp,2,2); & set_upbo(lp,4,5.3)\\n\");\n  set_lowbo(lp,2,2);\n  set_upbo(lp,4,5.3);\n  print_lp(lp);\n  press_ret();\n  solve(lp);\n  print_objective(lp);\n  print_solution(lp, 1);\n  print_constraints(lp, 1);\n  press_ret();\n  printf(\"Now remove a constraint with del_constraint(lp, 1)\\n\");\n  del_constraint(lp,1);\n  print_lp(lp);\n  printf(\"Add an equality constraint\\n\");\n  {\n    double row[] = {0, 1, 2, 1, 4};\n    if (!add_constraint(lp, row, EQ, 8))\n      ERROR();\n  }\n  print_lp(lp);\n  press_ret();\n  printf(\"A column can be added with:\\n\");\n  printf(\"add_column(lp,{3, 2, 2});\\n\");\n  {\n    double col[] = {3, 2, 2};\n    if (!add_column(lp, col))\n      ERROR();\n  }\n  print_lp(lp);\n  press_ret();\n  printf(\"A column can be removed with:\\n\");\n  printf(\"del_column(lp,3);\\n\");\n  del_column(lp,3);\n  print_lp(lp);\n  press_ret();\n  printf(\"We can use automatic scaling with:\\n\");\n  printf(\"set_scaling(lp, SCALE_MEAN);\\n\");\n  set_scaling(lp, SCALE_MEAN);\n  print_lp(lp);\n  press_ret();\n  printf(\"The function get_mat(lprec *lp, int row, int column) returns a single\\n\");\n  printf(\"matrix element\\n\");\n  printf(\"%s get_mat(lp,2,3), get_mat(lp,1,1); gives\\n\",\"printf(\\\"%f %f\\\\n\\\",\");\n  printf(\"%f %f\\n\", (double)get_mat(lp,2,3), (double)get_mat(lp,1,1));\n  printf(\"Notice that get_mat returns the value of the original unscaled problem\\n\");\n  press_ret();\n  printf(\"If there are any integer type variables, then only the rows are scaled\\n\");\n  printf(\"set_scaling(lp, SCALE_MEAN);\\n\");\n  set_scaling(lp, SCALE_MEAN);\n  printf(\"set_int(lp,3,FALSE);\\n\");\n  set_int(lp,3,FALSE);\n  print_lp(lp);\n  press_ret();\n  solve(lp);\n  printf(\"print_objective, print_solution gives the solution to the original problem\\n\");\n  print_objective(lp);\n  print_solution(lp, 1);\n  print_constraints(lp, 1);\n  press_ret();\n  printf(\"Scaling is turned off with unscale(lp);\\n\");\n  unscale(lp);\n  print_lp(lp);\n  press_ret();\n  printf(\"Now turn B&B debugging off and simplex tracing on with\\n\");\n  printf(\"set_debug(lp, FALSE), set_trace(lp, TRUE) and solve(lp)\\n\");\n  set_debug(lp, FALSE);\n  set_trace(lp, TRUE);\n  press_ret();\n  solve(lp);\n  printf(\"Where possible, lp_solve will start at the last found basis\\n\");\n  printf(\"We can reset the problem to the initial basis with\\n\");\n  printf(\"default_basis(lp). Now solve it again...\\n\");\n  press_ret();\n  default_basis(lp);\n  solve(lp);\n\n  printf(\"It is possible to give variables and constraints names\\n\");\n  printf(\"set_row_name(lp,1,\\\"speed\\\"); & set_col_name(lp,2,\\\"money\\\")\\n\");\n  if (!set_row_name(lp,1,\"speed\"))\n    ERROR();\n  if (!set_col_name(lp,2,\"money\"))\n    ERROR();\n  print_lp(lp);\n  printf(\"As you can see, all column and rows are assigned default names\\n\");\n  printf(\"If a column or constraint is deleted, the names shift place also:\\n\");\n  press_ret();\n  printf(\"del_column(lp,1);\\n\");\n  del_column(lp,1);\n  print_lp(lp);\n  press_ret();\n\n  write_lp(lp, \"lp.lp\");\n\n  delete_lp(lp);\n\n  printf(\"An lp structure can be created and read from a .lp file\\n\");\n  printf(\"lp = read_lp(\\\"lp.lp\\\", TRUE);\\n\");\n  printf(\"The verbose option is used\\n\");\n  if ((lp = read_LP(\"lp.lp\", TRUE, \"test\")) == NULL)\n    ERROR();\n  press_ret();\n  printf(\"lp is now:\\n\");\n  print_lp(lp);\n\n  press_ret();\n  printf(\"solution:\\n\");\n  set_debug(lp, TRUE);\n  solve(lp);\n  set_debug(lp, FALSE);\n  print_objective(lp);\n  print_solution(lp, 1);\n  print_constraints(lp, 1);\n  press_ret();\n\n  delete_lp(lp);\n\n#if defined FORTIFY\n  Fortify_LeaveScope();\n#endif\n\n  return(0);\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/demo.sln",
    "content": "Microsoft Visual Studio Solution File, Format Version 10.00\r\n# Visual Studio 2008\r\nProject(\"{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}\") = \"demo\", \"demo.vcproj\", \"{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}\"\r\nEndProject\r\nGlobal\r\n\tGlobalSection(SolutionConfigurationPlatforms) = preSolution\r\n\t\tDebug|Win32 = Debug|Win32\r\n\t\tDebug|x64 = Debug|x64\r\n\t\tRelease|Win32 = Release|Win32\r\n\t\tRelease|x64 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(ProjectConfigurationPlatforms) = postSolution\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Debug|Win32.ActiveCfg = Debug|Win32\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Debug|Win32.Build.0 = Debug|Win32\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Debug|x64.ActiveCfg = Debug|x64\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Debug|x64.Build.0 = Debug|x64\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Release|Win32.ActiveCfg = Release|Win32\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Release|Win32.Build.0 = Release|Win32\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Release|x64.ActiveCfg = Release|x64\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Release|x64.Build.0 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(SolutionProperties) = preSolution\r\n\t\tHideSolutionNode = FALSE\r\n\tEndGlobalSection\r\nEndGlobal\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/demo.vcproj",
    "content": "<?xml version=\"1.0\" encoding=\"Windows-1252\"?>\r\n<VisualStudioProject\r\n\tProjectType=\"Visual C++\"\r\n\tVersion=\"9.00\"\r\n\tName=\"demo\"\r\n\tProjectGUID=\"{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}\"\r\n\tTargetFrameworkVersion=\"131072\"\r\n\t>\r\n\t<Platforms>\r\n\t\t<Platform\r\n\t\t\tName=\"Win32\"\r\n\t\t/>\r\n\t\t<Platform\r\n\t\t\tName=\"x64\"\r\n\t\t/>\r\n\t</Platforms>\r\n\t<ToolFiles>\r\n\t</ToolFiles>\r\n\t<Configurations>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\demo.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tInlineFunctionExpansion=\"1\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_etaPFI;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG,WIN32,_CONSOLE,MSDOS,CHECK_SOLUTION,PARSER_LP,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tEnableFunctionLevelLinking=\"true\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\demo.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_etaPFI;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG,WIN32,_CONSOLE,MSDOS,CHECK_SOLUTION,FORTIFY,PARSER_LP,NORETURN,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"4\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.exe\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\demo.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tInlineFunctionExpansion=\"1\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_etaPFI;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG,WIN32,_CONSOLE,MSDOS,CHECK_SOLUTION,PARSER_LP,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tEnableFunctionLevelLinking=\"true\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\demo.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_etaPFI;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG,WIN32,_CONSOLE,MSDOS,CHECK_SOLUTION,FORTIFY,PARSER_LP,NORETURN,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.exe\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t</Configurations>\r\n\t<References>\r\n\t</References>\r\n\t<Files>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\colamd\\colamd.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\shared\\commonlib.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"demo.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\fortify.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\ini.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_crash.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\bfp\\bfp_etaPFI\\lp_etaPFI.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_Hash.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_lib.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_matrix.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_MDO.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_mipbb.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_MPS.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_params.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_presolve.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_price.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_pricePSE.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_report.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_rlp.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_scale.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_simplex.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_SOS.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_utils.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_wlp.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\shared\\mmio.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\shared\\myblas.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\yacc_read.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t</Files>\r\n\t<Globals>\r\n\t</Globals>\r\n</VisualStudioProject>\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/demolib.sln",
    "content": "Microsoft Visual Studio Solution File, Format Version 10.00\r\n# Visual Studio 2008\r\nProject(\"{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}\") = \"demo\", \"demolib.vcproj\", \"{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}\"\r\nEndProject\r\nGlobal\r\n\tGlobalSection(SolutionConfigurationPlatforms) = preSolution\r\n\t\tDebug|Win32 = Debug|Win32\r\n\t\tDebug|x64 = Debug|x64\r\n\t\tRelease|Win32 = Release|Win32\r\n\t\tRelease|x64 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(ProjectConfigurationPlatforms) = postSolution\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Debug|Win32.ActiveCfg = Debug|Win32\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Debug|Win32.Build.0 = Debug|Win32\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Debug|x64.ActiveCfg = Debug|x64\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Debug|x64.Build.0 = Debug|x64\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Release|Win32.ActiveCfg = Release|Win32\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Release|Win32.Build.0 = Release|Win32\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Release|x64.ActiveCfg = Release|x64\r\n\t\t{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}.Release|x64.Build.0 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(SolutionProperties) = preSolution\r\n\t\tHideSolutionNode = FALSE\r\n\tEndGlobalSection\r\nEndGlobal\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/demolib.vcproj",
    "content": "<?xml version=\"1.0\" encoding=\"Windows-1252\"?>\r\n<VisualStudioProject\r\n\tProjectType=\"Visual C++\"\r\n\tVersion=\"9.00\"\r\n\tName=\"demo\"\r\n\tProjectGUID=\"{CED6B89F-02F2-4DB1-8610-4F12A6D02F54}\"\r\n\tRootNamespace=\"demo\"\r\n\tTargetFrameworkVersion=\"131072\"\r\n\t>\r\n\t<Platforms>\r\n\t\t<Platform\r\n\t\t\tName=\"Win32\"\r\n\t\t/>\r\n\t\t<Platform\r\n\t\t\tName=\"x64\"\r\n\t\t/>\r\n\t</Platforms>\r\n\t<ToolFiles>\r\n\t</ToolFiles>\r\n\t<Configurations>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\demo.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tInlineFunctionExpansion=\"1\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\colamd\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG,WIN32,_CONSOLE,MSDOS,CHECK_SOLUTION,PARSER_LP,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tEnableFunctionLevelLinking=\"true\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib liblpsolve55.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tAdditionalLibraryDirectories=\"..\\lpsolve55\\bin\\win32\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\demo.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG,WIN32,_CONSOLE,NOFORTIFY\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"4\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib liblpsolve55d.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.exe\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tAdditionalLibraryDirectories=\"..\\lpsolve55\\bin\\win32\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\demo.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tInlineFunctionExpansion=\"1\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\colamd\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG,WIN32,_CONSOLE,MSDOS,CHECK_SOLUTION,PARSER_LP,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tEnableFunctionLevelLinking=\"true\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib liblpsolve55.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tAdditionalLibraryDirectories=\"..\\lpsolve55\\bin\\win64\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\demo.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG,WIN32,_CONSOLE,NOFORTIFY\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib liblpsolve55d.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.exe\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tAdditionalLibraryDirectories=\"..\\lpsolve55\\bin\\win64\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\demo.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t</Configurations>\r\n\t<References>\r\n\t</References>\r\n\t<Files>\r\n\t\t<File\r\n\t\t\tRelativePath=\"demo.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\fortify.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t</Files>\r\n\t<Globals>\r\n\t</Globals>\r\n</VisualStudioProject>\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/demo/readme.txt",
    "content": "This directory contains the files to build a demo program\r\n\r\nTo build the program under Windows with the Visual C/C++ compiler, use cvc6.bat (also works for VS.NET)\r\nTo build the program under DOS/Windows with the gcc compiler, use cgcc.bat\r\nTo build the program under Linux/Unix, use sh ccc\r\nTo build the program under Mac OS X 10.3.5, use sh ccc.osx\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/fortify.c",
    "content": "/*\n * FILE:\n *   fortify.c\n *\n * DESCRIPTION:\n *     A fortified shell for malloc, realloc, calloc, strdup, getcwd, tempnam\n *     and free.\n *     To use Fortify, each source file will need to #include \"fortify.h\".  To\n * enable  Fortify,  define the symbol FORTIFY.  If FORTIFY is not defined, it\n * will compile away to nothing.  If you do not have stderr available, you may\n * wish  to  set  an  alternate output function.  See _Fortify_SetOutputFunc(),\n * below.\n *     You will also need to link in fortify.o\n *\n *     None of the functions in this file should really be called\n *   directly; they really should be called through the macros\n *   defined in fortify.h\n *\n */\n\n#if defined FORTIFY\n\n#include <stdio.h>\n#include <stdlib.h>\n#include <sys/types.h>\n#include <stdlib.h>\n\n#if defined MSDOS || defined __BORLANDC__ || defined WIN32 || defined __HIGHC__\n# include <direct.h>\n#endif\n\nextern int EndOfPgr(int);\n\n#define __FORTIFY_C__ /* So fortify.h knows to not define the fortify macros */\n#include \"fortify.h\"\n\n#include \"ufortify.h\" /* the user's options */\n\nchar *_Fortify_file=NULL;\nint _Fortify_line=0;\n\n#ifndef FORTIFY_TRANSPARENT\n\n#include <string.h>\n#include <math.h>\n#include <time.h>\n#include <ctype.h>\n\n#if defined MSDOS || defined __BORLANDC__ || defined WIN32 || defined __HIGHC__\n# if !defined WIN32\n#  undef MSDOS\n#  define MSDOS\n# endif\n# include <conio.h>\n#else\n# include <unistd.h>\n# include <termio.h>\n# define getch() getchar()\n#endif\n\n#if defined _WINDOWS\n# include \"windows.h\"\n# if !defined WIN32\n#  include \"toolhelp.h\"\n# endif\n#endif\n\n#if defined LONGNAME\n# include \"longname.h\"\n#endif\n\n#if !defined MIN\n# define MIN(a, b) ((a) < (b) ? (a) : (b))\n#endif\n\nstruct Header\n{\n\tchar          *File;   /* The sourcefile of the caller   */\n\tunsigned short Line;   /* The sourceline of the caller   */\n\tsize_t         Size;   /* The size of the malloc'd block */\n\tstruct Header *Prev,   /* List pointers                  */\n\t\t      *Next;\n\tint            Checksum;  /* For validating the Header structure; see ChecksumHeader() */\n\tunsigned char  Scope;\n};\n\n#if defined AViiON || defined __GNUC__ || defined _MSC_VER\n# define _static static\n#else\n# define _static\n#endif\n\n_static char *address __OF((void *addr));\n_static int TimeToCheck __OF((void));\n_static int CheckBlock __OF((struct Header *h, char *file, unsigned long line));\n_static int CheckPointer __OF((unsigned char *ptr, unsigned long size, char *file, unsigned long line));\n_static int CheckFortification __OF((unsigned char *ptr, unsigned char value, size_t size));\n_static void SetFortification __OF((unsigned char *ptr, unsigned char value, size_t size));\n_static void OutputFortification __OF((unsigned char *ptr, unsigned char value, size_t size));\n_static int IsHeaderValid __OF((struct Header *h));\n_static void MakeHeaderValid __OF((struct Header *h));\n_static int ChecksumHeader __OF((struct Header *h));\n_static int IsOnList __OF((struct Header *h));\n_static void OutputHeader __OF((struct Header *h));\n_static void OutputMemory __OF((struct Header *h));\n_static void st_DefaultOutput __OF((char *String));\n_static void WaitIfstdOutput __OF((void));\n\nstatic char stdOutput = 0;        /* If true, did some stderr output */\nstatic OutputFuncPtr  st_Output = st_DefaultOutput; /* Output function for errors */\n\n#if !defined MSDOS && !defined WIN32\nstatic int strnicmp(s1,s2,maxlen)\n char *s1,*s2;\n size_t maxlen;\n {\n  while ((maxlen) && (*s1) && (*s2) && (toupper(*s1)==toupper(*s2))) {\n   maxlen--;\n   s1++;\n   s2++;\n  }\n  return((maxlen) ? toupper(*s1)-toupper(*s2) : 0);\n }\n\nstatic int stricmp(s1,s2)\n char *s1,*s2;\n {\n  return(strnicmp(s1,s2,strlen(s1)+1));\n }\n#endif\n\nstatic char *address(void *addr)\n{\n        static char str[80];\n\n#if defined KNOWS_POINTER_TYPE\n        sprintf(str,\"%p\",addr);\n#else\n        sprintf(str,\"%lx\",(unsigned long) addr);\n#endif\n        return(str);\n}\n\n#ifdef FORTIFY_CheckInterval\nint TimeToCheck()\n{\n        static time_t lastcheck=0L;\n\ttime_t t;\n        int ret = 0;\n\n\ttime(&t);\n\tif ((lastcheck==0L) || (t-lastcheck>=FORTIFY_CheckInterval))\n        {\n                lastcheck = t;\n                ret = 1;\n        }\n        return(ret);\n}\n#endif\n\nstatic FILE *gfile=NULL;\nstatic int Nchars=0,Nlines=0;\nstatic char flag=0;\n\nstatic void _Fortify_NoOutput()\n {\n }\n\nstatic void st_DefaultOutput(char *String)\n{\n        static FILE *file;\n        static char first=1;\n\n        if (first) {\n                file=stderr;\n                first=0;\n        }\n\n        if (stdOutput==0) {\n        \tNchars=Nlines=0;\n                if (gfile!=NULL) rewind(gfile);\n        }\n\n        if (flag==0)\n        {\n                char *ptr;\n\n        \tfile=stderr;\n                flag = 1;\n                if ((ptr=getenv(\"FORTIFY_OUTPUT\"))!=NULL)\n                {\n                        if ((stricmp(ptr,\"null\")==0) || (stricmp(ptr,\"nul\")==0))\n                                file=NULL;\n                        else if (stricmp(ptr,\"stderr\")==0)\n                                file=stderr;\n                        else if (stricmp(ptr,\"stdout\")==0)\n                                file=stdout;\n#if defined MSDOS && !defined _WINDOWS && !defined WIN32\n                        else if (stricmp(ptr,\"stdprn\")==0)\n                                file=stdprn;\n#endif\n                        else if ((file=fopen(ptr,\"w\"))==NULL)\n                        {\n#if !defined _WINDOWS\n                                fprintf(stderr,\"\\r\\nFortify: Unable to create logfile %s\\r\\n\",ptr);\n\t\t\t\tEndOfPgr(4);\n#else\n    \t\t\t\t{\n    \t\t\t\t\tchar str[255];\n\n    \t\t\t\t\tsprintf(str,\"Unable to create logfile\\n \\\"%s\\\"\",ptr);\n    \t\t\t\t\tMessageBox((HWND) NULL,(LPCSTR) str,(LPCSTR) \"Fortify\",(UINT) MB_ICONSTOP);\n#if 0\n#if defined WIN32\n\t\t\t\t        /* TerminateProcess(GetCurrentProcess(),65535); */\n                                        ExitProcess(65535);\n#else\n    \t\t\t\t\tTerminateApp((HTASK) NULL,(WORD) NO_UAE_BOX);\n#endif\n#else\n                                        EndOfPgr(1);\n#endif\n    \t\t\t\t}\n#endif\n                        }\n\t\t}\n\t\tif ((file!=NULL) && (file!=stderr) && (file!=stdout))\n\t\t{\n\t\t\ttime_t t;\n\n\t\t\ttime(&t);\n\t\t\tfprintf(file,\"Generated on: %s%s\\n\",\n                                ctime(&t),\n                                (file==stdout) || (file==stderr) ? \"\\r\" : \"\"\n                               );\n\t\t}\n\t}\n\tif (file!=NULL)\n\t{\n#if defined _WINDOWS\n                if ((file==stdout) || (file==stderr)) {\n#if defined LINE_BY_LINE\n                \tif (MessageBox((HWND) NULL,(LPCSTR) String,(LPCSTR) \"Fortify\",(UINT) MB_OKCANCEL /* |MB_ICONINFORMATION */)==IDCANCEL)\n#if 0\n#if defined WIN32\n                         /* TerminateProcess(GetCurrentProcess(),65535); */\n                         ExitProcess(65535);\n#else\n    \t\t\t TerminateApp((HTASK) NULL,(WORD) NO_UAE_BOX);\n#endif\n#else\n                         EndOfPgr(1);\n#endif\n#else\n\t\t\t{\n                        \tchar *ptr;\n\n                        \tptr=\"fortify.tmp\";\n\t\t\t\tif ((ptr==NULL) || ((file=gfile=fopen(ptr,\"w+\"))==NULL))\n                        \t{\n    \t\t\t\t\tchar str[255];\n\n    \t\t\t\t\tsprintf(str,\"Unable to create temporary file\\n \\\"%s\\\"\",(ptr==NULL) ? \"(NULL)\" : ptr);\n    \t\t\t\t\tMessageBox((HWND) NULL,(LPCSTR) str,(LPCSTR) \"Fortify\",(UINT) MB_ICONSTOP);\n#if 0\n#if defined WIN32\n                                        /* TerminateProcess(GetCurrentProcess(),65535); */\n                                        ExitProcess(65535);\n#else\n    \t\t\t\t\tTerminateApp((HTASK) NULL,(WORD) NO_UAE_BOX);\n#endif\n#else\n                                        EndOfPgr(1);\n#endif\n                        \t}\n                    \t}\n#endif\n                }\n                if ((file!=stdout) && (file!=stderr))\n#endif\n                        {\n                                int i,ch=-1;\n\n                        \tfor (i=0;(String[i]) && (Nlines<30);i++)\n                                 if (String[i]=='\\n') Nlines++;\n\t\t\t\tif ((String[i]) && (String[i+1])) {\n\t\t\t\t\tch=String[i+1];\n\t\t\t\t\tString[i+1]=0;\n\t\t\t\t}\n                                if ((file==stdout) || (file==stderr)) {\n                                 char *ptr=String;\n                                 int i;\n\n                                 do {\n                                  for (i=0;(ptr[i]) && (ptr[i]!='\\r') && (ptr[i]!='\\n');i++);\n                                  Nchars+=fprintf(file,\"%-*.*s%s\",\n                                                  i,i,\n                                                  ptr,\n                                                  (ptr[i]) ? \"\\r\\n\" : \"\"\n                                                 );\n                                  ptr+=i;\n                                  if (ptr[0]=='\\r') ptr++;\n                                  if (ptr[0]=='\\n') ptr++;\n                                 } while (*ptr);\n                                }\n                                else Nchars+=fprintf(file,String);\n\t\t\t\tif (ch>=0) String[i+1]=(char)ch;\n\t\t\t\tif (Nlines>=30) {\n                                \tWaitIfstdOutput();\n                                    \tNchars=Nlines=0;\n                                    \tstdOutput = 0;\n                                        if ((String[i]) && (String[i+1])) {\n                                                if ((file==stderr) || (file==stdout) || ((gfile!=NULL) && (Nchars)))\n                                                \tstdOutput = 1;\n                                         \tst_DefaultOutput(String+i);\n                                        }\n                                }\n                        }\n                if ((file==stderr) || (file==stdout) || ((gfile!=NULL) && (Nchars)))\n                \tstdOutput = 1;\n\t}\n}\n\nstatic void WaitIfstdOutput()\n{\n#if !defined _WINDOWS\n        if((stdOutput) && (st_Output != (OutputFuncPtr) _Fortify_NoOutput))\n        {\n#ifdef FORTIFY_WAIT_FOR_KEY\n                static signed char wait_on_key=-1;\n\n                if(wait_on_key<0)\n\t\t{\n\t\t\tchar *ptr;\n\n                        if (((ptr=getenv(\"FORTIFY_WAIT_FOR_KEY\"))!=NULL) &&\n\t\t\t    (tolower(*ptr)=='n')) wait_on_key = 0;\n                        else wait_on_key = 1;\n\n                }\n\t\tif(wait_on_key)\n\t\t{\n                        char c;\n\n#if !defined MSDOS && !defined WIN32\n                        struct termio tio,tiobak;\n                        char flag;\n\n                        if ((flag=ioctl(0,TCGETA,&tio))==0) /* handle 0 is stdin */\n                        {\n                                tiobak=tio;\n                        \ttio.c_lflag&=~ICANON;\n                                tio.c_lflag&=~ECHO;\n                        \ttio.c_cc[VMIN]=1;\n                        \tioctl(0,TCSETA,&tio);\n\t                }\n#endif /* !MSDOS */\n\t\t\tc = (char)getch();\n\n#if !defined MSDOS && !defined WIN32\n                        if (flag==0)\n                        \tioctl(0,TCSETA,&tiobak);\n#endif /* !MSDOS */\n\n\t\t\tif ((c == 3) || (c == 0x1b)) EndOfPgr(3);\n\t\t}\n#endif /* FORTIFY_WAIT_FOR_KEY */\n\n        }\n#else\n# if !defined LINE_BY_LINE\n        if ((stdOutput) && (gfile!=NULL) && (Nchars))\n        {\n                char *ptr;\n\n                ptr=(char *) malloc(Nchars+1);\n                if (ptr!=NULL)\n                {\n                        int n=0,l=0;\n\n                        rewind(gfile);\n                        while ((n<Nchars) && (l<Nlines))\n                        {\n                                fgets(ptr+n,Nchars-n+1,gfile);\n                                n+=(int)strlen(ptr+n);\n                                l++;\n                        }\n                \tif (MessageBox((HWND) NULL,(LPCSTR) ptr,(LPCSTR) \"Fortify\",(UINT) MB_OKCANCEL /* |MB_ICONINFORMATION */)==IDCANCEL)\n#if 0\n#if defined WIN32\n                         /* TerminateProcess(GetCurrentProcess(),65535); */\n                         ExitProcess(65535);\n#else\n    \t\t\t TerminateApp((HTASK) NULL,(WORD) NO_UAE_BOX);\n#endif\n#else\n                         EndOfPgr(1);\n#endif\n                }\n                free(ptr);\n        }\n# endif\n#endif\n\tstdOutput = 0;\n}\n\nstatic struct Header *st_Head = NULL; /* Head of alloc'd memory list */\nstatic char st_Buffer[256];       /* Temporary buffer for sprintf's */\nstatic int st_Disabled = 0;       /* If true, Fortify is inactive */\nstatic int st_MallocFailRate = 0; /* % of the time to fail mallocs */\n\nstatic char          *st_LastVerifiedFile = \"unknown\";\nstatic unsigned short st_LastVerifiedLine = 0;\nstatic unsigned char  st_Scope            = 0;\nstatic void           OutputLastVerifiedPoint __OF((void));\n\nvoid FORTIFY_STORAGE\n_Fortify_Init(char *file,unsigned long line)\n{\n\tif (gfile!=NULL) fclose(gfile);\n\tgfile=NULL;\n\tNchars=Nlines=0;\n        flag=0;\n        st_Head=NULL;\n        stdOutput=0;\n        st_Output=st_DefaultOutput;\n        st_Disabled=0;\n        st_MallocFailRate=0;\n        st_LastVerifiedFile=\"unknown\";\n        st_LastVerifiedLine=0;\n        st_Scope=0;\n}\n\n\n/*\n * _Fortify_malloc() - Allocates a block of memory, with extra bits for\n *                    misuse protection/detection.\n *\n *    Features:\n *     +  Adds the malloc'd memory onto Fortify's own private list.\n *        (With a checksum'd header to detect corruption of the memory list)\n *     +  Places sentinals on either side of the user's memory with\n *        known data in them, to detect use outside of the bounds\n *        of the block\n *     +  Initializes the malloc'd memory to some \"nasty\" value, so code\n *        can't rely on it's contents.\n *     +  Can check all sentinals on every malloc.\n *     +  Can generate a warning message on a malloc fail.\n *     +  Can randomly \"fail\" at a set fail rate\n */\nvoid *FORTIFY_STORAGE\n_Fortify_malloc(size_t size,char *file,unsigned long line)\n{\n\tunsigned char *ptr;\n\tstruct Header *h;\n\n        stdOutput = 0;\n\n\tFORTIFY_LOCK();\n\n\tif(st_Disabled)\n\t{\n\t\tptr = (unsigned char *) malloc(size);\n\t\tFORTIFY_UNLOCK();\n                WaitIfstdOutput();\n\t\treturn((void *) ptr);\n\t}\n\n#ifdef CHECK_ALL_MEMORY_ON_MALLOC\n#ifdef FORTIFY_CheckInterval\n        if (TimeToCheck())\n#endif\n\t\t_Fortify_CheckAllMemory(file, line);\n#endif\n\n\tif(size == 0)\n\t{\n#ifdef WARN_ON_ZERO_MALLOC\n    \tsprintf(st_Buffer,\n        \t    \"\\nFortify: %s.%ld\\n         malloc(0) attempted failed\\n\",\n            \tfile, line);\n\t\tst_Output(st_Buffer);\n#endif\n\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\tif(st_MallocFailRate > 0)\n\t{\n\t\tif(rand() % 100 < st_MallocFailRate)\n\t\t{\n#ifdef WARN_ON_FALSE_FAIL\n\t\t\tsprintf(st_Buffer,\n\t\t\t\t\t\"\\nFortify: %s.%ld\\n         malloc(%ld) \\\"false\\\" failed\\n\",\n\t\t\t\t\t\t\tfile, line, (unsigned long)size);\n\t\t\tst_Output(st_Buffer);\n#endif\n\t\t\tFORTIFY_UNLOCK();\n                        WaitIfstdOutput();\n                        return(0);\n\t\t}\n\t}\n\n\t/*\n\t * malloc the memory, including the space for the header and fortification\n\t * buffers\n\t */\n#ifdef WARN_ON_SIZE_T_OVERFLOW\n\t{\n\t\tsize_t private_size = sizeof(struct Header)\n\t\t\t\t\t\t\t+ FORTIFY_BEFORE_SIZE + size + FORTIFY_AFTER_SIZE;\n\n\t\tif(private_size < size) /* Check to see if the added baggage is larger than size_t */\n\t\t{\n\t\t\tsprintf(st_Buffer,\n\t\t\t\t\t\"\\nFortify: %s.%ld\\n         malloc(%ld) has overflowed size_t.\\n\",\n\t\t\t\t\tfile, line, (unsigned long)size);\n\t\t\tst_Output(st_Buffer);\n\t\t\tFORTIFY_UNLOCK();\n\t\t\tWaitIfstdOutput();\n\t\t\treturn(0);\n\t\t}\n\t}\n#endif\n\n\tptr = (unsigned char *) malloc(sizeof(struct Header) +\n\t\t\t\t FORTIFY_BEFORE_SIZE + size + FORTIFY_AFTER_SIZE);\n\tif(!ptr)\n\t{\n#ifdef WARN_ON_MALLOC_FAIL\n\t\tsprintf(st_Buffer, \"\\nFortify: %s.%ld\\n         malloc(%ld) failed\\n\",\n\t\t\t\tfile, line, (unsigned long)size);\n\t\tst_Output(st_Buffer);\n#endif\n\n\t\tFORTIFY_UNLOCK();\n                WaitIfstdOutput();\n                return(0);\n\t}\n\n\t/*\n\t * Initialize and validate the header\n\t */\n\th = (struct Header *)ptr;\n\n\th->Size = size;\n\n\th->File = file;\n\th->Line = (unsigned short) line;\n\n\th->Next = st_Head;\n\th->Prev = 0;\n\n\th->Scope = st_Scope;\n\n\tif(st_Head)\n\t{\n\t\tst_Head->Prev = h;\n\t\tMakeHeaderValid(st_Head);\n\t}\n\n\tst_Head = h;\n\n\tMakeHeaderValid(h);\n\n\n\t/*\n\t * Initialize the fortifications\n\t */\n\tSetFortification(ptr + sizeof(struct Header),\n\t                 FORTIFY_BEFORE_VALUE, FORTIFY_BEFORE_SIZE);\n\tSetFortification(ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE + size,\n\t                 FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);\n\n#ifdef FILL_ON_MALLOC\n\t/*\n\t * Fill the actual user memory\n\t */\n\tSetFortification(ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE,\n\t                 FILL_ON_MALLOC_VALUE, size);\n#endif\n\n\t/*\n\t * We return the address of the user's memory, not the start of the block,\n\t * which points to our magic cookies\n\t */\n\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n\treturn((void *) (ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE));\n}\n\n/*\n * _Fortify_free() - This free must be used for all memory allocated with\n *                  _Fortify_malloc().\n *\n *   Features:\n *     + Pointers are validated before attempting a free - the pointer\n *       must point to a valid malloc'd bit of memory.\n *     + Detects attempts at freeing the same block of memory twice\n *     + Can clear out memory as it is free'd, to prevent code from using\n *       the memory after it's been freed.\n *     + Checks the sentinals of the memory being freed.\n *     + Can check the sentinals of all memory.\n */\n\nvoid FORTIFY_STORAGE\n_Fortify_free(void *uptr,char *file,unsigned long line)\n{\n\tunsigned char *ptr;\n\tstruct Header *h;\n\n\tif(uptr == NULL)\n\t\treturn;\n\n\tptr = (unsigned char *)uptr - sizeof(struct Header) - FORTIFY_BEFORE_SIZE;\n\th = (struct Header *)ptr;\n\n\tstdOutput = 0;\n\n\tFORTIFY_LOCK();\n\n\tif(st_Disabled)\n\t{\n\t\tfree(uptr);\n\t\tFORTIFY_UNLOCK();\n                WaitIfstdOutput();\n                return;\n\t}\n\n#ifdef CHECK_ALL_MEMORY_ON_FREE\n#ifdef FORTIFY_CheckInterval\n        if (TimeToCheck())\n#endif\n\t\t_Fortify_CheckAllMemory(file, line);\n#endif\n\n#ifdef PARANOID_FREE\n\tif(!IsOnList(h))\n\t{\n\t\tsprintf(st_Buffer,\n\t\t \"\\nFortify: %s.%ld\\n         Invalid pointer, corrupted header, or possible free twice\\n\",\n\t\t\t\tfile, line);\n\t\tst_Output(st_Buffer);\n\t\tOutputLastVerifiedPoint();\n\t\tgoto fail;\n\t}\n#endif\n\n\tif(!CheckBlock(h, file, line))\n\t\tgoto fail;\n\n\t/*\n\t * Remove the block from the list\n\t */\n\tif(h->Prev)\n\t{\n\t\tif(!CheckBlock(h->Prev, file, line))\n\t\t\tgoto fail;\n\n\t\th->Prev->Next = h->Next;\n\t\tMakeHeaderValid(h->Prev);\n\t}\n\telse\n\t\tst_Head = h->Next;\n\n\tif(h->Next)\n\t{\n\t\tif(!CheckBlock(h->Next, file, line))\n\t\t\tgoto fail;\n\n\t\th->Next->Prev = h->Prev;\n\t\tMakeHeaderValid(h->Next);\n\t}\n\n#ifdef FILL_ON_FREE\n\t/*\n\t * Nuke out all memory that is about to be freed\n\t */\n\tSetFortification(ptr, FILL_ON_FREE_VALUE,\n\t                 sizeof(struct Header) + FORTIFY_BEFORE_SIZE + h->Size + FORTIFY_AFTER_SIZE);\n#endif\n\n\t/*\n\t * And do the actual free\n\t */\n\tfree(ptr);\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n        return;\n\nfail:\n\tsprintf(st_Buffer, \"         free(%s) failed\\n\", address(uptr));\n\tst_Output(st_Buffer);\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n}\n\n/*\n * _Fortify_realloc() - Uses _Fortify_malloc() and _Fortify_free() to implement\n *                     realloc().\n *\n *   Features:\n *        + The realloc'd block is ALWAYS moved.\n *        + The pointer passed to realloc() is verified in the same way that\n *          _Fortify_free() verifies pointers before it frees them.\n *        + All the _Fortify_malloc() and _Fortify_free() protection\n */\nvoid *FORTIFY_STORAGE\n_Fortify_realloc(void *ptr,size_t new_size,char *file,unsigned long line)\n{\n\tvoid *new_ptr;\n\tstruct Header *h;\n\n\tif(new_size == 0)\n\t{\n\t\t_Fortify_free(ptr,file,line);\n\t\treturn(NULL);\n\t}\n\n\th = (struct Header *)((unsigned char *)ptr - sizeof(struct Header) - FORTIFY_BEFORE_SIZE);\n\n        stdOutput = 0;\n\n\tif(st_Disabled)\n\t{\n\t\tFORTIFY_LOCK();\n\t\tnew_ptr = (void *) realloc(ptr, new_size);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n                return(new_ptr);\n\t}\n\n\tif(!ptr)\n        {\n\t\tvoid *FORTIFY_STORAGE ret = _Fortify_malloc(new_size, file, line);\n\n                WaitIfstdOutput();\n\t\treturn(ret);\n        }\n\n\tFORTIFY_LOCK();\n\n\tif(!IsOnList(h))\n\t{\n\t\tsprintf(st_Buffer,\n\t\t\t\t\"\\nFortify: %s.%ld\\n         Invalid pointer or corrupted header passed to realloc\\n\",\n\t\t\t\tfile, line);\n\t\tst_Output(st_Buffer);\n\t\tgoto fail;\n\t}\n\n\tif(!CheckBlock(h, file, line))\n\t\tgoto fail;\n\n\tnew_ptr = _Fortify_malloc(new_size, file, line);\n\tif(!new_ptr)\n\t{\n\t\tFORTIFY_UNLOCK();\n                WaitIfstdOutput();\n                return(0);\n\t}\n\n\tif(h->Size < new_size)\n\t\tmemcpy(new_ptr, ptr, h->Size);\n\telse\n\t\tmemcpy(new_ptr, ptr, new_size);\n\n\t_Fortify_free(ptr, file, line);\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n        return(new_ptr);\n\nfail:\n\tsprintf(st_Buffer, \"         realloc(%s, %ld) failed\\n\", address(ptr), (unsigned long)new_size);\n\tst_Output(st_Buffer);\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n        return(NULL);\n}\n\n\n/*\n * __Fortify_CheckPointer() - Returns true if the uptr points to a valid\n *   piece of _Fortify_malloc()'d memory. The memory must be on the malloc'd\n *   list, and it's sentinals must be in tact.\n *     If anything is wrong, an error message is issued.\n *\n *   (Note - if fortify is disabled, this function always returns true).\n */\nstatic int FORTIFY_STORAGE\n__Fortify_CheckPointer(void *uptr,char OnlyStart,unsigned long size,char *file,unsigned long line)\n{\n\tunsigned char *ptr = (unsigned char *)uptr - sizeof(struct Header) - FORTIFY_BEFORE_SIZE;\n\tint r = 1, StartPointer;\n\n        stdOutput = 0;\n\n\tif(st_Disabled)\n        {\n                WaitIfstdOutput();\n\t\treturn(1);\n        }\n\n\tFORTIFY_LOCK();\n\n\tStartPointer = IsOnList((struct Header *)ptr);\n\tif((OnlyStart) && (!StartPointer))\n\t{\n\t\tsprintf(st_Buffer,\n\t\t       \"\\nFortify: %s.%ld\\n         Invalid pointer or corrupted header detected (%s)\\n\",\n\t\t       file, line, address(uptr));\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n                WaitIfstdOutput();\n                return(0);\n\t}\n\n\tif((OnlyStart) || (StartPointer))\n\t\tr = CheckBlock((struct Header *)ptr, file, line);\n\tif(!OnlyStart)\n\t\tr = CheckPointer((unsigned char *)uptr, size, file, line);\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n        return(r);\n}\n\n\nint FORTIFY_STORAGE\n_Fortify_CheckPointer(void *uptr,char *file,unsigned long line)\n{\n\treturn(__Fortify_CheckPointer(uptr,1,0,file,line));\n}\n\n/*\n * Fortify_SetOutputFunc(OutputFuncPtr Output) - Sets the function used to\n *   output all error and diagnostic messages by fortify. The output function\n *   takes a single unsigned char * argument, and must be able to handle newlines.\n *     The function returns the old pointer.\n */\nFortify_OutputFuncPtr FORTIFY_STORAGE\n_Fortify_SetOutputFunc(Fortify_OutputFuncPtr Output)\n{\n\tOutputFuncPtr Old = st_Output;\n\n\tst_Output = (OutputFuncPtr) Output;\n\n\treturn((Fortify_OutputFuncPtr FORTIFY_STORAGE) Old);\n}\n\n/*\n * _Fortify_SetMallocFailRate(int Percent) - _Fortify_malloc() will make the\n *   malloc attempt fail this Percent of the time, even if the memory is\n *   available. Useful to \"stress-test\" an application. Returns the old\n *   value. The fail rate defaults to 0.\n */\nint FORTIFY_STORAGE\n_Fortify_SetMallocFailRate(int Percent)\n{\n\tint Old = st_MallocFailRate;\n\n\tst_MallocFailRate = Percent;\n\n\treturn(Old);\n}\n\n\n/*\n * _Fortify_CheckAllMemory() - Checks the sentinals of all malloc'd memory.\n *   Returns the number of blocks that failed.\n *\n *  (If Fortify is disabled, this function always returns 0).\n */\nint FORTIFY_STORAGE\n_Fortify_CheckAllMemory(char *file,unsigned long line)\n{\n\tstruct Header *curr = st_Head;\n\tint count = 0;\n\n\tstdOutput = 0;\n\n\tif(st_Disabled)\n\t{\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\tFORTIFY_LOCK();\n\n\twhile(curr)\n\t{\n\t\tif(!CheckBlock(curr, file, line))\n\t\t\tcount++;\n\n\t\tcurr = curr->Next;\n\t}\n\n\tif(file)\n\t{\n\t\tst_LastVerifiedFile = file;\n\t\tst_LastVerifiedLine = (short) line;\n\t}\n\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n        return(count);\n}\n\n/* _Fortify_EnterScope - enters a new Fortify scope level.\n * returns the new scope level.\n */\nint FORTIFY_STORAGE\n_Fortify_EnterScope(char *file,unsigned long line)\n{\n\treturn((int) ++st_Scope);\n}\n\n/* _Fortify_LeaveScope - leaves a Fortify scope level,\n * also prints a memory dump of all non-freed memory that was allocated\n * during the scope being exited.\n */\nint FORTIFY_STORAGE\n_Fortify_LeaveScope(char *file,unsigned long line)\n{\n\tstruct Header *curr = st_Head;\n\tint count = 0;\n\tsize_t size = 0;\n\n        stdOutput = 0;\n\n\tif(st_Disabled)\n        {\n                WaitIfstdOutput();\n                return(0);\n        }\n\n\tFORTIFY_LOCK();\n\n\tst_Scope--;\n\twhile(curr)\n\t{\n\t\tif(curr->Scope > st_Scope)\n\t\t{\n\t\t\tif(count == 0)\n\t\t\t{\n\t\t\t\tsprintf(st_Buffer, \"\\nFortify: Memory Dump at %s.%ld\\n\", file, line);\n\t\t\t\tst_Output(st_Buffer);\n\t\t\t\tOutputLastVerifiedPoint();\n\t\t\t\tsprintf(st_Buffer, \"%11s %8s %s\\n\", \"Address\", \"Size\", \"Allocator\");\n\t\t\t\tst_Output(st_Buffer);\n\t\t\t}\n\n\t\t\tOutputHeader(curr);\n\t\t\tcount++;\n\t\t\tsize += curr->Size;\n\t\t}\n\n\t\tcurr = curr->Next;\n\t}\n\n\tif(count)\n\t{\n\t\tsprintf(st_Buffer, \"%11s %8ld bytes overhead\\n\", \"and\",\n\t\t\t\t\t\t(unsigned long)(count * (sizeof(struct Header) + FORTIFY_BEFORE_SIZE + FORTIFY_AFTER_SIZE)));\n\t\t\t\t\t\tst_Output(st_Buffer);\n\n\t\tsprintf(st_Buffer,\"%11s %8ld bytes in %d blocks\\n\", \"total\", size, count);\n\t\tst_Output(st_Buffer);\n\t}\n\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n        return(count);\n}\n\n/*\n * _Fortify_OutputAllMemory() - Outputs the entire list of currently\n *     malloc'd memory. For each malloc'd block is output it's Address,\n *   Size, and the SourceFile and Line that allocated it.\n *\n *   If there is no memory on the list, this function outputs nothing.\n *\n *   It returns the number of blocks on the list, unless fortify has been\n *   disabled, in which case it always returns 0.\n */\nint FORTIFY_STORAGE\n_Fortify_OutputAllMemory(char *file,unsigned long line)\n{\n\tstruct Header *curr = st_Head;\n\tint count = 0;\n\tsize_t size = 0;\n\n        stdOutput = 0;\n\n\tif(st_Disabled)\n        {\n                WaitIfstdOutput();\n                return(0);\n        }\n\n\tFORTIFY_LOCK();\n\n\tif(curr)\n\t{\n\t\tsprintf(st_Buffer, \"\\nFortify: Memory Dump at %s.%ld\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tOutputLastVerifiedPoint();\n\t\tsprintf(st_Buffer, \"%11s %8s %s\\n\", \"Address\", \"Size\", \"Allocator\");\n\t\tst_Output(st_Buffer);\n\n\t\twhile(curr)\n\t\t{\n\t\t\tOutputHeader(curr);\n\t\t\tcount++;\n\t\t\tsize += curr->Size;\n\t\t\tcurr = curr->Next;\n\t\t}\n\n\t\tsprintf(st_Buffer, \"%11s %8ld bytes overhead\\n\", \"and\",\n\t\t\t\t(unsigned long)(count * (sizeof(struct Header) + FORTIFY_BEFORE_SIZE + FORTIFY_AFTER_SIZE)));\n\t\tst_Output(st_Buffer);\n\n\t\tsprintf(st_Buffer,\"%11s %8ld bytes in %d blocks\\n\", \"total\", size, count);\n\t\tst_Output(st_Buffer);\n\t}\n\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n\treturn(count);\n}\n\n/* _Fortify_DumpAllMemory(Scope) - Outputs the entire list of currently\n * new'd memory within the specified scope. For each new'd block is output\n * it's Address, Size, the SourceFile and Line that allocated it, a hex dump\n * of the contents of the memory and an ascii dump of printable characters.\n *\n * If there is no memory on the list, this function outputs nothing.\n *\n * It returns the number of blocks on the list, unless Fortify has been\n * disabled, in which case it always returns 0.\n */\nint FORTIFY_STORAGE\n_Fortify_DumpAllMemory(int scope,char *file,unsigned long line)\n{\n\tstruct Header *curr = st_Head;\n\tint count = 0;\n\tsize_t size = 0;\n\n        stdOutput = 0;\n\n\tif(st_Disabled)\n        {\n                WaitIfstdOutput();\n\t\treturn(0);\n        }\n\n\tFORTIFY_LOCK();\n\n\twhile(curr)\n\t{\n\t\tif(curr->Scope >= scope)\n\t\t{\n\t\t\tif(count == 0)\n\t\t\t{\n\t\t\t\tsprintf(st_Buffer, \"\\nFortify: Memory Dump at %s.%ld\\n\", file, line);\n\t\t\t\tst_Output(st_Buffer);\n\t\t\t\tOutputLastVerifiedPoint();\n\t\t\t\tsprintf(st_Buffer, \"%11s %8s %s\\n\", \"Address\", \"Size\", \"Allocator\");\n\t\t\t\tst_Output(st_Buffer);\n\t\t\t}\n\n\t\t\tOutputHeader(curr);\n\t\t\tOutputMemory(curr);\n\t\t\tst_Output(\"\\n\");\n\t\t\tcount++;\n\t\t\tsize += curr->Size;\n\t\t}\n\n\t\tcurr = curr->Next;\n\t}\n\n\tif(count)\n\t{\n\t\tsprintf(st_Buffer, \"%11s %8ld bytes overhead\\n\", \"and\",\n\t\t\t\t\t\t(unsigned long)(count * (sizeof(struct Header) + FORTIFY_BEFORE_SIZE + FORTIFY_AFTER_SIZE)));\n\t\t\t\t\t\tst_Output(st_Buffer);\n\n\t\tsprintf(st_Buffer,\"%11s %8ld bytes in %d blocks\\n\", \"total\", size, count);\n\t\tst_Output(st_Buffer);\n\t}\n\n\tFORTIFY_UNLOCK();\n        WaitIfstdOutput();\n        return(count);\n}\n\n/*\n * _Fortify_Disable() - This function provides a mechanism to disable Fortify\n *   without recompiling all the sourcecode.\n *   If 'how' is zero then it can only be called when there is no memory on the\n *   Fortify malloc'd list. (Ideally, at the start of the program before any\n *   memory has been allocated). If you call this function when there IS\n *   memory on the Fortify malloc'd list, it will issue an error, and fortify\n *   will not be disabled.\n *   If 'how' is nonzero then output will only be disabled. This can always be\n *   done.\n */\n\nint FORTIFY_STORAGE\n_Fortify_Disable(char *file,unsigned long line,int how)\n{\n\tint result;\n\n        if (how <= 0)\n        {\n    \t    stdOutput = 0;\n\n    \t    FORTIFY_LOCK();\n\n    \t    if((st_Head) && (how == 0))\n    \t    {\n    \t\t    sprintf(st_Buffer, \"Fortify: %s.%d\\n\", file, line);\n    \t\t    st_Output(st_Buffer);\n    \t\t    st_Output(\"         Fortify_Disable failed\\n\");\n    \t\t    st_Output(\"         (because there is memory on the Fortify memory list)\\n\");\n\n    \t\t    _Fortify_OutputAllMemory(file, line);\n    \t\t    result = 0;\n    \t    }\n    \t    else\n    \t    {\n    \t\t    st_Disabled = (how >= -1 ? 1 : 0);\n    \t\t    result = 1;\n    \t    }\n\n    \t    FORTIFY_UNLOCK();\n            WaitIfstdOutput();\n        }\n        else\n        {\n            _Fortify_SetOutputFunc((Fortify_OutputFuncPtr) _Fortify_NoOutput);\n            result = 1;\n        }\n\treturn(result);\n}\n\n/*\n * Check a block's header and fortifications.\n */\nstatic int CheckBlock(struct Header *h,char *file,unsigned long line)\n{\n\tunsigned char *ptr = (unsigned char *)h;\n\tint result = 1;\n\n        stdOutput = 0;\n\n\tif(!IsHeaderValid(h))\n\t{\n\t\tsprintf(st_Buffer,\n\t\t\t\t\"\\nFortify: %s.%ld\\n         Invalid pointer or corrupted header detected (%s)\\n\",\n\t\t\t\tfile, line, address(ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE));\n\t\tst_Output(st_Buffer);\n\t\tOutputLastVerifiedPoint();\n                WaitIfstdOutput();\n                return(0);\n\t}\n\n\tif(!CheckFortification(ptr + sizeof(struct Header),\n\t\t                   FORTIFY_BEFORE_VALUE, FORTIFY_BEFORE_SIZE))\n\t{\n\t\tsprintf(st_Buffer,\n\t\t        \"\\nFortify: %s.%ld\\n         Memory overrun detected before block\\n\",\n\t\t        file, line);\n\t\tst_Output(st_Buffer);\n\n\t\tsprintf(st_Buffer,\"         (%s,%ld,%s.%u)\\n\",\n\t\t\taddress(ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE),\n\t\t       (unsigned long)h->Size, h->File, h->Line);\n\t\tst_Output(st_Buffer);\n\n\t\tOutputFortification(ptr + sizeof(struct Header),\n\t\t                    FORTIFY_BEFORE_VALUE, FORTIFY_BEFORE_SIZE);\n\t\tOutputLastVerifiedPoint();\n\t\tresult = 0;\n\t}\n\n\tif(!CheckFortification(ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE + h->Size,\n\t                       FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE))\n\t{\n\t\tsprintf(st_Buffer, \"\\nFortify: %s.%ld\\n         Memory overrun detected after block\\n\",\n\t\t                   file, line);\n\t\tst_Output(st_Buffer);\n\n\t\tsprintf(st_Buffer,\"         (%s,%ld,%s.%u)\\n\",\n\t\t\t\t  address(ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE),\n\t\t\t\t (unsigned long)h->Size, h->File, h->Line);\n\t\tst_Output(st_Buffer);\n\n\t\tOutputFortification(ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE + h->Size,\n\t\t                    FORTIFY_AFTER_VALUE, FORTIFY_AFTER_SIZE);\n\t\tOutputLastVerifiedPoint();\n\t\tresult = 0;\n\t}\n\n        WaitIfstdOutput();\n\treturn(result);\n}\n\nstatic int CheckPointer(unsigned char *ptr,unsigned long size,char *file,unsigned long line)\n{\n\tstruct Header *curr;\n\tunsigned char *ptr1;\n\n\tcurr = st_Head;\n\twhile(curr)\n\t{\n\t\tptr1 = (unsigned char *)curr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE;\n\t\tif(ptr + size <= (unsigned char *)curr)\n\t\t\t;\n\t\telse if(ptr >= ptr1)\n\t\t\t;\n\t\telse\n\t\t{\n\t\t\tsprintf(st_Buffer, \"\\nFortify: %s.%ld\\n         Memory access detected before block\\n\",\n\t\t                file, line);\n\t\t\tst_Output(st_Buffer);\n\n\t\t\tsprintf(st_Buffer,\"         (%s,%ld,%s.%u)\\n\",\n\t\t\t\t\taddress(ptr1),\n\t\t\t\t\t(unsigned long)curr->Size, curr->File, curr->Line);\n\t\t\tst_Output(st_Buffer);\n\n\t\t\tWaitIfstdOutput();\n\t\t\treturn(0);\n\t\t}\n\n\t\tif(ptr + size <= ptr1 + curr->Size)\n\t\t\t;\n\t\telse if(ptr >= ptr1 + curr->Size + FORTIFY_AFTER_SIZE)\n\t\t\t;\n\t\telse\n\t\t{\n\t\t\tsprintf(st_Buffer, \"\\nFortify: %s.%ld\\n         Memory access detected after block\\n\",\n\t\t                file, line);\n\t\t\tst_Output(st_Buffer);\n\n\t\t\tsprintf(st_Buffer,\"         (%s,%ld,%s.%u)\\n\",\n\t\t\t\t\taddress(ptr1),\n\t\t\t\t\t(unsigned long)curr->Size, curr->File, curr->Line);\n\t\t\tst_Output(st_Buffer);\n\n\t\t\tWaitIfstdOutput();\n\t\t\treturn(0);\n\t\t}\n\n\t\tif((ptr >= ptr1) && (ptr < ptr1 + curr->Size) && (ptr + size > ptr1 + curr->Size))\n\t\t{\n\t\t\tsprintf(st_Buffer, \"\\nFortify: %s.%ld\\n         Memory access detected after block\\n\",\n\t\t                file, line);\n\t\t\tst_Output(st_Buffer);\n\n\t\t\tsprintf(st_Buffer,\"         (%s,%ld,%s.%u)\\n\",\n\t\t\t\t\taddress(ptr + sizeof(struct Header) + FORTIFY_BEFORE_SIZE),\n\t\t\t\t\t(unsigned long)curr->Size, curr->File, curr->Line);\n\t\t\tst_Output(st_Buffer);\n\t\t\tWaitIfstdOutput();\n\t\t\treturn(0);\n\t\t}\n\n\t\tcurr = curr->Next;\n\t}\n\treturn(1);\n}\n\n/*\n * Checks if the _size_ bytes from _ptr_ are all set to _value_\n */\nstatic int CheckFortification(unsigned char *ptr,unsigned char value,size_t size)\n{\n\twhile(size--)\n\t\tif(*ptr++ != value)\n\t\t\treturn(0);\n\n\treturn(1);\n}\n\n/*\n * Set the _size_ bytes from _ptr_ to _value_.\n */\nstatic void SetFortification(unsigned char *ptr,unsigned char value,size_t size)\n{\n\tmemset(ptr, value, size);\n}\n\n/*\n * Output the corrupted section of the fortification\n */\n/* Output the corrupted section of the fortification */\nstatic void\nOutputFortification(unsigned char *ptr,unsigned char value,size_t size)\n{\n\tunsigned long offset, column;\n\tchar\tascii[17];\n\n\tst_Output(\"Address     Offset Data\");\n\n\toffset = 0;\n\tcolumn = 0;\n\n\twhile(offset < size)\n\t{\n\t\tif(column == 0)\n\t\t{\n\t\t\tsprintf(st_Buffer, \"\\n%8s %8d \", address(ptr), offset);\n\t\t\tst_Output(st_Buffer);\n\t\t}\n\n\t\tsprintf(st_Buffer, \"%02x \", *ptr);\n\t\tst_Output(st_Buffer);\n\n\t\tascii[ (int) column ] = isprint( *ptr ) ? (char)(*ptr) : (char)(' ');\n\t\tascii[ (int) (column + 1) ] = '\\0';\n\n\t\tptr++;\n\t\toffset++;\n\t\tcolumn++;\n\n\t\tif(column == 16)\n\t\t{\n\t\t\tst_Output( \"   \\\"\" );\n\t\t\tst_Output( ascii );\n\t\t\tst_Output( \"\\\"\" );\n\t\t\tcolumn = 0;\n\t\t}\n\t}\n\n\tif ( column != 0 )\n\t{\n\t\twhile ( column ++ < 16 )\n\t\t{\n\t\t\tst_Output( \"   \" );\n\t\t}\n\t\tst_Output( \"   \\\"\" );\n\t\tst_Output( ascii );\n\t\tst_Output( \"\\\"\" );\n\t}\n\n\tst_Output(\"\\n\");\n}\n\n/*\n * Returns true if the supplied pointer does indeed point to a real Header\n */\nstatic int IsHeaderValid(struct Header *h)\n{\n\treturn(!ChecksumHeader(h));\n}\n\n/*\n * Updates the checksum to make the header valid\n */\nstatic void MakeHeaderValid(struct Header *h)\n{\n\th->Checksum = 0;\n\th->Checksum = -ChecksumHeader(h);\n}\n\n/*\n * Calculate (and return) the checksum of the header. (Including the Checksum\n * variable itself. If all is well, the checksum returned by this function should\n * be 0.\n */\nstatic int ChecksumHeader(struct Header *h)\n{\n\tregister int c, checksum, *p;\n\n\tfor(c = 0, checksum = 0, p = (int *)h; c < sizeof(struct Header)/sizeof(int); c++)\n\t\tchecksum += *p++;\n\n\treturn(checksum);\n}\n\n/*\n * Examines the malloc'd list to see if the given header is on it.\n */\nstatic int IsOnList(struct Header *h)\n{\n\tstruct Header *curr;\n\n\tcurr = st_Head;\n\twhile(curr)\n\t{\n\t\tif(curr == h)\n\t\t\treturn(1);\n\t\tcurr = curr->Next;\n\t}\n\n\treturn(0);\n}\n\n\n/*\n * Hex and ascii dump the memory\n */\nstatic void\nOutputMemory(struct Header *h)\n{\n\tOutputFortification((unsigned char*)h + sizeof(struct Header) + FORTIFY_BEFORE_SIZE,\n\t\t\t\t\t\t0, h->Size);\n}\n\n\n/*\n * Output the header...\n */\nstatic void OutputHeader(struct Header *h)\n{\n\tsprintf(st_Buffer, \"%11s %8ld %s.%u (%d)\\n\",\n\t\t\t   address((unsigned char*)h + sizeof(struct Header) + FORTIFY_BEFORE_SIZE),\n\t\t\t   (unsigned long)h->Size,\n\t\t\t   h->File, h->Line, (int) h->Scope);\n\tst_Output(st_Buffer);\n}\n\nstatic void OutputLastVerifiedPoint()\n{\n\tsprintf(st_Buffer, \"\\nLast Verified point: %s.%u\\n\",\n\t\t\t   st_LastVerifiedFile,\n\t\t\t   st_LastVerifiedLine);\n\tst_Output(st_Buffer);\n}\n\n#else  /* FORTIFY_TRANSPARENT */\n\nvoid *FORTIFY_STORAGE\n_Fortify_malloc(size,file,line)\n size_t size;\n char *file;\n unsigned long line;\n{\n\treturn(malloc(size));\n}\n\nvoid FORTIFY_STORAGE\n_Fortify_free(uptr,file,line)\n void *uptr;\n char *file;\n unsigned long line;\n{\n\tfree(uptr);\n}\n\nvoid *FORTIFY_STORAGE\n_Fortify_realloc(ptr,new_size,file,line)\n void *ptr;\n size_t new_size;\n char *file;\n unsigned long line;\n{\n\treturn(realloc(ptr, new_size));\n}\n\nint FORTIFY_STORAGE\n_Fortify_CheckPointer(uptr,file,line)\n void *uptr;\n char *file;\n unsigned long line;\n{\n\treturn(1);\n}\n\nFortify_OutputFuncPtr FORTIFY_STORAGE\n_Fortify_SetOutputFunc(Output)\n Fortify_OutputFuncPtr Output;\n{\n\treturn(0);\n}\n\nint FORTIFY_STORAGE\n_Fortify_SetMallocFailRate(Percent)\n int Percent;\n{\n\treturn(0);\n}\n\nint FORTIFY_STORAGE\n_Fortify_CheckAllMemory(file,line)\n char *file;\n unsigned long line;\n{\n\treturn(0);\n}\n\nint FORTIFY_STORAGE\n_Fortify_EnterScope(file,line)\n char *file;\n unsigned long line;\n{\n\treturn(0);\n}\n\nint FORTIFY_STORAGE\n_Fortify_LeaveScope(file,line)\n char *file;\n unsigned long line;\n{\n\treturn(0);\n}\n\nint FORTIFY_STORAGE\n_Fortify_OutputAllMemory(file,line)\n char *file;\n unsigned long line;\n{\n\treturn(0);\n}\n\nint FORTIFY_STORAGE\n_Fortify_DumpAllMemory(scope,file,line)\n int scope;\n char *file;\n unsigned long line;\n{\n\treturn(0);\n}\n\nint FORTIFY_STORAGE\n_Fortify_Disable(file,line)\n char *file;\n unsigned long line;\n{\n\treturn(1);\n}\n\n#endif /* !FORTIFY_TRANSPARENT */\n\n/* function that use _Fortify_malloc(), _Fortify_realloc(), _Fortify_free() */\n\n/*\n * Fortifty_calloc() - Uses _Fortify_malloc() to implement calloc(). Much\n *                     the same protection as _Fortify_malloc().\n */\nvoid *FORTIFY_STORAGE\n_Fortify_calloc(size_t nitems,size_t size,char *file,unsigned long line)\n{\n\tvoid *ptr;\n\n\tptr = _Fortify_malloc(nitems * size, file, line);\n\n\tif(ptr)\n\t\tmemset(ptr, 0, nitems * size);\n\n\treturn(ptr);\n}\n\n/*\n * Fortifty_strdup() - Uses _Fortify_malloc() to implement strdup(). Much\n *                     the same protection as _Fortify_malloc().\n * The library function is not used because it is not certain that getpwd\n * uses the library malloc function (if linked with an alternate library)\n * and if the memory is freed then strange things can happen\n */\nchar *FORTIFY_STORAGE\n_Fortify_strdup(char *str,char *file,unsigned long line)\n{\n\tchar *ptr;\n\tunsigned long l;\n\n\tif(str == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strdup pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\tl = (int) strlen(str) + 1;\n\t__Fortify_CheckPointer(str,0,l,file,line);\n\n\tptr = (char *) _Fortify_malloc(l, file, line);\n\n\tif(ptr)\n\t\tstrcpy(ptr, str);\n\n\treturn(ptr);\n}\n\n/*\n * Fortifty_getpwd() - Uses _Fortify_malloc() to implement getpwd(). Much\n *                     the same protection as _Fortify_malloc().\n * Memory is not allocated bu getcwd but by our routine for the same reason\n * as for strdup\n */\nchar *FORTIFY_STORAGE\n_Fortify_getcwd(char *buf,int size,char *file,unsigned long line)\n{\n\tchar *ptr;\n\n        if(buf!=NULL)\n                ptr = buf;\n\telse\n        \tptr = (char *) _Fortify_malloc(size + 1, file, line);\n\n\tif(ptr)\n\t\tptr = getcwd(ptr, size);\n\n\treturn(ptr);\n}\n\n/*\n * Fortifty_tempnam() - Uses _Fortify_strdup() to implement tempnam(). Much\n *                     the same protection as _Fortify_malloc().\n */\nchar *FORTIFY_STORAGE\n_Fortify_tempnam(char *dir,char *pfx,char *file,unsigned long line)\n{\n\tchar *ptr1, *ptr2;\n\n        ptr1 = tempnam(dir,pfx);\n\n\tif(ptr1)\n        {\n                ptr2=_Fortify_strdup(ptr1,file,line);\n                free(ptr1);\n                ptr1=ptr2;\n        }\n\n\treturn(ptr1);\n}\n\n/*\n * Fortify_memcpy()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nvoid *FORTIFY_STORAGE\n_Fortify_memcpy(void *to,void *from,size_t size,char *file,unsigned long line)\n{\n    if (size) {\n\t    if((from == NULL) || (to == NULL)) {\n\t\t    sprintf(st_Buffer,\n\t\t\t    \"\\nFortify: %s.%ld\\n         \", file, line);\n\t\t    if(from == NULL)\n\t\t\t    sprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"memcpy from pointer is NULL\", file, line);\n\t\t    if(to == NULL)\n\t\t\t    sprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (from == NULL) ? \"\" : \" and \", \"memcpy to pointer is NULL\", file, line);\n\t\t    strcat(st_Buffer, \"\\n\");\n\t\t    st_Output(st_Buffer);\n\t\t    FORTIFY_UNLOCK();\n\t\t    WaitIfstdOutput();\n\t\t    return(NULL);\n\t    }\n\n\t    __Fortify_CheckPointer(to,0,size,file,line);\n\t    __Fortify_CheckPointer(from,0,size,file,line);\n    }\n\treturn(memcpy(to,from,size));\n}\n\n/*\n * Fortify_memmove()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nvoid *FORTIFY_STORAGE\n_Fortify_memmove(void *to,void *from,size_t size,char *file,unsigned long line)\n{\n\tif((from == NULL) || (to == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(from == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"memmove from pointer is NULL\", file, line);\n\t\tif(to == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (from == NULL) ? \"\" : \" and \", \"memmove to pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(to,0,size,file,line);\n\t__Fortify_CheckPointer(from,0,size,file,line);\n\treturn(memmove(to,from,size));\n}\n\n/*\n * Fortify_memccpy()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nvoid *FORTIFY_STORAGE\n_Fortify_memccpy(void *to,void *from,int c,size_t size,char *file,unsigned long line)\n{\n\tif((from == NULL) || (to == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(from == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"memccpy from pointer is NULL\", file, line);\n\t\tif(to == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (from == NULL) ? \"\" : \" and \", \"memccpy to pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(to,0,size,file,line);\n\t__Fortify_CheckPointer(from,0,size,file,line);\n\treturn(memccpy(to,from,c,size));\n}\n\n/*\n * Fortify_memset()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nvoid *FORTIFY_STORAGE\n_Fortify_memset(void *buffer,int c,size_t size,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         memset pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,size,file,line);\n\treturn(memset(buffer,c,size));\n}\n\n/*\n * Fortify_memchr()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nvoid *FORTIFY_STORAGE\n_Fortify_memchr(void *buffer,int c,size_t size,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         memchr pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,size,file,line);\n\treturn(memchr(buffer,c,size));\n}\n\n/*\n * Fortify_memcmp()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nint FORTIFY_STORAGE\n_Fortify_memcmp(void *buffer1,void *buffer2,size_t size,char *file,unsigned long line)\n{\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"memcmp first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"memcmp second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,size,file,line);\n\t__Fortify_CheckPointer(buffer2,0,size,file,line);\n\treturn(memcmp(buffer1,buffer2,size));\n}\n\n/*\n * Fortify_memicmp()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nint FORTIFY_STORAGE\n_Fortify_memicmp(void *buffer1,void *buffer2,size_t size,char *file,unsigned long line)\n{\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"memicmp first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"memicmp second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,size,file,line);\n\t__Fortify_CheckPointer(buffer2,0,size,file,line);\n\treturn(memicmp(buffer1,buffer2,size));\n}\n\n/*\n * Fortify_strcoll()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nint FORTIFY_STORAGE\n_Fortify_strcoll(char *buffer1,char *buffer2,char *file,unsigned long line)\n{\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strcoll first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strcoll second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\t__Fortify_CheckPointer(buffer2,0,strlen(buffer2)+1,file,line);\n\treturn(strcoll(buffer1,buffer2));\n}\n\n/*\n * Fortify_strcspn()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nsize_t FORTIFY_STORAGE\n_Fortify_strcspn(char *buffer1,char *buffer2,char *file,unsigned long line)\n{\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strcspn first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strcspn second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\t__Fortify_CheckPointer(buffer2,0,strlen(buffer2)+1,file,line);\n\treturn(strcspn(buffer1,buffer2));\n}\n\n/*\n * Fortify_strcmp()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nint FORTIFY_STORAGE\n_Fortify_strcmp(char *buffer1,char *buffer2,char *file,unsigned long line)\n{\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strcmp first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strcmp second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\t__Fortify_CheckPointer(buffer2,0,strlen(buffer2)+1,file,line);\n\treturn(strcmp(buffer1,buffer2));\n}\n\n/*\n * Fortify_strcmpi()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nint FORTIFY_STORAGE\n_Fortify_strcmpi(char *buffer1,char *buffer2,char *file,unsigned long line)\n{\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strcmpi first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strcmpi second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\t__Fortify_CheckPointer(buffer2,0,strlen(buffer2)+1,file,line);\n\treturn(strcmpi(buffer1,buffer2));\n}\n\n/*\n * Fortify_strncmp()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nint FORTIFY_STORAGE\n_Fortify_strncmp(char *buffer1,char *buffer2,size_t size,char *file,unsigned long line)\n{\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strncmp first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strncmp second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,MIN(strlen(buffer1)+1,size),file,line);\n\t__Fortify_CheckPointer(buffer2,0,MIN(strlen(buffer2)+1,size),file,line);\n\treturn(strncmp(buffer1,buffer2,size));\n}\n\n/*\n * Fortify_strnicmp()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nint FORTIFY_STORAGE\n_Fortify_strnicmp(char *buffer1,char *buffer2,size_t size,char *file,unsigned long line)\n{\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strnicmp first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strnicmp second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,MIN(strlen(buffer1)+1,size),file,line);\n\t__Fortify_CheckPointer(buffer2,0,MIN(strlen(buffer2)+1,size),file,line);\n\treturn(strnicmp(buffer1,buffer2,size));\n}\n\n/*\n * Fortify_strchr()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strchr(char *buffer,int c,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         strchr pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,strlen(buffer)+1,file,line);\n\treturn(strchr(buffer,c));\n}\n\n/*\n * Fortify_strrchr()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strrchr(char *buffer,int c,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         strchr pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,strlen(buffer)+1,file,line);\n\treturn(strrchr(buffer,c));\n}\n\n/*\n * Fortify_strlwr()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strlwr(char *buffer,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         strlwr pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,strlen(buffer)+1,file,line);\n\treturn(strlwr(buffer));\n}\n\n/*\n * Fortify_strlwr()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strupr(char *buffer,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         strupr pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,strlen(buffer)+1,file,line);\n\treturn(strupr(buffer));\n}\n\n/*\n * Fortify_strrev()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strrev(char *buffer,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         strrev pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,strlen(buffer)+1,file,line);\n\treturn(strrev(buffer));\n}\n\n/*\n * Fortify_strlen()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nsize_t FORTIFY_STORAGE\n_Fortify_strlen(char *buffer,char *file,unsigned long line)\n{\n\tunsigned long l;\n\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         strlen pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\tl = strlen(buffer);\n\t__Fortify_CheckPointer(buffer,0,l+1,file,line);\n\treturn(l);\n}\n\n/*\n * Fortify_strcat()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strcat(char *buffer1,char *buffer2,char *file,unsigned long line)\n{\n\tunsigned long l;\n\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strcat first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strcat second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\tl = strlen(buffer2)+1;\n\t__Fortify_CheckPointer(buffer1,0,l,file,line);\n\t__Fortify_CheckPointer(buffer2,0,l,file,line);\n\treturn(strcat(buffer1,buffer2));\n}\n\n/*\n * Fortify_strpbrk()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strpbrk(char *buffer1,char *buffer2,char *file,unsigned long line)\n{\n\tunsigned long l;\n\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strpbrk first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strpbrk second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\tl = strlen(buffer2)+1;\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\t__Fortify_CheckPointer(buffer2,0,l,file,line);\n\treturn(strpbrk(buffer1,buffer2));\n}\n\n/*\n * Fortify_strstr()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strstr(char *buffer1,char *buffer2,char *file,unsigned long line)\n{\n\tunsigned long l;\n\n\tif((buffer1 == NULL) || (buffer2 == NULL)) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tif(buffer1 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strstr first pointer is NULL\", file, line);\n\t\tif(buffer2 == NULL)\n\t\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s%s\", (buffer2 == NULL) ? \"\" : \" and \", \"strstr second pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\tl = strlen(buffer2)+1;\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\t__Fortify_CheckPointer(buffer2,0,l,file,line);\n\treturn(strstr(buffer1,buffer2));\n}\n\n/*\n * Fortify_strtol()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nlong FORTIFY_STORAGE\n_Fortify_strtol(char *buffer1,char **buffer2,int n,char *file,unsigned long line)\n{\n\tif(buffer1 == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strtol first pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\treturn(strtol(buffer1,buffer2,n));\n}\n\n/*\n * Fortify_atoi()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nint FORTIFY_STORAGE\n_Fortify_atoi(char *buffer1,char *file,unsigned long line)\n{\n\tif(buffer1 == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"atoi first pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\treturn(atoi(buffer1));\n}\n\n/*\n * Fortify_atol()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nlong FORTIFY_STORAGE\n_Fortify_atol(char *buffer1,char *file,unsigned long line)\n{\n\tif(buffer1 == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"atol first pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\treturn(atol(buffer1));\n}\n\n/*\n * Fortify_atod()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\ndouble FORTIFY_STORAGE\n_Fortify_atof(char *buffer1,char *file,unsigned long line)\n{\n\tif(buffer1 == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"atod first pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\treturn(atof(buffer1));\n}\n\n/*\n * Fortify_strtoul()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nunsigned long FORTIFY_STORAGE\n_Fortify_strtoul(char *buffer1,char **buffer2,int n,char *file,unsigned long line)\n{\n\tif(buffer1 == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strtoul first pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\treturn(strtoul(buffer1,buffer2,n));\n}\n\n/*\n * Fortify_strtod()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\ndouble FORTIFY_STORAGE\n_Fortify_strtod(char *buffer1,char **buffer2,char *file,unsigned long line)\n{\n\tif(buffer1 == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         \", file, line);\n\t\tsprintf(st_Buffer + strlen(st_Buffer), \"%s\", \"strtod first pointer is NULL\", file, line);\n\t\tstrcat(st_Buffer, \"\\n\");\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(0);\n\t}\n\n\t__Fortify_CheckPointer(buffer1,0,strlen(buffer1)+1,file,line);\n\treturn(strtod(buffer1,buffer2));\n}\n\n/*\n * Fortify_strset()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strset(char *buffer,int c,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         strset pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,strlen(buffer)+1,file,line);\n\treturn(strset(buffer,c));\n}\n\n/*\n * Fortify_strnset()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strnset(char *buffer,int c,size_t size,char *file,unsigned long line)\n{\n\tif(buffer == NULL) {\n\t\tsprintf(st_Buffer,\n\t\t\t\"\\nFortify: %s.%ld\\n         strnset pointer is NULL\\n\", file, line);\n\t\tst_Output(st_Buffer);\n\t\tFORTIFY_UNLOCK();\n\t\tWaitIfstdOutput();\n\t\treturn(NULL);\n\t}\n\n\t__Fortify_CheckPointer(buffer,0,strlen(buffer)+1,file,line);\n\treturn(strnset(buffer,c,size));\n}\n\n/*\n * Fortify_strncpy()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nstatic char *FORTIFY_STORAGE\n__Fortify_strncpy(char *to,char *from,size_t size,int usesize,char *file,unsigned long line)\n{\n\tsize_t size1;\n\n\tsize1 = strlen(from) + 1;\n\tif(usesize)\n\t{\n\t\tif(size < size1)\n\t\t\tsize1 = size;\n\t}\n\n\treturn((char *) _Fortify_memcpy(to,from,size1,file,line));\n}\n\n/*\n * Fortify_strncpy()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strncpy(char *to,char *from,size_t size,char *file,unsigned long line)\n{\n\treturn(__Fortify_strncpy(to,from,size,1,file,line));\n}\n\n/*\n * Fortify_strncpy()  - check if from/to is in allocated space and if so, then check if start/end is not outside allocated space.\n */\nchar *FORTIFY_STORAGE\n_Fortify_strcpy(char *to,char *from,char *file,unsigned long line)\n{\n\treturn(__Fortify_strncpy(to,from,0,0,file,line));\n}\n\n#endif /* FORTIFY */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/fortify.h",
    "content": "#ifndef __FORTIFY_H__\n#define __FORTIFY_H__\n/*\n * FILE:\n *   fortify.h\n *\n * DESCRIPTION:\n *     Header file for fortify.c - A fortified shell for malloc, realloc,\n *   calloc, strdup, getcwd, tempnam & free\n *\n * WRITTEN:\n *   spb 29/4/94\n *\n * VERSION:\n *   1.0 29/4/94\n */\n#include <stdlib.h>\n\n#include \"declare.h\"\n\n#if defined HP9000 || defined AViiON || defined ALPHA || defined SIGNED_UNKNOWN\n# define signed\n#endif\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n#ifdef FORTIFY\n\ntypedef void (*OutputFuncPtr) __OF((char *));\n\nextern char *_Fortify_file;\nextern int _Fortify_line;\n\n#define Fortify_FILE(file) _Fortify_file=file\n#define Fortify_LINE(line) _Fortify_line=line\n\n#define _Fortify_FILE (_Fortify_file==(char *) 0 ? __FILE__ : _Fortify_file)\n#define _Fortify_LINE (_Fortify_line==0 ? __LINE__ : _Fortify_line)\n\nvoid  _Fortify_Init __OF((char *file, unsigned long line));\nvoid *_Fortify_malloc __OF((size_t size, char *file, unsigned long line));\nvoid *_Fortify_realloc __OF((void *ptr, size_t new_size, char *file, unsigned long line));\nvoid *_Fortify_calloc __OF((size_t nitems, size_t size, char *file, unsigned long line));\nchar *_Fortify_strdup __OF((char *str, char *file, unsigned long line));\nvoid *_Fortify_memcpy __OF((void *to, void *from, size_t size, char *file, unsigned long line));\nvoid *_Fortify_memmove __OF((void *to, void *from, size_t size, char *file, unsigned long line));\nvoid *_Fortify_memccpy __OF((void *to, void *from, int c, size_t size, char *file, unsigned long line));\nvoid *_Fortify_memset __OF((void *buffer, int c, size_t size, char *file, unsigned long line));\nvoid *_Fortify_memchr __OF((void *buffer, int c, size_t size, char *file, unsigned long line));\nint   _Fortify_memcmp __OF((void *buffer1, void *buffer2, size_t size, char *file, unsigned long line));\nint   _Fortify_memicmp __OF((void *buffer1, void *buffer2, size_t size, char *file, unsigned long line));\nchar *_Fortify_strchr __OF((char *buffer, int c, char *file, unsigned long line));\nchar *_Fortify_strrchr __OF((char *buffer, int c, char *file, unsigned long line));\nchar *_Fortify_strlwr __OF((char *buffer, char *file, unsigned long line));\nchar *_Fortify_strupr __OF((char *buffer, char *file, unsigned long line));\nchar *_Fortify_strrev __OF((char *buffer, char *file, unsigned long line));\nchar *_Fortify_strset __OF((char *buffer, int c, char *file, unsigned long line));\nchar *_Fortify_strnset __OF((char *buffer, int c, size_t size, char *file, unsigned long line));\nchar *_Fortify_strstr __OF((char *to, char *from, char *file, unsigned long line));\nchar *_Fortify_strcpy __OF((char *to, char *from, char *file, unsigned long line));\nchar *_Fortify_strncpy __OF((char *to, char *from, size_t size, char *file, unsigned long line));\nint   _Fortify_strcmp __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\ndouble _Fortify_strtod __OF((char *buffer1, char **buffer2, char *file, unsigned long line));\nlong _Fortify_strtol __OF((char *buffer1, char **buffer2, int n, char *file, unsigned long line));\nint _Fortify_atoi __OF((char *buffer1, char *file, unsigned long line));\nlong _Fortify_atol __OF((char *buffer1, char *file, unsigned long line));\ndouble _Fortify_atof __OF((char *buffer1, char *file, unsigned long line));\nunsigned long _Fortify_strtoul __OF((char *buffer1, char **buffer2, int n, char *file, unsigned long line));\nsize_t _Fortify_strcspn __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nint   _Fortify_strcoll __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nint   _Fortify_strcmpi __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nint   _Fortify_strncmp __OF((char *buffer1, char *buffer2, size_t size, char *file, unsigned long line));\nint   _Fortify_strnicmp __OF((char *buffer1, char *buffer2, size_t size, char *file, unsigned long line));\nchar *_Fortify_strcat __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nchar *_Fortify_strpbrk __OF((char *buffer1, char *buffer2, char *file, unsigned long line));\nsize_t _Fortify_strlen __OF((char *buffer, char *file, unsigned long line));\nchar *_Fortify_getcwd __OF((char *buf, int size, char *file, unsigned long line));\nchar *_Fortify_tempnam __OF((char *dir, char *pfx, char *file, unsigned long line));\nvoid  _Fortify_free __OF((void *uptr, char *file, unsigned long line));\n\nint   _Fortify_OutputAllMemory __OF((char *file, unsigned long line));\nint   _Fortify_CheckAllMemory __OF((char *file, unsigned long line));\nint   _Fortify_CheckPointer __OF((void *uptr, char *file, unsigned long line));\nint   _Fortify_Disable __OF((char *file, unsigned long line, int how));\nint   _Fortify_SetMallocFailRate __OF((int Percent));\nint   _Fortify_EnterScope __OF((char *file, unsigned long line));\nint   _Fortify_LeaveScope __OF((char *file, unsigned long line));\nint   _Fortify_DumpAllMemory __OF((int scope, char *file, unsigned long line));\n\ntypedef void (*Fortify_OutputFuncPtr) __OF((/* const */ char *));\nFortify_OutputFuncPtr _Fortify_SetOutputFunc __OF((Fortify_OutputFuncPtr Output));\n\n#endif /* FORTIFY */\n\n#ifdef __cplusplus\n}\n#endif\n\n#ifndef __FORTIFY_C__ /* Only define the macros if we're NOT in fortify.c */\n\n#ifdef FORTIFY /* Add file and line information to the fortify calls */\n\n#if defined malloc\n# undef malloc\n#endif\n#if defined realloc\n# undef realloc\n#endif\n#if defined calloc\n# undef calloc\n#endif\n#if defined strdup\n# undef strdup\n#endif\n#if defined memcpy\n# undef memcpy\n#endif\n#if defined memmove\n# undef memmove\n#endif\n#if defined memccpy\n# undef memccpy\n#endif\n#if defined memset\n# undef memset\n#endif\n#if defined memchr\n# undef memchr\n#endif\n#if defined memcmp\n# undef memcmp\n#endif\n#if defined memicmp\n# undef memicmp\n#endif\n#if defined strcoll\n# undef strcoll\n#endif\n#if defined strcspn\n# undef strcspn\n#endif\n#if defined strcmp\n# undef strcmp\n#endif\n#if defined strcmpi\n# undef strcmpi\n#endif\n#if defined stricmp\n# undef stricmp\n#endif\n#if defined strncmp\n# undef strncmp\n#endif\n#if defined strnicmp\n# undef strnicmp\n#endif\n#if defined strlwr\n# undef strlwr\n#endif\n#if defined strupr\n# undef strupr\n#endif\n#if defined strrev\n# undef strrev\n#endif\n#if defined strchr\n# undef strchr\n#endif\n#if defined strrchr\n# undef strrchr\n#endif\n#if defined strcat\n# undef strcat\n#endif\n#if defined strpbrk\n# undef strpbrk\n#endif\n#if defined strcpy\n# undef strcpy\n#endif\n#if defined atoi\n# undef atoi\n#endif\n#if defined atol\n# undef atol\n#endif\n#if defined atof\n# undef atof\n#endif\n#if defined strtol\n# undef strtol\n#endif\n#if defined strtoul\n# undef strtoul\n#endif\n#if defined strtod\n# undef strtod\n#endif\n#if defined strstr\n# undef strstr\n#endif\n#if defined strncpy\n# undef strncpy\n#endif\n#if defined strset\n# undef strset\n#endif\n#if defined strnset\n# undef strnset\n#endif\n#if defined strlen\n# undef strlen\n#endif\n#if defined getcwd\n# undef getcwd\n#endif\n#if defined tempnam\n# undef tempnam\n#endif\n#if defined free\n# undef free\n#endif\n\n#define malloc(size)                  _Fortify_malloc(size, _Fortify_FILE, _Fortify_LINE)\n#define realloc(ptr,new_size)         _Fortify_realloc(ptr, new_size, _Fortify_FILE, _Fortify_LINE)\n#define calloc(num,size)              _Fortify_calloc(num, size, _Fortify_FILE, _Fortify_LINE)\n#define strdup(str)                   _Fortify_strdup(str, _Fortify_FILE, _Fortify_LINE)\n#define memcpy(to,from,size)          _Fortify_memcpy((void *)(to),(void *)(from),size, _Fortify_FILE, _Fortify_LINE)\n#define memmove(to,from,size)         _Fortify_memmove((void *)(to),(void *)(from),size, _Fortify_FILE, _Fortify_LINE)\n#define memccpy(to,from,c,size)       _Fortify_memccpy((void *)(to),(void *)(from),c,size, _Fortify_FILE, _Fortify_LINE)\n#define memset(buffer,c,size)         _Fortify_memset(buffer,c,size, _Fortify_FILE, _Fortify_LINE)\n#define memchr(buffer,c,size)         _Fortify_memchr(buffer,c,size, _Fortify_FILE, _Fortify_LINE)\n#define memcmp(buffer1,buffer2,size)  _Fortify_memcmp((void *)buffer1,(void *)buffer2,size, _Fortify_FILE, _Fortify_LINE)\n#define memicmp(buffer1,buffer2,size) _Fortify_memicmp((void *)buffer1,(void *)buffer2,size, _Fortify_FILE, _Fortify_LINE)\n#define strlwr(buffer)                _Fortify_strlwr(buffer, _Fortify_FILE, _Fortify_LINE)\n#define strupr(buffer)                _Fortify_strupr(buffer, _Fortify_FILE, _Fortify_LINE)\n#define strrev(buffer)                _Fortify_strrev(buffer, _Fortify_FILE, _Fortify_LINE)\n#define strchr(buffer,c)              _Fortify_strchr(buffer,c, _Fortify_FILE, _Fortify_LINE)\n#define strrchr(buffer,c)             _Fortify_strrchr(buffer,c, _Fortify_FILE, _Fortify_LINE)\n#define strset(buffer,c)              _Fortify_strset(buffer,c, _Fortify_FILE, _Fortify_LINE)\n#define strnset(buffer,c)             _Fortify_strnset(buffer,c, _Fortify_FILE, _Fortify_LINE)\n#define strstr(buffer1,buffer2)       _Fortify_strstr(buffer1,buffer2, _Fortify_FILE, _Fortify_LINE)\n#define atoi(buffer)                  _Fortify_atoi(buffer, _Fortify_FILE, _Fortify_LINE)\n#define atol(buffer)                  _Fortify_atol(buffer, _Fortify_FILE, _Fortify_LINE)\n#define atof(buffer)                  _Fortify_atof(buffer, _Fortify_FILE, _Fortify_LINE)\n#define strtol(buffer1,buffer2,n)     _Fortify_strtol(buffer1,buffer2,n, _Fortify_FILE, _Fortify_LINE)\n#define strtoul(buffer1,buffer2,n)    _Fortify_strtoul(buffer1,buffer2,n, _Fortify_FILE, _Fortify_LINE)\n#define strtod(buffer1,buffer2)       _Fortify_strtod(buffer1,buffer2, _Fortify_FILE, _Fortify_LINE)\n#define strcpy(to,from)               _Fortify_strcpy((char *)(to),(char *)(from), _Fortify_FILE, _Fortify_LINE)\n#define strncpy(to,from,size)         _Fortify_strncpy((char *)(to),(char *)(from),size, _Fortify_FILE, _Fortify_LINE)\n#define strcoll(buffer1,buffer2)      _Fortify_strcoll((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strcspn(buffer1,buffer2)      _Fortify_strcspn((char*)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strcmp(buffer1,buffer2)       _Fortify_strcmp((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strcmpi(buffer1,buffer2)      _Fortify_strcmpi((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define stricmp(buffer1,buffer2)      _Fortify_strcmpi((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strncmp(buffer1,buffer2,size) _Fortify_strncmp((char *)(buffer1),(char *)(buffer2),size, _Fortify_FILE, _Fortify_LINE)\n#define strnicmp(buffer1,buffer2,size) _Fortify_strnicmp((char *)(buffer1),(char *)(buffer2),size, _Fortify_FILE, _Fortify_LINE)\n#define strcat(buffer1,buffer2)       _Fortify_strcat((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strpbrk(buffer1,buffer2)      _Fortify_strpbrk((char *)(buffer1),(char *)(buffer2), _Fortify_FILE, _Fortify_LINE)\n#define strlen(buffer)                _Fortify_strlen((char*)(buffer), _Fortify_FILE, _Fortify_LINE)\n#define getcwd(buf,size)              _Fortify_getcwd(buf, size, _Fortify_FILE, _Fortify_LINE)\n#define tempnam(dir,pfx)              _Fortify_tempnam(dir, pfx, _Fortify_FILE, _Fortify_LINE)\n#define free(ptr)                     _Fortify_free(ptr, _Fortify_FILE, _Fortify_LINE)\n\n#define Fortify_Init()                _Fortify_Init(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_OutputAllMemory()     _Fortify_OutputAllMemory(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_CheckAllMemory()      _Fortify_CheckAllMemory(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_CheckPointer(ptr)     _Fortify_CheckPointer(ptr, _Fortify_FILE, _Fortify_LINE)\n#define Fortify_Disable(how)          _Fortify_Disable(_Fortify_FILE, _Fortify_LINE,how)\n#define Fortify_EnterScope()          _Fortify_EnterScope(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_LeaveScope()          _Fortify_LeaveScope(_Fortify_FILE, _Fortify_LINE)\n#define Fortify_DumpAllMemory(s)      _Fortify_DumpAllMemory(s,_Fortify_FILE, _Fortify_LINE)\n\n#else /* FORTIFY Define the special fortify functions away to nothing */\n\n#define Fortify_FILE(file)\n#define Fortify_LINE(line)\n#define Fortify_Init()\n#define Fortify_OutputAllMemory()     0\n#define Fortify_CheckAllMemory()      0\n#define Fortify_CheckPointer(ptr)     1\n#define Fortify_Disable(how)          1\n#define Fortify_SetOutputFunc()       0\n#define Fortify_SetMallocFailRate(p)  0\n#define Fortify_EnterScope()          0\n#define Fortify_LeaveScope()          0\n#define Fortify_DumpAllMemory(s)      0\n\n#endif /*   FORTIFY     */\n#endif /* __FORTIFY_C__ */\n#endif /* __FORTIFY_H__ */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/ini.c",
    "content": "#include <stdio.h>\n#include <ctype.h>\n#include <string.h>\n\n#include \"lp_lib.h\"\n\n#include \"ini.h\"\n\nFILE *ini_create(char *filename)\n{\n  FILE *fp;\n\n  fp = fopen(filename, \"w\");\n\n  return(fp);\n}\n\nFILE *ini_open(char *filename)\n{\n  FILE *fp;\n\n  fp = fopen(filename, \"r\");\n\n  return(fp);\n}\n\nvoid ini_writecomment(FILE *fp, char *comment)\n{\n  fprintf(fp, \"; %s\\n\", comment);\n}\n\nvoid ini_writeheader(FILE *fp, char *header, int addnewline)\n{\n  if((addnewline) && (ftell(fp) > 0))\n    fputs(\"\\n\", fp);\n  fprintf(fp, \"[%s]\\n\", header);\n}\n\nvoid ini_writedata(FILE *fp, char *name, char *data)\n{\n  if(name != NULL)\n    fprintf(fp, \"%s=%s\\n\", name, data);\n  else\n    fprintf(fp, \"%s\\n\", data);\n}\n\nint ini_readdata(FILE *fp, char *data, int szdata, int withcomment)\n{\n  int l;\n  char *ptr;\n\n  if(fgets(data, szdata, fp) == NULL)\n    return(0);\n\n  if(!withcomment) {\n    ptr = strchr(data, ';');\n    if(ptr != NULL)\n      *ptr = 0;\n  }\n\n  l = (int) strlen(data);\n  while((l > 0) && (isspace(data[l - 1])))\n    l--;\n  data[l] = 0;\n  if((l >= 2) && (data[0] == '[') && (data[l - 1] == ']')) {\n    memcpy(data, data + 1, l - 2);\n    data[l - 2] = 0;\n    return(1);\n  }\n  return(2);\n}\n\nvoid ini_close(FILE *fp)\n{\n  fclose(fp);\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/ini.h",
    "content": "#include <stdio.h>\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\nextern FILE *ini_create(char *filename);\nextern FILE *ini_open(char *filename);\nextern void ini_writecomment(FILE *fp, char *comment);\nextern void ini_writeheader(FILE *fp, char *header, int addnewline);\nextern void ini_writedata(FILE *fp, char *name, char *data);\nextern int ini_readdata(FILE *fp, char *data, int szdata, int withcomment);\nextern void ini_close(FILE *fp);\n\n#ifdef __cplusplus\n}\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_Hash.c",
    "content": "\n#include <stdlib.h>\n#include <string.h>\n#include \"lp_lib.h\"\n#include \"lp_utils.h\"\n#include \"lp_report.h\"\n#include \"lp_Hash.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n#define HASH_START_SIZE  5000  /* Hash table size for row and column name storage */\n#define NUMHASHPRIMES      45\n\nSTATIC hashtable *create_hash_table(int size, int base)\n{\n  int i;\n  int HashPrimes[ ] = {\n             29,     229,     883,    1671,    2791,    4801,    8629,   10007,\n          15289,   25303,   34843,   65269,   99709,  129403,  147673,  166669,\n         201403,  222163,  242729,  261431,  303491,  320237,  402761,  501131,\n         602309,  701507,  800999,  900551, 1000619, 1100837, 1200359, 1300021,\n        1400017, 1500007, 1750009, 2000003, 2500009, 3000017, 4000037, 5000011,\n        6000011, 7000003, 8000009, 9000011, 9999991};\n  hashtable *ht;\n\n  /* Find a good size for the hash table */\n  if(size < HASH_START_SIZE)\n    size = HASH_START_SIZE;\n  for(i = 0; i < NUMHASHPRIMES-1; i++)\n    if(HashPrimes[i] > size)\n      break;\n  size = HashPrimes[i];\n\n  /* Then allocate and initialize memory */\n  ht = (hashtable *) calloc(1 , sizeof(*ht));\n  ht->table = (hashelem **) calloc(size, sizeof(*(ht->table)));\n  ht->size = size;\n  ht->base = base;\n  ht->count = base-1;\n\n  return(ht);\n}\n\nSTATIC void free_hash_item(hashelem **hp)\n{\n  free((*hp)->name);\n  free(*hp);\n  *hp = NULL;\n}\n\nSTATIC void free_hash_table(hashtable *ht)\n{\n  hashelem *hp, *thp;\n\n  hp = ht->first;\n  while(hp != NULL) {\n    thp = hp;\n    hp = hp->nextelem;\n    free_hash_item(&thp);\n  }\n  free(ht->table);\n  free(ht);\n}\n\n\n/* make a good hash function for any int size */\n/* inspired by Aho, Sethi and Ullman, Compilers ..., p436 */\n#define HASH_1 sizeof(unsigned int)\n#define HASH_2 (sizeof(unsigned int) * 6)\n#define HASH_3 (((unsigned int)0xF0) << ((sizeof(unsigned int) - 1) * CHAR_BIT))\n\nSTATIC int hashval(const char *string, int size)\n{\n  unsigned int result = 0, tmp;\n\n  for(; *string; string++) {\n    result = (result << HASH_1) + *string;\n    if((tmp = result & HASH_3) != 0) {\n      /* if any of the most significant bits is on */\n      result ^= tmp >> HASH_2; /* xor them in in a less significant part */\n      result ^= tmp; /* and reset the most significant bits to 0 */\n    }\n  }\n  return(result % size);\n} /* hashval */\n\n\nSTATIC hashelem *findhash(const char *name, hashtable *ht)\n{\n  hashelem *h_tab_p;\n  for(h_tab_p = ht->table[hashval(name, ht->size)];\n      h_tab_p != NULL;\n      h_tab_p = h_tab_p->next)\n    if(strcmp(name, h_tab_p->name) == 0) /* got it! */\n      break;\n  return(h_tab_p);\n} /* findhash */\n\n\nSTATIC hashelem *puthash(const char *name, int index, hashelem **list, hashtable *ht)\n{\n  hashelem *hp = NULL;\n  int      hashindex;\n\n  if(list != NULL) {\n    hp = list[index];\n    if(hp != NULL)\n      list[index] = NULL;\n  }\n\n  if((hp = findhash(name, ht)) == NULL) {\n\n    hashindex = hashval(name, ht->size);\n    hp = (hashelem *) calloc(1, sizeof(*hp));\n    allocCHAR(NULL, &hp->name, (int) (strlen(name) + 1), FALSE);\n    strcpy(hp->name, name);\n    hp->index = index;\n    ht->count++;\n    if(list != NULL)\n      list[index] = hp;\n\n    hp->next = ht->table[hashindex];\n    ht->table[hashindex] = hp;\n    if(ht->first == NULL)\n      ht->first = hp;\n    if(ht->last != NULL)\n      ht->last->nextelem = hp;\n    ht->last = hp;\n\n  }\n  return(hp);\n}\n\nSTATIC void drophash(const char *name, hashelem **list, hashtable *ht) {\n  hashelem *hp, *hp1, *hp2;\n  int      hashindex;\n\n  if((hp = findhash(name, ht)) != NULL) {\n    hashindex = hashval(name, ht->size);\n    if((hp1 = ht->table[hashindex]) != NULL) {\n      hp2 = NULL;\n      while((hp1 != NULL) && (hp1 != hp)) {\n        hp2 = hp1;\n        hp1 = hp1->next;\n      }\n      if(hp1 == hp) {\n        if(hp2 != NULL)\n          hp2->next = hp->next;\n        else\n          ht->table[hashindex] = hp->next;\n      }\n\n      hp1 = ht->first;\n      hp2 = NULL;\n      while((hp1 != NULL) && (hp1 != hp)) {\n        hp2 = hp1;\n        hp1 = hp1->nextelem;\n      }\n      if(hp1 == hp) {\n        if(hp2 != NULL)\n          hp2->nextelem = hp->nextelem;\n        else {\n          ht->first = hp->nextelem;\n          if (ht->first == NULL)\n            ht->last = NULL;\n        }\n      }\n      if(list != NULL)\n        list[hp->index] = NULL;\n      free_hash_item(&hp);\n      ht->count--;\n    }\n  }\n}\n\nSTATIC hashtable *copy_hash_table(hashtable *ht, hashelem **list, int newsize)\n{\n  hashtable *copy;\n  hashelem  *elem, *new_elem;\n\n  if(newsize < ht->size)\n    newsize = ht->size;\n\n  copy = create_hash_table(newsize, ht->base);\n  if (copy != NULL) {\n    elem = ht->first;\n    while (elem != NULL) {\n      if((new_elem = puthash(elem->name, elem->index, list, copy)) == NULL) {\n        free_hash_table(copy);\n        return(NULL);\n      }\n      elem = elem ->nextelem;\n    }\n  }\n\n  return(copy);\n}\n\nSTATIC int find_row(lprec *lp, char *name, MYBOOL Unconstrained_rows_found)\n{\n  hashelem *hp;\n\n  if (lp->rowname_hashtab != NULL)\n      hp = findhash(name, lp->rowname_hashtab);\n  else\n      hp = NULL;\n\n  if (hp == NULL) {\n    if(Unconstrained_rows_found) { /* just ignore them in this case */\n         return(-1);\n    }\n    else {\n      return(-1);\n    }\n  }\n  return(hp->index);\n}\n\nSTATIC int find_var(lprec *lp, char *name, MYBOOL verbose)\n{\n  hashelem *hp;\n\n  if (lp->colname_hashtab != NULL)\n      hp = findhash(name, lp->colname_hashtab);\n  else\n      hp = NULL;\n\n  if (hp == NULL) {\n    if(verbose)\n      report(lp, SEVERE, \"find_var: Unknown variable name '%s'\\n\", name);\n    return(-1);\n  }\n  return(hp->index);\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_Hash.h",
    "content": "#ifndef HEADER_lp_hash\n#define HEADER_lp_hash\n\n/* For row and column name hash tables */\n\ntypedef struct _hashelem\n{\n  char             *name;\n  int               index;\n  struct _hashelem *next;\n  struct _hashelem *nextelem;\n} hashelem;\n\ntypedef struct /* _hashtable */\n{\n  hashelem         **table;\n  int              size;\n  int              base;\n  int              count;\n  struct _hashelem *first;\n  struct _hashelem *last;\n} hashtable;\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nSTATIC hashtable *create_hash_table(int size, int base);\nSTATIC void      free_hash_table(hashtable *ht);\nSTATIC hashelem  *findhash(const char *name, hashtable *ht);\nSTATIC hashelem  *puthash(const char *name, int index, hashelem **list, hashtable *ht);\nSTATIC void      drophash(const char *name, hashelem **list, hashtable *ht);\nSTATIC void      free_hash_item(hashelem **hp);\nSTATIC hashtable *copy_hash_table(hashtable *ht, hashelem **list, int newsize);\nSTATIC int find_var(lprec *lp, char *name, MYBOOL verbose);\nSTATIC int find_row(lprec *lp, char *name, MYBOOL Unconstrained_rows_found);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_hash */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_MDO.c",
    "content": "/*\n    Minimum matrix inverse fill-in modules - interface for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Kjell Eikland \n    Contact:       kjell.eikland@broadpark.no \n    License terms: LGPL.\n    \n    Requires:      string.h, colamd.h, lp_lib.h\n\n    Release notes:\n    v1.0    1 September 2003    Preprocessing routines for minimum fill-in column \n                                ordering for inverse factorization using the open \n                                source COLAMD library.  Suitable for the dense parts\n                                of both the product form and LU factorization inverse \n                                methods.\n    v1.1    1 July 2004         Renamed from lp_colamdMDO to lp_MDO.                                \n\n   ---------------------------------------------------------------------------------- \n*/\n\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"colamd.h\"\n#include \"lp_MDO.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\nSTATIC MYBOOL includeMDO(MYBOOL *usedpos, int item)\n{\n/*  Legend:   TRUE            => A basic slack variable already in the basis\n              FALSE           => A column free for being pivoted in\n              AUTOMATIC+TRUE  => A row-singleton user column pivoted into the basis\n              AUTOMATIC+FALSE => A column-singleton user column pivoted into the basis */\n\n  /* Handle case where we are processing all columns */\n  if(usedpos == NULL)\n    return( TRUE );\n    \n  else {\n  /* Otherwise do the selective case */\n    MYBOOL test = usedpos[item];\n#if 1\n    return( test != TRUE );\n#else\n    test = test & TRUE;\n    return( test == FALSE );\n#endif\n  }\n}\n\nSTATIC int prepareMDO(lprec *lp, MYBOOL *usedpos, int *colorder, int *data, int *rowmap)\n/* This routine prepares data structures for colamd().  It is called twice, the first\n   time to count applicable non-zero elements by column, and the second time to fill in \n   the row indexes of the non-zero values from the first call.  Note that the colamd() \n   row index base is 0 (which suits lp_solve fine). */\n{\n  int     i, ii, j, k, kk;\n  int     nrows = lp->rows+1, ncols = colorder[0];\n  int     offset = 0, Bnz = 0, Tnz;\n  MYBOOL  dotally = (MYBOOL) (rowmap == NULL);\n  MATrec  *mat = lp->matA;\n  REAL    hold;\n  REAL    *value;\n  int     *rownr;\n\n  if(dotally)\n    data[0] = 0;\n\n  Tnz = nrows - ncols;\n  for(j = 1; j <= ncols; j++) {\n    kk = colorder[j];\n\n    /* Process slacks */\n    if(kk <= lp->rows) {\n      if(includeMDO(usedpos, kk)) {\n        if(!dotally)\n          data[Bnz] = rowmap[kk]+offset;\n        Bnz++;\n      }\n      Tnz++;\n    }\n    /* Process user columns */\n    else {\n      k = kk - lp->rows;\n      i = mat->col_end[k-1];\n      ii= mat->col_end[k];\n      Tnz += ii-i;\n#ifdef Paranoia\n      if(i >= ii)\n        lp->report(lp, SEVERE, \"prepareMDO: Encountered empty basic column %d\\n\", k);\n#endif\n\n      /* Detect if we need to do phase 1 adjustments of zero-valued OF variable */\n      rownr = &COL_MAT_ROWNR(i);\n      value = &COL_MAT_VALUE(i);\n      hold = 0;\n      if((*rownr > 0) && includeMDO(usedpos, 0) && modifyOF1(lp, kk, &hold, 1.0)) {\n        if(!dotally)\n          data[Bnz] = offset;\n        Bnz++;\n      }\n      /* Loop over all NZ-variables */\n      for(; i < ii; \n          i++, value += matValueStep, rownr += matRowColStep) {\n        if(!includeMDO(usedpos, *rownr))\n          continue;\n        /* See if we need to change phase 1 OF value */\n        if(*rownr == 0) {\n          hold = *value;\n          if(!modifyOF1(lp, kk, &hold, 1.0)) \n            continue;\n        }\n        /* Tally uneliminated constraint row values */\n        if(!dotally)\n          data[Bnz] = rowmap[*rownr]+offset;\n        Bnz++;\n      }\n    }\n    if(dotally)\n      data[j] = Bnz;\n  }\n  return( Tnz );\n}\n\nSTATIC MYBOOL verifyMDO(lprec *lp, int *col_end, int *row_nr, int rowmax, int colmax)\n{\n  int i, j, n, err = 0;\n\n  for(i = 1; i <= colmax; i++) {\n    n = 0;\n    for(j = col_end[i-1]; (j < col_end[i]) && (err == 0); j++, n++) {\n      if(row_nr[j] < 0 || row_nr[j] > rowmax)\n        err = 1;\n      if(n > 0 && row_nr[j] <= row_nr[j-1])\n        err = 2;\n      n++;\n    }\n  }\n  if(err != 0)\n    lp->report(lp, SEVERE, \"verifyMDO: Invalid MDO input structure generated (error %d)\\n\", err);\n  return( (MYBOOL) (err == 0) );\n}\n\nvoid *mdo_calloc(size_t size, size_t count)\n{\n  return ( calloc(size, count) );\n}\nvoid mdo_free(void *mem)\n{\n  free( mem );\n}\n\n\nint __WINAPI getMDO(lprec *lp, MYBOOL *usedpos, int *colorder, int *size, MYBOOL symmetric)\n{\n  int    error = FALSE;\n  int    nrows = lp->rows+1, ncols = colorder[0];\n  int    i, j, kk, n;\n  int    *col_end, *row_map = NULL;\n  int    Bnz, Blen, *Brows = NULL;\n  int    stats[COLAMD_STATS];\n  double knobs[COLAMD_KNOBS];\n\n /* Tally the non-zero counts of the unused columns/rows of the \n    basis matrix and store corresponding \"net\" starting positions */\n  allocINT(lp, &col_end, ncols+1, FALSE);\n  n = prepareMDO(lp, usedpos, colorder, col_end, NULL);\n  Bnz = col_end[ncols];\n\n /* Check that we have unused basic columns, otherwise skip analysis */  \n  if(ncols == 0 || Bnz == 0) \n    goto Transfer;\n\n /* Get net number of rows and fill mapper */\n  allocINT(lp, &row_map, nrows, FALSE);\n  nrows = 0;\n  for(i = 0; i <= lp->rows; i++) {\n    row_map[i] = i-nrows;\n   /* Increment eliminated row counter if necessary */\n    if(!includeMDO(usedpos, i)) \n      nrows++;\n  }\n  nrows = lp->rows+1 - nrows;\n\n /* Store row indeces of non-zero values in the basic columns */\n  Blen = colamd_recommended(Bnz, nrows, ncols);\n  allocINT(lp, &Brows, Blen, FALSE);\n  prepareMDO(lp, usedpos, colorder, Brows, row_map);\n#ifdef Paranoia\n  verifyMDO(lp, col_end, Brows, nrows, ncols);\n#endif\n\n /* Compute the MDO */\n#if 1\n  colamd_set_defaults(knobs);\n  knobs [COLAMD_DENSE_ROW] = 0.2+0.2 ;    /* default changed for UMFPACK */\n  knobs [COLAMD_DENSE_COL] = knobs [COLAMD_DENSE_ROW];    \n  if(symmetric && (nrows == ncols)) {\n    MEMCOPY(colorder, Brows, ncols + 1);\n    error = !symamd(nrows, colorder, col_end, Brows, knobs, stats, mdo_calloc, mdo_free);\n  }\n  else\n    error = !colamd(nrows, ncols, Blen, Brows, col_end, knobs, stats);\n#else\n  if(symmetric && (nrows == ncols)) {\n    MEMCOPY(colorder, Brows, ncols + 1);\n    error = !symamd(nrows, colorder, col_end, Brows, knobs, stats, mdo_calloc, mdo_free);\n  }\n  else\n    error = !colamd(nrows, ncols, Blen, Brows, col_end, (double *) NULL, stats);\n#endif\n\n /* Transfer the estimated optimal ordering, adjusting for index offsets */\nTransfer:\n  if(error) \n    error = stats[COLAMD_STATUS];\n  else {\n    MEMCOPY(Brows, colorder, ncols + 1);\n    for(j = 0; j < ncols; j++) {\n      kk = col_end[j];\n      n = Brows[kk+1];\n      colorder[j+1] = n;\n    }\n  }\n\n  /* Free temporary vectors */\n  FREE(col_end);\n  if(row_map != NULL)\n    FREE(row_map);\n  if(Brows != NULL)\n    FREE(Brows);\n\n  if(size != NULL)\n    *size = ncols;\n  return( error );\n}\n\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_MDO.h",
    "content": "#ifndef HEADER_MDO\n#define HEADER_MDO\n\n#include \"lp_types.h\"\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nint __WINAPI getMDO(lprec *lp, MYBOOL *usedpos, int *colorder, int *size, MYBOOL symmetric);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_MDO */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_MPS.c",
    "content": "\n#include <string.h>\n#include <stdarg.h>\n#include <ctype.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_scale.h\"\n#include \"lp_report.h\"\n#include \"lp_MPS.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* Define buffer-size controled function mapping */\n# if defined _MSC_VER\n#  define vsnprintf _vsnprintf\n# endif\n\n/* MPS file input and output routines for lp_solve                           */\n/* ------------------------------------------------------------------------- */\n\n/*\nA:  MPS format was named after an early IBM LP product and has emerged\nas a de facto standard ASCII medium among most of the commercial LP\ncodes.  Essentially all commercial LP codes accept this format, but if\nyou are using public domain software and have MPS files, you may need\nto write your own reader routine for this.  It's not too hard.  The\nmain things to know about MPS format are that it is column oriented (as\nopposed to entering the model as equations), and everything (variables,\nrows, etc.) gets a name.  MPS format is described in more detail in\nMurtagh's book, referenced in another section. Also,\n\nftp://softlib.cs.rice.edu/pub/miplib/mps_format\n\nis a nice short introduction.  exports\n\nMPS is an old format, so it is set up as though you were using punch\ncards, and is not free format. Fields start in column 1, 5, 15, 25, 40\nand 50.  Sections of an MPS file are marked by so-called header cards,\nwhich are distinguished by their starting in column 1.  Although it is\ntypical to use upper-case throughout the file (like I said, MPS has\nlong historical roots), many MPS-readers will accept mixed-case for\nanything except the header cards, and some allow mixed-case anywhere.\nThe names that you choose for the individual entities (constraints or\nvariables) are not important to the solver; you should pick names that\nare meaningful to you, or will be easy for a post-processing code to\nread.\n\nHere is a little sample model written in MPS format (explained in more\ndetail below):\n\nNAME          TESTPROB\nROWS\n N  COST\n L  LIM1\n G  LIM2\n E  MYEQN\nCOLUMNS\n    XONE      COST                 1   LIM1                 1\n    XONE      LIM2                 1\n    YTWO      COST                 4   LIM1                 1\n    YTWO      MYEQN               -1\n    ZTHREE    COST                 9   LIM2                 1\n    ZTHREE    MYEQN                1\nRHS\n    RHS1      LIM1                 5   LIM2                10\n    RHS1      MYEQN                7\nBOUNDS\n UP BND1      XONE                 4\n LO BND1      YTWO                -1\n UP BND1      YTWO                 1\nENDATA\n\nmeans:\n\nOptimize\n COST:    XONE + 4 YTWO + 9 ZTHREE\nSubject To\n LIM1:    XONE + YTWO <= 5\n LIM2:    XONE + ZTHREE >= 10\n MYEQN:   - YTWO + ZTHREE  = 7\nBounds\n 0 <= XONE <= 4\n-1 <= YTWO <= 1\nEnd\n\n*/\n\n/* copy a MPS name, only trailing spaces are removed. In MPS, names can have\n   embedded spaces! */\nSTATIC void namecpy(char *into, char *from)\n{\n  int i;\n\n  /* copy at most 8 characters of from, stop at end of string or newline */\n  for(i = 0; (from[i] != '\\0') && (from[i] != '\\n') && (from[i] != '\\r') && (i < 8); i++)\n    into[i] = from[i];\n\n  /* end with end of string */\n  into[i] = '\\0';\n\n  /* remove trailing spaces, if any */\n  for(i--; (i >= 0) && (into[i] == ' '); i--)\n    into[i] = '\\0';\n}\n\n/* scan an MPS line, and pick up the information in the fields that are\n   present */\n\n/* scan_line for fixed MPS format */\nSTATIC int scan_lineFIXED(lprec *lp, int section, char* line, char *field1, char *field2, char *field3,\n                          double *field4, char *field5, double *field6)\n{\n  int  items = 0, line_len;\n  char buf[16], *ptr1, *ptr2;\n\n  line_len = (int) strlen(line);\n  while ((line_len) && ((line[line_len-1] == '\\n') || (line[line_len-1] == '\\r') || (line[line_len-1] == ' ')))\n   line_len--;\n\n  if(line_len >= 1) { /* spaces or N/L/G/E or UP/LO */\n    strncpy(buf, line, 4);\n    buf[4] = '\\0';\n    sscanf(buf, \"%s\", field1);\n    items++;\n  }\n  else\n    field1[0] = '\\0';\n\n  line += 4;\n\n  if(line_len >= 5) { /* name */\n    if (line[-1] != ' ') {\n      report(lp, IMPORTANT, \"MPS_readfile: invalid data card; column 4 must be blank\\n\");\n      return(-1);\n    }\n    namecpy(field2, line);\n    items++;\n  }\n  else\n    field2[0] = '\\0';\n\n  line += 10;\n\n  if(line_len >= 14) { /* name */\n    if (line[-1] != ' ' || line[-2] != ' ') {\n      report(lp, IMPORTANT, \"MPS_readfile: invalid data card; columns 13-14 must be blank\\n\");\n      return(-1);\n    }\n    namecpy(field3, line);\n    items++;\n  }\n  else\n    field3[0] = '\\0';\n\n  line += 10;\n\n  if(line_len >= 25) { /* number */\n    if (line[-1] != ' ' || line[-2] != ' ') {\n      report(lp, IMPORTANT, \"MPS_readfile: invalid data card; columns 23-24 must be blank\\n\");\n      return(-1);\n    }\n    strncpy(buf, line, 15);\n    buf[15] = '\\0';\n    for(ptr1 = ptr2 = buf; ; ptr1++)\n      if(!isspace((unsigned char) *ptr1))\n        if((*(ptr2++) = *ptr1) == 0)\n          break;\n    /* *field4 = atof(buf); */\n    *field4 = strtod(buf, &ptr1);\n    if(*ptr1) {\n      report(lp, IMPORTANT, \"MPS_readfile: invalid number in columns 25-36 \\n\");\n      return(-1);\n    }\n    items++;\n  }\n  else\n    *field4 = 0;\n\n  line += 15;\n\n  if(line_len >= 40) { /* name */\n    if (line[-1] != ' ' || line[-2] != ' ' || line[-3] != ' ') {\n      report(lp, IMPORTANT, \"MPS_readfile: invalid data card; columns 37-39 must be blank\\n\");\n      return(-1);\n    }\n    namecpy(field5, line);\n    items++;\n  }\n  else\n    field5[0] = '\\0';\n  line += 10;\n\n  if(line_len >= 50) { /* number */\n    if (line[-1] != ' ' || line[-2] != ' ') {\n      report(lp, IMPORTANT, \"MPS_readfile: invalid data card; columns 48-49 must be blank\\n\");\n      return(-1);\n    }\n    strncpy(buf, line, 15);\n    buf[15] = '\\0';\n    for(ptr1 = ptr2 = buf; ; ptr1++)\n      if(!isspace((unsigned char) *ptr1))\n        if((*(ptr2++) = *ptr1) == 0)\n          break;\n    /* *field6 = atof(buf); */\n    *field6 = strtod(buf, &ptr1);\n    if(*ptr1) {\n      report(lp, IMPORTANT, \"MPS_readfile: invalid number in columns 50-61 \\n\");\n      return(-1);\n    }\n    items++;\n  }\n  else\n    *field6 = 0;\n\n  return(items);\n}\n\nSTATIC int spaces(char *line, int line_len)\n{\n  int l;\n  char *line1 = line;\n\n  while (*line1 == ' ')\n    line1++;\n  l = (int) (line1 - line);\n  if (line_len < l)\n    l = line_len;\n  return(l);\n}\n\nSTATIC int lenfield(char *line, int line_len)\n{\n  int l;\n  char *line1 = line;\n\n  while ((*line1) && (*line1 != ' '))\n    line1++;\n  l = (int) (line1 - line);\n  if (line_len < l)\n    l = line_len;\n  return(l);\n}\n\n/* scan_line for fixed MPS format */\nSTATIC int scan_lineFREE(lprec *lp, int section, char* line, char *field1, char *field2, char *field3,\n                         double *field4, char *field5, double *field6)\n{\n  int  items = 0, line_len, len;\n  char buf[256], *ptr1 = NULL, *ptr2;\n\n  line_len = (int) strlen(line);\n  while ((line_len) && ((line[line_len-1] == '\\n') || (line[line_len-1] == '\\r') || (line[line_len-1] == ' ')))\n   line_len--;\n\n  len = spaces(line, line_len);\n  line += len;\n  line_len -= len;\n\n  if ((section == MPSCOLUMNS) || (section == MPSRHS) || (section == MPSRANGES)) {\n    field1[0] = '\\0';\n    items++;\n  }\n  else {\n    len = lenfield(line, line_len);\n    if(line_len >= 1) { /* spaces or N/L/G/E or UP/LO */\n      strncpy(buf, line, len);\n      buf[len] = '\\0';\n      sscanf(buf, \"%s\", field1);\n      if(section == MPSBOUNDS) {\n        for(ptr1 = field1; *ptr1; ptr1++)\n          *ptr1=(char)toupper(*ptr1);\n      }\n      items++;\n    }\n    else\n      field1[0] = '\\0';\n\n    line += len;\n    line_len -= len;\n\n    len = spaces(line, line_len);\n    line += len;\n    line_len -= len;\n  }\n\n  len = lenfield(line, line_len);\n  if(line_len >= 1) { /* name */\n    strncpy(field2, line, len);\n    field2[len] = '\\0';\n    items++;\n  }\n  else\n    field2[0] = '\\0';\n\n  line += len;\n  line_len -= len;\n\n  len = spaces(line, line_len);\n  line += len;\n  line_len -= len;\n\n  len = lenfield(line, line_len);\n  if(line_len >= 1) { /* name */\n    strncpy(field3, line, len);\n    field3[len] = '\\0';\n    items++;\n  }\n  else\n    field3[0] = '\\0';\n\n  line += len;\n  line_len -= len;\n\n  len = spaces(line, line_len);\n  line += len;\n  line_len -= len;\n\n  if (*field3) {\n    if((section == MPSCOLUMNS) && (strcmp(field3, \"'MARKER'\") == 0)) {\n      *field4 = 0;\n      items++;\n      ptr1 = field3;\n    }\n    else if((section == MPSBOUNDS) &&\n            ((strcmp(field1, \"FR\") == 0) || (strcmp(field1, \"MI\") == 0) || (strcmp(field1, \"PL\") == 0) || (strcmp(field1, \"BV\") == 0)))\n      /* field3 *is* the variable name */;\n    else {\n      /* Some free MPS formats allow that field 2 is not provided after the first time.\n         The fieldname is then the same as the the defined field the line before.\n         In that case field2 shifts to field3, field1 shifts to field 2.\n         This situation is tested by checking if field3 is numerical AND there are an even number of fields after.\n      */\n      char *line1 = line;\n      int line_len1 = line_len;\n      int items1 = 0;\n\n      while (line_len1 > 0) {\n        len = lenfield(line1, line_len1);\n        if (len > 0) {\n          line1 += len;\n          line_len1 -= len;\n          items1++;\n        }\n        len = spaces(line1, line_len1);\n        line1 += len;\n        line_len1 -= len;\n      }\n      if ((items1 % 2) == 0) {\n        *field4 = strtod(field3, &ptr1);\n        if(*ptr1 == 0) {\n          strcpy(field3, field2);\n          if ((section == MPSROWS) || (section == MPSBOUNDS) /* || (section == MPSSOS) */)\n            *field2 = 0;\n          else {\n            strcpy(field2, field1);\n            *field1 = 0;\n          }\n          items++;\n        }\n        else\n          ptr1 = NULL;\n      }\n      else\n        ptr1 = NULL;\n    }\n  }\n  else {\n    ptr1 = NULL;\n    if((section == MPSBOUNDS) &&\n       ((strcmp(field1, \"FR\") == 0) || (strcmp(field1, \"MI\") == 0) || (strcmp(field1, \"PL\") == 0) || (strcmp(field1, \"BV\") == 0))) {\n      strcpy(field3, field2);\n      *field2 = 0;\n      items++;\n    }\n  }\n\n  if(ptr1 == NULL) {\n    len = lenfield(line, line_len);\n    if(line_len >= 1) { /* number */\n      strncpy(buf, line, len);\n      buf[len] = '\\0';\n      for(ptr1 = ptr2 = buf; ; ptr1++)\n        if(!isspace((unsigned char) *ptr1))\n          if((*(ptr2++) = *ptr1) == 0)\n            break;\n      /* *field4 = atof(buf); */\n      *field4 = strtod(buf, &ptr1);\n      if(*ptr1)\n        return(-1);\n      items++;\n    }\n    else\n      *field4 = 0;\n\n    line += len;\n    line_len -= len;\n\n    len = spaces(line, line_len);\n    line += len;\n    line_len -= len;\n  }\n\n  len = lenfield(line, line_len);\n  if(line_len >= 1) { /* name */\n    strncpy(field5, line, len);\n    field5[len] = '\\0';\n    items++;\n  }\n  else\n    field5[0] = '\\0';\n  line += len;\n  line_len -= len;\n\n  len = spaces(line, line_len);\n  line += len;\n  line_len -= len;\n\n  len = lenfield(line, line_len);\n  if(line_len >= 1) { /* number */\n    strncpy(buf, line, len);\n    buf[len] = '\\0';\n    for(ptr1 = ptr2 = buf; ; ptr1++)\n      if(!isspace((unsigned char) *ptr1))\n        if((*(ptr2++) = *ptr1) == 0)\n          break;\n    /* *field6 = atof(buf); */\n    *field6 = strtod(buf, &ptr1);\n    if(*ptr1)\n      return(-1);\n    items++;\n  }\n  else\n    *field6 = 0;\n\n  if((section == MPSSOS) && (items == 2)) {\n    strcpy(field3, field2);\n    strcpy(field2, field1);\n    *field1 = 0;\n  }\n\n  if((section != MPSOBJNAME) && (section != MPSBOUNDS)) {\n    for(ptr1 = field1; *ptr1; ptr1++)\n      *ptr1=(char)toupper(*ptr1);\n  }\n\n  return(items);\n}\n\nSTATIC int addmpscolumn(lprec *lp, MYBOOL Int_section, int typeMPS, MYBOOL *Column_ready,\n                        int *count, REAL *Last_column, int *Last_columnno, char *Last_col_name)\n{\n  int ok = TRUE;\n\n  if (*Column_ready) {\n    ok = add_columnex(lp, *count, Last_column, Last_columnno);\n    if (ok) {\n      ok = set_col_name(lp, lp->columns, Last_col_name);\n    }\n    if (ok) {\n      set_int(lp, lp->columns, Int_section);\n      if ((Int_section) && (typeMPS & MPSIBM))\n        set_bounds(lp, lp->columns, 10.0 / DEF_INFINITE, DEF_INFINITE / 10.0);\n    }\n  }\n  *Column_ready = FALSE;\n  *count = 0;\n  return(ok);\n}\n\n#if 0\nSTATIC MYBOOL appendmpsitem(int *count, int rowIndex[], REAL rowValue[])\n{\n  int i = *count;\n\n  if(rowValue[i] == 0)\n    return( FALSE );\n\n  while((i > 0) && (rowIndex[i] < rowIndex[i-1])) {\n    swapINT (rowIndex+i, rowIndex+i-1);\n    swapREAL(rowValue+i, rowValue+i-1);\n    i--;\n  }\n  (*count)++;\n  return( TRUE );\n}\n#endif\n\nSTATIC MYBOOL appendmpsitem(int *count, int rowIndex[], REAL rowValue[])\n{\n  int i = *count;\n\n  /* Check for non-negativity of the index */\n  if(rowIndex[i] < 0)\n    return( FALSE );\n\n  /* Move the element so that the index list is sorted ascending */\n  while((i > 0) && (rowIndex[i] < rowIndex[i-1])) {\n    swapINT (rowIndex+i, rowIndex+i-1);\n    swapREAL(rowValue+i, rowValue+i-1);\n    i--;\n  }\n\n  /* Add same-indexed items (which is rarely encountered), and shorten the list */\n  if((i < *count) && (rowIndex[i] == rowIndex[i+1])) {\n    int ii = i + 1;\n    rowValue[i] += rowValue[ii];\n    (*count)--;\n    while(ii < *count) {\n      rowIndex[ii] = rowIndex[ii+1];\n      rowValue[ii] = rowValue[ii+1];\n      ii++;\n    }\n  }\n\n  /* Update the count and return */\n  (*count)++;\n  return( TRUE );\n}\n\nMYBOOL MPS_readfile(lprec **newlp, char *filename, int typeMPS, int verbose)\n{\n  MYBOOL status = FALSE;\n  FILE   *fpin;\n\n  fpin = fopen(filename, \"r\");\n  if(fpin != NULL) {\n    status = MPS_readhandle(newlp, fpin, typeMPS, verbose);\n    fclose(fpin);\n  }\n  return( status );\n}\n\nstatic int __WINAPI MPS_input(void *fpin, char *buf, int max_size)\n{\n  return(fgets(buf, max_size, (FILE *) fpin) != NULL);\n}\n\nMYBOOL __WINAPI MPS_readhandle(lprec **newlp, FILE *filehandle, int typeMPS, int verbose)\n{\n  return(MPS_readex(newlp, (void *) filehandle, MPS_input, typeMPS, verbose));\n}\n\nMYBOOL __WINAPI MPS_readex(lprec **newlp, void *userhandle, read_modeldata_func read_modeldata, int typeMPS, int verbose)\n{\n  char   field1[BUFSIZ], field2[BUFSIZ], field3[BUFSIZ], field5[BUFSIZ], line[BUFSIZ], tmp[BUFSIZ],\n         Last_col_name[BUFSIZ], probname[BUFSIZ], OBJNAME[BUFSIZ], *ptr;\n  int    items, row, Lineno, var,\n         section = MPSUNDEF, variant = 0, NZ = 0, SOS = 0;\n  MYBOOL Int_section, Column_ready, Column_ready1,\n         Unconstrained_rows_found = FALSE, OF_found = FALSE, CompleteStatus = FALSE;\n  double field4, field6;\n  REAL   *Last_column = NULL;\n  int    count = 0, *Last_columnno = NULL;\n  int    OBJSENSE = ROWTYPE_EMPTY;\n  lprec  *lp;\n  int    (*scan_line)(lprec *lp, int section, char* line, char *field1, char *field2, char *field3,\n                      double *field4, char *field5, double *field6);\n\n  if(newlp == NULL)\n    return( CompleteStatus );\n  else if(*newlp == NULL)\n    lp = make_lp(0, 0);\n  else\n    lp = *newlp;\n\n  if((typeMPS & MPSFIXED) == MPSFIXED)\n    scan_line = scan_lineFIXED;\n  else if((typeMPS & MPSFREE) == MPSFREE)\n    scan_line = scan_lineFREE;\n  else {\n    report(lp, IMPORTANT, \"MPS_readfile: Unrecognized MPS line type.\\n\");\n    if (*newlp == NULL)\n      delete_lp(lp);\n    return( CompleteStatus );\n  }\n\n  if (lp != NULL) {\n    lp->source_is_file = TRUE;\n    lp->verbose = verbose;\n    strcpy(Last_col_name, \"\");\n    strcpy(OBJNAME, \"\");\n    Int_section = FALSE;\n    Column_ready = FALSE;\n    Lineno = 0;\n\n    /* let's initialize line to all zero's */\n    MEMCLEAR(line, BUFSIZ);\n\n    while(read_modeldata(userhandle, line, BUFSIZ - 1)) {\n      Lineno++;\n\n      for(ptr = line; (*ptr) && (isspace((unsigned char) *ptr)); ptr++);\n\n      /* skip lines which start with \"*\", they are comment */\n      if((line[0] == '*') || (*ptr == 0) || (*ptr == '\\n') || (*ptr == '\\r')) {\n        report(lp, FULL, \"Comment on line %d: %s\", Lineno, line);\n        continue;\n      }\n\n      report(lp, FULL, \"Line %6d: %s\", Lineno, line);\n\n      /* first check for \"special\" lines: NAME, ROWS, BOUNDS .... */\n      /* this must start in the first position of line */\n      if(line[0] != ' ') {\n        sscanf(line, \"%s\", tmp);\n        if(strcmp(tmp, \"NAME\") == 0) {\n          section = MPSNAME;\n          *probname = 0;\n          sscanf(line, \"NAME %s\", probname);\n          if (!set_lp_name(lp, probname))\n            break;\n        }\n        else if(((typeMPS & MPSFREE) == MPSFREE) && (strcmp(tmp, \"OBJSENSE\") == 0)) {\n          section = MPSOBJSENSE;\n          report(lp, FULL, \"Switching to OBJSENSE section\\n\");\n        }\n        else if(((typeMPS & MPSFREE) == MPSFREE) && (strcmp(tmp, \"OBJNAME\") == 0)) {\n          section = MPSOBJNAME;\n          report(lp, FULL, \"Switching to OBJNAME section\\n\");\n        }\n        else if(strcmp(tmp, \"ROWS\") == 0) {\n          section = MPSROWS;\n          report(lp, FULL, \"Switching to ROWS section\\n\");\n        }\n        else if(strcmp(tmp, \"COLUMNS\") == 0) {\n          allocREAL(lp, &Last_column, lp->rows + 1, TRUE);\n          allocINT(lp, &Last_columnno, lp->rows + 1, TRUE);\n          count = 0;\n          if ((Last_column == NULL) || (Last_columnno == NULL))\n            break;\n          section = MPSCOLUMNS;\n          report(lp, FULL, \"Switching to COLUMNS section\\n\");\n        }\n        else if(strcmp(tmp, \"RHS\") == 0) {\n          if (!addmpscolumn(lp, Int_section, typeMPS, &Column_ready, &count, Last_column, Last_columnno, Last_col_name))\n            break;\n          section = MPSRHS;\n          report(lp, FULL, \"Switching to RHS section\\n\");\n        }\n        else if(strcmp(tmp, \"BOUNDS\") == 0) {\n          section = MPSBOUNDS;\n          report(lp, FULL, \"Switching to BOUNDS section\\n\");\n        }\n        else if(strcmp(tmp, \"RANGES\") == 0) {\n          section = MPSRANGES;\n          report(lp, FULL, \"Switching to RANGES section\\n\");\n        }\n        else if((strcmp(tmp, \"SOS\") == 0) || (strcmp(tmp, \"SETS\") == 0)) {\n          section = MPSSOS;\n          if(strcmp(tmp, \"SOS\") == 0)\n            variant = 0;\n          else\n            variant = 1;\n          report(lp, FULL, \"Switching to %s section\\n\", tmp);\n        }\n        else if(strcmp(tmp, \"ENDATA\") == 0) {\n          report(lp, FULL, \"Finished reading MPS file\\n\");\n          CompleteStatus = TRUE;\n          break;\n        }\n        else { /* line does not start with space and does not match above */\n          report(lp, IMPORTANT, \"Unrecognized MPS line %d: %s\\n\", Lineno, line);\n          break;\n        }\n      }\n      else { /* normal line, process */\n        items = scan_line(lp, section, line, field1, field2, field3, &field4, field5, &field6);\n        if(items < 0){\n          report(lp, IMPORTANT, \"Syntax error on line %d: %s\\n\", Lineno, line);\n          break;\n        }\n\n        switch(section) {\n\n        case MPSNAME:\n          report(lp, IMPORTANT, \"Error, extra line under NAME line\\n\");\n          break;\n\n        case MPSOBJSENSE:\n          if(OBJSENSE != ROWTYPE_EMPTY) {\n            report(lp, IMPORTANT, \"Error, extra line under OBJSENSE line\\n\");\n            break;\n          }\n          if((strcmp(field1, \"MAXIMIZE\") == 0) || (strcmp(field1, \"MAX\") == 0)) {\n            OBJSENSE = ROWTYPE_OFMAX;\n            set_maxim(lp);\n          }\n          else if((strcmp(field1, \"MINIMIZE\") == 0) || (strcmp(field1, \"MIN\") == 0)) {\n            OBJSENSE = ROWTYPE_OFMIN;\n            set_minim(lp);\n          }\n          else {\n            report(lp, SEVERE, \"Unknown OBJSENSE direction '%s' on line %d\\n\", field1, Lineno);\n            break;\n          }\n          continue;\n\n        case MPSOBJNAME:\n          if(*OBJNAME) {\n            report(lp, IMPORTANT, \"Error, extra line under OBJNAME line\\n\");\n            break;\n          }\n          strcpy(OBJNAME, field1);\n          continue;\n\n        /* Process entries in the ROWS section */\n        case MPSROWS:\n          /* field1: rel. operator; field2: name of constraint */\n\n          report(lp, FULL, \"Row   %5d: %s %s\\n\", lp->rows + 1, field1, field2);\n\n          if(strcmp(field1, \"N\") == 0) {\n            if((*OBJNAME) && (strcmp(field2, OBJNAME)))\n              /* Ignore this objective name since it is not equal to the OBJNAME name */;\n            else if(!OF_found) { /* take the first N row as OF, ignore others */\n              if (!set_row_name(lp, 0, field2))\n                break;\n              OF_found = TRUE;\n            }\n            else if(!Unconstrained_rows_found) {\n              report(lp, IMPORTANT, \"Unconstrained row %s ignored\\n\", field2);\n              report(lp, IMPORTANT, \"Further messages of this kind will be suppressed\\n\");\n              Unconstrained_rows_found = TRUE;\n            }\n          }\n          else if(strcmp(field1, \"L\") == 0) {\n            if ((!str_add_constraint(lp, \"\" ,LE ,0)) || (!set_row_name(lp, lp->rows, field2)))\n              break;\n          }\n          else if(strcmp(field1, \"G\") == 0) {\n            if ((!str_add_constraint(lp, \"\" ,GE ,0)) || (!set_row_name(lp, lp->rows, field2)))\n              break;\n          }\n          else if(strcmp(field1, \"E\") == 0) {\n            if ((!str_add_constraint(lp, \"\",EQ ,0)) || (!set_row_name(lp, lp->rows, field2)))\n              break;\n          }\n          else {\n            report(lp, SEVERE, \"Unknown relation code '%s' on line %d\\n\", field1, Lineno);\n            break;\n          }\n\n          continue;\n\n        /* Process entries in the COLUMNS section */\n        case MPSCOLUMNS:\n          /* field2: variable; field3: constraint; field4: coef */\n          /* optional: field5: constraint; field6: coef */\n\n          report(lp, FULL, \"Column %4d: %s %s %g %s %g\\n\",\n                            lp->columns + 1, field2, field3, field4, field5, field6);\n\n          if((items == 4) || (items == 5) || (items == 6)) {\n            if (NZ == 0)\n              strcpy(Last_col_name, field2);\n            else if(*field2) {\n              Column_ready1 = (MYBOOL) (strcmp(field2, Last_col_name) != 0);\n              if(Column_ready1) {\n                if (find_var(lp, field2, FALSE) >= 0) {\n                  report(lp, SEVERE, \"Variable name (%s) is already used!\\n\", field2);\n                  break;\n                }\n\n                if(Column_ready) {  /* Added ability to handle non-standard \"same as above\" column name */\n                  if (addmpscolumn(lp, Int_section, typeMPS, &Column_ready, &count, Last_column, Last_columnno, Last_col_name)) {\n                    strcpy(Last_col_name, field2);\n                    NZ = 0;\n                  }\n                  else\n                    break;\n                }\n              }\n            }\n            if(items == 5) { /* there might be an INTEND or INTORG marker */\n             /* look for \"    <name>  'MARKER'                 'INTORG'\"\n                      or \"    <name>  'MARKER'                 'INTEND'\"  */\n              if(strcmp(field3, \"'MARKER'\") != 0)\n                break;\n              if(strcmp(field5, \"'INTORG'\") == 0) {\n                Int_section = TRUE;\n                report(lp, FULL, \"Switching to integer section\\n\");\n              }\n              else if(strcmp(field5, \"'INTEND'\") == 0) {\n                Int_section = FALSE;\n                report(lp, FULL, \"Switching to non-integer section\\n\");\n              }\n              else\n                report(lp, IMPORTANT, \"Unknown marker (ignored) at line %d: %s\\n\",\n                                       Lineno, field5);\n            }\n            else if((row = find_row(lp, field3, Unconstrained_rows_found)) >= 0) {\n              if(row > lp->rows)\n                report(lp, CRITICAL, \"Invalid row %s encountered in the MPS file\\n\", field3);\n              Last_columnno[count] = row;\n              Last_column[count] = (REAL)field4;\n              if(appendmpsitem(&count, Last_columnno, Last_column)) {\n                NZ++;\n                Column_ready = TRUE;\n              }\n            }\n          }\n          if(items == 6) {\n            if((row = find_row(lp, field5, Unconstrained_rows_found)) >= 0) {\n              if(row > lp->rows)\n                report(lp, CRITICAL, \"Invalid row %s encountered in the MPS file\\n\", field5);\n              Last_columnno[count] = row;\n              Last_column[count] = (REAL)field6;\n              if(appendmpsitem(&count, Last_columnno, Last_column)) {\n                NZ++;\n                Column_ready = TRUE;\n              }\n            }\n          }\n\n          if((items < 4) || (items > 6)) { /* Wrong! */\n            report(lp, CRITICAL, \"Wrong number of items (%d) in COLUMNS section (line %d)\\n\",\n                                  items, Lineno);\n            break;\n          }\n\n          continue;\n\n        /* Process entries in the RHS section */\n        /* field2: uninteresting name; field3: constraint name */\n        /* field4: value */\n        /* optional: field5: constraint name; field6: value */\n        case MPSRHS:\n\n          report(lp, FULL, \"RHS line: %s %s %g %s %g\\n\",\n                            field2, field3, field4, field5, field6);\n\n          if((items != 4) && (items != 6)) {\n            report(lp, CRITICAL, \"Wrong number of items (%d) in RHS section line %d\\n\",\n                                  items, Lineno);\n            break;\n          }\n\n          if((row = find_row(lp, field3, Unconstrained_rows_found)) >= 0) {\n            if ((row == 0) && ((typeMPS & MPSNEGOBJCONST) == MPSNEGOBJCONST))\n              field4 = -field4;\n            set_rh(lp, row, (REAL)field4);\n          }\n\n          if(items == 6) {\n            if((row = find_row(lp, field5, Unconstrained_rows_found)) >= 0) {\n              if ((row == 0) && ((typeMPS & MPSNEGOBJCONST) == MPSNEGOBJCONST))\n                field6 = -field6;\n              set_rh(lp, row, (REAL)field6);\n            }\n          }\n\n          continue;\n\n        /* Process entries in the BOUNDS section */\n        /* field1: bound type; field2: uninteresting name; */\n        /* field3: variable name; field4: value */\n        case MPSBOUNDS:\n\n          report(lp, FULL, \"BOUNDS line: %s %s %s %g\\n\",\n                            field1, field2, field3, field4);\n\n          var = find_var(lp, field3, FALSE);\n          if(var < 0){ /* bound on undefined var in COLUMNS section ... */\n            Column_ready = TRUE;\n            if (!addmpscolumn(lp, FALSE, typeMPS, &Column_ready, &count, Last_column, Last_columnno, field3))\n              break;\n            Column_ready = TRUE;\n            var = find_var(lp, field3, TRUE);\n          }\n          if(var < 0) /* undefined var and could add ... */;\n          else if(strcmp(field1, \"UP\") == 0) {\n          /* upper bound */\n            /* if(!set_bounds(lp, var, get_lowbo(lp, var), field4)) */\n            if(!set_upbo(lp, var, field4))\n              break;\n          }\n          else if(strcmp(field1, \"SC\") == 0) {\n            /* upper bound */\n            if(field4 == 0)\n              field4 = lp->infinite;\n            /* if(!set_bounds(lp, var, get_lowbo(lp, var), field4)) */\n            if(!set_upbo(lp, var, field4))\n              break;\n            set_semicont(lp, var, TRUE);\n          }\n          else if(strcmp(field1, \"SI\") == 0) {\n            /* upper bound */\n            if(field4 == 0)\n              field4 = lp->infinite;\n            /* if(!set_bounds(lp, var, get_lowbo(lp, var), field4)) */\n            if(!set_upbo(lp, var, field4))\n              break;\n            set_int(lp, var, TRUE);\n            set_semicont(lp, var, TRUE);\n          }\n          else if(strcmp(field1, \"LO\") == 0) {\n            /* lower bound */\n            /* if(!set_bounds(lp, var, field4, get_upbo(lp, var))) */\n            if(!set_lowbo(lp, var, field4))\n              break;\n          }\n          else if(strcmp(field1, \"PL\") == 0) { /* plus-ranged variable */\n            /* if(!set_bounds(lp, var, get_lowbo(lp, var), lp->infinite)) */\n            if(!set_upbo(lp, var, lp->infinite))\n              break;\n          }\n          else if(strcmp(field1, \"MI\") == 0) { /* minus-ranged variable */\n            /* if(!set_bounds(lp, var, -lp->infinite, get_upbo(lp, var))) */\n            if(!set_lowbo(lp, var, -lp->infinite))\n              break;\n          }\n          else if(strcmp(field1, \"FR\") == 0) { /* free variable */\n            set_unbounded(lp, var);\n          }\n          else if(strcmp(field1, \"FX\") == 0) {\n            /* fixed, upper _and_ lower  */\n            if(!set_bounds(lp, var, field4, field4))\n              break;\n          }\n          else if(strcmp(field1, \"BV\") == 0) { /* binary variable */\n            set_binary(lp, var, TRUE);\n          }\n          /* AMPL bounds type UI and LI added by E.Imamura (CRIEPI)  */\n          else if(strcmp(field1, \"UI\") == 0) { /* upper bound for integer variable */\n            /* if(!set_bounds(lp, var, get_lowbo(lp, var), field4)) */\n            if(!set_upbo(lp, var, field4))\n              break;\n            set_int(lp, var, TRUE);\n          }\n          else if(strcmp(field1, \"LI\") == 0) { /* lower bound for integer variable - corrected by KE */\n            /* if(!set_bounds(lp, var, field4, get_upbo(lp, var))) */\n            if(!set_lowbo(lp, var, field4))\n              break;\n            set_int(lp, var, TRUE);\n          }\n          else {\n            report(lp, CRITICAL, \"BOUND type %s on line %d is not supported\",\n                                  field1, Lineno);\n            break;\n          }\n\n          continue;\n\n          /* Process entries in the BOUNDS section */\n\n      /* We have to implement the following semantics:\n\n      D. The RANGES section is for constraints of the form: h <=\n      constraint <= u .  The range of the constraint is r = u - h .  The\n      value of r is specified in the RANGES section, and the value of u or\n      h is specified in the RHS section.  If b is the value entered in the\n      RHS section, and r is the value entered in the RANGES section, then\n      u and h are thus defined:\n\n      row type       sign of r       h          u\n      ----------------------------------------------\n     G            + or -         b        b + |r|\n     L            + or -       b - |r|      b\n     E              +            b        b + |r|\n     E              -          b - |r|      b            */\n\n        /* field2: uninteresting name; field3: constraint name */\n        /* field4: value */\n        /* optional: field5: constraint name; field6: value */\n\n        case MPSRANGES:\n\n          report(lp, FULL, \"RANGES line: %s %s %g %s %g\",\n                            field2, field3, field4, field5, field6);\n\n          if((items != 4) && (items != 6)) {\n            report(lp, CRITICAL, \"Wrong number of items (%d) in RANGES section line %d\",\n                                  items, Lineno);\n            break;\n          }\n\n          if((row = find_row(lp, field3, Unconstrained_rows_found)) >= 0) {\n            /* Determine constraint type */\n\n            if(fabs(field4) >= lp->infinite) {\n              report(lp, IMPORTANT,\n                          \"Warning, Range for row %s >= infinity (value %g) on line %d, ignored\",\n                          field3, field4, Lineno);\n            }\n            else if(field4 == 0) {\n              /* Change of a GE or LE to EQ */\n              if(lp->orig_upbo[row] != 0)\n                set_constr_type(lp, row, EQ);\n            }\n            else if(is_chsign(lp, row)) {\n              /* GE */\n              lp->orig_upbo[row] = fabs(field4);\n            }\n            else if((lp->orig_upbo[row] == 0) && (field4 >= 0)) {\n              /*  EQ with positive sign of r value */\n              set_constr_type(lp, row, GE);\n              lp->orig_upbo[row] = field4;\n            }\n            else if(lp->orig_upbo[row] == lp->infinite) {\n              /* LE */\n              lp->orig_upbo[row] = fabs(field4);\n            }\n            else if((lp->orig_upbo[row] == 0) && (field4 < 0)) {\n              /* EQ with negative sign of r value */\n              set_constr_type(lp, row, LE);\n              lp->orig_upbo[row] = my_flipsign(field4);\n            }\n            else { /* let's be paranoid */\n              report(lp, IMPORTANT,\n                          \"Cannot figure out row type, row = %d, is_chsign = %d, upbo = %g on line %d\",\n                          row, is_chsign(lp, row), (double)lp->orig_upbo[row], Lineno);\n            }\n          }\n\n          if(items == 6) {\n            if((row = find_row(lp, field5, Unconstrained_rows_found)) >= 0) {\n              /* Determine constraint type */\n\n              if(fabs(field6) >= lp->infinite) {\n                report(lp, IMPORTANT,\n                            \"Warning, Range for row %s >= infinity (value %g) on line %d, ignored\",\n                            field5, field6, Lineno);\n              }\n              else if(field6 == 0) {\n                /* Change of a GE or LE to EQ */\n                if(lp->orig_upbo[row] != 0)\n                  set_constr_type(lp, row, EQ);\n              }\n              else if(is_chsign(lp, row)) {\n                /* GE */\n                lp->orig_upbo[row] = fabs(field6);\n              }\n              else if(lp->orig_upbo[row] == 0 && field6 >= 0) {\n                /*  EQ with positive sign of r value */\n                set_constr_type(lp, row, GE);\n                lp->orig_upbo[row] = field6;\n              }\n              else if(lp->orig_upbo[row] == lp->infinite) {\n                /* LE */\n                lp->orig_upbo[row] = fabs(field6);\n              }\n              else if((lp->orig_upbo[row] == 0) && (field6 < 0)) {\n                /* EQ with negative sign of r value */\n                set_constr_type(lp, row, LE);\n                lp->orig_upbo[row] = my_flipsign(field6);\n              }\n              else { /* let's be paranoid */\n                report(lp, IMPORTANT,\n                            \"Cannot figure out row type, row = %d, is_chsign = %d, upbo = %g on line %d\",\n                            row, is_chsign(lp,row), (double) lp->orig_upbo[row], Lineno);\n              }\n            }\n          }\n\n          continue;\n\n        /* Process entries in the SOS section */\n\n        /* We have to implement the following semantics:\n\n          E. The SOS section is for ordered variable sets of the form:\n      x1, x2, x3 ... xn where only a given number of consequtive variables\n          may be non-zero.  Each set definition is prefaced by type, name\n      and priority data.  Each set member has an optional weight that\n      determines its order.  There are two forms supported; a full format\n      and a reduced CPLEX-like format.                                       */\n\n        case MPSSOS:\n          report(lp, FULL, \"SOS line: %s %s %g %s %g\",\n                             field2, field3, field4, field5, field6);\n\n          if((items == 0) || (items > 4)) {\n            report(lp, IMPORTANT,\n                   \"Invalid number of items (%d) in SOS section line %d\\n\",\n                   items, Lineno);\n            break;\n          }\n\n          if(strlen(field1) == 0) items--;  /* fix scanline anomoly! */\n\n          /* Check if this is the start of a new SOS */\n          if(items == 1 || items == 4) {\n            row = (int) (field1[1] - '0');\n            if((row <= 0) || (row > 9)) {\n              report(lp, IMPORTANT,\n                     \"Error: Invalid SOS type %s line %d\\n\", field1, Lineno);\n              break;\n            }\n            field1[0] = '\\0';               /* fix scanline anomoly! */\n\n            /* lp_solve needs a name for the SOS */\n            if(variant == 0) {\n              if(strlen(field3) == 0)  /* CPLEX format does not provide a SOS name; create one */\n                sprintf(field3, \"SOS_%d\", SOS_count(lp) + 1);\n            }\n            else {                     /* Remap XPRESS format name */\n              strcpy(field3, field1);\n            }\n            /* Obtain the SOS priority */\n            if(items == 4)\n              SOS = (int) field4;\n            else\n              SOS = 1;\n\n            /* Define a new SOS instance */\n\n            SOS = add_SOS(lp, field3, (int) row, SOS, 0, NULL, NULL);\n          }\n          /* Otherwise, add set members to the active SOS */\n          else {\n            char *field = (items == 3) ? field3 /* Native lp_solve and XPRESS formats */ : field2 /* CPLEX format */;\n\n            var = find_var(lp, field, FALSE);  /* Native lp_solve and XPRESS formats */\n            if(var < 0){ /* SOS on undefined var in COLUMNS section ... */\n              Column_ready = TRUE;\n              if (!addmpscolumn(lp, FALSE, typeMPS, &Column_ready, &count, Last_column, Last_columnno, field))\n                break;\n              Column_ready = TRUE;\n              var = find_var(lp, field, TRUE);\n            }\n            if((var < 0) || (SOS < 1)) /* undefined var and could add ... */;\n            else append_SOSrec(lp->SOS->sos_list[SOS-1], 1, &var, &field4);\n          }\n\n          continue;\n        }\n\n        /* If we got here there was an error \"upstream\" */\n         report(lp, IMPORTANT,\n                     \"Error: Cannot handle line %d\\n\", Lineno);\n         break;\n      }\n    }\n\n    if((*OBJNAME) && (!OF_found)) {\n      report(lp, IMPORTANT,\n                  \"Error: Objective function specified by OBJNAME card not found\\n\");\n      CompleteStatus = FALSE;\n    }\n\n    if(CompleteStatus == FALSE) {\n      if (*newlp == NULL)\n        delete_lp(lp);\n    }\n    else {\n      if (typeMPS & MPSIBM) {\n        REAL lower, upper;\n\n        for (var = 1; var <= lp->columns; var++)\n          if (is_int(lp, var)) {\n            lower = get_lowbo(lp, var);\n            upper = get_upbo(lp, var);\n            if ((lower == 10.0 / DEF_INFINITE) && (upper == DEF_INFINITE / 10.0))\n              upper = 1.0;\n            if (lower == 10.0 / DEF_INFINITE)\n              lower = 0.0;\n            if (upper == DEF_INFINITE / 10.0)\n              upper = lp->infinite;\n            set_bounds(lp, var, lower, upper);\n          }\n      }\n      *newlp = lp;\n    }\n    if(Last_column != NULL)\n      FREE(Last_column);\n    if(Last_columnno != NULL)\n      FREE(Last_columnno);\n  }\n\n  return( CompleteStatus );\n}\n\nstatic void number(char *str,REAL value)\n {\n  char __str[80], *_str;\n  int  i;\n\n  /* sprintf(_str,\"%12.6G\",value); */\n  _str=__str+2;\n  if (value>=0.0)\n   if ((value!=0.0) && ((value>0.99999999e12) || (value<0.0001))) {\n    int n=15;\n\n    do {\n     n--;\n     i=sprintf(_str,\"%*.*E\",n,n-6,(double) value);\n     if (i>12) {\n      char *ptr=strchr(_str,'E');\n\n      if (ptr!=NULL) {\n       if (*(++ptr)=='-') ptr++;\n       while ((i>12) && ((*ptr=='+') || (*ptr=='0'))) {\n        strcpy(ptr,ptr+1);\n        i--;\n       }\n      }\n     }\n    } while (i>12);\n   }\n   else if (value>=1.0e10) {\n    int n=13;\n\n    do {\n     i=sprintf(_str,\"%*.0f\",--n,(double) value);\n    } while (i>12);\n   }\n   else {\n    if (((i=sprintf(_str,\"%12.10f\",(double) value))>12) && (_str[12]>='5')) {\n     for (i=11;i>=0;i--)\n      if (_str[i]!='.') {\n       if (++_str[i]>'9') _str[i]='0';\n       else break;\n      }\n     if (i<0) {\n      *(--_str)='1';\n      *(--_str)=' ';\n     }\n    }\n   }\n  else\n   if ((value<-0.99999999e11) || (value>-0.0001)) {\n    int n=15;\n\n    do {\n     n--;\n     i=sprintf(_str,\"%*.*E\",n,n-7,(double) value);\n     if (i>12) {\n      char *ptr=strchr(_str,'E');\n\n      if (ptr!=NULL) {\n       if (*(++ptr)=='-') ptr++;\n       while ((i>12) && ((*ptr=='+') || (*ptr=='0'))) {\n        strcpy(ptr,ptr+1);\n        i--;\n       }\n      }\n     }\n    } while (i>12);\n   }\n   else if (value<=-1.0e9) {\n    int n=13;\n\n    do {\n     i=sprintf(_str,\"%*.0f\",--n,(double) value);\n    } while (i>12);\n   }\n   else\n    if (((i=sprintf(_str,\"%12.9f\",(double) value))>12) && (_str[12]>='5')) {\n     for (i=11;i>=1;i--)\n      if (_str[i]!='.') {\n       if (++_str[i]>'9') _str[i]='0';\n       else break;\n      }\n     if (i<1) {\n      *_str='1';\n      *(--_str)='-';\n      *(--_str)=' ';\n     }\n    }\n  strncpy(str,_str,12);\n }\n\nstatic char *formatnumber12(char *numberbuffer, double a)\n{\n#if 0\n  return(sprintf(numberbuffer, \"%12g\", a));\n#else\n  number(numberbuffer, a);\n  return(numberbuffer);\n#endif\n}\n\nSTATIC char *MPSnameFIXED(char *name0, char *name)\n{\n  sprintf(name0, \"%-8.8s\", name);\n  return(name0);\n}\n\nSTATIC char *MPSnameFREE(char *name0, char *name)\n{\n  if(strlen(name) < 8)\n    return(MPSnameFIXED(name0, name));\n  else\n    return(name);\n}\n\nstatic void write_data(void *userhandle, write_modeldata_func write_modeldata, char *format, ...)\n{\n  char buff[DEF_STRBUFSIZE+1];\n  va_list ap;\n\n  va_start(ap, format);\n  vsnprintf(buff, DEF_STRBUFSIZE, format, ap);\n  va_end(ap);\n  write_modeldata(userhandle, buff);\n}\n\nMYBOOL __WINAPI MPS_writefileex(lprec *lp, int typeMPS, void *userhandle, write_modeldata_func write_modeldata)\n{\n  int    i, j, jj, je, k, marker, putheader, ChangeSignObj = FALSE, *idx, *idx1;\n  MYBOOL ok = TRUE, names_used;\n  REAL   a, *val, *val1;\n  char * (*MPSname)(char *name0, char *name);\n  char numberbuffer[15];\n  char name0[9];\n\n  if((typeMPS & MPSFIXED) == MPSFIXED) {\n    MPSname = MPSnameFIXED;\n    ChangeSignObj = is_maxim(lp);\n  }\n  else if((typeMPS & MPSFREE) == MPSFREE) {\n    MPSname = MPSnameFREE;\n  }\n  else {\n    report(lp, IMPORTANT, \"MPS_writefile: unrecognized MPS name type.\\n\");\n    return(FALSE);\n  }\n\n  names_used = lp->names_used;\n\n  if((typeMPS & MPSFIXED) == MPSFIXED) {\n    /* Check if there is no variable name where the first 8 charachters are equal to the first 8 characters of anothe variable */\n    if(names_used)\n      for(i = 1; (i <= lp->columns) && (ok); i++)\n        if((lp->col_name[i] != NULL) && (lp->col_name[i]->name != NULL) && (!is_splitvar(lp, i)) && (strlen(lp->col_name[i]->name) > 8))\n          for(j = 1; (j < i) && (ok); j++)\n    if((lp->col_name[j] != NULL) && (lp->col_name[j]->name != NULL) && (!is_splitvar(lp, j)))\n      if(strncmp(lp->col_name[i]->name, lp->col_name[j]->name, 8) == 0)\n        ok = FALSE;\n  }\n\n  if(!ok) {\n    lp->names_used = FALSE;\n    ok = TRUE;\n  }\n\n  memset(numberbuffer, 0, sizeof(numberbuffer));\n\n  marker = 0;\n\n  /* First write metadata in structured comment form (lp_solve style) */\n  write_data(userhandle, write_modeldata, \"*<meta creator='lp_solve v%d.%d'>\\n\",\n                  (int) MAJORVERSION, (int) MINORVERSION);\n  write_data(userhandle, write_modeldata, \"*<meta rows=%d>\\n\", lp->rows);\n  write_data(userhandle, write_modeldata, \"*<meta columns=%d>\\n\", lp->columns);\n  write_data(userhandle, write_modeldata, \"*<meta equalities=%d>\\n\", lp->equalities);\n  if(SOS_count(lp) > 0)\n    write_data(userhandle, write_modeldata, \"*<meta SOS=%d>\\n\", SOS_count(lp));\n  write_data(userhandle, write_modeldata, \"*<meta integers=%d>\\n\", lp->int_vars);\n  if(lp->sc_vars > 0)\n    write_data(userhandle, write_modeldata, \"*<meta scvars=%d>\\n\", lp->sc_vars);\n  write_data(userhandle, write_modeldata, \"*<meta origsense='%s'>\\n\", (is_maxim(lp) ? \"MAX\" : \"MIN\"));\n  write_data(userhandle, write_modeldata, \"*\\n\");\n\n  /* Write the MPS content */\n  write_data(userhandle, write_modeldata, \"NAME          %s\\n\", MPSname(name0, get_lp_name(lp)));\n  if(((typeMPS & MPSFREE) == MPSFREE) && (is_maxim(lp)))\n    write_data(userhandle, write_modeldata, \"OBJSENSE\\n MAX\\n\");\n  write_data(userhandle, write_modeldata, \"ROWS\\n\");\n  for(i = 0; i <= lp->rows; i++) {\n    if(i == 0)\n      write_data(userhandle, write_modeldata, \" N  \");\n    else if(lp->orig_upbo[i] != 0) {\n      if(is_chsign(lp,i))\n        write_data(userhandle, write_modeldata, \" G  \");\n      else\n        write_data(userhandle, write_modeldata, \" L  \");\n    }\n    else\n      write_data(userhandle, write_modeldata, \" E  \");\n    write_data(userhandle, write_modeldata, \"%s\\n\", MPSname(name0, get_row_name(lp, i)));\n  }\n\n  allocREAL(lp, &val, 1 + lp->rows, TRUE);\n  allocINT(lp, &idx, 1 + lp->rows, TRUE);\n  write_data(userhandle, write_modeldata, \"COLUMNS\\n\");\n  for(i = 1; i <= lp->columns; i++) {\n    if(!is_splitvar(lp, i)) {\n      if(is_int(lp,i) && (marker % 2) == 0) {\n        write_data(userhandle, write_modeldata, \"    MARK%04d  'MARKER'                 'INTORG'\\n\",\n                marker);\n        marker++;\n      }\n      if(!is_int(lp,i) && (marker % 2) == 1) {\n        write_data(userhandle, write_modeldata, \"    MARK%04d  'MARKER'                 'INTEND'\\n\",\n                marker);\n        marker++;\n      }\n\n      /* Loop over non-zero column entries */\n      je = get_columnex(lp, i, val, idx);\n      for(k = 1, val1 = val, idx1 = idx, jj = 0; jj < je; jj++) {\n        k = 1 - k;\n        j = *(idx1++);\n        a = *(val1++);\n        if (k == 0) {\n          write_data(userhandle, write_modeldata, \"    %s\",\n                          MPSname(name0, get_col_name(lp, i)));\n          write_data(userhandle, write_modeldata, \"  %s  %s\",\n                          MPSname(name0, get_row_name(lp, j)),\n/*                          formatnumber12(numberbuffer, (double) a)); */\n                          formatnumber12(numberbuffer, (double) (a * (j == 0 && ChangeSignObj ? -1 : 1))));\n    }\n        else\n          write_data(userhandle, write_modeldata, \"   %s  %s\\n\",\n                          MPSname(name0, get_row_name(lp, j)),\n                          formatnumber12(numberbuffer, (double) (a * (j == 0 && ChangeSignObj ? -1 : 1))));\n/*                          formatnumber12(numberbuffer, (double) a)); */\n      }\n      if(k == 0)\n        write_data(userhandle, write_modeldata, \"\\n\");\n    }\n  }\n  if((marker % 2) == 1) {\n    write_data(userhandle, write_modeldata, \"    MARK%04d  'MARKER'                 'INTEND'\\n\",\n            marker);\n  /* marker++; */ /* marker not used after this */\n  }\n  FREE(idx);\n  FREE(val);\n\n  write_data(userhandle, write_modeldata, \"RHS\\n\");\n  for(k = 1, i = 0; i <= lp->rows; i++) {\n    a = lp->orig_rhs[i];\n    if(a) {\n      a = unscaled_value(lp, a, i);\n      if ((i == 0) && ((typeMPS & MPSNEGOBJCONST) == MPSNEGOBJCONST))\n        a = -a;\n      if((i == 0) || is_chsign(lp, i))\n        a = my_flipsign(a);\n      k = 1 - k;\n      if(k == 0)\n        write_data(userhandle, write_modeldata, \"    RHS       %s  %s\",\n                        MPSname(name0, get_row_name(lp, i)),\n                        formatnumber12(numberbuffer, (double)a));\n      else\n        write_data(userhandle, write_modeldata, \"   %s  %s\\n\",\n                        MPSname(name0, get_row_name(lp, i)),\n                        formatnumber12(numberbuffer, (double)a));\n    }\n  }\n  if(k == 0)\n    write_data(userhandle, write_modeldata, \"\\n\");\n\n  putheader = TRUE;\n  for(k = 1, i = 1; i <= lp->rows; i++){\n    a = 0;\n    if((lp->orig_upbo[i] < lp->infinite) && (lp->orig_upbo[i] != 0.0))\n      a = lp->orig_upbo[i];\n    if(a) {\n      if(putheader) {\n        write_data(userhandle, write_modeldata, \"RANGES\\n\");\n        putheader = FALSE;\n      }\n      a = unscaled_value(lp, a, i);\n      k = 1 - k;\n      if(k == 0)\n        write_data(userhandle, write_modeldata, \"    RGS       %s  %s\",\n                        MPSname(name0, get_row_name(lp, i)),\n                        formatnumber12(numberbuffer, (double)a));\n      else\n        write_data(userhandle, write_modeldata, \"   %s  %s\\n\",\n                        MPSname(name0, get_row_name(lp, i)),\n                        formatnumber12(numberbuffer, (double)a));\n    }\n  }\n  if(k == 0)\n    write_data(userhandle, write_modeldata, \"\\n\");\n\n  putheader = TRUE;\n  for(i = lp->rows + 1; i <= lp->sum; i++)\n    if(!is_splitvar(lp, i - lp->rows)) {\n      j = i - lp->rows;\n      if((lp->orig_lowbo[i] != 0) && (lp->orig_upbo[i] < lp->infinite) &&\n         (lp->orig_lowbo[i] == lp->orig_upbo[i])) {\n        a = lp->orig_upbo[i];\n        a = unscaled_value(lp, a, i);\n        if(putheader) {\n          write_data(userhandle, write_modeldata, \"BOUNDS\\n\");\n          putheader = FALSE;\n        }\n        write_data(userhandle, write_modeldata, \" FX BND       %s  %s\\n\",\n                        MPSname(name0, get_col_name(lp, j)),\n                        formatnumber12(numberbuffer, (double)a));\n      }\n      else if(is_binary(lp, j)) {\n        if(putheader) {\n          write_data(userhandle, write_modeldata, \"BOUNDS\\n\");\n          putheader = FALSE;\n        }\n        write_data(userhandle, write_modeldata, \" BV BND       %s\\n\",\n                        MPSname(name0, get_col_name(lp, j)));\n      }\n      else if(is_unbounded(lp, j)) {\n        if(putheader) {\n          write_data(userhandle, write_modeldata, \"BOUNDS\\n\");\n          putheader = FALSE;\n        }\n        write_data(userhandle, write_modeldata, \" FR BND       %s\\n\",\n                        MPSname(name0, get_col_name(lp, j)));\n      }\n      else {\n        if((lp->orig_lowbo[i] != 0) || (is_int(lp, j))) { /* Some solvers like CPLEX need to have a bound on a variable if it is integer, but not binary else it is interpreted as binary which is not ment */\n          a = lp->orig_lowbo[i];\n          a = unscaled_value(lp, a, i);\n          if(putheader) {\n            write_data(userhandle, write_modeldata, \"BOUNDS\\n\");\n            putheader = FALSE;\n          }\n          if(lp->orig_lowbo[i] != -lp->infinite)\n            write_data(userhandle, write_modeldata, \" LO BND       %s  %s\\n\",\n                            MPSname(name0, get_col_name(lp, j)),\n                            formatnumber12(numberbuffer, (double)a));\n          else\n            write_data(userhandle, write_modeldata, \" MI BND       %s\\n\",\n                            MPSname(name0, get_col_name(lp, j)));\n        }\n\n        if((lp->orig_upbo[i] < lp->infinite) || (is_semicont(lp, j))) {\n          a = lp->orig_upbo[i];\n          if(a < lp->infinite)\n            a = unscaled_value(lp, a, i);\n          if(putheader) {\n            write_data(userhandle, write_modeldata, \"BOUNDS\\n\");\n            putheader = FALSE;\n          }\n          if(is_semicont(lp, j)) {\n            if(is_int(lp, j))\n              write_data(userhandle, write_modeldata, \" SI BND       %s  %s\\n\",\n                              MPSname(name0, get_col_name(lp, j)),\n                  (a < lp->infinite) ? formatnumber12(numberbuffer, (double)a) : \"            \");\n            else\n              write_data(userhandle, write_modeldata, \" SC BND       %s  %s\\n\",\n                              MPSname(name0, get_col_name(lp, j)),\n                              (a < lp->infinite) ? formatnumber12(numberbuffer, (double)a) : \"            \");\n          }\n          else\n            write_data(userhandle, write_modeldata, \" UP BND       %s  %s\\n\",\n                            MPSname(name0, get_col_name(lp, j)),\n                            formatnumber12(numberbuffer, (double)a));\n        }\n      }\n    }\n\n /* Write optional SOS section */\n  putheader = TRUE;\n  for(i = 0; i < SOS_count(lp); i++) {\n    SOSgroup *SOS = lp->SOS;\n\n    if(putheader) {\n      write_data(userhandle, write_modeldata, \"SOS\\n\");\n      putheader = FALSE;\n    }\n    write_data(userhandle, write_modeldata, \" S%1d SOS       %s  %s\\n\",\n                    SOS->sos_list[i]->type,\n                    MPSname(name0, SOS->sos_list[i]->name),\n                    formatnumber12(numberbuffer, (double) SOS->sos_list[i]->priority));\n    for(j = 1; j <= SOS->sos_list[i]->size; j++) {\n      write_data(userhandle, write_modeldata, \"    SOS       %s  %s\\n\",\n                      MPSname(name0, get_col_name(lp, SOS->sos_list[i]->members[j])),\n                      formatnumber12(numberbuffer, (double) SOS->sos_list[i]->weights[j]));\n    }\n  }\n\n  write_data(userhandle, write_modeldata, \"ENDATA\\n\");\n\n  lp->names_used = names_used;\n\n  return(ok);\n}\n\nstatic int __WINAPI write_lpdata(void *userhandle, char *buf)\n{\n  fputs(buf, (FILE *) userhandle);\n  return(TRUE);\n}\n\nMYBOOL MPS_writefile(lprec *lp, int typeMPS, char *filename)\n{\n  FILE *output = stdout;\n  MYBOOL ok;\n\n  if (filename != NULL) {\n    ok = ((output = fopen(filename, \"w\")) != NULL);\n    if(!ok)\n      return(ok);\n  }\n  else\n    output = lp->outstream;\n\n  ok = MPS_writefileex(lp, typeMPS, (void *) output, write_lpdata);\n\n  if (filename != NULL)\n    fclose(output);\n\n  return(ok);\n}\n\nMYBOOL MPS_writehandle(lprec *lp, int typeMPS, FILE *output)\n{\n  MYBOOL ok;\n\n  if (output != NULL)\n    set_outputstream(lp, output);\n\n  output = lp->outstream;\n\n  ok = MPS_writefileex(lp, typeMPS, (void *) output, write_lpdata);\n\n  return(ok);\n}\n\n\n/* Read and write BAS files */\n/* #define OldNameMatch */\n#ifdef OldNameMatch\nstatic int MPS_getnameidx(lprec *lp, char *varname, MYBOOL isrow)\n{\n  int in = -1;\n\n  in = get_nameindex(lp, varname, isrow);\n  if((in < 0) && (strncmp(varname, (isrow ? ROWNAMEMASK : COLNAMEMASK), 1) == 0)) {\n    if(sscanf(varname + 1, \"%d\", &in) != 1)\n      in = -1;\n  }\n  return( in );\n}\n#else\nstatic int MPS_getnameidx(lprec *lp, char *varname, MYBOOL tryrowfirst)\n{\n  int in = -1;\n\n  /* Have we defined our own variable names? */\n  if(lp->names_used) {\n    /* First check the primary name list */\n    in = get_nameindex(lp, varname, tryrowfirst);\n    if((in > 0) && !tryrowfirst)\n      in += lp->rows;\n    /* If we were unsuccessful, try the secondary name list */\n    else if(in < 0) {\n      in = get_nameindex(lp, varname, (MYBOOL) !tryrowfirst);\n      if((in > 0) && tryrowfirst)\n        in += lp->rows;\n    }\n  }\n  /* If not, see if we can match the standard name mask */\n\n  if(in == -1) {\n    if(strncmp(varname, (tryrowfirst ? ROWNAMEMASK : COLNAMEMASK), 1) == 0) {\n      /* Fail if we did not successfully scan as a valid integer */\n      if((sscanf(varname + 1, \"%d\", &in) != 1) ||\n         (in < (tryrowfirst ? 0 : 1)) || (in > (tryrowfirst ? lp->rows : lp->columns)))\n        in = -1;\n    }\n    else if(strncmp(varname, (!tryrowfirst ? ROWNAMEMASK : COLNAMEMASK), 1) == 0) {\n      /* Fail if we did not successfully scan as a valid integer */\n      if((sscanf(varname + 1, \"%d\", &in) != 1) ||\n         (in < (tryrowfirst ? 0 : 1)) || (in > (tryrowfirst ? lp->rows : lp->columns)))\n        in = -1;\n    }\n  }\n  return( in );\n}\n#endif\n\nMYBOOL MPS_readBAS(lprec *lp, int typeMPS, char *filename, char *info)\n{\n  char   field1[BUFSIZ], field2[BUFSIZ], field3[BUFSIZ], field5[BUFSIZ],\n         line[BUFSIZ], tmp[BUFSIZ], *ptr;\n  double field4, field6;\n  int    ib, in, items, Lineno = 0;\n  MYBOOL ok;\n  FILE   *input = stdin;\n  int    (*scan_line)(lprec *lp, int section, char* line, char *field1, char *field2, char *field3,\n                      double *field4, char *field5, double *field6);\n\n  if((typeMPS & MPSFIXED) == MPSFIXED)\n    scan_line = scan_lineFIXED;\n  else if((typeMPS & MPSFREE) == MPSFREE)\n    scan_line = scan_lineFREE;\n  else {\n    report(lp, IMPORTANT, \"MPS_readBAS: unrecognized MPS line type.\\n\");\n    return(FALSE);\n  }\n\n  ok = (MYBOOL) ((filename != NULL) && ((input = fopen(filename,\"r\")) != NULL));\n  if(!ok)\n    return(ok);\n  default_basis(lp);\n\n  /* Let's initialize line to all zero's */\n  MEMCLEAR(line, BUFSIZ);\n  ok = FALSE;\n  while(fgets(line, BUFSIZ - 1, input)) {\n    Lineno++;\n\n    for(ptr = line; (*ptr) && (isspace((unsigned char) *ptr)); ptr++);\n\n    /* skip lines which start with \"*\", they are comment */\n    if((line[0] == '*') || (*ptr == 0) || (*ptr == '\\n') || (*ptr == '\\r')) {\n      report(lp, FULL, \"Comment on line %d: %s\", Lineno, line);\n      continue;\n    }\n\n    report(lp, FULL, \"Line %6d: %s\", Lineno, line);\n\n    /* first check for \"special\" lines: in our case only NAME and ENDATA,\n       ...this must start in the first position of line */\n    if(line[0] != ' ') {\n      sscanf(line, \"%s\", tmp);\n      if(strcmp(tmp, \"NAME\") == 0) {\n        if(info != NULL) {\n          *info = 0;\n          for(ptr = line + 4; (*ptr) && (isspace((unsigned char) *ptr)); ptr++);\n          in = (int) strlen(ptr);\n          while ((in > 0) && ((ptr[in - 1] == '\\r') || (ptr[in - 1] == '\\n') || isspace(ptr[in - 1])))\n            in--;\n          ptr[in] = 0;\n          strcpy(info, ptr);\n        }\n      }\n      else if(strcmp(tmp, \"ENDATA\") == 0) {\n        report(lp, FULL, \"Finished reading BAS file\\n\");\n        ok = TRUE;\n        break;\n      }\n      else { /* line does not start with space and does not match above */\n        report(lp, IMPORTANT, \"Unrecognized BAS line %d: %s\\n\", Lineno, line);\n        break;\n      }\n    }\n    else { /* normal line, process */\n      items = scan_line(lp, /* MPSRHS */ MPSBOUNDS, line, field1, field2, field3, &field4, field5, &field6);\n      if(items < 0){\n        report(lp, IMPORTANT, \"Syntax error on line %d: %s\\n\", Lineno, line);\n        break;\n      }\n      /* find first variable index value */\n      in = MPS_getnameidx(lp, field2, FALSE);\n#ifdef OldNameMatch\n      if(in < 0)\n        in = MPS_getnameidx(lp, field2, TRUE);\n      else\n        in += lp->rows;\n#endif\n      if(in < 0)\n        break;\n\n      /* check if we have the basic/non-basic variable format */\n      if(field1[0] == 'X') {\n        /* find second variable index value */\n        ib = in;\n        in = MPS_getnameidx(lp, field3, FALSE);\n#ifdef OldNameMatch\n        if(in < 0)\n          in = MPS_getnameidx(lp, field3, TRUE);\n        else\n          in += lp->rows;\n#endif\n        if(in < 0)\n          break;\n\n        lp->is_lower[in] = (MYBOOL) (field1[1] == 'L');\n        lp->is_basic[ib] = TRUE;\n      }\n      else\n        lp->is_lower[in] = (MYBOOL) (field1[0] == 'L');\n\n      lp->is_basic[in] = FALSE;\n\n    }\n  }\n  /* Update the basis index-to-variable array */\n  ib = 0;\n  items = lp->sum;\n  for(in = 1; in <= items; in++)\n    if(lp->is_basic[in]) {\n      ib++;\n      lp->var_basic[ib] = in;\n    }\n\n  fclose(input);\n  return( ok );\n}\n\nMYBOOL MPS_writeBAS(lprec *lp, int typeMPS, char *filename)\n{\n  int    ib, in;\n  MYBOOL ok;\n  char   name1[100], name2[100];\n  FILE   *output = stdout;\n  char * (*MPSname)(char *name0, char *name);\n  char name0[9];\n\n  /* Set name formatter */\n  if((typeMPS & MPSFIXED) == MPSFIXED)\n    MPSname = MPSnameFIXED;\n  else if((typeMPS & MPSFREE) == MPSFREE)\n    MPSname = MPSnameFREE;\n  else {\n    report(lp, IMPORTANT, \"MPS_writeBAS: unrecognized MPS name type.\\n\");\n    return(FALSE);\n  }\n\n  /* Open the file for writing */\n  ok = (MYBOOL) ((filename == NULL) || ((output = fopen(filename,\"w\")) != NULL));\n  if(!ok)\n    return(ok);\n  if(filename == NULL && lp->outstream != NULL)\n    output = lp->outstream;\n\n  fprintf(output, \"NAME          %s Rows %d Cols %d Iters %.0f\\n\",\n                  get_lp_name(lp), lp->rows, lp->columns, (double) get_total_iter(lp));\n\n  ib = lp->rows;\n  in = 0;\n  while ((ib < lp->sum) || (in < lp->sum)) {\n\n    /* Find next basic variable (skip slacks) */\n    ib++;\n    while((ib <= lp->sum) && !lp->is_basic[ib])\n      ib++;\n\n    /* Find next non-basic variable (skip lower-bounded structural variables) */\n    in++;\n    while((in <= lp->sum) && (lp->is_basic[in] ||\n                              ((in > lp->rows) && lp->is_lower[in])))\n      in++;\n\n    /* Check if we have a basic/non-basic variable pair */\n    if((ib <= lp->sum) && (in <= lp->sum)) {\n      strcpy(name1, MPSname(name0, (ib <= lp->rows ? get_row_name(lp, ib) :\n                                              get_col_name(lp, ib-lp->rows))));\n      strcpy(name2, MPSname(name0, (in <= lp->rows ? get_row_name(lp, in) :\n                                              get_col_name(lp, in-lp->rows))));\n      fprintf(output, \" %2s %s  %s\\n\", (lp->is_lower[in] ? \"XL\" : \"XU\"), name1, name2);\n    }\n\n    /* Otherwise just write the bound state of the non-basic variable */\n    else if(in <= lp->sum) {\n      strcpy(name1, MPSname(name0, (in <= lp->rows ? get_row_name(lp, in) :\n                                              get_col_name(lp, in-lp->rows))));\n      fprintf(output, \" %2s %s\\n\", (lp->is_lower[in] ? \"LL\" : \"UL\"), name1);\n    }\n\n  }\n  fprintf(output, \"ENDATA\\n\");\n\n  if(filename != NULL)\n    fclose(output);\n  return( ok );\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_MPS.h",
    "content": "#ifndef HEADER_lp_MPS\n#define HEADER_lp_MPS\n\n#include \"lp_types.h\"\n\n/* For MPS file reading and writing */\n#define ROWNAMEMASK          \"R%d\"\n#define ROWNAMEMASK2         \"r%d\"\n#define COLNAMEMASK          \"C%d\"\n#define COLNAMEMASK2         \"c%d\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Read an MPS file */\nMYBOOL MPS_readfile(lprec **newlp, char *filename, int typeMPS, int verbose);\nMYBOOL __WINAPI MPS_readhandle(lprec **newlp, FILE *filehandle, int typeMPS, int verbose);\n\n/* Write a MPS file to output */\nMYBOOL MPS_writefile(lprec *lp, int typeMPS, char *filename);\nMYBOOL MPS_writehandle(lprec *lp, int typeMPS, FILE *output);\n\n/* Read and write BAS files */\nMYBOOL MPS_readBAS(lprec *lp, int typeMPS, char *filename, char *info);\nMYBOOL MPS_writeBAS(lprec *lp, int typeMPS, char *filename);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_MPS */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_SOS.c",
    "content": "\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_report.h\"\n#include \"lp_SOS.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n/*\n    Specially Ordered Set (SOS) routines - w/interface for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Kjell Eikland\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      lp_lib.h\n\n    Release notes:\n    v1.0    1 September 2003    Complete package for SOS creation and use in a LP\n                                setting.  Notable feature of this implementation\n                                compared to those in other commercial systems is\n                                the generalization to SOS'es of \"unlimited\" order.\n    v1.1     8 December 2003    Added variable (index) deletion method.\n    v1.2    17 December 2004    Added bound change tracking functionality.\n    v1.3    18 September 2005   Added sparse SOS handling to speed up processing\n                                of large number of SOS'es.\n\n   ----------------------------------------------------------------------------------\n*/\n\n/* SOS group functions */\nSTATIC SOSgroup *create_SOSgroup(lprec *lp)\n{\n  SOSgroup *group;\n\n  group = (SOSgroup *) calloc(1, sizeof(*group));\n  group->lp = lp;\n  group->sos_alloc = SOS_START_SIZE;\n  group->sos_list = (SOSrec **) malloc((group->sos_alloc) * sizeof(*group->sos_list));\n  return(group);\n}\n\nSTATIC void resize_SOSgroup(SOSgroup *group)\n{\n  if(group->sos_count == group->sos_alloc) {\n    group->sos_alloc = (int)((double) group->sos_alloc*RESIZEFACTOR);\n    group->sos_list = (SOSrec **) realloc(group->sos_list,\n                                          (group->sos_alloc) * sizeof(*group->sos_list));\n  }\n}\n\nSTATIC int append_SOSgroup(SOSgroup *group, SOSrec *SOS)\n{\n  int    i, k;\n  SOSrec *SOSHold;\n\n  /* Check if we should resize */\n  resize_SOSgroup(group);\n\n  /* First append to the end of the list */\n  group->sos_list[group->sos_count] = SOS;\n  group->sos_count++;\n  i = abs(SOS->type);\n  SETMAX(group->maxorder, i);\n  if(i == 1)\n    group->sos1_count++;\n  k = group->sos_count;\n  SOS->tagorder = k;\n\n  /* Sort the SOS list by given priority */\n  for(i = group->sos_count-1; i > 0; i--) {\n    if(group->sos_list[i]->priority < group->sos_list[i-1]->priority) {\n      SOSHold = group->sos_list[i];\n      group->sos_list[i] = group->sos_list[i-1];\n      group->sos_list[i-1] = SOSHold;\n      if(SOSHold == SOS)\n        k = i; /* This is the index in the [1..> range */\n    }\n    else\n      break;\n  }\n  /* Return the list index of the new SOS */\n  return( k );\n}\n\n\nSTATIC int clean_SOSgroup(SOSgroup *group, MYBOOL forceupdatemap)\n{\n  int    i, n, k;\n  SOSrec *SOS;\n\n  if(group == NULL)\n    return( 0 );\n\n  /* Delete any SOS without members or trivial member count */\n  n = 0;\n  if(group->sos_alloc > 0) {\n    group->maxorder = 0;\n    for(i = group->sos_count; i > 0; i--) {\n      SOS = group->sos_list[i-1];\n      k = SOS->members[0];\n      if((k == 0) ||                              /* Empty */\n         ((k == abs(SOS->type)) && (k <= 2))) {   /* Trivial */\n        delete_SOSrec(group, i);\n        n++;\n      }\n      else {\n        SETMAX(group->maxorder, abs(SOS->type));\n      }\n    }\n    if((n > 0) || forceupdatemap)\n      SOS_member_updatemap(group);\n  }\n  return( n );\n}\n\n\nSTATIC void free_SOSgroup(SOSgroup **group)\n{\n  int i;\n\n  if((group == NULL) || (*group == NULL))\n    return;\n  if((*group)->sos_alloc > 0) {\n    for(i = 0; i < (*group)->sos_count; i++)\n      free_SOSrec((*group)->sos_list[i]);\n    FREE((*group)->sos_list);\n    FREE((*group)->membership);\n    FREE((*group)->memberpos);\n  }\n  FREE(*group);\n}\n\n/* SOS record functions */\nSTATIC SOSrec *create_SOSrec(SOSgroup *group, char *name, int type, int priority, int size, int *variables, REAL *weights)\n{\n  SOSrec *SOS;\n\n  SOS = (SOSrec *) calloc(1 , sizeof(*SOS));\n  SOS->parent = group;\n  SOS->type = type;\n  if(name == NULL)\n    SOS->name = NULL;\n  else\n  {\n    allocCHAR(group->lp, &SOS->name, (int) (strlen(name)+1), FALSE);\n    strcpy(SOS->name, name);\n  }\n  if(type < 0)\n    type = abs(type);\n  SOS->tagorder = 0;\n  SOS->size = 0;\n  SOS->priority = priority;\n  SOS->members = NULL;\n  SOS->weights = NULL;\n  SOS->membersSorted = NULL;\n  SOS->membersMapped = NULL;\n\n  if(size > 0)\n    size = append_SOSrec(SOS, size, variables, weights);\n\n  return(SOS);\n}\n\n\nSTATIC int append_SOSrec(SOSrec *SOS, int size, int *variables, REAL *weights)\n{\n  int   i, oldsize, newsize, nn;\n  lprec *lp = SOS->parent->lp;\n\n  oldsize = SOS->size;\n  newsize = oldsize + size;\n  nn = abs(SOS->type);\n\n /* Shift existing active data right (normally zero) */\n  if(SOS->members == NULL)\n    allocINT(lp, &SOS->members, 1+newsize+1+nn, TRUE);\n  else {\n    allocINT(lp, &SOS->members, 1+newsize+1+nn, AUTOMATIC);\n    for(i = newsize+1+nn; i > newsize+1; i--)\n    SOS->members[i] = SOS->members[i-size];\n  }\n  SOS->members[0] = newsize;\n  SOS->members[newsize+1] = nn;\n\n /* Copy the new data into the arrays */\n  if(SOS->weights == NULL)\n    allocREAL(lp, &SOS->weights, 1+newsize, TRUE);\n  else\n    allocREAL(lp, &SOS->weights, 1+newsize, AUTOMATIC);\n  for(i = oldsize+1; i <= newsize; i++) {\n    SOS->members[i] = variables[i-oldsize-1];\n    if((SOS->members[i] < 1) || (SOS->members[i] > lp->columns))\n      report(lp, IMPORTANT, \"append_SOS_rec: Invalid SOS variable definition for index %d\\n\", SOS->members[i]);\n    else {\n      if(SOS->isGUB)\n        lp->var_type[SOS->members[i]] |= ISGUB;\n      else\n        lp->var_type[SOS->members[i]] |= ISSOS;\n    }\n    if(weights == NULL)\n      SOS->weights[i] = i;  /* Follow standard, which is sorted ascending */\n    else\n      SOS->weights[i] = weights[i-oldsize-1];\n    SOS->weights[0] += SOS->weights[i];\n  }\n\n /* Sort the new paired lists ascending by weight (simple bubble sort) */\n  i = sortByREAL(SOS->members, SOS->weights, newsize, 1, TRUE);\n  if(i > 0)\n    report(lp, DETAILED, \"append_SOS_rec: Non-unique SOS variable weight for index %d\\n\", i);\n\n /* Define mapping arrays to search large SOS's faster */\n  allocINT(lp, &SOS->membersSorted, newsize, AUTOMATIC);\n  allocINT(lp, &SOS->membersMapped, newsize, AUTOMATIC);\n  for(i = oldsize+1; i <= newsize; i++) {\n    SOS->membersSorted[i - 1] = SOS->members[i];\n    SOS->membersMapped[i - 1] = i;\n  }\n  sortByINT(SOS->membersMapped, SOS->membersSorted, newsize, 0, TRUE);\n\n /* Confirm the new size */\n  SOS->size = newsize;\n\n  return(newsize);\n\n}\n\nSTATIC int make_SOSchain(lprec *lp, MYBOOL forceresort)\n{\n  int      i, j, k, n;\n  MYBOOL   *hold = NULL;\n  REAL     *order, sum, weight;\n  SOSgroup *group = lp->SOS;\n\n  /* PART A: Resort individual SOS member lists, if specified */\n  if(forceresort)\n    SOS_member_sortlist(group, 0);\n\n  /* PART B: Tally SOS variables and create master SOS variable list */\n  n = 0;\n  for(i = 0; i < group->sos_count; i++)\n    n += group->sos_list[i]->size;\n  lp->sos_vars = n;\n  if(lp->sos_vars > 0) /* Prevent memory loss in case of multiple solves */\n    FREE(lp->sos_priority);\n  allocINT(lp, &lp->sos_priority, n, FALSE);\n  allocREAL(lp, &order, n, FALSE);\n\n  /* Move variable data to the master SOS list and sort by ascending weight */\n  n = 0;\n  sum = 0;\n  for(i = 0; i < group->sos_count; i++) {\n    for(j = 1; j <= group->sos_list[i]->size; j++) {\n      lp->sos_priority[n] = group->sos_list[i]->members[j];\n      weight = group->sos_list[i]->weights[j];\n      sum += weight;\n      order[n] = sum;\n      n++;\n    }\n  }\n  hpsortex(order, n, 0, sizeof(*order), FALSE, compareREAL, lp->sos_priority);\n  FREE(order);\n\n  /* Remove duplicate SOS variables */\n  allocMYBOOL(lp, &hold, lp->columns+1, TRUE);\n  k = 0;\n  for(i = 0; i < n; i++) {\n    j = lp->sos_priority[i];\n    if(!hold[j]) {\n      hold[j] = TRUE;\n      if(k < i)\n        lp->sos_priority[k] = j;\n      k++;\n    }\n  }\n  FREE(hold);\n\n  /* Adjust the size of the master variable list, if necessary */\n  if(k < lp->sos_vars) {\n    allocINT(lp, &lp->sos_priority, k, AUTOMATIC);\n    lp->sos_vars = k;\n  }\n\n  return( k );\n\n}\n\n\nSTATIC MYBOOL delete_SOSrec(SOSgroup *group, int sosindex)\n{\n#ifdef Paranoia\n  if((sosindex <= 0) || (sosindex > group->sos_count)) {\n    report(group->lp, IMPORTANT, \"delete_SOSrec: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  /* Delete and free the SOS record */\n  if(abs(SOS_get_type(group, sosindex)) == 1)\n    group->sos1_count--;\n  free_SOSrec(group->sos_list[sosindex-1]);\n  while(sosindex < group->sos_count) {\n    group->sos_list[sosindex-1] = group->sos_list[sosindex];\n    sosindex++;\n  }\n  group->sos_count--;\n\n  /* Update maxorder */\n  group->maxorder = 0;\n  for(sosindex = 0; sosindex < group->sos_count; sosindex++) {\n    SETMAX(group->maxorder, abs(group->sos_list[sosindex]->type));\n  }\n\n  return(TRUE);\n}\n\n\nSTATIC void free_SOSrec(SOSrec *SOS)\n{\n  if(SOS->name != NULL)\n    FREE(SOS->name);\n  if(SOS->size > 0) {\n    FREE(SOS->members);\n    FREE(SOS->weights);\n    FREE(SOS->membersSorted);\n    FREE(SOS->membersMapped);\n  }\n  FREE(SOS);\n}\n\n\nSTATIC MYBOOL SOS_member_sortlist(SOSgroup *group, int sosindex)\n/* Routine to (re-)sort SOS member arrays for faster access to large SOSes */\n{\n  int    i, n;\n  int    *list;\n  lprec  *lp = group->lp;\n  SOSrec *SOS;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_member_sortlist: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if((sosindex == 0) && (group->sos_count == 1))\n    sosindex = 1;\n\n  if(sosindex == 0) {\n    for(i = 1; i <= group->sos_count; i++) {\n      if(!SOS_member_sortlist(group, i))\n        return(FALSE);\n    }\n  }\n  else {\n    SOS = group->sos_list[sosindex-1];\n    list = SOS->members;\n    n = list[0];\n    /* Make sure that the arrays are properly allocated and sized */\n    if(n != group->sos_list[sosindex-1]->size) {\n      allocINT(lp, &SOS->membersSorted, n, AUTOMATIC);\n      allocINT(lp, &SOS->membersMapped, n, AUTOMATIC);\n      group->sos_list[sosindex-1]->size = n;\n    }\n    /* Reload the arrays and do the sorting */\n    for(i = 1; i <= n; i++) {\n      SOS->membersSorted[i - 1] = list[i];\n      SOS->membersMapped[i - 1] = i;\n    }\n    sortByINT(SOS->membersMapped, SOS->membersSorted, n, 0, TRUE);\n  }\n  return( TRUE );\n}\n\nSTATIC int SOS_member_updatemap(SOSgroup *group)\n{\n  int      i, j, k, n, nvars = 0,\n           *list, *tally = NULL;\n  SOSrec   *rec;\n  lprec    *lp = group->lp;\n\n  /* (Re)-initialize usage arrays */\n  allocINT(lp, &group->memberpos, lp->columns+1, AUTOMATIC);\n  allocINT(lp, &tally, lp->columns+1, TRUE);\n\n  /* Get each variable's SOS membership count */\n  for(i = 0; i < group->sos_count; i++) {\n    rec = group->sos_list[i];\n    n = rec->size;\n    list = rec->members;\n    for(j = 1; j <= n; j++) {\n      k = list[j];\n#ifdef Paranoia\n      if((k < 1) || (k > lp->columns))\n        report(lp, SEVERE, \"SOS_member_updatemap: Member %j of SOS number %d is out of column range (%d)\\n\",\n                            j, i+1, k);\n#endif\n      tally[k]++;\n    }\n\n  }\n\n  /* Compute pointer into column-sorted array */\n  group->memberpos[0] = 0;\n  for(i = 1; i <= lp->columns; i++) {\n    n = tally[i];\n    if(n > 0)\n      nvars++;\n    group->memberpos[i] = group->memberpos[i-1] + n;\n  }\n  n = group->memberpos[lp->columns];\n  MEMCOPY(tally+1, group->memberpos, lp->columns);\n\n  /* Load the column-sorted SOS indeces / pointers */\n  allocINT(lp, &group->membership, n+1, AUTOMATIC);\n  for(i = 0; i < group->sos_count; i++) {\n    rec = group->sos_list[i];\n    n = rec->size;\n    list = rec->members;\n    for(j = 1; j <= n; j++) {\n      k = tally[list[j]]++;\n#ifdef Paranoia\n      if(k > group->memberpos[lp->columns])\n        report(lp, SEVERE, \"SOS_member_updatemap: Member mapping for variable %j of SOS number %d is invalid\\n\",\n                            list[j], i+1);\n#endif\n      group->membership[k] = i+1;\n    }\n  }\n  FREE(tally);\n\n  return( nvars );\n}\n\n\nSTATIC MYBOOL SOS_shift_col(SOSgroup *group, int sosindex, int column, int delta, LLrec *usedmap, MYBOOL forceresort)\n/* Routine to adjust SOS indeces for variable insertions or deletions;\n   Note: SOS_shift_col must be called before make_SOSchain! */\n{\n  int    i, ii, n, nn, nr;\n  int    changed;\n  int    *list;\n  REAL   *weights;\n\n#ifdef Paranoia\n  lprec  *lp = group->lp;\n\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_shift_col: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n  else if((column < 1) || (delta == 0)) {\n    report(lp, IMPORTANT, \"SOS_shift_col: Invalid column %d specified with delta %d\\n\",\n                          column, delta);\n    return(FALSE);\n  }\n#endif\n\n  if((sosindex == 0) && (group->sos_count == 1))\n    sosindex = 1;\n\n  if(sosindex == 0) {\n    for(i = 1; i <= group->sos_count; i++) {\n      if(!SOS_shift_col(group, i, column, delta, usedmap, forceresort))\n        return(FALSE);\n    }\n  }\n  else {\n    list = group->sos_list[sosindex-1]->members;\n    weights = group->sos_list[sosindex-1]->weights;\n    n = list[0];\n    nn = list[n+1];\n\n    /* Case where variable indeces are to be incremented */\n    if(delta > 0) {\n      for(i = 1; i <= n; i++) {\n        if(list[i] >= column)\n          list[i] += delta;\n      }\n    }\n    /* Case where variables are to be deleted/indeces decremented */\n    else {\n      changed = 0;\n      if(usedmap != NULL) {\n        int *newidx = NULL;\n        /* Defer creation of index mapper until we are sure that a\n           member of this SOS is actually targeted for deletion */\n        if(newidx == NULL) {\n          allocINT(group->lp, &newidx, group->lp->columns+1, TRUE);\n          for(i = firstActiveLink(usedmap), ii = 1; i != 0;\n              i = nextActiveLink(usedmap, i), ii++)\n            newidx[i] = ii;\n        }\n        for(i = 1, ii = 0; i <= n; i++) {\n          nr = list[i];\n          /* Check if this SOS variable should be deleted */\n          if(!isActiveLink(usedmap, nr))\n            continue;\n\n          /* If the index is \"high\" then make adjustment and shift */\n          changed++;\n          ii++;\n          list[ii] = newidx[nr];\n          weights[ii] = weights[i];\n        }\n        FREE(newidx);\n      }\n      else\n        for(i = 1, ii = 0; i <= n; i++) {\n          nr = list[i];\n          /* Check if this SOS variable should be deleted */\n          if((nr >= column) && (nr < column-delta))\n            continue;\n          /* If the index is \"high\" then decrement */\n          if(nr > column) {\n            changed++;\n            nr += delta;\n          }\n          ii++;\n          list[ii] = nr;\n          weights[ii] = weights[i];\n        }\n      /* Update the SOS length / type indicators */\n      if(ii < n) {\n        list[0] = ii;\n        list[ii+1] = nn;\n      }\n\n     /* Update mapping arrays to search large SOS's faster */\n      if(forceresort && ((ii < n) || (changed > 0)))\n        SOS_member_sortlist(group, sosindex);\n    }\n\n  }\n  return(TRUE);\n\n}\n\nint SOS_member_count(SOSgroup *group, int sosindex)\n{\n  SOSrec *SOS;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(group->lp, IMPORTANT, \"SOS_member_count: Invalid SOS index %d\\n\", sosindex);\n    return( -1 );\n  }\n#endif\n  SOS = group->sos_list[sosindex-1];\n  return( SOS->members[0] );\n}\n\nint SOS_member_delete(SOSgroup *group, int sosindex, int member)\n{\n  int   *list, i, i2, k, n, nn = 0;\n  SOSrec *SOS;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(group->lp, IMPORTANT, \"SOS_member_delete: Invalid SOS index %d\\n\", sosindex);\n    return( -1 );\n  }\n#endif\n\n  if(sosindex == 0) {\n    for(i = group->memberpos[member-1]; i < group->memberpos[member]; i++) {\n      k = group->membership[i];\n      n = SOS_member_delete(group, k, member);\n      if(n >= 0)\n        nn += n;\n      else\n        return( n );\n    }\n    /* We must update the mapper */\n    k = group->memberpos[member];\n    i = group->memberpos[member-1];\n    n = group->memberpos[lp->columns] - k;\n    if(n > 0)\n      MEMCOPY(group->membership + i, group->membership + k, n);\n    for(i = member; i <= lp->columns; i++)\n      group->memberpos[i] = group->memberpos[i-1];\n  }\n  else {\n    SOS = group->sos_list[sosindex-1];\n    list = SOS->members;\n    n = list[0];\n\n    /* Find the offset of the member */\n    i = 1;\n    while((i <= n) && (abs(list[i]) != member))\n      i++;\n    if(i > n)\n      return( -1 );\n    nn++;\n\n    /* Shift remaining members *and* the active count one position left */\n    while(i <= n) {\n      list[i] = list[i+1];\n      i++;\n    }\n    list[0]--;\n    SOS->size--;\n\n    /* Do the same with the active list one position left */\n    i = n + 1;\n    i2 = i + list[n];\n    k = i + 1;\n    while(i < i2) {\n      if(abs(list[k]) == member)\n        k++;\n      list[i] = list[k];\n      i++;\n      k++;\n    }\n  }\n\n  return( nn );\n}\n\nint SOS_get_type(SOSgroup *group, int sosindex)\n{\n#ifdef Paranoia\n  if((sosindex < 1) || (sosindex > group->sos_count)) {\n    report(group->lp, IMPORTANT, \"SOS_get_type: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  return(group->sos_list[sosindex-1]->type);\n}\n\n\nint SOS_infeasible(SOSgroup *group, int sosindex)\n{\n  int    i, n, nn, varnr, failindex, *list;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_infeasible: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if(sosindex == 0 && group->sos_count == 1)\n    sosindex = 1;\n\n  failindex = 0;\n  if(sosindex == 0) {\n    for(i = 1; i <= group->sos_count; i++) {\n      failindex = SOS_infeasible(group, i);\n      if(failindex > 0) break;\n    }\n  }\n  else {\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0];\n    nn = list[n+1];\n   /* Find index of next lower-bounded variable */\n    for(i = 1; i <= n; i++) {\n      varnr = abs(list[i]);\n      if((lp->orig_lowbo[lp->rows + varnr] > 0) &&\n         !((lp->sc_vars > 0) && is_semicont(lp, varnr)))\n        break;\n    }\n\n   /* Find if there is another lower-bounded variable beyond the type window */\n    i = i+nn;\n    while(i <= n) {\n      varnr = abs(list[i]);\n      if((lp->orig_lowbo[lp->rows + varnr] > 0) &&\n         !((lp->sc_vars > 0) && is_semicont(lp, varnr)))\n        break;\n      i++;\n    }\n    if(i <= n)\n      failindex = abs(list[i]);\n  }\n  return(failindex);\n}\n\n\nint SOS_member_index(SOSgroup *group, int sosindex, int member)\n{\n  int    n;\n  SOSrec *SOS;\n\n  SOS = group->sos_list[sosindex-1];\n  n = SOS->members[0];\n\n  n = searchFor(member, SOS->membersSorted, n, 0, FALSE);\n  if(n >= 0)\n    n = SOS->membersMapped[n];\n\n  return(n);\n}\n\n\nint SOS_memberships(SOSgroup *group, int varnr)\n{\n  int   i, n = 0;\n  lprec *lp;\n\n  /* Check if there is anything to do */\n  if((group == NULL) || (SOS_count(lp = group->lp) == 0))\n    return( n );\n\n#ifdef Paranoia\n  if((varnr < 0) || (varnr > lp->columns)) {\n    report(lp, IMPORTANT, \"SOS_memberships: Invalid variable index %d given\\n\", varnr);\n    return( n );\n  }\n#endif\n\n  if(varnr == 0) {\n    for(i = 1; i <= lp->columns; i++)\n      if(group->memberpos[i] > group->memberpos[i-1])\n        n++;\n  }\n  else\n    n = group->memberpos[varnr] - group->memberpos[varnr-1];\n\n  return( n );\n}\n\n\nint SOS_is_member(SOSgroup *group, int sosindex, int column)\n{\n  int    i, n = FALSE, *list;\n  lprec  *lp;\n\n  if(group == NULL)\n    return( FALSE );\n  lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_is_member: Invalid SOS index %d\\n\", sosindex);\n    return(n);\n  }\n#endif\n\n  if(sosindex == 0) {\n    if(lp->var_type[column] & (ISSOS | ISGUB))\n      n = (MYBOOL) (SOS_memberships(group, column) > 0);\n  }\n  else if(lp->var_type[column] & (ISSOS | ISGUB)) {\n\n   /* Search for the variable */\n    i = SOS_member_index(group, sosindex, column);\n\n   /* Signal active status if found, otherwise return FALSE */\n    if(i > 0) {\n      list = group->sos_list[sosindex-1]->members;\n      if(list[i] < 0)\n        n = -TRUE;\n      else\n      n = TRUE;\n    }\n  }\n  return(n);\n}\n\n\nMYBOOL SOS_is_member_of_type(SOSgroup *group, int column, int sostype)\n{\n  int i, k, n;\n\n  if(group != NULL)\n  for(i = group->memberpos[column-1]; i < group->memberpos[column]; i++) {\n    k = group->membership[i];\n    n = SOS_get_type(group, k);\n    if(((n == sostype) ||\n        ((sostype == SOSn) && (n > 2))) && SOS_is_member(group, k, column))\n      return(TRUE);\n  }\n  return(FALSE);\n}\n\n\nMYBOOL SOS_set_GUB(SOSgroup *group, int sosindex, MYBOOL state)\n{\n  int i;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(group->lp, IMPORTANT, \"SOS_set_GUB: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n  if((sosindex == 0) && (group->sos_count == 1))\n    sosindex = 1;\n\n  if(sosindex == 0) {\n    for(i = 1; i <= group->sos_count; i++)\n      SOS_set_GUB(group, i, state);\n  }\n  else\n    group->sos_list[sosindex-1]->isGUB = state;\n  return(TRUE);\n}\n\n\nMYBOOL SOS_is_GUB(SOSgroup *group, int sosindex)\n{\n  int    i;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(group->lp, IMPORTANT, \"SOS_is_GUB: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if((sosindex == 0) && (group->sos_count == 1))\n    sosindex = 1;\n\n  if(sosindex == 0) {\n    for(i = 1; i <= group->sos_count; i++) {\n      if(SOS_is_GUB(group, i))\n        return(TRUE);\n    }\n    return(FALSE);\n  }\n  else\n    return( group->sos_list[sosindex-1]->isGUB );\n}\n\n\nMYBOOL SOS_is_marked(SOSgroup *group, int sosindex, int column)\n{\n  int    i, k, n, *list;\n  lprec  *lp;\n\n  if(group == NULL)\n    return( FALSE );\n  lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_is_marked: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if(!(lp->var_type[column] & (ISSOS | ISGUB)))\n    return(FALSE);\n\n  if(sosindex == 0) {\n    for(i = group->memberpos[column-1]; i < group->memberpos[column]; i++) {\n      k = group->membership[i];\n      n = SOS_is_marked(group, k, column);\n      if(n)\n        return(TRUE);\n    }\n  }\n  else  {\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0];\n\n   /* Search for the variable (normally always faster to do linear search here) */\n    column = -column;\n    for(i = 1; i <= n; i++)\n      if(list[i] == column)\n        return(TRUE);\n  }\n  return(FALSE);\n}\n\n\nMYBOOL SOS_is_active(SOSgroup *group, int sosindex, int column)\n{\n  int    i, n, nn, *list;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_is_active: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if(!(lp->var_type[column] & (ISSOS | ISGUB)))\n    return(FALSE);\n\n  if(sosindex == 0) {\n    for(i = group->memberpos[column-1]; i < group->memberpos[column]; i++) {\n      nn = group->membership[i];\n      n = SOS_is_active(group, nn, column);\n      if(n)\n        return(TRUE);\n    }\n  }\n  else {\n\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0]+1;\n    nn = list[n];\n\n    /* Scan the active (non-zero) SOS index list */\n    for(i = 1; (i <= nn) && (list[n+i] != 0); i++)\n      if(list[n+i] == column)\n        return(TRUE);\n  }\n  return(FALSE);\n}\n\n\nMYBOOL SOS_is_full(SOSgroup *group, int sosindex, int column, MYBOOL activeonly)\n{\n  int    i, nn, n, *list;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_is_full: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if(!(lp->var_type[column] & (ISSOS | ISGUB)))\n    return(FALSE);\n\n  if(sosindex == 0) {\n    for(i = group->memberpos[column-1]; i < group->memberpos[column]; i++) {\n      nn = group->membership[i];\n      if(SOS_is_full(group, nn, column, activeonly))\n        return(TRUE);\n    }\n  }\n  else if(SOS_is_member(group, sosindex, column)) {\n\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0]+1;\n    nn = list[n];\n\n   /* Info: Last item in the active list is non-zero if the current SOS is full */\n    if(list[n+nn] != 0)\n      return(TRUE);\n\n    if(!activeonly) {\n      /* Spool to last active variable */\n      for(i = nn-1; (i > 0) && (list[n+i] == 0); i--);\n      /* Having found it, check if subsequent variables are set (via bounds) as inactive */\n      if(i > 0) {\n        nn -= i;  /* Compute unused active slots */\n        i = SOS_member_index(group, sosindex, list[n+i]);\n        for(; (nn > 0) && (list[i] < 0); i++, nn--);\n        if(nn == 0)\n          return(TRUE);\n      }\n    }\n  }\n\n  return(FALSE);\n}\n\n\nMYBOOL SOS_can_activate(SOSgroup *group, int sosindex, int column)\n{\n  int    i, n, nn, nz, *list;\n  lprec  *lp;\n\n  if(group == NULL)\n    return( FALSE );\n  lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_can_activate: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if(!(lp->var_type[column] & (ISSOS | ISGUB)))\n    return(FALSE);\n\n  if(sosindex == 0) {\n    for(i = group->memberpos[column-1]; i < group->memberpos[column]; i++) {\n      nn = group->membership[i];\n      n = SOS_can_activate(group, nn, column);\n      if(n == FALSE)\n        return(FALSE);\n    }\n  }\n  else if(SOS_is_member(group, sosindex, column)) {\n\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0]+1;\n    nn = list[n];\n\n#if 0\n    /* Accept if the SOS is empty */\n    if(list[n+1] == 0)\n      return(TRUE);\n#endif\n\n    /* Cannot activate a variable if the SOS is full */\n    if(list[n+nn] != 0)\n      return(FALSE);\n\n    /* Check if there are variables quasi-active via non-zero lower bounds */\n    nz = 0;\n    for(i = 1; i < n; i++)\n      if(lp->bb_bounds->lowbo[lp->rows+abs(list[i])] > 0) {\n        nz++;\n        /* Reject outright if selected column has a non-zero lower bound */\n        if(list[i] == column)\n          return(FALSE);\n      }\n#ifdef Paranoia\n    if(nz > nn)\n      report(lp, SEVERE, \"SOS_can_activate: Found too many non-zero member variables for SOS index %d\\n\", sosindex);\n#endif\n    for(i = 1; i <= nn; i++) {\n      if(list[n+i] == 0)\n        break;\n      if(lp->bb_bounds->lowbo[lp->rows+list[n+i]] == 0)\n        nz++;\n    }\n    if(nz == nn)\n      return(FALSE);\n\n    /* Accept if the SOS is empty */\n    if(list[n+1] == 0)\n      return(TRUE);\n\n    /* Check if we can set variable active in SOS2..SOSn\n      (must check left and right neighbours if one variable is already active) */\n    if(nn > 1) {\n\n     /* Find the variable that was last activated;\n       Also check that the candidate variable is not already active */\n      for(i = 1; i <= nn; i++) {\n        if(list[n+i] == 0)\n          break;\n        if(list[n+i] == column)\n          return(FALSE);\n      }\n      i--;\n      nn = list[n+i];\n\n      /* SOS accepts an additional variable; confirm neighbourness of candidate;\n         Search for the SOS set index of the last activated variable */\n      n = list[0];\n      for(i = 1; i <= n; i++)\n        if(abs(list[i]) == nn)\n          break;\n      if(i > n) {\n        report(lp, CRITICAL, \"SOS_can_activate: Internal index error at SOS %d\\n\", sosindex);\n        return(FALSE);\n      }\n\n      /* SOS accepts an additional variable; confirm neighbourness of candidate */\n\n      /* Check left neighbour */\n      if((i > 1) && (list[i-1] == column))\n        return(TRUE);\n      /* Check right neighbour */\n      if((i < n) && (list[i+1] == column))\n        return(TRUE);\n\n      /* It is not the right neighbour; return false */\n      return(FALSE);\n    }\n  }\n  return(TRUE);\n}\n\n\nMYBOOL SOS_set_marked(SOSgroup *group, int sosindex, int column, MYBOOL asactive)\n{\n  int    i, n, nn, *list;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_set_marked: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if(!(lp->var_type[column] & (ISSOS | ISGUB)))\n    return(FALSE);\n\n  if(sosindex == 0) {\n\n   /* Define an IBM-\"SOS3\" member variable temporarily as integer, if it is\n      not already a permanent integer; is reset in SOS_unmark */\n    if(asactive && !is_int(lp, column) && SOS_is_member_of_type(group, column, SOS3)) {\n      lp->var_type[column] |= ISSOSTEMPINT;\n      set_int(lp, column, TRUE);\n    }\n\n    nn = 0;\n    for(i = group->memberpos[column-1]; i < group->memberpos[column]; i++) {\n      n = group->membership[i];\n      if(SOS_set_marked(group, n, column, asactive))\n        nn++;\n    }\n    return((MYBOOL) (nn == group->sos_count));\n  }\n  else {\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0]+1;\n    nn = list[n];\n\n   /* Search for the variable */\n    i = SOS_member_index(group, sosindex, column);\n\n   /* First mark active in the set member list as used */\n    if((i > 0) && (list[i] > 0))\n      list[i] *= -1;\n    else\n      return(TRUE);\n\n   /* Then move the variable to the live list */\n    if(asactive) {\n      for(i = 1; i <= nn; i++) {\n        if(list[n+i] == column)\n          return(FALSE);\n        else if(list[n+i] == 0) {\n          list[n+i] = column;\n          return(FALSE);\n        }\n      }\n    }\n    return(TRUE);\n  }\n}\n\n\nMYBOOL SOS_unmark(SOSgroup *group, int sosindex, int column)\n{\n  int    i, n, nn, *list;\n  MYBOOL isactive;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_unmark: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if(!(lp->var_type[column] & (ISSOS | ISGUB)))\n    return(FALSE);\n\n\n  if(sosindex == 0) {\n\n    /* Undefine a SOS3 member variable that has temporarily been set as integer */\n    if(lp->var_type[column] & ISSOSTEMPINT) {\n      lp->var_type[column] &= !ISSOSTEMPINT;\n      set_int(lp, column, FALSE);\n    }\n\n    nn = 0;\n    for(i = group->memberpos[column-1]; i < group->memberpos[column]; i++) {\n      n = group->membership[i];\n      if(SOS_unmark(group, n, column))\n        nn++;\n    }\n    return((MYBOOL) (nn == group->sos_count));\n  }\n  else {\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0]+1;\n    nn = list[n];\n\n   /* Search for the variable */\n    i = SOS_member_index(group, sosindex, column);\n\n   /* Restore sign in main list */\n    if((i > 0) && (list[i] < 0))\n      list[i] *= -1;\n    else\n      return(TRUE);\n\n   /* Find the variable in the active list... */\n    isactive = SOS_is_active(group, sosindex, column);\n    if(isactive) {\n      for(i = 1; i <= nn; i++)\n        if(list[n+i] == column)\n          break;\n     /* ...shrink the list if found, otherwise return error */\n      if(i <= nn) {\n        for(; i<nn; i++)\n        list[n+i] = list[n+i+1];\n        list[n+nn] = 0;\n        return(TRUE);\n      }\n      return(FALSE);\n    }\n    else\n      return(TRUE);\n  }\n}\n\n\nint SOS_fix_unmarked(SOSgroup *group, int sosindex, int variable, REAL *bound, REAL value, MYBOOL isupper,\n                     int *diffcount, DeltaVrec *changelog)\n{\n  int    i, ii, count, n, nn, nLeft, nRight, *list;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_fix_unmarked: Invalid SOS index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  count = 0;\n  if(sosindex == 0) {\n    for(i = group->memberpos[variable-1]; i < group->memberpos[variable]; i++) {\n      n = group->membership[i];\n      count += SOS_fix_unmarked(group, n, variable, bound, value, isupper, diffcount, changelog);\n    }\n  }\n  else {\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0]+1;\n\n   /* Count the number of active and free SOS variables */\n    nn = list[n];\n    for(i = 1; i <= nn; i++) {\n      if(list[n+i] == 0)\n      break;\n    }\n    i--;\n    i = nn - i;  /* Establish the number of unused slots */\n\n   /* Determine the free SOS variable window */\n    if(i == nn) {\n      nLeft = 0;\n      nRight = SOS_member_index(group, sosindex, variable);\n    }\n    else {\n      nLeft  = SOS_member_index(group, sosindex, list[n+1]);\n      if(variable == list[n+1])\n        nRight = nLeft;\n      else\n        nRight = SOS_member_index(group, sosindex, variable);\n    }\n\n    nRight += i;  /* Loop (nRight+1)..n */\n\n   /* Fix variables outside of the free SOS variable window */\n    for(i = 1; i < n; i++)  {\n     /* Skip the SOS variable window */\n      if((i >= nLeft) && (i <= nRight))\n        continue;\n     /* Otherwise proceed to set bound */\n      ii = list[i];\n      if(ii > 0) {\n        ii += lp->rows;\n        if(bound[ii] != value) {\n         /* Verify that we don't violate original bounds */\n          if(isupper && (value < lp->orig_lowbo[ii]))\n            return(-ii);\n          else if(!isupper && (value > lp->orig_upbo[ii]))\n            return(-ii);\n         /* OK, set the new bound */\n          count++;\n          if(changelog == NULL)\n            bound[ii] = value;\n          else\n            modifyUndoLadder(changelog, ii, bound, value);\n\n        }\n        if((diffcount != NULL) && (lp->solution[ii] != value))\n          (*diffcount)++;\n      }\n    }\n  }\n  return(count);\n}\n\nint *SOS_get_candidates(SOSgroup *group, int sosindex, int column, MYBOOL excludetarget,\n                        REAL *upbound, REAL *lobound)\n{\n  int    i, ii, j, n, nn = 0, *list, *candidates = NULL;\n  lprec  *lp = group->lp;\n\n  if(group == NULL)\n    return( candidates );\n\n#ifdef Paranoia\n  if(sosindex > group->sos_count) {\n    report(lp, IMPORTANT, \"SOS_get_candidates: Invalid index %d\\n\", sosindex);\n    return( candidates );\n  }\n#endif\n\n  /* Determine SOS target(s); note that if \"sosindex\" is negative, only\n     the first non-empty SOS where \"column\" is a member is processed */\n  if(sosindex <= 0) {\n    i = 0;\n    ii = group->sos_count;\n  }\n  else {\n    i = sosindex - 1;\n    ii = sosindex;\n  }\n\n  /* Tally candidate usage */\n  allocINT(lp, &candidates, lp->columns+1, TRUE);\n  for(; i < ii; i++) {\n    if(!SOS_is_member(group, i+1, column))\n      continue;\n    list = group->sos_list[i]->members;\n    n = list[0];\n    while(n > 0) {\n      j = list[n];\n      if((j > 0) && (upbound[lp->rows+j] > 0)) {\n        if(lobound[lp->rows+j] > 0) {\n          report(lp, IMPORTANT, \"SOS_get_candidates: Invalid non-zero lower bound setting\\n\");\n          n = 0;\n          goto Finish;\n        }\n        if(candidates[j] == 0)\n          nn++;\n        candidates[j]++;\n      }\n      n--;\n    }\n    if((sosindex < 0) && (nn > 1))\n      break;\n  }\n\n  /* Condense the list into indeces */\n  n = 0;\n  for(i = 1; i <= lp->columns; i++) {\n    if((candidates[i] > 0) && (!excludetarget || (i != column))) {\n      n++;\n      candidates[n] = i;\n    }\n  }\n\n  /* Finalize */\nFinish:\n  candidates[0] = n;\n  if(n == 0)\n    FREE(candidates);\n\n  return( candidates);\n\n}\n\nint SOS_fix_list(SOSgroup *group, int sosindex, int variable, REAL *bound,\n                 int *varlist, MYBOOL isleft, DeltaVrec *changelog)\n{\n  int    i, ii, jj, count = 0;\n  REAL   value = 0;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_fix_list: Invalid index %d\\n\", sosindex);\n    return(FALSE);\n  }\n#endif\n\n  if(sosindex == 0) {\n    for(i = group->memberpos[variable-1]; i < group->memberpos[variable]; i++) {\n      ii = group->membership[i];\n      count += SOS_fix_list(group, ii, variable, bound, varlist, isleft, changelog);\n    }\n  }\n  else {\n\n    /* Establish the number of unmarked variables in the left window\n       (note that \"variable\" should have been marked previously) */\n    ii = varlist[0] / 2;\n    if(isleft) {\n      i = 1;\n      if(isleft == AUTOMATIC)\n        ii = varlist[0];\n    }\n    else {\n      i = ii + 1;\n      ii = varlist[0];\n    }\n\n    /* Loop over members to fix values at the new bound (zero) */\n    while(i <= ii) {\n      if(SOS_is_member(group, sosindex, varlist[i])) {\n        jj = lp->rows + varlist[i];\n\n        /* Verify that we don't violate original bounds */\n        if(value < lp->orig_lowbo[jj])\n          return( -jj );\n        /* OK, set the new bound */\n        count++;\n        if(changelog == NULL)\n          bound[jj] = value;\n        else\n          modifyUndoLadder(changelog, jj, bound, value);\n      }\n      i++;\n    }\n\n  }\n  return( count );\n}\n\nint SOS_is_satisfied(SOSgroup *group, int sosindex, REAL *solution)\n/* Determine if the SOS is satisfied for the current solution vector;\n   The return code is in the range [-2..+2], depending on the type of\n   satisfaction.  Positive return value means too many non-zero values,\n   negative value means set incomplete:\n\n              -2: Set member count not full (SOS3)\n              -1: Set member count not full\n               0: Set is full (also returned if the SOS index is invalid)\n               1: Too many non-zero sequential variables\n               2: Set consistency error\n\n*/\n{\n  int    i, n, nn, count, *list;\n  int    type, status = 0;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_is_satisfied: Invalid index %d\\n\", sosindex);\n    return( SOS_COMPLETE );\n  }\n#endif\n\n  if((sosindex == 0) && (group->sos_count == 1))\n    sosindex = 1;\n\n  if(sosindex == 0) {\n    for(i = 1; i <= group->sos_count; i++) {\n      status = SOS_is_satisfied(group, i, solution);\n      if((status != SOS_COMPLETE) && (status != SOS_INCOMPLETE))\n        break;\n    }\n  }\n  else {\n    type = SOS_get_type(group, sosindex);\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0]+1;\n    nn = list[n];\n\n   /* Count the number of active SOS variables */\n    for(i = 1; i <= nn; i++) {\n      if(list[n+i] == 0)\n        break;\n    }\n    count = i-1;\n    if(count == nn)\n      status = SOS_COMPLETE;    /* Set is full    */\n    else\n      status = SOS_INCOMPLETE;  /* Set is partial */\n\n   /* Find index of the first active variable; fail if some are non-zero */\n    if(count > 0) {\n      nn = list[n+1];\n      for(i = 1; i < n; i++) {\n        if((abs(list[i]) == nn) || (solution[lp->rows + abs(list[i])] != 0))\n          break;\n      }\n      if(abs(list[i]) != nn)\n        status = SOS_INTERNALERROR;  /* Set consistency error (leading set variables are non-zero) */\n      else {\n       /* Scan active SOS variables until we find a non-zero value */\n        while(count > 0) {\n          if(solution[lp->rows + abs(list[i])] != 0)\n            break;\n          i++;\n          count--;\n        }\n       /* Scan active non-zero SOS variables; break at first non-zero (rest required to be zero) */\n        while(count > 0) {\n          if(solution[lp->rows + abs(list[i])] == 0)\n            break;\n          i++;\n          count--;\n        }\n        if(count > 0)\n          status = SOS_INTERNALERROR; /* Set consistency error (active set variables are zero) */\n      }\n    }\n    else {\n      i = 1;\n      /* There are no active variables; see if we have happened to find a valid header */\n      while((i < n) && (solution[lp->rows + abs(list[i])] == 0))\n        i++;\n      count = 0;\n      while((i < n) && (count <= nn) && (solution[lp->rows + abs(list[i])] != 0)) {\n        count++;\n        i++;\n      }\n      if(count > nn)\n        status = SOS_INFEASIBLE;   /* Too-many sequential non-zero variables */\n    }\n\n    /* Scan the trailing set of SOS variables; fail if some are non-zero */\n    if(status <= 0) {\n      n--;\n      while(i <= n) {\n        if(solution[lp->rows + abs(list[i])] != 0)\n          break;\n        i++;\n      }\n      if(i <= n)\n        status = SOS_INFEASIBLE;  /* Too-many sequential non-zero variables */\n\n      /* Code member deficiency for SOS3 separately */\n      else if((status == -1) && (type <= SOS3))\n        status = SOS3_INCOMPLETE;\n    }\n\n  }\n  return( status );\n}\n\nMYBOOL SOS_is_feasible(SOSgroup *group, int sosindex, REAL *solution)\n/* Determine if the SOS is feasible up to the current SOS variable */\n{\n  int    i, n, nn, *list;\n  MYBOOL status = TRUE;\n  lprec  *lp = group->lp;\n\n#ifdef Paranoia\n  if((sosindex < 0) || (sosindex > group->sos_count)) {\n    report(lp, IMPORTANT, \"SOS_is_feasible: Invalid SOS index %d\\n\", sosindex);\n    return( 0 );\n  }\n#endif\n\n  if((sosindex == 0) && (group->sos_count == 1))\n    sosindex = 1;\n\n  if(sosindex == 0) {\n    for(i = 1; status && (i <= group->sos_count); i++) {\n      status = SOS_is_feasible(group, i, solution);\n    }\n  }\n  else {\n    list = group->sos_list[sosindex-1]->members;\n    n = list[0]+1;\n    nn = list[n];\n    if(nn <= 2)\n      return(status);\n\n   /* Find if we have a gap in the non-zero solution values */\n    i = 1;\n    sosindex = 0;\n    while((i <= nn) && (list[n+i] != 0)) {\n      while((i <= nn) && (list[n+i] != 0) && (solution[lp->rows+list[n+i]] == 0))\n        i++;\n      if((i <= nn) && (list[n+i] != 0)) {\n        i++;  /* Step to next */\n        while((i <= nn) && (list[n+i] != 0) && (solution[lp->rows+list[n+i]] != 0))\n          i++;\n        sosindex++;\n      }\n      i++;    /* Step to next */\n    }\n    status = (MYBOOL) (sosindex <= 1);\n  }\n  return(status);\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_SOS.h",
    "content": "#ifndef HEADER_lp_SOS\n#define HEADER_lp_SOS\n\n/* Specially Ordered Sets (SOS) prototypes and settings                      */\n/* ------------------------------------------------------------------------- */\n\n#include \"lp_types.h\"\n#include \"lp_utils.h\"\n#include \"lp_matrix.h\"\n\n\n/* SOS constraint defines                                                    */\n/* ------------------------------------------------------------------------- */\n#define SOS1                     1\n#define SOS2                     2\n#define SOS3                    -1\n#define SOSn                      MAXINT32\n#define SOS_START_SIZE          10  /* Start size of SOS_list array; realloced if needed */\n\n/* Define SOS_is_feasible() return values                                    */\n/* ------------------------------------------------------------------------- */\n#define SOS3_INCOMPLETE         -2\n#define SOS_INCOMPLETE          -1\n#define SOS_COMPLETE             0\n#define SOS_INFEASIBLE           1\n#define SOS_INTERNALERROR        2\n\n\ntypedef struct _SOSgroup SOSgroup;\n\ntypedef struct _SOSrec\n{\n  SOSgroup  *parent;\n  int       tagorder;\n  char      *name;\n  int       type;\n  MYBOOL    isGUB;\n  int       size;\n  int       priority;\n  int       *members;\n  REAL      *weights;\n  int       *membersSorted;\n  int       *membersMapped;\n} SOSrec;\n\n/* typedef */ struct _SOSgroup\n{\n  lprec     *lp;                /* Pointer to owner */\n  SOSrec    **sos_list;         /* Array of pointers to SOS lists */\n  int       sos_alloc;          /* Size allocated to specially ordered sets (SOS1, SOS2...) */\n  int       sos_count;          /* Number of specially ordered sets (SOS1, SOS2...) */\n  int       maxorder;           /* The highest-order SOS in the group */\n  int       sos1_count;         /* Number of the lowest order SOS in the group */\n  int       *membership;        /* Array of variable-sorted indeces to SOSes that the variable is member of */\n  int       *memberpos;         /* Starting positions of the each column's membership list */\n} /* SOSgroup */;\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* SOS storage structure */\nSTATIC SOSgroup *create_SOSgroup(lprec *lp);\nSTATIC void resize_SOSgroup(SOSgroup *group);\nSTATIC int append_SOSgroup(SOSgroup *group, SOSrec *SOS);\nSTATIC int clean_SOSgroup(SOSgroup *group, MYBOOL forceupdatemap);\nSTATIC void free_SOSgroup(SOSgroup **group);\n\nSTATIC SOSrec *create_SOSrec(SOSgroup *group, char *name, int type, int priority, int size, int *variables, REAL *weights);\nSTATIC MYBOOL delete_SOSrec(SOSgroup *group, int sosindex);\nSTATIC int append_SOSrec(SOSrec *SOS, int size, int *variables, REAL *weights);\nSTATIC void free_SOSrec(SOSrec *SOS);\n\n/* SOS utilities */\nSTATIC int make_SOSchain(lprec *lp, MYBOOL forceresort);\nSTATIC int SOS_member_updatemap(SOSgroup *group);\nSTATIC MYBOOL SOS_member_sortlist(SOSgroup *group, int sosindex);\nSTATIC MYBOOL SOS_shift_col(SOSgroup *group, int sosindex, int column, int delta, LLrec *usedmap, MYBOOL forceresort);\nint SOS_member_delete(SOSgroup *group, int sosindex, int member);\nint SOS_get_type(SOSgroup *group, int sosindex);\nint SOS_infeasible(SOSgroup *group, int sosindex);\nint SOS_member_index(SOSgroup *group, int sosindex, int member);\nint SOS_member_count(SOSgroup *group, int sosindex);\nint SOS_memberships(SOSgroup *group, int column);\nint *SOS_get_candidates(SOSgroup *group, int sosindex, int column, MYBOOL excludetarget, REAL *upbound, REAL *lobound);\nint SOS_is_member(SOSgroup *group, int sosindex, int column);\nMYBOOL SOS_is_member_of_type(SOSgroup *group, int column, int sostype);\nMYBOOL SOS_set_GUB(SOSgroup *group, int sosindex, MYBOOL state);\nMYBOOL SOS_is_GUB(SOSgroup *group, int sosindex);\nMYBOOL SOS_is_marked(SOSgroup *group, int sosindex, int column);\nMYBOOL SOS_is_active(SOSgroup *group, int sosindex, int column);\nMYBOOL SOS_is_full(SOSgroup *group, int sosindex, int column, MYBOOL activeonly);\nMYBOOL SOS_can_activate(SOSgroup *group, int sosindex, int column);\nMYBOOL SOS_set_marked(SOSgroup *group, int sosindex, int column, MYBOOL asactive);\nMYBOOL SOS_unmark(SOSgroup *group, int sosindex, int column);\nint SOS_fix_unmarked(SOSgroup *group, int sosindex, int variable, REAL *bound, REAL value,\n                     MYBOOL isupper, int *diffcount, DeltaVrec *changelog);\nint SOS_fix_list(SOSgroup *group, int sosindex, int variable, REAL *bound, \n                  int *varlist, MYBOOL isleft, DeltaVrec *changelog);\nint SOS_is_satisfied(SOSgroup *group, int sosindex, REAL *solution);\nMYBOOL SOS_is_feasible(SOSgroup *group, int sosindex, REAL *solution);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_SOS */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_bit.h",
    "content": "#include \"lp_types.h\"\r\n\r\n#if defined INLINE\r\n# define MYINLINE INLINE\r\n#else\r\n# define MYINLINE static\r\n#endif\r\n\r\nMYINLINE void set_biton(MYBOOL *bitarray, int item)\r\n{\r\n  bitarray[item / 8] |= (1 << (item % 8));\r\n}\r\n\r\nMYINLINE void set_bitoff(MYBOOL *bitarray, int item)\r\n{\r\n  bitarray[item / 8] &= ~(1 << (item % 8));\r\n}\r\n\r\nMYINLINE MYBOOL is_biton(MYBOOL *bitarray, int item)\r\n{\r\n  return( (MYBOOL) ((bitarray[item / 8] & (1 << (item % 8))) != 0) );\r\n}\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_crash.c",
    "content": "\n/*\n   ----------------------------------------------------------------------------------\n   Crash management routines in lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Kjell Eikland\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      lp_lib.h, lp_utils.h, lp_matrix.h\n\n    Release notes:\n    v1.0.0  1 April   2004      First version.\n    v1.1.0  20 July 2004        Reworked with flexible matrix storage model.\n\n   ----------------------------------------------------------------------------------\n*/\n\n#include <string.h>\n\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_scale.h\"\n#include \"lp_utils.h\"\n#include \"lp_report.h\"\n#include \"lp_matrix.h\"\n#include \"lp_crash.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\nMYBOOL crash_basis(lprec *lp)\n{\n  int     i;\n  MATrec  *mat = lp->matA;\n  MYBOOL  ok = TRUE;\n\n  /* Initialize basis indicators */\n  if(lp->basis_valid)\n    lp->var_basic[0] = FALSE;\n  else\n    default_basis(lp);\n\n  /* Set initial partial pricing blocks */\n  if(lp->rowblocks != NULL)\n    lp->rowblocks->blocknow = 1;\n  if(lp->colblocks != NULL)\n    lp->colblocks->blocknow = ((lp->crashmode == CRASH_NONE) || (lp->colblocks->blockcount == 1) ? 1 : 2);\n\n  /* Construct a basis that is in some measure the \"most feasible\" */\n  if((lp->crashmode == CRASH_MOSTFEASIBLE) && mat_validate(mat)) {\n    /* The logic here follows Maros */\n    LLrec   *rowLL = NULL, *colLL = NULL;\n    int     ii, rx, cx, ix, nz;\n    REAL    wx, tx, *rowMAX = NULL, *colMAX = NULL;\n    int     *rowNZ = NULL, *colNZ = NULL, *rowWT = NULL, *colWT = NULL;\n    REAL    *value;\n    int     *rownr, *colnr;\n\n    report(lp, NORMAL, \"crash_basis: 'Most feasible' basis crashing selected\\n\");\n\n    /* Tally row and column non-zero counts */\n    ok = allocINT(lp,  &rowNZ, lp->rows+1,     TRUE) &&\n         allocINT(lp,  &colNZ, lp->columns+1,  TRUE) &&\n         allocREAL(lp, &rowMAX, lp->rows+1,    FALSE) &&\n         allocREAL(lp, &colMAX, lp->columns+1, FALSE);\n    if(!ok)\n      goto Finish;\n\n    nz = mat_nonzeros(mat);\n    rownr = &COL_MAT_ROWNR(0);\n    colnr = &COL_MAT_COLNR(0);\n    value = &COL_MAT_VALUE(0);\n    for(i = 0; i < nz;\n        i++, rownr += matRowColStep, colnr += matRowColStep, value += matValueStep) {\n      rx = *rownr;\n      cx = *colnr;\n      wx = fabs(*value);\n      rowNZ[rx]++;\n      colNZ[cx]++;\n      if(i == 0) {\n        rowMAX[rx] = wx;\n        colMAX[cx] = wx;\n        colMAX[0]  = wx;\n      }\n      else {\n        SETMAX(rowMAX[rx], wx);\n        SETMAX(colMAX[cx], wx);\n        SETMAX(colMAX[0],  wx);\n      }\n    }\n    /* Reduce counts for small magnitude to preserve stability */\n    rownr = &COL_MAT_ROWNR(0);\n    colnr = &COL_MAT_COLNR(0);\n    value = &COL_MAT_VALUE(0);\n    for(i = 0; i < nz;\n        i++, rownr += matRowColStep, colnr += matRowColStep, value += matValueStep) {\n      rx = *rownr;\n      cx = *colnr;\n      wx = fabs(*value);\n#ifdef CRASH_SIMPLESCALE\n      if(wx < CRASH_THRESHOLD * colMAX[0]) {\n        rowNZ[rx]--;\n        colNZ[cx]--;\n      }\n#else\n      if(wx < CRASH_THRESHOLD * rowMAX[rx])\n        rowNZ[rx]--;\n      if(wx < CRASH_THRESHOLD * colMAX[cx])\n        colNZ[cx]--;\n#endif\n    }\n\n    /* Set up priority tables */\n    ok = allocINT(lp, &rowWT, lp->rows+1, TRUE);\n    createLink(lp->rows,    &rowLL, NULL);\n    ok &= (rowLL != NULL);\n    if(!ok)\n      goto Finish;\n    for(i = 1; i <= lp->rows; i++) {\n      if(get_constr_type(lp, i)==EQ)\n        ii = 3;\n      else if(lp->upbo[i] < lp->infinite)\n        ii = 2;\n      else if(fabs(lp->rhs[i]) < lp->infinite)\n        ii = 1;\n      else\n        ii = 0;\n      rowWT[i] = ii;\n      if(ii > 0)\n        appendLink(rowLL, i);\n    }\n    ok = allocINT(lp, &colWT, lp->columns+1, TRUE);\n    createLink(lp->columns, &colLL, NULL);\n    ok &= (colLL != NULL);\n    if(!ok)\n      goto Finish;\n    for(i = 1; i <= lp->columns; i++) {\n      ix = lp->rows+i;\n      if(is_unbounded(lp, i))\n        ii = 3;\n      else if(lp->upbo[ix] >= lp->infinite)\n        ii = 2;\n      else if(fabs(lp->upbo[ix]-lp->lowbo[ix]) > lp->epsmachine)\n        ii = 1;\n      else\n        ii = 0;\n      colWT[i] = ii;\n      if(ii > 0)\n        appendLink(colLL, i);\n    }\n\n    /* Loop over all basis variables */\n    for(i = 1; i <= lp->rows; i++) {\n\n      /* Select row */\n      rx = 0;\n      wx = -lp->infinite;\n      for(ii = firstActiveLink(rowLL); ii > 0; ii = nextActiveLink(rowLL, ii)) {\n        tx = rowWT[ii] - CRASH_SPACER*rowNZ[ii];\n        if(tx > wx) {\n          rx = ii;\n          wx = tx;\n        }\n      }\n      if(rx == 0)\n        break;\n      removeLink(rowLL, rx);\n\n      /* Select column */\n      cx = 0;\n      wx = -lp->infinite;\n      for(ii = mat->row_end[rx-1]; ii < mat->row_end[rx]; ii++) {\n\n        /* Update NZ column counts for row selected above */\n        tx = fabs(ROW_MAT_VALUE(ii));\n        ix = ROW_MAT_COLNR(ii);\n#ifdef CRASH_SIMPLESCALE\n        if(tx >= CRASH_THRESHOLD * colMAX[0])\n#else\n        if(tx >= CRASH_THRESHOLD * colMAX[ix])\n#endif\n          colNZ[ix]--;\n        if(!isActiveLink(colLL, ix) || (tx < CRASH_THRESHOLD * rowMAX[rx]))\n          continue;\n\n        /* Now do the test for best pivot */\n        tx = my_sign(lp->orig_obj[ix]) - my_sign(ROW_MAT_VALUE(ii));\n        tx = colWT[ix] + CRASH_WEIGHT*tx - CRASH_SPACER*colNZ[ix];\n        if(tx > wx) {\n          cx = ix;\n          wx = tx;\n        }\n      }\n      if(cx == 0)\n        break;\n      removeLink(colLL, cx);\n\n      /* Update row NZ counts */\n      ii = mat->col_end[cx-1];\n      rownr = &COL_MAT_ROWNR(ii);\n      value = &COL_MAT_VALUE(ii);\n      for(; ii < mat->col_end[cx];\n          ii++, rownr += matRowColStep, value += matValueStep) {\n        wx = fabs(*value);\n        ix = *rownr;\n#ifdef CRASH_SIMPLESCALE\n        if(wx >= CRASH_THRESHOLD * colMAX[0])\n#else\n        if(wx >= CRASH_THRESHOLD * rowMAX[ix])\n#endif\n          rowNZ[ix]--;\n      }\n\n      /* Set new basis variable */\n      set_basisvar(lp, rx, lp->rows+cx);\n    }\n\n    /* Clean up */\nFinish:\n    FREE(rowNZ);\n    FREE(colNZ);\n    FREE(rowMAX);\n    FREE(colMAX);\n    FREE(rowWT);\n    FREE(colWT);\n    freeLink(&rowLL);\n    freeLink(&colLL);\n  }\n\n  /* Construct a basis that is in some measure the \"least degenerate\" */\n  else if((lp->crashmode == CRASH_LEASTDEGENERATE) && mat_validate(mat)) {\n    /* The logic here follows Maros */\n    LLrec   *rowLL = NULL, *colLL = NULL;\n    int     ii, rx, cx, ix, nz, *merit = NULL;\n    REAL    *value, wx, hold, *rhs = NULL, *eta = NULL;\n    int     *rownr, *colnr;\n\n    report(lp, NORMAL, \"crash_basis: 'Least degenerate' basis crashing selected\\n\");\n\n    /* Create temporary arrays */\n    ok = allocINT(lp,  &merit, lp->columns + 1, FALSE) &&\n         allocREAL(lp, &eta, lp->rows + 1, FALSE) &&\n         allocREAL(lp, &rhs, lp->rows + 1, FALSE);\n    createLink(lp->columns, &colLL, NULL);\n    createLink(lp->rows, &rowLL, NULL);\n    ok &= (colLL != NULL) && (rowLL != NULL);\n    if(!ok)\n      goto FinishLD;\n    MEMCOPY(rhs, lp->orig_rhs, lp->rows + 1);\n    for(i = 1; i <= lp->columns; i++)\n      appendLink(colLL, i);\n    for(i = 1; i <= lp->rows; i++)\n      appendLink(rowLL, i);\n\n    /* Loop until we have found enough new bases */\n    while(colLL->count > 0) {\n\n      /* Tally non-zeros matching in RHS and each active column */\n      nz = mat_nonzeros(mat);\n      rownr = &COL_MAT_ROWNR(0);\n      colnr = &COL_MAT_COLNR(0);\n      ii = 0;\n      MEMCLEAR(merit, lp->columns + 1);\n      for(i = 0; i < nz;\n          i++, rownr += matRowColStep, colnr += matRowColStep) {\n        rx = *rownr;\n        cx = *colnr;\n        if(isActiveLink(colLL, cx) && (rhs[rx] != 0)) {\n          merit[cx]++;\n          ii++;\n        }\n      }\n      if(ii == 0)\n        break;\n\n      /* Find maximal match; break ties with column length */\n      i = firstActiveLink(colLL);\n      cx = i;\n      for(i = nextActiveLink(colLL, i); i != 0; i = nextActiveLink(colLL, i)) {\n        if(merit[i] >= merit[cx]) {\n          if((merit[i] > merit[cx]) || (mat_collength(mat, i) > mat_collength(mat, cx)))\n            cx = i;\n        }\n      }\n\n      /* Determine the best pivot row */\n      i = mat->col_end[cx-1];\n      nz = mat->col_end[cx];\n      rownr = &COL_MAT_ROWNR(i);\n      value = &COL_MAT_VALUE(i);\n      rx = 0;\n      wx = 0;\n      MEMCLEAR(eta, lp->rows + 1);\n      for(; i < nz;\n          i++, rownr += matRowColStep, value += matValueStep) {\n        ix = *rownr;\n        hold = *value;\n        eta[ix] = rhs[ix] / hold;\n        hold = fabs(hold);\n        if(isActiveLink(rowLL, ix) && (hold > wx)) {\n          wx = hold;\n          rx = ix;\n        }\n      }\n\n      /* Set new basis variable */\n      if(rx > 0) {\n\n        /* We have to update the rhs vector for the implied transformation\n          in order to be able to find the new RHS non-zero pattern */\n        for(i = 1; i <= lp->rows; i++)\n           rhs[i] -= wx * eta[i];\n        rhs[rx] = wx;\n\n        /* Do the exchange */\n        set_basisvar(lp, rx, lp->rows+cx);\n        removeLink(rowLL, rx);\n      }\n      removeLink(colLL, cx);\n\n    }\n\n    /* Clean up */\nFinishLD:\n    FREE(merit);\n    FREE(rhs);\n    freeLink(&rowLL);\n    freeLink(&colLL);\n\n  }\n  return( ok );\n}\n\n#if 0\nMYBOOL __WINAPI guess_basis(lprec *lp, REAL *guessvector, int *basisvector)\n{\n  MYBOOL status = FALSE;\n  REAL   *values = NULL, *violation = NULL,\n         *value, error, upB, loB, sortorder = 1.0;\n  int    i, n, *rownr, *colnr;\n  MATrec *mat = lp->matA;\n\n  if(!mat_validate(lp->matA))\n    return( status );\n\n  /* Create helper arrays */\n  if(!allocREAL(lp, &values, lp->sum+1, TRUE) ||\n     !allocREAL(lp, &violation, lp->sum+1, TRUE))\n    goto Finish;\n\n  /* Compute values of slack variables for given guess vector */\n  i = 0;\n  n = get_nonzeros(lp);\n  rownr = &COL_MAT_ROWNR(i);\n  colnr = &COL_MAT_COLNR(i);\n  value = &COL_MAT_VALUE(i);\n  for(; i < n; i++, rownr += matRowColStep, colnr += matRowColStep, value += matValueStep)\n    values[*rownr] += unscaled_mat(lp, my_chsign(is_chsign(lp, *rownr), *value), *rownr, *colnr) *\n                      guessvector[*colnr];\n  MEMMOVE(values+lp->rows+1, guessvector+1, lp->columns);\n\n  /* Initialize constraint bound violation measures */\n  for(i = 1; i <= lp->rows; i++) {\n    upB = get_rh_upper(lp, i);\n    loB = get_rh_lower(lp, i);\n    error = values[i] - upB;\n    if(error > lp->epsprimal)\n      violation[i] = sortorder*error;\n    else {\n      error = loB - values[i];\n      if(error > lp->epsprimal)\n        violation[i] = sortorder*error;\n      else if(is_infinite(lp, loB) && is_infinite(lp, upB))\n        ;\n      else if(is_infinite(lp, upB))\n        violation[i] = sortorder*(loB - values[i]);\n      else if(is_infinite(lp, loB))\n        violation[i] = sortorder*(values[i] - upB);\n      else\n        violation[i] = - sortorder*MAX(upB - values[i], values[i] - loB);\n    }\n    basisvector[i] = i;\n  }\n\n  /* Initialize user variable bound violation measures */\n  for(i = 1; i <= lp->columns; i++) {\n    n = lp->rows+i;\n    upB = get_upbo(lp, i);\n    loB = get_lowbo(lp, i);\n    error = guessvector[i] - upB;\n    if(error > lp->epsprimal)\n      violation[n] = sortorder*error;\n    else {\n      error = loB - values[n];\n      if(error > lp->epsprimal)\n        violation[n] = sortorder*error;\n      else if(is_infinite(lp, loB) && is_infinite(lp, upB))\n        ;\n      else if(is_infinite(lp, upB))\n        violation[n] = sortorder*(loB - values[n]);\n      else if(is_infinite(lp, loB))\n        violation[n] = sortorder*(values[n] - upB);\n      else\n        violation[n] = - sortorder*MAX(upB - values[n], values[n] - loB);\n    }\n    basisvector[n] = n;\n  }\n\n  /* Sort decending by violation; this means that variables with\n     the largest violations will be designated as basic */\n  sortByREAL(basisvector, violation, lp->sum, 1, FALSE);\n\n  /* Adjust the non-basic indeces for the (proximal) bound state */\n  error = lp->epsprimal;\n  for(i = lp->rows+1, rownr = basisvector+i; i <= lp->sum; i++, rownr++) {\n    if(*rownr <= lp->rows) {\n      if(values[*rownr] <= get_rh_lower(lp, *rownr)+error)\n        *rownr = -(*rownr);\n    }\n    else\n      if(values[i] <= get_lowbo(lp, (*rownr)-lp->rows)+error)\n        *rownr = -(*rownr);\n  }\n\n  /* Clean up and return status */\n  status = (MYBOOL) (violation[1] == 0);\nFinish:\n  FREE(values);\n  FREE(violation);\n\n\n  return( status );\n}\n#endif\n\n#if 0\nMYBOOL __WINAPI guess_basis(lprec *lp, REAL *guessvector, int *basisvector)\n{\n  MYBOOL *isnz, status = FALSE;\n  REAL   *values = NULL, *violation = NULL,\n         eps = lp->epsprimal,\n         *value, error, upB, loB, sortorder = 1.0;\n  int    i, j, n, *rownr, *colnr, *slkpos,\n         nrows = lp->rows, ncols = lp->columns;\n  MATrec *mat = lp->matA;\n\n  if(!mat_validate(mat))\n    return( status );\n\n  /* Create helper arrays */\n  if(!allocREAL(lp, &values, lp->sum+1, TRUE) ||\n     !allocREAL(lp, &violation, lp->sum+1, TRUE))\n    goto Finish;\n\n  /* Compute values of slack variables for given guess vector */\n  i = 0;\n  n = get_nonzeros(lp);\n  rownr = &COL_MAT_ROWNR(i);\n  colnr = &COL_MAT_COLNR(i);\n  value = &COL_MAT_VALUE(i);\n  for(; i < n; i++, rownr += matRowColStep, colnr += matRowColStep, value += matValueStep)\n    values[*rownr] += unscaled_mat(lp, my_chsign(is_chsign(lp, *rownr), *value), *rownr, *colnr) *\n                      guessvector[*colnr];\n  MEMMOVE(values+nrows+1, guessvector+1, ncols);\n\n  /* Initialize constraint bound violation measures (expressed as positive values) */\n  for(i = 1; i <= nrows; i++) {\n    upB = get_rh_upper(lp, i);\n    loB = get_rh_lower(lp, i);\n    error = values[i] - upB;\n    if(error > eps)\n      violation[i] = sortorder*error;\n    else {\n      error = loB - values[i];\n      if(error > eps)\n        violation[i] = sortorder*error;\n      else if(my_infinite(lp, loB) && my_infinite(lp, upB))\n        ;\n      else if(my_infinite(lp, upB))\n        violation[i] = sortorder*(loB - values[i]);\n      else if(my_infinite(lp, loB))\n        violation[i] = sortorder*(values[i] - upB);\n      else\n        violation[i] = -sortorder*MAX(upB - values[i], values[i] - loB);\n    }\n    basisvector[i] = i;\n  }\n\n  /* Initialize user variable bound violation measures (expressed as positive values) */\n  for(i = 1; i <= ncols; i++) {\n    n = nrows+i;\n    upB = get_upbo(lp, i);\n    loB = get_lowbo(lp, i);\n    error = guessvector[i] - upB;\n    if(error > eps)\n      violation[n] = sortorder*error;\n    else {\n      error = loB - values[n];\n      if(error > eps)\n        violation[n] = sortorder*error;\n      else if(my_infinite(lp, loB) && my_infinite(lp, upB))\n        ;\n      else if(my_infinite(lp, upB))\n        violation[n] = sortorder*(loB - values[n]);\n      else if(my_infinite(lp, loB))\n        violation[n] = sortorder*(values[n] - upB);\n      else\n        violation[n] = -sortorder*MAX(upB - values[n], values[n] - loB);\n    }\n    basisvector[n] = n;\n  }\n\n  /* Sort decending by violation; this means that variables with\n     the largest violations will be designated as basic */\n  sortByREAL(basisvector, violation, lp->sum, 1, FALSE);\n  error = violation[1];\n\n  /* Adjust the non-basic indeces for the (proximal) bound state */\n  for(i = nrows+1, rownr = basisvector+i; i <= lp->sum; i++, rownr++) {\n    if(*rownr <= nrows) {\n      if(values[*rownr] <= get_rh_lower(lp, *rownr)+eps)\n        *rownr = -(*rownr);\n    }\n    else\n      if(values[i] <= get_lowbo(lp, (*rownr)-nrows)+eps)\n        *rownr = -(*rownr);\n  }\n\n#if 1\n  /* Let us check for obvious row singularities and try to fix these;\n     First assemble necessary basis statistics... */\n  isnz = (MYBOOL *) values;\n  MEMCLEAR(isnz, nrows+1);\n  slkpos = (int *) violation;\n  MEMCLEAR(slkpos, nrows+1);\n  for(i = 1; i <= nrows; i++) {\n    j = abs(basisvector[i]);\n    if(j <= nrows) {\n      isnz[j] = TRUE;\n      slkpos[j] = i;\n    }\n    else {\n      j-= nrows;\n      j = mat->col_end[j-1];\n      isnz[COL_MAT_ROWNR(j)] = TRUE;\n      /*isnz[COL_MAT_ROWNR(j+1)] = TRUE;*/\n    }\n  }\n  for(; i <= lp->sum; i++) {\n    j = abs(basisvector[i]);\n    if(j <= nrows)\n      slkpos[j] = i;\n  }\n\n  /* ...then set the corresponding slacks basic for row rank deficient positions */\n  for(j = 1; j <= nrows; j++) {\n#ifdef Paranoia\n    if(slkpos[j] == 0)\n      report(lp, SEVERE, \"guess_basis: Internal error\");\n#endif\n    if(!isnz[j]) {\n      isnz[j] = TRUE;\n      i = slkpos[j];\n      swapINT(&basisvector[i], &basisvector[j]);\n      basisvector[j] = abs(basisvector[j]);\n    }\n  }\n#endif\n\n  /* Clean up and return status */\n  status = (MYBOOL) (error <= eps);\nFinish:\n  FREE(values);\n  FREE(violation);\n\n  return( status );\n}\n#endif\n\n#if 0\nMYBOOL __WINAPI guess_basis(lprec *lp, REAL *guessvector, int *basisvector)\n{\n  MYBOOL *isnz, status = FALSE;\n  REAL   *values = NULL, *violation = NULL,\n         eps = lp->epsprimal,\n         *value, error, upB, loB, sortorder = 1.0;\n  int    i, j, jj, n, *rownr, *colnr, *slkpos,\n         nrows = lp->rows, ncols = lp->columns;\n  MATrec *mat = lp->matA;\n\n  if(!mat_validate(mat))\n    return( status );\n\n  /* Create helper arrays */\n  if(!allocREAL(lp, &values, lp->sum+1, TRUE) ||\n     !allocREAL(lp, &violation, lp->sum+1, TRUE))\n    goto Finish;\n\n  /* Compute values of slack variables for given guess vector */\n  i = 0;\n  n = get_nonzeros(lp);\n  rownr = &COL_MAT_ROWNR(i);\n  colnr = &COL_MAT_COLNR(i);\n  value = &COL_MAT_VALUE(i);\n  for(; i < n; i++, rownr += matRowColStep, colnr += matRowColStep, value += matValueStep)\n    values[*rownr] += unscaled_mat(lp, my_chsign(is_chsign(lp, *rownr), *value), *rownr, *colnr) *\n                      guessvector[*colnr];\n  MEMMOVE(values+nrows+1, guessvector+1, ncols);\n\n  /* Initialize constraint bound violation measures (expressed as positive values) */\n  for(i = 1; i <= nrows; i++) {\n    upB = get_rh_upper(lp, i);\n    loB = get_rh_lower(lp, i);\n    error = values[i] - upB;\n    if(error > -eps)\n      violation[i] = sortorder*MAX(0,error);\n    else {\n      error = loB - values[i];\n      if(error > -eps)\n        violation[i] = sortorder*MAX(0,error);\n      else if(my_infinite(lp, loB) && my_infinite(lp, upB))\n        ;\n      else if(my_infinite(lp, upB))\n        violation[i] = sortorder*(loB - values[i]);\n      else if(my_infinite(lp, loB))\n        violation[i] = sortorder*(values[i] - upB);\n      else\n        violation[i] = -sortorder*MAX(upB - values[i], values[i] - loB);\n    }\n    basisvector[i] = i;\n  }\n\n  /* Initialize user variable bound violation measures (expressed as positive values) */\n  for(i = 1; i <= ncols; i++) {\n    n = nrows+i;\n    upB = get_upbo(lp, i);\n    loB = get_lowbo(lp, i);\n    error = guessvector[i] - upB;\n    if(error > -eps)\n      violation[n] = sortorder*MAX(0,error);\n    else {\n      error = loB - values[n];\n      if(error > -eps)\n        violation[n] = sortorder*MAX(0,error);\n      else if(my_infinite(lp, loB) && my_infinite(lp, upB))\n        ;\n      else if(my_infinite(lp, upB))\n        violation[n] = sortorder*(loB - values[n]);\n      else if(my_infinite(lp, loB))\n        violation[n] = sortorder*(values[n] - upB);\n      else\n        violation[n] = -sortorder*MAX(upB - values[n], values[n] - loB);\n    }\n    basisvector[n] = n;\n  }\n\n  /* Sort decending by violation; this means that variables with\n     the largest violations will be designated as basic */\n  sortByREAL(basisvector, violation, lp->sum, 1, FALSE);\n  error = violation[1];\n\n  /* Adjust the non-basic indeces for the (proximal) bound state */\n  for(i = nrows+1, rownr = basisvector+i; i <= lp->sum; i++, rownr++) {\n    if(*rownr <= nrows) {\n      values[*rownr] -= lp->orig_rhs[*rownr];\n      if(values[*rownr] <= eps)\n        *rownr = -(*rownr);\n    }\n    else\n      if(values[i] <= get_lowbo(lp, (*rownr)-nrows)+eps)\n        *rownr = -(*rownr);\n  }\n\n  /* Let us check for obvious row singularities and try to fix these;\n     First assemble necessary basis statistics... */\n  isnz = (MYBOOL *) values;\n  MEMCLEAR(isnz, nrows+1);\n  slkpos = (int *) violation;\n  MEMCLEAR(slkpos, nrows+1);\n  for(i = 1; i <= nrows; i++) {\n    j = abs(basisvector[i]);\n    if(j <= nrows) {\n      isnz[j] = TRUE;\n      slkpos[j] = i;\n    }\n    else {\n      j-= nrows;\n      jj = mat->col_end[j-1];\n      isnz[COL_MAT_ROWNR(jj)] = TRUE;\n/*      if(++jj < mat->col_end[j])\n        isnz[COL_MAT_ROWNR(jj)] = TRUE; */\n    }\n  }\n  for(; i <= lp->sum; i++) {\n    j = abs(basisvector[i]);\n    if(j <= nrows)\n      slkpos[j] = i;\n  }\n\n  /* ...then set the corresponding slacks basic for row rank deficient positions */\n  for(j = 1; j <= nrows; j++) {\n#ifdef Paranoia\n    if(slkpos[j] == 0)\n      report(lp, SEVERE, \"guess_basis: Internal error\");\n#endif\n    if(!isnz[j]) {\n      isnz[j] = TRUE;\n      i = slkpos[j];\n      swapINT(&basisvector[i], &basisvector[j]);\n      basisvector[j] = abs(basisvector[j]);\n    }\n  }\n\n  /* Lastly normalize all basic variables to be coded as lower-bounded */\n  for(i = 1; i <= nrows; i++)\n    basisvector[i] = -abs(basisvector[i]);\n\n  /* Clean up and return status */\n  status = (MYBOOL) (error <= eps);\nFinish:\n  FREE(values);\n  FREE(violation);\n\n  return( status );\n}\n#endif\n\nMYBOOL __WINAPI guess_basis(lprec *lp, REAL *guessvector, int *basisvector)\n{\n  MYBOOL *isnz = NULL, status = FALSE;\n  REAL   *values = NULL, *violation = NULL,\n         eps = lp->epsprimal,\n         *value, error, upB, loB, sortorder = -1.0;\n  int    i, j, jj, n, *rownr, *colnr, *slkpos = NULL,\n         nrows = lp->rows, ncols = lp->columns, nsum = lp->sum;\n  int    *basisnr;\n  MATrec *mat = lp->matA;\n\n  if(!mat_validate(mat))\n    return( status );\n\n  /* Create helper arrays, providing for multiple use of the violation array */\n  if(!allocREAL(lp, &values, nsum+1, TRUE) ||\n     !allocREAL(lp, &violation, nsum+1, TRUE))\n    goto Finish;\n\n  /* Compute the values of the constraints for the given guess vector */\n  i = 0;\n  n = get_nonzeros(lp);\n  rownr = &COL_MAT_ROWNR(i);\n  colnr = &COL_MAT_COLNR(i);\n  value = &COL_MAT_VALUE(i);\n  for(; i < n; i++, rownr += matRowColStep, colnr += matRowColStep, value += matValueStep)\n    values[*rownr] += unscaled_mat(lp, my_chsign(is_chsign(lp, *rownr), *value), *rownr, *colnr) *\n                      guessvector[*colnr];\n  MEMMOVE(values+nrows+1, guessvector+1, ncols);\n\n  /* Initialize bound \"violation\" or primal non-degeneracy measures, expressed\n     as the absolute value of the differences from the closest bound. */\n  for(i = 1; i <= nsum; i++) {\n    if(i <= nrows) {\n      loB = get_rh_lower(lp, i);\n      upB = get_rh_upper(lp, i);\n    }\n    else {\n      loB = get_lowbo(lp, i-nrows);\n      upB = get_upbo(lp, i-nrows);\n    }\n\n    /* Free constraints/variables */\n    if(my_infinite(lp, loB) && my_infinite(lp, upB))\n      error = 0;\n    /* Violated constraints/variable bounds */\n    else if(values[i]+eps < loB)\n      error = loB-values[i];\n    else if(values[i]-eps > upB)\n      error = values[i]-upB;\n    /* Non-violated constraints/variables bounds */\n    else if(my_infinite(lp, upB))\n      error = MAX(0, values[i]-loB);\n    else if(my_infinite(lp, loB))\n      error = MAX(0, upB-values[i]);\n    else\n      error = MIN(upB-values[i], values[i]-loB); /* MAX(upB-values[i], values[i]-loB); */\n    if(error != 0)\n      violation[i] = sortorder*error;\n    basisvector[i] = i;\n  }\n\n  /* Sort decending , meaning that variables with the largest\n     \"violations\" will be designated basic. Effectively, we are performing a\n     greedy type algorithm, but start at the \"least interesting\" end. */\n  sortByREAL(basisvector, violation, nsum, 1, FALSE);\n  error = violation[1]; /* Used for setting the return value */\n\n  /* Let us check for obvious row singularities and try to fix these.\n     Note that we reuse the memory allocated to the violation array.\n     First assemble necessary basis statistics... */\n  slkpos = (int *) violation;\n  n = nrows+1;\n  MEMCLEAR(slkpos, n);\n  isnz = (MYBOOL *) (slkpos+n+1);\n  MEMCLEAR(isnz, n);\n  for(i = 1; i <= nrows; i++) {\n    j = abs(basisvector[i]);\n    if(j <= nrows) {\n      isnz[j] = TRUE;\n      slkpos[j] = i;\n    }\n    else {\n      j-= nrows;\n      jj = mat->col_end[j-1];\n      jj = COL_MAT_ROWNR(jj);\n      isnz[jj] = TRUE;\n    }\n  }\n  for(; i <= nsum; i++) {\n    j = abs(basisvector[i]);\n    if(j <= nrows)\n      slkpos[j] = i;\n  }\n\n  /* ...then set the corresponding slacks basic for row rank deficient positions */\n  for(j = 1; j <= nrows; j++) {\n    if(slkpos[j] == 0)\n      report(lp, SEVERE, \"guess_basis: Internal error\");\n    if(!isnz[j]) {\n      isnz[j] = TRUE;\n      i = slkpos[j];\n      swapINT(&basisvector[i], &basisvector[j]);\n      basisvector[j] = abs(basisvector[j]);\n    }\n  }\n\n  /* Adjust the non-basic indeces for the (proximal) bound state */\n  for(i = nrows+1, basisnr = basisvector+i; i <= nsum; i++, basisnr++) {\n    n = *basisnr;\n    if(n <= nrows) {\n      values[n] -= get_rh_lower(lp, n);\n      if(values[n] <= eps)\n        *basisnr = -(*basisnr);\n    }\n    else\n      if(values[n]-eps <= get_lowbo(lp, n-nrows))\n        *basisnr = -(*basisnr);\n  }\n\n/* Lastly normalize all basic variables to be coded as lower-bounded,\n   or effectively zero-based in the case of free variables. */\n  for(i = 1; i <= nrows; i++)\n    basisvector[i] = -abs(basisvector[i]);\n\n  /* Clean up and return status */\n  status = (MYBOOL) (error <= eps);\nFinish:\n  FREE(values);\n  FREE(violation);\n\n  return( status );\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_crash.h",
    "content": "\n#ifndef HEADER_lp_crash\n#define HEADER_lp_crash\n\n\n#include \"lp_types.h\"\n\n#define CRASH_SIMPLESCALE       /* Specify if we should use a simple absolute scaling threshold */\n\n#define CRASH_THRESHOLD  0.167\n#define CRASH_SPACER        10\n#define CRASH_WEIGHT     0.500\n\n\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\nSTATIC MYBOOL crash_basis(lprec *lp);\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* HEADER_lp_crash */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_explicit.h",
    "content": "#define HEADER_lp_report\n\n#include \"lp_lib.h\"\n\n#if defined LPSOLVEAPIFROMLPRECDEF\n# define LPSOLVEAPIFROMLPREC\n# define LPSOLVEAPIDEF\n#endif\n\n#if defined LPSOLVEAPIFROMLIBDEF\n# define LPSOLVEAPIFROMLIB\n# define LPSOLVEAPIDEF\n#endif\n\n#if !defined LPSOLVEAPIDEF\n# define LPSOLVEAPIDEF extern\n#endif\n\n/* entries for lp structure */\nLPSOLVEAPIDEF add_column_func               *_add_column;\nLPSOLVEAPIDEF add_columnex_func             *_add_columnex;\nLPSOLVEAPIDEF add_constraint_func           *_add_constraint;\nLPSOLVEAPIDEF add_constraintex_func         *_add_constraintex;\nLPSOLVEAPIDEF add_lag_con_func              *_add_lag_con;\nLPSOLVEAPIDEF add_SOS_func                  *_add_SOS;\nLPSOLVEAPIDEF column_in_lp_func             *_column_in_lp;\nLPSOLVEAPIDEF copy_lp_func                  *_copy_lp;\nLPSOLVEAPIDEF default_basis_func            *_default_basis;\nLPSOLVEAPIDEF del_column_func               *_del_column;\nLPSOLVEAPIDEF del_constraint_func           *_del_constraint;\nLPSOLVEAPIDEF delete_lp_func                *_delete_lp;\nLPSOLVEAPIDEF dualize_lp_func               *_dualize_lp;\nLPSOLVEAPIDEF free_lp_func                  *_free_lp;\nLPSOLVEAPIDEF get_anti_degen_func           *_get_anti_degen;\nLPSOLVEAPIDEF get_basis_func                *_get_basis;\nLPSOLVEAPIDEF get_basiscrash_func           *_get_basiscrash;\nLPSOLVEAPIDEF get_bb_depthlimit_func        *_get_bb_depthlimit;\nLPSOLVEAPIDEF get_bb_floorfirst_func        *_get_bb_floorfirst;\nLPSOLVEAPIDEF get_bb_rule_func              *_get_bb_rule;\nLPSOLVEAPIDEF get_bounds_tighter_func       *_get_bounds_tighter;\nLPSOLVEAPIDEF get_break_at_value_func       *_get_break_at_value;\nLPSOLVEAPIDEF get_col_name_func             *_get_col_name;\nLPSOLVEAPIDEF get_column_func               *_get_column;\nLPSOLVEAPIDEF get_columnex_func             *_get_columnex;\nLPSOLVEAPIDEF get_constr_type_func          *_get_constr_type;\nLPSOLVEAPIDEF get_constr_value_func         *_get_constr_value;\nLPSOLVEAPIDEF get_constraints_func          *_get_constraints;\nLPSOLVEAPIDEF get_dual_solution_func        *_get_dual_solution;\nLPSOLVEAPIDEF get_epsb_func                 *_get_epsb;\nLPSOLVEAPIDEF get_epsd_func                 *_get_epsd;\nLPSOLVEAPIDEF get_epsel_func                *_get_epsel;\nLPSOLVEAPIDEF get_epsint_func               *_get_epsint;\nLPSOLVEAPIDEF get_epsperturb_func           *_get_epsperturb;\nLPSOLVEAPIDEF get_epspivot_func             *_get_epspivot;\nLPSOLVEAPIDEF get_improve_func              *_get_improve;\nLPSOLVEAPIDEF get_infinite_func             *_get_infinite;\nLPSOLVEAPIDEF get_lambda_func               *_get_lambda;\nLPSOLVEAPIDEF get_lowbo_func                *_get_lowbo;\nLPSOLVEAPIDEF get_lp_index_func             *_get_lp_index;\nLPSOLVEAPIDEF get_lp_name_func              *_get_lp_name;\nLPSOLVEAPIDEF get_Lrows_func                *_get_Lrows;\nLPSOLVEAPIDEF get_mat_func                  *_get_mat;\nLPSOLVEAPIDEF get_mat_byindex_func          *_get_mat_byindex;\nLPSOLVEAPIDEF get_max_level_func            *_get_max_level;\nLPSOLVEAPIDEF get_maxpivot_func             *_get_maxpivot;\nLPSOLVEAPIDEF get_mip_gap_func              *_get_mip_gap;\nLPSOLVEAPIDEF get_multiprice_func           *_get_multiprice;\nLPSOLVEAPIDEF get_nameindex_func            *_get_nameindex;\nLPSOLVEAPIDEF get_Ncolumns_func             *_get_Ncolumns;\nLPSOLVEAPIDEF get_negrange_func             *_get_negrange;\nLPSOLVEAPIDEF get_nz_func                   *_get_nonzeros;\nLPSOLVEAPIDEF get_Norig_columns_func        *_get_Norig_columns;\nLPSOLVEAPIDEF get_Norig_rows_func           *_get_Norig_rows;\nLPSOLVEAPIDEF get_Nrows_func                *_get_Nrows;\nLPSOLVEAPIDEF get_obj_bound_func            *_get_obj_bound;\nLPSOLVEAPIDEF get_objective_func            *_get_objective;\nLPSOLVEAPIDEF get_orig_index_func           *_get_orig_index;\nLPSOLVEAPIDEF get_origcol_name_func         *_get_origcol_name;\nLPSOLVEAPIDEF get_origrow_name_func         *_get_origrow_name;\nLPSOLVEAPIDEF get_partialprice_func         *_get_partialprice;\nLPSOLVEAPIDEF get_pivoting_func             *_get_pivoting;\nLPSOLVEAPIDEF get_presolve_func             *_get_presolve;\nLPSOLVEAPIDEF get_presolveloops_func        *_get_presolveloops;\nLPSOLVEAPIDEF get_primal_solution_func      *_get_primal_solution;\nLPSOLVEAPIDEF get_print_sol_func            *_get_print_sol;\nLPSOLVEAPIDEF get_pseudocosts_func          *_get_pseudocosts;\nLPSOLVEAPIDEF get_ptr_constraints_func      *_get_ptr_constraints;\nLPSOLVEAPIDEF get_ptr_dual_solution_func    *_get_ptr_dual_solution;\nLPSOLVEAPIDEF get_ptr_lambda_func           *_get_ptr_lambda;\nLPSOLVEAPIDEF get_ptr_primal_solution_func  *_get_ptr_primal_solution;\nLPSOLVEAPIDEF get_ptr_sensitivity_obj_func  *_get_ptr_sensitivity_obj;\nLPSOLVEAPIDEF get_ptr_sensitivity_objex_func *_get_ptr_sensitivity_objex;\nLPSOLVEAPIDEF get_ptr_sensitivity_rhs_func  *_get_ptr_sensitivity_rhs;\nLPSOLVEAPIDEF get_ptr_variables_func        *_get_ptr_variables;\nLPSOLVEAPIDEF get_rh_func                   *_get_rh;\nLPSOLVEAPIDEF get_rh_range_func             *_get_rh_range;\nLPSOLVEAPIDEF get_row_func                  *_get_row;\nLPSOLVEAPIDEF get_rowex_func                *_get_rowex;\nLPSOLVEAPIDEF get_row_name_func             *_get_row_name;\nLPSOLVEAPIDEF get_scalelimit_func           *_get_scalelimit;\nLPSOLVEAPIDEF get_scaling_func              *_get_scaling;\nLPSOLVEAPIDEF get_sensitivity_obj_func      *_get_sensitivity_obj;\nLPSOLVEAPIDEF get_sensitivity_objex_func    *_get_sensitivity_objex;\nLPSOLVEAPIDEF get_sensitivity_rhs_func      *_get_sensitivity_rhs;\nLPSOLVEAPIDEF get_simplextype_func          *_get_simplextype;\nLPSOLVEAPIDEF get_solutioncount_func        *_get_solutioncount;\nLPSOLVEAPIDEF get_solutionlimit_func        *_get_solutionlimit;\nLPSOLVEAPIDEF get_status_func               *_get_status;\nLPSOLVEAPIDEF get_statustext_func           *_get_statustext;\nLPSOLVEAPIDEF get_timeout_func              *_get_timeout;\nLPSOLVEAPIDEF get_total_iter_func           *_get_total_iter;\nLPSOLVEAPIDEF get_total_nodes_func          *_get_total_nodes;\nLPSOLVEAPIDEF get_upbo_func                 *_get_upbo;\nLPSOLVEAPIDEF get_var_branch_func           *_get_var_branch;\nLPSOLVEAPIDEF get_var_dualresult_func       *_get_var_dualresult;\nLPSOLVEAPIDEF get_var_primalresult_func     *_get_var_primalresult;\nLPSOLVEAPIDEF get_var_priority_func         *_get_var_priority;\nLPSOLVEAPIDEF get_variables_func            *_get_variables;\nLPSOLVEAPIDEF get_verbose_func              *_get_verbose;\nLPSOLVEAPIDEF get_working_objective_func    *_get_working_objective;\nLPSOLVEAPIDEF guess_basis_func              *_guess_basis;\nLPSOLVEAPIDEF has_BFP_func                  *_has_BFP;\nLPSOLVEAPIDEF has_XLI_func                  *_has_XLI;\nLPSOLVEAPIDEF is_add_rowmode_func           *_is_add_rowmode;\nLPSOLVEAPIDEF is_anti_degen_func            *_is_anti_degen;\nLPSOLVEAPIDEF is_binary_func                *_is_binary;\nLPSOLVEAPIDEF is_break_at_first_func        *_is_break_at_first;\nLPSOLVEAPIDEF is_constr_type_func           *_is_constr_type;\nLPSOLVEAPIDEF is_debug_func                 *_is_debug;\nLPSOLVEAPIDEF is_feasible_func              *_is_feasible;\nLPSOLVEAPIDEF is_unbounded_func             *_is_unbounded;\nLPSOLVEAPIDEF is_infinite_func              *_is_infinite;\nLPSOLVEAPIDEF is_int_func                   *_is_int;\nLPSOLVEAPIDEF is_integerscaling_func        *_is_integerscaling;\nLPSOLVEAPIDEF is_lag_trace_func             *_is_lag_trace;\nLPSOLVEAPIDEF is_maxim_func                 *_is_maxim;\nLPSOLVEAPIDEF is_nativeBFP_func             *_is_nativeBFP;\nLPSOLVEAPIDEF is_nativeXLI_func             *_is_nativeXLI;\nLPSOLVEAPIDEF is_negative_func              *_is_negative;\nLPSOLVEAPIDEF is_piv_mode_func              *_is_piv_mode;\nLPSOLVEAPIDEF is_piv_rule_func              *_is_piv_rule;\nLPSOLVEAPIDEF is_presolve_func              *_is_presolve;\nLPSOLVEAPIDEF is_scalemode_func             *_is_scalemode;\nLPSOLVEAPIDEF is_scaletype_func             *_is_scaletype;\nLPSOLVEAPIDEF is_semicont_func              *_is_semicont;\nLPSOLVEAPIDEF is_SOS_var_func               *_is_SOS_var;\nLPSOLVEAPIDEF is_trace_func                 *_is_trace;\nLPSOLVEAPIDEF is_use_names_func             *_is_use_names;\nLPSOLVEAPIDEF lp_solve_version_func         *_lp_solve_version;\nLPSOLVEAPIDEF make_lp_func                  *_make_lp;\nLPSOLVEAPIDEF print_constraints_func        *_print_constraints;\nLPSOLVEAPIDEF print_debugdump_func          *_print_debugdump;\nLPSOLVEAPIDEF print_duals_func              *_print_duals;\nLPSOLVEAPIDEF print_lp_func                 *_print_lp;\nLPSOLVEAPIDEF print_objective_func          *_print_objective;\nLPSOLVEAPIDEF print_scales_func             *_print_scales;\nLPSOLVEAPIDEF print_solution_func           *_print_solution;\nLPSOLVEAPIDEF print_str_func                *_print_str;\nLPSOLVEAPIDEF print_tableau_func            *_print_tableau;\nLPSOLVEAPIDEF put_abortfunc_func            *_put_abortfunc;\nLPSOLVEAPIDEF put_bb_nodefunc_func          *_put_bb_nodefunc;\nLPSOLVEAPIDEF put_bb_branchfunc_func        *_put_bb_branchfunc;\nLPSOLVEAPIDEF put_logfunc_func              *_put_logfunc;\nLPSOLVEAPIDEF put_msgfunc_func              *_put_msgfunc;\nLPSOLVEAPIDEF read_LP_func                  *_read_LP;\nLPSOLVEAPIDEF read_MPS_func                 *_read_MPS;\nLPSOLVEAPIDEF read_XLI_func                 *_read_XLI;\nLPSOLVEAPIDEF read_params_func              *_read_params;\nLPSOLVEAPIDEF read_basis_func               *_read_basis;\nLPSOLVEAPIDEF reset_basis_func              *_reset_basis;\nLPSOLVEAPIDEF reset_params_func             *_reset_params;\nLPSOLVEAPIDEF reportfunc                    *_report;\nLPSOLVEAPIDEF resize_lp_func                *_resize_lp;\nLPSOLVEAPIDEF set_add_rowmode_func          *_set_add_rowmode;\nLPSOLVEAPIDEF set_anti_degen_func           *_set_anti_degen;\nLPSOLVEAPIDEF set_basisvar_func             *_set_basisvar;\nLPSOLVEAPIDEF set_basis_func                *_set_basis;\nLPSOLVEAPIDEF set_basiscrash_func           *_set_basiscrash;\nLPSOLVEAPIDEF set_bb_depthlimit_func        *_set_bb_depthlimit;\nLPSOLVEAPIDEF set_bb_floorfirst_func        *_set_bb_floorfirst;\nLPSOLVEAPIDEF set_bb_rule_func              *_set_bb_rule;\nLPSOLVEAPIDEF set_BFP_func                  *_set_BFP;\nLPSOLVEAPIDEF set_binary_func               *_set_binary;\nLPSOLVEAPIDEF set_bounds_func               *_set_bounds;\nLPSOLVEAPIDEF set_bounds_tighter_func       *_set_bounds_tighter;\nLPSOLVEAPIDEF set_break_at_first_func       *_set_break_at_first;\nLPSOLVEAPIDEF set_break_at_value_func       *_set_break_at_value;\nLPSOLVEAPIDEF set_column_func               *_set_column;\nLPSOLVEAPIDEF set_columnex_func             *_set_columnex;\nLPSOLVEAPIDEF set_col_name_func             *_set_col_name;\nLPSOLVEAPIDEF set_constr_type_func          *_set_constr_type;\nLPSOLVEAPIDEF set_debug_func                *_set_debug;\nLPSOLVEAPIDEF set_epsb_func                 *_set_epsb;\nLPSOLVEAPIDEF set_epsd_func                 *_set_epsd;\nLPSOLVEAPIDEF set_epsel_func                *_set_epsel;\nLPSOLVEAPIDEF set_epsint_func               *_set_epsint;\nLPSOLVEAPIDEF set_epslevel_func             *_set_epslevel;\nLPSOLVEAPIDEF set_epsperturb_func           *_set_epsperturb;\nLPSOLVEAPIDEF set_epspivot_func             *_set_epspivot;\nLPSOLVEAPIDEF set_unbounded_func            *_set_unbounded;\nLPSOLVEAPIDEF set_improve_func              *_set_improve;\nLPSOLVEAPIDEF set_infinite_func             *_set_infinite;\nLPSOLVEAPIDEF set_int_func                  *_set_int;\nLPSOLVEAPIDEF set_lag_trace_func            *_set_lag_trace;\nLPSOLVEAPIDEF set_lowbo_func                *_set_lowbo;\nLPSOLVEAPIDEF set_lp_name_func              *_set_lp_name;\nLPSOLVEAPIDEF set_mat_func                  *_set_mat;\nLPSOLVEAPIDEF set_maxim_func                *_set_maxim;\nLPSOLVEAPIDEF set_maxpivot_func             *_set_maxpivot;\nLPSOLVEAPIDEF set_minim_func                *_set_minim;\nLPSOLVEAPIDEF set_mip_gap_func              *_set_mip_gap;\nLPSOLVEAPIDEF set_multiprice_func           *_set_multiprice;\nLPSOLVEAPIDEF set_negrange_func             *_set_negrange;\nLPSOLVEAPIDEF set_obj_bound_func            *_set_obj_bound;\nLPSOLVEAPIDEF set_obj_fn_func               *_set_obj_fn;\nLPSOLVEAPIDEF set_obj_fnex_func             *_set_obj_fnex;\nLPSOLVEAPIDEF set_obj_func                  *_set_obj;\nLPSOLVEAPIDEF set_outputfile_func           *_set_outputfile;\nLPSOLVEAPIDEF set_outputstream_func         *_set_outputstream;\nLPSOLVEAPIDEF set_partialprice_func         *_set_partialprice;\nLPSOLVEAPIDEF set_pivoting_func             *_set_pivoting;\nLPSOLVEAPIDEF set_preferdual_func           *_set_preferdual;\nLPSOLVEAPIDEF set_presolve_func             *_set_presolve;\nLPSOLVEAPIDEF set_print_sol_func            *_set_print_sol;\nLPSOLVEAPIDEF set_pseudocosts_func          *_set_pseudocosts;\nLPSOLVEAPIDEF set_rh_func                   *_set_rh;\nLPSOLVEAPIDEF set_rh_range_func             *_set_rh_range;\nLPSOLVEAPIDEF set_rh_vec_func               *_set_rh_vec;\nLPSOLVEAPIDEF set_row_func                  *_set_row;\nLPSOLVEAPIDEF set_rowex_func                *_set_rowex;\nLPSOLVEAPIDEF set_row_name_func             *_set_row_name;\nLPSOLVEAPIDEF set_scalelimit_func           *_set_scalelimit;\nLPSOLVEAPIDEF set_scaling_func              *_set_scaling;\nLPSOLVEAPIDEF set_semicont_func             *_set_semicont;\nLPSOLVEAPIDEF set_sense_func                *_set_sense;\nLPSOLVEAPIDEF set_simplextype_func          *_set_simplextype;\nLPSOLVEAPIDEF set_solutionlimit_func        *_set_solutionlimit;\nLPSOLVEAPIDEF set_timeout_func              *_set_timeout;\nLPSOLVEAPIDEF set_trace_func                *_set_trace;\nLPSOLVEAPIDEF set_upbo_func                 *_set_upbo;\nLPSOLVEAPIDEF set_var_branch_func           *_set_var_branch;\nLPSOLVEAPIDEF set_var_weights_func          *_set_var_weights;\nLPSOLVEAPIDEF set_verbose_func              *_set_verbose;\nLPSOLVEAPIDEF set_XLI_func                  *_set_XLI;\nLPSOLVEAPIDEF solve_func                    *_solve;\nLPSOLVEAPIDEF str_add_column_func           *_str_add_column;\nLPSOLVEAPIDEF str_add_constraint_func       *_str_add_constraint;\nLPSOLVEAPIDEF str_add_lag_con_func          *_str_add_lag_con;\nLPSOLVEAPIDEF str_set_obj_fn_func           *_str_set_obj_fn;\nLPSOLVEAPIDEF str_set_rh_vec_func           *_str_set_rh_vec;\nLPSOLVEAPIDEF time_elapsed_func             *_time_elapsed;\nLPSOLVEAPIDEF unscale_func                  *_unscale;\nLPSOLVEAPIDEF write_lp_func                 *_write_lp;\nLPSOLVEAPIDEF write_LP_func                 *_write_LP;\nLPSOLVEAPIDEF write_mps_func                *_write_mps;\nLPSOLVEAPIDEF write_MPS_func                *_write_MPS;\nLPSOLVEAPIDEF write_freemps_func            *_write_freemps;\nLPSOLVEAPIDEF write_freeMPS_func            *_write_freeMPS;\nLPSOLVEAPIDEF write_XLI_func                *_write_XLI;\nLPSOLVEAPIDEF write_basis_func              *_write_basis;\nLPSOLVEAPIDEF write_params_func             *_write_params;\n\n#if defined LPSOLVEAPIFROMLPREC\n\nstatic int init_lpsolve(lprec *lp)\n{\n  _add_column = lp->add_column;\n  _add_columnex = lp->add_columnex;\n  _add_constraint = lp->add_constraint;\n  _add_constraintex = lp->add_constraintex;\n  _add_lag_con = lp->add_lag_con;\n  _add_SOS = lp->add_SOS;\n  _column_in_lp = lp->column_in_lp;\n  _copy_lp = lp->copy_lp;\n  _default_basis = lp->default_basis;\n  _del_column = lp->del_column;\n  _del_constraint = lp->del_constraint;\n  _delete_lp = lp->delete_lp;\n  _dualize_lp = lp->dualize_lp;\n  _free_lp = lp->free_lp;\n  _get_anti_degen = lp->get_anti_degen;\n  _get_basis = lp->get_basis;\n  _get_basiscrash = lp->get_basiscrash;\n  _get_bb_depthlimit = lp->get_bb_depthlimit;\n  _get_bb_floorfirst = lp->get_bb_floorfirst;\n  _get_bb_rule = lp->get_bb_rule;\n  _get_bounds_tighter = lp->get_bounds_tighter;\n  _get_break_at_value = lp->get_break_at_value;\n  _get_col_name = lp->get_col_name;\n  _get_columnex = lp->get_columnex;\n  _get_constr_type = lp->get_constr_type;\n  _get_constr_value = lp->get_constr_value;\n  _get_constraints = lp->get_constraints;\n  _get_dual_solution = lp->get_dual_solution;\n  _get_epsb = lp->get_epsb;\n  _get_epsd = lp->get_epsd;\n  _get_epsel = lp->get_epsel;\n  _get_epsint = lp->get_epsint;\n  _get_epsperturb = lp->get_epsperturb;\n  _get_epspivot = lp->get_epspivot;\n  _get_improve = lp->get_improve;\n  _get_infinite = lp->get_infinite;\n  _get_lambda = lp->get_lambda;\n  _get_lowbo = lp->get_lowbo;\n  _get_lp_index = lp->get_lp_index;\n  _get_lp_name = lp->get_lp_name;\n  _get_Lrows = lp->get_Lrows;\n  _get_mat = lp->get_mat;\n  _get_mat_byindex = lp->get_mat_byindex;\n  _get_max_level = lp->get_max_level;\n  _get_maxpivot = lp->get_maxpivot;\n  _get_mip_gap = lp->get_mip_gap;\n  _get_multiprice = lp->get_multiprice;\n  _get_nameindex = lp->get_nameindex;\n  _get_Ncolumns = lp->get_Ncolumns;\n  _get_negrange = lp->get_negrange;\n  _get_nonzeros = lp->get_nonzeros;\n  _get_Norig_columns = lp->get_Norig_columns;\n  _get_Norig_rows = lp->get_Norig_rows;\n  _get_Nrows = lp->get_Nrows;\n  _get_obj_bound = lp->get_obj_bound;\n  _get_objective = lp->get_objective;\n  _get_orig_index = lp->get_orig_index;\n  _get_origcol_name = lp->get_origcol_name;\n  _get_origrow_name = lp->get_origrow_name;\n  _get_partialprice = lp->get_partialprice;\n  _get_pivoting = lp->get_pivoting;\n  _get_presolve = lp->get_presolve;\n  _get_presolveloops = lp->get_presolveloops;\n  _get_primal_solution = lp->get_primal_solution;\n  _get_print_sol = lp->get_print_sol;\n  _get_pseudocosts = lp->get_pseudocosts;\n  _get_ptr_constraints = lp->get_ptr_constraints;\n  _get_ptr_dual_solution = lp->get_ptr_dual_solution;\n  _get_ptr_lambda = lp->get_ptr_lambda;\n  _get_ptr_primal_solution = lp->get_ptr_primal_solution;\n  _get_ptr_sensitivity_obj = lp->get_ptr_sensitivity_obj;\n  _get_ptr_sensitivity_objex = lp->get_ptr_sensitivity_objex;\n  _get_ptr_sensitivity_rhs = lp->get_ptr_sensitivity_rhs;\n  _get_ptr_variables = lp->get_ptr_variables;\n  _get_rh = lp->get_rh;\n  _get_rh_range = lp->get_rh_range;\n  _get_row = lp->get_row;\n  _get_rowex = lp->get_rowex;\n  _get_row_name = lp->get_row_name;\n  _get_scalelimit = lp->get_scalelimit;\n  _get_scaling = lp->get_scaling;\n  _get_sensitivity_obj = lp->get_sensitivity_obj;\n  _get_sensitivity_objex = lp->get_sensitivity_objex;\n  _get_sensitivity_rhs = lp->get_sensitivity_rhs;\n  _get_simplextype = lp->get_simplextype;\n  _get_solutioncount = lp->get_solutioncount;\n  _get_solutionlimit = lp->get_solutionlimit;\n  _get_status = lp->get_status;\n  _get_statustext = lp->get_statustext;\n  _get_timeout = lp->get_timeout;\n  _get_total_iter = lp->get_total_iter;\n  _get_total_nodes = lp->get_total_nodes;\n  _get_upbo = lp->get_upbo;\n  _get_var_branch = lp->get_var_branch;\n  _get_var_dualresult = lp->get_var_dualresult;\n  _get_var_primalresult = lp->get_var_primalresult;\n  _get_var_priority = lp->get_var_priority;\n  _get_variables = lp->get_variables;\n  _get_verbose = lp->get_verbose;\n  _get_working_objective = lp->get_working_objective;\n  _has_BFP = lp->has_BFP;\n  _has_XLI = lp->has_XLI;\n  _is_add_rowmode = lp->is_add_rowmode;\n  _is_anti_degen = lp->is_anti_degen;\n  _is_binary = lp->is_binary;\n  _is_break_at_first = lp->is_break_at_first;\n  _is_constr_type = lp->is_constr_type;\n  _is_debug = lp->is_debug;\n  _is_feasible = lp->is_feasible;\n  _is_unbounded = lp->is_unbounded;\n  _is_infinite = lp->is_infinite;\n  _is_int = lp->is_int;\n  _is_integerscaling = lp->is_integerscaling;\n  _is_lag_trace = lp->is_lag_trace;\n  _is_maxim = lp->is_maxim;\n  _is_nativeBFP = lp->is_nativeBFP;\n  _is_nativeXLI = lp->is_nativeXLI;\n  _is_negative = lp->is_negative;\n  _is_piv_mode = lp->is_piv_mode;\n  _is_piv_rule = lp->is_piv_rule;\n  _is_presolve = lp->is_presolve;\n  _is_scalemode = lp->is_scalemode;\n  _is_scaletype = lp->is_scaletype;\n  _is_semicont = lp->is_semicont;\n  _is_SOS_var = lp->is_SOS_var;\n  _is_trace = lp->is_trace;\n  _is_use_names = lp->is_use_names;\n  _lp_solve_version = lp->lp_solve_version;\n  _make_lp = lp->make_lp;\n  _print_constraints = lp->print_constraints;\n  _print_debugdump = lp->print_debugdump;\n  _print_duals = lp->print_duals;\n  _print_lp = lp->print_lp;\n  _print_objective = lp->print_objective;\n  _print_scales = lp->print_scales;\n  _print_solution = lp->print_solution;\n  _print_str = lp->print_str;\n  _print_tableau = lp->print_tableau;\n  _put_abortfunc = lp->put_abortfunc;\n  _put_bb_nodefunc = lp->put_bb_nodefunc;\n  _put_bb_branchfunc = lp->put_bb_branchfunc;\n  _put_logfunc = lp->put_logfunc;\n  _put_msgfunc = lp->put_msgfunc;\n  _read_LP = lp->read_LP;\n  _read_MPS = lp->read_MPS;\n  _read_XLI = lp->read_XLI;\n  _read_params = lp->read_params;\n  _read_basis = lp->read_basis;\n  _reset_basis = lp->reset_basis;\n  _reset_params = lp->reset_params;\n  _report = lp->report;\n  _resize_lp = lp->resize_lp;\n  _set_add_rowmode = lp->set_add_rowmode;\n  _set_anti_degen = lp->set_anti_degen;\n  _set_basisvar = lp->set_basisvar;\n  _set_basis = lp->set_basis;\n  _set_basiscrash = lp->set_basiscrash;\n  _set_bb_depthlimit = lp->set_bb_depthlimit;\n  _set_bb_floorfirst = lp->set_bb_floorfirst;\n  _set_bb_rule = lp->set_bb_rule;\n  _set_BFP = lp->set_BFP;\n  _set_binary = lp->set_binary;\n  _set_bounds = lp->set_bounds;\n  _set_bounds_tighter = lp->set_bounds_tighter;\n  _set_break_at_first = lp->set_break_at_first;\n  _set_break_at_value = lp->set_break_at_value;\n  _set_column = lp->set_column;\n  _set_columnex = lp->set_columnex;\n  _set_col_name = lp->set_col_name;\n  _set_constr_type = lp->set_constr_type;\n  _set_debug = lp->set_debug;\n  _set_epsb = lp->set_epsb;\n  _set_epsd = lp->set_epsd;\n  _set_epsel = lp->set_epsel;\n  _set_epsint = lp->set_epsint;\n  _set_epslevel = lp->set_epslevel;\n  _set_epsperturb = lp->set_epsperturb;\n  _set_epspivot = lp->set_epspivot;\n  _set_unbounded = lp->set_unbounded;\n  _set_improve = lp->set_improve;\n  _set_infinite = lp->set_infinite;\n  _set_int = lp->set_int;\n  _set_lag_trace = lp->set_lag_trace;\n  _set_lowbo = lp->set_lowbo;\n  _set_lp_name = lp->set_lp_name;\n  _set_mat = lp->set_mat;\n  _set_maxim = lp->set_maxim;\n  _set_maxpivot = lp->set_maxpivot;\n  _set_minim = lp->set_minim;\n  _set_mip_gap = lp->set_mip_gap;\n  _set_multiprice = lp->set_multiprice;\n  _set_negrange = lp->set_negrange;\n  _set_obj_bound = lp->set_obj_bound;\n  _set_obj_fn = lp->set_obj_fn;\n  _set_obj_fnex = lp->set_obj_fnex;\n  _set_obj = lp->set_obj;\n  _set_outputfile = lp->set_outputfile;\n  _set_outputstream = lp->set_outputstream;\n  _set_partialprice = lp->set_partialprice;\n  _set_pivoting = lp->set_pivoting;\n  _set_preferdual = lp->set_preferdual;\n  _set_presolve = lp->set_presolve;\n  _set_print_sol = lp->set_print_sol;\n  _set_pseudocosts = lp->set_pseudocosts;\n  _set_rh = lp->set_rh;\n  _set_rh_range = lp->set_rh_range;\n  _set_rh_vec = lp->set_rh_vec;\n  _set_row = lp->set_row;\n  _set_rowex = lp->set_rowex;\n  _set_row_name = lp->set_row_name;\n  _set_scalelimit = lp->set_scalelimit;\n  _set_scaling = lp->set_scaling;\n  _set_semicont = lp->set_semicont;\n  _set_sense = lp->set_sense;\n  _set_simplextype = lp->set_simplextype;\n  _set_solutionlimit = lp->set_solutionlimit;\n  _set_timeout = lp->set_timeout;\n  _set_trace = lp->set_trace;\n  _set_upbo = lp->set_upbo;\n  _set_var_branch = lp->set_var_branch;\n  _set_var_weights = lp->set_var_weights;\n  _set_verbose = lp->set_verbose;\n  _set_XLI = lp->set_XLI;\n  _solve = lp->solve;\n  _str_add_column = lp->str_add_column;\n  _str_add_constraint = lp->str_add_constraint;\n  _str_add_lag_con = lp->str_add_lag_con;\n  _str_set_obj_fn = lp->str_set_obj_fn;\n  _str_set_rh_vec = lp->str_set_rh_vec;\n  _time_elapsed = lp->time_elapsed;\n  _unscale = lp->unscale;\n  _write_lp = lp->write_lp;\n  _write_LP = lp->write_LP;\n  _write_mps = lp->write_mps;\n  _write_MPS = lp->write_MPS;\n  _write_freemps = lp->write_freemps;\n  _write_freeMPS = lp->write_freeMPS;\n  _write_XLI = lp->write_XLI;\n  _write_basis = lp->write_basis;\n  _write_params = lp->write_params;\n\n  return(TRUE);\n}\n\n#elif defined LPSOLVEAPIFROMLIB\n\n#ifdef WIN32\n#  include <windows.h>\n#else\n#  include <dlfcn.h>\n#endif\n\n#if defined WIN32\n# define hlpsolve HINSTANCE\n#else\n# define hlpsolve void *\n#endif\n\nstatic hlpsolve open_lpsolve_lib(char *filename)\n{\n  hlpsolve lpsolve;\n\n# if defined WIN32\n  /* Get a handle to the Windows DLL module. */\n  lpsolve = LoadLibrary(\"lpsolve55.dll\");\n# else\n  lpsolve = dlopen(\"liblpsolve55.so\", RTLD_LAZY);;\n# endif\n  return(lpsolve);\n}\n\nstatic int close_lpsolve_lib(hlpsolve lpsolve)\n{\n#ifdef WIN32\n  FreeLibrary(lpsolve);\n#else\n  dlclose(lpsolve);\n#endif\n\n  return(TRUE);\n}\n\nstatic int init_lpsolve(hlpsolve lpsolve)\n{\n# if defined WIN32\n#   define AddressOf GetProcAddress\n# else\n#   define AddressOf dlsym\n# endif\n\n  /* assign API functions to lp structure */\n  _add_column = (add_column_func *) AddressOf(lpsolve, \"add_column\");\n  _add_columnex = (add_columnex_func *) AddressOf(lpsolve, \"add_columnex\");\n  _add_constraint = (add_constraint_func *) AddressOf(lpsolve, \"add_constraint\");\n  _add_constraintex = (add_constraintex_func *) AddressOf(lpsolve, \"add_constraintex\");\n  _add_lag_con = (add_lag_con_func *) AddressOf(lpsolve, \"add_lag_con\");\n  _add_SOS = (add_SOS_func *) AddressOf(lpsolve, \"add_SOS\");\n  _column_in_lp = (column_in_lp_func *) AddressOf(lpsolve, \"column_in_lp\");\n  _copy_lp = (copy_lp_func *) AddressOf(lpsolve, \"copy_lp\");\n  _default_basis = (default_basis_func *) AddressOf(lpsolve, \"default_basis\");\n  _del_column = (del_column_func *) AddressOf(lpsolve, \"del_column\");\n  _del_constraint = (del_constraint_func *) AddressOf(lpsolve, \"del_constraint\");\n  _delete_lp = (delete_lp_func *) AddressOf(lpsolve, \"delete_lp\");\n  _dualize_lp = (dualize_lp_func *) AddressOf(lpsolve, \"dualize_lp\");\n  _free_lp = (free_lp_func *) AddressOf(lpsolve, \"free_lp\");\n  _get_anti_degen = (get_anti_degen_func *) AddressOf(lpsolve, \"get_anti_degen\");\n  _get_basis = (get_basis_func *) AddressOf(lpsolve, \"get_basis\");\n  _get_basiscrash = (get_basiscrash_func *) AddressOf(lpsolve, \"get_basiscrash\");\n  _get_bb_depthlimit = (get_bb_depthlimit_func *) AddressOf(lpsolve, \"get_bb_depthlimit\");\n  _get_bb_floorfirst = (get_bb_floorfirst_func *) AddressOf(lpsolve, \"get_bb_floorfirst\");\n  _get_bb_rule = (get_bb_rule_func *) AddressOf(lpsolve, \"get_bb_rule\");\n  _get_bounds_tighter = (get_bounds_tighter_func *) AddressOf(lpsolve, \"get_bounds_tighter\");\n  _get_break_at_value = (get_break_at_value_func *) AddressOf(lpsolve, \"get_break_at_value\");\n  _get_col_name = (get_col_name_func *) AddressOf(lpsolve, \"get_col_name\");\n  _get_column = (get_column_func *) AddressOf(lpsolve, \"get_column\");\n  _get_columnex = (get_columnex_func *) AddressOf(lpsolve, \"get_columnex\");\n  _get_constr_type = (get_constr_type_func *) AddressOf(lpsolve, \"get_constr_type\");\n  _get_constr_value = (get_constr_value_func *) AddressOf(lpsolve, \"get_constr_value\");\n  _get_constraints = (get_constraints_func *) AddressOf(lpsolve, \"get_constraints\");\n  _get_dual_solution = (get_dual_solution_func *) AddressOf(lpsolve, \"get_dual_solution\");\n  _get_epsb = (get_epsb_func *) AddressOf(lpsolve, \"get_epsb\");\n  _get_epsd = (get_epsd_func *) AddressOf(lpsolve, \"get_epsd\");\n  _get_epsel = (get_epsel_func *) AddressOf(lpsolve, \"get_epsel\");\n  _get_epsint = (get_epsint_func *) AddressOf(lpsolve, \"get_epsint\");\n  _get_epsperturb = (get_epsperturb_func *) AddressOf(lpsolve, \"get_epsperturb\");\n  _get_epspivot = (get_epspivot_func *) AddressOf(lpsolve, \"get_epspivot\");\n  _get_improve = (get_improve_func *) AddressOf(lpsolve, \"get_improve\");\n  _get_infinite = (get_infinite_func *) AddressOf(lpsolve, \"get_infinite\");\n  _get_lambda = (get_lambda_func *) AddressOf(lpsolve, \"get_lambda\");\n  _get_lowbo = (get_lowbo_func *) AddressOf(lpsolve, \"get_lowbo\");\n  _get_lp_index = (get_lp_index_func *) AddressOf(lpsolve, \"get_lp_index\");\n  _get_lp_name = (get_lp_name_func *) AddressOf(lpsolve, \"get_lp_name\");\n  _get_Lrows = (get_Lrows_func *) AddressOf(lpsolve, \"get_Lrows\");\n  _get_mat = (get_mat_func *) AddressOf(lpsolve, \"get_mat\");\n  _get_mat_byindex = (get_mat_byindex_func *) AddressOf(lpsolve, \"get_mat_byindex\");\n  _get_max_level = (get_max_level_func *) AddressOf(lpsolve, \"get_max_level\");\n  _get_maxpivot = (get_maxpivot_func *) AddressOf(lpsolve, \"get_maxpivot\");\n  _get_mip_gap = (get_mip_gap_func *) AddressOf(lpsolve, \"get_mip_gap\");\n  _get_multiprice = (get_multiprice_func *) AddressOf(lpsolve, \"get_multiprice\");\n  _get_nameindex = (get_nameindex_func *) AddressOf(lpsolve, \"get_nameindex\");\n  _get_Ncolumns = (get_Ncolumns_func *) AddressOf(lpsolve, \"get_Ncolumns\");\n  _get_negrange = (get_negrange_func *) AddressOf(lpsolve, \"get_negrange\");\n  _get_nonzeros = (get_nz_func *) AddressOf(lpsolve, \"get_nonzeros\");\n  _get_Norig_columns = (get_Norig_columns_func *) AddressOf(lpsolve, \"get_Norig_columns\");\n  _get_Norig_rows = (get_Norig_rows_func *) AddressOf(lpsolve, \"get_Norig_rows\");\n  _get_Nrows = (get_Nrows_func *) AddressOf(lpsolve, \"get_Nrows\");\n  _get_obj_bound = (get_obj_bound_func *) AddressOf(lpsolve, \"get_obj_bound\");\n  _get_objective = (get_objective_func *) AddressOf(lpsolve, \"get_objective\");\n  _get_orig_index = (get_orig_index_func *) AddressOf(lpsolve, \"get_orig_index\");\n  _get_origcol_name = (get_origcol_name_func *) AddressOf(lpsolve, \"get_origcol_name\");\n  _get_origrow_name = (get_origrow_name_func *) AddressOf(lpsolve, \"get_origrow_name\");\n  _get_partialprice = (get_partialprice_func *) AddressOf(lpsolve, \"get_partialprice\");\n  _get_pivoting = (get_pivoting_func *) AddressOf(lpsolve, \"get_pivoting\");\n  _get_presolve = (get_presolve_func *) AddressOf(lpsolve, \"get_presolve\");\n  _get_presolveloops = (get_presolveloops_func *) AddressOf(lpsolve, \"get_presolveloops\");\n  _get_primal_solution = (get_primal_solution_func *) AddressOf(lpsolve, \"get_primal_solution\");\n  _get_print_sol = (get_print_sol_func *) AddressOf(lpsolve, \"get_print_sol\");\n  _get_pseudocosts = (get_pseudocosts_func *) AddressOf(lpsolve, \"get_pseudocosts\");\n  _get_ptr_constraints = (get_ptr_constraints_func *) AddressOf(lpsolve, \"get_ptr_constraints\");\n  _get_ptr_dual_solution = (get_ptr_dual_solution_func *) AddressOf(lpsolve, \"get_ptr_dual_solution\");\n  _get_ptr_lambda = (get_ptr_lambda_func *) AddressOf(lpsolve, \"get_ptr_lambda\");\n  _get_ptr_primal_solution = (get_ptr_primal_solution_func *) AddressOf(lpsolve, \"get_ptr_primal_solution\");\n  _get_ptr_sensitivity_obj = (get_ptr_sensitivity_obj_func *) AddressOf(lpsolve, \"get_ptr_sensitivity_obj\");\n  _get_ptr_sensitivity_objex = (get_ptr_sensitivity_objex_func *) AddressOf(lpsolve, \"get_ptr_sensitivity_objex\");\n  _get_ptr_sensitivity_rhs = (get_ptr_sensitivity_rhs_func *) AddressOf(lpsolve, \"get_ptr_sensitivity_rhs\");\n  _get_ptr_variables = (get_ptr_variables_func *) AddressOf(lpsolve, \"get_ptr_variables\");\n  _get_rh = (get_rh_func *) AddressOf(lpsolve, \"get_rh\");\n  _get_rh_range = (get_rh_range_func *) AddressOf(lpsolve, \"get_rh_range\");\n  _get_row = (get_row_func *) AddressOf(lpsolve, \"get_row\");\n  _get_rowex = (get_rowex_func *) AddressOf(lpsolve, \"get_rowex\");\n  _get_row_name = (get_row_name_func *) AddressOf(lpsolve, \"get_row_name\");\n  _get_scalelimit = (get_scalelimit_func *) AddressOf(lpsolve, \"get_scalelimit\");\n  _get_scaling = (get_scaling_func *) AddressOf(lpsolve, \"get_scaling\");\n  _get_sensitivity_obj = (get_sensitivity_obj_func *) AddressOf(lpsolve, \"get_sensitivity_obj\");\n  _get_sensitivity_objex = (get_sensitivity_objex_func *) AddressOf(lpsolve, \"get_sensitivity_objex\");\n  _get_sensitivity_rhs = (get_sensitivity_rhs_func *) AddressOf(lpsolve, \"get_sensitivity_rhs\");\n  _get_simplextype = (get_simplextype_func *) AddressOf(lpsolve, \"get_simplextype\");\n  _get_solutioncount = (get_solutioncount_func *) AddressOf(lpsolve, \"get_solutioncount\");\n  _get_solutionlimit = (get_solutionlimit_func *) AddressOf(lpsolve, \"get_solutionlimit\");\n  _get_status = (get_status_func *) AddressOf(lpsolve, \"get_status\");\n  _get_statustext = (get_statustext_func *) AddressOf(lpsolve, \"get_statustext\");\n  _get_timeout = (get_timeout_func *) AddressOf(lpsolve, \"get_timeout\");\n  _get_total_iter = (get_total_iter_func *) AddressOf(lpsolve, \"get_total_iter\");\n  _get_total_nodes = (get_total_nodes_func *) AddressOf(lpsolve, \"get_total_nodes\");\n  _get_upbo = (get_upbo_func *) AddressOf(lpsolve, \"get_upbo\");\n  _get_var_branch = (get_var_branch_func *) AddressOf(lpsolve, \"get_var_branch\");\n  _get_var_dualresult = (get_var_dualresult_func *) AddressOf(lpsolve, \"get_var_dualresult\");\n  _get_var_primalresult = (get_var_primalresult_func *) AddressOf(lpsolve, \"get_var_primalresult\");\n  _get_var_priority = (get_var_priority_func *) AddressOf(lpsolve, \"get_var_priority\");\n  _get_variables = (get_variables_func *) AddressOf(lpsolve, \"get_variables\");\n  _get_verbose = (get_verbose_func *) AddressOf(lpsolve, \"get_verbose\");\n  _get_working_objective = (get_working_objective_func *) AddressOf(lpsolve, \"get_working_objective\");\n  _guess_basis = (guess_basis_func *) AddressOf(lpsolve, \"guess_basis\");\n  _has_BFP = (has_BFP_func *) AddressOf(lpsolve, \"has_BFP\");\n  _has_XLI = (has_XLI_func *) AddressOf(lpsolve, \"has_XLI\");\n  _is_add_rowmode = (is_add_rowmode_func *) AddressOf(lpsolve, \"is_add_rowmode\");\n  _is_anti_degen = (is_anti_degen_func *) AddressOf(lpsolve, \"is_anti_degen\");\n  _is_binary = (is_binary_func *) AddressOf(lpsolve, \"is_binary\");\n  _is_break_at_first = (is_break_at_first_func *) AddressOf(lpsolve, \"is_break_at_first\");\n  _is_constr_type = (is_constr_type_func *) AddressOf(lpsolve, \"is_constr_type\");\n  _is_debug = (is_debug_func *) AddressOf(lpsolve, \"is_debug\");\n  _is_feasible = (is_feasible_func *) AddressOf(lpsolve, \"is_feasible\");\n  _is_unbounded = (is_unbounded_func *) AddressOf(lpsolve, \"is_unbounded\");\n  _is_infinite = (is_infinite_func *) AddressOf(lpsolve, \"is_infinite\");\n  _is_int = (is_int_func *) AddressOf(lpsolve, \"is_int\");\n  _is_integerscaling = (is_integerscaling_func *) AddressOf(lpsolve, \"is_integerscaling\");\n  _is_lag_trace = (is_lag_trace_func *) AddressOf(lpsolve, \"is_lag_trace\");\n  _is_maxim = (is_maxim_func *) AddressOf(lpsolve, \"is_maxim\");\n  _is_nativeBFP = (is_nativeBFP_func *) AddressOf(lpsolve, \"is_nativeBFP\");\n  _is_nativeXLI = (is_nativeXLI_func *) AddressOf(lpsolve, \"is_nativeXLI\");\n  _is_negative = (is_negative_func *) AddressOf(lpsolve, \"is_negative\");\n  _is_piv_mode = (is_piv_mode_func *) AddressOf(lpsolve, \"is_piv_mode\");\n  _is_piv_rule = (is_piv_rule_func *) AddressOf(lpsolve, \"is_piv_rule\");\n  _is_presolve = (is_presolve_func *) AddressOf(lpsolve, \"is_presolve\");\n  _is_scalemode = (is_scalemode_func *) AddressOf(lpsolve, \"is_scalemode\");\n  _is_scaletype = (is_scaletype_func *) AddressOf(lpsolve, \"is_scaletype\");\n  _is_semicont = (is_semicont_func *) AddressOf(lpsolve, \"is_semicont\");\n  _is_SOS_var = (is_SOS_var_func *) AddressOf(lpsolve, \"is_SOS_var\");\n  _is_trace = (is_trace_func *) AddressOf(lpsolve, \"is_trace\");\n  _is_use_names = (is_use_names_func *) AddressOf(lpsolve, \"is_use_names\");\n  _lp_solve_version = (lp_solve_version_func *) AddressOf(lpsolve, \"lp_solve_version\");\n  _make_lp = (make_lp_func *) AddressOf(lpsolve, \"make_lp\");\n  _print_constraints = (print_constraints_func *) AddressOf(lpsolve, \"print_constraints\");\n  _print_debugdump = (print_debugdump_func *) AddressOf(lpsolve, \"print_debugdump\");\n  _print_duals = (print_duals_func *) AddressOf(lpsolve, \"print_duals\");\n  _print_lp = (print_lp_func *) AddressOf(lpsolve, \"print_lp\");\n  _print_objective = (print_objective_func *) AddressOf(lpsolve, \"print_objective\");\n  _print_scales = (print_scales_func *) AddressOf(lpsolve, \"print_scales\");\n  _print_solution = (print_solution_func *) AddressOf(lpsolve, \"print_solution\");\n  _print_str = (print_str_func *) AddressOf(lpsolve, \"print_str\");\n  _print_tableau = (print_tableau_func *) AddressOf(lpsolve, \"print_tableau\");\n  _put_abortfunc = (put_abortfunc_func *) AddressOf(lpsolve, \"put_abortfunc\");\n  _put_bb_nodefunc = (put_bb_nodefunc_func *) AddressOf(lpsolve, \"put_bb_nodefunc\");\n  _put_bb_branchfunc = (put_bb_branchfunc_func *) AddressOf(lpsolve, \"put_bb_branchfunc\");\n  _put_logfunc = (put_logfunc_func *) AddressOf(lpsolve, \"put_logfunc\");\n  _put_msgfunc = (put_msgfunc_func *) AddressOf(lpsolve, \"put_msgfunc\");\n  _read_LP = (read_LP_func *) AddressOf(lpsolve, \"read_LP\");\n  _read_MPS = (read_MPS_func *) AddressOf(lpsolve, \"read_MPS\");\n  _read_XLI = (read_XLI_func *) AddressOf(lpsolve, \"read_XLI\");\n  _read_params = (read_params_func *) AddressOf(lpsolve, \"read_params\");\n  _read_basis = (read_basis_func *) AddressOf(lpsolve, \"read_basis\");\n  _reset_basis = (reset_basis_func *) AddressOf(lpsolve, \"reset_basis\");\n  _reset_params = (reset_params_func *) AddressOf(lpsolve, \"reset_params\");\n  _report = (reportfunc *) AddressOf(lpsolve, \"report\");\n  _resize_lp = (resize_lp_func *) AddressOf(lpsolve, \"resize_lp\");\n  _set_add_rowmode = (set_add_rowmode_func *) AddressOf(lpsolve, \"set_add_rowmode\");\n  _set_anti_degen = (set_anti_degen_func *) AddressOf(lpsolve, \"set_anti_degen\");\n  _set_basisvar = (set_basisvar_func *) AddressOf(lpsolve, \"set_basisvar\");\n  _set_basis = (set_basis_func *) AddressOf(lpsolve, \"set_basis\");\n  _set_basiscrash = (set_basiscrash_func *) AddressOf(lpsolve, \"set_basiscrash\");\n  _set_bb_depthlimit = (set_bb_depthlimit_func *) AddressOf(lpsolve, \"set_bb_depthlimit\");\n  _set_bb_floorfirst = (set_bb_floorfirst_func *) AddressOf(lpsolve, \"set_bb_floorfirst\");\n  _set_bb_rule = (set_bb_rule_func *) AddressOf(lpsolve, \"set_bb_rule\");\n  _set_BFP = (set_BFP_func *) AddressOf(lpsolve, \"set_BFP\");\n  _set_binary = (set_binary_func *) AddressOf(lpsolve, \"set_binary\");\n  _set_bounds = (set_bounds_func *) AddressOf(lpsolve, \"set_bounds\");\n  _set_bounds_tighter = (set_bounds_tighter_func *) AddressOf(lpsolve, \"set_bounds_tighter\");\n  _set_break_at_first = (set_break_at_first_func *) AddressOf(lpsolve, \"set_break_at_first\");\n  _set_break_at_value = (set_break_at_value_func *) AddressOf(lpsolve, \"set_break_at_value\");\n  _set_column = (set_column_func *) AddressOf(lpsolve, \"set_column\");\n  _set_columnex = (set_columnex_func *) AddressOf(lpsolve, \"set_columnex\");\n  _set_col_name = (set_col_name_func *) AddressOf(lpsolve, \"set_col_name\");\n  _set_constr_type = (set_constr_type_func *) AddressOf(lpsolve, \"set_constr_type\");\n  _set_debug = (set_debug_func *) AddressOf(lpsolve, \"set_debug\");\n  _set_epsb = (set_epsb_func *) AddressOf(lpsolve, \"set_epsb\");\n  _set_epsd = (set_epsd_func *) AddressOf(lpsolve, \"set_epsd\");\n  _set_epsel = (set_epsel_func *) AddressOf(lpsolve, \"set_epsel\");\n  _set_epsint = (set_epsint_func *) AddressOf(lpsolve, \"set_epsint\");\n  _set_epslevel = (set_epslevel_func *) AddressOf(lpsolve, \"set_epslevel\");\n  _set_epsperturb = (set_epsperturb_func *) AddressOf(lpsolve, \"set_epsperturb\");\n  _set_epspivot = (set_epspivot_func *) AddressOf(lpsolve, \"set_epspivot\");\n  _set_unbounded = (set_unbounded_func *) AddressOf(lpsolve, \"set_unbounded\");\n  _set_improve = (set_improve_func *) AddressOf(lpsolve, \"set_improve\");\n  _set_infinite = (set_infinite_func *) AddressOf(lpsolve, \"set_infinite\");\n  _set_int = (set_int_func *) AddressOf(lpsolve, \"set_int\");\n  _set_lag_trace = (set_lag_trace_func *) AddressOf(lpsolve, \"set_lag_trace\");\n  _set_lowbo = (set_lowbo_func *) AddressOf(lpsolve, \"set_lowbo\");\n  _set_lp_name = (set_lp_name_func *) AddressOf(lpsolve, \"set_lp_name\");\n  _set_mat = (set_mat_func *) AddressOf(lpsolve, \"set_mat\");\n  _set_maxim = (set_maxim_func *) AddressOf(lpsolve, \"set_maxim\");\n  _set_maxpivot = (set_maxpivot_func *) AddressOf(lpsolve, \"set_maxpivot\");\n  _set_minim = (set_minim_func *) AddressOf(lpsolve, \"set_minim\");\n  _set_mip_gap = (set_mip_gap_func *) AddressOf(lpsolve, \"set_mip_gap\");\n  _set_multiprice = (set_multiprice_func *) AddressOf(lpsolve, \"set_multiprice\");\n  _set_negrange = (set_negrange_func *) AddressOf(lpsolve, \"set_negrange\");\n  _set_obj_bound = (set_obj_bound_func *) AddressOf(lpsolve, \"set_obj_bound\");\n  _set_obj_fn = (set_obj_fn_func *) AddressOf(lpsolve, \"set_obj_fn\");\n  _set_obj_fnex = (set_obj_fnex_func *) AddressOf(lpsolve, \"set_obj_fnex\");\n  _set_obj = (set_obj_func *) AddressOf(lpsolve, \"set_obj\");\n  _set_outputfile = (set_outputfile_func *) AddressOf(lpsolve, \"set_outputfile\");\n  _set_outputstream = (set_outputstream_func *) AddressOf(lpsolve, \"set_outputstream\");\n  _set_partialprice = (set_partialprice_func *) AddressOf(lpsolve, \"set_partialprice\");\n  _set_pivoting = (set_pivoting_func *) AddressOf(lpsolve, \"set_pivoting\");\n  _set_preferdual = (set_preferdual_func *) AddressOf(lpsolve, \"set_preferdual\");\n  _set_presolve = (set_presolve_func *) AddressOf(lpsolve, \"set_presolve\");\n  _set_print_sol = (set_print_sol_func *) AddressOf(lpsolve, \"set_print_sol\");\n  _set_pseudocosts = (set_pseudocosts_func *) AddressOf(lpsolve, \"set_pseudocosts\");\n  _set_rh = (set_rh_func *) AddressOf(lpsolve, \"set_rh\");\n  _set_rh_range = (set_rh_range_func *) AddressOf(lpsolve, \"set_rh_range\");\n  _set_rh_vec = (set_rh_vec_func *) AddressOf(lpsolve, \"set_rh_vec\");\n  _set_row = (set_row_func *) AddressOf(lpsolve, \"set_row\");\n  _set_rowex = (set_rowex_func *) AddressOf(lpsolve, \"set_rowex\");\n  _set_row_name = (set_row_name_func *) AddressOf(lpsolve, \"set_row_name\");\n  _set_scalelimit = (set_scalelimit_func *) AddressOf(lpsolve, \"set_scalelimit\");\n  _set_scaling = (set_scaling_func *) AddressOf(lpsolve, \"set_scaling\");\n  _set_semicont = (set_semicont_func *) AddressOf(lpsolve, \"set_semicont\");\n  _set_sense = (set_sense_func *) AddressOf(lpsolve, \"set_sense\");\n  _set_simplextype = (set_simplextype_func *) AddressOf(lpsolve, \"set_simplextype\");\n  _set_solutionlimit = (set_solutionlimit_func *) AddressOf(lpsolve, \"set_solutionlimit\");\n  _set_timeout = (set_timeout_func *) AddressOf(lpsolve, \"set_timeout\");\n  _set_trace = (set_trace_func *) AddressOf(lpsolve, \"set_trace\");\n  _set_upbo = (set_upbo_func *) AddressOf(lpsolve, \"set_upbo\");\n  _set_var_branch = (set_var_branch_func *) AddressOf(lpsolve, \"set_var_branch\");\n  _set_var_weights = (set_var_weights_func *) AddressOf(lpsolve, \"set_var_weights\");\n  _set_verbose = (set_verbose_func *) AddressOf(lpsolve, \"set_verbose\");\n  _set_XLI = (set_XLI_func *) AddressOf(lpsolve, \"set_XLI\");\n  _solve = (solve_func *) AddressOf(lpsolve, \"solve\");\n  _str_add_column = (str_add_column_func *) AddressOf(lpsolve, \"str_add_column\");\n  _str_add_constraint = (str_add_constraint_func *) AddressOf(lpsolve, \"str_add_constraint\");\n  _str_add_lag_con = (str_add_lag_con_func *) AddressOf(lpsolve, \"str_add_lag_con\");\n  _str_set_obj_fn = (str_set_obj_fn_func *) AddressOf(lpsolve, \"str_set_obj_fn\");\n  _str_set_rh_vec = (str_set_rh_vec_func *) AddressOf(lpsolve, \"str_set_rh_vec\");\n  _time_elapsed = (time_elapsed_func *) AddressOf(lpsolve, \"time_elapsed\");\n  _unscale = (unscale_func *) AddressOf(lpsolve, \"unscale\");\n  _write_lp = (write_lp_func *) AddressOf(lpsolve, \"write_lp\");\n  _write_LP = (write_LP_func *) AddressOf(lpsolve, \"write_LP\");\n  _write_mps = (write_mps_func *) AddressOf(lpsolve, \"write_mps\");\n  _write_MPS = (write_MPS_func *) AddressOf(lpsolve, \"write_MPS\");\n  _write_freemps = (write_freemps_func *) AddressOf(lpsolve, \"write_freemps\");\n  _write_freeMPS = (write_freeMPS_func *) AddressOf(lpsolve, \"write_freeMPS\");\n  _write_XLI = (write_XLI_func *) AddressOf(lpsolve, \"write_XLI\");\n  _write_basis = (write_basis_func *) AddressOf(lpsolve, \"write_basis\");\n  _write_params = (write_params_func *) AddressOf(lpsolve, \"write_params\");\n\n  return(TRUE);\n# undef AddressOf\n}\n\n#else\n#  error Either LPSOLVEAPIFROMLPREC or LPSOLVEAPIFROMLIB must be defined\n#endif\n\n#define add_column _add_column\n#define add_columnex _add_columnex\n#define add_constraint _add_constraint\n#define add_constraintex _add_constraintex\n#define add_lag_con _add_lag_con\n#define add_SOS _add_SOS\n#define column_in_lp _column_in_lp\n#define copy_lp _copy_lp\n#define default_basis _default_basis\n#define del_column _del_column\n#define del_constraint _del_constraint\n#define delete_lp _delete_lp\n#define dualize_lp _dualize_lp\n#define free_lp _free_lp\n#define get_anti_degen _get_anti_degen\n#define get_basis _get_basis\n#define get_basiscrash _get_basiscrash\n#define get_bb_depthlimit _get_bb_depthlimit\n#define get_bb_floorfirst _get_bb_floorfirst\n#define get_bb_rule _get_bb_rule\n#define get_bounds_tighter _get_bounds_tighter\n#define get_break_at_value _get_break_at_value\n#define get_col_name _get_col_name\n#define get_column _get_column\n#define get_columnex _get_columnex\n#define get_constr_type _get_constr_type\n#define get_constr_value _get_constr_value\n#define get_constraints _get_constraints\n#define get_dual_solution _get_dual_solution\n#define get_epsb _get_epsb\n#define get_epsd _get_epsd\n#define get_epsel _get_epsel\n#define get_epsint _get_epsint\n#define get_epsperturb _get_epsperturb\n#define get_epspivot _get_epspivot\n#define get_improve _get_improve\n#define get_infinite _get_infinite\n#define get_lambda _get_lambda\n#define get_lowbo _get_lowbo\n#define get_lp_index _get_lp_index\n#define get_lp_name _get_lp_name\n#define get_Lrows _get_Lrows\n#define get_mat _get_mat\n#define get_mat_byindex _get_mat_byindex\n#define get_max_level _get_max_level\n#define get_maxpivot _get_maxpivot\n#define get_mip_gap _get_mip_gap\n#define get_multiprice _get_multiprice\n#define get_nameindex _get_nameindex\n#define get_Ncolumns _get_Ncolumns\n#define get_negrange _get_negrange\n#define get_nonzeros _get_nonzeros\n#define get_Norig_columns _get_Norig_columns\n#define get_Norig_rows _get_Norig_rows\n#define get_Nrows _get_Nrows\n#define get_obj_bound _get_obj_bound\n#define get_objective _get_objective\n#define get_orig_index _get_orig_index\n#define get_origcol_name _get_origcol_name\n#define get_origrow_name _get_origrow_name\n#define get_partialprice _get_partialprice\n#define get_pivoting _get_pivoting\n#define get_presolve _get_presolve\n#define get_presolveloops _get_presolveloops\n#define get_primal_solution _get_primal_solution\n#define get_print_sol _get_print_sol\n#define get_pseudocosts _get_pseudocosts\n#define get_ptr_constraints _get_ptr_constraints\n#define get_ptr_dual_solution _get_ptr_dual_solution\n#define get_ptr_lambda _get_ptr_lambda\n#define get_ptr_primal_solution _get_ptr_primal_solution\n#define get_ptr_sensitivity_obj _get_ptr_sensitivity_obj\n#define get_ptr_sensitivity_objex _get_ptr_sensitivity_objex\n#define get_ptr_sensitivity_rhs _get_ptr_sensitivity_rhs\n#define get_ptr_variables _get_ptr_variables\n#define get_rh _get_rh\n#define get_rh_range _get_rh_range\n#define get_row _get_row\n#define get_rowex _get_rowex\n#define get_row_name _get_row_name\n#define get_scalelimit _get_scalelimit\n#define get_scaling _get_scaling\n#define get_sensitivity_obj _get_sensitivity_obj\n#define get_sensitivity_objex _get_sensitivity_objex\n#define get_sensitivity_rhs _get_sensitivity_rhs\n#define get_simplextype _get_simplextype\n#define get_solutioncount _get_solutioncount\n#define get_solutionlimit _get_solutionlimit\n#define get_status _get_status\n#define get_statustext _get_statustext\n#define get_timeout _get_timeout\n#define get_total_iter _get_total_iter\n#define get_total_nodes _get_total_nodes\n#define get_upbo _get_upbo\n#define get_var_branch _get_var_branch\n#define get_var_dualresult _get_var_dualresult\n#define get_var_primalresult _get_var_primalresult\n#define get_var_priority _get_var_priority\n#define get_variables _get_variables\n#define get_verbose _get_verbose\n#define get_working_objective _get_working_objective\n#define guess_basis _guess_basis\n#define has_BFP _has_BFP\n#define has_XLI _has_XLI\n#define is_add_rowmode _is_add_rowmode\n#define is_anti_degen _is_anti_degen\n#define is_binary _is_binary\n#define is_break_at_first _is_break_at_first\n#define is_constr_type _is_constr_type\n#define is_debug _is_debug\n#define is_feasible _is_feasible\n#define is_unbounded _is_unbounded\n#define is_infinite _is_infinite\n#define is_int _is_int\n#define is_integerscaling _is_integerscaling\n#define is_lag_trace _is_lag_trace\n#define is_maxim _is_maxim\n#define is_nativeBFP _is_nativeBFP\n#define is_nativeXLI _is_nativeXLI\n#define is_negative _is_negative\n#define is_piv_mode _is_piv_mode\n#define is_piv_rule _is_piv_rule\n#define is_presolve _is_presolve\n#define is_scalemode _is_scalemode\n#define is_scaletype _is_scaletype\n#define is_semicont _is_semicont\n#define is_SOS_var _is_SOS_var\n#define is_trace _is_trace\n#define is_use_names _is_use_names\n#define lp_solve_version _lp_solve_version\n#define make_lp _make_lp\n#define print_constraints _print_constraints\n#define print_debugdump _print_debugdump\n#define print_duals _print_duals\n#define print_lp _print_lp\n#define print_objective _print_objective\n#define print_scales _print_scales\n#define print_solution _print_solution\n#define print_str _print_str\n#define print_tableau _print_tableau\n#define put_abortfunc _put_abortfunc\n#define put_bb_nodefunc _put_bb_nodefunc\n#define put_bb_branchfunc _put_bb_branchfunc\n#define put_logfunc _put_logfunc\n#define put_msgfunc _put_msgfunc\n#define read_LP _read_LP\n#define read_MPS _read_MPS\n#define read_XLI _read_XLI\n#define read_params _read_params\n#define read_basis _read_basis\n#define reset_basis _reset_basis\n#define reset_params _reset_params\n#define report _report\n#define resize_lp _resize_lp\n#define set_add_rowmode _set_add_rowmode\n#define set_anti_degen _set_anti_degen\n#define set_basisvar _set_basisvar\n#define set_basis _set_basis\n#define set_basiscrash _set_basiscrash\n#define set_bb_depthlimit _set_bb_depthlimit\n#define set_bb_floorfirst _set_bb_floorfirst\n#define set_bb_rule _set_bb_rule\n#define set_BFP _set_BFP\n#define set_binary _set_binary\n#define set_bounds _set_bounds\n#define set_bounds_tighter _set_bounds_tighter\n#define set_break_at_first _set_break_at_first\n#define set_break_at_value _set_break_at_value\n#define set_column _set_column\n#define set_columnex _set_columnex\n#define set_col_name _set_col_name\n#define set_constr_type _set_constr_type\n#define set_debug _set_debug\n#define set_epsb _set_epsb\n#define set_epsd _set_epsd\n#define set_epsel _set_epsel\n#define set_epsint _set_epsint\n#define set_epslevel _set_epslevel\n#define set_epsperturb _set_epsperturb\n#define set_epspivot _set_epspivot\n#define set_unbounded _set_unbounded\n#define set_improve _set_improve\n#define set_infinite _set_infinite\n#define set_int _set_int\n#define set_lag_trace _set_lag_trace\n#define set_lowbo _set_lowbo\n#define set_lp_name _set_lp_name\n#define set_mat _set_mat\n#define set_maxim _set_maxim\n#define set_maxpivot _set_maxpivot\n#define set_minim _set_minim\n#define set_mip_gap _set_mip_gap\n#define set_multiprice _set_multiprice\n#define set_negrange _set_negrange\n#define set_obj_bound _set_obj_bound\n#define set_obj_fn _set_obj_fn\n#define set_obj_fnex _set_obj_fnex\n#define set_obj _set_obj\n#define set_outputfile _set_outputfile\n#define set_outputstream _set_outputstream\n#define set_partialprice _set_partialprice\n#define set_pivoting _set_pivoting\n#define set_preferdual _set_preferdual\n#define set_presolve _set_presolve\n#define set_print_sol _set_print_sol\n#define set_pseudocosts _set_pseudocosts\n#define set_rh _set_rh\n#define set_rh_range _set_rh_range\n#define set_rh_vec _set_rh_vec\n#define set_row _set_row\n#define set_rowex _set_rowex\n#define set_row_name _set_row_name\n#define set_scalelimit _set_scalelimit\n#define set_scaling _set_scaling\n#define set_semicont _set_semicont\n#define set_sense _set_sense\n#define set_simplextype _set_simplextype\n#define set_solutionlimit _set_solutionlimit\n#define set_timeout _set_timeout\n#define set_trace _set_trace\n#define set_upbo _set_upbo\n#define set_var_branch _set_var_branch\n#define set_var_weights _set_var_weights\n#define set_verbose _set_verbose\n#define set_XLI _set_XLI\n#define solve _solve\n#define str_add_column _str_add_column\n#define str_add_constraint _str_add_constraint\n#define str_add_lag_con _str_add_lag_con\n#define str_set_obj_fn _str_set_obj_fn\n#define str_set_rh_vec _str_set_rh_vec\n#define time_elapsed _time_elapsed\n#define unscale _unscale\n#define write_lp _write_lp\n#define write_LP _write_LP\n#define write_mps _write_mps\n#define write_MPS _write_MPS\n#define write_freemps _write_freemps\n#define write_freeMPS _write_freeMPS\n#define write_XLI _write_XLI\n#define write_basis _write_basis\n#define write_params _write_params\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_fortify.h",
    "content": "#ifdef FORTIFY\n\n#include \"fortify.h\"\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_lib.c",
    "content": "\n/* ----------------------------------------------------------------------------------\n   Main library of routines for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Michel Berkelaar (to v3.2)\n                   Kjell Eikland    (v4.0 and forward)\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      (see below)\n\n    Release notes:\n    v5.0.0  1 January 2004      First integrated and repackaged version.\n    v5.0.1  8 May 2004          Cumulative update since initial release;\n                                overall functionality scope maintained.\n    v5.1.0  20 July 2004        Reworked lp_solve throughout to fit new\n                                flexible matrix storage model.\n\n   ---------------------------------------------------------------------------------- */\n\n/* ---------------------------------------------------------------------------------- */\n/* Main library of routines for lp_solve                                              */\n/*----------------------------------------------------------------------------------- */\n#include <signal.h>\n#include <string.h>\n#include <float.h>\n#include <math.h>\n\n#if LoadInverseLib == TRUE\n  #ifdef WIN32\n    #include <windows.h>\n  #else\n    #include <dlfcn.h>\n  #endif\n#endif\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Include core and support modules via headers                                       */\n/* ---------------------------------------------------------------------------------- */\n#include \"lp_lib.h\"\n#include \"commonlib.h\"\n#include \"lp_utils.h\"\n#include \"lp_matrix.h\"\n#include \"lp_SOS.h\"\n#include \"lp_Hash.h\"\n#include \"lp_MPS.h\"\n#include \"lp_wlp.h\"\n#include \"lp_presolve.h\"\n#include \"lp_scale.h\"\n#include \"lp_simplex.h\"\n#include \"lp_mipbb.h\"\n#include \"lp_report.h\"\n#include \"lp_MDO.h\"\n#include \"lp_bit.h\"\n\n#if INVERSE_ACTIVE==INVERSE_LUMOD\n  #include \"lp_LUMOD.h\"\n#elif INVERSE_ACTIVE==INVERSE_LUSOL\n  #include \"lp_LUSOL.h\"\n#elif INVERSE_ACTIVE==INVERSE_GLPKLU\n  #include \"lp_glpkLU.h\"\n#elif INVERSE_ACTIVE==INVERSE_ETAPFI\n  #include \"lp_etaPFI.h\"\n#elif INVERSE_ACTIVE==INVERSE_LEGACY\n  #include \"lp_etaPFI.h\"\n#endif\n\n#if libBLAS > 0\n  #include \"myblas.h\"\n#endif\n\n#ifdef __BORLANDC__\n  #pragma hdrstop\n  #pragma package(smart_init)\n#endif\n\n/* ---------------------------------------------------------------------------------- */\n/* Include selected basis inverse routines and price norm scalars                     */\n/* ---------------------------------------------------------------------------------- */\n\n#include \"lp_price.h\"\n#include \"lp_pricePSE.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n#define sensrejvar TRUE\n\n/* Return lp_solve version information */\nvoid __WINAPI lp_solve_version(int *majorversion, int *minorversion, int *release, int *build)\n{\n  if(majorversion != NULL)\n    (*majorversion) = MAJORVERSION;\n  if(minorversion != NULL)\n    (*minorversion) = MINORVERSION;\n  if(release != NULL)\n    (*release) = RELEASE;\n  if(build != NULL)\n    (*build) = BUILD;\n}\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Various interaction elements                                                       */\n/* ---------------------------------------------------------------------------------- */\n\nMYBOOL __WINAPI userabort(lprec *lp, int message)\n{\n  MYBOOL abort;\n  int spx_save;\n\n  spx_save = lp->spx_status;\n  lp->spx_status = RUNNING;\n  if(yieldformessages(lp) != 0) {\n    lp->spx_status = USERABORT;\n    if(lp->bb_level > 0)\n      lp->bb_break = TRUE;\n  }\n  if((message > 0) && (lp->usermessage != NULL) && (lp->msgmask & message))\n    lp->usermessage(lp, lp->msghandle, message);\n  abort = (MYBOOL) (lp->spx_status != RUNNING);\n  if(!abort)\n    lp->spx_status = spx_save;\n  return( abort );\n}\n\nSTATIC int yieldformessages(lprec *lp)\n{\n  if((lp->sectimeout > 0) &&\n     ((timeNow()-lp->timestart)-(REAL)lp->sectimeout>0))\n    lp->spx_status = TIMEOUT;\n\n  if(lp->ctrlc != NULL) {\n    int retcode = lp->ctrlc(lp, lp->ctrlchandle);\n    /* Check for command to restart the B&B */\n    if((retcode == ACTION_RESTART) && (lp->bb_level > 1)) {\n      lp->bb_break = AUTOMATIC;\n      retcode = 0;\n    }\n    return(retcode);\n  }\n  else\n    return(0);\n}\n\nvoid __WINAPI set_outputstream(lprec *lp, FILE *stream)\n{\n  if((lp->outstream != NULL) && (lp->outstream != stdout)) {\n    if(lp->streamowned)\n      fclose(lp->outstream);\n    else\n      fflush(lp->outstream);\n  }\n  if(stream == NULL)\n    lp->outstream = stdout;\n  else\n    lp->outstream = stream;\n  lp->streamowned = FALSE;\n}\n\nMYBOOL __WINAPI set_outputfile(lprec *lp, char *filename)\n{\n  MYBOOL ok;\n  FILE   *output = stdout;\n\n  ok = (MYBOOL) ((filename == NULL) || (*filename == 0) || ((output = fopen(filename,\"w\")) != NULL));\n  if(ok) {\n    set_outputstream(lp, output);\n    lp->streamowned = (MYBOOL) ((filename != NULL) && (*filename != 0));\n#if 1\n    if((filename != NULL) && (*filename == 0))\n      lp->outstream = NULL;\n#endif\n  }\n  return(ok);\n}\n\nREAL __WINAPI time_elapsed(lprec *lp)\n{\n  if(lp->timeend > 0)\n    return(lp->timeend - lp->timestart);\n  else\n    return(timeNow() - lp->timestart);\n}\n\nvoid __WINAPI put_bb_nodefunc(lprec *lp, lphandleint_intfunc newnode, void *bbnodehandle)\n{\n  lp->bb_usenode = newnode;\n  lp->bb_nodehandle = bbnodehandle;         /* User-specified \"owner process ID\" */\n}\nvoid __WINAPI put_bb_branchfunc(lprec *lp, lphandleint_intfunc newbranch, void *bbbranchhandle)\n{\n  lp->bb_usebranch = newbranch;\n  lp->bb_branchhandle = bbbranchhandle;     /* User-specified \"owner process ID\" */\n}\nvoid __WINAPI put_abortfunc(lprec *lp, lphandle_intfunc newctrlc, void *ctrlchandle)\n{\n  lp->ctrlc = newctrlc;\n  lp->ctrlchandle = ctrlchandle;            /* User-specified \"owner process ID\" */\n}\nvoid __WINAPI put_logfunc(lprec *lp, lphandlestr_func newlog, void *loghandle)\n{\n  lp->writelog = newlog;\n  lp->loghandle = loghandle;                /* User-specified \"owner process ID\" */\n}\nvoid __WINAPI put_msgfunc(lprec *lp, lphandleint_func newmsg, void *msghandle, int mask)\n{\n  lp->usermessage = newmsg;\n  lp->msghandle = msghandle;                /* User-specified \"owner process ID\" */\n  lp->msgmask = mask;\n}\n\n\n/* ---------------------------------------------------------------------------------- */\n/* DLL exported function                                                              */\n/* ---------------------------------------------------------------------------------- */\nlprec * __WINAPI read_MPS(char *filename, int options)\n{\n  lprec *lp = NULL;\n  int typeMPS;\n\n  typeMPS = (options & ~0x07) >> 2;\n  if ((typeMPS & (MPSFIXED|MPSFREE)) == 0)\n    typeMPS |= MPSFIXED;\n  if(MPS_readfile(&lp, filename, typeMPS, options & 0x07))\n    return( lp );\n  else\n    return( NULL );\n}\nlprec * __WINAPI read_mps(FILE *filename, int options)\n{\n  lprec *lp = NULL;\n  int typeMPS;\n\n  typeMPS = (options & ~0x07) >> 2;\n  if ((typeMPS & (MPSFIXED|MPSFREE)) == 0)\n    typeMPS |= MPSFIXED;\n  if(MPS_readhandle(&lp, filename, typeMPS, options & 0x07))\n    return( lp );\n  else\n    return( NULL );\n}\n/* #if defined develop */\nlprec * __WINAPI read_mpsex(void *userhandle, read_modeldata_func read_modeldata, int options)\n{\n  lprec *lp = NULL;\n  int typeMPS;\n\n  typeMPS = (options & ~0x07) >> 2;\n  if ((typeMPS & (MPSFIXED|MPSFREE)) == 0)\n    typeMPS |= MPSFIXED;\n  if(MPS_readex(&lp, userhandle, read_modeldata, typeMPS, options & 0x07))\n    return( lp );\n  else\n    return( NULL );\n}\n/* #endif */\nlprec * __WINAPI read_freeMPS(char *filename, int options)\n{\n  lprec *lp = NULL;\n  int typeMPS;\n\n  typeMPS = (options & ~0x07) >> 2;\n  typeMPS &= ~MPSFIXED;\n  typeMPS |= MPSFREE;\n  if(MPS_readfile(&lp, filename, typeMPS, options & 0x07))\n    return( lp );\n  else\n    return( NULL );\n}\nlprec * __WINAPI read_freemps(FILE *filename, int options)\n{\n  lprec *lp = NULL;\n  int typeMPS;\n\n  typeMPS = (options & ~0x07) >> 2;\n  typeMPS &= ~MPSFIXED;\n  typeMPS |= MPSFREE;\n  if(MPS_readhandle(&lp, filename, typeMPS, options & 0x07))\n    return( lp );\n  else\n    return( NULL );\n}\n/* #if defined develop */\nlprec * __WINAPI read_freempsex(void *userhandle, read_modeldata_func read_modeldata, int options)\n{\n  lprec *lp = NULL;\n  int typeMPS;\n\n  typeMPS = (options & ~0x07) >> 2;\n  typeMPS &= ~MPSFIXED;\n  typeMPS |= MPSFREE;\n  if(MPS_readex(&lp, userhandle, read_modeldata, typeMPS, options & 0x07))\n    return( lp );\n  else\n    return( NULL );\n}\n/* #endif */\nMYBOOL __WINAPI write_mps(lprec *lp, char *filename)\n{\n  return(MPS_writefile(lp, MPSFIXED, filename));\n}\nMYBOOL __WINAPI write_MPS(lprec *lp, FILE *output)\n{\n  return(MPS_writehandle(lp, MPSFIXED, output));\n}\n\nMYBOOL __WINAPI write_freemps(lprec *lp, char *filename)\n{\n  return(MPS_writefile(lp, MPSFREE, filename));\n}\nMYBOOL __WINAPI write_freeMPS(lprec *lp, FILE *output)\n{\n  return(MPS_writehandle(lp, MPSFREE, output));\n}\n\nMYBOOL __WINAPI write_lp(lprec *lp, char *filename)\n{\n  return(LP_writefile(lp, filename));\n}\nMYBOOL __WINAPI write_LP(lprec *lp, FILE *output)\n{\n  return(LP_writehandle(lp, output));\n}\n#ifndef PARSER_LP\nMYBOOL __WINAPI LP_readhandle(lprec **lp, FILE *filename, int verbose, char *lp_name)\n{\n  return(FALSE);\n}\nlprec * __WINAPI read_lp(FILE *filename, int verbose, char *lp_name)\n{\n  return(NULL);\n}\nlprec * __WINAPI read_LP(char *filename, int verbose, char *lp_name)\n{\n  return(NULL);\n}\n#endif\n\nMYBOOL __WINAPI write_basis(lprec *lp, char *filename)\n{\n  int typeMPS = MPSFIXED;\n  return( MPS_writeBAS(lp, typeMPS, filename) );\n}\nMYBOOL __WINAPI read_basis(lprec *lp, char *filename, char *info)\n{\n  int typeMPS = MPSFIXED;\n\n  typeMPS = MPS_readBAS(lp, typeMPS, filename, info);\n\n  /* Code basis */\n  if(typeMPS) {\n    set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n    lp->basis_valid = TRUE;   /* Do not re-initialize basis on entering Solve */\n    lp->var_basic[0] = FALSE; /* Set to signal that this is a non-default basis */\n  }\n  return( (MYBOOL) typeMPS );\n}\n\n/* Write and read lp_solve parameters (placeholders) - see lp_params.c */\nvoid __WINAPI reset_params(lprec *lp)\n{\n  int mode;\n\n  lp->epsmachine        = DEF_EPSMACHINE;\n  lp->epsperturb        = DEF_PERTURB;\n  lp->lag_accept        = DEF_LAGACCEPT;\n  set_epslevel(lp, EPS_DEFAULT);\n\n  lp->tighten_on_set    = FALSE;\n  lp->negrange          = DEF_NEGRANGE;\n\n#if 0\n  lp->do_presolve       = PRESOLVE_ROWS | PRESOLVE_COLS | PRESOLVE_MERGEROWS |\n                          PRESOLVE_REDUCEGCD |\n                          PRESOLVE_ROWDOMINATE;\n#else\n  lp->do_presolve       = PRESOLVE_NONE;\n#endif\n  lp->presolveloops     = DEF_MAXPRESOLVELOOPS;\n\n  lp->scalelimit        = DEF_SCALINGLIMIT;\n  lp->scalemode         = SCALE_INTEGERS |\n#if 0\n                          SCALE_POWER2 |\n                          SCALE_LOGARITHMIC | SCALE_MEAN;\n#else\n                          SCALE_LINEAR | SCALE_GEOMETRIC |\n                          SCALE_EQUILIBRATE;\n#endif\n\n  lp->crashmode         = CRASH_NONE;\n\n  lp->max_pivots        = 0;\n  lp->simplex_strategy  = SIMPLEX_DUAL_PRIMAL;\n#define PricerDefaultOpt 1\n#if PricerDefaultOpt == 1\n  mode = PRICER_DEVEX;\n#elif PricerDefaultOpt == 2\n  mode = PRICER_STEEPESTEDGE;\n  mode |= PRICE_TRUENORMINIT;\n#else\n  mode = PRICER_STEEPESTEDGE | PRICE_PRIMALFALLBACK;\n#endif\n  mode |= PRICE_ADAPTIVE;\n#ifdef EnableRandomizedPricing\n  mode |= PRICE_RANDOMIZE;\n#endif\n  set_pivoting(lp, mode);\n\n  lp->improve           = IMPROVE_DEFAULT;\n  lp->anti_degen        = ANTIDEGEN_DEFAULT;\n\n  lp->bb_floorfirst     = BRANCH_AUTOMATIC;\n  lp->bb_rule           = NODE_DYNAMICMODE | NODE_GREEDYMODE | NODE_GAPSELECT |\n#if 1\n                          NODE_PSEUDOCOSTSELECT |\n#else\n                          NODE_PSEUDOFEASSELECT |\n#endif\n                          NODE_RCOSTFIXING;\n  lp->bb_limitlevel     = DEF_BB_LIMITLEVEL;\n  lp->bb_PseudoUpdates  = DEF_PSEUDOCOSTUPDATES;\n\n  lp->bb_heuristicOF    = my_chsign(is_maxim(lp), MAX(DEF_INFINITE, lp->infinite));\n  lp->bb_breakOF        = -lp->bb_heuristicOF;\n\n  lp->sectimeout        = 0;\n  lp->solutionlimit     = 1;\n\n  set_outputstream(lp, NULL);          /* Set to default output stream */\n  lp->verbose           = NORMAL;\n  lp->print_sol         = FALSE;       /* Can be FALSE, TRUE, AUTOMATIC (only non-zeros printed) */\n  lp->spx_trace         = FALSE;\n  lp->lag_trace         = FALSE;\n  lp->bb_trace          = FALSE;\n}\n\nvoid __WINAPI unscale(lprec *lp)\n{\n  undoscale(lp);\n}\nint __WINAPI solve(lprec *lp)\n{\n#if defined FPUexception\n  catchFPU(_EM_INVALID | _EM_ZERODIVIDE | _EM_OVERFLOW | _EM_UNDERFLOW);\n#endif\n\n  if(has_BFP(lp)) {\n    lp->solvecount++;\n    if(is_add_rowmode(lp))\n      set_add_rowmode(lp, FALSE);\n    return(lin_solve(lp));\n  }\n  else\n    return( NOBFP );\n}\nvoid __WINAPI print_lp(lprec *lp)\n{\n  REPORT_lp(lp);\n}\nvoid __WINAPI print_tableau(lprec *lp)\n{\n  REPORT_tableau(lp);\n}\nvoid __WINAPI print_objective(lprec *lp)\n{\n  REPORT_objective(lp);\n}\nvoid __WINAPI print_solution(lprec *lp, int columns)\n{\n  REPORT_solution(lp, columns);\n}\nvoid __WINAPI print_constraints(lprec *lp, int columns)\n{\n  REPORT_constraints(lp, columns);\n}\nvoid __WINAPI print_duals(lprec *lp)\n{\n  REPORT_duals(lp);\n}\nvoid __WINAPI print_scales(lprec *lp)\n{\n  REPORT_scales(lp);\n}\nMYBOOL __WINAPI print_debugdump(lprec *lp, char *filename)\n{\n  return(REPORT_debugdump(lp, filename, (MYBOOL) (get_total_iter(lp) > 0)));\n}\nvoid __WINAPI print_str(lprec *lp, char *str)\n{\n  report(lp, lp->verbose, \"%s\", str);\n}\n\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Parameter setting and retrieval functions                                          */\n/* ---------------------------------------------------------------------------------- */\n\nvoid __WINAPI set_timeout(lprec *lp, long sectimeout)\n{\n  lp->sectimeout = sectimeout;\n}\n\nlong __WINAPI get_timeout(lprec *lp)\n{\n  return(lp->sectimeout);\n}\n\nvoid __WINAPI set_verbose(lprec *lp, int verbose)\n{\n  lp->verbose = verbose;\n}\n\nint __WINAPI get_verbose(lprec *lp)\n{\n  return(lp->verbose);\n}\n\nvoid __WINAPI set_print_sol(lprec *lp, int print_sol)\n{\n  lp->print_sol = print_sol;\n}\n\nint __WINAPI get_print_sol(lprec *lp)\n{\n  return(lp->print_sol);\n}\n\nvoid __WINAPI set_debug(lprec *lp, MYBOOL debug)\n{\n  lp->bb_trace = debug;\n}\n\nMYBOOL __WINAPI is_debug(lprec *lp)\n{\n  return(lp->bb_trace);\n}\n\nvoid __WINAPI set_trace(lprec *lp, MYBOOL trace)\n{\n  lp->spx_trace = trace;\n}\n\nMYBOOL __WINAPI is_trace(lprec *lp)\n{\n  return(lp->spx_trace);\n}\n\nvoid __WINAPI set_anti_degen(lprec *lp, int anti_degen)\n{\n  lp->anti_degen = anti_degen;\n}\n\nint __WINAPI get_anti_degen(lprec *lp)\n{\n  return(lp->anti_degen);\n}\n\nMYBOOL __WINAPI is_anti_degen(lprec *lp, int testmask)\n{\n  return((MYBOOL) ((lp->anti_degen == testmask) || ((lp->anti_degen & testmask) != 0)));\n}\n\nvoid __WINAPI set_presolve(lprec *lp, int presolvemode, int maxloops)\n{\n  presolvemode &= ~PRESOLVE_REDUCEMIP; /* disable PRESOLVE_REDUCEMIP since it is very rare that this is effective, and also that it adds code complications and delayed presolve effects that are not captured properly. */\n  lp->do_presolve = presolvemode;\n  lp->presolveloops = maxloops;\n}\n\nint __WINAPI get_presolve(lprec *lp)\n{\n  return(lp->do_presolve);\n}\n\nint __WINAPI get_presolveloops(lprec *lp)\n{\n  if(lp->presolveloops < 0)\n    return(DEF_MAXPRESOLVELOOPS);\n  else if(lp->presolveloops == 0)\n    return(MAXINT32);\n  else\n    return(lp->presolveloops);\n}\n\nMYBOOL __WINAPI is_presolve(lprec *lp, int testmask)\n{\n  return((MYBOOL) ((lp->do_presolve == testmask) || ((lp->do_presolve & testmask) != 0)));\n}\n\nvoid __WINAPI set_maxpivot(lprec *lp, int maxpivot)\n{\n  lp->max_pivots = maxpivot;\n}\n\nint __WINAPI get_maxpivot(lprec *lp)\n{\n  return( lp->bfp_pivotmax(lp) );\n}\n\nvoid __WINAPI set_bb_rule(lprec *lp, int bb_rule)\n{\n  lp->bb_rule = bb_rule;\n}\n\nint __WINAPI get_bb_rule(lprec *lp)\n{\n  return(lp->bb_rule);\n}\n\n/* INLINE */ MYBOOL is_bb_rule(lprec *lp, int bb_rule)\n{\n  return( (MYBOOL) ((lp->bb_rule & NODE_STRATEGYMASK) == bb_rule) );\n}\n\n/* INLINE */ MYBOOL is_bb_mode(lprec *lp, int bb_mask)\n{\n  return( (MYBOOL) ((lp->bb_rule & bb_mask) > 0) );\n}\n\nvoid __WINAPI set_action(int *actionvar, int actionmask)\n{\n  *actionvar |= actionmask;\n}\n\nvoid __WINAPI clear_action(int *actionvar, int actionmask)\n{\n  *actionvar &= ~actionmask;\n}\n\nMYBOOL __WINAPI is_action(int actionvar, int testmask)\n{\n  return( (MYBOOL) ((actionvar & testmask) != 0) );\n}\n\nvoid __WINAPI set_bb_depthlimit(lprec *lp, int bb_maxlevel)\n{\n  lp->bb_limitlevel = bb_maxlevel;\n}\n\nint __WINAPI get_bb_depthlimit(lprec *lp)\n{\n  return(lp->bb_limitlevel);\n}\n\nvoid __WINAPI set_obj_bound(lprec *lp, REAL bb_heuristicOF)\n{\n  lp->bb_heuristicOF = bb_heuristicOF;\n}\n\nREAL __WINAPI get_obj_bound(lprec *lp)\n{\n  return(lp->bb_heuristicOF);\n}\n\nvoid __WINAPI set_mip_gap(lprec *lp, MYBOOL absolute, REAL mip_gap)\n{\n  if(absolute)\n    lp->mip_absgap = mip_gap;\n  else\n    lp->mip_relgap = mip_gap;\n}\n\nREAL __WINAPI get_mip_gap(lprec *lp, MYBOOL absolute)\n{\n  if(absolute)\n    return(lp->mip_absgap);\n  else\n    return(lp->mip_relgap);\n}\n\nMYBOOL __WINAPI set_var_branch(lprec *lp, int colnr, int branch_mode)\n{\n  if(colnr > lp->columns || colnr < 1) {\n    report(lp, IMPORTANT, \"set_var_branch: Column %d out of range\\n\", colnr);\n    return( FALSE );\n  }\n\n  if(lp->bb_varbranch == NULL) {\n    int i;\n    if(branch_mode == BRANCH_DEFAULT)\n      return( TRUE );\n    allocMYBOOL(lp, &lp->bb_varbranch, lp->columns_alloc, FALSE);\n    for(i = 0; i < lp->columns; i++)\n      lp->bb_varbranch[i] = BRANCH_DEFAULT;\n  }\n  lp->bb_varbranch[colnr - 1] = (MYBOOL) branch_mode;\n  return( TRUE );\n}\n\nint __WINAPI get_var_branch(lprec *lp, int colnr)\n{\n  if(colnr > lp->columns || colnr < 1) {\n    report(lp, IMPORTANT, \"get_var_branch: Column %d out of range\\n\", colnr);\n    return(lp->bb_floorfirst);\n  }\n\n  if(lp->bb_varbranch == NULL)\n    return(lp->bb_floorfirst);\n  if(lp->bb_varbranch[colnr - 1] == BRANCH_DEFAULT)\n    return(lp->bb_floorfirst);\n  else\n    return(lp->bb_varbranch[colnr - 1]);\n}\n\nstatic void set_infiniteex(lprec *lp, REAL infinite, MYBOOL init)\n{\n  int i;\n\n  infinite = fabs(infinite);\n  if((init) || is_infinite(lp, lp->bb_heuristicOF))\n    lp->bb_heuristicOF = my_chsign(is_maxim(lp), infinite);\n  if((init) || is_infinite(lp, lp->bb_breakOF))\n    lp->bb_breakOF = my_chsign(is_maxim(lp), -infinite);\n  for(i = 0; i <= lp->sum; i++) {\n    if((!init) && is_infinite(lp, lp->orig_lowbo[i]))\n      lp->orig_lowbo[i] = -infinite;\n    if((init) || is_infinite(lp, lp->orig_upbo[i]))\n      lp->orig_upbo[i] = infinite;\n  }\n  lp->infinite = infinite;\n}\n\n\nMYBOOL __WINAPI is_infinite(lprec *lp, REAL value)\n{\n#if 1\n  return( (MYBOOL) (fabs(value) >= lp->infinite) );\n#else\n  if(fabs(value) >= lp->infinite)\n    return( TRUE );\n  else\n    return( FALSE );\n#endif\n}\n\nvoid __WINAPI set_infinite(lprec *lp, REAL infinite)\n{\n  set_infiniteex(lp, infinite, FALSE);\n}\n\nREAL __WINAPI get_infinite(lprec *lp)\n{\n  return(lp->infinite);\n}\n\nvoid __WINAPI set_epsperturb(lprec *lp, REAL epsperturb)\n{\n  lp->epsperturb = epsperturb;\n}\n\nREAL __WINAPI get_epsperturb(lprec *lp)\n{\n  return(lp->epsperturb);\n}\n\nvoid __WINAPI set_epspivot(lprec *lp, REAL epspivot)\n{\n  lp->epspivot = epspivot;\n}\n\nREAL __WINAPI get_epspivot(lprec *lp)\n{\n  return(lp->epspivot);\n}\n\nvoid __WINAPI set_epsint(lprec *lp, REAL epsint)\n{\n  lp->epsint = epsint;\n}\n\nREAL __WINAPI get_epsint(lprec *lp)\n{\n  return(lp->epsint);\n}\n\nvoid __WINAPI set_epsb(lprec *lp, REAL epsb)\n{\n  lp->epsprimal = MAX(epsb, lp->epsmachine);\n}\n\nREAL __WINAPI get_epsb(lprec *lp)\n{\n  return(lp->epsprimal);\n}\n\nvoid __WINAPI set_epsd(lprec *lp, REAL epsd)\n{\n  lp->epsdual = MAX(epsd, lp->epsmachine); /* Mainly used as tolerance for reduced cost */\n}\n\nREAL __WINAPI get_epsd(lprec *lp)\n{\n  return(lp->epsdual);\n}\n\nvoid __WINAPI set_epsel(lprec *lp, REAL epsel)\n{\n  lp->epsvalue = MAX(epsel, lp->epsmachine);\n}\n\nREAL __WINAPI get_epsel(lprec *lp)\n{\n  return(lp->epsvalue);\n}\n\nMYBOOL __WINAPI set_epslevel(lprec *lp, int epslevel)\n{\n  REAL SPX_RELAX, MIP_RELAX;\n\n  switch(epslevel) {\n    case EPS_TIGHT:  SPX_RELAX = 1;\n                      MIP_RELAX = 1;\n                      break;\n    case EPS_MEDIUM: SPX_RELAX = 10;\n                      MIP_RELAX = 1;\n                      break;\n    case EPS_LOOSE:  SPX_RELAX = 100;\n                      MIP_RELAX = 10;\n                      break;\n    case EPS_BAGGY:  SPX_RELAX = 1000;\n                      MIP_RELAX = 100;\n                      break;\n    default:        return( FALSE );\n  }\n  lp->epsvalue   = SPX_RELAX*DEF_EPSVALUE;\n  lp->epsprimal  = SPX_RELAX*DEF_EPSPRIMAL;\n  lp->epsdual    = SPX_RELAX*DEF_EPSDUAL;\n  lp->epspivot   = SPX_RELAX*DEF_EPSPIVOT;\n  lp->epssolution= MIP_RELAX*DEF_EPSSOLUTION;\n  lp->epsint     = MIP_RELAX*DEF_EPSINT;\n  lp->mip_absgap = MIP_RELAX*DEF_MIP_GAP;\n  lp->mip_relgap = MIP_RELAX*DEF_MIP_GAP;\n\n  return( TRUE );\n}\n\nvoid __WINAPI set_scaling(lprec *lp, int scalemode)\n{\n  lp->scalemode = scalemode;\n}\n\nint __WINAPI get_scaling(lprec *lp)\n{\n  return(lp->scalemode);\n}\n\nMYBOOL __WINAPI is_scalemode(lprec *lp, int testmask)\n{\n  return((MYBOOL) ((lp->scalemode & testmask) != 0));\n}\n\nMYBOOL __WINAPI is_scaletype(lprec *lp, int scaletype)\n{\n  int testtype;\n\n  testtype = lp->scalemode & SCALE_MAXTYPE;\n  return((MYBOOL) (scaletype == testtype));\n}\n\nvoid __WINAPI set_scalelimit(lprec *lp, REAL scalelimit)\n/* Set the relative scaling convergence criterion for the active scaling mode;\n   the integer part specifies the maximum number of iterations (default = 5). */\n{\n  lp->scalelimit = fabs(scalelimit);\n}\n\nREAL __WINAPI get_scalelimit(lprec *lp)\n{\n  return(lp->scalelimit);\n}\n\nMYBOOL __WINAPI is_integerscaling(lprec *lp)\n{\n  return(is_scalemode(lp, SCALE_INTEGERS));\n}\n\nvoid __WINAPI set_improve(lprec *lp, int improve)\n{\n  lp->improve = improve;\n}\n\nint __WINAPI get_improve(lprec *lp)\n{\n  return(lp->improve);\n}\n\nvoid __WINAPI set_lag_trace(lprec *lp, MYBOOL lag_trace)\n{\n  lp->lag_trace = lag_trace;\n}\n\nMYBOOL __WINAPI is_lag_trace(lprec *lp)\n{\n  return(lp->lag_trace);\n}\n\nvoid __WINAPI set_pivoting(lprec *lp, int pivoting)\n{\n  /* Set new pivoting strategy */\n  lp->piv_strategy = pivoting;\n  report(lp, DETAILED, \"set_pivoting: Pricing strategy set to '%s'\\n\",\n                       get_str_piv_rule(get_piv_rule(lp)));\n}\n\nint __WINAPI get_pivoting(lprec *lp)\n{\n  return( lp->piv_strategy );\n}\n\n/* INLINE */ int get_piv_rule(lprec *lp)\n{\n  return( (lp->piv_strategy | PRICE_STRATEGYMASK) ^ PRICE_STRATEGYMASK );\n}\n\nSTATIC char *get_str_piv_rule(int rule)\n{\n  static char *pivotText[PRICER_LASTOPTION+1] =\n  {\"Bland first index\", \"Dantzig\", \"Devex\", \"Steepest Edge\"};\n\n  return( pivotText[rule] );\n}\n\nMYBOOL __WINAPI is_piv_rule(lprec *lp, int rule)\n{\n  return( (MYBOOL) (get_piv_rule(lp) == rule) );\n}\n\nMYBOOL __WINAPI is_piv_mode(lprec *lp, int testmask)\n{\n  return((MYBOOL) (((testmask & PRICE_STRATEGYMASK) != 0) &&\n                   ((lp->piv_strategy & testmask) != 0)));\n}\n\nvoid __WINAPI set_break_at_first(lprec *lp, MYBOOL break_at_first)\n{\n  lp->bb_breakfirst = break_at_first;\n}\n\nMYBOOL __WINAPI is_break_at_first(lprec *lp)\n{\n  return(lp->bb_breakfirst);\n}\n\nvoid __WINAPI set_bb_floorfirst(lprec *lp, int bb_floorfirst)\n{\n  lp->bb_floorfirst = (MYBOOL) bb_floorfirst;\n}\n\nint __WINAPI get_bb_floorfirst(lprec *lp)\n{\n  return(lp->bb_floorfirst);\n}\n\nvoid __WINAPI set_break_at_value(lprec *lp, REAL break_at_value)\n{\n  lp->bb_breakOF = break_at_value;\n}\n\nREAL __WINAPI get_break_at_value(lprec *lp)\n{\n  return(lp->bb_breakOF);\n}\n\nvoid __WINAPI set_negrange(lprec *lp, REAL negrange)\n{\n  if(negrange <= 0)\n    lp->negrange = negrange;\n  else\n    lp->negrange = 0.0;\n}\n\nREAL __WINAPI get_negrange(lprec *lp)\n{\n  return(lp->negrange);\n}\n\nint __WINAPI get_max_level(lprec *lp)\n{\n  return(lp->bb_maxlevel);\n}\n\nCOUNTER __WINAPI get_total_nodes(lprec *lp)\n{\n  return(lp->bb_totalnodes);\n}\n\nCOUNTER __WINAPI get_total_iter(lprec *lp)\n{\n  return(lp->total_iter + lp->current_iter);\n}\n\nREAL __WINAPI get_objective(lprec *lp)\n{\n  if(lp->spx_status == OPTIMAL)\n    ;\n  else if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_objective: Not a valid basis\\n\");\n    return(0.0);\n  }\n\n  return( lp->best_solution[0] );\n}\n\nint __WINAPI get_nonzeros(lprec *lp)\n{\n  return( mat_nonzeros(lp->matA) );\n}\n\nMYBOOL __WINAPI set_mat(lprec *lp, int rownr, int colnr, REAL value)\n{\n  if((rownr < 0) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"set_mat: Row %d out of range\\n\", rownr);\n    return( FALSE );\n  }\n  if((colnr < 1) || (colnr > lp->columns)) {\n    report(lp, IMPORTANT, \"set_mat: Column %d out of range\\n\", colnr);\n    return( FALSE );\n  }\n\n#ifdef DoMatrixRounding\n  if(rownr == 0)\n    value = roundToPrecision(value, lp->matA->epsvalue);\n#endif\n  value = scaled_mat(lp, value, rownr, colnr);\n  if(rownr == 0) {\n    lp->orig_obj[colnr] = my_chsign(is_chsign(lp, rownr), value);\n    return( TRUE );\n  }\n  else\n    return( mat_setvalue(lp->matA, rownr, colnr, value, FALSE) );\n}\n\nREAL __WINAPI get_working_objective(lprec *lp)\n{\n  REAL value = 0.0;\n\n  if(!lp->basis_valid)\n    report(lp, CRITICAL, \"get_working_objective: Not a valid basis\\n\");\n  else if((lp->spx_status == RUNNING) && (lp->solutioncount == 0))\n    value = my_chsign(!is_maxim(lp), lp->rhs[0]);\n  else\n    value = lp->solution[0];\n\n  return(value);\n}\n\nREAL __WINAPI get_var_primalresult(lprec *lp, int index)\n{\n  if((index < 0) || (index > lp->presolve_undo->orig_sum)) {\n    report(lp, IMPORTANT, \"get_var_primalresult: Index %d out of range\\n\", index);\n    return( 0.0 );\n  }\n  if((lp->do_presolve & PRESOLVE_LASTMASKMODE) != PRESOLVE_NONE)\n    return( lp->full_solution[index] );\n  else\n    return( lp->best_solution[index] );\n}\n\nREAL __WINAPI get_var_dualresult(lprec *lp, int index)\n{\n  REAL *duals;\n\n  if((index < 0) || (index > lp->presolve_undo->orig_sum)) {\n    report(lp, IMPORTANT, \"get_var_dualresult: Index %d out of range\\n\", index);\n    return( 0.0 );\n  }\n\n  if(index == 0)\n    return( lp->best_solution[0] );\n\n  /* Make sure we actually have dual information available */\n  if(!get_ptr_sensitivity_rhs(lp, &duals, NULL, NULL))\n    return( 0.0 );\n  else\n    duals = ((lp->full_duals == NULL) ? lp->duals : lp->full_duals);\n  return( duals[index] );\n}\n\nMYBOOL __WINAPI get_variables(lprec *lp, REAL *var)\n{\n  if(lp->spx_status == OPTIMAL)\n    ;\n  else if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_variables: Not a valid basis\\n\");\n    return(FALSE);\n  }\n\n  MEMCOPY(var, lp->best_solution + (1 + lp->rows), lp->columns);\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_ptr_variables(lprec *lp, REAL **var)\n{\n  if(lp->spx_status == OPTIMAL)\n    ;\n  else if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_ptr_variables: Not a valid basis\\n\");\n    return(FALSE);\n  }\n\n  if(var != NULL)\n   *var = lp->best_solution + (1 + lp->rows);\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_constraints(lprec *lp, REAL *constr)\n{\n  if(lp->spx_status == OPTIMAL)\n    ;\n  else if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_constraints: Not a valid basis\\n\");\n    return(FALSE);\n  }\n\n  MEMCOPY(constr, lp->best_solution + 1, lp->rows);\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_ptr_constraints(lprec *lp, REAL **constr)\n{\n  if(lp->spx_status == OPTIMAL)\n    ;\n  else if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_ptr_constraints: Not a valid basis\\n\");\n    return(FALSE);\n  }\n\n  if(constr != NULL)\n   *constr = lp->best_solution + 1;\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_sensitivity_rhs(lprec *lp, REAL *duals, REAL *dualsfrom, REAL *dualstill)\n{\n  REAL *duals0, *dualsfrom0, *dualstill0;\n\n  if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_sensitivity_rhs: Not a valid basis\\n\");\n    return(FALSE);\n  }\n\n  if(!get_ptr_sensitivity_rhs(lp,\n                              (duals != NULL) ? &duals0 : NULL,\n                              (dualsfrom != NULL) ? &dualsfrom0 : NULL,\n                              (dualstill != NULL) ? &dualstill0 : NULL))\n    return(FALSE);\n\n  if(duals != NULL)\n    MEMCOPY(duals, duals0, lp->sum);\n  if(dualsfrom != NULL)\n    MEMCOPY(dualsfrom, dualsfrom0, lp->sum);\n  if(dualstill != NULL)\n    MEMCOPY(dualstill, dualstill0, lp->sum);\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_ptr_sensitivity_rhs(lprec *lp, REAL **duals, REAL **dualsfrom, REAL **dualstill)\n{\n  if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_ptr_sensitivity_rhs: Not a valid basis\\n\");\n    return(FALSE);\n  }\n\n  if(duals != NULL) {\n    if(lp->duals == NULL) {\n      if((MIP_count(lp) > 0) && (lp->bb_totalnodes > 0)) {\n        report(lp, CRITICAL, \"get_ptr_sensitivity_rhs: Sensitivity unknown\\n\");\n        return(FALSE);\n      }\n      if(!construct_duals(lp))\n        return(FALSE);\n    }\n    *duals = lp->duals + 1;\n  }\n\n  if((dualsfrom != NULL) || (dualstill != NULL)) {\n    if((lp->dualsfrom == NULL) || (lp->dualstill == NULL)) {\n      if((MIP_count(lp) > 0) && (lp->bb_totalnodes > 0)) {\n        report(lp, CRITICAL, \"get_ptr_sensitivity_rhs: Sensitivity unknown\\n\");\n        return(FALSE);\n      }\n      construct_sensitivity_duals(lp);\n      if((lp->dualsfrom == NULL) || (lp->dualstill == NULL))\n        return(FALSE);\n    }\n    if(dualsfrom != NULL)\n      *dualsfrom = lp->dualsfrom + 1;\n    if(dualstill != NULL)\n      *dualstill = lp->dualstill + 1;\n  }\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_sensitivity_objex(lprec *lp, REAL *objfrom, REAL *objtill, REAL *objfromvalue, REAL *objtillvalue)\n{\n  REAL *objfrom0, *objtill0, *objfromvalue0, *objtillvalue0;\n\n  if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_sensitivity_objex: Not a valid basis\\n\");\n    return(FALSE);\n  }\n\n  if(!get_ptr_sensitivity_objex(lp, (objfrom != NULL) ? &objfrom0 : NULL,\n                                    (objtill != NULL) ? &objtill0 : NULL,\n                                    (objfromvalue != NULL) ? &objfromvalue0 : NULL,\n                                    (objtillvalue != NULL) ? &objtillvalue0 : NULL))\n    return(FALSE);\n\n  if((objfrom != NULL) && (objfrom0 != NULL))\n    MEMCOPY(objfrom, objfrom0, lp->columns);\n  if((objtill != NULL) && (objtill0 != NULL))\n    MEMCOPY(objtill, objtill0, lp->columns);\n  if((objfromvalue != NULL) && (objfromvalue0 != NULL))\n    MEMCOPY(objfromvalue, objfromvalue0, lp->columns);\n  if((objtillvalue != NULL) && (objtillvalue0 != NULL))\n    MEMCOPY(objtillvalue, objtillvalue0, lp->columns);\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_sensitivity_obj(lprec *lp, REAL *objfrom, REAL *objtill)\n{\n  return(get_sensitivity_objex(lp, objfrom, objtill, NULL, NULL));\n}\n\nMYBOOL __WINAPI get_ptr_sensitivity_objex(lprec *lp, REAL **objfrom, REAL **objtill, REAL **objfromvalue, REAL **objtillvalue)\n{\n  if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_ptr_sensitivity_objex: Not a valid basis\\n\");\n    return(FALSE);\n  }\n\n  if((objfrom != NULL) || (objtill != NULL)) {\n    if((lp->objfrom == NULL) || (lp->objtill == NULL)) {\n      if((MIP_count(lp) > 0) && (lp->bb_totalnodes > 0)) {\n        report(lp, CRITICAL, \"get_ptr_sensitivity_objex: Sensitivity unknown\\n\");\n        return(FALSE);\n      }\n      construct_sensitivity_obj(lp);\n      if((lp->objfrom == NULL) || (lp->objtill == NULL))\n        return(FALSE);\n    }\n    if(objfrom != NULL)\n      *objfrom = lp->objfrom + 1;\n    if(objtill != NULL)\n      *objtill = lp->objtill + 1;\n  }\n\n  if((objfromvalue != NULL) /* || (objtillvalue != NULL) */) {\n    if((lp->objfromvalue == NULL) /* || (lp->objtillvalue == NULL) */) {\n      if((MIP_count(lp) > 0) && (lp->bb_totalnodes > 0)) {\n        report(lp, CRITICAL, \"get_ptr_sensitivity_objex: Sensitivity unknown\\n\");\n        return(FALSE);\n      }\n      construct_sensitivity_duals(lp);\n      if((lp->objfromvalue == NULL) /* || (lp->objtillvalue == NULL) */)\n        return(FALSE);\n    }\n  }\n\n  if(objfromvalue != NULL)\n    *objfromvalue = lp->objfromvalue + 1;\n\n  if(objtillvalue != NULL)\n    *objtillvalue = NULL /* lp->objtillvalue + 1 */;\n\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_ptr_sensitivity_obj(lprec *lp, REAL **objfrom, REAL **objtill)\n{\n  return(get_ptr_sensitivity_objex(lp, objfrom, objtill, NULL, NULL));\n}\n\nvoid __WINAPI set_solutionlimit(lprec *lp, int limit)\n{\n  lp->solutionlimit = limit;\n}\nint __WINAPI get_solutionlimit(lprec *lp)\n{\n  return(lp->solutionlimit);\n}\nint __WINAPI get_solutioncount(lprec *lp)\n{\n  return(lp->solutioncount);\n}\n\nint __WINAPI get_Nrows(lprec *lp)\n{\n  return(lp->rows);\n}\n\nint __WINAPI get_Norig_rows(lprec *lp)\n{\n  if(lp->varmap_locked)\n    return(lp->presolve_undo->orig_rows);\n  else\n    return(lp->rows);\n}\n\nint __WINAPI get_Lrows(lprec *lp)\n{\n  if(lp->matL == NULL)\n    return( 0 );\n  else\n    return( lp->matL->rows );\n}\n\nint __WINAPI get_Ncolumns(lprec *lp)\n{\n  return(lp->columns);\n}\n\nint __WINAPI get_Norig_columns(lprec *lp)\n{\n  if(lp->varmap_locked)\n    return(lp->presolve_undo->orig_columns);\n  else\n    return(lp->columns);\n}\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Core routines for lp_solve                                                         */\n/* ---------------------------------------------------------------------------------- */\nint __WINAPI get_status(lprec *lp)\n{\n  return(lp->spx_status);\n}\n\nchar * __WINAPI get_statustext(lprec *lp, int statuscode)\n{\n  if (statuscode == NOBFP)             return(\"No basis factorization package\");\n  else if (statuscode == DATAIGNORED)  return(\"Invalid input data provided\");\n  else if (statuscode == NOMEMORY)     return(\"Not enough memory available\");\n  else if (statuscode == NOTRUN)       return(\"Model has not been optimized\");\n  else if (statuscode == OPTIMAL)      return(\"OPTIMAL solution\");\n  else if (statuscode == SUBOPTIMAL)   return(\"SUB-OPTIMAL solution\");\n  else if (statuscode == INFEASIBLE)   return(\"Model is primal INFEASIBLE\");\n  else if (statuscode == UNBOUNDED)    return(\"Model is primal UNBOUNDED\");\n  else if (statuscode == RUNNING)      return(\"lp_solve is currently running\");\n  else if (statuscode == NUMFAILURE)   return(\"NUMERIC FAILURE encountered\");\n  else if (statuscode == DEGENERATE)   return(\"DEGENERATE situation\");\n  else if (statuscode == USERABORT)    return(\"User-requested termination\");\n  else if (statuscode == TIMEOUT)      return(\"Termination due to timeout\");\n  else if (statuscode == PRESOLVED)    return(\"Model solved by presolve\");\n  else if (statuscode == PROCFAIL)     return(\"B&B routine failed\");\n  else if (statuscode == PROCBREAK)    return(\"B&B routine terminated\");\n  else if (statuscode == FEASFOUND)    return(\"Feasible B&B solution found\");\n  else if (statuscode == NOFEASFOUND)  return(\"No feasible B&B solution found\");\n  else if (statuscode == FATHOMED)     return(\"Fathomed/pruned branch\");\n  else                                 return(\"Undefined internal error\");\n}\n\nMYBOOL __WINAPI is_obj_in_basis(lprec *lp)\n{\n  return( lp->obj_in_basis );\n}\n\nvoid __WINAPI set_obj_in_basis(lprec *lp, MYBOOL obj_in_basis)\n{\n  lp->obj_in_basis = (MYBOOL) (obj_in_basis == TRUE);\n}\n\nlprec * __WINAPI make_lp(int rows, int columns)\n{\n  lprec *lp;\n\n# if defined FORTIFY\n   /* Fortify_EnterScope(); */\n# endif\n\n  if(rows < 0 || columns < 0)\n    return(NULL);\n\n  lp = (lprec*) calloc(1, sizeof(*lp));\n  if(!lp)\n    return(NULL);\n\n  set_lp_name(lp, NULL);\n  lp->names_used    = FALSE;\n  lp->use_row_names = TRUE;\n  lp->use_col_names = TRUE;\n  lp->rowcol_name   = NULL;\n\n  /* Do standard initializations ------------------------------------------------------------ */\n#if 1\n  lp->obj_in_basis  = DEF_OBJINBASIS;\n#else\n  lp->obj_in_basis  = FALSE;\n#endif\n  lp->verbose       = NORMAL;\n  set_callbacks(lp);\n  set_BFP(lp, NULL);\n  set_XLI(lp, NULL);\n#if libBLAS > 0\n  init_BLAS();\n#if libBLAS > 1\n  if(is_nativeBLAS() && !load_BLAS(libnameBLAS))\n    /*report(lp, \"make_lp: Could not load external BLAS library '%s'.\\n\", libnameBLAS)*/;\n#endif\n#endif\n\n  /* Define the defaults for key user-settable values --------------------------------------- */\n  reset_params(lp);\n\n  /* Do other initializations --------------------------------------------------------------- */\n  lp->source_is_file    = FALSE;\n  lp->model_is_pure     = TRUE;\n  lp->model_is_valid    = FALSE;\n  lp->spx_status        = NOTRUN;\n  lp->lag_status        = NOTRUN;\n\n  lp->workarrays = mempool_create(lp);\n  lp->wasPreprocessed   = FALSE;\n  lp->wasPresolved      = FALSE;\n  presolve_createUndo(lp);\n\n  lp->bb_varactive      = NULL;\n  lp->bb_varbranch      = NULL;\n  lp->var_priority      = NULL;\n\n  lp->rhsmax            = 0.0;\n  lp->bigM              = 0.0;\n  lp->bb_deltaOF        = 0.0;\n\n  lp->equalities        = 0;\n  lp->fixedvars         = 0;\n  lp->int_vars          = 0;\n  lp->sc_vars           = 0;\n\n  lp->sos_ints          = 0;\n  lp->sos_vars          = 0;\n  lp->sos_priority      = NULL;\n\n  lp->rows_alloc        = 0;\n  lp->columns_alloc     = 0;\n  lp->sum_alloc         = 0;\n\n  lp->rows              = rows;\n  lp->columns           = columns;\n  lp->sum               = rows + columns;\n  varmap_clear(lp);\n\n  lp->matA = mat_create(lp, rows, columns, lp->epsvalue);\n  lp->matL = NULL;\n  lp->invB = NULL;\n  lp->duals = NULL;\n  lp->dualsfrom = NULL;\n  lp->dualstill = NULL;\n  lp->objfromvalue = NULL;\n  lp->objfrom = NULL;\n  lp->objtill = NULL;\n\n  inc_col_space(lp, columns + 1);\n  inc_row_space(lp, rows + 1);\n\n  /* Avoid bound-checker uninitialized variable error */\n  lp->orig_lowbo[0] = 0;\n\n  lp->rootbounds = NULL;\n  lp->bb_bounds = NULL;\n  lp->bb_basis = NULL;\n\n  lp->basis_valid       = FALSE;\n  lp->simplex_mode      = SIMPLEX_DYNAMIC;\n  lp->scaling_used      = FALSE;\n  lp->columns_scaled    = FALSE;\n  lp->P1extraDim        = 0;\n  lp->P1extraVal        = 0.0;\n  lp->bb_strongbranches = 0;\n  lp->current_iter      = 0;\n  lp->total_iter        = 0;\n  lp->current_bswap     = 0;\n  lp->total_bswap       = 0;\n  lp->solutioncount     = 0;\n  lp->solvecount        = 0;\n\n  allocINT(lp, &lp->rejectpivot, DEF_MAXPIVOTRETRY + 1, TRUE);\n\n  set_minim(lp);\n  set_infiniteex(lp, DEF_INFINITE, TRUE);\n\n  initPricer(lp);\n\n  /* Call-back routines by KE */\n  lp->ctrlc = NULL;\n  lp->ctrlchandle = NULL;\n  lp->writelog = NULL;\n  lp->loghandle = NULL;\n  lp->debuginfo = NULL;\n  lp->usermessage = NULL;\n  lp->msgmask = MSG_NONE;\n  lp->msghandle = NULL;\n\n  lp->timecreate = timeNow();\n\n  return(lp);\n}\n\nMYBOOL __WINAPI resize_lp(lprec *lp, int rows, int columns)\n{\n  MYBOOL status = TRUE;\n\n  if(columns > lp->columns)\n    status = inc_col_space(lp, columns - lp->columns);\n  else\n    while(status && (lp->columns > columns)) {\n      status = del_column(lp, lp->columns);\n    }\n  if(status && (rows > lp->rows))\n    status = inc_row_space(lp, rows - lp->rows);\n  else\n    while(status && (lp->rows > rows)) {\n      status = del_constraint(lp, lp->rows);\n    }\n  return( status );\n}\n\nvoid __WINAPI free_lp(lprec **plp)\n{\n  if(plp != NULL) {\n    lprec *lp = *plp;\n    if(lp != NULL)\n      delete_lp(lp);\n    *plp = NULL;\n  }\n}\n\nvoid __WINAPI delete_lp(lprec *lp)\n{\n  if(lp == NULL)\n    return;\n\n  FREE(lp->rowcol_name);\n  FREE(lp->lp_name);\n  FREE(lp->ex_status);\n  if(lp->names_used) {\n    FREE(lp->row_name);\n    FREE(lp->col_name);\n    free_hash_table(lp->rowname_hashtab);\n    free_hash_table(lp->colname_hashtab);\n  }\n\n  mat_free(&lp->matA);\n  lp->bfp_free(lp);\n#if LoadInverseLib == TRUE\n  if(lp->hBFP != NULL)\n    set_BFP(lp, NULL);\n#endif\n#if LoadLanguageLib == TRUE\n  if(lp->hXLI != NULL)\n    set_XLI(lp, NULL);\n#endif\n\n  unset_OF_p1extra(lp);\n  FREE(lp->orig_obj);\n  FREE(lp->orig_rhs);\n  FREE(lp->rhs);\n  FREE(lp->var_type);\n  set_var_weights(lp, NULL);\n  FREE(lp->bb_varbranch);\n  FREE(lp->sc_lobound);\n  FREE(lp->var_is_free);\n  FREE(lp->orig_upbo);\n  FREE(lp->orig_lowbo);\n  FREE(lp->upbo);\n  FREE(lp->lowbo);\n  FREE(lp->var_basic);\n  FREE(lp->is_basic);\n  FREE(lp->is_lower);\n  if(lp->bb_PseudoCost != NULL) {\n/*    report(lp, SEVERE, \"delete_lp: The B&B pseudo-cost array was not cleared on delete\\n\"); */\n    free_pseudocost(lp);\n  }\n  if(lp->bb_bounds != NULL) {\n    report(lp, SEVERE, \"delete_lp: The stack of B&B levels was not empty (failed at %.0f nodes)\\n\",\n                       (double) lp->bb_totalnodes);\n    unload_BB(lp);\n  }\n  if(lp->bb_basis != NULL) {\n/*    report(lp, SEVERE, \"delete_lp: The stack of saved bases was not empty on delete\\n\"); */\n    unload_basis(lp, FALSE);\n  }\n\n  FREE(lp->rejectpivot);\n  partial_freeBlocks(&(lp->rowblocks));\n  partial_freeBlocks(&(lp->colblocks));\n  multi_free(&(lp->multivars));\n  multi_free(&(lp->longsteps));\n\n  FREE(lp->solution);\n  FREE(lp->best_solution);\n  FREE(lp->full_solution);\n\n  presolve_freeUndo(lp);\n  mempool_free(&(lp->workarrays));\n\n  freePricer(lp);\n\n  FREE(lp->drow);\n  FREE(lp->nzdrow);\n\n  FREE(lp->duals);\n  FREE(lp->full_duals);\n  FREE(lp->dualsfrom);\n  FREE(lp->dualstill);\n  FREE(lp->objfromvalue);\n  FREE(lp->objfrom);\n  FREE(lp->objtill);\n  FREE(lp->row_type);\n\n  if(lp->sos_vars > 0)\n    FREE(lp->sos_priority);\n  free_SOSgroup(&(lp->SOS));\n  free_SOSgroup(&(lp->GUB));\n  freecuts_BB(lp);\n\n  if(lp->scaling_used)\n    FREE(lp->scalars);\n  if(lp->matL != NULL) {\n    FREE(lp->lag_rhs);\n    FREE(lp->lambda);\n    FREE(lp->lag_con_type);\n    mat_free(&lp->matL);\n  }\n  if(lp->streamowned)\n    set_outputstream(lp, NULL);\n\n#if libBLAS > 0\n  if(!is_nativeBLAS())\n    unload_BLAS();\n#endif\n\n  FREE(lp);\n\n# if defined FORTIFY\n    /* Fortify_LeaveScope(); */\n# endif\n}\n\nstatic MYBOOL get_SOS(lprec *lp, int index, char *name, int *sostype, int *priority, int *count, int *sosvars, REAL *weights)\n{\n  SOSrec *SOS;\n\n  if((index < 1) || (index > SOS_count(lp)))\n    return( FALSE );\n  SOS = lp->SOS->sos_list[index-1];\n  if(name != NULL)\n    strcpy(name, SOS->name);\n  if(sostype != NULL)\n    *sostype = SOS->type;\n  if(priority != NULL)\n    *priority = SOS->priority;\n  if(count != NULL) {\n    *count = SOS->size;\n    if(sosvars != NULL) {\n      int i;\n      for(i = 1; i <= *count; i++) {\n        sosvars[i-1] = SOS->members[i];\n        if(weights != NULL)\n          weights[i-1] = SOS->weights[i];\n      }\n    }\n  }\n  return( TRUE );\n}\n\n/* Make a copy of the existing model using (mostly) high-level\n   construction routines to simplify future maintainance. */\nlprec* __WINAPI copy_lp(lprec *lp)\n{\n  int   i, n, *idx = NULL;\n  REAL  hold, *val = NULL, infinite;\n  lprec *newlp = NULL;\n  char buf[256], ok = FALSE;\n  int sostype, priority, count, *sosvars, rows, columns;\n  REAL *weights = NULL;\n\n#if 0\n  if(lp->wasPresolved)\n    return( newlp );\n#endif\n\n  rows = get_Nrows(lp);\n  columns = get_Ncolumns(lp);\n\n  if(!allocINT(lp, &idx, rows+1, FALSE) ||\n     !allocREAL(lp, &val, rows+1, FALSE))\n    goto Finish;\n\n  /* Create the new object */\n  newlp = make_lp(rows, 0);\n  if(newlp == NULL)\n    goto Finish;\n  if(!resize_lp(newlp, rows, columns))\n    goto Finish;\n  set_sense(newlp, is_maxim(lp));\n  set_use_names(newlp, FALSE, is_use_names(lp, FALSE));\n  set_use_names(newlp, TRUE, is_use_names(lp, TRUE));\n  if(!set_lp_name(newlp, get_lp_name(lp)))\n    goto Finish;\n  /* set_algopt(newlp, get_algopt(lp)); */ /* v6 */\n  set_verbose(newlp, get_verbose(lp));\n\n  /* Transfer standard simplex parameters */\n  set_epspivot(newlp, get_epspivot(lp));\n  set_epsel(newlp, get_epsel(lp));\n  set_epsb(newlp, get_epsb(lp));\n  set_epsd(newlp, get_epsd(lp));\n  set_pivoting(newlp, get_pivoting(lp));\n  set_negrange(newlp, lp->negrange);\n  set_infinite(newlp, get_infinite(lp));\n  set_presolve(newlp, get_presolve(lp), get_presolveloops(lp));\n  set_scaling(newlp, get_scaling(lp));\n  set_scalelimit(newlp, get_scalelimit(lp));\n  set_simplextype(newlp, get_simplextype(lp));\n  set_epsperturb(newlp, get_epsperturb(lp));\n  set_anti_degen(newlp, get_anti_degen(lp));\n  set_improve(newlp, get_improve(lp));\n  set_basiscrash(newlp, get_basiscrash(lp));\n  set_maxpivot(newlp, get_maxpivot(lp));\n  set_timeout(newlp, get_timeout(lp));\n\n  /* Transfer MILP parameters */\n  set_epsint(newlp, get_epsint(lp));\n  set_bb_rule(newlp, get_bb_rule(lp));\n  set_bb_depthlimit(newlp, get_bb_depthlimit(lp));\n  set_bb_floorfirst(newlp, get_bb_floorfirst(lp));\n  set_mip_gap(newlp, TRUE, get_mip_gap(lp, TRUE));\n  set_mip_gap(newlp, FALSE, get_mip_gap(lp, FALSE));\n  set_break_at_first(newlp, is_break_at_first(lp));\n  set_break_at_value(newlp, get_break_at_value(lp));\n\n  /* Set RHS and range */\n  infinite = get_infinite(lp);\n  for(i = 0; i <= rows; i++) {\n    if(i > 0)\n      if(!set_constr_type(newlp, i, get_constr_type(lp, i)))\n        goto Finish;\n    if(!set_rh(newlp, i, get_rh(lp, i)))\n      goto Finish;\n    if((i > 0) && ((hold = get_rh_range(lp, i)) < infinite))\n      if(!set_rh_range(newlp, i, hold))\n        goto Finish;\n    if(lp->names_used && lp->use_row_names && (lp->row_name[i] != NULL) && (lp->row_name[i]->name != NULL))\n      if(!set_row_name(newlp, i, get_row_name(lp, i)))\n        goto Finish;\n  }\n\n  /* Load the constraint matrix and variable definitions */\n  for(i = 1; i <= columns; i++) {\n    n = get_columnex(lp, i, val, idx);\n    if ((n < 0) || (!add_columnex(newlp, n, val, idx)))\n      goto Finish;\n    if(is_binary(lp, i)) {\n      if (!set_binary(newlp, i, TRUE))\n        goto Finish;\n    }\n    else {\n      if(is_int(lp, i))\n        if(!set_int(newlp, i, TRUE))\n          goto Finish;\n      if((hold = get_lowbo(lp, i)) != 0)\n        if(!set_lowbo(newlp, i, hold))\n          goto Finish;\n      if((hold = get_upbo(lp, i)) < infinite)\n        if(!set_upbo(newlp, i, hold))\n          goto Finish;\n    }\n    if(is_semicont(lp, i))\n      if(!set_semicont(newlp, i, TRUE))\n        goto Finish;\n    if(lp->names_used && lp->use_col_names && (lp->col_name[i] != NULL) && (lp->col_name[i]->name != NULL))\n      if(!set_col_name(newlp, i, get_col_name(lp, i)))\n        goto Finish;\n  }\n\n  /* copy SOS data */\n  for(i = 1; get_SOS(lp, i, buf, &sostype, &priority, &count, NULL, NULL); i++)\n    if (count) {\n      if(!allocINT(lp, &sosvars, count, FALSE) ||\n         !allocREAL(lp, &weights, count, FALSE))\n        n = 0;\n      else {\n        get_SOS(lp, i, buf, &sostype, &priority, &count, sosvars, weights);\n        n = add_SOS(newlp, buf, sostype, priority, count, sosvars, weights);\n      }\n      FREE(weights);\n      FREE(sosvars);\n      if(n == 0)\n        goto Finish;\n    }\n\n#if 0\n  /* Other parameters set if the source model was previously solved */\n  if(lp->solvecount > 0) {\n    MEMCOPY(newlp->scalars, lp->scalars, lp->sum+1);\n    MEMCOPY(newlp->var_basic, lp->var_basic, rows+1);\n    MEMCOPY(newlp->is_basic, lp->is_basic, lp->sum+1);\n    MEMCOPY(newlp->is_lower, lp->is_lower, lp->sum+1);\n    MEMCOPY(newlp->solution, lp->solution, lp->sum+1);\n    if(lp->duals != NULL) {\n      allocREAL(newlp, &newlp->duals, newlp->sum_alloc+1, FALSE);\n      MEMCOPY(newlp->duals, lp->duals, lp->sum+1);\n    }\n    newlp->solutioncount = lp->solutioncount;\n    newlp->solvecount = lp->solvecount;\n  }\n#endif\n\n  ok = TRUE;\n\n  /* Clean up before returning */\nFinish:\n  if(!ok)\n    free_lp(&newlp);\n  FREE(val);\n  FREE(idx);\n\n  return( newlp );\n}\nMYBOOL __WINAPI dualize_lp(lprec *lp)\n{\n  int     i, n;\n  MATrec  *mat = lp->matA;\n  REAL    *item;\n\n  /* Are we allowed to perform the operation? */\n  if((MIP_count(lp) > 0) || (lp->solvecount > 0))\n    return( FALSE );\n\n  /* Modify sense */\n  set_sense(lp, (MYBOOL) !is_maxim(lp));\n\n  /* Transpose matrix and reverse signs */\n  n = mat_nonzeros(mat);\n  mat_transpose(mat);\n  item = &COL_MAT_VALUE(0);\n  for(i = 0; i < n; i++, item += matValueStep)\n    *item *= -1;\n\n  /* Row-column swap other vectors */\n  swapINT(&lp->rows, &lp->columns);\n  swapINT(&lp->rows_alloc, &lp->columns_alloc);\n  swapREAL(lp->orig_rhs, lp->orig_obj);\n  if ((lp->rhs != NULL) && (lp->obj != NULL))\n    swapREAL(lp->rhs, lp->obj);\n\n  /* Reallocate storage */\n/*\nvar_type\nsc_bound\nsolution\nbest_solution\nfull_solution\nduals\n*/\n\n  /* Shift variable bounds */\n/*\nis_basic\norig_upbo\norig_lowbo\nscalars\n*/\n\n  return( TRUE );\n}\n\n/* Optimize memory usage */\nSTATIC MYBOOL memopt_lp(lprec *lp, int rowextra, int colextra, int nzextra)\n{\n  MYBOOL status = FALSE;\n\n  if(lp == NULL)\n    return( status );\n\n  status = mat_memopt(lp->matA, rowextra, colextra, nzextra) &&\n           (++rowextra > 0) && (++colextra > 0) && (++nzextra > 0);\n\n#if 0 /* inc_ routines not well-tested for reduction in size allocation */\n  if(status) {\n    int colalloc = lp->columns_alloc - MIN(lp->columns_alloc, lp->columns + colextra),\n        rowalloc = lp->rows_alloc    - MIN(lp->rows_alloc,    lp->rows + rowextra);\n\n    status = inc_lag_space(lp, rowalloc, FALSE) &&\n             inc_row_space(lp, rowalloc) &&\n             inc_col_space(lp, colalloc);\n  }\n#endif\n\n  return( status );\n}\n\n\n/* Utility routine group for constraint and column deletion/insertion\n   mapping in relation to the original set of constraints and columns */\nSTATIC void varmap_lock(lprec *lp)\n{\n  presolve_fillUndo(lp, lp->rows, lp->columns, TRUE);\n  lp->varmap_locked = TRUE;\n}\nSTATIC void varmap_clear(lprec *lp)\n{\n  presolve_setOrig(lp, 0, 0);\n  lp->varmap_locked = FALSE;\n}\nSTATIC MYBOOL varmap_canunlock(lprec *lp)\n{\n  /* Don't do anything if variables aren't locked yet */\n  if(lp->varmap_locked) {\n    int i;\n    presolveundorec *psundo = lp->presolve_undo;\n\n    /* Check for the obvious */\n    if(/*lp->names_used ||\n       (psundo->orig_columns != lp->columns) || (psundo->orig_rows != lp->rows)) */\n       (psundo->orig_columns > lp->columns) || (psundo->orig_rows > lp->rows))\n      return( FALSE );\n\n    /* Check for deletions */\n    for(i = psundo->orig_rows + psundo->orig_columns; i > 0; i--)\n      if(psundo->orig_to_var[i] == 0)\n        return( FALSE );\n\n    /* Check for insertions */\n    for(i = lp->sum; i > 0; i--)\n      if(psundo->var_to_orig[i] == 0)\n        return( FALSE );\n  }\n  return( TRUE );\n}\nSTATIC void varmap_add(lprec *lp, int base, int delta)\n{\n  int i, ii;\n  presolveundorec *psundo = lp->presolve_undo;\n\n  /* Don't do anything if variables aren't locked yet */\n  if(!lp->varmap_locked)\n    return;\n\n  /* Set new constraints/columns to have an \"undefined\" mapping to original\n     constraints/columns (assumes that counters have NOT yet been updated) */\n  for(i = lp->sum; i >= base; i--) {\n    ii = i + delta;\n    psundo->var_to_orig[ii] = psundo->var_to_orig[i];\n  }\n\n  /* Initialize map of added rows/columns */\n  for(i = 0; i < delta; i++) {\n    ii = base + i;\n    psundo->var_to_orig[ii] = 0;\n  }\n}\n\nSTATIC void varmap_delete(lprec *lp, int base, int delta, LLrec *varmap)\n{\n  int             i, ii, j;\n  MYBOOL          preparecompact = (MYBOOL) (varmap != NULL);\n  presolveundorec *psundo = lp->presolve_undo;\n\n  /* Set the model \"dirty\" if we are deleting row of constraint */\n  lp->model_is_pure &= (MYBOOL) ((lp->solutioncount == 0) && !preparecompact);\n\n  /* Don't do anything if\n     1) variables aren't locked yet, or\n     2) the constraint was added after the variables were locked */\n  if(!lp->varmap_locked) {\n#if 0\n   if(lp->names_used)\n     varmap_lock(lp);\n   else\n     return;\n#else\n    if(!lp->model_is_pure && lp->names_used)\n      varmap_lock(lp);\n#endif\n  }\n\n  /* Do mass deletion via a linked list */\n  preparecompact = (MYBOOL) (varmap != NULL);\n  if(preparecompact) {\n    preparecompact = (MYBOOL) (base > lp->rows);  /* Set TRUE for columns */\n    for(j = firstInactiveLink(varmap); j != 0; j = nextInactiveLink(varmap, j)) {\n      i = j;\n      if(preparecompact) {\n#ifdef Paranoia\n        if(SOS_is_member(lp->SOS, 0, j))\n          report(lp, SEVERE, \"varmap_delete: Deleting variable %d, which is in a SOS!\\n\", j);\n#endif\n        i += lp->rows;\n      }\n      ii = psundo->var_to_orig[i];\n      if(ii > 0)  /* It was an original variable; reverse sign of index to flag deletion */\n        psundo->var_to_orig[i] = -ii;\n      else        /* It was a non-original variable; add special code for deletion */\n        psundo->var_to_orig[i] = -(psundo->orig_rows+psundo->orig_columns+i);\n    }\n    return;\n  }\n\n  /* Do legacy simplified version if we are doing batch delete operations */\n  preparecompact = (MYBOOL) (base < 0);\n  if(preparecompact) {\n    base = -base;\n    if(base > lp->rows)\n      base += (psundo->orig_rows - lp->rows);\n    for(i = base; i < base-delta; i++) {\n      ii = psundo->var_to_orig[i];\n      if(ii > 0)  /* It was an original variable; reverse sign of index to flag deletion */\n        psundo->var_to_orig[i] = -ii;\n      else       /* It was a non-original variable; add special code for deletion */\n        psundo->var_to_orig[i] = -(psundo->orig_rows+psundo->orig_columns+i);\n    }\n    return;\n  }\n\n  /* We are deleting an original constraint/column;\n     1) clear mapping of original to deleted\n     2) shift the deleted variable to original mappings left\n     3) decrement all subsequent original-to-current pointers\n  */\n  if(varmap_canunlock(lp))    lp->varmap_locked = FALSE;\n  for(i = base; i < base-delta; i++) {\n    ii = psundo->var_to_orig[i];\n    if(ii > 0)\n      psundo->orig_to_var[ii] = 0;\n  }\n  for(i = base; i <= lp->sum+delta; i++) {\n    ii = i - delta;\n    psundo->var_to_orig[i] = psundo->var_to_orig[ii];\n  }\n\n  i = 1;\n  j = psundo->orig_rows;\n  if(base > lp->rows) {\n    i += j;\n    j += psundo->orig_columns;\n  }\n  ii = base-delta;\n  for(; i <= j; i++) {\n    if(psundo->orig_to_var[i] >= ii)\n      psundo->orig_to_var[i] += delta;\n  }\n\n}\n\nSTATIC MYBOOL varmap_validate(lprec *lp, int varno)\n{\n  MYBOOL success = TRUE;\n  int i, ii, ix, ie,\n       n_rows = lp->rows,\n       orig_sum = lp->presolve_undo->orig_sum,\n       orig_rows = lp->presolve_undo->orig_rows;\n\n  if(varno <= 0) {\n    varno = 1;\n    ie = orig_sum;\n  }\n  else\n    ie = varno;\n  for(i = varno; success && (i <= ie); i++) {\n    ix = lp->presolve_undo->orig_to_var[i];\n    if((ix > 0) && (i > orig_rows))\n      ix += n_rows;\n\n    /* Check for index out of range due to presolve */\n    success = (MYBOOL) (ix <= orig_sum);\n    if(!success)\n      report(lp, SEVERE, \"varmap_validate: Invalid new mapping found for variable %d\\n\",\n                           i);\n    else if(ix != 0) {\n      ii = lp->presolve_undo->var_to_orig[ix];\n      if(ix > n_rows)\n        ii += orig_rows;\n      success = (MYBOOL) (ii == i);\n      if(!success)\n        report(lp, SEVERE, \"varmap_validate: Invalid old mapping found for variable %d (%d)\\n\",\n                           i, ii);\n    }\n  }\n  return( success );\n}\n\nSTATIC void varmap_compact(lprec *lp, int prev_rows, int prev_cols)\n{\n  presolveundorec *psundo = lp->presolve_undo;\n  int             i, ii, n_sum, n_rows,\n                  orig_rows = psundo->orig_rows,\n                  prev_sum = prev_rows + prev_cols;\n\n  /* Nothing to do if the model is not \"dirty\" or the variable map is not locked */\n  if(lp->model_is_pure || !lp->varmap_locked)\n    return;\n\n  /* We are deleting an original constraint/column;\n     1) clear mapping of original to deleted\n     2) shift the deleted variable to original mappings left\n     3) decrement all subsequent original-to-current pointers\n  */\n  n_sum = 0;\n  n_rows = 0;\n  for(i = 1; i <= prev_sum; i++) {\n    ii = psundo->var_to_orig[i];\n\n    /* Process variable if it was deleted in the previous round */\n    if(ii < 0) {\n      ii = -ii;\n      /* Update map back if we have an original variable, otherwise just skip */\n      if(i <= prev_rows)\n        psundo->orig_to_var[ii] = 0;\n      else\n        psundo->orig_to_var[orig_rows+ii] = 0;\n    }\n    /* Otherwise shift and update map back */\n    else {\n      n_sum++;\n      /* Shift only if necessary */\n      if(n_sum < i)\n        psundo->var_to_orig[n_sum] = ii;\n      /* Update map back if we have an original variable */\n      if(ii > 0) {\n        if(i <= prev_rows) {\n          psundo->orig_to_var[ii] = n_sum;\n          n_rows = n_sum;\n        }\n        else\n          psundo->orig_to_var[orig_rows+ii] = n_sum-n_rows;\n      }\n    }\n  }\n#ifdef xxParanoia\n  if(!varmap_validate(lp, 0))\n    report(lp, SEVERE, \"varmap_compact: Internal presolve mapping error at exit\\n\");\n#endif\n\n}\n\n/* Utility group for shifting row and column data */\nSTATIC MYBOOL shift_rowcoldata(lprec *lp, int base, int delta, LLrec *usedmap, MYBOOL isrow)\n/* Note: Assumes that \"lp->sum\" and \"lp->rows\" HAVE NOT been updated to the new counts */\n{\n  int  i, ii;\n  REAL lodefault;\n\n  /* Shift data right/down (insert), and set default values in positive delta-gap */\n  if(delta > 0) {\n\n    /* Determine if we can take the easy way out */\n    MYBOOL easyout = (MYBOOL) ((lp->solvecount == 0) && (base > lp->rows));\n\n    /* Shift the row/column data */\n\n    MEMMOVE(lp->orig_upbo + base + delta, lp->orig_upbo + base, lp->sum - base + 1);\n    MEMMOVE(lp->orig_lowbo + base + delta, lp->orig_lowbo + base, lp->sum - base + 1);\n\n    if(!easyout) {\n      MEMMOVE(lp->upbo + base + delta, lp->upbo + base, lp->sum - base + 1);\n      MEMMOVE(lp->lowbo + base + delta, lp->lowbo + base, lp->sum - base + 1);\n      if(lp->model_is_valid) {\n        MEMMOVE(lp->solution + base + delta, lp->solution + base, lp->sum - base + 1);\n        MEMMOVE(lp->best_solution + base + delta, lp->best_solution + base, lp->sum - base + 1);\n      }\n      MEMMOVE(lp->is_lower + base + delta, lp->is_lower + base, lp->sum - base + 1);\n    }\n\n    /* Deal with scalars; the vector can be NULL */\n    if(lp->scalars != NULL) {\n      if(!easyout)\n        for(ii = lp->sum; ii >= base; ii--) {\n          i = ii + delta;\n          lp->scalars[i] = lp->scalars[ii];\n        }\n      for(ii = base; ii < base + delta; ii++)\n        lp->scalars[ii] = 1;\n    }\n\n    /* Set defaults */\n#ifdef SlackInitMinusInf\n    if(isrow)\n      lodefault = -lp->infinite;\n    else\n#endif\n      lodefault = 0;\n\n    for(i = 0; i < delta; i++) {\n      ii = base + i;\n      lp->orig_upbo[ii] = lp->infinite;\n      lp->orig_lowbo[ii] = lodefault;\n      if(!easyout) {\n        lp->upbo[ii] = lp->orig_upbo[ii];\n        lp->lowbo[ii] = lp->orig_lowbo[ii];\n        lp->is_lower[ii] = TRUE;\n      }\n    }\n  }\n\n  /* Shift data left/up (delete) */\n  else if(usedmap != NULL) {\n    int k, offset = 0;\n    if(!isrow)\n      offset += lp->rows;\n    i = offset + 1;\n    for(k = firstActiveLink(usedmap); k != 0;\n        i++, k = nextActiveLink(usedmap, k)) {\n      ii = k + offset;\n      if(ii == i)\n        continue;\n      lp->upbo[i] = lp->upbo[ii];\n      lp->orig_upbo[i] = lp->orig_upbo[ii];\n      lp->lowbo[i] = lp->lowbo[ii];\n      lp->orig_lowbo[i] = lp->orig_lowbo[ii];\n      lp->solution[i] = lp->solution[ii];\n      lp->best_solution[i] = lp->best_solution[ii];\n      lp->is_lower[i] = lp->is_lower[ii];\n      if(lp->scalars != NULL)\n        lp->scalars[i] = lp->scalars[ii];\n    }\n    if(isrow) {\n      base = lp->rows + 1;\n      MEMMOVE(lp->upbo + i, lp->upbo + base, lp->columns);\n      MEMMOVE(lp->orig_upbo + i, lp->orig_upbo + base, lp->columns);\n      MEMMOVE(lp->lowbo + i, lp->lowbo + base, lp->columns);\n      MEMMOVE(lp->orig_lowbo + i, lp->orig_lowbo + base, lp->columns);\n      if(lp->model_is_valid) {\n        MEMMOVE(lp->solution + i, lp->solution + base, lp->columns);\n        MEMMOVE(lp->best_solution + i, lp->best_solution + base, lp->columns);\n      }\n      MEMMOVE(lp->is_lower + i, lp->is_lower + base, lp->columns);\n      if(lp->scalars != NULL)\n        MEMMOVE(lp->scalars + i, lp->scalars + base, lp->columns);\n    }\n  }\n\n  else if(delta < 0) {\n\n    /* First make sure we don't cross the sum count border */\n    if(base-delta-1 > lp->sum)\n      delta = base - lp->sum - 1;\n\n    /* Shift the data*/\n    for(i = base; i <= lp->sum + delta; i++) {\n      ii = i - delta;\n      lp->upbo[i] = lp->upbo[ii];\n      lp->orig_upbo[i] = lp->orig_upbo[ii];\n      lp->lowbo[i] = lp->lowbo[ii];\n      lp->orig_lowbo[i] = lp->orig_lowbo[ii];\n      lp->solution[i] = lp->solution[ii];\n      lp->best_solution[i] = lp->best_solution[ii];\n      lp->is_lower[i] = lp->is_lower[ii];\n      if(lp->scalars != NULL)\n        lp->scalars[i] = lp->scalars[ii];\n    }\n\n  }\n\n  lp->sum += delta;\n\n  lp->matA->row_end_valid = FALSE;\n\n  return(TRUE);\n}\n\nSTATIC MYBOOL shift_basis(lprec *lp, int base, int delta, LLrec *usedmap, MYBOOL isrow)\n/* Note: Assumes that \"lp->sum\" and \"lp->rows\" HAVE NOT been updated to the new counts */\n{\n  int i, ii;\n  MYBOOL Ok = TRUE;\n\n  /* Don't bother to shift the basis if it is not yet ready */\n  if(!is_BasisReady(lp))\n    return( Ok );\n\n  /* Basis adjustments due to insertions (after actual row/column insertions) */\n  if(delta > 0) {\n\n    /* Determine if the basis becomes invalidated */\n    if(isrow)\n      set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT);\n\n    /* Shift and fix invalid basis references (increment higher order basic variable index) */\n    if(base <= lp->sum)\n      MEMMOVE(lp->is_basic + base + delta, lp->is_basic + base, lp->sum - base + 1);\n\n    /* Prevent CPU-expensive basis updating if this is the initial model creation */\n    if(!lp->model_is_pure || (lp->solvecount > 0))\n      for(i = 1; i <= lp->rows; i++) {\n        ii = lp->var_basic[i];\n        if(ii >= base)\n          lp->var_basic[i] += delta;\n      }\n\n    /* Update the basis (shift and extend) */\n    for(i = 0; i < delta; i++) {\n      ii = base + i;\n      lp->is_basic[ii] = isrow;\n      if(isrow)\n        lp->var_basic[lp->rows+1+i] = ii;\n    }\n\n  }\n  /* Basis adjustments due to deletions (after actual row/column deletions) */\n  else {\n    int j,k;\n\n    /* Fix invalid basis references (decrement high basic slack variable indexes),\n       but reset the entire basis if a deleted variable is found in the basis */\n    k = 0;\n    for(i = 1; i <= lp->rows; i++) {\n      ii = lp->var_basic[i];\n      lp->is_basic[ii] = FALSE;\n      if(ii >= base) {\n       /* Skip to next basis variable if this one is to be deleted */\n        if(ii < base-delta) {\n          set_action(&lp->spx_action, ACTION_REBASE);\n          continue;\n        }\n       /* Otherwise, update the index of the basic variable for deleted variables */\n        ii += delta;\n      }\n      k++;\n      lp->var_basic[k] = ii;\n    }\n\n    /* Set the new basis indicators */\n    i = k;\n    if(isrow)\n      i = MIN(k, lp->rows+delta);\n    for(; i > 0; i--) {\n      j = lp->var_basic[i];\n      lp->is_basic[j] = TRUE;\n    }\n\n    /* If a column was deleted from the basis then simply add back a non-basic\n       slack variable; do two scans, if necessary to avoid adding equality slacks */\n    if(!isrow && (k < lp->rows)) {\n      for(j = 0; j <= 1; j++)\n      for(i = 1; (i <= lp->rows) && (k < lp->rows); i++)\n        if(!lp->is_basic[i]) {\n          if(!is_constr_type(lp, i, EQ) || (j == 1)) {\n            k++;\n            lp->var_basic[k] = i;\n            lp->is_basic[i] = TRUE;\n          }\n        }\n      k = 0;\n    }\n\n    /* We are left with \"k\" indexes; if no basis variable was deleted, k=rows and the\n       inverse is still valid, if k+delta < 0 we do not have a valid\n       basis and must create one (in most usage modes this should not happen,\n       unless there is a bug) */\n    if(k+delta < 0)\n      Ok = FALSE;\n    if(isrow || (k != lp->rows))\n      set_action(&lp->spx_action, ACTION_REINVERT);\n\n  }\n  return(Ok);\n\n}\n\nSTATIC MYBOOL shift_rowdata(lprec *lp, int base, int delta, LLrec *usedmap)\n/* Note: Assumes that \"lp->rows\" HAS NOT been updated to the new count */\n{\n  int i, ii;\n\n  /* Shift sparse matrix row data */\n  if(lp->matA->is_roworder)\n    mat_shiftcols(lp->matA, &base, delta, usedmap);\n  else\n    mat_shiftrows(lp->matA, &base, delta, usedmap);\n\n  /* Shift data down (insert row), and set default values in positive delta-gap */\n  if(delta > 0) {\n\n    /* Shift row data */\n    for(ii = lp->rows; ii >= base; ii--) {\n      i = ii + delta;\n      lp->orig_rhs[i] = lp->orig_rhs[ii];\n      lp->rhs[i] = lp->rhs[ii];\n      lp->row_type[i] = lp->row_type[ii];\n    }\n\n    /* Set defaults (actual basis set in separate procedure) */\n    for(i = 0; i < delta; i++) {\n      ii = base + i;\n      lp->orig_rhs[ii] = 0;\n      lp->rhs[ii] = 0;\n      lp->row_type[ii] = ROWTYPE_EMPTY;\n    }\n  }\n\n  /* Shift data up (delete row) */\n  else if(usedmap != NULL) {\n    for(i = 1, ii = firstActiveLink(usedmap); ii != 0;\n        i++, ii = nextActiveLink(usedmap, ii)) {\n      if(i == ii)\n        continue;\n      lp->orig_rhs[i] = lp->orig_rhs[ii];\n      lp->rhs[i] = lp->rhs[ii];\n      lp->row_type[i] = lp->row_type[ii];\n    }\n    delta = i - lp->rows - 1;\n  }\n  else if(delta < 0) {\n\n    /* First make sure we don't cross the row count border */\n    if(base-delta-1 > lp->rows)\n      delta = base - lp->rows - 1;\n\n    /* Shift row data (don't shift basis indexes here; done in next step) */\n    for(i = base; i <= lp->rows + delta; i++) {\n      ii = i - delta;\n      lp->orig_rhs[i] = lp->orig_rhs[ii];\n      lp->rhs[i] = lp->rhs[ii];\n      lp->row_type[i] = lp->row_type[ii];\n    }\n  }\n\n  shift_basis(lp, base, delta, usedmap, TRUE);\n  shift_rowcoldata(lp, base, delta, usedmap, TRUE);\n  inc_rows(lp, delta);\n\n  return(TRUE);\n}\n\nSTATIC MYBOOL shift_coldata(lprec *lp, int base, int delta, LLrec *usedmap)\n/* Note: Assumes that \"lp->columns\" has NOT been updated to the new count */\n{\n  int i, ii;\n\n  if(lp->bb_totalnodes == 0)\n    free_duals(lp);\n\n  /* Shift A matrix data */\n  if(lp->matA->is_roworder)\n    mat_shiftrows(lp->matA, &base, delta, usedmap);\n  else\n    mat_shiftcols(lp->matA, &base, delta, usedmap);\n\n  /* Shift data right (insert), and set default values in positive delta-gap */\n  if(delta > 0) {\n\n    /* Fix variable priority data */\n    if((lp->var_priority != NULL) && (base <= lp->columns)) {\n      for(i = 0; i < lp->columns; i++)\n        if(lp->var_priority[i] >= base)\n          lp->var_priority[i] += delta;\n    }\n    if((lp->sos_priority != NULL) && (base <= lp->columns)) {\n      for(i = 0; i < lp->sos_vars; i++)\n        if(lp->sos_priority[i] >= base)\n          lp->sos_priority[i] += delta;\n    }\n\n    /* Fix invalid split variable data */\n    if((lp->var_is_free != NULL) && (base <= lp->columns)) {\n      for(i = 1; i <= lp->columns; i++)\n        if(abs(lp->var_is_free[i]) >= base)\n          lp->var_is_free[i] += my_chsign(lp->var_is_free[i] < 0, delta);\n    }\n\n    /* Shift column data right */\n    for(ii = lp->columns; ii >= base; ii--) {\n      i = ii + delta;\n      lp->var_type[i] = lp->var_type[ii];\n      lp->sc_lobound[i] = lp->sc_lobound[ii];\n      lp->orig_obj[i] = lp->orig_obj[ii];\n      if(lp->obj != NULL)\n        lp->obj[i] = lp->obj[ii];\n/*\n      if(lp->objfromvalue != NULL)\n        lp->objfromvalue[i] = lp->objfromvalue[ii];\n      if(lp->objfrom != NULL)\n        lp->objfrom[i] = lp->objfrom[ii];\n      if(lp->objtill != NULL)\n        lp->objtill[i] = lp->objtill[ii];\n*/\n      if(lp->var_priority != NULL)\n        lp->var_priority[i-1] = lp->var_priority[ii-1];\n      if(lp->bb_varbranch != NULL)\n        lp->bb_varbranch[i-1] = lp->bb_varbranch[ii-1];\n      if(lp->var_is_free != NULL)\n        lp->var_is_free[i] = lp->var_is_free[ii];\n      if(lp->best_solution != NULL)\n        lp->best_solution[lp->rows + i] = lp->best_solution[lp->rows + ii];\n    }\n\n    /* Set defaults */\n    for(i = 0; i < delta; i++) {\n      ii = base + i;\n      lp->var_type[ii] = ISREAL;\n      lp->sc_lobound[ii] = 0;\n      lp->orig_obj[ii] = 0;\n      if(lp->obj != NULL)\n        lp->obj[ii] = 0;\n/*\n      if(lp->objfromvalue != NULL)\n        lp->objfromvalue[ii] = 0;\n      if(lp->objfrom != NULL)\n        lp->objfrom[ii] = 0;\n      if(lp->objtill != NULL)\n        lp->objtill[ii] = 0;\n*/\n      if(lp->var_priority != NULL)\n        lp->var_priority[ii-1] = ii;\n      if(lp->bb_varbranch != NULL)\n        lp->bb_varbranch[ii-1] = BRANCH_DEFAULT;\n      if(lp->var_is_free != NULL)\n        lp->var_is_free[ii] = 0;\n      if(lp->best_solution != NULL)\n        lp->best_solution[lp->rows + ii] = 0;\n    }\n  }\n\n  /* Shift data left (delete) */\n  else if(usedmap != NULL) {\n    /* Assume there is no need to handle split columns, since we are doing\n       this only from presolve, which comes before splitting of columns. */\n\n    /* First update counts */\n    if(lp->int_vars + lp->sc_vars > 0)\n    for(ii = firstInactiveLink(usedmap); ii != 0; ii = nextInactiveLink(usedmap, ii)) {\n      if(is_int(lp, ii)) {\n        lp->int_vars--;\n        if(SOS_is_member(lp->SOS, 0, ii))\n          lp->sos_ints--;\n      }\n      if(is_semicont(lp, ii))\n        lp->sc_vars--;\n    }\n    /* Shift array members */\n    for(i = 1, ii = firstActiveLink(usedmap); ii != 0;\n        i++, ii = nextActiveLink(usedmap, ii)) {\n      if(i == ii)\n        continue;\n      lp->var_type[i] = lp->var_type[ii];\n      lp->sc_lobound[i] = lp->sc_lobound[ii];\n      lp->orig_obj[i] = lp->orig_obj[ii];\n      if(lp->obj != NULL)\n        lp->obj[i] = lp->obj[ii];\n/*\n      if(lp->objfromvalue != NULL)\n        lp->objfromvalue[i] = lp->objfromvalue[ii];\n      if(lp->objfrom != NULL)\n        lp->objfrom[i] = lp->objfrom[ii];\n      if(lp->objtill != NULL)\n        lp->objtill[i] = lp->objtill[ii];\n*/\n      if(lp->bb_varbranch != NULL)\n        lp->bb_varbranch[i-1] = lp->bb_varbranch[ii-1];\n      if(lp->var_is_free != NULL)\n        lp->var_is_free[i] = lp->var_is_free[ii];\n      if(lp->best_solution != NULL)\n        lp->best_solution[lp->rows + i] = lp->best_solution[lp->rows + ii];\n    }\n    /* Shift variable priority data */\n    if((lp->var_priority != NULL) || (lp->sos_priority != NULL)) {\n      int *colmap = NULL, k;\n      allocINT(lp, &colmap, lp->columns + 1, TRUE);\n      for(i = 1, ii = 0; i <= lp->columns; i++) {\n        if(isActiveLink(usedmap, i)) {\n          ii++;\n          colmap[i] = ii;\n        }\n      }\n      if(lp->var_priority != NULL) {\n        for(i = 0, ii = 0; i < lp->columns; i++) {\n          k = colmap[lp->var_priority[i]];\n          if(k > 0) {\n            lp->var_priority[ii] = k;\n            ii++;\n          }\n        }\n      }\n      if(lp->sos_priority != NULL) {\n        for(i = 0, ii = 0; i < lp->sos_vars; i++) {\n          k = colmap[lp->sos_priority[i]];\n          if(k > 0) {\n            lp->sos_priority[ii] = k;\n            ii++;\n          }\n        }\n        lp->sos_vars = ii;\n      }\n      FREE(colmap);\n    }\n\n    delta = i - lp->columns - 1;\n  }\n  else if(delta < 0) {\n\n    /* Fix invalid split variable data */\n    if(lp->var_is_free != NULL) {\n      for(i = 1; i <= lp->columns; i++)\n        if(abs(lp->var_is_free[i]) >= base)\n          lp->var_is_free[i] -= my_chsign(lp->var_is_free[i] < 0, delta);\n    }\n\n    /* Shift column data (excluding the basis) */\n    for(i = base; i < base-delta; i++) {\n      if(is_int(lp, i)) {\n        lp->int_vars--;\n        if(SOS_is_member(lp->SOS, 0, i))\n          lp->sos_ints--;\n      }\n      if(is_semicont(lp, i))\n        lp->sc_vars--;\n    }\n    for(i = base; i <= lp->columns + delta; i++) {\n      ii = i - delta;\n      lp->var_type[i] = lp->var_type[ii];\n      lp->sc_lobound[i] = lp->sc_lobound[ii];\n      lp->orig_obj[i] = lp->orig_obj[ii];\n      if(lp->obj != NULL)\n        lp->obj[i] = lp->obj[ii];\n/*\n      if(lp->objfromvalue != NULL)\n        lp->objfromvalue[i] = lp->objfromvalue[ii];\n      if(lp->objfrom != NULL)\n        lp->objfrom[i] = lp->objfrom[ii];\n      if(lp->objtill != NULL)\n        lp->objtill[i] = lp->objtill[ii];\n*/\n      if(lp->var_priority != NULL)\n        lp->var_priority[i-1] = lp->var_priority[ii-1];\n      if(lp->bb_varbranch != NULL)\n        lp->bb_varbranch[i-1] = lp->bb_varbranch[ii-1];\n      if(lp->var_is_free != NULL)\n        lp->var_is_free[i] = lp->var_is_free[ii];\n      if(lp->best_solution != NULL)\n        lp->best_solution[lp->rows + i] = lp->best_solution[lp->rows + ii];\n    }\n\n    /* Fix invalid variable priority data */\n    if(lp->var_priority != NULL) {\n      for(i = 0, ii = 0; i < lp->columns; i++)\n        if(lp->var_priority[i] > base - delta)\n          lp->var_priority[ii++] = lp->var_priority[i] + delta;\n        else if(lp->var_priority[i] < base)\n          lp->var_priority[ii++] = lp->var_priority[i];\n    }\n    if(lp->sos_priority != NULL) {\n      for(i = 0, ii = 0; i < lp->sos_vars; i++) {\n        if(lp->sos_priority[i] > base - delta)\n          lp->sos_priority[ii++] = lp->sos_priority[i] + delta;\n        else if(lp->sos_priority[i] < base)\n          lp->sos_priority[ii++] = lp->sos_priority[i];\n      }\n      lp->sos_vars = ii;\n    }\n\n  }\n\n  shift_basis(lp, lp->rows+base, delta, usedmap, FALSE);\n  if(SOS_count(lp) > 0)\n    SOS_shift_col(lp->SOS, 0, base, delta, usedmap, FALSE);\n  shift_rowcoldata(lp, lp->rows+base, delta, usedmap, FALSE);\n  inc_columns(lp, delta);\n\n  return( TRUE );\n}\n\n/* Utility group for incrementing row and column vector storage space */\nSTATIC void inc_rows(lprec *lp, int delta)\n{\n  int i;\n\n  if(lp->names_used && (lp->row_name != NULL))\n    for(i = lp->rows + delta; i > lp->rows; i--)\n      lp->row_name[i] = NULL;\n\n  lp->rows += delta;\n  if(lp->matA->is_roworder)\n    lp->matA->columns += delta;\n  else\n    lp->matA->rows += delta;\n}\n\nSTATIC void inc_columns(lprec *lp, int delta)\n{\n  int i;\n\n  if(lp->names_used && (lp->col_name != NULL))\n    for(i = lp->columns + delta; i > lp->columns; i--)\n      lp->col_name[i] = NULL;\n\n  lp->columns += delta;\n  if(lp->matA->is_roworder)\n    lp->matA->rows += delta;\n  else\n    lp->matA->columns += delta;\n  if(get_Lrows(lp) > 0)\n    lp->matL->columns += delta;\n}\n\nSTATIC MYBOOL inc_rowcol_space(lprec *lp, int delta, MYBOOL isrows)\n{\n  int i, oldrowcolalloc, rowcolsum;\n\n  /* Get rid of dual arrays */\n  if(lp->solvecount > 0)\n    free_duals(lp);\n\n  /* Set constants */\n  oldrowcolalloc = lp->sum_alloc;\n  lp->sum_alloc += delta;\n  rowcolsum = lp->sum_alloc + 1;\n\n  /* Reallocate lp memory */\n  if(!allocREAL(lp, &lp->upbo, rowcolsum, AUTOMATIC) ||\n     !allocREAL(lp, &lp->orig_upbo, rowcolsum, AUTOMATIC) ||\n     !allocREAL(lp, &lp->lowbo, rowcolsum, AUTOMATIC) ||\n     !allocREAL(lp, &lp->orig_lowbo, rowcolsum, AUTOMATIC) ||\n     !allocREAL(lp, &lp->solution, rowcolsum, AUTOMATIC) ||\n     !allocREAL(lp, &lp->best_solution, rowcolsum, AUTOMATIC) ||\n     !allocMYBOOL(lp, &lp->is_basic, rowcolsum, AUTOMATIC) ||\n     !allocMYBOOL(lp, &lp->is_lower, rowcolsum, AUTOMATIC) ||\n     ((lp->scalars != NULL) && !allocREAL(lp, &lp->scalars, rowcolsum, AUTOMATIC)))\n    return( FALSE );\n\n  /* Fill in default values, where appropriate */\n  for(i = oldrowcolalloc+1; i < rowcolsum; i++) {\n    lp->upbo[i] = lp->infinite;\n    lp->orig_upbo[i] = lp->upbo[i];\n    lp->lowbo[i] = 0;\n    lp->orig_lowbo[i] = lp->lowbo[i];\n    lp->is_basic[i] = FALSE;\n    lp->is_lower[i] = TRUE;\n  }\n\n  /* Deal with scalars; the vector can be NULL and also contains Lagrangean information */\n  if(lp->scalars != NULL) {\n    for(i = oldrowcolalloc+1; i < rowcolsum; i++)\n      lp->scalars[i] = 1;\n    if(oldrowcolalloc == 0)\n      lp->scalars[0] = 1;\n  }\n\n  return( inc_presolve_space(lp, delta, isrows) &&\n           resizePricer(lp) );\n}\n\nSTATIC MYBOOL inc_lag_space(lprec *lp, int deltarows, MYBOOL ignoreMAT)\n{\n  int newsize;\n\n  if(deltarows > 0) {\n\n    newsize = get_Lrows(lp) + deltarows;\n\n    /* Reallocate arrays */\n    if(!allocREAL(lp, &lp->lag_rhs, newsize+1, AUTOMATIC) ||\n       !allocREAL(lp, &lp->lambda, newsize+1, AUTOMATIC) ||\n       !allocINT(lp, &lp->lag_con_type, newsize+1, AUTOMATIC))\n      return( FALSE );\n\n    /* Reallocate the matrix (note that the row scalars are stored at index 0) */\n    if(!ignoreMAT) {\n      if(lp->matL == NULL)\n        lp->matL = mat_create(lp, newsize, lp->columns, lp->epsvalue);\n      else\n        inc_matrow_space(lp->matL, deltarows);\n    }\n    lp->matL->rows += deltarows;\n\n  }\n  /* Handle column count expansion as special case */\n  else if(!ignoreMAT) {\n    inc_matcol_space(lp->matL, lp->columns_alloc-lp->matL->columns_alloc+1);\n  }\n\n\n  return( TRUE );\n}\n\nSTATIC MYBOOL inc_row_space(lprec *lp, int deltarows)\n{\n  int    i, rowsum, oldrowsalloc;\n  MYBOOL ok = TRUE;\n\n  /* Adjust lp row structures */\n  i = lp->rows_alloc+deltarows;\n  if(lp->matA->is_roworder) {\n    i -= lp->matA->columns_alloc;\n    SETMIN(i, deltarows);\n    if(i > 0)\n      inc_matcol_space(lp->matA, i);\n    rowsum = lp->matA->columns_alloc;\n  }\n  else {\n#if 0\n    if((lp->rows_alloc > 0) && (lp->rows + deltarows > lp->rows_alloc))\n      i = deltarows; /* peno 25/12/06 */\n    else\n#endif\n      i -= lp->matA->rows_alloc;\n    SETMIN(i, deltarows);\n    if(i > 0)\n      inc_matrow_space(lp->matA, i);\n    rowsum = lp->matA->rows_alloc;\n  }\n  if(lp->rows+deltarows > lp->rows_alloc) {\n\n    rowsum++;\n    oldrowsalloc = lp->rows_alloc;\n    lp->rows_alloc = rowsum;\n    deltarows = rowsum - oldrowsalloc;\n    rowsum++;\n\n    if(!allocREAL(lp, &lp->orig_rhs, rowsum, AUTOMATIC) ||\n       !allocLREAL(lp, &lp->rhs, rowsum, AUTOMATIC) ||\n       !allocINT(lp, &lp->row_type, rowsum, AUTOMATIC) ||\n       !allocINT(lp, &lp->var_basic, rowsum, AUTOMATIC))\n      return( FALSE );\n\n    if(oldrowsalloc == 0) {\n      lp->var_basic[0] = AUTOMATIC; /*TRUE;*/  /* Indicates default basis */\n      lp->orig_rhs[0] = 0;\n      lp->row_type[0] = ROWTYPE_OFMIN;\n    }\n    for(i = oldrowsalloc+1; i < rowsum; i++) {\n      lp->orig_rhs[i] = 0;\n      lp->rhs[i] = 0;\n      lp->row_type[i] = ROWTYPE_EMPTY;\n      lp->var_basic[i] = i;\n    }\n\n    /* Adjust hash name structures */\n    if(lp->names_used && (lp->row_name != NULL)) {\n\n      /* First check the hash table */\n      if(lp->rowname_hashtab->size < lp->rows_alloc) {\n        hashtable *ht;\n\n        ht = copy_hash_table(lp->rowname_hashtab, lp->row_name, lp->rows_alloc + 1);\n        if(ht == NULL) {\n          lp->spx_status = NOMEMORY;\n          return( FALSE );\n        }\n        free_hash_table(lp->rowname_hashtab);\n        lp->rowname_hashtab = ht;\n      }\n\n      /* Then the string storage (i.e. pointer to the item's hash structure) */\n      lp->row_name = (hashelem **) realloc(lp->row_name, (rowsum) * sizeof(*lp->row_name));\n      if(lp->row_name == NULL) {\n        lp->spx_status = NOMEMORY;\n        return( FALSE );\n      }\n      for(i = oldrowsalloc + 1; i < rowsum; i++)\n        lp->row_name[i] = NULL;\n    }\n\n    ok = inc_rowcol_space(lp, deltarows, TRUE);\n\n  }\n  return(ok);\n}\n\nSTATIC MYBOOL inc_col_space(lprec *lp, int deltacols)\n{\n  int i,colsum, oldcolsalloc;\n\n  i = lp->columns_alloc+deltacols;\n  if(lp->matA->is_roworder) {\n    i -= lp->matA->rows_alloc;\n    SETMIN(i, deltacols);\n    if(i > 0)\n      inc_matrow_space(lp->matA, i);\n    colsum = lp->matA->rows_alloc;\n  }\n  else {\n    i -= lp->matA->columns_alloc;\n    SETMIN(i, deltacols);\n    if(i > 0)\n      inc_matcol_space(lp->matA, i);\n    colsum = lp->matA->columns_alloc;\n  }\n\n  if(lp->columns+deltacols >= lp->columns_alloc) {\n\n    colsum++;\n    oldcolsalloc = lp->columns_alloc;\n    lp->columns_alloc = colsum;\n    deltacols = colsum - oldcolsalloc;\n    colsum++;\n\n    /* Adjust hash name structures */\n    if(lp->names_used && (lp->col_name != NULL)) {\n\n      /* First check the hash table */\n      if(lp->colname_hashtab->size < lp->columns_alloc) {\n        hashtable *ht;\n\n        ht = copy_hash_table(lp->colname_hashtab, lp->col_name, lp->columns_alloc + 1);\n        if(ht != NULL) {\n          free_hash_table(lp->colname_hashtab);\n          lp->colname_hashtab = ht;\n        }\n      }\n\n      /* Then the string storage (i.e. pointer to the item's hash structure) */\n      lp->col_name = (hashelem **) realloc(lp->col_name, (colsum) * sizeof(*lp->col_name));\n      for(i = oldcolsalloc+1; i < colsum; i++)\n        lp->col_name[i] = NULL;\n    }\n\n    if(!allocREAL(lp, &lp->orig_obj, colsum, AUTOMATIC) ||\n       !allocMYBOOL(lp, &lp->var_type, colsum, AUTOMATIC) ||\n       !allocREAL(lp, &lp->sc_lobound, colsum, AUTOMATIC) ||\n       ((lp->obj != NULL) && !allocREAL(lp, &lp->obj, colsum, AUTOMATIC)) ||\n       ((lp->var_priority != NULL) && !allocINT(lp, &lp->var_priority, colsum-1, AUTOMATIC)) ||\n       ((lp->var_is_free != NULL) && !allocINT(lp, &lp->var_is_free, colsum, AUTOMATIC)) ||\n       ((lp->bb_varbranch != NULL) && !allocMYBOOL(lp, &lp->bb_varbranch, colsum-1, AUTOMATIC)))\n      return( FALSE );\n\n    /* Make sure that Lagrangean constraints have the same number of columns */\n    if(get_Lrows(lp) > 0)\n      inc_lag_space(lp, 0, FALSE);\n\n    /* Update column pointers */\n    for(i = MIN(oldcolsalloc, lp->columns) + 1; i < colsum; i++) {\n      lp->orig_obj[i] = 0;\n      if(lp->obj != NULL)\n        lp->obj[i] = 0;\n      lp->var_type[i] = ISREAL;\n      lp->sc_lobound[i] = 0;\n      if(lp->var_priority != NULL)\n        lp->var_priority[i-1] = i;\n    }\n\n    if(lp->var_is_free != NULL) {\n      for(i = oldcolsalloc+1; i < colsum; i++)\n        lp->var_is_free[i] = 0;\n    }\n\n    if(lp->bb_varbranch != NULL) {\n      for(i = oldcolsalloc; i < colsum-1; i++)\n        lp->bb_varbranch[i] = BRANCH_DEFAULT;\n    }\n\n    inc_rowcol_space(lp, deltacols, FALSE);\n\n  }\n  return(TRUE);\n}\n\n/* Problem manipulation routines */\n\nMYBOOL __WINAPI set_obj(lprec *lp, int colnr, REAL value)\n{\n  if(colnr <= 0)\n    colnr = set_rh(lp, 0, value);\n  else\n    colnr = set_mat(lp, 0, colnr, value);\n  return((MYBOOL) colnr);\n}\n\nMYBOOL __WINAPI set_obj_fnex(lprec *lp, int count, REAL *row, int *colno)\n{\n  MYBOOL chsgn = is_maxim(lp);\n  int    i, ix;\n  REAL   value;\n\n  if(row == NULL)\n    return( FALSE );\n\n  else if(colno == NULL) {\n    if(count <= 0)\n      count = lp->columns;\n    for(i = 1; i <= count; i++) {\n      value = row[i];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, lp->matA->epsvalue);\n#endif\n      lp->orig_obj[i] = my_chsign(chsgn, scaled_mat(lp, value, 0, i));\n    }\n  }\n  else {\n    MEMCLEAR(lp->orig_obj, lp->columns+1);\n    for(i = 0; i < count; i++) {\n      ix = colno[i];\n      value = row[i];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, lp->matA->epsvalue);\n#endif\n      lp->orig_obj[ix] = my_chsign(chsgn, scaled_mat(lp, value, 0, ix));\n    }\n  }\n\n  return(TRUE);\n}\n\nMYBOOL __WINAPI set_obj_fn(lprec *lp, REAL *row)\n{\n  return( set_obj_fnex(lp, 0, row, NULL) );\n}\n\nMYBOOL __WINAPI str_set_obj_fn(lprec *lp, char *row_string)\n{\n  int    i;\n  MYBOOL ret = TRUE;\n  REAL   *arow;\n  char   *p, *newp;\n\n  allocREAL(lp, &arow, lp->columns + 1, FALSE);\n  p = row_string;\n  for(i = 1; i <= lp->columns; i++) {\n    arow[i] = (REAL) strtod(p, &newp);\n    if(p == newp) {\n      report(lp, IMPORTANT, \"str_set_obj_fn: Bad string %s\\n\", p);\n      lp->spx_status = DATAIGNORED;\n      ret = FALSE;\n      break;\n    }\n    else\n      p = newp;\n  }\n  if(lp->spx_status != DATAIGNORED)\n    ret = set_obj_fn(lp, arow);\n  FREE(arow);\n  return( ret );\n}\n\nSTATIC MYBOOL append_columns(lprec *lp, int deltacolumns)\n{\n  if(!inc_col_space(lp, deltacolumns))\n    return( FALSE );\n  varmap_add(lp, lp->sum+1, deltacolumns);\n  shift_coldata(lp, lp->columns+1, deltacolumns, NULL);\n  return( TRUE );\n}\n\nSTATIC MYBOOL append_rows(lprec *lp, int deltarows)\n{\n  if(!inc_row_space(lp, deltarows))\n    return( FALSE );\n  varmap_add(lp, lp->rows+1, deltarows);\n  shift_rowdata(lp, lp->rows+1, deltarows, NULL);\n\n  return( TRUE );\n}\n\nMYBOOL __WINAPI set_add_rowmode(lprec *lp, MYBOOL turnon)\n{\n  if((lp->solvecount == 0) && (turnon ^ lp->matA->is_roworder))\n    return( mat_transpose(lp->matA) );\n  else\n    return( FALSE );\n}\n\nMYBOOL __WINAPI is_add_rowmode(lprec *lp)\n{\n  return(lp->matA->is_roworder);\n}\n\nMYBOOL __WINAPI set_row(lprec *lp, int rownr, REAL *row)\n{\n  if((rownr < 0) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"set_row: Row %d out of range\\n\", rownr);\n    return( FALSE );\n  }\n  if(rownr == 0)\n    return( set_obj_fn(lp, row) );\n  else\n    return( mat_setrow(lp->matA, rownr, lp->columns, row, NULL, TRUE, TRUE) );\n}\n\nMYBOOL __WINAPI set_rowex(lprec *lp, int rownr, int count, REAL *row, int *colno)\n{\n  if((rownr < 0) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"set_rowex: Row %d out of range\\n\", rownr);\n    return( FALSE );\n  }\n  if(rownr == 0)\n    return( set_obj_fnex(lp, count, row, colno) );\n  else\n    return( mat_setrow(lp->matA, rownr, count, row, colno, TRUE, TRUE) );\n}\n\nMYBOOL __WINAPI add_constraintex(lprec *lp, int count, REAL *row, int *colno, int constr_type, REAL rh)\n{\n  int    n;\n  MYBOOL status = FALSE;\n\n  if(!(constr_type == LE || constr_type == GE || constr_type == EQ)) {\n    report(lp, IMPORTANT, \"add_constraintex: Invalid %d constraint type\\n\", constr_type);\n    return( status );\n  }\n\n  /* Prepare for a new row */\n  if(!append_rows(lp, 1))\n    return( status );\n\n  /* Set constraint parameters, fix the slack */\n  if((constr_type & ROWTYPE_CONSTRAINT) == EQ) {\n    lp->equalities++;\n    lp->orig_upbo[lp->rows] = 0;\n    lp->upbo[lp->rows] = 0;\n  }\n  lp->row_type[lp->rows] = constr_type;\n\n  if(is_chsign(lp, lp->rows) && (rh != 0))\n    lp->orig_rhs[lp->rows] = -rh;\n  else\n    lp->orig_rhs[lp->rows] = rh;\n\n  /* Insert the non-zero constraint values */\n  if(colno == NULL && row != NULL)\n    n = lp->columns;\n  else\n    n = count;\n  mat_appendrow(lp->matA, n, row, colno, my_chsign(is_chsign(lp, lp->rows), 1.0), TRUE);\n  if(!lp->varmap_locked)\n    presolve_setOrig(lp, lp->rows, lp->columns);\n\n#ifdef Paranoia\n  if(lp->matA->is_roworder)\n    n = lp->matA->columns;\n  else\n    n = lp->matA->rows;\n  if(lp->rows != n) {\n    report(lp, SEVERE, \"add_constraintex: Row count mismatch %d vs %d\\n\",\n                       lp->rows, n);\n  }\n  else if(is_BasisReady(lp) && !verify_basis(lp))\n    report(lp, SEVERE, \"add_constraintex: Invalid basis detected for row %d\\n\", lp->rows);\n  else\n#endif\n  status = TRUE;\n\n  return( status );\n}\n\nMYBOOL __WINAPI add_constraint(lprec *lp, REAL *row, int constr_type, REAL rh)\n{\n  return( add_constraintex(lp, 0, row, NULL, constr_type, rh) );\n}\n\nMYBOOL __WINAPI str_add_constraint(lprec *lp, char *row_string, int constr_type, REAL rh)\n{\n  int    i;\n  char   *p, *newp;\n  REAL   *aRow;\n  MYBOOL status = FALSE;\n\n  allocREAL(lp, &aRow, lp->columns + 1, FALSE);\n  p = row_string;\n\n  for(i = 1; i <= lp->columns; i++) {\n    aRow[i] = (REAL) strtod(p, &newp);\n    if(p == newp) {\n      report(lp, IMPORTANT, \"str_add_constraint: Bad string '%s'\\n\", p);\n      lp->spx_status = DATAIGNORED;\n      break;\n    }\n    else\n      p = newp;\n  }\n  if(lp->spx_status != DATAIGNORED)\n    status = add_constraint(lp, aRow, constr_type, rh);\n  FREE(aRow);\n\n  return(status);\n}\n\nSTATIC MYBOOL del_constraintex(lprec *lp, LLrec *rowmap)\n{\n  int i;\n\n  if(lp->equalities > 0)\n  for(i = firstInactiveLink(rowmap); i != 0; i = nextInactiveLink(rowmap, i)) {\n    if(is_constr_type(lp, i, EQ)) {\n#ifdef Paranoia\n      if(lp->equalities == 0)\n        report(lp, SEVERE, \"del_constraintex: Invalid count of equality constraints\\n\");\n#endif\n       lp->equalities--;\n    }\n  }\n\n  varmap_delete(lp, 1, -1, rowmap);\n  shift_rowdata(lp, 1, -1, rowmap);\n  if(!lp->varmap_locked) {\n    presolve_setOrig(lp, lp->rows, lp->columns);\n    if(lp->names_used)\n      del_varnameex(lp, lp->row_name, lp->rows, lp->rowname_hashtab, 0, rowmap);\n  }\n\n#ifdef Paranoia\n  if(is_BasisReady(lp) && !verify_basis(lp))\n    report(lp, SEVERE, \"del_constraintex: Invalid basis detected\\n\");\n#endif\n\n  return(TRUE);\n}\nMYBOOL __WINAPI del_constraint(lprec *lp, int rownr)\n{\n  MYBOOL preparecompact = (MYBOOL) (rownr < 0);\n\n  if(preparecompact)\n    rownr = -rownr;\n  if((rownr < 1) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"del_constraint: Attempt to delete non-existing constraint %d\\n\", rownr);\n    return(FALSE);\n  }\n  /*\n  if(lp->matA->is_roworder) {\n    report(lp, IMPORTANT, \"del_constraint: Cannot delete constraint while in row entry mode.\\n\");\n    return(FALSE);\n  }\n  */\n\n  if(is_constr_type(lp, rownr, EQ) && (lp->equalities > 0))\n    lp->equalities--;\n\n  varmap_delete(lp, my_chsign(preparecompact, rownr), -1, NULL);\n  shift_rowdata(lp, my_chsign(preparecompact, rownr), -1, NULL);\n\n/*\n   peno 04.10.07\n   Fixes a problem with del_constraint.\n   Constraints names were not shifted and reported variable result was incorrect.\n   See UnitTest1, UnitTest2\n\n   min: -2 x3;\n\n   c1: +x2 -x1 <= 10;\n   c: 0 x3 <= 0;\n   c2: +x3 +x2 +x1 <= 20;\n\n   2 <= x3 <= 3;\n   x1 <= 30;\n\n   // del_constraint(lp, 2);\n\n   // See write_LP and print_solution result\n\n   // To fix, commented if(!lp->varmap_locked)\n\n*/\n  if(!lp->varmap_locked)\n  {\n    presolve_setOrig(lp, lp->rows, lp->columns);\n    if(lp->names_used)\n      del_varnameex(lp, lp->row_name, lp->rows, lp->rowname_hashtab, rownr, NULL);\n  }\n\n#ifdef Paranoia\n  if(is_BasisReady(lp) && !verify_basis(lp))\n    report(lp, SEVERE, \"del_constraint: Invalid basis detected at row %d\\n\", rownr);\n#endif\n\n  return(TRUE);\n}\n\nMYBOOL __WINAPI add_lag_con(lprec *lp, REAL *row, int con_type, REAL rhs)\n{\n  int  k;\n  REAL sign;\n\n  if(con_type == LE || con_type == EQ)\n    sign = 1;\n  else if(con_type == GE)\n    sign = -1;\n  else {\n    report(lp, IMPORTANT, \"add_lag_con: Constraint type %d not implemented\\n\", con_type);\n    return(FALSE);\n  }\n\n  inc_lag_space(lp, 1, FALSE);\n\n  k = get_Lrows(lp);\n  lp->lag_rhs[k] = rhs * sign;\n  mat_appendrow(lp->matL, lp->columns, row, NULL, sign, TRUE);\n  lp->lambda[k] = 0;\n  lp->lag_con_type[k] = con_type;\n\n  return(TRUE);\n}\n\nMYBOOL __WINAPI str_add_lag_con(lprec *lp, char *row_string, int con_type, REAL rhs)\n{\n  int    i;\n  MYBOOL ret = TRUE;\n  REAL   *a_row;\n  char   *p, *new_p;\n\n  allocREAL(lp, &a_row, lp->columns + 1, FALSE);\n  p = row_string;\n\n  for(i = 1; i <= lp->columns; i++) {\n    a_row[i] = (REAL) strtod(p, &new_p);\n    if(p == new_p) {\n      report(lp, IMPORTANT, \"str_add_lag_con: Bad string '%s'\\n\", p);\n      lp->spx_status = DATAIGNORED;\n      ret = FALSE;\n      break;\n    }\n    else\n      p = new_p;\n  }\n  if(lp->spx_status != DATAIGNORED)\n    ret = add_lag_con(lp, a_row, con_type, rhs);\n  FREE(a_row);\n  return( ret );\n}\n\n/* INLINE */ MYBOOL is_splitvar(lprec *lp, int colnr)\n/* Two cases handled by var_is_free:\n\n   1) LB:-Inf / UB:<Inf variables\n      No helper column created, sign of var_is_free set negative with index to itself.\n   2) LB:-Inf / UB: Inf (free) variables\n      Sign of var_is_free set positive with index to new helper column,\n      helper column created with negative var_is_free with index to the original column.\n\n   This function helps identify the helper column in 2).\n*/\n{\n   return((MYBOOL) ((lp->var_is_free != NULL) &&\n                    (lp->var_is_free[colnr] < 0) && (-lp->var_is_free[colnr] != colnr)));\n}\n\nvoid del_splitvars(lprec *lp)\n{\n  int j, jj, i;\n\n  if(lp->var_is_free != NULL) {\n    for(j = lp->columns; j >= 1; j--)\n      if(is_splitvar(lp, j)) {\n        /* Check if we need to modify the basis */\n        jj = lp->rows+abs(lp->var_is_free[j]);\n        i = lp->rows+j;\n        if(lp->is_basic[i] && !lp->is_basic[jj]) {\n          i = findBasisPos(lp, i, NULL);\n          set_basisvar(lp, i, jj);\n        }\n        /* Delete the helper column */\n        del_column(lp, j);\n      }\n    FREE(lp->var_is_free);\n  }\n}\n\nMYBOOL __WINAPI set_column(lprec *lp, int colnr, REAL *column)\n{\n  return( mat_setcol(lp->matA, colnr, lp->rows, column, NULL, TRUE, TRUE) );\n}\n\nMYBOOL __WINAPI set_columnex(lprec *lp, int colnr, int count, REAL *column, int *rowno)\n{\n  return( mat_setcol(lp->matA, colnr, count, column, rowno, TRUE, TRUE) );\n}\n\nMYBOOL __WINAPI add_columnex(lprec *lp, int count, REAL *column, int *rowno)\n/* This function adds a data column to the current model; three cases handled:\n\n    1: Prepare for column data by setting column = NULL\n    2: Dense vector indicated by (rowno == NULL) over 0..count+get_Lrows() elements\n    3: Sparse vector set over row vectors rowno, over 0..count-1 elements.\n\n   NB! If the column has only one entry, this should be handled as\n       a bound, but this currently is not the case  */\n{\n  MYBOOL status = FALSE;\n\n /* Prepare and shift column vectors */\n  if(!append_columns(lp, 1))\n    return( status );\n\n /* Append sparse regular constraint values */\n  if(mat_appendcol(lp->matA, count, column, rowno, 1.0, TRUE) < 0)\n    report(lp, SEVERE, \"add_columnex: Data column %d supplied in non-ascending row index order.\\n\",\n                       lp->columns);\n  else\n#ifdef Paranoia\n  if(lp->columns != (lp->matA->is_roworder ? lp->matA->rows : lp->matA->columns)) {\n    report(lp, SEVERE, \"add_columnex: Column count mismatch %d vs %d\\n\",\n                       lp->columns, (lp->matA->is_roworder ? lp->matA->rows : lp->matA->columns));\n  }\n  else if(is_BasisReady(lp) && (lp->P1extraDim == 0) && !verify_basis(lp))\n    report(lp, SEVERE, \"add_columnex: Invalid basis detected for column %d\\n\",\n                       lp->columns);\n  else\n#endif\n    status = TRUE;\n\n  if(!lp->varmap_locked)\n    presolve_setOrig(lp, lp->rows, lp->columns);\n\n  return( status );\n}\n\nMYBOOL __WINAPI add_column(lprec *lp, REAL *column)\n{\n  del_splitvars(lp);\n  return(add_columnex(lp, lp->rows, column, NULL));\n}\n\nMYBOOL __WINAPI str_add_column(lprec *lp, char *col_string)\n{\n  int  i;\n  MYBOOL ret = TRUE;\n  REAL *aCol;\n  char *p, *newp;\n\n  allocREAL(lp, &aCol, lp->rows + 1, FALSE);\n  p = col_string;\n\n  for(i = 0; i <= lp->rows; i++) {\n    aCol[i] = (REAL) strtod(p, &newp);\n    if(p == newp) {\n      report(lp, IMPORTANT, \"str_add_column: Bad string '%s'\\n\", p);\n      lp->spx_status = DATAIGNORED;\n      ret = FALSE;\n      break;\n    }\n    else\n      p = newp;\n  }\n  if(lp->spx_status != DATAIGNORED)\n    ret = add_column(lp, aCol);\n  FREE(aCol);\n  return( ret );\n}\n\nSTATIC MYBOOL del_varnameex(lprec *lp, hashelem **namelist, int items, hashtable *ht, int varnr, LLrec *varmap)\n{\n  int i, n;\n\n  /* First drop hash table entries of the deleted variables */\n  if(varmap != NULL)\n    i = firstInactiveLink(varmap);\n  else\n    i = varnr;\n  while(i > 0) {\n    if(namelist[i] != NULL) {\n      if(namelist[i]->name != NULL)\n        drophash(namelist[i]->name, namelist, ht);\n    }\n    if(varmap != NULL)\n      i = nextInactiveLink(varmap, i);\n    else\n      i = 0;\n  }\n\n  /* Then compress the name list */\n  if(varmap != NULL) {\n    i = firstInactiveLink(varmap);\n    n = nextActiveLink(varmap, i);\n    varnr = i;\n  }\n  else {\n    i = varnr;\n    n = i + 1;\n  }\n  while(n != 0) {\n    namelist[i] = namelist[n];\n    if((namelist[i] != NULL) && (namelist[i]->index > varnr))\n      namelist[i]->index -= n - i;\n    i++;\n    if(varmap != NULL)\n      n = nextActiveLink(varmap, i);\n    else if(n <= items) /* items has been updated for the new count */\n      n++;\n    else\n      n = 0;\n  }\n\n  return( TRUE );\n}\nSTATIC MYBOOL del_columnex(lprec *lp, LLrec *colmap)\n{\n  varmap_delete(lp, lp->rows+1, -1, colmap);\n  shift_coldata(lp, 1, -1, colmap);\n  if(!lp->varmap_locked) {\n    presolve_setOrig(lp, lp->rows, lp->columns);\n    if(lp->names_used)\n      del_varnameex(lp, lp->col_name, lp->columns, lp->colname_hashtab, 0, colmap);\n  }\n#ifdef Paranoia\n  if(is_BasisReady(lp) && (lp->P1extraDim == 0) && !verify_basis(lp))\n    report(lp, SEVERE, \"del_columnex: Invalid basis detected\\n\");\n#endif\n\n  return(TRUE);\n}\nMYBOOL __WINAPI del_column(lprec *lp, int colnr)\n{\n  MYBOOL preparecompact = (MYBOOL) (colnr < 0);\n\n  if(preparecompact)\n    colnr = -colnr;\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"del_column: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n  /*\n  if(lp->matA->is_roworder) {\n    report(lp, IMPORTANT, \"del_column: Cannot delete column while in row entry mode.\\n\");\n    return(FALSE);\n  }\n  */\n\n  if((lp->var_is_free != NULL) && (lp->var_is_free[colnr] > 0))\n    del_column(lp, lp->var_is_free[colnr]); /* delete corresponding split column (is always after this column) */\n\n  varmap_delete(lp, my_chsign(preparecompact, lp->rows+colnr), -1, NULL);\n  shift_coldata(lp, my_chsign(preparecompact, colnr), -1, NULL);\n  if(!lp->varmap_locked) {\n    presolve_setOrig(lp, lp->rows, lp->columns);\n    if(lp->names_used)\n      del_varnameex(lp, lp->col_name, lp->columns, lp->colname_hashtab, colnr, NULL);\n  }\n#ifdef Paranoia\n  if(is_BasisReady(lp) && (lp->P1extraDim == 0) && !verify_basis(lp))\n    report(lp, SEVERE, \"del_column: Invalid basis detected at column %d (%d)\\n\", colnr, lp->columns);\n#endif\n\n  return(TRUE);\n}\n\nvoid __WINAPI set_simplextype(lprec *lp, int simplextype)\n{\n  lp->simplex_strategy = simplextype;\n}\n\nint __WINAPI get_simplextype(lprec *lp)\n{\n  return(lp->simplex_strategy);\n}\n\nvoid __WINAPI set_preferdual(lprec *lp, MYBOOL dodual)\n{\n  if(dodual & TRUE)\n    lp->simplex_strategy = SIMPLEX_DUAL_DUAL;\n  else\n    lp->simplex_strategy = SIMPLEX_PRIMAL_PRIMAL;\n}\n\nvoid __WINAPI set_bounds_tighter(lprec *lp, MYBOOL tighten)\n{\n  lp->tighten_on_set = tighten;\n}\nMYBOOL __WINAPI get_bounds_tighter(lprec *lp)\n{\n  return(lp->tighten_on_set);\n}\n\nMYBOOL __WINAPI set_upbo(lprec *lp, int colnr, REAL value)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"set_upbo: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n#ifdef DoBorderRounding\n  if(fabs(value) < lp->infinite)\n    value = my_avoidtiny(value, lp->matA->epsvalue);\n#endif\n  value = scaled_value(lp, value, lp->rows + colnr);\n  if(lp->tighten_on_set) {\n    if(value < lp->orig_lowbo[lp->rows + colnr]) {\n      report(lp, IMPORTANT, \"set_upbo: Upperbound must be >= lowerbound\\n\");\n      return(FALSE);\n    }\n    if(value < lp->orig_upbo[lp->rows + colnr]) {\n      set_action(&lp->spx_action, ACTION_REBASE);\n      lp->orig_upbo[lp->rows + colnr] = value;\n    }\n  }\n  else\n  {\n    set_action(&lp->spx_action, ACTION_REBASE);\n    if(value > lp->infinite)\n      value = lp->infinite;\n    lp->orig_upbo[lp->rows + colnr] = value;\n  }\n  return(TRUE);\n}\n\nREAL __WINAPI get_upbo(lprec *lp, int colnr)\n{\n  REAL value;\n\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"get_upbo: Column %d out of range\\n\", colnr);\n    return(0);\n  }\n\n  value = lp->orig_upbo[lp->rows + colnr];\n  value = unscaled_value(lp, value, lp->rows + colnr);\n  return(value);\n}\n\nMYBOOL __WINAPI set_lowbo(lprec *lp, int colnr, REAL value)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"set_lowbo: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n#ifdef DoBorderRounding\n  if(fabs(value) < lp->infinite)\n    value = my_avoidtiny(value, lp->matA->epsvalue);\n#endif\n  value = scaled_value(lp, value, lp->rows + colnr);\n  if(lp->tighten_on_set) {\n    if(value > lp->orig_upbo[lp->rows + colnr]) {\n      report(lp, IMPORTANT, \"set_lowbo: Upper bound must be >= lower bound\\n\");\n      return(FALSE);\n    }\n    if((value < 0) || (value > lp->orig_lowbo[lp->rows + colnr])) {\n      set_action(&lp->spx_action, ACTION_REBASE);\n      lp->orig_lowbo[lp->rows + colnr] = value;\n    }\n  }\n  else\n  {\n    set_action(&lp->spx_action, ACTION_REBASE);\n    if(value < -lp->infinite)\n      value = -lp->infinite;\n    lp->orig_lowbo[lp->rows + colnr] = value;\n  }\n  return(TRUE);\n}\n\nREAL __WINAPI get_lowbo(lprec *lp, int colnr)\n{\n  REAL value;\n\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"get_lowbo: Column %d out of range\\n\", colnr);\n    return(0);\n  }\n\n  value = lp->orig_lowbo[lp->rows + colnr];\n  value = unscaled_value(lp, value, lp->rows + colnr);\n  return(value);\n}\n\nMYBOOL __WINAPI set_bounds(lprec *lp, int colnr, REAL lower, REAL upper)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"set_bounds: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n  if(fabs(upper - lower) < lp->epsvalue) {\n    if(lower < 0)\n      lower = upper;\n    else\n      upper = lower;\n  }\n  else if(lower > upper) {\n    report(lp, IMPORTANT, \"set_bounds: Column %d upper bound must be >= lower bound\\n\",\n                          colnr);\n    return( FALSE );\n  }\n\n  colnr += lp->rows;\n\n  if(lower < -lp->infinite)\n    lower = -lp->infinite;\n  else if(lp->scaling_used) {\n    lower = scaled_value(lp, lower, colnr);\n#ifdef DoBorderRounding\n    lower = my_avoidtiny(lower, lp->matA->epsvalue);\n#endif\n  }\n\n  if(upper > lp->infinite)\n    upper = lp->infinite;\n  else if(lp->scaling_used) {\n    upper = scaled_value(lp, upper, colnr);\n#ifdef DoBorderRounding\n    upper = my_avoidtiny(upper, lp->matA->epsvalue);\n#endif\n  }\n\n  lp->orig_lowbo[colnr] = lower;\n  lp->orig_upbo[colnr]  = upper;\n  set_action(&lp->spx_action, ACTION_REBASE);\n\n  return(TRUE);\n}\n\nMYBOOL get_bounds(lprec *lp, int column, REAL *lower, REAL *upper)\n{\n  if((column > lp->columns) || (column < 1)) {\n    report(lp, IMPORTANT, \"get_bounds: Column %d out of range\", column);\n    return(FALSE);\n  }\n\n  if(lower != NULL)\n    *lower = get_lowbo(lp, column);\n  if(upper != NULL)\n    *upper = get_upbo(lp, column);\n\n  return(TRUE);\n}\n\nMYBOOL __WINAPI set_int(lprec *lp, int colnr, MYBOOL var_type)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"set_int: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n  if((lp->var_type[colnr] & ISINTEGER) != 0) {\n    lp->int_vars--;\n    lp->var_type[colnr] &= ~ISINTEGER;\n  }\n  if(var_type) {\n    lp->var_type[colnr] |= ISINTEGER;\n    lp->int_vars++;\n    if(lp->columns_scaled && !is_integerscaling(lp))\n      unscale_columns(lp);\n  }\n  return(TRUE);\n}\n\nMYBOOL __WINAPI is_int(lprec *lp, int colnr)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"is_int: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n  return((lp->var_type[colnr] & ISINTEGER) != 0);\n}\n\nMYBOOL __WINAPI is_SOS_var(lprec *lp, int colnr)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"is_SOS_var: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n  return((lp->var_type[colnr] & ISSOS) != 0);\n}\n\nint __WINAPI add_SOS(lprec *lp, char *name, int sostype, int priority, int count, int *sosvars, REAL *weights)\n{\n  SOSrec *SOS;\n  int    k;\n\n  if((sostype < 1) || (count < 0)) {\n    report(lp, IMPORTANT, \"add_SOS: Invalid SOS type definition %d\\n\", sostype);\n    return( 0 );\n  }\n\n  /* Make sure SOSes of order 3 and higher are properly defined */\n  if(sostype > 2) {\n    int j;\n    for(k = 0; k < count; k++) {\n      j = sosvars[k];\n      if(!is_int(lp, j) || !is_semicont(lp, j)) {\n        report(lp, IMPORTANT, \"add_SOS: SOS3+ members all have to be integer or semi-continuous.\\n\");\n        return( 0 );\n      }\n    }\n  }\n\n  /* Make size in the list to handle another SOS record */\n  if(lp->SOS == NULL)\n    lp->SOS = create_SOSgroup(lp);\n\n  /* Create and append SOS to list */\n  SOS = create_SOSrec(lp->SOS, name, sostype, priority, count, sosvars, weights);\n  k = append_SOSgroup(lp->SOS, SOS);\n\n  return(k);\n}\n\nSTATIC int add_GUB(lprec *lp, char *name, int priority, int count, int *gubvars)\n{\n  SOSrec *GUB;\n  int    k;\n\n#ifdef Paranoia\n  if(count < 0) {\n    report(lp, IMPORTANT, \"add_GUB: Invalid GUB member count %d\\n\", count);\n    return(FALSE);\n  }\n#endif\n\n  /* Make size in the list to handle another GUB record */\n  if(lp->GUB == NULL)\n    lp->GUB = create_SOSgroup(lp);\n\n  /* Create and append GUB to list */\n  GUB = create_SOSrec(lp->GUB, name, 1, priority, count, gubvars, NULL);\n  GUB->isGUB = TRUE;\n  k = append_SOSgroup(lp->GUB, GUB);\n\n  return(k);\n}\n\nMYBOOL __WINAPI set_binary(lprec *lp, int colnr, MYBOOL must_be_bin)\n{\n  MYBOOL status = FALSE;\n\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"set_binary: Column %d out of range\\n\", colnr);\n    return( status );\n  }\n\n  status = set_int(lp, colnr, must_be_bin);\n  if(status && must_be_bin)\n    status = set_bounds(lp, colnr, 0, 1);\n  return( status );\n}\n\nMYBOOL __WINAPI is_binary(lprec *lp, int colnr)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"is_binary: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n  return((MYBOOL) (((lp->var_type[colnr] & ISINTEGER) != 0) &&\n                    (get_lowbo(lp, colnr) == 0) &&\n                    (fabs(get_upbo(lp, colnr) - 1) < lp->epsprimal)));\n}\n\nMYBOOL __WINAPI set_unbounded(lprec *lp, int colnr)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"set_unbounded: Column %d out of range\\n\", colnr);\n    return( FALSE );\n  }\n\n  return( set_bounds(lp, colnr, -lp->infinite, lp->infinite) );\n}\n\nMYBOOL __WINAPI is_unbounded(lprec *lp, int colnr)\n{\n  MYBOOL test;\n\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"is_unbounded: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n  test = is_splitvar(lp, colnr);\n  if(!test) {\n    colnr += lp->rows;\n    test = (MYBOOL) ((lp->orig_lowbo[colnr] <= -lp->infinite) &&\n                     (lp->orig_upbo[colnr] >= lp->infinite));\n  }\n  return( test );\n}\n\nMYBOOL __WINAPI is_negative(lprec *lp, int colnr)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"is_negative: Column %d out of range\\n\", colnr);\n    return( FALSE );\n  }\n\n  colnr += lp->rows;\n  return( (MYBOOL) ((lp->orig_upbo[colnr] <= 0) &&\n                    (lp->orig_lowbo[colnr] < 0)) );\n}\n\nMYBOOL __WINAPI set_var_weights(lprec *lp, REAL *weights)\n{\n  if(lp->var_priority != NULL) {\n    FREE(lp->var_priority);\n  }\n  if(weights != NULL) {\n    int n;\n    allocINT(lp, &lp->var_priority, lp->columns_alloc, FALSE);\n    for(n = 0; n < lp->columns; n++) {\n      lp->var_priority[n] = n+1;\n    }\n    n = sortByREAL(lp->var_priority, weights, lp->columns, 0, FALSE);\n  }\n  return(TRUE);\n}\n\nMYBOOL __WINAPI set_var_priority(lprec *lp)\n/* Experimental automatic variable ordering/priority setting */\n{\n  MYBOOL status = FALSE;\n\n  if(is_bb_mode(lp, NODE_AUTOORDER) &&\n     (lp->var_priority == NULL) &&\n     (SOS_count(lp) == 0)) {\n\n    REAL *rcost = NULL;\n    int  i, j, *colorder = NULL;\n\n    allocINT(lp, &colorder, lp->columns+1, FALSE);\n\n    /* Create an \"optimal\" B&B variable ordering; this MDO-based routine\n       returns column indeces in an increasing order of co-dependency.\n       It can be argued that arranging the columns in right-to-left\n       MDO order should tend to minimize the consequences of choosing the\n       wrong variable by reducing the average B&B depth. */\n    colorder[0] = lp->columns;\n    for(j = 1; j <= lp->columns; j++)\n      colorder[j] = lp->rows+j;\n    i = getMDO(lp, NULL, colorder, NULL, FALSE);\n\n    /* Map to variable weight */\n    allocREAL(lp, &rcost, lp->columns+1, FALSE);\n    for(j = lp->columns; j > 0; j--) {\n      i = colorder[j]-lp->rows;\n      rcost[i] = -j;\n    }\n\n   /* Establish the MIP variable priorities */\n    set_var_weights(lp, rcost+1);\n\n    FREE(rcost);\n    FREE(colorder);\n    status = TRUE;\n  }\n\n  return( status );\n}\n\nint __WINAPI get_var_priority(lprec *lp, int colnr)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"get_var_priority: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n  if(lp->var_priority == NULL)\n    return(colnr);\n  else\n    return(lp->var_priority[colnr - 1]);\n}\n\nMYBOOL __WINAPI set_semicont(lprec *lp, int colnr, MYBOOL must_be_sc)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"set_semicont: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n  if(lp->sc_lobound[colnr] != 0) {\n    lp->sc_vars--;\n    lp->var_type[colnr] &= ~ISSEMI;\n  }\n  lp->sc_lobound[colnr] = must_be_sc;\n  if(must_be_sc) {\n    lp->var_type[colnr] |= ISSEMI;\n    lp->sc_vars++;\n  }\n  return(TRUE);\n}\n\nMYBOOL __WINAPI is_semicont(lprec *lp, int colnr)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"is_semicont: Column %d out of range\\n\", colnr);\n    return(FALSE);\n  }\n\n  return((lp->var_type[colnr] & ISSEMI) != 0);\n}\n\nMYBOOL __WINAPI set_rh(lprec *lp, int rownr, REAL value)\n{\n  if((rownr > lp->rows) || (rownr < 0)) {\n    report(lp, IMPORTANT, \"set_rh: Row %d out of range\\n\", rownr);\n    return(FALSE);\n  }\n\n  if(((rownr == 0) && (!is_maxim(lp))) ||\n     ((rownr > 0) && is_chsign(lp, rownr)))    /* setting of RHS of OF IS meaningful */\n    value = my_flipsign(value);\n  if(fabs(value) > lp->infinite) {\n    if(value < 0)\n      value = -lp->infinite;\n    else\n      value = lp->infinite;\n  }\n#ifdef DoBorderRounding\n  else\n    value = my_avoidtiny(value, lp->matA->epsvalue);\n#endif\n  value = scaled_value(lp, value, rownr);\n  lp->orig_rhs[rownr] = value;\n  set_action(&lp->spx_action, ACTION_RECOMPUTE);\n  return(TRUE);\n}\n\nREAL __WINAPI get_rh(lprec *lp, int rownr)\n{\n  REAL value;\n\n  if((rownr > lp->rows) || (rownr < 0)) {\n    report(lp, IMPORTANT, \"get_rh: Row %d out of range\", rownr);\n    return( 0.0 );\n  }\n\n  value = lp->orig_rhs[rownr];\n  if (((rownr == 0) && !is_maxim(lp)) ||\n      ((rownr > 0) && is_chsign(lp, rownr)))    /* setting of RHS of OF IS meaningful */\n    value = my_flipsign(value);\n  value = unscaled_value(lp, value, rownr);\n  return(value);\n}\n\nREAL get_rh_upper(lprec *lp, int rownr)\n{\n  REAL value, valueR;\n\n  value = lp->orig_rhs[rownr];\n  if(is_chsign(lp, rownr)) {\n    valueR = lp->orig_upbo[rownr];\n    if(is_infinite(lp, valueR))\n      return(lp->infinite);\n    value = my_flipsign(value);\n    value += valueR;\n  }\n  value = unscaled_value(lp, value, rownr);\n  return(value);\n}\n\nREAL get_rh_lower(lprec *lp, int rownr)\n{\n  REAL value, valueR;\n\n  value = lp->orig_rhs[rownr];\n  if(is_chsign(lp, rownr))\n    value = my_flipsign(value);\n  else {\n    valueR = lp->orig_upbo[rownr];\n    if(is_infinite(lp, valueR))\n      return(-lp->infinite);\n    value -= valueR;\n  }\n  value = unscaled_value(lp, value, rownr);\n  return(value);\n}\n\nMYBOOL set_rh_upper(lprec *lp, int rownr, REAL value)\n{\n  if(rownr > lp->rows || rownr < 1) {\n    report(lp, IMPORTANT, \"set_rh_upper: Row %d out of range\", rownr);\n    return(FALSE);\n  }\n\n /* First scale the value */\n  value = scaled_value(lp, value, rownr);\n\n /* orig_rhs stores the upper bound assuming a < constraint;\n    If we have a > constraint, we must adjust the range instead */\n  if(is_chsign(lp, rownr)) {\n    if(is_infinite(lp, value))\n      lp->orig_upbo[rownr] = lp->infinite;\n    else {\n#ifdef Paranoia\n      if(value + lp->orig_rhs[rownr] < 0) {\n        report(lp, SEVERE, \"set_rh_upper: Invalid negative range in row %d\\n\",\n                           rownr);\n        return(FALSE);\n      }\n#endif\n#ifdef DoBorderRounding\n      lp->orig_upbo[rownr] = my_avoidtiny(value + lp->orig_rhs[rownr], lp->epsvalue);\n#else\n      lp->orig_upbo[rownr] = value + lp->orig_rhs[rownr];\n#endif\n    }\n  }\n  else {\n    /* If there is a constraint range, then this has to be adjusted also */\n    if(!is_infinite(lp, lp->orig_upbo[rownr])) {\n      lp->orig_upbo[rownr] -= lp->orig_rhs[rownr] - value;\n      my_roundzero(lp->orig_upbo[rownr], lp->epsvalue);\n      if(lp->orig_upbo[rownr] < 0) {\n        report(lp, IMPORTANT, \"set_rh_upper: Negative bound set for constraint %d made 0\\n\", rownr);\n        lp->orig_upbo[rownr] = 0;\n      }\n    }\n    lp->orig_rhs[rownr] = value;\n  }\n  return(TRUE);\n}\n\nMYBOOL set_rh_lower(lprec *lp, int rownr, REAL value)\n{\n  if(rownr > lp->rows || rownr < 1) {\n    report(lp, IMPORTANT, \"set_rh_lower: Row %d out of range\", rownr);\n    return(FALSE);\n  }\n\n /* First scale the value */\n  value = scaled_value(lp, value, rownr);\n\n /* orig_rhs stores the upper bound assuming a < constraint;\n    If we have a < constraint, we must adjust the range instead */\n  if(!is_chsign(lp, rownr)) {\n    if(is_infinite(lp, value))\n      lp->orig_upbo[rownr] = lp->infinite;\n    else {\n#ifdef Paranoia\n      if(lp->orig_rhs[rownr] - value < 0) {\n        report(lp, SEVERE, \"set_rh_lower: Invalid negative range in row %d\\n\",\n                           rownr);\n        return(FALSE);\n      }\n#endif\n#ifdef DoBorderRounding\n      lp->orig_upbo[rownr] = my_avoidtiny(lp->orig_rhs[rownr] - value, lp->epsvalue);\n#else\n      lp->orig_upbo[rownr] = lp->orig_rhs[rownr] - value;\n#endif\n    }\n  }\n  else {\n    value = my_flipsign(value);\n    /* If there is a constraint range, then this has to be adjusted also */\n    if(!is_infinite(lp, lp->orig_upbo[rownr])) {\n      lp->orig_upbo[rownr] -= lp->orig_rhs[rownr] - value;\n      my_roundzero(lp->orig_upbo[rownr], lp->epsvalue);\n      if(lp->orig_upbo[rownr] < 0) {\n        report(lp, IMPORTANT, \"set_rh_lower: Negative bound set for constraint %d made 0\\n\", rownr);\n        lp->orig_upbo[rownr] = 0;\n      }\n    }\n    lp->orig_rhs[rownr] = value;\n  }\n  return(TRUE);\n}\n\nMYBOOL __WINAPI set_rh_range(lprec *lp, int rownr, REAL deltavalue)\n{\n  if((rownr > lp->rows) || (rownr < 1)) {\n    report(lp, IMPORTANT, \"set_rh_range: Row %d out of range\", rownr);\n    return(FALSE);\n  }\n\n  deltavalue = scaled_value(lp, deltavalue, rownr);\n  if(deltavalue > lp->infinite)\n    deltavalue = lp->infinite;\n  else if(deltavalue < -lp->infinite)\n    deltavalue = -lp->infinite;\n#ifdef DoBorderRounding\n  else\n    deltavalue = my_avoidtiny(deltavalue, lp->matA->epsvalue);\n#endif\n\n  if(fabs(deltavalue) < lp->epsprimal) {\n    /* Conversion to EQ */\n    set_constr_type(lp, rownr, EQ);\n  }\n  else if(is_constr_type(lp, rownr, EQ)) {\n    /* EQ with a non-zero range */\n    if(deltavalue > 0)\n      set_constr_type(lp, rownr, GE);\n    else\n      set_constr_type(lp, rownr, LE);\n    lp->orig_upbo[rownr] = fabs(deltavalue);\n  }\n  else {\n    /* Modify GE/LE ranges */\n    lp->orig_upbo[rownr] = fabs(deltavalue);\n  }\n\n  return(TRUE);\n}\n\nREAL __WINAPI get_rh_range(lprec *lp, int rownr)\n{\n  if((rownr > lp->rows) || (rownr < 0)) {\n    report(lp, IMPORTANT, \"get_rh_range: row %d out of range\\n\", rownr);\n    return(FALSE);\n  }\n\n  if(lp->orig_upbo[rownr] >= lp->infinite)\n    return(lp->orig_upbo[rownr]);\n  else\n    return(unscaled_value(lp, lp->orig_upbo[rownr], rownr));\n}\n\nvoid __WINAPI set_rh_vec(lprec *lp, REAL *rh)\n{\n  int  i;\n  REAL rhi;\n\n  for(i = 1; i <= lp->rows; i++) {\n    rhi = rh[i];\n#ifdef DoBorderRounding\n    rhi = my_avoidtiny(rhi, lp->matA->epsvalue);\n#endif\n    lp->orig_rhs[i] = my_chsign(is_chsign(lp, i), scaled_value(lp, rhi, i));\n  }\n  set_action(&lp->spx_action, ACTION_RECOMPUTE);\n}\n\nMYBOOL __WINAPI str_set_rh_vec(lprec *lp, char *rh_string)\n{\n  int  i;\n  MYBOOL ret = TRUE;\n  REAL *newrh;\n  char *p, *newp;\n\n  allocREAL(lp, &newrh, lp->rows + 1, TRUE);\n  p = rh_string;\n\n  for(i = 1; i <= lp->rows; i++) {\n    newrh[i] = (REAL) strtod(p, &newp);\n    if(p == newp) {\n      report(lp, IMPORTANT, \"str_set_rh_vec: Bad string %s\\n\", p);\n      lp->spx_status = DATAIGNORED;\n      ret = FALSE;\n      break;\n    }\n    else\n      p = newp;\n  }\n  if(!(lp->spx_status == DATAIGNORED))\n    set_rh_vec(lp, newrh);\n  FREE(newrh);\n  return( ret );\n}\n\nvoid __WINAPI set_sense(lprec *lp, MYBOOL maximize)\n{\n  maximize = (MYBOOL) (maximize != FALSE);\n  if(is_maxim(lp) != maximize) {\n    int i;\n    if(is_infinite(lp, lp->bb_heuristicOF))\n      lp->bb_heuristicOF = my_chsign(maximize, lp->infinite);\n    if(is_infinite(lp, lp->bb_breakOF))\n      lp->bb_breakOF = my_chsign(maximize, -lp->infinite);\n    lp->orig_rhs[0] = my_flipsign(lp->orig_rhs[0]);\n    for(i = 1; i <= lp->columns; i++)\n      lp->orig_obj[i] = my_flipsign(lp->orig_obj[i]);\n    set_action(&lp->spx_action, ACTION_REINVERT | ACTION_RECOMPUTE);\n  }\n  if(maximize)\n    lp->row_type[0] = ROWTYPE_OFMAX;\n  else\n    lp->row_type[0] = ROWTYPE_OFMIN;\n}\n\nvoid __WINAPI set_maxim(lprec *lp)\n{\n  set_sense(lp, TRUE);\n}\n\nvoid __WINAPI set_minim(lprec *lp)\n{\n  set_sense(lp, FALSE);\n}\n\nMYBOOL __WINAPI is_maxim(lprec *lp)\n{\n  return( (MYBOOL) ((lp->row_type != NULL) &&\n                     ((lp->row_type[0] & ROWTYPE_CHSIGN) == ROWTYPE_GE)) );\n}\n\nMYBOOL __WINAPI set_constr_type(lprec *lp, int rownr, int con_type)\n{\n  MYBOOL oldchsign;\n\n  if(rownr > lp->rows+1 || rownr < 1) {\n    report(lp, IMPORTANT, \"set_constr_type: Row %d out of range\\n\", rownr);\n    return( FALSE );\n  }\n\n  /* Prepare for a new row */\n  if((rownr > lp->rows) && !append_rows(lp, rownr-lp->rows))\n    return( FALSE );\n\n  /* Update the constraint type data */\n  if(is_constr_type(lp, rownr, EQ))\n    lp->equalities--;\n\n  if((con_type & ROWTYPE_CONSTRAINT) == EQ) {\n    lp->equalities++;\n    lp->orig_upbo[rownr] = 0;\n  }\n  else if(((con_type & LE) > 0) || ((con_type & GE) > 0) || (con_type == FR))\n    lp->orig_upbo[rownr] = lp->infinite;\n  else {\n    report(lp, IMPORTANT, \"set_constr_type: Constraint type %d not implemented (row %d)\\n\",\n                          con_type, rownr);\n    return( FALSE );\n  }\n\n  /* Change the signs of the row, if necessary */\n  oldchsign = is_chsign(lp, rownr);\n  if(con_type == FR)\n    lp->row_type[rownr] = LE;\n  else\n    lp->row_type[rownr] = con_type;\n  if(oldchsign != is_chsign(lp, rownr)) {\n    MATrec *mat = lp->matA;\n\n    if(mat->is_roworder)\n      mat_multcol(mat, rownr, -1, FALSE);\n    else\n      mat_multrow(mat, rownr, -1);\n    if(lp->orig_rhs[rownr] != 0)\n      lp->orig_rhs[rownr] *= -1;\n    set_action(&lp->spx_action, ACTION_RECOMPUTE);\n  }\n  if(con_type == FR)\n      lp->orig_rhs[rownr] = lp->infinite;\n\n  set_action(&lp->spx_action, ACTION_REINVERT);\n  lp->basis_valid = FALSE;\n\n  return( TRUE );\n}\n\n/* INLINE */ MYBOOL is_chsign(lprec *lp, int rownr)\n{\n  return( (MYBOOL) ((lp->row_type[rownr] & ROWTYPE_CONSTRAINT) == ROWTYPE_CHSIGN) );\n}\n\nMYBOOL __WINAPI is_constr_type(lprec *lp, int rownr, int mask)\n{\n  if((rownr < 0) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"is_constr_type: Row %d out of range\\n\", rownr);\n    return( FALSE );\n  }\n  return( (MYBOOL) ((lp->row_type[rownr] & ROWTYPE_CONSTRAINT) == mask));\n}\n\nint __WINAPI get_constr_type(lprec *lp, int rownr)\n{\n  if((rownr < 0) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"get_constr_type: Row %d out of range\\n\", rownr);\n    return(-1);\n  }\n  return( lp->row_type[rownr] );\n}\nREAL __WINAPI get_constr_value(lprec *lp, int rownr, int count, REAL *primsolution, int *nzindex)\n{\n  int    i;\n  REAL   value = 0.0;\n  MATrec *mat = lp->matA;\n\n  if((rownr < 0) || (rownr > get_Nrows(lp)))\n    return( value );\n\n  /* First do validation and initialization of applicable primal solution */\n  if(!mat_validate(mat) || ((primsolution == NULL) && (lp->solvecount == 0)))\n    return( value );\n  i = get_Ncolumns(lp);\n  if((primsolution != NULL) && (nzindex == NULL) &&\n     ((count <= 0) || (count > i)))\n    count = i;\n  if(primsolution == NULL) {\n    get_ptr_variables(lp, &primsolution);\n    primsolution--;\n    nzindex = NULL;\n    count = i;\n  }\n\n  /* Do objective or constraint, as specified */\n  if(rownr == 0) {\n    value += get_rh(lp, 0);\n    if(nzindex != NULL)\n      for(i = 0; i < count; i++)\n        value += get_mat(lp, 0, nzindex[i]) * primsolution[i];\n    else\n      for(i = 1; i <= count; i++)\n        value += get_mat(lp, 0, i) * primsolution[i];\n  }\n  else {\n    if(nzindex != NULL) {\n      for(i = 0; i < count; i++)\n        value += get_mat(lp, rownr, nzindex[i]) * primsolution[i];\n    }\n    else {\n      int j;\n\n      for(i = mat->row_end[rownr-1]; i < mat->row_end[rownr]; i++) {\n        j = ROW_MAT_COLNR(i);\n        value += unscaled_mat(lp, ROW_MAT_VALUE(i), rownr, j) * primsolution[j];\n      }\n      value = my_chsign(is_chsign(lp, rownr), value);\n    }\n  }\n  return( value );\n}\n\nSTATIC char *get_str_constr_class(lprec *lp, int con_class)\n{\n  switch(con_class) {\n    case ROWCLASS_Unknown:     return(\"Unknown\");\n    case ROWCLASS_Objective:   return(\"Objective\");\n    case ROWCLASS_GeneralREAL: return(\"General REAL\");\n    case ROWCLASS_GeneralMIP:  return(\"General MIP\");\n    case ROWCLASS_GeneralINT:  return(\"General INT\");\n    case ROWCLASS_GeneralBIN:  return(\"General BIN\");\n    case ROWCLASS_KnapsackINT: return(\"Knapsack INT\");\n    case ROWCLASS_KnapsackBIN: return(\"Knapsack BIN\");\n    case ROWCLASS_SetPacking:  return(\"Set packing\");\n    case ROWCLASS_SetCover:    return(\"Set cover\");\n    case ROWCLASS_GUB:         return(\"GUB\");\n    default:                   return(\"Error\");\n  }\n}\n\nSTATIC char *get_str_constr_type(lprec *lp, int con_type)\n{\n  switch(con_type) {\n    case FR: return(\"FR\");\n    case LE: return(\"LE\");\n    case GE: return(\"GE\");\n    case EQ: return(\"EQ\");\n    default: return(\"Error\");\n  }\n}\n\nSTATIC int get_constr_class(lprec *lp, int rownr)\n{\n  int    aBIN = 0, aINT = 0, aREAL = 0,\n         xBIN = 0, xINT = 0, xREAL = 0;\n  int    j, elmnr, elmend, nelm;\n  MYBOOL chsign;\n  REAL   a;\n  MATrec *mat = lp->matA;\n\n  if((rownr < 1) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"get_constr_class: Row %d out of range\\n\", rownr);\n    return( ROWCLASS_Unknown );\n  }\n  mat_validate(mat);\n\n  /* Tally counts of constraint variable types and coefficients */\n  if(rownr == 0) {\n    elmnr = 1;\n    elmend = lp->columns;\n    nelm = 0;\n  }\n  else {\n    elmnr  = mat->row_end[rownr - 1];\n    elmend = mat->row_end[rownr];\n    nelm = elmend - elmnr;\n  }\n  chsign = is_chsign(lp, rownr);\n  for(; elmnr < elmend; elmnr++) {\n    if(rownr == 0) {\n      a = lp->orig_obj[elmnr];\n      if(a == 0)\n        continue;\n      j = elmnr;\n    }\n    else {\n      j = ROW_MAT_COLNR(elmnr);\n      a = ROW_MAT_VALUE(elmnr);\n    }\n    a = unscaled_mat(lp, my_chsign(chsign, a), rownr, j);\n    if(is_binary(lp, j))\n      xBIN++;\n    else if((get_lowbo(lp, j) >= 0) && is_int(lp, j))\n      xINT++;\n    else\n      xREAL++;  /* Includes integer variables with negative lower bound */\n\n    if(fabs(a-1.0) < lp->epsvalue)\n      aBIN++;\n    else if((a > 0) && (fabs(floor(a+lp->epsvalue)-a) < lp->epsvalue))\n      aINT++;\n    else\n      aREAL++;  /* Includes negative integer-valued coefficients */\n  }\n\n  /* Get the constraint type and the RHS */\n  if(rownr == 0)\n    return( ROWCLASS_Objective );\n  j = get_constr_type(lp, rownr);\n  a = get_rh(lp, rownr);\n\n  /* Determine the constraint class */\n  if((aBIN == nelm) && (xBIN == nelm) && (a >= 1)) {\n    if(a > 1)\n      j = ROWCLASS_KnapsackBIN;\n    else if(j == EQ)\n      j = ROWCLASS_GUB;\n    else if(j == LE)\n      j = ROWCLASS_SetCover;\n    else\n      j = ROWCLASS_SetPacking;\n  }\n  else if((aINT == nelm) && (xINT == nelm) && (a >= 1))\n    j = ROWCLASS_KnapsackINT;\n  else if(xBIN == nelm)\n    j = ROWCLASS_GeneralBIN;\n  else if(xINT == nelm)\n    j = ROWCLASS_GeneralINT;\n  else if((xREAL > 0) && (xINT+xBIN > 0))\n    j = ROWCLASS_GeneralMIP;\n  else\n    j = ROWCLASS_GeneralREAL;\n\n  return( j );\n}\n\nREAL __WINAPI get_mat(lprec *lp, int rownr, int colnr)\n{\n  REAL value;\n  int  elmnr;\n  int colnr1 = colnr, rownr1 = rownr;\n\n  if((rownr < 0) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"get_mat: Row %d out of range\", rownr);\n    return(0);\n  }\n  if((colnr < 1) || (colnr > lp->columns)) {\n    report(lp, IMPORTANT, \"get_mat: Column %d out of range\", colnr);\n    return(0);\n  }\n  if(rownr == 0) {\n    value = lp->orig_obj[colnr];\n    value = my_chsign(is_chsign(lp, rownr), value);\n    value = unscaled_mat(lp, value, rownr, colnr);\n  }\n  else {\n    if(lp->matA->is_roworder)\n      swapINT(&colnr1, &rownr1);\n    elmnr = mat_findelm(lp->matA, rownr1, colnr1);\n    if(elmnr >= 0) {\n      MATrec *mat = lp->matA;\n      value = my_chsign(is_chsign(lp, rownr), COL_MAT_VALUE(elmnr));\n      value = unscaled_mat(lp, value, rownr, colnr);\n    }\n    else\n      value = 0;\n  }\n  return(value);\n}\n\nREAL __WINAPI get_mat_byindex(lprec *lp, int matindex, MYBOOL isrow, MYBOOL adjustsign)\n/* Note that this function does not adjust for sign-changed GT constraints! */\n{\n  int  *rownr, *colnr;\n  REAL *value, result;\n\n  mat_get_data(lp, matindex, isrow, &rownr, &colnr, &value);\n  if(adjustsign)\n    result = (*value) * (is_chsign(lp, *rownr) ? -1 : 1);\n  else\n    result = *value;\n  if(lp->scaling_used)\n    return( unscaled_mat(lp, result, *rownr, *colnr) );\n  else\n    return( result );\n}\n\nstatic int mat_getrow(lprec *lp, int rownr, REAL *row, int *colno)\n{\n  MYBOOL isnz;\n  int    j, countnz = 0;\n  REAL   a;\n\n  if((rownr == 0) || !mat_validate(lp->matA)) {\n    for(j = 1; j <= lp->columns; j++) {\n      a = get_mat(lp,rownr,j);\n      isnz = (a != 0);\n      if(colno == NULL)\n        row[j] = a;\n      else if(isnz) {\n        row[countnz]   = a;\n        colno[countnz] = j;\n      }\n      if(isnz)\n        countnz++;\n    }\n  }\n  else {\n    MYBOOL chsign = FALSE;\n    int    ie, i;\n    MATrec *mat = lp->matA;\n\n    if(colno == NULL)\n      MEMCLEAR(row, lp->columns+1);\n    if(mat->is_roworder) {\n     /* Add the objective function */\n      a = get_mat(lp, 0, rownr);\n      if(colno == NULL) {\n        row[countnz] = a;\n        if(a != 0)\n          countnz++;\n      }\n      else if(a != 0) {\n        row[countnz] = a;\n        colno[countnz] = 0;\n        countnz++;\n      }\n    }\n    i = mat->row_end[rownr-1];\n    ie = mat->row_end[rownr];\n    if(!lp->matA->is_roworder)\n      chsign = is_chsign(lp, rownr);\n    for(; i < ie; i++) {\n      j = ROW_MAT_COLNR(i);\n      a = get_mat_byindex(lp, i, TRUE, FALSE);\n      if(lp->matA->is_roworder)\n        chsign = is_chsign(lp, j);\n      a = my_chsign(chsign, a);\n      if(colno == NULL)\n        row[j] = a;\n      else {\n        row[countnz]   = a;\n        colno[countnz] = j;\n      }\n      countnz++;\n    }\n  }\n  return( countnz );\n}\n\nstatic int mat_getcolumn(lprec *lp, int colnr, REAL *column, int *nzrow)\n{\n  int    n = 0, i, ii, ie, *rownr;\n  REAL   hold, *value;\n  MATrec *mat = lp->matA;\n\n  if(nzrow == NULL)\n    MEMCLEAR(column, lp->rows + 1);\n  if(!mat->is_roworder) {\n     /* Add the objective function */\n    hold = get_mat(lp, 0, colnr);\n    if(nzrow == NULL) {\n      column[n] = hold;\n      if(hold != 0)\n        n++;\n    }\n    else if(hold != 0) {\n      column[n] = hold;\n      nzrow[n] = 0;\n      n++;\n    }\n  }\n\n  i  = lp->matA->col_end[colnr - 1];\n  ie = lp->matA->col_end[colnr];\n  if(nzrow == NULL)\n    n += ie - i;\n  rownr = &COL_MAT_ROWNR(i);\n  value = &COL_MAT_VALUE(i);\n  for(; i < ie;\n      i++, rownr += matRowColStep, value += matValueStep) {\n    ii = *rownr;\n\n    hold = my_chsign(is_chsign(lp, (mat->is_roworder) ? colnr : ii), *value);\n    hold = unscaled_mat(lp, hold, ii, colnr);\n    if(nzrow == NULL)\n      column[ii] = hold;\n    else if(hold != 0) {\n      column[n] = hold;\n      nzrow[n] = ii;\n      n++;\n    }\n  }\n  return( n );\n}\n\nint __WINAPI get_columnex(lprec *lp, int colnr, REAL *column, int *nzrow)\n{\n  if((colnr > lp->columns) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"get_columnex: Column %d out of range\\n\", colnr);\n    return( -1 );\n  }\n\n  if(lp->matA->is_roworder)\n    return(mat_getrow(lp, colnr, column, nzrow));\n  else\n    return(mat_getcolumn(lp, colnr, column, nzrow));\n}\n\nMYBOOL __WINAPI get_column(lprec *lp, int colnr, REAL *column)\n{\n  return( (MYBOOL) (get_columnex(lp, colnr, column, NULL) >= 0) );\n}\n\nint __WINAPI get_rowex(lprec *lp, int rownr, REAL *row, int *colno)\n{\n  if((rownr < 0) || (rownr > lp->rows)) {\n    report(lp, IMPORTANT, \"get_rowex: Row %d out of range\\n\", rownr);\n    return( -1 );\n  }\n\n  if(rownr != 0 && lp->matA->is_roworder)\n    return(mat_getcolumn(lp, rownr, row, colno));\n  else\n    return(mat_getrow(lp, rownr, row, colno));\n}\n\nMYBOOL __WINAPI get_row(lprec *lp, int rownr, REAL *row)\n{\n  return((MYBOOL) (get_rowex(lp, rownr, row, NULL) >= 0) );\n}\n\nSTATIC void set_OF_override(lprec *lp, REAL *ofVector)\n/* The purpose of this function is to set, or clear if NULL, the\n   ofVector[0..columns] as the active objective function instead of\n   the one stored in the A-matrix. See also lag_solve().*/\n{\n  lp->obj = ofVector;\n}\n\nMYBOOL modifyOF1(lprec *lp, int index, REAL *ofValue, REAL mult)\n/* Adjust objective function values for primal/dual phase 1, if appropriate */\n{\n  MYBOOL accept = TRUE;\n\n  /* Primal simplex: Set user variables to zero or BigM-scaled */\n  if(((lp->simplex_mode & SIMPLEX_Phase1_PRIMAL) != 0) && (abs(lp->P1extraDim) > 0)) {\n#ifndef Phase1EliminateRedundant\n    if(lp->P1extraDim < 0) {\n      if(index > lp->sum + lp->P1extraDim)\n        accept = FALSE;\n    }\n    else\n#endif\n    if((index <= lp->sum - lp->P1extraDim) || (mult == 0)) {\n      if((mult == 0) || (lp->bigM == 0))\n        accept = FALSE;\n      else\n        (*ofValue) /= lp->bigM;\n    }\n  }\n\n  /* Dual simplex: Subtract P1extraVal from objective function values */\n  else if(((lp->simplex_mode & SIMPLEX_Phase1_DUAL) != 0) && (index > lp->rows)) {\n#if 1  /* This may help increase sparsity of the (extended) basis matrix;\n         Can it introduce degeneracy in some cases? */\n    if((lp->P1extraVal != 0) && (lp->orig_obj[index - lp->rows] > 0))\n      *ofValue = 0;\n    else\n#endif\n    {\n      *ofValue -= lp->P1extraVal;\n#if 0\n      if(is_action(lp->anti_degen, ANTIDEGEN_RHSPERTURB))\n        *ofValue -= rand_uniform(lp, lp->epsperturb);\n#endif\n    }\n  }\n\n  /* Do scaling and test for zero */\n  if(accept) {\n    (*ofValue) *= mult;\n    if(fabs(*ofValue) < lp->epsmachine) {\n      (*ofValue) = 0;\n      accept = FALSE;\n    }\n  }\n  else\n    (*ofValue) = 0;\n\n  return( accept );\n}\n\nSTATIC void set_OF_p1extra(lprec *lp, REAL p1extra)\n{\n  int  i;\n  REAL *value;\n\n  if(lp->spx_trace)\n    report(lp, DETAILED, \"set_OF_p1extra: Set dual objective offset to %g at iter %.0f.\\n\",\n                          p1extra, (double) get_total_iter(lp));\n  lp->P1extraVal = p1extra;\n  if(lp->obj == NULL)\n    allocREAL(lp, &lp->obj, lp->columns_alloc+1, TRUE);\n  for(i = 1, value = lp->obj+1; i <= lp->columns; i++, value++) {\n    *value = lp->orig_obj[i];\n    modifyOF1(lp, lp->rows + i, value, 1.0);\n  }\n}\n\nSTATIC void unset_OF_p1extra(lprec *lp)\n{\n  lp->P1extraVal = 0;\n  FREE(lp->obj);\n}\n\nREAL __WINAPI get_OF_active(lprec *lp, int varnr, REAL mult)\n{\n  int  colnr = varnr - lp->rows;\n  REAL holdOF = 0;\n\n#ifdef Paranoia\n  if((colnr <= 0) || (colnr > lp->columns)) {\n    report(lp, SEVERE, \"get_OF_active: Invalid column index %d supplied\\n\", colnr);\n  }\n  else\n#endif\n  if(lp->obj == NULL) {\n    if(colnr > 0)\n      holdOF = lp->orig_obj[colnr];\n    modifyOF1(lp, varnr, &holdOF, mult);\n  }\n  else if(colnr > 0)\n    holdOF = lp->obj[colnr] * mult;\n\n  return( holdOF );\n}\n\nSTATIC MYBOOL is_OF_nz(lprec *lp, int colnr)\n{\n  return( (MYBOOL) (lp->orig_obj[colnr] != 0) );\n}\n\nSTATIC int singleton_column(lprec *lp, int row_nr, REAL *column, int *nzlist, REAL value, int *maxabs)\n{\n  int nz = 1;\n\n  if(nzlist == NULL) {\n    MEMCLEAR(column, lp->rows + 1);\n    column[row_nr] = value;\n  }\n  else {\n    column[nz] = value;\n    nzlist[nz] = row_nr;\n  }\n\n  if(maxabs != NULL)\n    *maxabs = row_nr;\n  return( nz );\n}\n\nSTATIC int expand_column(lprec *lp, int col_nr, REAL *column, int *nzlist, REAL mult, int *maxabs)\n{\n  int     i, ie, j, maxidx, nzcount;\n  REAL    value, maxval;\n  MATrec  *mat = lp->matA;\n  REAL    *matValue;\n  int     *matRownr;\n\n  /* Retrieve a column from the user data matrix A */\n  maxval = 0;\n  maxidx = -1;\n  if(nzlist == NULL) {\n    MEMCLEAR(column, lp->rows + 1);\n    i  = mat->col_end[col_nr - 1];\n    ie = mat->col_end[col_nr];\n    matRownr = &COL_MAT_ROWNR(i);\n    matValue = &COL_MAT_VALUE(i);\n    nzcount = i;\n    for(; i < ie;\n        i++, matRownr += matRowColStep, matValue += matValueStep) {\n      j = *matRownr;\n      value = *matValue;\n      if(j > 0) {\n        value *= mult;\n        if(fabs(value) > maxval) {\n          maxval = fabs(value);\n          maxidx = j;\n        }\n      }\n      column[j] = value;\n    }\n    nzcount = i - nzcount;\n\n    /* Get the objective as row 0, optionally adjusting the objective for phase 1 */\n    if(lp->obj_in_basis) {\n      column[0] = get_OF_active(lp, lp->rows+col_nr, mult);\n      if(column[0] != 0)\n        nzcount++;\n    }\n  }\n  else {\n    nzcount = 0;\n\n    /* Get the objective as row 0, optionally adjusting the objective for phase 1 */\n    if(lp->obj_in_basis) {\n      value = get_OF_active(lp, lp->rows+col_nr, mult);\n      if(value != 0) {\n        nzcount++;\n        nzlist[nzcount] = 0;\n        column[nzcount] = value;\n      }\n    }\n\n    /* Loop over the non-zero column entries */\n    i  = mat->col_end[col_nr - 1];\n    ie = mat->col_end[col_nr];\n    matRownr = &COL_MAT_ROWNR(i);\n    matValue = &COL_MAT_VALUE(i);\n    for(; i < ie;\n        i++, matRownr += matRowColStep, matValue += matValueStep) {\n      j = *matRownr;\n      value = (*matValue) * mult;\n      nzcount++;\n      nzlist[nzcount] = j;\n      column[nzcount] = value;\n      if(fabs(value) > maxval) {\n        maxval = fabs(value);\n        maxidx = nzcount;\n      }\n    }\n  }\n\n  if(maxabs != NULL)\n    *maxabs = maxidx;\n  return( nzcount );\n}\n\n\n/* Retrieve a column vector from the data matrix [1..rows, rows+1..rows+columns];\n   needs __WINAPI call model since it may be called from BFPs */\nint __WINAPI obtain_column(lprec *lp, int varin, REAL *pcol, int *nzlist, int *maxabs)\n{\n  REAL value = my_chsign(lp->is_lower[varin], -1);\n  if(varin > lp->rows) {\n    varin -= lp->rows;\n    varin = expand_column(lp, varin, pcol, nzlist, value, maxabs);\n  }\n  else if(lp->obj_in_basis || (varin > 0))\n    varin = singleton_column(lp, varin, pcol, nzlist, value, maxabs);\n  else\n    varin = get_basisOF(lp, NULL, pcol, nzlist);\n\n  return(varin);\n}\n\n/* GENERAL INVARIANT CALLBACK FUNCTIONS */\nMYBOOL set_callbacks(lprec *lp)\n{\n  /* Assign API functions to lp structure (mainly for XLIs) */\n  lp->add_column              = add_column;\n  lp->add_columnex            = add_columnex;\n  lp->add_constraint          = add_constraint;\n  lp->add_constraintex        = add_constraintex;\n  lp->add_lag_con             = add_lag_con;\n  lp->add_SOS                 = add_SOS;\n  lp->column_in_lp            = column_in_lp;\n  lp->copy_lp                 = copy_lp;\n  lp->default_basis           = default_basis;\n  lp->del_column              = del_column;\n  lp->del_constraint          = del_constraint;\n  lp->delete_lp               = delete_lp;\n  lp->dualize_lp              = dualize_lp;\n  lp->free_lp                 = free_lp;\n  lp->get_anti_degen          = get_anti_degen;\n  lp->get_basis               = get_basis;\n  lp->get_basiscrash          = get_basiscrash;\n  lp->get_bb_depthlimit       = get_bb_depthlimit;\n  lp->get_bb_floorfirst       = get_bb_floorfirst;\n  lp->get_bb_rule             = get_bb_rule;\n  lp->get_bounds_tighter      = get_bounds_tighter;\n  lp->get_break_at_value      = get_break_at_value;\n  lp->get_col_name            = get_col_name;\n  lp->get_columnex            = get_columnex;\n  lp->get_constr_type         = get_constr_type;\n  lp->get_constr_value        = get_constr_value;\n  lp->get_constraints         = get_constraints;\n  lp->get_dual_solution       = get_dual_solution;\n  lp->get_epsb                = get_epsb;\n  lp->get_epsd                = get_epsd;\n  lp->get_epsel               = get_epsel;\n  lp->get_epsint              = get_epsint;\n  lp->get_epsperturb          = get_epsperturb;\n  lp->get_epspivot            = get_epspivot;\n  lp->get_improve             = get_improve;\n  lp->get_infinite            = get_infinite;\n  lp->get_lambda              = get_lambda;\n  lp->get_lowbo               = get_lowbo;\n  lp->get_lp_index            = get_lp_index;\n  lp->get_lp_name             = get_lp_name;\n  lp->get_Lrows               = get_Lrows;\n  lp->get_mat                 = get_mat;\n  lp->get_mat_byindex         = get_mat_byindex;\n  lp->get_max_level           = get_max_level;\n  lp->get_maxpivot            = get_maxpivot;\n  lp->get_mip_gap             = get_mip_gap;\n  lp->get_multiprice          = get_multiprice;\n  lp->get_nameindex           = get_nameindex;\n  lp->get_Ncolumns            = get_Ncolumns;\n  lp->get_negrange            = get_negrange;\n  lp->get_nonzeros            = get_nonzeros;\n  lp->get_Norig_columns       = get_Norig_columns;\n  lp->get_Norig_rows          = get_Norig_rows;\n  lp->get_Nrows               = get_Nrows;\n  lp->get_obj_bound           = get_obj_bound;\n  lp->get_objective           = get_objective;\n  lp->get_orig_index          = get_orig_index;\n  lp->get_origcol_name        = get_origcol_name;\n  lp->get_origrow_name        = get_origrow_name;\n  lp->get_partialprice        = get_partialprice;\n  lp->get_pivoting            = get_pivoting;\n  lp->get_presolve            = get_presolve;\n  lp->get_presolveloops       = get_presolveloops;\n  lp->get_primal_solution     = get_primal_solution;\n  lp->get_print_sol           = get_print_sol;\n  lp->get_pseudocosts         = get_pseudocosts;\n  lp->get_ptr_constraints     = get_ptr_constraints;\n  lp->get_ptr_dual_solution   = get_ptr_dual_solution;\n  lp->get_ptr_lambda          = get_ptr_lambda;\n  lp->get_ptr_primal_solution = get_ptr_primal_solution;\n  lp->get_ptr_sensitivity_obj = get_ptr_sensitivity_obj;\n  lp->get_ptr_sensitivity_objex = get_ptr_sensitivity_objex;\n  lp->get_ptr_sensitivity_rhs = get_ptr_sensitivity_rhs;\n  lp->get_ptr_variables       = get_ptr_variables;\n  lp->get_rh                  = get_rh;\n  lp->get_rh_range            = get_rh_range;\n  lp->get_row                 = get_row;\n  lp->get_rowex               = get_rowex;\n  lp->get_row_name            = get_row_name;\n  lp->get_scalelimit          = get_scalelimit;\n  lp->get_scaling             = get_scaling;\n  lp->get_sensitivity_obj     = get_sensitivity_obj;\n  lp->get_sensitivity_objex   = get_sensitivity_objex;\n  lp->get_sensitivity_rhs     = get_sensitivity_rhs;\n  lp->get_simplextype         = get_simplextype;\n  lp->get_solutioncount       = get_solutioncount;\n  lp->get_solutionlimit       = get_solutionlimit;\n  lp->get_status              = get_status;\n  lp->get_statustext          = get_statustext;\n  lp->get_timeout             = get_timeout;\n  lp->get_total_iter          = get_total_iter;\n  lp->get_total_nodes         = get_total_nodes;\n  lp->get_upbo                = get_upbo;\n  lp->get_var_branch          = get_var_branch;\n  lp->get_var_dualresult      = get_var_dualresult;\n  lp->get_var_primalresult    = get_var_primalresult;\n  lp->get_var_priority        = get_var_priority;\n  lp->get_variables           = get_variables;\n  lp->get_verbose             = get_verbose;\n  lp->get_working_objective   = get_working_objective;\n  lp->has_BFP                 = has_BFP;\n  lp->has_XLI                 = has_XLI;\n  lp->is_add_rowmode          = is_add_rowmode;\n  lp->is_anti_degen           = is_anti_degen;\n  lp->is_binary               = is_binary;\n  lp->is_break_at_first       = is_break_at_first;\n  lp->is_constr_type          = is_constr_type;\n  lp->is_debug                = is_debug;\n  lp->is_feasible             = is_feasible;\n  lp->is_unbounded            = is_unbounded;\n  lp->is_infinite             = is_infinite;\n  lp->is_int                  = is_int;\n  lp->is_integerscaling       = is_integerscaling;\n  lp->is_lag_trace            = is_lag_trace;\n  lp->is_maxim                = is_maxim;\n  lp->is_nativeBFP            = is_nativeBFP;\n  lp->is_nativeXLI            = is_nativeXLI;\n  lp->is_negative             = is_negative;\n  lp->is_obj_in_basis         = is_obj_in_basis;\n  lp->is_piv_mode             = is_piv_mode;\n  lp->is_piv_rule             = is_piv_rule;\n  lp->is_presolve             = is_presolve;\n  lp->is_scalemode            = is_scalemode;\n  lp->is_scaletype            = is_scaletype;\n  lp->is_semicont             = is_semicont;\n  lp->is_SOS_var              = is_SOS_var;\n  lp->is_trace                = is_trace;\n  lp->lp_solve_version        = lp_solve_version;\n  lp->make_lp                 = make_lp;\n  lp->print_constraints       = print_constraints;\n  lp->print_debugdump         = print_debugdump;\n  lp->print_duals             = print_duals;\n  lp->print_lp                = print_lp;\n  lp->print_objective         = print_objective;\n  lp->print_scales            = print_scales;\n  lp->print_solution          = print_solution;\n  lp->print_str               = print_str;\n  lp->print_tableau           = print_tableau;\n  lp->put_abortfunc           = put_abortfunc;\n  lp->put_bb_nodefunc         = put_bb_nodefunc;\n  lp->put_bb_branchfunc       = put_bb_branchfunc;\n  lp->put_logfunc             = put_logfunc;\n  lp->put_msgfunc             = put_msgfunc;\n  lp->read_LP                 = read_LP;\n  lp->read_MPS                = read_MPS;\n  lp->read_XLI                = read_XLI;\n  lp->read_basis              = read_basis;\n  lp->reset_basis             = reset_basis;\n  lp->read_params             = read_params;\n  lp->reset_params            = reset_params;\n  lp->resize_lp               = resize_lp;\n  lp->set_action              = set_action;\n  lp->set_add_rowmode         = set_add_rowmode;\n  lp->set_anti_degen          = set_anti_degen;\n  lp->set_basisvar            = set_basisvar;\n  lp->set_basis               = set_basis;\n  lp->set_basiscrash          = set_basiscrash;\n  lp->set_bb_depthlimit       = set_bb_depthlimit;\n  lp->set_bb_floorfirst       = set_bb_floorfirst;\n  lp->set_bb_rule             = set_bb_rule;\n  lp->set_BFP                 = set_BFP;\n  lp->set_binary              = set_binary;\n  lp->set_bounds              = set_bounds;\n  lp->set_bounds_tighter      = set_bounds_tighter;\n  lp->set_break_at_first      = set_break_at_first;\n  lp->set_break_at_value      = set_break_at_value;\n  lp->set_col_name            = set_col_name;\n  lp->set_constr_type         = set_constr_type;\n  lp->set_debug               = set_debug;\n  lp->set_epsb                = set_epsb;\n  lp->set_epsd                = set_epsd;\n  lp->set_epsel               = set_epsel;\n  lp->set_epsint              = set_epsint;\n  lp->set_epslevel            = set_epslevel;\n  lp->set_epsperturb          = set_epsperturb;\n  lp->set_epspivot            = set_epspivot;\n  lp->set_unbounded           = set_unbounded;\n  lp->set_improve             = set_improve;\n  lp->set_infinite            = set_infinite;\n  lp->set_int                 = set_int;\n  lp->set_lag_trace           = set_lag_trace;\n  lp->set_lowbo               = set_lowbo;\n  lp->set_lp_name             = set_lp_name;\n  lp->set_mat                 = set_mat;\n  lp->set_maxim               = set_maxim;\n  lp->set_maxpivot            = set_maxpivot;\n  lp->set_minim               = set_minim;\n  lp->set_mip_gap             = set_mip_gap;\n  lp->set_multiprice          = set_multiprice;\n  lp->set_negrange            = set_negrange;\n  lp->set_obj                 = set_obj;\n  lp->set_obj_bound           = set_obj_bound;\n  lp->set_obj_fn              = set_obj_fn;\n  lp->set_obj_fnex            = set_obj_fnex;\n  lp->set_obj_in_basis        = set_obj_in_basis;\n  lp->set_outputfile          = set_outputfile;\n  lp->set_outputstream        = set_outputstream;\n  lp->set_partialprice        = set_partialprice;\n  lp->set_pivoting            = set_pivoting;\n  lp->set_preferdual          = set_preferdual;\n  lp->set_presolve            = set_presolve;\n  lp->set_print_sol           = set_print_sol;\n  lp->set_pseudocosts         = set_pseudocosts;\n  lp->set_rh                  = set_rh;\n  lp->set_rh_range            = set_rh_range;\n  lp->set_rh_vec              = set_rh_vec;\n  lp->set_row                 = set_row;\n  lp->set_rowex               = set_rowex;\n  lp->set_row_name            = set_row_name;\n  lp->set_scalelimit          = set_scalelimit;\n  lp->set_scaling             = set_scaling;\n  lp->set_semicont            = set_semicont;\n  lp->set_sense               = set_sense;\n  lp->set_simplextype         = set_simplextype;\n  lp->set_solutionlimit       = set_solutionlimit;\n  lp->set_timeout             = set_timeout;\n  lp->set_trace               = set_trace;\n  lp->set_upbo                = set_upbo;\n  lp->set_var_branch          = set_var_branch;\n  lp->set_var_weights         = set_var_weights;\n  lp->set_verbose             = set_verbose;\n  lp->set_XLI                 = set_XLI;\n  lp->solve                   = solve;\n  lp->str_add_column          = str_add_column;\n  lp->str_add_constraint      = str_add_constraint;\n  lp->str_add_lag_con         = str_add_lag_con;\n  lp->str_set_obj_fn          = str_set_obj_fn;\n  lp->str_set_rh_vec          = str_set_rh_vec;\n  lp->time_elapsed            = time_elapsed;\n  lp->unscale                 = unscale;\n  lp->write_lp                = write_lp;\n  lp->write_LP                = write_LP;\n  lp->write_mps               = write_mps;\n  lp->write_freemps           = write_freemps;\n  lp->write_MPS               = write_MPS;\n  lp->write_freeMPS           = write_freeMPS;\n  lp->write_XLI               = write_XLI;\n  lp->write_basis             = write_basis;\n  lp->write_params            = write_params;\n\n  /* Utility functions (mainly for BFPs) */\n  lp->userabort               = userabort;\n  lp->report                  = report;\n  lp->explain                 = explain;\n  lp->set_basisvar            = set_basisvar;\n  lp->get_lpcolumn            = obtain_column;\n  lp->get_basiscolumn         = get_basiscolumn;\n  lp->get_OF_active           = get_OF_active;\n  lp->getMDO                  = getMDO;\n  lp->invert                  = invert;\n  lp->set_action              = set_action;\n  lp->clear_action            = clear_action;\n  lp->is_action               = is_action;\n\n  return( TRUE );\n}\n\n/* SUPPORT FUNCTION FOR BASIS FACTORIZATION PACKAGES */\nMYBOOL __WINAPI has_BFP(lprec *lp)\n{\n  return( is_nativeBFP(lp)\n#if LoadInverseLib == TRUE\n       || (MYBOOL) (lp->hBFP != NULL)\n#endif\n        );\n}\n\nMYBOOL __WINAPI is_nativeBFP(lprec *lp)\n{\n#ifdef ExcludeNativeInverse\n  return( FALSE );\n#elif LoadInverseLib == TRUE\n  return( (MYBOOL) (lp->hBFP == NULL) );\n#else\n  return( TRUE );\n#endif\n}\n\nMYBOOL __WINAPI set_BFP(lprec *lp, char *filename)\n/* (Re)mapping of basis factorization variant methods is done here */\n{\n  int result = LIB_LOADED;\n\n  /* Release the BFP and basis if we are active */\n  if(lp->invB != NULL)\n    bfp_free(lp);\n\n#if LoadInverseLib == TRUE\n  if(lp->hBFP != NULL) {\n  #ifdef WIN32\n    FreeLibrary(lp->hBFP);\n  #else\n    dlclose(lp->hBFP);\n  #endif\n    lp->hBFP = NULL;\n  }\n#endif\n\n  if(filename == NULL) {\n    if(!is_nativeBFP(lp))\n      return( FALSE );\n#ifndef ExcludeNativeInverse\n    lp->bfp_name = bfp_name;\n    lp->bfp_compatible = bfp_compatible;\n    lp->bfp_free = bfp_free;\n    lp->bfp_resize = bfp_resize;\n    lp->bfp_nonzeros = bfp_nonzeros;\n    lp->bfp_memallocated = bfp_memallocated;\n    lp->bfp_restart = bfp_restart;\n    lp->bfp_mustrefactorize = bfp_mustrefactorize;\n    lp->bfp_preparefactorization = bfp_preparefactorization;\n    lp->bfp_factorize = bfp_factorize;\n    lp->bfp_finishupdate = bfp_finishupdate;\n    lp->bfp_ftran_normal = bfp_ftran_normal;\n    lp->bfp_ftran_prepare = bfp_ftran_prepare;\n    lp->bfp_btran_normal = bfp_btran_normal;\n    lp->bfp_status = bfp_status;\n    lp->bfp_implicitslack = bfp_implicitslack;\n    lp->bfp_indexbase = bfp_indexbase;\n    lp->bfp_rowoffset = bfp_rowoffset;\n    lp->bfp_pivotmax = bfp_pivotmax;\n    lp->bfp_init = bfp_init;\n    lp->bfp_pivotalloc = bfp_pivotalloc;\n    lp->bfp_colcount = bfp_colcount;\n    lp->bfp_canresetbasis = bfp_canresetbasis;\n    lp->bfp_finishfactorization = bfp_finishfactorization;\n    lp->bfp_updaterefactstats = bfp_updaterefactstats;\n    lp->bfp_prepareupdate = bfp_prepareupdate;\n    lp->bfp_pivotRHS = bfp_pivotRHS;\n    lp->bfp_btran_double = bfp_btran_double;\n    lp->bfp_efficiency = bfp_efficiency;\n    lp->bfp_pivotvector = bfp_pivotvector;\n    lp->bfp_pivotcount = bfp_pivotcount;\n    lp->bfp_refactcount = bfp_refactcount;\n    lp->bfp_isSetI = bfp_isSetI;\n    lp->bfp_findredundant = bfp_findredundant;\n#endif\n  }\n  else {\n#if LoadInverseLib == TRUE\n  #ifdef WIN32\n   /* Get a handle to the Windows DLL module. */\n    lp->hBFP = LoadLibrary(filename);\n\n   /* If the handle is valid, try to get the function addresses. */\n    if(lp->hBFP != NULL) {\n      lp->bfp_compatible           = (BFPbool_lpintintint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_compatible\");\n      if(lp->bfp_compatible == NULL)\n        result = LIB_NOINFO;\n      else if(lp->bfp_compatible(lp, BFPVERSION, MAJORVERSION, sizeof(REAL))) {\n\n      lp->bfp_name                 = (BFPchar *)\n                                      GetProcAddress(lp->hBFP, \"bfp_name\");\n      lp->bfp_free                 = (BFP_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_free\");\n      lp->bfp_resize               = (BFPbool_lpint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_resize\");\n      lp->bfp_nonzeros             = (BFPint_lpbool *)\n                                      GetProcAddress(lp->hBFP, \"bfp_nonzeros\");\n      lp->bfp_memallocated         = (BFPint_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_memallocated\");\n      lp->bfp_restart              = (BFPbool_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_restart\");\n      lp->bfp_mustrefactorize      = (BFPbool_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_mustrefactorize\");\n      lp->bfp_preparefactorization = (BFPint_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_preparefactorization\");\n      lp->bfp_factorize            = (BFPint_lpintintboolbool *)\n                                      GetProcAddress(lp->hBFP, \"bfp_factorize\");\n      lp->bfp_finishupdate         = (BFPbool_lpbool *)\n                                      GetProcAddress(lp->hBFP, \"bfp_finishupdate\");\n      lp->bfp_ftran_normal         = (BFP_lprealint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_ftran_normal\");\n      lp->bfp_ftran_prepare        = (BFP_lprealint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_ftran_prepare\");\n      lp->bfp_btran_normal         = (BFP_lprealint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_btran_normal\");\n      lp->bfp_status               = (BFPint_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_status\");\n      lp->bfp_implicitslack        = (BFPbool_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_implicitslack\");\n      lp->bfp_indexbase            = (BFPint_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_indexbase\");\n      lp->bfp_rowoffset            = (BFPint_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_rowoffset\");\n      lp->bfp_pivotmax             = (BFPint_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_pivotmax\");\n      lp->bfp_init                 = (BFPbool_lpintintchar *)\n                                      GetProcAddress(lp->hBFP, \"bfp_init\");\n      lp->bfp_pivotalloc           = (BFPbool_lpint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_pivotalloc\");\n      lp->bfp_colcount             = (BFPint_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_colcount\");\n      lp->bfp_canresetbasis        = (BFPbool_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_canresetbasis\");\n      lp->bfp_finishfactorization  = (BFP_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_finishfactorization\");\n      lp->bfp_updaterefactstats    = (BFP_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_updaterefactstats\");\n      lp->bfp_prepareupdate        = (BFPlreal_lpintintreal *)\n                                      GetProcAddress(lp->hBFP, \"bfp_prepareupdate\");\n      lp->bfp_pivotRHS             = (BFPreal_lplrealreal *)\n                                      GetProcAddress(lp->hBFP, \"bfp_pivotRHS\");\n      lp->bfp_btran_double         = (BFP_lprealintrealint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_btran_double\");\n      lp->bfp_efficiency           = (BFPreal_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_efficiency\");\n      lp->bfp_pivotvector          = (BFPrealp_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_pivotvector\");\n      lp->bfp_pivotcount           = (BFPint_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_pivotcount\");\n      lp->bfp_refactcount          = (BFPint_lpint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_refactcount\");\n      lp->bfp_isSetI               = (BFPbool_lp *)\n                                      GetProcAddress(lp->hBFP, \"bfp_isSetI\");\n      lp->bfp_findredundant        = (BFPint_lpintrealcbintint *)\n                                      GetProcAddress(lp->hBFP, \"bfp_findredundant\");\n      }\n      else\n        result = LIB_VERINVALID;\n    }\n  #else\n   /* First standardize UNIX .SO library name format. */\n    char bfpname[260], *ptr;\n\n    strcpy(bfpname, filename);\n    if((ptr = strrchr(filename, '/')) == NULL)\n      ptr = filename;\n    else\n      ptr++;\n    bfpname[(int) (ptr - filename)] = 0;\n    if(strncmp(ptr, \"lib\", 3))\n      strcat(bfpname, \"lib\");\n    strcat(bfpname, ptr);\n    if(strcmp(bfpname + strlen(bfpname) - 3, \".so\"))\n      strcat(bfpname, \".so\");\n\n   /* Get a handle to the module. */\n    lp->hBFP = dlopen(bfpname, RTLD_LAZY);\n\n   /* If the handle is valid, try to get the function addresses. */\n    if(lp->hBFP != NULL) {\n      lp->bfp_compatible           = (BFPbool_lpintintint *)\n                                      dlsym(lp->hBFP, \"bfp_compatible\");\n      if(lp->bfp_compatible == NULL)\n        result = LIB_NOINFO;\n      else if(lp->bfp_compatible(lp, BFPVERSION, MAJORVERSION, sizeof(REAL))) {\n\n      lp->bfp_name                 = (BFPchar *)\n                                      dlsym(lp->hBFP, \"bfp_name\");\n      lp->bfp_free                 = (BFP_lp *)\n                                      dlsym(lp->hBFP, \"bfp_free\");\n      lp->bfp_resize               = (BFPbool_lpint *)\n                                      dlsym(lp->hBFP, \"bfp_resize\");\n      lp->bfp_nonzeros             = (BFPint_lpbool *)\n                                      dlsym(lp->hBFP, \"bfp_nonzeros\");\n      lp->bfp_memallocated         = (BFPint_lp *)\n                                      dlsym(lp->hBFP, \"bfp_memallocated\");\n      lp->bfp_restart              = (BFPbool_lp *)\n                                      dlsym(lp->hBFP, \"bfp_restart\");\n      lp->bfp_mustrefactorize      = (BFPbool_lp *)\n                                      dlsym(lp->hBFP, \"bfp_mustrefactorize\");\n      lp->bfp_preparefactorization = (BFPint_lp *)\n                                      dlsym(lp->hBFP, \"bfp_preparefactorization\");\n      lp->bfp_factorize            = (BFPint_lpintintboolbool *)\n                                      dlsym(lp->hBFP, \"bfp_factorize\");\n      lp->bfp_finishupdate         = (BFPbool_lpbool *)\n                                      dlsym(lp->hBFP, \"bfp_finishupdate\");\n      lp->bfp_ftran_normal         = (BFP_lprealint *)\n                                      dlsym(lp->hBFP, \"bfp_ftran_normal\");\n      lp->bfp_ftran_prepare        = (BFP_lprealint *)\n                                      dlsym(lp->hBFP, \"bfp_ftran_prepare\");\n      lp->bfp_btran_normal         = (BFP_lprealint *)\n                                      dlsym(lp->hBFP, \"bfp_btran_normal\");\n      lp->bfp_status               = (BFPint_lp *)\n                                      dlsym(lp->hBFP, \"bfp_status\");\n      lp->bfp_implicitslack        = (BFPbool_lp *)\n                                      dlsym(lp->hBFP, \"bfp_implicitslack\");\n      lp->bfp_indexbase            = (BFPint_lp *)\n                                      dlsym(lp->hBFP, \"bfp_indexbase\");\n      lp->bfp_rowoffset            = (BFPint_lp *)\n                                      dlsym(lp->hBFP, \"bfp_rowoffset\");\n      lp->bfp_pivotmax             = (BFPint_lp *)\n                                      dlsym(lp->hBFP, \"bfp_pivotmax\");\n      lp->bfp_init                 = (BFPbool_lpintintchar *)\n                                      dlsym(lp->hBFP, \"bfp_init\");\n      lp->bfp_pivotalloc           = (BFPbool_lpint *)\n                                      dlsym(lp->hBFP, \"bfp_pivotalloc\");\n      lp->bfp_colcount             = (BFPint_lp *)\n                                      dlsym(lp->hBFP, \"bfp_colcount\");\n      lp->bfp_canresetbasis        = (BFPbool_lp *)\n                                      dlsym(lp->hBFP, \"bfp_canresetbasis\");\n      lp->bfp_finishfactorization  = (BFP_lp *)\n                                      dlsym(lp->hBFP, \"bfp_finishfactorization\");\n      lp->bfp_updaterefactstats    = (BFP_lp *)\n                                      dlsym(lp->hBFP, \"bfp_updaterefactstats\");\n      lp->bfp_prepareupdate        = (BFPlreal_lpintintreal *)\n                                      dlsym(lp->hBFP, \"bfp_prepareupdate\");\n      lp->bfp_pivotRHS             = (BFPreal_lplrealreal *)\n                                      dlsym(lp->hBFP, \"bfp_pivotRHS\");\n      lp->bfp_btran_double         = (BFP_lprealintrealint *)\n                                      dlsym(lp->hBFP, \"bfp_btran_double\");\n      lp->bfp_efficiency           = (BFPreal_lp *)\n                                      dlsym(lp->hBFP, \"bfp_efficiency\");\n      lp->bfp_pivotvector          = (BFPrealp_lp *)\n                                      dlsym(lp->hBFP, \"bfp_pivotvector\");\n      lp->bfp_pivotcount           = (BFPint_lp *)\n                                      dlsym(lp->hBFP, \"bfp_pivotcount\");\n      lp->bfp_refactcount          = (BFPint_lpint *)\n                                      dlsym(lp->hBFP, \"bfp_refactcount\");\n      lp->bfp_isSetI               = (BFPbool_lp *)\n                                      dlsym(lp->hBFP, \"bfp_isSetI\");\n      lp->bfp_findredundant        = (BFPint_lpintrealcbintint *)\n                                      dlsym(lp->hBFP, \"bfp_findredundant\");\n      }\n      else\n        result = LIB_VERINVALID;\n    }\n  #endif\n    else\n      result = LIB_NOTFOUND;\n#endif\n    /* Do validation */\n    if((result != LIB_LOADED) ||\n       ((lp->bfp_name == NULL) ||\n        (lp->bfp_compatible == NULL) ||\n        (lp->bfp_free == NULL) ||\n        (lp->bfp_resize == NULL) ||\n        (lp->bfp_nonzeros == NULL) ||\n        (lp->bfp_memallocated == NULL) ||\n        (lp->bfp_restart == NULL) ||\n        (lp->bfp_mustrefactorize == NULL) ||\n        (lp->bfp_preparefactorization == NULL) ||\n        (lp->bfp_factorize == NULL) ||\n        (lp->bfp_finishupdate == NULL) ||\n        (lp->bfp_ftran_normal == NULL) ||\n        (lp->bfp_ftran_prepare == NULL) ||\n        (lp->bfp_btran_normal == NULL) ||\n        (lp->bfp_status == NULL) ||\n        (lp->bfp_implicitslack == NULL) ||\n        (lp->bfp_indexbase == NULL) ||\n        (lp->bfp_rowoffset == NULL) ||\n        (lp->bfp_pivotmax == NULL) ||\n        (lp->bfp_init == NULL) ||\n        (lp->bfp_pivotalloc == NULL) ||\n        (lp->bfp_colcount == NULL) ||\n        (lp->bfp_canresetbasis == NULL) ||\n        (lp->bfp_finishfactorization == NULL) ||\n        (lp->bfp_updaterefactstats == NULL) ||\n        (lp->bfp_prepareupdate == NULL) ||\n        (lp->bfp_pivotRHS == NULL) ||\n        (lp->bfp_btran_double == NULL) ||\n        (lp->bfp_efficiency == NULL) ||\n        (lp->bfp_pivotvector == NULL) ||\n        (lp->bfp_pivotcount == NULL) ||\n        (lp->bfp_refactcount == NULL) ||\n        (lp->bfp_isSetI == NULL) ||\n        (lp->bfp_findredundant == NULL)\n       )) {\n      set_BFP(lp, NULL);\n      if(result == LIB_LOADED)\n        result = LIB_NOFUNCTION;\n    }\n  }\n  if(filename != NULL) {\n    char info[LIB_STR_MAXLEN+1];\n    switch(result) {\n      case LIB_NOTFOUND:   strcpy(info, LIB_STR_NOTFOUND);\n                           break;\n      case LIB_NOINFO:     strcpy(info, LIB_STR_NOINFO);\n                           break;\n      case LIB_NOFUNCTION: strcpy(info, LIB_STR_NOFUNCTION);\n                           break;\n      case LIB_VERINVALID: strcpy(info, LIB_STR_VERINVALID);\n                           break;\n      default:             strcpy(info, LIB_STR_LOADED);\n    }\n    report(lp, IMPORTANT, \"set_BFP: %s '%s'\\n\",\n                          info, filename);\n  }\n  return( (MYBOOL) (result == LIB_LOADED));\n}\n\n\n/* External language interface routines */\n/* DON'T MODIFY */\nlprec * __WINAPI read_XLI(char *xliname, char *modelname, char *dataname, char *options, int verbose)\n{\n  lprec *lp;\n\n  lp = make_lp(0, 0);\n  if(lp != NULL) {\n    lp->source_is_file = TRUE;\n    lp->verbose = verbose;\n    if(!set_XLI(lp, xliname)) {\n      free_lp(&lp);\n      printf(\"read_XLI: No valid XLI package selected or available.\\n\");\n    }\n    else {\n      if(!lp->xli_readmodel(lp, modelname, (dataname != NULL) && (*dataname != 0) ? dataname : NULL, options, verbose))\n        free_lp(&lp);\n    }\n  }\n  return( lp );\n}\n\nMYBOOL __WINAPI write_XLI(lprec *lp, char *filename, char *options, MYBOOL results)\n{\n  return( has_XLI(lp) && mat_validate(lp->matA) && lp->xli_writemodel(lp, filename, options, results) );\n}\n\nMYBOOL __WINAPI has_XLI(lprec *lp)\n{\n  return( is_nativeXLI(lp)\n#if LoadLanguageLib == TRUE\n       || (MYBOOL) (lp->hXLI != NULL)\n#endif\n        );\n}\n\nMYBOOL __WINAPI is_nativeXLI(lprec *lp)\n{\n#ifdef ExcludeNativeLanguage\n  return( FALSE );\n#elif LoadLanguageLib == TRUE\n  return( (MYBOOL) (lp->hXLI == NULL) );\n#else\n  return( TRUE );\n#endif\n}\n\nMYBOOL __WINAPI set_XLI(lprec *lp, char *filename)\n/* (Re)mapping of external language interface variant methods is done here */\n{\n  int result = LIB_LOADED;\n\n#if LoadLanguageLib == TRUE\n  if(lp->hXLI != NULL) {\n  #ifdef WIN32\n    FreeLibrary(lp->hXLI);\n  #else\n    dlclose(lp->hXLI);\n  #endif\n    lp->hXLI = NULL;\n  }\n#endif\n\n  if(filename == NULL) {\n    if(!is_nativeXLI(lp))\n      return( FALSE );\n#ifndef ExcludeNativeLanguage\n    lp->xli_name = xli_name;\n    lp->xli_compatible = xli_compatible;\n    lp->xli_readmodel = xli_readmodel;\n    lp->xli_writemodel = xli_writemodel;\n#endif\n  }\n  else {\n#if LoadLanguageLib == TRUE\n  #ifdef WIN32\n   /* Get a handle to the Windows DLL module. */\n    lp->hXLI = LoadLibrary(filename);\n\n   /* If the handle is valid, try to get the function addresses. */\n    if(lp->hXLI != NULL) {\n      lp->xli_compatible           = (XLIbool_lpintintint *)\n                                      GetProcAddress(lp->hXLI, \"xli_compatible\");\n      if(lp->xli_compatible == NULL)\n        result = LIB_NOINFO;\n      else if(lp->xli_compatible(lp, XLIVERSION, MAJORVERSION, sizeof(REAL))) {\n\n        lp->xli_name                 = (XLIchar *)\n                                        GetProcAddress(lp->hXLI, \"xli_name\");\n        lp->xli_readmodel            = (XLIbool_lpcharcharcharint *)\n                                        GetProcAddress(lp->hXLI, \"xli_readmodel\");\n        lp->xli_writemodel           = (XLIbool_lpcharcharbool *)\n                                        GetProcAddress(lp->hXLI, \"xli_writemodel\");\n      }\n      else\n        result = LIB_VERINVALID;\n    }\n  #else\n   /* First standardize UNIX .SO library name format. */\n    char xliname[260], *ptr;\n\n    strcpy(xliname, filename);\n    if((ptr = strrchr(filename, '/')) == NULL)\n      ptr = filename;\n    else\n      ptr++;\n    xliname[(int) (ptr - filename)] = 0;\n    if(strncmp(ptr, \"lib\", 3))\n      strcat(xliname, \"lib\");\n    strcat(xliname, ptr);\n    if(strcmp(xliname + strlen(xliname) - 3, \".so\"))\n      strcat(xliname, \".so\");\n\n   /* Get a handle to the module. */\n    lp->hXLI = dlopen(xliname, RTLD_LAZY);\n\n   /* If the handle is valid, try to get the function addresses. */\n    if(lp->hXLI != NULL) {\n      lp->xli_compatible           = (XLIbool_lpintintint *)\n                                      dlsym(lp->hXLI, \"xli_compatible\");\n      if(lp->xli_compatible == NULL)\n        result = LIB_NOINFO;\n      else if(lp->xli_compatible(lp, XLIVERSION, MAJORVERSION, sizeof(REAL))) {\n\n        lp->xli_name                 = (XLIchar *)\n                                        dlsym(lp->hXLI, \"xli_name\");\n        lp->xli_readmodel            = (XLIbool_lpcharcharcharint *)\n                                        dlsym(lp->hXLI, \"xli_readmodel\");\n        lp->xli_writemodel           = (XLIbool_lpcharcharbool *)\n                                        dlsym(lp->hXLI, \"xli_writemodel\");\n      }\n      else\n        result = LIB_VERINVALID;\n    }\n  #endif\n    else\n      result = LIB_NOTFOUND;\n#endif\n    /* Do validation */\n    if((result != LIB_LOADED) ||\n       ((lp->xli_name == NULL) ||\n        (lp->xli_compatible == NULL) ||\n        (lp->xli_readmodel == NULL) ||\n        (lp->xli_writemodel == NULL)\n       )) {\n      set_XLI(lp, NULL);\n      if(result == LIB_LOADED)\n        result = LIB_NOFUNCTION;\n    }\n  }\n  if(filename != NULL) {\n    char info[LIB_STR_MAXLEN+1];\n    switch(result) {\n      case LIB_NOTFOUND:   strcpy(info, LIB_STR_NOTFOUND);\n                           break;\n      case LIB_NOINFO:     strcpy(info, LIB_STR_NOINFO);\n                           break;\n      case LIB_NOFUNCTION: strcpy(info, LIB_STR_NOFUNCTION);\n                           break;\n      case LIB_VERINVALID: strcpy(info, LIB_STR_VERINVALID);\n                           break;\n      default:             strcpy(info, LIB_STR_LOADED);\n    }\n    report(lp, IMPORTANT, \"set_XLI: %s '%s'\\n\",\n                          info, filename);\n  }\n  return( (MYBOOL) (result == LIB_LOADED));\n}\n\n\nSTATIC int get_basisOF(lprec *lp, int coltarget[], REAL crow[], int colno[])\n/* Fill vector of basic OF values or subtract incoming values from these.\n   This function is called twice during reduced cost updates when the basis\n   does not contain the basic OF vector as the top row.  The colno[] array\n   is filled with the count of non-zero values and the index to those. */\n{\n  int            i, n = lp->rows, nz = 0;\n  REAL           *obj = lp->obj;\n  register REAL epsvalue = lp->epsvalue;\n\n  /* Compute offset over the specified objective indeces (step 2) */\n  if(coltarget != NULL) {\n    register int  ix, m = coltarget[0];\n    register REAL value;\n\n    for(i = 1, coltarget++; i <= m; i++, coltarget++) {\n      ix = *coltarget;\n      /* Finalize the computation of the reduced costs, based on the format that\n         duals are computed as negatives, ref description for step 1 above */\n      value = crow[ix];\n      if(ix > n)\n        value += obj[ix - n];\n/*      if(value != 0) { */\n      if(fabs(value) > epsvalue) {\n        nz++;\n        if(colno != NULL)\n          colno[nz] = ix;\n      }\n      else\n        value = 0.0;\n      crow[ix] = value;\n    }\n  }\n\n  /* Get the basic objective function values (step 1) */\n  else {\n    register int *basvar = lp->var_basic;\n\n    for(i = 1, crow++, basvar++; i <= n;\n         i++, crow++, basvar++) {\n      /* Load the objective value of the active basic variable; note that we\n         change the sign of the value to maintain computational compatibility with\n         the calculation of duals using in-basis storage of the basic OF values */\n      if(*basvar <= n)\n        *crow = 0;\n      else\n        *crow = -obj[(*basvar) - n];\n      if((*crow) != 0) {\n/*      if(fabs(*crow) > epsvalue) { */\n        nz++;\n        if(colno != NULL)\n          colno[nz] = i;\n      }\n    }\n  }\n  if(colno != NULL)\n    colno[0] = nz;\n  return( nz );\n}\n\nint __WINAPI get_basiscolumn(lprec *lp, int j, int rn[], double bj[])\n/* This routine returns sparse vectors for all basis\n   columns, including the OF dummy (index 0) and slack columns.\n   NOTE that the index usage is nonstandard for lp_solve, since\n   the array offset is 1, not 0. */\n{\n  int k = lp->bfp_rowoffset(lp),\n      matbase = lp->bfp_indexbase(lp);\n\n  /* Do target index adjustment (etaPFI with matbase==0 is special case) */\n  if(matbase > 0)\n    matbase += k - 1;\n\n /* Convert index of slack and user columns */\n  j -= k;\n  if((j > 0) && !lp->bfp_isSetI(lp))\n    j = lp->var_basic[j];\n\n /* Process OF dummy and slack columns (always at lower bound) */\n  if(j <= lp->rows) {\n    rn[1] = j + matbase;\n    bj[1] = 1.0;\n    k = 1;\n  }\n /* Process user columns (negated if at lower bound) */\n  else {\n    k = obtain_column(lp, j, bj, rn, NULL);\n    if(matbase != 0)\n      for(j = 1; j <= k; j++)\n        rn[j] += matbase;\n  }\n\n  return( k );\n}\n\nMYBOOL __WINAPI get_primal_solution(lprec *lp, REAL *pv)\n{\n  if(lp->spx_status == OPTIMAL)\n    ;\n  else if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_primal_solution: Not a valid basis\");\n    return(FALSE);\n  }\n\n  MEMCOPY(pv, lp->best_solution, lp->sum + 1);\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_ptr_primal_solution(lprec *lp, REAL **pv)\n{\n  *pv = lp->best_solution;\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_dual_solution(lprec *lp, REAL *rc)\n{\n  REAL *duals;\n  MYBOOL ret;\n\n  if(!lp->basis_valid) {\n    report(lp, CRITICAL, \"get_dual_solution: Not a valid basis\");\n    return(FALSE);\n  }\n\n  ret = get_ptr_sensitivity_rhs(lp, &duals, NULL, NULL);\n\n  if(ret)\n    MEMCOPY(rc, duals - 1, lp->sum + 1);\n  return(ret);\n}\n\nMYBOOL __WINAPI get_ptr_dual_solution(lprec *lp, REAL **rc)\n{\n  MYBOOL ret = lp->basis_valid;\n\n  /* Just return availability of dual information if rc is NULL */\n  if(rc == NULL)\n    return( ret && ((MIP_count(lp) == 0) || (lp->bb_totalnodes > 0)) );\n\n  if(!ret) {\n    report(lp, CRITICAL, \"get_ptr_dual_solution: Not a valid basis\");\n    return(ret);\n  }\n\n  /* Otherwise, get the pointer to the dual information (and optionally produce it) */\n  ret = get_ptr_sensitivity_rhs(lp, rc, NULL, NULL);\n  if(ret)\n    (*rc)--;\n\n  return(ret);\n}\n\nMYBOOL __WINAPI get_lambda(lprec *lp, REAL *lambda)\n{\n  if(!lp->basis_valid || (get_Lrows(lp) == 0)) {\n    report(lp, CRITICAL, \"get_lambda: Not a valid basis\");\n    return(FALSE);\n  }\n\n  MEMCOPY(lambda, lp->lambda+1, get_Lrows(lp));\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_ptr_lambda(lprec *lp, REAL **lambda)\n{\n  *lambda = lp->lambda;\n  return(TRUE);\n}\n\nint __WINAPI get_orig_index(lprec *lp, int lp_index)\n{\n  if(lp->varmap_locked)\n    return(lp->presolve_undo->var_to_orig[lp_index]);\n  else if(lp_index <= lp->presolve_undo->orig_rows)\n    return(lp_index);\n  else\n    return(lp_index-lp->presolve_undo->orig_rows);\n}\nint __WINAPI get_lp_index(lprec *lp, int orig_index)\n{\n  if(lp->varmap_locked)\n    return(lp->presolve_undo->orig_to_var[orig_index]);\n  else if(orig_index <= lp->presolve_undo->orig_rows)\n    return(orig_index);\n  else\n    return(orig_index-lp->presolve_undo->orig_rows);\n}\n\nMYBOOL __WINAPI is_feasible(lprec *lp, REAL *values, REAL threshold)\n/* Recommend to use threshold = lp->epspivot */\n{\n  int     i, j, elmnr, ie;\n  REAL    *this_rhs, dist;\n  REAL    *value;\n  int     *rownr;\n  MATrec  *mat = lp->matA;\n\n  for(i = lp->rows + 1; i <= lp->sum; i++) {\n    if(values[i - lp->rows] < unscaled_value(lp, lp->orig_lowbo[i], i)\n       || values[i - lp->rows] > unscaled_value(lp, lp->orig_upbo[i], i)) {\n      if(!((lp->sc_lobound[i - lp->rows]>0) && (values[i - lp->rows]==0)))\n        return(FALSE);\n    }\n  }\n\n  this_rhs = (REAL *) mempool_obtainVector(lp->workarrays, lp->rows+1, sizeof(*this_rhs));\n/*  allocREAL(lp, &this_rhs, lp->rows + 1, TRUE); */\n  for(j = 1; j <= lp->columns; j++) {\n    elmnr = mat->col_end[j - 1];\n    ie = mat->col_end[j];\n    rownr = &COL_MAT_ROWNR(elmnr);\n    value = &COL_MAT_VALUE(elmnr);\n    for(; elmnr < ie; elmnr++, rownr += matRowColStep, value += matValueStep) {\n      this_rhs[*rownr] += unscaled_mat(lp, *value, *rownr, j);\n    }\n  }\n  for(i = 1; i <= lp->rows; i++) {\n    dist = lp->orig_rhs[i] - this_rhs[i];\n    my_roundzero(dist, threshold);\n    if((lp->orig_upbo[i] == 0 && dist != 0) ||( dist < 0)) {\n      FREE(this_rhs);\n      return(FALSE);\n    }\n  }\n  mempool_releaseVector(lp->workarrays, (char *) this_rhs, FALSE);\n/*  FREE(this_rhs); */\n  return(TRUE);\n}\n\nint __WINAPI column_in_lp(lprec *lp, REAL *testcolumn)\n{\n  int    i, j, je, colnr = 0;\n  int    nz, ident = 1;\n  MATrec *mat = lp->matA;\n  int    *matRownr;\n  REAL   value, *matValue;\n\n  for(nz = 0, i = 1; i <= lp->rows; i++)\n    if(fabs(testcolumn[i]) > lp->epsvalue) nz++;\n\n  for(i = 1; (i <= lp->columns) && (ident); i++) {\n    ident = nz;\n    value = fabs(get_mat(lp, 0, i)-testcolumn[0]);\n    if(value > lp->epsvalue)\n      continue;\n    j = mat->col_end[i - 1];\n    je = mat->col_end[i];\n    matRownr = &COL_MAT_ROWNR(j);\n    matValue = &COL_MAT_VALUE(j);\n    for(; (j < je) && (ident >= 0);\n        j++, ident--, matRownr += matRowColStep, matValue += matValueStep) {\n      value = *matValue;\n      if(is_chsign(lp, *matRownr))\n        value = my_flipsign(value);\n      value = unscaled_mat(lp, value, *matRownr, i);\n      value -= testcolumn[*matRownr];\n      if(fabs(value) > lp->epsvalue)\n        break;\n    }\n    if(ident == 0)\n      colnr = i;\n  }\n  return( colnr );\n}\n\nMYBOOL __WINAPI set_lp_name(lprec *lp, char *name)\n{\n  if (name == NULL) {\n    FREE(lp->lp_name);\n    lp->lp_name = NULL;\n  }\n  else {\n    allocCHAR(lp, &lp->lp_name, (int) (strlen(name) + 1), AUTOMATIC);\n    strcpy(lp->lp_name, name);\n  }\n  return(TRUE);\n}\n\nchar * __WINAPI get_lp_name(lprec *lp)\n{\n  return((lp->lp_name != NULL) ? lp->lp_name : (char *) \"\");\n}\n\nSTATIC MYBOOL init_rowcol_names(lprec *lp)\n{\n  if(!lp->names_used) {\n    lp->row_name = (hashelem **) calloc(lp->rows_alloc + 1, sizeof(*lp->row_name));\n    lp->col_name = (hashelem **) calloc(lp->columns_alloc + 1, sizeof(*lp->col_name));\n    lp->rowname_hashtab = create_hash_table(lp->rows_alloc + 1, 0);\n    lp->colname_hashtab = create_hash_table(lp->columns_alloc + 1, 1);\n    lp->names_used = TRUE;\n  }\n  return(TRUE);\n}\n\nMYBOOL rename_var(lprec *lp, int varindex, char *new_name, hashelem **list, hashtable **ht)\n{\n  hashelem *hp;\n  MYBOOL   newitem;\n\n  hp = list[varindex];\n  newitem = (MYBOOL) (hp == NULL);\n  if(newitem)\n    hp = puthash(new_name, varindex, list, *ht);\n  else if((strlen(hp->name) != strlen(new_name)) ||\n          (strcmp(hp->name, new_name) != 0)) {\n    hashtable *newht, *oldht;\n\n    allocCHAR(lp, &hp->name, (int) (strlen(new_name) + 1), AUTOMATIC);\n    strcpy(hp->name, new_name);\n    oldht = *ht;\n    newht = copy_hash_table(oldht, list, oldht->size);\n    *ht = newht;\n    free_hash_table(oldht);\n  }\n  return(newitem);\n}\n\nMYBOOL __WINAPI is_use_names(lprec *lp, MYBOOL isrow)\n{\n  if(isrow)\n    return( lp->use_row_names );\n  else\n    return( lp->use_col_names );\n}\n\nvoid __WINAPI set_use_names(lprec *lp, MYBOOL isrow, MYBOOL use_names)\n{\n  if(isrow)\n    lp->use_row_names = use_names;\n  else\n    lp->use_col_names = use_names;\n}\n\nint __WINAPI get_nameindex(lprec *lp, char *varname, MYBOOL isrow)\n{\n  if(isrow)\n    return( find_row(lp, varname, FALSE) );\n  else\n    return( find_var(lp, varname, FALSE) );\n}\n\nMYBOOL __WINAPI set_row_name(lprec *lp, int rownr, char *new_name)\n{\n  if((rownr < 0) || (rownr > lp->rows+1)) {\n    report(lp, IMPORTANT, \"set_row_name: Row %d out of range\", rownr);\n    return(FALSE);\n  }\n\n  /* Prepare for a new row */\n  if((rownr > lp->rows) && !append_rows(lp, rownr-lp->rows))\n    return( FALSE );\n  if(!lp->names_used) {\n    if(!init_rowcol_names(lp))\n      return(FALSE);\n  }\n  rename_var(lp, rownr, new_name, lp->row_name, &lp->rowname_hashtab);\n\n  return(TRUE);\n}\n\nchar * __WINAPI get_row_name(lprec *lp, int rownr)\n{\n  if((rownr < 0) || (rownr > lp->rows+1)) {\n    report(lp, IMPORTANT, \"get_row_name: Row %d out of range\", rownr);\n    return(NULL);\n  }\n\n  if((lp->presolve_undo->var_to_orig != NULL) && lp->wasPresolved) {\n    if(lp->presolve_undo->var_to_orig[rownr] == 0)\n      rownr = -rownr;\n    else\n      rownr = lp->presolve_undo->var_to_orig[rownr];\n  }\n  return( get_origrow_name(lp, rownr) );\n}\n\nchar * __WINAPI get_origrow_name(lprec *lp, int rownr)\n{\n  MYBOOL newrow;\n  char   *ptr;\n\n  newrow = (MYBOOL) (rownr < 0);\n  rownr = abs(rownr);\n#ifdef Paranoia\n  if(((lp->presolve_undo->var_to_orig == NULL) && newrow) ||\n     (rownr > MAX(lp->rows, lp->presolve_undo->orig_rows))) {\n    report(lp, IMPORTANT, \"get_origrow_name: Row %d out of range\", rownr);\n    return(NULL);\n  }\n#endif\n\n  if(lp->names_used && lp->use_row_names && (lp->row_name[rownr] != NULL) &&\n                            (lp->row_name[rownr]->name != NULL)) {\n#ifdef Paranoia\n    if(lp->row_name[rownr]->index != rownr)\n      report(lp, SEVERE, \"get_origrow_name: Inconsistent row ordinal %d vs %d\\n\",\n                         rownr, lp->row_name[rownr]->index);\n#endif\n    ptr = lp->row_name[rownr]->name;\n  }\n  else {\n    if(lp->rowcol_name == NULL)\n      if (!allocCHAR(lp, &lp->rowcol_name, 20, FALSE))\n        return(NULL);\n    ptr = lp->rowcol_name;\n    if(newrow)\n      sprintf(ptr, ROWNAMEMASK2, rownr);\n    else\n      sprintf(ptr, ROWNAMEMASK, rownr);\n  }\n  return(ptr);\n}\n\nMYBOOL __WINAPI set_col_name(lprec *lp, int colnr, char *new_name)\n{\n  if((colnr > lp->columns+1) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"set_col_name: Column %d out of range\", colnr);\n  }\n\n  if((colnr > lp->columns) && !append_columns(lp, colnr-lp->columns))\n    return(FALSE);\n\n  if(!lp->names_used)\n    init_rowcol_names(lp);\n  rename_var(lp, colnr, new_name, lp->col_name, &lp->colname_hashtab);\n\n  return(TRUE);\n}\n\nchar * __WINAPI get_col_name(lprec *lp, int colnr)\n{\n  if((colnr > lp->columns+1) || (colnr < 1)) {\n    report(lp, IMPORTANT, \"get_col_name: Column %d out of range\", colnr);\n    return(NULL);\n  }\n\n  if((lp->presolve_undo->var_to_orig != NULL) && lp->wasPresolved) {\n    if(lp->presolve_undo->var_to_orig[lp->rows + colnr] == 0)\n      colnr = -colnr;\n    else\n      colnr = lp->presolve_undo->var_to_orig[lp->rows + colnr];\n  }\n  return( get_origcol_name(lp, colnr) );\n}\n\nchar * __WINAPI get_origcol_name(lprec *lp, int colnr)\n{\n  MYBOOL newcol;\n  char   *ptr;\n\n  newcol = (MYBOOL) (colnr < 0);\n  colnr = abs(colnr);\n#ifdef Paranoia\n  if(((lp->presolve_undo->var_to_orig == NULL) && newcol) ||\n     (colnr > MAX(lp->columns, lp->presolve_undo->orig_columns))) {\n    report(lp, IMPORTANT, \"get_origcol_name: Column %d out of range\", colnr);\n    return(NULL);\n  }\n#endif\n\n  if(lp->names_used && lp->use_col_names && (lp->col_name[colnr] != NULL) && (lp->col_name[colnr]->name != NULL)) {\n#ifdef Paranoia\n    if(lp->col_name[colnr]->index != colnr)\n      report(lp, SEVERE, \"get_origcol_name: Inconsistent column ordinal %d vs %d\\n\",\n                         colnr, lp->col_name[colnr]->index);\n#endif\n    ptr = lp->col_name[colnr]->name;\n  }\n  else {\n    if(lp->rowcol_name == NULL)\n      if (!allocCHAR(lp, &lp->rowcol_name, 20, FALSE))\n        return(NULL);\n    ptr = lp->rowcol_name;\n    if(newcol)\n      sprintf(ptr, COLNAMEMASK2, colnr);\n    else\n      sprintf(ptr, COLNAMEMASK, colnr);\n  }\n  return(ptr);\n}\n\nSTATIC int MIP_count(lprec *lp)\n{\n  return( lp->int_vars+lp->sc_vars+SOS_count(lp) );\n}\nSTATIC int bin_count(lprec *lp, MYBOOL working)\n{\n  int i, n = 0;\n  if(working) {\n    for(i = lp->rows+1; i <= lp->sum; i++)\n      if(fabs(unscaled_value(lp, lp->upbo[i], i) - 1) < lp->epsvalue)\n        n++;\n  }\n  else {\n    for(i = 1; i <= lp->columns; i++)\n      if((fabs(get_upbo(lp, i) - 1) < lp->epsvalue) &&\n         (fabs(get_lowbo(lp, i) - 0) < lp->epsvalue))\n        n++;\n  }\n  return( n );\n}\nSTATIC int SOS_count(lprec *lp)\n{\n  if(lp->SOS == NULL)\n    return( 0 );\n  else\n    return( lp->SOS->sos_count );\n}\nSTATIC int GUB_count(lprec *lp)\n{\n  if(lp->GUB == NULL)\n    return( 0 );\n  else\n    return( lp->GUB->sos_count );\n}\n\nSTATIC REAL compute_violation(lprec *lp, int row_nr)\n/* Returns the bound violation of a given basic variable; the return\n   value is negative if it is below is lower bound, it is positive\n   if it is greater than the upper bound, and zero otherwise. */\n{\n  REAL value, test;\n\n  value  = lp->rhs[row_nr];\n  row_nr = lp->var_basic[row_nr];\n  test = value - my_lowbound(lp->lowbo[row_nr]);\n  my_roundzero(test, lp->epsprimal);\n  if(test > 0) {\n    test = value - lp->upbo[row_nr];\n    my_roundzero(test, lp->epsprimal);\n    if(test < 0)\n      test = 0;\n  }\n  return( test );\n}\n\nSTATIC REAL feasibilityOffset(lprec *lp, MYBOOL isdual)\n{\n  int    i, j;\n  REAL   f, Extra;\n\n  Extra = 0;\n  if(isdual) {\n   /* This section computes a OF offset to ensure that the dual phase 1 is\n      feasible.  It is used to compute a primal feasible base that can be\n      passed to the primal simplex in phase 2. */\n#if 0\n\n   /* This is the legacy (v3.2-) P1extraVal logic that sets Extra to be the\n      smallest negative reduced cost. Note that the reduced costs are the\n      values of the dual slacks, which are [0..Inf> for feasibility.\n      If we have negative reduced costs for bounded non-basic variables, we\n      can simply switch the bound to obtain feasibility and possibly avoid\n      having to set Extra. */\n    if(!isDualFeasible(lp, lp->epsprimal, NULL, NULL, &f)\n      Extra = f;\n\n#else\n  /* Find the most negative of the objective coefficients. We will subtract this\n     value from every element of the objective row, making it non-negative and\n     the problem therefore dual feasible. */\n    for(i = 1; i <= lp->columns; i++) {\n      f = lp->orig_obj[i];\n      if(f < Extra)\n        Extra = f;\n    }\n#endif\n  }\n\n  else {\n  /* Set Extra to be the index of the most negative of the net RHS coefficients;\n     this approach can be used in the primal phase 1 followed by the dual phase 2\n     and when there are no ranged constraints.  When there are ranged constraints,\n     additional artificial variables must be introduced. */\n    Extra = 0;\n    j = 0;\n    Extra = lp->infinite;\n    for(i = 1; i <= lp->rows; i++) {\n      f = lp->rhs[i];\n      if(f < Extra) {\n        Extra = f;\n        j = i;\n      }\n    }\n    Extra = j;\n  }\n\n  return(Extra);\n\n}\n\nSTATIC REAL compute_dualslacks(lprec *lp, int target, REAL **dvalues, int **nzdvalues, MYBOOL dosum)\n/* Note that this function is similar to the compute_reducedcosts function in lp_price.c */\n{\n  int    i, varnr,\n         *coltarget, **nzduals, *nzvtemp = NULL;\n  REAL   d, g = 0, **duals, *vtemp = NULL;\n  MYBOOL localREAL = (MYBOOL) (dvalues == NULL),\n         localINT  = (MYBOOL) (nzdvalues == NULL);\n\n  if(is_action(lp->spx_action, ACTION_REBASE) ||\n     is_action(lp->spx_action, ACTION_REINVERT) || !lp->basis_valid)\n    return( g );\n\n  /* Initialize */\n  if(!localREAL) {\n    duals = dvalues;\n    nzduals = nzdvalues;\n  }\n  else {\n    duals = &vtemp;\n    nzduals = &nzvtemp;\n  }\n  if(localINT || (*nzduals == NULL))\n    allocINT(lp, nzduals, lp->columns + 1, AUTOMATIC);\n  if(localREAL || (*duals == NULL))\n    allocREAL(lp, duals, lp->sum + 1, AUTOMATIC);\n  if(target == 0)\n    target = SCAN_ALLVARS+ USE_NONBASICVARS;\n\n  /* Define variable target list and compute the reduced costs */\n  coltarget = (int *) mempool_obtainVector(lp->workarrays, lp->columns+1, sizeof(*coltarget));\n  if(!get_colIndexA(lp, target, coltarget, FALSE)) {\n    mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n    return(FALSE);\n  }\n  bsolve(lp, 0, *duals, NULL, lp->epsmachine*DOUBLEROUND, 1.0);\n  prod_xA(lp, coltarget, *duals, NULL, lp->epsmachine, 1.0,\n                         *duals, *nzduals, MAT_ROUNDDEFAULT | MAT_ROUNDRC);\n  mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n\n  /* Compute sum or maximum infeasibility as specified */\n  for(i = 1; i <= (*nzduals)[0]; i++) {\n    varnr = (*nzduals)[i];\n    d = my_chsign(!lp->is_lower[varnr], (*duals)[varnr]);\n    if(d < 0) {\n      if(dosum)\n        g += -d;         /* Compute sum as a positive number */\n      else {\n        SETMIN(g, d);    /* Compute gap as a negative number */\n      }\n    }\n  }\n\n  /* Clean up */\n  if(localREAL)\n    FREE(*duals);\n  if(localINT)\n    FREE(*nzduals);\n\n  return( g );\n}\n\nSTATIC REAL compute_feasibilitygap(lprec *lp, MYBOOL isdual, MYBOOL dosum)\n{\n  REAL f = 0;\n\n  /* This computes the primal feasibility gap (for use with the dual simplex phase 1) */\n  if(isdual) {\n    int  i;\n    REAL g;\n\n    for(i = 1; i <= lp->rows; i++) {\n      if(lp->rhs[i] < 0)\n        g = lp->rhs[i];\n      else if(lp->rhs[i] > lp->upbo[lp->var_basic[i]])\n        g = lp->rhs[i] - lp->upbo[lp->var_basic[i]];\n      else\n        g = 0;\n      if(dosum)\n        f += g;\n      else {\n        SETMAX(f, g);\n      }\n    }\n  }\n  /* This computes the dual feasibility gap (for use with the primal simplex phase 1) */\n  else\n    f = compute_dualslacks(lp, SCAN_USERVARS+USE_ALLVARS, NULL, NULL, dosum);\n\n  return( f );\n}\n\n/* Find the smallest fractional value in a given row of the OF/constraint matrix */\nSTATIC int row_decimals(lprec *lp, int rownr, MYBOOL intsonly, REAL *intscalar)\n{\n  int basi, i, j, ncols = lp->columns;\n  REAL f, /* g, */ epsvalue = lp->epsprimal;\n\n  basi = 0;\n  for(j = 1; j <= ncols; j++) {\n    if(intsonly && !is_int(lp, j)) {\n      if(intsonly == TRUE)\n        break;\n      else\n        continue;\n    }\n    f = fabs(get_mat(lp, rownr, j));\n    /* f = fmod(f, 1); */\n    f -= floor (f + epsvalue);\n/*\n    if(f <= epsvalue)\n      continue;\n    g = f;\n*/\n    for(i = 0; (i <= MAX_FRACSCALE) && (/* g */ f > epsvalue); i++) {\n      f *= 10;\n      /* g = fmod(f, 1); */\n      f -= floor (f + epsvalue);\n    }\n    if(i > MAX_FRACSCALE)\n      /* i = MAX_FRACSCALE */ break;\n    SETMAX(basi, i);\n  }\n  if(j > ncols)\n    *intscalar = pow(10.0, basi);\n  else {\n    basi = -1;\n    *intscalar = 1;\n  }\n  return( basi );\n}\n\nSTATIC int row_intstats(lprec *lp, int rownr, int pivcolnr, int *maxndec,\n                        int *plucount, int *intcount, int *intval, REAL *valGCD, REAL *pivcolval)\n{\n  int    jb, je, jj, nn = 0, multA, multB, intGCD = 0;\n  REAL   rowval, inthold, intfrac;\n  MATrec *mat = lp->matA;\n\n  /* Do we have a valid matrix? */\n  if(mat_validate(mat)) {\n\n    /* Get smallest fractional row value */\n    *maxndec = row_decimals(lp, rownr, AUTOMATIC, &intfrac);\n\n    /* Get OF row starting and ending positions, as well as the first column index */\n    if(rownr == 0) {\n      jb = 1;\n      je = lp->columns+1;\n    }\n    else {\n      jb = mat->row_end[rownr-1];\n      je = mat->row_end[rownr];\n    }\n    nn = je - jb;\n    *pivcolval = 1.0;\n    *plucount = 0;\n    *intcount = 0;\n    *intval   = 0;\n    for(; jb < je; jb++) {\n\n      if(rownr == 0) {\n        if(lp->orig_obj[jb] == 0) {\n          nn--;\n          continue;\n        }\n        jj = jb;\n      }\n      else\n        jj = ROW_MAT_COLNR(jb);\n\n      /* Pick up the value of the pivot column and continue */\n      if(jj == pivcolnr) {\n        if(rownr == 0)\n          *pivcolval = unscaled_mat(lp, lp->orig_obj[jb], 0, jb);\n        else\n          *pivcolval = get_mat_byindex(lp, jb, TRUE, FALSE);\n        continue;\n      }\n      if(!is_int(lp, jj))\n        continue;\n\n      /* Update the count of integer columns */\n      (*intcount)++;\n\n      /* Update the count of positive parameter values */\n      if(rownr == 0)\n        rowval = unscaled_mat(lp, lp->orig_obj[jb], 0, jb);\n      else\n        rowval = get_mat_byindex(lp, jb, TRUE, FALSE);\n      if(rowval > 0)\n        (*plucount)++;\n\n      /* Check if the parameter value is integer and update the row's GCD */\n      rowval = fabs(rowval) * intfrac;\n      rowval += rowval*lp->epsmachine;\n      rowval = modf(rowval, &inthold);\n      if(rowval < lp->epsprimal) {\n        (*intval)++;\n        if(*intval == 1)\n          intGCD = (int) inthold;\n        else\n          intGCD = gcd(intGCD, (LLONG) inthold, &multA, &multB);\n      }\n    }\n    *valGCD = intGCD;\n    *valGCD /= intfrac;\n  }\n\n  return(nn);\n}\n\n#if 0\nREAL MIP_stepOF(lprec *lp)\n/* This function tries to find a non-zero minimum improvement\n   if the OF contains all integer variables (logic only applies if we are\n   looking for a single solution, not possibly several equal-valued ones).\n*/\n{\n  MYBOOL OFgcd;\n  int    colnr, rownr, n, ib, ie, maxndec,\n         pluscount, intcount, intval;\n  REAL   value, valOF, divOF, valGCD;\n  MATrec *mat = lp->matA;\n\n  value = 0;\n  if((lp->int_vars > 0) && (lp->solutionlimit == 1) && mat_validate(mat)) {\n\n    /* Get statistics for integer OF variables and compute base stepsize */\n    n = row_intstats(lp, 0, -1, &maxndec, &pluscount, &intcount, &intval, &valGCD, &divOF);\n    if((n == 0) || (maxndec < 0))\n      return( value );\n    OFgcd = (MYBOOL) (intval > 0);\n    if(OFgcd)\n      value = valGCD;\n\n    /* Check non-ints in the OF to see if we can get more info */\n    if(n - intcount > 0) {\n      int nrv = 0;\n\n      /* See if we have equality constraints */\n      ie = lp->rows;\n      for(ib = 1; ib <= ie; ib++) {\n        if(is_constr_type(lp, ib, EQ))\n          break;\n      }\n\n      /* If so, there may be a chance to find an improved stepsize */\n      if(ib < ie)\n      for(colnr = 1; colnr <= lp->columns; colnr++) {\n\n        /* Go directly to the next variable if this is an integer or\n          there is no row candidate to explore for hidden bounds for\n          real-valued variables (limit scan to one row!) */\n        if(is_int(lp, colnr))\n          continue;\n        nrv++;\n        /* Scan equality constraints */\n        ib = mat->col_end[colnr-1];\n        ie = mat->col_end[colnr];\n        while(ib < ie) {\n          if(is_constr_type(lp, (rownr = COL_MAT_ROWNR(ib)), EQ)) {\n\n            /* Get \"child\" row statistics, but break out if we don't\n              find enough information, i.e. no integers with coefficients of proper type */\n            n = row_intstats(lp, rownr, colnr, &maxndec, &pluscount, &intcount, &intval, &valGCD, &divOF);\n            if((intval < n - 1) || (maxndec < 0)) {\n              value = 0;\n              break;\n            }\n\n            /* We can update */\n            valOF = unscaled_mat(lp, lp->orig_obj[colnr], 0, colnr);\n            valOF = fabs( valOF * (valGCD / divOF) );\n            if(OFgcd) {\n              SETMIN(value, valOF);\n            }\n            else {\n              OFgcd = TRUE;\n              value = valOF;\n            }\n          }\n          ib++;\n        }\n\n        /* No point in continuing scan if we failed in current column */\n        if(value == 0)\n          break;\n      }\n\n      /* Check if we found information for any real-valued variable;\n         if not, then we must set the iprovement delta to 0 */\n      if(nrv == 0)\n        value = 0;\n    }\n  }\n  return( value );\n}\n#else\n\nREAL MIP_stepOF(lprec *lp)\n/* This function tries to find a non-zero minimum improvement\n   if the OF contains all integer variables (logic only applies if we are\n   looking for a single solution, not possibly several equal-valued ones). */\n{\n  MYBOOL  OFgcd;\n  int     colnr, rownr, n, ib, ie,\n          pluscount, intcount;\n  int     intval, maxndec;\n  REAL    value = 0, valOF, divOF, valGCD;\n  MATrec  *mat = lp->matA;\n\n  if((lp->int_vars > 0) && (lp->solutionlimit == 1) && mat_validate(mat)) {\n\n    /* Get statistics for integer OF variables and compute base stepsize */\n    n = row_intstats(lp, 0, 0, &maxndec, &pluscount, &intcount, &intval, &valGCD, &divOF);\n    if((n == 0) || (maxndec < 0))\n      return( value );\n    OFgcd = (MYBOOL) (intval > 0);\n    if(OFgcd)\n      value = valGCD;\n\n    /* Check non-ints in the OF to see if we can get more info */\n    if(n - intcount > 0) {\n      int nrv = n - intcount; /* Number of real variables in the objective */\n      int niv = 0;            /* Number of real variables identified as integer */\n      int nrows = lp->rows;\n\n      /* See if we have equality constraints */\n      for(ib = 1; ib <= nrows; ib++) {\n        if(is_constr_type(lp, ib, EQ))\n          break;\n      }\n\n      /* If so, there may be a chance to find an improved stepsize */\n      if(ib < nrows)\n      for(colnr = 1; colnr <= lp->columns; colnr++) {\n\n        /* Go directly to the next variable if this is an integer or\n          there is no row candidate to explore for hidden bounds for\n          real-valued variables (limit scan to one row/no recursion) */\n        if((lp->orig_obj[colnr] == 0) || is_int(lp, colnr))\n          continue;\n\n        /* Scan equality constraints */\n        ib = mat->col_end[colnr-1];\n        ie = mat->col_end[colnr];\n        while(ib < ie) {\n          if(is_constr_type(lp, (rownr = COL_MAT_ROWNR(ib)), EQ)) {\n\n            /* Get \"child\" row statistics, but break out if we don't\n              find enough information, i.e. no integers with coefficients of proper type */\n            n = row_intstats(lp, rownr, colnr, &maxndec, &pluscount, &intcount, &intval, &valGCD, &divOF);\n            if((intval < n - 1) || (maxndec < 0)) {\n              value = 0;\n              break;\n            }\n            niv++;\n\n            /* We can update */\n            valOF = unscaled_mat(lp, lp->orig_obj[colnr], 0, colnr);\n            valOF = fabs( valOF * (valGCD / divOF) );\n            if(OFgcd) {\n              SETMIN(value, valOF);\n            }\n            else {\n              OFgcd = TRUE;\n              value = valOF;\n            }\n          }\n          ib++;\n        }\n\n        /* No point in continuing scan if we failed in current column */\n        if(value == 0)\n          break;\n      }\n\n      /* Check if we found information for any real-valued variable;\n         if not, then we must set the improvement delta to 0 */\n      if(nrv > niv)\n        value = 0;\n    }\n  }\n  return( value );\n}\n\n#endif\n\nSTATIC MYBOOL isPrimalSimplex(lprec *lp)\n{\n  return((MYBOOL) (((lp->simplex_mode & SIMPLEX_Phase1_PRIMAL) != 0) ||\n                   ((lp->simplex_mode & SIMPLEX_Phase2_PRIMAL) != 0)));\n}\n\nSTATIC MYBOOL isPhase1(lprec *lp)\n{\n  return((MYBOOL) (((lp->simplex_mode & SIMPLEX_Phase1_PRIMAL) != 0) ||\n                   ((lp->simplex_mode & SIMPLEX_Phase1_DUAL) != 0)));\n}\n\nSTATIC MYBOOL isP1extra(lprec *lp)\n{\n  return((MYBOOL) ((lp->P1extraDim > 0) || (lp->P1extraVal != 0)));\n}\n\nSTATIC MYBOOL feasiblePhase1(lprec *lp, REAL epsvalue)\n{\n  REAL   gap;\n  MYBOOL test;\n\n  gap = fabs(lp->rhs[0] - lp->orig_rhs[0]);\n  test = (MYBOOL) (gap < epsvalue);\n  return( test) ;\n}\n\nSTATIC MYBOOL isDegenerateBasis(lprec *lp, int basisvar)\n{\n  int varindex;\n\n  varindex = lp->var_basic[basisvar];\n  if((fabs(lp->rhs[basisvar]) < lp->epsprimal) ||\n     (fabs(lp->upbo[varindex]-lp->rhs[basisvar]) < lp->epsprimal))\n    return( TRUE );\n  else\n    return( FALSE );\n}\n\nSTATIC int findBasicFixedvar(lprec *lp, int afternr, MYBOOL slacksonly)\n{\n  int varnr, delta = 1;\n\n  if(afternr < 0) {\n    delta = -1;\n    afternr = -afternr;\n  }\n  afternr += delta;\n  if((afternr < 1) || (afternr > lp->rows))\n    return( 0 );\n\n  for(; (afternr > 0) && (afternr <= lp->rows); afternr += delta) {\n    varnr = lp->var_basic[afternr];\n    if(((varnr <= lp->rows) && is_constr_type(lp, varnr, EQ)) ||\n       (!slacksonly && (varnr > lp->rows) && is_fixedvar(lp, varnr)))\n      break;\n  }\n\n  if(afternr > lp->rows)\n    afternr = 0;\n\n  return( afternr );\n}\n\nSTATIC MYBOOL isBasisVarFeasible(lprec *lp, REAL tol, int basis_row)\n{\n  int    col;\n  REAL   x;\n  MYBOOL Ok = TRUE;\n  MYBOOL doSC = FALSE;\n\n  col = lp->var_basic[basis_row];\n  x = lp->rhs[basis_row];         /* The current solution of basic variables stored here! */\n  if((x < -tol) || (x > lp->upbo[col]+tol))\n    Ok = FALSE;\n  else if(doSC && (col > lp->rows) && (fabs(lp->sc_lobound[col - lp->rows]) > 0)) {\n    if((x > tol) && (x < fabs(lp->sc_lobound[col - lp->rows])-tol))\n      Ok = FALSE;\n  }\n  return( Ok );\n}\nSTATIC MYBOOL isPrimalFeasible(lprec *lp, REAL tol, int infeasibles[], REAL *feasibilitygap)\n{\n  int    i;\n  MYBOOL feasible = TRUE;\n\n  /* This is a short-hand call to rowdual() to check for primal infeasibility */\n\n#if 0\n  /* Traditional indexing style */\n  for(i = 1; i <= lp->rows; i++) {\n    feasible = isBasisVarFeasible(lp, tol, i);\n#else\n  /* Fast array pointer style */\n  LREAL *rhsptr;\n  int  *idxptr;\n\n  if(infeasibles != NULL)\n    infeasibles[0] = 0;\n  for(i = 1, rhsptr = lp->rhs+1, idxptr = lp->var_basic+1;\n      (i <= lp->rows); i++, rhsptr++, idxptr++) {\n    feasible = TRUE;\n/*    if(((*rhsptr) < lp->lowbo[*idxptr]-tol) || ((*rhsptr) > lp->upbo[*idxptr]+tol)) */\n    if(((*rhsptr) < -tol) || ((*rhsptr) > lp->upbo[*idxptr]+tol))\n      feasible = FALSE;\n#endif\n    if(!feasible) {\n      if(infeasibles == NULL)\n        break;\n      infeasibles[0]++;\n      infeasibles[infeasibles[0]] = i;\n    }\n  }\n\n  /* Compute feasibility gap (could actually do this calculation above) */\n  if(feasibilitygap != NULL) {\n    if(feasible)\n      *feasibilitygap = 0.0;\n    else\n      *feasibilitygap = feasibilityOffset(lp, FALSE);\n  }\n\n  return(feasible);\n}\n\nSTATIC MYBOOL isDualFeasible(lprec *lp, REAL tol, int *boundflipcount, int infeasibles[], REAL *feasibilitygap)\n{\n  int    i, varnr,\n         n = 0,  /* Number of infeasible duals corrected with bound-swaps */\n         m = 0,\n         target = SCAN_ALLVARS+USE_NONBASICVARS;\n  REAL   f = 0;\n  MYBOOL feasible, islower;\n\n\n  /* The reduced costs are the values of the dual slacks, which\n     are [0..Inf> for feasibility.  If we have negative reduced costs\n     for bounded non-basic variables, we can simply switch the bound\n     of bounded variables to obtain dual feasibility and possibly avoid\n     having to use dual simplex phase 1. */\n  if((infeasibles != NULL) || (boundflipcount != NULL)) {\n    int  *nzdcol = NULL;\n    REAL d, *dcol = NULL;\n\n    f = compute_dualslacks(lp, target, &dcol, &nzdcol, FALSE);\n    if(nzdcol != NULL)\n    for(i = 1; i <= nzdcol[0]; i++) {\n      varnr = nzdcol[i];\n      islower = lp->is_lower[varnr];\n      d = my_chsign(!islower, dcol[varnr]);\n\n      /* Don't bother with uninteresting non-basic variables */\n      if((d > -tol) ||                /* Positive reduced costs with a tolerance */\n         my_unbounded(lp, varnr) ||   /* Free variables cannot change bound */\n         is_fixedvar(lp, varnr))      /* Equality slack or a fixed variable (\"type 3\") */\n        continue;\n\n      /* Check if we have non-flippable bounds, i.e. an unbounded variable\n         (types 2+4), or bounded variables (type 3), and if the counter is NULL. */\n      if( (boundflipcount == NULL) ||\n          ((lp->bb_level <= 1) && (my_rangebo(lp, varnr) > fabs(lp->negrange))) ||\n          (islower && my_infinite(lp, lp->upbo[varnr])) ||\n          (!islower && my_infinite(lp, my_lowbo(lp, varnr))) ) {\n        m++;\n        if(infeasibles != NULL)\n          infeasibles[m] = varnr;\n      }\n      /* Only do bound flips if the user-provided counter is non-NULL */\n      else {\n        lp->is_lower[varnr] = !islower;\n        n++;\n      }\n    }\n    if(infeasibles != NULL)\n      infeasibles[0] = m;\n    FREE(dcol);\n    FREE(nzdcol);\n    if(n > 0) {\n      set_action(&lp->spx_action, ACTION_RECOMPUTE);\n      if(m == 0)\n        f = 0;\n    }\n  }\n  else\n    f = compute_dualslacks(lp, target, NULL, NULL, FALSE);\n/*    f = feasibilityOffset(lp, TRUE); */  /* Safe legacy mode */\n\n  /* Do an extra scan to see if there are bounded variables in the OF not present in any constraint;\n     Most typically, presolve fixes such cases, so this is rarely encountered. */\n\n  varnr = lp->rows + 1;\n  for(i = 1; i <= lp->columns; i++, varnr++) {\n    if (mat_collength(lp->matA, i) == 0) {\n      islower = lp->is_lower[varnr];\n      if((my_chsign(islower, lp->orig_obj[i]) > 0) && !SOS_is_member(lp->SOS, 0, i)) {\n        lp->is_lower[varnr] = !islower;\n        if((islower && my_infinite(lp,  lp->upbo[varnr] /* lp->orig_upbo[varnr] */)) ||\n           (!islower && my_infinite(lp,  my_lowbo(lp, varnr) /* lp->orig_lowbo[varnr] */))) {\n          lp->spx_status = UNBOUNDED;\n          break;\n        }\n        /* lp->is_lower[varnr] = !islower; */\n        n++;\n      }\n    }\n  }\n\n  /* Return status */\n\n  if(boundflipcount != NULL)\n    *boundflipcount = n;\n  if(feasibilitygap != NULL) {\n    my_roundzero(f, tol);\n    *feasibilitygap = f;\n  }\n  feasible = (MYBOOL) ((f == 0) && (m == 0));\n\n  return(feasible);\n}\n\nvoid __WINAPI default_basis(lprec *lp)\n{\n  int i;\n\n  /* Set the slack variables to be basic; note that the is_basic[] array\n     is a helper array filled in presolve() to match var_basic[]. */\n  for(i = 1; i <= lp->rows; i++) {\n    lp->var_basic[i] = i;\n    lp->is_basic[i] = TRUE;\n    lp->is_lower[i] = TRUE;\n  }\n  lp->var_basic[0] = TRUE; /* Set to signal that this is the default basis */\n\n  /* Set user variables at their lower bound, including the\n     dummy slack for the objective \"constraint\" */\n  for(; i <= lp->sum; i++) {\n    lp->is_basic[i] = FALSE;\n    lp->is_lower[i] = TRUE;\n  }\n  lp->is_lower[0] = TRUE;\n\n  set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n  lp->basis_valid = TRUE;  /* Do not re-initialize basis on entering Solve */\n}\n\nint __WINAPI get_basiscrash(lprec *lp)\n{\n  return(lp->crashmode);\n}\n\nvoid __WINAPI set_basiscrash(lprec *lp, int mode)\n{\n  lp->crashmode = mode;\n}\n\nMYBOOL __WINAPI set_basis(lprec *lp, int *bascolumn, MYBOOL nonbasic)   /* Added by KE */\n{\n  int    i,s,k,n;\n\n  /* Make sure we are consistent */\n  if(lp->wasPresolved && ((lp->rows != lp->presolve_undo->orig_rows) ||\n                          (lp->columns != lp->presolve_undo->orig_columns)))\n    return( FALSE );\n\n /* Initialize (lp->is_basic is set in preprocess); Note that as of v5 and before\n    it is an lp_solve convention that basic variables are at their lower bounds!\n    This routine provides for the a possible future case that basic variables\n    can be upper-bounded. */\n  lp->is_lower[0] = TRUE;\n  for(i = 1; i <= lp->sum; i++) {\n    lp->is_lower[i] = TRUE;\n    lp->is_basic[i] = FALSE;\n  }\n  for(i = 1; i <= lp->rows; i++)\n    lp->var_basic[i] = FALSE;\n\n /* Set basic and optionally non-basic variables;\n    negative index means at lower bound, positive at upper bound */\n  if(nonbasic)\n    n = lp->sum;\n  else\n    n = lp->rows;\n  for(i = 1; i <= n; i++) {\n    s = bascolumn[i];\n    k = abs(s);\n    if(k <= 0 || k > lp->sum)\n      return( FALSE );\n    if(i <= lp->rows) {\n      lp->var_basic[i] = k;\n      lp->is_basic[k] = TRUE;\n    }\n    else     /* Remove this test if basic variables can be upper-bounded */\n    if(s > 0)\n      lp->is_lower[k] = FALSE;\n  }\n  if(!verify_basis(lp))\n    return( FALSE );\n\n /* Invalidate basis */\n  set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n  lp->basis_valid = TRUE;   /* Do not re-initialize basis on entering Solve */\n  lp->var_basic[0] = FALSE; /* Set to signal that this is a non-default basis */\n\n  return( TRUE );\n}\n\nvoid __WINAPI reset_basis(lprec *lp)\n{\n  lp->basis_valid = FALSE;   /* Causes reinversion at next opportunity */\n}\n\nMYBOOL __WINAPI get_basis(lprec *lp, int *bascolumn, MYBOOL nonbasic)\n{\n  int    k, i;\n\n  if(!lp->basis_valid ||\n     (lp->rows != lp->presolve_undo->orig_rows) ||\n     (lp->columns != lp->presolve_undo->orig_columns))\n    return( FALSE );\n\n  *bascolumn = 0;\n\n  /* First save basic variable indexes */\n  for(i = 1; i <= lp->rows; i++) {\n    k = lp->var_basic[i];\n    bascolumn[i] = my_chsign(lp->is_lower[k], k);\n  }\n\n  /* Then optionally save non-basic variable indeces */\n  if(nonbasic) {\n    for(k = 1; (k <= lp->sum) && (i <= lp->sum); k++) {\n      if(lp->is_basic[k])\n        continue;\n      bascolumn[i] = my_chsign(lp->is_lower[k], k);\n      i++;\n    }\n  }\n  return( TRUE );\n}\n\nSTATIC MYBOOL is_BasisReady(lprec *lp)\n{\n  return( (MYBOOL) (lp->var_basic[0] != AUTOMATIC) );\n}\n\nSTATIC MYBOOL is_slackbasis(lprec *lp)\n{\n  int n = 0, err = 0;\n  if(lp->basis_valid) {\n    int i, k;\n    MYBOOL *used = NULL;\n\n    allocMYBOOL(lp, &used, lp->rows+1, TRUE);\n    for(i = 1; i <= lp->rows; i++) {\n      k = lp->var_basic[i];\n      if(k <= lp->rows) {\n        if(used[k])\n          err++;\n        else\n          used[k] = TRUE;\n        n++;\n      }\n    }\n    FREE(used);\n    if(err > 0)\n      report(lp, SEVERE, \"is_slackbasis: %d inconsistencies found in slack basis\\n\", err);\n  }\n  return( (MYBOOL) (n == lp->rows) );\n}\n\nSTATIC MYBOOL verify_basis(lprec *lp)\n{\n  int    i, ii, k = 0;\n  MYBOOL result = FALSE;\n\n  for(i = 1; i <= lp->rows; i++) {\n    ii = lp->var_basic[i];\n    if((ii < 1) || (ii > lp->sum) || !lp->is_basic[ii]) {\n      k = i;\n      ii = 0;\n      goto Done;\n    }\n  }\n\n  ii = lp->rows;\n  for(i = 1; i <= lp->sum; i++) {\n    if(lp->is_basic[i])\n      ii--;\n  }\n  result = (MYBOOL) (ii == 0);\n\nDone:\n#if 0  /* For testing */\n  if(!result)\n    ii = 0;\n#endif\n  return(result);\n}\n\nint __WINAPI set_basisvar(lprec *lp, int basisPos, int enteringCol)\n{\n  int leavingCol;\n\n  leavingCol = lp->var_basic[basisPos];\n\n#ifdef Paranoia\n  if((basisPos < 1) || (basisPos > lp->rows))\n    report(lp, SEVERE, \"set_basisvar: Invalid leaving basis position %d specified at iter %.0f\\n\",\n                       basisPos, (double) get_total_iter(lp));\n  if((leavingCol < 1) || (leavingCol > lp->sum))\n    report(lp, SEVERE, \"set_basisvar: Invalid leaving column %d referenced at iter %.0f\\n\",\n                       leavingCol, (double) get_total_iter(lp));\n  if((enteringCol < 1) || (enteringCol > lp->sum))\n    report(lp, SEVERE, \"set_basisvar: Invalid entering column %d specified at iter %.0f\\n\",\n                       enteringCol, (double) get_total_iter(lp));\n#endif\n\n#ifdef ParanoiaXY\n  if(!lp->is_basic[leavingCol])\n    report(lp, IMPORTANT, \"set_basisvar: Leaving variable %d is not basic at iter %.0f\\n\",\n                           leavingCol, (double) get_total_iter(lp));\n  if(enteringCol > lp->rows && lp->is_basic[enteringCol])\n    report(lp, IMPORTANT, \"set_basisvar: Entering variable %d is already basic at iter %.0f\\n\",\n                           enteringCol, (double) get_total_iter(lp));\n#endif\n\n  lp->var_basic[0]          = FALSE;       /* Set to signal that this is a non-default basis */\n  lp->var_basic[basisPos]   = enteringCol;\n  lp->is_basic[leavingCol]  = FALSE;\n  lp->is_basic[enteringCol] = TRUE;\n  if(lp->bb_basis != NULL)\n    lp->bb_basis->pivots++;\n\n  return(leavingCol);\n}\n\n/* Bounds updating and unloading routines; requires that the\n   current values for upbo and lowbo are in the original base. */\nSTATIC int perturb_bounds(lprec *lp, BBrec *perturbed, MYBOOL doRows, MYBOOL doCols, MYBOOL includeFIXED)\n{\n  int  i, ii, n = 0;\n  REAL new_lb, new_ub, *upbo, *lowbo;\n\n  if(perturbed == NULL)\n    return( n );\n\n /* Map reference bounds to previous state, i.e. cumulate\n    perturbations in case of persistent problems */\n  upbo  = perturbed->upbo;\n  lowbo = perturbed->lowbo;\n\n /* Set appropriate target variable range */\n  i = 1;\n  ii = lp->rows;\n  if(!doRows)\n    i += ii;\n  if(!doCols)\n    ii = lp->sum;\n\n /* Perturb (expand) finite variable bounds randomly */\n  for(; i <= ii; i++) {\n\n    /* Don't perturb regular slack variables */\n    if((i <= lp->rows) && (lowbo[i] == 0) && (upbo[i] >= lp->infinite))\n      continue;\n\n    new_lb = lowbo[i];\n    new_ub = upbo[i];\n\n    /* Don't perturb fixed variables if not specified */\n    if(!includeFIXED && (new_ub == new_lb))\n      continue;\n\n    /* Lower bound for variables (consider implementing RHS here w/contentmode== AUTOMATIC) */\n    if((i > lp->rows) && (new_lb < lp->infinite)) {\n      new_lb = rand_uniform(lp, RANDSCALE) + 1;\n      new_lb *= lp->epsperturb;\n      lowbo[i] -= new_lb;\n      n++;\n    }\n\n    /* Upper bound */\n    if(new_ub < lp->infinite) {\n      new_ub = rand_uniform(lp, RANDSCALE) + 1;\n      new_ub *= lp->epsperturb;\n      upbo[i] += new_ub;\n      n++;\n    }\n  }\n\n /* Make sure we start from scratch */\n  set_action(&lp->spx_action, ACTION_REBASE);\n\n  return( n );\n}\n\nSTATIC MYBOOL impose_bounds(lprec *lp, REAL *upbo, REAL *lowbo)\n/* Explicitly set working bounds to given vectors without pushing or popping */\n{\n  MYBOOL ok;\n\n  ok = (MYBOOL) ((upbo != NULL) || (lowbo != NULL));\n  if(ok) {\n    if((upbo != NULL) && (upbo != lp->upbo))\n      MEMCOPY(lp->upbo,  upbo,  lp->sum + 1);\n    if((lowbo != NULL) && (lowbo != lp->lowbo))\n      MEMCOPY(lp->lowbo, lowbo, lp->sum + 1);\n    if(lp->bb_bounds != NULL)\n      lp->bb_bounds->UBzerobased = FALSE;\n    set_action(&lp->spx_action, ACTION_REBASE);\n  }\n  set_action(&lp->spx_action, ACTION_RECOMPUTE);\n  return( ok );\n}\n\nSTATIC MYBOOL validate_bounds(lprec *lp, REAL *upbo, REAL *lowbo)\n/* Check if all bounds are Explicitly set working bounds to given vectors without pushing or popping */\n{\n  MYBOOL ok;\n  int    i;\n\n  ok = (MYBOOL) ((upbo != NULL) || (lowbo != NULL));\n  if(ok) {\n    for(i = 1; i <= lp->sum; i++)\n      if((lowbo[i] > upbo[i]) || (lowbo[i] < lp->orig_lowbo[i]) || (upbo[i] > lp->orig_upbo[i]))\n        break;\n    ok = (MYBOOL) (i > lp->sum);\n  }\n  return( ok );\n}\n\nSTATIC int unload_BB(lprec *lp)\n{\n  int levelsunloaded = 0;\n\n  if(lp->bb_bounds != NULL)\n    while(pop_BB(lp->bb_bounds))\n      levelsunloaded++;\n  return( levelsunloaded );\n}\n\n\n#define LowerStorageModel 1\n#define BasisStorageModel 1\nSTATIC basisrec *push_basis(lprec *lp, int *basisvar, MYBOOL *isbasic, MYBOOL *islower)\n/* Save the ingoing basis and push it onto the stack */\n{\n  int sum = lp->sum + 1;\n  basisrec *newbasis = NULL;\n\n  newbasis = (basisrec *) calloc(sizeof(*newbasis), 1);\n  if((newbasis != NULL) &&\n#if LowerStorageModel == 0\n    allocMYBOOL(lp, &newbasis->is_lower,  sum,  FALSE) &&\n#else\n    allocMYBOOL(lp, &newbasis->is_lower,  (sum + 8) / 8,  TRUE) &&\n#endif\n#if BasisStorageModel == 0\n    allocMYBOOL(lp, &newbasis->is_basic,  sum,  FALSE) &&\n#endif\n    allocINT(lp,    &newbasis->var_basic, lp->rows + 1, FALSE)) {\n\n    if(islower == NULL)\n      islower = lp->is_lower;\n    if(isbasic == NULL)\n      isbasic = lp->is_basic;\n    if(basisvar == NULL)\n      basisvar = lp->var_basic;\n\n#if LowerStorageModel == 0\n    MEMCOPY(newbasis->is_lower,  islower,  sum);\n#else\n    for(sum = 1; sum <= lp->sum; sum++)\n      if(islower[sum])\n        set_biton(newbasis->is_lower, sum);\n#endif\n#if BasisStorageModel == 0\n    MEMCOPY(newbasis->is_basic,  isbasic,  lp->sum + 1);\n#endif\n    MEMCOPY(newbasis->var_basic, basisvar, lp->rows + 1);\n\n    newbasis->previous = lp->bb_basis;\n    if(lp->bb_basis == NULL)\n      newbasis->level = 0;\n    else\n      newbasis->level = lp->bb_basis->level + 1;\n    newbasis->pivots = 0;\n\n    lp->bb_basis = newbasis;\n  }\n  return( newbasis );\n}\n\nSTATIC MYBOOL compare_basis(lprec *lp)\n/* Compares the last pushed basis with the currently active basis */\n{\n  int i, j;\n  MYBOOL same_basis = TRUE;\n\n  if(lp->bb_basis == NULL)\n    return( FALSE );\n\n  /* Loop over basis variables until a mismatch (order can be different) */\n  i = 1;\n  while(same_basis && (i <= lp->rows)) {\n    j = 1;\n    while(same_basis && (j <= lp->rows)) {\n      same_basis = (MYBOOL) (lp->bb_basis->var_basic[i] != lp->var_basic[j]);\n      j++;\n    }\n    same_basis = !same_basis;\n    i++;\n  }\n  /* Loop over bound status indicators until a mismatch */\n  i = 1;\n  while(same_basis && (i <= lp->sum)) {\n    same_basis = (lp->bb_basis->is_lower[i] && lp->is_lower[i]);\n    i++;\n  }\n\n  return( same_basis );\n}\n\nSTATIC MYBOOL restore_basis(lprec *lp)\n/* Restore values from the previously pushed / saved basis without popping it */\n{\n  MYBOOL ok;\n  int    i;\n\n  ok = (MYBOOL) (lp->bb_basis != NULL);\n  if(ok) {\n    MEMCOPY(lp->var_basic, lp->bb_basis->var_basic, lp->rows + 1);\n#if BasisStorageModel == 0\n    MEMCOPY(lp->is_basic,  lp->bb_basis->is_basic,  lp->sum + 1);\n#else\n    MEMCLEAR(lp->is_basic, lp->sum + 1);\n    for(i = 1; i <= lp->rows; i++)\n      lp->is_basic[lp->var_basic[i]] = TRUE;\n#endif\n#if LowerStorageModel == 0\n    MEMCOPY(lp->is_lower,  lp->bb_basis->is_lower,  lp->sum + 1);\n#else\n    for(i = 1; i <= lp->sum; i++)\n      lp->is_lower[i] = is_biton(lp->bb_basis->is_lower, i);\n#endif\n    set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT);\n  }\n  return( ok );\n}\n\nSTATIC MYBOOL pop_basis(lprec *lp, MYBOOL restore)\n/* Pop / free, and optionally restore the previously \"pushed\" / saved basis */\n{\n  MYBOOL ok;\n  basisrec *oldbasis;\n\n  ok = (MYBOOL) (lp->bb_basis != NULL);\n  if(ok) {\n    oldbasis = lp->bb_basis;\n    if(oldbasis != NULL) {\n      lp->bb_basis = oldbasis->previous;\n      FREE(oldbasis->var_basic);\n#if BasisStorageModel == 0\n      FREE(oldbasis->is_basic);\n#endif\n      FREE(oldbasis->is_lower);\n      FREE(oldbasis);\n    }\n    if(restore && (lp->bb_basis != NULL))\n      restore_basis(lp);\n  }\n  return( ok );\n}\n\nSTATIC int unload_basis(lprec *lp, MYBOOL restorelast)\n{\n  int levelsunloaded = 0;\n\n  if(lp->bb_basis != NULL)\n    while(pop_basis(lp, restorelast))\n      levelsunloaded++;\n  return( levelsunloaded );\n}\n\n\nSTATIC REAL scaled_floor(lprec *lp, int colnr, REAL value, REAL epsscale)\n{\n  value = floor(value);\n  if(value != 0)\n  if(lp->columns_scaled && is_integerscaling(lp)) {\n    value = scaled_value(lp, value, colnr);\n    if(epsscale != 0)\n      value += epsscale*lp->epsmachine;\n/*      value += epsscale*lp->epsprimal; */\n/*    value = restoreINT(value, lp->epsint); */\n  }\n  return(value);\n}\n\nSTATIC REAL scaled_ceil(lprec *lp, int colnr, REAL value, REAL epsscale)\n{\n  value = ceil(value);\n  if(value != 0)\n  if(lp->columns_scaled && is_integerscaling(lp)) {\n    value = scaled_value(lp, value, colnr);\n    if(epsscale != 0)\n      value -= epsscale*lp->epsmachine;\n/*      value -= epsscale*lp->epsprimal; */\n/*    value = restoreINT(value, lp->epsint); */\n  }\n  return(value);\n}\n\n/* Branch and bound variable selection functions */\n\nSTATIC MYBOOL is_sc_violated(lprec *lp, int column)\n{\n  int  varno;\n  REAL tmpreal;\n\n  varno = lp->rows+column;\n  tmpreal = unscaled_value(lp, lp->sc_lobound[column], varno);\n  return( (MYBOOL) ((tmpreal > 0) &&                    /* it is an (inactive) SC variable...    */\n                    (lp->solution[varno] < tmpreal) &&  /* ...and the NZ lower bound is violated */\n                    (lp->solution[varno] > 0)) );       /* ...and the Z lowerbound is violated   */\n}\nSTATIC int find_sc_bbvar(lprec *lp, int *count)\n{\n  int    i, ii, n, bestvar;\n  int    firstsc, lastsc;\n  REAL   hold, holdINT, bestval, OFval, randval, scval;\n  MYBOOL reversemode, greedymode, randomizemode,\n         pseudocostmode, pseudocostsel;\n\n  bestvar = 0;\n  if((lp->sc_vars == 0) || (*count > 0))\n    return(bestvar);\n\n  reversemode    = is_bb_mode(lp, NODE_WEIGHTREVERSEMODE);\n  greedymode     = is_bb_mode(lp, NODE_GREEDYMODE);\n  randomizemode  = is_bb_mode(lp, NODE_RANDOMIZEMODE);\n  pseudocostmode = is_bb_mode(lp, NODE_PSEUDOCOSTMODE);\n  pseudocostsel  = is_bb_rule(lp, NODE_PSEUDOCOSTSELECT) ||\n                   is_bb_rule(lp, NODE_PSEUDONONINTSELECT) ||\n                   is_bb_rule(lp, NODE_PSEUDORATIOSELECT);\n\n  bestvar = 0;\n  bestval = -lp->infinite;\n  hold    = 0;\n  randval = 1;\n  firstsc = 0;\n  lastsc  = lp->columns;\n\n  for(n = 1; n <= lp->columns; n++) {\n    ii = get_var_priority(lp, n);\n    i = lp->rows + ii;\n    if(!lp->bb_varactive[ii] && is_sc_violated(lp, ii) && !SOS_is_marked(lp->SOS, 0, ii)) {\n\n      /* Do tallies */\n      (*count)++;\n      lastsc = i;\n      if(firstsc <= 0)\n        firstsc = i;\n      scval = get_pseudorange(lp->bb_PseudoCost, ii, BB_SC);\n\n      /* Select default pricing/weighting mode */\n      if(pseudocostmode)\n        OFval = get_pseudonodecost(lp->bb_PseudoCost, ii, BB_SC, lp->solution[i]);\n      else\n        OFval = my_chsign(is_maxim(lp), get_mat(lp, 0, ii));\n\n      if(randomizemode)\n        randval = exp(rand_uniform(lp, 1.0));\n\n      /* Find the maximum pseudo-cost of a variable (don't apply pseudocostmode here) */\n      if(pseudocostsel) {\n        if(pseudocostmode)\n          hold = OFval;\n        else\n          hold = get_pseudonodecost(lp->bb_PseudoCost, ii, BB_SC, lp->solution[i]);\n        hold *= randval;\n        if(greedymode) {\n          if(pseudocostmode) /* Override! */\n            OFval = my_chsign(is_maxim(lp), get_mat(lp, 0, ii));\n          hold *= OFval;\n        }\n        hold = my_chsign(reversemode, hold);\n      }\n      else\n      /* Find the variable with the largest sc gap (closest to the sc mean) */\n      if(is_bb_rule(lp, NODE_FRACTIONSELECT)) {\n        hold = modf(lp->solution[i]/scval, &holdINT);\n        holdINT = hold-1;\n        if(fabs(holdINT) > hold)\n          hold = holdINT;\n        if(greedymode)\n          hold *= OFval;\n        hold = my_chsign(reversemode, hold)*scval*randval;\n      }\n      else\n      /* Do first or last violated sc index selection (default) */\n      /* if(is_bb_rule(lp, NODE_FIRSTSELECT)) */\n      {\n        if(reversemode)\n          continue;\n        else {\n          bestvar = i;\n          break;\n        }\n      }\n\n      /* Select better, check for ties, and split by proximity to 0.5*sc_lobound */\n      if(hold > bestval) {\n        if( (bestvar == 0) ||\n            (hold > bestval+lp->epsprimal) ||\n            (fabs(modf(lp->solution[i]/scval, &holdINT) - 0.5) <\n             fabs(modf(lp->solution[bestvar]/\n                       get_pseudorange(lp->bb_PseudoCost, bestvar-lp->rows, BB_SC), &holdINT) - 0.5)) ) {\n          bestval = hold;\n          bestvar = i;\n        }\n      }\n    }\n  }\n\n  if(is_bb_rule(lp, NODE_FIRSTSELECT) && reversemode)\n    bestvar = lastsc;\n\n  return(bestvar);\n}\n\nSTATIC int find_sos_bbvar(lprec *lp, int *count, MYBOOL intsos)\n{\n  int k, i, j, var;\n\n  var = 0;\n  if((lp->SOS == NULL) || (*count > 0))\n    return(var);\n\n  /* Check if the SOS'es happen to already be satisified */\n  i = SOS_is_satisfied(lp->SOS, 0, lp->solution);\n  if((i == SOS_COMPLETE) || (i == SOS_INCOMPLETE))\n    return(-1);\n\n  /* Otherwise identify a SOS variable to enter B&B */\n  for(k = 0; k < lp->sos_vars; k++) {\n    i = lp->sos_priority[k];\n#ifdef Paranoia\n    if((i < 1) || (i > lp->columns))\n      report(lp, SEVERE, \"find_sos_bbvar: Invalid SOS variable map %d at %d\\n\",\n                         i, k);\n#endif\n    j = lp->rows + i;\n    if(!SOS_is_marked(lp->SOS, 0, i) && !SOS_is_full(lp->SOS, 0, i, FALSE)) {\n/*    if(!SOS_is_marked(lp->SOS, 0, i) && !SOS_is_full(lp->SOS, 0, i, TRUE)) { */\n      if(!intsos || is_int(lp, i)) {\n        (*count)++;\n        if(var == 0) {\n          var = j;\n          break;\n        }\n      }\n    }\n  }\n#ifdef Paranoia\n  if((var > 0) && !SOS_is_member(lp->SOS, 0, var-lp->rows))\n     report(lp, SEVERE, \"find_sos_bbvar: Found variable %d, which is not a SOS!\\n\", var);\n#endif\n  return(var);\n}\n\nSTATIC int find_int_bbvar(lprec *lp, int *count, BBrec *BB, MYBOOL *isfeasible)\n{\n  int    i, ii, n, k, bestvar, depthmax, *nonint = NULL;\n  REAL   hold, holdINT, bestval, OFval, randval,\n         *lowbo = BB->lowbo, *upbo = BB->upbo;\n  MYBOOL reversemode, greedymode, depthfirstmode, breadthfirstmode,\n         randomizemode, rcostmode,\n         pseudocostmode, pseudocostsel, pseudostrong, isINT, valINT;\n\n  if((lp->int_vars == 0) || (*count > 0))\n    return( 0 );\n  if(lp->bb_usenode != NULL) {\n    i = lp->bb_usenode(lp, lp->bb_nodehandle, BB_INT);\n    if(i >= 0) {\n      if(i > 0)\n        (*count)++;\n      return( i );\n    }\n  }\n\n  reversemode    = is_bb_mode(lp, NODE_WEIGHTREVERSEMODE);\n  greedymode     = is_bb_mode(lp, NODE_GREEDYMODE);\n  randomizemode  = is_bb_mode(lp, NODE_RANDOMIZEMODE);\n  depthfirstmode = is_bb_mode(lp, NODE_DEPTHFIRSTMODE);\n  breadthfirstmode = is_bb_mode(lp, NODE_BREADTHFIRSTMODE) &&\n                     (MYBOOL) (lp->bb_level <= lp->int_vars);\n  rcostmode      = (MYBOOL) /* FALSE */ (BB->lp->solutioncount > 0) && is_bb_mode(lp, NODE_RCOSTFIXING) ; /* 5/2/08 peno disabled NODE_RCOSTFIXING because it results in non-optimal solutions with some models */ /* 15/2/8 peno enabled NODE_RCOSTFIXING again because a fix is found. See lp_simplex.c NODE__RCOSTFIXING fix */\n  pseudocostmode = is_bb_mode(lp, NODE_PSEUDOCOSTMODE);\n  pseudocostsel  = is_bb_rule(lp, NODE_PSEUDOCOSTSELECT) ||\n                   is_bb_rule(lp, NODE_PSEUDONONINTSELECT) ||\n                   is_bb_rule(lp, NODE_PSEUDORATIOSELECT);\n  pseudostrong   = FALSE &&\n                   pseudocostsel && !rcostmode && is_bb_mode(lp, NODE_STRONGINIT);\n\n  /* Fill list of non-ints */\n  allocINT(lp, &nonint, lp->columns + 1, FALSE);\n  n = 0;\n  depthmax = -1;\n  if(isfeasible != NULL)\n    *isfeasible = TRUE;\n  BB->lastrcf = 0;\n  for(k = 1; (k <= lp->columns); k++) {\n    ii = get_var_priority(lp, k);\n    isINT = is_int(lp,ii);\n    i  = lp->rows + ii;\n\n    /* Tally reduced cost fixing opportunities for ranged non-basic nonINTs */\n    if(!isINT) {\n#ifdef UseMilpExpandedRCF\n      if(rcostmode) {\n        bestvar = rcfbound_BB(BB, i, isINT, NULL, isfeasible);\n        if(bestvar != FR)\n          BB->lastrcf++;\n      }\n#endif\n    }\n    else {\n\n      valINT = solution_is_int(lp, i, FALSE);\n\n      /* Skip already fixed variables */\n      if(lowbo[i] == upbo[i]) {\n\n        /* Check for validity */\n#ifdef Paranoia\n        if(!valINT) {\n          report(lp, IMPORTANT,\n                 \"find_int_bbvar: INT var %d was fixed at %d, but computed as %g at node %.0f\\n\",\n                  ii, (int) lowbo[i], lp->solution[i], (double) lp->bb_totalnodes);\n          lp->bb_break = TRUE;\n          lp->spx_status = UNKNOWNERROR;\n          bestvar = 0;\n          goto Done;\n        }\n#endif\n      }\n\n      /* The variable has not yet been fixed */\n      else {\n\n        /* Tally reduced cost fixing opportunities (also when the\n           variables are integer-valued at the current relaxation) */\n        if(rcostmode) {\n          bestvar = rcfbound_BB(BB, i, isINT, NULL, isfeasible);\n          if(bestvar != FR)\n            BB->lastrcf++;\n        }\n        else\n          bestvar = FR;\n\n        /* Only qualify variable as branching node if it is non-integer and\n           it will not be subsequently fixed via reduced cost fixing logic */\n        if(!valINT && (bestvar >= FR)) {\n\n          n++;\n          nonint[n] = ii;\n          SETMAX(depthmax, lp->bb_varactive[ii]);\n        }\n      }\n\n    }\n  }\n\n#ifdef UseMilpSlacksRCF\n  /* Optionally also tally slacks */\n  if(rcostmode) {\n    for(i = 1; (i <= lp->rows) && (BB->lastrcf == 0); i++) {\n      /* Skip already fixed slacks (equalities) */\n      if(lowbo[i] < upbo[i]) {\n        bestvar = rcfbound_BB(BB, i, FALSE, NULL, isfeasible);\n        if(bestvar != FR)\n          BB->lastrcf++;\n      }\n    }\n  }\n#endif\n  nonint[0] = n;\n  *count    = n;\n  bestvar   = 0;\n  if(n == 0)     /* No non-integers found */\n    goto Done;\n\n  bestval  = -lp->infinite;\n  hold     = 0;\n  randval  = 1;\n\n  /* Sort non-ints by depth in case we have breadthfirst or depthfirst modes */\n  if((lp->bb_level > 1) && (depthmax > 0) && (depthfirstmode || breadthfirstmode)) {\n    int *depths = NULL;\n\n    /* Fill attribute array and make sure ordinal order breaks ties during sort */\n    allocINT(lp, &depths, n + 1, FALSE);\n    for(i = 1; i <= n; i++)\n      depths[i] = (depthfirstmode ? n+1-i : i) + (n+1)*lp->bb_varactive[nonint[i]];\n    hpsortex(depths, n, 1, sizeof(*nonint), depthfirstmode, compareINT, nonint);\n    FREE(depths);\n  }\n\n  /* Do simple firstselect handling */\n  if(is_bb_rule(lp, NODE_FIRSTSELECT)) {\n    if(reversemode)\n      bestvar = lp->rows + nonint[nonint[0]];\n    else\n      bestvar = lp->rows + nonint[1];\n  }\n\n  else for(n = 1; n <= nonint[0]; n++) {\n    ii = nonint[n];\n    i = lp->rows + ii;\n\n    /* Do the naive detection */\n    if(n == 1)\n      bestvar = i;\n\n    /* Should we do a \"strong\" pseudo-cost initialization or an incremental update? */\n    if(pseudostrong &&\n       (MAX(lp->bb_PseudoCost->LOcost[ii].rownr,\n            lp->bb_PseudoCost->UPcost[ii].rownr) < lp->bb_PseudoCost->updatelimit) &&\n       (MAX(lp->bb_PseudoCost->LOcost[ii].colnr,\n            lp->bb_PseudoCost->UPcost[ii].colnr) < 5*lp->bb_PseudoCost->updatelimit)) {\n      strongbranch_BB(lp, BB, ii, BB_INT, nonint[0]);\n    }\n\n    /* Select default pricing/weighting mode */\n    if(pseudocostmode)\n      OFval = get_pseudonodecost(lp->bb_PseudoCost, ii, BB_INT, lp->solution[i]);\n    else\n      OFval = my_chsign(is_maxim(lp), get_mat(lp, 0, ii));\n\n    if(randomizemode)\n      randval = exp(rand_uniform(lp, 1.0));\n\n    /* Find the maximum pseudo-cost of a variable (don't apply pseudocostmode here) */\n    if(pseudocostsel) {\n      if(pseudocostmode)\n        hold = OFval;\n      else\n        hold = get_pseudonodecost(lp->bb_PseudoCost, ii, BB_INT, lp->solution[i]);\n      hold *= randval;\n      if(greedymode) {\n        if(pseudocostmode) /* Override! */\n          OFval = my_chsign(is_maxim(lp), get_mat(lp, 0, ii));\n        hold *= OFval;\n      }\n      hold = my_chsign(reversemode, hold);\n    }\n    else\n    /* Find the variable with the largest gap to its bounds (distance from being fixed) */\n    if(is_bb_rule(lp, NODE_GAPSELECT)) {\n      hold = lp->solution[i];\n      holdINT = hold-unscaled_value(lp, upbo[i], i);\n      hold -= unscaled_value(lp, lowbo[i], i);\n      if(fabs(holdINT) > hold)\n        hold = holdINT;\n      if(greedymode)\n        hold *= OFval;\n      hold = my_chsign(reversemode, hold)*randval;\n    }\n    else\n    /* Find the variable with the largest integer gap (closest to 0.5) */\n    if(is_bb_rule(lp, NODE_FRACTIONSELECT)) {\n      hold = modf(lp->solution[i], &holdINT);\n      holdINT = hold-1;\n      if(fabs(holdINT) > hold)\n        hold = holdINT;\n      if(greedymode)\n        hold *= OFval;\n      hold = my_chsign(reversemode, hold)*randval;\n    }\n    else\n    /* Find the \"range\", most flexible variable */\n    if(is_bb_rule(lp, NODE_RANGESELECT)) {\n      hold = unscaled_value(lp, upbo[i]-lowbo[i], i);\n      if(greedymode)\n        hold *= OFval;\n      hold = my_chsign(reversemode, hold)*randval;\n    }\n\n    /* Select better, check for ties, and split by proximity to 0.5 */\n    if(hold > bestval) {\n      if( (hold > bestval+lp->epsprimal) ||\n          (fabs(modf(lp->solution[i], &holdINT) - 0.5) <\n           fabs(modf(lp->solution[bestvar], &holdINT) - 0.5)) ) {\n        bestval = hold;\n        bestvar = i;\n      }\n    }\n  }\n\nDone:\n  FREE(nonint);\n  return(bestvar);\n}\n\nSTATIC BBPSrec *init_pseudocost(lprec *lp, int pseudotype)\n{\n  int     i;\n  REAL    PSinitUP, PSinitLO;\n  BBPSrec *newitem;\n  MYBOOL  isPSCount;\n\n  /* Allocate memory */\n  newitem = (BBPSrec*) malloc(sizeof(*newitem));\n  newitem->lp = lp;\n  newitem->LOcost = (MATitem*) malloc((lp->columns+1) * sizeof(*newitem->LOcost));\n  newitem->UPcost = (MATitem*) malloc((lp->columns+1) * sizeof(*newitem->UPcost));\n  newitem->secondary = NULL;\n\n  /* Initialize with OF values */\n  newitem->pseodotype = (pseudotype & NODE_STRATEGYMASK);\n  isPSCount = ((pseudotype & NODE_PSEUDONONINTSELECT) != 0);\n  for(i = 1; i <= lp->columns; i++) {\n    newitem->LOcost[i].rownr = 1; /* Actual updates */\n    newitem->LOcost[i].colnr = 1; /* Attempted updates */\n    newitem->UPcost[i].rownr = 1;\n    newitem->UPcost[i].colnr = 1;\n\n    /* Initialize with the plain OF value as conventional usage suggests, or\n       override in case of pseudo-nonint count strategy */\n    PSinitUP = my_chsign(is_maxim(lp), get_mat(lp, 0, i));\n    PSinitLO = -PSinitUP;\n    if(isPSCount) {\n      /* Set default assumed reduction in the number of non-ints by choosing this variable;\n         KE changed from 0 on 30 June 2004 and made two-sided selectable.  Note that the\n         typical value range is <0..1>, with a positive bias for an \"a priori\" assumed\n         fast-converging (low \"MIP-complexity\") model. Very hard models may require\n         negative initialized values for one or both. */\n      PSinitUP = 0.1*0;\n#if 0\n      PSinitUP = my_chsign(PSinitUP < 0, PSinitUP);\n      PSinitLO = -PSinitUP;\n#else\n      PSinitLO = PSinitUP;\n#endif\n    }\n    newitem->UPcost[i].value = PSinitUP;\n    newitem->LOcost[i].value = PSinitLO;\n  }\n  newitem->updatelimit     = lp->bb_PseudoUpdates;\n  newitem->updatesfinished = 0;\n  newitem->restartlimit    = DEF_PSEUDOCOSTRESTART;\n\n  /* Let the user get an opportunity to initialize pseudocosts */\n  if(userabort(lp, MSG_INITPSEUDOCOST))\n    lp->spx_status = USERABORT;\n\n  return( newitem );\n}\n\nSTATIC MYBOOL free_pseudoclass(BBPSrec **PseudoClass)\n{\n  BBPSrec *target = *PseudoClass;\n\n  FREE(target->LOcost);\n  FREE(target->UPcost);\n  target = target->secondary;\n  FREE(*PseudoClass);\n  *PseudoClass = target;\n\n  return( (MYBOOL) (target != NULL) );\n}\n\nSTATIC void free_pseudocost(lprec *lp)\n{\n  if((lp != NULL) && (lp->bb_PseudoCost != NULL)) {\n    while(free_pseudoclass(&(lp->bb_PseudoCost)) );\n  }\n}\n\nMYBOOL __WINAPI set_pseudocosts(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit)\n{\n  int i;\n\n  if((lp->bb_PseudoCost == NULL) || ((clower == NULL) && (cupper == NULL)))\n    return(FALSE);\n  for(i = 1; i <= lp->columns; i++) {\n    if(clower != NULL)\n      lp->bb_PseudoCost->LOcost[i].value = clower[i];\n    if(cupper != NULL)\n      lp->bb_PseudoCost->UPcost[i].value = cupper[i];\n  }\n  if(updatelimit != NULL)\n    lp->bb_PseudoCost->updatelimit = *updatelimit;\n  return(TRUE);\n}\n\nMYBOOL __WINAPI get_pseudocosts(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit)\n{\n  int i;\n\n  if((lp->bb_PseudoCost == NULL) || ((clower == NULL) && (cupper == NULL)))\n    return(FALSE);\n  for(i = 1; i <= lp->columns; i++) {\n    if(clower != NULL)\n      clower[i] = lp->bb_PseudoCost->LOcost[i].value;\n    if(cupper != NULL)\n      cupper[i] = lp->bb_PseudoCost->UPcost[i].value;\n  }\n  if(updatelimit != NULL)\n    *updatelimit = lp->bb_PseudoCost->updatelimit;\n  return(TRUE);\n}\n\nSTATIC REAL get_pseudorange(BBPSrec *pc, int mipvar, int varcode)\n{\n  if(varcode == BB_SC)\n    return( unscaled_value(pc->lp, pc->lp->sc_lobound[mipvar], pc->lp->rows+mipvar) );\n  else\n    return( 1.0 );\n}\n\nSTATIC void update_pseudocost(BBPSrec *pc, int mipvar, int varcode, MYBOOL capupper, REAL varsol)\n{\n  REAL     OFsol, uplim;\n  MATitem  *PS;\n  MYBOOL   nonIntSelect = is_bb_rule(pc->lp, NODE_PSEUDONONINTSELECT);\n\n  /* Establish input values;\n     Note: The pseudocosts are normalized to the 0-1 range! */\n  uplim = get_pseudorange(pc, mipvar, varcode);\n  varsol = modf(varsol/uplim, &OFsol);\n\n  /* Set reference value according to pseudocost mode */\n  if(nonIntSelect)\n    OFsol = pc->lp->bb_bounds->lastvarcus;    /* The count of MIP infeasibilities */\n  else\n    OFsol = pc->lp->solution[0];              /* The problem's objective function value */\n\n  if(isnan(varsol)) {\n    pc->lp->bb_parentOF = OFsol;\n    return;\n  }\n\n  /* Point to the applicable (lower or upper) bound and increment attempted update count */\n  if(capupper) {\n    PS = &pc->LOcost[mipvar];\n  }\n  else {\n    PS = &pc->UPcost[mipvar];\n    varsol = 1-varsol;\n  }\n  PS->colnr++;\n\n  /* Make adjustment to divisor if we are using the ratio pseudo-cost approach */\n  if(is_bb_rule(pc->lp, NODE_PSEUDORATIOSELECT))\n    varsol *= capupper;\n\n  /* Compute the update (consider weighting in favor of most recent) */\n  mipvar = pc->updatelimit;\n  if(((mipvar <= 0) || (PS->rownr < mipvar)) &&\n     (fabs(varsol) > pc->lp->epspivot)) {\n    /* We are interested in the change in the MIP measure (contribution to increase\n       or decrease, as the case may be) and not its last value alone. */\n    PS->value = PS->value*PS->rownr + (pc->lp->bb_parentOF-OFsol) / (varsol*uplim);\n    PS->rownr++;\n    PS->value /= PS->rownr;\n    /* Check if we have enough information to restart */\n    if(PS->rownr == mipvar) {\n      pc->updatesfinished++;\n      if(is_bb_mode(pc->lp, NODE_RESTARTMODE) &&\n        (pc->updatesfinished/(2.0*pc->lp->int_vars) >\n         pc->restartlimit)) {\n        pc->lp->bb_break = AUTOMATIC;\n        pc->restartlimit *= 2.681;  /* KE: Who can figure this one out? */\n        if(pc->restartlimit > 1)\n          pc->lp->bb_rule -= NODE_RESTARTMODE;\n        report(pc->lp, NORMAL, \"update_pseudocost: Restarting with updated pseudocosts\\n\");\n      }\n    }\n  }\n  pc->lp->bb_parentOF = OFsol;\n}\n\nSTATIC REAL get_pseudobranchcost(BBPSrec *pc, int mipvar, MYBOOL dofloor)\n{\n  if(dofloor)\n    return( pc->LOcost[mipvar].value );\n  else\n    return( pc->UPcost[mipvar].value );\n}\n\nSTATIC REAL get_pseudonodecost(BBPSrec *pc, int mipvar, int vartype, REAL varsol)\n{\n  REAL hold, uplim;\n\n  uplim = get_pseudorange(pc, mipvar, vartype);\n  varsol = modf(varsol/uplim, &hold);\n  if(isnan(varsol))\n    varsol = 0;\n\n  hold = pc->LOcost[mipvar].value*varsol +\n         pc->UPcost[mipvar].value*(1-varsol);\n\n  return( hold*uplim );\n}\n\nSTATIC int compute_theta(lprec *lp, int rownr, LREAL *theta, int isupbound, REAL HarrisScalar, MYBOOL primal)\n/* The purpose of this routine is to compute the non-basic bound state / value of\n   the leaving variable. Note that the incoming theta is \"d\" in Chvatal-terminology */\n{\n  int             colnr = lp->var_basic[rownr];\n  register LREAL x     = lp->rhs[rownr];\n  REAL            lb    = 0,  /* Put lower bound here when the fully bounded version is implemented */\n                  ub    = lp->upbo[colnr],\n                  eps   = lp->epsprimal;  /* Primal feasibility tolerance */\n\n  /* Compute theta for the primal simplex */\n  HarrisScalar *= eps;\n  if(primal) {\n\n    if(*theta > 0)\n      x -= lb - HarrisScalar;   /* A positive number */\n    else if(ub < lp->infinite)\n      x -= ub + HarrisScalar;   /* A negative number */\n    else {\n      *theta = -lp->infinite;\n      return( colnr );\n    }\n  }\n  /* Compute theta for the dual simplex */\n  else {\n\n    if(isupbound)\n      *theta = -(*theta);\n\n    /* Current value is below or equal to its lower bound */\n    if(x < lb+eps)\n      x -= lb - HarrisScalar;\n\n    /* Current value is above or equal to its upper bound */\n    else if(x > ub-eps) {\n      if(ub >= lp->infinite) {\n        *theta = lp->infinite * my_sign(*theta);\n        return( colnr );\n      }\n      else\n        x -= ub + HarrisScalar;\n    }\n  }\n  my_roundzero(x, lp->epsmachine);\n  *theta = x / *theta;\n\n#ifdef EnforcePositiveTheta\n  /* Check if we have negative theta due to rounding or an internal error */\n  if(*theta < 0) {\n    if(primal && (ub == lb))\n      lp->rhs[rownr] = lb;\n    else\n#ifdef Paranoia\n    if(*theta < -eps) {\n      report(lp, DETAILED, \"compute_theta: Negative theta (%g) not allowed in base-0 version of lp_solve\\n\",\n                            *theta);\n    }\n#endif\n    *theta = 0;\n  }\n#endif\n\n  return( colnr );\n}\n\nSTATIC MYBOOL check_degeneracy(lprec *lp, REAL *pcol, int *degencount)\n/* Check if the entering column Pi=Inv(B)*a is likely to produce improvement;\n   (cfr. Istvan Maros: CTOTSM p. 233) */\n{\n  int  i, ndegen;\n  REAL *rhs, sdegen, epsmargin = lp->epsprimal;\n\n  sdegen = 0;\n  ndegen = 0;\n  rhs    = lp->rhs;\n  for(i = 1; i <= lp->rows; i++) {\n    rhs++;\n    pcol++;\n    if(fabs(*rhs) < epsmargin) {\n      sdegen += *pcol;\n      ndegen++;\n    }\n    else if(fabs((*rhs)-lp->upbo[lp->var_basic[i]]) < epsmargin) {\n      sdegen -= *pcol;\n      ndegen++;\n    }\n  }\n  if(degencount != NULL)\n    *degencount = ndegen;\n/*  sdegen += epsmargin*ndegen; */\n  return( (MYBOOL) (sdegen <= 0) );\n}\n\nSTATIC MYBOOL performiteration(lprec *lp, int rownr, int varin, LREAL theta, MYBOOL primal, MYBOOL allowminit,\n                               REAL *prow, int *nzprow, REAL *pcol, int *nzpcol, int *boundswaps)\n{\n  int    varout;\n  REAL   pivot, epsmargin, leavingValue, leavingUB, enteringUB;\n  MYBOOL leavingToUB = FALSE, enteringFromUB, enteringIsFixed, leavingIsFixed;\n  MYBOOL *islower = &(lp->is_lower[varin]);\n  MYBOOL minitNow = FALSE, minitStatus = ITERATE_MAJORMAJOR;\n  LREAL  deltatheta = theta;\n\n  if(userabort(lp, MSG_ITERATION))\n    return( minitNow );\n\n#ifdef Paranoia\n  if(rownr > lp->rows) {\n    if (lp->spx_trace)\n      report(lp, IMPORTANT, \"performiteration: Numeric instability encountered!\\n\");\n    lp->spx_status = NUMFAILURE;\n    return( FALSE );\n  }\n#endif\n  varout = lp->var_basic[rownr];\n#ifdef Paranoia\n  if(!lp->is_lower[varout])\n    report(lp, SEVERE, \"performiteration: Leaving variable %d was at its upper bound at iter %.0f\\n\",\n                        varout, (double) get_total_iter(lp));\n#endif\n\n  /* Theta is the largest change possible (strictest constraint) for the entering\n     variable (Theta is Chvatal's \"t\", ref. Linear Programming, pages 124 and 156) */\n  lp->current_iter++;\n\n  /* Test if it is possible to do a cheap \"minor iteration\"; i.e. set entering\n     variable to its opposite bound, without entering the basis - which is\n     obviously not possible for fixed variables! */\n  epsmargin = lp->epsprimal;\n  enteringFromUB = !(*islower);\n  enteringUB = lp->upbo[varin];\n  leavingUB  = lp->upbo[varout];\n  enteringIsFixed = (MYBOOL) (fabs(enteringUB) < epsmargin);\n  leavingIsFixed  = (MYBOOL) (fabs(leavingUB) < epsmargin);\n#if defined _PRICE_NOBOUNDFLIP\n  allowminit     &= !ISMASKSET(lp->piv_strategy, PRICE_NOBOUNDFLIP);\n#endif\n#ifdef Paranoia\n  if(enteringUB < 0)\n    report(lp, SEVERE, \"performiteration: Negative range for entering variable %d at iter %.0f\\n\",\n                        varin, (double) get_total_iter(lp));\n  if(leavingUB < 0)\n    report(lp, SEVERE, \"performiteration: Negative range for leaving variable %d at iter %.0f\\n\",\n                        varout, (double) get_total_iter(lp));\n#endif\n\n  /* Handle batch bound swaps with the dual long-step algorithm;\n     Loop over specified bound swaps; update RHS and Theta for bound swaps */\n  if((boundswaps != NULL) && (boundswaps[0] > 0)) {\n\n    int   i, boundvar;\n    REAL  *hold;\n\n    /* Allocate and initialize accumulation array */\n    allocREAL(lp, &hold, lp->rows + 1, TRUE);\n\n    /* Accumulate effective bound swaps and update flag */\n    for(i = 1; i <= boundswaps[0]; i++) {\n      boundvar = boundswaps[i];\n      deltatheta = my_chsign(!lp->is_lower[boundvar], lp->upbo[boundvar]);\n      mat_multadd(lp->matA, hold, boundvar, deltatheta);\n      lp->is_lower[boundvar] = !lp->is_lower[boundvar];\n    }\n    lp->current_bswap += boundswaps[0];\n    lp->current_iter  += boundswaps[0];\n\n    /* Solve for bound flip update vector (note that this does not\n       overwrite the stored update vector for the entering variable) */\n    ftran(lp, hold, NULL, lp->epsmachine);\n    if(!lp->obj_in_basis)\n      hold[0] = 0; /* The correct reduced cost goes here (adjusted for bound state) ****** */\n\n    /* Update the RHS / basic variable values and set revised thetas */\n    pivot = lp->bfp_pivotRHS(lp, 1, hold);\n    deltatheta = multi_enteringtheta(lp->longsteps);\n    theta = deltatheta;\n\n    FREE(hold);\n  }\n\n  /* Otherwise to traditional check for single bound swap */\n  else if(allowminit &&\n           !enteringIsFixed) {\n\n/*    pivot = epsmargin; */\n    pivot = lp->epsdual;\n/* #define v51mode */ /* Enable this for v5.1 operation mode */\n#ifdef v51mode\n    if(((lp->simplex_mode & SIMPLEX_Phase1_DUAL) == 0) ||\n       !is_constr_type(lp, rownr, EQ))                      /* *** DEBUG CODE KE */\n#endif\n    if(enteringUB - theta < -pivot) {\n\n#ifndef v51mode\n      if(fabs(enteringUB - theta) < pivot)\n        minitStatus = ITERATE_MINORMAJOR;\n      else\n#endif\n        minitStatus = ITERATE_MINORRETRY;\n      minitNow    = (MYBOOL) (minitStatus != ITERATE_MAJORMAJOR);\n    }\n  }\n\n  /* Process for traditional style single minor iteration */\n  if(minitNow) {\n\n   /* Set the new values (note that theta is set to always be positive) */\n    theta = MIN(fabs(theta), enteringUB);\n\n    /* Update the RHS / variable values and do bound-swap */\n    pivot = lp->bfp_pivotRHS(lp, theta, NULL);\n    *islower = !(*islower);\n\n    lp->current_bswap++;\n\n  }\n\n  /* Process for major iteration */\n  else {\n\n    /* Update the active pricer for the current pivot */\n    updatePricer(lp, rownr, varin, lp->bfp_pivotvector(lp), prow, nzprow);\n\n    /* Update the current basic variable values */\n    pivot = lp->bfp_pivotRHS(lp, theta, NULL);\n\n    /* See if the leaving variable goes directly to its upper bound. */\n    leavingValue = lp->rhs[rownr];\n    leavingToUB = (MYBOOL) (leavingValue > 0.5*leavingUB);\n    lp->is_lower[varout] = leavingIsFixed || !leavingToUB;\n\n    /* Set the value of the entering varible (theta always set to be positive) */\n    if(enteringFromUB) {\n      lp->rhs[rownr] = enteringUB - deltatheta;\n      *islower = TRUE;\n    }\n    else\n      lp->rhs[rownr] = deltatheta;\n    my_roundzero(lp->rhs[rownr], epsmargin);\n\n   /* Update basis indeces */\n    varout = set_basisvar(lp, rownr, varin);\n\n   /* Finalize the update in preparation for next major iteration */\n    lp->bfp_finishupdate(lp, enteringFromUB);\n\n  }\n\n  /* Show pivot tracking information, if specified */\n  if((lp->verbose > NORMAL) && (MIP_count(lp) == 0) &&\n     ((lp->current_iter % MAX(2, lp->rows / 10)) == 0))\n    report(lp, NORMAL, \"Objective value \" RESULTVALUEMASK \" at iter %10.0f.\\n\",\n                       lp->rhs[0], (double) get_total_iter(lp));\n\n#if 0\n  if(verify_solution(lp, FALSE, my_if(minitNow, \"MINOR\", \"MAJOR\")) >= 0) {\n    if(minitNow)\n      pivot = get_obj_active(lp, varin);\n    else\n      pivot = get_obj_active(lp, varout);\n  }\n#endif\n#if 0\n  if((lp->longsteps != NULL) && (boundswaps[0] > 0) && lp->longsteps->objcheck &&\n    ((pivot = fabs(my_reldiff(lp->rhs[0], lp->longsteps->obj_last))) > lp->epssolution)) {\n    report(lp, IMPORTANT, \"performiteration: Objective value gap %8.6f found at iter %6.0f (%d bound flips, %d)\\n\",\n                          pivot, (double) get_total_iter(lp), boundswaps[0], enteringFromUB);\n  }\n#endif\n\n  if(lp->spx_trace) {\n    if(minitNow)\n      report(lp, NORMAL, \"I:%5.0f - minor - %5d ignored,          %5d flips  from %s with THETA=%g and OBJ=%g\\n\",\n                         (double) get_total_iter(lp), varout, varin, (enteringFromUB ? \"UPPER\" : \"LOWER\"), theta, lp->rhs[0]);\n    else\n      report(lp, NORMAL, \"I:%5.0f - MAJOR - %5d leaves to %s,  %5d enters from %s with THETA=%g and OBJ=%g\\n\",\n                         (double) get_total_iter(lp), varout, (leavingToUB    ? \"UPPER\" : \"LOWER\"),\n                                           varin,  (enteringFromUB ? \"UPPER\" : \"LOWER\"), theta, lp->rhs[0]);\n    if(minitNow) {\n      if(!lp->is_lower[varin])\n        report(lp, DETAILED,\n        \"performiteration: Variable %d changed to its lower bound at iter %.0f (from %g)\\n\",\n        varin, (double) get_total_iter(lp), enteringUB);\n      else\n        report(lp, DETAILED,\n        \"performiteration: Variable %d changed to its upper bound at iter %.0f (to %g)\\n\",\n        varin, (double) get_total_iter(lp), enteringUB);\n    }\n    else\n      report(lp, NORMAL,\n          \"performiteration: Variable %d entered basis at iter %.0f at \" RESULTVALUEMASK \"\\n\",\n          varin, (double) get_total_iter(lp), lp->rhs[rownr]);\n    if(!primal) {\n      pivot = compute_feasibilitygap(lp, (MYBOOL)!primal, TRUE);\n      report(lp, NORMAL, \"performiteration: Feasibility gap at iter %.0f is \" RESULTVALUEMASK \"\\n\",\n                         (double) get_total_iter(lp), pivot);\n    }\n    else\n      report(lp, NORMAL,\n          \"performiteration: Current objective function value at iter %.0f is \" RESULTVALUEMASK \"\\n\",\n          (double) get_total_iter(lp), lp->rhs[0]);\n  }\n\n  return( minitStatus );\n\n} /* performiteration */\n\nSTATIC REAL get_refactfrequency(lprec *lp, MYBOOL final)\n{\n  COUNTER iters;\n  int     refacts;\n\n  /* Get numerator and divisor information */\n  iters   = (lp->total_iter+lp->current_iter) - (lp->total_bswap+lp->current_bswap);\n  refacts = lp->bfp_refactcount(lp, BFP_STAT_REFACT_TOTAL);\n\n  /* Return frequency for different cases:\n      1) Actual frequency in case final statistic is desired\n      2) Dummy if we are in a B&B process\n      3) Frequency with added initialization offsets which\n         are diluted in course of the solution process */\n  if(final)\n    return( (REAL) (iters) / MAX(1,refacts) );\n  else if(lp->bb_totalnodes > 0)\n    return( (REAL) lp->bfp_pivotmax(lp) );\n  else\n    return( (REAL) (lp->bfp_pivotmax(lp)+iters) / (1+refacts) );\n}\n\n#if 0\n/* INLINE */ MYBOOL is_fixedvar(lprec *lp, int variable)\n{\n  if((lp->bb_bounds != NULL && lp->bb_bounds->UBzerobased) || (variable <= lp->rows))\n    return( (MYBOOL) (lp->upbo[variable] < lp->epsprimal) );\n  else\n    return( (MYBOOL) (lp->upbo[variable]-lp->lowbo[variable] < lp->epsprimal) );\n} /* is_fixedvar */\n#else\nMYBOOL is_fixedvar(lprec *lp, int varnr)\n{\n  if(lp->bb_bounds == NULL) {\n    if(varnr <= lp->rows)\n      return( (MYBOOL) (lp->orig_upbo[varnr] < lp->epsmachine) );\n    else\n      return( (MYBOOL) (lp->orig_upbo[varnr]-lp->orig_lowbo[varnr] < lp->epsmachine) );\n  }\n  else if((varnr <= lp->rows) || (lp->bb_bounds->UBzerobased == TRUE))\n    return( (MYBOOL) (lp->upbo[varnr] < lp->epsvalue) );\n  else\n    return( (MYBOOL) (lp->upbo[varnr]-lp->lowbo[varnr] < lp->epsvalue) );\n}\n#endif\n\nSTATIC MYBOOL solution_is_int(lprec *lp, int index, MYBOOL checkfixed)\n{\n#if 1\n  return( (MYBOOL) (isINT(lp, lp->solution[index]) && (!checkfixed || is_fixedvar(lp, index))) );\n#else\n  if(isINT(lp, lp->solution[index])) {\n    if(checkfixed)\n      return(is_fixedvar(lp, index));\n    else\n      return(TRUE);\n  }\n  return(FALSE);\n#endif\n} /* solution_is_int */\n\n\nMYBOOL __WINAPI set_multiprice(lprec *lp, int multiblockdiv)\n{\n  /* See if we are resetting multiply priced column structures */\n  if(multiblockdiv != lp->multiblockdiv) {\n    if(multiblockdiv < 1)\n      multiblockdiv = 1;\n    lp->multiblockdiv = multiblockdiv;\n    multi_free(&(lp->multivars));\n  }\n  return( TRUE );\n}\n\nint __WINAPI get_multiprice(lprec *lp, MYBOOL getabssize)\n{\n  if((lp->multivars == NULL) || (lp->multivars->used == 0))\n    return( 0 );\n  if(getabssize)\n    return( lp->multivars->size );\n  else\n    return( lp->multiblockdiv );\n}\n\nMYBOOL __WINAPI set_partialprice(lprec *lp, int blockcount, int *blockstart, MYBOOL isrow)\n{\n  int        ne, i, items;\n  partialrec **blockdata;\n\n  /* Determine partial target (rows or columns) */\n  if(isrow)\n    blockdata = &(lp->rowblocks);\n  else\n    blockdata = &(lp->colblocks);\n\n  /* See if we are resetting partial blocks */\n  ne = 0;\n  items = IF(isrow, lp->rows, lp->columns);\n  if(blockcount == 1)\n    partial_freeBlocks(blockdata);\n\n  /* Set a default block count if this was not specified */\n  else if(blockcount <= 0) {\n    blockstart = NULL;\n    if(items < DEF_PARTIALBLOCKS*DEF_PARTIALBLOCKS)\n      blockcount = items / DEF_PARTIALBLOCKS + 1;\n    else\n      blockcount = DEF_PARTIALBLOCKS;\n    ne = items / blockcount;\n    if(ne * blockcount < items)\n      ne++;\n  }\n\n  /* Fill partial block arrays;\n     Note: These will be modified during preprocess to reflect\n           presolved columns and the handling of slack variables. */\n  if(blockcount > 1) {\n    MYBOOL     isNew = (MYBOOL) (*blockdata == NULL);\n\n    /* Provide for extra block with slack variables in the column mode */\n    i = 0;\n    if(!isrow)\n      i++;\n\n    /* (Re)-allocate memory */\n    if(isNew)\n      *blockdata = partial_createBlocks(lp, isrow);\n    allocINT(lp, &((*blockdata)->blockend), blockcount+i+1, AUTOMATIC);\n    allocINT(lp, &((*blockdata)->blockpos), blockcount+i+1, AUTOMATIC);\n\n    /* Copy the user-provided block start positions */\n    if(blockstart != NULL) {\n      MEMCOPY((*blockdata)->blockend+i, blockstart, blockcount+i+1);\n      if(!isrow) {\n        blockcount++;\n        (*blockdata)->blockend[0] = 1;\n        for(i = 1; i < blockcount; i++)\n          (*blockdata)->blockend[i] += lp->rows;\n      }\n    }\n\n    /* Fill the block ending positions if they were not specified */\n    else {\n      (*blockdata)->blockend[0] = 1;\n      (*blockdata)->blockpos[0] = 1;\n      if(ne == 0) {\n        ne = items / blockcount;\n        /* Increase the block size if we have a fractional value */\n        while(ne * blockcount < items)\n          ne++;\n      }\n      i = 1;\n      if(!isrow) {\n        (*blockdata)->blockend[i] = (*blockdata)->blockend[i-1]+lp->rows;\n        blockcount++;\n        i++;\n        items += lp->rows;\n      }\n      for(; i < blockcount; i++)\n        (*blockdata)->blockend[i] = (*blockdata)->blockend[i-1]+ne;\n\n      /* Let the last block handle the \"residual\" */\n      (*blockdata)->blockend[blockcount] = items+1;\n    }\n\n    /* Fill starting positions (used in multiple partial pricing) */\n    for(i = 1; i <= blockcount; i++)\n      (*blockdata)->blockpos[i] = (*blockdata)->blockend[i-1];\n\n  }\n\n  /* Update block count */\n  (*blockdata)->blockcount = blockcount;\n\n\n  return( TRUE );\n} /* set_partialprice */\n\nvoid __WINAPI get_partialprice(lprec *lp, int *blockcount, int *blockstart, MYBOOL isrow)\n{\n  partialrec *blockdata;\n\n  /* Determine partial target (rows or columns) */\n  if(isrow)\n    blockdata = lp->rowblocks;\n  else\n    blockdata = lp->colblocks;\n\n  *blockcount = partial_countBlocks(lp, isrow);\n  if((blockdata != NULL) && (blockstart != NULL)) {\n    int i = 0, k = *blockcount;\n    if(!isrow)\n      i++;\n    MEMCOPY(blockstart, blockdata->blockend + i, k - i);\n    if(!isrow) {\n      k -= i;\n      for(i = 0; i < k; i++)\n        blockstart[i] -= lp->rows;\n    }\n  }\n}\n\n\n/* Solution-related functions */\nSTATIC MYBOOL bb_better(lprec *lp, int target, int mode)\n/* Must handle four modes (logic assumes Min!):\n      -----|--.--|----->\n   1  ++++++-----------  LHS exclusive test point is better\n   2  +++++++++--------  LHS inclusive\n   3  ++++++-----++++++  LHS+RHS exclusive\n   4  --------+++++++++  RHS inclusive\n   5  -----------++++++  RHS exclusive\n*/\n{\n  REAL   epsvalue, offset = lp->epsprimal,\n         refvalue = lp->infinite, testvalue = lp->solution[0];\n  MYBOOL ismax = is_maxim(lp),\n         relgap = is_action(mode, OF_TEST_RELGAP),\n         fcast  = is_action(target, OF_PROJECTED),\n         delta  = is_action(target, OF_DELTA);\n\n  if(relgap) {\n    epsvalue = lp->mip_relgap;\n    clear_action(&mode, OF_TEST_RELGAP);\n  }\n  else\n    epsvalue = lp->mip_absgap;\n\n  if(delta)\n    clear_action(&target, OF_DELTA);\n  if(fcast)\n    clear_action(&target, OF_PROJECTED);\n#ifdef Paranoia\n  if((mode < OF_TEST_BT) || (mode > OF_TEST_WT))\n    report(lp, SEVERE, \"bb_better: Passed invalid mode '%d'\\n\", mode);\n#endif\n\n  switch(target) {\n    case OF_RELAXED:   refvalue = lp->real_solution;\n                       break;\n    case OF_INCUMBENT: refvalue = lp->best_solution[0];\n                       break;\n    case OF_WORKING:  refvalue = my_chsign(!ismax, lp->bb_workOF /* unscaled_value(lp, lp->bb_workOF, 0) */ );\n                       if(fcast)\n                         testvalue = my_chsign(!ismax, lp->longsteps->obj_last) - epsvalue;\n                       else\n                         testvalue = my_chsign(!ismax, lp->rhs[0] /* unscaled_value(lp, lp->rhs[0], 0) */);\n                       break;\n    case OF_USERBREAK: refvalue = lp->bb_breakOF;\n                       break;\n    case OF_HEURISTIC: refvalue = lp->bb_heuristicOF;\n                       break;\n    case OF_DUALLIMIT: refvalue = lp->bb_limitOF;\n                       break;\n    default         :  report(lp, SEVERE, \"bb_better: Passed invalid test target '%d'\\n\", target);\n                       return( FALSE );\n  }\n\n  /* Adjust the test value for the desired acceptability window */\n  if(delta) {\n    SETMAX(epsvalue, lp->bb_deltaOF - epsvalue);\n  }\n  else\n    epsvalue = my_chsign(target >= OF_USERBREAK, epsvalue); /* *** This seems Ok, but should be verified */\n  testvalue += my_chsign(ismax, epsvalue);\n\n  /* Compute the raw test value */\n  if(relgap)\n    testvalue = my_reldiff(testvalue, refvalue);\n  else\n    testvalue -= refvalue;\n\n  /* Make test value adjustment based on the selected option */\n  if(mode == OF_TEST_NE)\n    relgap = (MYBOOL) (fabs(testvalue) >= offset);\n  else {\n    testvalue = my_chsign(mode > OF_TEST_NE, testvalue);\n    testvalue = my_chsign(ismax, testvalue);\n    relgap = (MYBOOL) (testvalue < offset);\n  }\n  return( relgap );\n}\n\nSTATIC void construct_solution(lprec *lp, REAL *target)\n{\n  int     i, j, basi;\n  REAL    f, epsvalue = lp->epsprimal;\n  REAL    *solution;\n  REAL    *value;\n  int     *rownr;\n  MATrec  *mat = lp->matA;\n\n  if(target == NULL)\n    solution = lp->solution;\n  else\n    solution = target;\n\n  /* Initialize OF and slack variables. */\n  for(i = 0; i <= lp->rows; i++) {\n#ifdef LegacySlackDefinition\n    if(i == 0)\n      f = unscaled_value(lp, -lp->orig_rhs[i], i);\n    else {\n      j = lp->presolve_undo->var_to_orig[i];\n      if(j > 0) {\n        f = lp->presolve_undo->fixed_rhs[j];\n        f = unscaled_value(lp, f, i);\n      }\n      else\n        f = 0;\n    }\n#else\n    f = lp->orig_rhs[i];\n    if((i > 0) && !lp->is_basic[i] && !lp->is_lower[i])\n#ifdef SlackInitMinusInf\n      f -= my_chsign(is_chsign(lp, i), fabs(lp->upbo[i]));\n#else\n      f -= my_chsign(is_chsign(lp, i), fabs(lp->lowbo[i] + lp->upbo[i]));\n#endif\n    f = unscaled_value(lp, -f, i);\n#endif\n    solution[i] = f;\n  }\n\n  /* Initialize user variables to their lower bounds. */\n  for(i = lp->rows+1; i <= lp->sum; i++)\n    solution[i] = lp->lowbo[i];\n\n  /* Add values of user basic variables. */\n  for(i = 1; i <= lp->rows; i++) {\n    basi = lp->var_basic[i];\n    if(basi > lp->rows) {\n      solution[basi] += lp->rhs[i];\n    }\n  }\n\n  /* 1. Adjust non-basic variables at their upper bounds,\n     2. Unscale all user variables,\n     3. Optionally do precision management. */\n  for(i = lp->rows + 1; i <= lp->sum; i++) {\n    if(!lp->is_basic[i] && !lp->is_lower[i])\n      solution[i] += lp->upbo[i];\n    solution[i] = unscaled_value(lp, solution[i], i);\n#ifdef xImproveSolutionPrecision\n    if(is_int(lp, i-lp->rows))\n      solution[i] = restoreINT(solution[i], lp->epsint);\n    else\n      solution[i] = restoreINT(solution[i], lp->epsprimal);\n#endif\n  }\n\n  /* Compute the OF and slack values \"in extentio\" */\n  for(j = 1; j <= lp->columns; j++) {\n    f = solution[lp->rows + j];\n    if(f != 0) {\n      solution[0] += f * unscaled_mat(lp, lp->orig_obj[j], 0, j);\n      i = mat->col_end[j-1];\n      basi = mat->col_end[j];\n      rownr = &COL_MAT_ROWNR(i);\n      value = &COL_MAT_VALUE(i);\n      for(; i < basi;\n          i++, rownr += matRowColStep, value += matValueStep)\n        solution[*rownr] += f * unscaled_mat(lp, *value, *rownr, j);\n    }\n  }\n\n  /* Do slack precision management and sign reversal if necessary */\n  for(i = 0; i <= lp->rows; i++) {\n#ifdef ImproveSolutionPrecision\n    my_roundzero(solution[i], epsvalue);\n#endif\n    if(is_chsign(lp, i))\n      solution[i] = my_flipsign(solution[i]);\n  }\n\n /* Record the best real-valued solution and compute a simple MIP solution limit */\n  if(target == NULL) {\n    if(is_infinite(lp, lp->real_solution)) {\n      lp->bb_workOF = lp->rhs[0];\n      lp->real_solution = solution[0];\n      if(is_infinite(lp, lp->bb_limitOF))\n        lp->bb_limitOF = lp->real_solution;\n      else {\n        if(is_maxim(lp)) {\n          SETMIN(lp->bb_limitOF, lp->real_solution);\n        }\n        else {\n          SETMAX(lp->bb_limitOF, lp->real_solution);\n        }\n      }\n\n      /* Do MIP-related tests and computations */\n      if((lp->int_vars > 0) && mat_validate(lp->matA) /* && !lp->wasPresolved */) { /* && !lp->wasPresolved uncommented by findings of William H. Patton. The code was never executed when the test was there. The code has effect in an integer model with all integer objective coeff. to cut-off optimization and thus make it faster */\n        REAL fixedOF = unscaled_value(lp, lp->orig_rhs[0], 0);\n\n        /* Check if we have an all-integer OF */\n        basi = lp->columns;\n        for(j = 1; j <= basi; j++) {\n          f = fabs(get_mat(lp, 0, j)) + lp->epsint / 2;\n          if(f > lp->epsint) { /* If coefficient is 0 then it doesn't influence OF, even it variable is not integer */\n            if(!is_int(lp, j) || (fmod(f, 1) > lp->epsint))\n              break;\n          }\n        }\n\n        /* If so, we can round up the fractional OF */\n        if(j > basi) {\n          f = my_chsign(is_maxim(lp), lp->real_solution) + fixedOF;\n          f = floor(f+(1-epsvalue));\n          f = my_chsign(is_maxim(lp), f - fixedOF);\n          if(is_infinite(lp, lp->bb_limitOF))\n            lp->bb_limitOF = f;\n          else if(is_maxim(lp)) {\n            SETMIN(lp->bb_limitOF, f);\n          }\n          else {\n            SETMAX(lp->bb_limitOF, f);\n          }\n        }\n      }\n\n      /* Check that a user limit on the OF is feasible */\n      if((lp->int_vars > 0) &&\n         (my_chsign(is_maxim(lp), my_reldiff(lp->best_solution[0],lp->bb_limitOF)) < -epsvalue)) {\n        lp->spx_status = INFEASIBLE;\n        lp->bb_break = TRUE;\n      }\n    }\n  }\n\n} /* construct_solution */\n\nSTATIC int check_solution(lprec *lp, int  lastcolumn, REAL *solution,\n                          REAL *upbo, REAL *lowbo, REAL tolerance)\n{\n/*#define UseMaxValueInCheck*/\n  MYBOOL isSC;\n  REAL   test, value, hold, diff, maxdiff = 0.0, maxerr = 0.0, *matValue,\n#ifdef UseMaxValueInCheck\n         *maxvalue = NULL,\n#else\n         *plusum = NULL, *negsum = NULL;\n#endif\n  int    i,j,n, errlevel = IMPORTANT, errlimit = 10, *matRownr, *matColnr;\n  MATrec *mat = lp->matA;\n\n  report(lp, NORMAL, \" \\n\");\n  if(MIP_count(lp) > 0)\n    report(lp, NORMAL, \"%s solution  \" RESULTVALUEMASK \" after %10.0f iter, %9.0f nodes (gap %.1f%%).\\n\",\n                       my_if(lp->bb_break && !bb_better(lp, OF_DUALLIMIT, OF_TEST_BE) && bb_better(lp, OF_RELAXED, OF_TEST_NE), \"Subopt.\", \"Optimal\"),\n                       solution[0], (double) lp->total_iter, (double) lp->bb_totalnodes,\n                       100.0*fabs(my_reldiff(solution[0], lp->bb_limitOF)));\n  else\n    report(lp, NORMAL, \"Optimal solution  \" RESULTVALUEMASK \" after %10.0f iter.\\n\",\n                       solution[0], (double) lp->total_iter);\n\n /* Find the signed sums and the largest absolute product in the matrix (exclude the OF for speed) */\n#ifdef UseMaxValueInCheck\n  allocREAL(lp, &maxvalue, lp->rows + 1, FALSE);\n  for(i = 0; i <= lp->rows; i++)\n    maxvalue[i] = fabs(get_rh(lp, i));\n#else\n  allocREAL(lp, &plusum, lp->rows + 1, TRUE);\n  allocREAL(lp, &negsum, lp->rows + 1, TRUE);\n#endif\n  n = get_nonzeros(lp);\n  matRownr = &COL_MAT_ROWNR(0);\n  matColnr = &COL_MAT_COLNR(0);\n  matValue = &COL_MAT_VALUE(0);\n  for(i = 0; i < n; i++, matRownr += matRowColStep,\n                         matColnr += matRowColStep,\n                         matValue += matValueStep) {\n    test = unscaled_mat(lp, *matValue, *matRownr, *matColnr);\n    test *= solution[lp->rows + (*matColnr)];\n#ifdef UseMaxValueInCheck\n    test = fabs(test);\n    if(test > maxvalue[*matRownr])\n      maxvalue[*matRownr] = test;\n#else\n    if(test > 0)\n      plusum[*matRownr] += test;\n    else\n      negsum[*matRownr] += test;\n#endif\n  }\n\n\n /* Check if solution values are within the bounds; allowing a margin for numeric errors */\n  n = 0;\n  for(i = lp->rows + 1; i <= lp->rows+lastcolumn; i++) {\n\n    value = solution[i];\n\n    /* Check for case where we are testing an intermediate solution\n       (variables shifted to the origin) */\n    if(lowbo == NULL)\n      test = 0;\n    else\n      test = unscaled_value(lp, lowbo[i], i);\n\n    isSC = is_semicont(lp, i - lp->rows);\n    diff = my_reldiff(value, test);\n    if(diff < 0) {\n      if(isSC && (value < test/2))\n        test = 0;\n      SETMAX(maxerr, fabs(value-test));\n      SETMAX(maxdiff, fabs(diff));\n    }\n    if((diff < -tolerance) && !isSC)  {\n      if(n < errlimit)\n      report(lp, errlevel,\n        \"check_solution: Variable   %s = \" RESULTVALUEMASK \" is below its lower bound \" RESULTVALUEMASK \"\\n\",\n         get_col_name(lp, i-lp->rows), value, test);\n      n++;\n    }\n\n    test = unscaled_value(lp, upbo[i], i);\n    diff = my_reldiff(value, test);\n    if(diff > 0) {\n      SETMAX(maxerr, fabs(value-test));\n      SETMAX(maxdiff, fabs(diff));\n    }\n    if(diff > tolerance) {\n      if(n < errlimit)\n      report(lp, errlevel,\n         \"check_solution: Variable   %s = \" RESULTVALUEMASK \" is above its upper bound \" RESULTVALUEMASK \"\\n\",\n         get_col_name(lp, i-lp->rows), value, test);\n      n++;\n    }\n  }\n\n /* Check if constraint values are within the bounds; allowing a margin for numeric errors */\n  for(i = 1; i <= lp->rows; i++) {\n\n    test = lp->orig_rhs[i];\n    if(is_infinite(lp, test))\n      continue;\n\n#ifdef LegacySlackDefinition\n    j = lp->presolve_undo->var_to_orig[i];\n    if(j != 0) {\n      if(is_infinite(lp, lp->presolve_undo->fixed_rhs[j]))\n        continue;\n      test += lp->presolve_undo->fixed_rhs[j];\n    }\n#endif\n\n    if(is_chsign(lp, i)) {\n      test = my_flipsign(test);\n      test += fabs(upbo[i]);\n    }\n    value = solution[i];\n    test = unscaled_value(lp, test, i);\n#ifndef LegacySlackDefinition\n    value += test;\n#endif\n/*    diff = my_reldiff(value, test); */\n#ifdef UseMaxValueInCheck\n    hold = maxvalue[i];\n#else\n    hold = plusum[i] - negsum[i];\n#endif\n    if(hold < lp->epsvalue)\n      hold = 1;\n    diff = my_reldiff((value+1)/hold, (test+1)/hold);\n    if(diff > 0) {\n      SETMAX(maxerr, fabs(value-test));\n      SETMAX(maxdiff, fabs(diff));\n    }\n    if(diff > tolerance) {\n      if(n < errlimit)\n      report(lp, errlevel,\n        \"check_solution: Constraint %s = \" RESULTVALUEMASK \" is above its %s \" RESULTVALUEMASK \"\\n\",\n        get_row_name(lp, i), value,\n        (is_constr_type(lp, i, EQ) ? \"equality of\" : \"upper bound\"), test);\n      n++;\n    }\n\n    test = lp->orig_rhs[i];\n#ifdef LegacySlackDefinition\n    j = lp->presolve_undo->var_to_orig[i];\n    if(j != 0) {\n      if(is_infinite(lp, lp->presolve_undo->fixed_rhs[j]))\n        continue;\n      test += lp->presolve_undo->fixed_rhs[j];\n    }\n#endif\n\n    value = solution[i];\n    if(is_chsign(lp, i))\n      test = my_flipsign(test);\n    else {\n      if(is_infinite(lp, upbo[i]))\n        continue;\n      test -= fabs(upbo[i]);\n#ifndef LegacySlackDefinition\n      value = fabs(upbo[i]) - value;\n#endif\n    }\n    test = unscaled_value(lp, test, i);\n#ifndef LegacySlackDefinition\n    value += test;\n#endif\n/*    diff = my_reldiff(value, test); */\n#ifdef UseMaxValueInCheck\n    hold = maxvalue[i];\n#else\n    hold = plusum[i] - negsum[i];\n#endif\n    if(hold < lp->epsvalue)\n      hold = 1;\n    diff = my_reldiff((value+1)/hold, (test+1)/hold);\n    if(diff < 0) {\n      SETMAX(maxerr, fabs(value-test));\n      SETMAX(maxdiff, fabs(diff));\n    }\n    if(diff < -tolerance) {\n      if(n < errlimit)\n      report(lp, errlevel,\n        \"check_solution: Constraint %s = \" RESULTVALUEMASK \" is below its %s \" RESULTVALUEMASK \"\\n\",\n        get_row_name(lp, i), value,\n        (is_constr_type(lp, i, EQ) ? \"equality of\" : \"lower bound\"), test);\n      n++;\n    }\n  }\n\n#ifdef UseMaxValueInCheck\n  FREE(maxvalue);\n#else\n  FREE(plusum);\n  FREE(negsum);\n#endif\n\n  if(n > 0) {\n    report(lp, IMPORTANT, \"\\nSeriously low accuracy found ||*|| = %g (rel. error %g)\\n\",\n               maxerr, maxdiff);\n    return(NUMFAILURE);\n  }\n  else {\n    if(maxerr > 1.0e-7)\n      report(lp, NORMAL, \"\\nMarginal numeric accuracy ||*|| = %g (rel. error %g)\\n\",\n                 maxerr, maxdiff);\n    else if(maxerr > 1.0e-9)\n      report(lp, NORMAL, \"\\nReasonable numeric accuracy ||*|| = %g (rel. error %g)\\n\",\n                 maxerr, maxdiff);\n    else if(maxerr > 1.0e11)\n      report(lp, NORMAL, \"\\nVery good numeric accuracy ||*|| = %g\\n\", maxerr);\n    else\n      report(lp, NORMAL, \"\\nExcellent numeric accuracy ||*|| = %g\\n\", maxerr);\n\n    return(OPTIMAL);\n  }\n\n} /* check_solution */\n\nSTATIC void transfer_solution_var(lprec *lp, int uservar)\n{\n  if(lp->varmap_locked && (MYBOOL) ((lp->do_presolve & PRESOLVE_LASTMASKMODE) != PRESOLVE_NONE)) {\n    uservar += lp->rows;\n    lp->full_solution[lp->presolve_undo->orig_rows +\n                      lp->presolve_undo->var_to_orig[uservar]] = lp->best_solution[uservar];\n  }\n}\nSTATIC void transfer_solution(lprec *lp, MYBOOL dofinal)\n{\n  int i, ii;\n\n  MEMCOPY(lp->best_solution, lp->solution, lp->sum + 1);\n\n  /* Round integer solution values to actual integers */\n  if(is_integerscaling(lp) && (lp->int_vars > 0))\n    for(i = 1; i <= lp->columns; i++) {\n      if(is_int(lp, i)) {\n        ii = lp->rows + i;\n        lp->best_solution[ii] = floor(lp->best_solution[ii] + 0.5);\n      }\n    }\n\n  /* Transfer to full solution vector in the case of presolved eliminations */\n  if(dofinal && lp->varmap_locked &&\n     (MYBOOL) ((lp->do_presolve & PRESOLVE_LASTMASKMODE) != PRESOLVE_NONE)) {\n    presolveundorec *psundo = lp->presolve_undo;\n\n    lp->full_solution[0] = lp->best_solution[0];\n    for(i = 1; i <= lp->rows; i++) {\n      ii = psundo->var_to_orig[i];\n#ifdef Paranoia\n      if((ii < 0) || (ii > lp->presolve_undo->orig_rows))\n        report(lp, SEVERE, \"transfer_solution: Invalid mapping of row index %d to original index '%d'\\n\",\n                            i, ii);\n#endif\n      lp->full_solution[ii] = lp->best_solution[i];\n    }\n    for(i = 1; i <= lp->columns; i++) {\n      ii = psundo->var_to_orig[lp->rows+i];\n#ifdef Paranoia\n      if((ii < 0) || (ii > lp->presolve_undo->orig_columns))\n        report(lp, SEVERE, \"transfer_solution: Invalid mapping of column index %d to original index '%d'\\n\",\n                            i, ii);\n#endif\n      lp->full_solution[psundo->orig_rows+ii] = lp->best_solution[lp->rows+i];\n    }\n  }\n\n}\n\nSTATIC MYBOOL construct_duals(lprec *lp)\n{\n  int  i, n, *coltarget;\n  REAL scale0, value, dualOF;\n\n  if(lp->duals != NULL)\n    free_duals(lp);\n\n  if(is_action(lp->spx_action, ACTION_REBASE) ||\n     is_action(lp->spx_action, ACTION_REINVERT) || (!lp->basis_valid) ||\n     !allocREAL(lp, &(lp->duals), lp->sum + 1, AUTOMATIC))\n    return(FALSE);\n\n  /* Initialize */\n  coltarget = (int *) mempool_obtainVector(lp->workarrays, lp->columns+1, sizeof(*coltarget));\n  if(!get_colIndexA(lp, SCAN_USERVARS+USE_NONBASICVARS, coltarget, FALSE)) {\n    mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n    return(FALSE);\n  }\n  bsolve(lp, 0, lp->duals, NULL, lp->epsmachine*DOUBLEROUND, 1.0);\n  prod_xA(lp, coltarget, lp->duals, NULL, lp->epsmachine, 1.0,\n                         lp->duals, NULL, MAT_ROUNDDEFAULT | MAT_ROUNDRC);\n  mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n\n\n  /* The (Lagrangean) dual values are the reduced costs of the primal slacks;\n     when the slack is at its upper bound, change the sign. */\n  n = lp->rows;\n  for(i = 1; i <= n; i++) {\n    if(lp->is_basic[i])\n      lp->duals[i] = 0;\n    /* Added a test if variable is different from 0 because sometime you get -0 and this\n       is different from 0 on for example INTEL processors (ie 0 != -0 on INTEL !) PN */\n    else if((is_chsign(lp, 0) == is_chsign(lp, i)) && lp->duals[i])\n      lp->duals[i] = my_flipsign(lp->duals[i]);\n  }\n  if(is_maxim(lp)) {\n    n = lp->sum;\n    for(i = lp->rows + 1; i <= n; i++)\n      lp->duals[i] = my_flipsign(lp->duals[i]);\n  }\n\n  /* If we presolved, then reconstruct the duals */\n  n = lp->presolve_undo->orig_sum;\n  if(((lp->do_presolve & PRESOLVE_LASTMASKMODE) != PRESOLVE_NONE) &&\n      allocREAL(lp, &(lp->full_duals), n + 1, TRUE)) {\n    int ix, ii = lp->presolve_undo->orig_rows;\n\n    n = lp->sum;\n    for(ix = 1; ix <= n; ix++) {\n      i = lp->presolve_undo->var_to_orig[ix];\n      if(ix > lp->rows)\n        i += ii;\n#ifdef Paranoia\n      /* Check for index out of range due to presolve */\n      if(i > lp->presolve_undo->orig_sum)\n        report(lp, SEVERE, \"construct_duals: Invalid presolve variable mapping found\\n\");\n#endif\n      lp->full_duals[i] = lp->duals[ix];\n    }\n    presolve_rebuildUndo(lp, FALSE);\n  }\n\n  /* Calculate the dual OF and do scaling adjustments to the duals */\n  if(lp->scaling_used)\n    scale0 = lp->scalars[0];\n  else\n    scale0 = 1;\n  dualOF = my_chsign(is_maxim(lp), lp->orig_rhs[0]) / scale0;\n  for(i = 1; i <= lp->sum; i++) {\n    value = scaled_value(lp, lp->duals[i] / scale0, i);\n    my_roundzero(value, lp->epsprimal);\n    lp->duals[i] = value;\n    if(i <= lp->rows)\n      dualOF += value * lp->solution[i];\n  }\n\n#if 0\n  /* See if we can make use of the dual OF;\n     note that we do not currently adjust properly for presolve */\n  if(lp->rows == lp->presolve_undo->orig_rows)\n  if(MIP_count(lp) > 0) {\n    if(is_maxim(lp)) {\n      SETMIN(lp->bb_limitOF, dualOF);\n    }\n    else {\n      SETMAX(lp->bb_limitOF, dualOF);\n    }\n  }\n  else if(fabs(my_reldiff(dualOF, lp->solution[0])) > lp->epssolution)\n    report(lp, IMPORTANT, \"calculate_duals: Check for possible suboptimal solution!\\n\");\n#endif\n\n  return(TRUE);\n} /* construct_duals */\n\n/* Calculate sensitivity duals */\nSTATIC MYBOOL construct_sensitivity_duals(lprec *lp)\n{\n  int  k,varnr, ok = TRUE;\n  int  *workINT = NULL;\n  REAL *pcol,a,infinite,epsvalue,from,till,objfromvalue;\n\n  /* one column of the matrix */\n  FREE(lp->objfromvalue);\n  FREE(lp->dualsfrom);\n  FREE(lp->dualstill);\n  if(!allocREAL(lp, &pcol, lp->rows + 1, TRUE) ||\n     !allocREAL(lp, &lp->objfromvalue, lp->columns + 1, AUTOMATIC) ||\n     !allocREAL(lp, &lp->dualsfrom, lp->sum + 1, AUTOMATIC) ||\n     !allocREAL(lp, &lp->dualstill, lp->sum + 1, AUTOMATIC)) {\n    FREE(pcol);\n    FREE(lp->objfromvalue);\n    FREE(lp->dualsfrom);\n    FREE(lp->dualstill);\n    ok = FALSE;\n  }\n  else {\n    infinite=lp->infinite;\n    epsvalue=lp->epsmachine;\n    for(varnr=1; varnr<=lp->sum; varnr++) {\n      from=infinite;\n      till=infinite;\n      objfromvalue=infinite;\n      if (!lp->is_basic[varnr]) {\n        if (!fsolve(lp, varnr, pcol, workINT, epsvalue, 1.0, FALSE)) {  /* construct one column of the tableau */\n          ok = FALSE;\n          break;\n        }\n        /* Search for the rows(s) which first result in further iterations */\n        for (k=1; k<=lp->rows; k++) {\n          if (fabs(pcol[k])>epsvalue) {\n            a = lp->rhs[k]/pcol[k];\n            if((varnr > lp->rows) && (fabs(lp->solution[varnr]) <= epsvalue) && (a < objfromvalue) && (a >= lp->lowbo[varnr]))\n              objfromvalue = a;\n            if ((a<=0.0) && (pcol[k]<0.0) && (-a<from)) from=my_flipsign(a);\n            if ((a>=0.0) && (pcol[k]>0.0) && ( a<till)) till= a;\n            if (lp->upbo[lp->var_basic[k]] < infinite) {\n              a = (REAL) ((lp->rhs[k]-lp->upbo[lp->var_basic[k]])/pcol[k]);\n              if((varnr > lp->rows) && (fabs(lp->solution[varnr]) <= epsvalue) && (a < objfromvalue) && (a >= lp->lowbo[varnr]))\n                objfromvalue = a;\n              if ((a<=0.0) && (pcol[k]>0.0) && (-a<from)) from=my_flipsign(a);\n              if ((a>=0.0) && (pcol[k]<0.0) && ( a<till)) till= a;\n            }\n          }\n        }\n\n        if (!lp->is_lower[varnr]) {\n          a=from;\n          from=till;\n          till=a;\n        }\n        if ((varnr<=lp->rows) && (!is_chsign(lp, varnr))) {\n          a=from;\n          from=till;\n          till=a;\n        }\n      }\n\n      if (from!=infinite)\n        lp->dualsfrom[varnr]=lp->solution[varnr]-unscaled_value(lp, from, varnr);\n      else\n        lp->dualsfrom[varnr]=-infinite;\n      if (till!=infinite)\n        lp->dualstill[varnr]=lp->solution[varnr]+unscaled_value(lp, till, varnr);\n      else\n        lp->dualstill[varnr]=infinite;\n\n      if (varnr > lp->rows) {\n        if (objfromvalue != infinite) {\n          if ((!sensrejvar) || (lp->upbo[varnr] != 0.0)) {\n            if (!lp->is_lower[varnr])\n              objfromvalue = lp->upbo[varnr] - objfromvalue;\n            if ((lp->upbo[varnr] < infinite) && (objfromvalue > lp->upbo[varnr]))\n              objfromvalue = lp->upbo[varnr];\n          }\n          objfromvalue += lp->lowbo[varnr];\n          objfromvalue = unscaled_value(lp, objfromvalue, varnr);\n        }\n        else\n          objfromvalue = -infinite;\n        lp->objfromvalue[varnr - lp->rows] = objfromvalue;\n      }\n\n    }\n    FREE(pcol);\n  }\n  return((MYBOOL) ok);\n} /* construct_sensitivity_duals */\n\n/* Calculate sensitivity objective function */\nSTATIC MYBOOL construct_sensitivity_obj(lprec *lp)\n{\n  int  i, l, varnr, row_nr, ok = TRUE;\n  REAL *OrigObj = NULL, *drow = NULL, *prow = NULL,\n       sign, a, min1, min2, infinite, epsvalue, from, till;\n\n  /* objective function */\n  FREE(lp->objfrom);\n  FREE(lp->objtill);\n  if(!allocREAL(lp, &drow, lp->sum + 1, TRUE) ||\n     !allocREAL(lp, &OrigObj, lp->columns + 1, FALSE) ||\n     !allocREAL(lp, &prow, lp->sum + 1, TRUE) ||\n     !allocREAL(lp, &lp->objfrom, lp->columns + 1, AUTOMATIC) ||\n     !allocREAL(lp, &lp->objtill, lp->columns + 1, AUTOMATIC)) {\nAbandon:\n    FREE(drow);\n    FREE(OrigObj);\n    FREE(prow);\n    FREE(lp->objfrom);\n    FREE(lp->objtill);\n    ok = FALSE;\n  }\n  else {\n    int *coltarget;\n\n    infinite=lp->infinite;\n    epsvalue=lp->epsmachine;\n\n    coltarget = (int *) mempool_obtainVector(lp->workarrays, lp->columns+1, sizeof(*coltarget));\n    if(!get_colIndexA(lp, SCAN_USERVARS+USE_NONBASICVARS, coltarget, FALSE)) {\n      mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n      goto Abandon;\n    }\n    bsolve(lp, 0, drow, NULL, epsvalue*DOUBLEROUND, 1.0);\n    prod_xA(lp, coltarget, drow, NULL, epsvalue, 1.0,\n                           drow, NULL, MAT_ROUNDDEFAULT | MAT_ROUNDRC);\n\n    /* original (unscaled) objective function */\n    get_row(lp, 0, OrigObj);\n    for(i = 1; i <= lp->columns; i++) {\n      from=-infinite;\n      till= infinite;\n      varnr = lp->rows + i;\n      if(!lp->is_basic[varnr]) {\n      /* only the coeff of the objective function of column i changes. */\n        a = unscaled_mat(lp, drow[varnr], 0, i);\n        if(is_maxim(lp))\n          a = -a;\n        if ((!sensrejvar) && (lp->upbo[varnr] == 0.0))\n          /* ignore, because this case doesn't results in further iterations */ ;\n        else if(((lp->is_lower[varnr] != 0) == (is_maxim(lp) == FALSE)) && (a > -epsvalue))\n          from = OrigObj[i] - a; /* less than this value gives further iterations */\n        else\n          till = OrigObj[i] - a; /* bigger than this value gives further iterations */\n      }\n      else {\n      /* all the coeff of the objective function change. Search the minimal change needed for further iterations */\n        for(row_nr=1;\n            (row_nr<=lp->rows) && (lp->var_basic[row_nr]!=varnr); row_nr++)\n          /* Search on which row the variable exists in the basis */ ;\n        if(row_nr<=lp->rows) {       /* safety test; should always be found ... */\n          /* Construct one row of the tableau */\n          bsolve(lp, row_nr, prow, NULL, epsvalue*DOUBLEROUND, 1.0);\n          prod_xA(lp, coltarget, prow, NULL, epsvalue, 1.0,\n                                 prow, NULL, MAT_ROUNDDEFAULT);\n          /* sign = my_chsign(is_chsign(lp, row_nr), -1); */\n          sign = my_chsign(lp->is_lower[row_nr], -1);\n          min1=infinite;\n          min2=infinite;\n          for(l=1; l<=lp->sum; l++)   /* search for the column(s) which first results in further iterations */\n            if ((!lp->is_basic[l]) && (lp->upbo[l]>0.0) &&\n                (fabs(prow[l])>epsvalue) && (drow[l]*(lp->is_lower[l] ? -1 : 1)<epsvalue)) {\n              a = unscaled_mat(lp, fabs(drow[l] / prow[l]), 0, i);\n              if(prow[l]*sign*(lp->is_lower[l] ? 1 : -1) < 0.0) {\n                if(a < min1)\n                  min1 = a;\n              }\n              else {\n                if(a < min2)\n                  min2 = a;\n              }\n            }\n          if ((lp->is_lower[varnr] == 0) == (is_maxim(lp) == FALSE)) {\n            a = min1;\n            min1 = min2;\n            min2 = a;\n          }\n          if (min1<infinite)\n            from = OrigObj[i]-min1;\n          if (min2<infinite)\n            till = OrigObj[i]+min2;\n          a = lp->solution[varnr];\n          if (is_maxim(lp)) {\n            if (a - lp->lowbo[varnr] < epsvalue)\n              from = -infinite; /* if variable is at lower bound then decrementing objective coefficient will not result in extra iterations because it would only extra decrease the value, but since it is at its lower bound ... */\n            else if (((!sensrejvar) || (lp->upbo[varnr] != 0.0)) && (lp->lowbo[varnr] + lp->upbo[varnr] - a < epsvalue))\n              till = infinite;  /* if variable is at upper bound then incrementing objective coefficient will not result in extra iterations because it would only extra increase the value, but since it is at its upper bound ... */\n          }\n          else {\n            if (a - lp->lowbo[varnr] < epsvalue)\n              till = infinite;  /* if variable is at lower bound then incrementing objective coefficient will not result in extra iterations because it would only extra decrease the value, but since it is at its lower bound ... */\n            else if (((!sensrejvar) || (lp->upbo[varnr] != 0.0)) && (lp->lowbo[varnr] + lp->upbo[varnr] - a < epsvalue))\n              from = -infinite; /* if variable is at upper bound then decrementing objective coefficient will not result in extra iterations because it would only extra increase the value, but since it is at its upper bound ... */\n          }\n        }\n      }\n      lp->objfrom[i]=from;\n      lp->objtill[i]=till;\n    }\n    mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n  }\n  FREE(prow);\n  FREE(OrigObj);\n  FREE(drow);\n\n  return((MYBOOL) ok);\n} /* construct_sensitivity_obj */\n\nSTATIC MYBOOL refactRecent(lprec *lp)\n{\n  int pivcount = lp->bfp_pivotcount(lp);\n  if(pivcount == 0)\n    return( AUTOMATIC );\n  else if (pivcount < 2*DEF_MAXPIVOTRETRY)\n    return( TRUE );\n  else\n    return( FALSE );\n}\n\nSTATIC MYBOOL check_if_less(lprec *lp, REAL x, REAL y, int variable)\n{\n  if(y < x-scaled_value(lp, lp->epsint, variable)) {\n    if(lp->bb_trace)\n      report(lp, NORMAL, \"check_if_less: Invalid new bound %g should be < %g for %s\\n\",\n                         x, y, get_col_name(lp, variable));\n    return(FALSE);\n  }\n  else\n    return(TRUE);\n}\n\n/* Various basis utility routines */\n\nSTATIC int findNonBasicSlack(lprec *lp, MYBOOL *is_basic)\n{\n  int i;\n\n  for(i = lp->rows; i > 0; i--)\n    if(!is_basic[i])\n      break;\n  return( i );\n}\n\nSTATIC int findBasisPos(lprec *lp, int notint, int *var_basic)\n{\n  int i;\n\n  if(var_basic == NULL)\n    var_basic = lp->var_basic;\n  for(i = lp->rows; i > 0; i--)\n    if(var_basic[i] == notint)\n      break;\n  return( i );\n}\n\nSTATIC void replaceBasisVar(lprec *lp, int rownr, int var, int *var_basic, MYBOOL *is_basic)\n{\n  int out;\n\n  out = var_basic[rownr];\n  var_basic[rownr] = var;\n  is_basic[out] = FALSE;\n  is_basic[var] = TRUE;\n}\n\nSTATIC void free_duals(lprec *lp)\n{\n  FREE(lp->duals);\n  FREE(lp->full_duals);\n  FREE(lp->dualsfrom);\n  FREE(lp->dualstill);\n  FREE(lp->objfromvalue);\n  FREE(lp->objfrom);\n  FREE(lp->objtill);\n}\n\n/* Transform RHS by adjusting for the bound state of variables;\n   optionally rebase upper bound, and account for this in later calls */\nSTATIC void initialize_solution(lprec *lp, MYBOOL shiftbounds)\n{\n  int     i, k1, k2, *matRownr, colnr;\n  LREAL   theta;\n  REAL    value, *matValue, loB, upB;\n  MATrec  *mat = lp->matA;\n\n  /* Set bounding status indicators */\n  if(lp->bb_bounds != NULL) {\n    if(shiftbounds == INITSOL_SHIFTZERO) {\n      if(lp->bb_bounds->UBzerobased)\n        report(lp, SEVERE, \"initialize_solution: The upper bounds are already zero-based at refactorization %d\\n\",\n                           lp->bfp_refactcount(lp, BFP_STAT_REFACT_TOTAL));\n      lp->bb_bounds->UBzerobased = TRUE;\n    }\n    else if(!lp->bb_bounds->UBzerobased)\n        report(lp, SEVERE, \"initialize_solution: The upper bounds are not zero-based at refactorization %d\\n\",\n                           lp->bfp_refactcount(lp, BFP_STAT_REFACT_TOTAL));\n  }\n\n  /* Initialize the working RHS/basic variable solution vector */\n  i = is_action(lp->anti_degen, ANTIDEGEN_RHSPERTURB) && (lp->monitor != NULL) && lp->monitor->active;\n  if(sizeof(*lp->rhs) == sizeof(*lp->orig_rhs) && !i) {\n    MEMCOPY(lp->rhs, lp->orig_rhs, lp->rows+1);\n  }\n  else if(i) {\n    lp->rhs[0] = lp->orig_rhs[0];\n    for(i = 1; i <= lp->rows; i++) {\n      if(is_constr_type(lp, i, EQ))\n        theta = rand_uniform(lp, lp->epsvalue);\n      else {\n        theta = rand_uniform(lp, lp->epsperturb);\n/*        if(lp->orig_upbo[i] < lp->infinite)\n          lp->orig_upbo[i] += theta; */\n      }\n      lp->rhs[i] = lp->orig_rhs[i] + theta;\n    }\n  }\n  else\n    for(i = 0; i <= lp->rows; i++)\n      lp->rhs[i] = lp->orig_rhs[i];\n\n/* Adjust active RHS for variables at their active upper/lower bounds */\n  for(i = 1; i <= lp->sum; i++) {\n\n    upB = lp->upbo[i];\n    loB = lp->lowbo[i];\n\n    /* Shift to \"ranged\" upper bound, tantamount to defining zero-based variables */\n    if(shiftbounds == INITSOL_SHIFTZERO) {\n      if((loB > -lp->infinite) && (upB < lp->infinite))\n        lp->upbo[i] -= loB;\n      if(lp->upbo[i] < 0)\n        report(lp, SEVERE, \"initialize_solution: Invalid rebounding; variable %d at refact %d, iter %.0f\\n\",\n                           i, lp->bfp_refactcount(lp, BFP_STAT_REFACT_TOTAL), (double) get_total_iter(lp));\n    }\n\n    /* Use \"ranged\" upper bounds */\n    else if(shiftbounds == INITSOL_USEZERO) {\n      if((loB > -lp->infinite) && (upB < lp->infinite))\n        upB += loB;\n    }\n\n    /* Shift upper bound back to original value */\n    else if(shiftbounds == INITSOL_ORIGINAL) {\n      if((loB > -lp->infinite) && (upB < lp->infinite)) {\n        lp->upbo[i] += loB;\n        upB += loB;\n      }\n      continue;\n    }\n    else\n      report(lp, SEVERE, \"initialize_solution: Invalid option value '%d'\\n\",\n                         shiftbounds);\n\n    /* Set the applicable adjustment */\n    if(lp->is_lower[i])\n      theta = loB;\n    else\n      theta = upB;\n\n\n    /* Check if we need to pass through the matrix;\n       remember that basis variables are always lower-bounded */\n    if(theta == 0)\n      continue;\n\n    /* Do user and artificial variables */\n    if(i > lp->rows) {\n\n      /* Get starting and ending indeces in the NZ vector */\n      colnr = i - lp->rows;\n      k1 = mat->col_end[colnr - 1];\n      k2 = mat->col_end[colnr];\n      matRownr = &COL_MAT_ROWNR(k1);\n      matValue = &COL_MAT_VALUE(k1);\n\n      /* Get the objective as row 0, optionally adjusting the objective for phase 1 */\n      value = get_OF_active(lp, i, theta);\n      lp->rhs[0] -= value;\n\n      /* Do the normal case */\n      for(; k1 < k2;\n          k1++, matRownr += matRowColStep, matValue += matValueStep) {\n        lp->rhs[*matRownr] -= theta * (*matValue);\n      }\n    }\n\n    /* Do slack variables (constraint \"bounds\")*/\n    else {\n      lp->rhs[i] -= theta;\n    }\n\n  }\n\n  /* Do final pass to get the maximum value */\n  i = idamax(lp->rows /* +1 */, lp->rhs, 1);\n  lp->rhsmax = fabs(lp->rhs[i]);\n\n  if(shiftbounds == INITSOL_SHIFTZERO)\n    clear_action(&lp->spx_action, ACTION_REBASE);\n\n}\n\n/* This routine recomputes the basic variables using the full inverse */\nSTATIC void recompute_solution(lprec *lp, MYBOOL shiftbounds)\n{\n  /* Compute RHS = b - A(n)*x(n) */\n  initialize_solution(lp, shiftbounds);\n\n  /* Compute x(b) = Inv(B)*RHS (Ref. lp_solve inverse logic and Chvatal p. 121) */\n  lp->bfp_ftran_normal(lp, lp->rhs, NULL);\n  if(!lp->obj_in_basis) {\n    int i, ib, n = lp->rows;\n    for(i = 1; i <= n; i++) {\n      ib = lp->var_basic[i];\n      if(ib > n)\n        lp->rhs[0] -= get_OF_active(lp, ib, lp->rhs[i]);\n    }\n  }\n\n /* Round the values (should not be greater than the factor used in bfp_pivotRHS) */\n  roundVector(lp->rhs, lp->rows, lp->epsvalue);\n\n  clear_action(&lp->spx_action, ACTION_RECOMPUTE);\n}\n\n/* This routine compares an existing basic solution to a recomputed one;\n   Note that the routine must provide for the possibility that the order of the\n   basis variables can be changed by the inversion engine. */\nSTATIC int verify_solution(lprec *lp, MYBOOL reinvert, char *info)\n{\n  int  i, ii, n, *oldmap, *newmap, *refmap = NULL;\n  REAL *oldrhs, err, errmax;\n\n  allocINT(lp, &oldmap, lp->rows+1, FALSE);\n  allocINT(lp, &newmap, lp->rows+1, FALSE);\n  allocREAL(lp, &oldrhs, lp->rows+1, FALSE);\n\n  /* Get sorted mapping of the old basis */\n  for(i = 0; i <= lp->rows; i++)\n    oldmap[i] = i;\n  if(reinvert) {\n    allocINT(lp, &refmap, lp->rows+1, FALSE);\n    MEMCOPY(refmap, lp->var_basic, lp->rows+1);\n    sortByINT(oldmap, refmap, lp->rows, 1, TRUE);\n  }\n\n  /* Save old and calculate the new RHS vector */\n  MEMCOPY(oldrhs, lp->rhs, lp->rows+1);\n  if(reinvert)\n    invert(lp, INITSOL_USEZERO, FALSE);\n  else\n    recompute_solution(lp, INITSOL_USEZERO);\n\n  /* Get sorted mapping of the new basis */\n  for(i = 0; i <= lp->rows; i++)\n    newmap[i] = i;\n  if(reinvert) {\n    MEMCOPY(refmap, lp->var_basic, lp->rows+1);\n    sortByINT(newmap, refmap, lp->rows, 1, TRUE);\n  }\n\n  /* Identify any gap */\n  errmax = 0;\n  ii = -1;\n  n = 0;\n  for(i = lp->rows; i > 0; i--) {\n    err = fabs(my_reldiff(oldrhs[oldmap[i]], lp->rhs[newmap[i]]));\n    if(err > lp->epsprimal) {\n      n++;\n      if(err > errmax) {\n        ii = i;\n        errmax = err;\n      }\n    }\n  }\n  err = fabs(my_reldiff(oldrhs[i], lp->rhs[i]));\n  if(err < lp->epspivot) {\n    i--;\n    err = 0;\n  }\n  else {\n    n++;\n    if(ii < 0) {\n      ii = 0;\n      errmax = err;\n    }\n  }\n  if(n > 0) {\n    report(lp, IMPORTANT, \"verify_solution: Iter %.0f %s - %d errors; OF %g, Max @row %d %g\\n\",\n                           (double) get_total_iter(lp), my_if(info == NULL, \"\", info), n, err, newmap[ii], errmax);\n  }\n  /* Copy old results back (not possible for inversion) */\n  if(!reinvert)\n    MEMCOPY(lp->rhs, oldrhs, lp->rows+1);\n\n  FREE(oldmap);\n  FREE(newmap);\n  FREE(oldrhs);\n  if(reinvert)\n    FREE(refmap);\n\n  return( ii );\n\n}\n\n/* Preprocessing and postprocessing functions */\nSTATIC int identify_GUB(lprec *lp, MYBOOL mark)\n{\n  int    i, j, jb, je, k, knint, srh;\n  REAL   rh, mv, tv, bv;\n  MATrec *mat = lp->matA;\n\n  if((lp->equalities == 0) || !mat_validate(mat))\n    return( 0 );\n\n  k = 0;\n  for(i = 1; i <= lp->rows; i++) {\n\n    /* Check if it is an equality constraint */\n    if(!is_constr_type(lp, i, EQ))\n      continue;\n\n    rh = get_rh(lp, i);\n    srh = my_sign(rh);\n    knint = 0;\n    je = mat->row_end[i];\n    for(jb = mat->row_end[i-1]; jb < je; jb++) {\n      j = ROW_MAT_COLNR(jb);\n\n      /* Check for validity of the equation elements */\n      if(!is_int(lp, j))\n        knint++;\n      if(knint > 1)\n        break;\n\n      mv = get_mat_byindex(lp, jb, TRUE, FALSE);\n      if(fabs(my_reldiff(mv, rh)) > lp->epsprimal)\n        break;\n\n      tv = mv*get_upbo(lp, j);\n      bv = get_lowbo(lp, j);\n#if 0 /* Requires 1 as upper bound */\n      if((fabs(my_reldiff(tv, rh)) > lp->epsprimal) || (bv != 0))\n#else /* Can handle any upper bound >= 1 */\n      if((srh*(tv-rh) < -lp->epsprimal) || (bv != 0))\n#endif\n        break;\n    }\n\n    /* Update GUB count and optionally mark the GUB */\n    if(jb == je) {\n      k++;\n      if(mark == TRUE)\n        lp->row_type[i] |= ROWTYPE_GUB;\n      else if(mark == AUTOMATIC)\n        break;\n    }\n\n  }\n  return( k );\n}\n\nSTATIC int prepare_GUB(lprec *lp)\n{\n  int    i, j, jb, je, k, *members = NULL;\n  REAL   rh;\n  char   GUBname[16];\n  MATrec *mat = lp->matA;\n\n  if((lp->equalities == 0) ||\n     !allocINT(lp, &members, lp->columns+1, TRUE) ||\n     !mat_validate(mat))\n    return( 0 );\n\n  for(i = 1; i <= lp->rows; i++) {\n\n    /* Check if it has been marked as a GUB */\n    if(!(lp->row_type[i] & ROWTYPE_GUB))\n      continue;\n\n    /* Pick up the GUB column indeces */\n    k = 0;\n    je = mat->row_end[i];\n    for(jb = mat->row_end[i-1], k = 0; jb < je; jb++) {\n      members[k] = ROW_MAT_COLNR(jb);\n      k++;\n    }\n\n    /* Add the GUB */\n    j = GUB_count(lp) + 1;\n    sprintf(GUBname, \"GUB_%d\", i);\n    add_GUB(lp, GUBname, j, k, members);\n\n    /* Unmark the GUBs */\n    clear_action(&(lp->row_type[i]), ROWTYPE_GUB);\n\n    /* Standardize coefficients to 1 if necessary */\n    rh = get_rh(lp, i);\n    if(fabs(my_reldiff(rh, 1)) > lp->epsprimal) {\n      set_rh(lp, i, 1);\n      for(jb = mat->row_end[i-1]; jb < je; jb++) {\n        j = ROW_MAT_COLNR(jb);\n        set_mat(lp, i,j, 1);\n      }\n    }\n\n  }\n  FREE(members);\n  return(GUB_count(lp));\n}\n\n/* Pre- and post processing functions, i.a. splitting free variables */\nSTATIC MYBOOL pre_MIPOBJ(lprec *lp)\n{\n#ifdef MIPboundWithOF\n  if(MIP_count(lp) > 0) {\n    int i = 1;\n    while((i <= lp->rows) && !mat_equalRows(lp->matA, 0, i) && !is_constr_type(lp, i, EQ))\n      i++;\n    if(i <= lp->rows)\n      lp->constraintOF = i;\n  }\n#endif\n  lp->bb_deltaOF = MIP_stepOF(lp);\n  return( TRUE );\n}\nSTATIC MYBOOL post_MIPOBJ(lprec *lp)\n{\n#ifdef MIPboundWithOF\n/*\n  if(lp->constraintOF) {\n    del_constraint(lp, lp->rows);\n    if(is_BasisReady(lp) && !verify_basis(lp))\n      return( FALSE );\n  }\n*/\n#endif\n  return( TRUE );\n}\n\nint preprocess(lprec *lp)\n{\n  int    i, j, k, ok = TRUE, *new_index = NULL;\n  REAL   hold, *new_column = NULL;\n  MYBOOL scaled, primal1, primal2;\n\n /* do not process if already preprocessed */\n  if(lp->wasPreprocessed)\n    return( ok );\n\n  /* Write model statistics and optionally initialize partial pricing structures */\n  if(lp->lag_status != RUNNING) {\n    MYBOOL doPP;\n\n    /* Extract the user-specified simplex strategy choices */\n    primal1 = (MYBOOL) (lp->simplex_strategy & SIMPLEX_Phase1_PRIMAL);\n    primal2 = (MYBOOL) (lp->simplex_strategy & SIMPLEX_Phase2_PRIMAL);\n\n    /* Initialize partial pricing structures */\n    doPP = is_piv_mode(lp, PRICE_PARTIAL | PRICE_AUTOPARTIAL);\n/*    doPP &= (MYBOOL) (lp->columns / 2 > lp->rows); */\n    if(doPP) {\n      i = partial_findBlocks(lp, FALSE, FALSE);\n      if(i < 4)\n        i = (int) (5 * log((REAL) lp->columns / lp->rows));\n      report(lp, NORMAL, \"The model is %s to have %d column blocks/stages.\\n\",\n                         (i > 1 ? \"estimated\" : \"set\"), i);\n      set_partialprice(lp, i, NULL, FALSE);\n    }\n/*    doPP &= (MYBOOL) (lp->rows / 4 > lp->columns); */\n    if(doPP) {\n      i = partial_findBlocks(lp, FALSE, TRUE);\n      if(i < 4)\n        i = (int) (5 * log((REAL) lp->rows / lp->columns));\n      report(lp, NORMAL, \"The model is %s to have %d row blocks/stages.\\n\",\n                         (i > 1 ? \"estimated\" : \"set\"), i);\n      set_partialprice(lp, i, NULL, TRUE);\n    }\n\n    /* Check for presence of valid pricing blocks if partial pricing\n      is defined, but not autopartial is not set */\n    if(!doPP && is_piv_mode(lp, PRICE_PARTIAL)) {\n      if((lp->rowblocks == NULL) || (lp->colblocks == NULL)) {\n        report(lp, IMPORTANT, \"Ignoring partial pricing, since block structures are not defined.\\n\");\n        clear_action(&lp->piv_strategy, PRICE_PARTIAL);\n      }\n    }\n\n    /* Initialize multiple pricing block divisor */\n#if 0\n    if(primal1 || primal2)\n      lp->piv_strategy |= PRICE_MULTIPLE | PRICE_AUTOMULTIPLE;\n#endif\n    if(is_piv_mode(lp, PRICE_MULTIPLE) && (primal1 || primal2)) {\n      doPP = is_piv_mode(lp, PRICE_AUTOMULTIPLE);\n      if(doPP) {\n        i = (int) (2.5*log((REAL) lp->sum));\n        SETMAX( i, 1);\n        set_multiprice(lp, i);\n      }\n      if(lp->multiblockdiv > 1)\n      report(lp, NORMAL, \"Using %d-candidate primal simplex multiple pricing block.\\n\",\n                          lp->columns / lp->multiblockdiv);\n    }\n    else\n      set_multiprice(lp, 1);\n\n    report(lp, NORMAL, \"Using %s simplex for phase 1 and %s simplex for phase 2.\\n\",\n                       my_if(primal1, \"PRIMAL\", \"DUAL\"), my_if(primal2, \"PRIMAL\", \"DUAL\"));\n    i = get_piv_rule(lp);\n    if((i == PRICER_STEEPESTEDGE) && is_piv_mode(lp, PRICE_PRIMALFALLBACK))\n      report(lp, NORMAL, \"The pricing strategy is set to '%s' for the dual and '%s' for the primal.\\n\",\n                       get_str_piv_rule(i), get_str_piv_rule(i-1));\n    else\n      report(lp, NORMAL, \"The primal and dual simplex pricing strategy set to '%s'.\\n\",\n                       get_str_piv_rule(i));\n\n    report(lp, NORMAL, \" \\n\");\n  }\n\n  /* Compute a minimum step improvement step requirement */\n  pre_MIPOBJ(lp);\n\n /* First create extra columns for FR variables or flip MI variables */\n  for (j = 1; j <= lp->columns; j++) {\n\n#ifdef Paranoia\n    if((lp->rows != lp->matA->rows) || (lp->columns != lp->matA->columns))\n      report(lp, SEVERE, \"preprocess: Inconsistent variable counts found\\n\");\n#endif\n\n   /* First handle sign-flipping of variables:\n       1) ... with a finite upper bound and a negative Inf-bound (since basis variables are lower-bounded)\n       2) ... with bound assymetry within negrange limits (for stability reasons) */\n    i = lp->rows + j;\n    hold = lp->orig_upbo[i];\n/*\n    if((hold <= 0) || (!is_infinite(lp, lp->negrange) &&\n                       (hold < -lp->negrange) &&\n                       (lp->orig_lowbo[i] <= lp->negrange)) ) {\n*/\n#define fullybounded FALSE\n    if( ((hold < lp->infinite) && my_infinite(lp, lp->orig_lowbo[i])) ||\n        (!fullybounded && !my_infinite(lp, lp->negrange) &&\n         (hold < -lp->negrange) && (lp->orig_lowbo[i] <= lp->negrange)) ) {\n      /* Delete split sibling variable if one existed from before */\n      if((lp->var_is_free != NULL) && (lp->var_is_free[j] > 0))\n        del_column(lp, lp->var_is_free[j]);\n      /* Negate the column / flip to the positive range */\n      mat_multcol(lp->matA, j, -1, TRUE);\n      if(lp->var_is_free == NULL) {\n        if(!allocINT(lp, &lp->var_is_free, MAX(lp->columns, lp->columns_alloc) + 1, TRUE))\n          return(FALSE);\n      }\n      lp->var_is_free[j] = -j; /* Indicator UB and LB are switched, with no helper variable added */\n      lp->orig_upbo[i] = my_flipsign(lp->orig_lowbo[i]);\n      lp->orig_lowbo[i] = my_flipsign(hold);\n      /* Check for presence of negative ranged SC variable */\n      if(lp->sc_lobound[j] > 0) {\n        lp->sc_lobound[j] = lp->orig_lowbo[i];\n        lp->orig_lowbo[i] = 0;\n      }\n    }\n   /* Then deal with -+, full-range/FREE variables by creating a helper variable */\n    else if((lp->orig_lowbo[i] <= lp->negrange) && (hold >= -lp->negrange)) {\n      if(lp->var_is_free == NULL) {\n        if(!allocINT(lp, &lp->var_is_free, MAX(lp->columns,lp->columns_alloc) + 1, TRUE))\n          return(FALSE);\n      }\n      if(lp->var_is_free[j] <= 0) { /* If this variable wasn't split yet ... */\n        if(SOS_is_member(lp->SOS, 0, i - lp->rows)) {   /* Added */\n          report(lp, IMPORTANT, \"preprocess: Converted negative bound for SOS variable %d to zero\",\n                                i - lp->rows);\n          lp->orig_lowbo[i] = 0;\n          continue;\n        }\n        if(new_column == NULL) {\n          if(!allocREAL(lp, &new_column, lp->rows + 1, FALSE) ||\n             !allocINT(lp, &new_index, lp->rows + 1, FALSE)) {\n            ok = FALSE;\n            break;\n          }\n        }\n       /* Avoid precision loss by turning off unscaling and rescaling */\n       /* in get_column and add_column operations; also make sure that */\n       /* full scaling information is preserved */\n        scaled = lp->scaling_used;\n        lp->scaling_used = FALSE;\n        k = get_columnex(lp, j, new_column, new_index);\n        if(!add_columnex(lp, k, new_column, new_index)) {\n          ok = FALSE;\n          break;\n        }\n        mat_multcol(lp->matA, lp->columns, -1, TRUE);\n        if(scaled)\n          lp->scalars[lp->rows+lp->columns] = lp->scalars[i];\n        lp->scaling_used = (MYBOOL) scaled;\n        /* Only create name if we are not clearing a pre-used item, since this\n           variable could have been deleted by presolve but the name is required\n           for solution reconstruction. */\n        if(lp->names_used && (lp->col_name[j] == NULL)) {\n          char fieldn[50];\n\n          sprintf(fieldn, \"__AntiBodyOf(%d)__\", j);\n          if(!set_col_name(lp, lp->columns, fieldn)) {\n/*          if (!set_col_name(lp, lp->columns, get_col_name(lp, j))) { */\n            ok = FALSE;\n            break;\n          }\n        }\n        /* Set (positive) index to the original column's split / helper and back */\n        lp->var_is_free[j] = lp->columns;\n      }\n      lp->orig_upbo[lp->rows + lp->var_is_free[j]] = my_flipsign(lp->orig_lowbo[i]);\n      lp->orig_lowbo[i] = 0;\n\n      /* Negative index indicates x is split var and -var_is_free[x] is index of orig var */\n      lp->var_is_free[lp->var_is_free[j]] = -j;\n      lp->var_type[lp->var_is_free[j]] = lp->var_type[j];\n    }\n   /* Check for positive ranged SC variables */\n    else if(lp->sc_lobound[j] > 0) {\n      lp->sc_lobound[j] = lp->orig_lowbo[i];\n      lp->orig_lowbo[i] = 0;\n    }\n\n   /* Tally integer variables in SOS'es */\n    if(SOS_is_member(lp->SOS, 0, j) && is_int(lp, j))\n      lp->sos_ints++;\n  }\n\n  FREE(new_column);\n  FREE(new_index);\n\n  /* Fill lists of GUB constraints, if appropriate */\n  if((MIP_count(lp) > 0) && is_bb_mode(lp, NODE_GUBMODE) && (identify_GUB(lp, AUTOMATIC) > 0))\n    prepare_GUB(lp);\n\n  /* (Re)allocate reduced cost arrays */\n  ok = allocREAL(lp, &(lp->drow), lp->sum+1, AUTOMATIC) &&\n       allocINT(lp, &(lp->nzdrow), lp->sum+1, AUTOMATIC);\n  if(ok)\n    lp->nzdrow[0] = 0;\n\n  /* Minimize memory usage */\n  memopt_lp(lp, 0, 0, 0);\n\n  lp->wasPreprocessed = TRUE;\n\n  return(ok);\n}\n\nvoid postprocess(lprec *lp)\n{\n  int i,ii,j;\n  REAL hold;\n\n /* Check if the problem actually was preprocessed */\n  if(!lp->wasPreprocessed)\n    return;\n\n /* Must compute duals here in case we have free variables; note that in\n    this case sensitivity analysis is not possible unless done here */\n  if((lp->bb_totalnodes == 0) && (lp->var_is_free == NULL)) {\n    if(is_presolve(lp, PRESOLVE_DUALS))\n      construct_duals(lp);\n    if(is_presolve(lp, PRESOLVE_SENSDUALS))\n      if(!construct_sensitivity_duals(lp) || !construct_sensitivity_obj(lp))\n        report(lp, IMPORTANT, \"postprocess: Unable to allocate working memory for duals.\\n\");\n  }\n\n /* Loop over all columns */\n  for (j = 1; j <= lp->columns; j++) {\n    i = lp->rows + j;\n   /* Reconstruct strictly negative values */\n    if((lp->var_is_free != NULL) && (lp->var_is_free[j] < 0)) {\n      /* Check if we have the simple case where the UP and LB are negated and switched */\n      if(-lp->var_is_free[j] == j) {\n        mat_multcol(lp->matA, j, -1, TRUE);\n        hold = lp->orig_upbo[i];\n        lp->orig_upbo[i] = my_flipsign(lp->orig_lowbo[i]);\n        lp->orig_lowbo[i] = my_flipsign(hold);\n        lp->best_solution[i] = my_flipsign(lp->best_solution[i]);\n        transfer_solution_var(lp, j);\n\n        /* hold = lp->objfrom[j];\n        lp->objfrom[j] = my_flipsign(lp->objtill[j]);\n        lp->objtill[j] = my_flipsign(hold); */ /* under investigation <peno> */\n\n        /* lp->duals[i] = my_flipsign(lp->duals[i]);\n        hold = lp->dualsfrom[i];\n        lp->dualsfrom[i] = my_flipsign(lp->dualstill[i]);\n        lp->dualstill[i] = my_flipsign(hold); */ /* under investigation <peno> */\n       /* Bound switch undone, so clear the status */\n        lp->var_is_free[j] = 0;\n       /* Adjust negative ranged SC */\n        if(lp->sc_lobound[j] > 0)\n          lp->orig_lowbo[lp->rows + j] = -lp->sc_lobound[j];\n      }\n      /* Ignore the split / helper columns (will be deleted later) */\n    }\n   /* Condense values of extra columns of quasi-free variables split in two */\n    else if((lp->var_is_free != NULL) && (lp->var_is_free[j] > 0)) {\n      ii = lp->var_is_free[j]; /* Index of the split helper var */\n      /* if(lp->objfrom[j] == -lp->infinite)\n        lp->objfrom[j] = -lp->objtill[ii];\n      lp->objtill[ii] = lp->infinite;\n      if(lp->objtill[j] == lp->infinite)\n        lp->objtill[j] = my_flipsign(lp->objfrom[ii]);\n      lp->objfrom[ii] = -lp->infinite; */ /* under investigation <peno> */\n\n      ii += lp->rows;\n      lp->best_solution[i] -= lp->best_solution[ii]; /* join the solution again */\n      transfer_solution_var(lp, j);\n      lp->best_solution[ii] = 0;\n\n      /* if(lp->duals[i] == 0)\n        lp->duals[i] = my_flipsign(lp->duals[ii]);\n      lp->duals[ii] = 0;\n      if(lp->dualsfrom[i] == -lp->infinite)\n        lp->dualsfrom[i] = my_flipsign(lp->dualstill[ii]);\n      lp->dualstill[ii] = lp->infinite;\n      if(lp->dualstill[i] == lp->infinite)\n        lp->dualstill[i] = my_flipsign(lp->dualsfrom[ii]);\n      lp->dualsfrom[ii] = -lp->infinite; */ /* under investigation <peno> */\n\n      /* Reset to original bound */\n      lp->orig_lowbo[i] = my_flipsign(lp->orig_upbo[ii]);\n    }\n   /* Adjust for semi-continuous variables */\n    else if(lp->sc_lobound[j] > 0) {\n      lp->orig_lowbo[i] = lp->sc_lobound[j];\n    }\n  }\n\n  /* Remove any split column helper variables */\n  del_splitvars(lp);\n  post_MIPOBJ(lp);\n\n  /* Do extended reporting, if specified */\n  if(lp->verbose > NORMAL) {\n    REPORT_extended(lp);\n\n  }\n\n  lp->wasPreprocessed = FALSE;\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_lib.h",
    "content": "\n#ifndef HEADER_lp_lib\n#define HEADER_lp_lib\n\n/* --------------------------------------------------------------------------\n\n  This is the main library header file for the lp_solve v5.0 release\n\n  Starting at version 3.0, LP_Solve is released under the LGPL license.\n  For full information, see the enclosed file LGPL.txt.\n\n  Original developer:   Michel Berkelaar  -  michel@ics.ele.tue.nl\n  Most changes 1.5-2.0: Jeroen Dirks      -  jeroend@tor.numetrix.com\n  Changes 3.2-4.0:      Kjell Eikland     -  kjell.eikland@broadpark.no\n                        (Simplex code, SOS, SC, code optimization)\n                        Peter Notebaert   -  lpsolve@peno.be\n                        (Sensitivity analysis, documentation)\n  Changes 5.0+:         Kjell Eikland     -  kjell.eikland@broadpark.no\n                        (BFP, XLI, simplex, B&B, code modularization)\n                        Peter Notebaert   -  lpsolve@peno.be\n                        (Sensitivity analysis, New lp parser, LINDO (XLI)\n                        parser, VB/.NET interface, documentation)\n\n  Release notes:\n\n  Version 4.0 enhances version 3.2 in terms of internal program/simplex\n  architecture, call level interfaces, data layout, features and contains\n  several bug fixes.  There is now complete support for semi-continuous\n  variables and SOS constructions.  In the process, a complete API\n  was added. The MPS parser has been amended to support this.\n  Sensitivity analysis and variouse bug fixes was provided by Peter\n  Notebaert in 4.0 sub-releases.  Peter also wrote a complete\n  documentation of the API and contributed a VB interface, both of which\n  significantly enhanced the accessibility of lp_solve.\n\n  Version 5.0 is a major rewrite and code cleanup.  The main additions that\n  drove forward this cleanup were the modular inversion logic with optimal\n  column ordering, addition of primal phase 1 and dual phase 2 logic for\n  full flexibility in the selection of primal and dual simplex modes,\n  DEVEX and steepest edge pivot selection, along with dynamic cycling\n  detection and prevention.  This cleanup made it possible to harmonize the\n  internal rounding principles, contributing to increased numerical stability.\n\n  Version 5.1 rearranges the matrix storage model by enabling both legacy\n  element record-based storage and split vector storage.  In addition the\n  lprec structure is optimized and additional routines are added, mainly for\n  sparse vector additions and enhanced XLI functionality.  Support for XML-\n  based models was added on the basis of the LPFML schema via xli_LPFML.\n\n  Version 5.2 removes the objective function from the constraint matrix,\n  adds a number of presolve options and speed them up.  Degeneracy handling\n  is significantly improved. Support for XLI_ZIMPL was added.\n  Multiple and partial pricing has been enhanced and activated.\n\n  -------------------------------------------------------------------------- */\n/* Define user program feature option switches                               */\n/* ------------------------------------------------------------------------- */\n\n# if defined _WIN32 && !defined __GNUC__\n#  define isnan _isnan\n# endif\n#if defined NOISNAN\n# define isnan(x) FALSE\n#endif\n\n#define SETMASK(variable, mask)     variable |= mask\n#define CLEARMASK(variable, mask)   variable &= ~(mask)\n#define TOGGLEMASK(variable, mask)  variable ^= mask\n#define ISMASKSET(variable, mask)   (MYBOOL) (((variable) & (mask)) != 0)\n\n/* Utility/system settings                                                   */\n/* ------------------------------------------------------------------------- */\n/*#define INTEGERTIME */                    /* Set use of lower-resolution timer */\n\n\n/* New v5.0+ simplex/optimization features and settings                      */\n/* ------------------------------------------------------------------------- */\n/*#define NoRowScaleOF */               /* Optionally skip row-scaling of the OF */\n#define DoMatrixRounding                  /* Round A matrix elements to precision */\n#define DoBorderRounding            /* Round RHS, bounds and ranges to precision */\n#define Phase1EliminateRedundant        /* Remove rows of redundant artificials  */\n#define FixViolatedOptimal\n#define ImproveSolutionPrecision                 /* Round optimal solution values */\n/*#define IncreasePivotOnReducedAccuracy */  /* Increase epspivot on instability */\n/*#define FixInaccurateDualMinit */     /* Reinvert on inaccuracy in dual minits */\n/*#define EnforcePositiveTheta */        /* Ensure that the theta range is valid */\n#define ResetMinitOnReinvert\n/*#define UsePrimalReducedCostUpdate */                            /* Not tested */\n/*#define UseDualReducedCostUpdate */      /* Seems Ok, but slower than expected */\n/*#ifdef UseLegacyExtrad */                     /* Use v3.2- style Extrad method */\n#define UseMilpExpandedRCF         /* Non-ints in reduced cost bound tightening */\n/*#define UseMilpSlacksRCF */  /* Slacks in reduced cost bound tightening (degen\n                                  prone); requires !SlackInitMinusInf */\n#define LegacySlackDefinition      /* Slack as the \"value of the constraint\" */\n\n\n/* Development features (change at own risk)                                 */\n/* ------------------------------------------------------------------------- */\n/*#define MIPboundWithOF */ /* Enable to detect OF constraint for use during B&B */\n/*#define SlackInitMinusInf */        /* Slacks have 0 LB if this is not defined */\n#define FULLYBOUNDEDSIMPLEX FALSE     /* WARNING: Activate at your own risk! */\n\n\n/* Specify use of the basic linear algebra subroutine library                */\n/* ------------------------------------------------------------------------- */\n#define libBLAS                  2        /* 0: No, 1: Internal, 2: External */\n#define libnameBLAS        \"myBLAS\"\n\n\n/* Active inverse logic (default is optimized original etaPFI)               */\n/* ------------------------------------------------------------------------- */\n#if !defined LoadInverseLib\n# define LoadInverseLib TRUE          /* Enable alternate inverse libraries */\n#endif\n/*#define ExcludeNativeInverse     */   /* Disable INVERSE_ACTIVE inverse engine */\n\n#define DEF_OBJINBASIS        TRUE  /* Additional rows inserted at the top (1 => OF) */\n\n#define INVERSE_NONE            -1\n#define INVERSE_LEGACY           0\n#define INVERSE_ETAPFI           1\n#define INVERSE_LUMOD            2\n#define INVERSE_LUSOL            3\n#define INVERSE_GLPKLU           4\n\n#ifndef RoleIsExternalInvEngine            /* Defined in inverse DLL drivers */\n  #ifdef ExcludeNativeInverse\n    #define INVERSE_ACTIVE       INVERSE_NONE       /* Disable native engine */\n  #else\n    #define INVERSE_ACTIVE       INVERSE_LEGACY      /* User or DLL-selected */\n  #endif\n#endif\n\n\n/* Active external language interface logic (default is none)                */\n/* ------------------------------------------------------------------------- */\n#if !defined LoadLanguageLib\n# define LoadLanguageLib TRUE         /* Enable alternate language libraries */\n#endif\n#define ExcludeNativeLanguage                 /* Disable LANGUAGE_ACTIVE XLI */\n\n#define LANGUAGE_NONE           -1\n#define LANGUAGE_LEGACYLP        0\n#define LANGUAGE_CPLEXLP         1\n#define LANGUAGE_MPSX            2\n#define LANGUAGE_LPFML           3\n#define LANGUAGE_MATHPROG        4\n#define LANGUAGE_AMPL            5\n#define LANGUAGE_GAMS            6\n#define LANGUAGE_ZIMPL           7\n#define LANGUAGE_S               8\n#define LANGUAGE_R               9\n#define LANGUAGE_MATLAB         10\n#define LANGUAGE_OMATRIX        11\n#define LANGUAGE_SCILAB         12\n#define LANGUAGE_OCTAVE         13\n#define LANGUAGE_EMPS           14\n\n#ifndef RoleIsExternalLanguageEngine      /* Defined in XLI driver libraries */\n  #ifdef ExcludeNativeLanguage\n    #define LANGUAGE_ACTIVE       LANGUAGE_NONE     /* Disable native engine */\n  #else\n    #define LANGUAGE_ACTIVE       LANGUAGE_CPLEXLP   /* User or DLL-selected */\n  #endif\n#endif\n\n\n/* Default parameters and tolerances                                         */\n/* ------------------------------------------------------------------------- */\n#define OriginalPARAM           0\n#define ProductionPARAM         1\n#define ChvatalPARAM            2\n#define LoosePARAM              3\n#if 1\n  #define ActivePARAM           ProductionPARAM\n#else\n  #define ActivePARAM           LoosePARAM\n#endif\n\n\n/* Miscellaneous settings                                                    */\n/* ------------------------------------------------------------------------- */\n#ifndef Paranoia\n  #ifdef _DEBUG\n    #define Paranoia\n  #endif\n#endif\n\n\n/* Program version data                                                      */\n/* ------------------------------------------------------------------------- */\n#define MAJORVERSION             5\n#define MINORVERSION             5\n#define RELEASE                  2\n#define BUILD                    0\n#define BFPVERSION              12       /* Checked against bfp_compatible() */\n#define XLIVERSION              12       /* Checked against xli_compatible() */\n/* Note that both BFPVERSION and XLIVERSION typically have to be incremented\n   in the case that the lprec structure changes.                             */\n\n\n/* Include/header files                                                      */\n/* ------------------------------------------------------------------------- */\n#include <sys/types.h>\n#include <stdlib.h>\n#include <string.h>\n#include <math.h>\n#include <stdio.h>\n\n#include \"lp_types.h\"\n#include \"lp_utils.h\"\n\n#if (LoadInverseLib == TRUE) || (LoadLanguageLib == TRUE)\n  #ifdef WIN32\n    #include <windows.h>\n  #else\n    #include <dlfcn.h>\n  #endif\n#endif\n\n#ifndef BFP_CALLMODEL\n  #ifdef WIN32\n    #define BFP_CALLMODEL __stdcall   /* \"Standard\" call model */\n  #else\n    #define BFP_CALLMODEL\n  #endif\n#endif\n#ifndef XLI_CALLMODEL\n  #define XLI_CALLMODEL BFP_CALLMODEL\n#endif\n\n#define REGISTER        register      /* Speed up certain operations */\n\n\n/* Definition of program constrants                                          */\n/* ------------------------------------------------------------------------- */\n#define SIMPLEX_UNDEFINED        0\n#define SIMPLEX_Phase1_PRIMAL    1\n#define SIMPLEX_Phase1_DUAL      2\n#define SIMPLEX_Phase2_PRIMAL    4\n#define SIMPLEX_Phase2_DUAL      8\n#define SIMPLEX_DYNAMIC         16\n#define SIMPLEX_AUTODUALIZE     32\n\n#define SIMPLEX_PRIMAL_PRIMAL   (SIMPLEX_Phase1_PRIMAL + SIMPLEX_Phase2_PRIMAL)\n#define SIMPLEX_DUAL_PRIMAL     (SIMPLEX_Phase1_DUAL   + SIMPLEX_Phase2_PRIMAL)\n#define SIMPLEX_PRIMAL_DUAL     (SIMPLEX_Phase1_PRIMAL + SIMPLEX_Phase2_DUAL)\n#define SIMPLEX_DUAL_DUAL       (SIMPLEX_Phase1_DUAL   + SIMPLEX_Phase2_DUAL)\n#define SIMPLEX_DEFAULT         (SIMPLEX_DUAL_PRIMAL)\n\n/* Variable codes (internal) */\n#define ISREAL                   0\n#define ISINTEGER                1\n#define ISSEMI                   2\n#define ISSOS                    4\n#define ISSOSTEMPINT             8\n#define ISGUB                   16\n\n/* Presolve defines */\n#define PRESOLVE_NONE            0\n#define PRESOLVE_ROWS            1\n#define PRESOLVE_COLS            2\n#define PRESOLVE_LINDEP          4\n#define PRESOLVE_AGGREGATE       8  /* Not implemented */\n#define PRESOLVE_SPARSER        16  /* Not implemented */\n#define PRESOLVE_SOS            32\n#define PRESOLVE_REDUCEMIP      64\n#define PRESOLVE_KNAPSACK      128  /* Implementation not tested completely */\n#define PRESOLVE_ELIMEQ2       256\n#define PRESOLVE_IMPLIEDFREE   512\n#define PRESOLVE_REDUCEGCD    1024\n#define PRESOLVE_PROBEFIX     2048\n#define PRESOLVE_PROBEREDUCE  4096\n#define PRESOLVE_ROWDOMINATE  8192\n#define PRESOLVE_COLDOMINATE 16384  /* Reduced functionality, should be expanded */\n#define PRESOLVE_MERGEROWS   32768\n#define PRESOLVE_IMPLIEDSLK  65536\n#define PRESOLVE_COLFIXDUAL 131072\n#define PRESOLVE_BOUNDS     262144\n#define PRESOLVE_LASTMASKMODE    (PRESOLVE_DUALS - 1)\n#define PRESOLVE_DUALS      524288\n#define PRESOLVE_SENSDUALS 1048576\n\n/* Basis crash options */\n#define CRASH_NONE               0\n#define CRASH_NONBASICBOUNDS     1\n#define CRASH_MOSTFEASIBLE       2\n#define CRASH_LEASTDEGENERATE    3\n\n/* Solution recomputation options (internal) */\n#define INITSOL_SHIFTZERO        0\n#define INITSOL_USEZERO          1\n#define INITSOL_ORIGINAL         2\n\n/* Strategy codes to avoid or recover from degenerate pivots,\n   infeasibility or numeric errors via randomized bound relaxation */\n#define ANTIDEGEN_NONE           0\n#define ANTIDEGEN_FIXEDVARS      1\n#define ANTIDEGEN_COLUMNCHECK    2\n#define ANTIDEGEN_STALLING       4\n#define ANTIDEGEN_NUMFAILURE     8\n#define ANTIDEGEN_LOSTFEAS      16\n#define ANTIDEGEN_INFEASIBLE    32\n#define ANTIDEGEN_DYNAMIC       64\n#define ANTIDEGEN_DURINGBB     128\n#define ANTIDEGEN_RHSPERTURB   256\n#define ANTIDEGEN_BOUNDFLIP    512\n#define ANTIDEGEN_DEFAULT        (ANTIDEGEN_FIXEDVARS | ANTIDEGEN_STALLING /* | ANTIDEGEN_INFEASIBLE */)\n\n/* REPORT defines */\n#define NEUTRAL                  0\n#define CRITICAL                 1\n#define SEVERE                   2\n#define IMPORTANT                3\n#define NORMAL                   4\n#define DETAILED                 5\n#define FULL                     6\n\n/* MESSAGE defines */\n#define MSG_NONE                 0\n#define MSG_PRESOLVE             1\n#define MSG_ITERATION            2\n#define MSG_INVERT               4\n#define MSG_LPFEASIBLE           8\n#define MSG_LPOPTIMAL           16\n#define MSG_LPEQUAL             32\n#define MSG_LPBETTER            64\n#define MSG_MILPFEASIBLE       128\n#define MSG_MILPEQUAL          256\n#define MSG_MILPBETTER         512\n#define MSG_MILPSTRATEGY      1024\n#define MSG_MILPOPTIMAL       2048\n#define MSG_PERFORMANCE       4096\n#define MSG_INITPSEUDOCOST    8192\n\n/* MPS file types */\n#define MPSFIXED                 1\n#define MPSFREE                  2\n#define MPSIBM                   4\n#define MPSNEGOBJCONST           8\n\n#define MPS_FREE                 (MPSFREE<<2)\n#define MPS_IBM                  (MPSIBM<<2)\n#define MPS_NEGOBJCONST          (MPSNEGOBJCONST<<2)\n\n/* MPS defines (internal) */\n#define MPSUNDEF                -4\n#define MPSNAME                 -3\n#define MPSOBJSENSE             -2\n#define MPSOBJNAME              -1\n#define MPSROWS                  0\n#define MPSCOLUMNS               1\n#define MPSRHS                   2\n#define MPSBOUNDS                3\n#define MPSRANGES                4\n#define MPSSOS                   5\n\n#define MPSVARMASK          \"%-8s\"\n#define MPSVALUEMASK        \"%12g\"\n\n/* Constraint type codes  (internal) */\n#define ROWTYPE_EMPTY            0\n#define ROWTYPE_LE               1\n#define ROWTYPE_GE               2\n#define ROWTYPE_EQ               3\n#define ROWTYPE_CONSTRAINT       ROWTYPE_EQ  /* This is the mask for modes */\n#define ROWTYPE_OF               4\n#define ROWTYPE_INACTIVE         8\n#define ROWTYPE_RELAX           16\n#define ROWTYPE_GUB             32\n#define ROWTYPE_OFMAX            (ROWTYPE_OF + ROWTYPE_GE)\n#define ROWTYPE_OFMIN            (ROWTYPE_OF + ROWTYPE_LE)\n#define ROWTYPE_CHSIGN           ROWTYPE_GE\n\n/* Public constraint codes */\n#define FR                       ROWTYPE_EMPTY\n#define LE                       ROWTYPE_LE\n#define GE                       ROWTYPE_GE\n#define EQ                       ROWTYPE_EQ\n#define OF                       ROWTYPE_OF\n\n/* MIP constraint classes */\n#define ROWCLASS_Unknown         0   /* Undefined/unknown */\n#define ROWCLASS_Objective       1   /* The objective function */\n#define ROWCLASS_GeneralREAL     2   /* General real-values constraint */\n#define ROWCLASS_GeneralMIP      3   /* General mixed integer/binary and real valued constraint */\n#define ROWCLASS_GeneralINT      4   /* General integer-only constraint */\n#define ROWCLASS_GeneralBIN      5   /* General binary-only constraint */\n#define ROWCLASS_KnapsackINT     6   /* Sum of positive integer times integer variables <= positive integer */\n#define ROWCLASS_KnapsackBIN     7   /* Sum of positive integer times binary variables <= positive integer */\n#define ROWCLASS_SetPacking      8   /* Sum of binary variables >= 1 */\n#define ROWCLASS_SetCover        9   /* Sum of binary variables <= 1 */\n#define ROWCLASS_GUB            10   /* Sum of binary variables = 1  */\n#define ROWCLASS_MAX             ROWCLASS_GUB\n\n/* Column subsets (internal) */\n#define SCAN_USERVARS            1\n#define SCAN_SLACKVARS           2\n#define SCAN_ARTIFICIALVARS      4\n#define SCAN_PARTIALBLOCK        8\n#define USE_BASICVARS           16\n#define USE_NONBASICVARS        32\n#define SCAN_NORMALVARS         (SCAN_USERVARS + SCAN_ARTIFICIALVARS)\n#define SCAN_ALLVARS            (SCAN_SLACKVARS + SCAN_USERVARS + SCAN_ARTIFICIALVARS)\n#define USE_ALLVARS             (USE_BASICVARS + USE_NONBASICVARS)\n#define OMIT_FIXED              64\n#define OMIT_NONFIXED          128\n\n/* Improvement defines */\n#define IMPROVE_NONE             0\n#define IMPROVE_SOLUTION         1\n#define IMPROVE_DUALFEAS         2\n#define IMPROVE_THETAGAP         4\n#define IMPROVE_BBSIMPLEX        8\n#define IMPROVE_DEFAULT          (IMPROVE_DUALFEAS + IMPROVE_THETAGAP)\n#define IMPROVE_INVERSE          (IMPROVE_SOLUTION + IMPROVE_THETAGAP)\n\n/* Scaling types */\n#define SCALE_NONE               0\n#define SCALE_EXTREME            1\n#define SCALE_RANGE              2\n#define SCALE_MEAN               3\n#define SCALE_GEOMETRIC          4\n#define SCALE_FUTURE1            5\n#define SCALE_FUTURE2            6\n#define SCALE_CURTISREID         7   /* Override to Curtis-Reid \"optimal\" scaling */\n\n/* Alternative scaling weights */\n#define SCALE_LINEAR             0\n#define SCALE_QUADRATIC          8\n#define SCALE_LOGARITHMIC       16\n#define SCALE_USERWEIGHT        31\n#define SCALE_MAXTYPE            (SCALE_QUADRATIC-1)\n\n/* Scaling modes */\n#define SCALE_POWER2            32   /* As is or rounded to power of 2 */\n#define SCALE_EQUILIBRATE       64   /* Make sure that no scaled number is above 1 */\n#define SCALE_INTEGERS         128   /* Apply to integer columns/variables */\n#define SCALE_DYNUPDATE        256   /* Apply incrementally every solve() */\n#define SCALE_ROWSONLY         512   /* Override any scaling to only scale the rows */\n#define SCALE_COLSONLY        1024   /* Override any scaling to only scale the rows */\n\n/* Standard defines for typical scaling models (no Lagrangeans) */\n#define SCALEMODEL_EQUILIBRATED  (SCALE_LINEAR+SCALE_EXTREME+SCALE_INTEGERS)\n#define SCALEMODEL_GEOMETRIC     (SCALE_LINEAR+SCALE_GEOMETRIC+SCALE_INTEGERS)\n#define SCALEMODEL_ARITHMETIC    (SCALE_LINEAR+SCALE_MEAN+SCALE_INTEGERS)\n#define SCALEMODEL_DYNAMIC       (SCALEMODEL_GEOMETRIC+SCALE_EQUILIBRATE)\n#define SCALEMODEL_CURTISREID    (SCALE_CURTISREID+SCALE_INTEGERS+SCALE_POWER2)\n\n/* Iteration status and strategies (internal) */\n#define ITERATE_MAJORMAJOR       0\n#define ITERATE_MINORMAJOR       1\n#define ITERATE_MINORRETRY       2\n\n/* Pricing methods */\n#define PRICER_FIRSTINDEX        0\n#define PRICER_DANTZIG           1\n#define PRICER_DEVEX             2\n#define PRICER_STEEPESTEDGE      3\n#define PRICER_LASTOPTION        PRICER_STEEPESTEDGE\n\n/* Additional settings for pricers (internal) */\n#define PRICER_RANDFACT        0.1\n#define DEVEX_RESTARTLIMIT 1.0e+09    /* Reset the norms if any value exceeds this limit */\n#define DEVEX_MINVALUE       0.000    /* Minimum weight [0..1] for entering variable, consider 0.01 */\n\n/* Pricing strategies */\n#define PRICE_PRIMALFALLBACK     4    /* In case of Steepest Edge, fall back to DEVEX in primal */\n#define PRICE_MULTIPLE           8    /* Enable multiple pricing (primal simplex) */\n#define PRICE_PARTIAL           16    /* Enable partial pricing */\n#define PRICE_ADAPTIVE          32    /* Temporarily use alternative strategy if cycling is detected */\n#define PRICE_HYBRID            64    /* NOT IMPLEMENTED */\n#define PRICE_RANDOMIZE        128    /* Adds a small randomization effect to the selected pricer */\n#define PRICE_AUTOPARTIAL      256    /* Detect and use data on the block structure of the model (primal) */\n#define PRICE_AUTOMULTIPLE     512    /* Automatically select multiple pricing (primal simplex) */\n#define PRICE_LOOPLEFT        1024    /* Scan entering/leaving columns left rather than right */\n#define PRICE_LOOPALTERNATE   2048    /* Scan entering/leaving columns alternatingly left/right */\n#define PRICE_HARRISTWOPASS   4096    /* Use Harris' primal pivot logic rather than the default */\n#define PRICE_FORCEFULL       8192    /* Non-user option to force full pricing */\n#define PRICE_TRUENORMINIT   16384    /* Use true norms for Devex and Steepest Edge initializations */\n\n/*#define _PRICE_NOBOUNDFLIP*/\n#if defined _PRICE_NOBOUNDFLIP\n#define PRICE_NOBOUNDFLIP    65536    /* Disallow automatic bound-flip during pivot */\n#endif\n\n#define PRICE_STRATEGYMASK       (PRICE_PRIMALFALLBACK + \\\n                                  PRICE_MULTIPLE + PRICE_PARTIAL + \\\n                                  PRICE_ADAPTIVE + PRICE_HYBRID + \\\n                                  PRICE_RANDOMIZE + PRICE_AUTOPARTIAL + PRICE_AUTOMULTIPLE + \\\n                                  PRICE_LOOPLEFT + PRICE_LOOPALTERNATE + \\\n                                  PRICE_HARRISTWOPASS + \\\n                                  PRICE_FORCEFULL + PRICE_TRUENORMINIT)\n\n/* B&B active variable codes (internal) */\n#define BB_REAL                  0\n#define BB_INT                   1\n#define BB_SC                    2\n#define BB_SOS                   3\n#define BB_GUB                   4\n\n/* B&B strategies */\n#define NODE_FIRSTSELECT         0\n#define NODE_GAPSELECT           1\n#define NODE_RANGESELECT         2\n#define NODE_FRACTIONSELECT      3\n#define NODE_PSEUDOCOSTSELECT    4\n#define NODE_PSEUDONONINTSELECT  5    /* Kjell Eikland #1 - Minimize B&B depth */\n#define NODE_PSEUDOFEASSELECT   (NODE_PSEUDONONINTSELECT+NODE_WEIGHTREVERSEMODE)\n#define NODE_PSEUDORATIOSELECT   6    /* Kjell Eikland #2 - Minimize a \"cost/benefit\" ratio */\n#define NODE_USERSELECT          7\n#define NODE_STRATEGYMASK        (NODE_WEIGHTREVERSEMODE-1) /* Mask for B&B strategies */\n#define NODE_WEIGHTREVERSEMODE   8\n#define NODE_BRANCHREVERSEMODE  16\n#define NODE_GREEDYMODE         32\n#define NODE_PSEUDOCOSTMODE     64\n#define NODE_DEPTHFIRSTMODE    128\n#define NODE_RANDOMIZEMODE     256\n#define NODE_GUBMODE           512\n#define NODE_DYNAMICMODE      1024\n#define NODE_RESTARTMODE      2048\n#define NODE_BREADTHFIRSTMODE 4096\n#define NODE_AUTOORDER        8192\n#define NODE_RCOSTFIXING     16384\n#define NODE_STRONGINIT      32768\n\n#define BRANCH_CEILING           0\n#define BRANCH_FLOOR             1\n#define BRANCH_AUTOMATIC         2\n#define BRANCH_DEFAULT           3\n\n/* Action constants for simplex and B&B (internal) */\n#define ACTION_NONE              0\n#define ACTION_ACTIVE            1\n#define ACTION_REBASE            2\n#define ACTION_RECOMPUTE         4\n#define ACTION_REPRICE           8\n#define ACTION_REINVERT         16\n#define ACTION_TIMEDREINVERT    32\n#define ACTION_ITERATE          64\n#define ACTION_RESTART         255\n\n/* Solver status values */\n#define UNKNOWNERROR            -5\n#define DATAIGNORED             -4\n#define NOBFP                   -3\n#define NOMEMORY                -2\n#define NOTRUN                  -1\n#define OPTIMAL                  0\n#define SUBOPTIMAL               1\n#define INFEASIBLE               2\n#define UNBOUNDED                3\n#define DEGENERATE               4\n#define NUMFAILURE               5\n#define USERABORT                6\n#define TIMEOUT                  7\n#define RUNNING                  8\n#define PRESOLVED                9\n\n/* Branch & Bound and Lagrangean extra status values (internal) */\n#define PROCFAIL                10\n#define PROCBREAK               11\n#define FEASFOUND               12\n#define NOFEASFOUND             13\n#define FATHOMED                14\n\n/* Status values internal to the solver (internal) */\n#define SWITCH_TO_PRIMAL        20\n#define SWITCH_TO_DUAL          21\n#define SINGULAR_BASIS          22\n#define LOSTFEAS                23\n#define MATRIXERROR             24\n\n/* Objective testing options for \"bb_better\" (internal) */\n#define OF_RELAXED               0\n#define OF_INCUMBENT             1\n#define OF_WORKING               2\n#define OF_USERBREAK             3\n#define OF_HEURISTIC             4\n#define OF_DUALLIMIT             5\n#define OF_DELTA                 8  /* Mode */\n#define OF_PROJECTED            16  /* Mode - future, not active */\n\n#define OF_TEST_BT               1\n#define OF_TEST_BE               2\n#define OF_TEST_NE               3\n#define OF_TEST_WE               4\n#define OF_TEST_WT               5\n#define OF_TEST_RELGAP           8  /* Mode */\n\n\n/* Name list and sparse matrix storage parameters (internal) */\n#define MAT_START_SIZE       10000\n#define DELTACOLALLOC          100\n#define DELTAROWALLOC          100\n#define RESIZEFACTOR             4  /* Fractional increase in selected memory allocations */\n\n/* Default solver parameters and tolerances (internal) */\n#define DEF_PARTIALBLOCKS       10  /* The default number of blocks for partial pricing */\n#define DEF_MAXRELAX             7  /* Maximum number of non-BB relaxations in MILP */\n#define DEF_MAXPIVOTRETRY       10  /* Maximum number of times to retry a div-0 situation */\n#define DEF_MAXSINGULARITIES    10  /* Maximum number of singularities in refactorization */\n#define MAX_MINITUPDATES        60  /* Maximum number of bound swaps between refactorizations\n                                       without recomputing the whole vector - contain errors */\n#define MIN_REFACTFREQUENCY      5  /* Refactorization frequency indicating an inherent\n                                       numerical instability of the basis */\n#define LAG_SINGULARLIMIT        5  /* Number of times the objective does not change\n                                       before it is assumed that the Lagrangean constraints\n                                       are non-binding, and therefore impossible to converge;\n                                       upper iteration limit is divided by this threshold */\n#define MIN_TIMEPIVOT      5.0e-02  /* Minimum time per pivot for reinversion optimization\n                                       purposes; use active monitoring only if a pivot\n                                       takes more than MINTIMEPIVOT seconds.  5.0e-2 is\n                                       roughly suitable for a 1GHz system.  */\n#define MAX_STALLCOUNT          12  /* The absolute upper limit to the number of stalling or\n                                       cycling iterations before switching rule */\n#define MAX_RULESWITCH           5  /* The maximum number of times to try an alternate pricing rule\n                                       to recover from stalling; set negative for no limit. */\n#define DEF_TIMEDREFACT  AUTOMATIC  /* Default for timed refactorization in BFPs;\n                                       can be FALSE, TRUE or AUTOMATIC (dynamic) */\n\n#define DEF_SCALINGLIMIT         5  /* The default maximum number of scaling iterations */\n\n#define DEF_NEGRANGE      -1.0e+06  /* Downward limit for expanded variable range before the\n                                       variable is split into positive and negative components */\n#define DEF_BB_LIMITLEVEL      -50  /* Relative B&B limit to protect against very deep,\n                                       memory-consuming trees */\n\n#define MAX_FRACSCALE            6  /* The maximum decimal scan range for simulated integers */\n#define RANDSCALE              100  /* Randomization scaling range */\n#define DOUBLEROUND        0.0e-02  /* Extra rounding scalar used in btran/ftran calculations; the\n                                       rationale for 0.0 is that prod_xA() uses rounding as well */\n#define DEF_EPSMACHINE    2.22e-16  /* Machine relative precision (doubles) */\n#define MIN_STABLEPIVOT        5.0  /* Minimum pivot magnitude assumed to be numerically stable */\n\n\n/* Precision macros                                                                       */\n/* -------------------------------------------------------------------------------------- */\n#define PREC_REDUCEDCOST        lp->epsvalue\n#define PREC_IMPROVEGAP         lp->epsdual\n#define PREC_SUBSTFEASGAP       lp->epsprimal\n#if 1\n  #define PREC_BASICSOLUTION    lp->epsvalue  /* Zero-rounding of RHS/basic solution vector */\n#else\n  #define PREC_BASICSOLUTION    lp->epsmachine  /* Zero-rounding of RHS/basic solution vector */\n#endif\n#define LIMIT_ABS_REL         10.0  /* Limit for testing using relative metric */\n\n\n/* Parameters constants for short-cut setting of tolerances                           */\n/* -------------------------------------------------------------------------------------- */\n#define EPS_TIGHT                0\n#define EPS_MEDIUM               1\n#define EPS_LOOSE                2\n#define EPS_BAGGY                3\n#define EPS_DEFAULT              EPS_TIGHT\n\n\n#if ActivePARAM==ProductionPARAM    /* PARAMETER SET FOR PRODUCTION                       */\n/* -------------------------------------------------------------------------------------- */\n#define DEF_INFINITE       1.0e+30  /* Limit for dynamic range */\n#define DEF_EPSVALUE       1.0e-12  /* High accuracy and feasibility preserving tolerance */\n#define DEF_EPSPRIMAL      1.0e-10  /* For rounding primal/RHS values to 0 */\n#define DEF_EPSDUAL        1.0e-09  /* For rounding reduced costs to 0 */\n#define DEF_EPSPIVOT       2.0e-07  /* Pivot reject threshold */\n#define DEF_PERTURB        1.0e-05  /* Perturbation scalar for degenerate problems;\n                                       must at least be RANDSCALE greater than EPSPRIMAL */\n#define DEF_EPSSOLUTION    1.0e-05  /* Margin of error for solution bounds */\n#define DEF_EPSINT         1.0e-07  /* Accuracy for considering a float value as integer */\n\n#elif ActivePARAM==OriginalPARAM    /* PARAMETER SET FOR LEGACY VERSIONS                  */\n/* -------------------------------------------------------------------------------------- */\n#define DEF_INFINITE       1.0e+24  /* Limit for dynamic range */\n#define DEF_EPSVALUE       1.0e-08  /* High accuracy and feasibility preserving tolerance */\n#define DEF_EPSPRIMAL     5.01e-07  /* For rounding primal/RHS values to 0, infeasibility */\n#define DEF_EPSDUAL        1.0e-06  /* For rounding reduced costs to 0 */\n#define DEF_EPSPIVOT       1.0e-04  /* Pivot reject threshold */\n#define DEF_PERTURB        1.0e-05  /* Perturbation scalar for degenerate problems;\n                                       must at least be RANDSCALE greater than EPSPRIMAL */\n#define DEF_EPSSOLUTION    1.0e-02  /* Margin of error for solution bounds */\n#define DEF_EPSINT         1.0e-03  /* Accuracy for considering a float value as integer */\n\n#elif ActivePARAM==ChvatalPARAM     /* PARAMETER SET EXAMPLES FROM Vacek Chvatal          */\n/* -------------------------------------------------------------------------------------- */\n#define DEF_INFINITE       1.0e+30  /* Limit for dynamic range */\n#define DEF_EPSVALUE       1.0e-10  /* High accuracy and feasibility preserving tolerance */\n#define DEF_EPSPRIMAL       10e-07  /* For rounding primal/RHS values to 0 */\n#define DEF_EPSDUAL         10e-05  /* For rounding reduced costs to 0 */\n#define DEF_EPSPIVOT        10e-05  /* Pivot reject threshold */\n#define DEF_PERTURB         10e-03  /* Perturbation scalar for degenerate problems;\n                                       must at least be RANDSCALE greater than EPSPRIMAL */\n#define DEF_EPSSOLUTION    1.0e-05  /* Margin of error for solution bounds */\n#define DEF_EPSINT         5.0e-03  /* Accuracy for considering a float value as integer */\n\n#elif ActivePARAM==LoosePARAM       /* PARAMETER SET FOR LOOSE TOLERANCES                 */\n/* -------------------------------------------------------------------------------------- */\n#define DEF_INFINITE       1.0e+30  /* Limit for dynamic range */\n#define DEF_EPSVALUE       1.0e-10  /* High accuracy and feasibility preserving tolerance */\n#define DEF_EPSPRIMAL     5.01e-08  /* For rounding primal/RHS values to 0 */\n#define DEF_EPSDUAL        1.0e-07  /* For rounding reduced costs to 0 */\n#define DEF_EPSPIVOT       1.0e-05  /* Pivot reject threshold */\n#define DEF_PERTURB        1.0e-05  /* Perturbation scalar for degenerate problems;\n                                       must at least be RANDSCALE greater than EPSPRIMAL */\n#define DEF_EPSSOLUTION    1.0e-05  /* Margin of error for solution bounds */\n#define DEF_EPSINT         1.0e-04  /* Accuracy for considering a float value as integer */\n\n#endif\n\n\n#define DEF_MIP_GAP        1.0e-11  /* The default absolute and relative MIP gap */\n#define SCALEDINTFIXRANGE      1.6  /* Epsilon range multiplier < 2 for collapsing bounds to fix */\n\n#define MIN_SCALAR         1.0e-10  /* Smallest allowed scaling adjustment */\n#define MAX_SCALAR         1.0e+10  /* Largest allowed scaling adjustment */\n#define DEF_SCALINGEPS     1.0e-02  /* Relative scaling convergence criterion for auto_scale */\n\n#define DEF_LAGACCEPT      1.0e-03  /* Default Lagrangean convergence acceptance criterion */\n#define DEF_LAGCONTRACT       0.90  /* The contraction parameter for Lagrangean iterations */\n#define DEF_LAGMAXITERATIONS   100  /* The maximum number of Lagrangean iterations */\n\n#define DEF_PSEUDOCOSTUPDATES    7  /* The default number of times pseudo-costs are recalculated;\n                                       experiments indicate that costs tend to stabilize */\n#define DEF_PSEUDOCOSTRESTART 0.15  /* The fraction of price updates required for B&B restart\n                                       when the mode is NODE_RESTARTMODE */\n#define DEF_MAXPRESOLVELOOPS     0  /* Upper limit to the number of loops during presolve,\n                                       <= 0 for no limit. */\n\n\n/* Hashing prototypes and function headers                                   */\n/* ------------------------------------------------------------------------- */\n#include \"lp_Hash.h\"\n\n\n/* Sparse matrix prototypes                                                  */\n/* ------------------------------------------------------------------------- */\n#include \"lp_matrix.h\"\n\n\n/* Basis storage (mainly for B&B) */\ntypedef struct _basisrec\n{\n  int       level;\n  int       *var_basic;\n  MYBOOL    *is_basic;\n  MYBOOL    *is_lower;\n  int       pivots;\n  struct   _basisrec *previous;\n} basisrec;\n\n/* Presolve undo data storage */\ntypedef struct _presolveundorec\n{\n  lprec     *lp;\n  int       orig_rows;\n  int       orig_columns;\n  int       orig_sum;\n  int       *var_to_orig;       /* sum_alloc+1 : Mapping of variables from solution to\n                                   best_solution to account for removed variables and\n                                   rows during presolve; a non-positive value indicates\n                                   that the constraint or variable was removed */\n  int       *orig_to_var;       /* sum_alloc+1 : Mapping from original variable index to\n                                   current / working index number */\n  REAL      *fixed_rhs;         /* rows_alloc+1 : Storage of values of presolved fixed colums */\n  REAL      *fixed_obj;         /* columns_alloc+1: Storage of values of presolved fixed rows */\n  DeltaVrec *deletedA;          /* A matrix of eliminated data from matA */\n  DeltaVrec *primalundo;        /* Affine translation vectors for eliminated primal variables */\n  DeltaVrec *dualundo;          /* Affine translation vectors for eliminated dual variables */\n  MYBOOL    OFcolsdeleted;\n} presolveundorec;\n\n/* Pseudo-cost arrays used during B&B */\ntypedef struct _BBPSrec\n{\n  lprec     *lp;\n  int       pseodotype;\n  int       updatelimit;\n  int       updatesfinished;\n  REAL      restartlimit;\n  MATitem   *UPcost;\n  MATitem   *LOcost;\n  struct   _BBPSrec *secondary;\n} BBPSrec;\n\n#include \"lp_mipbb.h\"\n\n\n/* Partial pricing block data */\ntypedef struct _partialrec {\n  lprec     *lp;\n  int       blockcount;         /* ## The number of logical blocks or stages in the model */\n  int       blocknow;           /* The currently active block */\n  int       *blockend;          /* Array of column indeces giving the start of each block */\n  int       *blockpos;          /* Array of column indeces giving the start scan position */\n  MYBOOL    isrow;\n} partialrec;\n\n\n/* Specially Ordered Sets (SOS) prototypes and settings                      */\n/* ------------------------------------------------------------------------- */\n/* SOS storage structure (LINEARSEARCH is typically in the 0-10 range)       */\n#ifndef LINEARSEARCH\n#define LINEARSEARCH 0\n#endif\n\n#include \"lp_SOS.h\"\n\n\n/* Prototypes for user call-back functions                                   */\n/* ------------------------------------------------------------------------- */\ntypedef int    (__WINAPI lphandle_intfunc)(lprec *lp, void *userhandle);\ntypedef void   (__WINAPI lphandlestr_func)(lprec *lp, void *userhandle, char *buf);\ntypedef void   (__WINAPI lphandleint_func)(lprec *lp, void *userhandle, int message);\ntypedef int    (__WINAPI lphandleint_intfunc)(lprec *lp, void *userhandle, int message);\n\n\n/* API typedef definitions                                                   */\n/* ------------------------------------------------------------------------- */\ntypedef MYBOOL (__WINAPI add_column_func)(lprec *lp, REAL *column);\ntypedef MYBOOL (__WINAPI add_columnex_func)(lprec *lp, int count, REAL *column, int *rowno);\ntypedef MYBOOL (__WINAPI add_constraint_func)(lprec *lp, REAL *row, int constr_type, REAL rh);\ntypedef MYBOOL (__WINAPI add_constraintex_func)(lprec *lp, int count, REAL *row, int *colno, int constr_type, REAL rh);\ntypedef MYBOOL (__WINAPI add_lag_con_func)(lprec *lp, REAL *row, int con_type, REAL rhs);\ntypedef int (__WINAPI add_SOS_func)(lprec *lp, char *name, int sostype, int priority, int count, int *sosvars, REAL *weights);\ntypedef int (__WINAPI column_in_lp_func)(lprec *lp, REAL *column);\ntypedef lprec * (__WINAPI copy_lp_func)(lprec *lp);\ntypedef void (__WINAPI default_basis_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI del_column_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI del_constraint_func)(lprec *lp, int rownr);\ntypedef void (__WINAPI delete_lp_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI dualize_lp_func)(lprec *lp);\ntypedef void (__WINAPI free_lp_func)(lprec **plp);\ntypedef int (__WINAPI get_anti_degen_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_basis_func)(lprec *lp, int *bascolumn, MYBOOL nonbasic);\ntypedef int (__WINAPI get_basiscrash_func)(lprec *lp);\ntypedef int (__WINAPI get_bb_depthlimit_func)(lprec *lp);\ntypedef int (__WINAPI get_bb_floorfirst_func)(lprec *lp);\ntypedef int (__WINAPI get_bb_rule_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_bounds_tighter_func)(lprec *lp);\ntypedef REAL (__WINAPI get_break_at_value_func)(lprec *lp);\ntypedef char * (__WINAPI get_col_name_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI get_column_func)(lprec *lp, int colnr, REAL *column);\ntypedef int (__WINAPI get_columnex_func)(lprec *lp, int colnr, REAL *column, int *nzrow);\ntypedef int (__WINAPI get_constr_type_func)(lprec *lp, int rownr);\ntypedef REAL (__WINAPI get_constr_value_func)(lprec *lp, int rownr, int count, REAL *primsolution, int *nzindex);\ntypedef MYBOOL (__WINAPI get_constraints_func)(lprec *lp, REAL *constr);\ntypedef MYBOOL (__WINAPI get_dual_solution_func)(lprec *lp, REAL *rc);\ntypedef REAL (__WINAPI get_epsb_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epsd_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epsel_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epsint_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epsperturb_func)(lprec *lp);\ntypedef REAL (__WINAPI get_epspivot_func)(lprec *lp);\ntypedef int (__WINAPI get_improve_func)(lprec *lp);\ntypedef REAL (__WINAPI get_infinite_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_lambda_func)(lprec *lp, REAL *lambda);\ntypedef REAL (__WINAPI get_lowbo_func)(lprec *lp, int colnr);\ntypedef int (__WINAPI get_lp_index_func)(lprec *lp, int orig_index);\ntypedef char * (__WINAPI get_lp_name_func)(lprec *lp);\ntypedef int (__WINAPI get_Lrows_func)(lprec *lp);\ntypedef REAL (__WINAPI get_mat_func)(lprec *lp, int rownr, int colnr);\ntypedef REAL (__WINAPI get_mat_byindex_func)(lprec *lp, int matindex, MYBOOL isrow, MYBOOL adjustsign);\ntypedef int (__WINAPI get_max_level_func)(lprec *lp);\ntypedef int (__WINAPI get_maxpivot_func)(lprec *lp);\ntypedef REAL (__WINAPI get_mip_gap_func)(lprec *lp, MYBOOL absolute);\ntypedef int (__WINAPI get_multiprice_func)(lprec *lp, MYBOOL getabssize);\ntypedef MYBOOL (__WINAPI is_use_names_func)(lprec *lp, MYBOOL isrow);\ntypedef void (__WINAPI set_use_names_func)(lprec *lp, MYBOOL isrow, MYBOOL use_names);\ntypedef int (__WINAPI get_nameindex_func)(lprec *lp, char *varname, MYBOOL isrow);\ntypedef int (__WINAPI get_Ncolumns_func)(lprec *lp);\ntypedef REAL (__WINAPI get_negrange_func)(lprec *lp);\ntypedef int (__WINAPI get_nz_func)(lprec *lp);\ntypedef int (__WINAPI get_Norig_columns_func)(lprec *lp);\ntypedef int (__WINAPI get_Norig_rows_func)(lprec *lp);\ntypedef int (__WINAPI get_Nrows_func)(lprec *lp);\ntypedef REAL (__WINAPI get_obj_bound_func)(lprec *lp);\ntypedef REAL (__WINAPI get_objective_func)(lprec *lp);\ntypedef int (__WINAPI get_orig_index_func)(lprec *lp, int lp_index);\ntypedef char * (__WINAPI get_origcol_name_func)(lprec *lp, int colnr);\ntypedef char * (__WINAPI get_origrow_name_func)(lprec *lp, int rownr);\ntypedef void (__WINAPI get_partialprice_func)(lprec *lp, int *blockcount, int *blockstart, MYBOOL isrow);\ntypedef int (__WINAPI get_pivoting_func)(lprec *lp);\ntypedef int (__WINAPI get_presolve_func)(lprec *lp);\ntypedef int (__WINAPI get_presolveloops_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_primal_solution_func)(lprec *lp, REAL *pv);\ntypedef int (__WINAPI get_print_sol_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_pseudocosts_func)(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit);\ntypedef MYBOOL (__WINAPI get_ptr_constraints_func)(lprec *lp, REAL **constr);\ntypedef MYBOOL (__WINAPI get_ptr_dual_solution_func)(lprec *lp, REAL **rc);\ntypedef MYBOOL (__WINAPI get_ptr_lambda_func)(lprec *lp, REAL **lambda);\ntypedef MYBOOL (__WINAPI get_ptr_primal_solution_func)(lprec *lp, REAL **pv);\ntypedef MYBOOL (__WINAPI get_ptr_sensitivity_obj_func)(lprec *lp, REAL **objfrom, REAL **objtill);\ntypedef MYBOOL (__WINAPI get_ptr_sensitivity_objex_func)(lprec *lp, REAL **objfrom, REAL **objtill, REAL **objfromvalue, REAL **objtillvalue);\ntypedef MYBOOL (__WINAPI get_ptr_sensitivity_rhs_func)(lprec *lp, REAL **duals, REAL **dualsfrom, REAL **dualstill);\ntypedef MYBOOL (__WINAPI get_ptr_variables_func)(lprec *lp, REAL **var);\ntypedef REAL (__WINAPI get_rh_func)(lprec *lp, int rownr);\ntypedef REAL (__WINAPI get_rh_range_func)(lprec *lp, int rownr);\ntypedef int (__WINAPI get_rowex_func)(lprec *lp, int rownr, REAL *row, int *colno);\ntypedef MYBOOL (__WINAPI get_row_func)(lprec *lp, int rownr, REAL *row);\ntypedef char * (__WINAPI get_row_name_func)(lprec *lp, int rownr);\ntypedef REAL (__WINAPI get_scalelimit_func)(lprec *lp);\ntypedef int (__WINAPI get_scaling_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI get_sensitivity_obj_func)(lprec *lp, REAL *objfrom, REAL *objtill);\ntypedef MYBOOL (__WINAPI get_sensitivity_objex_func)(lprec *lp, REAL *objfrom, REAL *objtill, REAL *objfromvalue, REAL *objtillvalue);\ntypedef MYBOOL (__WINAPI get_sensitivity_rhs_func)(lprec *lp, REAL *duals, REAL *dualsfrom, REAL *dualstill);\ntypedef int (__WINAPI get_simplextype_func)(lprec *lp);\ntypedef int (__WINAPI get_solutioncount_func)(lprec *lp);\ntypedef int (__WINAPI get_solutionlimit_func)(lprec *lp);\ntypedef int (__WINAPI get_status_func)(lprec *lp);\ntypedef char * (__WINAPI get_statustext_func)(lprec *lp, int statuscode);\ntypedef long (__WINAPI get_timeout_func)(lprec *lp);\ntypedef COUNTER (__WINAPI get_total_iter_func)(lprec *lp);\ntypedef COUNTER (__WINAPI get_total_nodes_func)(lprec *lp);\ntypedef REAL (__WINAPI get_upbo_func)(lprec *lp, int colnr);\ntypedef int (__WINAPI get_var_branch_func)(lprec *lp, int colnr);\ntypedef REAL (__WINAPI get_var_dualresult_func)(lprec *lp, int index);\ntypedef REAL (__WINAPI get_var_primalresult_func)(lprec *lp, int index);\ntypedef int (__WINAPI get_var_priority_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI get_variables_func)(lprec *lp, REAL *var);\ntypedef int (__WINAPI get_verbose_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI guess_basis_func)(lprec *lp, REAL *guessvector, int *basisvector);\ntypedef REAL (__WINAPI get_working_objective_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI has_BFP_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI has_XLI_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_add_rowmode_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_anti_degen_func)(lprec *lp, int testmask);\ntypedef MYBOOL (__WINAPI is_binary_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_break_at_first_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_constr_type_func)(lprec *lp, int rownr, int mask);\ntypedef MYBOOL (__WINAPI is_debug_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_feasible_func)(lprec *lp, REAL *values, REAL threshold);\ntypedef MYBOOL (__WINAPI is_unbounded_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_infinite_func)(lprec *lp, REAL value);\ntypedef MYBOOL (__WINAPI is_int_func)(lprec *lp, int column);\ntypedef MYBOOL (__WINAPI is_integerscaling_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_lag_trace_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_maxim_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_nativeBFP_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_nativeXLI_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_negative_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_obj_in_basis_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI is_piv_mode_func)(lprec *lp, int testmask);\ntypedef MYBOOL (__WINAPI is_piv_rule_func)(lprec *lp, int rule);\ntypedef MYBOOL (__WINAPI is_presolve_func)(lprec *lp, int testmask);\ntypedef MYBOOL (__WINAPI is_scalemode_func)(lprec *lp, int testmask);\ntypedef MYBOOL (__WINAPI is_scaletype_func)(lprec *lp, int scaletype);\ntypedef MYBOOL (__WINAPI is_semicont_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_SOS_var_func)(lprec *lp, int colnr);\ntypedef MYBOOL (__WINAPI is_trace_func)(lprec *lp);\ntypedef void (__WINAPI lp_solve_version_func)(int *majorversion, int *minorversion, int *release, int *build);\ntypedef lprec * (__WINAPI make_lp_func)(int rows, int columns);\ntypedef void (__WINAPI print_constraints_func)(lprec *lp, int columns);\ntypedef MYBOOL (__WINAPI print_debugdump_func)(lprec *lp, char *filename);\ntypedef void (__WINAPI print_duals_func)(lprec *lp);\ntypedef void (__WINAPI print_lp_func)(lprec *lp);\ntypedef void (__WINAPI print_objective_func)(lprec *lp);\ntypedef void (__WINAPI print_scales_func)(lprec *lp);\ntypedef void (__WINAPI print_solution_func)(lprec *lp, int columns);\ntypedef void (__WINAPI print_str_func)(lprec *lp, char *str);\ntypedef void (__WINAPI print_tableau_func)(lprec *lp);\ntypedef void (__WINAPI put_abortfunc_func)(lprec *lp, lphandle_intfunc newctrlc, void *ctrlchandle);\ntypedef void (__WINAPI put_bb_nodefunc_func)(lprec *lp, lphandleint_intfunc newnode, void *bbnodehandle);\ntypedef void (__WINAPI put_bb_branchfunc_func)(lprec *lp, lphandleint_intfunc newbranch, void *bbbranchhandle);\ntypedef void (__WINAPI put_logfunc_func)(lprec *lp, lphandlestr_func newlog, void *loghandle);\ntypedef void (__WINAPI put_msgfunc_func)(lprec *lp, lphandleint_func newmsg, void *msghandle, int mask);\ntypedef lprec * (__WINAPI read_LP_func)(char *filename, int verbose, char *lp_name);\ntypedef lprec * (__WINAPI read_MPS_func)(char *filename, int options);\ntypedef lprec * (__WINAPI read_XLI_func)(char *xliname, char *modelname, char *dataname, char *options, int verbose);\ntypedef MYBOOL (__WINAPI read_basis_func)(lprec *lp, char *filename, char *info);\ntypedef void (__WINAPI reset_basis_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI read_params_func)(lprec *lp, char *filename, char *options);\ntypedef void (__WINAPI reset_params_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI resize_lp_func)(lprec *lp, int rows, int columns);\ntypedef MYBOOL (__WINAPI set_add_rowmode_func)(lprec *lp, MYBOOL turnon);\ntypedef void (__WINAPI set_anti_degen_func)(lprec *lp, int anti_degen);\ntypedef int  (__WINAPI set_basisvar_func)(lprec *lp, int basisPos, int enteringCol);\ntypedef MYBOOL (__WINAPI set_basis_func)(lprec *lp, int *bascolumn, MYBOOL nonbasic);\ntypedef void (__WINAPI set_basiscrash_func)(lprec *lp, int mode);\ntypedef void (__WINAPI set_bb_depthlimit_func)(lprec *lp, int bb_maxlevel);\ntypedef void (__WINAPI set_bb_floorfirst_func)(lprec *lp, int bb_floorfirst);\ntypedef void (__WINAPI set_bb_rule_func)(lprec *lp, int bb_rule);\ntypedef MYBOOL (__WINAPI set_BFP_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI set_binary_func)(lprec *lp, int colnr, MYBOOL must_be_bin);\ntypedef MYBOOL (__WINAPI set_bounds_func)(lprec *lp, int colnr, REAL lower, REAL upper);\ntypedef void (__WINAPI set_bounds_tighter_func)(lprec *lp, MYBOOL tighten);\ntypedef void (__WINAPI set_break_at_first_func)(lprec *lp, MYBOOL break_at_first);\ntypedef void (__WINAPI set_break_at_value_func)(lprec *lp, REAL break_at_value);\ntypedef MYBOOL (__WINAPI set_column_func)(lprec *lp, int colnr, REAL *column);\ntypedef MYBOOL (__WINAPI set_columnex_func)(lprec *lp, int colnr, int count, REAL *column, int *rowno);\ntypedef MYBOOL (__WINAPI set_col_name_func)(lprec *lp, int colnr, char *new_name);\ntypedef MYBOOL (__WINAPI set_constr_type_func)(lprec *lp, int rownr, int con_type);\ntypedef void (__WINAPI set_debug_func)(lprec *lp, MYBOOL debug);\ntypedef void (__WINAPI set_epsb_func)(lprec *lp, REAL epsb);\ntypedef void (__WINAPI set_epsd_func)(lprec *lp, REAL epsd);\ntypedef void (__WINAPI set_epsel_func)(lprec *lp, REAL epsel);\ntypedef void (__WINAPI set_epsint_func)(lprec *lp, REAL epsint);\ntypedef MYBOOL (__WINAPI set_epslevel_func)(lprec *lp, int epslevel);\ntypedef void (__WINAPI set_epsperturb_func)(lprec *lp, REAL epsperturb);\ntypedef void (__WINAPI set_epspivot_func)(lprec *lp, REAL epspivot);\ntypedef MYBOOL (__WINAPI set_unbounded_func)(lprec *lp, int colnr);\ntypedef void (__WINAPI set_improve_func)(lprec *lp, int improve);\ntypedef void (__WINAPI set_infinite_func)(lprec *lp, REAL infinite);\ntypedef MYBOOL (__WINAPI set_int_func)(lprec *lp, int colnr, MYBOOL must_be_int);\ntypedef void (__WINAPI set_lag_trace_func)(lprec *lp, MYBOOL lag_trace);\ntypedef MYBOOL (__WINAPI set_lowbo_func)(lprec *lp, int colnr, REAL value);\ntypedef MYBOOL (__WINAPI set_lp_name_func)(lprec *lp, char *lpname);\ntypedef MYBOOL (__WINAPI set_mat_func)(lprec *lp, int row, int column, REAL value);\ntypedef void (__WINAPI set_maxim_func)(lprec *lp);\ntypedef void (__WINAPI set_maxpivot_func)(lprec *lp, int max_num_inv);\ntypedef void (__WINAPI set_minim_func)(lprec *lp);\ntypedef void (__WINAPI set_mip_gap_func)(lprec *lp, MYBOOL absolute, REAL mip_gap);\ntypedef MYBOOL (__WINAPI set_multiprice_func)(lprec *lp, int multiblockdiv);\ntypedef void (__WINAPI set_negrange_func)(lprec *lp, REAL negrange);\ntypedef MYBOOL (__WINAPI set_obj_func)(lprec *lp, int colnr, REAL value);\ntypedef void (__WINAPI set_obj_bound_func)(lprec *lp, REAL obj_bound);\ntypedef MYBOOL (__WINAPI set_obj_fn_func)(lprec *lp, REAL *row);\ntypedef MYBOOL (__WINAPI set_obj_fnex_func)(lprec *lp, int count, REAL *row, int *colno);\ntypedef void (__WINAPI set_obj_in_basis_func)(lprec *lp, MYBOOL obj_in_basis);\ntypedef MYBOOL (__WINAPI set_outputfile_func)(lprec *lp, char *filename);\ntypedef void (__WINAPI set_outputstream_func)(lprec *lp, FILE *stream);\ntypedef MYBOOL (__WINAPI set_partialprice_func)(lprec *lp, int blockcount, int *blockstart, MYBOOL isrow);\ntypedef void (__WINAPI set_pivoting_func)(lprec *lp, int piv_rule);\ntypedef void (__WINAPI set_preferdual_func)(lprec *lp, MYBOOL dodual);\ntypedef void (__WINAPI set_presolve_func)(lprec *lp, int presolvemode, int maxloops);\ntypedef void (__WINAPI set_print_sol_func)(lprec *lp, int print_sol);\ntypedef MYBOOL (__WINAPI set_pseudocosts_func)(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit);\ntypedef MYBOOL (__WINAPI set_rh_func)(lprec *lp, int rownr, REAL value);\ntypedef MYBOOL (__WINAPI set_rh_range_func)(lprec *lp, int rownr, REAL deltavalue);\ntypedef void (__WINAPI set_rh_vec_func)(lprec *lp, REAL *rh);\ntypedef MYBOOL (__WINAPI set_row_func)(lprec *lp, int rownr, REAL *row);\ntypedef MYBOOL (__WINAPI set_rowex_func)(lprec *lp, int rownr, int count, REAL *row, int *colno);\ntypedef MYBOOL (__WINAPI set_row_name_func)(lprec *lp, int rownr, char *new_name);\ntypedef void (__WINAPI set_scalelimit_func)(lprec *lp, REAL scalelimit);\ntypedef void (__WINAPI set_scaling_func)(lprec *lp, int scalemode);\ntypedef MYBOOL (__WINAPI set_semicont_func)(lprec *lp, int colnr, MYBOOL must_be_sc);\ntypedef void (__WINAPI set_sense_func)(lprec *lp, MYBOOL maximize);\ntypedef void (__WINAPI set_simplextype_func)(lprec *lp, int simplextype);\ntypedef void (__WINAPI set_solutionlimit_func)(lprec *lp, int limit);\ntypedef void (__WINAPI set_timeout_func)(lprec *lp, long sectimeout);\ntypedef void (__WINAPI set_trace_func)(lprec *lp, MYBOOL trace);\ntypedef MYBOOL (__WINAPI set_upbo_func)(lprec *lp, int colnr, REAL value);\ntypedef MYBOOL (__WINAPI set_var_branch_func)(lprec *lp, int colnr, int branch_mode);\ntypedef MYBOOL (__WINAPI set_var_weights_func)(lprec *lp, REAL *weights);\ntypedef void (__WINAPI set_verbose_func)(lprec *lp, int verbose);\ntypedef MYBOOL (__WINAPI set_XLI_func)(lprec *lp, char *filename);\ntypedef int (__WINAPI solve_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI str_add_column_func)(lprec *lp, char *col_string);\ntypedef MYBOOL (__WINAPI str_add_constraint_func)(lprec *lp, char *row_string ,int constr_type, REAL rh);\ntypedef MYBOOL (__WINAPI str_add_lag_con_func)(lprec *lp, char *row_string, int con_type, REAL rhs);\ntypedef MYBOOL (__WINAPI str_set_obj_fn_func)(lprec *lp, char *row_string);\ntypedef MYBOOL (__WINAPI str_set_rh_vec_func)(lprec *lp, char *rh_string);\ntypedef REAL (__WINAPI time_elapsed_func)(lprec *lp);\ntypedef void (__WINAPI unscale_func)(lprec *lp);\ntypedef MYBOOL (__WINAPI write_lp_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI write_LP_func)(lprec *lp, FILE *output);\ntypedef MYBOOL (__WINAPI write_mps_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI write_MPS_func)(lprec *lp, FILE *output);\ntypedef MYBOOL (__WINAPI write_freemps_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI write_freeMPS_func)(lprec *lp, FILE *output);\ntypedef MYBOOL (__WINAPI write_XLI_func)(lprec *lp, char *filename, char *options, MYBOOL results);\ntypedef MYBOOL (__WINAPI write_basis_func)(lprec *lp, char *filename);\ntypedef MYBOOL (__WINAPI write_params_func)(lprec *lp, char *filename, char *options);\n\n\n/* Prototypes for callbacks from basis inverse/factorization libraries       */\n/* ------------------------------------------------------------------------- */\ntypedef MYBOOL (__WINAPI userabortfunc)(lprec *lp, int level);\ntypedef void   (__VACALL reportfunc)(lprec *lp, int level, char *format, ...);\ntypedef char * (__VACALL explainfunc)(lprec *lp, char *format, ...);\ntypedef int    (__WINAPI getvectorfunc)(lprec *lp, int varin, REAL *pcol, int *nzlist, int *maxabs);\ntypedef int    (__WINAPI getpackedfunc)(lprec *lp, int j, int rn[], double bj[]);\ntypedef REAL    (__WINAPI get_OF_activefunc)(lprec *lp, int varnr, REAL mult);\ntypedef int    (__WINAPI getMDOfunc)(lprec *lp, MYBOOL *usedpos, int *colorder, int *size, MYBOOL symmetric);\ntypedef MYBOOL (__WINAPI invertfunc)(lprec *lp, MYBOOL shiftbounds, MYBOOL final);\ntypedef void   (__WINAPI set_actionfunc)(int *actionvar, int actionmask);\ntypedef MYBOOL (__WINAPI is_actionfunc)(int actionvar, int testmask);\ntypedef void   (__WINAPI clear_actionfunc)(int *actionvar, int actionmask);\n\n\n/* Prototypes for basis inverse/factorization libraries                      */\n/* ------------------------------------------------------------------------- */\ntypedef char   *(BFP_CALLMODEL BFPchar)(void);\ntypedef void   (BFP_CALLMODEL BFP_lp)(lprec *lp);\ntypedef void   (BFP_CALLMODEL BFP_lpint)(lprec *lp, int newsize);\ntypedef int    (BFP_CALLMODEL BFPint_lp)(lprec *lp);\ntypedef int    (BFP_CALLMODEL BFPint_lpint)(lprec *lp, int kind);\ntypedef REAL   (BFP_CALLMODEL BFPreal_lp)(lprec *lp);\ntypedef REAL   *(BFP_CALLMODEL BFPrealp_lp)(lprec *lp);\ntypedef void   (BFP_CALLMODEL BFP_lpbool)(lprec *lp, MYBOOL maximum);\ntypedef int    (BFP_CALLMODEL BFPint_lpbool)(lprec *lp, MYBOOL maximum);\ntypedef int    (BFP_CALLMODEL BFPint_lpintintboolbool)(lprec *lp, int uservars, int Bsize, MYBOOL *usedpos, MYBOOL final);\ntypedef void   (BFP_CALLMODEL BFP_lprealint)(lprec *lp, REAL *pcol, int *nzidx);\ntypedef void   (BFP_CALLMODEL BFP_lprealintrealint)(lprec *lp, REAL *prow, int *pnzidx, REAL *drow, int *dnzidx);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lp)(lprec *lp);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lpbool)(lprec *lp, MYBOOL changesign);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lpint)(lprec *lp, int size);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lpintintchar)(lprec *lp, int size, int deltasize, char *options);\ntypedef MYBOOL (BFP_CALLMODEL BFPbool_lpintintint)(lprec *lp, int size, int deltasize, int sizeofvar);\ntypedef LREAL  (BFP_CALLMODEL BFPlreal_lpintintreal)(lprec *lp, int row_nr, int col_nr, REAL *pcol);\ntypedef REAL   (BFP_CALLMODEL BFPreal_lplrealreal)(lprec *lp, LREAL theta, REAL *pcol);\n\ntypedef int    (BFP_CALLMODEL getcolumnex_func)(lprec *lp, int colnr, REAL *nzvalues, int *nzrows, int *mapin);\ntypedef int    (BFP_CALLMODEL BFPint_lpintrealcbintint)(lprec *lp, int items, getcolumnex_func cb, int *maprow, int*mapcol);\n\n/* Prototypes for external language libraries                                */\n/* ------------------------------------------------------------------------- */\ntypedef char   *(XLI_CALLMODEL XLIchar)(void);\ntypedef MYBOOL (XLI_CALLMODEL XLIbool_lpintintint)(lprec* lp, int size, int deltasize, int sizevar);\ntypedef MYBOOL (XLI_CALLMODEL XLIbool_lpcharcharcharint)(lprec *lp, char *modelname, char *dataname, char *options, int verbose);\ntypedef MYBOOL (XLI_CALLMODEL XLIbool_lpcharcharbool)(lprec *lp, char *filename, char *options, MYBOOL results);\n\n\n/* Main lp_solve prototypes and function definitions                         */\n/* ------------------------------------------------------------------------- */\nstruct _lprec\n{\n  /* Full list of exported functions made available in a quasi object-oriented fashion */\n  add_column_func               *add_column;\n  add_columnex_func             *add_columnex;\n  add_constraint_func           *add_constraint;\n  add_constraintex_func         *add_constraintex;\n  add_lag_con_func              *add_lag_con;\n  add_SOS_func                  *add_SOS;\n  column_in_lp_func             *column_in_lp;\n  copy_lp_func                  *copy_lp;\n  default_basis_func            *default_basis;\n  del_column_func               *del_column;\n  del_constraint_func           *del_constraint;\n  delete_lp_func                *delete_lp;\n  dualize_lp_func               *dualize_lp;\n  free_lp_func                  *free_lp;\n  get_anti_degen_func           *get_anti_degen;\n  get_basis_func                *get_basis;\n  get_basiscrash_func           *get_basiscrash;\n  get_bb_depthlimit_func        *get_bb_depthlimit;\n  get_bb_floorfirst_func        *get_bb_floorfirst;\n  get_bb_rule_func              *get_bb_rule;\n  get_bounds_tighter_func       *get_bounds_tighter;\n  get_break_at_value_func       *get_break_at_value;\n  get_col_name_func             *get_col_name;\n  get_columnex_func             *get_columnex;\n  get_constr_type_func          *get_constr_type;\n  get_constr_value_func         *get_constr_value;\n  get_constraints_func          *get_constraints;\n  get_dual_solution_func        *get_dual_solution;\n  get_epsb_func                 *get_epsb;\n  get_epsd_func                 *get_epsd;\n  get_epsel_func                *get_epsel;\n  get_epsint_func               *get_epsint;\n  get_epsperturb_func           *get_epsperturb;\n  get_epspivot_func             *get_epspivot;\n  get_improve_func              *get_improve;\n  get_infinite_func             *get_infinite;\n  get_lambda_func               *get_lambda;\n  get_lowbo_func                *get_lowbo;\n  get_lp_index_func             *get_lp_index;\n  get_lp_name_func              *get_lp_name;\n  get_Lrows_func                *get_Lrows;\n  get_mat_func                  *get_mat;\n  get_mat_byindex_func          *get_mat_byindex;\n  get_max_level_func            *get_max_level;\n  get_maxpivot_func             *get_maxpivot;\n  get_mip_gap_func              *get_mip_gap;\n  get_multiprice_func           *get_multiprice;\n  get_nameindex_func            *get_nameindex;\n  get_Ncolumns_func             *get_Ncolumns;\n  get_negrange_func             *get_negrange;\n  get_nz_func                   *get_nonzeros;\n  get_Norig_columns_func        *get_Norig_columns;\n  get_Norig_rows_func           *get_Norig_rows;\n  get_Nrows_func                *get_Nrows;\n  get_obj_bound_func            *get_obj_bound;\n  get_objective_func            *get_objective;\n  get_orig_index_func           *get_orig_index;\n  get_origcol_name_func         *get_origcol_name;\n  get_origrow_name_func         *get_origrow_name;\n  get_partialprice_func         *get_partialprice;\n  get_pivoting_func             *get_pivoting;\n  get_presolve_func             *get_presolve;\n  get_presolveloops_func        *get_presolveloops;\n  get_primal_solution_func      *get_primal_solution;\n  get_print_sol_func            *get_print_sol;\n  get_pseudocosts_func          *get_pseudocosts;\n  get_ptr_constraints_func      *get_ptr_constraints;\n  get_ptr_dual_solution_func    *get_ptr_dual_solution;\n  get_ptr_lambda_func           *get_ptr_lambda;\n  get_ptr_primal_solution_func  *get_ptr_primal_solution;\n  get_ptr_sensitivity_obj_func  *get_ptr_sensitivity_obj;\n  get_ptr_sensitivity_objex_func *get_ptr_sensitivity_objex;\n  get_ptr_sensitivity_rhs_func  *get_ptr_sensitivity_rhs;\n  get_ptr_variables_func        *get_ptr_variables;\n  get_rh_func                   *get_rh;\n  get_rh_range_func             *get_rh_range;\n  get_row_func                  *get_row;\n  get_rowex_func                *get_rowex;\n  get_row_name_func             *get_row_name;\n  get_scalelimit_func           *get_scalelimit;\n  get_scaling_func              *get_scaling;\n  get_sensitivity_obj_func      *get_sensitivity_obj;\n  get_sensitivity_objex_func    *get_sensitivity_objex;\n  get_sensitivity_rhs_func      *get_sensitivity_rhs;\n  get_simplextype_func          *get_simplextype;\n  get_solutioncount_func        *get_solutioncount;\n  get_solutionlimit_func        *get_solutionlimit;\n  get_status_func               *get_status;\n  get_statustext_func           *get_statustext;\n  get_timeout_func              *get_timeout;\n  get_total_iter_func           *get_total_iter;\n  get_total_nodes_func          *get_total_nodes;\n  get_upbo_func                 *get_upbo;\n  get_var_branch_func           *get_var_branch;\n  get_var_dualresult_func       *get_var_dualresult;\n  get_var_primalresult_func     *get_var_primalresult;\n  get_var_priority_func         *get_var_priority;\n  get_variables_func            *get_variables;\n  get_verbose_func              *get_verbose;\n  get_working_objective_func    *get_working_objective;\n  has_BFP_func                  *has_BFP;\n  has_XLI_func                  *has_XLI;\n  is_add_rowmode_func           *is_add_rowmode;\n  is_anti_degen_func            *is_anti_degen;\n  is_binary_func                *is_binary;\n  is_break_at_first_func        *is_break_at_first;\n  is_constr_type_func           *is_constr_type;\n  is_debug_func                 *is_debug;\n  is_feasible_func              *is_feasible;\n  is_infinite_func              *is_infinite;\n  is_int_func                   *is_int;\n  is_integerscaling_func        *is_integerscaling;\n  is_lag_trace_func             *is_lag_trace;\n  is_maxim_func                 *is_maxim;\n  is_nativeBFP_func             *is_nativeBFP;\n  is_nativeXLI_func             *is_nativeXLI;\n  is_negative_func              *is_negative;\n  is_obj_in_basis_func          *is_obj_in_basis;\n  is_piv_mode_func              *is_piv_mode;\n  is_piv_rule_func              *is_piv_rule;\n  is_presolve_func              *is_presolve;\n  is_scalemode_func             *is_scalemode;\n  is_scaletype_func             *is_scaletype;\n  is_semicont_func              *is_semicont;\n  is_SOS_var_func               *is_SOS_var;\n  is_trace_func                 *is_trace;\n  is_unbounded_func             *is_unbounded;\n  is_use_names_func             *is_use_names;\n  lp_solve_version_func         *lp_solve_version;\n  make_lp_func                  *make_lp;\n  print_constraints_func        *print_constraints;\n  print_debugdump_func          *print_debugdump;\n  print_duals_func              *print_duals;\n  print_lp_func                 *print_lp;\n  print_objective_func          *print_objective;\n  print_scales_func             *print_scales;\n  print_solution_func           *print_solution;\n  print_str_func                *print_str;\n  print_tableau_func            *print_tableau;\n  put_abortfunc_func            *put_abortfunc;\n  put_bb_nodefunc_func          *put_bb_nodefunc;\n  put_bb_branchfunc_func        *put_bb_branchfunc;\n  put_logfunc_func              *put_logfunc;\n  put_msgfunc_func              *put_msgfunc;\n  read_LP_func                  *read_LP;\n  read_MPS_func                 *read_MPS;\n  read_XLI_func                 *read_XLI;\n  read_params_func              *read_params;\n  read_basis_func               *read_basis;\n  reset_basis_func              *reset_basis;\n  reset_params_func             *reset_params;\n  resize_lp_func                *resize_lp;\n  set_add_rowmode_func          *set_add_rowmode;\n  set_anti_degen_func           *set_anti_degen;\n  set_basisvar_func             *set_basisvar;\n  set_basis_func                *set_basis;\n  set_basiscrash_func           *set_basiscrash;\n  set_bb_depthlimit_func        *set_bb_depthlimit;\n  set_bb_floorfirst_func        *set_bb_floorfirst;\n  set_bb_rule_func              *set_bb_rule;\n  set_BFP_func                  *set_BFP;\n  set_binary_func               *set_binary;\n  set_bounds_func               *set_bounds;\n  set_bounds_tighter_func       *set_bounds_tighter;\n  set_break_at_first_func       *set_break_at_first;\n  set_break_at_value_func       *set_break_at_value;\n  set_column_func               *set_column;\n  set_columnex_func             *set_columnex;\n  set_col_name_func             *set_col_name;\n  set_constr_type_func          *set_constr_type;\n  set_debug_func                *set_debug;\n  set_epsb_func                 *set_epsb;\n  set_epsd_func                 *set_epsd;\n  set_epsel_func                *set_epsel;\n  set_epsint_func               *set_epsint;\n  set_epslevel_func             *set_epslevel;\n  set_epsperturb_func           *set_epsperturb;\n  set_epspivot_func             *set_epspivot;\n  set_unbounded_func            *set_unbounded;\n  set_improve_func              *set_improve;\n  set_infinite_func             *set_infinite;\n  set_int_func                  *set_int;\n  set_lag_trace_func            *set_lag_trace;\n  set_lowbo_func                *set_lowbo;\n  set_lp_name_func              *set_lp_name;\n  set_mat_func                  *set_mat;\n  set_maxim_func                *set_maxim;\n  set_maxpivot_func             *set_maxpivot;\n  set_minim_func                *set_minim;\n  set_mip_gap_func              *set_mip_gap;\n  set_multiprice_func           *set_multiprice;\n  set_negrange_func             *set_negrange;\n  set_obj_bound_func            *set_obj_bound;\n  set_obj_fn_func               *set_obj_fn;\n  set_obj_fnex_func             *set_obj_fnex;\n  set_obj_func                  *set_obj;\n  set_obj_in_basis_func         *set_obj_in_basis;\n  set_outputfile_func           *set_outputfile;\n  set_outputstream_func         *set_outputstream;\n  set_partialprice_func         *set_partialprice;\n  set_pivoting_func             *set_pivoting;\n  set_preferdual_func           *set_preferdual;\n  set_presolve_func             *set_presolve;\n  set_print_sol_func            *set_print_sol;\n  set_pseudocosts_func          *set_pseudocosts;\n  set_rh_func                   *set_rh;\n  set_rh_range_func             *set_rh_range;\n  set_rh_vec_func               *set_rh_vec;\n  set_row_func                  *set_row;\n  set_rowex_func                *set_rowex;\n  set_row_name_func             *set_row_name;\n  set_scalelimit_func           *set_scalelimit;\n  set_scaling_func              *set_scaling;\n  set_semicont_func             *set_semicont;\n  set_sense_func                *set_sense;\n  set_simplextype_func          *set_simplextype;\n  set_solutionlimit_func        *set_solutionlimit;\n  set_timeout_func              *set_timeout;\n  set_trace_func                *set_trace;\n  set_upbo_func                 *set_upbo;\n  set_use_names_func            *set_use_names;\n  set_var_branch_func           *set_var_branch;\n  set_var_weights_func          *set_var_weights;\n  set_verbose_func              *set_verbose;\n  set_XLI_func                  *set_XLI;\n  solve_func                    *solve;\n  str_add_column_func           *str_add_column;\n  str_add_constraint_func       *str_add_constraint;\n  str_add_lag_con_func          *str_add_lag_con;\n  str_set_obj_fn_func           *str_set_obj_fn;\n  str_set_rh_vec_func           *str_set_rh_vec;\n  time_elapsed_func             *time_elapsed;\n  unscale_func                  *unscale;\n  write_lp_func                 *write_lp;\n  write_LP_func                 *write_LP;\n  write_mps_func                *write_mps;\n  write_MPS_func                *write_MPS;\n  write_freemps_func            *write_freemps;\n  write_freeMPS_func            *write_freeMPS;\n  write_XLI_func                *write_XLI;\n  write_basis_func              *write_basis;\n  write_params_func             *write_params;\n\n  /* Spacer */\n  int       *alignmentspacer;\n\n  /* Problem description */\n  char      *lp_name;           /* The name of the model */\n\n  /* Problem sizes */\n  int       sum;                /* The total number of variables, including slacks */\n  int       rows;\n  int       columns;\n  int       equalities;         /* No of non-Lagrangean equality constraints in the problem */\n  int       boundedvars;        /* Count of bounded variables */\n  int       INTfuture1;\n\n  /* Memory allocation sizes */\n  int       sum_alloc;          /* The allocated memory for row+column-sized data */\n  int       rows_alloc;         /* The allocated memory for row-sized data */\n  int       columns_alloc;      /* The allocated memory for column-sized data */\n\n  /* Model status and solver result variables */\n  MYBOOL    source_is_file;     /* The base model was read from a file */\n  MYBOOL    model_is_pure;      /* The model has been built entirely from row and column additions */\n  MYBOOL    model_is_valid;     /* Has this lp pased the 'test' */\n  MYBOOL    tighten_on_set;     /* Specify if bounds will be tightened or overriden at bound setting */\n  MYBOOL    names_used;         /* Flag to indicate if names for rows and columns are used */\n  MYBOOL    use_row_names;      /* Flag to indicate if names for rows are used */\n  MYBOOL    use_col_names;      /* Flag to indicate if names for columns are used */\n\n  MYBOOL    lag_trace;          /* Print information on Lagrange progression */\n  MYBOOL    spx_trace;          /* Print information on simplex progression */\n  MYBOOL    bb_trace;           /* TRUE to print extra debug information */\n  MYBOOL    streamowned;        /* TRUE if the handle should be closed at delete_lp() */\n  MYBOOL    obj_in_basis;       /* TRUE if the objective function is in the basis matrix */\n\n  int       spx_status;         /* Simplex solver feasibility/mode code */\n  int       lag_status;         /* Extra status variable for lag_solve */\n  int       solutioncount;      /* number of equal-valued solutions found (up to solutionlimit) */\n  int       solutionlimit;      /* upper number of equal-valued solutions kept track of */\n\n  REAL      real_solution;      /* Optimal non-MIP solution base */\n  REAL      *solution;          /* sum_alloc+1 : Solution array of the next to optimal LP,\n                                   Index   0           : Objective function value,\n                                   Indeces 1..rows     : Slack variable values,\n                                   Indeced rows+1..sum : Variable values */\n  REAL      *best_solution;     /* sum_alloc+1 : Solution array of optimal 'Integer' LP,\n                                   structured as the solution array above */\n  REAL      *full_solution;     /* sum_alloc+1 : Final solution array expanded for deleted variables */\n  REAL      *edgeVector;        /* Array of reduced cost scaling norms (DEVEX and Steepest Edge) */\n\n  REAL      *drow;              /* sum+1: Reduced costs of the last simplex */\n  int       *nzdrow;            /* sum+1: Indeces of non-zero reduced costs of the last simplex */\n  REAL      *duals;             /* rows_alloc+1 : The dual variables of the last LP */\n  REAL      *full_duals;        /* sum_alloc+1: Final duals array expanded for deleted variables */\n  REAL      *dualsfrom;         /* sum_alloc+1 :The sensitivity on dual variables/reduced costs\n                                   of the last LP */\n  REAL      *dualstill;         /* sum_alloc+1 :The sensitivity on dual variables/reduced costs\n                                   of the last LP */\n  REAL      *objfrom;           /* columns_alloc+1 :The sensitivity on objective function\n                                   of the last LP */\n  REAL      *objtill;           /* columns_alloc+1 :The sensitivity on objective function\n                                   of the last LP */\n  REAL      *objfromvalue;      /* columns_alloc+1 :The value of the variables when objective value\n                                   is at its from value of the last LP */\n  REAL      *orig_obj;          /* Unused pointer - Placeholder for OF not part of B */\n  REAL      *obj;               /* Special vector used to temporarily change the OF vector */\n\n  COUNTER   current_iter;       /* Number of iterations in the current/last simplex */\n  COUNTER   total_iter;         /* Number of iterations over all B&B steps */\n  COUNTER   current_bswap;      /* Number of bound swaps in the current/last simplex */\n  COUNTER   total_bswap;        /* Number of bount swaps over all B&B steps */\n  int       solvecount;         /* The number of solve() performed in this model */\n  int       max_pivots;         /* Number of pivots between refactorizations of the basis */\n\n  /* Various execution parameters */\n  int       simplex_strategy;   /* Set desired combination of primal and dual simplex algorithms */\n  int       simplex_mode;       /* Specifies the current simplex mode during solve; see simplex_strategy */\n  int       verbose;            /* Set amount of run-time messages and results */\n  int       print_sol;          /* TRUE to print optimal solution; AUTOMATIC skips zeros */\n  FILE      *outstream;         /* Output stream, initialized to STDOUT */\n\n  /* Main Branch and Bound settings */\n  MYBOOL    *bb_varbranch;      /* Determines branching strategy at the individual variable level;\n                                   the setting here overrides the bb_floorfirst setting */\n  int       piv_strategy;       /* Strategy for selecting row and column entering/leaving */\n  int       _piv_rule_;         /* Internal working rule-part of piv_strategy above */\n  int       bb_rule;            /* Rule for selecting B&B variables */\n  MYBOOL    bb_floorfirst;      /* Set BRANCH_FLOOR for B&B to set variables to floor bound first;\n                                   conversely with BRANCH_CEILING, the ceiling value is set first */\n  MYBOOL    bb_breakfirst;      /* TRUE to stop at first feasible solution */\n  MYBOOL    _piv_left_;         /* Internal variable indicating active pricing loop order */\n  MYBOOL    BOOLfuture1;\n\n  REAL      scalelimit;         /* Relative convergence criterion for iterated scaling */\n  int       scalemode;          /* OR-ed codes for data scaling */\n  int       improve;            /* Set to non-zero for iterative improvement */\n  int       anti_degen;         /* Anti-degen strategy (or none) TRUE to avoid cycling */\n  int       do_presolve;        /* PRESOLVE_ parameters for LP presolving */\n  int       presolveloops;      /* Maximum number of presolve loops */\n\n  int       perturb_count;      /* The number of bound relaxation retries performed */\n\n  /* Row and column names storage variables */\n  hashelem  **row_name;         /* rows_alloc+1 */\n  hashelem  **col_name;         /* columns_alloc+1 */\n  hashtable *rowname_hashtab;   /* hash table to store row names */\n  hashtable *colname_hashtab;   /* hash table to store column names */\n\n  /* Optionally specify continuous rows/column blocks for partial pricing */\n  partialrec *rowblocks;\n  partialrec *colblocks;\n\n  /* Row and column type codes */\n  MYBOOL    *var_type;          /* sum_alloc+1 : TRUE if variable must be integer */\n\n  /* Data for multiple pricing */\n  multirec  *multivars;\n  int       multiblockdiv;      /* The divisor used to set or augment pricing block */\n\n  /* Variable (column) parameters */\n  int       fixedvars;          /* The current number of basic fixed variables in the model */\n  int       int_vars;           /* Number of variables required to be integer */\n\n  int       sc_vars;            /* Number of semi-continuous variables */\n  REAL      *sc_lobound;        /* sum_columns+1 : TRUE if variable is semi-continuous;\n                                   value replaced by conventional lower bound during solve */\n  int       *var_is_free;       /* columns+1: Index of twin variable if variable is free */\n  int       *var_priority;      /* columns: Priority-mapping of variables */\n\n  SOSgroup  *GUB;               /* Pointer to record containing GUBs */\n\n  int       sos_vars;           /* Number of variables in the sos_priority list */\n  int       sos_ints;           /* Number of integers in SOS'es above */\n  SOSgroup  *SOS;               /* Pointer to record containing all SOS'es */\n  int       *sos_priority;      /* Priority-sorted list of variables (no duplicates) */\n\n  /* Optionally specify list of active rows/columns used in multiple pricing */\n  REAL      *bsolveVal;         /* rows+1: bsolved solution vector for reduced costs */\n  int       *bsolveIdx;         /* rows+1: Non-zero indeces of bsolveVal */\n\n  /* RHS storage */\n  REAL      *orig_rhs;          /* rows_alloc+1 : The RHS after scaling and sign\n                                   changing, but before 'Bound transformation' */\n  LREAL     *rhs;               /* rows_alloc+1 : The RHS of the current simplex tableau */\n\n  /* Row (constraint) parameters */\n  int       *row_type;          /* rows_alloc+1 : Row/constraint type coding */\n\n  /* Optionally specify data for dual long-step */\n  multirec  *longsteps;\n\n  /* Original and working row and variable bounds */\n  REAL      *orig_upbo;         /* sum_alloc+1 : Bound before transformations */\n  REAL      *upbo;              /*  \" \" : Upper bound after transformation and B&B work */\n  REAL      *orig_lowbo;        /*  \"       \"                                 */\n  REAL      *lowbo;             /*  \" \" : Lower bound after transformation and B&B work */\n\n  /* User data and basis factorization matrices (ETA or LU, product form) */\n  MATrec    *matA;\n  INVrec    *invB;\n\n  /* Basis and bounds */\n  BBrec     *bb_bounds;         /* The linked list of B&B bounds */\n  BBrec     *rootbounds;        /* The bounds at the lowest B&B level */\n  basisrec  *bb_basis;          /* The linked list of B&B bases */\n  basisrec  *rootbasis;\n  OBJmonrec *monitor;           /* Objective monitoring record for stalling/degeneracy handling */\n\n  /* Scaling parameters */\n  REAL      *scalars;           /* sum_alloc+1:0..Rows the scaling of the rows,\n                                   Rows+1..Sum the scaling of the columns */\n  MYBOOL    scaling_used;       /* TRUE if scaling is used */\n  MYBOOL    columns_scaled;     /* TRUE if the columns are scaled too */\n  MYBOOL    varmap_locked;      /* Determines whether the var_to_orig and orig_to_var are fixed */\n\n  /* Variable state information */\n  MYBOOL    basis_valid;        /* TRUE is the basis is still valid */\n  int       crashmode;          /* Basis crashing mode (or none) */\n  int       *var_basic;         /* rows_alloc+1: The list of columns in the basis */\n  REAL      *val_nonbasic;      /* Array to store current values of non-basic variables */\n  MYBOOL    *is_basic;          /* sum_alloc+1: TRUE if the column is in the basis */\n  MYBOOL    *is_lower;          /*  \"       \" : TRUE if the variable is at its\n                                   lower bound (or in the basis), FALSE otherwise */\n\n  /* Simplex basis indicators */\n  int       *rejectpivot;       /* List of unacceptable pivot choices due to division-by-zero */\n  BBPSrec   *bb_PseudoCost;     /* Data structure for costing of node branchings */\n  int       bb_PseudoUpdates;   /* Maximum number of updates for pseudo-costs */\n  int       bb_strongbranches;  /* The number of strong B&B branches performed */\n  int       is_strongbranch;    /* Are we currently in a strong branch mode? */\n  int       bb_improvements;    /* The number of discrete B&B objective improvement steps */\n\n  /* Solver working variables */\n  REAL      rhsmax;             /* The maximum |value| of the rhs vector at any iteration */\n  REAL      suminfeas;          /* The working sum of primal and dual infeasibilities */\n  REAL      bigM;               /* Original objective weighting in primal phase 1 */\n  REAL      P1extraVal;         /* Phase 1 OF/RHS offset for feasibility */\n  int       P1extraDim;         /* Phase 1 additional columns/rows for feasibility */\n  int       spx_action;         /* ACTION_ variables for the simplex routine */\n  MYBOOL    spx_perturbed;      /* The variable bounds were relaxed/perturbed into this simplex */\n  MYBOOL    bb_break;           /* Solver working variable; signals break of the B&B */\n  MYBOOL    wasPreprocessed;    /* The solve preprocessing was performed */\n  MYBOOL    wasPresolved;       /* The solve presolver was invoked */\n  int      INTfuture2;\n\n  /* Lagragean solver storage and parameters */\n  MATrec    *matL;\n  REAL      *lag_rhs;           /* Array of Lagrangean rhs vector */\n  int       *lag_con_type;      /* Array of GT, LT or EQ */\n  REAL      *lambda;            /* Lambda values (Lagrangean multipliers) */\n  REAL      lag_bound;          /* The Lagrangian lower OF bound */\n  REAL      lag_accept;         /* The Lagrangian convergence criterion */\n\n  /* Solver thresholds */\n  REAL      infinite;           /* Limit for dynamic range */\n  REAL      negrange;           /* Limit for negative variable range */\n  REAL      epsmachine;         /* Default machine accuracy */\n  REAL      epsvalue;           /* Input data precision / rounding of data values to 0 */\n  REAL      epsprimal;          /* For rounding RHS values to 0/infeasibility */\n  REAL      epsdual;            /* For rounding reduced costs to zero */\n  REAL      epspivot;           /* Pivot reject tolerance */\n  REAL      epsperturb;         /* Perturbation scalar */\n  REAL      epssolution;        /* The solution tolerance for final validation */\n\n  /* Branch & Bound working parameters */\n  int       bb_status;          /* Indicator that the last solvelp() gave an improved B&B solution */\n  int       bb_level;           /* Solver B&B working variable (recursion depth) */\n  int       bb_maxlevel;        /* The deepest B&B level of the last solution */\n  int       bb_limitlevel;      /* The maximum B&B level allowed */\n  COUNTER   bb_totalnodes;      /* Total number of nodes processed in B&B */\n  int       bb_solutionlevel;   /* The B&B level of the last / best solution */\n  int       bb_cutpoolsize;     /* Size of the B&B cut pool */\n  int       bb_cutpoolused;     /* Currently used cut pool */\n  int       bb_constraintOF;    /* General purpose B&B parameter (typically for testing) */\n  int       *bb_cuttype;        /* The type of the currently used cuts */\n  int       *bb_varactive;      /* The B&B state of the variable; 0 means inactive */\n  DeltaVrec *bb_upperchange;    /* Changes to upper bounds during the B&B phase */\n  DeltaVrec *bb_lowerchange;    /* Changes to lower bounds during the B&B phase */\n\n  REAL      bb_deltaOF;         /* Minimum OF step value; computed at beginning of solve() */\n\n  REAL      bb_breakOF;         /* User-settable value for the objective function deemed\n                               to be sufficiently good in an integer problem */\n  REAL      bb_limitOF;         /* \"Dual\" bound / limit to final optimal MIP solution */\n  REAL      bb_heuristicOF;     /* Set initial \"at least better than\" guess for objective function\n                               (can significantly speed up B&B iterations) */\n  REAL      bb_parentOF;        /* The OF value of the previous BB simplex */\n  REAL      bb_workOF;          /* The unadjusted OF value for the current best solution */\n\n  /* Internal work arrays allocated as required */\n  presolveundorec *presolve_undo;\n  workarraysrec   *workarrays;\n\n  /* MIP parameters */\n  REAL      epsint;             /* Margin of error in determining if a float value is integer */\n  REAL      mip_absgap;         /* Absolute MIP gap */\n  REAL      mip_relgap;         /* Relative MIP gap */\n\n  /* Time/timer variables and extended status text */\n  double    timecreate;\n  double    timestart;\n  double    timeheuristic;\n  double    timepresolved;\n  double    timeend;\n  long      sectimeout;\n\n  /* Extended status message text set via explain() */\n  char      *ex_status;\n\n  /* Refactorization engine interface routines (for dynamic DLL/SO BFPs) */\n#if LoadInverseLib == TRUE\n  #ifdef WIN32\n    HINSTANCE                   hBFP;\n  #else\n    void                        *hBFP;\n  #endif\n#endif\n  BFPchar                       *bfp_name;\n  BFPbool_lpintintint           *bfp_compatible;\n  BFPbool_lpintintchar          *bfp_init;\n  BFP_lp                        *bfp_free;\n  BFPbool_lpint                 *bfp_resize;\n  BFPint_lp                     *bfp_memallocated;\n  BFPbool_lp                    *bfp_restart;\n  BFPbool_lp                    *bfp_mustrefactorize;\n  BFPint_lp                     *bfp_preparefactorization;\n  BFPint_lpintintboolbool       *bfp_factorize;\n  BFP_lp                        *bfp_finishfactorization;\n  BFP_lp                        *bfp_updaterefactstats;\n  BFPlreal_lpintintreal         *bfp_prepareupdate;\n  BFPreal_lplrealreal           *bfp_pivotRHS;\n  BFPbool_lpbool                *bfp_finishupdate;\n  BFP_lprealint                 *bfp_ftran_prepare;\n  BFP_lprealint                 *bfp_ftran_normal;\n  BFP_lprealint                 *bfp_btran_normal;\n  BFP_lprealintrealint          *bfp_btran_double;\n  BFPint_lp                     *bfp_status;\n  BFPint_lpbool                 *bfp_nonzeros;\n  BFPbool_lp                    *bfp_implicitslack;\n  BFPint_lp                     *bfp_indexbase;\n  BFPint_lp                     *bfp_rowoffset;\n  BFPint_lp                     *bfp_pivotmax;\n  BFPbool_lpint                 *bfp_pivotalloc;\n  BFPint_lp                     *bfp_colcount;\n  BFPbool_lp                    *bfp_canresetbasis;\n  BFPreal_lp                    *bfp_efficiency;\n  BFPrealp_lp                   *bfp_pivotvector;\n  BFPint_lp                     *bfp_pivotcount;\n  BFPint_lpint                  *bfp_refactcount;\n  BFPbool_lp                    *bfp_isSetI;\n  BFPint_lpintrealcbintint      *bfp_findredundant;\n\n  /* External language interface routines (for dynamic DLL/SO XLIs) */\n#if LoadLanguageLib == TRUE\n  #ifdef WIN32\n    HINSTANCE                   hXLI;\n  #else\n    void                        *hXLI;\n  #endif\n#endif\n  XLIchar                       *xli_name;\n  XLIbool_lpintintint           *xli_compatible;\n  XLIbool_lpcharcharcharint     *xli_readmodel;\n  XLIbool_lpcharcharbool        *xli_writemodel;\n\n  /* Miscellaneous internal functions made available externally */\n  userabortfunc                 *userabort;\n  reportfunc                    *report;\n  explainfunc                   *explain;\n  getvectorfunc                 *get_lpcolumn;\n  getpackedfunc                 *get_basiscolumn;\n  get_OF_activefunc             *get_OF_active;\n  getMDOfunc                    *getMDO;\n  invertfunc                    *invert;\n  set_actionfunc                *set_action;\n  is_actionfunc                 *is_action;\n  clear_actionfunc              *clear_action;\n\n  /* User program interface callbacks */\n  lphandle_intfunc              *ctrlc;\n    void                          *ctrlchandle;     /* User-specified \"owner process ID\" */\n  lphandlestr_func              *writelog;\n    void                          *loghandle;       /* User-specified \"owner process ID\" */\n  lphandlestr_func              *debuginfo;\n  lphandleint_func              *usermessage;\n    int                           msgmask;\n    void                          *msghandle;       /* User-specified \"owner process ID\" */\n  lphandleint_intfunc           *bb_usenode;\n    void                          *bb_nodehandle;   /* User-specified \"owner process ID\" */\n  lphandleint_intfunc           *bb_usebranch;\n    void                          *bb_branchhandle; /* User-specified \"owner process ID\" */\n\n  /* replacement of static variables */\n  char      *rowcol_name;       /* The name of a row/column */\n};\n\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\n\n/* User and system function interfaces                                       */\n/* ------------------------------------------------------------------------- */\n\nvoid __EXPORT_TYPE __WINAPI lp_solve_version(int *majorversion, int *minorversion, int *release, int *build);\n\nlprec __EXPORT_TYPE * __WINAPI make_lp(int rows, int columns);\nMYBOOL __EXPORT_TYPE __WINAPI resize_lp(lprec *lp, int rows, int columns);\nint __EXPORT_TYPE __WINAPI get_status(lprec *lp);\nchar __EXPORT_TYPE * __WINAPI get_statustext(lprec *lp, int statuscode);\nMYBOOL __EXPORT_TYPE __WINAPI is_obj_in_basis(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI set_obj_in_basis(lprec *lp, MYBOOL obj_in_basis);\n/* Create and initialise a lprec structure defaults */\n\nlprec __EXPORT_TYPE * __WINAPI copy_lp(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI dualize_lp(lprec *lp);\nSTATIC MYBOOL memopt_lp(lprec *lp, int rowextra, int colextra, int nzextra);\n/* Copy or dualize the lp */\n\nvoid __EXPORT_TYPE __WINAPI delete_lp(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI free_lp(lprec **plp);\n/* Remove problem from memory */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_lp_name(lprec *lp, char *lpname);\nchar __EXPORT_TYPE * __WINAPI get_lp_name(lprec *lp);\n/* Set and get the problem name */\n\nMYBOOL __EXPORT_TYPE __WINAPI has_BFP(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_nativeBFP(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI set_BFP(lprec *lp, char *filename);\n/* Set basis factorization engine */\n\nlprec __EXPORT_TYPE * __WINAPI read_XLI(char *xliname, char *modelname, char *dataname, char *options, int verbose);\nMYBOOL __EXPORT_TYPE __WINAPI write_XLI(lprec *lp, char *filename, char *options, MYBOOL results);\nMYBOOL __EXPORT_TYPE __WINAPI has_XLI(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_nativeXLI(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI set_XLI(lprec *lp, char *filename);\n/* Set external language interface */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_obj(lprec *lp, int colnr, REAL value);\nMYBOOL __EXPORT_TYPE __WINAPI set_obj_fn(lprec *lp, REAL *row);\nMYBOOL __EXPORT_TYPE __WINAPI set_obj_fnex(lprec *lp, int count, REAL *row, int *colno);\n/* set the objective function (Row 0) of the matrix */\nMYBOOL __EXPORT_TYPE __WINAPI str_set_obj_fn(lprec *lp, char *row_string);\n/* The same, but with string input */\nvoid __EXPORT_TYPE __WINAPI set_sense(lprec *lp, MYBOOL maximize);\nvoid __EXPORT_TYPE __WINAPI set_maxim(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI set_minim(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_maxim(lprec *lp);\n/* Set optimization direction for the objective function */\n\nMYBOOL __EXPORT_TYPE __WINAPI add_constraint(lprec *lp, REAL *row, int constr_type, REAL rh);\nMYBOOL __EXPORT_TYPE __WINAPI add_constraintex(lprec *lp, int count, REAL *row, int *colno, int constr_type, REAL rh);\nMYBOOL __EXPORT_TYPE __WINAPI set_add_rowmode(lprec *lp, MYBOOL turnon);\nMYBOOL __EXPORT_TYPE __WINAPI is_add_rowmode(lprec *lp);\n/* Add a constraint to the problem, row is the constraint row, rh is the right hand side,\n   constr_type is the type of constraint (LE (<=), GE(>=), EQ(=)) */\nMYBOOL __EXPORT_TYPE __WINAPI str_add_constraint(lprec *lp, char *row_string, int constr_type, REAL rh);\n/* The same, but with string input */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_row(lprec *lp, int rownr, REAL *row);\nMYBOOL __EXPORT_TYPE __WINAPI set_rowex(lprec *lp, int rownr, int count, REAL *row, int *colno);\nMYBOOL __EXPORT_TYPE __WINAPI get_row(lprec *lp, int rownr, REAL *row);\nint __EXPORT_TYPE __WINAPI get_rowex(lprec *lp, int rownr, REAL *row, int *colno);\n/* Fill row with the row row_nr from the problem */\n\nMYBOOL __EXPORT_TYPE __WINAPI del_constraint(lprec *lp, int rownr);\nSTATIC MYBOOL del_constraintex(lprec *lp, LLrec *rowmap);\n/* Remove constrain nr del_row from the problem */\n\nMYBOOL __EXPORT_TYPE __WINAPI add_lag_con(lprec *lp, REAL *row, int con_type, REAL rhs);\n/* add a Lagrangian constraint of form Row' x contype Rhs */\nMYBOOL __EXPORT_TYPE __WINAPI str_add_lag_con(lprec *lp, char *row_string, int con_type, REAL rhs);\n/* The same, but with string input */\nvoid __EXPORT_TYPE __WINAPI set_lag_trace(lprec *lp, MYBOOL lag_trace);\nMYBOOL __EXPORT_TYPE __WINAPI is_lag_trace(lprec *lp);\n/* Set debugging/tracing mode of the Lagrangean solver */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_constr_type(lprec *lp, int rownr, int con_type);\nint __EXPORT_TYPE __WINAPI get_constr_type(lprec *lp, int rownr);\nREAL __EXPORT_TYPE __WINAPI get_constr_value(lprec *lp, int rownr, int count, REAL *primsolution, int *nzindex);\nMYBOOL __EXPORT_TYPE __WINAPI is_constr_type(lprec *lp, int rownr, int mask);\nSTATIC char *get_str_constr_type(lprec *lp, int con_type);\nSTATIC int get_constr_class(lprec *lp, int rownr);\nSTATIC char *get_str_constr_class(lprec *lp, int con_class);\n/* Set the type of constraint in row Row (LE, GE, EQ) */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_rh(lprec *lp, int rownr, REAL value);\nREAL __EXPORT_TYPE __WINAPI get_rh(lprec *lp, int rownr);\n/* Set and get the right hand side of a constraint row */\nMYBOOL __EXPORT_TYPE __WINAPI set_rh_range(lprec *lp, int rownr, REAL deltavalue);\nREAL __EXPORT_TYPE __WINAPI get_rh_range(lprec *lp, int rownr);\n/* Set the RHS range; i.e. the lower and upper bounds of a constraint row */\nvoid __EXPORT_TYPE __WINAPI set_rh_vec(lprec *lp, REAL *rh);\n/* Set the right hand side vector */\nMYBOOL __EXPORT_TYPE __WINAPI str_set_rh_vec(lprec *lp, char *rh_string);\n/* The same, but with string input */\n\nMYBOOL __EXPORT_TYPE __WINAPI add_column(lprec *lp, REAL *column);\nMYBOOL __EXPORT_TYPE __WINAPI add_columnex(lprec *lp, int count, REAL *column, int *rowno);\nMYBOOL __EXPORT_TYPE __WINAPI str_add_column(lprec *lp, char *col_string);\n/* Add a column to the problem */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_column(lprec *lp, int colnr, REAL *column);\nMYBOOL __EXPORT_TYPE __WINAPI set_columnex(lprec *lp, int colnr, int count, REAL *column, int *rowno);\n/* Overwrite existing column data */\n\nint __EXPORT_TYPE __WINAPI column_in_lp(lprec *lp, REAL *column);\n/* Returns the column index if column is already present in lp, otherwise 0.\n   (Does not look at bounds and types, only looks at matrix values */\n\nint __EXPORT_TYPE __WINAPI get_columnex(lprec *lp, int colnr, REAL *column, int *nzrow);\nMYBOOL __EXPORT_TYPE __WINAPI get_column(lprec *lp, int colnr, REAL *column);\n/* Fill column with the column col_nr from the problem */\n\nMYBOOL __EXPORT_TYPE __WINAPI del_column(lprec *lp, int colnr);\nSTATIC MYBOOL del_columnex(lprec *lp, LLrec *colmap);\n/* Delete a column */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_mat(lprec *lp, int rownr, int colnr, REAL value);\n/* Fill in element (Row,Column) of the matrix\n   Row in [0..Rows] and Column in [1..Columns] */\nREAL __EXPORT_TYPE __WINAPI get_mat(lprec *lp, int rownr, int colnr);\nREAL __EXPORT_TYPE __WINAPI get_mat_byindex(lprec *lp, int matindex, MYBOOL isrow, MYBOOL adjustsign);\nint __EXPORT_TYPE __WINAPI get_nonzeros(lprec *lp);\n/* get a single element from the matrix */  /* Name changed from \"mat_elm\" by KE */\n\nvoid __EXPORT_TYPE __WINAPI set_bounds_tighter(lprec *lp, MYBOOL tighten);\nMYBOOL get_bounds(lprec *lp, int column, REAL *lower, REAL *upper);\nMYBOOL __EXPORT_TYPE __WINAPI get_bounds_tighter(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI set_upbo(lprec *lp, int colnr, REAL value);\nREAL __EXPORT_TYPE __WINAPI get_upbo(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_lowbo(lprec *lp, int colnr, REAL value);\nREAL __EXPORT_TYPE __WINAPI get_lowbo(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_bounds(lprec *lp, int colnr, REAL lower, REAL upper);\nMYBOOL __EXPORT_TYPE __WINAPI set_unbounded(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI is_unbounded(lprec *lp, int colnr);\n/* Set the upper and lower bounds of a variable */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_int(lprec *lp, int colnr, MYBOOL must_be_int);\nMYBOOL __EXPORT_TYPE __WINAPI is_int(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_binary(lprec *lp, int colnr, MYBOOL must_be_bin);\nMYBOOL __EXPORT_TYPE __WINAPI is_binary(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_semicont(lprec *lp, int colnr, MYBOOL must_be_sc);\nMYBOOL __EXPORT_TYPE __WINAPI is_semicont(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI is_negative(lprec *lp, int colnr);\nMYBOOL __EXPORT_TYPE __WINAPI set_var_weights(lprec *lp, REAL *weights);\nint __EXPORT_TYPE __WINAPI get_var_priority(lprec *lp, int colnr);\n/* Set the type of variable */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_pseudocosts(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit);\nMYBOOL __EXPORT_TYPE __WINAPI get_pseudocosts(lprec *lp, REAL *clower, REAL *cupper, int *updatelimit);\n/* Set initial values for, or get computed pseudocost vectors;\n   note that setting of pseudocosts can only happen in response to a\n   call-back function optionally requesting this */\n\nint  __EXPORT_TYPE __WINAPI add_SOS(lprec *lp, char *name, int sostype, int priority, int count, int *sosvars, REAL *weights);\nMYBOOL __EXPORT_TYPE __WINAPI is_SOS_var(lprec *lp, int colnr);\n/* Add SOS constraints */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_row_name(lprec *lp, int rownr, char *new_name);\nchar __EXPORT_TYPE * __WINAPI get_row_name(lprec *lp, int rownr);\nchar __EXPORT_TYPE * __WINAPI get_origrow_name(lprec *lp, int rownr);\n/* Set/Get the name of a constraint row */   /* Get added by KE */\n\nMYBOOL __EXPORT_TYPE __WINAPI set_col_name(lprec *lp, int colnr, char *new_name);\nchar __EXPORT_TYPE * __WINAPI get_col_name(lprec *lp, int colnr);\nchar __EXPORT_TYPE * __WINAPI get_origcol_name(lprec *lp, int colnr);\n/* Set/Get the name of a variable column */  /* Get added by KE */\n\nvoid __EXPORT_TYPE __WINAPI unscale(lprec *lp);\n/* Undo previous scaling of the problem */\n\nvoid __EXPORT_TYPE __WINAPI set_preferdual(lprec *lp, MYBOOL dodual);\nvoid __EXPORT_TYPE __WINAPI set_simplextype(lprec *lp, int simplextype);\nint __EXPORT_TYPE __WINAPI get_simplextype(lprec *lp);\n/* Set/Get if lp_solve should prefer the dual simplex over the primal -- added by KE */\n\nvoid __EXPORT_TYPE __WINAPI default_basis(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI set_basiscrash(lprec *lp, int mode);\nint __EXPORT_TYPE __WINAPI get_basiscrash(lprec *lp);\nint __EXPORT_TYPE __WINAPI set_basisvar(lprec *lp, int basisPos, int enteringCol);\nMYBOOL __EXPORT_TYPE __WINAPI set_basis(lprec *lp, int *bascolumn, MYBOOL nonbasic);\nMYBOOL __EXPORT_TYPE __WINAPI get_basis(lprec *lp, int *bascolumn, MYBOOL nonbasic);\nvoid __EXPORT_TYPE __WINAPI reset_basis(lprec *lp);\n/* Set/Get basis for a re-solved system */  /* Added by KE */\nMYBOOL __EXPORT_TYPE __WINAPI guess_basis(lprec *lp, REAL *guessvector, int *basisvector);\n\nMYBOOL __EXPORT_TYPE __WINAPI is_feasible(lprec *lp, REAL *values, REAL threshold);\n/* returns TRUE if the vector in values is a feasible solution to the lp */\n\nint __EXPORT_TYPE __WINAPI solve(lprec *lp);\n/* Solve the problem */\n\nREAL __EXPORT_TYPE __WINAPI time_elapsed(lprec *lp);\n/* Return the number of seconds since start of solution process */\n\nvoid __EXPORT_TYPE __WINAPI put_bb_nodefunc(lprec *lp, lphandleint_intfunc newnode, void *bbnodehandle);\nvoid __EXPORT_TYPE __WINAPI put_bb_branchfunc(lprec *lp, lphandleint_intfunc newbranch, void *bbbranchhandle);\n/* Allow the user to override B&B node and branching decisions */\n\nvoid __EXPORT_TYPE __WINAPI put_abortfunc(lprec *lp, lphandle_intfunc newctrlc, void *ctrlchandle);\n/* Allow the user to define an interruption callback function */\n\nvoid __EXPORT_TYPE __WINAPI put_logfunc(lprec *lp, lphandlestr_func newlog, void *loghandle);\n/* Allow the user to define a logging function */\n\nvoid __EXPORT_TYPE __WINAPI put_msgfunc(lprec *lp, lphandleint_func newmsg, void *msghandle, int mask);\n/* Allow the user to define an event-driven message/reporting */\n\nMYBOOL __EXPORT_TYPE __WINAPI get_primal_solution(lprec *lp, REAL *pv);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_primal_solution(lprec *lp, REAL **pv);\nMYBOOL __EXPORT_TYPE __WINAPI get_dual_solution(lprec *lp, REAL *rc);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_dual_solution(lprec *lp, REAL **rc);\nMYBOOL __EXPORT_TYPE __WINAPI get_lambda(lprec *lp, REAL *lambda);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_lambda(lprec *lp, REAL **lambda);\n/* Get the primal, dual/reduced costs and Lambda vectors */\n\n/* Read an MPS file */\nlprec __EXPORT_TYPE * __WINAPI read_MPS(char *filename, int options);\nlprec __EXPORT_TYPE * __WINAPI read_mps(FILE *filename, int options);\nlprec __EXPORT_TYPE * __WINAPI read_freeMPS(char *filename, int options);\nlprec __EXPORT_TYPE * __WINAPI read_freemps(FILE *filename, int options);\n\n/* Write a MPS file to output */\nMYBOOL __EXPORT_TYPE __WINAPI write_mps(lprec *lp, char *filename);\nMYBOOL __EXPORT_TYPE __WINAPI write_MPS(lprec *lp, FILE *output);\nMYBOOL __EXPORT_TYPE __WINAPI write_freemps(lprec *lp, char *filename);\nMYBOOL __EXPORT_TYPE __WINAPI write_freeMPS(lprec *lp, FILE *output);\n\nMYBOOL __EXPORT_TYPE __WINAPI write_lp(lprec *lp, char *filename);\nMYBOOL __EXPORT_TYPE __WINAPI write_LP(lprec *lp, FILE *output);\n /* Write a LP file to output */\n\nMYBOOL __WINAPI LP_readhandle(lprec **lp, FILE *filename, int verbose, char *lp_name);\nlprec __EXPORT_TYPE * __WINAPI read_lp(FILE *filename, int verbose, char *lp_name);\nlprec __EXPORT_TYPE * __WINAPI read_LP(char *filename, int verbose, char *lp_name);\n/* Old-style lp format file parser */\n\nMYBOOL __EXPORT_TYPE __WINAPI write_basis(lprec *lp, char *filename);\nMYBOOL __EXPORT_TYPE __WINAPI read_basis(lprec *lp, char *filename, char *info);\n/* Read and write basis from/to file in CPLEX BAS format */\n\nMYBOOL __EXPORT_TYPE __WINAPI write_params(lprec *lp, char *filename, char *options);\nMYBOOL __EXPORT_TYPE __WINAPI read_params(lprec *lp, char *filename, char *options);\nvoid __EXPORT_TYPE __WINAPI reset_params(lprec *lp);\n/* Read and write parameter file */\n\nvoid __EXPORT_TYPE __WINAPI print_lp(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI print_tableau(lprec *lp);\n/* Print the current problem, only useful in very small (test) problems */\n\nvoid __EXPORT_TYPE __WINAPI print_objective(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI print_solution(lprec *lp, int columns);\nvoid __EXPORT_TYPE __WINAPI print_constraints(lprec *lp, int columns);\n/* Print the solution to stdout */\n\nvoid __EXPORT_TYPE __WINAPI print_duals(lprec *lp);\n/* Print the dual variables of the solution */\n\nvoid __EXPORT_TYPE __WINAPI print_scales(lprec *lp);\n/* If scaling is used, print the scaling factors */\n\nvoid __EXPORT_TYPE __WINAPI print_str(lprec *lp, char *str);\n\nvoid __EXPORT_TYPE __WINAPI set_outputstream(lprec *lp, FILE *stream);\nMYBOOL __EXPORT_TYPE __WINAPI set_outputfile(lprec *lp, char *filename);\n\nvoid __EXPORT_TYPE __WINAPI set_verbose(lprec *lp, int verbose);\nint __EXPORT_TYPE __WINAPI get_verbose(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_timeout(lprec *lp, long sectimeout);\nlong __EXPORT_TYPE __WINAPI get_timeout(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_print_sol(lprec *lp, int print_sol);\nint __EXPORT_TYPE __WINAPI get_print_sol(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_debug(lprec *lp, MYBOOL debug);\nMYBOOL __EXPORT_TYPE __WINAPI is_debug(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_trace(lprec *lp, MYBOOL trace);\nMYBOOL __EXPORT_TYPE __WINAPI is_trace(lprec *lp);\n\nMYBOOL __EXPORT_TYPE __WINAPI print_debugdump(lprec *lp, char *filename);\n\nvoid __EXPORT_TYPE __WINAPI set_anti_degen(lprec *lp, int anti_degen);\nint __EXPORT_TYPE __WINAPI get_anti_degen(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_anti_degen(lprec *lp, int testmask);\n\nvoid __EXPORT_TYPE __WINAPI set_presolve(lprec *lp, int presolvemode, int maxloops);\nint __EXPORT_TYPE __WINAPI get_presolve(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_presolveloops(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_presolve(lprec *lp, int testmask);\n\nint __EXPORT_TYPE __WINAPI get_orig_index(lprec *lp, int lp_index);\nint __EXPORT_TYPE __WINAPI get_lp_index(lprec *lp, int orig_index);\n\nvoid __EXPORT_TYPE __WINAPI set_maxpivot(lprec *lp, int max_num_inv);\nint __EXPORT_TYPE __WINAPI get_maxpivot(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_obj_bound(lprec *lp, REAL obj_bound);\nREAL __EXPORT_TYPE __WINAPI get_obj_bound(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_mip_gap(lprec *lp, MYBOOL absolute, REAL mip_gap);\nREAL __EXPORT_TYPE __WINAPI get_mip_gap(lprec *lp, MYBOOL absolute);\n\nvoid __EXPORT_TYPE __WINAPI set_bb_rule(lprec *lp, int bb_rule);\nint __EXPORT_TYPE __WINAPI get_bb_rule(lprec *lp);\n\nMYBOOL __EXPORT_TYPE __WINAPI set_var_branch(lprec *lp, int colnr, int branch_mode);\nint __EXPORT_TYPE __WINAPI get_var_branch(lprec *lp, int colnr);\n\nMYBOOL __EXPORT_TYPE __WINAPI is_infinite(lprec *lp, REAL value);\nvoid __EXPORT_TYPE __WINAPI set_infinite(lprec *lp, REAL infinite);\nREAL __EXPORT_TYPE __WINAPI get_infinite(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsint(lprec *lp, REAL epsint);\nREAL __EXPORT_TYPE __WINAPI get_epsint(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsb(lprec *lp, REAL epsb);\nREAL __EXPORT_TYPE __WINAPI get_epsb(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsd(lprec *lp, REAL epsd);\nREAL __EXPORT_TYPE __WINAPI get_epsd(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsel(lprec *lp, REAL epsel);\nREAL __EXPORT_TYPE __WINAPI get_epsel(lprec *lp);\n\nMYBOOL __EXPORT_TYPE __WINAPI set_epslevel(lprec *lp, int epslevel);\n\nvoid __EXPORT_TYPE __WINAPI set_scaling(lprec *lp, int scalemode);\nint __EXPORT_TYPE __WINAPI get_scaling(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI is_scalemode(lprec *lp, int testmask);\nMYBOOL __EXPORT_TYPE __WINAPI is_scaletype(lprec *lp, int scaletype);\nMYBOOL __EXPORT_TYPE __WINAPI is_integerscaling(lprec *lp);\nvoid __EXPORT_TYPE __WINAPI set_scalelimit(lprec *lp, REAL scalelimit);\nREAL __EXPORT_TYPE __WINAPI get_scalelimit(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_improve(lprec *lp, int improve);\nint __EXPORT_TYPE __WINAPI get_improve(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_pivoting(lprec *lp, int piv_rule);\nint __EXPORT_TYPE __WINAPI get_pivoting(lprec *lp);\nMYBOOL __EXPORT_TYPE __WINAPI set_partialprice(lprec *lp, int blockcount, int *blockstart, MYBOOL isrow);\nvoid __EXPORT_TYPE __WINAPI get_partialprice(lprec *lp, int *blockcount, int *blockstart, MYBOOL isrow);\n\nMYBOOL __EXPORT_TYPE __WINAPI set_multiprice(lprec *lp, int multiblockdiv);\nint __EXPORT_TYPE __WINAPI get_multiprice(lprec *lp, MYBOOL getabssize);\n\nMYBOOL __EXPORT_TYPE __WINAPI is_use_names(lprec *lp, MYBOOL isrow);\nvoid __EXPORT_TYPE __WINAPI set_use_names(lprec *lp, MYBOOL isrow, MYBOOL use_names);\n\nint __EXPORT_TYPE __WINAPI get_nameindex(lprec *lp, char *varname, MYBOOL isrow);\n\nMYBOOL __EXPORT_TYPE __WINAPI is_piv_mode(lprec *lp, int testmask);\nMYBOOL __EXPORT_TYPE __WINAPI is_piv_rule(lprec *lp, int rule);\n\nvoid __EXPORT_TYPE __WINAPI set_break_at_first(lprec *lp, MYBOOL break_at_first);\nMYBOOL __EXPORT_TYPE __WINAPI is_break_at_first(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_bb_floorfirst(lprec *lp, int bb_floorfirst);\nint __EXPORT_TYPE __WINAPI get_bb_floorfirst(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_bb_depthlimit(lprec *lp, int bb_maxlevel);\nint __EXPORT_TYPE __WINAPI get_bb_depthlimit(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_break_at_value(lprec *lp, REAL break_at_value);\nREAL __EXPORT_TYPE __WINAPI get_break_at_value(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_negrange(lprec *lp, REAL negrange);\nREAL __EXPORT_TYPE __WINAPI get_negrange(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epsperturb(lprec *lp, REAL epsperturb);\nREAL __EXPORT_TYPE __WINAPI get_epsperturb(lprec *lp);\n\nvoid __EXPORT_TYPE __WINAPI set_epspivot(lprec *lp, REAL epspivot);\nREAL __EXPORT_TYPE __WINAPI get_epspivot(lprec *lp);\n\nint __EXPORT_TYPE __WINAPI get_max_level(lprec *lp);\nCOUNTER __EXPORT_TYPE __WINAPI get_total_nodes(lprec *lp);\nCOUNTER __EXPORT_TYPE __WINAPI get_total_iter(lprec *lp);\n\nREAL __EXPORT_TYPE __WINAPI get_objective(lprec *lp);\nREAL __EXPORT_TYPE __WINAPI get_working_objective(lprec *lp);\n\nREAL __EXPORT_TYPE __WINAPI get_var_primalresult(lprec *lp, int index);\nREAL __EXPORT_TYPE __WINAPI get_var_dualresult(lprec *lp, int index);\n\nMYBOOL __EXPORT_TYPE __WINAPI get_variables(lprec *lp, REAL *var);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_variables(lprec *lp, REAL **var);\n\nMYBOOL __EXPORT_TYPE __WINAPI get_constraints(lprec *lp, REAL *constr);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_constraints(lprec *lp, REAL **constr);\n\nMYBOOL __EXPORT_TYPE __WINAPI get_sensitivity_rhs(lprec *lp, REAL *duals, REAL *dualsfrom, REAL *dualstill);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_sensitivity_rhs(lprec *lp, REAL **duals, REAL **dualsfrom, REAL **dualstill);\n\nMYBOOL __EXPORT_TYPE __WINAPI get_sensitivity_obj(lprec *lp, REAL *objfrom, REAL *objtill);\nMYBOOL __EXPORT_TYPE __WINAPI get_sensitivity_objex(lprec *lp, REAL *objfrom, REAL *objtill, REAL *objfromvalue, REAL *objtillvalue);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_sensitivity_obj(lprec *lp, REAL **objfrom, REAL **objtill);\nMYBOOL __EXPORT_TYPE __WINAPI get_ptr_sensitivity_objex(lprec *lp, REAL **objfrom, REAL **objtill, REAL **objfromvalue, REAL **objtillvalue);\n\nvoid __EXPORT_TYPE __WINAPI set_solutionlimit(lprec *lp, int limit);\nint __EXPORT_TYPE __WINAPI get_solutionlimit(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_solutioncount(lprec *lp);\n\nint __EXPORT_TYPE __WINAPI get_Norig_rows(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_Nrows(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_Lrows(lprec *lp);\n\nint __EXPORT_TYPE __WINAPI get_Norig_columns(lprec *lp);\nint __EXPORT_TYPE __WINAPI get_Ncolumns(lprec *lp);\n\ntypedef int (__WINAPI read_modeldata_func)(void *userhandle, char *buf, int max_size);\ntypedef int (__WINAPI write_modeldata_func)(void *userhandle, char *buf);\nMYBOOL __WINAPI MPS_readex(lprec **newlp, void *userhandle, read_modeldata_func read_modeldata, int typeMPS, int options);\n\n/* #if defined develop */\nlprec __EXPORT_TYPE * __WINAPI read_lpex(void *userhandle, read_modeldata_func read_modeldata, int verbose, char *lp_name);\nMYBOOL __EXPORT_TYPE __WINAPI write_lpex(lprec *lp, void *userhandle, write_modeldata_func write_modeldata);\n\nlprec __EXPORT_TYPE * __WINAPI read_mpsex(void *userhandle, read_modeldata_func read_modeldata, int options);\nlprec __EXPORT_TYPE * __WINAPI read_freempsex(void *userhandle, read_modeldata_func read_modeldata, int options);\n\nMYBOOL __EXPORT_TYPE __WINAPI MPS_writefileex(lprec *lp, int typeMPS, void *userhandle, write_modeldata_func write_modeldata);\n/* #endif */\n\n#ifdef __cplusplus\n}\n#endif\n\n\n/* Forward definitions of functions used internaly by the lp toolkit */\nMYBOOL set_callbacks(lprec *lp);\nSTATIC int yieldformessages(lprec *lp);\nMYBOOL __WINAPI userabort(lprec *lp, int message);\n/*char * __VACALL explain(lprec *lp, char *format, ...);\nvoid __VACALL report(lprec *lp, int level, char *format, ...);*/\n\n/* Memory management routines */\nSTATIC MYBOOL append_rows(lprec *lp, int deltarows);\nSTATIC MYBOOL append_columns(lprec *lp, int deltacolumns);\nSTATIC void inc_rows(lprec *lp, int delta);\nSTATIC void inc_columns(lprec *lp, int delta);\nSTATIC MYBOOL init_rowcol_names(lprec *lp);\nSTATIC MYBOOL inc_row_space(lprec *lp, int deltarows);\nSTATIC MYBOOL inc_col_space(lprec *lp, int deltacols);\nSTATIC MYBOOL shift_rowcoldata(lprec *lp, int base, int delta, LLrec *usedmap, MYBOOL isrow);\nSTATIC MYBOOL shift_basis(lprec *lp, int base, int delta, LLrec *usedmap, MYBOOL isrow);\nSTATIC MYBOOL shift_rowdata(lprec *lp, int base, int delta, LLrec *usedmap);\nSTATIC MYBOOL shift_coldata(lprec *lp, int base, int delta, LLrec *usedmap);\n\n/* INLINE */ MYBOOL is_chsign(lprec *lp, int rownr);\n\nSTATIC MYBOOL inc_lag_space(lprec *lp, int deltarows, MYBOOL ignoreMAT);\nlprec *make_lag(lprec *server);\n\nREAL get_rh_upper(lprec *lp, int rownr);\nREAL get_rh_lower(lprec *lp, int rownr);\nMYBOOL set_rh_upper(lprec *lp, int rownr, REAL value);\nMYBOOL set_rh_lower(lprec *lp, int rownr, REAL value);\nSTATIC int bin_count(lprec *lp, MYBOOL working);\nSTATIC int MIP_count(lprec *lp);\nSTATIC int SOS_count(lprec *lp);\nSTATIC int GUB_count(lprec *lp);\nSTATIC int identify_GUB(lprec *lp, MYBOOL mark);\nSTATIC int prepare_GUB(lprec *lp);\n\nSTATIC MYBOOL refactRecent(lprec *lp);\nSTATIC MYBOOL check_if_less(lprec *lp, REAL x, REAL y, int variable);\nSTATIC MYBOOL feasiblePhase1(lprec *lp, REAL epsvalue);\nSTATIC void free_duals(lprec *lp);\nSTATIC void initialize_solution(lprec *lp, MYBOOL shiftbounds);\nSTATIC void recompute_solution(lprec *lp, MYBOOL shiftbounds);\nSTATIC int verify_solution(lprec *lp, MYBOOL reinvert, char *info);\nSTATIC int check_solution(lprec *lp, int  lastcolumn, REAL *solution,\n                          REAL *upbo, REAL *lowbo, REAL tolerance);\n/* INLINE */ MYBOOL is_fixedvar(lprec *lp, int variable);\n/* INLINE */ MYBOOL is_splitvar(lprec *lp, int colnr);\n\nvoid   __WINAPI set_action(int *actionvar, int actionmask);\nvoid   __WINAPI clear_action(int *actionvar, int actionmask);\nMYBOOL __WINAPI is_action(int actionvar, int testmask);\n\n/* INLINE */ MYBOOL is_bb_rule(lprec *lp, int bb_rule);\n/* INLINE */ MYBOOL is_bb_mode(lprec *lp, int bb_mask);\n/* INLINE */ int get_piv_rule(lprec *lp);\nSTATIC char *get_str_piv_rule(int rule);\nSTATIC MYBOOL __WINAPI set_var_priority(lprec *lp);\nSTATIC int find_sc_bbvar(lprec *lp, int *count);\nSTATIC int find_sos_bbvar(lprec *lp, int *count, MYBOOL intsos);\nSTATIC int find_int_bbvar(lprec *lp, int *count, BBrec *BB, MYBOOL *isfeasible);\n\n/* Solution-related functions */\nSTATIC REAL compute_dualslacks(lprec *lp, int target, REAL **dvalues, int **nzdvalues, MYBOOL dosum);\nSTATIC MYBOOL solution_is_int(lprec *lp, int index, MYBOOL checkfixed);\nSTATIC MYBOOL bb_better(lprec *lp, int target, int mode);\nSTATIC void construct_solution(lprec *lp, REAL *target);\nSTATIC void transfer_solution_var(lprec *lp, int uservar);\nSTATIC MYBOOL construct_duals(lprec *lp);\nSTATIC MYBOOL construct_sensitivity_duals(lprec *lp);\nSTATIC MYBOOL construct_sensitivity_obj(lprec *lp);\n\nSTATIC int add_GUB(lprec *lp, char *name, int priority, int count, int *sosvars);\nSTATIC basisrec *push_basis(lprec *lp, int *basisvar, MYBOOL *isbasic, MYBOOL *islower);\nSTATIC MYBOOL compare_basis(lprec *lp);\nSTATIC MYBOOL restore_basis(lprec *lp);\nSTATIC MYBOOL pop_basis(lprec *lp, MYBOOL restore);\nSTATIC MYBOOL is_BasisReady(lprec *lp);\nSTATIC MYBOOL is_slackbasis(lprec *lp);\nSTATIC MYBOOL verify_basis(lprec *lp);\nSTATIC int unload_basis(lprec *lp, MYBOOL restorelast);\n\nSTATIC int perturb_bounds(lprec *lp, BBrec *perturbed, MYBOOL doRows, MYBOOL doCols, MYBOOL includeFIXED);\nSTATIC MYBOOL validate_bounds(lprec *lp, REAL *upbo, REAL *lowbo);\nSTATIC MYBOOL impose_bounds(lprec *lp, REAL * upbo, REAL *lowbo);\nSTATIC int unload_BB(lprec *lp);\n\nSTATIC REAL feasibilityOffset(lprec *lp, MYBOOL isdual);\nSTATIC MYBOOL isP1extra(lprec *lp);\nSTATIC REAL get_refactfrequency(lprec *lp, MYBOOL final);\nSTATIC int findBasicFixedvar(lprec *lp, int afternr, MYBOOL slacksonly);\nSTATIC MYBOOL isBasisVarFeasible(lprec *lp, REAL tol, int basis_row);\nSTATIC MYBOOL isPrimalFeasible(lprec *lp, REAL tol, int infeasibles[], REAL *feasibilitygap);\nSTATIC MYBOOL isDualFeasible(lprec *lp, REAL tol, int *boundflips, int infeasibles[], REAL *feasibilitygap);\n\n/* Main simplex driver routines */\nSTATIC int preprocess(lprec *lp);\nSTATIC void postprocess(lprec *lp);\nSTATIC MYBOOL performiteration(lprec *lp, int rownr, int varin, LREAL theta, MYBOOL primal, MYBOOL allowminit, REAL *prow, int *nzprow, REAL *pcol, int *nzpcol, int *boundswaps);\nSTATIC void transfer_solution_var(lprec *lp, int uservar);\nSTATIC void transfer_solution(lprec *lp, MYBOOL dofinal);\n\n/* Scaling utilities */\nSTATIC REAL scaled_floor(lprec *lp, int colnr, REAL value, REAL epsscale);\nSTATIC REAL scaled_ceil(lprec *lp, int colnr, REAL value, REAL epsscale);\n\n/* Variable mapping utility routines */\nSTATIC void varmap_lock(lprec *lp);\nSTATIC void varmap_clear(lprec *lp);\nSTATIC MYBOOL varmap_canunlock(lprec *lp);\nSTATIC void varmap_addconstraint(lprec *lp);\nSTATIC void varmap_addcolumn(lprec *lp);\nSTATIC void varmap_delete(lprec *lp, int base, int delta, LLrec *varmap);\nSTATIC void varmap_compact(lprec *lp, int prev_rows, int prev_cols);\nSTATIC MYBOOL varmap_validate(lprec *lp, int varno);\n/* STATIC MYBOOL del_varnameex(lprec *lp, hashelem **namelist, hashtable *ht, int varnr, LLrec *varmap); */\n STATIC MYBOOL del_varnameex(lprec *lp, hashelem **namelist, int items, hashtable *ht, int varnr, LLrec *varmap);\n\n/* Pseudo-cost routines (internal) */\nSTATIC BBPSrec *init_pseudocost(lprec *lp, int pseudotype);\nSTATIC void free_pseudocost(lprec *lp);\nSTATIC REAL get_pseudorange(BBPSrec *pc, int mipvar, int varcode);\nSTATIC void update_pseudocost(BBPSrec *pc, int mipvar, int varcode, MYBOOL capupper, REAL varsol);\nSTATIC REAL get_pseudobranchcost(BBPSrec *pc, int mipvar, MYBOOL dofloor);\nSTATIC REAL get_pseudonodecost(BBPSrec *pc, int mipvar, int vartype, REAL varsol);\n\n/* Matrix access and equation solving routines */\nSTATIC void set_OF_override(lprec *lp, REAL *ofVector);\nSTATIC void set_OF_p1extra(lprec *lp, REAL p1extra);\nSTATIC void unset_OF_p1extra(lprec *lp);\nMYBOOL modifyOF1(lprec *lp, int index, REAL *ofValue, REAL mult);\nREAL __WINAPI get_OF_active(lprec *lp, int varnr, REAL mult);\nSTATIC MYBOOL is_OF_nz(lprec *lp, int colnr);\n\nSTATIC int get_basisOF(lprec *lp, int coltarget[], REAL crow[], int colno[]);\nint    __WINAPI get_basiscolumn(lprec *lp, int j, int rn[], double bj[]);\nint    __WINAPI obtain_column(lprec *lp, int varin, REAL *pcol, int *nzlist, int *maxabs);\nSTATIC int compute_theta(lprec *lp, int rownr, LREAL *theta, int isupbound, REAL HarrisScalar, MYBOOL primal);\n\n/* Pivot utility routines */\nSTATIC int findBasisPos(lprec *lp, int notint, int *var_basic);\nSTATIC MYBOOL check_degeneracy(lprec *lp, REAL *pcol, int *degencount);\n\n#endif /* HEADER_lp_lib */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_matrix.c",
    "content": "\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_scale.h\"\n#include \"lp_report.h\"\n#include \"lp_price.h\"\n#include \"lp_pricePSE.h\"\n#include \"lp_matrix.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n/* -------------------------------------------------------------------------\n   Basic matrix routines in lp_solve v5.0+\n   -------------------------------------------------------------------------\n    Author:        Michel Berkelaar (to lp_solve v3.2),\n                   Kjell Eikland    (v4.0 and forward)\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      lp_lib.h, lp_pricerPSE.h, lp_matrix.h\n\n    Release notes:\n    v5.0.0  1 January 2004      First integrated and repackaged version.\n    v5.0.1  7 May 2004          Added matrix transpose function.\n    v5.1.0  20 July 2004        Reworked with flexible matrix storage model.\n    v5.2.0  10 January 2005     Added fast deletion methods.\n                                Added data extraction to matrix method.\n                                Changed to explicit OF storage mode.\n\n   ------------------------------------------------------------------------- */\n\nSTATIC MATrec *mat_create(lprec *lp, int rows, int columns, REAL epsvalue)\n{\n  MATrec *newmat;\n\n  newmat = (MATrec *) calloc(1, sizeof(*newmat));\n  newmat->lp = lp;\n\n  newmat->rows_alloc = 0;\n  newmat->columns_alloc = 0;\n  newmat->mat_alloc = 0;\n\n  inc_matrow_space(newmat, rows);\n  newmat->rows = rows;\n  inc_matcol_space(newmat, columns);\n  newmat->columns = columns;\n  inc_mat_space(newmat, 0);\n\n  newmat->epsvalue = epsvalue;\n\n  return( newmat );\n}\n\nSTATIC void mat_free(MATrec **matrix)\n{\n  if((matrix == NULL) || (*matrix == NULL))\n    return;\n\n#if MatrixColAccess==CAM_Record\n  FREE((*matrix)->col_mat);\n#else /*if MatrixColAccess==CAM_Vector*/\n  FREE((*matrix)->col_mat_colnr);\n  FREE((*matrix)->col_mat_rownr);\n  FREE((*matrix)->col_mat_value);\n#endif\n  FREE((*matrix)->col_end);\n  FREE((*matrix)->col_tag);\n\n#if MatrixRowAccess==RAM_Index\n  FREE((*matrix)->row_mat);\n#elif MatrixColAccess==CAM_Record\n  FREE((*matrix)->row_mat);\n#else /*if MatrixRowAccess==COL_Vector*/\n  FREE((*matrix)->row_mat_colnr);\n  FREE((*matrix)->row_mat_rownr);\n  FREE((*matrix)->row_mat_value);\n#endif\n  FREE((*matrix)->row_end);\n  FREE((*matrix)->row_tag);\n\n  FREE((*matrix)->colmax);\n  FREE((*matrix)->rowmax);\n\n  FREE(*matrix);\n}\n\nSTATIC MYBOOL mat_memopt(MATrec *mat, int rowextra, int colextra, int nzextra)\n{\n  MYBOOL status = TRUE;\n  int matalloc, colalloc, rowalloc;\n\n  if((mat == NULL) ||\n#if 0\n     (++rowextra < 1) || (++colextra < 1) || (++nzextra < 1))\n#else\n     (rowextra < 0) || (colextra < 0) || (nzextra < 0))\n#endif\n    return( FALSE );\n\n  mat->rows_alloc    = MIN(mat->rows_alloc,    mat->rows + rowextra);\n  mat->columns_alloc = MIN(mat->columns_alloc, mat->columns + colextra);\n  mat->mat_alloc     = MIN(mat->mat_alloc,     mat->col_end[mat->columns] + nzextra);\n#if 0\n  rowalloc = mat->rows_alloc;\n  colalloc = mat->columns_alloc;\n  matalloc = mat->mat_alloc;\n#else\n  rowalloc = mat->rows_alloc + 1;\n  colalloc = mat->columns_alloc + 1;\n  matalloc = mat->mat_alloc + 1;\n#endif\n\n#if MatrixColAccess==CAM_Record\n  mat->col_mat = (MATitem *) realloc(mat->col_mat, matalloc * sizeof(*(mat->col_mat)));\n  status &= (mat->col_mat != NULL);\n#else /*if MatrixColAccess==CAM_Vector*/\n  status &= allocINT(mat->lp,  &(mat->col_mat_colnr), matalloc, AUTOMATIC) &&\n            allocINT(mat->lp,  &(mat->col_mat_rownr), matalloc, AUTOMATIC) &&\n            allocREAL(mat->lp, &(mat->col_mat_value), matalloc, AUTOMATIC);\n#endif\n  status &= allocINT(mat->lp, &mat->col_end, colalloc, AUTOMATIC);\n  if(mat->col_tag != NULL)\n    status &= allocINT(mat->lp, &mat->col_tag, colalloc, AUTOMATIC);\n\n#if MatrixRowAccess==RAM_Index\n  status &= allocINT(mat->lp, &(mat->row_mat), matalloc, AUTOMATIC);\n#elif MatrixColAccess==CAM_Record\n  mat->row_mat = (MATitem *) realloc(mat->row_mat, matalloc * sizeof(*(mat->row_mat)));\n  status &= (mat->row_mat != NULL);\n#else /*if MatrixRowAccess==COL_Vector*/\n  status &= allocINT(mat->lp,  &(mat->row_mat_colnr), matalloc, AUTOMATIC) &&\n            allocINT(mat->lp,  &(mat->row_mat_rownr), matalloc, AUTOMATIC) &&\n            allocREAL(mat->lp, &(mat->row_mat_value), matalloc, AUTOMATIC);\n#endif\n  status &= allocINT(mat->lp, &mat->row_end, rowalloc, AUTOMATIC);\n  if(mat->row_tag != NULL)\n    status &= allocINT(mat->lp, &mat->row_tag, rowalloc, AUTOMATIC);\n\n  if(mat->colmax != NULL)\n    status &= allocREAL(mat->lp, &(mat->colmax), colalloc, AUTOMATIC);\n  if(mat->rowmax != NULL)\n    status &= allocREAL(mat->lp, &(mat->rowmax), rowalloc, AUTOMATIC);\n\n  return( status );\n}\n\nSTATIC MYBOOL inc_mat_space(MATrec *mat, int mindelta)\n{\n  int spaceneeded, nz = mat_nonzeros(mat);\n\n  if(mindelta <= 0)\n    mindelta = MAX(mat->rows, mat->columns) + 1;\n  spaceneeded = DELTA_SIZE(mindelta, nz);\n  SETMAX(mindelta, spaceneeded);\n\n  if(mat->mat_alloc == 0)\n    spaceneeded = mindelta;\n  else\n    spaceneeded = nz + mindelta;\n\n  if(spaceneeded >= mat->mat_alloc) {\n    /* Let's allocate at least MAT_START_SIZE entries */\n    if(mat->mat_alloc < MAT_START_SIZE)\n      mat->mat_alloc = MAT_START_SIZE;\n\n    /* Increase the size by RESIZEFACTOR each time it becomes too small */\n    while(spaceneeded >= mat->mat_alloc)\n      mat->mat_alloc += mat->mat_alloc / RESIZEFACTOR;\n\n#if MatrixColAccess==CAM_Record\n    mat->col_mat = (MATitem *) realloc(mat->col_mat, (mat->mat_alloc) * sizeof(*(mat->col_mat)));\n#else /*if MatrixColAccess==CAM_Vector*/\n    allocINT(mat->lp,  &(mat->col_mat_colnr), mat->mat_alloc, AUTOMATIC);\n    allocINT(mat->lp,  &(mat->col_mat_rownr), mat->mat_alloc, AUTOMATIC);\n    allocREAL(mat->lp, &(mat->col_mat_value), mat->mat_alloc, AUTOMATIC);\n#endif\n\n#if MatrixRowAccess==RAM_Index\n    allocINT(mat->lp, &(mat->row_mat), mat->mat_alloc, AUTOMATIC);\n#elif MatrixColAccess==CAM_Record\n    mat->row_mat = (MATitem *) realloc(mat->row_mat, (mat->mat_alloc) * sizeof(*(mat->row_mat)));\n#else /*if MatrixColAccess==CAM_Vector*/\n    allocINT(mat->lp,  &(mat->row_mat_colnr), mat->mat_alloc, AUTOMATIC);\n    allocINT(mat->lp,  &(mat->row_mat_rownr), mat->mat_alloc, AUTOMATIC);\n    allocREAL(mat->lp, &(mat->row_mat_value), mat->mat_alloc, AUTOMATIC);\n#endif\n  }\n  return(TRUE);\n}\n\nSTATIC MYBOOL inc_matrow_space(MATrec *mat, int deltarows)\n{\n  int    rowsum, oldrowsalloc;\n  MYBOOL status = TRUE;\n\n  /* Adjust lp row structures */\n  if(mat->rows+deltarows >= mat->rows_alloc) {\n\n    /* Update memory allocation and sizes */\n    oldrowsalloc = mat->rows_alloc;\n    deltarows = DELTA_SIZE(deltarows, mat->rows);\n    SETMAX(deltarows, DELTAROWALLOC);\n    mat->rows_alloc += deltarows;\n    rowsum = mat->rows_alloc + 1;\n\n    /* Update row pointers */\n    status = allocINT(mat->lp, &mat->row_end, rowsum, AUTOMATIC);\n    mat->row_end_valid = FALSE;\n  }\n  return( status );\n}\n\nSTATIC MYBOOL inc_matcol_space(MATrec *mat, int deltacols)\n{\n  int    i, colsum, oldcolsalloc;\n  MYBOOL status = TRUE;\n\n  /* Adjust lp column structures */\n  if(mat->columns+deltacols >= mat->columns_alloc) {\n\n    /* Update memory allocation and sizes */\n    oldcolsalloc = mat->columns_alloc;\n    deltacols = DELTA_SIZE(deltacols, mat->columns);\n    SETMAX(deltacols, DELTACOLALLOC);\n    mat->columns_alloc += deltacols;\n    colsum = mat->columns_alloc + 1;\n    status = allocINT(mat->lp, &mat->col_end, colsum, AUTOMATIC);\n\n    /* Update column pointers */\n    if(oldcolsalloc == 0)\n      mat->col_end[0] = 0;\n    for(i = MIN(oldcolsalloc, mat->columns) + 1; i < colsum; i++)\n      mat->col_end[i] = mat->col_end[i-1];\n    mat->row_end_valid = FALSE;\n  }\n  return( status );\n}\n\nSTATIC int mat_collength(MATrec *mat, int colnr)\n{\n  return( mat->col_end[colnr] - mat->col_end[colnr-1] );\n}\n\nSTATIC int mat_rowlength(MATrec *mat, int rownr)\n{\n  if(mat_validate(mat)) {\n    if(rownr <= 0)\n      return( mat->row_end[0] );\n    else\n      return( mat->row_end[rownr] - mat->row_end[rownr-1] );\n  }\n  else\n    return( 0 );\n}\n\nSTATIC int mat_nonzeros(MATrec *mat)\n{\n  return( mat->col_end[mat->columns] );\n}\n\nSTATIC MYBOOL mat_indexrange(MATrec *mat, int index, MYBOOL isrow, int *startpos, int *endpos)\n{\n#ifdef Paranoia\n  if(isrow && ((index < 0) || (index > mat->rows)))\n    return( FALSE );\n  else if(!isrow && ((index < 1) || (index > mat->columns)))\n    return( FALSE );\n#endif\n\n  if(isrow && mat_validate(mat)) {\n    if(index == 0)\n      *startpos = 0;\n    else\n      *startpos = mat->row_end[index-1];\n    *endpos = mat->row_end[index];\n  }\n  else {\n    *startpos = mat->col_end[index-1];\n    *endpos = mat->col_end[index];\n  }\n  return( TRUE );\n}\n\nSTATIC int mat_shiftrows(MATrec *mat, int *bbase, int delta, LLrec *varmap)\n{\n  int     j, k, i, ii, thisrow, *colend, base;\n  MYBOOL  preparecompact = FALSE;\n  int     *rownr;\n\n  if(delta == 0)\n    return( 0 );\n  base = abs(*bbase);\n\n  if(delta > 0) {\n\n    /* Insert row by simply incrementing existing row indeces */\n    if(base <= mat->rows) {\n      k = mat_nonzeros(mat);\n      rownr = &COL_MAT_ROWNR(0);\n      for(ii = 0; ii < k; ii++, rownr += matRowColStep) {\n        if(*rownr >= base)\n          *rownr += delta;\n      }\n    }\n\n    /* Set defaults (actual basis set in separate procedure) */\n    for(i = 0; i < delta; i++) {\n      ii = base + i;\n      mat->row_end[ii] = 0;\n    }\n  }\n  else if(base <= mat->rows) {\n\n    /* Check for preparation of mass-deletion of rows */\n    preparecompact = (MYBOOL) (varmap != NULL);\n    if(preparecompact) {\n      /* Create the offset array */\n      int *newrowidx = NULL;\n      allocINT(mat->lp, &newrowidx, mat->rows+1, FALSE);\n      newrowidx[0] = 0;\n      delta = 0;\n      for(j = 1; j <= mat->rows; j++) {\n        if(isActiveLink(varmap, j)) {\n          delta++;\n          newrowidx[j] = delta;\n        }\n        else\n          newrowidx[j] = -1;\n      }\n      k = 0;\n      delta = 0;\n      base = mat_nonzeros(mat);\n      rownr = &COL_MAT_ROWNR(0);\n      for(i = 0; i < base; i++, rownr += matRowColStep) {\n        thisrow = newrowidx[*rownr];\n        if(thisrow < 0) {\n          *rownr = -1;\n          delta++;\n        }\n        else\n          *rownr = thisrow;\n      }\n      FREE(newrowidx);\n      return(delta);\n    }\n\n    /* Check if we should prepare for compacting later\n       (this is in order to speed up multiple row deletions) */\n    preparecompact = (MYBOOL) (*bbase < 0);\n    if(preparecompact)\n      *bbase = my_flipsign((*bbase));\n\n    /* First make sure we don't cross the row count border */\n    if(base-delta-1 > mat->rows)\n      delta = base - mat->rows - 1;\n\n    /* Then scan over all entries shifting and updating rows indeces */\n    if(preparecompact) {\n      k = 0;\n      for(j = 1, colend = mat->col_end + 1;\n          j <= mat->columns; j++, colend++) {\n        i = k;\n        k = *colend;\n        rownr = &COL_MAT_ROWNR(i);\n        for(; i < k; i++, rownr += matRowColStep) {\n          thisrow = *rownr;\n          if(thisrow < base)\n            continue;\n          else if(thisrow >= base-delta)\n            *rownr += delta;\n          else\n            *rownr = -1;\n        }\n      }\n    }\n    else {\n      k = 0;\n      ii = 0;\n      for(j = 1, colend = mat->col_end + 1;\n          j <= mat->columns; j++, colend++) {\n        i = k;\n        k = *colend;\n        rownr = &COL_MAT_ROWNR(i);\n        for(; i < k; i++, rownr += matRowColStep) {\n          thisrow = *rownr;\n          if(thisrow >= base) {\n            if(thisrow >= base-delta)\n              *rownr += delta;\n            else\n              continue;\n          }\n          if(ii != i) {\n            COL_MAT_COPY(ii, i);\n          }\n          ii++;\n        }\n        *colend = ii;\n      }\n    }\n  }\n  return( 0 );\n}\n\n/* Map-based compacting+insertion of matrix elements without changing row and column indeces.\n   When mat2 is NULL, a simple compacting of non-deleted rows and columns is done. */\nSTATIC int mat_mapreplace(MATrec *mat, LLrec *rowmap, LLrec *colmap, MATrec *mat2)\n{\n  lprec *lp = mat->lp;\n  int   i, ib, ie, ii, j, jj, jb, je, nz, *colend, *rownr, *rownr2, *indirect = NULL;\n  REAL  *value, *value2;\n\n  /* Check if there is something to insert */\n  if((mat2 != NULL) && ((mat2->col_tag == NULL) || (mat2->col_tag[0] <= 0) || (mat_nonzeros(mat2) == 0)))\n    return( 0 );\n\n  /* Create map and sort by increasing index in \"mat\" */\n  if(mat2 != NULL) {\n    jj = mat2->col_tag[0];\n    allocINT(lp, &indirect, jj+1, FALSE);\n    indirect[0] = jj;\n    for(i = 1; i <= jj; i++)\n      indirect[i] = i;\n    hpsortex(mat2->col_tag, jj, 1, sizeof(*indirect), FALSE, compareINT, indirect);\n  }\n\n  /* Do the compacting */\n  mat->row_end_valid = FALSE;\n  nz = mat->col_end[mat->columns];\n  ie = 0;\n  ii = 0;\n  if((mat2 == NULL) || (indirect[0] == 0)) {\n    je = mat->columns + 1;\n    jj = 1;\n    jb = 0;\n  }\n  else {\n    je = indirect[0];\n    jj = 0;\n    do {\n      jj++;\n      jb = mat2->col_tag[jj];\n    } while(jb <= 0);\n\n  }\n  for(j = 1, colend = mat->col_end + 1;\n      j <= mat->columns; j++, colend++) {\n    ib = ie;\n    ie = *colend;\n\n    /* Always skip (condense) replacement columns */\n    if(j == jb) {\n      jj++;\n      if(jj <= je)\n        jb = mat2->col_tag[jj];\n      else\n        jb = mat->columns + 1;\n    }\n\n    /* Only include active columns */\n    else if(isActiveLink(colmap, j)) {\n      rownr = &COL_MAT_ROWNR(ib);\n      for(; ib < ie; ib++, rownr += matRowColStep) {\n\n        /* Also make sure the row is active */\n        if(isActiveLink(rowmap, *rownr)) {\n          if(ii != ib) {\n            COL_MAT_COPY(ii, ib);\n          }\n          ii++;\n        }\n      }\n    }\n    *colend = ii;\n  }\n  if(mat2 == NULL)\n    goto Finish;\n\n  /* Tally non-zero insertions */\n  i = 0;\n  for(j = 1; j <= mat2->col_tag[0]; j++) {\n    jj = mat2->col_tag[j];\n    if((jj > 0) && isActiveLink(colmap, jj)) {\n      jj = indirect[j];\n      je = mat2->col_end[jj];\n      jb = mat2->col_end[jj-1];\n      rownr2 = &COL_MAT2_ROWNR(jb);\n      for(; jb < je; jb++, rownr2 += matRowColStep) {\n        if((*rownr2 > 0) && isActiveLink(rowmap, *rownr2))\n          i++;\n      }\n    }\n  }\n\n  /* Make sure we have enough matrix space */\n  ii = mat->col_end[mat->columns] + i;\n  if(mat->mat_alloc <= ii)\n    inc_mat_space(mat, i);\n\n  /* Do shifting and insertion - loop from the end going forward */\n  jj = indirect[0];\n  jj = mat2->col_tag[jj];\n  for(j = mat->columns, colend = mat->col_end + mat->columns, ib = *colend;\n      j > 0; j--) {\n\n    /* Update indeces for this loop */\n    ie = ib;\n    *colend = ii;\n    colend--;\n    ib = *colend;\n\n    /* Insert new values */\n    if(j == jj) {\n      /* Only include an active column */\n      if(isActiveLink(colmap, j)) {\n        jj = indirect[0];\n        jj = indirect[jj];\n        rownr = &COL_MAT_ROWNR(ii-1);\n        value = &COL_MAT_VALUE(ii-1);\n        jb = mat2->col_end[jj-1];\n        je = mat2->col_end[jj] - 1;\n        rownr2 = &COL_MAT2_ROWNR(je);\n        value2 = &COL_MAT2_VALUE(je);\n\n        /* Process constraint coefficients */\n        for(; je >= jb; je--, rownr2 -= matRowColStep, value2 -= matValueStep) {\n          i = *rownr2;\n          if(i == 0) {\n            i = -1;\n            break;\n          }\n          else if(isActiveLink(rowmap, i)) {\n            ii--;\n            *rownr = i;\n            rownr -= matRowColStep;\n            *value = my_chsign(is_chsign(lp, i), *value2);\n            value -= matValueStep;\n          }\n        }\n\n        /* Then handle the objective */\n        if(i == -1) {\n          lp->orig_obj[j] = my_chsign(is_maxim(lp), *value2);\n          rownr2 -= matRowColStep;\n          value2 -= matValueStep;\n        }\n        else\n          lp->orig_obj[j] = 0;\n\n      }\n      /* Update replacement column index or break if no more candidates */\n      jj = --indirect[0];\n      if(jj == 0)\n        break;\n      jj = mat2->col_tag[jj];\n      if(jj <= 0)\n        break;\n    }\n    /* Shift existing values down */\n    else {\n      if(isActiveLink(colmap, j))\n      while(ie > ib) {\n        ii--;\n        ie--;\n        if(ie != ii) {\n          COL_MAT_COPY(ii, ie);\n        }\n      }\n    }\n  }\n\n  /* Return the delta number of non-zero elements */\nFinish:\n  nz -= mat->col_end[mat->columns];\n  FREE(indirect);\n\n  return( nz );\n}\n\n/* Routines to compact rows in matrix based on precoded entries */\nSTATIC int mat_zerocompact(MATrec *mat)\n{\n  return( mat_rowcompact(mat, TRUE) );\n}\nSTATIC int mat_rowcompact(MATrec *mat, MYBOOL dozeros)\n{\n  int  i, ie, ii, j, nn, *colend, *rownr;\n  REAL *value;\n\n  nn = 0;\n  ie = 0;\n  ii = 0;\n  for(j = 1, colend = mat->col_end + 1;\n      j <= mat->columns; j++, colend++) {\n    i = ie;\n    ie = *colend;\n    rownr = &COL_MAT_ROWNR(i);\n    value = &COL_MAT_VALUE(i);\n    for(; i < ie;\n        i++, rownr += matRowColStep, value += matValueStep) {\n      if((*rownr < 0) || (dozeros && (fabs(*value) < mat->epsvalue))) {\n        nn++;\n        continue;\n      }\n      if(ii != i) {\n        COL_MAT_COPY(ii, i);\n      }\n      ii++;\n    }\n    *colend = ii;\n  }\n  return( nn );\n}\n\n/* Routines to compact columns and their indeces based on precoded entries */\nSTATIC int mat_colcompact(MATrec *mat, int prev_rows, int prev_cols)\n{\n  int             i, ii, j, k, n_del, n_sum, *colend, *newcolend, *colnr, newcolnr;\n  MYBOOL          deleted;\n  lprec           *lp = mat->lp;\n  presolveundorec *lpundo = lp->presolve_undo;\n\n\n  n_sum = 0;\n  k  = 0;\n  ii = 0;\n  newcolnr = 1;\n  for(j = 1, colend = newcolend = mat->col_end + 1;\n      j <= prev_cols; j++, colend++) {\n    n_del = 0;\n    i = k;\n    k = *colend;\n    for(colnr = &COL_MAT_COLNR(i); i < k;\n        i++, colnr += matRowColStep) {\n      if(*colnr < 0) {\n        n_del++;\n        n_sum++;\n        continue;\n      }\n      if(ii < i) {\n        COL_MAT_COPY(ii, i);\n      }\n      if(newcolnr < j) {\n        COL_MAT_COLNR(ii) = newcolnr;\n      }\n      ii++;\n    }\n    *newcolend = ii;\n\n    deleted = (MYBOOL) (n_del > 0);\n#if 1\n    /* Do hoops in case there was an empty column */\n    deleted |= (MYBOOL) (!lp->wasPresolved && (lpundo->var_to_orig[prev_rows+j] < 0));\n\n#endif\n    /* Increment column variables if current column was not deleted */\n    if(!deleted) {\n      newcolend++;\n      newcolnr++;\n    }\n  }\n  return(n_sum);\n}\n\nSTATIC int mat_shiftcols(MATrec *mat, int *bbase, int delta, LLrec *varmap)\n{\n  int     i, ii, k, n, base;\n\n\n  k = 0;\n  if(delta == 0)\n    return( k );\n  base = abs(*bbase);\n\n  if(delta > 0) {\n    /* Shift pointers right */\n    for(ii = mat->columns; ii > base; ii--) {\n      i = ii + delta;\n      mat->col_end[i] = mat->col_end[ii];\n    }\n    /* Set defaults */\n    for(i = 0; i < delta; i++) {\n      ii = base + i;\n      mat->col_end[ii] = mat->col_end[ii-1];\n    }\n  }\n  else {\n\n    /* Check for preparation of mass-deletion of columns */\n    MYBOOL preparecompact = (MYBOOL) (varmap != NULL);\n    if(preparecompact) {\n      /* Create the offset array */\n      int j, *colnr, *colend;\n      n = 0;\n      k = 0;\n      base = 0;\n      for(j = 1, colend = mat->col_end + 1;\n          j <= mat->columns; j++, colend++) {\n        i = k;\n        k = *colend;\n        if(isActiveLink(varmap, j)) {\n          base++;\n          ii = base;\n        }\n        else\n          ii = -1;\n        if(ii < 0)\n          n += k - i;\n        colnr = &COL_MAT_COLNR(i);\n        for(; i < k; i++, colnr += matRowColStep)\n          *colnr = ii;\n      }\n      return(n);\n    }\n\n    /* Check if we should prepare for compacting later\n       (this is in order to speed up multiple column deletions) */\n    preparecompact = (MYBOOL) (*bbase < 0);\n    if(preparecompact)\n      *bbase = my_flipsign((*bbase));\n\n    /* First make sure we don't cross the column count border */\n    if(base-delta-1 > mat->columns)\n      delta = base - mat->columns - 1;\n\n    /* Then scan over all entries shifting and updating column indeces */\n    if(preparecompact) {\n      int *colnr;\n      n = 0;\n      i = mat->col_end[base-1];\n      k = mat->col_end[base-delta-1];\n      for(colnr = &COL_MAT_COLNR(i); i < k;\n          i++, colnr += matRowColStep) {\n        n++;\n        *colnr = -1;\n      }\n      k = n;\n    }\n    else {\n      /* Delete sparse matrix data, if required */\n      if(base <= mat->columns) {\n\n        i = mat->col_end[base-1];          /* Beginning of data to be deleted */\n        ii = mat->col_end[base-delta-1];   /* Beginning of data to be shifted left */\n        n = mat_nonzeros(mat);             /* Total number of non-zeros */\n        k = ii-i;                          /* Number of entries to be deleted */\n        if((k > 0) && (n > i)) {\n          n -= ii;\n          COL_MAT_MOVE(i, ii, n);\n        }\n\n        /* Update indexes */\n        for(i = base; i <= mat->columns + delta; i++) {\n          ii = i - delta;\n          mat->col_end[i] = mat->col_end[ii] - k;\n        }\n      }\n    }\n  }\n  return( k );\n}\n\nSTATIC MATrec *mat_extractmat(MATrec *mat, LLrec *rowmap, LLrec *colmap, MYBOOL negated)\n{\n  int    *rownr, *colnr, xa, na;\n  REAL   *value;\n  MATrec *newmat = mat_create(mat->lp, mat->rows, mat->columns, mat->epsvalue);\n\n  /* Initialize */\n  na = mat_nonzeros(mat);\n  rownr = &COL_MAT_ROWNR(0);\n  colnr = &COL_MAT_COLNR(0);\n  value = &COL_MAT_VALUE(0);\n\n  /* Loop over the indeces, picking out values in qualifying rows and colums\n     (note that the loop could be speeded up for dense matrices by making an\n      outer loop for columns and inner loop for rows) */\n  for(xa = 0; xa < na; xa++, rownr += matRowColStep, colnr += matRowColStep, value += matValueStep) {\n    if((isActiveLink(colmap, *colnr) ^ negated) &&\n       (isActiveLink(rowmap, *rownr) ^ negated))\n      mat_setvalue(newmat, *rownr, *colnr, *value, FALSE);\n  }\n\n  /* Return the populated new matrix */\n  return( newmat );\n}\n\nSTATIC MYBOOL mat_setcol(MATrec *mat, int colno, int count, REAL *column, int *rowno, MYBOOL doscale, MYBOOL checkrowmode)\n{\n  int    i, jj = 0, elmnr, orignr, newnr, firstrow;\n  MYBOOL *addto = NULL, isA, isNZ;\n  REAL   value, saved = 0;\n  lprec  *lp = mat->lp;\n\n  /* Check if we are in row order mode and should add as row instead;\n     the matrix will be transposed at a later stage */\n  if(checkrowmode && mat->is_roworder)\n    return( mat_setrow(mat, colno, count, column, rowno, doscale, FALSE) );\n\n  /* Initialize and validate */\n  isA = (MYBOOL) (mat == mat->lp->matA);\n  isNZ = (MYBOOL) (rowno != NULL);\n  if(!isNZ)\n    count = mat->lp->rows;\n  else if((count < 0) || (count > mat->rows+((mat->is_roworder) ? 0 : 1)))\n    return( FALSE );\n  if(isNZ && (count > 0)) {\n    if(count > 1)\n      sortREALByINT(column, rowno, count, 0, TRUE);\n    if((rowno[0] < 0) || (rowno[count-1] > mat->rows))\n      return( FALSE );\n  }\n\n  /* Capture OF definition in column mode */\n  if(isA && !mat->is_roworder) {\n    if(isNZ && (count > 0) && (rowno[0] == 0)) {\n      value = column[0];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      if(doscale)\n        value = scaled_mat(lp, value, 0, colno);\n      value = my_chsign(is_maxim(lp), value);\n      lp->orig_obj[colno] = value;\n      count--;\n      column++;\n      rowno++;\n    }\n    else if(!isNZ && (column[0] != 0)) {\n      value = saved = column[0];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      if(doscale)\n        value = scaled_mat(lp, value, 0, colno);\n      value = my_chsign(is_maxim(lp), value);\n      lp->orig_obj[colno] = value;\n      column[0] = 0;\n    }\n    else\n      lp->orig_obj[colno] = 0;\n  }\n\n  /* Optionally tally and map the new non-zero values */\n  firstrow = mat->rows + 1;\n  if(isNZ) {\n    newnr = count;\n    if(newnr) {\n      firstrow = rowno[0];\n      jj = rowno[newnr - 1];\n    }\n  }\n  else {\n    newnr = 0;\n    if(!allocMYBOOL(lp, &addto, mat->rows + 1, TRUE)) {\n      return( FALSE );\n    }\n    for(i = mat->rows; i >= 0; i--) {\n      if(fabs(column[i]) > mat->epsvalue) {\n        addto[i] = TRUE;\n        firstrow = i;\n        newnr++;\n      }\n    }\n  }\n\n  /* Make sure we have enough matrix space */\n  if(!inc_mat_space(mat, newnr)) {\n    newnr = 0;\n    goto Done;\n  }\n\n  /* Shift existing column data and adjust position indeces */\n  orignr = mat_collength(mat, colno);\n  elmnr = newnr - orignr;\n  i = mat_nonzeros(mat) - mat->col_end[colno];\n  if((elmnr != 0) && (i > 0)) {\n    COL_MAT_MOVE(mat->col_end[colno] + elmnr, mat->col_end[colno], i);\n  }\n  if(elmnr != 0)\n    for(i = colno; i <= mat->columns; i++)\n      mat->col_end[i] += elmnr;\n\n  /* We are now ready to copy the new data */\n  jj = mat->col_end[colno-1];\n  if(isNZ) {\n    for(i = 0; i < count; jj++, i++) {\n      value = column[i];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      if(mat->is_roworder) {    /* Fix following Ingmar Stein bug report 12.10.2006 */\n        if(isA && doscale)\n          value = scaled_mat(lp, value, colno, rowno[i]);\n        if(isA)\n          value = my_chsign(is_chsign(lp, colno), value);\n      }\n      else {\n        if(isA && doscale)\n          value = scaled_mat(lp, value, rowno[i], colno);\n        if(isA)\n          value = my_chsign(is_chsign(lp, rowno[i]), value);\n      }\n      SET_MAT_ijA(jj, rowno[i], colno, value);\n    }\n  }\n  else {\n    for(i = firstrow; i <= mat->rows; i++) {\n      if(!addto[i])\n        continue;\n      value = column[i];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      if(mat->is_roworder) {    /* Fix following Ingmar Stein bug report 12.10.2006 */\n        if(isA && doscale)\n          value = scaled_mat(lp, value, colno, i);\n        if(isA)\n          value = my_chsign(is_chsign(lp, colno), value);\n      }\n      else {\n        if(isA && doscale)\n          value = scaled_mat(lp, value, i, colno);\n        if(isA)\n          value = my_chsign(is_chsign(lp, i), value);\n      }\n      SET_MAT_ijA(jj, i, colno, value);\n      jj++;\n    }\n  }\n  mat->row_end_valid = FALSE;\n\n  /* Finish and return */\nDone:\n  if(saved != 0)\n    column[0] = saved;\n  FREE(addto);\n  return( TRUE );\n\n}\n\nSTATIC MYBOOL mat_mergemat(MATrec *target, MATrec *source, MYBOOL usecolmap)\n{\n  lprec *lp = target->lp;\n  int   i, ix, iy, n, *colmap = NULL;\n  REAL  *colvalue = NULL;\n\n  if((target->rows < source->rows) || !allocREAL(lp, &colvalue, target->rows+1, FALSE))\n    return( FALSE );\n\n  if(usecolmap) {\n    n = source->col_tag[0];\n    allocINT(lp, &colmap, n+1, FALSE);\n    for(i = 1; i <= n; i++)\n      colmap[i] = i;\n    hpsortex(source->col_tag, n, 1, sizeof(*colmap), FALSE, compareINT, colmap);\n  }\n  else\n    n = source->columns;\n  for(i = 1; i <= n; i++) {\n    if(!usecolmap && (mat_collength(source, i) == 0))\n      continue;\n    if(usecolmap) {\n      ix = colmap[i];\n      if(ix <= 0)\n        continue;\n      iy = source->col_tag[i];\n      if(iy <= 0)\n        continue;\n    }\n    else\n      ix = iy = i;\n    mat_expandcolumn(source, ix, colvalue, NULL, FALSE);\n    mat_setcol(target, iy, 0, colvalue, NULL, FALSE, FALSE);\n  }\n\n  FREE( colvalue );\n  FREE( colmap );\n\n  return( TRUE );\n}\n\nSTATIC int mat_nz_unused(MATrec *mat)\n{\n  return( mat->mat_alloc - mat->col_end[mat->columns] );\n}\n\n#if 0\nSTATIC MYBOOL mat_setrow(MATrec *mat, int rowno, int count, REAL *row, int *colno, MYBOOL doscale, MYBOOL checkrowmode)\n{\n  lprec   *lp = mat->lp;\n  int     delta;\n  int k, kk, i, ii, j, jj = 0, jj_j, elmnr, orignr, newnr, firstcol, rownr, colnr, matz = 0;\n  MYBOOL  *addto = NULL, isA, isNZ;\n  REAL    value = 0.0, saved = 0;\n\n  /* Check if we are in row order mode and should add as column instead;\n     the matrix will be transposed at a later stage */\n  if(checkrowmode && mat->is_roworder)\n    return( mat_setcol(mat, rowno, count, row, colno, doscale, FALSE) );\n\n  /* Do initialization and validation */\n  if(!mat_validate(mat))\n    return( FALSE );\n  isA = (MYBOOL) (mat == lp->matA);\n  isNZ = (MYBOOL) (colno != NULL);\n  if(!isNZ)\n    count = mat->columns;\n  else if((count < 0) || (count > mat->columns))\n    return( FALSE );\n  if(isNZ && (count > 0)) {\n    if(count > 1)\n      sortREALByINT(row, (int *) colno, count, 0, TRUE);\n    if((colno[0] < 1) || (colno[count-1] > mat->columns))\n      return( FALSE );\n  }\n\n  /* Capture OF definition in row mode */\n  if(isA && mat->is_roworder) {\n    lp->orig_obj[rowno] = 0;\n    if(isNZ && (count > 0) && (colno[0] == 0)) {\n      value = row[0];\n      if(doscale)\n        value = scaled_mat(lp, value, 0, rowno);\n      value = my_chsign(is_maxim(lp), value);\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      lp->orig_obj[rowno] = value;\n      count--;\n      row++;\n      colno++;\n    }\n    else if(!isNZ && (row[0] != 0)) {\n      value = saved = row[0];\n      if(doscale)\n        value = scaled_mat(lp, value, 0, rowno);\n      value = my_chsign(is_maxim(lp), value);\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      lp->orig_obj[rowno] = value;\n      row[0] = 0;\n    }\n    else {\n      lp->orig_obj[rowno] = 0;\n      value = 0;\n    }\n  }\n\n  /* Optionally tally and map the new non-zero values */\n  i  = mat->row_end[rowno-1];\n  ii = mat->row_end[rowno];     // ****** KE 20070106 - was \"-1\"\n  firstcol = mat->columns + 1;\n  if(isNZ) {\n    /* See if we can do fast in-place replacements of leading items */\n    colnr = 1; /* initialise in case of an empty row */\n    while((i < ii) /* && (count > 0) */ && ((colnr = ROW_MAT_COLNR(i)) == *colno) && (count > 0)) {\n      value = *row;             // ****** KE 20080111 - Added line\n      if(mat->is_roworder) {\n        if(isA && doscale)\n          value = scaled_mat(lp, value, colnr, rowno);\n        if(isA)\n          value = my_chsign(is_chsign(lp, colnr), value);\n      }\n      else {\n        if(isA && doscale)\n          value = scaled_mat(lp, value, rowno, colnr);\n        if(isA)\n          value = my_chsign(is_chsign(lp, rowno), value);\n      }\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n      if(value == 0)\n        matz++;\n#endif\n      ROW_MAT_VALUE(i) = value;\n      i++;\n      count--;\n      row++;\n      colno++;\n    }\n  if(i >= ii)\n      colnr = 0;\n    /* Proceed with remaining entries */\n    newnr = count;\n    if(newnr > 0)\n      firstcol = colno[0];\n  }\n  else {\n    newnr = 0;\n    kk = mat->columns;\n    if(i < ii)\n      colnr = ROW_MAT_COLNR(i);\n    else\n      colnr = 0;\n    for(k = 1; k <= kk; k++) {\n      value = row[k];           // ****** KE 20080111 - Added line\n      if(fabs(value) > mat->epsvalue) {\n        /* See if we can do fast in-place replacements of leading items */\n        if((addto == NULL) && (i < ii) && (colnr == k)) {\n          if(mat->is_roworder) {\n            if(isA && doscale)\n              value = scaled_mat(lp, value, colnr, rowno);\n            if(isA)\n              value = my_chsign(is_chsign(lp, colnr), value);\n          }\n          else {\n            if(isA && doscale)\n              value = scaled_mat(lp, value, rowno, colnr);\n            if(isA)\n              value = my_chsign(is_chsign(lp, rowno), value);\n          }\n#ifdef DoMatrixRounding\n          value = roundToPrecision(value, mat->epsvalue);\n          if(value == 0)\n            matz++;\n#endif\n          ROW_MAT_VALUE(i) = value;\n          i++;\n          if(i < ii)\n            colnr = ROW_MAT_COLNR(i);\n          else\n            colnr = 0;\n        }\n        /* Otherwise update addto-list */\n        else {\n          if(addto == NULL) {\n            if(!allocMYBOOL(lp, &addto, mat->columns + 1, TRUE))\n              return( FALSE );\n            firstcol = k;\n          }\n          addto[k] = TRUE;\n          newnr++;\n        }\n      }\n    }\n  }\n  if(newnr == 0)\n   if (FALSE)\n    return( TRUE );\n\n  /* Make sure we have enough matrix space */\n  if((newnr > 0) && (mat_nz_unused(mat) <= newnr) && !inc_mat_space(mat, newnr)) {\n    newnr = 0;\n    goto Done;\n  }\n\n  /* Pack initial entries if existing row data has a lower column\n     start index than the first index of the new vector */\n  orignr = mat_nonzeros(mat);\n  /* delta = newnr - mat_rowlength(mat, rowno);*/\n  kk = 0;\n  if(rowno == 0)\n    ii = 0;\n  else\n    ii = mat->row_end[rowno-1];\n\n  if((orignr == 0) || (ii >= orignr))\n    j = firstcol;\n  else if(isNZ||TRUE)\n    j = colnr;\n  else\n    j = ROW_MAT_COLNR(ii); /* first column with a value on that row */\n\n  jj = mat->col_end[firstcol-1];  /* Set the index of the insertion point for the first new value */\n  if(jj >= orignr)\n    colnr = firstcol;\n  else\n    colnr = COL_MAT_COLNR(jj); /* first column with a value starting from firstcol */\n\n  if((j > 0) && (j < colnr)) {\n    jj = elmnr = mat->col_end[j-1];\n    for( ; j < colnr; j++) {\n      /* Shift entries in current column */\n      k = mat->col_end[j];\n      for( ; jj < k; jj++) {\n        if(COL_MAT_ROWNR(jj) != rowno) {\n          COL_MAT_COPY(elmnr, jj);\n          elmnr++;\n        }\n      }\n      /* Update next column start index */\n      mat->col_end[j] = elmnr;\n    }\n    delta = elmnr - jj;  /* The shrinkage count */\n  }\n  else {\n    delta = 0;\n    /* Adjust for case where we simply append values - jj is initially the first column item */\n    if((mat->col_end[firstcol] == orignr) && 0)\n      jj = orignr;\n  }\n\n  /* Make sure we have sufficient space for any additional entries and move existing data down;\n     this ensures that we only have to relocate matrix elements up in the next stage */\n  jj_j = MAX(0, newnr + delta);\n  if(jj_j > 0) {\n    if(!inc_mat_space(mat, jj_j)) {\n      FREE(addto);\n      return( FALSE );\n    }\n    if(orignr-jj > 0) {\n      COL_MAT_MOVE(jj+jj_j, jj, orignr-jj);\n    }\n    jj += jj_j;\n  }\n\n  /* Handle case where the matrix was empty before (or we can simply append) */\n  if((delta >= 0) && (mat->col_end[firstcol] == orignr) && 0) {\n    if(isNZ)\n      elmnr = count;\n    else\n      elmnr = mat->columns;\n    jj_j = mat->col_end[firstcol];\n    for(newnr = 0; newnr < elmnr; newnr++) {\n      if(isNZ)\n        colnr = colno[newnr];\n      else\n        colnr = newnr + 1;\n      /* Update column start position if we have crossed a column */\n      while(colnr > firstcol) {\n        mat->col_end[firstcol] = jj_j;\n        firstcol++;\n      }\n      if(isNZ || ((addto != NULL) && addto[colnr])) {\n        if(isNZ)\n          value = row[newnr];\n        else\n          value = row[colnr];\n        if(isA && doscale)\n          value = scaled_mat(lp, value, rowno, colnr);\n        if(isA)\n          value = my_chsign(is_chsign(lp, rowno), value);\n#ifdef DoMatrixRounding\n        value = roundToPrecision(value, mat->epsvalue);\n        if(value == 0)\n          matz++;\n#endif\n        SET_MAT_ijA(jj_j, rowno, colnr, value);\n        jj_j++;\n        /* Update last column start position */\n        mat->col_end[firstcol] = jj_j;\n        firstcol++;\n      }\n    }\n\n    /* Make sure we update tail empty column offsets */\n    while(firstcol <= mat->columns) {\n      mat->col_end[firstcol] = jj_j;\n      firstcol++;\n    }\n    jj_j = 0;\n  }\n\n  /* Start from the top of the first non-zero column of the new row */\n  elmnr = orignr + jj_j;\n  if(jj <= elmnr) {\n    if(isNZ)\n      newnr = 0;\n    else\n      newnr = firstcol - 1;\n    j = jj - mat->col_end[firstcol-1];\n    colnr = firstcol;\n    while((jj < elmnr) || (newnr < count)) {\n\n      /* Update column start position if we have crossed a column */\n      while(colnr > firstcol) {\n        mat->col_end[firstcol] = kk;\n        firstcol++;\n      }\n\n      /* See if we have a row equal to or greater than the target row */\n      jj_j = jj - j;\n      if(jj < elmnr) {\n        rownr = COL_MAT_ROWNR(jj);\n        colnr = COL_MAT_COLNR(jj);\n      }\n      else {\n        rownr = rowno;\n        if(!isNZ)                              /* KE added this conditional on 13.9.2006 */\n          colnr = firstcol + 1;\n        else\n          colnr = mat->columns + 1;\n      }\n\n      if(isNZ) {\n        if(newnr < count)\n          kk = colno[newnr];\n        else\n          kk = mat->columns + 1;\n      }\n      else\n        kk = newnr + 1;\n\n      /* Test if there is an available new item ... */\n      if((isNZ && (kk > colnr)) ||                    /* If this is not the case */\n         (!isNZ && ((kk > colnr) || (!addto[kk])))) {\n        /* DELETE if there is an existing value */\n        if(!isNZ && (kk <= colnr))\n          newnr++;\n        if(rownr == rowno) {\n          kk = jj_j;\n          j++;\n          jj++;\n          continue;\n        }\n        /* KEEP otherwise and move entry up */\n        if(!isNZ && (colnr > kk)) {\n          colnr = kk;\n          kk = jj_j;\n          continue;\n        }\n      }\n      else if((colnr > kk) ||                         /* Existing column index > new => INSERT */\n              ((colnr == kk) && (rownr >= rowno)) ) { /* Same column index, existing row >= target row => INSERT/REPLACE */\n\n        if(isNZ)\n          value = row[newnr];\n        else\n          value = row[newnr+1];\n        newnr++;\n        if(isA && doscale)\n          value = scaled_mat(lp, value, rowno, kk);\n        if(isA)\n          value = my_chsign(is_chsign(lp, rowno), value);\n#ifdef DoMatrixRounding\n        value = roundToPrecision(value, mat->epsvalue);\n        if(value == 0)\n          matz++;\n#endif\n        SET_MAT_ijA(jj_j, rowno, kk, value);\n\n        /* Adjust if we have inserted an element */\n        if((colnr > kk) || (rownr > rowno)) {\n          j--;\n          jj--;\n        }\n        colnr = kk;\n        kk = jj_j;\n        jj++;\n        continue;\n      }\n\n      /* Shift the matrix element up by the active difference */\n      if(jj_j != jj) {\n        COL_MAT_COPY(jj_j, jj);\n      }\n      kk = jj_j;\n      jj++;\n\n    }\n\n    /* Update pending / incomplete column start position */\n    while(colnr > firstcol) {\n      mat->col_end[firstcol] = kk;\n      firstcol++;\n    }\n\n    /* Make sure we update tail column offsets */\n    jj_j = jj - j;\n    while(firstcol <= mat->columns) {\n      mat->col_end[firstcol] = jj_j;\n      firstcol++;\n    }\n  }\n\n  /* Compact in the case that we added zeros and set flag for row index update */\n  if(matz > 0)\n    mat_zerocompact(mat);\n  mat->row_end_valid = FALSE;\n\nDone:\n  if(saved != 0)\n    row[0] = saved;\n  FREE(addto);\n  return( (MYBOOL) (newnr > 0) );\n\n}\n\n#else\n\nSTATIC MYBOOL mat_setrow(MATrec *mat, int rowno, int count, REAL *row, int *colno, MYBOOL doscale, MYBOOL checkrowmode)\n{\n  lprec   *lp = mat->lp;\n  int     delta, delta1;\n  int k, i, ii, j, jj_j, lendense,\n          origidx = 0, newidx, orignz, newnz,\n          rownr, colnr, colnr1;\n  MYBOOL  isA, isNZ;\n  REAL    value = 0.0;\n\n  /* Check if we are in row order mode and should add as column instead;\n     the matrix will be transposed at a later stage */\n  if(checkrowmode && mat->is_roworder)\n    return( mat_setcol(mat, rowno, count, row, colno, doscale, FALSE) );\n\n  /* Do initialization and validation */\n  if(!mat_validate(mat))\n    return( FALSE );\n  isA = (MYBOOL) (mat == lp->matA);\n  if(doscale && isA && !lp->scaling_used)\n    doscale = FALSE;\n  isNZ = (MYBOOL) (colno != NULL);\n  lendense = (mat->is_roworder ? lp->rows : lp->columns);\n  if((count < 0) || (count > lendense))\n    return( FALSE );\n  colnr1 = lendense + 1;\n\n  /* Capture OF definition in row mode */\n  if(isA && mat->is_roworder) {\n    lp->orig_obj[rowno] = 0;\n    if((count > 0) && (colno[0] == 0)) {\n      value = row[0];\n      if(doscale)\n        value = scaled_mat(lp, value, 0, rowno);\n      value = my_chsign(is_maxim(lp), value);\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      lp->orig_obj[rowno] = value;\n      if(isNZ) {\n        colno++;\n        row++;\n        count--;\n      }\n    }\n    else {\n      lp->orig_obj[rowno] = 0;\n      value = 0;\n    }\n  }\n\n  /* Make local working data copies */\n  if(!isNZ) {\n    REAL *tmprow = NULL;\n    if(!allocINT(lp, &colno, lendense+1, FALSE))\n      return( FALSE );\n    newnz = 0;\n    for(i = 1; i <= lendense; i++)\n      if((value = row[i]) != 0) {\n        if((tmprow == NULL) && !allocREAL(lp, &tmprow, lendense-i+1, FALSE)) {\n          FREE(colno);\n          return( FALSE );\n        }\n        tmprow[newnz] = value;\n        colno[newnz++] = i;\n      }\n    count = newnz;\n    row = tmprow;\n  }\n  else {\n    int *tmpcolno = NULL;\n    if(!allocINT(lp, &tmpcolno, lendense, FALSE))\n      return( FALSE );\n    newnz = count;\n    MEMCOPY(tmpcolno, colno, newnz);\n    colno = tmpcolno;\n    if(newnz > 1)\n      sortREALByINT(row, (int *) colno, newnz, 0, TRUE);\n    if((newnz > 0) && ((colno[0] < 0) || (colno[newnz-1] > lendense))) {\n      FREE(colno);\n      newnz = 0;\n      return( FALSE );\n    }\n  }\n\n  /* Make sure we have enough matrix space */\n  i  = mat->row_end[rowno-1];\n  ii = mat->row_end[rowno];\n  delta1 = delta = count - (ii-i);\n  colnr1 = (newnz > 0 ? colno[0] : lendense+1);\n\n  /* Pack initial entries if existing row data has a lower column\n     start index than the first index of the new vector */\n  orignz = mat_nonzeros(mat);\n  j = (i >= orignz ? colnr1 : ROW_MAT_COLNR(i));\n\n  /* Index of the column-top insertion point for the first new value */\n  origidx = mat->col_end[colnr1-1];\n  colnr = (origidx >= orignz ? colnr1 : COL_MAT_COLNR(origidx));\n\n  if(j < colnr) {\n    origidx = newidx = mat->col_end[j-1];\n    for( ; j < colnr; j++) {\n      /* Shift entries in current column */\n      jj_j = mat->col_end[j];\n      for( ; origidx < jj_j; origidx++) {\n        if(COL_MAT_ROWNR(origidx) != rowno) {\n          if(newidx != origidx) {\n            COL_MAT_COPY(newidx, origidx);\n          }\n          newidx++;\n        }\n      }\n      /* Update next column start index */\n      mat->col_end[j] = newidx;\n    }\n    delta = newidx - origidx;  /* The first stage element shrinkage count */\n  }\n  else {\n    delta = 0;\n    newidx = origidx;\n  }\n\n  /* Make sure we have sufficient space for any additional entries and move existing data down;\n     this ensures that we only have to relocate matrix elements up in the next stage */\n  jj_j = MAX(0, (int) newnz + delta);\n\n  j = !((orignz == lendense) && (newnz == orignz) && (delta1 == 0)) && (jj_j > 0) && (orignz > origidx);\n\n  if ((j) && (jj_j > delta1))\n    delta1 = jj_j;\n\n  if((delta1 > 0) && (mat_nz_unused(mat) <= delta1) && !inc_mat_space(mat, delta1)) {\n    newnz = 0;\n    goto Done;\n  }\n\n  if(j) {\n    COL_MAT_MOVE(origidx+jj_j, origidx, orignz-origidx);\n    origidx += jj_j;\n    orignz += jj_j;\n  }\n\n  /* Start from the top of the first non-zero column of the new row */\n  newnz = 0;\n  j = origidx - mat->col_end[colnr1-1];\n  k = colnr1;  /* Last column for which col_end is valid/updated */\n  while((colnr1 <= lendense) || (origidx < orignz)) {\n\n    /* Get the column index of the active update item */\n    if(newnz < count)\n      colnr1 = colno[newnz];\n    else\n      colnr1 = lendense + 1;\n\n    /* Get coordinate of active existing matrix entries */\n    if(origidx < orignz) {\n      rownr = COL_MAT_ROWNR(origidx);\n      colnr = COL_MAT_COLNR(origidx);\n    }\n    else {\n      if(colnr1 > lendense)\n        break;\n      rownr = rowno;\n      colnr = lendense + 1;\n    }\n\n    /* Update column start position if we just crossed into a column */\n    jj_j = origidx - j;\n    i = MIN(colnr, colnr1);\n    for(; k < i; k++)\n      mat->col_end[k] = jj_j;\n\n    /* Test if there is an available new item ... */\n    if(colnr1 > colnr) {             /* If this is not the case */\n      /* DELETE if there is an existing value */\n      if(rownr == rowno) {\nForceDelete:\n        j++;\n        delta--;\n        origidx++;\n        continue;\n      }\n    }\n    else if((colnr > colnr1) ||                         /* Existing column index > new => INSERT */\n            ((colnr == colnr1) && (rownr >= rowno)) ) { /* Same column index, existing row >= target row => INSERT/REPLACE */\n\n      value = row[newnz];\n      newnz++;\n      if(isA && doscale)\n        value = scaled_mat(lp, value, rowno, colnr1);\n      if(isA)\n        value = my_chsign(is_chsign(lp, rowno), value);\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n      if(value == 0) {\n        if((colnr > colnr1) || (rownr > rowno))\n        ;\n        else\n          goto ForceDelete;\n      }\n#endif\n      SET_MAT_ijA(jj_j, rowno, colnr1, value);\n\n      /* Adjust if we have inserted an element */\n      if((colnr > colnr1) || (rownr > rowno)) {\n        j--;\n        origidx--;\n        jj_j++;\n        delta++;\n      }\n      origidx++;\n      continue;\n    }\n\n    /* Shift the matrix element up by the active difference */\n    if(jj_j != origidx) {\n      COL_MAT_COPY(jj_j, origidx);\n    }\n    origidx++;\n  }\n\n  /* Update pending / incomplete column start position */\n  jj_j = origidx - j;\n  for(; k <= lendense; k++)\n    mat->col_end[k] = jj_j;\n  mat->row_end_valid = FALSE;\n\nDone:\n  if(!isNZ)\n    FREE(row);\n  FREE(colno);\n  return( (MYBOOL) (newnz > 0) );\n\n} /* mat_setrow */\n#endif\n\nSTATIC int mat_appendrow(MATrec *mat, int count, REAL *row, int *colno, REAL mult, MYBOOL checkrowmode)\n{\n  int    i, j, jj = 0, stcol, elmnr, orignr, newnr, firstcol;\n  MYBOOL *addto = NULL, isA, isNZ;\n  REAL   value, saved = 0;\n  lprec  *lp = mat->lp;\n\n  /* Check if we are in row order mode and should add as column instead;\n     the matrix will be transposed at a later stage */\n  if(checkrowmode && mat->is_roworder)\n    return( mat_appendcol(mat, count, row, colno, mult, FALSE) );\n\n  /* Do initialization and validation */\n  isA = (MYBOOL) (mat == lp->matA);\n  isNZ = (MYBOOL) (colno != NULL);\n  if(isNZ && (count > 0)) {\n    if(count > 1)\n      sortREALByINT(row, colno, count, 0, TRUE);\n    if((colno[0] < 1) || (colno[count-1] > mat->columns))\n      return( 0 );\n  }\n  /* else if((row != NULL) && !mat->is_roworder) */\n  else if(!isNZ && (row != NULL) && !mat->is_roworder)\n    row[0] = 0;\n\n  /* Capture OF definition in row mode */\n  if(isA && mat->is_roworder) {\n    if(isNZ && (colno[0] == 0)) {\n      value = row[0];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      value = scaled_mat(lp, value, 0, lp->columns);\n      value = my_chsign(is_maxim(lp), value);\n      lp->orig_obj[lp->columns] = value;\n      count--;\n      row++;\n      colno++;\n    }\n    else if(!isNZ && (row != NULL) && (row[0] != 0)) {\n      value = saved = row[0];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      value = scaled_mat(lp, value, 0, lp->columns);\n      value = my_chsign(is_maxim(lp), value);\n      lp->orig_obj[lp->columns] = value;\n      row[0] = 0;\n    }\n    else\n      lp->orig_obj[lp->columns] = 0;\n  }\n\n  /* Optionally tally and map the new non-zero values */\n  firstcol = mat->columns + 1;\n  if(isNZ) {\n    newnr = count;\n    if(newnr) {\n      firstcol = colno[0];\n      jj = colno[newnr - 1];\n    }\n  }\n  else {\n    newnr = 0;\n    if(row != NULL) {\n      if(!allocMYBOOL(lp, &addto, mat->columns + 1, TRUE)) {\n        return( newnr );\n      }\n      for(i = mat->columns; i >= 1; i--) {\n        if(fabs(row[i]) > mat->epsvalue) {\n          addto[i] = TRUE;\n          firstcol = i;\n          newnr++;\n        }\n      }\n    }\n  }\n\n  /* Make sure we have sufficient space */\n  if(!inc_mat_space(mat, newnr)) {\n    newnr = 0;\n    goto Done;\n  }\n\n  /* Insert the non-zero constraint values */\n  orignr = mat_nonzeros(mat) - 1;\n  elmnr = orignr + newnr;\n\n  for(j = mat->columns; j >= firstcol; j--) {\n    stcol = mat->col_end[j] - 1;\n    mat->col_end[j] = elmnr + 1;\n\n   /* Add a new non-zero entry */\n    if(((isNZ) && (j == jj)) || ((addto != NULL) && (addto[j]))) {\n      newnr--;\n      if(isNZ) {\n        value = row[newnr];\n        if(newnr)\n          jj = colno[newnr - 1];\n        else\n          jj = 0;\n      }\n      else\n        value = row[j];\n#ifdef DoMatrixRounding\n      value = roundToPrecision(value, mat->epsvalue);\n#endif\n      value *= mult;\n      if(isA) {\n        if(mat->is_roworder)\n          value = my_chsign(is_chsign(lp, j), value);\n        value = scaled_mat(lp, value, mat->rows, j);\n      }\n      SET_MAT_ijA(elmnr, mat->rows, j, value);\n      elmnr--;\n    }\n\n   /* Shift previous column entries down */\n    i = stcol - mat->col_end[j-1] + 1;\n    if(i > 0) {\n      orignr -= i;\n      elmnr  -= i;\n      COL_MAT_MOVE(elmnr+1, orignr+1, i);\n    }\n  }\n\nDone:\n  if(saved != 0)\n    row[0] = saved;\n  FREE(addto);\n\n  return( newnr );\n\n}\n\nSTATIC int mat_appendcol(MATrec *mat, int count, REAL *column, int *rowno, REAL mult, MYBOOL checkrowmode)\n{\n  int     i, row, elmnr, lastnr;\n  REAL    value;\n  MYBOOL  isA, isNZ;\n  lprec   *lp = mat->lp;\n\n  /* Check if we are in row order mode and should add as row instead;\n     the matrix will be transposed at a later stage */\n  if(checkrowmode && mat->is_roworder)\n    return( mat_appendrow(mat, count, column, rowno, mult, FALSE) );\n\n  /* Make sure we have enough space */\n/*\n  if(!inc_mat_space(mat, mat->rows+1))\n    return( 0 );\n*/\n  if(column == NULL)\n    i = 0;\n  else if(rowno != NULL)\n    i = count;\n  else {\n    int nrows = mat->rows;\n\n    elmnr = 0;\n    for(i = 1; i <= nrows; i++)\n      if(column[i] != 0)\n        elmnr++;\n    i = elmnr;\n  }\n  if((mat_nz_unused(mat) <= i) && !inc_mat_space(mat, i))\n    return( 0 );\n\n  /* Do initialization and validation */\n  isA = (MYBOOL) (mat == lp->matA);\n  isNZ = (MYBOOL) (column == NULL || rowno != NULL);\n  if(isNZ && (count > 0)) {\n    if(count > 1)\n      sortREALByINT(column, rowno, count, 0, TRUE);\n    if((rowno[0] < 0))\n      return( 0 );\n  }\n  if(rowno != NULL)\n    count--;\n\n  /* Append sparse regular constraint values */\n  elmnr = mat->col_end[mat->columns - 1];\n  if(column != NULL) {\n    row = -1;\n    for(i = ((isNZ || !mat->is_roworder) ? 0 : 1); i <= count ; i++) {\n      value = column[i];\n      if(fabs(value) > mat->epsvalue) {\n        if(isNZ) {\n          lastnr = row;\n          row = rowno[i];\n          /* Check if we have come to the Lagrangean constraints */\n          if(row > mat->rows)\n            break;\n          if(row <= lastnr)\n            return( -1 );\n        }\n        else\n          row = i;\n#ifdef DoMatrixRounding\n        value = roundToPrecision(value, mat->epsvalue);\n#endif\n        if(mat->is_roworder)\n          value *= mult;\n        else if(isA) {\n          value = my_chsign(is_chsign(lp, row), value);\n          value = scaled_mat(lp, value, row, mat->columns);\n          if(!mat->is_roworder && (row == 0)) {\n            lp->orig_obj[mat->columns] = value;\n            continue;\n          }\n        }\n\n       /* Store the item and update counters */\n        SET_MAT_ijA(elmnr, row, mat->columns, value);\n        elmnr++;\n      }\n    }\n\n   /* Fill dense Lagrangean constraints */\n    if(get_Lrows(lp) > 0)\n      mat_appendcol(lp->matL, get_Lrows(lp), column+mat->rows, NULL, mult, checkrowmode);\n\n  }\n\n /* Set end of data */\n  mat->col_end[mat->columns] = elmnr;\n\n  return( mat->col_end[mat->columns] - mat->col_end[mat->columns-1] );\n}\n\nSTATIC int mat_checkcounts(MATrec *mat, int *rownum, int *colnum, MYBOOL freeonexit)\n{\n  int i, j, n;\n  int *rownr;\n\n  if(rownum == NULL)\n    allocINT(mat->lp, &rownum, mat->rows + 1, TRUE);\n  if(colnum == NULL)\n    allocINT(mat->lp, &colnum, mat->columns + 1, TRUE);\n\n  for(i = 1 ; i <= mat->columns; i++) {\n    j = mat->col_end[i - 1];\n    n = mat->col_end[i];\n    rownr = &COL_MAT_ROWNR(j);\n    for(; j < n;\n        j++, rownr += matRowColStep) {\n      colnum[i]++;\n      rownum[*rownr]++;\n    }\n  }\n\n  n = 0;\n  if((mat->lp->do_presolve != PRESOLVE_NONE) &&\n     (mat->lp->spx_trace || (mat->lp->verbose > NORMAL))) {\n    for(j = 1; j <= mat->columns; j++)\n      if(colnum[j] == 0) {\n        n++;\n        report(mat->lp, FULL, \"mat_checkcounts: Variable %s is not used in any constraints\\n\",\n                              get_col_name(mat->lp, j));\n      }\n    for(i = 0; i <= mat->rows; i++)\n      if(rownum[i] == 0) {\n        n++;\n        report(mat->lp, FULL, \"mat_checkcounts: Constraint %s empty\\n\",\n                              get_row_name(mat->lp, i));\n      }\n  }\n\n  if(freeonexit) {\n    FREE(rownum);\n    FREE(colnum);\n  }\n\n  return( n );\n\n}\n\nSTATIC MYBOOL mat_validate(MATrec *mat)\n/* Routine to make sure that row mapping arrays are valid */\n{\n  int     i, j, je, *rownum;\n  int     *rownr, *colnr;\n\n  if(!mat->row_end_valid) {\n\n    MEMCLEAR(mat->row_end, mat->rows + 1);\n    allocINT(mat->lp, &rownum, mat->rows + 1, TRUE);\n\n    /* First tally row counts and then cumulate them */\n    j = mat_nonzeros(mat);\n    rownr = &COL_MAT_ROWNR(0);\n    for(i = 0; i < j; i++, rownr += matRowColStep)\n      mat->row_end[*rownr]++;\n    for(i = 1; i <= mat->rows; i++)\n      mat->row_end[i] += mat->row_end[i - 1];\n\n    /* Calculate the column index for every non-zero */\n    for(i = 1; i <= mat->columns; i++) {\n      j = mat->col_end[i - 1];\n      je = mat->col_end[i];\n      rownr = &COL_MAT_ROWNR(j);\n      colnr = &COL_MAT_COLNR(j);\n      for(; j < je; j++, rownr += matRowColStep, colnr += matRowColStep) {\n#ifdef Paranoia\n        if(/*(*colnr < 0) || (*colnr > mat->columns) || (Normally violated in primal phase 1) */\n           (*rownr < 0) || (*rownr > mat->rows)) {\n          report(mat->lp, SEVERE, \"mat_validate: Matrix value storage error row %d [0..%d], column %d [1..%d]\\n\",\n                                  *rownr, mat->rows, *colnr, mat->columns);\n          mat->lp->spx_status = UNKNOWNERROR;\n          return(FALSE);\n        }\n#endif\n        *colnr = i;\n        if(*rownr == 0)\n          mat_set_rowmap(mat, rownum[*rownr],\n                              *rownr, i, j);\n        else\n          mat_set_rowmap(mat, mat->row_end[*rownr - 1] + rownum[*rownr],\n                              *rownr, i, j);\n        rownum[*rownr]++;\n      }\n    }\n\n    FREE(rownum);\n    mat->row_end_valid = TRUE;\n  }\n\n  if(mat == mat->lp->matA)\n    mat->lp->model_is_valid = TRUE;\n  return( TRUE );\n}\n\nMYBOOL mat_get_data(lprec *lp, int matindex, MYBOOL isrow, int **rownr, int **colnr, REAL **value)\n{\n  MATrec *mat = lp->matA;\n\n#if MatrixRowAccess == RAM_Index\n  if(isrow)\n    matindex = mat->row_mat[matindex];\n  if(rownr != NULL)\n    *rownr = &COL_MAT_ROWNR(matindex);\n  if(colnr != NULL)\n    *colnr = &COL_MAT_COLNR(matindex);\n  if(value != NULL)\n    *value = &COL_MAT_VALUE(matindex);\n\n#else\n  if(isrow) {\n    if(rownr != NULL)\n      *rownr = &ROW_MAT_ROWNR(matindex);\n    if(colnr != NULL)\n      *colnr = &ROW_MAT_COLNR(matindex);\n    if(value != NULL)\n      *value = &ROW_MAT_VALUE(matindex);\n  }\n  else {\n    if(rownr != NULL)\n      *rownr = &COL_MAT_ROWNR(matindex);\n    if(colnr != NULL)\n      *colnr = &COL_MAT_COLNR(matindex);\n    if(value != NULL)\n      *value = &COL_MAT_VALUE(matindex);\n  }\n\n#endif\n\n  return( TRUE );\n}\n\n\nMYBOOL mat_set_rowmap(MATrec *mat, int row_mat_index, int rownr, int colnr, int col_mat_index)\n{\n#if MatrixRowAccess == RAM_Index\n  mat->row_mat[row_mat_index] = col_mat_index;\n\n#elif MatrixColAccess==CAM_Record\n  mat->row_mat[row_mat_index].rownr = rownr;\n  mat->row_mat[row_mat_index].colnr = colnr;\n  mat->row_mat[row_mat_index].value = COL_MAT_VALUE(col_mat_index);\n\n#else /* if MatrixColAccess==CAM_Vector */\n  mat->row_mat_rownr[row_mat_index] = rownr;\n  mat->row_mat_colnr[row_mat_index] = colnr;\n  mat->row_mat_value[row_mat_index] = COL_MAT_VALUE(col_mat_index);\n\n#endif\n\n  return( TRUE );\n}\n\n/* Implement combined binary/linear sub-search for matrix look-up */\nint mat_findelm(MATrec *mat, int row, int column)\n{\n  int low, high, mid, item;\n\n#if 0\n  if(mat->row_end_valid && (row > 0) &&\n     (ROW_MAT_COLNR(mat->row_mat[(low = mat->row_end[row-1])]) == column))\n    return(low);\n#endif\n\n  if((column < 1) || (column > mat->columns)) {\n    report(mat->lp, IMPORTANT, \"mat_findelm: Column %d out of range\\n\", column);\n    return( -1 );\n  }\n  if((row < 0) || (row > mat->rows)) {\n    report(mat->lp, IMPORTANT, \"mat_findelm: Row %d out of range\\n\", row);\n    return( -1 );\n  }\n\n  low = mat->col_end[column - 1];\n  high = mat->col_end[column] - 1;\n  if(low > high)\n    return( -2 );\n\n /* Do binary search logic */\n  mid = (low+high) / 2;\n  item = COL_MAT_ROWNR(mid);\n  while(high - low > LINEARSEARCH) {\n    if(item < row) {\n      low = mid + 1;\n      mid = (low+high) / 2;\n      item = COL_MAT_ROWNR(mid);\n    }\n    else if(item > row) {\n      high = mid - 1;\n      mid = (low+high) / 2;\n      item = COL_MAT_ROWNR(mid);\n    }\n    else {\n      low = mid;\n      high = mid;\n    }\n  }\n\n /* Do linear scan search logic */\n  if((high > low) && (high - low <= LINEARSEARCH)) {\n    item = COL_MAT_ROWNR(low);\n    while((low < high) && (item < row)) {\n      low++;\n      item = COL_MAT_ROWNR(low);\n    }\n    if(item == row)\n      high = low;\n  }\n\n  if((low == high) && (row == item))\n    return( low );\n  else\n    return( -2 );\n}\n\nint mat_findins(MATrec *mat, int row, int column, int *insertpos, MYBOOL validate)\n{\n  int low, high, mid, item, exitvalue, insvalue;\n\n#if 0\n  if(mat->row_end_valid && (row > 0) &&\n     (ROW_MAT_COLNR(mat->row_mat[(low = mat->row_end[row-1])]) == column)) {\n    insvalue = low;\n    exitvalue = low;\n    goto Done;\n  }\n#endif\n\n  insvalue = -1;\n\n  if((column < 1) || (column > mat->columns)) {\n    if((column > 0) && !validate) {\n      insvalue = mat->col_end[mat->columns];\n      exitvalue = -2;\n      goto Done;\n    }\n    report(mat->lp, IMPORTANT, \"mat_findins: Column %d out of range\\n\", column);\n    exitvalue = -1;\n    goto Done;\n  }\n  if((row < 0) || (row > mat->rows)) {\n    if((row >= 0) && !validate) {\n      insvalue = mat->col_end[column];\n      exitvalue = -2;\n      goto Done;\n    }\n    report(mat->lp, IMPORTANT, \"mat_findins: Row %d out of range\\n\", row);\n    exitvalue = -1;\n    goto Done;\n  }\n\n  low = mat->col_end[column - 1];\n  insvalue = low;\n  high = mat->col_end[column] - 1;\n  if(low > high) {\n    exitvalue = -2;\n    goto Done;\n  }\n\n /* Do binary search logic */\n  mid = (low+high) / 2;\n  item = COL_MAT_ROWNR(mid);\n  while(high - low > LINEARSEARCH) {\n    if(item < row) {\n      low = mid + 1;\n      mid = (low+high) / 2;\n      item = COL_MAT_ROWNR(mid);\n    }\n    else if(item > row) {\n      high = mid - 1;\n      mid = (low+high) / 2;\n      item = COL_MAT_ROWNR(mid);\n    }\n    else {\n      low = mid;\n      high = mid;\n    }\n  }\n\n /* Do linear scan search logic */\n  if((high > low) && (high - low <= LINEARSEARCH)) {\n    item = COL_MAT_ROWNR(low);\n    while((low < high) && (item < row)) {\n      low++;\n      item = COL_MAT_ROWNR(low);\n    }\n    if(item == row)\n      high = low;\n  }\n\n  insvalue = low;\n  if((low == high) && (row == item))\n    exitvalue = low;\n  else {\n    if((low < mat->col_end[column]) && (COL_MAT_ROWNR(low) < row))\n      insvalue++;\n    exitvalue = -2;\n  }\n\nDone:\n  if(insertpos != NULL)\n    (*insertpos) = insvalue;\n  return( exitvalue );\n}\n\nSTATIC REAL mat_getitem(MATrec *mat, int row, int column)\n{\n  int elmnr;\n\n#ifdef DirectOverrideOF\n  if((row == 0) && (mat == mat->lp->matA) && (mat->lp->OF_override != NULL))\n    return( mat->lp->OF_override[column] );\n  else\n#endif\n  {\n    elmnr = mat_findelm(mat, row, column);\n    if(elmnr >= 0)\n      return( COL_MAT_VALUE(elmnr) );\n    else\n      return( 0 );\n  }\n}\n\nSTATIC MYBOOL mat_additem(MATrec *mat, int row, int column, REAL delta)\n{\n  int elmnr;\n\n#ifdef DirectOverrideOF\n  if((row == 0) && (mat == mat->lp->matA) && (mat->lp->OF_override != NULL))\n    return( mat->lp->OF_override[column] );\n  else\n#endif\n  {\n    elmnr = mat_findelm(mat, row, column);\n    if(elmnr >= 0) {\n      COL_MAT_VALUE(elmnr) += delta;\n      return( TRUE );\n    }\n    else {\n      mat_setitem(mat, row, column, delta);\n      return( FALSE );\n    }\n  }\n}\n\nSTATIC MYBOOL mat_setitem(MATrec *mat, int row, int column, REAL value)\n{\n  return( mat_setvalue(mat, row, column, value, FALSE) );\n}\n\nSTATIC void mat_multrow(MATrec *mat, int row_nr, REAL mult)\n{\n  int i, k1, k2;\n\n#if 0\n  if(row_nr == 0) {\n    k2 = mat->col_end[0];\n    for(i = 1; i <= mat->columns; i++) {\n      k1 = k2;\n      k2 = mat->col_end[i];\n      if((k1 < k2) && (COL_MAT_ROWNR(k1) == row_nr))\n        COL_MAT_VALUE(k1) *= mult;\n    }\n  }\n  else if(mat_validate(mat)) {\n    if(row_nr == 0)\n      k1 = 0;\n    else\n#else\n  if(mat_validate(mat)) {\n    if(row_nr == 0)\n      k1 = 0;\n    else\n#endif\n    k1 = mat->row_end[row_nr-1];\n    k2 = mat->row_end[row_nr];\n    for(i = k1; i < k2; i++)\n      ROW_MAT_VALUE(i) *= mult;\n  }\n}\n\nSTATIC void mat_multcol(MATrec *mat, int col_nr, REAL mult, MYBOOL DoObj)\n{\n  int    i, ie;\n  MYBOOL isA;\n\n#ifdef Paranoia\n  if((col_nr < 1) || (col_nr > mat->columns)) {\n    report(mat->lp, IMPORTANT, \"mult_column: Column %d out of range\\n\", col_nr);\n    return;\n  }\n#endif\n  if(mult == 1.0)\n    return;\n\n  isA = (MYBOOL) (mat == mat->lp->matA);\n\n  ie = mat->col_end[col_nr];\n  for(i = mat->col_end[col_nr - 1]; i < ie; i++)\n    COL_MAT_VALUE(i) *= mult;\n  if(isA) {\n    if(DoObj)\n      mat->lp->orig_obj[col_nr] *= mult;\n    if(get_Lrows(mat->lp) > 0)\n      mat_multcol(mat->lp->matL, col_nr, mult, DoObj);\n  }\n}\n\nSTATIC void mat_multadd(MATrec *mat, REAL *lhsvector, int varnr, REAL mult)\n{\n  int               colnr;\n  register int      ib, ie, *matRownr;\n  register REAL     *matValue;\n\n  /* Handle case of a slack variable */\n  if(varnr <= mat->lp->rows) {\n    lhsvector[varnr] += mult;\n    return;\n  }\n\n  /* Do operation on the objective */\n  if(mat->lp->matA == mat)\n    lhsvector[0] += get_OF_active(mat->lp, varnr, mult);\n\n  /* Scan the constraint matrix target columns */\n  colnr = varnr - mat->lp->rows;\n  ib = mat->col_end[colnr - 1];\n  ie = mat->col_end[colnr];\n  if(ib < ie) {\n\n    /* Initialize pointers */\n    matRownr = &COL_MAT_ROWNR(ib);\n    matValue = &COL_MAT_VALUE(ib);\n\n    /* Then loop over all regular rows */\n    for(; ib < ie;\n        ib++, matValue += matValueStep, matRownr += matRowColStep) {\n      lhsvector[*matRownr] += mult * (*matValue);\n    }\n  }\n\n}\n\nSTATIC MYBOOL mat_setvalue(MATrec *mat, int Row, int Column, REAL Value, MYBOOL doscale)\n{\n  int    elmnr, lastelm, i, RowA = Row, ColumnA = Column;\n  MYBOOL isA;\n\n  /* This function is inefficient if used to add new matrix entries in\n     other places than at the end of the matrix. OK for replacing existing\n     a non-zero value with another non-zero value */\n  isA = (MYBOOL) (mat == mat->lp->matA);\n  if(mat->is_roworder)\n    swapINT(&Row, &Column);\n\n  /* Set small numbers to zero */\n  if(fabs(Value) < mat->epsvalue)\n    Value = 0;\n#ifdef DoMatrixRounding\n  else\n    Value = roundToPrecision(Value, mat->epsvalue);\n#endif\n\n  /* Check if we need to update column space */\n  if(Column > mat->columns) {\n    if(isA)\n      inc_col_space(mat->lp, ColumnA - mat->columns);\n    else\n      inc_matcol_space(mat, Column - mat->columns);\n  }\n\n  /* Find out if we already have such an entry, or return insertion point */\n  i = mat_findins(mat, Row, Column, &elmnr, FALSE);\n  if(i == -1)\n    return(FALSE);\n\n  if(isA)\n    set_action(&mat->lp->spx_action, ACTION_REBASE | ACTION_RECOMPUTE | ACTION_REINVERT);\n\n  if(i >= 0) {\n    /* there is an existing entry */\n    if(fabs(Value) > mat->epsvalue) { /* we replace it by something non-zero */\n      if(isA) {\n        Value = my_chsign(is_chsign(mat->lp, RowA), Value);\n        if(doscale && mat->lp->scaling_used)\n          Value = scaled_mat(mat->lp, Value, RowA, ColumnA);\n      }\n      COL_MAT_VALUE(elmnr) = Value;\n    }\n    else { /* setting existing non-zero entry to zero. Remove the entry */\n      /* This might remove an entire column, or leave just a bound. No\n          nice solution for that yet */\n\n      /* Shift up tail end of the matrix */\n      lastelm = mat_nonzeros(mat);\n#if 0\n      for(i = elmnr; i < lastelm ; i++) {\n        COL_MAT_COPY(i, i + 1);\n      }\n#else\n      lastelm -= elmnr;\n      COL_MAT_MOVE(elmnr, elmnr + 1, lastelm);\n#endif\n      for(i = Column; i <= mat->columns; i++)\n        mat->col_end[i]--;\n\n      mat->row_end_valid = FALSE;\n    }\n  }\n  else if(fabs(Value) > mat->epsvalue) {\n    /* no existing entry. make new one only if not nearly zero */\n    /* check if more space is needed for matrix */\n    if(!inc_mat_space(mat, 1))\n      return(FALSE);\n\n    if(Column > mat->columns) {\n      i = mat->columns + 1;\n      if(isA)\n        shift_coldata(mat->lp, i, ColumnA - mat->columns, NULL);\n      else\n        mat_shiftcols(mat, &i, Column - mat->columns, NULL);\n    }\n\n    /* Shift down tail end of the matrix by one */\n    lastelm = mat_nonzeros(mat);\n#if 1 /* Does compiler optimization work better here? */\n    for(i = lastelm; i > elmnr ; i--) {\n      COL_MAT_COPY(i, i - 1);\n    }\n#else\n    lastelm -= elmnr - 1;\n    COL_MAT_MOVE(elmnr + 1, elmnr, lastelm);\n#endif\n\n    /* Set new element */\n    if(isA) {\n      Value = my_chsign(is_chsign(mat->lp, RowA), Value);\n      if(doscale)\n        Value = scaled_mat(mat->lp, Value, RowA, ColumnA);\n    }\n    SET_MAT_ijA(elmnr, Row, Column, Value);\n\n    /* Update column indexes */\n    for(i = Column; i <= mat->columns; i++)\n      mat->col_end[i]++;\n\n    mat->row_end_valid = FALSE;\n  }\n\n  if(isA && (mat->lp->var_is_free != NULL) && (mat->lp->var_is_free[ColumnA] > 0))\n    return( mat_setvalue(mat, RowA, mat->lp->var_is_free[ColumnA], -Value, doscale) );\n  return(TRUE);\n}\n\nSTATIC MYBOOL mat_appendvalue(MATrec *mat, int Row, REAL Value)\n{\n  int *elmnr, Column = mat->columns;\n\n  /* Set small numbers to zero */\n  if(fabs(Value) < mat->epsvalue)\n    Value = 0;\n#ifdef DoMatrixRounding\n  else\n    Value = roundToPrecision(Value, mat->epsvalue);\n#endif\n\n  /* Check if more space is needed for matrix */\n  if(!inc_mat_space(mat, 1))\n    return(FALSE);\n\n#ifdef Paranoia\n  /* Check valid indeces */\n  if((Row < 0) || (Row > mat->rows)) {\n    report(mat->lp, SEVERE, \"mat_appendvalue: Invalid row index %d specified\\n\", Row);\n    return(FALSE);\n  }\n#endif\n\n  /* Get insertion point and set value */\n  elmnr = mat->col_end + Column;\n  SET_MAT_ijA((*elmnr), Row, Column, Value);\n\n  /* Update column count */\n  (*elmnr)++;\n  mat->row_end_valid = FALSE;\n\n  return(TRUE);\n}\n\nSTATIC MYBOOL mat_equalRows(MATrec *mat, int baserow, int comprow)\n{\n  MYBOOL status = FALSE;\n\n  if(mat_validate(mat)) {\n    int bj1 = 0, ej1, bj2 = 0, ej2;\n\n    /* Get starting and ending positions */\n    if(baserow >= 0)\n      bj1 = mat->row_end[baserow-1];\n    ej1 = mat->row_end[baserow];\n    if(comprow >= 0)\n      bj2 = mat->row_end[comprow-1];\n    ej2 = mat->row_end[comprow];\n    /* Fail if row lengths are unequal */\n    if((ej1-bj1) != (ej2-bj2))\n      return( status );\n\n    /* Compare column index and value, element by element */\n    for(; bj1 < ej1; bj1++, bj2++) {\n      if(COL_MAT_COLNR(bj1) != COL_MAT_COLNR(bj2))\n        break;\n#if 1\n      if(fabs(get_mat_byindex(mat->lp, bj1, TRUE, FALSE)-get_mat_byindex(mat->lp, bj2, TRUE, FALSE)) > mat->lp->epsprimal)\n#else\n      if(fabs(COL_MAT_VALUE(bj1)-COL_MAT_VALUE(bj2)) > mat->lp->epsprimal)\n#endif\n        break;\n    }\n    status = (MYBOOL) (bj1 == ej1);\n  }\n  return( status );\n}\n\nSTATIC int mat_findcolumn(MATrec *mat, int matindex)\n{\n  int j;\n\n  for(j = 1; j <= mat->columns; j++) {\n    if(matindex < mat->col_end[j])\n      break;\n  }\n  return(j);\n}\n\nSTATIC int mat_expandcolumn(MATrec *mat, int colnr, REAL *column, int *nzlist, MYBOOL signedA)\n{\n  MYBOOL  isA = (MYBOOL) (mat->lp->matA == mat);\n  int     i, ie, j, nzcount = 0;\n  REAL    *matValue;\n  int     *matRownr;\n\n  signedA &= isA;\n\n  /* Retrieve a column from the user data matrix A */\n  MEMCLEAR(column, mat->rows + 1);\n  if(isA) {\n    column[0] = mat->lp->orig_obj[colnr];\n    if(signedA && is_chsign(mat->lp, 0))\n      column[0] = -column[0];\n  }\n\n  i = mat->col_end[colnr - 1];\n  ie = mat->col_end[colnr];\n  matRownr = &COL_MAT_ROWNR(i);\n  matValue = &COL_MAT_VALUE(i);\n  for(; i < ie;\n      i++, matRownr += matRowColStep, matValue += matValueStep) {\n    j = *matRownr;\n    column[j] = *matValue;\n    if(signedA && is_chsign(mat->lp, j))\n      column[j] = -column[j];\n    nzcount++;\n    if(nzlist != NULL)\n      nzlist[nzcount] = j;\n  }\n  if(nzlist != NULL)\n    nzlist[0] = nzcount;\n  return( nzcount );\n}\n\nSTATIC MYBOOL mat_computemax(MATrec *mat)\n{\n  int  *rownr = &COL_MAT_ROWNR(0),\n       *colnr = &COL_MAT_COLNR(0),\n       i = 0, ie = mat->col_end[mat->columns], ez = 0;\n  REAL *value = &COL_MAT_VALUE(0), epsmachine = mat->lp->epsmachine, absvalue;\n\n  /* Prepare arrays */\n  if(!allocREAL(mat->lp, &mat->colmax, mat->columns_alloc+1, AUTOMATIC) ||\n     !allocREAL(mat->lp, &mat->rowmax, mat->rows_alloc+1, AUTOMATIC))\n     return( FALSE );\n  MEMCLEAR(mat->colmax, mat->columns+1);\n  MEMCLEAR(mat->rowmax, mat->rows+1);\n\n  /* Obtain the row and column maxima in one sweep */\n  mat->dynrange = mat->lp->infinite;\n  for(; i < ie;\n      i++, rownr += matRowColStep, colnr += matRowColStep, value += matValueStep) {\n    absvalue = fabs(*value);\n    SETMAX(mat->colmax[*colnr], absvalue);\n    SETMAX(mat->rowmax[*rownr], absvalue);\n    SETMIN(mat->dynrange, absvalue);\n    if(absvalue < epsmachine)\n      ez++;\n  }\n\n  /* Lastly, compute the global maximum and get the dynamic range */\n  for(i = 1; i <= mat->rows; i++)\n    SETMAX(mat->rowmax[0], mat->rowmax[i]);\n  mat->infnorm = mat->colmax[0] = mat->rowmax[0];\n  if(mat->dynrange == 0) {\n    report(mat->lp, SEVERE, \"%d matrix contains zero-valued coefficients.\\n\", ez);\n    mat->dynrange = mat->lp->infinite;\n  }\n  else {\n    mat->dynrange = mat->infnorm / mat->dynrange;\n    if(ez > 0)\n      report(mat->lp, IMPORTANT, \"%d matrix coefficients below machine precision were found.\\n\", ez);\n  }\n\n  return( TRUE );\n}\n\nSTATIC MYBOOL mat_transpose(MATrec *mat)\n{\n  int     i, j, nz, k;\n  MYBOOL  status;\n\n  status = mat_validate(mat);\n  if(status) {\n\n    /* Create a column-ordered sparse element list; \"column\" index must be shifted */\n    nz = mat_nonzeros(mat);\n    if(nz > 0) {\n#if MatrixColAccess==CAM_Record\n      MATitem *newmat;\n      newmat = (MATitem *) malloc((mat->mat_alloc) * sizeof(*(mat->col_mat)));\n      j = mat->row_end[0];\n      for(i = nz-1; i >= j ; i--) {\n        k = i-j;\n        newmat[k] = mat->col_mat[mat->row_mat[i]];\n        newmat[k].row_nr = newmat[k].col_nr;\n      }\n      for(i = j-1; i >= 0 ; i--) {\n        k = nz-j+i;\n        newmat[k] = mat->col_mat[mat->row_mat[i]];\n        newmat[k].row_nr = newmat[k].col_nr;\n      }\n      swapPTR((void **) &mat->col_mat, (void **) &newmat);\n      FREE(newmat);\n#else /*if MatrixColAccess==CAM_Vector*/\n      REAL *newValue = NULL;\n      int  *newRownr = NULL;\n      allocREAL(mat->lp, &newValue, mat->mat_alloc, FALSE);\n      allocINT(mat->lp, &newRownr, mat->mat_alloc, FALSE);\n\n      j = mat->row_end[0];\n      for(i = nz-1; i >= j ; i--) {\n        k = i-j;\n        newValue[k] = ROW_MAT_VALUE(i);\n        newRownr[k] = ROW_MAT_COLNR(i);\n      }\n      for(i = j-1; i >= 0 ; i--) {\n        k = nz-j+i;\n        newValue[k] = ROW_MAT_VALUE(i);\n        newRownr[k] = ROW_MAT_COLNR(i);\n      }\n\n      swapPTR((void **) &mat->col_mat_rownr, (void **) &newRownr);\n      swapPTR((void **) &mat->col_mat_value, (void **) &newValue);\n      FREE(newValue);\n      FREE(newRownr);\n#endif\n    }\n\n    /* Transfer row start to column start position; must adjust for different offsets */\n    if(mat->rows == mat->rows_alloc)\n      inc_matcol_space(mat, 1);\n    j = mat->row_end[0];\n    for(i = mat->rows; i >= 1; i--)\n      mat->row_end[i] -= j;\n    mat->row_end[mat->rows] = nz;\n    swapPTR((void **) &mat->row_end, (void **) &mat->col_end);\n\n    /* Swap arrays of maximum values */\n    swapPTR((void **) &mat->rowmax, (void **) &mat->colmax);\n\n    /* Swap array sizes */\n    swapINT(&mat->rows, &mat->columns);\n    swapINT(&mat->rows_alloc, &mat->columns_alloc);\n\n    /* Finally set current storage mode */\n    mat->is_roworder = (MYBOOL) !mat->is_roworder;\n    mat->row_end_valid = FALSE;\n  }\n  return(status);\n}\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Change-tracking routines                                                           */\n/* ---------------------------------------------------------------------------------- */\nSTATIC DeltaVrec *createUndoLadder(lprec *lp, int levelitems, int maxlevels)\n{\n  DeltaVrec *hold;\n\n  hold = (DeltaVrec *) malloc(sizeof(*hold));\n  hold->lp = lp;\n  hold->activelevel = 0;\n  hold->tracker = mat_create(lp, levelitems, 0, 0.0);\n  inc_matcol_space(hold->tracker, maxlevels);\n  return( hold );\n}\nSTATIC int incrementUndoLadder(DeltaVrec *DV)\n{\n  DV->activelevel++;\n  inc_matcol_space(DV->tracker, 1);\n  mat_shiftcols(DV->tracker, &(DV->activelevel), 1, NULL);\n  DV->tracker->columns++;\n  return(DV->activelevel);\n}\nSTATIC MYBOOL modifyUndoLadder(DeltaVrec *DV, int itemno, REAL target[], REAL newvalue)\n{\n  MYBOOL status;\n  int    varindex = itemno;\n  REAL   oldvalue = target[itemno];\n\n#ifndef UseMilpSlacksRCF  /* Check if we should include ranged constraints */\n  varindex -= DV->lp->rows;\n#endif\n  status = mat_appendvalue(DV->tracker, varindex, oldvalue);\n  target[itemno] = newvalue;\n  return(status);\n}\nSTATIC int countsUndoLadder(DeltaVrec *DV)\n{\n  if(DV->activelevel > 0)\n    return( mat_collength(DV->tracker, DV->activelevel) );\n  else\n    return( 0 );\n}\nSTATIC int restoreUndoLadder(DeltaVrec *DV, REAL target[])\n{\n  int iD = 0;\n\n  if(DV->activelevel > 0) {\n    MATrec *mat = DV->tracker;\n    int    iB = mat->col_end[DV->activelevel-1],\n           iE = mat->col_end[DV->activelevel],\n           *matRownr = &COL_MAT_ROWNR(iB);\n    REAL   *matValue = &COL_MAT_VALUE(iB),\n           oldvalue;\n\n    /* Restore the values */\n    iD = iE-iB;\n    for(; iB < iE; iB++, matValue += matValueStep, matRownr += matRowColStep) {\n      oldvalue = *matValue;\n#ifdef UseMilpSlacksRCF  /* Check if we should include ranged constraints */\n      target[(*matRownr)] = oldvalue;\n#else\n      target[DV->lp->rows+(*matRownr)] = oldvalue;\n#endif\n    }\n\n    /* Get rid of the changes */\n    mat_shiftcols(DV->tracker, &(DV->activelevel), -1, NULL);\n  }\n\n  return(iD);\n}\nSTATIC int decrementUndoLadder(DeltaVrec *DV)\n{\n  int deleted = 0;\n\n  if(DV->activelevel > 0) {\n    deleted = mat_shiftcols(DV->tracker, &(DV->activelevel), -1, NULL);\n    DV->activelevel--;\n    DV->tracker->columns--;\n  }\n  return(deleted);\n}\nSTATIC MYBOOL freeUndoLadder(DeltaVrec **DV)\n{\n  if((DV == NULL) || (*DV == NULL))\n    return(FALSE);\n\n  mat_free(&((*DV)->tracker));\n  FREE(*DV);\n  return(TRUE);\n}\n\nSTATIC MYBOOL appendUndoPresolve(lprec *lp, MYBOOL isprimal, REAL beta, int colnrDep)\n{\n  MATrec *mat;\n\n  /* Point to correct undo structure */\n  if(isprimal)\n    mat = lp->presolve_undo->primalundo->tracker;\n  else\n    mat = lp->presolve_undo->dualundo->tracker;\n\n  /* Append the data */\n  if((colnrDep > 0) && (beta != 0) &&\n     (mat != NULL) && (mat->col_tag[0] > 0)) {\n    int ix = mat->col_tag[0];\n#if 0\n    report(lp, NORMAL, \"appendUndoPresolve: %s %g * x%d\\n\",\n                       ( beta < 0 ? \"-\" : \"+\"), fabs(beta), colnrDep);\n#endif\n\n    /* Do normal user variable case */\n    if(colnrDep <= lp->columns)\n      mat_setvalue(mat, colnrDep, ix, beta, FALSE);\n\n    /* Handle case where a slack variable is referenced */\n    else {\n      int ipos, jx = mat->col_tag[ix];\n      mat_setvalue(mat, jx, ix, beta, FALSE);\n      jx = mat_findins(mat, jx, ix, &ipos, FALSE);\n      COL_MAT_ROWNR(ipos) = colnrDep;\n    }\n    return( TRUE );\n  }\n  else\n    return( FALSE );\n}\nSTATIC MYBOOL addUndoPresolve(lprec *lp, MYBOOL isprimal, int colnrElim, REAL alpha, REAL beta, int colnrDep)\n{\n  int       ix;\n  DeltaVrec **DV;\n  MATrec    *mat;\n  presolveundorec *psdata = lp->presolve_undo;\n\n  /* Point to and initialize undo structure at first call */\n  if(isprimal) {\n    DV = &(psdata->primalundo);\n    if(*DV == NULL) {\n      *DV = createUndoLadder(lp, lp->columns+1, lp->columns);\n      mat = (*DV)->tracker;\n      mat->epsvalue = lp->matA->epsvalue;\n      allocINT(lp, &(mat->col_tag), lp->columns+1, FALSE);\n      mat->col_tag[0] = 0;\n    }\n  }\n  else {\n    DV = &(psdata->dualundo);\n    if(*DV == NULL) {\n      *DV = createUndoLadder(lp, lp->rows+1, lp->rows);\n      mat = (*DV)->tracker;\n      mat->epsvalue = lp->matA->epsvalue;\n      allocINT(lp, &(mat->col_tag), lp->rows+1, FALSE);\n      mat->col_tag[0] = 0;\n    }\n  }\n  mat = (*DV)->tracker;\n#if 0\n  report(lp, NORMAL, \"addUndoPresolve: x%d = %g %s %g * x%d\\n\",\n                     colnrElim, alpha, ( beta < 0 ? \"-\" : \"+\"), fabs(beta), colnrDep);\n#endif\n  /* Add the data */\n  ix = mat->col_tag[0] = incrementUndoLadder(*DV);\n  mat->col_tag[ix] = colnrElim;\n  if(alpha != 0)\n    mat_setvalue(mat, 0, ix, alpha, FALSE);\n/*    mat_appendvalue(*mat, 0, alpha);*/\n  if((colnrDep > 0) && (beta != 0)) {\n    if(colnrDep > lp->columns)\n      return( appendUndoPresolve(lp, isprimal, beta, colnrDep) );\n    else\n      mat_setvalue(mat, colnrDep, ix, beta, FALSE);\n  }\n\n  return( TRUE );\n}\n\n\n\n/* ---------------------------------------------------------------------------------- */\n/* High level matrix inverse and product routines in lp_solve                         */\n/* ---------------------------------------------------------------------------------- */\n\n/* ---------------------------------------------------------------------------------- */\n/*    A brief description of the basis inverse and factorization logic in lp_solve    */\n/* ---------------------------------------------------------------------------------- */\n/*\n\n   In order to better understand the legacy code for operating with the\n   basis and its factorization in lp_solve I (KE) will briefly explain\n   the conventions and associated matrix algebra.  Note that with lp_solve\n   version 5.5, it is also possible to direct lp_solve to use the traditional\n   (textbook) format by setting the obj_in_B parameter to FALSE.\n\n   The matrix description of a linear program (as represented by lp_solve) goes\n   like this:\n\n           maximize         c'x\n           subject to  r <=  Ax <= b\n           where       l <=   x <= u\n\n   The matrix A is partitioned into two column sets [B|N], where B is\n   a square matrix of \"basis\" variables containing non-fixed\n   variables of the linear program at any given stage and N is the\n   submatrix of corresponding non-basic, fixed variables. The\n   variables (columns) in N may be fixed at their lower or upper levels.\n\n   Similarly, the c vector is partitioned into the basic and non-basic\n   parts [z|n].\n\n   While lp_solve stores the objective vector c in a dense format, and\n   the constraint matrix A in a (fairly standard) sparse format, the\n   column vectors passed to the factorization routine include the\n   objective coefficient at row index 0.  (In versions of lp_solve\n   before v5.2, c was actually explicitly stored as the 0-th row of A).\n   The expanded matrix may be called the \"A~\" form and looks like this:\n\n                       A~ = [ c ]\n                            [ A ]\n\n   Linear programming involves solving linear equations based on the\n   square basis matrix B, which includes is a subset of columns from A~.\n   The implications of the common storage of c and A (e.g. A~) vs. the\n   inverse / factorization of B for the operations and updates performed\n   by the simplex routine therefore needs to be understood.  As a consquence\n   of A~, in lp_solve B is stored in an expanded, bordered format using the\n   following (non-singular) representation:\n\n                       B~ = [ 1 z ]\n                            [ 0 B ]\n\n   Any basis inversion / factorization engine used by lp_solve must therefore\n   explicitly represent and handle the implications of this structure for\n   associated matrix operations.\n\n   The standard matrix formula for computing the inverse of a bordered\n   matrix shows what the inversion of B~ actually produces:\n\n                  Inv(B~) = [ 1 -z*Inv(B) ]\n                            [ 0   Inv(B)  ]\n\n   The A~ and B~ representations require awareness by the developer of the side\n   effects of the presence of the top row when doing product operations such as\n   b'N, btran and ftran.  Note in particular z*Inv(B) in the top row of Inv(B~),\n   which is actually the dual solution vector of the given basis.  This fact\n   makes a very common update in the simplex algorithm (reduced costs) returnable\n   as a vector simply by setting 1 at the top of a vector being pre-multiplied\n   with Inv(B~).\n\n   However, if the objective vector (c) is changed, the expanded representation\n   requires that B / B~ be refactorized.  Also, when doing FTRAN, BTRAN\n   and x'A-type operations, you will patently get the incorrect result\n   if you simply copy the operations given in textbooks.  First I'll show the\n   results of an FTRAN operation:\n\n                   Bx = a  ==>  x = FTRAN(a)\n\n   In lp_solve, this operation solves:\n\n                   [ 1 z ] [y] = [d]\n                   [ 0 B ] [x]   [a]\n\n   Using the Inv(B~) expression earlier, the FTRAN result is therefore:\n\n             [y] = [ 1 -z*Inv(B) ] [d] = [ d - z*Inv(B)*a ]\n             [x]   [ 0   Inv(B)  ] [a]   [   Inv(B)*a     ]\n\n   As an example, the value of the dual objective can be returned at the\n   0-th index by passing the active RHS vector with 0 at the 0-th position.\n\n   Similarily, doing the left solve - performing the BTRAN calculation:\n\n                   [x y] [ 1 z ] = [d a']\n                         [ 0 B ]\n\n   ... will produce the following result in lp_solve:\n\n   [x y] = [d a'] [ 1 -z*Inv(B) ] = [ d | -d*z*Inv(B) + a'*Inv(B) ]\n                  [ 0   Inv(B)  ]\n\n   So, if you thought you were simply computing \"a'*Inv(B)\", look again.\n   In order to produce the desired result, you have to set d to 0 before\n   the BTRAN operation.  On the other hand, if you set d to 1 and a to 0,\n   then you are very conveniently on your way to obtain the reduced costs\n   (needs a further matrix premultiplication with non-basic variables).\n\n   Incidentally, the BTRAN with [1 0] that yields [ 1 | -z*Inv(B) ] can\n   also be used as a fast way of checking the accuracy of the current\n   factorization.\n\n   Equipped with this understanding, I hope that you see that\n   the approach in lp_solve is actually pretty convenient.  It also\n   becomes easier to extend functionality in lp_solve by drawing on\n   formulas and expressions from LP literature that otherwise assume\n   the non-bordered syntax and representation.\n\n                                     Kjell Eikland -- November 2003\n                                     KE update     -- April 2005\n                                     KE update     -- June 2005\n\n*/\n\nSTATIC MYBOOL __WINAPI invert(lprec *lp, MYBOOL shiftbounds, MYBOOL final)\n{\n  MYBOOL *usedpos, resetbasis;\n  REAL   test;\n  int    k, i, j;\n  int    singularities, usercolB;\n\n /* Make sure the tags are correct */\n  if(!mat_validate(lp->matA)) {\n    lp->spx_status = INFEASIBLE;\n    return(FALSE);\n  }\n\n /* Create the inverse management object at the first call to invert() */\n  if(lp->invB == NULL)\n    lp->bfp_init(lp, lp->rows, 0, NULL);\n  else\n    lp->bfp_preparefactorization(lp);\n  singularities = 0;\n\n /* Must save spx_status since it is used to carry information about\n    the presence and handling of singular columns in the matrix */\n  if(userabort(lp, MSG_INVERT))\n    return(FALSE);\n\n#ifdef Paranoia\n  if(lp->spx_trace)\n    report(lp, DETAILED, \"invert: Iter %10g, fact-length %7d, OF \" RESULTVALUEMASK \".\\n\",\n                         (double) get_total_iter(lp), lp->bfp_colcount(lp), (double) -lp->rhs[0]);\n#endif\n\n /* Store state of pre-existing basis, and at the same time check if\n    the basis is I; in this case take the easy way out */\n  if(!allocMYBOOL(lp, &usedpos, lp->sum + 1, TRUE)) {\n    lp->bb_break = TRUE;\n    return(FALSE);\n  }\n  usedpos[0] = TRUE;\n  usercolB = 0;\n  for(i = 1; i <= lp->rows; i++) {\n    k = lp->var_basic[i];\n    if(k > lp->rows)\n      usercolB++;\n    usedpos[k] = TRUE;\n  }\n#ifdef Paranoia\n  if(!verify_basis(lp))\n    report(lp, SEVERE, \"invert: Invalid basis detected (iter %g).\\n\",\n                       (double) get_total_iter(lp));\n#endif\n\n /* Tally matrix nz-counts and check if we should reset basis\n    indicators to all slacks */\n  resetbasis = (MYBOOL) ((usercolB > 0) && lp->bfp_canresetbasis(lp));\n  k = 0;\n  for(i = 1; i <= lp->rows; i++) {\n    if(lp->var_basic[i] > lp->rows)\n      k += mat_collength(lp->matA, lp->var_basic[i] - lp->rows) + (is_OF_nz(lp,lp->var_basic[i] - lp->rows) ? 1 : 0);\n    if(resetbasis) {\n      j = lp->var_basic[i];\n      if(j > lp->rows)\n        lp->is_basic[j] = FALSE;\n      lp->var_basic[i] = i;\n      lp->is_basic[i] = TRUE;\n    }\n  }\n\n /* Now do the refactorization */\n  singularities = lp->bfp_factorize(lp, usercolB, k, usedpos, final);\n\n /* Do user reporting */\n  if(userabort(lp, MSG_INVERT))\n    goto Cleanup;\n\n /* Finalize factorization/inversion */\n  lp->bfp_finishfactorization(lp);\n\n  /* Recompute the RHS ( Ref. lp_solve inverse logic and Chvatal p. 121 ) */\n#ifdef DebugInv\n  blockWriteLREAL(stdout, \"RHS-values pre invert\", lp->rhs, 0, lp->rows);\n#endif\n  recompute_solution(lp, shiftbounds);\n  restartPricer(lp, AUTOMATIC);\n#ifdef DebugInv\n  blockWriteLREAL(stdout, \"RHS-values post invert\", lp->rhs, 0, lp->rows);\n#endif\n\nCleanup:\n  /* Check for numerical instability indicated by frequent refactorizations */\n  test = get_refactfrequency(lp, FALSE);\n  if(test < MIN_REFACTFREQUENCY) {\n    test = get_refactfrequency(lp, TRUE);\n    report(lp, NORMAL, \"invert: Refactorization frequency %.1g indicates numeric instability.\\n\",\n                       test);\n    lp->spx_status = NUMFAILURE;\n  }\n\n  FREE(usedpos);\n  return((MYBOOL) (singularities <= 0));\n} /* invert */\n\n\nSTATIC MYBOOL fimprove(lprec *lp, REAL *pcol, int *nzidx, REAL roundzero)\n{\n  REAL   *errors, sdp;\n  int    j;\n  MYBOOL Ok = TRUE;\n\n  allocREAL(lp, &errors, lp->rows + 1, FALSE);\n  if(errors == NULL) {\n    Ok = FALSE;\n    return(Ok);\n  }\n  MEMCOPY(errors, pcol, lp->rows + 1);\n  lp->bfp_ftran_normal(lp, pcol, nzidx);\n  prod_Ax(lp, NULL, pcol, NULL, 0.0, -1,\n                                errors, NULL, MAT_ROUNDDEFAULT);\n  lp->bfp_ftran_normal(lp, errors, NULL);\n\n  sdp = 0;\n  for(j = 1; j <= lp->rows; j++)\n    if(fabs(errors[j])>sdp)\n      sdp = fabs(errors[j]);\n  if(sdp > lp->epsmachine) {\n    report(lp, DETAILED, \"Iterative FTRAN correction metric %g\", sdp);\n    for(j = 1; j <= lp->rows; j++) {\n      pcol[j] += errors[j];\n      my_roundzero(pcol[j], roundzero);\n    }\n  }\n  FREE(errors);\n  return(Ok);\n}\n\nSTATIC MYBOOL bimprove(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero)\n{\n  int    j;\n  REAL   *errors, err, maxerr;\n  MYBOOL Ok = TRUE;\n\n  allocREAL(lp, &errors, lp->sum + 1, FALSE);\n  if(errors == NULL) {\n    Ok = FALSE;\n    return(Ok);\n  }\n  MEMCOPY(errors, rhsvector, lp->sum + 1);\n\n  /* Solve Ax=b for x, compute b back */\n  lp->bfp_btran_normal(lp, errors, nzidx);\n  prod_xA(lp, NULL, errors, NULL, 0.0, 1.0,\n                                  errors, NULL,\n                                  MAT_ROUNDDEFAULT);\n\n  /* Take difference with ingoing values, while shifting the column values\n     to the rows section and zeroing the columns again */\n  for(j = 1; j <= lp->rows; j++)\n    errors[j] = errors[lp->rows+lp->var_basic[j]] - rhsvector[j];\n  for(j = lp->rows; j <= lp->sum; j++)\n    errors[j] = 0;\n\n  /* Solve the b errors for the iterative x adjustment */\n  lp->bfp_btran_normal(lp, errors, NULL);\n\n  /* Generate the adjustments and compute statistic */\n  maxerr = 0;\n  for(j = 1; j <= lp->rows; j++) {\n    if(lp->var_basic[j]<=lp->rows) continue;\n    err = errors[lp->rows+lp->var_basic[j]];\n    if(fabs(err)>maxerr)\n      maxerr = fabs(err);\n  }\n  if(maxerr > lp->epsmachine) {\n    report(lp, DETAILED, \"Iterative BTRAN correction metric %g\", maxerr);\n    for(j = 1; j <= lp->rows; j++) {\n      if(lp->var_basic[j]<=lp->rows) continue;\n      rhsvector[j] += errors[lp->rows+lp->var_basic[j]];\n      my_roundzero(rhsvector[j], roundzero);\n    }\n  }\n  FREE(errors);\n  return(Ok);\n}\n\nSTATIC void ftran(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero)\n{\n#if 0\n  if(is_action(lp->improve, IMPROVE_SOLUTION) && lp->bfp_pivotcount(lp))\n    fimprove(lp, rhsvector, nzidx, roundzero);\n  else\n#endif\n    lp->bfp_ftran_normal(lp, rhsvector, nzidx);\n}\n\nSTATIC void btran(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero)\n{\n#if 0\n  if(is_action(lp->improve, IMPROVE_SOLUTION) && lp->bfp_pivotcount(lp))\n    bimprove(lp, rhsvector, nzidx, roundzero);\n  else\n#endif\n    lp->bfp_btran_normal(lp, rhsvector, nzidx);\n}\n\nSTATIC MYBOOL fsolve(lprec *lp, int varin, REAL *pcol, int *nzidx, REAL roundzero, REAL ofscalar, MYBOOL prepareupdate)\n/* Was setpivcol in versions earlier than 4.0.1.8 - KE */\n{\n  MYBOOL ok = TRUE;\n\n  if(varin > 0)\n    obtain_column(lp, varin, pcol, nzidx, NULL);\n\n /* Solve, adjusted for objective function scalar */\n  pcol[0] *= ofscalar;\n  if(prepareupdate)\n    lp->bfp_ftran_prepare(lp, pcol, nzidx);\n  else\n    ftran(lp, pcol, nzidx, roundzero);\n\n  return(ok);\n\n} /* fsolve */\n\n\nSTATIC MYBOOL bsolve(lprec *lp, int row_nr, REAL *rhsvector, int *nzidx, REAL roundzero, REAL ofscalar)\n{\n  MYBOOL ok = TRUE;\n\n  if(row_nr >= 0) /* Note that row_nr == 0 returns the [1, 0...0 ] vector */\n    row_nr = obtain_column(lp, row_nr, rhsvector, nzidx, NULL);\n\n  /* Solve, adjusted for objective function scalar */\n  rhsvector[0] *= ofscalar;\n  btran(lp, rhsvector, nzidx, roundzero);\n\n  return(ok);\n\n} /* bsolve */\n\n\n/* Vector compression and expansion routines */\nSTATIC MYBOOL vec_compress(REAL *densevector, int startpos, int endpos, REAL epsilon,\n                           REAL *nzvector, int *nzindex)\n{\n  int n;\n\n  if((densevector == NULL) || (nzindex == NULL) || (startpos > endpos))\n    return( FALSE );\n\n  n = 0;\n  densevector += startpos;\n  while(startpos <= endpos) {\n    if(fabs(*densevector) > epsilon) {  /* Apply zero-threshold */\n      if(nzvector != NULL)                       /* Only produce index if no nzvector is given */\n        nzvector[n] = *densevector;\n      n++;\n      nzindex[n] = startpos;\n    }\n    startpos++;\n    densevector++;\n  }\n  nzindex[0] = n;\n  return( TRUE );\n}\n\nSTATIC MYBOOL vec_expand(REAL *nzvector, int *nzindex, REAL *densevector, int startpos, int endpos)\n{\n  int i, n;\n\n  n = nzindex[0];\n  i = nzindex[n];\n  densevector += endpos;\n  while(endpos >= startpos) {                     /* Loop from behind to allow densevector == nzvector */\n    if(endpos == i) {\n      n--;\n      *densevector = nzvector[n];\n      i = nzindex[n];\n    }\n    else\n      *densevector = 0;\n    endpos--;\n    densevector--;\n  }\n  return( TRUE );\n}\n\n\n/* ----------------------------------------------------------------------- */\n/* Sparse matrix product routines and utility                              */\n/* ----------------------------------------------------------------------- */\n\nSTATIC MYBOOL get_colIndexA(lprec *lp, int varset, int *colindex, MYBOOL append)\n{\n  int      i, varnr, P1extraDim, vb, ve, n, nrows = lp->rows, nsum = lp->sum;\n  MYBOOL   omitfixed, omitnonfixed;\n  REAL     v;\n\n  /* Find what variable range to scan - default is {SCAN_USERVARS} */\n  /* First determine the starting position; add from the top, going down */\n  P1extraDim = abs(lp->P1extraDim);\n  vb = nrows + 1;\n  if(varset & SCAN_ARTIFICIALVARS)\n    vb = nsum - P1extraDim + 1;\n  if(varset & SCAN_USERVARS)\n    vb = nrows + 1;\n  if(varset & SCAN_SLACKVARS)\n    vb = 1;\n\n  /* Then determine the ending position, add from the bottom, going up */\n  ve = nsum;\n  if(varset & SCAN_SLACKVARS)\n    ve = nrows;\n  if(varset & SCAN_USERVARS)\n    ve = nsum - P1extraDim;\n  if(varset & SCAN_ARTIFICIALVARS)\n    ve = nsum;\n\n  /* Adjust for partial pricing */\n  if(varset & SCAN_PARTIALBLOCK) {\n    SETMAX(vb, partial_blockStart(lp, FALSE));\n    SETMIN(ve, partial_blockEnd(lp, FALSE));\n  }\n\n  /* Determine exclusion columns */\n  omitfixed = (MYBOOL) ((varset & OMIT_FIXED) != 0);\n  omitnonfixed = (MYBOOL) ((varset & OMIT_NONFIXED) != 0);\n  if(omitfixed && omitnonfixed)\n    return(FALSE);\n\n  /* Scan the target colums */\n  if(append)\n    n = colindex[0];\n  else\n    n = 0;\n  for(varnr = vb; varnr <= ve; varnr++) {\n\n    /* Skip gap in the specified column scan range (possibly user variables) */\n    if(varnr > nrows) {\n      if((varnr <= nsum-P1extraDim) && !(varset & SCAN_USERVARS))\n        continue;\n#if 1\n      /* Skip empty columns */\n      if(/*(lp->P1extraVal == 0) &&*/\n         (mat_collength(lp->matA, varnr-nrows) == 0))\n        continue;\n#endif\n    }\n\n    /* Find if the variable is in the scope - default is {} */\n    i = lp->is_basic[varnr];\n    if((varset & USE_BASICVARS) > 0 && (i))\n      ;\n    else if((varset & USE_NONBASICVARS) > 0 && (!i))\n      ;\n    else\n      continue;\n\n    v = lp->upbo[varnr];\n    if((omitfixed && (v == 0)) ||\n       (omitnonfixed && (v != 0)))\n      continue;\n\n    /* Append to list */\n    n++;\n    colindex[n] = varnr;\n  }\n  colindex[0] = n;\n\n  return(TRUE);\n}\n\nSTATIC int prod_Ax(lprec *lp, int *coltarget, REAL *input, int *nzinput,\n                              REAL roundzero, REAL ofscalar,\n                              REAL *output, int *nzoutput, int roundmode)\n/* prod_Ax is only used in fimprove; note that it is NOT VALIDATED/verified as of 20030801 - KE */\n{\n  int      j, colnr, ib, ie, vb, ve;\n  MYBOOL   localset, localnz = FALSE, isRC;\n  MATrec   *mat = lp->matA;\n  REAL     sdp;\n  REAL     *value;\n  int      *rownr;\n\n  /* Find what variable range to scan - default is {SCAN_USERVARS} */\n  /* Define default column target if none was provided */\n  isRC = (MYBOOL) ((roundmode & MAT_ROUNDRC) != 0);\n  localset = (MYBOOL) (coltarget == NULL);\n  if(localset) {\n    int varset = SCAN_SLACKVARS | SCAN_USERVARS |\n                 USE_BASICVARS | OMIT_FIXED;\n    if(isRC && is_piv_mode(lp, PRICE_PARTIAL) && !is_piv_mode(lp, PRICE_FORCEFULL))\n      varset |= SCAN_PARTIALBLOCK;\n    coltarget = (int *) mempool_obtainVector(lp->workarrays, lp->sum+1, sizeof(*coltarget));\n    if(!get_colIndexA(lp, varset, coltarget, FALSE)) {\n      mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n      return(FALSE);\n    }\n  }\n  localnz = (MYBOOL) (nzinput == NULL);\n  if(localnz) {\n    nzinput = (int *) mempool_obtainVector(lp->workarrays, lp->rows+1, sizeof(*nzinput));\n    vec_compress(input, 0, lp->rows, lp->matA->epsvalue, NULL, nzinput);\n  }\n\n  /* Scan the columns */\n  vb = 1;\n  ve = coltarget[0];\n  for(vb = 1; vb <= coltarget[0]; vb++) {\n    colnr = coltarget[vb];\n    j = lp->is_basic[colnr];\n\n    /* Perform the multiplication */\n    sdp = ofscalar*input[j];\n    if(colnr <= lp->rows)               /* A slack variable is in the basis */\n      output[colnr] += sdp;\n    else {                              /* A normal variable is in the basis */\n      colnr -= lp->rows;\n      ib = mat->col_end[colnr - 1];\n      ie = mat->col_end[colnr];\n      rownr = &COL_MAT_ROWNR(ib);\n      value = &COL_MAT_VALUE(ib);\n      for(; ib < ie;\n          ib++, rownr += matRowColStep, value += matValueStep) {\n        output[*rownr] += (*value)*sdp;\n      }\n    }\n  }\n  roundVector(output+1, lp->rows-1, roundzero);\n\n  /* Clean up and return */\n  if(localset)\n    mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n  if(localnz)\n    mempool_releaseVector(lp->workarrays, (char *) nzinput, FALSE);\n\n  return(TRUE);\n}\n\nSTATIC int prod_xA(lprec *lp, int *coltarget,\n                              REAL *input, int *nzinput, REAL roundzero, REAL ofscalar,\n                              REAL *output, int *nzoutput, int roundmode)\n/* Note that the dot product xa is stored at the active column index of A, i.e. of a.\n   This means that if the basis only contains non-slack variables, output may point to\n   the same vector as input, without overwriting the [0..rows] elements. */\n{\n  int      colnr, rownr, varnr, ib, ie, vb, ve, nrows = lp->rows;\n  MYBOOL   localset, localnz = FALSE, includeOF, isRC;\n  REALXP   vmax;\n  register REALXP v;\n  int      inz, *rowin, countNZ = 0;\n  MATrec   *mat = lp->matA;\n  register REAL     *matValue;\n  register int      *matRownr;\n\n  /* Clean output area (only necessary if we are returning the full vector) */\n  isRC = (MYBOOL) ((roundmode & MAT_ROUNDRC) != 0);\n  if(nzoutput == NULL) {\n    if(input == output)\n      MEMCLEAR(output+nrows+1, lp->columns);\n    else\n      MEMCLEAR(output, lp->sum+1);\n  }\n\n  /* Find what variable range to scan - default is {SCAN_USERVARS} */\n  /* Define default column target if none was provided */\n  localset = (MYBOOL) (coltarget == NULL);\n  if(localset) {\n    int varset = SCAN_SLACKVARS | SCAN_USERVARS |\n                 USE_NONBASICVARS | OMIT_FIXED;\n    if(isRC && is_piv_mode(lp, PRICE_PARTIAL) && !is_piv_mode(lp, PRICE_FORCEFULL))\n      varset |= SCAN_PARTIALBLOCK;\n    coltarget = (int *) mempool_obtainVector(lp->workarrays, lp->sum+1, sizeof(*coltarget));\n    if(!get_colIndexA(lp, varset, coltarget, FALSE)) {\n      mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n      return(FALSE);\n    }\n  }\n/*#define UseLocalNZ*/\n#ifdef UseLocalNZ\n  localnz = (MYBOOL) (nzinput == NULL);\n  if(localnz) {\n    nzinput = (int *) mempool_obtainVector(lp->workarrays, nrows+1, sizeof(*nzinput));\n    vec_compress(input, 0, nrows, lp->matA->epsvalue, NULL, nzinput);\n  }\n#endif\n  includeOF = (MYBOOL) (((nzinput == NULL) || (nzinput[1] == 0)) &&\n                        (input[0] != 0) && lp->obj_in_basis);\n\n  /* Scan the target colums */\n  vmax = 0;\n  ve = coltarget[0];\n  for(vb = 1; vb <= ve; vb++) {\n\n    varnr = coltarget[vb];\n\n    if(varnr <= nrows) {\n      v = input[varnr];\n    }\n    else {\n      colnr = varnr - nrows;\n      v = 0;\n      ib = mat->col_end[colnr - 1];\n      ie = mat->col_end[colnr];\n      if(ib < ie) {\n\n        /* Do dense input vector version */\n#ifdef UseLocalNZ\n        if(localnz || (nzinput == NULL)) {\n#else\n        if(nzinput == NULL) {\n#endif\n          /* Do the OF */\n          if(includeOF)\n#ifdef DirectArrayOF\n            v += input[0] * lp->obj[colnr] * ofscalar;\n#else\n            v += input[0] * get_OF_active(lp, varnr, ofscalar);\n#endif\n\n          /* Initialize pointers */\n          matRownr = &COL_MAT_ROWNR(ib);\n          matValue = &COL_MAT_VALUE(ib);\n\n          /* Do extra loop optimization based on target window overlaps */\n#ifdef UseLocalNZ\n          if((ib < ie)\n             && (colnr <= *nzinput)\n             && (COL_MAT_ROWNR(ie-1) >= nzinput[colnr])\n             && (*matRownr <= nzinput[*nzinput])\n             )\n#endif\n#ifdef NoLoopUnroll\n          /* Then loop over all regular rows */\n          for(; ib < ie; ib++) {\n            v += input[*matRownr] * (*matValue);\n            matValue += matValueStep;\n            matRownr += matRowColStep;\n          }\n#else\n          /* Prepare for simple loop unrolling */\n          if(((ie-ib) % 2) == 1) {\n            v += input[*matRownr] * (*matValue);\n            ib++;\n            matValue += matValueStep;\n            matRownr += matRowColStep;\n          }\n\n          /* Then loop over remaining pairs of regular rows */\n          while(ib < ie) {\n            v += input[*matRownr] * (*matValue);\n            v += input[*(matRownr+matRowColStep)] * (*(matValue+matValueStep));\n            ib += 2;\n            matValue += 2*matValueStep;\n            matRownr += 2*matRowColStep;\n          }\n#endif\n        }\n        /* Do sparse input vector version */\n        else {\n\n          /* Do the OF */\n          if(includeOF)\n#ifdef DirectArrayOF\n            v += input[0] * lp->obj[colnr] * ofscalar;\n#else\n            v += input[0] * get_OF_active(lp, varnr, ofscalar);\n#endif\n\n          /* Initialize pointers */\n          inz = 1;\n          rowin = nzinput+inz;\n          matRownr = &COL_MAT_ROWNR(ib);\n          matValue = &COL_MAT_VALUE(ib);\n          ie--;\n\n          /* Then loop over all non-OF rows */\n          while((inz <= *nzinput) && (ib <= ie)) {\n\n           /* Try to synchronize at right */\n            while((*rowin > *matRownr) && (ib < ie)) {\n              ib++;\n              matValue += matValueStep;\n              matRownr += matRowColStep;\n            }\n            /* Try to synchronize at left */\n            while((*rowin < *matRownr) && (inz < *nzinput)) {\n              inz++;\n              rowin++;\n            }\n            /* Perform dot product operation if there was a match */\n            if(*rowin == *matRownr) {\n              v += input[*rowin] * (*matValue);\n              /* Step forward at left */\n              inz++;\n              rowin++;\n            }\n          }\n        }\n      }\n      if((roundmode & MAT_ROUNDABS) != 0) {\n        my_roundzero(v, roundzero);\n      }\n    }\n\n    /* Special handling of small reduced cost values */\n    if(!isRC || (my_chsign(lp->is_lower[varnr], v) < 0)) {\n      SETMAX(vmax, fabs((REAL) v));\n    }\n    if(v != 0) {\n      countNZ++;\n      if(nzoutput != NULL)\n        nzoutput[countNZ] = varnr;\n    }\n    output[varnr] = (REAL) v;\n  }\n\n  /* Compute reduced cost if this option is active */\n  if(isRC && !lp->obj_in_basis)\n    countNZ = get_basisOF(lp, coltarget, output, nzoutput);\n\n  /* Check if we should do relative rounding */\n  if((roundmode & MAT_ROUNDREL) != 0) {\n    if((roundzero > 0) && (nzoutput != NULL)) {\n      ie = 0;\n      if(isRC) {\n        SETMAX(vmax, MAT_ROUNDRCMIN);  /* Make sure we don't use very small values */\n      }\n      vmax *= roundzero;\n      for(ib = 1; ib <= countNZ;  ib++) {\n        rownr = nzoutput[ib];\n        if(fabs(output[rownr]) < vmax)\n          output[rownr] = 0;\n        else {\n          ie++;\n          nzoutput[ie] = rownr;\n        }\n      }\n      countNZ = ie;\n    }\n  }\n\n  /* Clean up and return */\n  if(localset)\n    mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n  if(localnz)\n    mempool_releaseVector(lp->workarrays, (char *) nzinput, FALSE);\n\n  if(nzoutput != NULL)\n    *nzoutput = countNZ;\n  return(countNZ);\n}\n\nSTATIC MYBOOL prod_xA2(lprec *lp, int *coltarget,\n                                  REAL *prow, REAL proundzero, int *nzprow,\n                                  REAL *drow, REAL droundzero, int *nzdrow,\n                                  REAL ofscalar, int roundmode)\n{\n  int      varnr, colnr, ib, ie, vb, ve, nrows = lp->rows;\n  MYBOOL   includeOF, isRC;\n  REALXP   dmax, pmax;\n  register REALXP d, p;\n  MATrec   *mat = lp->matA;\n  REAL     value;\n  register REAL     *matValue;\n  register int      *matRownr;\n  MYBOOL localset;\n\n  /* Find what variable range to scan - default is {SCAN_USERVARS} */\n  /* First determine the starting position; add from the top, going down */\n  localset = (MYBOOL) (coltarget == NULL);\n  if(localset) {\n    int varset = SCAN_SLACKVARS + SCAN_USERVARS + /*SCAN_ALLVARS +*/\n                 /*SCAN_PARTIALBLOCK+*/\n                 USE_NONBASICVARS+OMIT_FIXED;\n    coltarget = (int *) mempool_obtainVector(lp->workarrays, lp->sum+1, sizeof(*coltarget));\n    if(!get_colIndexA(lp, varset, coltarget, FALSE)) {\n      mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n      return(FALSE);\n    }\n  }\n\n  /* Initialize variables */\n  isRC = (MYBOOL) ((roundmode & MAT_ROUNDRC) != 0);\n  pmax = 0;\n  dmax = 0;\n  if(nzprow != NULL)\n    *nzprow = 0;\n  if(nzdrow != NULL)\n    *nzdrow = 0;\n  includeOF = (MYBOOL) (((prow[0] != 0) || (drow[0] != 0)) &&\n                        lp->obj_in_basis);\n\n  /* Scan the target colums */\n  ve = coltarget[0];\n  for(vb = 1; vb <= ve; vb++) {\n\n    varnr = coltarget[vb];\n\n    if(varnr <= nrows) {\n      p = prow[varnr];\n      d = drow[varnr];\n    }\n    else {\n\n      colnr = varnr - nrows;\n\n      p = 0;\n      d = 0;\n      ib = mat->col_end[colnr - 1];\n      ie = mat->col_end[colnr];\n\n      if(ib < ie) {\n\n        /* Do the OF */\n        if(includeOF) {\n#ifdef DirectArrayOF\n          value = lp->obj[colnr] * ofscalar;\n#else\n          value = get_OF_active(lp, varnr, ofscalar);\n#endif\n          p += prow[0] * value;\n          d += drow[0] * value;\n        }\n\n        /* Then loop over all regular rows */\n        matRownr = &COL_MAT_ROWNR(ib);\n        matValue = &COL_MAT_VALUE(ib);\n#ifdef NoLoopUnroll\n        for( ; ib < ie; ib++) {\n          p += prow[*matRownr] * (*matValue);\n          d += drow[*matRownr] * (*matValue);\n          matValue += matValueStep;\n          matRownr += matRowColStep;\n        }\n#else\n        /* Prepare for simple loop unrolling */\n        if(((ie-ib) % 2) == 1) {\n          p += prow[*matRownr] * (*matValue);\n          d += drow[*matRownr] * (*matValue);\n          ib++;\n          matValue += matValueStep;\n          matRownr += matRowColStep;\n        }\n\n        /* Then loop over remaining pairs of regular rows */\n        while(ib < ie) {\n          p += prow[*matRownr] * (*matValue);\n          p += prow[*(matRownr+matRowColStep)] * (*(matValue+matValueStep));\n          d += drow[*matRownr] * (*matValue);\n          d += drow[*(matRownr+matRowColStep)] * (*(matValue+matValueStep));\n          ib += 2;\n          matValue += 2*matValueStep;\n          matRownr += 2*matRowColStep;\n        }\n#endif\n\n      }\n      if((roundmode & MAT_ROUNDABS) != 0) {\n        my_roundzero(p, proundzero);\n        my_roundzero(d, droundzero);\n      }\n    }\n\n    SETMAX(pmax, fabs((REAL) p));\n    prow[varnr] = (REAL) p;\n    if((nzprow != NULL) && (p != 0)) {\n      (*nzprow)++;\n      nzprow[*nzprow] = varnr;\n    }\n\n    /* Special handling of reduced cost rounding */\n    if(!isRC || (my_chsign(lp->is_lower[varnr], d) < 0)) {\n      SETMAX(dmax, fabs((REAL) d));\n    }\n    drow[varnr] = (REAL) d;\n    if((nzdrow != NULL) && (d != 0)) {\n      (*nzdrow)++;\n      nzdrow[*nzdrow] = varnr;\n    }\n  }\n\n  /* Compute reduced cost here if this option is active */\n  if((drow != 0) && !lp->obj_in_basis)\n    get_basisOF(lp, coltarget, drow, nzdrow);\n\n  /* Check if we should do relative rounding */\n  if((roundmode & MAT_ROUNDREL) != 0) {\n    if((proundzero > 0) && (nzprow != NULL)) {\n      ie = 0;\n      pmax *= proundzero;\n      for(ib = 1; ib <= *nzprow;  ib++) {\n        varnr = nzprow[ib];\n        if(fabs(prow[varnr]) < pmax)\n          prow[varnr] = 0;\n        else {\n          ie++;\n          nzprow[ie] = varnr;\n        }\n      }\n      *nzprow = ie;\n    }\n    if((droundzero > 0) && (nzdrow != NULL)) {\n      ie = 0;\n      if(isRC) {\n        SETMAX(dmax, MAT_ROUNDRCMIN);  /* Make sure we don't use very small values */\n      }\n      dmax *= droundzero;\n      for(ib = 1; ib <= *nzdrow;  ib++) {\n        varnr = nzdrow[ib];\n        if(fabs(drow[varnr]) < dmax)\n          drow[varnr] = 0;\n        else {\n          ie++;\n          nzdrow[ie] = varnr;\n        }\n      }\n      *nzdrow = ie;\n    }\n  }\n\n  /* Clean up and return */\n  if(localset)\n    mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n  return( TRUE );\n}\n\nSTATIC void bsolve_xA2(lprec *lp, int* coltarget,\n                                  int row_nr1, REAL *vector1, REAL roundzero1, int *nzvector1,\n                                  int row_nr2, REAL *vector2, REAL roundzero2, int *nzvector2, int roundmode)\n{\n  REAL ofscalar = 1.0;\n\n /* Clear and initialize first vector */\n  if(nzvector1 == NULL)\n    MEMCLEAR(vector1, lp->sum + 1);\n  else\n    MEMCLEAR(vector1, lp->rows + 1);\n  vector1[row_nr1] = 1;\n/*  workINT[0] = 1;\n  workINT[1] = row_nr1; */\n\n  if(vector2 == NULL) {\n    lp->bfp_btran_normal(lp, vector1, NULL);\n    prod_xA(lp, coltarget, vector1, NULL, roundzero1, ofscalar*0,\n                           vector1, nzvector1, roundmode);\n  }\n  else {\n\n   /* Clear and initialize second vector */\n    if(nzvector2 == NULL)\n      MEMCLEAR(vector2, lp->sum + 1);\n    else\n      MEMCLEAR(vector2, lp->rows + 1);\n    if(lp->obj_in_basis || (row_nr2 > 0)) {\n      vector2[row_nr2] = 1;\n/*      workINT[2] = 1;\n      workINT[3] = row_nr2; */\n    }\n    else\n      get_basisOF(lp, NULL, vector2, nzvector2);\n\n   /* A double BTRAN equation solver process is implemented \"in-line\" below in\n      order to save time and to implement different rounding for the two */\n    lp->bfp_btran_double(lp, vector1, NULL, vector2, NULL);\n\n   /* Multiply solution vectors with matrix values */\n    prod_xA2(lp, coltarget, vector1, roundzero1, nzvector1,\n                            vector2, roundzero2, nzvector2,\n                            ofscalar, roundmode);\n  }\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_matrix.h",
    "content": "#ifndef HEADER_lp_matrix\n#define HEADER_lp_matrix\n\n#include \"lp_types.h\"\n#include \"lp_utils.h\"\n\n\n/* Sparse matrix element (ordered columnwise) */\ntypedef struct _MATitem\n{\n  int  rownr;\n  int  colnr;\n  REAL value;\n} MATitem;\n\n/* Constants for matrix product rounding options */\n#define MAT_ROUNDNONE             0\n#define MAT_ROUNDABS              1\n#define MAT_ROUNDREL              2\n#define MAT_ROUNDABSREL          (MAT_ROUNDABS + MAT_ROUNDREL)\n#define MAT_ROUNDRC               4\n#define MAT_ROUNDRCMIN            1.0 /* lp->epspivot */\n#if 1\n #define MAT_ROUNDDEFAULT         MAT_ROUNDREL  /* Typically increases performance */\n#else\n #define MAT_ROUNDDEFAULT         MAT_ROUNDABS  /* Probably gives more precision */\n#endif\n\n/* Compiler option development features */\n/*#define DebugInv*/               /* Report array values at factorization/inversion */\n#define NoLoopUnroll              /* Do not do loop unrolling */\n#define DirectArrayOF             /* Reference lp->obj[] array instead of function call */\n\n\n/* Matrix column access macros to be able to easily change storage model */\n#define CAM_Record                0\n#define CAM_Vector                1\n#if 0\n #define MatrixColAccess           CAM_Record\n#else\n #define MatrixColAccess           CAM_Vector\n#endif\n\n#if MatrixColAccess==CAM_Record\n#define SET_MAT_ijA(item,i,j,A)   mat->col_mat[item].rownr = i; \\\n                                  mat->col_mat[item].colnr = j; \\\n                                  mat->col_mat[item].value = A\n#define COL_MAT_COLNR(item)       (mat->col_mat[item].colnr)\n#define COL_MAT_ROWNR(item)       (mat->col_mat[item].rownr)\n#define COL_MAT_VALUE(item)       (mat->col_mat[item].value)\n#define COL_MAT_COPY(left,right)  mat->col_mat[left] = mat->col_mat[right]\n#define COL_MAT_MOVE(to,from,rec) MEMMOVE(&(mat->col_mat[to]),&(mat->col_mat[from]),rec)\n#define COL_MAT2_COLNR(item)      (mat2->col_mat[item].colnr)\n#define COL_MAT2_ROWNR(item)      (mat2->col_mat[item].rownr)\n#define COL_MAT2_VALUE(item)      (mat2->col_mat[item].value)\n#define matRowColStep             (sizeof(MATitem)/sizeof(int))\n#define matValueStep              (sizeof(MATitem)/sizeof(REAL))\n\n#else /* if MatrixColAccess==CAM_Vector */\n#define SET_MAT_ijA(item,i,j,A)   mat->col_mat_rownr[item] = i; \\\n                                  mat->col_mat_colnr[item] = j; \\\n                                  mat->col_mat_value[item] = A\n#define COL_MAT_COLNR(item)       (mat->col_mat_colnr[item])\n#define COL_MAT_ROWNR(item)       (mat->col_mat_rownr[item])\n#define COL_MAT_VALUE(item)       (mat->col_mat_value[item])\n#define COL_MAT_COPY(left,right)  COL_MAT_COLNR(left) = COL_MAT_COLNR(right); \\\n                                  COL_MAT_ROWNR(left) = COL_MAT_ROWNR(right); \\\n                                  COL_MAT_VALUE(left) = COL_MAT_VALUE(right)\n#define COL_MAT_MOVE(to,from,rec) MEMMOVE(&COL_MAT_COLNR(to),&COL_MAT_COLNR(from),rec); \\\n                                  MEMMOVE(&COL_MAT_ROWNR(to),&COL_MAT_ROWNR(from),rec); \\\n                                  MEMMOVE(&COL_MAT_VALUE(to),&COL_MAT_VALUE(from),rec)\n#define COL_MAT2_COLNR(item)      (mat2->col_mat_colnr[item])\n#define COL_MAT2_ROWNR(item)      (mat2->col_mat_rownr[item])\n#define COL_MAT2_VALUE(item)      (mat2->col_mat_value[item])\n#define matRowColStep             1\n#define matValueStep              1\n\n#endif\n\n\n/* Matrix row access macros to be able to easily change storage model */\n#define RAM_Index                 0\n#define RAM_FullCopy              1\n#define MatrixRowAccess           RAM_Index\n\n#if MatrixRowAccess==RAM_Index\n#define ROW_MAT_COLNR(item)       COL_MAT_COLNR(mat->row_mat[item])\n#define ROW_MAT_ROWNR(item)       COL_MAT_ROWNR(mat->row_mat[item])\n#define ROW_MAT_VALUE(item)       COL_MAT_VALUE(mat->row_mat[item])\n\n#elif MatrixColAccess==CAM_Record\n#define ROW_MAT_COLNR(item)       (mat->row_mat[item].colnr)\n#define ROW_MAT_ROWNR(item)       (mat->row_mat[item].rownr)\n#define ROW_MAT_VALUE(item)       (mat->row_mat[item].value)\n\n#else /* if MatrixColAccess==CAM_Vector */\n#define ROW_MAT_COLNR(item)       (mat->row_mat_colnr[item])\n#define ROW_MAT_ROWNR(item)       (mat->row_mat_rownr[item])\n#define ROW_MAT_VALUE(item)       (mat->row_mat_value[item])\n\n#endif\n\n\ntypedef struct _MATrec\n{\n  /* Owner reference */\n  lprec     *lp;\n\n  /* Active dimensions */\n  int       rows;\n  int       columns;\n\n  /* Allocated memory */\n  int       rows_alloc;\n  int       columns_alloc;\n  int       mat_alloc;          /* The allocated size for matrix sized structures */\n\n  /* Sparse problem matrix storage */\n#if MatrixColAccess==CAM_Record  \n  MATitem   *col_mat;           /* mat_alloc : The sparse data storage */\n#else /*MatrixColAccess==CAM_Vector*/\n  int       *col_mat_colnr;\n  int       *col_mat_rownr;\n  REAL      *col_mat_value;\n#endif  \n  int       *col_end;           /* columns_alloc+1 : col_end[i] is the index of the\n                                   first element after column i; column[i] is stored\n                                   in elements col_end[i-1] to col_end[i]-1 */\n  int       *col_tag;           /* user-definable tag associated with each column */\n\n#if MatrixRowAccess==RAM_Index\n  int       *row_mat;           /* mat_alloc : From index 0, row_mat contains the\n                                   row-ordered index of the elements of col_mat */\n#elif MatrixColAccess==CAM_Record\n  MATitem   *row_mat;           /* mat_alloc : From index 0, row_mat contains the\n                                   row-ordered copy of the elements in col_mat */\n#else /*if MatrixColAccess==CAM_Vector*/\n  int       *row_mat_colnr;\n  int       *row_mat_rownr;\n  REAL      *row_mat_value;\n#endif\n  int       *row_end;           /* rows_alloc+1 : row_end[i] is the index of the\n                                   first element in row_mat after row i */\n  int       *row_tag;           /* user-definable tag associated with each row */\n\n  REAL      *colmax;            /* Array of maximum values of each column */\n  REAL      *rowmax;            /* Array of maximum values of each row */\n\n  REAL      epsvalue;           /* Zero element rejection threshold */\n  REAL      infnorm;            /* The largest absolute value in the matrix */\n  REAL      dynrange;\n  MYBOOL    row_end_valid;      /* TRUE if row_end & row_mat are valid */\n  MYBOOL    is_roworder;        /* TRUE if the current (temporary) matrix order is row-wise */\n\n} MATrec;\n\ntypedef struct _DeltaVrec\n{\n  lprec     *lp;\n  int       activelevel;\n  MATrec    *tracker;\n} DeltaVrec;\n\n\n#ifdef __cplusplus\n__EXTERN_C {\n#endif\n\n/* Sparse matrix routines */\nSTATIC MATrec *mat_create(lprec *lp, int rows, int columns, REAL epsvalue);\nSTATIC MYBOOL mat_memopt(MATrec *mat, int rowextra, int colextra, int nzextra);\nSTATIC void mat_free(MATrec **matrix);\nSTATIC MYBOOL inc_matrow_space(MATrec *mat, int deltarows);\nSTATIC int mat_mapreplace(MATrec *mat, LLrec *rowmap, LLrec *colmap, MATrec *insmat);\nSTATIC int mat_matinsert(MATrec *mat, MATrec *insmat);\nSTATIC int mat_zerocompact(MATrec *mat);\nSTATIC int mat_rowcompact(MATrec *mat, MYBOOL dozeros);\nSTATIC int mat_colcompact(MATrec *mat, int prev_rows, int prev_cols);\nSTATIC MYBOOL inc_matcol_space(MATrec *mat, int deltacols);\nSTATIC MYBOOL inc_mat_space(MATrec *mat, int mindelta);\nSTATIC int mat_shiftrows(MATrec *mat, int *bbase, int delta, LLrec *varmap);\nSTATIC int mat_shiftcols(MATrec *mat, int *bbase, int delta, LLrec *varmap);\nSTATIC MATrec *mat_extractmat(MATrec *mat, LLrec *rowmap, LLrec *colmap, MYBOOL negated);\nSTATIC int mat_appendrow(MATrec *mat, int count, REAL *row, int *colno, REAL mult, MYBOOL checkrowmode);\nSTATIC int mat_appendcol(MATrec *mat, int count, REAL *column, int *rowno, REAL mult, MYBOOL checkrowmode);\nMYBOOL mat_get_data(lprec *lp, int matindex, MYBOOL isrow, int **rownr, int **colnr, REAL **value);\nMYBOOL mat_set_rowmap(MATrec *mat, int row_mat_index, int rownr, int colnr, int col_mat_index);\nSTATIC MYBOOL mat_indexrange(MATrec *mat, int index, MYBOOL isrow, int *startpos, int *endpos);\nSTATIC MYBOOL mat_validate(MATrec *mat);\nSTATIC MYBOOL mat_equalRows(MATrec *mat, int baserow, int comprow);\nSTATIC int mat_findelm(MATrec *mat, int row, int column);\nSTATIC int mat_findins(MATrec *mat, int row, int column, int *insertpos, MYBOOL validate);\nSTATIC void mat_multcol(MATrec *mat, int col_nr, REAL mult, MYBOOL DoObj);\nSTATIC REAL mat_getitem(MATrec *mat, int row, int column);\nSTATIC MYBOOL mat_setitem(MATrec *mat, int row, int column, REAL value);\nSTATIC MYBOOL mat_additem(MATrec *mat, int row, int column, REAL delta);\nSTATIC MYBOOL mat_setvalue(MATrec *mat, int Row, int Column, REAL Value, MYBOOL doscale);\nSTATIC int mat_nonzeros(MATrec *mat);\nSTATIC int mat_collength(MATrec *mat, int colnr);\nSTATIC int mat_rowlength(MATrec *mat, int rownr);\nSTATIC void mat_multrow(MATrec *mat, int row_nr, REAL mult);\nSTATIC void mat_multadd(MATrec *mat, REAL *lhsvector, int varnr, REAL mult);\nSTATIC MYBOOL mat_setrow(MATrec *mat, int rowno, int count, REAL *row, int *colno, MYBOOL doscale, MYBOOL checkrowmode);\nSTATIC MYBOOL mat_setcol(MATrec *mat, int colno, int count, REAL *column, int *rowno, MYBOOL doscale, MYBOOL checkrowmode);\nSTATIC MYBOOL mat_mergemat(MATrec *target, MATrec *source, MYBOOL usecolmap);\nSTATIC int mat_checkcounts(MATrec *mat, int *rownum, int *colnum, MYBOOL freeonexit);\nSTATIC int mat_expandcolumn(MATrec *mat, int colnr, REAL *column, int *nzlist, MYBOOL signedA);\nSTATIC MYBOOL mat_computemax(MATrec *mat);\nSTATIC MYBOOL mat_transpose(MATrec *mat);\n\n/* Refactorization and recomputation routine */\nMYBOOL __WINAPI invert(lprec *lp, MYBOOL shiftbounds, MYBOOL final);\n\n/* Vector compression and expansion routines */\nSTATIC MYBOOL vec_compress(REAL *densevector, int startpos, int endpos, REAL epsilon, REAL *nzvector, int *nzindex);\nSTATIC MYBOOL vec_expand(REAL *nzvector, int *nzindex, REAL *densevector, int startpos, int endpos);\n\n/* Sparse matrix products */\nSTATIC MYBOOL get_colIndexA(lprec *lp, int varset, int *colindex, MYBOOL append);\nSTATIC int prod_Ax(lprec *lp, int *coltarget, REAL *input, int *nzinput, REAL roundzero, REAL ofscalar, REAL *output, int *nzoutput, int roundmode);\nSTATIC int prod_xA(lprec *lp, int *coltarget, REAL *input, int *nzinput, REAL roundzero, REAL ofscalar, REAL *output, int *nzoutput, int roundmode);\nSTATIC MYBOOL prod_xA2(lprec *lp, int *coltarget, REAL *prow, REAL proundzero, int *pnzprow,\n                                                  REAL *drow, REAL droundzero, int *dnzdrow, REAL ofscalar, int roundmode);\n\n/* Equation solution */\nSTATIC MYBOOL fimprove(lprec *lp, REAL *pcol, int *nzidx, REAL roundzero);\nSTATIC void ftran(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);\nSTATIC MYBOOL bimprove(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);\nSTATIC void btran(lprec *lp, REAL *rhsvector, int *nzidx, REAL roundzero);\n\n/* Combined equation solution and matrix product for simplex operations */\nSTATIC MYBOOL fsolve(lprec *lp, int varin, REAL *pcol, int *nzidx, REAL roundzero, REAL ofscalar, MYBOOL prepareupdate);\nSTATIC MYBOOL bsolve(lprec *lp, int row_nr, REAL *rhsvector, int *nzidx, REAL roundzero, REAL ofscalar);\nSTATIC void bsolve_xA2(lprec *lp, int* coltarget, \n                                  int row_nr1, REAL *vector1, REAL roundzero1, int *nzvector1,\n                                  int row_nr2, REAL *vector2, REAL roundzero2, int *nzvector2, int roundmode);\n\n/* Change-tracking routines (primarily for B&B and presolve) */\nSTATIC DeltaVrec *createUndoLadder(lprec *lp, int levelitems, int maxlevels);\nSTATIC int incrementUndoLadder(DeltaVrec *DV);\nSTATIC MYBOOL modifyUndoLadder(DeltaVrec *DV, int itemno, REAL target[], REAL newvalue);\nSTATIC int countsUndoLadder(DeltaVrec *DV);\nSTATIC int restoreUndoLadder(DeltaVrec *DV, REAL target[]);\nSTATIC int decrementUndoLadder(DeltaVrec *DV);\nSTATIC MYBOOL freeUndoLadder(DeltaVrec **DV);\n\n/* Specialized presolve undo functions */\nSTATIC MYBOOL appendUndoPresolve(lprec *lp, MYBOOL isprimal, REAL beta, int colnrDep);\nSTATIC MYBOOL addUndoPresolve(lprec *lp, MYBOOL isprimal, int colnrElim, REAL alpha, REAL beta, int colnrDep);\n\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif /* HEADER_lp_matrix */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_mipbb.c",
    "content": "\n/*\n    Mixed integer programming optimization drivers for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Michel Berkelaar (to lp_solve v3.2)\n                   Kjell Eikland    (v4.0 and forward)\n    Contact:\n    License terms: LGPL.\n\n    Requires:      string.h, float.h, commonlib.h, lp_lib.h, lp_report.h,\n                   lp_simplex.h\n\n    Release notes:\n    v5.0.0 31 January 2004      New unit isolating B&B routines.\n    v5.0.1 01 February 2004     Complete rewrite into non-recursive version.\n    v5.0.2 05 April 2004        Expanded pseudocosting with options for MIP fraction\n                                counts and \"cost/benefit\" ratio (KE special!).\n                                Added GUB functionality based on SOS structures.\n    v5.0.3    1 May 2004        Changed routine names to be more intuitive.\n    v5.0.4    15 May 2004       Added functinality to pack bounds in order to\n                                conserve memory in B&B-processing large MIP models.\n    v5.1.0    25 July 2004      Added functions for dynamic cut generation.\n    v5.2.0    15 December 2004  Added functions for reduced cost variable fixing\n                                and converted to delta-model of B&B bound storage.\n   ----------------------------------------------------------------------------------\n*/\n\n#include <string.h>\n#include <float.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_scale.h\"\n#include \"lp_report.h\"\n#include \"lp_simplex.h\"\n#include \"lp_mipbb.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n/* Allocation routine for the BB record structure */\nSTATIC BBrec *create_BB(lprec *lp, BBrec *parentBB, MYBOOL dofullcopy)\n{\n  BBrec *newBB;\n\n  newBB = (BBrec *) calloc(1, sizeof(*newBB));\n  if(newBB != NULL) {\n\n    if(parentBB == NULL) {\n      allocREAL(lp, &newBB->upbo,  lp->sum + 1, FALSE);\n      allocREAL(lp, &newBB->lowbo, lp->sum + 1, FALSE);\n      MEMCOPY(newBB->upbo,  lp->orig_upbo,  lp->sum + 1);\n      MEMCOPY(newBB->lowbo, lp->orig_lowbo, lp->sum + 1);\n    }\n    else if(dofullcopy) {\n      allocREAL(lp, &newBB->upbo,  lp->sum + 1, FALSE);\n      allocREAL(lp, &newBB->lowbo, lp->sum + 1, FALSE);\n      MEMCOPY(newBB->upbo,  parentBB->upbo,  lp->sum + 1);\n      MEMCOPY(newBB->lowbo, parentBB->lowbo, lp->sum + 1);\n    }\n    else {\n      newBB->upbo  = parentBB->upbo;\n      newBB->lowbo = parentBB->lowbo;\n    }\n    newBB->contentmode = dofullcopy;\n\n    newBB->lp = lp;\n\n    /* Set parent by default, but not child */\n    newBB->parent = parentBB;\n\n  }\n  return( newBB );\n}\n\n\n/* Pushing and popping routines for the B&B structure */\n\nSTATIC BBrec *push_BB(lprec *lp, BBrec *parentBB, int varno, int vartype, int varcus)\n/* Push ingoing bounds and B&B data onto the stack */\n{\n  BBrec *newBB;\n\n  /* Do initialization and updates */\n  if(parentBB == NULL)\n    parentBB = lp->bb_bounds;\n  newBB = create_BB(lp, parentBB, FALSE);\n  if(newBB != NULL) {\n\n    newBB->varno = varno;\n    newBB->vartype = vartype;\n    newBB->lastvarcus = varcus;\n    incrementUndoLadder(lp->bb_lowerchange);\n    newBB->LBtrack++;\n    incrementUndoLadder(lp->bb_upperchange);\n    newBB->UBtrack++;\n\n    /* Adjust variable fixing/bound tightening based on the last reduced cost */\n    if((parentBB != NULL) && (parentBB->lastrcf > 0)) {\n      MYBOOL isINT;\n      int    k, ii, nfixed = 0, ntighten = 0;\n      REAL   deltaUL;\n\n      for(k = 1; k <= lp->nzdrow[0]; k++) {\n        ii = lp->nzdrow[k];\n#ifdef UseMilpSlacksRCF  /* Check if we should include ranged constraints */\n        isINT = FALSE;\n#else\n        if(ii <= lp->rows)\n          continue;\n        isINT = is_int(lp, ii-lp->rows);\n#endif\n#ifndef UseMilpExpandedRCF  /* Don't include non-integers if it is not defined */\n        if(!isINT)\n          continue;\n#endif\n        switch(abs(rcfbound_BB(newBB, ii, isINT, &deltaUL, NULL))) {\n          case LE: SETMIN(deltaUL, newBB->upbo[ii]);\n                   SETMAX(deltaUL, newBB->lowbo[ii]);\n                   modifyUndoLadder(lp->bb_upperchange, ii, newBB->upbo, deltaUL);\n                   break;\n          case GE: SETMAX(deltaUL, newBB->lowbo[ii]);\n                   SETMIN(deltaUL, newBB->upbo[ii]);\n                   modifyUndoLadder(lp->bb_lowerchange, ii, newBB->lowbo, deltaUL);\n                   break;\n          default: continue;\n        }\n        if(newBB->upbo[ii] == newBB->lowbo[ii])\n          nfixed++;\n        else\n          ntighten++;\n      }\n      if(lp->bb_trace) {\n        report(lp, DETAILED,\n                 \"push_BB: Used reduced cost to fix %d variables and tighten %d bounds\\n\",\n                  nfixed, ntighten);\n      }\n    }\n\n    /* Handle case where we are pushing at the end */\n    if(parentBB == lp->bb_bounds)\n      lp->bb_bounds = newBB;\n    /* Handle case where we are pushing in the middle */\n    else\n      newBB->child = parentBB->child;\n    if(parentBB != NULL)\n      parentBB->child = newBB;\n\n    lp->bb_level++;\n    if(lp->bb_level > lp->bb_maxlevel)\n      lp->bb_maxlevel = lp->bb_level;\n\n    if(!initbranches_BB(newBB))\n      newBB = pop_BB(newBB);\n    else if(MIP_count(lp) > 0) {\n      if( (lp->bb_level <= 1) && (lp->bb_varactive == NULL) &&\n          (!allocINT(lp, &lp->bb_varactive, lp->columns+1, TRUE) ||\n           !initcuts_BB(lp)) )\n        newBB = pop_BB(newBB);\n      if(varno > 0) {\n        lp->bb_varactive[varno-lp->rows]++;\n      }\n    }\n  }\n  return( newBB );\n}\n\nSTATIC MYBOOL free_BB(BBrec **BB)\n{\n  MYBOOL parentreturned = FALSE;\n\n  if((BB != NULL) && (*BB != NULL)) {\n    BBrec *parent = (*BB)->parent;\n\n    if((parent == NULL) || (*BB)->contentmode) {\n      FREE((*BB)->upbo);\n      FREE((*BB)->lowbo);\n    }\n    FREE((*BB)->varmanaged);\n    FREE(*BB);\n\n    parentreturned = (MYBOOL) (parent != NULL);\n    if(parentreturned)\n      *BB = parent;\n\n  }\n  return( parentreturned );\n}\n\nSTATIC BBrec *pop_BB(BBrec *BB)\n/* Pop / free the previously \"pushed\" / saved bounds */\n{\n  int   k;\n  BBrec *parentBB;\n  lprec *lp = BB->lp;\n\n  if(BB == NULL)\n    return( BB );\n\n  /* Handle case where we are popping the end of the chain */\n  parentBB = BB->parent;\n  if(BB == lp->bb_bounds) {\n    lp->bb_bounds = parentBB;\n    if(parentBB != NULL)\n      parentBB->child = NULL;\n  }\n  /* Handle case where we are popping inside or at the beginning of the chain */\n  else {\n    if(parentBB != NULL)\n      parentBB->child = BB->child;\n    if(BB->child != NULL)\n      BB->child->parent = parentBB;\n  }\n\n  /* Unwind other variables */\n  if(lp->bb_upperchange != NULL) {\n    restoreUndoLadder(lp->bb_upperchange, BB->upbo);\n    for(; BB->UBtrack > 0; BB->UBtrack--) {\n      decrementUndoLadder(lp->bb_upperchange);\n      restoreUndoLadder(lp->bb_upperchange, BB->upbo);\n    }\n  }\n  if(lp->bb_lowerchange != NULL) {\n    restoreUndoLadder(lp->bb_lowerchange, BB->lowbo);\n    for(; BB->LBtrack > 0; BB->LBtrack--) {\n      decrementUndoLadder(lp->bb_lowerchange);\n      restoreUndoLadder(lp->bb_lowerchange, BB->lowbo);\n    }\n  }\n  lp->bb_level--;\n  k = BB->varno - lp->rows;\n  if(lp->bb_level == 0) {\n    if(lp->bb_varactive != NULL) {\n      FREE(lp->bb_varactive);\n      freecuts_BB(lp);\n    }\n    if(lp->int_vars+lp->sc_vars > 0)\n      free_pseudocost(lp);\n    pop_basis(lp, FALSE);\n    lp->rootbounds = NULL;\n  }\n  else\n    lp->bb_varactive[k]--;\n\n  /* Undo SOS/GUB markers */\n  if(BB->isSOS && (BB->vartype != BB_INT))\n    SOS_unmark(lp->SOS, 0, k);\n  else if(BB->isGUB)\n    SOS_unmark(lp->GUB, 0, k);\n\n  /* Undo the SC marker */\n  if(BB->sc_canset)\n    lp->sc_lobound[k] *= -1;\n\n  /* Pop the associated basis */\n#if 1\n  /* Original version that does not restore previous basis */\n  pop_basis(lp, FALSE);\n#else\n  /* Experimental version that restores previous basis */\n  pop_basis(lp, BB->isSOS);\n#endif\n\n  /* Finally free the B&B object */\n  free_BB(&BB);\n\n  /* Return the parent BB */\n  return( parentBB );\n}\n\n/* Here are heuristic routines to see if we need bother with branching further\n\n    1. A probing routine to see of the best OF can be better than incumbent\n    2. A presolve routine to fix other variables and detect infeasibility\n\n   THIS IS INACTIVE CODE, PLACEHOLDERS FOR FUTURE DEVELOPMENT!!! */\nSTATIC REAL probe_BB(BBrec *BB)\n{\n  int  i, ii;\n  REAL coefOF, sum = 0;\n  lprec *lp = BB->lp;\n\n  /* Loop over all ints to see if the best possible solution\n     stands any chance of being better than the incumbent solution */\n  if(lp->solutioncount == 0)\n    return( lp->infinite );\n  for(i = 1; i <= lp->columns; i++) {\n    if(!is_int(lp, i))\n      continue;\n    ii = lp->rows + i;\n    coefOF = lp->obj[i];\n    if(coefOF < 0) {\n      if(is_infinite(lp, BB->lowbo[ii]))\n        return( lp->infinite );\n      sum += coefOF * (lp->solution[ii]-BB->lowbo[ii]);\n    }\n    else {\n      if(is_infinite(lp, BB->upbo[ii]))\n        return( lp->infinite );\n      sum += coefOF * (BB->upbo[ii] - lp->solution[ii]);\n    }\n  }\n  return( sum );\n}\n\nSTATIC REAL presolve_BB(BBrec *BB)\n{\n  return( 0 );\n}\n\n/* Node and branch management routines */\nSTATIC MYBOOL initbranches_BB(BBrec *BB)\n{\n  REAL   new_bound, temp;\n  int    k;\n  lprec  *lp = BB->lp;\n\n /* Create and initialize local bounds and basis */\n  BB->nodestatus = NOTRUN;\n  BB->noderesult = lp->infinite;\n  push_basis(lp, NULL, NULL, NULL);\n\n /* Set default number of branches at the current B&B branch */\n  if(BB->vartype == BB_REAL)\n    BB->nodesleft = 1;\n\n  else {\n   /* The default is a binary up-low branching */\n    BB->nodesleft = 2;\n\n   /* Initialize the MIP status code pair and set reference values */\n    k = BB->varno - lp->rows;\n    BB->lastsolution = lp->solution[BB->varno];\n\n   /* Determine if we must process in the B&B SOS mode */\n    BB->isSOS = (MYBOOL) ((BB->vartype == BB_SOS) || SOS_is_member(lp->SOS, 0, k));\n#ifdef Paranoia\n    if((BB->vartype == BB_SOS) && !SOS_is_member(lp->SOS, 0, k))\n      report(lp, SEVERE, \"initbranches_BB: Inconsistent identification of SOS variable %s (%d)\\n\",\n                         get_col_name(lp, k), k);\n#endif\n\n   /* Check if we have a GUB-member variable that needs a triple-branch */\n    BB->isGUB = (MYBOOL) ((BB->vartype == BB_INT) && SOS_can_activate(lp->GUB, 0, k));\n    if(BB->isGUB) {\n      /* Obtain variable index list from applicable GUB - now the first GUB is used,\n        but we could also consider selecting the longest */\n      BB->varmanaged = SOS_get_candidates(lp->GUB, -1, k, TRUE, BB->upbo, BB->lowbo);\n      BB->nodesleft++;\n    }\n\n\n   /* Set local pruning info, automatic, or user-defined strategy */\n    if(BB->vartype == BB_SOS) {\n      if(!SOS_can_activate(lp->SOS, 0, k)) {\n        BB->nodesleft--;\n        BB->isfloor = TRUE;\n      }\n      else\n        BB->isfloor = (MYBOOL) (BB->lastsolution == 0);\n    }\n\n    /* First check if the user wishes to select the branching direction */\n    else if(lp->bb_usebranch != NULL)\n      BB->isfloor = (MYBOOL) lp->bb_usebranch(lp, lp->bb_branchhandle, k);\n\n    /* Otherwise check if we should do automatic branching */\n    else if(get_var_branch(lp, k) == BRANCH_AUTOMATIC) {\n      new_bound = modf(BB->lastsolution/get_pseudorange(lp->bb_PseudoCost, k, BB->vartype), &temp);\n      if(isnan(new_bound))\n        new_bound = 0;\n      else if(new_bound < 0)\n        new_bound += 1.0;\n      BB->isfloor = (MYBOOL) (new_bound <= 0.5);\n\n      /* Set direction by OF value; note that a zero-value in\n         the OF gives priority to floor_first = TRUE */\n      if(is_bb_mode(lp, NODE_GREEDYMODE)) {\n        if(is_bb_mode(lp, NODE_PSEUDOCOSTMODE))\n          BB->sc_bound = get_pseudonodecost(lp->bb_PseudoCost, k, BB->vartype, BB->lastsolution);\n        else\n          BB->sc_bound = mat_getitem(lp->matA, 0, k);\n        new_bound -= 0.5;\n        BB->sc_bound *= new_bound;\n        BB->isfloor = (MYBOOL) (BB->sc_bound > 0);\n      }\n      /* Set direction by pseudocost (normally used in tandem with NODE_PSEUDOxxxSELECT) */\n      else if(is_bb_mode(lp, NODE_PSEUDOCOSTMODE)) {\n        BB->isfloor = (MYBOOL) (get_pseudobranchcost(lp->bb_PseudoCost, k, TRUE) >\n                                get_pseudobranchcost(lp->bb_PseudoCost, k, FALSE));\n        if(is_maxim(lp))\n          BB->isfloor = !BB->isfloor;\n      }\n\n      /* Check for reversal */\n      if(is_bb_mode(lp, NODE_BRANCHREVERSEMODE))\n        BB->isfloor = !BB->isfloor;\n    }\n    else\n      BB->isfloor = (MYBOOL) (get_var_branch(lp, k) == BRANCH_FLOOR);\n\n    /* SC logic: If the current SC variable value is in the [0..NZLOBOUND> range, then\n\n      UP: Set lower bound to NZLOBOUND, upper bound is the original\n      LO: Fix the variable by setting upper/lower bound to zero\n\n      ... indicate that the variable is B&B-active by reversing sign of sc_lobound[]. */\n    new_bound = fabs(lp->sc_lobound[k]);\n    BB->sc_bound = new_bound;\n    BB->sc_canset = (MYBOOL) (new_bound != 0);\n\n   /* Must make sure that we handle fractional lower bounds properly;\n      also to ensure that we do a full binary tree search */\n    new_bound = unscaled_value(lp, new_bound, BB->varno);\n    if(is_int(lp, k) && ((new_bound > 0) &&\n                         (BB->lastsolution > floor(new_bound)))) {\n      if(BB->lastsolution < ceil(new_bound))\n        BB->lastsolution += 1;\n      modifyUndoLadder(lp->bb_lowerchange, BB->varno, BB->lowbo,\n                       scaled_floor(lp, BB->varno, BB->lastsolution, 1));\n    }\n  }\n\n  /* Now initialize the brances and set to first */\n  return( fillbranches_BB(BB) );\n}\n\nSTATIC MYBOOL fillbranches_BB(BBrec *BB)\n{\n  int    K, k;\n  REAL   ult_upbo, ult_lowbo;\n  REAL   new_bound, SC_bound, intmargin = BB->lp->epsprimal;\n  lprec  *lp = BB->lp;\n  MYBOOL OKstatus = FALSE;\n\n  if(lp->bb_break || userabort(lp, MSG_MILPSTRATEGY))\n    return( OKstatus );\n\n  K = BB->varno;\n  if(K > 0) {\n\n  /* Shortcut variables */\n    k = BB->varno - lp->rows;\n    ult_upbo  = lp->orig_upbo[K];\n    ult_lowbo = lp->orig_lowbo[K];\n    SC_bound  = unscaled_value(lp, BB->sc_bound, K);\n\n    /* First, establish the upper bound to be applied (when isfloor == TRUE)\n       --------------------------------------------------------------------- */\n/*SetUB:*/\n    BB->UPbound = lp->infinite;\n\n    /* Handle SC-variables for the [0-LoBound> range */\n    if((SC_bound > 0) && (fabs(BB->lastsolution) < SC_bound-intmargin)) {\n      new_bound = 0;\n    }\n    /* Handle pure integers (non-SOS, non-SC) */\n    else if(BB->vartype == BB_INT) {\n#if 1\n      if(((ult_lowbo >= 0) &&\n          ((floor(BB->lastsolution) < /* Skip cases where the lower bound becomes violated */\n            unscaled_value(lp, MAX(ult_lowbo, fabs(lp->sc_lobound[k])), K)-intmargin))) ||\n         ((ult_upbo <= 0) &&   /*  Was  ((ult_lowbo < 0) && */\n          ((floor(BB->lastsolution) > /* Skip cases where the upper bound becomes violated */\n            unscaled_value(lp, MIN(ult_upbo, -fabs(lp->sc_lobound[k])), K)-intmargin)))) {\n#else\n      if((floor(BB->lastsolution) <  /* Skip cases where the lower bound becomes violated */\n          unscaled_value(lp, MAX(ult_lowbo, fabs(lp->sc_lobound[k])), K)-intmargin)) {\n#endif\n        BB->nodesleft--;\n        goto SetLB;\n      }\n      new_bound = scaled_floor(lp, K, BB->lastsolution, 1);\n    }\n    else if(BB->isSOS) {           /* Handle all SOS variants */\n      new_bound = ult_lowbo;\n      if(is_int(lp, k))\n        new_bound = scaled_ceil(lp, K, unscaled_value(lp, new_bound, K), -1);\n    }\n    else                           /* Handle all other variable incarnations */\n      new_bound = BB->sc_bound;\n\n    /* Check if the new bound might conflict and possibly make adjustments */\n    if(new_bound < BB->lowbo[K])\n      new_bound = BB->lowbo[K] - my_avoidtiny(new_bound-BB->lowbo[K], intmargin);\n    if(new_bound < BB->lowbo[K]) {\n#ifdef Paranoia\n      debug_print(lp,\n          \"fillbranches_BB: New upper bound value %g conflicts with old lower bound %g\\n\",\n          new_bound, BB->lowbo[K]);\n#endif\n      BB->nodesleft--;\n      goto SetLB;\n    }\n#ifdef Paranoia\n    /* Do additional consistency checking */\n    else if(!check_if_less(lp, new_bound, BB->upbo[K], K)) {\n      BB->nodesleft--;\n      goto SetLB;\n    }\n#endif\n    /* Bound (at least near) feasible */\n    else {\n      /* Makes a difference with models like QUEEN\n         (note consistent use of epsint for scaled integer variables) */\n      if(fabs(new_bound - BB->lowbo[K]) < intmargin*SCALEDINTFIXRANGE)\n        new_bound = BB->lowbo[K];\n    }\n\n    BB->UPbound = new_bound;\n\n\n    /* Next, establish the lower bound to be applied (when isfloor == FALSE)\n       --------------------------------------------------------------------- */\nSetLB:\n    BB->LObound = -lp->infinite;\n\n    /* Handle SC-variables for the [0-LoBound> range */\n    if((SC_bound > 0) && (fabs(BB->lastsolution) < SC_bound)) {\n      if(is_int(lp, k))\n        new_bound = scaled_ceil(lp, K, SC_bound, 1);\n      else\n        new_bound = BB->sc_bound;\n    }\n    /* Handle pure integers (non-SOS, non-SC, but Ok for GUB!) */\n    else if((BB->vartype == BB_INT)) {\n      if(((ceil(BB->lastsolution) == BB->lastsolution)) ||    /* Skip branch 0 if the current solution is integer */\n         (ceil(BB->lastsolution) >   /* Skip cases where the upper bound becomes violated */\n          unscaled_value(lp, ult_upbo, K)+intmargin) ||\n          (BB->isSOS && (BB->lastsolution == 0))) {           /* Don't branch 0 since this is handled in SOS logic */\n        BB->nodesleft--;\n        goto Finish;\n      }\n      new_bound = scaled_ceil(lp, K, BB->lastsolution, 1);\n    }\n    else if(BB->isSOS) {             /* Handle all SOS variants */\n      if(SOS_is_member_of_type(lp->SOS, k, SOS3))\n        new_bound = scaled_floor(lp, K, 1, 1);\n      else {\n        new_bound = ult_lowbo;\n        if(is_int(lp, k))\n          new_bound = scaled_floor(lp, K, unscaled_value(lp, new_bound, K), 1);\n        /* If we have a high-order SOS (SOS3+) and this variable is \"intermediate\"\n          between members previously lower-bounded at a non-zero level, then we should\n          set this and similar neighbouring variables at non-zero lowbo-values (remember\n          that SOS3+ members are all either integers or semi-continuous). Flag this\n          situation and prune tree, since we cannot lower-bound. */\n        if((lp->SOS->maxorder > 2) && (BB->lastsolution == 0) &&\n           SOS_is_member_of_type(lp->SOS, k, SOSn)) {\n          BB->isSOS = AUTOMATIC;\n        }\n      }\n    }\n    else                              /* Handle all other variable incarnations */\n      new_bound = BB->sc_bound;\n\n    /* Check if the new bound might conflict and possibly make adjustments */\n    if(new_bound > BB->upbo[K])\n      new_bound = BB->upbo[K] + my_avoidtiny(new_bound-BB->upbo[K], intmargin);\n    if(new_bound > BB->upbo[K]) {\n#ifdef Paranoia\n      debug_print(lp,\n        \"fillbranches_BB: New lower bound value %g conflicts with old upper bound %g\\n\",\n        new_bound, BB->upbo[K]);\n#endif\n      BB->nodesleft--;\n      goto Finish;\n    }\n#ifdef Paranoia\n    /* Do additional consistency checking */\n    else if(!check_if_less(lp, BB->lowbo[K], new_bound, K)) {\n      BB->nodesleft--;\n      goto Finish;\n    }\n#endif\n    /* Bound (at least near-)feasible */\n    else {\n      /* Makes a difference with models like QUEEN\n         (note consistent use of lp->epsprimal for scaled integer variables) */\n      if(fabs(BB->upbo[K]-new_bound) < intmargin*SCALEDINTFIXRANGE)\n        new_bound = BB->upbo[K];\n    }\n\n    BB->LObound = new_bound;\n\n    /* Prepare for the first branch by making sure we are pointing correctly */\nFinish:\n    if(BB->nodesleft > 0) {\n\n      /* Make sure the change tracker levels are \"clean\" for the B&B */\n      if(countsUndoLadder(lp->bb_upperchange) > 0) {\n        incrementUndoLadder(lp->bb_upperchange);\n        BB->UBtrack++;\n      }\n      if(countsUndoLadder(lp->bb_lowerchange) > 0) {\n        incrementUndoLadder(lp->bb_lowerchange);\n        BB->LBtrack++;\n      }\n\n      /* Do adjustments */\n      if((BB->vartype != BB_SOS) && (fabs(BB->LObound-BB->UPbound) < intmargin)) {\n        BB->nodesleft--;\n        if(fabs(BB->lowbo[K]-BB->LObound) < intmargin)\n          BB->isfloor = FALSE;\n        else if(fabs(BB->upbo[K]-BB->UPbound) < intmargin)\n          BB->isfloor = TRUE;\n        else\n          report(BB->lp, IMPORTANT, \"fillbranches_BB: Inconsistent equal-valued bounds for %s\\n\",\n                                    get_col_name(BB->lp, k));\n      }\n      if((BB->nodesleft == 1) &&\n         ((BB->isfloor && (BB->UPbound >= lp->infinite)) ||\n          (!BB->isfloor && (BB->LObound <= -lp->infinite))))\n        BB->isfloor = !BB->isfloor;\n      /* Header initialization */\n      BB->isfloor = !BB->isfloor;\n      while(!OKstatus && /* !userabort(lp, -1) */ lp->spx_status != TIMEOUT && !lp->bb_break && (BB->nodesleft > 0))\n        OKstatus = nextbranch_BB( BB );\n    }\n\n    /* Set an SC variable active, if necessary */\n    if(BB->sc_canset)\n      lp->sc_lobound[k] *= -1;\n\n  }\n  else {\n    BB->nodesleft--;\n    OKstatus = TRUE;\n  }\n\n  return( OKstatus );\n}\n\nSTATIC MYBOOL nextbranch_BB(BBrec *BB)\n{\n  int    k;\n  lprec  *lp = BB->lp;\n  MYBOOL OKstatus = FALSE;\n\n  /* Undo the most recently imposed B&B bounds using the data\n     in the last level of change tracker; this code handles changes\n     to both upper and lower bounds */\n  if(BB->nodessolved > 0) {\n      restoreUndoLadder(lp->bb_upperchange, BB->upbo);\n      restoreUndoLadder(lp->bb_lowerchange, BB->lowbo);\n  }\n\n  if(lp->bb_break || userabort(lp, MSG_MILPSTRATEGY)) {\n    /* Handle the special case of B&B restart;\n       (typically used with the restart after pseudocost initialization) */\n    if((lp->bb_level == 1) && (lp->bb_break == AUTOMATIC)) {\n      lp->bb_break = FALSE;\n      OKstatus = TRUE;\n    }\n    return( OKstatus );\n  }\n\n  if(BB->nodesleft > 0) {\n\n    /* Step and update remaining branch count */\n    k = BB->varno - lp->rows;\n    BB->isfloor = !BB->isfloor;\n    BB->nodesleft--;\n\n    /* Special SOS handling:\n       1) Undo and set new marker for k,\n       2) In case that previous branch was ceiling restore upper bounds of the\n          non-k variables outside of the SOS window set to 0 */\n    if(BB->isSOS && (BB->vartype != BB_INT)) {\n\n      /* First undo previous marker */\n      if((BB->nodessolved > 0) || ((BB->nodessolved == 0) && (BB->nodesleft == 0))) {\n        if(BB->isfloor) {\n          if((BB->nodesleft == 0) && (lp->orig_lowbo[BB->varno] != 0))\n            return( OKstatus );\n        }\n        SOS_unmark(lp->SOS, 0, k);\n      }\n\n      /* Set new SOS marker */\n      if(BB->isfloor) {\n        SOS_set_marked(lp->SOS, 0, k, (MYBOOL) (BB->UPbound != 0));\n        /* Do case of high-order SOS where intervening variables need to be set */\n        if(BB->isSOS == AUTOMATIC) {\n\n/*          SOS_fix_list(lp->SOS, 0, k, BB->lowbo, NULL, AUTOMATIC, lp->bb_lowerchange); */\n        }\n      }\n      else {\n        SOS_set_marked(lp->SOS, 0, k, TRUE);\n        if(SOS_fix_unmarked(lp->SOS, 0, k, BB->upbo, 0, TRUE,\n                            NULL, lp->bb_upperchange) < 0)\n          return( OKstatus );\n      }\n    }\n\n    /* Special GUB handling (three branches):\n       1) Undo and set new marker for k,\n       2) Restore upper bounds of the left/right/all non-k variables\n          set to 0 in the previous branch\n       3) Set new upper bounds for the non-k variables (k is set later) */\n    else if(BB->isGUB) {\n\n      /* First undo previous marker */\n      if(BB->nodessolved > 0)\n        SOS_unmark(lp->GUB, 0, k);\n\n      /* Make sure we take floor bound twice */\n      if((BB->nodesleft == 0) && !BB->isfloor)\n        BB->isfloor = !BB->isfloor;\n\n      /* Handle two floor instances;\n         (selected variable and left/right halves of non-selected variables at 0) */\n      SOS_set_marked(lp->GUB, 0, k, (MYBOOL) !BB->isfloor);\n      if(BB->isfloor) {\n        if(SOS_fix_list(lp->GUB, 0, k, BB->upbo,\n                        BB->varmanaged, (MYBOOL) (BB->nodesleft > 0), lp->bb_upperchange) < 0)\n          return( OKstatus );\n      }\n      /* Handle one ceil instance;\n         (selected variable at 1, all other at 0) */\n      else {\n        if(SOS_fix_unmarked(lp->GUB, 0, k, BB->upbo, 0, TRUE,\n                            NULL, lp->bb_upperchange) < 0)\n          return( OKstatus );\n      }\n    }\n\n    OKstatus = TRUE;\n\n  }\n  /* Initialize simplex status variables */\n  if(OKstatus) {\n    lp->bb_totalnodes++;\n    BB->nodestatus = NOTRUN;\n    BB->noderesult = lp->infinite;\n  }\n  return( OKstatus );\n}\n\n\n/* Cut generation and management routines */\nSTATIC MYBOOL initcuts_BB(lprec *lp)\n{\n  return( TRUE );\n}\n\nSTATIC int updatecuts_BB(lprec *lp)\n{\n  return( 0 );\n}\n\nSTATIC MYBOOL freecuts_BB(lprec *lp)\n{\n  if(lp->bb_cuttype != NULL)\n    FREE(lp->bb_cuttype);\n  return( TRUE );\n}\n\n/* B&B solver routines */\nSTATIC int solve_LP(lprec *lp, BBrec *BB)\n{\n  int    tilted, restored, status;\n  REAL   testOF, *upbo = BB->upbo, *lowbo = BB->lowbo;\n  BBrec  *perturbed = NULL;\n\n  if(lp->bb_break)\n    return(PROCBREAK);\n\n#ifdef Paranoia\n  debug_print(lp, \"solve_LP: Starting solve for iter %.0f, B&B node level %d.\\n\",\n                   (double) lp->total_iter, lp->bb_level);\n  if(lp->bb_trace &&\n     !validate_bounds(lp, upbo, lowbo))\n    report(lp, SEVERE, \"solve_LP: Inconsistent bounds at iter %.0f, B&B node level %d.\\n\",\n                       (double) lp->total_iter, lp->bb_level);\n#endif\n\n  /* Copy user-specified entering bounds into lp_solve working bounds */\n  impose_bounds(lp, upbo, lowbo);\n\n  /* Restore previously pushed / saved basis for this level if we are in\n     the B&B mode and it is not the first call of the binary tree */\n  if(BB->nodessolved > 1)\n    restore_basis(lp);\n\n  /* Solve and possibly handle degeneracy cases via bound relaxations */\n  status   = RUNNING;\n  tilted   = 0;\n  restored = 0;\n\n  while(status == RUNNING) {\n\n    /* Copy user-specified entering bounds into lp_solve working bounds and run */\n    status = spx_run(lp, (MYBOOL) (tilted+restored > 0));\n    lp->bb_status     = status;\n    lp->spx_perturbed = FALSE;\n\n    if(tilted < 0)\n      break;\n\n    else if((status == OPTIMAL) && (tilted > 0)) {\n      if(lp->spx_trace)\n        report(lp, DETAILED, \"solve_LP: Restoring relaxed bounds at level %d.\\n\",\n                              tilted);\n\n    /* Restore original pre-perturbed problem bounds, and solve again using the basis\n       found for the perturbed problem; also make sure we rebase and recompute. */\n      free_BB(&perturbed);\n      if((perturbed == NULL) || (perturbed == BB)) {\n        perturbed = NULL;\n        impose_bounds(lp, upbo, lowbo);\n      }\n      else\n        impose_bounds(lp, perturbed->upbo, perturbed->lowbo);\n      set_action(&lp->spx_action, ACTION_REBASE | ACTION_RECOMPUTE);\n      BB->UBzerobased = FALSE;\n      if(lp->bb_totalnodes == 0)\n        lp->real_solution = lp->infinite;\n      status = RUNNING;\n      tilted--;\n      restored++;\n      lp->spx_perturbed = TRUE;\n    }\n\n    else if(((lp->bb_level <= 1) ||     is_anti_degen(lp, ANTIDEGEN_DURINGBB)) &&\n            (((status == LOSTFEAS) &&   is_anti_degen(lp, ANTIDEGEN_LOSTFEAS)) ||\n             ((status == INFEASIBLE) && is_anti_degen(lp, ANTIDEGEN_INFEASIBLE)) ||\n             ((status == NUMFAILURE) && is_anti_degen(lp, ANTIDEGEN_NUMFAILURE)) ||\n             ((status == DEGENERATE) && is_anti_degen(lp, ANTIDEGEN_STALLING)))) {\n     /* Allow up to .. consecutive relaxations for non-B&B phases */\n      if((tilted <= DEF_MAXRELAX) &&                       /* Conventional recovery case,...  */\n         !((tilted == 0) && (restored > DEF_MAXRELAX))) {  /* but not iterating infeasibility */\n\n        /* Create working copy of ingoing bounds if this is the first perturbation */\n        if(tilted == 0)\n          perturbed = BB;\n        perturbed = create_BB(lp, perturbed, TRUE);\n\n        /* Perturb/shift variable bounds; also make sure we rebase and recompute\n           (no refactorization is necessary, since the basis is unchanged) */\n#if 1\n        perturb_bounds(lp, perturbed, TRUE, TRUE, TRUE);\n#else\n        perturb_bounds(lp, perturbed, TRUE, TRUE, FALSE);\n#endif\n        impose_bounds(lp, perturbed->upbo, perturbed->lowbo);\n        set_action(&lp->spx_action, ACTION_REBASE | ACTION_RECOMPUTE);\n        BB->UBzerobased = FALSE;\n        status = RUNNING;\n        tilted++;\n        lp->perturb_count++;\n        lp->spx_perturbed = TRUE;\n        if(lp->spx_trace)\n          report(lp, DETAILED, \"solve_LP: Starting bound relaxation #%d ('%s')\\n\",\n                               tilted, get_statustext(lp, status));\n      }\n      else  {\n        if(lp->spx_trace)\n          report(lp, DETAILED, \"solve_LP: Relaxation limit exceeded in resolving infeasibility\\n\");\n        while((perturbed != NULL) && (perturbed != BB))\n          free_BB(&perturbed);\n        perturbed = NULL;\n      }\n    }\n  }\n\n  /* Handle the different simplex outcomes */\n  if(status != OPTIMAL) {\n    if(lp->bb_level <= 1)\n      lp->bb_parentOF = lp->infinite;\n    if((status == USERABORT) || (status == TIMEOUT)) {\n      /* Construct the last feasible solution, if available */\n      if((lp->solutioncount == 0) &&\n         /*\n            30/01/08 <peno> added MIP_count test because in following situation thing were wrong:\n             - The model contains integers\n             - A break at first is set\n             - A timeout is set\n             - The timeout occurs before a first integer solution is found\n             - When the timeout occurs, the simplex algorithm is in phase 2 and has a feasible (but non-integer) solution, but not optimal yet.\n            If above situation occurs then a (sub-optimal) solution was returned while no integer\n            solution isn't found yet at this time\n         */\n         (MIP_count(lp) == 0) &&\n         ((lp->simplex_mode & (SIMPLEX_Phase2_PRIMAL | SIMPLEX_Phase2_DUAL)) > 0)) {\n        lp->solutioncount++;\n        construct_solution(lp, NULL);\n        transfer_solution(lp, TRUE);\n      }\n      /* Return messages */\n      report(lp, NORMAL, \"\\nlp_solve optimization was stopped %s.\\n\",\n                         ((status == USERABORT) ? \"by the user\" : \"due to time-out\"));\n    }\n    else if(BB->varno == 0)\n      report(lp, NORMAL, \"The model %s\\n\",\n      (status == UNBOUNDED) ? \"is UNBOUNDED\" :\n      ((status == INFEASIBLE) ? \"is INFEASIBLE\" : \"FAILED\"));\n    else {\n#ifdef Paranoia\n      if((status != FATHOMED) && (status != INFEASIBLE))\n        report(lp, SEVERE, \"spx_solve: Invalid return code %d during B&B\\n\", status);\n#endif\n      /* If we fathomed a node due to an inferior OF having been detected, return infeasible */\n      if(status == FATHOMED)\n        lp->spx_status = INFEASIBLE;\n    }\n  }\n\n  else { /* ... there is a good solution */\n    construct_solution(lp, NULL);\n    if((lp->bb_level <= 1) && (restored > 0))\n      report(lp, DETAILED, \"%s numerics encountered; validate accuracy\\n\",\n                 (restored == 1) ? \"Difficult\" : \"Severe\");\n    /* Handle case where a user bound on the OF was found to\n       have been set too aggressively, giving an infeasible model */\n    if(lp->spx_status != OPTIMAL)\n      status = lp->spx_status;\n\n    else if((lp->bb_totalnodes == 0) && (MIP_count(lp) > 0)) {\n      if(lp->lag_status != RUNNING) {\n        report(lp, NORMAL, \"\\nRelaxed solution  \" RESULTVALUEMASK \" after %10.0f iter is B&B base.\\n\",\n                           lp->solution[0], (double) lp->total_iter);\n        report(lp, NORMAL, \" \\n\");\n      }\n      if((lp->usermessage != NULL) && (lp->msgmask & MSG_LPOPTIMAL)) {\n        REAL *best_solution = lp->best_solution;\n\n        /* transfer_solution(lp, TRUE); */\n        lp->best_solution = lp->solution;\n        lp->usermessage(lp, lp->msghandle, MSG_LPOPTIMAL);\n        lp->best_solution = best_solution;\n      }\n      set_var_priority(lp);\n    }\n\n   /* Check if we have a numeric problem (an earlier version of this code used the\n      absolute difference, but it is not robust for large-valued OFs) */\n    testOF = my_chsign(is_maxim(lp), my_reldiff(lp->solution[0], lp->real_solution));\n    if(testOF < -lp->epsprimal) {\n      report(lp, DETAILED, \"solve_LP: A MIP subproblem returned a value better than the base.\\n\");\n      status = INFEASIBLE;\n      lp->spx_status = status;\n      set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n    }\n    else if(testOF < 0)  /* Avoid problems later (could undo integer roundings, but usually Ok) */\n      lp->solution[0] = lp->real_solution;\n\n  }\n\n  /* status can have the following values:\n     OPTIMAL, SUBOPTIMAL, TIMEOUT, USERABORT, PROCFAIL, UNBOUNDED and INFEASIBLE. */\n\n  return( status );\n} /* solve_LP */\n\nSTATIC BBrec *findself_BB(BBrec *BB)\n{\n  int   varno = BB->varno, vartype = BB->vartype;\n\n  BB = BB->parent;\n  while((BB != NULL) && (BB->vartype != vartype) && (BB->varno != varno))\n    BB = BB->parent;\n  return( BB );\n}\n\n/* Function to determine the opportunity for variable fixing and bound\n   tightening based on a previous best MILP solution and a variable's\n   reduced cost at the current relaxation - inspired by Wolsley */\nSTATIC int rcfbound_BB(BBrec *BB, int varno, MYBOOL isINT, REAL *newbound, MYBOOL *isfeasible)\n{\n  int   i = FR;\n  lprec *lp = BB->lp;\n  REAL  deltaRC, rangeLU, deltaOF, lowbo, upbo;\n\n  /* Make sure we only accept non-basic variables */\n  if(lp->is_basic[varno])\n    return( i );\n\n  /* Make sure we only accept non-fixed variables */\n  lowbo = BB->lowbo[varno];\n  upbo  = BB->upbo[varno];\n  rangeLU = upbo - lowbo;\n\n  if(rangeLU > lp->epsprimal) {\n#if 1      /* v5.5 problematic - Gap between current node and the current best bound */\n    deltaOF = lp->rhs[0] - lp->bb_workOF;\n#elif 0    /* v6 less aggressive - Gap between current best bound and the relaxed problem */\n    deltaOF = my_chsign(is_maxim(lp), lp->real_solution) - lp->bb_workOF;\n#else      /* v6 more aggressive - Gap between current node and the relaxed problem */\n    deltaOF = my_chsign(is_maxim(lp), lp->real_solution) - lp->rhs[0];\n#endif\n\n    deltaRC = my_chsign(!lp->is_lower[varno], lp->drow[varno]);\n    /* Protect against divisions with tiny numbers and stray sign\n       reversals of the reduced cost */\n    if(deltaRC < lp->epspivot)\n      return( i );\n    deltaRC = deltaOF / deltaRC;  /* Should always be a positive number! */\n#ifdef Paranoia\n    if(deltaRC <= 0)\n      report(lp, SEVERE, \"rcfbound_BB: A negative bound fixing level was encountered after node %.0f\\n\",\n                         (double) lp->bb_totalnodes);\n#endif\n\n    /* Check if bound implied by the reduced cost is less than existing range */\n    if(deltaRC < rangeLU + lp->epsint) {\n      if(lp->is_lower[varno]) {\n        if(isINT)\n          deltaRC = scaled_floor(lp, varno, unscaled_value(lp, deltaRC, varno)+lp->epsprimal, 1);\n        upbo = lowbo + deltaRC;\n        deltaRC = upbo;\n        i = LE;  /* Sets the upper bound */\n      }\n      else {\n        if(isINT)\n          deltaRC = scaled_ceil(lp, varno, unscaled_value(lp, deltaRC, varno)+lp->epsprimal, 1);\n        lowbo = upbo - deltaRC;\n        deltaRC = lowbo;\n        i = GE;  /* Sets the lower bound */\n      }\n\n      /* Check and set feasibility status */\n      if((isfeasible != NULL) && (upbo - lowbo < -lp->epsprimal))\n        *isfeasible = FALSE;\n\n      /* Flag that we can fix the variable by returning the relation code negated */\n      else if(fabs(upbo - lowbo) < lp->epsprimal)\n        i = -i;\n      if(newbound != NULL) {\n        my_roundzero(deltaRC, lp->epsprimal);\n        *newbound = deltaRC;\n      }\n    }\n\n  }\n  return( i );\n}\n\n\nSTATIC MYBOOL findnode_BB(BBrec *BB, int *varno, int *vartype, int *varcus)\n{\n  int    countsossc, countnint, k, reasonmsg = MSG_NONE;\n  REAL   varsol;\n  MYBOOL is_better = FALSE, is_equal = FALSE, is_feasible = TRUE;\n  lprec  *lp = BB->lp;\n\n  /* Initialize result and return variables */\n  *varno    = 0;\n  *vartype  = BB_REAL;\n  *varcus   = 0;\n  countnint = 0;\n  BB->nodestatus = lp->spx_status;\n  BB->noderesult = lp->solution[0];\n\n  /* If this solution is worse than the best so far, this branch dies.\n     If we can only have integer OF values, and we only need the first solution\n     then the OF must be at least (unscaled) 1 better than the best so far */\n  if((lp->bb_limitlevel != 1) && (MIP_count(lp) > 0)) {\n\n    /* Check that we don't have a limit on the recursion level; two versions supported:\n        1) Absolute B&B level (bb_limitlevel > 0), and\n        2) B&B level relative to the \"B&B order\" (bb_limitlevel < 0). */\n    countsossc =  lp->sos_vars + lp->sc_vars;\n    if((lp->bb_limitlevel > 0) && (lp->bb_level > lp->bb_limitlevel+countsossc))\n      return( FALSE );\n    else if((lp->bb_limitlevel < 0) &&\n            (lp->bb_level > 2*(lp->int_vars+countsossc)*abs(lp->bb_limitlevel))) {\n      if(lp->bb_limitlevel == DEF_BB_LIMITLEVEL)\n        report(lp, IMPORTANT, \"findnode_BB: Default B&B limit reached at %d; optionally change strategy or limit.\\n\\n\",\n                              lp->bb_level);\n      return( FALSE );\n    }\n\n    /* First initialize or update pseudo-costs from previous optimal solution */\n    if(BB->varno == 0) {\n      varsol = lp->infinite;\n      if((lp->int_vars+lp->sc_vars > 0) && (lp->bb_PseudoCost == NULL))\n        lp->bb_PseudoCost = init_pseudocost(lp, get_bb_rule(lp));\n    }\n    else {\n      varsol = lp->solution[BB->varno];\n      if( ((lp->int_vars > 0) && (BB->vartype == BB_INT)) ||\n          ((lp->sc_vars > 0) && (BB->vartype == BB_SC) && !is_int(lp, BB->varno-lp->rows)) )\n        update_pseudocost(lp->bb_PseudoCost, BB->varno-lp->rows, BB->vartype, BB->isfloor, varsol);\n    }\n\n    /* Make sure we don't have numeric problems (typically due to integer scaling) */\n    if((lp->bb_totalnodes > 0) && !bb_better(lp, OF_RELAXED, OF_TEST_WE)) {\n      if(lp->bb_trace)\n        report(lp, IMPORTANT, \"findnode_BB: Simplex failure due to loss of numeric accuracy\\n\");\n      lp->spx_status = NUMFAILURE;\n      return( FALSE );\n    }\n\n    /* Abandon this branch if the solution is \"worse\" than a heuristically\n      determined limit or the previous best MIP solution */\n    if(((lp->solutioncount == 0) && !bb_better(lp, OF_HEURISTIC, OF_TEST_BE)) ||\n       ((lp->solutioncount > 0) &&\n        (!bb_better(lp, OF_INCUMBENT | OF_DELTA, OF_TEST_BE | OF_TEST_RELGAP) ||\n         !bb_better(lp, OF_INCUMBENT | OF_DELTA, OF_TEST_BE)))) {\n      return( FALSE );\n    }\n\n    /* Collect violated SC variables (since they can also be real-valued); the\n       approach is to get them out of the way, since a 0-value is assumed to be \"cheap\" */\n    if(lp->sc_vars > 0) {\n      *varno = find_sc_bbvar(lp, &countnint);\n      if(*varno > 0)\n        *vartype = BB_SC;\n    }\n\n    /* Look among SOS variables if no SC candidate was found */\n    if((SOS_count(lp) > 0) && (*varno == 0)) {\n      *varno = find_sos_bbvar(lp, &countnint, FALSE);\n      if(*varno < 0)\n        *varno = 0;\n      else if(*varno > 0)\n        *vartype = BB_SOS;\n    }\n\n    /* Then collect INTS that are not integer valued, and verify bounds */\n    if((lp->int_vars > 0) && (*varno == 0)) {\n      *varno = find_int_bbvar(lp, &countnint, BB, &is_feasible);\n      if(*varno > 0) {\n        *vartype = BB_INT;\n        if((countnint == 1) && !is_feasible) {\n          BB->lastrcf = 0;\n          return( FALSE );\n        }\n      }\n    }\n\n#if 1 /* peno */\n    /* Check if we have reached the depth limit for any individual variable\n      (protects against infinite recursions of mainly integer variables) */\n    k = *varno-lp->rows;\n    if((*varno > 0) && (lp->bb_limitlevel != 0) && (lp->bb_varactive[k] >= abs(lp->bb_limitlevel) /* abs(DEF_BB_LIMITLEVEL) */)) {\n      /* if(!is_action(lp->nomessage, NOMSG_BBLIMIT)) {*/\n/*\n        report(lp, IMPORTANT, \"findnode_BB: Reached B&B depth limit %d for variable %d; will not dive further.\\n\\n\",\n                              lp->bb_varactive[k], k);\n*/\n      /*  set_action(&lp->nomessage, NOMSG_BBLIMIT); */\n      /* } */\n      return( FALSE );\n    }\n#endif\n\n    /* Check if the current MIP solution is optimal; equal or better */\n    if(*varno == 0) {\n      is_better = (MYBOOL) (lp->solutioncount == 0) || bb_better(lp, OF_INCUMBENT | OF_DELTA, OF_TEST_BT);\n#if 1\n      is_better &= bb_better(lp, OF_INCUMBENT | OF_DELTA, OF_TEST_BT | OF_TEST_RELGAP);\n#else\n      /* Check if we can determine clear improvement */\n      is_better = (MYBOOL) (lp->solutioncount == 0) ||\n                  (MYBOOL) ((lp->bb_deltaOF > 0) &&\n                            (my_chsign(is_maxim(lp), lp->solution[0]-lp->best_solution[0]) < 0));\n\n      /* Apply gap-based improvement testing if the current solution is not clearly better */\n\n      if(!is_better) {\n        is_better  = bb_better(lp, OF_INCUMBENT | OF_DELTA, OF_TEST_BT);\n        is_better |= bb_better(lp, OF_INCUMBENT | OF_DELTA, OF_TEST_BT | OF_TEST_RELGAP);\n      }\n#endif\n      is_equal  = !is_better;\n\n      if(is_equal) {\n        if((lp->solutionlimit <= 0) || (lp->solutioncount < lp->solutionlimit)) {\n          lp->solutioncount++;\n          SETMIN(lp->bb_solutionlevel, lp->bb_level);\n          reasonmsg = MSG_MILPEQUAL;\n        }\n      }\n\n      /* Current solution is better */\n      else if(is_better) {\n\n        /* Update grand total solution count and check if we should go from\n           depth-first to best-first variable selection mode */\n        if(lp->bb_varactive != NULL) {\n          lp->bb_varactive[0]++;\n          if((lp->bb_varactive[0] == 1) &&\n             is_bb_mode(lp, NODE_DEPTHFIRSTMODE) && is_bb_mode(lp, NODE_DYNAMICMODE))\n            lp->bb_rule &= !NODE_DEPTHFIRSTMODE;\n        }\n\n        if(lp->bb_trace ||\n           ((lp->verbose >= NORMAL) && (lp->print_sol == FALSE) && (lp->lag_status != RUNNING))) {\n          report(lp, IMPORTANT,\n                 \"%s solution \" RESULTVALUEMASK \" after %10.0f iter, %9.0f nodes (gap %.1f%%)\\n\",\n                 (lp->bb_improvements == 0) ? \"Feasible\" : \"Improved\",\n                 lp->solution[0], (double) lp->total_iter, (double) lp->bb_totalnodes,\n                 100.0*fabs(my_reldiff(lp->solution[0], lp->bb_limitOF)));\n        }\n        if(MIP_count(lp) > 0) {\n          if(lp->bb_improvements == 0)\n            reasonmsg = MSG_MILPFEASIBLE;\n          else\n            reasonmsg = MSG_MILPBETTER;\n        }\n\n        lp->bb_status = FEASFOUND;\n        lp->bb_solutionlevel = lp->bb_level;\n        lp->solutioncount = 1;\n        lp->bb_improvements++;\n        lp->bb_workOF = lp->rhs[0];\n\n        if(lp->bb_breakfirst ||\n           (!is_infinite(lp, lp->bb_breakOF) && bb_better(lp, OF_USERBREAK, OF_TEST_BE)))\n          lp->bb_break = TRUE;\n      }\n    }\n  }\n  else {\n    is_better = TRUE;\n    lp->solutioncount = 1;\n  }\n\n  /* Transfer the successful solution vector */\n  if(is_better || is_equal) {\n#ifdef ParanoiaMIP\n    if((lp->bb_level > 0) &&\n       (check_solution(lp, lp->columns, lp->solution,\n                           lp->orig_upbo, lp->orig_lowbo, lp->epssolution) != OPTIMAL)) {\n      lp->solutioncount = 0;\n      lp->spx_status = NUMFAILURE;\n      lp->bb_status = lp->spx_status;\n      lp->bb_break = TRUE;\n      return( FALSE );\n    }\n#endif\n    transfer_solution(lp, (MYBOOL) ((lp->do_presolve & PRESOLVE_LASTMASKMODE) != PRESOLVE_NONE));\n    if((MIP_count(lp) > 0) && (lp->bb_totalnodes > 0)) {\n      if ((!construct_duals(lp)) ||\n          (is_presolve(lp, PRESOLVE_SENSDUALS) &&\n           (!construct_sensitivity_duals(lp) || !construct_sensitivity_obj(lp))\n          )\n         ) {\n      }\n    }\n    if((reasonmsg != MSG_NONE) && (lp->msgmask & reasonmsg) && (lp->usermessage != NULL))\n      lp->usermessage(lp, lp->msghandle, reasonmsg);\n\n    if(lp->print_sol != FALSE) {\n      print_objective(lp);\n      print_solution(lp, 1);\n    }\n  }\n\n  /* Do tracing and determine if we have arrived at the estimated lower MIP limit */\n  *varcus = countnint;\n  if(MIP_count(lp) > 0) {\n    if((countnint == 0) && (lp->solutioncount == 1) && (lp->solutionlimit == 1) &&\n       (bb_better(lp, OF_DUALLIMIT, OF_TEST_BE) || bb_better(lp, OF_USERBREAK, OF_TEST_BE | OF_TEST_RELGAP))) {\n      lp->bb_break = (MYBOOL) (countnint == 0);\n      return( FALSE );\n    }\n    else if(lp->bb_level > 0) {\n#ifdef MIPboundWithOF\n      if((lp->constraintOF > 0) && (countnint == 0))\n         set_rh(lp, lp->constraintOF, lp->solution[0] + my_chsign(!is_maxim(lp), lp->bb_deltaOF));\n#endif\n      if(lp->spx_trace)\n        report(lp, DETAILED, \"B&B level %5d OPT %16s value \" RESULTVALUEMASK \"\\n\",\n                             lp->bb_level, (*varno) ? \"   \" : \"INT\", lp->solution[0]);\n    }\n    return( (MYBOOL) (*varno > 0));\n  }\n  else\n    return( FALSE );\n\n}\n\nSTATIC int solve_BB(BBrec *BB)\n{\n  int   K, status;\n  lprec *lp = BB->lp;\n\n  /* Protect against infinite recursions do to integer rounding effects */\n  status = PROCFAIL;\n\n  /* Shortcut variables, set default bounds */\n  K = BB->varno;\n\n  /* Load simple MIP bounds */\n  if(K > 0) {\n\n    /* Update cuts, if specified */\n    updatecuts_BB(lp);\n\n    /* BRANCH_FLOOR: Force the variable to be smaller than the B&B upper bound */\n    if(BB->isfloor)\n      modifyUndoLadder(lp->bb_upperchange, K, BB->upbo, BB->UPbound);\n\n    /* BRANCH_CEILING: Force the variable to be greater than the B&B lower bound */\n    else\n      modifyUndoLadder(lp->bb_lowerchange, K, BB->lowbo, BB->LObound);\n\n    /* Update MIP node count */\n    BB->nodessolved++;\n\n  }\n\n  /* Solve! */\n  status = solve_LP(lp, BB);\n\n  /* Do special feasibility assessment of high order SOS'es */\n#if 1\n  if((status == OPTIMAL) && (BB->vartype == BB_SOS) && !SOS_is_feasible(lp->SOS, 0, lp->solution))\n    status = INFEASIBLE;\n#endif\n\n  return( status );\n}\n\n/* Routine to compute a \"strong\" pseudo-cost update for a node */\nSTATIC MYBOOL strongbranch_BB(lprec *lp, BBrec *BB, int varno, int vartype, int varcus)\n{\n  MYBOOL   success = FALSE;\n  int      i;\n  BBrec    *strongBB;\n\n  /* Create new B&B level and solve each of the branches */\n  lp->is_strongbranch = TRUE;\n  push_basis(lp, lp->var_basic, lp->is_basic, lp->is_lower);\n  strongBB = push_BB(lp, BB, lp->rows+varno, vartype, varcus);\n  if(strongBB == BB)\n    return( success );\n\n  do {\n\n    /* Solve incremental problem to local optimality */\n    lp->bb_strongbranches++;\n/*    set_action(&lp->spx_action, ACTION_REBASE | ACTION_RECOMPUTE); */\n    if(solve_BB(strongBB) == OPTIMAL) {\n\n      /* Update result indicator*/\n      success |= 1 << strongBB->isfloor;\n\n      /* Compute new count of non-ints */\n      strongBB->lastvarcus = 0;\n      for(i = 1; i <= lp->columns; i++) {\n        if(is_int(lp, i) && !solution_is_int(lp, lp->rows+i, FALSE))\n          strongBB->lastvarcus++;\n      }\n\n      /* Perform the pseudo-cost update */\n      update_pseudocost(lp->bb_PseudoCost, varno, strongBB->vartype, strongBB->isfloor,\n                                           lp->solution[strongBB->varno]);\n    }\n  }\n  while(nextbranch_BB(strongBB));\n\n  strongBB = pop_BB(strongBB);\n  if(strongBB != BB)\n    report(lp, SEVERE, \"strongbranch_BB: Invalid bound settings restored for variable %d\\n\",\n                       varno);\n  pop_basis(lp, TRUE);\n  set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n\n  lp->is_strongbranch = FALSE;\n\n  return( success );\n}\n\n/* Future functions */\nSTATIC MYBOOL pre_BB(lprec *lp)\n{\n  return( TRUE );\n}\nSTATIC MYBOOL post_BB(lprec *lp)\n{\n  return( TRUE );\n}\n\n/* This is the non-recursive B&B driver routine - beautifully simple, yet so subtle! */\nSTATIC int run_BB(lprec *lp)\n{\n  BBrec *currentBB;\n  int   varno, vartype, varcus, prevsolutions;\n  int   status = NOTRUN;\n\n  /* Initialize */\n  pre_BB(lp);\n  prevsolutions = lp->solutioncount;\n#ifdef UseMilpSlacksRCF  /* Check if we should include ranged constraints */\n  varno = lp->sum;\n#else\n  varno = lp->columns;\n#endif\n  lp->bb_upperchange = createUndoLadder(lp, varno, 2*MIP_count(lp));\n  lp->bb_lowerchange = createUndoLadder(lp, varno, 2*MIP_count(lp));\n  lp->rootbounds = currentBB = push_BB(lp, NULL, 0, BB_REAL, 0);\n\n  /* Perform the branch & bound loop */\n  while(lp->bb_level > 0) {\n    status = solve_BB(currentBB);\n\n#if 0\n    if((lp->bb_level == 1) && (MIP_count(lp) > 0)) {\n      if(status == RUNNING)\n        ;\n\n      /* Check if there was an integer solution of an aborted model */\n      else if((status == SUBOPTIMAL) && (lp->solutioncount == 1) &&\n              findnode_BB(currentBB, &varno, &vartype, &varcus))\n        status = USERABORT;\n    }\n#endif\n\n    if((status == OPTIMAL) && findnode_BB(currentBB, &varno, &vartype, &varcus))\n      currentBB = push_BB(lp, currentBB, varno, vartype, varcus);\n\n    else while((lp->bb_level > 0) && !nextbranch_BB(currentBB))\n      currentBB = pop_BB(currentBB);\n\n  }\n\n  /* Finalize */\n  freeUndoLadder(&(lp->bb_upperchange));\n  freeUndoLadder(&(lp->bb_lowerchange));\n\n  /* Check if we should adjust status */\n  if(lp->solutioncount > prevsolutions) {\n    if((status == PROCBREAK) || (status == USERABORT) || (status == TIMEOUT) || userabort(lp, -1))\n      status = SUBOPTIMAL;\n    else\n      status = OPTIMAL;\n    if(lp->bb_totalnodes > 0)\n      lp->spx_status = OPTIMAL;\n  }\n  post_BB(lp);\n  return( status );\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_mipbb.h",
    "content": "#ifndef HEADER_lp_mipbb\n#define HEADER_lp_mipbb\n\n#include \"lp_types.h\"\n#include \"lp_utils.h\"\n\n\n/* Bounds storage for B&B routines */\ntypedef struct _BBrec\n{\n  struct    _BBrec *parent;\n  struct    _BBrec *child;\n  lprec     *lp;\n  int       varno;\n  int       vartype;\n  int       lastvarcus;            /* Count of non-int variables of the previous branch */\n  int       lastrcf;\n  int       nodesleft;\n  int       nodessolved;\n  int       nodestatus;\n  REAL      noderesult;\n  REAL      lastsolution;          /* Optimal solution of the previous branch */\n  REAL      sc_bound;\n  REAL      *upbo,   *lowbo;\n  REAL      UPbound, LObound;\n  int       UBtrack, LBtrack;      /* Signals that incoming bounds were changed */\n  MYBOOL    contentmode;           /* Flag indicating if we \"own\" the bound vectors */\n  MYBOOL    sc_canset;\n  MYBOOL    isSOS;\n  MYBOOL    isGUB;\n  int       *varmanaged;           /* Extended list of variables managed by this B&B level */\n  MYBOOL    isfloor;               /* State variable indicating the active B&B bound */\n  MYBOOL    UBzerobased;           /* State variable indicating if bounds have been rebased */\n} BBrec;\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\nSTATIC BBrec *create_BB(lprec *lp, BBrec *parentBB, MYBOOL dofullcopy);\nSTATIC BBrec *push_BB(lprec *lp, BBrec *parentBB, int varno, int vartype, int varcus);\nSTATIC MYBOOL initbranches_BB(BBrec *BB);\nSTATIC MYBOOL fillbranches_BB(BBrec *BB);\nSTATIC MYBOOL nextbranch_BB(BBrec *BB);\nSTATIC MYBOOL strongbranch_BB(lprec *lp, BBrec *BB, int varno, int vartype, int varcus);\nSTATIC MYBOOL initcuts_BB(lprec *lp);\nSTATIC int updatecuts_BB(lprec *lp);\nSTATIC MYBOOL freecuts_BB(lprec *lp);\nSTATIC BBrec *findself_BB(BBrec *BB);\nSTATIC int solve_LP(lprec *lp, BBrec *BB);\nSTATIC int rcfbound_BB(BBrec *BB, int varno, MYBOOL isINT, REAL *newbound, MYBOOL *isfeasible);\nSTATIC MYBOOL findnode_BB(BBrec *BB, int *varno, int *vartype, int *varcus);\nSTATIC int solve_BB(BBrec *BB);\nSTATIC MYBOOL free_BB(BBrec **BB);\nSTATIC BBrec *pop_BB(BBrec *BB);\n\nSTATIC int run_BB(lprec *lp);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_mipbb */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_params.c",
    "content": "#include <stdio.h>\n#include <stdlib.h>\n#include <ctype.h>\n#include <errno.h>\n\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_report.h\"\n#include \"ini.h\"\n\ntypedef int (__WINAPI fn_int_get_function)(lprec *lp);\ntypedef long (__WINAPI fn_long_get_function)(lprec *lp);\ntypedef MYBOOL (__WINAPI fn_MYBOOL_get_function)(lprec *lp);\ntypedef REAL (__WINAPI fn_REAL_get_function)(lprec *lp);\ntypedef void (__WINAPI fn_int_set_function)(lprec *lp, int value);\ntypedef void (__WINAPI fn_long_set_function)(lprec *lp, long value);\ntypedef void (__WINAPI fn_MYBOOL_set_function)(lprec *lp, MYBOOL value);\ntypedef void (__WINAPI fn_REAL_set_function)(lprec *lp, REAL value);\n\n#define intfunction    1\n#define longfunction   2\n#define MYBOOLfunction 3\n#define REALfunction   4\n\n#define setvalues(values, basemask) values, sizeof(values) / sizeof(*values), basemask\n#define setNULLvalues NULL, 0, 0\n#define setvalue(value) value, #value\n#define setintfunction(get_function, set_function) { get_function }, { set_function }, intfunction\n#define setlongfunction(get_function, set_function) { (fn_int_get_function *) get_function }, {(fn_int_set_function *) set_function }, longfunction\n#define setMYBOOLfunction(get_function, set_function) { (fn_int_get_function *) get_function }, { (fn_int_set_function *) set_function }, MYBOOLfunction\n#define setREALfunction(get_function, set_function) {(fn_int_get_function *) get_function }, { (fn_int_set_function *) set_function }, REALfunction\n\n#define WRITE_COMMENTED 0\n#define WRITE_ACTIVE    1\n\nstruct _values {\n  int value;\n  char *svalue;\n};\n\nstruct _functions {\n  char *par;                                    /* name of parameter in ini file */\n  union {\n    fn_int_get_function *int_get_function;         /* set via setintfunction */\n    fn_long_get_function *long_get_function;       /* set via setlongfunction */\n    fn_MYBOOL_get_function *MYBOOL_get_function;   /* set via setMYBOOLfunction */\n    fn_REAL_get_function *REAL_get_function;       /* set via setREALfunction */\n  } get_function;\n  union {\n    fn_int_set_function *int_set_function;         /* set via setintfunction */\n    fn_long_set_function *long_set_function;       /* set via setlongfunction */\n    fn_MYBOOL_set_function *MYBOOL_set_function;   /* set via setMYBOOLfunction */\n    fn_REAL_set_function *REAL_set_function;       /* set via setREALfunction */\n  } set_function;\n  int type;                                     /* set via set*function */\n  struct _values *values;                       /* set via setvalues to a structure of _values */\n  int elements;                                 /*  or via setNULLvalues if the value is shown as is */\n  unsigned int basemask;\n  int mask;                                     /* WRITE_ACTIVE or WRITE_COMMENTED */\n};\n\nstatic struct _values anti_degen[] =\n{\n  { setvalue(ANTIDEGEN_NONE) },\n  { setvalue(ANTIDEGEN_FIXEDVARS) },\n  { setvalue(ANTIDEGEN_COLUMNCHECK) },\n  { setvalue(ANTIDEGEN_STALLING) },\n  { setvalue(ANTIDEGEN_NUMFAILURE) },\n  { setvalue(ANTIDEGEN_LOSTFEAS) },\n  { setvalue(ANTIDEGEN_INFEASIBLE) },\n  { setvalue(ANTIDEGEN_DYNAMIC) },\n  { setvalue(ANTIDEGEN_DURINGBB) },\n  { setvalue(ANTIDEGEN_RHSPERTURB) },\n  { setvalue(ANTIDEGEN_BOUNDFLIP) },\n};\n\nstatic struct _values basiscrash[] =\n{\n  { setvalue(CRASH_NONE) },\n  /* { setvalue(CRASH_NONBASICBOUNDS) }, */ /* not yet implemented */\n  { setvalue(CRASH_MOSTFEASIBLE) },\n  { setvalue(CRASH_LEASTDEGENERATE) },\n};\n\nstatic struct _values bb_floorfirst[] =\n{\n  { setvalue(BRANCH_CEILING) },\n  { setvalue(BRANCH_FLOOR) },\n  { setvalue(BRANCH_AUTOMATIC) },\n};\n\nstatic struct _values bb_rule[] =\n{\n  { setvalue(NODE_FIRSTSELECT) },\n  { setvalue(NODE_GAPSELECT) },\n  { setvalue(NODE_RANGESELECT) },\n  { setvalue(NODE_FRACTIONSELECT) },\n  { setvalue(NODE_PSEUDOCOSTSELECT) },\n  { setvalue(NODE_PSEUDONONINTSELECT) },\n  { setvalue(NODE_PSEUDORATIOSELECT) },\n  { setvalue(NODE_USERSELECT) },\n  { setvalue(NODE_WEIGHTREVERSEMODE) },\n  { setvalue(NODE_BRANCHREVERSEMODE) },\n  { setvalue(NODE_GREEDYMODE) },\n  { setvalue(NODE_PSEUDOCOSTMODE) },\n  { setvalue(NODE_DEPTHFIRSTMODE) },\n  { setvalue(NODE_RANDOMIZEMODE) },\n  { setvalue(NODE_GUBMODE) },\n  { setvalue(NODE_DYNAMICMODE) },\n  { setvalue(NODE_RESTARTMODE) },\n  { setvalue(NODE_BREADTHFIRSTMODE) },\n  { setvalue(NODE_AUTOORDER) },\n  { setvalue(NODE_RCOSTFIXING) },\n  { setvalue(NODE_STRONGINIT) },\n};\n\nstatic struct _values improve[] =\n{\n  { setvalue(IMPROVE_NONE) },\n  { setvalue(IMPROVE_SOLUTION) },\n  { setvalue(IMPROVE_DUALFEAS) },\n  { setvalue(IMPROVE_THETAGAP) },\n  { setvalue(IMPROVE_BBSIMPLEX) },\n};\n\nstatic REAL __WINAPI get_mip_gap_abs(lprec *lp)\n{\n  return(get_mip_gap(lp, TRUE));\n}\n\nstatic REAL __WINAPI get_mip_gap_rel(lprec *lp)\n{\n  return(get_mip_gap(lp, FALSE));\n}\n\nstatic void __WINAPI set_mip_gap_abs(lprec *lp, REAL mip_gap)\n{\n  set_mip_gap(lp, TRUE, mip_gap);\n}\n\nstatic void __WINAPI set_mip_gap_rel(lprec *lp, REAL mip_gap)\n{\n  set_mip_gap(lp, FALSE, mip_gap);\n}\n\nstatic struct _values pivoting[] =\n{\n  { setvalue(PRICER_FIRSTINDEX) },\n  { setvalue(PRICER_DANTZIG) },\n  { setvalue(PRICER_DEVEX) },\n  { setvalue(PRICER_STEEPESTEDGE) },\n  { setvalue(PRICE_PRIMALFALLBACK) },\n  { setvalue(PRICE_MULTIPLE) },\n  { setvalue(PRICE_PARTIAL) },\n  { setvalue(PRICE_ADAPTIVE) },\n  { setvalue(PRICE_RANDOMIZE) },\n  { setvalue(PRICE_AUTOPARTIAL) },\n  { setvalue(PRICE_LOOPLEFT) },\n  { setvalue(PRICE_LOOPALTERNATE) },\n  { setvalue(PRICE_HARRISTWOPASS) },\n  { setvalue(PRICE_TRUENORMINIT) },\n};\n\nstatic struct _values presolving[] =\n{\n  { setvalue(PRESOLVE_NONE) },\n  { setvalue(PRESOLVE_ROWS) },\n  { setvalue(PRESOLVE_COLS) },\n  { setvalue(PRESOLVE_LINDEP) },\n  { setvalue(PRESOLVE_AGGREGATE) },\n  { setvalue(PRESOLVE_SPARSER) },\n  { setvalue(PRESOLVE_SOS) },\n  { setvalue(PRESOLVE_REDUCEMIP) },\n  { setvalue(PRESOLVE_KNAPSACK) },\n  { setvalue(PRESOLVE_ELIMEQ2) },\n  { setvalue(PRESOLVE_IMPLIEDFREE) },\n  { setvalue(PRESOLVE_REDUCEGCD) },\n  { setvalue(PRESOLVE_PROBEFIX) },\n  { setvalue(PRESOLVE_PROBEREDUCE) },\n  { setvalue(PRESOLVE_ROWDOMINATE) },\n  { setvalue(PRESOLVE_COLDOMINATE) },\n  { setvalue(PRESOLVE_MERGEROWS) },\n  { setvalue(PRESOLVE_IMPLIEDSLK) },\n  { setvalue(PRESOLVE_COLFIXDUAL) },\n  { setvalue(PRESOLVE_BOUNDS) },\n  { setvalue(PRESOLVE_DUALS) },\n  { setvalue(PRESOLVE_SENSDUALS) },\n};\n\nstatic char *STRLWR(char *str)\n{\n  char *ptr;\n\n  for(ptr = str; *ptr; ptr++)\n    *ptr = (char) tolower((unsigned char) *ptr);\n\n  return(str);\n}\n\nstatic char *STRUPR(char *str)\n{\n  char *ptr;\n\n  for(ptr = str; *ptr; ptr++)\n    *ptr = (char) toupper((unsigned char) *ptr);\n\n  return(str);\n}\n\nstatic void __WINAPI set_presolve1(lprec *lp, int do_presolve)\n{\n  set_presolve(lp, do_presolve, get_presolveloops(lp));\n}\n\nstatic void __WINAPI set_presolve2(lprec *lp, int maxloops)\n{\n  set_presolve(lp, get_presolve(lp), maxloops);\n}\n\nstatic struct _values print_sol[] =\n{\n  { FALSE, \"0\" },\n  { TRUE,  \"1\" },\n  { setvalue(AUTOMATIC) },\n};\n\nstatic struct _values scaling[] =\n{\n  { setvalue(SCALE_NONE) },\n  { setvalue(SCALE_EXTREME) },\n  { setvalue(SCALE_RANGE) },\n  { setvalue(SCALE_MEAN) },\n  { setvalue(SCALE_GEOMETRIC) },\n  { setvalue(SCALE_CURTISREID) },\n  { setvalue(SCALE_QUADRATIC) },\n  { setvalue(SCALE_LOGARITHMIC) },\n  { setvalue(SCALE_USERWEIGHT) },\n  { setvalue(SCALE_POWER2) },\n  { setvalue(SCALE_EQUILIBRATE) },\n  { setvalue(SCALE_INTEGERS) },\n  { setvalue(SCALE_DYNUPDATE) },\n  { setvalue(SCALE_ROWSONLY) },\n  { setvalue(SCALE_COLSONLY) },\n};\n\nstatic struct _values simplextype[] =\n{\n  { setvalue(SIMPLEX_PRIMAL_PRIMAL) },\n  { setvalue(SIMPLEX_DUAL_PRIMAL) },\n  { setvalue(SIMPLEX_PRIMAL_DUAL) },\n  { setvalue(SIMPLEX_DUAL_DUAL) },\n};\n\nstatic struct _values verbose[] =\n{\n  { setvalue(NEUTRAL) },\n  { setvalue(CRITICAL) },\n  { setvalue(SEVERE) },\n  { setvalue(IMPORTANT) },\n  { setvalue(NORMAL) },\n  { setvalue(DETAILED) },\n  { setvalue(FULL) },\n};\n\nstatic struct _functions functions[] =\n{\n  /* solve options */\n  { \"ANTI_DEGEN\", setintfunction(get_anti_degen, set_anti_degen), setvalues(anti_degen, ~0), WRITE_ACTIVE },\n  { \"BASISCRASH\", setintfunction(get_basiscrash, set_basiscrash), setvalues(basiscrash, ~0), WRITE_ACTIVE },\n  { \"IMPROVE\", setintfunction(get_improve, set_improve), setvalues(improve, ~0), WRITE_ACTIVE },\n  { \"MAXPIVOT\", setintfunction(get_maxpivot, set_maxpivot), setNULLvalues, WRITE_ACTIVE },\n  { \"NEGRANGE\", setREALfunction(get_negrange, set_negrange), setNULLvalues, WRITE_ACTIVE },\n  { \"PIVOTING\", setintfunction(get_pivoting, set_pivoting), setvalues(pivoting, PRICER_LASTOPTION), WRITE_ACTIVE },\n  { \"PRESOLVE\", setintfunction(get_presolve, set_presolve1), setvalues(presolving, ~0), WRITE_ACTIVE },\n  { \"PRESOLVELOOPS\", setintfunction(get_presolveloops, set_presolve2), setNULLvalues, WRITE_ACTIVE },\n  { \"SCALELIMIT\", setREALfunction(get_scalelimit, set_scalelimit), setNULLvalues, WRITE_ACTIVE },\n  { \"SCALING\", setintfunction(get_scaling, set_scaling), setvalues(scaling, SCALE_CURTISREID), WRITE_ACTIVE },\n  { \"SIMPLEXTYPE\", setintfunction(get_simplextype, set_simplextype), setvalues(simplextype, ~0), WRITE_ACTIVE },\n  { \"OBJ_IN_BASIS\", setMYBOOLfunction(is_obj_in_basis, set_obj_in_basis), setNULLvalues, WRITE_COMMENTED },\n\n  /* B&B options */\n  { \"BB_DEPTHLIMIT\", setintfunction(get_bb_depthlimit, set_bb_depthlimit), setNULLvalues, WRITE_ACTIVE },\n  { \"BB_FLOORFIRST\", setintfunction(get_bb_floorfirst, set_bb_floorfirst), setvalues(bb_floorfirst, ~0), WRITE_ACTIVE },\n  { \"BB_RULE\", setintfunction(get_bb_rule, set_bb_rule), setvalues(bb_rule, NODE_STRATEGYMASK), WRITE_ACTIVE },\n  { \"BREAK_AT_FIRST\", setMYBOOLfunction(is_break_at_first, set_break_at_first), setNULLvalues, WRITE_COMMENTED },\n  { \"BREAK_AT_VALUE\", setREALfunction(get_break_at_value, set_break_at_value), setNULLvalues, WRITE_COMMENTED },\n  { \"MIP_GAP_ABS\", setREALfunction(get_mip_gap_abs, set_mip_gap_abs), setNULLvalues, WRITE_ACTIVE },\n  { \"MIP_GAP_REL\", setREALfunction(get_mip_gap_rel, set_mip_gap_rel), setNULLvalues, WRITE_ACTIVE },\n  { \"EPSINT\", setREALfunction(get_epsint, set_epsint), setNULLvalues, WRITE_ACTIVE },\n\n  /* tolerances, values */\n  { \"EPSB\", setREALfunction(get_epsb, set_epsb), setNULLvalues, WRITE_ACTIVE },\n  { \"EPSD\", setREALfunction(get_epsd, set_epsd), setNULLvalues, WRITE_ACTIVE },\n  { \"EPSEL\", setREALfunction(get_epsel, set_epsel), setNULLvalues, WRITE_ACTIVE },\n  { \"EPSPERTURB\", setREALfunction(get_epsperturb, set_epsperturb), setNULLvalues, WRITE_ACTIVE },\n  { \"EPSPIVOT\", setREALfunction(get_epspivot, set_epspivot), setNULLvalues, WRITE_ACTIVE },\n  { \"INFINITE\", setREALfunction(get_infinite, set_infinite), setNULLvalues, WRITE_ACTIVE },\n\n  /* read-only options */\n  { \"DEBUG\", setMYBOOLfunction(is_debug, set_debug), setNULLvalues, WRITE_COMMENTED },\n  { \"OBJ_BOUND\", setREALfunction(get_obj_bound, set_obj_bound), setNULLvalues, WRITE_COMMENTED },\n  { \"PRINT_SOL\", setintfunction(get_print_sol, set_print_sol), setvalues(print_sol, ~0), WRITE_COMMENTED },\n  { \"TIMEOUT\", setlongfunction(get_timeout, set_timeout), setNULLvalues, WRITE_COMMENTED },\n  { \"TRACE\", setMYBOOLfunction(is_trace, set_trace), setNULLvalues, WRITE_COMMENTED },\n  { \"VERBOSE\", setintfunction(get_verbose, set_verbose), setvalues(verbose, ~0), WRITE_COMMENTED },\n};\n\nstatic void write_params1(lprec *lp, FILE *fp, char *header, int newline)\n{\n  int ret = 0, ret2, i, j, k, value, value2, elements, majorversion, minorversion, release, build;\n  unsigned int basemask;\n  REAL a = 0;\n  char buf[4096], par[20];\n\n  ini_writeheader(fp, header, newline);\n  lp_solve_version(&majorversion, &minorversion, &release, &build);\n  sprintf(buf, \"lp_solve version %d.%d settings\\n\", majorversion, minorversion);\n  ini_writecomment(fp, buf);\n  for(i = 0; i < sizeof(functions) / sizeof(*functions); i++) {\n    switch(functions[i].type) {\n    case intfunction:\n      if(functions[i].get_function.int_get_function == NULL)\n        continue;\n      ret = functions[i].get_function.int_get_function(lp);\n      break;\n    case longfunction:\n      if(functions[i].get_function.long_get_function == NULL)\n        continue;\n      ret = functions[i].get_function.long_get_function(lp);\n      break;\n    case MYBOOLfunction:\n      if(functions[i].get_function.MYBOOL_get_function == NULL)\n        continue;\n      ret = (int) functions[i].get_function.MYBOOL_get_function(lp);\n      break;\n    case REALfunction:\n      if(functions[i].get_function.REAL_get_function == NULL)\n        continue;\n      a = functions[i].get_function.REAL_get_function(lp);\n      break;\n    }\n    buf[0] = 0;\n    if(functions[i].values == NULL) {\n      switch(functions[i].type) {\n      case intfunction:\n      case longfunction:\n      case MYBOOLfunction:\n        sprintf(buf, \"%d\", ret);\n        break;\n      case REALfunction:\n        sprintf(buf, \"%g\", a);\n        break;\n      }\n    }\n    else {\n      elements = functions[i].elements;\n      basemask = functions[i].basemask;\n      for(j = 0; j < elements; j++) {\n        value = functions[i].values[j].value;\n        ret2 = ret;\n        if(((unsigned int) value) < basemask)\n          ret2 &= basemask;\n        if(value == 0) {\n          if(ret2 == 0) {\n            if(*buf)\n              strcat(buf, \" + \");\n            strcat(buf, functions[i].values[j].svalue);\n          }\n        }\n        else if((ret2 & value) == value) {\n          for(k = 0; k < elements; k++) {\n            value2 = functions[i].values[k].value;\n            if((k != j) && (value2 > value) && ((value2 & value) == value) && ((ret2 & value2) == value2))\n              break;\n          }\n          if(k == elements) {\n            if(*buf)\n              strcat(buf, \" + \");\n            strcat(buf, functions[i].values[j].svalue);\n          }\n        }\n      }\n    }\n    if(functions[i].mask & WRITE_ACTIVE)\n      par[0] = 0;\n    else\n      strcpy(par, \";\");\n    strcat(par, functions[i].par);\n    ini_writedata(fp, STRLWR(par), buf);\n  }\n}\n\nstatic void readoptions(char *options, char **header)\n{\n  char *ptr1, *ptr2;\n\n  if(options != NULL) {\n    ptr1 = options;\n    while(*ptr1) {\n      ptr2 = strchr(ptr1, '-');\n      if(ptr2 == NULL)\n        break;\n      ptr2++;\n      if(tolower((unsigned char) *ptr2) == 'h') {\n        for(++ptr2; (*ptr2) && (isspace(*ptr2)); ptr2++);\n        for(ptr1 = ptr2; (*ptr1) && (!isspace(*ptr1)); ptr1++);\n        *header = (char *) calloc(1 + (int) (ptr1 - ptr2), 1);\n        memcpy(*header, ptr2, (int) (ptr1 - ptr2));\n      }\n    }\n  }\n\n  if(*header == NULL)\n    *header = strdup(\"Default\");\n}\n\nMYBOOL __WINAPI write_params(lprec *lp, char *filename, char *options)\n{\n  int k, ret, params_written;\n  FILE *fp, *fp0;\n  int state = 0, looping, newline;\n  char buf[4096], *filename0, *ptr1, *ptr2, *header = NULL;\n\n  readoptions(options, &header);\n\n  k = (int) strlen(filename);\n  filename0 = (char *) malloc(k + 1 + 1);\n  strcpy(filename0, filename);\n  ptr1 = strrchr(filename0, '.');\n  ptr2 = strrchr(filename0, '\\\\');\n  if((ptr1 == NULL) || ((ptr2 != NULL) && (ptr1 < ptr2)))\n    ptr1 = filename0 + k;\n  memmove(ptr1 + 1, ptr1, k + 1 - (int) (ptr1 - filename0));\n  ptr1[0] = '_';\n  if(rename(filename, filename0)) {\n    switch(errno) {\n    case ENOENT: /* File or path specified by oldname not found */\n      FREE(filename0);\n      filename0 = NULL;\n      break;\n    case EACCES: /* File or directory specified by newname already exists or could not be created (invalid path); or oldname is a directory and newname specifies a different path. */\n      FREE(filename0);\n      FREE(header);\n      return(FALSE);\n      break;\n    }\n  }\n\n  if((fp = ini_create(filename)) == NULL)\n    ret = FALSE;\n  else {\n    params_written = FALSE;\n    newline = TRUE;\n    if(filename0 != NULL) {\n      fp0 = ini_open(filename0);\n      if(fp0 == NULL) {\n        rename(filename0, filename);\n        FREE(filename0);\n        FREE(header);\n        return(FALSE);\n      }\n      looping = TRUE;\n      while(looping) {\n        switch(ini_readdata(fp0, buf, sizeof(buf), TRUE)) {\n        case 0: /* End of file */\n          looping = FALSE;\n          break;\n        case 1: /* header */\n          ptr1 = strdup(buf);\n          STRUPR(buf);\n          ptr2 = strdup(header);\n          STRUPR(ptr2);\n          if(strcmp(buf, ptr2) == 0) {\n            write_params1(lp, fp, ptr1, newline);\n            params_written = TRUE;\n            newline = TRUE;\n            state = 1;\n          }\n          else {\n            state = 0;\n            ini_writeheader(fp, ptr1, newline);\n            newline = TRUE;\n          }\n          FREE(ptr2);\n          FREE(ptr1);\n          break;\n        case 2: /* data */\n          if(state == 0) {\n            ini_writedata(fp, NULL, buf);\n            newline = (*buf != 0);\n          }\n          break;\n        }\n      }\n      ini_close(fp0);\n    }\n\n    if(!params_written)\n      write_params1(lp, fp, header, newline);\n\n    ini_close(fp);\n    ret = TRUE;\n  }\n\n  if(filename0 != NULL) {\n    remove(filename0);\n    FREE(filename0);\n  }\n\n  FREE(header);\n\n  return( (MYBOOL) ret );\n}\n\n\nMYBOOL __WINAPI read_params(lprec *lp, char *filename, char *options)\n{\n  int ret, looping, line;\n  FILE *fp;\n  hashtable *hashfunctions, *hashparameters;\n  hashelem *hp;\n  int i, j, elements, n, intvalue, state = 0;\n  REAL REALvalue;\n  char buf[4096], *header = NULL, *ptr, *ptr1, *ptr2;\n\n  if((fp = ini_open(filename)) == NULL)\n    ret = FALSE;\n  else {\n    /* create hashtable of all callable commands to find them quickly */\n    hashfunctions = create_hash_table(sizeof(functions) / sizeof(*functions), 0);\n    for (n = 0, i = 0; i < (int) (sizeof(functions)/sizeof(*functions)); i++) {\n      puthash(functions[i].par, i, NULL, hashfunctions);\n      if(functions[i].values != NULL)\n        n += functions[i].elements;\n    }\n    /* create hashtable of all arguments to find them quickly */\n    hashparameters = create_hash_table(n, 0);\n    for (n = 0, i = 0; i < (int) (sizeof(functions)/sizeof(*functions)); i++) {\n      if(functions[i].values != NULL) {\n        elements = functions[i].elements;\n        for(j = 0; j < elements; j++)\n          if((strcmp(functions[i].values[j].svalue, \"0\") != 0) &&\n             (strcmp(functions[i].values[j].svalue, \"1\") != 0))\n            puthash(functions[i].values[j].svalue, j, NULL, hashparameters);\n      }\n    }\n\n    readoptions(options, &header);\n\n    STRUPR(header);\n    ret = looping = TRUE;\n    line = 0;\n    while((ret) && (looping)) {\n      line++;\n      switch(ini_readdata(fp, buf, sizeof(buf), FALSE)) {\n        case 0: /* End of file */\n          looping = FALSE;\n          break;\n        case 1: /* header */\n          switch(state) {\n            case 0:\n              STRUPR(buf);\n              if(strcmp(buf, header) == 0)\n                state = 1;\n              break;\n            case 1:\n              looping = FALSE;\n              break;\n          }\n          break;\n        case 2: /* data */\n          if(state == 1) {\n            for(ptr = buf; (*ptr) && (isspace(*ptr)); ptr++);\n          }\n          else\n            ptr = NULL;\n          if((ptr != NULL) && (*ptr)) {\n            STRUPR(buf);\n            ptr = strchr(buf, '=');\n            if(ptr == NULL) {\n              report(lp, IMPORTANT, \"read_params: No equal sign on line %d\\n\", line);\n              ret = FALSE;\n            }\n            else {\n              *ptr = 0;\n              for(ptr1 = buf; isspace(*ptr1); ptr1++);\n              for(ptr2 = ptr - 1; (ptr2 >= ptr1) && (isspace(*ptr2)); ptr2--);\n              if(ptr2 <= ptr1) {\n                report(lp, IMPORTANT, \"read_params: No parameter name before equal sign on line %d\\n\", line);\n                ret = FALSE;\n              }\n              else {\n                ptr2[1] = 0;\n                hp = findhash(ptr1, hashfunctions);\n                if(hp == NULL) {\n                  report(lp, IMPORTANT, \"read_params: Unknown parameter name (%s) before equal sign on line %d\\n\", ptr1, line);\n                  ret = FALSE;\n                }\n                else {\n                  i = hp->index;\n                  ptr1 = ++ptr;\n                  intvalue = 0;\n                  REALvalue = 0;\n                  if(functions[i].values == NULL) {\n                    switch(functions[i].type) {\n                      case intfunction:\n                      case longfunction:\n                      case MYBOOLfunction:\n                        intvalue = strtol(ptr1, &ptr2, 10);\n                        while((*ptr2) && (isspace(*ptr2)))\n                          ptr2++;\n                        if(*ptr2) {\n                          report(lp, IMPORTANT, \"read_params: Invalid integer value on line %d\\n\", line);\n                          ret = FALSE;\n                        }\n                        break;\n                      case REALfunction:\n                        REALvalue = strtod(ptr1, &ptr2);\n                        while((*ptr2) && (isspace(*ptr2)))\n                          ptr2++;\n                        if(*ptr2) {\n                          report(lp, IMPORTANT, \"read_params: Invalid real value on line %d\\n\", line);\n                          ret = FALSE;\n                        }\n                        break;\n                    }\n                  }\n                  else {\n                    while(ret) {\n                      ptr = strchr(ptr1, '+');\n                      if(ptr == NULL)\n                        ptr = ptr1 + strlen(ptr1);\n                      for(; isspace(*ptr1); ptr1++);\n                      for(ptr2 = ptr - 1; (ptr2 >= ptr1) && (isspace(*ptr2)); ptr2--);\n                      if(ptr2 <= ptr1)\n                        break;\n                      else {\n                        ptr2[1] = 0;\n                        hp = findhash(ptr1, hashparameters);\n                        if (hp == NULL) {\n                          report(lp, IMPORTANT, \"read_params: Invalid parameter name (%s) on line %d\\n\", ptr1, line);\n                          ret = FALSE;\n                        }\n                        else {\n                          j = hp->index;\n                          if((j >= functions[i].elements) ||\n                             (strcmp(functions[i].values[j].svalue, ptr1))) {\n                            report(lp, IMPORTANT, \"read_params: Inappropriate parameter name (%s) on line %d\\n\", ptr1, line);\n                            ret = FALSE;\n                          }\n                          else {\n                            intvalue += functions[i].values[j].value;\n                          }\n                        }\n                        ptr1 = ptr + 1;\n                      }\n                    }\n                  }\n                  if(ret) {\n                    switch(functions[i].type) {\n                      case intfunction:\n                        functions[i].set_function.int_set_function(lp, intvalue);\n                        break;\n                      case longfunction:\n                        functions[i].set_function.long_set_function(lp, intvalue);\n                        break;\n                      case MYBOOLfunction:\n                        functions[i].set_function.MYBOOL_set_function(lp, (MYBOOL) intvalue);\n                        break;\n                      case REALfunction:\n                        functions[i].set_function.REAL_set_function(lp, REALvalue);\n                        break;\n                    }\n                  }\n                }\n              }\n            }\n          }\n          break;\n      }\n    }\n\n    FREE(header);\n    free_hash_table(hashfunctions);\n    free_hash_table(hashparameters);\n\n    ini_close(fp);\n  }\n\n  return( (MYBOOL) ret );\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_presolve.c",
    "content": "\n/* -------------------------------------------------------------------------\n   Presolve routines for lp_solve v5.0+\n   -------------------------------------------------------------------------\n    Author:        Kjell Eikland\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      lp_lib.h, lp_presolve, lp_crash.h, lp_scale.h, lp_report.h\n\n    Release notes:\n    v1.0.0  1 January 2003      Initial crude version used with lp_solve v4.\n    v5.0.0  1 January 2004      Significantly expanded and repackaged\n                                presolve routines for lp_solve v5 release.\n    v5.0.1  1 April   2004      Added reference to new crash module\n    v5.1.0  20 August 2004      Reworked infeasibility detection.\n                                Added encapsulation of presolve undo logic.\n    v5.1.1  10 September 2004   Added variable bound tightening based on\n                                full-constraint information, as well as\n                                variable fixing by duality.\n    v5.2.0  1 January 2005      Fixes to bound fixing handling.\n                                Added fast batch compression after presolve.\n                                Restructured calls by adding presolve wrapper.\n                                Major optimization of identification logic\n                                  along with bug fixes.\n                                Enabled storage of eliminated matrix data.\n                                Added function to report on constraint classes.\n    v5.5.0  1 June 2005         Added implied slack presolve, restructured\n                                looping logic to be more modular, and made\n                                active row/column selection logic faster.\n    v5.5.1  18 June 2005        Finished sparsity-enhancing logic and added\n                                initial version of column aggregation code.\n   ------------------------------------------------------------------------- */\n\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_presolve.h\"\n#include \"lp_crash.h\"\n#include \"lp_scale.h\"\n#include \"lp_report.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n#define presolve_setstatus(one, two)  presolve_setstatusex(one, two, __LINE__, __FILE__)\nSTATIC int presolve_setstatusex(presolverec *psdata, int status, int lineno, char *filename)\n{\n  if((status == INFEASIBLE) || (status == UNBOUNDED)) {\n    report(psdata->lp,\n#ifdef Paranoia\n           NORMAL,\n#else\n           DETAILED,\n#endif\n           \"presolve_setstatus: Status set to '%s' on code line %d, file '%s'\\n\",\n           (status == INFEASIBLE ? \"INFEASIBLE\" : \"UNBOUNDED\"), lineno, (filename == NULL ? \"Unknown\" : filename));\n  }\n  return( status );\n}\n\nSTATIC MYBOOL presolve_statuscheck(presolverec *psdata, int *status)\n{\n  if(*status == RUNNING) {\n    lprec *lp = psdata->lp;\n    if(!mat_validate(lp->matA))\n      *status = MATRIXERROR;\n    else if(userabort(lp, -1))\n      *status = lp->spx_status;\n  }\n  return( (MYBOOL) (*status == RUNNING) );\n}\n\nSTATIC MYBOOL presolve_createUndo(lprec *lp)\n{\n  if(lp->presolve_undo != NULL)\n    presolve_freeUndo(lp);\n  lp->presolve_undo = (presolveundorec *) calloc(1, sizeof(presolveundorec));\n  lp->presolve_undo->lp = lp;\n  if(lp->presolve_undo == NULL)\n    return( FALSE );\n  return( TRUE );\n}\nSTATIC MYBOOL inc_presolve_space(lprec *lp, int delta, MYBOOL isrows)\n{\n  int i, ii,\n      oldrowcolalloc, rowcolsum, oldrowalloc, oldcolalloc;\n  presolveundorec *psundo = lp->presolve_undo;\n\n  if(psundo == NULL) {\n    presolve_createUndo(lp);\n    psundo = lp->presolve_undo;\n  }\n\n  /* Set constants */\n  oldrowalloc = lp->rows_alloc-delta;\n  oldcolalloc = lp->columns_alloc-delta;\n  oldrowcolalloc = lp->sum_alloc-delta;\n  rowcolsum = lp->sum_alloc + 1;\n\n  /* Reallocate lp memory */\n  if(isrows)\n    allocREAL(lp, &psundo->fixed_rhs,   lp->rows_alloc+1, AUTOMATIC);\n  else\n    allocREAL(lp, &psundo->fixed_obj,   lp->columns_alloc+1, AUTOMATIC);\n  allocINT(lp,  &psundo->var_to_orig, rowcolsum, AUTOMATIC);\n  allocINT(lp,  &psundo->orig_to_var, rowcolsum, AUTOMATIC);\n\n  /* Fill in default values, where appropriate */\n  if(isrows)\n    ii = oldrowalloc+1;\n  else\n    ii = oldcolalloc+1;\n  for(i = oldrowcolalloc+1; i < rowcolsum; i++, ii++) {\n    psundo->var_to_orig[i] = 0;\n    psundo->orig_to_var[i] = 0;\n    if(isrows)\n      psundo->fixed_rhs[ii] = 0;\n    else\n      psundo->fixed_obj[ii] = 0;\n  }\n\n  return(TRUE);\n}\nSTATIC MYBOOL presolve_setOrig(lprec *lp, int orig_rows, int orig_cols)\n{\n  presolveundorec *psundo = lp->presolve_undo;\n\n  if(psundo == NULL)\n    return( FALSE );\n  psundo->orig_rows = orig_rows;\n  psundo->orig_columns = orig_cols;\n  psundo->orig_sum = orig_rows + orig_cols;\n  if(lp->wasPresolved)\n    presolve_fillUndo(lp, orig_rows, orig_cols, FALSE);\n  return( TRUE );\n}\nSTATIC MYBOOL presolve_fillUndo(lprec *lp, int orig_rows, int orig_cols, MYBOOL setOrig)\n{\n  int i;\n  presolveundorec *psundo = lp->presolve_undo;\n\n  for(i = 0; i <= orig_rows; i++) {\n    psundo->var_to_orig[i] = i;\n    psundo->orig_to_var[i] = i;\n    psundo->fixed_rhs[i]   = 0;\n  }\n  for(i = 1; i <= orig_cols; i++) {\n    psundo->var_to_orig[orig_rows + i] = i;\n    psundo->orig_to_var[orig_rows + i] = i;\n    psundo->fixed_obj[i] = 0;\n  }\n  if(setOrig)\n    presolve_setOrig(lp, orig_rows, orig_cols);\n\n  return( TRUE );\n}\nSTATIC MYBOOL presolve_rebuildUndo(lprec *lp, MYBOOL isprimal)\n{\n  int             ik, ie, ix, j, k, *colnrDep;\n  REAL             hold, *value, *solution, *slacks;\n  presolveundorec *psdata = lp->presolve_undo;\n  MATrec          *mat = NULL;\n\n  /* Point to and initialize undo structure at first call */\n  if(isprimal) {\n    if(psdata->primalundo != NULL)\n      mat = psdata->primalundo->tracker;\n    solution = lp->full_solution + lp->presolve_undo->orig_rows;\n    slacks   = lp->full_solution;\n  }\n  else {\n    if(psdata->dualundo != NULL)\n      mat = psdata->dualundo->tracker;\n    solution = lp->full_duals;\n    slacks   = lp->full_duals + lp->presolve_undo->orig_rows;\n  }\n  if(mat == NULL)\n    return( FALSE );\n\n  /* Loop backward over the undo chain */\n  for(j = mat->col_tag[0]; j > 0; j--) {\n    ix = mat->col_tag[j];\n    ik = mat->col_end[j-1];\n    ie = mat->col_end[j];\n    colnrDep = &COL_MAT_ROWNR(ik);\n    value    = &COL_MAT_VALUE(ik);\n    hold = 0;\n    k = 0;\n    for(; ik < ie; ik++, colnrDep += matRowColStep, value += matValueStep) {\n\n      /* Constant term */\n      if(*colnrDep == 0)\n        hold += *value;\n\n      /* Special case with dependence on a slack variable */\n      else if(isprimal && (*colnrDep > lp->presolve_undo->orig_columns)) {\n        k = (*colnrDep) - lp->presolve_undo->orig_columns;\n        hold -= (*value) * slacks[k];\n        slacks[k] = 0;\n      }\n      else if(!isprimal && (*colnrDep > lp->presolve_undo->orig_rows)) {\n        k = (*colnrDep) - lp->presolve_undo->orig_rows;\n        hold -= (*value) * slacks[k];\n        slacks[k] = 0;\n      }\n\n      /* Dependence on other user variable */\n      else\n        hold -= (*value) * solution[*colnrDep];\n\n      *value = 0;\n    }\n    if(fabs(hold) > lp->epsvalue)\n      solution[ix] = hold;\n  }\n\n  return( TRUE );\n}\nSTATIC MYBOOL presolve_freeUndo(lprec *lp)\n{\n  presolveundorec *psundo = lp->presolve_undo;\n\n  if(psundo == NULL)\n    return( FALSE );\n  FREE(psundo->orig_to_var);\n  FREE(psundo->var_to_orig);\n  FREE(psundo->fixed_rhs);\n  FREE(psundo->fixed_obj);\n  if(psundo->deletedA != NULL)\n    freeUndoLadder(&(psundo->deletedA));\n  if(psundo->primalundo != NULL)\n    freeUndoLadder(&(psundo->primalundo));\n  if(psundo->dualundo != NULL)\n    freeUndoLadder(&(psundo->dualundo));\n  FREE(lp->presolve_undo);\n  return( TRUE );\n}\n\nSTATIC void presolve_storeDualUndo(presolverec *psdata, int rownr, int colnr)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   firstdone = FALSE;\n  int      ix, iix, item;\n  REAL     Aij = get_mat(lp, rownr, colnr);\n  MATrec   *mat = lp->matA;\n\n  if(presolve_collength(psdata, colnr) == 0)\n    return;\n\n  /* Add undo information for the dual of the deleted constraint */\n  item = 0;\n  for(ix = presolve_nextrow(psdata, colnr, &item); ix >= 0;\n      ix = presolve_nextrow(psdata, colnr, &item)) {\n    iix = COL_MAT_ROWNR(ix);\n    if(iix == rownr)\n      continue;\n    if(!firstdone)\n      firstdone = addUndoPresolve(lp, FALSE, rownr, get_mat(lp, 0, colnr)/Aij,\n                                                    get_mat_byindex(lp, ix, FALSE, TRUE)/Aij, iix);\n    else\n      appendUndoPresolve(lp, FALSE, get_mat_byindex(lp, ix, FALSE, TRUE)/Aij, iix);\n  }\n}\n\n/* ----------------------------------------------------------------------------- */\n/* Presolve debugging routines                                                   */\n/* ----------------------------------------------------------------------------- */\nSTATIC MYBOOL presolve_SOScheck(presolverec *psdata)\n{\n  MYBOOL status = TRUE;\n  lprec  *lp = psdata->lp;\n  int    *list, i, j, n, k, nk, colnr, nSOS = SOS_count(lp), nerr = 0;\n  SOSrec *SOS;\n\n  if(nSOS == 0)\n    return( status );\n\n  /* For each SOS and each member check validity */\n  for(i = 1; i<= nSOS; i++) {\n    SOS = lp->SOS->sos_list[i-1];\n    list = SOS->members;\n    n = list[0];\n    for(j = 1; j<= n; j++) {\n      colnr = list[j];\n      /* Check valid range */\n      if((colnr < 1) || (colnr > lp->columns)) {\n        nerr++;\n        report(lp, IMPORTANT, \"presolve_SOScheck: A - Column index %d is outside of valid range\\n\",\n                              colnr);\n      }\n      /* Check for deletion */\n      if(!isActiveLink(psdata->cols->varmap, colnr)) {\n        nerr++;\n        report(lp, IMPORTANT, \"presolve_SOScheck: B - Column index %d has been marked for deletion\\n\",\n                              colnr);\n      }\n      /* Check if sorted member array is Ok */\n      if(SOS_member_index(lp->SOS, i, colnr) != j) {\n        nerr++;\n        report(lp, IMPORTANT, \"presolve_SOScheck: C - Column index %d not found in fast search array\\n\",\n                              colnr);\n      }\n      /* Check for variable membership in this SOS record of the sparse storage */\n      k = lp->SOS->memberpos[colnr-1];\n      nk = lp->SOS->memberpos[colnr];\n      while((k < nk) && (lp->SOS->membership[k] != i))\n        k++;\n      if(k >= nk) {\n        nerr++;\n        report(lp, IMPORTANT, \"presolve_SOScheck: D - Column index %d was not found in sparse array\\n\",\n                              colnr);\n      }\n    }\n  }\n\n  /* Check that all members in the sparse array can be validated as SOS members */\n  for(colnr = 1; colnr <= lp->columns; colnr++) {\n    k = lp->SOS->memberpos[colnr-1];\n    nk = lp->SOS->memberpos[colnr];\n    for(; k < nk; k++) {\n      if(!SOS_is_member(lp->SOS, lp->SOS->membership[k], colnr)) {\n        nerr++;\n        report(lp, IMPORTANT, \"presolve_SOScheck: E - Sparse array did not indicate column index %d as member of SOS %d\\n\",\n                              colnr, lp->SOS->membership[k]);\n      }\n    }\n  }\n  status = (MYBOOL) (nerr == 0);\n  if(!status)\n    report(lp, IMPORTANT, \"presolve_SOScheck: There were %d errors\\n\",\n                           nerr);\n\n\n  return( status );\n}\n\n/* ----------------------------------------------------------------------------- */\n/* Presolve routines for tightening the model                                    */\n/* ----------------------------------------------------------------------------- */\n\nINLINE REAL presolve_roundrhs(lprec *lp, REAL value, MYBOOL isGE)\n{\n#ifdef DoPresolveRounding\n  REAL eps = PRESOLVE_EPSVALUE*1000,\n  /* REAL eps = PRESOLVE_EPSVALUE*pow(10.0,MAX(0,log10(1+fabs(value)))), */\n  testout = my_precision(value, eps);\n#if 1\n  if(my_chsign(isGE, value-testout) < 0)\n    value = testout;\n#elif 0\n  if(my_chsign(isGE, value-testout) < 0)\n    value = testout;\n  else if(value != testout)\n    value += my_chsign(isGE, (value-testout)/2);\n    /* value = testout + my_chsign(isGE, (value-testout)/2); */\n#else\n  if(testout != value)\n    value += my_chsign(isGE, eps*1000);              /* BASE OPTION */\n#endif\n\n#endif\n  return( value );\n}\n\nINLINE REAL presolve_roundval(lprec *lp, REAL value)\n{\n#ifdef DoPresolveRounding\n  /* value = my_precision(value, PRESOLVE_EPSVALUE*MAX(1,log10(1+fabs(value)))); */\n  value = my_precision(value, PRESOLVE_EPSVALUE);    /* BASE OPTION */\n#endif\n  return( value );\n}\n\nINLINE MYBOOL presolve_mustupdate(lprec *lp, int colnr)\n{\n#if 0\n  return( my_infinite(lp, get_lowbo(lp, colnr)) ||\n          my_infinite(lp, get_upbo(lp, colnr)) );\n#else\n  return( my_infinite(lp, lp->orig_lowbo[lp->rows+colnr]) ||\n          my_infinite(lp, lp->orig_upbo[lp->rows+colnr]) );\n#endif\n}\n\nINLINE REAL presolve_sumplumin(lprec *lp, int item, psrec *ps, MYBOOL doUpper)\n{\n  REAL *plu = (doUpper ? ps->pluupper : ps->plulower),\n       *neg = (doUpper ? ps->negupper : ps->neglower);\n\n  if(fabs(plu[item]) >= lp->infinite)\n    return( plu[item] );\n  else if(fabs(neg[item]) >= lp->infinite)\n    return( neg[item] );\n  else\n    return( plu[item]+neg[item] );\n}\n\nINLINE void presolve_range(lprec *lp, int rownr, psrec *ps, REAL *loValue, REAL *hiValue)\n{\n  *loValue = presolve_sumplumin(lp, rownr,   ps, FALSE);\n  *hiValue = presolve_sumplumin(lp, rownr,   ps, TRUE);\n}\n\nSTATIC void presolve_rangeorig(lprec *lp, int rownr, psrec *ps, REAL *loValue, REAL *hiValue, REAL delta)\n{\n  delta = my_chsign(is_chsign(lp, rownr), lp->presolve_undo->fixed_rhs[rownr] + delta);\n  *loValue = presolve_sumplumin(lp, rownr,   ps, FALSE) + delta;\n  *hiValue = presolve_sumplumin(lp, rownr,   ps, TRUE) + delta;\n}\n\nSTATIC MYBOOL presolve_rowfeasible(presolverec *psdata, int rownr, MYBOOL userowmap)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   status = TRUE;\n  int      contype, origrownr = rownr;\n  REAL     LHS, RHS, value;\n\n  /* Optionally loop across all active rows in the provided map (debugging) */\n  if(userowmap)\n    rownr = firstActiveLink(psdata->rows->varmap);\n\n  /* Now do once for ingoing rownr or loop across rowmap */\n  while((status == TRUE) && (rownr != 0)) {\n\n    /* Check the lower bound */\n    value = presolve_sumplumin(lp, rownr, psdata->rows, TRUE);\n    LHS = get_rh_lower(lp, rownr);\n    if(value < LHS-lp->epssolution) {\n      contype = get_constr_type(lp, rownr);\n      report(lp, NORMAL, \"presolve_rowfeasible: Lower bound infeasibility in %s row %s (%g << %g)\\n\",\n                          get_str_constr_type(lp, contype), get_row_name(lp, rownr), value, LHS);\n      if(rownr != origrownr)\n      report(lp, NORMAL, \"        ...           Input row base used for testing was %s\\n\",\n                                                    get_row_name(lp, origrownr));\n      status = FALSE;\n    }\n\n    /* Check the upper bound */\n    value = presolve_sumplumin(lp, rownr, psdata->rows, FALSE);\n    RHS = get_rh_upper(lp, rownr);\n    if(value > RHS+lp->epssolution) {\n      contype = get_constr_type(lp, rownr);\n      report(lp, NORMAL, \"presolve_rowfeasible: Upper bound infeasibility in %s row %s (%g >> %g)\\n\",\n                          get_str_constr_type(lp, contype), get_row_name(lp, rownr), value, RHS);\n      status = FALSE;\n    }\n    if(userowmap)\n      rownr = nextActiveLink(psdata->rows->varmap, rownr);\n    else\n      rownr = 0;\n  }\n  return( status );\n}\n\nSTATIC MYBOOL presolve_debugmap(presolverec *psdata, char *caption)\n{\n  lprec *lp = psdata->lp;\n  MATrec *mat = lp->matA;\n  int    colnr, ix, ie, nx, jx, je, *cols, *rows, n;\n  int    nz = mat->col_end[lp->columns] - 1;\n  MYBOOL status = FALSE;\n\n  for(colnr = 1; colnr <= lp->columns; colnr++) {\n    rows = psdata->cols->next[colnr];\n    if(!isActiveLink(psdata->cols->varmap, colnr)) {\n      if(rows != NULL) {\n        report(lp, SEVERE, \"presolve_debugmap: Inactive column %d is non-empty\\n\",\n                           colnr);\n        goto Done;\n      }\n      else\n        continue;\n    }\n    if(rows == NULL)\n      report(lp, SEVERE, \"presolve_debugmap: Active column %d is empty\\n\",\n                         colnr);\n    je = *rows;\n    rows++;\n    for(jx = 1; jx <= je; jx++, rows++) {\n      if((*rows < 0) || (*rows > nz)) {\n        report(lp, SEVERE, \"presolve_debugmap: NZ index %d for column %d out of range (index %d<=%d)\\n\",\n                           *rows, colnr, jx, je);\n        goto Done;\n      }\n      cols = psdata->rows->next[COL_MAT_ROWNR(*rows)];\n      ie = cols[0];\n      n = 0;\n      for(ix = 1; ix <= ie; ix++) {\n        nx = cols[ix];\n        if((nx < 0) || (nx > nz)) {\n          report(lp, SEVERE, \"presolve_debugmap: NZ index %d for column %d to row %d out of range\\n\",\n                             nx, colnr, jx);\n          goto Done;\n        }\n      }\n    }\n  }\n  status = TRUE;\nDone:\n  if(!status && (caption != NULL))\n    report(lp, SEVERE, \"...caller was '%s'\\n\", caption);\n  return( status );\n}\n\nSTATIC MYBOOL presolve_validate(presolverec *psdata, MYBOOL forceupdate)\n{\n  int    i, ie, j, je, k, rownr, *items;\n  REAL   upbound, lobound, value;\n  lprec  *lp = psdata->lp;\n  MATrec *mat = lp->matA;\n  MYBOOL status = mat->row_end_valid && !forceupdate;\n\n  if(status)\n    return( status );\n  else if(!mat->row_end_valid)\n    status = mat_validate(mat);\n  else\n    status = forceupdate;\n  if(status) {\n\n    /* First update rows... */\n    for(i = 1; i <= lp->rows; i++) {\n\n      psdata->rows->plucount[i] = 0;\n      psdata->rows->negcount[i] = 0;\n      psdata->rows->pluneg[i]   = 0;\n\n      if(!isActiveLink(psdata->rows->varmap, i)) {\n        FREE(psdata->rows->next[i]);\n      }\n      else {\n        /* Create next column pointers by row */\n        k = mat_rowlength(mat, i);\n        allocINT(lp, &(psdata->rows->next[i]), k+1, AUTOMATIC);\n        items = psdata->rows->next[i];\n        je = mat->row_end[i];\n        k = 0;\n        for(j = mat->row_end[i-1]; j < je; j++)\n          if(isActiveLink(psdata->cols->varmap, ROW_MAT_COLNR(j))) {\n            k++;\n            items[k] = j;\n          }\n        items[0] = k;\n      }\n    }\n\n    /* ...then update columns */\n    for(j = 1; j <= lp->columns; j++) {\n\n      psdata->cols->plucount[j] = 0;\n      psdata->cols->negcount[j] = 0;\n      psdata->cols->pluneg[j]   = 0;\n\n      if(!isActiveLink(psdata->cols->varmap, j)) {\n        FREE(psdata->cols->next[j]);\n      }\n      else {\n        upbound = get_upbo(lp, j);\n        lobound = get_lowbo(lp, j);\n        if(is_semicont(lp, j) && (upbound > lobound)) {\n          if(lobound > 0)\n            lobound = 0;\n          else if(upbound < 0)\n            upbound = 0;\n        }\n\n        /* Create next row pointers by column */\n        k = mat_collength(mat, j);\n        allocINT(lp, &(psdata->cols->next[j]), k+1, AUTOMATIC);\n        items = psdata->cols->next[j];\n        ie = mat->col_end[j];\n        k = 0;\n        for(i = mat->col_end[j-1]; i < ie; i++) {\n          rownr = COL_MAT_ROWNR(i);\n          if(isActiveLink(psdata->rows->varmap, rownr)) {\n            k++;\n            items[k] = i;\n\n            /* Cumulate counts */\n            value = COL_MAT_VALUE(i);\n            if(my_chsign(is_chsign(lp, rownr), value) > 0) {\n              psdata->rows->plucount[rownr]++;\n              psdata->cols->plucount[j]++;\n            }\n            else {\n              psdata->rows->negcount[rownr]++;\n              psdata->cols->negcount[j]++;\n            }\n            if((lobound < 0) && (upbound >= 0)) {\n              psdata->rows->pluneg[rownr]++;\n              psdata->cols->pluneg[j]++;\n            }\n          }\n        }\n        items[0] = k;\n      }\n    }\n#ifdef Paranoia\n    presolve_debugmap(psdata, \"presolve_validate\");\n#endif\n  }\n  return( status );\n}\n\nSTATIC MYBOOL presolve_rowtallies(presolverec *psdata, int rownr, int *plu, int *neg, int *pluneg)\n{\n  REAL   value;\n  lprec  *lp = psdata->lp;\n  MATrec *mat = lp->matA;\n  int    ix, jx, ib = 0;\n  MYBOOL chsign = is_chsign(lp, rownr);\n\n  /* Initialize */\n  *plu = 0;\n  *neg = 0;\n  *pluneg = 0;\n\n  /* Loop over still active row members */\n  for(ix = presolve_nextcol(psdata, rownr, &ib); ix >= 0; ix = presolve_nextcol(psdata, rownr, &ib)) {\n\n    /* Get matrix column and value */\n    jx    = ROW_MAT_COLNR(ix);\n    value = ROW_MAT_VALUE(ix);\n\n    /* Cumulate counts */\n    if(my_chsign(chsign, value) > 0)\n      (*plu)++;\n    else\n      (*neg)++;\n    if((get_lowbo(lp, jx) < 0) && (get_upbo(lp, jx) >= 0))\n      (*pluneg)++;\n  }\n  return( TRUE );\n}\nSTATIC MYBOOL presolve_debugrowtallies(presolverec *psdata)\n{\n  lprec  *lp = psdata->lp;\n  int    i, plu, neg, pluneg, nerr = 0;\n\n  for(i = 1; i <= lp->rows; i++)\n    if(isActiveLink(psdata->rows->varmap, i) &&\n       presolve_rowtallies(psdata, i, &plu, &neg, &pluneg)) {\n      if((psdata->rows->plucount[i] != plu) ||\n         (psdata->rows->negcount[i] != neg) ||\n         (psdata->rows->pluneg[i] != pluneg)) {\n        nerr++;\n        report(lp, SEVERE, \"presolve_debugrowtallies: Detected inconsistent count for row %d\\n\", i);\n      }\n    }\n  return( (MYBOOL) (nerr == 0) );\n}\n\nSTATIC int presolve_debugcheck(lprec *lp, LLrec *rowmap, LLrec *colmap)\n{\n  int i, j, errc = 0;\n\n  /* Validate constraint bounds */\n  for(i = 1; i < lp->rows; i++) {\n    if((rowmap != NULL) && !isActiveLink(rowmap, i))\n      continue;\n    /* Check if we have a negative range */\n    if(lp->orig_upbo[i] < 0) {\n      errc++;\n      report(lp, SEVERE, \"presolve_debugcheck: Detected negative range %g for row %d\\n\",\n                         lp->orig_upbo[i], i);\n    }\n  }\n  /* Validate variables */\n  for(j = 1; j < lp->columns; j++) {\n    if((colmap != NULL) && !isActiveLink(colmap, j))\n      continue;\n    i = lp->rows+j;\n    /* Check if we have infeasible  bounds */\n    if(lp->orig_lowbo[i] > lp->orig_upbo[i]) {\n      errc++;\n      report(lp, SEVERE, \"presolve_debugcheck: Detected UB < LB for column %d\\n\",\n                         j);\n    }\n  }\n  /* Return total number of errors */\n  return( errc );\n}\n\nSTATIC MYBOOL presolve_candeletevar(presolverec *psdata, int colnr)\n{\n  lprec    *lp = psdata->lp;\n  int      usecount = SOS_memberships(lp->SOS, colnr);\n\n  return( (MYBOOL) ((lp->SOS == NULL) || (usecount == 0) ||\n                    (/*is_presolve(lp, PRESOLVE_SOS) &&*/\n                     (((lp->SOS->sos1_count == lp->SOS->sos_count)) ||\n                      (usecount == SOS_is_member_of_type(lp->SOS, colnr, SOS1))))) );\n}\n\nSTATIC int presolve_rowlengthex(presolverec *psdata, int rownr)\n{\n  int j1 = psdata->rows->plucount[rownr] + psdata->rows->negcount[rownr];\n#ifdef Paranoia\n  int j2 = presolve_rowlength(psdata, rownr);\n\n  if(j1 != j2) {\n    report(psdata->lp, SEVERE, \"presolve_rowlengthex: Expected row length %d, but found %d in row %s\\n\",\n                                j2, j1, get_row_name(psdata->lp, rownr));\n    j1 = -j1;\n  }\n#endif\n\n  return( j1 );\n}\nSTATIC int presolve_rowlengthdebug(presolverec *psdata)\n{\n  int rownr, n = 0;\n\n  for(rownr = firstActiveLink(psdata->rows->varmap); rownr != 0;\n    rownr = nextActiveLink(psdata->rows->varmap, rownr))\n    n += presolve_rowlengthex(psdata, rownr);\n  return( n );\n}\n\nINLINE int presolve_nextrecord(psrec *ps, int recnr, int *previtem)\n{\n  int *nzlist = ps->next[recnr], nzcount = nzlist[0], status = -1;\n\n  /* Check if we simply wish the last active column */\n  if(previtem == NULL) {\n    if(nzlist != NULL)\n      status = nzlist[*nzlist];\n    return( status );\n  }\n\n  /* Step to next */\n#ifdef Paranoia\n  else if((*previtem < 0) || (*previtem > nzcount))\n    return( status );\n#endif\n  (*previtem)++;\n\n  /* Set the return values */\n  if(*previtem > nzcount)\n    (*previtem) = 0;\n  else\n    status = nzlist[*previtem];\n\n  return( status );\n}\nINLINE int presolve_nextcol(presolverec *psdata, int rownr, int *previtem)\n/* Find the first active (non-eliminated) nonzero column in rownr after prevcol */\n{\n  return( presolve_nextrecord(psdata->rows, rownr, previtem) );\n}\nINLINE int presolve_lastcol(presolverec *psdata, int rownr)\n{\n  return( presolve_nextrecord(psdata->rows, rownr, NULL) );\n}\nINLINE int presolve_nextrow(presolverec *psdata, int colnr, int *previtem)\n/* Find the first active (non-eliminated) nonzero row in colnr after prevrow */\n{\n  return( presolve_nextrecord(psdata->cols, colnr, previtem) );\n}\nINLINE int presolve_lastrow(presolverec *psdata, int colnr)\n{\n  return( presolve_nextrecord(psdata->cols, colnr, NULL) );\n}\n\nINLINE void presolve_adjustrhs(presolverec *psdata, int rownr, REAL fixdelta, REAL epsvalue)\n{\n  lprec *lp = psdata->lp;\n\n  lp->orig_rhs[rownr] -= fixdelta;\n  if(epsvalue > 0)\n#if 1\n    my_roundzero(lp->orig_rhs[rownr], epsvalue);\n#else\n    lp->orig_rhs[rownr] = presolve_roundrhs(lp, lp->orig_rhs[rownr], FALSE);\n#endif\n  lp->presolve_undo->fixed_rhs[rownr] += fixdelta;\n}\n\nSTATIC int presolve_shrink(presolverec *psdata, int *nConRemove, int *nVarRemove)\n{\n  SOSgroup *SOS = psdata->lp->SOS;\n  int     status = RUNNING, countR = 0, countC = 0,\n          i, ix, n, *list;\n  REAL    fixValue;\n\n  /* Remove empty rows */\n  list = psdata->rows->empty;\n  if(list != NULL) {\n    n = list[0];\n    for(i = 1; i <= n; i++)\n      if(isActiveLink(psdata->rows->varmap, list[i])) {\n        presolve_rowremove(psdata, list[i], FALSE);\n        countR++;\n      }\n    if(nConRemove != NULL)\n      (*nConRemove) += countR;\n    list[0] = 0;\n  }\n\n  /* Fix and remove empty columns (unless they are in a SOS) */\n  list = psdata->cols->empty;\n  if(list != NULL) {\n    n = list[0];\n    for(i = 1; i <= n; i++) {\n      ix = list[i];\n      if(isActiveLink(psdata->cols->varmap, ix)) {\n        if(presolve_colfixdual(psdata, ix, &fixValue, &status)) {\n          if(!presolve_colfix(psdata, ix, fixValue, TRUE, nVarRemove)) {\n            status = presolve_setstatus(psdata, INFEASIBLE);\n            break;\n          }\n          presolve_colremove(psdata, ix, FALSE);\n          countC++;\n        }\n        else if(SOS_is_member(SOS, 0, ix))\n          report(psdata->lp, DETAILED, \"presolve_shrink: Empty column %d is member of a SOS\\n\", ix);\n      }\n    }\n    list[0] = 0;\n  }\n\n  return( status );\n}\n\nSTATIC void presolve_rowremove(presolverec *psdata, int rownr, MYBOOL allowcoldelete)\n{\n  lprec    *lp = psdata->lp;\n  MATrec   *mat = lp->matA;\n  int      ix, ie, nx, jx, je, *cols, *rows, n, colnr;\n\n#ifdef Paranoia\n  if((rownr < 1) || (rownr > lp->rows))\n    report(lp, SEVERE, \"presolve_rowremove: Row %d out of range\\n\", rownr);\n#endif\n\n  /* Remove this row for each column that is active in the row */\n  cols = psdata->rows->next[rownr];\n  ie = *cols;\n  cols++;\n  for(ix = 1; ix <= ie; ix++, cols++) {\n    n = 0;\n    colnr = ROW_MAT_COLNR(*cols);\n    rows = psdata->cols->next[colnr];\n    je = rows[0];\n    /* See if we can narrow the search window */\n    jx = je / 2;\n    if((jx > 5) && (rownr >= COL_MAT_ROWNR(rows[jx])))\n      n = jx-1;\n    else\n      jx = 1;\n    /* Do the compression loop */\n    for(; jx <= je; jx++) {\n      nx = rows[jx];\n      if(COL_MAT_ROWNR(nx) != rownr) {\n        n++;\n        rows[n] = nx;\n      }\n    }\n    rows[0] = n;\n\n    /* Make sure we delete columns that have become empty */\n#if 1\n    if((n == 0) && allowcoldelete) {\n      int *list = psdata->cols->empty;\n      n = ++list[0];\n      list[n] = colnr;\n    }\n#endif\n\n  }\n  FREE(psdata->rows->next[rownr]);\n\n  removeLink(psdata->rows->varmap, rownr);\n  switch(get_constr_type(lp, rownr)) {\n    case LE: removeLink(psdata->LTmap, rownr);\n              break;\n    case EQ: removeLink(psdata->EQmap, rownr);\n              break;\n  }\n  if(isActiveLink(psdata->INTmap, rownr))\n    removeLink(psdata->INTmap, rownr);\n}\n\nSTATIC int presolve_colremove(presolverec *psdata, int colnr, MYBOOL allowrowdelete)\n{\n  lprec    *lp = psdata->lp;\n\n#ifdef Paranoia\n  if((colnr < 1) || (colnr > lp->columns))\n    report(lp, SEVERE, \"presolve_colremove: Column %d out of range\\n\", colnr);\n  if(!isActiveLink(psdata->cols->varmap, colnr) || !presolve_candeletevar(psdata, colnr))\n    colnr = -1;\n  else\n#endif\n  {\n    MATrec *mat = lp->matA;\n    int    ix, ie, nx, jx, je, *cols, *rows, n, rownr;\n\n    /* Remove this column for each row that is active in the column */\n    rows = psdata->cols->next[colnr];\n    je = *rows;\n    rows++;\n    for(jx = 1; jx <= je; jx++, rows++) {\n      n = 0;\n      rownr = COL_MAT_ROWNR(*rows);\n      cols = psdata->rows->next[rownr];\n      ie = cols[0];\n      /* See if we can narrow the search window */\n      ix = ie / 2;\n      if((ix > 5) && (colnr >= ROW_MAT_COLNR(cols[ix])))\n        n = ix-1;\n      else\n        ix = 1;\n      /* Do the compression loop */\n      for(; ix <= ie; ix++) {\n        nx = cols[ix];\n        if(ROW_MAT_COLNR(nx) != colnr) {\n          n++;\n          cols[n] = nx;\n        }\n      }\n      cols[0] = n;\n\n      /* Make sure we delete rows that become empty */\n#if 1\n      if((n == 0) && allowrowdelete) {\n        int *list = psdata->rows->empty;\n        n = ++list[0];\n        list[n] = rownr;\n      }\n#endif\n\n    }\n    FREE(psdata->cols->next[colnr]);\n\n    /* Update other counts */\n    if(SOS_is_member(lp->SOS, 0, colnr)) {\n      if(lp->sos_priority != NULL) {\n        lp->sos_vars--;\n        if(is_int(lp, colnr))\n          lp->sos_ints--;\n      }\n      SOS_member_delete(lp->SOS, 0, colnr);\n      clean_SOSgroup(lp->SOS, TRUE);\n      if(SOS_count(lp) == 0)\n        free_SOSgroup(&(lp->SOS));\n    }\n\n    /* Finally remove the column from the active column list */\n    colnr = removeLink(psdata->cols->varmap, colnr);\n  }\n  return( colnr );\n}\n\nSTATIC int presolve_redundantSOS(presolverec *psdata, int *nb, int *nSum)\n{\n  lprec    *lp = psdata->lp;\n  int      i, ii, k, kk, j, nrows = lp->rows, *fixed = NULL,\n           iBoundTighten = 0, status = RUNNING;\n  SOSrec   *SOS;\n\n  /* Is there anything to do? */\n  i = ii = SOS_count(lp);\n  if(ii == 0)\n    return( status );\n\n  /* Allocate working member list */\n  if(!allocINT(lp, &fixed, lp->columns+1, FALSE) )\n    return( lp->spx_status );\n\n  /* Check if we have SOS'es that are already satisfied or fixable/satisfiable */\n  while(i > 0) {\n    SOS = lp->SOS->sos_list[i-1];\n    kk = SOS->members[0];\n    fixed[0] = 0;\n    for(k = 1; k <= kk; k++) {\n      j = SOS->members[k];\n      if((get_lowbo(lp, j) > 0) && !is_semicont(lp, j)) {\n        fixed[++fixed[0]] = k;\n        /* Abort if we have identified SOS infeasibility */\n        if(fixed[0] > SOS->type) {\n          status = presolve_setstatus(psdata, INFEASIBLE);\n          goto Done;\n        }\n      }\n    }\n    /* If there were an exact number of non-zero SOS members, check their sequentiality */\n    if(fixed[0] == SOS->type) {\n      /* Check sequentiality of members with non-zero lower bounds */\n      for(k = 2; k <= fixed[0]; k++) {\n        if(fixed[k] != fixed[k-1]+1) {\n          status = presolve_setstatus(psdata, INFEASIBLE);\n          goto Done;\n        }\n      }\n      /* Fix other member variables to zero, if necessary */\n      for(k = kk; k > 0; k--) {\n        j = SOS->members[k];\n        if((get_lowbo(lp, j) > 0) && !is_semicont(lp, j))\n          continue;\n        if(!presolve_colfix(psdata, j, 0.0, AUTOMATIC, &iBoundTighten)) {\n          status = presolve_setstatus(psdata, INFEASIBLE);\n          goto Done;\n        }\n      }\n      /* Remove the SOS */\n      delete_SOSrec(lp->SOS, i /* , FALSE */);\n    }\n    /* Otherwise, try to fix variables outside the SOS type window */\n    else if(fixed[0] > 0) {\n      for(k = kk; k > 0; k--) {\n        if((k > fixed[fixed[0]]-SOS->type) && /* After leading entries   */\n           (k < fixed[1]+SOS->type))          /* Before trailing entries */\n          continue;\n        j = SOS->members[k];\n        SOS_member_delete(lp->SOS, i, j);\n        /* if(get_upbo(lp, j) - get_lowbo(lp, j) < lp->epsprimal) */\n        if(is_fixedvar(lp, nrows+j))\n          continue;\n        if(!presolve_colfix(psdata, j, 0.0, AUTOMATIC, &iBoundTighten)) {\n          status = presolve_setstatus(psdata, INFEASIBLE);\n          goto Done;\n        }\n      }\n    }\n    i--;\n  }\n\n  /* Update the sparse member map if there were SOS deletions;\n     Remember that delete_SOSrec() above specified deferred updating! */\n  i = SOS_count(lp);\n  if((i < ii) || (iBoundTighten > 0)) {\n    SOS_member_updatemap(lp->SOS);\n  }\n\n  /* Update tag orders */\n  for(; i > 0; i--)\n    lp->SOS->sos_list[i-1]->tagorder = i;\n\nDone:\n  FREE(fixed);\n  (*nb) += iBoundTighten;\n  (*nSum) += iBoundTighten;\n\n  return( status );\n}\n\nSTATIC MYBOOL presolve_fixSOS1(presolverec *psdata, int colnr, REAL fixvalue, int *nr, int *nv)\n{\n  lprec    *lp = psdata->lp;\n  int      i, k, j;\n  SOSrec   *SOS;\n  REAL     newvalue;\n  MYBOOL   *fixed = NULL, status = FALSE;\n\n  /* Allocate working member list */\n  if(!allocMYBOOL(lp, &fixed, lp->columns+1, TRUE) )\n    return(FALSE);\n\n  /* Fix variables in SOS's where colnr is a member */\n  i = SOS_count(lp);\n  while(i > 0) {\n    /* Set next SOS target (note that colnr has been tested earlier as not being a member of a higher order SOS) */\n    SOS = lp->SOS->sos_list[i-1];\n    if(SOS_is_member(lp->SOS, i, colnr)) {\n      for(k = SOS->members[0]; k > 0; k--) {\n        j = SOS->members[k];\n        if(fixed[j])\n          continue;\n        if(j == colnr) {\n          fixed[j] = TRUE;\n          newvalue = fixvalue;\n        }\n        else {\n          fixed[j] = AUTOMATIC;\n          newvalue = 0.0;\n        }\n        /* If it is a member of a higher order SOS then just change bounds */\n        if(!presolve_candeletevar(psdata, j)) {\n          set_bounds(lp, j, newvalue, newvalue);\n          fixed[j] = TRUE | AUTOMATIC;\n          psdata->forceupdate = TRUE;\n        }\n        /* Otherwise fix it in preparation for removal */\n        else if(!presolve_colfix(psdata, j, newvalue, TRUE, nv))\n          goto Done;\n      }\n    }\n    i--;\n  }\n\n  /* Delete SOS'es or SOS member variables where we can */\n  k = i = SOS_count(lp);\n  while(i > 0) {\n    /* Set next SOS target */\n    SOS = lp->SOS->sos_list[i-1];\n    if(SOS_is_member(lp->SOS, i, colnr)) {\n      /* Always delete SOS1's */\n      if(SOS->type == SOS1)\n        delete_SOSrec(lp->SOS, i /* , FALSE */);\n      /* Only delete leading or trailing SOS members in higher-order SOS'es that are fixed at 0;\n        (note that this section of the code will never be called in the current setup) */\n      else {\n        /* First the leading entries... */\n        for(j = 1; j <= SOS->members[0]; j++) {\n          if(fixed[SOS->members[j]] == AUTOMATIC)\n            SOS_member_delete(lp->SOS, i, SOS->members[j]);\n        }\n        /* ...then trailing entries */\n        for(j = SOS->members[0]; j > 0; j--) {\n          if(fixed[SOS->members[j]] == AUTOMATIC)\n            SOS_member_delete(lp->SOS, i, SOS->members[j]);\n        }\n      }\n    }\n    i--;\n  }\n\n  /* Update the sparse member map if there were SOS deletions; delete_SOSrec() above\n     specified deferred updating */\n  i = SOS_count(lp);\n  if(i < k)\n    SOS_member_updatemap(lp->SOS);\n\n  /* Delete the variables that have been fixed */\n  k = 0;\n  for(j = lp->columns; j > 0; j--) {\n    if((fixed[j] == TRUE) || (fixed[j] == AUTOMATIC)) {\n       presolve_colremove(psdata, j, TRUE);\n       k++;\n    }\n  }\n\n  /* Update tag orders */\n  i = SOS_count(lp);\n  for(; i > 0; i--)\n    lp->SOS->sos_list[i-1]->tagorder = i;\n\n  status = TRUE;\n\nDone:\n  FREE(fixed);\n  return( status );\n}\n\nSTATIC void presolve_setEQ(presolverec *psdata, int rownr)\n{\n  lprec *lp = psdata->lp;\n\n  if(is_constr_type(lp, rownr, LE))\n     removeLink(psdata->LTmap, rownr);\n   setLink(psdata->EQmap, rownr);\n   set_constr_type(lp, rownr, EQ);\n   psdata->dv_lobo[rownr] = -lp->infinite;\n   psdata->dv_upbo[rownr] = lp->infinite;\n}\n\nSTATIC MYBOOL presolve_singletonbounds(presolverec *psdata, int rownr, int colnr, REAL *lobound, REAL *upbound, REAL *aval)\n{\n  lprec  *lp = psdata->lp;\n  REAL   coeff_a, epsvalue = psdata->epsvalue;\n  MYBOOL isneg;\n\n  /* Compute row singleton variable range */\n  if(is_constr_type(lp, rownr, EQ) && (fabs(*lobound) < epsvalue))\n    *lobound = *upbound = 0;\n  else {\n    if(aval == NULL)\n      coeff_a = get_mat(lp, rownr, colnr);\n    else\n      coeff_a = *aval;\n    isneg = (MYBOOL) (coeff_a < 0);\n    if(*lobound > -lp->infinite)\n      *lobound /= coeff_a;\n    else if(isneg)\n      *lobound = -(*lobound);\n    if(*upbound < lp->infinite)\n      *upbound /= coeff_a;\n    else if(isneg)\n      *upbound = -(*upbound);\n    if(isneg)\n      swapREAL(lobound, upbound);\n  }\n\n  /* Check against bound - handle SC variables specially */\n  if(is_semicont(lp, colnr)) {\n    coeff_a = get_lowbo(lp, colnr);\n    if(coeff_a > 0) {\n      SETMAX(*lobound, 0.0);\n      SETMIN(*upbound, get_upbo(lp, colnr));\n    }\n    else {\n      coeff_a = get_upbo(lp, colnr);\n      if(coeff_a > 0) {\n        SETMAX(*lobound, get_lowbo(lp, colnr));\n        SETMIN(*upbound, 0.0);\n      }\n    }\n  }\n  else {\n    SETMAX(*lobound, get_lowbo(lp, colnr));\n    SETMIN(*upbound, get_upbo(lp, colnr));\n  }\n\n  /* Return with consistency status */\n#ifdef DoPresolveRelativeTest\n  isneg = (MYBOOL) (my_reldiff(*upbound, *lobound) >= - epsvalue);\n#else\n  isneg = (MYBOOL) (*upbound >= *lobound - epsvalue);\n#endif\n  if(!isneg) {\n    /* Attempt bound-related error correction */\n    if(fabs(my_reldiff(*lobound, get_upbo(lp, colnr))) < PRESOLVE_BOUNDSLACK*epsvalue)\n      *lobound = get_upbo(lp, colnr);\n    else if(fabs(my_reldiff(*upbound, get_lowbo(lp, colnr))) < PRESOLVE_BOUNDSLACK*epsvalue)\n      *upbound = get_lowbo(lp, colnr);\n#ifdef DoPresolveRelativeTest\n    isneg = (MYBOOL) (my_reldiff(*upbound, *lobound) >= - epsvalue);\n#else\n    isneg = (MYBOOL) (*upbound >= *lobound - epsvalue);\n#endif\n    if(!isneg)\n      report(lp, NORMAL, \"presolve_singletonbounds: Singleton variable %s in row %s infeasibility (%g << %g)\\n\",\n                         get_col_name(lp, colnr), get_row_name(lp, rownr), *lobound, *upbound);\n  }\n  return( isneg );\n}\n\nSTATIC MYBOOL presolve_altsingletonvalid(presolverec *psdata, int rownr, int colnr, REAL reflotest, REAL refuptest)\n{\n  lprec *lp = psdata->lp;\n  REAL  coeff_bl, coeff_bu, epsvalue = psdata->epsvalue;\n\n  coeff_bl = get_rh_lower(lp, rownr);\n  coeff_bu = get_rh_upper(lp, rownr);\n\n  /* Check base data validity */\n#ifdef DoPresolveRelativeTest\n  if((my_reldiff(refuptest, reflotest) < -epsvalue) ||\n#else\n  if((reflotest > refuptest + epsvalue) ||\n#endif\n     !presolve_singletonbounds(psdata, rownr, colnr, &coeff_bl, &coeff_bu, NULL))\n    return( FALSE );\n\n  /* Base data is Ok, now check against against each other */\n  epsvalue = MAX(reflotest-coeff_bu, coeff_bl-refuptest) / epsvalue;\n  if(epsvalue > PRESOLVE_BOUNDSLACK) {\n    report(lp, NORMAL, \"presolve_altsingletonvalid: Singleton variable %s in row %s infeasible (%g)\\n\",\n                       get_col_name(lp, colnr), get_row_name(lp, rownr), MAX(reflotest-coeff_bu, coeff_bl-refuptest));\n    return( FALSE );\n  }\n  else\n    return( TRUE );\n}\n\nSTATIC MYBOOL presolve_multibounds(presolverec *psdata, int rownr, int colnr,\n                                   REAL *lobound, REAL *upbound, REAL *aval, MYBOOL *rowbinds)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   rowbindsvar = FALSE, status = FALSE;\n  REAL     coeff_a, LHS, RHS, netX, Xupper, Xlower, epsvalue = psdata->epsvalue;\n\n  /* Get variable bounds for netting */\n  LHS = *lobound;\n  RHS = *upbound;\n  Xlower = get_lowbo(lp, colnr);\n  Xupper = get_upbo(lp, colnr);\n\n  /* Identify opportunity for bound tightening */\n  if(aval == NULL)\n    coeff_a = get_mat(lp, rownr, colnr);\n  else\n    coeff_a = *aval;\n\n  netX = presolve_sumplumin(lp, rownr, psdata->rows, TRUE);\n  if(!my_infinite(lp, LHS) && !my_infinite(lp, netX)) {\n    if(coeff_a > 0) {\n      LHS -= netX-coeff_a*Xupper;\n      LHS /= coeff_a;\n      if(LHS > Xlower + epsvalue) {\n        Xlower = presolve_roundrhs(lp, LHS, TRUE);\n        status = TRUE;\n      }\n      else if(LHS > Xlower - epsvalue)\n        rowbindsvar = TRUE;\n    }\n    else {\n      LHS -= netX-coeff_a*Xlower;\n      LHS /= coeff_a;\n      if(LHS < Xupper - epsvalue) {\n        Xupper = presolve_roundrhs(lp, LHS, FALSE);\n        status = AUTOMATIC;\n      }\n      else if(LHS < Xupper + epsvalue)\n        rowbindsvar = AUTOMATIC;\n    }\n  }\n\n  netX = presolve_sumplumin(lp, rownr, psdata->rows, FALSE);\n  if(!my_infinite(lp, RHS) && !my_infinite(lp, netX)) {\n    if(coeff_a < 0) {\n      if(!my_infinite(lp, Xupper)) {\n        RHS -= netX-coeff_a*Xupper;\n        RHS /= coeff_a;\n        if(RHS > Xlower + epsvalue) {\n          Xlower = presolve_roundrhs(lp, RHS, TRUE);\n          status |= TRUE;\n        }\n        else if(RHS > Xlower - epsvalue)\n          rowbindsvar |= TRUE;\n      }\n    }\n    else if(!my_infinite(lp, Xlower)) {\n      RHS -= netX-coeff_a*Xlower;\n      RHS /= coeff_a;\n      if(RHS < Xupper - epsvalue) {\n        Xupper = presolve_roundrhs(lp, RHS, FALSE);\n        status |= AUTOMATIC;\n      }\n      else if(RHS < Xupper + epsvalue)\n        rowbindsvar |= AUTOMATIC;\n    }\n  }\n\n  *lobound = Xlower;\n  *upbound = Xupper;\n  if(rowbinds != NULL)\n    *rowbinds = rowbindsvar;\n\n  return(status);\n}\n\nSTATIC MYBOOL isnz_origobj(lprec *lp, int colnr)\n{\n  return( (MYBOOL) (lp->orig_obj[colnr] != 0) );\n}\n\nSTATIC MYBOOL presolve_testrow(presolverec *psdata, int lastrow)\n{\n  if(psdata->forceupdate) {\n    presolve_updatesums(psdata);\n    psdata->forceupdate = FALSE;\n  }\n  if(!presolve_rowfeasible(psdata, 0, TRUE))\n    return( FALSE );\n  else\n    return( TRUE );\n}\n\nSTATIC MYBOOL presolve_coltighten(presolverec *psdata, int colnr, REAL LOnew, REAL UPnew, int *count)\n{\n  lprec    *lp = psdata->lp;\n  int      elmnr, elmend, k, oldcount = 0, newcount = 0, deltainf;\n  REAL     LOold, UPold, Value, margin = psdata->epsvalue;\n  MATrec   *mat = lp->matA;\n  REAL     *value;\n  int      *rownr;\n\n  /* Attempt correction of marginally equal, but inconsistent input values */\n  Value = UPnew - LOnew;\n  if((Value <= -margin) && (Value > -lp->epsprimal)) {\n    if(fabs(fmod(UPnew, 1.0)) < margin)\n      LOnew = UPnew;\n    else\n      UPnew = LOnew;\n  }\n\n  /* Check if there is anything to do */\n  LOold = get_lowbo(lp, colnr);\n  UPold = get_upbo(lp, colnr);\n#ifdef Paranoia\n  if(((LOold > LOnew) && !is_semicont(lp, colnr)) || (UPold < UPnew)) {\n    report(lp, SEVERE, \"presolve_coltighten: Inconsistent new bounds requested for column %d\\n\", colnr);\n    return( FALSE );\n  }\n#endif\n  if(count != NULL)\n    newcount = *count;\n  oldcount = newcount;\n\n  /* Modify inf-count */\n  deltainf = 0;\n  if((UPold < lp->infinite) || (LOold > -lp->infinite))\n    deltainf -= 1;\n  if((UPnew < lp->infinite) || (LOnew > -lp->infinite))\n    deltainf += 1;\n  if(isnz_origobj(lp, colnr))\n    psdata->rows->infcount[0] += deltainf;\n  elmnr = mat->col_end[colnr-1];\n  elmend = mat->col_end[colnr];\n  rownr = &COL_MAT_ROWNR(elmnr);\n  for(; elmnr < elmend; elmnr++, rownr += matRowColStep) {\n    k = *rownr;\n    if(isActiveLink(psdata->rows->varmap, k))\n      psdata->rows->infcount[k] += deltainf;\n  }\n\n  /* Look for opportunity to tighten upper variable bound */\n  if((UPnew < lp->infinite) && (UPnew+margin < UPold)) {\n    if(is_int(lp, colnr))\n      UPnew = floor(UPnew+margin);\n    if(UPold < lp->infinite) {\n      /* First do OF */\n      k = 0;\n      Value = my_chsign(is_chsign(lp, k), lp->orig_obj[colnr]);\n      if((Value > 0) && (psdata->rows->pluupper[k] < lp->infinite))\n        psdata->rows->pluupper[k] += (UPnew-UPold)*Value;\n      else if((Value < 0) && (psdata->rows->negupper[k] < lp->infinite))\n        psdata->rows->negupper[k] += (LOnew-LOold)*Value;\n      psdata->rows->infcount[k] += deltainf;\n\n      /* Then scan the constraint rows */\n      elmnr = mat->col_end[colnr-1];\n      elmend = mat->col_end[colnr];\n      rownr = &COL_MAT_ROWNR(elmnr);\n      value = &COL_MAT_VALUE(elmnr);\n      for(; elmnr < elmend;\n          elmnr++, rownr += matRowColStep, value += matValueStep) {\n        k = *rownr;\n        if(!isActiveLink(psdata->rows->varmap, k))\n          continue;\n        Value = my_chsign(is_chsign(lp, k), *value);\n        if((Value > 0) && (psdata->rows->pluupper[k] < lp->infinite))\n          psdata->rows->pluupper[k] += (UPnew-UPold)*Value;\n        else if((Value < 0) && (psdata->rows->negupper[k] < lp->infinite))\n          psdata->rows->negupper[k] += (LOnew-LOold)*Value;\n      }\n    }\n    else\n      psdata->forceupdate = TRUE;\n    if(UPnew < UPold) {\n      UPold = UPnew;\n      newcount++;\n    }\n  }\n\n  /* Look for opportunity to tighten lower variable bound */\n  if((LOnew > -lp->infinite) && (LOnew-margin > LOold)) {\n    if(is_int(lp, colnr))\n       LOnew = ceil(LOnew-margin);\n    if(LOold > -lp->infinite) {\n      /* First do OF */\n      k = 0;\n      Value = my_chsign(is_chsign(lp, k), lp->orig_obj[colnr]);\n      if((Value > 0) && (psdata->rows->plulower[k] > -lp->infinite))\n        psdata->rows->plulower[k] += (LOnew-LOold)*Value;\n      else if((Value < 0) && (psdata->rows->neglower[k] > -lp->infinite))\n        psdata->rows->neglower[k] += (UPnew-UPold)*Value;\n\n      /* Then scan the constraint rows */\n      elmnr = mat->col_end[colnr-1];\n      elmend = mat->col_end[colnr];\n      rownr = &COL_MAT_ROWNR(elmnr);\n      value = &COL_MAT_VALUE(elmnr);\n      for(; elmnr < elmend;\n          elmnr++, rownr += matRowColStep, value += matValueStep) {\n        k = *rownr;\n        if(!isActiveLink(psdata->rows->varmap, k))\n          continue;\n        Value = my_chsign(is_chsign(lp, k), *value);\n        if((Value > 0) && (psdata->rows->plulower[k] > -lp->infinite))\n          psdata->rows->plulower[k] += (LOnew-LOold)*Value;\n        else if((Value < 0) && (psdata->rows->neglower[k] > -lp->infinite))\n          psdata->rows->neglower[k] += (UPnew-UPold)*Value;\n      }\n    }\n    else\n      psdata->forceupdate = TRUE;\n    if(LOnew > LOold) {\n      LOold = LOnew;\n      newcount++;\n    }\n  }\n\n  /* Now set the new variable bounds, if they are tighter */\n  if(newcount > oldcount) {\n    UPnew = presolve_roundval(lp, UPnew);\n    LOnew = presolve_roundval(lp, LOnew);\n    if(LOnew > UPnew) {\n      if(LOnew-UPnew < margin) {\n        LOnew = UPnew;\n      }\n      else {\n        report(lp, NORMAL, \"presolve_coltighten: Found column %s with LB %g > UB %g\\n\",\n                            get_col_name(lp, colnr), LOnew, UPnew);\n        return( FALSE );\n      }\n    }\n    if(lp->spx_trace || (lp->verbose > DETAILED))\n      report(lp, NORMAL, \"presolve_coltighten: Replaced bounds on column %s to [%g ... %g]\\n\",\n                         get_col_name(lp, colnr), LOnew, UPnew);\n    set_bounds(lp, colnr, LOnew, UPnew);\n  }\n  if(count != NULL)\n    *count = newcount;\n\n  return( TRUE );\n}\n\nSTATIC int presolve_rowtighten(presolverec *psdata, int rownr, int *tally, MYBOOL intsonly)\n{\n  lprec  *lp = psdata->lp;\n  MYBOOL rowbinds;\n  int    item = 0, jx, jjx, ix, idxn = 0, *idxbound = NULL, status = RUNNING;\n  REAL   *newbound = NULL, RHlo = get_rh_lower(lp, rownr), RHup = get_rh_upper(lp, rownr),\n         VARlo, VARup, Aval;\n  MATrec *mat = lp->matA;\n\n  jx = presolve_rowlength(psdata, rownr);\n  allocREAL(lp, &newbound, 2*jx, TRUE);\n  allocINT (lp, &idxbound, 2*jx, TRUE);\n\n  /* Identify bound tightening for each active variable in the constraint */\n  for(jx = presolve_nextcol(psdata, rownr, &item); jx >= 0;\n      jx = presolve_nextcol(psdata, rownr, &item)) {\n    jjx = ROW_MAT_COLNR(jx);\n    Aval = ROW_MAT_VALUE(jx);\n    Aval = my_chsign(rownr, Aval);\n\n    VARlo = RHlo;\n    VARup = RHup;\n    presolve_multibounds(psdata, rownr,jjx, &VARlo, &VARup, &Aval, &rowbinds);\n    if(rowbinds & TRUE) {\n      idxbound[idxn] = -jjx;\n      newbound[idxn] = VARlo;\n      idxn++;\n    }\n    if(rowbinds & AUTOMATIC) {\n      idxbound[idxn] = jjx;\n      newbound[idxn] = VARup;\n      idxn++;\n    }\n  }\n\n  /* Loop over the bounds identified for tightening and perform update */\n  ix = 0;\n  while(ix < idxn) {\n    jjx = idxbound[ix];\n    jx = abs(jjx);\n\n    /* Skip free variables and non-ints, if specified */\n    if(is_unbounded(lp, jx) ||\n       (intsonly && !is_int(lp, jx)))\n      continue;\n\n    VARlo = get_lowbo(lp, jx);\n    VARup = get_upbo(lp, jx);\n    /* while((ix < idxn) && (jx == abs(jjx))) { */\n    while((ix < idxn) && (jx == abs((jjx = idxbound[ix])))) {\n      if(jjx < 0)\n        VARlo = newbound[ix];\n      else\n        VARup = newbound[ix];\n      ix++;\n    }\n    if(!presolve_coltighten(psdata, jx, VARlo, VARup, tally)) {\n      status = presolve_setstatus(psdata, INFEASIBLE);\n      break;\n    }\n  }\n\n  FREE(newbound);\n  FREE(idxbound);\n\n  return(status);\n}\n\nSTATIC void set_dv_bounds(presolverec *psdata, int rownr, REAL lowbo, REAL upbo)\n{\n  psdata->dv_lobo[rownr] = lowbo;\n  psdata->dv_upbo[rownr] = upbo;\n}\nSTATIC REAL get_dv_lower(presolverec *psdata, int rownr)\n{\n  return( psdata->dv_lobo[rownr] );\n}\n\nSTATIC REAL get_dv_upper(presolverec *psdata, int rownr)\n{\n  return( psdata->dv_upbo[rownr] );\n}\n\nSTATIC MYBOOL presolve_rowfix(presolverec *psdata, int rownr, REAL newvalue, MYBOOL remove, int *tally)\n{\n  lprec    *lp = psdata->lp;\n  int      i, ix, ie;\n  MYBOOL   isneg, lofinite, upfinite, doupdate = FALSE, chsign = is_chsign(lp, rownr);\n  REAL     lobound, upbound, lovalue, upvalue,\n           Value, fixvalue, fixprod, mult;\n  MATrec   *mat = lp->matA;\n  psrec    *ps = psdata->cols;\n\n  /* Set \"fixed\" value in case we are deleting a variable */\n  upbound = get_dv_upper(psdata, rownr);\n  lobound = get_dv_lower(psdata, rownr);\n  if(remove) {\n    if(upbound-lobound < psdata->epsvalue) {\n      if((newvalue > lobound) && (newvalue < upbound))\n        fixvalue = newvalue;\n      else\n        fixvalue = lobound;\n    }\n    else {\n      if(my_infinite(lp, newvalue) && (get_rh(lp, rownr) == 0))\n        fixvalue = ((lobound <= 0) && (upbound >= 0) ? 0 : MIN(upbound, lobound));\n      else\n        fixvalue = newvalue;\n    }\n    set_dv_bounds(psdata, rownr, fixvalue, fixvalue);\n    if(fixvalue != 0)\n      addUndoPresolve(lp, FALSE, rownr, fixvalue, 0, 0);\n    mult = -1;\n  }\n  else {\n    mult = 1;\n    fixvalue = 0;\n  }\n\n  /* Loop over rows to update statistics */\n  ix = mat->row_end[rownr - 1];\n  ie = mat->row_end[rownr];\n  for(; ix < ie; ix++) {\n\n   /* Retrieve row data and adjust RHS if we are deleting a variable */\n    i     = ROW_MAT_COLNR(ix);\n    Value = ROW_MAT_VALUE(ix);\n    if(Value == 0)\n      continue;\n\n    if(remove && (fixvalue != 0)) {\n      fixprod = Value*fixvalue;\n      lp->orig_obj[i] -= fixprod;\n      my_roundzero(lp->orig_obj[i], psdata->epsvalue);\n      lp->presolve_undo->fixed_obj[i] += fixprod;\n    }\n\n   /* Prepare for further processing */\n    Value = my_chsign(chsign, Value);\n    isneg = (MYBOOL) (Value < 0);\n\n   /* Reduce row variable counts if we are removing the variable */\n    if(!isActiveLink(ps->varmap, i))\n      continue;\n    if(remove) {\n      if(isneg) {\n        ps->negcount[i]--;\n      }\n      else {\n        ps->plucount[i]--;\n      }\n      if((lobound < 0) && (upbound >= 0)) {\n        ps->pluneg[i]--;\n      }\n    }\n\n   /* Compute associated constraint contribution values */\n    upfinite = (MYBOOL) (upbound < lp->infinite);\n    lofinite = (MYBOOL) (lobound > -lp->infinite);\n    if(upfinite || lofinite) {\n      if(remove)\n        ps->infcount[i]--;\n      else\n        ps->infcount[i]++;\n    }\n    upvalue = my_if(upfinite, Value*upbound, my_chsign(isneg, lp->infinite));\n    lovalue = my_if(lofinite, Value*lobound, my_chsign(isneg, -lp->infinite));\n\n   /* Cumulate effective upper column bound (only bother with non-finite bound) */\n    if(isneg) {\n      if((ps->negupper[i] < lp->infinite) && lofinite) {\n        ps->negupper[i] += mult*lovalue;\n        ps->negupper[i] = presolve_roundrhs(lp, ps->negupper[i], FALSE);\n      }\n      else if(remove && !lofinite)\n        doupdate = TRUE;\n      else\n        ps->negupper[i] = lp->infinite;\n    }\n    else {\n      if((ps->pluupper[i] < lp->infinite) && upfinite) {\n        ps->pluupper[i] += mult*upvalue;\n        ps->pluupper[i] = presolve_roundrhs(lp, ps->pluupper[i], FALSE);\n      }\n      else if(remove && !upfinite)\n        doupdate = TRUE;\n      else\n        ps->pluupper[i] = lp->infinite;\n    }\n\n   /* Cumulate effective lower column bound (only bother with non-finite bound) */\n    if(isneg) {\n      if((ps->neglower[i] > -lp->infinite) && upfinite) {\n        ps->neglower[i] += mult*upvalue;\n        ps->neglower[i] = presolve_roundrhs(lp, ps->neglower[i], TRUE);\n      }\n      else if(remove && !upfinite)\n        doupdate = TRUE;\n      else\n        ps->neglower[i] = -lp->infinite;\n    }\n    else {\n      if((ps->plulower[i] > -lp->infinite) && lofinite) {\n        ps->plulower[i] += mult*lovalue;\n        ps->plulower[i] = presolve_roundrhs(lp, ps->plulower[i], TRUE);\n      }\n      else if(remove && !lofinite)\n        doupdate = TRUE;\n      else\n        ps->plulower[i] = -lp->infinite;\n    }\n\n   /* Validate consistency of eliminated singleton */\n    if(remove && ((i == 0) || (ps->next[i][0] == 1)) && !psdata->forceupdate) {\n      presolve_range(lp, i, ps, &lovalue, &upvalue);\n      Value = get_mat(lp, 0, i);\n      if((upvalue < Value) ||\n         (lovalue > Value)) {\n        report(lp, IMPORTANT, \"presolve: Row %s (%g << %g) infeasibility in column %s (OF=%g)\\n\",\n                              get_row_name(lp, rownr), lovalue, upvalue, get_col_name(lp, i), Value);\n        return( FALSE );\n      }\n    }\n  }\n  if(remove) {\n    psdata->forceupdate |= doupdate;\n    if(tally != NULL)\n      (*tally)++;\n  }\n  return( TRUE );\n}\n\n\nSTATIC int presolve_colsingleton(presolverec *psdata, int i, int j, int *count)\n{\n  lprec    *lp = psdata->lp;\n  REAL     RHlow, RHup, LObound, UPbound, Value;\n\n#ifdef Paranoia\n  if(!isActiveLink(psdata->cols->varmap, j))\n    report(lp, SEVERE, \"presolve_colsingleton: Nothing to do, column %d was eliminated earlier\\n\",\n                       j);\n#endif\n\n  Value = get_mat(lp,i,j);\n  if(Value == 0)\n    return( RUNNING );\n\n  /* Initialize and identify semicontinuous variable */\n  LObound = get_lowbo(lp, j);\n  UPbound = get_upbo(lp, j);\n  if(is_semicont(lp, j) && (UPbound > LObound)) {\n    if(LObound > 0)\n      LObound = 0;\n    else if(UPbound < 0)\n      UPbound = 0;\n  }\n\n  /* Get singleton variable bounds */\n  RHlow = get_rh_lower(lp, i);\n  RHup  = get_rh_upper(lp, i);\n  if(!presolve_singletonbounds(psdata, i,j, &RHlow, &RHup, &Value))\n    return( presolve_setstatus(psdata, INFEASIBLE) );\n\n  if(presolve_coltighten(psdata, j, RHlow, RHup, count))\n    return( RUNNING );\n  else\n    return( presolve_setstatus(psdata, INFEASIBLE) );\n}\n\nSTATIC MYBOOL presolve_colfix(presolverec *psdata, int colnr, REAL newvalue, MYBOOL remove, int *tally)\n{\n  lprec    *lp = psdata->lp;\n  int      i, ix, ie;\n  MYBOOL   isneg, lofinite, upfinite, doupdate = FALSE, doOF = TRUE;\n  REAL     lobound, upbound, lovalue, upvalue,\n           Value, fixvalue, mult;\n  MATrec   *mat = lp->matA;\n  psrec    *ps = psdata->rows;\n  REAL     *value;\n  int      *rownr;\n\n  /* Set \"fixed\" value in case we are deleting a variable */\n  upbound = get_upbo(lp, colnr);\n  lobound = get_lowbo(lp, colnr);\n  if(remove) {\n    if(upbound-lobound < psdata->epsvalue) {\n      if((newvalue > lobound) && (newvalue < upbound))\n        fixvalue = newvalue;\n      else\n        fixvalue = lobound;\n    }\n    else {\n      if(my_infinite(lp, newvalue) && (get_mat(lp, 0, colnr) == 0))\n        fixvalue = ((lobound <= 0) && (upbound >= 0) ? 0 : MIN(upbound, lobound));\n      else\n        fixvalue = newvalue;\n    }\n#if 1 /* Fast normal version */\n    set_bounds(lp, colnr, fixvalue, fixvalue);\n#else /* Slower version that can be used for debugging/control purposes */\n    presolve_coltighten(psdata, colnr, fixvalue, fixvalue, NULL);\n    lobound = fixvalue;\n    upbound = fixvalue;\n#endif\n    if(fixvalue != 0)\n      addUndoPresolve(lp, TRUE, colnr, fixvalue, 0, 0);\n    mult = -1;\n  }\n  else {\n    mult = 1;\n    fixvalue = 0;\n  }\n\n  /* Adjust semi-continuous variable bounds to zero-base */\n  if(is_semicont(lp, colnr) && (upbound > lobound)) {\n    if(lobound > 0)\n      lobound = 0;\n    else if(upbound < 0)\n      upbound = 0;\n  }\n\n  /* Loop over rows to update statistics */\n  ix = mat->col_end[colnr - 1];\n  ie = mat->col_end[colnr];\n  rownr = &COL_MAT_ROWNR(ix);\n  value = &COL_MAT_VALUE(ix);\n  for(; doOF || (ix < ie);\n      ix++, rownr += matRowColStep, value += matValueStep) {\n\n   /* Retrieve row data and adjust RHS if we are deleting a variable */\nRestart:\n    if(doOF) {\n      i = 0;\n      Value = lp->orig_obj[colnr];\n    }\n    else {\n      i = *rownr;\n      Value = *value;\n      if(!isActiveLink(ps->varmap, i))\n        continue;\n    }\n    if(Value == 0)\n      goto BlockEnd;\n\n    if(remove && (fixvalue != 0))\n      presolve_adjustrhs(psdata, i, Value*fixvalue, psdata->epsvalue);\n\n   /* Prepare for further processing */\n    Value = my_chsign(is_chsign(lp, i), Value);\n    isneg = (MYBOOL) (Value < 0);\n\n   /* Reduce row variable counts if we are removing the variable */\n    if(remove == TRUE) {\n      if(isneg) {\n        ps->negcount[i]--;\n      }\n      else {\n        ps->plucount[i]--;\n      }\n      if((lobound < 0) && (upbound >= 0)) {\n        ps->pluneg[i]--;\n      }\n    }\n\n   /* Compute associated constraint contribution values */\n    upfinite = (MYBOOL) (upbound < lp->infinite);\n    lofinite = (MYBOOL) (lobound > -lp->infinite);\n    if(upfinite || lofinite) {\n      if(remove)\n        ps->infcount[i]--;\n      else\n        ps->infcount[i]++;\n    }\n    upvalue = my_if(upfinite, Value*upbound, my_chsign(isneg, lp->infinite));\n    lovalue = my_if(lofinite, Value*lobound, my_chsign(isneg, -lp->infinite));\n\n   /* Cumulate effective upper row bound (only bother with non-finite bound) */\n    if(isneg) {\n      if((ps->negupper[i] < lp->infinite) && lofinite) {\n        ps->negupper[i] += mult*lovalue;\n        ps->negupper[i] = presolve_roundrhs(lp, ps->negupper[i], FALSE);\n      }\n      else if(remove && !lofinite)\n        doupdate = TRUE;\n      else\n        ps->negupper[i] = lp->infinite;\n    }\n    else {\n      if((ps->pluupper[i] < lp->infinite) && upfinite) {\n        ps->pluupper[i] += mult*upvalue;\n        ps->pluupper[i] = presolve_roundrhs(lp, ps->pluupper[i], FALSE);\n      }\n      else if(remove && !upfinite)\n        doupdate = TRUE;\n      else\n        ps->pluupper[i] = lp->infinite;\n    }\n\n   /* Cumulate effective lower row bound (only bother with non-finite bound) */\n    if(isneg) {\n      if((ps->neglower[i] > -lp->infinite) && upfinite) {\n        ps->neglower[i] += mult*upvalue;\n        ps->neglower[i] = presolve_roundrhs(lp, ps->neglower[i], TRUE);\n      }\n      else if(remove && !upfinite)\n        doupdate = TRUE;\n      else\n        ps->neglower[i] = -lp->infinite;\n    }\n    else {\n      if((ps->plulower[i] > -lp->infinite) && lofinite) {\n        ps->plulower[i] += mult*lovalue;\n        ps->plulower[i] = presolve_roundrhs(lp, ps->plulower[i], TRUE);\n      }\n      else if(remove && !lofinite)\n        doupdate = TRUE;\n      else\n        ps->plulower[i] = -lp->infinite;\n    }\n\n   /* Validate consistency of eliminated singleton */\n    if(remove && ((i == 0) || (ps->next[i][0] == 1)) && !psdata->forceupdate) {\n      if(i == 0) {\n        lovalue = get_rh_lower(lp, i);\n        upvalue = get_rh_upper(lp, i);\n        report(lp, DETAILED, \"presolve_colfix: Objective determined by presolve as %18g\\n\",\n                             (is_maxim(lp) ? upvalue : lovalue));\n      }\n      else {\n        presolve_range(lp, i, ps, &lovalue, &upvalue);\n#if 1\n        Value = 0;\n#else\n        Value = MAX(fabs(upvalue), fabs(lovalue));\n        Value = psdata->epsvalue * MAX(1, Value);\n#endif\n        if((upvalue < get_rh_lower(lp, i)-Value) ||\n           (lovalue > get_rh_upper(lp, i)+Value)) {\n          report(lp, NORMAL, \"presolve_colfix: Variable %s (%g << %g) infeasibility in row %s (%g << %g)\\n\",\n                              get_col_name(lp, colnr), lovalue, upvalue,\n                              get_row_name(lp, i), get_rh_lower(lp,i), get_rh_upper(lp, i));\n          return( FALSE );\n        }\n      }\n    }\nBlockEnd:\n    if(doOF) {\n      doOF = FALSE;\n      if(ix < ie)\n        goto Restart;\n    }\n\n  }\n  if(remove) {\n    psdata->forceupdate |= doupdate;\n    if(tally != NULL)\n      (*tally)++;\n  }\n  return( TRUE );\n}\n\n/* Delete the columns of the specified row, but make sure we don't delete SOS variables.\n   Note that we cannot use presolve_nextcol() here, since the variables are deleted. */\nSTATIC int presolve_rowfixzero(presolverec *psdata, int rownr, int *nv)\n{\n  lprec  *lp = psdata->lp;\n  MATrec *mat = lp->matA;\n  int    ix, jx, ib = mat->row_end[rownr-1];\n  for(ix = mat->row_end[rownr]-1; ix >= ib; ix--) {\n    jx = ROW_MAT_COLNR(ix);\n    if(isActiveLink(psdata->cols->varmap, jx)) {\n      if(!presolve_colfix(psdata, jx, 0.0, TRUE, nv))\n        return( presolve_setstatus(psdata, INFEASIBLE) );\n      if(presolve_candeletevar(psdata, jx))\n        presolve_colremove(psdata, jx, TRUE);\n    }\n  }\n#ifdef xxParanoia\n  if(!presolve_debugrowtallies(psdata))\n    return( INFEASIBLE );\n#endif\n  return( RUNNING );\n}\n\n/* Function to find if a variable can be fixed based on considering the dual */\nSTATIC MYBOOL presolve_colfixdual(presolverec *psdata, int colnr, REAL *fixValue, int *status)\n{\n  lprec   *lp = psdata->lp;\n  MYBOOL  hasOF, isMI, isDualFREE = TRUE;\n  int     i, ix, ie, *rownr, signOF;\n  REAL    *value, loX, upX, eps = psdata->epsvalue;\n  MATrec  *mat = lp->matA;\n\n  /* First check basic variable range */\n  loX = get_lowbo(lp, colnr);\n  upX = get_upbo(lp, colnr);\n  if(((loX < 0) && (upX > 0)) ||\n     (fabs(upX-loX) < lp->epsvalue) ||\n     SOS_is_member_of_type(lp->SOS, colnr, SOSn))\n    return( FALSE );\n  isMI = (MYBOOL) (upX <= 0);\n\n  /* Retrieve OF (standard form assuming maximization) */\n  ix = mat->col_end[colnr - 1];\n  ie = mat->col_end[colnr];\n  rownr = &COL_MAT_ROWNR(ix);\n  value = &COL_MAT_VALUE(ix);\n  hasOF = isnz_origobj(lp, colnr);\n  if(hasOF)\n    signOF = my_sign(lp->orig_obj[colnr]);\n  else\n    signOF = 0;\n\n  /* Loop over all constraints involving active variable (standard form with LE constraints)*/\n  for(; (ix < ie) && isDualFREE;\n      ix++, rownr += matRowColStep, value += matValueStep) {\n    i = *rownr;\n    if(!isActiveLink(psdata->rows->varmap, i))\n      continue;\n    if(presolve_rowlength(psdata, i) == 1) {\n      REAL val = my_chsign(is_chsign(lp, i), *value),\n           loR = get_rh_lower(lp, i),\n           upR = get_rh_upper(lp, i);\n      if(!presolve_singletonbounds(psdata, i, colnr, &loR, &upR, &val)) {\n        *status = presolve_setstatus(psdata, INFEASIBLE);\n        return( FALSE );\n      }\n      if(loR > loX + psdata->epsvalue)\n        loX = presolve_roundrhs(lp, loR, TRUE);\n      if(upR < upX - psdata->epsvalue)\n        upX = presolve_roundrhs(lp, upR, FALSE);\n      continue;\n    }\n    else\n      isDualFREE = my_infinite(lp, get_rh_range(lp, i)) ||                                          /* Explicitly free */\n                   ((presolve_sumplumin(lp, i, psdata->rows, TRUE)-eps <= get_rh_upper(lp, i)) &&   /* Implicitly free */\n                    (presolve_sumplumin(lp, i, psdata->rows, FALSE)+eps >= get_rh_lower(lp, i)));\n    if(isDualFREE) {\n      if(signOF == 0)  /* Test on the basis of identical signs in the constraints */\n        signOF = my_sign(*value);\n      else             /* Test on the basis of constraint sign equal to OF sign */\n        isDualFREE = (MYBOOL) (signOF == my_sign(*value));\n    }\n  }\n\n  /* Set fixing value if we were successful */\n  if(isDualFREE) {\n    if(signOF == 0) {\n      SETMAX(loX, 0);\n      *fixValue = MIN(loX, upX);\n    }\n    else if(signOF > 0) {\n      if(my_infinite(lp, loX))\n        isDualFREE = FALSE;\n      else {\n        if(is_int(lp, colnr))\n          *fixValue = ceil(loX-PRESOLVE_EPSVALUE);\n        else\n          *fixValue = loX;\n      }\n    }\n    else {\n      if(my_infinite(lp, upX))\n        isDualFREE = FALSE;\n      else {\n        if(is_int(lp, colnr) && (upX != 0))\n          *fixValue = floor(upX+PRESOLVE_EPSVALUE);\n        else\n          *fixValue = upX;\n      }\n    }\n    if((*fixValue != 0) && SOS_is_member(lp->SOS, 0, colnr))\n      return( FALSE );\n\n  }\n\n  return( isDualFREE );\n}\n\n#if 0\nSTATIC MYBOOL presolve_probefix01(presolverec *psdata, int colnr, REAL *fixvalue)\n{\n  lprec    *lp = psdata->lp;\n  int      i, ix, item;\n  REAL     loLim, absvalue, epsvalue = psdata->epsvalue;\n  MATrec   *mat = lp->matA;\n  MYBOOL   chsign, canfix = FALSE;\n\n  if(!is_binary(lp, colnr))\n    return( canfix );\n\n  /* Loop over all active rows to search for fixing opportunity */\n  item = 0;\n  for(ix = presolve_nextrow(psdata, colnr, &item);\n      (ix >= 0) && !canfix;\n      ix = presolve_nextrow(psdata, colnr, &item)) {\n    i = COL_MAT_ROWNR(ix);\n    *fixvalue = COL_MAT_VALUE(ix);\n    chsign = is_chsign(lp, i);\n\n    /* First check the lower bound of the normalized constraint */\n    loLim = presolve_sumplumin(lp, i, psdata->rows, chsign);\n    loLim = my_chsign(chsign, loLim);\n    absvalue = fabs(*fixvalue);\n    canfix = (MYBOOL) ((loLim + absvalue > lp->orig_rhs[i]+epsvalue*MAX(1, absvalue)));\n\n    /* If we were unsuccessful in fixing above, try the upper bound\n       of the normalized constraint - if it is finite */\n    if(!canfix && !my_infinite(lp, get_rh_range(lp, i))) {\n      loLim = presolve_sumplumin(lp, i, psdata->rows, (MYBOOL) !chsign);\n      loLim = my_chsign(!chsign, loLim);\n      *fixvalue = -(*fixvalue);\n      canfix = (MYBOOL) ((loLim + absvalue > get_rh_range(lp, i)-lp->orig_rhs[i]+epsvalue*MAX(1, absvalue)));\n    }\n  }\n\n  /* Check if we were successful in identifying fixing opportunity */\n  if(canfix) {\n    if(*fixvalue < 0)\n      *fixvalue = 1;\n    else\n      *fixvalue = 0;\n  }\n  return( canfix );\n}\n#else\nSTATIC MYBOOL presolve_probefix01(presolverec *psdata, int colnr, REAL *fixvalue)\n{\n  lprec    *lp = psdata->lp;\n  int      i, ix, item;\n  REAL     loLim, upLim, range, absvalue, epsvalue = psdata->epsvalue, tolgap;\n  MATrec   *mat = lp->matA;\n  MYBOOL   chsign, status = FALSE;\n\n  if(!is_binary(lp, colnr))\n    return( status );\n\n  /* Loop over all active rows to search for fixing opportunity.  The logic is that if a\n     constraint gets violated by setting a variable at one of its bounds, then it can be\n     fixed at its opposite bound. */\n  item = 0;\n\n  for(ix = presolve_nextrow(psdata, colnr, &item); (ix >= 0); ix = presolve_nextrow(psdata, colnr, &item)) {\n    i = COL_MAT_ROWNR(ix);\n    *fixvalue = COL_MAT_VALUE(ix);\n    absvalue = fabs(*fixvalue);\n    SETMIN(absvalue, 100);\n    tolgap = epsvalue*MAX(1, absvalue);\n    chsign = is_chsign(lp, i);\n\n    /* Get the constraint value limits based on variable bounds, normalized to LE constraint */\n    loLim = presolve_sumplumin(lp, i, psdata->rows, FALSE);\n    upLim = presolve_sumplumin(lp, i, psdata->rows, TRUE);\n    if(chsign) {\n      loLim = my_chsign(chsign, loLim);\n      upLim = my_chsign(chsign, upLim);\n      swapREAL(&loLim, &upLim);\n    }\n\n    /* Check the upper constraint bound for possible violation if the value were to be fixed at 1 */\n    if(loLim + *fixvalue > lp->orig_rhs[i]+tolgap) {\n      if(*fixvalue < 0)\n        presolve_setstatus(psdata, INFEASIBLE);\n      *fixvalue = 0;\n      break;\n    }\n\n    /* Check the lower constraint bound for possible violation if the value were to be fixed at 1 */\n    range = get_rh_range(lp, i);\n    if(!my_infinite(lp, range) &&\n       (upLim + *fixvalue < lp->orig_rhs[i]-range-tolgap)) {\n      if(*fixvalue > 0)\n        presolve_setstatus(psdata, INFEASIBLE);\n      *fixvalue = 0;\n      break;\n    }\n\n    /* Check if we have to fix the value at 1 to avoid constraint infeasibility */\n    if(psdata->rows->infcount[i] >= 1)\n      continue;\n    if(((*fixvalue < 0) && (upLim + *fixvalue >= loLim-tolgap) && (upLim > lp->orig_rhs[i]+tolgap)) ||\n       ((*fixvalue > 0) && (loLim + *fixvalue <= upLim+tolgap) && (loLim < lp->orig_rhs[i]-range-tolgap) && !my_infinite(lp, range))) {\n      *fixvalue = 1;\n      break;\n    }\n  }\n  status = (MYBOOL) (ix >= 0);\n\n  /* Returns TRUE if fixing opportunity was identified */\n  return( status );\n}\n#endif\n\nSTATIC int presolve_probetighten01(presolverec *psdata, int colnr)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   chsign;\n  int      i, ix, item, n = 0;\n  REAL     upLim, value, absvalue, epsvalue = psdata->epsvalue;\n  MATrec   *mat = lp->matA;\n\n#if 0 /* Handled in calling routine */\n  if(!is_binary(lp, colnr))\n    return( n );\n#endif\n\n  /* Loop over all active rows and do coefficient tightening for qualifying constraints */\n  item = 0;\n  for(ix = presolve_nextrow(psdata, colnr, &item); ix >= 0;\n      ix = presolve_nextrow(psdata, colnr, &item)) {\n    i = COL_MAT_ROWNR(ix);\n    value = COL_MAT_VALUE(ix);\n    chsign = is_chsign(lp, i);\n    upLim = presolve_sumplumin(lp, i, psdata->rows, (MYBOOL) !chsign);\n    upLim = my_chsign(chsign, upLim);\n\n    /* Does this constraint qualify for coefficient tightening? */\n    absvalue = fabs(value);\n    if(upLim - absvalue < lp->orig_rhs[i]-epsvalue*MAX(1, absvalue)) {\n      REAL delta = lp->orig_rhs[i] - upLim;\n      lp->orig_rhs[i] = upLim;\n      upLim = value - my_chsign(value < 0, delta);\n      COL_MAT_VALUE(ix) = upLim;\n      if(my_sign(value) != my_sign(upLim)) {\n        if(chsign) {\n          psdata->rows->negcount[i]--;\n          psdata->rows->plucount[i]++;\n        }\n        else {\n          psdata->rows->negcount[i]++;\n          psdata->rows->plucount[i]--;\n        }\n      }\n      n++;\n    }\n  }\n  return( n );\n}\n\nSTATIC int presolve_mergerows(presolverec *psdata, int *nRows, int *nSum)\n{\n  lprec *lp = psdata->lp;\n  MYBOOL candelete;\n  int    status = RUNNING, item1, item2,\n         firstix, RT1, RT2, i, ix, iix, j, jjx, n = 0;\n  REAL   Value1, Value2, bound;\n  MATrec *mat = lp->matA;\n\n  for(i = lastActiveLink(psdata->rows->varmap); (i > 0) && (status == RUNNING); ) {\n\n    /* First scan for rows with identical row lengths */\n    ix = prevActiveLink(psdata->rows->varmap, i);\n    if(ix == 0)\n      break;\n\n    /* Don't bother about empty rows or row singletons, since they are\n       handled by PRESOLVE_ROWS */\n    j = presolve_rowlength(psdata, i);\n    if(j <= 1) {\n      i = ix;\n      continue;\n    }\n\n#if 0\n    /* Enable this to scan all rows back */\n    RT2 = lp->rows;\n\n    /* Check abort since this section can be pretty \"expensive\" */\n    if(!presolve_statuscheck(psdata, &status))\n      return( status );\n#else\n    RT2 = 2+1;\n#endif\n    firstix = ix;\n    for(RT1 = 0; (ix > 0) && (RT1 < RT2) && (status == RUNNING);\n        ix = prevActiveLink(psdata->rows->varmap, ix), RT1++)  {\n      candelete = FALSE;\n      if(presolve_rowlength(psdata, ix) != j)\n        continue;\n\n      /* Check if the beginning columns are identical; if not, continue */\n      item1 = 0;\n      iix = presolve_nextcol(psdata, ix, &item1);\n      item2 = 0;\n      jjx = presolve_nextcol(psdata, i,  &item2);\n\n      if(ROW_MAT_COLNR(iix) != ROW_MAT_COLNR(jjx))\n        continue;\n\n      /* We have a candidate row; check if the entries have a fixed non-zero ratio */\n      Value1 = get_mat_byindex(lp, iix, TRUE, FALSE);\n      Value2 = get_mat_byindex(lp, jjx, TRUE, FALSE);\n      bound = Value1 / Value2;\n      Value1 = bound;\n\n      /* Loop over remaining entries */\n      jjx = presolve_nextcol(psdata, i, &item2);\n      for(; (jjx >= 0) && (Value1 == bound);\n          jjx = presolve_nextcol(psdata, i, &item2)) {\n        iix = presolve_nextcol(psdata, ix, &item1);\n        if(ROW_MAT_COLNR(iix) != ROW_MAT_COLNR(jjx))\n          break;\n        Value1 = get_mat_byindex(lp, iix, TRUE, FALSE);\n        Value2 = get_mat_byindex(lp, jjx, TRUE, FALSE);\n\n        /* If the ratio is different from the reference value we have a mismatch */\n        Value1 = Value1 / Value2;\n        if(bound == lp->infinite)\n          bound = Value1;\n        else if(fabs(Value1 - bound) > psdata->epsvalue)\n          break;\n      }\n\n      /* Check if we found a match (we traversed all active columns without a break) */\n      if(jjx < 0) {\n\n        /* Get main reference values */\n        Value1 = lp->orig_rhs[ix];\n        Value2 = lp->orig_rhs[i] * bound;\n\n        /* First check for inconsistent equalities */\n        if((fabs(Value1 - Value2) > psdata->epsvalue) &&\n           ((get_constr_type(lp, ix) == EQ) && (get_constr_type(lp, i) == EQ))) {\n          report(lp, NORMAL, \"presolve_mergerows: Inconsistent equalities %d and %d found\\n\",\n                             ix, i);\n          status = presolve_setstatus(psdata, INFEASIBLE);\n        }\n\n        else {\n\n          /* Update lower and upper bounds */\n          if(is_chsign(lp, i) != is_chsign(lp, ix))\n            bound = -bound;\n\n          Value1 = get_rh_lower(lp, i);\n          if(Value1 <= -lp->infinite)\n            Value1 *= my_sign(bound);\n          else\n            Value1 *= bound;\n          my_roundzero(Value1, lp->epsdual);      /* Extra rounding tolerance *** */\n\n          Value2 = get_rh_upper(lp, i);\n          if(Value2 >= lp->infinite)\n            Value2 *= my_sign(bound);\n          else\n            Value2 *= bound;\n          my_roundzero(Value2, lp->epsdual);      /* Extra rounding tolerance *** */\n\n          if((bound < 0))\n            swapREAL(&Value1, &Value2);\n\n          bound = get_rh_lower(lp, ix);\n          if(Value1 > bound + psdata->epsvalue)\n            set_rh_lower(lp, ix, Value1);\n          else\n            Value1 = bound;\n          bound = get_rh_upper(lp, ix);\n          if(Value2 < bound - psdata->epsvalue)\n            set_rh_upper(lp, ix, Value2);\n          else\n            Value2 = bound;\n\n          /* Check results and make equality if appropriate */\n          if(fabs(Value2-Value1) < psdata->epsvalue)\n            presolve_setEQ(psdata, ix);\n          else if(Value2 < Value1) {\n            status = presolve_setstatus(psdata, INFEASIBLE);\n          }\n\n          /* Verify if we can continue */\n          candelete = (MYBOOL) (status == RUNNING);\n          if(!candelete) {\n            report(lp, NORMAL, \"presolve: Range infeasibility found involving rows %s and %s\\n\",\n                                get_row_name(lp, ix), get_row_name(lp, i));\n          }\n        }\n      }\n      /* Perform i-row deletion if authorized */\n      if(candelete) {\n        presolve_rowremove(psdata, i, TRUE);\n        n++;\n        break;\n      }\n    }\n    i = firstix;\n  }\n  (*nRows) += n;\n  (*nSum)  += n;\n\n  return( status );\n}\n\nSTATIC MYBOOL presolve_reduceGCD(presolverec *psdata, int *nn, int *nb, int *nsum)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   status = TRUE;\n  int      i, jx, je, in = 0, ib = 0;\n  LLONG    GCDvalue;\n  REAL     *Avalue, Rvalue, epsvalue = psdata->epsvalue;\n  MATrec   *mat = lp->matA;\n\n  for(i = firstActiveLink(psdata->INTmap); i != 0; i = nextActiveLink(psdata->INTmap, i)) {\n\n    /* Obtain the row GCD */\n    jx = mat->row_end[i - 1];\n    je = mat->row_end[i];\n    Rvalue = ROW_MAT_VALUE(jx);\n    GCDvalue = abs((int) Rvalue);\n    jx++;\n    if(jx < je)\n    for(; (jx < je) && (GCDvalue > 1); jx++) {\n      Rvalue = fabs(ROW_MAT_VALUE(jx));\n      GCDvalue = gcd((LLONG) Rvalue, GCDvalue, NULL, NULL);\n    }\n\n    /* Reduce the coefficients, if possible */\n    if(GCDvalue > 1) {\n      jx = mat->row_end[i - 1];\n      je = mat->row_end[i];\n      for(; jx < je; jx++) {\n        Avalue = &ROW_MAT_VALUE(jx);\n        *Avalue /= GCDvalue;\n        in++;\n      }\n      Rvalue = (lp->orig_rhs[i] / GCDvalue) + epsvalue;\n      lp->orig_rhs[i] = floor(Rvalue);\n      Rvalue = fabs(lp->orig_rhs[i]-Rvalue);\n      if(is_constr_type(lp, i, EQ) && (Rvalue > epsvalue)) {\n        report(lp, NORMAL, \"presolve_reduceGCD: Infeasible equality constraint %d\\n\", i);\n        status = FALSE;\n        break;\n      }\n      if(!my_infinite(lp, lp->orig_upbo[i]))\n        lp->orig_upbo[i] = floor(lp->orig_upbo[i] / GCDvalue);\n      ib++;\n    }\n  }\n  if(status && (in > 0))\n    report(lp, DETAILED, \"presolve_reduceGCD: Did %d constraint coefficient reductions.\\n\", in);\n\n  (*nn)   += in;\n  (*nb)   += ib;\n  (*nsum) += in + ib;\n\n  return( status );\n}\n\nSTATIC int presolve_knapsack(presolverec *psdata, int *nn)\n{\n  lprec *lp = psdata->lp;\n  int    m, n, i, ix, j, jx, colnr, *rownr = NULL,\n         status = RUNNING;\n  REAL   *colOF = lp->orig_obj, value, *ratio = NULL;\n  LLrec  *map = psdata->EQmap;\n  MATrec *mat = lp->matA;\n\n  /* Check if it is worth trying */\n  m = mat->row_end[0];\n  if((map->count == 0) || (m < 2))\n    return( status );\n\n  /* Get the OF row */\n  allocINT(lp, &rownr,  map->count+1, FALSE);\n  allocREAL(lp, &ratio, map->count+1, FALSE);\n\n  /* Loop over each row trying to find equal entries in the OF */\n  rownr[0] = 0;\n  for(i = firstActiveLink(map); i != 0; i = nextActiveLink(map, i)) {\n    if(get_rh(lp, i) <= 0)\n      continue;\n    jx = mat->row_end[i];\n    n = 0;\n    for(j = mat->row_end[i-1]; j  < jx; j++, n++) {\n      colnr = ROW_MAT_COLNR(j);\n      value = ROW_MAT_VALUE(j);\n      if(colOF[colnr] == 0)\n        break;\n      if(n == 0) {\n        ratio[0] = colOF[colnr] / value;\n      }\n      else if(fabs(value * ratio[0] - colOF[colnr]) > psdata->epsvalue) {\n        n = -1;\n        break;\n      }\n    }\n    /* Register row if we were successful (and row long enough) */\n    if(n >= 2) {\n      ix = ++rownr[0];\n      rownr[ix] = i;\n      ratio[ix] = ratio[0];\n    }\n  }\n  n = rownr[0];\n  if(n == 0)\n    goto Finish;\n\n  /* Process the identified rows, eliminating the OF value */\n  for(ix = 1; ix <= n; ix++) {\n    i = rownr[ix];\n    jx = mat->row_end[i];\n    for(j = mat->row_end[i-1]; j  < jx; j++) {\n      colnr = ROW_MAT_COLNR(j);\n      colOF[colnr] = 0;\n    }\n  }\n\n  /* Update key mapper structures */\n  j = lp->columns;\n  psdata->cols->varmap = cloneLink(psdata->cols->varmap, j+n, TRUE);\n  psdata->forceupdate = TRUE;\n\n  /* Finally, add helper columns */\n  for(ix = 1; ix <= n; ix++) {\n    i = rownr[ix];\n    rownr[0] = 0;\n    colOF[0] = my_chsign(is_maxim(lp), ratio[ix]);\n    rownr[1] = i;\n    colOF[1] = -1;\n    value = get_rh(lp, i);\n/*    j = get_constr_type(lp, i); */\n    add_columnex(lp, 2, colOF, rownr);\n    set_bounds(lp, lp->columns, value, value);\n/*    presolve_setEQ(psdata, i); */\n    set_rh(lp, i, 0);\n    appendLink(psdata->cols->varmap, j+ix);\n  }\n  presolve_validate(psdata, TRUE);\n\n  /* Clean up before returning */\nFinish:\n  FREE(rownr);\n  FREE(ratio);\n  (*nn) += n;\n\n  return( status );\n}\n\nSTATIC MYBOOL presolve_invalideq2(lprec *lp, presolverec *psdata)\n{\n  int    jx, jjx, i = 0, item;\n  MATrec *mat = lp->matA;\n  MYBOOL error = FALSE;\n\n  do {\n\n    if(i == 0)\n      i = firstActiveLink(psdata->EQmap);\n    else\n      i = nextActiveLink(psdata->EQmap, i);\n    if(i == 0)\n      return( error );\n\n    /* Get the row index of the first 2-element equality */\n    for(; i > 0; i = nextActiveLink(psdata->EQmap, i))\n      if(presolve_rowlength(psdata, i) == 2)\n        break;\n    if(i == 0)\n      return( error );\n\n    /* Get the first column */\n    item = 0;\n    jx  = presolve_nextcol(psdata, i, &item);\n    if(jx < 0)\n      error = TRUE;\n    jx  = ROW_MAT_COLNR(jx);\n\n    /* Get the second column */\n    jjx = presolve_nextcol(psdata, i, &item);\n    if(jjx < 0)\n      error = AUTOMATIC;\n  } while(!error);\n\n  return( error );\n}\n\n/* Callback to obtain the non-zero rows of equality constraints */\nint BFP_CALLMODEL presolve_getcolumnEQ(lprec *lp, int colnr, REAL nzvalues[], int nzrows[], int mapin[])\n{\n  int    i, ib, ie, nn = 0;\n  MATrec *mat = lp->matA;\n\n  ib = mat->col_end[colnr-1];\n  ie = mat->col_end[colnr];\n  for(; ib < ie; ib++) {\n    i = COL_MAT_ROWNR(ib);\n    if(!is_constr_type(lp, i, EQ) ||  /* It has to be an equality constraint         */\n       (mapin[i] == 0))               /* And it should not already have been deleted */\n      continue;\n    if(nzvalues != NULL) {\n      nzrows[nn] = mapin[i];\n      nzvalues[nn] = COL_MAT_VALUE(ib);\n    }\n    nn++;\n  }\n  return( nn );\n}\nSTATIC int presolve_singularities(presolverec *psdata, int *nn, int *nr, int *nv, int *nSum)\n{\n  lprec *lp = psdata->lp;\n  int i, j, n, *rmapin = NULL, *rmapout = NULL, *cmapout = NULL;\n\n  if(lp->bfp_findredundant(lp, 0, NULL, NULL, NULL) == 0)\n    return( 0 );\n\n  /* Create condensed row map */\n  allocINT(lp, &rmapin, lp->rows+1, TRUE);\n  allocINT(lp, &rmapout, psdata->EQmap->count+1, FALSE);\n  allocINT(lp, &cmapout, lp->columns+1, FALSE);\n  n = 0;\n  for(i = firstActiveLink(psdata->EQmap); i != 0; i = nextActiveLink(psdata->EQmap, i)) {\n    n++;\n    rmapout[n] = i;\n    rmapin[i]  = n;\n  }\n  rmapout[0] = n;\n  n = 0;\n  for(i = firstActiveLink(psdata->cols->varmap); i != 0; i = nextActiveLink(psdata->cols->varmap, i)) {\n    n++;\n    cmapout[n]  = i;\n  }\n  cmapout[0] = n;\n\n  /* Do the rank-revealing factorization */\n  n = lp->bfp_findredundant(lp, psdata->EQmap->count, presolve_getcolumnEQ, rmapin, cmapout);\n\n  /* Delete the redundant rows */\n  for(i = 1; i <= n; i++) {\n    j = rmapin[i];\n    j = rmapout[j];\n    presolve_rowremove(psdata, j, TRUE);\n  }\n  (*nn)   += n;\n  (*nr)   += n;\n  (*nSum) += n;\n\n  /* Clean up */\n  FREE(rmapout);\n  FREE(rmapin);\n  FREE(cmapout);\n\n  return( n );\n}\n\nSTATIC int presolve_elimeq2(presolverec *psdata, int *nn, int *nr, int *nc, int *nSum)\n{\n  lprec     *lp = psdata->lp;\n  int       n, i, jx, jjx, k, item, *plucount, *negcount, colplu, colneg,\n            iCoeffChanged = 0, iRowsRemoved = 0, iVarsFixed = 0, nrows = lp->rows,\n            status = RUNNING, *colindex = NULL;\n  MYBOOL    freshupdate;\n  REAL      Coeff1, Coeff2, Value1, Value2, lobound, upbound, bound, test, product,\n            *colvalue = NULL, *delvalue = NULL, *colitem;\n  MATrec    *mat = lp->matA, *rev = NULL;\n  DeltaVrec *DV = NULL;\n  LLrec     *EQ2 = NULL;\n\n  /* See if there is anything to do */\n  if(psdata->EQmap->count == 0) {\n    (*nSum) = 0;\n    return( status );\n  }\n\n  /* Tally counts */\n  createLink(lp->rows, &EQ2, NULL);\n  if((EQ2 == NULL) || !allocREAL(lp, &colvalue, nrows+1, FALSE) ||\n                      !allocREAL(lp, &delvalue, nrows+1, FALSE))\n    goto Finish;\n  for(i = firstActiveLink(psdata->EQmap); i > 0; i = nextActiveLink(psdata->EQmap, i)) {\n    if(presolve_rowlength(psdata, i) == 2)\n      appendLink(EQ2, i);\n  }\n  if(EQ2->count == 0)\n    goto Finish;\n  n = 0;\n\n  /* Do the elimination loop for all identified 2-element equalities */\n  for(i = firstActiveLink(EQ2); i > 0; i = nextActiveLink(EQ2, i)) {\n\n    /* Check if the constraint has been modified by a previous elimination */\n    if(presolve_rowlength(psdata, i) != 2)\n      continue;\n\n    /* Get the column indeces of NZ-values of the \"pivot\" row */\n    item = 0;\n    jx  = presolve_nextcol(psdata, i, &item);   /* Eliminated variable coefficient    b */\n#ifdef Paranoia\n    if(jx < 0)\n      report(lp, SEVERE, \"presolve_elimeq2: No qualifying %dst column was found in row %s (ostensible length %d)\\n\",\n                         1, get_row_name(lp, i), presolve_rowlength(psdata, i));\n#endif\n    Coeff2 = ROW_MAT_VALUE(jx);\n    jx  = ROW_MAT_COLNR(jx);\n    jjx = presolve_nextcol(psdata, i, &item);  /* Non-eliminated variable coefficient a */\n#ifdef Paranoia\n    if(jjx < 0)\n      report(lp, SEVERE, \"presolve_elimeq2: No qualifying %dnd column was found in row %s (ostensible length %d)\\n\",\n                          2, get_row_name(lp, i), presolve_rowlength(psdata, i));\n#endif\n    Coeff1 = ROW_MAT_VALUE(jjx);\n    jjx = ROW_MAT_COLNR(jjx);\n\n    /* Check if at least one of the coefficients is large enough to preserve stability;\n       use opposing maximum column values for stability testing. */\n    if((fabs(Coeff1) < psdata->epspivot*mat->colmax[jx]) &&\n       ((fabs(Coeff1) != 1) && (fabs(Coeff2) != 1)) &&\n       (fabs(Coeff2) < psdata->epspivot*mat->colmax[jjx]))\n      continue;\n\n    /* Cannot eliminate a variable if both are SOS members or SC variables */\n    if((is_semicont(lp, jx) && is_semicont(lp, jjx)) ||\n        (SOS_is_member(lp->SOS, 0, jx) && SOS_is_member(lp->SOS, 0, jjx)))\n      continue;\n\n    /* First check if we are allowed to swap; set swap \"blockers\" */\n    k = 0;\n    if(!is_int(lp, jx) && is_int(lp, jjx))\n      k += 1;\n    else if(!is_semicont(lp, jx) && is_semicont(lp, jjx))\n      k += 2;\n    else if(!SOS_is_member(lp->SOS, 0, jx) && SOS_is_member(lp->SOS, 0, jjx))\n      k += 4;\n\n    /* If there were no blockers, determine if we MUST swap the variable to be eliminated */\n    if(k == 0) {\n      if(is_int(lp, jx) && !is_int(lp, jjx))\n        k += 8;\n      else if(is_semicont(lp, jx) && !is_semicont(lp, jjx))\n        k += 16;\n      else if(SOS_is_member(lp->SOS, 0, jx) && !SOS_is_member(lp->SOS, 0, jjx))\n        k += 32;\n\n      /* If we are not forced to swap, decide if it otherwise makes sense - high order */\n      if(k == 0) {\n        if((fabs(Coeff2) < psdata->epspivot*mat->colmax[jjx]) &&\n           (fabs(Coeff1) > psdata->epspivot*mat->colmax[jx]))\n          k += 64;\n        else if(presolve_collength(psdata, jx) > presolve_collength(psdata, jjx))\n          k += 128;\n      }\n\n      /* If we are not forced to swap, decide if it otherwise makes sense - low order */\n      if(k == 0) {\n        Value2 = Coeff1/Coeff2;\n#ifdef DualFeasibilityLogicEQ2\n        if((Value2*lp->orig_obj[jx] < 0) &&\n          (Value2*lp->orig_obj[jjx] > 0))                     /* Seek increased dual feasibility */\n          k += 256;\n#endif\n#ifdef DivisorIntegralityLogicEQ2\n        if((fabs(modf(Coeff2, &Value2)) >= lp->epsvalue) &&    /* Seek integrality of result */\n           (fabs(modf(Coeff1, &Value2)) < lp->epsvalue))\n          k += 512;\n        else if((fabs(fabs(Coeff2)-1) >= lp->epsvalue) &&    /* Seek integrality of divisor */\n                 (fabs(fabs(Coeff1)-1) < lp->epsvalue))\n          k += 1024;\n#endif\n      }\n\n    }\n    else\n      k = 0;\n\n    /* Perform variable index swap if indicated */\n    if(k != 0) {\n      swapINT(&jx, &jjx);\n      swapREAL(&Coeff1, &Coeff2);\n    }\n\n    Value1 = lp->orig_rhs[i]/Coeff2; /* Delta constant term */\n    Value2 = Coeff1/Coeff2;          /* Delta variable term */\n    upbound = lp->orig_upbo[lp->rows+jx];\n    lobound = lp->orig_lowbo[lp->rows+jx];\n    if(lp->spx_trace) {\n      report(lp, DETAILED, \"Row %3d : Elim %g %s - %d\\n\", i, Coeff2, get_col_name(lp, jx), jx);\n      report(lp, DETAILED, \"          Keep %g %s - %d\\n\",    Coeff1, get_col_name(lp, jjx), jjx);\n    }\n\n    /* Get the coefficient vectors of the independent (jjx) and dependent (jx) columns;\n      the dependent column will be deleted and reconstructed during postsolve. */\n    freshupdate = (MYBOOL) ((colindex == NULL) || (colindex[jjx] == 0));\n    if(freshupdate)\n      mat_expandcolumn(mat, jjx, colvalue, NULL, TRUE);\n    else\n      mat_expandcolumn(rev, colindex[jjx], colvalue, NULL, FALSE);\n    if((colindex == NULL) || (colindex[jx] == 0))\n      mat_expandcolumn(mat, jx, delvalue, NULL, TRUE);\n    else\n      mat_expandcolumn(rev, colindex[jx], delvalue, NULL, FALSE);\n\n    /* Add variable reconstruction information */\n    addUndoPresolve(lp, TRUE, jx, Value1, Value2, jjx);\n\n    /* If possible, tighten the bounds of the uneliminated variable based\n       on the bounds of the eliminated variable. Also handle roundings\n       and attempt precision management. */\n    bound = lobound;\n    k = nrows+jjx;\n    if(bound > -lp->infinite) {\n      bound = (lp->orig_rhs[i] - Coeff2*bound) / Coeff1;\n      if(Value2 > 0) {\n        test = lp->orig_upbo[k];\n        if(bound < test - psdata->epsvalue) {\n          if(is_int(lp, jjx))\n            lp->orig_upbo[k] = floor(bound + lp->epsint);\n          else\n            lp->orig_upbo[k] = presolve_roundrhs(lp, bound, FALSE);\n        }\n      }\n      else {\n        test = lp->orig_lowbo[k];\n        if(bound > test + psdata->epsvalue) {\n          if(is_int(lp, jjx))\n            lp->orig_lowbo[k] = ceil(bound - lp->epsint);\n          else\n            lp->orig_lowbo[k] = presolve_roundrhs(lp, bound, TRUE);\n        }\n      }\n    }\n    bound = upbound;\n    if(bound < lp->infinite) {\n      bound = (lp->orig_rhs[i] - Coeff2*bound) / Coeff1;\n      if(Value2 < 0) {\n        test = lp->orig_upbo[k];\n        if(bound < test - psdata->epsvalue) {\n          if(is_int(lp, jjx))\n            lp->orig_upbo[k] = floor(bound + lp->epsint);\n          else\n            lp->orig_upbo[k] = presolve_roundrhs(lp, bound, FALSE);\n        }\n      }\n      else {\n        test = lp->orig_lowbo[k];\n        if(bound > test + psdata->epsvalue) {\n          if(is_int(lp, jjx))\n            lp->orig_lowbo[k] = ceil(bound - lp->epsint);\n          else\n            lp->orig_lowbo[k] = presolve_roundrhs(lp, bound, TRUE);\n        }\n      }\n    }\n\n#ifdef Eq2Reldiff\n    test = 2*lp->epsvalue;\n#else\n    test = psdata->epsvalue;\n#endif\n    if(/*(lp->orig_upbo[k] < lp->orig_lowbo[k]) ||*/\n#ifdef Eq2Reldiff\n       (fabs(my_reldiff(lp->orig_upbo[k],lp->orig_lowbo[k])) < test)) {\n#else\n       (fabs(lp->orig_upbo[k] - lp->orig_lowbo[k]) < test)) {\n#endif\n      my_roundzero(lp->orig_lowbo[k], test);\n      lp->orig_upbo[k] = lp->orig_lowbo[k];\n    }\n    else {\n      my_roundzero(lp->orig_upbo[k], test);\n      my_roundzero(lp->orig_lowbo[k], test);\n    }\n\n    if(/*(upbound < lobound) ||*/\n#ifdef Eq2Reldiff\n       (fabs(my_reldiff(upbound, lobound)) < test)) {\n#else\n       (fabs(upbound - lobound) < test)) {\n#endif\n      my_roundzero(lobound, test);\n      lp->orig_upbo[nrows+jx] = lobound;\n      upbound = lobound;\n    }\n\n    /* Loop over the non-zero rows of the column (jx) to be eliminated;\n      substitute jx-variable by updating rhs and jjx coefficients */\n    colitem = colvalue;\n    plucount = psdata->rows->plucount;\n    negcount = psdata->rows->negcount;\n    colplu = 0;\n    colneg = 0;\n    /* Count of non-zeros in the independent column jjx */\n    item = presolve_collength(psdata, jjx) - 1;\n    if(isnz_origobj(lp, jjx))\n      item++;\n    for(k = 0; k <= nrows; k++, colitem++) {\n\n      bound = delvalue[k];\n      if((k == i) || (bound == 0) ||\n         ((k > 0) && !isActiveLink(psdata->rows->varmap, k)))\n        continue;\n\n      /* Do constraint and nz-count updates for the substituted variable */\n      product = bound*Value1;\n\n      /* \"Raw\"/unsigned data */\n      presolve_adjustrhs(psdata, k, my_chsign(is_chsign(lp, k), product), test);\n\n      /* Change back to signed part */\n      if(*colitem != 0) {\n        if(*colitem > 0) {\n          colplu--;\n          plucount[k]--;\n        }\n        else {\n          colneg--;\n          negcount[k]--;\n        }\n        if((lobound < 0) && (upbound >= 0)) {\n          psdata->cols->pluneg[jjx]--;\n          psdata->rows->pluneg[k]--;\n        }\n        item--;\n      }\n      (*colitem) -= bound*Value2;\n      iCoeffChanged++;\n\n      /* Update counts */\n      if(fabs(*colitem) >= mat->epsvalue) {\n        if(*colitem > 0) {\n          colplu++;\n          plucount[k]++;\n        }\n        else {\n          colneg++;\n          negcount[k]++;\n        }\n        if((lobound < 0) && (upbound >= 0)) {\n          psdata->cols->pluneg[jjx]++;\n          psdata->rows->pluneg[k]++;\n        }\n        item++;\n      }\n      else {\n        *colitem = 0;\n      }\n\n      /* Also reduce count if the row contains the deleted variable */\n      if(bound > 0)\n        plucount[k]--;\n      else\n        negcount[k]--;\n    }\n    psdata->cols->plucount[jjx] += colplu;\n    psdata->cols->negcount[jjx] += colneg;\n\n    /* Save the new column */\n    if(rev == NULL) {\n      DV = createUndoLadder(lp, nrows, lp->columns / RESIZEFACTOR);\n      rev = DV->tracker;\n      rev->epsvalue = mat->epsvalue;\n      allocINT(lp, &(rev->col_tag), mat->columns_alloc+1, FALSE);\n      allocINT(lp, &colindex, lp->columns+1, TRUE);\n      rev->col_tag[0] = 0;\n    }\n    n = rev->col_tag[0] = incrementUndoLadder(DV);\n    mat_setcol(rev, n, 0, colvalue, NULL, FALSE, FALSE);\n    rev->col_tag[n] = jjx;\n\n    /* Save index to updated vector, but specially handle case where we have\n      the same independent variable for multiple equations! */\n    if(!freshupdate)\n      rev->col_tag[colindex[jjx]] *= -1;\n    colindex[jjx] = n;\n\n    /* Delete the column dependent variable */\n    jx = presolve_colremove(psdata, jx, FALSE);\n    iVarsFixed++;\n\n    /* Check if we have been lucky enough to have eliminated the independent\n       variable via substitution of the dependent variable */\n    if(item == 0) {\n#ifdef Paranoia\n      report(lp, DETAILED, \"presolve_elimeq2: Was able to remove variables %d and %d in row %s\\n\",\n                         jx, jjx, get_row_name(lp, i));\n#endif\n      if(presolve_colfix(psdata, jjx, 0.0, TRUE, nc))\n        jjx = presolve_colremove(psdata, jjx, FALSE);\n    }\n\n    /* Delete the row */\n    presolve_rowremove(psdata, i, FALSE);\n    iRowsRemoved++;\n  }\n\n  /* Perform the column updates collected above */\n  if(n > 0) {\n    mat_mapreplace(mat, psdata->rows->varmap, psdata->cols->varmap, rev);\n    presolve_validate(psdata, TRUE);\n#ifdef PresolveForceUpdateMax\n    mat_computemax(mat /* , FALSE */);\n#endif\n    psdata->forceupdate = TRUE;\n  }\n\n  /* Free work arrays */\nFinish:\n  if(DV != NULL)\n    freeUndoLadder(&DV);\n  freeLink(&EQ2);\n  FREE(colvalue);\n  FREE(delvalue);\n  FREE(colindex);\n\n  /* Update counters */\n  (*nn)   += iCoeffChanged;\n  (*nr)   += iRowsRemoved;\n  (*nc)   += iVarsFixed;\n  (*nSum) += iCoeffChanged + iRowsRemoved + iVarsFixed;\n\n  return( status );\n}\n\nSTATIC MYBOOL presolve_impliedfree(lprec *lp, presolverec *psdata, int colnr)\n{\n  int    i, ix, ie;\n  REAL   Tlower, Tupper;\n  MYBOOL status, rowbinds, isfree = FALSE;\n  MATrec *mat = lp->matA;\n\n  if(my_infinite(lp, get_lowbo(lp, colnr)) && my_infinite(lp, get_upbo(lp, colnr)))\n    return( TRUE );\n\n  ie = mat->col_end[colnr];\n  for(ix = mat->col_end[colnr-1]; (isfree != (TRUE | AUTOMATIC)) && (ix < ie); ix++) {\n    i = COL_MAT_ROWNR(ix);\n    if(!isActiveLink(psdata->rows->varmap, i))\n      continue;\n    Tlower = get_rh_lower(lp, i);\n    Tupper = get_rh_upper(lp, i);\n    status = presolve_multibounds(psdata, i, colnr, &Tlower, &Tupper, NULL, &rowbinds);\n    isfree = isfree | status | rowbinds;\n  }\n\n  return( (MYBOOL) (isfree == (TRUE | AUTOMATIC)) );\n}\n\nSTATIC MYBOOL presolve_impliedcolfix(presolverec *psdata, int rownr, int colnr, MYBOOL isfree)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   signflip, undoadded = FALSE;\n  MATrec   *mat = lp->matA;\n  int      jx, i, ib, ie = mat->row_end[rownr];\n  REAL     varLo = 0, varHi = 0, varRange, conRange = 0, matValue = 0, dual, RHS = lp->orig_rhs[rownr],\n           pivot, matAij = mat_getitem(mat, rownr, colnr), *vecOF = lp->orig_obj;\n\n  /* We cannot have semi-continuous or non-qualifying integers */\n  if(is_semicont(lp, colnr) || is_SOS_var(lp, colnr))\n    return( FALSE );\n  if(is_int(lp, colnr)) {\n    if(!isActiveLink(psdata->INTmap, rownr) || !is_presolve(lp, PRESOLVE_KNAPSACK))\n      return( FALSE );\n    /* colnr must have a coefficient equal to the smallest in the row */\n    varRange = lp->infinite;\n    i = 0;\n    pivot = 0;\n    for(ib = presolve_nextcol(psdata, rownr, &i); i != 0; ib = presolve_nextcol(psdata, rownr, &i)) {\n      jx = ROW_MAT_COLNR(ib);\n      dual = fabs(ROW_MAT_VALUE(ib));\n      /* Check if we have the target column and save the pivot value */\n      if(jx == colnr) {\n        /* Always accept unit coefficient */\n        if(fabs(dual - 1) < psdata->epsvalue)\n          break;\n        pivot = dual;\n        /* Otherwise continue scan */\n      }\n      /* Cannot accept case where result can be fractional */\n      else if((pivot > dual + psdata->epsvalue) ||\n               ((pivot > 0) && (fabs(fmod(dual, pivot)) > psdata->epsvalue)))\n        return( FALSE );\n    }\n  }\n\n  /* Ascertain that the pivot value is large enough to preserve stability */\n  pivot = matAij;\n  if(fabs(pivot) < psdata->epspivot*mat->colmax[colnr])\n    return( FALSE );\n\n  /* Must ascertain that the row variables are not SOS'es; this is because\n     the eliminated variable will be a function of another variable. */\n  if(SOS_count(lp) > 0) {\n    for(ib = mat->row_end[rownr-1]; ib < ie; ib++)\n      if(SOS_is_member(lp->SOS, 0, ROW_MAT_COLNR(ib)))\n        return( FALSE );\n  }\n\n  /* Calculate the dual value */\n  dual = vecOF[colnr]/pivot;\n\n  /* Here we have free variable in an equality constraint; this means we can\n     can adjust the OF for the deleted variable and also delete the constraint. */\n  if(isfree && is_constr_type(lp, rownr, EQ)) {\n    matValue = RHS/pivot;\n    if(matValue != 0)\n      undoadded = addUndoPresolve(lp, TRUE, colnr, matValue, 0.0, 0);\n  }\n\n  else {\n\n    /* IMPLIEDFREE: For simplicity, ensure that we can keep the slack based at 0,\n                   and not its upper bound. Effectively, we consider the constraint\n                   an equality, using the information of the sign of the dual.\n       IMPLIEDSLK: Since we already have an equality constraint, we wish to make sure\n                   that the ensuing inequality constraint will have an RHS that is\n                   non-infinite. */\n    if(isfree) {\n      SETMIN(RHS, presolve_sumplumin(lp, rownr, psdata->rows, TRUE));\n      matValue = presolve_sumplumin(lp, rownr, psdata->rows, FALSE);\n      conRange = get_rh_lower(lp, rownr);\n      conRange = RHS - MAX(matValue, conRange);\n      signflip = (MYBOOL) ((dual > 0) &&\n                           !my_infinite(lp, conRange));\n    }\n    else {\n      varLo = get_lowbo(lp, colnr);\n      varLo *= (my_infinite(lp, varLo) ? my_sign(pivot) : pivot);\n      varHi = get_upbo(lp, colnr);\n      varHi *= (my_infinite(lp, varHi) ? my_sign(pivot) : pivot);\n      if(pivot < 0)\n        swapREAL(&varHi, &varLo);\n      signflip = my_infinite(lp, varLo);\n    }\n    if(signflip) {\n      mat_multrow(mat, rownr, -1);\n      RHS -= conRange;\n      RHS = -RHS;\n      lp->orig_rhs[rownr] = RHS;\n      pivot = -pivot;\n      dual  = -dual;\n      if(!isfree) {\n        varLo = -varLo;\n        varHi = -varHi;\n        swapREAL(&varHi, &varLo);\n      }\n    }\n    matValue = RHS/pivot;\n\n    /* Prepare for deleting free or implied free variable in inequality constraint.\n       Different strategies need to be used:\n\n       ACTUAL:  Find the proper constraint bound and store undo information for\n                recovering the value of the implied free variable.  The constraint\n                is then deleted.  We have to adjust the objective function if the\n                OF coefficient for the implied free variable is non-zero.\n       IMPLIED: Convert the constraint to an inequality at the proper bound.\n                For given models, the new equality constraint can later provide\n                an implied slack, which means that a further variable is eliminated,\n                and the constraint again becomes an inequality constraint.\n\n      Note that this version only implements the ACTUAL mode */\n    if(isfree) {\n      /* Add undo information connecting the deleted variable to the RHS */\n      if(matValue != 0)\n        undoadded = addUndoPresolve(lp, TRUE, colnr, matValue, 0.0, 0);\n      /* Add undo information for the dual of the deleted constraint */\n      if(dual != 0)\n        addUndoPresolve(lp, FALSE, rownr, dual, 0.0, 0);\n    }\n\n    /* Prepare for deleting implied slack variable.  The following two cases are\n      handled:\n\n      1. Equality constraint: Convert the constraint to an inequality constraint\n                              that is possibly ranged\n      2. Other constraints:   Expand existing slack variable / constraint\n                              range, if required. */\n    else {\n      if(my_infinite(lp, varHi))\n        varRange = lp->infinite;\n#ifdef Paranoia\n      else if(my_infinite(lp, varLo)) {\n        report(lp, SEVERE, \"presolve_impliedcolfix: Negative infinite limit for variable %d\\n\", colnr);\n        varRange = lp->infinite;\n      }\n#endif\n      else\n        varRange = my_precision(fabs(varHi - varLo) + lp->epsvalue, psdata->epsvalue);\n      presolve_adjustrhs(psdata, rownr, varLo, psdata->epsvalue);\n\n      /* Handle case 1 of an equality constraint */\n      if(is_constr_type(lp, rownr, EQ)) {\n        /* Make sure we actually have a ranged constraint */\n        if(varRange > 0) {\n          set_constr_type(lp, rownr, LE);\n          if(!my_infinite(lp, varRange))\n            lp->orig_upbo[rownr] = varRange;\n          setLink(psdata->LTmap, rownr);\n          removeLink(psdata->EQmap, rownr);\n        }\n      }\n      /* Handle case 2 of an inequality constraint (UNDER CONSTRUCTION!)*/\n      else {\n        if(!my_infinite(lp, lp->orig_upbo[rownr])) {\n          if(my_infinite(lp, varRange))\n            lp->orig_upbo[rownr] = lp->infinite;\n          else\n            lp->orig_upbo[rownr] += varHi - varLo;\n        }\n      }\n      /* Update counts */\n      if(matAij > 0)\n        psdata->rows->plucount[rownr]--;\n      else\n        psdata->rows->negcount[rownr]--;\n      if(my_sign(varLo) != my_sign(varHi))\n        psdata->rows->pluneg[rownr]--;\n\n      /* Add undo information for the deleted variable; note that we cannot link the\n        deleted variable to the slack, since it may not be available during undo.\n        We really should have a mini LP to compute this allocation ex-post. */\n      if(RHS != 0)\n        undoadded = addUndoPresolve(lp, TRUE, colnr, RHS/pivot, 0.0, 0);\n    }\n  }\n\n  /* Update the OF constant */\n  if(dual != 0) {\n    presolve_adjustrhs(psdata, 0, dual * RHS, 0);\n/*    lp->orig_rhs[0] -= dual * RHS; */\n    vecOF[colnr] = 0;\n  }\n\n  /* Do affine transformation with the constraint row */\n  i = 0;\n  for(ib = presolve_nextcol(psdata, rownr, &i); ib >= 0;\n      ib = presolve_nextcol(psdata, rownr, &i)) {\n\n    /* Get the constraint element */\n    jx = ROW_MAT_COLNR(ib);\n    if(jx == colnr)\n      continue;\n    matValue = ROW_MAT_VALUE(ib);\n\n    /* Adjust OF for the variable to be deleted */\n    if(dual != 0)\n      vecOF[jx] -= dual * matValue;\n\n    /* Add reconstruction/undo parameters for the deleted variable */\n    if(!undoadded)\n      undoadded = addUndoPresolve(lp, TRUE, colnr, 0.0, matValue/pivot, jx);\n    else\n      appendUndoPresolve(lp, TRUE, matValue/pivot, jx);\n  }\n\n  return( TRUE );\n}\n\nSTATIC psrec *presolve_initpsrec(lprec *lp, int size)\n{\n  psrec *ps = (psrec *) calloc(1, sizeof(*ps));\n\n  createLink(size, &ps->varmap, NULL);\n    fillLink(ps->varmap);\n\n  size++;\n\n  allocINT(lp, &ps->empty, size, FALSE);\n  ps->empty[0] = 0;\n\n  allocREAL(lp, &ps->pluupper,  size, FALSE);\n  allocREAL(lp, &ps->negupper,  size, FALSE);\n  allocREAL(lp, &ps->plulower,  size, FALSE);\n  allocREAL(lp, &ps->neglower,  size, FALSE);\n  allocINT(lp,  &ps->infcount,  size, FALSE);\n\n  ps->next = (int **) calloc(size, sizeof(*(ps->next)));\n\n  allocINT(lp,  &ps->plucount,  size, TRUE);\n  allocINT(lp,  &ps->negcount,  size, TRUE);\n  allocINT(lp,  &ps->pluneg,    size, TRUE);\n\n  ps->allocsize = size;\n\n  return( ps );\n}\nSTATIC void presolve_freepsrec(psrec **ps)\n{\n  FREE((*ps)->plucount);\n  FREE((*ps)->negcount);\n  FREE((*ps)->pluneg);\n  FREE((*ps)->infcount);\n\n  if((*ps)->next != NULL) {\n    int i, n = (*ps)->allocsize;\n    for(i = 0; i < n; i++)\n      FREE((*ps)->next[i]);\n    FREE((*ps)->next);\n  }\n\n  FREE((*ps)->plulower);\n  FREE((*ps)->neglower);\n  FREE((*ps)->pluupper);\n  FREE((*ps)->negupper);\n\n  FREE((*ps)->empty);\n\n  freeLink(&(*ps)->varmap);\n\n  FREE(*ps);\n}\n\nSTATIC presolverec *presolve_init(lprec *lp)\n{\n  int         k, i, ix, ixx, colnr,\n              ncols = lp->columns,\n              nrows = lp->rows;\n  REAL        hold;\n  MATrec      *mat = lp->matA;\n  presolverec *psdata = NULL;\n\n  /* Optimize memory usage if we have a very large model;\n     this is to reduce the risk of out-of-memory situations. */\n  ix  = get_nonzeros(lp);\n  ixx = lp->matA->mat_alloc;\n  if((ixx - ix > MAT_START_SIZE) && ((ixx - ix) * 20 > ixx))\n    mat_memopt(lp->matA, nrows / 20, ncols / 20, ix / 20);\n\n  psdata = (presolverec *) calloc(1, sizeof(*psdata));\n\n  psdata->lp   = lp;\n  psdata->rows = presolve_initpsrec(lp, nrows);\n  psdata->cols = presolve_initpsrec(lp, ncols);\n\n  psdata->epsvalue = PRESOLVE_EPSVALUE;\n  psdata->epspivot = PRESOLVE_EPSPIVOT;\n  psdata->forceupdate = TRUE;\n\n  /* Save incoming primal bounds */\n  k = lp->sum + 1;\n  allocREAL(lp, &psdata->pv_lobo, k, FALSE);\n  MEMCOPY(psdata->pv_lobo, lp->orig_lowbo, k);\n  allocREAL(lp, &psdata->pv_upbo, k, FALSE);\n  MEMCOPY(psdata->pv_upbo, lp->orig_upbo, k);\n\n  /* Create and initialize dual value (Langrangean and slack) limits */\n  allocREAL(lp, &psdata->dv_lobo, k, FALSE);\n  allocREAL(lp, &psdata->dv_upbo, k, FALSE);\n  for(i = 0; i <= nrows; i++) {\n    psdata->dv_lobo[i] = (is_constr_type(lp, i, EQ) ? -lp->infinite : 0);\n    psdata->dv_upbo[i] = lp->infinite;\n  }\n  k--;\n  for(; i <= k; i++) {\n    psdata->dv_lobo[i] = 0;\n    psdata->dv_upbo[i] = lp->infinite;\n  }\n\n /* Create NZ count and sign arrays, and do general initialization of row bounds */\n  createLink(nrows, &psdata->EQmap, NULL);\n  createLink(nrows, &psdata->LTmap, NULL);\n  createLink(nrows, &psdata->INTmap, NULL);\n  for(i = 1; i <= nrows; i++) {\n    switch (get_constr_type(lp, i)) {\n      case LE: appendLink(psdata->LTmap, i);\n                break;\n      case EQ: appendLink(psdata->EQmap, i);\n                break;\n    }\n    k = mat_rowlength(mat, i);\n    if((lp->int_vars > 0) && (k > 0))\n      appendLink(psdata->INTmap, i);\n  }\n\n  /* Seek to reduce set of sum(INT*INT) rows (mainly for GCD coefficient reductions) */\n  if(psdata->INTmap->count > 0)\n  for(i = 1; i <= nrows; i++) {\n    if(!isActiveLink(psdata->INTmap, i))\n      continue;\n    /* Disqualify if there is a non-int variable, otherwise find smallest absolute fractional row value */\n    ix = mat->row_end[i - 1];\n    ixx = mat->row_end[i];\n    colnr = 0;\n    for(; ix < ixx; ix++) {\n      if(!is_int(lp, ROW_MAT_COLNR(ix))) {\n        removeLink(psdata->INTmap, i);\n        break;\n      }\n      hold = fabs(ROW_MAT_VALUE(ix));\n      hold = fmod(hold, 1);\n      /* Adjust colnr to be a decimal scalar */\n      for(k = 0; (k <= MAX_FRACSCALE) && (hold+psdata->epsvalue < 1); k++)\n        hold *= 10;\n      if(k > MAX_FRACSCALE) {\n        removeLink(psdata->INTmap, i);\n        break;\n      }\n      SETMAX(colnr, k);\n    }\n    if(!isActiveLink(psdata->INTmap, i))\n      continue;\n    hold = pow(10.0, colnr);\n    /* Also disqualify if the RHS is fractional after scaling */\n    if(fabs(fmod(lp->orig_rhs[i] * hold, 1)) > psdata->epsvalue) {\n      removeLink(psdata->INTmap, i);\n      continue;\n    }\n    /* We have an all-int constraint, see if we should scale it up */\n    if(k > 0) {\n      ix = mat->row_end[i - 1];\n      for(; ix < ixx; ix++) {\n        ROW_MAT_VALUE(ix) *= hold;\n      }\n      lp->orig_rhs[i] *= hold;\n      if(!my_infinite(lp, lp->orig_upbo[i]))\n        lp->orig_upbo[i] *= hold; /* KE: Fix due to Andy Loto - 20070619 */\n    }\n  }\n\n  /* Do the real tallying and ordering work */\n  presolve_validate(psdata, TRUE);\n\n  return( psdata );\n}\n\nSTATIC void presolve_free(presolverec **psdata)\n{\n  presolve_freepsrec(&(*psdata)->rows);\n  presolve_freepsrec(&(*psdata)->cols);\n  FREE((*psdata)->dv_lobo);\n  FREE((*psdata)->dv_upbo);\n  FREE((*psdata)->pv_lobo);\n  FREE((*psdata)->pv_upbo);\n  freeLink(&(*psdata)->EQmap);\n  freeLink(&(*psdata)->LTmap);\n  freeLink(&(*psdata)->INTmap);\n  FREE(*psdata);\n}\n\nSTATIC int presolve_makefree(presolverec *psdata)\n{\n  lprec    *lp = psdata->lp;\n  int      i, ix, j, nn = 0;\n  REAL     Xlower, Xupper, losum, upsum, lorhs, uprhs, freeinf = lp->infinite / 10;\n  MATrec   *mat = lp->matA;\n  LLrec    *colLL = NULL;\n\n  /* First see if we can relax ranged constraints */\n  for(i = firstActiveLink(psdata->rows->varmap); i != 0; i = nextActiveLink(psdata->rows->varmap, i)) {\n    if(is_constr_type(lp, i, EQ))\n      continue;\n    presolve_range(lp, i, psdata->rows, &losum, &upsum);\n    lorhs = get_rh_lower(lp, i);\n    uprhs = get_rh_upper(lp, i);\n\n    /* Look for opportunity to relax constraint bounds */\n    if(presolve_rowlength(psdata, i) > 1) {\n      if((is_constr_type(lp, i, GE) && (upsum <= uprhs)) ||\n         (is_constr_type(lp, i, LE) && (losum >= lorhs)))\n        set_rh_range(lp, i, lp->infinite);\n    }\n  }\n\n  /* Collect columns available for bound relaxation (find implied free variables)\n     (consider sorting the list in decending order of column lengths or do call to\n      COLAMD to maximize impact) */\n  createLink(lp->columns, &colLL, NULL);\n  for(j = firstActiveLink(psdata->cols->varmap); j != 0; j = nextActiveLink(psdata->cols->varmap, j))\n    if(presolve_impliedfree(lp, psdata, j))\n      appendLink(colLL, j);\n\n  /* Find what columns to relax (ideally one per row) */\n  if(colLL->count > 0) {\n    LLrec  *rowLL = NULL;\n    MYBOOL canfree;\n\n    /* Create row tracker */\n    createLink(lp->rows, &rowLL, NULL);\n    fillLink(rowLL);\n\n    /* Loop over all column candidates */\n    for(j = firstActiveLink(colLL); (j > 0) && (rowLL->count > 0); j = nextActiveLink(colLL, j)) {\n\n      /* Verify that the variable is applicable */\n      canfree = TRUE;\n      for(ix = mat->col_end[j-1]; canfree && (ix < mat->col_end[j]); ix++)\n        canfree = isActiveLink(rowLL, COL_MAT_ROWNR(ix));\n\n      /* If so, then open the bounds and update the row availability mapper */\n      if(canfree) {\n        nn++;\n        Xlower = get_lowbo(lp, j);\n        Xupper = get_upbo(lp, j);\n        if(Xlower >= 0)\n          set_bounds(lp, j, 0, freeinf);\n        else if(Xupper <= 0)\n          set_bounds(lp, j, -freeinf, 0);\n        else\n/*          set_bounds(lo, j, -freeinf, freeinf); */\n          set_unbounded(lp, j);\n        for(ix = mat->col_end[j-1]; ix < mat->col_end[j]; ix++)\n          removeLink(rowLL, COL_MAT_ROWNR(ix));\n      }\n    }\n    freeLink(&rowLL);\n  }\n\n  /* Free list and return */\n  freeLink(&colLL);\n  return( nn );\n}\n\nSTATIC MYBOOL presolve_updatesums(presolverec *psdata)\n{\n  lprec    *lp = psdata->lp;\n  int      j;\n\n  /* Initialize row accumulation arrays */\n  MEMCLEAR(psdata->rows->pluupper, lp->rows + 1);\n  MEMCLEAR(psdata->rows->negupper, lp->rows + 1);\n  MEMCLEAR(psdata->rows->plulower, lp->rows + 1);\n  MEMCLEAR(psdata->rows->neglower, lp->rows + 1);\n  MEMCLEAR(psdata->rows->infcount, lp->rows + 1);\n\n  /* Loop over active columns */\n  for(j = firstActiveLink(psdata->cols->varmap); j != 0;\n      j = nextActiveLink(psdata->cols->varmap, j)) {\n    presolve_colfix(psdata, j, lp->infinite, FALSE, NULL);\n  }\n\n#ifdef UseDualPresolve\n  /* Initialize column accumulation arrays */\n  MEMCLEAR(psdata->cols->pluupper, lp->columns + 1);\n  MEMCLEAR(psdata->cols->negupper, lp->columns + 1);\n  MEMCLEAR(psdata->cols->plulower, lp->columns + 1);\n  MEMCLEAR(psdata->cols->neglower, lp->columns + 1);\n  MEMCLEAR(psdata->cols->infcount, lp->columns + 1);\n\n  /* Loop over active rows */\n  for(j = firstActiveLink(psdata->rows->varmap); j != 0;\n      j = nextActiveLink(psdata->rows->varmap, j)) {\n    presolve_rowfix(psdata, j, lp->infinite, FALSE, NULL);\n  }\n#endif\n\n  return( TRUE );\n}\n\nSTATIC MYBOOL presolve_finalize(presolverec *psdata)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   compactvars = FALSE;\n  int      ke, n;\n\n  /* Save eliminated rows and columns for restoration purposes */\n#ifdef SavePresolveEliminated\n  psdata->deletedA = mat_extractmat(lp->matA, rowmap, colmap, TRUE);\n  if(!mat_validate(psdata->deletedA))\n    report(lp, SEVERE, \"presolve_finalize: Could not validate matrix with undo data\\n\");\n#endif\n\n  /* Check if OF columns are to be deleted */\n  lp->presolve_undo->OFcolsdeleted = FALSE;\n  for(n = firstInactiveLink(psdata->cols->varmap); (n != 0) && !lp->presolve_undo->OFcolsdeleted;\n      n = nextInactiveLink(psdata->cols->varmap, n))\n    lp->presolve_undo->OFcolsdeleted = (MYBOOL) (lp->orig_obj[n] != 0);\n\n  /* Delete eliminated columns */\n  ke = lastInactiveLink(psdata->cols->varmap);\n  n = countInactiveLink(psdata->cols->varmap);\n  if((n > 0) && (ke > 0)) {\n    del_columnex(lp, psdata->cols->varmap);\n    mat_colcompact(lp->matA, lp->presolve_undo->orig_rows,\n                             lp->presolve_undo->orig_columns);\n    compactvars = TRUE;\n  }\n\n  /* Delete eliminated rows */\n  ke = lastInactiveLink(psdata->rows->varmap);\n  n = countInactiveLink(psdata->rows->varmap);\n  if((n > 0) && (ke > 0)) {\n    del_constraintex(lp, psdata->rows->varmap);\n    mat_rowcompact(lp->matA, TRUE);\n    compactvars = TRUE;\n  }\n  else if(psdata->nzdeleted > 0)\n    mat_zerocompact(lp->matA);\n\n  /* Do compacting and updating of variable maps */\n  if(compactvars)\n    varmap_compact(lp, lp->presolve_undo->orig_rows,\n                       lp->presolve_undo->orig_columns);\n\n  /* Reduce memory usage of postsolve matrices */\n  if(lp->presolve_undo->primalundo != NULL)\n    mat_memopt(lp->presolve_undo->primalundo->tracker, 0, 0, 0);\n  if(lp->presolve_undo->dualundo != NULL)\n    mat_memopt(lp->presolve_undo->dualundo->tracker, 0, 0, 0);\n\n  /* Round near-zero objective function coefficients and RHS values */\n  ke = lp->columns;\n  for(n = 1; n <= ke; n++)\n    my_roundzero(lp->orig_obj[n], lp->epsvalue);\n  ke = lp->rows;\n  for(n = 1; n <= ke; n++)\n    my_roundzero(lp->orig_rhs[n], lp->epsvalue);\n\n  /* Update the SOS sparse mapping */\n  if(SOS_count(lp) > 0)\n    SOS_member_updatemap(lp->SOS);\n\n  /* Validate matrix and reconstruct row indexation */\n  return(mat_validate(lp->matA));\n}\n\nSTATIC MYBOOL presolve_debugdump(lprec *lp, presolverec *psdata, char *filename, MYBOOL doappend)\n{\n  FILE   *output = stdout;\n  int   size;\n  MYBOOL ok;\n\n  ok = (MYBOOL) ((filename == NULL) || ((output = fopen(filename, my_if(doappend, \"a\", \"w\"))) != NULL));\n  if(!ok)\n    return(ok);\n  if((filename == NULL) && (lp->outstream != NULL))\n    output = lp->outstream;\n\n  fprintf(output, \"\\nPRESOLVE - Status at loop %d:%d:%d\\n\",\n                  psdata->outerloops, psdata->middleloops, psdata->innerloops);\n  fprintf(output, \"Model size:     %d rows (%d equalities, %d less than), %d columns\\n\",\n                  psdata->rows->varmap->count, psdata->EQmap->count, psdata->LTmap->count, psdata->cols->varmap->count);\n\n  fprintf(output, \"\\nMAPPERS\\n-------\\n\\n\");\n  size = 1;\n  blockWriteINT(output,  \"colmap\", psdata->cols->varmap->map, 0, size*psdata->cols->varmap->size);\n  blockWriteINT(output,  \"rowmap\", psdata->rows->varmap->map, 0, size*psdata->rows->varmap->size);\n  blockWriteINT(output,  \"EQmap\",  psdata->EQmap->map,  0, size*psdata->EQmap->size);\n  blockWriteINT(output,  \"LTmap\",  psdata->LTmap->map,  0, size*psdata->LTmap->size);\n\n  fprintf(output, \"\\nCOUNTS\\n------\\n\\n\");\n  blockWriteINT(output, \"plucount\",  psdata->rows->plucount,  0, lp->rows);\n  blockWriteINT(output, \"negcount\",  psdata->rows->negcount,  0, lp->rows);\n  blockWriteINT(output, \"pluneg\",    psdata->rows->pluneg,    0, lp->rows);\n\n  fprintf(output, \"\\nSUMS\\n----\\n\\n\");\n  blockWriteREAL(output, \"pluupper\", psdata->rows->pluupper, 0, lp->rows);\n  blockWriteREAL(output, \"negupper\", psdata->rows->negupper, 0, lp->rows);\n  blockWriteREAL(output, \"plulower\", psdata->rows->pluupper, 0, lp->rows);\n  blockWriteREAL(output, \"neglower\", psdata->rows->negupper, 0, lp->rows);\n\n  if(filename != NULL)\n    fclose(output);\n  return(ok);\n}\n\nint CMP_CALLMODEL compRedundant(const UNIONTYPE QSORTrec *current, const UNIONTYPE QSORTrec *candidate)\n{\n  int start1 = (int) (current->int4.intpar1),\n      start2 = (int) (candidate->int4.intpar1),\n      result = CMP_COMPARE(start1, start2);\n\n  if(result == 0) {\n    start1 = (int) (current->int4.intpar2);\n    start2 = (int) (candidate->int4.intpar2);\n    result = -CMP_COMPARE(start1, start2);\n  }\n  return( result );\n}\nint CMP_CALLMODEL compSparsity(const UNIONTYPE QSORTrec *current, const UNIONTYPE QSORTrec *candidate)\n{\n  int start1 = (int) (current->int4.intpar1),\n      start2 = (int) (candidate->int4.intpar1),\n      result = CMP_COMPARE(start1, start2);\n\n  if(result == 0) {\n    start1 = (int) (current->int4.intpar2);\n    start2 = (int) (candidate->int4.intpar2);\n    result = -CMP_COMPARE(start1, start2);\n  }\n\n  if(result == 0) {\n    start1 = (int) (current->int4.intval);\n    start2 = (int) (candidate->int4.intval);\n    result = CMP_COMPARE(start1, start2);\n  }\n  return( result );\n}\nint CMP_CALLMODEL compAggregate(const UNIONTYPE QSORTrec *current, const UNIONTYPE QSORTrec *candidate)\n{\n  int  index1 = (int) (current->pvoidint2.intval),\n       index2 = (int) (candidate->pvoidint2.intval);\n  lprec *lp   = (lprec *) current->pvoidint2.ptr;\n  REAL value1 = lp->orig_obj[index1],\n       value2 = lp->orig_obj[index2];\n\n  /* Smallest objective coefficient (largest contribution to OF) */\n  int  result = CMP_COMPARE(value1, value2);\n\n  /* Smallest lower variable bound */\n  if(result == 0) {\n    index1 += lp->rows;\n    index2 += lp->rows;\n    value1 = lp->orig_lowbo[index1];\n    value2 = lp->orig_lowbo[index2];\n    result = CMP_COMPARE(value1, value2);\n  }\n\n  /* Largest upper variable bound */\n  if(result == 0) {\n    value1 = lp->orig_upbo[index1];\n    value2 = lp->orig_upbo[index2];\n    result = -CMP_COMPARE(value1, value2);\n  }\n  return( result );\n}\n\nSTATIC int presolve_rowdominance(presolverec *psdata, int *nCoeffChanged, int *nRowsRemoved, int *nVarsFixed, int *nSum)\n{\n  lprec    *lp = psdata->lp;\n  MATrec   *mat = lp->matA;\n  int      i, ii, ib, ie, n, jb, je, jx, *coldel = NULL, status = RUNNING, item,\n           iCoeffChanged = 0, iRowRemoved = 0, iVarFixed = 0;\n  REAL     ratio, *rowvalues = NULL;\n  UNIONTYPE QSORTrec *QS = (UNIONTYPE QSORTrec *) calloc(lp->rows+1, sizeof(*QS));\n\n  /* Check if we were able to obtain working memory */\n  if(QS == NULL)\n    return( status);\n\n  /* A dominating row of variables always satisfy the following criteria:\n      1) The starting column position is never lower, but could be the same\n      2) The non-zero row count is always lower */\n  n = 0;\n  for(i = firstActiveLink(psdata->EQmap); i != 0; i = nextActiveLink(psdata->EQmap, i)) {\n    /* Make sure we have no SOS or semi-continuous variables */\n    jb = je = 0;\n    if((SOS_count(lp) > 0) || (lp->sc_vars > 0)) {\n      item = 0;\n      for(jb = presolve_nextcol(psdata, i, &item); jb >= 0;\n          jb = presolve_nextcol(psdata, i, &item)) {\n        jx = ROW_MAT_COLNR(jb);\n        if(SOS_is_member(lp->SOS, 0, jx) || is_semicont(lp, jx))\n          break;\n      }\n    }\n\n    /* Add to list if we are Ok */\n    if(jb < 0) {\n      QS[n].int4.intval = i;\n      item = 0;\n      ii = presolve_nextcol(psdata, i, &item);\n      QS[n].int4.intpar1 = ROW_MAT_COLNR(ii);\n      QS[n].int4.intpar2 = presolve_rowlength(psdata, i);\n      n++;\n    }\n  }\n  if(n <= 1)\n    goto Finish;\n  QS_execute(QS, n, (findCompare_func *) compRedundant, NULL);\n\n  /* Let us start from the top of the list, going forward and looking\n    for the longest possible dominating row */\n  if(!allocREAL(lp, &rowvalues, lp->columns + 1, TRUE) ||\n     !allocINT(lp, &coldel, lp->columns + 1, FALSE))\n    goto Finish;\n\n  for(ib = 0; ib < n; ib++) {\n\n    /* Get row and check if it was previously eliminated */\n    i = QS[ib].int4.intval;\n    if(i < 0)\n      continue;\n\n    /* Load the non-zero row values */\n    item = 0;\n    for(jb = presolve_nextcol(psdata, i, &item); jb >= 0;\n        jb = presolve_nextcol(psdata, i, &item)) {\n      jx = ROW_MAT_COLNR(jb);\n      rowvalues[jx] = ROW_MAT_VALUE(jb);\n    }\n\n    for(ie = ib+1; ie < n; ie++) {\n\n      /* Get row and check if it was previously eliminated */\n      ii = QS[ie].int4.intval;\n      if(ii < 0)\n        continue;\n\n#ifdef Paranoia\n      if((QS[ib].int4.intpar1 > QS[ie].int4.intpar1) ||\n         ((QS[ib].int4.intpar1 == QS[ie].int4.intpar1) && (QS[ib].int4.intpar2 < QS[ie].int4.intpar2)))\n        report(lp, SEVERE, \"presolve_rowdominance: Invalid sorted row order\\n\");\n#endif\n\n      /* Loop over every row member to confirm that the candidate\n        actually dominates in every position */\n      if((lp->orig_rhs[i] == 0) && (lp->orig_rhs[ii] == 0))\n        ratio = 0;\n      else if((lp->orig_rhs[i] != 0) && (lp->orig_rhs[ii] != 0))\n        ratio = lp->orig_rhs[i] / lp->orig_rhs[ii];\n      else\n        continue;\n      item = 0;\n      for(jb = presolve_nextcol(psdata, ii, &item); jb >= 0;\n          jb = presolve_nextcol(psdata, ii, &item)) {\n        jx = ROW_MAT_COLNR(jb);\n        if(rowvalues[jx] == 0)\n          break;\n        if(ratio == 0)\n          ratio = rowvalues[jx] / ROW_MAT_VALUE(jb);\n        else if(fabs(rowvalues[jx] - ratio*ROW_MAT_VALUE(jb)) > psdata->epsvalue)\n          break;\n      }\n\n      /* \"We have contact\" */\n      if(jb < 0) {\n        int sign_1 = 0, sign_j = 0;\n\n        /* Need to fix any superset columns, but require that they have equal signs */\n        coldel[0] = 0;\n        item = 0;\n        for(jb = presolve_nextcol(psdata, i, &item); jb >= 0;\n            jb = presolve_nextcol(psdata, i, &item)) {\n          jx = ROW_MAT_COLNR(jb);\n          if(mat_findelm(mat, ii, jx) <= 0) {\n\n            /* Cancel if we detect a free or \"quasi-free\" variable */\n            if((lp->orig_lowbo[lp->rows + jx] < 0) &&\n               (lp->orig_upbo[lp->rows + jx] > 0)) {\n              coldel[0] = -1;\n              break;\n            }\n\n            /* Ensure that we are feasible */\n            else if((lp->orig_lowbo[lp->rows + jx] > 0) ||\n               (lp->orig_upbo[lp->rows + jx] < 0)) {\n              report(lp, DETAILED, \"presolve_rowdominate: Column %s is infeasible due to conflict in rows %s and %s\\n\",\n                                    get_col_name(lp, jx), get_row_name(lp, i), get_row_name(lp, ii));\n              coldel[0] = -1;\n              break;\n            }\n\n            /* Check consistency / uniformity of signs */\n            sign_j = my_sign(ROW_MAT_VALUE(jb));\n            sign_j = my_chsign(is_negative(lp, jx), sign_j);\n            if(coldel[0] == 0) {\n              sign_1 = sign_j;\n              coldel[++coldel[0]] = jx;\n            }\n            else if(sign_j == sign_1) {\n              coldel[++coldel[0]] = jx;\n            }\n            else {\n              coldel[0] = -1;\n              break;\n            }\n          }\n        }\n\n        /* Force break / continuation if the superset columns were incompatible */\n        if(coldel[0] < 0)\n          continue;\n\n        /* Do the column fixing and deletion (check for infeasibility in the process) */\n        for(jb = 1; jb <= coldel[0]; jb++) {\n          jx = coldel[jb];\n          if(!presolve_colfix(psdata, jx, 0, TRUE, &iVarFixed)) {\n             status = presolve_setstatus(psdata, INFEASIBLE);\n             goto Finish;\n          }\n          presolve_colremove(psdata, jx, TRUE);\n          rowvalues[jx] = 0;\n        }\n\n        /* Then delete the row */\n        presolve_rowremove(psdata, ii, TRUE);\n        iRowRemoved++;\n        QS[ie].int4.intval = -ii;\n      }\n    }\n\n    /* Clear the non-zero row values ahead of the next row candidate */\n    ie = mat->row_end[i-1];\n    ii = mat->row_end[i];\n    for(; ie < ii; ie++)\n      rowvalues[ROW_MAT_COLNR(ie)] = 0;\n\n  }\nFinish:\n  FREE(QS);\n  FREE(rowvalues);\n  FREE(coldel);\n\n  (*nCoeffChanged) += iCoeffChanged;\n  (*nRowsRemoved)  += iRowRemoved;\n  (*nVarsFixed)    += iVarFixed;\n  (*nSum)          += iCoeffChanged + iRowRemoved + iVarFixed;\n\n  return( status );\n}\n\n#if 0\nSTATIC int presolve_coldominance01(presolverec *psdata, int *nConRemoved, int *nVarsFixed, int *nSum)\n/* The current version of this routine eliminates binary variables\n   that are dominated via set coverage or unit knapsack constraints */\n{\n  lprec    *lp = psdata->lp;\n  MATrec   *mat = lp->matA;\n  MYBOOL   first;\n  int      i, ii, ib, ie, n, jb, je, jx, jj, item, item2,\n           *coldel = NULL, status = RUNNING, iVarFixed = 0;\n  REAL     scale, rhsval, *colvalues = NULL;\n  UNIONTYPE QSORTrec *QS = (UNIONTYPE QSORTrec *) calloc(lp->columns+1, sizeof(*QS));\n\n  /* Check if we were able to obtain working memory */\n  if(QS == NULL)\n    return( status);\n  if(lp->int_vars == 0)\n    goto Finish;\n\n  /* A column dominates another binary variable column with the following criteria:\n      1) The relative matrix non-zero entries are identical\n      2) The relative objective coefficient is worse than the other;\n         if the OF coefficients are identical, we can delete an arbitrary variable */\n  n = 0;\n  for(i = firstActiveLink(psdata->cols->varmap); i != 0; i = nextActiveLink(psdata->cols->varmap, i))\n    if(is_binary(lp, i) && !SOS_is_member(lp->SOS, 0, i)) {\n      /* Make sure we have an all-binary, unit-coefficient row */\n      je = mat->col_end[i];\n      item = 0;\n      for(jb = presolve_nextrow(psdata, i, &item); jb >= 0;\n          jb = presolve_nextrow(psdata, i, &item)) {\n        jx = COL_MAT_ROWNR(jb);\n        if(COL_MAT_VALUE(jb) != 1)\n          break;\n      }\n\n      /* Add to list if we are Ok */\n      if(jb < 0) {\n        QS[n].int4.intval = i;\n        item = 0;\n        ii = presolve_nextrow(psdata, i, &item);\n        QS[n].int4.intpar1 = COL_MAT_ROWNR(ii);\n        ii = presolve_collength(psdata, i);\n        QS[n].int4.intpar2 = ii;\n        n++;\n      }\n    }\n  if(n <= 1) {\n    FREE(QS);\n    return( status );\n  }\n  QS_execute(QS, n, (findCompare_func *) compRedundant, NULL);\n\n  /* Let us start from the top of the list, going forward and looking\n    for the longest possible dominated column */\n  if(!allocREAL(lp, &colvalues, lp->rows + 1, TRUE) ||\n     !allocINT(lp, &coldel, lp->columns + 1, FALSE))\n    goto Finish;\n\n  for(ib = 0; ib < n; ib++) {\n\n    /* Get column and check if it was previously eliminated */\n    i = QS[ib].int4.intval;\n    if(i < 0)\n      continue;\n\n    /* Load the non-zero column values */\n    item = 0;\n    for(jb = presolve_nextrow(psdata, i, &item); jb >= 0;\n        jb = presolve_nextrow(psdata, i, &item)) {\n      jx = COL_MAT_ROWNR(jb);\n      colvalues[jx] = COL_MAT_VALUE(jb);\n    }\n\n    coldel[0] = 0;\n    for(ie = ib+1; ie < n; ie++) {\n\n      /* Insist on identical column lengths (sort is decending in column lengths) */\n      ii = QS[ib].int4.intpar2 - QS[ie].int4.intpar2;\n      if(ii != 0)\n        break;\n\n      /* Also insist on identical starting positions */\n      ii = QS[ib].int4.intpar1 - QS[ie].int4.intpar1;\n      if(ii != 0)\n        break;\n\n      /* Get column and check if it was previously eliminated */\n      ii = QS[ie].int4.intval;\n      if(ii < 0)\n        continue;\n\n      /* Also make sure that the variables have \"compatible\" bounds */\n#if 1\n      if((fabs(my_reldiff(lp->orig_lowbo[lp->rows + i], lp->orig_lowbo[lp->rows + ii])) > psdata->epsvalue) ||\n         (fabs(my_reldiff(lp->orig_upbo[lp->rows + i],  lp->orig_upbo[lp->rows + ii] )) > psdata->epsvalue))\n        continue;\n#endif\n\n#ifdef Paranoia\n      if((QS[ib].int4.intpar1 > QS[ie].int4.intpar1) ||\n         ((QS[ib].int4.intpar1 == QS[ie].int4.intpar1) && (QS[ib].int4.intpar2 < QS[ie].int4.intpar2)))\n        report(lp, SEVERE, \"presolve_coldominance01: Invalid sorted column order\\n\");\n#endif\n\n      /* Loop over every column member to confirm that the candidate is\n        relatively identical in every position */\n      first = TRUE;\n      item = 0;\n      item2 = 0;\n      scale = 1;\n      for(jb = presolve_nextrow(psdata, ii, &item),\n          jj = presolve_nextrow(psdata, i, &item2); jb >= 0;\n          jb = presolve_nextrow(psdata, ii, &item),\n          jj = presolve_nextrow(psdata, i, &item2)) {\n        jx = COL_MAT_ROWNR(jb);\n        if(jx != COL_MAT_ROWNR(jj))\n          break;\n        if(first) {\n          first = !first;\n          scale = colvalues[jx] / COL_MAT_VALUE(jb);\n        }\n        else {\n          if(fabs(colvalues[jx] - scale * COL_MAT_VALUE(jb)) > psdata->epsvalue)\n            break;\n        }\n        /* Also make sure we have a compatible RHS (since this version of the\n          dominance logic only applies to \"sets\") */\n        rhsval = scale*lp->orig_rhs[jx] - 1.0;\n        /* if((rhsval < 0) || (rhsval > 1 + psdata->epsvalue)) */\n        if(fabs(rhsval) > psdata->epsvalue)\n          break;\n      }\n\n      /* \"We have contact\" */\n      if(jb < 0) {\n        coldel[++coldel[0]] = ii;\n        QS[ie].int4.intval = -ii;\n      }\n    }\n\n    /* Find the dominant column and delete / fix the others;\n       if there is a tie, simply delete the second candidate */\n    ii = i;\n    for(jb = 1; jb <= coldel[0]; jb++) {\n      jx = coldel[jb];\n      if(lp->orig_obj[jx] < lp->orig_obj[ii])\n        swapINT(&ii, &coldel[jb]);\n    }\n    for(jb = 1; jb <= coldel[0]; jb++) {\n      jx = coldel[jb];\n      if(!presolve_colfix(psdata, jx, lp->orig_lowbo[lp->rows+jx], TRUE, &iVarFixed)) {\n         status = presolve_setstatus(psdata, INFEASIBLE);\n         goto Finish;\n      }\n      presolve_colremove(psdata, jx, TRUE);\n    }\n\n    /* Clear the non-zero row values ahead of the next row candidate */\n    if(ib + 1 < n) {\n      ie = mat->col_end[i-1];\n      ii = mat->col_end[i];\n      for(; ie < ii; ie++)\n        colvalues[COL_MAT_ROWNR(ie)] = 0;\n    }\n  }\nFinish:\n  FREE(QS);\n  FREE(colvalues);\n  FREE(coldel);\n\n  (*nVarsFixed) += iVarFixed;\n  (*nSum)       += iVarFixed;\n\n  return( status );\n}\n#else\n\n/* DEVELOPMENT/TEST CODE FOR POSSIBLE REPLACEMENT OF SIMILAR FUNCTION IN lp_presolve.c */\n\n#define NATURAL int\n\nSTATIC int presolve_coldominance01(presolverec *psdata, NATURAL *nConRemoved, NATURAL *nVarsFixed, NATURAL *nSum)\n/* The current version of this routine eliminates binary variables\n   that are dominated via set coverage or unit knapsack constraints */\n{\n  lprec    *lp = psdata->lp;\n  MATrec   *mat = lp->matA;\n  NATURAL  i, ib, ie, jx, item, item2,\n           n = lp->int_vars, iVarFixed = 0, nrows = lp->rows,\n           *coldel = NULL;\n  int      jb, jj, ii,\n           status = RUNNING;\n  REAL     rhsval = 0.0,\n           *colvalues = NULL, *colobj = NULL;\n  LLrec    *sets = NULL;\n  UNIONTYPE QSORTrec *QS = (UNIONTYPE QSORTrec *) calloc(n+1, sizeof(*QS));\n\n  /* Check if we were able to obtain working memory */\n  if(QS == NULL)\n    return( status);\n  if(n == 0)\n    goto Finish;\n\n  /* Create list of set coverage and knapsack constraints */\n  createLink(nrows, &sets, NULL);\n  for(i = firstActiveLink(psdata->rows->varmap); i != 0; i = nextActiveLink(psdata->rows->varmap, i)) {\n    if((lp->orig_rhs[i] < 0) || (psdata->rows->negcount[i] > 0))\n      continue;\n    item = 0;\n    for(jb = presolve_nextcol(psdata, i, &item); jb >= 0;\n        jb = presolve_nextcol(psdata, i, &item)) {\n      jx = ROW_MAT_COLNR(jb);\n      if(!is_binary(lp, jx))\n        break;\n      rhsval = ROW_MAT_VALUE(jb) - 1;\n      if(fabs(rhsval) > lp->epsvalue)\n        break;\n    }\n    if(jb < 0)\n      setLink(sets, i);\n  }\n  if(countActiveLink(sets) == 0)\n    goto Finish;\n\n  /* A column dominates another binary variable column with the following criteria:\n      1) The relative matrix non-zero entries are identical\n      2) The relative objective coefficient is worse than the other;\n         if the OF coefficients are identical, we can delete an arbitrary variable */\n  n = 0;\n  for(i = firstActiveLink(psdata->cols->varmap); i != 0; i = nextActiveLink(psdata->cols->varmap, i))\n    if(is_binary(lp, i) && !SOS_is_member(lp->SOS, 0, i)) {\n      /* Make sure the column is member of at least one set */\n      item = 0;\n      for(jb = presolve_nextrow(psdata, i, &item); jb >= 0;\n          jb = presolve_nextrow(psdata, i, &item)) {\n        jx = COL_MAT_ROWNR(jb);\n        if(isActiveLink(sets, jx))\n          break;\n      }\n\n      /* Add to list if set membership test is Ok */\n      if(jb >= 0) {\n        QS[n].int4.intval = i;\n        item = 0;\n        ii = presolve_nextrow(psdata, i, &item);\n        QS[n].int4.intpar1 = COL_MAT_ROWNR(ii);\n        ii = presolve_collength(psdata, i);\n        QS[n].int4.intpar2 = ii;\n        n++;\n      }\n    }\n  if(n <= 1) {\n    FREE(QS);\n    return( status );\n  }\n  QS_execute(QS, n, (findCompare_func *) compRedundant, NULL);\n\n  /* Let us start from the top of the list, going forward and looking\n    for the longest possible dominated column */\n  if(!allocREAL(lp, &colvalues, nrows + 1, TRUE) ||\n     !allocREAL(lp, &colobj, n + 1, FALSE) ||\n     !allocINT(lp, &coldel, n + 1, FALSE))\n    goto Finish;\n\n  for(ib = 0; ib < n; ib++) {\n\n    /* Get column and check if it was previously eliminated */\n    i = QS[ib].int4.intval;\n    if(!isActiveLink(psdata->cols->varmap, i))\n      continue;\n\n    /* Load the non-zero column values */\n    item = 0;\n    for(jb = presolve_nextrow(psdata, i, &item); jb >= 0;\n        jb = presolve_nextrow(psdata, i, &item)) {\n      jx = COL_MAT_ROWNR(jb);\n      colvalues[jx] = COL_MAT_VALUE(jb);\n    }\n\n    /* Store data for current column */\n    coldel[0] = 1;\n    coldel[1] = i;\n    colobj[1] = lp->orig_obj[i];\n\n    /* Loop over all other columns to see if they have equal constraint coefficients */\n    for(ie = ib+1; ie < n; ie++) {\n\n      /* Check if this column was previously eliminated */\n      ii = QS[ie].int4.intval;\n      if(!isActiveLink(psdata->cols->varmap, ii))\n        continue;\n\n      /* Insist on identical column lengths (sort is decending in column lengths) */\n      ii = QS[ib].int4.intpar2 - QS[ie].int4.intpar2;\n      if(ii != 0)\n        break;\n\n      /* Also insist on identical starting positions */\n      ii = QS[ib].int4.intpar1 - QS[ie].int4.intpar1;\n      if(ii != 0)\n        break;\n\n      /* Get column and check if it was previously eliminated */\n      ii = QS[ie].int4.intval;\n\n#ifdef Paranoia\n      if((QS[ib].int4.intpar1 > QS[ie].int4.intpar1) ||\n         ((QS[ib].int4.intpar1 == QS[ie].int4.intpar1) && (QS[ib].int4.intpar2 < QS[ie].int4.intpar2)))\n        report(lp, SEVERE, \"presolve_coldominance01: Invalid sorted column order\\n\");\n#endif\n\n      /* Loop over every column member to confirm that the candidate is identical in every row;\n         we also compute the minimal set order */\n      rhsval = lp->infinite;\n      item = 0;\n      item2 = 0;\n      for(jb = presolve_nextrow(psdata, ii, &item),\n          jj = presolve_nextrow(psdata, i, &item2); jb >= 0;\n          jb = presolve_nextrow(psdata, ii, &item),\n          jj = presolve_nextrow(psdata, i, &item2)) {\n        jx = COL_MAT_ROWNR(jb);\n        if(jx != COL_MAT_ROWNR(jj))\n          break;\n        if(isActiveLink(sets, jx))\n          SETMIN(rhsval, lp->orig_rhs[jx]);\n      }\n\n      /* \"We have contact\" */\n      if(jb < 0) {\n        coldel[++coldel[0]] = ii;\n        colobj[coldel[0]] = lp->orig_obj[ii];\n      }\n    }\n\n    /* Find the dominant columns, fix and delete the others */\n    if(coldel[0] > 1) {\n      qsortex(colobj+1, coldel[0], 0, sizeof(*colobj), FALSE, compareREAL, coldel+1, sizeof(*coldel));\n      /* if(rhsval+lp->epsvalue < lp->infinite) { */\n        jb = (NATURAL) (rhsval+lp->epsvalue);\n        /* printf(\"%f / %d\\n\", rhsval, jb); */\n        for(jb++; jb <= coldel[0]; jb++) {\n          jx = coldel[jb];\n          if(!presolve_colfix(psdata, jx, lp->orig_lowbo[nrows+jx], TRUE, &iVarFixed)) {\n            status = presolve_setstatus(psdata, INFEASIBLE);\n            goto Finish;\n          }\n          presolve_colremove(psdata, jx, TRUE);\n        }\n      /*} */\n    }\n\n    /* Clear the non-zero row values ahead of the next row candidate */\n    if(ib + 1 < n) {\n      ie = mat->col_end[i-1];\n      ii = mat->col_end[i];\n      for(; ie < ii; ie++)\n        colvalues[COL_MAT_ROWNR(ie)] = 0;\n    }\n  }\nFinish:\n  freeLink(&sets);\n  FREE(QS);\n  FREE(colvalues);\n  FREE(coldel);\n  FREE(colobj);\n\n  (*nVarsFixed) += iVarFixed;\n  (*nSum)       += iVarFixed;\n\n  return( status );\n}\n\n#endif\n\nSTATIC int presolve_aggregate(presolverec *psdata, int *nConRemoved, int *nVarsFixed, int *nSum)\n/* This routine combines compatible or identical columns */\n{\n  lprec    *lp = psdata->lp;\n  MATrec   *mat = lp->matA;\n  MYBOOL   first;\n  int      i, ii, ib, ie, ix, n, jb, je, jx, jj, item, item2,\n           *coldel = NULL, status = RUNNING, iVarFixed = 0;\n  REAL     scale, *colvalues = NULL;\n  UNIONTYPE QSORTrec *QScand = (UNIONTYPE QSORTrec *) calloc(lp->columns+1, sizeof(*QScand));\n\n  /* Check if we were able to obtain working memory */\n  if(QScand == NULL)\n    return( status);\n\n  /* Obtain the list of qualifying columns to be sorted */\n  n = 0;\n  for(i = firstActiveLink(psdata->cols->varmap); i != 0; i = nextActiveLink(psdata->cols->varmap, i))\n    if(!is_semicont(lp, i) && !SOS_is_member(lp->SOS, 0, i)) {\n      QScand[n].int4.intval = i;\n      item = 0;\n      ii = presolve_nextrow(psdata, i, &item);\n      QScand[n].int4.intpar1 = COL_MAT_ROWNR(ii);\n      ii = presolve_collength(psdata, i);\n      QScand[n].int4.intpar2 = ii;\n      n++;\n    }\n  if(n <= 1) {\n    FREE(QScand);\n    return( status );\n  }\n  QS_execute(QScand, n, (findCompare_func *) compRedundant, NULL);\n\n  /* Let us start from the top of the list, going forward and looking\n    for the longest possible identical column */\n  if(!allocREAL(lp, &colvalues, lp->rows + 1, TRUE) ||\n     !allocINT(lp, &coldel, lp->columns + 1, FALSE))\n    goto Finish;\n\n  for(ib = 0; ib < n; ib++) {\n\n    /* Get column and check if it was previously eliminated */\n    i = QScand[ib].int4.intval;\n    if(i < 0)\n      continue;\n\n    /* Load the non-zero column values of this active/reference column */\n    item = 0;\n    for(jb = presolve_nextrow(psdata, i, &item); jb >= 0;\n        jb = presolve_nextrow(psdata, i, &item)) {\n      jx = COL_MAT_ROWNR(jb);\n      colvalues[jx] = COL_MAT_VALUE(jb);\n    }\n\n    coldel[0] = 0;\n    for(ie = ib+1; ie < n; ie++) {\n\n      /* Insist on identical column lengths (sort is decending in column lengths) */\n      ii = QScand[ib].int4.intpar2 - QScand[ie].int4.intpar2;\n      if(ii != 0)\n        break;\n\n      /* Also insist on identical starting positions */\n      ii = QScand[ib].int4.intpar1 - QScand[ie].int4.intpar1;\n      if(ii != 0)\n        break;\n\n      /* Get column and check if it was previously eliminated */\n      ii = QScand[ie].int4.intval;\n      if(ii < 0)\n        continue;\n\n      /* Loop over every column member to confirm that the candidate is\n        relatively identical in every position */\n      first = TRUE;\n      item = 0;\n      item2 = 0;\n      scale = 1;\n      for(jb = presolve_nextrow(psdata, ii, &item),\n          jj = presolve_nextrow(psdata, i, &item2); jb >= 0;\n          jb = presolve_nextrow(psdata, ii, &item),\n          jj = presolve_nextrow(psdata, i, &item2)) {\n        jx = COL_MAT_ROWNR(jb);\n        if(jx != COL_MAT_ROWNR(jj))\n          break;\n        if(first) {\n          first = !first;\n          scale = colvalues[jx] / COL_MAT_VALUE(jb);\n        }\n        else {\n          if(fabs(colvalues[jx] - scale * COL_MAT_VALUE(jb)) > psdata->epsvalue)\n            break;\n        }\n      }\n\n      /* \"We have contact\", store the column in the aggregation list */\n      if(jb < 0) {\n        coldel[++coldel[0]] = ii;\n        QScand[ie].int4.intval = -ii;\n      }\n    }\n\n    /* Sort the aggregation list if we have aggregation candidates */\n    if(coldel[0] > 1) {\n      REAL     of, ofelim, fixvalue;\n      MYBOOL   isint;\n      UNIONTYPE QSORTrec *QSagg = (UNIONTYPE QSORTrec *) calloc(coldel[0], sizeof(*QSagg));\n\n      for(jb = 1; jb <= coldel[0]; jb++) {\n        ii = jb - 1;\n        QSagg[ii].pvoidint2.intval = coldel[jb];\n        QSagg[ii].pvoidint2.ptr    = (void *) lp;\n      }\n      QS_execute(QSagg, coldel[0], (findCompare_func *) compAggregate, NULL);\n\n      /* Process columns with identical OF coefficients */\n      jb = 0;\n      while((status == RUNNING) && (jb < coldel[0])) {\n        ii = QSagg[jb].pvoidint2.intval;\n        of = lp->orig_obj[ii];\n        isint = is_int(lp, ii);\n        je = jb + 1;\n        while((status == RUNNING) && (je < coldel[0]) &&\n              (fabs(lp->orig_obj[ix = QSagg[je].pvoidint2.intval] - of) < psdata->epsvalue)) {\n           /* We now have two columns with equal OFs; the following cases are possible:\n\n             1) The first column has Inf upper bound, which means that it can\n                \"absorb\" compatible columns, which are then fixed at the appropriate\n                bounds (or zero in case of free variables).\n             2) The first column has a -Inf lower bound, and further columns are\n                Inf upper bounds, which means steps towards forming a free variable\n                can be made.\n             3) The first column is a non-Inf upper bound, in which case the bounds\n                are summed into a helper variable and the variable simply deleted.\n                The deleted variables' value are allocated/distributed via a simple\n                linear programming routine at postsolve.\n\n             In the current version of this code, we only handle case 1. */\n          if(is_int(lp, ix) == isint) {\n            ofelim = lp->orig_obj[ix];\n            if(of == 0)\n              scale = 1;\n            else\n              scale = ofelim / of;\n\n            if(my_infinite(lp, lp->orig_upbo[lp->rows+ii])) { /* Case 1 (recipe.mps) */\n              if(is_unbounded(lp, ix))\n                fixvalue = 0;\n              else if(ofelim < 0)\n                fixvalue = lp->orig_upbo[lp->rows+ix];\n              else\n                fixvalue = lp->orig_lowbo[lp->rows+ix];\n              if(my_infinite(lp, fixvalue))\n                status = presolve_setstatus(psdata, UNBOUNDED);\n              else if(!presolve_colfix(psdata, ix, fixvalue, TRUE, &iVarFixed))\n                status = presolve_setstatus(psdata, INFEASIBLE);\n              else\n                presolve_colremove(psdata, ix, TRUE);\n            }\n\n            else if(my_infinite(lp, lp->orig_lowbo[lp->rows+ii])) { /* Case 2 */\n              /* Do nothing */\n            }\n\n            else {                                            /* Case 3 */\n#if 0\n              /* Do nothing */\n#else\n              if(ofelim >= 0) {\n                fixvalue = lp->orig_lowbo[lp->rows+ix];\n                lp->orig_upbo[lp->rows+ii] += scale * (lp->orig_upbo[lp->rows+ix] - fixvalue);\n              }\n              else {\n                fixvalue = lp->orig_upbo[lp->rows+ix];\n                lp->orig_upbo[lp->rows+ii] -= scale * (fixvalue - lp->orig_lowbo[lp->rows+ix]);\n              }\n              if(my_infinite(lp, fixvalue))\n                status = presolve_setstatus(psdata, UNBOUNDED);\n              else if(!presolve_colfix(psdata, ix, fixvalue, TRUE, &iVarFixed))\n                status = presolve_setstatus(psdata, INFEASIBLE);\n              else\n                presolve_colremove(psdata, ix, TRUE);\n#ifdef xxParanoia\n              if(presolve_rowlengthdebug(psdata) > 0)\n                report(lp, SEVERE, \"presolve_aggregate: Invalid row count\\n\");\n#endif\n              psdata->forceupdate = TRUE;\n#endif\n            }\n          }\n          je++;\n        }\n        jb = je;\n      }\n      FREE(QSagg);\n    }\n\n    /* Clear the non-zero row values ahead of the next row candidate */\n    if(ib + 1 < n) {\n      ie = mat->col_end[i-1];\n      ii = mat->col_end[i];\n      for(; ie < ii; ie++)\n        colvalues[COL_MAT_ROWNR(ie)] = 0;\n    }\n  }\nFinish:\n  FREE(QScand);\n  FREE(colvalues);\n  FREE(coldel);\n\n  (*nVarsFixed) += iVarFixed;\n  (*nSum)       += iVarFixed;\n\n  return( status );\n}\n\nSTATIC int presolve_makesparser(presolverec *psdata, int *nCoeffChanged, int *nConRemove, int *nVarFixed, int *nSum)\n{\n  lprec    *lp = psdata->lp;\n  MATrec   *mat = lp->matA;\n  MYBOOL   chsign;\n  int      i, ii, ib, ix, k, n, jb, je, jl, jjb, jje, jjl, jx, jjx, item, itemEQ,\n           *nzidx = NULL, status = RUNNING, iObjChanged = 0, iCoeffChanged = 0, iConRemove = 0;\n  REAL     test, ratio, value, valueEQ, *valptr;\n  LLrec    *EQlist = NULL;\n  UNIONTYPE QSORTrec *QS = (UNIONTYPE QSORTrec *) calloc(lp->rows, sizeof(*QS));\n\n  /* Check if we were able to obtain working memory */\n  if((QS == NULL) || (psdata->rows->varmap->count == 0) || (psdata->EQmap->count == 0))\n    return( status);\n\n  /* Sort rows in 1) increasing order of start index, 2) decreasing length, and\n     3) non-equalities (i.e. equalities last) */\n  n = 0;\n  for(i = firstActiveLink(psdata->rows->varmap); i != 0; i = nextActiveLink(psdata->rows->varmap, i)) {\n    k = presolve_rowlength(psdata, i);\n    if(k >= 2) {\n      item = 0;\n      ii = presolve_nextcol(psdata, i, &item);\n#ifdef Paranoia\n      if((ii < 0) || (item == 0)) {\n        report(lp, SEVERE, \"presolve_makesparser: Unexpected zero-length row %d\\n\", i);\n        continue;\n      }\n#endif\n      QS[n].int4.intval  = my_chsign(is_constr_type(lp, i, EQ), i);\n      QS[n].int4.intpar1 = ROW_MAT_COLNR(ii);\n      QS[n].int4.intpar2 = k;\n      n++;\n    }\n  }\n  if(n <= 1) {\n    FREE(QS);\n    return( status );\n  }\n  QS_execute(QS, n, (findCompare_func *) compSparsity, NULL);\n\n  /* Create associated sorted map of indeces to equality constraints;\n     note that we need to have a unit offset for compatibility. */\n  allocINT(lp, &nzidx, lp->columns + 1, FALSE);\n  createLink(lp->rows, &EQlist, NULL);\n  for(ib = 0; ib < n; ib++) {\n    i = QS[ib].int4.intval;\n    if(i < 0)\n      appendLink(EQlist, ib + 1);\n  }\n\n  /* Loop over all equality masks */\n  for(ix = firstActiveLink(EQlist); ix != 0; ) {\n\n    /* Get row starting and ending positions of the mask */\n    ii = abs(QS[ix-1].int4.intval);\n    jjb = QS[ix-1].int4.intpar1;\n    jje = presolve_lastcol(psdata, ii);\n    jje = ROW_MAT_COLNR(jje);\n    jjl = QS[ix-1].int4.intpar2;\n\n    /* Scan the OF */\n    i = 0;\n    chsign = is_chsign(lp, i);\n    test = ratio = 0.0;\n    itemEQ = 0;\n    nzidx[0] = 0;\n    while(((jjx = presolve_nextcol(psdata, ii, &itemEQ)) >= 0) && /*(itemEQ > 0) && */\n           (fabs(test-ratio) < psdata->epsvalue)) {\n      valueEQ = ROW_MAT_VALUE(jjx);\n      if(valueEQ == 0)\n        continue;\n      k = ROW_MAT_COLNR(jjx);\n      value = lp->orig_obj[k];\n      if(fabs(value) < psdata->epsvalue)\n        break;\n      if(ratio == 0.0) {\n        test = ratio = value / valueEQ;\n      }\n      else\n        test = value / valueEQ;\n      /* Store nz index */\n      nzidx[++nzidx[0]] = k;\n    }\n\n    /* We were successful if the equality was completely traversed; we will\n      then zero-out the OF coefficients and update the constant term. */\n    if((itemEQ == 0) && (nzidx[0] > 0) && (fabs(test-ratio) < psdata->epsvalue)) {\n      for(k = 1; k <= nzidx[0]; k++) {\n        /* We should add recovery data for the zero'ed coefficient here */\n        jx = nzidx[k];\n        value = lp->orig_obj[jx];\n        lp->orig_obj[jx] = 0.0;\n        /* Update counts */\n        value = my_chsign(chsign, value);\n        if(value < 0) {\n          psdata->rows->negcount[i]--;\n          psdata->cols->negcount[jx]--;\n        }\n        else {\n          psdata->rows->plucount[i]--;\n          psdata->cols->plucount[jx]--;\n        }\n        iObjChanged++;\n      }\n      value = ratio * lp->orig_rhs[ii];\n      presolve_adjustrhs(psdata, i, value, psdata->epsvalue);\n    }\n\n    /* Scan for compatible constraints that can be masked for sparsity elimination */\n    for(ib = 1; ib < ix; ib++) {\n\n      /* Get row starting and ending positions of the target constraint */\n      i  = abs(QS[ib-1].int4.intval);\n      jb = QS[ib-1].int4.intpar1;\n      je = presolve_lastcol(psdata, i);\n      je = ROW_MAT_COLNR(je);\n      jl = QS[ib-1].int4.intpar2;\n\n      /* Check if there is a window mismatch */\n      if((jjb < jb) || (jje > je) || (jjl > jl))\n        goto NextEQ;\n\n      /* We have a window match; now check if there is a (scalar) member-by-member\n        match as well.  We approach this in the following manner:\n          1) Get first (or next) member of active equality\n          2) Loop to matching member in the target constraint, but abandon if no match\n          3) Set ratio if this is the first match, otherwise compare ratio and abandon\n             on mismatch\n          4) Go to 1) of there are more elements in the active equality\n          5) Proceed to do sparsity elimination if we were successful. */\n      chsign = is_chsign(lp, i);\n      test = ratio = 0.0;\n      itemEQ = 0;\n      item = 0;\n      nzidx[0] = 0;\n      while(((jjx = presolve_nextcol(psdata, ii, &itemEQ)) >= 0) && /*(itemEQ > 0) &&*/\n             (fabs(test-ratio) < psdata->epsvalue)) {\n        valueEQ = ROW_MAT_VALUE(jjx);\n        if(valueEQ == 0)\n          continue;\n        jx = 0;\n        jjx = ROW_MAT_COLNR(jjx);\n        for(k = presolve_nextcol(psdata, i, &item);\n            (jx < jjx) && (item > 0);\n            k = presolve_nextcol(psdata, i, &item)) {\n          jx = ROW_MAT_COLNR(k);\n          /* Do we have a column index match? */\n          if(jx == jjx) {\n            value = ROW_MAT_VALUE(k);\n            /* Abandon if we have a zero value */\n            if(value == 0)\n              goto NextEQ;\n            if(ratio == 0.0) {\n              test = ratio = value / valueEQ;\n            }\n            else\n              test = value / valueEQ;\n           /* Store nz index */\n            nzidx[++nzidx[0]] = k;\n            break;\n          }\n          /* Give up matching if there is overshooting */\n          else if(jx > jjx)\n            goto NextEQ;\n        }\n      }\n\n      /* We were successful if the equality was completely traversed */\n      if((itemEQ == 0) && (nzidx[0] > 0) && (fabs(test-ratio) < psdata->epsvalue)) {\n\n        /* Check if we have found parametrically indentical constraints */\n        if(presolve_rowlength(psdata, i) == presolve_rowlength(psdata,ii)) {\n\n          value = lp->orig_rhs[i];\n          valueEQ = lp->orig_rhs[ii];\n\n          /* Are they both equalities? */\n          if(is_constr_type(lp, i, EQ)) {\n            /* Determine applicable ratio for the RHS */\n            if(fabs(valueEQ) < psdata->epsvalue) {\n              if(fabs(value) < psdata->epsvalue)\n                test = ratio;\n              else\n                test = lp->infinite;\n            }\n            else\n              test = value / valueEQ;\n            /* Check for infeasibility */\n            if(fabs(test-ratio) > psdata->epsvalue) {\n              report(lp, NORMAL, \"presolve_sparser: Infeasibility of relatively equal constraints %d and %d\\n\",\n                                 i, ii);\n              status = presolve_setstatus(psdata, INFEASIBLE);\n              goto Finish;\n            }\n            /* Otherwise we can delete a redundant constraint */\n            else {\n              removeLink(EQlist, i);\n              presolve_rowremove(psdata, i, TRUE);\n              MEMCOPY(&QS[ib-1], &QS[ib], n-ib);\n              n--;\n              iConRemove++;\n            }\n          }\n          /* ... if not, then delete the inequality, since the equality dominates */\n          else {\n            /* First verify feasibility of the RHS */\n            if((value+psdata->epsvalue < valueEQ) ||\n               (value-get_rh_range(lp, i)-psdata->epsvalue > valueEQ)) {\n              report(lp, NORMAL, \"presolve_sparser: Infeasibility of relatively equal RHS values for %d and %d\\n\",\n                                 i, ii);\n              status = presolve_setstatus(psdata, INFEASIBLE);\n              goto Finish;\n            }\n            presolve_rowremove(psdata, i, TRUE);\n            MEMCOPY(&QS[ib-1], &QS[ib], n-ib);\n            n--;\n            iConRemove++;\n          }\n        }\n\n        /* Otherwise zero-out the target constraint coefficients and update the RHS */\n        else {\n          for(k = 1; k <= nzidx[0]; k++) {\n            /* We should add recovery data for the zero'ed coefficient here */\n            jjx = nzidx[k];\n            jx = ROW_MAT_COLNR(jjx);\n            valptr = &ROW_MAT_VALUE(jjx);\n            value  = *valptr;\n            *valptr = 0.0;\n            /* Update counts */\n            value = my_chsign(chsign, value);\n            if(value < 0) {\n              psdata->rows->negcount[i]--;\n              psdata->cols->negcount[jx]--;\n            }\n            else {\n              psdata->rows->plucount[i]--;\n              psdata->cols->plucount[jx]--;\n            }\n            iCoeffChanged++;\n          }\n          value = ratio * lp->orig_rhs[ii];\n          presolve_adjustrhs(psdata, i, value, psdata->epsvalue);\n        }\n      }\n\n    }\n    /* Get next equality index */\nNextEQ:\n    ix = nextActiveLink(EQlist, ix);\n  }\n\nFinish:\n  FREE(QS);\n  freeLink(&EQlist);\n  FREE(nzidx);\n\n  /* Let us condense the matrix if we modified the constraint matrix */\n  if(iCoeffChanged > 0) {\n    mat->row_end_valid = FALSE;\n    mat_zerocompact(mat);\n    presolve_validate(psdata, TRUE);\n#ifdef PresolveForceUpdateMax\n    mat_computemax(mat /* , FALSE */);\n#endif\n    psdata->forceupdate = TRUE;\n  }\n\n  (*nConRemove)    += iConRemove;\n  (*nCoeffChanged) += iCoeffChanged + iObjChanged;\n  (*nSum)          += iCoeffChanged + iObjChanged + iConRemove;\n\n  return( status );\n}\n\nSTATIC int presolve_SOS1(presolverec *psdata, int *nCoeffChanged, int *nConRemove, int *nVarFixed, int *nSOS, int *nSum)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   candelete, SOS_GUBactive = FALSE;\n  int      iCoeffChanged = 0, iConRemove = 0, iSOS = 0,\n           i,ix,iix, j,jx,jjx, status = RUNNING;\n  REAL     Value1;\n  MATrec   *mat = lp->matA;\n\n  for(i = lastActiveLink(psdata->rows->varmap); i > 0; ) {\n    candelete = FALSE;\n    Value1 = get_rh(lp, i);\n    jx = get_constr_type(lp, i);\n    if((Value1 == 1) && (presolve_rowlength(psdata, i) >= MIN_SOS1LENGTH) &&\n       ((SOS_GUBactive && (jx != GE)) || (!SOS_GUBactive && (jx == LE)))) {\n      jjx = mat->row_end[i-1];\n      iix = mat->row_end[i];\n      for(; jjx < iix; jjx++) {\n        j = ROW_MAT_COLNR(jjx);\n        if(!isActiveLink(psdata->cols->varmap, j))\n          continue;\n        if(!is_binary(lp, j) || (ROW_MAT_VALUE(jjx) != 1))\n          break;\n      }\n      if(jjx >= iix) {\n        char SOSname[16];\n\n        /* Define a new SOS instance */\n        ix = SOS_count(lp) + 1;\n        sprintf(SOSname, \"SOS_%d\", ix);\n        ix = add_SOS(lp, SOSname, 1, ix, 0, NULL, NULL);\n        if(jx == EQ)\n          SOS_set_GUB(lp->SOS, ix, TRUE);\n        Value1 = 0;\n        jjx = mat->row_end[i-1];\n        for(; jjx < iix; jjx++) {\n          j = ROW_MAT_COLNR(jjx);\n          if(!isActiveLink(psdata->cols->varmap, j))\n            continue;\n          Value1 += 1;\n          append_SOSrec(lp->SOS->sos_list[ix-1], 1, &j, &Value1);\n        }\n        candelete = TRUE;\n        iSOS++;\n      }\n    }\n\n    /* Get next row and do the deletion of the previous, if indicated */\n    ix = i;\n    i = prevActiveLink(psdata->rows->varmap, i);\n    if(candelete) {\n      presolve_rowremove(psdata, ix, TRUE);\n      iConRemove++;\n    }\n  }\n  if(iSOS)\n    report(lp, DETAILED, \"presolve_SOS1: Converted %5d constraints to SOS1.\\n\", iSOS);\n  clean_SOSgroup(lp->SOS, (MYBOOL) (iSOS > 0));\n\n  (*nCoeffChanged) += iCoeffChanged;\n  (*nConRemove)    += iConRemove;\n  (*nSOS)          += iSOS;\n  (*nSum)          += iCoeffChanged+iConRemove+iSOS;\n\n  return( status );\n}\n\nSTATIC int presolve_boundconflict(presolverec *psdata, int baserowno, int colno)\n{\n  REAL   Value1, Value2;\n  lprec  *lp = psdata->lp;\n  MATrec *mat = lp->matA;\n  int    ix, item = 0,\n         status = RUNNING;\n\n  if(baserowno <= 0) do {\n    ix = presolve_nextrow(psdata, colno, &item);\n    if(ix < 0)\n      return( status );\n    baserowno = COL_MAT_ROWNR(ix);\n  } while(presolve_rowlength(psdata, baserowno) != 1);\n  Value1 = get_rh_upper(lp, baserowno),\n  Value2 = get_rh_lower(lp, baserowno);\n\n  if(presolve_singletonbounds(psdata, baserowno, colno, &Value2, &Value1, NULL)) {\n    int iix;\n    item = 0;\n    for(ix = presolve_nextrow(psdata, colno, &item);\n        ix >= 0; ix = presolve_nextrow(psdata, colno, &item)) {\n      iix = COL_MAT_ROWNR(ix);\n      if((iix != baserowno) &&\n         (presolve_rowlength(psdata, iix) == 1) &&\n         !presolve_altsingletonvalid(psdata, iix, colno, Value2, Value1)) {\n        status = presolve_setstatus(psdata, INFEASIBLE);\n        break;\n      }\n    }\n  }\n  else\n    status = presolve_setstatus(psdata, INFEASIBLE);\n  return( status );\n}\n\nSTATIC int presolve_columns(presolverec *psdata, int *nCoeffChanged, int *nConRemove, int *nVarFixed, int *nBoundTighten, int *nSum)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   candelete, isOFNZ, unbounded,\n           probefix = is_presolve(lp, PRESOLVE_PROBEFIX),\n#if 0\n           probereduce = is_presolve(lp, PRESOLVE_PROBEREDUCE),\n#endif\n           colfixdual = is_presolve(lp, PRESOLVE_COLFIXDUAL);\n  int      iCoeffChanged = 0, iConRemove = 0, iVarFixed = 0, iBoundTighten = 0,\n           status = RUNNING, ix, j, countNZ, item;\n  REAL     Value1;\n\n  for(j = firstActiveLink(psdata->cols->varmap); (j != 0) && (status == RUNNING); ) {\n\n    /* Don't presolve members SOS'es */\n    if(SOS_is_member(lp->SOS, 0, j)) {\n      j = nextActiveLink(psdata->cols->varmap, j);\n      continue;\n    }\n\n    /* Initialize */\n    countNZ = presolve_collength(psdata, j);\n    isOFNZ  = isnz_origobj(lp, j);\n    Value1  = get_lowbo(lp, j);\n    unbounded = is_unbounded(lp, j);\n\n    /* Clear unnecessary semicont-definitions */\n    if((lp->sc_vars > 0) && (Value1 == 0) && is_semicont(lp, j))\n      set_semicont(lp, j, FALSE);\n\n    candelete = FALSE;\n    item = 0;\n    ix = lp->rows + j;\n\n    /* Check if the variable is unused */\n    if((countNZ == 0) && !isOFNZ) {\n      if(Value1 != 0)\n        report(lp, DETAILED, \"presolve_columns: Eliminated unused variable %s\\n\",\n                              get_col_name(lp,j));\n      candelete = TRUE;\n    }\n\n    /* Check if the variable has a cost, but is not limited by constraints */\n    else if((countNZ == 0) && isOFNZ) {\n      if(lp->orig_obj[j] < 0)\n        Value1 = get_upbo(lp, j);\n      if(fabs(Value1) >= lp->infinite) {\n        report(lp, DETAILED, \"presolve_columns: Unbounded variable %s\\n\",\n                              get_col_name(lp,j));\n        status = presolve_setstatus(psdata, UNBOUNDED);\n      }\n      else {\n        /* Fix the value at its best bound */\n        report(lp, DETAILED, \"presolve_columns: Eliminated trivial variable %s fixed at %g\\n\",\n                              get_col_name(lp,j), Value1);\n        candelete = TRUE;\n      }\n    }\n\n    /* Check if the variable can be eliminated because it is fixed */\n    else if(isOrigFixed(lp, ix)) {\n      if(countNZ > 0) {\n        status = presolve_boundconflict(psdata, -1, j);\n        if(status != RUNNING)\n          break;\n      }\n      report(lp, DETAILED, \"presolve_columns: Eliminated variable %s fixed at %g\\n\",\n                            get_col_name(lp,j), Value1);\n      candelete = TRUE;\n    }\n\n#if 0\n    /* Merge OF-constraint column doubleton in equality constraint (if it has\n      not been captured by the singleton free variable rule above) */\n    else if((countNZ == 1) && isOFNZ &&\n             ((i = presolve_nextrow(psdata, j, &item)) >= 0) &&\n             is_constr_type(lp, i = COL_MAT_ROWNR(i), EQ)) {\n      MATrec *mat = lp->matA;\n\n      /* Merge the constraint into the OF */\n      Value1 = lp->orig_obj[j] / get_mat(lp, i, j);\n      for(jx = mat->row_end[i-1]; jx < mat->row_end[i]; jx++) {\n        jjx = ROW_MAT_COLNR(jx);\n        lp->orig_obj[jjx] -= Value1 * ROW_MAT_VALUE(jx);\n      }\n      Value2 = lp->orig_rhs[i];\n      presolve_adjustrhs(psdata, 0, Value1 * Value2, 0.0);\n\n      /* Verify feasibility */\n      Value2 /= get_mat(lp, i, j);\n      if((Value2 < get_lowbo(lp, j)) || (Value2 > get_upbo(lp, j))) {\n        status = presolve_setstatus(psdata, INFEASIBLE);\n        break;\n      }\n\n      /* Do column (and flag row) deletion */\n      presolve_rowremove(psdata, i, TRUE);\n      psdata->forceupdate = TRUE;\n      iConRemove++;\n      candelete = TRUE;\n    }\n#endif\n    /* Look for opportunity to fix column based on the dual */\n    else if(colfixdual && presolve_colfixdual(psdata, j, &Value1, &status)) {\n      if(my_infinite(lp, Value1)) {\n        report(lp, DETAILED, \"presolve_columns: Unbounded variable %s\\n\",\n                              get_col_name(lp,j));\n        status = presolve_setstatus(psdata, UNBOUNDED);\n      }\n      else {\n        /* Fix the value at its best bound */\n        report(lp, DETAILED, \"presolve_columns: Eliminated dual-zero variable %s fixed at %g\\n\",\n                              get_col_name(lp,j), Value1);\n        candelete = TRUE;\n      }\n    }\n\n    /* Do probing of binary variables to see if we can fix them */\n    else if(probefix && is_binary(lp, j) &&\n            presolve_probefix01(psdata, j, &Value1)) {\n      report(lp, DETAILED, \"presolve_columns: Fixed binary variable %s at %g\\n\",\n                            get_col_name(lp,j), Value1);\n      candelete = TRUE;\n    }\n#if 0\n    /* Do probing of binary variables to see if we can tighten their coefficients */\n    else if(probereduce && is_binary(lp, j) &&\n            (ix = presolve_probetighten01(psdata, j) > 0)) {\n      report(lp, DETAILED, \"presolve_columns: Tightened coefficients for binary variable %s in %d rows\\n\",\n                            get_col_name(lp,j), ix);\n      iCoeffChanged += ix;\n      psdata->forceupdate = TRUE;\n    }\n#endif\n\n    /* Perform fixing and deletion, if indicated */\n    if(candelete) {\n\n      /* If we have a SOS1 member variable fixed at a non-zero value, then we\n        must fix the other member variables at zero and delete the SOS(es) */\n      if((Value1 != 0) && SOS_is_member(lp->SOS, 0, j)) {\n        ix = iVarFixed;\n        if(!presolve_fixSOS1(psdata, j, Value1, &iConRemove, &iVarFixed))\n          status = presolve_setstatus(psdata, INFEASIBLE);\n        if(iVarFixed > ix)\n          psdata->forceupdate = TRUE;\n        break;\n      }\n      else {\n        if(!presolve_colfix(psdata, j, Value1, TRUE, &iVarFixed)) {\n          status = presolve_setstatus(psdata, INFEASIBLE);\n          break;\n        }\n        j = presolve_colremove(psdata, j, TRUE);\n      }\n    }\n    else\n      j = nextActiveLink(psdata->cols->varmap, j);\n  }\n\n  /* Remove any \"hanging\" empty row and columns */\n  if(status == RUNNING)\n    status = presolve_shrink(psdata, &iConRemove, &iVarFixed);\n\n  (*nCoeffChanged) += iCoeffChanged;\n  (*nConRemove)    += iConRemove;\n  (*nVarFixed)     += iVarFixed;\n  (*nBoundTighten) += iBoundTighten;\n  (*nSum)          += iCoeffChanged+iConRemove+iVarFixed+iBoundTighten;\n\n  return( status );\n}\n\nSTATIC int presolve_freeandslacks(presolverec *psdata, int *nCoeffChanged, int *nConRemove, int *nVarFixed, int *nSum)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   isOFNZ, unbounded,\n           impliedfree = is_presolve(lp, PRESOLVE_IMPLIEDFREE),\n           impliedslack = is_presolve(lp, PRESOLVE_IMPLIEDSLK);\n  int      iCoeffChanged = 0, iConRemove = 0, iVarFixed = 0,\n           status = RUNNING, i, ix, j, countNZ;\n  REAL     coeff_bl, coeff_bu;\n  MATrec   *mat = lp->matA;\n\n  if(impliedfree || impliedslack)\n  for(j = firstActiveLink(psdata->cols->varmap); j != 0; ) {\n\n    /* Check and initialize */\n    if((presolve_collength(psdata, j) != 1) ||\n       is_int(lp, j) || is_semicont(lp, j) ||\n       !presolve_candeletevar(psdata, j)) {\n      j = nextActiveLink(psdata->cols->varmap, j);\n      continue;\n    }\n    ix = 0;\n    i = COL_MAT_ROWNR(presolve_nextrow(psdata, j, &ix));\n    isOFNZ  = isnz_origobj(lp, j);\n    countNZ = presolve_rowlength(psdata, i);\n    coeff_bu = get_upbo(lp, j);\n    coeff_bl = get_lowbo(lp, j);\n    unbounded = my_infinite(lp, coeff_bl) && my_infinite(lp, coeff_bu);\n    ix = lp->rows + j;\n\n    /* Eliminate singleton free variable and its associated constraint */\n    if(impliedfree && unbounded &&\n       presolve_impliedcolfix(psdata, i, j, TRUE)) {\n      report(lp, DETAILED, \"presolve_freeandslacks: Eliminated free variable %s and row %s\\n\",\n                            get_col_name(lp, j), get_row_name(lp, i));\n      presolve_rowremove(psdata, i, TRUE);\n      iConRemove++;\n      j = presolve_colremove(psdata, j, TRUE);\n      iVarFixed++;\n    }\n\n    /* Check for implied slack variable in equality constraint */\n    else if(impliedslack &&\n             (countNZ > 1) &&\n             is_constr_type(lp, i, EQ) &&\n             presolve_impliedcolfix(psdata, i, j, FALSE)) {\n      report(lp, DETAILED, \"presolve_freeandslacks: Eliminated implied slack variable %s via row %s\\n\",\n                            get_col_name(lp, j), get_row_name(lp, i));\n      psdata->forceupdate = TRUE;\n      j = presolve_colremove(psdata, j, TRUE);\n      iVarFixed++;\n    }\n\n    /* Check for implied (generalized) slack variable in inequality constraint */\n    else if(impliedslack && !isOFNZ &&\n             my_infinite(lp, coeff_bu) &&                 /* Consider removing this test */\n#if 0 /* Force zero-bounded implicit slack  */\n             (coeff_bl == 0)) &&\n#else\n             !my_infinite(lp, coeff_bl) &&\n#endif\n             (countNZ > 1) &&\n             !is_constr_type(lp, i, EQ))  {\n      REAL *target,\n            ValueA   = COL_MAT_VALUE(presolve_lastrow(psdata, j));\n#if 0\n      coeff_bu = get_rh_upper(lp, i);\n      coeff_bl = get_rh_lower(lp, i);\n      if(!presolve_singletonbounds(psdata, i, j, &coeff_bl, &coeff_bu, &ValueA)) {\n        status = presolve_setstatus(psdata, INFEASIBLE);\n        break;\n      }\n#endif\n      if((coeff_bl != 0) && !my_infinite(lp, coeff_bl) && !my_infinite(lp, coeff_bu))\n        coeff_bu -= coeff_bl;\n\n      /* If the coefficient is negative, reduce the lower bound / increase range */\n      if(ValueA > 0) {\n        target = &lp->orig_upbo[i];\n        if(!my_infinite(lp, *target)) {\n          if(my_infinite(lp, coeff_bu)) {\n            *target = lp->infinite;\n            psdata->forceupdate = TRUE;\n          }\n          else {\n            *target += ValueA * coeff_bu;\n            *target = presolve_roundrhs(lp, *target, FALSE);\n          }\n        }\n      }\n      /* Otherwise see if the upper bound should be changed */\n      else {\n        target = &lp->orig_rhs[i];\n        if(my_infinite(lp, coeff_bu) || my_infinite(lp, *target)) {\n          /* Do we suddenly find that the constraint becomes redundant? (e226.mps) */\n          if(my_infinite(lp, lp->orig_upbo[i])) {\n            presolve_rowremove(psdata, i, TRUE);\n            iConRemove++;\n          }\n          /* Or does the upper bound of a ranged constraint become Inf? */\n          else {\n            *target -= lp->orig_upbo[i];\n            *target = -(*target);\n            mat_multrow(mat, i, -1);\n            lp->orig_upbo[i] = lp->infinite;\n            psdata->forceupdate = TRUE;\n          }\n        }\n        else {\n          *target -= ValueA * coeff_bu;\n          *target = presolve_roundrhs(lp, *target, FALSE);\n        }\n      }\n      presolve_colfix(psdata, j, coeff_bl, TRUE, &iVarFixed);\n      report(lp, DETAILED, \"presolve_freeandslacks: Eliminated duplicate slack variable %s via row %s\\n\",\n                            get_col_name(lp, j), get_row_name(lp, i));\n      j = presolve_colremove(psdata, j, TRUE);\n    }\n\n    /* Go to next column */\n    else\n      j = nextActiveLink(psdata->cols->varmap, j);\n  }\n\n  (*nCoeffChanged) += iCoeffChanged;\n  (*nConRemove)    += iConRemove;\n  (*nVarFixed)     += iVarFixed;\n  (*nSum)          += iCoeffChanged+iConRemove+iVarFixed;\n\n  return( status );\n}\n\nSTATIC int presolve_preparerows(presolverec *psdata, int *nBoundTighten, int *nSum)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   impliedfree = is_presolve(lp, PRESOLVE_IMPLIEDFREE),\n           tightenbounds  = is_presolve(lp, PRESOLVE_BOUNDS);\n  int      iRangeTighten = 0, iBoundTighten = 0, status = RUNNING, i, j;\n  REAL     losum, upsum, lorhs, uprhs, epsvalue = psdata->epsvalue;\n  MATrec   *mat = lp->matA;\n\n  for(i = lastActiveLink(psdata->rows->varmap); i > 0; i = prevActiveLink(psdata->rows->varmap, i)) {\n\n   /* First identify any full row infeasibilities */\n    j = presolve_rowlengthex(psdata, i);\n#ifdef Paranoia\n    if(!presolve_testrow(psdata, nextActiveLink(psdata->rows->varmap, i))) {\n#else\n    if((j > 1) && !psdata->forceupdate && !presolve_rowfeasible(psdata, i, FALSE)) {\n#endif\n      status = presolve_setstatus(psdata, INFEASIBLE);\n      break;\n    }\n\n    /* Do bound (LHS) or constraint range (RHS) tightening if we will later identify\n      implied free variables (tends to produce degeneracy otherwise) */\n    if(impliedfree && (j > 1) && mat_validate(mat)){\n\n      /* Look for opportunity to tighten constraint bounds (and check for feasibility again) */\n      presolve_range(lp, i, psdata->rows, &losum, &upsum);\n      lorhs = get_rh_lower(lp, i);\n      uprhs = get_rh_upper(lp, i);\n      if((losum > MIN(upsum, uprhs)+epsvalue) ||\n         (upsum < MAX(losum, lorhs)-epsvalue)) {\n        report(lp, NORMAL, \"presolve_preparerows: Variable bound / constraint value infeasibility in row %s.\\n\",\n                           get_row_name(lp, i));\n        status = presolve_setstatus(psdata, INFEASIBLE);\n        break;\n      }\n\n      if(losum > lorhs+epsvalue) {\n        set_rh_lower(lp, i, presolve_roundrhs(lp, losum, TRUE));\n        iRangeTighten++;\n      }\n      if(upsum < uprhs-epsvalue) {\n        set_rh_upper(lp, i, presolve_roundrhs(lp, upsum, FALSE));\n        iRangeTighten++;\n      }\n    }\n\n    /* Seek to tighten bounds on individual variables */\n    if(tightenbounds && mat_validate(mat)) {\n#if 1\n      if(j > 1)\n        status = presolve_rowtighten(psdata, i, &iBoundTighten, FALSE);\n#else\n      if((MIP_count(lp) > 0) && (j > 1))\n        status = presolve_rowtighten(psdata, i, &iBoundTighten, TRUE);\n#endif\n    }\n\n    /* Look for opportunity to convert ranged constraint to equality-type */\n    if(!is_constr_type(lp, i, EQ) && (get_rh_range(lp, i) < epsvalue)) {\n      presolve_setEQ(psdata, i);\n      iRangeTighten++;\n    }\n  }\n\n  psdata->forceupdate |= (MYBOOL) (iBoundTighten > 0);\n  (*nBoundTighten) += iBoundTighten+iRangeTighten;\n  (*nSum)          += iBoundTighten+iRangeTighten;\n\n  return( status );\n}\n\nSTATIC int presolve_rows(presolverec *psdata, int *nCoeffChanged, int *nConRemove, int *nVarFixed, int *nBoundTighten, int *nSum)\n{\n  lprec    *lp = psdata->lp;\n  MYBOOL   candelete;\n  int      iCoeffChanged = 0, iConRemove = 0, iVarFixed = 0, iBoundTighten = 0,\n           status = RUNNING, i,ix, j,jx, item;\n  REAL     Value1, Value2, losum, upsum, lorhs, uprhs, epsvalue = psdata->epsvalue;\n  MATrec   *mat = lp->matA;\n\n  for(i = lastActiveLink(psdata->rows->varmap); (i > 0) && (status == RUNNING); ) {\n\n    candelete = FALSE;\n\n   /* First identify any full row infeasibilities\n      Note: Handle singletons below to ensure that conflicting multiple singleton\n            rows with this variable do not provoke notice of infeasibility */\n    j = presolve_rowlengthex(psdata, i);\n    if((j > 1) &&\n       !psdata->forceupdate && !presolve_rowfeasible(psdata, i, FALSE)) {\n      status = presolve_setstatus(psdata, INFEASIBLE);\n      break;\n    }\n    presolve_range(lp, i, psdata->rows, &losum, &upsum);\n    lorhs = get_rh_lower(lp, i);\n    uprhs = get_rh_upper(lp, i);\n#ifdef Paranoia\n    if((losum>uprhs+epsvalue) || (upsum<lorhs-epsvalue)) {\n      status = presolve_setstatus(psdata, INFEASIBLE);\n      break;\n    }\n#endif\n\n    /* Delete empty rows */\n    if(j == 0)\n      candelete = TRUE;\n    else\n\n    /* Convert non-fixed row singletons to bounds */\n#if 0  /* Version that deletes bound-fixed columns in presolve_columns() */\n    if((j == 1) && (upsum-losum >= -epsvalue)) {\n#else  /* Version that deletes bound-fixed columns here */\n    if((j == 1) && (uprhs-lorhs >= -epsvalue)) {\n#endif\n      item = 0;\n      jx = presolve_nextcol(psdata, i, &item);\n      j = ROW_MAT_COLNR(jx);\n\n      /* Make sure we don't have conflicting other singleton rows with this variable */\n      Value1 = lp->infinite;\n      Value2 = -Value1;\n      if(presolve_collength(psdata, j) > 1)\n        status = presolve_boundconflict(psdata, i, j);\n      else if(is_constr_type(lp, i, EQ)) {\n        Value2 = ROW_MAT_VALUE(jx);\n        Value1 = lp->orig_rhs[i] / Value2;\n        if(Value2 < 0)\n          swapREAL(&losum, &upsum);\n        if((Value1 < losum / my_if(my_infinite(lp, losum), my_sign(Value2), Value2) - epsvalue) ||\n           (Value1 > upsum / my_if(my_infinite(lp, upsum), my_sign(Value2), Value2) + epsvalue))\n          status = presolve_setstatus(psdata, INFEASIBLE);\n        Value2 = Value1;\n      }\n\n      /* Proceed to fix and remove variable (if it is not a SOS member) */\n      if(status == RUNNING) {\n        if((fabs(Value2-Value1) < epsvalue) && (fabs(Value2) > epsvalue)) {\n          MYBOOL isSOS     = (MYBOOL) (SOS_is_member(lp->SOS, 0, j) != FALSE),\n                 deleteSOS = isSOS && presolve_candeletevar(psdata, j);\n          if((Value1 != 0) && deleteSOS) {\n            if(!presolve_fixSOS1(psdata, j, Value1, &iConRemove, &iVarFixed))\n              status = presolve_setstatus(psdata, INFEASIBLE);\n              psdata->forceupdate = TRUE;\n          }\n          else {\n            if(!presolve_colfix(psdata, j, Value1, (MYBOOL) !isSOS, NULL))\n              status = presolve_setstatus(psdata, INFEASIBLE);\n            else if(isSOS && !deleteSOS)\n              iBoundTighten++;\n            else {\n              presolve_colremove(psdata, j, TRUE);\n              iVarFixed++;\n            }\n          }\n        }\n        else\n          status = presolve_colsingleton(psdata, i, j, &iBoundTighten);\n      }\n      if(status == INFEASIBLE) {\n        break;\n      }\n      if(psdata->forceupdate != AUTOMATIC) {\n        /* Store dual recovery information and code for deletion */\n        presolve_storeDualUndo(psdata, i, j);\n        candelete = TRUE;\n      }\n    }\n\n    /* Delete non-empty rows and variables that are completely determined at zero */\n    else if((j > 0)                            /* Only examine non-empty rows, */\n       && (fabs(lp->orig_rhs[i]) < epsvalue)   /* .. and the current RHS is zero, */\n       && ((psdata->rows->plucount[i] == 0) ||\n           (psdata->rows->negcount[i] == 0))   /* .. and the parameter signs are all equal, */\n       && (psdata->rows->pluneg[i] == 0)       /* .. and no (quasi) free variables, */\n       && (is_constr_type(lp, i, EQ)\n#ifdef FindImpliedEqualities\n           || (fabs(lorhs-upsum) < epsvalue)   /* Convert to equalities */\n           || (fabs(uprhs-losum) < epsvalue)   /* Convert to equalities */\n#endif\n          )\n          ) {\n\n      /* Delete the columns we can delete */\n      status = presolve_rowfixzero(psdata, i, &iVarFixed);\n\n      /* Then delete the row, which is redundant */\n      if(status == RUNNING)\n        candelete = TRUE;\n    }\n\n\n    /* Check if we have a constraint made redundant through bounds on individual\n       variables; such constraints are often referred to as \"forcing constraints\" */\n    else if((losum >= lorhs-epsvalue) &&\n             (upsum <= uprhs+epsvalue)) {\n\n      /* Check if we can also fix all the variables */\n      if(fabs(losum-upsum) < epsvalue) {\n        item = 0;\n        jx = presolve_nextcol(psdata, i, &item);\n        while((status == RUNNING) && (jx >= 0)) {\n          j = ROW_MAT_COLNR(jx);\n          Value1 = get_lowbo(lp, j);\n          if(presolve_colfix(psdata, j, Value1, TRUE, &iVarFixed)) {\n            presolve_colremove(psdata, j, TRUE);\n            iVarFixed++;\n            jx = presolve_nextcol(psdata, i, &item);\n          }\n          else\n            status = presolve_setstatus(psdata, INFEASIBLE);\n        }\n      }\n      candelete = TRUE;\n    }\n\n    /* Get next row and do the deletion of the previous, if indicated */\n    ix = i;\n    i = prevActiveLink(psdata->rows->varmap, i);\n    if(candelete) {\n      presolve_rowremove(psdata, ix, TRUE);\n      iConRemove++;\n    }\n  }\n\n  /* Remove any \"hanging\" empty row and columns */\n  if(status == RUNNING)\n    status = presolve_shrink(psdata, &iConRemove, &iVarFixed);\n\n  (*nCoeffChanged) += iCoeffChanged;\n  (*nConRemove)    += iConRemove;\n  (*nVarFixed)     += iVarFixed;\n  (*nBoundTighten) += iBoundTighten;\n  (*nSum)          += iCoeffChanged+iConRemove+iVarFixed+iBoundTighten;\n\n  return( status );\n}\n\n/* Top level presolve routine */\nSTATIC int presolve(lprec *lp)\n{\n  int    status = RUNNING,\n         i, j = 0, jx = 0, jjx = 0, k, oSum,\n         iCoeffChanged = 0, iConRemove = 0, iVarFixed = 0, iBoundTighten = 0, iSOS = 0, iSum = 0,\n         nCoeffChanged = 0, nConRemove = 0, nVarFixed = 0, nBoundTighten = 0, nSOS = 0, nSum = 0;\n  REAL   Value1, Value2, initrhs0 = lp->orig_rhs[0];\n  presolverec *psdata = NULL;\n  MATrec *mat = lp->matA;\n\n#if 0\n  lp->do_presolve     = PRESOLVE_ROWS;\n  report(lp, IMPORTANT, \"presolve: Debug override of presolve setting to %d\\n\", lp->do_presolve);\n#endif\n\n /* Lock the variable mapping arrays and counts ahead of any row/column\n    deletion or creation in the course of presolve, solvelp or postsolve */\n  if(!lp->varmap_locked)\n    varmap_lock(lp);\n\n /* Check if we have already done presolve */\n  mat_validate(mat);\n  if(lp->wasPresolved) {\n    if(SOS_count(lp) > 0) {\n      SOS_member_updatemap(lp->SOS);\n      make_SOSchain(lp, (MYBOOL) ((lp->do_presolve & PRESOLVE_LASTMASKMODE) != PRESOLVE_NONE));\n    }\n    if((lp->solvecount > 1) && (lp->bb_level < 1) &&\n       ((lp->scalemode & SCALE_DYNUPDATE) != 0))\n      auto_scale(lp);\n    if(!lp->basis_valid) {\n      crash_basis(lp);\n      report(lp, DETAILED, \"presolve: Had to repair broken basis.\\n\");\n    }\n    lp->timepresolved = timeNow();\n    return(status);\n  }\n\n  /* Produce original model statistics (do hoops to produce correct stats if we have SOS'es) */\n  i = SOS_count(lp);\n  if(i > 0) {\n    SOS_member_updatemap(lp->SOS);\n    lp->sos_vars = SOS_memberships(lp->SOS, 0);\n  }\n  REPORT_modelinfo(lp, TRUE, \"SUBMITTED\");\n  report(lp, NORMAL, \" \\n\");\n  if(i > 0)\n    lp->sos_vars = 0;\n\n  /* Finalize basis indicators; if no basis was created earlier via\n     set_basis or crash_basis then simply set the default basis. */\n  if(!lp->basis_valid)\n    lp->var_basic[0] = AUTOMATIC; /* Flag that we are presolving */\n\n#if 0\nwrite_lp(lp, \"test_in.lp\");    /* Write to lp-formatted file for debugging */\n/*write_mps(lp, \"test_in.mps\");*/  /* Write to lp-formatted file for debugging */\n#endif\n\n  /* Update inf norms and check for potential factorization trouble */\n  mat_computemax(mat /*, FALSE */);\n#if 0\n  Value1 = fabs(lp->negrange);\n  if(is_obj_in_basis(lp) && (mat->dynrange < Value1) && vec_computeext(lp->orig_obj, 1, lp->columns, TRUE, &i, &j)) {\n\n    /* Compute relative scale metric */\n    Value2 = fabs(lp->orig_obj[j]/lp->orig_obj[i]) / mat->dynrange;\n    if(Value2 < 1.0)\n      Value2 = 1.0 / Value2;\n\n    /* Determine if we should alert modeler and possibly move the OF out of the coefficient matrix */\n    if((Value2 > Value1)           /* Case with extreme scale difference */\n#if 1\n        || (mat->dynrange == 1.0)  /* Case where we have an all-unit coefficient matrix, possibly totally unimodular */\n#endif\n      )\n      if((lp->simplex_strategy & SIMPLEX_DYNAMIC) > 0) {\n        clear_action(&lp->algopt, ALGOPT_OBJINBASIS);\n        report(lp, NORMAL, \"Moved objective function out of the basis matrix to enhance factorization accuracy.\\n\");\n      }\n      else if(mat->dynrange > 1.0)\n        report(lp, IMPORTANT, \"Warning: Objective/matrix coefficient magnitude differences will cause inaccuracy!\\n\");\n  }\n#endif\n\n  /* Do traditional simple presolve */\n  yieldformessages(lp);\n  if((lp->do_presolve & PRESOLVE_LASTMASKMODE) == PRESOLVE_NONE) {\n    mat_checkcounts(mat, NULL, NULL, TRUE);\n    i = 0;\n  }\n  else {\n\n    if(lp->full_solution == NULL)\n      allocREAL(lp, &lp->full_solution, lp->sum_alloc+1, TRUE);\n\n    /* Identify infeasible SOS'es prior to any pruning */\n    j = 0;\n    for(i = 1; i <= SOS_count(lp); i++) {\n      k = SOS_infeasible(lp->SOS, i);\n      if(k > 0) {\n        presolverec psdata;\n\n        psdata.lp = lp;\n        report(lp, NORMAL, \"presolve: Found SOS %d (type %d) to be range-infeasible on variable %d\\n\",\n                            i, SOS_get_type(lp->SOS, i), k);\n        status = presolve_setstatus(&psdata, INFEASIBLE);\n        j++;\n      }\n    }\n    if(j > 0)\n      goto Finish;\n\n    /* Create and initialize the presolve data structures */\n    psdata = presolve_init(lp);\n\n    /* Reentry point for the outermost, computationally expensive presolve loop */\n    psdata->outerloops = 0;\n    do {\n      psdata->outerloops++;\n      iCoeffChanged = 0;\n      iConRemove    = 0;\n      iVarFixed     = 0;\n      iBoundTighten = 0;\n      iSOS          = 0;\n      oSum          = nSum;\n\n      /* Do the middle elimination loop */\n      do {\n        psdata->middleloops++;\n        nSum += iSum;\n        iSum = 0;\n\n        /* Accumulate constraint bounds based on bounds on individual variables. */\n        j = 0;\n        while(presolve_statuscheck(psdata, &status) && psdata->forceupdate) {\n          psdata->forceupdate = FALSE;\n          /* Update sums, but limit iteration count to avoid possible\n            \"endless\" loops with only marginal bound improvements */\n          if(presolve_updatesums(psdata) && (j < MAX_PSBOUNDTIGHTENLOOPS)) {\n            /* Do row preparation useful for subsequent column and row presolve operations */\n            if((psdata->outerloops == 1) && (psdata->middleloops == 1))\n              status = presolve_preparerows(psdata, &iBoundTighten, &iSum);\n            nBoundTighten += iBoundTighten;\n            iBoundTighten  = 0;\n            nSum          += iSum;\n            iSum           = 0;\n            j++;\n            if(status != RUNNING)\n              report(lp, NORMAL, \"presolve: Break after bound tightening iteration %d.\\n\", j);\n          }\n        }\n        if(status != RUNNING)\n          break;\n\n        /* Do the relatively cheap innermost elimination loop */\n        do {\n\n          psdata->innerloops++;\n          nSum += iSum;\n          iSum = 0;\n\n          /* Eliminate empty rows, convert row singletons to bounds,\n            tighten bounds, and remove always satisfied rows */\n          if(presolve_statuscheck(psdata, &status) &&\n             is_presolve(lp, PRESOLVE_ROWS))\n            status = presolve_rows(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iBoundTighten, &iSum);\n\n          /* Eliminate empty or fixed columns (including trivial OF column singletons) */\n          if(presolve_statuscheck(psdata, &status) &&\n             is_presolve(lp, PRESOLVE_COLS))\n            status = presolve_columns(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iBoundTighten, &iSum);\n\n          /* Presolve SOS'es if possible (always do this) */\n          if(presolve_statuscheck(psdata, &status))\n            status = presolve_redundantSOS(psdata, &iBoundTighten, &iSum);\n\n        } while((status == RUNNING) && (iSum > 0));\n        if(status != RUNNING)\n          break;\n\n        /* Merge compatible similar rows; loop backwards over every row */\n        if(presolve_statuscheck(psdata, &status) &&\n           (psdata->outerloops == 1) && (psdata->middleloops <= MAX_PSMERGELOOPS) &&\n           is_presolve(lp, PRESOLVE_MERGEROWS))\n          status = presolve_mergerows(psdata, &iConRemove, &iSum);\n\n        /* Eliminate dominated rows */\n        if(presolve_statuscheck(psdata, &status) &&\n           is_presolve(lp, PRESOLVE_ROWDOMINATE))\n          presolve_rowdominance(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iSum);\n\n        /* See if we can convert some constraints to SOSes (only SOS1 handled) */\n        if(presolve_statuscheck(psdata, &status) && (MIP_count(lp) > 0) &&\n           is_presolve(lp, PRESOLVE_SOS))\n          status = presolve_SOS1(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iSOS, &iSum);\n\n        /* Eliminate dominated columns in set coverage models */\n        if(presolve_statuscheck(psdata, &status) && (lp->int_vars > 1) &&\n           is_presolve(lp, PRESOLVE_COLDOMINATE))\n          presolve_coldominance01(psdata, &iConRemove, &iVarFixed, &iSum);\n\n        /* Aggregate compatible columns */\n        if(presolve_statuscheck(psdata, &status) && /*TRUE ||*/\n           is_presolve(lp, PRESOLVE_AGGREGATE))\n          presolve_aggregate(psdata, &iConRemove, &iVarFixed, &iSum);\n\n        /* Eliminate free variables and implied slacks */\n        if(presolve_statuscheck(psdata, &status) &&\n/*           !is_presolve(lp, PRESOLVE_ELIMEQ2) && */\n           is_presolve(lp, PRESOLVE_IMPLIEDSLK | PRESOLVE_IMPLIEDFREE))\n          status = presolve_freeandslacks(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iSum);\n\n      } while((status == RUNNING) && (iSum > 0));\n      if(status != RUNNING)\n        break;\n\n      /* Check if we can do elimination of rank-deficient equality constraints */\n      if(presolve_statuscheck(psdata, &status) && (psdata->EQmap->count > 1) &&\n         is_presolve(lp, PRESOLVE_LINDEP)) {\n#if 0\n        REPORT_mat_mmsave(lp, \"A.mtx\", NULL, FALSE, \"Constraint matrix A\");\n#endif\n        presolve_singularities(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iSum);\n      }\n\n      /* Eliminate variable and tighten bounds using 2-element EQs;\n        note that this involves modifying the coefficients of A and\n        can therefore be a slow operation. */\n      if(presolve_statuscheck(psdata, &status) &&\n         is_presolve(lp, PRESOLVE_ELIMEQ2)) {\n        jjx = 0;\n        do {\n          jjx += iSum;\n          status = presolve_elimeq2(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iSum);\n        } while((status == RUNNING) && (iSum > jjx));\n        iSum = jjx;\n\n#if 0\n        /* Eliminate free variables and implied slacks */\n        if(presolve_statuscheck(psdata, &status) &&\n           is_presolve(lp, PRESOLVE_IMPLIEDSLK | PRESOLVE_IMPLIEDFREE))\n          status = presolve_freeandslacks(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iSum);\n#endif\n      }\n\n      /* Increase A matrix sparsity by discovering common subsets using EQs */\n      if(presolve_statuscheck(psdata, &status) && (psdata->EQmap->count > 0) &&\n         is_presolve(lp, PRESOLVE_SPARSER))\n        status = presolve_makesparser(psdata, &iCoeffChanged, &iConRemove, &iVarFixed, &iSum);\n\n      /* Do GCD-based coefficient reductions (also does row scaling,\n        even if no rhs INT truncations are possible) */\n      if(presolve_statuscheck(psdata, &status) && (psdata->INTmap->count > 0) &&\n         is_presolve(lp, PRESOLVE_REDUCEGCD))\n        if(!presolve_reduceGCD(psdata, &iCoeffChanged, &iBoundTighten, &iSum))\n          status = presolve_setstatus(psdata, INFEASIBLE);\n\n      /* Simplify knapsack or set coverage models where OF coefficients are\n        duplicated in the constraints.  At the cost of adding helper columns, this\n        increases sparsity and facilitates identification of lower and upper bounds. */\n      if(presolve_statuscheck(psdata, &status) &&\n          is_presolve(lp, PRESOLVE_KNAPSACK)) {\n        i = iCoeffChanged;\n        status = presolve_knapsack(psdata, &iCoeffChanged);\n      }\n\n      /* Remove any \"hanging\" empty row and columns */\n      if(status == RUNNING)\n        status = presolve_shrink(psdata, &iConRemove, &iVarFixed);\n\n      nCoeffChanged += iCoeffChanged;\n      nConRemove    += iConRemove;\n      nVarFixed     += iVarFixed;\n      nBoundTighten += iBoundTighten;\n      nSOS          += iSOS;\n      nSum          += iSum;\n\n      iSum           = iConRemove + iVarFixed + iBoundTighten + iCoeffChanged;\n      if(iSum > 0)\n        report(lp, NORMAL, \"Presolve O:%d -> Reduced rows:%5d, cols:%5d --- changed bnds:%5d, Ab:%5d.\\n\",\n                           psdata->outerloops, iConRemove, iVarFixed, iBoundTighten, iCoeffChanged);\n\n   /* Do the outermost loop again if we were successful in this presolve sequences */\n    } while(presolve_statuscheck(psdata, &status) &&\n           (psdata->forceupdate || (oSum < nSum)) &&\n           (psdata->outerloops < get_presolveloops(lp)) &&\n           (psdata->rows->varmap->count+psdata->cols->varmap->count > 0));\n\n   /* Finalize presolve */\n#ifdef Paranoia\n    i = presolve_debugcheck(lp, psdata->rows->varmap, psdata->cols->varmap);\n    if(i > 0)\n      report(lp, SEVERE, \"presolve: %d internal consistency failure%s\\n\", i, my_plural_std(i));\n    if((SOS_count(lp) > 0) && !presolve_SOScheck(psdata))\n      report(lp, SEVERE, \"presolve: SOS sparse member mapping problem - part 1\\n\");\n#endif\n    /* Perform bound relaxation to reduce chance of degeneracy. */\n    if((status == RUNNING) && !is_presolve(lp, PRESOLVE_IMPLIEDFREE))\n      jjx = presolve_makefree(psdata);\n    else\n      jjx = 0;\n\n\n    /* Finalize the presolve */\n    if(!presolve_finalize(psdata))\n      report(lp, SEVERE, \"presolve: Unable to construct internal data representation\\n\");\n\n   /* Report summary information */\n    i = NORMAL;\n    iVarFixed  = lp->presolve_undo->orig_columns - psdata->cols->varmap->count;\n    iConRemove = lp->presolve_undo->orig_rows - psdata->rows->varmap->count;\n    if(nSum > 0)\n      report(lp, i, \"PRESOLVE             Elimination loops performed.......... O%d:M%d:I%d\\n\",\n                                  psdata->outerloops, psdata->middleloops, psdata->innerloops);\n    if(nVarFixed)\n      report(lp, i, \"            %8d empty or fixed variables............. %s.\\n\", nVarFixed, \"REMOVED\");\n    if(nConRemove)\n      report(lp, i, \"            %8d empty or redundant constraints....... %s.\\n\", nConRemove, \"REMOVED\");\n    if(nBoundTighten)\n      report(lp, i, \"            %8d bounds............................... %s.\\n\", nBoundTighten, \"TIGHTENED\");\n    if(nCoeffChanged)\n      report(lp, i, \"            %8d matrix coefficients.................. %s.\\n\", nCoeffChanged, \"CHANGED\");\n    if(jjx > 0)\n      report(lp, i, \"            %8d variables' final bounds.............. %s.\\n\", jjx, \"RELAXED\");\n    if(nSOS)\n      report(lp, i, \"            %8d constraints detected as SOS1......... %s.\\n\", nSOS, \"CONVERTED\");\n\n    /* Report optimality or infeasibility */\n    if(status == UNBOUNDED)\n      report(lp, NORMAL, \"%20s Solution status detected............. %s.\\n\", \"\", \"UNBOUNDED\");\n    else if(status == INFEASIBLE)\n      report(lp, NORMAL, \"%20s Solution status detected............. %s.\\n\", \"\", \"INFEASIBLE\");\n    else {\n      if(psdata->cols->varmap->count == 0)\n        Value1 = Value2 = lp->presolve_undo->fixed_rhs[0] -initrhs0;\n      else\n        presolve_rangeorig(lp, 0, psdata->rows, &Value1, &Value2, -initrhs0);\n      if((fabs(Value1 - Value2) < psdata->epsvalue) || (fabs(my_reldiff(Value1, Value2)) < psdata->epsvalue)) {\n        if((lp->rows == 0) && (lp->columns == 0)) {\n          status = PRESOLVED;\n          Value1 = my_chsign(is_maxim(lp), Value1);\n          lp->solution[0] = Value1;\n          lp->best_solution[0] = Value1;\n          lp->full_solution[0] = Value1;\n        }\n        report(lp, NORMAL, \"%20s OPTIMAL solution found............... %-g\", \"\", Value1);\n      }\n      else if((status == RUNNING) && (i >= NORMAL)) {\n        char lonum[20], upnum[20];\n        if(my_infinite(lp, Value1))\n          sprintf(lonum, \"%13s\", \"-Inf\");\n        else\n          sprintf(lonum, \"%+12g\", Value1);\n        if(my_infinite(lp, Value2))\n          sprintf(upnum, \"%-13s\", \"Inf\");\n        else\n          sprintf(upnum, \"%+-12g\", Value2);\n        report(lp, i,    \"%20s [ %s < Z < %s ]\\n\", \"\", lonum, upnum);\n      }\n\n      /* Update values for dual limit and best heuristic values */\n      if((MIP_count(lp) > 0) || (get_Lrows(lp) > 0)) {\n        if(is_maxim(lp)) {\n          SETMAX(lp->bb_heuristicOF, Value1);\n          SETMIN(lp->bb_limitOF, Value2);\n        }\n        else {\n          SETMIN(lp->bb_heuristicOF, Value2);\n          SETMAX(lp->bb_limitOF, Value1);\n        }\n      }\n    }\n    report(lp, NORMAL, \" \\n\");\n\n    /* Clean up (but save counts of constraint types for display later) */\n    j = psdata->LTmap->count;\n    jx = psdata->EQmap->count;\n    jjx = lp->rows - j - jx;\n    presolve_free(&psdata);\n\n  }\n\n  /* Signal that we are done presolving */\n  if((lp->usermessage != NULL) &&\n     ((lp->do_presolve & PRESOLVE_LASTMASKMODE) != 0) && (lp->msgmask & MSG_PRESOLVE))\n     lp->usermessage(lp, lp->msghandle, MSG_PRESOLVE);\n\n  /* Create master SOS variable list */\n  if(SOS_count(lp) > 0) {\n    /*SOS_member_updatemap(lp->SOS); */\n    make_SOSchain(lp, (MYBOOL) ((lp->do_presolve & PRESOLVE_LASTMASKMODE) != PRESOLVE_NONE));\n  }\n\n  /* Finalize model not identified as infeasible or unbounded */\n  if(status == RUNNING) {\n\n    /* Resolve GUBs */\n    if(is_bb_mode(lp, NODE_GUBMODE))\n      identify_GUB(lp, TRUE);\n\n#if 0\n    /* Mark rows containing hidden identity matrices so that supporting factorization\n      engines can use this structural information to boost efficiency */\n    if(is_algopt(lp, ALGOPT_COMPACTBPF))\n      lp->bfpoptimize = (MYBOOL) (assist_factorization(lp, ROWTYPE_LOGICAL,\n                                                       &lp->rowset1, &lp->rowno1) > 0);\n#endif\n\n    /* Scale the model based on current settings */\n    auto_scale(lp);\n\n    /* Crash the basis, if specified */\n    crash_basis(lp);\n\n    /* Produce presolved model statistics */\n    if(nConRemove+nVarFixed+nBoundTighten+nVarFixed+nCoeffChanged > 0) {\n      REPORT_modelinfo(lp, FALSE, \"REDUCED\");\n      if(nSum > 0) {\n        report(lp, NORMAL, \"Row-types:   %7d LE,          %7d GE,             %7d EQ.\\n\",\n                           j, jjx, jx);\n        report(lp, NORMAL, \" \\n\");\n      }\n    }\n  }\n\n  /* Optionally produce data on constraint classes */\n  if(lp->verbose > NORMAL) {\n    report(lp, NORMAL, \" \\n\");\n    REPORT_constraintinfo(lp, \"CONSTRAINT CLASSES\");\n    report(lp, NORMAL, \" \\n\");\n  }\n\nFinish:\n  lp->wasPresolved  = TRUE;\n  lp->timepresolved = timeNow();\n\n#if 0\n/*  write_mps(lp, \"test_out.mps\"); */ /* Must put here due to variable name mapping */\n  write_lp(lp, \"test_out.lp\");   /* Must put here due to variable name mapping */\n#endif\n#if 0\n  REPORT_debugdump(lp, \"testint2.txt\", FALSE);\n#endif\n\n  return( status );\n\n}\n\nSTATIC MYBOOL postsolve(lprec *lp, int status)\n{\n  /* Verify solution */\n  if(lp->lag_status != RUNNING) {\n    int itemp;\n\n    if(status == PRESOLVED)\n      status = OPTIMAL;\n\n    if((status == OPTIMAL) || (status == SUBOPTIMAL)) {\n      itemp = check_solution(lp, lp->columns, lp->best_solution,\n                                 lp->orig_upbo, lp->orig_lowbo, lp->epssolution);\n      if((itemp != OPTIMAL) && (lp->spx_status == OPTIMAL))\n        lp->spx_status = itemp;\n      else if((itemp == OPTIMAL) && ((status == SUBOPTIMAL) || (lp->spx_status == PRESOLVED)))\n        lp->spx_status = status;\n    }\n    else if(status != PRESOLVED) {\n      report(lp, NORMAL, \"lp_solve unsuccessful after %.0f iter and a last best value of %g\\n\",\n             (double) get_total_iter(lp), lp->best_solution[0]);\n      if(lp->bb_totalnodes > 0)\n        report(lp, NORMAL, \"lp_solve explored %.0f nodes before termination\\n\",\n               (double) get_total_nodes(lp));\n    }\n    else\n      lp->spx_status = OPTIMAL;\n\n    /* Only rebuild primal solution here, since the dual is only computed on request */\n    presolve_rebuildUndo(lp, TRUE);\n  }\n\n  /* Check if we can clear the variable map */\n  if(varmap_canunlock(lp))\n    lp->varmap_locked = FALSE;\n#if 0\n  REPORT_mat_mmsave(lp, \"basis.mtx\", NULL, FALSE);  /* Write the current basis matrix (no OF) */\n#endif\n\n  return( TRUE );\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_presolve.h",
    "content": "#ifndef HEADER_lp_presolve\n#define HEADER_lp_presolve\n\n#include \"lp_types.h\"\n#include \"lp_matrix.h\"\n\n/* -------------------------------------------------------------------------------------------- */\n/* Defines for various presolve options                                                         */\n/* -------------------------------------------------------------------------------------------- */\n\n#define MAX_PSMERGELOOPS                2                 /* Max loops to merge compatible constraints */\n#define MAX_PSLINDEPLOOPS               1   /* Max loops to detect linearly dependendent constraints */\n#define MAX_PSBOUNDTIGHTENLOOPS         5     /* Maximumn number of loops to allow bound tightenings */\n#define MIN_SOS1LENGTH                  4   /* Minimum length of a constraint for conversion to SOS1 */\n#if 1\n  #define PRESOLVE_EPSVALUE (0.1*lp->epsprimal)\n#else\n  #define PRESOLVE_EPSVALUE  lp->epsvalue\n#endif\n#define PRESOLVE_EPSPIVOT         1.0e-3        /* Looses robustness at values smaller than ~1.0e-3 */\n#define PRESOLVE_BOUNDSLACK           10                     /* Extra error recovery/tolerance margin */\n\n#define DoPresolveRounding              /* Use absolute and directed rounding (disable at own risk) */\n/*#define DoPresolveRelativeTest*/\n\n/*#define PresolveForceUpdateMax*/\n\n/*#define DualFeasibilityLogicEQ2*/              /* Add low-order feasibility/accuracy logic to elimEQ2 */\n#define DivisorIntegralityLogicEQ2                                   /* Always prefer integer divisors */\n#define FindImpliedEqualities                               /* Detect equalities (default is enabled) */\n#define Eq2Reldiff\n\n/*#define SavePresolveEliminated */        /* Enable to activate storage of eliminated matrix data */\n/*#define UseDualPresolve */                    /* Enable to use full dual information for presolve */\n\n\ntypedef struct _psrec\n{\n  LLrec *varmap;\n  int  **next;\n  int  *empty;\n  int  *plucount;\n  int  *negcount;\n  int  *pluneg;\n  int  *infcount;\n  REAL  *plulower;\n  REAL  *neglower;\n  REAL  *pluupper;\n  REAL  *negupper;\n  int  allocsize;\n} psrec;\n\ntypedef struct _presolverec\n{\n  psrec *rows;\n  psrec *cols;\n  LLrec *EQmap;\n  LLrec *LTmap;\n  LLrec *INTmap;\n  REAL  *pv_upbo;\n  REAL  *pv_lobo;\n  REAL  *dv_upbo;\n  REAL  *dv_lobo;\n  lprec *lp;\n  REAL  epsvalue;\n  REAL  epspivot;\n  int   innerloops;\n  int   middleloops;\n  int   outerloops;\n  int   nzdeleted;\n  MYBOOL forceupdate;\n} presolverec;\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\n\nSTATIC MYBOOL presolve_createUndo(lprec *lp);\nSTATIC MYBOOL presolve_rebuildUndo(lprec *lp, MYBOOL isprimal);\nSTATIC MYBOOL inc_presolve_space(lprec *lp, int delta, MYBOOL isrows);\nSTATIC MYBOOL presolve_setOrig(lprec *lp, int orig_rows, int orig_cols);\nSTATIC MYBOOL presolve_colfix(presolverec *psdata, int colnr, REAL newvalue, MYBOOL remove, int *tally);\nSTATIC MYBOOL presolve_fillUndo(lprec *lp, int orig_rows, int orig_cols, MYBOOL setOrig);\nSTATIC MYBOOL presolve_freeUndo(lprec *lp);\n\nSTATIC MYBOOL presolve_updatesums(presolverec *psdata);\n\nINLINE int presolve_nextrow(presolverec *psdata, int colnr, int *previtem);\nINLINE int presolve_nextcol(presolverec *psdata, int rownr, int *previtem);\n\nSTATIC presolverec *presolve_init(lprec *lp);\nSTATIC void presolve_free(presolverec **psdata);\nSTATIC int presolve_shrink(presolverec *psdata, int *nConRemove, int *nVarRemove);\nSTATIC void presolve_rowremove(presolverec *psdata, int rownr, MYBOOL allowcoldelete);\nSTATIC int presolve_colremove(presolverec *psdata, int colnr, MYBOOL allowrowdelete);\n\nSTATIC MYBOOL presolve_colfixdual(presolverec *psdata, int colnr, REAL *fixValue, int *status);\n\nINLINE int presolve_rowlength(presolverec *psdata, int rownr)\n{\n  int *items = psdata->rows->next[rownr];\n\n  if(items == NULL)\n    return( 0 );\n  else\n    return( items[0] );\n}\nINLINE int presolve_collength(presolverec *psdata, int colnr)\n{\n  int *items = psdata->cols->next[colnr];\n  if(items == NULL)\n    return( 0 );\n  else\n    return( items[0] );\n}\n\nSTATIC int presolve(lprec *lp);\nSTATIC MYBOOL postsolve(lprec *lp, int status);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_presolve */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_price.c",
    "content": "\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_report.h\"\n#include \"lp_pricePSE.h\"\n#include \"lp_price.h\"\n\n#if libBLAS > 0\n  #include \"myblas.h\"\n#endif\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* Simplex pricing utility module - w/interface for lp_solve v5.0+\n   -------------------------------------------------------------------------\n    Author:        Kjell Eikland\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      lp_lib.h, commonlib.h\n\n    Release notes:\n    v1.0.0  1 July 2004         Routines extracted from lp_lib.\n    v1.0.1 10 July 2004         Added comparison operators for determination\n                                of entering and leaving variables.\n                                Added routines for multiple and partial\n                                pricing and made corresponding changes to\n                                colprim and rowdual.\n    v1.0.2 20 August 2004       Implemented relative pivot size control in\n                                rowprim and rowdual.\n    v1.1.0 15 October 2004      Added dual long step logic.\n    v1.1.1 22 October 2004      Added bound sort order to variable selections.\n    v1.2.0 24 March 2005        Completed multiple pricing logic.\n   ------------------------------------------------------------------------- */\n\n\n/* Comparison operators for entering and leaving variables for both the primal and\n   dual simplexes.  The functions compare a candidate variable with an incumbent. */\nint CMP_CALLMODEL compareImprovementVar(const pricerec *current, const pricerec *candidate)\n{\n  register int   result = COMP_PREFERNONE;\n  register lprec *lp = current->lp;\n  register REAL  testvalue, margin = PREC_IMPROVEGAP;\n  int currentcolno, currentvarno = current->varno,\n      candidatecolno, candidatevarno = candidate->varno;\n  MYBOOL isdual = candidate->isdual;\n\n  if(isdual) {\n    candidatevarno = lp->var_basic[candidatevarno];\n    currentvarno   = lp->var_basic[currentvarno];\n  }\n  candidatecolno = candidatevarno - lp->rows;\n  currentcolno   = currentvarno - lp->rows;\n\n  /* Do pivot-based selection unless Bland's (first index) rule is active */\n  if(lp->_piv_rule_ != PRICER_FIRSTINDEX) {\n\n    MYBOOL candbetter;\n\n    /* Find the largest value - normalize in case of the dual, since\n       constraint violation is expressed as a negative number. */\n    /* Use absolute test for \"small numbers\", relative otherwise */\n    testvalue = candidate->pivot;\n    if(fabs(testvalue) < LIMIT_ABS_REL)\n      testvalue -= current->pivot;\n    else\n      testvalue = my_reldiff(testvalue, current->pivot);\n    if(isdual)\n      testvalue = -testvalue;\n\n    candbetter = (MYBOOL) (testvalue > 0);\n    if(candbetter) {\n      if(testvalue > margin)\n        result = COMP_PREFERCANDIDATE;\n    }\n#if 0 /* Give more opportunity to optimize on non-primary criteria */\n    else if (testvalue < -margin)\n#else /* Give reduced opportunity to optimize on non-primary criteria */\n    else if (testvalue < -lp->epsvalue)\n#endif\n      result = COMP_PREFERINCUMBENT;\n\n#ifdef UseSortOnBound\n      /* Extra selection criterion based on the variable's range;\n        variable with - DUAL: small bound out; PRIMAL: large bound in */\n    if(result == COMP_PREFERNONE) {\n      testvalue = lp->upbo[candidatevarno] - lp->upbo[currentvarno];\n      if(testvalue < -margin)\n        result = COMP_PREFERINCUMBENT;\n      else if(testvalue > margin)\n        result = COMP_PREFERCANDIDATE;\n      result = my_chsign(isdual, result);\n    }\n#endif\n\n#ifdef UseSortOnColumnLength\n    /* Prevent long columns from entering the basis */\n    if(result == COMP_PREFERNONE) {\n      if(candidatecolno > 0)\n        testvalue = mat_collength(lp->matA, candidatecolno) +\n                    (is_obj_in_basis(lp) && (lp->obj[candidatecolno] != 0) ? 1 : 0);\n      else\n        testvalue = 1;\n      if(currentcolno > 0)\n        testvalue -= mat_collength(lp->matA, currentcolno) +\n                     (is_obj_in_basis(lp) && (lp->obj[currentcolno] != 0) ? 1 : 0);\n      else\n        testvalue -= 1;\n      if(testvalue > 0)\n        result = COMP_PREFERINCUMBENT;\n      else if(testvalue < 0)\n        result = COMP_PREFERCANDIDATE;\n      result = my_chsign(isdual, result);\n    }\n#endif\n\n    /* Select absolute best if the non-primary criteria failed to separate */\n    if((result == COMP_PREFERNONE) && candbetter) {\n      result = COMP_PREFERCANDIDATE;\n      goto Finish;\n    }\n  }\n\n  /* Final tie-breakers */\n  if(result == COMP_PREFERNONE) {\n\n    /* Add randomization tie-braker */\n    if(lp->piv_strategy & PRICE_RANDOMIZE) {\n      result = my_sign(PRICER_RANDFACT - rand_uniform(lp, 1.0));\n      if(candidatevarno < currentvarno)\n        result = -result;\n    }\n\n    /* Resolve ties via index ordinal */\n    if(result == COMP_PREFERNONE) {\n      if(candidatevarno < currentvarno)\n        result = COMP_PREFERCANDIDATE;\n      else /* if(candidatevarno > currentvarno) */\n        result = COMP_PREFERINCUMBENT;\n      if(lp->_piv_left_)\n        result = -result;\n    }\n  }\n\nFinish:\n  return( result );\n\n}\n\nint CMP_CALLMODEL compareSubstitutionVar(const pricerec *current, const pricerec *candidate)\n{\n  register int    result = COMP_PREFERNONE;\n  register lprec  *lp = current->lp;\n  register REAL   testvalue = candidate->theta,\n                  margin = current->theta;\n  MYBOOL isdual = candidate->isdual, candbetter;\n  int    currentcolno, currentvarno = current->varno,\n         candidatecolno, candidatevarno = candidate->varno;\n\n  if(!isdual) {\n    candidatevarno = lp->var_basic[candidatevarno];\n    currentvarno   = lp->var_basic[currentvarno];\n  }\n  candidatecolno = candidatevarno - lp->rows;\n  currentcolno   = currentvarno - lp->rows;\n\n  /* Compute the ranking test metric. */\n  if(isdual) {\n    testvalue = fabs(testvalue);\n    margin    = fabs(margin);\n  }\n\n  /* Use absolute test for \"small numbers\", relative otherwise */\n  if(fabs(testvalue) < LIMIT_ABS_REL)\n    testvalue -= margin;\n  else\n    testvalue = my_reldiff(testvalue, margin);\n\n  /* Find if the new Theta is smaller or near equal (i.e. testvalue <= eps)\n     compared to the previous best; ties will be broken by pivot size or index\n     NB! The margin below is essential in maintaining primal/dual feasibility\n         during the primal/dual simplex, respectively.  Sometimes a small\n         value prevents the selection of a suitable pivot, thereby weakening\n         the numerical stability of some models */\n  margin = PREC_SUBSTFEASGAP;\n  candbetter = (MYBOOL) (testvalue < 0);\n  if(candbetter) {\n    if(testvalue < -margin)\n      result = COMP_PREFERCANDIDATE;\n  }\n  else if(testvalue > margin)\n    result = COMP_PREFERINCUMBENT;\n\n  /* Resolve a tie */\n  if(result == COMP_PREFERNONE) {\n    REAL currentpivot = fabs(current->pivot),\n         candidatepivot = fabs(candidate->pivot);\n\n    /* Handle first index / Bland's rule specially */\n    if(lp->_piv_rule_ == PRICER_FIRSTINDEX) {\n#if 1\n      /* Special secondary selection by pivot size (limited stability protection) */\n      margin = candidate->epspivot;\n      if((candidatepivot >= margin) && (currentpivot < margin))\n        result = COMP_PREFERCANDIDATE;\n#endif\n    }\n\n    else {\n\n      /* General secondary selection based on pivot size */\n#if 0\n      if(candidatepivot > MIN_STABLEPIVOT)\n        testvalue = my_reldiff(testvalue, currentpivot);\n      else\n#endif\n        testvalue = candidatepivot - currentpivot;\n      if(testvalue > margin)\n        result = COMP_PREFERCANDIDATE;\n      else if(testvalue < -margin)\n        result = COMP_PREFERINCUMBENT;\n\n#ifdef UseSortOnBound\n      /* Extra selection criterion based on the variable's range;\n        variable with - PRIMAL: small bound out; DUAL: large bound in */\n      if(result == COMP_PREFERNONE) {\n        testvalue = lp->upbo[candidatevarno] - lp->upbo[currentvarno];\n        if(testvalue < -margin)\n          result = COMP_PREFERCANDIDATE;\n        else if(testvalue > margin)\n          result = COMP_PREFERINCUMBENT;\n        result = my_chsign(isdual, result);\n      }\n#endif\n\n#ifdef UseSortOnColumnLength\n      /* Prevent long columns from entering the basis */\n      if(result == COMP_PREFERNONE) {\n        if(candidatecolno > 0)\n          testvalue = mat_collength(lp->matA, candidatecolno) +\n                      (is_obj_in_basis(lp) && (lp->obj[candidatecolno] != 0) ? 1 : 0);\n        else\n          testvalue = 1;\n        if(currentcolno > 0)\n          testvalue -= mat_collength(lp->matA, currentcolno) +\n                       (is_obj_in_basis(lp) && (lp->obj[currentcolno] != 0) ? 1 : 0);\n        else\n          testvalue -= 1;\n        if(testvalue > 0)\n          result = COMP_PREFERCANDIDATE;\n        else if(testvalue < 0)\n          result = COMP_PREFERINCUMBENT;\n        result = my_chsign(isdual, result);\n      }\n#endif\n\n    }\n  }\n\n  /* Select absolute best if the non-primary criteria failed to separate */\n  if((result == COMP_PREFERNONE) && candbetter) {\n    result = COMP_PREFERCANDIDATE;\n    goto Finish;\n  }\n\n  /* Final tie-breakers */\n  if(result == COMP_PREFERNONE) {\n\n    /* Add randomization tie-braker */\n    if(lp->piv_strategy & PRICE_RANDOMIZE) {\n      result = my_sign(PRICER_RANDFACT - rand_uniform(lp, 1.0));\n      if(candidatevarno < currentvarno)\n        result = -result;\n    }\n\n    /* Resolve ties via index ordinal (also prefers slacks over user variables) */\n    if(result == COMP_PREFERNONE) {\n      if(candidatevarno < currentvarno)\n        result = COMP_PREFERCANDIDATE;\n      else /* if(candidatevarno > currentvarno) */\n        result = COMP_PREFERINCUMBENT;\n      if(lp->_piv_left_)\n        result = -result;\n    }\n  }\n\nFinish:\n  return( result );\n}\nint CMP_CALLMODEL compareBoundFlipVar(const pricerec *current, const pricerec *candidate)\n{\n  register REAL  testvalue, margin;\n  register int   result = COMP_PREFERNONE;\n  register lprec *lp = current->lp;\n  MYBOOL    candbetter;\n  int currentvarno = current->varno,\n      candidatevarno = candidate->varno;\n\n  if(!current->isdual) {\n    candidatevarno = lp->var_basic[candidatevarno];\n    currentvarno   = lp->var_basic[currentvarno];\n  }\n\n  /* Compute the ranking test metric. */\n  testvalue = candidate->theta;\n  margin    = current->theta;\n  if(candidate->isdual) {\n    testvalue = fabs(testvalue);\n    margin    = fabs(margin);\n  }\n  if(fabs(margin) < LIMIT_ABS_REL)\n    testvalue -= margin;\n  else\n    testvalue = my_reldiff(testvalue, margin);\n\n  /* Find if the new Theta is smaller or near equal (i.e. testvalue <= eps)\n     compared to the previous best; ties will be broken by pivot size or index */\n  margin = PREC_SUBSTFEASGAP;\n  candbetter = (MYBOOL) (testvalue < 0);\n  if(candbetter) {\n    if(testvalue < -margin)\n      result = COMP_PREFERCANDIDATE;\n  }\n  else if(testvalue > margin)\n    result = COMP_PREFERINCUMBENT;\n\n  /* Resolve a tie */\n  if(result == COMP_PREFERNONE) {\n\n    /* Tertiary selection based on priority for large pivot sizes */\n    if(result == COMP_PREFERNONE) {\n      REAL currentpivot   = fabs(current->pivot),\n           candidatepivot = fabs(candidate->pivot);\n      if(candidatepivot > currentpivot+margin)\n        result = COMP_PREFERCANDIDATE;\n      else if(candidatepivot < currentpivot-margin)\n        result = COMP_PREFERINCUMBENT;\n    }\n\n    /* Secondary selection based on priority for narrow-bounded variables */\n    if(result == COMP_PREFERNONE)\n      result = compareREAL(&(lp->upbo[currentvarno]),\n                           &(lp->upbo[candidatevarno]));\n\n  }\n\n  /* Select absolute best if the non-primary criteria failed to separate */\n  if((result == COMP_PREFERNONE) && candbetter) {\n    result = COMP_PREFERCANDIDATE;\n    goto Finish;\n  }\n\n  /* Quaternary selection by index value */\n  if(result == COMP_PREFERNONE) {\n    if(candidatevarno < currentvarno)\n      result = COMP_PREFERCANDIDATE;\n    else\n      result = COMP_PREFERINCUMBENT;\n    if(lp->_piv_left_)\n      result = -result;\n  }\n\nFinish:\n  return( result );\n}\n\n/* Validity operators for entering and leaving columns for both the primal and dual\n   simplex.  All candidates must satisfy these tests to qualify to be allowed to be\n   a subject for the comparison functions/operators. */\nSTATIC MYBOOL validImprovementVar(pricerec *candidate)\n{\n  register REAL candidatepivot = fabs(candidate->pivot);\n\n#ifdef Paranoia\n  return( (MYBOOL) ((candidate->varno > 0) && (candidatepivot > candidate->lp->epsvalue)) );\n#else\n  return( (MYBOOL) (candidatepivot > candidate->lp->epsvalue) );\n#endif\n}\n\nSTATIC MYBOOL validSubstitutionVar(pricerec *candidate)\n{\n  register lprec *lp   = candidate->lp;\n  register REAL  theta = (candidate->isdual ? fabs(candidate->theta) : candidate->theta);\n\n#ifdef Paranoia\n  if(candidate->varno <= 0)\n    return( FALSE );\n  else\n#endif\n  if(fabs(candidate->pivot) >= lp->infinite)\n    return( (MYBOOL) (theta < lp->infinite) );\n  else\n    return( (MYBOOL) ((theta < lp->infinite) &&\n                      (fabs(candidate->pivot) >= candidate->epspivot)) );\n}\n\nint CMP_CALLMODEL compareImprovementQS(const UNIONTYPE QSORTrec *current, const UNIONTYPE QSORTrec *candidate)\n{\n  return( compareImprovementVar((pricerec *) current->pvoidint2.ptr, (pricerec *) candidate->pvoidint2.ptr) );\n}\nint CMP_CALLMODEL compareSubstitutionQS(const UNIONTYPE QSORTrec *current, const UNIONTYPE QSORTrec *candidate)\n{\n  return( compareBoundFlipVar((pricerec *) current->pvoidint2.ptr, (pricerec *) candidate->pvoidint2.ptr) );\n/*  return( compareSubstitutionVar((pricerec *) current->self, (pricerec *) candidate->self) ); */\n}\n\n/* Function to add a valid pivot candidate into the specified list */\nSTATIC int addCandidateVar(pricerec *candidate, multirec *multi, findCompare_func findCompare, MYBOOL allowSortedExpand)\n{\n  int     insertpos, delta = 1;\n  pricerec *targetrec;\n\n  /* Find the insertion point (if any) */\n  if((multi->freeList[0] == 0) ||\n     (multi->sorted && allowSortedExpand) ||\n     (candidate->isdual && (multi->used == 1) && ((multi->step_last >= multi->epszero) ||\n                                                  multi_truncatingvar(multi, ((pricerec *) (multi->sortedList[0].pvoidreal.ptr))->varno)))\n     ) {\n    UNIONTYPE QSORTrec searchTarget;\n\n    /* Make sure that the list is sorted before the search for an insertion point */\n    if((multi->freeList[0] == 0) && !multi->sorted) {\n      multi->sorted = QS_execute(multi->sortedList, multi->used, findCompare, &insertpos);\n      multi->dirty  = (MYBOOL) (insertpos > 0);\n    }\n\n    /* Perform the search */\n    searchTarget.pvoidint2.ptr = (void *) candidate;\n    insertpos = sizeof(searchTarget);\n    insertpos = findIndexEx(&searchTarget, multi->sortedList-delta, multi->used, delta, insertpos, findCompare, TRUE);\n    if(insertpos > 0)\n      return( -1 );\n    insertpos = -insertpos - delta;\n\n    /* Check if the candidate is worse than the worst of the list */\n    if(((insertpos >= multi->size) && (multi->freeList[0] == 0)) ||\n       ((insertpos == multi->used) && (!allowSortedExpand ||\n                                       (multi->step_last >= multi->epszero))))\n      return( -1 );\n\n#ifdef Paranoia\n    /* Do validation */\n    if((insertpos < 0) || (insertpos > multi->used))\n      return( -1 );\n#endif\n\n    /* Define the target for storing the candidate;\n       Case 1: List is full and we must discard the previously worst candidate\n       Case 2: List is not full and we simply use the next free position */\n    if(multi->freeList[0] == 0)\n      targetrec = (pricerec *) multi->sortedList[multi->used-1].pvoidreal.ptr;\n    else {\n      delta = multi->freeList[0]--;\n      delta = multi->freeList[delta];\n      targetrec = &(multi->items[delta]);\n    }\n  }\n  else {\n    delta = multi->freeList[0]--;\n    delta = multi->freeList[delta];\n    targetrec = &(multi->items[delta]);\n    insertpos = multi->used;\n  }\n\n  /* Insert the new candidate record in the data store */\n  MEMCOPY(targetrec, candidate, 1);\n\n  /* Store the pointer data and handle tree cases:\n     Case 1: The list is unsorted and not full; simply append pointer to list,\n     Case 2: The list is sorted and full; insert the pointer by discarding previous last,\n     Case 3: The list is sorted and not full; shift the inferior items down, and increment count */\n  if((multi->used < multi->size) && (insertpos >= multi->used)) {\n    QS_append(multi->sortedList, insertpos, targetrec);\n    multi->used++;\n  }\n  else {\n    if(multi->used == multi->size)\n      QS_insert(multi->sortedList, insertpos, targetrec, multi->size-1); /* Discard previous last */\n    else {\n      QS_insert(multi->sortedList, insertpos, targetrec, multi->used);   /* Keep previous last    */\n      multi->used++;\n    }\n  }\n  multi->active = insertpos;\n\n#ifdef Paranoia\n  if((insertpos >= multi->size) || (insertpos >= multi->used))\n    report(multi->lp, SEVERE, \"addCandidateVar: Insertion point beyond limit!\\n\");\n#endif\n\n  return( insertpos );\n}\n\nSTATIC MYBOOL findImprovementVar(pricerec *current, pricerec *candidate, MYBOOL collectMP, int *candidatecount)\n/* PRIMAL: Find a variable to enter the basis\n   DUAL:   Find a variable to leave the basis\n\n   Allowed variable set: Any pivot PRIMAL:larger or DUAL:smaller than threshold value of 0 */\n{\n  MYBOOL Action = FALSE,\n#ifdef ExtractedValidityTest\n         Accept = TRUE;\n#else    /* Check for validity and compare result with previous best */\n         Accept = validImprovementVar(candidate);\n#endif\n  if(Accept) {\n    if(candidatecount != NULL)\n      (*candidatecount)++;\n    if(collectMP) {\n      if(addCandidateVar(candidate, current->lp->multivars, (findCompare_func *) compareImprovementQS, FALSE) < 0)\n        return(Action);\n    }\n    if(current->varno > 0)\n      Accept = (MYBOOL) (compareImprovementVar(current, candidate) > 0);\n  }\n\n /* Apply candidate if accepted */\n  if(Accept) {\n    (*current) = *candidate;\n\n    /* Force immediate acceptance for Bland's rule using the primal simplex */\n    if(!candidate->isdual)\n      Action = (MYBOOL) (candidate->lp->_piv_rule_ == PRICER_FIRSTINDEX);\n  }\n  return(Action);\n}\n\n/* Bound flip variable accumulation routine */\nSTATIC MYBOOL collectMinorVar(pricerec *candidate, multirec *longsteps, MYBOOL isphase2, MYBOOL isbatch)\n{\n  int   inspos;\n\n  /* 1. Check for ratio and pivot validity (to have the extra flexibility that all\n        bound-flip candidates are also possible as basis-entering variables */\n  if(!validSubstitutionVar(candidate))\n    return( FALSE );\n\n  /* 2. If the free-list is empty we need to see if we have a better candidate,\n        and for this the candidate list has to be sorted by merit */\n  if(!isbatch &&\n     !longsteps->sorted && (longsteps->used > 1) &&\n     ((longsteps->freeList[0] == 0) ||\n      multi_truncatingvar(longsteps, candidate->varno) ||\n      (longsteps->step_last >= longsteps->epszero) )) {\n    longsteps->sorted = QS_execute(longsteps->sortedList, longsteps->used,\n                                   (findCompare_func *) compareSubstitutionQS, &inspos);\n    longsteps->dirty  = (MYBOOL) (inspos > 0);\n    if(longsteps->dirty)\n      multi_recompute(longsteps, 0, isphase2, TRUE);\n  }\n\n  /* 3. Now handle three cases...\n        - Add to the list when the list is not full and there is opportunity for improvement,\n        - Check if we should replace an incumbent when the list is full,\n        - Check if we should replace an incumbent when the list is not full, there is no room\n          for improvement, but the current candidate is better than an incumbent. */\n  inspos = addCandidateVar(candidate, longsteps, (findCompare_func *) compareSubstitutionQS, TRUE);\n\n  /* 4. Recompute steps and objective, and (if relevant) determine if we\n        may be suboptimal in relation to an incumbent MILP solution. */\n  return( (MYBOOL) (inspos >= 0) &&\n           ((isbatch == TRUE) || multi_recompute(longsteps, inspos, isphase2, TRUE)) );\n}\n\nSTATIC MYBOOL findSubstitutionVar(pricerec *current, pricerec *candidate, int *candidatecount)\n/* PRIMAL: Find a variable to leave the basis\n   DUAL:   Find a variable to enter the basis\n\n   Allowed variable set: \"Equal-valued\" smallest thetas! */\n{\n  MYBOOL Action = FALSE,\n#ifdef ExtractedValidityTest\n         Accept = TRUE;\n#else  /* Check for validity and comparison result with previous best */\n         Accept = validSubstitutionVar(candidate);\n#endif\n  if(Accept) {\n    if(candidatecount != NULL)\n      (*candidatecount)++;\n    if(current->varno != 0)\n      Accept = (MYBOOL) (compareSubstitutionVar(current, candidate) > 0);\n  }\n\n /* Apply candidate if accepted */\n  if(Accept) {\n    (*current) = *candidate;\n\n    /* Force immediate acceptance for Bland's rule using the dual simplex */\n#ifdef ForceEarlyBlandRule\n    if(candidate->isdual)\n      Action = (MYBOOL) (candidate->lp->_piv_rule_ == PRICER_FIRSTINDEX);\n#endif\n  }\n  return(Action);\n}\n\n/* Partial pricing management routines */\nSTATIC partialrec *partial_createBlocks(lprec *lp, MYBOOL isrow)\n{\n  partialrec *blockdata;\n\n  blockdata = (partialrec *) calloc(1, sizeof(*blockdata));\n  blockdata->lp = lp;\n  blockdata->blockcount = 1;\n  blockdata->blocknow = 1;\n  blockdata->isrow = isrow;\n\n  return(blockdata);\n}\nSTATIC int partial_countBlocks(lprec *lp, MYBOOL isrow)\n{\n  partialrec *blockdata = IF(isrow, lp->rowblocks, lp->colblocks);\n\n  if(blockdata == NULL)\n    return( 1 );\n  else\n    return( blockdata->blockcount );\n}\nSTATIC int partial_activeBlocks(lprec *lp, MYBOOL isrow)\n{\n  partialrec *blockdata = IF(isrow, lp->rowblocks, lp->colblocks);\n\n  if(blockdata == NULL)\n    return( 1 );\n  else\n    return( blockdata->blocknow );\n}\nSTATIC void partial_freeBlocks(partialrec **blockdata)\n{\n  if((blockdata == NULL) || (*blockdata == NULL))\n    return;\n  FREE((*blockdata)->blockend);\n  FREE((*blockdata)->blockpos);\n  FREE(*blockdata);\n}\n\n\n/* Function to provide for left-right or right-left scanning of entering/leaving\n   variables; note that *end must have been initialized by the calling routine! */\nSTATIC void makePriceLoop(lprec *lp, int *start, int *end, int *delta)\n{\n  int offset = is_piv_mode(lp, PRICE_LOOPLEFT);\n\n  if((offset) ||\n     (((lp->total_iter+offset) % 2 == 0) && is_piv_mode(lp, PRICE_LOOPALTERNATE))) {\n    *delta = -1; /* Step backwards - \"left\" */\n    swapINT(start, end);\n    lp->_piv_left_ = TRUE;\n  }\n  else {\n    *delta = 1;  /* Step forwards - \"right\" */\n    lp->_piv_left_ = FALSE;\n  }\n}\n\n/* Routine to verify accuracy of the current basis factorization */\nSTATIC MYBOOL serious_facterror(lprec *lp, REAL *bvector, int maxcols, REAL tolerance)\n{\n  int    i, j, ib, ie, nz, nc;\n  REAL   sum, tsum = 0, err = 0;\n  MATrec *mat = lp->matA;\n\n  if(bvector == 0)\n    bvector = lp->bsolveVal;\n  nc =0;\n  nz = 0;\n  for(i = 1; (i <= lp->rows) && (nc <= maxcols); i++) {\n\n    /* Do we have a non-slack variable? (we choose to skip slacks,\n      since they have \"natural\" good accuracy properties) */\n    j = lp->var_basic[i] - lp->rows;\n    if(j <= 0)\n      continue;\n    nc++;\n\n    /* Compute cross product for basic, non-slack column */\n    ib = mat->col_end[j-1];\n    ie = mat->col_end[j];\n    nz += ie - ib;\n    sum = get_OF_active(lp, j+lp->rows, bvector[0]);\n    for(; ib < ie; ib++)\n      sum += COL_MAT_VALUE(ib)*bvector[COL_MAT_ROWNR(ib)];\n\n    /* Catch high precision early, so we don't to uneccessary work */\n    tsum += sum;\n    SETMAX(err, fabs(sum));\n    if((tsum / nc > tolerance / 100) && (err < tolerance / 100))\n      break;\n  }\n  err /= mat->infnorm;\n  return( (MYBOOL) (err >= tolerance) );\n}\n\n/* Computation of reduced costs */\nSTATIC void update_reducedcosts(lprec *lp, MYBOOL isdual, int leave_nr, int enter_nr, REAL *prow, REAL *drow)\n{\n  /* \"Fast\" update of the dual reduced cost vector; note that it must be called\n     after the pivot operation and only applies to a major \"true\" iteration */\n  int  i;\n  REAL hold;\n\n  if(isdual) {\n    hold = -drow[enter_nr]/prow[enter_nr];\n    for(i=1; i <= lp->sum; i++)\n      if(!lp->is_basic[i]) {\n        if(i == leave_nr)\n          drow[i] = hold;\n        else {\n          drow[i] += hold*prow[i];\n          my_roundzero(drow[i], lp->epsmachine);\n        }\n      }\n  }\n  else\n    report(lp, SEVERE, \"update_reducedcosts: Cannot update primal reduced costs!\\n\");\n}\n\n\nSTATIC void compute_reducedcosts(lprec *lp, MYBOOL isdual, int row_nr, int *coltarget, MYBOOL dosolve,\n                                            REAL *prow, int *nzprow,\n                                            REAL *drow, int *nzdrow,\n                                            int roundmode)\n{\n  REAL epsvalue = lp->epsvalue;  /* Any larger value can produce a suboptimal result */\n  roundmode |=  MAT_ROUNDRC;\n\n  if(isdual) {\n    bsolve_xA2(lp, coltarget,\n                   row_nr, prow, epsvalue, nzprow,  /* Calculate net sensitivity given a leaving variable */\n                        0, drow, epsvalue, nzdrow,  /* Calculate the net objective function values */\n                   roundmode);\n  }\n  else {\n    REAL *bVector;\n\n#if 1 /* Legacy mode, that is possibly a little faster */\n    if((lp->multivars == NULL) && (lp->P1extraDim == 0))\n      bVector = drow;\n    else\n#endif\n      bVector = lp->bsolveVal;\n    if(dosolve) {\n      bsolve(lp, 0, bVector, lp->bsolveIdx, epsvalue*DOUBLEROUND, 1.0);\n      if(!isdual && (row_nr == 0) && (lp->improve & IMPROVE_SOLUTION) && !refactRecent(lp) &&\n         serious_facterror(lp, bVector, lp->rows, lp->epsvalue))\n        set_action(&lp->spx_action, ACTION_REINVERT);\n    }\n    prod_xA(lp,   coltarget,\n                  bVector, lp->bsolveIdx, epsvalue, 1.0,\n                  drow, nzdrow, roundmode);\n  }\n}\n\n\n/* Primal: Prevent acceptance of an entering variable when the magnitude of\n           other candidates is also very small.\n   Dual:   Prevent acceptance of a leaving variable when the magnitude of\n           other candidates is also very small.\n\n   Both of these cases are associated with numerical stalling, which we could\n   argue should be detected and handled by the stalling monitor routine. */\nSTATIC MYBOOL verify_stability(lprec *lp, MYBOOL isprimal, REAL xfeas, REAL sfeas, int nfeas)\n{\n  MYBOOL testOK = TRUE;\n  return( testOK );\n\n#if 1\n  /* Try to make dual feasibility as tight as possible */\n  if(!isprimal)\n/*  if(lp->P1extraVal == 0) */\n  {\n    xfeas /= (1+lp->rhsmax);\n    sfeas /= (1+lp->rhsmax);\n  }\n#endif\n  xfeas = fabs(xfeas);             /* Maximum (positive) infeasibility */\n/*  if(xfeas < lp->epspivot) { */\n  if(xfeas < lp->epssolution) {\n    REAL f;\n    sfeas = fabs(sfeas);           /* Make sum of infeasibilities positive */\n    xfeas = (sfeas-xfeas)/nfeas;   /* Average \"residual\" feasibility */\n    f = 1 + log10((REAL) nfeas);   /* Some numerical complexity scalar */\n    /* Numerical errors can interact to cause non-convergence, and the\n      idea is to relax the tolerance to account for this and only\n      marginally weakening the (user-specified) tolerance. */\n    if((sfeas-xfeas) < f*lp->epsprimal)\n      testOK = FALSE;\n  }\n  return( testOK );\n}\n\n\n/* Find an entering column for the case that the specified basic variable\n   is fixed or zero - typically used for artificial variable elimination */\nSTATIC int find_rowReplacement(lprec *lp, int rownr, REAL *prow, int *nzprow)\n/* The logic in this section generally follows Chvatal: Linear Programming, p. 130\n   Basically, the function is a specialized coldual(). */\n{\n  int  i, bestindex;\n  REAL bestvalue;\n\n /* Solve for \"local reduced cost\" */\n  set_action(&lp->piv_strategy, PRICE_FORCEFULL);\n    compute_reducedcosts(lp, TRUE, rownr, NULL, TRUE,\n                             prow, nzprow, NULL, NULL, MAT_ROUNDDEFAULT);\n  clear_action(&lp->piv_strategy, PRICE_FORCEFULL);\n\n /* Find a suitably non-singular variable to enter (\"most orthogonal\") */\n  bestindex = 0;\n  bestvalue = 0;\n  for(i = 1; i <= lp->sum-abs(lp->P1extraDim); i++) {\n    if(!lp->is_basic[i] && !is_fixedvar(lp, i) &&\n      (fabs(prow[i]) > bestvalue)) {\n      bestindex = i;\n      bestvalue = fabs(prow[i]);\n    }\n  }\n\n  /* Prepare to update inverse and pivot/iterate (compute Bw=a) */\n  if(i > lp->sum-abs(lp->P1extraDim))\n    bestindex = 0;\n  else\n    fsolve(lp, bestindex, prow, nzprow, lp->epsmachine, 1.0, TRUE);\n\n  return( bestindex );\n}\n\n/* Find the primal simplex entering non-basic column variable */\nSTATIC int colprim(lprec *lp, REAL *drow, int *nzdrow, MYBOOL skipupdate, int partialloop, int *candidatecount, MYBOOL updateinfeas, REAL *xviol)\n{\n  int      i, ix, iy, iz, ninfeas, nloop = 0;\n  REAL     f, sinfeas, xinfeas, epsvalue = lp->epsdual;\n  pricerec current, candidate;\n  MYBOOL   collectMP = FALSE;\n  int      *coltarget = NULL;\n\n  /* Identify pivot column according to pricing strategy; set\n     entering variable initial threshold reduced cost value to \"0\" */\n  current.pivot    = lp->epsprimal;    /* Minimum acceptable improvement */\n  current.varno    = 0;\n  current.lp       = lp;\n  current.isdual   = FALSE;\n  candidate.lp     = lp;\n  candidate.isdual = FALSE;\n  *candidatecount  = 0;\n\n  /* Update local value of pivot setting and determine active multiple pricing set */\n  lp->_piv_rule_ = get_piv_rule(lp);\ndoLoop:\n  nloop++;\n  if((lp->multivars != NULL) && ((lp->simplex_mode & SIMPLEX_PRIMAL_PRIMAL) != 0)) {\n    collectMP = multi_mustupdate(lp->multivars);\n    if(collectMP) {\n      multi_restart(lp->multivars);\n      coltarget = NULL;\n    }\n    else\n      coltarget = multi_indexSet(lp->multivars, FALSE);\n  }\n\n  /* Compute reduced costs c - c*Inv(B), if necessary\n     (i.e. the previous iteration was not a \"minor\" iteration/bound flip) */\n  if(!skipupdate) {\n#ifdef UsePrimalReducedCostUpdate\n    /* Recompute from scratch only at the beginning, otherwise update */\n    if((lp->current_iter > 0) && (refactRecent(lp) == AUTOMATIC))\n#endif\n    compute_reducedcosts(lp, FALSE, 0, coltarget, (MYBOOL) ((nloop <= 1) || (partialloop > 1)),\n                             NULL, NULL,\n                             drow, nzdrow,\n                             MAT_ROUNDDEFAULT);\n  }\n\n  /* Loop over active partial column set; we presume that reduced costs\n     have only been updated for columns in the active partial range. */\n  ix = 1;\n  iy = nzdrow[0];\n  ninfeas = 0;\n  xinfeas = 0;\n  sinfeas = 0;\n  makePriceLoop(lp, &ix, &iy, &iz);\n  iy *= iz;\n  for(; ix*iz <= iy; ix += iz) {\n    i = nzdrow[ix];\n#if 0 /* Not necessary since we masked them out in compute_reducedcosts() */\n    if(i > lp->sum-abs(lp->P1extraDim))\n      continue;\n#endif\n\n    /* Check if the pivot candidate is on the block-list */\n    if(lp->rejectpivot[0] > 0) {\n      int kk;\n      for(kk = 1; (kk <= lp->rejectpivot[0]) && (i != lp->rejectpivot[kk]); kk++);\n      if(kk <= lp->rejectpivot[0])\n        continue;\n    }\n\n   /* Retrieve the applicable reduced cost - threshold should not be smaller than 0 */\n    f = my_chsign(lp->is_lower[i], drow[i]);\n    if(f <= epsvalue)\n      continue;\n\n   /* Find entering variable according to strategy (largest positive f) */\n    ninfeas++;\n    SETMAX(xinfeas, f);\n    sinfeas += f;\n    candidate.pivot = normalizeEdge(lp, i, f, FALSE);\n    candidate.varno = i;\n    if(findImprovementVar(&current, &candidate, collectMP, candidatecount))\n      break;\n  }\n\n  /* Check if we should loop again after a multiple pricing update */\n  if(lp->multivars != NULL) {\n    if(collectMP) {\n      if(!lp->multivars->sorted)\n        lp->multivars->sorted = QS_execute(lp->multivars->sortedList, lp->multivars->used,\n                                           (findCompare_func *) compareImprovementQS, NULL);\n      coltarget = multi_indexSet(lp->multivars, TRUE);\n    }\n    else if((current.varno == 0) && (lp->multivars->retries == 0)) {\n      ix = partial_blockStart(lp, FALSE);\n      iy = partial_blockEnd(lp, FALSE);\n      lp->multivars->used = 0;\n      lp->multivars->retries++;\n      goto doLoop;\n    }\n    /* Shrink the candidate list */\n    lp->multivars->retries = 0;\n    if(current.varno != 0)\n      multi_removevar(lp->multivars, current.varno);\n  }\n\n  /* Check for optimality */\n  if(xviol != NULL)\n    *xviol = xinfeas;\n  if(updateinfeas)\n    lp->suminfeas = fabs(sinfeas);\n  if((lp->multivars == NULL) && (current.varno > 0) &&\n     !verify_stability(lp, TRUE, xinfeas, sinfeas, ninfeas))\n    current.varno = 0;\n\n  /* Produce statistics */\n  if(lp->spx_trace) {\n    if(current.varno > 0)\n      report(lp, DETAILED, \"colprim: Column %d reduced cost = \" RESULTVALUEMASK \"\\n\",\n                          current.varno, current.pivot);\n    else\n      report(lp, DETAILED, \"colprim: No positive reduced costs found, optimality!\\n\");\n  }\n\n  return( current.varno );\n} /* colprim */\n\n/* Find the primal simplex leaving basic column variable */\nSTATIC int rowprim(lprec *lp, int colnr, LREAL *theta, REAL *pcol, int *nzpcol, MYBOOL forceoutEQ, REAL *xviol)\n{\n  int      i, ii, iy, iz, Hpass, k, *nzlist;\n  LREAL    f, savef;\n  REAL     Heps, Htheta, Hlimit, epsvalue, epspivot, p = 0.0;\n  pricerec current, candidate;\n  MYBOOL   isupper = !lp->is_lower[colnr], HarrisTwoPass = FALSE;\n\n  /* Update local value of pivot setting */\n  lp->_piv_rule_ = get_piv_rule(lp);\n  if(nzpcol == NULL)\n    nzlist = (int *) mempool_obtainVector(lp->workarrays, lp->rows+1, sizeof(*nzlist));\n  else\n    nzlist = nzpcol;\n\n  /* Find unconditional non-zeros and optionally compute relative size of epspivot */\n  epspivot = lp->epspivot;\n  epsvalue = lp->epsvalue;\n  Hlimit = 0;\n  Htheta = 0;\n  k = 0;\n  for(i = 1; i <= lp->rows; i++) {\n    p = fabs(pcol[i]);\n    if(p > Hlimit)\n      Hlimit = p;\n    if(p > epsvalue) {\n      k++;\n      nzlist[k] = i;\n      SETMAX(Htheta, p);\n    }\n#ifdef Paranoia\n    else {\n      if(lp->spx_trace)\n        report(lp, FULL, \"rowprim: Row %d with pivot \" RESULTVALUEMASK \" rejected as too small\\n\",\n                         i, p);\n    }\n#endif\n  }\n  if(xviol != NULL)\n    *xviol = Htheta;\n  Htheta = 0;\n\n  /* Update non-zero list based on the new pivot threshold */\n#ifdef UseRelativePivot_Primal\n/*  epspivot *= sqrt(lp->matA->dynrange) / lp->matA->infnorm; */\n  epspivot /= MAX(1, sqrt(lp->matA->colmax[colnr]));\n  iy = k;\n  k = 0;\n  p = 0;\n  for(ii = 1; ii <= iy; ii++) {\n    i = nzlist[ii];\n    p = fabs(pcol[i]);\n\n    /* Compress the list of valid alternatives, if appropriate */\n    if(p > epspivot) {\n      k++;\n      nzlist[k] = i;\n    }\n#ifdef Paranoia\n    else {\n      if(lp->spx_trace)\n        report(lp, FULL, \"rowprim: Row %d with pivot \" RESULTVALUEMASK \" rejected as too small\\n\",\n                         i, p);\n    }\n#endif\n  }\n#endif\n\n  /* Initialize counters */\n  nzlist[0] = k;\n  k = 0;\n\nRetry:\n  k++;\n  HarrisTwoPass = is_piv_mode(lp, PRICE_HARRISTWOPASS);\n  if(HarrisTwoPass)\n    Hpass = 1;\n  else\n    Hpass = 2;\n  current.theta    = lp->infinite;\n  current.pivot    = 0;\n  current.varno    = 0;\n  current.isdual   = FALSE;\n  current.epspivot = epspivot;\n  current.lp       = lp;\n  candidate.epspivot = epspivot;\n  candidate.isdual = FALSE;\n  candidate.lp     = lp;\n  savef  = 0;\n  for(; Hpass <= 2; Hpass++) {\n    Htheta = lp->infinite;\n    if(Hpass == 1) {\n      Hlimit = lp->infinite;           /* Don't apply any limit in the first pass */\n      Heps   = epspivot/lp->epsprimal; /* Scaled to lp->epsprimal used in compute_theta() */\n    }\n    else {\n      Hlimit = current.theta;          /* This is the smallest Theta of the first pass */\n      Heps   = 0.0;\n    }\n    current.theta = lp->infinite;\n    current.pivot = 0;\n    current.varno = 0;\n    savef = 0;\n\n    ii = 1;\n    iy = nzlist[0];\n    makePriceLoop(lp, &ii, &iy, &iz);\n    iy *= iz;\n    for(; ii*iz <= iy; ii += iz) {\n      i = nzlist[ii];\n      f = pcol[i];\n      candidate.theta = f;\n      candidate.pivot = f;\n      candidate.varno = i;\n\n      /*i =*/ compute_theta(lp, i, &candidate.theta, isupper,\n                            my_if(lp->upbo[lp->var_basic[i]] < lp->epsprimal, Heps/10, Heps), TRUE);\n\n      if(fabs(candidate.theta) >= lp->infinite) {\n        savef = f;\n        candidate.theta = 2*lp->infinite;\n        continue;\n      }\n\n      /* Find the candidate leaving variable according to strategy (smallest theta) */\n      if((Hpass == 2) && (candidate.theta > Hlimit))\n        continue;\n\n      /* Give a slight preference to fixed variables (mainly equality slacks) */\n      if(forceoutEQ) {\n        p = candidate.pivot;\n        if(lp->upbo[lp->var_basic[i]] < lp->epsprimal) {\n          /* Give an extra early boost to equality slack elimination, if specified */\n          if(forceoutEQ == AUTOMATIC)\n            candidate.pivot *= 1.0+lp->epspivot;\n          else\n            candidate.pivot *= 10.0;\n\n        }\n      }\n      if(HarrisTwoPass) {\n        f = candidate.theta;\n        if(Hpass == 2)\n          candidate.theta = 1;\n        if(findSubstitutionVar(&current, &candidate, NULL))\n          break;\n        if((Hpass == 2) && (current.varno == candidate.varno))\n          Htheta = f;\n      }\n      else\n        if(findSubstitutionVar(&current, &candidate, NULL))\n          break;\n      /* Restore temporarily modified pivot */\n      if(forceoutEQ && (current.varno == candidate.varno))\n        current.pivot = p;\n    }\n  }\n  if(HarrisTwoPass)\n    current.theta = Htheta;\n\n  /* Handle case of no available leaving variable */\n  if(current.varno == 0) {\n    if(lp->upbo[colnr] >= lp->infinite) {\n      /* Optionally try again with reduced pivot threshold level */\n      if(k < 2) {\n        epspivot = epspivot / 10;\n        goto Retry;\n      }\n    }\n    else {\n#if 1\n      i = 1;\n      while((pcol[i] >= 0) && (i <= lp->rows))\n        i++;\n      if(i > lp->rows) { /* Empty column with upper bound! */\n        lp->is_lower[colnr] = !lp->is_lower[colnr];\n/*        lp->is_lower[colnr] = FALSE; */\n        lp->rhs[0] += lp->upbo[colnr]*pcol[0];\n      }\n      else /* if(pcol[i]<0) */\n      {\n        current.varno = i;\n      }\n#endif\n    }\n  }\n  else if(current.theta >= lp->infinite) {\n    report(lp, IMPORTANT, \"rowprim: Numeric instability pcol[%d] = %g, rhs[%d] = %g, upbo = %g\\n\",\n                          current.varno, savef, current.varno, lp->rhs[current.varno],\n                          lp->upbo[lp->var_basic[current.varno]]);\n  }\n\n /* Return working array to pool */\n  if(nzpcol == NULL)\n    mempool_releaseVector(lp->workarrays, (char *) nzlist, FALSE);\n\n  if(lp->spx_trace)\n    report(lp, DETAILED, \"row_prim: %d, pivot size = \" RESULTVALUEMASK \"\\n\",\n                         current.varno, current.pivot);\n\n/*  *theta = current.theta; */\n  *theta = fabs(current.theta);\n\n  return(current.varno);\n} /* rowprim */\n\n\n/* Find the dual simplex leaving basic variable */\nSTATIC int rowdual(lprec *lp, REAL *rhvec, MYBOOL forceoutEQ, MYBOOL updateinfeas, REAL *xviol)\n{\n  int       k, i, iy, iz, ii, ninfeas;\n  register REAL     rh;\n  REAL      up, lo = 0,\n            epsvalue, sinfeas, xinfeas;\n  pricerec  current, candidate;\n  MYBOOL    collectMP = FALSE;\n\n  /* Initialize */\n  if(rhvec == NULL)\n    rhvec = lp->rhs;\n  epsvalue = lp->epsdual;\n  current.pivot    = -epsvalue;  /* Initialize leaving variable threshold; \"less than 0\" */\n  current.theta    = 0;\n  current.varno    = 0;\n  current.isdual   = TRUE;\n  current.lp       = lp;\n  candidate.isdual = TRUE;\n  candidate.lp     = lp;\n\n  /* Loop over active partial row set */\n  if(is_action(lp->piv_strategy, PRICE_FORCEFULL)) {\n    k  = 1;\n    iy = lp->rows;\n  }\n  else {\n    k = partial_blockStart(lp, TRUE);\n    iy = partial_blockEnd(lp, TRUE);\n  }\n  ninfeas = 0;\n  xinfeas = 0;\n  sinfeas = 0;\n  makePriceLoop(lp, &k, &iy, &iz);\n  iy *= iz;\n  for(; k*iz <= iy; k += iz) {\n\n    /* Map loop variable to target */\n    i = k;\n\n    /* Check if the pivot candidate is on the block-list */\n    if(lp->rejectpivot[0] > 0) {\n      int kk;\n      for(kk = 1; (kk <= lp->rejectpivot[0]) && (i != lp->rejectpivot[kk]); kk++);\n      if(kk <= lp->rejectpivot[0])\n        continue;\n    }\n\n    /* Set local variables - express violation as a negative number */\n    ii = lp->var_basic[i];\n    up = lp->upbo[ii];\n    lo = 0;\n    rh = rhvec[i];\n    if(rh > up)\n      rh = up - rh;\n    else\n      rh -= lo;\n    up -= lo;\n\n   /* Analyze relevant constraints ...\n      KE version skips uninteresting alternatives and gives a noticeable speedup */\n/*    if((rh < -epsvalue*sqrt(lp->matA->rowmax[i])) || */\n    if((rh < -epsvalue) ||\n       ((forceoutEQ == TRUE) && (up < epsvalue))) {  /* It causes instability to remove the \"TRUE\" test */\n\n     /* Accumulate stats */\n      ninfeas++;\n      SETMIN(xinfeas, rh);\n      sinfeas += rh;\n\n     /* Give a slight preference to fixed variables (mainly equality slacks) */\n      if(up < epsvalue) {\n        /* Break out immediately if we are directed to force slacks out of the basis */\n        if(forceoutEQ == TRUE) {\n          current.varno = i;\n          current.pivot = -1;\n          break;\n        }\n        /* Give an extra early boost to equality slack elimination, if specified */\n        if(forceoutEQ == AUTOMATIC)\n          rh *= 10.0;\n        else /* .. or just the normal. marginal boost */\n          rh *= 1.0+lp->epspivot;\n      }\n\n     /* Select leaving variable according to strategy (the most negative/largest violation) */\n      candidate.pivot = normalizeEdge(lp, i, rh, TRUE);\n      candidate.varno = i;\n      if(findImprovementVar(&current, &candidate, collectMP, NULL))\n        break;\n    }\n  }\n\n  /* Verify infeasibility */\n  if(updateinfeas)\n    lp->suminfeas = fabs(sinfeas);\n  if((ninfeas > 1) &&\n     !verify_stability(lp, FALSE, xinfeas, sinfeas, ninfeas)) {\n    report(lp, IMPORTANT, \"rowdual: Check for reduced accuracy and tolerance settings.\\n\");\n    current.varno = 0;\n  }\n\n  /* Produce statistics */\n  if(lp->spx_trace) {\n    report(lp, NORMAL, \"rowdual: Infeasibility sum \" RESULTVALUEMASK \" in %7d constraints.\\n\",\n                        sinfeas, ninfeas);\n    if(current.varno > 0) {\n      report(lp, DETAILED, \"rowdual: rhs[%d] = \" RESULTVALUEMASK \"\\n\",\n                           current.varno, lp->rhs[current.varno]);\n    }\n    else\n      report(lp, FULL, \"rowdual: Optimality - No primal infeasibilities found\\n\");\n  }\n  if(xviol != NULL)\n    *xviol = fabs(xinfeas);\n\n  return(current.varno);\n} /* rowdual */\n\n\nSTATIC void longdual_testset(lprec *lp, int which, int rownr, REAL *prow, int *nzprow,\n                                                    REAL *drow, int *nzdrow)\n{\n  int i,j;\n  REAL F = lp->infinite;\n  if(which == 0) {             /* Maros Example-1 - raw data */\n    j =  1; i = lp->rows+j; lp->upbo[i] = 0;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] =  2; drow[i] = -1;\n    j =  2; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -2; drow[i] =  2;\n    j =  3; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] =  1; drow[i] =  5;\n    j =  4; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] =  3; drow[i] = -6;\n    j =  5; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] = -4; drow[i] = -2;\n    j =  6; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -1; drow[i] =  0;\n    j =  7; i = lp->rows+j; lp->upbo[i] = 2;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] =  1; drow[i] =  0;\n    j =  8; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] = -2; drow[i] =  0;\n    j =  9; i = lp->rows+j; lp->upbo[i] = 5;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -1; drow[i] =  4;\n    j = 10; i = lp->rows+j; lp->upbo[i] = F;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -2; drow[i] = 10;\n    nzprow[0] = i-lp->rows;\n    lp->rhs[rownr] = -11;\n    lp->upbo[lp->var_basic[rownr]] = F;\n    lp->rhs[0] = 1;\n  }\n  else if(which == 1) {       /* Maros Example-1 - presorted in correct order */\n    j =  1; i = lp->rows+j; lp->upbo[i] = 0;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] =  2; drow[i] = -1;\n    j =  2; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] =  1; drow[i] =  5;\n    j =  3; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] = -4; drow[i] = -2;\n    j =  4; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] = -2; drow[i] =  0;\n\n    j =  5; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -1; drow[i] =  0;\n    j =  6; i = lp->rows+j; lp->upbo[i] = 2;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] =  1; drow[i] =  0;\n    j =  7; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -2; drow[i] =  2;\n    j =  8; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] =  3; drow[i] = -6;\n    j =  9; i = lp->rows+j; lp->upbo[i] = 5;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -1; drow[i] =  4;\n    j = 10; i = lp->rows+j; lp->upbo[i] = F;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -2; drow[i] = 10;\n    nzprow[0] = i-lp->rows;\n    lp->rhs[rownr] = -11;\n    lp->upbo[lp->var_basic[rownr]] = F;\n    lp->rhs[0] = 1;\n  }\n\n  else if(which == 10) {       /* Maros Example-2 - raw data */\n    j =  1; i = lp->rows+j; lp->upbo[i] = 5;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] = -2; drow[i] =  2;\n    j =  2; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] =  3; drow[i] =  3;\n    j =  3; i = lp->rows+j; lp->upbo[i] = 1;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] = -2; drow[i] =  0;\n    j =  4; i = lp->rows+j; lp->upbo[i] = 2;  lp->is_lower[i] = FALSE; nzprow[j] = i; prow[i] = -1; drow[i] = -2;\n    j =  5; i = lp->rows+j; lp->upbo[i] = 2;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] =  1; drow[i] =  0;\n    j =  6; i = lp->rows+j; lp->upbo[i] = F;  lp->is_lower[i] =  TRUE; nzprow[j] = i; prow[i] =  3; drow[i] =  9;\n    nzprow[0] = i-lp->rows;\n    lp->rhs[rownr] = 14;\n    lp->upbo[lp->var_basic[rownr]] = 2;\n    lp->rhs[0] = 6;\n  }\n}\n\n\n/* Find the dual simplex entering non-basic variable */\nSTATIC int coldual(lprec *lp, int row_nr, REAL *prow, int *nzprow,\n                                          REAL *drow, int *nzdrow,\n                                          MYBOOL dualphase1, MYBOOL skipupdate,\n                                          int *candidatecount, REAL *xviol)\n{\n  int      i, iy, iz, ix, k, nbound;\n  LREAL    w, g, quot;\n  REAL     viol, p, epspivot = lp->epspivot;\n#ifdef MachinePrecRoundRHS\n  REAL     epsvalue = lp->epsmachine;\n#else\n  REAL     epsvalue = lp->epsvalue;\n#endif\n  pricerec current, candidate;\n  MYBOOL   isbatch = FALSE, /* Requires that lp->longsteps->size > lp->sum */\n           dolongsteps = (MYBOOL) (lp->longsteps != NULL);\n\n  /* Initialize */\n  if(xviol != NULL)\n    *xviol = lp->infinite;\n  if(dolongsteps && !dualphase1)\n    dolongsteps = AUTOMATIC;  /* Sets Phase1 = TRUE, Phase2 = AUTOMATIC */\n  current.theta    = lp->infinite;\n  current.pivot    = 0;\n  current.varno    = 0;\n  current.epspivot = epspivot;\n  current.isdual   = TRUE;\n  current.lp       = lp;\n  candidate.epspivot = epspivot;\n  candidate.isdual = TRUE;\n  candidate.lp     = lp;\n  *candidatecount  = 0;\n\n  /* Compute reduced costs */\n  if(!skipupdate) {\n#ifdef UseDualReducedCostUpdate\n    /* Recompute from scratch only at the beginning, otherwise update */\n    if((lp->current_iter > 0) && (refactRecent(lp) < AUTOMATIC))\n      compute_reducedcosts(lp, TRUE, row_nr, NULL, TRUE,\n                               prow, nzprow,\n                               NULL, NULL,\n                               MAT_ROUNDDEFAULT);\n    else\n#endif\n      compute_reducedcosts(lp, TRUE, row_nr, NULL, TRUE,\n                               prow, nzprow,\n                               drow, nzdrow,\n                               MAT_ROUNDDEFAULT);\n  }\n\n#if 0\n  /* Override all above to do in-line testing with fixed test set */\n  if(lp->rows > 1 && lp->columns > 10)\n    longdual_testset(lp, 10, row_nr, prow, nzprow, drow, nzdrow);\n#endif\n\n  /* Compute the current violation of the bounds of the outgoing variable,\n     negative for violation of lower bound, positive for upper bound violation.\n     (Basic variables are always lower-bounded, by lp_solve convention) */\n  g = 1;\n  viol = lp->rhs[row_nr];\n  if(viol > 0) {   /* Check if the leaving variable is >= its upper bound */\n    p = lp->upbo[lp->var_basic[row_nr]];\n    if(p < lp->infinite) {\n      viol -= p;\n      my_roundzero(viol, epsvalue);\n      if(viol > 0)\n        g = -1;\n    }\n    /* Do validation of numerics */\n    if(g == 1) {\n      if(viol >= lp->infinite) {\n        report(lp, IMPORTANT, \"coldual: Large basic solution value %g at iter %.0f indicates numerical instability\\n\",\n                               lp->rhs[row_nr], (double) get_total_iter(lp));\n        lp->spx_status = NUMFAILURE;\n        return( 0 );\n\n      }\n      if(skipupdate)\n        report(lp, DETAILED, \"coldual: Inaccurate bound-flip accuracy at iter %.0f\\n\",\n                              (double) get_total_iter(lp));\n      else\n        report(lp, SEVERE,   \"coldual: Leaving variable %d does not violate bounds at iter %.0f\\n\",\n                              row_nr, (double) get_total_iter(lp));\n      return( -1 );\n    }\n  }\n\n  /* Update local value of pivot setting */\n  lp->_piv_rule_ = get_piv_rule(lp);\n\n  /* Condense list of relevant targets */\n  p = 0;\n  k = 0;\n  nbound = 0;\n  ix = 1;\n  iy = nzprow[0];\n  for(ix = 1; ix <= iy; ix++) {\n    i = nzprow[ix];\n    w = prow[i] * g;            /* Change sign if upper bound of the leaving variable is violated   */\n    /* Change sign if the non-basic variable is currently upper-bounded */\n    /* w *= 2*lp->is_lower[i] - 1; */ /* fails on AIX!!! */\n    w = my_chsign(!lp->is_lower[i], w);\n\n    /* Check if the candidate is worth using for anything */\n    if(w < -epsvalue) {\n      /* Tally bounded variables */\n      if(lp->upbo[i] < lp->infinite)\n        nbound++;\n\n      /* Update the nz-index */\n      k++;\n      nzprow[k] = i;\n      SETMAX(p, -w);\n    }\n#ifdef Paranoia\n    else {\n      if(lp->spx_trace) {\n        report(lp, FULL, \"coldual: Candidate variable prow[%d] rejected with %g too small\\n\",\n                         i, w);\n      }\n    }\n#endif\n\n  }\n  nzprow[0] = k;\n  if(xviol != NULL)\n    *xviol = p;\n\n#ifdef UseRelativePivot_Dual\n/*  epspivot *= sqrt(lp->matA->dynrange) / lp->matA->infnorm; */\n  epspivot /= MAX(1, sqrt(lp->matA->rowmax[row_nr]));\n#endif\n  current.epspivot   = epspivot;\n  candidate.epspivot = epspivot;\n\n  /* Initialize the long-step structures if indicated */\n  if(dolongsteps) {\n    if((nzprow[0] <= 1) || (nbound == 0)) {  /* Don't bother */\n      dolongsteps = FALSE;\n      lp->longsteps->indexSet[0] = 0;\n    }\n    else {\n      multi_restart(lp->longsteps);\n      multi_valueInit(lp->longsteps, g*viol, lp->rhs[0]);\n    }\n  }\n\n  /* Loop over all entering column candidates */\n  ix = 1;\n  iy = nzprow[0];\n  makePriceLoop(lp, &ix, &iy, &iz);\n  iy *= iz;\n  for(; ix*iz <= iy; ix += iz) {\n    i = nzprow[ix];\n\n    /* Compute the dual ratio (prow = w and drow = cbar in Chvatal's \"nomenclatura\") */\n    w    = prow[i] * g;         /* Change sign if upper bound of the leaving variable is violated   */\n    quot = -drow[i] / w;        /* Remember this sign-reversal in multi_recompute!                  */\n\n    /* Apply the selected pivot strategy (smallest theta) */\n    candidate.theta = quot;  /* Note that abs() is applied in findSubstitutionVar */\n    candidate.pivot = w;\n    candidate.varno = i;\n\n    /* Collect candidates for minor iterations/bound flips */\n    if(dolongsteps) {\n      if(isbatch && (ix == iy))\n        isbatch = AUTOMATIC;\n      if(collectMinorVar(&candidate, lp->longsteps, (MYBOOL) (dolongsteps == AUTOMATIC), isbatch) &&\n         lp->spx_trace)\n        report(lp, DETAILED, \"coldual: Long-dual break point with %d bound-flip variables\\n\",\n                             lp->longsteps->used);\n      if(lp->spx_status == FATHOMED)\n        return( 0 );\n    }\n\n    /* We have a candidate for entering the basis; check if it is better than the incumbent */\n    else if(findSubstitutionVar(&current, &candidate, candidatecount))\n      break;\n  }\n\n  /* Set entering variable and long-step bound swap variables */\n  if(dolongsteps) {\n    *candidatecount = lp->longsteps->used;\n    i = multi_enteringvar(lp->longsteps, NULL, 3);\n  }\n  else\n    i = current.varno;\n\n  if(lp->spx_trace)\n    report(lp, NORMAL, \"coldual: Entering column %d, reduced cost %g, pivot value %g, bound swaps %d\\n\",\n                       i, drow[i], prow[i], multi_used(lp->longsteps));\n\n  return( i );\n} /* coldual */\n\n\nINLINE REAL normalizeEdge(lprec *lp, int item, REAL edge, MYBOOL isdual)\n{\n#if 1\n  /* Don't use the pricer \"close to home\", since this can possibly\n    worsen the final feasibility picture (mainly a Devex issue?) */\n  if(fabs(edge) > lp->epssolution)\n#endif\n    edge /= getPricer(lp, item, isdual);\n  if((lp->piv_strategy & PRICE_RANDOMIZE) != 0)\n    edge *= (1.0-PRICER_RANDFACT) + PRICER_RANDFACT*rand_uniform(lp, 1.0);\n  return( edge );\n\n}\n\n/* Support routines for block detection and partial pricing */\nSTATIC int partial_findBlocks(lprec *lp, MYBOOL autodefine, MYBOOL isrow)\n{\n  int    i, jj, n, nb, ne, items;\n  REAL   hold, biggest, *sum = NULL;\n  MATrec *mat = lp->matA;\n  partialrec *blockdata;\n\n  if(!mat_validate(mat))\n    return( 1 );\n\n  blockdata = IF(isrow, lp->rowblocks, lp->colblocks);\n  items     = IF(isrow, lp->rows, lp->columns);\n  allocREAL(lp, &sum, items+1, FALSE);\n\n  /* Loop over items and compute the average column index for each */\n  sum[0] = 0;\n  for(i = 1; i <= items; i++) {\n    n = 0;\n    if(isrow) {\n      nb = mat->row_end[i-1];\n      ne = mat->row_end[i];\n    }\n    else {\n      nb = mat->col_end[i-1];\n      ne = mat->col_end[i];\n    }\n    n = ne-nb;\n    sum[i] = 0;\n    if(n > 0) {\n      if(isrow)\n        for(jj = nb; jj < ne; jj++)\n          sum[i] += ROW_MAT_COLNR(jj);\n      else\n        for(jj = nb; jj < ne; jj++)\n          sum[i] += COL_MAT_ROWNR(jj);\n      sum[i] /= n;\n    }\n    else\n      sum[i] = sum[i-1];\n  }\n\n  /* Loop over items again, find largest difference and make monotone */\n  hold = 0;\n  biggest = 0;\n  for(i = 2; i <= items; i++) {\n    hold = sum[i] - sum[i-1];\n    if(hold > 0) {\n      if(hold > biggest)\n        biggest = hold;\n    }\n    else\n      hold = 0;\n    sum[i-1] = hold;\n  }\n\n  /* Loop over items again and find differences exceeding threshold;\n     the discriminatory power of this routine depends strongly on the\n     magnitude of the scaling factor - from empirical evidence > 0.9 */\n  biggest = MAX(1, 0.9*biggest);\n  n = 0;\n  nb = 0;\n  ne = 0;\n  for(i = 1; i < items; i++)\n    if(sum[i] > biggest) {\n      ne += i-nb;        /* Compute sum of index gaps between maxima */\n      nb = i;\n      n++;               /* Increment count */\n    }\n\n  /* Clean up */\n  FREE(sum);\n\n  /* Require that the maxima are spread \"nicely\" across the columns,\n     otherwise return that there is only one monolithic block.\n     (This is probably an area for improvement in the logic!) */\n  if(n > 0) {\n    ne /= n;                 /* Average index gap between maxima */\n    i = IF(isrow, lp->columns, lp->rows);\n    nb = i / ne;             /* Another estimated block count */\n    if(abs(nb - n) > 2)      /* Probably Ok to require equality (nb==n)*/\n      n = 1;\n    else if(autodefine)      /* Generate row/column break-indeces for partial pricing */\n      set_partialprice(lp, nb, NULL, isrow);\n  }\n  else\n    n = 1;\n\n  return( n );\n}\nSTATIC int partial_blockStart(lprec *lp, MYBOOL isrow)\n{\n  partialrec *blockdata;\n\n  blockdata = IF(isrow, lp->rowblocks, lp->colblocks);\n  if(blockdata == NULL)\n    return( 1 );\n  else {\n    if((blockdata->blocknow < 1) || (blockdata->blocknow > blockdata->blockcount))\n      blockdata->blocknow = 1;\n    return( blockdata->blockend[blockdata->blocknow-1] );\n  }\n}\nSTATIC int partial_blockEnd(lprec *lp, MYBOOL isrow)\n{\n  partialrec *blockdata;\n\n  blockdata = IF(isrow, lp->rowblocks, lp->colblocks);\n  if(blockdata == NULL)\n    return( IF(isrow, lp->rows, lp->sum) );\n  else {\n    if((blockdata->blocknow < 1) || (blockdata->blocknow > blockdata->blockcount))\n      blockdata->blocknow = 1;\n    return( blockdata->blockend[blockdata->blocknow]-1 );\n  }\n}\nSTATIC int partial_blockNextPos(lprec *lp, int block, MYBOOL isrow)\n{\n  partialrec *blockdata;\n\n  blockdata = IF(isrow, lp->rowblocks, lp->colblocks);\n#ifdef Paranoia\n  if((blockdata == NULL) || (block <= 1) || (block > blockdata->blockcount)) {\n    report(lp, SEVERE, \"partial_blockNextPos: Invalid block %d specified.\\n\",\n                       block);\n    return( -1 );\n  }\n#endif\n  block--;\n  if(blockdata->blockpos[block] == blockdata->blockend[block+1])\n    blockdata->blockpos[block] = blockdata->blockend[block];\n  else\n    blockdata->blockpos[block]++;\n  return( blockdata->blockpos[block] );\n}\nSTATIC MYBOOL partial_blockStep(lprec *lp, MYBOOL isrow)\n{\n  partialrec *blockdata;\n\n  blockdata = IF(isrow, lp->rowblocks, lp->colblocks);\n  if(blockdata == NULL)\n    return( FALSE );\n  else if(blockdata->blocknow < blockdata->blockcount) {\n    blockdata->blocknow++;\n    return( TRUE);\n  }\n  else {\n    blockdata->blocknow = 1;\n    return( TRUE );\n  }\n}\nSTATIC MYBOOL partial_isVarActive(lprec *lp, int varno, MYBOOL isrow)\n{\n  partialrec *blockdata;\n\n  blockdata = IF(isrow, lp->rowblocks, lp->colblocks);\n  if(blockdata == NULL)\n    return( TRUE );\n  else {\n    return( (MYBOOL) ((varno >= blockdata->blockend[blockdata->blocknow-1]) &&\n                      (varno < blockdata->blockend[blockdata->blocknow])) );\n  }\n}\n\n\n/* Multiple pricing routines */\nSTATIC multirec *multi_create(lprec *lp, MYBOOL truncinf)\n{\n  multirec *multi;\n\n  multi = (multirec *) calloc(1, sizeof(*multi));\n  if(multi != NULL) {\n    multi->active = 1;\n    multi->lp = lp;\n    multi->epszero = lp->epsprimal;\n    multi->truncinf = truncinf;\n  }\n\n  return(multi);\n}\nSTATIC void multi_free(multirec **multi)\n{\n  if((multi == NULL) || (*multi == NULL))\n    return;\n  FREE((*multi)->items);\n  FREE((*multi)->valueList);\n  FREE((*multi)->indexSet);\n  FREE((*multi)->freeList);\n  FREE((*multi)->sortedList);\n  FREE(*multi);\n}\nSTATIC MYBOOL multi_mustupdate(multirec *multi)\n{\n  return( (MYBOOL) ((multi != NULL) &&\n                     (multi->used < multi->limit)) );\n}\nSTATIC MYBOOL multi_resize(multirec *multi, int blocksize, int blockdiv, MYBOOL doVlist, MYBOOL doIset)\n{\n  MYBOOL ok = TRUE;\n\n  if((blocksize > 1) && (blockdiv > 0)) {\n    int oldsize = multi->size;\n\n    multi->size = blocksize;\n    if(blockdiv > 1)\n      multi->limit += (multi->size-oldsize) / blockdiv;\n\n    multi->items = (pricerec *) realloc(multi->items, (multi->size+1)*sizeof(*(multi->items)));\n    multi->sortedList = (UNIONTYPE QSORTrec *) realloc(multi->sortedList, (multi->size+1)*sizeof(*(multi->sortedList)));\n    ok = (multi->items != NULL) && (multi->sortedList != NULL) &&\n         allocINT(multi->lp, &(multi->freeList), multi->size+1, AUTOMATIC);\n    if(ok) {\n      int i, n;\n\n      if(oldsize == 0)\n        i = 0;\n      else\n        i = multi->freeList[0];\n      multi->freeList[0] = i + (multi->size-oldsize);\n      for(n = multi->size - 1, i++; i <= multi->freeList[0]; i++, n--)\n        multi->freeList[i] = n;\n    }\n    if(doVlist)\n      ok &= allocREAL(multi->lp, &(multi->valueList), multi->size+1, AUTOMATIC);\n    if(doIset) {\n      ok &= allocINT(multi->lp, &(multi->indexSet), multi->size+1, AUTOMATIC);\n      if(ok && (oldsize == 0))\n        multi->indexSet[0] = 0;\n    }\n    if(!ok)\n      goto Undo;\n\n  }\n  else {\nUndo:\n    multi->size = 0;\n    FREE(multi->items);\n    FREE(multi->valueList);\n    FREE(multi->indexSet);\n    FREE(multi->freeList);\n    FREE(multi->sortedList);\n  }\n  multi->active = 1;\n\n  return( ok );\n}\n\nSTATIC int multi_size(multirec *multi)\n{\n  if(multi == NULL)\n    return( 0 );\n  else\n    return( multi->size );\n}\n\nSTATIC int multi_used(multirec *multi)\n{\n  if(multi == NULL)\n    return( 0 );\n  else\n    return( multi->used );\n}\n\nSTATIC int multi_restart(multirec *multi)\n{\n  int i, n = multi->used;\n\n  multi->used   = 0;\n  multi->sorted = FALSE;\n  multi->dirty  = FALSE;\n  if(multi->freeList != NULL) {\n    for(i = 1; i <= multi->size; i++)\n      multi->freeList[i] = multi->size - i;\n    multi->freeList[0] = multi->size;\n  }\n#if 0\n  if(multi->indexSet != NULL)\n    multi->indexSet[0] = 0;\n#endif\n  return( n );\n}\n\nSTATIC void multi_valueInit(multirec *multi, REAL step_base, REAL obj_base)\n{\n  multi->step_base = multi->step_last = step_base;\n  multi->obj_base  = multi->obj_last  = obj_base;\n#ifdef Paranoia\n  if(step_base > 0)\n    report(multi->lp, SEVERE, \"multi_valueInit: Positive constraint violation %g provided at iteration %6.0f\\n\",\n                              step_base, (double) get_total_iter(multi->lp));\n#endif\n}\n\nSTATIC REAL *multi_valueList(multirec *multi)\n{\n  return(multi->valueList);\n}\n\nSTATIC int *multi_indexSet(multirec *multi, MYBOOL regenerate)\n{\n  if(regenerate)\n    multi_populateSet(multi, NULL, -1);\n  return(multi->indexSet);\n}\n\nSTATIC int multi_getvar(multirec *multi, int item)\n{\n#ifdef Paranoia\n  if((item < 1) || (item >= multi->size))\n    return(-1);\n#endif\n  return( ((pricerec *) &(multi->sortedList[item].pvoidreal.ptr))->varno );\n}\n\nSTATIC MYBOOL multi_recompute(multirec *multi, int index, MYBOOL isphase2, MYBOOL fullupdate)\n{\n  int      i, n;\n  REAL     lB, uB, Alpha, this_theta, prev_theta;\n  lprec    *lp = multi->lp;\n  pricerec *thisprice;\n\n  /* Define target update window */\n  if(multi->dirty) {\n    index = 0;\n    n = multi->used - 1;\n  }\n  else if(fullupdate)\n    n = multi->used - 1;\n  else\n    n = index;\n\n  /* Initialize accumulators from the specified update index */\n  if(index == 0) {\n    multi->maxpivot = 0;\n    multi->maxbound = 0;\n    multi->step_last = multi->step_base;\n    multi->obj_last  = multi->obj_base;\n    thisprice  = NULL;\n    this_theta  = 0;\n  }\n  else {\n    multi->obj_last  = multi->valueList[index-1];\n    multi->step_last = multi->sortedList[index-1].pvoidreal.realval;\n    thisprice  = (pricerec *) (multi->sortedList[index-1].pvoidreal.ptr);\n    this_theta = thisprice->theta;\n  }\n\n  /* Update step lengths and objective values */\n  while((index <= n) && (multi->step_last < multi->epszero)) {\n\n    /* Update parameters for this loop */\n    prev_theta = this_theta;\n    thisprice  = (pricerec *) (multi->sortedList[index].pvoidreal.ptr);\n    this_theta = thisprice->theta;\n    Alpha = fabs(thisprice->pivot);\n    uB = lp->upbo[thisprice->varno];\n    lB = 0;\n    SETMAX(multi->maxpivot, Alpha);\n    SETMAX(multi->maxbound, uB);\n\n    /* Do the value updates */\n    if(isphase2) {\n      multi->obj_last += (this_theta - prev_theta) * multi->step_last; /* Sign-readjusted from coldual()/Maros */\n      if(uB >= lp->infinite)\n        multi->step_last  = lp->infinite;\n      else\n        multi->step_last += Alpha*(uB-lB);\n    }\n    else {\n      multi->obj_last += (this_theta - prev_theta) * multi->step_last; /* Sign-readjusted from coldual()/Maros */\n      multi->step_last += Alpha;\n    }\n\n    /* Store updated values at the indexed locations */\n    multi->sortedList[index].pvoidreal.realval = multi->step_last;\n    multi->valueList[index] = multi->obj_last;\n#ifdef Paranoia\n    if(lp->spx_trace &&\n       (multi->step_last > lp->infinite))\n      report(lp, SEVERE, \"multi_recompute: A very large step-size %g was generated at iteration %6.0f\\n\",\n                         multi->step_last, (double) get_total_iter(lp));\n#endif\n    index++;\n  }\n\n  /* Discard candidates entered earlier that now make the OF worsen, and\n     make sure that the released positions are added to the free list. */\n  n = index;\n  while(n < multi->used) {\n    i = ++multi->freeList[0];\n    multi->freeList[i] = (int) (((pricerec *) multi->sortedList[n].pvoidreal.ptr) - multi->items);\n    n++;\n  }\n  multi->used  = index;\n  if(multi->sorted && (index == 1))\n    multi->sorted = FALSE;\n  multi->dirty = FALSE;\n\n  /* Return TRUE if the step is now positive */\n  return( (MYBOOL) (multi->step_last >= multi->epszero) );\n}\n\nSTATIC MYBOOL multi_truncatingvar(multirec *multi, int varnr)\n{\n  return( multi->truncinf && is_infinite(multi->lp, multi->lp->upbo[varnr]) );\n}\n\nSTATIC MYBOOL multi_removevar(multirec *multi, int varnr)\n{\n  int i = 1;\n  int *coltarget = multi->indexSet;\n\n  if(coltarget == NULL)\n    return( FALSE );\n\n  while((i <= multi->used) && (coltarget[i] != varnr))\n    i++;\n  if(i > multi->used)\n    return( FALSE );\n\n  for(; i < multi->used; i++)\n    coltarget[i] = coltarget[i+1];\n  coltarget[0]--;\n  multi->used--;\n  multi->dirty = TRUE;\n  return( TRUE );\n}\n\nSTATIC int multi_enteringvar(multirec *multi, pricerec *current, int priority)\n{\n  lprec    *lp = multi->lp;\n  int      i = 0, bestindex, colnr;\n  REAL     bound, score, bestscore = -lp->infinite;\n  REAL     b1, b2, b3;\n  pricerec *candidate, *bestcand;\n\n  /* Check that we have a candidate */\n  multi->active = bestindex = 0;\n  if((multi == NULL) || (multi->used == 0))\n    return( bestindex );\n\n  /* Check for pruning possibility of the B&B tree */\n  if(multi->objcheck && (lp->solutioncount > 0) &&\n     bb_better(lp, OF_WORKING | OF_PROJECTED, OF_TEST_WE)) {\n    lp->spx_status = FATHOMED;\n    return( bestindex );\n  }\n\n  /* Check the trivial case */\n  if(multi->used == 1) {\n    bestcand = (pricerec *) (multi->sortedList[bestindex].pvoidreal.ptr);\n    goto Finish;\n  }\n\n  /* Set priority weights */\nRedo:\n  switch(priority) {\n    case 0:  b1 = 0.0, b2 = 0.0, b3 = 1.0;          /* Only OF          */\n              bestindex = multi->used - 2;   break;\n    case 1:  b1 = 0.2, b2 = 0.3, b3 = 0.5; break;  /* Emphasize OF     */\n    case 2:  b1 = 0.3, b2 = 0.5, b3 = 0.2; break;  /* Emphasize bound  */\n    case 3:  b1 = 0.6, b2 = 0.2, b3 = 0.2; break;  /* Emphasize pivot  */\n    case 4:  b1 = 1.0, b2 = 0.0, b3 = 0.0; break;  /* Only pivot       */\n    default: b1 = 0.4, b2 = 0.2, b3 = 0.4;         /* Balanced default */\n  }\n  bestcand = (pricerec *) (multi->sortedList[bestindex].pvoidreal.ptr);\n\n  /* Loop over all candidates to get the best entering candidate;\n     start at the end to try to maximize the chain length */\n  for(i = multi->used - 1; i >= 0; i--) {\n    candidate = (pricerec *) (multi->sortedList[i].pvoidreal.ptr);\n    colnr = candidate->varno;\n    bound = lp->upbo[colnr];\n    score = fabs(candidate->pivot) / multi->maxpivot;\n    score = pow(1.0 + score                           , b1) *\n            pow(1.0 + log(bound / multi->maxbound + 1), b2) *\n            pow(1.0 + (REAL) i / multi->used          , b3);\n    if(score > bestscore) {\n      bestscore = score;\n      bestindex = i;\n      bestcand  = candidate;\n    }\n  }\n\n  /* Do pivot protection */\n  if((priority < 4) && (fabs(bestcand->pivot) < lp->epssolution)) {\n    bestindex = 0;\n    priority++;\n    goto Redo;\n  }\n\nFinish:\n  /* Make sure we shrink the list and update */\n  multi->active = colnr = bestcand->varno;\n  if(bestindex < multi->used - 1) {\n#if 0\n/*    if(lp->upbo[colnr] >= lp->infinite) */\n    QS_swap(multi->sortedList, bestindex, multi->used-1);\n    multi_recompute(multi, bestindex, (bestcand->isdual == AUTOMATIC), TRUE);\n#else\n    multi->used = i + 1;\n#endif\n  }\n  multi_populateSet(multi, NULL, multi->active);\n\n  /* Compute the entering theta and update parameters */\n  score = (multi->used == 1 ? multi->step_base : multi->sortedList[multi->used-2].pvoidreal.realval);\n  score /= bestcand->pivot;\n  score = my_chsign(!lp->is_lower[multi->active], score);\n\n  if(lp->spx_trace &&\n     (fabs(score) > 1/lp->epsprimal))\n    report(lp, IMPORTANT, \"multi_enteringvar: A very large Theta %g was generated (pivot %g)\\n\",\n                       score, bestcand->pivot);\n  multi->step_base = score;\n  if(current != NULL)\n    *current = *bestcand;\n\n  return( multi->active );\n}\n\nSTATIC REAL multi_enteringtheta(multirec *multi)\n{\n  return( multi->step_base );\n}\n\nSTATIC int multi_populateSet(multirec *multi, int **list, int excludenr)\n{\n  int n = 0;\n  if(list == NULL)\n    list = &(multi->indexSet);\n  if((multi->used > 0) &&\n     ((*list != NULL) || allocINT(multi->lp, list, multi->size+1, FALSE))) {\n    int i, colnr;\n\n    for(i = 0; i < multi->used; i++) {\n      colnr = ((pricerec *) (multi->sortedList[i].pvoidreal.ptr))->varno;\n      if((colnr != excludenr) &&\n        /* Prevent an unbounded variable from \"bound-flip\"; this could\n          actually indicate that we should let the entering variable be\n          bound-swapped (in the case that it is bounded), but we\n          disregard this possibility here, since it brings with it\n          issues of pivot size, etc. */\n        ((excludenr > 0) && (multi->lp->upbo[colnr] < multi->lp->infinite))) {\n        n++;\n        (*list)[n] = colnr;\n      }\n    }\n    (*list)[0] = n;\n  }\n  return( n );\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_price.h",
    "content": "#ifndef HEADER_lp_price\n#define HEADER_lp_price\n\n/* Local defines                                                             */\n/* ------------------------------------------------------------------------- */\n#define UseSortOnBound_Improve\n/*#define UseSortOnBound_Substitute*/\n\n#if 0 /* Stricter feasibility-preserving tolerance; use w/ *_UseRejectionList */\n  #define UseRelativeFeasibility       /* Use machine-precision and A-scale data */\n#endif\n#if 0          /* Stricter pivot-selection criteria; use w/ *UseRejectionList */\n  #define UseRelativePivot_Primal             /* In rowprim based on A-scale data */\n  #define UseRelativePivot_Dual               /* In coldual based on A-scale data */\n#endif\n\n\n/* Include required library headers                                          */\n/* ------------------------------------------------------------------------- */\n#include \"lp_types.h\"\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Comparison and validity routines */\nint CMP_CALLMODEL compareImprovementVar(const pricerec *current, const pricerec *candidate);\nint CMP_CALLMODEL compareSubstitutionVar(const pricerec *current, const pricerec *candidate);\nint CMP_CALLMODEL compareBoundFlipVar(const pricerec *current, const pricerec *candidate);\nSTATIC int addCandidateVar(pricerec *candidate, multirec *multi, findCompare_func findCompare, MYBOOL allowSortedExpand);\nSTATIC MYBOOL collectMinorVar(pricerec *candidate, multirec *longsteps, MYBOOL isphase2, MYBOOL isbatch);\nSTATIC MYBOOL validImprovementVar(pricerec *candidate);\nSTATIC MYBOOL validSubstitutionVar(pricerec *candidate);\n\n/* Row+column selection routines */\nSTATIC MYBOOL findImprovementVar(pricerec *current, pricerec *candidate, MYBOOL collectMP, int *candidatecount);\nSTATIC MYBOOL findSubstitutionVar(pricerec *current, pricerec *candidate, int *candidatecount);\nINLINE REAL normalizeEdge(lprec *lp, int item, REAL edge, MYBOOL isdual);\nSTATIC void makePriceLoop(lprec *lp, int *start, int *end, int *delta);\n\n/* Computation of reduced costs */\nSTATIC void update_reducedcosts(lprec *lp, MYBOOL isdual, int leave_nr, int enter_nr, REAL *prow, REAL *drow);\nSTATIC void compute_reducedcosts(lprec *lp, MYBOOL isdual, int row_nr, int *coltarget, MYBOOL dosolve,\n                                                            REAL *prow, int *nzprow,\n                                                            REAL *drow, int *nzdrow,\n                                                            int roundmode);\n\n/* Leaving variable selection and entering column pricing loops */\nSTATIC int find_rowReplacement(lprec *lp, int rownr, REAL *prow, int *nzprow);\nSTATIC int colprim(lprec *lp, REAL *drow, int *nzdrow,\n                              MYBOOL skipupdate, int partialloop, int *candidatecount, MYBOOL updateinfeas, REAL *xviol);\nSTATIC int rowprim(lprec *lp, int colnr, LREAL *theta, REAL *pcol, int *nzpcol, MYBOOL forceoutEQ, REAL *xviol);\nSTATIC int rowdual(lprec *lp, REAL *rhvec, MYBOOL forceoutEQ, MYBOOL updateinfeas, REAL *xviol);\nSTATIC int coldual(lprec *lp, int row_nr,\n                              REAL *prow, int *nzprow, REAL *drow, int *nzdrow,\n                              MYBOOL dualphase1, MYBOOL skipupdate,\n                              int *candidatecount, REAL *xviol);\n\n/* Partial pricing management routines */\nSTATIC partialrec *partial_createBlocks(lprec *lp, MYBOOL isrow);\nSTATIC int partial_countBlocks(lprec *lp, MYBOOL isrow);\nSTATIC int partial_activeBlocks(lprec *lp, MYBOOL isrow);\nSTATIC void partial_freeBlocks(partialrec **blockdata);\n\n/* Partial pricing utility routines */\nSTATIC int partial_findBlocks(lprec *lp, MYBOOL autodefine, MYBOOL isrow);\nSTATIC int partial_blockStart(lprec *lp, MYBOOL isrow);\nSTATIC int partial_blockEnd(lprec *lp, MYBOOL isrow);\nSTATIC int partial_blockNextPos(lprec *lp, int block, MYBOOL isrow);\n\nSTATIC MYBOOL partial_blockStep(lprec *lp, MYBOOL isrow);\nSTATIC MYBOOL partial_isVarActive(lprec *lp, int varno, MYBOOL isrow);\n\n/* Multiple pricing / dual long step management routines */\nSTATIC multirec *multi_create(lprec *lp, MYBOOL truncinf);\nSTATIC MYBOOL multi_resize(multirec *multi, int blocksize, int blockdiv, MYBOOL doVlist, MYBOOL doIset);\nSTATIC int multi_restart(multirec *multi);\nSTATIC int multi_size(multirec *multi);\nSTATIC int multi_used(multirec *multi);\nSTATIC MYBOOL multi_truncatingvar(multirec *multi, int varnr);\nSTATIC MYBOOL multi_mustupdate(multirec *multi);\nSTATIC void multi_valueInit(multirec *multi, REAL step_base, REAL obj_base);\nSTATIC REAL *multi_valueList(multirec *multi);\nSTATIC int *multi_indexSet(multirec *multi, MYBOOL regenerate);\nSTATIC int multi_getvar(multirec *multi, int item);\nSTATIC MYBOOL multi_recompute(multirec *multi, int index, MYBOOL isphase2, MYBOOL fullupdate);\nSTATIC MYBOOL multi_removevar(multirec *multi, int varnr);\nSTATIC int multi_enteringvar(multirec *multi, pricerec *current, int priority);\nSTATIC REAL multi_enteringtheta(multirec *multi);\nSTATIC void multi_free(multirec **multi);\nSTATIC int multi_populateSet(multirec *multi, int **list, int excludenr);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_price */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_pricePSE.c",
    "content": "\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_report.h\"\n#include \"lp_pricePSE.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n/*\n    Advanced simplex price scaling modules - w/interface for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Kjell Eikland\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      lp_lib.h\n\n    Release notes:\n    v1.0.0  1 September 2003    Implementation of DEVEX and STEEPEST EDGE\n                                routines for the primal and dual simplex.\n    v1.0.1  1 January 2004      Made initial value of weight of ingoing\n                                variable for the standard mode of DEVEX\n                                consistent with the initialization at restart;\n                                original version could at worst contribute\n                                to cycling.\n    v1.0.2  23 March 2004       Added floors to Steepest Edge updates and\n                                moved tests for tiny update higher. Previous\n                                logic can be simulated by disabling the compiler\n                                define ApplySteepestEdgeMinimum.\n    v1.1.0  1 July 2004         Renamed from lp_pricerPSE to lp_pricePSE in\n                                conjuction with the creation of a separate\n                                price library.\n    v1.2.0  1 March 2005        Changed memory allocation routines to use\n                                standard lp_solve functions, improve error handling\n                                and return boolean status values.\n\n   ----------------------------------------------------------------------------------\n*/\n\nINLINE MYBOOL applyPricer(lprec *lp)\n{\n  int rule = get_piv_rule(lp);\n  return( (MYBOOL) ((rule == PRICER_DEVEX) || (rule == PRICER_STEEPESTEDGE)) );\n}\n\n\nSTATIC void simplexPricer(lprec *lp, MYBOOL isdual)\n{\n  if(lp->edgeVector != NULL)\n    lp->edgeVector[0] = (REAL) isdual;\n}\n\n\nSTATIC void freePricer(lprec *lp)\n{\n  FREE(lp->edgeVector);\n}\n\n\nSTATIC MYBOOL resizePricer(lprec *lp)\n{\n  if(!applyPricer(lp))\n    return( TRUE );\n\n  /* Reallocate vector for new size */\n  if(!allocREAL(lp, &(lp->edgeVector), lp->sum_alloc+1, AUTOMATIC))\n    return( FALSE );\n\n  /* Signal that we have not yet initialized the price vector */\n  MEMCLEAR(lp->edgeVector, lp->sum_alloc+1);\n  lp->edgeVector[0] = -1;\n  return( TRUE );\n}\n\n\nSTATIC MYBOOL initPricer(lprec *lp)\n{\n  if(!applyPricer(lp))\n    return( FALSE );\n\n  /* Free any pre-existing pricer */\n  freePricer(lp);\n\n  /* Allocate vector to fit current problem size */\n  return( resizePricer(lp) );\n}\n\n\nSTATIC REAL getPricer(lprec *lp, int item, MYBOOL isdual)\n{\n  REAL value = 1.0;\n\n  if(!applyPricer(lp))\n    return( value );\n\n  value = *lp->edgeVector;\n\n  /* Make sure we have a price vector to use */\n  if(value < 0) {\n#ifdef Paranoia\n    report(lp, SEVERE, \"getPricer: Called without having being initialized!\\n\");\n#endif\n    return( 1.0 );\n  }\n  /* We may be calling the primal from the dual (and vice-versa) for validation\n     of feasibility; ignore calling origin and simply return 1 */\n  else if(isdual != value) {\n    return( 1.0 );\n  }\n  /* Do the normal norm retrieval */\n  else {\n\n    if(isdual)\n      item = lp->var_basic[item];\n\n    value = lp->edgeVector[item];\n\n    if(value == 0) {\n      value = 1.0;\n      report(lp, SEVERE, \"getPricer: Detected a zero-valued price at index %d\\n\", item);\n    }\n#ifdef Paranoia\n    else if(value < 0)\n      report(lp, SEVERE, \"getPricer: Invalid %s reduced cost norm %g at index %d\\n\",\n                          my_if(isdual, \"dual\", \"primal\"), value, item);\n#endif\n\n  /* Return the norm */\n    return( sqrt(value) );\n  }\n}\n\nSTATIC MYBOOL restartPricer(lprec *lp, MYBOOL isdual)\n{\n  REAL   *sEdge = NULL, seNorm, hold;\n  int    i, j, m;\n  MYBOOL isDEVEX, ok = applyPricer(lp);\n\n  if(!ok)\n    return( ok );\n\n  /* Store the active/current pricing type */\n  if(isdual == AUTOMATIC)\n    isdual = (MYBOOL) lp->edgeVector[0];\n  else\n    lp->edgeVector[0] = isdual;\n\n  m = lp->rows;\n\n  /* Determine strategy and check if we have strategy fallback for the primal */\n  isDEVEX = is_piv_rule(lp, PRICER_DEVEX);\n  if(!isDEVEX && !isdual)\n    isDEVEX = is_piv_mode(lp, PRICE_PRIMALFALLBACK);\n\n  /* Check if we only need to do the simple DEVEX initialization */\n  if(!is_piv_mode(lp, PRICE_TRUENORMINIT)) {\n    if(isdual) {\n      for(i = 1; i <= m; i++)\n        lp->edgeVector[lp->var_basic[i]] = 1.0;\n    }\n    else {\n      for(i = 1; i <= lp->sum; i++)\n        if(!lp->is_basic[i])\n          lp->edgeVector[i] = 1.0;\n    }\n    return( ok );\n  }\n\n  /* Otherwise do the full Steepest Edge norm initialization */\n  ok = allocREAL(lp, &sEdge, m+1, FALSE);\n  if(!ok)\n    return( ok );\n\n  if(isdual) {\n\n   /* Extract the rows of the basis inverse and compute their squared norms */\n\n    for(i = 1; i <= m; i++) {\n\n      bsolve(lp, i, sEdge, NULL, 0, 0.0);\n\n      /* Compute the edge norm */\n      seNorm = 0;\n      for(j = 1; j <= m; j++) {\n        hold = sEdge[j];\n        seNorm += hold*hold;\n      }\n\n      j = lp->var_basic[i];\n      lp->edgeVector[j] = seNorm;\n    }\n\n  }\n  else {\n\n   /* Solve a=Bb for b over all non-basic variables and compute their squared norms */\n\n    for(i = 1; i <= lp->sum; i++) {\n      if(lp->is_basic[i])\n        continue;\n\n      fsolve(lp, i, sEdge, NULL, 0, 0.0, FALSE);\n\n      /* Compute the edge norm */\n      seNorm = 1;\n      for(j = 1; j <= m; j++) {\n        hold = sEdge[j];\n        seNorm += hold*hold;\n      }\n\n      lp->edgeVector[i] = seNorm;\n    }\n\n  }\n\n  FREE(sEdge);\n\n  return( ok );\n\n}\n\n\nSTATIC MYBOOL formWeights(lprec *lp, int colnr, REAL *pcol, REAL **w)\n/* This computes Bw = a, where B is the basis and a is a column of A */\n{\n  MYBOOL ok = allocREAL(lp, w, lp->rows+1, FALSE);\n\n  if(ok) {\n    if(pcol == NULL)\n      fsolve(lp, colnr, *w, NULL, 0.0, 0.0, FALSE);\n    else {\n      MEMCOPY(*w, pcol, lp->rows+1);\n/*    *w[0] = 0; */ /* Test */\n    }\n  }\n/*\n  if(pcol != NULL) {\n    REAL cEdge, hold;\n    int  i;\n\n    cEdge = 0;\n    for(i = 1; i <= m; i++) {\n      hold = *w[i]-pcol[i];\n      cEdge += hold*hold;\n    }\n    cEdge /= m;\n    cEdge = sqrt(cEdge);\n    if(cEdge > lp->epspivot)\n      report(lp, SEVERE, \"updatePricer: MRS error is %g\\n\", cEdge);\n  }\n*/\n  return(ok);\n}\nSTATIC void freeWeights(REAL *w)\n{\n  FREE(w);\n}\n\n\nSTATIC MYBOOL updatePricer(lprec *lp, int rownr, int colnr, REAL *pcol, REAL *prow, int *nzprow)\n{\n  REAL   *vEdge = NULL, cEdge, hold, *newEdge, *w = NULL;\n  int    i, m, n, exitcol, errlevel = DETAILED;\n  MYBOOL forceRefresh = FALSE, isDual, isDEVEX, ok = FALSE;\n\n  if(!applyPricer(lp))\n    return(ok);\n\n  /* Make sure we have something to update */\n  hold = lp->edgeVector[0];\n  if(hold < 0)\n    return(ok);\n  isDual = (MYBOOL) (hold > 0);\n\n  /* Do common initializations and computations */\n  m = lp->rows;\n  n = lp->sum;\n  isDEVEX = is_piv_rule(lp, PRICER_DEVEX);\n  exitcol = lp->var_basic[rownr];\n\n  /* Solve/copy Bw = a */\n#if 0\n  ok = formWeights(lp, colnr, NULL, &w);  /* Compute from scratch - Experimental */\n#else\n  ok = formWeights(lp, colnr, pcol, &w);  /* Use previously computed values */\n#endif\n  if(!ok)\n    return( ok );\n\n  /* Price norms for the dual simplex - the basic columns */\n  if(isDual) {\n    REAL rw;\n    int  targetcol;\n\n    /* Don't need to compute cross-products with DEVEX */\n    if(!isDEVEX) {\n      ok = allocREAL(lp, &vEdge, m+1, FALSE);\n      if(!ok)\n        return( ok );\n\n    /* Extract the row of the inverse containing the leaving variable\n       and then form the dot products against the other variables, i.e. \"Tau\" */\n#if 0 /* Extract row explicitly */\n      bsolve(lp, rownr, vEdge, 0, 0.0);\n#else /* Reuse previously extracted row data */\n      MEMCOPY(vEdge, prow, m+1);\n      vEdge[0] = 0;\n#endif\n      lp->bfp_ftran_normal(lp, vEdge, NULL);\n    }\n\n    /* Update the squared steepest edge norms; first store some constants */\n    cEdge = lp->edgeVector[exitcol];\n    rw = w[rownr];\n    if(fabs(rw) < lp->epspivot) {\n      forceRefresh = TRUE;\n      goto Finish2;\n    }\n\n   /* Deal with the variable entering the basis to become a new leaving candidate */\n    hold = 1 / rw;\n    lp->edgeVector[colnr] = (hold*hold) * cEdge;\n\n#ifdef Paranoia\n    if(lp->edgeVector[colnr] <= lp->epsmachine)\n      report(lp, errlevel, \"updatePricer: Invalid dual norm %g at entering index %d - iteration %.0f\\n\",\n                           lp->edgeVector[colnr], rownr, (double) (lp->total_iter+lp->current_iter));\n#endif\n\n   /* Then loop over all basic variables, but skip the leaving row */\n    for(i = 1; i <= m; i++) {\n      if(i == rownr)\n        continue;\n      targetcol = lp->var_basic[i];\n      hold = w[i];\n      if(hold == 0)\n        continue;\n      hold /= rw;\n      if(fabs(hold) < lp->epsmachine)\n        continue;\n\n      newEdge = &(lp->edgeVector[targetcol]);\n      *newEdge += (hold*hold) * cEdge;\n      if(isDEVEX) {\n        if((*newEdge) > DEVEX_RESTARTLIMIT) {\n          forceRefresh = TRUE;\n          break;\n        }\n      }\n      else {\n        *newEdge -= 2*hold*vEdge[i];\n#ifdef xxApplySteepestEdgeMinimum\n        SETMAX(*newEdge, hold*hold+1); /* Kludge; use the primal lower bound */\n#else\n        if(*newEdge <= 0) {\n          report(lp, errlevel, \"updatePricer: Invalid dual norm %g at index %d - iteration %.0f\\n\",\n                                *newEdge, i, (double) (lp->total_iter+lp->current_iter));\n          forceRefresh = TRUE;\n          break;\n        }\n#endif\n      }\n    }\n\n\n  }\n  /* Price norms for the primal simplex - the non-basic columns */\n  else {\n\n    REAL *vTemp = NULL, *vAlpha = NULL, cAlpha;\n    int  *coltarget;\n\n    ok = allocREAL(lp, &vTemp, m+1, TRUE) &&\n         allocREAL(lp, &vAlpha, n+1, TRUE);\n    if(!ok)\n      return( ok );\n\n    /* Check if we have strategy fallback for the primal */\n    if(!isDEVEX)\n      isDEVEX = is_piv_mode(lp, PRICE_PRIMALFALLBACK);\n\n    /* Initialize column target array */\n    coltarget = (int *) mempool_obtainVector(lp->workarrays, lp->sum+1, sizeof(*coltarget));\n    ok = get_colIndexA(lp, SCAN_SLACKVARS+SCAN_USERVARS+USE_NONBASICVARS, coltarget, FALSE);\n    if(!ok) {\n      mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n      return( ok );\n    }\n\n    /* Don't need to compute cross-products with DEVEX */\n    if(!isDEVEX) {\n      ok = allocREAL(lp, &vEdge, n+1, TRUE);\n      if(!ok)\n        return( ok );\n\n      /* Compute v and then N'v */\n      MEMCOPY(vTemp, w, m+1);\n      bsolve(lp, -1, vTemp, NULL, lp->epsmachine*DOUBLEROUND, 0.0);\n      vTemp[0] = 0;\n      prod_xA(lp, coltarget, vTemp, NULL, lp->epsmachine, 0.0,\n                             vEdge, NULL, MAT_ROUNDDEFAULT);\n    }\n\n    /* Compute Sigma and then Alpha */\n    bsolve(lp, rownr, vTemp, NULL, 0*DOUBLEROUND, 0.0);\n    vTemp[0] = 0;\n    prod_xA(lp, coltarget, vTemp, NULL, lp->epsmachine, 0.0,\n                           vAlpha, NULL, MAT_ROUNDDEFAULT);\n    mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n\n    /* Update the squared steepest edge norms; first store some constants */\n    cEdge = lp->edgeVector[colnr];\n    cAlpha = vAlpha[colnr];\n    if(fabs(cAlpha) < lp->epspivot) {\n      forceRefresh = TRUE;\n      goto Finish1;\n    }\n\n    /* Deal with the variable leaving the basis to become a new entry candidate */\n    hold = 1 / cAlpha;\n    lp->edgeVector[exitcol] = (hold*hold) * cEdge;\n\n#ifdef Paranoia\n    if(lp->edgeVector[exitcol] <= lp->epsmachine)\n      report(lp, errlevel, \"updatePricer: Invalid primal norm %g at leaving index %d - iteration %.0f\\n\",\n                          lp->edgeVector[exitcol], exitcol, (double) (lp->total_iter+lp->current_iter));\n#endif\n\n    /* Then loop over all non-basic variables, but skip the entering column */\n    for(i = 1; i <= lp->sum; i++) {\n      if(lp->is_basic[i] || (i == colnr))\n        continue;\n      hold = vAlpha[i];\n      if(hold == 0)\n        continue;\n      hold /= cAlpha;\n      if(fabs(hold) < lp->epsmachine)\n        continue;\n\n      newEdge = &(lp->edgeVector[i]);\n      *newEdge += (hold*hold) * cEdge;\n      if(isDEVEX) {\n        if((*newEdge) > DEVEX_RESTARTLIMIT) {\n          forceRefresh = TRUE;\n          break;\n        }\n      }\n      else {\n        *newEdge -= 2*hold*vEdge[i];\n#ifdef ApplySteepestEdgeMinimum\n        SETMAX(*newEdge, hold*hold+1);\n#else\n        if(*newEdge < 0) {\n          report(lp, errlevel, \"updatePricer: Invalid primal norm %g at index %d - iteration %.0f\\n\",\n                               *newEdge, i, (double) (lp->total_iter+lp->current_iter));\n          if(lp->spx_trace)\n            report(lp, errlevel, \"Error detail: (RelAlpha=%g, vEdge=%g, cEdge=%g)\\n\", hold, vEdge[i], cEdge);\n          forceRefresh = TRUE;\n          break;\n        }\n#endif\n      }\n    }\n\nFinish1:\n    FREE(vAlpha);\n    FREE(vTemp);\n\n  }\n\nFinish2:\n  FREE(vEdge);\n  freeWeights(w);\n\n  if(forceRefresh)\n    ok = restartPricer(lp, AUTOMATIC);\n  else\n    ok = TRUE;\n\n  return( ok );\n\n}\n\n\nSTATIC MYBOOL verifyPricer(lprec *lp)\n{\n  REAL value;\n  int  i, n;\n  MYBOOL ok = applyPricer(lp);\n\n  if(!ok)\n    return( ok );\n  ok = FALSE;\n\n  /* Verify */\n  if(lp->edgeVector == NULL)\n    return( ok );\n  value = *lp->edgeVector;\n  if(value < 0)\n    return( ok );\n\n  /* Check the primal */\n  n = 1;\n  if(value == 0) {\n\n    for(n = lp->sum; n > 0; n--) {\n      if(lp->is_basic[n])\n        continue;\n      value = lp->edgeVector[n];\n      if(value <= 0)\n        break;\n    }\n  }\n  /* Check the dual */\n  else {\n    for(i = lp->rows; i > 0; i--) {\n      n = lp->var_basic[i];\n      value = lp->edgeVector[n];\n      if(value <= 0)\n        break;\n    }\n  }\n\n  ok = (MYBOOL) (n == 0);\n#ifdef Paranoia\n  if(!ok)\n    report(lp, SEVERE, \"verifyPricer: Invalid norm %g at index %d\\n\",\n                       value, n);\n#endif\n  return( ok );\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_pricePSE.h",
    "content": "#ifndef HEADER_lp_pricePSE\n#define HEADER_lp_pricePSE\n\n#include \"lp_types.h\"\n\n#define ApplySteepestEdgeMinimum\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Price norm management routines */\nSTATIC MYBOOL initPricer(lprec *lp);\nINLINE MYBOOL applyPricer(lprec *lp);\nSTATIC void simplexPricer(lprec *lp, MYBOOL isdual);\nSTATIC void freePricer(lprec *lp);\nSTATIC MYBOOL resizePricer(lprec *lp);\nSTATIC REAL getPricer(lprec *lp, int item, MYBOOL isdual);\nSTATIC MYBOOL restartPricer(lprec *lp, MYBOOL isdual);\nSTATIC MYBOOL updatePricer(lprec *lp, int rownr, int colnr, REAL *pcol, REAL *prow, int *nzprow);\nSTATIC MYBOOL verifyPricer(lprec *lp);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_pricePSE */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_report.c",
    "content": "\n/*\n    Mixed integer programming optimization drivers for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Michel Berkelaar (to lp_solve v3.2),\n                   Kjell Eikland\n    Contact:\n    License terms: LGPL.\n\n    Requires:      stdarg.h, lp_lib.h\n\n    Release notes:\n    v5.0.0 3   1 January 2004      New unit isolating reporting routines.\n    v5.2.0.0   1 December 2005     Addition of Matrix Market writing function.\n\n   ----------------------------------------------------------------------------------\n*/\n\n#include <stdio.h>\n#include <stdarg.h>\n#include <string.h>\n\n#include \"lp_lib.h\"\n#include \"lp_scale.h\"\n#include \"commonlib.h\"\n#include \"lp_report.h\"\n\n#include \"mmio.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* Define buffer-size controled function mapping */\n# if defined _MSC_VER\n#  define vsnprintf _vsnprintf\n# endif\n\n/* Various reporting functions for lp_solve                                  */\n/* ------------------------------------------------------------------------- */\n\n/* First define general utilties for reporting and output */\nchar * __VACALL explain(lprec *lp, char *format, ...)\n{\n  char buff[DEF_STRBUFSIZE+1];\n  va_list ap;\n\n  va_start(ap, format);\n  vsnprintf(buff, DEF_STRBUFSIZE, format, ap);\n  va_end(ap);\n  allocCHAR(lp, &(lp->ex_status), (int) strlen(buff), AUTOMATIC);\n  strcpy(lp->ex_status, buff);\n  return( lp->ex_status );\n}\nvoid __VACALL report(lprec *lp, int level, char *format, ...)\n{\n  char buff[DEF_STRBUFSIZE+1];\n  va_list ap;\n\n  if(lp == NULL) {\n    va_start(ap, format);\n    vfprintf(stderr, format, ap);\n    va_end(ap);\n  }\n  else if(level <= lp->verbose) {\n    if(lp->writelog != NULL) {\n      va_start(ap, format);\n      vsnprintf(buff, DEF_STRBUFSIZE, format, ap);\n      va_end(ap);\n      lp->writelog(lp, lp->loghandle, buff);\n    }\n    if(lp->outstream != NULL) {\n      va_start(ap, format);\n      vfprintf(lp->outstream, format, ap);\n      va_end(ap);\n      if(lp->outstream != stdout)\n        fflush(lp->outstream);\n    }\n  }\n#ifdef xParanoia\n  if(level == CRITICAL)\n    raise(SIGSEGV);\n#endif\n}\n\nSTATIC void print_indent(lprec *lp)\n{\n  int i;\n\n  report(lp, NEUTRAL, \"%2d\", lp->bb_level);\n  if(lp->bb_level < 50) /* useless otherwise */\n    for(i = lp->bb_level; i > 0; i--)\n      report(lp, NEUTRAL, \"--\");\n  else\n    report(lp, NEUTRAL, \" *** too deep ***\");\n  report(lp, NEUTRAL, \"> \");\n} /* print_indent */\n\nSTATIC void debug_print(lprec *lp, char *format, ...)\n{\n  va_list ap;\n\n  if(lp->bb_trace) {\n    print_indent(lp);\n    if (lp == NULL)\n    {\n      va_start(ap, format);\n      vfprintf(stderr, format, ap);\n      va_end(ap);\n      fputc('\\n', stderr);\n    }\n    else if(lp->debuginfo != NULL)\n    {\n      char buff[DEF_STRBUFSIZE+1];\n      va_start(ap, format);\n      vsnprintf(buff, DEF_STRBUFSIZE, format, ap);\n      va_end(ap);\n      lp->debuginfo(lp, lp->loghandle, buff);\n    }\n  }\n} /* debug_print */\n\nSTATIC void debug_print_solution(lprec *lp)\n{\n  int i;\n\n  if(lp->bb_trace)\n    for (i = lp->rows + 1; i <= lp->sum; i++) {\n      print_indent(lp);\n      report(lp, NEUTRAL, \"%s \" RESULTVALUEMASK \"\\n\",\n                 get_col_name(lp, i - lp->rows),\n                (double)lp->solution[i]);\n    }\n} /* debug_print_solution */\n\nSTATIC void debug_print_bounds(lprec *lp, REAL *upbo, REAL *lowbo)\n{\n  int i;\n\n  if(lp->bb_trace)\n    for(i = lp->rows + 1; i <= lp->sum; i++) {\n      if(lowbo[i] == upbo[i]) {\n        print_indent(lp);\n        report(lp, NEUTRAL, \"%s = \" RESULTVALUEMASK \"\\n\", get_col_name(lp, i - lp->rows),\n                             (double)lowbo[i]);\n      }\n      else {\n        if(lowbo[i] != 0) {\n          print_indent(lp);\n          report(lp, NEUTRAL, \"%s > \" RESULTVALUEMASK \"\\n\", get_col_name(lp, i - lp->rows),\n                               (double)lowbo[i]);\n        }\n        if(upbo[i] != lp->infinite) {\n          print_indent(lp);\n          report(lp, NEUTRAL, \"%s < \" RESULTVALUEMASK \"\\n\", get_col_name(lp, i - lp->rows),\n                               (double)upbo[i]);\n    }\n      }\n    }\n} /* debug_print_bounds */\n\n/* List a vector of LREAL values for the given index range */\nvoid blockWriteLREAL(FILE *output, char *label, LREAL *vector, int first, int last)\n{\n  int i, k = 0;\n\n  fprintf(output, \"%s\", label);\n  fprintf(output, \"\\n\");\n  for(i = first; i <= last; i++) {\n    fprintf(output, \" %18g\", vector[i]);\n    k++;\n    if(my_mod(k, 4) == 0) {\n      fprintf(output, \"\\n\");\n      k = 0;\n    }\n  }\n  if(my_mod(k, 4) != 0)\n    fprintf(output, \"\\n\");\n}\n\n/* List the current user data matrix columns over the selected row range */\nvoid blockWriteAMAT(FILE *output, const char *label, lprec* lp, int first, int last)\n{\n  int    i, j, k = 0;\n  int    nzb, nze, jb;\n  double hold;\n  MATrec *mat = lp->matA;\n\n  if(!mat_validate(mat))\n    return;\n  if(first < 0)\n    first = 0;\n  if(last < 0)\n    last = lp->rows;\n\n  fprintf(output, \"%s\", label);\n  fprintf(output, \"\\n\");\n\n  if(first == 0) {\n    for(j = 1; j <= lp->columns; j++) {\n      hold = get_mat(lp, 0, j);\n      fprintf(output, \" %18g\", hold);\n      k++;\n      if(my_mod(k, 4) == 0) {\n        fprintf(output, \"\\n\");\n        k = 0;\n      }\n    }\n    if(my_mod(k, 4) != 0) {\n      fprintf(output, \"\\n\");\n      k = 0;\n    }\n    first++;\n  }\n  nze = mat->row_end[first-1];\n  for(i = first; i <= last; i++) {\n    nzb = nze;\n    nze = mat->row_end[i];\n    if(nzb >= nze)\n      jb = lp->columns+1;\n    else\n      jb = ROW_MAT_COLNR(nzb);\n    for(j = 1; j <= lp->columns; j++) {\n      if(j < jb)\n        hold = 0;\n      else {\n        hold = get_mat(lp, i, j);\n        nzb++;\n        if(nzb < nze)\n          jb = ROW_MAT_COLNR(nzb);\n        else\n          jb = lp->columns+1;\n      }\n      fprintf(output, \" %18g\", hold);\n      k++;\n      if(my_mod(k, 4) == 0) {\n        fprintf(output, \"\\n\");\n        k = 0;\n      }\n    }\n    if(my_mod(k, 4) != 0) {\n      fprintf(output, \"\\n\");\n      k = 0;\n    }\n  }\n  if(my_mod(k, 4) != 0)\n    fprintf(output, \"\\n\");\n}\n\n/* List the current basis matrix columns over the selected row range */\nvoid blockWriteBMAT(FILE *output, const char *label, lprec* lp, int first, int last)\n{\n  int    i, j, jb, k = 0;\n  double hold;\n\n  if(first < 0)\n    first = 0;\n  if(last < 0)\n    last = lp->rows;\n\n  fprintf(output, \"%s\", label);\n  fprintf(output, \"\\n\");\n\n  for(i = first; i <= last; i++) {\n    for(j = 1; j <= lp->rows; j++) {\n      jb = lp->var_basic[j];\n      if(jb <= lp->rows) {\n        if(jb == i)\n          hold = 1;\n        else\n          hold = 0;\n      }\n      else\n        hold = get_mat(lp, i, j);\n      if(i == 0)\n        modifyOF1(lp, jb, &hold, 1);\n      hold = unscaled_mat(lp, hold, i, jb);\n      fprintf(output, \" %18g\", hold);\n      k++;\n      if(my_mod(k, 4) == 0) {\n        fprintf(output, \"\\n\");\n        k = 0;\n      }\n    }\n    if(my_mod(k, 4) != 0) {\n      fprintf(output, \"\\n\");\n      k = 0;\n    }\n  }\n  if(my_mod(k, 4) != 0)\n    fprintf(output, \"\\n\");\n}\n\n/* Do a generic readable data dump of key lp_solve model variables;\n   principally for run difference and debugging purposes */\nMYBOOL REPORT_debugdump(lprec *lp, char *filename, MYBOOL livedata)\n{\n  FILE   *output = stdout;\n  MYBOOL ok;\n\n  ok = (MYBOOL) ((filename == NULL) || ((output = fopen(filename,\"w\")) != NULL));\n  if(!ok)\n    return(ok);\n  if((filename == NULL) && (lp->outstream != NULL))\n    output = lp->outstream;\n\n  fprintf(output, \"\\nGENERAL INFORMATION\\n-------------------\\n\\n\");\n  fprintf(output, \"Model size:     %d rows (%d equalities, %d Lagrangean), %d columns (%d integers, %d SC, %d SOS, %d GUB)\\n\",\n                  lp->rows, lp->equalities, get_Lrows(lp), lp->columns,\n      lp->int_vars, lp->sc_vars, SOS_count(lp), GUB_count(lp));\n  fprintf(output, \"Data size:      %d model non-zeros, %d invB non-zeros (engine is %s)\\n\",\n                  get_nonzeros(lp), my_if(lp->invB == NULL, 0, lp->bfp_nonzeros(lp, FALSE)), lp->bfp_name());\n  fprintf(output, \"Internal sizes: %d rows allocated, %d columns allocated, %d columns used, %d eta length\\n\",\n                  lp->rows_alloc, lp->columns_alloc, lp->columns, my_if(lp->invB == NULL, 0, lp->bfp_colcount(lp)));\n  fprintf(output, \"Memory use:     %d sparse matrix, %d eta\\n\",\n                  lp->matA->mat_alloc, my_if(lp->invB == NULL, 0, lp->bfp_memallocated(lp)));\n  fprintf(output, \"Parameters:     Maximize=%d, Names used=%d, Scalingmode=%d, Presolve=%d, SimplexPivot=%d\\n\",\n                  is_maxim(lp), lp->names_used, lp->scalemode, lp->do_presolve, lp->piv_strategy);\n  fprintf(output, \"Precision:      EpsValue=%g, EpsPrimal=%g, EpsDual=%g, EpsPivot=%g, EpsPerturb=%g\\n\",\n                  lp->epsvalue, lp->epsprimal, lp->epsdual, lp->epspivot, lp->epsperturb);\n  fprintf(output, \"Stability:      AntiDegen=%d, Improvement=%d, Split variables at=%g\\n\",\n                  lp->improve, lp->anti_degen, lp->negrange);\n  fprintf(output, \"B&B settings:   BB pivot rule=%d, BB branching=%s, BB strategy=%d, Integer precision=%g, MIP gaps=%g,%g\\n\",\n                  lp->bb_rule, my_boolstr(lp->bb_varbranch), lp->bb_floorfirst, lp->epsint, lp->mip_absgap, lp->mip_relgap);\n\n  fprintf(output, \"\\nCORE DATA\\n---------\\n\\n\");\n  blockWriteINT(output,  \"Column starts\", lp->matA->col_end, 0, lp->columns);\n  blockWriteINT(output,  \"row_type\", lp->row_type, 0, lp->rows);\n  blockWriteREAL(output, \"orig_rhs\", lp->orig_rhs, 0, lp->rows);\n  blockWriteREAL(output, \"orig_lowbo\", lp->orig_lowbo, 0, lp->sum);\n  blockWriteREAL(output, \"orig_upbo\", lp->orig_upbo, 0, lp->sum);\n  blockWriteINT(output,  \"row_type\", lp->row_type, 0, lp->rows);\n  blockWriteBOOL(output, \"var_type\", lp->var_type, 0, lp->columns, TRUE);\n  blockWriteAMAT(output, \"A\", lp, 0, lp->rows);\n\n  if(livedata) {\n    fprintf(output, \"\\nPROCESS DATA\\n------------\\n\\n\");\n    blockWriteREAL(output,  \"Active rhs\", lp->rhs, 0, lp->rows);\n    blockWriteINT(output,  \"Basic variables\", lp->var_basic, 0, lp->rows);\n    blockWriteBOOL(output, \"is_basic\", lp->is_basic, 0, lp->sum, TRUE);\n    blockWriteREAL(output, \"lowbo\", lp->lowbo, 0, lp->sum);\n    blockWriteREAL(output, \"upbo\", lp->upbo, 0, lp->sum);\n    if(lp->scalars != NULL)\n      blockWriteREAL(output, \"scalars\", lp->scalars, 0, lp->sum);\n  }\n\n  if(filename != NULL)\n    fclose(output);\n  return(ok);\n}\n\n\n/* High level reports for model results */\n\nvoid REPORT_objective(lprec *lp)\n{\n  if(lp->outstream == NULL)\n    return;\n  if(fabs(lp->best_solution[0]) < 1e-5)\n    fprintf(lp->outstream, \"\\nValue of objective function: %g\\n\", (double)lp->best_solution[0]);\n  else\n    fprintf(lp->outstream, \"\\nValue of objective function: %.8f\\n\", (double)lp->best_solution[0]);\n  fflush(lp->outstream);\n}\n\nvoid REPORT_solution(lprec *lp, int columns)\n{\n  int i, j, n;\n  REAL value;\n  presolveundorec *psundo = lp->presolve_undo;\n  MYBOOL NZonly = (MYBOOL) ((lp->print_sol & AUTOMATIC) > 0);\n\n  if(lp->outstream == NULL)\n    return;\n\n  fprintf(lp->outstream, \"\\nActual values of the variables:\\n\");\n  if(columns <= 0)\n    columns = 2;\n  n = 0;\n  for(i = 1; i <= psundo->orig_columns; i++) {\n    j = psundo->orig_rows + i;\n    value = get_var_primalresult(lp, j);\n    if(NZonly && (fabs(value) < lp->epsprimal))\n      continue;\n    n = (n+1) % columns;\n    fprintf(lp->outstream, \"%-20s %12g\", get_origcol_name(lp, i), (double) value);\n    if(n == 0)\n      fprintf(lp->outstream, \"\\n\");\n    else\n      fprintf(lp->outstream, \"       \");\n  }\n\n  fflush(lp->outstream);\n} /* REPORT_solution */\n\nvoid REPORT_constraints(lprec *lp, int columns)\n{\n  int i, n;\n  REAL value;\n  MYBOOL NZonly = (MYBOOL) ((lp->print_sol & AUTOMATIC) > 0);\n\n  if(lp->outstream == NULL)\n    return;\n\n  if(columns <= 0)\n    columns = 2;\n\n  fprintf(lp->outstream, \"\\nActual values of the constraints:\\n\");\n  n = 0;\n  for(i = 1; i <= lp->rows; i++) {\n    value = (double)lp->best_solution[i];\n    if(NZonly && (fabs(value) < lp->epsprimal))\n      continue;\n    n = (n+1) % columns;\n    fprintf(lp->outstream, \"%-20s %12g\", get_row_name(lp, i), value);\n    if(n == 0)\n      fprintf(lp->outstream, \"\\n\");\n    else\n      fprintf(lp->outstream, \"       \");\n  }\n\n  fflush(lp->outstream);\n}\n\nvoid REPORT_duals(lprec *lp)\n{\n  int i;\n  REAL *duals, *dualsfrom, *dualstill, *objfrom, *objtill, *objfromvalue;\n  MYBOOL ret;\n\n  if(lp->outstream == NULL)\n    return;\n\n  ret = get_ptr_sensitivity_objex(lp, &objfrom, &objtill, &objfromvalue, NULL);\n  if(ret) {\n    fprintf(lp->outstream, \"\\nObjective function limits:\\n\");\n    fprintf(lp->outstream, \"                                 From            Till       FromValue\\n\");\n    for(i = 1; i <= lp->columns; i++)\n      if(!is_splitvar(lp, i))\n        fprintf(lp->outstream, \"%-20s  %15.7g %15.7g %15.7g\\n\", get_col_name(lp, i),\n         (double)objfrom[i - 1], (double)objtill[i - 1], (double)objfromvalue[i - 1]);\n  }\n\n  ret = get_ptr_sensitivity_rhs(lp, &duals, &dualsfrom, &dualstill);\n  if(ret) {\n    fprintf(lp->outstream, \"\\nDual values with from - till limits:\\n\");\n    fprintf(lp->outstream, \"                           Dual value            From            Till\\n\");\n    for(i = 1; i <= lp->sum; i++)\n      fprintf(lp->outstream, \"%-20s  %15.7g %15.7g %15.7g\\n\",\n              (i <= lp->rows) ? get_row_name(lp, i) : get_col_name(lp, i - lp->rows),\n              (double)duals[i - 1], (double)dualsfrom[i - 1], (double)dualstill[i - 1]);\n    fflush(lp->outstream);\n  }\n}\n\n/* Printing of sensitivity analysis reports */\nvoid REPORT_extended(lprec *lp)\n{\n  int  i, j;\n  REAL hold;\n  REAL *duals, *dualsfrom, *dualstill, *objfrom, *objtill;\n  MYBOOL ret;\n\n  ret = get_ptr_sensitivity_obj(lp, &objfrom, &objtill);\n  report(lp, NORMAL, \" \\n\");\n  report(lp, NORMAL, \"Primal objective:\\n\");\n  report(lp, NORMAL, \" \\n\");\n  report(lp, NORMAL, \"  Column name                      Value   Objective         Min         Max\\n\");\n  report(lp, NORMAL, \"  --------------------------------------------------------------------------\\n\");\n  for(j = 1; j <= lp->columns; j++) {\n    hold = get_mat(lp,0,j);\n    report(lp, NORMAL, \"  %-25s \" MPSVALUEMASK MPSVALUEMASK MPSVALUEMASK MPSVALUEMASK \"\\n\",\n           get_col_name(lp,j),\n           my_precision(hold,lp->epsprimal),\n           my_precision(hold*lp->best_solution[lp->rows+j],lp->epsprimal),\n           my_precision((ret) ? objfrom[j - 1] : 0.0,lp->epsprimal),\n           my_precision((ret) ? objtill[j - 1] : 0.0,lp->epsprimal));\n  }\n  report(lp, NORMAL, \" \\n\");\n\n  ret = get_ptr_sensitivity_rhs(lp, &duals, &dualsfrom, &dualstill);\n  report(lp, NORMAL, \"Primal variables:\\n\");\n  report(lp, NORMAL, \" \\n\");\n  report(lp, NORMAL, \"  Column name                      Value       Slack         Min         Max\\n\");\n  report(lp, NORMAL, \"  --------------------------------------------------------------------------\\n\");\n  for(j = 1; j <= lp->columns; j++)\n    report(lp, NORMAL, \"  %-25s \" MPSVALUEMASK MPSVALUEMASK MPSVALUEMASK MPSVALUEMASK \"\\n\",\n           get_col_name(lp,j),\n           my_precision(lp->best_solution[lp->rows+j],lp->epsprimal),\n           my_precision(my_inflimit(lp, (ret) ? duals[lp->rows+j-1] : 0.0),lp->epsprimal),\n           my_precision((ret) ? dualsfrom[lp->rows+j-1] : 0.0,lp->epsprimal),\n           my_precision((ret) ? dualstill[lp->rows+j-1] : 0.0,lp->epsprimal));\n\n  report(lp, NORMAL, \" \\n\");\n  report(lp, NORMAL, \"Dual variables:\\n\");\n  report(lp, NORMAL, \" \\n\");\n  report(lp, NORMAL, \"  Row name                         Value       Slack         Min         Max\\n\");\n  report(lp, NORMAL, \"  --------------------------------------------------------------------------\\n\");\n  for(i = 1; i <= lp->rows; i++)\n    report(lp, NORMAL, \"  %-25s \" MPSVALUEMASK MPSVALUEMASK MPSVALUEMASK MPSVALUEMASK \"\\n\",\n           get_row_name(lp,i),\n           my_precision((ret) ? duals[i - 1] : 0.0, lp->epsprimal),\n           my_precision(lp->best_solution[i], lp->epsprimal),\n           my_precision((ret) ? dualsfrom[i - 1] : 0.0,lp->epsprimal),\n           my_precision((ret) ? dualstill[i - 1] : 0.0,lp->epsprimal));\n\n  report(lp, NORMAL, \" \\n\");\n}\n\n/* A more readable lp-format report of the model; antiquated and not updated */\nvoid REPORT_lp(lprec *lp)\n{\n  int  i, j;\n\n  if(lp->outstream == NULL)\n    return;\n\n  fprintf(lp->outstream, \"Model name: %s\\n\", get_lp_name(lp));\n  fprintf(lp->outstream, \"          \");\n\n  for(j = 1; j <= lp->columns; j++)\n    fprintf(lp->outstream, \"%8s \", get_col_name(lp,j));\n\n  fprintf(lp->outstream, \"\\n%simize  \", (is_maxim(lp) ? \"Max\" : \"Min\"));\n  for(j = 1; j <= lp->columns; j++)\n      fprintf(lp->outstream, \"%8g \", get_mat(lp, 0, j));\n  fprintf(lp->outstream, \"\\n\");\n\n  for(i = 1; i <= lp->rows; i++) {\n    fprintf(lp->outstream, \"%-9s \", get_row_name(lp, i));\n    for(j = 1; j <= lp->columns; j++)\n      fprintf(lp->outstream, \"%8g \", get_mat(lp, i, j));\n    if(is_constr_type(lp, i, GE))\n      fprintf(lp->outstream, \">= \");\n    else if(is_constr_type(lp, i, LE))\n      fprintf(lp->outstream, \"<= \");\n    else\n      fprintf(lp->outstream, \" = \");\n    fprintf(lp->outstream, \"%8g\", get_rh(lp, i));\n\n    if(is_constr_type(lp, i, GE)) {\n      if(get_rh_upper(lp, i) < lp->infinite)\n        fprintf(lp->outstream, \"  %s = %8g\", \"upbo\", get_rh_upper(lp, i));\n    }\n    else if(is_constr_type(lp, i, LE)) {\n      if(get_rh_lower(lp, i) > -lp->infinite)\n        fprintf(lp->outstream, \"  %s = %8g\", \"lowbo\", get_rh_lower(lp, i));\n    }\n    fprintf(lp->outstream, \"\\n\");\n  }\n\n  fprintf(lp->outstream, \"Type      \");\n  for(i = 1; i <= lp->columns; i++) {\n    if(is_int(lp,i))\n      fprintf(lp->outstream, \"     Int \");\n    else\n      fprintf(lp->outstream, \"    Real \");\n  }\n\n  fprintf(lp->outstream, \"\\nupbo      \");\n  for(i = 1; i <= lp->columns; i++)\n    if(get_upbo(lp, i) >= lp->infinite)\n      fprintf(lp->outstream, \"     Inf \");\n    else\n      fprintf(lp->outstream, \"%8g \", get_upbo(lp, i));\n  fprintf(lp->outstream, \"\\nlowbo     \");\n  for(i = 1; i <= lp->columns; i++)\n    if(get_lowbo(lp, i) <= -lp->infinite)\n      fprintf(lp->outstream, \"    -Inf \");\n    else\n      fprintf(lp->outstream, \"%8g \", get_lowbo(lp, i));\n  fprintf(lp->outstream, \"\\n\");\n\n  fflush(lp->outstream);\n}\n\n/* Report the scaling factors used; extremely rarely used */\nvoid REPORT_scales(lprec *lp)\n{\n  int i, colMax;\n\n  colMax = lp->columns;\n\n  if(lp->outstream == NULL)\n    return;\n\n  if(lp->scaling_used) {\n    fprintf(lp->outstream, \"\\nScale factors:\\n\");\n    for(i = 0; i <= lp->rows + colMax; i++)\n      fprintf(lp->outstream, \"%-20s scaled at %g\\n\",\n              (i <= lp->rows) ? get_row_name(lp, i) : get_col_name(lp, i - lp->rows),\n        (double)lp->scalars[i]);\n  }\n  fflush(lp->outstream);\n}\n\n/* Report the traditional tableau corresponding to the current basis */\nMYBOOL REPORT_tableau(lprec *lp)\n{\n  int  j, row_nr, *coltarget;\n  REAL *prow = NULL;\n  FILE *stream = lp->outstream;\n\n  if(lp->outstream == NULL)\n    return(FALSE);\n\n  if(!lp->model_is_valid || !has_BFP(lp) ||\n     (get_total_iter(lp) == 0) || (lp->spx_status == NOTRUN)) {\n    lp->spx_status = NOTRUN;\n    return(FALSE);\n  }\n  if(!allocREAL(lp, &prow,lp->sum + 1, TRUE)) {\n    lp->spx_status = NOMEMORY;\n    return(FALSE);\n  }\n\n  fprintf(stream, \"\\n\");\n  fprintf(stream, \"Tableau at iter %.0f:\\n\", (double) get_total_iter(lp));\n\n  for(j = 1; j <= lp->sum; j++)\n    if (!lp->is_basic[j])\n      fprintf(stream, \"%15d\", (j <= lp->rows ?\n                               (j + lp->columns) * ((lp->orig_upbo[j] == 0) ||\n                                                    (is_chsign(lp, j)) ? 1 : -1) : j - lp->rows) *\n                              (lp->is_lower[j] ? 1 : -1));\n  fprintf(stream, \"\\n\");\n\n  coltarget = (int *) mempool_obtainVector(lp->workarrays, lp->columns+1, sizeof(*coltarget));\n  if(!get_colIndexA(lp, SCAN_USERVARS+USE_NONBASICVARS, coltarget, FALSE)) {\n    mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n    return(FALSE);\n  }\n  for(row_nr = 1; (row_nr <= lp->rows + 1); row_nr++) {\n    if (row_nr <= lp->rows)\n      fprintf(stream, \"%3d\", (lp->var_basic[row_nr] <= lp->rows ?\n                              (lp->var_basic[row_nr] + lp->columns) * ((lp->orig_upbo[lp->var_basic [row_nr]] == 0) ||\n                                                                       (is_chsign(lp, lp->var_basic[row_nr])) ? 1 : -1) : lp->var_basic[row_nr] - lp->rows) *\n                             (lp->is_lower[lp->var_basic [row_nr]] ? 1 : -1));\n    else\n      fprintf(stream, \"   \");\n    bsolve(lp, row_nr <= lp->rows ? row_nr : 0, prow, NULL, lp->epsmachine*DOUBLEROUND, 1.0);\n    prod_xA(lp, coltarget, prow, NULL, lp->epsmachine, 1.0,\n                                       prow, NULL, MAT_ROUNDDEFAULT);\n\n    for(j = 1; j <= lp->rows + lp->columns; j++)\n      if (!lp->is_basic[j])\n        fprintf(stream, \"%15.7f\", prow[j] * (lp->is_lower[j] ? 1 : -1) *\n                                            (row_nr <= lp->rows ? 1 : -1));\n    fprintf(stream, \"%15.7f\", lp->rhs[row_nr <= lp->rows ? row_nr : 0] *\n                              (double) ((row_nr <= lp->rows) || (is_maxim(lp)) ? 1 : -1));\n    fprintf(stream, \"\\n\");\n  }\n  fflush(stream);\n\n  mempool_releaseVector(lp->workarrays, (char *) coltarget, FALSE);\n  FREE(prow);\n  return(TRUE);\n}\n\nvoid REPORT_constraintinfo(lprec *lp, char *datainfo)\n{\n  int i, tally[ROWCLASS_MAX+1];\n\n  MEMCLEAR(tally, ROWCLASS_MAX+1);\n  for(i = 1; i <= lp->rows; i++)\n    tally[get_constr_class(lp, i)]++;\n\n  if(datainfo != NULL)\n    report(lp, NORMAL, \"%s\\n\", datainfo);\n\n  for(i = 0; i <= ROWCLASS_MAX; i++)\n    if(tally[i] > 0)\n      report(lp, NORMAL, \"%-15s %4d\\n\", get_str_constr_class(lp, i), tally[i]);\n}\n\nvoid REPORT_modelinfo(lprec *lp, MYBOOL doName, char *datainfo)\n{\n  if(doName) {\n    report(lp, NORMAL, \"\\nModel name:  '%s' - run #%-5d\\n\",\n                       get_lp_name(lp), lp->solvecount);\n    report(lp, NORMAL, \"Objective:   %simize(%s)\\n\",\n                       my_if(is_maxim(lp), \"Max\", \"Min\"), get_row_name(lp, 0));\n    report(lp, NORMAL, \" \\n\");\n  }\n  if(datainfo != NULL)\n    report(lp, NORMAL, \"%s\\n\", datainfo);\n\n  report(lp, NORMAL, \"Model size:  %7d constraints, %7d variables, %12d non-zeros.\\n\",\n         lp->rows, lp->columns, get_nonzeros(lp));\n  if(GUB_count(lp)+SOS_count(lp) > 0)\n  report(lp, NORMAL, \"Var-types:   %7d integer,     %7d semi-cont.,     %7d SOS.\\n\",\n         lp->int_vars, lp->sc_vars, lp->sos_vars);\n  report(lp, NORMAL, \"Sets:                             %7d GUB,            %7d SOS.\\n\",\n                         GUB_count(lp), SOS_count(lp));\n}\n\n/* Save a matrix column subset to a MatrixMarket formatted file,\n   say to export the basis matrix for further numerical analysis.\n   If colndx is NULL, then the full constraint matrix is assumed. */\nMYBOOL REPORT_mat_mmsave(lprec *lp, char *filename, int *colndx, MYBOOL includeOF, char *infotext)\n{\n  int         n, m, nz, i, j, k, kk;\n  MATrec      *mat = lp->matA;\n  MM_typecode matcode;\n  FILE        *output = stdout;\n  MYBOOL      ok;\n  REAL        *acol = NULL;\n  int         *nzlist = NULL;\n\n  /* Open file */\n  ok = (MYBOOL) ((filename == NULL) || ((output = fopen(filename,\"w\")) != NULL));\n  if(!ok)\n    return(ok);\n  if((filename == NULL) && (lp->outstream != NULL))\n    output = lp->outstream;\n\n  /* Compute column and non-zero counts */\n  if(colndx == lp->var_basic) {\n    if(!lp->basis_valid)\n      return( FALSE );\n    m = lp->rows;\n  }\n  else if(colndx != NULL)\n    m = colndx[0];\n  else\n    m = lp->columns;\n  n = lp->rows;\n  nz = 0;\n\n  for(j = 1; j <= m; j++) {\n    k = (colndx == NULL ? n + j : colndx[j]);\n    if(k > n) {\n      k -= lp->rows;\n      nz += mat_collength(mat, k);\n      if(includeOF && is_OF_nz(lp, k))\n        nz++;\n    }\n    else\n      nz++;\n  }\n  kk = 0;\n  if(includeOF) {\n    n++;   /* Row count */\n    kk++;  /* Row index offset */\n  }\n\n  /* Initialize */\n  mm_initialize_typecode(&matcode);\n  mm_set_matrix(&matcode);\n  mm_set_coordinate(&matcode);\n  mm_set_real(&matcode);\n\n  mm_write_banner(output, matcode);\n  mm_write_mtx_crd_size(output, n+kk, m, nz+(colndx == lp->var_basic ? 1 : 0));\n\n  /* Allocate working arrays for sparse column storage */\n  allocREAL(lp, &acol, n+2, FALSE);\n  allocINT(lp, &nzlist, n+2, FALSE);\n\n  /* Write the matrix non-zero values column-by-column.\n     NOTE: matrixMarket files use 1-based indeces,\n     i.e. first row of a vector has index 1, not 0. */\n  if(infotext != NULL) {\n    fprintf(output, \"%%\\n\");\n    fprintf(output, \"%% %s\\n\", infotext);\n    fprintf(output, \"%%\\n\");\n  }\n  if(includeOF && (colndx == lp->var_basic))\n    fprintf(output, \"%d %d %g\\n\", 1, 1, 1.0);\n  for(j = 1; j <= m; j++) {\n    k = (colndx == NULL ? lp->rows + j : colndx[j]);\n    if(k == 0)\n      continue;\n    nz = obtain_column(lp, k, acol, nzlist, NULL);\n    for(i = 1; i <= nz; i++) {\n      if(!includeOF && (nzlist[i] == 0))\n        continue;\n      fprintf(output, \"%d %d %g\\n\", nzlist[i]+kk, j+kk, acol[i]);\n    }\n  }\n  fprintf(output, \"%% End of MatrixMarket file\\n\");\n\n  /* Finish */\n  FREE(acol);\n  FREE(nzlist);\n  fclose(output);\n\n  return(ok);\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_report.h",
    "content": "#ifndef HEADER_lp_report\n#define HEADER_lp_report\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* General information functions */\nchar * __VACALL explain(lprec *lp, char *format, ...);\nvoid __VACALL report(lprec *lp, int level, char *format, ...);\n\n/* Prototypes for debugging and general data dumps */\nvoid debug_print(lprec *lp, char *format, ...);\nvoid debug_print_solution(lprec *lp);\nvoid debug_print_bounds(lprec *lp, REAL *upbo, REAL *lowbo);\nvoid blockWriteLREAL(FILE *output, char *label, LREAL *vector, int first, int last);\nvoid blockWriteAMAT(FILE *output, const char *label, lprec* lp, int first, int last);\nvoid blockWriteBMAT(FILE *output, const char *label, lprec* lp, int first, int last);\n\n\n/* Model reporting headers */\nvoid REPORT_objective(lprec *lp);\nvoid REPORT_solution(lprec *lp, int columns);\nvoid REPORT_constraints(lprec *lp, int columns);\nvoid REPORT_duals(lprec *lp);\nvoid REPORT_extended(lprec *lp);\n\n/* Other rarely used, but sometimes extremely useful reports */\nvoid REPORT_constraintinfo(lprec *lp, char *datainfo);\nvoid REPORT_modelinfo(lprec *lp, MYBOOL doName, char *datainfo);\nvoid REPORT_lp(lprec *lp);\nMYBOOL REPORT_tableau(lprec *lp);\nvoid REPORT_scales(lprec *lp);\nMYBOOL REPORT_debugdump(lprec *lp, char *filename, MYBOOL livedata);\nMYBOOL REPORT_mat_mmsave(lprec *lp, char *filename, int *colndx, MYBOOL includeOF, char *infotext);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_report */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_rlp.bat",
    "content": "rem flex -L -l lp_rlp.l\r\nflex -L lp_rlp.l\r\nrem sed -e \"s/^#line.*//g\" lex.yy.c >lp_rlp.h\r\nsed -e \"s/yy/lp_yy/g\" lex.yy.c | sed -e \"s/^#line.*//g\" >lp_rlp.h\r\nrem copy lex.yy.c lp_rlp.h\r\ndel lex.yy.c\r\n\r\nbison --no-lines -y lp_rlp.y\r\nsed -e \"s/yy/lp_yy/g\" y.tab.c >lp_rlp.c\r\nrem copy y.tab.c lp_rlp.c\r\ndel y.tab.c\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_rlp.c",
    "content": "/* A Bison parser, made by GNU Bison 2.3.  */\n\n/* Skeleton implementation for Bison's Yacc-like parsers in C\n\n   Copyright (C) 1984, 1989, 1990, 2000, 2001, 2002, 2003, 2004, 2005, 2006\n   Free Software Foundation, Inc.\n\n   This program is free software; you can redistribute it and/or modify\n   it under the terms of the GNU General Public License as published by\n   the Free Software Foundation; either version 2, or (at your option)\n   any later version.\n\n   This program is distributed in the hope that it will be useful,\n   but WITHOUT ANY WARRANTY; without even the implied warranty of\n   MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n   GNU General Public License for more details.\n\n   You should have received a copy of the GNU General Public License\n   along with this program; if not, write to the Free Software\n   Foundation, Inc., 51 Franklin Street, Fifth Floor,\n   Boston, MA 02110-1301, USA.  */\n\n/* As a special exception, you may create a larger work that contains\n   part or all of the Bison parser skeleton and distribute that work\n   under terms of your choice, so long as that work isn't itself a\n   parser generator using the skeleton or a modified version thereof\n   as a parser skeleton.  Alternatively, if you modify or redistribute\n   the parser skeleton itself, you may (at your option) remove this\n   special exception, which will cause the skeleton and the resulting\n   Bison output files to be licensed under the GNU General Public\n   License without this special exception.\n\n   This special exception was added by the Free Software Foundation in\n   version 2.2 of Bison.  */\n\n/* C LALR(1) parser skeleton written by Richard Stallman, by\n   simplifying the original so-called \"semantic\" parser.  */\n\n/* All symbols defined below should begin with lp_yy or YY, to avoid\n   infringing on user name space.  This should be done even for local\n   variables, as they might otherwise be expanded by user macros.\n   There are some unavoidable exceptions within include files to\n   define necessary library symbols; they are noted \"INFRINGES ON\n   USER NAME SPACE\" below.  */\n\n/* Identify Bison output.  */\n#define YYBISON 1\n\n/* Bison version.  */\n#define YYBISON_VERSION \"2.3\"\n\n/* Skeleton name.  */\n#define YYSKELETON_NAME \"yacc.c\"\n\n/* Pure parsers.  */\n#define YYPURE 1\n\n/* Using locations.  */\n#define YYLSP_NEEDED 0\n\n\n\n/* Tokens.  */\n#ifndef YYTOKENTYPE\n# define YYTOKENTYPE\n   /* Put the tokens into the symbol table, so that GDB and other debuggers\n      know about them.  */\n   enum lp_yytokentype {\n     VAR = 258,\n     CONS = 259,\n     INTCONS = 260,\n     VARIABLECOLON = 261,\n     INF = 262,\n     SEC_INT = 263,\n     SEC_BIN = 264,\n     SEC_SEC = 265,\n     SEC_SOS = 266,\n     SOSDESCR = 267,\n     SEC_FREE = 268,\n     TOK_SIGN = 269,\n     AR_M_OP = 270,\n     RE_OPEQ = 271,\n     RE_OPLE = 272,\n     RE_OPGE = 273,\n     END_C = 274,\n     COMMA = 275,\n     COLON = 276,\n     MINIMISE = 277,\n     MAXIMISE = 278,\n     UNDEFINED = 279\n   };\n#endif\n/* Tokens.  */\n#define VAR 258\n#define CONS 259\n#define INTCONS 260\n#define VARIABLECOLON 261\n#define INF 262\n#define SEC_INT 263\n#define SEC_BIN 264\n#define SEC_SEC 265\n#define SEC_SOS 266\n#define SOSDESCR 267\n#define SEC_FREE 268\n#define TOK_SIGN 269\n#define AR_M_OP 270\n#define RE_OPEQ 271\n#define RE_OPLE 272\n#define RE_OPGE 273\n#define END_C 274\n#define COMMA 275\n#define COLON 276\n#define MINIMISE 277\n#define MAXIMISE 278\n#define UNDEFINED 279\n\n\n\n\n/* Copy the first part of user declarations.  */\n\n\n#include <stdlib.h>\n#include <string.h>\n#include <ctype.h>\n\n#define scanner lp_yyscanner\n#define PARM lp_yyget_extra(lp_yyscanner)\n#define YYSTYPE int\n#define YY_EXTRA_TYPE parse_parm *\n#define YY_FATAL_ERROR(msg) lex_fatal_error(PARM, lp_yyscanner, msg)\n#undef YY_INPUT\n#define YY_INPUT(buf,result,max_size) result = lp_input((void *) PARM, buf, max_size);\n#define lp_yyerror read_error\n\n#include \"lpkit.h\"\n#include \"yacc_read.h\"\n\ntypedef struct parse_vars_s\n{\n  read_modeldata_func *lp_input;\n  void *userhandle;\n  char HadVar, HadVar0, HadVar1, HadVar2, HasAR_M_OP, HadConstraint, Had_lineair_sum, Had_lineair_sum0, do_add_row, HadSign, OP, Sign, isign, isign0, make_neg;\n  char state, state0;\n  char Within_int_decl;  /* TRUE when we are within an char declaration */\n  char Within_bin_decl;  /* TRUE when we are within an bin declaration */\n  char Within_sec_decl;  /* TRUE when we are within a sec declaration */\n  char Within_sos_decl;  /* TRUE when we are within a sos declaration */\n  char Within_sos_decl1;\n  char Within_free_decl; /* TRUE when we are within a free declaration */\n  short SOStype, SOStype0;        /* SOS type */\n  int SOSNr;\n  int SOSweight;         /* SOS weight */\n  char *Last_var, *Last_var0;\n  REAL f, f0, f1;\n} parse_vars;\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* let's please C++ users */\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n#if defined MSDOS || defined __MSDOS__ || defined WINDOWS || defined _WINDOWS || defined WIN32 || defined _WIN32\n#define YY_NO_UNISTD_H\n\nstatic int isatty(int f)\n{\n  return(FALSE);\n}\n\n#if !defined _STDLIB_H\n# define _STDLIB_H\n#endif\n#endif\n\nstatic int __WINAPI lp_input_lp_yyin(void *fpin, char *buf, int max_size)\n{\n  int result;\n\n  result = fread( (char*)buf, sizeof(char), max_size, (FILE *)fpin);\n\n  return(result);\n}\n\nstatic int __WINAPI lp_input(void *vpp, char *buf, int max_size)\n{\n  parse_parm *pp = (parse_parm *) vpp;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  int result;\n\n  result = pv->lp_input(pv->userhandle, buf, max_size);\n  if (result < 0)\n    lex_fatal_error(pp, pp->scanner, \"read() in flex scanner failed\");\n  return(result);\n}\n\n#ifdef __cplusplus\n};\n#endif\n\n#include \"lp_rlp.h\"\n\n#undef lp_yylval\n\n\n\n/* Enabling traces.  */\n#ifndef YYDEBUG\n# define YYDEBUG 0\n#endif\n\n/* Enabling verbose error messages.  */\n#ifdef YYERROR_VERBOSE\n# undef YYERROR_VERBOSE\n# define YYERROR_VERBOSE 1\n#else\n# define YYERROR_VERBOSE 0\n#endif\n\n/* Enabling the token table.  */\n#ifndef YYTOKEN_TABLE\n# define YYTOKEN_TABLE 0\n#endif\n\n#if ! defined YYSTYPE && ! defined YYSTYPE_IS_DECLARED\ntypedef int YYSTYPE;\n# define lp_yystype YYSTYPE /* obsolescent; will be withdrawn */\n# define YYSTYPE_IS_DECLARED 1\n# define YYSTYPE_IS_TRIVIAL 1\n#endif\n\n\n\n/* Copy the second part of user declarations.  */\n\n\n/* Line 216 of yacc.c.  */\n\n\n#ifdef short\n# undef short\n#endif\n\n#ifdef YYTYPE_UINT8\ntypedef YYTYPE_UINT8 lp_yytype_uint8;\n#else\ntypedef unsigned char lp_yytype_uint8;\n#endif\n\n#ifdef YYTYPE_INT8\ntypedef YYTYPE_INT8 lp_yytype_int8;\n#elif (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\ntypedef signed char lp_yytype_int8;\n#else\ntypedef short int lp_yytype_int8;\n#endif\n\n#ifdef YYTYPE_UINT16\ntypedef YYTYPE_UINT16 lp_yytype_uint16;\n#else\ntypedef unsigned short int lp_yytype_uint16;\n#endif\n\n#ifdef YYTYPE_INT16\ntypedef YYTYPE_INT16 lp_yytype_int16;\n#else\ntypedef short int lp_yytype_int16;\n#endif\n\n#ifndef YYSIZE_T\n# ifdef __SIZE_TYPE__\n#  define YYSIZE_T __SIZE_TYPE__\n# elif defined size_t\n#  define YYSIZE_T size_t\n# elif ! defined YYSIZE_T && (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\n#  include <stddef.h> /* INFRINGES ON USER NAME SPACE */\n#  define YYSIZE_T size_t\n# else\n#  define YYSIZE_T unsigned int\n# endif\n#endif\n\n#define YYSIZE_MAXIMUM ((YYSIZE_T) -1)\n\n#ifndef YY_\n# if YYENABLE_NLS\n#  if ENABLE_NLS\n#   include <libintl.h> /* INFRINGES ON USER NAME SPACE */\n#   define YY_(msgid) dgettext (\"bison-runtime\", msgid)\n#  endif\n# endif\n# ifndef YY_\n#  define YY_(msgid) msgid\n# endif\n#endif\n\n/* Suppress unused-variable warnings by \"using\" E.  */\n#if ! defined lint || defined __GNUC__\n# define YYUSE(e) ((void) (e))\n#else\n# define YYUSE(e) /* empty */\n#endif\n\n/* Identity function, used to suppress warnings about constant conditions.  */\n#ifndef lint\n# define YYID(n) (n)\n#else\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nstatic int\nYYID (int i)\n#else\nstatic int\nYYID (i)\n    int i;\n#endif\n{\n  return i;\n}\n#endif\n\n#if ! defined lp_yyoverflow || YYERROR_VERBOSE\n\n/* The parser invokes alloca or malloc; define the necessary symbols.  */\n\n# ifdef YYSTACK_USE_ALLOCA\n#  if YYSTACK_USE_ALLOCA\n#   ifdef __GNUC__\n#    define YYSTACK_ALLOC __builtin_alloca\n#   elif defined __BUILTIN_VA_ARG_INCR\n#    include <alloca.h> /* INFRINGES ON USER NAME SPACE */\n#   elif defined _AIX\n#    define YYSTACK_ALLOC __alloca\n#   elif defined _MSC_VER\n#    include <malloc.h> /* INFRINGES ON USER NAME SPACE */\n#    define alloca _alloca\n#   else\n#    define YYSTACK_ALLOC alloca\n#    if ! defined _ALLOCA_H && ! defined _STDLIB_H && (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\n#     include <stdlib.h> /* INFRINGES ON USER NAME SPACE */\n#     ifndef _STDLIB_H\n#      define _STDLIB_H 1\n#     endif\n#    endif\n#   endif\n#  endif\n# endif\n\n# ifdef YYSTACK_ALLOC\n   /* Pacify GCC's `empty if-body' warning.  */\n#  define YYSTACK_FREE(Ptr) do { /* empty */; } while (YYID (0))\n#  ifndef YYSTACK_ALLOC_MAXIMUM\n    /* The OS might guarantee only one guard page at the bottom of the stack,\n       and a page size can be as small as 4096 bytes.  So we cannot safely\n       invoke alloca (N) if N exceeds 4096.  Use a slightly smaller number\n       to allow for a few compiler-allocated temporary stack slots.  */\n#   define YYSTACK_ALLOC_MAXIMUM 4032 /* reasonable circa 2006 */\n#  endif\n# else\n#  define YYSTACK_ALLOC YYMALLOC\n#  define YYSTACK_FREE YYFREE\n#  ifndef YYSTACK_ALLOC_MAXIMUM\n#   define YYSTACK_ALLOC_MAXIMUM YYSIZE_MAXIMUM\n#  endif\n#  if (defined __cplusplus && ! defined _STDLIB_H \\\n       && ! ((defined YYMALLOC || defined malloc) \\\n\t     && (defined YYFREE || defined free)))\n#   include <stdlib.h> /* INFRINGES ON USER NAME SPACE */\n#   ifndef _STDLIB_H\n#    define _STDLIB_H 1\n#   endif\n#  endif\n#  ifndef YYMALLOC\n#   define YYMALLOC malloc\n#   if ! defined malloc && ! defined _STDLIB_H && (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nvoid *malloc (YYSIZE_T); /* INFRINGES ON USER NAME SPACE */\n#   endif\n#  endif\n#  ifndef YYFREE\n#   define YYFREE free\n#   if ! defined free && ! defined _STDLIB_H && (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nvoid free (void *); /* INFRINGES ON USER NAME SPACE */\n#   endif\n#  endif\n# endif\n#endif /* ! defined lp_yyoverflow || YYERROR_VERBOSE */\n\n\n#if (! defined lp_yyoverflow \\\n     && (! defined __cplusplus \\\n\t || (defined YYSTYPE_IS_TRIVIAL && YYSTYPE_IS_TRIVIAL)))\n\n/* A type that is properly aligned for any stack member.  */\nunion lp_yyalloc\n{\n  lp_yytype_int16 lp_yyss;\n  YYSTYPE lp_yyvs;\n  };\n\n/* The size of the maximum gap between one aligned stack and the next.  */\n# define YYSTACK_GAP_MAXIMUM (sizeof (union lp_yyalloc) - 1)\n\n/* The size of an array large to enough to hold all stacks, each with\n   N elements.  */\n# define YYSTACK_BYTES(N) \\\n     ((N) * (sizeof (lp_yytype_int16) + sizeof (YYSTYPE)) \\\n      + YYSTACK_GAP_MAXIMUM)\n\n/* Copy COUNT objects from FROM to TO.  The source and destination do\n   not overlap.  */\n# ifndef YYCOPY\n#  if defined __GNUC__ && 1 < __GNUC__\n#   define YYCOPY(To, From, Count) \\\n      __builtin_memcpy (To, From, (Count) * sizeof (*(From)))\n#  else\n#   define YYCOPY(To, From, Count)\t\t\\\n      do\t\t\t\t\t\\\n\t{\t\t\t\t\t\\\n\t  YYSIZE_T lp_yyi;\t\t\t\t\\\n\t  for (lp_yyi = 0; lp_yyi < (Count); lp_yyi++)\t\\\n\t    (To)[lp_yyi] = (From)[lp_yyi];\t\t\\\n\t}\t\t\t\t\t\\\n      while (YYID (0))\n#  endif\n# endif\n\n/* Relocate STACK from its old location to the new one.  The\n   local variables YYSIZE and YYSTACKSIZE give the old and new number of\n   elements in the stack, and YYPTR gives the new location of the\n   stack.  Advance YYPTR to a properly aligned location for the next\n   stack.  */\n# define YYSTACK_RELOCATE(Stack)\t\t\t\t\t\\\n    do\t\t\t\t\t\t\t\t\t\\\n      {\t\t\t\t\t\t\t\t\t\\\n\tYYSIZE_T lp_yynewbytes;\t\t\t\t\t\t\\\n\tYYCOPY (&lp_yyptr->Stack, Stack, lp_yysize);\t\t\t\t\\\n\tStack = &lp_yyptr->Stack;\t\t\t\t\t\t\\\n\tlp_yynewbytes = lp_yystacksize * sizeof (*Stack) + YYSTACK_GAP_MAXIMUM; \\\n\tlp_yyptr += lp_yynewbytes / sizeof (*lp_yyptr);\t\t\t\t\\\n      }\t\t\t\t\t\t\t\t\t\\\n    while (YYID (0))\n\n#endif\n\n/* YYFINAL -- State number of the termination state.  */\n#define YYFINAL  3\n/* YYLAST -- Last index in YYTABLE.  */\n#define YYLAST   115\n\n/* YYNTOKENS -- Number of terminals.  */\n#define YYNTOKENS  25\n/* YYNNTS -- Number of nonterminals.  */\n#define YYNNTS  56\n/* YYNRULES -- Number of rules.  */\n#define YYNRULES  89\n/* YYNRULES -- Number of states.  */\n#define YYNSTATES  123\n\n/* YYTRANSLATE(YYLEX) -- Bison symbol number corresponding to YYLEX.  */\n#define YYUNDEFTOK  2\n#define YYMAXUTOK   279\n\n#define YYTRANSLATE(YYX)\t\t\t\t\t\t\\\n  ((unsigned int) (YYX) <= YYMAXUTOK ? lp_yytranslate[YYX] : YYUNDEFTOK)\n\n/* YYTRANSLATE[YYLEX] -- Bison symbol number corresponding to YYLEX.  */\nstatic const lp_yytype_uint8 lp_yytranslate[] =\n{\n       0,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     2,     2,     2,     2,\n       2,     2,     2,     2,     2,     2,     1,     2,     3,     4,\n       5,     6,     7,     8,     9,    10,    11,    12,    13,    14,\n      15,    16,    17,    18,    19,    20,    21,    22,    23,    24\n};\n\n#if YYDEBUG\n/* YYPRHS[YYN] -- Index of the first RHS symbol of rule number YYN in\n   YYRHS.  */\nstatic const lp_yytype_uint8 lp_yyprhs[] =\n{\n       0,     0,     3,     4,     5,    10,    13,    16,    18,    21,\n      23,    25,    27,    29,    31,    34,    36,    37,    41,    42,\n      43,    44,    53,    55,    56,    57,    63,    65,    67,    69,\n      70,    74,    75,    78,    80,    83,    86,    88,    89,    93,\n      95,    97,    99,   102,   104,   106,   108,   110,   112,   114,\n     116,   118,   120,   122,   124,   127,   129,   131,   133,   135,\n     137,   138,   142,   143,   149,   151,   154,   156,   157,   161,\n     163,   164,   169,   171,   174,   176,   178,   180,   184,   186,\n     188,   190,   191,   193,   195,   198,   202,   205,   208,   211\n};\n\n/* YYRHS -- A `-1'-separated list of the rules' RHS.  */\nstatic const lp_yytype_int8 lp_yyrhs[] =\n{\n      27,     0,    -1,    -1,    -1,    28,    29,    32,    58,    -1,\n      23,    30,    -1,    22,    30,    -1,    30,    -1,    31,    19,\n      -1,    26,    -1,    46,    -1,    26,    -1,    33,    -1,    34,\n      -1,    33,    34,    -1,    36,    -1,    -1,     6,    35,    36,\n      -1,    -1,    -1,    -1,    43,    37,    52,    38,    44,    39,\n      40,    19,    -1,    26,    -1,    -1,    -1,    52,    41,    53,\n      42,    57,    -1,    26,    -1,    44,    -1,    46,    -1,    -1,\n       7,    45,    57,    -1,    -1,    47,    48,    -1,    49,    -1,\n      48,    49,    -1,    55,    50,    -1,    54,    -1,    -1,    56,\n      51,     3,    -1,    16,    -1,    17,    -1,    18,    -1,    55,\n      54,    -1,     7,    -1,     5,    -1,     4,    -1,    26,    -1,\n      14,    -1,    26,    -1,    15,    -1,    26,    -1,    26,    -1,\n      59,    -1,    61,    -1,    59,    61,    -1,     8,    -1,     9,\n      -1,    10,    -1,    11,    -1,    13,    -1,    -1,    60,    62,\n      65,    -1,    -1,    64,    66,    71,    68,    19,    -1,    63,\n      -1,    65,    63,    -1,    26,    -1,    -1,    12,    67,    77,\n      -1,    26,    -1,    -1,    17,     5,    69,    70,    -1,    26,\n      -1,    21,     5,    -1,    26,    -1,    72,    -1,    78,    -1,\n      72,    73,    78,    -1,    26,    -1,    20,    -1,    26,    -1,\n      -1,    26,    -1,    26,    -1,     3,    74,    -1,     6,    75,\n      79,    -1,    54,    76,    -1,    77,    80,    -1,     3,    74,\n      -1,     6,    75,    54,    76,    -1\n};\n\n/* YYRLINE[YYN] -- source line where rule number YYN was defined.  */\nstatic const lp_yytype_uint16 lp_yyrline[] =\n{\n       0,   116,   116,   120,   120,   145,   149,   153,   156,   170,\n     171,   201,   202,   205,   206,   210,   212,   211,   224,   232,\n     242,   223,   288,   298,   311,   297,   342,   355,   364,   366,\n     365,   376,   376,   400,   401,   405,   444,   452,   451,   470,\n     470,   470,   473,   475,   489,   489,   492,   500,   510,   517,\n     526,   547,   548,   551,   552,   555,   555,   555,   555,   555,\n     560,   559,   570,   570,   598,   599,   602,   604,   603,   614,\n     626,   624,   643,   650,   660,   661,   664,   665,   670,   671,\n     674,   703,   724,   749,   770,   772,   777,   779,   784,   786\n};\n#endif\n\n#if YYDEBUG || YYERROR_VERBOSE || YYTOKEN_TABLE\n/* YYTNAME[SYMBOL-NUM] -- String name of the symbol SYMBOL-NUM.\n   First, the terminals, then, starting at YYNTOKENS, nonterminals.  */\nstatic const char *const lp_yytname[] =\n{\n  \"$end\", \"error\", \"$undefined\", \"VAR\", \"CONS\", \"INTCONS\",\n  \"VARIABLECOLON\", \"INF\", \"SEC_INT\", \"SEC_BIN\", \"SEC_SEC\", \"SEC_SOS\",\n  \"SOSDESCR\", \"SEC_FREE\", \"TOK_SIGN\", \"AR_M_OP\", \"RE_OPEQ\", \"RE_OPLE\",\n  \"RE_OPGE\", \"END_C\", \"COMMA\", \"COLON\", \"MINIMISE\", \"MAXIMISE\",\n  \"UNDEFINED\", \"$accept\", \"EMPTY\", \"inputfile\", \"@1\", \"objective_function\",\n  \"real_of\", \"lineair_sum\", \"constraints\", \"x_constraints\", \"constraint\",\n  \"@2\", \"real_constraint\", \"@3\", \"@4\", \"@5\", \"optionalrange\", \"@6\", \"@7\",\n  \"x_lineair_sum2\", \"x_lineair_sum3\", \"@8\", \"x_lineair_sum\", \"@9\",\n  \"x_lineair_sum1\", \"x_lineair_term\", \"x_lineair_term1\", \"@10\", \"RE_OP\",\n  \"cons_term\", \"REALCONS\", \"x_SIGN\", \"optional_AR_M_OP\", \"RHS_STORE\",\n  \"int_bin_sec_sos_free_declarations\", \"real_int_bin_sec_sos_free_decls\",\n  \"SEC_INT_BIN_SEC_SOS_FREE\", \"int_bin_sec_sos_free_declaration\", \"@11\",\n  \"xx_int_bin_sec_sos_free_declaration\", \"@12\",\n  \"x_int_bin_sec_sos_free_declaration\", \"optionalsos\", \"@13\",\n  \"optionalsostype\", \"@14\", \"optionalSOSweight\", \"vars\", \"x_vars\",\n  \"optionalcomma\", \"variable\", \"variablecolon\", \"sosweight\", \"sosdescr\",\n  \"onevarwithoptionalweight\", \"INTCONSorVARIABLE\",\n  \"x_onevarwithoptionalweight\", 0\n};\n#endif\n\n# ifdef YYPRINT\n/* YYTOKNUM[YYLEX-NUM] -- Internal token number corresponding to\n   token YYLEX-NUM.  */\nstatic const lp_yytype_uint16 lp_yytoknum[] =\n{\n       0,   256,   257,   258,   259,   260,   261,   262,   263,   264,\n     265,   266,   267,   268,   269,   270,   271,   272,   273,   274,\n     275,   276,   277,   278,   279\n};\n# endif\n\n/* YYR1[YYN] -- Symbol number of symbol that rule YYN derives.  */\nstatic const lp_yytype_uint8 lp_yyr1[] =\n{\n       0,    25,    26,    28,    27,    29,    29,    29,    30,    31,\n      31,    32,    32,    33,    33,    34,    35,    34,    37,    38,\n      39,    36,    40,    41,    42,    40,    43,    43,    44,    45,\n      44,    47,    46,    48,    48,    49,    50,    51,    50,    52,\n      52,    52,    53,    53,    54,    54,    55,    55,    56,    56,\n      57,    58,    58,    59,    59,    60,    60,    60,    60,    60,\n      62,    61,    64,    63,    65,    65,    66,    67,    66,    68,\n      69,    68,    70,    70,    71,    71,    72,    72,    73,    73,\n      74,    75,    76,    77,    78,    78,    79,    79,    80,    80\n};\n\n/* YYR2[YYN] -- Number of symbols composing right hand side of rule YYN.  */\nstatic const lp_yytype_uint8 lp_yyr2[] =\n{\n       0,     2,     0,     0,     4,     2,     2,     1,     2,     1,\n       1,     1,     1,     1,     2,     1,     0,     3,     0,     0,\n       0,     8,     1,     0,     0,     5,     1,     1,     1,     0,\n       3,     0,     2,     1,     2,     2,     1,     0,     3,     1,\n       1,     1,     2,     1,     1,     1,     1,     1,     1,     1,\n       1,     1,     1,     1,     2,     1,     1,     1,     1,     1,\n       0,     3,     0,     5,     1,     2,     1,     0,     3,     1,\n       0,     4,     1,     2,     1,     1,     1,     3,     1,     1,\n       1,     0,     1,     1,     2,     3,     2,     2,     2,     4\n};\n\n/* YYDEFACT[STATE-NAME] -- Default rule to reduce with in state\n   STATE-NUM when YYTABLE doesn't specify something else to do.  Zero\n   means the default is an error.  */\nstatic const lp_yytype_uint8 lp_yydefact[] =\n{\n       3,     0,    31,     1,    31,    31,     9,     2,     7,     0,\n      10,     2,     6,     5,    16,    29,    11,     2,    12,    13,\n      15,    18,    27,    28,     8,    47,    46,     2,    33,     2,\n      31,     2,    55,    56,    57,    58,    59,    51,     4,    52,\n      60,    53,    26,    14,     0,    34,    45,    44,    49,    48,\n      35,    36,    37,    17,    50,    30,    54,    62,    39,    40,\n      41,    19,     0,    64,     2,    61,    31,    38,    67,    66,\n       2,    65,    20,     2,     2,    81,    74,     2,     2,    76,\n       2,    83,    68,    80,    84,     2,     0,    69,     0,    79,\n      78,     0,    22,     0,    23,     2,     0,    85,    70,    63,\n      77,    21,     2,    82,    86,     2,    81,    87,     2,    43,\n      24,     0,    88,     0,     0,    72,    71,     2,    42,     2,\n      73,    25,    89\n};\n\n/* YYDEFGOTO[NTERM-NUM].  */\nstatic const lp_yytype_int8 lp_yydefgoto[] =\n{\n      -1,     6,     1,     2,     7,     8,     9,    17,    18,    19,\n      30,    20,    44,    66,    80,    93,   102,   117,    21,    22,\n      31,    23,    11,    27,    28,    50,    62,    61,   110,    51,\n      29,    52,    55,    38,    39,    40,    41,    57,    63,    64,\n      65,    70,    73,    88,   108,   116,    77,    78,    91,    84,\n      85,   104,    82,    79,    97,   107\n};\n\n/* YYPACT[STATE-NUM] -- Index in YYTABLE of the portion describing\n   STATE-NUM.  */\n#define YYPACT_NINF -85\nstatic const lp_yytype_int8 lp_yypact[] =\n{\n     -85,    13,    46,   -85,     2,     2,   -85,    32,   -85,     7,\n     -85,    26,   -85,   -85,   -85,   -85,    64,    40,    27,   -85,\n     -85,   -85,   -85,   -85,   -85,   -85,   -85,    42,   -85,     3,\n      -2,   -85,   -85,   -85,   -85,   -85,   -85,   -85,   -85,    40,\n     -85,   -85,   -85,   -85,    67,   -85,   -85,   -85,   -85,   -85,\n     -85,   -85,   -85,   -85,   -85,   -85,   -85,   -85,   -85,   -85,\n     -85,   -85,    59,   -85,    52,     0,    84,   -85,   -85,   -85,\n      22,   -85,   -85,   -85,   -85,   -85,   -85,    60,    35,   -85,\n      67,   -85,   -85,   -85,   -85,    82,    87,   -85,    74,   -85,\n     -85,    22,   -85,    75,   -85,   -85,    73,   -85,   -85,   -85,\n     -85,   -85,    -5,   -85,   -85,   -85,   -85,   -85,    76,   -85,\n     -85,    82,   -85,    82,    91,   -85,   -85,   -85,   -85,   -85,\n     -85,   -85,   -85\n};\n\n/* YYPGOTO[NTERM-NUM].  */\nstatic const lp_yytype_int8 lp_yypgoto[] =\n{\n     -85,    -7,   -85,   -85,   -85,    85,   -85,   -85,   -85,    81,\n     -85,    72,   -85,   -85,   -85,   -85,   -85,   -85,   -85,    34,\n     -85,    70,   -85,   -85,    77,   -85,   -85,    23,   -85,   -84,\n       4,   -85,   -12,   -85,   -85,   -85,    68,   -85,    43,   -85,\n     -85,   -85,   -85,   -85,   -85,   -85,   -85,   -85,   -85,     6,\n       8,   -10,    28,    24,   -85,   -85\n};\n\n/* YYTABLE[YYPACT[STATE-NUM]].  What to do in state STATE-NUM.  If\n   positive, shift that token.  If negative, reduce the rule which\n   number is the opposite.  If zero, do what YYDEFACT says.\n   If YYTABLE_NINF, syntax error.  */\n#define YYTABLE_NINF -76\nstatic const lp_yytype_int8 lp_yytable[] =\n{\n      16,    95,   109,   -62,    26,    15,   -62,    46,    47,    25,\n      37,    42,   -62,     3,    -2,    -2,    -2,   -62,    48,   -62,\n      26,    -2,    49,    42,    54,    74,    24,   118,    75,   119,\n     -31,   -31,   -31,    14,    15,   -31,   -31,   -31,    14,    15,\n      25,   -31,   -31,    -2,    -2,    -2,   -31,   -31,    32,    33,\n      34,    35,   -75,    36,   -75,    89,    25,    69,   -32,   -32,\n     -32,   -32,    67,    76,    68,    -2,    81,    83,     4,     5,\n      87,    90,    10,    92,    10,    10,   105,    86,    81,   106,\n     -26,   -26,   -26,    58,    59,    60,    46,    47,   103,    12,\n      13,    15,    98,    99,   101,    26,   120,   114,    83,    43,\n      72,   115,    53,    94,    45,   121,   111,    56,    71,   122,\n      54,   112,   103,    96,   113,   100\n};\n\nstatic const lp_yytype_uint8 lp_yycheck[] =\n{\n       7,    85,     7,     3,    11,     7,     6,     4,     5,    14,\n      17,    18,    12,     0,    16,    17,    18,    17,    15,    19,\n      27,    19,    29,    30,    31,     3,    19,   111,     6,   113,\n       3,     4,     5,     6,     7,     3,     4,     5,     6,     7,\n      14,    14,    15,    16,    17,    18,    14,    15,     8,     9,\n      10,    11,    17,    13,    19,    20,    14,    64,    16,    17,\n      18,    19,     3,    70,    12,    19,    73,    74,    22,    23,\n      77,    78,     2,    80,     4,     5,     3,    17,    85,     6,\n      16,    17,    18,    16,    17,    18,     4,     5,    95,     4,\n       5,     7,     5,    19,    19,   102,     5,    21,   105,    18,\n      66,   108,    30,    80,    27,   117,   102,    39,    65,   119,\n     117,   105,   119,    85,   106,    91\n};\n\n/* YYSTOS[STATE-NUM] -- The (internal number of the) accessing\n   symbol of state STATE-NUM.  */\nstatic const lp_yytype_uint8 lp_yystos[] =\n{\n       0,    27,    28,     0,    22,    23,    26,    29,    30,    31,\n      46,    47,    30,    30,     6,     7,    26,    32,    33,    34,\n      36,    43,    44,    46,    19,    14,    26,    48,    49,    55,\n      35,    45,     8,     9,    10,    11,    13,    26,    58,    59,\n      60,    61,    26,    34,    37,    49,     4,     5,    15,    26,\n      50,    54,    56,    36,    26,    57,    61,    62,    16,    17,\n      18,    52,    51,    63,    64,    65,    38,     3,    12,    26,\n      66,    63,    44,    67,     3,     6,    26,    71,    72,    78,\n      39,    26,    77,    26,    74,    75,    17,    26,    68,    20,\n      26,    73,    26,    40,    52,    54,    77,    79,     5,    19,\n      78,    19,    41,    26,    76,     3,     6,    80,    69,     7,\n      53,    55,    74,    75,    21,    26,    70,    42,    54,    54,\n       5,    57,    76\n};\n\n#define lp_yyerrok\t\t(lp_yyerrstatus = 0)\n#define lp_yyclearin\t(lp_yychar = YYEMPTY)\n#define YYEMPTY\t\t(-2)\n#define YYEOF\t\t0\n\n#define YYACCEPT\tgoto lp_yyacceptlab\n#define YYABORT\t\tgoto lp_yyabortlab\n#define YYERROR\t\tgoto lp_yyerrorlab\n\n\n/* Like YYERROR except do call lp_yyerror.  This remains here temporarily\n   to ease the transition to the new meaning of YYERROR, for GCC.\n   Once GCC version 2 has supplanted version 1, this can go.  */\n\n#define YYFAIL\t\tgoto lp_yyerrlab\n\n#define YYRECOVERING()  (!!lp_yyerrstatus)\n\n#define YYBACKUP(Token, Value)\t\t\t\t\t\\\ndo\t\t\t\t\t\t\t\t\\\n  if (lp_yychar == YYEMPTY && lp_yylen == 1)\t\t\t\t\\\n    {\t\t\t\t\t\t\t\t\\\n      lp_yychar = (Token);\t\t\t\t\t\t\\\n      lp_yylval = (Value);\t\t\t\t\t\t\\\n      lp_yytoken = YYTRANSLATE (lp_yychar);\t\t\t\t\\\n      YYPOPSTACK (1);\t\t\t\t\t\t\\\n      goto lp_yybackup;\t\t\t\t\t\t\\\n    }\t\t\t\t\t\t\t\t\\\n  else\t\t\t\t\t\t\t\t\\\n    {\t\t\t\t\t\t\t\t\\\n      lp_yyerror (parm, scanner, YY_(\"syntax error: cannot back up\")); \\\n      YYERROR;\t\t\t\t\t\t\t\\\n    }\t\t\t\t\t\t\t\t\\\nwhile (YYID (0))\n\n\n#define YYTERROR\t1\n#define YYERRCODE\t256\n\n\n/* YYLLOC_DEFAULT -- Set CURRENT to span from RHS[1] to RHS[N].\n   If N is 0, then set CURRENT to the empty location which ends\n   the previous symbol: RHS[0] (always defined).  */\n\n#define YYRHSLOC(Rhs, K) ((Rhs)[K])\n#ifndef YYLLOC_DEFAULT\n# define YYLLOC_DEFAULT(Current, Rhs, N)\t\t\t\t\\\n    do\t\t\t\t\t\t\t\t\t\\\n      if (YYID (N))                                                    \\\n\t{\t\t\t\t\t\t\t\t\\\n\t  (Current).first_line   = YYRHSLOC (Rhs, 1).first_line;\t\\\n\t  (Current).first_column = YYRHSLOC (Rhs, 1).first_column;\t\\\n\t  (Current).last_line    = YYRHSLOC (Rhs, N).last_line;\t\t\\\n\t  (Current).last_column  = YYRHSLOC (Rhs, N).last_column;\t\\\n\t}\t\t\t\t\t\t\t\t\\\n      else\t\t\t\t\t\t\t\t\\\n\t{\t\t\t\t\t\t\t\t\\\n\t  (Current).first_line   = (Current).last_line   =\t\t\\\n\t    YYRHSLOC (Rhs, 0).last_line;\t\t\t\t\\\n\t  (Current).first_column = (Current).last_column =\t\t\\\n\t    YYRHSLOC (Rhs, 0).last_column;\t\t\t\t\\\n\t}\t\t\t\t\t\t\t\t\\\n    while (YYID (0))\n#endif\n\n\n/* YY_LOCATION_PRINT -- Print the location on the stream.\n   This macro was not mandated originally: define only if we know\n   we won't break user code: when these are the locations we know.  */\n\n#ifndef YY_LOCATION_PRINT\n# if YYLTYPE_IS_TRIVIAL\n#  define YY_LOCATION_PRINT(File, Loc)\t\t\t\\\n     fprintf (File, \"%d.%d-%d.%d\",\t\t\t\\\n\t      (Loc).first_line, (Loc).first_column,\t\\\n\t      (Loc).last_line,  (Loc).last_column)\n# else\n#  define YY_LOCATION_PRINT(File, Loc) ((void) 0)\n# endif\n#endif\n\n\n/* YYLEX -- calling `lp_yylex' with the right arguments.  */\n\n#ifdef YYLEX_PARAM\n# define YYLEX lp_yylex (&lp_yylval, YYLEX_PARAM)\n#else\n# define YYLEX lp_yylex (&lp_yylval, scanner)\n#endif\n\n/* Enable debugging if requested.  */\n#if YYDEBUG\n\n# ifndef YYFPRINTF\n#  include <stdio.h> /* INFRINGES ON USER NAME SPACE */\n#  define YYFPRINTF fprintf\n# endif\n\n# define YYDPRINTF(Args)\t\t\t\\\ndo {\t\t\t\t\t\t\\\n  if (lp_yydebug)\t\t\t\t\t\\\n    YYFPRINTF Args;\t\t\t\t\\\n} while (YYID (0))\n\n# define YY_SYMBOL_PRINT(Title, Type, Value, Location)\t\t\t  \\\ndo {\t\t\t\t\t\t\t\t\t  \\\n  if (lp_yydebug)\t\t\t\t\t\t\t\t  \\\n    {\t\t\t\t\t\t\t\t\t  \\\n      YYFPRINTF (stderr, \"%s \", Title);\t\t\t\t\t  \\\n      lp_yy_symbol_print (stderr,\t\t\t\t\t\t  \\\n\t\t  Type, Value, parm, scanner); \\\n      YYFPRINTF (stderr, \"\\n\");\t\t\t\t\t\t  \\\n    }\t\t\t\t\t\t\t\t\t  \\\n} while (YYID (0))\n\n\n/*--------------------------------.\n| Print this symbol on YYOUTPUT.  |\n`--------------------------------*/\n\n/*ARGSUSED*/\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nstatic void\nlp_yy_symbol_value_print (FILE *lp_yyoutput, int lp_yytype, YYSTYPE const * const lp_yyvaluep, parse_parm *parm, void *scanner)\n#else\nstatic void\nlp_yy_symbol_value_print (lp_yyoutput, lp_yytype, lp_yyvaluep, parm, scanner)\n    FILE *lp_yyoutput;\n    int lp_yytype;\n    YYSTYPE const * const lp_yyvaluep;\n    parse_parm *parm;\n    void *scanner;\n#endif\n{\n  if (!lp_yyvaluep)\n    return;\n  YYUSE (parm);\n  YYUSE (scanner);\n# ifdef YYPRINT\n  if (lp_yytype < YYNTOKENS)\n    YYPRINT (lp_yyoutput, lp_yytoknum[lp_yytype], *lp_yyvaluep);\n# else\n  YYUSE (lp_yyoutput);\n# endif\n  switch (lp_yytype)\n    {\n      default:\n\tbreak;\n    }\n}\n\n\n/*--------------------------------.\n| Print this symbol on YYOUTPUT.  |\n`--------------------------------*/\n\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nstatic void\nlp_yy_symbol_print (FILE *lp_yyoutput, int lp_yytype, YYSTYPE const * const lp_yyvaluep, parse_parm *parm, void *scanner)\n#else\nstatic void\nlp_yy_symbol_print (lp_yyoutput, lp_yytype, lp_yyvaluep, parm, scanner)\n    FILE *lp_yyoutput;\n    int lp_yytype;\n    YYSTYPE const * const lp_yyvaluep;\n    parse_parm *parm;\n    void *scanner;\n#endif\n{\n  if (lp_yytype < YYNTOKENS)\n    YYFPRINTF (lp_yyoutput, \"token %s (\", lp_yytname[lp_yytype]);\n  else\n    YYFPRINTF (lp_yyoutput, \"nterm %s (\", lp_yytname[lp_yytype]);\n\n  lp_yy_symbol_value_print (lp_yyoutput, lp_yytype, lp_yyvaluep, parm, scanner);\n  YYFPRINTF (lp_yyoutput, \")\");\n}\n\n/*------------------------------------------------------------------.\n| lp_yy_stack_print -- Print the state stack from its BOTTOM up to its |\n| TOP (included).                                                   |\n`------------------------------------------------------------------*/\n\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nstatic void\nlp_yy_stack_print (lp_yytype_int16 *bottom, lp_yytype_int16 *top)\n#else\nstatic void\nlp_yy_stack_print (bottom, top)\n    lp_yytype_int16 *bottom;\n    lp_yytype_int16 *top;\n#endif\n{\n  YYFPRINTF (stderr, \"Stack now\");\n  for (; bottom <= top; ++bottom)\n    YYFPRINTF (stderr, \" %d\", *bottom);\n  YYFPRINTF (stderr, \"\\n\");\n}\n\n# define YY_STACK_PRINT(Bottom, Top)\t\t\t\t\\\ndo {\t\t\t\t\t\t\t\t\\\n  if (lp_yydebug)\t\t\t\t\t\t\t\\\n    lp_yy_stack_print ((Bottom), (Top));\t\t\t\t\\\n} while (YYID (0))\n\n\n/*------------------------------------------------.\n| Report that the YYRULE is going to be reduced.  |\n`------------------------------------------------*/\n\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nstatic void\nlp_yy_reduce_print (YYSTYPE *lp_yyvsp, int lp_yyrule, parse_parm *parm, void *scanner)\n#else\nstatic void\nlp_yy_reduce_print (lp_yyvsp, lp_yyrule, parm, scanner)\n    YYSTYPE *lp_yyvsp;\n    int lp_yyrule;\n    parse_parm *parm;\n    void *scanner;\n#endif\n{\n  int lp_yynrhs = lp_yyr2[lp_yyrule];\n  int lp_yyi;\n  unsigned long int lp_yylno = lp_yyrline[lp_yyrule];\n  YYFPRINTF (stderr, \"Reducing stack by rule %d (line %lu):\\n\",\n\t     lp_yyrule - 1, lp_yylno);\n  /* The symbols being reduced.  */\n  for (lp_yyi = 0; lp_yyi < lp_yynrhs; lp_yyi++)\n    {\n      fprintf (stderr, \"   $%d = \", lp_yyi + 1);\n      lp_yy_symbol_print (stderr, lp_yyrhs[lp_yyprhs[lp_yyrule] + lp_yyi],\n\t\t       &(lp_yyvsp[(lp_yyi + 1) - (lp_yynrhs)])\n\t\t       \t\t       , parm, scanner);\n      fprintf (stderr, \"\\n\");\n    }\n}\n\n# define YY_REDUCE_PRINT(Rule)\t\t\\\ndo {\t\t\t\t\t\\\n  if (lp_yydebug)\t\t\t\t\\\n    lp_yy_reduce_print (lp_yyvsp, Rule, parm, scanner); \\\n} while (YYID (0))\n\n/* Nonzero means print parse trace.  It is left uninitialized so that\n   multiple parsers can coexist.  */\nint lp_yydebug;\n#else /* !YYDEBUG */\n# define YYDPRINTF(Args)\n# define YY_SYMBOL_PRINT(Title, Type, Value, Location)\n# define YY_STACK_PRINT(Bottom, Top)\n# define YY_REDUCE_PRINT(Rule)\n#endif /* !YYDEBUG */\n\n\n/* YYINITDEPTH -- initial size of the parser's stacks.  */\n#ifndef\tYYINITDEPTH\n# define YYINITDEPTH 200\n#endif\n\n/* YYMAXDEPTH -- maximum size the stacks can grow to (effective only\n   if the built-in stack extension method is used).\n\n   Do not make this value too large; the results are undefined if\n   YYSTACK_ALLOC_MAXIMUM < YYSTACK_BYTES (YYMAXDEPTH)\n   evaluated with infinite-precision integer arithmetic.  */\n\n#ifndef YYMAXDEPTH\n# define YYMAXDEPTH 10000\n#endif\n\n\f\n\n#if YYERROR_VERBOSE\n\n# ifndef lp_yystrlen\n#  if defined __GLIBC__ && defined _STRING_H\n#   define lp_yystrlen strlen\n#  else\n/* Return the length of YYSTR.  */\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nstatic YYSIZE_T\nlp_yystrlen (const char *lp_yystr)\n#else\nstatic YYSIZE_T\nlp_yystrlen (lp_yystr)\n    const char *lp_yystr;\n#endif\n{\n  YYSIZE_T lp_yylen;\n  for (lp_yylen = 0; lp_yystr[lp_yylen]; lp_yylen++)\n    continue;\n  return lp_yylen;\n}\n#  endif\n# endif\n\n# ifndef lp_yystpcpy\n#  if defined __GLIBC__ && defined _STRING_H && defined _GNU_SOURCE\n#   define lp_yystpcpy stpcpy\n#  else\n/* Copy YYSRC to YYDEST, returning the address of the terminating '\\0' in\n   YYDEST.  */\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nstatic char *\nlp_yystpcpy (char *lp_yydest, const char *lp_yysrc)\n#else\nstatic char *\nlp_yystpcpy (lp_yydest, lp_yysrc)\n    char *lp_yydest;\n    const char *lp_yysrc;\n#endif\n{\n  char *lp_yyd = lp_yydest;\n  const char *lp_yys = lp_yysrc;\n\n  while ((*lp_yyd++ = *lp_yys++) != '\\0')\n    continue;\n\n  return lp_yyd - 1;\n}\n#  endif\n# endif\n\n# ifndef lp_yytnamerr\n/* Copy to YYRES the contents of YYSTR after stripping away unnecessary\n   quotes and backslashes, so that it's suitable for lp_yyerror.  The\n   heuristic is that double-quoting is unnecessary unless the string\n   contains an apostrophe, a comma, or backslash (other than\n   backslash-backslash).  YYSTR is taken from lp_yytname.  If YYRES is\n   null, do not copy; instead, return the length of what the result\n   would have been.  */\nstatic YYSIZE_T\nlp_yytnamerr (char *lp_yyres, const char *lp_yystr)\n{\n  if (*lp_yystr == '\"')\n    {\n      YYSIZE_T lp_yyn = 0;\n      char const *lp_yyp = lp_yystr;\n\n      for (;;)\n\tswitch (*++lp_yyp)\n\t  {\n\t  case '\\'':\n\t  case ',':\n\t    goto do_not_strip_quotes;\n\n\t  case '\\\\':\n\t    if (*++lp_yyp != '\\\\')\n\t      goto do_not_strip_quotes;\n\t    /* Fall through.  */\n\t  default:\n\t    if (lp_yyres)\n\t      lp_yyres[lp_yyn] = *lp_yyp;\n\t    lp_yyn++;\n\t    break;\n\n\t  case '\"':\n\t    if (lp_yyres)\n\t      lp_yyres[lp_yyn] = '\\0';\n\t    return lp_yyn;\n\t  }\n    do_not_strip_quotes: ;\n    }\n\n  if (! lp_yyres)\n    return lp_yystrlen (lp_yystr);\n\n  return lp_yystpcpy (lp_yyres, lp_yystr) - lp_yyres;\n}\n# endif\n\n/* Copy into YYRESULT an error message about the unexpected token\n   YYCHAR while in state YYSTATE.  Return the number of bytes copied,\n   including the terminating null byte.  If YYRESULT is null, do not\n   copy anything; just return the number of bytes that would be\n   copied.  As a special case, return 0 if an ordinary \"syntax error\"\n   message will do.  Return YYSIZE_MAXIMUM if overflow occurs during\n   size calculation.  */\nstatic YYSIZE_T\nlp_yysyntax_error (char *lp_yyresult, int lp_yystate, int lp_yychar)\n{\n  int lp_yyn = lp_yypact[lp_yystate];\n\n  if (! (YYPACT_NINF < lp_yyn && lp_yyn <= YYLAST))\n    return 0;\n  else\n    {\n      int lp_yytype = YYTRANSLATE (lp_yychar);\n      YYSIZE_T lp_yysize0 = lp_yytnamerr (0, lp_yytname[lp_yytype]);\n      YYSIZE_T lp_yysize = lp_yysize0;\n      YYSIZE_T lp_yysize1;\n      int lp_yysize_overflow = 0;\n      enum { YYERROR_VERBOSE_ARGS_MAXIMUM = 5 };\n      char const *lp_yyarg[YYERROR_VERBOSE_ARGS_MAXIMUM];\n      int lp_yyx;\n\n# if 0\n      /* This is so xgettext sees the translatable formats that are\n\t constructed on the fly.  */\n      YY_(\"syntax error, unexpected %s\");\n      YY_(\"syntax error, unexpected %s, expecting %s\");\n      YY_(\"syntax error, unexpected %s, expecting %s or %s\");\n      YY_(\"syntax error, unexpected %s, expecting %s or %s or %s\");\n      YY_(\"syntax error, unexpected %s, expecting %s or %s or %s or %s\");\n# endif\n      char *lp_yyfmt;\n      char const *lp_yyf;\n      static char const lp_yyunexpected[] = \"syntax error, unexpected %s\";\n      static char const lp_yyexpecting[] = \", expecting %s\";\n      static char const lp_yyor[] = \" or %s\";\n      char lp_yyformat[sizeof lp_yyunexpected\n\t\t    + sizeof lp_yyexpecting - 1\n\t\t    + ((YYERROR_VERBOSE_ARGS_MAXIMUM - 2)\n\t\t       * (sizeof lp_yyor - 1))];\n      char const *lp_yyprefix = lp_yyexpecting;\n\n      /* Start YYX at -YYN if negative to avoid negative indexes in\n\t YYCHECK.  */\n      int lp_yyxbegin = lp_yyn < 0 ? -lp_yyn : 0;\n\n      /* Stay within bounds of both lp_yycheck and lp_yytname.  */\n      int lp_yychecklim = YYLAST - lp_yyn + 1;\n      int lp_yyxend = lp_yychecklim < YYNTOKENS ? lp_yychecklim : YYNTOKENS;\n      int lp_yycount = 1;\n\n      lp_yyarg[0] = lp_yytname[lp_yytype];\n      lp_yyfmt = lp_yystpcpy (lp_yyformat, lp_yyunexpected);\n\n      for (lp_yyx = lp_yyxbegin; lp_yyx < lp_yyxend; ++lp_yyx)\n\tif (lp_yycheck[lp_yyx + lp_yyn] == lp_yyx && lp_yyx != YYTERROR)\n\t  {\n\t    if (lp_yycount == YYERROR_VERBOSE_ARGS_MAXIMUM)\n\t      {\n\t\tlp_yycount = 1;\n\t\tlp_yysize = lp_yysize0;\n\t\tlp_yyformat[sizeof lp_yyunexpected - 1] = '\\0';\n\t\tbreak;\n\t      }\n\t    lp_yyarg[lp_yycount++] = lp_yytname[lp_yyx];\n\t    lp_yysize1 = lp_yysize + lp_yytnamerr (0, lp_yytname[lp_yyx]);\n\t    lp_yysize_overflow |= (lp_yysize1 < lp_yysize);\n\t    lp_yysize = lp_yysize1;\n\t    lp_yyfmt = lp_yystpcpy (lp_yyfmt, lp_yyprefix);\n\t    lp_yyprefix = lp_yyor;\n\t  }\n\n      lp_yyf = YY_(lp_yyformat);\n      lp_yysize1 = lp_yysize + lp_yystrlen (lp_yyf);\n      lp_yysize_overflow |= (lp_yysize1 < lp_yysize);\n      lp_yysize = lp_yysize1;\n\n      if (lp_yysize_overflow)\n\treturn YYSIZE_MAXIMUM;\n\n      if (lp_yyresult)\n\t{\n\t  /* Avoid sprintf, as that infringes on the user's name space.\n\t     Don't have undefined behavior even if the translation\n\t     produced a string with the wrong number of \"%s\"s.  */\n\t  char *lp_yyp = lp_yyresult;\n\t  int lp_yyi = 0;\n\t  while ((*lp_yyp = *lp_yyf) != '\\0')\n\t    {\n\t      if (*lp_yyp == '%' && lp_yyf[1] == 's' && lp_yyi < lp_yycount)\n\t\t{\n\t\t  lp_yyp += lp_yytnamerr (lp_yyp, lp_yyarg[lp_yyi++]);\n\t\t  lp_yyf += 2;\n\t\t}\n\t      else\n\t\t{\n\t\t  lp_yyp++;\n\t\t  lp_yyf++;\n\t\t}\n\t    }\n\t}\n      return lp_yysize;\n    }\n}\n#endif /* YYERROR_VERBOSE */\n\f\n\n/*-----------------------------------------------.\n| Release the memory associated to this symbol.  |\n`-----------------------------------------------*/\n\n/*ARGSUSED*/\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nstatic void\nlp_yydestruct (const char *lp_yymsg, int lp_yytype, YYSTYPE *lp_yyvaluep, parse_parm *parm, void *scanner)\n#else\nstatic void\nlp_yydestruct (lp_yymsg, lp_yytype, lp_yyvaluep, parm, scanner)\n    const char *lp_yymsg;\n    int lp_yytype;\n    YYSTYPE *lp_yyvaluep;\n    parse_parm *parm;\n    void *scanner;\n#endif\n{\n  YYUSE (lp_yyvaluep);\n  YYUSE (parm);\n  YYUSE (scanner);\n\n  if (!lp_yymsg)\n    lp_yymsg = \"Deleting\";\n  YY_SYMBOL_PRINT (lp_yymsg, lp_yytype, lp_yyvaluep, lp_yylocationp);\n\n  switch (lp_yytype)\n    {\n\n      default:\n\tbreak;\n    }\n}\n\f\n\n/* Prevent warnings from -Wmissing-prototypes.  */\n\n#ifdef YYPARSE_PARAM\n#if defined __STDC__ || defined __cplusplus\nint lp_yyparse (void *YYPARSE_PARAM);\n#else\nint lp_yyparse ();\n#endif\n#else /* ! YYPARSE_PARAM */\n#if defined __STDC__ || defined __cplusplus\nint lp_yyparse (parse_parm *parm, void *scanner);\n#else\nint lp_yyparse ();\n#endif\n#endif /* ! YYPARSE_PARAM */\n\n\n\n\n\n\n/*----------.\n| lp_yyparse.  |\n`----------*/\n\n#ifdef YYPARSE_PARAM\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nint\nlp_yyparse (void *YYPARSE_PARAM)\n#else\nint\nlp_yyparse (YYPARSE_PARAM)\n    void *YYPARSE_PARAM;\n#endif\n#else /* ! YYPARSE_PARAM */\n#if (defined __STDC__ || defined __C99__FUNC__ \\\n     || defined __cplusplus || defined _MSC_VER)\nint\nlp_yyparse (parse_parm *parm, void *scanner)\n#else\nint\nlp_yyparse (parm, scanner)\n    parse_parm *parm;\n    void *scanner;\n#endif\n#endif\n{\n  /* The look-ahead symbol.  */\nint lp_yychar;\n\n/* The semantic value of the look-ahead symbol.  */\nYYSTYPE lp_yylval;\n\n/* Number of syntax errors so far.  */\nint lp_yynerrs;\n\n  int lp_yystate;\n  int lp_yyn;\n  int lp_yyresult;\n  /* Number of tokens to shift before error messages enabled.  */\n  int lp_yyerrstatus;\n  /* Look-ahead token as an internal (translated) token number.  */\n  int lp_yytoken = 0;\n#if YYERROR_VERBOSE\n  /* Buffer for error messages, and its allocated size.  */\n  char lp_yymsgbuf[128];\n  char *lp_yymsg = lp_yymsgbuf;\n  YYSIZE_T lp_yymsg_alloc = sizeof lp_yymsgbuf;\n#endif\n\n  /* Three stacks and their tools:\n     `lp_yyss': related to states,\n     `lp_yyvs': related to semantic values,\n     `lp_yyls': related to locations.\n\n     Refer to the stacks thru separate pointers, to allow lp_yyoverflow\n     to reallocate them elsewhere.  */\n\n  /* The state stack.  */\n  lp_yytype_int16 lp_yyssa[YYINITDEPTH];\n  lp_yytype_int16 *lp_yyss = lp_yyssa;\n  lp_yytype_int16 *lp_yyssp;\n\n  /* The semantic value stack.  */\n  YYSTYPE lp_yyvsa[YYINITDEPTH];\n  YYSTYPE *lp_yyvs = lp_yyvsa;\n  YYSTYPE *lp_yyvsp;\n\n\n\n#define YYPOPSTACK(N)   (lp_yyvsp -= (N), lp_yyssp -= (N))\n\n  YYSIZE_T lp_yystacksize = YYINITDEPTH;\n\n  /* The variables used to return semantic value and location from the\n     action routines.  */\n  YYSTYPE lp_yyval;\n\n\n  /* The number of symbols on the RHS of the reduced rule.\n     Keep to zero when no symbol should be popped.  */\n  int lp_yylen = 0;\n\n  YYDPRINTF ((stderr, \"Starting parse\\n\"));\n\n  lp_yystate = 0;\n  lp_yyerrstatus = 0;\n  lp_yynerrs = 0;\n  lp_yychar = YYEMPTY;\t\t/* Cause a token to be read.  */\n\n  /* Initialize stack pointers.\n     Waste one element of value and location stack\n     so that they stay on the same level as the state stack.\n     The wasted elements are never initialized.  */\n\n  lp_yyssp = lp_yyss;\n  lp_yyvsp = lp_yyvs;\n\n  goto lp_yysetstate;\n\n/*------------------------------------------------------------.\n| lp_yynewstate -- Push a new state, which is found in lp_yystate.  |\n`------------------------------------------------------------*/\n lp_yynewstate:\n  /* In all cases, when you get here, the value and location stacks\n     have just been pushed.  So pushing a state here evens the stacks.  */\n  lp_yyssp++;\n\n lp_yysetstate:\n  *lp_yyssp = lp_yystate;\n\n  if (lp_yyss + lp_yystacksize - 1 <= lp_yyssp)\n    {\n      /* Get the current used size of the three stacks, in elements.  */\n      YYSIZE_T lp_yysize = lp_yyssp - lp_yyss + 1;\n\n#ifdef lp_yyoverflow\n      {\n\t/* Give user a chance to reallocate the stack.  Use copies of\n\t   these so that the &'s don't force the real ones into\n\t   memory.  */\n\tYYSTYPE *lp_yyvs1 = lp_yyvs;\n\tlp_yytype_int16 *lp_yyss1 = lp_yyss;\n\n\n\t/* Each stack pointer address is followed by the size of the\n\t   data in use in that stack, in bytes.  This used to be a\n\t   conditional around just the two extra args, but that might\n\t   be undefined if lp_yyoverflow is a macro.  */\n\tlp_yyoverflow (YY_(\"memory exhausted\"),\n\t\t    &lp_yyss1, lp_yysize * sizeof (*lp_yyssp),\n\t\t    &lp_yyvs1, lp_yysize * sizeof (*lp_yyvsp),\n\n\t\t    &lp_yystacksize);\n\n\tlp_yyss = lp_yyss1;\n\tlp_yyvs = lp_yyvs1;\n      }\n#else /* no lp_yyoverflow */\n# ifndef YYSTACK_RELOCATE\n      goto lp_yyexhaustedlab;\n# else\n      /* Extend the stack our own way.  */\n      if (YYMAXDEPTH <= lp_yystacksize)\n\tgoto lp_yyexhaustedlab;\n      lp_yystacksize *= 2;\n      if (YYMAXDEPTH < lp_yystacksize)\n\tlp_yystacksize = YYMAXDEPTH;\n\n      {\n\tlp_yytype_int16 *lp_yyss1 = lp_yyss;\n\tunion lp_yyalloc *lp_yyptr =\n\t  (union lp_yyalloc *) YYSTACK_ALLOC (YYSTACK_BYTES (lp_yystacksize));\n\tif (! lp_yyptr)\n\t  goto lp_yyexhaustedlab;\n\tYYSTACK_RELOCATE (lp_yyss);\n\tYYSTACK_RELOCATE (lp_yyvs);\n\n#  undef YYSTACK_RELOCATE\n\tif (lp_yyss1 != lp_yyssa)\n\t  YYSTACK_FREE (lp_yyss1);\n      }\n# endif\n#endif /* no lp_yyoverflow */\n\n      lp_yyssp = lp_yyss + lp_yysize - 1;\n      lp_yyvsp = lp_yyvs + lp_yysize - 1;\n\n\n      YYDPRINTF ((stderr, \"Stack size increased to %lu\\n\",\n\t\t  (unsigned long int) lp_yystacksize));\n\n      if (lp_yyss + lp_yystacksize - 1 <= lp_yyssp)\n\tYYABORT;\n    }\n\n  YYDPRINTF ((stderr, \"Entering state %d\\n\", lp_yystate));\n\n  goto lp_yybackup;\n\n/*-----------.\n| lp_yybackup.  |\n`-----------*/\nlp_yybackup:\n\n  /* Do appropriate processing given the current state.  Read a\n     look-ahead token if we need one and don't already have one.  */\n\n  /* First try to decide what to do without reference to look-ahead token.  */\n  lp_yyn = lp_yypact[lp_yystate];\n  if (lp_yyn == YYPACT_NINF)\n    goto lp_yydefault;\n\n  /* Not known => get a look-ahead token if don't already have one.  */\n\n  /* YYCHAR is either YYEMPTY or YYEOF or a valid look-ahead symbol.  */\n  if (lp_yychar == YYEMPTY)\n    {\n      YYDPRINTF ((stderr, \"Reading a token: \"));\n      lp_yychar = YYLEX;\n    }\n\n  if (lp_yychar <= YYEOF)\n    {\n      lp_yychar = lp_yytoken = YYEOF;\n      YYDPRINTF ((stderr, \"Now at end of input.\\n\"));\n    }\n  else\n    {\n      lp_yytoken = YYTRANSLATE (lp_yychar);\n      YY_SYMBOL_PRINT (\"Next token is\", lp_yytoken, &lp_yylval, &lp_yylloc);\n    }\n\n  /* If the proper action on seeing token YYTOKEN is to reduce or to\n     detect an error, take that action.  */\n  lp_yyn += lp_yytoken;\n  if (lp_yyn < 0 || YYLAST < lp_yyn || lp_yycheck[lp_yyn] != lp_yytoken)\n    goto lp_yydefault;\n  lp_yyn = lp_yytable[lp_yyn];\n  if (lp_yyn <= 0)\n    {\n      if (lp_yyn == 0 || lp_yyn == YYTABLE_NINF)\n\tgoto lp_yyerrlab;\n      lp_yyn = -lp_yyn;\n      goto lp_yyreduce;\n    }\n\n  if (lp_yyn == YYFINAL)\n    YYACCEPT;\n\n  /* Count tokens shifted since error; after three, turn off error\n     status.  */\n  if (lp_yyerrstatus)\n    lp_yyerrstatus--;\n\n  /* Shift the look-ahead token.  */\n  YY_SYMBOL_PRINT (\"Shifting\", lp_yytoken, &lp_yylval, &lp_yylloc);\n\n  /* Discard the shifted token unless it is eof.  */\n  if (lp_yychar != YYEOF)\n    lp_yychar = YYEMPTY;\n\n  lp_yystate = lp_yyn;\n  *++lp_yyvsp = lp_yylval;\n\n  goto lp_yynewstate;\n\n\n/*-----------------------------------------------------------.\n| lp_yydefault -- do the default action for the current state.  |\n`-----------------------------------------------------------*/\nlp_yydefault:\n  lp_yyn = lp_yydefact[lp_yystate];\n  if (lp_yyn == 0)\n    goto lp_yyerrlab;\n  goto lp_yyreduce;\n\n\n/*-----------------------------.\n| lp_yyreduce -- Do a reduction.  |\n`-----------------------------*/\nlp_yyreduce:\n  /* lp_yyn is the number of a rule to reduce with.  */\n  lp_yylen = lp_yyr2[lp_yyn];\n\n  /* If YYLEN is nonzero, implement the default value of the action:\n     `$$ = $1'.\n\n     Otherwise, the following line sets YYVAL to garbage.\n     This behavior is undocumented and Bison\n     users should not rely upon it.  Assigning to YYVAL\n     unconditionally makes the parser a bit smaller, and it avoids a\n     GCC warning that YYVAL may be used uninitialized.  */\n  lp_yyval = lp_yyvsp[1-lp_yylen];\n\n\n  YY_REDUCE_PRINT (lp_yyn);\n  switch (lp_yyn)\n    {\n        case 3:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = 0;\n  pv->make_neg = 0;\n  pv->Sign = 0;\n  pv->HadConstraint = FALSE;\n  pv->HadVar = pv->HadVar0 = FALSE;\n}\n    break;\n\n  case 5:\n\n    {\n  set_obj_dir(PARM, TRUE);\n}\n    break;\n\n  case 6:\n\n    {\n  set_obj_dir(PARM, FALSE);\n}\n    break;\n\n  case 8:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  add_row(pp);\n  pv->HadConstraint = FALSE;\n  pv->HadVar = pv->HadVar0 = FALSE;\n  pv->isign = 0;\n  pv->make_neg = 0;\n}\n    break;\n\n  case 16:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(!add_constraint_name(pp, pv->Last_var))\n    YYABORT;\n  pv->HadConstraint = TRUE;\n}\n    break;\n\n  case 18:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->HadVar1 = pv->HadVar0;\n  pv->HadVar0 = FALSE;\n}\n    break;\n\n  case 19:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(!store_re_op(pp, pv->OP, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n    YYABORT;\n  pv->make_neg = 1;\n  pv->f1 = 0;\n}\n    break;\n\n  case 20:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->Had_lineair_sum0 = pv->Had_lineair_sum;\n  pv->Had_lineair_sum = TRUE;\n  pv->HadVar2 = pv->HadVar0;\n  pv->HadVar0 = FALSE;\n  pv->do_add_row = FALSE;\n  if(pv->HadConstraint && !pv->HadVar ) {\n    /* it is a range */\n    /* already handled */\n  }\n  else if(!pv->HadConstraint && pv->HadVar) {\n    /* it is a bound */\n\n    if(!store_bounds(pp, TRUE))\n      YYABORT;\n  }\n  else {\n    /* it is a row restriction */\n    if(pv->HadConstraint && pv->HadVar)\n      store_re_op(pp, '\\0', (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum); /* makes sure that data stored in temporary buffers is treated correctly */\n    pv->do_add_row = TRUE;\n  }\n}\n    break;\n\n  case 21:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((!pv->HadVar) && (!pv->HadConstraint)) {\n    lp_yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n  if(pv->do_add_row)\n    add_row(pp);\n  pv->HadConstraint = FALSE;\n  pv->HadVar = pv->HadVar0 = FALSE;\n  pv->isign = 0;\n  pv->make_neg = 0;\n  null_tmp_store(pp, TRUE);\n}\n    break;\n\n  case 22:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((!pv->HadVar1) && (pv->Had_lineair_sum0))\n    if(!negate_constraint(pp))\n      YYABORT;\n}\n    break;\n\n  case 23:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->make_neg = 0;\n  pv->isign = 0;\n  if(pv->HadConstraint)\n    pv->HadVar = pv->Had_lineair_sum = FALSE;\n  pv->HadVar0 = FALSE;\n  if(!store_re_op(pp, (char) ((pv->OP == '<') ? '>' : (pv->OP == '>') ? '<' : pv->OP), (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n    YYABORT;\n}\n    break;\n\n  case 24:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->f -= pv->f1;\n}\n    break;\n\n  case 25:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((pv->HadVar1) || (!pv->HadVar2) || (pv->HadVar0)) {\n    lp_yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n\n  if(pv->HadConstraint && !pv->HadVar ) {\n    /* it is a range */\n    /* already handled */\n    if(!negate_constraint(pp))\n      YYABORT;\n  }\n  else if(!pv->HadConstraint && pv->HadVar) {\n    /* it is a bound */\n\n    if(!store_bounds(pp, TRUE))\n      YYABORT;\n  }\n}\n    break;\n\n  case 26:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  /* to allow a range */\n  /* constraint: < max */\n  if(!pv->HadConstraint) {\n    lp_yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n  pv->Had_lineair_sum = FALSE;\n}\n    break;\n\n  case 27:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->Had_lineair_sum = TRUE;\n}\n    break;\n\n  case 29:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = pv->Sign;\n}\n    break;\n\n  case 31:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->state = pv->state0 = 0;\n}\n    break;\n\n  case 32:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if (pv->state == 1) {\n    /* RHS_STORE */\n    if (    (pv->isign0 || !pv->make_neg)\n        && !(pv->isign0 && !pv->make_neg)) /* but not both! */\n      pv->f0 = -pv->f0;\n    if(pv->make_neg)\n      pv->f1 += pv->f0;\n    if(!rhs_store(pp, pv->f0, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n      YYABORT;\n  }\n}\n    break;\n\n  case 35:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if ((pv->HadSign || pv->state == 1) && (pv->state0 == 1)) {\n    /* RHS_STORE */\n    if (    (pv->isign0 || !pv->make_neg)\n        && !(pv->isign0 && !pv->make_neg)) /* but not both! */\n      pv->f0 = -pv->f0;\n    if(pv->make_neg)\n      pv->f1 += pv->f0;\n    if(!rhs_store(pp, pv->f0, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n      YYABORT;\n  }\n  if (pv->state == 1) {\n    pv->f0 = pv->f;\n    pv->isign0 = pv->isign;\n  }\n  if (pv->state == 2) {\n    if((pv->HadSign) || (pv->state0 != 1)) {\n     pv->isign0 = pv->isign;\n     pv->f0 = 1.0;\n    }\n    if (    (pv->isign0 || pv->make_neg)\n        && !(pv->isign0 && pv->make_neg)) /* but not both! */\n      pv->f0 = -pv->f0;\n    if(!var_store(pp, pv->Last_var, pv->f0, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum)) {\n      lp_yyerror(pp, pp->scanner, \"var_store failed\");\n      YYABORT;\n    }\n    pv->HadConstraint |= pv->HadVar;\n    pv->HadVar = pv->HadVar0 = TRUE;\n  }\n  pv->state0 = pv->state;\n}\n    break;\n\n  case 36:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->state = 1;\n}\n    break;\n\n  case 37:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if ((pv->HasAR_M_OP) && (pv->state != 1)) {\n    lp_yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n}\n    break;\n\n  case 38:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->state = 2;\n}\n    break;\n\n  case 43:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = pv->Sign;\n}\n    break;\n\n  case 46:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = 0;\n  pv->HadSign = FALSE;\n}\n    break;\n\n  case 47:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = pv->Sign;\n  pv->HadSign = TRUE;\n}\n    break;\n\n  case 48:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->HasAR_M_OP = FALSE;\n}\n    break;\n\n  case 49:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->HasAR_M_OP = TRUE;\n}\n    break;\n\n  case 50:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if (    (pv->isign || !pv->make_neg)\n      && !(pv->isign && !pv->make_neg)) /* but not both! */\n    pv->f = -pv->f;\n  if(!rhs_store(pp, pv->f, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n    YYABORT;\n  pv->isign = 0;\n}\n    break;\n\n  case 60:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->Within_sos_decl1 = pv->Within_sos_decl;\n}\n    break;\n\n  case 62:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl1) && (!pv->Within_free_decl)) {\n    lp_yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n  pv->SOStype = pv->SOStype0;\n  check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, (int) (pv->Within_sos_decl1 = (pv->Within_sos_decl1 ? 1 : 0)), (int) pv->Within_free_decl);\n}\n    break;\n\n  case 63:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((pv->Within_sos_decl1) && (pv->SOStype == 0))\n  {\n    lp_yyerror(pp, pp->scanner, \"Unsupported SOS type (0)\");\n    YYABORT;\n  }\n}\n    break;\n\n  case 67:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  FREE(pv->Last_var0);\n  pv->Last_var0 = strdup(pv->Last_var);\n}\n    break;\n\n  case 69:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(pv->Within_sos_decl1) {\n    set_sos_type(pp, pv->SOStype);\n    set_sos_weight(pp, (double) pv->SOSweight, 1);\n  }\n}\n    break;\n\n  case 70:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((pv->Within_sos_decl1) && (!pv->SOStype))\n  {\n    set_sos_type(pp, pv->SOStype = (short) (pv->f + .1));\n  }\n  else\n  {\n    lp_yyerror(pp, pp->scanner, \"SOS type not expected\");\n    YYABORT;\n  }\n}\n    break;\n\n  case 72:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  set_sos_weight(pp, (double) pv->SOSweight, 1);\n}\n    break;\n\n  case 73:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  set_sos_weight(pp, pv->f, 1);\n}\n    break;\n\n  case 80:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(pv->Within_sos_decl1 == 1)\n  {\n    char buf[16];\n\n    pv->SOSweight++;\n    sprintf(buf, \"SOS%d\", pv->SOSweight);\n    storevarandweight(pp, buf);\n\n    check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, 2, (int) pv->Within_free_decl);\n    pv->Within_sos_decl1 = 2;\n    pv->SOSNr = 0;\n  }\n\n  storevarandweight(pp, pv->Last_var);\n\n  if(pv->Within_sos_decl1 == 2)\n  {\n    pv->SOSNr++;\n    set_sos_weight(pp, (double) pv->SOSNr, 2);\n  }\n}\n    break;\n\n  case 81:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(!pv->Within_sos_decl1) {\n    lp_yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n  if(pv->Within_sos_decl1 == 1) {\n    FREE(pv->Last_var0);\n    pv->Last_var0 = strdup(pv->Last_var);\n  }\n  if(pv->Within_sos_decl1 == 2)\n  {\n    storevarandweight(pp, pv->Last_var);\n    pv->SOSNr++;\n    set_sos_weight(pp, (double) pv->SOSNr, 2);\n  }\n}\n    break;\n\n  case 82:\n\n    {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(pv->Within_sos_decl1 == 1)\n  {\n    char buf[16];\n\n    pv->SOSweight++;\n    sprintf(buf, \"SOS%d\", pv->SOSweight);\n    storevarandweight(pp, buf);\n\n    check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, 2, (int) pv->Within_free_decl);\n    pv->Within_sos_decl1 = 2;\n    pv->SOSNr = 0;\n\n    storevarandweight(pp, pv->Last_var0);\n    pv->SOSNr++;\n  }\n\n  set_sos_weight(pp, pv->f, 2);\n}\n    break;\n\n  case 83:\n\n    { /* SOS name */\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(pv->Within_sos_decl1 == 1)\n  {\n    parse_parm *pp = PARM;\n    parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n    storevarandweight(pp, pv->Last_var0);\n    set_sos_type(pp, pv->SOStype);\n    check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, 2, (int) pv->Within_free_decl);\n    pv->Within_sos_decl1 = 2;\n    pv->SOSNr = 0;\n    pv->SOSweight++;\n  }\n}\n    break;\n\n\n/* Line 1267 of yacc.c.  */\n\n      default: break;\n    }\n  YY_SYMBOL_PRINT (\"-> $$ =\", lp_yyr1[lp_yyn], &lp_yyval, &lp_yyloc);\n\n  YYPOPSTACK (lp_yylen);\n  lp_yylen = 0;\n  YY_STACK_PRINT (lp_yyss, lp_yyssp);\n\n  *++lp_yyvsp = lp_yyval;\n\n\n  /* Now `shift' the result of the reduction.  Determine what state\n     that goes to, based on the state we popped back to and the rule\n     number reduced by.  */\n\n  lp_yyn = lp_yyr1[lp_yyn];\n\n  lp_yystate = lp_yypgoto[lp_yyn - YYNTOKENS] + *lp_yyssp;\n  if (0 <= lp_yystate && lp_yystate <= YYLAST && lp_yycheck[lp_yystate] == *lp_yyssp)\n    lp_yystate = lp_yytable[lp_yystate];\n  else\n    lp_yystate = lp_yydefgoto[lp_yyn - YYNTOKENS];\n\n  goto lp_yynewstate;\n\n\n/*------------------------------------.\n| lp_yyerrlab -- here on detecting error |\n`------------------------------------*/\nlp_yyerrlab:\n  /* If not already recovering from an error, report this error.  */\n  if (!lp_yyerrstatus)\n    {\n      ++lp_yynerrs;\n#if ! YYERROR_VERBOSE\n      lp_yyerror (parm, scanner, YY_(\"syntax error\"));\n#else\n      {\n\tYYSIZE_T lp_yysize = lp_yysyntax_error (0, lp_yystate, lp_yychar);\n\tif (lp_yymsg_alloc < lp_yysize && lp_yymsg_alloc < YYSTACK_ALLOC_MAXIMUM)\n\t  {\n\t    YYSIZE_T lp_yyalloc = 2 * lp_yysize;\n\t    if (! (lp_yysize <= lp_yyalloc && lp_yyalloc <= YYSTACK_ALLOC_MAXIMUM))\n\t      lp_yyalloc = YYSTACK_ALLOC_MAXIMUM;\n\t    if (lp_yymsg != lp_yymsgbuf)\n\t      YYSTACK_FREE (lp_yymsg);\n\t    lp_yymsg = (char *) YYSTACK_ALLOC (lp_yyalloc);\n\t    if (lp_yymsg)\n\t      lp_yymsg_alloc = lp_yyalloc;\n\t    else\n\t      {\n\t\tlp_yymsg = lp_yymsgbuf;\n\t\tlp_yymsg_alloc = sizeof lp_yymsgbuf;\n\t      }\n\t  }\n\n\tif (0 < lp_yysize && lp_yysize <= lp_yymsg_alloc)\n\t  {\n\t    (void) lp_yysyntax_error (lp_yymsg, lp_yystate, lp_yychar);\n\t    lp_yyerror (parm, scanner, lp_yymsg);\n\t  }\n\telse\n\t  {\n\t    lp_yyerror (parm, scanner, YY_(\"syntax error\"));\n\t    if (lp_yysize != 0)\n\t      goto lp_yyexhaustedlab;\n\t  }\n      }\n#endif\n    }\n\n\n\n  if (lp_yyerrstatus == 3)\n    {\n      /* If just tried and failed to reuse look-ahead token after an\n\t error, discard it.  */\n\n      if (lp_yychar <= YYEOF)\n\t{\n\t  /* Return failure if at end of input.  */\n\t  if (lp_yychar == YYEOF)\n\t    YYABORT;\n\t}\n      else\n\t{\n\t  lp_yydestruct (\"Error: discarding\",\n\t\t      lp_yytoken, &lp_yylval, parm, scanner);\n\t  lp_yychar = YYEMPTY;\n\t}\n    }\n\n  /* Else will try to reuse look-ahead token after shifting the error\n     token.  */\n  goto lp_yyerrlab1;\n\n\n/*---------------------------------------------------.\n| lp_yyerrorlab -- error raised explicitly by YYERROR.  |\n`---------------------------------------------------*/\nlp_yyerrorlab:\n\n  /* Pacify compilers like GCC when the user code never invokes\n     YYERROR and the label lp_yyerrorlab therefore never appears in user\n     code.  */\n  if (/*CONSTCOND*/ 0)\n     goto lp_yyerrorlab;\n\n  /* Do not reclaim the symbols of the rule which action triggered\n     this YYERROR.  */\n  YYPOPSTACK (lp_yylen);\n  lp_yylen = 0;\n  YY_STACK_PRINT (lp_yyss, lp_yyssp);\n  lp_yystate = *lp_yyssp;\n  goto lp_yyerrlab1;\n\n\n/*-------------------------------------------------------------.\n| lp_yyerrlab1 -- common code for both syntax error and YYERROR.  |\n`-------------------------------------------------------------*/\nlp_yyerrlab1:\n  lp_yyerrstatus = 3;\t/* Each real token shifted decrements this.  */\n\n  for (;;)\n    {\n      lp_yyn = lp_yypact[lp_yystate];\n      if (lp_yyn != YYPACT_NINF)\n\t{\n\t  lp_yyn += YYTERROR;\n\t  if (0 <= lp_yyn && lp_yyn <= YYLAST && lp_yycheck[lp_yyn] == YYTERROR)\n\t    {\n\t      lp_yyn = lp_yytable[lp_yyn];\n\t      if (0 < lp_yyn)\n\t\tbreak;\n\t    }\n\t}\n\n      /* Pop the current state because it cannot handle the error token.  */\n      if (lp_yyssp == lp_yyss)\n\tYYABORT;\n\n\n      lp_yydestruct (\"Error: popping\",\n\t\t  lp_yystos[lp_yystate], lp_yyvsp, parm, scanner);\n      YYPOPSTACK (1);\n      lp_yystate = *lp_yyssp;\n      YY_STACK_PRINT (lp_yyss, lp_yyssp);\n    }\n\n  if (lp_yyn == YYFINAL)\n    YYACCEPT;\n\n  *++lp_yyvsp = lp_yylval;\n\n\n  /* Shift the error token.  */\n  YY_SYMBOL_PRINT (\"Shifting\", lp_yystos[lp_yyn], lp_yyvsp, lp_yylsp);\n\n  lp_yystate = lp_yyn;\n  goto lp_yynewstate;\n\n\n/*-------------------------------------.\n| lp_yyacceptlab -- YYACCEPT comes here.  |\n`-------------------------------------*/\nlp_yyacceptlab:\n  lp_yyresult = 0;\n  goto lp_yyreturn;\n\n/*-----------------------------------.\n| lp_yyabortlab -- YYABORT comes here.  |\n`-----------------------------------*/\nlp_yyabortlab:\n  lp_yyresult = 1;\n  goto lp_yyreturn;\n\n#ifndef lp_yyoverflow\n/*-------------------------------------------------.\n| lp_yyexhaustedlab -- memory exhaustion comes here.  |\n`-------------------------------------------------*/\nlp_yyexhaustedlab:\n  lp_yyerror (parm, scanner, YY_(\"memory exhausted\"));\n  lp_yyresult = 2;\n  /* Fall through.  */\n#endif\n\nlp_yyreturn:\n  if (lp_yychar != YYEOF && lp_yychar != YYEMPTY)\n     lp_yydestruct (\"Cleanup: discarding lookahead\",\n\t\t lp_yytoken, &lp_yylval, parm, scanner);\n  /* Do not reclaim the symbols of the rule which action triggered\n     this YYABORT or YYACCEPT.  */\n  YYPOPSTACK (lp_yylen);\n  YY_STACK_PRINT (lp_yyss, lp_yyssp);\n  while (lp_yyssp != lp_yyss)\n    {\n      lp_yydestruct (\"Cleanup: popping\",\n\t\t  lp_yystos[*lp_yyssp], lp_yyvsp, parm, scanner);\n      YYPOPSTACK (1);\n    }\n#ifndef lp_yyoverflow\n  if (lp_yyss != lp_yyssa)\n    YYSTACK_FREE (lp_yyss);\n#endif\n#if YYERROR_VERBOSE\n  if (lp_yymsg != lp_yymsgbuf)\n    YYSTACK_FREE (lp_yymsg);\n#endif\n  /* Make sure YYID is used.  */\n  return YYID (lp_yyresult);\n}\n\n\n\n\n\nstatic void lp_yy_delete_allocated_memory(parse_parm *pp)\n{\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  /* free memory allocated by flex. Otherwise some memory is not freed.\n     This is a bit tricky. There is not much documentation about this, but a lot of\n     reports of memory that keeps allocated */\n\n  /* If you get errors on this function call, just comment it. This will only result\n     in some memory that is not being freed. */\n\n# if defined YY_CURRENT_BUFFER\n    /* flex defines the macro YY_CURRENT_BUFFER, so you should only get here if lp_rlp.h is\n       generated by flex */\n    /* lex doesn't define this macro and thus should not come here, but lex doesn't has\n       this memory leak also ...*/\n\n#  if 0\n    /* older versions of flex */\n    lp_yy_delete_buffer(YY_CURRENT_BUFFER); /* comment this line if you have problems with it */\n    lp_yy_init = 1; /* make sure that the next time memory is allocated again */\n    lp_yy_start = 0;\n#  else\n    /* As of version 2.5.9 Flex  */\n    lp_yylex_destroy(pp->scanner); /* comment this line if you have problems with it */\n#  endif\n# endif\n\n  FREE(pv->Last_var);\n  FREE(pv->Last_var0);\n}\n\nstatic int parse(parse_parm *pp)\n{\n  return(lp_yyparse(pp, pp->scanner));\n}\n\nlprec *read_lp1(lprec *lp, void *userhandle, read_modeldata_func read_modeldata, int verbose, char *lp_name)\n{\n  parse_vars *pv;\n  lprec *lp1 = NULL;\n\n  CALLOC(pv, 1, parse_vars);\n  if (pv != NULL) {\n    parse_parm pp;\n\n    memset(&pp, 0, sizeof(pp));\n    pp.parse_vars = (void *) pv;\n\n    lp_yylex_init(&pp.scanner);\n    lp_yyset_extra(&pp, pp.scanner);\n\n    lp_yyset_in((FILE *) userhandle, pp.scanner);\n    lp_yyset_out(NULL, pp.scanner);\n    pv->lp_input = read_modeldata;\n    pv->userhandle = userhandle;\n    lp1 = yacc_read(lp, verbose, lp_name, parse, &pp, lp_yy_delete_allocated_memory);\n    FREE(pv);\n  }\n  return(lp1);\n}\n\nlprec * __WINAPI read_lp(FILE *filename, int verbose, char *lp_name)\n{\n  return(read_lp1(NULL, filename, lp_input_lp_yyin, verbose, lp_name));\n}\n\nlprec * __WINAPI read_lpex(void *userhandle, read_modeldata_func read_modeldata, int verbose, char *lp_name)\n{\n  return(read_lp1(NULL, userhandle, read_modeldata, verbose, lp_name));\n}\n\nlprec *read_LP1(lprec *lp, char *filename, int verbose, char *lp_name)\n{\n  FILE *fpin;\n\n  if((fpin = fopen(filename, \"r\")) != NULL) {\n    lp = read_lp1(lp, fpin, lp_input_lp_yyin, verbose, lp_name);\n    fclose(fpin);\n  }\n  else\n    lp = NULL;\n  return(lp);\n}\n\nlprec * __WINAPI read_LP(char *filename, int verbose, char *lp_name)\n{\n  return(read_LP1(NULL, filename, verbose, lp_name));\n}\n\nMYBOOL __WINAPI LP_readhandle(lprec **lp, FILE *filename, int verbose, char *lp_name)\n{\n  if(lp != NULL)\n    *lp = read_lp1(*lp, filename, lp_input_lp_yyin, verbose, lp_name);\n\n  return((lp != NULL) && (*lp != NULL));\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_rlp.h",
    "content": "\n\n\n#define  YY_INT_ALIGNED short int\n\n/* A lexical scanner generated by flex */\n\n#define FLEX_SCANNER\n#define YY_FLEX_MAJOR_VERSION 2\n#define YY_FLEX_MINOR_VERSION 5\n#define YY_FLEX_SUBMINOR_VERSION 35\n#if YY_FLEX_SUBMINOR_VERSION > 0\n#define FLEX_BETA\n#endif\n\n/* First, we deal with  platform-specific or compiler-specific issues. */\n\n/* begin standard C headers. */\n#include <stdio.h>\n#include <string.h>\n#include <errno.h>\n#include <stdlib.h>\n\n/* end standard C headers. */\n\n/* flex integer type definitions */\n\n#ifndef FLEXINT_H\n#define FLEXINT_H\n\n/* C99 systems have <inttypes.h>. Non-C99 systems may or may not. */\n\n#if defined (__STDC_VERSION__) && __STDC_VERSION__ >= 199901L\n\n/* C99 says to define __STDC_LIMIT_MACROS before including stdint.h,\n * if you want the limit (max/min) macros for int types. \n */\n#ifndef __STDC_LIMIT_MACROS\n#define __STDC_LIMIT_MACROS 1\n#endif\n\n#include <inttypes.h>\ntypedef int8_t flex_int8_t;\ntypedef uint8_t flex_uint8_t;\ntypedef int16_t flex_int16_t;\ntypedef uint16_t flex_uint16_t;\ntypedef int32_t flex_int32_t;\ntypedef uint32_t flex_uint32_t;\n#else\ntypedef signed char flex_int8_t;\ntypedef short int flex_int16_t;\ntypedef int flex_int32_t;\ntypedef unsigned char flex_uint8_t; \ntypedef unsigned short int flex_uint16_t;\ntypedef unsigned int flex_uint32_t;\n#endif /* ! C99 */\n\n/* Limits of integral types. */\n#ifndef INT8_MIN\n#define INT8_MIN               (-128)\n#endif\n#ifndef INT16_MIN\n#define INT16_MIN              (-32767-1)\n#endif\n#ifndef INT32_MIN\n#define INT32_MIN              (-2147483647-1)\n#endif\n#ifndef INT8_MAX\n#define INT8_MAX               (127)\n#endif\n#ifndef INT16_MAX\n#define INT16_MAX              (32767)\n#endif\n#ifndef INT32_MAX\n#define INT32_MAX              (2147483647)\n#endif\n#ifndef UINT8_MAX\n#define UINT8_MAX              (255U)\n#endif\n#ifndef UINT16_MAX\n#define UINT16_MAX             (65535U)\n#endif\n#ifndef UINT32_MAX\n#define UINT32_MAX             (4294967295U)\n#endif\n\n#endif /* ! FLEXINT_H */\n\n#ifdef __cplusplus\n\n/* The \"const\" storage-class-modifier is valid. */\n#define YY_USE_CONST\n\n#else\t/* ! __cplusplus */\n\n/* C99 requires __STDC__ to be defined as 1. */\n#if defined (__STDC__)\n\n#define YY_USE_CONST\n\n#endif\t/* defined (__STDC__) */\n#endif\t/* ! __cplusplus */\n\n#ifdef YY_USE_CONST\n#define lp_yyconst const\n#else\n#define lp_yyconst\n#endif\n\n/* Returned upon end-of-file. */\n#define YY_NULL 0\n\n/* Promotes a possibly negative, possibly signed char to an unsigned\n * integer for use as an array index.  If the signed char is negative,\n * we want to instead treat it as an 8-bit unsigned char, hence the\n * double cast.\n */\n#define YY_SC_TO_UI(c) ((unsigned int) (unsigned char) c)\n\n/* An opaque pointer. */\n#ifndef YY_TYPEDEF_YY_SCANNER_T\n#define YY_TYPEDEF_YY_SCANNER_T\ntypedef void* lp_yyscan_t;\n#endif\n\n/* For convenience, these vars (plus the bison vars far below)\n   are macros in the reentrant scanner. */\n#define lp_yyin lp_yyg->lp_yyin_r\n#define lp_yyout lp_yyg->lp_yyout_r\n#define lp_yyextra lp_yyg->lp_yyextra_r\n#define lp_yyleng lp_yyg->lp_yyleng_r\n#define lp_yytext lp_yyg->lp_yytext_r\n#define lp_yylineno (YY_CURRENT_BUFFER_LVALUE->lp_yy_bs_lineno)\n#define lp_yycolumn (YY_CURRENT_BUFFER_LVALUE->lp_yy_bs_column)\n#define lp_yy_flex_debug lp_yyg->lp_yy_flex_debug_r\n\n/* Enter a start condition.  This macro really ought to take a parameter,\n * but we do it the disgusting crufty way forced on us by the ()-less\n * definition of BEGIN.\n */\n#define BEGIN lp_yyg->lp_yy_start = 1 + 2 *\n\n/* Translate the current start state into a value that can be later handed\n * to BEGIN to return to the state.  The YYSTATE alias is for lex\n * compatibility.\n */\n#define YY_START ((lp_yyg->lp_yy_start - 1) / 2)\n#define YYSTATE YY_START\n\n/* Action number for EOF rule of a given start state. */\n#define YY_STATE_EOF(state) (YY_END_OF_BUFFER + state + 1)\n\n/* Special action meaning \"start processing a new file\". */\n#define YY_NEW_FILE lp_yyrestart(lp_yyin ,lp_yyscanner )\n\n#define YY_END_OF_BUFFER_CHAR 0\n\n/* Size of default input buffer. */\n#ifndef YY_BUF_SIZE\n#define YY_BUF_SIZE 16384\n#endif\n\n/* The state buf must be large enough to hold one state per character in the main buffer.\n */\n#define YY_STATE_BUF_SIZE   ((YY_BUF_SIZE + 2) * sizeof(lp_yy_state_type))\n\n#ifndef YY_TYPEDEF_YY_BUFFER_STATE\n#define YY_TYPEDEF_YY_BUFFER_STATE\ntypedef struct lp_yy_buffer_state *YY_BUFFER_STATE;\n#endif\n\n#define EOB_ACT_CONTINUE_SCAN 0\n#define EOB_ACT_END_OF_FILE 1\n#define EOB_ACT_LAST_MATCH 2\n\n    /* Note: We specifically omit the test for lp_yy_rule_can_match_eol because it requires\n     *       access to the local variable lp_yy_act. Since lp_yyless() is a macro, it would break\n     *       existing scanners that call lp_yyless() from OUTSIDE lp_yylex. \n     *       One obvious solution it to make lp_yy_act a global. I tried that, and saw\n     *       a 5% performance hit in a non-lp_yylineno scanner, because lp_yy_act is\n     *       normally declared as a register variable-- so it is not worth it.\n     */\n    #define  YY_LESS_LINENO(n) \\\n            do { \\\n                int lp_yyl;\\\n                for ( lp_yyl = n; lp_yyl < lp_yyleng; ++lp_yyl )\\\n                    if ( lp_yytext[lp_yyl] == '\\n' )\\\n                        --lp_yylineno;\\\n            }while(0)\n    \n/* Return all but the first \"n\" matched characters back to the input stream. */\n#define lp_yyless(n) \\\n\tdo \\\n\t\t{ \\\n\t\t/* Undo effects of setting up lp_yytext. */ \\\n        int lp_yyless_macro_arg = (n); \\\n        YY_LESS_LINENO(lp_yyless_macro_arg);\\\n\t\t*lp_yy_cp = lp_yyg->lp_yy_hold_char; \\\n\t\tYY_RESTORE_YY_MORE_OFFSET \\\n\t\tlp_yyg->lp_yy_c_buf_p = lp_yy_cp = lp_yy_bp + lp_yyless_macro_arg - YY_MORE_ADJ; \\\n\t\tYY_DO_BEFORE_ACTION; /* set up lp_yytext again */ \\\n\t\t} \\\n\twhile ( 0 )\n\n#define unput(c) lp_yyunput( c, lp_yyg->lp_yytext_ptr , lp_yyscanner )\n\n#ifndef YY_TYPEDEF_YY_SIZE_T\n#define YY_TYPEDEF_YY_SIZE_T\ntypedef size_t lp_yy_size_t;\n#endif\n\n#ifndef YY_STRUCT_YY_BUFFER_STATE\n#define YY_STRUCT_YY_BUFFER_STATE\nstruct lp_yy_buffer_state\n\t{\n\tFILE *lp_yy_input_file;\n\n\tchar *lp_yy_ch_buf;\t\t/* input buffer */\n\tchar *lp_yy_buf_pos;\t\t/* current position in input buffer */\n\n\t/* Size of input buffer in bytes, not including room for EOB\n\t * characters.\n\t */\n\tlp_yy_size_t lp_yy_buf_size;\n\n\t/* Number of characters read into lp_yy_ch_buf, not including EOB\n\t * characters.\n\t */\n\tint lp_yy_n_chars;\n\n\t/* Whether we \"own\" the buffer - i.e., we know we created it,\n\t * and can realloc() it to grow it, and should free() it to\n\t * delete it.\n\t */\n\tint lp_yy_is_our_buffer;\n\n\t/* Whether this is an \"interactive\" input source; if so, and\n\t * if we're using stdio for input, then we want to use getc()\n\t * instead of fread(), to make sure we stop fetching input after\n\t * each newline.\n\t */\n\tint lp_yy_is_interactive;\n\n\t/* Whether we're considered to be at the beginning of a line.\n\t * If so, '^' rules will be active on the next match, otherwise\n\t * not.\n\t */\n\tint lp_yy_at_bol;\n\n    int lp_yy_bs_lineno; /**< The line count. */\n    int lp_yy_bs_column; /**< The column count. */\n    \n\t/* Whether to try to fill the input buffer when we reach the\n\t * end of it.\n\t */\n\tint lp_yy_fill_buffer;\n\n\tint lp_yy_buffer_status;\n\n#define YY_BUFFER_NEW 0\n#define YY_BUFFER_NORMAL 1\n\t/* When an EOF's been seen but there's still some text to process\n\t * then we mark the buffer as YY_EOF_PENDING, to indicate that we\n\t * shouldn't try reading from the input source any more.  We might\n\t * still have a bunch of tokens to match, though, because of\n\t * possible backing-up.\n\t *\n\t * When we actually see the EOF, we change the status to \"new\"\n\t * (via lp_yyrestart()), so that the user can continue scanning by\n\t * just pointing lp_yyin at a new input file.\n\t */\n#define YY_BUFFER_EOF_PENDING 2\n\n\t};\n#endif /* !YY_STRUCT_YY_BUFFER_STATE */\n\n/* We provide macros for accessing buffer states in case in the\n * future we want to put the buffer states in a more general\n * \"scanner state\".\n *\n * Returns the top of the stack, or NULL.\n */\n#define YY_CURRENT_BUFFER ( lp_yyg->lp_yy_buffer_stack \\\n                          ? lp_yyg->lp_yy_buffer_stack[lp_yyg->lp_yy_buffer_stack_top] \\\n                          : NULL)\n\n/* Same as previous macro, but useful when we know that the buffer stack is not\n * NULL or when we need an lvalue. For internal use only.\n */\n#define YY_CURRENT_BUFFER_LVALUE lp_yyg->lp_yy_buffer_stack[lp_yyg->lp_yy_buffer_stack_top]\n\nvoid lp_yyrestart (FILE *input_file ,lp_yyscan_t lp_yyscanner );\nvoid lp_yy_switch_to_buffer (YY_BUFFER_STATE new_buffer ,lp_yyscan_t lp_yyscanner );\nYY_BUFFER_STATE lp_yy_create_buffer (FILE *file,int size ,lp_yyscan_t lp_yyscanner );\nvoid lp_yy_delete_buffer (YY_BUFFER_STATE b ,lp_yyscan_t lp_yyscanner );\nvoid lp_yy_flush_buffer (YY_BUFFER_STATE b ,lp_yyscan_t lp_yyscanner );\nvoid lp_yypush_buffer_state (YY_BUFFER_STATE new_buffer ,lp_yyscan_t lp_yyscanner );\nvoid lp_yypop_buffer_state (lp_yyscan_t lp_yyscanner );\n\nstatic void lp_yyensure_buffer_stack (lp_yyscan_t lp_yyscanner );\nstatic void lp_yy_load_buffer_state (lp_yyscan_t lp_yyscanner );\nstatic void lp_yy_init_buffer (YY_BUFFER_STATE b,FILE *file ,lp_yyscan_t lp_yyscanner );\n\n#define YY_FLUSH_BUFFER lp_yy_flush_buffer(YY_CURRENT_BUFFER ,lp_yyscanner)\n\nYY_BUFFER_STATE lp_yy_scan_buffer (char *base,lp_yy_size_t size ,lp_yyscan_t lp_yyscanner );\nYY_BUFFER_STATE lp_yy_scan_string (lp_yyconst char *lp_yy_str ,lp_yyscan_t lp_yyscanner );\nYY_BUFFER_STATE lp_yy_scan_bytes (lp_yyconst char *bytes,int len ,lp_yyscan_t lp_yyscanner );\n\nvoid *lp_yyalloc (lp_yy_size_t ,lp_yyscan_t lp_yyscanner );\nvoid *lp_yyrealloc (void *,lp_yy_size_t ,lp_yyscan_t lp_yyscanner );\nvoid lp_yyfree (void * ,lp_yyscan_t lp_yyscanner );\n\n#define lp_yy_new_buffer lp_yy_create_buffer\n\n#define lp_yy_set_interactive(is_interactive) \\\n\t{ \\\n\tif ( ! YY_CURRENT_BUFFER ){ \\\n        lp_yyensure_buffer_stack (lp_yyscanner); \\\n\t\tYY_CURRENT_BUFFER_LVALUE =    \\\n            lp_yy_create_buffer(lp_yyin,YY_BUF_SIZE ,lp_yyscanner); \\\n\t} \\\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_is_interactive = is_interactive; \\\n\t}\n\n#define lp_yy_set_bol(at_bol) \\\n\t{ \\\n\tif ( ! YY_CURRENT_BUFFER ){\\\n        lp_yyensure_buffer_stack (lp_yyscanner); \\\n\t\tYY_CURRENT_BUFFER_LVALUE =    \\\n            lp_yy_create_buffer(lp_yyin,YY_BUF_SIZE ,lp_yyscanner); \\\n\t} \\\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol = at_bol; \\\n\t}\n\n#define YY_AT_BOL() (YY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol)\n\n/* Begin user sect3 */\n\n#define lp_yywrap(n) 1\n#define YY_SKIP_YYWRAP\n\ntypedef unsigned char YY_CHAR;\n\ntypedef int lp_yy_state_type;\n\n#define lp_yytext_ptr lp_yytext_r\n\nstatic lp_yy_state_type lp_yy_get_previous_state (lp_yyscan_t lp_yyscanner );\nstatic lp_yy_state_type lp_yy_try_NUL_trans (lp_yy_state_type current_state  ,lp_yyscan_t lp_yyscanner);\nstatic int lp_yy_get_next_buffer (lp_yyscan_t lp_yyscanner );\nstatic void lp_yy_fatal_error (lp_yyconst char msg[] ,lp_yyscan_t lp_yyscanner );\n\n/* Done after the current pattern has been matched and before the\n * corresponding action - sets up lp_yytext.\n */\n#define YY_DO_BEFORE_ACTION \\\n\tlp_yyg->lp_yytext_ptr = lp_yy_bp; \\\n\tlp_yyleng = (size_t) (lp_yy_cp - lp_yy_bp); \\\n\tlp_yyg->lp_yy_hold_char = *lp_yy_cp; \\\n\t*lp_yy_cp = '\\0'; \\\n\tlp_yyg->lp_yy_c_buf_p = lp_yy_cp;\n\n#define YY_NUM_RULES 33\n#define YY_END_OF_BUFFER 34\n/* This struct is not used in this scanner,\n   but its presence is necessary. */\nstruct lp_yy_trans_info\n\t{\n\tflex_int32_t lp_yy_verify;\n\tflex_int32_t lp_yy_nxt;\n\t};\nstatic lp_yyconst flex_int16_t lp_yy_accept[144] =\n    {   0,\n        0,    0,    0,    0,    0,    0,   34,   32,   10,   10,\n       27,   17,   11,   32,   32,   14,   26,   31,   29,   28,\n       30,   25,   25,   10,   25,   25,   25,   25,    3,    4,\n        3,    3,    9,    7,    8,   10,   17,   17,    0,   15,\n        1,    6,   15,   14,    0,   29,   30,    0,   25,   24,\n        0,   25,   25,   10,    0,    0,    0,    0,   25,   25,\n       25,   25,   25,    2,    0,   15,    0,   15,   22,    0,\n       25,   25,    0,    0,    0,    0,    0,   19,   25,   18,\n       20,   25,   25,   21,    0,   25,    0,   13,   25,    0,\n       12,   25,   19,    0,   18,   20,   21,   25,   23,   25,\n\n       20,   21,   21,   16,   16,    0,   25,   25,    0,   23,\n        0,   21,   25,   25,    0,    0,   25,   25,    0,    0,\n       19,   25,    0,    0,   25,   25,   19,    0,   18,    0,\n        0,   25,   25,   18,    0,    0,    0,    0,    0,    0,\n        0,    0,    0\n    } ;\n\nstatic lp_yyconst flex_int32_t lp_yy_ec[256] =\n    {   0,\n        1,    1,    1,    1,    1,    1,    1,    1,    2,    3,\n        1,    1,    4,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    2,    1,    1,    5,    6,    5,    5,    5,    1,\n        1,    7,    8,    9,   10,   11,   12,   13,   14,   14,\n       13,   13,   13,   13,   13,   13,   13,   15,   16,   17,\n       18,   19,    1,    5,   20,   21,   22,   23,   24,   25,\n       26,   23,   27,   23,   23,   23,   28,   29,   30,   23,\n       23,   31,   32,   33,   34,   23,   23,   35,   36,   37,\n        5,    1,    5,    5,    5,    1,   20,   21,   22,   23,\n\n       24,   25,   26,   23,   27,   23,   23,   23,   28,   29,\n       30,   23,   23,   31,   32,   33,   34,   23,   23,   35,\n       36,   37,    5,    1,    5,    5,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1\n    } ;\n\nstatic lp_yyconst flex_int32_t lp_yy_meta[38] =\n    {   0,\n        1,    2,    3,    3,    4,    5,    6,    3,    6,    3,\n        5,    5,    5,    5,    7,    6,    7,    6,    6,    4,\n        4,    4,    4,    4,    4,    4,    8,    4,    4,    4,\n        4,    4,    4,    4,    4,    4,    4\n    } ;\n\nstatic lp_yyconst flex_int16_t lp_yy_base[150] =\n    {   0,\n        0,   36,   36,   38,   43,   45,  366,  388,   48,   62,\n      388,  338,  388,   40,   48,   60,  388,  388,  346,  388,\n      326,   60,   65,   91,   81,   74,   85,  102,  388,  388,\n      388,  330,  388,  388,  388,  125,  313,  134,  308,   96,\n      388,  388,  117,  132,  139,  388,  388,   88,  146,  320,\n        0,  149,  152,    0,  307,  301,  294,   83,  153,  156,\n      157,  189,  160,  388,  286,  126,   65,  108,  388,  289,\n      181,  185,  272,  273,  250,  249,  220,  199,  203,  208,\n      192,  211,  219,  227,  243,  109,  163,  225,  202,  174,\n      224,  215,  213,  207,  191,  388,  189,  227,  228,  231,\n\n      244,  240,  253,  276,  388,  170,  260,  262,  166,  388,\n      169,  179,  263,  241,  166,  159,  270,  272,  149,  155,\n      284,  288,  130,  124,  296,  303,  388,  103,  300,   96,\n       45,  324,  328,  388,   82,  311,   79,   68,   54,   56,\n       25,   12,  388,  345,  353,  360,  367,  372,  379\n    } ;\n\nstatic lp_yyconst flex_int16_t lp_yy_def[150] =\n    {   0,\n      143,    1,  144,  144,  145,  145,  143,  143,  143,  143,\n      143,  146,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  147,  147,  143,  147,  147,  147,  147,  143,  143,\n      143,  143,  143,  143,  143,  143,  146,  143,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  147,  143,\n      148,  147,  147,   24,  143,  143,  143,  143,  147,  147,\n      147,  147,  147,  143,  143,  143,  143,  143,  143,  148,\n      147,  147,  143,  143,  143,  143,  143,  147,  147,  147,\n      147,  147,  147,  147,  149,  143,  143,  143,   62,  143,\n      143,   62,  143,  143,  143,  143,  143,   62,   62,   62,\n\n       62,   62,   62,  143,  143,  143,   62,   62,  143,  143,\n      143,  143,   62,   62,  143,  143,   62,   62,  143,  143,\n       62,   62,  143,  143,   62,   62,  143,  143,   62,  143,\n      143,  147,  147,  143,  143,  149,  143,  143,  143,  143,\n      143,  143,    0,  143,  143,  143,  143,  143,  143\n    } ;\n\nstatic lp_yyconst flex_int16_t lp_yy_nxt[426] =\n    {   0,\n        8,    9,   10,    9,    8,    8,   11,   12,   13,   12,\n       14,   15,   16,   16,   17,   18,   19,   20,   21,   22,\n       22,   22,   22,   22,   22,   22,   22,   23,   22,   22,\n       22,   22,   22,   22,   22,   22,   22,   24,   30,   31,\n       30,   31,   32,   96,   32,   34,   35,   34,   35,   36,\n       36,   36,   40,   40,   41,   37,   25,   37,  142,   42,\n       26,   48,   27,   36,   36,   36,   48,   28,  136,   37,\n       43,   37,   44,   44,   50,   48,   51,   68,   68,   50,\n      136,   51,   48,   45,   52,  141,   48,  140,   50,   48,\n       51,   53,   54,   36,   36,   50,  139,   51,   37,   50,\n\n       37,   51,   50,   48,   60,  138,   76,   59,   40,   40,\n       48,   55,   77,   61,  137,   56,   50,   57,   51,   45,\n       68,   68,   58,   50,  135,   62,   36,   36,   36,   66,\n       66,   63,   37,  134,   37,   38,   38,   38,   66,   66,\n       45,   38,   43,   38,   44,   44,   67,   48,   67,   45,\n       48,   68,   68,   48,   48,   45,  131,   48,   48,  130,\n       50,   48,   51,   50,   87,   51,   50,   50,   51,   51,\n       50,   50,   51,   51,   50,   90,   51,   88,  128,   79,\n       72,   78,   87,   71,  127,  124,   90,  123,   91,   80,\n       48,   84,  112,   48,  120,   88,  119,   51,  116,   91,\n\n       48,   51,  112,   50,   48,   51,   50,   89,   51,   48,\n       81,   92,   48,   50,  111,   51,   82,   50,   98,   51,\n       48,   83,   50,   49,   51,   50,   99,   51,   48,  107,\n      110,  100,  109,   50,   49,   51,   49,  101,   69,   69,\n      103,   50,  108,   51,  104,  104,  104,   49,   49,   49,\n      102,   97,   49,  115,   49,   49,  114,  113,   49,   49,\n       49,   49,   49,   49,  122,   49,  103,   49,   49,  106,\n       96,   49,   49,   49,   49,   81,   49,  104,  104,  104,\n       49,   49,   95,   49,   49,   49,  117,   49,  118,   49,\n       49,   49,   49,   49,   49,   49,   94,   49,  121,   49,\n\n       93,  125,   49,  126,   49,   49,  125,   86,  126,   49,\n       85,   49,  104,  104,  104,   49,   49,   49,  129,  132,\n       49,   49,   75,   49,   49,   87,  133,   49,   49,   90,\n       49,   74,   49,   73,   69,   49,   65,  143,   88,   39,\n       51,   64,   91,   47,   51,   29,   29,   29,   29,   29,\n       29,   29,   29,   33,   33,   33,   33,   33,   33,   33,\n       33,   38,   38,   46,   39,  143,  143,   38,   49,  143,\n       49,   49,  143,   49,   49,   70,   70,  143,  143,   70,\n      105,  105,  143,  105,  105,  105,  105,    7,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  143,  143,  143,  143\n    } ;\n\nstatic lp_yyconst flex_int16_t lp_yy_chk[426] =\n    {   0,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    1,    1,    1,\n        1,    1,    1,    1,    1,    1,    1,    2,    3,    3,\n        4,    4,    3,  142,    4,    5,    5,    6,    6,    9,\n        9,    9,   14,   14,   15,    9,    2,    9,  141,   15,\n        2,   22,    2,   10,   10,   10,   23,    2,  131,   10,\n       16,   10,   16,   16,   22,   26,   22,   67,   67,   23,\n      131,   23,   25,   16,   23,  140,   27,  139,   26,   48,\n       26,   23,   24,   24,   24,   25,  138,   25,   24,   27,\n\n       24,   27,   48,   28,   26,  137,   58,   25,   40,   40,\n       86,   24,   58,   27,  135,   24,   28,   24,   28,   40,\n       68,   68,   24,   86,  130,   28,   36,   36,   36,   43,\n       43,   28,   36,  128,   36,   38,   38,   38,   66,   66,\n       43,   38,   44,   38,   44,   44,   45,   49,   45,   66,\n       52,   45,   45,   53,   59,   44,  124,   60,   61,  123,\n       49,   63,   49,   52,   87,   52,   53,   59,   53,   59,\n       60,   61,   60,   61,   63,   90,   63,   87,  120,   60,\n       53,   59,   71,   52,  119,  116,   72,  115,   90,   61,\n       62,   63,  112,   81,  111,   71,  109,   71,  106,   72,\n\n       78,   72,   97,   62,   79,   62,   81,   71,   81,   80,\n       62,   72,   82,   78,   95,   78,   62,   79,   78,   79,\n       83,   62,   80,   89,   80,   82,   79,   82,   84,   89,\n       94,   80,   93,   83,   89,   83,   92,   82,   91,   88,\n       84,   84,   92,   84,   85,   85,   85,   92,   98,   99,\n       83,   77,  100,  101,   98,   99,  100,   98,  100,   98,\n       99,  102,  114,  100,  114,  101,  103,  102,  114,   85,\n       76,  101,  102,  114,  103,  101,  101,  104,  104,  104,\n      103,  107,   75,  108,  113,  103,  107,  107,  108,  108,\n      113,  117,  107,  118,  108,  113,   74,  117,  113,  118,\n\n       73,  117,  117,  118,  118,  121,  117,   70,  118,  122,\n       65,  121,  136,  136,  136,  122,  121,  125,  122,  125,\n      122,  129,   57,  125,  126,  132,  126,  129,  125,  133,\n      126,   56,  129,   55,   50,  126,   39,  136,  132,   37,\n      132,   32,  133,   21,  133,  144,  144,  144,  144,  144,\n      144,  144,  144,  145,  145,  145,  145,  145,  145,  145,\n      145,  146,  146,   19,   12,    7,    0,  146,  147,    0,\n      147,  147,    0,  147,  147,  148,  148,    0,    0,  148,\n      149,  149,    0,  149,  149,  149,  149,  143,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  143,  143,  143,  143,  143,  143,  143,  143,  143,\n      143,  143,  143,  143,  143\n    } ;\n\n/* Table of booleans, true if rule could match eol. */\nstatic lp_yyconst flex_int32_t lp_yy_rule_can_match_eol[34] =\n    {   0,\n0, 0, 0, 1, 0, 0, 1, 0, 0, 1, 0, 0, 0, 0, 0, 1, 1, 0, 0, \n    0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0, 0,     };\n\n/* The intent behind this definition is that it'll catch\n * any uses of REJECT which flex missed.\n */\n#define REJECT reject_used_but_not_detected\n#define lp_yymore() lp_yymore_used_but_not_detected\n#define YY_MORE_ADJ 0\n#define YY_RESTORE_YY_MORE_OFFSET\n/*\n   made reentrant with help of\n   http://www.usualcoding.eu/post/2007/09/03/Building-a-reentrant-parser-in-C-with-Flex/Bison\n*/\n/*\n   Note that a minimum version of flex is needed to be able to compile this.\n   Older version don't know the reentrant code.\n   Version 2.5.4 is not enough. Probably at least v2.5.31 is needed. Tested with v2.5.35\n*/\n/*\n** We want the scanner to be reentrant, therefore generate no global variables.\n** That what the 'reentrant' option is for.\n** 'bison-bridge' is used to create a bison compatible scanner and share lp_yylval\n*/\n\n#define INITIAL 0\n#define COMMENT 1\n#define LINECOMMENT 2\n\n#ifndef YY_NO_UNISTD_H\n/* Special case for \"unistd.h\", since it is non-ANSI. We include it way\n * down here because we want the user's section 1 to have been scanned first.\n * The user has a chance to override it with an option.\n */\n#include <unistd.h>\n#endif\n\n#ifndef YY_EXTRA_TYPE\n#define YY_EXTRA_TYPE void *\n#endif\n\n/* Holds the entire state of the reentrant scanner. */\nstruct lp_yyguts_t\n    {\n\n    /* User-defined. Not touched by flex. */\n    YY_EXTRA_TYPE lp_yyextra_r;\n\n    /* The rest are the same as the globals declared in the non-reentrant scanner. */\n    FILE *lp_yyin_r, *lp_yyout_r;\n    size_t lp_yy_buffer_stack_top; /**< index of top of stack. */\n    size_t lp_yy_buffer_stack_max; /**< capacity of stack. */\n    YY_BUFFER_STATE * lp_yy_buffer_stack; /**< Stack as an array. */\n    char lp_yy_hold_char;\n    int lp_yy_n_chars;\n    int lp_yyleng_r;\n    char *lp_yy_c_buf_p;\n    int lp_yy_init;\n    int lp_yy_start;\n    int lp_yy_did_buffer_switch_on_eof;\n    int lp_yy_start_stack_ptr;\n    int lp_yy_start_stack_depth;\n    int *lp_yy_start_stack;\n    lp_yy_state_type lp_yy_last_accepting_state;\n    char* lp_yy_last_accepting_cpos;\n\n    int lp_yylineno_r;\n    int lp_yy_flex_debug_r;\n\n    char *lp_yytext_r;\n    int lp_yy_more_flag;\n    int lp_yy_more_len;\n\n    YYSTYPE * lp_yylval_r;\n\n    }; /* end struct lp_yyguts_t */\n\nstatic int lp_yy_init_globals (lp_yyscan_t lp_yyscanner );\n\n    /* This must go here because YYSTYPE and YYLTYPE are included\n     * from bison output in section 1.*/\n    #    define lp_yylval lp_yyg->lp_yylval_r\n    \nint lp_yylex_init (lp_yyscan_t* scanner);\n\nint lp_yylex_init_extra (YY_EXTRA_TYPE user_defined,lp_yyscan_t* scanner);\n\n/* Accessor methods to globals.\n   These are made visible to non-reentrant scanners for convenience. */\n\nint lp_yylex_destroy (lp_yyscan_t lp_yyscanner );\n\nint lp_yyget_debug (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_debug (int debug_flag ,lp_yyscan_t lp_yyscanner );\n\nYY_EXTRA_TYPE lp_yyget_extra (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_extra (YY_EXTRA_TYPE user_defined ,lp_yyscan_t lp_yyscanner );\n\nFILE *lp_yyget_in (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_in  (FILE * in_str ,lp_yyscan_t lp_yyscanner );\n\nFILE *lp_yyget_out (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_out  (FILE * out_str ,lp_yyscan_t lp_yyscanner );\n\nint lp_yyget_leng (lp_yyscan_t lp_yyscanner );\n\nchar *lp_yyget_text (lp_yyscan_t lp_yyscanner );\n\nint lp_yyget_lineno (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_lineno (int line_number ,lp_yyscan_t lp_yyscanner );\n\nYYSTYPE * lp_yyget_lval (lp_yyscan_t lp_yyscanner );\n\nvoid lp_yyset_lval (YYSTYPE * lp_yylval_param ,lp_yyscan_t lp_yyscanner );\n\n/* Macros after this point can all be overridden by user definitions in\n * section 1.\n */\n\n#ifndef YY_SKIP_YYWRAP\n#ifdef __cplusplus\nextern \"C\" int lp_yywrap (lp_yyscan_t lp_yyscanner );\n#else\nextern int lp_yywrap (lp_yyscan_t lp_yyscanner );\n#endif\n#endif\n\n    static void lp_yyunput (int c,char *buf_ptr  ,lp_yyscan_t lp_yyscanner);\n    \n#ifndef lp_yytext_ptr\nstatic void lp_yy_flex_strncpy (char *,lp_yyconst char *,int ,lp_yyscan_t lp_yyscanner);\n#endif\n\n#ifdef YY_NEED_STRLEN\nstatic int lp_yy_flex_strlen (lp_yyconst char * ,lp_yyscan_t lp_yyscanner);\n#endif\n\n#ifndef YY_NO_INPUT\n\n#ifdef __cplusplus\nstatic int lp_yyinput (lp_yyscan_t lp_yyscanner );\n#else\nstatic int input (lp_yyscan_t lp_yyscanner );\n#endif\n\n#endif\n\n/* Amount of stuff to slurp up with each read. */\n#ifndef YY_READ_BUF_SIZE\n#define YY_READ_BUF_SIZE 8192\n#endif\n\n/* Copy whatever the last rule matched to the standard output. */\n#ifndef ECHO\n/* This used to be an fputs(), but since the string might contain NUL's,\n * we now use fwrite().\n */\n#define ECHO fwrite( lp_yytext, lp_yyleng, 1, lp_yyout )\n#endif\n\n/* Gets input and stuffs it into \"buf\".  number of characters read, or YY_NULL,\n * is returned in \"result\".\n */\n#ifndef YY_INPUT\n#define YY_INPUT(buf,result,max_size) \\\n\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_is_interactive ) \\\n\t\t{ \\\n\t\tint c = '*'; \\\n\t\tint n; \\\n\t\tfor ( n = 0; n < max_size && \\\n\t\t\t     (c = getc( lp_yyin )) != EOF && c != '\\n'; ++n ) \\\n\t\t\tbuf[n] = (char) c; \\\n\t\tif ( c == '\\n' ) \\\n\t\t\tbuf[n++] = (char) c; \\\n\t\tif ( c == EOF && ferror( lp_yyin ) ) \\\n\t\t\tYY_FATAL_ERROR( \"input in flex scanner failed\" ); \\\n\t\tresult = n; \\\n\t\t} \\\n\telse \\\n\t\t{ \\\n\t\terrno=0; \\\n\t\twhile ( (result = fread(buf, 1, max_size, lp_yyin))==0 && ferror(lp_yyin)) \\\n\t\t\t{ \\\n\t\t\tif( errno != EINTR) \\\n\t\t\t\t{ \\\n\t\t\t\tYY_FATAL_ERROR( \"input in flex scanner failed\" ); \\\n\t\t\t\tbreak; \\\n\t\t\t\t} \\\n\t\t\terrno=0; \\\n\t\t\tclearerr(lp_yyin); \\\n\t\t\t} \\\n\t\t}\\\n\\\n\n#endif\n\n/* No semi-colon after return; correct usage is to write \"lp_yyterminate();\" -\n * we don't want an extra ';' after the \"return\" because that will cause\n * some compilers to complain about unreachable statements.\n */\n#ifndef lp_yyterminate\n#define lp_yyterminate() return YY_NULL\n#endif\n\n/* Number of entries by which start-condition stack grows. */\n#ifndef YY_START_STACK_INCR\n#define YY_START_STACK_INCR 25\n#endif\n\n/* Report a fatal error. */\n#ifndef YY_FATAL_ERROR\n#define YY_FATAL_ERROR(msg) lp_yy_fatal_error( msg , lp_yyscanner)\n#endif\n\n/* end tables serialization structures and prototypes */\n\n/* Default declaration of generated scanner - a define so the user can\n * easily add parameters.\n */\n#ifndef YY_DECL\n#define YY_DECL_IS_OURS 1\n\nextern int lp_yylex \\\n               (YYSTYPE * lp_yylval_param ,lp_yyscan_t lp_yyscanner);\n\n#define YY_DECL int lp_yylex \\\n               (YYSTYPE * lp_yylval_param , lp_yyscan_t lp_yyscanner)\n#endif /* !YY_DECL */\n\n/* Code executed at the beginning of each rule, after lp_yytext and lp_yyleng\n * have been set up.\n */\n#ifndef YY_USER_ACTION\n#define YY_USER_ACTION\n#endif\n\n/* Code executed at the end of each rule. */\n#ifndef YY_BREAK\n#define YY_BREAK break;\n#endif\n\n#define YY_RULE_SETUP \\\n\tif ( lp_yyleng > 0 ) \\\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol = \\\n\t\t\t\t(lp_yytext[lp_yyleng - 1] == '\\n'); \\\n\tYY_USER_ACTION\n\n/** The main scanner function which does all the work.\n */\nYY_DECL\n{\n\tregister lp_yy_state_type lp_yy_current_state;\n\tregister char *lp_yy_cp, *lp_yy_bp;\n\tregister int lp_yy_act;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n    lp_yylval = lp_yylval_param;\n\n\tif ( !lp_yyg->lp_yy_init )\n\t\t{\n\t\tlp_yyg->lp_yy_init = 1;\n\n#ifdef YY_USER_INIT\n\t\tYY_USER_INIT;\n#endif\n\n\t\tif ( ! lp_yyg->lp_yy_start )\n\t\t\tlp_yyg->lp_yy_start = 1;\t/* first start state */\n\n\t\tif ( ! lp_yyin )\n\t\t\tlp_yyin = stdin;\n\n\t\tif ( ! lp_yyout )\n\t\t\tlp_yyout = stdout;\n\n\t\tif ( ! YY_CURRENT_BUFFER ) {\n\t\t\tlp_yyensure_buffer_stack (lp_yyscanner);\n\t\t\tYY_CURRENT_BUFFER_LVALUE =\n\t\t\t\tlp_yy_create_buffer(lp_yyin,YY_BUF_SIZE ,lp_yyscanner);\n\t\t}\n\n\t\tlp_yy_load_buffer_state(lp_yyscanner );\n\t\t}\n\n\twhile ( 1 )\t\t/* loops until end-of-file is reached */\n\t\t{\n\t\tlp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\n\t\t/* Support of lp_yytext. */\n\t\t*lp_yy_cp = lp_yyg->lp_yy_hold_char;\n\n\t\t/* lp_yy_bp points to the position in lp_yy_ch_buf of the start of\n\t\t * the current run.\n\t\t */\n\t\tlp_yy_bp = lp_yy_cp;\n\n\t\tlp_yy_current_state = lp_yyg->lp_yy_start;\n\t\tlp_yy_current_state += YY_AT_BOL();\nlp_yy_match:\n\t\tdo\n\t\t\t{\n\t\t\tregister YY_CHAR lp_yy_c = lp_yy_ec[YY_SC_TO_UI(*lp_yy_cp)];\n\t\t\tif ( lp_yy_accept[lp_yy_current_state] )\n\t\t\t\t{\n\t\t\t\tlp_yyg->lp_yy_last_accepting_state = lp_yy_current_state;\n\t\t\t\tlp_yyg->lp_yy_last_accepting_cpos = lp_yy_cp;\n\t\t\t\t}\n\t\t\twhile ( lp_yy_chk[lp_yy_base[lp_yy_current_state] + lp_yy_c] != lp_yy_current_state )\n\t\t\t\t{\n\t\t\t\tlp_yy_current_state = (int) lp_yy_def[lp_yy_current_state];\n\t\t\t\tif ( lp_yy_current_state >= 144 )\n\t\t\t\t\tlp_yy_c = lp_yy_meta[(unsigned int) lp_yy_c];\n\t\t\t\t}\n\t\t\tlp_yy_current_state = lp_yy_nxt[lp_yy_base[lp_yy_current_state] + (unsigned int) lp_yy_c];\n\t\t\t++lp_yy_cp;\n\t\t\t}\n\t\twhile ( lp_yy_base[lp_yy_current_state] != 388 );\n\nlp_yy_find_action:\n\t\tlp_yy_act = lp_yy_accept[lp_yy_current_state];\n\t\tif ( lp_yy_act == 0 )\n\t\t\t{ /* have to back up */\n\t\t\tlp_yy_cp = lp_yyg->lp_yy_last_accepting_cpos;\n\t\t\tlp_yy_current_state = lp_yyg->lp_yy_last_accepting_state;\n\t\t\tlp_yy_act = lp_yy_accept[lp_yy_current_state];\n\t\t\t}\n\n\t\tYY_DO_BEFORE_ACTION;\n\n\t\tif ( lp_yy_act != YY_END_OF_BUFFER && lp_yy_rule_can_match_eol[lp_yy_act] )\n\t\t\t{\n\t\t\tint lp_yyl;\n\t\t\tfor ( lp_yyl = 0; lp_yyl < lp_yyleng; ++lp_yyl )\n\t\t\t\tif ( lp_yytext[lp_yyl] == '\\n' )\n\t\t\t\t\t   \n    do{ lp_yylineno++;\n        lp_yycolumn=0;\n    }while(0)\n;\n\t\t\t}\n\ndo_action:\t/* This label is used only to access EOF actions. */\n\n\t\tswitch ( lp_yy_act )\n\t{ /* beginning of action switch */\n\t\t\tcase 0: /* must back up */\n\t\t\t/* undo the effects of YY_DO_BEFORE_ACTION */\n\t\t\t*lp_yy_cp = lp_yyg->lp_yy_hold_char;\n\t\t\tlp_yy_cp = lp_yyg->lp_yy_last_accepting_cpos;\n\t\t\tlp_yy_current_state = lp_yyg->lp_yy_last_accepting_state;\n\t\t\tgoto lp_yy_find_action;\n\ncase 1:\nYY_RULE_SETUP\n{\n  BEGIN COMMENT;\n} /* begin skip comment */\n\tYY_BREAK\ncase 2:\nYY_RULE_SETUP\n{\n  BEGIN INITIAL;\n} /* end skip comment */\n\tYY_BREAK\ncase 3:\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 4:\n/* rule 4 can match eol */\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 5:\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 6:\nYY_RULE_SETUP\n{\n  BEGIN LINECOMMENT;\n} /* begin skip LINECOMMENT */\n\tYY_BREAK\ncase 7:\n/* rule 7 can match eol */\nYY_RULE_SETUP\n{\n  BEGIN INITIAL;\n} /* end skip LINECOMMENT */\n\tYY_BREAK\ncase 8:\nYY_RULE_SETUP\n{\n  BEGIN INITIAL;\n} /* end skip LINECOMMENT */\n\tYY_BREAK\ncase 9:\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 10:\n/* rule 10 can match eol */\nYY_RULE_SETUP\n{\n}\n\tYY_BREAK\ncase 11:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return(COMMA);\n}\n\tYY_BREAK\ncase 12:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return(MINIMISE);\n}\n\tYY_BREAK\ncase 13:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return(MAXIMISE);\n}\n\tYY_BREAK\ncase 14:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->f = atof((char *)lp_yytext);\n  return(INTCONS);\n} /* f contains the last float */\n\tYY_BREAK\ncase 15:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->f = atof((char *)lp_yytext);\n  return(CONS);\n} /* f contains the last float */\n\tYY_BREAK\ncase 16:\n/* rule 16 can match eol */\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  char *ptr, c;\n\n  pp->lineno = lp_yylineno;\n  pv->f = DEF_INFINITE;\n  pv->Sign = 0;\n  ptr = (char *)lp_yytext;\n  while (isspace(*ptr)) ptr++;\n  if(*ptr == '-')\n    pv->Sign = 1;\n  if(lp_yyleng > 0) {\n    c = lp_yytext[lp_yyleng - 1];\n    if(!isalnum(c))\n      unput(c);\n  }\n  return(INF);\n} /* f contains the last float */\n\tYY_BREAK\ncase 17:\n/* rule 17 can match eol */\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  int x;\n\n  pp->lineno = lp_yylineno;\n  pv->Sign = 0;\n  for(x = 0; x < lp_yyleng; x++)\n    if(lp_yytext[x] == '-' || lp_yytext[x] == '+')\n      pv->Sign = (pv->Sign == (lp_yytext[x] == '+'));\n  return (TOK_SIGN);\n  /* Sign is TRUE if the sign-string\n     represents a '-'. Otherwise Sign\n     is FALSE */\n}\n\tYY_BREAK\ncase 18:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_int_decl = 1;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_INT);\n}\n\tYY_BREAK\ncase 19:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_int_decl = 2;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_BIN);\n}\n\tYY_BREAK\ncase 20:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_sec_decl = TRUE;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_SEC);\n}\n\tYY_BREAK\ncase 21:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if(!pv->Within_sos_decl)\n    pv->SOStype0 = (short)atoi(((char *)lp_yytext) + 3);\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl))\n    pv->Within_sos_decl = TRUE;\n  return(SEC_SOS);\n}\n\tYY_BREAK\ncase 22:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)lp_yytext);\n  pv->Last_var[strlen(pv->Last_var) - 2] = 0;\n  return(SOSDESCR);\n}\n\tYY_BREAK\ncase 23:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_free_decl = TRUE;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_FREE);\n}\n\tYY_BREAK\ncase 24:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  char *ptr;\n\n  pp->lineno = lp_yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)lp_yytext);\n  ptr = pv->Last_var + strlen(pv->Last_var);\n  ptr[-1] = ' ';\n  while ((--ptr >= pv->Last_var) && (isspace(*ptr)))\n    *ptr = 0;\n  return(VARIABLECOLON);\n}\n\tYY_BREAK\ncase 25:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)lp_yytext);\n  return(VAR);\n}\n\tYY_BREAK\ncase 26:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return (COLON);\n}\n\tYY_BREAK\ncase 27:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  return(AR_M_OP);\n}\n\tYY_BREAK\ncase 28:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->OP = *lp_yytext;\n  return(RE_OPEQ);\n}\n\tYY_BREAK\ncase 29:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->OP = *lp_yytext;\n  return(RE_OPLE);\n}\n\tYY_BREAK\ncase 30:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->OP = *lp_yytext;\n  return(RE_OPGE);\n}\n\tYY_BREAK\ncase 31:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = lp_yylineno;\n  pv->Within_int_decl = pv->Within_sec_decl = pv->Within_sos_decl = pv->Within_free_decl = FALSE;\n  check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, (int) pv->Within_sos_decl, (int) pv->Within_free_decl);\n  return(END_C);\n}\n\tYY_BREAK\ncase 32:\nYY_RULE_SETUP\n{\n  parse_parm *pp = PARM;\n\n  pp->lineno = lp_yylineno;\n  report(NULL, CRITICAL, \"LEX ERROR : %s lineno %d\\n\", lp_yytext, lp_yylineno);\n  return(UNDEFINED);\n}\n\tYY_BREAK\ncase 33:\nYY_RULE_SETUP\nECHO;\n\tYY_BREAK\ncase YY_STATE_EOF(INITIAL):\ncase YY_STATE_EOF(COMMENT):\ncase YY_STATE_EOF(LINECOMMENT):\n\tlp_yyterminate();\n\n\tcase YY_END_OF_BUFFER:\n\t\t{\n\t\t/* Amount of text matched not including the EOB char. */\n\t\tint lp_yy_amount_of_matched_text = (int) (lp_yy_cp - lp_yyg->lp_yytext_ptr) - 1;\n\n\t\t/* Undo the effects of YY_DO_BEFORE_ACTION. */\n\t\t*lp_yy_cp = lp_yyg->lp_yy_hold_char;\n\t\tYY_RESTORE_YY_MORE_OFFSET\n\n\t\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_buffer_status == YY_BUFFER_NEW )\n\t\t\t{\n\t\t\t/* We're scanning a new file or input source.  It's\n\t\t\t * possible that this happened because the user\n\t\t\t * just pointed lp_yyin at a new source and called\n\t\t\t * lp_yylex().  If so, then we have to assure\n\t\t\t * consistency between YY_CURRENT_BUFFER and our\n\t\t\t * globals.  Here is the right place to do so, because\n\t\t\t * this is the first action (other than possibly a\n\t\t\t * back-up) that will match for the new input source.\n\t\t\t */\n\t\t\tlp_yyg->lp_yy_n_chars = YY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars;\n\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_input_file = lp_yyin;\n\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buffer_status = YY_BUFFER_NORMAL;\n\t\t\t}\n\n\t\t/* Note that here we test for lp_yy_c_buf_p \"<=\" to the position\n\t\t * of the first EOB in the buffer, since lp_yy_c_buf_p will\n\t\t * already have been incremented past the NUL character\n\t\t * (since all states make transitions on EOB to the\n\t\t * end-of-buffer state).  Contrast this with the test\n\t\t * in input().\n\t\t */\n\t\tif ( lp_yyg->lp_yy_c_buf_p <= &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars] )\n\t\t\t{ /* This was really a NUL. */\n\t\t\tlp_yy_state_type lp_yy_next_state;\n\n\t\t\tlp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yytext_ptr + lp_yy_amount_of_matched_text;\n\n\t\t\tlp_yy_current_state = lp_yy_get_previous_state( lp_yyscanner );\n\n\t\t\t/* Okay, we're now positioned to make the NUL\n\t\t\t * transition.  We couldn't have\n\t\t\t * lp_yy_get_previous_state() go ahead and do it\n\t\t\t * for us because it doesn't know how to deal\n\t\t\t * with the possibility of jamming (and we don't\n\t\t\t * want to build jamming into it because then it\n\t\t\t * will run more slowly).\n\t\t\t */\n\n\t\t\tlp_yy_next_state = lp_yy_try_NUL_trans( lp_yy_current_state , lp_yyscanner);\n\n\t\t\tlp_yy_bp = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ;\n\n\t\t\tif ( lp_yy_next_state )\n\t\t\t\t{\n\t\t\t\t/* Consume the NUL. */\n\t\t\t\tlp_yy_cp = ++lp_yyg->lp_yy_c_buf_p;\n\t\t\t\tlp_yy_current_state = lp_yy_next_state;\n\t\t\t\tgoto lp_yy_match;\n\t\t\t\t}\n\n\t\t\telse\n\t\t\t\t{\n\t\t\t\tlp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\t\t\t\tgoto lp_yy_find_action;\n\t\t\t\t}\n\t\t\t}\n\n\t\telse switch ( lp_yy_get_next_buffer( lp_yyscanner ) )\n\t\t\t{\n\t\t\tcase EOB_ACT_END_OF_FILE:\n\t\t\t\t{\n\t\t\t\tlp_yyg->lp_yy_did_buffer_switch_on_eof = 0;\n\n\t\t\t\tif ( lp_yywrap(lp_yyscanner ) )\n\t\t\t\t\t{\n\t\t\t\t\t/* Note: because we've taken care in\n\t\t\t\t\t * lp_yy_get_next_buffer() to have set up\n\t\t\t\t\t * lp_yytext, we can now set up\n\t\t\t\t\t * lp_yy_c_buf_p so that if some total\n\t\t\t\t\t * hoser (like flex itself) wants to\n\t\t\t\t\t * call the scanner after we return the\n\t\t\t\t\t * YY_NULL, it'll still work - another\n\t\t\t\t\t * YY_NULL will get returned.\n\t\t\t\t\t */\n\t\t\t\t\tlp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ;\n\n\t\t\t\t\tlp_yy_act = YY_STATE_EOF(YY_START);\n\t\t\t\t\tgoto do_action;\n\t\t\t\t\t}\n\n\t\t\t\telse\n\t\t\t\t\t{\n\t\t\t\t\tif ( ! lp_yyg->lp_yy_did_buffer_switch_on_eof )\n\t\t\t\t\t\tYY_NEW_FILE;\n\t\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t\t}\n\n\t\t\tcase EOB_ACT_CONTINUE_SCAN:\n\t\t\t\tlp_yyg->lp_yy_c_buf_p =\n\t\t\t\t\tlp_yyg->lp_yytext_ptr + lp_yy_amount_of_matched_text;\n\n\t\t\t\tlp_yy_current_state = lp_yy_get_previous_state( lp_yyscanner );\n\n\t\t\t\tlp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\t\t\t\tlp_yy_bp = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ;\n\t\t\t\tgoto lp_yy_match;\n\n\t\t\tcase EOB_ACT_LAST_MATCH:\n\t\t\t\tlp_yyg->lp_yy_c_buf_p =\n\t\t\t\t&YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars];\n\n\t\t\t\tlp_yy_current_state = lp_yy_get_previous_state( lp_yyscanner );\n\n\t\t\t\tlp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\t\t\t\tlp_yy_bp = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ;\n\t\t\t\tgoto lp_yy_find_action;\n\t\t\t}\n\t\tbreak;\n\t\t}\n\n\tdefault:\n\t\tYY_FATAL_ERROR(\n\t\t\t\"fatal flex scanner internal error--no action found\" );\n\t} /* end of action switch */\n\t\t} /* end of scanning one token */\n} /* end of lp_yylex */\n\n/* lp_yy_get_next_buffer - try to read in a new buffer\n *\n * Returns a code representing an action:\n *\tEOB_ACT_LAST_MATCH -\n *\tEOB_ACT_CONTINUE_SCAN - continue scanning from current position\n *\tEOB_ACT_END_OF_FILE - end of file\n */\nstatic int lp_yy_get_next_buffer (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tregister char *dest = YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf;\n\tregister char *source = lp_yyg->lp_yytext_ptr;\n\tregister int number_to_move, i;\n\tint ret_val;\n\n\tif ( lp_yyg->lp_yy_c_buf_p > &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars + 1] )\n\t\tYY_FATAL_ERROR(\n\t\t\"fatal flex scanner internal error--end of buffer missed\" );\n\n\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_fill_buffer == 0 )\n\t\t{ /* Don't try to fill the buffer, so this is an EOF. */\n\t\tif ( lp_yyg->lp_yy_c_buf_p - lp_yyg->lp_yytext_ptr - YY_MORE_ADJ == 1 )\n\t\t\t{\n\t\t\t/* We matched a single character, the EOB, so\n\t\t\t * treat this as a final EOF.\n\t\t\t */\n\t\t\treturn EOB_ACT_END_OF_FILE;\n\t\t\t}\n\n\t\telse\n\t\t\t{\n\t\t\t/* We matched some text prior to the EOB, first\n\t\t\t * process it.\n\t\t\t */\n\t\t\treturn EOB_ACT_LAST_MATCH;\n\t\t\t}\n\t\t}\n\n\t/* Try to read more data. */\n\n\t/* First move last chars to start of buffer. */\n\tnumber_to_move = (int) (lp_yyg->lp_yy_c_buf_p - lp_yyg->lp_yytext_ptr) - 1;\n\n\tfor ( i = 0; i < number_to_move; ++i )\n\t\t*(dest++) = *(source++);\n\n\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_buffer_status == YY_BUFFER_EOF_PENDING )\n\t\t/* don't do the read, it's not guaranteed to return an EOF,\n\t\t * just force an EOF\n\t\t */\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars = lp_yyg->lp_yy_n_chars = 0;\n\n\telse\n\t\t{\n\t\t\tint num_to_read =\n\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size - number_to_move - 1;\n\n\t\twhile ( num_to_read <= 0 )\n\t\t\t{ /* Not enough room in the buffer - grow it. */\n\n\t\t\t/* just a shorter name for the current buffer */\n\t\t\tYY_BUFFER_STATE b = YY_CURRENT_BUFFER;\n\n\t\t\tint lp_yy_c_buf_p_offset =\n\t\t\t\t(int) (lp_yyg->lp_yy_c_buf_p - b->lp_yy_ch_buf);\n\n\t\t\tif ( b->lp_yy_is_our_buffer )\n\t\t\t\t{\n\t\t\t\tint new_size = b->lp_yy_buf_size * 2;\n\n\t\t\t\tif ( new_size <= 0 )\n\t\t\t\t\tb->lp_yy_buf_size += b->lp_yy_buf_size / 8;\n\t\t\t\telse\n\t\t\t\t\tb->lp_yy_buf_size *= 2;\n\n\t\t\t\tb->lp_yy_ch_buf = (char *)\n\t\t\t\t\t/* Include room in for 2 EOB chars. */\n\t\t\t\t\tlp_yyrealloc((void *) b->lp_yy_ch_buf,b->lp_yy_buf_size + 2 ,lp_yyscanner );\n\t\t\t\t}\n\t\t\telse\n\t\t\t\t/* Can't grow it, we don't own it. */\n\t\t\t\tb->lp_yy_ch_buf = 0;\n\n\t\t\tif ( ! b->lp_yy_ch_buf )\n\t\t\t\tYY_FATAL_ERROR(\n\t\t\t\t\"fatal error - scanner input buffer overflow\" );\n\n\t\t\tlp_yyg->lp_yy_c_buf_p = &b->lp_yy_ch_buf[lp_yy_c_buf_p_offset];\n\n\t\t\tnum_to_read = YY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size -\n\t\t\t\t\t\tnumber_to_move - 1;\n\n\t\t\t}\n\n\t\tif ( num_to_read > YY_READ_BUF_SIZE )\n\t\t\tnum_to_read = YY_READ_BUF_SIZE;\n\n\t\t/* Read in more data. */\n\t\tYY_INPUT( (&YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[number_to_move]),\n\t\t\tlp_yyg->lp_yy_n_chars, (size_t) num_to_read );\n\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars = lp_yyg->lp_yy_n_chars;\n\t\t}\n\n\tif ( lp_yyg->lp_yy_n_chars == 0 )\n\t\t{\n\t\tif ( number_to_move == YY_MORE_ADJ )\n\t\t\t{\n\t\t\tret_val = EOB_ACT_END_OF_FILE;\n\t\t\tlp_yyrestart(lp_yyin  ,lp_yyscanner);\n\t\t\t}\n\n\t\telse\n\t\t\t{\n\t\t\tret_val = EOB_ACT_LAST_MATCH;\n\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buffer_status =\n\t\t\t\tYY_BUFFER_EOF_PENDING;\n\t\t\t}\n\t\t}\n\n\telse\n\t\tret_val = EOB_ACT_CONTINUE_SCAN;\n\n\tif ((lp_yy_size_t) (lp_yyg->lp_yy_n_chars + number_to_move) > YY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size) {\n\t\t/* Extend the array by 50%, plus the number we really need. */\n\t\tlp_yy_size_t new_size = lp_yyg->lp_yy_n_chars + number_to_move + (lp_yyg->lp_yy_n_chars >> 1);\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf = (char *) lp_yyrealloc((void *) YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf,new_size ,lp_yyscanner );\n\t\tif ( ! YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf )\n\t\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_get_next_buffer()\" );\n\t}\n\n\tlp_yyg->lp_yy_n_chars += number_to_move;\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars] = YY_END_OF_BUFFER_CHAR;\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars + 1] = YY_END_OF_BUFFER_CHAR;\n\n\tlp_yyg->lp_yytext_ptr = &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[0];\n\n\treturn ret_val;\n}\n\n/* lp_yy_get_previous_state - get the state just before the EOB char was reached */\n\n    static lp_yy_state_type lp_yy_get_previous_state (lp_yyscan_t lp_yyscanner)\n{\n\tregister lp_yy_state_type lp_yy_current_state;\n\tregister char *lp_yy_cp;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tlp_yy_current_state = lp_yyg->lp_yy_start;\n\tlp_yy_current_state += YY_AT_BOL();\n\n\tfor ( lp_yy_cp = lp_yyg->lp_yytext_ptr + YY_MORE_ADJ; lp_yy_cp < lp_yyg->lp_yy_c_buf_p; ++lp_yy_cp )\n\t\t{\n\t\tregister YY_CHAR lp_yy_c = (*lp_yy_cp ? lp_yy_ec[YY_SC_TO_UI(*lp_yy_cp)] : 1);\n\t\tif ( lp_yy_accept[lp_yy_current_state] )\n\t\t\t{\n\t\t\tlp_yyg->lp_yy_last_accepting_state = lp_yy_current_state;\n\t\t\tlp_yyg->lp_yy_last_accepting_cpos = lp_yy_cp;\n\t\t\t}\n\t\twhile ( lp_yy_chk[lp_yy_base[lp_yy_current_state] + lp_yy_c] != lp_yy_current_state )\n\t\t\t{\n\t\t\tlp_yy_current_state = (int) lp_yy_def[lp_yy_current_state];\n\t\t\tif ( lp_yy_current_state >= 144 )\n\t\t\t\tlp_yy_c = lp_yy_meta[(unsigned int) lp_yy_c];\n\t\t\t}\n\t\tlp_yy_current_state = lp_yy_nxt[lp_yy_base[lp_yy_current_state] + (unsigned int) lp_yy_c];\n\t\t}\n\n\treturn lp_yy_current_state;\n}\n\n/* lp_yy_try_NUL_trans - try to make a transition on the NUL character\n *\n * synopsis\n *\tnext_state = lp_yy_try_NUL_trans( current_state );\n */\n    static lp_yy_state_type lp_yy_try_NUL_trans  (lp_yy_state_type lp_yy_current_state , lp_yyscan_t lp_yyscanner)\n{\n\tregister int lp_yy_is_jam;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner; /* This var may be unused depending upon options. */\n\tregister char *lp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\n\tregister YY_CHAR lp_yy_c = 1;\n\tif ( lp_yy_accept[lp_yy_current_state] )\n\t\t{\n\t\tlp_yyg->lp_yy_last_accepting_state = lp_yy_current_state;\n\t\tlp_yyg->lp_yy_last_accepting_cpos = lp_yy_cp;\n\t\t}\n\twhile ( lp_yy_chk[lp_yy_base[lp_yy_current_state] + lp_yy_c] != lp_yy_current_state )\n\t\t{\n\t\tlp_yy_current_state = (int) lp_yy_def[lp_yy_current_state];\n\t\tif ( lp_yy_current_state >= 144 )\n\t\t\tlp_yy_c = lp_yy_meta[(unsigned int) lp_yy_c];\n\t\t}\n\tlp_yy_current_state = lp_yy_nxt[lp_yy_base[lp_yy_current_state] + (unsigned int) lp_yy_c];\n\tlp_yy_is_jam = (lp_yy_current_state == 143);\n\n\treturn lp_yy_is_jam ? 0 : lp_yy_current_state;\n}\n\n    static void lp_yyunput (int c, register char * lp_yy_bp , lp_yyscan_t lp_yyscanner)\n{\n\tregister char *lp_yy_cp;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n    lp_yy_cp = lp_yyg->lp_yy_c_buf_p;\n\n\t/* undo effects of setting up lp_yytext */\n\t*lp_yy_cp = lp_yyg->lp_yy_hold_char;\n\n\tif ( lp_yy_cp < YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf + 2 )\n\t\t{ /* need to shift things up to make room */\n\t\t/* +2 for EOB chars. */\n\t\tregister int number_to_move = lp_yyg->lp_yy_n_chars + 2;\n\t\tregister char *dest = &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[\n\t\t\t\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size + 2];\n\t\tregister char *source =\n\t\t\t\t&YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[number_to_move];\n\n\t\twhile ( source > YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf )\n\t\t\t*--dest = *--source;\n\n\t\tlp_yy_cp += (int) (dest - source);\n\t\tlp_yy_bp += (int) (dest - source);\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars =\n\t\t\tlp_yyg->lp_yy_n_chars = YY_CURRENT_BUFFER_LVALUE->lp_yy_buf_size;\n\n\t\tif ( lp_yy_cp < YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf + 2 )\n\t\t\tYY_FATAL_ERROR( \"flex scanner push-back overflow\" );\n\t\t}\n\n\t*--lp_yy_cp = (char) c;\n\n    if ( c == '\\n' ){\n        --lp_yylineno;\n    }\n\n\tlp_yyg->lp_yytext_ptr = lp_yy_bp;\n\tlp_yyg->lp_yy_hold_char = *lp_yy_cp;\n\tlp_yyg->lp_yy_c_buf_p = lp_yy_cp;\n}\n\n#ifndef YY_NO_INPUT\n#ifdef __cplusplus\n    static int lp_yyinput (lp_yyscan_t lp_yyscanner)\n#else\n    static int input  (lp_yyscan_t lp_yyscanner)\n#endif\n\n{\n\tint c;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\t*lp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yy_hold_char;\n\n\tif ( *lp_yyg->lp_yy_c_buf_p == YY_END_OF_BUFFER_CHAR )\n\t\t{\n\t\t/* lp_yy_c_buf_p now points to the character we want to return.\n\t\t * If this occurs *before* the EOB characters, then it's a\n\t\t * valid NUL; if not, then we've hit the end of the buffer.\n\t\t */\n\t\tif ( lp_yyg->lp_yy_c_buf_p < &YY_CURRENT_BUFFER_LVALUE->lp_yy_ch_buf[lp_yyg->lp_yy_n_chars] )\n\t\t\t/* This was really a NUL. */\n\t\t\t*lp_yyg->lp_yy_c_buf_p = '\\0';\n\n\t\telse\n\t\t\t{ /* need more input */\n\t\t\tint offset = lp_yyg->lp_yy_c_buf_p - lp_yyg->lp_yytext_ptr;\n\t\t\t++lp_yyg->lp_yy_c_buf_p;\n\n\t\t\tswitch ( lp_yy_get_next_buffer( lp_yyscanner ) )\n\t\t\t\t{\n\t\t\t\tcase EOB_ACT_LAST_MATCH:\n\t\t\t\t\t/* This happens because lp_yy_g_n_b()\n\t\t\t\t\t * sees that we've accumulated a\n\t\t\t\t\t * token and flags that we need to\n\t\t\t\t\t * try matching the token before\n\t\t\t\t\t * proceeding.  But for input(),\n\t\t\t\t\t * there's no matching to consider.\n\t\t\t\t\t * So convert the EOB_ACT_LAST_MATCH\n\t\t\t\t\t * to EOB_ACT_END_OF_FILE.\n\t\t\t\t\t */\n\n\t\t\t\t\t/* Reset buffer status. */\n\t\t\t\t\tlp_yyrestart(lp_yyin ,lp_yyscanner);\n\n\t\t\t\t\t/*FALLTHROUGH*/\n\n\t\t\t\tcase EOB_ACT_END_OF_FILE:\n\t\t\t\t\t{\n\t\t\t\t\tif ( lp_yywrap(lp_yyscanner ) )\n\t\t\t\t\t\treturn EOF;\n\n\t\t\t\t\tif ( ! lp_yyg->lp_yy_did_buffer_switch_on_eof )\n\t\t\t\t\t\tYY_NEW_FILE;\n#ifdef __cplusplus\n\t\t\t\t\treturn lp_yyinput(lp_yyscanner);\n#else\n\t\t\t\t\treturn input(lp_yyscanner);\n#endif\n\t\t\t\t\t}\n\n\t\t\t\tcase EOB_ACT_CONTINUE_SCAN:\n\t\t\t\t\tlp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yytext_ptr + offset;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\tc = *(unsigned char *) lp_yyg->lp_yy_c_buf_p;\t/* cast for 8-bit char's */\n\t*lp_yyg->lp_yy_c_buf_p = '\\0';\t/* preserve lp_yytext */\n\tlp_yyg->lp_yy_hold_char = *++lp_yyg->lp_yy_c_buf_p;\n\n\tYY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol = (c == '\\n');\n\tif ( YY_CURRENT_BUFFER_LVALUE->lp_yy_at_bol )\n\t\t   \n    do{ lp_yylineno++;\n        lp_yycolumn=0;\n    }while(0)\n;\n\n\treturn c;\n}\n#endif\t/* ifndef YY_NO_INPUT */\n\n/** Immediately switch to a different input stream.\n * @param input_file A readable stream.\n * @param lp_yyscanner The scanner object.\n * @note This function does not reset the start condition to @c INITIAL .\n */\n    void lp_yyrestart  (FILE * input_file , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tif ( ! YY_CURRENT_BUFFER ){\n        lp_yyensure_buffer_stack (lp_yyscanner);\n\t\tYY_CURRENT_BUFFER_LVALUE =\n            lp_yy_create_buffer(lp_yyin,YY_BUF_SIZE ,lp_yyscanner);\n\t}\n\n\tlp_yy_init_buffer(YY_CURRENT_BUFFER,input_file ,lp_yyscanner);\n\tlp_yy_load_buffer_state(lp_yyscanner );\n}\n\n/** Switch to a different input buffer.\n * @param new_buffer The new input buffer.\n * @param lp_yyscanner The scanner object.\n */\n    void lp_yy_switch_to_buffer  (YY_BUFFER_STATE  new_buffer , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\t/* TODO. We should be able to replace this entire function body\n\t * with\n\t *\t\tlp_yypop_buffer_state();\n\t *\t\tlp_yypush_buffer_state(new_buffer);\n     */\n\tlp_yyensure_buffer_stack (lp_yyscanner);\n\tif ( YY_CURRENT_BUFFER == new_buffer )\n\t\treturn;\n\n\tif ( YY_CURRENT_BUFFER )\n\t\t{\n\t\t/* Flush out information for old buffer. */\n\t\t*lp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yy_hold_char;\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buf_pos = lp_yyg->lp_yy_c_buf_p;\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars = lp_yyg->lp_yy_n_chars;\n\t\t}\n\n\tYY_CURRENT_BUFFER_LVALUE = new_buffer;\n\tlp_yy_load_buffer_state(lp_yyscanner );\n\n\t/* We don't actually know whether we did this switch during\n\t * EOF (lp_yywrap()) processing, but the only time this flag\n\t * is looked at is after lp_yywrap() is called, so it's safe\n\t * to go ahead and always set it.\n\t */\n\tlp_yyg->lp_yy_did_buffer_switch_on_eof = 1;\n}\n\nstatic void lp_yy_load_buffer_state  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tlp_yyg->lp_yy_n_chars = YY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars;\n\tlp_yyg->lp_yytext_ptr = lp_yyg->lp_yy_c_buf_p = YY_CURRENT_BUFFER_LVALUE->lp_yy_buf_pos;\n\tlp_yyin = YY_CURRENT_BUFFER_LVALUE->lp_yy_input_file;\n\tlp_yyg->lp_yy_hold_char = *lp_yyg->lp_yy_c_buf_p;\n}\n\n/** Allocate and initialize an input buffer state.\n * @param file A readable stream.\n * @param size The character buffer size in bytes. When in doubt, use @c YY_BUF_SIZE.\n * @param lp_yyscanner The scanner object.\n * @return the allocated buffer state.\n */\n    YY_BUFFER_STATE lp_yy_create_buffer  (FILE * file, int  size , lp_yyscan_t lp_yyscanner)\n{\n\tYY_BUFFER_STATE b;\n    \n\tb = (YY_BUFFER_STATE) lp_yyalloc(sizeof( struct lp_yy_buffer_state ) ,lp_yyscanner );\n\tif ( ! b )\n\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_create_buffer()\" );\n\n\tb->lp_yy_buf_size = size;\n\n\t/* lp_yy_ch_buf has to be 2 characters longer than the size given because\n\t * we need to put in 2 end-of-buffer characters.\n\t */\n\tb->lp_yy_ch_buf = (char *) lp_yyalloc(b->lp_yy_buf_size + 2 ,lp_yyscanner );\n\tif ( ! b->lp_yy_ch_buf )\n\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_create_buffer()\" );\n\n\tb->lp_yy_is_our_buffer = 1;\n\n\tlp_yy_init_buffer(b,file ,lp_yyscanner);\n\n\treturn b;\n}\n\n/** Destroy the buffer.\n * @param b a buffer created with lp_yy_create_buffer()\n * @param lp_yyscanner The scanner object.\n */\n    void lp_yy_delete_buffer (YY_BUFFER_STATE  b , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tif ( ! b )\n\t\treturn;\n\n\tif ( b == YY_CURRENT_BUFFER ) /* Not sure if we should pop here. */\n\t\tYY_CURRENT_BUFFER_LVALUE = (YY_BUFFER_STATE) 0;\n\n\tif ( b->lp_yy_is_our_buffer )\n\t\tlp_yyfree((void *) b->lp_yy_ch_buf ,lp_yyscanner );\n\n\tlp_yyfree((void *) b ,lp_yyscanner );\n}\n\n#ifndef __cplusplus\nextern int isatty (int );\n#endif /* __cplusplus */\n    \n/* Initializes or reinitializes a buffer.\n * This function is sometimes called more than once on the same buffer,\n * such as during a lp_yyrestart() or at EOF.\n */\n    static void lp_yy_init_buffer  (YY_BUFFER_STATE  b, FILE * file , lp_yyscan_t lp_yyscanner)\n\n{\n\tint oerrno = errno;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tlp_yy_flush_buffer(b ,lp_yyscanner);\n\n\tb->lp_yy_input_file = file;\n\tb->lp_yy_fill_buffer = 1;\n\n    /* If b is the current buffer, then lp_yy_init_buffer was _probably_\n     * called from lp_yyrestart() or through lp_yy_get_next_buffer.\n     * In that case, we don't want to reset the lineno or column.\n     */\n    if (b != YY_CURRENT_BUFFER){\n        b->lp_yy_bs_lineno = 1;\n        b->lp_yy_bs_column = 0;\n    }\n\n        b->lp_yy_is_interactive = file ? (isatty( fileno(file) ) > 0) : 0;\n    \n\terrno = oerrno;\n}\n\n/** Discard all buffered characters. On the next scan, YY_INPUT will be called.\n * @param b the buffer state to be flushed, usually @c YY_CURRENT_BUFFER.\n * @param lp_yyscanner The scanner object.\n */\n    void lp_yy_flush_buffer (YY_BUFFER_STATE  b , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tif ( ! b )\n\t\treturn;\n\n\tb->lp_yy_n_chars = 0;\n\n\t/* We always need two end-of-buffer characters.  The first causes\n\t * a transition to the end-of-buffer state.  The second causes\n\t * a jam in that state.\n\t */\n\tb->lp_yy_ch_buf[0] = YY_END_OF_BUFFER_CHAR;\n\tb->lp_yy_ch_buf[1] = YY_END_OF_BUFFER_CHAR;\n\n\tb->lp_yy_buf_pos = &b->lp_yy_ch_buf[0];\n\n\tb->lp_yy_at_bol = 1;\n\tb->lp_yy_buffer_status = YY_BUFFER_NEW;\n\n\tif ( b == YY_CURRENT_BUFFER )\n\t\tlp_yy_load_buffer_state(lp_yyscanner );\n}\n\n/** Pushes the new state onto the stack. The new state becomes\n *  the current state. This function will allocate the stack\n *  if necessary.\n *  @param new_buffer The new state.\n *  @param lp_yyscanner The scanner object.\n */\nvoid lp_yypush_buffer_state (YY_BUFFER_STATE new_buffer , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tif (new_buffer == NULL)\n\t\treturn;\n\n\tlp_yyensure_buffer_stack(lp_yyscanner);\n\n\t/* This block is copied from lp_yy_switch_to_buffer. */\n\tif ( YY_CURRENT_BUFFER )\n\t\t{\n\t\t/* Flush out information for old buffer. */\n\t\t*lp_yyg->lp_yy_c_buf_p = lp_yyg->lp_yy_hold_char;\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_buf_pos = lp_yyg->lp_yy_c_buf_p;\n\t\tYY_CURRENT_BUFFER_LVALUE->lp_yy_n_chars = lp_yyg->lp_yy_n_chars;\n\t\t}\n\n\t/* Only push if top exists. Otherwise, replace top. */\n\tif (YY_CURRENT_BUFFER)\n\t\tlp_yyg->lp_yy_buffer_stack_top++;\n\tYY_CURRENT_BUFFER_LVALUE = new_buffer;\n\n\t/* copied from lp_yy_switch_to_buffer. */\n\tlp_yy_load_buffer_state(lp_yyscanner );\n\tlp_yyg->lp_yy_did_buffer_switch_on_eof = 1;\n}\n\n/** Removes and deletes the top of the stack, if present.\n *  The next element becomes the new top.\n *  @param lp_yyscanner The scanner object.\n */\nvoid lp_yypop_buffer_state (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\tif (!YY_CURRENT_BUFFER)\n\t\treturn;\n\n\tlp_yy_delete_buffer(YY_CURRENT_BUFFER ,lp_yyscanner);\n\tYY_CURRENT_BUFFER_LVALUE = NULL;\n\tif (lp_yyg->lp_yy_buffer_stack_top > 0)\n\t\t--lp_yyg->lp_yy_buffer_stack_top;\n\n\tif (YY_CURRENT_BUFFER) {\n\t\tlp_yy_load_buffer_state(lp_yyscanner );\n\t\tlp_yyg->lp_yy_did_buffer_switch_on_eof = 1;\n\t}\n}\n\n/* Allocates the stack if it does not exist.\n *  Guarantees space for at least one push.\n */\nstatic void lp_yyensure_buffer_stack (lp_yyscan_t lp_yyscanner)\n{\n\tint num_to_alloc;\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n\tif (!lp_yyg->lp_yy_buffer_stack) {\n\n\t\t/* First allocation is just for 2 elements, since we don't know if this\n\t\t * scanner will even need a stack. We use 2 instead of 1 to avoid an\n\t\t * immediate realloc on the next call.\n         */\n\t\tnum_to_alloc = 1;\n\t\tlp_yyg->lp_yy_buffer_stack = (struct lp_yy_buffer_state**)lp_yyalloc\n\t\t\t\t\t\t\t\t(num_to_alloc * sizeof(struct lp_yy_buffer_state*)\n\t\t\t\t\t\t\t\t, lp_yyscanner);\n\t\tif ( ! lp_yyg->lp_yy_buffer_stack )\n\t\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yyensure_buffer_stack()\" );\n\t\t\t\t\t\t\t\t  \n\t\tmemset(lp_yyg->lp_yy_buffer_stack, 0, num_to_alloc * sizeof(struct lp_yy_buffer_state*));\n\t\t\t\t\n\t\tlp_yyg->lp_yy_buffer_stack_max = num_to_alloc;\n\t\tlp_yyg->lp_yy_buffer_stack_top = 0;\n\t\treturn;\n\t}\n\n\tif (lp_yyg->lp_yy_buffer_stack_top >= (lp_yyg->lp_yy_buffer_stack_max) - 1){\n\n\t\t/* Increase the buffer to prepare for a possible push. */\n\t\tint grow_size = 8 /* arbitrary grow size */;\n\n\t\tnum_to_alloc = lp_yyg->lp_yy_buffer_stack_max + grow_size;\n\t\tlp_yyg->lp_yy_buffer_stack = (struct lp_yy_buffer_state**)lp_yyrealloc\n\t\t\t\t\t\t\t\t(lp_yyg->lp_yy_buffer_stack,\n\t\t\t\t\t\t\t\tnum_to_alloc * sizeof(struct lp_yy_buffer_state*)\n\t\t\t\t\t\t\t\t, lp_yyscanner);\n\t\tif ( ! lp_yyg->lp_yy_buffer_stack )\n\t\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yyensure_buffer_stack()\" );\n\n\t\t/* zero only the new slots.*/\n\t\tmemset(lp_yyg->lp_yy_buffer_stack + lp_yyg->lp_yy_buffer_stack_max, 0, grow_size * sizeof(struct lp_yy_buffer_state*));\n\t\tlp_yyg->lp_yy_buffer_stack_max = num_to_alloc;\n\t}\n}\n\n/** Setup the input buffer state to scan directly from a user-specified character buffer.\n * @param base the character buffer\n * @param size the size in bytes of the character buffer\n * @param lp_yyscanner The scanner object.\n * @return the newly allocated buffer state object. \n */\nYY_BUFFER_STATE lp_yy_scan_buffer  (char * base, lp_yy_size_t  size , lp_yyscan_t lp_yyscanner)\n{\n\tYY_BUFFER_STATE b;\n    \n\tif ( size < 2 ||\n\t     base[size-2] != YY_END_OF_BUFFER_CHAR ||\n\t     base[size-1] != YY_END_OF_BUFFER_CHAR )\n\t\t/* They forgot to leave room for the EOB's. */\n\t\treturn 0;\n\n\tb = (YY_BUFFER_STATE) lp_yyalloc(sizeof( struct lp_yy_buffer_state ) ,lp_yyscanner );\n\tif ( ! b )\n\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_scan_buffer()\" );\n\n\tb->lp_yy_buf_size = size - 2;\t/* \"- 2\" to take care of EOB's */\n\tb->lp_yy_buf_pos = b->lp_yy_ch_buf = base;\n\tb->lp_yy_is_our_buffer = 0;\n\tb->lp_yy_input_file = 0;\n\tb->lp_yy_n_chars = b->lp_yy_buf_size;\n\tb->lp_yy_is_interactive = 0;\n\tb->lp_yy_at_bol = 1;\n\tb->lp_yy_fill_buffer = 0;\n\tb->lp_yy_buffer_status = YY_BUFFER_NEW;\n\n\tlp_yy_switch_to_buffer(b ,lp_yyscanner );\n\n\treturn b;\n}\n\n/** Setup the input buffer state to scan a string. The next call to lp_yylex() will\n * scan from a @e copy of @a str.\n * @param lp_yystr a NUL-terminated string to scan\n * @param lp_yyscanner The scanner object.\n * @return the newly allocated buffer state object.\n * @note If you want to scan bytes that may contain NUL values, then use\n *       lp_yy_scan_bytes() instead.\n */\nYY_BUFFER_STATE lp_yy_scan_string (lp_yyconst char * lp_yystr , lp_yyscan_t lp_yyscanner)\n{\n    \n\treturn lp_yy_scan_bytes(lp_yystr,strlen(lp_yystr) ,lp_yyscanner);\n}\n\n/** Setup the input buffer state to scan the given bytes. The next call to lp_yylex() will\n * scan from a @e copy of @a bytes.\n * @param bytes the byte buffer to scan\n * @param len the number of bytes in the buffer pointed to by @a bytes.\n * @param lp_yyscanner The scanner object.\n * @return the newly allocated buffer state object.\n */\nYY_BUFFER_STATE lp_yy_scan_bytes  (lp_yyconst char * lp_yybytes, int  _lp_yybytes_len , lp_yyscan_t lp_yyscanner)\n{\n\tYY_BUFFER_STATE b;\n\tchar *buf;\n\tlp_yy_size_t n;\n\tint i;\n    \n\t/* Get memory for full buffer, including space for trailing EOB's. */\n\tn = _lp_yybytes_len + 2;\n\tbuf = (char *) lp_yyalloc(n ,lp_yyscanner );\n\tif ( ! buf )\n\t\tYY_FATAL_ERROR( \"out of dynamic memory in lp_yy_scan_bytes()\" );\n\n\tfor ( i = 0; i < _lp_yybytes_len; ++i )\n\t\tbuf[i] = lp_yybytes[i];\n\n\tbuf[_lp_yybytes_len] = buf[_lp_yybytes_len+1] = YY_END_OF_BUFFER_CHAR;\n\n\tb = lp_yy_scan_buffer(buf,n ,lp_yyscanner);\n\tif ( ! b )\n\t\tYY_FATAL_ERROR( \"bad buffer in lp_yy_scan_bytes()\" );\n\n\t/* It's okay to grow etc. this buffer, and we should throw it\n\t * away when we're done.\n\t */\n\tb->lp_yy_is_our_buffer = 1;\n\n\treturn b;\n}\n\n#ifndef YY_EXIT_FAILURE\n#define YY_EXIT_FAILURE 2\n#endif\n\nstatic void lp_yy_fatal_error (lp_yyconst char* msg , lp_yyscan_t lp_yyscanner)\n{\n    \t(void) fprintf( stderr, \"%s\\n\", msg );\n\texit( YY_EXIT_FAILURE );\n}\n\n/* Redefine lp_yyless() so it works in section 3 code. */\n\n#undef lp_yyless\n#define lp_yyless(n) \\\n\tdo \\\n\t\t{ \\\n\t\t/* Undo effects of setting up lp_yytext. */ \\\n        int lp_yyless_macro_arg = (n); \\\n        YY_LESS_LINENO(lp_yyless_macro_arg);\\\n\t\tlp_yytext[lp_yyleng] = lp_yyg->lp_yy_hold_char; \\\n\t\tlp_yyg->lp_yy_c_buf_p = lp_yytext + lp_yyless_macro_arg; \\\n\t\tlp_yyg->lp_yy_hold_char = *lp_yyg->lp_yy_c_buf_p; \\\n\t\t*lp_yyg->lp_yy_c_buf_p = '\\0'; \\\n\t\tlp_yyleng = lp_yyless_macro_arg; \\\n\t\t} \\\n\twhile ( 0 )\n\n/* Accessor  methods (get/set functions) to struct members. */\n\n/** Get the user-defined data for this scanner.\n * @param lp_yyscanner The scanner object.\n */\nYY_EXTRA_TYPE lp_yyget_extra  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yyextra;\n}\n\n/** Get the current line number.\n * @param lp_yyscanner The scanner object.\n */\nint lp_yyget_lineno  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    \n        if (! YY_CURRENT_BUFFER)\n            return 0;\n    \n    return lp_yylineno;\n}\n\n/** Get the current column number.\n * @param lp_yyscanner The scanner object.\n */\nint lp_yyget_column  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    \n        if (! YY_CURRENT_BUFFER)\n            return 0;\n    \n    return lp_yycolumn;\n}\n\n/** Get the input stream.\n * @param lp_yyscanner The scanner object.\n */\nFILE *lp_yyget_in  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yyin;\n}\n\n/** Get the output stream.\n * @param lp_yyscanner The scanner object.\n */\nFILE *lp_yyget_out  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yyout;\n}\n\n/** Get the length of the current token.\n * @param lp_yyscanner The scanner object.\n */\nint lp_yyget_leng  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yyleng;\n}\n\n/** Get the current token.\n * @param lp_yyscanner The scanner object.\n */\n\nchar *lp_yyget_text  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yytext;\n}\n\n/** Set the user-defined data. This data is never touched by the scanner.\n * @param user_defined The data to be associated with this scanner.\n * @param lp_yyscanner The scanner object.\n */\nvoid lp_yyset_extra (YY_EXTRA_TYPE  user_defined , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yyextra = user_defined ;\n}\n\n/** Set the current line number.\n * @param line_number\n * @param lp_yyscanner The scanner object.\n */\nvoid lp_yyset_lineno (int  line_number , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n        /* lineno is only valid if an input buffer exists. */\n        if (! YY_CURRENT_BUFFER )\n           lp_yy_fatal_error( \"lp_yyset_lineno called with no buffer\" , lp_yyscanner); \n    \n    lp_yylineno = line_number;\n}\n\n/** Set the current column.\n * @param line_number\n * @param lp_yyscanner The scanner object.\n */\nvoid lp_yyset_column (int  column_no , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n        /* column is only valid if an input buffer exists. */\n        if (! YY_CURRENT_BUFFER )\n           lp_yy_fatal_error( \"lp_yyset_column called with no buffer\" , lp_yyscanner); \n    \n    lp_yycolumn = column_no;\n}\n\n/** Set the input stream. This does not discard the current\n * input buffer.\n * @param in_str A readable stream.\n * @param lp_yyscanner The scanner object.\n * @see lp_yy_switch_to_buffer\n */\nvoid lp_yyset_in (FILE *  in_str , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yyin = in_str ;\n}\n\nvoid lp_yyset_out (FILE *  out_str , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yyout = out_str ;\n}\n\nint lp_yyget_debug  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yy_flex_debug;\n}\n\nvoid lp_yyset_debug (int  bdebug , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yy_flex_debug = bdebug ;\n}\n\n/* Accessor methods for lp_yylval and lp_yylloc */\n\nYYSTYPE * lp_yyget_lval  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    return lp_yylval;\n}\n\nvoid lp_yyset_lval (YYSTYPE *  lp_yylval_param , lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    lp_yylval = lp_yylval_param;\n}\n\n/* User-visible API */\n\n/* lp_yylex_init is special because it creates the scanner itself, so it is\n * the ONLY reentrant function that doesn't take the scanner as the last argument.\n * That's why we explicitly handle the declaration, instead of using our macros.\n */\n\nint lp_yylex_init(lp_yyscan_t* ptr_lp_yy_globals)\n\n{\n    if (ptr_lp_yy_globals == NULL){\n        errno = EINVAL;\n        return 1;\n    }\n\n    *ptr_lp_yy_globals = (lp_yyscan_t) lp_yyalloc ( sizeof( struct lp_yyguts_t ), NULL );\n\n    if (*ptr_lp_yy_globals == NULL){\n        errno = ENOMEM;\n        return 1;\n    }\n\n    /* By setting to 0xAA, we expose bugs in lp_yy_init_globals. Leave at 0x00 for releases. */\n    memset(*ptr_lp_yy_globals,0x00,sizeof(struct lp_yyguts_t));\n\n    return lp_yy_init_globals ( *ptr_lp_yy_globals );\n}\n\n/* lp_yylex_init_extra has the same functionality as lp_yylex_init, but follows the\n * convention of taking the scanner as the last argument. Note however, that\n * this is a *pointer* to a scanner, as it will be allocated by this call (and\n * is the reason, too, why this function also must handle its own declaration).\n * The user defined value in the first argument will be available to lp_yyalloc in\n * the lp_yyextra field.\n */\n\nint lp_yylex_init_extra(YY_EXTRA_TYPE lp_yy_user_defined,lp_yyscan_t* ptr_lp_yy_globals )\n\n{\n    struct lp_yyguts_t dummy_lp_yyguts;\n\n    lp_yyset_extra (lp_yy_user_defined, &dummy_lp_yyguts);\n\n    if (ptr_lp_yy_globals == NULL){\n        errno = EINVAL;\n        return 1;\n    }\n\t\n    *ptr_lp_yy_globals = (lp_yyscan_t) lp_yyalloc ( sizeof( struct lp_yyguts_t ), &dummy_lp_yyguts );\n\t\n    if (*ptr_lp_yy_globals == NULL){\n        errno = ENOMEM;\n        return 1;\n    }\n    \n    /* By setting to 0xAA, we expose bugs in\n    lp_yy_init_globals. Leave at 0x00 for releases. */\n    memset(*ptr_lp_yy_globals,0x00,sizeof(struct lp_yyguts_t));\n    \n    lp_yyset_extra (lp_yy_user_defined, *ptr_lp_yy_globals);\n    \n    return lp_yy_init_globals ( *ptr_lp_yy_globals );\n}\n\nstatic int lp_yy_init_globals (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n    /* Initialization is the same as for the non-reentrant scanner.\n     * This function is called from lp_yylex_destroy(), so don't allocate here.\n     */\n\n    lp_yyg->lp_yy_buffer_stack = 0;\n    lp_yyg->lp_yy_buffer_stack_top = 0;\n    lp_yyg->lp_yy_buffer_stack_max = 0;\n    lp_yyg->lp_yy_c_buf_p = (char *) 0;\n    lp_yyg->lp_yy_init = 0;\n    lp_yyg->lp_yy_start = 0;\n\n    lp_yyg->lp_yy_start_stack_ptr = 0;\n    lp_yyg->lp_yy_start_stack_depth = 0;\n    lp_yyg->lp_yy_start_stack =  NULL;\n\n/* Defined in main.c */\n#ifdef YY_STDINIT\n    lp_yyin = stdin;\n    lp_yyout = stdout;\n#else\n    lp_yyin = (FILE *) 0;\n    lp_yyout = (FILE *) 0;\n#endif\n\n    /* For future reference: Set errno on error, since we are called by\n     * lp_yylex_init()\n     */\n    return 0;\n}\n\n/* lp_yylex_destroy is for both reentrant and non-reentrant scanners. */\nint lp_yylex_destroy  (lp_yyscan_t lp_yyscanner)\n{\n    struct lp_yyguts_t * lp_yyg = (struct lp_yyguts_t*)lp_yyscanner;\n\n    /* Pop the buffer stack, destroying each element. */\n\twhile(YY_CURRENT_BUFFER){\n\t\tlp_yy_delete_buffer(YY_CURRENT_BUFFER ,lp_yyscanner );\n\t\tYY_CURRENT_BUFFER_LVALUE = NULL;\n\t\tlp_yypop_buffer_state(lp_yyscanner);\n\t}\n\n\t/* Destroy the stack itself. */\n\tlp_yyfree(lp_yyg->lp_yy_buffer_stack ,lp_yyscanner);\n\tlp_yyg->lp_yy_buffer_stack = NULL;\n\n    /* Destroy the start condition stack. */\n        lp_yyfree(lp_yyg->lp_yy_start_stack ,lp_yyscanner );\n        lp_yyg->lp_yy_start_stack = NULL;\n\n    /* Reset the globals. This is important in a non-reentrant scanner so the next time\n     * lp_yylex() is called, initialization will occur. */\n    lp_yy_init_globals( lp_yyscanner);\n\n    /* Destroy the main struct (reentrant only). */\n    lp_yyfree ( lp_yyscanner , lp_yyscanner );\n    lp_yyscanner = NULL;\n    return 0;\n}\n\n/*\n * Internal utility routines.\n */\n\n#ifndef lp_yytext_ptr\nstatic void lp_yy_flex_strncpy (char* s1, lp_yyconst char * s2, int n , lp_yyscan_t lp_yyscanner)\n{\n\tregister int i;\n\tfor ( i = 0; i < n; ++i )\n\t\ts1[i] = s2[i];\n}\n#endif\n\n#ifdef YY_NEED_STRLEN\nstatic int lp_yy_flex_strlen (lp_yyconst char * s , lp_yyscan_t lp_yyscanner)\n{\n\tregister int n;\n\tfor ( n = 0; s[n]; ++n )\n\t\t;\n\n\treturn n;\n}\n#endif\n\nvoid *lp_yyalloc (lp_yy_size_t  size , lp_yyscan_t lp_yyscanner)\n{\n\treturn (void *) malloc( size );\n}\n\nvoid *lp_yyrealloc  (void * ptr, lp_yy_size_t  size , lp_yyscan_t lp_yyscanner)\n{\n\t/* The cast to (char *) in the following accommodates both\n\t * implementations that use char* generic pointers, and those\n\t * that use void* generic pointers.  It works with the latter\n\t * because both ANSI C and C++ allow castless assignment from\n\t * any pointer type to void*, and deal with argument conversions\n\t * as though doing an assignment.\n\t */\n\treturn (void *) realloc( (char *) ptr, size );\n}\n\nvoid lp_yyfree (void * ptr , lp_yyscan_t lp_yyscanner)\n{\n\tfree( (char *) ptr );\t/* see lp_yyrealloc() for (char *) cast */\n}\n\n#define YYTABLES_NAME \"lp_yytables\"\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_rlp.l",
    "content": "WS1  [ \\t]\nWS2  [ \\t\\r\\n]\nLT   [A-Za-z]\nKR   [A-Za-z0-9_\\[\\]\\{\\}/.&#$%~'@^]\nDI   [0-9]\nINNM {DI}+\nNM   (({DI}+\\.?{DI}*)|(\\.{DI}+))([Ee][-+]?{DI}+)?\nVR   {LT}{KR}*(<{KR}+>)?\nOPEQ =\nOPLE [<]=?\nOPGE [>]=?\nEOW  $|[*+-;<=>]|{WS2}+\nINF  {WS2}*[-+][Ii][Nn][Ff]([Ii][Nn][Ii][Tt]([Ee]|[Yy]))?{EOW}\nS_OP [-+ \\t\\n\\r]+\nMIN  [mM][iI][nN]([iI][mM][iI][zZsS][eE])?{WS1}*:\nMAX  [mM][aA][xX]([iI][mM][iI][zZsS][eE])?{WS1}*:\nINT  ^{WS1}*[Ii][Nn][Tt]([Ee][Gg][Ee][Rr])?\nBIN  ^{WS1}*[Bb][Ii][Nn]([Aa][Rr][Yy])?\nSEC  ^{WS1}*([Ss][Ee][Cc])|([Ss][Ee][Mm][Ii]-[Cc][Oo][Nn][Tt][Ii][Nn][Uu][Oo][Uu][Ss])|([Ss][Ee][Mm][Ii])|([Ss][Ee][Mm][Ii][Ss])\nSOS  ^{WS1}*([Ss][Oo][Ss][12]*)|([Ss][Ee][Tt][Ss])\nFREE ^{WS1}*[Ff][Rr][Ee][Ee]\nLBL  {VR}{WS1}*:\nSOSD {LBL}:\n\n/*\n   made reentrant with help of\n   http://www.usualcoding.eu/post/2007/09/03/Building-a-reentrant-parser-in-C-with-Flex/Bison\n*/\n\n/*\n   Note that a minimum version of flex is needed to be able to compile this.\n   Older version don't know the reentrant code.\n   Version 2.5.4 is not enough. Probably at least v2.5.31 is needed. Tested with v2.5.35\n*/\n\n/*\n** We want the scanner to be reentrant, therefore generate no global variables.\n** That what the 'reentrant' option is for.\n** 'bison-bridge' is used to create a bison compatible scanner and share yylval\n*/\n\n%option reentrant bison-bridge\n%option noyywrap\n%option yylineno\n\n%start COMMENT\n%start LINECOMMENT\n\n%%\n<INITIAL>\"/*\" {\n  BEGIN COMMENT;\n} /* begin skip comment */\n\n<COMMENT>\"*/\" {\n  BEGIN INITIAL;\n} /* end skip comment */\n\n<COMMENT>. {\n}\n\n<COMMENT>\\n {\n}\n\n<COMMENT>\\r {\n}\n\n<INITIAL>\"//\" {\n  BEGIN LINECOMMENT;\n} /* begin skip LINECOMMENT */\n\n<LINECOMMENT>\\n {\n  BEGIN INITIAL;\n} /* end skip LINECOMMENT */\n\n<LINECOMMENT>\\r {\n  BEGIN INITIAL;\n} /* end skip LINECOMMENT */\n\n<LINECOMMENT>. {\n}\n\n<INITIAL>{WS2}+ {\n}\n\n<INITIAL>\",\" {\n  parse_parm *pp = PARM;\n\n  pp->lineno = yylineno;\n  return(COMMA);\n}\n\n<INITIAL>{MIN} {\n  parse_parm *pp = PARM;\n\n  pp->lineno = yylineno;\n  return(MINIMISE);\n}\n\n<INITIAL>{MAX} {\n  parse_parm *pp = PARM;\n\n  pp->lineno = yylineno;\n  return(MAXIMISE);\n}\n\n<INITIAL>{INNM} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  pv->f = atof((char *)yytext);\n  return(INTCONS);\n} /* f contains the last float */\n\n<INITIAL>{NM} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  pv->f = atof((char *)yytext);\n  return(CONS);\n} /* f contains the last float */\n\n<INITIAL>{INF} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  char *ptr, c;\n\n  pp->lineno = yylineno;\n  pv->f = DEF_INFINITE;\n  pv->Sign = 0;\n  ptr = (char *)yytext;\n  while (isspace(*ptr)) ptr++;\n  if(*ptr == '-')\n    pv->Sign = 1;\n  if(yyleng > 0) {\n    c = yytext[yyleng - 1];\n    if(!isalnum(c))\n      unput(c);\n  }\n  return(INF);\n} /* f contains the last float */\n\n<INITIAL>{S_OP} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  int x;\n\n  pp->lineno = yylineno;\n  pv->Sign = 0;\n  for(x = 0; x < yyleng; x++)\n    if(yytext[x] == '-' || yytext[x] == '+')\n      pv->Sign = (pv->Sign == (yytext[x] == '+'));\n  return (TOK_SIGN);\n  /* Sign is TRUE if the sign-string\n     represents a '-'. Otherwise Sign\n     is FALSE */\n}\n\n<INITIAL>{INT} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_int_decl = 1;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_INT);\n}\n\n<INITIAL>{BIN} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_int_decl = 2;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_BIN);\n}\n\n<INITIAL>{SEC} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_sec_decl = TRUE;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_SEC);\n}\n\n<INITIAL>{SOS} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  if(!pv->Within_sos_decl)\n    pv->SOStype0 = (short)atoi(((char *)yytext) + 3);\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl))\n    pv->Within_sos_decl = TRUE;\n  return(SEC_SOS);\n}\n\n<INITIAL>{SOSD} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)yytext);\n  pv->Last_var[strlen(pv->Last_var) - 2] = 0;\n  return(SOSDESCR);\n}\n\n<INITIAL>{FREE} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl) && (!pv->Within_free_decl)) {\n    pv->Within_free_decl = TRUE;\n    pv->Within_sos_decl1 = FALSE;\n  }\n  return(SEC_FREE);\n}\n\n<INITIAL>{LBL} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  char *ptr;\n\n  pp->lineno = yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)yytext);\n  ptr = pv->Last_var + strlen(pv->Last_var);\n  ptr[-1] = ' ';\n  while ((--ptr >= pv->Last_var) && (isspace(*ptr)))\n    *ptr = 0;\n  return(VARIABLECOLON);\n}\n\n<INITIAL>{VR} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  FREE(pv->Last_var);\n  pv->Last_var = strdup((char *)yytext);\n  return(VAR);\n}\n\n<INITIAL>\":\" {\n  parse_parm *pp = PARM;\n\n  pp->lineno = yylineno;\n  return (COLON);\n}\n\n<INITIAL>\"*\" {\n  parse_parm *pp = PARM;\n\n  pp->lineno = yylineno;\n  return(AR_M_OP);\n}\n\n<INITIAL>{OPEQ} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  pv->OP = *yytext;\n  return(RE_OPEQ);\n}\n\n<INITIAL>{OPLE} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  pv->OP = *yytext;\n  return(RE_OPLE);\n}\n\n<INITIAL>{OPGE} {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  pv->OP = *yytext;\n  return(RE_OPGE);\n}\n\n<INITIAL>\";\" {\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pp->lineno = yylineno;\n  pv->Within_int_decl = pv->Within_sec_decl = pv->Within_sos_decl = pv->Within_free_decl = FALSE;\n  check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, (int) pv->Within_sos_decl, (int) pv->Within_free_decl);\n  return(END_C);\n}\n\n<INITIAL>. {\n  parse_parm *pp = PARM;\n\n  pp->lineno = yylineno;\n  report(NULL, CRITICAL, \"LEX ERROR : %s lineno %d\\n\", yytext, yylineno);\n  return(UNDEFINED);\n}\n\n%%\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_rlp.y",
    "content": "/* ========================================================================= */\n/* NAME  : lp_rlp.y                                                          */\n/* ========================================================================= */\n\n/*\n   made reentrant with help of\n   http://www.usualcoding.eu/post/2007/09/03/Building-a-reentrant-parser-in-C-with-Flex/Bison\n*/\n\n/*\n   Note that a minimum version of bison is needed to be able to compile this.\n   Older version don't know the reentrant code.\n   Version 1.35 is not enough. v1.875 could be ok. Tested with v2.3\n*/\n\n%pure-parser\n%parse-param {parse_parm *parm}\n%parse-param {void *scanner}\n%lex-param {yyscan_t *scanner}\n\n%token VAR CONS INTCONS VARIABLECOLON INF SEC_INT SEC_BIN SEC_SEC SEC_SOS SOSDESCR SEC_FREE TOK_SIGN AR_M_OP RE_OPEQ RE_OPLE RE_OPGE END_C COMMA COLON MINIMISE MAXIMISE UNDEFINED\n\n\n%{\n#include <stdlib.h>\n#include <string.h>\n#include <ctype.h>\n\n#define scanner yyscanner\n#define PARM yyget_extra(yyscanner)\n#define YYSTYPE int\n#define YY_EXTRA_TYPE parse_parm *\n#define YY_FATAL_ERROR(msg) lex_fatal_error(PARM, yyscanner, msg)\n#undef YY_INPUT\n#define YY_INPUT(buf,result,max_size) result = lp_input((void *) PARM, buf, max_size);\n#define yyerror read_error\n\n#include \"lpkit.h\"\n#include \"yacc_read.h\"\n\ntypedef struct parse_vars_s\n{\n  read_modeldata_func *lp_input;\n  void *userhandle;\n  char HadVar, HadVar0, HadVar1, HadVar2, HasAR_M_OP, HadConstraint, Had_lineair_sum, Had_lineair_sum0, do_add_row, HadSign, OP, Sign, isign, isign0, make_neg;\n  char state, state0;\n  char Within_int_decl;  /* TRUE when we are within an char declaration */\n  char Within_bin_decl;  /* TRUE when we are within an bin declaration */\n  char Within_sec_decl;  /* TRUE when we are within a sec declaration */\n  char Within_sos_decl;  /* TRUE when we are within a sos declaration */\n  char Within_sos_decl1;\n  char Within_free_decl; /* TRUE when we are within a free declaration */\n  short SOStype, SOStype0;        /* SOS type */\n  int SOSNr;\n  int SOSweight;         /* SOS weight */\n  char *Last_var, *Last_var0;\n  REAL f, f0, f1;\n} parse_vars;\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* let's please C++ users */\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n#if defined MSDOS || defined __MSDOS__ || defined WINDOWS || defined _WINDOWS || defined WIN32 || defined _WIN32\n#define YY_NO_UNISTD_H\n\nstatic int isatty(int f)\n{\n  return(FALSE);\n}\n\n#if !defined _STDLIB_H\n# define _STDLIB_H\n#endif\n#endif\n\nstatic int __WINAPI lp_input_yyin(void *fpin, char *buf, int max_size)\n{\n  int result;\n\n  result = fread( (char*)buf, sizeof(char), max_size, (FILE *)fpin);\n\n  return(result);\n}\n\nstatic int __WINAPI lp_input(void *vpp, char *buf, int max_size)\n{\n  parse_parm *pp = (parse_parm *) vpp;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  int result;\n\n  result = pv->lp_input(pv->userhandle, buf, max_size);\n  if (result < 0)\n    lex_fatal_error(pp, pp->scanner, \"read() in flex scanner failed\");\n  return(result);\n}\n\n#ifdef __cplusplus\n};\n#endif\n\n#include \"lp_rlp.h\"\n\n#undef yylval\n\n%}\n\n%start inputfile\n%%\n\nEMPTY: /* EMPTY */\n                ;\n\ninputfile       :\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = 0;\n  pv->make_neg = 0;\n  pv->Sign = 0;\n  pv->HadConstraint = FALSE;\n  pv->HadVar = pv->HadVar0 = FALSE;\n}\n                  objective_function\n                  constraints\n                  int_bin_sec_sos_free_declarations\n                ;\n\n/* start objective_function */\n\n/*\n\n objective_function: MAXIMISE real_of | MINIMISE real_of | real_of;\n real_of:            lineair_sum END_C;\n lineair_sum:        EMPTY | x_lineair_sum;\n\n*/\n\nobjective_function:   MAXIMISE real_of\n{\n  set_obj_dir(PARM, TRUE);\n}\n                    | MINIMISE real_of\n{\n  set_obj_dir(PARM, FALSE);\n}\n                    | real_of\n                ;\n\nreal_of:            lineair_sum\n                    END_C\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  add_row(pp);\n  pv->HadConstraint = FALSE;\n  pv->HadVar = pv->HadVar0 = FALSE;\n  pv->isign = 0;\n  pv->make_neg = 0;\n}\n                ;\n\nlineair_sum:          EMPTY\n                    | x_lineair_sum\n                ;\n\n/* end objective_function */\n\n\n\n/* start constraints */\n\n/*\n\n constraints:        EMPTY | x_constraints;\n x_constraints:      constraint | x_constraints constraint;\n constraint:         real_constraint | VARIABLECOLON real_constraint;\n real_constraint:    x_lineair_sum2 RE_OP x_lineair_sum3 optionalrange END_C;\n optionalrange:      EMPTY | RE_OP cons_term RHS_STORE;\n RE_OP:              RE_OPEQ | RE_OPLE | RE_OPGE;\n cons_term:          x_SIGN REALCONS | INF;\n x_lineair_sum2:     EMPTY | x_lineair_sum3;\n x_lineair_sum3:     x_lineair_sum | INF RHS_STORE;\n x_lineair_sum:      x_lineair_sum1;\n x_lineair_sum1:     x_lineair_term | x_lineair_sum1 x_lineair_term;\n x_lineair_term:     x_SIGN x_lineair_term1;\n x_lineair_term1:    REALCONS | optional_AR_M_OP VAR;\n x_SIGN:             EMPTY | TOK_SIGN;\n REALCONS:           INTCONS | CONS;\n optional_AR_M_OP:   EMPTY | AR_M_OP;\n\n*/\n\nconstraints:      EMPTY\n                | x_constraints\n                ;\n\nx_constraints   : constraint\n                | x_constraints\n                  constraint\n                ;\n\nconstraint      : real_constraint\n                | VARIABLECOLON\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(!add_constraint_name(pp, pv->Last_var))\n    YYABORT;\n  pv->HadConstraint = TRUE;\n}\n                  real_constraint\n                ;\n\nreal_constraint : x_lineair_sum2\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->HadVar1 = pv->HadVar0;\n  pv->HadVar0 = FALSE;\n}\n                  RE_OP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(!store_re_op(pp, pv->OP, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n    YYABORT;\n  pv->make_neg = 1;\n  pv->f1 = 0;\n}\n                  x_lineair_sum3\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->Had_lineair_sum0 = pv->Had_lineair_sum;\n  pv->Had_lineair_sum = TRUE;\n  pv->HadVar2 = pv->HadVar0;\n  pv->HadVar0 = FALSE;\n  pv->do_add_row = FALSE;\n  if(pv->HadConstraint && !pv->HadVar ) {\n    /* it is a range */\n    /* already handled */\n  }\n  else if(!pv->HadConstraint && pv->HadVar) {\n    /* it is a bound */\n\n    if(!store_bounds(pp, TRUE))\n      YYABORT;\n  }\n  else {\n    /* it is a row restriction */\n    if(pv->HadConstraint && pv->HadVar)\n      store_re_op(pp, '\\0', (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum); /* makes sure that data stored in temporary buffers is treated correctly */\n    pv->do_add_row = TRUE;\n  }\n}\n                  optionalrange\n                  END_C\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((!pv->HadVar) && (!pv->HadConstraint)) {\n    yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n  if(pv->do_add_row)\n    add_row(pp);\n  pv->HadConstraint = FALSE;\n  pv->HadVar = pv->HadVar0 = FALSE;\n  pv->isign = 0;\n  pv->make_neg = 0;\n  null_tmp_store(pp, TRUE);\n}\n                ;\n\noptionalrange:    EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((!pv->HadVar1) && (pv->Had_lineair_sum0))\n    if(!negate_constraint(pp))\n      YYABORT;\n}\n                | RE_OP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->make_neg = 0;\n  pv->isign = 0;\n  if(pv->HadConstraint)\n    pv->HadVar = pv->Had_lineair_sum = FALSE;\n  pv->HadVar0 = FALSE;\n  if(!store_re_op(pp, (char) ((pv->OP == '<') ? '>' : (pv->OP == '>') ? '<' : pv->OP), (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n    YYABORT;\n}\n                  cons_term\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->f -= pv->f1;\n}\n                  RHS_STORE\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((pv->HadVar1) || (!pv->HadVar2) || (pv->HadVar0)) {\n    yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n\n  if(pv->HadConstraint && !pv->HadVar ) {\n    /* it is a range */\n    /* already handled */\n    if(!negate_constraint(pp))\n      YYABORT;\n  }\n  else if(!pv->HadConstraint && pv->HadVar) {\n    /* it is a bound */\n\n    if(!store_bounds(pp, TRUE))\n      YYABORT;\n  }\n}\n                ;\n\nx_lineair_sum2:   EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  /* to allow a range */\n  /* constraint: < max */\n  if(!pv->HadConstraint) {\n    yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n  pv->Had_lineair_sum = FALSE;\n}\n                | x_lineair_sum3\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->Had_lineair_sum = TRUE;\n}\n                ;\n\nx_lineair_sum3  :  x_lineair_sum\n                | INF\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = pv->Sign;\n}\n                  RHS_STORE\n                ;\n\nx_lineair_sum:\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->state = pv->state0 = 0;\n}\n                x_lineair_sum1\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if (pv->state == 1) {\n    /* RHS_STORE */\n    if (    (pv->isign0 || !pv->make_neg)\n        && !(pv->isign0 && !pv->make_neg)) /* but not both! */\n      pv->f0 = -pv->f0;\n    if(pv->make_neg)\n      pv->f1 += pv->f0;\n    if(!rhs_store(pp, pv->f0, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n      YYABORT;\n  }\n}\n                ;\n\nx_lineair_sum1  : x_lineair_term\n                | x_lineair_sum1\n                  x_lineair_term\n                ;\n\nx_lineair_term  : x_SIGN\n                  x_lineair_term1\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if ((pv->HadSign || pv->state == 1) && (pv->state0 == 1)) {\n    /* RHS_STORE */\n    if (    (pv->isign0 || !pv->make_neg)\n        && !(pv->isign0 && !pv->make_neg)) /* but not both! */\n      pv->f0 = -pv->f0;\n    if(pv->make_neg)\n      pv->f1 += pv->f0;\n    if(!rhs_store(pp, pv->f0, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n      YYABORT;\n  }\n  if (pv->state == 1) {\n    pv->f0 = pv->f;\n    pv->isign0 = pv->isign;\n  }\n  if (pv->state == 2) {\n    if((pv->HadSign) || (pv->state0 != 1)) {\n     pv->isign0 = pv->isign;\n     pv->f0 = 1.0;\n    }\n    if (    (pv->isign0 || pv->make_neg)\n        && !(pv->isign0 && pv->make_neg)) /* but not both! */\n      pv->f0 = -pv->f0;\n    if(!var_store(pp, pv->Last_var, pv->f0, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum)) {\n      yyerror(pp, pp->scanner, \"var_store failed\");\n      YYABORT;\n    }\n    pv->HadConstraint |= pv->HadVar;\n    pv->HadVar = pv->HadVar0 = TRUE;\n  }\n  pv->state0 = pv->state;\n}\n                ;\n\nx_lineair_term1 : REALCONS\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->state = 1;\n}\n                | optional_AR_M_OP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if ((pv->HasAR_M_OP) && (pv->state != 1)) {\n    yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n}\n                  VAR\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->state = 2;\n}\n                ;\n\nRE_OP: RE_OPEQ | RE_OPLE | RE_OPGE\n                ;\n\ncons_term:        x_SIGN\n                  REALCONS\n                | INF\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = pv->Sign;\n}\n                ;\n\n/* end constraints */\n\n\n/* start common for objective & constraints */\n\nREALCONS: INTCONS | CONS\n                ;\n\nx_SIGN:           EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = 0;\n  pv->HadSign = FALSE;\n}\n                | TOK_SIGN\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->isign = pv->Sign;\n  pv->HadSign = TRUE;\n}\n                ;\n\noptional_AR_M_OP: EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->HasAR_M_OP = FALSE;\n}\n                | AR_M_OP\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->HasAR_M_OP = TRUE;\n}\n                ;\n\nRHS_STORE:        EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if (    (pv->isign || !pv->make_neg)\n      && !(pv->isign && !pv->make_neg)) /* but not both! */\n    pv->f = -pv->f;\n  if(!rhs_store(pp, pv->f, (int) pv->HadConstraint, (int) pv->HadVar, (int) pv->Had_lineair_sum))\n    YYABORT;\n  pv->isign = 0;\n}\n                ;\n\n/* end common for objective & constraints */\n\n\n\n/* start int_bin_sec_sos_free_declarations */\n\nint_bin_sec_sos_free_declarations:\n                  EMPTY\n                | real_int_bin_sec_sos_free_decls\n                ;\n\nreal_int_bin_sec_sos_free_decls: int_bin_sec_sos_free_declaration\n                | real_int_bin_sec_sos_free_decls int_bin_sec_sos_free_declaration\n                ;\n\nSEC_INT_BIN_SEC_SOS_FREE: SEC_INT | SEC_BIN | SEC_SEC | SEC_SOS | SEC_FREE\n                ;\n\nint_bin_sec_sos_free_declaration:\n                  SEC_INT_BIN_SEC_SOS_FREE\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  pv->Within_sos_decl1 = pv->Within_sos_decl;\n}\n                  x_int_bin_sec_sos_free_declaration\n                ;\n\nxx_int_bin_sec_sos_free_declaration:\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((!pv->Within_int_decl) && (!pv->Within_sec_decl) && (!pv->Within_sos_decl1) && (!pv->Within_free_decl)) {\n    yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n  pv->SOStype = pv->SOStype0;\n  check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, (int) (pv->Within_sos_decl1 = (pv->Within_sos_decl1 ? 1 : 0)), (int) pv->Within_free_decl);\n}\n                  optionalsos\n                  vars\n                  optionalsostype\n                  END_C\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((pv->Within_sos_decl1) && (pv->SOStype == 0))\n  {\n    yyerror(pp, pp->scanner, \"Unsupported SOS type (0)\");\n    YYABORT;\n  }\n}\n                ;\n\nx_int_bin_sec_sos_free_declaration:\n                  xx_int_bin_sec_sos_free_declaration\n                | x_int_bin_sec_sos_free_declaration xx_int_bin_sec_sos_free_declaration\n                ;\n\noptionalsos:      EMPTY\n                | SOSDESCR\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  FREE(pv->Last_var0);\n  pv->Last_var0 = strdup(pv->Last_var);\n}\n                  sosdescr\n                ;\n\noptionalsostype:  EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(pv->Within_sos_decl1) {\n    set_sos_type(pp, pv->SOStype);\n    set_sos_weight(pp, (double) pv->SOSweight, 1);\n  }\n}\n                | RE_OPLE\n                  INTCONS\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if((pv->Within_sos_decl1) && (!pv->SOStype))\n  {\n    set_sos_type(pp, pv->SOStype = (short) (pv->f + .1));\n  }\n  else\n  {\n    yyerror(pp, pp->scanner, \"SOS type not expected\");\n    YYABORT;\n  }\n}\n                optionalSOSweight\n                ;\n\noptionalSOSweight:EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  set_sos_weight(pp, (double) pv->SOSweight, 1);\n}\n                | COLON\n                  INTCONS\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  set_sos_weight(pp, pv->f, 1);\n}\n                ;\n\nvars:             EMPTY\n                | x_vars\n                ;\n\nx_vars          : onevarwithoptionalweight\n                | x_vars\n                  optionalcomma\n                  onevarwithoptionalweight\n                ;\n\noptionalcomma:    EMPTY\n                | COMMA\n                ;\n\nvariable:         EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(pv->Within_sos_decl1 == 1)\n  {\n    char buf[16];\n\n    pv->SOSweight++;\n    sprintf(buf, \"SOS%d\", pv->SOSweight);\n    storevarandweight(pp, buf);\n\n    check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, 2, (int) pv->Within_free_decl);\n    pv->Within_sos_decl1 = 2;\n    pv->SOSNr = 0;\n  }\n\n  storevarandweight(pp, pv->Last_var);\n\n  if(pv->Within_sos_decl1 == 2)\n  {\n    pv->SOSNr++;\n    set_sos_weight(pp, (double) pv->SOSNr, 2);\n  }\n}\n                ;\n\nvariablecolon:\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(!pv->Within_sos_decl1) {\n    yyerror(pp, pp->scanner, \"parse error\");\n    YYABORT;\n  }\n  if(pv->Within_sos_decl1 == 1) {\n    FREE(pv->Last_var0);\n    pv->Last_var0 = strdup(pv->Last_var);\n  }\n  if(pv->Within_sos_decl1 == 2)\n  {\n    storevarandweight(pp, pv->Last_var);\n    pv->SOSNr++;\n    set_sos_weight(pp, (double) pv->SOSNr, 2);\n  }\n}\n                ;\n\nsosweight:        EMPTY\n{\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(pv->Within_sos_decl1 == 1)\n  {\n    char buf[16];\n\n    pv->SOSweight++;\n    sprintf(buf, \"SOS%d\", pv->SOSweight);\n    storevarandweight(pp, buf);\n\n    check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, 2, (int) pv->Within_free_decl);\n    pv->Within_sos_decl1 = 2;\n    pv->SOSNr = 0;\n\n    storevarandweight(pp, pv->Last_var0);\n    pv->SOSNr++;\n  }\n\n  set_sos_weight(pp, pv->f, 2);\n}\n                ;\n\nsosdescr:         EMPTY\n{ /* SOS name */\n  parse_parm *pp = PARM;\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n  if(pv->Within_sos_decl1 == 1)\n  {\n    parse_parm *pp = PARM;\n    parse_vars *pv = (parse_vars *) pp->parse_vars;\n\n    storevarandweight(pp, pv->Last_var0);\n    set_sos_type(pp, pv->SOStype);\n    check_int_sec_sos_free_decl(pp, (int) pv->Within_int_decl, (int) pv->Within_sec_decl, 2, (int) pv->Within_free_decl);\n    pv->Within_sos_decl1 = 2;\n    pv->SOSNr = 0;\n    pv->SOSweight++;\n  }\n}\n                ;\n\nonevarwithoptionalweight:\n                  VAR\n                  variable\n                | VARIABLECOLON\n                  variablecolon\n                  INTCONSorVARIABLE\n                ;\n\nINTCONSorVARIABLE:REALCONS /* INTCONS */\n                  sosweight\n                | sosdescr\n                  x_onevarwithoptionalweight\n                ;\n\nx_onevarwithoptionalweight:\n                  VAR\n                  variable\n                | VARIABLECOLON\n                  variablecolon\n                  REALCONS /* INTCONS */\n                  sosweight\n                ;\n\n/* end int_bin_sec_sos_free_declarations */\n\n%%\n\nstatic void yy_delete_allocated_memory(parse_parm *pp)\n{\n  parse_vars *pv = (parse_vars *) pp->parse_vars;\n  /* free memory allocated by flex. Otherwise some memory is not freed.\n     This is a bit tricky. There is not much documentation about this, but a lot of\n     reports of memory that keeps allocated */\n\n  /* If you get errors on this function call, just comment it. This will only result\n     in some memory that is not being freed. */\n\n# if defined YY_CURRENT_BUFFER\n    /* flex defines the macro YY_CURRENT_BUFFER, so you should only get here if lp_rlp.h is\n       generated by flex */\n    /* lex doesn't define this macro and thus should not come here, but lex doesn't has\n       this memory leak also ...*/\n\n#  if 0\n    /* older versions of flex */\n    yy_delete_buffer(YY_CURRENT_BUFFER); /* comment this line if you have problems with it */\n    yy_init = 1; /* make sure that the next time memory is allocated again */\n    yy_start = 0;\n#  else\n    /* As of version 2.5.9 Flex  */\n    yylex_destroy(pp->scanner); /* comment this line if you have problems with it */\n#  endif\n# endif\n\n  FREE(pv->Last_var);\n  FREE(pv->Last_var0);\n}\n\nstatic int parse(parse_parm *pp)\n{\n  return(yyparse(pp, pp->scanner));\n}\n\nlprec *read_lp1(lprec *lp, void *userhandle, read_modeldata_func read_modeldata, int verbose, char *lp_name)\n{\n  parse_vars *pv;\n  lprec *lp1 = NULL;\n\n  CALLOC(pv, 1, parse_vars);\n  if (pv != NULL) {\n    parse_parm pp;\n\n    memset(&pp, 0, sizeof(pp));\n    pp.parse_vars = (void *) pv;\n\n    yylex_init(&pp.scanner);\n    yyset_extra(&pp, pp.scanner);\n\n    yyset_in((FILE *) userhandle, pp.scanner);\n    yyset_out(NULL, pp.scanner);\n    pv->lp_input = read_modeldata;\n    pv->userhandle = userhandle;\n    lp1 = yacc_read(lp, verbose, lp_name, parse, &pp, yy_delete_allocated_memory);\n    FREE(pv);\n  }\n  return(lp1);\n}\n\nlprec * __WINAPI read_lp(FILE *filename, int verbose, char *lp_name)\n{\n  return(read_lp1(NULL, filename, lp_input_yyin, verbose, lp_name));\n}\n\nlprec * __WINAPI read_lpex(void *userhandle, read_modeldata_func read_modeldata, int verbose, char *lp_name)\n{\n  return(read_lp1(NULL, userhandle, read_modeldata, verbose, lp_name));\n}\n\nlprec *read_LP1(lprec *lp, char *filename, int verbose, char *lp_name)\n{\n  FILE *fpin;\n\n  if((fpin = fopen(filename, \"r\")) != NULL) {\n    lp = read_lp1(lp, fpin, lp_input_yyin, verbose, lp_name);\n    fclose(fpin);\n  }\n  else\n    lp = NULL;\n  return(lp);\n}\n\nlprec * __WINAPI read_LP(char *filename, int verbose, char *lp_name)\n{\n  return(read_LP1(NULL, filename, verbose, lp_name));\n}\n\nMYBOOL __WINAPI LP_readhandle(lprec **lp, FILE *filename, int verbose, char *lp_name)\n{\n  if(lp != NULL)\n    *lp = read_lp1(*lp, filename, lp_input_yyin, verbose, lp_name);\n\n  return((lp != NULL) && (*lp != NULL));\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_scale.c",
    "content": "\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_report.h\"\n#include \"lp_scale.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n/*\n    Scaling routines for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Kjell Eikland\n    Contact:       kjell.eikland@broadpark.no\n    License terms: LGPL.\n\n    Requires:      lp_lib.h, lp_scale.h\n\n    Release notes:\n    v5.0.0  1 January 2004      Significantly expanded and repackaged scaling\n                                routines.\n    v5.0.1  20 February 2004    Modified rounding behaviour in several areas.\n    v5.1.0  20 July 2004        Reworked with flexible matrix storage model.\n    v5.2.0  20 February 2005    Converted to matrix storage model without the OF.\n\n   ----------------------------------------------------------------------------------\n*/\n\n/* First define scaling and unscaling primitives */\n\nREAL scaled_value(lprec *lp, REAL value, int index)\n{\n  if(fabs(value) < lp->infinite) {\n    if(lp->scaling_used) {\n      if(index > lp->rows)\n        value /= lp->scalars[index];\n      else\n        value *= lp->scalars[index];\n    }\n  }\n  else\n    value = my_sign(value)*lp->infinite;\n  return(value);\n}\n\nREAL unscaled_value(lprec *lp, REAL value, int index)\n{\n  if(fabs(value) < lp->infinite) {\n    if(lp->scaling_used) {\n      if(index > lp->rows)\n        value *= lp->scalars[index];\n      else\n        value /= lp->scalars[index];\n    }\n  }\n  else\n    value = my_sign(value)*lp->infinite;\n  return(value);\n}\n\nSTATIC REAL scaled_mat(lprec *lp, REAL value, int rownr, int colnr)\n{\n  if(lp->scaling_used)\n    value *= lp->scalars[rownr] * lp->scalars[lp->rows + colnr];\n  return( value );\n}\n\nSTATIC REAL unscaled_mat(lprec *lp, REAL value, int rownr, int colnr)\n{\n  if(lp->scaling_used)\n    value /= lp->scalars[rownr] * lp->scalars[lp->rows + colnr];\n  return( value );\n}\n\n/* Compute the scale factor by the formulae:\n      FALSE: SUM (log |Aij|) ^ 2\n      TRUE:  SUM (log |Aij| - RowScale[i] - ColScale[j]) ^ 2 */\nREAL CurtisReidMeasure(lprec *lp, MYBOOL _Advanced, REAL *FRowScale, REAL *FColScale)\n{\n  int      i, nz;\n  REAL     absvalue, logvalue;\n  register REAL result;\n  MATrec   *mat = lp->matA;\n  REAL     *value;\n  int      *rownr, *colnr;\n\n  /* Do OF part */\n  result = 0;\n  for(i = 1; i <= lp->columns; i++) {\n    absvalue = fabs(lp->orig_obj[i]);\n    if(absvalue > 0) {\n      logvalue = log(absvalue);\n      if(_Advanced)\n        logvalue -= FRowScale[0] + FColScale[i];\n      result += logvalue*logvalue;\n    }\n  }\n\n  /* Do constraint matrix part */\n  mat_validate(mat);\n  value = &(COL_MAT_VALUE(0));\n  rownr = &(COL_MAT_ROWNR(0));\n  colnr = &(COL_MAT_COLNR(0));\n  nz = get_nonzeros(lp);\n  for(i = 0; i < nz;\n      i++, value += matValueStep, rownr += matRowColStep, colnr += matRowColStep) {\n    absvalue = fabs(*value);\n    if(absvalue > 0) {\n      logvalue = log(absvalue);\n      if(_Advanced)\n        logvalue -= FRowScale[*rownr] + FColScale[*colnr];\n      result += logvalue*logvalue;\n    }\n  }\n  return( result );\n}\n\n/* Implementation of the Curtis-Reid scaling based on the paper\n   \"On the Automatic Scaling of Matrices for Gaussian\n    Elimination,\" Journal of the Institute of Mathematics and\n    Its Applications (1972) 10, 118-124.\n\n    Solve the system | M   E | (r)   (sigma)\n                     |       | ( ) = (     )\n                     | E^T N | (c)   ( tau )\n\n    by the conjugate gradient method (clever recurrences).\n\n    E is the matrix A with all elements = 1\n\n    M is diagonal matrix of row    counts (RowCount)\n    N is diagonal matrix of column counts (ColCount)\n\n    sigma is the vector of row    logarithm sums (RowSum)\n    tau   is the vector of column logarithm sums (ColSum)\n\n    r, c are resulting row and column scalings (RowScale, ColScale) */\n\nint CurtisReidScales(lprec *lp, MYBOOL _Advanced, REAL *FRowScale, REAL *FColScale)\n{\n  int    i, row, col, ent, nz;\n  REAL   *RowScalem2, *ColScalem2,\n         *RowSum, *ColSum,\n         *residual_even, *residual_odd;\n  REAL   sk,   qk,     ek,\n         skm1, qkm1,   ekm1,\n         qkm2, qkqkm1, ekm2, ekekm1,\n         absvalue, logvalue,\n         StopTolerance;\n  int    *RowCount, *ColCount, colMax;\n  int    Result;\n  MATrec *mat = lp->matA;\n  REAL   *value;\n  int    *rownr, *colnr;\n\n  if(CurtisReidMeasure(lp, _Advanced, FRowScale, FColScale)<0.1*get_nonzeros(lp))\n  return(0);\n\n  /* Allocate temporary memory and find RowSum and ColSum measures */\n  nz = get_nonzeros(lp);\n  colMax = lp->columns;\n\n  allocREAL(lp, &RowSum, lp->rows+1, TRUE);\n  allocINT(lp,  &RowCount, lp->rows+1, TRUE);\n  allocREAL(lp, &residual_odd, lp->rows+1, TRUE);\n\n  allocREAL(lp, &ColSum, colMax+1, TRUE);\n  allocINT(lp,  &ColCount, colMax+1, TRUE);\n  allocREAL(lp, &residual_even, colMax+1, TRUE);\n\n  allocREAL(lp, &RowScalem2, lp->rows+1, FALSE);\n  allocREAL(lp, &ColScalem2, colMax+1, FALSE);\n\n  /* Set origin for row scaling */\n  for(i = 1; i <= colMax; i++) {\n    absvalue=fabs(lp->orig_obj[i]);\n    if(absvalue>0) {\n      logvalue = log(absvalue);\n      ColSum[i] += logvalue;\n      RowSum[0] += logvalue;\n      ColCount[i]++;\n      RowCount[0]++;\n    }\n  }\n\n  value = &(COL_MAT_VALUE(0));\n  rownr = &(COL_MAT_ROWNR(0));\n  colnr = &(COL_MAT_COLNR(0));\n  for(i = 0; i < nz;\n      i++, value += matValueStep, rownr += matRowColStep, colnr += matRowColStep) {\n    absvalue=fabs(*value);\n    if(absvalue>0) {\n      logvalue = log(absvalue);\n      ColSum[*colnr] += logvalue;\n      RowSum[*rownr] += logvalue;\n      ColCount[*colnr]++;\n      RowCount[*rownr]++;\n    }\n  }\n\n  /* Make sure we dont't have division by zero errors */\n  for(row = 0; row <= lp->rows; row++)\n    if(RowCount[row] == 0)\n      RowCount[row] = 1;\n  for(col = 1; col <= colMax; col++)\n    if(ColCount[col] == 0)\n      ColCount[col] = 1;\n\n  /* Initialize to RowScale = RowCount-1 RowSum\n                   ColScale = 0.0\n                   residual = ColSum - ET RowCount-1 RowSum */\n\n  StopTolerance= MAX(lp->scalelimit-floor(lp->scalelimit), DEF_SCALINGEPS);\n  StopTolerance *= (REAL) nz;\n  for(row = 0; row <= lp->rows; row++) {\n    FRowScale[row] = RowSum[row] / (REAL) RowCount[row];\n    RowScalem2[row] = FRowScale[row];\n  }\n\n  /* Compute initial residual */\n  for(col = 1; col <= colMax; col++) {\n    FColScale[col] = 0;\n    ColScalem2[col] = 0;\n    residual_even[col] = ColSum[col];\n\n    if(lp->orig_obj[col] != 0)\n      residual_even[col] -= RowSum[0] / (REAL) RowCount[0];\n\n    i = mat->col_end[col-1];\n    rownr = &(COL_MAT_ROWNR(i));\n    ent = mat->col_end[col];\n    for(; i < ent;\n        i++, rownr += matRowColStep) {\n      residual_even[col] -= RowSum[*rownr] / (REAL) RowCount[*rownr];\n    }\n  }\n\n  /* Compute sk */\n  sk = 0;\n  skm1 = 0;\n  for(col = 1; col <= colMax; col++)\n    sk += (residual_even[col]*residual_even[col]) / (REAL) ColCount[col];\n\n  Result = 0;\n  qk=1; qkm1=0; qkm2=0;\n  ek=0; ekm1=0; ekm2=0;\n\n  while(sk>StopTolerance) {\n  /* Given the values of residual and sk, construct\n     ColScale (when pass is even)\n     RowScale (when pass is odd)  */\n\n    qkqkm1 = qk * qkm1;\n    ekekm1 = ek * ekm1;\n    if((Result % 2) == 0) { /* pass is even; construct RowScale[pass+1] */\n      if(Result != 0) {\n        for(row = 0; row <= lp->rows; row++)\n          RowScalem2[row] = FRowScale[row];\n        if(qkqkm1 != 0) {\n          for(row = 0; row <= lp->rows; row++)\n            FRowScale[row]*=(1 + ekekm1 / qkqkm1);\n          for(row = 0; row<=lp->rows; row++)\n            FRowScale[row]+=(residual_odd[row] / (qkqkm1 * (REAL) RowCount[row]) -\n                             RowScalem2[row] * ekekm1 / qkqkm1);\n        }\n      }\n    }\n    else { /* pass is odd; construct ColScale[pass+1] */\n      for(col = 1; col <= colMax; col++)\n        ColScalem2[col] = FColScale[col];\n      if(qkqkm1 != 0) {\n        for(col = 1; col <= colMax; col++)\n          FColScale[col] *= (1 + ekekm1 / qkqkm1);\n        for(col = 1; col <= colMax; col++)\n          FColScale[col] += (residual_even[col] / ((REAL) ColCount[col] * qkqkm1) -\n                             ColScalem2[col] * ekekm1 / qkqkm1);\n      }\n    }\n\n    /* update residual and sk (pass + 1) */\n    if((Result % 2) == 0) { /* even */\n       /* residual */\n      for(row = 0; row <= lp->rows; row++)\n        residual_odd[row] *= ek;\n\n      for(i = 1; i <= colMax; i++)\n        if(lp->orig_obj[i] != 0)\n          residual_odd[0] += (residual_even[i] / (REAL) ColCount[i]);\n\n      rownr = &(COL_MAT_ROWNR(0));\n      colnr = &(COL_MAT_COLNR(0));\n      for(i = 0; i < nz;\n          i++, rownr += matRowColStep, colnr += matRowColStep) {\n        residual_odd[*rownr] += (residual_even[*colnr] / (REAL) ColCount[*colnr]);\n      }\n      for(row = 0; row <= lp->rows; row++)\n        residual_odd[row] *= (-1 / qk);\n\n      /* sk */\n      skm1 = sk;\n      sk = 0;\n      for(row = 0; row <= lp->rows; row++)\n        sk += (residual_odd[row]*residual_odd[row]) / (REAL) RowCount[row];\n    }\n    else { /* odd */\n      /* residual */\n      for(col = 1; col <= colMax; col++)\n        residual_even[col] *= ek;\n\n      for(i = 1; i <= colMax; i++)\n        if(lp->orig_obj[i] != 0)\n          residual_even[i] += (residual_odd[0] / (REAL) RowCount[0]);\n\n      rownr = &(COL_MAT_ROWNR(0));\n      colnr = &(COL_MAT_COLNR(0));\n      for(i = 0; i < nz;\n          i++, rownr += matRowColStep, colnr += matRowColStep) {\n        residual_even[*colnr] += (residual_odd[*rownr] / (REAL) RowCount[*rownr]);\n      }\n      for(col = 1; col <= colMax; col++)\n        residual_even[col] *= (-1 / qk);\n\n      /* sk */\n      skm1 = sk;\n      sk = 0;\n      for(col = 1; col <= colMax; col++)\n        sk += (residual_even[col]*residual_even[col]) / (REAL) ColCount[col];\n    }\n\n    /* Compute ek and qk */\n    ekm2=ekm1;\n    ekm1=ek;\n    ek=qk * sk / skm1;\n\n    qkm2=qkm1;\n    qkm1=qk;\n    qk=1-ek;\n\n    Result++;\n  }\n\n  /* Synchronize the RowScale and ColScale vectors */\n  ekekm1 = ek * ekm1;\n  if(qkm1 != 0) {\n  if((Result % 2) == 0) { /* pass is even, compute RowScale */\n    for(row = 0; row<=lp->rows; row++)\n      FRowScale[row]*=(1.0 + ekekm1 / qkm1);\n    for(row = 0; row<=lp->rows; row++)\n      FRowScale[row]+=(residual_odd[row] / (qkm1 * (REAL) RowCount[row]) -\n                      RowScalem2[row] * ekekm1 / qkm1);\n  }\n  else { /* pass is odd, compute ColScale */\n    for(col=1; col<=colMax; col++)\n      FColScale[col]*=(1 + ekekm1 / qkm1);\n    for(col=1; col<=colMax; col++)\n      FColScale[col]+=(residual_even[col] / ((REAL) ColCount[col] * qkm1) -\n                       ColScalem2[col] * ekekm1 / qkm1);\n  }\n  }\n\n  /* Do validation, if indicated */\n  if(FALSE && mat_validate(mat)){\n    double check, error;\n\n    /* CHECK: M RowScale + E ColScale = RowSum */\n    error = 0;\n    for(row = 0; row <= lp->rows; row++) {\n      check = (REAL) RowCount[row] * FRowScale[row];\n      if(row == 0) {\n        for(i = 1; i <= colMax; i++) {\n          if(lp->orig_obj[i] != 0)\n            check += FColScale[i];\n        }\n      }\n      else {\n        i = mat->row_end[row-1];\n        ent = mat->row_end[row];\n        for(; i < ent; i++) {\n          col = ROW_MAT_COLNR(i);\n          check += FColScale[col];\n        }\n      }\n      check -= RowSum[row];\n      error += check*check;\n    }\n\n    /* CHECK: E^T RowScale + N ColScale = ColSum */\n    error = 0;\n    for(col = 1; col <= colMax; col++) {\n      check = (REAL) ColCount[col] * FColScale[col];\n\n      if(lp->orig_obj[col] != 0)\n        check += FRowScale[0];\n\n      i = mat->col_end[col-1];\n      ent = mat->col_end[col];\n      rownr = &(COL_MAT_ROWNR(i));\n      for(; i < ent;\n          i++, rownr += matRowColStep) {\n        check += FRowScale[*rownr];\n      }\n      check -= ColSum[col];\n      error += check*check;\n    }\n  }\n\n  /* Convert to scaling factors (rounding to nearest power\n     of 2 can optionally be done as a separate step later) */\n  for(col = 1; col <= colMax; col++) {\n    absvalue = exp(-FColScale[col]);\n    if(absvalue < MIN_SCALAR) absvalue = MIN_SCALAR;\n    if(absvalue > MAX_SCALAR) absvalue = MAX_SCALAR;\n    if(!is_int(lp,col) || is_integerscaling(lp))\n        FColScale[col] = absvalue;\n    else\n        FColScale[col] = 1;\n  }\n  for(row = 0; row <= lp->rows; row++) {\n    absvalue = exp(-FRowScale[row]);\n    if(absvalue < MIN_SCALAR) absvalue = MIN_SCALAR;\n    if(absvalue > MAX_SCALAR) absvalue = MAX_SCALAR;\n    FRowScale[row] = absvalue;\n  }\n\n /* free temporary memory */\n  FREE(RowSum);\n  FREE(ColSum);\n  FREE(RowCount);\n  FREE(ColCount);\n  FREE(residual_even);\n  FREE(residual_odd);\n  FREE(RowScalem2);\n  FREE(ColScalem2);\n\n  return(Result);\n\n}\n\nSTATIC MYBOOL scaleCR(lprec *lp, REAL *scaledelta)\n{\n  REAL *scalechange = NULL;\n  int  Result;\n\n  if(!lp->scaling_used) {\n    allocREAL(lp, &lp->scalars, lp->sum_alloc + 1, FALSE);\n    for(Result = 0; Result <= lp->sum; Result++)\n      lp->scalars[Result] = 1;\n    lp->scaling_used = TRUE;\n  }\n\n  if(scaledelta == NULL)\n    allocREAL(lp, &scalechange, lp->sum + 1, FALSE);\n  else\n    scalechange = scaledelta;\n\n  Result=CurtisReidScales(lp, FALSE, scalechange, &scalechange[lp->rows]);\n  if(Result>0) {\n\n    /* Do the scaling*/\n    if(scale_updaterows(lp, scalechange, TRUE) ||\n       scale_updatecolumns(lp, &scalechange[lp->rows], TRUE))\n      lp->scalemode |= SCALE_CURTISREID;\n\n    set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n  }\n\n  if(scaledelta == NULL)\n    FREE(scalechange);\n\n  return((MYBOOL) (Result > 0));\n}\n\nSTATIC MYBOOL transform_for_scale(lprec *lp, REAL *value)\n{\n  MYBOOL Accept = TRUE;\n  *value = fabs(*value);\n#ifdef Paranoia\n  if(*value < lp->epsmachine) {\n    Accept = FALSE;\n    report(lp, SEVERE, \"transform_for_scale: A zero-valued entry was passed\\n\");\n  }\n  else\n#endif\n  if(is_scalemode(lp, SCALE_LOGARITHMIC))\n    *value = log(*value);\n  else if(is_scalemode(lp, SCALE_QUADRATIC))\n    (*value) *= (*value);\n  return( Accept );\n}\n\nSTATIC void accumulate_for_scale(lprec *lp, REAL *min, REAL *max, REAL value)\n{\n  if(transform_for_scale(lp, &value)) {\n    if(is_scaletype(lp, SCALE_MEAN)) {\n      *max += value;\n      *min += 1;\n    }\n    else {\n      SETMAX(*max, value);\n      SETMIN(*min, value);\n    }\n  }\n}\n\nSTATIC REAL minmax_to_scale(lprec *lp, REAL min, REAL max, int itemcount)\n{\n  REAL scale;\n\n  /* Initialize according to transformation / weighting model */\n  if(is_scalemode(lp, SCALE_LOGARITHMIC))\n    scale = 0;\n  else\n    scale = 1;\n  if(itemcount <= 0)\n    return(scale);\n\n  /* Compute base scalar according to chosen scaling type */\n  if(is_scaletype(lp, SCALE_MEAN)) {\n    if(min > 0)\n      scale = max / min;\n  }\n  else if(is_scaletype(lp, SCALE_RANGE))\n    scale = (max + min) / 2;\n  else if(is_scaletype(lp, SCALE_GEOMETRIC))\n    scale = sqrt(min*max);\n  else if(is_scaletype(lp, SCALE_EXTREME))\n    scale = max;\n\n  /* Compute final scalar according to transformation / weighting model */\n  if(is_scalemode(lp, SCALE_LOGARITHMIC))\n    scale = exp(-scale);\n  else if(is_scalemode(lp, SCALE_QUADRATIC)) {\n    if(scale == 0)\n      scale = 1;\n    else\n      scale = 1 / sqrt(scale);\n  }\n  else {\n    if(scale == 0)\n      scale = 1;\n    else\n      scale = 1 / scale;\n  }\n\n  /* Make sure we are within acceptable scaling ranges */\n  SETMAX(scale, MIN_SCALAR);\n  SETMIN(scale, MAX_SCALAR);\n\n  return(scale);\n}\n\nSTATIC REAL roundPower2(REAL scale)\n/* Purpose is to round a number to it nearest power of 2; in a system\n   with binary number representation, this avoids rounding errors when\n   scale is used to normalize another value */\n{\n  long int power2;\n  MYBOOL   isSmall = FALSE;\n\n  if(scale == 1)\n    return( scale );\n\n  /* Obtain the fractional power of 2 */\n  if(scale < 2) {\n    scale = 2 / scale;\n    isSmall = TRUE;\n  }\n  else\n    scale /= 2;\n  scale = log(scale)/log(2.0);\n\n  /* Find the desired nearest power of two and compute the associated scalar */\n  power2 = (long) ceil(scale-0.5);\n  scale = 1 << power2;\n  if(isSmall)\n    scale = 1.0 / scale;\n\n  return( scale );\n\n}\n\nSTATIC MYBOOL scale_updatecolumns(lprec *lp, REAL *scalechange, MYBOOL updateonly)\n{\n  int i, j;\n\n  /* Verify that the scale change is significant (different from the unit) */\n  for(i = lp->columns; i > 0; i--)\n    if(fabs(scalechange[i]-1) > lp->epsprimal)\n      break;\n  if(i <= 0)\n    return( FALSE );\n\n /* Update the pre-existing column scalar */\n  if(updateonly)\n    for(i = 1, j = lp->rows + 1; j <= lp->sum; i++, j++)\n      lp->scalars[j] *= scalechange[i];\n  else\n    for(i = 1, j = lp->rows + 1; j <= lp->sum; i++, j++)\n      lp->scalars[j] = scalechange[i];\n\n  return( TRUE );\n}\n\nSTATIC MYBOOL scale_updaterows(lprec *lp, REAL *scalechange, MYBOOL updateonly)\n{\n  int i;\n\n  /* Verify that the scale change is significant (different from the unit) */\n  for(i = lp->rows; i >= 0; i--) {\n    if(fabs(scalechange[i]-1) > lp->epsprimal)\n      break;\n  }\n  if(i < 0)\n    return( FALSE );\n\n /* Update the pre-existing row scalar */\n  if(updateonly)\n    for(i = 0; i <= lp->rows; i++)\n      lp->scalars[i] *= scalechange[i];\n  else\n    for(i = 0; i <= lp->rows; i++)\n      lp->scalars[i] = scalechange[i];\n\n  return( TRUE );\n}\n\nSTATIC MYBOOL scale_columns(lprec *lp, REAL *scaledelta)\n{\n  int     i,j, colMax, nz;\n  REAL    *scalechange;\n  REAL    *value;\n  int     *colnr;\n  MATrec  *mat = lp->matA;\n\n  /* Check that columns are in fact targeted */\n  if((lp->scalemode & SCALE_ROWSONLY) != 0)\n    return( TRUE );\n\n  if(scaledelta == NULL)\n    scalechange = &lp->scalars[lp->rows];\n  else\n    scalechange = &scaledelta[lp->rows];\n\n  colMax = lp->columns;\n\n  /* Scale matrix entries (including any Lagrangean constraints) */\n  for(i = 1; i <= lp->columns; i++) {\n    lp->orig_obj[i] *= scalechange[i];\n  }\n\n  mat_validate(lp->matA);\n  nz = get_nonzeros(lp);\n  value = &(COL_MAT_VALUE(0));\n  colnr = &(COL_MAT_COLNR(0));\n  for(i = 0; i < nz;\n      i++, value += matValueStep, colnr += matRowColStep) {\n    (*value) *= scalechange[*colnr];\n  }\n\n  /* Scale variable bounds as well */\n  for(i = 1, j = lp->rows + 1; j <= lp->sum; i++, j++) {\n    if(lp->orig_lowbo[j] > -lp->infinite)\n      lp->orig_lowbo[j] /= scalechange[i];\n    if(lp->orig_upbo[j] < lp->infinite)\n      lp->orig_upbo[j] /= scalechange[i];\n    if(lp->sc_lobound[i] != 0)\n      lp->sc_lobound[i] /= scalechange[i];\n  }\n\n  lp->columns_scaled = TRUE;\n  set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n\n  return( TRUE );\n}\n\nSTATIC MYBOOL scale_rows(lprec *lp, REAL *scaledelta)\n{\n  int     i, j, nz, colMax;\n  REAL    *scalechange;\n  REAL    *value;\n  int     *rownr;\n  MATrec  *mat = lp->matA;\n\n\n  /* Check that rows are in fact targeted */\n  if((lp->scalemode & SCALE_COLSONLY) != 0)\n    return( TRUE );\n\n  if(scaledelta == NULL)\n    scalechange = lp->scalars;\n  else\n    scalechange = scaledelta;\n\n  colMax = lp->columns;\n\n  /* First row-scale the matrix (including the objective function) */\n  for(i = 1; i <= colMax; i++) {\n    lp->orig_obj[i] *= scalechange[0];\n  }\n\n  nz = get_nonzeros(lp);\n  value = &(COL_MAT_VALUE(0));\n  rownr = &(COL_MAT_ROWNR(0));\n  for(i = 0; i < nz;\n      i++, value += matValueStep, rownr += matRowColStep) {\n    (*value) *= scalechange[*rownr];\n  }\n\n  /* ...and scale the rhs and the row bounds (RANGES in MPS!!) */\n  for(i = 0; i <= lp->rows; i++) {\n    if(fabs(lp->orig_rhs[i]) < lp->infinite)\n      lp->orig_rhs[i] *= scalechange[i];\n\n    j = lp->presolve_undo->var_to_orig[i];\n    if(j != 0)\n      lp->presolve_undo->fixed_rhs[j] *= scalechange[i];\n\n    if(lp->orig_upbo[i] < lp->infinite)     /* This is the range */\n      lp->orig_upbo[i] *= scalechange[i];\n\n    if((lp->orig_lowbo[i] != 0) && (fabs(lp->orig_lowbo[i]) < lp->infinite))\n      lp->orig_lowbo[i] *= scalechange[i];\n  }\n\n  set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n\n  return( TRUE );\n}\n\nSTATIC REAL scale(lprec *lp, REAL *scaledelta)\n{\n  int     i, j, nz, row_count, nzOF = 0;\n  REAL    *row_max, *row_min, *scalechange = NULL, absval;\n  REAL    col_max, col_min;\n  MYBOOL  rowscaled, colscaled;\n  MATrec  *mat = lp->matA;\n  REAL    *value;\n  int     *rownr;\n\n  if(is_scaletype(lp, SCALE_NONE))\n    return(0.0);\n\n  if(!lp->scaling_used) {\n    allocREAL(lp, &lp->scalars, lp->sum_alloc + 1, FALSE);\n    for(i = 0; i <= lp->sum; i++) {\n      lp->scalars[i] = 1;\n    }\n    lp->scaling_used = TRUE;\n  }\n#ifdef Paranoia\n  else\n    for(i = 0; i <= lp->sum; i++) {\n      if(lp->scalars[i] == 0)\n        report(lp, SEVERE, \"scale: Zero-valued scalar found at index %d\\n\", i);\n    }\n#endif\n  if(scaledelta == NULL)\n    allocREAL(lp, &scalechange, lp->sum + 1, FALSE);\n  else\n    scalechange = scaledelta;\n\n /* Must initialize due to computation of scaling statistic - KE */\n  for(i = 0; i <= lp->sum; i++)\n    scalechange[i] = 1;\n\n  row_count = lp->rows;\n  allocREAL(lp, &row_max, row_count + 1, TRUE);\n  allocREAL(lp, &row_min, row_count + 1, FALSE);\n\n  /* Initialise min and max values of rows */\n  for(i = 0; i <= row_count; i++) {\n    if(is_scaletype(lp, SCALE_MEAN))\n      row_min[i] = 0;             /* Carries the count of elements */\n    else\n      row_min[i] = lp->infinite;  /* Carries the minimum element */\n  }\n\n  /* Calculate row scaling data */\n  for(j = 1; j <= lp->columns; j++) {\n\n    absval = lp->orig_obj[j];\n    if(absval != 0) {\n      absval = scaled_mat(lp, absval, 0, j);\n      accumulate_for_scale(lp, &row_min[0], &row_max[0], absval);\n      nzOF++;\n    }\n\n    i = mat->col_end[j - 1];\n    value = &(COL_MAT_VALUE(i));\n    rownr = &(COL_MAT_ROWNR(i));\n    nz = mat->col_end[j];\n    for(; i < nz;\n        i++, value += matValueStep, rownr += matRowColStep) {\n      absval = scaled_mat(lp, *value, *rownr, j);\n      accumulate_for_scale(lp, &row_min[*rownr], &row_max[*rownr], absval);\n    }\n  }\n\n  /* Calculate scale factors for rows */\n  i = 0;\n  for(; i <= lp->rows; i++) {\n    if(i == 0)\n      nz = nzOF;\n    else\n      nz = mat_rowlength(lp->matA, i);\n    absval = minmax_to_scale(lp, row_min[i], row_max[i], nz); /* nz instead of nzOF KJEI 20/05/2010 */\n    if(absval == 0)\n      absval = 1;\n    scalechange[i] = absval;\n  }\n\n  FREE(row_max);\n  FREE(row_min);\n\n  /* Row-scale the matrix (including the objective function and Lagrangean constraints) */\n  rowscaled = scale_updaterows(lp, scalechange, TRUE);\n\n  /* Calculate column scales */\n  i = 1;\n  for(j = 1; j <= lp->columns; j++) {\n    if(is_int(lp,j) && !is_integerscaling(lp)) { /* do not scale integer columns */\n      scalechange[lp->rows + j] = 1;\n    }\n    else {\n      col_max = 0;\n      if(is_scaletype(lp, SCALE_MEAN))\n        col_min = 0;\n      else\n        col_min = lp->infinite;\n\n      absval = lp->orig_obj[j];\n      if(absval != 0) {\n        absval = scaled_mat(lp, absval, 0, j);\n        accumulate_for_scale(lp, &col_min, &col_max, absval);\n      }\n\n      i = mat->col_end[j - 1];\n      value = &(COL_MAT_VALUE(i));\n      rownr = &(COL_MAT_ROWNR(i));\n      nz = mat->col_end[j];\n      for(; i < nz;\n          i++, value += matValueStep, rownr += matRowColStep) {\n        absval = scaled_mat(lp, *value, *rownr, j);\n        accumulate_for_scale(lp, &col_min, &col_max, absval);\n      }\n      nz = mat_collength(lp->matA, j);\n      if(fabs(lp->orig_obj[j]) > 0)\n        nz++;\n      scalechange[lp->rows + j] = minmax_to_scale(lp, col_min, col_max, nz);\n    }\n  }\n\n  /* ... and then column-scale the already row-scaled matrix */\n  colscaled = scale_updatecolumns(lp, &scalechange[lp->rows], TRUE);\n\n  /* Create a geometric mean-type measure of the extent of scaling performed; */\n  /* ideally, upon successive calls to scale() the value should converge to 0 */\n  if(rowscaled || colscaled) {\n    col_max = 0;\n    for(j = 1; j <= lp->columns; j++)\n      col_max += log(scalechange[lp->rows + j]);\n    col_max = exp(col_max/lp->columns);\n\n    i = 0;\n    col_min = 0;\n    for(; i <= lp->rows; i++)\n      col_min += log(scalechange[i]);\n    col_min = exp(col_min/row_count);\n  }\n  else {\n    col_max = 1;\n    col_min = 1;\n  }\n\n  if(scaledelta == NULL)\n    FREE(scalechange);\n\n  return(1 - sqrt(col_max*col_min));\n}\n\nSTATIC MYBOOL finalize_scaling(lprec *lp, REAL *scaledelta)\n{\n  int i;\n\n  /* Check if we should equilibrate */\n  if(is_scalemode(lp, SCALE_EQUILIBRATE) && !is_scaletype(lp, SCALE_CURTISREID)) {\n    int oldmode;\n\n    oldmode = lp->scalemode;\n    lp->scalemode = SCALE_LINEAR + SCALE_EXTREME;\n    scale(lp, scaledelta);\n    lp->scalemode = oldmode;\n  }\n\n  /* Check if we should prevent rounding errors */\n  if(is_scalemode(lp, SCALE_POWER2)) {\n    REAL *scalars;\n    if(scaledelta == NULL)\n      scalars = lp->scalars;\n    else\n      scalars = scaledelta;\n\n    for(i = 0; i <= lp->sum; i++)\n      scalars[i] = roundPower2(scalars[i]);\n  }\n\n  /* Then transfer the scalars to the model's data */\n  return( scale_rows(lp, scaledelta) && scale_columns(lp, scaledelta) );\n\n}\n\nSTATIC REAL auto_scale(lprec *lp)\n{\n  int    n = 1;\n  REAL   scalingmetric = 0, *scalenew = NULL;\n\n  if(lp->scaling_used &&\n     ((((lp->scalemode & SCALE_DYNUPDATE) == 0)) || (lp->bb_level > 0)))\n    return( scalingmetric);\n\n  if(lp->scalemode != SCALE_NONE) {\n\n    /* Allocate array for incremental scaling if appropriate */\n    if((lp->solvecount > 1) && (lp->bb_level < 1) &&\n       ((lp->scalemode & SCALE_DYNUPDATE) != 0))\n      allocREAL(lp, &scalenew, lp->sum + 1, FALSE);\n\n    if(is_scaletype(lp, SCALE_CURTISREID)) {\n      scalingmetric = scaleCR(lp, scalenew);\n    }\n    else {\n      REAL scalinglimit, scalingdelta;\n      int  count;\n\n      /* Integer value of scalelimit holds the maximum number of iterations; default to 1 */\n      count = (int) floor(lp->scalelimit);\n      scalinglimit = lp->scalelimit;\n      if((count == 0) || (scalinglimit == 0)) {\n        if(scalinglimit > 0)\n          count = DEF_SCALINGLIMIT;  /* A non-zero convergence has been given, default to max 5 iterations */\n        else\n          count = 1;\n      }\n      else\n        scalinglimit -= count;\n\n      /* Scale to desired relative convergence or iteration limit */\n      n = 0;\n      scalingdelta = 1.0;\n      scalingmetric = 1.0;\n      while((n < count) && (fabs(scalingdelta) > scalinglimit)) {\n        n++;\n        scalingdelta = scale(lp, scalenew);\n        scalingmetric = scalingmetric*(1+scalingdelta);\n      }\n      scalingmetric -= 1;\n    }\n  }\n\n  /* Update the inf norm of the elements of the matrix (excluding the OF) */\n  mat_computemax(lp->matA);\n\n  /* Check if we really have to do scaling */\n  if(lp->scaling_used && (fabs(scalingmetric) >= lp->epsprimal))\n    /* Ok, do it */\n    finalize_scaling(lp, scalenew);\n\n  else {\n\n    /* Otherwise reset scaling variables */\n    if(lp->scalars != NULL) {\n      FREE(lp->scalars);\n    }\n    lp->scaling_used = FALSE;\n    lp->columns_scaled = FALSE;\n  }\n  if(scalenew != NULL)\n    FREE(scalenew);\n\n  return(scalingmetric);\n}\n\nSTATIC void unscale_columns(lprec *lp)\n{\n  int     i, j, nz;\n  MATrec  *mat = lp->matA;\n  REAL    *value;\n  int     *rownr, *colnr;\n\n  if(!lp->columns_scaled)\n    return;\n\n  /* Unscale OF */\n  for(j = 1; j <= lp->columns; j++) {\n    lp->orig_obj[j] = unscaled_mat(lp, lp->orig_obj[j], 0, j);\n  }\n\n  /* Unscale mat */\n  mat_validate(mat);\n  nz = get_nonzeros(lp);\n  value = &(COL_MAT_VALUE(0));\n  rownr = &(COL_MAT_ROWNR(0));\n  colnr = &(COL_MAT_COLNR(0));\n  for(j = 0; j < nz;\n      j++, value += matValueStep, rownr += matRowColStep, colnr += matRowColStep) {\n    *value = unscaled_mat(lp, *value, *rownr, *colnr);\n  }\n\n  /* Unscale bounds as well */\n  for(i = lp->rows + 1, j = 1; i <= lp->sum; i++, j++) {\n    lp->orig_lowbo[i] = unscaled_value(lp, lp->orig_lowbo[i], i);\n    lp->orig_upbo[i]  = unscaled_value(lp, lp->orig_upbo[i], i);\n    lp->sc_lobound[j]  = unscaled_value(lp, lp->sc_lobound[j], i);\n  }\n\n  for(i = lp->rows + 1; i<= lp->sum; i++)\n    lp->scalars[i] = 1;\n\n  lp->columns_scaled = FALSE;\n  set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n}\n\nvoid undoscale(lprec *lp)\n{\n  int     i, j, nz;\n  MATrec  *mat = lp->matA;\n  REAL    *value;\n  int     *rownr, *colnr;\n\n  if(lp->scaling_used) {\n\n    /* Unscale the OF */\n    for(j = 1; j <= lp->columns; j++) {\n      lp->orig_obj[j] = unscaled_mat(lp, lp->orig_obj[j], 0, j);\n    }\n\n    /* Unscale the matrix */\n    mat_validate(mat);\n    nz = get_nonzeros(lp);\n    value = &(COL_MAT_VALUE(0));\n    rownr = &(COL_MAT_ROWNR(0));\n    colnr = &(COL_MAT_COLNR(0));\n    for(j = 0; j < nz;\n        j++, value += matValueStep, rownr += matRowColStep, colnr += matRowColStep) {\n      *value = unscaled_mat(lp, *value, *rownr, *colnr);\n    }\n\n    /* Unscale variable bounds */\n    for(i = lp->rows + 1, j = 1; i <= lp->sum; i++, j++) {\n      lp->orig_lowbo[i] = unscaled_value(lp, lp->orig_lowbo[i], i);\n      lp->orig_upbo[i]  = unscaled_value(lp, lp->orig_upbo[i], i);\n      lp->sc_lobound[j]  = unscaled_value(lp, lp->sc_lobound[j], i);\n    }\n\n    /* Unscale the rhs, upper and lower bounds... */\n    for(i = 0; i <= lp->rows; i++) {\n      lp->orig_rhs[i] = unscaled_value(lp, lp->orig_rhs[i], i);\n      j = lp->presolve_undo->var_to_orig[i];\n      if(j != 0)\n        lp->presolve_undo->fixed_rhs[j] = unscaled_value(lp, lp->presolve_undo->fixed_rhs[j], i);\n      lp->orig_lowbo[i] = unscaled_value(lp, lp->orig_lowbo[i], i);\n      lp->orig_upbo[i] = unscaled_value(lp, lp->orig_upbo[i], i);\n    }\n\n    FREE(lp->scalars);\n    lp->scaling_used = FALSE;\n    lp->columns_scaled = FALSE;\n\n    set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT | ACTION_RECOMPUTE);\n  }\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_scale.h",
    "content": "#ifndef HEADER_lp_scale\n#define HEADER_lp_scale\n\n#include \"lp_types.h\"\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\nSTATIC MYBOOL scale_updatecolumns(lprec *lp, REAL *scalechange, MYBOOL updateonly);\nSTATIC MYBOOL scale_updaterows(lprec *lp, REAL *scalechange, MYBOOL updateonly);\nSTATIC MYBOOL scale_rows(lprec *lp, REAL *scaledelta);\nSTATIC MYBOOL scale_columns(lprec *lp, REAL *scaledelta);\nSTATIC void unscale_columns(lprec *lp);\nSTATIC REAL scale(lprec *lp, REAL *scaledelta);\nSTATIC REAL scaled_mat(lprec *lp, REAL value, int rownr, int colnr);\nSTATIC REAL unscaled_mat(lprec *lp, REAL value, int rownr, int colnr);\nSTATIC REAL scaled_value(lprec *lp, REAL value, int index);\nSTATIC REAL unscaled_value(lprec *lp, REAL value, int index);\nSTATIC MYBOOL scaleCR(lprec *lp, REAL *scaledelta);\nSTATIC MYBOOL finalize_scaling(lprec *lp, REAL *scaledelta);\nSTATIC REAL auto_scale(lprec *lp);\nvoid undoscale(lprec *lp);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_scale */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_simplex.c",
    "content": "\n/*\n    Core optimization drivers for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Michel Berkelaar (to lp_solve v3.2),\n                   Kjell Eikland    (v4.0 and forward)\n    Contact:\n    License terms: LGPL.\n\n    Requires:      lp_lib.h, lp_simplex.h, lp_presolve.h, lp_pricerPSE.h\n\n    Release notes:\n    v5.0.0  1 January 2004      New unit applying stacked basis and bounds storage.\n    v5.0.1 31 January 2004      Moved B&B routines to separate file and implemented\n                                a new runsolver() general purpose call method.\n    v5.0.2  1 May 2004          Changed routine names to be more intuitive.\n    v5.1.0  10 January 2005     Created modular stalling/cycling functions.\n                                Rewrote dualloop() to optimize long dual and\n                                also streamlined primloop() correspondingly.\n    v5.2.0  20 March 2005       Reimplemented primal phase 1 logic.\n                                Made multiple pricing finally work (primal simplex).\n\n   ----------------------------------------------------------------------------------\n*/\n\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_BFP.h\"\n#include \"lp_simplex.h\"\n#include \"lp_crash.h\"\n#include \"lp_presolve.h\"\n#include \"lp_price.h\"\n#include \"lp_pricePSE.h\"\n#include \"lp_report.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\nSTATIC void stallMonitor_update(lprec *lp, REAL newOF)\n{\n  int newpos;\n  OBJmonrec *monitor = lp->monitor;\n\n  if(monitor->countstep < OBJ_STEPS)\n    monitor->countstep++;\n  else\n    monitor->startstep = mod(monitor->startstep + 1, OBJ_STEPS);\n  newpos = mod(monitor->startstep + monitor->countstep - 1, OBJ_STEPS);\n  monitor->objstep[newpos] = newOF;\n  monitor->idxstep[newpos] = monitor->Icount;\n  monitor->currentstep = newpos;\n}\n\nSTATIC MYBOOL stallMonitor_creepingObj(lprec *lp)\n{\n  OBJmonrec *monitor = lp->monitor;\n\n  if(monitor->countstep > 1) {\n    REAL deltaOF = (monitor->objstep[monitor->currentstep] -\n                    monitor->objstep[monitor->startstep]) / monitor->countstep;\n    deltaOF /= MAX(1, (monitor->idxstep[monitor->currentstep] -\n                       monitor->idxstep[monitor->startstep]));\n    deltaOF = my_chsign(monitor->isdual, deltaOF);\n    return( (MYBOOL) (deltaOF < monitor->epsvalue) );\n  }\n  else\n    return( FALSE );\n}\n\nSTATIC MYBOOL stallMonitor_shortSteps(lprec *lp)\n{\n  OBJmonrec *monitor = lp->monitor;\n\n  if(monitor->countstep == OBJ_STEPS) {\n    REAL deltaOF = MAX(1, (monitor->idxstep[monitor->currentstep] -\n                           monitor->idxstep[monitor->startstep])) / monitor->countstep;\n    deltaOF = pow(deltaOF*OBJ_STEPS, 0.66);\n    return( (MYBOOL) (deltaOF > monitor->limitstall[TRUE]) );\n  }\n  else\n    return( FALSE );\n}\n\nSTATIC void stallMonitor_reset(lprec *lp)\n{\n  OBJmonrec *monitor = lp->monitor;\n\n  monitor->ruleswitches = 0;\n  monitor->Ncycle = 0;\n  monitor->Mcycle = 0;\n  monitor->Icount = 0;\n  monitor->startstep = 0;\n  monitor->objstep[monitor->startstep] = lp->infinite;\n  monitor->idxstep[monitor->startstep] = monitor->Icount;\n  monitor->prevobj = 0;\n  monitor->countstep = 1;\n}\n\nSTATIC MYBOOL stallMonitor_create(lprec *lp, MYBOOL isdual, char *funcname)\n{\n  OBJmonrec *monitor = NULL;\n  if(lp->monitor != NULL)\n    return( FALSE );\n\n  monitor = (OBJmonrec *) calloc(sizeof(*monitor), 1);\n  if(monitor == NULL)\n    return( FALSE );\n\n  monitor->lp = lp;\n  strcpy(monitor->spxfunc, funcname);\n  monitor->isdual = isdual;\n  monitor->pivdynamic = is_piv_mode(lp, PRICE_ADAPTIVE);\n  monitor->oldpivstrategy = lp->piv_strategy;\n  monitor->oldpivrule = get_piv_rule(lp);\n  if(MAX_STALLCOUNT <= 1)\n    monitor->limitstall[FALSE] = 0;\n  else\n    monitor->limitstall[FALSE] = MAX(MAX_STALLCOUNT,\n                                     (int) pow((REAL) (lp->rows+lp->columns)/2, 0.667));\n#if 1\n  monitor->limitstall[FALSE] *= 2+2;  /* Expand degeneracy/stalling tolerance range */\n#endif\n  monitor->limitstall[TRUE] = monitor->limitstall[FALSE];\n  if(monitor->oldpivrule == PRICER_DEVEX) /* Increase tolerance since primal Steepest Edge is expensive */\n    monitor->limitstall[TRUE] *= 2;\n  if(MAX_RULESWITCH <= 0)\n    monitor->limitruleswitches = MAXINT32;\n  else\n    monitor->limitruleswitches = MAX(MAX_RULESWITCH,\n                                     lp->rows/MAX_RULESWITCH);\n  monitor->epsvalue = lp->epsprimal; /* lp->epsvalue; */\n  lp->monitor = monitor;\n  stallMonitor_reset(lp);\n  lp->suminfeas = lp->infinite;\n  return( TRUE );\n}\n\nSTATIC MYBOOL stallMonitor_check(lprec *lp, int rownr, int colnr, int lastnr,\n                                 MYBOOL minit, MYBOOL approved, MYBOOL *forceoutEQ)\n{\n  OBJmonrec *monitor = lp->monitor;\n  MYBOOL    isStalled, isCreeping, acceptance = TRUE;\n  int       altrule,\n#ifdef Paranoia\n         msglevel = NORMAL;\n#else\n         msglevel = DETAILED;\n#endif\n  REAL   deltaobj = lp->suminfeas;\n\n  /* Accept unconditionally if this is the first or second call */\n  monitor->active = FALSE;\n  if(monitor->Icount <= 1) {\n    if(monitor->Icount == 1) {\n      monitor->prevobj = lp->rhs[0];\n      monitor->previnfeas = deltaobj;\n    }\n    monitor->Icount++;\n    return( acceptance );\n  }\n\n  /* Define progress as primal objective less sum of (primal/dual) infeasibilities */\n  monitor->thisobj = lp->rhs[0];\n  monitor->thisinfeas = deltaobj;\n  if(lp->spx_trace &&\n     (lastnr > 0))\n    report(lp, NORMAL, \"%s: Objective at iter %10.0f is \" RESULTVALUEMASK \" (%4d: %4d %s- %4d)\\n\",\n                       monitor->spxfunc,\n                       (double) get_total_iter(lp), monitor->thisobj, rownr, lastnr,\n                       my_if(minit == ITERATE_MAJORMAJOR, \"<\",\"|\"), colnr);\n  monitor->pivrule = get_piv_rule(lp);\n\n  /* Check if we have a stationary solution at selected tolerance level;\n     allow some difference in case we just refactorized the basis. */\n  deltaobj = my_reldiff(monitor->thisobj, monitor->prevobj);\n  deltaobj = fabs(deltaobj); /* Pre v5.2 version */\n  isStalled = (MYBOOL) (deltaobj < monitor->epsvalue);\n\n  /* Also require that we have a measure of infeasibility-stalling */\n  if(isStalled) {\n    REAL testvalue, refvalue = monitor->epsvalue;\n#if 1\n    if(monitor->isdual)\n      refvalue *= 1000*log10(9.0+lp->rows);\n    else\n      refvalue *= 1000*log10(9.0+lp->columns);\n#else\n      refvalue *= 1000*log10(9.0+lp->sum);\n#endif\n    testvalue = my_reldiff(monitor->thisinfeas, monitor->previnfeas);\n    isStalled &= (fabs(testvalue) < refvalue);\n\n    /* Check if we should force \"major\" pivoting, i.e. no bound flips;\n      this is activated when we see the feasibility deteriorate */\n/*    if(!isStalled && (testvalue > 0) && (TRUE || is_action(lp->anti_degen, ANTIDEGEN_BOUNDFLIP))) */\n#if !defined _PRICE_NOBOUNDFLIP\n    if(!isStalled && (testvalue > 0) && is_action(lp->anti_degen, ANTIDEGEN_BOUNDFLIP))\n      acceptance = AUTOMATIC;\n  }\n#else\n    if(!isStalled && (testvalue > 0) && !ISMASKSET(lp->piv_strategy, PRICE_NOBOUNDFLIP)) {\n      SETMASK(lp->piv_strategy, PRICE_NOBOUNDFLIP);\n      acceptance = AUTOMATIC;\n    }\n  }\n  else\n    CLEARMASK(lp->piv_strategy, PRICE_NOBOUNDFLIP);\n#endif\n\n#if 1\n  isCreeping = FALSE;\n#else\n  isCreeping |= stallMonitor_creepingObj(lp);\n/*  isCreeping |= stallMonitor_shortSteps(lp); */\n#endif\n  if(isStalled || isCreeping) {\n\n    /* Update counters along with specific tolerance for bound flips */\n#if 1\n    if(minit != ITERATE_MAJORMAJOR) {\n      if(++monitor->Mcycle > 2) {\n        monitor->Mcycle = 0;\n        monitor->Ncycle++;\n      }\n    }\n    else\n#endif\n      monitor->Ncycle++;\n\n    /* Start to monitor for variable cycling if this is the initial stationarity */\n    if(monitor->Ncycle <= 1) {\n      monitor->Ccycle = colnr;\n      monitor->Rcycle = rownr;\n    }\n\n    /* Check if we should change pivoting strategy */\n    else if(isCreeping ||                                                 /* We have OF creep */\n            (monitor->Ncycle > monitor->limitstall[monitor->isdual]) ||   /* KE empirical value */\n            ((monitor->Ccycle == rownr) && (monitor->Rcycle == colnr))) {   /* Obvious cycling */\n\n      monitor->active = TRUE;\n\n      /* Try to force out equality slacks to combat degeneracy */\n      if((lp->fixedvars > 0) && (*forceoutEQ != TRUE)) {\n        *forceoutEQ = TRUE;\n        goto Proceed;\n      }\n\n      /* Our options are now to select an alternative rule or to do bound perturbation;\n         check if these options are available to us or if we must signal failure and break out. */\n      approved &= monitor->pivdynamic && (monitor->ruleswitches < monitor->limitruleswitches);\n      if(!approved && !is_anti_degen(lp, ANTIDEGEN_STALLING)) {\n        lp->spx_status = DEGENERATE;\n        report(lp, msglevel, \"%s: Stalling at iter %10.0f; no alternative strategy left.\\n\",\n                             monitor->spxfunc, (double) get_total_iter(lp));\n        acceptance = FALSE;\n        return( acceptance );\n      }\n\n      /* See if we can do the appropriate alternative rule. */\n      switch (monitor->oldpivrule) {\n        case PRICER_FIRSTINDEX:    altrule = PRICER_DEVEX;\n                                   break;\n        case PRICER_DANTZIG:       altrule = PRICER_DEVEX;\n                                   break;\n        case PRICER_DEVEX:         altrule = PRICER_STEEPESTEDGE;\n                                   break;\n        case PRICER_STEEPESTEDGE:  altrule = PRICER_DEVEX;\n                                   break;\n        default:                   altrule = PRICER_FIRSTINDEX;\n      }\n      if(approved &&\n         (monitor->pivrule != altrule) && (monitor->pivrule == monitor->oldpivrule)) {\n\n        /* Switch rule to combat degeneracy. */\n        monitor->ruleswitches++;\n        lp->piv_strategy = altrule;\n        monitor->Ccycle = 0;\n        monitor->Rcycle = 0;\n        monitor->Ncycle = 0;\n        monitor->Mcycle = 0;\n        report(lp, msglevel, \"%s: Stalling at iter %10.0f; changed to '%s' rule.\\n\",\n                             monitor->spxfunc, (double) get_total_iter(lp),\n                             get_str_piv_rule(get_piv_rule(lp)));\n        if((altrule == PRICER_DEVEX) || (altrule == PRICER_STEEPESTEDGE))\n          restartPricer(lp, AUTOMATIC);\n      }\n\n      /* If not, code for bound relaxation/perturbation */\n      else {\n        report(lp, msglevel, \"%s: Stalling at iter %10.0f; proceed to bound relaxation.\\n\",\n                             monitor->spxfunc, (double) get_total_iter(lp));\n        acceptance = FALSE;\n        lp->spx_status = DEGENERATE;\n        return( acceptance );\n      }\n    }\n  }\n\n  /* Otherwise change back to original selection strategy as soon as possible */\n  else {\n    if(monitor->pivrule != monitor->oldpivrule) {\n      lp->piv_strategy = monitor->oldpivstrategy;\n      altrule = monitor->oldpivrule;\n      if((altrule == PRICER_DEVEX) || (altrule == PRICER_STEEPESTEDGE))\n        restartPricer(lp, AUTOMATIC);\n      report(lp, msglevel, \"...returned to original pivot selection rule at iter %.0f.\\n\",\n                           (double) get_total_iter(lp));\n    }\n    stallMonitor_update(lp, monitor->thisobj);\n    monitor->Ccycle = 0;\n    monitor->Rcycle = 0;\n    monitor->Ncycle = 0;\n    monitor->Mcycle = 0;\n  }\n\n  /* Update objective progress tracker */\nProceed:\n  monitor->Icount++;\n  if(deltaobj >= monitor->epsvalue)\n    monitor->prevobj = monitor->thisobj;\n  monitor->previnfeas = monitor->thisinfeas;\n\n  return( acceptance );\n}\n\nSTATIC void stallMonitor_finish(lprec *lp)\n{\n  OBJmonrec *monitor = lp->monitor;\n  if(monitor == NULL)\n    return;\n  if(lp->piv_strategy != monitor->oldpivstrategy)\n    lp->piv_strategy = monitor->oldpivstrategy;\n  FREE(monitor);\n  lp->monitor = NULL;\n}\n\n\nSTATIC MYBOOL add_artificial(lprec *lp, int forrownr, REAL *nzarray, int *idxarray)\n/* This routine is called for each constraint at the start of\n   primloop and the primal problem is infeasible. Its\n   purpose is to add artificial variables and associated\n   objective function values to populate primal phase 1. */\n{\n  MYBOOL add;\n\n  /* Make sure we don't add unnecessary artificials, i.e. avoid\n     cases where the slack variable is enough */\n  add = !isBasisVarFeasible(lp, lp->epspivot, forrownr);\n\n  if(add) {\n    int    *rownr = NULL, i, bvar, ii;\n    REAL   *avalue = NULL, rhscoef, acoef;\n    MATrec *mat = lp->matA;\n\n    /* Check the simple case where a slack is basic */\n    for(i = 1; i <= lp->rows; i++) {\n      if(lp->var_basic[i] == forrownr)\n        break;\n    }\n    acoef = 1;\n\n    /* If not, look for any basic user variable that has a\n       non-zero coefficient in the current constraint row */\n    if(i > lp->rows) {\n      for(i = 1; i <= lp->rows; i++) {\n        ii = lp->var_basic[i] - lp->rows;\n        if((ii <= 0) || (ii > (lp->columns-lp->P1extraDim)))\n          continue;\n        ii = mat_findelm(mat, forrownr, ii);\n        if(ii >= 0) {\n          acoef = COL_MAT_VALUE(ii);\n          break;\n        }\n      }\n    }\n\n    /* If no candidate was found above, gamble on using the densest column available */\n#if 0\n    if(i > lp->rows) {\n      int len = 0;\n      bvar = 0;\n      for(i = 1; i <= lp->rows; i++) {\n        ii = lp->var_basic[i] - lp->rows;\n        if((ii <= 0) || (ii > (lp->columns-lp->P1extraDim)))\n          continue;\n        if(mat_collength(mat, ii) > len) {\n          len = mat_collength(mat, ii);\n          bvar = i;\n        }\n      }\n      i = bvar;\n      acoef = 1;\n    }\n#endif\n\n    bvar = i;\n\n    add = (MYBOOL) (bvar <= lp->rows);\n    if(add) {\n      rhscoef = lp->rhs[forrownr];\n\n     /* Create temporary sparse array storage */\n      if(nzarray == NULL)\n        allocREAL(lp, &avalue, 2, FALSE);\n      else\n        avalue = nzarray;\n      if(idxarray == NULL)\n        allocINT(lp, &rownr, 2, FALSE);\n      else\n        rownr = idxarray;\n\n     /* Set the objective coefficient */\n      rownr[0]  =  0;\n      avalue[0] = my_chsign(is_chsign(lp, 0), 1);\n\n     /* Set the constraint row coefficient */\n      rownr[1]  = forrownr;\n      avalue[1] = my_chsign(is_chsign(lp, forrownr), my_sign(rhscoef/acoef));\n\n     /* Add the column of artificial variable data to the user data matrix */\n      add_columnex(lp, 2, avalue, rownr);\n\n     /* Free the temporary sparse array storage */\n      if(idxarray == NULL)\n        FREE(rownr);\n      if(nzarray == NULL)\n        FREE(avalue);\n\n     /* Now set the artificial variable to be basic */\n      set_basisvar(lp, bvar, lp->sum);\n      lp->P1extraDim++;\n    }\n    else {\n      report(lp, CRITICAL, \"add_artificial: Could not find replacement basis variable for row %d\\n\",\n                           forrownr);\n      lp->basis_valid = FALSE;\n    }\n\n  }\n\n  return(add);\n\n}\n\nSTATIC int get_artificialRow(lprec *lp, int colnr)\n{\n  MATrec *mat = lp->matA;\n\n#ifdef Paranoia\n  if((colnr <= lp->columns-abs(lp->P1extraDim)) || (colnr > lp->columns))\n    report(lp, SEVERE, \"get_artificialRow: Invalid column index %d\\n\", colnr);\n  if(mat->col_end[colnr] - mat->col_end[colnr-1] != 1)\n    report(lp, SEVERE, \"get_artificialRow: Invalid column non-zero count\\n\");\n#endif\n\n  /* Return the row index of the singleton */\n  colnr = mat->col_end[colnr-1];\n  colnr = COL_MAT_ROWNR(colnr);\n  return( colnr );\n}\n\nSTATIC int findAnti_artificial(lprec *lp, int colnr)\n/* Primal simplex: Find a basic artificial variable to swap\n   against the non-basic slack variable, if possible */\n{\n  int    i, k, rownr = 0, P1extraDim = abs(lp->P1extraDim);\n\n  if((P1extraDim == 0) || (colnr > lp->rows) || !lp->is_basic[colnr])\n    return( rownr );\n\n  for(i = 1; i <= lp->rows; i++) {\n    k = lp->var_basic[i];\n    if((k > lp->sum-P1extraDim) && (lp->rhs[i] == 0)) {\n      rownr = get_artificialRow(lp, k-lp->rows);\n\n      /* Should we find the artificial's slack direct \"antibody\"? */\n      if(rownr == colnr)\n        break;\n      rownr = 0;\n    }\n  }\n  return( rownr );\n}\n\nSTATIC int findBasicArtificial(lprec *lp, int before)\n{\n  int i = 0, P1extraDim = abs(lp->P1extraDim);\n\n  if(P1extraDim > 0) {\n    if(before > lp->rows || before <= 1)\n      i = lp->rows;\n    else\n      i = before;\n\n    while((i > 0) && (lp->var_basic[i] <= lp->sum-P1extraDim))\n      i--;\n  }\n\n  return(i);\n}\n\nSTATIC void eliminate_artificials(lprec *lp, REAL *prow)\n{\n  int   i, j, colnr, rownr, P1extraDim = abs(lp->P1extraDim);\n\n  for(i = 1; (i <= lp->rows) && (P1extraDim > 0); i++) {\n    j = lp->var_basic[i];\n    if(j <= lp->sum-P1extraDim)\n      continue;\n    j -= lp->rows;\n    rownr = get_artificialRow(lp, j);\n    colnr = find_rowReplacement(lp, rownr, prow, NULL);\n#if 0\n    performiteration(lp, rownr, colnr, 0.0, TRUE, FALSE, prow, NULL,\n                                                          NULL, NULL, NULL);\n#else\n    set_basisvar(lp, rownr, colnr);\n#endif\n    del_column(lp, j);\n    P1extraDim--;\n  }\n  lp->P1extraDim = 0;\n}\n\nSTATIC void clear_artificials(lprec *lp)\n{\n  int i, j, n, P1extraDim;\n\n  /* Substitute any basic artificial variable for its slack counterpart */\n  n = 0;\n  P1extraDim = abs(lp->P1extraDim);\n  for(i = 1; (i <= lp->rows) && (n < P1extraDim); i++) {\n    j = lp->var_basic[i];\n    if(j <= lp->sum-P1extraDim)\n      continue;\n    j = get_artificialRow(lp, j-lp->rows);\n    set_basisvar(lp, i, j);\n    n++;\n  }\n#ifdef Paranoia\n  if(n != lp->P1extraDim)\n    report(lp, SEVERE, \"clear_artificials: Unable to clear all basic artificial variables\\n\");\n#endif\n\n  /* Delete any remaining non-basic artificial variables */\n  while(P1extraDim > 0) {\n    i = lp->sum-lp->rows;\n    del_column(lp, i);\n    P1extraDim--;\n  }\n  lp->P1extraDim = 0;\n  if(n > 0) {\n    set_action(&lp->spx_action, ACTION_REINVERT);\n    lp->basis_valid = TRUE;\n  }\n}\n\n\nSTATIC int primloop(lprec *lp, MYBOOL primalfeasible, REAL primaloffset)\n{\n  MYBOOL primal = TRUE, bfpfinal = FALSE, changedphase = FALSE, forceoutEQ = AUTOMATIC,\n         primalphase1, pricerCanChange, minit, stallaccept, pendingunbounded;\n  int    i, j, k, colnr = 0, rownr = 0, lastnr = 0,\n         candidatecount = 0, minitcount = 0, ok = TRUE;\n  LREAL  theta = 0.0;\n  REAL   epsvalue, xviolated = 0.0, cviolated = 0.0,\n         *prow = NULL, *pcol = NULL,\n         *drow = lp->drow;\n  int    *workINT = NULL,\n         *nzdrow = lp->nzdrow;\n\n  if(lp->spx_trace)\n    report(lp, DETAILED, \"Entered primal simplex algorithm with feasibility %s\\n\",\n                         my_boolstr(primalfeasible));\n\n /* Add sufficent number of artificial variables to make the problem feasible\n    through the first phase; delete when primal feasibility has been achieved */\n  lp->P1extraDim = 0;\n  if(!primalfeasible) {\n    lp->simplex_mode = SIMPLEX_Phase1_PRIMAL;\n#ifdef Paranoia\n    if(!verify_basis(lp))\n      report(lp, SEVERE, \"primloop: No valid basis for artificial variables\\n\");\n#endif\n#if 0\n    /* First check if we can get away with a single artificial variable */\n    if(lp->equalities == 0) {\n      i = (int) feasibilityOffset(lp, !primal);\n      add_artificial(lp, i, prow, (int *) pcol);\n    }\n    else\n#endif\n    /* Otherwise add as many artificial variables as is necessary\n       to force primal feasibility. */\n      for(i = 1; i <= lp->rows; i++) {\n        add_artificial(lp, i, NULL, NULL);\n      }\n\n    /* Make sure we update the working objective */\n    if(lp->P1extraDim > 0) {\n#if 1 /* v5.1 code: Not really necessary since we do not price the artificial\n        variables (stored at the end of the column list, they are initially\n        basic and are never allowed to enter the basis, once they exit) */\n      ok = allocREAL(lp, &(lp->drow), lp->sum+1, AUTOMATIC) &&\n           allocINT(lp, &(lp->nzdrow), lp->sum+1, AUTOMATIC);\n      if(!ok)\n        goto Finish;\n      lp->nzdrow[0] = 0;\n      drow = lp->drow;\n      nzdrow = lp->nzdrow;\n#endif\n      mat_validate(lp->matA);\n      set_OF_p1extra(lp, 0.0);\n    }\n    if(lp->spx_trace)\n      report(lp, DETAILED, \"P1extraDim count = %d\\n\", lp->P1extraDim);\n\n    simplexPricer(lp, (MYBOOL)!primal);\n    invert(lp, INITSOL_USEZERO, TRUE);\n  }\n  else {\n    lp->simplex_mode = SIMPLEX_Phase2_PRIMAL;\n    restartPricer(lp, (MYBOOL)!primal);\n  }\n\n  /* Create work arrays and optionally the multiple pricing structure */\n  ok = allocREAL(lp, &(lp->bsolveVal), lp->rows + 1, FALSE) &&\n       allocREAL(lp, &prow, lp->sum + 1, TRUE) &&\n       allocREAL(lp, &pcol, lp->rows + 1, TRUE);\n  if(is_piv_mode(lp, PRICE_MULTIPLE) && (lp->multiblockdiv > 1)) {\n    lp->multivars = multi_create(lp, FALSE);\n    ok &= (lp->multivars != NULL) &&\n          multi_resize(lp->multivars, lp->sum / lp->multiblockdiv, 2, FALSE, TRUE);\n  }\n  if(!ok)\n    goto Finish;\n\n  /* Initialize regular primal simplex algorithm variables */\n  lp->spx_status = RUNNING;\n  minit = ITERATE_MAJORMAJOR;\n  epsvalue = lp->epspivot;\n  pendingunbounded = FALSE;\n\n  ok = stallMonitor_create(lp, FALSE, \"primloop\");\n  if(!ok)\n    goto Finish;\n\n  lp->rejectpivot[0] = 0;\n\n /* Iterate while we are successful; exit when the model is infeasible/unbounded,\n    or we must terminate due to numeric instability or user-determined reasons */\n  while((lp->spx_status == RUNNING) && !userabort(lp, -1)) {\n\n    primalphase1 = (MYBOOL) (lp->P1extraDim > 0);\n    clear_action(&lp->spx_action, ACTION_REINVERT | ACTION_ITERATE);\n\n    /* Check if we have stalling (from numerics or degenerate cycling) */\n    pricerCanChange = !primalphase1;\n    stallaccept = stallMonitor_check(lp, rownr, colnr, lastnr, minit, pricerCanChange, &forceoutEQ);\n    if(!stallaccept)\n      break;\n\n   /* Find best column to enter the basis */\nRetryCol:\n#if 0\n    if(verify_solution(lp, FALSE, \"spx_loop\") > 0)\n      i = 1; /* This is just a debug trap */\n#endif\n    if(!changedphase) {\n      i = 0;\n      do {\n        i++;\n        colnr = colprim(lp, drow, nzdrow, (MYBOOL) (minit == ITERATE_MINORRETRY), i, &candidatecount, TRUE, &xviolated);\n      } while ((colnr == 0) && (i < partial_countBlocks(lp, (MYBOOL) !primal)) &&\n                                partial_blockStep(lp, (MYBOOL) !primal));\n\n      /* Handle direct outcomes */\n      if(colnr == 0)\n        lp->spx_status = OPTIMAL;\n      if(lp->rejectpivot[0] > 0)\n        minit = ITERATE_MAJORMAJOR;\n\n      /* See if accuracy check during compute_reducedcosts flagged refactorization */\n      if(is_action(lp->spx_action, ACTION_REINVERT))\n        bfpfinal = TRUE;\n\n    }\n\n    /* Make sure that we do not erroneously conclude that an unbounded model is optimal */\n#ifdef primal_UseRejectionList\n    if((colnr == 0) && (lp->rejectpivot[0] > 0)) {\n      lp->spx_status = UNBOUNDED;\n      if((lp->spx_trace && (lp->bb_totalnodes == 0)) ||\n         (lp->bb_trace && (lp->bb_totalnodes > 0)))\n        report(lp, DETAILED, \"The model is primal unbounded.\\n\");\n      colnr = lp->rejectpivot[1];\n      rownr = 0;\n      lp->rejectpivot[0] = 0;\n      ok = FALSE;\n      break;\n    }\n#endif\n\n    /* Check if we found an entering variable (indicating that we are still dual infeasible) */\n    if(colnr > 0) {\n      changedphase = FALSE;\n      fsolve(lp, colnr, pcol, NULL, lp->epsmachine, 1.0, TRUE);  /* Solve entering column for Pi */\n\n      /* Do special anti-degeneracy column selection, if specified */\n      if(is_anti_degen(lp, ANTIDEGEN_COLUMNCHECK) && !check_degeneracy(lp, pcol, NULL)) {\n        if(lp->rejectpivot[0] < DEF_MAXPIVOTRETRY/3) {\n          i = ++lp->rejectpivot[0];\n          lp->rejectpivot[i] = colnr;\n          report(lp, DETAILED, \"Entering column %d found to be non-improving due to degeneracy.\\n\",\n                     colnr);\n          minit = ITERATE_MINORRETRY;\n          goto RetryCol;\n        }\n        else {\n          lp->rejectpivot[0] = 0;\n          report(lp, DETAILED, \"Gave up trying to find a strictly improving entering column.\\n\");\n        }\n      }\n\n      /* Find the leaving variable that gives the most stringent bound on the entering variable */\n      theta = drow[colnr];\n      rownr = rowprim(lp, colnr, &theta, pcol, workINT, forceoutEQ, &cviolated);\n\n#ifdef AcceptMarginalAccuracy\n      /* Check for marginal accuracy */\n      if((rownr > 0) && (xviolated+cviolated < lp->epspivot)) {\n        if(lp->bb_trace || (lp->bb_totalnodes == 0))\n          report(lp, DETAILED, \"primloop: Assuming convergence with reduced accuracy %g.\\n\",\n                               MAX(xviolated, cviolated));\n        rownr = 0;\n        colnr = 0;\n        goto Optimality;\n      }\n      else\n#endif\n\n      /* See if we can do a straight artificial<->slack replacement (when \"colnr\" is a slack) */\n      if((lp->P1extraDim != 0) && (rownr == 0) && (colnr <= lp->rows))\n        rownr = findAnti_artificial(lp, colnr);\n\n      if(rownr > 0) {\n        pendingunbounded = FALSE;\n        lp->rejectpivot[0] = 0;\n        set_action(&lp->spx_action, ACTION_ITERATE);\n        if(!lp->obj_in_basis)  /* We must manually copy the reduced cost for RHS update */\n          pcol[0] = my_chsign(!lp->is_lower[colnr], drow[colnr]);\n        lp->bfp_prepareupdate(lp, rownr, colnr, pcol);\n      }\n\n      /* We may be unbounded... */\n      else {\n        /* First make sure that we are not suffering from precision loss */\n#ifdef primal_UseRejectionList\n        if(lp->rejectpivot[0] < DEF_MAXPIVOTRETRY) {\n          lp->spx_status = RUNNING;\n          lp->rejectpivot[0]++;\n          lp->rejectpivot[lp->rejectpivot[0]] = colnr;\n          report(lp, DETAILED, \"...trying to recover via another pivot column.\\n\");\n          minit = ITERATE_MINORRETRY;\n          goto RetryCol;\n        }\n        else\n#endif\n        /* Check that we are not having numerical problems */\n        if(!refactRecent(lp) && !pendingunbounded) {\n          bfpfinal = TRUE;\n          pendingunbounded = TRUE;\n          set_action(&lp->spx_action, ACTION_REINVERT);\n        }\n\n        /* Conclude that the model is unbounded */\n        else {\n          lp->spx_status = UNBOUNDED;\n          report(lp, DETAILED, \"The model is primal unbounded.\\n\");\n          break;\n        }\n      }\n    }\n\n    /* We handle optimality and phase 1 infeasibility ... */\n    else {\n\nOptimality:\n      /* Handle possible transition from phase 1 to phase 2 */\n      if(!primalfeasible || isP1extra(lp)) {\n\n        if(feasiblePhase1(lp, epsvalue)) {\n          lp->spx_status = RUNNING;\n          if(lp->bb_totalnodes == 0) {\n            report(lp, NORMAL, \"Found feasibility by primal simplex after  %10.0f iter.\\n\",\n                                (double) get_total_iter(lp));\n            if((lp->usermessage != NULL) && (lp->msgmask & MSG_LPFEASIBLE))\n              lp->usermessage(lp, lp->msghandle, MSG_LPFEASIBLE);\n          }\n          changedphase = FALSE;\n          primalfeasible = TRUE;\n          lp->simplex_mode = SIMPLEX_Phase2_PRIMAL;\n          set_OF_p1extra(lp, 0.0);\n\n         /* We can do two things now;\n            1) delete the rows belonging to those variables, since they are redundant, OR\n            2) drive out the existing artificial variables via pivoting. */\n          if(lp->P1extraDim > 0) {\n\n#ifdef Phase1EliminateRedundant\n           /* If it is not a MIP model we can try to delete redundant rows */\n            if((lp->bb_totalnodes == 0) && (MIP_count(lp) == 0)) {\n              while(lp->P1extraDim > 0) {\n                i = lp->rows;\n                while((i > 0) && (lp->var_basic[i] <= lp->sum-lp->P1extraDim))\n                  i--;\n#ifdef Paranoia\n                if(i <= 0) {\n                  report(lp, SEVERE, \"primloop: Could not find redundant artificial.\\n\");\n                  break;\n                }\n#endif\n                /* Obtain column and row indeces */\n                j = lp->var_basic[i]-lp->rows;\n                k = get_artificialRow(lp, j);\n\n                /* Delete row before column due to basis \"compensation logic\" */\n                if(lp->is_basic[k]) {\n                  lp->is_basic[lp->rows+j] = FALSE;\n                  del_constraint(lp, k);\n                }\n                else\n                  set_basisvar(lp, i, k);\n                del_column(lp, j);\n                lp->P1extraDim--;\n              }\n              lp->basis_valid = TRUE;\n            }\n           /* Otherwise we drive out the artificials by elimination pivoting */\n            else\n              eliminate_artificials(lp, prow);\n\n#else\n            /* Indicate phase 2 with artificial variables by negating P1extraDim */\n            lp->P1extraDim = my_flipsign(lp->P1extraDim);\n#endif\n          }\n\n          /* We must refactorize since the OF changes from phase 1 to phase 2 */\n          set_action(&lp->spx_action, ACTION_REINVERT);\n          bfpfinal = TRUE;\n        }\n\n        /* We are infeasible in phase 1 */\n        else {\n          lp->spx_status = INFEASIBLE;\n          minit = ITERATE_MAJORMAJOR;\n          if(lp->spx_trace)\n            report(lp, NORMAL, \"Model infeasible by primal simplex at iter   %10.0f.\\n\",\n                               (double) get_total_iter(lp));\n        }\n      }\n\n      /* Handle phase 1 optimality */\n      else {\n        /* (Do nothing special) */\n      }\n\n      /* Check if we are still primal feasible; the default assumes that this check\n         is not necessary after the relaxed problem has been solved satisfactorily. */\n      if((lp->bb_level <= 1) || (lp->improve & IMPROVE_BBSIMPLEX) /* || (lp->bb_rule & NODE_RCOSTFIXING) */) { /* NODE_RCOSTFIXING fix */\n        set_action(&lp->piv_strategy, PRICE_FORCEFULL);\n          i = rowdual(lp, lp->rhs, FALSE, FALSE, NULL);\n        clear_action(&lp->piv_strategy, PRICE_FORCEFULL);\n        if(i > 0) {\n          lp->spx_status = LOSTFEAS;\n          if(lp->total_iter == 0)\n            report(lp, DETAILED, \"primloop: Lost primal feasibility at iter  %10.0f: will try to recover.\\n\",\n                                 (double) get_total_iter(lp));\n        }\n      }\n    }\n\n    /* Pivot row/col and update the inverse */\n    if(is_action(lp->spx_action, ACTION_ITERATE)) {\n      lastnr = lp->var_basic[rownr];\n\n      if(refactRecent(lp) == AUTOMATIC)\n        minitcount = 0;\n      else if(minitcount > MAX_MINITUPDATES) {\n        recompute_solution(lp, INITSOL_USEZERO);\n        minitcount = 0;\n      }\n      minit = performiteration(lp, rownr, colnr, theta, primal,\n                                                 (MYBOOL) (/*(candidatecount > 1) && */\n                                                           (stallaccept != AUTOMATIC)),\n                                                 NULL, NULL,\n                                                 pcol, NULL, NULL);\n      if(minit != ITERATE_MAJORMAJOR)\n        minitcount++;\n\n      if((lp->spx_status == USERABORT) || (lp->spx_status == TIMEOUT))\n        break;\n      else if(minit == ITERATE_MINORMAJOR)\n        continue;\n#ifdef UsePrimalReducedCostUpdate\n      /* Do a fast update of the reduced costs in preparation for the next iteration */\n      if(minit == ITERATE_MAJORMAJOR)\n        update_reducedcosts(lp, primal, lastnr, colnr, pcol, drow);\n#endif\n\n      /* Detect if an auxiliary variable has left the basis and delete it; if\n         the non-basic variable only changed bound (a \"minor iteration\"), the\n         basic artificial variable did not leave and there is nothing to do */\n      if((minit == ITERATE_MAJORMAJOR) && (lastnr > lp->sum - abs(lp->P1extraDim))) {\n#ifdef Paranoia\n        if(lp->is_basic[lastnr] || !lp->is_basic[colnr])\n          report(lp, SEVERE, \"primloop: Invalid basis indicator for variable %d at iter %10.0f.\\n\",\n                              lastnr, (double) get_total_iter(lp));\n#endif\n        del_column(lp, lastnr-lp->rows);\n        if(lp->P1extraDim > 0)\n          lp->P1extraDim--;\n        else\n          lp->P1extraDim++;\n        if(lp->P1extraDim == 0) {\n          colnr = 0;\n          changedphase = TRUE;\n          stallMonitor_reset(lp);\n        }\n      }\n    }\n\n    if(lp->spx_status == SWITCH_TO_DUAL)\n      ;\n    else if(!changedphase && lp->bfp_mustrefactorize(lp)) {\n#ifdef ResetMinitOnReinvert\n      minit = ITERATE_MAJORMAJOR;\n#endif\n      if(!invert(lp, INITSOL_USEZERO, bfpfinal))\n        lp->spx_status = SINGULAR_BASIS;\n      bfpfinal = FALSE;\n    }\n  }\n\n  /* Remove any remaining artificial variables (feasible or infeasible model) */\n  lp->P1extraDim = abs(lp->P1extraDim);\n/*  if((lp->P1extraDim > 0) && (lp->spx_status != DEGENERATE)) { */\n  if(lp->P1extraDim > 0) {\n    clear_artificials(lp);\n    if(lp->spx_status != OPTIMAL)\n      restore_basis(lp);\n    i = invert(lp, INITSOL_USEZERO, TRUE);\n  }\n#ifdef Paranoia\n  if(!verify_basis(lp))\n    report(lp, SEVERE, \"primloop: Invalid basis detected due to internal error\\n\");\n#endif\n\n  /* Switch to dual phase 1 simplex for MIP models during\n     B&B phases, since this is typically far more efficient */\n#ifdef ForceDualSimplexInBB\n  if((lp->bb_totalnodes == 0) && (MIP_count(lp) > 0) &&\n     ((lp->simplex_strategy & SIMPLEX_Phase1_DUAL) == 0)) {\n    lp->simplex_strategy &= ~SIMPLEX_Phase1_PRIMAL;\n    lp->simplex_strategy += SIMPLEX_Phase1_DUAL;\n  }\n#endif\n\nFinish:\n  stallMonitor_finish(lp);\n  multi_free(&(lp->multivars));\n  FREE(prow);\n  FREE(pcol);\n  FREE(lp->bsolveVal);\n\n  return(ok);\n} /* primloop */\n\nSTATIC int dualloop(lprec *lp, MYBOOL dualfeasible, int dualinfeasibles[], REAL dualoffset)\n{\n  MYBOOL primal = FALSE, inP1extra, dualphase1 = FALSE, changedphase = TRUE,\n         pricerCanChange, minit, stallaccept, longsteps,\n         forceoutEQ = FALSE, bfpfinal = FALSE;\n  int    i, colnr = 0, rownr = 0, lastnr = 0,\n         candidatecount = 0, minitcount = 0,\n#ifdef FixInaccurateDualMinit\n         minitcolnr = 0,\n#endif\n         ok = TRUE;\n  int    *boundswaps = NULL;\n  LREAL  theta = 0.0;\n  REAL   epsvalue, xviolated, cviolated,\n         *prow = NULL, *pcol = NULL,\n         *drow = lp->drow;\n  int    *nzprow = NULL, *workINT = NULL,\n         *nzdrow = lp->nzdrow;\n\n  if(lp->spx_trace)\n    report(lp, DETAILED, \"Entered dual simplex algorithm with feasibility %s.\\n\",\n                         my_boolstr(dualfeasible));\n\n  /* Allocate work arrays */\n  ok = allocREAL(lp, &prow,   lp->sum + 1,  TRUE) &&\n       allocINT (lp, &nzprow, lp->sum + 1,  FALSE) &&\n       allocREAL(lp, &pcol,   lp->rows + 1, TRUE);\n  if(!ok)\n    goto Finish;\n\n  /* Set non-zero P1extraVal value to force dual feasibility when the dual\n     simplex is used as a phase 1 algorithm for the primal simplex.\n     The value will be reset when primal feasibility has been achieved, or\n     a dual non-feasibility has been encountered (no candidate for a first\n     leaving variable) */\n  inP1extra = (MYBOOL) (dualoffset != 0);\n  if(inP1extra) {\n    set_OF_p1extra(lp, dualoffset);\n    simplexPricer(lp, (MYBOOL)!primal);\n    invert(lp, INITSOL_USEZERO, TRUE);\n  }\n  else\n    restartPricer(lp, (MYBOOL)!primal);\n\n  /* Prepare dual long-step structures */\n#if 0\n  longsteps = TRUE;\n#elif 0\n  longsteps = (MYBOOL) ((MIP_count(lp) > 0) && (lp->bb_level > 1));\n#elif 0\n  longsteps = (MYBOOL) ((MIP_count(lp) > 0) && (lp->solutioncount >= 1));\n#else\n  longsteps = FALSE;\n#endif\n#ifdef UseLongStepDualPhase1\n  longsteps = !dualfeasible && (MYBOOL) (dualinfeasibles != NULL);\n#endif\n\n  if(longsteps) {\n    lp->longsteps = multi_create(lp, TRUE);\n    ok = (lp->longsteps != NULL) &&\n         multi_resize(lp->longsteps, MIN(lp->boundedvars+2, 11), 1, TRUE, TRUE);\n    if(!ok)\n      goto Finish;\n#ifdef UseLongStepPruning\n    lp->longsteps->objcheck = TRUE;\n#endif\n    boundswaps = multi_indexSet(lp->longsteps, FALSE);\n  }\n\n  /* Do regular dual simplex variable initializations */\n  lp->spx_status = RUNNING;\n  minit = ITERATE_MAJORMAJOR;\n  epsvalue = lp->epspivot;\n\n  ok = stallMonitor_create(lp, TRUE, \"dualloop\");\n  if(!ok)\n    goto Finish;\n\n  lp->rejectpivot[0] = 0;\n  if(dualfeasible)\n    lp->simplex_mode = SIMPLEX_Phase2_DUAL;\n  else\n    lp->simplex_mode = SIMPLEX_Phase1_DUAL;\n\n  /* Check if we have equality slacks in the basis and we should try to\n     drive them out in order to reduce chance of degeneracy in Phase 1.\n     forceoutEQ = FALSE :    Only eliminate assured \"good\" violated\n                             equality constraint slacks\n                  AUTOMATIC: Seek more elimination of equality constraint\n                             slacks (but not as aggressive as the rule\n                             used in lp_solve v4.0 and earlier)\n                  TRUE:      Force remaining equality slacks out of the\n                             basis */\n  if(dualphase1 || inP1extra ||\n     ((lp->fixedvars > 0) && is_anti_degen(lp, ANTIDEGEN_FIXEDVARS))) {\n    forceoutEQ = AUTOMATIC;\n  }\n#if 1\n  if(is_anti_degen(lp, ANTIDEGEN_DYNAMIC) && (bin_count(lp, TRUE)*2 > lp->columns)) {\n    switch (forceoutEQ) {\n      case FALSE:     forceoutEQ = AUTOMATIC;\n                      break;\n /*     case AUTOMATIC: forceoutEQ = TRUE;\n                      break;\n      default:        forceoutEQ = TRUE; */\n    }\n  }\n#endif\n\n  while((lp->spx_status == RUNNING) && !userabort(lp, -1)) {\n\n    /* Check if we have stalling (from numerics or degenerate cycling) */\n    pricerCanChange = !dualphase1 && !inP1extra;\n    stallaccept = stallMonitor_check(lp, rownr, colnr, lastnr, minit, pricerCanChange, &forceoutEQ);\n    if(!stallaccept)\n      break;\n\n    /* Store current LP index for reference at next iteration */\n    changedphase = FALSE;\n\n    /* Compute (pure) dual phase1 offsets / reduced costs if appropriate */\n    dualphase1 &= (MYBOOL) (lp->simplex_mode == SIMPLEX_Phase1_DUAL);\n    if(longsteps && dualphase1 && !inP1extra) {\n      obtain_column(lp, dualinfeasibles[1], pcol, NULL, NULL);\n      i = 2;\n      for(i = 2; i <= dualinfeasibles[0]; i++)\n        mat_multadd(lp->matA, pcol, dualinfeasibles[i], 1.0);\n      /* Solve (note that solved pcol will be used instead of lp->rhs) */\n      ftran(lp, pcol, NULL, lp->epsmachine);\n    }\n\n    /* Do minor iterations (non-basic variable bound flips) for as\n       long as possible since this is a cheap way of iterating */\n#if (defined dual_Phase1PriceEqualities) || (defined dual_UseRejectionList)\nRetryRow:\n#endif\n    if(minit != ITERATE_MINORRETRY) {\n      i = 0;\n      do {\n        i++;\n        rownr = rowdual(lp, my_if(dualphase1, pcol, NULL), forceoutEQ, TRUE, &xviolated);\n      } while ((rownr == 0) && (i < partial_countBlocks(lp, (MYBOOL) !primal)) &&\n                                partial_blockStep(lp, (MYBOOL) !primal));\n    }\n\n    /* Make sure that we do not erroneously conclude that an infeasible model is optimal */\n#ifdef dual_UseRejectionList\n    if((rownr == 0) && (lp->rejectpivot[0] > 0)) {\n      lp->spx_status = INFEASIBLE;\n      if((lp->spx_trace && (lp->bb_totalnodes == 0)) ||\n         (lp->bb_trace && (lp->bb_totalnodes > 0)))\n        report(lp, DETAILED, \"The model is primal infeasible.\\n\");\n      rownr = lp->rejectpivot[1];\n      colnr = 0;\n      lp->rejectpivot[0] = 0;\n      ok = FALSE;\n      break;\n    }\n#endif\n\n    /* If we found a leaving variable, find a matching entering one */\n    clear_action(&lp->spx_action, ACTION_ITERATE);\n    if(rownr > 0) {\n      colnr = coldual(lp, rownr, prow, nzprow, drow, nzdrow,\n                                 (MYBOOL) (dualphase1 && !inP1extra),\n                                 (MYBOOL) (minit == ITERATE_MINORRETRY), &candidatecount, &cviolated);\n      if(colnr < 0) {\n        minit = ITERATE_MAJORMAJOR;\n        continue;\n      }\n#ifdef AcceptMarginalAccuracy\n      else if(xviolated+cviolated < lp->epspivot) {\n        if(lp->bb_trace || (lp->bb_totalnodes == 0))\n          report(lp, DETAILED, \"dualloop: Assuming convergence with reduced accuracy %g.\\n\",\n                               MAX(xviolated, cviolated));\n        rownr = 0;\n        colnr = 0;\n      }\n#endif\n      /* Check if the long-dual found reason to prune the B&B tree */\n      if(lp->spx_status == FATHOMED)\n        break;\n    }\n    else\n      colnr = 0;\n\n    /* Process primal-infeasible row */\n    if(rownr > 0) {\n\n      if(colnr > 0) {\n#ifdef Paranoia\n        if((rownr > lp->rows) || (colnr > lp->sum)) {\n          report(lp, SEVERE, \"dualloop: Invalid row %d(%d) and column %d(%d) pair selected at iteration %.0f\\n\",\n                             rownr, lp->rows, colnr-lp->columns, lp->columns, (double) get_total_iter(lp));\n          lp->spx_status = UNKNOWNERROR;\n          break;\n        }\n#endif\n        fsolve(lp, colnr, pcol, workINT, lp->epsmachine, 1.0, TRUE);\n\n#ifdef FixInaccurateDualMinit\n       /* Prevent bound flip-flops during minor iterations; used to detect\n          infeasibility after triggering of minor iteration accuracy management */\n        if(colnr != minitcolnr)\n          minitcolnr = 0;\n#endif\n\n       /* Getting division by zero here; catch it and try to recover */\n        if(pcol[rownr] == 0) {\n          if(lp->spx_trace)\n            report(lp, DETAILED, \"dualloop: Attempt to divide by zero (pcol[%d])\\n\", rownr);\n          if(!refactRecent(lp)) {\n            report(lp, DETAILED, \"...trying to recover by refactorizing basis.\\n\");\n            set_action(&lp->spx_action, ACTION_REINVERT);\n            bfpfinal = FALSE;\n          }\n          else {\n            if(lp->bb_totalnodes == 0)\n              report(lp, DETAILED, \"...cannot recover by refactorizing basis.\\n\");\n            lp->spx_status = NUMFAILURE;\n            ok = FALSE;\n          }\n        }\n        else {\n          set_action(&lp->spx_action, ACTION_ITERATE);\n          lp->rejectpivot[0] = 0;\n          if(!lp->obj_in_basis)  /* We must manually copy the reduced cost for RHS update */\n            pcol[0] = my_chsign(!lp->is_lower[colnr], drow[colnr]);\n          theta = lp->bfp_prepareupdate(lp, rownr, colnr, pcol);\n\n         /* Verify numeric accuracy of the basis factorization and change to\n            the \"theoretically\" correct version of the theta */\n          if((lp->improve & IMPROVE_THETAGAP) && !refactRecent(lp) &&\n             (my_reldiff(fabs(theta), fabs(prow[colnr])) >\n              lp->epspivot*10.0*log(2.0+50.0*lp->rows))) {  /* This is my kludge - KE */\n            set_action(&lp->spx_action, ACTION_REINVERT);\n            bfpfinal = TRUE;\n#ifdef IncreasePivotOnReducedAccuracy\n            lp->epspivot = MIN(1.0e-4, lp->epspivot*2.0);\n#endif\n            report(lp, DETAILED, \"dualloop: Refactorizing at iter %.0f due to loss of accuracy.\\n\",\n                                 (double) get_total_iter(lp));\n          }\n          theta = prow[colnr];\n          compute_theta(lp, rownr, &theta, !lp->is_lower[colnr], 0, primal);\n        }\n      }\n\n#ifdef FixInaccurateDualMinit\n      /* Force reinvertion and try another row if we did not find a bound-violated leaving column */\n      else if(!refactRecent(lp) && (minit != ITERATE_MAJORMAJOR) && (colnr != minitcolnr)) {\n        minitcolnr = colnr;\n        i = invert(lp, INITSOL_USEZERO, TRUE);\n        if((lp->spx_status == USERABORT) || (lp->spx_status == TIMEOUT))\n          break;\n        else if(!i) {\n          lp->spx_status = SINGULAR_BASIS;\n          break;\n        }\n        minit = ITERATE_MAJORMAJOR;\n        continue;\n      }\n#endif\n\n      /* We may be infeasible, have lost dual feasibility, or simply have no valid entering\n         variable for the selected row.  The strategy is to refactorize if we suspect numerical\n         problems and loss of dual feasibility; this is done if it has been a while since\n         refactorization.  If not, first try to select a different row/leaving variable to\n         see if a valid entering variable can be found.  Otherwise, determine this model\n         as infeasible. */\n      else {\n\n        /* As a first option, try to recover from any numerical trouble by refactorizing */\n        if(!refactRecent(lp)) {\n          set_action(&lp->spx_action, ACTION_REINVERT);\n          bfpfinal = TRUE;\n        }\n\n#ifdef dual_UseRejectionList\n        /* Check for pivot size issues */\n        else if(lp->rejectpivot[0] < DEF_MAXPIVOTRETRY) {\n          lp->spx_status = RUNNING;\n          lp->rejectpivot[0]++;\n          lp->rejectpivot[lp->rejectpivot[0]] = rownr;\n          if(lp->bb_totalnodes == 0)\n            report(lp, DETAILED, \"...trying to find another pivot row!\\n\");\n          goto RetryRow;\n        }\n#endif\n        /* Check if we may have lost dual feasibility if we also did phase 1 here */\n        else if(dualphase1 && (dualoffset != 0)) {\n          lp->spx_status = LOSTFEAS;\n          if((lp->spx_trace && (lp->bb_totalnodes == 0)) ||\n             (lp->bb_trace && (lp->bb_totalnodes > 0)))\n            report(lp, DETAILED, \"dualloop: Model lost dual feasibility.\\n\");\n          ok = FALSE;\n          break;\n        }\n\n        /* Otherwise just determine that we are infeasible */\n        else {\n          if(lp->spx_status == RUNNING) {\n#if 1\n            if(xviolated < lp->epspivot) {\n              if(lp->bb_trace || (lp->bb_totalnodes == 0))\n                report(lp, NORMAL, \"The model is primal optimal, but marginally infeasible.\\n\");\n              lp->spx_status = OPTIMAL;\n              break;\n            }\n#endif\n            lp->spx_status = INFEASIBLE;\n            if((lp->spx_trace && (lp->bb_totalnodes == 0)) ||\n               (lp->bb_trace && (lp->bb_totalnodes > 0)))\n            report(lp, DETAILED, \"The model is primal infeasible.\\n\");\n          }\n          ok = FALSE;\n          break;\n        }\n      }\n    }\n\n    /* Make sure that we enter the primal simplex with a high quality solution */\n    else if(inP1extra && !refactRecent(lp) && is_action(lp->improve, IMPROVE_INVERSE)) {\n       set_action(&lp->spx_action, ACTION_REINVERT);\n       bfpfinal = TRUE;\n    }\n\n    /* High quality solution with no leaving candidates available ... */\n    else {\n\n      bfpfinal = TRUE;\n\n#ifdef dual_RemoveBasicFixedVars\n      /* See if we should try to eliminate basic fixed variables;\n        can be time-consuming for some models */\n      if(inP1extra && (colnr == 0) && (lp->fixedvars > 0) && is_anti_degen(lp, ANTIDEGEN_FIXEDVARS)) {\n        report(lp, DETAILED, \"dualloop: Trying to pivot out %d fixed basic variables at iter %.0f\\n\",\n                             lp->fixedvars, (double) get_total_iter(lp));\n        rownr = 0;\n        while(lp->fixedvars > 0) {\n          rownr = findBasicFixedvar(lp, rownr, TRUE);\n          if(rownr == 0) {\n            colnr = 0;\n            break;\n          }\n          colnr = find_rowReplacement(lp, rownr, prow, nzprow);\n          if(colnr > 0) {\n            theta = 0;\n            performiteration(lp, rownr, colnr, theta, TRUE, FALSE, prow, NULL,\n                                                            NULL, NULL, NULL);\n            lp->fixedvars--;\n          }\n        }\n      }\n#endif\n\n      /* Check if we are INFEASIBLE for the case that the dual is used\n         as phase 1 before the primal simplex phase 2 */\n      if(inP1extra && (colnr < 0) && !isPrimalFeasible(lp, lp->epsprimal, NULL, NULL)) {\n        if(lp->bb_totalnodes == 0) {\n          if(dualfeasible)\n            report(lp, DETAILED, \"The model is primal infeasible and dual feasible.\\n\");\n          else\n            report(lp, DETAILED, \"The model is primal infeasible and dual unbounded.\\n\");\n        }\n        set_OF_p1extra(lp, 0);\n        inP1extra = FALSE;\n        set_action(&lp->spx_action, ACTION_REINVERT);\n        lp->spx_status = INFEASIBLE;\n        lp->simplex_mode = SIMPLEX_UNDEFINED;\n        ok = FALSE;\n      }\n\n      /* Check if we are FEASIBLE (and possibly also optimal) for the case that the\n         dual is used as phase 1 before the primal simplex phase 2 */\n      else if(inP1extra) {\n\n        /* Set default action; force an update of the rhs vector, adjusted for\n           the new P1extraVal=0 (set here so that usermessage() behaves properly) */\n        if(lp->bb_totalnodes == 0) {\n          report(lp, NORMAL, \"Found feasibility by dual simplex after    %10.0f iter.\\n\",\n                             (double) get_total_iter(lp));\n          if((lp->usermessage != NULL) && (lp->msgmask & MSG_LPFEASIBLE))\n            lp->usermessage(lp, lp->msghandle, MSG_LPFEASIBLE);\n        }\n        set_OF_p1extra(lp, 0);\n        inP1extra = FALSE;\n        set_action(&lp->spx_action, ACTION_REINVERT);\n\n#if 1\n        /* Optionally try another dual loop, if so selected by the user */\n        if((lp->simplex_strategy & SIMPLEX_DUAL_PRIMAL) && (lp->fixedvars == 0))\n          lp->spx_status = SWITCH_TO_PRIMAL;\n#endif\n        changedphase = TRUE;\n\n      }\n\n      /* We are primal feasible and also optimal if we were in phase 2 */\n      else  {\n\n        lp->simplex_mode = SIMPLEX_Phase2_DUAL;\n\n        /* Check if we still have equality slacks stuck in the basis; drive them out? */\n        if((lp->fixedvars > 0) && (lp->bb_totalnodes == 0)) {\n#ifdef dual_Phase1PriceEqualities\n          if(forceoutEQ != TRUE) {\n            forceoutEQ = TRUE;\n            goto RetryRow;\n          }\n#endif\n#ifdef Paranoia\n          report(lp, NORMAL,\n#else\n          report(lp, DETAILED,\n#endif\n                    \"Found dual solution with %d fixed slack variables left basic.\\n\",\n                    lp->fixedvars);\n        }\n        /* Check if we are still dual feasible; the default assumes that this check\n          is not necessary after the relaxed problem has been solved satisfactorily. */\n        colnr = 0;\n        if((dualoffset != 0) || (lp->bb_level <= 1) || (lp->improve & IMPROVE_BBSIMPLEX) || (lp->bb_rule & NODE_RCOSTFIXING)) { /* NODE_RCOSTFIXING fix */\n          set_action(&lp->piv_strategy, PRICE_FORCEFULL);\n            colnr = colprim(lp, drow, nzdrow, FALSE, 1, &candidatecount, FALSE, NULL);\n          clear_action(&lp->piv_strategy, PRICE_FORCEFULL);\n          if((dualoffset == 0) && (colnr > 0)) {\n            lp->spx_status = LOSTFEAS;\n            if(lp->total_iter == 0)\n              report(lp, DETAILED, \"Recovering lost dual feasibility at iter %10.0f.\\n\",\n                                   (double) get_total_iter(lp));\n            break;\n          }\n        }\n\n        if(colnr == 0)\n          lp->spx_status = OPTIMAL;\n        else {\n          lp->spx_status = SWITCH_TO_PRIMAL;\n          if(lp->total_iter == 0)\n            report(lp, DETAILED, \"Use primal simplex for finalization at iter  %10.0f.\\n\",\n                                 (double) get_total_iter(lp));\n        }\n        if((lp->total_iter == 0) && (lp->spx_status == OPTIMAL))\n          report(lp, DETAILED, \"Optimal solution with dual simplex at iter   %10.0f.\\n\",\n                               (double) get_total_iter(lp));\n      }\n\n      /* Determine if we are ready to break out of the loop */\n      if(!changedphase)\n        break;\n    }\n\n    /* Check if we are allowed to iterate on the chosen column and row */\n    if(is_action(lp->spx_action, ACTION_ITERATE)) {\n\n      lastnr = lp->var_basic[rownr];\n      if(refactRecent(lp) == AUTOMATIC)\n        minitcount = 0;\n      else if(minitcount > MAX_MINITUPDATES) {\n        recompute_solution(lp, INITSOL_USEZERO);\n        minitcount = 0;\n      }\n      minit = performiteration(lp, rownr, colnr, theta, primal,\n                                                 (MYBOOL) (/*(candidatecount > 1) && */\n                                                           (stallaccept != AUTOMATIC)),\n                                                 prow, nzprow,\n                                                 pcol, NULL, boundswaps);\n\n      /* Check if we should abandon iterations on finding that there is no\n        hope that this branch can improve on the incumbent B&B solution */\n      if(!lp->is_strongbranch && (lp->solutioncount >= 1) && !lp->spx_perturbed && !inP1extra &&\n          bb_better(lp, OF_WORKING, OF_TEST_WE)) {\n        lp->spx_status = FATHOMED;\n        ok = FALSE;\n        break;\n      }\n\n      if(minit != ITERATE_MAJORMAJOR)\n        minitcount++;\n\n      /* Update reduced costs for (pure) dual long-step phase 1 */\n      if(longsteps && dualphase1 && !inP1extra) {\n        dualfeasible = isDualFeasible(lp, lp->epsprimal, NULL, dualinfeasibles, NULL);\n        if(dualfeasible) {\n          dualphase1 = FALSE;\n          changedphase = TRUE;\n          lp->simplex_mode = SIMPLEX_Phase2_DUAL;\n        }\n      }\n#ifdef UseDualReducedCostUpdate\n      /* Do a fast update of reduced costs in preparation for the next iteration */\n      else if(minit == ITERATE_MAJORMAJOR)\n        update_reducedcosts(lp, primal, lastnr, colnr, prow, drow);\n#endif\n      if((minit == ITERATE_MAJORMAJOR) && (lastnr <= lp->rows) && is_fixedvar(lp, lastnr))\n        lp->fixedvars--;\n    }\n\n    /* Refactorize if required to */\n    if(lp->bfp_mustrefactorize(lp)) {\n      if(invert(lp, INITSOL_USEZERO, bfpfinal)) {\n\n#if 0\n        /* Verify dual feasibility in case we are attempting the extra dual loop */\n        if(changedphase && (dualoffset != 0) && !inP1extra && (lp->spx_status != SWITCH_TO_PRIMAL)) {\n#if 1\n          if(!isDualFeasible(lp, lp->epsdual, &colnr, NULL, NULL)) {\n#else\n          set_action(&lp->piv_strategy, PRICE_FORCEFULL);\n            colnr = colprim(lp, drow, nzdrow, FALSE, 1, &candidatecount, FALSE, NULL);\n          clear_action(&lp->piv_strategy, PRICE_FORCEFULL);\n          if(colnr > 0) {\n#endif\n            lp->spx_status = SWITCH_TO_PRIMAL;\n            colnr = 0;\n          }\n        }\n#endif\n\n        bfpfinal = FALSE;\n#ifdef ResetMinitOnReinvert\n        minit = ITERATE_MAJORMAJOR;\n#endif\n      }\n      else\n        lp->spx_status = SINGULAR_BASIS;\n    }\n  }\n\nFinish:\n  stallMonitor_finish(lp);\n  multi_free(&(lp->longsteps));\n  FREE(prow);\n  FREE(nzprow);\n  FREE(pcol);\n\n  return(ok);\n}\n\nSTATIC int spx_run(lprec *lp, MYBOOL validInvB)\n{\n  int    i, j, singular_count, lost_feas_count, *infeasibles = NULL, *boundflip_count;\n  MYBOOL primalfeasible, dualfeasible, lost_feas_state, isbb;\n  REAL   primaloffset = 0, dualoffset = 0;\n\n  lp->current_iter  = 0;\n  lp->current_bswap = 0;\n  lp->spx_status    = RUNNING;\n  lp->bb_status = lp->spx_status;\n  lp->P1extraDim = 0;\n  set_OF_p1extra(lp, 0);\n  singular_count  = 0;\n  lost_feas_count = 0;\n  lost_feas_state = FALSE;\n  lp->simplex_mode = SIMPLEX_DYNAMIC;\n\n  /* Compute the number of fixed basic and bounded variables (used in long duals) */\n  lp->fixedvars = 0;\n  lp->boundedvars = 0;\n  for(i = 1; i <= lp->rows; i++) {\n    j = lp->var_basic[i];\n    if((j <= lp->rows) && is_fixedvar(lp, j))\n      lp->fixedvars++;\n    if((lp->upbo[i] < lp->infinite) && (lp->upbo[i] > lp->epsprimal))\n      lp->boundedvars++;\n  }\n  for(; i <= lp->sum; i++){\n    if((lp->upbo[i] < lp->infinite) && (lp->upbo[i] > lp->epsprimal))\n      lp->boundedvars++;\n  }\n#ifdef UseLongStepDualPhase1\n  allocINT(lp, &infeasibles, lp->columns + 1, FALSE);\n  infeasibles[0] = 0;\n#endif\n\n  /* Reinvert for initialization, if necessary */\n  isbb = (MYBOOL) ((MIP_count(lp) > 0) && (lp->bb_level > 1));\n  if(is_action(lp->spx_action, ACTION_REINVERT)) {\n    if(isbb && (lp->bb_bounds->nodessolved == 0))\n/*    if(isbb && (lp->bb_basis->pivots == 0)) */\n      recompute_solution(lp, INITSOL_SHIFTZERO);\n    else {\n      i = my_if(is_action(lp->spx_action, ACTION_REBASE), INITSOL_SHIFTZERO, INITSOL_USEZERO);\n      invert(lp, (MYBOOL) i, TRUE);\n    }\n  }\n  else if(is_action(lp->spx_action, ACTION_REBASE))\n    recompute_solution(lp, INITSOL_SHIFTZERO);\n\n  /* Optionally try to do bound flips to obtain dual feasibility */\n  if(is_action(lp->improve, IMPROVE_DUALFEAS) || (lp->rows == 0))\n    boundflip_count = &i;\n  else\n    boundflip_count = NULL;\n\n  /* Loop for as long as is needed */\n  while(lp->spx_status == RUNNING) {\n\n    /* Check for dual and primal feasibility */\n    dualfeasible   = isbb ||\n                     isDualFeasible(lp, lp->epsprimal, boundflip_count, infeasibles, &dualoffset);\n\n    /* Recompute if the dual feasibility check included bound flips */\n    if(is_action(lp->spx_action, ACTION_RECOMPUTE))\n      recompute_solution(lp, INITSOL_USEZERO);\n    primalfeasible = isPrimalFeasible(lp, lp->epsprimal, NULL, &primaloffset);\n\n    if(userabort(lp, -1))\n      break;\n\n    if(lp->spx_trace) {\n      if(primalfeasible)\n        report(lp, NORMAL, \"Start at primal feasible basis\\n\");\n      else if(dualfeasible)\n        report(lp, NORMAL, \"Start at dual feasible basis\\n\");\n      else if(lost_feas_count > 0)\n        report(lp, NORMAL, \"Continuing at infeasible basis\\n\");\n      else\n        report(lp, NORMAL, \"Start at infeasible basis\\n\");\n    }\n\n   /* Now do the simplex magic */\n    if(((lp->simplex_strategy & SIMPLEX_Phase1_DUAL) == 0) ||\n       ((MIP_count(lp) > 0) && (lp->total_iter == 0) &&\n        is_presolve(lp, PRESOLVE_REDUCEMIP))) {\n      if(!lost_feas_state && primalfeasible && ((lp->simplex_strategy & SIMPLEX_Phase2_DUAL) > 0))\n        lp->spx_status = SWITCH_TO_DUAL;\n      else\n        primloop(lp, primalfeasible, 0.0);\n      if(lp->spx_status == SWITCH_TO_DUAL)\n        dualloop(lp, TRUE, NULL, 0.0);\n    }\n    else {\n      if(!lost_feas_state && primalfeasible && ((lp->simplex_strategy & SIMPLEX_Phase2_PRIMAL) > 0))\n        lp->spx_status = SWITCH_TO_PRIMAL;\n      else\n        dualloop(lp, dualfeasible, infeasibles, dualoffset);\n      if(lp->spx_status == SWITCH_TO_PRIMAL)\n        primloop(lp, TRUE, 0.0);\n    }\n\n    /* Check for simplex outcomes that always involve breaking out of the loop;\n       this includes optimality, unboundedness, pure infeasibility (i.e. not\n       loss of feasibility), numerical failure and perturbation-based degeneracy\n       handling */\n    i = lp->spx_status;\n    primalfeasible = (MYBOOL) (i == OPTIMAL);\n    if(primalfeasible || (i == UNBOUNDED))\n      break;\n    else if(((i == INFEASIBLE) && is_anti_degen(lp, ANTIDEGEN_INFEASIBLE)) ||\n             ((i == LOSTFEAS)   && is_anti_degen(lp, ANTIDEGEN_LOSTFEAS)) ||\n             ((i == NUMFAILURE) && is_anti_degen(lp, ANTIDEGEN_NUMFAILURE)) ||\n             ((i == DEGENERATE) && is_anti_degen(lp, ANTIDEGEN_STALLING))) {\n      /* Check if we should not loop here, but do perturbations */\n      if((lp->bb_level <= 1)   || is_anti_degen(lp, ANTIDEGEN_DURINGBB))\n        break;\n\n      /* Assume that accuracy during B&B is high and that infeasibility is \"real\" */\n#ifdef AssumeHighAccuracyInBB\n      if((lp->bb_level > 1) && (i == INFEASIBLE))\n        break;\n#endif\n    }\n\n    /* Check for outcomes that may involve trying another simplex loop */\n    if(lp->spx_status == SINGULAR_BASIS) {\n      lost_feas_state = FALSE;\n      singular_count++;\n      if(singular_count >= DEF_MAXSINGULARITIES) {\n        report(lp, IMPORTANT, \"spx_run: Failure due to too many singular bases.\\n\");\n        lp->spx_status = NUMFAILURE;\n        break;\n      }\n      if(lp->spx_trace || (lp->verbose > DETAILED))\n        report(lp, NORMAL, \"spx_run: Singular basis; attempting to recover.\\n\");\n      lp->spx_status = RUNNING;\n      /* Singular pivots are simply skipped by the inversion, leaving a row's\n         slack variable in the basis instead of the singular user variable. */\n    }\n    else {\n      lost_feas_state = (MYBOOL) (lp->spx_status == LOSTFEAS);\n#if 0\n      /* Optionally handle loss of numerical accuracy as loss of feasibility,\n         but only attempt a single loop to try to recover from this. */\n      lost_feas_state |= (MYBOOL) ((lp->spx_status == NUMFAILURE) && (lost_feas_count < 1));\n#endif\n      if(lost_feas_state) {\n        lost_feas_count++;\n        if(lost_feas_count < DEF_MAXSINGULARITIES) {\n          report(lp, DETAILED, \"spx_run: Recover lost feasibility at iter  %10.0f.\\n\",\n                                (double) get_total_iter(lp));\n          lp->spx_status = RUNNING;\n        }\n        else {\n          report(lp, IMPORTANT, \"spx_run: Lost feasibility %d times - iter %10.0f and %9.0f nodes.\\n\",\n                                lost_feas_count, (double) get_total_iter(lp), (double) lp->bb_totalnodes);\n          lp->spx_status = NUMFAILURE;\n        }\n      }\n    }\n  }\n\n  /* Update iteration tallies before returning */\n  lp->total_iter   += lp->current_iter;\n  lp->current_iter  = 0;\n  lp->total_bswap  += lp->current_bswap;\n  lp->current_bswap = 0;\n  FREE(infeasibles);\n\n  return(lp->spx_status);\n} /* spx_run */\n\nlprec *make_lag(lprec *lpserver)\n{\n  int    i;\n  lprec  *hlp;\n  MYBOOL ret;\n  REAL   *duals;\n\n  /* Create a Lagrangean solver instance */\n  hlp = make_lp(0, lpserver->columns);\n\n  if(hlp != NULL) {\n\n    /* First create and core variable data */\n    set_sense(hlp, is_maxim(lpserver));\n    hlp->lag_bound = lpserver->bb_limitOF;\n    for(i = 1; i <= lpserver->columns; i++) {\n      set_mat(hlp, 0, i, get_mat(lpserver, 0, i));\n      if(is_binary(lpserver, i))\n        set_binary(hlp, i, TRUE);\n      else {\n        set_int(hlp, i, is_int(lpserver, i));\n        set_bounds(hlp, i, get_lowbo(lpserver, i), get_upbo(lpserver, i));\n      }\n    }\n    /* Then fill data for the Lagrangean constraints */\n    hlp->matL = lpserver->matA;\n    inc_lag_space(hlp, lpserver->rows, TRUE);\n    ret = get_ptr_sensitivity_rhs(hlp, &duals, NULL, NULL);\n    for(i = 1; i <= lpserver->rows; i++) {\n      hlp->lag_con_type[i] = get_constr_type(lpserver, i);\n      hlp->lag_rhs[i] = lpserver->orig_rhs[i];\n      hlp->lambda[i] = (ret) ? duals[i - 1] : 0.0;\n    }\n  }\n\n  return(hlp);\n}\n\nSTATIC int heuristics(lprec *lp, int mode)\n/* Initialize / bound a MIP problem */\n{\n  lprec *hlp;\n  int   status = PROCFAIL;\n\n  if(lp->bb_level > 1)\n    return( status );\n\n  status = RUNNING;\n  lp->bb_limitOF = my_chsign(is_maxim(lp), -lp->infinite);\n  if(FALSE && (lp->int_vars > 0)) {\n\n    /* 1. Copy the problem into a new relaxed instance, extracting Lagrangean constraints */\n    hlp = make_lag(lp);\n\n    /* 2. Run the Lagrangean relaxation */\n    status = solve(hlp);\n\n    /* 3. Copy the key results (bound) into the original problem */\n    lp->bb_heuristicOF = hlp->best_solution[0];\n\n    /* 4. Delete the helper heuristic */\n    hlp->matL = NULL;\n    delete_lp(hlp);\n  }\n\n  lp->timeheuristic = timeNow();\n  return( status );\n}\n\nSTATIC int lag_solve(lprec *lp, REAL start_bound, int num_iter)\n{\n  int    i, j, citer, nochange, oldpresolve;\n  MYBOOL LagFeas, AnyFeas, Converged, same_basis;\n  REAL   *OrigObj, *ModObj, *SubGrad, *BestFeasSol;\n  REAL   Zub, Zlb, Znow, Zprev, Zbest, rhsmod, hold;\n  REAL   Phi, StepSize = 0.0, SqrsumSubGrad;\n\n  /* Make sure we have something to work with */\n  if(lp->spx_status != OPTIMAL) {\n    lp->lag_status = NOTRUN;\n    return( lp->lag_status );\n  }\n\n  /* Allocate iteration arrays */\n  if(!allocREAL(lp, &OrigObj, lp->columns + 1, FALSE) ||\n     !allocREAL(lp, &ModObj,  lp->columns + 1, TRUE) ||\n     !allocREAL(lp, &SubGrad, get_Lrows(lp) + 1, TRUE) ||\n     !allocREAL(lp, &BestFeasSol, lp->sum + 1, TRUE)) {\n    lp->lag_status = NOMEMORY;\n     return( lp->lag_status );\n  }\n  lp->lag_status = RUNNING;\n\n  /* Prepare for Lagrangean iterations using results from relaxed problem */\n  oldpresolve = lp->do_presolve;\n  lp->do_presolve = PRESOLVE_NONE;\n  push_basis(lp, NULL, NULL, NULL);\n\n  /* Initialize variables (assume minimization problem in overall structure) */\n  Zlb      = lp->best_solution[0];\n  Zub      = start_bound;\n  Zbest    = Zub;\n  Znow     = Zlb;\n  Zprev    = lp->infinite;\n  rhsmod   = 0;\n\n  Phi      = DEF_LAGCONTRACT; /* In the range 0-2.0 to guarantee convergence */\n/*  Phi      = 0.15; */\n  LagFeas  = FALSE;\n  Converged= FALSE;\n  AnyFeas  = FALSE;\n  citer    = 0;\n  nochange = 0;\n\n  /* Initialize reference and solution vectors; don't bother about the\n     original OF offset since we are maintaining an offset locally. */\n\n/* #define DirectOverrideOF */\n\n  get_row(lp, 0, OrigObj);\n#ifdef DirectOverrideOF\n  set_OF_override(lp, ModObj);\n#endif\n  OrigObj[0] = get_rh(lp, 0);\n  for(i = 1 ; i <= get_Lrows(lp); i++)\n    lp->lambda[i] = 0;\n\n  /* Iterate to convergence, failure or user-specified termination */\n  while((lp->lag_status == RUNNING) && (citer < num_iter)) {\n\n    citer++;\n\n    /* Compute constraint feasibility gaps and associated sum of squares,\n       and determine feasibility over the Lagrangean constraints;\n       SubGrad is the subgradient, which here is identical to the slack. */\n    LagFeas = TRUE;\n    Converged = TRUE;\n    SqrsumSubGrad = 0;\n    for(i = 1; i <= get_Lrows(lp); i++) {\n      hold = lp->lag_rhs[i];\n      for(j = 1; j <= lp->columns; j++)\n        hold -= mat_getitem(lp->matL, i, j) * lp->best_solution[lp->rows + j];\n      if(LagFeas) {\n        if(lp->lag_con_type[i] == EQ) {\n          if(fabs(hold) > lp->epsprimal)\n            LagFeas = FALSE;\n        }\n        else if(hold < -lp->epsprimal)\n          LagFeas = FALSE;\n      }\n      /* Test for convergence and update */\n      if(Converged && (fabs(my_reldiff(hold , SubGrad[i])) > lp->lag_accept))\n        Converged = FALSE;\n      SubGrad[i] = hold;\n      SqrsumSubGrad += hold * hold;\n    }\n    SqrsumSubGrad = sqrt(SqrsumSubGrad);\n#if 1\n    Converged &= LagFeas;\n#endif\n    if(Converged)\n      break;\n\n    /* Modify step parameters and initialize ahead of next iteration */\n    Znow = lp->best_solution[0] - rhsmod;\n    if(Znow > Zub) {\n      /* Handle exceptional case where we overshoot */\n      Phi *= DEF_LAGCONTRACT;\n      StepSize *= (Zub-Zlb) / (Znow-Zlb);\n    }\n    else\n#define LagBasisContract\n#ifdef LagBasisContract\n/*      StepSize = Phi * (Zub - Znow) / SqrsumSubGrad; */\n      StepSize = Phi * (2-DEF_LAGCONTRACT) * (Zub - Znow) / SqrsumSubGrad;\n#else\n      StepSize = Phi * (Zub - Znow) / SqrsumSubGrad;\n#endif\n\n    /* Compute the new dual price vector (Lagrangean multipliers, lambda) */\n    for(i = 1; i <= get_Lrows(lp); i++) {\n      lp->lambda[i] += StepSize * SubGrad[i];\n      if((lp->lag_con_type[i] != EQ) && (lp->lambda[i] > 0)) {\n        /* Handle case where we overshoot and need to correct (see above) */\n        if(Znow < Zub)\n          lp->lambda[i] = 0;\n      }\n    }\n/*    normalizeVector(lp->lambda, get_Lrows(lp)); */\n\n    /* Save the current vector if it is better */\n    if(LagFeas && (Znow < Zbest)) {\n\n      /* Recompute the objective function value in terms of the original values */\n      MEMCOPY(BestFeasSol, lp->best_solution, lp->sum+1);\n      hold = OrigObj[0];\n      for(i = 1; i <= lp->columns; i++)\n        hold += lp->best_solution[lp->rows + i] * OrigObj[i];\n      BestFeasSol[0] = hold;\n      if(lp->lag_trace)\n        report(lp, NORMAL, \"lag_solve: Improved feasible solution at iteration %d of %g\\n\",\n                           citer, hold);\n\n      /* Reset variables */\n      Zbest = Znow;\n      AnyFeas  = TRUE;\n      nochange = 0;\n    }\n    else if(Znow == Zprev) {\n      nochange++;\n      if(nochange > LAG_SINGULARLIMIT) {\n        Phi *= 0.5;\n        nochange = 0;\n      }\n    }\n    Zprev = Znow;\n\n    /* Recompute the objective function values for the next iteration */\n    for(j = 1; j <= lp->columns; j++) {\n      hold = 0;\n      for(i = 1; i <= get_Lrows(lp); i++)\n        hold += lp->lambda[i] * mat_getitem(lp->matL, i, j);\n      ModObj[j] = OrigObj[j] - my_chsign(is_maxim(lp), hold);\n#ifndef DirectOverrideOF\n      set_mat(lp, 0, j, ModObj[j]);\n#endif\n    }\n\n    /* Recompute the fixed part of the new objective function */\n    rhsmod = my_chsign(is_maxim(lp), get_rh(lp, 0));\n    for(i = 1; i <= get_Lrows(lp); i++)\n      rhsmod += lp->lambda[i] * lp->lag_rhs[i];\n\n    /* Print trace/debugging information, if specified */\n    if(lp->lag_trace) {\n      report(lp, IMPORTANT, \"Zub: %10g Zlb: %10g Stepsize: %10g Phi: %10g Feas %d\\n\",\n                 (double) Zub, (double) Zlb, (double) StepSize, (double) Phi, LagFeas);\n      for(i = 1; i <= get_Lrows(lp); i++)\n        report(lp, IMPORTANT, \"%3d SubGrad %10g lambda %10g\\n\",\n                   i, (double) SubGrad[i], (double) lp->lambda[i]);\n      if(lp->sum < 20)\n        print_lp(lp);\n    }\n\n    /* Solve the Lagrangean relaxation, handle failures and compute\n       the Lagrangean objective value, if successful */\n    i = spx_solve(lp);\n    if(lp->spx_status == UNBOUNDED) {\n      if(lp->lag_trace) {\n        report(lp, NORMAL, \"lag_solve: Unbounded solution encountered with this OF:\\n\");\n        for(i = 1; i <= lp->columns; i++)\n          report(lp, NORMAL, RESULTVALUEMASK \" \", (double) ModObj[i]);\n      }\n      goto Leave;\n    }\n    else if((lp->spx_status == NUMFAILURE)   || (lp->spx_status == PROCFAIL) ||\n            (lp->spx_status == USERABORT) || (lp->spx_status == TIMEOUT) ||\n            (lp->spx_status == INFEASIBLE)) {\n      lp->lag_status = lp->spx_status;\n    }\n\n    /* Compare optimal bases and contract if we have basis stationarity */\n#ifdef LagBasisContract\n    same_basis = compare_basis(lp);\n    if(LagFeas &&\n       !same_basis) {\n      pop_basis(lp, FALSE);\n      push_basis(lp, NULL, NULL, NULL);\n      Phi *= DEF_LAGCONTRACT;\n    }\n    if(lp->lag_trace) {\n      report(lp, DETAILED, \"lag_solve: Simplex status code %d, same basis %s\\n\",\n                 lp->spx_status, my_boolstr(same_basis));\n      print_solution(lp, 1);\n    }\n#endif\n  }\n\n  /* Transfer solution values */\n  if(AnyFeas) {\n    lp->lag_bound = my_chsign(is_maxim(lp), Zbest);\n    for(i = 0; i <= lp->sum; i++)\n      lp->solution[i] = BestFeasSol[i];\n    transfer_solution(lp, TRUE);\n    if(!is_maxim(lp))\n      for(i = 1; i <= get_Lrows(lp); i++)\n        lp->lambda[i] = my_flipsign(lp->lambda[i]);\n  }\n\n  /* Do standard postprocessing */\nLeave:\n\n  /* Set status variables and report */\n  if(citer >= num_iter) {\n    if(AnyFeas)\n      lp->lag_status = FEASFOUND;\n    else\n      lp->lag_status = NOFEASFOUND;\n  }\n  else\n    lp->lag_status = lp->spx_status;\n  if(lp->lag_status == OPTIMAL) {\n    report(lp, NORMAL, \"\\nLagrangean convergence achieved in %d iterations\\n\",  citer);\n    i = check_solution(lp, lp->columns,\n                       lp->best_solution, lp->orig_upbo, lp->orig_lowbo, lp->epssolution);\n  }\n  else {\n    report(lp, NORMAL, \"\\nUnsatisfactory convergence achieved over %d Lagrangean iterations.\\n\",\n                       citer);\n    if(AnyFeas)\n      report(lp, NORMAL, \"The best feasible Lagrangean objective function value was %g\\n\",\n                         lp->best_solution[0]);\n  }\n\n  /* Restore the original objective function */\n#ifdef DirectOverrideOF\n  set_OF_override(lp, NULL);\n#else\n  for(i = 1; i <= lp->columns; i++)\n    set_mat(lp, 0, i, OrigObj[i]);\n#endif\n\n  /* ... and then free memory */\n  FREE(BestFeasSol);\n  FREE(SubGrad);\n  FREE(OrigObj);\n  FREE(ModObj);\n  pop_basis(lp, FALSE);\n\n  lp->do_presolve = oldpresolve;\n\n  return( lp->lag_status );\n}\n\nSTATIC int spx_solve(lprec *lp)\n{\n  int       status;\n  MYBOOL    iprocessed;\n\n  lp->total_iter       = 0;\n  lp->total_bswap      = 0;\n  lp->perturb_count    = 0;\n  lp->bb_maxlevel      = 1;\n  lp->bb_totalnodes    = 0;\n  lp->bb_improvements  = 0;\n  lp->bb_strongbranches= 0;\n  lp->is_strongbranch  = FALSE;\n  lp->bb_level         = 0;\n  lp->bb_solutionlevel = 0;\n  lp->best_solution[0] = my_chsign(is_maxim(lp), lp->infinite);\n  if(lp->invB != NULL)\n    lp->bfp_restart(lp);\n\n  lp->spx_status = presolve(lp);\n  if(lp->spx_status == PRESOLVED) {\n    status = lp->spx_status;\n    goto Reconstruct;\n  }\n  else if(lp->spx_status != RUNNING)\n    goto Leave;\n\n  iprocessed = !lp->wasPreprocessed;\n  if(!preprocess(lp) || userabort(lp, -1))\n    goto Leave;\n\n  if(mat_validate(lp->matA)) {\n\n    /* Do standard initializations */\n    lp->solutioncount = 0;\n    lp->real_solution = lp->infinite;\n    set_action(&lp->spx_action, ACTION_REBASE | ACTION_REINVERT);\n    lp->bb_break = FALSE;\n\n    /* Do the call to the real underlying solver (note that\n       run_BB is replaceable with any compatible MIP solver) */\n    status = run_BB(lp);\n\n    /* Restore modified problem */\n    if(iprocessed)\n      postprocess(lp);\n\n    /* Restore data related to presolve (mainly a placeholder as of v5.1) */\nReconstruct:\n    if(!postsolve(lp, status))\n      report(lp, SEVERE, \"spx_solve: Failure during postsolve.\\n\");\n\n    goto Leave;\n  }\n\n  /* If we get here, mat_validate(lp) failed. */\n  if(lp->bb_trace || lp->spx_trace)\n    report(lp, CRITICAL, \"spx_solve: The current LP seems to be invalid\\n\");\n  lp->spx_status = NUMFAILURE;\n\nLeave:\n  lp->timeend = timeNow();\n\n  if((lp->lag_status != RUNNING) && (lp->invB != NULL)) {\n    int       itemp;\n    REAL      test;\n\n    itemp = lp->bfp_nonzeros(lp, TRUE);\n    test = 100;\n    if(lp->total_iter > 0)\n      test *= (REAL) lp->total_bswap/lp->total_iter;\n    report(lp, NORMAL, \"\\n \");\n    report(lp, NORMAL, \"MEMO: lp_solve version %d.%d.%d.%d for %d bit OS, with %d bit REAL variables.\\n\",\n                        MAJORVERSION, MINORVERSION, RELEASE, BUILD, 8*sizeof(void *), 8*sizeof(REAL));\n    report(lp, NORMAL, \"      In the total iteration count %.0f, %.0f (%.1f%%) were bound flips.\\n\",\n                        (double) lp->total_iter, (double) lp->total_bswap, test);\n    report(lp, NORMAL, \"      There were %d refactorizations, %d triggered by time and %d by density.\\n\",\n                        lp->bfp_refactcount(lp, BFP_STAT_REFACT_TOTAL),\n                        lp->bfp_refactcount(lp, BFP_STAT_REFACT_TIMED),\n                        lp->bfp_refactcount(lp, BFP_STAT_REFACT_DENSE));\n    report(lp, NORMAL, \"       ... on average %.1f major pivots per refactorization.\\n\",\n                        get_refactfrequency(lp, TRUE));\n    report(lp, NORMAL, \"      The largest [%s] fact(B) had %d NZ entries, %.1fx largest basis.\\n\",\n                        lp->bfp_name(), itemp, lp->bfp_efficiency(lp));\n    if(lp->perturb_count > 0)\n      report(lp, NORMAL, \"      The bounds were relaxed via perturbations %d times.\\n\",\n                          lp->perturb_count);\n    if(MIP_count(lp) > 0) {\n      if(lp->bb_solutionlevel > 0)\n        report(lp, NORMAL, \"      The maximum B&B level was %d, %.1fx MIP order, %d at the optimal solution.\\n\",\n                        lp->bb_maxlevel, (double) lp->bb_maxlevel / (MIP_count(lp)+lp->int_vars), lp->bb_solutionlevel);\n      else\n        report(lp, NORMAL, \"      The maximum B&B level was %d, %.1fx MIP order, with %.0f nodes explored.\\n\",\n                        lp->bb_maxlevel, (double) lp->bb_maxlevel / (MIP_count(lp)+lp->int_vars), (double) get_total_nodes(lp));\n      if(GUB_count(lp) > 0)\n        report(lp, NORMAL, \"      %d general upper-bounded (GUB) structures were employed during B&B.\\n\",\n                         GUB_count(lp));\n    }\n    report(lp, NORMAL, \"      The constraint matrix inf-norm is %g, with a dynamic range of %g.\\n\",\n                        lp->matA->infnorm, lp->matA->dynrange);\n    report(lp, NORMAL, \"      Time to load data was %.3f seconds, presolve used %.3f seconds,\\n\",\n                        lp->timestart-lp->timecreate, lp->timepresolved-lp->timestart);\n    report(lp, NORMAL, \"       ... %.3f seconds in simplex solver, in total %.3f seconds.\\n\",\n                        lp->timeend-lp->timepresolved, lp->timeend-lp->timecreate);\n  }\n  return( lp->spx_status );\n\n} /* spx_solve */\n\nint lin_solve(lprec *lp)\n{\n  int status = NOTRUN;\n\n  /* Don't do anything in case of an empty model */\n  lp->lag_status = NOTRUN;\n  /* if(get_nonzeros(lp) == 0) { */\n  if(lp->columns == 0) {\n    default_basis(lp);\n    lp->spx_status = NOTRUN;\n    return( /* OPTIMAL */ lp->spx_status);\n  }\n\n  /* Otherwise reset selected arrays before solving */\n  unset_OF_p1extra(lp);\n  free_duals(lp);\n  FREE(lp->drow);\n  FREE(lp->nzdrow);\n  if(lp->bb_cuttype != NULL)\n    freecuts_BB(lp);\n\n  /* Reset/initialize timers */\n  lp->timestart        = timeNow();\n  lp->timeheuristic    = 0;\n  lp->timepresolved    = 0;\n  lp->timeend          = 0;\n\n  /* Do heuristics ahead of solving the model */\n  if(heuristics(lp, AUTOMATIC) != RUNNING)\n    return( INFEASIBLE );\n\n  /* Solve the full, prepared model */\n  status = spx_solve(lp);\n  if((get_Lrows(lp) > 0) && (lp->lag_status == NOTRUN)) {\n    if(status == OPTIMAL)\n      status = lag_solve(lp, lp->bb_heuristicOF, DEF_LAGMAXITERATIONS);\n    else\n      report(lp, IMPORTANT, \"\\nCannot do Lagrangean optimization since root model was not solved.\\n\");\n  }\n\n  /* Reset heuristic in preparation for next run (if any) */\n  lp->bb_heuristicOF = my_chsign(is_maxim(lp), lp->infinite);\n\n  /* Check that correct status code is returned */\n/*\n   peno 26.12.07\n   status was not set to SUBOPTIMAL, only lp->spx_status\n   Bug occured by a change in 5.5.0.10 when  && (lp->bb_totalnodes > 0) was added\n   added status =\n   See UnitTest3\n*/\n/*\n   peno 12.01.08\n   If an integer solution is found with the same objective value as the relaxed solution then\n   searching is stopped. This by setting lp->bb_break. However this resulted in a report of SUBOPTIMAL\n   solution. For this,  && !bb_better(lp, OF_DUALLIMIT, OF_TEST_BE) is added in the test.\n   See UnitTest20\n*/\n  if((lp->spx_status == OPTIMAL) && (lp->bb_totalnodes > 0)) {\n    if((lp->bb_break && !bb_better(lp, OF_DUALLIMIT, OF_TEST_BE)) /* ||\n       ISMASKSET(lp->trace, TRACE_NOBBLIMIT) */)\n    status = lp->spx_status = SUBOPTIMAL;\n  }\n\n  return( status );\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_simplex.h",
    "content": "#ifndef HEADER_lp_simplex\n#define HEADER_lp_simplex\n\n#include \"lp_types.h\"\n\n#define ForceDualSimplexInBB               /* Force use/switch of dual simplex in B&B */\n#define AssumeHighAccuracyInBB    /* No iteration of simplex solves at infeasibility */\n/*#define UseLongStepPruning*/\n/*#define UseLongStepDualPhase1*/\n#define primal_UseRejectionList\n#define dual_UseRejectionList\n#define dual_RemoveBasicFixedVars\n/*#define dual_Phase1PriceEqualities */   /* Force elimination of equality slacks */\n#define AcceptMarginalAccuracy\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\nSTATIC int primloop(lprec *lp, MYBOOL primalfeasible, REAL primaloffset);\nSTATIC int dualloop(lprec *lp, MYBOOL dualfeasible, int dualinfeasibles[], REAL dualoffset);\nSTATIC int spx_run(lprec *lp, MYBOOL validInvB);\nSTATIC int spx_solve(lprec *lp);\nSTATIC int lag_solve(lprec *lp, REAL start_bound, int num_iter);\nSTATIC int heuristics(lprec *lp, int mode);\nSTATIC int lin_solve(lprec *lp);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_simplex */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/cbcc32.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lp_solve driver program with the Borland C++ 5.5 compiler for Windows\r\n\r\n\r\nset src=../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c lp_solve.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c ../lp_MDO.c ../colamd/colamd.c\r\nset c=bcc32 -w-8004 -w-8057\r\nrem  -DLLONG=__int64\r\n\r\nset PLATFORM=win32\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\n%c% -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared -a8 -DWIN32 -DYY_NEVER_INTERACTIVE=1 -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine -ebin\\%PLATFORM%\\lp_solve.exe %src%\r\n\r\nif exist *.obj del *.obj\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/ccc",
    "content": ":\nsrc='../lp_MDO.c ../shared/commonlib.c ../colamd/colamd.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c lp_solve.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\nc=cc\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\nmath=-lm\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'main(){isnan(0.0);}'>>/tmp/isnan.c\n$c /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\nopts='-O3'\n\ndef=\nif [ \"$PLATFORM\" = \"SCO_UNIX\" ]\nthen opts='-O0'\n     def='-dy -K PIC -DLLONG=long'\n     dl=-ldl\nelse dl=-ldl\nfi\n\n$c -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src -o bin/$PLATFORM/lp_solve $math $dl\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/ccc.osx",
    "content": ":\nsrc='../lp_MDO.c ../shared/commonlib.c ../colamd/colamd.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c lp_solve.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\nc=cc\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'main(){printf(\"osx%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\nmath=-lm\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'main(){isnan(0.0);}'>>/tmp/isnan.c\n$c /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\ndef=\ndl=-ldl\n\nopts='-idirafter /usr/include/sys -O3 -DINTEGERTIME -Wno-long-double'\n\n$c -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src -o bin/$PLATFORM/lp_solve $math $dl\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/cgcc.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lp_solve driver program with the GNU gcc compiler under Windows\r\n\r\nset c=gcc\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% platform.c -o platform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nset src=../lp_MDO.c ../shared/commonlib.c ../colamd/colamd.c ../shared/mmio.c ../shared/myblas.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c lp_solve.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c ..\\ini.c ..\\lp_params.c\r\n\r\n%c% -DINLINE=static -Wall -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared -O3 -DBFP_CALLMODEL=__stdcall -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src% -o bin\\%PLATFORM%\\lp_solve.exe\r\n\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/cvc6.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lp_solve driver program with the Microsoft Visual C/C++ compiler under Windows\r\n\r\n\r\nset src=../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c lp_solve.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c ../lp_MDO.c ../colamd/colamd.c %1\r\nset c=cl\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% /nologo platform.c /Feplatform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif \"%PLATFORM%\" == \"win32\" goto ok1\r\necho.\r\necho This batch file is entended for 32 bit compilation with MS Visual C 6\r\necho For newer versions use cvc8*.bat\r\ngoto done\r\n:ok1\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\n%c% -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared /O2 /Zp8 /Gd -D\"LP_MAXLINELEN=0\" -DNoParanoia -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine -Febin\\%PLATFORM%\\lp_solve.exe %src%\r\n\r\nif exist *.obj del *.obj\r\n:done\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/cvc6d.bat",
    "content": "call cvc6 -DParanoia %1\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/cvc8.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lp_solve driver program with the Microsoft Visual C/C++ compiler under Windows\r\n\r\nset c=cl\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% /nologo platform.c /Feplatform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nset src=../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c lp_solve.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c ../lp_MDO.c ../colamd/colamd.c %1\r\n\r\n%c% -I.. -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I../shared /O1 /Zp8 /Gd -D\"LP_MAXLINELEN=0\" -DNoParanoia -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine -Febin\\%PLATFORM%\\lp_solve.exe %src%\r\neditbin /LARGEADDRESSAWARE bin\\%PLATFORM%\\lp_solve.exe\r\n\r\nif exist *.obj del *.obj\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/lp_solve.c",
    "content": "#include <string.h>\r\n#include <time.h>\r\n#include <signal.h>\r\n#include <math.h>\r\n#include <ctype.h>\r\n#include \"lp_lib.h\"\r\n\r\n#ifdef FORTIFY\r\n# include \"lp_fortify.h\"\r\n#endif\r\n\r\n#define filetypeLP      1\r\n#define filetypeMPS     2\r\n#define filetypeFREEMPS 3\r\n#define filetypeCPLEX   4\r\n#define filetypeXLI     5\r\n\r\n#define FORCED_EXIT 255\r\n\r\nint EndOfPgr(int i)\r\n{\r\n#   if defined FORTIFY\r\n      Fortify_LeaveScope();\r\n#   endif\r\n    exit(i);\r\n    return(0);\r\n}\r\n\r\nvoid SIGABRT_func(int sig)\r\n {\r\n   EndOfPgr(FORCED_EXIT);\r\n }\r\n\r\nvoid print_help(char *argv[])\r\n{\r\n  printf(\"Usage of %s version %d.%d.%d.%d:\\n\", argv[0], MAJORVERSION, MINORVERSION, RELEASE, BUILD);\r\n  printf(\"%s [options] [[<]input_file]\\n\", argv[0]);\r\n  printf(\"List of options:\\n\");\r\n  printf(\"-h\\t\\tprints this message\\n\");\r\n#if defined PARSER_LP\r\n  printf(\"-lp\\t\\tread from LP file (default)\\n\");\r\n#endif\r\n  printf(\"-mps\\t\\tread from MPS file, default in fixed format\\n\");\r\n  printf(\"-mps_free\\t\\tuse free format\\n\");\r\n  printf(\"-mps_ibm\\t\\tinterprete integers accoring to ibm format\\n\");\r\n  printf(\"-mps_negobjconst\\tnegate objective constant\\n\");\r\n  printf(\"-fmps\\t\\tread from MPS file in free format\\n\");\r\n  printf(\"-rpar filename\\tread parameters from filename.\\n\");\r\n  printf(\"-rparopt options\\n\\t\\toptions for parameter file:\\n\");\r\n  printf(\"\\t\\t -H headername: header name for parameters. By default 'Default'\\n\");\r\n  printf(\"-rxli xliname filename\\n\\t\\tread file with xli library\\n\");\r\n  printf(\"-rxlidata datafilename\\n\\t\\tdata file name for xli library.\\n\");\r\n  printf(\"-rxliopt options\\n\\t\\toptions for xli library.\\n\");\r\n  printf(\"-rbas filename\\tread basis from filename.\\n\");\r\n  printf(\"-gbas filename\\tguess basis with variables from filename.\\n\");\r\n  printf(\"-plp\\t\\tprint model.\\n\");\r\n  printf(\"-wlp filename\\twrite to LP file\\n\");\r\n  printf(\"-wmps filename\\twrite to MPS file in fixed format\\n\");\r\n  printf(\"-wfmps filename\\twrite to MPS file in free format\\n\");\r\n  printf(\"-wxli xliname filename\\n\\t\\twrite file with xli library\\n\");\r\n  printf(\"-wxliopt options\\n\\t\\toptions for xli library.\\n\");\r\n  printf(\"-wxlisol xliname filename\\n\\t\\twrite solution file with xli library\\n\");\r\n  printf(\"-wxlisolopt options\\n\\t\\toptions for xli library.\\n\");\r\n  printf(\"-wbas filename\\twrite basis to filename.\\n\");\r\n  printf(\"-wpar filename\\twrite parameters to filename.\\n\");\r\n  printf(\"-wparopt options\\n\\t\\toptions for parameter file:\\n\");\r\n  printf(\"\\t\\t -H headername: header name for parameters. By default 'Default'\\n\");\r\n  printf(\"-wafter\\t\\tWrite model after solve (useful if presolve used).\\n\");\r\n  printf(\"-parse_only\\tparse input file but do not solve\\n\");\r\n  printf(\"-nonames\\tIgnore variables and constraint names\\n\");\r\n  printf(\"-norownames\\tIgnore constraint names\\n\");\r\n  printf(\"-nocolnames\\tIgnore variable names\\n\");\r\n  printf(\"\\n\");\r\n  printf(\"-min\\t\\tMinimize the lp problem (overrules setting in file)\\n\");\r\n  printf(\"-max\\t\\tMaximize the lp problem (overrules setting in file)\\n\");\r\n  printf(\"-r <value>\\tspecify max nbr of pivots between a re-inversion of the matrix\\n\");\r\n  printf(\"-piv <rule>\\tspecify simplex pivot rule\\n\");\r\n  printf(\"\\t -piv0: Select first\\n\");\r\n  printf(\"\\t -piv1: Select according to Dantzig\\n\");\r\n  printf(\"\\t -piv2: Select Devex pricing from Paula Harris (default)\\n\");\r\n  printf(\"\\t -piv3: Select steepest edge\\n\");\r\n  printf(\"These pivot rules can be combined with any of the following:\\n\");\r\n  printf(\"-pivf\\t\\tIn case of Steepest Edge, fall back to DEVEX in primal.\\n\");\r\n  printf(\"-pivm\\t\\tMultiple pricing.\\n\");\r\n  printf(\"-piva\\t\\tTemporarily use First Index if cycling is detected.\\n\");\r\n  printf(\"-pivr\\t\\tAdds a small randomization effect to the selected pricer.\\n\");\r\n#if defined EnablePartialOptimization\r\n  printf(\"-pivp\\t\\tEnable partial pricing.\\n\");\r\n  printf(\"-pivpc\\t\\tEnable partial pricing on columns.\\n\");\r\n  printf(\"-pivpr\\t\\tEnable partial pricing on rows.\\n\");\r\n#endif\r\n  printf(\"-pivll\\t\\tScan entering/leaving columns left rather than right.\\n\");\r\n  printf(\"-pivla\\t\\tScan entering/leaving columns alternatingly left/right.\\n\");\r\n  printf(\"-pivh\\t\\tUse Harris' primal pivot logic rather than the default.\\n\");\r\n  printf(\"-pivt\\t\\tUse true norms for Devex and Steepest Edge initializations.\\n\");\r\n  printf(\"-o0\\t\\tDon't put objective in basis%s.\\n\", DEF_OBJINBASIS ? \"\" : \" (default)\");\r\n  printf(\"-o1\\t\\tPut objective in basis%s.\\n\", DEF_OBJINBASIS ? \" (default)\" : \"\");\r\n  printf(\"-s <mode> <scaleloop>\\tuse automatic problem scaling.\\n\");\r\n  printf(\"\\t -s0: No scaling\\n\");\r\n  printf(\"\\t -s1: Geometric scaling (default)\\n\");\r\n  printf(\"\\t -s2: Curtis-reid scaling\\n\");\r\n  printf(\"\\t -s3: Scale to convergence using largest absolute value\\n\");\r\n  printf(\"\\t  -s:\\n\");\r\n  printf(\"\\t -s4: Numerical range-based scaling\\n\");\r\n  printf(\"\\t -s5: Scale to convergence using logarithmic mean of all values\\n\");\r\n  printf(\"\\t -s6: Scale based on the simple numerical range\\n\");\r\n  printf(\"\\t -s7: Scale quadratic\\n\");\r\n  printf(\"These scaling rules can be combined with any of the following:\\n\");\r\n  printf(\"-sp\\t\\talso do power scaling.\\n\");\r\n  printf(\"-si\\t\\talso do Integer scaling (default).\\n\");\r\n  printf(\"-se\\t\\talso do equilibration to scale to the -1..1 range (default).\\n\");\r\n  printf(\"-presolve\\tpresolve problem before start optimizing (rows+columns)\\n\");\r\n  printf(\"-presolverow\\tpresolve problem before start optimizing (rows only)\\n\");\r\n  printf(\"-presolvecol\\tpresolve problem before start optimizing (columns only)\\n\");\r\n  printf(\"-presolvel\\talso eliminate linearly dependent rows\\n\");\r\n  printf(\"-presolves\\talso convert constraints to SOSes (only SOS1 handled)\\n\");\r\n  printf(\"-presolver\\tIf the phase 1 solution process finds that a constraint is\\n\\t\\tredundant then this constraint is deleted\\n\");\r\n  printf(\"-presolvek\\tSimplification of knapsack-type constraints through\\n\\t\\taddition of an extra variable, which also helps bound the OF\\n\");\r\n  printf(\"-presolveq\\tDirect substitution of one variable in 2-element equality\\n\\t\\tconstraints; this requires changes to the constraint matrix\\n\");\r\n  printf(\"-presolvem\\tMerge rows\\n\");\r\n  printf(\"-presolvefd\\tCOLFIXDUAL\\n\");\r\n  printf(\"-presolvebnd\\tPresolve bounds\\n\");\r\n  printf(\"-presolved\\tPresolve duals\\n\");\r\n  printf(\"-presolvef\\tIdentify implied free variables (releasing their expl. bounds)\\n\");\r\n  printf(\"-presolveslk\\tIMPLIEDSLK\\n\");\r\n  printf(\"-presolveg\\tReduce (tighten) coef. in integer models based on GCD argument\\n\");\r\n  printf(\"-presolveb\\tAttempt to fix binary variables at one of their bounds\\n\");\r\n  printf(\"-presolvec\\tAttempt to reduce coefficients in binary models\\n\");\r\n  printf(\"-presolverowd\\tIdenfify and delete qualifying constraints that\\n\\t\\tare dominated by others, also fixes variables at a bound\\n\");\r\n  printf(\"-presolvecold\\tDeletes variables (mainly binary), that are dominated\\n\\t\\tby others (only one can be non-zero)\\n\");\r\n  printf(\"-C <mode>\\tbasis crash mode\\n\");\r\n  printf(\"\\t -C0: No crash basis\\n\");\r\n  printf(\"\\t -C2: Most feasible basis\\n\");\r\n  printf(\"\\t -C3: Least degenerate basis\\n\");\r\n  printf(\"-prim\\t\\tPrefer the primal simplex for both phases.\\n\");\r\n  printf(\"-dual\\t\\tPrefer the dual simplex for both phases.\\n\");\r\n  printf(\"-simplexpp\\tSet Phase1 Primal, Phase2 Primal.\\n\");\r\n  printf(\"-simplexdp\\tSet Phase1 Dual, Phase2 Primal.\\n\");\r\n  printf(\"-simplexpd\\tSet Phase1 Primal, Phase2 Dual.\\n\");\r\n  printf(\"-simplexdd\\tSet Phase1 Dual, Phase2 Dual.\\n\");\r\n  printf(\"-degen\\t\\tuse perturbations to reduce degeneracy,\\n\\t\\tcan increase numerical instability\\n\");\r\n  printf(\"-degenc\\t\\tuse column check to reduce degeneracy\\n\");\r\n  printf(\"-degend\\t\\tdynamic check to reduce degeneracy\\n\");\r\n  printf(\"-degenf\\t\\tanti-degen fixedvars\\n\");\r\n  printf(\"-degens\\t\\tanti-degen stalling\\n\");\r\n  printf(\"-degenn\\t\\tanti-degen numfailure\\n\");\r\n  printf(\"-degenl\\t\\tanti-degen lostfeas\\n\");\r\n  printf(\"-degeni\\t\\tanti-degen infeasible\\n\");\r\n  printf(\"-degenb\\t\\tanti-degen B&B\\n\");\r\n  printf(\"-degenr\\t\\tanti-degen Perturbation of the working RHS at refactorization\\n\");\r\n  printf(\"-degenp\\t\\tanti-degen Limit bound flips\\n\");\r\n  printf(\"-trej <Trej>\\tset minimum pivot value\\n\");\r\n  printf(\"-epsd <epsd>\\tset minimum tolerance for reduced costs\\n\");\r\n  printf(\"-epsb <epsb>\\tset minimum tolerance for the RHS\\n\");\r\n  printf(\"-epsel <epsel>\\tset tolerance for rounding values to zero\\n\");\r\n  printf(\"-epsp <epsp>\\tset the value that is used as perturbation scalar for\\n\\t\\tdegenerative problems\\n\");\r\n  printf(\"-improve <level>\\titerative improvement level\\n\");\r\n  printf(\"\\t -improve0: none\\n\");\r\n  printf(\"\\t -improve1: Running accuracy measurement of solved equations on Bx=r\\n\");\r\n  printf(\"\\t -improve2: Improve initial dual feasibility by bound flips (default)\\n\");\r\n  printf(\"\\t -improve4: Low-cost accuracy monitoring in the dual\\n\");\r\n  printf(\"\\t -improve8: check for primal/dual feasibility at the node level\\n\");\r\n  printf(\"-timeout <sec>\\tTimeout after sec seconds when not solution found.\\n\");\r\n/*\r\n  printf(\"-timeoutok\\tIf timeout, take the best yet found solution.\\n\");\r\n*/\r\n  printf(\"-bfp <filename>\\tSet basis factorization package.\\n\");\r\n  printf(\"\\n\");\r\n  printf(\"-noint\\t\\tIgnore integer restrictions\\n\");\r\n  printf(\"-e <number>\\tspecifies the tolerance which is used to determine whether a\\n\\t\\tfloating point number is in fact an integer.\\n\\t\\tShould be < 0.5\\n\");\r\n  printf(\"-g <number>\\n\");\r\n  printf(\"-ga <number>\\tspecifies the absolute MIP gap for branch-and-bound.\\n\\t\\tThis specifies the absolute allowed tolerance\\n\\t\\ton the object function. Can result in faster solving times.\\n\");\r\n  printf(\"-gr <number>\\tspecifies the relative MIP gap for branch-and-bound.\\n\\t\\tThis specifies the relative allowed tolerance\\n\\t\\ton the object function. Can result in faster solving times.\\n\");\r\n  printf(\"-f\\t\\tspecifies that branch-and-bound algorithm stops at first found\\n\");\r\n  printf(\"\\t\\tsolution\\n\");\r\n  printf(\"-b <bound>\\tspecify a lower bound for the objective function\\n\\t\\tto the program. If close enough, may speed up the\\n\\t\\tcalculations.\\n\");\r\n  printf(\"-o <value>\\tspecifies that branch-and-bound algorithm stops when objective\\n\");\r\n  printf(\"\\t\\tvalue is better than value\\n\");\r\n  printf(\"-c\\n\");\r\n  printf(\"-cc\\t\\tduring branch-and-bound, take the ceiling branch first\\n\");\r\n  printf(\"-cf\\t\\tduring branch-and-bound, take the floor branch first\\n\");\r\n  printf(\"-ca\\t\\tduring branch-and-bound, the algorithm chooses branch\\n\");\r\n  printf(\"-depth <limit>\\tset branch-and-bound depth limit\\n\");\r\n  printf(\"-n <solnr>\\tspecify which solution number to return\\n\");\r\n  printf(\"-B <rule>\\tspecify branch-and-bound rule\\n\");\r\n  printf(\"\\t -B0: Select Lowest indexed non-integer column (default)\\n\");\r\n  printf(\"\\t -B1: Selection based on distance from the current bounds\\n\");\r\n  printf(\"\\t -B2: Selection based on the largest current bound\\n\");\r\n  printf(\"\\t -B3: Selection based on largest fractional value\\n\");\r\n  printf(\"\\t -B4: Simple, unweighted pseudo-cost of a variable\\n\");\r\n  printf(\"\\t -B5: This is an extended pseudo-costing strategy based on minimizing\\n\\t      the number of integer infeasibilities\\n\");\r\n  printf(\"\\t -B6: This is an extended pseudo-costing strategy based on maximizing\\n\\t      the normal pseudo-cost divided by the number of infeasibilities.\\n\\t      Similar to (the reciprocal of) a cost/benefit ratio\\n\");\r\n  printf(\"These branch-and-bound rules can be combined with any of the following:\\n\");\r\n  printf(\"-Bw\\t\\tWeightReverse branch-and-bound\\n\");\r\n  printf(\"-Bb\\t\\tBranchReverse branch-and-bound\\n\");\r\n  printf(\"-Bg\\t\\tGreedy branch-and-bound\\n\");\r\n  printf(\"-Bp\\t\\tPseudoCost branch-and-bound\\n\");\r\n  printf(\"-BR\\t\\tExtended PseudoCost branch-and-bound\\n\");\r\n  printf(\"-Bf\\t\\tDepthFirst branch-and-bound\\n\");\r\n  printf(\"-Br\\t\\tRandomize branch-and-bound\\n\");\r\n  printf(\"-BG\\t\\tGubMode branch-and-bound\\n\");\r\n  printf(\"-Bd\\t\\tDynamic branch-and-bound\\n\");\r\n  printf(\"-Bs\\t\\tRestartMode branch-and-bound\\n\");\r\n  printf(\"-BB\\t\\tBreadthFirst branch-and-bound\\n\");\r\n  printf(\"-Bo\\t\\tOrder variables to improve branch-and-bound performance\\n\");\r\n  printf(\"-Bc\\t\\tDo bound tightening during B&B based of reduced cost info\\n\");\r\n  printf(\"-Bi\\t\\tInitialize pseudo-costs by strong branching\\n\");\r\n  printf(\"\\n\");\r\n  printf(\"-time\\t\\tPrint CPU time to parse input and to calculate result.\\n\");\r\n  printf(\"-v <level>\\tverbose mode, gives flow through the program.\\n\");\r\n  printf(\"\\t\\t if level not provided (-v) then -v4 (NORMAL) is taken.\\n\");\r\n  printf(\"\\t -v0: NEUTRAL\\n\");\r\n  printf(\"\\t -v1: CRITICAL\\n\");\r\n  printf(\"\\t -v2: SEVERE\\n\");\r\n  printf(\"\\t -v3: IMPORTANT (default)\\n\");\r\n  printf(\"\\t -v4: NORMAL\\n\");\r\n  printf(\"\\t -v5: DETAILED\\n\");\r\n  printf(\"\\t -v6: FULL\\n\");\r\n  printf(\"-t\\t\\ttrace pivot selection\\n\");\r\n  printf(\"-d\\t\\tdebug mode, all intermediate results are printed,\\n\\t\\tand the branch-and-bound decisions\\n\");\r\n  printf(\"-R\\t\\treport information while solving the model\\n\");\r\n  printf(\"-Db <filename>\\tDo a generic readable data dump of key lp_solve model variables\\n\\t\\tbefore solve.\\n\\t\\tPrincipally for run difference and debugging purposes\\n\");\r\n  printf(\"-Da <filename>\\tDo a generic readable data dump of key lp_solve model variables\\n\\t\\tafter solve.\\n\\t\\tPrincipally for run difference and debugging purposes\\n\");\r\n  printf(\"-i\\t\\tprint all intermediate valid solutions.\\n\\t\\tCan give you useful solutions even if the total run time\\n\\t\\tis too long\\n\");\r\n  printf(\"-ia\\t\\tprint all intermediate (only non-zero values) valid solutions.\\n\\t\\tCan give you useful solutions even if the total run time\\n\\t\\tis too long\\n\");\r\n  printf(\"-stat\\t\\tPrint model statistics\\n\");\r\n  printf(\"-S <detail>\\tPrint solution. If detail omitted, then -S2 is used.\\n\");\r\n  printf(\"\\t -S0: Print nothing\\n\");\r\n  printf(\"\\t -S1: Only objective value\\n\");\r\n  printf(\"\\t -S2: Obj value+variables (default)\\n\");\r\n  printf(\"\\t -S3: Obj value+variables+constraints\\n\");\r\n  printf(\"\\t -S4: Obj value+variables+constraints+duals\\n\");\r\n  printf(\"\\t -S5: Obj value+variables+constraints+duals+lp model\\n\");\r\n  printf(\"\\t -S6: Obj value+variables+constraints+duals+lp model+scales\\n\");\r\n  printf(\"\\t -S7: Obj value+variables+constraints+duals+lp model+scales+lp tableau\\n\");\r\n}\r\n\r\nvoid print_cpu_times(const char *info)\r\n{\r\n  static clock_t last_time = 0;\r\n  clock_t new_time;\r\n\r\n  new_time = clock();\r\n  fprintf(stderr, \"CPU Time for %s: %gs (%gs total since program start)\\n\",\r\n          info, (new_time - last_time) / (double) CLOCKS_PER_SEC,\r\n          new_time / (double) CLOCKS_PER_SEC);\r\n  last_time = new_time;\r\n}\r\n\r\n#if 0\r\nint myabortfunc(lprec *lp, void *aborthandle)\r\n{\r\n  /* printf(\"%f\\n\",lp->rhs[0]*(lp->maximise ? 1 : -1)); */\r\n  return(0);\r\n}\r\n#endif\r\n\r\nstatic MYBOOL isNum(char *val)\r\n{\r\n  int ord;\r\n  char *pointer;\r\n\r\n  ord = strtol(val, &pointer, 10);\r\n  return(*pointer == 0);\r\n}\r\n\r\nstatic void DoReport(lprec *lp, char *str)\r\n{\r\n  fprintf(stderr, \"%s %6.1fsec %8g\\n\", str, time_elapsed(lp), get_working_objective(lp));\r\n}\r\n\r\nstatic void __WINAPI LPMessageCB(lprec *lp, void *USERHANDLE, int msg)\r\n{\r\n  if(msg==MSG_LPFEASIBLE)\r\n    DoReport(lp, \"Feasible solution \");\r\n  else if(msg==MSG_LPOPTIMAL)\r\n    DoReport(lp, \"Real solution \");\r\n  else if(msg==MSG_MILPFEASIBLE)\r\n    DoReport(lp, \"First MILP    \");\r\n  else if(msg==MSG_MILPBETTER)\r\n    DoReport(lp, \"Improved MILP \");\r\n}\r\n\r\nvoid write_model(lprec *lp, char plp, char *wlp, char *wmps, char *wfmps, char *wxli, char *wxlisol, char *wxliname, char *wxlioptions)\r\n{\r\n  if(plp)\r\n    print_lp(lp);\r\n\r\n  if(wlp != NULL)\r\n    write_lp(lp, wlp);\r\n\r\n  if(wmps != NULL)\r\n    write_mps(lp, wmps);\r\n\r\n  if(wfmps != NULL)\r\n    write_freemps(lp, wfmps);\r\n\r\n  if((wxliname != NULL) && (wxli != NULL)) {\r\n    if(!set_XLI(lp, wxliname)) {\r\n      fprintf(stderr, \"Unable to set XLI library (%s).\\n\", wxliname);\r\n      EndOfPgr(FORCED_EXIT);\r\n    }\r\n    write_XLI(lp, wxli, wxlioptions, FALSE);\r\n    set_XLI(lp, NULL);\r\n  }\r\n\r\n  if((wxliname != NULL) && (wxlisol != NULL)) {\r\n    if(!set_XLI(lp, wxliname)) {\r\n      fprintf(stderr, \"Unable to set XLI library (%s).\\n\", wxliname);\r\n      EndOfPgr(FORCED_EXIT);\r\n    }\r\n    write_XLI(lp, wxlisol, wxlioptions, TRUE);\r\n    set_XLI(lp, NULL);\r\n  }\r\n}\r\n\r\nstatic void or_value(int *value, int orvalue)\r\n{\r\n  if(*value == -1)\r\n    *value = 0;\r\n  *value |= orvalue;\r\n}\r\n\r\nstatic void set_value(int *value, int orvalue)\r\n{\r\n  *value = orvalue;\r\n}\r\n\r\n#define nstats 5\r\n\r\nstatic void minmax1(REAL value0, REAL factor, REAL *minmax, int *nminmax, int row, int *rowminmax, int col, int *colminmax)\r\n{\r\n  int i, n;\r\n  REAL value;\r\n\r\n  if (value0 == 0)\r\n    return;\r\n  value = fabs(value0) * factor;\r\n  for (i = 0; (i < *nminmax) && (value <= fabs(minmax[i]) * factor); i++)\r\n    if (value == fabs(minmax[i]) * factor)\r\n      return;\r\n  if (i >= nstats)\r\n    return;\r\n  n = *nminmax;\r\n  if (n == nstats)\r\n    n--;\r\n  memmove(minmax + i + 1, minmax + i, (n - i) * sizeof(*minmax));\r\n  minmax[i] = value0;\r\n  if (rowminmax != NULL) {\r\n    memmove(rowminmax + i + 1, rowminmax + i, (n - i) * sizeof(*rowminmax));\r\n    rowminmax[i] = row;\r\n  }\r\n  if (colminmax != NULL) {\r\n    memmove(colminmax + i + 1, colminmax + i, (n - i) * sizeof(*colminmax));\r\n    colminmax[i] = col;\r\n  }\r\n  if (*nminmax < nstats)\r\n    (*nminmax)++;\r\n}\r\n\r\nstatic void minmax(REAL value, REAL *minima, REAL *maxima, int *nminima, int *nmaxima, int row, int *rowmin, int *rowmax, int col, int *colmin, int *colmax)\r\n{\r\n  minmax1(value, -1.0, minima, nminima, row, rowmin, col, colmin);\r\n  minmax1(value, +1.0, maxima, nmaxima, row, rowmax, col, colmax);\r\n}\r\n\r\n/*\r\nstatic void printminmax1(lprec *lp, char *s, REAL *minmax, int nminmax, int *rowminmax, int *colminmax)\r\n{\r\n  int i;\r\n\r\n  for (i = 0; i < nminmax; i++) {\r\n    printf(\" %s(\", s);\r\n    if (rowminmax != NULL)\r\n      printf(\"%s\", get_row_name(lp, rowminmax[i]));\r\n    if ((rowminmax != NULL) && (colminmax != NULL))\r\n      printf(\", \");\r\n    if (colminmax != NULL)\r\n      printf(\"%s\", get_col_name(lp, colminmax[i]));\r\n    printf(\") = %.8f\\n\", minmax[i]);\r\n  }\r\n}\r\n\r\nstatic void printminmax(lprec *lp, char *s, REAL *minima, REAL *maxima, int nminima, int nmaxima, int *rowmin, int *rowmax, int *colmin, int *colmax)\r\n{\r\n  printf(\"Minima:\\n\");\r\n  printminmax1(lp, s, minima, nminima, rowmin, colmin);\r\n  printf(\"Maxima:\\n\");\r\n  printminmax1(lp, s, maxima, nmaxima, rowmax, colmax);\r\n}\r\n*/\r\n\r\nstatic void printminmax(lprec *lp, char *s, REAL *minima, REAL *maxima, int nminima, int nmaxima, int *rowmin, int *rowmax, int *colmin, int *colmax)\r\n{\r\n  int i, nminmax, n;\r\n\r\n  nminmax = nminima;\r\n  if (nmaxima > nminmax)\r\n    nminmax = nmaxima;\r\n  for (i = 0; i < nminmax; i++) {\r\n    n = 0;\r\n    if (i < nminima) {\r\n      n += printf(\"%s(\", s);\r\n      if (rowmin != NULL)\r\n        n+= printf(\"%s\", get_row_name(lp, rowmin[i]));\r\n      if ((rowmin != NULL) && (colmin != NULL))\r\n        n += printf(\", \");\r\n      if (colmin != NULL)\r\n        n += printf(\"%s\", get_col_name(lp, colmin[i]));\r\n      n += printf(\") = %.8f\", minima[i]);\r\n    }\r\n    if (n < 40)\r\n      n = 40 - n;\r\n    else\r\n      n = 1;\r\n    printf(\"%*.*s\", n, n, \"\");\r\n\r\n    if (i < nmaxima) {\r\n      n += printf(\"%s(\", s);\r\n      if (rowmax != NULL)\r\n        n+= printf(\"%s\", get_row_name(lp, rowmax[i]));\r\n      if ((rowmax != NULL) && (colmax != NULL))\r\n        n += printf(\", \");\r\n      if (colmax != NULL)\r\n        n += printf(\"%s\", get_col_name(lp, colmax[i]));\r\n      n += printf(\") = %.8f\", maxima[i]);\r\n    }\r\n\r\n    printf(\"\\n\");\r\n  }\r\n}\r\n\r\nstatic void print_statistics(lprec *lp)\r\n{\r\n  REAL *col, *RHSmin, *RHSmax, *OBJmin, *OBJmax, *MATmin, *MATmax;\r\n  int *nz, ret, m, n, i, j, k, l, nRHSmin = 0, nRHSmax = 0, nOBJmin = 0, nOBJmax = 0, nMATmin = 0, nMATmax = 0, *rowRHSmin, *rowRHSmax, *colOBJmin, *colOBJmax, *rowMATmin, *rowMATmax, *colMATmin, *colMATmax;\r\n\r\n  m = get_Nrows(lp);\r\n  n = get_Ncolumns(lp);\r\n\r\n  col = (REAL *) malloc((1 + m) * sizeof(*col));\r\n  nz = (int *) malloc((1 + m) * sizeof(*RHSmin));\r\n  RHSmin = (REAL *) malloc(nstats * sizeof(*RHSmin));\r\n  RHSmax = (REAL *) malloc(nstats * sizeof(*RHSmax));\r\n  rowRHSmin = (int *) malloc(nstats * sizeof(*RHSmin));\r\n  rowRHSmax = (int *) malloc(nstats * sizeof(*RHSmax));\r\n  OBJmin = (REAL *) malloc(nstats * sizeof(*OBJmin));\r\n  OBJmax = (REAL *) malloc(nstats * sizeof(*OBJmax));\r\n  colOBJmin = (int *) malloc(nstats * sizeof(*colOBJmin));\r\n  colOBJmax = (int *) malloc(nstats * sizeof(*colOBJmax));\r\n  MATmin = (REAL *) malloc(nstats * sizeof(*MATmin));\r\n  MATmax = (REAL *) malloc(nstats * sizeof(*MATmax));\r\n  rowMATmin = (int *) malloc(nstats * sizeof(*rowMATmin));\r\n  rowMATmax = (int *) malloc(nstats * sizeof(*rowMATmax));\r\n  colMATmin = (int *) malloc(nstats * sizeof(*colMATmin));\r\n  colMATmax = (int *) malloc(nstats * sizeof(*colMATmax));\r\n\r\n/*\r\n  minmax(2.0, MATmin, MATmax, &nMATmin, &nMATmax, 1, rowMATmin, rowMATmax, 8, colMATmin, colMATmax);\r\n  minmax(1.0, MATmin, MATmax, &nMATmin, &nMATmax, 2, rowMATmin, rowMATmax, 7, colMATmin, colMATmax);\r\n  minmax(1.5, MATmin, MATmax, &nMATmin, &nMATmax, 3, rowMATmin, rowMATmax, 6, colMATmin, colMATmax);\r\n  minmax(3.0, MATmin, MATmax, &nMATmin, &nMATmax, 4, rowMATmin, rowMATmax, 5, colMATmin, colMATmax);\r\n  minmax(4.0, MATmin, MATmax, &nMATmin, &nMATmax, 5, rowMATmin, rowMATmax, 4, colMATmin, colMATmax);\r\n  minmax(0.1, MATmin, MATmax, &nMATmin, &nMATmax, 6, rowMATmin, rowMATmax, 3, colMATmin, colMATmax);\r\n  minmax(5.0, MATmin, MATmax, &nMATmin, &nMATmax, 7, rowMATmin, rowMATmax, 2, colMATmin, colMATmax);\r\n  minmax(1.4, MATmin, MATmax, &nMATmin, &nMATmax, 8, rowMATmin, rowMATmax, 1, colMATmin, colMATmax);\r\n\r\n  printminmax(MATmin, MATmax, nMATmin, nMATmax, rowMATmin, rowMATmax, colMATmin, colMATmax);\r\n*/\r\n\r\n  for (i = 1; i <= m; i++)\r\n    minmax(get_rh(lp, i), RHSmin, RHSmax, &nRHSmin, &nRHSmax, i, rowRHSmin, rowRHSmax, 0, NULL, NULL);\r\n\r\n  for (j = 1; j <= n; j++) {\r\n    ret = get_columnex(lp, j, col, nz);\r\n    for (i = 0; i < ret; i++)\r\n      if (nz[i] == 0)\r\n        minmax(col[i], OBJmin, OBJmax, &nOBJmin, &nOBJmax, 0, NULL, NULL, j, colOBJmin, colOBJmax);\r\n      else\r\n        minmax(col[i], MATmin, MATmax, &nMATmin, &nMATmax, nz[i], rowMATmin, rowMATmax, j, colMATmin, colMATmax);\r\n  }\r\n\r\n  printf(\"Constraints: %d\\n\", get_Nrows(lp));\r\n  printf(\"Variables  : %d\\n\", get_Ncolumns(lp));\r\n  for (j = k = l = 0, i = n; i >= 1; i--) {\r\n    if (is_int(lp, i))\r\n      j++;\r\n    if (is_semicont(lp, i))\r\n      k++;\r\n    if (is_SOS_var(lp, i))\r\n      l++;\r\n  }\r\n  printf(\"Integers   : %d\\n\", j);\r\n  printf(\"Semi-cont  : %d\\n\", k);\r\n  printf(\"SOS        : %d\\n\", l);\r\n  k = get_nonzeros(lp);\r\n  printf(\"Non-zeros  : %d\\tdensity=%f%%\\n\", k, ((double) k) / (((double) m) * ((double) n)) * 100.0);\r\n\r\n  printf(\"\\nAbsolute Ranges:\\n\\n       Minima                                  Maxima\\n\");\r\n  printf(\"\\nMatrix Coeficients:\\n\");\r\n  printminmax(lp, \"A\", MATmin, MATmax, nMATmin, nMATmax, rowMATmin, rowMATmax, colMATmin, colMATmax);\r\n\r\n  printf(\"\\nObj. Vector:\\n\");\r\n  printminmax(lp, \"c\", OBJmin, OBJmax, nOBJmin, nOBJmax, NULL, NULL, colOBJmin, colOBJmax);\r\n\r\n  printf(\"\\nRHS Vector:\\n\");\r\n  printminmax(lp, \"b\", RHSmin, RHSmax, nRHSmin, nRHSmax, rowRHSmin, rowRHSmax, NULL, NULL);\r\n\r\n  free(col);\r\n  free(nz);\r\n  free(RHSmin);\r\n  free(RHSmax);\r\n  free(rowRHSmin);\r\n  free(rowRHSmax);\r\n  free(OBJmin);\r\n  free(OBJmax);\r\n  free(colOBJmin);\r\n  free(colOBJmax);\r\n  free(MATmin);\r\n  free(MATmax);\r\n  free(rowMATmin);\r\n  free(rowMATmax);\r\n  free(colMATmin);\r\n  free(colMATmax);\r\n}\r\n\r\nint main(int argc, char *argv[])\r\n{\r\n  lprec *lp = NULL;\r\n  char *filen, *wlp = NULL, *wmps = NULL, *wfmps = NULL, plp = FALSE;\r\n  int i;\r\n  int verbose = IMPORTANT /* CRITICAL */;\r\n  int debug = -1;\r\n  MYBOOL report = FALSE;\r\n  MYBOOL nonames = FALSE, norownames = FALSE, nocolnames = FALSE;\r\n  MYBOOL write_model_after = FALSE;\r\n  MYBOOL noint = FALSE;\r\n  int print_sol = -1;\r\n  MYBOOL print_stats = FALSE;\r\n  int floor_first = -1;\r\n  MYBOOL do_set_bb_depthlimit = FALSE;\r\n  int bb_depthlimit = 0;\r\n  MYBOOL do_set_solutionlimit = FALSE;\r\n  int solutionlimit = 0;\r\n  MYBOOL break_at_first = FALSE;\r\n  int scaling = 0;\r\n  double scaleloop = 0;\r\n  MYBOOL tracing = FALSE;\r\n  short filetype = filetypeLP;\r\n  int anti_degen1 = -1;\r\n  int anti_degen2 = -1;\r\n  short print_timing = FALSE;\r\n  short parse_only = FALSE;\r\n  int do_presolve = -1;\r\n  short objective = 0;\r\n  short PRINT_SOLUTION = 2;\r\n  int improve = -1;\r\n  int pivoting1 = -1;\r\n  int pivoting2 = -1;\r\n  int bb_rule1 = -1;\r\n  int bb_rule2 = -1;\r\n  int max_num_inv = -1;\r\n  int scalemode1 = -1;\r\n  int scalemode2 = -1;\r\n  int crashmode = -1;\r\n  char *guessbasis = NULL;\r\n  /* short timeoutok = FALSE; */\r\n  long sectimeout = -1;\r\n  int result;\r\n  MYBOOL preferdual = AUTOMATIC;\r\n  int simplextype = -1;\r\n  MYBOOL do_set_obj_bound = FALSE;\r\n  REAL obj_bound = 0;\r\n  REAL mip_absgap = -1;\r\n  REAL mip_relgap = -1;\r\n  REAL epsperturb = -1;\r\n  REAL epsint = -1;\r\n  REAL epspivot = -1;\r\n  REAL epsd = -1;\r\n  REAL epsb = -1;\r\n  REAL epsel = -1;\r\n  MYBOOL do_set_break_at_value = FALSE;\r\n  REAL break_at_value = 0;\r\n  FILE *fpin = stdin;\r\n  char *bfp = NULL;\r\n  char *rxliname = NULL, *rxli = NULL, *rxlidata = NULL, *rxlioptions = NULL, *wxliname = NULL, *wxlisol = NULL, *wxli = NULL, *wxlioptions = NULL, *wxlisoloptions = NULL;\r\n  char *rbasname = NULL, *wbasname = NULL;\r\n  char *debugdump_before = NULL;\r\n  char *debugdump_after = NULL;\r\n  char *rparname = NULL;\r\n  char *rparoptions = NULL;\r\n  char *wparname = NULL;\r\n  char *wparoptions = NULL;\r\n  char obj_in_basis = -1;\r\n  char mps_ibm = FALSE;\r\n  char mps_negobjconst = FALSE;\r\n  char mps_free = FALSE;\r\n  MYBOOL ok;\r\n# define SCALINGTHRESHOLD 0.03\r\n\r\n  /* read command line arguments */\r\n\r\n# if defined FORTIFY\r\n   Fortify_EnterScope();\r\n# endif\r\n\r\n  for(i = 1; i < argc; i++) {\r\n    ok = FALSE;\r\n    if(strncmp(argv[i], \"-v\", 2) == 0) {\r\n      if (argv[i][2])\r\n        verbose = atoi(argv[i] + 2);\r\n      else\r\n        verbose = NORMAL;\r\n    }\r\n    else if(strcmp(argv[i], \"-d\") == 0)\r\n      debug = TRUE;\r\n    else if(strcmp(argv[i], \"-R\") == 0)\r\n      report = TRUE;\r\n    else if(strcmp(argv[i], \"-i\") == 0)\r\n      print_sol = TRUE;\r\n    else if(strcmp(argv[i], \"-ia\") == 0)\r\n      print_sol = AUTOMATIC;\r\n    else if(strcmp(argv[i], \"-stat\") == 0)\r\n      print_stats = TRUE;\r\n    else if(strcmp(argv[i], \"-nonames\") == 0)\r\n      nonames = TRUE;\r\n    else if(strcmp(argv[i], \"-norownames\") == 0)\r\n      norownames = TRUE;\r\n    else if(strcmp(argv[i], \"-nocolnames\") == 0)\r\n      nocolnames = TRUE;\r\n    else if((strcmp(argv[i], \"-c\") == 0) || (strcmp(argv[i], \"-cc\") == 0))\r\n      floor_first = BRANCH_CEILING;\r\n    else if(strcmp(argv[i], \"-cf\") == 0)\r\n      floor_first = BRANCH_FLOOR;\r\n    else if(strcmp(argv[i], \"-ca\") == 0)\r\n      floor_first = BRANCH_AUTOMATIC;\r\n    else if((strcmp(argv[i], \"-depth\") == 0) && (i + 1 < argc)) {\r\n      do_set_bb_depthlimit = TRUE;\r\n      bb_depthlimit = atoi(argv[++i]);\r\n    }\r\n    else if(strcmp(argv[i], \"-Bw\") == 0)\r\n      or_value(&bb_rule2, NODE_WEIGHTREVERSEMODE);\r\n    else if(strcmp(argv[i], \"-Bb\") == 0)\r\n      or_value(&bb_rule2, NODE_BRANCHREVERSEMODE);\r\n    else if(strcmp(argv[i], \"-Bg\") == 0)\r\n      or_value(&bb_rule2, NODE_GREEDYMODE);\r\n    else if(strcmp(argv[i], \"-Bp\") == 0)\r\n      or_value(&bb_rule2, NODE_PSEUDOCOSTMODE);\r\n    else if(strcmp(argv[i], \"-BR\") == 0)\r\n      or_value(&bb_rule2, NODE_PSEUDORATIOSELECT);\r\n    else if(strcmp(argv[i], \"-Bf\") == 0)\r\n      or_value(&bb_rule2, NODE_DEPTHFIRSTMODE);\r\n    else if(strcmp(argv[i], \"-Br\") == 0)\r\n      or_value(&bb_rule2, NODE_RANDOMIZEMODE);\r\n    else if(strcmp(argv[i], \"-BG\") == 0)\r\n      or_value(&bb_rule2, 0 /* NODE_GUBMODE */); /* doesn't work yet */\r\n    else if(strcmp(argv[i], \"-Bd\") == 0)\r\n      or_value(&bb_rule2, NODE_DYNAMICMODE);\r\n    else if(strcmp(argv[i], \"-Bs\") == 0)\r\n      or_value(&bb_rule2, NODE_RESTARTMODE);\r\n    else if(strcmp(argv[i], \"-BB\") == 0)\r\n      or_value(&bb_rule2, NODE_BREADTHFIRSTMODE);\r\n    else if(strcmp(argv[i], \"-Bo\") == 0)\r\n      or_value(&bb_rule2, NODE_AUTOORDER);\r\n    else if(strcmp(argv[i], \"-Bc\") == 0)\r\n      or_value(&bb_rule2, NODE_RCOSTFIXING);\r\n    else if(strcmp(argv[i], \"-Bi\") == 0)\r\n      or_value(&bb_rule2, NODE_STRONGINIT);\r\n    else if(strncmp(argv[i], \"-B\", 2) == 0) {\r\n      if (argv[i][2])\r\n        set_value(&bb_rule1, atoi(argv[i] + 2));\r\n      else\r\n        set_value(&bb_rule1, NODE_FIRSTSELECT);\r\n    }\r\n    else if((strcmp(argv[i], \"-n\") == 0) && (i + 1 < argc)) {\r\n      do_set_solutionlimit = TRUE;\r\n      solutionlimit = atoi(argv[++i]);\r\n    }\r\n    else if((strcmp(argv[i], \"-b\") == 0) && (i + 1 < argc)) {\r\n      obj_bound = atof(argv[++i]);\r\n      do_set_obj_bound = TRUE;\r\n    }\r\n    else if(((strcmp(argv[i], \"-g\") == 0) || (strcmp(argv[i], \"-ga\") == 0)) && (i + 1 < argc))\r\n      mip_absgap = atof(argv[++i]);\r\n    else if((strcmp(argv[i], \"-gr\") == 0) && (i + 1 < argc))\r\n      mip_relgap = atof(argv[++i]);\r\n    else if((strcmp(argv[i], \"-e\") == 0) && (i + 1 < argc)) {\r\n      epsint = atof(argv[++i]);\r\n      if((epsint <= 0.0) || (epsint >= 0.5)) {\r\n        fprintf(stderr, \"Invalid tolerance %g; 0 < epsilon < 0.5\\n\",\r\n                (double)epsint);\r\n        EndOfPgr(FORCED_EXIT);\r\n      }\r\n    }\r\n    else if((strcmp(argv[i], \"-r\") == 0) && (i + 1 < argc))\r\n      max_num_inv = atoi(argv[++i]);\r\n    else if((strcmp(argv[i], \"-o\") == 0) && (i + 1 < argc)) {\r\n      break_at_value = atof(argv[++i]);\r\n      do_set_break_at_value = TRUE;\r\n    }\r\n    else if(strcmp(argv[i], \"-f\") == 0)\r\n      break_at_first = TRUE;\r\n    else if(strcmp(argv[i], \"-timeoutok\") == 0)\r\n      /* timeoutok = TRUE */; /* option no longer needed, but still accepted */\r\n    else if(strcmp(argv[i], \"-h\") == 0) {\r\n      print_help(argv);\r\n      EndOfPgr(EXIT_SUCCESS);\r\n    }\r\n    else if(strcmp(argv[i], \"-prim\") == 0)\r\n      preferdual = FALSE;\r\n    else if(strcmp(argv[i], \"-dual\") == 0)\r\n      preferdual = TRUE;\r\n    else if(strcmp(argv[i], \"-simplexpp\") == 0)\r\n      simplextype = SIMPLEX_PRIMAL_PRIMAL;\r\n    else if(strcmp(argv[i], \"-simplexdp\") == 0)\r\n      simplextype = SIMPLEX_DUAL_PRIMAL;\r\n    else if(strcmp(argv[i], \"-simplexpd\") == 0)\r\n      simplextype = SIMPLEX_PRIMAL_DUAL;\r\n    else if(strcmp(argv[i], \"-simplexdd\") == 0)\r\n      simplextype = SIMPLEX_DUAL_DUAL;\r\n    else if(strcmp(argv[i], \"-sp\") == 0)\r\n      or_value(&scalemode2, SCALE_POWER2);\r\n    else if(strcmp(argv[i], \"-si\") == 0)\r\n      or_value(&scalemode2, SCALE_INTEGERS);\r\n    else if(strcmp(argv[i], \"-se\") == 0)\r\n      or_value(&scalemode2, SCALE_EQUILIBRATE);\r\n    else if(strncmp(argv[i], \"-s\", 2) == 0) {\r\n      set_value(&scalemode1, SCALE_NONE);\r\n      scaling = SCALE_MEAN;\r\n      if (argv[i][2]) {\r\n        switch (atoi(argv[i] + 2)) {\r\n        case 0:\r\n          scaling = SCALE_NONE;\r\n          break;\r\n        case 1:\r\n          set_value(&scalemode1, SCALE_GEOMETRIC);\r\n          break;\r\n        case 2:\r\n          set_value(&scalemode1, SCALE_CURTISREID);\r\n          break;\r\n        case 3:\r\n          set_value(&scalemode1, SCALE_EXTREME);\r\n          break;\r\n        case 4:\r\n          set_value(&scalemode1, SCALE_MEAN);\r\n          break;\r\n        case 5:\r\n          set_value(&scalemode1, SCALE_MEAN | SCALE_LOGARITHMIC);\r\n          break;\r\n        case 6:\r\n          set_value(&scalemode1, SCALE_RANGE);\r\n          break;\r\n        case 7:\r\n          set_value(&scalemode1, SCALE_MEAN | SCALE_QUADRATIC);\r\n          break;\r\n        }\r\n      }\r\n      else\r\n        set_value(&scalemode1, SCALE_MEAN);\r\n      if((i + 1 < argc) && (isNum(argv[i + 1])))\r\n        scaleloop = atoi(argv[++i]);\r\n    }\r\n    else if(strncmp(argv[i], \"-C\", 2) == 0)\r\n      crashmode = atoi(argv[i] + 2);\r\n    else if((strcmp(argv[i],\"-gbas\") == 0) && (i + 1 < argc))\r\n      guessbasis = argv[++i];\r\n    else if(strcmp(argv[i], \"-t\") == 0)\r\n      tracing = TRUE;\r\n    else if(strncmp(argv[i], \"-S\", 2) == 0) {\r\n      if (argv[i][2])\r\n        PRINT_SOLUTION = (short) atoi(argv[i] + 2);\r\n      else\r\n        PRINT_SOLUTION = 2;\r\n    }\r\n    else if(strncmp(argv[i], \"-improve\", 8) == 0) {\r\n      if (argv[i][8])\r\n        or_value(&improve, atoi(argv[i] + 8));\r\n    }\r\n    else if(strcmp(argv[i], \"-pivll\") == 0)\r\n      or_value(&pivoting2, PRICE_LOOPLEFT);\r\n    else if(strcmp(argv[i], \"-pivla\") == 0)\r\n      or_value(&pivoting2, PRICE_LOOPALTERNATE);\r\n#if defined EnablePartialOptimization\r\n    else if(strcmp(argv[i], \"-pivpc\") == 0)\r\n      or_value(&pivoting2, PRICE_AUTOPARTIALCOLS);\r\n    else if(strcmp(argv[i], \"-pivpr\") == 0)\r\n      or_value(&pivoting2, PRICE_AUTOPARTIALROWS);\r\n    else if(strcmp(argv[i], \"-pivp\") == 0)\r\n      or_value(&pivoting2, PRICE_AUTOPARTIAL);\r\n#endif\r\n    else if(strcmp(argv[i], \"-pivf\") == 0)\r\n      or_value(&pivoting2, PRICE_PRIMALFALLBACK);\r\n    else if(strcmp(argv[i], \"-pivm\") == 0)\r\n      or_value(&pivoting2, PRICE_MULTIPLE);\r\n    else if(strcmp(argv[i], \"-piva\") == 0)\r\n      or_value(&pivoting2, PRICE_ADAPTIVE);\r\n    else if(strcmp(argv[i], \"-pivr\") == 0)\r\n      or_value(&pivoting2, PRICE_RANDOMIZE);\r\n    else if(strcmp(argv[i], \"-pivh\") == 0)\r\n      or_value(&pivoting2, PRICE_HARRISTWOPASS);\r\n    else if(strcmp(argv[i], \"-pivt\") == 0)\r\n      or_value(&pivoting2, PRICE_TRUENORMINIT);\r\n    else if(strncmp(argv[i], \"-piv\", 4) == 0) {\r\n      if (argv[i][4])\r\n        set_value(&pivoting1, atoi(argv[i] + 4));\r\n      else\r\n    set_value(&pivoting1, PRICER_DEVEX | PRICE_ADAPTIVE);\r\n    }\r\n#if defined PARSER_LP\r\n    else if(strcmp(argv[i],\"-lp\") == 0)\r\n      filetype = filetypeLP;\r\n#endif\r\n    else if((strcmp(argv[i],\"-wlp\") == 0) && (i + 1 < argc))\r\n      wlp = argv[++i];\r\n    else if(strcmp(argv[i],\"-plp\") == 0)\r\n      plp = TRUE;\r\n    else if(strcmp(argv[i],\"-mps\") == 0)\r\n      filetype = filetypeMPS;\r\n    else if(strcmp(argv[i],\"-mps_ibm\") == 0)\r\n      mps_ibm = TRUE;\r\n    else if(strcmp(argv[i],\"-mps_negobjconst\") == 0)\r\n      mps_negobjconst = TRUE;\r\n    else if(strcmp(argv[i],\"-mps_free\") == 0)\r\n      mps_free = TRUE;\r\n    else if(strcmp(argv[i],\"-fmps\") == 0)\r\n      filetype = filetypeFREEMPS;\r\n    else if((strcmp(argv[i],\"-wmps\") == 0) && (i + 1 < argc))\r\n      wmps = argv[++i];\r\n    else if((strcmp(argv[i],\"-wfmps\") == 0) && (i + 1 < argc))\r\n      wfmps = argv[++i];\r\n    else if(strcmp(argv[i],\"-wafter\") == 0)\r\n      write_model_after = TRUE;\r\n    else if(strcmp(argv[i],\"-degen\") == 0)\r\n      set_value(&anti_degen1, ANTIDEGEN_DEFAULT);\r\n    else if(strcmp(argv[i],\"-degenf\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_FIXEDVARS);\r\n    else if(strcmp(argv[i],\"-degenc\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_COLUMNCHECK);\r\n    else if(strcmp(argv[i],\"-degens\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_STALLING);\r\n    else if(strcmp(argv[i],\"-degenn\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_NUMFAILURE);\r\n    else if(strcmp(argv[i],\"-degenl\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_LOSTFEAS);\r\n    else if(strcmp(argv[i],\"-degeni\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_INFEASIBLE);\r\n    else if(strcmp(argv[i],\"-degend\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_DYNAMIC);\r\n    else if(strcmp(argv[i],\"-degenb\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_DURINGBB);\r\n    else if(strcmp(argv[i],\"-degenr\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_RHSPERTURB);\r\n    else if(strcmp(argv[i],\"-degenp\") == 0)\r\n      or_value(&anti_degen2, ANTIDEGEN_BOUNDFLIP);\r\n    else if(strcmp(argv[i],\"-time\") == 0) {\r\n      if(clock() == -1)\r\n        fprintf(stderr, \"CPU times not available on this machine\\n\");\r\n      else\r\n        print_timing = TRUE;\r\n    }\r\n    else if((strcmp(argv[i],\"-bfp\") == 0) && (i + 1 < argc))\r\n      bfp = argv[++i];\r\n    else if((strcmp(argv[i],\"-rxli\") == 0) && (i + 2 < argc)) {\r\n      rxliname = argv[++i];\r\n      rxli = argv[++i];\r\n      fpin = NULL;\r\n      filetype = filetypeXLI;\r\n    }\r\n    else if((strcmp(argv[i],\"-rxlidata\") == 0) && (i + 1 < argc))\r\n      rxlidata = argv[++i];\r\n    else if((strcmp(argv[i],\"-rxliopt\") == 0) && (i + 1 < argc))\r\n      rxlioptions = argv[++i];\r\n    else if((strcmp(argv[i],\"-wxli\") == 0) && (i + 2 < argc)) {\r\n      wxliname = argv[++i];\r\n      wxli = argv[++i];\r\n    }\r\n    else if((strcmp(argv[i],\"-wxliopt\") == 0) && (i + 1 < argc))\r\n      wxlioptions = argv[++i];\r\n    else if((strcmp(argv[i],\"-wxlisol\") == 0) && (i + 2 < argc)) {\r\n      wxliname = argv[++i];\r\n      wxlisol = argv[++i];\r\n    }\r\n    else if((strcmp(argv[i],\"-wxlisolopt\") == 0) && (i + 1 < argc))\r\n      wxlisoloptions = argv[++i];\r\n    else if((strcmp(argv[i],\"-rbas\") == 0) && (i + 1 < argc))\r\n      rbasname = argv[++i];\r\n    else if((strcmp(argv[i],\"-wbas\") == 0) && (i + 1 < argc))\r\n      wbasname = argv[++i];\r\n    else if((strcmp(argv[i],\"-Db\") == 0) && (i + 1 < argc))\r\n      debugdump_before = argv[++i];\r\n    else if((strcmp(argv[i],\"-Da\") == 0) && (i + 1 < argc))\r\n      debugdump_after = argv[++i];\r\n    else if((strcmp(argv[i],\"-timeout\") == 0) && (i + 1 < argc))\r\n      sectimeout = atol(argv[++i]);\r\n    else if((strcmp(argv[i],\"-trej\") == 0) && (i + 1 < argc))\r\n      epspivot = atof(argv[++i]);\r\n    else if((strcmp(argv[i],\"-epsp\") == 0) && (i + 1 < argc))\r\n      epsperturb = atof(argv[++i]);\r\n    else if((strcmp(argv[i],\"-epsd\") == 0) && (i + 1 < argc))\r\n      epsd = atof(argv[++i]);\r\n    else if((strcmp(argv[i],\"-epsb\") == 0) && (i + 1 < argc))\r\n      epsb = atof(argv[++i]);\r\n    else if((strcmp(argv[i],\"-epsel\") == 0) && (i + 1 < argc))\r\n      epsel = atof(argv[++i]);\r\n    else if(strcmp(argv[i],\"-parse_only\") == 0)\r\n      parse_only = TRUE;\r\n    else\r\n      ok = TRUE;\r\n\r\n    if(!ok)\r\n      ;\r\n    else if(strcmp(argv[i],\"-presolverow\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_ROWS);\r\n    else if(strcmp(argv[i],\"-presolvecol\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_COLS);\r\n    else if(strcmp(argv[i],\"-presolve\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_ROWS | PRESOLVE_COLS);\r\n    else if(strcmp(argv[i],\"-presolvel\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_LINDEP);\r\n    else if(strcmp(argv[i],\"-presolves\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_SOS);\r\n    else if(strcmp(argv[i],\"-presolver\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_REDUCEMIP);\r\n    else if(strcmp(argv[i],\"-presolvek\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_KNAPSACK);\r\n    else if(strcmp(argv[i],\"-presolveq\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_ELIMEQ2);\r\n    else if(strcmp(argv[i],\"-presolvem\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_MERGEROWS);\r\n    else if(strcmp(argv[i],\"-presolvefd\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_COLFIXDUAL);\r\n    else if(strcmp(argv[i],\"-presolvebnd\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_BOUNDS);\r\n    else if(strcmp(argv[i],\"-presolved\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_DUALS);\r\n    else if(strcmp(argv[i],\"-presolvef\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_IMPLIEDFREE);\r\n    else if(strcmp(argv[i],\"-presolveslk\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_IMPLIEDSLK);\r\n    else if(strcmp(argv[i],\"-presolveg\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_REDUCEGCD);\r\n    else if(strcmp(argv[i],\"-presolveb\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_PROBEFIX);\r\n    else if(strcmp(argv[i],\"-presolvec\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_PROBEREDUCE);\r\n    else if(strcmp(argv[i],\"-presolverowd\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_ROWDOMINATE);\r\n    else if(strcmp(argv[i],\"-presolvecold\") == 0)\r\n      or_value(&do_presolve, PRESOLVE_COLDOMINATE);\r\n    else if(strcmp(argv[i],\"-min\") == 0)\r\n      objective = -1;\r\n    else if(strcmp(argv[i],\"-max\") == 0)\r\n      objective =  1;\r\n    else if(strcmp(argv[i],\"-noint\") == 0)\r\n      noint =  TRUE;\r\n    else if((strcmp(argv[i],\"-rpar\") == 0) && (i + 1 < argc))\r\n      i++;\r\n    else if((strcmp(argv[i],\"-rparopt\") == 0) && (i + 1 < argc))\r\n      i++;\r\n    else if((strcmp(argv[i],\"-wpar\") == 0) && (i + 1 < argc))\r\n      i++;\r\n    else if((strcmp(argv[i],\"-wparopt\") == 0) && (i + 1 < argc))\r\n      i++;\r\n    else if(strcmp(argv[i],\"-o0\") == 0)\r\n      obj_in_basis = FALSE;\r\n    else if(strcmp(argv[i],\"-o1\") == 0)\r\n      obj_in_basis = TRUE;\r\n    else if(fpin == stdin) {\r\n      filen = argv[i];\r\n      if(*filen == '<')\r\n        filen++;\r\n      if((fpin = fopen(filen, \"r\")) == NULL) {\r\n        print_help(argv);\r\n        fprintf(stderr,\"\\nError, Unable to open input file '%s'\\n\",\r\n                argv[i]);\r\n        EndOfPgr(FORCED_EXIT);\r\n      }\r\n    }\r\n    else {\r\n      filen = argv[i];\r\n      if(*filen != '>') {\r\n        print_help(argv);\r\n        fprintf(stderr, \"\\nError, Unrecognized command line argument '%s'\\n\",\r\n                argv[i]);\r\n        EndOfPgr(FORCED_EXIT);\r\n      }\r\n    }\r\n  }\r\n\r\n  signal(SIGABRT,/* (void (*) OF((int))) */ SIGABRT_func);\r\n\r\n  if ((filetype != filetypeXLI) && (fpin == NULL)) {\r\n    lp = NULL;\r\n    fprintf(stderr, \"Cannot combine -rxli option with -lp, -mps, -fmps.\\n\");\r\n  }\r\n  else {\r\n    switch(filetype) {\r\n  #if defined PARSER_LP\r\n    case filetypeLP:\r\n      lp = read_lp(fpin, verbose, NULL);\r\n      break;\r\n  #endif\r\n    case filetypeMPS:\r\n      lp = read_mps(fpin, verbose | (mps_free ? MPS_FREE : 0) | (mps_ibm ? MPS_IBM : 0) | (mps_negobjconst ? MPS_NEGOBJCONST : 0));\r\n      break;\r\n    case filetypeFREEMPS:\r\n      lp = read_freemps(fpin, verbose | (mps_ibm ? MPS_IBM : 0) | (mps_negobjconst ? MPS_NEGOBJCONST : 0));\r\n      break;\r\n    case filetypeXLI:\r\n      lp = read_XLI(rxliname, rxli, rxlidata, rxlioptions, verbose);\r\n      break;\r\n    }\r\n  }\r\n\r\n  if((fpin != NULL) && (fpin != stdin))\r\n    fclose(fpin);\r\n\r\n  if(print_timing)\r\n    print_cpu_times(\"Parsing input\");\r\n\r\n  if(lp == NULL) {\r\n    fprintf(stderr, \"Unable to read model.\\n\");\r\n    EndOfPgr(FORCED_EXIT);\r\n  }\r\n\r\n  for(i = 1; i < argc; i++) {\r\n    if((strcmp(argv[i],\"-rpar\") == 0) && (i + 1 < argc)) {\r\n      if(rparname != NULL) {\r\n        if(!read_params(lp, rparname, rparoptions)) {\r\n          fprintf(stderr, \"Unable to read parameter file (%s)\\n\", rparname);\r\n          delete_lp(lp);\r\n          EndOfPgr(FORCED_EXIT);\r\n        }\r\n      }\r\n      rparname = argv[++i];\r\n    }\r\n    else if((strcmp(argv[i],\"-rparopt\") == 0) && (i + 1 < argc))\r\n      rparoptions = argv[++i];\r\n    else if((strcmp(argv[i],\"-wpar\") == 0) && (i + 1 < argc))\r\n      wparname = argv[++i];\r\n    else if((strcmp(argv[i],\"-wparopt\") == 0) && (i + 1 < argc))\r\n      wparoptions = argv[++i];\r\n  }\r\n\r\n  if(rparname != NULL)\r\n    if(!read_params(lp, rparname, rparoptions)) {\r\n      fprintf(stderr, \"Unable to read parameter file (%s)\\n\", rparname);\r\n      delete_lp(lp);\r\n      EndOfPgr(FORCED_EXIT);\r\n    }\r\n\r\n  if((nonames) || (nocolnames))\r\n    set_use_names(lp, FALSE, FALSE);\r\n  if((nonames) || (norownames))\r\n    set_use_names(lp, TRUE, FALSE);\r\n\r\n  if(objective != 0) {\r\n    if(objective == 1)\r\n      set_maxim(lp);\r\n    else\r\n      set_minim(lp);\r\n  }\r\n\r\n  if (obj_in_basis != -1)\r\n    set_obj_in_basis(lp, obj_in_basis);\r\n\r\n  if(noint) { /* remove integer conditions */\r\n    for(i = get_Ncolumns(lp); i >= 1; i--) {\r\n      if(is_SOS_var(lp, i)) {\r\n        fprintf(stderr, \"Unable to remove integer conditions because there is at least one SOS constraint\\n\");\r\n        delete_lp(lp);\r\n        EndOfPgr(FORCED_EXIT);\r\n      }\r\n      set_semicont(lp, i, FALSE);\r\n      set_int(lp, i, FALSE);\r\n    }\r\n  }\r\n\r\n  if(!write_model_after)\r\n    write_model(lp, plp, wlp, wmps, wfmps, wxli, NULL, wxliname, wxlioptions);\r\n\r\n  if(print_stats)\r\n    print_statistics(lp);\r\n\r\n  if(parse_only) {\r\n    if(!write_model_after) {\r\n      delete_lp(lp);\r\n      EndOfPgr(0);\r\n    }\r\n    /* else if(!sectimeout) */\r\n      sectimeout = 1;\r\n  }\r\n\r\n  if(PRINT_SOLUTION >= 5)\r\n    print_lp(lp);\r\n\r\n#if 0\r\n  put_abortfunc(lp,(abortfunc *) myabortfunc, NULL);\r\n#endif\r\n\r\n  if(sectimeout > 0)\r\n    set_timeout(lp, sectimeout);\r\n  if(print_sol >= 0)\r\n    set_print_sol(lp, print_sol);\r\n  if(epsint >= 0)\r\n    set_epsint(lp, epsint);\r\n  if(epspivot >= 0)\r\n    set_epspivot(lp, epspivot);\r\n  if(epsperturb >= 0)\r\n    set_epsperturb(lp, epsperturb);\r\n  if(epsd >= 0)\r\n    set_epsd(lp, epsd);\r\n  if(epsb >= 0)\r\n    set_epsb(lp, epsb);\r\n  if(epsel >= 0)\r\n    set_epsel(lp, epsel);\r\n  if(debug >= 0)\r\n    set_debug(lp, (MYBOOL) debug);\r\n  if(floor_first != -1)\r\n    set_bb_floorfirst(lp, floor_first);\r\n  if(do_set_bb_depthlimit)\r\n    set_bb_depthlimit(lp, bb_depthlimit);\r\n  if(do_set_solutionlimit)\r\n    set_solutionlimit(lp, solutionlimit);\r\n  if(tracing)\r\n    set_trace(lp, tracing);\r\n  if(do_set_obj_bound)\r\n    set_obj_bound(lp, obj_bound);\r\n  if(do_set_break_at_value)\r\n    set_break_at_value(lp, break_at_value);\r\n  if(break_at_first)\r\n    set_break_at_first(lp, break_at_first);\r\n  if(mip_absgap >= 0)\r\n    set_mip_gap(lp, TRUE, mip_absgap);\r\n  if(mip_relgap >= 0)\r\n    set_mip_gap(lp, FALSE, mip_relgap);\r\n  if((anti_degen1 != -1) || (anti_degen2 != -1)) {\r\n    if((anti_degen1 == -1) || (anti_degen2 != -1))\r\n      anti_degen1 = 0;\r\n    if(anti_degen2 == -1)\r\n      anti_degen2 = 0;\r\n    set_anti_degen(lp, anti_degen1 | anti_degen2);\r\n  }\r\n  set_presolve(lp, ((do_presolve == -1) ? get_presolve(lp): do_presolve) | ((PRINT_SOLUTION >= 4) ? PRESOLVE_SENSDUALS : 0), get_presolveloops(lp));\r\n  if(improve != -1)\r\n    set_improve(lp, improve);\r\n  if(max_num_inv >= 0)\r\n    set_maxpivot(lp, max_num_inv);\r\n  if(preferdual != AUTOMATIC)\r\n    set_preferdual(lp, preferdual);\r\n  if((pivoting1 != -1) || (pivoting2 != -1)) {\r\n    if(pivoting1 == -1)\r\n      pivoting1 = get_pivoting(lp) & PRICER_LASTOPTION;\r\n    if(pivoting2 == -1)\r\n      pivoting2 = 0;\r\n    set_pivoting(lp, pivoting1 | pivoting2);\r\n  }\r\n  if((scalemode1 != -1) || (scalemode2 != -1)) {\r\n    if(scalemode1 == -1)\r\n      scalemode1 = get_scaling(lp) & SCALE_CURTISREID;\r\n    if(scalemode2 == -1)\r\n      scalemode2 = 0;\r\n    set_scaling(lp, scalemode1 | scalemode2);\r\n  }\r\n  if(crashmode != -1)\r\n    set_basiscrash(lp, crashmode);\r\n  if((bb_rule1 != -1) || (bb_rule2 != -1)) {\r\n    if(bb_rule1 == -1)\r\n      bb_rule1 = get_bb_rule(lp) & NODE_USERSELECT;\r\n    if(bb_rule2 == -1)\r\n      bb_rule2 = 0;\r\n    set_bb_rule(lp, bb_rule1 | bb_rule2);\r\n  }\r\n  if(simplextype != -1)\r\n    set_simplextype(lp, simplextype);\r\n  if(bfp != NULL)\r\n    if(!set_BFP(lp, bfp)) {\r\n      fprintf(stderr, \"Unable to set BFP package.\\n\");\r\n      delete_lp(lp);\r\n      EndOfPgr(FORCED_EXIT);\r\n    }\r\n  if(debugdump_before != NULL)\r\n    print_debugdump(lp, debugdump_before);\r\n  if(report)\r\n    put_msgfunc(lp, LPMessageCB, NULL, MSG_LPFEASIBLE | MSG_LPOPTIMAL | MSG_MILPFEASIBLE | MSG_MILPBETTER | MSG_PERFORMANCE);\r\n\r\n  if(scaling) {\r\n    if(scaleloop <= 0)\r\n      scaleloop = 5;\r\n    if(scaleloop - (int) scaleloop < SCALINGTHRESHOLD)\r\n      scaleloop = (int) scaleloop + SCALINGTHRESHOLD;\r\n    set_scalelimit(lp, scaleloop);\r\n  }\r\n\r\n  if(guessbasis != NULL) {\r\n    REAL *guessvector, a;\r\n    int *basisvector;\r\n    int Nrows = get_Nrows(lp);\r\n    int Ncolumns = get_Ncolumns(lp);\r\n    int col;\r\n    char buf[50], *ptr;\r\n    FILE *fp;\r\n\r\n    if ((fp = fopen(guessbasis, \"r\")) != NULL) {\r\n      guessvector = (REAL *) calloc(1+Ncolumns, sizeof(*guessvector));\r\n      basisvector = (int *) malloc((1+Nrows+Ncolumns)*sizeof(*basisvector));\r\n      if ((guessvector != NULL) && (basisvector != NULL)) {\r\n        while ((!feof(fp)) && (fgets(buf, sizeof(buf), fp) != NULL)) {\r\n          ptr = strrchr(buf, ':');\r\n          if (ptr == NULL) {\r\n            printf(\"Mallformed line: %s\\n\", buf);\r\n          }\r\n          else {\r\n            a = atof(ptr + 1);\r\n            while ((ptr > buf) && (isspace(ptr[-1])))\r\n              ptr--;\r\n            *ptr = 0;\r\n            col = get_nameindex(lp, buf, FALSE);\r\n            if (col < 1)\r\n              printf(\"guess_basis: Unknown variable name %s\\n\", buf);\r\n            else\r\n              guessvector[col] = a;\r\n          }\r\n        }\r\n        if (guess_basis(lp, guessvector, basisvector)) {\r\n          if (!set_basis(lp, basisvector, TRUE))\r\n            printf(\"Unable to set guessed basis.\\n\");\r\n        }\r\n        else\r\n          printf(\"Unable to guess basis from provided variables.\\n\");\r\n      }\r\n      else\r\n        printf(\"guess_basis: Out of memory.\\n\");\r\n      if (basisvector != NULL)\r\n        free(basisvector);\r\n      if (guessvector != NULL)\r\n        free(guessvector);\r\n      fclose(fp);\r\n    }\r\n    else\r\n      printf(\"Unable to open file %s\\n\", guessbasis);\r\n  }\r\n\r\n  if(rbasname != NULL)\r\n    if(!read_basis(lp, rbasname, NULL)) {\r\n      fprintf(stderr, \"Unable to read basis file.\\n\");\r\n      delete_lp(lp);\r\n      EndOfPgr(FORCED_EXIT);\r\n    }\r\n\r\n  result = solve(lp);\r\n\r\n  if(wbasname != NULL)\r\n    if(!write_basis(lp, wbasname))\r\n      fprintf(stderr, \"Unable to write basis file.\\n\");\r\n\r\n  if(write_model_after)\r\n    write_model(lp, plp, wlp, wmps, wfmps, wxli, NULL, wxliname, wxlioptions);\r\n\r\n  write_model(lp, FALSE, NULL, NULL, NULL, NULL, wxlisol, wxliname, wxlisoloptions);\r\n\r\n  if(PRINT_SOLUTION >= 6)\r\n    print_scales(lp);\r\n\r\n  if((print_timing) && (!parse_only))\r\n    print_cpu_times(\"solving\");\r\n\r\n  if(debugdump_after != NULL)\r\n    print_debugdump(lp, debugdump_after);\r\n\r\n  if(wparname != NULL)\r\n    if(!write_params(lp, wparname, wparoptions)) {\r\n      fprintf(stderr, \"Unable to write parameter file (%s)\\n\", wparname);\r\n      delete_lp(lp);\r\n      EndOfPgr(FORCED_EXIT);\r\n    }\r\n\r\n  if(parse_only) {\r\n    delete_lp(lp);\r\n    EndOfPgr(0);\r\n  }\r\n\r\n/*\r\n  if((timeoutok) && (result == TIMEOUT) && (get_solutioncount(lp) > 0))\r\n    result = OPTIMAL;\r\n*/\r\n\r\n  switch(result) {\r\n  case SUBOPTIMAL:\r\n  case PRESOLVED:\r\n  case OPTIMAL:\r\n  case PROCBREAK:\r\n  case FEASFOUND:\r\n    if ((result == SUBOPTIMAL) && (PRINT_SOLUTION >= 1))\r\n      printf(\"Suboptimal solution\\n\");\r\n\r\n    if (result == PRESOLVED)\r\n      printf(\"Presolved solution\\n\");\r\n\r\n    if (PRINT_SOLUTION >= 1)\r\n      print_objective(lp);\r\n\r\n    if (PRINT_SOLUTION >= 2)\r\n      print_solution(lp, 1);\r\n\r\n    if (PRINT_SOLUTION >= 3)\r\n      print_constraints(lp, 1);\r\n\r\n    if (PRINT_SOLUTION >= 4)\r\n      print_duals(lp);\r\n\r\n    if(tracing)\r\n      fprintf(stderr,\r\n              \"Branch & Bound depth: %d\\nNodes processed: %.0f\\nSimplex pivots: %.0f\\nNumber of equal solutions: %d\\n\",\r\n              get_max_level(lp), (REAL) get_total_nodes(lp), (REAL) get_total_iter(lp), get_solutioncount(lp));\r\n    break;\r\n  case NOMEMORY:\r\n    if (PRINT_SOLUTION >= 1)\r\n      printf(\"Out of memory\\n\");\r\n    break;\r\n  case INFEASIBLE:\r\n    if (PRINT_SOLUTION >= 1)\r\n      printf(\"This problem is infeasible\\n\");\r\n    break;\r\n  case UNBOUNDED:\r\n    if (PRINT_SOLUTION >= 1)\r\n      printf(\"This problem is unbounded\\n\");\r\n    break;\r\n  case PROCFAIL:\r\n   if (PRINT_SOLUTION >= 1)\r\n      printf(\"The B&B routine failed\\n\");\r\n    break;\r\n  case TIMEOUT:\r\n    if (PRINT_SOLUTION >= 1)\r\n      printf(\"Timeout\\n\");\r\n    break;\r\n  case USERABORT:\r\n    if (PRINT_SOLUTION >= 1)\r\n      printf(\"User aborted\\n\");\r\n    break;\r\n  default:\r\n    if (PRINT_SOLUTION >= 1)\r\n      printf(\"lp_solve failed\\n\");\r\n    break;\r\n  }\r\n\r\n  if (PRINT_SOLUTION >= 7)\r\n    print_tableau(lp);\r\n\r\n  delete_lp(lp);\r\n\r\n  EndOfPgr(result);\r\n  return(result);\r\n}\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/lp_solve.sln",
    "content": "﻿\r\nMicrosoft Visual Studio Solution File, Format Version 10.00\r\n# Visual Studio 2008\r\nProject(\"{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}\") = \"lp_solve\", \"lp_solve.vcproj\", \"{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}\"\r\nEndProject\r\nGlobal\r\n\tGlobalSection(SolutionConfigurationPlatforms) = preSolution\r\n\t\tDebug Fortify|Win32 = Debug Fortify|Win32\r\n\t\tDebug Fortify|x64 = Debug Fortify|x64\r\n\t\tDebug|Win32 = Debug|Win32\r\n\t\tDebug|x64 = Debug|x64\r\n\t\tDebug2|Win32 = Debug2|Win32\r\n\t\tDebug2|x64 = Debug2|x64\r\n\t\toops|Win32 = oops|Win32\r\n\t\toops|x64 = oops|x64\r\n\t\tRelease|Win32 = Release|Win32\r\n\t\tRelease|x64 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(ProjectConfigurationPlatforms) = postSolution\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug Fortify|Win32.ActiveCfg = Debug Fortify|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug Fortify|Win32.Build.0 = Debug Fortify|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug Fortify|x64.ActiveCfg = Debug Fortify|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug Fortify|x64.Build.0 = Debug Fortify|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug|Win32.ActiveCfg = Debug|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug|Win32.Build.0 = Debug|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug|x64.ActiveCfg = Debug|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug|x64.Build.0 = Debug|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug2|Win32.ActiveCfg = Debug2|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug2|Win32.Build.0 = Debug2|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug2|x64.ActiveCfg = Debug2|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Debug2|x64.Build.0 = Debug2|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.oops|Win32.ActiveCfg = oops|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.oops|Win32.Build.0 = oops|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.oops|x64.ActiveCfg = oops|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.oops|x64.Build.0 = oops|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Release|Win32.ActiveCfg = Release|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Release|Win32.Build.0 = Release|Win32\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Release|x64.ActiveCfg = Release|x64\r\n\t\t{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}.Release|x64.Build.0 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(SolutionProperties) = preSolution\r\n\t\tHideSolutionNode = FALSE\r\n\tEndGlobalSection\r\nEndGlobal\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/lp_solve.vcproj",
    "content": "<?xml version=\"1.0\" encoding=\"Windows-1252\"?>\r\n<VisualStudioProject\r\n\tProjectType=\"Visual C++\"\r\n\tVersion=\"9.00\"\r\n\tName=\"lp_solve\"\r\n\tProjectGUID=\"{2098FB68-99FD-40D4-ABD6-87E2FD11D1B5}\"\r\n\tRootNamespace=\"lp_solve\"\r\n\tKeyword=\"Win32Proj\"\r\n\tTargetFrameworkVersion=\"131072\"\r\n\t>\r\n\t<Platforms>\r\n\t\t<Platform\r\n\t\t\tName=\"Win32\"\r\n\t\t/>\r\n\t\t<Platform\r\n\t\t\tName=\"x64\"\r\n\t\t/>\r\n\t</Platforms>\r\n\t<ToolFiles>\r\n\t</ToolFiles>\r\n\t<Configurations>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\shared;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra\"\r\n\t\t\t\tPreprocessorDefinitions=\"FPUexception;WIN32;NOFORTIFY;_DEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE,LP_MAXLINELEN=0\"\r\n\t\t\t\tStringPooling=\"false\"\r\n\t\t\t\tMinimalRebuild=\"false\"\r\n\t\t\t\tBasicRuntimeChecks=\"0\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tDisableLanguageExtensions=\"false\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"2\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.pdb\"\r\n\t\t\t\tGenerateMapFile=\"true\"\r\n\t\t\t\tMapExports=\"true\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\shared;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra\"\r\n\t\t\t\tPreprocessorDefinitions=\"FPUexception;WIN32;NOFORTIFY;_DEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE,LP_MAXLINELEN=0\"\r\n\t\t\t\tStringPooling=\"false\"\r\n\t\t\t\tMinimalRebuild=\"false\"\r\n\t\t\t\tBasicRuntimeChecks=\"0\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tDisableLanguageExtensions=\"false\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"2\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.pdb\"\r\n\t\t\t\tGenerateMapFile=\"true\"\r\n\t\t\t\tMapExports=\"true\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"2\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra;..\\shared;D:\\LP_SOLVE\\include\"\r\n\t\t\t\tPreprocessorDefinitions=\"WIN32;NDEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE,PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"4\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"0\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t\tDisableSpecificWarnings=\"4100;4127\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tOptimizeReferences=\"2\"\r\n\t\t\t\tEnableCOMDATFolding=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"2\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra;..\\shared;D:\\LP_SOLVE\\include\"\r\n\t\t\t\tPreprocessorDefinitions=\"WIN32;NDEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE,PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"4\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"0\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t\tDisableSpecificWarnings=\"4100;4127\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tOptimizeReferences=\"2\"\r\n\t\t\t\tEnableCOMDATFolding=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug Fortify|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"WIN32;FORTIFY;_DEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"false\"\r\n\t\t\t\tMinimalRebuild=\"false\"\r\n\t\t\t\tBasicRuntimeChecks=\"0\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tDisableLanguageExtensions=\"false\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug Fortify|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"WIN32;FORTIFY;_DEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"false\"\r\n\t\t\t\tMinimalRebuild=\"false\"\r\n\t\t\t\tBasicRuntimeChecks=\"0\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tDisableLanguageExtensions=\"false\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.pdb\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"oops|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"2\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra;..\\shared;D:\\LP_SOLVE\\include\"\r\n\t\t\t\tPreprocessorDefinitions=\"WIN32;NDEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE,PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"4\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t\tDisableSpecificWarnings=\"4100;4127\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tOptimizeReferences=\"2\"\r\n\t\t\t\tEnableCOMDATFolding=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"oops|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"2\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra;..\\shared;D:\\LP_SOLVE\\include\"\r\n\t\t\t\tPreprocessorDefinitions=\"WIN32;NDEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE,PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"4\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t\tDisableSpecificWarnings=\"4100;4127\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tOptimizeReferences=\"2\"\r\n\t\t\t\tEnableCOMDATFolding=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug2|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra;..\\shared;D:\\LP_SOLVE\\include\"\r\n\t\t\t\tPreprocessorDefinitions=\"WIN32;NDEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE,PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"4\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t\tDisableSpecificWarnings=\"4100;4127\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tOptimizeReferences=\"2\"\r\n\t\t\t\tEnableCOMDATFolding=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug2|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"1\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tCharacterSet=\"2\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\extra;..\\shared;D:\\LP_SOLVE\\include\"\r\n\t\t\t\tPreprocessorDefinitions=\"WIN32;NDEBUG;_CONSOLE,MSDOS,CHECK_SOLUTION,YY_NEVER_INTERACTIVE,PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tWarningLevel=\"4\"\r\n\t\t\t\tDetect64BitPortabilityProblems=\"false\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t\tDisableSpecificWarnings=\"4100;4127\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lp_solve.exe\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tSubSystem=\"1\"\r\n\t\t\t\tOptimizeReferences=\"2\"\r\n\t\t\t\tEnableCOMDATFolding=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t</Configurations>\r\n\t<References>\r\n\t</References>\r\n\t<Files>\r\n\t\t<Filter\r\n\t\t\tName=\"Source Files\"\r\n\t\t\tFilter=\"cpp;c;cxx;def;odl;idl;hpj;bat;asm;asmx\"\r\n\t\t\tUniqueIdentifier=\"{4FC737F1-C7A5-4376-A066-2A32D752A2FF}\"\r\n\t\t\t>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\colamd\\colamd.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\shared\\commonlib.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\fortify.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\ini.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_crash.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_Hash.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_lib.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\Bfp\\Bfp_lusol\\lp_LUSOL.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_matrix.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_MDO.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_mipbb.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_MPS.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_params.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_presolve.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_price.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_pricePSE.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_report.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_rlp.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_scale.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_simplex.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"lp_solve.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_SOS.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_utils.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_wlp.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\Bfp\\Bfp_lusol\\LUSOL\\lusol.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\shared\\mmio.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\shared\\myblas.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\yacc_read.c\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t</Filter>\r\n\t\t<Filter\r\n\t\t\tName=\"Header Files\"\r\n\t\t\tFilter=\"h;hpp;hxx;hm;inl;inc;xsd\"\r\n\t\t\tUniqueIdentifier=\"{93995380-89BD-4b04-88EB-625FBE52EBFB}\"\r\n\t\t\t>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\colamd\\colamd.h\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\ini.h\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\bfp\\bfp_etaPFI\\lp_etaPFI.h\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_lib.h\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_matrix.h\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lp_MPS.h\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\lpkit.h\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t\t<File\r\n\t\t\t\tRelativePath=\"..\\patchlevel.h\"\r\n\t\t\t\t>\r\n\t\t\t</File>\r\n\t\t</Filter>\r\n\t\t<Filter\r\n\t\t\tName=\"Resource Files\"\r\n\t\t\tFilter=\"rc;ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe;resx\"\r\n\t\t\tUniqueIdentifier=\"{67DA6AB6-F800-4c08-8B7A-83BB121AAD01}\"\r\n\t\t\t>\r\n\t\t</Filter>\r\n\t\t<File\r\n\t\t\tRelativePath=\".\\debug\\BuildLog.htm\"\r\n\t\t\tDeploymentContent=\"true\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t</Files>\r\n\t<Globals>\r\n\t</Globals>\r\n</VisualStudioProject>\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve/readme.txt",
    "content": "This directory contains the files to build the lp_solve program\r\n\r\nTo build the program under Windows with the Visual C/C++ compiler, use cvc6.bat (also works for VS.NET)\r\nTo build the program under DOS/Windows with the gcc compiler, use cgcc.bat\r\nTo build the program under Linux/Unix, use sh ccc\r\nTo build the program under Mac OS X 10.3.5, use sh ccc.osx\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solve.def",
    "content": "EXPORTS\r\n   add_SOS\r\n   add_column\r\n   add_columnex\r\n   add_constraint\r\n   add_constraintex\r\n   add_lag_con\r\n   column_in_lp\r\n   copy_lp\r\n   default_basis\r\n   del_column\r\n   del_constraint\r\n   delete_lp\r\n   dualize_lp\r\n   free_lp\r\n   get_Lrows\r\n   get_Ncolumns\r\n   get_Norig_columns\r\n   get_Norig_rows\r\n   get_Nrows\r\n   get_pseudocosts\r\n   get_anti_degen\r\n   get_basis\r\n   get_basiscrash\r\n   get_bb_depthlimit\r\n   get_bb_floorfirst\r\n   get_bb_rule\r\n   get_bounds_tighter\r\n   get_break_at_value\r\n   get_col_name\r\n   get_column\r\n   get_columnex\r\n   get_constr_type\r\n   get_constr_value\r\n   get_constraints\r\n   get_dual_solution\r\n   get_epsb\r\n   get_epsd\r\n   get_epsel\r\n   get_epsint\r\n   get_epsperturb\r\n   get_epspivot\r\n   get_improve\r\n   get_infinite\r\n   get_lambda\r\n   get_lowbo\r\n   get_lp_index\r\n   get_lp_name\r\n   get_mat\r\n   get_mat_byindex\r\n   get_max_level\r\n   get_maxpivot\r\n   get_mip_gap\r\n   get_multiprice\r\n   get_nameindex\r\n   get_negrange\r\n   get_nonzeros\r\n   get_obj_bound\r\n   get_objective\r\n   get_orig_index\r\n   get_origcol_name\r\n   get_origrow_name\r\n   get_partialprice\r\n   get_pivoting\r\n   get_presolve\r\n   get_presolveloops\r\n   get_primal_solution\r\n   get_print_sol\r\n   get_ptr_constraints\r\n   get_ptr_dual_solution\r\n   get_ptr_lambda\r\n   get_ptr_primal_solution\r\n   get_ptr_sensitivity_obj\r\n   get_ptr_sensitivity_objex\r\n   get_ptr_sensitivity_rhs\r\n   get_ptr_variables\r\n   get_rh\r\n   get_rh_range\r\n   get_row\r\n   get_rowex\r\n   get_row_name\r\n   get_scalelimit\r\n   get_scaling\r\n   get_sensitivity_obj\r\n   get_sensitivity_objex\r\n   get_sensitivity_rhs\r\n   get_simplextype\r\n   get_solutioncount\r\n   get_solutionlimit\r\n   get_status\r\n   get_statustext\r\n   get_timeout\r\n   get_total_iter\r\n   get_total_nodes\r\n   get_upbo\r\n   get_var_branch\r\n   get_var_dualresult\r\n   get_var_primalresult\r\n   get_var_priority\r\n   get_variables\r\n   get_verbose\r\n   get_working_objective\r\n   guess_basis\r\n   has_BFP\r\n   has_XLI\r\n   is_SOS_var\r\n   is_add_rowmode\r\n   is_anti_degen\r\n   is_binary\r\n   is_break_at_first\r\n   is_constr_type\r\n   is_debug\r\n   is_feasible\r\n   is_unbounded\r\n   is_infinite\r\n   is_int\r\n   is_integerscaling\r\n   is_lag_trace\r\n   is_maxim\r\n   is_nativeBFP\r\n   is_nativeXLI\r\n   is_negative\r\n   is_obj_in_basis\r\n   is_piv_mode\r\n   is_piv_rule\r\n   is_presolve\r\n   is_scalemode\r\n   is_scaletype\r\n   is_semicont\r\n   is_trace\r\n   is_use_names\r\n   lp_solve_version\r\n   make_lp\r\n   print_constraints\r\n   print_debugdump\r\n   print_duals\r\n   print_lp\r\n   print_objective\r\n   print_scales\r\n   print_solution\r\n   print_str\r\n   print_tableau\r\n   put_abortfunc\r\n   put_bb_nodefunc\r\n   put_bb_branchfunc\r\n   put_logfunc\r\n   put_msgfunc\r\n   read_LP\r\n   read_MPS\r\n   read_XLI\r\n   read_freeMPS\r\n   read_freemps\r\n   read_lp\r\n   read_lpex\r\n   read_mps\r\n   read_basis\r\n   read_params\r\n   reset_basis\r\n   reset_params\r\n   resize_lp\r\n   set_BFP\r\n   set_pseudocosts\r\n   set_XLI\r\n   set_add_rowmode\r\n   set_anti_degen\r\n   set_basis\r\n   set_basiscrash\r\n   set_basisvar\r\n   set_bb_depthlimit\r\n   set_bb_floorfirst\r\n   set_bb_rule\r\n   set_binary\r\n   set_bounds\r\n   set_bounds_tighter\r\n   set_break_at_first\r\n   set_break_at_value\r\n   set_col_name\r\n   set_column\r\n   set_columnex\r\n   set_constr_type\r\n   set_debug\r\n   set_epsb\r\n   set_epsd\r\n   set_epsel\r\n   set_epsint\r\n   set_epslevel\r\n   set_epsperturb\r\n   set_epspivot\r\n   set_unbounded\r\n   set_improve\r\n   set_infinite\r\n   set_int\r\n   set_lag_trace\r\n   set_lowbo\r\n   set_lp_name\r\n   set_mat\r\n   set_maxim\r\n   set_maxpivot\r\n   set_minim\r\n   set_mip_gap\r\n   set_multiprice\r\n   set_negrange\r\n   set_obj\r\n   set_obj_bound\r\n   set_obj_fn\r\n   set_obj_fnex\r\n   set_obj_in_basis\r\n   set_outputfile\r\n   set_outputstream\r\n   set_partialprice\r\n   set_pivoting\r\n   set_preferdual\r\n   set_presolve\r\n   set_print_sol\r\n   set_rh\r\n   set_rh_range\r\n   set_rh_vec\r\n   set_row\r\n   set_row_name\r\n   set_rowex\r\n   set_scalelimit\r\n   set_scaling\r\n   set_semicont\r\n   set_sense\r\n   set_simplextype\r\n   set_solutionlimit\r\n   set_timeout\r\n   set_trace\r\n   set_upbo\r\n   set_use_names\r\n   set_var_branch\r\n   set_var_weights\r\n   set_verbose\r\n   solve\r\n   str_add_column\r\n   str_add_constraint\r\n   str_add_lag_con\r\n   str_set_obj_fn\r\n   str_set_rh_vec\r\n   time_elapsed\r\n   unscale\r\n   write_LP\r\n   write_MPS\r\n   write_XLI\r\n   write_freeMPS\r\n   write_freemps\r\n   MPS_writefileex\r\n   write_lp\r\n   write_lpex\r\n   write_mps\r\n   write_basis\r\n   write_params\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solveDLL.c",
    "content": "\n/* lp_solve.cpp : Defines the entry point for the DLL. */\n\n#include \"lp_solveDLL.h\"\n\n\nBOOL APIENTRY DllMain( HANDLE hModule,\n                       DWORD  ul_reason_for_call,\n                       LPVOID lpReserved\n           )\n{\n    return TRUE;\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_solveDLL.h",
    "content": "// stdafx.h : include file for standard system include files,\n//  or project specific include files that are used frequently, but\n//      are changed infrequently\n//\n\n#if !defined(AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_)\n#define AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_\n\n#if _MSC_VER > 1000\n#pragma once\n#endif // _MSC_VER > 1000\n\n\n// Insert your headers here\n#define WIN32_LEAN_AND_MEAN // Exclude rarely-used stuff from Windows headers\n\n#include <windows.h>\n\n// TODO: reference additional headers your program requires here\n\n//{{AFX_INSERT_LOCATION}}\n// Microsoft Visual C++ will insert additional declarations immediately before the previous line.\n\n#endif // !defined(AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_)\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_types.h",
    "content": "#ifndef HEADER_lp_types\n#define HEADER_lp_types\n\n#ifdef WIN32\n  #include <windows.h>\n#endif\n\n/* Define data types                                                         */\n/* ------------------------------------------------------------------------- */\n#ifndef LLONG\n  #if defined __BORLANDC__\n    #define LLONG __int64\n  #elif !defined _MSC_VER || _MSC_VER >= 1310\n    #define LLONG long long\n  #else\n    #define LLONG __int64\n  #endif\n#endif\n\n#ifndef COUNTER\n  #define COUNTER LLONG\n#endif\n\n#ifndef REAL\n  #define REAL    double\n#endif\n\n#ifndef REALXP\n  #if 1\n    #define REALXP long double  /* Set local accumulation variable as long double */\n  #else\n    #define REALXP REAL          /* Set local accumulation as default precision */\n  #endif\n#endif\n\n#ifndef LREAL\n  #if 0\n    #define LREAL long double   /* Set global solution update variable as long double */\n  #else\n    #define LREAL REAL           /* Set global solution update variable as default precision */\n  #endif\n#endif\n\n#define RESULTVALUEMASK \"%18.12g\" /* Set fixed-format real-valued output precision;\n                                  suggested width: ABS(exponent of DEF_EPSVALUE)+6. */\n#define INDEXVALUEMASK  \"%8d\"     /* Set fixed-format integer-valued output width */\n\n#ifndef DEF_STRBUFSIZE\n  #define DEF_STRBUFSIZE   512\n#endif\n#ifndef MAXINT32\n  #define MAXINT32  2147483647\n#endif\n#ifndef MAXUINT32\n  #define MAXUINT32 4294967295\n#endif\n\n#ifndef MAXINT64\n  #if defined _LONGLONG || defined __LONG_LONG_MAX__ || defined LLONG_MAX\n    #define MAXINT64   9223372036854775807ll\n  #else\n    #define MAXINT64   9223372036854775807l\n  #endif\n#endif\n#ifndef MAXUINT64\n  #if defined _LONGLONG || defined __LONG_LONG_MAX__ || defined LLONG_MAX\n    #define MAXUINT64 18446744073709551615ll\n  #else\n    #define MAXUINT64 18446744073709551615l\n  #endif\n#endif\n\n#ifndef CHAR_BIT\n  #define CHAR_BIT  8\n#endif\n#ifndef MYBOOL\n  #define MYBOOL  unsigned char    /* Conserve memory, could be unsigned int */\n#endif\n\n\n/* Constants                                                                 */\n/* ------------------------------------------------------------------------- */\n#ifndef NULL\n  #define NULL                   0\n#endif\n\n/* Byte-sized Booleans and extended options */\n#define FALSE                    0\n#define TRUE                     1\n#define AUTOMATIC                2\n#define DYNAMIC                  4\n\n/* Sorting and comparison constants */\n#define COMP_PREFERCANDIDATE     1\n#define COMP_PREFERNONE          0\n#define COMP_PREFERINCUMBENT    -1\n\n/* Library load status values */\n#define LIB_LOADED               0\n#define LIB_NOTFOUND             1\n#define LIB_NOINFO               2\n#define LIB_NOFUNCTION           3\n#define LIB_VERINVALID           4\n#define LIB_STR_LOADED           \"Successfully loaded\"\n#define LIB_STR_NOTFOUND         \"File not found\"\n#define LIB_STR_NOINFO           \"No version data\"\n#define LIB_STR_NOFUNCTION       \"Missing function header\"\n#define LIB_STR_VERINVALID       \"Incompatible version\"\n#define LIB_STR_MAXLEN           23\n\n\n/* Compiler/target settings                                                  */\n/* ------------------------------------------------------------------------- */\n#if (defined _WIN32) || (defined WIN32) || (defined _WIN64) || (defined WIN64)\n# define __WINAPI WINAPI\n#else\n# define __WINAPI\n#endif\n\n#if (defined _WIN32) || (defined WIN32) || (defined _WIN64) || (defined WIN64)\n# define __VACALL __cdecl\n#else\n# define __VACALL\n#endif\n\n#ifndef __BORLANDC__\n\n  #ifdef _USRDLL\n\n    #if 1\n      #define __EXPORT_TYPE __declspec(dllexport)\n    #else\n     /* Set up for the Microsoft compiler */\n      #ifdef LP_SOLVE_EXPORTS\n        #define __EXPORT_TYPE __declspec(dllexport)\n      #else\n        #define __EXPORT_TYPE __declspec(dllimport)\n      #endif\n    #endif\n\n  #else\n\n    #define __EXPORT_TYPE\n\n  #endif\n\n  #ifdef __cplusplus\n    #define __EXTERN_C extern \"C\"\n  #else\n    #define __EXTERN_C\n  #endif\n\n#else  /* Otherwise set up for the Borland compiler */\n\n  #ifdef __DLL__\n\n    #define _USRDLL\n    #define __EXTERN_C extern \"C\"\n\n    #ifdef __READING_THE_DLL\n      #define __EXPORT_TYPE __import\n    #else\n      #define __EXPORT_TYPE __export\n    #endif\n\n  #else\n\n    #define __EXPORT_TYPE\n    #define __EXTERN_C extern \"C\"\n\n  #endif\n\n#endif\n\n\n#if 0\n  #define STATIC static\n#else\n  #define STATIC\n#endif\n\n#if !defined INLINE\n  #if defined __cplusplus\n    #define INLINE inline\n  #elif (defined _WIN32) || (defined WIN32) || (defined _WIN64) || (defined WIN64)\n    #define INLINE __inline\n  #else\n    #define INLINE static\n  #endif\n#endif\n\n/* Function macros                                                           */\n/* ------------------------------------------------------------------------- */\n#define my_limitrange(x, lo, hi) ((x) < (lo) ? (lo) : ((x) > (hi) ? (hi) : (x)))\n#ifndef my_mod\n  #define my_mod(n, m)          ((n) % (m))\n#endif\n#define my_if(t, x, y)          ((t) ? (x) : (y))\n#define my_sign(x)              ((x) < 0 ? -1 : 1)\n#if 1\n  #define my_chsign(t, x)       ( ((t) && ((x) != 0)) ? -(x) : (x))\n#else\n  #define my_chsign(t, x)       ( (2*((t) == 0) - 1) * (x) )  /* \"Pipelined\", but problem with \"negative zero\" and possible problems on AIX  */\n#endif\n#define my_flipsign(x)          ( fabs((REAL) (x)) == 0 ? 0 : -(x) )\n#define my_roundzero(val, eps)  if (fabs((REAL) (val)) < eps) val = 0\n#define my_avoidtiny(val, eps)  (fabs((REAL) (val)) < eps ? 0 : val)\n\n#if 1\n  #define my_infinite(lp, val)  ( (MYBOOL) (fabs(val) >= lp->infinite) )\n#else\n  #define my_infinite(lp, val)  is_infinite(lp, val)\n#endif\n#define my_inflimit(lp, val)    ( my_infinite(lp, val) ? lp->infinite * my_sign(val) : (val) )\n#if 0\n  #define my_precision(val, eps) ((fabs((REAL) (val))) < (eps) ? 0 : (val))\n#else\n  #define my_precision(val, eps) restoreINT(val, eps)\n#endif\n#define my_reldiff(x, y)       (((x) - (y)) / (1.0 + fabs((REAL) (y))))\n#define my_boundstr(x)         (fabs(x) < lp->infinite ? sprintf(\"%g\",x) : ((x) < 0 ? \"-Inf\" : \"Inf\") )\n#ifndef my_boolstr\n  #define my_boolstr(x)          (!(x) ? \"FALSE\" : \"TRUE\")\n#endif\n#define my_basisstr(isbasic)     ((isbasic) ? \"BASIC\" : \"NON-BASIC\")\n#define my_simplexstr(isdual)    ((isdual) ? \"DUAL\" : \"PRIMAL\")\n#define my_plural_std(count)     (count == 1 ? \"\" : \"s\")\n#define my_plural_y(count)       (count == 1 ? \"y\" : \"ies\")\n#define my_lowbound(x)           ((FULLYBOUNDEDSIMPLEX) ? (x) : 0)\n\n\n/* Bound macros usable for both the standard and fully bounded simplex       */\n/* ------------------------------------------------------------------------- */\n/*\n#define my_lowbo(lp, varnr)      ( lp->isfullybounded ? lp->lowbo[varnr] : 0.0 )\n#define my_upbo(lp, varnr)       ( lp->isfullybounded ? lp->upbo[varnr]  : lp->lowbo[varnr] + lp->upbo[varnr] )\n#define my_rangebo(lp, varnr)    ( lp->isfullybounded ? lp->upbo[varnr] - lp->lowbo[varnr] : lp->upbo[varnr] )\n*/\n#define my_lowbo(lp, varnr)      ( 0.0 )\n#define my_upbo(lp, varnr)       ( lp->lowbo[varnr] + lp->upbo[varnr] )\n#define my_rangebo(lp, varnr)    ( lp->upbo[varnr] )\n\n#define my_unbounded(lp, varnr)  ((lp->upbo[varnr] >= lp->infinite) && (lp->lowbo[varnr] <= -lp->infinite))\n#define my_bounded(lp, varnr)    ((lp->upbo[varnr] < lp->infinite) && (lp->lowbo[varnr] > -lp->infinite))\n\n/* Forward declarations                                                      */\n/* ------------------------------------------------------------------------- */\ntypedef struct _lprec     lprec;\ntypedef struct _INVrec    INVrec;\nunion  QSORTrec;\n\n#ifndef UNIONTYPE\n  #ifdef __cplusplus\n    #define UNIONTYPE\n  #else\n    #define UNIONTYPE union\n  #endif\n#endif\n\n/* B4 factorization optimization data */\ntypedef struct _B4rec\n{\n  int  *B4_var;  /* Position of basic columns in the B4 basis */\n  int  *var_B4;  /* Variable in the B4 basis */\n  int  *B4_row;  /* B4 position of the i'th row */\n  int  *row_B4;  /* Original position of the i'th row */\n  REAL *wcol;\n  int  *nzwcol;\n} B4rec;\n\n#define OBJ_STEPS   5\ntypedef struct _OBJmonrec {\n  lprec  *lp;\n  int    oldpivstrategy,\n         oldpivrule, pivrule, ruleswitches,\n         limitstall[2], limitruleswitches,\n         idxstep[OBJ_STEPS], countstep, startstep, currentstep,\n         Rcycle, Ccycle, Ncycle, Mcycle, Icount;\n  REAL   thisobj, prevobj,\n         objstep[OBJ_STEPS],\n         thisinfeas, previnfeas,\n         epsvalue;\n  char   spxfunc[10];\n  MYBOOL pivdynamic;\n  MYBOOL isdual;\n  MYBOOL active;\n} OBJmonrec;\n\ntypedef struct _edgerec\n{\n  REAL      *edgeVector;\n} edgerec;\n\ntypedef struct _pricerec\n{\n  REAL   theta;\n  REAL   pivot;\n  REAL   epspivot;\n  int    varno;\n  lprec  *lp;\n  MYBOOL isdual;\n} pricerec;\ntypedef struct _multirec\n{\n  lprec    *lp;\n  int      size;                  /* The maximum number of multiply priced rows/columns */\n  int      used;                  /* The current / active number of multiply priced rows/columns */\n  int      limit;                 /* The active/used count at which a full update is triggered */\n  pricerec *items;                /* Array of best multiply priced rows/columns */\n  int      *freeList;             /* The indeces of available positions in \"items\" */\n  UNIONTYPE QSORTrec *sortedList; /* List of pointers to \"pricerec\" items in sorted order */\n  REAL     *stepList;             /* Working array (values in sortedList order) */\n  REAL     *valueList;            /* Working array (values in sortedList order) */\n  int      *indexSet;             /* The final exported index list of pivot variables */\n  int      active;                /* Index of currently active multiply priced row/column */\n  int      retries;\n  REAL     step_base;\n  REAL     step_last;\n  REAL     obj_base;\n  REAL     obj_last;\n  REAL     epszero;\n  REAL     maxpivot;\n  REAL     maxbound;\n  MYBOOL   sorted;\n  MYBOOL   truncinf;\n  MYBOOL   objcheck;\n  MYBOOL   dirty;\n} multirec;\n\n#endif /* HEADER_lp_types */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_utils.c",
    "content": "#define CODE_lp_utils\n\n#include <string.h>\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_utils.h\"\n#include <time.h>\n#include <sys/timeb.h>\n#include \"lp_bit.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n\n/*\n    Miscellaneous utilities as implemented for lp_solve v5.0+\n   ----------------------------------------------------------------------------------\n    Author:        Kjell Eikland\n    Contact:       kjell.eikland@broadpark.no\n    License terms: GLPL.\n\n    Requires:      lp_utils.h, lp_lib.h\n\n    Release notes:\n    v1.0.0  1 January 2003      Memory allocation, sorting, searching, time and\n                                doubly linked list functions.\n    v1.1.0  15 May 2004         Added vector packing functionality\n    v1.2.0  10 January 2005     Added vector pushing/popping functionality\n                                Modified return values and fixed problem in\n                                linked list functions.\n\n   ----------------------------------------------------------------------------------\n*/\n\nSTATIC MYBOOL allocCHAR(lprec *lp, char **ptr, int size, MYBOOL clear)\n{\n  if(clear == TRUE)\n    *ptr = (char *) calloc(size, sizeof(**ptr));\n  else if(clear & AUTOMATIC) {\n    *ptr = (char *) realloc(*ptr, size * sizeof(**ptr));\n    if(clear & TRUE)\n      MEMCLEAR(*ptr, size);\n  }\n  else\n    *ptr = (char *) malloc(size * sizeof(**ptr));\n  if(((*ptr) == NULL) && (size > 0)) {\n    lp->report(lp, CRITICAL, \"alloc of %d 'char' failed\\n\", size);\n    lp->spx_status = NOMEMORY;\n    return( FALSE );\n  }\n  else\n    return( TRUE );\n}\nSTATIC MYBOOL allocMYBOOL(lprec *lp, MYBOOL **ptr, int size, MYBOOL clear)\n{\n  if(clear == TRUE)\n    *ptr = (MYBOOL *) calloc(size, sizeof(**ptr));\n  else if(clear & AUTOMATIC) {\n    *ptr = (MYBOOL *) realloc(*ptr, size * sizeof(**ptr));\n    if(clear & TRUE)\n      MEMCLEAR(*ptr, size);\n  }\n  else\n    *ptr = (MYBOOL *) malloc(size * sizeof(**ptr));\n  if(((*ptr) == NULL) && (size > 0)) {\n    lp->report(lp, CRITICAL, \"alloc of %d 'MYBOOL' failed\\n\", size);\n    lp->spx_status = NOMEMORY;\n    return( FALSE );\n  }\n  else\n    return( TRUE );\n}\nSTATIC MYBOOL allocINT(lprec *lp, int **ptr, int size, MYBOOL clear)\n{\n  if(clear == TRUE)\n    *ptr = (int *) calloc(size, sizeof(**ptr));\n  else if(clear & AUTOMATIC) {\n    *ptr = (int *) realloc(*ptr, size * sizeof(**ptr));\n    if(clear & TRUE)\n      MEMCLEAR(*ptr, size);\n  }\n  else\n    *ptr = (int *) malloc(size * sizeof(**ptr));\n  if(((*ptr) == NULL) && (size > 0)) {\n    lp->report(lp, CRITICAL, \"alloc of %d 'INT' failed\\n\", size);\n    lp->spx_status = NOMEMORY;\n    return( FALSE );\n  }\n  else\n    return( TRUE );\n}\nSTATIC MYBOOL allocREAL(lprec *lp, REAL **ptr, int size, MYBOOL clear)\n{\n  if(clear == TRUE)\n    *ptr = (REAL *) calloc(size, sizeof(**ptr));\n  else if(clear & AUTOMATIC) {\n    *ptr = (REAL *) realloc(*ptr, size * sizeof(**ptr));\n    if(clear & TRUE)\n      MEMCLEAR(*ptr, size);\n  }\n  else\n    *ptr = (REAL *) malloc(size * sizeof(**ptr));\n  if(((*ptr) == NULL) && (size > 0)) {\n    lp->report(lp, CRITICAL, \"alloc of %d 'REAL' failed\\n\", size);\n    lp->spx_status = NOMEMORY;\n    return( FALSE );\n  }\n  else\n    return( TRUE );\n}\nSTATIC MYBOOL allocLREAL(lprec *lp, LREAL **ptr, int size, MYBOOL clear)\n{\n  if(clear == TRUE)\n    *ptr = (LREAL *) calloc(size, sizeof(**ptr));\n  else if(clear & AUTOMATIC) {\n    *ptr = (LREAL *) realloc(*ptr, size * sizeof(**ptr));\n    if(clear & TRUE)\n      MEMCLEAR(*ptr, size);\n  }\n  else\n    *ptr = (LREAL *) malloc(size * sizeof(**ptr));\n  if(((*ptr) == NULL) && (size > 0)) {\n    lp->report(lp, CRITICAL, \"alloc of %d 'LREAL' failed\\n\", size);\n    lp->spx_status = NOMEMORY;\n    return( FALSE );\n  }\n  else\n    return( TRUE );\n}\n\nSTATIC MYBOOL allocFREE(lprec *lp, void **ptr)\n{\n  MYBOOL status = TRUE;\n\n  if(*ptr != NULL) {\n    free(*ptr);\n    *ptr = NULL;\n  }\n  else {\n    status = FALSE;\n    lp->report(lp, CRITICAL, \"free() failed on line %d of file %s\\n\",\n                             __LINE__, __FILE__);\n  }\n  return(status);\n}\n\n/* Do hoops to provide debugging info with FORTIFY */\n#undef CODE_lp_utils\n#include \"lp_utils.h\"\n/* alloc-routines should always be before this line! */\n\nint comp_bits(MYBOOL *bitarray1, MYBOOL *bitarray2, int items)\n{\n  int            i, items4, left = 0, right = 0;\n  MYBOOL         comp1;\n  unsigned long comp4;\n\n  /* Convert items count to 8-bit representation, if necessary */\n  if(items > 0) {\n    i = items % 8;\n    items /= 8;\n    if(i)\n      items++;\n  }\n  else\n    items = -items;\n\n  /* Do the wide unsigned integer part for speed */\n  items4 = items / sizeof(unsigned long);\n  i = 0;\n  while(i < items4) {\n    comp4 = ((unsigned long *) bitarray1)[i] &  ~((unsigned long *) bitarray2)[i];\n    if(comp4)\n      left++;\n    comp4 = ((unsigned long *) bitarray2)[i] &  ~((unsigned long *) bitarray1)[i];\n    if(comp4)\n      right++;\n    i++;\n  }\n\n  /* Do the trailing slow narrow unsigned integer part */\n  i *= sizeof(unsigned long);\n  i++;\n  while(i < items) {\n    comp1 = bitarray1[i] & ~bitarray2[i];\n    if(comp1)\n      left++;\n    comp1 = bitarray2[i] & ~bitarray1[i];\n    if(comp1)\n      right++;\n    i++;\n  }\n\n  /* Determine set comparison outcomes */\n  if((left > 0) && (right == 0))         /* array1 is a superset of array2 */\n    i = 1;\n  else if((left == 0) && (right > 0))   /* array2 is a superset of array1 */\n    i = -1;\n  else if((left == 0) && (right == 0))  /* array1 and array2 are identical */\n    i = 0;\n  else\n    i = -2;                              /* indicate all other outcomes */\n  return( i );\n}\n\n\nSTATIC workarraysrec *mempool_create(lprec *lp)\n{\n  workarraysrec *temp;\n  temp = (workarraysrec *) calloc(1, sizeof(workarraysrec));\n  temp->lp = lp;\n  return( temp );\n}\nSTATIC char *mempool_obtainVector(workarraysrec *mempool, int count, int unitsize)\n{\n  char   *newmem = NULL;\n  MYBOOL *bnewmem = NULL;\n  int    *inewmem = NULL, size, i, ib, ie, memMargin = 0;\n  REAL   *rnewmem = NULL;\n\n  /* First find the iso-sized window (binary search) */\n  size = count*unitsize;\n  memMargin += size;\n  ib = 0;\n  ie = mempool->count-1;\n  while(ie >= ib) {\n    i = (ib+ie) / 2;\n    if(abs(mempool->vectorsize[i]) > memMargin)\n      ie = i-1;\n    else if(abs(mempool->vectorsize[i]) < size)\n      ib = i+1;\n    else {\n      /* Find the beginning of the exact-sized array group */\n      do {\n        ib = i;\n        i--;\n      } while((i >= 0) && (abs(mempool->vectorsize[i]) >= size));\n      break;\n    }\n  }\n\n  /* Check if we have a preallocated unused array of sufficient size */\n  ie = mempool->count-1;\n  for(i = ib; i <= ie; i++)\n    if(mempool->vectorsize[i] < 0)\n      break;\n\n  /* Obtain and activate existing, unused vector if we are permitted */\n  if(i <= ie) {\n#ifdef Paranoia\n    if((mempool->vectorsize[i] > 0) || (abs(mempool->vectorsize[i]) < size)) {\n      lprec *lp = mempool->lp;\n      lp->report(lp, SEVERE, \"mempool_obtainVector: Invalid %s existing vector selected\\n\",\n                             (ie < 0 ? \"too small\" : \"occupied\"));\n      lp->spx_status = NOMEMORY;\n      lp->bb_break = TRUE;\n      return( newmem );\n    }\n#endif\n    newmem = mempool->vectorarray[i];\n    mempool->vectorsize[i] *= -1;\n  }\n\n  /* Otherwise allocate a new vector */\n  else if(unitsize == sizeof(MYBOOL)) {\n    allocMYBOOL(mempool->lp, &bnewmem, count, TRUE);\n    newmem = (char *) bnewmem;\n  }\n  else if(unitsize == sizeof(int)) {\n    allocINT(mempool->lp, &inewmem, count, TRUE);\n    newmem = (char *) inewmem;\n  }\n  else if(unitsize == sizeof(REAL)) {\n    allocREAL(mempool->lp, &rnewmem, count, TRUE);\n    newmem = (char *) rnewmem;\n  }\n\n  /* Insert into master array if necessary (maintain sort by ascending size) */\n  if((i > ie) && (newmem != NULL)) {\n    mempool->count++;\n    if(mempool->count >= mempool->size) {\n      mempool->size += 10;\n      mempool->vectorarray = (char **) realloc(mempool->vectorarray,\n                                     sizeof(*(mempool->vectorarray))*mempool->size);\n      mempool->vectorsize  = (int *) realloc(mempool->vectorsize,\n                                     sizeof(*(mempool->vectorsize))*mempool->size);\n    }\n    ie++;\n    i = ie + 1;\n    if(i < mempool->count) {\n      MEMMOVE(mempool->vectorarray+i, mempool->vectorarray+ie, 1);\n      MEMMOVE(mempool->vectorsize+i,  mempool->vectorsize+ie,  1);\n    }\n    mempool->vectorarray[ie] = newmem;\n    mempool->vectorsize[ie]  = size;\n  }\n\n  return( newmem );\n}\nSTATIC MYBOOL mempool_releaseVector(workarraysrec *mempool, char *memvector, MYBOOL forcefree)\n{\n  int i;\n\n#if 0\n  forcefree = TRUE;\n#endif\n\n  for(i = mempool->count-1; i >= 0; i--)\n    if(mempool->vectorarray[i] == memvector)\n      break;\n\n  if((i < 0) || (mempool->vectorsize[i] < 0))\n    return( FALSE );\n\n  if(forcefree) {\n    FREE(mempool->vectorarray[i]);\n    mempool->count--;\n    for(; i < mempool->count; i++)\n      mempool->vectorarray[i] = mempool->vectorarray[i+1];\n  }\n  else\n    mempool->vectorsize[i] *= -1;\n\n  return( TRUE );\n}\nSTATIC MYBOOL mempool_free(workarraysrec **mempool)\n{\n  int i = (*mempool)->count;\n\n  while(i > 0) {\n    i--;\n    if((*mempool)->vectorsize[i] < 0)  /* Handle unused vectors */\n      (*mempool)->vectorsize[i] *= -1;\n    mempool_releaseVector(*mempool, (*mempool)->vectorarray[i], TRUE);\n  }\n  FREE((*mempool)->vectorarray);\n  FREE((*mempool)->vectorsize);\n  FREE(*mempool);\n  return( TRUE );\n}\n\nREAL *cloneREAL(lprec *lp, REAL *origlist, int size)\n{\n  REAL *newlist;\n\n  size += 1;\n  if(allocREAL(lp, &newlist, size, FALSE))\n    MEMCOPY(newlist, origlist, size);\n  return(newlist);\n}\nMYBOOL *cloneMYBOOL(lprec *lp, MYBOOL *origlist, int size)\n{\n  MYBOOL *newlist;\n\n  size += 1;\n  if(allocMYBOOL(lp, &newlist, size, FALSE))\n    MEMCOPY(newlist, origlist, size);\n  return(newlist);\n}\nint *cloneINT(lprec *lp, int *origlist, int size)\n{\n  int *newlist;\n\n  size += 1;\n  if(allocINT(lp, &newlist, size, FALSE))\n    MEMCOPY(newlist, origlist, size);\n  return(newlist);\n}\n\nSTATIC void roundVector(LREAL *myvector, int endpos, LREAL roundzero)\n{\n  if(roundzero > 0)\n    for(; endpos >= 0; myvector++, endpos--)\n      if(fabs(*myvector) < roundzero)\n        *myvector = 0;\n}\n\nSTATIC REAL normalizeVector(REAL *myvector, int endpos)\n/* Scale the ingoing vector so that its norm is unit, and return the original length */\n{\n  int  i;\n  REAL SSQ;\n\n  /* Cumulate squares */\n  SSQ = 0;\n  for(i = 0; i <= endpos; myvector++, i++)\n    SSQ += (*myvector) * (*myvector);\n\n  /* Normalize */\n  SSQ = sqrt(SSQ);\n  if(SSQ > 0)\n    for(myvector--; i > 0; myvector--, i--)\n      (*myvector) /= SSQ;\n\n  return( SSQ );\n}\n\n/* ---------------------------------------------------------------------------------- */\n/* Other general utilities                                                            */\n/* ---------------------------------------------------------------------------------- */\n\nSTATIC void swapINT(int *item1, int *item2)\n{\n  int hold = *item1;\n  *item1 = *item2;\n  *item2 = hold;\n}\n\nSTATIC void swapREAL(REAL *item1, REAL *item2)\n{\n  REAL hold = *item1;\n  *item1 = *item2;\n  *item2 = hold;\n}\n\nSTATIC void swapPTR(void **item1, void **item2)\n{\n  void *hold;\n  hold = *item1;\n  *item1 = *item2;\n  *item2 = hold;\n}\n\n\nSTATIC REAL restoreINT(REAL valREAL, REAL epsilon)\n{\n  REAL valINT, fracREAL, fracABS;\n\n  fracREAL = modf(valREAL, &valINT);\n  fracABS = fabs(fracREAL);\n  if(fracABS < epsilon)\n    return(valINT);\n  else if(fracABS > 1-epsilon) {\n    if(fracREAL < 0)\n      return(valINT-1);\n    else\n      return(valINT+1);\n  }\n  return(valREAL);\n}\n\nSTATIC REAL roundToPrecision(REAL value, REAL precision)\n{\n#if 1\n  REAL  vmod;\n  int   vexp2, vexp10;\n  LLONG sign;\n\n  if(precision == 0)\n    return(value);\n\n  sign  = my_sign(value);\n  value = fabs(value);\n\n  /* Round to integer if possible */\n  if(value < precision)\n    return( 0 );\n  else if(value == floor(value))\n    return( value*sign );\n  else if((value < (REAL) MAXINT64) &&\n     (modf((REAL) (value+precision), &vmod) < precision)) {\n    /* sign *= (LLONG) (value+precision); */\n    sign *= (LLONG) (value+0.5);\n    return( (REAL) sign );\n  }\n\n  /* Optionally round with base 2 representation for additional precision */\n#define roundPrecisionBase2\n#ifdef roundPrecisionBase2\n  value = frexp(value, &vexp2);\n#else\n  vexp2 = 0;\n#endif\n\n  /* Convert to desired precision */\n  vexp10 = (int) log10(value);\n  precision *= pow(10.0, vexp10);\n  modf(value/precision+0.5, &value);\n  value *= sign*precision;\n\n  /* Restore base 10 representation if base 2 was active */\n  if(vexp2 != 0)\n    value = ldexp(value, vexp2);\n#endif\n\n  return( value );\n}\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Searching function specialized for lp_solve                                        */\n/* ---------------------------------------------------------------------------------- */\nSTATIC int searchFor(int target, int *attributes, int size, int offset, MYBOOL absolute)\n{\n  int beginPos, endPos;\n  int newPos, match;\n\n /* Set starting and ending index offsets */\n  beginPos = offset;\n  endPos = beginPos + size - 1;\n\n /* Do binary search logic based on a sorted attribute vector */\n  newPos = (beginPos + endPos) / 2;\n  match = attributes[newPos];\n  if(absolute)\n    match = abs(match);\n  while(endPos - beginPos > LINEARSEARCH) {\n    if(match < target) {\n      beginPos = newPos + 1;\n      newPos = (beginPos + endPos) / 2;\n      match = attributes[newPos];\n      if(absolute)\n        match = abs(match);\n    }\n    else if(match > target) {\n      endPos = newPos - 1;\n      newPos = (beginPos + endPos) / 2;\n      match = attributes[newPos];\n      if(absolute)\n        match = abs(match);\n    }\n    else {\n      beginPos = newPos;\n      endPos = newPos;\n    }\n  }\n\n /* Do linear (unsorted) search logic */\n  if(endPos - beginPos <= LINEARSEARCH) {\n    match = attributes[beginPos];\n    if(absolute)\n      match = abs(match);\n      while((beginPos < endPos) && (match != target)) {\n        beginPos++;\n        match = attributes[beginPos];\n        if(absolute)\n          match = abs(match);\n      }\n      if(match == target)\n        endPos = beginPos;\n  }\n\n /* Return the index if a match was found, or signal failure with a -1 */\n  if((beginPos == endPos) && (match == target))\n    return(beginPos);\n  else\n    return(-1);\n\n}\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Other supporting math routines                                                     */\n/* ---------------------------------------------------------------------------------- */\n\nSTATIC MYBOOL isINT(lprec *lp, REAL value)\n{\n#if 0\n  return( (MYBOOL) (modf(fabs(value)+lp->epsint, &value) < 2*lp->epsint) );\n#elif 1\n  value = fabs(value)+lp->epsint;\n  return( (MYBOOL) (my_reldiff(value, floor(value)) < 2*lp->epsint) );\n#elif 0\n  REAL hold;\n  value = fabs(value);\n  hold = pow(10, MIN(-2, log10(value+1)+log10(lp->epsint)));\n  return( (MYBOOL) (modf(value+lp->epsint, &value) < 2*hold) );\n#elif 0\n  value -= (REAL)floor(value);\n  return( (MYBOOL) ((value < lp->epsint) || (value > (1 - lp->epsint)) );\n#else\n  value += lp->epsint;\n  return( (MYBOOL) (fabs(value-floor(value)) < 2*lp->epsint) );\n#endif\n}\n\nSTATIC MYBOOL isOrigFixed(lprec *lp, int varno)\n{\n  return( (MYBOOL) (lp->orig_upbo[varno] - lp->orig_lowbo[varno] <= lp->epsmachine) );\n}\n\nSTATIC void chsign_bounds(REAL *lobound, REAL *upbound)\n{\n  REAL temp;\n  temp = *upbound;\n  if(fabs(*lobound) > 0)\n    *upbound = -(*lobound);\n  else\n    *upbound = 0;\n  if(fabs(temp) > 0)\n    *lobound = -temp;\n  else\n    *lobound = 0;\n}\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Define randomization routine                                                       */\n/* ---------------------------------------------------------------------------------- */\nSTATIC REAL rand_uniform(lprec *lp, REAL range)\n{\n  static MYBOOL randomized = FALSE; /* static ok here for reentrancy/multithreading */\n\n  if(!randomized) {\n    randomized = TRUE;\n    srand((unsigned) time( NULL ));\n  }\n  range *= (REAL) rand() / (REAL) RAND_MAX;\n  return( range );\n}\n\n\n/* ---------------------------------------------------------------------------------- */\n/* Define routines for doubly linked lists of integers                                */\n/* ---------------------------------------------------------------------------------- */\n\nSTATIC int createLink(int size, LLrec **linkmap, MYBOOL *usedpos)\n{\n  int i, j;\n  MYBOOL reverse;\n\n  *linkmap = (LLrec *) calloc(1, sizeof(**linkmap));\n  if(*linkmap == NULL)\n    return( -1 );\n\n  reverse = (MYBOOL) (size < 0);\n  if(reverse)\n    size = -size;\n  (*linkmap)->map = (int *) calloc(2*(size + 1), sizeof(int));\n  if((*linkmap)->map == NULL)\n    return( -1 );\n\n  (*linkmap)->size = size;\n  j = 0;\n  if(usedpos == NULL)\n    (*linkmap)->map[0] = 0;\n  else {\n    for(i = 1; i <= size; i++)\n      if(!usedpos[i] ^ reverse) {\n        /* Set the forward link */\n        (*linkmap)->map[j] = i;\n        /* Set the backward link */\n        (*linkmap)->map[size+i] = j;\n        j = i;\n        if((*linkmap)->count == 0)\n          (*linkmap)->firstitem = i;\n        (*linkmap)->lastitem = i;\n        (*linkmap)->count++;\n      }\n  }\n  (*linkmap)->map[2*size+1] = j;\n\n  return( (*linkmap)->count );\n}\n\nSTATIC MYBOOL freeLink(LLrec **linkmap)\n{\n  MYBOOL status = TRUE;\n\n  if((linkmap == NULL) || (*linkmap == NULL))\n    status = FALSE;\n  else {\n    if((*linkmap)->map != NULL)\n      free((*linkmap)->map);\n    free(*linkmap);\n    *linkmap = NULL;\n  }\n  return( status );\n}\n\nSTATIC int sizeLink(LLrec *linkmap)\n{\n  return(linkmap->size);\n}\n\nSTATIC MYBOOL isActiveLink(LLrec *linkmap, int itemnr)\n{\n  if((linkmap->map[itemnr] != 0) ||\n     (linkmap->map[linkmap->size+itemnr] != 0) ||\n     (linkmap->map[0] == itemnr))\n    return( TRUE );\n  else\n    return( FALSE );\n}\n\nSTATIC int countActiveLink(LLrec *linkmap)\n{\n  return(linkmap->count);\n}\n\nSTATIC int countInactiveLink(LLrec *linkmap)\n{\n  return(linkmap->size-linkmap->count);\n}\n\nSTATIC int firstActiveLink(LLrec *linkmap)\n{\n  return(linkmap->map[0]);\n}\n\nSTATIC int lastActiveLink(LLrec *linkmap)\n{\n  return(linkmap->map[2*linkmap->size+1]);\n}\n\nSTATIC MYBOOL appendLink(LLrec *linkmap, int newitem)\n{\n  int k, size;\n  size = linkmap->size;\n\n  if(linkmap->map[newitem] != 0)\n    return( FALSE );\n\n  /* Link forward */\n  k = linkmap->map[2*size+1];\n  linkmap->map[k] = newitem;\n\n  /* Link backward */\n  linkmap->map[size+newitem] = k;\n  linkmap->map[2*size+1] = newitem;\n\n  /* Update count and return */\n  if(linkmap->count == 0)\n    linkmap->firstitem = newitem;\n  linkmap->lastitem = newitem;\n  linkmap->count++;\n\n  return( TRUE );\n}\n\nSTATIC MYBOOL insertLink(LLrec *linkmap, int afteritem, int newitem)\n{\n  int k, size;\n\n  size = linkmap->size;\n\n  if(linkmap->map[newitem] != 0)\n    return( FALSE );\n\n  if(afteritem == linkmap->map[2*size+1])\n    appendLink(linkmap, newitem);\n  else {\n    /* Link forward */\n    k = linkmap->map[afteritem];\n    linkmap->map[afteritem] = newitem;\n    linkmap->map[newitem] = k;\n\n    /* Link backward */\n    linkmap->map[size+k] = newitem;\n    linkmap->map[size+newitem] = afteritem;\n\n    /* Update count */\n    SETMIN(linkmap->firstitem, newitem);\n    SETMAX(linkmap->lastitem, newitem);\n    linkmap->count++;\n  }\n\n  return( TRUE );\n}\n\nSTATIC MYBOOL setLink(LLrec *linkmap, int newitem)\n{\n  if(isActiveLink(linkmap, newitem))\n    return( FALSE );\n  else\n    return( insertLink(linkmap, prevActiveLink(linkmap, newitem), newitem) );\n}\n\nSTATIC MYBOOL fillLink(LLrec *linkmap)\n{\n  int k, size;\n  size = linkmap->size;\n\n  k = firstActiveLink(linkmap);\n  if(k != 0)\n    return( FALSE );\n  for(k = 1; k <= size; k++)\n    appendLink(linkmap, k);\n  return( TRUE );\n}\n\nSTATIC int nextActiveLink(LLrec *linkmap, int backitemnr)\n{\n  if((backitemnr < 0) || (backitemnr > linkmap->size))\n    return( -1 );\n  else {\n    if(backitemnr < linkmap->lastitem)\n    while((backitemnr > linkmap->firstitem) && (linkmap->map[backitemnr] == 0))\n      backitemnr--;\n    return(linkmap->map[backitemnr]);\n  }\n}\n\nSTATIC int prevActiveLink(LLrec *linkmap, int forwitemnr)\n{\n  if((forwitemnr <= 0) || (forwitemnr > linkmap->size+1))\n    return( -1 );\n  else {\n    if(forwitemnr > linkmap->lastitem)\n      return( linkmap->lastitem);\n    if(forwitemnr > linkmap->firstitem) {\n      forwitemnr += linkmap->size;\n      while((forwitemnr < linkmap->size + linkmap->lastitem) && (linkmap->map[forwitemnr] == 0))\n        forwitemnr++;\n    }\n    else\n      forwitemnr += linkmap->size;\n    return(linkmap->map[forwitemnr]);\n  }\n}\n\nSTATIC int firstInactiveLink(LLrec *linkmap)\n{\n  int i, n;\n\n  if(countInactiveLink(linkmap) == 0)\n    return( 0 );\n  n = 1;\n  i = firstActiveLink(linkmap);\n  while(i == n) {\n    n++;\n    i = nextActiveLink(linkmap, i);\n  }\n  return( n );\n}\n\nSTATIC int lastInactiveLink(LLrec *linkmap)\n{\n  int i, n;\n\n  if(countInactiveLink(linkmap) == 0)\n    return( 0 );\n  n = linkmap->size;\n  i = lastActiveLink(linkmap);\n  while(i == n) {\n    n--;\n    i = prevActiveLink(linkmap, i);\n  }\n  return( n );\n}\n\nSTATIC int nextInactiveLink(LLrec *linkmap, int backitemnr)\n{\n  do {\n    backitemnr++;\n  } while((backitemnr <= linkmap->size) && isActiveLink(linkmap, backitemnr));\n  if(backitemnr <= linkmap->size)\n    return( backitemnr );\n  else\n    return( 0 );\n}\n\nSTATIC int prevInactiveLink(LLrec *linkmap, int forwitemnr)\n{\n  return( 0 );\n}\n\nSTATIC int removeLink(LLrec *linkmap, int itemnr)\n{\n  int size, prevnr, nextnr = -1;\n\n  size = linkmap->size;\n  if((itemnr <= 0) || (itemnr > size))\n    return( nextnr );\n#ifdef Paranoia\n  if(!isActiveLink(linkmap, itemnr))\n    return( nextnr );\n#endif\n\n  /* Get link data at the specified position */\n  nextnr = linkmap->map[itemnr];\n  prevnr = linkmap->map[size+itemnr];\n  if(itemnr == linkmap->firstitem)\n    linkmap->firstitem = nextnr;\n  if(itemnr == linkmap->lastitem)\n    linkmap->lastitem = prevnr;\n\n  /* Update forward link */\n  linkmap->map[prevnr] = linkmap->map[itemnr];\n  linkmap->map[itemnr] = 0;\n\n  /* Update backward link */\n  if(nextnr == 0)\n    linkmap->map[2*size+1] = prevnr;\n  else\n    linkmap->map[size+nextnr] = linkmap->map[size+itemnr];\n  linkmap->map[size+itemnr] = 0;\n\n  /* Decrement the count */\n  linkmap->count--;\n\n  /* Return the next active item */\n  return( nextnr );\n}\n\nSTATIC LLrec *cloneLink(LLrec *sourcemap, int newsize, MYBOOL freesource)\n{\n  LLrec *testmap = NULL;\n\n  if((newsize == sourcemap->size) || (newsize <= 0)) {\n    createLink(sourcemap->size, &testmap, NULL);\n    MEMCOPY(testmap->map, sourcemap->map, 2*(sourcemap->size+1));\n    testmap->firstitem = sourcemap->firstitem;\n    testmap->lastitem = sourcemap->lastitem;\n    testmap->size = sourcemap->size;\n    testmap->count = sourcemap->count;\n  }\n  else {\n    int j;\n\n    createLink(newsize, &testmap, NULL);\n    for(j = firstActiveLink(sourcemap); (j != 0) && (j <= newsize); j = nextActiveLink(sourcemap, j))\n      appendLink(testmap, j);\n  }\n  if(freesource)\n    freeLink(&sourcemap);\n\n  return(testmap);\n}\n\nSTATIC int compareLink(LLrec *linkmap1, LLrec *linkmap2)\n{\n  int test;\n\n  test = memcmp(&linkmap1->size, &linkmap2->size, sizeof(int));\n  if(test == 0)\n    test = memcmp(&linkmap1->count, &linkmap2->count, sizeof(int));\n    if(test == 0)\n      test = memcmp(linkmap1->map, linkmap2->map, sizeof(int)*(2*linkmap1->size+1));\n\n  return( test );\n}\n\nSTATIC MYBOOL verifyLink(LLrec *linkmap, int itemnr, MYBOOL doappend)\n{\n  LLrec *testmap;\n\n  testmap = cloneLink(linkmap, -1, FALSE);\n  if(doappend) {\n    appendLink(testmap, itemnr);\n    removeLink(testmap, itemnr);\n  }\n  else {\n    int previtem = prevActiveLink(testmap, itemnr);\n    removeLink(testmap, itemnr);\n    insertLink(testmap, previtem, itemnr);\n  }\n  itemnr = compareLink(linkmap, testmap);\n  freeLink(&testmap);\n  return((MYBOOL) (itemnr == 0));\n}\n\n/* Packed vector routines */\nSTATIC PVrec *createPackedVector(int size, REAL *values, int *workvector)\n{\n  int      i, k;\n  REGISTER REAL  ref;\n  PVrec    *newPV = NULL;\n  MYBOOL   localWV = (MYBOOL) (workvector == NULL);\n\n  if(localWV)\n    workvector = (int *) malloc((size+1)*sizeof(*workvector));\n\n  /* Tally equal-valued vector entries - also check if it is worth compressing */\n  k = 0;\n  workvector[k] = 1;\n  ref = values[1];\n  for(i = 2; i <= size; i++) {\n    if(fabs(ref - values[i]) > DEF_EPSMACHINE) {\n      k++;\n      workvector[k] = i;\n      ref = values[i];\n    }\n  }\n  if(k > size / 2) {\n    if(localWV)\n      FREE(workvector);\n    return( newPV );\n  }\n\n  /* Create the packing object, adjust the position vector and allocate value vector */\n  newPV = (PVrec *) malloc(sizeof(*newPV));\n  k++;                            /* Adjust from index to to count */\n  newPV->count = k;\n  if(localWV)\n    newPV->startpos = (int *) realloc(workvector, (k + 1)*sizeof(*(newPV->startpos)));\n  else {\n    newPV->startpos = (int *) malloc((k + 1)*sizeof(*(newPV->startpos)));\n    MEMCOPY(newPV->startpos, workvector, k);\n  }\n  newPV->startpos[k] = size + 1;  /* Store terminal index + 1 for searching purposes */\n  newPV->value = (REAL *) malloc(k*sizeof(*(newPV->value)));\n\n  /* Fill the values vector before returning */\n  for(i = 0; i < k; i++)\n    newPV->value[i] = values[newPV->startpos[i]];\n\n  return( newPV );\n}\n\nSTATIC MYBOOL unpackPackedVector(PVrec *PV, REAL **target)\n{\n  int      i, ii, k;\n  REGISTER REAL ref;\n\n  /* Test for validity of the target and create it if necessary */\n  if(target == NULL)\n    return( FALSE );\n  if(*target == NULL)\n    allocREAL(NULL, target, PV->startpos[PV->count], FALSE);\n\n  /* Expand the packed vector into the target */\n  i = PV->startpos[0];\n  for(k = 0; k < PV->count; k++) {\n    ii = PV->startpos[k+1];\n    ref = PV->value[k];\n    while (i < ii) {\n      (*target)[i] = ref;\n      i++;\n    }\n  }\n  return( TRUE );\n}\n\nSTATIC REAL getvaluePackedVector(PVrec *PV, int index)\n{\n  index = searchFor(index, PV->startpos, PV->count, 0, FALSE);\n  index = abs(index)-1;\n  if(index >= 0)\n    return( PV->value[index] );\n  else\n    return( 0 );\n}\n\nSTATIC MYBOOL freePackedVector(PVrec **PV)\n{\n  if((PV == NULL) || (*PV == NULL))\n    return( FALSE );\n\n  FREE((*PV)->value);\n  FREE((*PV)->startpos);\n  FREE(*PV);\n  return( TRUE );\n}\n\nSTATIC void pushPackedVector(PVrec *PV, PVrec *parent)\n{\n  PV->parent = parent;\n}\n\nSTATIC PVrec *popPackedVector(PVrec *PV)\n{\n  PVrec *parent = PV->parent;\n  freePackedVector(&PV);\n  return( parent );\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_utils.h",
    "content": "#ifndef HEADER_lp_utils\n#define HEADER_lp_utils\n\n#ifdef FORTIFY\n\n#include \"lp_fortify.h\"\n\n#define allocCHAR allocCHAR_FORTIFY\n#define allocMYBOOL allocMYBOOL_FORTIFY\n#define allocINT allocINT_FORTIFY\n#define allocREAL allocREAL_FORTIFY\n#define allocLREAL allocLREAL_FORTIFY\n\n#endif\n\n#include \"lp_types.h\"\n\n/* Temporary data storage arrays */\ntypedef struct _workarraysrec\n{\n  lprec     *lp;\n  int       size;\n  int       count;\n  char      **vectorarray;\n  int       *vectorsize;\n} workarraysrec;\n\ntypedef struct _LLrec\n{\n  int       size;               /* The allocated list size */\n  int       count;              /* The current entry count */\n  int       firstitem;\n  int       lastitem;\n  int       *map;               /* The list of forward and backward-mapped entries */\n} LLrec;\n\ntypedef struct _PVrec\n{\n  int       count;              /* The allocated list item count */\n  int       *startpos;          /* Starting index of the current value */\n  REAL      *value;             /* The list of forward and backward-mapped entries */\n  struct   _PVrec *parent;     /* The parent record in a pushed chain */\n} PVrec;\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\nSTATIC MYBOOL allocCHAR(lprec *lp, char **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocMYBOOL(lprec *lp, MYBOOL **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocINT(lprec *lp, int **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocREAL(lprec *lp, REAL **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocLREAL(lprec *lp, LREAL **ptr, int size, MYBOOL clear);\nSTATIC MYBOOL allocFREE(lprec *lp, void **ptr);\nREAL *cloneREAL(lprec *lp, REAL *origlist, int size);\nMYBOOL *cloneMYBOOL(lprec *lp, MYBOOL *origlist, int size);\nint *cloneINT(lprec *lp, int *origlist, int size);\n\nint comp_bits(MYBOOL *bitarray1, MYBOOL *bitarray2, int items);\n\nSTATIC workarraysrec *mempool_create(lprec *lp);\nSTATIC char *mempool_obtainVector(workarraysrec *mempool, int count, int unitsize);\nSTATIC MYBOOL mempool_releaseVector(workarraysrec *mempool, char *memvector, MYBOOL forcefree);\nSTATIC MYBOOL mempool_free(workarraysrec **mempool);\n\nSTATIC void roundVector(LREAL *myvector, int endpos, LREAL roundzero);\nSTATIC REAL normalizeVector(REAL *myvector, int endpos);\n\nSTATIC void swapINT(int *item1, int *item2);\nSTATIC void swapREAL(REAL *item1, REAL *item2);\nSTATIC void swapPTR(void **item1, void **item2);\nSTATIC REAL restoreINT(REAL valREAL, REAL epsilon);\nSTATIC REAL roundToPrecision(REAL value, REAL precision);\n\nSTATIC int searchFor(int target, int *attributes, int size, int offset, MYBOOL absolute);\n\nSTATIC MYBOOL isINT(lprec *lp, REAL value);\nSTATIC MYBOOL isOrigFixed(lprec *lp, int varno);\nSTATIC void chsign_bounds(REAL *lobound, REAL *upbound);\nSTATIC REAL rand_uniform(lprec *lp, REAL range);\n\n/* Doubly linked list routines */\nSTATIC int createLink(int size, LLrec **linkmap, MYBOOL *usedpos);\nSTATIC MYBOOL freeLink(LLrec **linkmap);\nSTATIC int sizeLink(LLrec *linkmap);\nSTATIC MYBOOL isActiveLink(LLrec *linkmap, int itemnr);\nSTATIC int countActiveLink(LLrec *linkmap);\nSTATIC int countInactiveLink(LLrec *linkmap);\nSTATIC int firstActiveLink(LLrec *linkmap);\nSTATIC int lastActiveLink(LLrec *linkmap);\nSTATIC MYBOOL appendLink(LLrec *linkmap, int newitem);\nSTATIC MYBOOL insertLink(LLrec *linkmap, int afteritem, int newitem);\nSTATIC MYBOOL setLink(LLrec *linkmap, int newitem);\nSTATIC MYBOOL fillLink(LLrec *linkmap);\nSTATIC int nextActiveLink(LLrec *linkmap, int backitemnr);\nSTATIC int prevActiveLink(LLrec *linkmap, int forwitemnr);\nSTATIC int firstInactiveLink(LLrec *linkmap);\nSTATIC int lastInactiveLink(LLrec *linkmap);\nSTATIC int nextInactiveLink(LLrec *linkmap, int backitemnr);\nSTATIC int prevInactiveLink(LLrec *linkmap, int forwitemnr);\nSTATIC int removeLink(LLrec *linkmap, int itemnr);\nSTATIC LLrec *cloneLink(LLrec *sourcemap, int newsize, MYBOOL freesource);\nSTATIC int compareLink(LLrec *linkmap1, LLrec *linkmap2);\nSTATIC MYBOOL verifyLink(LLrec *linkmap, int itemnr, MYBOOL doappend);\n\n/* Packed vector routines */\nSTATIC PVrec  *createPackedVector(int size, REAL *values, int *workvector);\nSTATIC void   pushPackedVector(PVrec *PV, PVrec *parent);\nSTATIC MYBOOL unpackPackedVector(PVrec *PV, REAL **target);\nSTATIC REAL   getvaluePackedVector(PVrec *PV, int index);\nSTATIC PVrec  *popPackedVector(PVrec *PV);\nSTATIC MYBOOL freePackedVector(PVrec **PV);\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_utils */\n\n#ifdef FORTIFY\n\n#if defined CODE_lp_utils && !defined CODE_lp_utils_\nint _Fortify_ret;\n#else\nextern int _Fortify_ret;\n#endif\n\n#ifdef CODE_lp_utils\n#define CODE_lp_utils_\n#else\n# undef allocCHAR\n# undef allocMYBOOL\n# undef allocINT\n# undef allocREAL\n# undef allocLREAL\n# define allocCHAR(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocCHAR_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n# define allocMYBOOL(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocMYBOOL_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n# define allocINT(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocINT_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n# define allocREAL(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocREAL_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n# define allocLREAL(lp, ptr, size, clear) (Fortify_LINE(__LINE__), Fortify_FILE(__FILE__), _Fortify_ret = allocLREAL_FORTIFY(lp, ptr, size, clear), Fortify_LINE(0), Fortify_FILE(NULL), _Fortify_ret)\n#endif\n\n#endif\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_wlp.c",
    "content": "\n#include <stdio.h>\n#include <stdarg.h>\n#include <string.h>\n\n#include \"commonlib.h\"\n#include \"lp_lib.h\"\n#include \"lp_scale.h\"\n#include \"lp_utils.h\"\n#include \"lp_report.h\"\n#include \"lp_wlp.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* Define buffer-size controled function mapping */\n# if defined _MSC_VER\n#  define vsnprintf _vsnprintf\n# endif\n\n/* ------------------------------------------------------------------------- */\n/* Input and output of lp format model files for lp_solve                    */\n/* ------------------------------------------------------------------------- */\n\nstatic int write_data(void *userhandle, write_modeldata_func write_modeldata, char *format, ...)\n{\n  char buff[DEF_STRBUFSIZE+1];\n  va_list ap;\n  int n;\n\n  va_start(ap, format);\n  vsnprintf(buff, DEF_STRBUFSIZE, format, ap);\n  va_end(ap);\n  n = write_modeldata(userhandle, buff);\n  return(n);\n}\n\nSTATIC void write_lpcomment(void *userhandle, write_modeldata_func write_modeldata, char *string, MYBOOL newlinebefore)\n{\n  write_data(userhandle, write_modeldata, \"%s/* %s */\\n\", (newlinebefore) ? \"\\n\" : \"\", string);\n}\n\nSTATIC int write_lprow(lprec *lp, int rowno, void *userhandle, write_modeldata_func write_modeldata, int maxlen, int *idx, REAL *val)\n{\n  int     i, j, nchars, elements;\n  REAL    a;\n  MYBOOL  first = TRUE;\n  char    buf[50];\n\n  elements = get_rowex(lp, rowno, val, idx);\n  if(write_modeldata != NULL) {\n    nchars = 0;\n    for(i = 0; i < elements; i++) {\n      j = idx[i];\n      if(is_splitvar(lp, j))\n        continue;\n      a = val[i];\n      if(!first)\n        nchars += write_data(userhandle, write_modeldata, \" \");\n      else\n        first = FALSE;\n      sprintf(buf, \"%+.12g\", (double)a);\n      if(strcmp(buf, \"-1\") == 0)\n        nchars += write_data(userhandle, write_modeldata, \"-\");\n      else if(strcmp(buf, \"+1\") == 0)\n        nchars += write_data(userhandle, write_modeldata, \"+\");\n      else\n        nchars += write_data(userhandle, write_modeldata, \"%s \", buf);\n      nchars += write_data(userhandle, write_modeldata, \"%s\", get_col_name(lp, j));\n      /* Check if we should add a linefeed */\n      if((maxlen > 0) && (nchars >= maxlen) && (i < elements-1)) {\n        write_data(userhandle, write_modeldata, \"%s\", \"\\n\");\n        nchars = 0;\n      }\n    }\n  }\n  return(elements);\n}\n\n#if !defined LP_MAXLINELEN\n# define LP_MAXLINELEN 100\n#endif\n\nMYBOOL __WINAPI write_lpex(lprec *lp, void *userhandle, write_modeldata_func write_modeldata)\n{\n  int    i, j, b,\n         nrows = lp->rows,\n         ncols = lp->columns,\n         nchars, maxlen = LP_MAXLINELEN,\n         *idx;\n  MYBOOL ok;\n  REAL   a, *val;\n  char   *ptr;\n\n  if(!mat_validate(lp->matA)) {\n    report(lp, IMPORTANT, \"LP_writefile: Could not validate the data matrix.\\n\");\n    return(FALSE);\n  }\n\n  /* Write name of model */\n  ptr = get_lp_name(lp);\n  if(ptr != NULL) {\n    if(*ptr)\n      write_lpcomment(userhandle, write_modeldata, ptr, FALSE);\n    else\n      ptr = NULL;\n  }\n\n  /* Write the objective function */\n  write_lpcomment(userhandle, write_modeldata, \"Objective function\", (MYBOOL) (ptr != NULL));\n  if(is_maxim(lp))\n    write_data(userhandle, write_modeldata, \"max: \");\n  else\n    write_data(userhandle, write_modeldata, \"min: \");\n\n  allocREAL(lp, &val, 1 + lp->columns, TRUE);\n  allocINT(lp, &idx, 1 + lp->columns, TRUE);\n\n  write_lprow(lp, 0, userhandle, write_modeldata, maxlen, idx, val);\n  a = get_rh(lp, 0);\n  if(a != 0)\n    write_data(userhandle, write_modeldata, \" %+.12g\", a);\n  write_data(userhandle, write_modeldata, \";\\n\");\n\n  /* Write constraints */\n  if(nrows > 0)\n    write_lpcomment(userhandle, write_modeldata, \"Constraints\", TRUE);\n  for(j = 1; j <= nrows; j++) {\n    if(((lp->names_used) && (lp->row_name[j] != NULL)) || (write_lprow(lp, j, userhandle, NULL, maxlen, idx, val) == 1))\n      ptr = get_row_name(lp, j);\n    else\n      ptr = NULL;\n    if((ptr != NULL) && (*ptr))\n      write_data(userhandle, write_modeldata, \"%s: \", ptr);\n\n#ifndef SingleBoundedRowInLP\n    /* Write the ranged part of the constraint, if specified */\n    if ((lp->orig_upbo[j]) && (lp->orig_upbo[j] < lp->infinite)) {\n      if(my_chsign(is_chsign(lp, j), lp->orig_rhs[j]) == -lp->infinite)\n        write_data(userhandle, write_modeldata, \"-Inf %s \", (is_chsign(lp, j)) ? \">=\" : \"<=\");\n      else if(my_chsign(is_chsign(lp, j), lp->orig_rhs[j]) == lp->infinite)\n        write_data(userhandle, write_modeldata, \"+Inf %s \", (is_chsign(lp, j)) ? \">=\" : \"<=\");\n      else\n        write_data(userhandle, write_modeldata, \"%+.12g %s \",\n                (lp->orig_upbo[j]-lp->orig_rhs[j]) * (is_chsign(lp, j) ? 1.0 : -1.0) / (lp->scaling_used ? lp->scalars[j] : 1.0),\n                (is_chsign(lp, j)) ? \">=\" : \"<=\");\n    }\n#endif\n\n    if((!write_lprow(lp, j, userhandle, write_modeldata, maxlen, idx, val)) && (ncols >= 1))\n      write_data(userhandle, write_modeldata, \"0 %s\", get_col_name(lp, 1));\n\n    if(lp->orig_upbo[j] == 0)\n      write_data(userhandle, write_modeldata, \" =\");\n    else if(is_chsign(lp, j))\n      write_data(userhandle, write_modeldata, \" >=\");\n    else\n      write_data(userhandle, write_modeldata, \" <=\");\n    if(fabs(get_rh(lp, j) + lp->infinite) < 1)\n      write_data(userhandle, write_modeldata, \" -Inf;\\n\");\n    else if(fabs(get_rh(lp, j) - lp->infinite) < 1)\n      write_data(userhandle, write_modeldata, \" +Inf;\\n\");\n    else\n      write_data(userhandle, write_modeldata, \" %.12g;\\n\", get_rh(lp, j));\n\n#ifdef SingleBoundedRowInLP\n    /* Write the ranged part of the constraint, if specified */\n    if ((lp->orig_upbo[j]) && (lp->orig_upbo[j] < lp->infinite)) {\n      if(((lp->names_used) && (lp->row_name[j] != NULL)) || (write_lprow(lp, j, userhandle, NULL, maxlen, idx, val) == 1))\n        ptr = get_row_name(lp, j);\n      else\n        ptr = NULL;\n      if((ptr != NULL) && (*ptr))\n        write_data(userhandle, write_modeldata, \"%s: \", ptr);\n      if((!write_lprow(lp, j, userhandle, write_modeldata, maxlen, idx, val)) && (get_Ncolumns(lp) >= 1))\n        write_data(userhandle, write_modeldata, \"0 %s\", get_col_name(lp, 1));\n      write_data(userhandle, write_modeldata, \" %s %g;\\n\",\n                     (is_chsign(lp, j)) ? \"<=\" : \">=\",\n                     (lp->orig_upbo[j]-lp->orig_rhs[j]) * (is_chsign(lp, j) ? 1.0 : -1.0) / (lp->scaling_used ? lp->scalars[j] : 1.0));\n    }\n#endif\n  }\n\n  /* Write bounds on variables */\n  ok = FALSE;\n  for(i = nrows + 1; i <= lp->sum; i++)\n    if(!is_splitvar(lp, i - nrows)) {\n      if(lp->orig_lowbo[i] == lp->orig_upbo[i]) {\n        if(!ok) {\n          write_lpcomment(userhandle, write_modeldata, \"Variable bounds\", TRUE);\n          ok = TRUE;\n        }\n        write_data(userhandle, write_modeldata, \"%s = %.12g;\\n\", get_col_name(lp, i - nrows), get_upbo(lp, i - nrows));\n      }\n      else {\n#ifndef SingleBoundedRowInLP\n        if((lp->orig_lowbo[i] != 0) && (lp->orig_upbo[i] < lp->infinite)) {\n          if(!ok) {\n            write_lpcomment(userhandle, write_modeldata, \"Variable bounds\", TRUE);\n            ok = TRUE;\n          }\n          if(lp->orig_lowbo[i] == -lp->infinite)\n            write_data(userhandle, write_modeldata, \"-Inf\");\n          else\n            write_data(userhandle, write_modeldata, \"%.12g\", get_lowbo(lp, i - nrows));\n          write_data(userhandle, write_modeldata, \" <= %s <= \", get_col_name(lp, i - nrows));\n          if(lp->orig_lowbo[i] == lp->infinite)\n            write_data(userhandle, write_modeldata, \"+Inf\");\n          else\n            write_data(userhandle, write_modeldata, \"%.12g\", get_upbo(lp, i - nrows));\n          write_data(userhandle, write_modeldata, \";\\n\");\n        }\n        else\n#endif\n        {\n          if(lp->orig_lowbo[i] != 0) {\n            if(!ok) {\n              write_lpcomment(userhandle, write_modeldata, \"Variable bounds\", TRUE);\n              ok = TRUE;\n            }\n            if(lp->orig_lowbo[i] == -lp->infinite)\n              write_data(userhandle, write_modeldata, \"%s >= -Inf;\\n\", get_col_name(lp, i - nrows));\n            else if(lp->orig_lowbo[i] == lp->infinite)\n              write_data(userhandle, write_modeldata, \"%s >= +Inf;\\n\", get_col_name(lp, i - nrows));\n            else\n              write_data(userhandle, write_modeldata, \"%s >= %.12g;\\n\",\n                         get_col_name(lp, i - nrows), get_lowbo(lp, i - nrows));\n          }\n          if(lp->orig_upbo[i] != lp->infinite) {\n            if(!ok) {\n              write_lpcomment(userhandle, write_modeldata, \"Variable bounds\", TRUE);\n              ok = TRUE;\n            }\n            write_data(userhandle, write_modeldata, \"%s <= %.12g;\\n\",\n                       get_col_name(lp, i - nrows), get_upbo(lp, i - nrows));\n          }\n        }\n      }\n    }\n\n  /* Write optional integer section */\n  if(lp->int_vars > 0) {\n    write_lpcomment(userhandle, write_modeldata, \"Integer definitions\", TRUE);\n    i = 1;\n    while((i <= ncols) && !is_int(lp, i))\n      i++;\n    if(i <= ncols) {\n      nchars = write_data(userhandle, write_modeldata, \"int %s\", get_col_name(lp, i));\n      i++;\n      for(; i <= ncols; i++)\n        if((!is_splitvar(lp, i)) && (is_int(lp, i))) {\n          if((maxlen!= 0) && (nchars > maxlen)) {\n            write_data(userhandle, write_modeldata, \"%s\", \"\\n\");\n            nchars = 0;\n          }\n          write_data(userhandle, write_modeldata, \",%s\", get_col_name(lp, i));\n        }\n      write_data(userhandle, write_modeldata, \";\\n\");\n    }\n  }\n\n  /* Write optional SEC section */\n  if(lp->sc_vars > 0) {\n    write_lpcomment(userhandle, write_modeldata, \"Semi-continuous variables\", TRUE);\n    i = 1;\n    while((i <= ncols) && !is_semicont(lp, i))\n      i++;\n    if(i <= ncols) {\n      nchars = write_data(userhandle, write_modeldata, \"sec %s\", get_col_name(lp, i));\n      i++;\n      for(; i <= ncols; i++)\n        if((!is_splitvar(lp, i)) && (is_semicont(lp, i))) {\n          if((maxlen != 0) && (nchars > maxlen)) {\n            write_data(userhandle, write_modeldata, \"%s\", \"\\n\");\n            nchars = 0;\n          }\n          nchars += write_data(userhandle, write_modeldata, \",%s\", get_col_name(lp, i));\n        }\n      write_data(userhandle, write_modeldata, \";\\n\");\n    }\n  }\n\n  /* Write optional SOS section */\n  if(SOS_count(lp) > 0) {\n    SOSgroup *SOS = lp->SOS;\n    write_lpcomment(userhandle, write_modeldata, \"SOS definitions\", TRUE);\n    write_data(userhandle, write_modeldata, \"SOS\\n\");\n    for(b = 0, i = 0; i < SOS->sos_count; b = SOS->sos_list[i]->priority, i++) {\n      nchars = write_data(userhandle, write_modeldata, \"%s: \",\n              (SOS->sos_list[i]->name == NULL) ||\n              (*SOS->sos_list[i]->name==0) ? \"SOS\" : SOS->sos_list[i]->name); /* formatnumber12((double) lp->sos_list[i]->priority) */\n\n      for(a = 0.0, j = 1; j <= SOS->sos_list[i]->size; a = SOS->sos_list[i]->weights[j], j++) {\n        if((maxlen != 0) && (nchars > maxlen)) {\n          write_data(userhandle, write_modeldata, \"%s\", \"\\n\");\n          nchars = 0;\n        }\n        if(SOS->sos_list[i]->weights[j] == ++a)\n          nchars += write_data(userhandle, write_modeldata, \"%s%s\",\n                  (j > 1) ? \",\" : \"\",\n                  get_col_name(lp, SOS->sos_list[i]->members[j]));\n        else\n          nchars += write_data(userhandle, write_modeldata, \"%s%s:%.12g\",\n                  (j > 1) ? \",\" : \"\",\n                  get_col_name(lp, SOS->sos_list[i]->members[j]),\n        SOS->sos_list[i]->weights[j]);\n      }\n      if(SOS->sos_list[i]->priority == ++b)\n        nchars += write_data(userhandle, write_modeldata, \" <= %d;\\n\", SOS->sos_list[i]->type);\n      else\n        nchars += write_data(userhandle, write_modeldata, \" <= %d:%d;\\n\", SOS->sos_list[i]->type, SOS->sos_list[i]->priority);\n    }\n  }\n\n  FREE(val);\n  FREE(idx);\n\n  ok = TRUE;\n\n  return(ok);\n}\n\nstatic int __WINAPI write_lpdata(void *userhandle, char *buf)\n{\n  return(fprintf((FILE *) userhandle, \"%s\", buf));\n}\n\nMYBOOL LP_writefile(lprec *lp, char *filename)\n{\n  FILE *output = stdout;\n  MYBOOL ok;\n\n  if (filename != NULL) {\n    ok = (MYBOOL) ((output = fopen(filename, \"w\")) != NULL);\n    if(!ok)\n      return(ok);\n  }\n  else\n    output = lp->outstream;\n\n  ok = write_lpex(lp, (void *) output, write_lpdata);\n\n  if (filename != NULL)\n    fclose(output);\n\n  return(ok);\n}\n\nMYBOOL LP_writehandle(lprec *lp, FILE *output)\n{\n  MYBOOL ok;\n\n  if (output != NULL)\n    set_outputstream(lp, output);\n\n  output = lp->outstream;\n\n  ok = write_lpex(lp, (void *) output, write_lpdata);\n\n  return(ok);\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lp_wlp.h",
    "content": "#ifndef HEADER_lp_lp\n#define HEADER_lp_lp\n\n#include \"lp_types.h\"\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n/* Put function headers here */\nMYBOOL LP_writefile(lprec *lp, char *filename);\nMYBOOL LP_writehandle(lprec *lp, FILE *output);\n\n\n#ifdef __cplusplus\n }\n#endif\n\n#endif /* HEADER_lp_lp */\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpkit.h",
    "content": "#include \"lp_lib.h\"\n#include \"lp_report.h\"\n\n#define MALLOC(ptr, nr, type)\\\n  ((((nr) == 0) || ((ptr = (type *) malloc((size_t)((nr) * sizeof(*ptr)))) == NULL)) ? \\\n   report(NULL, CRITICAL, \"malloc of %d bytes failed on line %d of file %s\\n\",\\\n           (nr) * sizeof(*ptr), __LINE__, __FILE__), (ptr = NULL /* (void *) 0 */) : \\\n   ptr\\\n  )\n\n#define CALLOC(ptr, nr, type)\\\n  ((((nr) == 0) || ((ptr = (type *) calloc((size_t)(nr), sizeof(*ptr))) == NULL)) ? \\\n   report(NULL, CRITICAL, \"calloc of %d bytes failed on line %d of file %s\\n\",\\\n           (nr) * sizeof(*ptr), __LINE__, __FILE__), (ptr = NULL /* (void *) 0 */) : \\\n   ptr\\\n  )\n\n#define REALLOC(ptr, nr, type)\\\n  ((((nr) == 0) || ((ptr = (type *) realloc(ptr, (size_t)((nr) * sizeof(*ptr)))) == NULL)) ? \\\n   report(NULL, CRITICAL, \"realloc of %d bytes failed on line %d of file %s\\n\",\\\n           (nr) * sizeof(*ptr), __LINE__, __FILE__), (ptr = NULL /* (void *) 0 */) : \\\n   ptr\\\n  )\n\n#if defined FREE\n# undef FREE\n#endif\n\n#define FREE(ptr) if (ptr != NULL) {free(ptr), ptr = NULL;} else\n\n#define MALLOCCPY(nptr, optr, nr, type)\\\n  (MALLOC(nptr, nr, type), (nptr != NULL) ? memcpy(nptr, optr, (size_t)((nr) * sizeof(*optr))) : 0, nptr)\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve.h",
    "content": "// stdafx.h : include file for standard system include files,\n//  or project specific include files that are used frequently, but\n//      are changed infrequently\n//\n\n#if !defined(AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_)\n#define AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_\n\n#if _MSC_VER > 1000\n#pragma once\n#endif // _MSC_VER > 1000\n\n\n// Insert your headers here\n#define WIN32_LEAN_AND_MEAN\t\t// Exclude rarely-used stuff from Windows headers\n\n#include <windows.h>\n\n// TODO: reference additional headers your program requires here\n\n//{{AFX_INSERT_LOCATION}}\n// Microsoft Visual C++ will insert additional declarations immediately before the previous line.\n\n#endif // !defined(AFX_STDAFX_H__22BF6D92_917F_4BDF_B806_0954721EBA95__INCLUDED_)\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/ccc",
    "content": ":\nsrc='../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\n#c=cc\n\nif [ \"$ARCH\" = \"\" ]; then\n\tCFLAGS=-m32\nfi\nif [ \"$ARCH\" = \"amd64\" ]; then\n\tCFLAGS=\"-m64 -fPIC -DPIC\"\nfi\nif [ \"$ARCH\" = \"ia64\" ]; then\n\tCFLAGS=\"-fPIC -DPIC\"\nfi\nif [ \"$ARCH\" = \"aarch64\" ]; then\n\tCFLAGS=\"-fPIC -DPIC\"\nfi\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'int main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c $CFLAGS /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'int main(){isnan(0.0);}'>>/tmp/isnan.c\n$c $CFLAGS /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\ndef=\nso=\nif [ \"$PLATFORM\" = \"SCO_UNIX\" ]\nthen def='-dy -K PIC -DNOLONGLONG'\n     dl=-lc\nelse dl=-ldl\n     so=y\nfi\n\nopts='-O3'\n\n$c $CFLAGS -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\nar rv bin/$PLATFORM/liblpsolve55.a `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'`\nranlib bin/$PLATFORM/liblpsolve55.a\n\nif [ \"$so\" != \"\" ]\nthen\n  $c $CFLAGS -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I. $opts $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\n  $c $CFLAGS -shared -Wl,-Bsymbolic -Wl,-soname,liblpsolve55.so -o bin/$PLATFORM/liblpsolve55.so `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'` -lc -lm -ldl\n  mv bin/$PLATFORM/liblpsolve55.so ../../../lib\nfi\n\nrm *.o 2>/dev/null\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/ccc.aix",
    "content": ":\nsrc='../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\n\ntype xlc >/dev/null 2>&1\nif [ $? = 0 ]\nthen c=xlc\nelse c=cc\nfi\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'int main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'int main(){isnan(0.0);}'>>/tmp/isnan.c\n$c /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\ndef=\ndl=-ldl\nso=y\n\nopts='-O2'\n\n$c -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\nar rv bin/$PLATFORM/liblpsolve55.a `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'`\nranlib bin/$PLATFORM/liblpsolve55.a\n\nif [ \"$so\" != \"\" ]\nthen\n  $c -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I. $opts $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\n  tr -d '\\r' <../lp_solve.def | sed -e \"s/^EXPORTS$//g\" >liblpsolve55.exp\n  rm liblpsolve55.so 2>/dev/null\n  $c -bM:SRE -bE:liblpsolve55.exp -bnoentry -o bin/$PLATFORM/liblpsolve55.so `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'` -lc -lm -ldl\nfi\n\nrm *.o 2>/dev/null\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/ccc.cygwin",
    "content": ":\nsrc='../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\n#c=cc\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'int main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'int main(){isnan(0.0);}'>>/tmp/isnan.c\n$c /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\ndef=\nso=\nif [ \"$PLATFORM\" = \"SCO_UNIX\" ]\nthen def='-dy -K PIC -DNOLONGLONG'\n     dl=-lc\nelse dl=-ldl\n     so=y\nfi\n\nopts='-O3'\n\n#$c -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine -mno-cygwin $src\n#ar rv bin/$PLATFORM/liblpsolve55.a `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'`\n#ranlib bin/$PLATFORM/liblpsolve55.a\n\nif [ \"$so\" != \"\" ]\nthen\n  $c -DINLINE=static -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -s -O3 -shared -mno-cygwin -enable-stdcall-fixup -D_USRDLL -DWIN32 -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src ../lp_solve.def -o bin/$PLATFORM/lpsolve55.dll\n  $c -DINLINE=static -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -s -O3 -shared -D_USRDLL -DWIN32 -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src -o bin/$PLATFORM/liblpsolve55.so\n  mv bin/$PLATFORM/lpsolve55.dll ../../../lib\nfi\n\nrm *.o 2>/dev/null\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/ccc.hp-ux",
    "content": ":\r\nsrc='../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\r\nc=cc\r\n\r\n#determine platform (32/64 bit)\r\n>/tmp/platform.c\r\necho '#include <stdlib.h>'>>/tmp/platform.c\r\necho '#include <stdio.h>'>>/tmp/platform.c\r\necho 'int main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\r\n$c /tmp/platform.c -o /tmp/platform\r\nPLATFORM=`/tmp/platform`\r\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\r\n\r\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\r\n\r\n#check if this system has the isnan function\r\n>/tmp/isnan.c\r\necho '#include <stdio.h>'>>/tmp/isnan.c\r\necho '#include <stdlib.h>'>>/tmp/isnan.c\r\necho '#include <math.h>'>>/tmp/isnan.c\r\necho 'int main(){isnan(0.0);}'>>/tmp/isnan.c\r\n$c /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\r\nif [ $? = 0 ]\r\nthen NOISNAN=\r\nelse NOISNAN=-DNOISNAN\r\nfi\r\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\r\n\r\ndef=\r\ndl=-ldld\r\nso=y\r\n\r\nopts='-O3'\r\n\r\n$c -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\r\nar rv bin/$PLATFORM/liblpsolve55.a `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'`\r\nranlib bin/$PLATFORM/liblpsolve55.a\r\n\r\nif [ \"$so\" != \"\" ]\r\nthen\r\n  $c -O +Z -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I. $opts $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\r\n  ld -b -o bin/$PLATFORM/liblpsolve55.sl *.o\r\nfi\r\n\r\nrm *.o 2>/dev/null\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/ccc.osx",
    "content": ":\nsrc='../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\n#c=cc\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'int main(){printf(\"osx%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c -arch i386 /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'int main(){isnan(0.0);}'>>/tmp/isnan.c\n$c -arch i386 /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\ndef=\ndl=-ldl\nso=y\n\nopts='-idirafter /usr/include/sys -O3 -DINTEGERTIME'\n\n$c -arch i386 -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\nlibtool -static -o bin/$PLATFORM/liblpsolve55.a `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'`\n\nif [ \"$so\" != \"\" ]\nthen\n  $c -arch i386 -fPIC -fno-common -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I. $opts $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\n  $c -arch i386 -dynamiclib bin/$PLATFORM/liblpsolve55.a -compatibility_version 5.5.0 -current_version 5.5.0 -Wl,-install_name,@rpath/liblpsolve55.dylib -o bin/$PLATFORM/liblpsolve55.dylib `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'` -lc\n  mv bin/$PLATFORM/liblpsolve55.dylib ../../../lib\nfi\n\nrm *.o 2>/dev/null\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/ccc.osx64",
    "content": ":\nsrc='../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\n#c=gcc-4.0\n\nif [ \"$ARCH\" = \"x86_64\" ]; then\n\tCFLAGS=\"-arch x86_64\"\nfi\nif [ \"$ARCH\" = \"arm64\" ]; then\n\tCFLAGS=\"-arch arm64\"\nfi\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'int main(){printf(\"osx%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c $CFLAGS /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'int main(){isnan(0.0);}'>>/tmp/isnan.c\n$c $CFLAGS /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\ndef=\ndl=-ldl\nso=y\n\nopts='-idirafter /usr/include/sys -O3 -DINTEGERTIME'\n\n$c $CFLAGS -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\nlibtool -static -o bin/$PLATFORM/liblpsolve55.a `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'`\n\nif [ \"$so\" != \"\" ]\nthen\n  $c $CFLAGS -fPIC -fno-common -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I. $opts $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\n  $c $CFLAGS -dynamiclib bin/$PLATFORM/liblpsolve55.a -compatibility_version 5.5.0 -current_version 5.5.0 -Wl,-install_name,@rpath/liblpsolve55.dylib -o bin/$PLATFORM/liblpsolve55.dylib `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'` -lc\n  mv bin/$PLATFORM/liblpsolve55.dylib ../../../lib\nfi\n\nrm *.o 2>/dev/null\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/ccc.solaris",
    "content": ":\nsrc='../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c'\n#c=cc\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'int main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'int main(){isnan(0.0);}'>>/tmp/isnan.c\n$c /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\ndef=\ndl=-ldl\nso=y\n\nopts='-O3'\n\n$c -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\nar rv bin/$PLATFORM/liblpsolve55.a `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'`\nranlib bin/$PLATFORM/liblpsolve55.a\n\nif [ \"$so\" != \"\" ]\nthen\n  $c -fpic -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I. $opts $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\n  $c -G -R,-Bsymbolic -Wl,-h,liblpsolve55.so -o bin/$PLATFORM/liblpsolve55.so `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'` -lc -lm -ldl\nfi\n\nrm *.o 2>/dev/null\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/cccLUSOL.osx",
    "content": "src='../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../fortify.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c ../bfp/bfp_LUSOL/lusol.c'\nc=cc\n\n#determine platform (32/64 bit)\n>/tmp/platform.c\necho '#include <stdlib.h>'>>/tmp/platform.c\necho '#include <stdio.h>'>>/tmp/platform.c\necho 'int main(){printf(\"ux%d\", (int) (sizeof(void *)*8));}'>>/tmp/platform.c\n$c /tmp/platform.c -o /tmp/platform\nPLATFORM=`/tmp/platform`\nrm /tmp/platform /tmp/platform.c >/dev/null 2>&1\n\nmkdir bin bin/$PLATFORM >/dev/null 2>&1\n\n#check if this system has the isnan function\n>/tmp/isnan.c\necho '#include <stdio.h>'>>/tmp/isnan.c\necho '#include <stdlib.h>'>>/tmp/isnan.c\necho '#include <math.h>'>>/tmp/isnan.c\necho 'int main(){isnan(0.0);}'>>/tmp/isnan.c\n$c /tmp/isnan.c -o /tmp/isnan $math >/dev/null 2>&1\nif [ $? = 0 ]\nthen NOISNAN=\nelse NOISNAN=-DNOISNAN\nfi\nrm /tmp/isnan.c /tmp/isnan >/dev/null 2>&1\n\ndef=\nso=\ndl=-ldl\nso=y\n\nopts='-idirafter /usr/include/sys -O3 -DINTEGERTIME -Wno-long-double'\n\n$c -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd $opts $def $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\nlibtool -static -o bin/$PLATFORM/liblpsolve55.a `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'`\n\nif [ \"$so\" != \"\" ]\nthen\n  $c -fPIC -fno-common -s -c -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -I. $opts $NOISNAN -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine $src\n  $c -dynamiclib bin/$PLATFORM/liblpsolve55.a -compatibility_version 5.5.0 -current_version 5.5.0 -o bin/$PLATFORM/liblpsolve55.dylib `echo $src|sed s/[.]c/.o/g|sed 's/[^ ]*\\///g'` -lc\nfi\n\nrm *.o 2>/dev/null\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/cg++.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lpsolve libraries with the GNU gcc compiler under Windows\r\n\r\nset c=g++\r\n\r\nset PLATFORM=win32\r\n\r\nset src=../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nrem rc lpsolve.rc\r\n%c% -DINLINE=static -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -s -O3 -shared -mno-cygwin -enable-stdcall-fixup -D_USRDLL -DWIN32 -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src% ..\\lp_solve.def -o bin\\%PLATFORM%\\lpsolve55.dll\r\n\r\n%c% -DINLINE=static -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -s -O3 -shared -D_USRDLL -DWIN32 -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src% -o bin\\%PLATFORM%\\liblpsolve55.so\r\n\r\nif exist *.o del *.o\r\n%c% -DINLINE=static -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -s -O3 -c -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src%\r\nar rv bin\\%PLATFORM%\\liblpsolve55.a *.o\r\n\r\nif exist *.o del *.o\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/cgcc.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lpsolve libraries with the GNU gcc compiler under Windows\r\n\r\nset c=gcc\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% platform.c -o platform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nset src=../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c\r\n\r\nrem rc lpsolve.rc\r\n%c% -DINLINE=static -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -s -O3 -shared -mno-cygwin -enable-stdcall-fixup -D_USRDLL -DWIN32 -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src% ..\\lp_solve.def -o bin\\%PLATFORM%\\lpsolve55.dll\r\n\r\n%c% -DINLINE=static -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -s -O3 -shared -D_USRDLL -DWIN32 -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src% -o bin\\%PLATFORM%\\liblpsolve55.so\r\n\r\nif exist *.o del *.o\r\n%c% -DINLINE=static -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd -s -O3 -c -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src%\r\nar rv bin\\%PLATFORM%\\liblpsolve55.a *.o\r\n\r\nif exist *.o del *.o\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/cvc6.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lpsolve libraries with the Microsoft Visual C/C++ compiler under Windows\r\n\r\nset c=cl\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% /nologo platform.c /Feplatform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif \"%PLATFORM%\" == \"win32\" goto ok1\r\necho.\r\necho This batch file is intended for 32 bit compilation with MS Visual C 6\r\necho For newer versions use cvc8*.bat\r\ngoto done\r\n:ok1\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nset src=../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c\r\n\r\nrc lpsolve.rc\r\n%c% -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /LD /MD /O2 /Zp8 /Gz -D\"LP_MAXLINELEN=0\" -D_WINDLL -D_USRDLL -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src% lpsolve.res ..\\lp_solve.def -o bin\\%PLATFORM%\\lpsolve55.dll\r\nrem /link /LINK50COMPAT\r\n\r\nif exist *.obj del *.obj\r\n%c% -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /MT /O2 /Zp8 /Gd /c -D\"LP_MAXLINELEN=0\" -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src%\r\nlib *.obj /OUT:bin\\%PLATFORM%\\liblpsolve55.lib\r\n\r\nif exist *.obj del *.obj\r\n%c% -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /MTd /O2 /Zp8 /Gd /c -D\"LP_MAXLINELEN=0\" -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src%\r\nlib *.obj /OUT:bin\\%PLATFORM%\\liblpsolve55d.lib\r\n\r\nif exist *.obj del *.obj\r\n:done\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/cvc8NOmsvcrt.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lpsolve libraries with the Microsoft Visual C/C++ compiler under Windows\r\n\r\nset c=cl\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% /nologo platform.c /Feplatform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nset src=../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c\r\n\r\nrc lpsolve.rc\r\nrem use /MT to remove dependence on msvcrt*.dll calls kernel libs directly about 200K larger dll.\r\n%c% -W1 -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /LD /MT /O2 /Zp8 /Gz -D_WINDLL -D_USRDLL -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src% lpsolve.res /Febin\\%PLATFORM%\\lpsolve55.dll\r\neditbin /LARGEADDRESSAWARE bin\\%PLATFORM%\\lpsolve55.dll\r\n\r\nrem http://msdn2.microsoft.com/en-us/library/ms235229.aspx\r\nrem for vs2005 need to embed manifest in dll with manifest tool - #2 on the next line does this.\r\nrem mt /outputresource:\"bin\\%PLATFORM%\\lpsolve55.dll;#2\" /manifest \"bin\\%PLATFORM%\\lpsolve55.dll.manifest\"\r\nrem pause\r\n\r\nif exist *.obj del *.obj\r\n%c% -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /MT /O2 /Zp8 /Gd /c -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src%\r\nlib *.obj /OUT:bin\\%PLATFORM%\\liblpsolve55.lib\r\n\r\nif exist *.obj del *.obj\r\n%c% -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /MTd /Od /Zp8 /Gd /RTC1 /c -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src%\r\nlib *.obj /OUT:bin\\%PLATFORM%\\liblpsolve55d.lib\r\n\r\nif exist *.obj del *.obj\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/cvc8msvcrt.bat",
    "content": "@echo off\r\n\r\nREM This batch file compiles the lpsolve libraries with the Microsoft Visual C/C++ compiler under Windows\r\n\r\nREM Microsoft Visual C++ 2005 or 2008 Redistributable Package must be installed at the client for this to work:\r\n\r\nREM 32-bit:\r\nREM http://www.microsoft.com/downloads/details.aspx?FamilyId=32BC1BEE-A3F9-4C13-9C99-220B62A191EE&displaylang=en\r\nREM http://www.microsoft.com/downloads/details.aspx?familyid=9B2DA534-3E03-4391-8A4D-074B9F2BC1BF&displaylang=en\r\nREM http://www.microsoft.com/downloads/details.aspx?familyid=A5C84275-3B97-4AB7-A40D-3802B2AF5FC2&displaylang=en\r\n\r\nREM 64-bit:\r\nREM http://www.microsoft.com/downloads/details.aspx?familyid=BA9257CA-337F-4B40-8C14-157CFDFFEE4E&displaylang=en\r\n\r\nREM See also\r\nREM http://channel9.msdn.com/ShowPost.aspx?PostID=23261\r\nREM http://msdn2.microsoft.com/en-us/library/ms235291.aspx  (How to: Deploy using XCopy)\r\nREM http://msdn2.microsoft.com/en-us/library/ms235299.aspx  (Redistributing Visual C++ Files)\r\n\r\nset c=cl\r\n\r\nREM determine platform (win32/win64)\r\necho main(){printf(\"SET PLATFORM=win%%d\\n\", (int) (sizeof(void *)*8));}>platform.c\r\n%c% /nologo platform.c /Feplatform.exe\r\ndel platform.c\r\nplatform.exe >platform.bat\r\ndel platform.exe\r\ncall platform.bat\r\ndel platform.bat\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nset src=../lp_MDO.c ../shared/commonlib.c ../shared/mmio.c ../shared/myblas.c ../ini.c ../colamd/colamd.c ../lp_rlp.c ../lp_crash.c ../bfp/bfp_LUSOL/lp_LUSOL.c ../bfp/bfp_LUSOL/LUSOL/lusol.c ../lp_Hash.c ../lp_lib.c ../lp_wlp.c ../lp_matrix.c ../lp_mipbb.c ../lp_MPS.c ../lp_params.c ../lp_presolve.c ../lp_price.c ../lp_pricePSE.c ../lp_report.c ../lp_scale.c ../lp_simplex.c ../lp_SOS.c ../lp_utils.c ../yacc_read.c\r\n\r\nif not exist bin\\%PLATFORM%\\*.* md bin\\%PLATFORM%\r\n\r\nrc lpsolve.rc\r\n%c% -W1 -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /LD /MD /O2 /Zp8 /Gz -D_WINDLL -D_USRDLL -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src% lpsolve.res /Febin\\%PLATFORM%\\lpsolve55.dll\r\neditbin /LARGEADDRESSAWARE bin\\%PLATFORM%\\lpsolve55.dll\r\n\r\nrem http://msdn2.microsoft.com/en-us/library/ms235229.aspx\r\nrem for vs2005 need to embed manifest in dll with manifest tool - #2 on the next line does this.\r\nmt /outputresource:\"bin\\%PLATFORM%\\lpsolve55.dll;#2\" /manifest \"bin\\%PLATFORM%\\lpsolve55.dll.manifest\"\r\nrem pause\r\n\r\nif exist *.obj del *.obj\r\n%c% -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /MT /O2 /Zp8 /Gd /c -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src%\r\nlib *.obj /OUT:bin\\%PLATFORM%\\liblpsolve55.lib\r\n\r\nif exist *.obj del *.obj\r\n%c% -I.. -I../shared -I../bfp -I../bfp/bfp_LUSOL -I../bfp/bfp_LUSOL/LUSOL -I../colamd /MTd /Od /Zp8 /Gd /RTC1 /c -DWIN32 -D_CRT_SECURE_NO_DEPRECATE -D_CRT_NONSTDC_NO_DEPRECATE -DYY_NEVER_INTERACTIVE -DPARSER_LP -DINVERSE_ACTIVE=INVERSE_LUSOL -DRoleIsExternalInvEngine %src%\r\nlib *.obj /OUT:bin\\%PLATFORM%\\liblpsolve55d.lib\r\n\r\nif exist *.obj del *.obj\r\nset PLATFORM=\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/dll.sln",
    "content": "Microsoft Visual Studio Solution File, Format Version 10.00\r\n# Visual Studio 2008\r\nProject(\"{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}\") = \"lpsolve55\", \"dll.vcproj\", \"{C97E3E84-BCC5-4CCB-9675-5833C056E702}\"\r\nEndProject\r\nGlobal\r\n\tGlobalSection(SolutionConfigurationPlatforms) = preSolution\r\n\t\tDebug fortify|Win32 = Debug fortify|Win32\r\n\t\tDebug fortify|x64 = Debug fortify|x64\r\n\t\tDebug|Win32 = Debug|Win32\r\n\t\tDebug|x64 = Debug|x64\r\n\t\tRelease|Win32 = Release|Win32\r\n\t\tRelease|x64 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(ProjectConfigurationPlatforms) = postSolution\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Debug fortify|Win32.ActiveCfg = Debug fortify|Win32\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Debug fortify|Win32.Build.0 = Debug fortify|Win32\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Debug fortify|x64.ActiveCfg = Debug fortify|x64\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Debug fortify|x64.Build.0 = Debug fortify|x64\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Debug|Win32.ActiveCfg = Debug|Win32\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Debug|Win32.Build.0 = Debug|Win32\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Debug|x64.ActiveCfg = Debug|x64\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Debug|x64.Build.0 = Debug|x64\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Release|Win32.ActiveCfg = Release|Win32\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Release|Win32.Build.0 = Release|Win32\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Release|x64.ActiveCfg = Release|x64\r\n\t\t{C97E3E84-BCC5-4CCB-9675-5833C056E702}.Release|x64.Build.0 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(SolutionProperties) = preSolution\r\n\t\tHideSolutionNode = FALSE\r\n\tEndGlobalSection\r\nEndGlobal\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/dll.vcproj",
    "content": "<?xml version=\"1.0\" encoding=\"Windows-1252\"?>\r\n<VisualStudioProject\r\n\tProjectType=\"Visual C++\"\r\n\tVersion=\"9.00\"\r\n\tName=\"lpsolve55\"\r\n\tProjectGUID=\"{C97E3E84-BCC5-4CCB-9675-5833C056E702}\"\r\n\tRootNamespace=\"lpsolve55\"\r\n\tTargetFrameworkVersion=\"131072\"\r\n\t>\r\n\t<Platforms>\r\n\t\t<Platform\r\n\t\t\tName=\"Win32\"\r\n\t\t/>\r\n\t\t<Platform\r\n\t\t\tName=\"x64\"\r\n\t\t/>\r\n\t</Platforms>\r\n\t<ToolFiles>\r\n\t</ToolFiles>\r\n\t<Configurations>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug fortify|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"2\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"1\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\dll.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"FORTIFY;_DEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;_USRDLL;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tRuntimeLibrary=\"3\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\dll.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"4\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"c:\\Program Files\\Microsoft Visual Studio\\VC98\\mfc\\include\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve55.dll\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tModuleDefinitionFile=\"..\\lp_solve.def\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.pdb\"\r\n\t\t\t\tSubSystem=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tImportLibrary=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.lib\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"2\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"1\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\dll.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;_USRDLL;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE;FORTIFY\"\r\n\t\t\t\tRuntimeLibrary=\"3\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\dll.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"4\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"c:\\Program Files\\Microsoft Visual Studio\\VC98\\mfc\\include\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve55.dll\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tModuleDefinitionFile=\"..\\lp_solve.def\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.pdb\"\r\n\t\t\t\tSubSystem=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tImportLibrary=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.lib\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"2\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"1\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\dll.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tInlineFunctionExpansion=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;_USRDLL;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"false\"\r\n\t\t\t\tExceptionHandling=\"0\"\r\n\t\t\t\tRuntimeLibrary=\"2\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tBufferSecurityCheck=\"false\"\r\n\t\t\t\tEnableFunctionLevelLinking=\"false\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\dll.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tCallingConvention=\"2\"\r\n\t\t\t\tCompileAs=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve55.dll\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tModuleDefinitionFile=\"..\\lp_solve.def\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.pdb\"\r\n\t\t\t\tSubSystem=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tImportLibrary=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.lib\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug fortify|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"2\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\dll.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"FORTIFY;_DEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;_USRDLL;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tRuntimeLibrary=\"3\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\dll.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"c:\\Program Files\\Microsoft Visual Studio\\VC98\\mfc\\include\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve55.dll\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tModuleDefinitionFile=\"..\\lp_solve.def\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.pdb\"\r\n\t\t\t\tSubSystem=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tImportLibrary=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.lib\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"2\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\dll.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;_USRDLL;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE;FORTIFY\"\r\n\t\t\t\tRuntimeLibrary=\"3\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\dll.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"c:\\Program Files\\Microsoft Visual Studio\\VC98\\mfc\\include\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve55.dll\"\r\n\t\t\t\tLinkIncremental=\"2\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tModuleDefinitionFile=\"..\\lp_solve.def\"\r\n\t\t\t\tGenerateDebugInformation=\"true\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.pdb\"\r\n\t\t\t\tSubSystem=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tImportLibrary=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.lib\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"2\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\dll.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tInlineFunctionExpansion=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;_USRDLL;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"false\"\r\n\t\t\t\tExceptionHandling=\"0\"\r\n\t\t\t\tRuntimeLibrary=\"2\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tBufferSecurityCheck=\"false\"\r\n\t\t\t\tEnableFunctionLevelLinking=\"false\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\dll.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tCallingConvention=\"2\"\r\n\t\t\t\tCompileAs=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLinkerTool\"\r\n\t\t\t\tAdditionalDependencies=\"odbc32.lib odbccp32.lib\"\r\n\t\t\t\tOutputFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve55.dll\"\r\n\t\t\t\tLinkIncremental=\"1\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tModuleDefinitionFile=\"..\\lp_solve.def\"\r\n\t\t\t\tProgramDatabaseFile=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.pdb\"\r\n\t\t\t\tSubSystem=\"2\"\r\n\t\t\t\tRandomizedBaseAddress=\"1\"\r\n\t\t\t\tDataExecutionPrevention=\"0\"\r\n\t\t\t\tImportLibrary=\"$(PlatformName)\\$(ConfigurationName)\\lpsolve.lib\"\r\n\t\t\t\tTargetMachine=\"17\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManifestTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCAppVerifierTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t</Configurations>\r\n\t<References>\r\n\t</References>\r\n\t<Files>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\Bfp\\Bfp_lusol\\bfp_LUSOL.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\colamd\\colamd.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\shared\\commonlib.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\fortify.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\ini.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_crash.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_Hash.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_lib.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\Bfp\\Bfp_lusol\\lp_LUSOL.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_matrix.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_MDO.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_mipbb.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_MPS.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_params.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_presolve.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_price.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_pricePSE.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_report.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_rlp.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_scale.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_simplex.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_SOS.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_utils.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_wlp.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"lpsolve.rc\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\Bfp\\Bfp_lusol\\Lusol\\lusol.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\Shared\\mmio.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\shared\\myblas.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\yacc_read.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t</Files>\r\n\t<Globals>\r\n\t</Globals>\r\n</VisualStudioProject>\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/lib.sln",
    "content": "Microsoft Visual Studio Solution File, Format Version 10.00\r\n# Visual Studio 2008\r\nProject(\"{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}\") = \"liblpsolve55\", \"lib.vcproj\", \"{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}\"\r\nEndProject\r\nGlobal\r\n\tGlobalSection(SolutionConfigurationPlatforms) = preSolution\r\n\t\tDebug fortify|Win32 = Debug fortify|Win32\r\n\t\tDebug fortify|x64 = Debug fortify|x64\r\n\t\tDebug|Win32 = Debug|Win32\r\n\t\tDebug|x64 = Debug|x64\r\n\t\tRelease|Win32 = Release|Win32\r\n\t\tRelease|x64 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(ProjectConfigurationPlatforms) = postSolution\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Debug fortify|Win32.ActiveCfg = Debug fortify|Win32\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Debug fortify|Win32.Build.0 = Debug fortify|Win32\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Debug fortify|x64.ActiveCfg = Debug fortify|x64\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Debug fortify|x64.Build.0 = Debug fortify|x64\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Debug|Win32.ActiveCfg = Debug|Win32\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Debug|Win32.Build.0 = Debug|Win32\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Debug|x64.ActiveCfg = Debug|x64\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Debug|x64.Build.0 = Debug|x64\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Release|Win32.ActiveCfg = Release|Win32\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Release|Win32.Build.0 = Release|Win32\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Release|x64.ActiveCfg = Release|x64\r\n\t\t{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}.Release|x64.Build.0 = Release|x64\r\n\tEndGlobalSection\r\n\tGlobalSection(SolutionProperties) = preSolution\r\n\t\tHideSolutionNode = FALSE\r\n\tEndGlobalSection\r\nEndGlobal\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/lib.vcproj",
    "content": "<?xml version=\"1.0\" encoding=\"Windows-1252\"?>\r\n<VisualStudioProject\r\n\tProjectType=\"Visual C++\"\r\n\tVersion=\"9.00\"\r\n\tName=\"liblpsolve55\"\r\n\tProjectGUID=\"{AEDD8A5B-DFA6-4995-9E9E-EB381C34CEAF}\"\r\n\tTargetFrameworkVersion=\"131072\"\r\n\t>\r\n\t<Platforms>\r\n\t\t<Platform\r\n\t\t\tName=\"Win32\"\r\n\t\t/>\r\n\t\t<Platform\r\n\t\t\tName=\"x64\"\r\n\t\t/>\r\n\t</Platforms>\r\n\t<ToolFiles>\r\n\t</ToolFiles>\r\n\t<Configurations>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug fortify|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"4\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"1\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\lib.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG;FORTIFY;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;MYBOOL=unsigned short;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\lib.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"4\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLibrarianTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"4\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"1\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\lib.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\lib.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"4\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLibrarianTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|Win32\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"4\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"1\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\lib.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tInlineFunctionExpansion=\"1\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tEnableFunctionLevelLinking=\"true\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\lib.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLibrarianTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug fortify|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"4\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\lib.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG;FORTIFY;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;MYBOOL=unsigned short;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\lib.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCompileAs=\"1\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLibrarianTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Debug|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"4\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\lib.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tOptimization=\"0\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tRuntimeLibrary=\"1\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\lib.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tDebugInformationFormat=\"3\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"_DEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLibrarianTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t\t<Configuration\r\n\t\t\tName=\"Release|x64\"\r\n\t\t\tOutputDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tIntermediateDirectory=\"$(PlatformName)\\$(ConfigurationName)\"\r\n\t\t\tConfigurationType=\"4\"\r\n\t\t\tInheritedPropertySheets=\"$(VCInstallDir)VCProjectDefaults\\UpgradeFromVC71.vsprops\"\r\n\t\t\tUseOfMFC=\"0\"\r\n\t\t\tATLMinimizesCRunTimeLibraryUsage=\"false\"\r\n\t\t\t>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreBuildEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCustomBuildTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXMLDataGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCWebServiceProxyGeneratorTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCMIDLTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tMkTypLibCompatible=\"true\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tTargetEnvironment=\"3\"\r\n\t\t\t\tTypeLibraryName=\"$(PlatformName)\\$(ConfigurationName)\\lib.tlb\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCCLCompilerTool\"\r\n\t\t\t\tInlineFunctionExpansion=\"1\"\r\n\t\t\t\tAdditionalIncludeDirectories=\"..;..\\bfp;..\\bfp\\bfp_LUSOL;..\\bfp\\bfp_LUSOL\\LUSOL;..\\colamd;..\\shared\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG;WIN32;_WINDOWS;MSDOS;CHECK_SOLUTION;YY_NEVER_INTERACTIVE;PARSER_LP;INVERSE_ACTIVE=INVERSE_LUSOL;RoleIsExternalInvEngine,_CRT_SECURE_NO_DEPRECATE,_CRT_NONSTDC_NO_DEPRECATE,_SCL_SECURE_NO_DEPRECATE\"\r\n\t\t\t\tStringPooling=\"true\"\r\n\t\t\t\tRuntimeLibrary=\"0\"\r\n\t\t\t\tStructMemberAlignment=\"4\"\r\n\t\t\t\tEnableFunctionLevelLinking=\"true\"\r\n\t\t\t\tUsePrecompiledHeader=\"0\"\r\n\t\t\t\tPrecompiledHeaderFile=\"$(PlatformName)\\$(ConfigurationName)\\lib.pch\"\r\n\t\t\t\tAssemblerListingLocation=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tObjectFile=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tProgramDataBaseFileName=\"$(PlatformName)\\$(ConfigurationName)\\\"\r\n\t\t\t\tWarningLevel=\"3\"\r\n\t\t\t\tSuppressStartupBanner=\"true\"\r\n\t\t\t\tCallingConvention=\"0\"\r\n\t\t\t\tCompileAs=\"0\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCManagedResourceCompilerTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCResourceCompilerTool\"\r\n\t\t\t\tPreprocessorDefinitions=\"NDEBUG\"\r\n\t\t\t\tCulture=\"2067\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPreLinkEventTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCLibrarianTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCALinkTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCXDCMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCBscMakeTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCFxCopTool\"\r\n\t\t\t/>\r\n\t\t\t<Tool\r\n\t\t\t\tName=\"VCPostBuildEventTool\"\r\n\t\t\t/>\r\n\t\t</Configuration>\r\n\t</Configurations>\r\n\t<References>\r\n\t</References>\r\n\t<Files>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\Bfp\\Bfp_lusol\\bfp_LUSOL.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\colamd\\colamd.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\shared\\commonlib.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\fortify.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\ini.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_crash.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_Hash.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_lib.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\Bfp\\Bfp_lusol\\lp_LUSOL.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_matrix.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_MDO.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_mipbb.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_MPS.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_params.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_presolve.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_price.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_pricePSE.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_report.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_rlp.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_scale.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_simplex.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_SOS.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_utils.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\lp_wlp.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\Bfp\\Bfp_lusol\\Lusol\\lusol.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\Shared\\mmio.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\shared\\myblas.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t\t<File\r\n\t\t\tRelativePath=\"..\\yacc_read.c\"\r\n\t\t\t>\r\n\t\t</File>\r\n\t</Files>\r\n\t<Globals>\r\n\t</Globals>\r\n</VisualStudioProject>\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/lpsolve.rc",
    "content": "// Microsoft Visual C++ generated resource script.\r\n//\r\n#include \"resource.h\"\r\n\r\n#define APSTUDIO_READONLY_SYMBOLS\r\n/////////////////////////////////////////////////////////////////////////////\r\n//\r\n// Generated from the TEXTINCLUDE 2 resource.\r\n//\r\n#include \"afxres.h\"\r\n\r\n/////////////////////////////////////////////////////////////////////////////\r\n#undef APSTUDIO_READONLY_SYMBOLS\r\n\r\n/////////////////////////////////////////////////////////////////////////////\r\n// Dutch (Belgium) resources\r\n\r\n#if !defined(AFX_RESOURCE_DLL) || defined(AFX_TARG_NLB)\r\n#ifdef _WIN32\r\nLANGUAGE LANG_DUTCH, SUBLANG_DUTCH_BELGIAN\r\n#pragma code_page(1252)\r\n#endif //_WIN32\r\n\r\n/////////////////////////////////////////////////////////////////////////////\r\n//\r\n// Version\r\n//\r\n\r\nVS_VERSION_INFO VERSIONINFO\r\n FILEVERSION 5,5,2,0\r\n PRODUCTVERSION 5,5,2,0\r\n FILEFLAGSMASK 0x3fL\r\n#ifdef _DEBUG\r\n FILEFLAGS 0x1L\r\n#else\r\n FILEFLAGS 0x0L\r\n#endif\r\n FILEOS 0x40004L\r\n FILETYPE 0x2L\r\n FILESUBTYPE 0x0L\r\nBEGIN\r\n    BLOCK \"StringFileInfo\"\r\n    BEGIN\r\n        BLOCK \"040904b0\"\r\n        BEGIN\r\n            VALUE \"Comments\", \"Mixed Integer Lineair Program Solver\"\r\n            VALUE \"CompanyName\", \"Free Software Foundation, Inc.\"\r\n            VALUE \"FileDescription\", \"lpsolve\"\r\n            VALUE \"FileVersion\", \"5, 5, 2, 0\"\r\n            VALUE \"InternalName\", \"lpsolve\"\r\n            VALUE \"LegalCopyright\", \"Copyright  1991, 2010 Free Software Foundation, Inc.\"\r\n            VALUE \"OriginalFilename\", \"lpsolve55.dll\"\r\n            VALUE \"ProductName\", \"lpsolve\"\r\n            VALUE \"ProductVersion\", \"5, 5, 2, 0\"\r\n        END\r\n    END\r\n    BLOCK \"VarFileInfo\"\r\n    BEGIN\r\n        VALUE \"Translation\", 0x409, 1200\r\n    END\r\nEND\r\n\r\n\r\n#ifdef APSTUDIO_INVOKED\r\n/////////////////////////////////////////////////////////////////////////////\r\n//\r\n// TEXTINCLUDE\r\n//\r\n\r\n1 TEXTINCLUDE\r\nBEGIN\r\n    \"resource.h\\0\"\r\nEND\r\n\r\n2 TEXTINCLUDE\r\nBEGIN\r\n    \"#include \"\"afxres.h\"\"\\r\\n\"\r\n    \"\\0\"\r\nEND\r\n\r\n3 TEXTINCLUDE\r\nBEGIN\r\n    \"\\r\\n\"\r\n    \"\\0\"\r\nEND\r\n\r\n#endif    // APSTUDIO_INVOKED\r\n\r\n#endif    // Dutch (Belgium) resources\r\n/////////////////////////////////////////////////////////////////////////////\r\n\r\n\r\n\r\n#ifndef APSTUDIO_INVOKED\r\n/////////////////////////////////////////////////////////////////////////////\r\n//\r\n// Generated from the TEXTINCLUDE 3 resource.\r\n//\r\n\r\n\r\n/////////////////////////////////////////////////////////////////////////////\r\n#endif    // not APSTUDIO_INVOKED\r\n\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/readme.txt",
    "content": "This directory contains the files to build the Windows lpsolve55.dll dll / /linux/Unix lpsolve55.a library\r\n\r\nTo build the program under Windows with the Visual C/C++ compiler, use cvc6.bat (also works for VS.NET)\r\nTo build the program under DOS/Windows with the gcc compiler, use cgcc.bat\r\nTo build the program under Linux/Unix, use sh ccc\r\nTo build the program under Mac OS X 10.3.5, use sh ccc.osx\r\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/lpsolve55/resource.h",
    "content": "//{{NO_DEPENDENCIES}}\n// Microsoft Developer Studio generated include file.\n// Used by lpsolve.rc\n//\n\n// Next default values for new objects\n// \n#ifdef APSTUDIO_INVOKED\n#ifndef APSTUDIO_READONLY_SYMBOLS\n#define _APS_NEXT_RESOURCE_VALUE        101\n#define _APS_NEXT_COMMAND_VALUE         40001\n#define _APS_NEXT_CONTROL_VALUE         1000\n#define _APS_NEXT_SYMED_VALUE           101\n#endif\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/shared/commonlib.c",
    "content": "\n#include <sys/types.h>\n\n#if defined INTEGERTIME || defined CLOCKTIME || defined PosixTime\n# include <time.h>\n#elif defined EnhTime\n# include <windows.h>\n#else\n# include <sys/timeb.h>\n#endif\n\n#include <stdlib.h>\n#include <stdio.h>\n#ifdef WIN32\n# include <io.h>       /* Used in file search functions */\n#endif\n#include <ctype.h>\n#include <string.h>\n#include <float.h>\n#include <math.h>\n#include \"commonlib.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n#if defined FPUexception\n/* FPU exception masks */\nunsigned int clearFPU()\n{\n  return( _clearfp() );\n}\nunsigned int resetFPU(unsigned int mask)\n{\n  _clearfp();\n  mask = _controlfp( mask, 0xfffff);\n  return( mask );\n}\nunsigned int catchFPU(unsigned int mask)\n{\n  /* Always call _clearfp before enabling/unmasking a FPU exception */\n  unsigned int u = _clearfp();\n\n  /* Set the new mask by not-and'ing it with the previous settings */\n  u = _controlfp(0, 0);\n  mask = u & ~mask;\n  mask = _controlfp(mask, _MCW_EM);\n\n  /* Return the previous mask */\n  return( u );\n}\n#endif\n\n/* Math operator equivalence function */\nint intpow(int base, int exponent)\n{\n  int result = 1;\n  while(exponent > 0) {\n    result *= base;\n    exponent--;\n  }\n  while(exponent < 0) {\n    result /= base;\n    exponent++;\n  }\n  return( result );\n}\nint mod(int n, int d)\n{\n  return(n % d);\n}\n\n/* Some string functions */\nvoid strtoup(char *s)\n{\n  if(s != NULL)\n  while (*s) {\n    *s = toupper(*s);\n    s++;\n  }\n}\nvoid strtolo(char *s)\n{\n  if(s != NULL)\n  while (*s) {\n    *s = tolower(*s);\n    s++;\n  }\n}\nvoid strcpyup(char *t, char *s)\n{\n  if((s != NULL) && (t != NULL)) {\n    while (*s) {\n      *t = toupper(*s);\n      t++;\n      s++;\n    }\n    *t = '\\0';\n  }\n}\nvoid strcpylo(char *t, char *s)\n{\n  if((s != NULL) && (t != NULL)) {\n    while (*s) {\n      *t = tolower(*s);\n      t++;\n      s++;\n    }\n    *t = '\\0';\n  }\n}\n\n/* Unix library naming utility function */\nMYBOOL so_stdname(char *stdname, char *descname, int buflen)\n{\n  char *ptr;\n\n  if((descname == NULL) || (stdname == NULL) || (((int) strlen(descname)) >= buflen - 6))\n    return( FALSE );\n\n  strcpy(stdname, descname);\n  if((ptr = strrchr(descname, '/')) == NULL)\n    ptr = descname;\n  else\n    ptr++;\n  stdname[(int) (ptr - descname)] = 0;\n  if(strncmp(ptr, \"lib\", 3))\n    strcat(stdname, \"lib\");\n  strcat(stdname, ptr);\n  if(strcmp(stdname + strlen(stdname) - 3, \".so\"))\n    strcat(stdname, \".so\");\n  return( TRUE );\n}\n\n/* Return the greatest common divisor of a and b, or -1 if it is\n   not defined. Return through the pointer arguments the integers\n   such that gcd(a,b) = c*a + b*d. */\nint gcd(LLONG a, LLONG b, int *c, int *d)\n{\n  LLONG q,r,t;\n  int   cret,dret,C,D,rval, sgn_a = 1,sgn_b = 1, swap = 0;\n\n  if((a == 0) || (b == 0))\n    return( -1 );\n\n  /* Use local multiplier instances, if necessary */\n  if(c == NULL)\n    c = &cret;\n  if(d == NULL)\n    d = &dret;\n\n  /* Normalize so that 0 < a <= b */\n  if(a < 0){\n    a = -a;\n    sgn_a = -1;\n  }\n  if(b < 0){\n    b = -b;\n    sgn_b = -1;\n  }\n  if(b < a){\n    t = b;\n    b = a;\n    a = t;\n    swap = 1;\n  }\n\n  /* Now a <= b and both >= 1. */\n  q = b/a;\n  r = b - a*q;\n  if(r == 0) {\n    if(swap){\n      *d = 1;\n      *c = 0;\n    }\n    else {\n      *c = 1;\n      *d = 0;\n    }\n    *c = sgn_a*(*c);\n    *d = sgn_b*(*d);\n    return( (int) a );\n  }\n\n  rval = gcd(a,r,&C,&D);\n  if(swap){\n    *d = (int) (C-D*q);\n    *c = D;\n  }\n  else {\n    *d = D;\n    *c = (int) (C-D*q);\n  }\n  *c = sgn_a*(*c);\n  *d = sgn_b*(*d);\n  return( rval );\n}\n\n/* Array search functions */\nint findIndex(int target, int *attributes, int count, int offset)\n{\n  int focusPos, beginPos, endPos;\n  int focusAttrib, beginAttrib, endAttrib;\n\n /* Set starting and ending index offsets */\n  beginPos = offset;\n  endPos = beginPos + count - 1;\n  if(endPos < beginPos)\n    return(-1);\n\n /* Do binary search logic based on a sorted (decending) attribute vector */\n  focusPos = (beginPos + endPos) / 2;\n  beginAttrib = attributes[beginPos];\n  focusAttrib = attributes[focusPos];\n  endAttrib   = attributes[endPos];\n\n  while(endPos - beginPos > LINEARSEARCH) {\n    if(beginAttrib == target) {\n      focusAttrib = beginAttrib;\n      endPos = beginPos;\n    }\n    else if(endAttrib == target) {\n      focusAttrib = endAttrib;\n      beginPos = endPos;\n    }\n    else if(focusAttrib < target) {\n      beginPos = focusPos + 1;\n      beginAttrib = attributes[beginPos];\n      focusPos = (beginPos + endPos) / 2;\n      focusAttrib = attributes[focusPos];\n    }\n    else if(focusAttrib > target) {\n      endPos = focusPos - 1;\n      endAttrib = attributes[endPos];\n      focusPos = (beginPos + endPos) / 2;\n      focusAttrib = attributes[focusPos];\n    }\n    else {\n      beginPos = focusPos;\n      endPos = focusPos;\n    }\n  }\n\n /* Do linear (unsorted) search logic */\n  if(endPos - beginPos <= LINEARSEARCH) {\n\n    /* CPU intensive loop; provide alternative evaluation models */\n#if defined DOFASTMATH\n    /* Do fast pointer arithmetic */\n    int *attptr = attributes + beginPos;\n    while((beginPos < endPos) && ((*attptr) < target)) {\n      beginPos++;\n      attptr++;\n    }\n    focusAttrib = (*attptr);\n#else\n    /* Do traditional indexed access */\n    focusAttrib = attributes[beginPos];\n    while((beginPos < endPos) && (focusAttrib < target)) {\n      beginPos++;\n      focusAttrib = attributes[beginPos];\n    }\n#endif\n  }\n\n /* Return the index if a match was found, or signal failure with a -1        */\n  if(focusAttrib == target)             /* Found; return retrieval index      */\n    return(beginPos);\n  else if(focusAttrib > target)         /* Not found; last item               */\n    return(-beginPos);\n  else if(beginPos > offset+count-1)\n    return(-(endPos+1));                /* Not found; end of list             */\n  else\n    return(-(beginPos+1));              /* Not found; intermediate point      */\n\n}\nint findIndexEx(void *target, void *attributes, int count, int offset, int recsize, findCompare_func findCompare, MYBOOL ascending)\n{\n  int  focusPos, beginPos, endPos, compare, order;\n  void *focusAttrib, *beginAttrib, *endAttrib;\n\n /* Set starting and ending index offsets */\n  beginPos = offset;\n  endPos = beginPos + count - 1;\n  if(endPos < beginPos)\n    return(-1);\n  order = (ascending ? -1 : 1);\n\n /* Do binary search logic based on a sorted attribute vector */\n  focusPos = (beginPos + endPos) / 2;\n  beginAttrib = CMP_ATTRIBUTES(beginPos);\n  focusAttrib = CMP_ATTRIBUTES(focusPos);\n  endAttrib   = CMP_ATTRIBUTES(endPos);\n\n  compare = 0;\n  while(endPos - beginPos > LINEARSEARCH) {\n    if(findCompare(target, beginAttrib) == 0) {\n      focusAttrib = beginAttrib;\n      endPos = beginPos;\n    }\n    else if(findCompare(target, endAttrib) == 0) {\n      focusAttrib = endAttrib;\n      beginPos = endPos;\n    }\n    else {\n      compare = findCompare(target, focusAttrib)*order;\n      if(compare < 0) {\n        beginPos = focusPos + 1;\n        beginAttrib = CMP_ATTRIBUTES(beginPos);\n        focusPos = (beginPos + endPos) / 2;\n        focusAttrib = CMP_ATTRIBUTES(focusPos);\n      }\n      else if(compare > 0) {\n        endPos = focusPos - 1;\n        endAttrib = CMP_ATTRIBUTES(endPos);\n        focusPos = (beginPos + endPos) / 2;\n        focusAttrib = CMP_ATTRIBUTES(focusPos);\n      }\n      else {\n        beginPos = focusPos;\n        endPos = focusPos;\n      }\n    }\n  }\n\n /* Do linear (unsorted) search logic */\n  if(endPos - beginPos <= LINEARSEARCH) {\n\n    /* Do traditional indexed access */\n    focusAttrib = CMP_ATTRIBUTES(beginPos);\n    if(beginPos == endPos)\n      compare = findCompare(target, focusAttrib)*order;\n    else\n    while((beginPos < endPos) &&\n          ((compare = findCompare(target, focusAttrib)*order) < 0)) {\n      beginPos++;\n      focusAttrib = CMP_ATTRIBUTES(beginPos);\n    }\n  }\n\n /* Return the index if a match was found, or signal failure with a -1        */\n  if(compare == 0)                      /* Found; return retrieval index      */\n    return(beginPos);\n  else if(compare > 0)                  /* Not found; last item               */\n    return(-beginPos);\n  else if(beginPos > offset+count-1)\n    return(-(endPos+1));                /* Not found; end of list             */\n  else\n    return(-(beginPos+1));              /* Not found; intermediate point      */\n\n}\n\n/* Simple sorting and searching comparison \"operators\" */\nint CMP_CALLMODEL compareCHAR(const void *current, const void *candidate)\n{\n  return( CMP_COMPARE( *(char *) current, *(char *) candidate ) );\n}\nint CMP_CALLMODEL compareINT(const void *current, const void *candidate)\n{\n  return( CMP_COMPARE( *(int *) current, *(int *) candidate ) );\n}\nint CMP_CALLMODEL compareREAL(const void *current, const void *candidate)\n{\n  return( CMP_COMPARE( *(REAL *) current, *(REAL *) candidate ) );\n}\n\n/* Heap sort function (procedurally based on the Numerical Recipes version,\n   but expanded and generalized to hande any object with the use of\n   qsort-style comparison operator).  An expanded version is also implemented,\n   where interchanges are reflected in a caller-initialized integer \"tags\" list. */\nvoid hpsort(void *attributes, int count, int offset, int recsize, MYBOOL descending, findCompare_func findCompare)\n{\n  register int  i, j, k, ir, order;\n  register char *hold, *base;\n  char          *save;\n\n  if(count < 2)\n    return;\n  offset -= 1;\n  attributes = CMP_ATTRIBUTES(offset);\n  base = CMP_ATTRIBUTES(1);\n  save = (char *) malloc(recsize);\n  if(descending)\n    order = -1;\n  else\n    order = 1;\n\n  k = (count >> 1) + 1;\n  ir = count;\n\n  for(;;) {\n    if(k > 1) {\n      MEMCOPY(save, CMP_ATTRIBUTES(--k), recsize);\n    }\n    else {\n      hold = CMP_ATTRIBUTES(ir);\n      MEMCOPY(save, hold, recsize);\n      MEMCOPY(hold, base, recsize);\n      if(--ir == 1) {\n        MEMCOPY(base, save, recsize);\n        break;\n      }\n    }\n\n    i = k;\n    j = k << 1;\n    while(j <= ir) {\n      hold = CMP_ATTRIBUTES(j);\n      if( (j < ir) && (findCompare(hold, CMP_ATTRIBUTES(j+1))*order < 0) ) {\n        hold += recsize;\n        j++;\n      }\n      if(findCompare(save, hold)*order < 0) {\n        MEMCOPY(CMP_ATTRIBUTES(i), hold, recsize);\n        i = j;\n        j <<= 1;\n\t    }\n      else\n        break;\n    }\n    MEMCOPY(CMP_ATTRIBUTES(i), save, recsize);\n  }\n\n  FREE(save);\n}\nvoid hpsortex(void *attributes, int count, int offset, int recsize, MYBOOL descending, findCompare_func findCompare, int *tags)\n{\n  if(count < 2)\n    return;\n  if(tags == NULL) {\n    hpsort(attributes, count, offset, recsize, descending, findCompare);\n    return;\n  }\n  else {\n    register int  i, j, k, ir, order;\n    register char *hold, *base;\n    char          *save;\n    int           savetag;\n\n    offset -= 1;\n    attributes = CMP_ATTRIBUTES(offset);\n    tags += offset;\n    base = CMP_ATTRIBUTES(1);\n    save = (char *) malloc(recsize);\n    if(descending)\n      order = -1;\n    else\n      order = 1;\n\n    k = (count >> 1) + 1;\n    ir = count;\n\n    for(;;) {\n      if(k > 1) {\n        MEMCOPY(save, CMP_ATTRIBUTES(--k), recsize);\n        savetag = tags[k];\n      }\n      else {\n        hold = CMP_ATTRIBUTES(ir);\n        MEMCOPY(save, hold, recsize);\n        MEMCOPY(hold, base, recsize);\n        savetag = tags[ir];\n        tags[ir] = tags[1];\n        if(--ir == 1) {\n          MEMCOPY(base, save, recsize);\n          tags[1] = savetag;\n          break;\n        }\n      }\n\n      i = k;\n      j = k << 1;\n      while(j <= ir) {\n        hold = CMP_ATTRIBUTES(j);\n        if( (j < ir) && (findCompare(hold, CMP_ATTRIBUTES(j+1))*order < 0) ) {\n          hold += recsize;\n          j++;\n        }\n        if(findCompare(save, hold)*order < 0) {\n          MEMCOPY(CMP_ATTRIBUTES(i), hold, recsize);\n          tags[i] = tags[j];\n          i = j;\n          j <<= 1;\n  \t    }\n        else\n          break;\n      }\n      MEMCOPY(CMP_ATTRIBUTES(i), save, recsize);\n      tags[i] = savetag;\n    }\n\n    FREE(save);\n  }\n}\n\n/* This is a \"specialized generic\" version of C.A.R Hoare's Quick Sort algorithm.\n   It will handle arrays that are already sorted, and arrays with duplicate keys.\n   There are two versions here; one extended conventional with optional tag data\n   for each sortable value, and a version for the QSORTrec format.  The QSORTrec\n   format i.a. includes the ability for to do linked list sorting. If the passed\n   comparison operator is NULL, the comparison is assumed to be for integers. */\n#define QS_IS_switch LINEARSEARCH    /* Threshold for switching to insertion sort */\n\nvoid qsortex_swap(void *attributes, int l, int r, int recsize,\n                         void *tags, int tagsize, char *save, char *savetag)\n{\n   MEMCOPY(save, CMP_ATTRIBUTES(l), recsize);\n   MEMCOPY(CMP_ATTRIBUTES(l), CMP_ATTRIBUTES(r), recsize);\n   MEMCOPY(CMP_ATTRIBUTES(r), save, recsize);\n   if(tags != NULL) {\n     MEMCOPY(savetag, CMP_TAGS(l), tagsize);\n     MEMCOPY(CMP_TAGS(l), CMP_TAGS(r), tagsize);\n     MEMCOPY(CMP_TAGS(r), savetag, tagsize);\n   }\n}\n\nint qsortex_sort(void *attributes, int l, int r, int recsize, int sortorder, findCompare_func findCompare,\n                        void *tags, int tagsize, char *save, char *savetag)\n{\n  register int i, j, nmove = 0;\n  char     *v;\n\n  /* Perform the a fast QuickSort */\n  if((r-l) > QS_IS_switch) {\n    i = (r+l)/2;\n\n    /* Tri-Median Method */\n    if(sortorder*findCompare(CMP_ATTRIBUTES(l), CMP_ATTRIBUTES(i)) > 0)\n      { nmove++; qsortex_swap(attributes, l,i, recsize, tags, tagsize, save, savetag); }\n    if(sortorder*findCompare(CMP_ATTRIBUTES(l), CMP_ATTRIBUTES(r)) > 0)\n      { nmove++; qsortex_swap(attributes, l,r, recsize, tags, tagsize, save, savetag); }\n    if(sortorder*findCompare(CMP_ATTRIBUTES(i), CMP_ATTRIBUTES(r)) > 0)\n      { nmove++; qsortex_swap(attributes, i,r, recsize, tags, tagsize, save, savetag); }\n\n    j = r-1;\n    qsortex_swap(attributes, i,j, recsize, tags, tagsize, save, savetag);\n    i = l;\n    v = CMP_ATTRIBUTES(j);\n    for(;;) {\n      while(sortorder*findCompare(CMP_ATTRIBUTES(++i), v) < 0);\n      while(sortorder*findCompare(CMP_ATTRIBUTES(--j), v) > 0);\n      if(j < i) break;\n      nmove++; qsortex_swap(attributes, i,j, recsize, tags, tagsize, save, savetag);\n    }\n    nmove++; qsortex_swap(attributes, i,r-1, recsize, tags, tagsize, save, savetag);\n    nmove += qsortex_sort(attributes, l,j,   recsize, sortorder, findCompare, tags, tagsize, save, savetag);\n    nmove += qsortex_sort(attributes, i+1,r, recsize, sortorder, findCompare, tags, tagsize, save, savetag);\n  }\n  return( nmove );\n}\n\nint qsortex_finish(void *attributes, int lo0, int hi0, int recsize, int sortorder, findCompare_func findCompare,\n                          void *tags, int tagsize, char *save, char *savetag)\n{\n  int i, j, nmove = 0;\n\n  /* This is actually InsertionSort, which is faster for local sorts */\n  for(i = lo0+1; i <= hi0; i++) {\n\n    /* Save bottom-most item */\n    MEMCOPY(save, CMP_ATTRIBUTES(i), recsize);\n    if(tags != NULL)\n      MEMCOPY(savetag, CMP_TAGS(i), tagsize);\n\n    /* Shift down! */\n    j = i;\n    while ((j > lo0) && (sortorder*findCompare(CMP_ATTRIBUTES(j-1), save) > 0)) {\n      MEMCOPY(CMP_ATTRIBUTES(j), CMP_ATTRIBUTES(j-1), recsize);\n      if(tags != NULL)\n        MEMCOPY(CMP_TAGS(j), CMP_TAGS(j-1), tagsize);\n      j--;\n      nmove++;\n    }\n\n    /* Store bottom-most item at the top */\n    MEMCOPY(CMP_ATTRIBUTES(j), save, recsize);\n    if(tags != NULL)\n      MEMCOPY(CMP_TAGS(j), savetag, tagsize);\n  }\n  return( nmove );\n}\n\nint qsortex(void *attributes, int count, int offset, int recsize, MYBOOL descending, findCompare_func findCompare, void *tags, int tagsize)\n{\n  int  iswaps = 0, sortorder = (descending ? -1 : 1);\n  char *save = NULL, *savetag = NULL;\n\n  /* Check and initialize to zero-based arrays */\n  if(count <= 1)\n    goto Finish;\n  attributes = (void *) CMP_ATTRIBUTES(offset);\n  save = (char *) malloc(recsize);\n  if((tagsize <= 0) && (tags != NULL))\n    tags = NULL;\n  else if(tags != NULL) {\n    tags = (void *) CMP_TAGS(offset);\n    savetag = (char *) malloc(tagsize);\n  }\n  count--;\n\n  /* Perform sort */\n  iswaps = qsortex_sort(attributes, 0, count, recsize, sortorder, findCompare, tags, tagsize, save, savetag);\n#if QS_IS_switch > 0\n  iswaps += qsortex_finish(attributes, 0, count, recsize, sortorder, findCompare, tags, tagsize, save, savetag);\n#endif\n\nFinish:\n  FREE(save);\n  FREE(savetag);\n  return( iswaps );\n}\n\n#undef QS_IS_switch\n\n/* This is a \"specialized generic\" version of C.A.R Hoare's Quick Sort algorithm.\n   It will handle arrays that are already sorted, and arrays with duplicate keys.\n   The implementation here requires the user to pass a comparison operator and\n   assumes that the array passed has the QSORTrec format, which i.a. includes\n   the ability for to do linked list sorting. If the passed comparison operator\n   is NULL, the comparison is assumed to be for integers. */\n#define QS_IS_switch 4    /* Threshold for switching to insertion sort */\n\nvoid QS_swap(UNIONTYPE QSORTrec a[], int i, int j)\n{\n  UNIONTYPE QSORTrec T = a[i];\n  a[i] = a[j];\n  a[j] = T;\n}\nint QS_addfirst(UNIONTYPE QSORTrec a[], void *mydata)\n{\n  a[0].pvoid2.ptr = mydata;\n  return( 0 );\n}\nint QS_append(UNIONTYPE QSORTrec a[], int ipos, void *mydata)\n{\n  if(ipos <= 0)\n    ipos = QS_addfirst(a, mydata);\n  else\n    a[ipos].pvoid2.ptr = mydata;\n  return( ipos );\n}\nvoid QS_replace(UNIONTYPE QSORTrec a[], int ipos, void *mydata)\n{\n  a[ipos].pvoid2.ptr = mydata;\n}\nvoid QS_insert(UNIONTYPE QSORTrec a[], int ipos, void *mydata, int epos)\n{\n  for(; epos > ipos; epos--)\n    a[epos] = a[epos-1];\n  a[ipos].pvoid2.ptr = mydata;\n}\nvoid QS_delete(UNIONTYPE QSORTrec a[], int ipos, int epos)\n{\n  for(; epos > ipos; epos--)\n    a[epos] = a[epos-1];\n}\nint QS_sort(UNIONTYPE QSORTrec a[], int l, int r, findCompare_func findCompare)\n{\n  register int i, j, nmove = 0;\n  UNIONTYPE QSORTrec v;\n\n  /* Perform the a fast QuickSort */\n  if((r-l) > QS_IS_switch) {\n    i = (r+l)/2;\n\n    /* Tri-Median Method */\n    if(findCompare((char *) &a[l], (char *) &a[i]) > 0)\n      { nmove++; QS_swap(a,l,i); }\n    if(findCompare((char *) &a[l], (char *) &a[r]) > 0)\n      { nmove++; QS_swap(a,l,r); }\n    if(findCompare((char *) &a[i], (char *) &a[r]) > 0)\n      { nmove++; QS_swap(a,i,r); }\n\n    j = r-1;\n    QS_swap(a,i,j);\n    i = l;\n    v = a[j];\n    for(;;) {\n      while(findCompare((char *) &a[++i], (char *) &v) < 0);\n      while(findCompare((char *) &a[--j], (char *) &v) > 0);\n      if(j < i) break;\n      nmove++; QS_swap (a,i,j);\n    }\n    nmove++; QS_swap(a,i,r-1);\n    nmove += QS_sort(a,l,j,findCompare);\n    nmove += QS_sort(a,i+1,r,findCompare);\n  }\n  return( nmove );\n}\nint QS_finish(UNIONTYPE QSORTrec a[], int lo0, int hi0, findCompare_func findCompare)\n{\n  int      i, j, nmove = 0;\n  UNIONTYPE QSORTrec v;\n\n  /* This is actually InsertionSort, which is faster for local sorts */\n  for(i = lo0+1; i <= hi0; i++) {\n\n    /* Save bottom-most item */\n    v = a[i];\n\n    /* Shift down! */\n    j = i;\n    while ((j > lo0) && (findCompare((char *) &a[j-1], (char *) &v) > 0)) {\n      a[j] = a[j-1];\n      j--;\n      nmove++;\n    }\n\n    /* Store bottom-most item at the top */\n    a[j] = v;\n  }\n  return( nmove );\n}\nMYBOOL QS_execute(UNIONTYPE QSORTrec a[], int count, findCompare_func findCompare, int *nswaps)\n{\n  int iswaps = 0;\n\n  /* Check and initialize */\n  if(count <= 1)\n    goto Finish;\n  count--;\n\n  /* Perform sort */\n  iswaps = QS_sort(a, 0, count, findCompare);\n#if QS_IS_switch > 0\n  iswaps += QS_finish(a, 0, count, findCompare);\n#endif\n\nFinish:\n  if(nswaps != NULL)\n    *nswaps = iswaps;\n  return( TRUE );\n}\n\n\n\n/* Simple specialized bubble/insertion sort functions */\nint sortByREAL(int *item, REAL *weight, int size, int offset, MYBOOL unique)\n{\n  int i, ii, saveI;\n  REAL saveW;\n\n  for(i = 1; i < size; i++) {\n    ii = i+offset-1;\n    while ((ii >= offset) && (weight[ii] >= weight[ii+1])) {\n      if(weight[ii] == weight[ii+1]) {\n        if(unique)\n          return(item[ii]);\n      }\n      else {\n        saveI = item[ii];\n        saveW = weight[ii];\n        item[ii] = item[ii+1];\n        weight[ii] = weight[ii+1];\n        item[ii+1] = saveI;\n        weight[ii+1] = saveW;\n      }\n      ii--;\n    }\n  }\n  return(0);\n}\nint sortByINT(int *item, int *weight, int size, int offset, MYBOOL unique)\n{\n  int i, ii, saveI;\n  int saveW;\n\n  for(i = 1; i < size; i++) {\n    ii = i+offset-1;\n    while ((ii >= offset) && (weight[ii] >= weight[ii+1])) {\n      if(weight[ii] == weight[ii+1]) {\n        if(unique)\n          return(item[ii]);\n      }\n      else {\n        saveI = item[ii];\n        saveW = weight[ii];\n        item[ii] = item[ii+1];\n        weight[ii] = weight[ii+1];\n        item[ii+1] = saveI;\n        weight[ii+1] = saveW;\n      }\n      ii--;\n    }\n  }\n  return(0);\n}\nREAL sortREALByINT(REAL *item, int *weight, int size, int offset, MYBOOL unique)\n{\n  int  i, ii, saveW;\n  REAL saveI;\n\n  for(i = 1; i < size; i++) {\n    ii = i+offset-1;\n    while ((ii >= offset) && (weight[ii] >= weight[ii+1])) {\n      if(weight[ii] == weight[ii+1]) {\n        if(unique)\n          return(item[ii]);\n      }\n      else {\n        saveI = item[ii];\n        saveW = weight[ii];\n        item[ii] = item[ii+1];\n        weight[ii] = weight[ii+1];\n        item[ii+1] = saveI;\n        weight[ii+1] = saveW;\n      }\n      ii--;\n    }\n  }\n  return(0);\n}\n\n\n/* Time and message functions */\ndouble timeNow(void)\n{\n#ifdef INTEGERTIME\n  return((double)time(NULL));\n#elif defined CLOCKTIME\n  return((double)clock()/CLOCKS_PER_SEC /* CLK_TCK */);\n#elif defined PosixTime\n  struct timespec t;\n# if 0\n  clock_gettime(CLOCK_REALTIME, &t);\n  return( (double) t.tv_sec + (double) t.tv_nsec/1.0e9 );\n# else\n  static double   timeBase;\n\n  clock_gettime(CLOCK_MONOTONIC, &t);\n  if(timeBase == 0)\n    timeBase = clockNow() - ((double) t.tv_sec + (double) t.tv_nsec/1.0e9);\n  return( timeBase + (double) t.tv_sec + (double) t.tv_nsec/1.0e9 );\n# endif\n#elif defined EnhTime\n  static LARGE_INTEGER freq;\n  static double        timeBase;\n  LARGE_INTEGER        now;\n\n  QueryPerformanceCounter(&now);\n  if(timeBase == 0) {\n    QueryPerformanceFrequency(&freq);\n    timeBase = clockNow() - (double) now.QuadPart/(double) freq.QuadPart;\n  }\n  return( timeBase + (double) now.QuadPart/(double) freq.QuadPart );\n#else\n  struct timeb buf;\n\n  ftime(&buf);\n  return((double)buf.time+((double) buf.millitm)/1000.0);\n#endif\n}\n\n\n/* Miscellaneous reporting functions */\n\n/* List a vector of INT values for the given index range */\nvoid blockWriteINT(FILE *output, char *label, int *myvector, int first, int last)\n{\n  int i, k = 0;\n\n  fprintf(output, \"%s\", label);\n  fprintf(output, \"\\n\");\n  for(i = first; i <= last; i++) {\n    fprintf(output, \" %5d\", myvector[i]);\n    k++;\n    if(k % 12 == 0) {\n      fprintf(output, \"\\n\");\n      k = 0;\n    }\n  }\n  if(k % 12 != 0)\n    fprintf(output, \"\\n\");\n}\n\n/* List a vector of MYBOOL values for the given index range */\nvoid blockWriteBOOL(FILE *output, char *label, MYBOOL *myvector, int first, int last, MYBOOL asRaw)\n{\n  int i, k = 0;\n\n  fprintf(output, \"%s\", label);\n  fprintf(output, \"\\n\");\n  for(i = first; i <= last; i++) {\n    if(asRaw)\n      fprintf(output, \" %1d\", myvector[i]);\n    else\n      fprintf(output, \" %5s\", my_boolstr(myvector[i]));\n    k++;\n    if(k % 36 == 0) {\n      fprintf(output, \"\\n\");\n      k = 0;\n    }\n  }\n  if(k % 36 != 0)\n    fprintf(output, \"\\n\");\n}\n\n/* List a vector of REAL values for the given index range */\nvoid blockWriteREAL(FILE *output, char *label, REAL *myvector, int first, int last)\n{\n  int i, k = 0;\n\n  fprintf(output, \"%s\", label);\n  fprintf(output, \"\\n\");\n  for(i = first; i <= last; i++) {\n    fprintf(output, \" %18g\", myvector[i]);\n    k++;\n    if(k % 4 == 0) {\n      fprintf(output, \"\\n\");\n      k = 0;\n    }\n  }\n  if(k % 4 != 0)\n    fprintf(output, \"\\n\");\n}\n\n\n/* CONSOLE vector and matrix printing routines */\nvoid printvec( int n, REAL *x, int modulo )\n{\n  int i;\n\n  if (modulo <= 0) modulo = 5;\n  for (i = 1; i<=n; i++) {\n    if(mod(i, modulo) == 1)\n      printf(\"\\n%2d:%12g\", i, x[i]);\n    else\n      printf(\" %2d:%12g\", i, x[i]);\n  }\n  if(i % modulo != 0) printf(\"\\n\");\n}\n\n\nvoid printmatUT( int size, int n, REAL *U, int modulo)\n{\n   int i, ll;\n   ll = 0;\n   for(i = 1; i<=n; i++) {\n     printvec(n-i+1, &U[ll], modulo);\n     ll += size-i+1;\n   }\n}\n\n\nvoid printmatSQ( int size, int n, REAL *X, int modulo)\n{\n   int i, ll;\n   ll = 0;\n   for(i = 1; i<=n; i++) {\n     printvec(n, &X[ll], modulo);\n     ll += size;\n   }\n}\n\n/* Miscellaneous file functions */\n#if defined _MSC_VER\n/* Check MS versions before 7 */\n#if _MSC_VER < 1300\n# define intptr_t long\n#endif\n\nint fileCount( char *filemask )\n{\n  struct   _finddata_t c_file;\n  intptr_t hFile;\n  int      count = 0;\n\n  /* Find first .c file in current directory */\n  if( (hFile = _findfirst( filemask, &c_file )) == -1L )\n    ;\n  /* Iterate over all matching names */\n  else {\n     while( _findnext( hFile, &c_file ) == 0 )\n       count++;\n    _findclose( hFile );\n  }\n  return( count );\n}\nMYBOOL fileSearchPath( char *envvar, char *searchfile, char *foundpath )\n{\n   char pathbuffer[_MAX_PATH];\n\n   _searchenv( searchfile, envvar, pathbuffer );\n   if(pathbuffer[0] == '\\0')\n     return( FALSE );\n   else {\n     if(foundpath != NULL)\n       strcpy(foundpath, pathbuffer);\n     return( TRUE );\n   }\n}\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/shared/commonlib.h",
    "content": "#ifndef HEADER_commonlib\n#define HEADER_commonlib\n\n#include <stdlib.h>\n#include <stdio.h>\n#ifdef WIN32\n  #include <windows.h>\n#endif\n\n/* static char SpaceChars[3] = {\" \" \"\\7\"}; */\n/* static char NumChars[14]  = {\"0123456789-+.\"}; */\n\n#define BIGNUMBER      1.0e+30\n#define TINYNUMBER     1.0e-04\n#define MACHINEPREC   2.22e-16\n#define MATHPREC       1.0e-16\n#define ERRLIMIT       1.0e-06\n\n#ifndef LINEARSEARCH\n  #define LINEARSEARCH 5\n#endif\n\n#if 0\n  #define INTEGERTIME\n#endif\n\n/* ************************************************************************ */\n/* Define loadable library function headers                                 */\n/* ************************************************************************ */\n#if (defined WIN32) || (defined WIN64)\n  #define my_LoadLibrary(name)              LoadLibrary(name)\n  #define my_GetProcAddress(handle, name)   GetProcAddress(handle, name)\n  #define my_FreeLibrary(handle)            FreeLibrary(handle); \\\n                                            handle = NULL\n#else\n  #define my_LoadLibrary(name)              dlopen(name, RTLD_LAZY)\n  #define my_GetProcAddress(handle, name)   dlsym(handle, name)\n  #define my_FreeLibrary(handle)            dlclose(handle); \\\n                                            handle = NULL\n#endif\n\n\n/* ************************************************************************ */\n/* Define sizes of standard number types                                    */\n/* ************************************************************************ */\n#ifndef LLONG\n  #if defined __BORLANDC__\n    #define LLONG __int64\n  #elif !defined _MSC_VER || _MSC_VER >= 1310\n    #define LLONG long long\n  #else\n    #define LLONG __int64\n  #endif\n#endif\n\n#ifndef MYBOOL\n  #if 0\n    #define MYBOOL unsigned int\n  #else\n    #define MYBOOL unsigned char\n  #endif\n#endif\n\n#ifndef REAL\n  #define REAL     double\n#endif\n#ifndef BLAS_prec\n  #define BLAS_prec \"d\" /* The BLAS precision prefix must correspond to the REAL type */\n#endif\n\n#ifndef REALXP\n  #if 1\n    #define REALXP long double  /* Set local accumulation variable as long double */\n  #else\n    #define REALXP REAL          /* Set local accumulation as default precision */\n  #endif\n#endif\n\n#ifndef my_boolstr\n  #define my_boolstr(x)          (!(x) ? \"FALSE\" : \"TRUE\")\n#endif\n\n#ifndef NULL\n  #define NULL \t       0\n#endif\n\n#ifndef FALSE\n  #define FALSE        0\n  #define TRUE         1\n#endif\n\n#ifndef DEF_STRBUFSIZE\n  #define DEF_STRBUFSIZE   512\n#endif\n#ifndef MAXINT32\n  #define MAXINT32  2147483647\n#endif\n#ifndef MAXUINT32\n  #define MAXUINT32 4294967295\n#endif\n\n#ifndef MAXINT64\n  #if defined _LONGLONG || defined __LONG_LONG_MAX__ || defined LLONG_MAX\n    #define MAXINT64   9223372036854775807ll\n  #else\n    #define MAXINT64   9223372036854775807l\n  #endif\n#endif\n#ifndef MAXUINT64\n  #if defined _LONGLONG || defined __LONG_LONG_MAX__ || defined LLONG_MAX\n    #define MAXUINT64 18446744073709551615ll\n  #else\n    #define MAXUINT64 18446744073709551615l\n  #endif\n#endif\n\n#ifndef DOFASTMATH\n  #define DOFASTMATH\n#endif\n\n\n#ifndef CALLOC\n#define CALLOC(ptr, nr)\\\n  if(!((void *) ptr = calloc((size_t)(nr), sizeof(*ptr))) && nr) {\\\n    printf(\"calloc of %d bytes failed on line %d of file %s\\n\",\\\n           (size_t) nr * sizeof(*ptr), __LINE__, __FILE__);\\\n  }\n#endif\n\n#ifndef MALLOC\n#define MALLOC(ptr, nr)\\\n  if(!((void *) ptr = malloc((size_t)((size_t) (nr) * sizeof(*ptr)))) && nr) {\\\n    printf(\"malloc of %d bytes failed on line %d of file %s\\n\",\\\n           (size_t) nr * sizeof(*ptr), __LINE__, __FILE__);\\\n  }\n#endif\n\n#ifndef REALLOC\n#define REALLOC(ptr, nr)\\\n  if(!((void *) ptr = realloc(ptr, (size_t)((size_t) (nr) * sizeof(*ptr)))) && nr) {\\\n    printf(\"realloc of %d bytes failed on line %d of file %s\\n\",\\\n           (size_t) nr * sizeof(*ptr), __LINE__, __FILE__);\\\n  }\n#endif\n\n#ifndef FREE\n#define FREE(ptr)\\\n  if((void *) ptr != NULL) {\\\n    free(ptr);\\\n    ptr = NULL; \\\n  }\n#endif\n\n#ifndef MEMCOPY\n#define MEMCOPY(nptr, optr, nr)\\\n  memcpy((nptr), (optr), (size_t)((size_t)(nr) * sizeof(*(optr))))\n#endif\n\n#ifndef MEMMOVE\n#define MEMMOVE(nptr, optr, nr)\\\n  memmove((nptr), (optr), (size_t)((size_t)(nr) * sizeof(*(optr))))\n#endif\n\n#ifndef MEMALLOCCOPY\n#define MEMALLOCCOPY(nptr, optr, nr)\\\n  {MALLOC(nptr, (size_t)(nr));\\\n   MEMCOPY(nptr, optr, (size_t)(nr));}\n#endif\n\n#ifndef STRALLOCCOPY\n#define STRALLOCCOPY(nstr, ostr)\\\n  {nstr = (char *) malloc((size_t) (strlen(ostr) + 1));\\\n   strcpy(nstr, ostr);}\n#endif\n\n#ifndef MEMCLEAR\n/*#define useMMX*/\n#ifdef useMMX\n  #define MEMCLEAR(ptr, nr)\\\n    mem_set((ptr), '\\0', (size_t)((size_t)(nr) * sizeof(*(ptr))))\n#else\n  #define MEMCLEAR(ptr, nr)\\\n    memset((ptr), '\\0', (size_t)((size_t)(nr) * sizeof(*(ptr))))\n#endif\n#endif\n\n\n#define MIN(x, y)         ((x) < (y) ? (x) : (y))\n#define MAX(x, y)         ((x) > (y) ? (x) : (y))\n#define SETMIN(x, y)      if((x) > (y)) x = y\n#define SETMAX(x, y)      if((x) < (y)) x = y\n#define LIMIT(lo, x, hi)  ((x < (lo) ? lo : ((x) > hi ? hi : x)))\n#define BETWEEN(x, a, b)  (MYBOOL) (((x)-(a)) * ((x)-(b)) <= 0)\n#define IF(t, x, y)       ((t) ? (x) : (y))\n#define SIGN(x)           ((x) < 0 ? -1 : 1)\n\n#define DELTA_SIZE(newSize, oldSize) ((int) ((newSize) * MIN(1.33, pow(1.5, fabs((double)newSize)/((oldSize+newSize)+1)))))\n\n#ifndef CMP_CALLMODEL\n#if (defined WIN32) || (defined WIN64)\n  #define CMP_CALLMODEL _cdecl\n#else\n  #define CMP_CALLMODEL\n#endif\n#endif\n\ntypedef int (CMP_CALLMODEL findCompare_func)(const void *current, const void *candidate);\n#define CMP_COMPARE(current, candidate) ( current < candidate ? -1 : (current > candidate ? 1 : 0) )\n#define CMP_ATTRIBUTES(item)            (((char *) attributes)+(item)*recsize)\n#define CMP_TAGS(item)                  (((char *) tags)+(item)*tagsize)\n\n#ifndef UNIONTYPE\n  #ifdef __cplusplus\n    #define UNIONTYPE\n  #else\n    #define UNIONTYPE union\n  #endif\n#endif\n\n/* This defines a 16 byte sort record (in both 32 and 64 bit OS-es) */\ntypedef struct _QSORTrec1\n{\n  void     *ptr;\n  void     *ptr2;\n} QSORTrec1;\ntypedef struct _QSORTrec2\n{\n  void     *ptr;\n  double   realval;\n} QSORTrec2;\ntypedef struct _QSORTrec3\n{\n  void     *ptr;\n  int      intval;\n  int      intpar1;\n} QSORTrec3;\ntypedef struct _QSORTrec4\n{\n  REAL     realval;\n  int      intval;\n  int      intpar1;\n} QSORTrec4;\ntypedef struct _QSORTrec5\n{\n  double   realval;\n  long int longval;\n} QSORTrec5;\ntypedef struct _QSORTrec6\n{\n  double   realval;\n  double   realpar1;\n} QSORTrec6;\ntypedef struct _QSORTrec7\n{\n  int      intval;\n  int      intpar1;\n  int      intpar2;\n  int      intpar3;\n} QSORTrec7;\nunion QSORTrec\n{\n  QSORTrec1 pvoid2;\n  QSORTrec2 pvoidreal;\n  QSORTrec3 pvoidint2;\n  QSORTrec4 realint2;\n  QSORTrec5 reallong;\n  QSORTrec6 real2;\n  QSORTrec7 int4;\n};\n\n\n#ifdef __cplusplus\n  extern \"C\" {\n#endif\n\nint intpow(int base, int exponent);\nint mod(int n, int d);\n\nvoid strtoup(char *s);\nvoid strtolo(char *s);\nvoid strcpyup(char *t, char *s);\nvoid strcpylo(char *t, char *s);\n\nMYBOOL so_stdname(char *stdname, char *descname, int buflen);\nint gcd(LLONG a, LLONG b, int *c, int *d);\n\nint findIndex(int target, int *attributes, int count, int offset);\nint findIndexEx(void *target, void *attributes, int count, int offset, int recsize, findCompare_func findCompare, MYBOOL ascending);\n\nvoid qsortex_swap(void *attributes, int l, int r, int recsize,\n                         void *tags, int tagsize, char *save, char *savetag);\n\nint qsortex(void *attributes, int count, int offset, int recsize, MYBOOL descending, findCompare_func findCompare, void *tags, int tagsize);\n\nint CMP_CALLMODEL compareCHAR(const void *current, const void *candidate);\nint CMP_CALLMODEL compareINT(const void *current, const void *candidate);\nint CMP_CALLMODEL compareREAL(const void *current, const void *candidate);\nvoid hpsort(void *attributes, int count, int offset, int recsize, MYBOOL descending, findCompare_func findCompare);\nvoid hpsortex(void *attributes, int count, int offset, int recsize, MYBOOL descending, findCompare_func findCompare, int *tags);\n\nvoid QS_swap(UNIONTYPE QSORTrec a[], int i, int j);\nint QS_addfirst(UNIONTYPE QSORTrec a[], void *mydata);\nint QS_append(UNIONTYPE QSORTrec a[], int ipos, void *mydata);\nvoid QS_replace(UNIONTYPE QSORTrec a[], int ipos, void *mydata);\nvoid QS_insert(UNIONTYPE QSORTrec a[], int ipos, void *mydata, int epos);\nvoid QS_delete(UNIONTYPE QSORTrec a[], int ipos, int epos);\nMYBOOL QS_execute(UNIONTYPE QSORTrec a[], int count, findCompare_func findCompare, int *nswaps);\n\nint sortByREAL(int *item, REAL *weight, int size, int offset, MYBOOL unique);\nint sortByINT(int *item, int *weight, int size, int offset, MYBOOL unique);\nREAL sortREALByINT(REAL *item, int *weight, int size, int offset, MYBOOL unique);\n\ndouble timeNow(void);\n\nvoid blockWriteBOOL(FILE *output, char *label, MYBOOL *myvector, int first, int last, MYBOOL asRaw);\nvoid blockWriteINT(FILE *output, char *label, int *myvector, int first, int last);\nvoid blockWriteREAL(FILE *output, char *label, REAL *myvector, int first, int last);\n\nvoid printvec( int n, REAL *x, int modulo );\nvoid printmatSQ( int size, int n, REAL *X, int modulo );\nvoid printmatUT( int size, int n, REAL *U, int modulo );\n\nunsigned int catchFPU(unsigned int mask);\n\n#if defined _MSC_VER\nint fileCount( char *filemask );\nMYBOOL fileSearchPath( char *envvar, char *searchfile, char *foundpath );\n#endif\n\n#ifdef __cplusplus\n  }\n#endif\n\n#endif /* HEADER_commonlib */\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/shared/mmio.c",
    "content": "/*\n*   Matrix Market I/O library for ANSI C\n*\n*   See http://math.nist.gov/MatrixMarket for details.\n*\n*   (Version 1.01, 5/2003)\n*/\n\n\n#include <stdlib.h>\n#include <stdio.h>\n#include <string.h>\n#include <ctype.h>\n\n#include \"mmio.h\"\n\nint mm_read_unsymmetric_sparse(const char *fname, int *M_, int *N_, int *nz_,\n                double **val_, int **I_, int **J_)\n{\n    FILE *f;\n    MM_typecode matcode;\n    int M, N, nz;\n    int i;\n    double *val;\n    int *I, *J;\n    int x;\n\n    if ((f = fopen(fname, \"r\")) == NULL)\n            return -1;\n\n\n    if (mm_read_banner(f, &matcode) != 0)\n    {\n        printf(\"mm_read_unsymetric: Could not process Matrix Market banner \");\n        printf(\" in file [%s]\\n\", fname);\n        return -1;\n    }\n\n\n\n    if ( !(mm_is_real(matcode) && mm_is_matrix(matcode) &&\n            mm_is_sparse(matcode)))\n    {\n        fprintf(stderr, \"Sorry, this application does not support \");\n        fprintf(stderr, \"Market Market type: [%s]\\n\",\n                mm_typecode_to_str(matcode));\n        return -1;\n    }\n\n    /* find out size of sparse matrix: M, N, nz .... */\n\n    if (mm_read_mtx_crd_size(f, &M, &N, &nz) !=0)\n    {\n        fprintf(stderr, \"read_unsymmetric_sparse(): could not parse matrix size.\\n\");\n        return -1;\n    }\n\n    *M_ = M;\n    *N_ = N;\n    *nz_ = nz;\n\n    /* reseve memory for matrices */\n\n    I = (int *) malloc(nz * sizeof(int));\n    J = (int *) malloc(nz * sizeof(int));\n    val = (double *) malloc(nz * sizeof(double));\n\n    *val_ = val;\n    *I_ = I;\n    *J_ = J;\n\n    /* NOTE: when reading in doubles, ANSI C requires the use of the \"l\"  */\n    /*   specifier as in \"%lg\", \"%lf\", \"%le\", otherwise errors will occur */\n    /*  (ANSI C X3.159-1989, Sec. 4.9.6.2, p. 136 lines 13-15)            */\n\n    for (i=0; i<nz; i++)\n    {\n        x = fscanf(f, \"%d %d %lg\\n\", &I[i], &J[i], &val[i]);\n        I[i]--;  /* adjust from 1-based to 0-based */\n        J[i]--;\n    }\n    fclose(f);\n\n    return 0;\n}\n\nint mm_is_valid(MM_typecode matcode)\n{\n    if (!mm_is_matrix(matcode)) return 0;\n    if (mm_is_dense(matcode) && mm_is_pattern(matcode)) return 0;\n    if (mm_is_real(matcode) && mm_is_hermitian(matcode)) return 0;\n    if (mm_is_pattern(matcode) && (mm_is_hermitian(matcode) ||\n                mm_is_skew(matcode))) return 0;\n    return 1;\n}\n\nint mm_read_banner(FILE *f, MM_typecode *matcode)\n{\n    char line[MM_MAX_LINE_LENGTH];\n    char banner[MM_MAX_TOKEN_LENGTH];\n    char mtx[MM_MAX_TOKEN_LENGTH];\n    char crd[MM_MAX_TOKEN_LENGTH];\n    char data_type[MM_MAX_TOKEN_LENGTH];\n    char storage_scheme[MM_MAX_TOKEN_LENGTH];\n    char *p;\n\n\n    mm_clear_typecode(matcode);\n\n    if (fgets(line, MM_MAX_LINE_LENGTH, f) == NULL)\n        return MM_PREMATURE_EOF;\n\n    if (sscanf(line, \"%s %s %s %s %s\", banner, mtx, crd, data_type,\n        storage_scheme) != 5)\n        return MM_PREMATURE_EOF;\n\n\t/* convert to lower case */\n    for (p=mtx; *p!='\\0'; *p= (char) tolower(*p),p++);\n    for (p=crd; *p!='\\0'; *p= (char) tolower(*p),p++);\n    for (p=data_type; *p!='\\0'; *p= (char) tolower(*p),p++);\n    for (p=storage_scheme; *p!='\\0'; *p= (char) tolower(*p),p++);\n\n    /* check for banner */\n    if (strncmp(banner, MatrixMarketBanner, strlen(MatrixMarketBanner)) != 0)\n        return MM_NO_HEADER;\n\n    /* first field should be \"mtx\" */\n    if (strcmp(mtx, MM_MTX_STR) != 0)\n        return  MM_UNSUPPORTED_TYPE;\n    mm_set_matrix(matcode);\n\n\n    /* second field describes whether this is a sparse matrix (in coordinate\n            storgae) or a dense array */\n\n\n    if (strcmp(crd, MM_SPARSE_STR) == 0)\n        mm_set_sparse(matcode);\n    else\n    if (strcmp(crd, MM_DENSE_STR) == 0)\n            mm_set_dense(matcode);\n    else\n        return MM_UNSUPPORTED_TYPE;\n\n\n    /* third field */\n\n    if (strcmp(data_type, MM_REAL_STR) == 0)\n        mm_set_real(matcode);\n    else\n    if (strcmp(data_type, MM_COMPLEX_STR) == 0)\n        mm_set_complex(matcode);\n    else\n    if (strcmp(data_type, MM_PATTERN_STR) == 0)\n        mm_set_pattern(matcode);\n    else\n    if (strcmp(data_type, MM_INT_STR) == 0)\n        mm_set_integer(matcode);\n    else\n        return MM_UNSUPPORTED_TYPE;\n\n\n    /* fourth field */\n\n    if (strcmp(storage_scheme, MM_GENERAL_STR) == 0)\n        mm_set_general(matcode);\n    else\n    if (strcmp(storage_scheme, MM_SYMM_STR) == 0)\n        mm_set_symmetric(matcode);\n    else\n    if (strcmp(storage_scheme, MM_HERM_STR) == 0)\n        mm_set_hermitian(matcode);\n    else\n    if (strcmp(storage_scheme, MM_SKEW_STR) == 0)\n        mm_set_skew(matcode);\n    else\n        return MM_UNSUPPORTED_TYPE;\n\n\n    return 0;\n}\n\nint mm_write_mtx_crd_size(FILE *f, int M, int N, int nz)\n{\n    if (fprintf(f, \"%d %d %d\\n\", M, N, nz) < 0)\n        return MM_COULD_NOT_WRITE_FILE;\n    else\n        return 0;\n}\n\nint mm_read_mtx_crd_size(FILE *f, int *M, int *N, int *nz )\n{\n    char line[MM_MAX_LINE_LENGTH];\n    int num_items_read;\n\n    /* set return null parameter values, in case we exit with errors */\n    *M = *N = *nz = 0;\n\n    /* now continue scanning until you reach the end-of-comments */\n    do {\n      if (fgets(line,MM_MAX_LINE_LENGTH,f) == NULL)\n          return MM_PREMATURE_EOF;\n    } while (line[0] == '%');\n\n    /* line[] is either blank, har M,N or M,N,nz */\n    if (sscanf(line, \"%d %d %d\", M, N, nz) >= 2)\n      return 0;\n\n    else\n    do {\n        num_items_read = fscanf(f, \"%d %d %d\", M, N, nz);\n        if (num_items_read == EOF) return MM_PREMATURE_EOF;\n    } while (num_items_read < 2);\n\n    return 0;\n}\n\n\nint mm_read_mtx_array_size(FILE *f, int *M, int *N)\n{\n    char line[MM_MAX_LINE_LENGTH];\n    int num_items_read;\n    /* set return null parameter values, in case we exit with errors */\n    *M = *N = 0;\n\n    /* now continue scanning until you reach the end-of-comments */\n    do\n    {\n        if (fgets(line,MM_MAX_LINE_LENGTH,f) == NULL)\n            return MM_PREMATURE_EOF;\n    }while (line[0] == '%');\n\n    /* line[] is either blank or has M,N, nz */\n    if (sscanf(line, \"%d %d\", M, N) == 2)\n        return 0;\n\n    else /* we have a blank line */\n    do\n    {\n        num_items_read = fscanf(f, \"%d %d\", M, N);\n        if (num_items_read == EOF) return MM_PREMATURE_EOF;\n    }\n    while (num_items_read != 2);\n\n    return 0;\n}\n\nint mm_write_mtx_array_size(FILE *f, int M, int N)\n{\n    if (fprintf(f, \"%d %d\\n\", M, N) < 0)\n        return MM_COULD_NOT_WRITE_FILE;\n    else\n        return 0;\n}\n\n\n\n/*-------------------------------------------------------------------------*/\n\n/******************************************************************/\n/* use when I[], J[], and val[]J, and val[] are already allocated */\n/******************************************************************/\n\nint mm_read_mtx_crd_data(FILE *f, int M, int N, int nz, int I[], int J[],\n        double val[], MM_typecode matcode)\n{\n    int i;\n    if (mm_is_complex(matcode))\n    {\n        for (i=0; i<nz; i++)\n            if (fscanf(f, \"%d %d %lg %lg\", &I[i], &J[i], &val[2*i], &val[2*i+1])\n                != 4) return MM_PREMATURE_EOF;\n    }\n    else if (mm_is_real(matcode))\n    {\n        for (i=0; i<nz; i++)\n        {\n            if (fscanf(f, \"%d %d %lg\\n\", &I[i], &J[i], &val[i])\n                != 3) return MM_PREMATURE_EOF;\n\n        }\n    }\n\n    else if (mm_is_pattern(matcode))\n    {\n        for (i=0; i<nz; i++)\n            if (fscanf(f, \"%d %d\", &I[i], &J[i])\n                != 2) return MM_PREMATURE_EOF;\n    }\n    else\n        return MM_UNSUPPORTED_TYPE;\n\n    return 0;\n\n}\n\nint mm_read_mtx_crd_entry(FILE *f, int *I, int *J,\n        double *real, double *imag, MM_typecode matcode)\n{\n    if (mm_is_complex(matcode))\n    {\n            if (fscanf(f, \"%d %d %lg %lg\", I, J, real, imag)\n                != 4) return MM_PREMATURE_EOF;\n    }\n    else if (mm_is_real(matcode))\n    {\n            if (fscanf(f, \"%d %d %lg\\n\", I, J, real)\n                != 3) return MM_PREMATURE_EOF;\n\n    }\n\n    else if (mm_is_pattern(matcode))\n    {\n            if (fscanf(f, \"%d %d\", I, J) != 2) return MM_PREMATURE_EOF;\n    }\n    else\n        return MM_UNSUPPORTED_TYPE;\n\n    return 0;\n\n}\n\n\n/************************************************************************\n    mm_read_mtx_crd()  fills M, N, nz, array of values, and return\n                        type code, e.g. 'MCRS'\n\n                        if matrix is complex, values[] is of size 2*nz,\n                            (nz pairs of real/imaginary values)\n************************************************************************/\n\nint mm_read_mtx_crd(char *fname, int *M, int *N, int *nz, int **I, int **J,\n        double **val, MM_typecode *matcode)\n{\n    int ret_code;\n    FILE *f;\n\n    if (strcmp(fname, \"stdin\") == 0) f=stdin;\n    else\n    if ((f = fopen(fname, \"r\")) == NULL)\n        return MM_COULD_NOT_READ_FILE;\n\n\n    if ((ret_code = mm_read_banner(f, matcode)) != 0)\n        return ret_code;\n\n    if (!(mm_is_valid(*matcode) && mm_is_sparse(*matcode) &&\n            mm_is_matrix(*matcode)))\n        return MM_UNSUPPORTED_TYPE;\n\n    if ((ret_code = mm_read_mtx_crd_size(f, M, N, nz)) != 0)\n        return ret_code;\n\n\n    *I = (int *)  malloc(*nz * sizeof(int));\n    *J = (int *)  malloc(*nz * sizeof(int));\n    *val = NULL;\n\n    if (mm_is_complex(*matcode))\n    {\n        *val = (double *) malloc(*nz * 2 * sizeof(double));\n        ret_code = mm_read_mtx_crd_data(f, *M, *N, *nz, *I, *J, *val,\n                *matcode);\n        if (ret_code != 0) return ret_code;\n    }\n    else if (mm_is_real(*matcode))\n    {\n        *val = (double *) malloc(*nz * sizeof(double));\n        ret_code = mm_read_mtx_crd_data(f, *M, *N, *nz, *I, *J, *val,\n                *matcode);\n        if (ret_code != 0) return ret_code;\n    }\n\n    else if (mm_is_pattern(*matcode))\n    {\n        ret_code = mm_read_mtx_crd_data(f, *M, *N, *nz, *I, *J, *val,\n                *matcode);\n        if (ret_code != 0) return ret_code;\n    }\n\n    if (f != stdin) fclose(f);\n    return 0;\n}\n\nint mm_write_banner(FILE *f, MM_typecode matcode)\n{\n    char *str = mm_typecode_to_str(matcode);\n    int ret_code;\n\n    ret_code = fprintf(f, \"%s %s\\n\", MatrixMarketBanner, str);\n/*    free(str);  This is a bug from the official distribution - KE fixed */\n    if (ret_code < 0 )\n        return MM_COULD_NOT_WRITE_FILE;\n    else\n        return 0;\n}\n\nint mm_write_mtx_crd(char fname[], int M, int N, int nz, int I[], int J[],\n        double val[], MM_typecode matcode)\n{\n    FILE *f;\n    int i;\n\n    if (strcmp(fname, \"stdout\") == 0)\n        f = stdout;\n    else\n    if ((f = fopen(fname, \"w\")) == NULL)\n        return MM_COULD_NOT_WRITE_FILE;\n\n    /* print banner followed by typecode */\n    fprintf(f, \"%s \", MatrixMarketBanner);\n    fprintf(f, \"%s\\n\", mm_typecode_to_str(matcode));\n\n    /* print matrix sizes and nonzeros */\n    fprintf(f, \"%d %d %d\\n\", M, N, nz);\n\n    /* print values */\n    if (mm_is_pattern(matcode))\n        for (i=0; i<nz; i++)\n            fprintf(f, \"%d %d\\n\", I[i], J[i]);\n    else\n    if (mm_is_real(matcode))\n        for (i=0; i<nz; i++)\n            fprintf(f, \"%d %d %20.16g\\n\", I[i], J[i], val[i]);\n    else\n    if (mm_is_complex(matcode))\n        for (i=0; i<nz; i++)\n            fprintf(f, \"%d %d %20.16g %20.16g\\n\", I[i], J[i], val[2*i],\n                        val[2*i+1]);\n    else\n    {\n        if (f != stdout) fclose(f);\n        return MM_UNSUPPORTED_TYPE;\n    }\n\n    if (f !=stdout) fclose(f);\n\n    return 0;\n}\n\n\nchar  *mm_typecode_to_str(MM_typecode matcode)\n{\n    static char buffer[MM_MAX_LINE_LENGTH];\n    char *types[4];\n\n    /* check for MTX type */\n    if (mm_is_matrix(matcode))\n        types[0] = MM_MTX_STR;\n    else\n        return NULL;\n\n    /* check for CRD or ARR matrix */\n    if (mm_is_sparse(matcode))\n        types[1] = MM_SPARSE_STR;\n    else\n    if (mm_is_dense(matcode))\n        types[1] = MM_DENSE_STR;\n    else\n        return NULL;\n\n    /* check for element data type */\n    if (mm_is_real(matcode))\n        types[2] = MM_REAL_STR;\n    else\n    if (mm_is_complex(matcode))\n        types[2] = MM_COMPLEX_STR;\n    else\n    if (mm_is_pattern(matcode))\n        types[2] = MM_PATTERN_STR;\n    else\n    if (mm_is_integer(matcode))\n        types[2] = MM_INT_STR;\n    else\n        return NULL;\n\n\n    /* check for symmetry type */\n    if (mm_is_general(matcode))\n        types[3] = MM_GENERAL_STR;\n    else\n    if (mm_is_symmetric(matcode))\n        types[3] = MM_SYMM_STR;\n    else\n    if (mm_is_hermitian(matcode))\n        types[3] = MM_HERM_STR;\n    else\n    if (mm_is_skew(matcode))\n        types[3] = MM_SKEW_STR;\n    else\n        return NULL;\n\n    sprintf(buffer,\"%s %s %s %s\", types[0], types[1], types[2], types[3]);\n    return & buffer[0];\n\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/shared/mmio.h",
    "content": "/*\n*   Matrix Market I/O library for ANSI C\n*\n*   See http://math.nist.gov/MatrixMarket for details.\n*\n*\n*/\n\n#ifndef MM_IO_H\n#define MM_IO_H\n\n#define MM_MAX_LINE_LENGTH 1025\n#define MatrixMarketBanner \"%%MatrixMarket\"\n#define MM_MAX_TOKEN_LENGTH 64\n\ntypedef char MM_typecode[4];\n\nchar *mm_typecode_to_str(MM_typecode matcode);\n\nint mm_read_banner(FILE *f, MM_typecode *matcode);\nint mm_read_mtx_crd_size(FILE *f, int *M, int *N, int *nz);\nint mm_read_mtx_array_size(FILE *f, int *M, int *N);\n\nint mm_write_banner(FILE *f, MM_typecode matcode);\nint mm_write_mtx_crd_size(FILE *f, int M, int N, int nz);\nint mm_write_mtx_array_size(FILE *f, int M, int N);\n\n\n/********************* MM_typecode query fucntions ***************************/\n\n#define mm_is_matrix(typecode)  ((typecode)[0]=='M')\n\n#define mm_is_sparse(typecode)  ((typecode)[1]=='C')\n#define mm_is_coordinate(typecode)((typecode)[1]=='C')\n#define mm_is_dense(typecode) ((typecode)[1]=='A')\n#define mm_is_array(typecode) ((typecode)[1]=='A')\n\n#define mm_is_complex(typecode) ((typecode)[2]=='C')\n#define mm_is_real(typecode)    ((typecode)[2]=='R')\n#define mm_is_pattern(typecode) ((typecode)[2]=='P')\n#define mm_is_integer(typecode) ((typecode)[2]=='I')\n\n#define mm_is_symmetric(typecode)((typecode)[3]=='S')\n#define mm_is_general(typecode) ((typecode)[3]=='G')\n#define mm_is_skew(typecode)  ((typecode)[3]=='K')\n#define mm_is_hermitian(typecode)((typecode)[3]=='H')\n\nint mm_is_valid(MM_typecode matcode);   /* too complex for a macro */\n\n\n/********************* MM_typecode modify fucntions ***************************/\n\n#define mm_set_matrix(typecode) ((*typecode)[0]='M')\n#define mm_set_coordinate(typecode) ((*typecode)[1]='C')\n#define mm_set_array(typecode)  ((*typecode)[1]='A')\n#define mm_set_dense(typecode)  mm_set_array(typecode)\n#define mm_set_sparse(typecode) mm_set_coordinate(typecode)\n\n#define mm_set_complex(typecode)((*typecode)[2]='C')\n#define mm_set_real(typecode) ((*typecode)[2]='R')\n#define mm_set_pattern(typecode)((*typecode)[2]='P')\n#define mm_set_integer(typecode)((*typecode)[2]='I')\n\n\n#define mm_set_symmetric(typecode)((*typecode)[3]='S')\n#define mm_set_general(typecode)((*typecode)[3]='G')\n#define mm_set_skew(typecode) ((*typecode)[3]='K')\n#define mm_set_hermitian(typecode)((*typecode)[3]='H')\n\n#define mm_clear_typecode(typecode) ((*typecode)[0]=(*typecode)[1]= \\\n                  (*typecode)[2]=' ',(*typecode)[3]='G')\n\n#define mm_initialize_typecode(typecode) mm_clear_typecode(typecode)\n\n\n/********************* Matrix Market error codes ***************************/\n\n\n#define MM_COULD_NOT_READ_FILE  11\n#define MM_PREMATURE_EOF        12\n#define MM_NOT_MTX              13\n#define MM_NO_HEADER            14\n#define MM_UNSUPPORTED_TYPE     15\n#define MM_LINE_TOO_LONG        16\n#define MM_COULD_NOT_WRITE_FILE 17\n\n\n/******************** Matrix Market internal definitions ********************\n\n   MM_matrix_typecode: 4-character sequence\n\n            ojbect    sparse/     data        storage\n                  dense       type        scheme\n\n   string position:  [0]        [1]     [2]         [3]\n\n   Matrix typecode:  M(atrix)  C(oord)    R(eal)    G(eneral)\n                    A(array)  C(omplex)   H(ermitian)\n                      P(attern)   S(ymmetric)\n                        I(nteger) K(kew)\n\n ***********************************************************************/\n\n#define MM_MTX_STR    \"matrix\"\n#define MM_ARRAY_STR  \"array\"\n#define MM_DENSE_STR  \"array\"\n#define MM_COORDINATE_STR \"coordinate\"\n#define MM_SPARSE_STR \"coordinate\"\n#define MM_COMPLEX_STR  \"complex\"\n#define MM_REAL_STR   \"real\"\n#define MM_INT_STR    \"integer\"\n#define MM_GENERAL_STR  \"general\"\n#define MM_SYMM_STR   \"symmetric\"\n#define MM_HERM_STR   \"hermitian\"\n#define MM_SKEW_STR   \"skew-symmetric\"\n#define MM_PATTERN_STR  \"pattern\"\n\n\n/*  high level routines */\n\nint mm_write_mtx_crd(char fname[], int M, int N, int nz, int I[], int J[],\n     double val[], MM_typecode matcode);\nint mm_read_mtx_crd_data(FILE *f, int M, int N, int nz, int I[], int J[],\n    double val[], MM_typecode matcode);\nint mm_read_mtx_crd_entry(FILE *f, int *I, int *J, double *real, double *img,\n      MM_typecode matcode);\n\nint mm_read_unsymmetric_sparse(const char *fname, int *M_, int *N_, int *nz_,\n                double **val_, int **I_, int **J_);\n\n\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/shared/myblas.c",
    "content": "\n#include <stdlib.h>\n#include <stdio.h>\n/*#include <memory.h>*/\n#include <string.h>\n#include <math.h>\n#include \"myblas.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n/* ************************************************************************ */\n/* Initialize BLAS interfacing routines                                     */\n/* ************************************************************************ */\nMYBOOL mustinitBLAS = TRUE;\n#ifdef WIN32\n  HINSTANCE hBLAS = NULL;\n#else\n  void      *hBLAS = NULL;\n#endif\n\n\n/* ************************************************************************ */\n/* Function pointers for external BLAS library (C base 0)                   */\n/* ************************************************************************ */\nBLAS_dscal_func  *BLAS_dscal;\nBLAS_dcopy_func  *BLAS_dcopy;\nBLAS_daxpy_func  *BLAS_daxpy;\nBLAS_dswap_func  *BLAS_dswap;\nBLAS_ddot_func   *BLAS_ddot;\nBLAS_idamax_func *BLAS_idamax;\nBLAS_dload_func  *BLAS_dload;\nBLAS_dnormi_func *BLAS_dnormi;\n\n\n/* ************************************************************************ */\n/* Define the BLAS interfacing routines                                     */\n/* ************************************************************************ */\n\nvoid init_BLAS(void)\n{\n  if(mustinitBLAS) {\n    load_BLAS(NULL);\n    mustinitBLAS = FALSE;\n  }\n}\n\nMYBOOL is_nativeBLAS(void)\n{\n#ifdef LoadableBlasLib\n  return( (MYBOOL) (hBLAS == NULL) );\n#else\n  return( TRUE );\n#endif\n}\n\nMYBOOL load_BLAS(char *libname)\n{\n  MYBOOL result = TRUE;\n\n#ifdef LoadableBlasLib\n  if(hBLAS != NULL) {\n  #ifdef WIN32\n    FreeLibrary(hBLAS);\n  #else\n    dlclose(hBLAS);\n  #endif\n    hBLAS = NULL;\n  }\n#endif\n\n  if(libname == NULL) {\n    if(!mustinitBLAS && is_nativeBLAS())\n      return( FALSE );\n    BLAS_dscal = my_dscal;\n    BLAS_dcopy = my_dcopy;\n    BLAS_daxpy = my_daxpy;\n    BLAS_dswap = my_dswap;\n    BLAS_ddot  = my_ddot;\n    BLAS_idamax = my_idamax;\n    BLAS_dload = my_dload;\n    BLAS_dnormi = my_dnormi;\n    if(mustinitBLAS)\n      mustinitBLAS = FALSE;\n  }\n  else {\n#ifdef LoadableBlasLib\n  #ifdef WIN32\n   /* Get a handle to the Windows DLL module. */\n    hBLAS = LoadLibrary(libname);\n\n   /* If the handle is valid, try to get the function addresses. */\n    result = (MYBOOL) (hBLAS != NULL);\n    if(result) {\n      BLAS_dscal  = (BLAS_dscal_func *)  GetProcAddress(hBLAS, BLAS_prec \"scal\");\n      BLAS_dcopy  = (BLAS_dcopy_func *)  GetProcAddress(hBLAS, BLAS_prec \"copy\");\n      BLAS_daxpy  = (BLAS_daxpy_func *)  GetProcAddress(hBLAS, BLAS_prec \"axpy\");\n      BLAS_dswap  = (BLAS_dswap_func *)  GetProcAddress(hBLAS, BLAS_prec \"swap\");\n      BLAS_ddot   = (BLAS_ddot_func *)   GetProcAddress(hBLAS, BLAS_prec \"dot\");\n      BLAS_idamax = (BLAS_idamax_func *) GetProcAddress(hBLAS, \"i\" BLAS_prec \"amax\");\n#if 0      \n      BLAS_dload  = (BLAS_dload_func *)  GetProcAddress(hBLAS, BLAS_prec \"load\");\n      BLAS_dnormi = (BLAS_dnormi_func *) GetProcAddress(hBLAS, BLAS_prec \"normi\");\n#endif      \n    }\n  #else\n   /* First standardize UNIX .SO library name format. */\n    char blasname[260], *ptr;\n\n    strcpy(blasname, libname);\n    if((ptr = strrchr(libname, '/')) == NULL)\n      ptr = libname;\n    else\n      ptr++;\n    blasname[(int) (ptr - libname)] = 0;\n    if(strncmp(ptr, \"lib\", 3))\n      strcat(blasname, \"lib\");\n    strcat(blasname, ptr);\n    if(strcmp(blasname + strlen(blasname) - 3, \".so\"))\n      strcat(blasname, \".so\");\n\n   /* Get a handle to the module. */\n    hBLAS = dlopen(blasname, RTLD_LAZY);\n\n   /* If the handle is valid, try to get the function addresses. */\n    result = (MYBOOL) (hBLAS != NULL);\n    if(result) {\n      BLAS_dscal  = (BLAS_dscal_func *)  dlsym(hBLAS, BLAS_prec \"scal\");\n      BLAS_dcopy  = (BLAS_dcopy_func *)  dlsym(hBLAS, BLAS_prec \"copy\");\n      BLAS_daxpy  = (BLAS_daxpy_func *)  dlsym(hBLAS, BLAS_prec \"axpy\");\n      BLAS_dswap  = (BLAS_dswap_func *)  dlsym(hBLAS, BLAS_prec \"swap\");\n      BLAS_ddot   = (BLAS_ddot_func *)   dlsym(hBLAS, BLAS_prec \"dot\");\n      BLAS_idamax = (BLAS_idamax_func *) dlsym(hBLAS, \"i\" BLAS_prec \"amax\");\n#if 0      \n      BLAS_dload  = (BLAS_dload_func *)  dlsym(hBLAS, BLAS_prec \"load\");\n      BLAS_dnormi = (BLAS_dnormi_func *) dlsym(hBLAS, BLAS_prec \"normi\");\n#endif      \n    }\n  #endif\n#endif\n    /* Do validation */\n    if(!result ||\n       ((BLAS_dscal  == NULL) ||\n        (BLAS_dcopy  == NULL) ||\n        (BLAS_daxpy  == NULL) ||\n        (BLAS_dswap  == NULL) ||\n        (BLAS_ddot   == NULL) ||\n        (BLAS_idamax == NULL) ||\n        (BLAS_dload  == NULL) ||\n        (BLAS_dnormi == NULL))\n      ) {\n      load_BLAS(NULL);\n      result = FALSE;\n    }\n  }\n  return( result );\n}\nMYBOOL unload_BLAS(void)\n{\n  return( load_BLAS(NULL) );\n}\n\n\n/* ************************************************************************ */\n/* Now define the unoptimized local BLAS functions                          */\n/* ************************************************************************ */\nvoid daxpy( int n, REAL da, REAL *dx, int incx, REAL *dy, int incy)\n{\n  dx++;\n  dy++;\n  BLAS_daxpy( &n, &da, dx, &incx, dy, &incy);\n}\nvoid BLAS_CALLMODEL my_daxpy( int *_n, REAL *_da, REAL *dx, int *_incx, REAL *dy, int *_incy)\n{\n\n/* constant times a vector plus a vector.\n   uses unrolled loops for increments equal to one.\n   jack dongarra, linpack, 3/11/78.\n   modified 12/3/93, array[1] declarations changed to array[*] */\n\n  int      i, ix, iy;\n#if !defined DOFASTMATH\n  int      m, mp1;\n#endif\n  register REAL rda;\n  REAL     da = *_da;\n  int      n = *_n, incx = *_incx, incy = *_incy;\n\n  if (n <= 0) return;\n  if (da == 0.0) return;\n\n  dx--;\n  dy--;\n  ix = 1;\n  iy = 1;\n  if (incx < 0)\n     ix = (-n+1)*incx + 1;\n  if (incy < 0)\n     iy = (-n+1)*incy + 1;\n  rda = da;\n\n/* CPU intensive loop; option to do pointer arithmetic */\n#if defined DOFASTMATH\n  {\n    REAL *xptr, *yptr;\n    for (i = 1, xptr = dx + ix, yptr = dy + iy;\n         i <= n; i++, xptr += incx, yptr += incy)\n      (*yptr) += rda*(*xptr);\n    return;\n  }\n#else  \n\n  if (incx==1 && incy==1) goto x20;\n\n/* code for unequal increments or equal increments not equal to 1 */\n  for (i = 1; i<=n; i++) {\n     dy[iy]+= rda*dx[ix];\n     ix+= incx;\n     iy+= incy;\n  }\n  return;\n\n/*  code for both increments equal to 1 */\n\n/*  clean-up loop */\nx20:\n  m = n % 4;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++)\n     dy[i]+= rda*dx[i];\n  if(n < 4) return;\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+4) {\n    dy[i]+= rda*dx[i];\n    dy[i + 1]+= rda*dx[i + 1];\n    dy[i + 2]+= rda*dx[i + 2];\n    dy[i + 3]+= rda*dx[i + 3];\n  }\n#endif\n}\n\n\n/* ************************************************************************ */\nvoid dcopy( int n, REAL *dx, int incx, REAL *dy, int incy)\n{\n  dx++;\n  dy++;\n  BLAS_dcopy( &n, dx, &incx, dy, &incy);\n}\n\nvoid BLAS_CALLMODEL my_dcopy (int *_n, REAL *dx, int *_incx, REAL *dy, int *_incy)\n{\n\n/* copies a vector, x, to a vector, y.\n   uses unrolled loops for increments equal to one.\n   jack dongarra, linpack, 3/11/78.\n   modified 12/3/93, array[1] declarations changed to array[*] */\n\n  int      i, ix, iy;\n#if !defined DOFASTMATH\n  int      m, mp1;\n#endif\n  int      n = *_n, incx = *_incx, incy = *_incy;\n\n  if (n<=0) return;\n\n  dx--;\n  dy--;\n  ix = 1;\n  iy = 1;\n  if (incx<0)\n    ix = (-n+1)*incx + 1;\n  if (incy<0)\n    iy = (-n+1)*incy + 1;\n\n\n/* CPU intensive loop; option to do pointer arithmetic */\n#if defined DOFASTMATH\n  {\n    REAL *xptr, *yptr;\n    for (i = 1, xptr = dx + ix, yptr = dy + iy;\n         i <= n; i++, xptr += incx, yptr += incy)\n      (*yptr) = (*xptr);\n    return;\n  }\n#else\n\n  if (incx==1 && incy==1) goto x20;\n\n/* code for unequal increments or equal increments not equal to 1 */\n\n  for (i = 1; i<=n; i++) {\n    dy[iy] = dx[ix];\n    ix+= incx;\n    iy+= incy;\n  }\n  return;\n\n/* code for both increments equal to 1 */\n\n/* version with fast machine copy logic (requires memory.h or string.h) */\nx20:\n#if defined DOFASTMATH\n  MEMCOPY(&dy[1], &dx[1], n);\n  return;\n#else\n\n  m = n % 7;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++)\n     dy[i] = dx[i];\n  if (n < 7) return;\n\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+7) {\n     dy[i] = dx[i];\n     dy[i + 1] = dx[i + 1];\n     dy[i + 2] = dx[i + 2];\n     dy[i + 3] = dx[i + 3];\n     dy[i + 4] = dx[i + 4];\n     dy[i + 5] = dx[i + 5];\n     dy[i + 6] = dx[i + 6];\n  }\n#endif\n#endif\n}\n\n\n/* ************************************************************************ */\n\nvoid dscal (int n, REAL da, REAL *dx, int incx)\n{\n  dx++;\n  BLAS_dscal (&n, &da, dx, &incx);\n}\n\nvoid BLAS_CALLMODEL my_dscal (int *_n, REAL *_da, REAL *dx, int *_incx)\n{\n\n/* Multiply a vector by a constant.\n\n     --Input--\n        N  number of elements in input vector(s)\n       DA  double precision scale factor\n       DX  double precision vector with N elements\n     INCX  storage spacing between elements of DX\n\n     --Output--\n       DX  double precision result (unchanged if N.LE.0)\n\n     Replace double precision DX by double precision DA*DX.\n     For I = 0 to N-1, replace DX(IX+I*INCX) with  DA * DX(IX+I*INCX),\n     where IX = 1 if INCX .GE. 0, else IX = 1+(1-N)*INCX. */\n\n  int      i;\n#if !defined DOFASTMATH\n  int      ix, m, mp1;\n#endif\n  register REAL rda;\n  REAL      da = *_da;\n  int      n = *_n, incx = *_incx;\n\n  if (n <= 0)\n    return;\n  rda = da;  \n  \n  dx--;\n\n/* Optionally do fast pointer arithmetic */\n#if defined DOFASTMATH\n  {\n    REAL *xptr;\n    for (i = 1, xptr = dx + 1; i <= n; i++, xptr += incx)\n      (*xptr) *= rda;\n    return;\n  }\n#else\n\n  if (incx == 1)\n    goto x20;\n\n/* Code for increment not equal to 1 */\n  ix = 1;\n  if (incx < 0)\n    ix = (-n+1)*incx + 1;\n  for(i = 1; i <= n; i++, ix += incx)\n    dx[ix] *= rda;\n  return;\n\n/* Code for increment equal to 1. */\n/* Clean-up loop so remaining vector length is a multiple of 5. */\nx20:\n  m = n % 5;\n  if (m == 0) goto x40;\n  for( i = 1; i <= m; i++)\n    dx[i] *= rda;\n  if (n < 5)\n    return;\nx40:\n  mp1 = m + 1;\n  for(i = mp1; i <= n; i += 5) {\n    dx[i]   *= rda;\n    dx[i+1] *= rda;\n    dx[i+2] *= rda;\n    dx[i+3] *= rda;\n    dx[i+4] *= rda;\n  }\n#endif\n}\n\n\n/* ************************************************************************ */\n\nREAL ddot(int n, REAL *dx, int incx, REAL *dy, int incy)\n{\n  dx++;\n  dy++;\n  return( BLAS_ddot (&n, dx, &incx, dy, &incy) );\n}\n\nREAL BLAS_CALLMODEL my_ddot(int *_n, REAL *dx, int *_incx, REAL *dy, int *_incy)\n{\n\n/* forms the dot product of two vectors.\n   uses unrolled loops for increments equal to one.\n   jack dongarra, linpack, 3/11/78.\n   modified 12/3/93, array[1] declarations changed to array[*] */\n\n  register REAL dtemp;\n  int      i, ix, iy;\n#if !defined DOFASTMATH\n  int      m, mp1;\n#endif\n  int      n = *_n, incx = *_incx, incy = *_incy;\n\n  dtemp = 0.0;\n  if (n<=0)\n    return( (REAL) dtemp);\n\n  dx--;\n  dy--;\n  ix = 1;\n  iy = 1;\n  if (incx<0)\n     ix = (-n+1)*incx + 1;\n  if (incy<0)\n     iy = (-n+1)*incy + 1;\n\n/* CPU intensive loop; option to do pointer arithmetic */\n\n#if defined DOFASTMATH\n  {\n    REAL *xptr, *yptr;\n    for (i = 1, xptr = dx + ix, yptr = dy + iy;\n         i <= n; i++, xptr += incx, yptr += incy)\n      dtemp+= (*yptr)*(*xptr);\n    return(dtemp);\n  }\n#else\n\n  if (incx==1 && incy==1) goto x20;\n\n/* code for unequal increments or equal increments not equal to 1 */\n\n  for (i = 1; i<=n; i++) {\n     dtemp+= dx[ix]*dy[iy];\n     ix+= incx;\n     iy+= incy;\n  }\n  return(dtemp);\n\n/* code for both increments equal to 1 */\n\n/* clean-up loop */\n\nx20:\n  m = n % 5;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++)\n     dtemp+= dx[i]*dy[i];\n  if (n < 5) goto x60;\n\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+5)\n     dtemp+= dx[i]*dy[i] + dx[i + 1]*dy[i + 1] +\n             dx[i + 2]*dy[i + 2] + dx[i + 3]*dy[i + 3] + dx[i + 4]*dy[i + 4];\n\nx60:\n  return(dtemp);\n#endif\n}\n\n\n/* ************************************************************************ */\n\nvoid dswap( int n, REAL *dx, int incx, REAL *dy, int incy )\n{\n  dx++;\n  dy++;\n  BLAS_dswap( &n, dx, &incx, dy, &incy );\n}\n\nvoid BLAS_CALLMODEL my_dswap( int *_n, REAL *dx, int *_incx, REAL *dy, int *_incy )\n{\n  int   i, ix, iy;\n#if !defined DOFASTMATH\n  int   m, mp1, ns;\n  REAL  dtemp2, dtemp3;\n#endif\n  REAL  dtemp1;\n  int   n = *_n, incx = *_incx, incy = *_incy;\n\n  if (n <= 0) return;\n\n  dx--;\n  dy--;\n  ix = 1;\n  iy = 1;\n  if (incx < 0)\n    ix = (-n+1)*incx + 1;\n  if (incy < 0)\n    iy = (-n+1)*incy + 1;\n\n/* CPU intensive loop; option to do pointer arithmetic */\n#if defined DOFASTMATH\n  {\n    REAL *xptr, *yptr;\n    for (i = 1, xptr = dx + ix, yptr = dy + iy;\n         i <= n; i++, xptr += incx, yptr += incy) {\n      dtemp1 = (*xptr);\n     (*xptr) = (*yptr);\n     (*yptr) = dtemp1;\n    }\n    return;\n  }\n#else  \n\n  if (incx == incy) {\n    if (incx <= 0) goto x5;\n    if (incx == 1) goto x20;\n    goto x60;\n  }\n\n/* code for unequal or nonpositive increments. */\nx5:\n  for (i = 1; i<=n; i++) {\n     dtemp1 = dx[ix];\n     dx[ix] = dy[iy];\n     dy[iy] = dtemp1;\n     ix+= incx;\n     iy+= incy;\n  }\n  return;\n\n/* code for both increments equal to 1.\n   clean-up loop so remaining vector length is a multiple of 3. */\nx20:\n  m = n % 3;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++) {\n     dtemp1 = dx[i];\n     dx[i] = dy[i];\n     dy[i] = dtemp1;\n  }\n  if (n < 3) return;\n\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+3) {\n     dtemp1 = dx[i];\n     dtemp2 = dx[i+1];\n     dtemp3 = dx[i+2];\n     dx[i] = dy[i];\n     dx[i+1] = dy[i+1];\n     dx[i+2] = dy[i+2];\n     dy[i] = dtemp1;\n     dy[i+1] = dtemp2;\n     dy[i+2] = dtemp3;\n  }\n  return;\n\n/* code for equal, positive, non-unit increments. */\nx60:\n  ns = n*incx;\n  for (i = 1; i<=ns; i=i+incx) {\n     dtemp1 = dx[i];\n     dx[i] = dy[i];\n     dy[i] = dtemp1;\n  }\n#endif\n}\n\n\n/* ************************************************************************ */\n\nvoid dload(int n, REAL da, REAL *dx, int incx)\n{\n  dx++;\n  BLAS_dload (&n, &da, dx, &incx);\n}\n\nvoid BLAS_CALLMODEL my_dload (int *_n, REAL *_da, REAL *dx, int *_incx)\n{\n/* copies a scalar, a, to a vector, x.\n   uses unrolled loops when incx equals one.\n\n   To change the precision of this program, run the change\n   program on dload.f\n   Alternatively, to make a single precision version append a\n   comment character to the start of all lines between sequential\n      precision > double\n   and\n      end precision > double\n   comments and delete the comment character at the start of all\n   lines between sequential\n      precision > single\n   and\n      end precision > single\n   comments.  To make a double precision version interchange\n    the append and delete operations in these instructions. */\n\n  int    i, ix, m, mp1;\n  REAL   da = *_da;\n  int    n = *_n, incx = *_incx;\n\n  if (n<=0) return;\n  dx--;\n  if (incx==1) goto x20;\n\n/* code for incx not equal to 1 */\n\n  ix = 1;\n  if (incx<0)\n     ix = (-n+1)*incx + 1;\n  for (i = 1; i<=n; i++) {\n     dx[ix] = da;\n     ix+= incx;\n  }\n  return;\n\n/* code for incx equal to 1 and clean-up loop */\n\nx20:\n  m = n % 7;\n  if (m == 0) goto x40;\n  for (i = 1; i<=m; i++)\n     dx[i] = da;\n  if (n < 7) return;\n\nx40:\n  mp1 = m + 1;\n  for (i = mp1; i<=n; i=i+7) {\n     dx[i] = da;\n     dx[i + 1] = da;\n     dx[i + 2] = da;\n     dx[i + 3] = da;\n     dx[i + 4] = da;\n     dx[i + 5] = da;\n     dx[i + 6] = da;\n  }\n}\n\n/* ************************************************************************ */\nint idamax( int n, REAL *x, int is )\n{\n  x++;\n  return ( BLAS_idamax( &n, x, &is ) );\n}\n\nint BLAS_CALLMODEL my_idamax( int *_n, REAL *x, int *_is )\n{\n  register REAL xmax, xtest;\n  int    i, imax = 0;\n#if !defined DOFASTMATH\n  int    ii;\n#endif\n  int    n = *_n, is = *_is;\n\n  if((n < 1) || (is <= 0))\n    return(imax);\n  imax = 1;\n  if(n == 1)\n    return(imax);\n\n#if defined DOFASTMATH\n  xmax = fabs(*x);\n  for (i = 2, x += is; i <= n; i++, x += is) {\n    xtest = fabs(*x);\n    if(xtest > xmax) {\n      xmax = xtest;\n      imax = i;\n    }\n  }\n#else\n  x--;\n  ii = 1;\n  xmax = fabs(x[ii]);\n  for(i = 2, ii+ = is; i <= n; i++, ii+ = is) {\n    xtest = fabs(x[ii]);\n\t  if(xtest > xmax) {\n      xmax = xtest;\n\t\t  imax = i;\n    }\n  }\n#endif  \n  return(imax);\n}\n\n\n/* ************************************************************************ */\nREAL dnormi( int n, REAL *x )\n{\n  x++;\n  return( BLAS_dnormi( &n, x ) );\n}\n\nREAL BLAS_CALLMODEL my_dnormi( int *_n, REAL *x )\n{\n/* ===============================================================\n   dnormi  returns the infinity-norm of the vector x.\n   =============================================================== */\n   int      j;\n   register REAL hold, absval;\n   int      n = *_n;\n\n   x--;\n   hold = 0.0;\n/*   for(j = 1; j <= n; j++) */\n   for(j = n; j > 0; j--) {\n     absval = fabs(x[j]);\n     hold = MAX( hold, absval );\n   }\n\n   return( hold );\n}\n\n\n/* ************************************************************************ */\n/* Subvector and submatrix access routines (Fortran compatibility)          */\n/* ************************************************************************ */\n\n#ifndef UseMacroVector\nint  subvec( int item)\n{\n  return( item-1 );\n}\n#endif\n\nint submat( int nrowb, int row, int col)\n{\n  return( nrowb*(col-1) + subvec(row) );\n}\n\nint posmat( int nrowb, int row, int col)\n{\n  return( submat(nrowb, row, col)+BLAS_BASE );\n}\n\n/* ************************************************************************ */\n/* Randomization functions                                                  */\n/* ************************************************************************ */\n\nvoid randomseed(int seeds[])\n/* Simply create some default seed values */\n{\n  seeds[1] = 123456;\n  seeds[2] = 234567;\n  seeds[3] = 345678;\n}\n\nvoid randomdens( int n, REAL *x, REAL r1, REAL r2, REAL densty, int *seeds )\n{\n/* ------------------------------------------------------------------\n   random  generates a vector x[*] of random numbers\n   in the range (r1, r2) with (approximate) specified density.\n   seeds[*] must be initialized before the first call.\n   ------------------------------------------------------------------ */\n\n  int   i;\n  REAL  *y;\n\n  y = (REAL *) malloc(sizeof(*y) * (n+1));\n  ddrand( n, x, 1, seeds );\n  ddrand( n, y, 1, seeds );\n\n  for (i = 1; i<=n; i++) {\n     if (y[i] < densty)\n        x[i] = r1  +  (r2 - r1) * x[i];\n     else\n        x[i] = 0.0;\n  }\n  free(y);\n}\n\n\n/* ++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++ */\n\nvoid ddrand( int n, REAL *x, int incx, int *seeds )\n{\n\n/* ------------------------------------------------------------------\n   ddrand fills a vector x with uniformly distributed random numbers\n   in the interval (0, 1) using a method due to  Wichman and Hill.\n\n   seeds[1..3] should be set to integer values\n   between 1 and 30000 before the first entry.\n\n   Integer arithmetic up to 30323 is required.\n\n   Blatantly copied from Wichman and Hill 19-January-1987.\n   14-Feb-94. Original version.\n   30 Jun 1999. seeds stored in an array.\n   30 Jun 1999. This version of ddrand.\n   ------------------------------------------------------------------ */\n\n  int    ix, xix;\n\n  if (n < 1) return;\n\n  for (ix = 1; ix<=1+(n-1)*incx; ix=ix+incx) {\n     seeds[1]     = 171*(seeds[1] % 177) -  2*(seeds[1]/177);\n     seeds[2]     = 172*(seeds[2] % 176) - 35*(seeds[2]/176);\n     seeds[3]     = 170*(seeds[3] % 178) - 63*(seeds[3]/178);\n\n     if (seeds[1] < 0) seeds[1] = seeds[1] + 30269;\n     if (seeds[2] < 0) seeds[2] = seeds[2] + 30307;\n     if (seeds[3] < 0) seeds[3] = seeds[3] + 30323;\n\n\t x[ix]  = ((REAL) seeds[1])/30269.0 +\n             ((REAL) seeds[2])/30307.0 +\n             ((REAL) seeds[3])/30323.0;\n     xix    = (int) x[ix];\n\t x[ix]  = fabs(x[ix] - xix);\n   }\n\n}\n\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/shared/myblas.h",
    "content": "#ifndef HEADER_myblas\n#define HEADER_myblas\n\n/* ************************************************************************ */\n/* BLAS function interface with local and external loadable versions        */\n/* Author:  Kjell Eikland                                                   */\n/* Version: Initial version spring 2004                                     */\n/* Licence: LGPL                                                            */\n/* ************************************************************************ */\n/* Changes: 19 September 2004   Moved function pointer variable             */\n/*                              declarations from myblas.h to myblas.c      */\n/*                              to avoid linker problems with the Mac.      */\n/*          20 April 2005       Modified all double types to REAL to self-  */\n/*                              adjust to global settings.  Note that BLAS  */\n/*                              as of now does not have double double.      */\n/* ************************************************************************ */\n\n#define BLAS_BASE         1\n#define UseMacroVector\n#if defined LoadableBlasLib\n#  if LoadableBlasLib == 0\n#    undef LoadableBlasLib\n#  endif\n#else\n#  define LoadableBlasLib\n#endif\n\n\n/* ************************************************************************ */\n/* Include necessary libraries                                              */\n/* ************************************************************************ */\n#include \"commonlib.h\"\n#ifdef LoadableBlasLib\n  #ifdef WIN32\n    #include <windows.h>\n  #else\n    #include <dlfcn.h>\n  #endif\n#endif\n\n\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n\n\n/* ************************************************************************ */\n/* BLAS functions                                                           */\n/* ************************************************************************ */\n\n#ifndef BLAS_CALLMODEL\n#ifdef WIN32\n# define BLAS_CALLMODEL _cdecl\n#else\n# define BLAS_CALLMODEL\n#endif\n#endif\n\ntypedef void   (BLAS_CALLMODEL BLAS_dscal_func) (int *n, REAL *da, REAL *dx, int *incx);\ntypedef void   (BLAS_CALLMODEL BLAS_dcopy_func) (int *n, REAL *dx, int *incx,  REAL *dy, int *incy);\ntypedef void   (BLAS_CALLMODEL BLAS_daxpy_func) (int *n, REAL *da, REAL *dx, int *incx,  REAL *dy, int *incy);\ntypedef void   (BLAS_CALLMODEL BLAS_dswap_func) (int *n, REAL *dx, int *incx,  REAL *dy, int *incy);\ntypedef double (BLAS_CALLMODEL BLAS_ddot_func)  (int *n, REAL *dx, int *incx,  REAL *dy, int *incy);\ntypedef int    (BLAS_CALLMODEL BLAS_idamax_func)(int *n, REAL *x,  int *is);\ntypedef void   (BLAS_CALLMODEL BLAS_dload_func) (int *n, REAL *da, REAL *dx, int *incx);\ntypedef double (BLAS_CALLMODEL BLAS_dnormi_func)(int *n, REAL *x);\n\n#ifndef __WINAPI\n# ifdef WIN32\n#  define __WINAPI WINAPI\n# else\n#  define __WINAPI\n# endif\n#endif\n\nvoid init_BLAS(void);\nMYBOOL is_nativeBLAS(void);\nMYBOOL load_BLAS(char *libname);\nMYBOOL unload_BLAS(void);\n\n/* ************************************************************************ */\n/* User-callable BLAS definitions (C base 1)                                */\n/* ************************************************************************ */\nvoid dscal ( int n, REAL da,  REAL *dx, int incx );\nvoid dcopy ( int n, REAL *dx, int incx, REAL *dy, int incy );\nvoid daxpy ( int n, REAL da,  REAL *dx, int incx,   REAL *dy, int incy );\nvoid dswap ( int n, REAL *dx, int incx, REAL *dy, int incy );\nREAL ddot  ( int n, REAL *dx, int incx, REAL *dy, int incy );\nint  idamax( int n, REAL *x,  int is );\nvoid dload ( int n, REAL da,  REAL *dx, int incx );\nREAL dnormi( int n, REAL *x );\n\n\n/* ************************************************************************ */\n/* Locally implemented BLAS functions (C base 0)                            */\n/* ************************************************************************ */\nvoid BLAS_CALLMODEL my_dscal ( int *n, REAL *da, REAL *dx,  int *incx );\nvoid BLAS_CALLMODEL my_dcopy ( int *n, REAL *dx, int *incx, REAL *dy, int *incy );\nvoid BLAS_CALLMODEL my_daxpy ( int *n, REAL *da, REAL *dx,  int *incx,  REAL *dy, int *incy );\nvoid BLAS_CALLMODEL my_dswap ( int *n, REAL *dx, int *incx, REAL *dy, int *incy );\nREAL BLAS_CALLMODEL my_ddot  ( int *n, REAL *dx, int *incx,  REAL *dy, int *incy );\nint  BLAS_CALLMODEL my_idamax( int *n, REAL *x,  int *is );\nvoid BLAS_CALLMODEL my_dload ( int *n, REAL *da, REAL *dx, int *incx );\nREAL BLAS_CALLMODEL my_dnormi( int *n, REAL *x );\n\n\n/* ************************************************************************ */\n/* Subvector and submatrix access routines (Fortran compatibility)          */\n/* ************************************************************************ */\n#ifdef UseMacroVector\n  #define subvec(item) (item - 1)\n#else\n  int subvec( int item );\n#endif\n\nint submat( int nrowb, int row, int col );\nint posmat( int nrowb, int row, int col );\n\n\n/* ************************************************************************ */\n/* Randomization functions                                                  */\n/* ************************************************************************ */\nvoid randomseed(int *seeds);\nvoid randomdens( int n, REAL *x, REAL r1, REAL r2, REAL densty, int *seeds);\nvoid ddrand( int n, REAL *x, int incx, int *seeds );\n\n\n#ifdef __cplusplus\n}\n#endif\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/ufortify.h",
    "content": "/*\n * FILE:\n *   ufortify.h\n *\n * DESCRIPTION:\n *   User options for fortify. Changes to this file require fortify.c to be\n * recompiled, but nothing else.\n */\n\n#ifndef __UFORTIFY_H__\n#define __UFORTIFY_H__\n\n#define FORTIFY_STORAGE\n\n#if defined MSDOS || defined __BORLANDC__ || defined __HIGHC__\n# define KNOWS_POINTER_TYPE\n#endif\n\n#define FORTIFY_WAIT_FOR_KEY         /* Pause after message            */\n\n#if !defined FORTIFY_BEFORE_SIZE\n# define FORTIFY_BEFORE_SIZE     16  /* Bytes to allocate before block */\n#endif\n\n#if !defined FORTIFY_BEFORE_VALUE\n# define FORTIFY_BEFORE_VALUE  0xA3  /* Fill value before block        */\n#endif\n\n#if !defined FORTIFY_AFTER_SIZE\n# define FORTIFY_AFTER_SIZE      16  /* Bytes to allocate after block  */\n#endif\n\n#if !defined FORTIFY_AFTER_VALUE\n# define FORTIFY_AFTER_VALUE   0xA5  /* Fill value after block         */\n#endif\n\n#define FILL_ON_MALLOC               /* Nuke out malloc'd memory       */\n\n#if !defined FILL_ON_MALLOC_VALUE\n# define FILL_ON_MALLOC_VALUE  0xA7  /* Value to initialize with       */\n#endif\n\n#define FILL_ON_FREE                 /* free'd memory is cleared       */\n\n#if !defined FILL_ON_FREE_VALUE\n# define FILL_ON_FREE_VALUE    0xA9  /* Value to de-initialize with    */\n#endif\n\n#define FORTIFY_CheckInterval 1      /* seconds */\n/* #define CHECK_ALL_MEMORY_ON_MALLOC */\n#define CHECK_ALL_MEMORY_ON_FREE\n#define PARANOID_FREE\n\n#define WARN_ON_MALLOC_FAIL    /* A debug is issued on a failed malloc */\n#define WARN_ON_ZERO_MALLOC    /* A debug is issued on a malloc(0)     */\n#define WARN_ON_FALSE_FAIL     /* See Fortify_SetMallocFailRate        */\n#define WARN_ON_SIZE_T_OVERFLOW/* Watch for breaking the 64K limit in  */\n                               /* some braindead architectures...      */\n\n#define FORTIFY_LOCK()\n#define FORTIFY_UNLOCK()\n\n#endif\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/yacc_read.c",
    "content": "/*\n   ============================================================================\n   NAME : yacc_read.c\n\n   PURPOSE : translation of lp-problem and storage in sparse matrix\n\n   SHORT : Subroutines for yacc program to store the input in an intermediate\n   data-structure. The yacc and lex programs translate the input.  First the\n   problemsize is determined and the date is read into an intermediate\n   structure, then readinput fills the sparse matrix.\n\n   USAGE : call yyparse(); to start reading the input.  call readinput(); to\n   fill the sparse matrix.\n   ============================================================================\n   Rows : contains the amount of rows + 1. Rows-1 is the amount of constraints\n   (no bounds) Rows also contains the rownr 0 which is the objective function\n\n   Columns : contains the amount of columns (different variable names found in\n   the constraints)\n\n   Nonnuls : contains the amount of nonnuls = sum of different entries of all\n   columns in the constraints and in the objectfunction\n\n   Hash_tab : contains all columnnames on the first level of the structure the\n   row information is kept under each column structure in a linked list (also\n   the objective funtion is in this structure) Bound information is also\n   stored under under the column name\n\n   First_rside : points to a linked list containing all relational operators\n   and the righthandside values of the constraints the linked list is in\n   reversed order with respect to the rownumbers\n   ============================================================================ */\n#include <string.h>\n#include <limits.h>\n#include <setjmp.h>\n#include \"lpkit.h\"\n#include \"yacc_read.h\"\n\n#ifdef FORTIFY\n# include \"lp_fortify.h\"\n#endif\n\n#define tol 1.0e-10\n#define coldatastep 100\n\n#define HASHSIZE       10007  /* A prime number! */\n\nstruct structSOSvars {\n  char                 *name;\n  int                  col;\n  REAL                 weight;\n  struct structSOSvars *next;\n};\n\nstruct structSOS {\n  char                 *name;\n  short                type;\n  int                  Nvars;\n  int                  weight;\n  struct structSOSvars *SOSvars, *LastSOSvars;\n  struct structSOS     *next;\n};\n\nstruct SOSrow {\n  int  col;\n  REAL value;\n  struct SOSrow *next;\n};\n\nstruct SOSrowdata {\n  short type;\n  char *name;\n  struct SOSrow *SOSrow;\n};\n\nstruct rside /* contains relational operator and rhs value */\n{\n  int           row;\n  REAL          value;\n  REAL          range_value;\n  struct rside  *next;\n  short         relat;\n  short         range_relat;\n  char          negate;\n  short         SOStype;\n};\n\nstruct column\n{\n  int            row;\n  REAL           value;\n  struct  column *next;\n  struct  column *prev;\n};\n\nstruct structcoldata {\n  int               must_be_int;\n  int               must_be_sec;\n  int               must_be_free;\n  REAL              upbo;\n  REAL              lowbo;\n  struct  column   *firstcol;\n  struct  column   *col;\n};\n\nstatic void error(parse_parm *pp, int verbose, char *string)\n{\n  if(pp == NULL)\n    report(NULL, CRITICAL, string);\n  else if(pp->Verbose >= verbose)\n    report(NULL, verbose, \"%s on line %d\\n\", string, pp->lineno);\n}\n\n/*\n * error handling routine for yyparse()\n */\nvoid read_error(parse_parm *pp, void *scanner, char *string)\n{\n  error(pp, CRITICAL, string);\n}\n\n/* called when lex gets a fatal error */\nvoid lex_fatal_error(parse_parm *pp, void *scanner, char *msg)\n{\n  read_error(pp, scanner, msg);\n  longjmp(pp->jump_buf, 1);\n}\n\nvoid add_row(parse_parm *pp)\n{\n  pp->Rows++;\n  pp->rs = NULL;\n  pp->Lin_term_count = 0;\n}\n\nvoid add_sos_row(parse_parm *pp, short SOStype)\n{\n  if (pp->rs != NULL)\n    pp->rs->SOStype = SOStype;\n  pp->Rows++;\n  pp->rs = NULL;\n  pp->Lin_term_count = 0;\n}\n\nvoid check_int_sec_sos_free_decl(parse_parm *pp, int within_int_decl, int within_sec_decl, int sos_decl0, int within_free_decl)\n{\n  pp->Ignore_int_decl = TRUE;\n  pp->Ignore_sec_decl = TRUE;\n  pp->Ignore_free_decl = TRUE;\n  pp->sos_decl = 0;\n  if(within_int_decl) {\n    pp->Ignore_int_decl = FALSE;\n    pp->int_decl = (char) within_int_decl;\n    if(within_sec_decl)\n      pp->Ignore_sec_decl = FALSE;\n  }\n  else if(within_sec_decl) {\n    pp->Ignore_sec_decl = FALSE;\n  }\n  else if(sos_decl0) {\n    pp->sos_decl = (char) sos_decl0;\n  }\n  else if(within_free_decl) {\n    pp->Ignore_free_decl = FALSE;\n  }\n}\n\nstatic void add_int_var(parse_parm *pp, char *name, short int_decl)\n{\n  hashelem *hp;\n\n  if((hp = findhash(name, pp->Hash_tab)) == NULL) {\n    char buf[256];\n\n    sprintf(buf, \"Unknown variable %s declared integer, ignored\", name);\n    error(pp, NORMAL, buf);\n  }\n  else if(pp->coldata[hp->index].must_be_int) {\n    char buf[256];\n\n    sprintf(buf, \"Variable %s declared integer more than once, ignored\", name);\n    error(pp, NORMAL, buf);\n  }\n  else {\n    pp->coldata[hp->index].must_be_int = TRUE;\n    if(int_decl == 2) {\n      if(pp->coldata[hp->index].lowbo != -DEF_INFINITE * (REAL) 10.0) {\n        char buf[256];\n\n        sprintf(buf, \"Variable %s: lower bound on variable redefined\", name);\n        error(pp, NORMAL, buf);\n      }\n      pp->coldata[hp->index].lowbo = 0;\n      if(pp->coldata[hp->index].upbo < DEF_INFINITE) {\n        char buf[256];\n\n        sprintf(buf, \"Variable %s: upper bound on variable redefined\", name);\n        error(pp, NORMAL, buf);\n      }\n      pp->coldata[hp->index].upbo = 1;\n    }\n    else if(int_decl == 3) {\n      if(pp->coldata[hp->index].upbo == DEF_INFINITE * (REAL) 10.0)\n        pp->coldata[hp->index].upbo = 1.0;\n    }\n  }\n}\n\nstatic void add_sec_var(parse_parm *pp, char *name)\n{\n  hashelem *hp;\n\n  if((hp = findhash(name, pp->Hash_tab)) == NULL) {\n    char buf[256];\n\n    sprintf(buf, \"Unknown variable %s declared semi-continuous, ignored\", name);\n    error(pp, NORMAL, buf);\n  }\n  else if(pp->coldata[hp->index].must_be_sec) {\n    char buf[256];\n\n    sprintf(buf, \"Variable %s declared semi-continuous more than once, ignored\", name);\n    error(pp, NORMAL, buf);\n  }\n  else\n    pp->coldata[hp->index].must_be_sec = TRUE;\n}\n\nint set_sec_threshold(parse_parm *pp, char *name, REAL threshold)\n{\n  hashelem *hp;\n\n  if((hp = findhash(name, pp->Hash_tab)) == NULL) {\n    char buf[256];\n\n    sprintf(buf, \"Unknown variable %s declared semi-continuous, ignored\", name);\n    error(pp, NORMAL, buf);\n    return(FALSE);\n  }\n\n  if ((pp->coldata[hp->index].lowbo > 0.0) && (threshold > 0.0)) {\n    char buf[256];\n\n    pp->coldata[hp->index].must_be_sec = FALSE;\n    sprintf(buf, \"Variable %s declared semi-continuous, but it has a non-negative lower bound (%f), ignored\", name, pp->coldata[hp->index].lowbo);\n    error(pp, NORMAL, buf);\n  }\n  if (threshold > pp->coldata[hp->index].lowbo)\n    pp->coldata[hp->index].lowbo = threshold;\n\n  return(pp->coldata[hp->index].must_be_sec);\n}\n\nstatic void add_free_var(parse_parm *pp, char *name)\n{\n  hashelem *hp;\n\n  if((hp = findhash(name, pp->Hash_tab)) == NULL) {\n    char buf[256];\n\n    sprintf(buf, \"Unknown variable %s declared free, ignored\", name);\n    error(pp, NORMAL, buf);\n  }\n  else if(pp->coldata[hp->index].must_be_free) {\n    char buf[256];\n\n    sprintf(buf, \"Variable %s declared free more than once, ignored\", name);\n    error(pp, NORMAL, buf);\n  }\n  else\n    pp->coldata[hp->index].must_be_free = TRUE;\n}\n\nstatic int add_sos_name(parse_parm *pp, char *name)\n{\n  struct structSOS *SOS;\n\n  if(CALLOC(SOS, 1, struct structSOS) == NULL)\n    return(FALSE);\n\n  if(MALLOC(SOS->name, strlen(name) + 1, char) == NULL)\n  {\n    FREE(SOS);\n    return(FALSE);\n  }\n  strcpy(SOS->name, name);\n  SOS->type = 0;\n\n  if(pp->FirstSOS == NULL)\n    pp->FirstSOS = SOS;\n  else\n    pp->LastSOS->next = SOS;\n  pp->LastSOS = SOS;\n\n  return(TRUE);\n}\n\nstatic int add_sos_var(parse_parm *pp, char *name)\n{\n  struct structSOSvars *SOSvar;\n\n  if(name != NULL) {\n    if(CALLOC(SOSvar, 1, struct structSOSvars) == NULL)\n      return(FALSE);\n\n    if(MALLOC(SOSvar->name, strlen(name) + 1, char) == NULL)\n    {\n      FREE(SOSvar);\n      return(FALSE);\n    }\n    strcpy(SOSvar->name, name);\n\n    if(pp->LastSOS->SOSvars == NULL)\n      pp->LastSOS->SOSvars = SOSvar;\n    else\n      pp->LastSOS->LastSOSvars->next = SOSvar;\n    pp->LastSOS->LastSOSvars = SOSvar;\n    pp->LastSOS->Nvars = pp->LastSOS->Nvars + 1;\n  }\n  pp->LastSOS->LastSOSvars->weight = 0;\n\n  return(TRUE);\n}\n\nvoid storevarandweight(parse_parm *pp, char *name)\n{\n  if(!pp->Ignore_int_decl) {\n    add_int_var(pp, name, pp->int_decl);\n    if(!pp->Ignore_sec_decl)\n      add_sec_var(pp, name);\n  }\n  else if(!pp->Ignore_sec_decl)\n    add_sec_var(pp, name);\n  else if(pp->sos_decl==1)\n    add_sos_name(pp, name);\n  else if(pp->sos_decl==2)\n    add_sos_var(pp, name);\n  else if(!pp->Ignore_free_decl)\n    add_free_var(pp, name);\n}\n\nint set_sos_type(parse_parm *pp, int SOStype)\n{\n  if(pp->LastSOS != NULL)\n    pp->LastSOS->type = (short) SOStype;\n  return(TRUE);\n}\n\nint set_sos_weight(parse_parm *pp, double weight, int sos_decl)\n{\n  if(pp->LastSOS != NULL) {\n    if(sos_decl==1)\n      pp->LastSOS->weight = (int) (weight+.1);\n    else\n      pp->LastSOS->LastSOSvars->weight = weight;\n  }\n  return(TRUE);\n}\n\nstatic int inccoldata(parse_parm *pp)\n{\n  long Columns = pp->Columns;\n\n  if(Columns == 0)\n    CALLOC(pp->coldata, coldatastep, struct structcoldata);\n  else if((Columns%coldatastep) == 0)\n    REALLOC(pp->coldata, Columns + coldatastep, struct structcoldata);\n\n  if(pp->coldata != NULL) {\n    pp->coldata[Columns].upbo = (REAL) DEF_INFINITE * (REAL) 10.0;\n    pp->coldata[Columns].lowbo = (REAL) -DEF_INFINITE * (REAL) 10.0; /* temporary. If still this value then 0 will be taken */\n    pp->coldata[Columns].col = NULL;\n    pp->coldata[Columns].firstcol = NULL;\n    pp->coldata[Columns].must_be_int = FALSE;\n    pp->coldata[Columns].must_be_sec = FALSE;\n    pp->coldata[Columns].must_be_free = FALSE;\n  }\n\n  return(pp->coldata != NULL);\n}\n\n/*\n * initialisation of hashstruct and globals.\n */\nstatic int init_read(parse_parm *pp, int verbose)\n{\n  int ok = FALSE;\n\n  pp->Verbose = verbose;\n  set_obj_dir(pp, TRUE);\n  pp->Rows = 0;\n  pp->Non_zeros = 0;\n  pp->Columns = 0;\n  pp->FirstSOS = pp->LastSOS = NULL;\n  pp->Lin_term_count = 0;\n  if (CALLOC(pp->First_rside, 1, struct rside) != NULL) {\n    pp->rs = pp->First_rside;\n    pp->rs->value = pp->rs->range_value = 0;\n    /* first row (nr 0) is always the objective function */\n    pp->rs->relat = OF;\n    pp->rs->range_relat = -1;\n    pp->rs->SOStype = 0;\n    pp->Hash_tab = NULL;\n    pp->Hash_constraints = NULL;\n    if (((pp->Hash_tab = create_hash_table(HASHSIZE, 0)) == NULL) ||\n        ((pp->Hash_constraints = create_hash_table(HASHSIZE, 0)) == NULL)){\n      FREE(pp->First_rside);\n      FREE(pp->Hash_tab);\n      FREE(pp->Hash_constraints);\n    }\n    else\n      ok = TRUE;\n  }\n  return(ok);\n} /* init */\n\n/*\n * clears the tmp_store variable after all information has been copied\n */\nvoid null_tmp_store(parse_parm *pp, int init_Lin_term_count)\n{\n  pp->tmp_store.value = 0;\n  pp->tmp_store.rhs_value = 0;\n  FREE(pp->tmp_store.name);\n  if(init_Lin_term_count)\n    pp->Lin_term_count = 0;\n}\n\n/*\n * variable : pointer to text array with name of variable\n * row      : the rownumber of the constraint\n * value    : value of matrixelement\n *            A(row, variable).\n * Sign     : (global)  determines the sign of value.\n * store()  : stores value in matrix\n *            A(row, variable). If A(row, variable) already contains data,\n *            value is added to the existing value.\n */\nstatic int store(parse_parm *pp, char *variable,\n                 int row,\n                 REAL value)\n{\n  hashelem *h_tab_p;\n  struct column *col_p;\n\n  if(value == 0) {\n    char buf[256];\n\n    sprintf(buf, \"(store) Warning, variable %s has an effective coefficient of 0, Ignored\", variable);\n    error(pp, NORMAL, buf);\n    /* return(TRUE); */\n  }\n\n  if((h_tab_p = findhash(variable, pp->Hash_tab)) == NULL) {\n    if (((h_tab_p = puthash(variable, pp->Columns, NULL, pp->Hash_tab)) == NULL)\n       ) return(FALSE);\n    inccoldata(pp);\n    pp->Columns++; /* counter for calloc of final array */\n    if(value) {\n      if (CALLOC(col_p, 1, struct column) == NULL)\n        return(FALSE);\n      pp->Non_zeros++; /* for calloc of final arrays */\n      col_p->row = row;\n      col_p->value = value;\n      pp->coldata[h_tab_p->index].firstcol = pp->coldata[h_tab_p->index].col = col_p;\n    }\n  }\n  else if((pp->coldata[h_tab_p->index].col == NULL) || (pp->coldata[h_tab_p->index].col->row != row)) {\n    if(value) {\n      if (CALLOC(col_p, 1, struct column) == NULL)\n        return(FALSE);\n      pp->Non_zeros++; /* for calloc of final arrays */\n      if(pp->coldata[h_tab_p->index].col != NULL)\n        pp->coldata[h_tab_p->index].col->prev = col_p;\n      else\n        pp->coldata[h_tab_p->index].firstcol = col_p;\n      col_p->value = value;\n      col_p->row = row;\n      col_p->next = pp->coldata[h_tab_p->index].col;\n      pp->coldata[h_tab_p->index].col = col_p;\n    }\n  }\n  else if(value) {\n    pp->coldata[h_tab_p->index].col->value += value;\n    if(fabs(pp->coldata[h_tab_p->index].col->value) < tol) /* eliminitate rounding errors */\n      pp->coldata[h_tab_p->index].col->value = 0;\n  }\n  return(TRUE);\n} /* store */\n\nstatic int storefirst(parse_parm *pp)\n{\n    struct rside *rp;\n\n    if ((pp->rs != NULL) && (pp->rs->row == pp->tmp_store.row))\n      return(TRUE);\n\n    /* make space for the rhs information */\n    if (CALLOC(rp, 1, struct rside) == NULL)\n      return(FALSE);\n    rp->next = pp->First_rside;\n    pp->First_rside = pp->rs = rp;\n    pp->rs->row = /* row */ pp->tmp_store.row;\n    pp->rs->value = pp->tmp_store.rhs_value;\n    pp->rs->relat = pp->tmp_store.relat;\n    pp->rs->range_relat = -1;\n    pp->rs->SOStype = 0;\n\n    if(pp->tmp_store.name != NULL) {\n      if(pp->tmp_store.value != 0) {\n        if (!store(pp, pp->tmp_store.name, pp->tmp_store.row, pp->tmp_store.value))\n          return(FALSE);\n      }\n      else {\n        char buf[256];\n\n        sprintf(buf, \"Warning, variable %s has an effective coefficient of 0, ignored\", pp->tmp_store.name);\n        error(pp, NORMAL, buf);\n      }\n    }\n    null_tmp_store(pp, FALSE);\n    return(TRUE);\n}\n\n/*\n * store relational operator given in yylex[0] in the rightside list.\n * Also checks if it constraint was a bound and if so stores it in the\n * boundslist\n */\nint store_re_op(parse_parm *pp, char OP, int HadConstraint, int HadVar, int Had_lineair_sum)\n{\n  short tmp_relat;\n\n  switch(OP) {\n\n  case '=':\n    tmp_relat = EQ;\n    break;\n\n  case '>':\n    tmp_relat = GE;\n    break;\n\n  case '<':\n    tmp_relat = LE;\n    break;\n\n  case 0:\n    if(pp->rs != NULL)\n      tmp_relat = pp->rs->relat;\n    else\n      tmp_relat = pp->tmp_store.relat;\n    break;\n\n  default:\n    {\n      char buf[256];\n\n      sprintf(buf, \"Error: unknown relational operator %c\", OP);\n      error(pp, CRITICAL, buf);\n    }\n    return(FALSE);\n    break;\n  }\n\n  if(/* pp->Lin_term_count > 1 */ HadConstraint && HadVar) {/* it is not a bound */\n    if(pp->Lin_term_count <= 1)\n      if(!storefirst(pp))\n        return(FALSE);\n    pp->rs->relat = tmp_relat;\n  }\n  else if(/* pp->Lin_term_count == 0 */ HadConstraint && !Had_lineair_sum /* HadVar */ /* && (pp->rs != NULL) */) { /* it is a range */\n    if(pp->Lin_term_count == 1)\n      if(!storefirst(pp))\n        return(FALSE);\n    if(pp->rs == NULL) { /* range before row, already reported */\n      error(pp, CRITICAL, \"Error: range for undefined row\");\n      return(FALSE);\n    }\n\n    if(pp->rs->negate)\n      switch (tmp_relat) {\n      case LE:\n        tmp_relat = GE;\n        break;\n      case GE:\n        tmp_relat = LE;\n        break;\n      }\n\n    if(pp->rs->range_relat != -1) {\n      error(pp, CRITICAL, \"Error: There was already a range for this row\");\n      return(FALSE);\n    }\n    else if(tmp_relat == pp->rs->relat) {\n      error(pp, CRITICAL, \"Error: relational operator for range is the same as relation operator for equation\");\n      return(FALSE);\n    }\n    else\n      pp->rs->range_relat = tmp_relat;\n  }\n  else /* could be a bound */\n    pp->tmp_store.relat = tmp_relat;\n\n  return(TRUE);\n} /* store_re_op */\n\nint negate_constraint(parse_parm *pp)\n{\n    if(pp->rs != NULL)\n      pp->rs->negate = TRUE;\n\n    return(TRUE);\n}\n\n/*\n * store RHS value in the rightside structure\n * if type = true then\n */\nint rhs_store(parse_parm *pp, REAL value, int HadConstraint, int HadVar, int Had_lineair_sum)\n{\n  if(/* pp->Lin_term_count > 1 */ (HadConstraint && HadVar) || (pp->Rows == 0)){ /* not a bound */\n    if (pp->Rows == 0)\n      value = -value;\n    /* if(pp->Lin_term_count < 2) */\n    if(pp->rs == NULL)\n      pp->tmp_store.rhs_value += value;\n    else\n\n    if(pp->rs == NULL) {\n      error(pp, CRITICAL, \"Error: No variable specified\");\n      return(FALSE);\n    }\n    else\n      pp->rs->value += value;\n  }\n  else if(/* pp->Lin_term_count == 0 */ HadConstraint && !HadVar) { /* a range */\n    if(pp->rs == NULL) /* if range before row, already reported */\n      pp->tmp_store.rhs_value += value;\n    else if(pp->rs->range_relat < 0) /* was a bad range; ignore */;\n    else {\n      if(pp->rs->negate)\n        value = -value;\n      if(((pp->rs->relat == LE) && (pp->rs->range_relat == GE) &&\n         (pp->rs->value < value)) ||\n        ((pp->rs->relat == GE) && (pp->rs->range_relat == LE) &&\n         (pp->rs->value > value)) ||\n        ((pp->rs->relat == EQ) || (pp->rs->range_relat == EQ))) {\n        pp->rs->range_relat = -2;\n        error(pp, CRITICAL, \"Error: range restriction conflicts\");\n        return(FALSE);\n      }\n      else\n        pp->rs->range_value += value;\n    }\n  }\n  else /* a bound */\n    pp->tmp_store.rhs_value += value;\n  return(TRUE);\n} /* RHS_store */\n\n/*\n * store all data in the right place\n * count the amount of lineair terms in a constraint\n * only store in data-structure if the constraint is not a bound\n */\nint var_store(parse_parm *pp, char *var, REAL value, int HadConstraint, int HadVar, int Had_lineair_sum)\n{\n  int row;\n\n  row = pp->Rows;\n\n  /* also in a bound the same var name can occur more than once. Check for\n     this. Don't increment Lin_term_count */\n\n  if(pp->Lin_term_count != 1 || pp->tmp_store.name == NULL || strcmp(pp->tmp_store.name, var) != 0)\n    pp->Lin_term_count++;\n\n  /* always store objective function with rownr == 0. */\n  if(row == 0)\n    return(store(pp, var,  row,  value));\n\n  if(pp->Lin_term_count == 1) { /* don't store yet. could be a bound */\n    if(MALLOC(pp->tmp_store.name, strlen(var) + 1, char) != NULL)\n      strcpy(pp->tmp_store.name, var);\n    pp->tmp_store.row = row;\n    pp->tmp_store.value += value;\n    return(TRUE);\n  }\n\n  if(pp->Lin_term_count == 2) { /* now you can also store the first variable */\n    if(!storefirst(pp))\n      return(FALSE);\n    /* null_tmp_store(pp, FALSE); */\n  }\n\n  return(store(pp, var, row, value));\n} /* var_store */\n\n\n\n/*\n * store the information in tmp_store because it is a bound\n */\nint store_bounds(parse_parm *pp, int warn)\n{\n  if(pp->tmp_store.value != 0) {\n    hashelem *h_tab_p;\n    REAL boundvalue;\n\n    if((h_tab_p = findhash(pp->tmp_store.name, pp->Hash_tab)) == NULL) {\n      /* a new columnname is found, create an entry in the hashlist */\n      if ((h_tab_p = puthash(pp->tmp_store.name, pp->Columns, NULL, pp->Hash_tab)) == NULL) {\n        error(pp, CRITICAL, \"Not enough memory\");\n        return(FALSE);\n      }\n      inccoldata(pp);\n      pp->Columns++; /* counter for calloc of final array */\n    }\n\n    if(pp->tmp_store.value < 0) { /* divide by negative number, */\n      /* relational operator may change */\n      if(pp->tmp_store.relat == GE)\n        pp->tmp_store.relat = LE;\n      else if(pp->tmp_store.relat == LE)\n        pp->tmp_store.relat = GE;\n    }\n\n    boundvalue = pp->tmp_store.rhs_value / pp->tmp_store.value;\n\n#if FALSE\n    /* Check sanity of bound; all variables should be positive */\n    if(   ((pp->tmp_store.relat == EQ) && (boundvalue < 0))\n       || ((pp->tmp_store.relat == LE) && (boundvalue < 0))) { /* Error */\n      error(pp, CRITICAL, \"Error: variables must always be non-negative\");\n      return(FALSE);\n    }\n#endif\n\n#if FALSE\n    if((pp->tmp_store.relat == GE) && (boundvalue <= 0)) /* Warning */\n      error(pp, NORMAL, \"Warning: useless bound; variables are always >= 0\");\n#endif\n\n    /* bound seems to be sane, add it */\n    if((pp->tmp_store.relat == GE) || (pp->tmp_store.relat == EQ)) {\n      if(boundvalue > pp->coldata[h_tab_p->index].lowbo - tol)\n        pp->coldata[h_tab_p->index].lowbo = boundvalue;\n      else if(warn)\n        error(pp, NORMAL, \"Ineffective lower bound, ignored\");\n    }\n    if((pp->tmp_store.relat == LE) || (pp->tmp_store.relat == EQ)) {\n      if(boundvalue < pp->coldata[h_tab_p->index].upbo + tol)\n        pp->coldata[h_tab_p->index].upbo  = boundvalue;\n      else if (warn)\n        error(pp, NORMAL, \"Ineffective upper bound, ignored\");\n    }\n\n    /* check for empty range */\n    if((warn) && (pp->coldata[h_tab_p->index].upbo + tol < pp->coldata[h_tab_p->index].lowbo)) {\n      error(pp, CRITICAL, \"Error: bound contradicts earlier bounds\");\n      return(FALSE);\n    }\n  }\n  else /* pp->tmp_store.value = 0 ! */ {\n    char buf[256];\n\n    if((pp->tmp_store.rhs_value == 0) ||\n       ((pp->tmp_store.rhs_value > 0) && (pp->tmp_store.relat == LE)) ||\n       ((pp->tmp_store.rhs_value < 0) && (pp->tmp_store.relat == GE))) {\n      sprintf(buf, \"Variable %s has an effective coefficient of 0 in bound, ignored\",\n              pp->tmp_store.name);\n      if(warn)\n        error(pp, NORMAL, buf);\n    }\n    else {\n      sprintf(buf, \"Error, variable %s has an effective coefficient of 0 in bound\",\n              pp->tmp_store.name);\n      error(pp, CRITICAL, buf);\n      return(FALSE);\n    }\n  }\n\n  /* null_tmp_store(pp, FALSE); */\n  pp->tmp_store.rhs_value = 0;\n\n  return(TRUE);\n} /* store_bounds */\n\nint set_title(parse_parm *pp, char *name)\n{\n  pp->title = strdup(name);\n  return(TRUE);\n}\n\nint add_constraint_name(parse_parm *pp, char *name)\n{\n  int row;\n  hashelem *hp;\n\n  if((hp = findhash(name, pp->Hash_constraints)) != NULL) {\n    row = hp->index;\n    pp->rs = pp->First_rside;\n    while ((pp->rs != NULL) && (pp->rs->row != row))\n      pp->rs = pp->rs->next;\n  }\n  else {\n    row = pp->Rows;\n    if (((hp = puthash(name, row, NULL, pp->Hash_constraints)) == NULL)\n       ) return(FALSE);\n    if(row)\n      pp->rs = NULL;\n  }\n\n  return(TRUE);\n}\n\n/*\n * transport the data from the intermediate structure to the sparse matrix\n * and free the intermediate structure\n */\nstatic int readinput(parse_parm *pp, lprec *lp)\n{\n  int    i, i1, count, index, col;\n  struct column *cp, *tcp;\n  hashelem *hp;\n  struct rside *rp;\n  signed char *negateAndSOS = NULL;\n  REAL *row = NULL, a;\n  int *rowno = NULL;\n  MYBOOL SOSinMatrix = FALSE;\n  struct SOSrowdata *SOSrowdata = NULL;\n  struct SOSrow *SOSrow, *SOSrow1;\n\n  if(lp != NULL) {\n    if (CALLOC(negateAndSOS, 1 + pp->Rows, signed char) == NULL)\n      return(FALSE);\n\n    rp = pp->First_rside;\n    for(i = pp->Rows; (i >= 0) && (rp != NULL); i--) {\n      if(rp->SOStype == 0)\n        negateAndSOS[i] = (rp->negate ? -1 : 0);\n      else\n        negateAndSOS[i] = (signed char) rp->SOStype;\n\n      rp = rp->next;\n    }\n\n    /* fill names with the rownames */\n    hp = pp->Hash_constraints->first;\n    while(hp != NULL) {\n      if (/* (negateAndSOS[hp->index] <= 0) && */ (!set_row_name(lp, hp->index, hp->name)))\n        return(FALSE);\n      hp = hp->nextelem;\n    }\n  }\n\n  for(i = pp->Rows; i >= 0; i--) {\n    rp = pp->First_rside;\n    if((lp != NULL) && (rp != NULL)) {\n      if(rp->SOStype == 0) {\n        if (rp->negate) {\n          switch (rp->relat) {\n          case LE:\n            rp->relat = GE;\n            break;\n          case GE:\n            rp->relat = LE;\n            break;\n          }\n          switch (rp->range_relat) {\n          case LE:\n            rp->range_relat = GE;\n            break;\n          case GE:\n            rp->range_relat = LE;\n            break;\n          }\n          rp->range_value = -rp->range_value;\n          rp->value = -rp->value;\n        }\n\n        if((rp->range_relat >= 0) && (rp->value == lp->infinite)) {\n          rp->value = rp->range_value;\n          rp->relat = rp->range_relat;\n          rp->range_relat = -1;\n        }\n        else if((rp->range_relat >= 0) && (rp->value == -lp->infinite)) {\n          rp->value = rp->range_value;\n          rp->relat = rp->range_relat;\n          rp->range_relat = -1;\n        }\n        if ((rp->range_relat >= 0) && (rp->range_value == rp->value)) {\n          rp->relat = EQ;\n          rp->range_relat = EQ;\n        }\n        if(i) {\n          set_constr_type(lp, i, rp->relat);\n          pp->relat[i] = rp->relat;\n        }\n        set_rh(lp, i, rp->value);\n        if (rp->range_relat >= 0)\n          set_rh_range(lp, i, rp->range_value - rp->value);\n      }\n      else {\n        SOSinMatrix = TRUE;\n        if(i)\n          pp->relat[i] = rp->relat;\n      }\n    }\n    if(rp != NULL) {\n      pp->First_rside = rp->next;\n      free(rp); /* free memory when data has been read */\n    }\n    else\n      pp->First_rside = NULL;\n  }\n\n  while(pp->First_rside != NULL) {\n    rp = pp->First_rside;\n    pp->First_rside = rp->next;\n    free(rp); /* free memory when data has been read */\n  }\n\n  /* start reading the Hash_list structure */\n  index = 0;\n\n  if((SOSinMatrix) && (CALLOC(SOSrowdata, 1 + pp->Rows, struct SOSrowdata) == NULL)) {\n    FREE(negateAndSOS);\n    FREE(row);\n    FREE(rowno);\n    return(FALSE);\n  }\n\n  if((lp != NULL) &&\n     ((MALLOC(row, 1 + pp->Rows, REAL) == NULL) || (MALLOC(rowno, 1 + pp->Rows, int) == NULL))) {\n    FREE(SOSrowdata);\n    FREE(negateAndSOS);\n    FREE(row);\n    FREE(rowno);\n    return(FALSE);\n  }\n\n  /* for(i = 0; i < pp->Hash_tab->size; i++) {\n    hp = pp->Hash_tab->table[i]; */\n    hp = pp->Hash_tab->first;\n    while(hp != NULL) {\n      count = 0;\n      index++;\n      cp = pp->coldata[hp->index].firstcol;\n      col = hp->index + 1;\n      while(cp != NULL) {\n        if(lp != NULL) {\n          if (negateAndSOS[cp->row] <= 0) {\n            rowno[count] = cp->row;\n              a = cp->value;\n              if (negateAndSOS[cp->row])\n                a = -a;\n            row[count++] = a;\n          }\n          else {\n            if (MALLOC(SOSrow, 1, struct SOSrow) == NULL) {\n              FREE(SOSrowdata);\n              FREE(negateAndSOS);\n              FREE(row);\n              FREE(rowno);\n              return(FALSE);\n            }\n            if(SOSrowdata[cp->row].SOSrow == NULL)\n              SOSrowdata[cp->row].name = strdup(get_row_name(lp, cp->row));\n            SOSrow->next = SOSrowdata[cp->row].SOSrow;\n            SOSrowdata[cp->row].SOSrow = SOSrow;\n            SOSrowdata[cp->row].type = negateAndSOS[cp->row];\n            SOSrow->col = col;\n            SOSrow->value = cp->value;\n          }\n        }\n        tcp = cp;\n        /* cp = cp->next; */\n        cp = cp->prev;\n        free(tcp); /* free memory when data has been read */\n      }\n\n      if(lp != NULL) {\n        add_columnex(lp, count, row, rowno);\n        /* check for bound */\n        if(pp->coldata[hp->index].lowbo == -DEF_INFINITE * 10.0)\n          /* lp->orig_lowbo[pp->Rows+index] = 0.0; */\n          set_lowbo(lp, index, 0);\n        else\n          /* lp->orig_lowbo[pp->Rows+index] = pp->coldata[hp->index].lowbo; */\n          set_lowbo(lp, index, pp->coldata[hp->index].lowbo);\n        /* lp->orig_upbo[pp->Rows+index] = pp->coldata[hp->index].upbo; */\n        if(pp->coldata[hp->index].upbo >= DEF_INFINITE)\n          set_upbo(lp, index, DEF_INFINITE);\n        else\n          set_upbo(lp, index, pp->coldata[hp->index].upbo);\n\n        /* check if it must be an integer variable */\n        if(pp->coldata[hp->index].must_be_int) {\n          /* lp->must_be_int[pp->Rows + index]=TRUE; */\n          set_int(lp, index, TRUE);\n        }\n        if(pp->coldata[hp->index].must_be_sec) {\n          set_semicont(lp, index, TRUE);\n        }\n        if(pp->coldata[hp->index].must_be_free) {\n          set_unbounded(lp, index);\n        }\n\n        /* copy name of column variable */\n        if (!set_col_name(lp, index, hp->name)) {\n          FREE(SOSrowdata);\n          FREE(negateAndSOS);\n          FREE(row);\n          FREE(rowno);\n          return(FALSE);\n        }\n\n        /* put matrix values in intermediate row */\n        /* cp = hp->col; */\n        /* cp = hp->firstcol; */\n      }\n\n      /* thp = hp; */\n      /* hp = hp->next; */\n      /* free(thp->name); */\n      /* free(thp); */ /* free memory when data has been read */\n\n      hp = hp->nextelem;\n\n    }\n    /* pp->Hash_tab->table[i] = NULL; */\n\n  FREE(pp->coldata);\n\n  if(SOSrowdata != NULL) {\n    struct structSOS *structSOS;\n    struct structSOSvars *SOSvars, *SOSvars1;\n    int SOSweight = 0;\n\n    for(i = 1; i <= pp->Rows; i++) {\n      SOSrow = SOSrowdata[i].SOSrow;\n      if(SOSrow != NULL) {\n        if(MALLOC(structSOS, 1, struct structSOS) == NULL) {\n          FREE(SOSrowdata);\n          FREE(negateAndSOS);\n          FREE(row);\n          FREE(rowno);\n          return(FALSE);\n        }\n        structSOS->Nvars = 0;\n        structSOS->type = SOSrowdata[i].type;\n        structSOS->weight = ++SOSweight;\n        structSOS->name = strdup(SOSrowdata[i].name);\n        structSOS->LastSOSvars = NULL;\n        structSOS->next = pp->FirstSOS;\n        pp->FirstSOS = structSOS;\n        SOSvars = NULL;\n        while(SOSrow != NULL) {\n          SOSvars1 = SOSvars;\n          MALLOC(SOSvars, 1, struct structSOSvars);\n          SOSvars->next = SOSvars1;\n          SOSvars->col = SOSrow->col;\n          SOSvars->weight = SOSrow->value;\n          SOSvars->name = NULL;\n          structSOS->Nvars++;\n          SOSrow1 = SOSrow->next;\n          FREE(SOSrow);\n          SOSrow = SOSrow1;\n        }\n        structSOS->SOSvars = SOSvars;\n      }\n    }\n    FREE(SOSrowdata);\n  }\n\n  while(pp->FirstSOS != NULL)\n  {\n    struct structSOSvars *SOSvars, *SOSvars1;\n    int *sosvars, n, col;\n    REAL *weights;\n    hashelem *hp;\n\n    pp->LastSOS = pp->FirstSOS;\n    pp->FirstSOS = pp->FirstSOS->next;\n    SOSvars = pp->LastSOS->SOSvars;\n    if(lp != NULL) {\n      MALLOC(sosvars, pp->LastSOS->Nvars, int);\n      MALLOC(weights, pp->LastSOS->Nvars, double);\n    }\n    else {\n      sosvars = NULL;\n      weights = NULL;\n    }\n    n = 0;\n    while(SOSvars != NULL)\n    {\n      SOSvars1 = SOSvars;\n      SOSvars = SOSvars->next;\n      if(lp != NULL) {\n        col = SOSvars1->col;\n        if(col == 0)\n          if((hp = findhash(SOSvars1->name, lp->colname_hashtab)) != NULL)\n            col = hp->index;\n        if (col) {\n          sosvars[n] = col;\n          weights[n++] = SOSvars1->weight;\n        }\n      }\n      FREE(SOSvars1->name);\n      FREE(SOSvars1);\n    }\n    if(lp != NULL) {\n      add_SOS(lp, pp->LastSOS->name, pp->LastSOS->type, pp->LastSOS->weight, n, sosvars, weights);\n      FREE(weights);\n      FREE(sosvars);\n    }\n    FREE(pp->LastSOS->name);\n    FREE(pp->LastSOS);\n  }\n\n  if(negateAndSOS != NULL) {\n    for(i1 = 0, i = 1; i <= pp->Rows; i++)\n      if(negateAndSOS[i] <= 0)\n        pp->relat[++i1] = pp->relat[i];\n\n#if 01\n    for(i = pp->Rows; i > 0; i--)\n      if(negateAndSOS[i] > 0) {\n        del_constraint(lp, i);\n        pp->Rows--;\n      }\n#endif\n  }\n\n  /* the following should be replaced by a call to the MPS print routine MB */\n\n#if 0\n  if(pp->Verbose) {\n    int j;\n\n    printf(\"\\n\");\n    printf(\"**********Data read**********\\n\");\n    printf(\"Rows    : %d\\n\", pp->Rows);\n    printf(\"Columns : %d\\n\", pp->Columns);\n    printf(\"Nonnuls : %d\\n\", pp->Non_zeros);\n    printf(\"NAME          LPPROB\\n\");\n    printf(\"ROWS\\n\");\n    for(i = 0; i <= pp->Rows; i++) {\n      if(pp->relat[i] == LE)\n        printf(\" L  \");\n      else if(pp->relat[i] == EQ)\n        printf(\" E  \");\n      else if(pp->relat[i] == GE)\n        printf(\" G  \");\n      else if(pp->relat[i] == OF)\n        printf(\" N  \");\n      printf(\"%s\\n\", get_row_name(lp, i));\n    }\n\n    printf(\"COLUMNS\\n\");\n    j = 0;\n    for(i = 0; i < pp->Non_zeros; i++) {\n      if(i == lp->col_end[j])\n        j++;\n      printf(\"    %-8s  %-8s  %g\\n\", get_col_name(lp, j),\n             get_row_name(lp, lp->mat[i].row_nr), (double)lp->mat[i].value);\n    }\n\n    printf(\"RHS\\n\");\n    for(i = 0; i <= pp->Rows; i++) {\n      printf(\"    RHS       %-8s  %g\\n\", get_row_name(lp, i),\n             (double)lp->orig_rhs[i]);\n    }\n\n    printf(\"RANGES\\n\");\n    for(i = 1; i <= pp->Rows; i++)\n      if((lp->orig_upbo[i] != lp->infinite) && (lp->orig_upbo[i] != 0)) {\n        printf(\"    RGS       %-8s  %g\\n\", get_row_name(lp, i),\n               (double)lp->orig_upbo[i]);\n      }\n      else if((lp->orig_lowbo[i] != 0)) {\n        printf(\"    RGS       %-8s  %g\\n\", get_row_name(lp, i),\n               (double)-lp->orig_lowbo[i]);\n      }\n\n    printf(\"BOUNDS\\n\");\n    for(i = pp->Rows + 1; i <= pp->Rows + pp->Columns; i++) {\n      if((lp->orig_lowbo[i] != 0) && (lp->orig_upbo[i] < lp->infinite) &&\n         (lp->orig_lowbo[i] == lp->orig_upbo[i])) {\n        printf(\" FX BND       %-8s  %g\\n\", get_col_name(lp, i - pp->Rows),\n               (double)lp->orig_upbo[i]);\n      }\n      else {\n        if(lp->orig_upbo[i] < lp->infinite)\n            printf(\" UP BND       %-8s  %g\\n\", get_col_name(lp, i - pp->Rows),\n                   (double)lp->orig_upbo[i]);\n        if(lp->orig_lowbo[i] > 0)\n            printf(\" LO BND       %-8s  %g\\n\", get_col_name(lp, i - pp->Rows),\n                   (double)lp->orig_lowbo[i]);\n      }\n    }\n\n    printf(\"ENDATA\\n\");\n  }\n#endif\n\n  FREE(row);\n  FREE(rowno);\n  FREE(negateAndSOS);\n  return(TRUE);\n} /* readinput */\n\nlprec *yacc_read(lprec *lp, int verbose, char *lp_name, int (*parse) (parse_parm *pp), parse_parm *pp, void (*delete_allocated_memory) (parse_parm *pp))\n{\n  REAL *orig_upbo;\n  int stat = -1;\n  lprec *lp0 = lp;\n\n  pp->title = lp_name;\n\n  if(!init_read(pp, verbose))\n    error(pp, CRITICAL, \"init_read failed\");\n  else if (setjmp(pp->jump_buf) == 0)\n    stat = parse(pp);\n\n  delete_allocated_memory(pp);\n\n  pp->Rows--;\n\n  pp->relat = NULL;\n  if((stat != 0) || (CALLOC(pp->relat, pp->Rows + 1, short) != NULL)) {\n    if(stat == 0) {\n      if(lp == NULL) {\n        lp = make_lp(pp->Rows, 0);\n      }\n      else {\n        int NRows;\n\n        for(NRows = get_Nrows(lp); NRows < pp->Rows; NRows++)\n          add_constraintex(lp, 0, NULL, NULL, LE, 0);\n      }\n    }\n    else\n      lp = NULL;\n    if ((stat != 0) || (lp != NULL)) {\n      if(lp != NULL) {\n        set_verbose(lp, pp->Verbose);\n      }\n\n      if (!readinput(pp, lp)) {\n        if((lp != NULL) && (lp0 == NULL))\n          delete_lp(lp);\n        lp = NULL;\n      }\n\n      if(lp != NULL) {\n        set_lp_name(lp, pp->title);\n        if(pp->Maximise)\n          set_maxim(lp);\n\n        if(pp->Rows) {\n          int row;\n\n          MALLOCCPY(orig_upbo, lp->orig_upbo, 1 + pp->Rows, REAL);\n          for(row = 1; row <= pp->Rows; row++)\n            set_constr_type(lp, row, pp->relat[row]);\n\n          memcpy(lp->orig_upbo, orig_upbo, (1 + pp->Rows) * sizeof(*orig_upbo)); /* restore upper bounds (range) */\n          FREE(orig_upbo);\n        }\n      }\n      if((pp->title != NULL) && (pp->title != lp_name))\n        free(pp->title);\n\n      free_hash_table(pp->Hash_tab);\n      free_hash_table(pp->Hash_constraints);\n    }\n    FREE(pp->relat);\n  }\n  null_tmp_store(pp, FALSE);\n  return(lp);\n}\n"
  },
  {
    "path": "prism/ext/lpsolve55/src/lp_solve_5.5/yacc_read.h",
    "content": "/* prototypes of functions used in the parser */\n\n#include <setjmp.h>\n\n#ifndef __READ_H__\n#define __READ_H__\n\nstruct _tmp_store_struct\n{\n  char    *name;\n  int     row;\n  REAL    value;\n  REAL    rhs_value;\n  short   relat;\n};\n\ntypedef struct parse_parm_s\n{\n  void *scanner;\n  long lineno;\n  int Verbose;\n  jmp_buf jump_buf;\n  long Rows, Columns, Non_zeros, Lin_term_count;\n  struct rside *First_rside, *rs;\n  short SOStype;         /* SOS type */\n  char Ignore_int_decl, int_decl, Ignore_sec_decl, Ignore_free_decl, sos_decl, Maximise;\n  hashtable *Hash_tab, *Hash_constraints;\n  struct structcoldata *coldata;\n  struct structSOS *FirstSOS, *LastSOS;\n  struct _tmp_store_struct tmp_store;\n  char *title;\n  short *relat;\n  void *parse_vars;\n} parse_parm;\n\nvoid lex_fatal_error(parse_parm *, void *, char *);\nint set_title(parse_parm *pp, char *name);\nint add_constraint_name(parse_parm *pp, char *name);\nint store_re_op(parse_parm *pp, char OP, int HadConstraint, int HadVar, int Had_lineair_sum);\nvoid null_tmp_store(parse_parm *pp, int init_Lin_term_count);\nint store_bounds(parse_parm *pp, int warn);\nvoid storevarandweight(parse_parm *pp, char *name);\nint set_sos_type(parse_parm *pp, int SOStype);\nint set_sos_weight(parse_parm *pp, double weight, int sos_decl);\nint set_sec_threshold(parse_parm *pp, char *name, REAL threshold);\nint rhs_store(parse_parm *pp, REAL value, int HadConstraint, int HadVar, int Had_lineair_sum);\nint var_store(parse_parm *pp, char *var, REAL value, int HadConstraint, int HadVar, int Had_lineair_sum);\nint negate_constraint(parse_parm *pp);\nvoid add_row(parse_parm *pp);\nvoid add_sos_row(parse_parm *pp, short SOStype);\n\nvoid read_error(parse_parm *, void *, char *);\nvoid check_int_sec_sos_free_decl(parse_parm *, int, int, int, int);\nlprec *yacc_read(lprec *lp, int verbose, char *lp_name, int (*parse) (parse_parm *pp), parse_parm *pp, void (*delete_allocated_memory) (parse_parm *pp));\n\n#define set_obj_dir(pp, maximise) pp->Maximise = maximise\n#endif\n"
  },
  {
    "path": "prism/images/README.txt",
    "content": "Many of these images are taken from or based on those from\tEveraldo Coelho's\r\nCrystal icon set (details below) which is released under LGPL.\r\n\r\n++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++++\r\nThis copyright and license notice covers the images in this directory.\r\n************************************************************************\r\n\r\nTITLE:\tCrystal Project Icons\r\nAUTHOR:\tEveraldo Coelho\r\nSITE:\thttp://www.everaldo.com\r\nCONTACT: everaldo@everaldo.com\r\n\r\nCopyright (c)  2006-2007  Everaldo Coelho.\r\n\r\n"
  },
  {
    "path": "prism/include/DoubleVector.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/dv_DoubleVector.h\"\n"
  },
  {
    "path": "prism/include/ExportIterations.h",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\n\n#ifndef EXPORT_ITERATIONS_H\n#define EXPORT_ITERATIONS_H\n\n#include <cstdio>\n#include <string>\n#include <cmath>\n\n#include <cudd.h>\n#include <dd.h>\n#include \"dv.h\"\n#include \"prism.h\"\n#include <odd.h>\n\nclass ExportIterations {\nprivate:\n\tFILE *fp;\n\tstd::string filename;\n\npublic:\n\t/**\n\t * Constructor, provide filename.\n\t */\n\tExportIterations(const char* title = \"\", const char* filename = get_export_iterations_filename()) {\n\t\tfp = fopen(filename, \"w\");\n\t\tthis->filename = filename;\n\n\t\tfprintf(fp, \"<!DOCTYPE html>\\n\");\n\t\tfprintf(fp, \"<html><head>\\n\");\n\t\tfprintf(fp, \"<meta charset=\\\"utf-8\\\">\\n\");\n\t\tfprintf(fp, \"<!-- HTML file automatically generated by the PRISM model checker -->\\n\");\n\t\tfprintf(fp, \"<!-- For visualising the individual steps of a value iteration computation -->\\n\");\n\t\tfprintf(fp, \"<!-- Loads supporting Javascript and CSS from www.prismmodelchecker.org -->\\n\");\n\t\tfprintf(fp, \"<title>%s</title>\\n\", title);\n\t\tfprintf(fp, \"<link rel='stylesheet' href='https://www.prismmodelchecker.org/js/res/iteration-vis-v1.css'>\\n\");\n\t\tfprintf(fp, \"<script src=\\\"https://www.prismmodelchecker.org/js/res/d3.js-v4/d3.min.js\\\"></script>\\n\");\n\t\tfprintf(fp, \"<body onload='init();'>\\n\");\n\t\tfprintf(fp, \"<h1>%s</h1>\\n\", title);\n\t\tfprintf(fp, \"<svg></svg>\\n\");\n\t\tfprintf(fp, \"<script src=\\\"https://www.prismmodelchecker.org/js/res/iteration-vis-v1.js\\\"></script>\\n\");\n\t}\n\n\t/**\n\t * Get the filename used for exporting.\n\t */\n\tconst std::string& getFileName() {\n\t\treturn filename;\n\t}\n\n\t/**\n\t * Export the given vector, with size n and given type (0 = normal, VI from below, 1 = VI from above)\n\t */\n\tvoid exportVector(double *soln, int64_t n, int type) {\n\t\tfprintf(fp, \"<script>addVector([\");\n\t\tfor (int64_t i = 0; i < n; i++) {\n\t\t\tif (i>0) fprintf(fp, \",\");\n\t\t\tdouble d = soln[i];\n\t\t\tif (std::isinf(d)) {\n\t\t\t\tif (d > 0)\n\t\t\t\t\tfprintf(fp, \"Infinity\");\n\t\t\t\telse\n\t\t\t\t\tfprintf(fp, \"-Infinity\");\n\t\t\t} else {\n\t\t\t\tfprintf(fp, \"%.17g\", soln[i]);\n\t\t\t}\n\t\t}\n\t\tfprintf(fp, \"],%d)</script>\\n\", type);\n\t\tfflush(fp);\n\t}\n\n\t/**\n\t * Export the given MTBDD vector, with num_rvars row variables,\n\t * odd for reachable state space and type (0= normal, VI from below, 1 = VI from above)\n\t */\n\tvoid exportVector(DdNode *dd, DdNode **rvars, int num_rvars, ODDNode* odd, int type)\n\t{\n\t\tdouble* vec = mtbdd_to_double_vector(ddman, dd, rvars, num_rvars, odd);\n\n\t\t// get number of states\n\t\tint64_t n = odd->eoff + odd->toff;\n\n\t\texportVector(vec, n, type);\n\t\tdelete[] vec;\n\t}\n\n\t/** Destructor, close file */\n\t~ExportIterations() {\n\t\tfprintf(fp, \"</body></html>\\n\");\n\t\tfclose(fp);\n\t}\n};\n\n#endif\n"
  },
  {
    "path": "prism/include/IntegerVector.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/dv_IntegerVector.h\"\n"
  },
  {
    "path": "prism/include/IntervalIteration.h",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\n#ifndef INTERVAL_ITERATION_H\n#define INTERVAL_ITERATION_H\n\n#include <cmath>\n\n// helper class for interval iteration\nclass IntervalIteration {\nprivate:\n\tbool ensure_monotonic_from_below;\n\tbool ensure_monotonic_from_above;\n\tbool select_midpoint;\n\npublic:\n\texplicit IntervalIteration(int flags) {\n\t\tensure_monotonic_from_below = (flags & 0x01);\n\t\tensure_monotonic_from_above = (flags & 0x02);\n\t\tselect_midpoint = (flags & 0x04);\n\t}\n\n\tbool flag_ensure_monotonic_from_below() const\n\t{\n\t\treturn ensure_monotonic_from_below;\n\t}\n\n\tbool flag_ensure_monotonic_from_above() const\n\t{\n\t\treturn ensure_monotonic_from_above;\n\t}\n\n\tbool flag_select_midpoint() const\n\t{\n\t\treturn select_midpoint;\n\t}\n\n\t// Store the appropriate value into 'target', optionally ensuring monotonicity\n\tinline void updateValueFromBelow(double& target, double old_value, double new_value) const\n\t{\n\t\tif (!ensure_monotonic_from_below) {\n\t\t\ttarget = new_value;\n\t\t} else {\n\t\t\t// from below: do max\n\t\t\t// the 'if' part below fails if either old_value or new_value is NaN,\n\t\t\t// in which case new_value is taken\n\t\t\ttarget = (old_value > new_value ? old_value : new_value);\n\t\t}\n\t}\n\n\t// Store the appropriate value into 'target', optionally ensuring monotonicity\n\tinline void updateValueFromAbove(double& target, double old_value, double new_value) const\n\t{\n\t\tif (!ensure_monotonic_from_above) {\n\t\t\ttarget = new_value;\n\t\t} else {\n\t\t\t// from above: do min\n\t\t\t// the 'if' part below fails if either old_value or new_value is NaN,\n\t\t\t// in which case new_value is taken\n\t\t\ttarget = (old_value < new_value ? old_value : new_value);\n\t\t}\n\t}\n\n\t// store the appropriate value into 'target', optionally ensuring monotonicity\n\tinline void updateValue(double& target, double old_value, double new_value, bool from_below)\n\t{\n\t\tif (from_below) {\n\t\t\tupdateValueFromBelow(target, old_value, new_value);\n\t\t} else {\n\t\t\tupdateValueFromAbove(target, old_value, new_value);\n\t\t}\n\t}\n\n\t// Ensure monotonicity for the given solution vectors (iteration from below).\n\t// Compares old and new values, overwrites value in 'new_values' if old value was larger.\n\t// n = number of elements\n\tinline void ensureMonotonicityFromBelow(double *old_values, double *new_values, int n) const\n\t{\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tupdateValueFromBelow(*new_values, *old_values, *new_values);\n\t\t\told_values++;\n\t\t\tnew_values++;\n\t\t}\n\t}\n\n\t// Ensure monotonicity for the given solution vectors (iteration from above).\n\t// Compares old and new values, overwrites value in 'new_values' if old value was smaller.\n\t// n = number of elements\n\tinline void ensureMonotonicityFromAbove(double *old_values, double *new_values, int n) const\n\t{\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tupdateValueFromAbove(*new_values, *old_values, *new_values);\n\t\t\told_values++;\n\t\t\tnew_values++;\n\t\t}\n\t}\n\n\t// Compute midpoint between solution from below and solution from above,\n\t// store result in soln_below\n\t// n = number of states / size of solution vectors\n\tinline void selectMidpoint(double* soln_below, double* soln_above, int n)\n\t{\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (soln_above[i] != soln_below[i]) {\n\t\t\t\t// use x + ( y - x ) / 2 instead of (x+y)/2 for better numerical\n\t\t\t\t// stability\n\t\t\t\tdouble d = soln_below[i] + ( (soln_above[i] - soln_below[i]) / 2.0 );\n\t\t\t\tif (d <= soln_above[i] && d >= soln_below[i]) {\n\t\t\t\t\t// only store result if between soln_below and soln_above to\n\t\t\t\t\t// guard against rounding problems,\n\t\t\t\t\t// fallback is to simply return soln_below as is\n\t\t\t\t\tsoln_below[i] = d;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n};\n\n#endif\n"
  },
  {
    "path": "prism/include/JDD.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/jdd_JDD.h\"\n"
  },
  {
    "path": "prism/include/JDDNode.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/jdd_JDDNode.h\"\n"
  },
  {
    "path": "prism/include/JDDVars.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/jdd_JDDVars.h\"\n"
  },
  {
    "path": "prism/include/Measures.h",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\n#ifndef MEASURE_H\n#define MEASURE_H\n\n#include <cstddef>  // for std::size_t type\n#include <cmath>  // for std::isinf\n#include <limits>\n\n/**\n * Measure: Computes maximum element-wise difference between value vectors.\n * In relative mode, the difference is scaled by the value.\n */\nclass MeasureSupNorm {\nprivate:\n\t// relative mode?\n\tconst bool relative;\n\t// the current maximal value\n\tdouble sup_norm;\n\npublic:\n\t/** Constructor, set relative flag */\n\texplicit MeasureSupNorm(bool relative) : relative(relative) {\n\t\treset();\n\t}\n\n\t/** Reset for new measurement */\n\tvoid reset() {\n\t\tsup_norm = 0.0;\n\t}\n\n\t/** Relative mode? */\n\tbool isRelative() const {\n\t\treturn relative;\n\t}\n\n\t/**\n\t * Do the measurement for a single pair of values.\n\t * For relative mode, the first value is used as the divisor.\n\t */\n\tinline void measure(double v1, double v2) {\n\t\tdouble x;\n\n\t\t// compute absolute of difference\n\t\tx = fabs(v2 - v1);\n\t\tif (relative) {\n\t\t\t// for relative mode: divide by second value\n\t\t\t// We take the absolute value of v1 to ensure that\n\t\t\t// x remains non-negative. v1 can become negative e.g.\n\t\t\t// during iterations with over-relaxation with large\n\t\t\t// omega values.\n\t\t\t// Note: if v1 is 0, then x will become +inf for x>0 and NaN for x=0, i.e., v1=v2=0\n\t\t\t// In the later case, the max computation below will ignore the NaN,\n\t\t\t// as NaN > y is false for all y\n\t\t\tx /= fabs(v1);\n\t\t}\n\n\t\t// sup_norm = max { x, sup_norm }\n\t\tif (x > sup_norm) {\n\t\t\tsup_norm = x;\n\t\t}\n\t}\n\n\t/**\n\t * Do the measurement for two value arrays of size n.\n\t * For relative mode, the values of the first array are used as the divisors.\n\t */\n\tinline void measure(const double *soln, const double *soln2, std::size_t n) {\n\t\tfor (std::size_t i = 0; i < n; i++) {\n\t\t\tmeasure(soln[i], soln2[i]);\n\t\t}\n\t}\n\n\t/** Return the measured value */\n\tdouble value() const {\n\t\treturn sup_norm;\n\t}\n\n};\n\n/**\n * Measure for determining the difference between the upper and lower values in\n * an interval iteration.\n * In relative mode, the difference is scaled by the mid-point between upper and lower value.\n */\nclass MeasureSupNormInterval {\nprivate:\n\t// relative mode?\n\tconst bool relative;\n\t// the current maximal value\n\tdouble sup_norm;\n\npublic:\n\t/** Constructor, set relative flag */\n\texplicit MeasureSupNormInterval(bool relative) : relative(relative) {\n\t\treset();\n\t}\n\n\t/** Reset for new measurement */\n\tvoid reset() {\n\t\tsup_norm = 0.0;\n\t}\n\n\t/** Relative mode? */\n\tbool isRelative() const {\n\t\treturn relative;\n\t}\n\n\t/**\n\t * Do the measurement for an upper and lower value pair.\n\t * For relative mode, the lower value is used as the divisor.\n\t */\n\tinline void measure(double lower, double upper) {\n\t\tdouble x;\n\n\t\t// special case: one of the values is infinite (this can happen e.g. for non-converging\n\t\t// iterations when the values grow extremely large and overflow to infinity).\n\t\tif (std::isinf(lower) || std::isinf(upper)) {\n\t\t\tx = std::numeric_limits<double>::infinity();\n\t\t} else {\n\t\t\t// compute difference\n\t\t\t// we don't use fabs like for MeasureSupNorm, as we want x to become negative\n\t\t\t// in situations where upper < lower (should only happen due to numerical inaccuracies / rounding)\n\t\t\tx = upper - lower;\n\t\t\t// we clamp to zero for negative values\n\t\t\tif (x < 0)\n\t\t\t\tx = 0;\n\n\t\t\tif (relative && x != 0.0) {\n\t\t\t\t// for relative mode: divide by lower\n\t\t\t\t// taking lower ensures that if the actual value should happen to be\n\t\t\t\t// the lower value, that then the relative precision is satisfied.\n\t\t\t\t// We take the absolute value of the lower to ensure that\n\t\t\t\t// x does not flip signs.\n\t\t\t\t// Note: if lower is 0.0, then x will become +inf, as x!=0\n\t\t\t\tx /= fabs(lower);\n\t\t\t}\n\t\t}\n\n\t\t// sup_norm = max { x, sup_norm }\n\t\tif (x > sup_norm) {\n\t\t\tsup_norm = x;\n\t\t}\n\t}\n\n\t/**\n\t * Do the measurement for a pair of arrays (lower and upper bounds) of size n.\n\t * For relative mode, the midpoints are used as the divisors.\n\t */\n\tinline void measure(const double *lower, const double *upper, std::size_t n) {\n\t\tfor (std::size_t i = 0; i < n; i++) {\n\t\t\tmeasure(lower[i], upper[i]);\n\t\t}\n\t}\n\n\t/** Return the measured value */\n\tdouble value() const {\n\t\treturn sup_norm;\n\t}\n\n};\n\n#endif\n"
  },
  {
    "path": "prism/include/NDSparseMatrix.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/sparse_NDSparseMatrix.h\"\n"
  },
  {
    "path": "prism/include/NativeIntArray.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/prism_NativeIntArray.h\"\n"
  },
  {
    "path": "prism/include/ODDUtils.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/odd_ODDUtils.h\"\n"
  },
  {
    "path": "prism/include/PrismHybrid.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/hybrid_PrismHybrid.h\"\n"
  },
  {
    "path": "prism/include/PrismMTBDD.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/mtbdd_PrismMTBDD.h\"\n"
  },
  {
    "path": "prism/include/PrismNative.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/prism_PrismNative.h\"\n"
  },
  {
    "path": "prism/include/PrismNativeGlob.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#ifndef PRISMNATIVEGLOB_H\n#define PRISMNATIVEGLOB_H\n\n//------------------------------------------------------------------------------\n\n#include <stdarg.h>\n#include <cstdio>\n#include <jni.h>\n#include <cudd.h>\n\n// Flags for building Windows DLLs\n#ifdef __MINGW32__\n\t#define EXPORT __declspec(dllexport)\n#else\n\t#define EXPORT\n#endif\n\n//------------------------------------------------------------------------------\n\n// macro for attributing printf-like functions to notify the compiler\n// that we'd like to have format string / argument sanity checking\n\n#ifdef __GNUC__\n  // __attribute__ should be supported by compilers that claim to behave like GNU GCC\n\n  // we have to determine the printf format string, as MINGW supports two printf backends\n#if defined(__USE_MINGW_ANSI_STDIO) && __USE_MINGW_ANSI_STDIO\n  // this should be the default for C++\n#define PRISM_PRINTF_FORMAT gnu_printf\n#elif defined(__USE_MINGW_ANSI_STDIO) && !(__USE_MINGW_ANSI_STDIO)\n#define PRISM_PRINTF_FORMAT ms_printf\n#else\n  // normal GCC: use printf as format\n#define PRISM_PRINTF_FORMAT printf\n#endif\n\n// define IS_LIKE_PRINTF, which can be placed after a printf-like function\n// first parameter is index of format string, second parameter is first vararg\n#define IS_LIKE_PRINTF(format_index, first_arg) __attribute__((__format__(PRISM_PRINTF_FORMAT, format_index,first_arg)))\n\n#else // !defined __GNUC__\n// empty IS_LIKE_PRINTF\n#define IS_LIKE_PRINTF(format_index, first_arg)\n#endif\n\n\n//------------------------------------------------------------------------------\n\n#define MAX_LOG_STRING_LEN 1024\n#define MAX_ERR_STRING_LEN 1024\n\n// Constants - these need to match the definitions in prism/Prism.java\n\nconst int EXPORT_PLAIN = 1;\nconst int EXPORT_MATLAB = 2;\nconst int EXPORT_DOT = 3;\nconst int EXPORT_MRMC = 4;\nconst int EXPORT_ROWS = 5;\nconst int EXPORT_DOT_STATES = 6;\n\nconst int LIN_EQ_METHOD_POWER = 1;\nconst int LIN_EQ_METHOD_JACOBI = 2;\nconst int LIN_EQ_METHOD_GAUSSSEIDEL = 3;\nconst int LIN_EQ_METHOD_BGAUSSSEIDEL = 4;\nconst int LIN_EQ_METHOD_PGAUSSSEIDEL = 5;\nconst int LIN_EQ_METHOD_BPGAUSSSEIDEL = 6;\nconst int LIN_EQ_METHOD_JOR = 7;\nconst int LIN_EQ_METHOD_SOR = 8;\nconst int LIN_EQ_METHOD_BSOR = 9;\nconst int LIN_EQ_METHOD_PSOR = 10;\nconst int LIN_EQ_METHOD_BPSOR = 11;\n\nconst int TERM_CRIT_ABSOLUTE = 1;\nconst int TERM_CRIT_RELATIVE = 2;\n\nconst int EXPORT_ADV_NONE = 1;\nconst int EXPORT_ADV_DTMC = 2;\nconst int EXPORT_ADV_MDP = 3;\n\nconst int REACH_BFS = 1;\nconst int REACH_FRONTIER = 2;\n\n//------------------------------------------------------------------------------\n\n#define logtwo(X) log((double)X)/log(2.0)\n\n// External refs to global variables\n\n// Prism object\nEXPORT extern jclass prism_cls;\nEXPORT extern jobject prism_obj;\n\n// CUDD manager: stored so that it doesn't have to be passed to every CUDD/dd call.\n// Set via (JNI) PN_SetCUDDManager, cached here and accessible across all native code.\nEXPORT extern DdManager *ddman;\n\n// Export stuff:\n\nEXPORT extern int export_type;\nEXPORT extern FILE *export_file;\nEXPORT extern JNIEnv *export_env;\n// adversary export mode\nEXPORT extern int export_adv;\n// adversary export filename\nEXPORT extern const char *export_adv_filename;\n// export iterations filename\nEXPORT extern const char *export_iterations_filename;\n\n// Options:\n\n// numerical method stuff\nEXPORT extern int lin_eq_method;\nEXPORT extern double lin_eq_method_param;\nEXPORT extern int term_crit;\nEXPORT extern double term_crit_param;\nEXPORT extern int max_iters;\nEXPORT extern int export_model_precision;\n// use \"compact modified\" sparse matrix storage?\nEXPORT extern bool compact;\n// sparse bits info\nEXPORT extern int sb_max_mem;\nEXPORT extern int num_sb_levels;\n// hybrid sor info\nEXPORT extern int sor_max_mem;\nEXPORT extern int num_sor_levels;\n// use steady-state detection for transient computation?\nEXPORT extern bool do_ss_detect;\n\n// details from numerical computation which may be queried\nEXPORT extern double last_error_bound;\n\n//------------------------------------------------------------------------------\n\n// function prototypes\n\nEXPORT void PN_SetErrorMessage(const char *str, ...)  IS_LIKE_PRINTF(1,2);\nEXPORT char *PH_GetErrorMessage();\n\nint store_export_info(int type, jstring fn, JNIEnv *env);\nvoid export_string(const char *str, ...) IS_LIKE_PRINTF(1,2);\nbool PN_GetFlagExportIterations();\n\nvoid PN_PrintToMainLog(JNIEnv *env, const char *str, ...) IS_LIKE_PRINTF(2,3);\nvoid PN_PrintWarningToMainLog(JNIEnv *env, const char *str, ...) IS_LIKE_PRINTF(2,3);\nvoid PN_PrintMemoryToMainLog(JNIEnv *env, const char *before, double mem, const char *after);\n\n//------------------------------------------------------------------------------\n\n#endif\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/PrismSparse.h",
    "content": "/* Forwarding header in the legacy location, pointing to the new location of the JNI auto-generated header file */\n#include \"jni/sparse_PrismSparse.h\"\n"
  },
  {
    "path": "prism/include/SimulatorEngine.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class simulator_SimulatorEngine */\n\n#ifndef _Included_simulator_SimulatorEngine\n#define _Included_simulator_SimulatorEngine\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n#undef simulator_SimulatorEngine_ERROR\n#define simulator_SimulatorEngine_ERROR -1L\n#undef simulator_SimulatorEngine_OUTOFRANGE\n#define simulator_SimulatorEngine_OUTOFRANGE -1L\n#undef simulator_SimulatorEngine_NULL\n#define simulator_SimulatorEngine_NULL 0L\n#undef simulator_SimulatorEngine_NOT_LOADED\n#define simulator_SimulatorEngine_NOT_LOADED 0L\n#undef simulator_SimulatorEngine_PROBABILISTIC\n#define simulator_SimulatorEngine_PROBABILISTIC 1L\n#undef simulator_SimulatorEngine_NONDETERMINISTIC\n#define simulator_SimulatorEngine_NONDETERMINISTIC 2L\n#undef simulator_SimulatorEngine_STOCHASTIC\n#define simulator_SimulatorEngine_STOCHASTIC 3L\n#undef simulator_SimulatorEngine_UNDEFINED_INT\n#define simulator_SimulatorEngine_UNDEFINED_INT -2147483647L\n#undef simulator_SimulatorEngine_UNDEFINED_DOUBLE\n#define simulator_SimulatorEngine_UNDEFINED_DOUBLE -1.0000000138484279E24\n#undef simulator_SimulatorEngine_INFINITY\n#define simulator_SimulatorEngine_INFINITY 1.0000000138484279E24\n#undef simulator_SimulatorEngine_SIM_PATH_NUM_STEPS\n#define simulator_SimulatorEngine_SIM_PATH_NUM_STEPS 0L\n#undef simulator_SimulatorEngine_SIM_PATH_TIME\n#define simulator_SimulatorEngine_SIM_PATH_TIME 1L\n#undef simulator_SimulatorEngine_SIM_PATH_DEADLOCK\n#define simulator_SimulatorEngine_SIM_PATH_DEADLOCK 2L\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/dd.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// function prototypes for stuff in dd.cc\n\nvoid DD_SetOutputStream(FILE *fp);\nFILE *DD_GetOutputStream();\n\n// headers for all other files\n\n#include \"dd_cudd.h\"\n#include \"dd_basics.h\"\n#include \"dd_vars.h\"\n#include \"dd_abstr.h\"\n#include \"dd_term.h\"\n#include \"dd_info.h\"\n#include \"dd_matrix.h\"\n#include \"dd_export.h\"\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dd_abstr.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_ThereExists(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\nDdNode *DD_ForAll(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\nDdNode *DD_SumAbstract(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\nDdNode *DD_ProductAbstract(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\nDdNode *DD_MinAbstract(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\nDdNode *DD_MaxAbstract(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dd_basics.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n\n//------------------------------------------------------------------------------\n\n#define APPLY_PLUS 1\n#define APPLY_MINUS 2\n#define APPLY_TIMES 3\n#define APPLY_DIVIDE 4\n#define APPLY_MIN 5\n#define APPLY_MAX 6\n#define APPLY_EQUALS 7\n#define APPLY_NOTEQUALS 8\n#define APPLY_GREATERTHAN 9\n#define APPLY_GREATERTHANEQUALS 10\n#define APPLY_LESSTHAN 11\n#define APPLY_LESSTHANEQUALS 12\n#define APPLY_FLOOR 13\n#define APPLY_CEIL 14\n#define APPLY_POW 15\n#define APPLY_MOD 16\n#define APPLY_LOGXY 17\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Create(DdManager *ddman);\nDdNode *DD_Constant(DdManager *ddman, double value); \nDdNode *DD_PlusInfinity(DdManager *ddman);\nDdNode *DD_MinusInfinity(DdManager *ddman);\nDdNode *DD_Var(DdManager *ddman, int i);\nDdNode *DD_Not(DdManager *ddman, DdNode *dd);\nDdNode *DD_Or(DdManager *ddman, DdNode *dd1, DdNode *dd2);\nDdNode *DD_And(DdManager *ddman, DdNode *dd1, DdNode *dd2);\nDdNode *DD_Xor(DdManager *ddman, DdNode *dd1, DdNode *dd2);\nDdNode *DD_Implies(DdManager *ddman, DdNode *dd1, DdNode *dd2);\nDdNode *DD_Apply(DdManager *ddman, int op, DdNode *dd1, DdNode *dd2);\nDdNode *DD_MonadicApply(DdManager *ddman, int op, DdNode *dd);\nDdNode *DD_Restrict(DdManager *ddman, DdNode *dd, DdNode *cube);\nDdNode *DD_ITE(DdManager *ddman, DdNode *dd1, DdNode *dd2, DdNode *dd3);\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dd_cudd.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n#include <map>\n\n//------------------------------------------------------------------------------\n\nDdManager *DD_InitialiseCUDD();\nDdManager *DD_InitialiseCUDD(long maxmem, double epsilon);\nvoid DD_SetCUDDMaxMem(DdManager *ddman, long max_mem);\nvoid DD_SetCUDDEpsilon(DdManager *ddman, double epsilon);\nvoid DD_PrintCacheInfo(DdManager *ddman);\nvoid DD_CloseDownCUDD(DdManager *ddman);\nvoid DD_CloseDownCUDD(DdManager *ddman, bool check);\nvoid DD_ReportExternalRefCounts(DdManager *ddman);\nvoid DD_GetExternalRefCounts(DdManager *ddman, std::map<DdNode*,int>& external_refs);\nbool DD_GetErrorFlag(DdManager *ddman);\nvoid DD_SetErrorFlag();\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dd_export.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportDDToDotFile(DdManager *ddman, DdNode *dd, char *filename);\nvoid DD_ExportDDToDotFileLabelled(DdManager *ddman, DdNode *dd, char *filename, char **var_names);\nvoid DD_ExportDDToDotFile(DdManager *ddman, DdNode *dd, FILE *fp_out);\nvoid DD_ExportDDToDotFileLabelled(DdManager *ddman, DdNode *dd, FILE *fp_out, char *title, char **var_names);\n\nvoid DD_ExportDDToDDFile(DdManager *ddman, DdNode *dd, FILE *fp_out);\nvoid DD_ExportDDToDDFile(DdManager *ddman, DdNode *dd, char *filename);\nvoid DD_ExportVectorToMatlabFile(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, char *name, char *filename);\nvoid DD_ExportVectorToMatlabFile(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, char *name, FILE *fp_out);\nvoid DD_ExportMatrixToMatlabFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, char *name, char *filename);\nvoid DD_ExportMatrixToMatlabFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, char *name, FILE *fp_out);\nvoid DD_ExportMatrixToPPFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, char *filename);\nvoid DD_ExportMatrixToPPFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, FILE *fp_out);\nvoid DD_Export3dMatrixToPPFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, DdNode **nvars, int num_nvars, char *filename);\nvoid DD_Export3dMatrixToPPFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, DdNode **nvars, int num_nvars, FILE *fp);\nvoid DD_ExportMatrixToSpyFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, int depth, char *filename);\nvoid DD_ExportMatrixToSpyFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, int depth, FILE *fp_out);\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dd_info.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n\n//------------------------------------------------------------------------------\n\nint DD_GetNumNodes(DdManager *ddman, DdNode *dd);\nint DD_GetNumTerminals(DdManager *ddman, DdNode *dd);\ndouble DD_GetNumMinterms(DdManager *ddman, DdNode *dd, int num_vars);\ndouble DD_GetNumPaths(DdManager *ddman, DdNode *dd);\nvoid DD_PrintInfo(DdManager *ddman, DdNode *dd, int num_vars);\nvoid DD_PrintInfoBrief(DdManager *ddman, DdNode *dd, int num_vars);\nvoid DD_PrintSupport(DdManager *ddman, DdNode *dd);\nvoid DD_PrintSupportNames(DdManager *ddman, DdNode *dd, char **var_names);\nDdNode *DD_GetSupport(DdManager *ddman, DdNode *dd);\nvoid DD_PrintTerminals(DdManager *ddman, DdNode *dd);\nvoid DD_PrintTerminalsAndNumbers(DdManager *ddman, DdNode *dd, int num_vars);\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dd_matrix.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n\n// DD_PrintVector/Matrix accuracy flags\n\n#define ACCURACY_ZERO_ONE 1\n#define ACCURACY_LOW 2\n#define ACCURACY_NORMAL 3\n#define ACCURACY_HIGH 4\n#define ACCURACY_LIST 5\n\n// DD_MatrixMultiply method flags\n\n#define MM_CMU 1\n#define MM_BOULDER 2\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_SetVectorElement(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, long index, double value);\nDdNode *DD_SetMatrixElement(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, long rindex, long cindex, double value);\nDdNode *DD_Set3DMatrixElement(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, DdNode **lvars, int num_lvars, long rindex, long cindex, long lindex, double value);\ndouble DD_GetVectorElement(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, long index);\nDdNode *DD_Identity(DdManager *ddman, DdNode **rvars, DdNode **cvars, int num_vars);\nDdNode *DD_Transpose(DdManager *ddman, DdNode *dd, DdNode **row_vars, DdNode **col_vars, int num_vars);\nDdNode *DD_MatrixMultiply(DdManager *ddman, DdNode *dd1, DdNode *dd2, DdNode **vars, int num_vars, int method);\nvoid DD_PrintVector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\nvoid DD_PrintVector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, int accuracy);\nvoid DD_PrintMatrix(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars);\nvoid DD_PrintMatrix(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, int accuracy);\nvoid DD_PrintVectorFiltered(DdManager *ddman, DdNode *dd, DdNode *filter, DdNode **vars, int num_vars);\nvoid DD_PrintVectorFiltered(DdManager *ddman, DdNode *dd, DdNode *filter, DdNode **vars, int num_vars, int accuracy);\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dd_term.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Threshold(DdManager *ddman, DdNode *dd, double threshold);\nDdNode *DD_StrictThreshold(DdManager *ddman, DdNode *dd, double threshold);\nDdNode *DD_GreaterThan(DdManager *ddman, DdNode *dd, double threshold);\nDdNode *DD_GreaterThanEquals(DdManager *ddman, DdNode *dd, double threshold);\nDdNode *DD_LessThan(DdManager *ddman, DdNode *dd, double threshold);\nDdNode *DD_LessThanEquals(DdManager *ddman, DdNode *dd, double threshold);\nDdNode *DD_Equals(DdManager *ddman, DdNode *dd, double value);\nDdNode *DD_Interval(DdManager *ddman, DdNode *dd, double lower, double upper);\nDdNode *DD_RoundOff(DdManager *ddman, DdNode *dd, int places);\nbool DD_EqualSupNorm(DdManager *ddman, DdNode *dd1, DdNode *dd2, double epsilon);\nbool DD_EqualSupNormRel(DdManager *ddman, DdNode *dd1, DdNode *dd2, double epsilon);\ndouble DD_FindMin(DdManager *ddman, DdNode *dd);\ndouble DD_FindMinPositive(DdManager *ddman, DdNode *dd);\ndouble DD_FindMax(DdManager *ddman, DdNode *dd);\ndouble DD_FindMaxFinite(DdManager *ddman, DdNode *dd);\nDdNode *DD_RestrictToFirst(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\nbool DD_IsZeroOneMTBDD(DdManager *ddman, DdNode *dd);\n\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dd_vars.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_PermuteVariables(DdManager *ddman, DdNode *dd, DdNode **old_vars, DdNode **new_vars, int num_vars);\nDdNode *DD_SwapVariables(DdManager *ddman, DdNode *dd, DdNode **old_vars, DdNode **new_vars, int num_vars);\nDdNode *DD_VariablesGreaterThan(DdManager *ddman, DdNode **x_vars, DdNode **y_vars, int num_vars);\nDdNode *DD_VariablesGreaterThanEquals(DdManager *ddman, DdNode **x_vars, DdNode **y_vars, int num_vars);\nDdNode *DD_VariablesLessThan(DdManager *ddman, DdNode **x_vars, DdNode **y_vars, int num_vars);\nDdNode *DD_VariablesLessThanEquals(DdManager *ddman, DdNode **x_vars, DdNode **y_vars, int num_vars);\nDdNode *DD_VariablesEquals(DdManager *ddman, DdNode **x_vars, DdNode **y_vars, int num_vars);\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/dv.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#ifndef DV_H\n#define DV_H\n\n//------------------------------------------------------------------------------\n\n#include <util.h>\n#include <cudd.h>\n#include <odd.h>\n\n// Flags for building Windows DLLs\n#ifdef __MINGW32__\n\t#define EXPORT __declspec(dllexport)\n#else\n\t#define EXPORT\n#endif\n\n// constants\n\n#define DV_GREATER_THAN_EQUALS\t1\n#define DV_GREATER_THAN\t\t\t2\n#define DV_LESS_THAN_EQUALS\t\t3\n#define DV_LESS_THAN\t\t\t4\n#define DV_INTERVAL\t\t\t\t5\n#define DV_CLOSE_ABS\t\t\t6\n#define DV_CLOSE_REL\t\t\t7\n\n// distinct vectors\n\ntypedef struct DistVector DistVector;\n\nstruct DistVector\n{\n\tdouble *dist;\n\tint num_dist;\n\tunsigned short *ptrs;\n\t\n\tEXPORT DistVector();\n\tEXPORT ~DistVector();\n};\n\n// function prototypes\n\nEXPORT double *mtbdd_to_double_vector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT double *mtbdd_to_double_vector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd, double *res);\nEXPORT DdNode *double_vector_to_mtbdd(DdManager *ddman, double *vec, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT DdNode *double_vector_to_bdd(DdManager *ddman, double *vec, int rel_op, double value, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT DdNode *double_vector_to_bdd(DdManager *ddman, double *vec, int rel_op, double value1, double value2, DdNode **vars, int num_vars, ODDNode *odd);\n\nEXPORT void filter_double_vector(DdManager *ddman, double *vec, DdNode *filter, double d, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT void max_double_vector_mtbdd(DdManager *ddman, double *vec, DdNode *vec2, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT double get_first_from_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT double min_double_vector_over_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT double max_double_vector_over_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT double max_finite_double_vector_over_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT double sum_double_vector_over_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT double sum_double_vector_over_mtbdd(DdManager *ddman, double *vec, DdNode *mult, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT void sum_double_vector_over_dd_vars(DdManager *ddman, double *vec, double *vec2, DdNode **vars, int num_vars, int first_var, int last_var, ODDNode *odd, ODDNode *odd2);\n\nEXPORT DistVector *double_vector_to_dist(double *v, int n);\n\nEXPORT bool doubles_are_close_abs(double d1, double d2, double epsilon);\nEXPORT bool doubles_are_close_rel(double d1, double d2, double epsilon);\n\n//------------------------------------------------------------------------------\n\n#endif\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/hybrid.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Rashid Mehmood <rxm@cs.bham.uc.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <inttypes.h>\n#include <util.h>\n#include <cudd.h>\n#include <odd.h>\n\n//------------------------------------------------------------------------------\n\n// hdd data structure definitions\n\n// hybrid mtbdd node (based on structure of CUDD nodes)\n\ntypedef struct HDDNode HDDNode;\n\ntypedef struct HDDKids {\n\tHDDNode *e;\n\tHDDNode *t;\n} HDDKids;\n\nstruct HDDNode\n{\n\tunion {\n\t\tdouble val;\t\t// for terminals\n\t\tHDDKids kids;\t// for non-terminals\n\t} type;\n\tunion {\t\t\t\t// offset info (else edge, used most often)\n\t\tint val;\t\t// integer offset\n\t\tODDNode* ptr;\t// temporary pointer storage used during construction\n\t} off;\n\tunion {\t\t\t\t// 2nd offset info (then edge, rarely used)\n\t\tint val;\t\t// integer offset\n\t\tODDNode* ptr;\t// temporary pointer storage used during construction\n\t} off2;\n\tunion {\t\t\t\t// sparse matrix pointer\n\t\tvoid *ptr;\t\t// the pointer (void* because can be of different types)\n\t\tint val;\t\t// temporary storage for integer used during construction\n\t} sm;\n\tHDDNode *next;\n};\n\n// hybrid mtbdd block storage (for sor/gs)\n// (sparse storage - either row/col major)\n\ntypedef struct HDDBlocks HDDBlocks;\n\nstruct HDDBlocks\n{\n\t// stats\n\tint n;\n\tint nnz;\n\tint max;\n\t// arrays for sparse storage\n\tHDDNode **blocks;\n\tunsigned int *rowscols;\n\tunsigned char *counts;\n\tint *offsets;\n\t// is counts array used for counts?\n\t// (as opposed to starts)\n\tbool use_counts;\n\t// distinct pointers info\n\tint dist_num;\n\tint dist_shift;\n\tint dist_mask;\n\t\n\tHDDBlocks();\n\t~HDDBlocks();\n};\n\n// hybrid mtbdd matrix\n\ntypedef struct HDDMatrix HDDMatrix;\n\nstruct HDDMatrix\n{\n\t// flags\n\tbool row_major; \n\tbool compact_b;\n\tbool compact_sm;\n\t// stats (levels)\n\tint num_levels;\n\tint l_b;\n\tint l_sm;\n\t// stats (counters)\n\tint num_nodes;\n\tint num_b;\n\tint num_sm;\n\t// stats (memory)\n\tdouble mem_nodes;\n\tdouble mem_b;\n\tdouble mem_sm;\n\t// node storage\n\tHDDNode **row_lists;\n\tHDDNode **col_lists;\n\tHDDNode ***row_tables;\n\tHDDNode ***col_tables;\n\tint *row_sizes;\n\tint *col_sizes;\n\t// pointers to special nodes\n\tHDDNode *top;\n\tHDDNode *zero;\n\t// odd\n\tODDNode *odd;\n\t// block stuff\n\tHDDBlocks *blocks;\n\t// distinct values info\n\tdouble *dist;\n\tint dist_num;\n\tint dist_shift;\n\tint dist_mask;\n\t\n\tHDDMatrix();\n\t~HDDMatrix();\n};\n\n// hybrid mtbdd matrices\n\ntypedef struct HDDMatrices HDDMatrices;\n\nstruct HDDMatrices\n{\n\t// flags (counts of)\n\tint compact_sm;\n\t// stats\n\tint num_levels;\n\tint l_sm_min;\n\tint l_sm_max;\n\tint num_nodes;\n\tint num_sm;\n\tdouble mem_nodes;\n\tdouble mem_sm;\n\t// num matrices (choices)\n\tint nm;\n\t// matrices (choices)\n\tHDDMatrix **choices;\n\t// and their bdd cubes\n\tDdNode **cubes;\n\t\n\tHDDMatrices();\n\t~HDDMatrices();\n};\n\n//------------------------------------------------------------------------------\n\n// function prototypes\n\nHDDMatrix *build_hdd_matrix(DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool row_major);\nvoid split_hdd_matrix(HDDMatrix *hddm, bool compact_b, bool meet);\nvoid add_sparse_matrices(HDDMatrix *hm, bool compact_sm, bool diags_meet);\n\nHDDMatrix *build_hdd_matrix(DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool row_major, bool transpose);\nvoid split_hdd_matrix(HDDMatrix *hddm, bool compact_b, bool meet, bool transpose);\nvoid add_sparse_matrices(HDDMatrix *hm, bool compact_sm, bool diags_meet, bool transpose);\n\nHDDMatrices *build_hdd_matrices_mdp(DdNode *mdp, HDDMatrices *existing_mdp, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, ODDNode *odd);\nvoid add_sparse_matrices_mdp(HDDMatrices *hddms, bool compact_sm);\n\nvoid rearrange_hdd_blocks(HDDMatrix *hddm, bool ooc);\ndouble *hdd_negative_row_sums(HDDMatrix *hddm, int n);\n\ndouble *hdd_negative_row_sums(HDDMatrix *hddm, int n, bool transpose);\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/iv.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#ifndef IV_H\n#define IV_H\n\n//------------------------------------------------------------------------------\n\n#include <util.h>\n#include <cudd.h>\n#include <odd.h>\n\n// Flags for building Windows DLLs\n#ifdef __MINGW32__\n\t#define EXPORT __declspec(dllexport)\n#else\n\t#define EXPORT\n#endif\n\n// function prototypes\n\nEXPORT int *mtbdd_to_integer_vector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT int *mtbdd_to_integer_vector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd, int *res);\nEXPORT DdNode *integer_vector_to_mtbdd(DdManager *ddman, int *vec, DdNode **vars, int num_vars, ODDNode *odd);\n\n//------------------------------------------------------------------------------\n\n#endif\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/jni/dv_DoubleVector.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class dv_DoubleVector */\n\n#ifndef _Included_dv_DoubleVector\n#define _Included_dv_DoubleVector\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_CreateZeroVector\n * Signature: (I)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1CreateZeroVector\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_ConvertMTBDD\n * Signature: (JJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1ConvertMTBDD\n  (JNIEnv *, jobject, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_GetElement\n * Signature: (JII)D\n */\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1GetElement\n  (JNIEnv *, jobject, jlong, jint, jint);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_SetElement\n * Signature: (JIID)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1SetElement\n  (JNIEnv *, jobject, jlong, jint, jint, jdouble);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_SetAllElements\n * Signature: (JID)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1SetAllElements\n  (JNIEnv *, jobject, jlong, jint, jdouble);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_RoundOff\n * Signature: (JII)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1RoundOff\n  (JNIEnv *, jobject, jlong, jint, jint);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_SubtractFromOne\n * Signature: (JI)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1SubtractFromOne\n  (JNIEnv *, jobject, jlong, jint);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_Add\n * Signature: (JIJ)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1Add\n  (JNIEnv *, jobject, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_TimesConstant\n * Signature: (JID)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1TimesConstant\n  (JNIEnv *, jobject, jlong, jint, jdouble);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_DotProduct\n * Signature: (JIJ)D\n */\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1DotProduct\n  (JNIEnv *, jobject, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_Filter\n * Signature: (JJDJIJ)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1Filter\n  (JNIEnv *, jobject, jlong, jlong, jdouble, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_MaxMTBDD\n * Signature: (JJJIJ)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1MaxMTBDD\n  (JNIEnv *, jobject, jlong, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_Clear\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1Clear\n  (JNIEnv *, jobject, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_GetNNZ\n * Signature: (JI)I\n */\nJNIEXPORT jint JNICALL Java_dv_DoubleVector_DV_1GetNNZ\n  (JNIEnv *, jobject, jlong, jint);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_FirstFromBDD\n * Signature: (JJJIJ)D\n */\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1FirstFromBDD\n  (JNIEnv *, jobject, jlong, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_MinOverBDD\n * Signature: (JJJIJ)D\n */\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1MinOverBDD\n  (JNIEnv *, jobject, jlong, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_MaxOverBDD\n * Signature: (JJJIJ)D\n */\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1MaxOverBDD\n  (JNIEnv *, jobject, jlong, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_MaxFiniteOverBDD\n * Signature: (JJJIJ)D\n */\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1MaxFiniteOverBDD\n  (JNIEnv *, jobject, jlong, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_SumOverBDD\n * Signature: (JJJIJ)D\n */\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1SumOverBDD\n  (JNIEnv *, jobject, jlong, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_SumOverMTBDD\n * Signature: (JJJIJ)D\n */\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1SumOverMTBDD\n  (JNIEnv *, jobject, jlong, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_SumOverDDVars\n * Signature: (JJJIIIJJ)V\n */\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1SumOverDDVars\n  (JNIEnv *, jobject, jlong, jlong, jlong, jint, jint, jint, jlong, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_BDDGreaterThanEquals\n * Signature: (JDJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1BDDGreaterThanEquals\n  (JNIEnv *, jobject, jlong, jdouble, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_BDDGreaterThan\n * Signature: (JDJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1BDDGreaterThan\n  (JNIEnv *, jobject, jlong, jdouble, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_BDDLessThanEquals\n * Signature: (JDJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1BDDLessThanEquals\n  (JNIEnv *, jobject, jlong, jdouble, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_BDDLessThan\n * Signature: (JDJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1BDDLessThan\n  (JNIEnv *, jobject, jlong, jdouble, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_BDDInterval\n * Signature: (JDDJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1BDDInterval\n  (JNIEnv *, jobject, jlong, jdouble, jdouble, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_BDDCloseValueAbs\n * Signature: (JDDJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1BDDCloseValueAbs\n  (JNIEnv *, jobject, jlong, jdouble, jdouble, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_BDDCloseValueRel\n * Signature: (JDDJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1BDDCloseValueRel\n  (JNIEnv *, jobject, jlong, jdouble, jdouble, jlong, jint, jlong);\n\n/*\n * Class:     dv_DoubleVector\n * Method:    DV_ConvertToMTBDD\n * Signature: (JJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1ConvertToMTBDD\n  (JNIEnv *, jobject, jlong, jlong, jint, jlong);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/dv_IntegerVector.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class dv_IntegerVector */\n\n#ifndef _Included_dv_IntegerVector\n#define _Included_dv_IntegerVector\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     dv_IntegerVector\n * Method:    IV_CreateZeroVector\n * Signature: (I)J\n */\nJNIEXPORT jlong JNICALL Java_dv_IntegerVector_IV_1CreateZeroVector\n  (JNIEnv *, jobject, jint);\n\n/*\n * Class:     dv_IntegerVector\n * Method:    IV_ConvertMTBDD\n * Signature: (JJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_dv_IntegerVector_IV_1ConvertMTBDD\n  (JNIEnv *, jobject, jlong, jlong, jint, jlong);\n\n/*\n * Class:     dv_IntegerVector\n * Method:    IV_GetElement\n * Signature: (JII)I\n */\nJNIEXPORT jint JNICALL Java_dv_IntegerVector_IV_1GetElement\n  (JNIEnv *, jobject, jlong, jint, jint);\n\n/*\n * Class:     dv_IntegerVector\n * Method:    IV_SetElement\n * Signature: (JIII)V\n */\nJNIEXPORT void JNICALL Java_dv_IntegerVector_IV_1SetElement\n  (JNIEnv *, jobject, jlong, jint, jint, jint);\n\n/*\n * Class:     dv_IntegerVector\n * Method:    IV_SetAllElements\n * Signature: (JII)V\n */\nJNIEXPORT void JNICALL Java_dv_IntegerVector_IV_1SetAllElements\n  (JNIEnv *, jobject, jlong, jint, jint);\n\n/*\n * Class:     dv_IntegerVector\n * Method:    IV_Clear\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_dv_IntegerVector_IV_1Clear\n  (JNIEnv *, jobject, jlong);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/hybrid_PrismHybrid.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class hybrid_PrismHybrid */\n\n#ifndef _Included_hybrid_PrismHybrid\n#define _Included_hybrid_PrismHybrid\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_ProbBoundedUntil\n * Signature: (JJJIJIJJI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1ProbBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_ProbUntil\n * Signature: (JJJIJIJJ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1ProbUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_ProbUntilInterval\n * Signature: (JJJIJIJJI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1ProbUntilInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_ProbCumulReward\n * Signature: (JJJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1ProbCumulReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_ProbInstReward\n * Signature: (JJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1ProbInstReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_ProbReachReward\n * Signature: (JJJJJIJIJJJ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1ProbReachReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_ProbReachRewardInterval\n * Signature: (JJJJJIJIJJJJJI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1ProbReachRewardInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jlong, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_ProbTransient\n * Signature: (JJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1ProbTransient\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_NondetBoundedUntil\n * Signature: (JJJIJIJIJJIZ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1NondetBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jint, jboolean);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_NondetUntil\n * Signature: (JJJIJIJIJJZ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1NondetUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jboolean);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_NondetUntilInterval\n * Signature: (JJJIJIJIJJZI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1NondetUntilInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jboolean, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_NondetReachReward\n * Signature: (JJJJJIJIJIJJJZ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1NondetReachReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_StochBoundedUntil\n * Signature: (JJJIJIJJDJ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1StochBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jdouble, jlong);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_StochCumulReward\n * Signature: (JJJJJIJID)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1StochCumulReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jdouble);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_StochSteadyState\n * Signature: (JJJJIJI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1StochSteadyState\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_StochTransient\n * Signature: (JJJJIJID)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1StochTransient\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jdouble);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_Power\n * Signature: (JJIJIJJJZ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1Power\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_PowerInterval\n * Signature: (JJIJIJJJJZI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1PowerInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_JOR\n * Signature: (JJIJIJJJZZD)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1JOR\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean, jboolean, jdouble);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_JORInterval\n * Signature: (JJIJIJJJJZZDI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1JORInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jboolean, jdouble, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_SOR\n * Signature: (JJIJIJJJZZDZ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1SOR\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean, jboolean, jdouble, jboolean);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_SORInterval\n * Signature: (JJIJIJJJJZZDZI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1SORInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jboolean, jdouble, jboolean, jint);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_PSOR\n * Signature: (JJIJIJJJZZDZ)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1PSOR\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean, jboolean, jdouble, jboolean);\n\n/*\n * Class:     hybrid_PrismHybrid\n * Method:    PH_PSORInterval\n * Signature: (JJIJIJJJJZZDZI)J\n */\nJNIEXPORT jlong JNICALL Java_hybrid_PrismHybrid_PH_1PSORInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jboolean, jdouble, jboolean, jint);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/jdd_JDD.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class jdd_JDD */\n\n#ifndef _Included_jdd_JDD\n#define _Included_jdd_JDD\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n#undef jdd_JDD_PLUS\n#define jdd_JDD_PLUS 1L\n#undef jdd_JDD_MINUS\n#define jdd_JDD_MINUS 2L\n#undef jdd_JDD_TIMES\n#define jdd_JDD_TIMES 3L\n#undef jdd_JDD_DIVIDE\n#define jdd_JDD_DIVIDE 4L\n#undef jdd_JDD_MIN\n#define jdd_JDD_MIN 5L\n#undef jdd_JDD_MAX\n#define jdd_JDD_MAX 6L\n#undef jdd_JDD_EQUALS\n#define jdd_JDD_EQUALS 7L\n#undef jdd_JDD_NOTEQUALS\n#define jdd_JDD_NOTEQUALS 8L\n#undef jdd_JDD_GREATERTHAN\n#define jdd_JDD_GREATERTHAN 9L\n#undef jdd_JDD_GREATERTHANEQUALS\n#define jdd_JDD_GREATERTHANEQUALS 10L\n#undef jdd_JDD_LESSTHAN\n#define jdd_JDD_LESSTHAN 11L\n#undef jdd_JDD_LESSTHANEQUALS\n#define jdd_JDD_LESSTHANEQUALS 12L\n#undef jdd_JDD_FLOOR\n#define jdd_JDD_FLOOR 13L\n#undef jdd_JDD_CEIL\n#define jdd_JDD_CEIL 14L\n#undef jdd_JDD_POW\n#define jdd_JDD_POW 15L\n#undef jdd_JDD_MOD\n#define jdd_JDD_MOD 16L\n#undef jdd_JDD_LOGXY\n#define jdd_JDD_LOGXY 17L\n#undef jdd_JDD_ZERO_ONE\n#define jdd_JDD_ZERO_ONE 1L\n#undef jdd_JDD_LOW\n#define jdd_JDD_LOW 2L\n#undef jdd_JDD_NORMAL\n#define jdd_JDD_NORMAL 3L\n#undef jdd_JDD_HIGH\n#define jdd_JDD_HIGH 4L\n#undef jdd_JDD_LIST\n#define jdd_JDD_LIST 5L\n#undef jdd_JDD_CMU\n#define jdd_JDD_CMU 1L\n#undef jdd_JDD_BOULDER\n#define jdd_JDD_BOULDER 2L\n/*\n * Class:     jdd_JDD\n * Method:    GetCUDDManager\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_GetCUDDManager\n  (JNIEnv *, jclass);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_SetOutputStream\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1SetOutputStream\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GetOutputStream\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1GetOutputStream\n  (JNIEnv *, jclass);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_InitialiseCUDD\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1InitialiseCUDD__\n  (JNIEnv *, jclass);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_InitialiseCUDD\n * Signature: (JD)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1InitialiseCUDD__JD\n  (JNIEnv *, jclass, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_SetCUDDMaxMem\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1SetCUDDMaxMem\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_SetCUDDEpsilon\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1SetCUDDEpsilon\n  (JNIEnv *, jclass, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_CloseDownCUDD\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1CloseDownCUDD\n  (JNIEnv *, jclass, jboolean);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Ref\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1Ref\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Deref\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1Deref\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintCacheInfo\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintCacheInfo\n  (JNIEnv *, jclass);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GetErrorFlag\n * Signature: ()Z\n */\nJNIEXPORT jboolean JNICALL Java_jdd_JDD_DD_1GetErrorFlag\n  (JNIEnv *, jclass);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Create\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Create\n  (JNIEnv *, jclass);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Constant\n * Signature: (D)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Constant\n  (JNIEnv *, jclass, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PlusInfinity\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1PlusInfinity\n  (JNIEnv *, jclass);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_MinusInfinity\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1MinusInfinity\n  (JNIEnv *, jclass);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Var\n * Signature: (I)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Var\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Not\n * Signature: (J)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Not\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Or\n * Signature: (JJ)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Or\n  (JNIEnv *, jclass, jlong, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_And\n * Signature: (JJ)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1And\n  (JNIEnv *, jclass, jlong, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Xor\n * Signature: (JJ)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Xor\n  (JNIEnv *, jclass, jlong, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Implies\n * Signature: (JJ)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Implies\n  (JNIEnv *, jclass, jlong, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Apply\n * Signature: (IJJ)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Apply\n  (JNIEnv *, jclass, jint, jlong, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_MonadicApply\n * Signature: (IJ)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1MonadicApply\n  (JNIEnv *, jclass, jint, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Restrict\n * Signature: (JJ)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Restrict\n  (JNIEnv *, jclass, jlong, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ITE\n * Signature: (JJJ)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1ITE\n  (JNIEnv *, jclass, jlong, jlong, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PermuteVariables\n * Signature: (JJJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1PermuteVariables\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_SwapVariables\n * Signature: (JJJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1SwapVariables\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_VariablesGreaterThan\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1VariablesGreaterThan\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_VariablesGreaterThanEquals\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1VariablesGreaterThanEquals\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_VariablesLessThan\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1VariablesLessThan\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_VariablesLessThanEquals\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1VariablesLessThanEquals\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_VariablesEquals\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1VariablesEquals\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ThereExists\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1ThereExists\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ForAll\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1ForAll\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_SumAbstract\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1SumAbstract\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ProductAbstract\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1ProductAbstract\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_MinAbstract\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1MinAbstract\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_MaxAbstract\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1MaxAbstract\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GreaterThan\n * Signature: (JD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1GreaterThan\n  (JNIEnv *, jclass, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GreaterThanEquals\n * Signature: (JD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1GreaterThanEquals\n  (JNIEnv *, jclass, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_LessThan\n * Signature: (JD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1LessThan\n  (JNIEnv *, jclass, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_LessThanEquals\n * Signature: (JD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1LessThanEquals\n  (JNIEnv *, jclass, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Equals\n * Signature: (JD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Equals\n  (JNIEnv *, jclass, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Interval\n * Signature: (JDD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Interval\n  (JNIEnv *, jclass, jlong, jdouble, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_RoundOff\n * Signature: (JI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1RoundOff\n  (JNIEnv *, jclass, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_EqualSupNorm\n * Signature: (JJD)Z\n */\nJNIEXPORT jboolean JNICALL Java_jdd_JDD_DD_1EqualSupNorm\n  (JNIEnv *, jclass, jlong, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_FindMin\n * Signature: (J)D\n */\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1FindMin\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_FindMinPositive\n * Signature: (J)D\n */\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1FindMinPositive\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_FindMax\n * Signature: (J)D\n */\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1FindMax\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_FindMaxFinite\n * Signature: (J)D\n */\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1FindMaxFinite\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_RestrictToFirst\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1RestrictToFirst\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_IsZeroOneMTBDD\n * Signature: (J)Z\n */\nJNIEXPORT jboolean JNICALL Java_jdd_JDD_DD_1IsZeroOneMTBDD\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GetNumNodes\n * Signature: (J)I\n */\nJNIEXPORT jint JNICALL Java_jdd_JDD_DD_1GetNumNodes\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GetNumTerminals\n * Signature: (J)I\n */\nJNIEXPORT jint JNICALL Java_jdd_JDD_DD_1GetNumTerminals\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GetNumMinterms\n * Signature: (JI)D\n */\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1GetNumMinterms\n  (JNIEnv *, jclass, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GetNumPaths\n * Signature: (J)D\n */\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1GetNumPaths\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintInfo\n * Signature: (JI)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintInfo\n  (JNIEnv *, jclass, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintInfoBrief\n * Signature: (JI)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintInfoBrief\n  (JNIEnv *, jclass, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintSupport\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintSupport\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintSupportNames\n * Signature: (JLjava/util/List;)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintSupportNames\n  (JNIEnv *, jclass, jlong, jobject);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GetSupport\n * Signature: (J)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1GetSupport\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintTerminals\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintTerminals\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintTerminalsAndNumbers\n * Signature: (JI)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintTerminalsAndNumbers\n  (JNIEnv *, jclass, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_SetVectorElement\n * Signature: (JJIJD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1SetVectorElement\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_SetMatrixElement\n * Signature: (JJIJIJJD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1SetMatrixElement\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Set3DMatrixElement\n * Signature: (JJIJIJIJJJD)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Set3DMatrixElement\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jlong, jdouble);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_GetVectorElement\n * Signature: (JJIJ)D\n */\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1GetVectorElement\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Identity\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Identity\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Transpose\n * Signature: (JJJI)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1Transpose\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_MatrixMultiply\n * Signature: (JJJII)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1MatrixMultiply\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintVector\n * Signature: (JJII)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintVector\n  (JNIEnv *, jclass, jlong, jlong, jint, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintMatrix\n * Signature: (JJIJII)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintMatrix\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_PrintVectorFiltered\n * Signature: (JJJII)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintVectorFiltered\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jint);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ExportDDToDotFile\n * Signature: (JLjava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportDDToDotFile\n  (JNIEnv *, jclass, jlong, jstring);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ExportDDToDotFileLabelled\n * Signature: (JLjava/lang/String;Ljava/util/List;)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportDDToDotFileLabelled\n  (JNIEnv *, jclass, jlong, jstring, jobject);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ExportMatrixToPPFile\n * Signature: (JJIJILjava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportMatrixToPPFile\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jstring);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_Export3dMatrixToPPFile\n * Signature: (JJIJIJILjava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1Export3dMatrixToPPFile\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jint, jstring);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ExportMatrixToMatlabFile\n * Signature: (JJIJILjava/lang/String;Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportMatrixToMatlabFile\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jstring, jstring);\n\n/*\n * Class:     jdd_JDD\n * Method:    DD_ExportMatrixToSpyFile\n * Signature: (JJIJIILjava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportMatrixToSpyFile\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jint, jstring);\n\n/*\n * Class:     jdd_JDD\n * Method:    DebugJDD_GetRefCount\n * Signature: (J)I\n */\nJNIEXPORT jint JNICALL Java_jdd_JDD_DebugJDD_1GetRefCount\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDD\n * Method:    DebugJDD_GetExternalRefCounts\n * Signature: ()[J\n */\nJNIEXPORT jlongArray JNICALL Java_jdd_JDD_DebugJDD_1GetExternalRefCounts\n  (JNIEnv *, jclass);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/jdd_JDDNode.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class jdd_JDDNode */\n\n#ifndef _Included_jdd_JDDNode\n#define _Included_jdd_JDDNode\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     jdd_JDDNode\n * Method:    DDN_IsConstant\n * Signature: (J)Z\n */\nJNIEXPORT jboolean JNICALL Java_jdd_JDDNode_DDN_1IsConstant\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDDNode\n * Method:    DDN_GetIndex\n * Signature: (J)I\n */\nJNIEXPORT jint JNICALL Java_jdd_JDDNode_DDN_1GetIndex\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDDNode\n * Method:    DDN_GetValue\n * Signature: (J)D\n */\nJNIEXPORT jdouble JNICALL Java_jdd_JDDNode_DDN_1GetValue\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDDNode\n * Method:    DDN_GetThen\n * Signature: (J)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDDNode_DDN_1GetThen\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     jdd_JDDNode\n * Method:    DDN_GetElse\n * Signature: (J)J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDDNode_DDN_1GetElse\n  (JNIEnv *, jclass, jlong);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/jdd_JDDVars.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class jdd_JDDVars */\n\n#ifndef _Included_jdd_JDDVars\n#define _Included_jdd_JDDVars\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     jdd_JDDVars\n * Method:    DDV_BuildArray\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_jdd_JDDVars_DDV_1BuildArray\n  (JNIEnv *, jobject);\n\n/*\n * Class:     jdd_JDDVars\n * Method:    DDV_FreeArray\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_jdd_JDDVars_DDV_1FreeArray\n  (JNIEnv *, jobject, jlong);\n\n/*\n * Class:     jdd_JDDVars\n * Method:    DDV_GetIndex\n * Signature: (J)I\n */\nJNIEXPORT jint JNICALL Java_jdd_JDDVars_DDV_1GetIndex\n  (JNIEnv *, jobject, jlong);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/mtbdd_PrismMTBDD.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class mtbdd_PrismMTBDD */\n\n#ifndef _Included_mtbdd_PrismMTBDD\n#define _Included_mtbdd_PrismMTBDD\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_Reachability\n * Signature: (JJIJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1Reachability\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_Prob1\n * Signature: (JJJIJIJJJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob1\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_Prob0\n * Signature: (JJJIJIJJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob0\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_Prob1E\n * Signature: (JJJIJIJIJJJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob1E\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_Prob1A\n * Signature: (JJJJIJIJIJJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob1A\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_Prob0E\n * Signature: (JJJJIJIJIJJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob0E\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_Prob0A\n * Signature: (JJJIJIJIJJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob0A\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ProbBoundedUntil\n * Signature: (JJJIJIJJI)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ProbUntil\n * Signature: (JJJIJIJJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ProbUntilInterval\n * Signature: (JJJIJIJJI)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbUntilInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ProbCumulReward\n * Signature: (JJJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbCumulReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ProbInstReward\n * Signature: (JJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbInstReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ProbReachReward\n * Signature: (JJJJJIJIJJJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbReachReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ProbReachRewardInterval\n * Signature: (JJJJJIJIJJJJJI)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbReachRewardInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jlong, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ProbTransient\n * Signature: (JJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbTransient\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_NondetBoundedUntil\n * Signature: (JJJJIJIJIJJIZ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jint, jboolean);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_NondetUntil\n * Signature: (JJJJIJIJIJJZ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jboolean);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_NondetUntilInterval\n * Signature: (JJJJIJIJIJJZI)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetUntilInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jboolean, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_NondetInstReward\n * Signature: (JJJJJIJIJIIZJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetInstReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jint, jboolean, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_NondetReachReward\n * Signature: (JJJJJJIJIJIJJJZ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetReachReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_NondetReachRewardInterval\n * Signature: (JJJJJJIJIJIJJJJJZI)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetReachRewardInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jlong, jboolean, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_StochBoundedUntil\n * Signature: (JJJIJIJJDJ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1StochBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jdouble, jlong);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_StochCumulReward\n * Signature: (JJJJJIJID)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1StochCumulReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jdouble);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_StochSteadyState\n * Signature: (JJJJIJI)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1StochSteadyState\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_StochTransient\n * Signature: (JJJJIJID)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1StochTransient\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jdouble);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ExportVector\n * Signature: (JLjava/lang/String;JIJILjava/lang/String;Ljava/lang/String;Z)I\n */\nJNIEXPORT jint JNICALL Java_mtbdd_PrismMTBDD_PM_1ExportVector\n  (JNIEnv *, jclass, jlong, jstring, jlong, jint, jlong, jint, jstring, jstring, jboolean);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ExportMatrix\n * Signature: (JLjava/lang/String;JIJIJILjava/lang/String;Ljava/lang/String;Z)I\n */\nJNIEXPORT jint JNICALL Java_mtbdd_PrismMTBDD_PM_1ExportMatrix\n  (JNIEnv *, jclass, jlong, jstring, jlong, jint, jlong, jint, jlong, jint, jstring, jstring, jboolean);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_ExportLabels\n * Signature: ([J[Ljava/lang/String;Ljava/lang/String;JIJILjava/lang/String;)I\n */\nJNIEXPORT jint JNICALL Java_mtbdd_PrismMTBDD_PM_1ExportLabels\n  (JNIEnv *, jclass, jlongArray, jobjectArray, jstring, jlong, jint, jlong, jint, jstring);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_Power\n * Signature: (JJIJIJJJZ)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1Power\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_PowerInterval\n * Signature: (JJIJIJJJJZI)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1PowerInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jint);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_JOR\n * Signature: (JJIJIJJJZD)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1JOR\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean, jdouble);\n\n/*\n * Class:     mtbdd_PrismMTBDD\n * Method:    PM_JORInterval\n * Signature: (JJIJIJJJJZDI)J\n */\nJNIEXPORT jlong JNICALL Java_mtbdd_PrismMTBDD_PM_1JORInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jdouble, jint);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/odd_ODDUtils.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class odd_ODDUtils */\n\n#ifndef _Included_odd_ODDUtils\n#define _Included_odd_ODDUtils\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_BuildODD\n * Signature: (JJI)J\n */\nJNIEXPORT jlong JNICALL Java_odd_ODDUtils_ODD_1BuildODD\n  (JNIEnv *, jclass, jlong, jlong, jint);\n\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_ClearODD\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_odd_ODDUtils_ODD_1ClearODD\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_GetNumODDNodes\n * Signature: ()I\n */\nJNIEXPORT jint JNICALL Java_odd_ODDUtils_ODD_1GetNumODDNodes\n  (JNIEnv *, jclass);\n\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_GetIndexOfFirstFromDD\n * Signature: (JJJI)I\n */\nJNIEXPORT jint JNICALL Java_odd_ODDUtils_ODD_1GetIndexOfFirstFromDD\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint);\n\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_SingleIndexToDD\n * Signature: (IJJI)J\n */\nJNIEXPORT jlong JNICALL Java_odd_ODDUtils_ODD_1SingleIndexToDD\n  (JNIEnv *, jclass, jint, jlong, jlong, jint);\n\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_GetTOff\n * Signature: (J)J\n */\nJNIEXPORT jlong JNICALL Java_odd_ODDUtils_ODD_1GetTOff\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_GetEOff\n * Signature: (J)J\n */\nJNIEXPORT jlong JNICALL Java_odd_ODDUtils_ODD_1GetEOff\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_GetThen\n * Signature: (J)J\n */\nJNIEXPORT jlong JNICALL Java_odd_ODDUtils_ODD_1GetThen\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     odd_ODDUtils\n * Method:    ODD_GetElse\n * Signature: (J)J\n */\nJNIEXPORT jlong JNICALL Java_odd_ODDUtils_ODD_1GetElse\n  (JNIEnv *, jclass, jlong);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/prism_NativeIntArray.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class prism_NativeIntArray */\n\n#ifndef _Included_prism_NativeIntArray\n#define _Included_prism_NativeIntArray\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     prism_NativeIntArray\n * Method:    NIA_CreateArray\n * Signature: (I)J\n */\nJNIEXPORT jlong JNICALL Java_prism_NativeIntArray_NIA_1CreateArray\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_NativeIntArray\n * Method:    NIA_DeleteArray\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_prism_NativeIntArray_NIA_1DeleteArray\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     prism_NativeIntArray\n * Method:    NIA_Get\n * Signature: (JI)I\n */\nJNIEXPORT jint JNICALL Java_prism_NativeIntArray_NIA_1Get\n  (JNIEnv *, jclass, jlong, jint);\n\n/*\n * Class:     prism_NativeIntArray\n * Method:    NIA_Set\n * Signature: (JII)V\n */\nJNIEXPORT void JNICALL Java_prism_NativeIntArray_NIA_1Set\n  (JNIEnv *, jclass, jlong, jint, jint);\n\n/*\n * Class:     prism_NativeIntArray\n * Method:    NIA_SetAll\n * Signature: (JIII)V\n */\nJNIEXPORT void JNICALL Java_prism_NativeIntArray_NIA_1SetAll\n  (JNIEnv *, jclass, jlong, jint, jint, jint);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/prism_PrismNative.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class prism_PrismNative */\n\n#ifndef _Included_prism_PrismNative\n#define _Included_prism_PrismNative\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     prism_PrismNative\n * Method:    PN_FreeGlobalRefs\n * Signature: ()V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1FreeGlobalRefs\n  (JNIEnv *, jclass);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetPrism\n * Signature: (Lprism/Prism;)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetPrism\n  (JNIEnv *, jclass, jobject);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetCUDDManager\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetCUDDManager\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetMainLog\n * Signature: (Lprism/PrismLog;)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetMainLog\n  (JNIEnv *, jclass, jobject);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_GetErrorMessage\n * Signature: ()Ljava/lang/String;\n */\nJNIEXPORT jstring JNICALL Java_prism_PrismNative_PN_1GetErrorMessage\n  (JNIEnv *, jclass);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetExportIterations\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetExportIterations\n  (JNIEnv *, jclass, jboolean);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetCompact\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetCompact\n  (JNIEnv *, jclass, jboolean);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetLinEqMethod\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetLinEqMethod\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetLinEqMethodParam\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetLinEqMethodParam\n  (JNIEnv *, jclass, jdouble);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetTermCrit\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetTermCrit\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetTermCritParam\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetTermCritParam\n  (JNIEnv *, jclass, jdouble);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetMaxIters\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetMaxIters\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetExportModelPrecision\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetExportModelPrecision\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetSBMaxMem\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetSBMaxMem\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetNumSBLevels\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetNumSBLevels\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetSORMaxMem\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetSORMaxMem\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetNumSORLevels\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetNumSORLevels\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetDoSSDetect\n * Signature: (Z)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetDoSSDetect\n  (JNIEnv *, jclass, jboolean);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetExportAdv\n * Signature: (I)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetExportAdv\n  (JNIEnv *, jclass, jint);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetExportAdvFilename\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetExportAdvFilename\n  (JNIEnv *, jclass, jstring);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetDefaultExportIterationsFilename\n * Signature: (Ljava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetDefaultExportIterationsFilename\n  (JNIEnv *, jclass, jstring);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetWorkingDirectory\n * Signature: (Ljava/lang/String;)I\n */\nJNIEXPORT jint JNICALL Java_prism_PrismNative_PN_1SetWorkingDirectory\n  (JNIEnv *, jclass, jstring);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_SetLastErrorBound\n * Signature: (D)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetLastErrorBound\n  (JNIEnv *, jclass, jdouble);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_GetLastErrorBound\n * Signature: ()D\n */\nJNIEXPORT jdouble JNICALL Java_prism_PrismNative_PN_1GetLastErrorBound\n  (JNIEnv *, jclass);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_GetStdout\n * Signature: ()J\n */\nJNIEXPORT jlong JNICALL Java_prism_PrismNative_PN_1GetStdout\n  (JNIEnv *, jclass);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_OpenFile\n * Signature: (Ljava/lang/String;)J\n */\nJNIEXPORT jlong JNICALL Java_prism_PrismNative_PN_1OpenFile\n  (JNIEnv *, jclass, jstring);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_OpenFileAppend\n * Signature: (Ljava/lang/String;)J\n */\nJNIEXPORT jlong JNICALL Java_prism_PrismNative_PN_1OpenFileAppend\n  (JNIEnv *, jclass, jstring);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_PrintToFile\n * Signature: (JLjava/lang/String;)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1PrintToFile\n  (JNIEnv *, jclass, jlong, jstring);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_FlushFile\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1FlushFile\n  (JNIEnv *, jclass, jlong);\n\n/*\n * Class:     prism_PrismNative\n * Method:    PN_CloseFile\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1CloseFile\n  (JNIEnv *, jclass, jlong);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/sparse_NDSparseMatrix.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class sparse_NDSparseMatrix */\n\n#ifndef _Included_sparse_NDSparseMatrix\n#define _Included_sparse_NDSparseMatrix\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     sparse_NDSparseMatrix\n * Method:    PS_NDGetActionIndex\n * Signature: (JII)I\n */\nJNIEXPORT jint JNICALL Java_sparse_NDSparseMatrix_PS_1NDGetActionIndex\n  (JNIEnv *, jclass, jlong, jint, jint);\n\n/*\n * Class:     sparse_NDSparseMatrix\n * Method:    PS_BuildNDSparseMatrix\n * Signature: (JJJIJIJI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_NDSparseMatrix_PS_1BuildNDSparseMatrix\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jint);\n\n/*\n * Class:     sparse_NDSparseMatrix\n * Method:    PS_BuildSubNDSparseMatrix\n * Signature: (JJJIJIJIJ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_NDSparseMatrix_PS_1BuildSubNDSparseMatrix\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong);\n\n/*\n * Class:     sparse_NDSparseMatrix\n * Method:    PS_AddActionsToNDSparseMatrix\n * Signature: (JJJJIJIJIJ)V\n */\nJNIEXPORT void JNICALL Java_sparse_NDSparseMatrix_PS_1AddActionsToNDSparseMatrix\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong);\n\n/*\n * Class:     sparse_NDSparseMatrix\n * Method:    PS_DeleteNDSparseMatrix\n * Signature: (J)V\n */\nJNIEXPORT void JNICALL Java_sparse_NDSparseMatrix_PS_1DeleteNDSparseMatrix\n  (JNIEnv *, jclass, jlong);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jni/sparse_PrismSparse.h",
    "content": "/* DO NOT EDIT THIS FILE - it is machine generated */\n#include <jni.h>\n/* Header for class sparse_PrismSparse */\n\n#ifndef _Included_sparse_PrismSparse\n#define _Included_sparse_PrismSparse\n#ifdef __cplusplus\nextern \"C\" {\n#endif\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ProbBoundedUntil\n * Signature: (JJJIJIJJI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1ProbBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ProbUntil\n * Signature: (JJJIJIJJ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1ProbUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ProbUntilInterval\n * Signature: (JJJIJIJJI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1ProbUntilInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ProbCumulReward\n * Signature: (JJJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1ProbCumulReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ProbInstReward\n * Signature: (JJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1ProbInstReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ProbReachReward\n * Signature: (JJJJJIJIJJJ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1ProbReachReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ProbReachRewardInterval\n * Signature: (JJJJJIJIJJJJJI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1ProbReachRewardInterval\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jlong, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ProbTransient\n * Signature: (JJJJIJII)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1ProbTransient\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetBoundedUntil\n * Signature: (JJJIJIJIJJIZ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1NondetBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jint, jboolean);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetUntil\n * Signature: (JJLjava/util/List;JJIJIJIJJZJ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1NondetUntil\n  (JNIEnv *, jclass, jlong, jlong, jobject, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jboolean, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetUntilInterval\n * Signature: (JJLjava/util/List;JJIJIJIJJZJI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1NondetUntilInterval\n  (JNIEnv *, jclass, jlong, jlong, jobject, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jboolean, jlong, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetCumulReward\n * Signature: (JJJJJIJIJIIZ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1NondetCumulReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jint, jboolean);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetInstReward\n * Signature: (JJJJIJIJIIZJ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1NondetInstReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jint, jboolean, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetReachReward\n * Signature: (JJLjava/util/List;JJJJIJIJIJJJZ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1NondetReachReward\n  (JNIEnv *, jclass, jlong, jlong, jobject, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetReachRewardInterval\n * Signature: (JJLjava/util/List;JJJJIJIJIJJJJJZI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1NondetReachRewardInterval\n  (JNIEnv *, jclass, jlong, jlong, jobject, jlong, jlong, jlong, jlong, jint, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jlong, jboolean, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetMultiObj\n * Signature: (JJIJIJIZJJJLjava/util/List;[J[I[J[D[I)[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_sparse_PrismSparse_PS_1NondetMultiObj\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jint, jboolean, jlong, jlong, jlong, jobject, jlongArray, jintArray, jlongArray, jdoubleArray, jintArray);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetMultiObjGS\n * Signature: (JJIJIJIZJJJ[J[J[D)[D\n */\nJNIEXPORT jdoubleArray JNICALL Java_sparse_PrismSparse_PS_1NondetMultiObjGS\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jint, jboolean, jlong, jlong, jlong, jlongArray, jlongArray, jdoubleArray);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetMultiReach\n * Signature: (JJLjava/util/List;JJIJIJI[J[I[DJJ)D\n */\nJNIEXPORT jdouble JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReach\n  (JNIEnv *, jclass, jlong, jlong, jobject, jlong, jlong, jint, jlong, jint, jlong, jint, jlongArray, jintArray, jdoubleArray, jlong, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetMultiReach1\n * Signature: (JJLjava/util/List;JJIJIJI[J[J[I[I[DJJ)D\n */\nJNIEXPORT jdouble JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReach1\n  (JNIEnv *, jclass, jlong, jlong, jobject, jlong, jlong, jint, jlong, jint, jlong, jint, jlongArray, jlongArray, jintArray, jintArray, jdoubleArray, jlong, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetMultiReachReward\n * Signature: (JJLjava/util/List;JJIJIJI[J[I[D[I[DJJ[JJ)D\n */\nJNIEXPORT jdouble JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReachReward\n  (JNIEnv *, jclass, jlong, jlong, jobject, jlong, jlong, jint, jlong, jint, jlong, jint, jlongArray, jintArray, jdoubleArray, jintArray, jdoubleArray, jlong, jlong, jlongArray, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_NondetMultiReachReward1\n * Signature: (JJLjava/util/List;JJIJIJI[J[J[I[I[D[I[DJJ[JJ)D\n */\nJNIEXPORT jdouble JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReachReward1\n  (JNIEnv *, jclass, jlong, jlong, jobject, jlong, jlong, jint, jlong, jint, jlong, jint, jlongArray, jlongArray, jintArray, jintArray, jdoubleArray, jintArray, jdoubleArray, jlong, jlong, jlongArray, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_StochBoundedUntil\n * Signature: (JJJIJIJJDJ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1StochBoundedUntil\n  (JNIEnv *, jclass, jlong, jlong, jlong, jint, jlong, jint, jlong, jlong, jdouble, jlong);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_StochCumulReward\n * Signature: (JJJJJIJID)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1StochCumulReward\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jlong, jint, jlong, jint, jdouble);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_StochSteadyState\n * Signature: (JJJJIJI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1StochSteadyState\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_StochTransient\n * Signature: (JJJJIJID)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1StochTransient\n  (JNIEnv *, jclass, jlong, jlong, jlong, jlong, jint, jlong, jint, jdouble);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ExportMatrix\n * Signature: (JLjava/lang/String;JIJIJILjava/lang/String;Ljava/lang/String;Z)I\n */\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportMatrix\n  (JNIEnv *, jclass, jlong, jstring, jlong, jint, jlong, jint, jlong, jint, jstring, jstring, jboolean);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ExportMC\n * Signature: ([JLjava/util/List;Ljava/lang/String;JIJIJILjava/lang/String;)I\n */\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportMC\n  (JNIEnv *, jclass, jlongArray, jobject, jstring, jlong, jint, jlong, jint, jlong, jint, jstring);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ExportMDP\n * Signature: (JJLjava/util/List;Ljava/lang/String;JIJIJIJILjava/lang/String;)I\n */\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportMDP\n  (JNIEnv *, jclass, jlong, jlong, jobject, jstring, jlong, jint, jlong, jint, jlong, jint, jlong, jint, jstring);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_ExportSubMDP\n * Signature: (JJLjava/lang/String;JIJIJIJILjava/lang/String;Ljava/lang/String;Z)I\n */\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportSubMDP\n  (JNIEnv *, jclass, jlong, jlong, jstring, jlong, jint, jlong, jint, jlong, jint, jlong, jint, jstring, jstring, jboolean);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_Power\n * Signature: (JJIJIJJJZ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1Power\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_PowerInterval\n * Signature: (JJIJIJJJJZI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1PowerInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_JOR\n * Signature: (JJIJIJJJZZD)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1JOR\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean, jboolean, jdouble);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_JORInterval\n * Signature: (JJIJIJJJJZZDI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1JORInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jboolean, jdouble, jint);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_SOR\n * Signature: (JJIJIJJJZZDZ)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1SOR\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jboolean, jboolean, jdouble, jboolean);\n\n/*\n * Class:     sparse_PrismSparse\n * Method:    PS_SORInterval\n * Signature: (JJIJIJJJJZZDZI)J\n */\nJNIEXPORT jlong JNICALL Java_sparse_PrismSparse_PS_1SORInterval\n  (JNIEnv *, jclass, jlong, jlong, jint, jlong, jint, jlong, jlong, jlong, jlong, jboolean, jboolean, jdouble, jboolean, jint);\n\n#ifdef __cplusplus\n}\n#endif\n#endif\n"
  },
  {
    "path": "prism/include/jnipointer.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Alistair John Strachan <alistair@devzero.co.uk> (University of Edinburgh)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#ifndef JNIPOINTER_H\n#define JNIPOINTER_H\n\n#include <inttypes.h>\n#include \"jni.h\"\n\n/*\n * Currently does nothing, used to annotate jlong's that are pointers (or arrays of)\n */\n\n#define __jlongpointer\n\n#define __jlongpointerArray\n\n/*\n * C++ doesn't support implicit conversion from void*\n */\n\n#define jlong_to_FILE(x)\t\t(FILE *)jlong_to_ptr(x)\n\n// for dd\n#define jlong_to_DdManager(x)\t\t(DdManager *)jlong_to_ptr(x)\n#define jlong_to_DdNode(x)\t\t(DdNode *)jlong_to_ptr(x)\n#define jlong_to_DdNode_array(x)\t(DdNode **)jlong_to_ptr(x)\n\n// for odd\n#define jlong_to_ODDNode(x)\t\t(ODDNode *)jlong_to_ptr(x)\n#define jlong_to_double(x)\t\t(double *)jlong_to_ptr(x)\n\n// for sparse matrices\n#define jlong_to_NDSparseMatrix(x)\t(NDSparseMatrix *)jlong_to_ptr(x)\n\n// void* <-> jlong conversions functions\n\nstatic inline jlong __jlongpointer ptr_to_jlong(void *ptr)\n{\n\treturn (jlong)((intptr_t)ptr);\n}\n\nstatic inline void *jlong_to_ptr(jlong __jlongpointer ptr)\n{\n\treturn (void*)((intptr_t)ptr);\n}\n\n#endif // JNIPOINTER_H\n"
  },
  {
    "path": "prism/include/odd.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#ifndef ODD_H\n#define ODD_H\n\n//------------------------------------------------------------------------------\n\n#include <cstdint>\n\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n\n// Flags for building Windows DLLs\n#ifdef __MINGW32__\n\t#define EXPORT __declspec(dllexport)\n#else\n\t#define EXPORT\n#endif\n\n// odd definitions\n\ntypedef struct ODDNode ODDNode;\n\nstruct ODDNode \n{\n\t//int index;\n\tDdNode *dd;\n\tODDNode *next;\n\tODDNode *e;\n\tODDNode *t;\n\tint64_t eoff;\n\tint64_t toff;\n};\n\n// function prototypes\n\nEXPORT ODDNode *build_odd(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars);\nEXPORT void clear_odd(ODDNode *odd);\nEXPORT int get_index_of_first_from_bdd(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT DdNode *single_index_to_bdd(DdManager *ddman, int i, DdNode **vars, int num_vars, ODDNode *odd);\nEXPORT int get_num_odd_nodes();\n\n//------------------------------------------------------------------------------\n\n#endif\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/prism.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#ifndef PRISM_H\n#define PRISM_H\n\n//------------------------------------------------------------------------------\n#include <jni.h>\n\n// Flags for building Windows DLLs\n#ifdef __MINGW32__\n\t#define EXPORT __declspec(dllexport)\n#else\n\t#define EXPORT\n#endif\n\n// Fox-Glynn weights struct\ntypedef struct FoxGlynnWeights\n{\n\tlong left;\n\tlong right;\n\tdouble total_weight;\n\tdouble *weights;\n} FoxGlynnWeights;\n\n// Function prototypes\nEXPORT long get_real_time(JNIEnv *env);\nEXPORT void get_string_array_from_java(JNIEnv *env, jobject strings_list, jstring *&strings_jstrings, const char **&strings, int &size);\nEXPORT void release_string_array_from_java(JNIEnv *env, jstring *strings_jstrings, const char **strings, jint size);\nEXPORT FoxGlynnWeights fox_glynn(double q_tmax, double underflow, double overflow, double accuracy);\nEXPORT const char* get_export_iterations_filename();\n\n// Global constants\n// Delay between occasional updates for slow processes, e.g. numerical solution (milliseconds)\nconst int UPDATE_DELAY = 5000;\n\n//------------------------------------------------------------------------------\n\n#endif\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/include/sparse.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#ifndef SPARSE_H\n#define SPARSE_H\n\n#include <util.h>\n#include <cudd.h>\n#include <odd.h>\n\n// Flags for building Windows DLLs\n#ifdef __MINGW32__\n\t#define EXPORT __declspec(dllexport)\n#else\n\t#define EXPORT\n#endif\n\n// data structures\n\n// \"row major\" sparse matrix\n\ntypedef struct RMSparseMatrix RMSparseMatrix;\n\nstruct RMSparseMatrix\n{\n\tint n;\t\t\t\t// num states\n\tint nnz;\t\t\t// num non zeros\n\tbool use_counts;\t// store counts? (as opposed to starts)\n\tdouble mem;\t\t\t// memory used\n\t\n\tdouble *non_zeros;\n\tunsigned int *cols;\n\tunsigned char *row_counts;\n\t\n\tunsigned int *actions; \t\t// indices for action of each transition\n\t\n\tEXPORT RMSparseMatrix();\n\tEXPORT ~RMSparseMatrix();\n};\n\n// \"column major\" sparse matrix\n\ntypedef struct CMSparseMatrix CMSparseMatrix;\n\nstruct CMSparseMatrix\n{\n\tint n;\t\t\t\t// num states\n\tint nnz;\t\t\t// num non zeros\n\tbool use_counts;\t// store counts? (as opposed to starts)\n\tdouble mem;\t\t\t// memory used\n\t\n\tdouble *non_zeros;\n\tunsigned int *rows;\n\tunsigned char *col_counts;\n\t\n\tEXPORT CMSparseMatrix();\n\tEXPORT ~CMSparseMatrix();\n};\n\n// \"row/column\" sparse matrix\n\ntypedef struct RCSparseMatrix RCSparseMatrix;\n\nstruct RCSparseMatrix\n{\n\tint n;\t\t\t\t// num states\n\tint nnz;\t\t\t// num non zeros\n\tbool use_counts;\t// store counts? (as opposed to starts)\n\tdouble mem;\t\t\t// memory used\n\t\n\tdouble *non_zeros;\n\tunsigned int *rows;\n\tunsigned int *cols;\n\t\n\tEXPORT RCSparseMatrix();\n\tEXPORT ~RCSparseMatrix();\n};\n\n// \"compact modified sparse row\" sparse matrix\n\ntypedef struct CMSRSparseMatrix CMSRSparseMatrix;\n\nstruct CMSRSparseMatrix\n{\n\tint n;\t\t\t\t// num states\n\tint nnz;\t\t\t// num non zeros\n\tbool use_counts;\t// store counts? (as opposed to starts)\n\tdouble mem; \t\t// memory used\n\t\n\tdouble *dist;\t\t// distinct values info\n\tint dist_num;\n\tint dist_shift;\n\tint dist_mask;\n\t\n\tunsigned int *cols;\n\tunsigned char *row_counts;\n\t\n\tEXPORT CMSRSparseMatrix();\n\tEXPORT ~CMSRSparseMatrix();\n};\n\n// \"compact modified sparse column\" sparse matrix\n\ntypedef struct CMSCSparseMatrix CMSCSparseMatrix;\n\nstruct CMSCSparseMatrix\n{\n\tint n;\t\t\t\t// num states\n\tint nnz;\t\t\t// num non zeros\n\tbool use_counts;\t// store counts? (as opposed to starts)\n\tdouble mem; \t\t// memory used\n\t\n\tdouble *dist;\t\t// distinct values info\n\tint dist_num;\n\tint dist_shift;\n\tint dist_mask;\n\t\n\tunsigned int *rows;\n\tunsigned char *col_counts;\n\t\n\tEXPORT CMSCSparseMatrix();\n\tEXPORT ~CMSCSparseMatrix();\n};\n\n// nondeterministic (mdp) sparse matrix\n\ntypedef struct NDSparseMatrix NDSparseMatrix;\n\nstruct NDSparseMatrix\n{\n\tint n;\t\t\t\t// num states\n\tint nc;\t\t\t\t// num choices\n\tint nnz;\t\t\t// num non zeros\n//\tint nm; \t\t\t// num matrices (upper bound on max num choices in a state)\n\tint k;\t\t\t\t// max num choices in a state\n\tbool use_counts;\t// store counts? (as opposed to starts)\n\tdouble mem;\t\t\t// memory used\n\t\n\tdouble *non_zeros;\n\tunsigned int *cols;\n\tunsigned char *row_counts;\n\tunsigned char *choice_counts;\n\t\n\tint *actions; // indices for actions of each choice\n\t\n\tEXPORT NDSparseMatrix();\n\tEXPORT ~NDSparseMatrix();\n};\n\n// function prototypes\n\nRMSparseMatrix *build_rm_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd);\nRMSparseMatrix *build_rm_sparse_matrix_act(DdManager *ddman, DdNode **matrices, int num_actions, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd);\nCMSparseMatrix *build_cm_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd);\nRCSparseMatrix *build_rc_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd);\nCMSRSparseMatrix *build_cmsr_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd);\nCMSCSparseMatrix *build_cmsc_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd);\nNDSparseMatrix *build_nd_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, ODDNode *odd);\nNDSparseMatrix *build_sub_nd_sparse_matrix(DdManager *ddman, DdNode *mdp, DdNode *submdp, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, ODDNode *odd);\nvoid build_nd_action_vector(DdManager *ddman, DdNode *mdp, DdNode *trans_actions, NDSparseMatrix *mdp_ndsm, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, ODDNode *odd);\n\nRMSparseMatrix *build_rm_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose);\nRMSparseMatrix *build_rm_sparse_matrix_act(DdManager *ddman, DdNode **matrices, int num_actions, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose);\nCMSparseMatrix *build_cm_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose);\nRCSparseMatrix *build_rc_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose);\nCMSRSparseMatrix *build_cmsr_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose);\nCMSCSparseMatrix *build_cmsc_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose);\n\ndouble *rm_negative_row_sums(RMSparseMatrix *rmsm);\ndouble *cm_negative_row_sums(CMSparseMatrix *cmsm);\ndouble *cmsr_negative_row_sums(CMSRSparseMatrix *cmsrsm);\ndouble *cmsc_negative_row_sums(CMSCSparseMatrix *cmscsm);\n\ndouble *rm_negative_row_sums(RMSparseMatrix *rmsm, bool transpose);\ndouble *cm_negative_row_sums(CMSparseMatrix *cmsm, bool transpose);\ndouble *cmsr_negative_row_sums(CMSRSparseMatrix *cmsrsm, bool transpose);\ndouble *cmsc_negative_row_sums(CMSCSparseMatrix *cmscsm, bool transpose);\n\n//------------------------------------------------------------------------------\n\n#endif // SPARSE_H\n"
  },
  {
    "path": "prism/include/sparse_adv.h",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n#include <odd.h>\n#include \"sparse.h\"\n\n// Flags for building Windows DLLs\n#ifdef __MINGW32__\n\t#define EXPORT __declspec(dllexport)\n#else\n\t#define EXPORT\n#endif\n\n// function prototypes\n\nvoid export_model(NDSparseMatrix *ndsm, int n, int *yes_vec, int start_index);\nvoid export_adversary_ltl_dot(NDSparseMatrix *ndsm, int n, long nnz, int *yes_vec, double *maybe_vec, int num_lp_vars, int *map_var, double *lp_soln, int start_index);\nvoid export_adversary_ltl_dot_reward(const char *export_adv_filename, NDSparseMatrix *ndsm, int *actions, const char** action_names, int n, long nnz, int *yes_vec, double *maybe_vec, int num_lp_vars, int *map_var, double *lp_soln, double *back_arr_reals, int start_index);\nvoid export_adversary_ltl_tra(const char *export_adv_filename, NDSparseMatrix *ndsm, int *actions, const char** action_names, int *yes_vec, double *maybe_vec, int num_lp_vars, int *map_var, double *lp_soln, int start_index);\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/install.sh",
    "content": "#!/bin/sh\n\n# Installation of a compiled PRISM distribution\n# All this does is edit the \"PRISM_DIR=...\" lines in the program startup scripts\n# so if you have any problems, just do this manually\n# NB: This installation script should be run from within the PRISM directory\n\n# You are supposed to run this from the main PRISM directory\n# but in case someone is in the bin directory, change...\nPRISM_DIR=`pwd`\nif [ `basename \"$PRISM_DIR\"` = bin ]; then\n  PRISM_DIR=`cd ..;pwd`\nfi\n\n# Now start the 'installation'\nif [ ! \"$1\" = \"silent\" ] ; then\n    echo \"Installing PRISM (directory=$PRISM_DIR)\"\nfi\nTEMP_FILE=\"tmp$RANDOM\"\n# Search for the scripts that should be changed\n# We exclude:\n#  - Windows .BAT files\n#  - the ngprism binary\n#  - hidden files (starting with a dot, e.g., the .DS_Store files from MacOS)\nFILES_TO_CHANGE=`find bin -maxdepth 1 ! -type d ! -iname '*.bat' ! -iname ngprism ! -name '.*'`\nfor FILE_TO_CHANGE in $FILES_TO_CHANGE\ndo\n  if [ -f \"$PRISM_DIR\"/$FILE_TO_CHANGE ]; then\n    if [ ! \"$1\" = \"silent\" ] ; then\n        echo \"Setting path in startup script $PRISM_DIR/$FILE_TO_CHANGE...\"\n    fi\n    if sed -e \"s|PRISM_DIR=.*|PRISM_DIR=\\\"$PRISM_DIR\\\"|g\" \"$PRISM_DIR\"/$FILE_TO_CHANGE > \"$PRISM_DIR\"/$TEMP_FILE ; then\n      /bin/mv \"$PRISM_DIR\"/$TEMP_FILE \"$PRISM_DIR\"/$FILE_TO_CHANGE\n      chmod 755 \"$PRISM_DIR\"/$FILE_TO_CHANGE\n    else\n      echo \"Error: Failed to modify startup scripts.\"\n      exit 0\n    fi\n  else\n    echo \"Error: Could not locate startup script $PRISM_DIR/$FILE_TO_CHANGE\"\n    exit\n  fi\ndone\nif [ ! \"$1\" = \"silent\" ] ; then\n    echo \"Installation complete.\"\nfi\n\nif [ ! \"$1\" = \"silent\" ] && [ \"$(uname -s)\" = \"Darwin\" ]; then\n    echo \"\\nOn macOS, you may want to run the following command now,\"\n    echo \"which avoids manually approving the integrity of the binary files:\"\n    echo \"\\nxattr -d com.apple.quarantine lib/*lib\"\n    echo\nfi\n"
  },
  {
    "path": "prism/lib/README.md",
    "content": "This folder contains the following libraries:\n\n```\n+--- colt:colt:1.2.0\n|    \\--- concurrent:concurrent:1.3.4\n+--- de.uni-mannheim.rz.krum:jas:2.7.200\n|    \\--- org.apache.logging.log4j:log4j-api:[2.17.1,) -> 2.24.0\n+--- com.google.code.gson:gson:2.11.0\n|    \\--- com.google.errorprone:error_prone_annotations:2.27.0\n+--- org.apache.commons:commons-compress:1.24.0\n+--- org.tukaani:xz:1.10\n+--- it.unimi.dsi:fastutil:8.5.15\n+--- org.jfree:jfreechart:1.0.14\n|    +--- org.jfree:jcommon:1.0.17\n|    +--- xml-apis:xml-apis:1.3.04\n|    \\--- com.lowagie:itext:2.1.5\n|         +--- bouncycastle:bcmail-jdk14:138\n|         \\--- bouncycastle:bcprov-jdk14:138\n+--- org.apache.logging.log4j:log4j-api:2.24.0\n+--- org.apache.logging.log4j:log4j-core:2.24.0\n|    \\--- org.apache.logging.log4j:log4j-api:2.24.0\n\\--- org.junit.platform:junit-platform-console-standalone:1.7.2\n```\n\nSee here for more details and links:\n\nhttp://www.prismmodelchecker.org/other-downloads.php\n"
  },
  {
    "path": "prism/src/README.txt",
    "content": "Brief notes on the structure of this source directory.\r\nFurther details on packages are in the Javadoc.\r\nDave Parker.\r\n\r\n-----------\r\n\r\n* bin/ - OS-specific build scripts, customised and installed by make.\r\n* dd/ - A C/C++ library of BDD/MTBDD functions, mostly just wrappers for the CUDD library.\r\n* dv/ - Utility functions for operations on vectors of doubles (stored in C++ through JNI).\r\n* explicit/ - Explicit-state probabilistic model checking engine, implemented in Java.\r\n* hybrid/ - The \"Hybrid\" engine: data structures and model checking algorithms that mix MTBDDs and explicit-state techniques.\r\n* jdd/ - A Java library providing a wrapper around the dd library and hence Java access to CUDD via JNI.\r\n* jltl2ba/ - Java port of the LTL to Buchi automata conversion library.\r\n* jltl2dstar/ - Java port of the LTL to deterministic Rabin automata conversion library.\r\n* mtbdd/ - The \"MTBDD\" engine: fully symbolic implementations of model checking algorithms.\r\n* odd/ - ODDs (offset-labelled BDDs), used to facilitate indexing of states between BDDs and explicit-state data structures.\r\n* parser/ - The PRISM model/properties parser, accompanying abstract syntax tree data structures and tools (and JavaCC parser files).\r\n* pepa/ - PEPA-to-PRISM model translation.\r\n* prism/ - The main Prism API, the command-line tool, and Java classes for symbolic data structures and algorithms.\r\n* pta/ - Probabilistic timed automata (PTA) model checking, including DBM library.\r\n* scripts/ - Shell script(s) used from within make.\r\n* settings/ - Generic 'settings' functionality.\r\n* simulator/ - The discrete event simulation engine and approximate (statistical) model checking code.\r\n* sparse/ - The \"Sparse\" engine: sparse matrix data structures and corresponding implementations of model checking algorithms.\r\n* userinterface/ - PRISM's graphical user interface (GUI).\r\n\r\n* nsis_script.nsi - Script to build Windows binaries with NSIS.\r\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceBuchi.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.io.PrintStream;\nimport java.util.BitSet;\n\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport jdd.JDDVars;\n\n/**\n * A Büchi acceptance condition (based on BitSet state sets).\n * The acceptance is defined via a set of \"accepting\" states\n * (sometimes also called final states) and is accepting if\n *  \"infinitely often an accepting state is visited\"\n */\npublic class AcceptanceBuchi implements AcceptanceOmega\n{\n\t/** The set of goal states */\n\tprivate BitSet acceptingStates = new BitSet();\n\n\t/** Constructor (no accepting states) */\n\tpublic AcceptanceBuchi()\n\t{\n\t}\n\n\t/** Constructor (set accepting states) */\n\tpublic AcceptanceBuchi(BitSet acceptingStates)\n\t{\n\t\tthis.acceptingStates = acceptingStates;\n\t}\n\n\t/** Get the accepting state set */\n\tpublic BitSet getAcceptingStates()\n\t{\n\t\treturn acceptingStates;\n\t}\n\n\t/** Set the accepting state set */\n\tpublic void setAcceptingStates(BitSet acceptingStates)\n\t{\n\t\tthis.acceptingStates = acceptingStates;\n\t}\n\n\t/** Make a copy of the acceptance condition. */\n\tpublic AcceptanceBuchi clone()\n\t{\n\t\treturn new AcceptanceBuchi((BitSet)acceptingStates.clone());\n\t}\n\t\n\t@Override\n\tpublic boolean isBSCCAccepting(BitSet bscc_states)\n\t{\n\t\treturn bscc_states.intersects(acceptingStates);\n\t}\n\n\t/**\n\t * Get the Rabin acceptance condition that is the equivalent of this Buchi condition.\n\t */\n\tpublic AcceptanceRabin toRabin()\n\t{\n\t\tAcceptanceRabin rabin = new AcceptanceRabin();\n\t\trabin.add(new AcceptanceRabin.RabinPair(new BitSet(), (BitSet) acceptingStates.clone()));\n\t\treturn rabin;\n\t}\n\n\t/**\n\t * Get the Streett acceptance condition that is the equivalent of this Buchi condition.\n\t */\n\tpublic AcceptanceStreett toStreett(int numStates)\n\t{\n\t\tAcceptanceStreett streett = new AcceptanceStreett();\n\t\tBitSet allStates = new BitSet();\n\t\tallStates.set(0, numStates);\n\t\tstreett.add(new AcceptanceStreett.StreettPair(allStates, (BitSet) acceptingStates.clone()));\n\t\treturn streett;\n\t}\n\n\t/**\n\t * Get a Rabin acceptance condition that is the complement of this condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Rabin condition.\n\t *\n\t * @param numStates the number of states in the underlying model / automaton (needed for complementing BitSets)\n\t * @return the complement Rabin acceptance condition\n\t */\n\tpublic AcceptanceRabin complementToRabin(int numStates)\n\t{\n\t\tAcceptanceRabin rabin = new AcceptanceRabin();\n\t\tBitSet allStates = new BitSet();\n\t\tallStates.set(0, numStates);\n\t\trabin.add(new AcceptanceRabin.RabinPair((BitSet) acceptingStates.clone(), allStates));\n\t\treturn rabin;\n\t}\n\n\t/**\n\t * Get a Streett acceptance condition that is the complement of this condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Streett condition.\n\t * <br>\n\t * Relies on the fact that once the goal states have been reached, all subsequent states\n\t * are goal states.\n\t *\n\t * @param numStates the number of states in the underlying model / automaton (needed for complementing BitSets)\n\t * @return the complement Streett acceptance condition\n\t */\n\tpublic AcceptanceStreett complementToStreett(int numStates)\n\t{\n\t\tAcceptanceStreett streett = new AcceptanceStreett();\n\t\tstreett.add(new AcceptanceStreett.StreettPair((BitSet) acceptingStates.clone(), new BitSet()));\n\t\treturn streett;\n\t}\n\n\t/** Complement this acceptance condition, return as AcceptanceGeneric. */\n\tpublic AcceptanceGeneric complementToGeneric()\n\t{\n\t\treturn toAcceptanceGeneric().complementToGeneric();\n\t}\n\n\t@Override\n\tpublic AcceptanceOmega complement(int numStates, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.RABIN)) {\n\t\t\treturn complementToRabin(numStates);\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.STREETT)) {\n\t\t\treturn complementToStreett(numStates);\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\t@Override\n\tpublic void lift(LiftBitSet lifter)\n\t{\n\t\tacceptingStates=lifter.lift(acceptingStates);\n\t}\n\n\t@Override\n\tpublic AcceptanceBuchiDD toAcceptanceDD(JDDVars ddRowVars)\n\t{\n\t\treturn new AcceptanceBuchiDD(this, ddRowVars);\n\t}\n\n\t@Override\n\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t{\n\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.INF, (BitSet) acceptingStates.clone());\n\t}\n\n\t@Override\n\tpublic String getSignatureForState(int i)\n\t{\n\t\treturn acceptingStates.get(i) ? \"!\" : \" \";\n\t}\n\t\n\t@Override\n\tpublic String getSignatureForStateHOA(int stateIndex)\n\t{\n\t\tif (acceptingStates.get(stateIndex)) {\n\t\t\treturn \"{0}\";\n\t\t} else {\n\t\t\treturn \"\";\n\t\t}\n\t}\n\n\t/** Returns a textual representation of this acceptance condition. */\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn acceptingStates.toString();\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn acceptingStates.cardinality()+\" accepting states\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.BUCHI;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated()\n\t{\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName()\n\t{\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic void outputHOAHeader(PrintStream out)\n\t{\n\t\tout.println(\"acc-name: Buchi\");\n\t\tout.println(\"Acceptance: 1 Inf(0)\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceBuchiDD.java",
    "content": "//==============================================================================\n//\n//Copyright (c) 2016-\n//Authors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//This file is part of PRISM.\n//\n//PRISM is free software; you can redistribute it and/or modify\n//it under the terms of the GNU General Public License as published by\n//the Free Software Foundation; either version 2 of the License, or\n//(at your option) any later version.\n//\n//PRISM is distributed in the hope that it will be useful,\n//but WITHOUT ANY WARRANTY; without even the implied warranty of\n//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//GNU General Public License for more details.\n//\n//You should have received a copy of the GNU General Public License\n//along with PRISM; if not, write to the Free Software Foundation,\n//Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage acceptance;\n\nimport common.IterableBitSet;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismNotSupportedException;\n\n/**\n * A Büchi acceptance condition (based on JDD state sets).\n * The acceptance is defined via a set of \"accepting\" states\n * (sometimes also called final states) and is accepting if\n *  \"infinitely often an accepting state is visited\"\n */\npublic class AcceptanceBuchiDD implements AcceptanceOmegaDD\n{\n\t/** The accepting states */\n\tprivate JDDNode acceptingStates;\n\n\t/**\n\t * Constructor, set acceptingStates.\n\t * Becomes owner of the references of acceptingStates.\n\t */\n\tpublic AcceptanceBuchiDD(JDDNode acceptingStates)\n\t{\n\t\tthis.acceptingStates = acceptingStates;\n\t}\n\t\n\t/**\n\t * Constructor, from a BitSet-based AcceptanceBuchi.\n\t *\n\t * @param acceptance the BitSet-based acceptance condition\n\t * @param ddRowVars JDDVars of the row variables corresponding to the bits in the bit set\n\t */\n\tpublic AcceptanceBuchiDD(AcceptanceBuchi acceptance, JDDVars ddRowVars)\n\t{\n\t\tacceptingStates = JDD.Constant(0);\n\t\t// get BDD based on the acceptingState bit set\n\t\tfor (int i : IterableBitSet.getSetBits(acceptance.getAcceptingStates())) {\n\t\t\tacceptingStates = JDD.SetVectorElement(acceptingStates, ddRowVars, i, 1.0);\n\t\t}\n\t}\n\n\t/** Get a referenced copy of the state set of the accepting states.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getAcceptingStates()\n\t{\n\t\tJDD.Ref(acceptingStates);\n\t\treturn acceptingStates;\n\t}\n\n\t/**\n\t * Set the accepting states.\n\t * Becomes owner of the reference to acceptingStates.\n\t */\n\tpublic void setAcceptingStates(JDDNode acceptingStates)\n\t{\n\t\tclear();\n\t\tthis.acceptingStates = acceptingStates;\n\t}\n\n\t@Override\n\tpublic boolean isBSCCAccepting(JDDNode bscc_states)\n\t{\n\t\treturn JDD.AreIntersecting(acceptingStates, bscc_states);\n\t}\n\n\t@Override\n\tpublic AcceptanceBuchiDD clone()\n\t{\n\t\treturn new AcceptanceBuchiDD(acceptingStates.copy());\n\t}\n\n\t@Override\n\tpublic void intersect(JDDNode restrict)\n\t{\n\t\tacceptingStates = JDD.And(acceptingStates, restrict.copy());\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn \"one set of accepting states\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.BUCHI;\n\t}\n\n\t/**\n\t * Get the Streett acceptance condition that is the equivalent of this Buchi condition.\n\t */\n\tpublic AcceptanceStreettDD toStreett()\n\t{\n\t\tAcceptanceStreettDD streett = new AcceptanceStreettDD();\n\t\tstreett.add(new AcceptanceStreettDD.StreettPairDD(JDD.Constant(1), acceptingStates.copy()));\n\t\treturn streett;\n\t}\n\n\t@Override\n\tpublic AcceptanceOmegaDD complement(AcceptanceType... allowedAcceptance) throws PrismNotSupportedException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.RABIN)) {\n\t\t\treturn complementToRabin();\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.STREETT)) {\n\t\t\treturn complementToStreett();\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\t/**\n\t * Get a Rabin acceptance condition that is the complement of this condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Rabin condition.\n\t *\n\t * @return the complement Rabin acceptance condition\n\t */\n\tpublic AcceptanceRabinDD complementToRabin()\n\t{\n\t\tAcceptanceRabinDD rabin = new AcceptanceRabinDD();\n\t\trabin.add(new AcceptanceRabinDD.RabinPairDD(acceptingStates.copy(), JDD.Constant(1)));\n\t\treturn rabin;\n\t}\n\n\t/**\n\t * Get a Streett acceptance condition that is the complement of this condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Streett condition.\n\t * <br>\n\t * Relies on the fact that once the goal states have been reached, all subsequent states\n\t * are goal states.\n\t *\n\t * @return the complement Streett acceptance condition\n\t */\n\tpublic AcceptanceStreettDD complementToStreett()\n\t{\n\t\tAcceptanceStreettDD streett = new AcceptanceStreettDD();\n\t\tstreett.add(new AcceptanceStreettDD.StreettPairDD(acceptingStates.copy(), JDD.Constant(0)));\n\t\treturn streett;\n\t}\n\n\t@Override\n\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n\t{\n\t\treturn new AcceptanceGenericDD(AcceptanceGeneric.ElementType.INF, acceptingStates.copy());\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated()\n\t{\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName()\n\t{\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tif (acceptingStates != null) {\n\t\t\tJDD.Deref(acceptingStates);\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceGenRabin.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\n\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport jdd.JDDVars;\n\n/**\n * A Generalized Rabin acceptance condition (based on BitSet state sets)\n * This is a list of GenRabinPairs, which can be manipulated with the usual List interface.\n * <br>\n * Semantics: Each Generalized Rabin pair has state sets L and K_1,...,K_n and is accepting iff\n * L is not visited infinitely often and all K_j are visited infinitely often:\n *   (F G !\"L\") & (G F \"K_1\") & ... & (G F \"K_n\").\n *\n * The Generalized Rabin condition is accepting if at least one of the pairs is accepting.\n */\n@SuppressWarnings(\"serial\")\npublic class AcceptanceGenRabin\n       extends ArrayList<AcceptanceGenRabin.GenRabinPair>\n       implements AcceptanceOmega\n{\n\n\t/**\n\t * A pair in a Generalized Rabin acceptance condition, i.e., with\n\t *  (F G !\"L\") & (G F \"K_1\") & ... & (G F \"K_n\").\n\t **/\n\tpublic static class GenRabinPair {\n\t\t/** State set L (should be visited only finitely often) */\n\t\tprivate BitSet L;\n\n\t\t/** State sets K_j (should all be visited infinitely often) */\n\t\tprivate ArrayList<BitSet> K_list;\n\n\t\t/** Constructor with L and K_j state sets */\n\t\tpublic GenRabinPair(BitSet L, ArrayList<BitSet> K_list) {\n\t\t\tthis.L = L;\n\t\t\tthis.K_list = K_list;\n\t\t}\n\n\t\t/** Get the state set L */\n\t\tpublic BitSet getL()\n\t\t{\n\t\t\treturn L;\n\t\t}\n\n\t\t/** Get the number of K_j sets */\n\t\tpublic int getNumK()\n\t\t{\n\t\t\treturn K_list.size();\n\t\t}\n\t\t\n\t\t/** Get the state set K_j */\n\t\tpublic BitSet getK(int j)\n\t\t{\n\t\t\treturn K_list.get(j);\n\t\t}\n\n\t\t/** Returns true if the bottom strongly connected component\n\t\t * given by bscc_states is accepting for this pair.\n\t\t */\n\t\tpublic boolean isBSCCAccepting(BitSet bscc_states)\n\t\t{\n\t\t\tif (L.intersects(bscc_states)) {\n\t\t\t\t// there is some state in bscc_states that is\n\t\t\t\t// forbidden by L\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\tfor (BitSet K_j : K_list) {\n\t\t\t\tif (!K_j.intersects(bscc_states)) {\n\t\t\t\t\t// there is some state in bscc_states that is\n\t\t\t\t\t// contained in K -> infinitely often visits to K\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\treturn true;\n\t\t}\n\n\t\t/** Generate signature for this Rabin pair and the given state.\n\t\t *  If the state is a member of L, returns \"-pairIndex\".\n\t\t *  If the state is a member of K, returns \"+pairIndex\".\n\t\t *  @param stateIndex the state index\n\t\t *  @param pairIndex the index of this Rabin pair\n\t\t **/\n\t\tpublic String getSignatureForState(int stateIndex, int pairIndex)\n\t\t{\n\t\t\t// TODO: (What is the correct syntax here?)\n\t\t\t/*if (L.get(stateIndex)) {\n\t\t\t\treturn \"-\"+pairIndex;\n\t\t\t} else if (K.get(stateIndex)) {\n\t\t\t\treturn \"+\"+pairIndex;\n\t\t\t} else {\n\t\t\t\treturn \"\";\n\t\t\t}*/\n\t\t\treturn \"?\";\n\t\t}\n\n\t\t@Override\n\t\tpublic GenRabinPair clone()\n\t\t{\n\t\t\tArrayList<BitSet> newK_list = new ArrayList<BitSet>();\n\t\t\tfor (BitSet K_j : K_list)\n\t\t\t\tnewK_list.add((BitSet) K_j.clone());\n\t\t\treturn new GenRabinPair((BitSet)L.clone(), newK_list);\n\t\t}\n\n\t\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t\t{\n\t\t\tAcceptanceGeneric genericL = new AcceptanceGeneric(AcceptanceGeneric.ElementType.FIN, (BitSet) L.clone());\n\t\t\tif (getNumK() == 0) {\n\t\t\t\treturn genericL;\n\t\t\t}\n\t\t\tAcceptanceGeneric genericKs = null;\n\t\t\tfor (BitSet K : K_list) {\n\t\t\t\tAcceptanceGeneric genericK = new AcceptanceGeneric(AcceptanceGeneric.ElementType.INF, (BitSet) K.clone());\n\t\t\t\tif (genericKs == null) {\n\t\t\t\t\tgenericKs = genericK;\n\t\t\t\t} else {\n\t\t\t\t\tgenericKs = new AcceptanceGeneric(AcceptanceGeneric.ElementType.AND, genericKs, genericK);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.AND, genericL, genericKs);\n\t\t}\n\t\n\t\t/** Returns a textual representation of this Generalized Rabin pair. */\n\t\t@Override\n\t\tpublic String toString() {\n\t\t\tString s = \"(\" + L;\n\t\t\tfor (BitSet K_j : K_list)\n\t\t\t\ts += \",\" + K_j;\n\t\t\ts += \")\";\n\t\t\treturn s;\n\t\t}\n\t}\n\n\t/** Make a copy of the acceptance condition. */\n\tpublic AcceptanceGenRabin clone()\n\t{\n\t\tAcceptanceGenRabin result = new AcceptanceGenRabin();\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/** Returns true if the bottom strongly connected component\n\t * given by bscc_states is accepting for this Rabin condition,\n\t * i.e., there is a pair that accepts for bscc_states.\n\t */\n\tpublic boolean isBSCCAccepting(BitSet bscc_states)\n\t{\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tif (pair.isBSCCAccepting(bscc_states)) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\n\t\treturn false;\n\t}\n\n\t/** Complement this acceptance condition, return as AcceptanceGeneric. */\n\tpublic AcceptanceGeneric complementToGeneric()\n\t{\n\t\tAcceptanceGeneric generic = toAcceptanceGeneric();\n\t\treturn generic.complementToGeneric();\n\t}\n\n\t@Override\n\tpublic AcceptanceOmega complement(int numStates, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\t@Override\n\tpublic void lift(LiftBitSet lifter) {\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tpair.L = lifter.lift(pair.L);\n\t\t\tint n = pair.K_list.size();\n\t\t\tfor (int j = 0; j < n; j++)\n\t\t\t\tpair.K_list.set(j, lifter.lift(pair.K_list.get(j)));\n\t\t}\n\t}\n\n\t/**\n\t * Returns a new Generalized Rabin acceptance condition that corresponds to the disjunction\n\t * of this and the other Generalized Rabin acceptance condition. The GenRabinPairs are cloned, i.e.,\n\t * not shared with the argument acceptance condition.\n\t * @param other the other GeneralizedRabin acceptance condition\n\t * @return new AcceptanceGenRabin, disjunction of this and other\n\t */\n\tpublic AcceptanceGenRabin or(AcceptanceGenRabin other)\n\t{\n\t\tAcceptanceGenRabin result = new AcceptanceGenRabin();\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tresult.add((GenRabinPair) pair.clone());\n\t\t}\n\t\tfor (GenRabinPair pair : other) {\n\t\t\tresult.add((GenRabinPair) pair.clone());\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic AcceptanceGenRabinDD toAcceptanceDD(JDDVars ddRowVars)\n\t{\n\t\treturn new AcceptanceGenRabinDD(this, ddRowVars);\n\t}\n\n\t@Override\n\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t{\n\t\tif (size() == 0) {\n\t\t\treturn new AcceptanceGeneric(false);\n\t\t}\n\t\tAcceptanceGeneric genericPairs = null;\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tAcceptanceGeneric genericPair = pair.toAcceptanceGeneric();\n\t\t\tif (genericPairs == null) {\n\t\t\t\tgenericPairs = genericPair;\n\t\t\t} else {\n\t\t\t\tgenericPairs = new AcceptanceGeneric(AcceptanceGeneric.ElementType.OR, genericPairs, genericPair);\n\t\t\t}\n\t\t}\n\t\treturn genericPairs;\n\t}\n\n\t/**\n\t * Get the acceptance signature for state stateIndex.\n\t **/\n\tpublic String getSignatureForState(int stateIndex)\n\t{\n\t\tString result = \"\";\n\n\t\tfor (int pairIndex=0; pairIndex<size(); pairIndex++) {\n\t\t\tGenRabinPair pair = get(pairIndex);\n\t\t\tresult += pair.getSignatureForState(stateIndex,  pairIndex);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSignatureForStateHOA(int stateIndex)\n\t{\n\t\tString result = \"\";\n\n\t\tint set_index = 0;\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tif (pair.getL().get(stateIndex)) {\n\t\t\t\tresult += (result.isEmpty() ? \"\" : \" \") + set_index;\n\t\t\t}\n\t\t\tset_index++;\n\t\t\tfor (int i=0; i < pair.getNumK(); i++) {\n\t\t\t\tif (pair.getK(i).get(stateIndex)) {\n\t\t\t\t\tresult += (result.isEmpty() ? \"\" : \" \") + set_index;\n\t\t\t\t}\n\t\t\t\tset_index++;\n\t\t\t}\n\t\t}\n\n\t\tif (!result.isEmpty())\n\t\t\tresult = \"{\"+result+\"}\";\n\n\t\treturn result;\n\t}\n\n\t/** Returns a textual representation of this acceptance condition. */\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString result = \"\";\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tresult += pair.toString();\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn size() + \" Generalized Rabin pairs\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.GENERALIZED_RABIN;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic void outputHOAHeader(PrintStream out)\n\t{\n\t\tint sets = 0;\n\t\tout.print(\"acc-name: generalized-Rabin \"+size());\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tsets++;  // the Fin\n\t\t\tout.print(\" \"+pair.getNumK());\n\t\t\tsets += pair.getNumK();\n\t\t}\n\t\tout.println();\n\t\tout.print(\"Acceptance: \" + sets);\n\t\tif (sets == 0) {\n\t\t\tout.println(\"f\");\n\t\t\treturn;\n\t\t}\n\n\t\tint set_index = 0;\n\t\tfor (GenRabinPair pair : this) {\n\t\t\tif (set_index > 0) out.print(\" | \");\n\t\t\tout.print(\"( Fin(\" + set_index + \")\");\n\t\t\tset_index++;\n\t\t\tfor (int i = 0; i < pair.getNumK(); i++) {\n\t\t\t\tout.print(\" & Inf(\" + set_index +\")\");\n\t\t\t\tset_index++;\n\t\t\t}\n\t\t\tout.print(\")\");\n\t\t}\n\t\tout.println();\n\t}\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceGenRabinDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.util.ArrayList;\n\nimport common.IterableBitSet;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismNotSupportedException;\n\n/**\n * A Generalized Rabin acceptance condition (based on JDD state sets)\n * This is a list of GenRabinPairs, which can be manipulated with the usual List interface.\n * <br>\n * Semantics: Each Generalized Rabin pair has state sets L and K_1,...,K_n and is accepting iff\n * L is not visited infinitely often and all K_j are visited infinitely often:\n *   (F G !\"L\") & (G F \"K_1\") & ... & (G F \"K_n\").\n *\n * The Generalized Rabin condition is accepting if at least one of the pairs is accepting.\n */\n@SuppressWarnings(\"serial\")\npublic class AcceptanceGenRabinDD\n       extends ArrayList<AcceptanceGenRabinDD.GenRabinPairDD>\n       implements AcceptanceOmegaDD\n{\n\n\t/**\n\t * A pair in a Generalized Rabin acceptance condition, i.e., with\n\t *  (F G !\"L\") & (G F \"K_1\") & ... & (G F \"K_n\").\n\t **/\n\tpublic static class GenRabinPairDD implements Cloneable {\n\t\t/** State set L (should be visited only finitely often) */\n\t\tprivate JDDNode L;\n\n\t\t/** State sets K_j (should all be visited infinitely often) */\n\t\tprivate ArrayList<JDDNode> K_list;\n\n\t\t/**\n\t\t * Constructor with L and K_j state sets.\n\t\t * Becomes owner of the references of L and K_j's.\n\t\t */\n\t\tpublic GenRabinPairDD(JDDNode L, ArrayList<JDDNode> K_list)\n\t\t{\n\t\t\tthis.L = L;\n\t\t\tthis.K_list = K_list;\n\t\t}\n\n\t\t/** Clear resources of the state sets */\n\t\tpublic void clear()\n\t\t{\n\t\t\tif (L!=null) JDD.Deref(L);\n\t\t\tfor (JDDNode K_j : K_list)\n\t\t\t\tJDD.Deref(K_j);\n\t\t}\n\n\t\t/** Get a referenced copy of the state set L.\n\t\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic JDDNode getL()\n\t\t{\n\t\t\treturn L.copy();\n\t\t}\n\n\t\t/** Get the number of K_j sets */\n\t\tpublic int getNumK()\n\t\t{\n\t\t\treturn K_list.size();\n\t\t}\n\t\t\n\t\t/** Get a referenced copy of the state set K_j.\n\t\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic JDDNode getK(int j)\n\t\t{\n\t\t\treturn K_list.get(j).copy();\n\t\t}\n\n\t\t@Override\n\t\tpublic GenRabinPairDD clone()\n\t\t{\n\t\t\tArrayList<JDDNode> newK_list = new ArrayList<JDDNode>();\n\t\t\tfor (JDDNode K_j : K_list) {\n\t\t\t\tnewK_list.add(K_j.copy());\n\t\t\t}\n\t\t\treturn new GenRabinPairDD(getL(), newK_list);\n\t\t}\n\n\t\t/** Returns true if the bottom strongly connected component\n\t\t * given by bscc_states is accepting for this pair.\n\t\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic boolean isBSCCAccepting(JDDNode bscc_states)\n\t\t{\n\t\t\tif (JDD.AreIntersecting(L, bscc_states)) {\n\t\t\t\t// there is some state in bscc_states that is\n\t\t\t\t// forbidden by L\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\tfor (JDDNode K_j : K_list) {\n\t\t\t\tif (!JDD.AreIntersecting(K_j, bscc_states)) {\n\t\t\t\t\t// there is some state in bscc_states that is\n\t\t\t\t\t// contained in K_j -> infinitely often visits to K_j\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\treturn true;\n\t\t}\n\n\t\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n \t\t{\n\t\t\tAcceptanceGenericDD genericL = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.FIN, L.copy());\n\t\t\tif (getNumK() == 0) {\n\t\t\t\treturn genericL;\n\t\t\t}\n\t\t\tAcceptanceGenericDD genericKs = null;\n\t\t\tfor (JDDNode K : K_list) {\n\t\t\t\tAcceptanceGenericDD genericK = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.INF, K.copy());\n\t\t\t\tif (genericKs == null) {\n\t\t\t\t\tgenericKs = genericK;\n\t\t\t\t} else {\n\t\t\t\t\tgenericKs = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.AND, genericKs, genericK);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn new AcceptanceGenericDD(AcceptanceGeneric.ElementType.AND, genericL, genericKs);\n \t\t}\n\n\t\t/**\n\t\t * Replaces the BDD functions for the acceptance sets\n\t\t * of this generalized Rabin pair with the intersection\n\t\t * of the current acceptance sets and the function {@code restrict}.\n\t\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic void intersect(JDDNode restrict)\n\t\t{\n\t\t\tL = JDD.And(L, restrict.copy());\n\t\t\tfor (int i = 0; i < K_list.size(); i++) {\n\t\t\t\tK_list.set(i, JDD.And(K_list.get(i), restrict.copy()));\n\t\t\t}\n\t\t}\n\n\t\t/** Returns a textual representation of this Rabin pair. */\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\tString s = \"(\" + L;\n\t\t\tfor (JDDNode K_j : K_list)\n\t\t\t\ts += \",\" + K_j;\n\t\t\ts += \")\";\n\t\t\treturn s;\n\t\t}\n\t}\n\n\t/** Constructor, create empty condition */\n\tpublic AcceptanceGenRabinDD()\n\t{\n\t}\n\n\t/**\n\t * Constructor, from a BitSet-based AcceptanceGenRabin.\n\t *\n\t * @param acceptance the BitSet-based acceptance condition\n\t * @param ddRowVars JDDVars of the row variables corresponding to the bits in the bit set\n\t */\n\tpublic AcceptanceGenRabinDD(AcceptanceGenRabin acceptance, JDDVars ddRowVars)\n\t{\n\t\tfor (AcceptanceGenRabin.GenRabinPair pair : acceptance) {\n\t\t\t// get BDD based newL and newK from the bit sets\n\t\t\tJDDNode newL = JDD.Constant(0);\n\t\t\tfor (int i : IterableBitSet.getSetBits(pair.getL())) {\n\t\t\t\tnewL = JDD.SetVectorElement(newL, ddRowVars, i, 1.0);\n\t\t\t}\n\n\t\t\tArrayList<JDDNode> newK_list = new ArrayList<JDDNode>();\n\t\t\tint n = pair.getNumK();\n\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\tJDDNode newK_j = JDD.Constant(0);\n\t\t\t\tfor (int i : IterableBitSet.getSetBits(pair.getK(j))) {\n\t\t\t\t\tnewK_j = JDD.SetVectorElement(newK_j, ddRowVars, i, 1.0);\n\t\t\t\t}\n\t\t\t\tnewK_list.add(newK_j);\n\t\t\t}\n\n\t\t\tGenRabinPairDD newPair = new GenRabinPairDD(newL, newK_list);\n\t\t\tthis.add(newPair);\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean isBSCCAccepting(JDDNode bscc_states)\n\t{\n\t\tfor (GenRabinPairDD pair : this) {\n\t\t\tif (pair.isBSCCAccepting(bscc_states)) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic AcceptanceGenRabinDD clone()\n\t{\n\t\tAcceptanceGenRabinDD result = new AcceptanceGenRabinDD();\n\t\tfor (GenRabinPairDD pair : this) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic void intersect(JDDNode restrict)\n\t{\n\t\tfor (GenRabinPairDD pair : this) {\n\t\t\tpair.intersect(restrict);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tfor (GenRabinPairDD pair : this) {\n\t\t\tpair.clear();\n\t\t}\n\t\tsuper.clear();\n\t}\n\n\t/** Returns a textual representation of this acceptance condition. */\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString result = \"\";\n\t\tfor (GenRabinPairDD pair : this) {\n\t\t\tresult += pair.toString();\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn size() + \" Generalized Rabin pairs\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.GENERALIZED_RABIN;\n\t}\n\n\t@Override\n\tpublic AcceptanceOmegaDD complement(AcceptanceType... allowedAcceptance) throws PrismNotSupportedException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\t@Override\n\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n\t{\n\t\tif (size() == 0) {\n\t\t\treturn new AcceptanceGenericDD(false);\n\t\t}\n\t\tAcceptanceGenericDD genericPairs = null;\n\t\tfor (GenRabinPairDD pair : this) {\n\t\t\tAcceptanceGenericDD genericPair = pair.toAcceptanceGeneric();\n\t\t\tif (genericPairs == null) {\n\t\t\t\tgenericPairs = genericPair;\n\t\t\t} else {\n\t\t\t\tgenericPairs = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.OR, genericPairs, genericPair);\n\t\t\t}\n\t\t}\n\t\treturn genericPairs;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceGeneric.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.List;\nimport java.util.Stack;\n\nimport acceptance.AcceptanceRabin.RabinPair;\nimport acceptance.AcceptanceStreett.StreettPair;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport jdd.JDDVars;\n\n/**\n * A generic acceptance condition (based on BitSet state sets).\n * This is an AST of a boolean formula (conjunction and disjunction) over\n * atoms of the form Inf(states), Inf(!states), Fin(states) and Fin(!states).\n * <br>\n * Semantics:\n *  Inf(states)  <=> G F states\n *  Inf(!states) <=> G F !states\n *  Fin(states)  <=> F G !states\n *  Fin(!states) <=> F G states\n */\npublic class AcceptanceGeneric implements AcceptanceOmega {\n\t\n\t/** The types of elements in the AST */\n\tpublic enum ElementType {\n\t\tFALSE,\n\t\tTRUE, \n\n\t\tOR,\n\t\tAND,\n\n\t\tINF,\n\t\tFIN,\n\t\tINF_NOT,\n\t\tFIN_NOT;\n\t}\n\t\n\t/** The type of this node in the AST */\n\tprivate ElementType kind;\n\n\t/** The left child (if it exists) */ \n\tprivate AcceptanceGeneric left = null;\n\n\t/** The right child (if it exists) */ \n\tprivate AcceptanceGeneric right = null;\n\n\t/** The set of states (if this is one of INF, FIN, INF_NOT, FIN_NOT) */\n\tprivate BitSet states = null;\n\n\t/**\n\t * Constructor for TRUE or FALSE\n\t * @param value true or false?\n\t */\n\tpublic AcceptanceGeneric(boolean value) {\n\t\tkind = value ? ElementType.TRUE : ElementType.FALSE;\n\t}\n\t\n\t/** \n\t * Constructor for an INF, FIN, INF_NOT or FIN_NOT element. \n\t */\n\tpublic AcceptanceGeneric(ElementType kind, BitSet states) {\n\t\tthis.kind = kind;\n\n\t\tthis.states = states;\n\t}\n\n\t/**\n\t * Constructor for a binary operator (AND/OR).\n\t * @param kind\n\t * @param left\n\t * @param right\n\t */\n\tpublic AcceptanceGeneric(ElementType kind, AcceptanceGeneric left, AcceptanceGeneric right) {\n\t\tthis.kind = kind;\n\t\tthis.left = left;\n\t\tthis.right = right;\n\t}\n\n\t/** Get the ElementType of this AST element */\n\tpublic ElementType getKind() {\n\t\treturn kind;\n\t}\n\n\t/** Get the left child of this AST element */\n\tpublic AcceptanceGeneric getLeft() {\n\t\treturn left;\n\t}\n\n\t/** Get the right child of this AST element */\n\tpublic AcceptanceGeneric getRight() {\n\t\treturn right;\n\t}\n\n\t/** Get the state set of this element (if kind is one of INF, FIN, INF_NOT, FIN_NOT).\n\t */\n\tpublic BitSet getStates() {\n\t\treturn states;\n\t}\n\n\t@Override\n\tpublic boolean isBSCCAccepting(BitSet bscc) {\n\t\tswitch(kind) {\n\t\t\tcase TRUE: return true;\n\t\t\tcase FALSE: return false;\n\t\t\tcase AND: return left.isBSCCAccepting(bscc) && right.isBSCCAccepting(bscc);\n\t\t\tcase OR: return left.isBSCCAccepting(bscc) || right.isBSCCAccepting(bscc);\n\t\t\tcase INF:\n\t\t\t\t// bscc |= G F states?\n\t\t\t\t// there exists a state in bscc and states\n\t\t\t\treturn bscc.intersects(states);\n\t\t\tcase INF_NOT: {\n\t\t\t\t// bscc_state |= G F !states?\n\t\t\t\t// the BSCC does not consist only of states\n\t\t\t\tBitSet bs = (BitSet) bscc.clone();\n\t\t\t\tbs.andNot(states);\n\t\t\t\treturn !bs.isEmpty();\n\t\t\t}\n\t\t\tcase FIN: {\n\t\t\t\t// bscc |= F G !states?\n\t\t\t\t// <=> there exists no states state in BSCC\n\t\t\t\treturn !bscc.intersects(states);\n\t\t\t}\n\t\t\tcase FIN_NOT: {\n\t\t\t\t// bscc |= F G states?\n\t\t\t\t// the BSCC consists entirely of states\n\t\t\t\tBitSet bs = (BitSet) bscc.clone();\n\t\t\t\tbs.and(states);\n\t\t\t\treturn bs.equals(bscc);\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** Get a list of all the (non-true/false) leaf nodes in this acceptance condition */\n\tpublic List<AcceptanceGeneric> getLeafNodes()\n\t{\n\t\tswitch (getKind()) {\n\t\tcase AND:\n\t\tcase OR: {\n\t\t\tList<AcceptanceGeneric> result = new ArrayList<AcceptanceGeneric>();\n\t\t\tresult.addAll(left.getLeafNodes());\n\t\t\tresult.addAll(right.getLeafNodes());\n\t\t\treturn result;\n\t\t}\n\t\tcase TRUE:\n\t\tcase FALSE:\n\t\t\treturn Collections.emptyList();\n\t\tcase FIN:\n\t\tcase FIN_NOT:\n\t\tcase INF:\n\t\tcase INF_NOT:\n\t\t\treturn Collections.singletonList(this);\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unknown kind\");\n\t}\n\n\t@Override\n\tpublic String getSignatureForState(int stateIndex) {\n\t\tList<AcceptanceGeneric> leafNodes = getLeafNodes();\n\n\t\tString result = \"\";\n\t\tfor (int i=0; i < leafNodes.size(); i++) {\n\t\t\tif (leafNodes.get(i).getStates().get(stateIndex)) {\n\t\t\t\tresult += (result.isEmpty() ? \"\" : \",\")+i;\n\t\t\t}\n\t\t}\n\n\t\tresult = \"{\" + result + \"}\";\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSignatureForStateHOA(int stateIndex) {\n\t\tList<AcceptanceGeneric> leafNodes = getLeafNodes();\n\n\t\tString result = \"\";\n\t\tfor (int i=0; i < leafNodes.size(); i++) {\n\t\t\tif (leafNodes.get(i).getStates().get(stateIndex)) {\n\t\t\t\tresult += (result.isEmpty() ? \"\" : \" \")+i;\n\t\t\t}\n\t\t}\n\n\t\tif (!result.isEmpty())\n\t\t\tresult = \"{\" + result + \"}\";\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics() {\n\t\treturn \"generic acceptance with \" + countAcceptanceSets() + \" acceptance sets\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType() {\n\t\treturn AcceptanceType.GENERIC;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic AcceptanceGeneric clone() {\n\t\tswitch (kind) {\n\t\t\tcase FIN:\n\t\t\tcase FIN_NOT:\n\t\t\tcase INF:\n\t\t\tcase INF_NOT:\n\t\t\t\treturn new AcceptanceGeneric(kind, states);\n\t\t\tcase AND:\n\t\t\tcase OR:\n\t\t\t\treturn new AcceptanceGeneric(kind, left.clone(), right.clone());\n\t\t\tcase FALSE:\n\t\t\t\treturn new AcceptanceGeneric(false);\n\t\t\tcase TRUE:\n\t\t\t\treturn new AcceptanceGeneric(true);\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operator in generic acceptance condition\");\n\t}\n\n\t/**\n\t * Returns a new generic acceptance condition that corresponds to the conjunction\n\t * of this and the other acceptance condition. Both conditions are <b>not</b>\n\t * cloned; take care not to modify the conditions or clone beforehand.\n\t * @param other the other generic acceptance condition\n\t * @return new AcceptanceRabin, conjunction of this and other\n\t */\n\tpublic AcceptanceGeneric and(AcceptanceGeneric other)\n\t{\n\t\treturn new AcceptanceGeneric(ElementType.AND, this, other);\n\t}\n\n\t/**\n\t * Returns a new generic acceptance condition that corresponds to the disjunction\n\t * of this and the other acceptance condition. Both conditions are <b>not</b>\n\t * cloned; take care not to modify the conditions or clone beforehand.\n\t * @param other the other generic acceptance condition\n\t * @return new AcceptanceGeneric, disjunction of this and other\n\t */\n\tpublic AcceptanceGeneric or(AcceptanceGeneric other)\n\t{\n\t\treturn new AcceptanceGeneric(ElementType.OR, this, other);\n\t}\n\n\t/** Complement this acceptance condition, return as AcceptanceGeneric. */\n\tpublic AcceptanceGeneric complementToGeneric()\n\t{\n\t\tswitch (kind) {\n\t\tcase TRUE: return new AcceptanceGeneric(false);\n\t\tcase FALSE:  return new AcceptanceGeneric(true);\n\n\t\tcase AND:\n\t\t\treturn new AcceptanceGeneric(ElementType.OR,\n\t\t\t                             getLeft().complementToGeneric(),\n\t\t\t                             getRight().complementToGeneric());\n\t\tcase OR:\n\t\t\treturn new AcceptanceGeneric(ElementType.AND,\n                        \t             getLeft().complementToGeneric(),\n                        \t             getRight().complementToGeneric());\n\t\tcase FIN:\n\t\t\treturn new AcceptanceGeneric(ElementType.INF, (BitSet) states.clone());\n\t\tcase FIN_NOT:\n\t\t\treturn new AcceptanceGeneric(ElementType.INF_NOT, (BitSet) states.clone());\n\t\tcase INF:\n\t\t\treturn new AcceptanceGeneric(ElementType.FIN, (BitSet) states.clone());\n\t\tcase INF_NOT:\n\t\t\treturn new AcceptanceGeneric(ElementType.FIN_NOT, (BitSet) states.clone());\n\t\tdefault:\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\t}\n\n\t@Override\n\tpublic AcceptanceOmega complement(int numStates, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn this.complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to required acceptance type\");\n\t}\n\n\t@Override\n\tpublic void lift(LiftBitSet lifter) {\n\t\tswitch(kind) {\n\t\t\tcase TRUE:\n\t\t\tcase FALSE:\n\t\t\t\treturn;\n\t\t\tcase INF:\n\t\t\tcase INF_NOT:\n\t\t\tcase FIN:\n\t\t\tcase FIN_NOT:\n\t\t\t\tstates = lifter.lift(states);\n\t\t\t\treturn;\n\t\t\tcase AND:\n\t\t\tcase OR:\n\t\t\t\tleft.lift(lifter);\n\t\t\t\tright.lift(lifter);\n\t\t\t\treturn;\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operator in generic acceptance condition\");\n\t}\n\n\t/** Count the number of state sets in this acceptance condition */\n\tpublic int countAcceptanceSets() {\n\t\tswitch(kind) {\n\t\t\tcase FALSE:\n\t\t\tcase TRUE:\n\t\t\t\treturn 0;\n\t\t\tcase INF:\n\t\t\tcase FIN: \n\t\t\tcase INF_NOT:\n\t\t\tcase FIN_NOT:\n\t\t\t\treturn 1;\n\t\t\tcase OR:\n\t\t\tcase AND: \n\t\t\t\treturn left.countAcceptanceSets() + right.countAcceptanceSets();\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operator in generic acceptance condition\");\n\t}\n\n\t@Override\n\tpublic AcceptanceOmegaDD toAcceptanceDD(JDDVars ddRowVars) {\n\t\treturn new AcceptanceGenericDD(this, ddRowVars);\n\t}\n\n\t@Override\n\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t{\n\t\treturn this.clone();\n\t}\n\n\t/**\n\t * Attempt to convert this generic acceptance condition\n\t * to a Rabin condition. If this condition does not have\n\t * the required form (top-level disjunctions with conjunctive pairs),\n\t * returns {@code null}.\n\t * <br>\n\t * If the condition does not syntactically have the required\n\t * from but can be easily converted to one (e.g., by converting\n\t * a single Inf(S) to a Fin(emptyset) & Inf(S) etc) or by swapping\n\t * Inf and Fin, this will be done.\n\t * <br>\n\t * The BitSets for the state sets are cloned, i.e., modifications of\n\t * the state sets of the returned acceptance condition will not affect\n\t * the original generic acceptance condition.\n\t *\n\t * @param numStates the number of states in the underlying model/automaton (for generating state sets for true)\n\t * @return the generated AcceptanceRabin condition, or false on failure\n\t */\n\tpublic AcceptanceRabin toAcceptanceRabin(int numStates)\n\t{\n\t\tAcceptanceRabin result = new AcceptanceRabin();\n\t\tList<AcceptanceGeneric> disjuncts = extractDisjuncts();\n\n\t\tfor (AcceptanceGeneric term : disjuncts) {\n\t\t\tRabinPair pair = term.toAcceptanceRabinPair(numStates);\n\t\t\tif (pair == null) return null;\n\t\t\tresult.add(pair);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Attempt to convert this generic acceptance to a Rabin pair.\n\t *\n\t * @param numStates the number of states in the underlying model/automaton (for generating state sets for true)\n\t * @return the generated RabinPair, or false on failure\n\t */\n\tprivate RabinPair toAcceptanceRabinPair(int numStates)\n\t{\n\t\tBitSet L = null, K = null;\n\t\tswitch (getKind()) {\n\t\tcase TRUE:\n\t\t\tL = new BitSet();\n\t\t\tK = new BitSet();\n\t\t\tK.set(0, numStates);\n\t\t\tbreak;\n\t\tcase FALSE:\n\t\t\tL = new BitSet();\n\t\t\tL.set(0, numStates);\n\t\t\tK = new BitSet();\n\t\t\tbreak;\n\t\tcase AND: {\n\t\t\tAcceptanceGeneric left = getLeft();\n\t\t\tAcceptanceGeneric right = getRight();\n\n\t\t\tif (left.getKind() == ElementType.INF || left.getKind() == ElementType.INF_NOT) {\n\t\t\t\t// swap\n\t\t\t\tAcceptanceGeneric tmp = left;\n\t\t\t\tleft = right;\n\t\t\t\tright = tmp;\n\t\t\t}\n\n\t\t\tswitch (left.getKind()) {\n\t\t\tcase AND:\n\t\t\tcase OR:\n\t\t\tcase FALSE:\n\t\t\tcase TRUE:\n\t\t\tcase INF:\n\t\t\tcase INF_NOT:\n\t\t\t\t// not a Rabin condition\n\t\t\t\treturn null;\n\t\t\tcase FIN:\n\t\t\t\t// Fin(A) <=> <>[]!A\n\t\t\t\t// L = A\n\t\t\t\tL = (BitSet) left.getStates().clone();\n\t\t\t\tbreak;\n\t\t\tcase FIN_NOT:\n\t\t\t\t// Fin(!A) <=> <>[]A\n\t\t\t\t// L = !A\n\t\t\t\tL = (BitSet) left.getStates().clone();\n\t\t\t\tL.flip(0, numStates);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tswitch (right.getKind()) {\n\t\t\tcase AND:\n\t\t\tcase OR:\n\t\t\tcase FALSE:\n\t\t\tcase TRUE:\n\t\t\tcase FIN:\n\t\t\tcase FIN_NOT:\n\t\t\t\t// not a Rabin condition\n\t\t\t\treturn null;\n\t\t\tcase INF:\n\t\t\t\t// Inf(A) <=> []<>A\n\t\t\t\t// K = A\n\t\t\t\tK = (BitSet) right.getStates().clone();\n\t\t\t\tbreak;\n\t\t\tcase INF_NOT:\n\t\t\t\t// Inf(!A) <=> []<>!A\n\t\t\t\t// K = !A\n\t\t\t\tK = (BitSet) right.getStates().clone();\n\t\t\t\tK.flip(0, numStates);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tbreak;\n\t\t}\n\t\tcase FIN:\n\t\t\t// Fin(A) <=> <>[]!A & []<> true <=> RabinPair(A, true)\n\t\t\t// L = A\n\t\t\tL = (BitSet) getStates().clone();\n\t\t\t// K = true\n\t\t\tK = new BitSet();\n\t\t\tK.set(0, numStates);\n\t\t\tbreak;\n\t\tcase FIN_NOT:\n\t\t\t// Fin(!A) <=> <>[]A & []<> true <=> RabinPair(!A, true)\n\t\t\t// L = !A\n\t\t\tL = (BitSet) getStates().clone();\n\t\t\tL.flip(0, numStates);\n\t\t\t// K = true\n\t\t\tK = new BitSet();\n\t\t\tK.set(0, numStates);\n\t\t\tbreak;\n\t\tcase INF:\n\t\t\t// Inf(A) <=> <>[]!false & []<> A <=> RabinPair(false, A)\n\t\t\t// L = false\n\t\t\tL = new BitSet();\n\t\t\t// K = A\n\t\t\tK = (BitSet) getStates().clone();\n\t\t\tbreak;\n\t\tcase INF_NOT:\n\t\t\t// Inf(!A) <=> <>[]!false & []<> !A <=> RabinPair(false, !A)\n\t\t\t// L = false\n\t\t\tL = new BitSet();\n\t\t\t// K = !A\n\t\t\tK = (BitSet) getStates().clone();\n\t\t\tK.flip(0, numStates);\n\t\t\tbreak;\n\t\tcase OR:\n\t\t\t// not a Rabin pair\n\t\t\treturn null;\n\t\t}\n\n\t\treturn new AcceptanceRabin.RabinPair(L, K);\n\t}\n\n\t/**\n\t * Attempt to convert this generic acceptance condition\n\t * to a Streett condition. If this condition does not have\n\t * the required form (top-level conjunction with disjunctive pairs),\n\t * returns {@code null}.\n\t * <br>\n\t * If the condition does not syntactically have the required\n\t * from but can be easily converted to one (e.g., by converting\n\t * a single Inf(S) to a Fin(true) | Inf(S) etc) or by swapping\n\t * Inf and Fin, this will be done.\n\t * <br>\n\t * The BitSets for the state sets are cloned, i.e., modifications of\n\t * the state sets of the returned acceptance condition will not affect\n\t * the original generic acceptance condition.\n\t *\n\t * @param numStates the number of states in the underlying model/automaton (for generating state sets for true)\n\t * @return the generated AcceptanceRabin condition, or false on failure\n\t */\n\tpublic AcceptanceStreett toAcceptanceStreett(int numStates)\n\t{\n\t\tAcceptanceStreett result = new AcceptanceStreett();\n\t\tList<AcceptanceGeneric> conjuncts = extractConjuncts();\n\n\t\tfor (AcceptanceGeneric term : conjuncts) {\n\t\t\tStreettPair pair = term.toAcceptanceStreettPair(numStates);\n\t\t\tif (pair == null) return null;\n\t\t\tresult.add(pair);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Attempt to convert this generic acceptance to a Streett pair.\n\t *\n\t * @param numStates the number of states in the underlying model/automaton (for generating state sets for true)\n\t * @return the generated RabinPair, or false on failure\n\t */\n\tprivate StreettPair toAcceptanceStreettPair(int numStates)\n\t{\n\t\tBitSet R = null, G = null;\n\t\tswitch (getKind()) {\n\t\tcase TRUE:\n\t\t\t// true = []<> false -> []<> false\n\t\t\tR = new BitSet();\n\t\t\tG = new BitSet();\n\t\t\tbreak;\n\t\tcase FALSE:\n\t\t\t// false = []<> true -> []<> false\n\t\t\tR = new BitSet();\n\t\t\tR.set(0, numStates);\n\t\t\tG = new BitSet();\n\t\t\tbreak;\n\t\tcase OR: {\n\t\t\tAcceptanceGeneric left = getLeft();\n\t\t\tAcceptanceGeneric right = getRight();\n\n\t\t\tif (left.getKind() == ElementType.INF || left.getKind() == ElementType.INF_NOT) {\n\t\t\t\t// swap\n\t\t\t\tAcceptanceGeneric tmp = left;\n\t\t\t\tleft = right;\n\t\t\t\tright = tmp;\n\t\t\t}\n\n\t\t\tswitch (left.getKind()) {\n\t\t\tcase AND:\n\t\t\tcase OR:\n\t\t\tcase FALSE:\n\t\t\tcase TRUE:\n\t\t\tcase INF:\n\t\t\tcase INF_NOT:\n\t\t\t\t// not a Streett condition\n\t\t\t\treturn null;\n\t\t\tcase FIN:\n\t\t\t\t// Fin(A) -> R = A\n\t\t\t\tR = (BitSet) left.getStates().clone();\n\t\t\t\tbreak;\n\t\t\tcase FIN_NOT:\n\t\t\t\t// Fin(!A) -> R = !A\n\t\t\t\tR = (BitSet) left.getStates().clone();\n\t\t\t\tR.flip(0, numStates);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tswitch (right.getKind()) {\n\t\t\tcase AND:\n\t\t\tcase OR:\n\t\t\tcase FALSE:\n\t\t\tcase TRUE:\n\t\t\tcase FIN:\n\t\t\tcase FIN_NOT:\n\t\t\t\t// not a Streett condition\n\t\t\t\treturn null;\n\t\t\tcase INF:\n\t\t\t\t// Inf(A) -> G = A\n\t\t\t\tG = (BitSet) right.getStates().clone();\n\t\t\t\tbreak;\n\t\t\tcase INF_NOT:\n\t\t\t\t// Inf(!A) -> G = !A\n\t\t\t\tG = (BitSet) right.getStates().clone();\n\t\t\t\tG.flip(0, numStates);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tbreak;\n\t\t}\n\t\tcase FIN:\n\t\t\t// Fin(A) <=> []<>A -> []<>false\n\t\t\t// R = A\n\t\t\tR = (BitSet) getStates().clone();\n\t\t\t// G = false\n\t\t\tG = new BitSet();\n\t\t\tbreak;\n\t\tcase FIN_NOT:\n\t\t\t// Fin(!A) <=> []<>!A -> []<>false\n\t\t\t// R = !A\n\t\t\tR = (BitSet) getStates().clone();\n\t\t\tR.flip(0, numStates);\n\t\t\t// G = false\n\t\t\tG = new BitSet();\n\t\t\tbreak;\n\t\tcase INF:\n\t\t\t// Inf(A) <=> []<>true -> []<>A\n\t\t\t// R = true\n\t\t\tR = new BitSet();\n\t\t\tR.set(0, numStates);\n\t\t\t// G = A\n\t\t\tG = (BitSet) getStates().clone();\n\t\t\tbreak;\n\t\tcase INF_NOT:\n\t\t\t// Inf(!A) <=> []<>true -> []<>!A\n\t\t\t// R = true\n\t\t\tR = new BitSet();\n\t\t\tR.set(0, numStates);\n\t\t\t// G = !A\n\t\t\tG = (BitSet) getStates().clone();\n\t\t\tG.flip(0, numStates);\n\t\t\tbreak;\n\t\tcase AND:\n\t\t\t// not a Streett pair\n\t\t\treturn null;\n\t\t}\n\n\t\treturn new AcceptanceStreett.StreettPair(R,G);\n\t}\n\n\t/**\n\t * Extract the operands of the top-level disjunctions, e.g.,\n\t * for (A & B) | (C | D)) would return the list [A&B,C,D].\n\t */\n\tpublic List<AcceptanceGeneric> extractDisjuncts()\n\t{\n\t\tArrayList<AcceptanceGeneric> result = new ArrayList<AcceptanceGeneric>();\n\t\tStack<AcceptanceGeneric> todo = new Stack<AcceptanceGeneric>();\n\n\t\ttodo.add(this);\n\t\twhile (!todo.isEmpty()) {\n\t\t\tAcceptanceGeneric current = todo.pop();\n\t\t\tswitch (current.getKind()) {\n\t\t\tcase AND:\n\t\t\tcase FALSE:\n\t\t\tcase TRUE:\n\t\t\tcase FIN:\n\t\t\tcase FIN_NOT:\n\t\t\tcase INF:\n\t\t\tcase INF_NOT:\n\t\t\t\t// not a top level disjunction, add to list\n\t\t\t\tresult.add(current);\n\t\t\t\tbreak;\n\t\t\tcase OR:\n\t\t\t\t// still a top level disjunction, recurse\n\t\t\t\ttodo.push(current.getRight());\n\t\t\t\ttodo.push(current.getLeft());\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Extract the operands of the top-level conjunctions, e.g.,\n\t * for (A | B) & (C & D)) would return the list [A|B,C,D].\n\t */\n\tpublic List<AcceptanceGeneric> extractConjuncts()\n\t{\n\t\tArrayList<AcceptanceGeneric> result = new ArrayList<AcceptanceGeneric>();\n\t\tStack<AcceptanceGeneric> todo = new Stack<AcceptanceGeneric>();\n\n\t\ttodo.add(this);\n\t\twhile (!todo.isEmpty()) {\n\t\t\tAcceptanceGeneric current = todo.pop();\n\t\t\tswitch (current.getKind()) {\n\t\t\tcase OR:\n\t\t\tcase FALSE:\n\t\t\tcase TRUE:\n\t\t\tcase FIN:\n\t\t\tcase FIN_NOT:\n\t\t\tcase INF:\n\t\t\tcase INF_NOT:\n\t\t\t\t// not a top level conjunction, add to list\n\t\t\t\tresult.add(current);\n\t\t\t\tbreak;\n\t\t\tcase AND:\n\t\t\t\t// still a top level conjunction, recurse\n\t\t\t\ttodo.push(current.getRight());\n\t\t\t\ttodo.push(current.getLeft());\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String toString() {\n\t\tswitch(kind) {\n\t\t\tcase TRUE:\n\t\t\t\treturn \"true\";\n\t\t\tcase FALSE:\n\t\t\t\treturn \"false\";\n\t\t\tcase AND:\n\t\t\t\treturn  \"(\" + left.toString() + \" & \" + right.toString() + \")\";\n\t\t\tcase OR:\n\t\t\t\treturn  \"(\" + left.toString() + \" | \" + right.toString() + \")\";\n\t\t\tcase INF:\n\t\t\t\treturn \"Inf(\" + states.toString() + \")\";\n\t\t\tcase FIN:\n\t\t\t\treturn \"Fin(\" + states.toString() + \")\";\n\t\t\tcase INF_NOT:\n\t\t\t\treturn \"Inf(!\" + states.toString() + \")\";\n\t\t\tcase FIN_NOT:\n\t\t\t\treturn \"Fin(!\" + states.toString() + \")\";\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t}\n\t}\n\n\t@Override\n\tpublic void outputHOAHeader(PrintStream out)\n\t{\n\t\tList<AcceptanceGeneric> leafNodes = getLeafNodes();\n\t\tout.print(\"Acceptance: \"+leafNodes.size()+\" \");\n\t\toutputHOAFormula(out, 0);\n\t\tout.println();\n\t}\n\n\tprivate int outputHOAFormula(PrintStream out, int nextSetIndex)\n\t{\n\t\tswitch (kind) {\n\t\tcase AND:\n\t\t\tout.print(\"(\");\n\t\t\tnextSetIndex = left.outputHOAFormula(out, nextSetIndex);\n\t\t\tout.print(\")&(\");\n\t\t\tnextSetIndex = right.outputHOAFormula(out, nextSetIndex);\n\t\t\tout.print(\")\");\n\t\t\treturn nextSetIndex;\n\t\tcase OR:\n\t\t\tout.print(\"(\");\n\t\t\tnextSetIndex = left.outputHOAFormula(out, nextSetIndex);\n\t\t\tout.print(\")|(\");\n\t\t\tnextSetIndex = right.outputHOAFormula(out, nextSetIndex);\n\t\t\tout.print(\")\");\n\t\t\treturn nextSetIndex;\n\t\tcase TRUE:\n\t\t\tout.print(\"t\");\n\t\t\treturn nextSetIndex;\n\t\tcase FALSE:\n\t\t\tout.print(\"f\");\n\t\t\treturn nextSetIndex;\n\t\tcase FIN:\n\t\t\tout.print(\"Fin(\"+nextSetIndex+\")\");\n\t\t\treturn nextSetIndex+1;\n\t\tcase FIN_NOT:\n\t\t\tout.print(\"Fin(!\"+nextSetIndex+\")\");\n\t\t\treturn nextSetIndex+1;\n\t\tcase INF:\n\t\t\tout.print(\"Inf(\"+nextSetIndex+\")\");\n\t\t\treturn nextSetIndex+1;\n\t\tcase INF_NOT:\n\t\t\tout.print(\"Inf(!\"+nextSetIndex+\")\");\n\t\t\treturn nextSetIndex+1;\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unknown kind\");\n\t}\n\n\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceGenericDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport common.IterableBitSet;\nimport acceptance.AcceptanceGeneric.ElementType;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismNotSupportedException;\n\n/**\n * A generic acceptance condition (based on JDD state sets).\n * This is an AST of a boolean formula (conjunction and disjunction) over\n * atoms of the form Inf(states), Inf(!states), Fin(states) and Fin(!states).\n * <br>\n * Semantics:\n *  Inf(states)  <=> G F states\n *  Inf(!states) <=> G F !states\n *  Fin(states)  <=> F G !states\n *  Fin(!states) <=> F G states\n */\npublic class AcceptanceGenericDD implements AcceptanceOmegaDD {\n\n\tprivate ElementType kind;\n\tprivate AcceptanceGenericDD left = null;\n\tprivate AcceptanceGenericDD right = null;\n\tprivate JDDNode states = null;\n\n\tpublic AcceptanceGenericDD(AcceptanceGeneric acceptance, JDDVars ddRowVars)\n\t{\n\t\tswitch(acceptance.getKind()) {\n\t\t\tcase AND:\n\t\t\tcase OR:\n\t\t\t\tkind = acceptance.getKind();\n\t\t\t\tleft = (AcceptanceGenericDD) acceptance.getLeft().toAcceptanceDD(ddRowVars);\n\t\t\t\tright = (AcceptanceGenericDD) acceptance.getRight().toAcceptanceDD(ddRowVars);\n\t\t\t\treturn;\n\t\t\tcase TRUE:\n\t\t\t\tkind = ElementType.TRUE;\n\t\t\t\treturn;\n\t\t\tcase FALSE:\n\t\t\t\tkind = ElementType.FALSE;\n\t\t\t\treturn;\n\t\t\tcase INF:\n\t\t\tcase INF_NOT:\n\t\t\tcase FIN:\n\t\t\tcase FIN_NOT:\n\t\t\t\tkind = acceptance.getKind();\n\t\t\t\tstates = JDD.Constant(0);\n\t\t\t\tfor (int i : IterableBitSet.getSetBits(acceptance.getStates())) {\n\t\t\t\t\tstates = JDD.SetVectorElement(states, ddRowVars, i, 1.0);\n\t\t\t\t}\n\t\t\t\treturn;\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operatator in generic acceptance condition\");\n\t}\n\n\t/**\n\t * Constructor for TRUE or FALSE\n\t * @param value true or false?\n\t */\n\tpublic AcceptanceGenericDD(boolean value) {\n\t\tkind = value ? ElementType.TRUE : ElementType.FALSE;\n\t}\n\n\t/**\n\t * Constructor for an INF, FIN, INF_NOT or FIN_NOT element.\n\t * <br>[ STORES: <i>states</i> ]\n\t */\n\tpublic AcceptanceGenericDD(ElementType kind, JDDNode states)\n\t{\n\t\tthis.kind = kind;\n\t\tleft = null;\n\t\tright = null;\n\t\tthis.states = states;\n\t}\n\n\t/**\n\t * Constructor for a binary operator (AND/OR).\n\t * <br>[ STORES: <i>left, right operand</i> ]\n\t */\n\tpublic AcceptanceGenericDD(ElementType kind, AcceptanceGenericDD left, AcceptanceGenericDD right)\n\t{\n\t\tthis.kind = kind;\n\t\tthis.left = left;\n\t\tthis.right = right;\n\t\tstates = null;\n\t}\n\n\t/** Get the ElementType of this AST element */\n\tpublic ElementType getKind()\n\t{\n\t\treturn kind;\n\t}\n\n\t/** Get the left child of this AST element */\n\tpublic AcceptanceGenericDD getLeft()\n\t{\n\t\treturn left;\n\t}\n\n\t/** Get the right child of this AST element */\n\tpublic AcceptanceGenericDD getRight()\n\t{\n\t\treturn right;\n\t}\n\n\t/** Get a referenced copy of the state sets (if kind is one of INF, FIN, INF_NOT, FIN_NOT).\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getStates()\n\t{\n\t\tif (states != null) {\n\t\t\tJDD.Ref(states);\n\t\t}\n\t\treturn states;\n\t}\n\n\t@Override\n\tpublic boolean isBSCCAccepting(JDDNode bscc)\n\t{\n\t\tswitch(kind) {\n\t\tcase TRUE: \n\t\t\treturn true;\n\t\tcase FALSE: \n\t\t\treturn false;\n\t\tcase AND: \n\t\t\treturn left.isBSCCAccepting(bscc) && right.isBSCCAccepting(bscc);\n\t\tcase OR: \n\t\t\treturn left.isBSCCAccepting(bscc) || right.isBSCCAccepting(bscc);\n\t\tcase INF:\n\t\t\t// bscc |= G F states?\n\t\t\t// there exists a state in bscc and states\n\t\t\treturn JDD.AreIntersecting(states, bscc);\n\t\tcase INF_NOT:\n\t\t\t// bscc_state |= G F !states?\n\t\t\t// the BSCC intersects Not(states)\n\t\t\tJDD.Ref(states);\n\t\t\treturn JDD.AreIntersecting(JDD.Not(states), bscc);\n\t\tcase FIN:\n\t\t\t// bscc |= F G !states?\n\t\t\t// the BSCC consists only of !states\n\t\t\treturn !JDD.AreIntersecting(states, bscc);\n\t\tcase FIN_NOT:\n\t\t\t// bscc |= F G states?\n\t\t\t// the BSCC consists entirely of states\n\t\t\tJDD.Ref(states);\n\t\t\treturn !JDD.AreIntersecting(JDD.Not(states), bscc);\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operator in generic acceptance expression\");\n\t}\n\n\t@Override\n\tpublic void intersect(JDDNode restrict)\n\t{\n\t\tswitch(kind) {\n\t\tcase TRUE:\n\t\tcase FALSE:\n\t\t\treturn;\n\t\tcase AND:\n\t\tcase OR:\n\t\t\tleft.intersect(restrict);\n\t\t\tright.intersect(restrict);\n\t\t\treturn;\n\t\tcase INF:\n\t\tcase INF_NOT:\n\t\tcase FIN:\n\t\tcase FIN_NOT:\n\t\t\tstates = JDD.And(states, restrict.copy());\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operator in generic acceptance expression\");\n\t}\n\n\n\t@Override\n\tpublic AcceptanceGenericDD clone()\n\t{\n\t\tswitch(kind) {\n\t\tcase TRUE:\n\t\t\treturn new AcceptanceGenericDD(true);\n\t\tcase FALSE:\n\t\t\treturn new AcceptanceGenericDD(false);\n\t\tcase AND:\n\t\t\treturn new AcceptanceGenericDD(ElementType.AND, left.clone(), right.clone());\n\t\tcase OR:\n\t\t\treturn new AcceptanceGenericDD(ElementType.OR, left.clone(), right.clone());\n\t\tcase INF:\n\t\tcase INF_NOT:\n\t\tcase FIN:\n\t\tcase FIN_NOT:\n\t\t\treturn new AcceptanceGenericDD(kind, states.copy());\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operatator in generic acceptance condition\");\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics() {\n\t\treturn \"generic acceptance with \" + countAcceptanceSets() + \" acceptance sets\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType() {\n\t\treturn AcceptanceType.GENERIC;\n\t}\n\n\t@Override\n\tpublic AcceptanceOmegaDD complement(AcceptanceType... allowedAcceptance) throws PrismNotSupportedException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn this.complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to required acceptance type\");\n\t}\n\n\t/** Complement this acceptance condition, return as AcceptanceGeneric. */\n\t@Override\n\tpublic AcceptanceGenericDD complementToGeneric()\n\t{\n\t\t// overrides the default implementation in AcceptanceOmegaDD, as it's the base case\n\t\t// that is used there\n\n\t\tswitch (kind) {\n\t\tcase TRUE:\n\t\t\treturn new AcceptanceGenericDD(false);\n\t\tcase FALSE:\n\t\t\treturn new AcceptanceGenericDD(true);\n\t\tcase AND:\n\t\t\treturn new AcceptanceGenericDD(ElementType.OR,\n\t\t\t                               getLeft().complementToGeneric(),\n\t\t\t                               getRight().complementToGeneric());\n\t\tcase OR:\n\t\t\treturn new AcceptanceGenericDD(ElementType.AND,\n\t\t\t                               getLeft().complementToGeneric(),\n\t\t\t                               getRight().complementToGeneric());\n\t\tcase FIN:\n\t\t\treturn new AcceptanceGenericDD(ElementType.INF, states.copy());\n\t\tcase FIN_NOT:\n\t\t\treturn new AcceptanceGenericDD(ElementType.INF_NOT, states.copy());\n\t\tcase INF:\n\t\t\treturn new AcceptanceGenericDD(ElementType.FIN, states.copy());\n\t\tcase INF_NOT:\n\t\t\treturn new AcceptanceGenericDD(ElementType.FIN_NOT, states.copy());\n\t\tdefault:\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\t}\n\n\t@Override\n\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n\t{\n\t\treturn this.clone();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic void clear() {\n\t\tswitch (kind) {\n\t\t\tcase TRUE:\n\t\t\tcase FALSE:\n\t\t\t\treturn;\n\t\t\tcase AND:\n\t\t\tcase OR:\n\t\t\t\tleft.clear();\n\t\t\t\tright.clear();\n\t\t\t\treturn;\n\t\t\tcase INF_NOT:\n\t\t\tcase FIN:\n\t\t\tcase FIN_NOT:\n\t\t\tcase INF:\n\t\t\t\tif (states != null) JDD.Deref(states);\n\t\t\t\tstates = null;\n\t\t\t\treturn;\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operator in generic acceptance expression\");\n\t}\n\n\t/** Count the number of state sets in this acceptance condition */\n\tpublic int countAcceptanceSets() {\n\t\tswitch(kind) {\n\t\t\tcase FALSE:\n\t\t\tcase TRUE:\n\t\t\t\treturn 0;\n\t\t\tcase INF:\n\t\t\tcase FIN: \n\t\t\tcase INF_NOT:\n\t\t\tcase FIN_NOT:\n\t\t\t\treturn 1;\n\t\t\tcase OR:\n\t\t\tcase AND: \n\t\t\t\treturn left.countAcceptanceSets() + right.countAcceptanceSets();\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operator in generic acceptance expression\");\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceOmega.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.io.PrintStream;\nimport java.util.BitSet;\n\nimport prism.PrismException;\nimport jdd.JDDVars;\n\n/**\n * Generic interface for an omega-regular acceptance condition (BitSet-based).\n */\npublic interface AcceptanceOmega extends Cloneable\n{\n\t/** Returns true if the bottom strongly connected component (BSSC)\n\t *  given by bscc_states is accepting for this acceptance condition.\n\t **/\n\tpublic boolean isBSCCAccepting(BitSet bscc_states);\n\n\t/** Get the acceptance signature for state {@code stateIndex}.\n\t **/\n\tpublic String getSignatureForState(int stateIndex);\n\n\t/** Get the acceptance signature for state {@code stateIndex} (HOA format).\n\t */\n\tpublic String getSignatureForStateHOA(int stateIndex);\n\n\t/**\n\t * Get a string describing the acceptance condition's size,\n\t * i.e. \"x Rabin pairs\", etc.\n\t */\n\tpublic String getSizeStatistics();\n\n\t/** Returns the AcceptanceType of this acceptance condition */\n\tpublic AcceptanceType getType();\n\n\t/** Returns the type of this acceptance condition as a String,\n\t * i.e., \"R\" for Rabin.\n\t * <br>\n\t * Deprecated, use {@code getType().getNameAbbreviated()}\n\t */\n\t@Deprecated\n\tpublic String getTypeAbbreviated();\n\n\t/** Returns a full name for this acceptance condition\n\t * <br>\n\t * Deprecated, use {@code getType()} in String context or {@code getType().getName()}\n\t */\n\t@Deprecated\n\tpublic String getTypeName();\n\n\t/** Print the appropriate Acceptance (and potentially acc-name) header */\n\tpublic void outputHOAHeader(PrintStream out);\n\n\t/** Make a copy of the acceptance condition. */\n\tpublic AcceptanceOmega clone();\n\n\t/**\n\t * Complement the acceptance condition if possible.\n\t * @param numStates the number of states in the underlying model / automaton (needed for complementing BitSets)\n\t * @param allowedAcceptance the allowed acceptance types that may be used for complementing\n\t */\n\tpublic AcceptanceOmega complement(int numStates, AcceptanceType... allowedAcceptance) throws PrismException;\n\n\t/** Abstract functor for use with the lift function. */\n\tpublic static abstract class LiftBitSet {\n\t\tpublic abstract BitSet lift(BitSet states);\n\t};\n\n\t/**\n\t * Lift the state sets in the acceptance condition.\n\t * For each state set {@code states} in the condition,\n\t * {@code lifter.lift(states)} is called and the state set is\n\t * replaced by the result.\n\t **/\n\tpublic void lift(LiftBitSet lifter);\n\n\t/**\n\t * Convert this BitSet based acceptance condition to the corresponding BDD based acceptance condition.\n\t * @param ddRowVars JDDVars of the row variables corresponding to the bits in the bitset\n\t */\n\tpublic AcceptanceOmegaDD toAcceptanceDD(JDDVars ddRowVars);\n\t\n\t/**\n\t * Convert this acceptance condition to an AcceptanceGeneric condition.\n\t */\n\tpublic AcceptanceGeneric toAcceptanceGeneric();\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceOmegaDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport jdd.JDDNode;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Generic interface for an omega-regular acceptance condition (BDD-based).\n */\npublic interface AcceptanceOmegaDD extends Cloneable\n{\n\t/** Returns true if the bottom strongly connected component (BSSC)\n\t *  given by bscc_states is accepting for this acceptance condition.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t **/\n\tpublic boolean isBSCCAccepting(JDDNode bscc_states);\n\n\t/**\n\t * Provides a copy of this acceptance condition.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic AcceptanceOmegaDD clone();\n\n\t/**\n\t * Replaces the BDD functions for all the acceptance sets\n\t * of this acceptance condition with the intersection\n\t * of the current acceptance sets and the function {@code restrict}.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic void intersect(JDDNode restrict);\n\n\t/**\n\t * Get a string describing the acceptance condition's size,\n\t * i.e. \"x Rabin pairs\", etc.\n\t */\n\tpublic String getSizeStatistics();\n\n\t/** Returns the AcceptanceType of this acceptance condition */\n\tpublic AcceptanceType getType();\n\n\t/**\n\t * Complement the acceptance condition if possible.\n\t * <br>\n\t * [ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param allowedAcceptance the allowed acceptance types that may be used for complementing\n\t * @throws PrismNotSupportedException if none of the allowed acceptance types can be used as target for complementing\n\t */\n\tpublic AcceptanceOmegaDD complement(AcceptanceType... allowedAcceptance) throws PrismNotSupportedException;\n\n\t/**\n\t * Complement this acceptance condition to an AcceptanceGeneric condition.\n\t * <br>\n\t * Default implementation: toAcceptanceGeneric().complementToGeneric()\n\t * [ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic default AcceptanceGenericDD complementToGeneric()\n\t{\n\t\tAcceptanceGenericDD generic = this.toAcceptanceGeneric();\n\t\tAcceptanceGenericDD complemented = generic.complementToGeneric();\n\t\tgeneric.clear();\n\t\treturn complemented;\n\t}\n\n\t/**\n\t * Convert this acceptance condition to an AcceptanceGeneric condition.\n\t * <br>\n\t * [ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic AcceptanceGenericDD toAcceptanceGeneric();\n\n\t/** Returns the type of this acceptance condition as a String,\n\t * i.e., \"R\" for Rabin\n\t */\n\t@Deprecated\n\tpublic String getTypeAbbreviated();\n\n\t/**\n\t * Clear the resources used by this acceptance condition.\n\t * Call to ensure that the JDD based state sets actually get\n\t * dereferenced.\n\t */\n\tvoid clear();\n\n\t/** Returns a full name for this acceptance condition */\n\t@Deprecated\n\tpublic String getTypeName();\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceRabin.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\n\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport jdd.JDDVars;\n\n/**\n * A Rabin acceptance condition (based on BitSet state sets).\n * This is a list of RabinPairs, which can be manipulated with the usual List interface.\n * <br>\n * Semantics: Each Rabin pair has a state set L and K and is accepting iff\n * L is not visited infinitely often and K is visited infinitely often:\n *   (F G !\"L\") & (G F \"K\").\n *\n * The Rabin condition is accepting if at least one of the pairs is accepting.\n */\n@SuppressWarnings(\"serial\")\npublic class AcceptanceRabin\n       extends ArrayList<AcceptanceRabin.RabinPair>\n       implements AcceptanceOmega\n{\n\n\t/**\n\t * A pair in a Rabin acceptance condition, i.e., with\n\t *  (F G !\"L\")  &  (G F \"K\")\n\t **/\n\tpublic static class RabinPair {\n\t\t/** State set L (should be visited only finitely often) */\n\t\tprivate BitSet L;\n\n\t\t/** State set K (should be visited infinitely often) */\n\t\tprivate BitSet K;\n\n\t\t/**\n\t\t * Constructor with L and K state sets.\n\t\t *  (F G !\"L\")  &  (G F \"K\")\n\t\t */\n\t\tpublic RabinPair(BitSet L, BitSet K) {\n\t\t\tthis.L = L;\n\t\t\tthis.K = K;\n\t\t}\n\n\t\t/** Get the state set L */\n\t\tpublic BitSet getL()\n\t\t{\n\t\t\treturn L;\n\t\t}\n\n\t\t/** Get the state set K */\n\t\tpublic BitSet getK()\n\t\t{\n\t\t\treturn K;\n\t\t}\n\n\t\t/** Returns true if the bottom strongly connected component\n\t\t * given by bscc_states is accepting for this pair.\n\t\t */\n\t\tpublic boolean isBSCCAccepting(BitSet bscc_states)\n\t\t{\n\t\t\tif (L.intersects(bscc_states)) {\n\t\t\t\t// there is some state in bscc_states that is\n\t\t\t\t// forbidden by L\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\tif (K.intersects(bscc_states)) {\n\t\t\t\t// there is some state in bscc_states that is\n\t\t\t\t// contained in K -> infinitely often visits to K\n\t\t\t\treturn true;\n\t\t\t}\n\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t\t{\n\t\t\tAcceptanceGeneric genericL = new AcceptanceGeneric(AcceptanceGeneric.ElementType.FIN, (BitSet)L.clone());\n\t\t\tAcceptanceGeneric genericK = new AcceptanceGeneric(AcceptanceGeneric.ElementType.INF, (BitSet)K.clone());\n\t\t\t\n\t\t\t//      F G ! \"L\" & G F \"K\"\n\t\t\t// <=>  Fin(L) & Inf(K)\n\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.AND, genericL, genericK);\n\t\t}\n\n\t\t/** Generate signature for this Rabin pair and the given state.\n\t\t *  If the state is a member of L, returns \"-pairIndex\".\n\t\t *  If the state is a member of K, returns \"+pairIndex\".\n\t\t *  @param stateIndex the state index\n\t\t *  @param pairIndex the index of this Rabin pair\n\t\t **/\n\t\tpublic String getSignatureForState(int stateIndex, int pairIndex)\n\t\t{\n\t\t\tif (L.get(stateIndex)) {\n\t\t\t\treturn \"-\"+pairIndex;\n\t\t\t} else if (K.get(stateIndex)) {\n\t\t\t\treturn \"+\"+pairIndex;\n\t\t\t} else {\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic RabinPair clone()\n\t\t{\n\t\t\treturn new RabinPair((BitSet)L.clone(), (BitSet)K.clone());\n\t\t}\n\n\t\t/** Returns a textual representation of this Rabin pair. */\n\t\t@Override\n\t\tpublic String toString() {\n\t\t\treturn \"(\" + L + \",\" + K + \")\";\n\t\t}\n\t}\n\n\t/** Make a copy of the acceptance condition. */\n\tpublic AcceptanceRabin clone()\n\t{\n\t\tAcceptanceRabin result = new AcceptanceRabin();\n\t\tfor (RabinPair pair : this) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/** Returns true if the bottom strongly connected component\n\t * given by bscc_states is accepting for this Rabin condition,\n\t * i.e., there is a pair that accepts for bscc_states.\n\t */\n\tpublic boolean isBSCCAccepting(BitSet bscc_states)\n\t{\n\t\tfor (RabinPair pair : this) {\n\t\t\tif (pair.isBSCCAccepting(bscc_states)) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic void lift(LiftBitSet lifter) {\n\t\tfor (RabinPair pair : this) {\n\t\t\tpair.L = lifter.lift(pair.L);\n\t\t\tpair.K = lifter.lift(pair.K);\n\t\t}\n\t}\n\n\t/**\n\t * Get the Streett acceptance condition that is the dual of this Rabin acceptance condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Streett condition.\n\t * @return the complement Streett acceptance condition\n\t */\n\tpublic AcceptanceStreett complementToStreett()\n\t{\n\t\tAcceptanceStreett accStreett = new AcceptanceStreett();\n\n\t\tfor (RabinPair accPairRabin : this) {\n\t\t\tBitSet R = (BitSet) accPairRabin.getK().clone();\n\t\t\tBitSet G = (BitSet) accPairRabin.getL().clone();\n\t\t\tAcceptanceStreett.StreettPair accPairStreett = new AcceptanceStreett.StreettPair(R, G);\n\t\t\taccStreett.add(accPairStreett);\n\t\t}\n\n\t\treturn accStreett;\n\t}\n\n\t/** Complement this acceptance condition, return as AcceptanceGeneric. */\n\tpublic AcceptanceGeneric complementToGeneric()\n\t{\n\t\treturn toAcceptanceGeneric().complementToGeneric();\n\t}\n\n\t@Override\n\tpublic AcceptanceOmega complement(int numStates, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.STREETT)) {\n\t\t\treturn complementToStreett();\n\t\t}\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\t/**\n\t * Returns a new Rabin acceptance condition that corresponds to the disjunction\n\t * of this and the other Rabin acceptance condition. The RabinPairs are cloned, i.e.,\n\t * not shared with the argument acceptance condition.\n\t * @param other the other Rabin acceptance condition\n\t * @return new AcceptanceRabin, disjunction of this and other\n\t */\n\tpublic AcceptanceRabin or(AcceptanceRabin other)\n\t{\n\t\tAcceptanceRabin result = new AcceptanceRabin();\n\t\tfor (RabinPair pair : this) {\n\t\t\tresult.add((RabinPair) pair.clone());\n\t\t}\n\t\tfor (RabinPair pair : other) {\n\t\t\tresult.add((RabinPair) pair.clone());\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic AcceptanceRabinDD toAcceptanceDD(JDDVars ddRowVars)\n\t{\n\t\treturn new AcceptanceRabinDD(this, ddRowVars);\n\t}\n\n\t@Override\n\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t{\n\t\tif (size() == 0) {\n\t\t\treturn new AcceptanceGeneric(false);\n\t\t}\n\t\tAcceptanceGeneric genericPairs = null;\n\t\tfor (RabinPair pair : this) {\n\t\t\tAcceptanceGeneric genericPair = pair.toAcceptanceGeneric();\n\t\t\tif (genericPairs == null) {\n\t\t\t\tgenericPairs = genericPair;\n\t\t\t} else {\n\t\t\t\tgenericPairs = new AcceptanceGeneric(AcceptanceGeneric.ElementType.OR, genericPairs, genericPair);\n\t\t\t}\n\t\t}\n\t\treturn genericPairs;\n\t}\n\n\t/**\n\t * Get the acceptance signature for state stateIndex.\n\t **/\n\tpublic String getSignatureForState(int stateIndex)\n\t{\n\t\tString result = \"\";\n\n\t\tfor (int pairIndex=0; pairIndex<size(); pairIndex++) {\n\t\t\tRabinPair pair = get(pairIndex);\n\t\t\tresult += pair.getSignatureForState(stateIndex,  pairIndex);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSignatureForStateHOA(int stateIndex)\n\t{\n\t\tString result = \"\";\n\n\t\tfor (int pairIndex=0; pairIndex<size(); pairIndex++) {\n\t\t\tRabinPair pair = get(pairIndex);\n\t\t\tif (pair.getL().get(stateIndex)) {\n\t\t\t\tresult += (result.isEmpty() ? \"\" : \" \") + pairIndex*2;\n\t\t\t}\n\t\t\tif (pair.getK().get(stateIndex)) {\n\t\t\t\tresult += (result.isEmpty() ? \"\" : \" \") + (pairIndex*2+1);\n\t\t\t}\n\t\t}\n\n\t\tif (!result.isEmpty())\n\t\t\tresult = \"{\"+result+\"}\";\n\n\t\treturn result;\n\t}\n\n\t\n\t/** Returns a textual representation of this acceptance condition. */\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString result = \"\";\n\t\tfor (RabinPair pair : this) {\n\t\t\tresult += pair.toString();\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn size() + \" Rabin pairs\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.RABIN;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic void outputHOAHeader(PrintStream out)\n\t{\n\t\tout.println(\"acc-name: Rabin \"+size());\n\t\tout.print(\"Acceptance: \" + (size()*2)+\" \");\n\t\tif (size() == 0) {\n\t\t\tout.println(\"f\");\n\t\t\treturn;\n\t\t}\n\n\t\tfor (int pair = 0; pair < size(); pair++) {\n\t\t\tif (pair > 0) out.print(\" | \");\n\t\t\tout.print(\"( Fin(\" + 2*pair + \") & Inf(\" + (2*pair+1) +\") )\");\n\t\t}\n\t\tout.println();\n\t}\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceRabinDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.util.ArrayList;\n\nimport common.IterableBitSet;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismNotSupportedException;\n\n/**\n * A Rabin acceptance condition (based on JDD state sets)\n * This is a list of RabinPairs, which can be manipulated with the usual List interface.\n * <br>\n * Semantics: Each Rabin pair has a state set L and K and is accepting iff\n * L is not visited infinitely often and K is visited infinitely often:\n *   (F G !\"L\") & (G F \"K\").\n *\n * The Rabin condition is accepting if at least one of the pairs is accepting.\n */\n@SuppressWarnings(\"serial\")\npublic class AcceptanceRabinDD\n       extends ArrayList<AcceptanceRabinDD.RabinPairDD>\n       implements AcceptanceOmegaDD\n{\n\n\t/**\n\t * A pair in a Rabin acceptance condition, i.e., with\n\t *  (F G !\"L\")  &  (G F \"K\")\n\t **/\n\tpublic static class RabinPairDD {\n\t\t/** State set L (should be visited only finitely often) */\n\t\tprivate JDDNode L;\n\n\t\t/** State set K (should be visited infinitely often) */\n\t\tprivate JDDNode K;\n\n\t\t/**\n\t\t * Constructor with L and K state sets.\n\t\t * Becomes owner of the references of L and K.\n\t\t */\n\t\tpublic RabinPairDD(JDDNode L, JDDNode K)\n\t\t{\n\t\t\tthis.L = L;\n\t\t\tthis.K = K;\n\t\t}\n\n\t\t/** Clear resources of the state sets */\n\t\tpublic void clear()\n\t\t{\n\t\t\tif (L!=null) JDD.Deref(L);\n\t\t\tif (K!=null) JDD.Deref(K);\n\t\t}\n\n\t\t/** Get a referenced copy of the state set L.\n\t\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic JDDNode getL()\n\t\t{\n\t\t\treturn L.copy();\n\t\t}\n\n\t\t/** Get a referenced copy of the state set K.\n\t\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic JDDNode getK()\n\t\t{\n\t\t\treturn K.copy();\n\t\t}\n\n\t\tpublic RabinPairDD clone()\n\t\t{\n\t\t\treturn new RabinPairDD(getL(), getK());\n\t\t}\n\n\t\t/** Returns true if the bottom strongly connected component\n\t\t * given by bscc_states is accepting for this pair.\n\t\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic boolean isBSCCAccepting(JDDNode bscc_states)\n\t\t{\n\t\t\tif (JDD.AreIntersecting(L, bscc_states)) {\n\t\t\t\t// there is some state in bscc_states that is\n\t\t\t\t// forbidden by L\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\tif (JDD.AreIntersecting(K, bscc_states)) {\n\t\t\t\t// there is some state in bscc_states that is\n\t\t\t\t// contained in K -> infinitely often visits to K\n\t\t\t\treturn true;\n\t\t\t}\n\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n \t\t{\n\t\t\tAcceptanceGenericDD genericL = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.FIN, getL());\n\t\t\tAcceptanceGenericDD genericK = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.INF, getK());\n\n\t\t\t//      F G ! \"L\" & G F \"K\"\n\t\t\t// <=>  Fin(L) & Inf(K)\n\t\t\treturn new AcceptanceGenericDD(AcceptanceGeneric.ElementType.AND, genericL, genericK);\n \t\t}\n\n\t\t/**\n\t\t * Replaces the BDD functions for the acceptance sets\n\t\t * of this Rabin pair with the intersection\n\t\t * of the current acceptance sets and the function {@code restrict}.\n\t\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic void intersect(JDDNode restrict)\n\t\t{\n\t\t\tL = JDD.And(L, restrict.copy());\n\t\t\tK = JDD.And(K, restrict.copy());\n\t\t}\n\n\t\t/** Returns a textual representation of this Rabin pair. */\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn \"(\" + L + \",\" + K + \")\";\n\t\t}\n\t}\n\n\t/** Constructor, create empty condition */\n\tpublic AcceptanceRabinDD()\n\t{\n\t}\n\n\t/**\n\t * Constructor, from a BitSet-based AcceptanceRabin.\n\t *\n\t * @param acceptance the BitSet-based acceptance condition\n\t * @param ddRowVars JDDVars of the row variables corresponding to the bits in the bit set\n\t */\n\tpublic AcceptanceRabinDD(AcceptanceRabin acceptance, JDDVars ddRowVars)\n\t{\n\t\tfor (AcceptanceRabin.RabinPair pair : acceptance) {\n\t\t\t// get BDD based newL and newK from the bit sets\n\t\t\tJDDNode newL = JDD.Constant(0);\n\t\t\tfor (int i : IterableBitSet.getSetBits(pair.getL())) {\n\t\t\t\tnewL = JDD.SetVectorElement(newL, ddRowVars, i, 1.0);\n\t\t\t}\n\n\t\t\tJDDNode newK = JDD.Constant(0);\n\t\t\tfor (int i : IterableBitSet.getSetBits(pair.getK())) {\n\t\t\t\tnewK = JDD.SetVectorElement(newK, ddRowVars, i, 1.0);\n\t\t\t}\n\n\t\t\tRabinPairDD newPair = new RabinPairDD(newL, newK);\n\t\t\tthis.add(newPair);\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean isBSCCAccepting(JDDNode bscc_states)\n\t{\n\t\tfor (RabinPairDD pair : this) {\n\t\t\tif (pair.isBSCCAccepting(bscc_states)) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic AcceptanceRabinDD clone()\n\t{\n\t\tAcceptanceRabinDD result = new AcceptanceRabinDD();\n\t\tfor (RabinPairDD pair : this) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic void intersect(JDDNode restrict)\n\t{\n\t\tfor (RabinPairDD pair : this) {\n\t\t\tpair.intersect(restrict);\n\t\t}\n\t}\n\n\t/**\n\t * Get the Streett acceptance condition that is the dual of this Rabin acceptance condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Streett condition.\n\t * <br>\n\t * Deprecated, use complementToStreett() or complement(...)\n\t * @return the complement Streett acceptance condition\n\t */\n\t@Deprecated\n\tpublic AcceptanceStreettDD complement()\n\t{\n\t\treturn complementToStreett();\n\t}\n\n\t/**\n\t * Returns a new Rabin acceptance condition that corresponds to the disjunction\n\t * of this and the other Rabin acceptance condition. The RabinPairs are cloned, i.e.,\n\t * not shared with the argument acceptance condition.\n\t * @param other the other Rabin acceptance condition\n\t * @return new AcceptanceRabin, disjunction of this and other\n\t */\n\tpublic AcceptanceRabinDD or(AcceptanceRabinDD other)\n\t{\n\t\tAcceptanceRabinDD result = new AcceptanceRabinDD();\n\t\tfor (RabinPairDD pair : this) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\t\tfor (RabinPairDD pair : other) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tfor (RabinPairDD pair : this) {\n\t\t\tpair.clear();\n\t\t}\n\t\tsuper.clear();\n\t}\n\n\t/** Returns a textual representation of this acceptance condition. */\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString result = \"\";\n\t\tfor (RabinPairDD pair : this) {\n\t\t\tresult += pair.toString();\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn size() + \" Rabin pairs\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.RABIN;\n\t}\n\n\t@Override\n\tpublic AcceptanceOmegaDD complement(AcceptanceType... allowedAcceptance) throws PrismNotSupportedException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.STREETT)) {\n\t\t\treturn complementToStreett();\n\t\t}\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\t/**\n\t * Get the Streett acceptance condition that is the dual of this Rabin acceptance condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Streett condition.\n\t * @return the complement Streett acceptance condition\n\t */\n\tpublic AcceptanceStreettDD complementToStreett()\n\t{\n\t\tAcceptanceStreettDD accStreett = new AcceptanceStreettDD();\n\n\t\tfor (RabinPairDD accPairRabin : this) {\n\t\t\tJDDNode R = accPairRabin.getK();\n\t\t\tJDDNode G = accPairRabin.getL();\n\t\t\tAcceptanceStreettDD.StreettPairDD accPairStreett = new AcceptanceStreettDD.StreettPairDD(R, G);\n\t\t\taccStreett.add(accPairStreett);\n\t\t}\n\n\t\treturn accStreett;\n\t}\n\n\t@Override\n\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n\t{\n\t\tif (size() == 0) {\n\t\t\treturn new AcceptanceGenericDD(false);\n\t\t}\n\t\tAcceptanceGenericDD genericPairs = null;\n\t\tfor (RabinPairDD pair : this) {\n\t\t\tAcceptanceGenericDD genericPair = pair.toAcceptanceGeneric();\n\t\t\tif (genericPairs == null) {\n\t\t\t\tgenericPairs = genericPair;\n\t\t\t} else {\n\t\t\t\tgenericPairs = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.OR, genericPairs, genericPair);\n\t\t\t}\n\t\t}\n\t\treturn genericPairs;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceReach.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.io.PrintStream;\nimport java.util.BitSet;\n\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport jdd.JDDVars;\n\n/**\n * A reachability acceptance condition (based on BitSet state sets).\n * The acceptance is defined via a set of goal states and\n * has to be \"upward-closed\", i.e., once a goal state has been reached,\n * all successor states are goal states as well.\n */\npublic class AcceptanceReach implements AcceptanceOmega\n{\n\t/** The set of goal states */\n\tprivate BitSet goalStates = new BitSet();\n\n\t/** Constructor (no goal states) */\n\tpublic AcceptanceReach()\n\t{\n\t}\n\n\t/** Constructor (set goal states) */\n\tpublic AcceptanceReach(BitSet goalStates)\n\t{\n\t\tthis.goalStates = goalStates;\n\t}\n\n\t/** Get the goal state set */\n\tpublic BitSet getGoalStates()\n\t{\n\t\treturn goalStates;\n\t}\n\n\t/** Set the goal state set */\n\tpublic void setGoalStates(BitSet goalStates)\n\t{\n\t\tthis.goalStates = goalStates;\n\t}\n\n\t/** Make a copy of the acceptance condition. */\n\tpublic AcceptanceReach clone()\n\t{\n\t\treturn new AcceptanceReach((BitSet)goalStates.clone());\n\t}\n\t\n\t@Override\n\tpublic boolean isBSCCAccepting(BitSet bscc_states)\n\t{\n\t\treturn bscc_states.intersects(goalStates);\n\t}\n\n\t/**\n\t * Get a Rabin acceptance condition that is the complement of this condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Rabin condition.\n\t * <br>\n\t * Relies on the fact that once the goal states have been reached, all subsequent states\n\t * are goal states.\n\t *\n\t * @param numStates the number of states in the underlying model / automaton (needed for complementing BitSets)\n\t * @return the complement Rabin acceptance condition\n\t */\n\tpublic AcceptanceRabin complementToRabin(int numStates)\n\t{\n\t\tAcceptanceRabin rabin = new AcceptanceRabin();\n\t\tBitSet allStates = new BitSet();\n\t\tallStates.set(0, numStates);\n\t\trabin.add(new AcceptanceRabin.RabinPair((BitSet) goalStates.clone(), allStates));\n\t\treturn rabin;\n\t}\n\n\t/**\n\t * Get a Streett acceptance condition that is the complement of this condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Streett condition.\n\t * <br>\n\t * Relies on the fact that once the goal states have been reached, all subsequent states\n\t * are goal states.\n\t *\n\t * @param numStates the number of states in the underlying model / automaton (needed for complementing BitSets)\n\t * @return the complement Streett acceptance condition\n\t */\n\tpublic AcceptanceStreett complementToStreett(int numStates)\n\t{\n\t\tAcceptanceStreett streett = new AcceptanceStreett();\n\t\tstreett.add(new AcceptanceStreett.StreettPair((BitSet) goalStates.clone(), new BitSet()));\n\t\treturn streett;\n\t}\n\n\t/** Complement this acceptance condition, return as AcceptanceGeneric. */\n\tpublic AcceptanceGeneric complementToGeneric()\n\t{\n\t\treturn toAcceptanceGeneric().complementToGeneric();\n\t}\n\n\t@Override\n\tpublic AcceptanceOmega complement(int numStates, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.RABIN)) {\n\t\t\treturn complementToRabin(numStates);\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.STREETT)) {\n\t\t\treturn complementToStreett(numStates);\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\t@Override\n\tpublic void lift(LiftBitSet lifter)\n\t{\n\t\tgoalStates=lifter.lift(goalStates);\n\t}\n\n\t@Override\n\tpublic AcceptanceReachDD toAcceptanceDD(JDDVars ddRowVars)\n\t{\n\t\treturn new AcceptanceReachDD(this, ddRowVars);\n\t}\n\n\t@Override\n\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t{\n\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.INF, (BitSet) goalStates.clone());\n\t}\n\n\t@Override\n\tpublic String getSignatureForState(int i)\n\t{\n\t\treturn goalStates.get(i) ? \"!\" : \" \";\n\t}\n\t\n\t@Override\n\tpublic String getSignatureForStateHOA(int stateIndex)\n\t{\n\t\tif (goalStates.get(stateIndex)) {\n\t\t\treturn \"{0}\";\n\t\t} else {\n\t\t\treturn \"\";\n\t\t}\n\t}\n\n\t/** Returns a textual representation of this acceptance condition. */\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn goalStates.toString();\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn goalStates.cardinality()+\" goal states\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.REACH;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic void outputHOAHeader(PrintStream out)\n\t{\n\t\tout.println(\"acc-name: Buchi\");\n\t\tout.println(\"Acceptance: 1 Inf(0)\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceReachDD.java",
    "content": "//==============================================================================\n//\n//Copyright (c) 2014-\n//Authors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//This file is part of PRISM.\n//\n//PRISM is free software; you can redistribute it and/or modify\n//it under the terms of the GNU General Public License as published by\n//the Free Software Foundation; either version 2 of the License, or\n//(at your option) any later version.\n//\n//PRISM is distributed in the hope that it will be useful,\n//but WITHOUT ANY WARRANTY; without even the implied warranty of\n//MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//GNU General Public License for more details.\n//\n//You should have received a copy of the GNU General Public License\n//along with PRISM; if not, write to the Free Software Foundation,\n//Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage acceptance;\n\nimport common.IterableBitSet;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismNotSupportedException;\n\n/**\n * A reachability acceptance condition (based on JDD state sets).\n * The acceptance is defined via a set of goal states and\n * has to be \"upward-closed\", i.e., once a goal state has been reached,\n * all successor states are goal states as well.\n */\npublic class AcceptanceReachDD implements AcceptanceOmegaDD\n{\n\t/** The goal states */\n\tprivate JDDNode goalStates;\n\n\t/**\n\t * Constructor, set goalStates.\n\t * Becomes owner of the references of goalStates.\n\t */\n\tpublic AcceptanceReachDD(JDDNode goalStates)\n\t{\n\t\tthis.goalStates = goalStates;\n\t}\n\t\n\t/**\n\t * Constructor, from a BitSet-based AcceptanceReach.\n\t *\n\t * @param acceptance the BitSet-based acceptance condition\n\t * @param ddRowVars JDDVars of the row variables corresponding to the bits in the bit set\n\t */\n\tpublic AcceptanceReachDD(AcceptanceReach acceptance, JDDVars ddRowVars)\n\t{\n\t\tgoalStates = JDD.Constant(0);\n\t\t// get BDD based on the goalState bit set\n\t\tfor (int i : IterableBitSet.getSetBits(acceptance.getGoalStates())) {\n\t\t\tgoalStates = JDD.SetVectorElement(goalStates, ddRowVars, i, 1.0);\n\t\t}\n\t}\n\n\t/** Get a referenced copy of the state set of the goal states.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getGoalStates()\n\t{\n\t\tJDD.Ref(goalStates);\n\t\treturn goalStates;\n\t}\n\n\t/**\n\t * Set the goal states.\n\t * Becomes owner of the reference to goalStates.\n\t */\n\tpublic void setGoalStates(JDDNode goalStates)\n\t{\n\t\tclear();\n\t\tthis.goalStates = goalStates;\n\t}\n\n\t@Override\n\tpublic boolean isBSCCAccepting(JDDNode bscc_states)\n\t{\n\t\treturn JDD.AreIntersecting(goalStates, bscc_states);\n\t}\n\n\t@Override\n\tpublic AcceptanceReachDD clone()\n\t{\n\t\treturn new AcceptanceReachDD(goalStates.copy());\n\t}\n\n\t@Override\n\tpublic void intersect(JDDNode restrict)\n\t{\n\t\tgoalStates = JDD.And(goalStates, restrict.copy());\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn \"one set of goal states\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.REACH;\n\t}\n\n\t@Override\n\tpublic AcceptanceOmegaDD complement(AcceptanceType... allowedAcceptance) throws PrismNotSupportedException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.RABIN)) {\n\t\t\treturn complementToRabin();\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.STREETT)) {\n\t\t\treturn complementToStreett();\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\t/**\n\t * Get a Rabin acceptance condition that is the complement of this condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Rabin condition.\n\t * <br>\n\t * Relies on the fact that once the goal states have been reached, all subsequent states\n\t * are goal states.\n\t *\n\t * @return the complement Rabin acceptance condition\n\t */\n\tpublic AcceptanceRabinDD complementToRabin()\n\t{\n\t\tAcceptanceRabinDD rabin = new AcceptanceRabinDD();\n\t\trabin.add(new AcceptanceRabinDD.RabinPairDD(goalStates.copy(), JDD.Constant(1)));\n\t\treturn rabin;\n\t}\n\n\t/**\n\t * Get a Streett acceptance condition that is the complement of this condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Streett condition.\n\t * <br>\n\t * Relies on the fact that once the goal states have been reached, all subsequent states\n\t * are goal states.\n\t *\n\t * @return the complement Streett acceptance condition\n\t */\n\tpublic AcceptanceStreettDD complementToStreett()\n\t{\n\t\tAcceptanceStreettDD streett = new AcceptanceStreettDD();\n\t\tstreett.add(new AcceptanceStreettDD.StreettPairDD(goalStates.copy(), JDD.Constant(0)));\n\t\treturn streett;\n\t}\n\n\t@Override\n\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n\t{\n\t\treturn new AcceptanceGenericDD(AcceptanceGeneric.ElementType.INF, goalStates.copy());\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tif (goalStates != null) {\n\t\t\tJDD.Deref(goalStates);\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceStreett.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\n\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport jdd.JDDVars;\n\n/**\n * A Streett acceptance condition (based on BitSet state sets).\n * This is a list of StreettPairs, which can be manipulated with the usual List interface.\n * <br>\n * Semantics: Each Streett pair has a state set R and G and is accepting iff\n * visiting R infinitely often implies visiting G infinitely often:\n *   (G F \"R\") -> (G F \"G\").\n *\n * The Streett condition is accepting if all pairs are accepting.\n */\n@SuppressWarnings(\"serial\")\npublic class AcceptanceStreett\n       extends ArrayList<AcceptanceStreett.StreettPair>\n       implements AcceptanceOmega\n{\n\n\t/**\n\t * A pair in a Streett acceptance condition, i.e., with\n\t *  (G F \"R\") -> (G F \"G\")\n\t **/\n\tpublic static class StreettPair {\n\t\t/** State set R */\n\t\tprivate BitSet R;\n\n\t\t/** State set G */\n\t\tprivate BitSet G;\n\n\t\t/**\n\t\t * Constructor with R and G state sets.\n\t\t * \t (G F \"R\") -> (G F \"G\")\n\t\t */\n\t\tpublic StreettPair(BitSet R, BitSet G)\n\t\t{\n\t\t\tthis.R = R;\n\t\t\tthis.G = G;\n\t\t}\n\n\t\t/** Get the state set R */\n\t\tpublic BitSet getR()\n\t\t{\n\t\t\treturn R;\n\t\t}\n\n\t\t/** Get the state set G */\n\t\tpublic BitSet getG()\n\t\t{\n\t\t\treturn G;\n\t\t}\n\n\t\t/** Returns true if the bottom strongly connected component\n\t\t * given by bscc_states is accepting for this pair.\n\t\t */\n\t\tpublic boolean isBSCCAccepting(BitSet bscc_states)\n\t\t{\n\t\t\tif (R.intersects(bscc_states)) {\n\t\t\t\t// there is some state in bscc_states\n\t\t\t\t// that is in R, requiring that G is visited\n\t\t\t\t// as well:\n\t\t\t\tif (!G.intersects(bscc_states)) {\n\t\t\t\t\treturn false;\n\t\t\t\t} else {\n\t\t\t\t\t// G is visited as well\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\t// no R visited, no need to check for G\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\n\t\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t\t{\n\t\t\tAcceptanceGeneric genericR = new AcceptanceGeneric(AcceptanceGeneric.ElementType.FIN, (BitSet)R.clone());\n\t\t\tAcceptanceGeneric genericG = new AcceptanceGeneric(AcceptanceGeneric.ElementType.INF, (BitSet)G.clone());\n\t\t\t//      G F \"R\" -> G F \"G\"\n\t\t\t// <=>  ! G F \"R\"  | G F \"G\"\n\t\t\t// <=>  F G ! \"R\"  | G F \"G\"\n\t\t\t// <=>  Fin(R) | Inf(G)\n\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.OR, genericR, genericG);\n\t\t}\n\n\t\t/** Generate signature for this Streett pair and the given state.\n\t\t *  If the state is a member of R, returns \"-pairIndex\".\n\t\t *  If the state is a member of G, returns \"+pairIndex\".\n\t\t *  @param stateIndex the state index\n\t\t *  @param pairIndex the index of this Streeet pair\n\t\t **/\n\t\tpublic String getSignatureForState(int stateIndex, int pairIndex)\n\t\t{\n\t\t\tif (G.get(stateIndex)) {\n\t\t\t\treturn \"+\"+pairIndex;\n\t\t\t} else if (R.get(stateIndex)) {\n\t\t\t\treturn \"-\"+pairIndex;\n\t\t\t} else {\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic StreettPair clone()\n\t\t{\n\t\t\treturn new StreettPair((BitSet)R.clone(), (BitSet)G.clone());\n\t\t}\n\n\t\t/** Returns a textual representation of this Streett pair. */\n\t\t@Override\n\t\tpublic String toString() {\n\t\t\treturn \"(\" + R + \"->\" + G + \")\";\n\t\t}\n\t}\n\n\t/** Make a copy of the acceptance condition. */\n\tpublic AcceptanceStreett clone()\n\t{\n\t\tAcceptanceStreett result = new AcceptanceStreett();\n\t\tfor (StreettPair pair : this) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/** Returns true if the bottom strongly connected component\n\t * given by bscc_states is accepting for this Streett condition,\n\t * i.e., all pairs accept for bscc_states.\n\t */\n\t@Override\n\tpublic boolean isBSCCAccepting(BitSet bscc_states)\n\t{\n\t\tfor (StreettPair pair : this) {\n\t\t\tif (!pair.isBSCCAccepting(bscc_states)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\n\t@Override\n\tpublic void lift(LiftBitSet lifter) {\n\t\tfor (StreettPair pair : this) {\n\t\t\tpair.R = lifter.lift(pair.R);\n\t\t\tpair.G = lifter.lift(pair.G);\n\t\t}\n\t}\n\n\t/**\n\t * Get the Rabin acceptance condition that is the dual of this Streett acceptance condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Rabin condition.\n\t * @return the complement Rabin acceptance condition\n\t */\n\tpublic AcceptanceRabin complementToRabin()\n\t{\n\t\tAcceptanceRabin accRabin = new AcceptanceRabin();\n\n\t\tfor (StreettPair accPairStreett : this) {\n\t\t\tBitSet L = (BitSet) accPairStreett.getG().clone();\n\t\t\tBitSet K = (BitSet) accPairStreett.getR().clone();\n\t\t\tAcceptanceRabin.RabinPair accPairRabin = new AcceptanceRabin.RabinPair(L, K);\n\t\t\taccRabin.add(accPairRabin);\n\t\t}\n\t\treturn accRabin;\n\t}\n\n\t/** Complement this acceptance condition, return as AcceptanceGeneric. */\n\tpublic AcceptanceGeneric complementToGeneric()\n\t{\n\t\treturn toAcceptanceGeneric().complementToGeneric();\n\t}\n\n\t@Override\n\tpublic AcceptanceOmega complement(int numStates, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.RABIN)) {\n\t\t\treturn complementToRabin();\n\t\t}\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\n\t/**\n\t * Returns a new Streett acceptance condition that corresponds to the conjunction\n\t * of this and the other Streett acceptance condition. The StreettPairs are cloned, i.e.,\n\t * not shared with the argument acceptance condition.\n\t * @param other the other Streett acceptance condition\n\t * @return new AcceptanceStreett, conjunction of this and other\n\t */\n\tpublic AcceptanceStreett and(AcceptanceStreett other)\n\t{\n\t\tAcceptanceStreett result = new AcceptanceStreett();\n\t\tfor (StreettPair pair : this) {\n\t\t\tresult.add((StreettPair) pair.clone());\n\t\t}\n\t\tfor (StreettPair pair : other) {\n\t\t\tresult.add((StreettPair) pair.clone());\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic AcceptanceStreettDD toAcceptanceDD(JDDVars ddRowVars)\n\t{\n\t\treturn new AcceptanceStreettDD(this, ddRowVars);\n\t}\n\n\t@Override\n\tpublic AcceptanceGeneric toAcceptanceGeneric()\n\t{\n\t\tif (size() == 0) {\n\t\t\treturn new AcceptanceGeneric(true);\n\t\t}\n\t\tAcceptanceGeneric genericPairs = null;\n\t\tfor (StreettPair pair : this) {\n\t\t\tAcceptanceGeneric genericPair = pair.toAcceptanceGeneric();\n\t\t\tif (genericPairs == null) {\n\t\t\t\tgenericPairs = genericPair;\n\t\t\t} else {\n\t\t\t\tgenericPairs = new AcceptanceGeneric(AcceptanceGeneric.ElementType.AND, genericPairs, genericPair);\n\t\t\t}\n\t\t}\n\t\treturn genericPairs;\n\t}\n\n\t/**\n\t * Get the acceptance signature for state stateIndex.\n\t **/\n\tpublic String getSignatureForState(int stateIndex)\n\t{\n\t\tString result = \"\";\n\n\t\tfor (int pairIndex=0; pairIndex<size(); pairIndex++) {\n\t\t\tStreettPair pair = get(pairIndex);\n\t\t\tresult += pair.getSignatureForState(stateIndex,  pairIndex);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSignatureForStateHOA(int stateIndex)\n\t{\n\t\tString result = \"\";\n\n\t\tfor (int pairIndex=0; pairIndex<size(); pairIndex++) {\n\t\t\tStreettPair pair = get(pairIndex);\n\t\t\tif (pair.getR().get(stateIndex)) {\n\t\t\t\tresult += (result.isEmpty() ? \"\" : \" \") + pairIndex*2;\n\t\t\t}\n\t\t\tif (pair.getG().get(stateIndex)) {\n\t\t\t\tresult += (result.isEmpty() ? \"\" : \" \") + (pairIndex*2+1);\n\t\t\t}\n\t\t}\n\n\t\tif (!result.isEmpty())\n\t\t\tresult = \"{\"+result+\"}\";\n\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString result = \"\";\n\t\tfor (StreettPair pair : this) {\n\t\t\tresult += pair.toString();\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn size() + \" Streett pairs\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.STREETT;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n\n\t@Override\n\tpublic void outputHOAHeader(PrintStream out)\n\t{\n\t\tout.println(\"acc-name: Streett \"+size());\n\t\tout.print(\"Acceptance: \" + (size()*2)+\" \");\n\t\tif (size() == 0) {\n\t\t\tout.println(\"t\");\n\t\t\treturn;\n\t\t}\n\n\t\tfor (int pair = 0; pair < size(); pair++) {\n\t\t\tif (pair > 0) out.print(\" & \");\n\t\t\tout.print(\"( Fin(\" + (2*pair) + \") | Inf(\" + (2*pair+1) +\") )\");\n\t\t}\n\t\tout.println();\n\t}\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceStreettDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\nimport java.util.ArrayList;\n\nimport common.IterableBitSet;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismNotSupportedException;\n\n/**\n * A Streett acceptance condition (based on JDD state sets).\n * This is a list of StreettPairs, which can be manipulated with the usual List interface.\n * <br>\n * Semantics: Each Streett pair has a state set R and G and is accepting iff\n * visiting R infinitely often implies visiting G infinitely often:\n *   (G F \"R\") -> (G F \"G\").\n *\n * The Streett condition is accepting if all pairs are accepting.\n */\n@SuppressWarnings(\"serial\")\npublic class AcceptanceStreettDD\n       extends ArrayList<AcceptanceStreettDD.StreettPairDD>\n       implements AcceptanceOmegaDD\n{\n\n\t/**\n\t * A pair in a Streett acceptance condition, i.e., with\n\t *  (G F \"R\") -> (G F \"G\")\n\t **/\n\tpublic static class StreettPairDD {\n\t\t/** State set R */\n\t\tprivate JDDNode R;\n\t\t\n\t\t/** State set G */\n\t\tprivate JDDNode G;\n\n\t\t/**\n\t\t * Constructor with R and G state sets.\n\t\t * Becomes owner of the references of R and G.\n\t\t */\n\t\tpublic StreettPairDD(JDDNode R, JDDNode G)\n\t\t{\n\t\t\tthis.R = R;\n\t\t\tthis.G = G;\n\t\t}\n\n\t\t/** Clear resources of the state sets */\n\t\tpublic void clear()\n\t\t{\n\t\t\tif (R != null) JDD.Deref(R);\n\t\t\tif (G != null) JDD.Deref(G);\n\t\t}\n\n\t\t/** Get a referenced copy of the state set R.\n\t\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic JDDNode getR()\n\t\t{\n\t\t\treturn R.copy();\n\t\t}\n\n\t\t/** Get a referenced copy of the state set G.\n\t\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic JDDNode getG()\n\t\t{\n\t\t\treturn G.copy();\n\t\t}\n\n\t\tpublic StreettPairDD clone()\n\t\t{\n\t\t\treturn new StreettPairDD(getR(), getG());\n\t\t}\n\n\t\t/** Returns true if the bottom strongly connected component\n\t\t * given by bscc_states is accepting for this pair.\n\t\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic boolean isBSCCAccepting(JDDNode bscc_states)\n\t\t{\n\t\t\tif (JDD.AreIntersecting(R, bscc_states)) {\n\t\t\t\t// there is some state in bscc_states\n\t\t\t\t// that is in R, requiring that G is visited\n\t\t\t\t// as well:\n\t\t\t\tif (!JDD.AreIntersecting(G, bscc_states)) {\n\t\t\t\t\treturn false;\n\t\t\t\t} else {\n\t\t\t\t\t// G is visited as well\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\t// no R visited, no need to check for G\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\n\t\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n\t\t{\n\t\t    AcceptanceGenericDD genericR = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.FIN, getR());\n\t\t    AcceptanceGenericDD genericG = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.INF, getG());\n\t\t    //      G F \"R\" -> G F \"G\"\n\t\t    // <=>  ! G F \"R\"  | G F \"G\"\n\t\t    // <=>  F G ! \"R\"  | G F \"G\"\n\t\t    // <=>  Fin(R) | Inf(G)\n\t\t    return new AcceptanceGenericDD(AcceptanceGeneric.ElementType.OR, genericR, genericG);\n                }\n\n\t\t/**\n\t\t * Replaces the BDD functions for the acceptance sets\n\t\t * of this Streett pair with the intersection\n\t\t * of the current acceptance sets and the function {@code restrict}.\n\t\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic void intersect(JDDNode restrict)\n\t\t{\n\t\t\tR = JDD.And(R, restrict.copy());\n\t\t\tG = JDD.And(G, restrict.copy());\n\t\t}\n\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn \"(\" + R + \"->\" + G + \")\";\n\t\t}\n\t}\n\n\t/** Constructor, create empty condition */\n\tpublic AcceptanceStreettDD()\n\t{\n\t}\n\n\t/**\n\t * Constructor, from a BitSet-based AcceptanceStreett.\n\t *\n\t * @param acceptance the BitSet-based acceptance condition\n\t * @param ddRowVars JDDVars of the row variables corresponding to the bits in the bit set\n\t */\n\tpublic AcceptanceStreettDD(AcceptanceStreett acceptance, JDDVars ddRowVars)\n\t{\n\t\tfor (AcceptanceStreett.StreettPair pair : acceptance) {\n\t\t\t// get BDD based newR and newG from the bit sets\n\t\t\tJDDNode newR = JDD.Constant(0);\n\t\t\tfor (int i : IterableBitSet.getSetBits(pair.getR())) {\n\t\t\t\tnewR = JDD.SetVectorElement(newR, ddRowVars, i, 1.0);\n\t\t\t}\n\t\n\t\t\tJDDNode newG = JDD.Constant(0);\n\t\t\tfor (int i : IterableBitSet.getSetBits(pair.getG())) {\n\t\t\t\tnewG = JDD.SetVectorElement(newG, ddRowVars, i, 1.0);\n\t\t\t}\n\t\n\t\t\tStreettPairDD newPair = new StreettPairDD(newR, newG);\n\t\t\tthis.add(newPair);\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean isBSCCAccepting(JDDNode bscc_states)\n\t{\n\t\tfor (StreettPairDD pair : this) {\n\t\t\tif (!pair.isBSCCAccepting(bscc_states)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic AcceptanceStreettDD clone()\n\t{\n\t\tAcceptanceStreettDD result = new AcceptanceStreettDD();\n\t\tfor (StreettPairDD pair : this) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\t\treturn result;\n\t}\n\n\n\t@Override\n\tpublic void intersect(JDDNode restrict)\n\t{\n\t\tfor (StreettPairDD pair : this) {\n\t\t\tpair.intersect(restrict);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tfor (StreettPairDD pair : this) {\n\t\t\tpair.clear();\n\t\t}\n\t\tsuper.clear();\n\t}\n\n\t/**\n\t * Returns a new Streett acceptance condition that corresponds to the conjunction\n\t * of this and the other Streett acceptance condition. The StreettPairs are cloned, i.e.,\n\t * not shared with the argument acceptance condition.\n\t * @param other the other Streett acceptance condition\n\t * @return new AcceptanceStreett, conjunction of this and other\n\t */\n\tpublic AcceptanceStreettDD and(AcceptanceStreettDD other)\n\t{\n\t\tAcceptanceStreettDD result = new AcceptanceStreettDD();\n\t\tfor (StreettPairDD pair : this) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\t\tfor (StreettPairDD pair : other) {\n\t\t\tresult.add(pair.clone());\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Get the Rabin acceptance condition that is the dual of this Streett acceptance condition, i.e.,\n\t * any word that is accepted by this condition is rejected by the returned Rabin condition.\n\t * <br>\n\t * Deprecated, use complementToRabin or complement(...).\n\t * @return the complement Rabin acceptance condition\n\t */\n\t@Deprecated\n\tpublic AcceptanceRabinDD complement()\n\t{\n\t\treturn complementToRabin();\n\t}\n\n\t@Override\n\tpublic String toString() {\n\t\tString result = \"\";\n\t\tfor (StreettPairDD pair : this) {\n\t\t\tresult += pair.toString();\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic String getSizeStatistics()\n\t{\n\t\treturn size() + \" Streett pairs\";\n\t}\n\n\t@Override\n\tpublic AcceptanceType getType()\n\t{\n\t\treturn AcceptanceType.STREETT;\n\t}\n\n\t@Override\n\tpublic AcceptanceOmegaDD complement(AcceptanceType... allowedAcceptance) throws PrismNotSupportedException\n\t{\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.RABIN)) {\n\t\t\treturn complementToRabin();\n\t\t}\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\treturn complementToGeneric();\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Can not complement \" + getType() + \" acceptance to a supported acceptance type\");\n\t}\n\n\tpublic AcceptanceRabinDD complementToRabin()\n\t{\n\t\tAcceptanceRabinDD accRabin = new AcceptanceRabinDD();\n\n\t\tfor (StreettPairDD accPairStreett : this) {\n\t\t\tJDDNode L = accPairStreett.getG();\n\t\t\tJDDNode K = accPairStreett.getR();\n\t\t\tAcceptanceRabinDD.RabinPairDD accPairRabin = new AcceptanceRabinDD.RabinPairDD(L, K);\n\t\t\taccRabin.add(accPairRabin);\n\t\t}\n\t\treturn accRabin;\n\t}\n\n\t@Override\n\tpublic AcceptanceGenericDD toAcceptanceGeneric()\n\t{\n\t\tif (size() == 0) {\n\t\t\treturn new AcceptanceGenericDD(true);\n\t\t}\n\t\tAcceptanceGenericDD genericPairs = null;\n\t\tfor (StreettPairDD pair : this) {\n\t\t\tAcceptanceGenericDD genericPair = pair.toAcceptanceGeneric();\n\t\t\tif (genericPairs == null) {\n\t\t\t\tgenericPairs = genericPair;\n\t\t\t} else {\n\t\t\t\tgenericPairs = new AcceptanceGenericDD(AcceptanceGeneric.ElementType.AND, genericPairs, genericPair);\n\t\t\t}\n\t\t}\n\t\treturn genericPairs;\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeAbbreviated() {\n\t\treturn getType().getNameAbbreviated();\n\t}\n\n\t@Override\n\t@Deprecated\n\tpublic String getTypeName() {\n\t\treturn getType().getName();\n\t}\n}\n"
  },
  {
    "path": "prism/src/acceptance/AcceptanceType.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage acceptance;\n\n/**\n * An omega-regular acceptance type.\n */\npublic enum AcceptanceType {\n\t/** Büchi acceptance */\n\tBUCHI(\"Buchi\", \"B\"),\n\t/** Rabin acceptance */\n\tRABIN(\"Rabin\", \"R\"),\n\t/** Streett acceptance */\n \tSTREETT(\"Streett\", \"S\"),\n \t/** Finite acceptance (goal states) */\n \tREACH(\"Finite\", \"F\"),\n \t/** Generalized Rabin acceptance */\n\tGENERALIZED_RABIN(\"generalized-Rabin\", \"GR\"),\n\t/** Generic acceptance, i.e., a boolean formula over Inf and Fin as in HOA format */\n \tGENERIC(\"generic\", \"\");   // abbreviation for generic is empty, results in DA\n\n\t/** The long form name */\n\tprivate final String typeName;\n\t/** The abbreviated name */\n\tprivate final String typeNameAbbreviated;\n\n\tprivate AcceptanceType(String typeName, String typeNameAbbreviated)\n\t{\n\t\tthis.typeName = typeName;\n\t\tthis.typeNameAbbreviated = typeNameAbbreviated;\n\t}\n\n\t/** Returns the long form name for this acceptance type */\n\tpublic String getName()\n\t{\n\t\treturn typeName;\n\t}\n\n\t/** Returns the abbreviated form of the name for this acceptance type */\n\tpublic String getNameAbbreviated()\n\t{\n\t\treturn typeNameAbbreviated;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\t// the long form name\n\t\treturn getName();\n\t}\n\n\t/**\n\t * Check whether an array of AcceptanceTypes contains a specific element.\n\t * @param types the array of AcceptanceTypes\n\t * @param type the AcceptanceType that is tested for\n\t */\n\tpublic static boolean contains(AcceptanceType[] types, AcceptanceType type)\n\t{\n\t\tfor (AcceptanceType t: types) {\n\t\t\tif (t.equals(type))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** Return an array containing all the acceptance types */\n\tpublic static AcceptanceType[] allTypes()\n\t{\n\t\treturn values();\n\t}\n}\n"
  },
  {
    "path": "prism/src/authors.txt",
    "content": "aissim = aissim <Aistis.Simaitis@cs.ox.ac.uk>\najovanovic = ajovanovic <aleksandra.jovanovic@cs.ox.ac.uk>\napuggelli = apuggelli <puggelli@eecs.berkeley.edu>\narchitteneja = architteneja <archittaneja8@gmail.com>\nbbarbot = bbarbot <benoit.barbot@u-pec.fr>\nbruni = bruni <alessandro.bruni@gmail.com>\nbrunol = brunol <b.lacerda@cs.bham.ac.uk>\nchrisd = chrisd <dehnert@cs.rwth-aachen.de>\nclewil = clewil <clemens.wiltsche@gmail.com>\ncmu = cmu <c.mu@cs.bham.ac.uk>\ncopik = copik <mcopik@gmail.com>\ndraeger = draeger <Klaus.Draeger@cs.ox.ac.uk>\ndxp = Dave Parker <dave.x.parker@gmail.com>\nemhahn = Ernst Moritz Hahn <emhahn@cs.ox.ac.uk>\nfritsd = Frits Dannenberg <frits.dannenberg@cs.ox.ac.uk>\nganindu88 = ganindu88 <ganindu88@gmail.com>\ngsantos = gsantos <gabrielhrsantos@gmail.com>\ngxn = Gethin Norman <gethin.norman@glasgow.ac.uk>\nhongyang = hongyang <h.qu@sheffield.ac.uk>\njklein = Joachim Klein <klein@tcs.inf.tu-dresden.de>\nkostas = Kostas Chatzikokolakis <kostas@chatzi.org>\nkrause = Christian Krause <christian.krause@hpi.uni-potsdam.de>\nlukeh = Luke Herbert <herbert.luke@gmail.com>\nmceska = mceska <xceska@fi.muni.cz>\nmujma = Mateusz Ujma <mateusz.ujma@cs.ox.ac.uk>\nmxk = Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk>\nnishan = Nishan Kamaleson <nxk249@bham.ac.uk>\nsergiogiro = sergiogiro <sergio.giro.ar@gmail.com>\nvojta = Vojtech Forejt <forejtv@gmail.com>\n(no author) = Dave Parker <dave.x.parker@gmail.com>\n"
  },
  {
    "path": "prism/src/automata/DA.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Hongyang Qu <hongyang.qu@cs.ox.ac.uk> (University of Oxford)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* David Mueller <david.mueller@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage automata;\n\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APElementIterator;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismPrintStreamLog;\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceRabin;\n\n/**\n * Class to store a deterministic automata of some acceptance type Acceptance.\n * States are 0-indexed integers; class is parameterised by edge labels (Symbol).\n */\npublic class DA<Symbol, Acceptance extends AcceptanceOmega>\n{\n\t/** AP list */\n\tprivate List<String> apList;\n\t/** Size, i.e. number of states */\n\tprivate int size;\n\t/** Start state (index) */\n\tprivate int start;\n\t/** Edges of DRA */\n\tprivate List<List<Edge>> edges;\n\t/** The acceptance condition (as BitSets) */\n\tprivate Acceptance acceptance;\n\n\t/** Local class to represent DRA edge */\n\tclass Edge\n\t{\n\t\tprivate Symbol label;\n\t\tprivate int dest;\n\n\t\tpublic Edge(Symbol label, int dest)\n\t\t{\n\t\t\tthis.label = label;\n\t\t\tthis.dest = dest;\n\t\t}\n\t}\n\n\t/**\n\t * Construct a DRA with zero states, use addState to add states.\n\t */\n\tpublic DA()\n\t{\n\t\tthis(0);\n\t}\n\n\t/**\n\t * Construct a DRA of fixed size (i.e. fixed number of states).\n\t */\n\tpublic DA(int size)\n\t{\n\t\tapList = null;\n\t\tthis.size = size;\n\t\tthis.start = -1;\n\t\tedges = new ArrayList<List<Edge>>(size);\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tedges.add(new ArrayList<Edge>());\n\t\t}\n\t}\n\n\tpublic void setAcceptance(Acceptance acceptance)\n\t{\n\t\tthis.acceptance = acceptance;\n\t}\n\n\tpublic Acceptance getAcceptance() {\n\t\treturn acceptance;\n\t}\n\n\t// TODO: finish/tidy this\n\tpublic void setAPList(List<String> apList)\n\t{\n\t\tthis.apList = apList;\n\t}\n\n\tpublic List<String> getAPList()\n\t{\n\t\treturn apList;\n\t}\n\n\t// Mutators\n\n\t/**\n\t * Add a state.\n\t * @return index of the fresh state\n\t */\n\tpublic int addState()\n\t{\n\t\tedges.add(new ArrayList<Edge>());\n\t\tsize++;\n\t\treturn size-1;\n\t}\n\n\t/**\n\t * Set the start state (index)\n\t */\n\tpublic void setStartState(int start)\n\t{\n\t\tthis.start = start;\n\t}\n\n\t/**\n\t * Returns true if the automaton has an edge for {@code src} and {@label}.\n\t */\n\tpublic boolean hasEdge(int src, Symbol label)\n\t{\n\t\tfor (Edge edge : edges.get(src)) {\n\t\t\tif (edge.label.equals(label)) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Add an edge\n\t */\n\tpublic void addEdge(int src, Symbol label, int dest)\n\t{\n\t\tedges.get(src).add(new Edge(label, dest));\n\t}\n\n\t// Accessors\n\n\t/**\n\t * Get the size (number of states).\n\t */\n\tpublic int size()\n\t{\n\t\treturn size;\n\t}\n\n\t/**\n\t * Get the start state (index)\n\t */\n\tpublic int getStartState()\n\t{\n\t\treturn start;\n\t}\n\n\t/**\n\t * Get the number of edges from state i\n\t */\n\tpublic int getNumEdges(int i)\n\t{\n\t\treturn edges.get(i).size();\n\t}\n\n\t/**\n\t * Get the destination of edge j from state i\n\t */\n\tpublic int getEdgeDest(int i, int j)\n\t{\n\t\treturn edges.get(i).get(j).dest;\n\t}\n\n\t/**\n\t * Get the label of edge j from state i.\n\t */\n\tpublic Symbol getEdgeLabel(int i, int j)\n\t{\n\t\treturn edges.get(i).get(j).label;\n\t}\n\n\t/**\n\t * Get the destination of the edge from state i with label lab.\n\t * Returns -1 if no such edge is found.\n\t */\n\tpublic int getEdgeDestByLabel(int i, Symbol lab)\n\t{\n\t\tfor (Edge e : edges.get(i))\n\t\t\tif (e.label.equals(lab))\n\t\t\t\treturn e.dest;\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Print the automaton in Dot format to an output stream.\n\t */\n\tpublic void printDot(PrintStream out) throws PrismException\n\t{\n\t\tprintDot(new PrismPrintStreamLog(out));\n\t}\n\n\t/**\n\t * Print automaton in Dot format to a PrismLog\n\t */\n\tpublic void printDot(PrismLog out) throws PrismException\n\t{\n\t\tint i;\n\t\tout.println(\"digraph model {\");\n\t\tfor (i = 0; i < size; i++) {\n\t\t\tout.print(\"\t\" + i + \" [label=\\\"\" + i + \" [\");\n\t\t\tout.print(acceptance.getSignatureForState(i));\n\t\t\tout.print(\"]\\\", shape=\");\n\t\t\tif (i == start)\n\t\t\t\tout.println(\"doublecircle]\");\n\t\t\telse\n\t\t\t\tout.println(\"ellipse]\");\n\t\t}\n\t\tfor (i = 0; i < size; i++) {\n\t\t\tfor (Edge e : edges.get(i)) {\n\t\t\t\tout.println(\"\t\" + i + \" -> \" + e.dest + \" [label=\\\"\" + e.label + \"\\\"]\");\n\t\t\t}\n\t\t}\n\t\tout.println(\"}\");\n\t}\n\t\n\t/**\n\t * Print the DRA in ltl2dstar v2 format to the output stream.\n\t * @param out the output stream \n\t */\n\tpublic static void printLtl2dstar(DA<BitSet, AcceptanceRabin> dra, PrintStream out) throws PrismException {\n\t\tAcceptanceRabin acceptance = dra.getAcceptance();\n\n\t\tif (dra.getStartState() < 0) {\n\t\t\t// No start state! \n\t\t\tthrow new PrismException(\"No start state in DA!\");\n\t\t}\n\n\t\tout.println(\"DRA v2 explicit\");\n\t\tout.println(\"States: \" + dra.size());\n\t\tout.println(\"Acceptance-Pairs: \" + acceptance.size());\n\t\tout.println(\"Start: \" + dra.getStartState());\n\n\t\t// Enumerate APSet\n\t\tout.print(\"AP: \" + dra.getAPList().size());\n\t\tfor (String ap : dra.getAPList()) {\n\t\t\tout.print(\" \\\"\" + ap + \"\\\"\");\n\t\t}\n\t\tout.println();\n\n\t\tout.println(\"---\");\n\n\t\tfor (int i_state = 0; i_state < dra.size(); i_state++) {\n\t\t\tout.println(\"State: \" + i_state);\n\n\t\t\tout.print(\"Acc-Sig:\");\n\t\t\tfor (int pair = 0; pair < acceptance.size(); pair++) {\n\t\t\t\tif (acceptance.get(pair).getL().get(i_state)) {\n\t\t\t\t\tout.print(\" -\"+pair);\n\t\t\t\t} else if (acceptance.get(pair).getK().get(i_state)) {\n\t\t\t\t\tout.print(\" +\"+pair);\n\t\t\t\t}\n\t\t\t}\n\t\t\tout.println();\n\t\t\t\n\t\t\tAPElementIterator it = new APElementIterator(dra.apList.size());\n\t\t\twhile (it.hasNext()) {\n\t\t\t\tAPElement edge = it.next();\n\t\t\t\tout.println(dra.getEdgeDestByLabel(i_state, edge));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Print the DA in HOA format to the output stream.\n\t * @param out the output stream\n\t */\n\tpublic void printHOA(PrintStream out) throws PrismException {\n\t\tout.println(\"HOA: v1\");\n\t\tout.println(\"States: \"+size());\n\t\t\n\t\t// AP\n\t\tout.print(\"AP: \"+apList.size());\n\t\tfor (String ap : apList) {\n\t\t\t// TODO(JK): Proper quoting\n\t\t\tout.print(\" \\\"\"+ap+\"\\\"\");\n\t\t}\n\t\tout.println();\n\n\t\tout.println(\"Start: \"+start);\n\t\tacceptance.outputHOAHeader(out);\n\t\tout.println(\"properties: trans-labels explicit-labels state-acc no-univ-branch deterministic\");\n\t\tout.println(\"--BODY--\");\n\t\tfor (int i = 0; i < size(); i++) {\n\t\t\tout.print(\"State: \"+i+\" \");  // id\n\t\t\tout.println(acceptance.getSignatureForStateHOA(i));\n\n\t\t\tfor (Edge edge : edges.get(i)) {\n\t\t\t\tSymbol label = edge.label;\n\t\t\t\tif (!(label instanceof BitSet))\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Can not print automaton with \"+label.getClass()+\" labels\");\n\t\t\t\tString labelString = \"[\"+APElement.toStringHOA((BitSet)label, apList.size())+\"]\";\n\t\t\t\tout.print(labelString);\n\t\t\t\tout.print(\" \");\n\t\t\t\tout.println(edge.dest);\n\t\t\t}\n\t\t}\n\t\tout.println(\"--END--\");\n\t}\n\n\t/**\n\t * Print automaton to a PrismLog in a specified format (\"dot\" or \"txt\").\n\t */\n\tpublic void print(PrismLog out, String type) throws PrismException\n\t{\n\t\tswitch (type) {\n\t\tcase \"txt\":\n\t\t\tout.println(toString());\n\t\t\tbreak;\n\t\tcase \"dot\":\n\t\t\tprintDot(out);\n\t\t\tbreak;\n\t\t// Default to txt\n\t\tdefault:\n\t\t\tout.println(toString());\n\t\t\tbreak;\n\t\t}\n\t}\n\n\t/**\n\t * Print automaton to a PrintStream in a specified format (\"dot\", \"txt\" or \"hoa\").\n\t */\n\tpublic void print(PrintStream out, String type) throws PrismException\n\t{\n\t\tswitch (type) {\n\t\tcase \"txt\":\n\t\t\tout.println(toString());\n\t\t\tbreak;\n\t\tcase \"dot\":\n\t\t\tprintDot(out);\n\t\t\tbreak;\n\t\tcase \"hoa\":\n\t\t\tprintHOA(out);\n\t\t\tbreak;\n\t\t// Default to txt\n\t\tdefault:\n\t\t\tout.println(toString());\n\t\t\tbreak;\n\t\t}\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tint i;\n\t\ts += size + \" states (start \" + start + \")\";\n\t\tif (apList != null)\n\t\t\ts += \", \" + apList.size() + \" labels (\" + apList + \")\";\n\t\ts += \":\";\n\t\tfor (i = 0; i < size; i++) {\n\t\t\tfor (Edge e : edges.get(i)) {\n\t\t\t\ts += \" \" + i + \"-\" + e.label + \"->\" + e.dest;\n\t\t\t}\n\t\t}\n\t\ts += \"; \" + acceptance.getType() + \" acceptance: \";\n\t\ts += acceptance;\n\t\treturn s;\n\t}\n\n\tpublic String getAutomataType()\n\t{\n\t\treturn \"D\"+acceptance.getType().getNameAbbreviated()+\"A\";\n\t}\n\n\t/**\n\t * Switch the acceptance condition. This may change the acceptance type,\n\t * i.e., a DA&lt;BitSet, AcceptanceRabin&gt; may become a DA&lt;BitSet, AcceptanceStreett&gt;\n\t * @param da the automaton\n\t * @param newAcceptance the new acceptance condition\n\t */\n\t@SuppressWarnings({ \"rawtypes\", \"unchecked\" })\n\tpublic static void switchAcceptance(DA da, AcceptanceOmega newAcceptance)\n\t{\n\t\t// as Java generics are only compile time, we can change the AcceptanceType\n\t\tda.acceptance = newAcceptance;\n\t}\n\n\t/**\n\t * Validates that the atomic propositions of this automaton\n\t * conform to the standard values that PRISM expects:\n\t *   L0, ..., Ln-1 (in arbitrary order)\n\t * if there are {@code n} expected atomic propositions.\n\t * <br/>\n\t * The automaton may actually have less atomic propositions than expected,\n\t * e.g., if the given atomic proposition does not influence the acceptance\n\t * of a run in the automaton.\n\t * <br/>\n\t * If there is an error, throws a {@code PrismException} detailing the problem.\n\t * @param expectedNumberOfAPs the expected number of atomic propositions\n\t */\n\tpublic void checkForCanonicalAPs(int expectedNumberOfAPs) throws PrismException {\n\t\tBitSet seen = new BitSet();\n\t\tfor (String ap : apList) {\n\t\t\tif (!ap.substring(0,1).equals(\"L\")) {\n\t\t\t\tthrow new PrismException(\"In deterministic automaton, unexpected atomic proposition \"+ap+\", expected L0, L1, ...\");\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tint index = Integer.parseInt(ap.substring(1));\n\t\t\t\tif (seen.get(index)) {\n\t\t\t\t\tthrow new PrismException(\"In deterministic automaton, duplicate atomic proposition \"+ap);\n\t\t\t\t}\n\t\t\t\tif (index < 0) {\n\t\t\t\t\tthrow new PrismException(\"In deterministic automaton, unexpected atomic proposition \"+ap+\", expected L0, L1, ...\");\n\t\t\t\t}\n\t\t\t\tif (index >= expectedNumberOfAPs) {\n\t\t\t\t\tthrow new PrismException(\"In deterministic automaton, unexpected atomic proposition \"+ap+\", expected highest index to be \"+(expectedNumberOfAPs-1));\n\t\t\t\t}\n\t\t\t\tseen.set(index);\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"In deterministic automaton, unexpected atomic proposition \"+ap+\", expected L0, L1, ...\");\n\t\t\t}\n\t\t}\n\t\t// We are fine with an empty apList or an apList that lacks some of the expected Li.\n\t}\n}\n"
  },
  {
    "path": "prism/src/automata/DASimplifyAcceptance.java",
    "content": "package automata;\n\nimport java.util.BitSet;\n\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport explicit.LTS;\nimport explicit.SCCComputer;\nimport explicit.SCCConsumerStore;\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceType;\nimport acceptance.AcceptanceRabin.RabinPair;\n\npublic class DASimplifyAcceptance\n{\n\n\t/**\n\t * Tries to simplify the acceptance condition of the deterministic automaton.\n\t * Note that the passed parameter {@code da} may be destroyed by this function.\n\t * @param parent the calling PrismComponent (for SCC computer)\n\t * @param da the DA to be simplified (may be destroyed)\n\t * @param allowedAcceptance the allowed acceptance types\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic static DA<BitSet, ? extends AcceptanceOmega> simplifyAcceptance(PrismComponent parent, DA<BitSet, ? extends AcceptanceOmega> da, AcceptanceType... allowedAcceptance)\n\t\t\tthrows PrismException\n\t{\n\t\t// Simplifications for DRAs\n\t\tif (da.getAcceptance() instanceof AcceptanceRabin) {\n\t\t\tDA<BitSet, AcceptanceRabin> dra = (DA<BitSet, AcceptanceRabin>) da;\n\t\t\t// K_i states that do not occur in a (non-trivial) SCC of the DRA may as well be removed\n\t\t\tLTS lts = new LTSFromDA(da);\n\t\t\tSCCConsumerStore sccStore = new SCCConsumerStore();\n\t\t\tSCCComputer sccComp = explicit.SCCComputer.createSCCComputer(parent, lts, sccStore);\n\t\t\tsccComp.computeSCCs();\n\t\t\tBitSet trivial = sccStore.getNotInSCCs();\n\t\t\tfor (RabinPair pair : dra.getAcceptance()) {\n\t\t\t\tif (pair.getK().intersects(trivial)) {\n\t\t\t\t\tpair.getK().andNot(trivial);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// See if the DRA is actually a DFA\n\t\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.REACH) && isDFA(dra)) {\n\t\t\t\t// we can switch to AcceptanceReach\n\t\t\t\tAcceptanceReach reachAcceptance = new AcceptanceReach(getDFAGoalStatesForRabin(dra.getAcceptance()));\n\t\t\t\tDA.switchAcceptance(dra, reachAcceptance);\n\t\t\t\tda = dra;\n\t\t\t}\n\t\t}\n\t\treturn da;\n\t}\n\n\t/**\n\t * Is this Rabin automaton actually a finite automaton? This check is done syntactically:\n\t * it returns true if every transition from a K_i state goes to another K_i state.\n\t * We also require that there are no L_i states overlapping with any K_j states.\n\t */\n\tpublic static boolean isDFA(DA<BitSet, AcceptanceRabin> dra)\n\t{\n\t\tAcceptanceRabin acceptance = dra.getAcceptance();\n\t\t// Compute potential set of goal states as the union of all K_i sets\n\t\tBitSet goalStates = getDFAGoalStatesForRabin(acceptance);\n\n\t\t// Make sure there are no L_i states in the goal states for any i\n\t\tfor (int i = 0; i < acceptance.size(); i++) {\n\t\t\tif (goalStates.intersects(acceptance.get(i).getL()))\n\t\t\t\treturn false;\n\t\t}\n\t\t// Check if every transition from a goal state goes to another goal state\n\t\tfor (int i = goalStates.nextSetBit(0); i >= 0; i = goalStates.nextSetBit(i + 1)) {\n\t\t\tint m = dra.getNumEdges(i);\n\t\t\tfor (int j = 0; j < m; j++) {\n\t\t\t\tif (!goalStates.get(dra.getEdgeDest(i, j)))\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get the union of the K_i states of a Rabin acceptance condition.\n\t */\n\tpublic static BitSet getDFAGoalStatesForRabin(AcceptanceRabin acceptance)\n\t{\n\t\t// Compute set of goal states as the union of all K_i sets\n\t\tBitSet goalStates = new BitSet();\n\t\tint n = acceptance.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tgoalStates.or(acceptance.get(i).getK());\n\t\t}\n\t\treturn goalStates;\n\t}\n}\n"
  },
  {
    "path": "prism/src/automata/HOAF2DA.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* David Mueller <david.mueller@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage automata;\n\nimport java.io.FileInputStream;\nimport java.io.InputStream;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Set;\n\nimport prism.PrismException;\nimport jhoafparser.ast.AtomAcceptance;\nimport jhoafparser.ast.AtomLabel;\nimport jhoafparser.ast.BooleanExpression;\nimport jhoafparser.consumer.HOAConsumer;\nimport jhoafparser.consumer.HOAConsumerException;\nimport jhoafparser.consumer.HOAIntermediateStoreAndManipulate;\nimport jhoafparser.parser.HOAFParser;\nimport jhoafparser.transformations.ToStateAcceptance;\nimport jhoafparser.util.ImplicitEdgeHelper;\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport jltl2dstar.APMonom;\nimport jltl2dstar.APMonom2APElements;\nimport acceptance.AcceptanceBuchi;\nimport acceptance.AcceptanceGenRabin;\nimport acceptance.AcceptanceGenRabin.GenRabinPair;\nimport acceptance.AcceptanceGeneric;\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceRabin.RabinPair;\nimport acceptance.AcceptanceStreett;\nimport acceptance.AcceptanceStreett.StreettPair;\n\n/**\n * A HOAConsumer for jhoafparser that constructs a prism.DA from the parsed automaton.\n * <br>\n * The automaton has to be deterministic and complete, with state-based acceptance and\n * labels (explicit/implicit) on the edges.\n * <br>\n * If the automaton has transition-based acceptance, {@code TransitionBasedAcceptanceException}\n * is thrown.\n * <br>\n * There are (currently) more restrictions on the automaton:\n * <ul>\n * <li>The Start and States headers have to be present</li>\n * <li>At least one state in the automaton.\n * <li>All explicit edge labels have to be in disjunctive normal form (disjunction of conjunctive clauses)</li>\n * <li>At most 30 atomic propositions</li>\n * </ul>\n */\npublic class HOAF2DA implements HOAConsumer {\n\n\n\t/** An exception that is thrown to indicate that the automaton had transition based acceptance. */\n\t@SuppressWarnings(\"serial\")\n\tpublic class TransitionBasedAcceptanceException extends HOAConsumerException {\n\t\tpublic TransitionBasedAcceptanceException(String e) {super(e);}\n\t}\n\n\t/** The resulting deterministic automaton */\n\tprivate DA<BitSet, ? extends AcceptanceOmega> da;\n\t/** The set of atomic propositions of the automaton (in APSet form) */\n\tprivate APSet aps = new APSet();\n\n\t/** Size, i.e. number of states */\n\tprivate int size;\n\t/** Do we know the number of states? Is provided by the optional HOA States-header */\n\tprivate boolean knowSize = false;\n\n\t/** Start state (index) */\n\tprivate int startState;\n\t/** Do we know the start state? Is provided by the HOA Start-header */\n\tprivate boolean knowStartState = false;\n\n\t/** The acceptance condition */\n\tprivate BooleanExpression<AtomAcceptance> accExpr = null;\n\t/** The condition name from the acc-name header (optional) */\n\tprivate String accName;\n\t/** The extra information from the acc-name header (optional) */\n\tprivate List<Object> extraInfo;\n\n\t/** For each acceptance set in the HOA automaton, the set of states that are included in that set */\n\tprivate List<BitSet> acceptanceSets = null;\n\t/** The set of acceptance set indizes where state membership has to be inverted */\n\tprivate Set<Integer> negateAcceptanceSetMembership = null;\n\t/** The list of atomic propositions (in List form) */\n\tprivate List<String> apList;\n\n\t/** The helper for handling implicit edges */\n\tprivate ImplicitEdgeHelper implicitEdgeHelper = null;\n\n\t/**\n\t * The expected number of edges per state. As the automaton has to be complete,\n\t * this is 2^|AP|.\n\t */\n\tprivate long expectedNumberOfEdgesPerState;\n\n\t/**\n\t * If we do not know the number of states beforehand (knowSize = false),\n\t * we track here if we have seen a state definition for all states. True for index i if\n\t * state i had no definition yet.\n\t */\n\tprivate BitSet statesWithoutDefinition = null;\n\n\n\t/** In the knowSize=false case, ensure that all states (including with index id) exist */\n\tprivate void ensureStateExists(int id) {\n\t\t// generate as many intermediate states as required so that state with id exists\n\t\twhile (id >= da.size()) {\n\t\t\tint i = da.addState();\n\t\t\t// remember that we don't have a definition yet\n\t\t\tstatesWithoutDefinition.set(i);\n\t\t}\n\t}\n\n\t/** Clear the various state information */\n\tpublic void clear() {\n\t\taps = new APSet();\n\n\t\timplicitEdgeHelper = null;\n\n\t\tsize = 0;\n\t\tknowSize = false;\n\n\t\tstartState = 0;\n\t\tknowStartState = false;\n\n\t\taccExpr = null;\n\t\taccName = null;\n\t\textraInfo = null;\n\n\t\tacceptanceSets = null;\n\t\tnegateAcceptanceSetMembership = null;\n\t\tapList = null;\n\n\t\tstatesWithoutDefinition = null;\n\t}\n\n\t/** Constructor */\n\tpublic HOAF2DA() {\n\t}\n\n\t@Override\n\tpublic boolean parserResolvesAliases() {\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic void notifyHeaderStart(String version) throws HOAConsumerException {\n\t\t// NOP\n\t}\n\n\t@Override\n\tpublic void setNumberOfStates(int numberOfStates)\n\t\t\tthrows HOAConsumerException {\n\t\tsize = numberOfStates;\n\t\tknowSize = true;\n\t\tif (numberOfStates == 0) {\n\t\t\tthrow new HOAConsumerException(\"Automaton with zero states, need at least one state\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void addStartStates(List<Integer> stateConjunction)\n\t\t\tthrows HOAConsumerException {\n\t\tif(stateConjunction.size() > 1 || knowStartState) {\n\t\t\tthrow new HOAConsumerException(\"Not a deterministic automaton: More then one Start state\");\n\t\t}\n\t\tstartState = stateConjunction.get(0).intValue();\n\t\tknowStartState = true;\n\t}\n\n\t@Override\n\tpublic void addAlias(String name, BooleanExpression<AtomLabel> labelExpr)\n\t\t\tthrows HOAConsumerException {\n\t\t// NOP, aliases are already resolved\n\t}\n\n\t@Override\n\tpublic void setAPs(List<String> aps) throws HOAConsumerException {\n\t\tif (aps.size() > 30) {\n\t\t\tthrow new HOAConsumerException(\"Automaton has \"+aps.size()+\" atomic propositions, at most 30 are supported\");\n\t\t}\n\n\t\tapList = aps;\n\t\texpectedNumberOfEdgesPerState = 1L << apList.size();\n\n\t\tfor (String ap : aps) {\n\t\t\tthis.aps.addAP(ap);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void setAcceptanceCondition(int numberOfSets,\n\t\t\tBooleanExpression<AtomAcceptance> accExpr)\n\t\t\tthrows HOAConsumerException {\n\t\tthis.accExpr = accExpr;\n\t}\n\n\t@Override\n\tpublic void provideAcceptanceName(String name, List<Object> extraInfo)\n\t\t\tthrows HOAConsumerException {\n\t\taccName = name;\n\t\tthis.extraInfo = extraInfo;\n\t}\n\n\t@Override\n\tpublic void setName(String name) throws HOAConsumerException {\n\t\t// NOP\n\t}\n\n\t@Override\n\tpublic void setTool(String name, String version) throws HOAConsumerException {\n\t\t// NOP\n\t}\n\n\t@Override\n\tpublic void addProperties(List<String> properties)\n\t\t\tthrows HOAConsumerException {\n\t\tif(!properties.contains(\"deterministic\")) {\n\t\t\t// we don't know yet whether the automaton is actually deterministic...\n\t\t}\n\t\tif(properties.contains(\"univ-branch\")) {\n\t\t\tthrow new HOAConsumerException(\"A HOAF with universal branching is not deterministic\");\n\t\t}\n\t\t\n\t\tif(properties.contains(\"state-labels\")) {\n\t\t\tthrow new HOAConsumerException(\"Can't handle state labelling\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void addMiscHeader(String name, List<Object> content)\n\t\t\tthrows HOAConsumerException {\n\t\tif (name.substring(0,1).toUpperCase().equals(name.substring(0,1))) {\n\t\t\tthrow new HOAConsumerException(\"Unknown header \"+name+\" potentially containing semantic information, can not handle\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void notifyBodyStart() throws HOAConsumerException {\n\t\tif (!knowStartState) {\n\t\t\tthrow new HOAConsumerException(\"Not a deterministic automaton: No initial state specified (Start header)\");\n\t\t}\n\t\tif (knowSize && startState >= size) {\n\t\t\tthrow new HOAConsumerException(\"Initial state \"+startState+\" is out of range\");\n\t\t}\n\n\t\tif (knowSize) {\n\t\t\tda = new DA<BitSet,AcceptanceGeneric>(size);\n\t\t\tda.setStartState(startState);\n\t\t} else {\n\t\t\t// init with empty DA\n\t\t\tda = new DA<BitSet,AcceptanceGeneric>();\n\t\t\t// and prepare the bitset used to track whether we had definitions for all states or not\n\t\t\tstatesWithoutDefinition = new BitSet();\n\n\t\t\t// ensure that all states in the DA up to the startState index are allocated\n\t\t\t// and then set the start state\n\t\t\tensureStateExists(startState);\n\t\t\tda.setStartState(startState);\n\t\t}\n\n\t\tif (apList == null) {\n\t\t\t// no call to setAPs\n\t\t\tapList = new ArrayList<String>(0);\n\t\t}\n\t\tda.setAPList(apList);\n\t\timplicitEdgeHelper = new ImplicitEdgeHelper(apList.size());\n\n\t\tDA.switchAcceptance(da, prepareAcceptance());\n\t}\n\n\t/**\n\t * Prepare an acceptance condition for the parsed automaton.\n\t * Called in notifyBodyStart()\n\t **/\n\tprivate AcceptanceOmega prepareAcceptance() throws HOAConsumerException\n\t{\n\t\tif (accName != null) {\n\t\t\tif (accName.equals(\"Rabin\")) {\n\t\t\t\treturn prepareAcceptanceRabin();\n\t\t\t} else if (accName.equals(\"generalized-Rabin\")) {\n\t\t\t\treturn prepareAcceptanceGenRabin();\n\t\t\t} else if (accName.equals(\"Streett\")) {\n\t\t\t\treturn prepareAcceptanceStreett();\n\t\t\t} else if (accName.equals(\"Buchi\")) {\n\t\t\t\treturn prepareAcceptanceBuchi();\n\t\t\t}\n\t\t}\n\n\t\tacceptanceSets = new ArrayList<BitSet>();\n\t\treturn prepareAcceptanceGeneric(accExpr);\n\t}\n\n\t/**\n\t * Prepare a generic acceptance condition for the parsed automaton.\n\t **/\n\tprivate AcceptanceGeneric prepareAcceptanceGeneric(BooleanExpression<AtomAcceptance> expr) throws HOAConsumerException\n\t{\n\t\tswitch (expr.getType()) {\n\t\tcase EXP_TRUE:\n\t\t\treturn new AcceptanceGeneric(true);\n\t\tcase EXP_FALSE:\n\t\t\treturn new AcceptanceGeneric(false);\n\t\tcase EXP_AND:\n\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.AND,\n                    prepareAcceptanceGeneric(expr.getLeft()),\n                    prepareAcceptanceGeneric(expr.getRight()));\n\t\tcase EXP_OR:\n\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.OR,\n                    prepareAcceptanceGeneric(expr.getLeft()),\n                    prepareAcceptanceGeneric(expr.getRight()));\n\t\tcase EXP_NOT:\n\t\t\tthrow new HOAConsumerException(\"Boolean negation not allowed in acceptance expression\");\n\t\tcase EXP_ATOM: {\n\t\t\tint index = expr.getAtom().getAcceptanceSet();\n\t\t\twhile (index >= acceptanceSets.size()) {\n\t\t\t\t// ensure that the acceptanceSets array is large enough\n\t\t\t\tacceptanceSets.add(null);\n\t\t\t}\n\t\t\tif (acceptanceSets.get(index) == null) {\n\t\t\t\t// this acceptance set index has not been seen yet, create BitSet\n\t\t\t\tacceptanceSets.set(index, new BitSet());\n\t\t\t}\n\t\t\tBitSet acceptanceSet = acceptanceSets.get(index);\n\t\t\tswitch (expr.getAtom().getType()) {\n\t\t\tcase TEMPORAL_FIN:\n\t\t\t\tif (expr.getAtom().isNegated()) {\n\t\t\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.FIN_NOT, acceptanceSet);\n\t\t\t\t} else {\n\t\t\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.FIN, acceptanceSet);\n\t\t\t\t}\n\t\t\tcase TEMPORAL_INF:\n\t\t\t\tif (expr.getAtom().isNegated()) {\n\t\t\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.INF_NOT, acceptanceSet);\n\t\t\t\t} else {\n\t\t\t\t\treturn new AcceptanceGeneric(AcceptanceGeneric.ElementType.INF, acceptanceSet);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t}\n\n\t\tthrow new UnsupportedOperationException(\"Unknown operator in acceptance condition: \"+expr);\n\t}\n\n\t/**\n\t * Prepare a Buchi acceptance condition from the acc-name header.\n\t */\n\tprivate AcceptanceBuchi prepareAcceptanceBuchi() throws HOAConsumerException\n\t{\n\t\tif (extraInfo.size() != 0) {\n\t\t\tthrow new HOAConsumerException(\"Invalid acc-name: Buchi header\");\n\t\t}\n\n\t\tacceptanceSets = new ArrayList<BitSet>(1);\n\t\tBitSet acceptingStates = new BitSet();\n\t\tAcceptanceBuchi acceptanceBuchi = new AcceptanceBuchi(acceptingStates);\n\t\tacceptanceSets.add(acceptingStates);  // Inf(0)\n\n\t\treturn acceptanceBuchi;\n\t}\n\n\t/**\n\t * Prepare a Rabin acceptance condition from the acc-name header.\n\t */\n\tprivate AcceptanceRabin prepareAcceptanceRabin() throws HOAConsumerException\n\t{\n\t\tif (extraInfo.size() != 1 ||\n\t\t    !(extraInfo.get(0) instanceof Integer)) {\n\t\t\tthrow new HOAConsumerException(\"Invalid acc-name: Rabin header\");\n\t\t}\n\n\t\tint numberOfPairs = (Integer)extraInfo.get(0);\n\t\tAcceptanceRabin acceptanceRabin = new AcceptanceRabin();\n\t\tacceptanceSets = new ArrayList<BitSet>(numberOfPairs*2);\n\t\tfor (int i = 0; i< numberOfPairs; i++) {\n\t\t\tBitSet L = new BitSet();\n\t\t\tBitSet K = new BitSet();\n\n\t\t\tacceptanceSets.add(L);   // 2*i   = Fin(L) = F G !L\n\t\t\tacceptanceSets.add(K);   // 2*i+1 = Inf(K) = G F  K\n\n\t\t\tacceptanceRabin.add(new RabinPair(L,K));\n\t\t}\n\n\t\treturn acceptanceRabin;\n\t}\n\n\t/**\n\t * Prepare a Streett acceptance condition from the acc-name header.\n\t */\n\tprivate AcceptanceStreett prepareAcceptanceStreett() throws HOAConsumerException\n\t{\n\t\tif (extraInfo.size() != 1 ||\n\t\t    !(extraInfo.get(0) instanceof Integer)) {\n\t\t\tthrow new HOAConsumerException(\"Invalid acc-name: Streett header\");\n\t\t}\n\n\t\tint numberOfPairs = (Integer)extraInfo.get(0);\n\t\tAcceptanceStreett acceptanceStreett = new AcceptanceStreett();\n\t\tacceptanceSets = new ArrayList<BitSet>(numberOfPairs*2);\n\t\tfor (int i = 0; i< numberOfPairs; i++) {\n\t\t\tBitSet R = new BitSet();\n\t\t\tBitSet G = new BitSet();\n\n\t\t\tacceptanceSets.add(R);   // 2*i\n\t\t\tacceptanceSets.add(G);   // 2*i+1\n\n\t\t\tacceptanceStreett.add(new StreettPair(R,G));\n\t\t}\n\n\t\treturn acceptanceStreett;\n\t}\n\n\t/**\n\t * Prepare a Generalized Rabin acceptance condition from the acc-name header.\n\t */\n\tprivate AcceptanceGenRabin prepareAcceptanceGenRabin() throws HOAConsumerException\n\t{\n\t\tif (extraInfo.size() < 1 ||\n\t\t    !(extraInfo.get(0) instanceof Integer)) {\n\t\t\tthrow new HOAConsumerException(\"Invalid acc-name: generalized-Rabin header\");\n\t\t}\n\n\t\tint numberOfPairs = (Integer)extraInfo.get(0);\n\t\tif (extraInfo.size() != numberOfPairs + 1) {\n\t\t\tthrow new HOAConsumerException(\"Invalid acc-name: generalized-Rabin header\");\n\t\t}\n\t\tint numberOfKs[] = new int[numberOfPairs];\n\t\tfor (int i = 0; i < numberOfPairs; i++) {\n\t\t\tif (!(extraInfo.get(i + 1) instanceof Integer)) {\n\t\t\t\tthrow new HOAConsumerException(\"Invalid acc-name: generalized-Rabin header\");\n\t\t\t}\n\t\t\tnumberOfKs[i] = (Integer) extraInfo.get(i + 1);\n\t\t}\n\t\t\n\t\tAcceptanceGenRabin acceptanceGenRabin = new AcceptanceGenRabin();\n\t\tacceptanceSets = new ArrayList<BitSet>(numberOfPairs*2);\n\t\tfor (int i = 0; i< numberOfPairs; i++) {\n\t\t\tBitSet L = new BitSet();\n\t\t\tacceptanceSets.add(L);   // Fin(L) = F G !L\n\t\t\tArrayList<BitSet> K_list = new ArrayList<BitSet>();\n\t\t\tfor (int j = 0; j < numberOfKs[i]; j++) {\n\t\t\t\tBitSet K_j = new BitSet();\n\t\t\t\tK_list.add(K_j);\n\t\t\t\tacceptanceSets.add(K_j);   // Inf(K_j) = G F  K_j\n\t\t\t}\n\t\t\tacceptanceGenRabin.add(new GenRabinPair(L, K_list));\n\t\t}\n\n\t\treturn acceptanceGenRabin;\n\t}\n\n\t@Override\n\tpublic void addState(int id, String info,\n\t\t\tBooleanExpression<AtomLabel> labelExpr, List<Integer> accSignature)\n\t\t\tthrows HOAConsumerException {\n\t\timplicitEdgeHelper.startOfState(id);\n\n\t\tif(labelExpr != null) {\n\t\t\tthrow new HOAConsumerException(\"State \"+id+\" has a state label, currently only supports labels on transitions\");\n\t\t}\n\n\t\tif (knowSize) {\n\t\t\t// we know the number of states, so if we are out of range then it's a hard error\n\t\t\tif (id >= size) {\n\t\t\t\tthrow new HOAConsumerException(\"Illegal state index \"+id+\", out of range\");\n\t\t\t}\n\t\t} else {\n\t\t\t// ensure that all states up to id are allocated\n\t\t\tensureStateExists(id);\n\t\t\t// and remember that state id actually had a definition\n\t\t\tstatesWithoutDefinition.clear(id);\n\t\t}\n\n\t\tif (accSignature != null) {\n\t\t\tfor (int index : accSignature) {\n\t\t\t\tif (index >= acceptanceSets.size()) {\n\t\t\t\t\t// acceptance set index not used in acceptance condition, ignore\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tBitSet accSet = acceptanceSets.get(index);\n\t\t\t\tif (accSet == null) {\n\t\t\t\t\t// acceptance set index not used in acceptance condition, ignore\n\t\t\t\t} else {\n\t\t\t\t\taccSet.set(id);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void addEdgeImplicit(int stateId, List<Integer> conjSuccessors,\n\t\t\tList<Integer> accSignature) throws HOAConsumerException {\n\t\tif (conjSuccessors.size() != 1) {\n\t\t\tthrow new HOAConsumerException(\"Not a DA, state \"+stateId+\" has transition with conjunctive target\");\n\t\t}\n\n\t\tif (accSignature != null) {\n\t\t\tthrow new TransitionBasedAcceptanceException(\"DA has transition-based acceptance (state \"+stateId+\", currently only state-labeled acceptance is supported\");\n\t\t}\n\n\t\tint to = conjSuccessors.get(0);\n\n\t\tif (knowSize) {\n\t\t\tif (to >= size) {\n\t\t\t\tthrow new HOAConsumerException(\"Illegal state index \"+to+\" in edge from state \"+stateId+\", out of range\");\n\t\t\t}\n\t\t} else {\n\t\t\tensureStateExists(to);\n\t\t}\n\n\t\tBitSet edge = new BitSet();\n\t\tlong tmp = implicitEdgeHelper.nextImplicitEdge();\n\t\tint index = 0;\n\t\twhile (tmp != 0) {\n\t\t\tif (tmp % 2 == 1) {\n\t\t\t\tedge.set(index);\n\t\t\t}\n\t\t\ttmp = tmp >> 1L;\n\t\t\tindex++;\n\t\t}\n\t\tda.addEdge(stateId, edge, to);\n\t}\n\t\n\t/**\n\t * Returns a list of APMonoms for the expression. The expression currently has to be in\n\t * disjunctive normal form. Returns one APMonom for each clause of the DNF.\n\t */\n\tprivate List<APMonom> labelExpressionToAPMonom(BooleanExpression<AtomLabel> expr) throws HOAConsumerException {\n\t\tList<APMonom> result = new ArrayList<APMonom>();\n\t\t\n\t\tswitch (expr.getType()) {\n\t\tcase EXP_AND:\n\t\tcase EXP_ATOM:\n\t\tcase EXP_NOT: {\n\t\t\tAPMonom monom = new APMonom();\n\t\t\tlabelExpressionToAPMonom(expr, monom);\n\t\t\tresult.add(monom);\n\t\t\treturn result;\n\t\t}\n\t\tcase EXP_TRUE:\n\t\t\tresult.add(new APMonom(true));\n\t\t\treturn result;\n\t\tcase EXP_FALSE:\n\t\t\tresult.add(new APMonom(false));\n\t\t\treturn result;\n\t\tcase EXP_OR:\n\t\t\tresult.addAll(labelExpressionToAPMonom(expr.getLeft()));\n\t\t\tresult.addAll(labelExpressionToAPMonom(expr.getRight()));\n\t\t\treturn result;\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unsupported operator in label expression: \"+expr);\n\t}\n\n\t\n\t/**\n\t * Returns a single APMonom for a single clause of the overall DNF formula.\n\t * Modifies APMonom result such that in the end it is correct.\n\t */\n\tprivate void labelExpressionToAPMonom(BooleanExpression<AtomLabel> expr, APMonom result) throws HOAConsumerException {\n\t\ttry {\n\t\t\tswitch (expr.getType()) {\n\t\t\tcase EXP_TRUE:\n\t\t\tcase EXP_FALSE:\n\t\t\tcase EXP_OR:\n\t\t\t\tthrow new HOAConsumerException(\"Complex transition labels are not yet supported, only disjunctive normal form: \"+expr);\n\n\t\t\tcase EXP_AND:\n\t\t\t\tlabelExpressionToAPMonom(expr.getLeft(), result);\n\t\t\t\tlabelExpressionToAPMonom(expr.getRight(), result);\n\t\t\t\treturn;\n\t\t\tcase EXP_ATOM: {\n\t\t\t\tint apIndex = expr.getAtom().getAPIndex();\n\t\t\t\tif (result.isSet(apIndex) && result.getValue(apIndex)!=true) {\n\t\t\t\t\tthrow new HOAConsumerException(\"Complex transition labels are not yet supported, transition label evaluates to false\");\n\t\t\t\t}\n\t\t\t\tresult.setValue(apIndex, true);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tcase EXP_NOT: {\n\t\t\t\tif (!expr.getLeft().isAtom()) {\n\t\t\t\t\tthrow new HOAConsumerException(\"Complex transition labels are not yet supported, only conjunction of (negated) labels\");\n\t\t\t\t}\n\t\t\t\tint apIndex = expr.getLeft().getAtom().getAPIndex();\n\t\t\t\tif (result.isSet(apIndex) && result.getValue(apIndex)!=false) {\n\t\t\t\t\tthrow new HOAConsumerException(\"Complex transition labels are not yet supported, transition label evaluates to false\");\n\t\t\t\t}\n\t\t\t\tresult.setValue(apIndex, false);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tthrow new HOAConsumerException(\"While parsing, APMonom exception: \"+e.getMessage());\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void addEdgeWithLabel(int stateId,\n\t\t\tBooleanExpression<AtomLabel> labelExpr,\n\t\t\tList<Integer> conjSuccessors, List<Integer> accSignature)\n\t\t\tthrows HOAConsumerException {\n\n\t\tif (conjSuccessors.size() != 1) {\n\t\t\tthrow new HOAConsumerException(\"Not a DA, state \"+stateId+\" has transition with conjunctive target\");\n\t\t}\n\n\t\tif (accSignature != null) {\n\t\t\tthrow new TransitionBasedAcceptanceException(\"DA has transition-based acceptance (state \"+stateId+\", currently only state-labeled acceptance is supported\");\n\t\t}\n\n\t\tif (labelExpr == null) {\n\t\t\tthrow new HOAConsumerException(\"Missing label on transition\");\n\t\t}\n\n\t\tint to = conjSuccessors.get(0);\n\n\t\tif (knowSize) {\n\t\t\tif (to >= size) {\n\t\t\t\tthrow new HOAConsumerException(\"Illegal state index \"+to+\" in edge from state \"+stateId+\", out of range\");\n\t\t\t}\n\t\t} else {\n\t\t\tensureStateExists(to);\n\t\t}\n\n\t\tfor (APMonom monom : labelExpressionToAPMonom(labelExpr)) {\n\t\t\tAPMonom2APElements it = new APMonom2APElements(aps, monom);\n\t\t\twhile(it.hasNext()) {\n\t\t\t\tAPElement el = it.next();\n\t\t\t\t// check whether this edge already exist\n\t\t\t\tint previousTo = da.getEdgeDestByLabel(stateId, el);\n\t\t\t\tif (previousTo == to) {\n\t\t\t\t\t// there is already an edge for this label, but the target\n\t\t\t\t\t// state is the same, so we don't add an additional edge\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (previousTo != -1) {\n\t\t\t\t\tthrow new HOAConsumerException(\"Not a deterministic automaton, non-determinism detected (state \"+stateId+\", label = \"+el+\", to=\"+to+\", previously to \"+previousTo+\")\");\n\t\t\t\t}\n\t\t\t\tda.addEdge(stateId, el, to);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void notifyEndOfState(int stateId) throws HOAConsumerException\n\t{\n\t\timplicitEdgeHelper.endOfState();\n\n\t\tif (da.getNumEdges(stateId) != expectedNumberOfEdgesPerState) {\n\t\t\tthrow new HOAConsumerException(\"State \"+ stateId +\" has \" + da.getNumEdges(stateId)\n\t\t\t                               + \" transitions, should have \" + expectedNumberOfEdgesPerState\n\t\t\t                               + \" (automaton is required to be complete and deterministic)\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void notifyEnd() throws HOAConsumerException {\n\t\tif (!knowSize) {\n\t\t\t// We did not know the number of states a-priori, so we check that all states\n\t\t\t// that we have allocated actually had a definition\n\t\t\tif (!statesWithoutDefinition.isEmpty()) {\n\t\t\t\tint stateId = statesWithoutDefinition.nextSetBit(0);\n\t\t\t\tthrow new HOAConsumerException(statesWithoutDefinition.cardinality() + \" states (e.g., state \"\n\t\t\t\t                               + stateId + \") have no definition (automaton is required to be complete and deterministic)\");\n\t\t\t}\n\t\t}\n\n\t\t// flip acceptance sets that need negating\n\t\tif (negateAcceptanceSetMembership != null) {\n\t\t\tfor (int index : negateAcceptanceSetMembership) {\n\t\t\t\tacceptanceSets.get(index).flip(0, da.size());\n\t\t\t}\n\t\t}\n\n\t\tclear();\n\t}\n\n\t@Override\n\tpublic void notifyAbort() {\n\t\tclear();\n\t\t\n\t}\n\t\n\tpublic DA<BitSet,? extends AcceptanceOmega> getDA() {\n\t\treturn da;\n\t}\n\n\t@Override\n\tpublic void notifyWarning(String warning) throws HOAConsumerException\n\t{\n\t\t// warnings are fatal\n\t\tthrow new HOAConsumerException(warning);\n\t}\n\n\t/** Command-line interface for reading, parsing and printing a HOA automaton (for testing) */\n\tpublic static void main(String args[])\n\t{\n\t\tint rv = 0;\n\t\tInputStream input = null;\n\t\ttry {\n\t\t\tif (args.length != 2) {\n\t\t\t\tSystem.err.println(\"Usage: input-file output-file\\n\\n Filename can be '-' for standard input/output\");\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t\tif (args[0].equals(\"-\")) {\n\t\t\t\tinput = System.in;\n\t\t\t} else {\n\t\t\t\tinput = new FileInputStream(args[0]);\n\t\t\t}\n\n\t\t\tPrintStream output;\n\t\t\tString outfile = args[1];\n\t\t\tif (outfile.equals(\"-\")) {\n\t\t\t\toutput = System.out;\n\t\t\t} else {\n\t\t\t\toutput = new PrintStream(outfile);\n\t\t\t}\n\n\t\t\tDA<BitSet, ? extends AcceptanceOmega> result;\n\t\t\ttry {\n\t\t\t\tHOAF2DA consumerDA = new HOAF2DA();\n\t\t\t\tHOAFParser.parseHOA(input, consumerDA);\n\t\t\t\tresult = consumerDA.getDA();\n\t\t\t} catch (HOAF2DA.TransitionBasedAcceptanceException e) {\n\t\t\t\t// try again, this time transforming to state acceptance\n\t\t\t\tif (input == System.in) {\n\t\t\t\t\tSystem.out.println(\"Automaton with transition-based acceptance, can only be (re)parsed from file\");\n\t\t\t\t\tSystem.exit(1);\n\t\t\t\t}\n\t\t\t\tSystem.out.println(\"Automaton with transition-based acceptance, automatically converting to state-based acceptance...\");\n\t\t\t\tHOAF2DA consumerDA = new HOAF2DA();\n\t\t\t\tHOAIntermediateStoreAndManipulate consumerTransform = new HOAIntermediateStoreAndManipulate(consumerDA, new ToStateAcceptance());\n\n\t\t\t\tHOAFParser.parseHOA(input, consumerTransform);\n\t\t\t\tresult = consumerDA.getDA();\n\t\t\t}\n\n\t\t\tif (result == null) {\n\t\t\t\tthrow new PrismException(\"Could not construct DA\");\n\t\t\t}\n\n\t\t\t// should we try and simplify?\n\t\t\t// result = DASimplifyAcceptance.simplifyAcceptance(result, acceptance.AcceptanceType.REACH);\n\n\t\t\tresult.printHOA(output);\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(e.toString());\n\t\t\trv = 1;\n\t\t}\n\t\t\n\t\tif (rv != 0) {\n\t\t\tSystem.exit(rv);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/automata/LTL2DA.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage automata;\n\nimport java.io.File;\nimport java.io.FileInputStream;\nimport java.io.FileWriter;\nimport java.io.IOException;\nimport java.io.InputStream;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\nimport acceptance.AcceptanceBuchi;\nimport jhoafparser.consumer.HOAIntermediateStoreAndManipulate;\nimport jhoafparser.parser.HOAFParser;\nimport jhoafparser.parser.generated.ParseException;\nimport jhoafparser.transformations.ToStateAcceptance;\nimport jltl2ba.APSet;\nimport jltl2ba.SimpleLTL;\nimport jltl2ba.LTLFragments;\nimport jltl2dstar.LTL2Rabin;\nimport parser.Values;\nimport parser.ast.Expression;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceType;\n\n/**\n * Infrastructure for constructing deterministic automata for LTL formulas.\n */\npublic class LTL2DA extends PrismComponent\n{\n\n\tpublic LTL2DA(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Convert an LTL formula into a deterministic Rabin automaton.\n\t * The LTL formula is represented as a PRISM Expression,\n\t * in which atomic propositions are represented by ExpressionLabel objects.\n\t * @param ltl the formula\n\t * @param constantValues the values of constants, may be {@code null}\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic DA<BitSet, AcceptanceRabin> convertLTLFormulaToDRA(Expression ltl, Values constantValues) throws PrismException\n\t{\n\t\tAcceptanceType[] allowedAcceptance = {\n\t\t\t\tAcceptanceType.BUCHI,\n\t\t\t\tAcceptanceType.RABIN,\n\t\t};\n\t\tDA<BitSet, ? extends AcceptanceOmega> da = convertLTLFormulaToDA(ltl, constantValues, allowedAcceptance);\n\t\tif (da.getAcceptance() instanceof AcceptanceBuchi) {\n\t\t\t((DA<BitSet, AcceptanceRabin>) da).setAcceptance(((AcceptanceBuchi) da.getAcceptance()).toRabin());\n\t\t}\n\t\treturn (DA<BitSet, AcceptanceRabin>) da;\n\t}\n\n\t/**\n\t * Convert an LTL formula into a deterministic automaton.\n\t * The LTL formula is represented as a PRISM Expression,\n\t * in which atomic propositions are represented by ExpressionLabel objects.\n\t * @param ltl the formula\n\t * @param constants the values of constants, may be {@code null}\n\t * @param allowedAcceptance the AcceptanceTypes that are allowed to be returned\n\t */\n\tpublic DA<BitSet, ? extends AcceptanceOmega> convertLTLFormulaToDA(Expression ltl, Values constants, AcceptanceType... allowedAcceptance)\n\t\t\tthrows PrismException\n\t{\n\t\tDA<BitSet, ? extends AcceptanceOmega> result = null;\n\n\t\tboolean useExternal = useExternal();\n\t\tboolean containsTemporalBounds = Expression.containsTemporalTimeBounds(ltl);\n\t\tif (containsTemporalBounds) {\n\t\t\tuseExternal = false;\n\t\t}\n\n\t\tif (!useExternal) {\n\t\t\ttry {\n\t\t\t\t// checking the library first\n\t\t\t\tresult = LTL2RabinLibrary.getDAforLTL(ltl, constants, allowedAcceptance);\n\t\t\t\tif (result != null) {\n\t\t\t\t\tgetLog().println(\"Taking \"+result.getAutomataType()+\" from library...\");\n\t\t\t\t}\n\t\t\t} catch (Exception e) {\n\t\t\t\tif (containsTemporalBounds) {\n\t\t\t\t\t// there is (currently) no other way to translate LTL with temporal bounds,\n\t\t\t\t\t// so treat an exception as a \"real\" one\n\t\t\t\t\tthrow e;\n\t\t\t\t} else {\n\t\t\t\t\t// there is the possibility that we might be able to construct\n\t\t\t\t\t// an automaton below, just issue a warning\n\t\t\t\t\tgetLog().println(\"Warning: Exception during attempt to construct DRA using the LTL2RabinLibrary:\");\n\t\t\t\t\tgetLog().println(\" \" + e.getMessage());\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (result == null) {\n\t\t\tif (!containsTemporalBounds) {\n\t\t\t\tif (useExternal) {\n\t\t\t\t\tresult = convertLTLFormulaToDAWithExternalTool(ltl, constants, allowedAcceptance);\n\t\t\t\t} else {\n\t\t\t\t\tSimpleLTL simpleLTL = ltl.convertForJltl2ba();\n\n\t\t\t\t\t// don't use LTL2WDBA translation yet\n\t\t\t\t\tboolean allowLTL2WDBA = false;\n\t\t\t\t\tif (allowLTL2WDBA) {\n\t\t\t\t\t\tLTLFragments fragments = LTLFragments.analyse(simpleLTL);\n\t\t\t\t\t\tmainLog.println(fragments);\n\n\t\t\t\t\t\tif (fragments.isSyntacticGuarantee() && AcceptanceType.contains(allowedAcceptance, AcceptanceType.REACH)) {\n\t\t\t\t\t\t\t// a co-safety property\n\t\t\t\t\t\t\tmainLog.println(\"Generating DFA for co-safety property...\");\n\t\t\t\t\t\t\tLTL2WDBA ltl2wdba = new LTL2WDBA(this);\n\t\t\t\t\t\t\tresult = ltl2wdba.cosafeltl2dfa(simpleLTL);\n\t\t\t\t\t\t} else if (allowLTL2WDBA && fragments.isSyntacticObligation() && AcceptanceType.contains(allowedAcceptance, AcceptanceType.BUCHI)) {\n\t\t\t\t\t\t\t// an obligation property\n\t\t\t\t\t\t\tmainLog.println(\"Generating DBA for obligation property...\");\n\t\t\t\t\t\t\tLTL2WDBA ltl2wdba = new LTL2WDBA(this);\n\t\t\t\t\t\t\tresult = ltl2wdba.obligation2wdba(simpleLTL);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (result == null) {\n\t\t\t\t\t\t// use jltl2dstar LTL2DA\n\t\t\t\t\t\tresult = LTL2Rabin.ltl2da(simpleLTL, allowedAcceptance);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismNotSupportedException(\"Could not convert LTL formula to deterministic automaton, formula had time-bounds\");\n\t\t\t}\n\t\t}\n\n\t\tif (result == null) {\n\t\t\tthrow new PrismNotSupportedException(\"Could not convert LTL formula to deterministic automaton\");\n\t\t}\n\n\t\tif (!getSettings().getBoolean(PrismSettings.PRISM_NO_DA_SIMPLIFY)) {\n\t\t\tresult = DASimplifyAcceptance.simplifyAcceptance(this, result, allowedAcceptance);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\tpublic DA<BitSet, ? extends AcceptanceOmega> convertLTLFormulaToDAWithExternalTool(Expression ltl, Values constants, AcceptanceType... allowedAcceptance)\n\t\t\tthrows PrismException\n\t{\n\t\tString ltl2daTool = getSettings().getString(PrismSettings.PRISM_LTL2DA_TOOL);\n\n\t\tSimpleLTL ltlFormula = ltl.convertForJltl2ba();\n\n\t\t// switch from the L0, L1, ... APs of PRISM to the\n\t\t// safer p0, p1, ... APs for the external tool\n\t\tSimpleLTL ltlFormulaSafeAP = ltlFormula.clone();\n\t\tltlFormulaSafeAP.renameAP(\"L\", \"p\");\n\n\t\tDA<BitSet, ? extends AcceptanceOmega> result = null;\n\n\t\ttry {\n\n\t\t\tString syntax = getSettings().getString(PrismSettings.PRISM_LTL2DA_SYNTAX);\n\t\t\tif (syntax == null || syntax.isEmpty()) {\n\t\t\t\tthrow new PrismException(\"No LTL syntax option provided\");\n\t\t\t}\n\t\t\tString ltlOutput;\n\t\t\tswitch (syntax) {\n\t\t\tcase \"LBT\":\n\t\t\t\tltlOutput = ltlFormulaSafeAP.toStringLBT();\n\t\t\t\tbreak;\n\t\t\tcase \"Spin\":\n\t\t\t\tltlOutput = ltlFormulaSafeAP.toStringSpin();\n\t\t\t\tbreak;\n\t\t\tcase \"Spot\":\n\t\t\t\tltlOutput = ltlFormulaSafeAP.toStringSpot();\n\t\t\t\tbreak;\n\t\t\tcase \"Rabinizer\":\n\t\t\t\tltlFormulaSafeAP = ltlFormulaSafeAP.toBasicOperators();\n\t\t\t\tltlOutput = ltlFormulaSafeAP.toStringSpot();\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown LTL syntax option \\\"\" + syntax + \"\\\"\");\n\t\t\t}\n\n\t\t\tFile ltl_file = File.createTempFile(\"prism-ltl-external-\", \".ltl\", null);\n\t\t\tFile da_file = File.createTempFile(\"prism-ltl-external-\", \".hoa\", null);\n\t\t\tFile tool_output = File.createTempFile(\"prism-ltl-external-\", \".output\", null);\n\n\t\t\tFileWriter ltlWriter = new FileWriter(ltl_file);\n\t\t\tltlWriter.write(ltlOutput);\n\t\t\tltlWriter.close();\n\n\t\t\tList<String> arguments = new ArrayList<String>();\n\t\t\targuments.add(ltl2daTool);\n\n\t\t\tgetLog().print(\"Calling external LTL->DA tool: \");\n\t\t\tfor (String s : arguments) {\n\t\t\t\tgetLog().print(\" \" + s);\n\t\t\t}\n\t\t\tgetLog().println();\n\n\t\t\tgetLog().print(\"LTL formula (in \" + syntax + \" syntax):  \");\n\t\t\tgetLog().println(ltlOutput);\n\n\t\t\targuments.add(ltl_file.getAbsolutePath());\n\t\t\targuments.add(da_file.getAbsolutePath());\n\n\t\t\tProcessBuilder builder = new ProcessBuilder(arguments);\n\t\t\tbuilder.redirectOutput(tool_output);\n\t\t\tbuilder.redirectErrorStream(true);\n\n\t\t\t// if we are running under the Nailgun environment, setup the\n\t\t\t// environment to include the environment variables of the Nailgun client\n\t\t\tprism.PrismNG.setupChildProcessEnvironment(builder);\n\n\t\t\tProcess p = builder.start();\n\t\t\tp.getInputStream().close();\n\n\t\t\tint rv;\n\t\t\twhile (true) {\n\t\t\t\ttry {\n\t\t\t\t\trv = p.waitFor();\n\t\t\t\t\tbreak;\n\t\t\t\t} catch (InterruptedException e) {\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (rv != 0) {\n\t\t\t\tthrow new PrismException(\"Call to external LTL->DA tool failed, return value = \" + rv + \".\\n\"\n\t\t\t\t\t\t+ \"To investigate, please consult the following files:\" + \"\\n LTL formula:                     \" + ltl_file.getAbsolutePath()\n\t\t\t\t\t\t+ \"\\n Automaton output:                \" + da_file.getAbsolutePath() + \"\\n Tool output (stdout and stderr): \"\n\t\t\t\t\t\t+ tool_output.getAbsolutePath() + \"\\n\");\n\t\t\t}\n\n\t\t\ttool_output.delete();\n\n\t\t\ttry {\n\t\t\t\ttry {\n\t\t\t\t\tHOAF2DA consumerDA = new HOAF2DA();\n\n\t\t\t\t\tInputStream input = new FileInputStream(da_file);\n\t\t\t\t\tHOAFParser.parseHOA(input, consumerDA);\n\t\t\t\t\tresult = consumerDA.getDA();\n\t\t\t\t} catch (HOAF2DA.TransitionBasedAcceptanceException e) {\n\t\t\t\t\t// try again, this time transforming to state acceptance\n\t\t\t\t\tgetLog().println(\"Automaton with transition-based acceptance, automatically converting to state-based acceptance...\");\n\t\t\t\t\tHOAF2DA consumerDA = new HOAF2DA();\n\t\t\t\t\tHOAIntermediateStoreAndManipulate consumerTransform = new HOAIntermediateStoreAndManipulate(consumerDA, new ToStateAcceptance());\n\n\t\t\t\t\tInputStream input = new FileInputStream(da_file);\n\t\t\t\t\tHOAFParser.parseHOA(input, consumerTransform);\n\t\t\t\t\tresult = consumerDA.getDA();\n\t\t\t\t}\n\n\t\t\t\tif (result == null) {\n\t\t\t\t\tthrow new PrismException(\"Could not construct DA\");\n\t\t\t\t}\n\t\t\t\tcheckAPs(ltlFormulaSafeAP, result.getAPList());\n\n\t\t\t\t// rename back from safe APs, i.e., p0, p1, ... to L0, L1, ...\n\t\t\t\tList<String> automatonAPList = result.getAPList();\n\t\t\t\tfor (int i = 0; i < automatonAPList.size(); i++) {\n\t\t\t\t\tif (automatonAPList.get(i).startsWith(\"p\")) {\n\t\t\t\t\t\tString renamed = \"L\" + automatonAPList.get(i).substring(\"p\".length());\n\t\t\t\t\t\tautomatonAPList.set(i, renamed);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} catch (ParseException e) {\n\t\t\t\tthrow new PrismException(\"Parse error: \" + e.getMessage() + \".\\n\" + \"To investigate, please consult the following files:\\n\"\n\t\t\t\t\t\t+ \" LTL formula:        \" + ltl_file.getAbsolutePath() + \"\\n Automaton output: \" + da_file.getAbsolutePath() + \"\\n\");\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow new PrismException(e.getMessage() + \".\\n\" + \"To investigate, please consult the following files:\" + \"\\n LTL formula: \"\n\t\t\t\t\t\t+ ltl_file.getAbsolutePath() + \"\\n Automaton output: \" + da_file.getAbsolutePath() + \"\\n\");\n\t\t\t}\n\n\t\t\tda_file.delete();\n\t\t\tltl_file.delete();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(e.getMessage());\n\t\t}\n\n\t\tif (!getSettings().getBoolean(PrismSettings.PRISM_NO_DA_SIMPLIFY)) {\n\t\t\tresult = DASimplifyAcceptance.simplifyAcceptance(this, result, allowedAcceptance);\n\t\t}\n\n\t\tAcceptanceOmega acceptance = result.getAcceptance();\n\t\tif (AcceptanceType.contains(allowedAcceptance, acceptance.getType())) {\n\t\t\treturn result;\n\t\t} else if (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\t// The specific acceptance type is not allowed, but GENERIC is allowed\n\t\t\t//   -> transform to generic acceptance and switch acceptance condition\n\t\t\tDA.switchAcceptance(result, acceptance.toAcceptanceGeneric());\n\t\t\treturn result;\n\t\t} else {\n\t\t\tthrow new PrismException(\"The external LTL->DA tool returned an automaton with \" + acceptance.getType()\n\t\t\t\t\t+ \" acceptance, which is not yet supported for model checking this model / property\");\n\t\t}\n\t}\n\n\t/** Check whether we should use an external LTL->DA tool */\n\tprivate boolean useExternal()\n\t{\n\t\tString ltl2da_tool = getSettings().getString(PrismSettings.PRISM_LTL2DA_TOOL);\n\t\tif (ltl2da_tool != null && !ltl2da_tool.isEmpty()) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** Check the atomic propositions of the (externally generated) automaton */\n\tprivate void checkAPs(SimpleLTL ltl, List<String> automatonAPs) throws PrismException\n\t{\n\t\tAPSet ltlAPs = ltl.getAPs();\n\t\tfor (String ap : automatonAPs) {\n\t\t\tif (!ltlAPs.hasAP(ap)) {\n\t\t\t\tthrow new PrismException(\"Generated automaton has extra atomic proposition \\\"\" + ap + \"\\\"\");\n\t\t\t}\n\t\t}\n\t\t// It's fine for the automaton to not have APs that occur in the formula, e.g., for\n\t\t// p0 | !p0, the external tool could simplify to 'true' and omit all APs\n\t}\n\n\t/**\n\t * Simple test method: convert LTL formula (in LBT format) to HOA/Dot/txt\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\ttry {\n\t\t\t// Usage:\n\t\t\t// * ... 'X p1' \n\t\t\t// * ... 'X p1' da.hoa \n\t\t\t// * ... 'X p1' da.hoa hoa \n\t\t\t// * ... 'X p1' da.dot dot \n\t\t\t// * ... 'X p1' - hoa \n\t\t\t// * ... 'X p1' - txt \n\n\t\t\t// Convert to Expression (from PRISM format)\n\t\t\t/*String pltl = \"P=?[\" + ltl + \"]\";\n\t\t\tPropertiesFile pf = Prism.getPrismParser().parsePropertiesFile(new ModulesFile(), new ByteArrayInputStream(pltl.getBytes()));\n\t\t\tPrism.releasePrismParser();\n\t\t\tExpression expr = pf.getProperty(0);\n\t\t\texpr = ((ExpressionProb) expr).getExpression();\n\t\t\tSystem.out.println(\"LTL: \" + expr);*/\n\n\t\t\t// Convert to Expression (from LBT format)\n\t\t\t// String ltl = args[0];\n\t\t\tSimpleLTL sltl = SimpleLTL.parseFormulaLBT(args[0]);\n\t\t\tExpression expr = Expression.createFromJltl2ba(sltl);\n\t\t\t// System.out.println(\"LBT: \" + ltl);\n\t\t\t// System.out.println(\"LTL: \" + expr);\n\n\t\t\t// Build/export DA\n\t\t\tLTL2DA ltl2da = new LTL2DA(new PrismComponent());\n\t\t\tDA<BitSet, ? extends AcceptanceOmega> da = ltl2da.convertLTLFormulaToDA(expr, null, AcceptanceType.RABIN, AcceptanceType.REACH);\n\t\t\tPrintStream out = (args.length < 2 || \"-\".equals(args[1])) ? System.out : new PrintStream(args[1]);\n\t\t\tString format = (args.length < 3) ? \"hoa\" : args[2];\n\t\t\tda.print(out, format);\n\n\t\t} catch (Exception e) {\n\t\t\te.printStackTrace();\n\t\t\tSystem.err.print(\"Error: \" + e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/automata/LTL2NBA.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage automata;\n\nimport jltl2ba.SimpleLTL;\nimport jltl2dstar.NBA;\nimport parser.Values;\nimport parser.ast.Expression;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Infrastructure for constructing non-deterministic Büchi automata for LTL formulas.\n */\npublic class LTL2NBA extends PrismComponent\n{\n\n\tpublic LTL2NBA(PrismComponent parent) throws PrismException {\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Convert an LTL formula into a non-deterministic Büchi automaton.\n\t * The LTL formula is represented as a PRISM Expression,\n\t * in which atomic propositions are represented by ExpressionLabel objects.\n\t * @param ltl the formula\n\t * @param constantValues the values of constants, may be {@code null}\n\t */\n\tpublic NBA convertLTLFormulaToNBA(Expression ltl, Values constantValues) throws PrismException\n\t{\n\t\tif (Expression.containsTemporalTimeBounds(ltl)) {\n\t\t\tthrow new PrismNotSupportedException(\"LTL with time bounds currently not supported for LTL model checking.\");\n\t\t}\n\n\t\t// convert to jltl2ba LTL, simplify formula\n\t\tSimpleLTL ltlSimple = ltl.convertForJltl2ba().simplify();\n\t\treturn ltlSimple.toNBA();\n\t}\n}\n"
  },
  {
    "path": "prism/src/automata/LTL2RabinLibrary.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage automata;\n\nimport java.io.*;\nimport java.util.*;\n\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceRabin.RabinPair;\nimport acceptance.AcceptanceType;\nimport parser.Values;\nimport parser.ast.*;\nimport parser.visitor.ASTTraverse;\nimport parser.visitor.ASTTraverseModify;\nimport prism.IntegerBound;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismNotSupportedException;\n\n/**\n * LTL-to-DRA conversion via\n * <ol>\n *  <li> hard-coded DRA for special formulas </li>\n *  <li> direct translation into DRA for simple path formulas with temporal bounds</li>\n * </ol>\n */\npublic class LTL2RabinLibrary\n{\n\tprivate static ArrayList<String> labels;\n\n\tprivate static HashMap<String, String> dras;\n\tstatic {\n\t\t// Hard-coded DRA descriptions for various LTL formulas \n\t\tdras = new HashMap<String, String>();\n\t\tdras.put(\"F \\\"L0\\\"\", \"2 states (start 0), 1 labels: 0-{}->0 0-{0}->1 1-{}->1 1-{0}->1; 1 acceptance pairs: ({},{1})\");\n\t\tdras.put(\"G \\\"L0\\\"\", \"2 states (start 0), 1 labels: 0-{}->1 0-{0}->0 1-{}->1 1-{0}->1; 1 acceptance pairs: ({1},{0})\");\n\t\tdras.put(\"G F \\\"L0\\\"\", \"2 states (start 0), 1 labels: 0-{0}->1 0-{}->0 1-{0}->1 1-{}->0; 1 acceptance pairs: ({},{1})\");\n\t\tdras.put(\"!(G F \\\"L0\\\")\", \"2 states (start 0), 1 labels: 0-{}->1 0-{0}->0 1-{}->1 1-{0}->0; 1 acceptance pairs: ({0},{1})\");\n\t\tdras.put(\"F G \\\"L0\\\"\", \"2 states (start 0), 1 labels: 0-{0}->1 0-{}->0 1-{0}->1 1-{}->0; 1 acceptance pairs: ({0},{1})\");\n\t\tdras.put(\"!(F G \\\"L0\\\")\", \"2 states (start 0), 1 labels: 0-{}->1 0-{0}->0 1-{}->1 1-{0}->0; 1 acceptance pairs: ({},{1})\");\n\t\t//dras.put(\"F (\\\"L0\\\"&(X \\\"L1\\\"))\", \"3 states (start 2), 2 labels: 0-{1}->0 0-{0, 1}->0 0-{}->0 0-{0}->0 1-{1}->0 1-{0, 1}->0 1-{}->2 1-{0}->1 2-{1}->2 2-{0, 1}->1 2-{}->2 2-{0}->1; 1 acceptance pairs: ({},{0})\");\n\t\t//dras.put(\"!(F (\\\"L0\\\"&(X \\\"L1\\\")))\", \"4 states (start 3), 2 labels: 0-{1}->0 0-{0, 1}->1 0-{}->0 0-{0}->1 1-{1}->2 1-{0, 1}->2 1-{}->0 1-{0}->1 2-{1}->2 2-{0, 1}->2 2-{}->2 2-{0}->2 3-{1}->0 3-{0, 1}->1 3-{}->0 3-{0}->1; 1 acceptance pairs: ({2},{0, 1})\");\n\t\t//dras.put(\"(X \\\"L0\\\")=>(G \\\"L1\\\")\", \"6 states (start 5), 2 labels: 0-{1}->0 0-{0, 1}->0 0-{}->0 0-{0}->0 1-{1}->0 1-{0, 1}->3 1-{}->0 1-{0}->4 2-{1}->0 2-{0, 1}->4 2-{}->0 2-{0}->4 3-{1}->3 3-{0, 1}->3 3-{}->4 3-{0}->4 4-{1}->4 4-{0, 1}->4 4-{}->4 4-{0}->4 5-{1}->1 5-{0, 1}->1 5-{}->2 5-{0}->2; 1 acceptance pairs: ({4},{0, 1, 2, 3})\");\n\t\t//dras.put(\"!((X \\\"L0\\\")=>(G \\\"L1\\\"))\", \"6 states (start 5), 2 labels: 0-{1}->0 0-{0, 1}->0 0-{}->0 0-{0}->0 1-{1}->1 1-{0, 1}->1 1-{}->1 1-{0}->1 2-{1}->2 2-{0, 1}->2 2-{}->0 2-{0}->0 3-{1}->1 3-{0, 1}->0 3-{}->1 3-{0}->0 4-{1}->1 4-{0, 1}->2 4-{}->1 4-{0}->0 5-{1}->4 5-{0, 1}->4 5-{}->3 5-{0}->3; 1 acceptance pairs: ({1},{0})\");\n\t\t//dras.put(\"(G !\\\"b\\\")&(G F \\\"a\\\")\", \"5 states (start 4), 2 labels: 0-{1}->0 0-{0, 1}->2 0-{}->1 0-{0}->2 1-{1}->3 1-{0, 1}->2 1-{}->4 1-{0}->2 2-{1}->2 2-{0, 1}->2 2-{}->2 2-{0}->2 3-{1}->0 3-{0, 1}->2 3-{}->1 3-{0}->2 4-{1}->3 4-{0, 1}->2 4-{}->4 4-{0}->2; 1 acceptance pairs: ({2},{0, 1})\");\n\t\t//dras.put(\"(G \\\"L0\\\")&(G F \\\"L1\\\")\", \"5 states (start 4), 2 labels: 0-{1}->2 0-{0, 1}->0 0-{}->2 0-{0}->1 1-{1}->2 1-{0, 1}->3 1-{}->2 1-{0}->4 2-{1}->2 2-{0, 1}->2 2-{}->2 2-{0}->2 3-{1}->2 3-{0, 1}->0 3-{}->2 3-{0}->1 4-{1}->2 4-{0, 1}->3 4-{}->2 4-{0}->4; 1 acceptance pairs: ({2},{0, 1})\");\n\t\t//dras.put(\"(G (\\\"L0\\\"=>(F \\\"L1\\\")))&(F G \\\"L2\\\")\", \"7 states (start 3), 3 labels: 0-{1, 2}->1 0-{0, 1, 2}->1 0-{2}->0 0-{0, 2}->0 0-{1}->3 0-{0, 1}->3 0-{}->4 0-{0}->4 1-{1, 2}->6 1-{0, 1, 2}->6 1-{2}->6 1-{0, 2}->5 1-{1}->3 1-{0, 1}->3 1-{}->3 1-{0}->4 2-{1, 2}->1 2-{0, 1, 2}->1 2-{2}->1 2-{0, 2}->0 2-{1}->3 2-{0, 1}->3 2-{}->3 2-{0}->4 3-{1, 2}->2 3-{0, 1, 2}->2 3-{2}->2 3-{0, 2}->4 3-{1}->3 3-{0, 1}->3 3-{}->3 3-{0}->4 4-{1, 2}->2 4-{0, 1, 2}->2 4-{2}->4 4-{0, 2}->4 4-{1}->3 4-{0, 1}->3 4-{}->4 4-{0}->4 5-{1, 2}->1 5-{0, 1, 2}->1 5-{2}->0 5-{0, 2}->0 5-{1}->3 5-{0, 1}->3 5-{}->4 5-{0}->4 6-{1, 2}->6 6-{0, 1, 2}->6 6-{2}->6 6-{0, 2}->5 6-{1}->3 6-{0, 1}->3 6-{}->3 6-{0}->4; 1 acceptance pairs: ({2, 3, 4},{5, 6})\");\n\t\t//dras.put(\"!((G \\\"L0\\\")&(G F \\\"L1\\\"))\", \"4 states (start 3), 2 labels: 0-{1}->1 0-{0, 1}->3 0-{}->1 0-{0}->0 1-{1}->1 1-{0, 1}->1 1-{}->1 1-{0}->1 2-{1}->1 2-{0, 1}->3 2-{}->1 2-{0}->0 3-{1}->1 3-{0, 1}->3 3-{}->1 3-{0}->2; 2 acceptance pairs: ({},{1}) ({1, 2, 3},{0})\"); \n\t}\n\n\t/**\n\t * Attempts to convert an LTL formula into a deterministic omega-automaton (with\n\t * one of the allowed acceptance conditions) by direct translation methods of the library:\n\t *\n\t * Relies on getDRAForLTL, with appropriate pre/post-processing for acceptance types\n\t * that are not Rabin.\n\t *\n\t * Return {@code null} if the automaton can not be constructed using the library.\n\t * <br> The LTL formula is represented as a PRISM Expression,\n\t * in which atomic propositions are represented by ExpressionLabel objects.\n\t * @param ltl the LTL formula\n\t * @param constants values for constants in the formula (may be {@code null})\n\t */\n\tpublic static DA<BitSet, ? extends AcceptanceOmega> getDAforLTL(Expression ltl, Values constants, AcceptanceType... allowedAcceptance) throws PrismException {\n\t\t// first try Rabin ...\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.RABIN)) {\n\t\t\treturn getDRAforLTL(ltl, constants);\n\t\t}\n\n\t\t// ..., then Streett (via negation and complementation at the acceptance level)\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.STREETT)) {\n\t\t\tExpression negatedLtl = Expression.Not(ltl);\n\t\t\tDA<BitSet, AcceptanceRabin> da = getDRAforLTL(negatedLtl, constants);\n\t\t\tif (da != null) {\n\t\t\t\tDA.switchAcceptance(da, da.getAcceptance().complementToStreett());\n\t\t\t\treturn da;\n\t\t\t}\n\t\t}\n\n\t\t// ..., and then generic acceptance\n\t\tif (AcceptanceType.contains(allowedAcceptance, AcceptanceType.GENERIC)) {\n\t\t\tDA<BitSet, AcceptanceRabin> da = getDRAforLTL(ltl, constants);\n\t\t\tDA.switchAcceptance(da, da.getAcceptance().toAcceptanceGeneric());\n\t\t\treturn da;\n\t\t}\n\n\t\treturn null;\n\t}\n\n\t/**\n\t * Attempts to convert an LTL formula into a DRA by direct translation methods of the library:\n\t * <ul>\n\t * <li>First, look up hard-coded DRA from the DRA map.</li>\n\t * <li>Second, if the formula is a simple path formula with temporal bounds, use the special\n\t *     constructions {@code constructDRAFor....}\n\t * </ul>\n\t * Return {@code null} if the automaton can not be constructed using the library.\n\t * <br> The LTL formula is represented as a PRISM Expression,\n\t * in which atomic propositions are represented by ExpressionLabel objects.\n\t * @param ltl the LTL formula\n\t * @param constants values for constants in the formula (may be {@code null})\n\t */\n\tpublic static DA<BitSet, AcceptanceRabin> getDRAforLTL(Expression ltl, Values constants) throws PrismException {\n\t\t// Get list of labels appearing\n\t\tlabels = new ArrayList<String>();\n\t\tltl.accept(new ASTTraverse()\n\t\t{\n\t\t\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t\t\t{\n\t\t\t\tlabels.add(e.getName());\n\t\t\t\treturn null;\n\t\t\t}\n\t\t});\n\n\t\t// On a copy of formula, rename labels to \"L0\", \"L1\", \"L2\", ...\n\t\t// (for looking up LTL formula in table of strings)\n\t\tExpression ltl2 = ltl.deepCopy();\n\t\tltl2.accept(new ASTTraverseModify()\n\t\t{\n\t\t\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t\t\t{\n\t\t\t\tint i = labels.indexOf(e.getName());\n\t\t\t\t//char letter = (char) ('a' + i);\n\t\t\t\treturn new ExpressionLabel(\"L\" + i);\n\t\t\t}\n\t\t});\n\n\t\t// See if we have a hard-coded DRA to return\n\t\tString draString = dras.get(ltl2.toString());\n\t\tif (draString != null)\n\t\t\treturn createDRAFromString(draString, labels);\n\n\t\t// handle simple until formula with time bounds\n\t\tif (Expression.containsTemporalTimeBounds(ltl)) {\n\t\t\tif (!ltl.isSimplePathFormula()) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Unsupported LTL formula with time bounds: \"+ltl);\n\t\t\t}\n\n\t\t\tltl = Expression.convertSimplePathFormulaToCanonicalForm(ltl);\n\t\t\tboolean negated = false;\n\n\t\t\tif (ltl instanceof ExpressionUnaryOp &&\n\t\t\t    ((ExpressionUnaryOp)ltl).getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\t\t// negated\n\t\t\t\tnegated = true;\n\t\t\t\tltl = ((ExpressionUnaryOp)ltl).getOperand();\n\t\t\t}\n\n\t\t\tif (ltl instanceof ExpressionTemporal &&\n\t\t\t    ((ExpressionTemporal)ltl).getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\treturn constructDRAForSimpleUntilFormula((ExpressionTemporal)ltl, constants, negated);\t\t\t\t\n\t\t\t} else {\n\t\t\t\t// should not be reached\n\t\t\t\tthrow new PrismException(\"Implementation error\");\n\t\t\t}\n\t\t}\n\t\t\n\t\t// No time-bounded operators, do not convert using the library\n\t\treturn null;\n\t}\n\n\t/** Helper class for storing info about an operand of a simple Until formula:\n\t *  Can be either TRUE, FALSE, a label or a negated label\n\t */\n\tstatic class OperandInfo {\n\t\tprivate String label;\n\t\tprivate boolean notNegated;\n\n\t\t/**\n\t\t * Constructor: TRUE / FALSE\n\t\t * @param value the value\n\t\t **/\n\t\tpublic OperandInfo(boolean value)\n\t\t{\n\t\t\tthis.label = null;\n\t\t\tnotNegated = value;\n\t\t}\n\n\t\t/**\n\t\t * Constructor: label or negated label\n\t\t * @param label the label\n\t\t * @param notNegated {@code true} if 'label', {@false} if '!label'\n\t\t */\n\t\tpublic OperandInfo(String label, boolean notNegated)\n\t\t{\n\t\t\tthis.label = label;\n\t\t\tthis.notNegated = notNegated;\n\t\t}\n\n\t\t/**\n\t\t * Static constructor: Extract info from an Expression.\n\t\t * Expression has to an ExpressionLabel or a boolean literal, possibly negated.\n\t\t */\n\t\tpublic static OperandInfo constructFrom(Expression expr) throws PrismException\n\t\t{\n\t\t\tif (expr instanceof ExpressionLabel) {\n\t\t\t\treturn new OperandInfo(((ExpressionLabel)expr).getName(), true);\n\t\t\t} else if (Expression.isNot(expr)) {\n\t\t\t\treturn constructFrom(((ExpressionUnaryOp)expr).getOperand()).negated();\n\t\t\t} else if (expr instanceof ExpressionLiteral &&\n\t\t\t           ((ExpressionLiteral) expr).getValue() instanceof Boolean) {\n\t\t\t\tboolean b = (Boolean)((ExpressionLiteral)expr).getValue();\n\t\t\t\treturn new OperandInfo(b);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"Unsupported expression \"+expr+\" in formula.\");\n\t\t\t}\n\t\t}\n\n\t\t/** Operand = TRUE? */\n\t\tpublic boolean isTrue()\n\t\t{\n\t\t\treturn label == null && notNegated;\n\t\t}\n\n\t\t/** Operand = FALSE? */\n\t\tpublic boolean isFalse()\n\t\t{\n\t\t\treturn label == null && !notNegated;\n\t\t}\n\n\t\t/** Operand = label or operand = !label? */\n\t\tpublic boolean isProperLabel()\n\t\t{\n\t\t\treturn label != null;\n\t\t}\n\n\t\t/** Get the label. Check first that {@code isProperLabel() == true}*/\n\t\tpublic String getLabel()\n\t\t{\n\t\t\tassert(label != null);\n\t\t\treturn label;\n\t\t}\n\n\t\t/** Operand = !label? Check first that {@code isProperLabel() == true}*/\n\t\tpublic boolean isLabelNegated()\n\t\t{\n\t\t\tassert(label != null);\n\t\t\treturn !notNegated;\n\t\t}\n\n\t\t/** Construct a negated version of this OperandInfo */\n\t\tpublic OperandInfo negated()\n\t\t{\n\t\t\treturn new OperandInfo(label, !notNegated);\n\t\t}\n\t}\n\n\t/**\n\t * Construct a prism.DA&lt;BitSet,AcceptanceRabin&gt; for the given until formula.\n\t * The expression is expected to have the form A U B, where\n\t * A and B are either ExpressionLabels or true/false, both possibly negated.\n\t * The operator can have integer bounds.\n\t * @param expr the until formula\n\t * @param constants values for constants (in bounds)\n\t * @param negated create DRA for the complement, i.e., !(A U B)\n\t */\n\tpublic static DA<BitSet,AcceptanceRabin> constructDRAForSimpleUntilFormula(ExpressionTemporal expr, Values constants, boolean negated) throws PrismException\n\t{\n\t\tIntegerBound bounds;\n\t\tDA<BitSet,AcceptanceRabin> dra;\n\n\t\tif (expr.getOperator() != ExpressionTemporal.P_U) {\n\t\t\tthrow new PrismException(\"ConstructDRAForSimpleUntilFormula: Not an Until operator!\");\n\t\t}\n\n\t\t// get and check bounds information (non-negative, non-empty)\n\t\tbounds = IntegerBound.fromExpressionTemporal(expr, constants, true);\n\n\t\t// extract information about the operands of the until operator\n\t\tOperandInfo opA, opB;\n\n\t\topA = OperandInfo.constructFrom(expr.getOperand1());\n\t\topB = OperandInfo.constructFrom(expr.getOperand2());\n\n\t\t// handle the special cases where one of the operands is true / false\n\t\tif (!opA.isProperLabel() && !opB.isProperLabel()) {\n\t\t\t// bool U bool\n\t\t\tboolean untilIsTrue;\n\n\t\t\tif (opB.isFalse()) {\n\t\t\t\t// ? U false <=> false\n\t\t\t\tuntilIsTrue = false;\n\t\t\t} else { // bBoolean == true\n\t\t\t\tif (opA.isTrue()) {\n\t\t\t\t\t// true U true <=> true\n\t\t\t\t\tuntilIsTrue = true;\n\t\t\t\t} else {\n\t\t\t\t\t// false U_bounds true\n\t\t\t\t\t// depends on bound, is true if 0 is in bound, false otherwise\n\t\t\t\t\tuntilIsTrue = bounds.isInBounds(0);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tdra = constructDRAForTrue(null);\n\t\t\tif (!untilIsTrue) {\n\t\t\t\tnegated = !negated;\n\t\t\t}\n\t\t} else if (!opA.isProperLabel()) {\n\t\t\t// first operand is boolean, second is label, bool U B\n\t\t\tif (opA.isTrue()) {\n\t\t\t\t// true U_bounds B <=> F_bounds B\n\t\t\t\tdra = constructDRAForFinally(opB.getLabel(), opB.isLabelNegated(), bounds);\n\t\t\t} else {\n\t\t\t\t// false U_bounds B <=> B in first step and first step in bounds\n\t\t\t\tif (bounds.isInBounds(0)) {\n\t\t\t\t\tdra = constructDRAForInitialStateLabel(opB.getLabel(), opB.isLabelNegated());\n\t\t\t\t} else {\n\t\t\t\t\t// false\n\t\t\t\t\tdra = constructDRAForTrue(opB.getLabel());\n\t\t\t\t\tnegated = !negated;\n\t\t\t\t}\n\t\t\t}\n\t\t} else if (!opB.isProperLabel()) {\n\t\t\t// second operand is boolean, first is label, A U bool\n\t\t\tif (opB.isFalse()) {\n\t\t\t\t// A U false <=> false\n\t\t\t\tdra = constructDRAForTrue(opA.getLabel());\n\t\t\t\tnegated = !negated;\n\t\t\t} else {\n\t\t\t\tif ((!bounds.hasLowerBound()) ||\n\t\t\t\t\t(bounds.isInBounds(0))) {\n\t\t\t\t\t// A U_bounds true <=> true if there is no lower bound\n\t\t\t\t\t// or if lower bound is >=0\n\t\t\t\t\tdra = constructDRAForTrue(opA.getLabel());\n\t\t\t\t} else {\n\t\t\t\t\t//     A U>=lower true\n\t\t\t\t\t// <=> G<lower A\n\t\t\t\t\t// <=> !(F<lower !A)\n\n\t\t\t\t\t// newBounds: >=lower becomes <lower\n\t\t\t\t\tIntegerBound newBounds = new IntegerBound(null, false,\n\t\t\t\t\t                                            bounds.getLowestInteger(), true);\n\t\t\t\t\tdra = constructDRAForFinally(opA.getLabel(), !opA.isLabelNegated(), newBounds);\n\t\t\t\t\tnegated = !negated;\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\t// the general case, A U_bounds B\n\t\t\tdra = constructDRAForUntil(opA.getLabel(), opA.isLabelNegated(),\n\t\t\t                           opB.getLabel(), opB.isLabelNegated(), bounds);\n\t\t}\n\n\t\tif (negated) {\n\t\t\t// the constructed DRAs can be complemented by switching L and K\n\t\t\tBitSet accL = (BitSet) dra.getAcceptance().get(0).getL().clone();\n\t\t\tBitSet accK = (BitSet) dra.getAcceptance().get(0).getK().clone();\n\t\t\t\n\t\t\tdra.getAcceptance().get(0).getL().clear();\n\t\t\tdra.getAcceptance().get(0).getL().or(accK);\n\t\t\t\n\t\t\tdra.getAcceptance().get(0).getK().clear();\n\t\t\tdra.getAcceptance().get(0).getK().or(accL);\n\t\t}\n\t\t\n\t\treturn dra;\n\t}\n\n\t/**\n\t * Construct a DRA for A U_bounds B.\n\t * Can be complemented by switching the acceptance sets.\n\t * @param labelA the label of A\n\t * @param aNegated is A negated?\n\t * @param labelB the label of B\n\t * @param bNegated is B negated?\n\t */\n\tpublic static DA<BitSet, AcceptanceRabin> constructDRAForUntil(String labelA, boolean aNegated, String labelB, boolean bNegated, IntegerBound bounds)\n\t{\n\t\tDA<BitSet, AcceptanceRabin> dra;\n\t\tList<String> apList = new ArrayList<String>();\n\n\t\t/** Edge label for edge where first and second operand are false */\n\t\tBitSet edge_ab = null;\n\t\t/** Edge label for edge where first operand is true and second operand is false */\n\t\tBitSet edge_Ab = null;\n\t\t/** Edge label for edge where first operand is false and second operand is true */\n\t\tBitSet edge_aB = null;\n\t\t/** Edge label for edge where first and second operand are are true */\n\t\tBitSet edge_AB = null;\n\n\t\t/** Set of states contained in L part of Rabin pair */\n\t\tBitSet accL;\n\t\t/** Set of states contained in K part of Rabin pair */\n\t\tBitSet accK;\n\n\t\tint saturation = bounds.getMaximalInterestingValue();\n\n\t\t// Construct states for [0,saturation] + yes + no\n\t\tint states = saturation + 3;\n\n\t\tapList.add(labelA);\n\t\tif (!labelA.equals(labelB)) {\n\t\t\t// if the labels are equal, we only add the AP once\n\t\t\tapList.add(labelB);\n\t\t}\n\n\t\tdra = new DA<BitSet,AcceptanceRabin>(states);\n\t\tdra.setAcceptance(new AcceptanceRabin());\n\t\tdra.setAPList(apList);\n\t\tdra.setStartState(0);\n\n\t\tif (labelA.equals(labelB)) {\n\t\t\t// special treatment if the labels of a and b are the same...\n\t\t\tif (aNegated == bNegated) {\n\t\t\t\tedge_ab = new BitSet();  // !a & !b <=> !a\n\t\t\t\tedge_ab.set(0, aNegated ? true : false);\n\t\t\t\tedge_AB = new BitSet();  //  a &  b <=> a\n\t\t\t\tedge_AB.set(0, aNegated ? false : true);\n\n\t\t\t\t// the other edges are contradictory, we set them to null\n\t\t\t\t// to ensure that they are ignored below\n\t\t\t\tedge_Ab = null;\n\t\t\t\tedge_aB = null;\n\t\t\t} else {\n\t\t\t\tedge_aB = new BitSet();  // !a & b <=> !a\n\t\t\t\tedge_aB.set(0, aNegated ? true : false);\n\t\t\t\tedge_Ab = new BitSet();  //  a & !b <=> a\n\t\t\t\tedge_Ab.set(0, aNegated ? false : true);\n\n\t\t\t\t// the other edges are contradictory, we set them to null\n\t\t\t\t// to ensure that they are ignored below\n\t\t\t}\n\t\t} else {\n\t\t\tedge_ab = new BitSet();  // !a & !b\n\t\t\tedge_ab.set(0, aNegated ? true : false);\n\t\t\tedge_ab.set(1, bNegated ? true : false);\n\t\t\t\n\t\t\tedge_Ab = new BitSet();  //  a & !b\n\t\t\tedge_Ab.set(0, aNegated ? false : true);\n\t\t\tedge_Ab.set(1, bNegated ? true : false);\n\t\t\t\n\t\t\tedge_aB = new BitSet();  // !a &  b\n\t\t\tedge_aB.set(0, aNegated ? true : false);\n\t\t\tedge_aB.set(1, bNegated ? false : true);\n\n\t\t\tedge_AB = new BitSet();  //  a &  b\n\t\t\tedge_AB.set(0, aNegated ? false : true);\n\t\t\tedge_AB.set(1, bNegated ? false : true);\n\t\t}\n\n\t\t// the index of the yes state\n\t\tint yes_state = states - 2;\n\t\t// the index of the no states\n\t\tint no_state = states - 1;\n\n\t\t// generate the counter states for [0..saturation]\n\t\tfor (int counter = 0; counter <= saturation; counter++) {\n\t\t\tint next_counter = counter + 1;\n\t\t\tif (next_counter > saturation) next_counter = saturation;\n\n\t\t\tif (bounds.isInBounds(counter)) {\n\t\t\t\t// B => yes\n\t\t\t\tif (edge_aB != null) dra.addEdge(counter, edge_aB, yes_state);\n\t\t\t\tif (edge_AB != null) dra.addEdge(counter, edge_AB, yes_state);\n\n\t\t\t\t// !A & !B => no\n\t\t\t\tif (edge_ab != null) dra.addEdge(counter, edge_ab, no_state);\n\n\t\t\t\t// A & !B => next_counter\n\t\t\t\tif (edge_Ab != null) dra.addEdge(counter, edge_Ab, next_counter);\n\t\t\t} else {\n\t\t\t\t// !A => no\n\t\t\t\tif (edge_aB != null) dra.addEdge(counter, edge_aB, no_state);\n\t\t\t\tif (edge_ab != null) dra.addEdge(counter, edge_ab, no_state);\n\n\t\t\t\t// A => next_counter\n\t\t\t\tif (edge_Ab != null) dra.addEdge(counter, edge_Ab, next_counter);\n\t\t\t\tif (edge_AB != null) dra.addEdge(counter, edge_AB, next_counter);\n\t\t\t}\n\t\t}\n\n\t\t// yes state = true loop\n\t\tif (edge_ab != null) dra.addEdge(yes_state, edge_ab, yes_state);\n\t\tif (edge_aB != null) dra.addEdge(yes_state, edge_aB, yes_state);\n\t\tif (edge_Ab != null) dra.addEdge(yes_state, edge_Ab, yes_state);\n\t\tif (edge_AB != null) dra.addEdge(yes_state, edge_AB, yes_state);\n\n\t\t// no state = true loop\n\t\tif (edge_ab != null) dra.addEdge(no_state, edge_ab, no_state);\n\t\tif (edge_aB != null) dra.addEdge(no_state, edge_aB, no_state);\n\t\tif (edge_Ab != null) dra.addEdge(no_state, edge_Ab, no_state);\n\t\tif (edge_AB != null) dra.addEdge(no_state, edge_AB, no_state);\n\n\t\t// acceptance =\n\t\t//   infinitely often yes_state,\n\t\t//   not infinitely often no_state or saturation state\n\t\t// this allows complementing by switching L and K.\n\t\taccL = new BitSet();\n\t\taccL.set(no_state);\n\t\taccL.set(saturation);\n\t\taccK = new BitSet();\n\t\taccK.set(yes_state);\n\n\t\tdra.getAcceptance().add(new AcceptanceRabin.RabinPair(accL, accK));\n\n\t\treturn dra;\n\t}\n\n\t/**\n\t * Construct a DRA for LTL formula \"F_bounds a\".\n\t * If {@code negateA == true}, constructs DRA for \"F_bounds !a\".\n\t * Can be complemented by switching the acceptance sets. */\n\tpublic static DA<BitSet,AcceptanceRabin> constructDRAForFinally(String labelA, boolean negateA, IntegerBound bounds)\n\t{\n\t\tDA<BitSet,AcceptanceRabin> dra;\n\t\tList<String> apList = new ArrayList<String>();\n\t\tBitSet edge_no, edge_yes;\n\t\tBitSet accL, accK;\n\n\t\tint saturation = bounds.getMaximalInterestingValue();\n\t\t\n\t\t// [0,saturation] + yes\n\t\tint states = saturation + 2;\n\t\t\n\t\tapList.add(labelA);\n\t\t\n\t\tdra = new DA<BitSet,AcceptanceRabin>(states);\n\t\tdra.setAcceptance(new AcceptanceRabin());\n\t\tdra.setAPList(apList);\n\t\tdra.setStartState(0);\n\t\t\n\t\t// edge labeled with the target label\n\t\tedge_yes  = new BitSet();\n\t\t// edge not labeled with the target label\n\t\tedge_no = new BitSet();\n\t\t\n\t\tif (negateA) {\n\t\t\tedge_no.set(0);  // no = a, yes = !a\n\t\t} else {\n\t\t\tedge_yes.set(0); // yes = a, no = !a\n\t\t}\n\n\t\tint yes_state = states - 1;\n\n\t\tfor (int counter = 0; counter <= saturation; counter++) {\n\t\t\tint next_counter = counter + 1;\n\t\t\tif (next_counter > saturation) next_counter = saturation;\n\t\t\n\t\t\tif (bounds.isInBounds(counter)) {\n\t\t\t\t// yes => yes_state\n\t\t\t\tdra.addEdge(counter, edge_yes, yes_state);\n\t\t\t\n\t\t\t\t// no => next_counter\n\t\t\t\tdra.addEdge(counter, edge_no, next_counter);\n\t\t\t} else {\n\t\t\t\t// true => next_counter\n\t\t\t\tdra.addEdge(counter, edge_no, next_counter);\n\t\t\t\tdra.addEdge(counter, edge_yes, next_counter);\n\t\t\t}\n\t\t}\n\n\t\t// yes state = true loop\n\t\tdra.addEdge(yes_state, edge_no, yes_state);\n\t\tdra.addEdge(yes_state, edge_yes, yes_state);\n\n\t\t// acceptance =\n\t\t//   infinitely often yes_state,\n\t\t//   not infinitely often saturation state\n\t\t// this allows complementing by switching L and K.\n\t\taccL = new BitSet();\n\t\taccL.set(saturation);\n\t\taccK = new BitSet();\n\t\taccK.set(yes_state);\n\n\t\tdra.getAcceptance().add(new RabinPair(accL, accK));\n\n\t\treturn dra;\n\t}\n\n\t/**\n\t * Construct a DRA that always accepts.\n\t * If {@code label == null}, then there is no label, if {@code label != null} then\n\t * there is a single label in the set of atomic propositions.\n\t * Can be complemented by switching the acceptance sets.\n\t */\n\tpublic static DA<BitSet,AcceptanceRabin> constructDRAForTrue(String label) throws PrismException {\n\t\tif (label != null) {\n\t\t\tList<String> labels = new ArrayList<String>();\n\t\t\tlabels.add(label);\n\t\t\treturn createDRAFromString(\"1 states (start 0), 1 labels: 0-{}->0 0-{0}->0; 1 acceptance pairs: ({},{0})\", labels);\n\t\t} else {\n\t\t\treturn createDRAFromString(\"1 states (start 0), 0 labels: 0-{}->0; 1 acceptance pairs: ({},{0})\", new ArrayList<String>());\n\t\t}\n\t}\n\n\t/**\n\t * Construct a DRA that accepts if the first label corresponds to the provided label.\n\t * If {@code negatedLabel == true} then automaton accepts if the word starts with the negated label.\n\t * Can be complemented by switching the acceptance sets.\n\t */\n\tpublic static DA<BitSet,AcceptanceRabin> constructDRAForInitialStateLabel(String label, boolean negatedLabel) throws PrismException {\n\t\tList<String> labels = new ArrayList<String>();\n\t\tlabels.add(label);\n\t\tif (negatedLabel) {\n\t\t\treturn createDRAFromString(\"3 states (start 0), 1 labels: 0-{ }->1 0-{0}->2 1-{0}->1 1-{ }->1 2-{}->2 2-{0}->2; 1 acceptance pairs: ({2},{1})\", labels);\n\t\t} else {\n\t\t\treturn createDRAFromString(\"3 states (start 0), 1 labels: 0-{0}->1 0-{ }->2 1-{ }->1 1-{0}->1 2-{}->2 2-{0}->2; 1 acceptance pairs: ({2},{1})\", labels);\n\t\t}\n\t}\n\n\t/**\n\t * Create a DRA from a string, e.g.:\n\t * \"2 states (start 0), 1 labels: 0-{0}->1 0-{}->0 1-{0}->1 1-{}->0; 1 acceptance pairs: ({},{1})\"\n\t */\n\tprivate static DA<BitSet,AcceptanceRabin> createDRAFromString(String s, List<String> labels) throws PrismException\n\t{\n\t\tint ptr = 0, i, j, k, n, from, to;\n\t\tString bs;\n\t\tDA<BitSet,AcceptanceRabin> draNew;\n\t\tAcceptanceRabin acceptance = new AcceptanceRabin();\n\n\t\ttry {\n\t\t\t// Num states\n\t\t\tj = s.indexOf(\"states\", ptr);\n\t\t\tn = Integer.parseInt(s.substring(0, j).trim());\n\t\t\tdraNew = new DA<BitSet,AcceptanceRabin>(n);\n\t\t\tdraNew.setAcceptance(acceptance);\n\t\t\tdraNew.setAPList(labels);\n\t\t\t// Start state\n\t\t\ti = s.indexOf(\"start\", j) + 6;\n\t\t\tj = s.indexOf(\")\", i);\n\t\t\tn = Integer.parseInt(s.substring(i, j).trim());\n\t\t\tdraNew.setStartState(n);\n\t\t\t// Edges\n\t\t\ti = s.indexOf(\"labels\", j) + 8;\n\t\t\tj = s.indexOf(\"-{\", i);\n\t\t\twhile (j != -1) {\n\t\t\t\tfrom = Integer.parseInt(s.substring(i, j).trim());\n\t\t\t\ti = j + 2;\n\t\t\t\tj = s.indexOf(\"}\", i);\n\t\t\t\tbs = s.substring(i, j);\n\t\t\t\ti = j + 3;\n\t\t\t\tj = Math.min(s.indexOf(\";\", i), s.indexOf(\" \", i));\n\t\t\t\tto = Integer.parseInt(s.substring(i, j).trim());\n\t\t\t\tdraNew.addEdge(from, createBitSetFromString(bs), to);\n\t\t\t\ti = j + 1;\n\t\t\t\tj = s.indexOf(\"-{\", i);\n\t\t\t}\n\t\t\t// Acceptance pairs\n\t\t\ti = s.indexOf(\"({\", i);\n\t\t\twhile (i != -1) {\n\t\t\t\tj = s.indexOf(\"},{\", i);\n\t\t\t\tk = s.indexOf(\"})\", j);\n\t\t\t\tBitSet L = createBitSetFromString(s.substring(i + 2, j));\n\t\t\t\tBitSet K = createBitSetFromString(s.substring(j + 3, k));\n\t\t\t\tacceptance.add(new AcceptanceRabin.RabinPair(L,K));\n\t\t\t\ti = s.indexOf(\"({\", k);\n\t\t\t}\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error in DRA string format\");\n\t\t}\n\n\t\treturn draNew;\n\t}\n\n\t/**\n\t * Create a BitSet from a string, e.g. \"0,3,4\".\n\t */\n\tprivate static BitSet createBitSetFromString(String s) throws PrismException\n\t{\n\t\tint i, n;\n\t\tBitSet bs = new BitSet();\n\t\tString ss[] = s.split(\",\");\n\t\tn = ss.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = ss[i].trim();\n\t\t\tif (s.length() == 0)\n\t\t\t\tcontinue;\n\t\t\tbs.set(Integer.parseInt(s));\n\t\t}\n\t\treturn bs;\n\t}\n\n\t// Example: manual creation of DRA for: !(F (\"L0\"&(X \"L1\")))\n\tpublic static DA<BitSet,AcceptanceRabin> draForNotFaCb(String l0, String l1) throws PrismException\n\t{\n\t\tint numStates;\n\t\tList<String> apList;\n\t\tDA<BitSet,AcceptanceRabin> draNew;\n\n\t\t// 4 states (start 3), 2 labels: 0-{1}->0 0-{0, 1}->1 0-{}->0 0-{0}->1 1-{1}->2 1-{0, 1}->2 1-{}->0 1-{0}->1 2-{1}->2 2-{0, 1}->2 2-{}->2 2-{0}->2 3-{1}->0 3-{0, 1}->1 3-{}->0 3-{0}->1; 1 acceptance pairs: ({2},{0, 1})\n\t\tnumStates = 4;\n\t\tdraNew = new DA<BitSet,AcceptanceRabin>(numStates);\n\t\tdraNew.setAcceptance(new AcceptanceRabin());\n\t\t// AP set\n\t\tapList = new ArrayList<String>(2);\n\t\tapList.add(l0);\n\t\tapList.add(l1);\n\t\tdraNew.setAPList(apList);\n\t\t// Start state\n\t\tdraNew.setStartState(3);\n\t\t// Bitsets for edges\n\t\tBitSet bitset = new BitSet(); // {}\n\t\tBitSet bitset0 = new BitSet(); // {0}\n\t\tbitset0.set(0);\n\t\tBitSet bitset1 = new BitSet(); // {1}\n\t\tbitset1.set(1);\n\t\tBitSet bitset01 = new BitSet(); // {0, 1}\n\t\tbitset01.set(0);\n\t\tbitset01.set(1);\n\t\t// Edges\n\t\t//   3-{}->0 3-{0}->1; 1 acceptance pairs: ({2},{0, 1})\n\t\tdraNew.addEdge(0, bitset1, 0);\n\t\tdraNew.addEdge(0, bitset01, 1);\n\t\tdraNew.addEdge(0, bitset, 0);\n\t\tdraNew.addEdge(0, bitset0, 1);\n\t\tdraNew.addEdge(1, bitset1, 2);\n\t\tdraNew.addEdge(1, bitset01, 2);\n\t\tdraNew.addEdge(1, bitset, 0);\n\t\tdraNew.addEdge(1, bitset0, 1);\n\t\tdraNew.addEdge(2, bitset1, 2);\n\t\tdraNew.addEdge(2, bitset01, 2);\n\t\tdraNew.addEdge(2, bitset, 2);\n\t\tdraNew.addEdge(2, bitset0, 2);\n\t\tdraNew.addEdge(3, bitset1, 0);\n\t\tdraNew.addEdge(3, bitset01, 1);\n\t\tdraNew.addEdge(3, bitset, 0);\n\t\tdraNew.addEdge(3, bitset0, 1);\n\t\t// Acceptance pairs\n\t\tBitSet bitsetL = new BitSet();\n\t\tbitsetL.set(2);\n\t\tBitSet bitsetK = new BitSet();\n\t\tbitsetK.set(01);\n\t\tbitsetK.set(1);\n\t\tdraNew.getAcceptance().add(new AcceptanceRabin.RabinPair(bitsetL, bitsetK));\n\n\t\treturn draNew;\n\t}\n\n\t// To run:\n\t// PRISM_MAINCLASS=prism.LTL2RabinLibrary bin/prism 'G F \"L0\"'\n\tpublic static void main(String args[])\n\t{\n\t\ttry {\n\t\t\tString ltl = args.length > 0 ? args[0] : \"G F \\\"L0\\\"\";\n\n\t\t\t// Convert to Expression\n\t\t\tString pltl = \"P=?[\" + ltl + \"]\";\n\t\t\tPropertiesFile pf = Prism.getPrismParser().parsePropertiesFile(new ModulesFile(), new ByteArrayInputStream(pltl.getBytes()));\n\t\t\tPrism.releasePrismParser();\n\t\t\tExpression expr = pf.getProperty(0);\n\t\t\texpr = ((ExpressionProb) expr).getExpression();\n\n\t\t\tSystem.out.println(ltl);\n\t\t\tSystem.out.println(expr.toString());\n\t\t\tSystem.out.println(ltl.equals(expr.toString()));\n\t\t\tDA<BitSet,AcceptanceRabin> dra1 = jltl2dstar.LTL2Rabin.ltl2rabin(expr.convertForJltl2ba());\n\t\t\tSystem.out.println(dra1);\n\t\t\tDA<BitSet,AcceptanceRabin> dra2 = getDRAforLTL(expr, null);\n\t\t\tif (dra2 == null) {\n\t\t\t    dra2 = jltl2dstar.LTL2Rabin.ltl2rabin(expr.convertForJltl2ba());\n\t\t\t}\n\t\t\tSystem.out.println(dra2);\n\t\t\tSystem.out.println(dra1.toString().equals(dra2.toString()));\n\t\t\t//dra2.printDot(new PrintStream(new File(\"dra\")));\n\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.print(\"Error: \" + e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/automata/LTL2WDBA.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage automata;\n\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.LinkedList;\nimport java.util.Queue;\nimport java.util.Stack;\n\nimport jltl2ba.APElement;\nimport jltl2ba.LTLFragments;\nimport jltl2ba.MyBitSet;\nimport jltl2ba.SimpleLTL;\nimport jltl2dstar.NBA;\nimport prism.PrismComponent;\nimport prism.PrismDevNullLog;\nimport prism.PrismException;\nimport acceptance.AcceptanceBuchi;\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceReach;\n\nimport common.IterableBitSet;\n\nimport explicit.LTS;\nimport explicit.LTSSimple;\nimport explicit.NonProbModelChecker;\nimport explicit.SCCComputer;\nimport explicit.SCCConsumerStore;\n\n/**\n * <p>\n * Construction of weak Deterministic Büchi Automata for\n * a fragment of LTL, based on the algorithm presented in\n * Christian Dax, Jochen Eisinger, Felix Klaedtke:\n * <a href=\"https://doi.org/10.1007/978-3-540-75596-8_17\">\n * \"Mechanizing the Powerset Construction for Restricted\n *  Classes of omega-Automata\"</a>,\n * ATVA 2007, LNCS 4762.\n * </p>\n * <p>\n * The approach works as follows: First, we construct a\n * DBA via a standard power set construction of the NBA\n * for the LTL formula. Then, for the suitable fragment of LTL,\n * it is guaranteed that either all states in a SCC in the DA\n * can be made accepting or all can be made non-accepting (the\n * \"weakness\" property of the DBA).\n * </p>\n * <p>\n * Using the algorithm described in\n * Christof Löding:\n * <a href=\"https://doi.org/10.1016/S0020-0190(00)00183-6\">\n * \"Efficient minimization of deterministic weak omega-automata\"</a>,\n * Inf. Process. Lett. 79(3), 2001,\n * it is then possible to obtain a minimal automaton for the language\n * via a DFA-based minimisation.\n * </p>\n * <p>\n * This minimisation step is not yet included, but will\n * be added in the future. Currently, we are using this\n * construction to obtain DAs with AcceptanceReach that\n * are suitable for the model checking of co-safety rewards.\n * For further details, see Sec. 4 of\n * Joachim Klein et al:\n * <a href=\"https://doi.org/10.1007/s10009-017-0456-3\">\n * \"Advances in probabilistic model checking with PRISM:\n *  variable reordering, quantiles and weak deterministic\n *  Büchi automata\"</a>, International Journal on Software\n *  Tools for Technology Transfer, 2017.\n * </p>\n * <p>TODO: Optimise for performance</p>\n */\npublic class LTL2WDBA extends PrismComponent\n{\n\t/** Constructor */\n\tpublic LTL2WDBA(PrismComponent parent)\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * For a co-safe LTL formula, construct a DFA (i.e., a DA with AcceptanceReach)\n\t * with the additional property that every state that accepts the full language\n\t * is accepting, i.e., that state s in F iff s |= Sigma^omega.\n\t * <br>\n\t * Note: Does not check if the formula is actually syntactically cosafe, it is the responsibility\n\t * of the caller to ensure that the formula corresponds to a cosafe language.\n\t * @param ltl the ltl formula, has to\n\t * @return a DA with AcceptanceReach\n\t */\n\tpublic DA<BitSet, AcceptanceReach> cosafeltl2dfa(SimpleLTL ltl) throws PrismException\n\t{\n\t\t// construct DBA using the powerset-based construction\n\t\tDA<BitSet, AcceptanceBuchi> wdba = ltl2wdba(ltl);\n\n\t\tBitSet F = wdba.getAcceptance().getAcceptingStates();\n\t\tBitSet notF = (BitSet) F.clone();\n\t\tnotF.flip(0, wdba.size());\n\n\t\t// Now, to satisfy that s in F iff s |= Sigma^omega, we determine\n\t\t// the set of states that can not avoid reaching an F state, as\n\t\t// those are the states that will accept any word\n\t\tLTS lts = new LTSFromDA(wdba);\n\t\tNonProbModelChecker ctlMC = new NonProbModelChecker(this);\n\t\tctlMC.setLog(new PrismDevNullLog());  // quietly\n\t\tBitSet canAvoidF = ctlMC.computeExistsGlobally(lts, notF);\n\t\tBitSet canNotAvoidF = (BitSet)canAvoidF.clone();\n\t\tcanNotAvoidF.flip(0, wdba.size());\n\n\t\t// As the result, we construct the DFA on the transition structure\n\t\t// of the wdba, with goal states = canNotAvoidF\n\t\tDA<BitSet, AcceptanceReach> dfa = toDFA(wdba, canNotAvoidF);\n\t\t//dfa.printDot(System.out);\n\t\treturn dfa;\n\t}\n\n\t/**\n\t * For an LTL formula in the obligation fragment, return a WDBA.\n\t * @param ltl the LTL formula\n\t * @return a weak deterministic Büchi automaton\n\t */\n\tpublic DA<BitSet, AcceptanceBuchi> obligation2wdba(SimpleLTL ltl) throws PrismException\n\t{\n\t\treturn ltl2wdba(ltl);\n\t}\n\n\t/**\n\t * Generate DFA (i.e., DA with AcceptanceReach) with the underlying transition\n\t * structure of {@code da}. The set of goal states should be upward closed,\n\t * i.e., once a goal state has been reached, all successor states should\n\t * be goal states as well.\n\t * <br>\n\t * Note: {@code da} is destroyed during the transformation\n\t * and should not be used afterwards.\n\t * @param da the DA\n\t * @param goalStates the set of goalStates for the DFA.\n\t * @return\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprivate DA<BitSet, AcceptanceReach> toDFA(DA<BitSet, ? extends AcceptanceOmega> da, BitSet goalStates)\n\t{\n\t\tAcceptanceReach reach = new AcceptanceReach(goalStates);\n\t\tDA.switchAcceptance(da, reach);\n\t\treturn (DA<BitSet, AcceptanceReach>) da;\n\t}\n\n\t/**\n\t * Perform the power set construction as described in\n\t * \"Mechanizing the Powerset Construction for Restricted Classes of omega-Automata\",\n\t * and determine whether the SCCs of the resulting automaton should be accepting\n\t * or non-accepting.\n\t * <br>\n\t * The resulting WDBA is only equivalent to the language of the LTL formula\n\t * if the language of the LTL formula is WDBA-realizable.\n\t * @param ltl the LTL formula.\n\t * @return a weak deterministich Büchi automaton.\n\t */\n\tprivate DA<BitSet, AcceptanceBuchi> ltl2wdba(SimpleLTL ltl) throws PrismException\n\t{\n\t\tltl = ltl.simplify();\n\n\t\tNBA nba = ltl.toNBA();\n\t\tPowersetDA P = powersetConstruction(nba);\n\t\tdetermineF(P);\n\n\t\treturn P.da;\n\t}\n\n\t/**\n\t * Storage for a DA resulting from the powerset\n\t * construction on an NBA;\n\t */\n\tprivate static class PowersetDA\n\t{\n\t\t/** The original NBA */\n\t\tpublic NBA nba;\n\n\t\t/** The DBA */\n\t\tpublic DA<BitSet, AcceptanceBuchi> da;\n\n\t\t/**\n\t\t * The set of states in the DBA where at least\n\t\t * one of the corresponding NBA states is accepting.\n\t\t */\n\t\tpublic MyBitSet powersetOneF;\n\n\t\t/**\n\t\t * The set of states in the DBA where all\n\t\t * of the corresponding NBA states are accepting.\n\t\t */\n\t\tpublic MyBitSet powersetAllF;\n\n\t\t/** Mapping DBA state index to the set of NBA states */\n\t\tpublic ArrayList<BitSet> idToState;\n\n\t\t/** The accepting states of the DBA */\n\t\tpublic BitSet F = new BitSet();\n\t}\n\n\t/** Perform powerset construction on the NBA */\n\tprivate PowersetDA powersetConstruction(NBA nba) throws PrismException\n\t{\n\t\t//System.out.println(\"--- NBA ---\");\n\t\t//nba.print_hoa(System.out);\n\t\tDA<BitSet, AcceptanceBuchi> da = new DA<BitSet, AcceptanceBuchi>();\n\t\tda.setAcceptance(new AcceptanceBuchi());\n\n\t\tHashMap<BitSet,Integer> stateToId = new HashMap<BitSet,Integer>();\n\t\tArrayList<BitSet> idToState = new ArrayList<BitSet>();\n\n\t\tMyBitSet nbaF = nba.getFinalStates();\n\t\tMyBitSet powersetOneF = new MyBitSet();\n\t\tMyBitSet powersetAllF = new MyBitSet();\n\n\t\tQueue<Integer> todo = new LinkedList<Integer>();\n\t\tBitSet initialState = new BitSet();\n\t\tinitialState.set(nba.getStartState().getName());\n\t\tint initialId = da.addState();\n\t\tstateToId.put(initialState, initialId);\n\t\tidToState.add(initialState);\n\t\ttodo.add(initialId);\n\t\tda.setStartState(initialId);\n\t\tda.setAPList(new ArrayList<String>(nba.getAPSet().asList()));\n\n\t\tif (initialState.intersects(nbaF)) {\n\t\t\tpowersetOneF.set(initialId);\n\t\t}\n\t\tif (nbaF.containsAll(initialState)) {\n\t\t\tpowersetAllF.set(initialId);\n\t\t}\n\n\t\t//System.out.println(\"new: \"+initialId+\" \"+initialState);\n\n\t\tBitSet visited = new BitSet();\n\t\twhile (!todo.isEmpty()) {\n\t\t\tint curId = todo.poll();\n\t\t\tif (visited.get(curId)) continue;\n\n\t\t\tBitSet cur = idToState.get(curId);\n\t\t\t//System.out.println(\"Expand \"+curId+\" \"+cur);\n\n\t\t\tfor (APElement e : nba.getAPSet().elements()) {\n\t\t\t\tBitSet to = new BitSet();\n\t\t\t\tfor (int f : IterableBitSet.getSetBits(cur)) {\n\t\t\t\t\tto.or(nba.get(f).getEdge(e));\n\t\t\t\t}\n\n\t\t\t\tInteger toId = stateToId.get(to);\n\t\t\t\tif (toId == null) {\n\t\t\t\t\ttoId = da.addState();\n\t\t\t\t\tstateToId.put(to, toId);\n\t\t\t\t\tidToState.add(to);\n\t\t\t\t\ttodo.add(toId);\n\n\t\t\t\t\t//System.out.println(\"new: \"+toId+\" \"+to);\n\n\t\t\t\t\tif (to.intersects(nbaF)) {\n\t\t\t\t\t\tpowersetOneF.set(toId);\n\t\t\t\t\t}\n\t\t\t\t\tif (nbaF.containsAll(to)) {\n\t\t\t\t\t\tpowersetAllF.set(toId);\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t//System.out.println(\" delta(\" + curId + \", \" + e + \") = \" + toId);\n\t\t\t\tda.addEdge(curId, e, toId);\n\t\t\t}\n\t\t}\n\n\t\t//da.printHOA(System.out);\n\n\t\tPowersetDA result = new PowersetDA();\n\t\tresult.nba = nba;\n\t\tresult.da = da;\n\t\tresult.idToState = idToState;\n\t\tresult.powersetOneF = powersetOneF;\n\t\tresult.powersetAllF = powersetAllF;\n\t\t//System.out.println(\"powersetOneF = \"+powersetOneF);\n\t\t//System.out.println(\"powersetAllF = \"+powersetAllF);\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Analyse the SCCs of the DA obtained by the power set construction,\n\t * whether they should be accepting or rejecting.\n\t * @param P the DA\n\t */\n\tprivate void determineF(final PowersetDA P) throws PrismException\n\t{\n\t\tLTS daLTS = new LTSFromDA(P.da);\n\n\t\tSCCConsumerStore sccStore = new SCCConsumerStore();\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, daLTS, sccStore);\n\t\tsccComputer.computeSCCs();\n\t\tfor (BitSet scc : sccStore.getSCCs()) {\n\t\t\tif (hasAcceptingCycle(P, scc)) {\n\t\t\t\t// mark all SCC states as final in powerset automaton\n\t\t\t\tP.F.or(scc);\n\t\t\t}\n\t\t}\n\n\t\t// construct acceptance\n\t\tP.da.getAcceptance().setAcceptingStates(P.F);\n\t}\n\n\t/**\n\t * Check whether the given SCC of the DBA has an accepting cycle\n\t * in the underlying NBA.\n\t * @param P the powerset DBA\n\t * @param scc an SCC of P\n\t */\n\tprivate boolean hasAcceptingCycle(PowersetDA P, BitSet scc) throws PrismException\n\t{\n\t\t//System.out.println(\"hasAcceptingCycle \"+scc+\"?\");\n\t\t if (!scc.intersects(P.powersetOneF)) {\n\t\t\t// none of the NBA states in this powerset SCC are final\n\t\t\t//System.out.println(\" -> no (none final)\");\n\t\t\treturn false;\n\t\t}\n\t\tif (P.powersetAllF.containsAll(scc)) {\n\t\t\t// all NBA states in this powerset SCC are final\n\t\t\t//System.out.println(\" -> yes (all final)\");\n\t\t\treturn true;\n\t\t}\n\n\t\t// first, construct an arbitrary lasso in P, remaining\n\t\t// in the SCC\n\t\tLasso lasso = findLasso(P, scc);\n\t\t//System.out.println(cycle);\n\n\t\t// second, construct the NBA fragment corresponding to the\n\t\t// lasso\n\t\tfinal BuchiLTS buchilts = buildLTSforLasso(P, lasso);\n\t\t// String name = \"lts\"+scc+\".dot\";\n\t\t// buchilts.lts.exportToDotFile(name, p.F);\n\t\t//System.out.println(\"DOT: \"+name);\n\n\t\t// perform cycle check\n\t\t// TODO: use nested-DFS?\n\t\tboolean hasCycleViaF = false;\n\t\tSCCConsumerStore sccStore = new SCCConsumerStore();\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, buchilts.lts, sccStore);\n\t\tsccComputer.computeSCCs();\n\t\tfor (BitSet subSCC : sccStore.getSCCs()) {\n\t\t\tif (subSCC.intersects(buchilts.F)) {\n\t\t\t\thasCycleViaF = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\t//System.out.println(hasCycleViaF ? \" -> yes\" : \" -> no\");\n\t\treturn hasCycleViaF;\n\t}\n\n\t/** A lasso, i.e., an infinite word uw^omega */\n\tprivate static class Lasso {\n\t\tLinkedList<APElement> word;\n\t\t/** start of the w fragment */\n\t\tint cycleStart;\n\n\t\tpublic String toString()\n\t\t{\n\t\t\tString s = \"Cycle starting at \"+cycleStart+\" with \";\n\t\t\ts+= word.toString();\n\t\t\treturn s;\n\t\t}\n\t}\n\n\t/** Construct an arbitrary lasso inside the SCC of the DA */\n\tprivate Lasso findLasso(PowersetDA P, BitSet scc) throws PrismException\n\t{\n\t\t// pick a start state\n\t\tint R = scc.nextSetBit(0);\n\n\t\tStack<Integer> states = new Stack<Integer>();\n\t\tStack<BitSet> letters = new Stack<BitSet>();\n\t\tBitSet onStack = new BitSet();\n\n\t\tstates.push(R);\n\t\tonStack.set(R);\n\n\t\tfinal DA<BitSet, AcceptanceBuchi> da = P.da;\n\n\t\twhile (true) {\n\t\t\tint cur = states.peek();\n\t\t\t// find first letter that allows remaining in SCC\n\t\t\tint n = da.getNumEdges(cur);\n\t\t\tboolean found = false;\n\t\t\tint to = -1;\n\t\t\tfor (int i=0; i<n; i++) {\n\t\t\t\tto = P.da.getEdgeDest(cur, i);\n\t\t\t\tif (scc.get(to)) {\n\t\t\t\t\tBitSet letter = da.getEdgeLabel(cur, i);\n\t\t\t\t\tletters.add(letter);\n\t\t\t\t\tstates.add(to);\n\t\t\t\t\tfound = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!found) {\n\t\t\t\tthrow new PrismException(\"Implementation error in findCycle\");\n\t\t\t}\n\n\t\t\tif (!onStack.get(to)) {\n\t\t\t\t// not yet a cycle\n\t\t\t\tonStack.set(to);\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\t// found a cycle\n\t\t\tint cycleStart = to;\n\t\t\tLasso cycle = new Lasso();\n\t\t\tcycle.word = new LinkedList<APElement>();\n\t\t\tcycle.cycleStart = cycleStart;\n\n\t\t\tdo {\n\t\t\t\tAPElement label = new APElement();\n\t\t\t\tlabel.or(letters.pop());\n\t\t\t\tcycle.word.addFirst(label);\n\t\t\t\tstates.pop();\n\t\t\t} while (states.peek() != to);\n\n\t\t\treturn cycle;\n\t\t}\n\t}\n\n\tprivate static class LassoLTSState\n\t{\n\t\tint nbaState;\n\t\tint cyclePos;\n\n\t\tLassoLTSState(int nbaState, int cyclePos)\n\t\t{\n\t\t\tthis.nbaState = nbaState;\n\t\t\tthis.cyclePos = cyclePos;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn \"(\"+nbaState+\",\"+cyclePos+\")\";\n\t\t}\n\n\t\t@Override\n\t\tpublic int hashCode()\n\t\t{\n\t\t\tfinal int prime = 31;\n\t\t\tint result = 1;\n\t\t\tresult = prime * result + cyclePos;\n\t\t\tresult = prime * result + nbaState;\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(Object obj)\n\t\t{\n\t\t\tif (this == obj)\n\t\t\t\treturn true;\n\t\t\tif (obj == null)\n\t\t\t\treturn false;\n\t\t\tLassoLTSState other = (LassoLTSState) obj;\n\t\t\tif (cyclePos != other.cyclePos)\n\t\t\t\treturn false;\n\t\t\tif (nbaState != other.nbaState)\n\t\t\t\treturn false;\n\t\t\treturn true;\n\t\t}\n\t}\n\n\tprivate static class BuchiLTS\n\t{\n\t\tLTS lts;\n\t\tBitSet F;\n\t}\n\n\t/** Build an LTS for the NBA fragment corresponding to the lasso in the DBA. */\n\tprivate BuchiLTS buildLTSforLasso(PowersetDA p, Lasso lasso)\n\t{\n\t\tHashMap<LassoLTSState, Integer> stateToIndex = new HashMap<LassoLTSState, Integer>();\n\t\tArrayList<LassoLTSState> indexToState = new ArrayList<LassoLTSState>();\n\n\t\tStack<Integer> todo = new Stack<Integer>();\n\t\tBitSet expanded = new BitSet();\n\t\tBitSet F = new BitSet();\n\n\t\tLTSSimple lts = new LTSSimple();\n\n\t\tfor (int startNBA : IterableBitSet.getSetBits(p.idToState.get(lasso.cycleStart))) {\n\t\t\tint i = lts.addState();\n\t\t\ttodo.push(i);\n\t\t\tLassoLTSState s = new LassoLTSState(startNBA, 0);\n\t\t\tstateToIndex.put(s, i);\n\t\t\tindexToState.add(s);\n\t\t\tif (p.nba.get(startNBA).isFinal()) {\n\t\t\t\tF.set(i);\n\t\t\t}\n\n\t\t\t//System.out.println(\"new: \" + i + \" = \"+ s);\n\t\t}\n\n\t\twhile (!todo.isEmpty()) {\n\t\t\tint curProd = todo.pop();\n\t\t\tif (expanded.get(curProd)) continue;\n\n\t\t\tLassoLTSState cur = indexToState.get(curProd);\n\t\t\t// expand\n\t\t\t//System.out.println(\"Expand \"+curProd+\" = \"+cur);\n\t\t\tAPElement letter = lasso.word.get(cur.cyclePos);\n\t\t\tMyBitSet toSet = p.nba.get(cur.nbaState).getEdge(letter);\n\t\t\tint cyclePos = (cur.cyclePos+1) % lasso.word.size();\n\n\t\t\tfor (int to : toSet) {\n\t\t\t\tLassoLTSState toProd = new LassoLTSState(to, cyclePos);\n\t\t\t\tInteger prodTo = stateToIndex.get(toProd);\n\t\t\t\tif (prodTo == null) {\n\t\t\t\t\tprodTo = lts.addState();\n\t\t\t\t\ttodo.push(prodTo);\n\t\t\t\t\tstateToIndex.put(toProd, prodTo);\n\t\t\t\t\tindexToState.add(toProd);\n\n\t\t\t\t\tif (p.nba.get(to).isFinal()) {\n\t\t\t\t\t\tF.set(prodTo);\n\t\t\t\t\t}\n\n\t\t\t\t\t//System.out.println(\"new: \" + prodTo + \" = \" +toProd);\n\t\t\t\t}\n\n\t\t\t\tlts.addTransition(curProd, prodTo);\n\t\t\t\t//System.out.println(\" \" + curProd +\" -> \" +prodTo);\n\t\t\t}\n\t\t}\n\n\t\tBuchiLTS result = new BuchiLTS();\n\t\tresult.lts = lts;\n\t\tresult.F = F;\n\t\treturn result;\n\t}\n\n\n\t/**\n\t * Simple test method: convert LTL formula (in LBT format) to HOA/Dot/txt\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\ttry {\n\t\t\t// Usage:\n\t\t\t// * ... 'X p1'\n\t\t\t// * ... 'X p1' da.hoa\n\t\t\t// * ... 'X p1' da.hoa hoa\n\t\t\t// * ... 'X p1' da.dot dot\n\t\t\t// * ... 'X p1' - hoa\n\t\t\t// * ... 'X p1' - txt\n\n\t\t\t// Convert to Expression (from LBT format)\n\t\t\tSimpleLTL sltl = SimpleLTL.parseFormulaLBT(args[0]);\n\n\t\t\t// Build/export DA\n\t\t\tPrismComponent parent = new PrismComponent();\n\t\t\tparent.setLog(new PrismDevNullLog());\n\t\t\tLTL2WDBA ltl2wdba = new LTL2WDBA(parent);\n\t\t\tLTLFragments tl = LTLFragments.analyse(sltl);\n\n\t\t\tDA<BitSet, ? extends AcceptanceOmega> da;\n\t\t\tif (tl.isSyntacticGuarantee()) {\n\t\t\t\tda = ltl2wdba.cosafeltl2dfa(sltl);\n\t\t\t} else if (tl.isSyntacticObligation()) {\n\t\t\t\tda = ltl2wdba.obligation2wdba(sltl);\n\t\t\t} else {\n\t\t\t\tthrow new Exception(\"Can not construct an automaton for \" + sltl +\", not syntactically co-safe or obligation\");\n\t\t\t}\n\t\t\tPrintStream out = (args.length < 2 || \"-\".equals(args[1])) ? System.out : new PrintStream(args[1]);\n\t\t\tString format = (args.length < 3) ? \"hoa\" : args[2];\n\t\t\tda.print(out, format);\n\n\t\t} catch (Exception e) {\n\t\t\te.printStackTrace();\n\t\t\tSystem.err.println(\"Error: \" + e + \".\");\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/automata/LTSFromDA.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n// * Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage automata;\n\nimport java.util.BitSet;\n\nimport explicit.LTS;\nimport explicit.Model;\nimport explicit.ModelExplicit;\nimport explicit.SuccessorsIterator;\nimport prism.ModelType;\nimport prism.PrismException;\nimport strat.MDStrategy;\n\n/**\n * Class giving access to the labelled transition system (LTS) underlying a deterministic automaton (DA).\n * This is not particularly efficient; we assume the DA will probably be relatively small.\n */\npublic class LTSFromDA<Value> extends ModelExplicit<Value> implements LTS<Value>\n{\n\t/** Underlying DA */\n\tprivate DA<?, ?> da;\n\n\tpublic LTSFromDA(DA<?, ?> da)\n\t{\n\t\tthis.numStates = da.size();\n\t\tthis.da = da;\n\t}\n\n\t// Methods to implement Model\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(int s)\n\t{\n\t\treturn new SuccessorsIterator() {\n\t\t\tprivate int n = da.getNumEdges(s);\n\t\t\tprivate int i = 0;\n\n\t\t\t@Override\n\t\t\tpublic boolean successorsAreDistinct()\n\t\t\t{\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn i < n;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\treturn da.getEdgeDest(s, i++);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t@Override\n\tpublic void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn ModelType.LTS;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions()\n\t{\n\t\tint size = da.size();\n\t\tint num = 0;\n\t\tfor (int s = 0; s < size; s++) {\n\t\t\tnum += da.getNumEdges(s);\n\t\t}\n\t\treturn num;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s)\n\t{\n\t\treturn da.getNumEdges(s);\n\t}\n\n\t@Override\n\tpublic boolean isSuccessor(int s1, int s2)\n\t{\n\t\tint n = da.getNumEdges(s1);\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (da.getEdgeDest(s1, i) == s2) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t// Methods to implement NondetModel\n\n\t@Override\n\tpublic int getNumChoices(int s)\n\t{\n\t\treturn da.getNumEdges(s);\n\t}\n\n\t@Override\n\tpublic int getMaxNumChoices()\n\t{\n\t\tint size = da.size();\n\t\tint max = 0;\n\t\tfor (int s = 0; s < size; s++) {\n\t\t\tmax = Math.max(max, da.getNumEdges(s));\n\t\t}\n\t\treturn max;\n\t}\n\n\t@Override\n\tpublic int getNumChoices()\n\t{\n\t\treturn getNumTransitions();\n\t}\n\n\t@Override\n\tpublic Object getAction(int s, int i)\n\t{\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s, int i)\n\t{\n\t\treturn 1;\n\t}\n\n\t@Override\n\tpublic boolean allSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn set.get(da.getEdgeDest(s, i));\n\t}\n\n\t@Override\n\tpublic boolean someSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn set.get(da.getEdgeDest(s, i));\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(int s, int i)\n\t{\n\t\treturn SuccessorsIterator.fromSingleton(da.getEdgeDest(s, i));\n\t}\n\n\t@Override\n\tpublic Model<Value> constructInducedModel(MDStrategy<Value> strat)\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\t\n\t// Methods to implement LTS\n\t\n\t@Override\n\tpublic int getSuccessor(int s, int i)\n\t{\n\t\treturn da.getEdgeDest(s, i); \n\t}\n}\n"
  },
  {
    "path": "prism/src/bin/prism.bat.win",
    "content": "@echo off\r\n\r\nrem Startup script for PRISM (Windows)\r\n\r\nrem PRISM home directory\r\nrem Default is .. so it can be run directly from the bin directory.\r\nrem Change \"..\" to the actual PRISM directory to allow it to be run from anywhere.\r\nrem An example would be: set PRISM_DIR=c:\\Program Files\\prism-3.2\r\nrem Note: Do not put quotes (\"...\") around the path.\r\nset PRISM_DIR=..\r\n\r\nrem Add PRISM to path\r\npath=%PRISM_DIR%\\lib;%path%\r\n\r\nrem Set up CLASSPATH:\r\nrem  - PRISM jar file (for binary versions) (gets priority)\r\nrem  - classes directory (most PRISM classes)\r\nrem  - top-level directory (for images, dtds)\r\nrem  - lib/pepa.zip (PEPA stuff)\r\nrem  - lib/*.jar (all other jars)\r\nset CP=%PRISM_DIR%\\lib\\prism.jar;%PRISM_DIR%\\classes;%PRISM_DIR%;%PRISM_DIR%\\lib\\pepa.zip;%PRISM_DIR%\\lib\\*\r\n\r\nrem Run PRISM through Java\r\njava -Xss4M -Djava.library.path=\"%PRISM_DIR%\\lib\" -classpath \"%CP%\" prism.PrismCL %*\r\n"
  },
  {
    "path": "prism/src/bin/prism.cygwin",
    "content": "#!/bin/sh\n\n# Startup script for PRISM (Linux/Solaris)\n\n# PRISM home directory\nPRISM_DIR=/home/luser/prism\n\n# Command to launch Java\nPRISM_JAVA=${PRISM_JAVA:-java}\n\n#### Java heap size handling (either via -javamaxmem argument or PRISM_JAVAMAXMEM environment variable)\n\n# If there is a -javamaxmem switch, use it for PRISM_JAVAMAXMEM\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javamaxmem\" -o \"${ARGS[$i]}\" = \"--javamaxmem\" ]; then\n\t\tPRISM_JAVAMAXMEM=${ARGS[$i+1]}\n\t\tPRISM_JAVAMAXMEM=`echo \"$PRISM_JAVAMAXMEM\" | awk /^[0-9]+[kmg]?$/`\n\t\tif [ \"$PRISM_JAVAMAXMEM\" = \"\" ]; then\n\t\t\techo; echo \"Error: Invalid value for -javamaxmem switch.\"; exit\n\t\tfi\n\tfi\ndone\n\n# Max memory for Java\nif [ \"$PRISM_JAVAMAXMEM\" != \"\" ]; then\n\tPRISM_JAVAMAXMEM=`echo \"$PRISM_JAVAMAXMEM\" | awk /^[0-9]+[kmg]?$/`\n\tif [ \"$PRISM_JAVAMAXMEM\" = \"\" ]; then\n\t\techo; echo \"Error: Environment variable PRISM_JAVAMAXMEM is invalid.\"; exit\n\tfi\n\tPRISM_JAVAMAXMEM=\"-Xmx$PRISM_JAVAMAXMEM\"\nfi\n\n#### Java stack size handling (either via -javastack argument or PRISM_JAVASTACKSIZE environment variable)\n\n# If there is a -javastack switch, use it for PRISM_JAVASTACKSIZE\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javastack\" -o \"${ARGS[$i]}\" = \"--javastack\" ]; then\n\t\tPRISM_JAVASTACKSIZE=${ARGS[$i+1]}\n\t\tPRISM_JAVASTACKSIZE=`echo \"$PRISM_JAVASTACKSIZE\" | awk /^[0-9]+[kmg]?$/`\n\t\tif [ \"$PRISM_JAVASTACKSIZE\" = \"\" ]; then\n\t\t\techo; echo \"Error: Invalid value for -javastack switch.\"; exit\n\t\tfi\n\tfi\ndone\n\n# Stack size for Java\nif [ \"$PRISM_JAVASTACKSIZE\" != \"\" ]; then\n\tPRISM_JAVASTACKSIZE=`echo \"$PRISM_JAVASTACKSIZE\" | awk /^[0-9]+[kmg]?$/`\n\tif [ \"$PRISM_JAVASTACKSIZE\" = \"\" ]; then\n\t\techo; echo \"Error: Environment variable PRISM_JAVASTACKSIZE is invalid.\"; exit\n\tfi\n\tPRISM_JAVASTACKSIZE=\"-Xss$PRISM_JAVASTACKSIZE\"\nelse\n\t# default (4 MB)\n\tPRISM_JAVASTACKSIZE=\"-Xss4m\"\nfi\n\n####\n\n# Add JVM parameters for JNI (if Java is new enough)\nPRISM_JAVA_VERSION=$(java -version 2>&1 | awk -F '\"' '/version/ {print $2}')\nPRISM_JAVA_VERSION_MAJOR=$(echo \"$PRISM_JAVA_VERSION\" | cut -d. -f1)\nif [ \"$PRISM_JAVA_VERSION_MAJOR\" -ge 17 ]; then\n\tPRISM_JAVA_PARAMS=${PRISM_JAVA_PARAMS}${PRISM_JAVA_PARAMS:+ }\"--enable-native-access=ALL-UNNAMED\"\nfi\n\n# JVM parameters via -javaparams switch\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javaparams\" -o \"${ARGS[$i]}\" = \"--javaparams\" ]; then\n\t\tPRISM_JAVA_PARAMS=${PRISM_JAVA_PARAMS}${PRISM_JAVA_PARAMS:+ }${ARGS[$i+1]}\n\tfi\ndone\n\n# Detect -javaversion switch\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javaversion\" -o \"${ARGS[$i]}\" = \"--javaversion\" ]; then\n\t\tPRISM_PRINT_JAVA_VERSION=yes\n\tfi\ndone\n\n# Set up CLASSPATH:\n#  - PRISM jar file (for binary versions) (gets priority)\n#  - classes directory (most PRISM classes)\n#  - top-level directory (for images, dtds)\n#  - lib/pepa.zip (PEPA stuff)\n#  - lib/*.jar (all other jars)\nPRISM_CLASSPATH=\"$PRISM_DIR\"/lib/prism.jar:\"$PRISM_DIR\"/classes:\"$PRISM_DIR\":\"$PRISM_DIR\"/lib/pepa.zip:\"$PRISM_DIR\"/lib/*\n\n# Set up pointers to libraries\nPRISM_LIB_PATH=\"$PRISM_DIR\"/lib\n\n# Copy library path to relevant vars\nPATH=\"${PRISM_LIB_PATH}${PATH:+:}${PATH}\"\nJAVA_LIBRARY_PATH=\"$PRISM_LIB_PATH\"\n\n# Export environment variables\nexport PRISM_DIR PATH\n\n# Main Java class to launch\nPRISM_MAINCLASS=${PRISM_MAINCLASS:-prism.PrismCL}\n\n# Do we run headless? (GUI overrides this)\nPRISM_HEADLESS=${PRISM_HEADLESS:-true}\n\n# Convert paths to Windows form\nPRISM_CLASSPATH_WIN=`cygpath -wp $\"$PRISM_CLASSPATH\"`\nJAVA_LIBRARY_PATH_WIN=`cygpath -wp \"$JAVA_LIBRARY_PATH\"`\n\n# If debugging enabled, set up vars accordingly\nif [ \"$PRISM_DEBUG\" != \"\" ]; then\n\tPRISM_JAVA_ARG1=\"$PRISM_JAVA\"\n\tPRISM_JAVA_ARG2=\"$PRISM_DEBUG_ARG\"\n\tPRISM_JAVA=\"$PRISM_DEBUG\"\nfi\n\n# If requested, just print the version of Java and exit\nif [ \"$PRISM_PRINT_JAVA_VERSION\" = \"yes\" ]; then\n\t\"$PRISM_JAVA\" -version && exit\nfi\n\n#\n# If environment variable PRISM_NO_EXEC is set to 'yes', use old method of starting Java.\n# The default method is to use an exec call.\n#\nif [ \"$PRISM_NO_EXEC\" = \"yes\" ]; then\n\t# Run PRISM through Java as a child process (exit code of script is exit code of the java call)\n\t# Note: Killing this startup script will not necessarily kill the Java process\n\t\"$PRISM_JAVA\" $PRISM_JAVA_ARG1 $PRISM_JAVA_ARG2 $PRISM_JAVA_DEBUG $PRISM_JAVA_PARAMS $PRISM_JAVAMAXMEM $PRISM_JAVASTACKSIZE -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=\"$JAVA_LIBRARY_PATH_WIN\" -classpath \"$PRISM_CLASSPATH_WIN\" $PRISM_MAINCLASS \"$@\"\nelse\n\t# (Default) Run PRISM through Java via an exec call (the shell process is replaced by the Java process)\n\texec \"$PRISM_JAVA\" $PRISM_JAVA_ARG1 $PRISM_JAVA_ARG2 $PRISM_JAVA_DEBUG $PRISM_JAVA_PARAMS $PRISM_JAVAMAXMEM $PRISM_JAVASTACKSIZE -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=\"$JAVA_LIBRARY_PATH_WIN\" -classpath \"$PRISM_CLASSPATH_WIN\" $PRISM_MAINCLASS \"$@\"\nfi\n\n"
  },
  {
    "path": "prism/src/bin/prism.darwin",
    "content": "#!/bin/sh\n\n# Startup script for PRISM (Mac OS X)\n\n# PRISM home directory\nPRISM_DIR=/home/luser/prism\n\n# Command to launch Java\nif [ \"$PRISM_JAVA\" = \"\" ]; then\n\tPRISM_JAVA=java\n\t# On OS X, we want to avoiding calling java from the /usr/bin link\n\t# since it causes problems with dynamic linking (DYLD_LIBRARY_PATH)\n\tif $(which java | grep -q '^/usr/bin'); then\n\t\tif [ -x /usr/libexec/java_home ]; then\n\t\t\tPRISM_JAVA=`/usr/libexec/java_home`\"/bin/java\"\n\t\tfi\n\tfi\nfi\n\n#### Java heap size handling (either via -javamaxmem argument or PRISM_JAVAMAXMEM environment variable)\n\n# If there is a -javamaxmem switch, use it for PRISM_JAVAMAXMEM\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javamaxmem\" -o \"${ARGS[$i]}\" = \"--javamaxmem\" ]; then\n\t\tPRISM_JAVAMAXMEM=${ARGS[$i+1]}\n\t\tPRISM_JAVAMAXMEM=`echo \"$PRISM_JAVAMAXMEM\" | awk /^[0-9]+[kmg]?$/`\n\t\tif [ \"$PRISM_JAVAMAXMEM\" = \"\" ]; then\n\t\t\techo; echo \"Error: Invalid value for -javamaxmem switch.\"; exit\n\t\tfi\n\tfi\ndone\n\n# Max memory for Java\nif [ \"$PRISM_JAVAMAXMEM\" != \"\" ]; then\n\tPRISM_JAVAMAXMEM=`echo \"$PRISM_JAVAMAXMEM\" | awk /^[0-9]+[kmg]?$/`\n\tif [ \"$PRISM_JAVAMAXMEM\" = \"\" ]; then\n\t\techo; echo \"Error: Environment variable PRISM_JAVAMAXMEM is invalid.\"; exit\n\tfi\n\tPRISM_JAVAMAXMEM=\"-Xmx$PRISM_JAVAMAXMEM\"\nfi\n\n#### Java stack size handling (either via -javastack argument or PRISM_JAVASTACKSIZE environment variable)\n\n# If there is a -javastack switch, use it for PRISM_JAVASTACKSIZE\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javastack\" -o \"${ARGS[$i]}\" = \"--javastack\" ]; then\n\t\tPRISM_JAVASTACKSIZE=${ARGS[$i+1]}\n\t\tPRISM_JAVASTACKSIZE=`echo \"$PRISM_JAVASTACKSIZE\" | awk /^[0-9]+[kmg]?$/`\n\t\tif [ \"$PRISM_JAVASTACKSIZE\" = \"\" ]; then\n\t\t\techo; echo \"Error: Invalid value for -javastack switch.\"; exit\n\t\tfi\n\tfi\ndone\n\n# Stack size for Java\nif [ \"$PRISM_JAVASTACKSIZE\" != \"\" ]; then\n\tPRISM_JAVASTACKSIZE=`echo \"$PRISM_JAVASTACKSIZE\" | awk /^[0-9]+[kmg]?$/`\n\tif [ \"$PRISM_JAVASTACKSIZE\" = \"\" ]; then\n\t\techo; echo \"Error: Environment variable PRISM_JAVASTACKSIZE is invalid.\"; exit\n\tfi\n\tPRISM_JAVASTACKSIZE=\"-Xss$PRISM_JAVASTACKSIZE\"\nelse\n\t# default (4 MB)\n\tPRISM_JAVASTACKSIZE=\"-Xss4m\"\nfi\n\n####\n\n# Add JVM parameters for JNI (if Java is new enough)\nPRISM_JAVA_VERSION=$(java -version 2>&1 | awk -F '\"' '/version/ {print $2}')\nPRISM_JAVA_VERSION_MAJOR=$(echo \"$PRISM_JAVA_VERSION\" | cut -d. -f1)\nif [ \"$PRISM_JAVA_VERSION_MAJOR\" -ge 17 ]; then\n\tPRISM_JAVA_PARAMS=${PRISM_JAVA_PARAMS}${PRISM_JAVA_PARAMS:+ }\"--enable-native-access=ALL-UNNAMED\"\nfi\n\n# JVM parameters via -javaparams switch\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javaparams\" -o \"${ARGS[$i]}\" = \"--javaparams\" ]; then\n\t\tPRISM_JAVA_PARAMS=${PRISM_JAVA_PARAMS}${PRISM_JAVA_PARAMS:+ }${ARGS[$i+1]}\n\tfi\ndone\n\n# Detect -javaversion switch\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javaversion\" -o \"${ARGS[$i]}\" = \"--javaversion\" ]; then\n\t\tPRISM_PRINT_JAVA_VERSION=yes\n\tfi\ndone\n\n# Set up CLASSPATH:\n#  - PRISM jar file (for binary versions) (gets priority)\n#  - classes directory (most PRISM classes)\n#  - top-level directory (for images, dtds)\n#  - lib/pepa.zip (PEPA stuff)\n#  - lib/*.jar (all other jars)\nPRISM_CLASSPATH=\"$PRISM_DIR\"/lib/prism.jar:\"$PRISM_DIR\"/classes:\"$PRISM_DIR\":\"$PRISM_DIR\"/lib/pepa.zip:\"$PRISM_DIR\"/lib/*\n\n# Set up pointers to libraries\nPRISM_LIB_PATH=\"$PRISM_DIR\"/lib\n\n# Copy library path to relevant vars\n#DYLD_LIBRARY_PATH=\"${PRISM_LIB_PATH}${DYLD_LIBRARY_PATH:+:}${DYLD_LIBRARY_PATH}\"\nJAVA_LIBRARY_PATH=\"$PRISM_LIB_PATH\"\n\n# Export environment variables\nexport PRISM_DIR\n# export LD_LIBRARY_PATH\n\n# Main Java class to launch\nPRISM_MAINCLASS=${PRISM_MAINCLASS:-prism.PrismCL}\n\n# Do we run headless? (GUI overrides this)\nPRISM_HEADLESS=${PRISM_HEADLESS:-true}\n\nPRISM_ICON=\"-Xdock:icon=$PRISM_DIR/etc/icons/p64.png\"\nPRISM_DOCK_NAME=\"-Xdock:name=PRISM\"\n\n# If debugging enabled, set up vars accordingly\nif [ \"$PRISM_DEBUG\" != \"\" ]; then\n\tPRISM_JAVA_ARG1=\"$PRISM_JAVA\"\n\tPRISM_JAVA_ARG2=\"$PRISM_DEBUG_ARG\"\n\tPRISM_JAVA=\"$PRISM_DEBUG\"\nfi\n\n# If requested, just print the version of Java and exit\nif [ \"$PRISM_PRINT_JAVA_VERSION\" = \"yes\" ]; then\n\t\"$PRISM_JAVA\" -version && exit\nfi\n\n#\n# If environment variable PRISM_NO_EXEC is set to 'yes', use old method of starting Java.\n# The default method is to use an exec call.\n#\nif [ \"$PRISM_NO_EXEC\" = \"yes\" ]; then\n\t# Run PRISM through Java as a child process (exit code of script is exit code of the java call)\n\t# Note: Killing this startup script will not necessarily kill the Java process\n\t\"$PRISM_JAVA\" $PRISM_JAVA_ARG1 $PRISM_JAVA_ARG2 $PRISM_JAVA_DEBUG $PRISM_JAVA_PARAMS $PRISM_JAVAMAXMEM $PRISM_JAVASTACKSIZE \"$PRISM_ICON\" \"$PRISM_DOCK_NAME\" -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=\"$JAVA_LIBRARY_PATH\" -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"\nelse\n\t# (Default) Run PRISM through Java via an exec call (the shell process is replaced by the Java process)\n\texec \"$PRISM_JAVA\" $PRISM_JAVA_ARG1 $PRISM_JAVA_ARG2 $PRISM_JAVA_DEBUG $PRISM_JAVA_PARAMS $PRISM_JAVAMAXMEM $PRISM_JAVASTACKSIZE \"$PRISM_ICON\" \"$PRISM_DOCK_NAME\" -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=\"$JAVA_LIBRARY_PATH\" -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"\nfi\n\n"
  },
  {
    "path": "prism/src/bin/prism.linux",
    "content": "#!/bin/bash\n\n# Startup script for PRISM (Linux/Solaris)\n\n# PRISM home directory\nPRISM_DIR=/home/luser/prism\n\n# Command to launch Java\nPRISM_JAVA=${PRISM_JAVA:-java}\n\n#### Java heap size handling (either via -javamaxmem argument or PRISM_JAVAMAXMEM environment variable)\n\n# If there is a -javamaxmem switch, use it for PRISM_JAVAMAXMEM\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javamaxmem\" -o \"${ARGS[$i]}\" = \"--javamaxmem\" ]; then\n\t\tPRISM_JAVAMAXMEM=${ARGS[$i+1]}\n\t\tPRISM_JAVAMAXMEM=`echo \"$PRISM_JAVAMAXMEM\" | awk /^[0-9]+[kmg]?$/`\n\t\tif [ \"$PRISM_JAVAMAXMEM\" = \"\" ]; then\n\t\t\techo; echo \"Error: Invalid value for -javamaxmem switch.\"; exit\n\t\tfi\n\tfi\ndone\n\n# Max memory for Java\nif [ \"$PRISM_JAVAMAXMEM\" != \"\" ]; then\n\tPRISM_JAVAMAXMEM=`echo \"$PRISM_JAVAMAXMEM\" | awk /^[0-9]+[kmg]?$/`\n\tif [ \"$PRISM_JAVAMAXMEM\" = \"\" ]; then\n\t\techo; echo \"Error: Environment variable PRISM_JAVAMAXMEM is invalid.\"; exit\n\tfi\n\tPRISM_JAVAMAXMEM=\"-Xmx$PRISM_JAVAMAXMEM\"\nfi\n\n#### Java stack size handling (either via -javastack argument or PRISM_JAVASTACKSIZE environment variable)\n\n# If there is a -javastack switch, use it for PRISM_JAVASTACKSIZE\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javastack\" -o \"${ARGS[$i]}\" = \"--javastack\" ]; then\n\t\tPRISM_JAVASTACKSIZE=${ARGS[$i+1]}\n\t\tPRISM_JAVASTACKSIZE=`echo \"$PRISM_JAVASTACKSIZE\" | awk /^[0-9]+[kmg]?$/`\n\t\tif [ \"$PRISM_JAVASTACKSIZE\" = \"\" ]; then\n\t\t\techo; echo \"Error: Invalid value for -javastack switch.\"; exit\n\t\tfi\n\tfi\ndone\n\n# Stack size for Java\nif [ \"$PRISM_JAVASTACKSIZE\" != \"\" ]; then\n\tPRISM_JAVASTACKSIZE=`echo \"$PRISM_JAVASTACKSIZE\" | awk /^[0-9]+[kmg]?$/`\n\tif [ \"$PRISM_JAVASTACKSIZE\" = \"\" ]; then\n\t\techo; echo \"Error: Environment variable PRISM_JAVASTACKSIZE is invalid.\"; exit\n\tfi\n\tPRISM_JAVASTACKSIZE=\"-Xss$PRISM_JAVASTACKSIZE\"\nelse\n\t# default (4 MB)\n\tPRISM_JAVASTACKSIZE=\"-Xss4m\"\nfi\n\n####\n\n# Add JVM parameters for JNI (if Java is new enough)\nPRISM_JAVA_VERSION=$(java -version 2>&1 | awk -F '\"' '/version/ {print $2}')\nPRISM_JAVA_VERSION_MAJOR=$(echo \"$PRISM_JAVA_VERSION\" | cut -d. -f1)\nif [ \"$PRISM_JAVA_VERSION_MAJOR\" -ge 17 ]; then\n\tPRISM_JAVA_PARAMS=${PRISM_JAVA_PARAMS}${PRISM_JAVA_PARAMS:+ }\"--enable-native-access=ALL-UNNAMED\"\nfi\n\n# JVM parameters via -javaparams switch\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javaparams\" -o \"${ARGS[$i]}\" = \"--javaparams\" ]; then\n\t\tPRISM_JAVA_PARAMS=${PRISM_JAVA_PARAMS}${PRISM_JAVA_PARAMS:+ }${ARGS[$i+1]}\n\tfi\ndone\n\n# Detect -javaversion switch\nARGS=( \"$@\" )\nfor ((i=0;i<${#ARGS[@]};i+=1)); do\n\tif [ \"${ARGS[$i]}\" = \"-javaversion\" -o \"${ARGS[$i]}\" = \"--javaversion\" ]; then\n\t\tPRISM_PRINT_JAVA_VERSION=yes\n\tfi\ndone\n\n# Set up CLASSPATH:\n#  - PRISM jar file (for binary versions) (gets priority)\n#  - classes directory (most PRISM classes)\n#  - top-level directory (for images, dtds)\n#  - lib/pepa.zip (PEPA stuff)\n#  - lib/*.jar (all other jars)\nPRISM_CLASSPATH=\"$PRISM_DIR\"/lib/prism.jar:\"$PRISM_DIR\"/classes:\"$PRISM_DIR\":\"$PRISM_DIR\"/lib/pepa.zip:\"$PRISM_DIR\"/lib/*\n\n# Set up pointers to libraries\nPRISM_LIB_PATH=\"$PRISM_DIR\"/lib\n\n# Copy library path to relevant vars\n#LD_LIBRARY_PATH=\"${PRISM_LIB_PATH}${LD_LIBRARY_PATH:+:}${LD_LIBRARY_PATH}\"\nJAVA_LIBRARY_PATH=\"$PRISM_LIB_PATH\"\n\n# Export environment variables\nexport PRISM_DIR\n# export LD_LIBRARY_PATH\n\n# Main Java class to launch\nPRISM_MAINCLASS=${PRISM_MAINCLASS:-prism.PrismCL}\n\n# Do we run headless? (GUI overrides this)\nPRISM_HEADLESS=${PRISM_HEADLESS:-true}\n\n# If debugging enabled, set up vars accordingly\nif [ \"$PRISM_DEBUG\" != \"\" ]; then\n\tPRISM_JAVA_ARG1=\"$PRISM_JAVA\"\n\tPRISM_JAVA_ARG2=\"$PRISM_DEBUG_ARG\"\n\tPRISM_JAVA=\"$PRISM_DEBUG\"\nfi\n\n# If requested, just print the version of Java and exit\nif [ \"$PRISM_PRINT_JAVA_VERSION\" = \"yes\" ]; then\n\t\"$PRISM_JAVA\" -version && exit\nfi\n\n#\n# If environment variable PRISM_NO_EXEC is set to 'yes', use old method of starting Java.\n# The default method is to use an exec call.\n#\nif [ \"$PRISM_NO_EXEC\" = \"yes\" ]; then\n\t# Run PRISM through Java as a child process (exit code of script is exit code of the java call)\n\t# Note: Killing this startup script will not necessarily kill the Java process\n\t\"$PRISM_JAVA\" $PRISM_JAVA_ARG1 $PRISM_JAVA_ARG2 $PRISM_JAVA_DEBUG $PRISM_JAVA_PARAMS $PRISM_JAVAMAXMEM $PRISM_JAVASTACKSIZE -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=\"$JAVA_LIBRARY_PATH\" -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"\nelse\n\t# (Default) Run PRISM through Java via an exec call (the shell process is replaced by the Java process)\n\texec \"$PRISM_JAVA\" $PRISM_JAVA_ARG1 $PRISM_JAVA_ARG2 $PRISM_JAVA_DEBUG $PRISM_JAVA_PARAMS $PRISM_JAVAMAXMEM $PRISM_JAVASTACKSIZE -Djava.awt.headless=$PRISM_HEADLESS -Djava.library.path=\"$JAVA_LIBRARY_PATH\" -classpath \"$PRISM_CLASSPATH\" $PRISM_MAINCLASS \"$@\"\nfi\n\n"
  },
  {
    "path": "prism/src/bin/xprism.bat.win",
    "content": "@echo off\r\n\r\nrem Startup script for PRISM (Windows)\r\necho Loading PRISM...\r\n\r\nrem PRISM home directory\r\nrem Default is .. so it can be run directly from the bin directory.\r\nrem An example would be: set PRISM_DIR=c:\\Program Files\\prism-3.2\r\nrem Note: Do not put quotes (\"...\") around the path.\r\nset PRISM_DIR=..\r\n\r\nrem Add PRISM to path\r\npath=%PRISM_DIR%\\lib;%path%\r\n\r\nrem Set up CLASSPATH:\r\nrem  - PRISM jar file (for binary versions) (gets priority)\r\nrem  - classes directory (most PRISM classes)\r\nrem  - top-level directory (for images, dtds)\r\nrem  - lib/pepa.zip (PEPA stuff)\r\nrem  - lib/*.jar (all other jars)\r\nset CP=%PRISM_DIR%\\lib\\prism.jar;%PRISM_DIR%\\classes;%PRISM_DIR%;%PRISM_DIR%\\lib\\pepa.zip;%PRISM_DIR%\\lib\\*\r\n\r\nrem Run PRISM through Java\r\nstart \"PRISM\" javaw -Xmx1g -Xss4M -Djava.library.path=\"%PRISM_DIR%\\lib\" -classpath \"%CP%\" userinterface/GUIPrism %*\r\nexit"
  },
  {
    "path": "prism/src/bin/xprism.linux",
    "content": "#!/bin/sh\n\n# Startup script for PRISM GUI (Linux/Solaris)\n\n# PRISM home directory\nPRISM_DIR=/home/luser/prism\n\n# Launch using main PRISM script\nPRISM_MAINCLASS=userinterface.GUIPrism\nPRISM_HEADLESS=false\nexport PRISM_MAINCLASS PRISM_HEADLESS\n\"$PRISM_DIR\"/bin/prism \"$@\"\n"
  },
  {
    "path": "prism/src/cex/CexPathAsBDDs.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage cex;\n\nimport java.util.ArrayList;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport parser.State;\nimport simulator.PathFullInfo;\nimport symbolic.model.Model;;\n\n/**\n * Class to store a counterexample/witness comprising a single path, as a list of BDDs.\n * The basic contents of the path is is a sequence of states (BDDs).\n * Optionally, action labels can also be included.\n */\npublic class CexPathAsBDDs implements PathFullInfo\n{\n\tprotected Model model;\n\tprotected ArrayList<JDDNode> states;\n\n\t/**\n\t * Construct empty path.\n\t */\n\tpublic CexPathAsBDDs(Model model)\n\t{\n\t\tthis.model = model;\n\t\tstates = new ArrayList<JDDNode>();\n\t}\n\n\t/**\n\t * Add a state to the path (as a BDD, which will be stored and Ref'ed).\n\t */\n\tpublic void addState(JDDNode state)\n\t{\n\t\tJDD.Ref(state);\n\t\tstates.add(state);\n\t}\n\n\t/**\n\t * Clear the counterexample.\n\t */\n\tpublic void clear()\n\t{\n\t\tfor (JDDNode dd : states) {\n\t\t\tJDD.Deref(dd);\n\t\t}\n\t}\n\n\t// ACCESSORS (for PathFullInfo)\n\t\n\t@Override\n\tpublic long size()\n\t{\n\t\treturn states.size() - 1;\n\t}\n\t\n\t@Override\n\tpublic State getState(int step)\n\t{\n\t\treturn model.convertBddToState(states.get(step));\n\t}\n\t\n\t@Override\n\tpublic State getObservation(int step)\n\t{\n\t\treturn null;\n\t}\n\t\n\t@Override\n\tpublic double getStateReward(int step, int rsi)\n\t{\n\t\treturn 0.0;\n\t}\n\n\t@Override\n\tpublic int getStrategyMemory(int step)\n\t{\n\t\treturn -1;\n\t}\n\t\n\t@Override\n\tpublic Object getStrategyDecision(int step)\n\t{\n\t\treturn null;\n\t}\n\t\n\t@Override\n\tpublic double getCumulativeTime(int step)\n\t{\n\t\treturn 0.0;\n\t}\n\n\t@Override\n\tpublic double getCumulativeReward(int step, int rsi)\n\t{\n\t\treturn 0.0;\n\t}\n\n\t@Override\n\tpublic double getTime(int step)\n\t{\n\t\treturn 0.0;\n\t}\n\n\t@Override\n\tpublic int getChoice(int step)\n\t{\n\t\treturn 0;\n\t}\n\n\t@Override\n\tpublic Object getAction(int step)\n\t{\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic String getActionString(int step)\n\t{\n\t\treturn \"\";\n\t}\n\n\t@Override\n\tpublic double getTransitionReward(int step, int rsi)\n\t{\n\t\treturn 0.0;\n\t}\n\t\n\t@Override\n\tpublic boolean isLooping()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic long loopStart()\n\t{\n\t\treturn 0;\n\t}\n\t\n\t@Override\n\tpublic long loopEnd()\n\t{\n\t\treturn 0;\n\t}\n\t\n\t@Override\n\tpublic boolean hasRewardInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean hasChoiceInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean hasActionInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean hasTimeInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean hasLoopInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t// Standard method\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tState state;\n\t\tint i, n;\n\t\tString s = \"\";\n\t\tn = states.size();\n\t\tfor (i = 0; i < n; i++) { \n\t\t\tstate = model.convertBddToState(states.get(i));\n\t\t\ts += state.toString();\n\t\t\tif (i < n - 1)\n\t\t\t\ts += \"\\n\";\n\t\t}\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/cex/CexPathStates.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage cex;\n\nimport java.util.ArrayList;\n\nimport parser.State;\nimport simulator.PathFullInfo;\nimport symbolic.model.Model;;\n\n/**\n * Class to store a counterexample/witness comprising a single path,\n * represented as a list of states, stored as State objects. \n */\npublic class CexPathStates implements PathFullInfo\n{\n\tprotected Model model;\n\tprotected ArrayList<State> states;\n\n\t/**\n\t * Construct empty path.\n\t */\n\tpublic CexPathStates(Model model)\n\t{\n\t\tthis.model = model;\n\t\tstates = new ArrayList<State>();\n\t}\n\n\t/**\n\t * Add a state to the path (will be stored, not copied).\n\t */\n\tpublic void addState(State state)\n\t{\n\t\tstates.add(state);\n\t}\n\n\t/**\n\t * Clear the counterexample.\n\t */\n\tpublic void clear()\n\t{\n\t\tstates = null;\n\t}\n\n\t// ACCESSORS (for PathFullInfo)\n\t\n\t@Override\n\tpublic long size()\n\t{\n\t\treturn states.size() - 1;\n\t}\n\t\n\t@Override\n\tpublic State getState(int step)\n\t{\n\t\treturn states.get(step);\n\t}\n\t\n\t@Override\n\tpublic State getObservation(int step)\n\t{\n\t\treturn null;\n\t}\n\t\n\t@Override\n\tpublic double getStateReward(int step, int rsi)\n\t{\n\t\treturn 0.0;\n\t}\n\n\t@Override\n\tpublic int getStrategyMemory(int step)\n\t{\n\t\treturn -1;\n\t}\n\t\n\t@Override\n\tpublic Object getStrategyDecision(int step)\n\t{\n\t\treturn null;\n\t}\n\t\n\t@Override\n\tpublic double getCumulativeTime(int step)\n\t{\n\t\treturn 0.0;\n\t}\n\n\t@Override\n\tpublic double getCumulativeReward(int step, int rsi)\n\t{\n\t\treturn 0.0;\n\t}\n\n\t@Override\n\tpublic double getTime(int step)\n\t{\n\t\treturn 0.0;\n\t}\n\n\t@Override\n\tpublic int getChoice(int step)\n\t{\n\t\treturn 0;\n\t}\n\n\t@Override\n\tpublic Object getAction(int step)\n\t{\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic String getActionString(int step)\n\t{\n\t\treturn \"\";\n\t}\n\n\t@Override\n\tpublic double getTransitionReward(int step, int rsi)\n\t{\n\t\treturn 0.0;\n\t}\n\t\n\t@Override\n\tpublic boolean isLooping()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic long loopStart()\n\t{\n\t\treturn 0;\n\t}\n\t\n\t@Override\n\tpublic long loopEnd()\n\t{\n\t\treturn 0;\n\t}\n\t\n\t@Override\n\tpublic boolean hasRewardInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean hasChoiceInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean hasActionInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean hasTimeInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean hasLoopInfo()\n\t{\n\t\treturn false;\n\t}\n\t\n\t// Standard method\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tState state;\n\t\tint i, n;\n\t\tString s = \"\";\n\t\tn = states.size();\n\t\tfor (i = 0; i < n; i++) { \n\t\t\tstate = states.get(i);\n\t\t\ts += state.toString();\n\t\t\tif (i < n - 1)\n\t\t\t\ts += \"\\n\";\n\t\t}\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/IntSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\nimport java.util.BitSet;\nimport java.util.Objects;\nimport java.util.PrimitiveIterator;\nimport java.util.Spliterator;\nimport java.util.Spliterators;\nimport java.util.function.IntPredicate;\nimport java.util.stream.IntStream;\nimport java.util.stream.StreamSupport;\n\nimport common.IterableBitSet;\nimport common.iterable.FunctionalPrimitiveIterable;\nimport common.iterable.FunctionalPrimitiveIterator;\nimport common.iterable.SingletonIterable;\n\n/**\n * Interface for an ordered set of integers that allows efficient\n * (1) iteration (normal and reversed order)\n * and (2) efficient tests of set membership.\n * <br>\n * Provides static helpers for wrapping a BitSet or a singleton value.\n */\npublic interface IntSet extends FunctionalPrimitiveIterable.OfInt\n{\n\t/** Return a FunctionalPrimitiveIterator.OfInt iterator for iteration, reversed order */\n\tFunctionalPrimitiveIterator.OfInt reversedIterator();\n\n\t/** Return the cardinality (number of elements) for this set */\n\tdefault long cardinality()\n\t{\n\t\treturn count();\n\t}\n\n\t/**\n\t * Return true if {@code index} is a member of this set\n\t * (convenience method to ease migration from use of BitSet).\n\t * <p>\n\t * <i>Default implementation</i>: Calls contains(index).\n\t */\n\tdefault boolean get(int index)\n\t{\n\t\treturn contains(index);\n\t}\n\n\t/**\n\t * Return true if this set contains the {@code other}\n\t * set.\n\t * <p>\n\t * <i>Default implementation</i>:\n\t * Tests via contains for all elements of other.\n\t */\n\tdefault boolean contains(IntSet other)\n\t{\n\t\treturn other.allMatch((IntPredicate) this::contains);\n\t}\n\n\t/**\n\t * Return true if this set contains the {@code other}\n\t * set.\n\t * <p>\n\t * <i>Default implementation</i>:\n\t * Uses contains(IntSet other).\n\t */\n\tdefault boolean contains(BitSet other)\n\t{\n\t\treturn contains(asIntSet(other));\n\t}\n\n\t/**\n\t * Produce an IntStream for this set.\n\t * <p>\n\t * <i>Default implementation</i>:\n\t * Wrap iterator() into an intStream.\n\t */\n\tdefault IntStream stream()\n\t{\n\t\treturn StreamSupport.intStream(\n\t\t\t\t() -> spliterator(),\n\t\t\t\tSpliterator.SIZED | Spliterator.DISTINCT,\n\t\t\t\tfalse);\n\t}\n\n\t@Override\n\tdefault Spliterator.OfInt spliterator()\n\t{\n\t\treturn Spliterators.spliterator(\n\t\t\t\titerator(),\n\t\t\t\tcardinality(),\n\t\t\t\tSpliterator.SIZED | Spliterator.DISTINCT);\n\t}\n\n\t/** Return this set as a String */\n\t@Override\n\tdefault String asString()\n\t{\n\t\t// can't overload toString() with a default method in interface\n\t\tStringBuffer sb = new StringBuffer();\n\t\tsb.append(\"{\");\n\t\tboolean first = true;\n\t\tfor (PrimitiveIterator.OfInt it = iterator(); it.hasNext(); ) {\n\t\t\tif (!first)\n\t\t\t\tsb.append(\",\");\n\t\t\tfirst = false;\n\t\t\tsb.append(it.nextInt());\n\t\t}\n\t\tsb.append(\"}\");\n\t\treturn sb.toString();\n\t}\n\n\n\n\t/**\n\t * Wrapper class for obtaining an IntSet from a BitSet.\n\t * <p>\n\t * Note: The BitSet should not be modified as long as the\n\t * derived IntSet is in use.\n\t */\n\tstatic class IntSetFromBitSet implements IntSet\n\t{\n\t\t/** The wrapped BitSet */\n\t\tprotected BitSet bs;\n\t\t/** The cardinality of the underlying BitSet (cached, -1 = not yet computed) */\n\t\tint cardinality = -1;\n\n\t\t/** Constructor */\n\t\tpublic IntSetFromBitSet(BitSet bs)\n\t\t{\n\t\t\tObjects.requireNonNull(bs);\n\t\t\tthis.bs = bs;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t\t{\n\t\t\treturn IterableBitSet.getSetBits(bs).iterator();\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt reversedIterator()\n\t\t{\n\t\t\treturn IterableBitSet.getSetBitsReversed(bs).iterator();\n\t\t}\n\n\t\t@Override\n\t\tpublic IntStream stream()\n\t\t{\n\t\t\treturn bs.stream();\n\t\t}\n\n\t\t@Override\n\t\tpublic long count()\n\t\t{\n\t\t\t// not yet computed?\n\t\t\tif (cardinality == -1)\n\t\t\t\tcardinality = bs.cardinality();\n\n\t\t\treturn cardinality;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(int index)\n\t\t{\n\t\t\treturn bs.get(index);\n\t\t}\n\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn asString();\n\t\t}\n\t};\n\n\n\n\t/** Convenience class for simulating a singleton set */\n\tstatic class SingletonIntSet extends SingletonIterable.OfInt implements IntSet\n\t{\n\t\t/**\n\t\t * Constructor.\n\t\t * @param singleMember the single member of this set\n\t\t */\n\t\tpublic SingletonIntSet(int singleMember)\n\t\t{\n\t\t\tsuper(singleMember);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt reversedIterator()\n\t\t{\n\t\t\t// iteration order does not matter for singleton set\n\t\t\treturn iterator();\n\t\t}\n\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn \"{\" + element + \"}\";\n\t\t}\n\t}\n\n\t/**\n\t * Factory method for obtaining an IntSet from a BitSet\n\t * <p>\n\t * Note: The BitSet should not be modified as long as the derived IntSet is in use.\n\t *\n\t * @param bs The underlying BitSet\n\t */\n\tstatic IntSet asIntSet(BitSet bs)\n\t{\n\t\treturn new IntSetFromBitSet(bs);\n\t}\n\n\t/**\n\t * Factory method for obtaining an IntSet for a singleton set.\n\t *\n\t * @param singleMember The single member of the singleton set\n\t */\n\tstatic IntSet asIntSet(int singleMember)\n\t{\n\t\treturn new SingletonIntSet(singleMember);\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/Interval.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\n/**\n * This class stores an interval of numerical values.\n */\npublic class Interval<Value>\n{\n\t// Lower/upper value\n\tprivate Value lower;\n\tprivate Value upper;\n\n\t/**\n\t * Construct an Interval.\n\t */\n\tpublic Interval(Value lower, Value upper)\n\t{\n\t\tthis.lower = lower;\n\t\tthis.upper = upper;\n\t}\n\t\n\tpublic void setLower(Value lower)\n\t{\n\t\tthis.lower = lower;\n\t}\n\n\tpublic void setUpper(Value upper)\n\t{\n\t\tthis.upper = upper;\n\t}\n\n\tpublic Value getLower()\n\t{\n\t\treturn lower;\n\t}\n\n\tpublic Value getUpper()\n\t{\n\t\treturn upper;\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + lower + \",\" + upper + \"]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/IterableBitSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\nimport java.util.BitSet;\nimport java.util.NoSuchElementException;\nimport java.util.Objects;\n\nimport common.iterable.FunctionalPrimitiveIterable;\nimport common.iterable.FunctionalPrimitiveIterator;\n\n/**\n * Convenience class to loop easily over the set/clear bits of a BitSet.\n *\n * For example:<br/><br/>\n * <code>for (Integer index : getSetBits(set)) { ... }</code><br/>\n */\npublic class IterableBitSet implements FunctionalPrimitiveIterable.OfInt\n{\n\tprotected final BitSet set;\n\tprotected final boolean clearBits;\n\tprotected final boolean reversed;\n\tprotected final int maxIndex;\n\n\t/**\n\t * Constructor for an Iterable that iterates over the set bits of {@code set}\n\t *\n\t * @param set the underlying BitSet\n\t */\n\tpublic IterableBitSet(BitSet set)\n\t{\n\t\tthis(set, null, false, false);\n\t}\n\n\t/**\n\t * Constructor for an Iterable that iterates over bits of the given set {@code set},\n\t * up to the maximal index given by {@code maxIndex} (optional).\n\t * If {@code clearBits} is {@code true}, iterate over the cleared bits instead of the set bits\n\t * (requires {@code maxIndex} to be non-null).\n\t * @param set the underlying BitSet\n\t * @param maxIndex the maximal index for iteration (negative = iterate over the empty set, {@code null} = no restrictions)\n\t * @param clearBits if true, iterate over the cleared bits in the BitSet\n\t */\n\tpublic IterableBitSet(BitSet set, Integer maxIndex, boolean clearBits)\n\t{\n\t\tthis(set, maxIndex, clearBits, false);\n\t}\n\n\t/**\n\t * Constructor for an Iterable that iterates over bits of the given set {@code set},\n\t * up to the maximal index given by {@code maxIndex} (optional).\n\t * If {@code clearBits} is {@code true}, iterate over the cleared bits instead of the set bits\n\t * (requires {@code maxIndex} to be non-null).\n\t * If {@code reversed} is set, iterate in reverse order (highest to lowest).\n\t * @param set the underlying BitSet\n\t * @param maxIndex the maximal index for iteration (negative = iterate over the empty set, {@code null} = no restrictions)\n\t * @param clearBits if true, iterate over the cleared bits in the BitSet\n\t * @param reversed if true, iterate in reversed order\n\t */\n\tpublic IterableBitSet(BitSet set, Integer maxIndex, boolean clearBits, boolean reversed)\n\t{\n\t\tObjects.requireNonNull(set);\n\t\tthis.set = set;\n\t\tthis.maxIndex = maxIndex == null ? Integer.MAX_VALUE : Math.max(maxIndex, -1);\n\t\tthis.clearBits = clearBits;\n\t\tthis.reversed = reversed;\n\t}\n\n\t/** Implementation of the iterator over the set bits */\n\tprivate class SetBitsIterator implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\tprivate int current = -1;\n\t\tprivate int next = set.nextSetBit(0);\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\tif (next > maxIndex) {\n\t\t\t\t// limit to 0 ... maxIndex\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\treturn next >= 0;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tif (hasNext()) {\n\t\t\t\tcurrent = next;\n\t\t\t\t// mind potential overflow\n\t\t\t\tint from = current + 1;\n\t\t\t\tnext = from < 0 ? -1 : set.nextSetBit(from);\n\t\t\t\treturn current;\n\t\t\t}\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\n\t\t@Override\n\t\tpublic void remove()\n\t\t{\n\t\t\tif (current >= 0) {\n\t\t\t\tset.clear(current);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Implementation of the iterator over the set bits (reverse order) */\n\tprivate class SetBitsReversedIterator implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\tprivate int current = -1;\n\t\tprivate int next;\n\n\t\tpublic SetBitsReversedIterator()\n\t\t{\n\t\t\t// only consider set bits with index <= maxIndex\n\t\t\tnext = maxIndex < 0 ? -1 : set.previousSetBit(maxIndex);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn next >= 0;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tif (hasNext()) {\n\t\t\t\tcurrent = next;\n\t\t\t\tnext = set.previousSetBit(current - 1);\n\t\t\t\treturn current;\n\t\t\t}\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\n\t\t@Override\n\t\tpublic void remove()\n\t\t{\n\t\t\tif (current >= 0) {\n\t\t\t\tset.clear(current);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Implementation of the iterator over the cleared bits, requires that {@code maxIndex != null} */\n\tprivate class ClearBitsIterator implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\tprivate int current = -1;\n\t\tprivate int next = set.nextClearBit(0);\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\tif (next > maxIndex) {\n\t\t\t\t// limit to 0 ... maxIndex\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\treturn next >= 0;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tif (hasNext()) {\n\t\t\t\tcurrent = next;\n\t\t\t\tint from = current + 1;\n\t\t\t\t// mind potential overflow\n\t\t\t\tnext = from < 0 ? -1 : set.nextClearBit(from);\n\t\t\t\treturn current;\n\t\t\t}\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\n\t\t@Override\n\t\tpublic void remove()\n\t\t{\n\t\t\tif (current >= 0) {\n\t\t\t\tset.set(current);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Implementation of the iterator over the clear bits (reverse order), requires that {@code maxIndex != null} */\n\tprivate class ClearBitsReversedIterator implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\tprivate int current = -1;\n\t\tprivate int next;\n\n\t\tpublic ClearBitsReversedIterator()\n\t\t{\n\t\t\t// only consider clear bits with index <= maxIndex\n\t\t\tnext = maxIndex < 0 ? -1 : set.previousClearBit(maxIndex);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn next >= 0;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tif (hasNext()) {\n\t\t\t\tcurrent = next;\n\t\t\t\tnext = set.previousClearBit(current - 1);\n\t\t\t\treturn current;\n\t\t\t}\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\n\t\t@Override\n\t\tpublic void remove()\n\t\t{\n\t\t\tif (current >= 0) {\n\t\t\t\tset.set(current);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t{\n\t\tif (clearBits == false) {\n\t\t\tif (reversed) {\n\t\t\t\treturn new SetBitsReversedIterator();\n\t\t\t} else {\n\t\t\t\treturn new SetBitsIterator();\n\t\t\t}\n\t\t} else {\n\t\t\tif (reversed) {\n\t\t\t\treturn new ClearBitsReversedIterator();\n\t\t\t} else {\n\t\t\t\treturn new ClearBitsIterator();\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Get an IterableBitSet that iterates over the bits of {@code set} that are set.\n\t * @param set a BitSet\n\t * @return an IterableBitSet over the set bits\n\t */\n\tpublic static IterableBitSet getSetBits(BitSet set)\n\t{\n\t\treturn new IterableBitSet(set);\n\t}\n\n\t/**\n\t * Get an IterableBitSet that iterates over the bits of {@code set} that are set,\n\t * in reverse order (highest to lowest index).\n\t * @param set a BitSet\n\t * @return an IterableBitSet over the set bits\n\t */\n\tpublic static IterableBitSet getSetBitsReversed(BitSet set)\n\t{\n\t\treturn new IterableBitSet(set, null, false, true);\n\t}\n\n\t/**\n\t * Get an IterableBitSet that iterates over the cleared bits of {@code set}, up to {@code maxIndex}\n\t * @param set a BitSet\n\t * @param maxIndex the maximal index\n\t * @return an IterableBitSet over the cleared bits\n\t */\n\tpublic static IterableBitSet getClearBits(BitSet set, int maxIndex)\n\t{\n\t\treturn new IterableBitSet(set, maxIndex, true);\n\t}\n\n\t/**\n\t * Get an IterableBitSet that iterates over the cleared bits of {@code set}, up to {@code maxIndex},\n\t * in reverse order (highest to lowest index).\n\t * @param set a BitSet\n\t * @return an IterableBitSet over the set bits\n\t */\n\tpublic static IterableBitSet getClearBitsReversed(BitSet set, int maxIndex)\n\t{\n\t\treturn new IterableBitSet(set, maxIndex, true, true);\n\t}\n\n\t/**\n\t * Simple test method.\n\t *\n\t * @param args ignored\n\t */\n\tpublic static void main(String[] args)\n\t{\n\t\tBitSet test = new BitSet();\n\t\ttest.set(0);\n\t\ttest.set(1);\n\t\ttest.set(2);\n\t\ttest.set(3);\n\t\ttest.set(5);\n\t\ttest.set(8);\n\t\ttest.set(13);\n\t\ttest.set(21);\n\t\ttest.set(Integer.MAX_VALUE);\n\n\t\tSystem.out.println(\"\\n\" + test + \" - set bits:\");\n\t\tfor (Integer index : getSetBits(test)) {\n\t\t\tSystem.out.println(index);\n\t\t}\n\n\t\ttest.clear();\n\t\tfor (@SuppressWarnings(\"unused\")\n\t\t     Integer index : getSetBits(test)) {\n\t\t\tthrow new RuntimeException(\"BitSet should be empty!\");\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/IterableStateSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\nimport java.util.BitSet;\n\nimport common.iterable.EmptyIterable;\nimport common.iterable.FunctionalPrimitiveIterable;\nimport common.iterable.FunctionalPrimitiveIterator;\nimport common.iterable.Range;\n\n/**\n * A convenience wrapper around IterableBitSet that handles the three cases of\n * iterating over the set or cleared bits of a BitSet representing a set of states\n * as well as iterating over all states if the BitSet is {@code null}.\n */\npublic class IterableStateSet implements FunctionalPrimitiveIterable.OfInt\n{\n\tprotected final FunctionalPrimitiveIterable.OfInt setOfStates;\n\n\t/**\n\t * Constructor (iterate over all states 0..numStates-1)\n\t * \n\t * @param numStates the number of states in the model, i.e., with indices 0..numStates-1\n\t */\n\tpublic IterableStateSet(int numStates)\n\t{\n\t\tthis(null, numStates, false);\n\t}\n\n\t/**\n\t * Constructor (iterate over the sets given by setOfStates or over all states)\n\t * \n\t * @param setOfStates the BitSet representing state indices in the model.\n\t *                    {@code null} signifies \"all states in the model\"\n\t * @param numStates the number of states in the model, i.e., with indices 0..numStates-1\n\t */\n\tpublic IterableStateSet(BitSet setOfStates, int numStates)\n\t{\n\t\tthis(setOfStates, numStates, false);\n\t}\n\n\t/**\n\t * Constructor\n\t *\n\t * @param setOfStates the BitSet representing state indices in the model.\n\t *                    {@code null} signifies \"all states in the model\"\n\t * @param numStates the number of states in the model, i.e., with indices 0..numStates-1\n\t * @param complement if {@code true}, iterate over all the states not included in setOfStates\n\t */\n\tpublic IterableStateSet(BitSet setOfStates, int numStates, boolean complement)\n\t{\n\t\tthis(setOfStates, numStates, complement, false);\n\t}\n\n\t/**\n\t * Constructor (most general form)\n\t *\n\t * @param setOfStates the BitSet representing state indices in the model.\n\t *                    {@code null} signifies \"all states in the model\"\n\t * @param numStates the number of states in the model, i.e., with indices 0..numStates-1\n\t * @param complement if {@code true}, iterate over all the states not included in setOfStates\n\t * @param reversed iterate in reverse order?\n\t */\n\tpublic IterableStateSet(BitSet setOfStates, int numStates, boolean complement, boolean reversed)\n\t{\n\t\tif (setOfStates == null || (setOfStates.length() == numStates && setOfStates.cardinality() == numStates)) {\n\t\t\t// all states\n\t\t\tif (complement) {\n\t\t\t\tthis.setOfStates = EmptyIterable.ofInt();\n\t\t\t} else {\n\t\t\t\tthis.setOfStates = reversed ? new Range(numStates).reversed() : new Range(numStates);\n\t\t\t}\n\t\t} else if (setOfStates.isEmpty()) {\n\t\t\t// no states\n\t\t\tif (complement) {\n\t\t\t\tthis.setOfStates = reversed ? new Range(numStates).reversed() : new Range(numStates);\n\t\t\t} else {\n\t\t\t\tthis.setOfStates = EmptyIterable.ofInt();\n\t\t\t}\n\t\t} else {\n\t\t\t// build appropriate IterableBitSet with maxIndex = numStates-1\n\t\t\tthis.setOfStates = new IterableBitSet(setOfStates, numStates - 1, complement, reversed);\n\t\t}\n\t}\n\n\t@Override\n\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t{\n\t\treturn setOfStates.iterator();\n\t}\n\n\t/**\n\t * Simple test method.\n\t *\n\t * @param args ignored\n\t */\n\tpublic static void main(String[] args)\n\t{\n\t\tBitSet test = new BitSet();\n\t\ttest.set(1);\n\t\ttest.set(3);\n\n\t\tint numStates = 5;\n\n\t\tSystem.out.println(\"\\n\" + test + \" - included states:\");\n\t\tfor (Integer index : new IterableStateSet(test, numStates)) {\n\t\t\tSystem.out.println(index);\n\t\t}\n\n\t\tSystem.out.println(\"\\n\" + test + \" - excluded states:\");\n\t\tfor (Integer index : new IterableStateSet(test, numStates, true)) {\n\t\t\tSystem.out.println(index);\n\t\t}\n\n\t\tSystem.out.println(\"\\nAll \" + numStates + \" states:\");\n\t\tfor (Integer index : new IterableStateSet((BitSet) null, numStates)) {\n\t\t\tSystem.out.println(index);\n\t\t}\n\n\t\tSystem.out.println(\"\\nNo \" + numStates + \" states:\");\n\t\tfor (Integer index : new IterableStateSet(null, numStates, true)) {\n\t\t\tSystem.out.println(index);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/IteratorTools.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\nimport java.util.Iterator;\nimport java.util.OptionalDouble;\nimport java.util.OptionalInt;\nimport java.util.OptionalLong;\nimport java.util.PrimitiveIterator.OfDouble;\nimport java.util.PrimitiveIterator.OfInt;\nimport java.util.PrimitiveIterator.OfLong;\nimport java.util.function.Predicate;\n\nimport common.iterable.Reducible;\n\n/**\n * Convenience methods for performing operations on Iterators / Iterables\n */\npublic class IteratorTools\n{\n\t/**\n\t * Boolean AND-function: Are all elements true?\n\t */\n\tpublic static boolean and(Iterator<Boolean> booleans)\n\t{\n\t\twhile (booleans.hasNext()) {\n\t\t\tif (!booleans.next()) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Boolean OR-function: Is at least one elements true?\n\t */\n\tpublic static boolean or(Iterator<Boolean> booleans)\n\t{\n\t\twhile (booleans.hasNext()) {\n\t\t\tif (booleans.next()) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Count the number of elements\n\t */\n\tpublic static long count(Iterable<?> iterable)\n\t{\n\t\treturn Reducible.extend(iterable).count();\n\t}\n\n\t/**\n\t * Count the number of elements\n\t */\n\tpublic static long count(Iterator<?> iterator)\n\t{\n\t\treturn Reducible.extend(iterator).count();\n\t}\n\n\t/**\n\t * Count the number of elements\n\t */\n\tpublic static <T> long count(Iterable<T> iterable, Predicate<? super T> predicate)\n\t{\n\t\treturn Reducible.extend(iterable).count(predicate);\n\t}\n\n\t/**\n\t * Count the number of elements\n\t */\n\tpublic static <T> long count(Iterator<T> iterator, Predicate<? super T> predicate)\n\t{\n\t\treturn Reducible.extend(iterator).count(predicate);\n\t}\n\n\t/**\n\t * Maximum over iterator elements\n\t */\n\tpublic static OptionalDouble max(OfDouble numbers)\n\t{\n\t\treturn Reducible.extend(numbers).max();\n\t}\n\n\t/**\n\t * Maximum over iterator elements\n\t */\n\tpublic static OptionalInt max(OfInt numbers)\n\t{\n\t\treturn Reducible.extend(numbers).max();\n\t}\n\n\t/**\n\t * Maximum over iterator elements\n\t */\n\tpublic static OptionalLong max(OfLong numbers)\n\t{\n\t\treturn Reducible.extend(numbers).max();\n\t}\n\n\t/**\n\t * Maximum over non-null iterator elements\n\t */\n\tpublic static OptionalDouble maxDouble(Iterator<Double> numbers)\n\t{\n\t\treturn Reducible.unboxDouble(Reducible.extend(numbers).nonNull()).max();\n\t}\n\n\t/**\n\t * Maximum over non-null iterator elements\n\t */\n\tpublic static OptionalInt maxInt(Iterator<Integer> numbers)\n\t{\n\t\treturn Reducible.unboxInt(Reducible.extend(numbers).nonNull()).max();\n\t}\n\n\t/**\n\t * Maximum over non-null iterator elements\n\t */\n\tpublic static OptionalLong maxLong(Iterator<Long> numbers)\n\t{\n\t\treturn Reducible.unboxLong(Reducible.extend(numbers).nonNull()).max();\n\t}\n\n\t/**\n\t * Minimum over iterator elements\n\t */\n\tpublic static OptionalDouble min(OfDouble numbers)\n\t{\n\t\treturn Reducible.extend(numbers).min();\n\t}\n\n\t/**\n\t * Minimum over iterator elements\n\t */\n\tpublic static OptionalInt min(OfInt numbers)\n\t{\n\t\treturn Reducible.extend(numbers).min();\n\t}\n\n\t/**\n\t * Minimum over iterator elements\n\t */\n\tpublic static OptionalLong min(OfLong numbers)\n\t{\n\t\treturn Reducible.extend(numbers).min();\n\t}\n\n\t/**\n\t * Minimum over non-null iterator elements\n\t */\n\tpublic static OptionalDouble minDouble(Iterator<Double> numbers)\n\t{\n\t\treturn Reducible.unboxDouble(Reducible.extend(numbers).nonNull()).min();\n\t}\n\n\t/**\n\t * Minimum over non-null iterator elements\n\t */\n\tpublic static OptionalInt minInt(Iterator<Integer> numbers)\n\t{\n\t\treturn Reducible.unboxInt(Reducible.extend(numbers).nonNull()).min();\n\t}\n\n\t/**\n\t * Minimum over non-null iterator elements\n\t */\n\tpublic static OptionalLong minLong(Iterator<Long> numbers)\n\t{\n\t\treturn Reducible.unboxLong(Reducible.extend(numbers).nonNull()).min();\n\t}\n\n\t/**\n\t * Sum over iterator elements\n\t */\n\tpublic static double sum(OfDouble numbers)\n\t{\n\t\treturn Reducible.extend(numbers).sum();\n\t}\n\n\t/**\n\t * Sum over iterator elements\n\t */\n\tpublic static long sum(OfInt numbers)\n\t{\n\t\treturn Reducible.extend(numbers).sum();\n\t}\n\n\t/**\n\t * Sum over iterator elements\n\t */\n\tpublic static long sum(OfLong numbers)\n\t{\n\t\treturn Reducible.extend(numbers).sum();\n\t}\n\n\t/**\n\t * Sum over non-null iterator elements\n\t */\n\tpublic static double sumDouble(Iterator<Double> numbers)\n\t{\n\t\treturn Reducible.unboxDouble(Reducible.extend(numbers).nonNull()).sum();\n\t}\n\n\t/**\n\t * Sum over non-null iterator elements\n\t */\n\tpublic static long sumInt(Iterator<Integer> numbers)\n\t{\n\t\treturn Reducible.unboxInt(Reducible.extend(numbers).nonNull()).sum();\n\t}\n\n\t/**\n\t * Sum over non-null iterator elements\n\t */\n\tpublic static long sumLong(Iterator<Long> numbers)\n\t{\n\t\treturn Reducible.unboxLong(Reducible.extend(numbers).nonNull()).sum();\n\t}\n\n\t/**\n\t * Create String \"name = {e_1, e_2}\".\n\t * \n\t * @param name     name of a variable\n\t * @param iterator the iterator to be printed\n\t */\n\tpublic static <T> void printIterator(String name, Iterator<T> iterator)\n\t{\n\t\tSystem.out.print(name + \" = \");\n\t\tSystem.out.print(Reducible.extend(iterator).asString());\n\t\tSystem.out.println();\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/PeriodicTimer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\n/**\n * This class keeps time, returning {@code true} for the method {@code triggered()}\n * when another period of {@code period} milliseconds has elapsed.\n * <br>\n * The time is only checked when {@code triggered} is called, so if there\n * can be long delays between calls to that method, intermediate periods are ignored.\n * <br>\n * This class is thus most helpful for \"print some update at least after 5 seconds\" style\n * jobs.\n */\npublic class PeriodicTimer\n{\n\t/** The period */\n\tlong period;\n\t/** The time when the timer was started */\n\tlong start;\n\t/** The time when the last period was detected */\n\tlong startOfCurrentPeriod;\n\n\t/** Constructor, provide the period in milliseconds, e.g., 5000 = 5 seconds */\n\tpublic PeriodicTimer(long periodMillis)\n\t{\n\t\tthis.period = periodMillis;\n\t\tthis.start = -1;\n\t\tthis.startOfCurrentPeriod = -1;\n\t}\n\n\t/** Start the timer */\n\tpublic void start()\n\t{\n\t\tstart = System.currentTimeMillis();\n\t\tstartOfCurrentPeriod = start;\n\t}\n\n\t/**\n\t * Returns true if at least 'period' milliseconds have\n\t * elapsed since the last time that this method has\n\t * returned {@code true}.\n\t */\n\tpublic boolean triggered()\n\t{\n\t\tlong now = System.currentTimeMillis();\n\t\tif (now - startOfCurrentPeriod > period) {\n\t\t\tstartOfCurrentPeriod = now;\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** Get the number of milliseconds since {@code start()} was called */\n\tpublic long elapsedMillisTotal()\n\t{\n\t\tlong now = System.currentTimeMillis();\n\t\treturn now - start;\n\t}\n\n\t/**\n\t * Get the number of milliseconds since {@code triggered()} has returned {@code true}\n\t * the last time\n\t */\n\tpublic long elapsedMillisInThisPeriod()\n\t{\n\t\tlong now = System.currentTimeMillis();\n\t\treturn now - startOfCurrentPeriod;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/common/SafeCast.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2018-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\nimport prism.PrismException;\n\n/**\n * This class provides utility methods to allow the detection of\n * primitive cast errors, e.g. like overflows and special values.\n */\npublic class SafeCast\n{\n\t/**\n\t * Convert a primitive {@code double} value to a primitive {@code int} value,\n\t * throwing an exception if the value can not be exactly represented as an {@code int}.\n\t * Wrapper method for toIntExact, converting an ArithmeticException to a PrismException.\n\t *\n\t * @param value {@code double} value\n\t * @return the corresponding {@code int} value\n\t * @throws PrismException if the value cannot be converted to {@code int}\n\t */\n\tpublic static int toInt(double value) throws PrismException\n\t{\n\t\ttry {\n\t\t\treturn toIntExact(value);\n\t\t} catch (ArithmeticException e) {\n\t\t\tthrow new PrismException(e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Convert a primitive {@code long} value to a primitive {@code int} value,\n\t * throwing an exception if the value can not be exactly represented as an {@code int}.\n\t * Wrapper method for toIntExact, converting an ArithmeticException to a PrismException.\n\t *\n\t * @param value {@code long} value\n\t * @return the corresponding {@code int} value\n\t * @throws PrismException if the value cannot be converted to {@code int}\n\t */\n\tpublic static int toInt(long value) throws PrismException\n\t{\n\t\ttry {\n\t\t\treturn toIntExact(value);\n\t\t} catch (ArithmeticException e) {\n\t\t\tthrow new PrismException(e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Convert a primitive {@code double} to a primitive {@code int} value,\n\t * throwing an exception if the value can not be exactly represented as an {@code int}.\n\t *\n\t * @param value {@code double} value\n\t * @return the corresponding {@code int} value\n\t * @throws ArithmeticException if the value cannot be converted to {@code int}\n\t */\n\tpublic static int toIntExact(double value)\n\t{\n\t\tif (!Double.isFinite(value)) {\n\t\t\tthrow new ArithmeticException(value + \" is non-finite, cannot be represented by int\");\n\t\t}\n\n\t\tif ((int) value != value) {\n\t\t\tthrow new ArithmeticException(value + \" cannot be losslessly converted to int\");\n\t\t}\n\n\t\treturn (int) value;\n\t}\n\n\t/**\n\t * Convert a primitive {@code long} to a primitive {@code int} value,\n\t * throwing an exception if the value can not be exactly represented as an {@code int}.\n\t *\n\t * @param value {@code long} value\n\t * @return the corresponding {@code int} value\n\t * @throws ArithmeticException if the value cannot be converted to {@code int}\n\t */\n\tpublic static int toIntExact(long value)\n\t{\n\t\tif (value < Integer.MIN_VALUE || value > Integer.MAX_VALUE) {\n\t\t\tthrow new ArithmeticException(value + \" cannot be losslessly converted to int\");\n\t\t}\n\t\treturn (int) value;\n\t}\n\n\t/**\n\t * Convert a primitive double to a primitive long value\n\t * throwing an exception if the value is a special value or not an {@code long}.\n\t *\n\t * @param value {@code double} value\n\t * @return the equivalent {@code long} value\n\t * @throws ArithmeticException if the value cannot be converted to {@code long}\n\t */\n\tpublic static long toLongExact(double value)\n\t{\n\t\tif (!Double.isFinite(value)) {\n\t\t\tthrow new ArithmeticException(value + \" is non-finite, cannot be represented by long\");\n\t\t}\n\n\t\tif ((long) value != value) {\n\t\t\tthrow new ArithmeticException(value + \" cannot be losslessly converted to long\");\n\t\t}\n\t\treturn (long) value;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/common/StackTraceHelper.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2018-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\n/** Helper class for converting stack traces to strings for output */\npublic class StackTraceHelper\n{\n\t/** Default limit for number of lines in a stack trace */\n\tpublic static final int DEFAULT_STACK_TRACE_LIMIT = 25;\n\n\t/**\n\t * Get a string representation of the stack trace for the Throwable\n\t * (up to the given limit of lines).\n\t * @param throwable the throwable\n\t * @param limit the limit\n\t */\n\tpublic static String asString(Throwable throwable, int limit)\n\t{\n\t\treturn asString(throwable.getStackTrace(), limit);\n\t}\n\n\t/**\n\t * Get a string representation of the stack trace for the given stack trace array\n\t * (up to the given limit of lines).\n\t * @param elements array of stack trace elements (zero-th element is top of stack)\n\t * @param limit the limit (0 = no limit)\n\t */\n\tpublic static String asString(StackTraceElement[] elements, int limit)\n\t{\n\t\tStringBuilder sb = new StringBuilder();\n\n\t\tint i = 0;\n\t\tfor (StackTraceElement element : elements) {\n\t\t\tif (limit != 0 && i++ > limit) {\n\t\t\t\tsb.append(\"    ....\\n\");\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tsb.append(\"    at \");\n\t\t\tsb.append(element);\n\t\t\tsb.append(\"\\n\");\n\t\t}\n\n\t\treturn sb.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/StopWatch.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\nimport java.util.function.Function;\nimport java.util.function.Supplier;\n\nimport prism.PrismLog;\n\n/**\n * Stop watch for keeping track of the runtime of some computation,\n * optionally printing the elapsed time to the log after the computation\n * has stopped.\n * <br>\n * Example usage:\n * <pre>\n * StopWatch timer = new StopWatch(log);\n * timer.start(\"model checking\");\n * // ... do the actual computation ...\n * timer.stop();\n * </pre>\n * would result in the output\n * <pre>\n * Time for model checking 42.00 seconds.\n * </pre>\n * <br>\n * Stopping via\n * <pre>\n * timer.stop(\"result was xyz\");\n * </pre>\n * results in\n * <pre>\n * Time for model checking 42.00 seconds, result was xyz.\n * </pre>\n */\npublic class StopWatch\n{\n\t/** The (optional) log */\n\tprotected PrismLog log;\n\n\t/** An (optional) task description */\n\tprotected String taskDescription;\n\n\t/** For storing the time */\n\tprotected long time = 0;\n\n\t/** Is watch running? */\n\tprotected boolean running = false;\n\n\t/** Constructor, no log and no output */\n\tpublic StopWatch()\n\t{\n\t}\n\n\t/** Constructor, stores log for output */\n\tpublic StopWatch(PrismLog log)\n\t{\n\t\tthis.log = log;\n\t}\n\n\t/** Start the stop watch (without task description) */\n\tpublic StopWatch start()\n\t{\n\t\treturn start(null);\n\t}\n\n\t/** Start the stop watch, store task description (may be {@code null}) */\n\tpublic StopWatch start(String taskDescription)\n\t{\n\t\tthis.taskDescription = taskDescription;\n\t\trunning = true;\n\t\ttime = System.currentTimeMillis();\n\t\treturn this;\n\t}\n\n\t/**\n\t * Stop the stop watch.\n\t * If a task description and a log was given, output elapsed time.\n\t * @return elapsed time in milliseconds\n\t */\n\tpublic long stop()\n\t{\n\t\treturn stop(null);\n\t}\n\n\t/**\n\t * Stop the stop watch, optionally taking extra text for output.\n\t * If a log and a task description / extra text was given, output\n\t * elapsed time.\n\t * <br>\n\t * Extra text is output as \"... xx.yy seconds, extra-text.\"\n\t * @param extraText extra text to output (optional, ignored if {@code null})\n\t */\n\tpublic long stop(String extraText)\n\t{\n\t\ttime = System.currentTimeMillis() - time;\n\t\trunning = false;\n\t\tif (log != null) {\n\t\t\tif (taskDescription != null) {\n\t\t\t\tlog.print(\"Time for \" + taskDescription + \": \" + elapsedSeconds() + \" seconds\");\n\t\t\t\tif (extraText != null) {\n\t\t\t\t\tlog.print(\", \" + extraText);\n\t\t\t\t}\n\t\t\t\tlog.println(\".\");\n\t\t\t} else if (extraText != null) {\n\t\t\t\tlog.println(\"Time: \" + elapsedSeconds() + \" seconds, \" + extraText + \".\");\n\t\t\t}\n\t\t}\n\t\treturn time;\n\t}\n\n\t/** Get the number of elapsed milliseconds (fixed value after having called stop). */\n\tpublic long elapsedMillis()\n\t{\n\t\treturn running ? System.currentTimeMillis() - time : time;\n\t}\n\n\t/** Get the number of elapsed seconds (fixed value after having called stop). */\n\tpublic double elapsedSeconds()\n\t{\n\t\treturn elapsedMillis() / 1000.0;\n\t}\n\n\t/**\n\t * Stop the execution time of a task.\n\t *\n\t * @return time in milliseconds\n\t **/\n\tpublic long run(Runnable task)\n\t{\n\t\treturn run(task, null, null);\n\t}\n\n\t/**\n\t * Stop the execution time of a task.\n\t *\n\t * @param taskDescription description or {@code null})\n\t * @param extraText text or {@code null}\n\t * @return time in milliseconds\n\t **/\n\tpublic long run(Runnable task, String taskDescription, String extraText)\n\t{\n\t\tstart(taskDescription);\n\t\ttask.run();\n\t\treturn stop(extraText);\n\t}\n\n\t/**\n\t * Stop the execution time of a task and return the result.\n\t * Time is available via {@code elapsedMillis()} and {@code elapsedSeconds()}.\n\t *\n\t * @return task result\n\t **/\n\tpublic <T> T run(Supplier<T> task)\n\t{\n\t\treturn run(task, null, (String) null);\n\t}\n\n\t/**\n\t * Stop the execution time of a task and return the result.\n\t * Time is available via {@code elapsedMillis()} and {@code elapsedSeconds()}.\n\t *\n\t * @param taskDescription description or {@code null}\n\t * @param extraText text or {@code null}\n\t * @return task result\n\t **/\n\tpublic <T> T run(Supplier<T> task, String taskDescription, String extraText)\n\t{\n\t\tstart(taskDescription);\n\t\tT result = task.get();\n\t\tstop(extraText);\n\t\treturn result;\n\t}\n\n\t/**\n\t * Stop the execution time of a task and return the result.\n\t * Time is available via {@code elapsedMillis()} and {@code elapsedSeconds()}.\n\t *\n\t * @param taskDescription description or {@code null}\n\t * @param resultDescription function that provides a description or {@code null}\n\t * @return task result\n\t **/\n\tpublic <T> T run(Supplier<T> task, String taskDescription, Function<? super T, String> resultDescription)\n\t{\n\t\tstart(taskDescription);\n\t\tT result = task.get();\n\t\tstop(resultDescription.apply(result));\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/Timeout.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common;\n\n/**\n * Simple timeout mechanism.\n * After the specified number of seconds have elapsed (measured by\n * System.currentTimeMillis()), a Runnable is invoked.\n * Checks once per second.\n */\npublic class Timeout implements Runnable\n{\n\t/** The time after which the timeout is expired. */\n\tprivate final long timeoutTime;\n\t/** The Runnable to call after the timeout has expired. */\n\tprivate final Runnable timeoutRunnable;\n\n\t/**\n\t * Set a timeout.\n\t * Starts a (daemon) thread which checks if the timeout has elapsed.\n\t */\n\tpublic static void setTimeout(int timeoutInSeconds, Runnable timeoutRunnable) {\n\t\tTimeout t = new Timeout(timeoutInSeconds, timeoutRunnable);\n\t\tThread timeoutThread = new Thread(t);\n\t\t// the thread should be a daemon thread, because otherwise\n\t\t// the VM will not exit before the timeout is expired...\n\t\ttimeoutThread.setDaemon(true);\n\t\ttimeoutThread.start();\n\t}\n\n\t/**\n\t * Constructor.\n\t */\n\tprivate Timeout(int timeoutInSeconds, Runnable timeoutRunnable)\n\t{\n\t\ttimeoutTime = System.currentTimeMillis() + timeoutInSeconds*1000;\n\t\tthis.timeoutRunnable = timeoutRunnable;\n\t}\n\n\t@Override\n\tpublic void run()\n\t{\n\t\twhile (true) {\n\t\t\tlong current = System.currentTimeMillis();\n\t\t\tif (current > timeoutTime) {\n\t\t\t\t// Timeout is expired, run Runnable\n\t\t\t\ttimeoutRunnable.run();\n\t\t\t\treturn;\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tThread.sleep(1000);\n\t\t\t} catch (InterruptedException e) {}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/functions/DoubleLongToDoubleFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\n/**\n * Functional interface for a binary function (double, long) -> double.\n */\n@FunctionalInterface\npublic interface DoubleLongToDoubleFunction\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tdouble applyAsDouble(double d, long l);\n}\n"
  },
  {
    "path": "prism/src/common/functions/DoubleObjToDoubleFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\nimport java.util.Objects;\nimport java.util.function.DoubleUnaryOperator;\n\n/**\n * Functional interface for a binary function (double, T) -> double.\n */\n@FunctionalInterface\npublic interface DoubleObjToDoubleFunction<T>\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tdouble applyAsDouble(double d, T t);\n\n\t/**\n\t * Returns a composed function that first applies this function to\n\t * its input, and then applies the {@code after} function to the result.\n\t */\n\tdefault <V> DoubleObjToDoubleFunction<T> andThen(DoubleUnaryOperator after) {\n\t\tObjects.requireNonNull(after);\n\t\treturn (double d, T t) -> after.applyAsDouble(applyAsDouble(d, t));\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/functions/IntDoubleToIntFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\n/**\n * Functional interface for a binary function (int, double) -> int.\n */\n@FunctionalInterface\npublic interface IntDoubleToIntFunction\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tint applyAsInt(int i, double d);\n}\n"
  },
  {
    "path": "prism/src/common/functions/IntLongToIntFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\n/**\n * Functional interface for a binary function (int, long) -> int.\n */\n@FunctionalInterface\npublic interface IntLongToIntFunction\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tint applyAsInt(int i, long l);\n}\n"
  },
  {
    "path": "prism/src/common/functions/IntObjToIntFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\nimport java.util.Objects;\nimport java.util.function.IntUnaryOperator;\n\n/**\n * Functional interface for a binary function (int, T) -> int.\n */\n@FunctionalInterface\npublic interface IntObjToIntFunction<T>\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tint applyAsInt(int i, T t);\n\n\t/**\n\t * Returns a composed function that first applies this function to\n\t * its input, and then applies the {@code after} function to the result.\n\t */\n\tdefault <V> IntObjToIntFunction<T> andThen(IntUnaryOperator after) {\n\t\tObjects.requireNonNull(after);\n\t\treturn (int i, T t) -> after.applyAsInt(applyAsInt(i, t));\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/functions/LongDoubleToLongFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\n/**\n * Functional interface for a binary function (int, double) -> int.\n */\n@FunctionalInterface\npublic interface LongDoubleToLongFunction\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tlong applyAsLong(long l, double i);\n}\n"
  },
  {
    "path": "prism/src/common/functions/LongObjToLongFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\nimport java.util.Objects;\nimport java.util.function.LongUnaryOperator;\n\n/**\n * Functional interface for a binary function (long, T) -> long.\n */\n@FunctionalInterface\npublic interface LongObjToLongFunction<T>\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tlong applyAsLong(long i, T t);\n\n\t/**\n\t * Returns a composed function that first applies this function to\n\t * its input, and then applies the {@code after} function to the result.\n\t */\n\tdefault <V> LongObjToLongFunction<T> andThen(LongUnaryOperator after) {\n\t\tObjects.requireNonNull(after);\n\t\treturn (long l, T t) -> after.applyAsLong(applyAsLong(l, t));\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/functions/ObjDoubleFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\nimport java.util.Objects;\nimport java.util.function.Function;\n\n/**\n * Functional interface for a binary function (T, double) -> R.\n */\n@FunctionalInterface\npublic interface ObjDoubleFunction<T, R>\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tR apply(T t, double d);\n\n\t/**\n\t * Returns a composed function that first applies this function to\n\t * its input, and then applies the {@code after} function to the result.\n\t */\n\tdefault <V> ObjDoubleFunction<T, V> andThen(Function<? super R, ? extends V> after) {\n\t\tObjects.requireNonNull(after);\n\t\treturn (T t, double d) -> after.apply(apply(t, d));\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/functions/ObjIntFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\nimport java.util.Objects;\nimport java.util.function.Function;\n\n/**\n * Functional interface for a binary function (T, int) -> R.\n */\n@FunctionalInterface\npublic interface ObjIntFunction<T, R>\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tR apply(T t, int i);\n\n\t/**\n\t * Returns a composed function that first applies this function to\n\t * its input, and then applies the {@code after} function to the result.\n\t */\n\tdefault <V> ObjIntFunction<T, V> andThen(Function<? super R, ? extends V> after) {\n\t\tObjects.requireNonNull(after);\n\t\treturn (T t, int i) -> after.apply(apply(t, i));\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/functions/ObjLongFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\nimport java.util.Objects;\nimport java.util.function.Function;\n\n/**\n * Functional interface for a binary function (T, long) -> R.\n */\n@FunctionalInterface\npublic interface ObjLongFunction<T, R>\n{\n\t/**\n\t * Applies this function to the given arguments.\n\t */\n\tR apply(T t, long l);\n\n\t/**\n\t * Returns a composed function that first applies this function to\n\t * its input, and then applies the {@code after} function to the result.\n\t */\n\tdefault <V> ObjLongFunction<T, V> andThen(Function<? super R, ? extends V> after) {\n\t\tObjects.requireNonNull(after);\n\t\treturn (T t, long l) -> after.apply(apply(t, l));\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/functions/PairPredicateInt.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.functions;\n\n/**\n * Functional interface for a predicate (int, int) -> boolean.\n */\n@FunctionalInterface\npublic interface PairPredicateInt\n{\n\t/**\n\t * Evaluates this predicate on the given arguments.\n\t */\n\tboolean test(int i, int j);\n\n\t/**\n\t * Returns a predicate that represents the logical negation of this predicate.\n\t */\n\tdefault PairPredicateInt negate()\n\t{\n\t\treturn (i, j) -> !test(i, j);\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/ArrayIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Marcus Daum <marcus.daum@ivi.fraunhofer.de> (Frauenhofer Institut)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Objects;\n\n/**\n * Abstract base class of efficient Iterators over array slices.\n * Implementations should release the underlying array after iteration.\n *\n * @param <E> type of the array elements\n */\npublic abstract class ArrayIterator<E> implements FunctionalIterator<E>\n{\n\tprotected final int toIndex;\n\tprotected int nextIndex;\n\n\t/**\n\t * Iterate over all elements in index interval [fromIndex, toIndex).\n\t *\n\t * @param fromIndex first index, inclusive\n\t * @param toIndex last index, exclusive\n\t * @param length length of the array\n\t */\n\tprotected ArrayIterator(int fromIndex, int toIndex, int length)\n\t{\n\t\tObjects.checkFromToIndex(fromIndex, toIndex, length);\n\t\tthis.nextIndex = fromIndex;\n\t\tthis.toIndex   = toIndex;\n\t}\n\n\t@Override\n\tpublic boolean hasNext()\n\t{\n\t\tif (nextIndex < toIndex) {\n\t\t\treturn true;\n\t\t}\n\t\trelease();\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic long count()\n\t{\n\t\treturn Math.max(0, toIndex - nextIndex);\n\t}\n\n\t/**\n\t * Get the index of the next element.\n\t */\n\tpublic int nextIndex()\n\t{\n\t\trequireNext();\n\t\treturn nextIndex;\n\t}\n\n\t/**\n\t * Release reference to the underlying array.\n\t */\n\t@Override\n\tpublic void release()\n\t{\n\t\tnextIndex = toIndex;\n\t}\n\n\t/**\n\t * Generic implementation of an Iterator over an array slice.\n\t *\n\t * @param <E> type of the array elements\n\t */\n\tpublic static class Of<E> extends ArrayIterator<E>\n\t{\n\t\t/** Placeholder array after Iterator is exhausted */\n\t\tpublic static final Object[] EMPTY_OBJECT = new Object[0];\n\n\t\tprotected E[] elements;\n\n\t\t/**\n\t\t * Iterate over all elements.\n\t\t */\n\t\t@SafeVarargs\n\t\tpublic Of(E... elements)\n\t\t{\n\t\t\tthis(elements, 0, elements.length);\n\t\t}\n\n\t\t/**\n\t\t * Iterate over all elements in index interval [fromIndex, toIndex).\n\t\t *\n\t\t * @param fromIndex first index, inclusive\n\t\t * @param toIndex last index, exclusive\n\t\t */\n\t\tpublic Of(E[] elements, int fromIndex, int toIndex)\n\t\t{\n\t\t\tsuper(fromIndex, toIndex, elements.length);\n\t\t\tthis.elements = elements;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn elements[nextIndex++];\n\t\t}\n\n\t\t@SuppressWarnings(\"unchecked\")\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\telements = (E[]) EMPTY_OBJECT;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of an Iterator over an array slice.\n\t */\n\tpublic static class OfDouble extends ArrayIterator<Double> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/** Placeholder array after Iterator is exhausted */\n\t\tpublic static final double[] EMPTY_DOUBLE = new double[0];\n\n\t\tprotected double[] elements;\n\n\t\t/**\n\t\t * Iterate over all elements.\n\t\t */\n\t\tpublic OfDouble(double... elements)\n\t\t{\n\t\t\tthis(elements, 0, elements.length);\n\t\t}\n\n\t\t/**\n\t\t * Iterate over all elements in index interval [fromIndex, toIndex).\n\t\t *\n\t\t * @param fromIndex first index, inclusive\n\t\t * @param toIndex last index, exclusive\n\t\t */\n\t\tpublic OfDouble(double[] elements, int fromIndex, int toIndex)\n\t\t{\n\t\t\tsuper(fromIndex, toIndex, elements.length);\n\t\t\tthis.elements = elements;\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn elements[nextIndex++];\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\telements = EMPTY_DOUBLE;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of an Iterator over an array slice.\n\t */\n\tpublic static class OfInt extends ArrayIterator<Integer> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/** Placeholder array after Iterator is exhausted */\n\t\tpublic static final int[] EMPTY_INT = new int[0];\n\n\t\tprotected int[] elements;\n\n\t\t/**\n\t\t * Iterate over all elements.\n\t\t */\n\t\tpublic OfInt(int... elements)\n\t\t{\n\t\t\tthis(elements, 0, elements.length);\n\t\t}\n\n\t\t/**\n\t\t * Iterate over all elements in index interval [fromIndex, toIndex).\n\t\t *\n\t\t * @param fromIndex first index, inclusive\n\t\t * @param toIndex last index, exclusive\n\t\t */\n\t\tpublic OfInt(int[] elements, int fromIndex, int toIndex)\n\t\t{\n\t\t\tsuper(fromIndex, toIndex, elements.length);\n\t\t\tthis.elements = elements;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn elements[nextIndex++];\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\telements = EMPTY_INT;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of an Iterator over an array slice.\n\t */\n\tpublic static class OfLong extends ArrayIterator<Long> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/** Placeholder array after Iterator is exhausted */\n\t\tpublic static final long[] EMPTY_LONG = new long[0];\n\n\t\tprotected long[] elements;\n\n\t\t/**\n\t\t * Iterate over all elements.\n\t\t */\n\t\tpublic OfLong(long... elements)\n\t\t{\n\t\t\tthis(elements, 0, elements.length);\n\t\t}\n\n\t\t/**\n\t\t * Iterate over all elements in index interval [fromIndex, toIndex).\n\t\t *\n\t\t * @param fromIndex first index, inclusive\n\t\t * @param toIndex last index, exclusive\n\t\t */\n\t\tpublic OfLong(long[] elements, int fromIndex, int toIndex)\n\t\t{\n\t\t\tsuper(fromIndex, toIndex, elements.length);\n\t\t\tthis.elements = elements;\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn elements[nextIndex++];\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\telements = EMPTY_LONG;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/ChainedIterable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Objects;\n\n/**\n * Abstract base class for Iterables that chain a sequence of Iterables.\n *\n * @param <E> type of the Iterator's elements\n * @param <I> type of the underlying Iterables\n */\npublic abstract class ChainedIterable<E, I extends Iterable<E>> implements FunctionalIterable<E>\n{\n\t/** The Iterable over the sequence of Iterables that are chained */\n\tprotected final FunctionalIterable<? extends I> iterables;\n\n\t/**\n\t * Constructor for an Iterable that chains Iterables provided in an Iterable.\n\t *\n\t * @param iterables an Iterable of Iterables to be chained\n\t */\n\tpublic ChainedIterable(Iterable<? extends I> iterables)\n\t{\n\t\tObjects.requireNonNull(iterables);\n\t\tthis.iterables = Reducible.extend(iterables);\n\t}\n\n\n\n\t/**\n\t * Generic implementation of a chained Iterable.\n\t *\n\t * @param <E> type of the Iterable's elements\n\t */\n\tpublic static class Of<E> extends ChainedIterable<E, Iterable<E>>\n\t{\n\t\t/**\n\t\t * Constructor for an Iterable that chains Iterables provided in an Iterable.\n\t\t *\n\t\t * @param iterables an Iterable of Iterables to be chained\n\t\t */\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tpublic Of(Iterable<? extends Iterable<? extends E>> iterables)\n\t\t{\n\t\t\tsuper((Iterable<? extends Iterable<E>>) iterables);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalIterator<E> iterator()\n\t\t{\n\t\t\treturn new ChainedIterator.Of<>(iterables.map(Iterable::iterator).iterator());\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of a chained Iterable.\n\t */\n\tpublic static class OfDouble extends ChainedIterable<Double, PrimitiveIterable.OfDouble> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/**\n\t\t * Constructor for an Iterable that chains Iterables provided in an Iterable.\n\t\t *\n\t\t * @param iterables an Iterable of Iterables to be chained\n\t\t */\n\t\tpublic OfDouble(Iterable<? extends PrimitiveIterable.OfDouble> iterables)\n\t\t{\n\t\t\tsuper(iterables);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn new ChainedIterator.OfDouble(iterables.map(PrimitiveIterable.OfDouble::iterator).iterator());\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of a chained Iterable.\n\t */\n\tpublic static class OfInt extends ChainedIterable<Integer, PrimitiveIterable.OfInt> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/**\n\t\t * Constructor for an Iterable that chains Iterables provided in an Iterable.\n\t\t *\n\t\t * @param iterables an Iterable of Iterables to be chained\n\t\t */\n\t\tpublic OfInt(Iterable<? extends PrimitiveIterable.OfInt> iterables)\n\t\t{\n\t\t\tsuper(iterables);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t\t{\n\t\t\treturn new ChainedIterator.OfInt(iterables.map(PrimitiveIterable.OfInt::iterator).iterator());\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of a chained Iterable.\n\t */\n\tpublic static class OfLong extends ChainedIterable<Long, PrimitiveIterable.OfLong> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/**\n\t\t * Constructor for an Iterable that chains Iterables provided in an Iterable.\n\t\t *\n\t\t * @param iterables an Iterable of Iterables to be chained\n\t\t */\n\t\tpublic OfLong(Iterable<? extends PrimitiveIterable.OfLong> iterables)\n\t\t{\n\t\t\tsuper(iterables);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfLong iterator()\n\t\t{\n\t\t\treturn new ChainedIterator.OfLong(iterables.map(PrimitiveIterable.OfLong::iterator).iterator());\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/common/iterable/ChainedIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Iterator;\nimport java.util.Objects;\nimport java.util.OptionalDouble;\nimport java.util.OptionalInt;\nimport java.util.OptionalLong;\nimport java.util.PrimitiveIterator;\n\n/**\n * Abstract base class implementing an Iterator that chains a sequence of Iterators.\n * Returns all the elements of the first Iterator, then the elements of the\n * second Iterator and so on.\n * <p>\n * The calls to {@code next()} of the underlying Iterator happen on-the-fly,\n * i.e., only when {@code next()} is called for this Iterator.\n * <p>\n * Implementations should release the underlying Iterators after iteration.\n * <p>\n * This Iterator does not support the {@code remove()} method, even if the underlying\n * Iterators support it.\n *\n * @param <E> type of the {@link Iterator}'s elements\n * @param <I> common super type of {@link FunctionalIterator} for all Iterators in the chain\n */\npublic abstract class ChainedIterator<E, I extends FunctionalIterator<E>> implements FunctionalIterator<E>\n{\n\t/** The Iterator over the sequence of Iterators that are chained */\n\tprotected FunctionalIterator<I> iterators;\n\t/** The current Iterator in the sequence of Iterators */\n\tprotected I current;\n\n\t/**\n\t * Constructor for an Iterator that chains Iterators provided in an Iterator.\n\t *\n\t * @param iterators an Iterator over Iterators to be chained\n\t */\n\tpublic ChainedIterator(Iterator<? extends Iterator<E>>iterators)\n\t{\n\t\tthis(EmptyIterator.of(), iterators);\n\t}\n\n\t/**\n\t * Constructor for chaining an Iterator and a number of Iterators provided in an Iterator.\n\t *\n\t * @param iterator  an Iterator to prepend the chain\n\t * @param iterators an Iterator over Iterators to be chained\n\t */\n\t@SuppressWarnings({ \"unchecked\"})\n\tpublic ChainedIterator(Iterator<E> iterator, Iterator<? extends Iterator<E>> iterators)\n\t{\n\t\tObjects.requireNonNull(iterator);\n\t\tObjects.requireNonNull(iterators);\n\t\tthis.current   = (I) Reducible.extend(iterator);\n\t\tthis.iterators = (FunctionalIterator<I>) Reducible.extend(iterators).map(Reducible::extend);\n\t\thasNext();\n\t}\n\n\t@Override\n\tpublic boolean hasNext()\n\t{\n\t\tif (current.hasNext()) {\n\t\t\t// the current iterator has another element\n\t\t\treturn true;\n\t\t}\n\n\t\t// the current iterator has no more elements,\n\t\t// search for the next iterator that as an element\n\t\twhile (iterators.hasNext()) {\n\t\t\t// consider the next iterator\n\t\t\tcurrent = iterators.next();\n\t\t\tif (current.hasNext()) {\n\t\t\t\t// iterator has element, keep current and return true\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\t// there are no more iterators / elements\n\t\trelease();\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic long count()\n\t{\n\t\tlong count = current.count() + iterators.mapToLong(FunctionalIterator::count).sum();\n\t\trelease();\n\t\treturn count;\n\t}\n\n\t@Override\n\tpublic void release()\n\t{\n\t\titerators = EmptyIterator.of();\n\t}\n\n\n\n\t/**\n\t * Generic implementation of a chained Iterator.\n\t *\n\t * @param <E> type of the Iterator's elements\n\t */\n\tpublic static class Of<E> extends ChainedIterator<E, FunctionalIterator<E>>\n\t{\n\t\t/**\n\t\t * Constructor for an Iterator that chains Iterators provided in an Iterator.\n\t\t *\n\t\t * @param iterators an Iterator over Iterators to be chained\n\t\t */\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tpublic Of(Iterator<? extends Iterator<? extends E>> iterators)\n\t\t{\n\t\t\tsuper((Iterator<? extends Iterator<E>>) iterators);\n\t\t}\n\n\t\t/**\n\t\t * Constructor for chaining an Iterator and a number of Iterators provided in an Iterator.\n\t\t *\n\t\t * @param iterator  an Iterator to prepend the chain\n\t\t * @param iterators an Iterator over Iterators to be chained\n\t\t */\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tpublic Of(Iterator<? extends E> iterator, Iterator<? extends Iterator<? extends E>> iterators)\n\t\t{\n\t\t\tsuper((Iterator<E>) iterator, (Iterator<? extends Iterator<E>>) iterators);\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn current.next();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(Object obj)\n\t\t{\n\t\t\tboolean contains = current.contains(obj) || iterators.anyMatch(it -> it.contains(obj));\n\t\t\trelease();\n\t\t\treturn contains;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\tcurrent   = EmptyIterator.of();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of a chained Iterator.\n\t */\n\tpublic static class OfDouble extends ChainedIterator<Double, FunctionalPrimitiveIterator.OfDouble> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/**\n\t\t * Constructor for an Iterator that chains Iterators provided in an Iterator.\n\t\t *\n\t\t * @param iterators an Iterator over Iterators to be chained\n\t\t */\n\t\tpublic OfDouble(Iterator<? extends PrimitiveIterator.OfDouble> iterators)\n\t\t{\n\t\t\tsuper(iterators);\n\t\t}\n\n\t\t/**\n\t\t * Constructor for chaining an Iterator and a number of Iterators provided in an Iterator.\n\t\t *\n\t\t * @param iterator  an Iterator to prepend the chain\n\t\t * @param iterators an Iterator over Iterators to be chained\n\t\t */\n\t\tpublic OfDouble(PrimitiveIterator.OfDouble iterator, Iterator<? extends PrimitiveIterator.OfDouble> iterators)\n\t\t{\n\t\t\tsuper(iterator, iterators);\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn current.nextDouble();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(double d)\n\t\t{\n\t\t\tboolean result = current.contains(d) || iterators.anyMatch(it -> it.contains(d));\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalDouble max()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalDouble.empty();\n\t\t\t}\n\t\t\tdouble max = current.max().getAsDouble();\n\t\t\tmax = iterators.reduce(max, (m, it) -> Math.max(m, it.max().orElse(m)));\n\t\t\trelease();\n\t\t\treturn OptionalDouble.of(max);\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalDouble min()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalDouble.empty();\n\t\t\t}\n\t\t\tdouble min = current.min().getAsDouble();\n\t\t\tmin = iterators.reduce(min, (m, it) -> Math.min(m, it.min().orElse(m)));\n\t\t\trelease();\n\t\t\treturn OptionalDouble.of(min);\n\t\t}\n\n\t\t@Override\n\t\tpublic double sum()\n\t\t{\n\t\t\tdouble sum = iterators.reduce(current.sum(), (s, it) -> s + it.sum());\n\t\t\trelease();\n\t\t\treturn sum;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\tcurrent   = EmptyIterator.ofDouble();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of a chained Iterator.\n\t */\n\tpublic static class OfInt extends ChainedIterator<Integer, FunctionalPrimitiveIterator.OfInt> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/**\n\t\t * Constructor for an Iterator that chains Iterators provided in an Iterator.\n\t\t *\n\t\t * @param iterators an Iterator over Iterators to be chained\n\t\t */\n\t\tpublic OfInt(Iterator<? extends PrimitiveIterator.OfInt> iterators)\n\t\t{\n\t\t\tsuper(iterators);\n\t\t}\n\n\t\t/**\n\t\t * Constructor for chaining an Iterator and a number of Iterators provided in an Iterator.\n\t\t *\n\t\t * @param iterator  an Iterator to prepend the chain\n\t\t * @param iterators an Iterator over Iterators to be chained\n\t\t */\n\t\tpublic OfInt(PrimitiveIterator.OfInt iterator, Iterator<? extends PrimitiveIterator.OfInt> iterators)\n\t\t{\n\t\t\tsuper(iterator, iterators);\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn current.nextInt();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(int i)\n\t\t{\n\t\t\tboolean result = current.contains(i) || iterators.anyMatch(it -> it.contains(i));\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt max()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalInt.empty();\n\t\t\t}\n\t\t\tint max = current.max().getAsInt();\n\t\t\tmax = iterators.reduce(max, (int m, FunctionalPrimitiveIterator.OfInt it) -> Math.max(m, it.max().orElse(m)));\n\t\t\trelease();\n\t\t\treturn OptionalInt.of(max);\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt min()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalInt.empty();\n\t\t\t}\n\t\t\tint min = current.min().getAsInt();\n\t\t\tmin = iterators.reduce(min, (int m, FunctionalPrimitiveIterator.OfInt it) -> Math.min(m, it.min().orElse(m)));\n\t\t\trelease();\n\t\t\treturn OptionalInt.of(min);\n\t\t}\n\n\t\t@Override\n\t\tpublic long sum()\n\t\t{\n\t\t\tlong sum = iterators.reduce(current.sum(), (long s, FunctionalPrimitiveIterator.OfInt it) -> s + it.sum());\n\t\t\trelease();\n\t\t\treturn sum;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\tcurrent   = EmptyIterator.ofInt();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of a chained iterator.\n\t */\n\tpublic static class OfLong extends ChainedIterator<Long, FunctionalPrimitiveIterator.OfLong> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/**\n\t\t * Constructor for an Iterator that chains Iterators provided in an Iterator.\n\t\t *\n\t\t * @param iterators an Iterator over Iterators to be chained\n\t\t */\n\t\tpublic OfLong(Iterator<? extends PrimitiveIterator.OfLong> iterators)\n\t\t{\n\t\t\tsuper(iterators);\n\t\t}\n\n\t\t/**\n\t\t * Constructor for chaining an Iterator and a number of Iterators provided in an Iterator.\n\t\t *\n\t\t * @param iterator  an Iterator to prepend the chain\n\t\t * @param iterators an Iterator over Iterators to be chained\n\t\t */\n\t\tpublic OfLong(PrimitiveIterator.OfLong iterator, Iterator<? extends PrimitiveIterator.OfLong> iterators)\n\t\t{\n\t\t\tsuper(iterator, iterators);\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn current.nextLong();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(long l)\n\t\t{\n\t\t\tboolean result = current.contains(l) || iterators.anyMatch(it -> it.contains(l));\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalLong max()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalLong.empty();\n\t\t\t}\n\t\t\tlong max = current.max().getAsLong();\n\t\t\tmax = iterators.reduce(max, (long m, FunctionalPrimitiveIterator.OfLong it) -> Math.max(m, it.max().orElse(m)));\n\t\t\trelease();\n\t\t\treturn OptionalLong.of(max);\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalLong min()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalLong.empty();\n\t\t\t}\n\t\t\tlong min = current.min().getAsLong();\n\t\t\tmin = iterators.reduce(min, (long m, FunctionalPrimitiveIterator.OfLong it) -> Math.min(m, it.min().orElse(m)));\n\t\t\trelease();\n\t\t\treturn OptionalLong.of(min);\n\t\t}\n\n\t\t@Override\n\t\tpublic long sum()\n\t\t{\n\t\t\tlong sum = iterators.reduce(current.sum(), (long s, FunctionalPrimitiveIterator.OfLong it) -> s + it.sum());\n\t\t\trelease();\n\t\t\treturn sum;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\tcurrent   = EmptyIterator.ofLong();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/Distinct.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.HashSet;\nimport java.util.Set;\nimport java.util.function.DoublePredicate;\nimport java.util.function.IntPredicate;\nimport java.util.function.LongPredicate;\nimport java.util.function.Predicate;\n\n/**\n * Mutable predicate that tells whether it encounters an element the first time or not.\n *\n * @param <E> the type of the objects this predicate tests\n */\npublic abstract class Distinct<E>\n{\n\tprotected final Set<E> seen = new HashSet<>();\n\n\t/**\n\t * Answer whether the element has not been seen yet.\n\t *\n\t * @param element the element to be tested\n\t * @return true iff the element has not been seen yet\n\t */\n\tprotected boolean isUnseen(E element)\n\t{\n\t\treturn seen.add(element);\n\t}\n\n\t/**\n\t * Answer the elements that have already been seen.\n\t */\n\tpublic abstract FunctionalIterable<E> getSeen();\n\n\n\n\t/**\n\t * Mutable predicate for {@code Object} that tells whether it encounters an element the first time or not.\n\t * Elements are identified in terms of {@link Object#equals(Object)} which requires to be accompanied by a matching {@link Object#hashCode()} implementation.\n\t * This implementation uses a {@code HashSet} to store the elements it has already seen.\n\t *\n\t * @param <E> the type of the objects this predicate tests\n\t */\n\tpublic static class Of<E> extends Distinct<E> implements Predicate<E>\n\t{\n\t\t@Override\n\t\tpublic boolean test(E element)\n\t\t{\n\t\t\treturn super.isUnseen(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalIterable<E> getSeen()\n\t\t{\n\t\t\treturn Reducible.extend(seen);\n\t\t}\n\n\t}\n\n\n\n\t/**\n\t * Mutable predicate for {@code double} that tells whether it encounters an element the first time or not.\n\t * Elements are identified in terms of {@link ==} except for {@code NaN} for which all instances are consider equal, although {@code Double.NaN != Double.NaN}.\n\t * This implementation uses a {@code HashSet} to store the elements it has already seen.\n\t */\n\tpublic static class OfDouble extends Distinct<Double> implements DoublePredicate\n\t{\n\t\tboolean zeroSeen = false;\n\n\t\t@Override\n\t\tpublic boolean test(double value)\n\t\t{\n\t\t\tif (value == 0.0) {\n\t\t\t\t// Circumvent HashSet considering +0.0 != -0.0\n\t\t\t\tif (zeroSeen) {\n\t\t\t\t\treturn false;\n\t\t\t\t} else {\n\t\t\t\t\tzeroSeen = true;\n\t\t\t\t\tseen.add(value);\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// HashSet considers two Double.NaN instances to be equal\n\t\t\treturn super.isUnseen(value);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterable.OfDouble getSeen()\n\t\t{\n\t\t\treturn Reducible.unboxDouble(seen);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Mutable predicate for {@code int} that tells whether it encounters an element the first time or not.\n\t * Elements are identified in terms of {@link ==}.\n\t * This implementation uses a {@code HashSet} to store the elements it has already seen.\n\t */\n\tpublic static class OfInt extends Distinct<Integer> implements IntPredicate\n\t{\n\t\t@Override\n\t\tpublic boolean test(int value)\n\t\t{\n\t\t\treturn super.isUnseen(value);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterable.OfInt getSeen()\n\t\t{\n\t\t\treturn Reducible.unboxInt(seen);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Mutable predicate for {@code long} that tells whether it encounters an element the first time or not.\n\t * Elements are identified in terms of {@link ==}.\n\t * This implementation uses a {@code HashSet} to store the elements it has already seen.\n\t */\n\tpublic static class OfLong extends Distinct<Long> implements LongPredicate\n\t{\n\t\t@Override\n\t\tpublic boolean test(long value)\n\t\t{\n\t\t\treturn super.isUnseen(value);\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterable.OfLong getSeen()\n\t\t{\n\t\t\treturn Reducible.unboxLong(seen);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/EmptyIterable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\n/**\n * Abstract base class for empty Iterables.\n * The four natural implementations (generic, double, int, and long)\n * are implemented as Singletons and their instances accessible by a static method.\n *\n * @param <E> type of the Iterable's elements\n */\npublic abstract class EmptyIterable<E> implements FunctionalIterable<E>\n{\n\t/**\n\t * Get unique instance for elements of a generic type.\n\t *\n\t * @param <E> type of the Iterable's elements\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic static <E> Of<E> of()\n\t{\n\t\treturn (Of<E>) Of.OF;\n\t}\n\n\t/**\n\t * Get unique instance for {@code double} elements.\n\t */\n\tpublic static OfDouble ofDouble()\n\t{\n\t\treturn OfDouble.OF_DOUBLE;\n\t}\n\n\t/**\n\t * Get unique instance for {@code int} elements.\n\t */\n\tpublic static OfInt ofInt()\n\t{\n\t\treturn OfInt.OF_INT;\n\t}\n\n\t/**\n\t * Get unique instance for {@code long} elements.\n\t */\n\tpublic static OfLong ofLong()\n\t{\n\t\treturn OfLong.OF_LONG;\n\t}\n\n\n\n\t/**\n\t * Generic implementation of an empty Iterable as Singleton.\n\t *\n\t * @param <E> type of the Iterable's elements\n\t */\n\tpublic static class Of<E> extends EmptyIterable<E>\n\t{\n\t\t/** Singleton instance elements of a generic type */\n\t\tprivate static final Of<?> OF = new Of<>();\n\n\t\t/**\n\t\t * Private constructor for the Singleton instance.\n\t\t */\n\t\tprivate Of() {}\n\n\t\t@Override\n\t\tpublic EmptyIterator.Of<E> iterator()\n\t\t{\n\t\t\treturn EmptyIterator.of();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of an empty Iterable as Singleton.\n\t */\n\tpublic static class OfDouble extends EmptyIterable<Double> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/** Singleton instance for {@code double} elements */\n\t\tprivate static final EmptyIterable.OfDouble OF_DOUBLE = new EmptyIterable.OfDouble();\n\n\t\t/**\n\t\t * Private constructor for the Singleton instance.\n\t\t */\n\t\tprivate OfDouble() {}\n\t\n\t\t@Override\n\t\tpublic EmptyIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn EmptyIterator.ofDouble();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of an empty Iterable as Singleton.\n\t */\n\tpublic static class OfInt extends EmptyIterable<Integer> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/** Singleton instance for {@code int} elements */\n\t\tprivate static final EmptyIterable.OfInt OF_INT = new EmptyIterable.OfInt();\n\n\t\t/**\n\t\t * Private constructor for the Singleton instance.\n\t\t */\n\t\tprivate OfInt() {}\n\n\t\t@Override\n\t\tpublic EmptyIterator.OfInt iterator()\n\t\t{\n\t\t\treturn EmptyIterator.ofInt();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of an empty Iterable as Singleton.\n\t */\n\tpublic static class OfLong extends EmptyIterable<Long> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/** Singleton instance for {@code long} elements*/\n\t\tprivate static final EmptyIterable.OfLong OF_LONG = new EmptyIterable.OfLong();\n\n\t\t/**\n\t\t * Private constructor for the Singleton instance.\n\t\t */\n\t\tprivate OfLong() {}\n\n\t\t@Override\n\t\tpublic EmptyIterator.OfLong iterator()\n\t\t{\n\t\t\treturn EmptyIterator.ofLong();\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/common/iterable/EmptyIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.NoSuchElementException;\nimport java.util.OptionalDouble;\nimport java.util.OptionalInt;\nimport java.util.OptionalLong;\n\n/**\n * Abstract base class for empty Iterators.\n * The four natural implementations (generic, double, int, and long)\n * are implemented as Singletons and their instances accessible by a static method.\n *\n * @param <E> type of the Iterator's elements\n */\npublic abstract class EmptyIterator<E> implements FunctionalIterator<E>\n{\n\t/**\n\t * Get unique instance for elements of a generic type.\n\t *\n\t * @param <E> type of the Iterator's elements\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic static <E> Of<E> of()\n\t{\n\t\treturn (Of<E>) Of.OF;\n\t}\n\n\t/**\n\t * Get unique instance for {@code double} elements.\n\t */\n\tpublic static OfDouble ofDouble()\n\t{\n\t\treturn OfDouble.OF_DOUBLE;\n\t}\n\n\t/**\n\t * Get unique instance for {@code int} elements.\n\t */\n\tpublic static OfInt ofInt()\n\t{\n\t\treturn OfInt.OF_INT;\n\t}\n\n\t/**\n\t * Get unique instance for {@code long} elements.\n\t */\n\tpublic static OfLong ofLong()\n\t{\n\t\treturn OfLong.OF_LONG;\n\t}\n\n\t@Override\n\tpublic boolean hasNext()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic EmptyIterator<E> dedupe()\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic EmptyIterator<E> distinct()\n\t{\n\t\treturn this;\n\t}\n\n\n\n\t/**\n\t * Generic implementation of an empty Iterator as Singleton.\n\t *\n\t * @param <E> type of the Iterator's elements\n\t */\n\tpublic static class Of<E> extends EmptyIterator<E>\n\t{\n\t\t/** Singleton instance elements of a generic type */\n\t\tprivate static final Of<?> OF = new Of<>();\n\n\t\t/**\n\t\t * Private constructor for the Singleton instance.\n\t\t */\n\t\tprivate Of() {}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of an empty Iterator as Singleton.\n\t */\n\tpublic static class OfDouble extends EmptyIterator<Double> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/** Singleton instance for {@code double} elements */\n\t\tprivate static final EmptyIterator.OfDouble OF_DOUBLE = new EmptyIterator.OfDouble();\n\n\t\t/**\n\t\t * Private constructor for the Singleton instance.\n\t\t */\n\t\tprivate OfDouble() {}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\n\t\t@Override\n\t\tpublic EmptyIterator.OfDouble dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic EmptyIterator.OfDouble distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalDouble max()\n\t\t{\n\t\t\treturn OptionalDouble.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalDouble min()\n\t\t{\n\t\t\treturn max();\n\t\t}\n\n\t\t@Override\n\t\tpublic double sum()\n\t\t{\n\t\t\treturn 0.0;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of an empty Iterator as Singleton.\n\t */\n\tpublic static class OfInt extends EmptyIterator<Integer> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/** Singleton instance for {@code int} elements */\n\t\tprivate static final EmptyIterator.OfInt OF_INT = new EmptyIterator.OfInt();\n\n\t\t/**\n\t\t * Private constructor for the Singleton instance.\n\t\t */\n\t\tprivate OfInt() {}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\n\t\t@Override\n\t\tpublic EmptyIterator.OfInt dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic EmptyIterator.OfInt distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt max()\n\t\t{\n\t\t\treturn OptionalInt.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt min()\n\t\t{\n\t\t\treturn max();\n\t\t}\n\n\t\t@Override\n\t\tpublic long sum()\n\t\t{\n\t\t\treturn 0;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of an empty Iterator as Singleton.\n\t */\n\tpublic static class OfLong extends EmptyIterator<Long> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/** Singleton instance for {@code long} elements*/\n\t\tprivate static final EmptyIterator.OfLong OF_LONG = new EmptyIterator.OfLong();\n\n\t\t/**\n\t\t * Private constructor for the Singleton instance.\n\t\t */\n\t\tprivate OfLong() {}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\n\t\t@Override\n\t\tpublic EmptyIterator.OfLong dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic EmptyIterator.OfLong distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalLong max()\n\t\t{\n\t\t\treturn OptionalLong.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalLong min()\n\t\t{\n\t\t\treturn max();\n\t\t}\n\n\t\t@Override\n\t\tpublic long sum()\n\t\t{\n\t\t\treturn 0;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/FilteringIterable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Objects;\nimport java.util.function.DoublePredicate;\nimport java.util.function.IntPredicate;\nimport java.util.function.LongPredicate;\nimport java.util.function.Predicate;\n\n/**\n * Abstract base class for Iterables that filter elements by a predicate.\n * Returns only those elements for which the filter predicate evaluates to {@code true}.\n *\n * @param <E> type of the Iterable's elements\n * @param <I> type of the underlying Iterable\n */\npublic abstract class FilteringIterable<E, I extends Iterable<E>> implements FunctionalIterable<E>\n{\n\t/** The Iterable which elements are filtered */\n\tprotected final I iterable;\n\n\t/**\n\t * Constructor for a filtering Iterable without a predicate.\n\t *\n\t * @param iterable an Iterable to be filtered\n\t */\n\tpublic FilteringIterable(I iterable)\n\t{\n\t\tObjects.requireNonNull(iterable);\n\t\tthis.iterable = iterable;\n\t}\n\n\n\n\t/**\n\t * Generic implementation of a filtering Iterable.\n\t *\n\t * @param <E> type of the Iterable's elements\n\t */\n\tpublic static class Of<E> extends FilteringIterable<E, Iterable<E>>\n\t{\n\t\t/** The predicate the Iterable uses to filter the elements */\n\t\tprotected final Predicate<? super E> filter;\n\n\t\t/**\n\t\t * Constructor for an Iterable that filters elements by a predicate.\n\t\t * <p>\n\t\t * Attention! If the predicate is <em>stateful</em>, subsequent iterations may yield different elements.\n\t\t *\n\t\t * @param iterable an Iterable to be filtered\n\t\t * @param predicate a predicate used to filter the elements\n\t\t */\n\t\tpublic Of(Iterable<E> iterable, Predicate<? super E> predicate)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(predicate);\n\t\t\tthis.filter = predicate;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalIterator<E> iterator()\n\t\t{\n\t\t\treturn new FilteringIterator.Of<>(iterable.iterator(), filter);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of a filtering Iterable.\n\t */\n\tpublic static class OfDouble extends FilteringIterable<Double, PrimitiveIterable.OfDouble> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/** The predicate the Iterable uses to filter the elements */\n\t\tprotected final DoublePredicate filter;\n\n\t\t/**\n\t\t * Constructor for an Iterable that filters elements by a predicate.\n\t\t * <p>\n\t\t * Attention! If the predicate is <em>stateful</em>, subsequent iterations may yield different elements.\n\t\t *\n\t\t * @param iterable an Iterable to be filtered\n\t\t * @param predicate a predicate used to filter the elements\n\t\t */\n\t\tpublic OfDouble(PrimitiveIterable.OfDouble iterable, DoublePredicate predicate)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(predicate);\n\t\t\tthis.filter = predicate;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn new FilteringIterator.OfDouble(iterable.iterator(), filter);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of a filtering Iterable.\n\t */\n\tpublic static class OfInt extends FilteringIterable<Integer, PrimitiveIterable.OfInt> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/** The predicate the Iterable uses to filter the elements */\n\t\tprotected final IntPredicate filter;\n\n\t\t/**\n\t\t * Constructor for an Iterable that filters elements by a predicate.\n\t\t * <p>\n\t\t * Attention! If the predicate is <em>stateful</em>, subsequent iterations may yield different elements.\n\t\t *\n\t\t * @param iterable an Iterable to be filtered\n\t\t * @param predicate a predicate used to filter the elements\n\t\t */\n\t\tpublic OfInt(PrimitiveIterable.OfInt iterable, IntPredicate predicate)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(predicate);\n\t\t\tthis.filter = predicate;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t\t{\n\t\t\treturn new FilteringIterator.OfInt(iterable.iterator(), filter);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of a filtering Iterable.\n\t */\n\tpublic static class OfLong extends FilteringIterable<Long, PrimitiveIterable.OfLong> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/** The predicate the Iterable uses to filter the elements */\n\t\tprotected final LongPredicate filter;\n\n\t\t/**\n\t\t * Constructor for an Iterable that filters elements by a predicate.\n\t\t * <p>\n\t\t * Attention! If the predicate is <em>stateful</em>, subsequent iterations may yield different elements.\n\t\t *\n\t\t * @param iterable an Iterable to be filtered\n\t\t * @param predicate a predicate used to filter the elements\n\t\t */\n\t\tpublic OfLong(PrimitiveIterable.OfLong iterable, LongPredicate predicate)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(predicate);\n\t\t\tthis.filter = predicate;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfLong iterator()\n\t\t{\n\t\t\treturn new FilteringIterator.OfLong(iterable.iterator(), filter);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/FilteringIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Iterator;\nimport java.util.Objects;\nimport java.util.PrimitiveIterator;\nimport java.util.function.DoublePredicate;\nimport java.util.function.IntPredicate;\nimport java.util.function.LongPredicate;\nimport java.util.function.Predicate;\n\n/**\n * Abstract base class implementing an Iterator that filters elements by a predicate.\n * Returns only those elements for which the filter predicate evaluates to {@code true}.\n * <p>\n * The calls to {@code next()} of the underlying Iterator happen on-the-fly,\n * i.e., only when {@code next()} is called for this Iterator.\n * <p>\n * Implementations should release the underlying Iterator after iteration.\n * <p>\n * This Iterator does not support the {@code remove()} method, even if the underlying\n * Iterator support it.\n *\n * @param <E> type of the Iterator's elements\n * @param <I> type of the underlying Iterator\n */\npublic abstract class FilteringIterator<E, I extends Iterator<E>> implements FunctionalIterator<E>\n{\n\t/** The Iterator which elements are filtered */\n\tprotected I iterator;\n\t/** A flag indicating whether another element exists */\n\tprotected boolean hasNext;\n\n\t/**\n\t * Constructor for a FilteringIterator without a predicate.\n\t *\n\t * @param iterator an Iterator to be filtered\n\t */\n\tpublic FilteringIterator(I iterator)\n\t{\n\t\tObjects.requireNonNull(iterator);\n\t\tthis.iterator = iterator;\n\t}\n\n\t@Override\n\tpublic boolean hasNext()\n\t{\n\t\treturn hasNext;\n\t}\n\n\t@Override\n\tpublic void release()\n\t{\n\t\thasNext = false;\n\t}\n\n\t/**\n\t * Seek and store the next element for which the filter evaluates to {@code true}.\n\t */\n\tprotected abstract void seekNext();\n\n\n\n\n\t/**\n\t * Generic implementation of a FilteringIterator.\n\t *\n\t * @param <E> type of the Iterable's elements\n\t */\n\tpublic static class Of<E> extends FilteringIterator<E, Iterator<E>>\n\t{\n\t\t/** The predicate the Iterator uses to filter the elements */\n\t\tprotected final Predicate<E> filter;\n\t\t/** The next element for which the filter predicates evaluates to {@code true} */\n\t\tprotected E next;\n\n\t\t/**\n\t\t * Constructor for an Iterator that filters elements by a predicate.\n\t\t *\n\t\t * @param iterator an Iterator to be filtered\n\t\t * @param predicate a predicate used to filter the elements\n\t\t */\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tpublic Of(Iterator<E> iterator, Predicate<? super E> predicate)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(predicate);\n\t\t\tthis.filter = (Predicate<E>) predicate;\n\t\t\tseekNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\trequireNext();\n\t\t\tE current = next;\n\t\t\tseekNext();\n\t\t\treturn current;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\titerator = EmptyIterator.of();\n\t\t\tnext     = null;\n\t\t}\n\n\t\t@Override\n\t\tprotected void seekNext()\n\t\t{\n\t\t\twhile (iterator.hasNext()) {\n\t\t\t\tnext = iterator.next();\n\t\t\t\tif (filter.test(next)) {\n\t\t\t\t\thasNext = true;\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\trelease();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of a FilteringIterator.\n\t */\n\tpublic static class OfDouble extends FilteringIterator<Double, PrimitiveIterator.OfDouble> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/** The predicate the Iterator uses to filter the elements */\n\t\tprotected final DoublePredicate filter;\n\t\t/** The next element for which the filter predicates evaluates to {@code true} */\n\t\tprotected double next;\n\n\t\t/**\n\t\t * Constructor for an Iterator that filters elements by a predicate.\n\t\t *\n\t\t * @param iterator an Iterator to be filtered\n\t\t * @param predicate a predicate used to filter the elements\n\t\t */\n\t\tpublic OfDouble(PrimitiveIterator.OfDouble iterator, DoublePredicate predicate)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(predicate);\n\t\t\tthis.filter = predicate;\n\t\t\tseekNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\trequireNext();\n\t\t\tdouble current = next;\n\t\t\tseekNext();\n\t\t\treturn current;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\titerator = EmptyIterator.ofDouble();\n\t\t\tnext     = 0.0;\n\t\t}\n\n\t\t@Override\n\t\tprotected void seekNext()\n\t\t{\n\t\t\twhile (iterator.hasNext()) {\n\t\t\t\tnext = iterator.nextDouble();\n\t\t\t\tif (filter.test(next)) {\n\t\t\t\t\thasNext = true;\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\trelease();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of a FilteringIterator.\n\t */\n\tpublic static class OfInt extends FilteringIterator<Integer, PrimitiveIterator.OfInt> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/** The predicate the Iterator uses to filter the elements */\n\t\tprotected final IntPredicate filter;\n\t\t/** The next element for which the filter predicates evaluates to {@code true} */\n\t\tprotected int next;\n\n\t\t/**\n\t\t * Constructor for an Iterator that filters elements by a predicate.\n\t\t *\n\t\t * @param iterator an Iterator to be filtered\n\t\t * @param predicate a predicate used to filter the elements\n\t\t */\n\t\tpublic OfInt(PrimitiveIterator.OfInt iterator, IntPredicate predicate)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(predicate);\n\t\t\tthis.filter = predicate;\n\t\t\tseekNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\tint current = next;\n\t\t\tseekNext();\n\t\t\treturn current;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\titerator = EmptyIterator.ofInt();\n\t\t\tnext     = 0;\n\t\t}\n\n\t\t@Override\n\t\tprotected void seekNext()\n\t\t{\n\t\t\twhile (iterator.hasNext()) {\n\t\t\t\tnext = iterator.nextInt();\n\t\t\t\tif (filter.test(next)) {\n\t\t\t\t\thasNext = true;\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\thasNext = false;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of a FilteringIterator.\n\t */\n\tpublic static class OfLong extends FilteringIterator<Long, PrimitiveIterator.OfLong> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/** The predicate the Iterator uses to filter the elements */\n\t\tprotected final LongPredicate filter;\n\t\t/** The next element for which the filter predicates evaluates to {@code true} */\n\t\tprotected long next;\n\n\t\t/**\n\t\t * Constructor for an Iterator that filters elements by a predicate.\n\t\t *\n\t\t * @param iterator an Iterator to be filtered\n\t\t * @param predicate a predicate used to filter the elements\n\t\t */\n\t\tpublic OfLong(PrimitiveIterator.OfLong iterator, LongPredicate predicate)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(predicate);\n\t\t\tthis.filter = predicate;\n\t\t\tseekNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\trequireNext();\n\t\t\tlong current = next;\n\t\t\tseekNext();\n\t\t\treturn current;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\titerator = EmptyIterator.ofLong();\n\t\t\tnext     = 0;\n\t\t}\n\n\t\t@Override\n\t\tprotected void seekNext()\n\t\t{\n\t\t\twhile (iterator.hasNext()) {\n\t\t\t\tnext = iterator.nextLong();\n\t\t\t\tif (filter.test(next)) {\n\t\t\t\t\thasNext = true;\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t\thasNext = false;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/FunctionalIterable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport common.functions.DoubleObjToDoubleFunction;\nimport common.functions.IntObjToIntFunction;\nimport common.functions.LongObjToLongFunction;\n\nimport java.util.Optional;\nimport java.util.function.*;\n\n/**\n * A base type that implements the <em>transformation</em> and <em>accumulation</em> operations from {@link Reducible} for {@link Iterable}s.\n * Additionally, it provides the methods {@link FunctionalIterable#flatMap} and its primitive specializations\n * {@link FunctionalIterable#flatMapToDouble}, {@link FunctionalIterable#flatMapToInt} and {@link FunctionalIterable#flatMapToLong}.\n *\n * @param <E> the type of elements returned by this Iterable\n */\npublic interface FunctionalIterable<E> extends Reducible<E, Iterable<? extends E>>, Iterable<E>\n{\n\t// Bridging methods to Iterator-based code\n\n\t/**\n\t * Create a FunctionalIterable over the given elements.\n\t *\n\t * @param elements the elements\n\t * @param <E> the type of the elements\n\t * @return a FunctionalIterable over the elements\n\t */\n\t@SafeVarargs\n\tstatic <E> FunctionalIterable<E> of(E ... elements)\n\t{\n\t\tswitch (elements.length) {\n\t\t\tcase 0: return EmptyIterable.of();\n\t\t\tcase 1: return new SingletonIterable.Of<>(elements[0]);\n\t\t\tdefault: return new IterableArray.Of<>(elements);\n\t\t}\n\t}\n\n\t/**\n\t * Create a FunctionalPrimitiveIterable.OfDouble over the given doubles.\n\t *\n\t * @param numbers the doubles\n\t * @return a FunctionalPrimitiveIterable.OfDouble over the doubles\n\t */\n\tstatic FunctionalPrimitiveIterable.OfDouble ofDouble(double ... numbers)\n\t{\n\t\tswitch (numbers.length) {\n\t\t\tcase 0: return EmptyIterable.ofDouble();\n\t\t\tcase 1: return new SingletonIterable.OfDouble(numbers[0]);\n\t\t\tdefault: return new IterableArray.OfDouble(numbers);\n\t\t}\n\t}\n\n\t/**\n\t * Create a FunctionalPrimitiveIterable.OfInt over the given ints.\n\t *\n\t * @param numbers the ints\n\t * @return a FunctionalPrimitiveIterable.OfInt over the ints\n\t */\n\tstatic FunctionalPrimitiveIterable.OfInt ofInt(int ... numbers)\n\t{\n\t\tswitch (numbers.length) {\n\t\t\tcase 0: return EmptyIterable.ofInt();\n\t\t\tcase 1: return new SingletonIterable.OfInt(numbers[0]);\n\t\t\tdefault: return new IterableArray.OfInt(numbers);\n\t\t}\n\t}\n\n\t/**\n\t * Create a FunctionalPrimitiveIterable.OfLong over the given longs.\n\t *\n\t * @param numbers the longs\n\t * @return a FunctionalPrimitiveIterable.OfLong over the longs\n\t */\n\tstatic FunctionalPrimitiveIterable.OfLong ofLong(long ... numbers)\n\t{\n\t\tswitch (numbers.length) {\n\t\t\tcase 0: return EmptyIterable.ofLong();\n\t\t\tcase 1: return new SingletonIterable.OfLong(numbers[0]);\n\t\t\tdefault: return new IterableArray.OfLong(numbers);\n\t\t}\n\t}\n\n\n\n\t// Fundamental methods\n\n\t@Override\n\tFunctionalIterator<E> iterator();\n\n\t@Override\n\tdefault void forEach(Consumer<? super E> action)\n\t{\n\t\titerator().forEach(action);\n\t}\n\n\t@Override\n\tdefault boolean isEmpty()\n\t{\n\t\treturn !iterator().hasNext();\n\t}\n\n\n\n\t// Transforming Methods\n\n\t@Override\n\tdefault FunctionalIterable<E> concat(Iterable<? extends E> iterable)\n\t{\n\t\treturn new ChainedIterable.Of<>(new IterableArray.Of<>(this, iterable));\n\t}\n\n\t@Override\n\tdefault FunctionalIterable<E> dedupe()\n\t{\n\t\treturn (FunctionalIterable<E>) Reducible.super.dedupe();\n\t}\n\n\t@Override\n\tdefault FunctionalIterable<E> distinct()\n\t{\n\t\treturn (FunctionalIterable<E>) Reducible.super.distinct();\n\t}\n\n\t@Override\n\tdefault FunctionalIterable<E> filter(Predicate<? super E> predicate)\n\t{\n\t\treturn new FilteringIterable.Of<>(this, predicate);\n\t}\n\n\t/**\n\t * Map each element to an Iterable and concatenate the obtained Iterables.\n\t *\n\t * @param function a function that maps each element to an {@link Iterable}\n\t */\n\tdefault <T> FunctionalIterable<T> flatMap(Function<? super E, ? extends Iterable<? extends T>> function)\n\t{\n\t\treturn new ChainedIterable.Of<>(map(function));\n\t}\n\n\t/**\n\t * Map each element to an FunctionalPrimitiveIterable.OfDouble and concatenate the obtained Iterables.\n\t *\n\t * @param function a function that maps each element to an {@link FunctionalPrimitiveIterable.OfDouble}\n\t */\n\tdefault FunctionalPrimitiveIterable.OfDouble flatMapToDouble(Function<? super E, PrimitiveIterable.OfDouble> function)\n\t{\n\t\treturn new ChainedIterable.OfDouble(map(function));\n\t}\n\n\t/**\n\t * Map each element to an FunctionalPrimitiveIterable.OfInt and concatenate the obtained Iterables.\n\t *\n\t * @param function a function that maps each element to an {@link FunctionalPrimitiveIterable.OfInt}\n\t */\n\tdefault FunctionalPrimitiveIterable.OfInt flatMapToInt(Function<? super E, PrimitiveIterable.OfInt> function)\n\t{\n\t\treturn new ChainedIterable.OfInt(map(function));\n\t}\n\n\t/**\n\t * Map each element to an FunctionalPrimitiveIterable.OfLong and concatenate the obtained Iterables.\n\t *\n\t * @param function a function that maps each element to an {@link FunctionalPrimitiveIterable.OfLong}\n\t */\n\tdefault FunctionalPrimitiveIterable.OfLong flatMapToLong(Function<? super E, PrimitiveIterable.OfLong> function)\n\t{\n\t\treturn new ChainedIterable.OfLong(map(function));\n\t}\n\n\t@Override\n\tdefault <T> FunctionalIterable<T> map(Function<? super E, ? extends T> function)\n\t{\n\t\treturn new MappingIterable.ObjToObj<>(this, function);\n\t}\n\n\t@Override\n\tdefault FunctionalPrimitiveIterable.OfDouble mapToDouble(ToDoubleFunction<? super E> function)\n\t{\n\t\treturn new MappingIterable.ObjToDouble<>(this, function);\n\t}\n\n\t@Override\n\tdefault FunctionalPrimitiveIterable.OfInt mapToInt(ToIntFunction<? super E> function)\n\t{\n\t\treturn new MappingIterable.ObjToInt<>(this, function);\n\t}\n\n\t@Override\n\tdefault FunctionalPrimitiveIterable.OfLong mapToLong(ToLongFunction<? super E> function)\n\t{\n\t\treturn new MappingIterable.ObjToLong<>(this, function);\n\t}\n\n\t@Override\n\tdefault FunctionalIterable<E> nonNull()\n\t{\n\t\treturn (FunctionalIterable<E>) Reducible.super.nonNull();\n\t}\n\n\n\n\t// Accumulations Methods (Consuming)\n\n\t@Override\n\tdefault FunctionalIterable<E> consume()\n\t{\n\t\treturn (FunctionalIterable<E>) Reducible.super.consume();\n\t}\n\n\t@Override\n\tdefault E detect(Predicate<? super E> predicate)\n\t{\n\t\treturn iterator().detect(predicate);\n\t}\n\n\t@Override\n\tdefault Optional<E> reduce(BinaryOperator<E> accumulator)\n\t{\n\t\treturn iterator().reduce(accumulator);\n\t}\n\n\t@Override\n\tdefault <T> T reduce(T init, BiFunction<T, ? super E, T> accumulator)\n\t{\n\t\treturn iterator().reduce(init, accumulator);\n\t}\n\n\t@Override\n\tdefault double reduce(double init, DoubleObjToDoubleFunction<? super E> accumulator)\n\t{\n\t\treturn iterator().reduce(init, accumulator);\n\t}\n\n\t@Override\n\tdefault int reduce(int init, IntObjToIntFunction<? super E> accumulator)\n\t{\n\t\treturn iterator().reduce(init, accumulator);\n\t}\n\n\t@Override\n\tdefault long reduce(long init, LongObjToLongFunction<? super E> accumulator)\n\t{\n\t\treturn iterator().reduce(init, accumulator);\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/FunctionalIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport common.functions.DoubleObjToDoubleFunction;\nimport common.functions.IntObjToIntFunction;\nimport common.functions.LongObjToLongFunction;\n\nimport java.util.*;\nimport java.util.function.*;\n\n/**\n * A base type that implements the <em>transformation</em> and <em>accumulation</em> operations from {@link Reducible} for {@link Iterator}s.\n * Additionally, it provides the methods {@link FunctionalIterator#flatMap} and its primitive specializations\n * {@link FunctionalIterator#flatMapToDouble}, {@link FunctionalIterator#flatMapToInt} and {@link FunctionalIterator#flatMapToLong}.\n *\n * @param <E> the type of elements returned by this Iterator\n */\npublic interface FunctionalIterator<E> extends Reducible<E, Iterator<? extends E>>, Iterator<E>\n{\n\t// Bridging methods to Iterator-based code\n\n\t/**\n\t * Create a FunctionalIterator over the given elements.\n\t *\n\t * @param elements the elements\n\t * @param <E> the type of the elements\n\t * @return a FunctionalIterator over the elements\n\t */\n\t@SafeVarargs\n\tstatic <E> FunctionalIterator<E> of(E ... elements)\n\t{\n\t\tswitch (elements.length) {\n\t\t\tcase 0: return EmptyIterator.of();\n\t\t\tcase 1: return new SingletonIterator.Of<>(elements[0]);\n\t\t\tdefault: return new ArrayIterator.Of<>(elements);\n\t\t}\n\t}\n\n\t/**\n\t * Create a FunctionalPrimitiveIterator.OfDouble over the given doubles.\n\t *\n\t * @param numbers the doubles\n\t * @return a FunctionalPrimitiveIterator.OfDouble over the doubles\n\t */\n\tstatic FunctionalPrimitiveIterator.OfDouble ofDouble(double ... numbers)\n\t{\n\t\tswitch (numbers.length) {\n\t\t\tcase 0: return EmptyIterator.ofDouble();\n\t\t\tcase 1: return new SingletonIterator.OfDouble(numbers[0]);\n\t\t\tdefault: return new ArrayIterator.OfDouble(numbers);\n\t\t}\n\t}\n\n\t/**\n\t * Create a FunctionalPrimitiveIterator.OfInt over the given ints.\n\t *\n\t * @param numbers the ints\n\t * @return a FunctionalPrimitiveIterator.OfInt over the ints\n\t */\n\tstatic FunctionalPrimitiveIterator.OfInt ofInt(int ... numbers)\n\t{\n\t\tswitch (numbers.length) {\n\t\t\tcase 0: return EmptyIterator.ofInt();\n\t\t\tcase 1: return new SingletonIterator.OfInt(numbers[0]);\n\t\t\tdefault: return new ArrayIterator.OfInt(numbers);\n\t\t}\n\t}\n\n\t/**\n\t * Create a FunctionalPrimitiveIterator.OfLong over the given longs.\n\t *\n\t * @param numbers the longs\n\t * @return a FunctionalPrimitiveIterator.OfLong over the longs\n\t */\n\tstatic FunctionalPrimitiveIterator.OfLong ofLong(long ... numbers)\n\t{\n\t\tswitch (numbers.length) {\n\t\t\tcase 0: return EmptyIterator.ofLong();\n\t\t\tcase 1: return new SingletonIterator.OfLong(numbers[0]);\n\t\t\tdefault: return new ArrayIterator.OfLong(numbers);\n\t\t}\n\t}\n\n\n\n\t// Fundamental methods\n\n\t@Override\n\tdefault void forEach(Consumer<? super E> action)\n\t{\n\t\tunwrap().forEachRemaining(action);\n\t\trelease();\n\t}\n\n\t@Override\n\tdefault boolean isEmpty()\n\t{\n\t\treturn ! hasNext();\n\t}\n\n\t/**\n\t * Unwrap a nested iterator if this instance is an adapting wrapper.\n\t * Use to avoid repeated indirections, especially in loops.\n\t * \n\t * @return {@code this} instance\n\t */\n\tdefault Iterator<E> unwrap()\n\t{\n\t\treturn this;\n\t}\n\n\t/**\n\t * Release resources such as wrapped Iterators making this Iterator empty.\n\t * Should be called internally after an Iterator is exhausted.\n\t */\n\tdefault void release()\n\t{\n\t\t// no-op\n\t}\n\n\t/**\n\t * Check that there is a next element, throw if not.\n\t *\n\t * @throws NoSuchElementException if Iterator is exhausted\n\t */\n\tdefault void requireNext()\n\t{\n\t\tif (!hasNext()) {\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\t}\n\n\n\n\t// Transforming Methods\n\n\t@Override\n\tdefault FunctionalIterator<E> concat(Iterator<? extends E> iterator)\n\t{\n\t\treturn new ChainedIterator.Of<>(unwrap(), new ArrayIterator.Of<>(iterator));\n\t}\n\n\t@Override\n\tdefault FunctionalIterator<E> dedupe()\n\t{\n\t\treturn (FunctionalIterator<E>) Reducible.super.dedupe();\n\t}\n\n\t@Override\n\tdefault FunctionalIterator<E> distinct()\n\t{\n\t\treturn (FunctionalIterator<E>) Reducible.super.distinct();\n\t}\n\n\t@Override\n\tdefault FunctionalIterator<E> filter(Predicate<? super E> predicate)\n\t{\n\t\treturn new FilteringIterator.Of<>(unwrap(), predicate);\n\t}\n\n\t/**\n\t * Map each element to an Iterator and concatenate the obtained Iterators.\n\t *\n\t * @param function a function that maps each element to an {@link Iterator}\n\t */\n\tdefault <T> FunctionalIterator<T> flatMap(Function<? super E, ? extends Iterator<? extends T>> function)\n\t{\n\t\treturn new ChainedIterator.Of<>(map(function));\n\t}\n\n\t/**\n\t * Map each element to a PrimitiveIterator over {@code double} and concatenate the obtained Iterators.\n\t *\n\t * @param function a function that maps each element to an {@link PrimitiveIterator.OfDouble}\n\t */\n\tdefault FunctionalPrimitiveIterator.OfDouble flatMapToDouble(Function<? super E, PrimitiveIterator.OfDouble> function)\n\t{\n\t\treturn new ChainedIterator.OfDouble(map(function));\n\t}\n\n\t/**\n\t * Map each element to a PrimitiveIterator over {@code int} and concatenate the obtained Iterators.\n\t *\n\t * @param function a function that maps each element to an {@link PrimitiveIterator.OfInt}\n\t */\n\tdefault FunctionalPrimitiveIterator.OfInt flatMapToInt(Function<? super E, PrimitiveIterator.OfInt> function)\n\t{\n\t\treturn new ChainedIterator.OfInt(map(function));\n\t}\n\n\t/**\n\t * Map each element to a PrimitiveIterator over {@code long} and concatenate the obtained Iterators.\n\t *\n\t * @param function a function that maps each element to an {@link PrimitiveIterator.OfLong}\n\t */\n\tdefault FunctionalPrimitiveIterator.OfLong flatMapToLong(Function<? super E, PrimitiveIterator.OfLong> function)\n\t{\n\t\treturn new ChainedIterator.OfLong(map(function));\n\t}\n\n\t@Override\n\tdefault <T> FunctionalIterator<T> map(Function<? super E, ? extends T> function)\n\t{\n\t\treturn new MappingIterator.ObjToObj<>(unwrap(), function);\n\t}\n\n\t@Override\n\tdefault FunctionalPrimitiveIterator.OfDouble mapToDouble(ToDoubleFunction<? super E> function)\n\t{\n\t\treturn new MappingIterator.ObjToDouble<>(unwrap(), function);\n\t}\n\n\t@Override\n\tdefault FunctionalPrimitiveIterator.OfInt mapToInt(ToIntFunction<? super E> function)\n\t{\n\t\treturn new MappingIterator.ObjToInt<>(unwrap(), function);\n\t}\n\t@Override\n\tdefault FunctionalPrimitiveIterator.OfLong mapToLong(ToLongFunction<? super E> function)\n\t{\n\t\treturn new MappingIterator.ObjToLong<>(unwrap(), function);\n\t}\n\n\t@Override\n\tdefault FunctionalIterator<E> nonNull()\n\t{\n\t\treturn (FunctionalIterator<E>) Reducible.super.nonNull();\n\t}\n\n\n\n\t// Accumulations Methods (Consuming)\n\n\t@Override\n\tdefault FunctionalIterator<E> consume()\n\t{\n\t\treturn (FunctionalIterator<E>) Reducible.super.consume();\n\t}\n\n\t@Override\n\tdefault E detect(Predicate<? super E> predicate)\n\t{\n\t\treturn filter(predicate).next();\n\t}\n\n\t@Override\n\tdefault Optional<E> reduce(BinaryOperator<E> accumulator)\n\t{\n\t\tObjects.requireNonNull(accumulator);\n\t\tif (! hasNext()) {\n\t\t\treturn Optional.empty();\n\t\t}\n\t\treturn Optional.of(reduce(next(), accumulator));\n\t}\n\n\t@Override\n\tdefault <T> T reduce(T init, BiFunction<T, ? super E, T> accumulator)\n\t{\n\t\tObjects.requireNonNull(accumulator);\n\t\t// avoid redirection in wrappers\n\t\tIterator<E> local = unwrap();\n\t\tT result  = init;\n\t\twhile (local.hasNext()) {\n\t\t\tresult = accumulator.apply(result, local.next());\n\t\t}\n\t\trelease();\n\t\treturn result;\n\t}\n\n\t@Override\n\tdefault double reduce(double init, DoubleObjToDoubleFunction<? super E> accumulator)\n\t{\n\t\tObjects.requireNonNull(accumulator);\n\t\t// avoid redirection in wrappers\n\t\tIterator<E> local = unwrap();\n\t\tdouble result = init;\n\t\twhile (local.hasNext()) {\n\t\t\tresult = accumulator.applyAsDouble(result, local.next());\n\t\t}\n\t\trelease();\n\t\treturn result;\n\t}\n\n\t@Override\n\tdefault int reduce(int init, IntObjToIntFunction<? super E> accumulator)\n\t{\n\t\tObjects.requireNonNull(accumulator);\n\t\t// avoid redirection in wrappers\n\t\tIterator<E> local = unwrap();\n\t\tint result = init;\n\t\twhile (local.hasNext()) {\n\t\t\tresult = accumulator.applyAsInt(result, local.next());\n\t\t}\n\t\trelease();\n\t\treturn result;\n\t}\n\n\t@Override\n\tdefault long reduce(long init, LongObjToLongFunction<? super E> accumulator)\n\t{\n\t\tObjects.requireNonNull(accumulator);\n\t\t// avoid redirection in wrappers\n\t\tIterator<E> local = unwrap();\n\t\tlong result = init;\n\t\twhile (local.hasNext()) {\n\t\t\tresult = accumulator.applyAsLong(result, local.next());\n\t\t}\n\t\trelease();\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/FunctionalPrimitiveIterable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport common.functions.*;\n\nimport java.util.OptionalDouble;\nimport java.util.OptionalInt;\nimport java.util.OptionalLong;\nimport java.util.function.*;\n\n/**\n * A base type for primitive specializations of the methods provided by {@link FunctionalIterable}.\n * Specialized sub interfaces are provided for {@code double}, {@code int} and {@code long}:\n * <ul>\n *     <li>{@link PrimitiveIterable.OfDouble double}</li>\n *     <li>{@link PrimitiveIterable.OfInt int}</li>\n *     <li>{@link PrimitiveIterable.OfLong long}</li>\n * </ul>\n *\n * @param <E>      the type of elements hold by this PrimitiveIterable\n * @param <E_CONS> the type of primitive consumer\n */\npublic interface FunctionalPrimitiveIterable<E, E_CONS> extends PrimitiveReducible<E, Iterable<? extends E>, E_CONS>, FunctionalIterable<E>, PrimitiveIterable<E, E_CONS>\n{\n\t@Override\n\tFunctionalPrimitiveIterator<E, E_CONS> iterator();\n\n\t@Override\n\tdefault void forEach(E_CONS action)\n\t{\n\t\titerator().forEach(action);\n\t}\n\n\n\t/**\n\t * Specialisation for {@code double} of a FunctionalPrimitiveIterable.\n\t */\n\tinterface OfDouble extends FunctionalPrimitiveIterable<Double, DoubleConsumer>, PrimitiveReducible.OfDouble<Iterable<? extends Double>>, PrimitiveIterable.OfDouble\n\t{\n\t\t@Override\n\t\tFunctionalPrimitiveIterator.OfDouble iterator();\n\n\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault FunctionalIterable<Double> concat(Iterable<? extends Double> iterable)\n\t\t{\n\t\t\tif (iterable instanceof PrimitiveIterable.OfDouble) {\n\t\t\t\treturn concat((PrimitiveIterable.OfDouble) iterable);\n\t\t\t}\n\t\t\treturn FunctionalPrimitiveIterable.super.concat(iterable);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code concat} for {@code double}.\n\t\t *\n\t\t * @param iterable the {@link PrimitiveIterable.OfDouble} to append\n\t\t * @return an {@link Iterable} that iterates over the elements of the receiver and the argument\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfDouble concat(PrimitiveIterable.OfDouble iterable)\n\t\t{\n\t\t\treturn new ChainedIterable.OfDouble(new IterableArray.Of<>(this, iterable));\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble dedupe()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfDouble) PrimitiveReducible.OfDouble.super.dedupe();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble distinct()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfDouble) PrimitiveReducible.OfDouble.super.distinct();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble filter(DoublePredicate predicate)\n\t\t{\n\t\t\treturn new FilteringIterable.OfDouble(this, predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMap} for {@code double}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMap(java.util.function.Function)\n\t\t */\n\t\tdefault <T> FunctionalIterable<T> flatMap(DoubleFunction<? extends Iterable<? extends T>> function)\n\t\t{\n\t\t\treturn new ChainedIterable.Of<>(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToDouble} for {@code double}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToDouble(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfDouble flatMapToDouble(DoubleFunction<PrimitiveIterable.OfDouble> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfDouble(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToInt} for {@code double}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToInt(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfInt flatMapToInt(DoubleFunction<PrimitiveIterable.OfInt> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfInt(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToLong} for {@code double}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToLong(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfLong flatMapToLong(DoubleFunction<PrimitiveIterable.OfLong> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfLong(map(function));\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> FunctionalIterable<T> map(DoubleFunction<? extends T> function)\n\t\t{\n\t\t\treturn new MappingIterable.DoubleToObj<>(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble mapToDouble(DoubleUnaryOperator function)\n\t\t{\n\t\t\treturn new MappingIterable.DoubleToDouble(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt mapToInt(DoubleToIntFunction function)\n\t\t{\n\t\t\treturn new MappingIterable.DoubleToInt(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong mapToLong(DoubleToLongFunction function)\n\t\t{\n\t\t\treturn new MappingIterable.DoubleToLong(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble nonNull()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble consume()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfDouble) PrimitiveReducible.OfDouble.super.consume();\n\t\t}\n\n\t\t@Override\n\t\tdefault double detect(DoublePredicate predicate)\n\t\t{\n\t\t\treturn iterator().detect(predicate);\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalDouble reduce(DoubleBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> T reduce(T init, ObjDoubleFunction<T, T> accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault double reduce(double init, DoubleBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault int reduce(int init, IntDoubleToIntFunction accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault long reduce(long init, LongDoubleToLongFunction accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\t}\n\n\n\t/**\n\t * Specialisation for {@code int} of a FunctionalPrimitiveIterable.\n\t */\n\tinterface OfInt extends FunctionalPrimitiveIterable<Integer, IntConsumer>, PrimitiveReducible.OfInt<Iterable<? extends Integer>>, PrimitiveIterable.OfInt\n\t{\n\t\t@Override\n\t\tFunctionalPrimitiveIterator.OfInt iterator();\n\n\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault FunctionalIterable<Integer> concat(Iterable<? extends Integer> iterable)\n\t\t{\n\t\t\tif (iterable instanceof PrimitiveIterable.OfInt) {\n\t\t\t\treturn concat((PrimitiveIterable.OfInt) iterable);\n\t\t\t}\n\t\t\treturn FunctionalPrimitiveIterable.super.concat(iterable);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code concat} for {@code int}.\n\t\t *\n\t\t * @param iterable the {@link PrimitiveIterable.OfInt} to append\n\t\t * @return an {@link Iterable} that iterates over the elements of the receiver and the argument\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfInt concat(PrimitiveIterable.OfInt iterable)\n\t\t{\n\t\t\treturn new ChainedIterable.OfInt(new IterableArray.Of<>(this, iterable));\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt dedupe()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfInt) PrimitiveReducible.OfInt.super.dedupe();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt distinct()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfInt) PrimitiveReducible.OfInt.super.distinct();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt filter(IntPredicate predicate)\n\t\t{\n\t\t\treturn new FilteringIterable.OfInt(this, predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMap} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMap(java.util.function.Function)\n\t\t */\n\t\tdefault <T> FunctionalIterable<T> flatMap(IntFunction<? extends Iterable<? extends T>> function)\n\t\t{\n\t\t\treturn new ChainedIterable.Of<>(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToDouble} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToDouble(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfDouble flatMapToDouble(IntFunction<PrimitiveIterable.OfDouble> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfDouble(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToInt} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToInt(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfInt flatMapToInt(IntFunction<PrimitiveIterable.OfInt> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfInt(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToLong} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToLong(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfLong flatMapToLong(IntFunction<PrimitiveIterable.OfLong> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfLong(map(function));\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> FunctionalIterable<T> map(IntFunction<? extends T> function)\n\t\t{\n\t\t\treturn new MappingIterable.IntToObj<>(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble mapToDouble(IntToDoubleFunction function)\n\t\t{\n\t\t\treturn new MappingIterable.IntToDouble(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt mapToInt(IntUnaryOperator function)\n\t\t{\n\t\t\treturn new MappingIterable.IntToInt(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong mapToLong(IntToLongFunction function)\n\t\t{\n\t\t\treturn new MappingIterable.IntToLong(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt nonNull()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt consume()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfInt) PrimitiveReducible.OfInt.super.consume();\n\t\t}\n\n\t\t@Override\n\t\tdefault int detect(IntPredicate predicate)\n\t\t{\n\t\t\treturn iterator().detect(predicate);\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalDouble reduce(DoubleBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalInt reduce(IntBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalLong reduce(LongBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> T reduce(T init, ObjIntFunction<T, T> accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault double reduce(double init, DoubleBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault int reduce(int init, IntBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault long reduce(long init, LongBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\t}\n\n\n\t/**\n\t * Specialisation for {@code long} of a FunctionalPrimitiveIterable.\n\t */\n\tinterface OfLong extends FunctionalPrimitiveIterable<Long, LongConsumer>, PrimitiveReducible.OfLong<Iterable<? extends Long>>, PrimitiveIterable.OfLong\n\t{\n\t\t@Override\n\t\tFunctionalPrimitiveIterator.OfLong iterator();\n\n\n\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault FunctionalIterable<Long> concat(Iterable<? extends Long> iterable)\n\t\t{\n\t\t\tif (iterable instanceof PrimitiveIterable.OfLong) {\n\t\t\t\treturn concat((PrimitiveIterable.OfLong) iterable);\n\t\t\t}\n\t\t\treturn FunctionalPrimitiveIterable.super.concat(iterable);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code concat} for {@code long}.\n\t\t *\n\t\t * @param iterable the {@link PrimitiveIterable.OfLong} to append\n\t\t * @return an {@link Iterable} that iterates over the elements of the receiver and the argument\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfLong concat(PrimitiveIterable.OfLong iterable)\n\t\t{\n\t\t\treturn new ChainedIterable.OfLong(new IterableArray.Of<>(this, iterable));\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong dedupe()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfLong) PrimitiveReducible.OfLong.super.dedupe();\n\t\t}\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong distinct()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfLong) PrimitiveReducible.OfLong.super.distinct();\n\t\t}\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong filter(LongPredicate predicate)\n\t\t{\n\t\t\treturn new FilteringIterable.OfLong(this, predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMap} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMap(java.util.function.Function)\n\t\t */\n\t\tdefault <T> FunctionalIterable<T> flatMap(LongFunction<? extends Iterable<? extends T>> function)\n\t\t{\n\t\t\treturn new ChainedIterable.Of<>(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToDouble} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToDouble(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfDouble flatMapToDouble(LongFunction<PrimitiveIterable.OfDouble> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfDouble(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToInt} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToInt(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfInt flatMapToInt(LongFunction<PrimitiveIterable.OfInt> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfInt(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToLong} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterable#flatMapToLong(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterable.OfLong flatMapToLong(LongFunction<PrimitiveIterable.OfLong> function)\n\t\t{\n\t\t\treturn new ChainedIterable.OfLong(map(function));\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> FunctionalIterable<T> map(LongFunction<? extends T> function)\n\t\t{\n\t\t\treturn new MappingIterable.LongToObj<>(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble mapToDouble(LongToDoubleFunction function)\n\t\t{\n\t\t\treturn new MappingIterable.LongToDouble(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt mapToInt(LongToIntFunction function)\n\t\t{\n\t\t\treturn new MappingIterable.LongToInt(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong mapToLong(LongUnaryOperator function)\n\t\t{\n\t\t\treturn new MappingIterable.LongToLong(this, function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong nonNull()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong consume()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterable.OfLong) PrimitiveReducible.OfLong.super.consume();\n\t\t}\n\n\t\t@Override\n\t\tdefault long detect(LongPredicate predicate)\n\t\t{\n\t\t\treturn iterator().detect(predicate);\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalLong reduce(LongBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> T reduce(T init, ObjLongFunction<T, T> accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault double reduce(double init, DoubleLongToDoubleFunction accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault int reduce(int init, IntLongToIntFunction accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\n\t\t@Override\n\t\tdefault long reduce(long init, LongBinaryOperator accumulator)\n\t\t{\n\t\t\treturn iterator().reduce(init, accumulator);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/FunctionalPrimitiveIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport common.functions.*;\n\nimport java.util.*;\nimport java.util.function.*;\n\n/**\n * A base type for primitive specializations of the methods provided by {@link FunctionalIterator}.\n * Specialized sub interfaces are provided for {@code double}, {@code int} and {@code long}:\n * <ul>\n *     <li>{@link PrimitiveIterator.OfDouble double}</li>\n *     <li>{@link PrimitiveIterator.OfInt int}</li>\n *     <li>{@link PrimitiveIterator.OfLong long}</li>\n * </ul>\n *\n * @param <E> the type of elements returned by this PrimitiveIterator\n * @param <E_CONS> the type of primitive consumer\n */\npublic interface FunctionalPrimitiveIterator<E, E_CONS> extends PrimitiveReducible<E, Iterator<? extends E>, E_CONS>,FunctionalIterator<E>, PrimitiveIterator<E, E_CONS>\n{\n\t@Override\n\tdefault void forEach(E_CONS action)\n\t{\n\t\tunwrap().forEachRemaining(action);\n\t\trelease();\n\t}\n\n\t@Override\n\tPrimitiveIterator<E, E_CONS> unwrap();\n\n\n\n\t/**\n\t * Specialisation for {@code double} of a FunctionalPrimitiveIterator.\n\t */\n\tinterface OfDouble extends FunctionalPrimitiveIterator<Double, DoubleConsumer>, PrimitiveReducible.OfDouble<Iterator<? extends Double>>, PrimitiveIterator.OfDouble\n\t{\n\t\t@Override\n\t\tdefault PrimitiveIterator.OfDouble unwrap()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault FunctionalIterator<Double> concat(Iterator<? extends Double> iterator)\n\t\t{\n\t\t\tif (iterator instanceof PrimitiveIterator.OfDouble) {\n\t\t\t\treturn concat((PrimitiveIterator.OfDouble) iterator);\n\t\t\t}\n\t\t\treturn FunctionalPrimitiveIterator.super.concat(iterator);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code concat} for {@code double}.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfDouble} to append\n\t\t * @return an {@link Iterator} that iterates over the elements of the receiver and the argument\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfDouble concat(PrimitiveIterator.OfDouble iterator)\n\t\t{\n\t\t\treturn new ChainedIterator.OfDouble(unwrap(), new ArrayIterator.Of<>(iterator));\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfDouble dedupe()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfDouble) PrimitiveReducible.OfDouble.super.dedupe();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfDouble distinct()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfDouble) PrimitiveReducible.OfDouble.super.distinct();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfDouble filter(DoublePredicate predicate)\n\t\t{\n\t\t\treturn new FilteringIterator.OfDouble(unwrap(), predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMap} for {@code double}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMap(java.util.function.Function)\n\t\t */\n\t\tdefault <T> FunctionalIterator<T> flatMap(DoubleFunction<? extends Iterator<? extends T>> function)\n\t\t{\n\t\t\treturn new ChainedIterator.Of<>(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToDouble} for {@code double}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToDouble(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfDouble flatMapToDouble(DoubleFunction<PrimitiveIterator.OfDouble> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfDouble(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToInt} for {@code double}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToInt(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfInt flatMapToInt(DoubleFunction<PrimitiveIterator.OfInt> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfInt(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToLong} for {@code double}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToLong(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfLong flatMapToLong(DoubleFunction<PrimitiveIterator.OfLong> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfLong(map(function));\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> FunctionalIterator<T> map(DoubleFunction<? extends T> function)\n\t\t{\n\t\t\treturn new MappingIterator.DoubleToObj<>(unwrap(), function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfDouble mapToDouble(DoubleUnaryOperator function)\n\t\t{\n\t\t\treturn new MappingIterator.DoubleToDouble(unwrap(), function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfInt mapToInt(DoubleToIntFunction function)\n\t\t{\n\t\t\treturn new MappingIterator.DoubleToInt(unwrap(), function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfLong mapToLong(DoubleToLongFunction function)\n\t\t{\n\t\t\treturn new MappingIterator.DoubleToLong(unwrap(), function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfDouble nonNull()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfDouble consume()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfDouble) PrimitiveReducible.OfDouble.super.consume();\n\t\t}\n\n\t\t@Override\n\t\tdefault boolean contains(Object obj)\n\t\t{\n\t\t\tboolean found = PrimitiveReducible.OfDouble.super.contains(obj);\n\t\t\trelease();\n\t\t\treturn found;\n\t\t}\n\n\t\t@Override\n\t\tdefault double detect(DoublePredicate predicate)\n\t\t{\n\t\t\treturn filter(predicate).nextDouble();\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalDouble reduce(DoubleBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\tif (! hasNext()) {\n\t\t\t\treturn OptionalDouble.empty();\n\t\t\t}\n\t\t\treturn OptionalDouble.of(reduce(nextDouble(), accumulator));\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> T reduce(T init, ObjDoubleFunction<T, T> accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfDouble local = unwrap();\n\t\t\tT result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.apply(result, local.nextDouble());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault double reduce(double init, DoubleBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfDouble local = unwrap();\n\t\t\tdouble result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsDouble(result, local.nextDouble());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault int reduce(int init, IntDoubleToIntFunction accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfDouble local = unwrap();\n\t\t\tint result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsInt(result, local.nextDouble());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault long reduce(long init, LongDoubleToLongFunction accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfDouble local = unwrap();\n\t\t\tlong result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsLong(result, local.nextDouble());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Specialisation for {@code int} of a FunctionalPrimitiveIterator.\n\t */\n\tinterface OfInt extends FunctionalPrimitiveIterator<Integer, IntConsumer>, PrimitiveReducible.OfInt<Iterator<? extends Integer>>, PrimitiveIterator.OfInt\n\t{\n\t\t@Override\n\t\tdefault PrimitiveIterator.OfInt unwrap()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault FunctionalIterator<Integer> concat(Iterator<? extends Integer> iterator)\n\t\t{\n\t\t\tif (iterator instanceof PrimitiveIterator.OfInt) {\n\t\t\t\treturn concat((PrimitiveIterator.OfInt) iterator);\n\t\t\t}\n\t\t\treturn FunctionalPrimitiveIterator.super.concat(iterator);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code concat} for {@code int}.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfInt} to append\n\t\t * @return an {@link Iterator} that iterates over the elements of the receiver and the argument\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfInt concat(PrimitiveIterator.OfInt iterator)\n\t\t{\n\t\t\treturn new ChainedIterator.OfInt(unwrap(), new ArrayIterator.Of<>(iterator));\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfInt dedupe()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfInt) PrimitiveReducible.OfInt.super.dedupe();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfInt distinct()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfInt) PrimitiveReducible.OfInt.super.distinct();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfInt filter(IntPredicate predicate)\n\t\t{\n\t\t\treturn new FilteringIterator.OfInt(unwrap(), predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMap} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMap(java.util.function.Function)\n\t\t */\n\t\tdefault <T> FunctionalIterator<T> flatMap(IntFunction<? extends Iterator<? extends T>> function)\n\t\t{\n\t\t\treturn new ChainedIterator.Of<>(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToDouble} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToDouble(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfDouble flatMapToDouble(IntFunction<PrimitiveIterator.OfDouble> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfDouble(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToInt} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToInt(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfInt flatMapToInt(IntFunction<PrimitiveIterator.OfInt> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfInt(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToLong} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToLong(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfLong flatMapToLong(IntFunction<PrimitiveIterator.OfLong> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfLong(map(function));\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> FunctionalIterator<T> map(IntFunction<? extends T> function)\n\t\t{\n\t\t\treturn new MappingIterator.IntToObj<>(unwrap(), function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfDouble mapToDouble(IntToDoubleFunction function)\n\t\t{\n\t\t\treturn new MappingIterator.IntToDouble(unwrap(), function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfInt mapToInt(IntUnaryOperator function)\n\t\t{\n\t\t\treturn new MappingIterator.IntToInt(unwrap(), function);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code mapToLong} for {@code int}.\n\t\t *\n\t\t * @see FunctionalIterator#mapToLong(java.util.function.ToLongFunction)\n\t\t */\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfLong mapToLong(IntToLongFunction function)\n\t\t{\n\t\t\treturn new MappingIterator.IntToLong(unwrap(), function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfInt nonNull()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfInt consume()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfInt) PrimitiveReducible.OfInt.super.consume();\n\t\t}\n\n\t\t@Override\n\t\tdefault boolean contains(Object obj)\n\t\t{\n\t\t\tboolean found = PrimitiveReducible.OfInt.super.contains(obj);\n\t\t\trelease();\n\t\t\treturn found;\n\t\t}\n\n\t\t@Override\n\t\tdefault int detect(IntPredicate predicate)\n\t\t{\n\t\t\treturn filter(predicate).nextInt();\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalDouble reduce(DoubleBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\tif (! hasNext()) {\n\t\t\t\treturn OptionalDouble.empty();\n\t\t\t}\n\t\t\treturn OptionalDouble.of(reduce(nextInt(), accumulator));\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalInt reduce(IntBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\tif (! hasNext()) {\n\t\t\t\treturn OptionalInt.empty();\n\t\t\t}\n\t\t\treturn OptionalInt.of(reduce(nextInt(), accumulator));\n\t\t}\n\n\t\t@Override\n\t\tdefault OptionalLong reduce(LongBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\tif (! hasNext()) {\n\t\t\t\treturn OptionalLong.empty();\n\t\t\t}\n\t\t\treturn OptionalLong.of(reduce(nextInt(), accumulator));\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> T reduce(T init, ObjIntFunction<T, T> accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfInt local = unwrap();\n\t\t\tT result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.apply(result, local.nextInt());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault double reduce(double init, DoubleBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfInt local = unwrap();\n\t\t\tdouble result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsDouble(result, local.nextInt());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault int reduce(int init, IntBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfInt local = unwrap();\n\t\t\tint result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsInt(result, local.nextInt());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault long reduce(long init, LongBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfInt local = unwrap();\n\t\t\tlong result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsLong(result, local.nextInt());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Specialisation for {@code long} of a FunctionalPrimitiveIterator.\n\t */\n\tinterface OfLong extends FunctionalPrimitiveIterator<Long, LongConsumer>, PrimitiveReducible.OfLong<Iterator<? extends Long>>, PrimitiveIterator.OfLong\n\t{\n\t\t@Override\n\t\tdefault PrimitiveIterator.OfLong unwrap()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault FunctionalIterator<Long> concat(Iterator<? extends Long> iterator)\n\t\t{\n\t\t\tif (iterator instanceof PrimitiveIterator.OfLong) {\n\t\t\t\treturn concat((PrimitiveIterator.OfLong) iterator);\n\t\t\t}\n\t\t\treturn FunctionalPrimitiveIterator.super.concat(iterator);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code concat} for {@code long}.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfLong} to append\n\t\t * @return an {@link Iterator} that iterates over the elements of the receiver and the argument\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfLong concat(PrimitiveIterator.OfLong iterator)\n\t\t{\n\t\t\treturn new ChainedIterator.OfLong(unwrap(), new ArrayIterator.Of<>(iterator));\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfLong dedupe()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfLong) PrimitiveReducible.OfLong.super.dedupe();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfLong distinct()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfLong) PrimitiveReducible.OfLong.super.distinct();\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfLong filter(LongPredicate predicate)\n\t\t{\n\t\t\treturn new FilteringIterator.OfLong(unwrap(), predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMap} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMap(java.util.function.Function)\n\t\t */\n\t\tdefault <T> FunctionalIterator<T> flatMap(LongFunction<? extends Iterator<? extends T>> function)\n\t\t{\n\t\t\treturn new ChainedIterator.Of<>(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToDouble} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToDouble(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfDouble flatMapToDouble(LongFunction<PrimitiveIterator.OfDouble> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfDouble(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToInt} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToInt(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfInt flatMapToInt(LongFunction<PrimitiveIterator.OfInt> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfInt(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code flatMapToLong} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterator#flatMapToLong(java.util.function.Function)\n\t\t */\n\t\tdefault FunctionalPrimitiveIterator.OfLong flatMapToLong(LongFunction<PrimitiveIterator.OfLong> function)\n\t\t{\n\t\t\treturn new ChainedIterator.OfLong(map(function));\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterator#map(java.util.function.Function)\n\t\t */\n\t\t@Override\n\t\tdefault <T> FunctionalIterator<T> map(LongFunction<? extends T> function)\n\t\t{\n\t\t\treturn new MappingIterator.LongToObj<>(unwrap(), function);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterator#mapToDouble(java.util.function.ToDoubleFunction)\n\t\t */\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfDouble mapToDouble(LongToDoubleFunction function)\n\t\t{\n\t\t\treturn new MappingIterator.LongToDouble(unwrap(), function);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterator#mapToInt(java.util.function.ToIntFunction)\n\t\t */\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfInt mapToInt(LongToIntFunction function)\n\t\t{\n\t\t\treturn new MappingIterator.LongToInt(unwrap(), function);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code long}.\n\t\t *\n\t\t * @see FunctionalIterator#mapToLong(java.util.function.ToLongFunction)\n\t\t */\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfLong mapToLong(LongUnaryOperator function)\n\t\t{\n\t\t\treturn new MappingIterator.LongToLong(unwrap(), function);\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfLong nonNull()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterator.OfLong consume()\n\t\t{\n\t\t\treturn (FunctionalPrimitiveIterator.OfLong) PrimitiveReducible.OfLong.super.consume();\n\t\t}\n\n\t\t@Override\n\t\tdefault boolean contains(Object obj)\n\t\t{\n\t\t\tboolean found = PrimitiveReducible.OfLong.super.contains(obj);\n\t\t\trelease();\n\t\t\treturn found;\n\t\t}\n\n\t\t@Override\n\t\tdefault long detect(LongPredicate predicate)\n\t\t{\n\t\t\treturn filter(predicate).nextLong();\n\t\t}\n\n\t\tdefault OptionalLong reduce(LongBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\tif (! hasNext()) {\n\t\t\t\treturn OptionalLong.empty();\n\t\t\t}\n\t\t\treturn OptionalLong.of(reduce(nextLong(), accumulator));\n\t\t}\n\n\t\t@Override\n\t\tdefault <T> T reduce(T init, ObjLongFunction<T, T> accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfLong local = unwrap();\n\t\t\tT result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.apply(result, local.nextLong());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault double reduce(double init, DoubleLongToDoubleFunction accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfLong local = unwrap();\n\t\t\tdouble result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsDouble(result, local.nextLong());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault int reduce(int init, IntLongToIntFunction accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfLong local = unwrap();\n\t\t\tint result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsInt(result, local.nextLong());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tdefault long reduce(long init, LongBinaryOperator accumulator)\n\t\t{\n\t\t\tObjects.requireNonNull(accumulator);\n\t\t\t// avoid redirection in wrappers\n\t\t\tPrimitiveIterator.OfLong local = unwrap();\n\t\t\tlong result = init;\n\t\t\twhile (local.hasNext()) {\n\t\t\t\tresult = accumulator.applyAsLong(result, local.nextLong());\n\t\t\t}\n\t\t\trelease();\n\t\t\treturn result;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/IterableAdaptor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Objects;\nimport java.util.PrimitiveIterator;\nimport java.util.function.Consumer;\nimport java.util.function.DoubleConsumer;\nimport java.util.function.IntConsumer;\nimport java.util.function.LongConsumer;\n\n/**\n * An adaptor that extends non-functional Iterables with the methods provided by {@link FunctionalIterable}.\n *\n * @param <E> type of the {@link Iterable}'s elements\n * @param <I> type of the Iterable to extend\n */\npublic abstract class IterableAdaptor<E, I extends Iterable<E>> implements FunctionalIterable<E>\n{\n\t/** the Iterable that is extended */\n\tprotected final I iterable;\n\n\t/**\n\t * Generic constructor that wraps an Iterable.\n\t *\n\t * @param iterable the {@link Iterable} to be extended\n\t */\n\tpublic IterableAdaptor(I iterable)\n\t{\n\t\tObjects.requireNonNull(iterable);\n\t\tthis.iterable = iterable;\n\t}\n\n\t@Override\n\tpublic void forEach(Consumer<? super E> action)\n\t{\n\t\titerable.forEach(action);\n\t}\n\n\n\n\tpublic static class Of<E> extends IterableAdaptor<E, Iterable<E>>\n\t{\n\t\t/**\n\t\t * Generic constructor that wraps an Iterable.\n\t\t *\n\t\t * @param iterable the {@link Iterable} to be extended\n\t\t */\n\t\tpublic Of(Iterable<E> iterable)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t}\n\n\t\t@Override\n\t\tpublic IteratorAdaptor.Of <E> iterator()\n\t\t{\n\t\t\treturn new IteratorAdaptor.Of<>(iterable.iterator());\n\t\t}\n\t}\n\n\n\n\tpublic static class OfDouble extends IterableAdaptor<Double, PrimitiveIterable.OfDouble> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/**\n\t\t * Constructor that wraps a PrimitiveIterator.OfDouble.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfDouble} to be extended\n\t\t */\n\t\tpublic OfDouble(PrimitiveIterable.OfDouble iterator)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t}\n\n\t\t@Override\n\t\tpublic IteratorAdaptor.OfDouble iterator()\n\t\t{\n\t\t\treturn new IteratorAdaptor.OfDouble(iterable.iterator());\n\t\t}\n\n\t\t@Override\n\t\tpublic void forEach(DoubleConsumer action)\n\t\t{\n\t\t\titerable.forEach(action);\n\t\t}\n\t}\n\n\n\n\tpublic static class OfInt extends IterableAdaptor<Integer, PrimitiveIterable.OfInt> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/**\n\t\t * Constructor that wraps a PrimitiveIterator.OfInt.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfLong} to be extended\n\t\t */\n\t\tpublic OfInt(PrimitiveIterable.OfInt iterator)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t}\n\n\t\t@Override\n\t\tpublic IteratorAdaptor.OfInt iterator()\n\t\t{\n\t\t\treturn new IteratorAdaptor.OfInt(iterable.iterator());\n\t\t}\n\n\t\t@Override\n\t\tpublic void forEach(IntConsumer action)\n\t\t{\n\t\t\titerable.forEach(action);\n\t\t}\n}\n\n\n\n\tpublic static class OfLong extends IterableAdaptor<Long, PrimitiveIterable.OfLong> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/**\n\t\t * Constructor that wraps a PrimitiveIterator.OfLong.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfLong} to be extended\n\t\t */\n\t\tpublic OfLong(PrimitiveIterable.OfLong iterator)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t}\n\n\t\t@Override\n\t\tpublic IteratorAdaptor.OfLong iterator()\n\t\t{\n\t\t\treturn new IteratorAdaptor.OfLong(iterable.iterator());\n\t\t}\n\n\t\t@Override\n\t\tpublic void forEach(LongConsumer action)\n\t\t{\n\t\t\titerable.forEach(action);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/IterableArray.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Marcus Daum <marcus.daum@ivi.fraunhofer.de> (Frauenhofer Institut)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Objects;\n\n/**\n * Abstract base class of efficient Iterables over array slices.\n *\n * @param <E> type of the array elements\n */\npublic abstract class IterableArray<E> implements FunctionalIterable<E>\n{\n\tprotected final int fromIndex;\n\tprotected final int toIndex;\n\n\t/**\n\t * Iterable slice of array in index interval [fromIndex, toIndex).\n\t *\n\t * @param fromIndex first index, inclusive\n\t * @param toIndex last index, exclusive\n\t * @param length length of the array\n\t */\n\tprotected IterableArray(int fromIndex, int toIndex, int length)\n\t{\n\t\tObjects.checkFromToIndex(fromIndex, toIndex, length);\n\t\tthis.fromIndex = fromIndex;\n\t\tthis.toIndex   = toIndex;\n\t}\n\n\t@Override\n\tpublic long count()\n\t{\n\t\treturn size();\n\t}\n\n\t@Override\n\tpublic abstract ArrayIterator<E> iterator();\n\n\t/**\n\t * Get the number of elements.\n\t */\n\tpublic int size()\n\t{\n\t\treturn Math.max(0, toIndex - fromIndex);\n\t}\n\n\n\n\t/**\n\t * Generic implementation of an Iterable over an array slice.\n\t *\n\t * @param <E> type of the array elements\n\t */\n\tpublic static class Of<E> extends IterableArray<E>\n\t{\n\t\tprotected final E[] elements;\n\n\t\t/**\n\t\t * Iterable slice of array over all elements.\n\t\t */\n\t\t@SafeVarargs\n\t\tpublic Of(E... elements)\n\t\t{\n\t\t\tthis(elements,0, elements.length);\n\t\t}\n\n\t\t/**\n\t\t * Iterable slice of array in index interval [fromIndex, toIndex).\n\t\t *\n\t\t * @param fromIndex first index, inclusive\n\t\t * @param toIndex last index, exclusive\n\t\t */\n\t\tpublic Of(E[] elements, int fromIndex, int toIndex)\n\t\t{\n\t\t\tsuper(fromIndex, toIndex, elements.length);\n\t\t\tthis.elements = elements;\n\t\t}\n\n\t\t@Override\n\t\tpublic ArrayIterator.Of<E> iterator()\n\t\t{\n\t\t\treturn new ArrayIterator.Of<>(elements, fromIndex, toIndex);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of an Iterable over an array slice.\n\t */\n\tpublic static class OfInt extends IterableArray<Integer> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\tprotected final int[] elements;\n\n\t\t/**\n\t\t * Iterable slice of array over all elements.\n\t\t */\n\t\tpublic OfInt(int... elements)\n\t\t{\n\t\t\tthis(elements, 0, elements.length);\n\t\t}\n\n\t\tpublic OfInt(int[] elements, int fromIndex, int toIndex)\n\t\t{\n\t\t\tsuper(fromIndex, toIndex, elements.length);\n\t\t\tthis.elements = elements;\n\t\t}\n\n\t\t@Override\n\t\tpublic ArrayIterator.OfInt iterator()\n\t\t{\n\t\t\treturn new ArrayIterator.OfInt(elements, fromIndex, toIndex);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of an Iterable over an array slice.\n\t */\n\tpublic static class OfDouble extends IterableArray<Double> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\tprotected final double[] elements;\n\n\t\t/**\n\t\t * Iterable slice of array over all elements.\n\t\t */\n\t\tpublic OfDouble(double... elements)\n\t\t{\n\t\t\tthis(elements,0, elements.length);\n\t\t}\n\n\t\t/**\n\t\t * Iterable slice of array in index interval [fromIndex, toIndex).\n\t\t *\n\t\t * @param fromIndex first index, inclusive\n\t\t * @param toIndex last index, exclusive\n\t\t */\n\t\tpublic OfDouble(double[] elements, int fromIndex, int toIndex)\n\t\t{\n\t\t\tsuper(fromIndex, toIndex, elements.length);\n\t\t\tthis.elements = elements;\n\t\t}\n\n\t\t@Override\n\t\tpublic ArrayIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn new ArrayIterator.OfDouble(elements, fromIndex, toIndex);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of an Iterable over an array slice.\n\t */\n\tpublic static class OfLong extends IterableArray<Long> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\tprotected final long[] elements;\n\n\t\t/**\n\t\t * Iterable slice of array over all elements.\n\t\t */\n\t\tpublic OfLong(long... elements)\n\t\t{\n\t\t\tthis(elements,0, elements.length);\n\t\t}\n\n\t\t/**\n\t\t * Iterable slice of array in index interval [fromIndex, toIndex).\n\t\t *\n\t\t * @param fromIndex first index, inclusive\n\t\t * @param toIndex last index, exclusive\n\t\t */\n\t\tpublic OfLong(long[] elements, int fromIndex, int toIndex)\n\t\t{\n\t\t\tsuper(fromIndex, toIndex, elements.length);\n\t\t\tthis.elements = elements;\n\t\t}\n\n\t\t@Override\n\t\tpublic ArrayIterator.OfLong iterator()\n\t\t{\n\t\t\treturn new ArrayIterator.OfLong(elements, fromIndex, toIndex);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/IteratorAdaptor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Iterator;\nimport java.util.Objects;\nimport java.util.PrimitiveIterator;\nimport java.util.function.Consumer;\nimport java.util.function.DoubleConsumer;\nimport java.util.function.IntConsumer;\nimport java.util.function.LongConsumer;\n\n/**\n * Abstract base class of adaptors that extend non-functional Iterators with the methods provided by {@link FunctionalIterator}.\n * Implementations should release the underlying Iterator after iteration.\n *\n * @param <E> type of the {@link Iterator}'s elements\n * @param <I> type of the Iterator to extend\n */\npublic abstract class IteratorAdaptor<E, I extends Iterator<E>> implements FunctionalIterator<E>\n{\n\t/** the Iterator that is extended */\n\tprotected I iterator;\n\n\t/**\n\t * Generic constructor that wraps an Iterator.\n\t *\n\t * @param iterator the {@link Iterator} to be extended\n\t */\n\tpublic IteratorAdaptor(I iterator)\n\t{\n\t\tObjects.requireNonNull(iterator);\n\t\tthis.iterator = iterator;\n\t}\n\n\t@Override\n\tpublic boolean hasNext()\n\t{\n\t\tif (iterator.hasNext()) {\n\t\t\treturn true;\n\t\t}\n\t\trelease();\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic E next()\n\t{\n\t\treturn iterator.next();\n\t}\n\n\t@Override\n\tpublic void forEachRemaining(Consumer<? super E> action)\n\t{\n\t\titerator.forEachRemaining(action);\n\t\trelease();\n\t}\n\n\t/**\n\t * Unwrap a nested iterator if this instance is an adaptor wrapping an Iterator.\n\t * Use to avoid repeated indirections, especially in loops.\n\t *\n\t * @return the wrapped iterator.\n\t */\n\t@Override\n\tpublic I unwrap()\n\t{\n\t\treturn iterator;\n\t}\n\n\n\n\t/**\n\t * Generic implementation of an {@link IteratorAdaptor}.\n\t *\n\t * @param <E> type of the Iterator's elements\n\t */\n\tpublic static class Of<E> extends IteratorAdaptor<E, Iterator<E>>\n\t{\n\t\tpublic Of(Iterator<E> iterator)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.of();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of an {@link IteratorAdaptor}.\n\t */\n\tpublic static class OfDouble extends IteratorAdaptor<Double, PrimitiveIterator.OfDouble> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/**\n\t\t * Constructor that wraps a PrimitiveIterator.OfDouble.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfDouble} to be extended\n\t\t */\n\t\tpublic OfDouble(PrimitiveIterator.OfDouble iterator)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\treturn iterator.nextDouble();\n\t\t}\n\n\t\t@Override\n\t\tpublic void forEachRemaining(DoubleConsumer action)\n\t\t{\n\t\t\titerator.forEachRemaining(action);\n\t\t\trelease();\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofDouble();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of an {@link IteratorAdaptor}.\n\t */\n\tpublic static class OfInt extends IteratorAdaptor<Integer, PrimitiveIterator.OfInt> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/**\n\t\t * Constructor that wraps a PrimitiveIterator.OfInt.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfInt} to be extended\n\t\t */\n\t\tpublic OfInt(PrimitiveIterator.OfInt iterator)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\treturn iterator.nextInt();\n\t\t}\n\n\t\t@Override\n\t\tpublic void forEachRemaining(IntConsumer action)\n\t\t{\n\t\t\titerator.forEachRemaining(action);\n\t\t\trelease();\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofInt();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of an {@link IteratorAdaptor}.\n\t */\n\tpublic static class OfLong extends IteratorAdaptor<Long, PrimitiveIterator.OfLong> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/**\n\t\t * Constructor that wraps a PrimitiveIterator.OfLong.\n\t\t *\n\t\t * @param iterator the {@link PrimitiveIterator.OfLong} to be extended\n\t\t */\n\t\tpublic OfLong(PrimitiveIterator.OfLong iterator)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\treturn iterator.nextLong();\n\t\t}\n\n\t\t@Override\n\t\tpublic void forEachRemaining(LongConsumer action)\n\t\t{\n\t\t\titerator.forEachRemaining(action);\n\t\t\trelease();\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofLong();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/MappingIterable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Objects;\nimport java.util.function.DoubleFunction;\nimport java.util.function.DoubleToIntFunction;\nimport java.util.function.DoubleToLongFunction;\nimport java.util.function.DoubleUnaryOperator;\nimport java.util.function.Function;\nimport java.util.function.IntFunction;\nimport java.util.function.IntToDoubleFunction;\nimport java.util.function.IntToLongFunction;\nimport java.util.function.IntUnaryOperator;\nimport java.util.function.LongFunction;\nimport java.util.function.LongToDoubleFunction;\nimport java.util.function.LongToIntFunction;\nimport java.util.function.LongUnaryOperator;\nimport java.util.function.ToDoubleFunction;\nimport java.util.function.ToIntFunction;\nimport java.util.function.ToLongFunction;\n\n/**\n * Abstract base class for Iterables that map elements using a function {@code f: S -> E}.\n * Yields the result of applying {@code f} to each each element of the underlying Iterable:\n * Iterable(S) -{@code f}-> Iterable(E)\n *\n * @param <S> type of the underlying Iterable's elements\n * @param <E> type of the Iterable's elements after mapping\n * @param <I> type of the underlying Iterable\n */\npublic abstract class MappingIterable<S, E, I extends Iterable<S>> implements FunctionalIterable<E>\n{\n\t/** The Iterable which elements are mapped */\n\tprotected final I iterable;\n\n\t/**\n\t * Constructor for a mapping Iterable without a mapping function.\n\t *\n\t * @param iterable an Iterable to be mapped\n\t */\n\tpublic MappingIterable(I iterable)\n\t{\n\t\tObjects.requireNonNull(iterable);\n\t\tthis.iterable = iterable;\n\t}\n\n\n\n\t/**\n\t * Generic implementation  using a function {@code f: S -> E}.\n\t *\n\t * @param <S> type of the underlying Iterable's elements\n\t * @param <E> type of the Iterable's elements after mapping\n\t */\n\tpublic static class ObjToObj<S, E> extends MappingIterable<S, E, Iterable<S>>\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final Function<? super S, ? extends E> function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic ObjToObj(Iterable<S> iterable, Function<? super S, ? extends E> function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalIterator<E> iterator()\n\t\t{\n\t\t\treturn new MappingIterator.ObjToObj<>(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: S -> double}.\n\t *\n\t * @param <S> type of the underlying Iterable's elements\n\t */\n\tpublic static class ObjToDouble<S> extends MappingIterable<S, Double, Iterable<S>> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final ToDoubleFunction<? super S> function;\n\t\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic ObjToDouble(Iterable<S> iterable, ToDoubleFunction<? super S> function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\t\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn new MappingIterator.ObjToDouble<>(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: S -> int}.\n\t *\n\t * @param <S> type of the underlying Iterable's elements\n\t */\n\tpublic static class ObjToInt<S> extends MappingIterable<S, Integer, Iterable<S>> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final ToIntFunction<? super S> function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic ObjToInt(Iterable<S> iterable, ToIntFunction<? super S> function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t\t{\n\t\t\treturn new MappingIterator.ObjToInt<>(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: S -> long}.\n\t *\n\t * @param <S> type of the underlying Iterable's elements\n\t */\n\tpublic static class ObjToLong<S> extends MappingIterable<S, Long, Iterable<S>> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final ToLongFunction<? super S> function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic ObjToLong(Iterable<S> iterable, ToLongFunction<? super S> function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfLong iterator()\n\t\t{\n\t\t\treturn new MappingIterator.ObjToLong<>(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: double -> E}.\n\t *\n\t * @param <E> type of the Iterable's elements after mapping\n\t */\n\tpublic static class DoubleToObj<E> extends MappingIterable<Double, E, PrimitiveIterable.OfDouble>\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final DoubleFunction<? extends E> function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic DoubleToObj(PrimitiveIterable.OfDouble iterable, DoubleFunction<? extends E> function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalIterator<E> iterator()\n\t\t{\n\t\t\treturn new MappingIterator.DoubleToObj<>(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: double -> double}.\n\t */\n\tpublic static class DoubleToDouble extends MappingIterable<Double, Double, PrimitiveIterable.OfDouble> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final DoubleUnaryOperator function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic DoubleToDouble(PrimitiveIterable.OfDouble iterable, DoubleUnaryOperator function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn new MappingIterator.DoubleToDouble(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: double -> int}.\n\t */\n\tpublic static class DoubleToInt extends MappingIterable<Double, Integer, PrimitiveIterable.OfDouble> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final DoubleToIntFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic DoubleToInt(PrimitiveIterable.OfDouble iterable, DoubleToIntFunction function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t\t{\n\t\t\treturn new MappingIterator.DoubleToInt(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: double -> long}.\n\t */\n\tpublic static class DoubleToLong extends MappingIterable<Double, Long, PrimitiveIterable.OfDouble> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final DoubleToLongFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic DoubleToLong(PrimitiveIterable.OfDouble iterable, DoubleToLongFunction function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfLong iterator()\n\t\t{\n\t\t\treturn new MappingIterator.DoubleToLong(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: int -> E}.\n\t *\n\t * @param <E> type of the Iterable's elements after mapping\n\t */\n\tpublic static class IntToObj<E> extends MappingIterable<Integer, E, PrimitiveIterable.OfInt>\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final IntFunction<? extends E> function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic IntToObj(PrimitiveIterable.OfInt iterable, IntFunction<? extends E> function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalIterator<E> iterator()\n\t\t{\n\t\t\treturn new MappingIterator.IntToObj<>(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: int -> double}.\n\t */\n\tpublic static class IntToDouble extends MappingIterable<Integer, Double, PrimitiveIterable.OfInt> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final IntToDoubleFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic IntToDouble(PrimitiveIterable.OfInt iterable, IntToDoubleFunction function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn new MappingIterator.IntToDouble(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: int -> int}.\n\t */\n\tpublic static class IntToInt extends MappingIterable<Integer, Integer, PrimitiveIterable.OfInt> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final IntUnaryOperator function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic IntToInt(PrimitiveIterable.OfInt iterable, IntUnaryOperator function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t\t{\n\t\t\treturn new MappingIterator.IntToInt(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: int -> long}.\n\t */\n\tpublic static class IntToLong extends MappingIterable<Integer, Long, PrimitiveIterable.OfInt> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final IntToLongFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic IntToLong(PrimitiveIterable.OfInt iterable, IntToLongFunction function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfLong iterator()\n\t\t{\n\t\t\treturn new MappingIterator.IntToLong(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: long -> E}.\n\t *\n\t * @param <E> type of the Iterable's elements after mapping\n\t */\n\tpublic static class LongToObj<E> extends MappingIterable<Long, E, PrimitiveIterable.OfLong>\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final LongFunction<? extends E> function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic LongToObj(PrimitiveIterable.OfLong iterable, LongFunction<? extends E> function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalIterator<E> iterator()\n\t\t{\n\t\t\treturn new MappingIterator.LongToObj<>(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: long -> double}.\n\t */\n\tpublic static class LongToDouble extends MappingIterable<Long, Double, PrimitiveIterable.OfLong> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final LongToDoubleFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic LongToDouble(PrimitiveIterable.OfLong iterable, LongToDoubleFunction function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn new MappingIterator.LongToDouble(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: long -> int}.\n\t */\n\tpublic static class LongToInt extends MappingIterable<Long, Integer, PrimitiveIterable.OfLong> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final LongToIntFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic LongToInt(PrimitiveIterable.OfLong iterable, LongToIntFunction function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t\t{\n\t\t\treturn new MappingIterator.LongToInt(iterable.iterator(), function);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a mapping Iterable using a function {@code f: long -> long}.\n\t */\n\tpublic static class LongToLong extends MappingIterable<Long, Long, PrimitiveIterable.OfLong> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/** The function the Iterable uses to map the elements */\n\t\tprotected final LongUnaryOperator function;\n\n\t\t/**\n\t\t * Constructor for an Iterable that maps elements using a function.\n\t\t *\n\t\t * @param iterable an Iterable to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic LongToLong(PrimitiveIterable.OfLong iterable, LongUnaryOperator function)\n\t\t{\n\t\t\tsuper(iterable);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalPrimitiveIterator.OfLong iterator()\n\t\t{\n\t\t\treturn new MappingIterator.LongToLong(iterable.iterator(), function);\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/common/iterable/MappingIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Iterator;\nimport java.util.Objects;\nimport java.util.PrimitiveIterator;\nimport java.util.PrimitiveIterator.OfDouble;\nimport java.util.PrimitiveIterator.OfInt;\nimport java.util.PrimitiveIterator.OfLong;\nimport java.util.function.DoubleFunction;\nimport java.util.function.DoubleToIntFunction;\nimport java.util.function.DoubleToLongFunction;\nimport java.util.function.DoubleUnaryOperator;\nimport java.util.function.Function;\nimport java.util.function.IntFunction;\nimport java.util.function.IntToDoubleFunction;\nimport java.util.function.IntToLongFunction;\nimport java.util.function.IntUnaryOperator;\nimport java.util.function.LongFunction;\nimport java.util.function.LongToDoubleFunction;\nimport java.util.function.LongToIntFunction;\nimport java.util.function.LongUnaryOperator;\nimport java.util.function.ToDoubleFunction;\nimport java.util.function.ToIntFunction;\nimport java.util.function.ToLongFunction;\n\n/**\n * Abstract base class for Iterators that map elements using a function {@code f: S -> E}.\n * Yields the result of applying {@code f} to each each element of the underlying Iterator:\n * Iterator(S) -{@code f}-> Iterator(E)\n * <p>\n * The calls to {@code next()} of the underlying Iterator happen on-the-fly,\n * i.e., only when {@code next()} is called for this Iterator.\n * <p>\n * Implementations should release the underlying Iterator after iteration.\n *\n * @param <S> type of the underlying Iterator's elements\n * @param <E> type of the Iterator's elements after mapping\n * @param <I> type of the underlying Iterator\n */\npublic abstract class MappingIterator<S, E, I extends Iterator<S>> implements FunctionalIterator<E>\n{\n\t/** The Iterator which elements are mapped */\n\tprotected I iterator;\n\n\t/**\n\t * Constructor for a MappingIterator without a mapping function.\n\t *\n\t * @param iterator an Iterator to be mapped\n\t */\n\tpublic MappingIterator(I iterator)\n\t{\n\t\tObjects.requireNonNull(iterator);\n\t\tthis.iterator = iterator;\n\t}\n\n\t@Override\n\tpublic boolean hasNext()\n\t{\n\t\tif (iterator.hasNext()) {\n\t\t\treturn true;\n\t\t}\n\t\trelease();\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic long count()\n\t{\n\t\t// do not apply mapping, just count elements of underlying iterator\n\t\treturn Reducible.extend(iterator).count();\n\t}\n\n\n\n\t/**\n\t * Generic implementation of a MappingIterator using a function {@code f: S -> E}.\n\t *\n\t * @param <S> type of the underlying Iterator's elements\n\t * @param <E> type of the Iterator's elements after mapping\n\t */\n\tpublic static class ObjToObj<S, E> extends MappingIterator<S, E, Iterator<S>>\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final Function<? super S, ? extends E> function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic ObjToObj(Iterator<S> iterator, Function<? super S, ? extends E> function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.apply(iterator.next());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.of();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: S -> double}.\n\t *\n\t * @param <S> type of the underlying Iterator's elements\n\t */\n\tpublic static class ObjToDouble<S> extends MappingIterator<S, Double, Iterator<S>> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final ToDoubleFunction<? super S> function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic ObjToDouble(Iterator<S> iterator, ToDoubleFunction<? super S> function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsDouble(iterator.next());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.of();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: S -> int}.\n\t *\n\t * @param <S> type of the underlying Iterator's elements\n\t */\n\tpublic static class ObjToInt<S> extends MappingIterator<S, Integer, Iterator<S>> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final ToIntFunction<? super S> function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic ObjToInt(Iterator<S> iterator, ToIntFunction<? super S> function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsInt(iterator.next());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.of();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: S -> long}.\n\t *\n\t * @param <S> type of the underlying Iterator's elements\n\t */\n\tpublic static class ObjToLong<S> extends MappingIterator<S, Long, Iterator<S>> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final ToLongFunction<? super S> function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic ObjToLong(Iterator<S> iterator, ToLongFunction<? super S> function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsLong(iterator.next());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.of();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: double -> E}.\n\t *\n\t * @param <E> type of the Iterator's elements after mapping\n\t */\n\tpublic static class DoubleToObj<E> extends MappingIterator<Double, E, PrimitiveIterator.OfDouble>\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final DoubleFunction<? extends E> function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic DoubleToObj(OfDouble iterator, DoubleFunction<? extends E> function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.apply(iterator.nextDouble());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofDouble();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: double -> double}.\n\t */\n\tpublic static class DoubleToDouble extends MappingIterator<Double, Double, PrimitiveIterator.OfDouble> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final DoubleUnaryOperator function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic DoubleToDouble(PrimitiveIterator.OfDouble iterator, DoubleUnaryOperator function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsDouble(iterator.nextDouble());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofDouble();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: double -> int}.\n\t */\n\tpublic static class DoubleToInt extends MappingIterator<Double, Integer, PrimitiveIterator.OfDouble> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final DoubleToIntFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic DoubleToInt(PrimitiveIterator.OfDouble iterator, DoubleToIntFunction function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsInt(iterator.nextDouble());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofDouble();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: double -> long}.\n\t */\n\tpublic static class DoubleToLong extends MappingIterator<Double, Long, PrimitiveIterator.OfDouble> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final DoubleToLongFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic DoubleToLong(PrimitiveIterator.OfDouble iterator, DoubleToLongFunction function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsLong(iterator.nextDouble());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofDouble();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: int -> E}.\n\t *\n\t * @param <E> type of the Iterator's elements after mapping\n\t */\n\tpublic static class IntToObj<E> extends MappingIterator<Integer, E, PrimitiveIterator.OfInt>\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final IntFunction<? extends E> function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic IntToObj(OfInt iterator, IntFunction<? extends E> function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.apply(iterator.nextInt());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofInt();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: int -> double}.\n\t */\n\tpublic static class IntToDouble extends MappingIterator<Integer, Double, PrimitiveIterator.OfInt> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final IntToDoubleFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic IntToDouble(PrimitiveIterator.OfInt iterator, IntToDoubleFunction function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsDouble(iterator.nextInt());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofInt();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: int -> int}.\n\t */\n\tpublic static class IntToInt extends MappingIterator<Integer, Integer, PrimitiveIterator.OfInt> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final IntUnaryOperator function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic IntToInt(PrimitiveIterator.OfInt iterator, IntUnaryOperator function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsInt(iterator.nextInt());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofInt();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: int -> long}.\n\t */\n\tpublic static class IntToLong extends MappingIterator<Integer, Long, PrimitiveIterator.OfInt> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final IntToLongFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic IntToLong(PrimitiveIterator.OfInt iterator, IntToLongFunction function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsLong(iterator.nextInt());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofInt();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: long -> E}.\n\t *\n\t * @param <E> type of the Iterator's elements after mapping\n\t */\n\tpublic static class LongToObj<E> extends MappingIterator<Long, E, PrimitiveIterator.OfLong>\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final LongFunction<? extends E> function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic LongToObj(OfLong iterator, LongFunction<? extends E> function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.apply(iterator.nextLong());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofLong();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: long -> double}.\n\t */\n\tpublic static class LongToDouble extends MappingIterator<Long, Double, PrimitiveIterator.OfLong> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final LongToDoubleFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic LongToDouble(PrimitiveIterator.OfLong iterator, LongToDoubleFunction function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsDouble(iterator.nextLong());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofLong();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: long -> int}.\n\t */\n\tpublic static class LongToInt extends MappingIterator<Long, Integer, PrimitiveIterator.OfLong> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final LongToIntFunction function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic LongToInt(PrimitiveIterator.OfLong iterator, LongToIntFunction function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsInt(iterator.nextLong());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofLong();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation of a MappingIterator using a function {@code f: long -> long}.\n\t */\n\tpublic static class LongToLong extends MappingIterator<Long, Long, PrimitiveIterator.OfLong> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/** The function the Iterator uses to map the elements */\n\t\tprotected final LongUnaryOperator function;\n\n\t\t/**\n\t\t * Constructor for an Iterator that maps elements using a function.\n\t\t *\n\t\t * @param iterator an Iterator to be mapped\n\t\t * @param function a function used to map the elements\n\t\t */\n\t\tpublic LongToLong(PrimitiveIterator.OfLong iterator, LongUnaryOperator function)\n\t\t{\n\t\t\tsuper(iterator);\n\t\t\tObjects.requireNonNull(function);\n\t\t\tthis.function = function;\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\trequireNext();\n\t\t\treturn function.applyAsLong(iterator.nextLong());\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\titerator = EmptyIterator.ofLong();\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/common/iterable/PrimitiveIterable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.Iterator;\nimport java.util.Objects;\nimport java.util.PrimitiveIterator;\nimport java.util.function.DoubleConsumer;\nimport java.util.function.IntConsumer;\nimport java.util.function.LongConsumer;\n\n/**\n * A base interface for primitive specializations of {@code Iterable}.\n * Specialized sub interfaces are provided for the types {@link OfInt int}, {@link OfLong long} and {@link OfDouble double}.\n *\n * @param <E> the type of elements hold by this PrimitiveIterable\n * @param <E_CONS> the type of primitive consumer\n *\n * @see Iterable\n * @see PrimitiveIterator\n */\npublic interface PrimitiveIterable<E, E_CONS> extends Iterable<E>\n{\n\t/**\n\t * Convert an Iterable&lt;Double&gt; to a PrimitiveIterable.OfDouble by unboxing each element.\n\t * If the argument's Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterable if it already implements of PrimitiveIterable.OfDouble.\n\t *\n\t * @param iterable the {@link Iterable}&lt;Double&gt; to extend\n\t * @return a {@link PrimitiveIterable.OfDouble} that is either the argument or an adaptor on the argument\n\t */\n\tstatic PrimitiveIterable.OfDouble unboxDouble(Iterable<Double> iterable)\n\t{\n\t\tObjects.requireNonNull(iterable);\n\n\t\treturn () -> unboxDouble(iterable.iterator());\n\t}\n\n\t/**\n\t * Convert an Iterator&lt;Double&gt; to a PrimitiveIterator.OfDouble by unboxing each element.\n\t * If the Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterator if it already implements of PrimitiveIterator.OfDouble.\n\t *\n\t * @param iterator the {@link Iterator}&lt;Double&gt; to extend\n\t * @return a {@link PrimitiveIterator.OfDouble} that is either the argument or an adaptor on the argument\n\t */\n\tstatic PrimitiveIterator.OfDouble unboxDouble(Iterator<Double> iterator)\n\t{\n\t\tObjects.requireNonNull(iterator);\n\n\t\tif (iterator instanceof PrimitiveIterator.OfDouble) {\n\t\t\treturn (PrimitiveIterator.OfDouble) iterator;\n\t\t}\n\n\t\treturn new PrimitiveIterator.OfDouble()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn iterator.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic double nextDouble()\n\t\t\t{\n\t\t\t\treturn iterator.next();\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Convert an Iterable&lt;Integer&gt; to a PrimitiveIterable.OfInt by unboxing each element.\n\t * If the argument's Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterable if it already implements of PrimitiveIterable.OfInt.\n\t *\n\t * @param iterable the {@link Iterable}&lt;Integer&gt; to extend\n\t * @return a {@link PrimitiveIterable.OfInt} that is either the argument or an adaptor on the argument\n\t */\n\tstatic PrimitiveIterable.OfInt unboxInt(Iterable<Integer> iterable)\n\t{\n\t\tObjects.requireNonNull(iterable);\n\n\t\treturn () -> unboxInt(iterable.iterator());\n\t}\n\n\t/**\n\t * Convert an Iterator&lt;Integer&gt; to a PrimitiveIterator.OfInt by unboxing each element.\n\t * If the Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterator if it already implements of PrimitiveIterator.OfInt.\n\t *\n\t * @param iterator the {@link Iterator}&lt;Integer&gt; to extend\n\t * @return a {@link PrimitiveIterator.OfInt} that is either the argument or an adaptor on the argument\n\t */\n\tstatic PrimitiveIterator.OfInt unboxInt(Iterator<Integer> iterator)\n\t{\n\t\tObjects.requireNonNull(iterator);\n\n\t\tif (iterator instanceof PrimitiveIterator.OfInt) {\n\t\t\treturn (PrimitiveIterator.OfInt) iterator;\n\t\t}\n\n\t\treturn new PrimitiveIterator.OfInt()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn iterator.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\treturn iterator.next();\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Convert an Iterable&lt;Long&gt; to a PrimitiveIterable.OfLong by unboxing each element.\n\t * If the argument's Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterable if it already implements of PrimitiveIterable.OfLong.\n\t *\n\t * @param iterable the {@link Iterable}&lt;Long&gt; to extend\n\t * @return a {@link PrimitiveIterable.OfLong} that is either the argument or an adaptor on the argument\n\t */\n\tstatic PrimitiveIterable.OfLong unboxLong(Iterable<Long> iterable)\n\t{\n\t\tObjects.requireNonNull(iterable);\n\n\t\treturn () -> unboxLong(iterable.iterator());\n\t}\n\n\t/**\n\t * Convert an Iterator&lt;Long&gt; to a PrimitiveIterator.OfLong by unboxing each element.\n\t * If the Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterator if it already implements of PrimitiveIterator.OfLong.\n\t *\n\t * @param iterator the {@link Iterator}&lt;Long&gt; to extend\n\t * @return a {@link PrimitiveIterator.OfLong} that is either the argument or an adaptor on the argument\n\t */\n\tstatic PrimitiveIterator.OfLong unboxLong(Iterator<Long> iterator)\n\t{\n\t\tObjects.requireNonNull(iterator);\n\n\t\tif (iterator instanceof PrimitiveIterator.OfLong) {\n\t\t\treturn (PrimitiveIterator.OfLong) iterator;\n\t\t}\n\n\t\treturn new PrimitiveIterator.OfLong()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn iterator.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic long nextLong()\n\t\t\t{\n\t\t\t\treturn iterator.next();\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tPrimitiveIterator<E, E_CONS> iterator();\n\n\t/**\n\t * Perform the given action for each element of the receiver.\n\t *\n\t * @see Iterable#forEach(java.util.function.Consumer)\n\t */\n\tdefault void forEach(E_CONS action)\n\t{\n\t\titerator().forEachRemaining(action);\n\t}\n\n\n\n\t/**\n\t * Specialisation for {@code double} of a PrimitiveIterable.\n\t */\n\tinterface OfDouble extends PrimitiveIterable<Double, DoubleConsumer>\n\t{\n\t\t@Override\n\t\tPrimitiveIterator.OfDouble iterator();\n\t}\n\n\n\n\t/**\n\t * Specialisation for {@code int} of a PrimitiveIterable.\n\t */\n\tinterface OfInt extends PrimitiveIterable<Integer, IntConsumer>\n\t{\n\t\t@Override\n\t\tPrimitiveIterator.OfInt iterator();\n\t}\n\n\n\n\t/**\n\t * Specialisation for {@code long} of a PrimitiveIterable.\n\t */\n\tinterface OfLong extends PrimitiveIterable<Long, LongConsumer>\n\t{\n\t\t@Override\n\t\tPrimitiveIterator.OfLong iterator();\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/PrimitiveReducible.java",
    "content": "package common.iterable;\n\nimport common.functions.*;\n\nimport java.util.*;\nimport java.util.function.*;\n\n/**\n * A base type for primitive specializations of the methods provided by {@link Reducible}.\n * Specialized sub interfaces are provided for {@code double}, {@code int} and {@code long}:\n * <ul>\n *     <li>{@link PrimitiveReducible.OfDouble}</li>\n *     <li>{@link PrimitiveReducible.OfInt}</li>\n *     <li>{@link PrimitiveReducible.OfLong}</li>\n * </ul>\n *\n * @param <E> the type of elements returned by this Reducible\n * @param <E_CONS> the type of primitive consumers for the elements\n *\n * @see java.util.stream.DoubleStream DoubleStream\n * @see java.util.stream.IntStream IntStream\n * @see java.util.stream.LongStream LongStream\n */\npublic interface PrimitiveReducible<E, E_CAT, E_CONS> extends Reducible<E, E_CAT>\n{\n\t/**\n\t * Primitive specialisation of {@link Reducible#forEach}.\n\t *\n\t * @param action the action to be performed with each element\n\t * @see PrimitiveIterator#forEachRemaining(Object);\n\t */\n\tvoid forEach(E_CONS action);\n\n\n\n\t/**\n\t * Specialisation for {@code double} of a {@link PrimitiveReducible}.\n\t */\n\tinterface OfDouble<E_CAT> extends PrimitiveReducible<Double, E_CAT, DoubleConsumer>\n\t{\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault OfDouble<E_CAT> dedupe()\n\t\t{\n\t\t\tDoublePredicate isFirst = new DoublePredicate()\n\t\t\t{\n\t\t\t\tboolean start = true;\n\t\t\t\tdouble previous = 0.0;\n\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(double d)\n\t\t\t\t{\n\t\t\t\t\tif (start) {\n\t\t\t\t\t\tstart = false;\n\t\t\t\t\t} else if (previous == d) {\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t} else if (Double.isNaN(previous) && Double.isNaN(d)) {\n\t\t\t\t\t\t// Circumvent Double.NaN != Double.NaN\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t\tprevious = d;\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t};\n\t\t\treturn filter(isFirst);\n\t\t}\n\n\t\t@Override\n\t\tdefault OfDouble<E_CAT> distinct()\n\t\t{\n\t\t\treturn filter(new Distinct.OfDouble());\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code filter} for {@code double}.\n\t\t *\n\t\t * @see Reducible#filter(java.util.function.Predicate)\n\t\t */\n\t\tOfDouble<E_CAT> filter(DoublePredicate predicate);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code double}.\n\t\t *\n\t\t * @see Reducible#map(java.util.function.Function)\n\t\t */\n\t\t<T> Reducible<T, ?> map(DoubleFunction<? extends T> function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code mapToDouble} for {@code double}.\n\t\t *\n\t\t * @see Reducible#mapToDouble(java.util.function.ToDoubleFunction)\n\t\t */\n\t\tOfDouble<?> mapToDouble(DoubleUnaryOperator function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code mapToInt} for {@code double}.\n\t\t *\n\t\t * @see Reducible#mapToInt(java.util.function.ToIntFunction)\n\t\t */\n\t\tOfInt<?> mapToInt(DoubleToIntFunction function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code mapToLong} for {@code double}.\n\t\t *\n\t\t * @see Reducible#mapToLong(java.util.function.ToLongFunction)\n\t\t */\n\t\tOfLong<?> mapToLong(DoubleToLongFunction function);\n\n\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault OfDouble<E_CAT> consume()\n\t\t{\n\t\t\tforEach((double each) -> {});\n\t\t\treturn this;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code allMatch} for {@code double}.\n\t\t *\n\t\t * @see Reducible#allMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean allMatch(DoublePredicate predicate)\n\t\t{\n\t\t\treturn ! anyMatch(predicate.negate());\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code anyMatch} for {@code double}.\n\t\t *\n\t\t * @see Reducible#anyMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean anyMatch(DoublePredicate predicate)\n\t\t{\n\t\t\treturn ! filter(predicate).isEmpty();\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code noneMatch} for {@code double}.\n\t\t *\n\t\t * @see Reducible#noneMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean noneMatch(DoublePredicate predicate)\n\t\t{\n\t\t\treturn ! anyMatch(predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collect} for {@code double}.\n\t\t *\n\t\t * @see Reducible#collect(Object[])\n\t\t */\n\t\tdefault double[] collect(double[] array)\n\t\t{\n\t\t\treturn collect(array, 0);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collect} for {@code double}.\n\t\t *\n\t\t * @see Reducible#collect(Object[], int)\n\t\t */\n\t\tdefault double[] collect(double[] array, int offset)\n\t\t{\n\t\t\tcollectAndCount(array, offset);\n\t\t\treturn array;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collectAndCount} for {@code double}.\n\t\t *\n\t\t * @see Reducible#collectAndCount(Object[])\n\t\t */\n\t\tdefault int collectAndCount(double[] array)\n\t\t{\n\t\t\treturn collectAndCount(array, 0);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collectAndCount} for {@code double}.\n\t\t *\n\t\t * @see Reducible#collectAndCount(Object[], int)\n\t\t */\n\t\tdefault int collectAndCount(double[] array, int offset)\n\t\t{\n\t\t\tObjects.requireNonNull(array);\n\t\t\tint index = reduce(offset, (int i, double e) -> {\n\t\t\t\tarray[i] = e;\n\t\t\t\treturn i + 1;\n\t\t\t});\n\t\t\treturn index - offset;\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfDouble collectDistinct()\n\t\t{\n\t\t\tDistinct.OfDouble unseen = new Distinct.OfDouble();\n\t\t\tfilter(unseen).consume();\n\t\t\treturn unseen.getSeen();\n\t\t}\n\n\t\t@Override\n\t\tdefault boolean contains(Object obj)\n\t\t{\n\t\t\tif (obj instanceof Double) {\n\t\t\t\treturn contains(((Double) obj).doubleValue());\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code contains} for {@code double}.\n\t\t * Inclusion is defined in terms of {@link ==} except for {@code NaN} for which all instances are consider equal, although {@code Double.NaN != Double.NaN}.\n\t\t *\n\t\t * @see Reducible#contains(Object)\n\t\t */\n\t\tdefault boolean contains(double d)\n\t\t{\n\t\t\treturn anyMatch(Double.isNaN(d) ? (double e) -> Double.isNaN(e) : (double e) -> e == d);\n\t\t}\n\n\t\t@Override\n\t\tdefault long count()\n\t\t{\n\t\t\t// avoid auto-boxing\n\t\t\treturn reduce(0L, (long c, double d) -> c + 1);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code count} for {@code double}.\n\t\t *\n\t\t * @see Reducible#count(java.util.function.Predicate)\n\t\t */\n\t\tdefault long count(DoublePredicate predicate)\n\t\t{\n\t\t\treturn filter(predicate).count();\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code detect} for {@code double}.\n\t\t *\n\t\t * @see Reducible#detect(java.util.function.Predicate)\n\t\t */\n\t\tdouble detect(DoublePredicate predicate);\n\n\t\t/**\n\t\t * Find the maximum.\n\t\t *\n\t\t * @return an {@link OptionalDouble} either containing the maximum or being empty if the receiver is empty\n\t\t * @see Math#max(double, double).\n\t\t */\n\t\tdefault OptionalDouble max()\n\t\t{\n\t\t\treturn reduce((DoubleBinaryOperator) Math::max);\n\t\t}\n\n\t\t/**\n\t\t * Find the minimum.\n\t\t *\n\t\t * @return an {@link OptionalDouble} either containing the minimum or being empty if the receiver is empty\n\t\t * @see Math#min(double, double).\n\t\t */\n\t\tdefault OptionalDouble min()\n\t\t{\n\t\t\treturn reduce((DoubleBinaryOperator) Math::min);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code double}.\n\t\t *\n\t\t * @see Reducible#reduce(java.util.function.BinaryOperator)\n\t\t */\n\t\tOptionalDouble reduce(DoubleBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code double}.\n\t\t *\n\t\t * @see Reducible#reduce(Object, java.util.function.BiFunction)\n\t\t */\n\t\t<T> T reduce(T init, ObjDoubleFunction<T, T> accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code double}.\n\t\t *\n\t\t * @see Reducible#reduce(double, common.functions.DoubleObjToDoubleFunction)\n\t\t */\n\t\tdouble reduce(double init, DoubleBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code double}.\n\t\t *\n\t\t * @see Reducible#reduce(int, common.functions.IntObjToIntFunction)\n\t\t */\n\t\tint reduce(int init, IntDoubleToIntFunction accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code double}.\n\t\t *\n\t\t * @see Reducible#reduce(long, common.functions.LongObjToLongFunction)\n\t\t */\n\t\tlong reduce(long init, LongDoubleToLongFunction accumulator);\n\n\t\t/**\n\t\t * Compute the sum over all elements of the receiver.\n\t\t *\n\t\t * @return the sum over all elements or 0 if the receiver is empty\n\t\t */\n\t\tdefault double sum()\n\t\t{\n\t\t\treturn reduce(0.0, (DoubleBinaryOperator) Double::sum);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Specialisation for {@code int} of a PrimitiveReducible.\n\t */\n\tinterface OfInt<E_CAT> extends PrimitiveReducible<Integer, E_CAT, IntConsumer>\n\t{\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault OfInt<E_CAT> dedupe()\n\t\t{\n\t\t\tIntPredicate isFirst = new IntPredicate()\n\t\t\t{\n\t\t\t\tboolean start = true;\n\t\t\t\tint previous = 0;\n\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(int i)\n\t\t\t\t{\n\t\t\t\t\tif (start) {\n\t\t\t\t\t\tstart = false;\n\t\t\t\t\t} else if (previous == i) {\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t\tprevious = i;\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t};\n\t\t\treturn filter(isFirst);\n\t\t}\n\n\t\t@Override\n\t\tdefault OfInt<E_CAT> distinct()\n\t\t{\n\t\t\treturn filter(new Distinct.OfInt());\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code filter} for {@code int}.\n\t\t *\n\t\t * @see Reducible#filter(java.util.function.Predicate)\n\t\t */\n\t\tOfInt<E_CAT> filter(IntPredicate predicate);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code int}.\n\t\t *\n\t\t * @see Reducible#map(java.util.function.Function)\n\t\t */\n\t\t<T> Reducible<T, ?> map(IntFunction<? extends T> function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code mapToDouble} for {@code int}.\n\t\t *\n\t\t * @see Reducible#mapToDouble(java.util.function.ToDoubleFunction)\n\t\t */\n\t\tOfDouble<?> mapToDouble(IntToDoubleFunction function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code mapToInt} for {@code int}.\n\t\t *\n\t\t * @see Reducible#mapToInt(java.util.function.ToIntFunction)\n\t\t */\n\t\tOfInt<?> mapToInt(IntUnaryOperator function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code mapToLong} for {@code int}.\n\t\t *\n\t\t * @see Reducible#mapToLong(java.util.function.ToLongFunction)\n\t\t */\n\t\tOfLong<?> mapToLong(IntToLongFunction function);\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault OfInt<E_CAT> consume()\n\t\t{\n\t\t\tforEach((int each) -> {});\n\t\t\treturn this;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code allMatch} for {@code int}.\n\t\t *\n\t\t * @see Reducible#allMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean allMatch(IntPredicate predicate)\n\t\t{\n\t\t\treturn ! anyMatch(predicate.negate());\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code anyMatch} for {@code int}.\n\t\t *\n\t\t * @see Reducible#anyMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean anyMatch(IntPredicate predicate)\n\t\t{\n\t\t\treturn ! filter(predicate).isEmpty();\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code noneMatch} for {@code int}.\n\t\t *\n\t\t * @see Reducible#noneMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean noneMatch(IntPredicate predicate)\n\t\t{\n\t\t\treturn ! anyMatch(predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collect} for {@code int}.\n\t\t *\n\t\t * @see Reducible#collect(Object[])\n\t\t */\n\t\tdefault int[] collect(int[] array)\n\t\t{\n\t\t\treturn collect(array, 0);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collect} for {@code int}.\n\t\t *\n\t\t * @see Reducible#collect(Object[], int)\n\t\t */\n\t\tdefault int[] collect(int[] array, int offset)\n\t\t{\n\t\t\tcollectAndCount(array, offset);\n\t\t\treturn array;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collect} for {@code int} storing the elements in a {@link BitSet}.\n\t\t * This method fails if the receiver yields a negative integer.\n\t\t *\n\t\t * @param indices a {@link BitSet}\n\t\t * @return the BitSet with all elements added to it\n\t\t * @throws IndexOutOfBoundsException if an integer is negative\n\t\t * @see Reducible#collect(java.util.Collection)\n\t\t */\n\t\tdefault BitSet collect(BitSet indices)\n\t\t{\n\t\t\tforEach((IntConsumer) indices::set);\n\t\t\treturn indices;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collectAndCount} for {@code int}.\n\t\t *\n\t\t * @see Reducible#collectAndCount(Object[])\n\t\t */\n\t\tdefault int collectAndCount(int[] array)\n\t\t{\n\t\t\treturn collectAndCount(array, 0);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collectAndCount} for {@code int}.\n\t\t *\n\t\t * @see Reducible#collectAndCount(Object[])\n\t\t */\n\t\tdefault int collectAndCount(int[] array, int offset)\n\t\t{\n\t\t\tObjects.requireNonNull(array);\n\t\t\tint index = reduce(offset, (int i, int e) -> {\n\t\t\t\tarray[i] = e;\n\t\t\t\treturn i + 1;\n\t\t\t});\n\t\t\treturn index - offset;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collectAndCount} for {@code int} storing the elements in a {@link BitSet}.\n\t\t * This method fails if the receiver yields a negative integer.\n\t\t *\n\t\t * @param indices a {@link BitSet}\n\t\t * @return the number of elements added to the BitSet\n\t\t * @throws IndexOutOfBoundsException if an integer is negative\n\t\t * @see Reducible#collectAndCount(java.util.Collection)\n\t\t */\n\t\tdefault int collectAndCount(BitSet indices)\n\t\t{\n\t\t\tObjects.requireNonNull(indices);\n\t\t\treturn reduce(0, (int c, int i) -> {\n\t\t\t\tindices.set(i);\n\t\t\t\treturn c + 1;\n\t\t\t});\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfInt collectDistinct()\n\t\t{\n\t\t\tDistinct.OfInt unseen = new Distinct.OfInt();\n\t\t\tfilter(unseen).consume();\n\t\t\treturn unseen.getSeen();\n\t\t}\n\n\t\t@Override\n\t\tdefault boolean contains(Object obj)\n\t\t{\n\t\t\tif (obj instanceof Integer) {\n\t\t\t\treturn contains(((Integer) obj).intValue());\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code contains} for {@code int}.\n\t\t *\n\t\t * @see Reducible#contains(Object)\n\t\t */\n\t\tdefault boolean contains(int i)\n\t\t{\n\t\t\treturn anyMatch((int e) -> e == i);\n\t\t}\n\n\t\t@Override\n\t\tdefault long count()\n\t\t{\n\t\t\t// avoid auto-boxing\n\t\t\treturn reduce(0, (long c, long i) -> c + 1);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code count} for {@code int}.\n\t\t *\n\t\t * @see Reducible#count(java.util.function.Predicate)\n\t\t */\n\t\tdefault long count(IntPredicate predicate)\n\t\t{\n\t\t\treturn filter(predicate).count();\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code detect} for {@code int}.\n\t\t *\n\t\t * @see Reducible#detect(java.util.function.Predicate)\n\t\t */\n\t\tint detect(IntPredicate predicate);\n\n\t\t/**\n\t\t * Find the maximum.\n\t\t *\n\t\t * @return an {@link OptionalDouble} either containing the maximum or being empty if the receiver is empty\n\t\t * @see Math#max(int, int).\n\t\t */\n\t\tdefault OptionalInt max()\n\t\t{\n\t\t\treturn reduce((IntBinaryOperator) Math::max);\n\t\t}\n\n\t\t/**\n\t\t * Find the minimum.\n\t\t *\n\t\t * @return an {@link OptionalDouble} either containing the minimum or being empty if the receiver is empty\n\t\t * @see Math#min(int, int).\n\t\t */\n\t\tdefault OptionalInt min()\n\t\t{\n\t\t\treturn reduce((IntBinaryOperator) Math::min);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code double}.\n\t\t * This methods exploits the <em>widening primitive conversion</em> from {@code int} to {@code double}.\n\t\t *\n\t\t * @see Reducible#reduce(java.util.function.BinaryOperator)\n\t\t */\n\t\tOptionalDouble reduce(DoubleBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code int}.\n\t\t *\n\t\t * @see Reducible#reduce(java.util.function.BinaryOperator)\n\t\t */\n\t\tOptionalInt reduce(IntBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code long}.\n\t\t * This methods exploits the <em>widening primitive conversion</em> from {@code int} to {@code long}.\n\t\t *\n\t\t * @see Reducible#reduce(java.util.function.BinaryOperator)\n\t\t */\n\t\tOptionalLong reduce(LongBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code int}.\n\t\t *\n\t\t * @see Reducible#reduce(Object, java.util.function.BiFunction)\n\t\t */\n\t\t<T> T reduce(T init, ObjIntFunction<T, T> accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code double}.\n\t\t * This methods exploits the <em>widening primitive conversion</em> from {@code int} to {@code double}.\n\t\t *\n\t\t * @see Reducible#reduce(double, common.functions.DoubleObjToDoubleFunction)\n\t\t */\n\t\tdouble reduce(double init, DoubleBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code int}.\n\t\t *\n\t\t * @see Reducible#reduce(int, common.functions.IntObjToIntFunction)\n\t\t */\n\t\tint reduce(int init, IntBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code long}.\n\t\t * This methods exploits the <em>widening primitive conversion</em> from {@code int} to {@code long}.\n\t\t *\n\t\t * @see Reducible#reduce(long, common.functions.LongObjToLongFunction)\n\t\t */\n\t\tlong reduce(long init, LongBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Compute the sum over all elements of the receiver.\n\t\t *\n\t\t * @return the sum over all elements or 0 if the receiver is empty\n\t\t */\n\t\tdefault long sum()\n\t\t{\n\t\t\treturn reduce(0L, (LongBinaryOperator) Long::sum);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Specialisation for {@code long} of a PrimitiveReducible.\n\t */\n\tinterface OfLong<E_CAT> extends PrimitiveReducible<Long, E_CAT, LongConsumer>\n\t{\n\t\t// Transforming Methods\n\n\t\t@Override\n\t\tdefault OfLong<E_CAT> dedupe()\n\t\t{\n\t\t\tLongPredicate isFirst = new LongPredicate()\n\t\t\t{\n\t\t\t\tboolean start = true;\n\t\t\t\tlong previous = 0;\n\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(long l)\n\t\t\t\t{\n\t\t\t\t\tif (start) {\n\t\t\t\t\t\tstart = false;\n\t\t\t\t\t} else if (previous == l) {\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t\tprevious = l;\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t};\n\t\t\treturn filter(isFirst);\n\t\t}\n\n\t\t@Override\n\t\tdefault OfLong<E_CAT> distinct()\n\t\t{\n\t\t\treturn filter(new Distinct.OfLong());\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code filter} for {@code long}.\n\t\t *\n\t\t * @see Reducible#filter(java.util.function.Predicate)\n\t\t */\n\t\tOfLong<E_CAT> filter(LongPredicate predicate);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code long}.\n\t\t *\n\t\t * @see Reducible#map(java.util.function.Function)\n\t\t */\n\t\t<T> Reducible<T, ?> map(LongFunction<? extends T> function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code long}.\n\t\t *\n\t\t * @see Reducible#mapToDouble(java.util.function.ToDoubleFunction)\n\t\t */\n\t\tOfDouble<?> mapToDouble(LongToDoubleFunction function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code long}.\n\t\t *\n\t\t * @see Reducible#mapToInt(java.util.function.ToIntFunction)\n\t\t */\n\t\tOfInt<?> mapToInt(LongToIntFunction function);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code map} for {@code long}.\n\t\t *\n\t\t * @see Reducible#mapToLong(java.util.function.ToLongFunction)\n\t\t */\n\t\tOfLong<?> mapToLong(LongUnaryOperator function);\n\n\n\n\t\t// Accumulations Methods (Consuming)\n\n\t\t@Override\n\t\tdefault OfLong<E_CAT> consume()\n\t\t{\n\t\t\tforEach((long each) -> {});\n\t\t\treturn this;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code allMatch} for {@code long}.\n\t\t *\n\t\t * @see Reducible#allMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean allMatch(LongPredicate predicate)\n\t\t{\n\t\t\treturn ! anyMatch(predicate.negate());\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code anyMatch} for {@code long}.\n\t\t *\n\t\t * @see Reducible#anyMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean anyMatch(LongPredicate predicate)\n\t\t{\n\t\t\treturn ! filter(predicate).isEmpty();\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code noneMatch} for {@code long}.\n\t\t *\n\t\t * @see Reducible#noneMatch(java.util.function.Predicate)\n\t\t */\n\t\tdefault boolean noneMatch(LongPredicate predicate)\n\t\t{\n\t\t\treturn ! anyMatch(predicate);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collect} for {@code long}.\n\t\t *\n\t\t * @see Reducible#collect(Object[])\n\t\t */\n\t\tdefault long[] collect(long[] array)\n\t\t{\n\t\t\treturn collect(array, 0);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collect} for {@code long}.\n\t\t *\n\t\t * @see Reducible#collect(Object[], int)\n\t\t */\n\t\tdefault long[] collect(long[] array, int offset)\n\t\t{\n\t\t\tcollectAndCount(array, offset);\n\t\t\treturn array;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collectAndCount} for {@code long}.\n\t\t *\n\t\t * @see Reducible#collectAndCount(Object[])\n\t\t */\n\t\tdefault int collectAndCount(long[] array)\n\t\t{\n\t\t\treturn collectAndCount(array, 0);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code collectAndCount} for {@code long}.\n\t\t *\n\t\t * @see Reducible#collectAndCount(Object[], int)\n\t\t */\n\t\tdefault int collectAndCount(long[] array, int offset)\n\t\t{\n\t\t\tObjects.requireNonNull(array);\n\t\t\tint index = reduce(offset, (int i, long e) -> {array[i] = e; return i + 1;});\n\t\t\treturn index - offset;\n\t\t}\n\n\t\t@Override\n\t\tdefault FunctionalPrimitiveIterable.OfLong collectDistinct()\n\t\t{\n\t\t\tDistinct.OfLong unseen = new Distinct.OfLong();\n\t\t\tfilter(unseen).consume();\n\t\t\treturn unseen.getSeen();\n\t\t}\n\n\t\t@Override\n\t\tdefault boolean contains(Object obj)\n\t\t{\n\t\t\tif (obj instanceof Long) {\n\t\t\t\treturn contains(((Long) obj).longValue());\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code contains} for {@code long}.\n\t\t *\n\t\t * @see Reducible#contains(Object)\n\t\t */\n\t\tdefault boolean contains(long l)\n\t\t{\n\t\t\treturn anyMatch((long e) -> e == l);\n\t\t}\n\n\t\t@Override\n\t\tdefault long count()\n\t\t{\n\t\t\t// avoid auto-boxing\n\t\t\treturn reduce(0, (long c, long l) -> c + 1);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code count} for {@code long}.\n\t\t *\n\t\t * @see Reducible#count(java.util.function.Predicate)\n\t\t */\n\t\tdefault long count(LongPredicate predicate)\n\t\t{\n\t\t\treturn filter(predicate).count();\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code detect} for {@code long}.\n\t\t *\n\t\t * @see Reducible#detect(java.util.function.Predicate)\n\t\t */\n\t\tlong detect(LongPredicate predicate);\n\n\t\t/**\n\t\t * Find the maximum.\n\t\t *\n\t\t * @return an {@link OptionalDouble} either containing the maximum or being empty if the receiver is empty\n\t\t * @see Math#max(long, long).\n\t\t */\n\t\tdefault OptionalLong max()\n\t\t{\n\t\t\treturn reduce((LongBinaryOperator) Math::max);\n\t\t}\n\n\t\t/**\n\t\t * Find the minimum.\n\t\t *\n\t\t * @return an {@link OptionalDouble} either containing the minimum or being empty if the receiver is empty\n\t\t * @see Math#min(long, long).\n\t\t */\n\t\tdefault OptionalLong min()\n\t\t{\n\t\t\treturn reduce((LongBinaryOperator) Math::min);\n\t\t}\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code long}.\n\t\t *\n\t\t * @see Reducible#reduce(java.util.function.BinaryOperator)\n\t\t */\n\t\tOptionalLong reduce(LongBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code long}.\n\t\t *\n\t\t * @see Reducible#reduce(Object, java.util.function.BiFunction)\n\t\t */\n\t\t<T> T reduce(T init, ObjLongFunction<T, T> accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code double}.\n\t\t *\n\t\t * @see Reducible#reduce(double, common.functions.DoubleObjToDoubleFunction)\n\t\t */\n\t\tdouble reduce(double init, DoubleLongToDoubleFunction accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code int}.\n\t\t *\n\t\t * @see Reducible#reduce(int, common.functions.IntObjToIntFunction)\n\t\t */\n\t\tint reduce(int init, IntLongToIntFunction accumulator);\n\n\t\t/**\n\t\t * Primitive specialisation of {@code reduce} for {@code long}.\n\t\t *\n\t\t * @see Reducible#reduce(long, common.functions.LongObjToLongFunction)\n\t\t */\n\t\tlong reduce(long init, LongBinaryOperator accumulator);\n\n\t\t/**\n\t\t * Compute the sum over all elements of the receiver.\n\t\t *\n\t\t * @return the sum over all elements or 0 if the receiver is empty\n\t\t */\n\t\tdefault long sum()\n\t\t{\n\t\t\treturn reduce(0L, (LongBinaryOperator) Long::sum);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/Range.java",
    "content": "package common.iterable;\n\nimport java.util.OptionalInt;\n\n/**\n * An Iterable that yields all integers between two values, first and last (both inclusive).\n * The step width can be customized and defaults to 1.\n * <p>\n * If {@code step > 0} then the sequence is <br>\n * <em>ascending</em> (start, start+1, ... , stop).<br>\n * otherwise<br>\n * <em>descending</em> (start, start-1, ... , stop).<br>\n */\npublic class Range implements FunctionalPrimitiveIterable.OfInt\n{\n\tprotected final int first; // inclusive\n\tprotected final int last;  // inclusive\n\tprotected final int step;\n\n\t/**\n\t * Factory method for a range from {@code 0} to {@code stop} (both inclusive)\n\t * with step width {@code 1}.\n\t *\n\t * @param stop last {@code int}, inclusive\n\t * @throws ArithmeticException if enumerating the Range would cause an integer over- or underflow\n\t */\n\tpublic static Range closed(int stop)\n\t{\n\t\treturn closed(0, stop, 1);\n\t}\n\n\t/**\n\t * Factory method for a range from {@code start} to {@code stop} (both inclusive)\n\t * with step width {@code 1}.\n\t *\n\t * @param start first {@code int}, inclusive\n\t * @param stop last {@code int}, inclusive\n\t * @throws ArithmeticException if enumerating the Range would cause an integer over- or underflow\n\t */\n\tpublic static Range closed(int start, int stop)\n\t{\n\t\treturn closed(start, stop, 1);\n\t}\n\n\t/**\n\t * Factory method for a range from {@code start} (inclusive) to {@code stop} (inclusive it it is a step)\n\t * with step width {@code step}.\n\t *\n\t * @param start first {@code int}, inclusive\n\t * @param stop last {@code int}, inclusive if it is a step\n\t * @param step an {@code int != 0} giving the step width\n\t * @throws ArithmeticException if enumerating the Range would cause an integer over- or underflow\n\t */\n\tpublic static Range closed(int start, int stop, int step)\n\t{\n\t\treturn new Range(start, stop, step, true);\n\t}\n\n\n\n\t/**\n\t * Constructor for a range from {@code 0} (inclusive) to {@code stop} (exclusive)\n\t * with step width 1.\n\t *\n\t * @param stop last {@code int}, exclusive\n\t * @throws ArithmeticException if enumerating the Range would cause an integer over- or underflow\n\t */\n\tpublic Range(int stop)\n\t{\n\t\tthis(0, stop);\n\t}\n\n\t/**\n\t * Constructor for a range from {@code start} (inclusive) to {@code stop} (exclusive)\n\t * with step width 1.\n\t *\n\t * @param start first {@code int}, inclusive\n\t * @param stop last {@code int}, exclusive\n\t * @throws ArithmeticException if enumerating the Range would cause an integer over- or underflow\n\t */\n\tpublic Range(int start, int stop)\n\t{\n\t\tthis(start, stop, 1);\n\t}\n\n\t/**\n\t * Constructor for a range from {@code start} (inclusive) to {@code stop} (exclusive)\n\t * with step width {@code step}.\n\t *\n\t * @param start first {@code int}, inclusive\n\t * @param stop last {@code int}, exclusive\n\t * @param step an {@code int != 0} giving the step width\n\t * @throws ArithmeticException if enumerating the Range would cause an integer over- or underflow\n\t */\n\tpublic Range(int start, int stop, int step)\n\t{\n\t\tthis(start, stop, step, false);\n\t}\n\n\t/**\n\t * Constructor for a range from {@code start} (inclusive) to {@code stop} (inclusive or exclusive)\n\t * with step width {@code step}.\n\t * If {@code step > 0} the range is ascending and otherwise descending.\n\t *\n\t * @param start first {@code int}, inclusive\n\t * @param stop last {@code int}, inclusive if it is a step and {@code closed == true}\n\t * @param step an {@code int != 0}\n\t * @param closed flag whether {@code stop} is inclusive ({@code true}) or not ({@code false})\n\t * @throws ArithmeticException if enumerating the Range would cause an integer over- or underflow\n\t */\n\tprivate Range(int start, int stop, int step, boolean closed)\n\t{\n\t\tif (step == 0) {\n\t\t\tthrow new IllegalArgumentException(\"Expected: step != 0\");\n\t\t}\n\t\t// convert to inclusive bound\n\t\tif (!closed) {\n\t\t\tstop = Math.addExact(stop, (step > 0) ? -1 : +1);\n\t\t}\n\t\t// normalize parameters\n\t\tlong distance = (long) stop - (long) start;\n\t\tif ((step > 0 && distance < 0) || (step < 0 && distance > 0)) {\n\t\t\t// empty range\n\t\t\tthis.first = 0;\n\t\t\tthis.last = -1;\n\t\t\tthis.step = 1;\n\t\t} else {\n\t\t\t// non-empty range\n\t\t\tthis.first = start;\n\t\t\t// calculate last element\n\t\t\tthis.last = (int) (start + (distance / step) * step);\n\t\t\t// set step = 1 for singleton ranges\n\t\t\tthis.step = (this.first == this.last) ? 1 : step;\n\t\t}\n\t\t// check for over- and underflows\n\t\tcheckForOverAndUnderflows();\n\t}\n\n\t/**\n\t * Check that the iteration does not over- or underflow at Integer.MAX_VALUE or Integer.MIN_VALUE.\n\t */\n\tprivate void checkForOverAndUnderflows()\n\t{\n\t\tif (isAscending()) {\n\t\t\tif (last + step < last) {\n\t\t\t\tthrow new ArithmeticException(\"integer overflow\");\n\t\t\t}\n\t\t} else {\n\t\t\tif (last + step > last) {\n\t\t\t\tthrow new ArithmeticException(\"integer underflow\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Answer whether the receiver is in ascending order.\n\t * Empty and singleton ranges are ascending by default.\n\t */\n\tpublic boolean isAscending()\n\t{\n\t\treturn step > 0;\n\t}\n\n\t/**\n\t * Answer whether the receiver contains exactly one number.\n\t */\n\tpublic boolean isSingleton()\n\t{\n\t\treturn first == last;\n\t}\n\n\t/**\n\t * Return a new range with all elements in reverse order.\n\t */\n\tpublic Range reversed()\n\t{\n\t\treturn new Range(last, first, -step, true);\n\t}\n\n\t@Override\n\tpublic RangeIterator iterator()\n\t{\n\t\tif (isAscending()) {\n\t\t\treturn new AscendingRangeIterator();\n\t\t} else {\n\t\t\treturn new DescendingRangeIterator();\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean isEmpty()\n\t{\n\t\t// Empty ranges are ascending by default.\n\t\treturn isAscending() && first > last;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn getClass().getSimpleName() + \".closed(\" + first + \", \" + last + \", \" + step + \")\";\n\t}\n\n\t/* (non-Javadoc)\n\t * @see java.lang.Object#hashCode()\n\t */\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tif (isEmpty()) {\n\t\t\treturn result;\n\t\t}\n\t\tresult = prime * result + first;\n\t\tresult = prime * result + last;\n\t\tresult = prime * result + step;\n\t\treturn result;\n\t}\n\n\t/* (non-Javadoc)\n\t * @see java.lang.Object#equals(java.lang.Object)\n\t */\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj) {\n\t\t\treturn true;\n\t\t}\n\t\tif (obj == null) {\n\t\t\treturn false;\n\t\t}\n\t\tif (!(obj instanceof Range)) {\n\t\t\treturn false;\n\t\t}\n\t\tRange other = (Range) obj;\n\t\tif (first != other.first) {\n\t\t\treturn false;\n\t\t}\n\t\tif (last != other.last) {\n\t\t\treturn false;\n\t\t}\n\t\tif (step != other.step) {\n\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\n\n\t/**\n\t * A abstract base class for an Iterator from {@code first} (inclusive) and {@code last} (exclusive) with a custom step width.\n\t */\n\tpublic abstract class RangeIterator implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\tprotected int next;\n\n\t\t/**\n\t\t * Constructor for a range Iterator.\n\t\t */\n\t\tpublic RangeIterator()\n\t\t{\n\t\t\tassert step != 0 : \"Expected: step != 0\";\n\t\t\tthis.next = first;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\tint current = next;\n\t\t\tnext += step;\n\t\t\treturn current;\n\t\t}\n\n\t\t@Override\n\t\tpublic long count()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn 0;\n\t\t\t}\n\t\t\tlong count = ((long) last - (long) next) / step + 1;\n\t\t\trelease();\n\t\t\treturn count;\n\t\t}\n\n\t\t@Override\n\t\tpublic long sum()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn 0;\n\t\t\t}\n\t\t\t// S(1..n) = k + (k+s) + (k+2s) + ... + (k+(n-1)s)\n\t\t\t// S(1..n) = n(2k + (n-1)s) / 2\n\t\t\tlong k = next; // store next, since count() exhausts the iterator\n\t\t\tlong count = count();\n\t\t\tlong sum = count * (2 * k + (count - 1) * step) / 2;\n\t\t\trelease();\n\t\t\treturn sum;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tnext = last + step;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Ascending Iterator from {@code first} (inclusive) and {@code last} (inclusive) with a custom step width.\n\t */\n\tprotected class AscendingRangeIterator extends RangeIterator\n\t{\n\t\t/**\n\t\t * Constructor for an ascending Iterator.\n\t\t */\n\t\tpublic AscendingRangeIterator()\n\t\t{\n\t\t\tsuper();\n\t\t\tassert step > 0 : \"Expected: step > 0\";\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn next <= last;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(int i)\n\t\t{\n\t\t\t// Is in interval?\n\t\t\tboolean inInterval = (i >= next) && (i <= last);\n\t\t\t// Is a step? Mind potential overflow!\n\t\t\tboolean contains = inInterval && (((long) i - (long) next) % step) == 0;\n\t\t\trelease();\n\t\t\treturn contains;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt max()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalInt.empty();\n\t\t\t}\n\t\t\tOptionalInt max = OptionalInt.of(last);\n\t\t\trelease();\n\t\t\treturn max;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt min()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalInt.empty();\n\t\t\t}\n\t\t\tOptionalInt min = OptionalInt.of(next);\n\t\t\trelease();\n\t\t\treturn min;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Descending Iterator from {@code first} (inclusive) and {@code last} (inclusive) with a custom step width.\n\t */\n\tprotected class DescendingRangeIterator extends RangeIterator\n\t{\n\t\t/**\n\t\t * Constructor for an descending Iterator.\n\t\t */\n\t\tpublic DescendingRangeIterator()\n\t\t{\n\t\t\tsuper();\n\t\t\tassert step < 0 : \"Expected: step < 0\";\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn next >= last;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(int i)\n\t\t{\n\t\t\t// Is in interval?\n\t\t\tboolean inInterval = (i <= next) && (i >= last);\n\t\t\t// Is a step? Mind potential overflow!\n\t\t\tboolean contains = inInterval && (((long) i - (long) next) % step) == 0;\n\t\t\trelease();\n\t\t\treturn contains;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt max()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalInt.empty();\n\t\t\t}\n\t\t\tOptionalInt max = OptionalInt.of(next);\n\t\t\trelease();\n\t\t\treturn max;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt min()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\treturn OptionalInt.empty();\n\t\t\t}\n\t\t\tOptionalInt min = OptionalInt.of(last);\n\t\t\trelease();\n\t\t\treturn min;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/Reducible.java",
    "content": "package common.iterable;\n\nimport common.functions.DoubleObjToDoubleFunction;\nimport common.functions.IntObjToIntFunction;\nimport common.functions.LongObjToLongFunction;\n\nimport java.util.*;\nimport java.util.function.*;\n\n/**\n * A {@link Reducible} provides <em>transformation</em> and <em>accumulation</em> operations similar to {@link java.util.stream.Stream Stream}.\n * It serves as a bridge between Iterator-based code and the functional API provided by Java streams.\n * The operations are implemented and specialized in {@link FunctionalIterator} and {@link FunctionalIterable}.\n * The following example illustrates is usage.\n *\n * <pre>\n * List&lt;String>  allFibonacci = List.of(\"0\", \"1\", \"1\", \"2\", \"3\", \"5\", \"8\", \"13\");\n * List&lt;Integer> oddFibonacci = Reducible.extend(allFibonacci)\n *                                   .mapToInt(Integer::parseInt)\n *                                   .filter((int i) -> i % 2 != 0)\n *                                   .collect(ArrayList::new);\n * </pre>\n * The code computes the odd Fibonacci numbers from a {@code List} of {@code String} representations:\n * <ol>\n * <li>Extend an ordinary Iterable (the {@code List}) with the methods of this interface\n * <li>Map the String representation of each number to its respective {@code int} value\n * <li>Filter all odd numbers\n * <li>Collect the filtered numbers in a new {@code ArrayList}\n * </ol>\n * Please note that {@link Reducible#mapToInt} and {@link Reducible#filter} only wrap the underlying Reducible.\n * The actual computation happens on-the-fly when {@code collect} is called.\n *\n * <p><em>Transformation operations</em> (known as <a href=\"package-summary.html#StreamOps\">intermediate operations</a> on streams)\n * <em>transform the sequence of elements</em>, e.g., by filtering with a predicate or by mapping elements using a function.\n * All transformation operations are defined in this interface with one exception:\n * {@code flatMap} and its primitive specializations {@code flatMapToDouble}, {@code flatMapToInt} and {@code flatMapToLong}\n * have to be defined in the implementors of this interface, as Java's generic type system is not flexible enough to define it here.\n *\n * <p><em>Accumulation operations</em> (known as <a href=\"package-summary.html#StreamOps\">terminal operations</a> on streams)\n * <em>consume the elements</em> and <em>compute a result</em>, e.g., by testing whether all elements match a predicate or by collecting all elements in an array.\n * The most general accumulation operation is {@link Reducible#reduce(Object, BiFunction) reduce}.\n * To enable an efficient treatment of the primitive types {@code double}, {@code int} and {@code long}, reduce is overloaded.\n * Please note that implementors of the interface may consume no elements if the result of an accumulation can be computed directly.\n *\n * @param <E> the type of elements returned by this Reducible\n * @param <E_CAT> the type of Reducibles accepted by {@link Reducible#concat concat}\n *ø\n * @see java.util.stream.Stream Stream\n */\npublic interface Reducible<E, E_CAT>\n{\n\t// Bridging methods to Iterator-based code\n\n\t/**\n\t * Extend an Iterable with the methods provided by FunctionalIterable.\n\t * Answer the argument if it already implements {@code FunctionalIterable}.\n\t *\n\t * @param iterable the {@link Iterable} to extend\n\t * @return a {@link FunctionalIterable} that is either the argument or an adaptor on the argument\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tstatic <E> FunctionalIterable<E> extend(Iterable<E> iterable)\n\t{\n\t\tif (iterable instanceof FunctionalIterable) {\n\t\t\treturn (FunctionalIterable<E>) iterable;\n\t\t}\n\t\tif (iterable instanceof PrimitiveIterable.OfDouble) {\n\t\t\treturn (FunctionalIterable<E>) extend((PrimitiveIterable.OfDouble) iterable);\n\t\t}\n\t\tif (iterable instanceof PrimitiveIterable.OfInt) {\n\t\t\treturn (FunctionalIterable<E>) extend((PrimitiveIterable.OfInt) iterable);\n\t\t}\n\t\tif (iterable instanceof PrimitiveIterable.OfLong) {\n\t\t\treturn (FunctionalIterable<E>) extend((PrimitiveIterable.OfLong) iterable);\n\t\t}\n\t\treturn new IterableAdaptor.Of<>(iterable);\n\n\t}\n\n\t/**\n\t * Extend an Iterator with the methods provided by FunctionalIterator.\n\t * If the Iterator is a PrimitiveIterator, the extension is a {@code FunctionalPrimitiveIterator}.\n\t * Answer the argument if it already implements {@code FunctionalIterator}.\n\t *\n\t * @param iterator the {@link Iterator} to extend\n\t * @return a {@link FunctionalIterator} that is either the argument or an adaptor on the argument\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tstatic <E> FunctionalIterator<E> extend(Iterator<E> iterator)\n\t{\n\t\tif (iterator instanceof FunctionalIterator) {\n\t\t\treturn (FunctionalIterator<E>) iterator;\n\t\t}\n\t\tif (iterator instanceof PrimitiveIterator.OfDouble) {\n\t\t\treturn (FunctionalIterator<E>) extend((PrimitiveIterator.OfDouble) iterator);\n\t\t}\n\t\tif (iterator instanceof PrimitiveIterator.OfInt) {\n\t\t\treturn (FunctionalIterator<E>) extend((PrimitiveIterator.OfInt) iterator);\n\t\t}\n\t\tif (iterator instanceof PrimitiveIterator.OfLong) {\n\t\t\treturn (FunctionalIterator<E>) extend((PrimitiveIterator.OfLong) iterator);\n\t\t}\n\t\treturn new IteratorAdaptor.Of<>(iterator);\n\t}\n\n\t/**\n\t * Extend a PrimitiveIterable.OfDouble with the methods provided by FunctionalPrimitiveIterable.\n\t * Answer the argument if it already implements {@code FunctionalIterable}.\n\t *\n\t * @param iterable the {@link PrimitiveIterable.OfDouble} to extend\n\t * @return a {@link FunctionalPrimitiveIterable.OfDouble} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterable.OfDouble extend(PrimitiveIterable.OfDouble iterable)\n\t{\n\t\tif (iterable instanceof FunctionalPrimitiveIterable.OfDouble) {\n\t\t\treturn (FunctionalPrimitiveIterable.OfDouble) iterable;\n\t\t}\n\t\treturn new IterableAdaptor.OfDouble(iterable);\n\t}\n\n\t/**\n\t * Extend a PrimitiveIterator.OfDouble with the methods provided by FunctionalPrimitiveIterator.\n\t * Answer the argument if it already implements {@code FunctionalPrimitiveIterator.OfDouble}.\n\t *\n\t * @param iterator the {@link PrimitiveIterator.OfDouble} to extend\n\t * @return a {@link FunctionalPrimitiveIterator.OfDouble} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterator.OfDouble extend(PrimitiveIterator.OfDouble iterator)\n\t{\n\t\tif (iterator instanceof FunctionalPrimitiveIterator.OfDouble) {\n\t\t\treturn (FunctionalPrimitiveIterator.OfDouble) iterator;\n\t\t}\n\t\treturn new IteratorAdaptor.OfDouble(iterator);\n\t}\n\n\t/**\n\t * Extend a PrimitiveIterable.OfInt with the methods provided by FunctionalPrimitiveIterable.\n\t * Answer the argument if it already implements {@code FunctionalPrimitiveIterable}.\n\t *\n\t * @param iterable the {@link PrimitiveIterable.OfInt} to extend\n\t * @return a {@link FunctionalPrimitiveIterable.OfDouble} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterable.OfInt extend(PrimitiveIterable.OfInt iterable)\n\t{\n\t\tif (iterable instanceof FunctionalPrimitiveIterable.OfInt) {\n\t\t\treturn (FunctionalPrimitiveIterable.OfInt) iterable;\n\t\t}\n\t\treturn new IterableAdaptor.OfInt(iterable);\n\t}\n\n\t/**\n\t * Extend a PrimitiveIterator.OfInt with the methods provided by FunctionalPrimitiveIterator.\n\t * Answer the argument if it already implements {@code FunctionalPrimitiveIterator.OfInt}.\n\t *\n\t * @param iterator the {@link PrimitiveIterator.OfInt} to extend\n\t * @return a {@link FunctionalPrimitiveIterator.OfInt} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterator.OfInt extend(PrimitiveIterator.OfInt iterator)\n\t{\n\t\tif (iterator instanceof FunctionalPrimitiveIterator.OfInt) {\n\t\t\treturn (FunctionalPrimitiveIterator.OfInt) iterator;\n\t\t}\n\t\treturn new IteratorAdaptor.OfInt(iterator);\n\t}\n\n\t/**\n\t * Extend a PrimitiveIterable.OfLong with the methods provided by FunctionalPrimitiveIterable.\n\t * Answer the argument if it already implements {@code FunctionalPrimitiveIterable}.\n\t *\n\t * @param iterable the {@link PrimitiveIterable.OfLong} to extend\n\t * @return a {@link FunctionalPrimitiveIterable.OfLong} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterable.OfLong extend(PrimitiveIterable.OfLong iterable)\n\t{\n\t\tif (iterable instanceof FunctionalPrimitiveIterable.OfLong) {\n\t\t\treturn (FunctionalPrimitiveIterable.OfLong) iterable;\n\t\t}\n\t\treturn new IterableAdaptor.OfLong(iterable);\n\t}\n\n\t/**\n\t * Extend a PrimitiveIterator.OfLong with the methods provided by FunctionalPrimitiveIterator.\n\t * Answer the argument if it already implements {@code FunctionalPrimitiveIterator.OfLong}.\n\t *\n\t * @param iterator the {@link PrimitiveIterator.OfLong} to extend\n\t * @return a {@link FunctionalPrimitiveIterator.OfLong} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterator.OfLong extend(PrimitiveIterator.OfLong iterator)\n\t{\n\t\tif (iterator instanceof FunctionalPrimitiveIterator.OfLong) {\n\t\t\treturn (FunctionalPrimitiveIterator.OfLong) iterator;\n\t\t}\n\t\treturn new IteratorAdaptor.OfLong(iterator);\n\t}\n\n\t/**\n\t * Concatenate a sequence of Iterables.\n\t * The returned FunctionalIterable iterates over the elements in the order of the argument sequence.\n\t *\n\t * @param iterables the {@link Iterable}s to concatenate\n\t * @return a {@link FunctionalIterable} that iterates over the elements of each Iterable\n\t */\n\tstatic <E> FunctionalIterable<E> concat(Iterable<? extends Iterable<? extends E>> iterables)\n\t{\n\t\treturn new ChainedIterable.Of(iterables);\n\t}\n\n\t/**\n\t * Concatenate a sequence of Iterators.\n\t * The returned FunctionalIterator iterates over the elements in the order of the argument sequence.\n\t *\n\t * @param iterators the {@link Iterator}s to concatenate\n\t * @return a {@link FunctionalIterator} that iterates over the elements of each Iterator\n\t */\n\tstatic <E> FunctionalIterator<E> concat(Iterator<? extends Iterator<? extends E>> iterators)\n\t{\n\t\treturn new ChainedIterator.Of(iterators);\n\t}\n\n\t/**\n\t * Primitive specialisation of {@code concat} for {@code double}.\n\t *\n\t * @param iterables the {@link PrimitiveIterable.OfDouble}s to concatenate\n\t * @return a {@link FunctionalPrimitiveIterable.OfDouble} that iterates over the elements of each Iterable\n\t */\n\tstatic FunctionalPrimitiveIterable.OfDouble concatDouble(Iterable<? extends PrimitiveIterable.OfDouble> iterables)\n\t{\n\t\treturn new ChainedIterable.OfDouble(iterables);\n\t}\n\n\t/**\n\t * Primitive specialisation of {@code concat} for {@code double}.\n\t *\n\t * @param iterators the {@link PrimitiveIterator.OfDouble}s to concatenate\n\t * @return a {@link FunctionalPrimitiveIterator.OfDouble} that iterates over the elements of each Iterator\n\t */\n\tstatic FunctionalPrimitiveIterator.OfDouble concatDouble(Iterator<? extends PrimitiveIterator.OfDouble> iterators)\n\t{\n\t\treturn new ChainedIterator.OfDouble(iterators);\n\t}\n\n\t/**\n\t * Primitive specialisation of {@code concat} for {@code int}.\n\t *\n\t * @param iterables the {@link PrimitiveIterable.OfInt}s to concatenate\n\t * @return a {@link FunctionalPrimitiveIterable.OfInt} that iterates over the elements of each Iterable\n\t */\n\tstatic FunctionalPrimitiveIterable.OfInt concatInt(Iterable<? extends PrimitiveIterable.OfInt> iterables)\n\t{\n\t\treturn new ChainedIterable.OfInt(iterables);\n\t}\n\n\t/**\n\t * Primitive specialisation of {@code concat} for {@code int}.\n\t *\n\t * @param iterators the {@link PrimitiveIterator.OfInt}s to concatenate\n\t * @return a {@link FunctionalPrimitiveIterator.OfInt} that iterates over the elements of each Iterator\n\t */\n\tstatic FunctionalPrimitiveIterator.OfInt concatInt(Iterator<? extends PrimitiveIterator.OfInt> iterators)\n\t{\n\t\treturn new ChainedIterator.OfInt(iterators);\n\t}\n\n\t/**\n\t * Primitive specialisation of {@code concat} for {@code long}.\n\t *\n\t * @param iterables the {@link PrimitiveIterable.OfLong}s to concatenate\n\t * @return a {@link FunctionalPrimitiveIterable.OfLong} that iterates over the elements of each Iterable\n\t */\n\tstatic FunctionalPrimitiveIterable.OfLong concatLong(Iterable<? extends PrimitiveIterable.OfLong> iterables)\n\t{\n\t\treturn new ChainedIterable.OfLong(iterables);\n\t}\n\n\t/**\n\t * Primitive specialisation of {@code concat} for {@code long}.\n\t *\n\t * @param iterators the {@link PrimitiveIterator.OfLong}s to concatenate\n\t * @return a {@link FunctionalPrimitiveIterator.OfLong} that iterates over the elements of each Iterator\n\t */\n\tstatic FunctionalPrimitiveIterator.OfLong concatLong(Iterator<? extends PrimitiveIterator.OfLong> iterators)\n\t{\n\t\treturn new ChainedIterator.OfLong(iterators);\n\t}\n\n\t/**\n\t * Convert an Iterable&lt;Double&gt; to a FunctionalPrimitiveIterable.OfDouble by unboxing each element.\n\t * If the argument's Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterable if it already implements of FunctionalPrimitiveIterable.OfDouble.\n\t *\n\t * @param iterable the {@link Iterable}&lt;Double&gt; to extend\n\t * @return a {@link FunctionalPrimitiveIterable.OfDouble} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterable.OfDouble unboxDouble(Iterable<Double> iterable)\n\t{\n\t\tif (iterable instanceof FunctionalPrimitiveIterable.OfDouble) {\n\t\t\treturn (FunctionalPrimitiveIterable.OfDouble) iterable;\n\t\t}\n\t\treturn extend(PrimitiveIterable.unboxDouble(iterable));\n\t}\n\n\t/**\n\t * Convert an Iterator&lt;Double&gt; to a FunctionalPrimitiveIterator.OfDouble by unboxing each element.\n\t * If the Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterator if it already implements of FunctionalPrimitiveIterator.OfDouble.\n\t *\n\t * @param iterator the {@link Iterator}&lt;Double&gt; to unbox\n\t * @return a {@link FunctionalPrimitiveIterator.OfDouble} that is either the argument or an unboxing iterator\n\t */\n\tstatic FunctionalPrimitiveIterator.OfDouble unboxDouble(Iterator<Double> iterator)\n\t{\n\t\tif (iterator instanceof PrimitiveIterator.OfDouble) {\n\t\t\treturn extend((PrimitiveIterator.OfDouble) iterator);\n\t\t}\n\t\treturn extend(PrimitiveIterable.unboxDouble(iterator));\n\t}\n\n\t/**\n\t * Convert an Iterable&lt;Integer&gt; to a FunctionalPrimitiveIterable.OfInt by unboxing each element.\n\t * If the argument's Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterable if it already implements of FunctionalPrimitiveIterable.OfInt.\n\t *\n\t * @param iterable the {@link Iterable}&lt;Integer&gt; to extend\n\t * @return a {@link FunctionalPrimitiveIterable.OfInt} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterable.OfInt unboxInt(Iterable<Integer> iterable)\n\t{\n\t\tif (iterable instanceof FunctionalPrimitiveIterable.OfInt) {\n\t\t\treturn (FunctionalPrimitiveIterable.OfInt) iterable;\n\t\t}\n\t\treturn extend(PrimitiveIterable.unboxInt(iterable));\n\t}\n\n\t/**\n\t * Convert an Iterator&lt;Integer&gt; to a FunctionalPrimitiveIterator.OfInt by unboxing each element.\n\t * If the Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterator if it already implements of FunctionalPrimitiveIterator.OfInt.\n\t *\n\t * @param iterator the {@link Iterator}&lt;Integer&gt; to unbox\n\t * @return a {@link FunctionalPrimitiveIterator.OfInt} that is either the argument or an unboxing iterator\n\t */\n\tstatic FunctionalPrimitiveIterator.OfInt unboxInt(Iterator<Integer> iterator)\n\t{\n\t\tif (iterator instanceof PrimitiveIterator.OfInt) {\n\t\t\treturn extend((PrimitiveIterator.OfInt) iterator);\n\t\t}\n\t\treturn extend(PrimitiveIterable.unboxInt(iterator));\n\t}\n\n\t/**\n\t * Convert an Iterable&lt;Long&gt; to a FunctionalPrimitiveIterable.OfLong by unboxing each element.\n\t * If the argument's Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterable if it already implements of FunctionalPrimitiveIterable.OfLong.\n\t *\n\t * @param iterable the {@link Iterable}&lt;Long&gt; to extend\n\t * @return a {@link FunctionalPrimitiveIterable.OfLong} that is either the argument or an adaptor on the argument\n\t */\n\tstatic FunctionalPrimitiveIterable.OfLong unboxLong(Iterable<Long> iterable)\n\t{\n\t\tif (iterable instanceof FunctionalPrimitiveIterable.OfLong) {\n\t\t\treturn (FunctionalPrimitiveIterable.OfLong) iterable;\n\t\t}\n\t\treturn extend(PrimitiveIterable.unboxLong(iterable));\n\t}\n\n\t/**\n\t * Convert an Iterator&lt;Long&gt; to a FunctionalPrimitiveIterator.OfLong by unboxing each element.\n\t * If the Iterator yields {@code null}, a {@link NullPointerException} is thrown when iterating.\n\t * Answer the Iterator if it already implements of FunctionalPrimitiveIterator.OfLong.\n\t *\n\t * @param iterator the {@link Iterator}&lt;Long&gt; to unbox\n\t * @return a {@link FunctionalPrimitiveIterator.OfLong} that is either the argument or an unboxing iterator\n\t */\n\tstatic FunctionalPrimitiveIterator.OfLong unboxLong(Iterator<Long> iterator)\n\t{\n\t\tif (iterator instanceof PrimitiveIterator.OfLong) {\n\t\t\treturn extend((PrimitiveIterator.OfLong) iterator);\n\t\t}\n\t\treturn extend(PrimitiveIterable.unboxLong(iterator));\n\t}\n\n\n\n\t// Fundamental methods\n\n\t/**\n\t * Perform an action with each of the receivers elements.\n\t *\n\t * @param action the action to be performed with each element\n\t * @see Iterable#forEach(Consumer)\n\t */\n\tvoid forEach(Consumer<? super E> action);\n\n\t/**\n\t * Test whether the receiver is empty.\n\t *\n\t * @return {@code true} iff the receiver is empty\n\t */\n\tboolean isEmpty();\n\n\n\n\t// Transforming Methods\n\n\t/**\n\t * Concatenate the receiver and the argument.\n\t * The returned Reducible first iterates over the elements of the receiver and then over the elements of the argument.\n\t *\n\t * @param reducible the {@link Reducible} to append\n\t * @return a {@link Reducible} that iterates over the elements of the receiver and the argument\n\t */\n\tReducible<E,E_CAT> concat(E_CAT reducible);\n\n\t/**\n\t * Remove consecutive duplicate elements such that only the first occurrence in a sequence is retained.\n\t * Duplicates are identified in terms of {@link Object#equals}.\n\t */\n\tdefault Reducible<E,E_CAT> dedupe()\n\t{\n\t\tPredicate<E> isFirst = new Predicate<>()\n\t\t{\n\t\t\tObject previous = new Object();\n\n\t\t\t@Override\n\t\t\tpublic boolean test(E obj)\n\t\t\t{\n\t\t\t\tif (Objects.equals(previous, obj)) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t\tprevious = obj;\n\t\t\t\treturn true;\n\t\t\t}\n\t\t};\n\t\treturn filter(isFirst);\n\t}\n\n\t/**\n\t * Remove duplicate elements from the receiver such that only one occurrence is retained.\n\t * Duplicates are identified in terms of {@link Object#equals} which requires a proper implementation of {@link Object#hashCode}.\n\t */\n\tdefault Reducible<E,E_CAT> distinct()\n\t{\n\t\treturn filter(new Distinct.Of<>());\n\t}\n\n\t/**\n\t * Filter the receiver by a predicate, i.e., only elements that match the predicate are kept.\n\t *\n\t * @param predicate a predicate evaluating to {@code true} for the elements to keep\n\t */\n\tReducible<E,E_CAT> filter(Predicate<? super E> predicate);\n\n\t/**\n\t * Map each element.\n\t *\n\t * @param function a mapping function that is applied to each element\n\t */\n\t<T> Reducible<T,?> map(Function<? super E, ? extends T> function);\n\n\t/**\n\t * Map each element to a {@code double}.\n\t *\n\t * @param function a mapping function that is applied to each element\n\t */\n\tPrimitiveReducible.OfDouble<?> mapToDouble(ToDoubleFunction<? super E> function);\n\n\t/**\n\t * Map each element to an {@code int}.\n\t *\n\t * @param function a mapping function that is applied to each element\n\t */\n\tPrimitiveReducible.OfInt<?> mapToInt(ToIntFunction<? super E> function);\n\n\t/**\n\t * Map each element to a {@code long}.\n\t *\n\t * @param function a mapping function that is applied to each element\n\t */\n\tPrimitiveReducible.OfLong<?> mapToLong(ToLongFunction<? super E> function);\n\n\t/**\n\t * Remove all {@code null} elements.\n\t */\n\tdefault Reducible<E,E_CAT> nonNull()\n\t{\n\t\treturn filter(Objects::nonNull);\n\t}\n\n\n\n\t// Accumulations Methods (Consuming)\n\n\t/**\n\t * Consume this Reducible, i.e., iterate over all its elements.\n\t */\n\tdefault Reducible<E,E_CAT> consume()\n\t{\n\t\tforEach((E each) -> {});\n\t\treturn this;\n\t}\n\n\t/**\n\t * Test whether each element matches a predicate.\n\t *\n\t * @param predicate a {@link Predicate} to test the element against\n\t * @return {@code true} iff the predicate evaluates to {@code true} for each element\n\t */\n\tdefault boolean allMatch(Predicate<? super E> predicate)\n\t{\n\t\treturn !anyMatch(predicate.negate());\n\t}\n\n\t/**\n\t * Test whether any element matches a predicate.\n\t * Return {@code true} after the first match without testing the remaining elements.\n\t *\n\t * @param predicate a {@link Predicate} to test the elements against\n\t * @return {@code true} iff the predicate evaluates to {@code true} for any element\n\t */\n\tdefault boolean anyMatch(Predicate<? super E> predicate)\n\t{\n\t\treturn ! filter(predicate).isEmpty();\n\t}\n\n\t/**\n\t * Test whether no element matches a predicate.\n\t * Return {@code false} after the first match without testing the remaining elements.\n\t *\n\t * @param predicate a {@link Predicate} to test the elements against\n\t * @return {@code false} iff the predicate evaluates to {@code true} for any element\n\t */\n\tdefault boolean noneMatch(Predicate<? super E> predicate)\n\t{\n\t\treturn !anyMatch(predicate);\n\t}\n\n\t/**\n\t * Build an array-like string that lists the string representation {@link Object#toString} of each element.\n\t *\n\t * @return a String of the form \"[e_1, e_2, ... , e_n]\"\n\t */\n\tdefault String asString()\n\t{\n\t\tStringBuilder builder = new StringBuilder(\"[\");\n\t\tforEach(each -> {\n\t\t\tif (builder.length() > 1) {\n\t\t\t\tbuilder.append(\", \");\n\t\t\t}\n\t\t\tbuilder.append(each);\n\t\t});\n\t\treturn builder.append(\"]\").toString();\n\t}\n\n\t/**\n\t * Add each element to a newly instantiated {@code Collection} supplied by the argument using {@link Collection#add(Object)}.\n\t *\n\t * @param constructor a function yielding a new Collection\n\t * @return the new Collection with all elements added to it\n\t * @see java.util.stream.Stream#collect(Supplier, java.util.function.BiConsumer, java.util.function.BiConsumer)\n\t */\n\tdefault <C extends Collection<? super E>> C collect(Supplier<? extends C> constructor)\n\t{\n\t\tObjects.requireNonNull(constructor);\n\t\tC collection = constructor.get();\n\t\tcollect(collection);\n\t\treturn collection;\n\t}\n\n\t/**\n\t * Add each element to the argument {@code Collection} using {@link Collection#add(Object)}.\n\t *\n\t * @param collection a {@link Collection}\n\t * @return the Collection with all elements added to it\n\t */\n\tdefault <C extends Collection<? super E>> C collect(C collection)\n\t{\n\t\tObjects.requireNonNull(collection);\n\t\tforEach(collection::add);\n\t\treturn collection;\n\t}\n\n\t/**\n\t * Store each element in an array starting at index 0.\n\t *\n\t * @param array an Array of the receiver's element type\n\t * @return the array with all elements stored in it\n\t */\n\tdefault E[] collect(E[] array)\n\t{\n\t\treturn collect(array, 0);\n\t}\n\n\t/**\n\t * Store each element in an array starting at index {@code offset}.\n\t *\n\t * @param array an Array of the receiver's element type\n\t * @param offset an index (inclusive) from which on the elements are stored\n\t * @return the array with all elements stored in it\n\t */\n\tdefault E[] collect(E[] array, int offset)\n\t{\n\t\tcollectAndCount(array, offset);\n\t\treturn array;\n\t}\n\n\t/**\n\t * Add each element to the argument {@code Collection} using {@link Collection#add(Object)} and count the number of elements added.\n\t *\n\t * @param collection a {@link Collection}\n\t * @return the number of elements added to the Collection\n\t */\n\tdefault long collectAndCount(Collection<? super E> collection)\n\t{\n\t\tObjects.requireNonNull(collection);\n\t\treturn reduce(0L, (long c, E e) -> {collection.add(e); return c + 1;});\n\t}\n\n\t/**\n\t * Store each element in an array starting at index 0 and count the number of elements stored.\n\t *\n\t * @param array an Array of the receiver's element type\n\t * @return the number of elements stored in the array\n\t */\n\tdefault int collectAndCount(E[] array)\n\t{\n\t\treturn collectAndCount(array, 0);\n\t}\n\n\t/**\n\t * Store each element in an array starting at index {@code offset} and count the number of elements stored.\n\t *\n\t * @param array an Array of the receiver's element type\n\t * @param offset an index (inclusive) from which on the elements are stored\n\t * @return the number of elements stored in the array\n\t */\n\tdefault int collectAndCount(E[] array, int offset)\n\t{\n\t\tObjects.requireNonNull(array);\n\t\tint index = reduce(offset, (int i, E e) -> {array[i] = e; return i + 1;});\n\t\treturn index - offset;\n\t}\n\n\t/**\n\t * Collect distinct elements from the receiver such that only one occurrence of each element is retained.\n\t * Duplicates are identified in terms of {@link Object#equals} which requires a proper implementation of {@link Object#hashCode}.\n\t * The order of elements in the result may differ from the order in the receiver.\n\t *\n\t * @return a {@link FunctionalIterable} that contains each distinct of the receiver exactly once\n\t * @see FunctionalIterator#distinct()\n\t */\n\tdefault FunctionalIterable<E> collectDistinct()\n\t{\n\t\tDistinct.Of<E> unseen = new Distinct.Of<>();\n\t\tfilter(unseen).consume();\n\t\treturn unseen.getSeen();\n\t}\n\n\t/**\n\t * Test in terms of {@link Object#equals} whether an object (or {@code null}) is one of the receiver's elements.\n\t *\n\t * @param obj an object to be found in the receiver\n\t * @return {@code true} if the argument is contained in the receiver\n\t */\n\tdefault boolean contains(Object obj)\n\t{\n\t\treturn anyMatch((obj == null) ? Objects::isNull : obj::equals);\n\t}\n\n\t/**\n\t * Count the number of elements in the receiver.\n\t *\n\t * @return the number of elements\n\t */\n\tdefault long count()\n\t{\n\t\treturn reduce(0L, (long c, E e) -> c + 1);\n\t}\n\n\t/**\n\t * Count the number of elements that match a predicate.\n\t *\n\t * @param predicate a {@link Predicate} evaluating to {@code true} for the elements to count\n\t * @return the number of elements matching the predicate\n\t */\n\tdefault long count(Predicate<? super E> predicate)\n\t{\n\t\treturn filter(predicate).count();\n\t}\n\n\t/**\n\t * Find the first element that matches a predicate.\n\t *\n\t * @param predicate a {@link Predicate} evaluating to {@code true} for the element to return\n\t * @return the first a matching element\n\t * @throws NoSuchElementException if no matching element was found\n\t */\n\tE detect(Predicate<? super E> predicate);\n\n\t/**\n\t * Reduce the receiver with an accumulator similar to {@code fold}.\n\t * The first element serves as initial value for the reduction of the remaining elements.\n\t *\n\t * @param accumulator a {@link BinaryOperator} taking an intermediate result as first argument and an element as second argument\n\t * @return an {@link Optional} either containing the result of the evaluation of the accumulator with the last element or being empty if the receiver is empty.\n\t * @throws NullPointerException if the result of the reduction is {@code null}\n\t * @see FunctionalIterator#reduce(Object, BiFunction)\n\t */\n\tOptional<E> reduce(BinaryOperator<E> accumulator);\n\n\t/**\n\t * Reduce the receiver with an accumulator and an initial value.\n\t * First, the accumulator is evaluated with the initial value and the first element.\n\t * Then it is evaluated with each subsequent element and the result of the previous evaluation.\n\t *\n\t * @param init an initial value for the reduction\n\t * @param accumulator a {@link BiFunction} taking an intermediate result as first argument and an element as second argument\n\t * @return the result of the evaluation of the accumulator with the last element\n\t */\n\t<T> T reduce(T init, BiFunction<T, ? super E, T> accumulator);\n\n\t/**\n\t * Primitive specialisation of {@code reduce} for values of type {@code double}.\n\t *\n\t * @see FunctionalIterator#reduce(Object, BiFunction)\n\t */\n\tdouble reduce(double init, DoubleObjToDoubleFunction<? super E> accumulator);\n\n\t/**\n\t * Primitive specialisation of {@code reduce} for values of type {@code int}.\n\t *\n\t * @see FunctionalIterator#reduce(Object, BiFunction)\n\t */\n\tint reduce(int init, IntObjToIntFunction<? super E> accumulator);\n\n\t/**\n\t * Primitive specialisation of {@code reduce} for values of type {@code long}.\n\t *\n\t * @see FunctionalIterator#reduce(Object, BiFunction)\n\t */\n\tlong reduce(long init, LongObjToLongFunction<? super E> accumulator);\n}\n"
  },
  {
    "path": "prism/src/common/iterable/SingletonIterable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\n/**\n * Abstract base class for Iterables ranging over a single element.\n *\n * @param <E> type of the Iterable's elements\n */\npublic abstract class SingletonIterable<E> implements FunctionalIterable<E>\n{\n\t@Override\n\tpublic long count()\n\t{\n\t\treturn 1;\n\t}\n\n\t@Override\n\tpublic boolean isEmpty()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic SingletonIterable<E> dedupe()\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic SingletonIterable<E> distinct()\n\t{\n\t\treturn this;\n\t}\n\n\n\n\t/**\n\t * Generic implementation of an singleton Iterable.\n\t *\n\t * @param <E> type of the Iterables's elements\n\t */\n\tpublic static class Of<E> extends SingletonIterable<E>\n\t{\n\t\t/** The single element */\n\t\tprotected final E element;\n\n\t\t/**\n\t\t * Constructor for an Iterable ranging over a single element.\n\t\t *\n\t\t * @param element the single element of the Iterable\n\t\t */\n\t\tpublic Of(E theElement)\n\t\t{\n\t\t\telement = theElement;\n\t\t}\n\n\t\t@Override\n\t\tpublic FunctionalIterator<E> iterator()\n\t\t{\n\t\t\treturn new SingletonIterator.Of<>(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(Object o)\n\t\t{\n\t\t\treturn element == null ? o == null : element.equals(o);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of an singleoton Iterable.\n\t */\n\tpublic static class OfDouble extends SingletonIterable<Double> implements FunctionalPrimitiveIterable.OfDouble\n\t{\n\t\t/** The single element */\n\t\tprotected final double element;\n\n\t\t/**\n\t\t * Constructor for an Iterable ranging over a single element.\n\t\t *\n\t\t * @param element the single element of the Iterable\n\t\t */\n\t\tpublic OfDouble(double theElement)\n\t\t{\n\t\t\telement = theElement;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn new SingletonIterator.OfDouble(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterable.OfDouble dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterable.OfDouble distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(double d)\n\t\t{\n\t\t\treturn element == d;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of an singleoton Iterable.\n\t */\n\tpublic static class OfInt extends SingletonIterable<Integer> implements FunctionalPrimitiveIterable.OfInt\n\t{\n\t\t/** The single element */\n\t\tprotected final int element;\n\n\t\t/**\n\t\t * Constructor for an Iterable ranging over a single element.\n\t\t *\n\t\t * @param element the single element of the Iterable\n\t\t */\n\t\tpublic OfInt(int theElement)\n\t\t{\n\t\t\telement = theElement;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfInt iterator()\n\t\t{\n\t\t\treturn new SingletonIterator.OfInt(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterable.OfInt dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterable.OfInt distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(int i)\n\t\t{\n\t\t\treturn element == i;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of an singleoton Iterable.\n\t */\n\tpublic static class OfLong extends SingletonIterable<Long> implements FunctionalPrimitiveIterable.OfLong\n\t{\n\t\t/** The single element */\n\t\tprotected final long element;\n\n\t\t/**\n\t\t * Constructor for an Iterable ranging over a single element.\n\t\t *\n\t\t * @param element the single element of the Iterable\n\t\t */\n\t\tpublic OfLong(long theElement)\n\t\t{\n\t\t\telement = theElement;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfLong iterator()\n\t\t{\n\t\t\treturn new SingletonIterator.OfLong(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterable.OfLong dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterable.OfLong distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean contains(long l)\n\t\t{\n\t\t\treturn element == l;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/common/iterable/SingletonIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage common.iterable;\n\nimport java.util.OptionalDouble;\nimport java.util.OptionalInt;\nimport java.util.OptionalLong;\n\n/**\n * Abstract base class for Iterators ranging over a single element.\n *\n * @param <E> type of the Iterator's elements\n */\npublic abstract class SingletonIterator<E> implements FunctionalIterator<E>\n{\n\tprotected boolean hasNext = true;\n\n\t@Override\n\tpublic SingletonIterator<E> dedupe()\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic SingletonIterator<E> distinct()\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic boolean hasNext()\n\t{\n\t\treturn hasNext;\n\t}\n\n\t@Override\n\tpublic void release()\n\t{\n\t\thasNext = false;\n\t}\n\n\n\t/**\n\t * Generic implementation of an singleton Iterator.\n\t *\n\t * @param <E> type of the Iterator's elements\n\t */\n\tpublic static class Of<E> extends SingletonIterator<E>\n\t{\n\t\t/** The single element */\n\t\tprotected E element;\n\n\t\t/**\n\t\t * Constructor for an Iterator ranging over a single element.\n\t\t *\n\t\t * @param element the single element of the Iterator\n\t\t */\n\t\tpublic Of(E element)\n\t\t{\n\t\t\tthis.element = element;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\trequireNext();\n\t\t\tE next = element;\n\t\t\trelease();\n\t\t\treturn next;\n\t\t}\n\n\t\t@Override\n\t\tpublic void release()\n\t\t{\n\t\t\tsuper.release();\n\t\t\telement = null;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code double} of an singleoton Iterator.\n\t */\n\tpublic static class OfDouble extends SingletonIterator<Double> implements FunctionalPrimitiveIterator.OfDouble\n\t{\n\t\t/** The single element */\n\t\tprotected final double element;\n\n\t\t/**\n\t\t * Constructor for an Iterator ranging over a single element.\n\t\t *\n\t\t * @param element the single element of the Iterator\n\t\t */\n\t\tpublic OfDouble(double element)\n\t\t{\n\t\t\tthis.element = element;\n\t\t}\n\n\t\t@Override\n\t\tpublic double nextDouble()\n\t\t{\n\t\t\trequireNext();\n\t\t\trelease();\n\t\t\treturn element;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfDouble dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfDouble distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalDouble max()\n\t\t{\n\t\t\tif (hasNext) {\n\t\t\t\trelease();\n\t\t\t\treturn OptionalDouble.of(element);\n\t\t\t}\n\t\t\treturn OptionalDouble.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalDouble min()\n\t\t{\n\t\t\treturn max();\n\t\t}\n\n\t\t@Override\n\t\tpublic double sum()\n\t\t{\n\t\t\treturn hasNext ? element : 0.0;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code int} of an singleoton Iterator.\n\t */\n\tpublic static class OfInt extends SingletonIterator<Integer> implements FunctionalPrimitiveIterator.OfInt\n\t{\n\t\t/** The single element */\n\t\tprotected final int element;\n\n\t\t/**\n\t\t * Constructor for an Iterator ranging over a single element.\n\t\t *\n\t\t * @param element the single element of the Iterator\n\t\t */\n\t\tpublic OfInt(int element)\n\t\t{\n\t\t\tthis.element = element;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\trequireNext();\n\t\t\trelease();\n\t\t\treturn element;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfInt dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfInt distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt max()\n\t\t{\n\t\t\tif (hasNext) {\n\t\t\t\trelease();\n\t\t\t\treturn OptionalInt.of(element);\n\t\t\t}\n\t\t\treturn OptionalInt.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalInt min()\n\t\t{\n\t\t\treturn max();\n\t\t}\n\n\t\t@Override\n\t\tpublic long sum()\n\t\t{\n\t\t\treturn hasNext ? element : 0L;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Primitive specialisation for {@code long} of an singleoton Iterator.\n\t */\n\tpublic static class OfLong extends SingletonIterator<Long> implements FunctionalPrimitiveIterator.OfLong\n\t{\n\t\t/** The single element */\n\t\tprotected final long element;\n\n\t\t/**\n\t\t * Constructor for an Iterator ranging over a single element.\n\t\t *\n\t\t * @param element the single element of the Iterator\n\t\t */\n\t\tpublic OfLong(long element)\n\t\t{\n\t\t\tthis.element = element;\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\trequireNext();\n\t\t\trelease();\n\t\t\treturn element;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfLong dedupe()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic SingletonIterator.OfLong distinct()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalLong max()\n\t\t{\n\t\t\tif (hasNext) {\n\t\t\t\trelease();\n\t\t\t\treturn OptionalLong.of(element);\n\t\t\t}\n\t\t\treturn OptionalLong.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic OptionalLong min()\n\t\t{\n\t\t\treturn max();\n\t\t}\n\n\t\t@Override\n\t\tpublic long sum()\n\t\t{\n\t\t\treturn hasNext ? element : 0L;\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/csv/BasicReader.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//\tThe original MIT-licensed code can be found at: https://github.com/merkste/SimpleCsvJava\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage csv;\n\nimport java.io.IOException;\nimport java.io.Reader;\n\nimport csv.ReplacingReader.FromChar;\nimport csv.ReplacingReader.FromPair;\n\n/**\n * Interface to provide simple reader-like access to an input stream\n */\npublic interface BasicReader extends AutoCloseable\n{\n\tpublic static final int CR = (int) '\\r';\n\tpublic static final int LF = (int) '\\n';\n\tpublic static final int EOF = -1;\n\n\t/**\n\t * Wrap a source reader.\n\t *\n\t * @param source the reader\n\t */\n\tpublic static Wrapper wrap(Reader reader)\n\t{\n\t\treturn new Wrapper(reader);\n\t}\n\n\t@Override\n\tpublic abstract void close() throws IOException;\n\n\t/**\n\t * Create a reader that replaces all occurrences of a character with the replacement integer {@link ReplacingReader#REPLACE}.\n\t * \n\t * @param char_1 the character to be replaced\n\t * @return A reader that performs the replacement on the fly\n\t */\n\tdefault ReplacingReader<BasicReader> convert(int char_1)\n\t{\n\t\treturn new FromChar(this, char_1);\n\t}\n\n\t/**\n\t * Create a reader that replaces all occurrences of a pair of characters with the replacement integer {@link ReplacingReader#REPLACE}.\n\t * \n\t * @param char_1 the first character of the pair to be replaced\n\t * @param char_2 the second character of the pair to be replaced\n\t * @return A reader that performs the replacement on the fly\n\t */\n\tdefault ReplacingReader<PeekableReader> convert(int char_1, int char_2) throws IOException\n\t{\n\t\treturn new FromPair(this, char_1, char_2);\n\t}\n\n\t/**\n\t * Convert the line endings {@link #CR};{@link #LF} (\\r\\n) and {@link #CR} (\\r) to {@link #LF} (\\n).\n\t *\n\t * @return A reader that performs the normalization on the fly\n\t * @throws IOException\n\t */\n\tdefault ReplacingReader.ToChar normalizeLineEndings() throws IOException\n\t{\n\t\treturn normalizLineEndings(LF);\n\t}\n\n\t/**\n\t * Convert the line endings {@link #CR};{@link #LF} (\\r\\n) and {@link #CR} (\\r) and LF (\\n) to the provided character {@code eol} .\n\t *\n\t * @param eol the character to be used for line endings\n\t * @return A reader that performs the normalization on the fly\n\t * @throws IOException\n\t */\n\tdefault ReplacingReader.ToChar normalizLineEndings(int eol) throws IOException\n\t{\n\t\treturn convert(CR, LF).convert(CR).to(eol);\n\t}\n\n\t/**\n\t * Convert the line endings {@link #CR};{@link #LF} (\\r\\n) and {@link #CR} (\\r) and LF (\\n) to provided characters {@code eol_1};{@code eol_2} .\n\t *\n\t * @param eol_1 the first character to be used for line endings\n\t * @param eol_2 the second character to be used for line endings\n\t * @return A reader that performs the normalization on the fly\n\t * @throws IOException\n\t */\n\tdefault ReplacingReader.ToPair normalizLineEndings(int eol_1, int eol_2) throws IOException\n\t{\n\t\treturn convert(CR, LF).convert(CR).to(eol_1, eol_2);\n\t}\n\n\t/**\n\t * Read a single character from the input.\n\t * \n\t * @return The next character as an integer in the range of 0 to 65536 or {@link #EOF} ({@value #EOF})\n\t * @throws IOException If and I/O error occurs\n\t */\n\tint read() throws IOException;\n\n\t/**\n\t * Create a reader that can be peeked for the next character.\n\t * \n\t * @return A peekable reader\n\t * @throws IOException If an I/O error occurs\n\t */\n\tdefault PeekableReader peekable() throws IOException\n\t{\n\t\tif (this instanceof PeekableReader) {\n\t\t\treturn (PeekableReader) this;\n\t\t}\n\t\treturn new PeekableReader(this);\n\t}\n\n\n\n\t/**\n\t * Wrapper to adapt a {@link Reader} to the interface of {@link BasicReader}.\n\t */\n\tpublic static class Wrapper implements BasicReader\n\t{\n\t\tprotected final Reader source;\n\n\t\t/**\n\t\t * Wrap a source reader.\n\t\t * \n\t\t * @param source the reader\n\t\t */\n\t\tpublic Wrapper(Reader source)\n\t\t{\n\t\t\tthis.source = source;\n\t\t}\n\n\t\t@Override\n\t\tpublic void close() throws IOException\n\t\t{\n\t\t\tsource.close();\n\t\t}\n\n\t\t@Override\n\t\tpublic int read() throws IOException\n\t\t{\n\t\t\treturn source.read();\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Wrapper to enable peeking the next character without advancing the underlying reader.\n\t */\n\tpublic static class PeekableReader implements BasicReader\n\t{\n\t\tprotected final BasicReader source;\n\t\tprotected int next;\n\n\t\t/**\n\t\t * Wrap a source reader.\n\t\t * \n\t\t * @param source the reader\n\t\t */\n\t\tpublic PeekableReader(Reader source) throws IOException\n\t\t{\n\t\t\tthis.source = new BasicReader.Wrapper(source);\n\t\t\tthis.next = source.read();\n\t\t}\n\n\t\t/**\n\t\t * Wrap a source reader.\n\t\t * \n\t\t * @param source the reader to be wrapped\n\t\t */\n\t\tpublic PeekableReader(BasicReader source) throws IOException\n\t\t{\n\t\t\tthis.source = source;\n\t\t\tthis.next = source.read();\n\t\t}\n\n\t\t@Override\n\t\tpublic void close() throws IOException\n\t\t{\n\t\t\tsource.close();\n\t\t}\n\n\t\t@Override\n\t\tpublic int read() throws IOException\n\t\t{\n\t\t\tint current = next;\n\t\t\tnext = source.read();\n\t\t\treturn current;\n\t\t}\n\n\t\t/**\n\t\t * Peek the next character without advancing the underlying reader.\n\t\t * \n\t\t * @return The next character as an integer in the range of 0 to 65536 or {@code EOF} (-1)\n\t\t */\n\t\tpublic int peek()\n\t\t{\n\t\t\treturn next;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/csv/CsvFormatException.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//\tThe original MIT-licensed code can be found at: https://github.com/merkste/SimpleCsvJava\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage csv;\n\n/**\n * Class to signal syntax errors in CSV files. \n */\npublic class CsvFormatException extends Exception\n{\n\tprivate static final long serialVersionUID = -445612337957123597L;\n\n\tprivate final int line;\n\tprivate final int column;\n\n\t/**\n\t * Create an exception with a line number.\n\t * \n\t * @param message the description of the error\n\t * @param line the line number of the error\n\t */\n\tpublic CsvFormatException(String message, int line)\n\t{\n\t\tthis(message, line, 0);\n\t}\n\n\t/**\n\t * Create an exception with a line number and a column number.\n\t * \n\t * @param message the description of the error\n\t * @param line the line number of the error\n\t * @param column the column number of the error\n\t */\n\tpublic CsvFormatException(String message, int line, int column)\n\t{\n\t\tsuper(message + inputPosition(line, column));\n\t\tthis.line = line;\n\t\tthis.column = column;\n\t}\n\n\t/**\n\t * Get the line number of the error.\n\t * \n\t * @return The line number of the error or {@code null}\n\t */\n\tpublic int getLine()\n\t{\n\t\treturn line;\n\t}\n\n\t/**\n\t * Get the line number of the error.\n\t * \n\t * @return The column number of the error or {@code null}\n\t */\n\tpublic int getColumn()\n\t{\n\t\treturn column;\n\t}\n\n\t/**\n\t * Print a string describing the position of the error.\n\t * \n\t * @param line the line number of the error\n\t * @param column the column number of the error\n\t * @return The position the error if {@code line > 0}.\n\t */\n\tprotected static String inputPosition(int line, int column)\n\t{\n\t\tString position = \"\";\n\t\tif (line > 0) {\n\t\t\tposition += \" (input line: \" + line;\n\t\t\tif (column > 0) {\n\t\t\t\tposition += \", column: \" + column + \")\";\n\t\t\t}\n\t\t\tposition += \")\";\n\t\t}\n\t\treturn position;\n\t}\n}\n"
  },
  {
    "path": "prism/src/csv/CsvReader.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//\tThe original MIT-licensed code can be found at: https://github.com/merkste/SimpleCsvJava\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage csv;\n\nimport java.io.IOException;\nimport java.io.StringReader;\nimport java.util.*;\n\nimport csv.BasicReader.PeekableReader;\n\nimport static csv.BasicReader.CR;\nimport static csv.BasicReader.LF;\nimport static csv.BasicReader.EOF;\n\n/**\n * A class that implements a simple CSV reader according to RFC 4180.\n * The field separator can be configured to another character than a comma.\n * The line endings can be configured to either {@link BasicReader#CR} ({@value BasicReader#CR}), {@link BasicReader#LF} ({@value BasicReader#LF})  or {@link #CR_LF} ({@value #CR_LF}) using the provided constants.\n * \n * @see <a href=\"https://tools.ietf.org/html/rfc4180\">RFC 4180</a>\n */\npublic class CsvReader implements AutoCloseable, Iterable<String[]>\n{\n\tpublic static final int CR_LF = ReplacingReader.REPLACE;\n\tpublic static final int EOL = ReplacingReader.REPLACE;\n\tpublic static final int COMMA = (int) ',';\n\tpublic static final char DOUBLE_QUOTES = (int) '\"';\n\tpublic static final String[] STRING_ARRAY = new String[0];\n\n\tprotected final PeekableReader input;\n\tprotected final String lineSeparator;\n\tprotected final int fieldSeparator;\n\tprotected final String[] header;\n\tprotected boolean hasNextRecord = true;\n\tprotected int numFields;\n\tprotected int line = 1;\n\tprotected int column = 0;\n\n\t/**\n\t * Create a CSV reader on an input.\n\t * Assume the file starts with a header of distinct fields and all records have the same number of fields.\n\t * Use a comma as field separator and CR;LF as line ending.\n\t *\n\t * @param reader the underlying reader\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException        If an I/O error occurs\n\t */\n\tpublic CsvReader(BasicReader reader) throws CsvFormatException, IOException\n\t{\n\t\tthis(reader, true, true, true, COMMA, CR_LF);\n\t}\n\n\t/**\n\t * Create a CSV reader on an input.\n\t * Assume the file starts with a header of distinct fields and all records have the same number of fields.\n\t *\n\t * @param reader         the underlying reader\n\t * @param fieldSeparator the field separator, e.g., a comma or semicolon\n\t * @param lineSeparator  the line ending, i.e., either {@link BasicReader#CR} ({@value BasicReader#CR}), {@link BasicReader#LF} ({@value BasicReader#LF})  or {@link #CR_LF} ({@value #CR_LF})\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException        If an I/O error occurs\n\t */\n\tpublic CsvReader(BasicReader reader, int fieldSeparator, int lineSeparator) throws CsvFormatException, IOException\n\t{\n\t\tthis(reader, true, true, true, fieldSeparator, lineSeparator);\n\t}\n\n\t/**\n\t * Create a CSV reader on an input.\n\t * Use a comma as field separator and CR;LF as line ending.\n\t *\n\t * @param reader             the underlying reader\n\t * @param hasHeader          treat the first line as header\n\t * @param fixNumFields       ensure all records have the same number of fields\n\t * @param distinctFieldNames check that the header fields are distinct\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException        If an I/O error occurs\n\t */\n\tpublic CsvReader(BasicReader reader, boolean hasHeader, boolean fixNumFields, boolean distinctFieldNames) throws CsvFormatException, IOException\n\t{\n\t\tthis(reader, hasHeader, fixNumFields, distinctFieldNames, COMMA, CR_LF);\n\t}\n\n\t/**\n\t * Create a CSV reader on an input.\n\t *\n\t * @param reader             the underlying reader\n\t * @param hasHeader          treat the first line as header\n\t * @param fixNumFields       ensure all records have the same number of fields\n\t * @param distinctFieldNames check that the header fields are distinct\n\t * @param fieldSeparator     the field separator, e.g., a comma or semicolon\n\t * @param lineSeparator      the line ending, i.e., either {@link BasicReader#CR} ({@value BasicReader#CR}), {@link BasicReader#LF} ({@value BasicReader#LF})  or {@link #CR_LF} ({@value #CR_LF})\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException        If an I/O error occurs\n\t */\n\tpublic CsvReader(BasicReader reader, boolean hasHeader, boolean fixNumFields, boolean distinctFieldNames, int fieldSeparator, int lineSeparator) throws CsvFormatException, IOException\n\t{\n\t\tthis.fieldSeparator = fieldSeparator;\n\t\tswitch (lineSeparator) {\n\t\t\tcase CR:\n\t\t\t\tthis.lineSeparator = \"\\r\";\n\t\t\t\tthis.input = reader.convert(CR).to(EOL).peekable();\n\t\t\t\tbreak;\n\t\t\tcase LF:\n\t\t\t\tthis.lineSeparator = \"\\n\";\n\t\t\t\tthis.input = reader.convert(LF).to(EOL).peekable();\n\t\t\t\tbreak;\n\t\t\tcase CR_LF:\n\t\t\t\tthis.lineSeparator = \"\\r\\n\";\n\t\t\t\tthis.input = reader.convert(CR, LF).to(EOL).peekable();\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new IllegalArgumentException(\"Expected lineSeparator to be either CR (\" + CR + \"), LF (\" + LF + \") or CR_LF\" + (CR_LF) + \") but got: \" + lineSeparator);\n\t\t}\n\t\tthis.line = 1;\n\t\tthis.column = 0;\n\t\tthis.numFields = fixNumFields ? 0 : -1;\n\t\tif (hasHeader) {\n\t\t\theader = nextRecord();\n\t\t\tif (!hasNextRecord()) {\n\t\t\t\tthrow new CsvFormatException(\"no record found except for header\", line);\n\t\t\t}\n\t\t\tif (distinctFieldNames) {\n\t\t\t\tSet<String> fieldNames = new HashSet<String>();\n\t\t\t\tCollections.addAll(fieldNames, header);\n\t\t\t\tif (fieldNames.size() != header.length) {\n\t\t\t\t\tthrow new CsvFormatException(\"duplicated field names: \" + Arrays.toString(header), 1);\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\theader = null;\n\t\t}\n\t}\n\n\t@Override\n\tpublic void close() throws IOException\n\t{\n\t\tinput.close();\n\t}\n\n\t/**\n\t * Get the header if present.\n\t *\n\t * @return The header or {@code null} if no header was expected\n\t */\n\tpublic String[] getHeader()\n\t{\n\t\treturn header;\n\t}\n\n\t/**\n\t * Get the number of fields in each record.\n\t *\n\t * @return The number of fields or {@code -1} if the number is not fixed or {@code 0} if the number is not known yet\n\t */\n\tpublic int getNumberOfFields()\n\t{\n\t\treturn numFields;\n\t}\n\n\t/**\n\t * Get the line number of the last read character for error reporting.\n\t * {@code EOL} is read if {@code column==0}.\n\t *\n\t * @return The current line number as an integer > 0\n\t */\n\tpublic int getLine()\n\t{\n\t\treturn line;\n\t}\n\n\t/**\n\t * Get the current column number of the last character read  for error reporting.\n\t * {@code EOL} is read if {@code column==0}.\n\t *\n\t * @return The current line number as an integer >= 0\n\t */\n\tpublic int getColumn ()\n\t{\n\t\treturn column;\n\t}\n\n\n\t/**\n\t * Read a single character from the input and update the counters {@code line} and {@code column}.\n\t *\n\t * @return The next character as an integer in the range of 0 to 65536 or {@link BasicReader#EOF} ({@value BasicReader#EOF})\n\t * @throws IOException If and I/O error occurs\n\t */\n\tprotected int read() throws IOException\n\t{\n\t\tint current = input.read();\n\t\tif (current == EOL) {\n\t\t\tline += 1;\n\t\t\tcolumn = 0;\n\t\t} else {\n\t\t\tcolumn += 1;\n\t\t}\n\t\treturn current;\n\t}\n\n\t/**\n\t * Answer whether the CSV file has another record.\n\t *\n\t * @return {@code true} if the file has another record\n\t */\n\tpublic boolean hasNextRecord()\n\t{\n\t\treturn hasNextRecord;\n\t}\n\n\t/**\n\t * Get the next record.\n\t *\n\t * @return The next record as an array of strings, possibly empty\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException        If an I/O error occurs\n\t */\n\tpublic String[] nextRecord() throws CsvFormatException, IOException\n\t{\n\t\tif (!hasNextRecord()) {\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\t\tString[] nextRecord = readRecord();\n\t\tif (peek() == EOL) {\n\t\t\tread();\n\t\t}\n\t\tif (peek() == EOF) {\n\t\t\thasNextRecord = false;\n\t\t}\n\t\tif (numFields > 0 && nextRecord.length != numFields) {\n\t\t\tthrow new CsvFormatException(\"records contain different numbers of fields\", line);\n\t\t} else if (numFields == 0) {\n\t\t\tnumFields = nextRecord.length;\n\t\t}\n\t\treturn nextRecord;\n\t}\n\n\t/**\n\t * Returns an iterator over the records.\n\t * Calling {@link Iterator#next} may throw an {@link IOException} or a {@link CsvFormatException} as unchecked exception.\n\t *\n\t * @return The iterator over the records\n\t * @see #nextRecord()\n\t */\n\t@Override\n\tpublic Iterator<String[]> iterator()\n\t{\n\t\treturn new Iterator<String[]>()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn hasNextRecord();\n\t\t\t}\n\n\t\t\t/**\n\t\t\t * Returns the next record in the iteration.\n\t\t\t *\n\t\t\t * @return The next record in the iteration\n\t\t\t * @throws CsvFormatException If a CSV syntax error occurs\n\t\t\t * @throws IOException        If an I/O error occurs\n\t\t\t */\n\t\t\t@Override\n\t\t\tpublic String[] next()\n\t\t\t{\n\t\t\t\ttry {\n\t\t\t\t\treturn nextRecord();\n\t\t\t\t} catch (Exception e) {\n\t\t\t\t\tthrow throwUnchecked(e);\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Read a record from the input.\n\t * \n\t * @return The record as an array of strings, possibly empty\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException If an I/O error occurs\n\t */\n\tprotected String[] readRecord() throws CsvFormatException, IOException\n\t{\n\t\tList<String> record = new ArrayList<>();\n\t\tint next;\n\t\tdo {\n\t\t\tString field = readField();\n\t\t\trecord.add(field);\n\t\t\tnext = peek();\n\t\t\tif (next == fieldSeparator) {\n\t\t\t\tread();\n\t\t\t}\n\t\t} while (! isEndOfRecord(next));\n\t\treturn record.toArray(STRING_ARRAY);\n\t}\n\n\t/**\n\t * Peek the next character without advancing the underlying reader.\n\t *\n\t * @return The next character as an integer in the range of 0 to 65536 or {@link BasicReader#EOF} ({@value BasicReader#EOF})\n\t */\n\tprotected int peek()\n\t{\n\t\treturn input.peek();\n\t}\n\n\t/**\n\t * Read a field from the input.\n\t * \n\t * @return The field as string, possibly empty\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException If an I/O error occurs\n\t */\n\tprotected String readField() throws CsvFormatException, IOException\n\t{\n\t\tString quoted = readQuotedField();\n\t\tif (quoted == null) {\n\t\t\treturn readPlainField();\n\t\t} else {\n\t\t\treturn quoted;\n\t\t}\n\t}\n\n\t/**\n\t * Read a quoted field from the input and strip the quotes.\n\t * \n\t * @return The field as string, possibly empty\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException If an I/O error occurs\n\t */\n\tprotected String readQuotedField() throws CsvFormatException, IOException\n\t{\n\t\tif (peek() != DOUBLE_QUOTES) {\n\t\t\treturn null;\n\t\t}\n\t\tread(); // Skip opening double quotes\n\t\tStringBuilder field = new StringBuilder();\n\t\twhile (peek() != EOF) {\n\t\t\tint character = read();\n\t\t\tif (character == DOUBLE_QUOTES) {\n\t\t\t\tint next = peek();\n\t\t\t\tif (next == DOUBLE_QUOTES) {\n\t\t\t\t\t// 1. Escaped double quotes\n\t\t\t\t\tread();\n\t\t\t\t} else if (isEndOfField(next)) {\n\t\t\t\t\t// 2. Closing double quotes\n\t\t\t\t\treturn field.toString();\n\t\t\t\t} else {\n\t\t\t\t\t// 3. Error\n\t\t\t\t\tthrow new CsvFormatException(\"double quotes (\\\") in quoted field not escaped (\\\"\\\")\", line, column);\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (character == EOL) {\n\t\t\t\tfield.append(lineSeparator);\n\t\t\t} else {\n\t\t\t\tfield.append((char) character);\n\t\t\t}\n\t\t}\n\t\tthrow new CsvFormatException(\"double quotes (\\\") missing to close quoted field\", line, column);\n\t}\n\n\t/**\n\t * Read a non-quoted field from the input.\n\t * \n\t * @return The field as string, possibly empty\n\t * @throws CsvFormatException If a CSV syntax error occurs\n\t * @throws IOException If an I/O error occurs\n\t */\n\tprotected String readPlainField() throws CsvFormatException, IOException\n\t{\n\t\tStringBuilder field = new StringBuilder();\n\t\twhile (! isEndOfField(peek())) {\n\t\t\tint character = read();\n\t\t\tif (character == DOUBLE_QUOTES) {\n\t\t\t\tthrow new CsvFormatException(\"double quotes (\\\") found in non-quoted field\", line, column);\n\t\t\t}\n\t\t\tfield.append((char) character);\n\t\t}\n\t\treturn field.toString();\n\t}\n\n\t/**\n\t * Check whether a character is the end of a field.\n\t * \n\t * @param character the character to check\n\t * @return {@code true} if the character is the end of a field\n\t */\n\tprotected boolean isEndOfField(int character)\n\t{\n\t\treturn character == fieldSeparator || isEndOfRecord(character);\n\t}\n\n\t/**\n\t * Check whether a character is the end of a record.\n\t * \n\t * @param character the character to check\n\t * @return {@code true} if the character is the end of a record\n\t */\n\tprotected boolean isEndOfRecord(int character)\n\t{\n\t\treturn character == EOL || character == EOF;\n\t}\n\n\t/**\n\t * Print a record with quoted fields.\n\t *\n\t * @param record the record to be printed\n\t * @return A string representation of the records with quoted fields.\n\t */\n\tpublic static String printRecord(String[] record)\n\t{\n\t\tString[] quoted = new String[record.length];\n\t\tfor (int i=record.length-1; i>=0; i--) {\n\t\t\tquoted[i] = \"\\\"\" + record[i].replaceAll(\"\\\\\\\"\", \"\\\\\\\\\\\"\") + \"\\\"\";\n\t\t}\n\t\treturn Arrays.toString(quoted);\n\t}\n\n\n\t/**\n\t * Cast a CheckedException as an unchecked one.\n\t *\n\t * @param throwable to cast\n\t * @param <T>       the type of the Throwable\n\t * @return this method will never return a Throwable instance, it will just throw it.\n\t * @throws T the throwable as an unchecked throwable\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected static <T extends Throwable> RuntimeException throwUnchecked(Throwable throwable) throws T\n\t{\n\t\tthrow (T) throwable; // rely on vacuous cast\n\t}\n\n\t/**\n\t * Simple test to show how to use the CSV reader.\n\t */\n\tpublic static void main(String[] args) throws CsvFormatException, IOException\n\t{\n\t\tString emptyCsv = \"\";\n\t\tSystem.out.println(\"CSV with single empty line:\\n---\");\n\t\tSystem.out.println(emptyCsv);\n\t\tSystem.out.println(\"---\\nRecords:\");\n\t\ttry (BasicReader reader = BasicReader.wrap(new StringReader(emptyCsv)).normalizeLineEndings();\n\t\t\t\tCsvReader emptyRecords = new CsvReader(reader, false, true, true, COMMA, LF)) {\n\t\t\tint i = 1;\n\t\t\twhile (emptyRecords.hasNextRecord()) {\n\t\t\t\tSystem.out.println((i++) + \": \" + printRecord(emptyRecords.nextRecord()));\n\t\t\t}\n\t\t}\n\n\t\tString mixedCsv = \"h1;h2;h3\\r\"\n\t\t\t\t+ \"plain;\\\"quoted\\\";\\\"quotes\\\"\\\"\\\";\\\"\\\"\\n\"\n\t\t\t\t+ \";1;2;3;4\\n\"\n\t\t\t\t+ \"\\r\\n\"\n\t\t\t\t+ \";;\\n\";\n\t\tSystem.out.println();\n\t\tSystem.out.println(\"CSV with mixed and quoted records:\\n---\");\n\t\tSystem.out.println(mixedCsv);\n\t\tSystem.out.println(\"---\\nRecords:\");\n\t\ttry (BasicReader reader = BasicReader.wrap(new StringReader(mixedCsv)).normalizeLineEndings();\n\t\t\t\tCsvReader mixedRecords = new CsvReader(reader, true, false, true, ';', LF)) {\n\t\t\tSystem.out.println(\"H: \" + Arrays.toString(mixedRecords.getHeader()));\n\t\t\tint j = 1;\n\t\t\twhile (mixedRecords.hasNextRecord()) {\n\t\t\t\tSystem.out.println((j++) + \": \" + printRecord(mixedRecords.nextRecord()));\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/csv/ReplacingReader.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//\tThe original MIT-licensed code can be found at: https://github.com/merkste/SimpleCsvJava\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage csv;\n\nimport java.io.IOException;\n\n/**\n * Abstract base class for readers that convert single chars or pairs of chars.\n * \n * @param <T> the type of the underlying reader\n */\npublic abstract class ReplacingReader<T extends BasicReader> implements BasicReader\n{\n\tpublic static final int REPLACE = -2;\n\n\tpublic final T source;\n\n\t/**\n\t * Create a converting reader on a source reader.\n\t * \n\t * @param source the source reader\n\t */\n\tpublic ReplacingReader(T source)\n\t{\n\t\tthis.source = source;\n\t}\n\n\t@Override\n\tpublic void close() throws IOException\n\t{\n\t\tsource.close();\n\t}\n\n\t@Override\n\tpublic abstract int read() throws IOException;\n\n\t/**\n\t * Replace each occurrence of the replacement integer {@link #REPLACE} with a single character.\n\t * \n\t * @param char_1 the character used as replacement\n\t * @return A reader that performs the replacement on the fly\n\t */\n\tpublic ToChar to(int char_1)\n\t{\n\t\treturn new ToChar(this, char_1);\n\t}\n\n\t/**\n\t * Replace each occurrence of the replacement integer {@link #REPLACE} with a pair of characters.\n\t * \n\t * @param char_1 the first character of the pair used as replacement\n\t * @param char_2 the second character of the pair used as replacement\n\t * @return A reader that performs the replacement on the fly\n\t */\n\tpublic ToPair to(int char_1, int char_2)\n\t{\n\t\treturn new ToPair(this, char_1, char_2);\n\t}\n\n\n\n\t/**\n\t * A reader that replaces all occurrences of a character with the replacement integer {@link ReplacingReader#REPLACE}.\n\t */\n\tpublic static class FromChar extends ReplacingReader<BasicReader>\n\t{\n\t\tprotected final int char_1;\n\n\t\t/**\n\t\t * Wrap a source reader to perform the replacement.\n\t\t * \n\t\t * @param source the source reader\n\t\t * @param char_1 the character to be replaced\n\t\t */\n\t\tpublic FromChar(BasicReader source, int char_1)\n\t\t{\n\t\t\tsuper(source);\n\t\t\tthis.char_1 = char_1;\n\t\t}\n\n\t\t/**\n\t\t * Read a single character from the input.\n\t\t * \n\t\t * @return The next character as an integer in the range of 0 to 65536, {@link BasicReader#EOF} ({@value BasicReader#EOF}) or {@link #REPLACE} ({@value #REPLACE})\n\t\t * @throws IOException If and I/O error occurs\n\t\t */\n\t\t@Override\n\t\tpublic int read() throws IOException\n\t\t{\n\t\t\tint current = source.read();\n\t\t\treturn current == char_1 ? REPLACE : current;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * A reader that replaces all occurrences of a pair of characters with the replacement integer {@link ReplacingReader#REPLACE}.\n\t */\n\tpublic static class FromPair extends ReplacingReader<PeekableReader>\n\t{\n\t\tprotected final int char_1;\n\t\tprotected final int char_2;\n\n\t\t/**\n\t\t * Wrap a source reader to perform the replacement.\n\t\t * \n\t\t * @param source the source reader\n\t\t * @param char_1 the first character to be replaced\n\t\t * @param char_2 the second character to be replaced\n\t\t */\n\t\tpublic FromPair(BasicReader source, int char_1, int char_2) throws IOException\n\t\t{\n\t\t\tthis(new PeekableReader(source), char_1, char_2);\n\t\t}\n\n\t\t/**\n\t\t * Wrap a source reader to perform the replacement.\n\t\t * \n\t\t * @param source the source reader\n\t\t * @param char_1 the first character to be replaced\n\t\t * @param char_2 the second character to be replaced\n\t\t */\n\t\tpublic FromPair(PeekableReader source, int char_1, int char_2)\n\t\t{\n\t\t\tsuper(source);\n\t\t\tthis.char_1 = char_1;\n\t\t\tthis.char_2 = char_2;\n\t\t}\n\n\t\t/**\n\t\t * Read a single character from the input.\n\t\t * \n\t\t * @return The next character as an integer in the range of 0 to 65536, {@link BasicReader#EOF} ({@value BasicReader#EOF}) or {@link #REPLACE} ({@value #REPLACE})\n\t\t * @throws IOException If and I/O error occurs\n\t\t */\n\t\t@Override\n\t\tpublic int read() throws IOException\n\t\t{\n\t\t\tint current = source.read();\n\t\t\tif (current == char_1 && source.peek() == char_2) {\n\t\t\t\tsource.read();\n\t\t\t\treturn REPLACE;\n\t\t\t}\n\t\t\treturn current;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * A reader that replaces all occurrences the replacement integer {@link ReplacingReader#REPLACE} with a pair of characters.\n\t */\n\tpublic static class ToChar extends ReplacingReader<ReplacingReader<?>>\n\t{\n\t\tprotected final int repl_1;\n\n\t\t/**\n\t\t * Wrap a source reader to perform the replacement.\n\t\t * \n\t\t * @param source the source reader\n\t\t * @param char_1 the character used as replacement\n\t\t */\n\t\tpublic ToChar(ReplacingReader<?> source, int repl_1)\n\t\t{\n\t\t\tsuper(source);\n\t\t\tthis.repl_1 = repl_1;\n\t\t}\n\n\t\t@Override\n\t\tpublic int read() throws IOException\n\t\t{\n\t\t\tint current = source.read();\n\t\t\treturn current == REPLACE ? repl_1 : current; \n\t\t}\n\t}\n\n\n\n\t/**\n\t * A reader that replaces all occurrences the replacement integer {@link ReplacingReader#REPLACE} with a pair of characters.\n\t */\n\tpublic static class ToPair extends ReplacingReader<ReplacingReader<?>>\n\t{\n\t\tprotected final int repl_1;\n\t\tprotected final int repl_2;\n\t\tprotected boolean replacing = false;\n\n\t\t/**\n\t\t * Wrap a source reader to perform the replacement.\n\t\t * \n\t\t * @param source the source reader\n\t\t * @param char_1 the first character of the pair used as replacement\n\t\t * @param char_2 the second character of the pair used as replacement\n\t\t */\n\t\tpublic ToPair(ReplacingReader<?> source, int repl_1, int repl_2)\n\t\t{\n\t\t\tsuper(source);\n\t\t\tthis.repl_1 = repl_1;\n\t\t\tthis.repl_2 = repl_2;\n\t\t}\n\n\t\t@Override\n\t\tpublic int read() throws IOException\n\t\t{\n\t\t\tif (replacing) {\n\t\t\t\treplacing = false;\n\t\t\t\treturn repl_2;\n\t\t\t}\n\t\t\tint current = source.read();\n\t\t\tif (current == REPLACE) {\n\t\t\t\treplacing = true;\n\t\t\t\treturn repl_1;\n\t\t\t}\n\t\t\treturn current;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/dd/dd.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: Any stuff global to the dd package\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <cstdio>\n\n// output stream for anything printed by the dd package\n// (stdout by default)\n\nFILE *dd_out = stdout;\n\n//------------------------------------------------------------------------------\n\nvoid DD_SetOutputStream(FILE *fp)\n{\n\tdd_out = fp;\n}\n\n//------------------------------------------------------------------------------\n\nFILE *DD_GetOutputStream()\n{\n\treturn dd_out;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dd/dd_abstr.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: DD abstraction functions\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n#include \"dd_abstr.h\"\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_ThereExists\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars\n)\n{\n\tDdNode *cube, *res;\n\n\tif (dd == NULL) return NULL;\n\n\tcube = Cudd_addComputeCube(ddman, vars, NULL, num_vars);\n\tif (cube == NULL) return NULL;\n\tCudd_Ref(cube);\n\tres = Cudd_addOrAbstract(ddman, dd, cube);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\tCudd_RecursiveDeref(ddman,cube);\n\n\treturn res;\t\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_ForAll\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars\n)\n{\n\tDdNode *cube, *res;\n\n\tif (dd == NULL) return NULL;\n\n\tcube = Cudd_addComputeCube(ddman, vars, NULL, num_vars);\n\tif (cube == NULL) return NULL;\n\tCudd_Ref(cube);\n\tres = Cudd_addUnivAbstract(ddman, dd, cube);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\tCudd_RecursiveDeref(ddman, cube);\n\n\treturn res;\t\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_SumAbstract\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars\n)\n{\n\tDdNode *cube, *res;\n\n\tif (dd == NULL) return NULL;\n\n\tcube = Cudd_addComputeCube(ddman, vars, NULL, num_vars);\n\tif (cube == NULL) return NULL;\n\tCudd_Ref(cube);\n\tres = Cudd_addExistAbstract(ddman, dd, cube);\t\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\tCudd_RecursiveDeref(ddman, cube);\n\n\treturn res;\t\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_ProductAbstract\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars\n)\n{\n\tDdNode *cube, *res;\n\n\tif (dd == NULL) return NULL;\n\n\tcube = Cudd_addComputeCube(ddman, vars, NULL, num_vars);\n\tif (cube == NULL) return NULL;\n\tCudd_Ref(cube);\n\tres = Cudd_addUnivAbstract(ddman, dd, cube);\t\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\tCudd_RecursiveDeref(ddman, cube);\n\n\treturn res;\t\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_MinAbstract\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars\n)\n{\n\tDdNode *cube, *res;\n\n\tif (dd == NULL) return NULL;\n\n\tcube = Cudd_addComputeCube(ddman, vars, NULL, num_vars);\n\tif (cube == NULL) return NULL;\n\tCudd_Ref(cube);\n\tres = Cudd_addMinAbstract(ddman, dd, cube);\t\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\tCudd_RecursiveDeref(ddman, cube);\n\n\treturn res;\t\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_MaxAbstract\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars\n)\n{\n\tDdNode *cube, *res;\n\n\tif (dd == NULL) return NULL;\n\n\tcube = Cudd_addComputeCube(ddman, vars, NULL, num_vars);\n\tif (cube == NULL) return NULL;\n\tCudd_Ref(cube);\n\tres = Cudd_addMaxAbstract(ddman, dd, cube);\t\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\tCudd_RecursiveDeref(ddman, cube);\n\n\treturn res;\t\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dd/dd_basics.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: Basic DD functions\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <cstdio>\n#include <cstdlib>\n#include <util.h>\n#include <cudd.h>\n#include \"dd_basics.h\"\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Create(DdManager *ddman)\n{\n\tDdNode *res;\n\n\tres = Cudd_addConst(ddman, 0);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Constant(DdManager *ddman, double value)\n{\n\tDdNode *res;\n\n\tres = Cudd_addConst(ddman, value);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_PlusInfinity(DdManager *ddman)\n{\n\tDdNode *res;\n\n\tres = Cudd_ReadPlusInfinity(ddman);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_MinusInfinity(DdManager *ddman)\n{\n\tDdNode *res;\n\n\tres = Cudd_ReadMinusInfinity(ddman);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Var(DdManager *ddman, int i)\n{\n\tDdNode *res;\n\n\tres = Cudd_addIthVar(ddman, i);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Not(DdManager *ddman, DdNode *dd)\n{\n\tDdNode *res;\n\n\tif (dd == NULL) return NULL;\n\n\tres = Cudd_addCmpl(ddman, dd);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Or(DdManager *ddman, DdNode *dd1, DdNode *dd2)\n{\n\tDdNode *res;\n\n\tif (dd1 == NULL) return NULL;\n\tif (dd2 == NULL) return NULL;\n\n\tres = Cudd_addApply(ddman, Cudd_addOr, dd1, dd2);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd1);\n\tCudd_RecursiveDeref(ddman, dd2);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_And(DdManager *ddman, DdNode *dd1, DdNode *dd2)\n{\n\tif (dd1 == NULL) return NULL;\n\tif (dd2 == NULL) return NULL;\n\n\treturn DD_Not(ddman, DD_Or(ddman, DD_Not(ddman, dd1), DD_Not(ddman, dd2))); \n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Xor(DdManager *ddman, DdNode *dd1, DdNode *dd2)\n{\n\tDdNode *res;\n\n\tif (dd1 == NULL) return NULL;\n\tif (dd2 == NULL) return NULL;\n\n\tres = Cudd_addApply(ddman, Cudd_addXor, dd1, dd2);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd1);\n\tCudd_RecursiveDeref(ddman, dd2);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Implies(DdManager *ddman, DdNode *dd1, DdNode *dd2)\n{\n\tif (dd1 == NULL) return NULL;\n\tif (dd2 == NULL) return NULL;\n\n\treturn DD_Or(ddman, DD_Not(ddman, dd1), dd2);\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Apply(DdManager *ddman, int op, DdNode *dd1, DdNode *dd2)\n{\n\tDdNode *res;\n\n\tif (dd1 == NULL) return NULL;\n\tif (dd2 == NULL) return NULL;\n\n\tswitch (op) {\n\t\tcase APPLY_PLUS: res = Cudd_addApply(ddman, Cudd_addPlus, dd1, dd2); break;\n\t\tcase APPLY_MINUS: res = Cudd_addApply(ddman, Cudd_addMinus, dd1, dd2); break;\n\t\tcase APPLY_TIMES: res = Cudd_addApply(ddman, Cudd_addTimes, dd1, dd2); break;\n\t\tcase APPLY_DIVIDE: res = Cudd_addApply(ddman, Cudd_addDivide, dd1, dd2); break;\n\t\tcase APPLY_MIN: res = Cudd_addApply(ddman, Cudd_addMinimum, dd1, dd2); break;\n\t\tcase APPLY_MAX: res = Cudd_addApply(ddman, Cudd_addMaximum, dd1, dd2); break;\n\t\tcase APPLY_EQUALS: res = Cudd_addApply(ddman, Cudd_addEquals, dd1, dd2); break;\n\t\tcase APPLY_NOTEQUALS: res = Cudd_addApply(ddman, Cudd_addNotEquals, dd1, dd2); break;\n\t\tcase APPLY_GREATERTHAN: res = Cudd_addApply(ddman, Cudd_addGreaterThan, dd1, dd2); break;\n\t\tcase APPLY_GREATERTHANEQUALS: res = Cudd_addApply(ddman, Cudd_addGreaterThanEquals, dd1, dd2); break;\n\t\tcase APPLY_LESSTHAN: res = Cudd_addApply(ddman, Cudd_addLessThan, dd1, dd2); break;\n\t\tcase APPLY_LESSTHANEQUALS: res = Cudd_addApply(ddman, Cudd_addLessThanEquals, dd1, dd2); break;\n\t\tcase APPLY_POW: res = Cudd_addApply(ddman, Cudd_addPow, dd1, dd2); break;\n\t\tcase APPLY_MOD: res = Cudd_addApply(ddman, Cudd_addMod, dd1, dd2); break;\n\t\tcase APPLY_LOGXY: res = Cudd_addApply(ddman, Cudd_addLogXY, dd1, dd2); break;\n\t\tdefault: printf(\"\\nError: Invalid APPLY operator.\\n\"); exit(1);\n\t}\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd1);\n\tCudd_RecursiveDeref(ddman, dd2);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_MonadicApply(DdManager *ddman, int op, DdNode *dd)\n{\n\tDdNode *res;\n\n\tif (dd == NULL) return NULL;\n\n\tswitch (op) {\n\t\tcase APPLY_FLOOR: res = Cudd_addMonadicApply(ddman, Cudd_addFloor, dd); break;\n\t\tcase APPLY_CEIL: res = Cudd_addMonadicApply(ddman, Cudd_addCeil, dd); break;\n\t\tdefault: printf(\"\\nError: Invalid monadic APPLY operator.\\n\"); exit(1);\n\t}\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Restrict(DdManager *ddman, DdNode *dd, DdNode *cube)\n{\n\tDdNode *res;\n\n\tif (dd == NULL) return NULL;\n\tif (cube == NULL) return NULL;\n\n\tres = Cudd_addRestrict(ddman, dd, cube);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\tCudd_RecursiveDeref(ddman, cube);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_ITE(DdManager *ddman, DdNode *dd1, DdNode *dd2, DdNode *dd3)\n{\n\tDdNode *res;\n\n\tif (dd1 == NULL) return NULL;\n\tif (dd2 == NULL) return NULL;\n\tif (dd3 == NULL) return NULL;\n\n\tres = Cudd_addIte(ddman, dd1, dd2, dd3);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd1);\n\tCudd_RecursiveDeref(ddman, dd2);\n\tCudd_RecursiveDeref(ddman, dd3);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dd/dd_cudd.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: CUDD functions\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"util.h\"\n#include \"cuddInt.h\"\n#include \"dd_cudd.h\"\n\n#include <map>\n#include <set>\n#include <string>\n\nextern FILE *dd_out;\n\n// A flag indicating that a CUDD error has occurred\n// that could not be signalled by returning a NULL DdNode*\n// from a function\nbool dd_cudd_error_flag = false;\n\nstatic int Cudd_CheckZeroRefVerbose(DdManager *ddman);\n\n//-----------------------------------------------------------------------------------\n\nDdManager *DD_InitialiseCUDD()\n{\n\t// choose some ensible defaults\n\t// (cudd max memory = 200 MB)\n\t// (cudd epsilon = 1.0e-15, very close to min precision of doubles, 1.1e-16)\n\t\n\treturn DD_InitialiseCUDD(200*1024, 1.0e-15);\n}\n\n//-----------------------------------------------------------------------------------\n\nDdManager *DD_InitialiseCUDD(long max_mem, double epsilon)\n{\n\tDdManager *ddman;\n\t\n\t// initialise CUDD package\n\tddman = Cudd_Init(0, 0, CUDD_UNIQUE_SLOTS, CUDD_CACHE_SLOTS, max_mem * 1024);\n\tCudd_SetStderr(ddman, stdout);\n\tCudd_SetMaxMemory(ddman, max_mem * 1024);\n\tCudd_SetEpsilon(ddman, epsilon);\n\n\treturn ddman;\n}\n\n//-----------------------------------------------------------------------------------\n\nvoid DD_SetCUDDMaxMem(DdManager *ddman, long max_mem)\n{\n\tCudd_SetMaxMemory(ddman, max_mem * 1024);\n}\n\n//-----------------------------------------------------------------------------------\n\nvoid DD_SetCUDDEpsilon(DdManager *ddman, double epsilon)\n{\n\tCudd_SetEpsilon(ddman, epsilon);\n}\n\n//-----------------------------------------------------------------------------------\n\nvoid DD_PrintCacheInfo(DdManager *ddman)\n{\n\tstatic double old_lookups, old_hits;\n\tdouble slots = Cudd_ReadCacheSlots(ddman);\n\tdouble used_slots = Cudd_ReadCacheUsedSlots(ddman);\n\tdouble lookups = Cudd_ReadCacheLookUps(ddman);\n\tdouble hits = Cudd_ReadCacheHits(ddman);\n\tdouble percent;\n\t\n\tfprintf(dd_out, \"Cache info: %.2f%% of %.0f slots used, \", 100.0*used_slots, slots);\n\tpercent = (lookups <= old_lookups) ? 0 : 100.0*(hits-old_hits)/(lookups-old_lookups);\n\tfprintf(dd_out, \"lookup success: %.0f/%.0f = %.2f%% \", hits-old_hits, lookups-old_lookups, percent);\n\tpercent = (lookups <= 0) ? 0 : 100.0*hits/lookups;\n\tfprintf(dd_out, \"(total %.0f/%.0f = %.2f%%)\\n\", hits, lookups, 100.0*hits/lookups);\n\told_lookups = lookups;\n\told_hits = hits;\n}\n\n//-----------------------------------------------------------------------------------\n\nvoid DD_CloseDownCUDD(DdManager *ddman) { DD_CloseDownCUDD(ddman, true); }\nvoid DD_CloseDownCUDD(DdManager *ddman, bool check)\n{\n//\tfprintf(dd_out, \"Memory in use: %.1fKB\\n\", Cudd_ReadMemoryInUse(ddman)/1024.0);\n//\tfprintf(dd_out, \"Peak number of nodes: %ld\\n\", Cudd_ReadPeakNodeCount(ddman));\n//\tfprintf(dd_out, \"Peak number of live nodes: %d\\n\", Cudd_ReadPeakLiveNodeCount(ddman));\n//\tfprintf(dd_out, \"Number of cache entries: %u\\n\", ddman->cacheSlots);\n//\tfprintf(dd_out, \"Hard limit for cache size: %u\\n\", Cudd_ReadMaxCacheHard(ddman));\n//\tfprintf(dd_out, \"Soft limit for cache size: %u\\n\", Cudd_ReadMaxCache(ddman));\n\n\n\tif (check) {\n\t\t// if required, check everthing is closed down OK and warn if not\n\t\t// for now, we disable the debug check since there are increasingly\n\t\t// problems occurring on 64 bit Linux/Mac\n\t\t/*if (Cudd_DebugCheck(ddman)) {\n\t\t\tprintf(\"\\nWarning: CUDD reports an error on closing.\\n\");\n\t\t}*/\n\t\tif (Cudd_CheckZeroRef(ddman) > 0) {\n\t\t\tfprintf(dd_out, \"\\nWarning: CUDD reports %d non-zero references.\\n\", Cudd_CheckZeroRef(ddman));\n\t\t}\n\t}\n\t\n\t// close down the CUDD package\n\tCudd_Quit(ddman);\n}\n\n//-----------------------------------------------------------------------------------\n\nint Cudd_CheckZeroRefVerbose(DdManager *manager)\n{\n \tint size;\n \tint i, j;\n \tint remain;\n \tDdNode **nodelist;\n \tDdNode *node;\n \tDdNode *sentinel = &(manager->sentinel);\n \tDdSubtable *subtable;\n \tint count = 0;\n \tint index;\n\n\tprintf(\"Checking for non-zero references...\\n\");\n\n \t/* First look at the BDD/ADD subtables. */\n \tremain = 1; /* reference from the manager */\n \tsize = manager->size;\n \tremain += 2 * size;\t/* reference from the BDD projection functions */\n\n \tfor (i = 0; i < size; i++) {\n\tsubtable = &(manager->subtables[i]);\n\tnodelist = subtable->nodelist;\n\tfor (j = 0; (unsigned) j < subtable->slots; j++) {\n\t \tnode = nodelist[j];\n\t \twhile (node != sentinel) {\n\t\tif (node->ref != 0 && node->ref != DD_MAXREF) {\n\t\t \tindex = (int) node->index;\n\t\t \tif (node != manager->vars[index]) {\n\t\t\t\tprintf(\"* node found (index %d)\\n\", index);\n\t\t\t\tcount++;\n\t\t \t} \n\t\t\telse {\n\t\t\t\tif (node->ref != 1) {\n\t\t\t\t\tprintf(\"* variable found (index %d)\\n\", index);\n\t\t\t\t \tcount++;\n\t\t\t\t}\n\t\t \t}\n\t\t}\n\t\tnode = node->next;\n\t \t}\n\t}\n \t}\n\n \t/* Then look at the ZDD subtables. */\n \tsize = manager->sizeZ;\n \tif (size) /* references from ZDD universe */\n\tremain += 2;\n\n \tfor (i = 0; i < size; i++) {\n\tsubtable = &(manager->subtableZ[i]);\n\tnodelist = subtable->nodelist;\n\tfor (j = 0; (unsigned) j < subtable->slots; j++) {\n\t \tnode = nodelist[j];\n\t \twhile (node != NULL) {\n\t\tif (node->ref != 0 && node->ref != DD_MAXREF) {\n\t\t \tindex = (int) node->index;\n\t\t \tif (node == manager->univ[manager->permZ[index]]) {\n\t\t\tif (node->ref > 2) {\n\t\t\t \tcount++;\n\t\t\t}\n\t\t \t} else {\n\t\t\tcount++;\n\t\t \t}\n\t\t}\n\t\tnode = node->next;\n\t \t}\n\t}\n \t}\n\n \t/* Now examine the constant table. Plusinfinity, minusinfinity, and\n \t** zero are referenced by the manager. One is referenced by the\n \t** manager, by the ZDD universe, and by all projection functions.\n \t** All other nodes should have no references.\n \t*/\n \tnodelist = manager->constants.nodelist;\n \tfor (j = 0; (unsigned) j < manager->constants.slots; j++) {\n\tnode = nodelist[j];\n\twhile (node != NULL) {\n\t \tif (node->ref != 0 && node->ref != DD_MAXREF) {\n\t\tif (node == manager->one) {\n\t\t \tif ((int) node->ref != remain) {\n\t\t\tcount++;\n\t\t \t}\n\t\t} else if (node == manager->zero ||\n\t\tnode == manager->plusinfinity ||\n\t\tnode == manager->minusinfinity) {\n\t\t \tif (node->ref != 1) {\n\t\t\tcount++;\n\t\t \t}\n\t\t} else {\n\t\t\tprintf(\"* constant found (index %g)\\n\", node->type.value);\n\t\t \tcount++;\n\t\t}\n\t \t}\n\t \tnode = node->next;\n\t}\n \t}\n \treturn(count);\n\n}\n\n//-----------------------------------------------------------------------------------\n\n// -------------- Reference analysis ------------------------------------------------\n\n// dump info about a node\nstatic void dump_node(DdNode* node)\n{\n\tif (Cudd_IsConstant(node)) {\n\t\tprintf(\"%p: value=%f, refs=%d\\n\", node, Cudd_V(node), node->ref);\n\t} else {\n\t\tint index = node->index;\n\t\tprintf(\"%p: var=%d, refs=%d\\n\", node, index, node->ref);\n\t}\n}\n\n// add a reference for node to the reference map\nstatic void add_reference(std::map<DdNode*, int>& references, DdNode* node, int increase=1)\n{\n\tstd::map<DdNode*, int>::iterator it = references.find(node);\n\tif (it == references.end()) {\n\t\t// node was not yet registered\n\t\treferences[node] = increase;\n\t} else {\n\t\t// increase the value\n\t\tint& v = it->second;\n\t\tv += increase;\n\t}\n}\n\n// Analyze the nodes, return all encountered nodes in the set nodes\n// and return the number of internal references for each node in the\n// map internal_refs.\n// An internal reference is a reference via the then or else pointer of\n// another node or a reference by the manager (projection functions, some constants).\nstatic void DD_AnalyzeRefCounts(DdManager *manager, std::set<DdNode*>& nodes, std::map<DdNode*,int>& internal_refs)\n{\n \tint size;\n \tint i, j;\n \tint remain;\n \tDdNode **nodelist;\n \tDdNode *node;\n \tDdNode *sentinel = &(manager->sentinel);\n \tDdSubtable *subtable;\n \tint count = 0;\n \tint index;\n \tconst bool debug = false;\n\n#ifndef DD_NO_DEATH_ROW\n\tcuddClearDeathRow(manager);\n#endif\n\n\tif (manager->sizeZ > 0) {\n\t\tprintf(\"Can not handle ZDD in Cudd, abort...\");\n\t\treturn;\n\t}\n\n\tsize = manager->size;\n\tif (debug)\n\t\tprintf(\"manager->size = %d\\n\", size);\n\n \tfor (i = 0; i < size; i++) {\n\tsubtable = &(manager->subtables[i]);\n\tnodelist = subtable->nodelist;\n\tfor (j = 0; (unsigned) j < subtable->slots; j++) {\n\t \tnode = nodelist[j];\n\t \twhile (node != sentinel) {\n\t \tnodes.insert(node);\n\t \tif (debug) printf(\"add:\\n \");\n\t \tif (debug) dump_node(node);\n\t \tif (node->ref == DD_MAXREF) {\n\t \t\t// TODO: Error handling, how do we deal with this case?\n\t \t}\n\t\tindex = (int) node->index;\n\t\tif (node == manager->vars[index]) {\n\t\t\t// a projection function, deal with references from the manager later\n\t\t\tif (debug) printf(\"%p is projection\\n\", node);\n\t\t} else if (node->ref > 0) {\n\t\t\tDdNode *t = Cudd_Regular(Cudd_T(node));\n\t\t\tadd_reference(internal_refs, t);\n\t\t\tif (debug) printf(\"t ref: %p  -> %d\\n\", t, internal_refs[t]);\n\t\t\tDdNode *e = Cudd_Regular(Cudd_E(node));\n\t\t\tadd_reference(internal_refs, e);\n\t\t\tif (debug) printf(\"e ref: %p  -> %d\\n\", e, internal_refs[e]);\n\t\t}\n\t\tnode = node->next;\n\t \t}\n\t}\n \t}\n\n\tfor (i=0; i<size; i++) {\n\t\tnode = manager->vars[i];\n\t\tadd_reference(internal_refs, node);\n\t\tif (debug) printf(\"::%p projection -> %d\\n\", node, internal_refs[node]);\n\t\tDdNode *t = Cudd_Regular(Cudd_T(node));\n\t\tadd_reference(internal_refs, t);\n\t\tif (debug) printf(\"t ref: %p  -> %d\\n\", t, internal_refs[t]);\n\t\tDdNode *e = Cudd_Regular(Cudd_E(node));\n\t\tadd_reference(internal_refs, e);\n\t\tif (debug) printf(\"e ref: %p  -> %d\\n\", e, internal_refs[e]);\n\t}\n\n \t// Examine the constant table. Plusinfinity, minusinfinity, one and\n \t// zero are referenced by the manager.\n \tnodelist = manager->constants.nodelist;\n \tfor (j = 0; (unsigned) j < manager->constants.slots; j++) {\n\tnode = nodelist[j];\n\twhile (node != NULL) {\n\t\tnodes.insert(node);\n\t \tif (node->ref == DD_MAXREF) {\n\t \t\t// Error handling\n\t \t}\n\t\tif (node == manager->one ||\n\t\t    node == manager->zero ||\n\t\t    node == manager->plusinfinity ||\n\t\t    node == manager->minusinfinity) {\n\t\t\t// manager refs\n\t\t\tadd_reference(internal_refs, node);\n\t\t\tif (debug) printf(\"%p Constant(%f) -> %d\\n\", node, Cudd_V(node), internal_refs[node]);\n\t\t}\n\t \tnode = node->next;\n\t}\n\t}\n}\n\n\n// Print a report about the nodes of this manager, with the number of internal references\nvoid DD_ReportExternalRefCounts(DdManager *manager)\n{\n\tstd::set<DdNode*> nodes;\n\tstd::map<DdNode*, int> internal_refs;\n\n\tDD_AnalyzeRefCounts(manager, nodes, internal_refs);\n\tprintf(\"%s nodes\\n\", std::to_string(nodes.size()).c_str());  // no portable format string flag for size_t at the moment\n\n\tfor (std::set<DdNode*>::iterator it = nodes.begin();\n\t     it != nodes.end();\n\t     ++it) {\n\t     DdNode* node = *it;\n\t\tprintf(\"%d -> \", (internal_refs.find(node) != internal_refs.end() ? internal_refs[node] : 0));\n\t\tdump_node(node);\n\t}\n\n\t// Analysis\n\tprintf(\"\\nExternal references:\\n\");\n\tfor (std::set<DdNode*>::iterator it = nodes.begin();\n\t     it != nodes.end();\n\t     ++it) {\n\t\tDdNode* node = *it;\n\t\tint internal = (internal_refs.find(node) != internal_refs.end() ? internal_refs[node] : 0);\n\n\t\tif (node->ref > internal) {\n\t\t\tdump_node(node);\n\t\t\tprintf(\" Internal references: %d\\n\", internal);\n\t\t} else if (node->ref < internal) {\n\t\t\tdump_node(node);\n\t\t\tprintf(\"Underflow! Internal references: %d\\n\", internal);\n\t\t}\n\t}\n}\n\n// Analyze the BDD and return the implied number of external references per node\n// in the map external_refs (only return nodes with non-zero external references)\nvoid DD_GetExternalRefCounts(DdManager *manager, std::map<DdNode*,int>& external_refs)\n{\n\tstd::set<DdNode*> nodes;\n\tstd::map<DdNode*, int> internal_refs;\n\n\tDD_AnalyzeRefCounts(manager, nodes, internal_refs);\n\n\tfor (std::set<DdNode*>::iterator it = nodes.begin();\n\t     it != nodes.end();\n\t     ++it) {\n\t\tDdNode* node = *it;\n\t\tint internal = (internal_refs.find(node) != internal_refs.end() ? internal_refs[node] : 0);\n\n\t\tif (node->ref != internal) {\n\t\t\texternal_refs[node] = node->ref - internal;\n\t\t}\n\t}\n\t// printf(\"Found %lu problematic nodes\\n\", external_refs.size());\n}\n\n//-----------------------------------------------------------------------------------\n\n// Get the value of the DD error flag\nbool DD_GetErrorFlag(DdManager *ddman)\n{\n\treturn dd_cudd_error_flag || (ddman->errorCode != CUDD_NO_ERROR);\n}\n\n//-----------------------------------------------------------------------------------\n\n// Set the DD error flag. Should be set if a CUDD error has been\n// detected that could not be signalled by returning a NULL DdNode*\n// from the function\nvoid DD_SetErrorFlag()\n{\n\tdd_cudd_error_flag = true;\n}\n\n\n//-----------------------------------------------------------------------------------\n\n\n"
  },
  {
    "path": "prism/src/dd/dd_export.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\tDescription: DD export functions\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <cstdio>\n#include <cstdlib>\n#include <cmath>\n#include <cinttypes>\n#include <util.h>\n#include <cudd.h>\n#include \"dd.h\"\n#include \"dd_basics.h\"\n#include \"dd_abstr.h\"\n#include \"dd_info.h\"\n\n//------------------------------------------------------------------------------\n\n// local prototypes\n\nstatic int  DD_ExportDDToDDFile(DdManager *ddman, DdNode *dd, DdNode **done, int count, FILE *fp);\nstatic void DD_ExportMatrixToPPFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, FILE *fp, int rstart, int cstart);\nstatic void DD_ExportVectorToMatlabFile(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, char *name, FILE *fp, int start);\nstatic void DD_ExportMatrixToMatlabFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, char *name, FILE *fp, int rstart, int cstart);\nstatic void DD_ExportMatrixToPPFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, FILE *fp, int rstart, int cstart);\nstatic void DD_ExportMatrixToSpyFile(DdManager *ddman, DdNode *dd, DdNode **rvars, int num_rvars, DdNode **cvars, int num_cvars, FILE *fp, int rstart, int cstart, unsigned char **array);\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportDDToDotFile\n(\nDdManager *ddman,\nDdNode *dd,\nchar *filename\n)\n{\n\tFILE *fp = fopen(filename, \"w\");\n\tif (fp == NULL) {\n\t\t// crash out\n\t\treturn;\n\t}\n\tDD_ExportDDToDotFileLabelled(ddman, dd, fp, (char*)\"DD\", NULL);\n\tfclose(fp);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportDDToDotFileLabelled\n(\nDdManager *ddman,\nDdNode *dd,\nchar *filename,\nchar **var_names\n)\n{\n\tFILE *fp = fopen(filename, \"w\");\n\tif (fp == NULL) {\n\t\t// crash out\n\t\treturn;\n\t}\n\tDD_ExportDDToDotFileLabelled(ddman, dd, fp, (char*)\"DD\", var_names);\n\tfclose(fp);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportDDToDotFile\n(\nDdManager *ddman,\nDdNode *dd,\nFILE *fp\n)\n{\n\tDD_ExportDDToDotFileLabelled(ddman, dd, fp, (char*)\"DD\", NULL);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportDDToDotFileLabelled\n(\nDdManager *ddman,\nDdNode *dd,\nFILE *fp,\nchar *title,\nchar **var_names\n)\n{\n\tCudd_DumpDot(ddman, 1, &dd, var_names, &title, fp);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportDDToDDFile\n(\nDdManager *ddman,\nDdNode *dd,\nchar *filename\n)\n{\n\tFILE *fp = fopen(filename, \"w\");\n\tif (fp == NULL) {\n\t\t// crash out\n\t\treturn;\n\t}\n\tDD_ExportDDToDDFile(ddman, dd, fp);\n\tfclose(fp);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportDDToDDFile\n(\nDdManager *ddman,\nDdNode *dd,\nFILE *fp\n)\n{\n\tint num_nodes;\n\tDdNode **stored;\n\t\n\tnum_nodes = DD_GetNumNodes(ddman, dd);\n\tfprintf(fp, \"%d\\n\", num_nodes);\n\tstored = new DdNode*[num_nodes];\n\t\n\tDD_ExportDDToDDFile(ddman, dd, stored, 0, fp);\n\t\n\tdelete[] stored;\n}\n\n//------------------------------------------------------------------------------\n\nstatic int DD_ExportDDToDDFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **stored,\nint count,\nFILE *fp\n)\n{\n\tint i;\n\tbool found;\n\t\n\ti = 0;\n\tfound = false;\n\twhile (i < count && !found) {\n\t\tif (stored[i] == dd) {\n\t\t\tfound = true;\n\t\t}\n\t\telse {\n\t\t\ti++;\n\t\t}\n\t}\n\tif (!found) {\n\t\tstored[count++] = dd;\n\t}\n\n\tfprintf(fp, \"%\" PRIuPTR \"\\n\", (uintptr_t)dd);\n\n\treturn 0;\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportVectorToMatlabFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars,\nchar *name,\nchar *filename\n)\n{\n\tFILE *fp = fopen(filename, \"w\");\n\tif (fp == NULL) {\n\t\t// crash out\n\t\treturn;\n\t}\n\tDD_ExportVectorToMatlabFile(ddman, dd, vars, num_vars, name, fp);\n\tfclose(fp);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportVectorToMatlabFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars,\nchar *name,\nFILE *fp\n)\n{\n\tfprintf(fp, \"%s = sparse(1, %d);\\n\", name, (int)pow(2.0, num_vars));\n\tDD_ExportVectorToMatlabFile(ddman, dd, vars, num_vars, name, fp, 0);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void DD_ExportVectorToMatlabFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars,\nchar *name,\nFILE *fp,\nint start\n)\n{\n\tDdNode *n, *s;\n\t\n\tif (dd == Cudd_addConst(ddman, 0)) {\n\t\treturn;\n\t}\n\t\t\t\n\tif (num_vars == 0) {\n\t\tfprintf(fp, \"%s(1, %d) = %f;\\n\", name, start+1, Cudd_V(dd));\n\t}\n\telse {\n\t\t// split into 2 cases\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(vars[0]);\n\t\tn = DD_Restrict(ddman, dd, DD_Not(ddman, vars[0]));\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(vars[0]);\n\t\ts = DD_Restrict(ddman, dd, vars[0]);\n\t\t\n\t\tDD_ExportVectorToMatlabFile(ddman, n, &vars[1], num_vars-1, name, fp, start);\n\t\tDD_ExportVectorToMatlabFile(ddman, s, &vars[1], num_vars-1, name, fp, start+(int)pow(2.0, num_vars-1));\n\t\t\n\t\tCudd_RecursiveDeref(ddman, n);\n\t\tCudd_RecursiveDeref(ddman, s);\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportMatrixToMatlabFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nchar *name,\nchar *filename\n)\n{\n\tFILE *fp = fopen(filename, \"w\");\n\tif (fp == NULL) {\n\t\t// crash out\n\t\treturn;\n\t}\n\tDD_ExportMatrixToMatlabFile(ddman, dd, rvars, num_rvars, cvars, num_cvars, name, fp);\n\tfclose(fp);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportMatrixToMatlabFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nchar *name,\nFILE *fp\n)\n{\n\tfprintf(fp, \"%s = sparse(%d, %d);\\n\", name, (int)pow(2.0, num_rvars), (int)pow(2.0, num_cvars));\n\tDD_ExportMatrixToMatlabFile(ddman, dd, rvars, num_rvars, cvars, num_cvars, name, fp, 0, 0);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void DD_ExportMatrixToMatlabFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nchar *name,\nFILE *fp,\nint rstart,\nint cstart\n)\n{\n\tDdNode *n, *s, *ne, *nw, *sw, *se;\n\t\n\tif (dd == Cudd_addConst(ddman, 0)) {\n\t\treturn;\n\t}\n\t\t\t\n\tif (num_rvars == 0) {\n\t\tfprintf(fp, \"%s(%d, %d) = %f;\\n\", name, rstart+1, cstart+1, Cudd_V(dd));\n\t}\n\telse {\n\t\t// split into 4 cases\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(rvars[0]);\n\t\tn = DD_Restrict(ddman, dd, DD_Not(ddman, rvars[0]));\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(rvars[0]);\n\t\ts = DD_Restrict(ddman, dd, rvars[0]);\n\t\tCudd_Ref(n);\n\t\tCudd_Ref(cvars[0]);\n\t\tnw = DD_Restrict(ddman, n, DD_Not(ddman, cvars[0]));\n\t\tCudd_Ref(n);\n\t\tCudd_Ref(cvars[0]);\n\t\tne = DD_Restrict(ddman, n, cvars[0]);\n\t\tCudd_Ref(s);\n\t\tCudd_Ref(cvars[0]);\n\t\tsw = DD_Restrict(ddman, s, DD_Not(ddman, cvars[0]));\n\t\tCudd_Ref(s);\n\t\tCudd_Ref(cvars[0]);\n\t\tse = DD_Restrict(ddman, s, cvars[0]);\n\t\t\n\t\tDD_ExportMatrixToMatlabFile(ddman, nw, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, name, fp, rstart, cstart);\n\t\tDD_ExportMatrixToMatlabFile(ddman, ne, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, name, fp, rstart, cstart+(int)pow(2.0, num_cvars-1));\n\t\tDD_ExportMatrixToMatlabFile(ddman, sw, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, name, fp, rstart+(int)pow(2.0, num_rvars-1), cstart);\n\t\tDD_ExportMatrixToMatlabFile(ddman, se, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, name, fp, rstart+(int)pow(2.0, num_rvars-1), cstart+(int)pow(2.0, num_cvars-1));\n\t\t\n\t\tCudd_RecursiveDeref(ddman, n);\n\t\tCudd_RecursiveDeref(ddman, s);\n\t\tCudd_RecursiveDeref(ddman, nw);\n\t\tCudd_RecursiveDeref(ddman, ne);\n\t\tCudd_RecursiveDeref(ddman, sw);\n\t\tCudd_RecursiveDeref(ddman, se);\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportMatrixToPPFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nchar *filename\n)\n{\n\tFILE *fp = fopen(filename, \"w\");\n\tif (fp == NULL) {\n\t\t// crash out\n\t\treturn;\n\t}\n\tDD_ExportMatrixToPPFile(ddman, dd, rvars, num_rvars, cvars, num_cvars, fp);\n\tfclose(fp);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportMatrixToPPFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nFILE *fp\n)\n{\n\tfprintf(fp, \"%d\\n\", (int)pow(2.0, num_rvars));\n\tDD_ExportMatrixToPPFile(ddman, dd, rvars, num_rvars, cvars, num_cvars, fp, 0, 0);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void DD_ExportMatrixToPPFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nFILE *fp,\nint rstart,\nint cstart\n)\n{\n\tDdNode *n, *s, *ne, *nw, *sw, *se;\n\t\n\tif (dd == Cudd_addConst(ddman, 0)) {\n\t\treturn;\n\t}\n\t\n\t// handle non square bit (if r < c ...)\n\t// (if i can be bothered)\n\t\t\n\tif (num_rvars == 0) {\n\t\tfprintf(fp, \"%d %d %f\\n\", rstart, cstart, Cudd_V(dd));\n\t}\n\telse {\n\t\t// split into 4 cases\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(rvars[0]);\n\t\tn = DD_Restrict(ddman, dd, DD_Not(ddman, rvars[0]));\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(rvars[0]);\n\t\ts = DD_Restrict(ddman, dd, rvars[0]);\n\t\tCudd_Ref(n);\n\t\tCudd_Ref(cvars[0]);\n\t\tnw = DD_Restrict(ddman, n, DD_Not(ddman, cvars[0]));\n\t\tCudd_Ref(n);\n\t\tCudd_Ref(cvars[0]);\n\t\tne = DD_Restrict(ddman, n, cvars[0]);\n\t\tCudd_Ref(s);\n\t\tCudd_Ref(cvars[0]);\n\t\tsw = DD_Restrict(ddman, s, DD_Not(ddman, cvars[0]));\n\t\tCudd_Ref(s);\n\t\tCudd_Ref(cvars[0]);\n\t\tse = DD_Restrict(ddman, s, cvars[0]);\n\t\t\n\t\tDD_ExportMatrixToPPFile(ddman, nw, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, fp, rstart, cstart);\n\t\tDD_ExportMatrixToPPFile(ddman, ne, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, fp, rstart, cstart+(int)pow(2.0, num_cvars-1));\n\t\tDD_ExportMatrixToPPFile(ddman, sw, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, fp, rstart+(int)pow(2.0, num_rvars-1), cstart);\n\t\tDD_ExportMatrixToPPFile(ddman, se, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, fp, rstart+(int)pow(2.0, num_rvars-1), cstart+(int)pow(2.0, num_cvars-1));\n\t\t\n\t\tCudd_RecursiveDeref(ddman, n);\n\t\tCudd_RecursiveDeref(ddman, s);\n\t\tCudd_RecursiveDeref(ddman, nw);\n\t\tCudd_RecursiveDeref(ddman, ne);\n\t\tCudd_RecursiveDeref(ddman, sw);\n\t\tCudd_RecursiveDeref(ddman, se);\n\t}\n}\n\n//------------------------------------------------------------------------------\n\n// Given a BDD that represents a MDP transition matrices, this method\n// outputs one matrix for every action.\n// note that the output is in fact not a PP file, but\n// several PP files concatenated into one file.\n//\n// For example, for a model with the variable\n//  x : [0..2];\n// and transitions\n//  [a] (x=0) -> 0.3:(x'=1) + 0.7:(x'=2);\n//  [b] (x=0) -> 1:(x'=2);\n//  [a] (x=2) -> (x'=1);\n//  [a] (x=1) -> (x'=0);\n// the output would be (e.g.)\n//  4\n//  4\n//  0 2 1.000000\n//  4\n//  0 1 0.300000\n//  1 0 1.000000\n//  0 2 0.700000\n//  2 1 1.000000\n//  4\nvoid DD_Export3dMatrixToPPFile\n(\n DdManager *ddman,\n DdNode *dd,\n DdNode **rvars,\n int num_rvars,\n DdNode **cvars,\n int num_cvars,\n DdNode **nvars,\n int num_nvars,\n char *filename\n )\n{\n\tFILE *fp = fopen(filename, \"w\");\n\tif (fp == NULL) {\n\t\t// crash out\n\t\treturn;\n\t}\n\tDD_Export3dMatrixToPPFile(ddman, dd, rvars, num_rvars, cvars, num_cvars, nvars, num_nvars, fp);\n\tfclose(fp);\n}\n\nvoid DD_Export3dMatrixToPPFile\n(\n DdManager *ddman,\n DdNode *dd,\n DdNode **rvars,\n int num_rvars,\n DdNode **cvars,\n int num_cvars,\n DdNode **nvars,\n int num_nvars,\n FILE *fp\n )\n{\n\tDdNode *n, *s;\n\tif (num_nvars == 0)\n\t{   //base step: if there are no nondeterministic variables, print output as for normal PP file\n\t\tfprintf(fp, \"%d\\n\", (int)pow(2.0, num_rvars));\n\t\tDD_ExportMatrixToPPFile(ddman, dd, rvars, num_rvars, cvars, num_cvars, fp, 0, 0);\n\t}\n\telse\n\t{ //if there are some nondeterministic variables, we remove one of them, splitting into two cases\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(nvars[0]);\n\t\tn = DD_Restrict(ddman, dd, DD_Not(ddman, nvars[0]));\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(nvars[0]);\n\t\ts = DD_Restrict(ddman, dd, nvars[0]);\n\t\t\n\t\tDD_Export3dMatrixToPPFile(ddman, n, rvars, num_rvars, cvars, num_cvars, &nvars[1], num_nvars-1, fp);\n\t\tDD_Export3dMatrixToPPFile(ddman, s, rvars, num_rvars, cvars, num_cvars, &nvars[1], num_nvars-1, fp);\n\t\t\n\t\tCudd_RecursiveDeref(ddman, n);\n\t\tCudd_RecursiveDeref(ddman, s);\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportMatrixToSpyFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nint depth,\nchar *filename\n)\n{\n\tFILE *fp = fopen(filename, \"w\");\n\tif (fp == NULL) {\n\t\t// crash out\n\t\treturn;\n\t}\n\tDD_ExportMatrixToSpyFile(ddman, dd, rvars, num_rvars, cvars, num_cvars, depth, fp);\n\tfclose(fp);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_ExportMatrixToSpyFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nint depth,\nFILE *fp\n)\n{\n\tDdNode *new_dd;\n\tint num_states, i, j;\n\tunsigned char **array;\n\t\n\tif (depth > num_rvars || depth < 3) {\n\t\treturn;\n\t}\n\t\n\t// abstract away bottom of input dd to leave required depth\n\tCudd_Ref(dd);\n\tnew_dd = DD_MaxAbstract(ddman, dd, &rvars[depth], num_rvars - depth);\n\tnew_dd = DD_MaxAbstract(ddman, new_dd, &cvars[depth], num_cvars - depth);\n\tnew_dd = DD_StrictThreshold(ddman, new_dd, 0);\n\t\n\t// create array to store 0-1 spy info\n\tnum_states = (int)pow(2.0, depth);\n\tarray = new unsigned char*[num_states];\n\tfor (i = 0; i < num_states; i++) {\n\t\tarray[i] = new unsigned char[num_states/8];\n\t\tfor (j = 0; j < num_states/8; j++) {\n\t\t\tarray[i][j] = 0;\n\t\t}\n\t}\n\t\n\tDD_ExportMatrixToSpyFile(ddman, new_dd, rvars, depth, cvars, depth, fp, 0, 0, array);\n\t\n\tfwrite(&num_rvars, sizeof(num_rvars), 1, fp);\n\tfwrite(&depth, sizeof(depth), 1, fp);\n\tfor (i = 0; i < num_states; i++) {\n\t\tfwrite(array[i], num_states/8, 1, fp);\n\t}\n\t\n\tCudd_RecursiveDeref(ddman, new_dd);\n\tfor (i = 0; i < num_states; i++) delete[] array[i];\n\tdelete[] array;\n}\n\n//------------------------------------------------------------------------------\n\nstatic void DD_ExportMatrixToSpyFile\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nFILE *fp,\nint rstart,\nint cstart,\nunsigned char **array\n)\n{\n\tDdNode *n, *s, *ne, *nw, *sw, *se;\n\t\n\tif (dd == Cudd_addConst(ddman, 0)) {\n\t\treturn;\n\t}\n\t\n\t// handle non square bit (if r < c ...)\n\t// (if i can be bothered)\n\t\t\n\tif (num_rvars == 0) {\n\t\tarray[rstart][cstart/8] |= (int)pow(2.0,(cstart%8));\n\t}\n\telse {\n\t\t// split into 4 cases\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(rvars[0]);\n\t\tn = DD_Restrict(ddman, dd, DD_Not(ddman, rvars[0]));\n\t\tCudd_Ref(dd);\n\t\tCudd_Ref(rvars[0]);\n\t\ts = DD_Restrict(ddman, dd, rvars[0]);\n\t\tCudd_Ref(n);\n\t\tCudd_Ref(cvars[0]);\n\t\tnw = DD_Restrict(ddman, n, DD_Not(ddman, cvars[0]));\n\t\tCudd_Ref(n);\n\t\tCudd_Ref(cvars[0]);\n\t\tne = DD_Restrict(ddman, n, cvars[0]);\n\t\tCudd_Ref(s);\n\t\tCudd_Ref(cvars[0]);\n\t\tsw = DD_Restrict(ddman, s, DD_Not(ddman, cvars[0]));\n\t\tCudd_Ref(s);\n\t\tCudd_Ref(cvars[0]);\n\t\tse = DD_Restrict(ddman, s, cvars[0]);\n\t\t\n\t\tDD_ExportMatrixToSpyFile(ddman, nw, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, fp, rstart, cstart, array);\n\t\tDD_ExportMatrixToSpyFile(ddman, ne, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, fp, rstart, cstart+(int)pow(2.0, num_cvars-1), array);\n\t\tDD_ExportMatrixToSpyFile(ddman, sw, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, fp, rstart+(int)pow(2.0, num_rvars-1), cstart, array);\n\t\tDD_ExportMatrixToSpyFile(ddman, se, &rvars[1], num_rvars-1, &cvars[1], num_cvars-1, fp, rstart+(int)pow(2.0, num_rvars-1), cstart+(int)pow(2.0, num_cvars-1), array);\n\t\t\n\t\tCudd_RecursiveDeref(ddman, n);\n\t\tCudd_RecursiveDeref(ddman, s);\n\t\tCudd_RecursiveDeref(ddman, nw);\n\t\tCudd_RecursiveDeref(ddman, ne);\n\t\tCudd_RecursiveDeref(ddman, sw);\n\t\tCudd_RecursiveDeref(ddman, se);\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dd/dd_info.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: DD analysis/information functions\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include \"dd_basics.h\"\n#include \"dd_term.h\"\n#include \"dd_info.h\"\n\nextern FILE *dd_out;\n\nextern void DD_PrintTerminals(DdManager *ddman, DdNode *dd, int num_vars, bool and_numbers);\n\n//------------------------------------------------------------------------------\n\nint DD_GetNumNodes\n(\nDdManager *ddman,\nDdNode *dd\n)\n{\n\treturn Cudd_DagSize(dd);\n}\n\n//------------------------------------------------------------------------------\n\nint DD_GetNumTerminals\n(\nDdManager *ddman,\nDdNode *dd\n)\n{\n\treturn Cudd_CountLeaves(dd);\n}\n\n//------------------------------------------------------------------------------\n\ndouble DD_GetNumMinterms\n(\nDdManager *ddman,\nDdNode *dd,\nint num_vars\n)\n{\n\treturn Cudd_CountMinterm(ddman, dd, num_vars);\n}\n\n//------------------------------------------------------------------------------\n\ndouble DD_GetNumPaths\n(\nDdManager *ddman,\nDdNode *dd\n)\n{\n\treturn Cudd_CountPath(dd);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintInfo\n(\nDdManager *ddman,\nDdNode *dd,\nint num_vars)\n{\n\tint nodes, terminals;\n\tdouble minterms;\n\t\n\tnodes = Cudd_DagSize(dd);\n\tterminals = Cudd_CountLeaves(dd);\n\tminterms = Cudd_CountMinterm(ddman, dd, num_vars);\n\tfprintf(dd_out, \"%d nodes (%d terminal), %.0f minterms\\n\", nodes, terminals, minterms);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintInfoBrief\n(\nDdManager *ddman,\nDdNode *dd,\nint num_vars)\n{\n\tint nodes, terminals;\n\tdouble minterms;\n\t\n\tnodes = Cudd_DagSize(dd);\n\tterminals = Cudd_CountLeaves(dd);\n\tminterms = Cudd_CountMinterm(ddman, dd, num_vars);\n\tfprintf(dd_out, \"[%d,%d,%.0f]\\n\", nodes, terminals, minterms);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintSupport\n(\nDdManager *ddman,\nDdNode *dd\n)\n{\n\tDD_PrintSupportNames(ddman, dd, NULL);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintSupportNames\n(\nDdManager *ddman,\nDdNode *dd,\nchar **var_names\n)\n{\n\tint i;\n\tDdNode *supp, *tmp;\n\t\n\tfprintf(dd_out, \"(\");\n\tsupp = Cudd_Support(ddman, dd);\n\tCudd_Ref(supp);\n\ttmp = supp;\n\twhile (!Cudd_IsConstant(tmp)) {\n\t\ti = Cudd_NodeReadIndex(tmp);\n\t\tif (var_names) fprintf(dd_out, \" %s\", var_names[i]);\n\t\telse fprintf(dd_out, \" %d\", i);\n\t\ttmp = Cudd_T(tmp);\n\t}\n\tfprintf(dd_out, \" )\\n\");\n\tCudd_RecursiveDeref(ddman, supp);\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_GetSupport\n(\nDdManager *ddman,\nDdNode *dd\n)\n{\n\tDdNode *supp, *supp2;\n\t\n\tsupp = Cudd_Support(ddman, dd);\n\tCudd_Ref(supp);\n\tsupp2 = Cudd_BddToAdd(ddman, supp);\t\n\tCudd_Ref(supp2);\t\n\tCudd_RecursiveDeref(ddman, supp);\n\t\n\treturn supp2;\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintTerminals(DdManager *ddman, DdNode *dd) { DD_PrintTerminals(ddman, dd, 0, false); }\n\nvoid DD_PrintTerminalsAndNumbers(DdManager *ddman, DdNode *dd, int num_vars) { DD_PrintTerminals(ddman, dd, num_vars, true); }\n\nvoid DD_PrintTerminals\n(\nDdManager *ddman,\nDdNode *dd,\nint num_vars,\nbool and_numbers)\n{\n\tDdNode *tmp, *tmp2;\n\tdouble min, max, num, count = 0.0;\n\n\t// Take a copy of dd\t\n\tCudd_Ref(dd);\n\ttmp = dd;\n\t// Check the min (will use at end)\n\tmin = Cudd_V(Cudd_addFindMin(ddman, tmp));\n\t// Loop through terminals in descending order\n\twhile (tmp != Cudd_ReadMinusInfinity(ddman)) {\n\t\t// Find next (max) terminal and display\n\t\tmax = Cudd_V(Cudd_addFindMax(ddman, tmp));\n\t\tfprintf(dd_out, \"%f \", max);\n\t\t// Remove the terminals, counting/displaying number if required\n\t\tCudd_Ref(tmp);\n\t\ttmp2 = DD_Equals(ddman, tmp, max);\n\t\tif (and_numbers) {\n\t\t\tnum = Cudd_CountMinterm(ddman, tmp2, num_vars);\n\t\t\tcount += num;\n\t\t\tfprintf(dd_out, \"(%.0f) \", num);\n\t\t}\n\t\ttmp = DD_ITE(ddman, tmp2, DD_MinusInfinity(ddman), tmp);\n\t}\n\tCudd_RecursiveDeref(ddman, tmp);\n\t// Finally, print if there are (and possibly how many) minus infinities\n\tif (and_numbers) {\n\t\tif (count < (1<<num_vars)) fprintf(dd_out, \"-inf (%.0f)\", pow(2.0, num_vars) - count);\n\t} else {\n\t\tif (min == -HUGE_VAL) fprintf(dd_out, \"-inf\");\n\t}\n\tfprintf(dd_out, \"\\n\");\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dd/dd_matrix.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: DD matrix functions\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <cstdio>\n#include <cstdlib>\n#include <cmath>\n#include <util.h>\n#include <limits>  // for NaN value\n#include <cudd.h>\n#include <cuddInt.h>\n#include \"dd_matrix.h\"\n#include \"dd_basics.h\"\n#include \"dd_cudd.h\"\n\nextern FILE *dd_out;\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_SetVectorElement\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars,\nlong index,\ndouble value\n)\n{\n\tDdNode *tmp, *tmp2, *f, *tmp_f, *g, *res;\n\tint i;\n\n\tif (dd == NULL) return NULL;\n\n\t// build a 0-1 ADD to store position of element of the vector\n\tf = DD_Constant(ddman, 1);\n\tif (f == NULL) return NULL;\n\tfor (i = 0; i < num_vars; i++) {\n\t\tCudd_Ref(tmp = vars[i]);\t\t\t\t\n\t\tif ((index & (1l<<(num_vars-i-1))) == 0) {\n\t\t\ttmp2 = Cudd_addCmpl(ddman, tmp);\n\t\t\tif (tmp2 == NULL) return NULL;\n\t\t\tCudd_Ref(tmp2);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\ttmp = tmp2;\n\t\t}\n\t\ttmp_f = Cudd_addApply(ddman, Cudd_addTimes, tmp, f);\n\t\tif (tmp_f == NULL) return NULL;\n\t\tCudd_Ref(tmp_f);\n\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\tCudd_RecursiveDeref(ddman, f);\n\t\tf = tmp_f;\n\t}\n\t\n\tg = DD_Constant(ddman, value);\n\tif (g == NULL) return NULL;\n\t\n\t// compute new vector\n\tres = Cudd_addIte(ddman, f, g, dd);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, f);\n\tCudd_RecursiveDeref(ddman, g);\n\tCudd_RecursiveDeref(ddman, dd);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_SetMatrixElement\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nlong rindex,\nlong cindex,\ndouble value\n)\n{\n\tDdNode *tmp, *tmp2, *f, *tmp_f, *g, *res;\n\tint i;\n\n\tif (dd == NULL) return NULL;\n\n\t// build a 0-1 ADD to store position of element of the matrix\n\tf = DD_Constant(ddman, 1);\n\tif (f == NULL) return NULL;\n\tfor (i = 0; i < num_rvars; i++) {\n\t\tCudd_Ref(tmp = rvars[i]);\t\t\t\t\n\t\tif ((rindex & (1l<<(num_rvars-i-1))) == 0) {\n\t\t\ttmp2 = Cudd_addCmpl(ddman, tmp);\n\t\t\tif (tmp2 == NULL) return NULL;\n\t\t\tCudd_Ref(tmp2);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\ttmp = tmp2;\n\t\t}\n\t\ttmp_f = Cudd_addApply(ddman, Cudd_addTimes, tmp, f);\n\t\tif (tmp_f == NULL) return NULL;\n\t\tCudd_Ref(tmp_f);\n\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\tCudd_RecursiveDeref(ddman, f);\n\t\tf = tmp_f;\n\t}\n\tfor (i = 0; i < num_cvars; i++) {\n\t\tCudd_Ref(tmp = cvars[i]);\t\t\t\t\n\t\tif ((cindex & (1l<<(num_cvars-i-1))) == 0) {\n\t\t\ttmp2 = Cudd_addCmpl(ddman, tmp);\n\t\t\tif (tmp2 == NULL) return NULL;\n\t\t\tCudd_Ref(tmp2);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\ttmp = tmp2;\n\t\t}\n\t\ttmp_f = Cudd_addApply(ddman, Cudd_addTimes, tmp, f);\n\t\tif (tmp_f == NULL) return NULL;\n\t\tCudd_Ref(tmp_f);\n\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\tCudd_RecursiveDeref(ddman, f);\n\t\tf = tmp_f;\n\t}\n\t\n\tg = DD_Constant(ddman, value);\n\tif (g == NULL) return NULL;\n\t\n\t// compute new vector\n\tres = Cudd_addIte(ddman, f, g, dd);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, f);\n\tCudd_RecursiveDeref(ddman, g);\n\tCudd_RecursiveDeref(ddman, dd);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Set3DMatrixElement\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nDdNode **lvars,\nint num_lvars,\nlong rindex,\nlong cindex,\nlong lindex,\ndouble value\n)\n{\n\tDdNode *tmp, *tmp2, *f, *tmp_f, *g, *res;\n\tint i;\n\n\tif (dd == NULL) return NULL;\n\n\t// build a 0-1 ADD to store position of element of the matrix\n\tf = DD_Constant(ddman, 1);\n\tif (f == NULL) return NULL;\n\tfor (i = 0; i < num_rvars; i++) {\n\t\tCudd_Ref(tmp = rvars[i]);\t\t\t\t\n\t\tif ((rindex & (1l<<(num_rvars-i-1))) == 0) {\n\t\t\ttmp2 = Cudd_addCmpl(ddman, tmp);\n\t\t\tif (tmp2 == NULL) return NULL;\n\t\t\tCudd_Ref(tmp2);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\ttmp = tmp2;\n\t\t}\n\t\ttmp_f = Cudd_addApply(ddman, Cudd_addTimes, tmp, f);\n\t\tif (tmp_f == NULL) return NULL;\n\t\tCudd_Ref(tmp_f);\n\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\tCudd_RecursiveDeref(ddman, f);\n\t\tf = tmp_f;\n\t}\n\tfor (i = 0; i < num_cvars; i++) {\n\t\tCudd_Ref(tmp = cvars[i]);\t\t\t\t\n\t\tif ((cindex & (1l<<(num_cvars-i-1))) == 0) {\n\t\t\ttmp2 = Cudd_addCmpl(ddman, tmp);\n\t\t\tif (tmp2 == NULL) return NULL;\n\t\t\tCudd_Ref(tmp2);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\ttmp = tmp2;\n\t\t}\n\t\ttmp_f = Cudd_addApply(ddman, Cudd_addTimes, tmp, f);\n\t\tif (tmp_f == NULL) return NULL;\n\t\tCudd_Ref(tmp_f);\n\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\tCudd_RecursiveDeref(ddman, f);\n\t\tf = tmp_f;\n\t}\n\tfor (i = 0; i < num_lvars; i++) {\n\t\tCudd_Ref(tmp = lvars[i]);\t\t\t\t\n\t\tif ((lindex & (1l<<(num_lvars-i-1))) == 0) {\n\t\t\ttmp2 = Cudd_addCmpl(ddman, tmp);\n\t\t\tif (tmp2 == NULL) return NULL;\n\t\t\tCudd_Ref(tmp2);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\ttmp = tmp2;\n\t\t}\n\t\ttmp_f = Cudd_addApply(ddman, Cudd_addTimes, tmp, f);\n\t\tif (tmp_f == NULL) return NULL;\n\t\tCudd_Ref(tmp_f);\n\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\tCudd_RecursiveDeref(ddman, f);\n\t\tf = tmp_f;\n\t}\n\t\n\tg = DD_Constant(ddman, value);\n\tif (g == NULL) return NULL;\n\t\n\t// compute new vector\n\tres = Cudd_addIte(ddman, f, g, dd);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, f);\n\tCudd_RecursiveDeref(ddman, g);\n\tCudd_RecursiveDeref(ddman, dd);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\ndouble DD_GetVectorElement\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars,\nlong x\n)\n{\n\tint i;\n\tDdNode *node;\n\tint *inputs;\n\tdouble val;\n\n\tif (dd == NULL) {\n\t\tDD_SetErrorFlag();\n\t\treturn std::numeric_limits<double>::quiet_NaN();\n\t}\n\n\t// create array to store 0's & 1's used to query DD\n\tinputs = new int[Cudd_ReadSize(ddman)];\n\n\tfor (i = 0; i < Cudd_ReadSize(ddman); i++) {\n\t\tinputs[i] = 0;\n\t}\n\n\tfor (i = 0; i < num_vars; i++) {\n\t\tinputs[vars[i]->index] = ((x & (1l<<(num_vars-i-1))) == 0) ? 0 : 1;\n\t}\n\tnode = Cudd_Eval(ddman, dd, inputs);\n\tif (node == NULL) {\n\t\tDD_SetErrorFlag();\n\t\treturn std::numeric_limits<double>::quiet_NaN();\n\t}\n\tval = Cudd_V(node);\n\n\tif (inputs != NULL) {\n\t\tdelete[] inputs;\n\t}\n\n\treturn val;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Identity\n(\nDdManager *ddman,\nDdNode **rvars,\nDdNode **cvars,\nint num_vars\n)\n{\n\tDdNode *tmp;\n\t\n\ttmp = Cudd_addXeqy(ddman, num_vars, rvars, cvars);\n\tif (tmp == NULL) return NULL;\n\tCudd_Ref(tmp);\n\n\treturn tmp;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_MatrixMultiply\n(\nDdManager *ddman,\nDdNode *dd1,\nDdNode *dd2,\nDdNode **vars,\nint num_vars,\nint method\n)\n{\n\tDdNode *res;\n\n\tif (dd1 == NULL) return NULL;\n\tif (dd2 == NULL) return NULL;\n\n\tif (method == MM_CMU) {\n\t\tres = Cudd_addTimesPlus(ddman, dd1, dd2, vars, num_vars);\n\t}\n\telse { // (method == MM_BOULDER)\n\t\tres = Cudd_addMatrixMultiply(ddman, dd1, dd2, vars, num_vars);\n\t}\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd1);\n\tCudd_RecursiveDeref(ddman, dd2);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Transpose\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **row_vars,\nDdNode **col_vars,\nint num_vars\n)\n{\n\tint i, *permut;\n\tDdNode *res;\n\n\tif (dd == NULL) return NULL;\n\n\tpermut = new int[Cudd_ReadSize(ddman)];\n\tfor (i = 0; i < Cudd_ReadSize(ddman); i++) {\n\t\tpermut[i] = i;\n\t}\n\tfor (i = 0; i < num_vars; i++) {\n\t\tpermut[row_vars[i]->index] = col_vars[i]->index;\n\t\tpermut[col_vars[i]->index] = row_vars[i]->index;\n\t}\t\n\tres = Cudd_addPermute(ddman, dd, permut);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\n\tif (permut != NULL) {\n\t\tdelete[] permut;\n\t}\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintVector\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars\n)\n{\n\tDD_PrintVector(ddman, dd, vars, num_vars, ACCURACY_NORMAL);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintVector\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars,\nint accuracy\n)\n{\n\tint j;\n\tlong i, length;\n\tDdNode *node;\n\tint *inputs;\n\tdouble val;\n\n\t// create array to store 0's & 1's used to query DD\n\tinputs = new int[Cudd_ReadSize(ddman)];\n\t\n\tfor (j = 0; j < Cudd_ReadSize(ddman); j++) {\n\t\tinputs[j] = 0;\n\t}\n\t\t\n\tlength = (long)pow(2.0, num_vars);\n\n\tfor (i = 0; i < length; i++) {\n\t\tfor (j = 0; j < num_vars; j++) {\t\t\t\n\t\t\tinputs[vars[j]->index] = ((i & (1l<<(num_vars-j-1))) == 0) ? 0 : 1;\n\t\t}\n\t\tnode = Cudd_Eval(ddman, dd, inputs);\n\t\tif (node == NULL) {\n\t\t\tDD_SetErrorFlag();\n\t\t\treturn;\n\t\t}\n\t\tval = Cudd_V(node);\n\t\tswitch (accuracy) {\n\t\tcase ACCURACY_ZERO_ONE: fprintf(dd_out, \"%c\", val>0?'1':'0'); break;\n\t\tcase ACCURACY_LOW: fprintf(dd_out, \"%.2f \", val); break;\n\t\tcase ACCURACY_NORMAL: fprintf(dd_out, \"%f \", val); break;\n\t\tcase ACCURACY_HIGH: fprintf(dd_out, \"%.10f \", val); break;\n\t\tcase ACCURACY_LIST: if (val>0) fprintf(dd_out, \"%ld:%f \", i, val); break;\n\t\t}\n\t}\n\tfprintf(dd_out, \"\\n\");\n\t\n\tif (inputs != NULL) {\n\t\tdelete[] inputs;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintMatrix\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars\n)\n{\n\tDD_PrintMatrix(ddman, dd, rvars, num_rvars, cvars, num_cvars, ACCURACY_NORMAL);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintMatrix\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **rvars,\nint num_rvars,\nDdNode **cvars,\nint num_cvars,\nint accuracy\n)\n{\n\tint i, j, rows, cols;\n\tint k;\n\tDdNode *node;\n\tint *inputs;\n\tdouble val;\n\n\t// create array to store 0's & 1's used to query DD\n\tinputs = new int[Cudd_ReadSize(ddman)];\n\t\n\tfor (k = 0; k < Cudd_ReadSize(ddman); k++) {\n\t\tinputs[k] = 0;\n\t}\n\t\t\n\trows = (long)pow(2.0, num_rvars);\n\tcols = (long)pow(2.0, num_cvars);\n\t\n\tfor (i = 0; i < rows; i++) {\n\t\tfor (j = 0; j < cols; j++) {\n\t\t\tfor (k = 0; k < num_rvars; k++) {\t\t\t\n\t\t\t\tinputs[rvars[k]->index] = ((i & (1l<<(num_rvars-k-1))) == 0) ? 0 : 1;\n\t\t\t}\n\t\t\tfor (k = 0; k < num_cvars; k++) {\t\t\t\n\t\t\t\tinputs[cvars[k]->index] = ((j & (1l<<(num_cvars-k-1))) == 0) ? 0 : 1;\n\t\t\t}\n\t\t\tnode = Cudd_Eval(ddman, dd, inputs);\n\t\t\tif (node == NULL) {\n\t\t\t\tDD_SetErrorFlag();\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tval = Cudd_V(node);\n\t\t\tswitch (accuracy) {\n\t\t\tcase ACCURACY_ZERO_ONE: fprintf(dd_out, \"%c\", val>0?'1':'0'); break;\n\t\t\tcase ACCURACY_LOW: fprintf(dd_out, \"%.2f \", val); break;\n\t\t\tcase ACCURACY_NORMAL: fprintf(dd_out, \"%f \", val); break;\n\t\t\tcase ACCURACY_HIGH: fprintf(dd_out, \"%.10f \", val); break;\n\t\t\tcase ACCURACY_LIST: if (val>0) fprintf(dd_out, \"%d,%d:%f \", i, j, val); break;\n\t\t\t}\n\t\t}\n\t\tif (accuracy != ACCURACY_LIST) fprintf(dd_out, \"\\n\");\n\t}\n\t\n\tif (inputs != NULL) {\n\t\tdelete[] inputs;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintVectorFiltered\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode *filter,\nDdNode **vars,\nint num_vars\n)\n{\n\tDD_PrintVectorFiltered(ddman, dd, filter, vars, num_vars, ACCURACY_NORMAL);\n}\n\n//------------------------------------------------------------------------------\n\nvoid DD_PrintVectorFiltered\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode *filter,\nDdNode **vars,\nint num_vars,\nint accuracy\n)\n{\n\tint j;\n\tlong i, length, count;\n\tDdNode *node;\n\tint *inputs;\n\tdouble val;\n\n\t// create array to store 0's & 1's used to query DD\n\tinputs = new int[Cudd_ReadSize(ddman)];\n\t\n\tfor (j = 0; j < Cudd_ReadSize(ddman); j++) {\n\t\tinputs[j] = 0;\n\t}\n\t\t\n\tlength = (long)pow(2.0, num_vars);\n\n\tcount = -1;\n\tfor (i = 0; i < length; i++) {\n\t\t// only print elements which get thru filter\n\t\tif (DD_GetVectorElement(ddman, filter, vars, num_vars, i) > 0) {\n\t\t\tcount++;\n\t\t\tfor (j = 0; j < num_vars; j++) {\t\t\t\n\t\t\t\tinputs[vars[j]->index] = ((i & (1l<<(num_vars-j-1))) == 0) ? 0 : 1;\n\t\t\t}\n\t\t\tnode = Cudd_Eval(ddman, dd, inputs);\n\t\t\tif (node == NULL) {\n\t\t\t\tDD_SetErrorFlag();\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tval = Cudd_V(node);\n\t\t\tswitch (accuracy) {\n\t\t\tcase ACCURACY_ZERO_ONE: fprintf(dd_out, \"%c\", val>0?'1':'0'); break;\n\t\t\tcase ACCURACY_LOW: fprintf(dd_out, \"%.2f \", val); break;\n\t\t\tcase ACCURACY_NORMAL: fprintf(dd_out, \"%f \", val); break;\n\t\t\tcase ACCURACY_HIGH: fprintf(dd_out, \"%.10f \", val); break;\n\t\t\tcase ACCURACY_LIST: if (val>0) fprintf(dd_out, \"%ld:%f \", count, val); break;\n\t\t\t}\n\t\t}\n\t}\n\tfprintf(dd_out, \"\\n\");\n\t\n\tif (inputs != NULL) {\n\t\tdelete[] inputs;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dd/dd_term.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: DD functions on terminals\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n#include \"dd_basics.h\"\n#include \"dd_term.h\"\n#include \"dd_export.h\"\n#include \"dd_cudd.h\"\n#include <limits>  // for NaN value\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Threshold\n(\nDdManager *ddman,\nDdNode *dd,\ndouble threshold\n)\n{\n\tDdNode *tmp, *tmp2;\n\n\tif (dd == NULL) return NULL;\n\n\ttmp = Cudd_addBddThreshold(ddman, dd, threshold);\n\tif (tmp == NULL) return NULL;\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDeref(ddman, dd);\n\ttmp2 = Cudd_BddToAdd(ddman, tmp);\t\n\tCudd_Ref(tmp2);\t\n\tCudd_RecursiveDeref(ddman, tmp);\n\t\n\treturn tmp2;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_StrictThreshold\n(\nDdManager *ddman,\nDdNode *dd,\ndouble threshold\n)\n{\n\tDdNode *tmp, *tmp2;\n\n\tif (dd == NULL) return NULL;\n\n\ttmp = Cudd_addBddStrictThreshold(ddman, dd, threshold);\n\tif (tmp == NULL) return NULL;\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDeref(ddman, dd);\n\ttmp2 = Cudd_BddToAdd(ddman, tmp);\t\n\tCudd_Ref(tmp2);\t\n\tCudd_RecursiveDeref(ddman, tmp);\n\t\n\treturn tmp2;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_GreaterThan\n(\nDdManager *ddman,\nDdNode *dd,\ndouble threshold\n)\n{\n\treturn DD_StrictThreshold(ddman, dd, threshold);\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_GreaterThanEquals\n(\nDdManager *ddman,\nDdNode *dd,\ndouble threshold\n)\n{\n\treturn DD_Threshold(ddman, dd, threshold);\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_LessThan\n(\nDdManager *ddman,\nDdNode *dd,\ndouble threshold\n)\n{\n\tDdNode* res;\n\n\tif (dd == NULL) return NULL;\n\n\tres = DD_Threshold(ddman, dd, threshold);\n\tif (res == NULL) return NULL;\n\treturn DD_Not(ddman, res);\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_LessThanEquals\n(\nDdManager *ddman,\nDdNode *dd,\ndouble threshold\n)\n{\n\tDdNode* res;\n\n\tif (dd == NULL) return NULL;\n\n\tres = DD_StrictThreshold(ddman, dd, threshold);\n\tif (res == NULL) return NULL;\n\treturn DD_Not(ddman, res);\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Equals\n(\nDdManager *ddman,\nDdNode *dd,\ndouble value\n)\n{\n\treturn DD_Interval(ddman, dd, value, value);\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_Interval\n(\nDdManager *ddman,\nDdNode *dd,\ndouble lower,\ndouble upper\n)\n{\n\tDdNode *tmp, *tmp2;\n\n\tif (dd == NULL) return NULL;\n\n\ttmp = Cudd_addBddInterval(ddman, dd, lower, upper);\n\tif (tmp == NULL) return NULL;\n\tCudd_Ref(tmp);\n\tCudd_RecursiveDeref(ddman, dd);\n\ttmp2 = Cudd_BddToAdd(ddman, tmp);\n\tif (tmp2 == NULL) return NULL;\n\tCudd_Ref(tmp2);\n\tCudd_RecursiveDeref(ddman, tmp);\n\n\treturn tmp2;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_RoundOff\n(\nDdManager *ddman,\nDdNode *dd,\nint places\n)\n{\n\tDdNode *res;\n\n\tif (dd == NULL) return NULL;\n\n\tres = Cudd_addRoundOff(ddman, dd, places);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nbool DD_EqualSupNorm\n(\nDdManager *ddman,\nDdNode *dd1,\nDdNode *dd2,\ndouble epsilon\n)\n{\n\tif (Cudd_EqualSupNorm(ddman, dd1, dd2, epsilon, 0)) {\n\t\treturn true;\n\t}\n\treturn false;\n}\t\n\n//------------------------------------------------------------------------------\n\nbool DD_EqualSupNormRel\n(\nDdManager *ddman,\nDdNode *dd1,\nDdNode *dd2,\ndouble epsilon\n)\n{\n\tif (Cudd_EqualSupNormRel(ddman, dd1, dd2, epsilon, 0)) {\n\t\treturn true;\n\t}\n\treturn false;\n}\t\n\n//------------------------------------------------------------------------------\n\ndouble DD_FindMin\n(\nDdManager *ddman,\nDdNode *dd\t\n)\n{\n\tDdNode *v = Cudd_addFindMin(ddman, dd);\n\tif (v == NULL) {\n\t\tDD_SetErrorFlag();\n\t\treturn std::numeric_limits<double>::quiet_NaN();\n\t}\n\treturn Cudd_V(v);\n}\n\n//------------------------------------------------------------------------------\n\n// Find minimal terminal node (constant) that is greater than zero\ndouble DD_FindMinPositive\n(\nDdManager *ddman,\nDdNode *dd\n)\n{\n\tDdGen *gen;\n\tDdNode *node;\n\tbool rv = true;\n\n\tdouble min_v = std::numeric_limits<double>::infinity();\n\n\tCudd_ForeachNode(ddman, dd, gen, node) {\n\t\tif (Cudd_IsConstant(node)) {\n\t\t\tdouble v = Cudd_V(node);\n\t\t\tif (v > 0 && v < min_v) {\n\t\t\t\tmin_v = v;\n\t\t\t}\n\t\t}\n\t}\n\n\treturn min_v;\n}\n\n//------------------------------------------------------------------------------\n\n// Find maximal finite terminal node (constant). Returns -infinity if there is none\ndouble DD_FindMaxFinite\n(\nDdManager *ddman,\nDdNode *dd\n)\n{\n\tDdGen *gen;\n\tDdNode *node;\n\tbool rv = true;\n\n\tdouble max_v = -std::numeric_limits<double>::infinity();\n\n\tCudd_ForeachNode(ddman, dd, gen, node) {\n\t\tif (Cudd_IsConstant(node)) {\n\t\t\tdouble v = Cudd_V(node);\n\t\t\tif (v < std::numeric_limits<double>::infinity() && v > max_v) {\n\t\t\t\tmax_v = v;\n\t\t\t}\n\t\t}\n\t}\n\n\treturn max_v;\n}\n\n//------------------------------------------------------------------------------\n\ndouble DD_FindMax\n(\nDdManager *ddman,\nDdNode *dd\t\n)\n{\n\tDdNode *v = Cudd_addFindMax(ddman, dd);\n\tif (v == NULL) {\n\t\tDD_SetErrorFlag();\n\t\treturn std::numeric_limits<double>::quiet_NaN();\n\t}\n\treturn Cudd_V(v);\n}\n\n\n//------------------------------------------------------------------------------\n\nbool DD_IsZeroOneMTBDD\n(\nDdManager *ddman,\nDdNode *dd\n)\n{\n\tDdGen *gen;\n\tDdNode *node;\n\tbool rv = true;\n\n\tCudd_ForeachNode(ddman, dd, gen, node) {\n\t\tif (Cudd_IsConstant(node)) {\n\t\t\tif (node != Cudd_ReadOne(ddman) && node != Cudd_ReadZero(ddman)) {\n\t\t\t\trv = false;\n\t\t\t\t// we could break here, as it's clear that we are done\n\t\t\t\t// however, it looks like CUDD would then not free the\n\t\t\t\t// DdGen* gen\n\t\t\t}\n\t\t}\n\t}\n\n\treturn rv;\n}\n\n//------------------------------------------------------------------------------\n\nDdNode *DD_RestrictToFirst\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **vars,\nint num_vars\n)\n{\n\tint i;\n\tDdNode *ptr, *next_ptr, *filter, *res;\n\n\tif (dd == NULL) return NULL;\n\n\t// construct filter to get first non-zero element\n\tptr = dd;\n\tfilter = DD_Constant(ddman, 1);\n\tif (filter == NULL) return NULL;\n\tfor (i = 0; i < num_vars; i++) {\n\t\tnext_ptr = (Cudd_NodeReadIndex(ptr) > Cudd_NodeReadIndex(vars[i])) ? ptr : Cudd_E(ptr);\n\t\tif (next_ptr != Cudd_ReadZero(ddman)) {\n\t\t\tCudd_Ref(vars[i]);\n\t\t\tfilter = DD_And(ddman, filter, DD_Not(ddman, vars[i]));\n\t\t\tif (filter == NULL) return NULL;\n\t\t}\n\t\telse {\n\t\t\tnext_ptr = (Cudd_NodeReadIndex(ptr) > Cudd_NodeReadIndex(vars[i])) ? ptr : Cudd_T(ptr);\n\t\t\tCudd_Ref(vars[i]);\n\t\t\tfilter = DD_And(ddman, filter, vars[i]);\n\t\t\tif (filter == NULL) return NULL;\n\t\t}\n\t\tptr = next_ptr;\n\t}\n\t\n\t// filter\n\tres = DD_Apply(ddman, APPLY_TIMES, dd, filter);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dd/dd_test.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: Small test program\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <cstdio>\n\n#include <util.h>\n#include <cudd.h>\n#include \"dd.h\"\n\nint main()\n{\n\tDdManager *ddman;\n\tDdNode *a, *b, *c;\n\tDdNode **vars;\n\t\n\tprintf(\"\\nTest program for DD\\n===================\\n\");\n\t\n\t// initialise cudd\n\tddman = DD_InitialiseCUDD();\n\t\n\t// set up some variables\n\tvars = new DdNode*[2];\n\tvars[0] = DD_Var(ddman, 0);\n\tvars[1] = DD_Var(ddman, 2);\n\t\n\t// blank dd\n\ta = DD_Create(ddman);\n\tprintf(\"\\nCreate()\\n\");\n\tDD_PrintVector(ddman, a, vars, 2);\n\tCudd_RecursiveDeref(ddman, a);\n\n\t// constant\n\ta = DD_Constant(ddman, 1.5);\n\tprintf(\"\\nConstant(1.5)\\n\");\n\tDD_PrintVector(ddman, a, vars, 2);\n\tCudd_RecursiveDeref(ddman, a);\n\n\t// plus infinity\n\ta = DD_PlusInfinity(ddman);\n\tprintf(\"\\nPlusInfinity()\\n\");\n\tDD_PrintVector(ddman, a, vars, 2);\n\tCudd_RecursiveDeref(ddman, a);\n\n\t// minus infinity\n\ta = DD_MinusInfinity(ddman);\n\tprintf(\"\\nMinusInfinity()\\n\");\n\tDD_PrintVector(ddman, a, vars, 2);\n\tCudd_RecursiveDeref(ddman, a);\n\n\t// var\n\ta = DD_Var(ddman, 0);\n\tprintf(\"\\nVar(0)\\n\");\n\tDD_PrintVector(ddman, a, vars, 2);\n\tCudd_RecursiveDeref(ddman, a);\n\n\ta = DD_Var(ddman, 0);\n\tb = DD_Var(ddman, 2);\n\tprintf(\"\\na: \");\n\tDD_PrintVector(ddman, a, vars, 2);\n\tprintf(\"b: \");\n\tDD_PrintVector(ddman, b, vars, 2);\n\n\t// not\n\tCudd_Ref(a);\n\tc = DD_Not(ddman, a);\n\tprintf(\"\\nNot(a)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\n\t// or\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\tc = DD_Or(ddman, a, b);\n\tprintf(\"\\nOr(a, b)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\n\t// and\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\tc = DD_And(ddman, a, b);\n\tprintf(\"\\nAnd(a, b)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\n\t// xor\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\tc = DD_Xor(ddman, a, b);\n\tprintf(\"\\nXor(a, b)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\n\t// implies\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\tc = DD_Implies(ddman, a, b);\n\tprintf(\"\\nImplies(a, b)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, b);\n\n\ta = DD_Create(ddman);\n\ta = DD_SetVectorElement(ddman, a, vars, 2, 0, 1);\n\ta = DD_SetVectorElement(ddman, a, vars, 2, 1, 2);\n\ta = DD_SetVectorElement(ddman, a, vars, 2, 2, 3);\n\ta = DD_SetVectorElement(ddman, a, vars, 2, 3, 4);\n\tb = DD_Create(ddman);\n\tb = DD_SetVectorElement(ddman, b, vars, 2, 0, 0);\n\tb = DD_SetVectorElement(ddman, b, vars, 2, 1, 2);\n\tb = DD_SetVectorElement(ddman, b, vars, 2, 2, 4);\n\tb = DD_SetVectorElement(ddman, b, vars, 2, 3, 6);\n\tprintf(\"\\na: \");\n\tDD_PrintVector(ddman, a, vars, 2);\n\tprintf(\"b: \");\n\tDD_PrintVector(ddman, b, vars, 2);\n\n\t// apply\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\tc = DD_Apply(ddman, APPLY_PLUS, a, b);\n\tprintf(\"\\nApply(+, a, b)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\tc = DD_Apply(ddman, APPLY_MINUS, a, b);\n\tprintf(\"\\nApply(-, a, b)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\tc = DD_Apply(ddman, APPLY_TIMES, a, b);\n\tprintf(\"\\nApply(*, a, b)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\tc = DD_Apply(ddman, APPLY_DIVIDE, a, b);\n\tprintf(\"\\nApply(/, a, b)\\n\");\n\tDD_PrintVector(ddman, c, vars, 2);\n\tCudd_RecursiveDeref(ddman, c);\n\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, b);\n\n\t// dereference variables\n\tCudd_RecursiveDeref(ddman,vars[0]);\n\tCudd_RecursiveDeref(ddman,vars[1]);\n\n\t// close down cudd\n\tDD_CloseDownCUDD(ddman);\n\tprintf(\"\\n\");\n}\n"
  },
  {
    "path": "prism/src/dd/dd_vars.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: DD variable functions\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <util.h>\n#include <cudd.h>\n#include \"dd_vars.h\"\n#include \"dd_basics.h\"\n\n//------------------------------------------------------------------------------\n\n// note: this PERMUTES variables (i.e. x_i -> y_i) cf. DD_SwapVariables\n\nDdNode *DD_PermuteVariables\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **old_vars,\nDdNode **new_vars,\nint num_vars\n)\n{\n\tint i, *permut;\n\tDdNode *res;\n\n\tif (dd == NULL) return NULL;\n\n\tpermut = new int[Cudd_ReadSize(ddman)];\n\tfor (i = 0; i < Cudd_ReadSize(ddman); i++) {\n\t\tpermut[i] = i;\n\t}\n\tfor (i = 0; i < num_vars; i++) {\n\t\tpermut[Cudd_NodeReadIndex(old_vars[i])] = Cudd_NodeReadIndex(new_vars[i]);\n\t}\t\n\tres = Cudd_addPermute(ddman, dd, permut);\t\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\n\tif (permut != NULL) {\n\t\tdelete[] permut;\n\t}\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\n// note: this SWAPS variables (i.e. x_i <-> y_i) cf. DD_PermuteVariables\n\nDdNode *DD_SwapVariables\n(\nDdManager *ddman,\nDdNode *dd,\nDdNode **old_vars,\nDdNode **new_vars,\nint num_vars\n)\n{\n\tDdNode *res;\n\n\tif (dd == NULL) return NULL;\n\n\tres = Cudd_addSwapVariables(ddman, dd, old_vars, new_vars, num_vars);\n\tif (res != NULL) Cudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, dd);\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\n// Generates BDD for the function x > y\n// where x, y are num_vars-bit numbers encoded by variables x_vars, y_vars\n\nDdNode *DD_VariablesGreaterThan\n(\nDdManager *ddman,\nDdNode **x_vars,\nDdNode **y_vars,\nint num_vars\n)\n{\n\tDdNode *tmp, *res;\n\tDdNode **x_bdd_vars, **y_bdd_vars;\n\tint i;\n\t\n\t// create bdd vars from add vars\n\tx_bdd_vars = new DdNode*[num_vars];\n\ty_bdd_vars = new DdNode*[num_vars];\n\tfor (i = 0; i < num_vars; i++) {\n\t\tx_bdd_vars[i] = Cudd_bddIthVar(ddman, Cudd_NodeReadIndex(x_vars[i]));\n\t\tif (x_bdd_vars[i] == NULL) return NULL;\n\t\tCudd_Ref(x_bdd_vars[i]);\n\t\ty_bdd_vars[i] = Cudd_bddIthVar(ddman, Cudd_NodeReadIndex(y_vars[i]));\n\t\tif (y_bdd_vars[i] == NULL) return NULL;\n\t\tCudd_Ref(y_bdd_vars[i]);\n\t}\n\t// call main function\n\ttmp = Cudd_Xgty(ddman, num_vars, NULL, x_bdd_vars, y_bdd_vars);\n\tif (tmp == NULL) return NULL;\n\tCudd_Ref(tmp);\n\t// convert bdd to add\n\tres = Cudd_BddToAdd(ddman, tmp);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, tmp);\n\t// free variables\n\tfor (i = 0; i < num_vars; i++) {\n\t\tCudd_RecursiveDeref(ddman, x_bdd_vars[i]);\n\t\tCudd_RecursiveDeref(ddman, y_bdd_vars[i]);\n\t}\n\tdelete[] x_bdd_vars;\n\tdelete[] y_bdd_vars;\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\n// Generates BDD for the function x >= y\n// where x, y are num_vars-bit numbers encoded by variables x_vars, y_vars\n\nDdNode *DD_VariablesGreaterThanEquals\n(\nDdManager *ddman,\nDdNode **x_vars,\nDdNode **y_vars,\nint num_vars\n)\n{\n\tDdNode* res = DD_VariablesLessThan(ddman, x_vars, y_vars, num_vars);\n\tif (res == NULL) return NULL;\n\treturn DD_Not(ddman, res);\n}\n\n//------------------------------------------------------------------------------\n\n// Generates BDD for the function x < y\n// where x, y are num_vars-bit numbers encoded by variables x_vars, y_vars\n\nDdNode *DD_VariablesLessThan\n(\nDdManager *ddman,\nDdNode **x_vars,\nDdNode **y_vars,\nint num_vars\n)\n{\n\tDdNode *tmp, *res;\n\tDdNode **x_bdd_vars, **y_bdd_vars;\n\tint i;\n\t\n\t// create bdd vars from add vars\n\tx_bdd_vars = new DdNode*[num_vars];\n\ty_bdd_vars = new DdNode*[num_vars];\n\tfor (i = 0; i < num_vars; i++) {\n\t\tx_bdd_vars[i] = Cudd_bddIthVar(ddman, Cudd_NodeReadIndex(x_vars[i]));\n\t\tif (x_bdd_vars[i] == NULL) return NULL;\n\t\tCudd_Ref(x_bdd_vars[i]);\n\t\ty_bdd_vars[i] = Cudd_bddIthVar(ddman, Cudd_NodeReadIndex(y_vars[i]));\n\t\tif (y_bdd_vars[i] == NULL) return NULL;\n\t\tCudd_Ref(y_bdd_vars[i]);\n\t}\n\t// call main function\n\ttmp = Cudd_Xgty(ddman, num_vars, NULL, y_bdd_vars, x_bdd_vars);\n\tif (tmp == NULL) return NULL;\n\tCudd_Ref(tmp);\n\t// convert bdd to add\n\tres = Cudd_BddToAdd(ddman, tmp);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, tmp);\n\t// free variables\n\tfor (i = 0; i < num_vars; i++) {\n\t\tCudd_RecursiveDeref(ddman, x_bdd_vars[i]);\n\t\tCudd_RecursiveDeref(ddman, y_bdd_vars[i]);\n\t}\n\tdelete[] x_bdd_vars;\n\tdelete[] y_bdd_vars;\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\n// Generates BDD for the function x <= y\n// where x, y are num_vars-bit numbers encoded by variables x_vars, y_vars\n\nDdNode *DD_VariablesLessThanEquals\n(\nDdManager *ddman,\nDdNode **x_vars,\nDdNode **y_vars,\nint num_vars\n)\n{\n\tDdNode* res = DD_VariablesGreaterThan(ddman, x_vars, y_vars, num_vars);\n\treturn DD_Not(ddman, res);\n}\n\n//------------------------------------------------------------------------------\n\n// Generates BDD for the function x == y\n// where x, y are num_vars-bit numbers encoded by variables x_vars, y_vars\n\nDdNode *DD_VariablesEquals\n(\nDdManager *ddman,\nDdNode **x_vars,\nDdNode **y_vars,\nint num_vars\n)\n{\n\tDdNode *tmp, *res;\n\tDdNode **x_bdd_vars, **y_bdd_vars;\n\tint i;\n\t\n\t// create bdd vars from add vars\n\tx_bdd_vars = new DdNode*[num_vars];\n\ty_bdd_vars = new DdNode*[num_vars];\n\tfor (i = 0; i < num_vars; i++) {\n\t\tx_bdd_vars[i] = Cudd_bddIthVar(ddman, Cudd_NodeReadIndex(x_vars[i]));\n\t\tif (x_bdd_vars[i] == NULL) return NULL;\n\t\tCudd_Ref(x_bdd_vars[i]);\n\t\ty_bdd_vars[i] = Cudd_bddIthVar(ddman, Cudd_NodeReadIndex(y_vars[i]));\n\t\tif (y_bdd_vars[i] == NULL) return NULL;\n\t\tCudd_Ref(y_bdd_vars[i]);\n\t}\n\t// call main function\n\ttmp = Cudd_Xeqy(ddman, num_vars, x_bdd_vars, y_bdd_vars);\n\tif (tmp == NULL) return NULL;\n\tCudd_Ref(tmp);\n\t// convert bdd to add\n\tres = Cudd_BddToAdd(ddman, tmp);\n\tif (res == NULL) return NULL;\n\tCudd_Ref(res);\n\tCudd_RecursiveDeref(ddman, tmp);\n\t// free variables\n\tfor (i = 0; i < num_vars; i++) {\n\t\tCudd_RecursiveDeref(ddman, x_bdd_vars[i]);\n\t\tCudd_RecursiveDeref(ddman, y_bdd_vars[i]);\n\t}\n\tdelete[] x_bdd_vars;\n\tdelete[] y_bdd_vars;\n\t\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dv/DoubleVector.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: C++ code for double vector\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"dv.h\"\n#include \"DoubleVector.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n#include <cmath>\n#include <new>\n\n//------------------------------------------------------------------------------\n// DoubleVector methods\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1CreateZeroVector\n(\nJNIEnv *env,\njobject obj,\njint n\n)\n{\n\tdouble *vector;\n\tint i;\n\ttry {\n\t\tvector = new double[n];\n\t} catch (std::bad_alloc e) {\n\t\treturn 0;\n\t}\n\tfor (i = 0; i < n; i++) {\n\t\tvector[i] = 0;\n\t}\n\t\n\treturn ptr_to_jlong(vector);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1ConvertMTBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer dd,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tmtbdd_to_double_vector(\n\t\t\tddman,\n\t\t\tjlong_to_DdNode(dd),\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1GetElement\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njint i\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\treturn (jdouble)vector[i];\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1SetElement\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njint i,\njdouble d\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\tvector[i] = d;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1SetAllElements\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njdouble d\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\tfor(int i = 0; i < n; i++)\n\t\tvector[i] = d;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1RoundOff\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njint places\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\tdouble trunc, d;\n\tint i, j;\n\n\ttrunc = pow(10.0, places);\n\tfor (i = 0; i < n; i++) {\n\t\td = trunc * vector[i];\n\t\tj = (int)floor(d);\n\t\tif (d-j >= 0.5) j += 1;\n\t\tvector[i] = j / trunc;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1SubtractFromOne\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\tint i;\n\n\tfor (i = 0; i < n; i++) {\n\t\tvector[i] = 1.0 - vector[i];\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1Add\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njlong __jlongpointer v2\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\tdouble *vector2 = jlong_to_double(v2);\n\tint i;\n\n\tfor (i = 0; i < n; i++) {\n\t\tvector[i] += vector2[i];\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1TimesConstant\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njdouble d\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\tint i;\n\n\tfor (i = 0; i < n; i++) {\n\t\tvector[i] *= d;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1DotProduct\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njlong __jlongpointer v2\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\tdouble *vector2 = jlong_to_double(v2);\n\tint i;\n\tdouble d = 0.0;\n\n\tfor (i = 0; i < n; i++) {\n\t\td += vector[i] * vector2[i];\n\t}\n\t\n\treturn d;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1Filter\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer filter,\njdouble d,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\tfilter_double_vector(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_DdNode(filter),\n\t\td,\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1MaxMTBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer vector2,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\tmax_double_vector_mtbdd(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_DdNode(vector2),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1Clear\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector\n)\n{\n\t// note we assume that this memory was created with new\n\tdelete jlong_to_double(vector);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_dv_DoubleVector_DV_1GetNNZ\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n\n)\n{\n\tdouble *vector = jlong_to_double(v);\n\tint i, count;\n\t\n\tcount = 0;\n\tfor (i = 0; i < n; i++) {\n\t\tif (vector[i] != 0) count++;\n\t}\n\t\n\treturn count;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1FirstFromBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer filter,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn (jdouble)get_first_from_bdd(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_DdNode(filter),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1MinOverBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer filter,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn (jdouble)min_double_vector_over_bdd(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_DdNode(filter),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1MaxOverBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer filter,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn (jdouble)max_double_vector_over_bdd(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_DdNode(filter),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1MaxFiniteOverBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer filter,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn (jdouble)max_finite_double_vector_over_bdd(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_DdNode(filter),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1SumOverBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer filter,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn (jdouble)sum_double_vector_over_bdd(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_DdNode(filter),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_dv_DoubleVector_DV_1SumOverMTBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer mult,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn (jdouble)sum_double_vector_over_mtbdd(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_DdNode(mult),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_DoubleVector_DV_1SumOverDDVars\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer vector2,\njlong __jlongpointer vars,\njint num_vars,\njint first_var,\njint last_var,\njlong __jlongpointer odd,\njlong __jlongpointer odd2\n)\n{\n\tsum_double_vector_over_dd_vars(\n\t\tddman,\n\t\tjlong_to_double(vector),\n\t\tjlong_to_double(vector2),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tfirst_var, last_var,\n\t\tjlong_to_ODDNode(odd),\n\t\tjlong_to_ODDNode(odd2)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1BDDGreaterThanEquals\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njdouble bound,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tdouble_vector_to_bdd(\n\t\t\tddman,\n\t\t\tjlong_to_double(vector),\n\t\t\tDV_GREATER_THAN_EQUALS,\n\t\t\tbound,\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong JNICALL Java_dv_DoubleVector_DV_1BDDGreaterThan\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njdouble bound,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tdouble_vector_to_bdd(\n\t\t\tddman,\n\t\t\tjlong_to_double(vector),\n\t\t\tDV_GREATER_THAN,\n\t\t\tbound,\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1BDDLessThanEquals\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njdouble bound,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tdouble_vector_to_bdd(\n\t\t\tddman,\n\t\t\tjlong_to_double(vector),\n\t\t\tDV_LESS_THAN_EQUALS,\n\t\t\tbound,\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1BDDLessThan\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njdouble bound,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tdouble_vector_to_bdd(\n\t\t\tddman,\n\t\t\tjlong_to_double(vector),\n\t\t\tDV_LESS_THAN,\n\t\t\tbound,\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1BDDInterval\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njdouble lo,\njdouble hi,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tdouble_vector_to_bdd(\n\t\t\tddman,\n\t\t\tjlong_to_double(vector),\n\t\t\tDV_INTERVAL,\n\t\t\tlo, hi,\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1BDDCloseValueAbs\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njdouble value,\njdouble epsilon,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tdouble_vector_to_bdd(\n\t\t\tddman,\n\t\t\tjlong_to_double(vector),\n\t\t\tDV_CLOSE_ABS,\n\t\t\tvalue, epsilon,\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1BDDCloseValueRel\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njdouble value,\njdouble epsilon,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tdouble_vector_to_bdd(\n\t\t\tddman,\n\t\t\tjlong_to_double(vector),\n\t\t\tDV_CLOSE_REL,\n\t\t\tvalue, epsilon,\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_DoubleVector_DV_1ConvertToMTBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tdouble_vector_to_mtbdd(\n\t\t\tddman,\n\t\t\tjlong_to_double(vector),\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dv/DoubleVector.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage dv;\n\nimport parser.ast.RelOp;\nimport prism.*;\nimport jdd.*;\nimport odd.*;\n\n/**\n * Class to encapsulate a vector of doubles, stored natively.\n */\npublic class DoubleVector\n{\n\t//------------------------------------------------------------------------------\n\t// Load JNI stuff from shared library\n\t//------------------------------------------------------------------------------\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\t\n\t//------------------------------------------------------------------------------\n\t// Instance variables/methods\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Vector contents (C/C++ pointer cast to a long)\n\t */\n\tprivate long v;\n\t/**\n\t * Size of vector\n\t */\n\tprivate int n;\n\t\n\t// Constructors\n\t\n\t/**\n\t * Create a new DoubleVector of size {@code size} with all entries set to 0.\n\t * @throws PrismException if there is insufficient memory to create the array.\n\t */\n\tpublic DoubleVector(int size) throws PrismException\n\t{\n\t\tv = DV_CreateZeroVector(size);\n\t\tif (v == 0) throw new PrismException(\"Out of memory\");\n\t\tn = size;\n\t}\n\t\n\tprivate native long DV_CreateZeroVector(int n);\n\t\n\t/**\n\t * Create a new DoubleVector from a pointer {@code vect} to an existing native double array of size {@code size}.\n\t */\n\tpublic DoubleVector(long vector, int size)\n\t{\n\t\tv = vector;\n\t\tn = size;\n\t}\n\t\n\t/**\n\t * Create a new DoubleVector from an existing MTBDD representation of an array.\n\t * <br>[ DEREFS: <i>none</i> ]\n\t * @throws PrismException if number of states is too large (uses Java int based indices)\n\t */\n\tpublic DoubleVector(JDDNode dd, JDDVars vars, ODDNode odd) throws PrismException\n\t{\n\t\tODDUtils.checkInt(odd, \"Can not create DoubleVector\");\n\n\t\tv = DV_ConvertMTBDD(dd.ptr(), vars.array(), vars.n(), odd.ptr());\n\t\tn = (int)odd.getNumStates();\n\t}\n\t\n\tprivate native long DV_ConvertMTBDD(long dd, long vars, int num_vars, long odd);\n\n\t// Accessors\n\t\n\t/**\n\t * Get the pointer to the native vector (C/C++ pointer cast to a long).\n\t */\n\tpublic long getPtr()\n\t{\n\t\treturn v;\n\t}\n\n\t/**\n\t * Get the size of the vector.\n\t */\n\tpublic int getSize()\n\t{\n\t\treturn n;\n\t}\n\n\t/**\n\t * Get element {@code i} of the vector.\n\t */\n\tpublic double getElement(int i)\n\t{\n\t\treturn DV_GetElement(v, n, i);\n\t}\n\n\tprivate native double DV_GetElement(long v, int n, int i);\n\t\n\t// Mutators\n\t\n\t/**\n\t * Set element {@code i} of the vector to value {@code d}.\n\t */\n\tpublic void setElement(int i, double d)\n\t{\n\t\tDV_SetElement(v, n, i, d);\n\t}\n\n\tprivate native void DV_SetElement(long v, int n, int i, double d);\n\t\n\t/**\n\t * Set all elements of the vector to the same value {@code d}.\n\t */\n\tpublic void setAllElements(double d)\n\t{\n\t\tDV_SetAllElements(v, n, d);\n\t}\n\n\tprivate native void DV_SetAllElements(long v, int n, double d);\n\t\n\t// round off\n\tprivate native void DV_RoundOff(long v, int n, int places);\n\tpublic void roundOff(int places)\n\t{\n\t\tDV_RoundOff(v, n, places);\n\t}\n\n\t// subtract all values from 1\n\tprivate native void DV_SubtractFromOne(long v, int n);\n\tpublic void subtractFromOne() \n\t{\n\t\tDV_SubtractFromOne(v, n);\n\t}\n\n\t// add another vector to this one\n\tprivate native void DV_Add(long v, int n, long v2);\n\tpublic void add(DoubleVector dv) \n\t{\n\t\tDV_Add(v, n, dv.v);\n\t}\n\n\t// multiply vector by a constant\n\tprivate native void DV_TimesConstant(long v, int n, double d);\n\tpublic void timesConstant(double d) \n\t{\n\t\tDV_TimesConstant(v, n, d);\n\t}\n\n\t// compute dot (inner) product of this and another vector\n\tprivate native double DV_DotProduct(long v, int n, long v2);\n\tpublic double dotProduct(DoubleVector dv) \n\t{\n\t\treturn DV_DotProduct(v, n, dv.v);\n\t}\n\n\n\tprivate native void DV_Filter(long v, long filter, double d, long vars, int num_vars, long odd);\n\t/**\n\t * Filter vector using a bdd (set elements not in filter to d)\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic void filter(JDDNode filter, double d, JDDVars vars, ODDNode odd)\n\t{\n\t\tDV_Filter(v, filter.ptr(), d, vars.array(), vars.n(), odd.ptr());\n\t}\n\n\t/**\n\t * Filter vector using a bdd (set elements not in filter to 0)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic void filter(JDDNode filter, JDDVars vars, ODDNode odd)\n\t{\n\t\tDV_Filter(v, filter.ptr(), 0.0, vars.array(), vars.n(), odd.ptr());\n\t}\n\t\n\t// apply max operator, i.e. v[i] = max(v[i], v2[i]), where v2 is an mtbdd\n\tprivate native void DV_MaxMTBDD(long v, long v2, long vars, int num_vars, long odd);\n\tpublic void maxMTBDD(JDDNode v2, JDDVars vars, ODDNode odd)\n\t{\n\t\tDV_MaxMTBDD(v, v2.ptr(), vars.array(), vars.n(), odd.ptr());\n\t}\n\n\t// clear (free memory)\n\tprivate native void DV_Clear(long v);\n\tpublic void clear() \n\t{\n\t\tDV_Clear(v);\n\t}\n\n\t// get number of non zeros\n\tprivate native int DV_GetNNZ(long v, int n);\n\tpublic int getNNZ()\n\t{\n\t\treturn DV_GetNNZ(v, n);\n\t}\n\n\t// get value of first element in BDD filter\n\tprivate native double DV_FirstFromBDD(long v, long filter, long vars, int num_vars, long odd);\n\tpublic double firstFromBDD(JDDNode filter, JDDVars vars, ODDNode odd)\n\t{\n\t\treturn DV_FirstFromBDD(v, filter.ptr(), vars.array(), vars.n(), odd.ptr());\n\t}\n\t\n\t// get min value over BDD filter\n\tprivate native double DV_MinOverBDD(long v, long filter, long vars, int num_vars, long odd);\n\tpublic double minOverBDD(JDDNode filter, JDDVars vars, ODDNode odd)\n\t{\n\t\treturn DV_MinOverBDD(v, filter.ptr(), vars.array(), vars.n(), odd.ptr());\n\t}\n\t\n\t// get max value over BDD filter\n\tprivate native double DV_MaxOverBDD(long v, long filter, long vars, int num_vars, long odd);\n\tpublic double maxOverBDD(JDDNode filter, JDDVars vars, ODDNode odd)\n\t{\n\t\treturn DV_MaxOverBDD(v, filter.ptr(), vars.array(), vars.n(), odd.ptr());\n\t}\n\n\tprivate native double DV_MaxFiniteOverBDD(long v, long filter, long vars, int num_vars, long odd);\n\tpublic double maxFiniteOverBDD(JDDNode filter, JDDVars vars, ODDNode odd)\n\t{\n\t\treturn DV_MaxOverBDD(v, filter.ptr(), vars.array(), vars.n(), odd.ptr());\n\t}\n\n\t// sum elements of vector according to a bdd (used for csl steady state operator)\n\tprivate native double DV_SumOverBDD(long v, long filter, long vars, int num_vars, long odd);\n\tpublic double sumOverBDD(JDDNode filter, JDDVars vars, ODDNode odd)\n\t{\n\t\treturn DV_SumOverBDD(v, filter.ptr(), vars.array(), vars.n(), odd.ptr());\n\t}\n\t\n\t// do a weighted sum of the elements of a double array and the values the mtbdd passed in\n\t// (used for csl reward steady state operator)\n\tprivate native double DV_SumOverMTBDD(long v, long mult, long vars, int num_vars, long odd);\n\tpublic double sumOverMTBDD(JDDNode mult, JDDVars vars, ODDNode odd)\n\t{\n\t\treturn DV_SumOverMTBDD(v, mult.ptr(), vars.array(), vars.n(), odd.ptr());\n\t}\n\t\n\t// sum up the elements of a double array, over a subset of its dd vars\n\t// the dd var subset must be a continuous range of vars, identified by indices: first_var, last_var\n\t// store the result in a new DoubleVector (whose indices are given by odd2)\n\tprivate native void DV_SumOverDDVars(long vec, long vec2, long vars, int num_vars, int first_var, int last_var, long odd, long odd2);\n\t// throws PrismException on out-of-memory\n\tpublic DoubleVector sumOverDDVars(JDDVars vars, ODDNode odd, ODDNode odd2, int first_var, int last_var) throws PrismException\n\t{\n\t\tDoubleVector dv2 = new DoubleVector((int)(odd2.getEOff() + odd2.getTOff()));\n\t\tDV_SumOverDDVars(v, dv2.v, vars.array(), vars.n(), first_var, last_var, odd.ptr(), odd2.ptr());\n\t\treturn dv2;\n\t}\n\t\n\t/**\n\t * \tGenerate BDD for states in the given interval\n\t * (interval specified as relational operator and bound)\n\t */\n\tpublic JDDNode getBDDFromInterval(String relOpString, double bound, JDDVars vars, ODDNode odd)\n\t{\n\t\treturn getBDDFromInterval(RelOp.parseSymbol(relOpString), bound, vars, odd);\n\t}\n\t\n\t/**\n\t * \tGenerate BDD for states in the given interval\n\t * (interval specified as relational operator and bound)\n\t */\n\tpublic JDDNode getBDDFromInterval(RelOp relOp, double bound, JDDVars vars, ODDNode odd)\n\t{\n\t\tJDDNode sol = null;\n\t\t\n\t\tswitch (relOp) {\n\t\tcase GEQ:\n\t\t\tsol = JDD.ptrToNode(\n\t\t\t\tDV_BDDGreaterThanEquals(v, bound, vars.array(), vars.n(), odd.ptr())\n\t\t\t);\n\t\t\tbreak;\n\t\tcase GT:\n\t\t\tsol = JDD.ptrToNode(\n\t\t\t\tDV_BDDGreaterThan(v, bound, vars.array(), vars.n(), odd.ptr())\n\t\t\t);\n\t\t\tbreak;\n\t\tcase LEQ:\n\t\t\tsol = JDD.ptrToNode(\n\t\t\t\tDV_BDDLessThanEquals(v, bound, vars.array(), vars.n(), odd.ptr())\n\t\t\t);\n\t\t\tbreak;\n\t\tcase LT:\n\t\t\tsol = JDD.ptrToNode(\n\t\t\t\tDV_BDDLessThan(v, bound, vars.array(), vars.n(), odd.ptr())\n\t\t\t);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\t// Don't handle\n\t\t}\n\t\t\n\t\treturn sol;\n\t}\n\tprivate native long DV_BDDGreaterThanEquals(long v, double bound, long vars, int num_vars, long odd);\n\tprivate native long DV_BDDGreaterThan(long v, double bound, long vars, int num_vars, long odd);\n\tprivate native long DV_BDDLessThanEquals(long v, double bound, long vars, int num_vars, long odd);\n\tprivate native long DV_BDDLessThan(long v, double bound, long vars, int num_vars, long odd);\n\t\n\t/**\n\t * \tGenerate BDD for states in the given interval\n\t * (interval specified as lower/upper bound)\n\t */\n\tpublic JDDNode getBDDFromInterval(double lo, double hi, JDDVars vars, ODDNode odd)\n\t{\n\t\tJDDNode sol;\n\t\t\n\t\tsol = JDD.ptrToNode(\n\t\t\tDV_BDDInterval(v, lo, hi, vars.array(), vars.n(), odd.ptr())\n\t\t);\n\t\t\n\t\treturn sol;\n\t}\n\tprivate native long DV_BDDInterval(long v, double lo, double hi, long vars, int num_vars, long odd);\n\t\n\t/**\n\t * \tGenerate BDD for states whose value is close to 'value'\n\t * (within absolute error 'epsilon')\n\t */\n\tpublic JDDNode getBDDFromCloseValueAbs(double value, double epsilon, JDDVars vars, ODDNode odd)\n\t{\n\t\tJDDNode sol;\n\t\t\n\t\tsol = JDD.ptrToNode(\n\t\t\tDV_BDDCloseValueAbs(v, value, epsilon, vars.array(), vars.n(), odd.ptr())\n\t\t);\n\t\t\n\t\treturn sol;\n\t}\n\tprivate native long DV_BDDCloseValueAbs(long v, double value, double epsilon, long vars, int num_vars, long odd);\n\t\n\t/**\n\t * \tGenerate BDD for states whose value is close to 'value'\n\t * (within relative error 'epsilon')\n\t */\n\tpublic JDDNode getBDDFromCloseValueRel(double value, double epsilon, JDDVars vars, ODDNode odd)\n\t{\n\t\tJDDNode sol;\n\t\t\n\t\tsol = JDD.ptrToNode(\n\t\t\tDV_BDDCloseValueRel(v, value, epsilon, vars.array(), vars.n(), odd.ptr())\n\t\t);\n\t\t\n\t\treturn sol;\n\t}\n\tprivate native long DV_BDDCloseValueRel(long v, double value, double epsilon, long vars, int num_vars, long odd);\n\t\n\t/**\n\t * Convert to an MTBDD representation.\n\t */\n\tprivate native long DV_ConvertToMTBDD(long v, long vars, int num_vars, long odd);\n\tpublic JDDNode convertToMTBDD(JDDVars vars, ODDNode odd)\n\t{\n\t\tJDDNode sol;\n\t\t\n\t\tsol = JDD.ptrToNode(\n\t\t\tDV_ConvertToMTBDD(v, vars.array(), vars.n(), odd.ptr())\n\t\t);\n\t\t\n\t\treturn sol;\n\t}\n\t\n\t// print (all, including nonzeros)\n\tpublic void print(PrismLog log)\n\t{\n\t\tint i;\n\t\tdouble d;\n\t\t\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td = DV_GetElement(v, n, i);\n\t\t\tlog.print(d + \" \");\n\t\t}\n\t\tlog.println();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dv/IntegerVector.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: C++ code for integer vector\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"iv.h\"\n#include \"IntegerVector.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n#include <cmath>\n#include <new>\n\n//------------------------------------------------------------------------------\n// IntegerVector methods\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_IntegerVector_IV_1CreateZeroVector\n(\nJNIEnv *env,\njobject obj,\njint n\n)\n{\n\tint *vector;\n\tint i;\n\ttry {\n\t\tvector = new int[n];\n\t} catch (std::bad_alloc e) {\n\t\treturn 0;\n\t}\n\tfor (i = 0; i < n; i++) {\n\t\tvector[i] = 0;\n\t}\n\t\n\treturn ptr_to_jlong(vector);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_dv_IntegerVector_IV_1ConvertMTBDD\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer dd,\njlong __jlongpointer vars,\njint num_vars,\njlong __jlongpointer odd\n)\n{\n\treturn ptr_to_jlong(\n\t\tmtbdd_to_integer_vector(\n\t\t\tddman,\n\t\t\tjlong_to_DdNode(dd),\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_dv_IntegerVector_IV_1GetElement\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njint i\n)\n{\n\tint *vector = (int *) jlong_to_ptr(v);\n\treturn (jint)vector[i];\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_IntegerVector_IV_1SetElement\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njint i,\njint j\n)\n{\n\tint *vector = (int *) jlong_to_ptr(v);\n\tvector[i] = j;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_IntegerVector_IV_1SetAllElements\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer v,\njint n,\njint j\n)\n{\n\tint *vector = (int *) jlong_to_ptr(v);\n\tfor(int i = 0; i < n; i++)\n\t\tvector[i] = j;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_dv_IntegerVector_IV_1Clear\n(\nJNIEnv *env,\njobject obj,\njlong __jlongpointer vector\n)\n{\n\t// note we assume that this memory was created with new\n\tif (vector) delete (int *) jlong_to_ptr(vector);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dv/IntegerVector.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage dv;\n\nimport prism.*;\nimport jdd.*;\nimport odd.*;\n\n/**\n * Class to encapsulate a vector of integer, stored natively.\n */\npublic class IntegerVector\n{\n\t//------------------------------------------------------------------------------\n\t// Load JNI stuff from shared library\n\t//------------------------------------------------------------------------------\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\t\n\t//------------------------------------------------------------------------------\n\t// Instance variables/methods\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Vector contents (C/C++ pointer cast to a long)\n\t */\n\tprivate long v;\n\t/**\n\t * Size of vector\n\t */\n\tprivate int n;\n\t\n\t// Constructors\n\t\n\t/**\n\t * Create a new IntegerVector of size {@code size} with all entries set to 0.\n\t * @throws PrismException if there is insufficient memory to create the array.\n\t */\n\tpublic IntegerVector(int size) throws PrismException\n\t{\n\t\tv = IV_CreateZeroVector(size);\n\t\tif (v == 0) throw new PrismException(\"Out of memory\");\n\t\tn = size;\n\t}\n\t\n\tprivate native long IV_CreateZeroVector(int n);\n\t\n\t/**\n\t * Create a new IntegerVector from a pointer {@code vect} to an existing native integer array of size {@code size}.\n\t */\n\tpublic IntegerVector(long vector, int size)\n\t{\n\t\tv = vector;\n\t\tn = size;\n\t}\n\t\n\t/**\n\t * Create a new IntegerVector from an existing MTBDD representation of an array.\n\t * <br>[ DEREFS: <i>none</i> ]\n\t * @throws PrismException if number of states is too large (uses Java int based indices)\n\t */\n\tpublic IntegerVector(JDDNode dd, JDDVars vars, ODDNode odd) throws PrismException\n\t{\n\t\tODDUtils.checkInt(odd, \"Can not create IntegerVector\");\n\n\t\tv = IV_ConvertMTBDD(dd.ptr(), vars.array(), vars.n(), odd.ptr());\n\t\tn = (int)odd.getNumStates();\n\t}\n\t\n\tprivate native long IV_ConvertMTBDD(long dd, long vars, int num_vars, long odd);\n\t\n\t// Accessors\n\t\n\t/**\n\t * Get the pointer to the native vector (C/C++ pointer cast to a long).\n\t */\n\tpublic long getPtr()\n\t{\n\t\treturn v;\n\t}\n\n\t/**\n\t * Get the size of the vector.\n\t */\n\tpublic int getSize()\n\t{\n\t\treturn n;\n\t}\n\n\t/**\n\t * Get element {@code i} of the vector.\n\t */\n\tpublic int getElement(int i)\n\t{\n\t\treturn IV_GetElement(v, n, i);\n\t}\n\n\tprivate native int IV_GetElement(long v, int n, int i);\n\t\n\t// Mutators\n\t\n\t/**\n\t * Set element {@code i} of the vector to value {@code j}.\n\t */\n\tpublic void setElement(int i, int j)\n\t{\n\t\tIV_SetElement(v, n, i, j);\n\t}\n\n\tprivate native void IV_SetElement(long v, int n, int i, int j);\n\t\n\t/**\n\t * Set all elements of the vector to the same value {@code j}.\n\t */\n\tpublic void setAllElements(int j)\n\t{\n\t\tIV_SetAllElements(v, n, j);\n\t}\n\n\tprivate native void IV_SetAllElements(long v, int n, int j);\n\t\n\t/**\n\t * Clear storage of the vector.\n\t */\n\tpublic void clear() \n\t{\n\t\tIV_Clear(v);\n\t}\n\n\tprivate native void IV_Clear(long v);\n\t\n\t/**\n\t * Print the (all elements, including non-zeros) to a log.\n\t */\n\tpublic void print(PrismLog log)\n\t{\n\t\tint i, j;\n\t\t\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tj = IV_GetElement(v, n, i);\n\t\t\tlog.print(j + \" \");\n\t\t}\n\t\tlog.println();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/dv/dv.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: C++ code for double vector stuff\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"dv.h\"\n#include <cmath>\n#include <new>\n#include <cstdint>\n#include <limits>\n\n// local function prototypes\n\nstatic void mtbdd_to_double_vector_rec(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o, int64_t n, double *res);\nstatic DdNode *double_vector_to_mtbdd_rec(DdManager *ddman, double *vec, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic DdNode *double_vector_to_bdd_rec(DdManager *ddman, double *vec, int rel_op, double value1, double value2, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic void filter_double_vector_rec(DdManager *ddman, double *vec, DdNode *filter, double d, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic void max_double_vector_mtbdd_rec(DdManager *ddman, double *vec, DdNode *vec2, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic double get_first_from_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic double min_double_vector_over_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic double max_double_vector_over_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic double max_finite_double_vector_over_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic double sum_double_vector_over_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic double sum_double_vector_over_mtbdd_rec(DdManager *ddman, double *vec, DdNode *mult, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\nstatic void sum_double_vector_over_dd_vars_rec(DdManager *ddman, double *vec, double *vec2, DdNode **vars, int num_vars, int level, int first_var, int last_var, ODDNode *odd, ODDNode *odd2, int64_t o, int64_t o2);\n\n// Threshold for comparison of doubles\nstatic double epsilon_double = 1e-12;\n\n//------------------------------------------------------------------------------\n\n// converts an mtbdd representing a vector to an array of doubles\n// it is optional whether or not an array is passed in to be used\n// if so, it should be the right size (as determined by row->eoff+row->toff)\n// if not, a new one is created\n// in either the case, a pointer to the array is returned\n// throws std::bad_alloc on out-of-memory\n\nEXPORT double *mtbdd_to_double_vector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn mtbdd_to_double_vector(ddman, dd, vars, num_vars, odd, NULL);\n}\n\nEXPORT double *mtbdd_to_double_vector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd, double *res)\n{\n\tint64_t i, n;\n\n\t// determine size\n\tn = odd->eoff + odd->toff;\n\t// create array (if not supplied)\n\tif (!res) res = new double[n];\n\t// initialise to zero\n\tfor (i = 0; i < n; i++) {\n\t\tres[i] = 0.0;\n\t}\n\t// build array recursively\n\tmtbdd_to_double_vector_rec(ddman, dd, vars, num_vars, 0, odd, 0, n, res);\n\n\treturn res;\n}\n\nvoid mtbdd_to_double_vector_rec(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o, int64_t n, double *res)\n{\n\tDdNode *e, *t;\n\n\tif (dd == Cudd_ReadZero(ddman)) return;\n\n\tif (level == num_vars) {\n\t\tif (o < 0 || o >= n) {\n\t\t\tprintf(\"Internal error: Can not convert MTBDD to double vector: Value out of range of the ODD (does the MTBDD encode non-reachable states?)\\n\");\n\t\t\texit(1);\n\t\t}\n\t\tres[o] = Cudd_V(dd);\n\t\treturn;\n\t}\n\telse if (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(vars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\n\tmtbdd_to_double_vector_rec(ddman, e, vars, num_vars, level+1, odd->e, o, n, res);\n\tmtbdd_to_double_vector_rec(ddman, t, vars, num_vars, level+1, odd->t, o+odd->eoff, n, res);\n}\n\n//------------------------------------------------------------------------------\n\n// converts an array of doubles to an mtbdd\n\nEXPORT DdNode *double_vector_to_mtbdd(DdManager *ddman, double *vec, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn double_vector_to_mtbdd_rec(ddman, vec, vars, num_vars, 0, odd, 0);\n}\n\nDdNode *double_vector_to_mtbdd_rec(DdManager *ddman, double *vec, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tDdNode *e, *t;\n\n\tif (level == num_vars) {\n\t\treturn DD_Constant(ddman, vec[o]);\n\t}\n\telse {\n\t\tif (odd->eoff > 0) {\n\t\t\te = double_vector_to_mtbdd_rec(ddman, vec, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\telse {\n\t\t\te = DD_Constant(ddman, 0);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tt = double_vector_to_mtbdd_rec(ddman, vec, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t\telse {\n\t\t\tt = DD_Constant(ddman, 0);\n\t\t}\n\t\tif (e == t) {\n\t\t\tCudd_RecursiveDeref(ddman, t);\n\t\t\treturn e;\n\t\t}\n\t\telse {\n\t\t\tCudd_Ref(vars[level]);\n\t\t\treturn DD_ITE(ddman, vars[level], t, e);\n\t\t}\n\t}\n}\t\n\n//------------------------------------------------------------------------------\n\n// Converts an array of doubles to a BDD using a relational operator and a value (or values)\n// Options for rel_op:\n// * DV_GREATER_THAN_EQUALS: >= value\n// * DV_GREATER_THAN: > value\n// * DV_LESS_THAN_EQUALS <= value\n// * DV_LESS_THAN: < value\n// * DV_INTERVAL: in [value1,value2]\n// * DV_CLOSE_ABS: =value1 (with absolute error <= value2)\n// * DV_CLOSE_REL: =value1 (with relative error <= value2)\n\n\nEXPORT DdNode *double_vector_to_bdd(DdManager *ddman, double *vec, int rel_op, double value, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn double_vector_to_bdd(ddman, vec, rel_op, value, 0, vars, num_vars, odd);\n}\n\nEXPORT DdNode *double_vector_to_bdd(DdManager *ddman, double *vec, int rel_op, double value1, double value2, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn double_vector_to_bdd_rec(ddman, vec, rel_op, value1, value2, vars, num_vars, 0, odd, 0);\n}\n\n// Recursive call for double_vector_to_bdd methods\n\nDdNode *double_vector_to_bdd_rec(DdManager *ddman, double *vec, int rel_op, double value1, double value2, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tDdNode *e, *t;\n\n\tif (level == num_vars) {\n\t\tswitch (rel_op) {\n\t\tcase DV_GREATER_THAN_EQUALS: return (vec[o] >= value1) ? DD_Constant(ddman, 1) : DD_Constant(ddman, 0); break;\n\t\tcase DV_GREATER_THAN: return (vec[o] > value1) ? DD_Constant(ddman, 1) : DD_Constant(ddman, 0); break;\n\t\tcase DV_LESS_THAN_EQUALS: return (vec[o] <= value1) ? DD_Constant(ddman, 1) : DD_Constant(ddman, 0); break;\n\t\tcase DV_LESS_THAN: return (vec[o] < value1) ? DD_Constant(ddman, 1) : DD_Constant(ddman, 0); break;\n\t\tcase DV_INTERVAL: return (vec[o] >= value1 && vec[o] <= value2) ? DD_Constant(ddman, 1) : DD_Constant(ddman, 0); break;\n\t\tcase DV_CLOSE_ABS: return doubles_are_close_abs(vec[o], value1, value2) ? DD_Constant(ddman, 1) : DD_Constant(ddman, 0); break;\n\t\tcase DV_CLOSE_REL: return doubles_are_close_rel(vec[o], value1, value2) ? DD_Constant(ddman, 1) : DD_Constant(ddman, 0); break;\n\t\t}\n\t}\n\telse {\n\t\tif (odd->eoff > 0) {\n\t\t\te = double_vector_to_bdd_rec(ddman, vec, rel_op, value1, value2, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\telse {\n\t\t\te = DD_Constant(ddman, 0);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tt = double_vector_to_bdd_rec(ddman, vec, rel_op, value1, value2, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t\telse {\n\t\t\tt = DD_Constant(ddman, 0);\n\t\t}\n\t\tif (e == t) {\n\t\t\tCudd_RecursiveDeref(ddman, t);\n\t\t\treturn e;\n\t\t}\n\t\telse {\n\t\t\tCudd_Ref(vars[level]);\n\t\t\treturn DD_ITE(ddman, vars[level], t, e);\n\t\t}\n\t}\n\t// Never get here:\n\treturn NULL;\n}\t\n\n//------------------------------------------------------------------------------\n\n// filter vector using a bdd (set elements not in filter to constant d)\n\nEXPORT void filter_double_vector(DdManager *ddman, double *vec, DdNode *filter, double d, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\tfilter_double_vector_rec(ddman, vec, filter, d, vars, num_vars, 0, odd, 0);\n}\n\nvoid filter_double_vector_rec(DdManager *ddman, double *vec, DdNode *filter, double d, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tDdNode *dd;\n\t\n\tif (level == num_vars) {\n\t\tif (Cudd_V(filter) == 0) {\n\t\t\tvec[o] = d;\n\t\t}\n\t}\n\telse {\n\t\tif (odd->eoff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_E(filter);\n\t\t\tfilter_double_vector_rec(ddman, vec, dd, d, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_T(filter);\n\t\t\tfilter_double_vector_rec(ddman, vec, dd, d, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n\n// apply max operator, i.e. vec[i] = max(vec[i], vec2[i]), where vec2 is an mtbdd\n\nEXPORT void max_double_vector_mtbdd(DdManager *ddman, double *vec, DdNode *vec2, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\tmax_double_vector_mtbdd_rec(ddman, vec, vec2, vars, num_vars, 0, odd, 0);\n}\n\nvoid max_double_vector_mtbdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tDdNode *dd;\n\tdouble d;\n\t\n\tif (level == num_vars) {\n\t\n\t\td = Cudd_V(filter);\n\t\tif (d > vec[o]) {\n\t\t\tvec[o] = d;\n\t\t}\n\t}\n\telse {\n\t\tif (odd->eoff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_E(filter);\n\t\t\tmax_double_vector_mtbdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_T(filter);\n\t\t\tmax_double_vector_mtbdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t}\n}\t\n\n//------------------------------------------------------------------------------\n\n// get value of first element in BDD filter\n\nEXPORT double get_first_from_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\t// This shouldn't really be called with an empty filter.\n\t// But we check for this anyway and return NaN.\n\t// This is unfortunately indistinguishable from the case\n\t// where the vector does actually contain NaN. Ho hum.\n\tif (filter == Cudd_ReadZero(ddman)) return NAN;\n\t// Recurse...\n\telse return get_first_from_bdd_rec(ddman, vec, filter, vars, num_vars, 0, odd, 0);\n}\n\ndouble get_first_from_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tDdNode *dd;\n\t\n\tif (level == num_vars) {\n\t\treturn vec[o];\n\t}\n\telse {\n\t\t// go down filter along first non-zero path\n\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_E(filter);\n\t\tif (dd != Cudd_ReadZero(ddman)) {\n\t\t\treturn get_first_from_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\telse {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_T(filter);\n\t\t\treturn get_first_from_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t}\n}\t\n\n//------------------------------------------------------------------------------\n\n// compute the minimum value of those in the bdd passed in\n\nEXPORT double min_double_vector_over_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn min_double_vector_over_bdd_rec(ddman, vec, filter, vars, num_vars, 0, odd, 0);\n}\n\ndouble min_double_vector_over_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tdouble d1, d2;\n\tDdNode *dd;\n\t\n\tif (level == num_vars) {\n\t\tif (Cudd_V(filter) > 0) {\n\t\t\treturn vec[o];\n\t\t}\n\t\telse {\n\t\t\treturn HUGE_VAL;\n\t\t}\n\t}\n\telse {\n\t\td1 = d2 = HUGE_VAL;\n\t\tif (odd->eoff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_E(filter);\n\t\t\td1 = min_double_vector_over_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_T(filter);\n\t\t\td2 = min_double_vector_over_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t\treturn (d1 < d2) ? d1 : d2;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\n// compute the maximum value of those in the bdd passed in\n\nEXPORT double max_double_vector_over_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn max_double_vector_over_bdd_rec(ddman, vec, filter, vars, num_vars, 0, odd, 0);\n}\n\ndouble max_double_vector_over_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tdouble d1, d2;\n\tDdNode *dd;\n\t\n\tif (level == num_vars) {\n\t\tif (Cudd_V(filter) > 0) {\n\t\t\treturn vec[o];\n\t\t}\n\t\telse {\n\t\t\treturn -HUGE_VAL;\n\t\t}\n\t}\n\telse {\n\t\td1 = d2 = -HUGE_VAL;\n\t\tif (odd->eoff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_E(filter);\n\t\t\td1 = max_double_vector_over_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_T(filter);\n\t\t\td2 = max_double_vector_over_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t\treturn (d1 > d2) ? d1 : d2;\n\t}\n}\n\n\nEXPORT double max_finite_double_vector_over_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn max_finite_double_vector_over_bdd_rec(ddman, vec, filter, vars, num_vars, 0, odd, 0);\n}\n\ndouble max_finite_double_vector_over_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tdouble d1, d2;\n\tDdNode *dd;\n\n\tif (level == num_vars) {\n\t\tif (Cudd_V(filter) > 0) {\n\t\t\tdouble v = vec[o];\n\t\t\tif (v < std::numeric_limits<double>::infinity()) {\n\t\t\t\treturn -std::numeric_limits<double>::infinity();\n\t\t\t} else {\n\t\t\t\treturn v;\n\t\t\t}\n\t\t}\n\t\telse {\n\t\t\treturn -std::numeric_limits<double>::infinity();\n\t\t}\n\t}\n\telse {\n\t\td1 = d2 = -HUGE_VAL;\n\t\tif (odd->eoff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_E(filter);\n\t\t\td1 = max_double_vector_over_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_T(filter);\n\t\t\td2 = max_double_vector_over_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t\treturn (d1 > d2) ? d1 : d2;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\n// sums up the elements of a double array - but only those in the bdd passed in\n\nEXPORT double sum_double_vector_over_bdd(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn sum_double_vector_over_bdd_rec(ddman, vec, filter, vars, num_vars, 0, odd, 0);\n}\n\ndouble sum_double_vector_over_bdd_rec(DdManager *ddman, double *vec, DdNode *filter, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tdouble d;\n\tDdNode *dd;\n\t\n\tif (level == num_vars) {\n\t\tif (Cudd_V(filter) > 0) {\n\t\t\treturn vec[o];\n\t\t}\n\t\telse {\n\t\t\treturn 0;\n\t\t}\n\t}\n\telse {\n\t\td = 0;\n\t\tif (odd->eoff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_E(filter);\n\t\t\td += sum_double_vector_over_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(filter) > Cudd_NodeReadIndex(vars[level])) ? filter : Cudd_T(filter);\n\t\t\td += sum_double_vector_over_bdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t\treturn d;\n\t}\n}\t\n\n//------------------------------------------------------------------------------\n\n// sums up the elements of a double array - multiplied by the corresponding values in the mtbdd passed in\n\nEXPORT double sum_double_vector_over_mtbdd(DdManager *ddman, double *vec, DdNode *mult, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn sum_double_vector_over_mtbdd_rec(ddman, vec, mult, vars, num_vars, 0, odd, 0);\n}\n\ndouble sum_double_vector_over_mtbdd_rec(DdManager *ddman, double *vec, DdNode *mult, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tdouble d;\n\tDdNode *dd;\n\t\n\tif (level == num_vars) {\n\t\treturn Cudd_V(mult) * vec[o];\n\t}\n\telse {\n\t\td = 0;\n\t\tif (odd->eoff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(mult) > Cudd_NodeReadIndex(vars[level])) ? mult : Cudd_E(mult);\n\t\t\td += sum_double_vector_over_mtbdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tdd = (Cudd_NodeReadIndex(mult) > Cudd_NodeReadIndex(vars[level])) ? mult : Cudd_T(mult);\n\t\t\td += sum_double_vector_over_mtbdd_rec(ddman, vec, dd, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t\treturn d;\n\t}\n}\t\n\n//------------------------------------------------------------------------------\n\n// sum up the elements of a double array, over a subset of its dd vars\n// the dd var subset must be a continuous range of vars, identified by indices: first_var, last_var\n// store the result in the vector vec2\n\nEXPORT void sum_double_vector_over_dd_vars(DdManager *ddman, double *vec, double *vec2, DdNode **vars, int num_vars, int first_var, int last_var, ODDNode *odd, ODDNode *odd2)\n{\n\treturn sum_double_vector_over_dd_vars_rec(ddman, vec, vec2, vars, num_vars, 0, first_var, last_var, odd, odd2, 0, 0);\n}\n\nvoid sum_double_vector_over_dd_vars_rec(DdManager *ddman, double *vec, double *vec2, DdNode **vars, int num_vars, int level, int first_var, int last_var, ODDNode *odd, ODDNode *odd2, int64_t o, int64_t o2)\n{\n\tif (level == num_vars) {\n\t\tvec2[o2] += vec[o];\n\t}\n\telse {\n\t\tif (odd->eoff > 0) {\n\t\t\tif (Cudd_NodeReadIndex(vars[level]) >= first_var && Cudd_NodeReadIndex(vars[level]) <= last_var) {\n\t\t\t\tsum_double_vector_over_dd_vars_rec(ddman, vec, vec2, vars, num_vars, level+1, first_var, last_var, odd->e, odd2, o, o2);\n\t\t\t} else {\n\t\t\t\tsum_double_vector_over_dd_vars_rec(ddman, vec, vec2, vars, num_vars, level+1, first_var, last_var, odd->e, odd2->e, o, o2);\n\t\t\t}\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tif (Cudd_NodeReadIndex(vars[level]) >= first_var && Cudd_NodeReadIndex(vars[level]) <= last_var) {\n\t\t\t\tsum_double_vector_over_dd_vars_rec(ddman, vec, vec2, vars, num_vars, level+1, first_var, last_var, odd->t, odd2, o+odd->eoff, o2);\n\t\t\t} else {\n\t\t\t\tsum_double_vector_over_dd_vars_rec(ddman, vec, vec2, vars, num_vars, level+1, first_var, last_var, odd->t, odd2->t, o+odd->eoff, o2+odd2->eoff);\n\t\t\t}\n\t\t}\n\t}\n}\t\n\n//-----------------------------------------------------------------------------\n\n// Converts an array of doubles to a a DistVector, which stores only one copy of each distinct double\n// and an array of short pointers to them. Fails and returns NULL if there are more distinct values\n// than can be indexed by a short or if we run out of memory.\n\nEXPORT DistVector *double_vector_to_dist(double *v, int n)\n{\n\tdouble *buffer = NULL, *tmp = NULL;\n\tint i, j, num_dist, buffer_size, buffer_inc;\n\tunsigned int max_size, s;\n\tunsigned short *ptrs = NULL;\n\tDistVector *dv = NULL;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create buffer to store distinct values\n\tbuffer_inc = 256;\n\tbuffer_size = 256;\n\tmax_size = 1 << (8*sizeof(short));\n\tbuffer = new double[buffer_size];\n\tptrs = new unsigned short[n];\n\t\n\tnum_dist = 0;\n\t// go thru vector\n\tfor (i = 0; i < n; i++) {\n\t\tfor (s = 0; s < num_dist; s++) {\n\t\t\tif (buffer[s] == v[i]) break;\n\t\t}\n\t\t// add a new val if necessary...\n\t\tif (s == num_dist) {\n\t\t\t// ...increasing buffer size if required...\n\t\t\tif (num_dist >= buffer_size) {\n\t\t\t\t// ...and bailing out if there are too many\n\t\t\t\tif (buffer_size+buffer_inc > max_size) {\n\t\t\t\t\tthrow std::bad_alloc();\n\t\t\t\t}\n\t\t\t\ttmp = new double[buffer_size+buffer_inc];\n\t\t\t\tfor (j = 0; j < buffer_size; j++) {\n\t\t\t\t\ttmp[j] = buffer[j];\n\t\t\t\t}\n\t\t\t\tdelete[] buffer;\n\t\t\t\tbuffer = tmp;\n\t\t\t\ttmp = NULL;\n\t\t\t\tbuffer_size += buffer_inc;\n\t\t\t}\n\t\t\t// add val\n\t\t\tbuffer[s] = v[i];\n\t\t\tnum_dist++;\n\t\t}\n\t\tptrs[i] = s;\n\t}\n\t\n\t// create data str to store result\n\tdv = new DistVector();\n\tdv->dist = buffer;\n\tdv->num_dist = num_dist;\n\tdv->ptrs = ptrs;\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (buffer) delete[] buffer;\n\t\tif (tmp) delete[] tmp;\n\t\tif (ptrs) delete[] ptrs;\n\t\tif (dv) delete dv;\n\t\treturn NULL;\n\t}\n\t\n\treturn dv;\n}\n\n//-----------------------------------------------------------------------------------\n\n// free distinct vector struct\n\nEXPORT DistVector::DistVector()\n{\n\tdist = NULL;\n\tnum_dist = 0;\n\tptrs = NULL;\n}\n\nEXPORT DistVector::~DistVector()\n{\n\tif (dist) delete[] dist;\n\tif (ptrs) delete[] ptrs;\n}\n\n//------------------------------------------------------------------------------\n\n// Utililty methods for checking whether two doubles are close\n// (based on code in prism.PrismUtils.java)\n\nEXPORT bool doubles_are_close_abs(double d1, double d2, double epsilon)\n{\n\t// Deal with infinite cases\n\tif (std::isinf(d1)) {\n\t\treturn std::isinf(d2) && (d1 > 0) == (d2 > 0);\n\t} else if (std::isinf(d2)) {\n\t\treturn false;\n\t}\n\t// Compute/check error\n\treturn (fabs(d1 - d2) < epsilon);\n}\n\nEXPORT bool doubles_are_close_rel(double d1, double d2, double epsilon)\n{\n\t// Deal with infinite cases\n\tif (std::isinf(d1)) {\n\t\treturn std::isinf(d2) && (d1 > 0) == (d2 > 0);\n\t} else if (std::isinf(d2)) {\n\t\treturn false;\n\t}\n\t// Compute/check error\n\td1 = fabs(d1);\n\td2 = fabs(d2);\n\tif (d2 == 0) {\n\t\t   // If both are zero, error is 0; otherwise +inf\n\t\t   return (d1 == 0);\n\t}\n\treturn (fabs(d1 - d2) / d1 < epsilon);\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/dv/iv.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\tDescription: C++ code for double vector stuff\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"iv.h\"\n#include <cmath>\n#include <new>\n#include <cstdint>\n\n// local function prototypes\n\nstatic void mtbdd_to_integer_vector_rec(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o, int64_t n, int *res);\nstatic DdNode *integer_vector_to_mtbdd_rec(DdManager *ddman, int *vec, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o);\n\n//------------------------------------------------------------------------------\n\n// converts an mtbdd representing a vector to an array of integers\n// values are cast from double to integer when extracting from the mtbdd\n// it is optional whether or not an array is passed in to be used\n// if so, it should be the right size (as determined by row->eoff+row->toff)\n// if not, a new one is created\n// in either the case, a pointer to the array is returned\n// throws std::bad_alloc on out-of-memory\n\nEXPORT int *mtbdd_to_integer_vector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn mtbdd_to_integer_vector(ddman, dd, vars, num_vars, odd, NULL);\n}\n\nEXPORT int *mtbdd_to_integer_vector(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd, int *res)\n{\n\tint64_t i, n;\n\n\t// determine size\n\tn = odd->eoff + odd->toff;\n\t// create array (if not supplied)\n\tif (!res) res = new int[n];\n\t// initialise to zero\n\tfor (i = 0; i < n; i++) {\n\t\tres[i] = 0.0;\n\t}\n\t// build array recursively\n\tmtbdd_to_integer_vector_rec(ddman, dd, vars, num_vars, 0, odd, 0, n, res);\n\t\n\treturn res;\n}\n\nvoid mtbdd_to_integer_vector_rec(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o, int64_t n, int *res)\n{\n\tDdNode *e, *t;\n\n\tif (dd == Cudd_ReadZero(ddman)) return;\n\n\tif (level == num_vars) {\n\t\tif (o < 0 || o >= n) {\n\t\t\tprintf(\"Internal error: Can not convert MTBDD to integer vector: Value out of range of the ODD (does the MTBDD encode non-reachable states?)\\n\");\n\t\t\texit(1);\n\t\t}\n\t\tres[o] = (int) Cudd_V(dd);\n\t\treturn;\n\t}\n\telse if (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(vars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\n\tmtbdd_to_integer_vector_rec(ddman, e, vars, num_vars, level+1, odd->e, o, n, res);\n\tmtbdd_to_integer_vector_rec(ddman, t, vars, num_vars, level+1, odd->t, o+odd->eoff, n, res);\n}\n\n//------------------------------------------------------------------------------\n\n// converts an array of integers to an mtbdd\n\nEXPORT DdNode *integer_vector_to_mtbdd(DdManager *ddman, int *vec, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn integer_vector_to_mtbdd_rec(ddman, vec, vars, num_vars, 0, odd, 0);\n}\n\nDdNode *integer_vector_to_mtbdd_rec(DdManager *ddman, int *vec, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t o)\n{\n\tDdNode *e, *t;\n\n\tif (level == num_vars) {\n\t\treturn DD_Constant(ddman, vec[o]);\n\t}\n\telse {\n\t\tif (odd->eoff > 0) {\n\t\t\te = integer_vector_to_mtbdd_rec(ddman, vec, vars, num_vars, level+1, odd->e, o);\n\t\t}\n\t\telse {\n\t\t\te = DD_Constant(ddman, 0);\n\t\t}\n\t\tif (odd->toff > 0) {\n\t\t\tt = integer_vector_to_mtbdd_rec(ddman, vec, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t}\n\t\telse {\n\t\t\tt = DD_Constant(ddman, 0);\n\t\t}\n\t\tif (e == t) {\n\t\t\tCudd_RecursiveDeref(ddman, t);\n\t\t\treturn e;\n\t\t}\n\t\telse {\n\t\t\tCudd_Ref(vars[level]);\n\t\t\treturn DD_ITE(ddman, vars[level], t, e);\n\t\t}\n\t}\n}\t\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/dv/package-info.java",
    "content": "/**\n * Utility functions for operations on vectors of doubles or integers (stored in C++ through JNI).\n */\npackage dv;\n"
  },
  {
    "path": "prism/src/explicit/BasicModelTransformation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.function.IntFunction;\n\nimport prism.PrismException;\n\n/**\n * Base class for model transformations, providing support for mapping between states.\n */\npublic class BasicModelTransformation<OM extends Model<?>, TM extends Model<?>> implements ModelTransformation<OM, TM>\n{\n\tpublic static final IntFunction<Integer> IDENTITY = Integer::valueOf;\n\n\tprotected final OM originalModel;\n\tprotected final TM transformedModel;\n\tprotected final IntFunction<Integer> mapToTransformedModel;\n\n\tprotected final int numberOfStates;\n\n\t/** Constructor for a model transformation that maps states one-on-one. */\n\tpublic BasicModelTransformation(final OM originalModel, final TM transformedModel)\n\t{\n\t\tthis(originalModel, transformedModel, IDENTITY);\n\t}\n\n\t/**\n\t * Constructor for a model transformation where the state mapping is given by a function\n\t */\n\tpublic BasicModelTransformation(final OM originalModel, final TM transformedModel, final IntFunction<Integer> mapToTransformedModel)\n\t{\n\t\tthis.originalModel               = originalModel;\n\t\tthis.transformedModel            = transformedModel;\n\t\tthis.numberOfStates              = originalModel.getNumStates();\n\t\tthis.mapToTransformedModel       = mapToTransformedModel;\n\t}\n\n\t@Override\n\tpublic OM getOriginalModel()\n\t{\n\t\treturn originalModel;\n\t}\n\n\t@Override\n\tpublic TM getTransformedModel()\n\t{\n\t\treturn transformedModel;\n\t}\n\n\t@Override\n\tpublic StateValues projectToOriginalModel(final StateValues sv) throws PrismException\n\t{\n\t\treturn sv.mapToNewModel(originalModel, mapToTransformedModel);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/Belief.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Xueyi Zou <xz972@york.ac.uk> (University of York)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Arrays;\nimport java.util.List;\n\nimport parser.State;\nimport prism.PrismUtils;\n\n/**\n * A belief state for a partially observable model.\n * This assumes that states are split into observable and unobservable parts,\n * and so stores (separately) a fixed value for the observable part,\n * and a distribution over the unobservable part.\n * This class just uses indices - the actual observations/unobservations\n * are assumed to be stored elsewhere (in a {@link PartiallyObservableModel}). \n */\npublic class Belief implements Comparable<Belief>\n{\n\t/** The state of the observable part of the model **/\n\tpublic int so;\n\t\n\t/** The probability distribution over the unobservable part of the model **/\n\tpublic double[] bu;\n\n\t/**\n\t * Constructor\n\t * @param so Observable part (index of observation)\n\t * @param bu Distribution over unobservable part (probability for each unobservation)\n\t */\n\tpublic Belief(int so, double[] bu)\n\t{\n\t\tthis.so = so;\n\t\tthis.bu = bu;\n\t}\n\n\t/**\n\t * Constructor\n\t * @param dist Distribution over states of a model (probability for each state)\n\t * @param model The (partially observable) model\n\t * If {@code dist} is a not a valid distribution, the resulting belief will be invalid too.\n\t */\n\tprotected Belief(double[] dist, PartiallyObservableModel<?> model)\n\t{\n\t\tso = -1;\n\t\tbu = new double[model.getNumUnobservations()];\n\t\tfor (int s = 0; s < dist.length; s++) {\n\t\t\tif (dist[s] != 0) {\n\t\t\t\tso = model.getObservation(s);\n\t\t\t\tbu[model.getUnobservation(s)] += dist[s];\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Construct a point distribution over a single model stete\n\t * @param s A model state\n\t * @param model The (partially observable) model\n\t */\n\tpublic static Belief pointDistribution(int s, PartiallyObservableModel<?> model)\n\t{\n\t\tint so = model.getObservation(s);\n\t\tdouble[] bu = new double[model.getNumUnobservations()];\n\t\tbu[model.getUnobservation(s)] = 1.0;\n\t\treturn new Belief(so, bu);\n\t}\n\t\n\t/**\n\t * Convert to a probability distribution over all model states\n\t * (represented as an array of probabilities). \n\t * @param model The (partially observable) model\n\t */\n\tpublic double[] toDistributionOverStates(PartiallyObservableModel<?> model)\n\t{\n\t\tdouble[] distributionOverStates = new double[model.getNumStates()];\n\t\tint n = model.getNumStates();\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tif (model.getObservation(s) == so) {\n\t\t\t\tint unobserv = model.getUnobservation(s);\n\t\t\t\tdistributionOverStates[s] = bu[unobserv];\n\t\t\t}\n\t\t}\n\t\tPrismUtils.normalise(distributionOverStates);\n\t\treturn distributionOverStates;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\treturn 13 * Arrays.hashCode(bu) + so;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\n\t\tBelief other = (Belief) obj;\n\n\t\tif (so != other.so) {\n\t\t\treturn false;\n\t\t} else {\n\t\t\tif (bu.length != other.bu.length) {\n\t\t\t\treturn false;\n\t\t\t} else {\n\t\t\t\tfor (int i = 0; i < other.bu.length; i++) {\n\t\t\t\t\tif (Math.abs(bu[i] - other.bu[i]) > 1e-6)\n\t\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic int compareTo(Belief b)\n\t{\n\t\t// Can't compare to null\n\t\tif (b == null)\n\t\t\tthrow new NullPointerException();\n\t\t// Beliefs of different size are incomparable \n\t\tdouble[] bbu = b.bu;\n\t\tint n = bu.length;\n\t\tif (n != bbu.length)\n\t\t\tthrow new ClassCastException(\"Beliefs are different sizes\");\n\t\t// Compare\n\t\tif (so > b.so)\n\t\t\treturn 1;\n\t\tif (so < b.so)\n\t\t\treturn -1;\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (bu[i] - bbu[i] > 1e-6)\n\t\t\t\treturn 1;\n\t\t\tif (bbu[i] - bu[i] > 1e-6)\n\t\t\t\treturn -1;\n\t\t}\n\t\treturn 0;\n\t}\n\n\t/**\n\t * Convert to string representation, using observation info,\n\t * e.g. \"(6),0.5:(8)+0.5:(9)\" for an observable variable equal to 6\n\t * and an unobservable variable equally likely to be 8 or 9.\n\t */\n\tpublic String toString(PartiallyObservableModel<?> poModel)\n\t{\n\t\treturn toString(so, bu, poModel);\n\t}\n\n\t/**\n\t * Convert a belief, specified as an index to an observable and\n\t * a double array representing a distribution over unobservables,\n\t * to string representation, using observation info,\n\t * e.g. \"(6),0.5:(8)+0.5:(9)\" for an observable variable equal to 6\n\t * and an unobservable variable equally likely to be 8 or 9.\n\t */\n\tpublic static String toString(int so, double bu[], PartiallyObservableModel<?> poModel)\n\t{\n\t\treturn poModel.getObservationsList().get(so).toString() + \",\" + toStringUnobs(bu, poModel);\n\t}\n\n\t/**\n\t * Convert a double array representing a distribution over unobservables,\n\t * to string representation, using observation info,\n\t * e.g. \"0.5:(8)+0.5:(9)\" for an unobservable variable equally likely to be 8 or 9.\n\t */\n\tpublic static String toStringUnobs(double bu[], PartiallyObservableModel<?> poModel)\n\t{\n\t\tList<State> unobs = poModel.getUnobservationsList();\n\t\tString s = \"\";\n\t\tboolean first = true;\n\t\tfor (int i = 0; i < bu.length; i++) {\n\t\t\tif (bu[i] > 0) {\n\t\t\t\tif (!first) s+= \"+\";\n\t\t\t\ts += bu[i] + \":\" + unobs.get(i).toString();\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t}\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"{\" + so + \"},\" + Arrays.toString(bu);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/BirthProcess.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//  * Frits Dannenberg <frits.dannenberg@cs.ox.ac.uk> (University of Oxford)\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport prism.PrismException;\n\n/**\n * Class to efficiently compute transient probabilities of a birth process.\n *\n * @author Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n * @author Frits Dannenberg <frits.dannenberg@cs.ox.ac.uk> (University of Oxford)\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk>  (University of Oxford)\n */\npublic class BirthProcess\n{\n\t/* uniformisation rate to compute probabilities.\n\t * Must be at least as large as largest rate. */\n\tdouble unifRate;\n\t/* precision of computations using Fox-Glynn algorithm */\n\tdouble epsilon;\n\t/* time to compute probabilities for */\n\tdouble time;\n\t/* values used to compute probability to be in a given stage */\n\tdouble[] probs;\n\t/* same as above */\n\tdouble[] newProbs;\n\t/* whether rates added by calculateNextRate will be stored */\n\tboolean withRateArray;\n\tArrayList<Double> jumpRates;\n\tboolean initialising;\n\t/* current birth process stage */\n\tint stageNr;\n\t/* whether to try to avoid birth process computations in\n\t * case all rates are the same\n\t */\n\tboolean avoidBirthComputation; \n\n\t/**\n\t * Construct birth process.\n\t */\n\tpublic BirthProcess()\n\t{\n\t\tstageNr = 0;\n\t\tepsilon = 1E-7;\n\t\twithRateArray = true;\n\t\tinitialising = true;\n\t\tavoidBirthComputation = true;\n\t}\n\n\t/**\n\t * Sets whether rates added by calculateNextRate will be stored.\n\t * The default is to do so. Setting it to false allows to save space,\n\t * but will not allow rates larger than @a unifRate to be added.\n\t *\n\t * @param withRateArray whether to store rates in array\n\t */\n\tpublic void setWithRateArray(boolean withRateArray)\n\t{\n\t\tif (!initialising) {\n\t\t\tthrow new IllegalArgumentException(\"this method might not be called after calculateNextRate\");\n\t\t}\n\t\tthis.withRateArray = withRateArray;\n\t}\n\n\t/**\n\t * Sets the time to compute probabilities for.\n\t * \n\t * @param time time to compute probabilities for\n\t */\n\tpublic void setTime(double time)\n\t{\n\t\tif (!initialising) {\n\t\t\tthrow new IllegalArgumentException(\"this method might not be called after calculateNextRate\");\n\t\t}\n\t\tif (time < 0.0) {\n\t\t\tthrow new IllegalArgumentException(\"time must be nonnegative\");\n\t\t}\n\t\tthis.time = time;\n\t}\n\n\t/**\n\t * Sets precision to be used to compute probabilities.\n\t * \n\t * @param epsilon precision to be used to compute probabilities\n\t */\n\tpublic void setEpsilon(double epsilon)\n\t{\n\t\tif (!initialising) {\n\t\t\tthrow new IllegalArgumentException(\"this method might not be called after calculateNextRate\");\n\t\t}\n\n\t\tthis.epsilon = epsilon;\n\t}\n\n\t/**\n\t * Chooses whether to try to avoid birth process construction.\n\t * In case all rates provided to calculateNextProb are the same, it is\n\t * possible to use the Fox-Glynn algorithm to compute probabilities in\n\t * the birth process, which is then a Poisson process. If delayBirthComputation\n\t * is true, the more expensive computations will only be computed in case\n\t * this is necessary. Thus, if calculateNextProb is called with the same\n\t * rate all the time, computations are significantly faster. \n\t * \n\t * @param avoidBirthComputation true iff birth process construction shall be delayed\n\t */\n\tpublic void setAvoidBirthComputation(boolean avoidBirthComputation)\n\t{\n\t\tif (!initialising) {\n\t\t\tthrow new IllegalArgumentException(\"this method might not be called after calculateNextRate\");\n\t\t}\n\t\tthis.avoidBirthComputation = avoidBirthComputation;\n\t}\n\n\t/**\n\t * Computes probability to reside in next process stage at given time.\n\t * If this is the nth call to the process, computes the probability\n\t * to reside in the nth stage of the birth process. The rates of the\n\t * birth process up to the n-1th stage have been set by previous calls\n\t * to the function, the nth rate is set by the current call. The time\n\t * probabilities are computed for must have been set previously by\n\t * setTime.\n\t * \n\t * @param rate leaving rate of current state\n\t * @return probability to reside in current stage at given time\n\t * @throws PrismException\n\t */\n\tpublic double calculateNextProb(double rate) throws PrismException\n\t{\n\t\tif (initialising && 0.0 == unifRate && !withRateArray) {\n\t\t\tthrow new IllegalArgumentException(\"unifRate must be set if withRateArray is false\");\n\t\t}\n\t\tif (withRateArray && initialising) {\n\t\t\tjumpRates = new ArrayList<Double>();\n\t\t}\n\t\tinitialising = false;\n\t\tif (!withRateArray && rate > unifRate) {\n\t\t\tthrow new IllegalArgumentException(\"cannot use rates larger than initial rate if withRateArray is false\");\n\t\t}\n\t\tif (withRateArray) {\n\t\t\tjumpRates.add(rate);\n\t\t}\n\t\tboolean recompute = false;\n\t\tif (rate > unifRate) {\n\t\t\tif (!avoidBirthComputation) {\n\t\t\t\trecompute = true;\n\t\t\t\tunifRate = rate * 1.25 * 1.02;\n\t\t\t} else {\n\t\t\t\tunifRate = rate;\n\t\t\t}\n\t\t}\n\t\tif ((jumpRates.size() != 1) && (Math.abs(rate - jumpRates.get(jumpRates.size() - 2)) > 1E-100)) {\n\t\t\tif (avoidBirthComputation) {\n\t\t\t\trecompute = true;\n\t\t\t}\n\t\t\tavoidBirthComputation = false;\n\t\t}\n\t\t\n\t\tif (null == probs || recompute) {\n\t\t\tinitPoisson();\n\t\t}\n\t\tdouble result = 0.0;\n\t\tif (recompute) {\n\t\t\tfor (stageNr = 0; stageNr < jumpRates.size(); stageNr++) {\n\t\t\t\tresult = compNextStageProb(jumpRates.get(stageNr));\n\t\t\t}\n\t\t} else {\n\t\t\tif (avoidBirthComputation) {\n\t\t\t    result = (stageNr < probs.length) ? probs[stageNr] : 0.0;\n\t\t\t\tstageNr++;\n\t\t\t} else {\n\t\t\t\tresult = compNextStageProb(rate);\n\t\t\t\tstageNr++;\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\tprivate double compNextStageProb(double rate)\n\t{\n\t\tassert(rate > 0.0);\n\t\tdouble prob = rate / unifRate; // p = r / q\n\t\tdouble omprob = 1.0 - prob; // 1-p\n\t\tdouble result = 0.0;\n\n\t\tdouble omprobtti = 1.0; // (1-p)^i\n\t\tfor (int i = 0; i < probs.length; i++) {\n\t\t\tresult += omprobtti * probs[i];\n\t\t\tomprobtti *= omprob;\n\t\t}\n\n\t\tnewProbs[newProbs.length - 1] = 0.0;\n\t\tfor (int i = probs.length - 1; i >= 1; i--) {\n\t\t\tnewProbs[i - 1] = newProbs[i] * omprob + probs[i] * prob;\n\t\t}\n\t\tdouble[] temp = probs;\n\t\tprobs = newProbs;\n\t\tnewProbs = temp;\n\t\treturn result;\n\t}\n\n\t/**\n\t * Initialises probability vectors by Poisson probabilities.\n\t */\n\tprivate void initPoisson() throws PrismException\n\t{\n\t\tlong left, right;\n\t\tdouble qt = unifRate * time;\n\t\tdouble acc = epsilon / 8.0;\n\t\tdouble[] weights;\n\t\tdouble totalWeight;\n\t\tif (unifRate * time == 0.0) {\n\t\t\tleft = 0;\n\t\t\tright = 0;\n\t\t\ttotalWeight = 1.0;\n\t\t\tweights = new double[1];\n\t\t\tweights[0] = 1.0;\n\t\t} else {\n\t\t\tFoxGlynn fg = new FoxGlynn(qt, 1e-300, 1e+300, acc);\n\t\t\tleft = fg.getLeftTruncationPoint();\n\t\t\tright = fg.getRightTruncationPoint();\n\t\t\tif (right < 0 || right == Integer.MAX_VALUE) {\n\t\t\t\tthrow new PrismException(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\t\t\t}\n\t\t\tweights = fg.getWeights();\n\t\t\ttotalWeight = fg.getTotalWeight();\n\t\t}\n\t\tfor (long i = left; i <= right; i++) {\n\t\t\tweights[(int) (i - left)] /= totalWeight;\n\t\t}\n\t\tprobs = new double[(int) (right + 1)];\n\t\tnewProbs = new double[(int) (right + 1)];\n\t\tfor (long entryNr = left; entryNr <= right; entryNr++) {\n\t\t\tprobs[(int) entryNr] = weights[(int) (entryNr - left)];\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/Bisimulation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\nimport parser.State;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Class to perform bisimulation minimisation for explicit-state models.\n */\npublic class Bisimulation<Value> extends PrismComponent\n{\n\t// Local storage of partition info\n\tprotected int numStates;\n\tprotected int[] partition;\n\tprotected int numBlocks;\n\tprotected MDPSimple<Value> mdp;\n\n\t/**\n\t * Construct a new Bisimulation object.\n\t */\n\tpublic Bisimulation(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Perform bisimulation minimisation on a model.\n\t * @param model The model\n\t * @param propNames Names of the propositions in {@code propBSs}\n\t * @param propBSs Propositions (satisfying sets of states) to be preserved by bisimulation.\n\t */\n\tpublic Model<Value> minimise(Model<Value> model, List<String> propNames, List<BitSet> propBSs) throws PrismException\n\t{\n\t\tswitch (model.getModelType()) {\n\t\tcase DTMC:\n\t\t\treturn minimiseDTMC((DTMC<Value>) model, propNames, propBSs);\n\t\tcase CTMC:\n\t\t\treturn minimiseCTMC((CTMC<Value>) model, propNames, propBSs);\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Bisimulation minimisation not yet supported for \" + model.getModelType() + \"s\");\n\t\t}\n\t}\n\n\t/**\n\t * Perform bisimulation minimisation on a DTMC.\n\t * @param dtmc The DTMC\n\t * @param propNames Names of the propositions in {@code propBSs}\n\t * @param propBSs Propositions (satisfying sets of states) to be preserved by bisimulation.\n\t */\n\tprivate DTMC<Value> minimiseDTMC(DTMC<Value> dtmc, List<String> propNames, List<BitSet> propBSs)\n\t{\n\t\t// Create initial partition based on propositions\n\t\tinitialisePartitionInfo(dtmc, propBSs);\n\t\t//printPartition(dtmc);\n\n\t\t// Iterative splitting\n\t\tboolean changed = true;\n\t\twhile (changed)\n\t\t\tchanged = splitDTMC(dtmc);\n\t\tmainLog.println(\"Minimisation: \" + numStates + \" to \" + numBlocks + \" States\");\n\t\t//printPartition(dtmc);\n\n\t\t// Build reduced model\n\t\tDTMCSimple<Value> dtmcNew = new DTMCSimple<>(numBlocks);\n\t\tfor (int i = 0; i < numBlocks; i++) {\n\t\t\tfor (Map.Entry<Integer, Value> e : mdp.getChoice(i, 0)) {\n\t\t\t\tdtmcNew.setProbability(i, e.getKey(), e.getValue());\n\t\t\t}\n\t\t}\n\t\tattachStatesAndLabels(dtmc, dtmcNew, propNames, propBSs);\n\n\t\treturn dtmcNew;\n\t}\n\n\t/**\n\t * Perform bisimulation minimisation on a CTMC.\n\t * @param ctmc The CTMC\n\t * @param propNames Names of the propositions in {@code propBSs}\n\t * @param propBSs Propositions (satisfying sets of states) to be preserved by bisimulation.\n\t */\n\tprivate CTMC<Value> minimiseCTMC(CTMC<Value> ctmc, List<String> propNames, List<BitSet> propBSs)\n\t{\n\t\t// Create initial partition based on propositions\n\t\tinitialisePartitionInfo(ctmc, propBSs);\n\t\t//printPartition(ctmc);\n\n\t\t// Iterative splitting\n\t\tboolean changed = true;\n\t\twhile (changed)\n\t\t\tchanged = splitDTMC(ctmc);\n\t\tmainLog.println(\"Minimisation: \" + numStates + \" to \" + numBlocks + \" States\");\n\t\t//printPartition(ctmc);\n\n\t\t// Build reduced model\n\t\tCTMCSimple<Value> ctmcNew = new CTMCSimple<>(numBlocks);\n\t\tfor (int i = 0; i < numBlocks; i++) {\n\t\t\tfor (Map.Entry<Integer, Value> e : mdp.getChoice(i, 0)) {\n\t\t\t\tctmcNew.setProbability(i, e.getKey(), e.getValue());\n\t\t\t}\n\t\t}\n\t\tattachStatesAndLabels(ctmc, ctmcNew, propNames, propBSs);\n\n\t\treturn ctmcNew;\n\t}\n\n\t/**\n\t * Construct the initial partition based on a set of proposition bitsets.\n\t * Store info in {@code numStates}, {@code numBlocks} and {@code partition}.\n\t */\n\tprivate void initialisePartitionInfo(Model<Value> model, List<BitSet> propBSs)\n\t{\n\t\tBitSet bs1, bs0;\n\t\tnumStates = model.getNumStates();\n\t\tpartition = new int[numStates];\n\n\t\t// Compute all non-empty combinations of propositions\n\t\tList<BitSet> all = new ArrayList<BitSet>();\n\t\tbs1 = (BitSet) propBSs.get(0).clone();\n\t\tbs0 = (BitSet) bs1.clone();\n\t\tbs0.flip(0, numStates);\n\t\tall.add(bs1);\n\t\tall.add(bs0);\n\t\tint n = propBSs.size();\n\t\tfor (int i = 1; i < n; i++) {\n\t\t\tBitSet bs = propBSs.get(i);\n\t\t\tint m = all.size();\n\t\t\tfor (int j = 0; j < m; j++) {\n\t\t\t\tbs1 = all.get(j);\n\t\t\t\tbs0 = (BitSet) bs1.clone();\n \t\t\t\tbs0.andNot(bs);\n\t\t\t\tbs1.and(bs);\n\t\t\t\tif (bs1.isEmpty()) {\n\t\t\t\t\tall.set(j, bs0);\n\t\t\t\t} else {\n\t\t\t\t\tif (!bs0.isEmpty())\n\t\t\t\t\t\tall.add(bs0);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Construct initial partition\n\t\tnumBlocks = all.size();\n\t\tfor (int j = 0; j < numBlocks; j++) {\n\t\t\tBitSet bs = all.get(j);\n\t\t\tfor (int i = bs.nextSetBit(0); i >= 0; i = bs.nextSetBit(i + 1)) {\n\t\t\t\tpartition[i] = j;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Perform a split of the current partition, if possible, updating {@code numBlocks} and {@code partition}.\n\t * @return whether or not the partition was split \n\t */\n\tprivate boolean splitDTMC(DTMC<Value> dtmc)\n\t{\n\t\tint s, a, i, numBlocksNew, numChoicesOld;\n\t\tDistribution<Value> distrNew;\n\t\tint partitionNew[];\n\n\t\tpartitionNew = new int[numStates];\n\t\tnumBlocksNew = 0;\n\t\t// Compute the signature for each state (i.e. the distribution for outgoing\n\t\t// transitions, lifted to the current partition)\n\t\t// For convenience, we just store them as an MDP, with action label equal to the index of the block\n\t\tmdp = new MDPSimple<>(numBlocks);\n\t\tfor (s = 0; s < numStates; s++) {\n\t\t\t// Build lifted distribution\n\t\t\tIterator<Map.Entry<Integer, Value>> iter = dtmc.getTransitionsIterator(s);\n\t\t\tdistrNew = new Distribution<>(dtmc.getEvaluator());\n\t\t\twhile (iter.hasNext()) {\n\t\t\t\tMap.Entry<Integer, Value> e = iter.next();\n\t\t\t\tdistrNew.add(partition[e.getKey()], e.getValue());\n\t\t\t}\n\t\t\t// Store in MDP, update new partition\n\t\t\ta = partition[s];\n\t\t\tnumChoicesOld = mdp.getNumChoices(a);\n\t\t\ti = mdp.addChoice(a, distrNew);\n\t\t\tif (i == numChoicesOld)\n\t\t\t\tmdp.setAction(a, i, numBlocksNew++);\n\t\t\tpartitionNew[s] = (Integer) mdp.getAction(a, i);\n\t\t}\n\t\t// Debug info\n\t\t//mainLog.println(\"New partition: \" + java.util.Arrays.toString(partitionNew));\n\t\t//mainLog.println(\"Signatures MDP: \" + mdp.infoString());\n\t\t//mainLog.println(\"Signatures MDP: \" + mdp);\n\t\t//try { mdp.exportToDotFile(\"mdp.dot\"); } catch (PrismException e) {}\n\t\t// Update info\n\t\tboolean changed = numBlocks != numBlocksNew;\n\t\tif (changed) {\n\t\t\t// Note, once converged, we keep the partition from the previous iter\n\t\t\t// because the transition info in the MDP is in terms of this\n\t\t\tpartition = partitionNew;\n\t\t\tnumBlocks = numBlocksNew;\n\t\t}\n\n\t\treturn changed;\n\t}\n\n\t/**\n\t * Display the current partition, showing the states in each block.\n\t */\n\t@SuppressWarnings(\"unused\")\n\tprivate void printPartition(Model<Value> model)\n\t{\n\t\tfor (int i = 0; i < numBlocks; i++) {\n\t\t\tmainLog.print(i + \":\");\n\t\t\tfor (int j = 0; j < numStates; j++)\n\t\t\t\tif (partition[j] == i)\n\t\t\t\t\tif (model.getStatesList() != null)\n\t\t\t\t\t\tmainLog.print(\" \" + model.getStatesList().get(j));\n\t\t\t\t\telse\n\t\t\t\t\t\tmainLog.print(\" \" + j);\n\t\t\tmainLog.println();\n\t\t}\n\t}\n\n\t/**\n\t * Attach a list of states to the minimised model by adding a representative state\n\t * from the original model.\n\t * Also attach information about the propositions (used for bisimulation minimisation)\n\t * to the minimised model, in the form of labels (stored as BitSets).\n\t * @param model The original model\n\t * @param modelNew The minimised model\n\t * @param propNames The names of the propositions\n\t * @param propBSs Satisfying states (of the minimised model) for the propositions\n\t */\n\tprivate void attachStatesAndLabels(Model<Value> model, ModelExplicit<Value> modelNew, List<String> propNames, List<BitSet> propBSs)\n\t{\n\t\t// Attach states\n\t\tif (model.getStatesList() != null) {\n\t\t\tList<State> statesList = model.getStatesList();\n\t\t\tList<State> statesListNew = new ArrayList<State>(numBlocks);\n\t\t\tfor (int i = 0; i < numBlocks; i++) {\n\t\t\t\tstatesListNew.add(null);\n\t\t\t}\n\t\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t\tif (statesListNew.get(partition[i]) == null)\n\t\t\t\t\tstatesListNew.set(partition[i], statesList.get(i));\n\t\t\t}\n\t\t\tmodelNew.setStatesList(statesListNew);\n\t\t}\n\n\t\t// Build/attach new labels\n\t\tint numProps = propBSs.size();\n\t\tfor (int i = 0; i < numProps; i++) {\n\t\t\tString propName = propNames.get(i);\n\t\t\tBitSet propBS = propBSs.get(i);\n\t\t\tBitSet propBSnew = new BitSet();\n\t\t\tfor (int j = propBS.nextSetBit(0); j >= 0; j = propBS.nextSetBit(j + 1))\n\t\t\t\tpropBSnew.set(partition[j]);\n\t\t\tmodelNew.addLabel(propName, propBSnew);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/CTMC.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.Map;\n\nimport prism.ModelType;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state CTMC.\n */\npublic interface CTMC<Value> extends DTMC<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.CTMC;\n\t}\n\n\t// Accessors\n\n\t/**\n\t * Get an iterator over the embedded DTMC transitions from state s.\n\t */\n\tpublic Iterator<Map.Entry<Integer, Value>> getEmbeddedTransitionsIterator(int s);\n\n\t/**\n\t * Get the exit rate for state {@code i}.\n\t * i.e. sum_j R(i,j)\n\t */\n\tpublic Value getExitRate(int i);\n\t\n\t/**\n\t * Compute the maximum exit rate.\n\t * i.e. max_i { sum_j R(i,j) }\n\t */\n\tpublic Value getMaxExitRate();\n\t\n\t/**\n\t * Compute the maximum exit rate over states in {@code subset}.\n\t * i.e. max_{i in subset} { sum_j R(i,j) }\n\t */\n\tpublic Value getMaxExitRate(BitSet subset);\n\t\n\t/**\n\t * Compute the default rate used to uniformise this CTMC. \n\t */\n\tpublic Value getDefaultUniformisationRate();\n\t\n\t/**\n\t * Compute the default rate used to uniformise this CTMC,\n\t * assuming that all states *not* in {@code nonAbs} have been made absorbing.\n\t */\n\tpublic Value getDefaultUniformisationRate(BitSet nonAbs);\n\t\n\t/**\n\t * Build the embedded DTMC for this CTMC, in implicit form\n\t * (i.e. where the details are computed on the fly from this one).\n\t */\n\tpublic DTMC<Value> buildImplicitEmbeddedDTMC();\n\n\t/**\n\t * Get the embedded DTMC for this CTMC, in implicit form\n\t * (i.e. where the details are computed on the fly from this one).\n\t * <p>\n\t * If there is no cached embedded DTMC, build it and cache it.\n\t * Otherwise, return the cached one.\n\t * <p>\n\t * If the underlying CTMC has changed, build a fresh one using\n\t * buildImplicitEmbeddedDTMC, which will update the cached embedded\n\t * DTMC.\n\t */\n\tpublic DTMC<Value> getImplicitEmbeddedDTMC();\n\n\t/**\n\t * Build (a new) embedded DTMC for this CTMC.\n\t */\n\tpublic DTMCSimple<Value> buildEmbeddedDTMC();\n\n\t/**\n\t * Convert this CTMC into a uniformised CTMC.\n\t * @param q Uniformisation rate\n\t */\n\tpublic void uniformise(Value q);\n\n\t/**\n\t * Build the uniformised DTMC for this CTMC, in implicit form\n\t * (i.e. where the details are computed on the fly from this one).\n\t * @param q Uniformisation rate\n\t */\n\tpublic DTMC<Value> buildImplicitUniformisedDTMC(Value q);\n\n\t/**\n\t * Build (a new) uniformised DTMC for this CTMC.\n\t * @param q Uniformisation rate\n\t */\n\tpublic DTMCSimple<Value> buildUniformisedDTMC(Value q);\n\n}\n"
  },
  {
    "path": "prism/src/explicit/CTMCModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.util.*;\n\nimport common.IterableBitSet;\nimport explicit.StateValues;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.Rewards;\nimport explicit.rewards.StateRewardsArray;\nimport parser.ast.*;\nimport prism.*;\n\n/**\n * Explicit-state model checker for continuous-time Markov chains (CTMCs).\n */\npublic class CTMCModelChecker extends ProbModelChecker\n{\n\t/**\n\t * Create a new CTMCModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic CTMCModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\t\n\t// Model checking functions\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tprotected StateValues checkProbPathFormulaLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tthrow new PrismNotSupportedException(\"LTL formulas with time bounds not supported for CTMCs\");\n\t\t}\n\n\t\tif (!(model instanceof ModelExplicit)) {\n\t\t\t// needs a ModelExplicit to allow attaching labels in the handleMaximalStateFormulas step\n\t\t\tthrow new PrismNotSupportedException(\"Need CTMC with ModelExplicit for LTL checking\");\n\t\t}\n\t\t// we first handle the sub-formulas by computing their satisfaction sets,\n\t\t// attaching them as labels to the model and modifying the formula\n\t\t// appropriately\n\t\texpr = handleMaximalStateFormulas((ModelExplicit<?>) model, expr);\n\n\t\t// Now, we construct embedded DTMC and do the plain LTL computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ((CTMC<Double>)model).getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().checkProbPathFormulaLTL(dtmcEmb, expr, qual, minMax, statesOfInterest);\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tprotected StateValues checkRewardCoSafeLTL(Model<?> model, Rewards<?> modelRewards, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tthrow new PrismNotSupportedException(\"LTL formulas with time bounds not supported for CTMCs\");\n\t\t}\n\n\t\tif (!(model instanceof ModelExplicit)) {\n\t\t\t// needs a ModelExplicit to allow attaching labels in the handleMaximalStateFormulas step\n\t\t\tthrow new PrismNotSupportedException(\"Need CTMC with ModelExplicit for cosafety LTL reward checking\");\n\t\t}\n\t\t// we first handle the sub-formulas by computing their satisfaction sets,\n\t\t// attaching them as labels to the model and modifying the formula\n\t\t// appropriately\n\t\texpr = handleMaximalStateFormulas((ModelExplicit<?>) model, expr);\n\n\t\t// Construct embedded DTMC (and convert rewards for it) and do remaining computation\n\t\t// on that with the \"pure\" cosafety LTL formula\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ((CTMC<Double>)model).getImplicitEmbeddedDTMC();\n\t\tint n = model.getNumStates();\n\t\tStateRewardsArray rewEmb = new StateRewardsArray(n);\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\trewEmb.setStateReward(i, ((MCRewards<Double>) modelRewards).getStateReward(i) / ((CTMC<Double>)model).getExitRate(i));\n\t\t}\n\t\treturn createDTMCModelChecker().checkRewardCoSafeLTL(dtmcEmb, rewEmb, expr, minMax, statesOfInterest);\n\t}\n\n\t@Override\n\tprotected StateValues checkExistsLTL(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tthrow new PrismNotSupportedException(\"LTL formulas with time bounds not supported for CTMCs\");\n\t\t}\n\n\t\tif (!(model instanceof ModelExplicit)) {\n\t\t\t// needs a ModelExplicit to allow attaching labels in the handleMaximalStateFormulas step\n\t\t\tthrow new PrismNotSupportedException(\"Need CTMC with ModelExplicit for LTL checking\");\n\t\t}\n\t\t// we first handle the sub-formulas by computing their satisfaction sets,\n\t\t// attaching them as labels to the model and modifying the formula\n\t\t// appropriately\n\t\texpr = handleMaximalStateFormulas((ModelExplicit<?>) model, expr);\n\n\t\t// Now, we construct embedded DTMC and do the plain E[ LTL ] computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<?> dtmcEmb = ((CTMC<?>)model).getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().checkExistsLTL(dtmcEmb, expr, statesOfInterest);\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tprotected StateValues checkProbBoundedUntil(Model<?> model, ExpressionTemporal expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tdouble lTime, uTime; // time bounds\n\t\tExpression exprTmp;\n\t\tBitSet b1, b2, tmp;\n\t\tStateValues probs = null;\n\t\tModelCheckerResult tmpRes = null, res = null;\n\n\t\t// get info from bounded until\n\n\t\t// lower bound is 0 if not specified\n\t\t// (i.e. if until is of form U<=t)\n\t\texprTmp = expr.getLowerBound();\n\t\tif (exprTmp != null) {\n\t\t\tlTime = exprTmp.evaluateDouble(constantValues);\n\t\t\tif (lTime < 0) {\n\t\t\t\tthrow new PrismException(\"Invalid lower bound \" + lTime + \" in time-bounded until formula\");\n\t\t\t}\n\t\t} else {\n\t\t\tlTime = 0;\n\t\t}\n\t\t// upper bound is -1 if not specified\n\t\t// (i.e. if until is of form U>=t)\n\t\texprTmp = expr.getUpperBound();\n\t\tif (exprTmp != null) {\n\t\t\tuTime = exprTmp.evaluateDouble(constantValues);\n\t\t\tif (uTime < 0 || (uTime == 0 && expr.upperBoundIsStrict())) {\n\t\t\t\tString bound = (expr.upperBoundIsStrict() ? \"<\" : \"<=\") + uTime;\n\t\t\t\tthrow new PrismException(\"Invalid upper bound \" + bound + \" in time-bounded until formula\");\n\t\t\t}\n\t\t\tif (uTime < lTime) {\n\t\t\t\tthrow new PrismException(\"Upper bound must exceed lower bound in time-bounded until formula\");\n\t\t\t}\n\t\t} else {\n\t\t\tuTime = -1;\n\t\t}\n\n\t\t// model check operands first for all states\n\t\tb1 = checkExpression(model, expr.getOperand1(), null).getBitSet();\n\t\tb2 = checkExpression(model, expr.getOperand2(), null).getBitSet();\n\n\t\t// compute probabilities\n\n\t\t// a trivial case: \"U<=0\"\n\t\tif (lTime == 0 && uTime == 0) {\n\t\t\t// prob is 1 in b2 states, 0 otherwise\n\t\t\tprobs = StateValues.createFromBitSetAsDoubles(b2, model);\n\t\t} else {\n\n\t\t\t// break down into different cases to compute probabilities\n\n\t\t\t// >= lTime\n\t\t\tif (uTime == -1) {\n\t\t\t\t// check for special case of lTime == 0, this is actually an unbounded until\n\t\t\t\tif (lTime == 0) {\n\t\t\t\t\t// compute probs\n\t\t\t\t\tres = computeUntilProbs((CTMC<Double>)model, b1, b2);\n\t\t\t\t\tprobs = StateValues.createFromDoubleArray(res.soln, model);\n\t\t\t\t} else {\n\t\t\t\t\t// compute unbounded until probs\n\t\t\t\t\ttmpRes = computeUntilProbs((CTMC<Double>)model, b1, b2);\n\t\t\t\t\t// compute bounded until probs\n\t\t\t\t\tres = computeTransientBackwardsProbs((CTMC<Double>) model, b1, b1, lTime, tmpRes.soln);\n\t\t\t\t\tprobs = StateValues.createFromDoubleArray(res.soln, model);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// <= uTime\n\t\t\telse if (lTime == 0) {\n\t\t\t\t// nb: uTime != 0 since would be caught above (trivial case)\n\t\t\t\tb1.andNot(b2);\n\t\t\t\tres = computeTransientBackwardsProbs((CTMC<Double>) model, b2, b1, uTime, null);\n\t\t\t\tprobs = StateValues.createFromDoubleArray(res.soln, model);\n\t\t\t\t// set values to exactly 1 for target (b2) states\n\t\t\t\t// (these are computed inexactly during uniformisation)\n\t\t\t\tint n = model.getNumStates();\n\t\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\t\tif (b2.get(i))\n\t\t\t\t\t\tprobs.setValue(i, 1.0);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// [lTime,uTime] (including where lTime == uTime)\n\t\t\telse {\n\t\t\t\ttmp = (BitSet) b1.clone();\n\t\t\t\ttmp.andNot(b2);\n\t\t\t\ttmpRes = computeTransientBackwardsProbs((CTMC<Double>) model, b2, tmp, uTime - lTime, null);\n\t\t\t\tres = computeTransientBackwardsProbs((CTMC<Double>) model, b1, b1, lTime, tmpRes.soln);\n\t\t\t\tprobs = StateValues.createFromDoubleArray(res.soln, model);\n\t\t\t}\n\t\t}\n\n\t\treturn probs;\n\t}\n\n\t// Steady-state/transient probability computation\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doSteadyState(CTMC<Double> ctmc) throws PrismException\n\t{\n\t\treturn doSteadyState(ctmc, (StateValues) null);\n\t}\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Optionally, use the passed in file initDistFile to give the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doSteadyState(CTMC<Double> ctmc, File initDistFile) throws PrismException\n\t{\n\t\tStateValues initDist = readDistributionFromFile(initDistFile, ctmc);\n\t\treturn doSteadyState(ctmc, initDist);\n\t}\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Optionally, use the passed in vector initDist as the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * For reasons of efficiency, when a vector is passed in, it will be trampled over,\n\t * so if you wanted it, take a copy.\n\t * @param ctmc The CTMC\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic StateValues doSteadyState(CTMC<Double> ctmc, StateValues initDist) throws PrismException\n\t{\n\t\tStateValues initDistNew = (initDist == null) ? buildInitialDistribution(ctmc) : initDist;\n\t\tModelCheckerResult res = computeSteadyStateProbs(ctmc, initDistNew.getDoubleArray());\n\t\treturn StateValues.createFromDoubleArray(res.soln, ctmc);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doTransient(CTMC<Double> ctmc, double time) throws PrismException\n\t{\n\t\treturn doTransient(ctmc, time, (StateValues) null);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Optionally, use the passed in file initDistFile to give the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * @param ctmc The CTMC\n\t * @param t Time point\n\t * @param initDistFile File containing initial distribution\n\t */\n\tpublic StateValues doTransient(CTMC<Double> ctmc, double t, File initDistFile) throws PrismException\n\t{\n\t\tStateValues initDist = readDistributionFromFile(initDistFile, ctmc);\n\t\treturn doTransient(ctmc, t, initDist);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Optionally, use the passed in vector initDist as the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * For reasons of efficiency, when a vector is passed in, it will be trampled over,\n\t * so if you wanted it, take a copy. \n\t * @param ctmc The CTMC\n\t * @param t Time point\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic StateValues doTransient(CTMC<Double> ctmc, double t, StateValues initDist) throws PrismException\n\t{\n\t\tStateValues initDistNew = (initDist == null) ? buildInitialDistribution(ctmc) : initDist;\n\t\tModelCheckerResult res = computeTransientProbs(ctmc, t, initDistNew.getDoubleArray());\n\t\treturn StateValues.createFromDoubleArray(res.soln, ctmc);\n\t}\n\n\t// Numerical computation functions\n\n\t/**\n\t * Compute next=state probabilities.\n\t * i.e. compute the probability of being in a state in {@code target} in the next step.\n\t * @param ctmc The CTMC\n\t * @param target Target states\n\t */\n\tpublic ModelCheckerResult computeNextProbs(CTMC<Double> ctmc, BitSet target) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeNextProbs(dtmcEmb, target);\n\t}\n\n\t/**\n\t * Compute reachability probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target}.\n\t * @param ctmc The CTMC\n\t * @param target Target states\n\t */\n\tpublic ModelCheckerResult computeReachProbs(CTMC<Double> ctmc, BitSet target) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeReachProbs(dtmcEmb, target);\n\t}\n\n\t/**\n\t * Compute until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * while remaining in those in @{code remain}.\n\t * @param ctmc The CTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t */\n\tpublic ModelCheckerResult computeUntilProbs(CTMC<Double> ctmc, BitSet remain, BitSet target) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeUntilProbs(dtmcEmb, remain, target);\n\t}\n\n\t/**\n\t * Compute reachability/until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * while remaining in those in @{code remain}.\n\t * @param ctmc The CTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param init Optionally, an initial solution vector (may be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tpublic ModelCheckerResult computeReachProbs(CTMC<Double> ctmc, BitSet remain, BitSet target, double init[], BitSet known) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeReachProbs(dtmcEmb, remain, target, init, known);\n\t}\n\n\t/**\n\t * Compute time-bounded reachability probabilities,\n\t * i.e. compute the probability of reaching a state in {@code target} within time {@code t}.\n\t * @param ctmc The CTMC\n\t * @param target Target states\n\t * @param t Time bound\n\t */\n\tpublic ModelCheckerResult computeTimeBoundedReachProbs(CTMC<Double> ctmc, BitSet target, double t) throws PrismException\n\t{\n\t\treturn computeTimeBoundedUntilProbs(ctmc, null, target, t);\n\t}\n\n\t/**\n\t * Compute time-bounded until probabilities,\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * within time {@code t}, and while remaining in states in {@code remain}.\n\t * @param ctmc The CTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param t Time bound\n\t */\n\tpublic ModelCheckerResult computeTimeBoundedUntilProbs(CTMC<Double> ctmc, BitSet remain, BitSet target, double t) throws PrismException\n\t{\n\t\tBitSet nonAbs = null;\n\t\tif (remain != null) {\n\t\t\tnonAbs = (BitSet) remain.clone();\n\t\t\tnonAbs.andNot(target);\n\t\t}\n\t\tModelCheckerResult res = computeTransientBackwardsProbs(ctmc, target, nonAbs, t, null);\n\t\t// Set values to exactly 1 for target states\n\t\t// (these are computed inexactly during uniformisation)\n\t\tint n = ctmc.getNumStates();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (target.get(i))\n\t\t\t\tres.soln[i] = 1.0;\n\t\t}\n\t\treturn res;\n\t}\n\n\t/**\n\t * Perform transient probability computation, as required for (e.g. CSL) model checking.\n\t * Compute, for each state, the sum over {@code target} states\n\t * of the probability of being in that state at time {@code t}\n\t * multiplied by the corresponding probability in the vector {@code multProbs},\n\t * assuming that all states *not* in {@code nonAbs} are made absorbing.\n\t * If {@code multProbs} is null, it is assumed to be all 1s.\n\t * @param ctmc The CTMC\n\t * @param target Target states\n\t * @param nonAbs States *not* to be made absorbing (optional: null means \"all\")\n\t * @param t Time bound\n\t * @param multProbs Multiplication vector (optional: null means all 1s)\n\t */\n\tpublic ModelCheckerResult computeTransientBackwardsProbs(CTMC<Double> ctmc, BitSet target, BitSet nonAbs, double t, double multProbs[]) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[], sum[];\n\t\tDTMC<Double> dtmc;\n\t\tlong timer;\n\t\t// Fox-Glynn stuff\n\t\tFoxGlynn fg;\n\t\tint left, right;\n\t\tdouble q, qt, acc, weights[], totalWeight;\n\n\t\t// Optimisations: If (nonAbs is empty or t = 0) and multProbs is null, this is easy.\n\t\tif (((nonAbs != null && nonAbs.isEmpty()) || (t == 0)) && multProbs == null) {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(target, ctmc.getNumStates());\n\t\t\treturn res;\n\t\t}\n\n\t\t// Start backwards transient computation\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting backwards transient probability computation...\");\n\n\t\t// Store num states\n\t\tn = ctmc.getNumStates();\n\n\t\t// Get uniformisation rate; do Fox-Glynn\n\t\tq = ctmc.getDefaultUniformisationRate(nonAbs);\n\t\tqt = q * t;\n\t\tmainLog.println(\"\\nUniformisation: q.t = \" + q + \" x \" + t + \" = \" + qt);\n\t\tacc = termCritParam / 8.0;\n\t\tfg = new FoxGlynn(qt, 1e-300, 1e+300, acc);\n\t\tleft = fg.getLeftTruncationPoint();\n\t\tright = fg.getRightTruncationPoint();\n\t\tif (right < 0) {\n\t\t\tthrow new PrismException(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\t\t}\n\t\tweights = fg.getWeights();\n\t\ttotalWeight = fg.getTotalWeight();\n\t\tfor (i = left; i <= right; i++) {\n\t\t\tweights[i - left] /= totalWeight;\n\t\t}\n\t\tmainLog.println(\"Fox-Glynn (\" + acc + \"): left = \" + left + \", right = \" + right);\n\n\t\t// Build (implicit) uniformised DTMC\n\t\tdtmc = ctmc.buildImplicitUniformisedDTMC(q);\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\t\tsum = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\t// Vectors soln/soln2 are 1 for target states, or multProbs[i] if supplied.\n\t\t// Vector sum is all zeros (done by array creation).\n\t\tif (multProbs != null) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? multProbs[i] : 0.0;\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : 0.0;\n\t\t}\n\n\t\t// If necessary, do 0th element of summation (doesn't require any matrix powers)\n\t\tif (left == 0)\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsum[i] += weights[0] * soln[i];\n\n\t\t// Start iterations\n\t\titers = 1;\n\t\twhile (iters <= right) {\n\t\t\t// Matrix-vector multiply\n\t\t\tdtmc.mvMult(soln, soln2, nonAbs, false);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t\t// Add to sum\n\t\t\tif (iters >= left) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsum[i] += weights[iters - left] * soln[i];\n\t\t\t}\n\t\t\titers++;\n\t\t}\n\n\t\t// Finished backwards transient computation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Backwards transient probability computation\");\n\t\tmainLog.println(\" took \" + iters + \" iters and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = sum;\n\t\tres.lastSoln = soln2;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Perform cumulative reward computation.\n\t * Compute, for each state of {@ctmc}, the expected rewards accumulated until {@code t}\n\t * when starting in this state and using reward structure {@code mcRewards}.\n\t * @param ctmc The CTMC\n\t * @param mcRewards The rewards\n\t * @param t Time bound\n\t */\n\tpublic ModelCheckerResult computeCumulativeRewards(CTMC<Double> ctmc, MCRewards<Double> mcRewards, double t) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[], sum[];\n\t\tlong timer;\n\t\t// Fox-Glynn stuff\n\t\tFoxGlynn fg;\n\t\tint left, right;\n\t\tdouble q, qt, acc, weights[], totalWeight;\n\n\t\t// Optimisation: If t = 0, this is easy.\n\t\tif (t == 0) {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = new double[ctmc.getNumStates()];\n\t\t\treturn res;\n\t\t}\n\n\t\t// Start backwards transient computation\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting backwards cumulative rewards computation...\");\n\n\t\t// Store num states\n\t\tn = ctmc.getNumStates();\n\n\t\t// Get uniformisation rate; do Fox-Glynn\n\t\tq = ctmc.getDefaultUniformisationRate();\n\t\tqt = q * t;\n\t\tmainLog.println(\"\\nUniformisation: q.t = \" + q + \" x \" + t + \" = \" + qt);\n\t\tacc = termCritParam / 8.0;\n\t\tfg = new FoxGlynn(qt, 1e-300, 1e+300, acc);\n\t\tleft = fg.getLeftTruncationPoint();\n\t\tright = fg.getRightTruncationPoint();\n\t\tif (right < 0) {\n\t\t\tthrow new PrismException(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\t\t}\n\t\tweights = fg.getWeights();\n\t\ttotalWeight = fg.getTotalWeight();\n\t\tfor (i = left; i <= right; i++) {\n\t\t\tweights[i - left] /= totalWeight;\n\t\t}\n\n\t\t// modify the poisson probabilities to what we need for this computation\n\t\t// first make the kth value equal to the sum of the values for 0...k\n\t\tfor (i = left+1; i <= right; i++) {\n\t\t\tweights[i - left] += weights[i - 1 - left];\n\t\t}\n\t\t// then subtract from 1 and divide by uniformisation constant (q) to give mixed poisson probabilities\n\t\tfor (i = left; i <= right; i++) {\n\t\t\tweights[i - left] = (1 - weights[i - left]) / q;\n\t\t}\n\t\tmainLog.println(\"Fox-Glynn (\" + acc + \"): left = \" + left + \", right = \" + right);\n\n\t\t// Build (implicit) uniformised DTMC\n\t\tDTMC<Double> dtmcUnif = ctmc.buildImplicitUniformisedDTMC(q);\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = mcRewards.getStateReward(i);\n\n\t\t// do 0th element of summation (doesn't require any matrix powers)\n\t\tsum = new double[n];\n\t\tif (left == 0) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsum[i] += weights[0] * soln[i];\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsum[i] += soln[i] / q;\n\t\t}\n\n\t\t// Start iterations\n\t\titers = 1;\n\t\twhile (iters <= right) {\n\t\t\t// Matrix-vector multiply\n\t\t\tdtmcUnif.mvMult(soln, soln2, null, false);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t\t// Add to sum\n\t\t\tif (iters >= left) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsum[i] += weights[iters - left] * soln[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsum[i] += soln[i] / q;\n\t\t\t}\n\t\t\titers++;\n\t\t}\n\n\t\t// Finished backwards transient computation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Backwards transient cumulative rewards computation\");\n\t\tmainLog.println(\" took \" + iters + \" iters and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = sum;\n\t\tres.lastSoln = soln2;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected total rewards.\n\t * @param ctmc The CTMC\n\t * @param mcRewards The rewards\n\t */\n\tpublic ModelCheckerResult computeTotalRewards(CTMC<Double> ctmc, MCRewards<Double> mcRewards) throws PrismException\n\t{\n\t\tint i, n;\n\t\t// Build embedded DTMC\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\t\t// Convert rewards\n\t\tn = ctmc.getNumStates();\n\t\tStateRewardsArray rewEmb = new StateRewardsArray(n);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\trewEmb.setStateReward(i, mcRewards.getStateReward(i) / ctmc.getExitRate(i));\n\t\t}\n\t\t// Do computation on DTMC\n\t\treturn createDTMCModelChecker().computeTotalRewards(dtmcEmb, rewEmb);\n\t}\n\n\t/**\n\t * Perform instantaneous reward computation.\n\t * Compute, for each state of {@ctmc}, the expected rewards at time {@code t}\n\t * when starting in this state and using reward structure {@code mcRewards}.\n\t * @param ctmc The CTMC\n\t * @param mcRewards The rewards\n\t * @param t Time bound\n\t */\n\tpublic ModelCheckerResult computeInstantaneousRewards(CTMC<Double> ctmc, MCRewards<Double> mcRewards, double t) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[], sum[];\n\t\tlong timer;\n\t\t// Fox-Glynn stuff\n\t\tFoxGlynn fg;\n\t\tint left, right;\n\t\tdouble q, qt, acc, weights[], totalWeight;\n\n\t\t// Store num states\n\t\tn = ctmc.getNumStates();\n\n\t\t// Optimisation: If t = 0, this is easy.\n\t\tif (t == 0) {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = new double[ctmc.getNumStates()];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tres.soln[i] = mcRewards.getStateReward(i);\n\t\t\treturn res;\n\t\t}\n\n\t\t// Start backwards transient computation\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting backwards instantaneous rewards computation...\");\n\n\t\t// Get uniformisation rate; do Fox-Glynn\n\t\tq = ctmc.getDefaultUniformisationRate();\n\t\tqt = q * t;\n\t\tmainLog.println(\"\\nUniformisation: q.t = \" + q + \" x \" + t + \" = \" + qt);\n\t\tacc = termCritParam / 8.0;\n\t\tfg = new FoxGlynn(qt, 1e-300, 1e+300, acc);\n\t\tleft = fg.getLeftTruncationPoint();\n\t\tright = fg.getRightTruncationPoint();\n\t\tif (right < 0) {\n\t\t\tthrow new PrismException(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\t\t}\n\t\tweights = fg.getWeights();\n\t\ttotalWeight = fg.getTotalWeight();\n\t\tfor (i = left; i <= right; i++) {\n\t\t\tweights[i - left] /= totalWeight;\n\t\t}\n\n\t\tmainLog.println(\"Fox-Glynn (\" + acc + \"): left = \" + left + \", right = \" + right);\n\n\t\t// Build (implicit) uniformised DTMC\n\t\tDTMC<Double> dtmcUnif = ctmc.buildImplicitUniformisedDTMC(q);\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = mcRewards.getStateReward(i);\n\n\t\t// do 0th element of summation (doesn't require any matrix powers)\n\t\tsum = new double[n];\n\t\tif (left == 0)\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsum[i] += weights[0] * soln[i];\n\n\t\t// Start iterations\n\t\titers = 1;\n\t\twhile (iters <= right) {\n\t\t\t// Matrix-vector multiply\n\t\t\tdtmcUnif.mvMult(soln, soln2, null, false);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t\t// Add to sum\n\t\t\tif (iters >= left) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsum[i] += weights[iters - left] * soln[i];\n\t\t\t}\n\t\t\titers++;\n\t\t}\n\n\t\t// Finished backwards transient computation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Backwards transient instantaneous rewards computation\");\n\t\tmainLog.println(\" took \" + iters + \" iters and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = sum;\n\t\tres.lastSoln = soln2;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards.\n\t * @param ctmc The CTMC\n\t * @param mcRewards The rewards\n\t * @param target Target states\n\t */\n\tpublic ModelCheckerResult computeReachRewards(CTMC<Double> ctmc, MCRewards<Double> mcRewards, BitSet target) throws PrismException\n\t{\n\t\tint i, n;\n\t\t// Build embedded DTMC\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\t\t// Convert rewards\n\t\tn = ctmc.getNumStates();\n\t\tStateRewardsArray rewEmb = new StateRewardsArray(n);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\trewEmb.setStateReward(i, mcRewards.getStateReward(i) / ctmc.getExitRate(i));\n\t\t}\n\t\t// Do computation on DTMC\n\t\treturn createDTMCModelChecker().computeReachRewards(dtmcEmb, rewEmb, target);\n\t}\n\n\t/**\n\t * We compute steady-state probabilities in the embedded DTMC.\n\t * To take the exit rates into account, we have to weight the\n\t * steady-state probabilities in each BSCC, using this post-processor.\n\t * See: Baier et al, \"Approximate Symbolic Model Checking of Continuous-Time Markov Chains\"\n\t * CONCUR'99, p. 151\n\t */\n\tprivate static class SteadyStateBSCCPostProcessor implements DTMCModelChecker.BSCCPostProcessor {\n\t\tprivate CTMC<Double> ctmc;\n\n\t\tpublic SteadyStateBSCCPostProcessor(CTMC<Double> ctmc)\n\t\t{\n\t\t\tthis.ctmc = ctmc;\n\t\t}\n\n\t\t@Override\n\t\tpublic void apply(double[] soln, BitSet bscc)\n\t\t{\n\t\t\t// compute sum_{s in BSCC} pi'[s] / E[S]\n\t\t\t// where pi' are the steady-state probabilities in the BSCC of the embedded DTMC\n\t\t\tdouble sum = 0.0;\n\t\t\tfor (int s : IterableBitSet.getSetBits(bscc)) {\n\t\t\t\tdouble E = ctmc.getExitRate(s);\n\t\t\t\tif (E == 0.0) // corner case: no outgoing transitions -> self-loop with rate 1\n\t\t\t\t\tE = 1.0;\n\n\t\t\t\tsum += soln[s] / E;\n\t\t\t}\n\n\t\t\t// set pi[s] = pi'[s] / sum for each state s in BSCC, where again\n\t\t\t// pi' are the steady-state probabilities in the BSCC of the embedded DTMC\n\t\t\t// and pi are the steady-state probabilities in the BSCC of the original CTMC\n\t\t\tfor (int s : IterableBitSet.getSetBits(bscc)) {\n\t\t\t\tdouble E = ctmc.getExitRate(s);\n\t\t\t\tif (E == 0.0) // corner case: no outgoing transitions -> self-loop with rate 1\n\t\t\t\t\tE = 1.0;\n\n\t\t\t\tsoln[s] /= E;\n\t\t\t\tsoln[s] /= sum;\n\t\t\t}\n\t\t}\n\n\t}\n\n\t/**\n\t * Compute steady-state probabilities for an S operator, i.e., S=?[ b ].\n\t * @param ctmc the CTMC\n\t * @param b the satisfaction set of states for the inner state formula of the operators\n\t */\n\tprotected StateValues computeSteadyStateFormula(CTMC<Double> ctmc, BitSet b) throws PrismException\n\t{\n\t\tdouble multProbs[] = Utils.bitsetToDoubleArray(b, ctmc.getNumStates());\n\n\t\t// We construct the embedded DTMC and do the steady-state computation there\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\n\t\t// compute the steady-state probabilities in the embedded DTMC, applying the BSCC value post-processing\n\t\tmainLog.println(\"Doing steady-state computation in embedded DTMC (with exit-rate weighting for BSCC probabilities)...\");\n\t\tModelCheckerResult res = createDTMCModelChecker().computeSteadyStateBackwardsProbs(dtmcEmb, multProbs, new SteadyStateBSCCPostProcessor(ctmc));\n\t\treturn StateValues.createFromDoubleArray(res.soln, ctmc);\n\t}\n\n\t/**\n\t * Compute (forwards) steady-state probabilities\n\t * i.e. compute the long-run probability of being in each state,\n\t * assuming the initial distribution {@code initDist}.\n\t * For space efficiency, the initial distribution vector will be modified and values over-written,\n\t * so if you wanted it, take a copy.\n\t * @param ctmc The CTMC\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic ModelCheckerResult computeSteadyStateProbs(CTMC<Double> ctmc, double initDist[]) throws PrismException\n\t{\n\t\t// We construct the embedded DTMC and do the steady-state computation there\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\n\t\t// compute the steady-state probabilities in the embedded DTMC, applying the BSCC value post-processing\n\t\tmainLog.println(\"Doing steady-state computation in embedded DTMC (with exit-rate weighting for BSCC probabilities)...\");\n\t\treturn createDTMCModelChecker().computeSteadyStateProbs(dtmcEmb, initDist, new SteadyStateBSCCPostProcessor(ctmc));\n\t}\n\n\t/**\n\t * @see DTMCModelChecker#computeSteadyStateProbsForBSCC}\n\t */\n\tpublic ModelCheckerResult computeSteadyStateProbsForBSCC(CTMC<Double> ctmc, BitSet states, double result[]) throws PrismException\n\t{\n\t\t// We construct the embedded DTMC and do the steady-state computation there\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\n\t\treturn createDTMCModelChecker().computeSteadyStateProbsForBSCC(dtmcEmb, states, result, new SteadyStateBSCCPostProcessor(ctmc));\n\t}\n\n\t/**\n\t * Compute steady-state rewards, i.e., R=?[ S ].\n\t * @param ctmc the CTMC\n\t * @param modelRewards the (state) rewards\n\t */\n\tpublic ModelCheckerResult computeSteadyStateRewards(CTMC<Double> ctmc, MCRewards<Double> modelRewards) throws PrismException\n\t{\n\t\tint n = ctmc.getNumStates();\n\t\tdouble multRewards[] = new double[n];\n\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tmultRewards[i] = modelRewards.getStateReward(i);\n\t\t}\n\n\t\t// We construct the embedded DTMC and do the steady-state computation there\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<Double> dtmcEmb = ctmc.getImplicitEmbeddedDTMC();\n\n\t\t// compute the steady-state rewards in the embedded DTMC, applying the BSCC value post-processing\n\t\tmainLog.println(\"Doing steady-state computation in embedded DTMC (with exit-rate weighting for BSCC probabilities)...\");\n\t\treturn createDTMCModelChecker().computeSteadyStateBackwardsProbs(dtmcEmb, multRewards, new SteadyStateBSCCPostProcessor(ctmc));\n\t}\n\n\t/**\n\t * Compute transient probabilities.\n\t * i.e. compute the probability of being in each state at time {@code t},\n\t * assuming the initial distribution {@code initDist}. \n\t * For space efficiency, the initial distribution vector will be modified and values over-written,  \n\t * so if you wanted it, take a copy. \n\t * @param ctmc The CTMC\n\t * @param t Time point\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic ModelCheckerResult computeTransientProbs(CTMC<Double> ctmc, double t, double initDist[]) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[], sum[];\n\t\tDTMC<Double> dtmc;\n\t\tlong timer;\n\t\t// Fox-Glynn stuff\n\t\tFoxGlynn fg;\n\t\tint left, right;\n\t\tdouble q, qt, acc, weights[], totalWeight;\n\n\t\t// Start bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting transient probability computation...\");\n\n\t\t// Store num states\n\t\tn = ctmc.getNumStates();\n\n\t\t// Get uniformisation rate; do Fox-Glynn\n\t\tq = ctmc.getDefaultUniformisationRate();\n\t\tqt = q * t;\n\t\tmainLog.println(\"\\nUniformisation: q.t = \" + q + \" x \" + t + \" = \" + qt);\n\t\tacc = termCritParam / 8.0;\n\t\tfg = new FoxGlynn(qt, 1e-300, 1e+300, acc);\n\t\tleft = fg.getLeftTruncationPoint();\n\t\tright = fg.getRightTruncationPoint();\n\t\tif (right < 0) {\n\t\t\tthrow new PrismException(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\t\t}\n\t\tweights = fg.getWeights();\n\t\ttotalWeight = fg.getTotalWeight();\n\t\tfor (i = left; i <= right; i++) {\n\t\t\tweights[i - left] /= totalWeight;\n\t\t}\n\t\tmainLog.println(\"Fox-Glynn (\" + acc + \"): left = \" + left + \", right = \" + right);\n\n\t\t// Build (implicit) uniformised DTMC\n\t\tdtmc = ctmc.buildImplicitUniformisedDTMC(q);\n\n\t\t// Create solution vector(s)\n\t\t// For soln, we just use init (since we are free to modify this vector)\n\t\tsoln = initDist;\n\t\tsoln2 = new double[n];\n\t\tsum = new double[n];\n\n\t\t// Initialise solution vectors\n\t\t// (don't need to do soln2 since will be immediately overwritten)\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsum[i] = 0.0;\n\n\t\t// If necessary, do 0th element of summation (doesn't require any matrix powers)\n\t\tif (left == 0)\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsum[i] += weights[0] * soln[i];\n\n\t\t// Start iterations\n\t\titers = 1;\n\t\twhile (iters <= right) {\n\t\t\t// Matrix-vector multiply\n\t\t\tdtmc.vmMult(soln, soln2);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t\t// Add to sum\n\t\t\tif (iters >= left) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsum[i] += weights[iters - left] * soln[i];\n\t\t\t}\n\t\t\titers++;\n\t\t}\n\n\t\t// Finished bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Transient probability computation\");\n\t\tmainLog.println(\" took \" + iters + \" iters and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = sum;\n\t\tres.lastSoln = soln2;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\t// Utility methods\n\t\n\t/**\n\t * Create a new DTMC model checker with the same settings as this one. \n\t */\n\tprivate DTMCModelChecker createDTMCModelChecker() throws PrismException\n\t{\n\t\tDTMCModelChecker mcDTMC = new DTMCModelChecker(this);\n\t\tmcDTMC.inheritSettings(this);\n\t\treturn mcDTMC;\n\t}\n\n\t// ------------------ CTL model checking ------------------------------------------------\n\t//\n\t// For CTL model checking, the actual computation happens in the\n\t// embedded DTMC (due to the possibility of a zero exit rate turning\n\t// into a self-loop.\n\t// So, we don't override the check... methods (so that recursive computation\n\t// of the subformulas happens in the CTMCModelChecker), but override the\n\t// compute... methods to use a DTMCModelChecker for the computations instead\n\n\t@Override\n\tpublic BitSet computeExistsNext(Model<?> model, BitSet target, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do CTL computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<?> dtmcEmb = ((CTMC<?>)model).getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeExistsNext(dtmcEmb, target, statesOfInterest);\n\t}\n\n\t@Override\n\tpublic BitSet computeForAllNext(Model<?> model, BitSet target, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do CTL computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<?> dtmcEmb = ((CTMC<?>)model).getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeForAllNext(dtmcEmb, target, statesOfInterest);\n\t}\n\n\t@Override\n\tpublic BitSet computeExistsUntil(Model<?> model, BitSet A, BitSet B) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do CTL computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<?> dtmcEmb = ((CTMC<?>)model).getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeExistsUntil(dtmcEmb, A, B);\n\t}\n\n\tpublic BitSet computeExistsGlobally(Model<?> model, BitSet A) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do CTL computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<?> dtmcEmb = ((CTMC<?>)model).getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeExistsGlobally(dtmcEmb, A);\n\t}\n\n\tpublic BitSet computeExistsRelease(Model<?> model, BitSet A, BitSet B) throws PrismException\n\t{\n\t\t// Construct embedded DTMC and do CTL computation on that\n\t\tmainLog.println(\"Building embedded DTMC...\");\n\t\tDTMC<?> dtmcEmb = ((CTMC<?>)model).getImplicitEmbeddedDTMC();\n\t\treturn createDTMCModelChecker().computeExistsRelease(dtmcEmb, A, B);\n\t}\n\n\t/**\n\t * Simple test program.\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tCTMCModelChecker mc;\n\t\tCTMCSimple<Double> ctmc;\n\t\tModelCheckerResult res;\n\t\tBitSet target;\n\t\tMap<String, BitSet> labels;\n\t\ttry {\n\t\t\tmc = new CTMCModelChecker(null);\n\t\t\tctmc = new CTMCSimple<>();\n\t\t\tctmc.buildFromPrismExplicit(args[0]);\n\t\t\tctmc.addInitialState(0);\n\t\t\t//System.out.println(ctmc);\n\t\t\tlabels = StateModelChecker.loadLabelsFile(args[1]);\n\t\t\t//System.out.println(labels);\n\t\t\ttarget = labels.get(args[2]);\n\t\t\tif (target == null)\n\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + args[2] + \"\\\"\");\n\t\t\tfor (int i = 4; i < args.length; i++) {\n\t\t\t\tif (args[i].equals(\"-nopre\"))\n\t\t\t\t\tmc.setPrecomp(false);\n\t\t\t}\n\t\t\tres = mc.computeTimeBoundedReachProbs(ctmc, target, Double.parseDouble(args[3]));\n\t\t\tSystem.out.println(res.soln[0]);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/CTMCSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport prism.Evaluator;\n\nimport java.util.AbstractMap;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.Map;\nimport java.util.function.Function;\n\n/**\n * Simple explicit-state representation of a CTMC.\n */\npublic class CTMCSimple<Value> extends DTMCSimple<Value> implements CTMC<Value>\n{\n\t/**\n\t * The cached embedded DTMC.\n\t * <p>\n\t * Will become invalid if the CTMC is changed. In this case\n\t * construct a new one by calling buildImplicitEmbeddedDTMC()\n\t * <p>\n\t * We cache this so that the PredecessorRelation of the\n\t * embedded DTMC is cached.\n\t */\n\tprivate DTMCEmbeddedSimple<Value> cachedEmbeddedDTMC = null;\n\n\t// Constructors\n\n\t/**\n\t * Constructor: empty CTMC.\n\t */\n\tpublic CTMCSimple()\n\t{\n\t\tsuper();\n\t}\n\n\t/**\n\t * Constructor: new CTMC with fixed number of states.\n\t */\n\tpublic CTMCSimple(int numStates)\n\t{\n\t\tsuper(numStates);\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic CTMCSimple(CTMCSimple<Value> ctmc)\n\t{\n\t\tsuper(ctmc);\n\t}\n\t\n\t/**\n\t * Construct a CTMC from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t * Note: have to build new Distributions from scratch anyway to do this,\n\t * so may as well provide this functionality as a constructor.\n\t */\n\tpublic CTMCSimple(CTMCSimple<Value> ctmc, int permut[])\n\t{\n\t\tsuper(ctmc, permut);\n\t}\n\n\t/**\n\t * Construct a CTMCSimple object from a CTMC object.\n\t */\n\tpublic CTMCSimple(CTMC<Value> ctmc)\n\t{\n\t\tsuper(ctmc);\n\t}\n\n\t/**\n\t * Construct a CTMCSimple object from a CTMC object,\n\t * mapping rate values using the provided function.\n\t */\n\tpublic CTMCSimple(CTMC<Value> ctmc, Function<? super Value, ? extends Value> rateMap)\n\t{\n\t\tsuper(ctmc, rateMap, ctmc.getEvaluator());\n\t}\n\n\t/**\n\t * Construct a CTMCSimple object from a CTMC object,\n\t * mapping rate values using the provided function.\n\t * Since the type changes (T -> Value), an Evaluator for Value must be given.\n\t */\n\tpublic <T> CTMCSimple(DTMC<T> ctmc, Function<? super T, ? extends Value> rateMap, Evaluator<Value> eval)\n\t{\n\t\tsuper(ctmc, rateMap, eval);\n\t}\n\n\t// Accessors (for CTMC)\n\n\t@Override\n\tpublic Iterator<Map.Entry<Integer, Value>> getEmbeddedTransitionsIterator(int s)\n\t{\n\t\t// Create iterator (no removal of duplicates)\n\t\treturn new Iterator<>() {\n\t\t\tprivate final int n = succ.get(s).size();\n\t\t\tprivate int i = 0;\n\t\t\tprivate Value exitRate = getExitRate(s);\n\n\t\t\t@Override\n\t\t\tpublic Map.Entry<Integer, Value> next()\n\t\t\t{\n\t\t\t\tif (n == 0) {\n\t\t\t\t\treturn new AbstractMap.SimpleEntry<>(i++, getEvaluator().one());\n\t\t\t\t} else {\n\t\t\t\t\treturn new AbstractMap.SimpleImmutableEntry<>(succ.get(s).get(i), getEvaluator().divide(trans.get(s).get(i++), exitRate));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn i < (n == 0 ? 1 : n);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic Value getExitRate(int i)\n\t{\n\t\treturn getEvaluator().sum(trans.get(i));\n\t}\n\t\n\t@Override\n\tpublic Value getMaxExitRate()\n\t{\n\t\tValue max = null;\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tValue d = getEvaluator().sum(trans.get(i));\n\t\t\tif (max == null || getEvaluator().gt(d, max)) {\n\t\t\t\tmax = d;\n\t\t\t}\n\t\t}\n\t\treturn max;\n\t}\n\t\n\t@Override\n\tpublic Value getMaxExitRate(BitSet subset)\n\t{\n\t\tValue max = null;\n\t\tfor (int i = subset.nextSetBit(0); i >= 0; i = subset.nextSetBit(i + 1)) {\n\t\t\tValue d = getEvaluator().sum(trans.get(i));\n\t\t\tif (max == null || getEvaluator().gt(d, max)) {\n\t\t\t\tmax = d;\n\t\t\t}\n\t\t}\n\t\treturn max;\n\t}\n\t\n\t@Override\n\tpublic Value getDefaultUniformisationRate()\n\t{\n\t\treturn getEvaluator().multiply(getEvaluator().fromString(\"1.02\"), getMaxExitRate()); \n\t}\n\t\n\t@Override\n\tpublic Value getDefaultUniformisationRate(BitSet nonAbs)\n\t{\n\t\treturn getEvaluator().multiply(getEvaluator().fromString(\"1.02\"), getMaxExitRate(nonAbs)); \n\t}\n\t\n\t@Override\n\tpublic DTMC<Value> buildImplicitEmbeddedDTMC()\n\t{\n\t\tDTMCEmbeddedSimple<Value> dtmc = new DTMCEmbeddedSimple<>(this);\n\t\tif (cachedEmbeddedDTMC != null) {\n\t\t\t// replace cached DTMC\n\t\t\tcachedEmbeddedDTMC = dtmc;\n\t\t}\n\t\treturn dtmc;\n\t}\n\t\n\t@Override\n\tpublic DTMC<Value> getImplicitEmbeddedDTMC()\n\t{\n\t\tif (cachedEmbeddedDTMC == null) {\n\t\t\tcachedEmbeddedDTMC = new DTMCEmbeddedSimple<>(this);\n\t\t}\n\t\treturn cachedEmbeddedDTMC;\n\t}\n\n\t\n\t@Override\n\tpublic DTMCSimple<Value> buildEmbeddedDTMC()\n\t{\n\t\tDTMCSimple<Value> dtmc = new DTMCSimple<>(numStates);\n\t\tfor (int in : getInitialStates()) {\n\t\t\tdtmc.addInitialState(in);\n\t\t}\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tValue d = getEvaluator().sum(trans.get(i));\n\t\t\tif (getEvaluator().isZero(d)) {\n\t\t\t\tdtmc.setProbability(i, i, getEvaluator().one(), null);\n\t\t\t} else {\n\t\t\t\tint numSucc = succ.get(i).size();\n\t\t\t\tfor (int j = 0; j < numSucc; j++) {\n\t\t\t\t\tdtmc.setProbability(i, succ.get(i).get(j), getEvaluator().divide(trans.get(i).get(j), d), actions.getAction(i, j));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn dtmc;\n\t}\n\n\t@Override\n\tpublic void uniformise(Value q)\n\t{\n\t\tthrow new UnsupportedOperationException(\"Not implemented\");\n\t}\n\n\t@Override\n\tpublic DTMC<Value> buildImplicitUniformisedDTMC(Value q)\n\t{\n\t\treturn new DTMCUniformisedSimple<>(this, q);\n\t}\n\t\n\t@Override\n\tpublic DTMCSimple<Value> buildUniformisedDTMC(Value q)\n\t{\n\t\tDTMCSimple<Value> dtmc = new DTMCSimple<>(numStates);\n\t\tfor (int in : getInitialStates()) {\n\t\t\tdtmc.addInitialState(in);\n\t\t}\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t// Add scaled off-diagonal entries\n\t\t\tint numSucc = succ.get(i).size();\n\t\t\tfor (int j = 0; j < numSucc; j++) {\n\t\t\t\tdtmc.setProbability(i, succ.get(i).get(j), getEvaluator().divide(trans.get(i).get(j), q), actions.getAction(i, j));\n\t\t\t}\n\t\t\t// Add diagonal, if needed\n\t\t\tValue d = getEvaluator().zero();\n\t\t\tfor (int j = 0; j < numSucc; j++) {\n\t\t\t\tif (succ.get(i).get(j) != i) {\n\t\t\t\t\td = getEvaluator().add(d, trans.get(i).get(j));\n\t\t\t\t}\n\t\t\t}\n\t\t\t// if (d < q): P(i,i) = 1 - (d / q)\n\t\t\tif (!getEvaluator().geq(d, q)) {\n\t\t\t\tdtmc.setProbability(i, i, getEvaluator().subtract(getEvaluator().one(), getEvaluator().divide(d, q)), null);\n\t\t\t}\n\t\t}\n\t\treturn dtmc;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/CTMDP.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport prism.ModelType;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state CTMDP.\n */\npublic interface CTMDP<Value> extends MDP<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.CTMDP;\n\t}\n\n\t// Accessors\n\t\n\t// TODO: copy/modify functions from CTMC\n\t\n\t/**\n\t * Compute the maximum exit rate.\n\t */\n\tpublic Value getMaxExitRate();\n\t\n\t/**\n\t * Check if the CTMDP is locally uniform, i.e. each state has the same exit rate for all actions. \n\t */\n\tpublic boolean isLocallyUniform();\n\t\n\t/**\n\t * Build the discretised (DT)MDP for this CTMDP, in implicit form\n\t * (i.e. where the details are computed on the fly from this one).\n\t * @param tau Step duration\n\t */\n\tpublic MDP<Value> buildImplicitDiscretisedMDP(double tau);\n\n\t/**\n\t * Build (a new) discretised (DT)MDP for this CTMDP.\n\t * @param tau Step duration\n\t */\n\tpublic MDPSimple<Value> buildDiscretisedMDP(double tau);\n}\n"
  },
  {
    "path": "prism/src/explicit/CTMDPModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Map;\n\nimport parser.ast.ExpressionTemporal;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Explicit-state model checker for continuous-time Markov decision processes (CTMDPs).\n */\npublic class CTMDPModelChecker extends ProbModelChecker\n{\n\t/**\n\t * Create a new CTMDPModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic CTMDPModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\t\n\t// Model checking functions\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tprotected StateValues checkProbBoundedUntil(Model<?> model, ExpressionTemporal expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tdouble uTime;\n\t\tBitSet b1, b2;\n\t\tStateValues probs = null;\n\t\tModelCheckerResult res = null;\n\n\t\t// get info from bounded until\n\t\tuTime = expr.getUpperBound().evaluateDouble(constantValues);\n\t\tif (uTime < 0 || (uTime == 0 && expr.upperBoundIsStrict())) {\n\t\t\tString bound = (expr.upperBoundIsStrict() ? \"<\" : \"<=\") + uTime;\n\t\t\tthrow new PrismException(\"Invalid upper bound \" + bound + \" in time-bounded until formula\");\n\t\t}\n\n\t\t// model check operands first for all states\n\t\tb1 = checkExpression(model, expr.getOperand1(), null).getBitSet();\n\t\tb2 = checkExpression(model, expr.getOperand2(), null).getBitSet();\n\n\t\t// compute probabilities\n\n\t\t// a trivial case: \"U<=0\"\n\t\tif (uTime == 0) {\n\t\t\t// prob is 1 in b2 states, 0 otherwise\n\t\t\tprobs = StateValues.createFromBitSetAsDoubles(b2, model);\n\t\t} else {\n\t\t\tres = computeBoundedUntilProbs((CTMDP<Double>) model, b1, b2, uTime, minMax.isMin());\n\t\t\tprobs = StateValues.createFromDoubleArray(res.soln, model);\n\t\t}\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute bounded until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * within time t, and while remaining in states in @{code remain}.\n\t * @param ctmdp The CTMDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param t Bound\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeBoundedUntilProbs(CTMDP<Double> ctmdp, BitSet remain, BitSet target, double t, boolean min) throws PrismException\n\t{\n\t\treturn computeBoundedReachProbs(ctmdp, remain, target, t, min, null, null);\n\t}\n\n\t/**\n\t * Compute bounded probabilistic reachability.\n\t * @param ctmdp The CTMDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param t Time bound\n\t * @param min Min or max probabilities for (true=min, false=max)\n\t * @param init Initial solution vector - pass null for default\n\t * @param results Optional array of size b+1 to store (init state) results for each step (null if unused)\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(CTMDP<Double> ctmdp, BitSet remain, BitSet target, double t, boolean min, double init[], double results[]) throws PrismException\n\t{\n\t\t// TODO: implement until\n\t\t\n\t\tMDP<Double> mdp;\n\t\tMDPModelChecker mc;\n\t\tModelCheckerResult res;\n\n\t\tif (!ctmdp.isLocallyUniform())\n\t\t\tthrow new PrismException(\"Can't compute bounded reachability probabilities for non-locally uniform CTMDP\");\n\t\t// TODO: check locally uniform\n\t\tdouble epsilon = 1e-3;\n\t\tdouble q = ctmdp.getMaxExitRate();\n\t\tint k = (int) Math.ceil((q * t * q * t) / (2 * epsilon));\n\t\tdouble tau = t / k;\n\t\tmainLog.println(\"q = \" + q + \", k = \" + k + \", tau = \" + tau);\n\t\tmdp = ctmdp.buildDiscretisedMDP(tau);\n\t\tmainLog.println(mdp);\n\t\tmc = new MDPModelChecker(this);\n\t\tmc.inheritSettings(this);\n\t\tres = mc.computeBoundedUntilProbs(mdp, null, target, k, min);\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute bounded reachability/until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * within time t, and while remaining in states in @{code remain}.\n\t * @param ctmdp The CTMDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param t: Time bound\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param init: Initial solution vector - pass null for default\n\t * @param results: Optional array of size b+1 to store (init state) results for each step (null if unused)\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbsOld(CTMDP<Double> ctmdp, BitSet remain, BitSet target, double t, boolean min, double init[], double results[]) throws PrismException\n\t{\n\t\t// TODO: implement until\n\t\t\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[], sum[];\n\t\tlong timer;\n\t\t// Fox-Glynn stuff\n\t\tFoxGlynn fg;\n\t\tint left, right;\n\t\tdouble q, qt, weights[], totalWeight;\n\n\t\t// Start bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"Starting time-bounded probabilistic reachability...\");\n\n\t\t// Store num states\n\t\tn = ctmdp.getNumStates();\n\n\t\t// Get uniformisation rate; do Fox-Glynn\n\t\tq = 99;//ctmdp.unif;\n\t\tqt = q * t;\n\t\tmainLog.println(\"\\nUniformisation: q.t = \" + q + \" x \" + t + \" = \" + qt);\n\t\tfg = new FoxGlynn(qt, 1e-300, 1e+300, termCritParam / 8.0);\n\t\tleft = fg.getLeftTruncationPoint();\n\t\tright = fg.getRightTruncationPoint();\n\t\tif (right < 0) {\n\t\t\tthrow new PrismException(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\t\t}\n\t\tweights = fg.getWeights();\n\t\ttotalWeight = fg.getTotalWeight();\n\t\tfor (i = left; i <= right; i++) {\n\t\t\tweights[i - left] /= totalWeight;\n\t\t}\n\t\tmainLog.println(\"Fox-Glynn: left = \" + left + \", right = \" + right);\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = (init == null) ? new double[n] : init;\n\t\tsum = new double[n];\n\n\t\t// Initialise solution vectors. Use passed in initial vector, if present\n\t\tif (init != null) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : init[i];\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : 0.0;\n\t\t}\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsum[i] = 0.0;\n\n\t\t// If necessary, do 0th element of summation (doesn't require any matrix powers)\n\t\tif (left == 0)\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsum[i] += weights[0] * soln[i];\n\n\t\t// Start iterations\n\t\titers = 1;\n\t\twhile (iters <= right) {\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tctmdp.mvMultMinMax(soln, min, soln2, target, true, null);\n\t\t\t// Since is globally uniform, can do this? and more?\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln2[i] /= q;\n\t\t\t// Store intermediate results if required\n\t\t\t// TODO?\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t\t// Add to sum\n\t\t\tif (iters >= left) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsum[i] += weights[iters - left] * soln[i];\n\t\t\t}\n\t\t\titers++;\n\t\t}\n\n\t\t// Print vector (for debugging)\n\t\tmainLog.println(sum);\n\n\t\t// Finished bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Time-bounded probabilistic reachability (\" + (min ? \"min\" : \"max\") + \")\");\n\t\tmainLog.println(\" took \" + iters + \" iters and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = sum;\n\t\tres.lastSoln = soln2;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute reachability probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target}.\n\t * @param ctmdp The CTMDP\n\t * @param target Target states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeReachProbs(CTMDP<Double> ctmdp, BitSet target, boolean min) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Not implemented yet\");\n\t}\n\n\t/**\n\t * Construct strategy information for min/max reachability probabilities.\n\t * (More precisely, list of indices of choices resulting in min/max.)\n\t * (Note: indices are guaranteed to be sorted in ascending order.)\n\t * @param ctmdp The CTMDP\n\t * @param state The state to generate strategy info for\n\t * @param target The set of target states to reach\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param lastSoln Vector of values from which to recompute in one iteration \n\t */\n\tpublic List<Integer> probReachStrategy(CTMDP<Double> ctmdp, int state, BitSet target, boolean min, double lastSoln[]) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Not implemented yet\");\n\t}\n\n\t/**\n\t * Simple test program.\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tCTMDPModelChecker mc;\n\t\tCTMDPSimple<Double> ctmdp;\n\t\tModelCheckerResult res;\n\t\tBitSet target;\n\t\tMap<String, BitSet> labels;\n\t\tboolean min = true;\n\t\ttry {\n\t\t\tmc = new CTMDPModelChecker(null);\n\t\t\tctmdp = new CTMDPSimple<>();\n\t\t\tctmdp.buildFromPrismExplicit(args[0]);\n\t\t\tctmdp.addInitialState(0);\n\t\t\tSystem.out.println(ctmdp);\n\t\t\tlabels = StateModelChecker.loadLabelsFile(args[1]);\n\t\t\tSystem.out.println(labels);\n\t\t\ttarget = labels.get(args[2]);\n\t\t\tif (target == null)\n\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + args[2] + \"\\\"\");\n\t\t\tfor (int i = 4; i < args.length; i++) {\n\t\t\t\tif (args[i].equals(\"-min\"))\n\t\t\t\t\tmin = true;\n\t\t\t\telse if (args[i].equals(\"-max\"))\n\t\t\t\t\tmin = false;\n\t\t\t\telse if (args[i].equals(\"-nopre\"))\n\t\t\t\t\tmc.setPrecomp(false);\n\t\t\t}\n\t\t\tres = mc.computeBoundedReachProbs(ctmdp, null, target, Double.parseDouble(args[3]), min, null, null);\n\t\t\tSystem.out.println(res.soln[0]);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/CTMDPSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Map;\n\nimport prism.PrismUtils;\n\n/**\n * Simple explicit-state representation of a CTMDP.\n */\npublic class CTMDPSimple<Value> extends MDPSimple<Value> implements CTMDP<Value>\n{\n\t// Constructors\n\n\t/**\n\t * Constructor: empty CTMDP.\n\t */\n\tpublic CTMDPSimple()\n\t{\n\t\tinitialise(0);\n\t}\n\n\t/**\n\t * Constructor: new CTMDP with fixed number of states.\n\t */\n\tpublic CTMDPSimple(int numStates)\n\t{\n\t\tinitialise(numStates);\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic CTMDPSimple(CTMDPSimple<Value> ctmdp)\n\t{\n\t\tsuper(ctmdp);\n\t}\n\n\t/**\n\t * Construct a CTMDP from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t * Note: have to build new Distributions from scratch anyway to do this,\n\t * so may as well provide this functionality as a constructor.\n\t */\n\tpublic CTMDPSimple(CTMDPSimple<Value> ctmdp, int permut[])\n\t{\n\t\tsuper(ctmdp, permut);\n\t}\n\n\t// Accessors (for CTMDP)\n\n\t@Override\n\tpublic Value getMaxExitRate()\n\t{\n\t\tValue max = null;\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tfor (Distribution<Value> distr : trans.get(i)) {\n\t\t\t\tValue d = distr.sum();\n\t\t\t\tif (max == null || getEvaluator().gt(d, max)) {\n\t\t\t\t\tmax = d;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn max;\n\t}\n\n\t@Override\n\tpublic boolean isLocallyUniform()\n\t{\n\t\tint i, j, n;\n\t\tdouble d;\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tn = trans.get(i).size();\n\t\t\tif (n < 2)\n\t\t\t\tcontinue;\n\t\t\td = (Double) trans.get(i).get(0).sum();\n\t\t\tfor (j = 1; j < n; j++) {\n\t\t\t\tif (!PrismUtils.doublesAreCloseAbs((Double) trans.get(i).get(j).sum(), d, 1e-12))\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic MDP<Value> buildImplicitDiscretisedMDP(double tau)\n\t{\n\t\t// TODO\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic MDPSimple<Value> buildDiscretisedMDP(double tau)\n\t{\n\t\t// Assumes doubles for now (needs exponent)\n\t\tMDPSimple mdp;\n\t\tDistribution distrNew;\n\t\tint i;\n\t\tdouble sum, d;\n\t\tmdp = new MDPSimple(numStates);\n\t\tfor (int in : getInitialStates()) {\n\t\t\tmdp.addInitialState(in);\n\t\t}\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tfor (Distribution distr : trans.get(i)) {\n\t\t\t\tdistrNew = Distribution.ofDouble();\n\t\t\t\tsum = (Double) distr.sum();\n\t\t\t\td = Math.exp(-sum * tau);\n\t\t\t\tfor (Map.Entry<Integer, Double> e : (Distribution<Double>) distr) {\n\t\t\t\t\tdistrNew.add(e.getKey(), (1 - d) * (e.getValue() / sum));\n\t\t\t\t}\n\t\t\t\tdistrNew.add(i, d);\n\t\t\t\tmdp.addChoice(i, distrNew);\n\t\t\t}\n\t\t}\n\t\treturn mdp;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ChoiceActionsSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.LinkedHashSet;\nimport java.util.List;\nimport java.util.function.IntUnaryOperator;\n\n/**\n * Explicit-state storage of the action labels attached to choices in a model.\n * \n * Uses simple, mutable data structures, matching the \"Simple\" range of models.\n */\npublic class ChoiceActionsSimple\n{\n\t// Action labels for each choice in each state\n\t// (null list means no actions; null in element s means no actions for state s)\n\t// Note: The number of states and choices per state is unknown,\n\t// so lists may be under-sized, in which case missing entries are assumed to be null.\n\tprotected ArrayList<ArrayList<Object>> actions;\n\n\t// Constructors\n\t\n\t/**\n\t * Constructor: empty action storage\n\t */\n\tpublic ChoiceActionsSimple()\n\t{\n\t\tactions = null;\n\t}\n\n\t/**\n\t * Copy constructor\n\t */\n\tpublic ChoiceActionsSimple(ChoiceActionsSimple cas)\n\t{\n\t\tactions = null;\n\t\tif (cas.actions != null) {\n\t\t\tint numStates = cas.actions.size();\n\t\t\tactions = new ArrayList<ArrayList<Object>>(numStates);\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tactions.add(null);\n\t\t\t}\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tif (cas.actions.get(s) != null) {\n\t\t\t\t\tactions.set(s, new ArrayList<>(cas.actions.get(s)));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Copy constructor, but with a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t */\n\tpublic ChoiceActionsSimple(ChoiceActionsSimple cas, int permut[])\n\t{\n\t\tactions = null;\n\t\tif (cas.actions != null) {\n\t\t\t// NB: permut.length is a more reliable source of numStates\n\t\t\t// since cas.actions may be undersized\n\t\t\tint numStates = permut.length;\n\t\t\tactions = new ArrayList<ArrayList<Object>>(numStates);\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tactions.add(null);\n\t\t\t}\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tif (s < cas.actions.size() && cas.actions.get(s) != null) {\n\t\t\t\t\tactions.set(permut[s], new ArrayList<>(cas.actions.get(s)));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// Mutators\n\t\n\t/**\n\t * Clear all actions for state {@code s}\n\t */\n\tpublic void clearState(int s)\n\t{\n\t\tif (actions != null && actions.get(s) != null) {\n\t\t\tactions.get(s).clear();\n\t\t}\n\t}\n\t\n\t/**\n\t * Set the action label for choice {@code i} of state {@code s}. \n\t */\n\tpublic void setAction(int s, int i, Object action)\n\t{\n\t\t// Create main list if not done yet \n\t\tif (actions == null) {\n\t\t\tif (action == null) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tactions = new ArrayList<ArrayList<Object>>();\n\t\t}\n\t\t// Expand main list up to state s if needed,\n\t\t// storing null for newly added items \n\t\tif (s >= actions.size()) {\n\t\t\tif (action == null) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tint n = s - actions.size() + 1;\n\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\tactions.add(null);\n\t\t\t}\n\t\t}\n\t\t// Create action list for state s if needed\n\t\tArrayList<Object> list;\n\t\tif ((list = actions.get(s)) == null) {\n\t\t\tif (action == null) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tactions.set(s, (list = new ArrayList<Object>()));\n\t\t}\n\t\t// Expand action list up to choice i if needed,\n\t\t// storing null for newly added items \n\t\tif (i >= list.size()) {\n\t\t\tif (action == null) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tint n = i - list.size() + 1;\n\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\tlist.add(null);\n\t\t\t}\n\t\t}\n\t\t// Store the action\n\t\tlist.set(i, action);\n\t}\n\t\n\t// Accessors\n\n\t/**\n\t * Produce a list of the action labels attached to choices/transitions.\n\t * Absence of an action label is denoted by null,\n\t * and null is also included in this list if there are unlabelled choices/transitions.\n\t * @param numStates The number of states in the model\n\t * @param counts A function giving the number of choices/transitions for each state\n\t */\n\tpublic List<Object> findActionsUsed(int numStates, IntUnaryOperator counts)\n\t{\n\t\tif (actions == null) {\n\t\t\t// Null storage means all choices/transitions are unlabelled\n\t\t\treturn Collections.singletonList(null);\n\t\t} else {\n\t\t\tLinkedHashSet<Object> allActions = new LinkedHashSet<>();\n\t\t\tint numStatesStored = actions.size();\n\t\t\tfor (int s = 0; s < numStatesStored; s++) {\n\t\t\t\tArrayList<Object> list = actions.get(s);\n\t\t\t\tif (list == null) {\n\t\t\t\t\t// Null list means any/all choices/transitions are unlabelled for s\n\t\t\t\t\tif (counts.applyAsInt(s) > 0) {\n\t\t\t\t\t\tallActions.add(null);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tallActions.addAll(list);\n\t\t\t\t\tif (list.size() < counts.applyAsInt(s)) {\n\t\t\t\t\t\t// Undersized list means there are unlabelled choices/transitions\n\t\t\t\t\t\tallActions.add(null);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (int s = numStatesStored; s < numStates; s++) {\n\t\t\t\t// Missing list means any/all choices/transitions are unlabelled for s\n\t\t\t\tif (counts.applyAsInt(s) > 0) {\n\t\t\t\t\tallActions.add(null);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn new ArrayList<>(allActions);\n\t\t}\n\t}\n\n\t/**\n\t * Do all choices/transitions have empty (null) action labels?\n\t */\n\tpublic boolean onlyNullActionUsed()\n\t{\n\t\t// NB: it's still possible that action storage has been created but has ended up all null\n\t\t// We ignore this possibility\n\t\treturn actions == null;\n\t}\n\n\t/**\n\t * Get the action label for choice {@code i} of state {@code s}.\n\t */\n\tpublic Object getAction(int s, int i)\n\t{\n\t\t// Null list means no (null) actions everywhere\n\t\tif (actions == null) {\n\t\t\treturn null;\n\t\t}\n\t\ttry {\n\t\t\t// Undersized list means no actions in this state\n\t\t\tif (s >= actions.size()) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\tArrayList<Object> list = actions.get(s);\n\t\t\t// Null list means no (null) actions in this state\n\t\t\tif (list == null) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\t// Undersized list means no action on this choice\n\t\t\tif (i >= list.size()) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\treturn list.get(i);\n\t\t}\n\t\t// Lists may be under-sized, indicating no action added \n\t\tcatch (IndexOutOfBoundsException e) {\n\t\t\treturn null;\n\t\t}\n\t}\n\n\t/**\n\t * Check whether the action label for choice {@code i} of state {@code s}\n\t * matches {@code action} (where {@code null} matches no action).\n\t */\n\tpublic boolean actionMatches(int s, int i, Object action)\n\t{\n\t\tObject siAction = getAction(s, i);\n\t\treturn siAction == null ? (action == null) : siAction.equals(action);\n\t}\n\t\n\t/**\n\t * Convert to \"sparse\" storage for a given model,\n\t * i.e., a single array where all actions are stored in\n\t * order, per state and then per choice.\n\t * A corresponding NondetModel is required because the\n\t * number of states and choices per state may be unknown.\n\t * If this action storage is completely empty,\n\t * then this method may simply return null.\n\t */\n\tpublic Object[] convertToSparseStorage(NondetModel<?> model)\n\t{\n\t\tif (actions == null) {\n\t\t\treturn null;\n\t\t} else {\n\t\t\tObject arr[] = new Object[model.getNumChoices()];\n\t\t\tint numStates = model.getNumStates();\n\t\t\tint count = 0;\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tint numChoices = model.getNumChoices(s);\n\t\t\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\t\t\tarr[count++] = getAction(s, i);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn arr;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ConstructInducedModel.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2023-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport common.Interval;\nimport parser.State;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport strat.Strategy;\nimport strat.StrategyExportOptions.InducedModelMode;\nimport strat.StrategyInfo;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\n/**\n * Construct the model induced by a memoryless deterministic strategy on a nondeterministic model\n */\npublic class ConstructInducedModel\n{\n\t/**\n\t * The \"mode\" of construction:\n\t * \"restrict\" (same model type but restrict to selected action choices); or\n\t * \"reduce\" (change mode type by removing nondeterminism)\n\t */\n\tprivate InducedModelMode mode = InducedModelMode.RESTRICT;\n\n\t/**\n\t * Whether to restrict strategy/model to reachable states\n\t */\n\tprivate boolean reachOnly = true;\n\n\t/**\n\t * Set the \"mode\" of construction:\n\t * \"restrict\" (same model type but restrict to selected action choices); or\n\t * \"reduce\" (change mode type by removing nondeterminism)\n\t */\n\tpublic ConstructInducedModel setMode(InducedModelMode mode)\n\t{\n\t\tthis.mode = mode;\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to restrict strategy/model to reachable states\n\t */\n\tpublic ConstructInducedModel setReachOnly(boolean reachOnly)\n\t{\n\t\tthis.reachOnly = reachOnly;\n\t\treturn this;\n\t}\n\n\t/**\n\t * Construct the model induced by a memoryless deterministic strategy on a nondeterministic model\n\t * @param model The model\n\t * @param strat The strategy\n\t * @return The induced model\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <Value> Model<Value> constructInducedModel(NondetModel<Value> model, Strategy<Value> strat) throws PrismException\n\t{\n\t\t// This is for memoryless strategies\n\t\tif (strat.hasMemory()) {\n\t\t\tthrow new PrismException(\"Induced model construction is for memoryless strategies\");\n\t\t}\n\n\t\t// Determine type of induced model\n\t\tModelType modelType = model.getModelType();\n\t\tModelType inducedModelType = strat.getInducedModelType(mode);\n\t\tif (inducedModelType == null) {\n\t\t\tthrow new PrismNotSupportedException(\"Induced model construction not supported for \" + modelType + \"s\");\n\t\t}\n\n\t\t// Create a (simple, mutable) model of the appropriate type\n\t\tModelSimple<Value> inducedModel = (ModelSimple<Value>) ModelSimple.forModelType(inducedModelType);\n\t\t\n\t\t// Attach evaluator and copy variable info\n\t\t((ModelExplicit<Value>) inducedModel).setEvaluator(model.getEvaluator());\n\t\tif (inducedModel instanceof IntervalModelExplicit) {\n\t\t\t((IntervalModelExplicit<Value>) inducedModel).setIntervalEvaluator(((IntervalModel<Value>) model).getIntervalEvaluator());\n\t\t}\n\t\t((ModelExplicit<Value>) inducedModel).setVarList(model.getVarList());\n\n\t\t// Now do the actual induced model construction\n\t\treturn doConstructInducedModel(modelType, inducedModelType, inducedModel, model, strat);\n\t}\n\n\t/**\n\t * Do the main part of the construction of the model induced\n\t * by a memoryless deterministic strategy on a nondeterministic model,\n\t * inserting states and transitions into the provided ModelSimple object.\n\t * @param modelType The type of the original model\n\t * @param inducedModelType The type of the induced model\n\t * @param inducedModel The (empty) induced model\n\t * @param model The model\n\t * @param strat The strategy\n\t * @return The product model\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <Value> Model<Value> doConstructInducedModel(ModelType modelType, ModelType inducedModelType, ModelSimple<Value> inducedModel, NondetModel<Value> model, Strategy<Value> strat) throws PrismException\n\t{\n\t\t// Create new states list if needed\n\t\tList<State> inducedStatesList = model.getStatesList();\n\t\tif (reachOnly && inducedStatesList != null) {\n\t\t\tinducedStatesList = new ArrayList<>();\n\t\t}\n\n\t\t// Initially create an array with 0s for reachable state indices and -1s for unreachable ones\n\t\tint numStates = model.getNumStates();\n\t\tint[] map = new int[numStates];\n\t\tif (reachOnly) {\n\t\t\tArrays.fill(map, -1);\n\t\t\tBitSet explore = new BitSet();\n\t\t\t// Get initial states\n\t\t\tfor (int is : model.getInitialStates()) {\n\t\t\t\tmap[is] = 0;\n\t\t\t\texplore.set(is);\n\t\t\t}\n\n\t\t\t// Compute reachable states (and store 0s in map)\n\t\t\twhile (!explore.isEmpty()) {\n\t\t\t\tfor (int s = explore.nextSetBit(0); s >= 0; s = explore.nextSetBit(s + 1)) {\n\t\t\t\t\texplore.set(s, false);\n\t\t\t\t\tint numChoices =  model.getNumChoices(s);\n\t\t\t\t\t// Extract strategy decision\n\t\t\t\t\tObject decision = strat.getChoiceAction(s, -1);\n\t\t\t\t\t// If it is undefined, just pick the first one\n\t\t\t\t\tif (decision == StrategyInfo.UNDEFINED && numChoices > 0) {\n\t\t\t\t\t\tdecision = model.getAction(s, 0);\n\t\t\t\t\t}\n\t\t\t\t\t// Go through transitions from state s_1 in original model\n\t\t\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\t\t\tObject act = model.getAction(s, j);\n\t\t\t\t\t\t// Skip choices not picked by the strategy\n\t\t\t\t\t\tif (!strat.isActionChosen(decision, act)) {\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tfor (Iterator<Integer> it = model.getSuccessorsIterator(s, j); it.hasNext(); ) {\n\t\t\t\t\t\t\tint dest = it.next();\n\t\t\t\t\t\t\tif (map[dest] == -1) {\n\t\t\t\t\t\t\t\tmap[dest] = 0;\n\t\t\t\t\t\t\t\texplore.set(dest);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Then populate map with indices\n\t\t\tint count = 0;\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tif (map[s] != -1) {\n\t\t\t\t\tmap[s] = count++;\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\t// Skip reachability\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tmap[s] = s;\n\t\t\t}\n\t\t}\n\n\t\t// Iterate through reachable states to create new model\n\t\tValue stratChoiceProb = model.getEvaluator().one();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tif (map[s] == -1) {\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\t// Add state to model\n\t\t\tswitch (inducedModelType) {\n\t\t\t\tcase STPG:\n\t\t\t\t\t((STPGSimple<Value>) inducedModel).addState(((STPG<Value>) model).getPlayer(s));\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tinducedModel.addState();\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (model.isInitialState(s)) {\n\t\t\t\tinducedModel.addInitialState(map[s]);\n\t\t\t}\n\t\t\tif (reachOnly && inducedStatesList != null) {\n\t\t\t\tinducedStatesList.add(model.getStatesList().get(s));\n\t\t\t}\n\n\t\t\tint numChoices =  model.getNumChoices(s);\n\t\t\t// Extract strategy decision\n\t\t\tObject decision = strat.getChoiceAction(s, -1);\n\t\t\t// If it is undefined, just pick the first one\n\t\t\tif (decision == StrategyInfo.UNDEFINED && numChoices > 0) {\n\t\t\t\tdecision = model.getAction(s, 0);\n\t\t\t}\n\t\t\t// To build nondeterministic models, store new transitions in a distribution\n\t\t\tObject inducedAction = null;\n\t\t\tDistribution<Value> prodDistr = null;\n\t\t\tDistribution<Interval<Value>> prodDistrIntv = null;\n\t\t\tif (inducedModelType.nondeterministic()) {\n\t\t\t\tif (modelType != ModelType.IMDP) {\n\t\t\t\t\tprodDistr = new Distribution<>(model.getEvaluator());\n\t\t\t\t} else {\n\t\t\t\t\tprodDistrIntv = new Distribution<>(((IMDP<Value>) model).getIntervalEvaluator());\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Go through choices from state s in original model\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\tObject act = model.getAction(s, j);\n\t\t\t\t// Skip choices not picked by the strategy\n\t\t\t\tif (!strat.isActionChosen(decision, act)) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t// Get strategy choice probability if needed\n\t\t\t\tif (strat.isRandomised()) {\n\t\t\t\t\tstratChoiceProb = strat.getChoiceActionProbability(decision, act);\n\t\t\t\t}\n\t\t\t\t// Get choice action for induced model if needed\n\t\t\t\tif (inducedModelType.nondeterministic()) {\n\t\t\t\t\tinducedAction = strat.getInducedAction(decision, act);\n\t\t\t\t}\n\t\t\t\t// Go through transitions of original model\n\t\t\t\tIterator<Map.Entry<Integer, Value>> iter = null;\n\t\t\t\tIterator<Map.Entry<Integer, Interval<Value>>> iterIntv = null;\n\t\t\t\tswitch (modelType) {\n\t\t\t\t\tcase MDP:\n\t\t\t\t\t\titer = ((MDP<Value>) model).getTransitionsIterator(s, j);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase POMDP:\n\t\t\t\t\t\titer = ((POMDP<Value>) model).getTransitionsIterator(s, j);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase IMDP:\n\t\t\t\t\t\titerIntv = ((IMDP<Value>) model).getIntervalTransitionsIterator(s, j);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase STPG:\n\t\t\t\t\t\titer = ((STPG<Value>) model).getTransitionsIterator(s, j);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tthrow new PrismNotSupportedException(\"Induced model construction not implemented for \" + modelType + \"s\");\n\t\t\t\t}\n\t\t\t\tif (modelType != ModelType.IMDP) {\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Value> e = iter.next();\n\t\t\t\t\t\tint s_2 = e.getKey();\n\t\t\t\t\t\tValue prob = e.getValue();\n\t\t\t\t\t\tif (strat.isRandomised()) {\n\t\t\t\t\t\t\tprob = model.getEvaluator().multiply(prob, stratChoiceProb);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// Add transition to model\n\t\t\t\t\t\tswitch (inducedModelType) {\n\t\t\t\t\t\t\tcase DTMC:\n\t\t\t\t\t\t\t\t((DTMCSimple<Value>) inducedModel).addToProbability(map[s], map[s_2], prob, act);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tcase MDP:\n\t\t\t\t\t\t\tcase POMDP:\n\t\t\t\t\t\t\tcase STPG:\n\t\t\t\t\t\t\t\tprodDistr.add(map[s_2], prob);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tthrow new PrismNotSupportedException(\"Induced model construction not implemented for \" + modelType + \"s\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\twhile (iterIntv.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Interval<Value>> e = iterIntv.next();\n\t\t\t\t\t\tint s_2 = e.getKey();\n\t\t\t\t\t\tInterval<Value> prob = e.getValue();\n\t\t\t\t\t\tif (strat.isRandomised()) {\n\t\t\t\t\t\t\tprob = ((IMDP<Value>) model).getIntervalEvaluator().multiply(prob, new Interval<>(stratChoiceProb, stratChoiceProb));\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// Add transition to model\n\t\t\t\t\t\tswitch (inducedModelType) {\n\t\t\t\t\t\t\tcase IDTMC:\n\t\t\t\t\t\t\t\t((IDTMCSimple<Value>) inducedModel).addToProbability(map[s], map[s_2], prob, act);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tcase IMDP:\n\t\t\t\t\t\t\t\tprodDistrIntv.add(map[s_2], prob);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tthrow new PrismNotSupportedException(\"Induced model construction not implemented for \" + modelType + \"s\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Add distribution to nondeterministic model\n\t\t\tif (inducedModelType.nondeterministic()) {\n\t\t\t\tswitch (inducedModelType) {\n\t\t\t\t\tcase MDP:\n\t\t\t\t\t\t((MDPSimple<Value>) inducedModel).addActionLabelledChoice(map[s], prodDistr, inducedAction);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase POMDP:\n\t\t\t\t\t\t((POMDPSimple<Value>) inducedModel).addActionLabelledChoice(map[s], prodDistr, inducedAction);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase IMDP:\n\t\t\t\t\t\t((IMDPSimple<Value>) inducedModel).addActionLabelledChoice(map[s], prodDistrIntv, inducedAction);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase STPG:\n\t\t\t\t\t\t((STPGSimple<Value>) inducedModel).addActionLabelledChoice(map[s], prodDistr, inducedAction);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tinducedModel.findDeadlocks(false);\n\n\t\tif (inducedStatesList != null) {\n\t\t\tinducedModel.setStatesList(inducedStatesList);\n\t\t}\n\n\t\treturn inducedModel;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ConstructModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.BitSet;\nimport java.util.LinkedList;\nimport java.util.List;\n\nimport common.Interval;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport prism.ModelGenerator;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismPrintStreamLog;\nimport prism.ProgressDisplay;\nimport prism.UndefinedConstants;\n\n/**\n * Class to perform explicit-state reachability and model construction.\n * The information about the model to be built is provided via a {@link prism.ModelGenerator} interface.\n * To build a PRISM model, use {@link simulator.ModulesFileModelGenerator}.\n */\npublic class ConstructModel extends PrismComponent\n{\n\t// Options:\n\n\t/** Find deadlocks during model construction? */\n\tprotected boolean findDeadlocks = true;\n\t/** Automatically fix deadlocks? */\n\tprotected boolean fixDeadlocks = true;\n\t/** Sort the reachable states before constructing the model? */\n\tprotected boolean sortStates = true;\n\t/** Build a sparse representation, if possible?\n\t *  (e.g. MDPSparse rather than MDPSimple data structure) */\n\tprotected boolean buildSparse = true;\n\t/** Should actions be attached to distributions (and used to distinguish them)? */\n\tprotected boolean distinguishActions = true;\n\t/** Should labels be processed and attached to the model? */\n\tprotected boolean attachLabels = true;\n\n\t// Details of built model:\n\n\t/** Reachable states */\n\tprotected List<State> statesList;\n\n\tpublic ConstructModel(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Get the list of states associated with the last model construction performed.  \n\t */\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn statesList;\n\t}\n\n\t/**\n\t * Automatically fix deadlocks, if needed?\n\t * (by adding self-loops in those states)\n\t */\n\tpublic void setFixDeadlocks(boolean fixDeadlocks)\n\t{\n\t\tthis.fixDeadlocks = fixDeadlocks;\n\t}\n\n\t/**\n\t * Sort the reachable states before constructing the model?\n\t */\n\tpublic void setSortStates(boolean sortStates)\n\t{\n\t\tthis.sortStates = sortStates;\n\t}\n\n\t/**\n\t * Build a sparse representation, if possible?\n\t * (e.g. MDPSparse rather than MDPSimple data structure)\n\t */\n\tpublic void setBuildSparse(boolean buildSparse)\n\t{\n\t\tthis.buildSparse = buildSparse;\n\t}\n\n\t/**\n\t * Should actions be attached to distributions (and used to distinguish them)?\n\t */\n\tpublic void setDistinguishActions(boolean distinguishActions)\n\t{\n\t\tthis.distinguishActions = distinguishActions;\n\t}\n\n\t/**\n\t * Should labels be processed and attached to the model?\n\t */\n\tpublic void setAttachLabels(boolean attachLabels)\n\t{\n\t\tthis.attachLabels = attachLabels;\n\t}\n\n\t/**\n\t * Build the set of reachable states for a model and return it.\n\t * @param modelGen The ModelGenerator interface providing the model \n\t */\n\tpublic List<State> computeReachableStates(ModelGenerator<?> modelGen) throws PrismException\n\t{\n\t\tconstructModel(modelGen, true);\n\t\treturn getStatesList();\n\t}\n\n\t/**\n\t * Construct an explicit-state model and return it.\n\t * @param modelGen The ModelGenerator interface providing the model \n\t */\n\tpublic <Value> Model<Value> constructModel(ModelGenerator<Value> modelGen) throws PrismException\n\t{\n\t\treturn constructModel(modelGen, false);\n\t}\n\n\t/**\n\t * Construct an explicit-state model and return it.\n\t * If {@code justReach} is true, no model is built and null is returned;\n\t * the set of reachable states can be obtained with {@link #getStatesList()}.\n\t * @param modelGen The ModelGenerator interface providing the model \n\t * @param justReach If true, just build the reachable state set, not the model\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <Value> Model<Value> constructModel(ModelGenerator<Value> modelGen, boolean justReach) throws PrismException\n\t{\n\t\t// Model info\n\t\tModelType modelType;\n\t\t// State storage\n\t\tStateStorage<State> states;\n\t\tLinkedList<State> explore;\n\t\tState state, stateNew;\n\t\t// Explicit model storage\n\t\tModelSimple<?> modelSimple = null;\n\t\tDTMCSimple<Value> dtmc = null;\n\t\tCTMCSimple<Value> ctmc = null;\n\t\tMDPSimple<Value> mdp = null;\n\t\tPOMDPSimple<Value> pomdp = null;\n\t\tCTMDPSimple<Value> ctmdp = null;\n\t\tIDTMCSimple<Value> idtmc = null;\n\t\tIMDPSimple<Value> imdp = null;\n\t\tIPOMDPSimple<Value> ipomdp = null;\n\t\tLTSSimple<Value> lts = null;\n\t\tDistribution<Value> distr = null;\n\t\tDistribution<Interval<Value>> distrUnc = null;\n\t\t// Misc\n\t\tint i, j, nc, nt, src, dest;\n\t\tlong timer;\n\n\t\t// Get model info\n\t\tmodelType = modelGen.getModelType();\n\t\t\n\t\t// Display a warning if there are unbounded vars\n\t\tVarList varList = modelGen.createVarList();\n\t\tif (modelGen.containsUnboundedVariables())\n\t\t\tmainLog.printWarning(\"Model contains one or more unbounded variables: model construction may not terminate\");\n\n\t\t// Starting reachability...\n\t\tmainLog.print(\"\\nComputing reachable states...\");\n\t\tmainLog.flush();\n\t\tProgressDisplay progress = new ProgressDisplay(mainLog);\n\t\tprogress.start();\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Create model storage\n\t\tif (!justReach) {\n\t\t\t// Create a (simple, mutable) model of the appropriate type\n\t\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\t\tmodelSimple = dtmc = new DTMCSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase CTMC:\n\t\t\t\tmodelSimple = ctmc = new CTMCSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\t\tmodelSimple = mdp = new MDPSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase POMDP:\n\t\t\t\tmodelSimple = pomdp = new POMDPSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase CTMDP:\n\t\t\t\tmodelSimple = ctmdp = new CTMDPSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase IDTMC:\n\t\t\t\tmodelSimple = idtmc = new IDTMCSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase IMDP:\n\t\t\t\tmodelSimple = imdp = new IMDPSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase IPOMDP:\n\t\t\t\tmodelSimple = ipomdp = new IPOMDPSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase LTS:\n\t\t\t\tmodelSimple = lts = new LTSSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase STPG:\n\t\t\tcase SMG:\n\t\t\tcase PTA:\n\t\t\tcase POPTA:\n\t\t\t\tthrow new PrismNotSupportedException(\"Model construction not supported for \" + modelType + \"s\");\n\t\t\t}\n\t\t\t// Attach evaluator and variable info\n\t\t\t((ModelExplicit<Value>) modelSimple).setEvaluator(modelGen.getEvaluator());\n\t\t\tif (modelSimple instanceof IntervalModelExplicit) {\n\t\t\t\t((IntervalModelExplicit<Value>) modelSimple).setIntervalEvaluator(modelGen.getIntervalEvaluator());\n\t\t\t}\n\t        ((ModelExplicit<Value>) modelSimple).setVarList(varList);\n\t\t\t// Attach actions, if provided\n\t\t\tList<Object> actions = modelGen.getActions();\n\t\t\tif (actions != null) {\n\t\t\t\t((ModelExplicit<Value>) modelSimple).setActions(actions);\n\t\t\t}\n\t\t}\n\n\t\t// Initialise states storage\n\t\tstates = new IndexedSet<State>(true);\n\t\texplore = new LinkedList<State>();\n\t\t// Add initial state(s) to 'explore', 'states' and to the model\n\t\tfor (State initState : modelGen.getInitialStates()) {\n\t\t\texplore.add(initState);\n\t\t\tstates.add(initState);\n\t\t\tif (!justReach) {\n\t\t\t\tmodelSimple.addState();\n\t\t\t\tmodelSimple.addInitialState(modelSimple.getNumStates() - 1);\n\t\t\t}\n\t\t}\n\t\t// Explore...\n\t\tsrc = -1;\n\t\twhile (!explore.isEmpty()) {\n\t\t\t// Pick next state to explore\n\t\t\t// (they are stored in order found so know index is src+1)\n\t\t\tstate = explore.removeFirst();\n\t\t\tsrc++;\n\t\t\t// Explore all choices/transitions from this state\n\t\t\tmodelGen.exploreState(state);\n\t\t\t// Look at each outgoing choice in turn\n\t\t\tnc = modelGen.getNumChoices();\n\t\t\tfor (i = 0; i < nc; i++) {\n\t\t\t\t// If required, check for duplicate actions here\n\t\t\t\tif (modelType.partiallyObservable()) {\n\t\t\t\t\tif (((NondetModel<Value>) modelSimple).getChoiceByAction(src, modelGen.getChoiceAction(i)) != -1) {\n\t\t\t\t\t\tString act = modelGen.getChoiceAction(i) == null ? \"\" : modelGen.getChoiceAction(i).toString();\n\t\t\t\t\t\tString err = modelType + \" is not allowed duplicate action\";\n\t\t\t\t\t\terr += \" (\\\"\" + act + \"\\\") in state \" + state.toString(modelGen);\n\t\t\t\t\t\tthrow new PrismException(err);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// For nondet models, collect transitions in a Distribution\n\t\t\t\tif (!justReach && modelType.nondeterministic()) {\n\t\t\t\t\tif (!modelType.uncertain()) {\n\t\t\t\t\t\tdistr = new Distribution<>(modelGen.getEvaluator());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tdistrUnc = new Distribution<>(modelGen.getIntervalEvaluator());\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Look at each transition in the choice\n\t\t\t\tnt = modelGen.getNumTransitions(i);\n\t\t\t\tfor (j = 0; j < nt; j++) {\n\t\t\t\t\tstateNew = modelGen.computeTransitionTarget(i, j);\n\t\t\t\t\t// Is this a new state?\n\t\t\t\t\tif (states.add(stateNew)) {\n\t\t\t\t\t\t// If so, add to the explore list\n\t\t\t\t\t\texplore.add(stateNew);\n\t\t\t\t\t\t// And to model\n\t\t\t\t\t\tif (!justReach) {\n\t\t\t\t\t\t\tmodelSimple.addState();\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Get index of state in state set\n\t\t\t\t\tdest = states.getIndexOfLastAdd();\n\t\t\t\t\t// Get transition action\n\t\t\t\t\tObject action = null;\n\t\t\t\t\tif (distinguishActions && !modelType.nondeterministic()) {\n\t\t\t\t\t\taction = modelGen.getTransitionAction(i, j);\n\t\t\t\t\t}\n\t\t\t\t\t// Add transitions to model\n\t\t\t\t\tif (!justReach) {\n\t\t\t\t\t\tswitch (modelType) {\n\t\t\t\t\t\tcase DTMC:\n\t\t\t\t\t\t\tdtmc.addToProbability(src, dest, modelGen.getTransitionProbability(i, j), action);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase CTMC:\n\t\t\t\t\t\t\tctmc.addToProbability(src, dest, modelGen.getTransitionProbability(i, j), action);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase IDTMC:\n\t\t\t\t\t\t\tidtmc.addToProbability(src, dest, modelGen.getTransitionProbabilityInterval(i, j), action);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase MDP:\n\t\t\t\t\t\tcase POMDP:\n\t\t\t\t\t\tcase CTMDP:\n\t\t\t\t\t\t\tdistr.add(dest, modelGen.getTransitionProbability(i, j));\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase IMDP:\n\t\t\t\t\t\tcase IPOMDP:\n\t\t\t\t\t\t\tdistrUnc.add(dest, modelGen.getTransitionProbabilityInterval(i, j));\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase LTS:\n\t\t\t\t\t\t\tif (distinguishActions) {\n\t\t\t\t\t\t\t\tlts.addActionLabelledTransition(src, dest, modelGen.getChoiceAction(i));\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tlts.addTransition(src, dest);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase STPG:\n\t\t\t\t\t\tcase SMG:\n\t\t\t\t\t\tcase PTA:\n\t\t\t\t\t\tcase POPTA:\n\t\t\t\t\t\t\tthrow new PrismNotSupportedException(\"Model construction not supported for \" + modelType + \"s\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// For nondet models, add collated transition to model\n\t\t\t\tint ch = -1;\n\t\t\t\tif (!justReach) {\n\t\t\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\t\t\tif (distinguishActions) {\n\t\t\t\t\t\t\tmdp.addActionLabelledChoice(src, distr, modelGen.getChoiceAction(i));\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tmdp.addChoice(src, distr);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (modelType == ModelType.POMDP) {\n\t\t\t\t\t\tif (distinguishActions) {\n\t\t\t\t\t\t\tpomdp.addActionLabelledChoice(src, distr, modelGen.getChoiceAction(i));\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tpomdp.addChoice(src, distr);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (modelType == ModelType.CTMDP) {\n\t\t\t\t\t\tif (distinguishActions) {\n\t\t\t\t\t\t\tctmdp.addActionLabelledChoice(src, distr, modelGen.getChoiceAction(i));\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tctmdp.addChoice(src, distr);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (modelType == ModelType.IMDP) {\n\t\t\t\t\t\tif (distinguishActions) {\n\t\t\t\t\t\t\tch = imdp.addActionLabelledChoice(src, distrUnc, modelGen.getChoiceAction(i));\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tch = imdp.addChoice(src, distrUnc);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (modelType == ModelType.IPOMDP) {\n\t\t\t\t\t\tif (distinguishActions) {\n\t\t\t\t\t\t\tch = ipomdp.addActionLabelledChoice(src, distrUnc, modelGen.getChoiceAction(i));\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tch = ipomdp.addChoice(src, distrUnc);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// For interval models, we delimit the constructed distributions\n\t\t\t\tif (modelType == ModelType.IDTMC) {\n\t\t\t\t\tidtmc.delimit(src);\n\t\t\t\t} else if (modelType == ModelType.IMDP) {\n\t\t\t\t\timdp.delimit(src, ch);\n\t\t\t\t} else if (modelType == ModelType.IPOMDP) {\n\t\t\t\t\tipomdp.delimit(src, ch);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// For partially observable models, add observation info to state\n\t\t\t// (do it after transitions are added, since observation actions are checked)\n\t\t\tif (!justReach && (modelType == ModelType.POMDP || modelType == ModelType.IPOMDP)) {\n\t\t\t\tsetStateObservation(modelGen, (PartiallyObservableModel<Value>) modelSimple, src, state);\n\t\t\t}\n\t\t\t// Print some progress info occasionally\n\t\t\tprogress.updateIfReady(src + 1);\n\t\t}\n\n\t\t// Finish progress display\n\t\tprogress.update(src + 1);\n\t\tprogress.end(\" states\");\n\n\t\t// Reachability complete\n\t\tmainLog.print(\"Reachable states exploration\" + (justReach ? \"\" : \" and model construction\"));\n\t\tmainLog.println(\" done in \" + ((System.currentTimeMillis() - timer) / 1000.0) + \" secs.\");\n\t\t//mainLog.println(states);\n\n\t\t// Find/fix deadlocks (if required)\n\t\tif (!justReach && findDeadlocks) {\n\t\t\tmodelSimple.findDeadlocks(fixDeadlocks);\n\t\t}\n\n\t\tint permut[] = null;\n\n\t\tif (sortStates) {\n\t\t\t// Sort states and convert set to list\n\t\t\tmainLog.println(\"Sorting reachable states list...\");\n\t\t\tpermut = states.buildSortingPermutation();\n\t\t\tstatesList = states.toPermutedArrayList(permut);\n\t\t\t//mainLog.println(permut);\n\t\t} else {\n\t\t\tstatesList = states.toArrayList();\n\t\t}\n\t\tstates.clear();\n\t\tstates = null;\n\t\t//mainLog.println(statesList);\n\n\t\t// Construct new explicit-state model (with correct state ordering, if desired)\n\t\tModelExplicit<Value> model = null;\n\t\tif (!justReach) {\n\t\t\tboolean isDbl = modelSimple.getEvaluator().one() instanceof Double; \n\t\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\t\tif (buildSparse && isDbl) {\n\t\t\t\t\tmodel = (ModelExplicit<Value>) (sortStates ? new DTMCSparse((DTMC<Double>) dtmc, permut) : new DTMCSparse((DTMC<Double>) dtmc));\n\t\t\t\t} else {\n\t\t\t\t\tmodel = sortStates ? new DTMCSimple<>(dtmc, permut) : (DTMCSimple<Value>) dtmc;\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase CTMC:\n\t\t\t\tmodel = sortStates ? new CTMCSimple<>(ctmc, permut) : (CTMCSimple<Value>) ctmc;\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\t\tif (buildSparse && isDbl) {\n\t\t\t\t\tmodel = (ModelExplicit<Value>) (sortStates ? new MDPSparse((MDPSimple<Double>) mdp, true, permut) : new MDPSparse((MDP<Double>) mdp));\n\t\t\t\t} else {\n\t\t\t\t\tmodel = sortStates ? new MDPSimple<>(mdp, permut) : mdp;\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase POMDP:\n\t\t\t\tmodel = sortStates ? new POMDPSimple<>(pomdp, permut) : pomdp;\n\t\t\t\tbreak;\n\t\t\tcase CTMDP:\n\t\t\t\tmodel = sortStates ? new CTMDPSimple<>(ctmdp, permut) : ctmdp;\n\t\t\t\tbreak;\n\t\t\tcase IDTMC:\n\t\t\t\tmodel = sortStates ? new IDTMCSimple<>(idtmc, permut) : idtmc;\n\t\t\t\tbreak;\n\t\t\tcase IMDP:\n\t\t\t\tmodel = sortStates ? new IMDPSimple<>(imdp, permut) : imdp;\n\t\t\t\tbreak;\n\t\t\tcase IPOMDP:\n\t\t\t\tmodel = sortStates ? new IPOMDPSimple<>(ipomdp, permut) : ipomdp;\n\t\t\t\tbreak;\n\t\t\tcase LTS:\n\t\t\t\tmodel = sortStates ? new LTSSimple<>(lts, permut) : lts;\n\t\t\t\tbreak;\n\t\t\tcase STPG:\n\t\t\tcase SMG:\n\t\t\tcase PTA:\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Model construction not supported for \" + modelType + \"s\");\n\t\t\t}\n\t\t\tmodel.setStatesList(statesList);\n\t\t\tmodel.setConstantValues(new Values(modelGen.getConstantValues()));\n\t\t\t//mainLog.println(\"Model: \" + model);\n\t\t}\n\n\t\t// Discard permutation\n\t\tpermut = null;\n\n\t\tif (!justReach && attachLabels)\n\t\t\tattachLabels(modelGen, model);\n\t\t\n\t\treturn model;\n\t}\n\n\tprivate <Value> void setStateObservation(ModelGenerator<Value> modelGen, PartiallyObservableModel<Value> pomdp, int s, State state) throws PrismException\n\t{\n\t\t// Get observation for the current state\n\t\t// An observation is a State containing the value for each observable\n\t\tState sObs = modelGen.getObservation(state);\n\t\t// Build unobservation for the current state\n\t\t// An unobservation is a State containing the value for\n\t\t// all variables that are not observable\n\t\tint numVars = modelGen.getNumVars();\n\t\tint numUnobsVars = numVars - modelGen.getNumObservableVars();\n\t\tState sUnobs = new State(numUnobsVars);\n\t\tint count = 0;\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tif (!modelGen.isVarObservable(i)) {\n\t\t\t\tsUnobs.setValue(count++, state.varValues[i]);\n\t\t\t}\n\t\t}\n\t\t// Set observation/unobservation\n\t\tpomdp.setObservation(s, sObs, sUnobs, modelGen.getObservableNames());\n\t}\n\t\n\tprivate <Value> void attachLabels(ModelGenerator<Value> modelGen, ModelExplicit<Value> model) throws PrismException\n\t{\n\t\t// Get state info\n\t\tList <State> statesList = model.getStatesList();\n\t\tint numStates = statesList.size();\n\t\t// Create storage for labels\n\t\tint numLabels = modelGen.getNumLabels();\n\t\t// No need to continue unless this ModelGenerator uses labels\n\t\tif (numLabels == 0) return;\n\t\tBitSet bitsets[] = new BitSet[numLabels];\n\t\tfor (int j = 0; j < numLabels; j++) {\n\t\t\tbitsets[j] = new BitSet();\n\t\t}\n\t\t// Construct bitsets for labels\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tState state = statesList.get(i);\n\t\t\tmodelGen.exploreState(state);\n\t\t\tfor (int j = 0; j < numLabels; j++) {\n\t\t\t\tif (modelGen.isLabelTrue(j)) {\n\t\t\t\t\tbitsets[j].set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Attach labels/bitsets\n\t\tfor (int j = 0; j < numLabels; j++) {\n\t\t\tmodel.addLabel(modelGen.getLabelName(j), bitsets[j]);\n\t\t}\n\t}\n\n\t/**\n\t * Test method.\n\t */\n\tpublic static void main(String[] args)\n\t{\n\t\ttry {\n\t\t\t// Simple example: parse a PRISM file from a file, construct the model and export to a .tra file\n\t\t\tPrismLog mainLog = new PrismPrintStreamLog(System.out);\n\t\t\tPrism prism = new Prism(mainLog);\n\t\t\tparser.ast.ModulesFile modulesFile = prism.parseModelFile(new File(args[0]));\n\t\t\tUndefinedConstants undefinedConstants = new UndefinedConstants(modulesFile, null);\n\t\t\tif (args.length > 2)\n\t\t\t\tundefinedConstants.defineUsingConstSwitch(args[2]);\n\t\t\tmodulesFile.setSomeUndefinedConstants(undefinedConstants.getMFConstantValues());\n\t\t\tConstructModel constructModel = new ConstructModel(prism);\n\t\t\tconstructModel.setSortStates(true);\n\t\t\tsimulator.ModulesFileModelGenerator<?> modelGen = simulator.ModulesFileModelGenerator.create(modulesFile, constructModel);\n\t\t\tModel<?> model = constructModel.constructModel(modelGen);\n\t\t\tmodel.exportToPrismExplicitTra(args[1]);\n\t\t} catch (FileNotFoundException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ConstructStrategyProduct.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.awt.Point;\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.LinkedList;\nimport java.util.List;\nimport java.util.Map;\n\nimport common.Interval;\nimport parser.State;\nimport parser.VarList;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationInt;\nimport parser.ast.Expression;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport strat.Strategy;\nimport strat.StrategyExportOptions;\nimport strat.StrategyInfo;\n\n/**\n * Construct the product model induced by a finite-memory strategy on a nondeterministic model\n */\npublic class ConstructStrategyProduct\n{\n\t/**\n\t * The \"mode\" of construction:\n\t * \"restrict\" (same model type but restrict to selected action choices); or\n\t * \"reduce\" (change mode type by removing nondeterminism)\n\t */\n\tprivate StrategyExportOptions.InducedModelMode mode = StrategyExportOptions.InducedModelMode.RESTRICT;\n\n\t/**\n\t * Set the \"mode\" of construction:\n\t * \"restrict\" (same model type but restrict to selected action choices); or\n\t * \"reduce\" (change mode type by removing nondeterminism)\n\t */\n\tpublic ConstructStrategyProduct setMode(StrategyExportOptions.InducedModelMode mode)\n\t{\n\t\tthis.mode = mode;\n\t\treturn this;\n\t}\n\n\t/**\n\t * Construct the product model induced by a finite-memory strategy on a nondeterministic model\n\t * @param model The model\n\t * @param strat The strategy\n\t * @return The product model\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <Value> Model<Value> constructProductModel(NondetModel<Value> model, Strategy<Value> strat) throws PrismException\n\t{\n\t\t// This is for finite-memory strategies\n\t\tif (!strat.hasMemory()) {\n\t\t\tthrow new PrismException(\"Product construction is for finite-memory strategies\");\n\t\t}\n\t\t\n\t\t// If the model has a VarList, we will create a new one\n\t\tVarList newVarList = null;\n\t\tif (model.getVarList() != null) {\n\t\t\tVarList varList = model.getVarList();\n\t\t\t// Create a (new, unique) name for the variable that will represent memory states\n\t\t\tString memVar = \"_mem\";\n\t\t\twhile (varList.getIndex(memVar) != -1) {\n\t\t\t\tmemVar = \"_\" + memVar;\n\t\t\t}\n\t\t\tnewVarList = (VarList) varList.clone();\n\t\t\tDeclaration decl = new Declaration(memVar, new DeclarationInt(Expression.Int(0), Expression.Int(strat.getMemorySize())));\n\t\t\tnewVarList.addVarAtStart(decl, 1);\n\t\t}\n\n\t\t// Determine type of induced model\n\t\tModelType modelType = model.getModelType();\n\t\tModelType productModelType = strat.getInducedModelType(mode);\n\t\tif (productModelType == null) {\n\t\t\tthrow new PrismNotSupportedException(\"Product construction not supported for \" + modelType + \"s\");\n\t\t}\n\n\t\t// Create a (simple, mutable) model of the appropriate type\n\t\tModelSimple<Value> prodModel = (ModelSimple<Value>) ModelSimple.forModelType(productModelType);\n\n\t\t// Attach evaluator and variable info\n\t\t((ModelExplicit<Value>) prodModel).setEvaluator(model.getEvaluator());\n\t\tif (prodModel instanceof IntervalModelExplicit) {\n\t\t\t((IntervalModelExplicit<Value>) prodModel).setIntervalEvaluator(((IntervalModel<Value>) model).getIntervalEvaluator());\n\t\t}\n\t\t((ModelExplicit<Value>) prodModel).setVarList(newVarList);\n\n\t\t// Now do the actual product model construction\n\t\treturn doConstructProductModel(modelType, productModelType, prodModel, model, strat);\n\t}\n\t\n\t/**\n\t * Do the main part of the construction of the product model induced\n\t * by a finite-memory strategy on a nondeterministic model,\n\t * inserting states and transitions into the provided ModelSimple object.\n\t * @param modelType The type of the original model\n\t * @param productModelType The type of the product model\n\t * @param prodModel The (empty) product model\n\t * @param model The model\n\t * @param strat The strategy\n\t * @return The product model\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <Value> Model<Value> doConstructProductModel(ModelType modelType, ModelType productModelType, ModelSimple<Value> prodModel, NondetModel<Value> model, Strategy<Value> strat) throws PrismException\n\t{\n\t\tint modelNumStates = model.getNumStates();\n\t\tint memSize = strat.getMemorySize();\n\t\tint prodNumStates;\n\t\tList<State> prodStatesList, memStatesList;\n\t\tValue stratChoiceProb = model.getEvaluator().one();\n\n\t\t// Check size limits for this product construction approach\n\t\ttry {\n\t\t\tprodNumStates = Math.multiplyExact(modelNumStates, memSize);\n\t\t} catch (ArithmeticException e) {\n\t\t\tthrow new PrismException(\"Size of product state space of model and strategy is too large for explicit engine\");\n\t\t}\n\t\t\n\t\t// Encoding: \n\t\t// each state s' = <s, q> = s * memSize + q\n\t\t// s(s') = s' / memSize\n\t\t// q(s') = s' % memSize\n\n\t\t// Initialise state info storage\n\t\tLinkedList<Point> queue = new LinkedList<Point>();\n\t\tBitSet visited = new BitSet(prodNumStates);\n\t\tint map[] = new int[prodNumStates];\n\t\tArrays.fill(map, -1);\n\t\tif (model.getStatesList() != null) {\n\t\t\tprodStatesList = new ArrayList<State>();\n\t\t\tmemStatesList = new ArrayList<State>(memSize);\n\t\t\tfor (int i = 0; i < memSize; i++) {\n\t\t\t\tmemStatesList.add(new State(1).setValue(0, i));\n\t\t\t}\n\t\t} else {\n\t\t\tprodStatesList = null;\n\t\t\tmemStatesList = null;\n\t\t}\n\n\t\t// Code to get the index for a new product state for model successor state s_2\n\t\t// (or initial state s_2 if init==true)\n\t\t// assuming the current memory status is q_1 and the action taken is act\n\t\t// (q_1 and act are ignored if init==true)\n\t\tNewStateMap newStateMap = (init, q_1, act, s_2) -> {\n\t\t\t// Find corresponding memory value\n\t\t\tint q_2 = -1;\n\t\t\tif (init) {\n\t\t\t\tq_2 = strat.getInitialMemory(s_2);\n\t\t\t} else {\n\t\t\t\tq_2 = strat.getUpdatedMemory(q_1, act, s_2);\n\t\t\t}\n\t\t\tif (q_2 < 0) {\n\t\t\t\tthrow new PrismException(\"The memory status is unknown (state \" + s_2 + \")\");\n\t\t\t}\n\t\t\t// Add state/transition to model\n\t\t\tif (!visited.get(s_2 * memSize + q_2) && map[s_2 * memSize + q_2] == -1) {\n\t\t\t\tqueue.add(new Point(s_2, q_2));\n\t\t\t\tswitch (productModelType) {\n\t\t\t\t\tcase STPG:\n\t\t\t\t\t\t((STPGSimple<Value>) prodModel).addState(((STPG<Value>) model).getPlayer(s_2));\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tprodModel.addState();\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tmap[s_2 * memSize + q_2] = prodModel.getNumStates() - 1;\n\t\t\t\tif (prodStatesList != null) {\n\t\t\t\t\t// Store state information for the product\n\t\t\t\t\tprodStatesList.add(new State(model.getStatesList().get(s_2), memStatesList.get(q_2)));\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn map[s_2 * memSize + q_2];\n\t\t};\n\n\t\t// Get initial states\n\t\tfor (int s_0 : model.getInitialStates()) {\n\t\t\tint map_0 = newStateMap.apply(true, -1, null, s_0);\n\t\t\tprodModel.addInitialState(map_0);\n\t\t}\n\n\t\t// Explore product\n\t\twhile (!queue.isEmpty()) {\n\t\t\tPoint p = queue.pop();\n\t\t\tint s_1 = p.x;\n\t\t\tint q_1 = p.y;\n\t\t\tvisited.set(s_1 * memSize + q_1);\n\t\t\tint map_1 = map[s_1 * memSize + q_1];\n\n\t\t\tint numChoices =  model.getNumChoices(s_1);\n\t\t\t// Extract strategy decision\n\t\t\tObject decision = strat.getChoiceAction(s_1, q_1);\n\t\t\t// If it is undefined, just pick the first one\n\t\t\tif (decision == StrategyInfo.UNDEFINED && numChoices > 0) {\n\t\t\t\tdecision = model.getAction(s_1, 0);\n\t\t\t}\n\t\t\t// To build nondeterministic models, store new transitions in a distribution\n\t\t\tObject inducedAction = null;\n\t\t\tDistribution<Value> prodDistr = null;\n\t\t\tDistribution<Interval<Value>> prodDistrIntv = null;\n\t\t\tif (productModelType.nondeterministic()) {\n\t\t\t\tif (modelType != ModelType.IMDP) {\n\t\t\t\t\tprodDistr = new Distribution<>(model.getEvaluator());\n\t\t\t\t} else {\n\t\t\t\t\tprodDistrIntv = new Distribution<>(((IMDP<Value>) model).getIntervalEvaluator());\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Go through choices from state s_1 in original model\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\tObject act = model.getAction(s_1, j);\n\t\t\t\t// Skip choices not picked by the strategy\n\t\t\t\tif (!strat.isActionChosen(decision, act)) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t// Get strategy choice probability if needed\n\t\t\t\tif (strat.isRandomised()) {\n\t\t\t\t\tstratChoiceProb = strat.getChoiceActionProbability(decision, act);\n\t\t\t\t}\n\t\t\t\t// Get choice action for induced model if needed\n\t\t\t\tif (productModelType.nondeterministic()) {\n\t\t\t\t\tinducedAction = strat.getInducedAction(decision, act);\n\t\t\t\t}\n\t\t\t\t// Go through transitions of original model\n\t\t\t\tIterator<Map.Entry<Integer, Value>> iter = null;\n\t\t\t\tIterator<Map.Entry<Integer, Interval<Value>>> iterIntv = null;\n\t\t\t\tswitch (modelType) {\n\t\t\t\tcase MDP:\n\t\t\t\t\titer = ((MDP<Value>) model).getTransitionsIterator(s_1, j);\n\t\t\t\t\tbreak;\n\t\t\t\tcase POMDP:\n\t\t\t\t\titer = ((POMDP<Value>) model).getTransitionsIterator(s_1, j);\n\t\t\t\t\tbreak;\n\t\t\t\tcase IMDP:\n\t\t\t\t\titerIntv = ((IMDP<Value>) model).getIntervalTransitionsIterator(s_1, j);\n\t\t\t\t\tbreak;\n\t\t\t\tcase STPG:\n\t\t\t\t\titer = ((STPG<Value>) model).getTransitionsIterator(s_1, j);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Product construction not implemented for \" + modelType + \"s\");\n\t\t\t\t}\n\t\t\t\tif (modelType != ModelType.IMDP) {\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Value> e = iter.next();\n\t\t\t\t\t\tint s_2 = e.getKey();\n\t\t\t\t\t\tValue prob = e.getValue();\n\t\t\t\t\t\tif (strat.isRandomised()) {\n\t\t\t\t\t\t\tprob = model.getEvaluator().multiply(prob, stratChoiceProb);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tint map_2 = newStateMap.apply(false, q_1, act, s_2);\n\n\t\t\t\t\t\tswitch (productModelType) {\n\t\t\t\t\t\t\tcase DTMC:\n\t\t\t\t\t\t\t\t((DTMCSimple<Value>) prodModel).addToProbability(map_1, map_2, prob, act);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tcase MDP:\n\t\t\t\t\t\t\tcase POMDP:\n\t\t\t\t\t\t\tcase STPG:\n\t\t\t\t\t\t\t\tprodDistr.add(map_2, prob);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tthrow new PrismNotSupportedException(\"Product construction not implemented for \" + modelType + \"s\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\twhile (iterIntv.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Interval<Value>> e = iterIntv.next();\n\t\t\t\t\t\tint s_2 = e.getKey();\n\t\t\t\t\t\tInterval<Value> prob = e.getValue();\n\t\t\t\t\t\tif (strat.isRandomised()) {\n\t\t\t\t\t\t\tprob = ((IMDP<Value>) model).getIntervalEvaluator().multiply(prob, new Interval<>(stratChoiceProb, stratChoiceProb));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tint map_2 = newStateMap.apply(false, q_1, act, s_2);\n\t\t\t\t\t\t// Add transition to model\n\t\t\t\t\t\tswitch (productModelType) {\n\t\t\t\t\t\t\tcase IDTMC:\n\t\t\t\t\t\t\t\t((IDTMCSimple<Value>) prodModel).addToProbability(map_1, map_2, prob, act);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tcase IMDP:\n\t\t\t\t\t\t\t\tprodDistrIntv.add(map_2, prob);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tthrow new PrismNotSupportedException(\"Induced model construction not implemented for \" + modelType + \"s\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Add distribution to nondeterministic model\n\t\t\tif (productModelType.nondeterministic()) {\n\t\t\t\tswitch (productModelType) {\n\t\t\t\tcase MDP:\n\t\t\t\t\t((MDPSimple<Value>) prodModel).addActionLabelledChoice(map_1, prodDistr, inducedAction);\n\t\t\t\t\tbreak;\n\t\t\t\tcase IMDP:\n\t\t\t\t\t((IMDPSimple<Value>) prodModel).addActionLabelledChoice(map_1, prodDistrIntv, inducedAction);\n\t\t\t\t\tbreak;\n\t\t\t\tcase POMDP:\n\t\t\t\t\t((POMDPSimple<Value>) prodModel).addActionLabelledChoice(map_1, prodDistr, inducedAction);\n\t\t\t\t\tbreak;\n\t\t\t\tcase STPG:\n\t\t\t\t\t((STPGSimple<Value>) prodModel).addActionLabelledChoice(map_1, prodDistr, inducedAction);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tprodModel.findDeadlocks(false);\n\n\t\tif (prodStatesList != null) {\n\t\t\tprodModel.setStatesList(prodStatesList);\n\t\t}\n\t\t\n\t\treturn prodModel;\n\t}\n\n\t@FunctionalInterface\n\tinterface NewStateMap\n\t{\n\t\tint apply(boolean init, int q_1, Object act, int s_2) throws PrismException;\n\t};\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMC.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.FileWriter;\nimport java.io.IOException;\nimport java.util.AbstractMap;\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.LinkedHashSet;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.Objects;\nimport java.util.PrimitiveIterator;\nimport java.util.PrimitiveIterator.OfInt;\nimport java.util.TreeMap;\nimport java.util.function.Function;\n\nimport common.IterableStateSet;\nimport common.iterable.FunctionalIterator;\nimport common.iterable.PrimitiveIterable;\nimport common.iterable.Reducible;\nimport explicit.rewards.MCRewards;\nimport prism.ActionList;\nimport prism.ModelType;\nimport prism.Pair;\nimport prism.PrismException;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state DTMC.\n */\npublic interface DTMC<Value> extends Model<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.DTMC;\n\t}\n\n\t@Override\n\tdefault void exportToPrismLanguage(final String filename, int precision) throws PrismException\n\t{\n\t\ttry (FileWriter out = new FileWriter(filename)) {\n\t\t\tout.write(getModelType().keyword() + \"\\n\");\n\t\t\tout.write(\"module M\\nx : [0..\" + (getNumStates() - 1) + \"];\\n\");\n\t\t\tfinal TreeMap<Integer, Pair<Value, Object>> sorted = new TreeMap<>();\n\t\t\tfor (int state = 0, max = getNumStates(); state < max; state++) {\n\t\t\t\t// Extract transitions and sort by destination state index (to match PRISM-exported files)\n\t\t\t\tfor (Iterator<Entry<Integer, Pair<Value, Object>>> transitions = getTransitionsAndActionsIterator(state); transitions.hasNext();) {\n\t\t\t\t\tfinal Entry<Integer, Pair<Value, Object>> transition = transitions.next();\n\t\t\t\t\tsorted.put(transition.getKey(), transition.getValue());\n\t\t\t\t}\n\t\t\t\t// Print out (sorted) transitions\n\t\t\t\tfor (Entry<Integer, Pair<Value, Object>> transition : sorted.entrySet()) {\n\t\t\t\t\tString action = transition.getValue().second == null ? \"\" : transition.getValue().second.toString();\n\t\t\t\t\tout.write(\"[\" + action + \"]x=\" + state + \"->\");\n\t\t\t\t\tout.write(getEvaluator().toStringPrism(transition.getValue().first, precision) + \":(x'=\" + transition.getKey() + \")\");\n\t\t\t\t\tout.write(\";\\n\");\n\t\t\t\t}\n\t\t\t\tsorted.clear();\n\t\t\t}\n\t\t\tout.write(\"endmodule\\n\");\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"Could not export \" + getModelType() + \" to file \\\"\" + filename + \"\\\"\" + e);\n\t\t}\n\t}\n\n\t// Accessors\n\n\t@Override\n\tdefault List<Object> findActionsUsed()\n\t{\n\t\t// Find unique actions across all transitions\n\t\tif (onlyNullActionUsed()) {\n\t\t\treturn Collections.singletonList(null);\n\t\t}\n\t\tLinkedHashSet<Object> actions = new LinkedHashSet<>();\n\t\tint numStates = getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tfor (Iterator<Entry<Integer, Pair<Value, Object>>> transitions = getTransitionsAndActionsIterator(s); transitions.hasNext();) {\n\t\t\t\tfinal Entry<Integer, Pair<Value, Object>> transition = transitions.next();\n\t\t\t\tactions.add(transition.getValue().second);\n\t\t\t}\n\t\t}\n\t\treturn new ArrayList<>(actions);\n\t}\n\n\t/**\n\t * Get an iterator over the transitions from state s.\n\t */\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(int s);\n\n\t/**\n\t * Get an iterator over the transitions from state s, with their attached actions if present.\n\t */\n\tpublic default Iterator<Entry<Integer, Pair<Value, Object>>> getTransitionsAndActionsIterator(int s)\n\t{\n\t\t// Default implementation just adds null actions \n\t\tfinal Iterator<Entry<Integer, Value>> transitions = getTransitionsIterator(s);\n\t\treturn Reducible.extend(transitions).map(transition -> attachAction(transition, null));\n\t}\n\n\t/**\n\t * Get an iterator over the actions attached to transitions from state s.\n\t */\n\tpublic default Iterator<Object> getActionsIterator(int s)\n\t{\n\t\t// Default implementation just assumes null actions\n\t\treturn Collections.nCopies(getNumTransitions(s), null).iterator();\n\t}\n\n\t/**\n\t * Get an iterator over the indices of actions attached to transitions from state s.\n\t * Indices are into the list given by {@link #getActions()},\n\t * which includes null if there are unlabelled choices,\n\t * so this method should always return values >= 0.\n\t */\n\tpublic default PrimitiveIterator.OfInt getActionIndicesIterator(int s)\n\t{\n\t\t// Default implementation looks up indices from getActionsIterator\n\t\treturn new PrimitiveIterator.OfInt()\n\t\t{\n\t\t\tprivate final Iterator<Object> iter = getActionsIterator(s);\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn iter.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\treturn actionIndex(iter.next());\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get an iterator over the strings representing actions attached to transitions from state s.\n\t */\n\tpublic default Iterator<String> getActionStringsIterator(int s)\n\t{\n\t\t// Default implementation looks up indices from getActionsIterator\n\t\treturn new Iterator<String>()\n\t\t{\n\t\t\tprivate final Iterator<Object> iter = getActionsIterator(s);\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn iter.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic String next()\n\t\t\t{\n\t\t\t\treturn ActionList.actionString(iter.next());\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get the index of the (first) transition in state {@code s} with action label {@code action}.\n\t * Action labels (which are {@link Object}s) are tested for equality using\n\t * {@link Objects#equals(Object, Object)}, i.e., including null matching null.\n\t * Returns -1 if there is no matching action.\n\t */\n\tdefault int getTransitionByAction(int s, Object action)\n\t{\n\t\tIterator<Object> iter = getActionsIterator(s);\n\t\tfor (int i = 0; iter.hasNext(); i++) {\n\t\t\tif (Objects.equals(iter.next(), action)) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Get an iterator over the transitions from state {@code s},\n\t * after mapping probability values using the provided function.\n\t */\n\tpublic default <T> FunctionalIterator<Entry<Integer, T>> getTransitionsMappedIterator(int s, Function<? super Value, ? extends T> function)\n\t{\n\t\treturn Reducible.extend(getTransitionsIterator(s)).map(t -> new AbstractMap.SimpleImmutableEntry<>(t.getKey(), function.apply(t.getValue())));\n\t}\n\n\t/**\n\t * Attach an action to a transition, assuming iterators as used in\n\t * {@link #getTransitionsIterator(int)} and {@link #getTransitionsAndActionsIterator(int)}\n\t */\n\tpublic static <Value> Entry<Integer, Pair<Value, Object>> attachAction(final Entry<Integer, Value> transition, final Object action)\n\t{\n\t\tfinal Integer state = transition.getKey();\n\t\tfinal Value probability = transition.getValue();\n\t\treturn new AbstractMap.SimpleImmutableEntry<>(state, new Pair<>(probability, action));\n\t}\n\n\t/**\n\t * Functional interface for a consumer,\n\t * accepting transitions (s,t,d), i.e.,\n\t * from state s to state t with value d.\n\t */\n\t@FunctionalInterface\n\tpublic interface TransitionConsumer<Value> {\n\t\tvoid accept(int s, int t, Value d);\n\t}\n\n\t/**\n\t * Iterate over the outgoing transitions of state {@code s} and call the accept method\n\t * of the consumer for each of them:\n\t * <br>\n\t * Call {@code accept(s,t,d)} where t is the successor state and,\n\t * in a DTMC, d = P(s,t) is the probability from s to t,\n\t * while in CTMC, d = R(s,t) is the rate from s to t.\n\t * <p>\n\t * <i>Default implementation</i>: The default implementation relies on iterating over the\n\t * iterator returned by {@code getTransitionsIterator()}.\n\t * <p><i>Note</i>: This method is the base for the default implementation of the numerical\n\t * computation methods (mvMult, etc). In derived classes, it may thus be worthwhile to\n\t * provide a specialised implementation for this method that avoids using the Iterator mechanism.\n\t *\n\t * @param s the state s\n\t * @param c the consumer\n\t */\n\tpublic default void forEachTransition(int s, TransitionConsumer<Value> c)\n\t{\n\t\tfor (Iterator<Entry<Integer, Value>> it = getTransitionsIterator(s); it.hasNext(); ) {\n\t\t\tEntry<Integer, Value> e = it.next();\n\t\t\tc.accept(s, e.getKey(), e.getValue());\n\t\t}\n\t}\n\n\t/**\n\t * Functional interface for a function\n\t * mapping transitions (s,t,d), i.e.,\n\t * from state s to state t with value d\n\t * to a numerical value.\n\t */\n\t@FunctionalInterface\n\tpublic interface TransitionToValueFunction<Value> {\n\t\tValue apply(int s, int t, Value d);\n\t}\n\n\t/**\n\t * Iterate over the outgoing transitions of state {@code s}, call the function {@code f}\n\t * and return the sum of the result values:\n\t * <br>\n\t * Return sum_t f(s, t, P(s,t)), where t ranges over the successors of s.\n\t *\n\t * @param s the state s\n\t * @param f the consumer\n\t */\n\tpublic default Value sumOverTransitions(final int s, final TransitionToValueFunction<Value> f)\n\t{\n\t\tclass Sum {\n\t\t\tValue sum = getEvaluator().zero();\n\t\t\tvoid accept(int s, int t, Value d)\n\t\t\t{\n\t\t\t\tsum = getEvaluator().add(sum, f.apply(s, t, d));\n\t\t\t}\n\t\t}\n\n\t\tSum sum = new Sum();\n\t\tforEachTransition(s, sum::accept);\n\n\t\treturn sum.sum;\n\t}\n\n\t// Methods for case where Value is Double\n\t\n\t/**\n\t * Functional interface for a consumer,\n\t * accepting transitions (s,t,d), i.e.,\n\t * from state s to state t with value d.\n\t */\n\t@FunctionalInterface\n\tpublic interface DoubleTransitionConsumer {\n\t\tvoid accept(int s, int t, double d);\n\t}\n\n\t/**\n\t * Iterate over the outgoing transitions of state {@code s} and call the accept method\n\t * of the consumer for each of them:\n\t * <br>\n\t * Call {@code accept(s,t,d)} where t is the successor state and,\n\t * in a DTMC, d = P(s,t) is the probability from s to t,\n\t * while in CTMC, d = R(s,t) is the rate from s to t.\n\t * <p>\n\t * <i>Default implementation</i>: The default implementation relies on iterating over the\n\t * iterator returned by {@code getTransitionsIterator()}.\n\t * <p><i>Note</i>: This method is the base for the default implementation of the numerical\n\t * computation methods (mvMult, etc). In derived classes, it may thus be worthwhile to\n\t * provide a specialised implementation for this method that avoids using the Iterator mechanism.\n\t *\n\t * @param s the state s\n\t * @param c the consumer\n\t */\n\tpublic default void forEachDoubleTransition(int s, DoubleTransitionConsumer c)\n\t{\n\t\tfor (Iterator<Entry<Integer, Value>> it = getTransitionsIterator(s); it.hasNext(); ) {\n\t\t\tEntry<Integer, Value> e = it.next();\n\t\t\tc.accept(s, e.getKey(), getEvaluator().toDouble(e.getValue()));\n\t\t}\n\t}\n\n\t/**\n\t * Functional interface for a function\n\t * mapping transitions (s,t,d), i.e.,\n\t * from state s to state t with value d\n\t * to a numerical value.\n\t */\n\t@FunctionalInterface\n\tpublic interface DoubleTransitionToDoubleFunction {\n\t\tdouble apply(int s, int t, double d);\n\t}\n\n\t/**\n\t * Iterate over the outgoing transitions of state {@code s}, call the function {@code f}\n\t * and return the sum of the result values:\n\t * <br>\n\t * Return sum_t f(s, t, P(s,t)), where t ranges over the successors of s.\n\t *\n\t * @param s the state s\n\t * @param f the function\n\t */\n\tpublic default double sumOverDoubleTransitions(final int s, final DoubleTransitionToDoubleFunction f)\n\t{\n\t\tclass Sum {\n\t\t\tdouble sum = 0.0;\n\t\t\tvoid accept(int s, int t, double d)\n\t\t\t{\n\t\t\t\tsum += f.apply(s, t, d);\n\t\t\t}\n\t\t}\n\n\t\tSum sum = new Sum();\n\t\tforEachDoubleTransition(s, sum::accept);\n\n\t\treturn sum.sum;\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication for\n\t * the DTMC's transition probability matrix P and the vector {@code vect} passed in.\n\t * i.e. for all s: result[s] = sum_j P(s,j)*vect[j]\n\t * @param vect Vector to multiply by\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t */\n\tpublic default void mvMult(double vect[], double result[], BitSet subset, boolean complement)\n\t{\n\t\tmvMult(vect, result, new IterableStateSet(subset, getNumStates(), complement).iterator());\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication for the DTMC's transition probability matrix P\n\t * and the vector {@code vect} passed in, for the state indices provided by the iterator,\n\t * i.e., for all s of {@code states}: result[s] = sum_j P(s,j)*vect[j]\n\t * <p>\n\t * If the state indices in the iterator are not distinct, the result will still be valid,\n\t * but this situation should be avoided for performance reasons.\n\t * @param vect Vector to multiply by\n\t * @param result Vector to store result in\n\t * @param states Perform multiplication for these rows, in the iteration order\n\t */\n\tpublic default void mvMult(double vect[], double result[], PrimitiveIterator.OfInt states)\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tresult[s] = mvMultSingle(s, vect);\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication for\n\t * the DTMC's transition probability matrix P and the vector {@code vect} passed in.\n\t * i.e. return sum_j P(s,j)*vect[j]\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t */\n\tpublic default double mvMultSingle(int s, double vect[])\n\t{\n\t\treturn sumOverDoubleTransitions(s, (__, t, prob) -> {\n\t\t\treturn prob * vect[t];\n\t\t});\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication for\n\t * the DTMC's transition probability matrix P and the vector {@code vect} passed in,\n\t * storing new values directly in {@code vect} as computed.\n\t * i.e. for all s: vect[s] = (sum_{j!=s} P(s,j)*vect[j]) / (1-P(s,s))\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t * @return The maximum difference between old/new elements of {@code vect}\n\t */\n\tpublic default double mvMultGS(double vect[], BitSet subset, boolean complement, boolean absolute)\n\t{\n\t\treturn mvMultGS(vect, new IterableStateSet(subset, getNumStates(), complement).iterator(), absolute);\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication for\n\t * the DTMC's transition probability matrix P and the vector {@code vect} passed in,\n\t * storing new values directly in {@code vect} as computed.\n\t * The order and subset of states is given by the iterator {@code states},\n\t * i.e. for s in {@code states}: vect[s] = (sum_{j!=s} P(s,j)*vect[j]) / (1-P(s,s))\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param states Do multiplication for these rows, in this order\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t * @return The maximum difference between old/new elements of {@code vect}\n\t */\n\tpublic default double mvMultGS(double vect[], PrimitiveIterator.OfInt states, boolean absolute)\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\n\t\t\td = mvMultJacSingle(s, vect);\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication (in the interval iteration context) for\n\t * the DTMC's transition probability matrix P and the vector {@code vect} passed in,\n\t * storing new values directly in {@code vect} as computed (for use in interval iteration).\n\t * i.e. for all s: vect[s] = (sum_{j!=s} P(s,j)*vect[j]) / (1-P(s,s))\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param states Do multiplication for these rows, in this order\n\t * @param ensureMonotonic ensure monotonicity\n\t * @param checkMonotonic check monotonicity\n\t * @param fromBelow iteration from below or from above? (for ensureMonotonicity, checkMonotonicity)\n\t */\n\tpublic default void mvMultGSIntervalIter(double vect[], PrimitiveIterator.OfInt states, boolean ensureMonotonic, boolean checkMonotonic, boolean fromBelow) throws PrismException\n\t{\n\t\tdouble d;\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\n\t\t\td = mvMultJacSingle(s, vect);\n\t\t\tif (ensureMonotonic) {\n\t\t\t\tif (fromBelow) {\n\t\t\t\t\t// from below: do max old and new\n\t\t\t\t\tif (vect[s] > d) {\n\t\t\t\t\t\td = vect[s];\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// from above: do min old and new\n\t\t\t\t\tif (vect[s] < d) {\n\t\t\t\t\t\td = vect[s];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (checkMonotonic) {\n\t\t\t\tif (fromBelow) {\n\t\t\t\t\tif (vect[s] > d) {\n\t\t\t\t\t\tthrow new PrismException(\"Monotonicity violated (from below): old value \" + vect[s] + \" > new value \" + d);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (vect[s] < d) {\n\t\t\t\t\t\tthrow new PrismException(\"Monotonicity violated (from above): old value \" + vect[s] + \" < new value \" + d);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tvect[s] = d;\n\t\t}\n\t}\n\n\t/**\n\t * Do a Jacobi-style matrix-vector multiplication for the DTMC's transition probability matrix P\n\t * and the vector {@code vect} passed in, for the state indices provided by the iterator,\n\t * i.e., for all s of {@code states}: result[s] = (sum_{j!=s} P(s,j)*vect[j]) / (1-P(s,s))\n\t * <p>\n\t * If the state indices in the iterator are not distinct, the result will still be valid,\n\t * but this situation should be avoided for performance reasons.\n\t * @param vect Vector to multiply by\n\t * @param result Vector to store result in\n\t * @param states Perform multiplication for these rows, in the iteration order\n\t */\n\tpublic default void mvMultJac(double vect[], double result[], PrimitiveIterator.OfInt states)\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tresult[s] = mvMultJacSingle(s, vect);\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of Jacobi-style matrix-vector multiplication for\n\t * the DTMC's transition probability matrix P and the vector {@code vect} passed in.\n\t * i.e. return (sum_{j!=s} P(s,j)*vect[j]) / (1-P(s,s))\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t */\n\tpublic default double mvMultJacSingle(int s, double vect[])\n\t{\n\t\tclass Jacobi {\n\t\t\tdouble diag = 1.0;\n\t\t\tdouble d = 0.0;\n\n\t\t\tvoid accept(int s, int t, double prob) {\n\t\t\t\tif (t != s) {\n\t\t\t\t\td += prob * vect[t];\n\t\t\t\t} else {\n\t\t\t\t\tdiag -= prob;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tJacobi jac = new Jacobi();\n\t\tforEachDoubleTransition(s, jac::accept);\n\n\t\tdouble d = jac.d;\n\t\tdouble diag = jac.diag;\n\t\tif (diag > 0)\n\t\t\td /= diag;\n\n\t\treturn d;\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of action reward.\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t */\n\tpublic default void mvMultRew(double vect[], MCRewards<Double> mcRewards, double result[], BitSet subset, boolean complement)\n\t{\n\t\tmvMultRew(vect, mcRewards, result, new IterableStateSet(subset, getNumStates(), complement).iterator());\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of action reward.\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t * @param result Vector to store result in\n\t * @param states Do multiplication for these rows, in the specified order\n\t */\n\tpublic default void mvMultRew(double vect[], MCRewards<Double> mcRewards, double result[], PrimitiveIterator.OfInt states)\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tresult[s] = mvMultRewSingle(s, vect, mcRewards);\n\t\t}\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of action reward (Jacobi).\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t * @param result Vector to store result in\n\t * @param states Do multiplication for these rows, in the specified order\n\t */\n\tpublic default void mvMultRewJac(double vect[], MCRewards<Double> mcRewards, double result[], PrimitiveIterator.OfInt states)\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tresult[s] = mvMultRewJacSingle(s, vect, mcRewards);\n\t\t}\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of action reward (Gauss-Seidel).\n\t * @param vect Vector to multiply by and store result in\n\t * @param mcRewards The rewards\n\t * @param states Do multiplication for these rows, in the specified order\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t * @return The maximum difference between old/new elements of {@code vect}\n\t */\n\tpublic default double mvMultRewGS(double vect[], MCRewards<Double> mcRewards, PrimitiveIterator.OfInt states, boolean absolute)\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\td = mvMultRewJacSingle(s, vect, mcRewards);\n\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of action reward (Gauss-Seidel, interval iteration context).\n\t * @param vect Vector to multiply by and store result in\n\t * @param mcRewards The rewards\n\t * @param states Do multiplication for these rows, in the specified order\n\t * @param ensureMonotonic ensure monotonicity\n\t * @param checkMonotonic check monotonicity\n\t * @param fromBelow iteration from below or from above? (for ensureMonotonicity, checkMonotonicity)\n\t */\n\tpublic default void mvMultRewGSIntervalIter(double vect[], MCRewards<Double> mcRewards, PrimitiveIterator.OfInt states, boolean ensureMonotonic, boolean checkMonotonic, boolean fromBelow) throws PrismException\n\t{\n\t\tdouble d;\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\n\t\t\td = mvMultRewJacSingle(s, vect, mcRewards);\n\t\t\tif (ensureMonotonic) {\n\t\t\t\tif (fromBelow) {\n\t\t\t\t\t// from below: do max old and new\n\t\t\t\t\tif (vect[s] > d) {\n\t\t\t\t\t\td = vect[s];\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// from above: do min old and new\n\t\t\t\t\tif (vect[s] < d) {\n\t\t\t\t\t\td = vect[s];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (checkMonotonic) {\n\t\t\t\tif (fromBelow) {\n\t\t\t\t\tif (vect[s] > d) {\n\t\t\t\t\t\tthrow new PrismException(\"Monotonicity violated (from below): old value \" + vect[s] + \" > new value \" + d);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (vect[s] < d) {\n\t\t\t\t\t\tthrow new PrismException(\"Monotonicity violated (from above): old value \" + vect[s] + \" < new value \" + d);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tvect[s] = d;\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication and sum of action reward.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t */\n\tpublic default double mvMultRewSingle(int s, double vect[], MCRewards<Double> mcRewards)\n\t{\n\t\tdouble d = mcRewards.getStateReward(s);\n\t\td += sumOverDoubleTransitions(s, (__, t, prob) -> {\n\t\t\treturn prob * vect[t];\n\t\t});\n\t\treturn d;\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication and sum of reward, Jacobi-style,\n\t * i.e., return  ( rew(s) + sum_{t!=s} P(s,t)*vect[t] ) / (1 - P(s,s))\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t */\n\tpublic default double mvMultRewJacSingle(int s, double vect[], MCRewards<Double> mcRewards)\n\t{\n\t\tclass Jacobi {\n\t\t\tdouble diag = 1.0;\n\t\t\tdouble d = mcRewards.getStateReward(s);\n\t\t\tboolean onlySelfLoops = true;\n\n\t\t\tvoid accept(int s, int t, double prob) {\n\t\t\t\tif (t != s) {\n\t\t\t\t\td += prob * vect[t];\n\t\t\t\t\tonlySelfLoops = false;\n\t\t\t\t} else {\n\t\t\t\t\tdiag -= prob;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tJacobi jac = new Jacobi();\n\t\tforEachDoubleTransition(s, jac::accept);\n\n\t\tdouble d = jac.d;\n\t\tdouble diag = jac.diag;\n\n\t\tif (jac.onlySelfLoops) {\n\t\t\tif (d != 0) {\n\t\t\t\td = (d > 0 ? Double.POSITIVE_INFINITY : Double.NEGATIVE_INFINITY);\n\t\t\t} else {\n\t\t\t\t// no reward & only self-loops: d remains 0\n\t\t\t\td = 0;\n\t\t\t}\n\t\t} else {\n\t\t\t// not only self-loops, do Jacobi division\n\t\t\tif (diag > 0)\n\t\t\t\td /= diag;\n\t\t}\n\n\t\treturn d;\n\t}\n\n\t/**\n\t * Do a vector-matrix multiplication for\n\t * the DTMC's transition probability matrix P and the vector {@code vect} passed in.\n\t * i.e. for all s: result[s] = sum_i P(i,s)*vect[i]\n\t * @param vect Vector to multiply by\n\t * @param result Vector to store result in\n\t */\n\tpublic default void vmMult(double vect[], double result[])\n\t{\n\t\t// Initialise result to 0\n\t\tArrays.fill(result, 0);\n\t\t// Go through matrix elements (by row)\n\t\tfor (int state = 0, numStates = getNumStates(); state < numStates; state++) {\n\t\t\tforEachDoubleTransition(state, (s, t, prob) -> {\n\t\t\t\tresult[t] += prob * vect[s];\n\t\t\t});\n\t\t}\n\t}\n\n\t/**\n\t * Do a vector-matrix multiplication for steady-state computation with the power method.\n\t * <p>\n\t * Computes<br>\n\t * {@code result = vect * P} with matrix\n\t * {@code P = (Q * deltaT + I)} where<br/>\n\t * {@code Q} is the generator matrix,\n\t * {@code deltaT} the preconditioning factor and\n\t * {@code I} is the the identity matrix.<br/>\n\t * Please refer to <em>William J. Stewart: \"Introduction to the Numerical Solution of Markov Chains\"</em> p.124 for details.\n\t * </p>\n\t * <p>\n\t * If the {@code states} argument only specifies a subset of the state space,\n\t * only those entries of the {@code result} vector are modified that are either\n\t * states in {@code states} or their successors; other entries remain unchanged.\n\t * Thus, it generally only makes sense to use this method with a state sets that consists\n\t * of (the union of) bottom strongly-connected components (BSCCs).\n\t * </p>\n\t * @param vect Vector to multiply by\n\t * @param result Vector to store result in\n\t * @param diagsQ vector of the diagonal entries of the generator matrix Q, i.e., diagsQ[s] = -sum_{s!=t} prob(s,t)\n\t * @param deltaT deltaT conditioning factor\n\t * @param states subset of states to consider\n\t */\n\tpublic default void vmMultPowerSteadyState(double vect[], double[] result, double[] diagsQ, double deltaT, PrimitiveIterable.OfInt states)\n\t{\n\t\t// Recall that the generator matrix Q has entries\n\t\t//       Q(s,s) = -sum_{t!=s} prob(s,t)\n\t\t// and   Q(s,t) = prob(s,t)  for s!=t\n\t\t// The values Q(s,s) are passed in via the diagsQ vector, while the\n\t\t// values Q(s,t) correspond to the normal transitions\n\n\t\t// Initialise result for relevant states to vect[s] * (deltaT * diagsQ[s] + 1),\n\t\t// i.e., handle the product with the diagonal entries of (deltaT * Q) + I\n\t\tfor (OfInt it = states.iterator(); it.hasNext(); ) {\n\t\t\tint state = it.nextInt();\n\t\t\tresult[state] = vect[state] * ((deltaT * diagsQ[state]) + 1.0);\n\t\t}\n\n\t\t// For each relevant state...\n\t\tfor (OfInt it = states.iterator(); it.hasNext();) {\n\t\t\tint state = it.nextInt();\n\n\t\t\t// ... handle all Q(state,t) entries of the generator matrix\n\t\t\tforEachDoubleTransition(state, (s, t, prob) -> {\n\t\t\t\tif (s != t) {\n\t\t\t\t\t// ignore self loop, diagonal entries of the generator matrix handled above\n\t\t\t\t\t// update result vector entry for the *successor* state\n\t\t\t\t\tresult[t] += deltaT * prob * vect[s];\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t}\n\n\t/**\n\t * Generate a string representation for a DTMC.\n\t */\n\tdefault String toStringDTMC()\n\t{\n\t\tStringBuilder str = new StringBuilder(\"[ \");\n\t\tint numStates = getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tif (s > 0) {\n\t\t\t\tstr.append(\", \");\n\t\t\t}\n\t\t\tstr.append(s).append(\": \");\n\t\t\tstr.append(\"{\");\n\t\t\tIterator<Entry<Integer, Pair<Value, Object>>> iter = getTransitionsAndActionsIterator(s);\n\t\t\tboolean first = true;\n\t\t\twhile (iter.hasNext()) {\n\t\t\t\tif (first) {\n\t\t\t\t\tfirst = false;\n\t\t\t\t} else {\n\t\t\t\t\tstr.append(\",\");\n\t\t\t\t}\n\t\t\t\tEntry<Integer, Pair<Value, Object>> entry = iter.next();\n\t\t\t\tstr.append(entry.getValue().first).append(\":\").append(entry.getKey());\n\t\t\t\tif (entry.getValue().second != null) {\n\t\t\t\t\tstr.append(\":\").append(entry.getValue().second);\n\t\t\t\t}\n\t\t\t}\n\t\t\tstr.append(\"}\");\n\t\t}\n\t\tstr.append(\" ]\\n\");\n\t\treturn str.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMCEmbeddedSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.*;\nimport java.util.Map.Entry;\n\nimport explicit.rewards.MCRewards;\nimport parser.State;\nimport parser.Values;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Simple explicit-state representation of a DTMC, constructed (implicitly) as the embedded DTMC of a CTMC.\n * i.e. P(i,j) = R(i,j) / E(i) if E(i) > 0 and P(i,i) = 1 otherwise\n * where E(i) is the exit rate for state i: sum_j R(i,j).\n * This class is read-only: most of data is pointers to other model info.\n */\npublic class DTMCEmbeddedSimple<Value> extends DTMCExplicit<Value>\n{\n\t// Parent CTMC\n\tprotected CTMCSimple<Value> ctmc;\n\t// Exit rates vector\n\tprotected List<Value> exitRates;\n\t// Number of extra transitions added (just for stats)\n\tprotected int numExtraTransitions;\n\n\t/**\n\t * Constructor: create from CTMC.\n\t */\n\tpublic DTMCEmbeddedSimple(CTMCSimple<Value> ctmc)\n\t{\n\t\t// Initialise/copy basic model info\n\t\tinitialise(ctmc.getNumStates());\n\t\tcopyFrom(ctmc);\n\t\t// Store CTMC info\n\t\tthis.ctmc = ctmc;\n\t\texitRates = new ArrayList<>(numStates);\n\t\tnumExtraTransitions = 0;\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tValue sum = ctmc.getTransitions(i).sum();\n\t\t\texitRates.add(sum);\n\t\t\tif (getEvaluator().isZero(sum))\n\t\t\t\tnumExtraTransitions++;\n\t\t}\n\t}\n\n\t@Override\n\tpublic void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Not supported\");\n\t}\n\t\n\t// Accessors (for Model)\n\n\tpublic int getNumStates()\n\t{\n\t\treturn ctmc.getNumStates();\n\t}\n\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn ctmc.getNumInitialStates();\n\t}\n\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn ctmc.getInitialStates();\n\t}\n\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn ctmc.getFirstInitialState();\n\t}\n\n\tpublic boolean isInitialState(int i)\n\t{\n\t\treturn ctmc.isInitialState(i);\n\t}\n\n\tpublic boolean isDeadlockState(int i)\n\t{\n\t\treturn ctmc.isDeadlockState(i);\n\t}\n\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn ctmc.getStatesList();\n\t}\n\t\n\tpublic Values getConstantValues()\n\t{\n\t\treturn ctmc.getConstantValues();\n\t}\n\t\n\tpublic int getNumTransitions()\n\t{\n\t\treturn ctmc.getNumTransitions() + numExtraTransitions;\n\t}\n\n\tpublic int getNumTransitions(int s)\n\t{\n\t\tif (getEvaluator().isZero(exitRates.get(s))) {\n\t\t\treturn 1;\n\t\t} else {\n\t\t\treturn ctmc.getNumTransitions(s);\n\t\t}\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(final int s)\n\t{\n\t\tif (getEvaluator().isZero(exitRates.get(s))) {\n\t\t\treturn SuccessorsIterator.fromSingleton(s);\n\t\t} else {\n\t\t\treturn ctmc.getSuccessors(s);\n\t\t}\n\t}\n\n\tpublic int getNumChoices(int s)\n\t{\n\t\t// Always 1 for a DTMC\n\t\treturn 1;\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(String name)\n\t{\n\t\treturn ctmc.getLabelStates(name);\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn ctmc.hasLabel(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn ctmc.getLabels();\n\t}\n\n\t@Override\n\tpublic void addLabel(String name, BitSet states)\n\t{\n\t\tthrow new RuntimeException(\"Can not add label to DTMCEmbeddedSimple\");\n\t}\n\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\tpublic void checkForDeadlocks() throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\t@Override\n\tpublic String infoString()\n\t{\n\t\tString s = \"\";\n\t\ts += numStates + \" states (\" + getNumInitialStates() + \" initial)\";\n\t\ts += \", \" + getNumTransitions() + \" transitions (incl. \" + numExtraTransitions + \" self-loops)\";\n\t\treturn s;\n\t}\n\n\t// Accessors (for DTMC)\n\n\tpublic Iterator<Entry<Integer,Value>> getTransitionsIterator(int s)\n\t{\n\t\tif (getEvaluator().isZero(exitRates.get(s))) {\n\t\t\t// return prob-1 self-loop\n\t\t\treturn Collections.singletonMap(s, getEvaluator().one()).entrySet().iterator();\n\t\t} else {\n\t\t\tfinal Iterator<Entry<Integer,Value>> ctmcIterator = ctmc.getTransitionsIterator(s);\n\t\t\t\n\t\t\t// return iterator over entries, with probabilities divided by exitRates[s]\n\t\t\tfinal Value er = exitRates.get(s);\n\t\t\treturn new Iterator<Entry<Integer,Value>>() {\n\t\t\t\t@Override\n\t\t\t\tpublic boolean hasNext()\n\t\t\t\t{\n\t\t\t\t\treturn ctmcIterator.hasNext();\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic Entry<Integer, Value> next()\n\t\t\t\t{\n\t\t\t\t\tfinal Entry<Integer, Value> ctmcEntry = ctmcIterator.next();\n\t\t\t\t\t\n\t\t\t\t\treturn new Entry<Integer, Value>() {\n\t\t\t\t\t\t@Override\n\t\t\t\t\t\tpublic Integer getKey()\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\treturn ctmcEntry.getKey();\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t@Override\n\t\t\t\t\t\tpublic Value getValue()\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\treturn getEvaluator().divide(ctmcEntry.getValue(), er);\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t@Override\n\t\t\t\t\t\tpublic Value setValue(Value value)\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tthrow new UnsupportedOperationException();\n\t\t\t\t\t\t}\n\t\t\t\t\t};\n\t\t\t\t}\n\t\t\t};\n\t\t}\n\t}\n\n\t@Override\n\tpublic void forEachTransition(int s, TransitionConsumer<Value> c)\n\t{\n\t\tfinal Value er = exitRates.get(s);\n\t\tif (getEvaluator().isZero(er)) {\n\t\t\t// exit rate = 0 -> prob 1 self loop\n\t\t\tc.accept(s, s, getEvaluator().one());\n\t\t} else {\n\t\t\tctmc.forEachTransition(s, (s_,t,rate) -> {\n\t\t\t\tc.accept(s_, t, getEvaluator().divide(rate, er));\n\t\t\t});\n\t\t}\n\t}\n\n\t@Override\n\tpublic void forEachDoubleTransition(int s, DoubleTransitionConsumer c)\n\t{\n\t\tfinal double er = getEvaluator().toDouble(exitRates.get(s));\n\t\tif (er == 0) {\n\t\t\t// exit rate = 0 -> prob 1 self loop\n\t\t\tc.accept(s, s, 1.0);\n\t\t} else {\n\t\t\tctmc.forEachDoubleTransition(s, (s_,t,rate) -> {\n\t\t\t\tc.accept(s_, t, rate / er);\n\t\t\t});\n\t\t}\n\t}\n\n\tpublic double mvMultSingle(int s, double vect[])\n\t{\n\t\tDistribution<Value> distr = ctmc.getTransitions(s);\n\t\tdouble d = 0.0;\n\t\tdouble er = getEvaluator().toDouble(exitRates.get(s));\n\t\t// Exit rate 0: prob 1 self-loop\n\t\tif (er == 0) {\n\t\t\td += vect[s];\n\t\t}\n\t\t// Exit rate > 0\n\t\telse {\n\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\tint k = e.getKey();\n\t\t\t\tdouble prob = getEvaluator().toDouble(e.getValue());\n\t\t\t\td += prob * vect[k];\n\t\t\t}\n\t\t\td /= er;\n\t\t}\n\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double mvMultJacSingle(int s, double vect[])\n\t{\n\t\tDistribution<Value> distr = ctmc.getTransitions(s);\n\t\tdouble diag = 0.0, d = 0.0;\n\t\tdouble er = getEvaluator().toDouble(exitRates.get(s));\n\t\t// Exit rate 0: prob 1 self-loop\n\t\tif (er == 0) {\n\t\t\treturn 0.0;\n\t\t}\n\t\t// Exit rate > 0\n\t\telse {\n\t\t\t// (sum_{j!=s} P(s,j)*vect[j]) / (1-P(s,s))\n\t\t\t// = (sum_{j!=s} (R(s,j)/E(s))*vect[j]) / (1-(P(s,s)/E(s)))\n\t\t\t// = (sum_{j!=s} R(s,j)*vect[j]) / (E(s)-P(s,s))\n\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\tint k = e.getKey();\n\t\t\t\tdouble prob = getEvaluator().toDouble(e.getValue());\n\t\t\t\t// Non-diagonal entries only\n\t\t\t\tif (k != s) {\n\t\t\t\t\td += prob * vect[k];\n\t\t\t\t} else {\n\t\t\t\t\tdiag = prob;\n\t\t\t\t}\n\t\t\t}\n\t\t\td /= (er - diag);\n\t\t}\n\t\t\n\t\treturn d;\n\t}\n\n\tpublic double mvMultRewSingle(int s, double vect[], MCRewards<Double> mcRewards)\n\t{\n\t\tDistribution<Value> distr = ctmc.getTransitions(s);\n\t\tdouble er = getEvaluator().toDouble(exitRates.get(s));\n\t\tdouble d = 0;\n\t\t// Exit rate 0: prob 1 self-loop\n\t\tif (er == 0) {\n\t\t\td += vect[s];\n\t\t}\n\t\t// Exit rate > 0\n\t\telse {\n\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\tint k = e.getKey();\n\t\t\t\tdouble prob = getEvaluator().toDouble(e.getValue());\n\t\t\t\td += prob * vect[k];\n\t\t\t}\n\t\t\td /= er;\n\t\t}\n\t\td += mcRewards.getStateReward(s);\n\n\t\treturn d;\n\t}\n\n\t//@Override\n\tpublic double mvMultRewJacSingle(int s, double vect[], MCRewards<Double> mcRewards)\n\t{\n\t\tDistribution<Value> distr = ctmc.getTransitions(s);\n\t\tdouble diag = 0.0, d = 0.0;\n\t\tdouble er = getEvaluator().toDouble(exitRates.get(s));\n\t\t// Exit rate 0: prob 1 self-loop\n\t\tif (er == 0) {\n\t\t\treturn mcRewards.getStateReward(s);\n\t\t}\n\t\t// Exit rate > 0\n\t\telse {\n\t\t\t// (rew(s) + sum_{j!=s} P(s,j)*vect[j]) / (1-P(s,s))\n\t\t\t// = (rew(s) + sum_{j!=s} (R(s,j)/E(s))*vect[j]) / (1-(P(s,s)/E(s)))\n\t\t\t// = (E(s)*rew(s) + sum_{j!=s} R(s,j)*vect[j]) / (E(s)-P(s,s))\n\t\t\td = er * mcRewards.getStateReward(s);\n\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\tint k = e.getKey();\n\t\t\t\tdouble prob = getEvaluator().toDouble(e.getValue());\n\t\t\t\t// Non-diagonal entries only\n\t\t\t\tif (k != s) {\n\t\t\t\t\td += prob * vect[k];\n\t\t\t\t} else {\n\t\t\t\t\tdiag = prob;\n\t\t\t\t}\n\t\t\t}\n\t\t\td /= (er - diag);\n\t\t}\n\t\t\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic void vmMult(double vect[], double result[])\n\t{\n\t\t// Initialise result to 0\n\t\tArrays.fill(result, 0);\n\t\t// Go through matrix elements (by row)\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tdouble er = getEvaluator().toDouble(exitRates.get(state));\n\t\t\t// Exit rate 0: prob 1 self-loop\n\t\t\tif (er == 0) {\n\t\t\t\tresult[state] += vect[state];\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\t// Exit rate > 0\n\t\t\tfor (Iterator<Entry<Integer, Value>> transitions = ctmc.getTransitionsIterator(state); transitions.hasNext();) {\n\t\t\t\tEntry<Integer, Value> trans = transitions.next();\n\t\t\t\tint target  = trans.getKey();\n\t\t\t\tdouble prob = getEvaluator().toDouble(trans.getValue()) / er;\n\t\t\t\tresult[target] += prob * vect[state];\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, numStates;\n\t\tboolean first;\n\t\tString s = \"\";\n\t\ts += \"ctmc: \" + ctmc;\n\t\tfirst = true;\n\t\ts = \", exitRates: [ \";\n\t\tnumStates = getNumStates();\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\ts += \", \";\n\t\t\ts += i + \": \" + exitRates.get(i);\n\t\t}\n\t\ts += \" ]\";\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof DTMCEmbeddedSimple))\n\t\t\treturn false;\n\t\tDTMCEmbeddedSimple<?> dtmc = (DTMCEmbeddedSimple<?>) o;\n\t\tif (!ctmc.equals(dtmc.ctmc))\n\t\t\treturn false;\n\t\tif (!exitRates.equals(dtmc.exitRates))\n\t\t\treturn false;\n\t\tif (numExtraTransitions != dtmc.numExtraTransitions)\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMCExplicit.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\n/**\n * Base class for explicit-state representations of a DTMC.\n */\npublic abstract class DTMCExplicit<Value> extends ModelExplicit<Value> implements DTMC<Value>\n{\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMCFromMDPAndMDStrategy.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.*;\nimport java.util.Map.Entry;\n\nimport common.iterable.Reducible;\nimport explicit.rewards.MCRewards;\nimport parser.State;\nimport parser.Values;\nimport prism.Pair;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport strat.MDStrategy;\n\n/**\n* Explicit-state representation of a DTMC, constructed (implicitly)\n* from an MDP and a memoryless deterministic (MD) adversary.\n* This class is read-only: most of the data is pointers to other model info.\n*/\npublic class DTMCFromMDPAndMDStrategy<Value> extends DTMCExplicit<Value>\n{\n\t// Parent MDP\n\tprotected MDP<Value> mdp;\n\t// MD strategy\n\tprotected MDStrategy strat;\n\n\t/**\n\t * Constructor: create from MDP and memoryless adversary.\n\t */\n\tpublic DTMCFromMDPAndMDStrategy(MDP<Value> mdp, MDStrategy strat)\n\t{\n\t\tthis.mdp = mdp;\n\t\tthis.numStates = mdp.getNumStates();\n\t\tthis.strat = strat;\n\t}\n\n\t@Override\n\tpublic void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Not supported\");\n\t}\n\n\t// Accessors (for Model)\n\n\tpublic int getNumStates()\n\t{\n\t\treturn mdp.getNumStates();\n\t}\n\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn mdp.getNumInitialStates();\n\t}\n\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn mdp.getInitialStates();\n\t}\n\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn mdp.getFirstInitialState();\n\t}\n\n\tpublic boolean isInitialState(int i)\n\t{\n\t\treturn mdp.isInitialState(i);\n\t}\n\n\tpublic boolean isDeadlockState(int i)\n\t{\n\t\treturn mdp.isDeadlockState(i);\n\t}\n\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn mdp.getStatesList();\n\t}\n\n\tpublic Values getConstantValues()\n\t{\n\t\treturn mdp.getConstantValues();\n\t}\n\n\tpublic int getNumTransitions(int s)\n\t{\n\t\treturn strat.isChoiceDefined(s) ? mdp.getNumTransitions(s, strat.getChoiceIndex(s)) : 0;\n\t}\n\n\tpublic SuccessorsIterator getSuccessors(final int s)\n\t{\n\t\tif (strat.isChoiceDefined(s)) {\n\t\t\treturn mdp.getSuccessors(s, strat.getChoiceIndex(s));\n\t\t} else {\n\t\t\treturn SuccessorsIterator.empty();\n\t\t}\n\t}\n\n\tpublic int getNumChoices(int s)\n\t{\n\t\t// Always 1 for a DTMC\n\t\treturn 1;\n\t}\n\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\tpublic void checkForDeadlocks() throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\t// Accessors (for DTMC)\n\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(int s)\n\t{\n\t\tif (strat.isChoiceDefined(s)) {\n\t\t\treturn mdp.getTransitionsIterator(s, strat.getChoiceIndex(s));\n\t\t} else {\n\t\t\treturn Collections.emptyIterator();\n\t\t}\n\t}\n\n\tpublic Iterator<Entry<Integer, Pair<Value, Object>>> getTransitionsAndActionsIterator(int s)\n\t{\n\t\tif (strat.isChoiceDefined(s)) {\n\t\t\tfinal Iterator<Entry<Integer, Value>> transitions = mdp.getTransitionsIterator(s, strat.getChoiceIndex(s));\n\t\t\treturn Reducible.extend(transitions).map(transition -> DTMC.attachAction(transition, mdp.getAction(s, strat.getChoiceIndex(s))));\n\t\t} else {\n\t\t\treturn Collections.emptyIterator();\n\t\t}\n\t}\n\n\t@Override\n\tpublic Iterator<Object> getActionsIterator(int s)\n\t{\n\t\tif (strat.isChoiceDefined(s)) {\n\t\t\treturn Collections.nCopies(getNumTransitions(s), mdp.getAction(s, strat.getChoiceIndex(s))).iterator();\n\t\t} else {\n\t\t\treturn Collections.emptyIterator();\n\t\t}\n\t}\n\n\t@Override\n\tpublic void forEachTransition(int s, TransitionConsumer<Value> c)\n\t{\n\t\tif (!strat.isChoiceDefined(s)) {\n\t\t\treturn;\n\t\t}\n\t\tmdp.forEachTransition(s, strat.getChoiceIndex(s), c::accept);\n\t}\n\n\t@Override\n\tpublic double mvMultSingle(int s, double vect[])\n\t{\n\t\treturn strat.isChoiceDefined(s) ? mdp.mvMultSingle(s, strat.getChoiceIndex(s), vect) : 0;\n\t}\n\n\t@Override\n\tpublic double mvMultJacSingle(int s, double vect[])\n\t{\n\t\treturn strat.isChoiceDefined(s) ? mdp.mvMultJacSingle(s, strat.getChoiceIndex(s), vect) : 0;\n\t}\n\n\t@Override\n\tpublic double mvMultRewSingle(int s, double vect[], MCRewards<Double> mcRewards)\n\t{\n\t\treturn strat.isChoiceDefined(s) ? mdp.mvMultRewSingle(s, strat.getChoiceIndex(s), vect, mcRewards) : 0;\n\t}\n\n\t@Override\n\tpublic void vmMult(double vect[], double result[])\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMCFromMDPMemorylessAdversary.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\n\nimport common.iterable.Reducible;\nimport parser.State;\nimport parser.Values;\nimport prism.Pair;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport explicit.rewards.MCRewards;\n\n/**\n * Explicit-state representation of a DTMC, constructed (implicitly)\n * from an MDP and a memoryless adversary, specified as an array of integer indices.\n * This class is read-only: most of data is pointers to other model info.\n */\npublic class DTMCFromMDPMemorylessAdversary<Value> extends DTMCExplicit<Value>\n{\n\t// Parent MDP\n\tprotected MDP<Value> mdp;\n\t// Adversary (array of choice indices; -1 denotes no choice)\n\tprotected int adv[];\n\n\t/**\n\t * Constructor: create from MDP and memoryless adversary.\n\t */\n\tpublic DTMCFromMDPMemorylessAdversary(MDP<Value> mdp, int adv[])\n\t{\n\t\tthis.mdp = mdp;\n\t\tthis.numStates = mdp.getNumStates();\n\t\tthis.adv = adv;\n\t}\n\n\t@Override\n\tpublic void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Not supported\");\n\t}\n\n\t// Accessors (for Model)\n\n\tpublic int getNumStates()\n\t{\n\t\treturn mdp.getNumStates();\n\t}\n\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn mdp.getNumInitialStates();\n\t}\n\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn mdp.getInitialStates();\n\t}\n\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn mdp.getFirstInitialState();\n\t}\n\n\tpublic boolean isInitialState(int i)\n\t{\n\t\treturn mdp.isInitialState(i);\n\t}\n\n\tpublic boolean isDeadlockState(int i)\n\t{\n\t\treturn mdp.isDeadlockState(i);\n\t}\n\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn mdp.getStatesList();\n\t}\n\n\tpublic Values getConstantValues()\n\t{\n\t\treturn mdp.getConstantValues();\n\t}\n\n\tpublic int getNumTransitions(int s)\n\t{\n\t\treturn adv[s] >= 0 ? mdp.getNumTransitions(s, adv[s]) : 0;\n\t}\n\n\tpublic SuccessorsIterator getSuccessors(final int s)\n\t{\n\t\tif (adv[s] >= 0) {\n\t\t\treturn mdp.getSuccessors(s, adv[s]);\n\t\t} else {\n\t\t\treturn SuccessorsIterator.empty();\n\t\t}\n\t}\n\n\tpublic int getNumChoices(int s)\n\t{\n\t\t// Always 1 for a DTMC\n\t\treturn 1;\n\t}\n\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\tpublic void checkForDeadlocks() throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\t// Accessors (for DTMC)\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(int s)\n\t{\n\t\tif (adv[s] >= 0) {\n\t\t\treturn mdp.getTransitionsIterator(s, adv[s]);\n\t\t} else {\n\t\t\treturn Collections.emptyIterator();\n\t\t}\n\t}\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Pair<Value, Object>>> getTransitionsAndActionsIterator(int s)\n\t{\n\t\tif (adv[s] >= 0) {\n\t\t\tfinal Iterator<Entry<Integer, Value>> transitions = mdp.getTransitionsIterator(s, adv[s]);\n\t\t\treturn Reducible.extend(transitions).map(transition -> DTMC.attachAction(transition, mdp.getAction(s, adv[s])));\n\t\t} else {\n\t\t\treturn Collections.emptyIterator();\n\t\t}\n\t}\n\n\t@Override\n\tpublic Iterator<Object> getActionsIterator(int s)\n\t{\n\t\tif (adv[s] >= 0) {\n\t\t\treturn Collections.nCopies(getNumTransitions(s), mdp.getAction(s, adv[s])).iterator();\n\t\t} else {\n\t\t\treturn Collections.emptyIterator();\n\t\t}\n\t}\n\n\t@Override\n\tpublic double mvMultSingle(int s, double vect[])\n\t{\n\t\treturn adv[s] >= 0 ? mdp.mvMultSingle(s, adv[s], vect) : 0;\n\t}\n\n\t@Override\n\tpublic double mvMultJacSingle(int s, double vect[])\n\t{\n\t\treturn adv[s] >= 0 ? mdp.mvMultJacSingle(s, adv[s], vect) : 0;\n\t}\n\n\t@Override\n\tpublic double mvMultRewSingle(int s, double vect[], MCRewards<Double> mcRewards)\n\t{\n\t\treturn adv[s] >= 0 ? mdp.mvMultRewSingle(s, adv[s], vect, mcRewards) : 0;\n\t}\n\n\t@Override\n\tpublic void vmMult(double vect[], double result[])\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMCModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Map.Entry;\nimport java.util.PrimitiveIterator;\nimport java.util.PrimitiveIterator.OfInt;\n\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceType;\nimport common.IntSet;\nimport common.IterableBitSet;\nimport common.StopWatch;\nimport explicit.modelviews.DTMCAlteredDistributions;\nimport explicit.modelviews.MDPFromDTMC;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.Rewards;\nimport io.ModelExportFormat;\nimport parser.ast.Expression;\nimport prism.AccuracyFactory;\nimport prism.ModelType;\nimport prism.OptionsIntervalIteration;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport prism.PrismUtils;\n\n/**\n * Explicit-state model checker for discrete-time Markov chains (DTMCs).\n */\npublic class DTMCModelChecker extends ProbModelChecker\n{\n\t/**\n\t * Create a new DTMCModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic DTMCModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t// Model checking functions\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tprotected StateValues checkProbPathFormulaLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of Markov chain and DA for the LTL formula, and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tAcceptanceType[] allowedAcceptance = {\n\t\t\t\tAcceptanceType.RABIN,\n\t\t\t\tAcceptanceType.REACH,\n\t\t\t\tAcceptanceType.BUCHI,\n\t\t\t\tAcceptanceType.STREETT,\n\t\t\t\tAcceptanceType.GENERIC\n\t\t};\n\t\tLTLModelChecker.LTLProduct<DTMC<Double>> product = mcLtl.constructDAProductForLTLFormula(this, (DTMC<Double>) model, expr, statesOfInterest, allowedAcceptance);\n\t\tdoProductExports(product);\n\t\t\n\t\t// Find accepting states + compute reachability probabilities\n\t\tBitSet acc;\n\t\tif (product.getAcceptance() instanceof AcceptanceReach) {\n\t\t\tmainLog.println(\"\\nSkipping BSCC computation since acceptance is defined via goal states...\");\n\t\t\tacc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\t\t} else {\n\t\t\tmainLog.println(\"\\nFinding accepting BSCCs...\");\n\t\t\tacc = mcLtl.findAcceptingBSCCs(product.getProductModel(), product.getAcceptance());\n\t\t}\n\t\tmainLog.println(\"\\nComputing reachability probabilities...\");\n\t\tDTMCModelChecker mcProduct = new DTMCModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachProbs(product.getProductModel(), acc); \n\t\tStateValues probsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\t\tprobsProduct.print(out, false, false, false, false);\n\t\t\t\tout.close();\n\t\t}\n\t\t\n\t\t// Mapping probabilities in the original model\n\t\tStateValues probs = product.projectToOriginalModel(probsProduct);\n\t\tprobsProduct.clear();\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute rewards for a co-safe LTL reward operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardCoSafeLTL(Model<?> model, Rewards<?> modelRewards, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of MC and DFA for the LTL formula, convert rewards and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tLTLModelChecker.LTLProduct<DTMC<Double>> product = mcLtl.constructDFAProductForCosafetyReward(this, (DTMC<Double>) model, expr, statesOfInterest);\n\t\tMCRewards<Double> productRewards = ((MCRewards<Double>) modelRewards).liftFromModel(product);\n\t\tdoProductExports(product);\n\n\t\t// Find accepting states + compute reachability rewards\n\t\tBitSet acc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\n\t\tmainLog.println(\"\\nComputing reachability rewards...\");\n\t\tDTMCModelChecker mcProduct = new DTMCModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachRewards((DTMC<Double>)product.getProductModel(), productRewards, acc);\n\t\tStateValues rewardsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\t\trewardsProduct.print(out, false, false, false, false);\n\t\t\t\tout.close();\n\t\t}\n\n\t\t// Mapping rewards in the original model\n\t\tStateValues rewards = product.projectToOriginalModel(rewardsProduct);\n\t\trewardsProduct.clear();\n\n\t\treturn rewards;\n\t}\n\t\n\tpublic ModelCheckerResult computeInstantaneousRewards(DTMC<Double> dtmc, MCRewards<Double> mcRewards, int k, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tif (statesOfInterest.cardinality() == 1) {\n\t\t\treturn computeInstantaneousRewardsForwards(dtmc, mcRewards, k, statesOfInterest.nextSetBit(0));\n\t\t} else {\n\t\t\treturn computeInstantaneousRewardsBackwards(dtmc, mcRewards, k);\n\t\t}\n\t}\n\t\n\tpublic ModelCheckerResult computeInstantaneousRewardsBackwards(DTMC<Double> dtmc, MCRewards<Double> mcRewards, int k) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Start backwards transient computation\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting backwards instantaneous rewards computation...\");\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = mcRewards.getStateReward(i);\n\n\t\t// Start iterations\n\t\tfor (iters = 0; iters < k; iters++) {\n\t\t\t// Matrix-vector multiply\n\t\t\tdtmc.mvMult(soln, soln2, null, false);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished backwards transient computation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Backwards transient instantaneous rewards computation\");\n\t\tmainLog.println(\" took \" + iters + \" iters and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.lastSoln = soln2;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\tpublic ModelCheckerResult computeInstantaneousRewardsForwards(DTMC<Double> dtmc, MCRewards<Double> mcRewards, int k, int stateOfInterest) throws PrismException\n\t{\n\t\t// Build a point probability distribution for the required state  \n\t\tdouble[] initDist = new double[dtmc.getNumStates()];\n\t\tinitDist[stateOfInterest] = 1.0;\n\t\t\n\t\t// Compute (forward) transient probabilities\n\t\tModelCheckerResult res = computeTransientProbs(dtmc, k, initDist);\n\t\t\n\t\t// Compute expected value (from initial state)\n\t\tint n = dtmc.getNumStates();\n\t\tdouble avg = 0.0;\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tavg += res.soln[i] *= mcRewards.getStateReward(i);\n\t\t}\n\n\t\t// Reuse vector/result storage\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tres.soln[i] = 0.0;\n\t\t}\n\t\tres.soln[stateOfInterest] = avg;\n\t\t\n\t\treturn res;\n\t}\n\t\n\tpublic ModelCheckerResult computeCumulativeRewards(DTMC<Double> dtmc, MCRewards<Double> mcRewards, double t) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\t\tint right = (int) t;\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Start backwards transient computation\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting backwards cumulative rewards computation...\");\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Start iterations\n\t\tfor (iters = 0; iters < right; iters++) {\n\t\t\t// Matrix-vector multiply plus adding rewards\n\t\t\tdtmc.mvMult(soln, soln2, null, false);\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tsoln2[i] += mcRewards.getStateReward(i);\n\t\t\t}\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished backwards transient computation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Backwards cumulative rewards computation\");\n\t\tmainLog.println(\" took \" + iters + \" iters and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.lastSoln = soln2;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\tpublic ModelCheckerResult computeTotalRewards(DTMC<Double> dtmc, MCRewards<Double> mcRewards) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint n, numBSCCs = 0;\n\t\tlong timer;\n\n\t\tif (getDoIntervalIteration()) {\n\t\t\tthrow new PrismNotSupportedException(\"Interval iteration for total rewards is currently not supported\");\n\t\t}\n\n\t\t// Switch to a supported method, if necessary\n\t\tif (!(linEqMethod == LinEqMethod.POWER)) {\n\t\t\tlinEqMethod = LinEqMethod.POWER;\n\t\t\tmainLog.printWarning(\"Switching to linear equation solution method \\\"\" + linEqMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Start total rewards computation\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting total reward computation...\");\n\n\t\t// Compute bottom strongly connected components (BSCCs)\n\t\tSCCConsumerStore sccStore = new SCCConsumerStore();\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, dtmc, sccStore);\n\t\tsccComputer.computeSCCs();\n\t\tList<BitSet> bsccs = sccStore.getBSCCs();\n\t\tnumBSCCs = bsccs.size();\n\n\t\t// Find BSCCs with non-zero reward\n\t\tBitSet bsccsNonZero = new BitSet();\n\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\tBitSet bscc = bsccs.get(b);\n\t\t\tfor (int i = bscc.nextSetBit(0); i >= 0; i = bscc.nextSetBit(i + 1)) {\n\t\t\t\tif (mcRewards.getStateReward(i) > 0) {\n\t\t\t\t\tbsccsNonZero.or(bscc);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tmainLog.print(\"States in non-zero reward BSCCs: \" + bsccsNonZero.cardinality() + \"\\n\");\n\n\t\t// Find states with infinite reward (those reach a non-zero reward BSCC with prob > 0)\n\t\tBitSet inf;\n\t\tif (preRel) {\n\t\t\t// prob0 using predecessor relation\n\t\t\tPredecessorRelation pre = dtmc.getPredecessorRelation(this, true);\n\t\t\tinf = prob0(dtmc, null, bsccsNonZero, pre);\n\t\t} else {\n\t\t\t// prob0 using fixed point algorithm\n\t\t\tinf = prob0(dtmc, null, bsccsNonZero);\n\t\t}\n\t\tinf.flip(0, n);\n\t\tint numInf = inf.cardinality();\n\t\tmainLog.println(\"inf=\" + numInf + \", maybe=\" + (n - numInf));\n\t\t\n\t\t// Compute rewards\n\t\t// (do this using the functions for \"reward reachability\" properties but with no targets)\n\t\tswitch (linEqMethod) {\n\t\tcase POWER:\n\t\t\tres = computeReachRewardsValIter(dtmc, mcRewards, new BitSet(), inf, null, null);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown linear equation solution method \" + linEqMethod.fullName());\n\t\t}\n\n\t\t// Finished total reward computation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Total reward computation\");\n\t\tmainLog.println(\" took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\treturn res;\n\t}\n\n\t// Steady-state/transient probability computation\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doSteadyState(DTMC<Double> dtmc) throws PrismException\n\t{\n\t\treturn doSteadyState(dtmc, (StateValues) null);\n\t}\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Optionally, use the passed in file initDistFile to give the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doSteadyState(DTMC<Double> dtmc, File initDistFile) throws PrismException\n\t{\n\t\tStateValues initDist = readDistributionFromFile(initDistFile, dtmc);\n\t\treturn doSteadyState(dtmc, initDist);\n\t}\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Optionally, use the passed in vector initDist as the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * For reasons of efficiency, when a vector is passed in, it will be trampled over,\n\t * so if you wanted it, take a copy. \n\t * @param dtmc The DTMC\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic StateValues doSteadyState(DTMC<Double> dtmc, StateValues initDist) throws PrismException\n\t{\n\t\tStateValues initDistNew = (initDist == null) ? buildInitialDistribution(dtmc) : initDist;\n\t\tModelCheckerResult res = computeSteadyStateProbs(dtmc, initDistNew.getDoubleArray());\n\t\treturn StateValues.createFromDoubleArray(res.soln, dtmc);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doTransient(DTMC<Double> dtmc, int k) throws PrismException\n\t{\n\t\treturn doTransient(dtmc, k, (StateValues) null);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Optionally, use the passed in file initDistFile to give the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * @param dtmc The DTMC\n\t * @param k Time step\n\t * @param initDistFile File containing initial distribution\n\t */\n\tpublic StateValues doTransient(DTMC<Double> dtmc, int k, File initDistFile) throws PrismException\n\t{\n\t\tStateValues initDist = readDistributionFromFile(initDistFile, dtmc);\n\t\treturn doTransient(dtmc, k, initDist);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Optionally, use the passed in vector initDist as the initial probability distribution (time step 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * For reasons of efficiency, when a vector is passed in, it will be trampled over,\n\t * so if you wanted it, take a copy. \n\t * @param dtmc The DTMC\n\t * @param k Time step\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic StateValues doTransient(DTMC<Double> dtmc, int k, StateValues initDist) throws PrismException\n\t{\n\t\tStateValues initDistNew = (initDist == null) ? buildInitialDistribution(dtmc) : initDist;\n\t\tModelCheckerResult res = computeTransientProbs(dtmc, k, initDistNew.getDoubleArray());\n\t\treturn StateValues.createFromDoubleArray(res.soln, dtmc);\n\t}\n\n\t// Numerical computation functions\n\n\t/**\n\t * Compute next=state probabilities.\n\t * i.e. compute the probability of being in a state in {@code target} in the next step.\n\t * @param dtmc The DTMC\n\t * @param target Target states\n\t */\n\tpublic ModelCheckerResult computeNextProbs(DTMC<Double> dtmc, BitSet target) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint n;\n\t\tdouble soln[], soln2[];\n\t\tlong timer;\n\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Create/initialise solution vector(s)\n\t\tsoln = Utils.bitsetToDoubleArray(target, n);\n\t\tsoln2 = new double[n];\n\n\t\t// Next-step probabilities \n\t\tdtmc.mvMult(soln, soln2, null, false);\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.soln = soln2;\n\t\tres.numIters = 1;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Given a value vector x, compute the probability:\n\t *   v(s) = Sum_s' P(s,s')*x(s')   for s labeled with a,\n\t *   v(s) = 0                      for s not labeled with a.\n\t *\n\t * @param dtmc the DTMC model\n\t * @param a the set of states labeled with a\n\t * @param x the value vector\n\t */\n\tprotected double[] computeRestrictedNext(DTMC<Double> dtmc, BitSet a, double[] x)\n\t{\n\t\tdouble[] soln;\n\t\tint n;\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// initialized to 0.0\n\t\tsoln = new double[n];\n\n\t\t// Next-step probabilities multiplication\n\t\t// restricted to a states\n\t\tdtmc.mvMult(x, soln, a, false);\n\n\t\treturn soln;\n\t}\n\n\t/**\n\t * Compute reachability probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target}.\n\t * @param dtmc The DTMC\n\t * @param target Target states\n\t */\n\tpublic ModelCheckerResult computeReachProbs(DTMC<Double> dtmc, BitSet target) throws PrismException\n\t{\n\t\treturn computeReachProbs(dtmc, null, target, null, null);\n\t}\n\n\t/**\n\t * Compute until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * while remaining in those in {@code remain}.\n\t * @param dtmc The DTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t */\n\tpublic ModelCheckerResult computeUntilProbs(DTMC<Double> dtmc, BitSet remain, BitSet target) throws PrismException\n\t{\n\t\treturn computeReachProbs(dtmc, remain, target, null, null);\n\t}\n\n\t/**\n\t * Compute reachability/until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * while remaining in those in {@code remain}.\n\t * @param dtmc The DTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param init Optionally, an initial solution vector (may be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tpublic ModelCheckerResult computeReachProbs(DTMC<Double> dtmc, BitSet remain, BitSet target, double init[], BitSet known) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet no, yes;\n\t\tint n, numYes, numNo;\n\t\tlong timer, timerProb0, timerProb1;\n\t\tPredecessorRelation pre = null;\n\t\t// Local copy of setting\n\t\tLinEqMethod linEqMethod = this.linEqMethod;\n\n\t\t// Switch to a supported method, if necessary\n\t\tswitch (linEqMethod)\n\t\t{\n\t\tcase POWER:\n\t\tcase GAUSS_SEIDEL:\n\t\tcase BACKWARDS_GAUSS_SEIDEL:\n\t\tcase JACOBI:\n\t\t\tbreak; // supported\n\t\tdefault:\n\t\t\tlinEqMethod = LinEqMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to linear equation solution method \\\"\" + linEqMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\tif (doIntervalIteration && (!precomp || !prob0 || !prob1)) {\n\t\t\tthrow new PrismNotSupportedException(\"Interval iteration requires precomputations to be active\");\n\t\t}\n\n\t\t// Start probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting probabilistic reachability...\");\n\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tdtmc.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Optimise by enlarging target set (if more info is available)\n\t\tif (init != null && known != null && !known.isEmpty()) {\n\t\t\tBitSet targetNew = (BitSet) target.clone();\n\t\t\tfor (int i : new IterableBitSet(known)) {\n\t\t\t\tif (init[i] == 1.0) {\n\t\t\t\t\ttargetNew.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\ttarget = targetNew;\n\t\t}\n\n\t\t// If required, export info about target states\n\t\tif (getExportTarget()) {\n\t\t\tBitSet bsInit = new BitSet(n);\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tbsInit.set(i, dtmc.isInitialState(i));\n\t\t\t}\n\t\t\tList<BitSet> labels = Arrays.asList(bsInit, target);\n\t\t\tList<String> labelNames = Arrays.asList(\"init\", \"target\");\n\t\t\tmainLog.println(\"\\nExporting target states info to file \\\"\" + getExportTargetFilename() + \"\\\"...\");\n\t\t\texportLabels(dtmc, labelNames, labels, new File(getExportTargetFilename()), ModelExportFormat.EXPLICIT);\n\t\t}\n\n\t\tif (precomp && (prob0 || prob1) && preRel) {\n\t\t\tpre = dtmc.getPredecessorRelation(this, true);\n\t\t}\n\n\t\t// Precomputation\n\t\ttimerProb0 = System.currentTimeMillis();\n\t\tif (precomp && prob0) {\n\t\t\tif (preRel) {\n\t\t\t\tno = prob0(dtmc, remain, target, pre);\n\t\t\t} else {\n\t\t\t\tno = prob0(dtmc, remain, target);\n\t\t\t}\n\t\t} else {\n\t\t\tno = new BitSet();\n\t\t\tif (remain != null) {\n\t\t\t\tno.or(remain);\n\t\t\t\tno.or(target);\n\t\t\t\tno.flip(0, n);\n\t\t\t}\n\t\t}\n\t\ttimerProb0 = System.currentTimeMillis() - timerProb0;\n\t\ttimerProb1 = System.currentTimeMillis();\n\t\tif (precomp && prob1) {\n\t\t\tif (preRel) {\n\t\t\t\tyes = prob1(dtmc, remain, target, pre);\n\t\t\t} else {\n\t\t\t\tyes = prob1(dtmc, remain, target);\n\t\t\t}\n\t\t} else {\n\t\t\tyes = (BitSet) target.clone();\n\t\t}\n\t\ttimerProb1 = System.currentTimeMillis() - timerProb1;\n\n\t\t// Print results of precomputation\n\t\tnumYes = yes.cardinality();\n\t\tnumNo = no.cardinality();\n\t\tmainLog.println(\"target=\" + target.cardinality() + \", yes=\" + numYes + \", no=\" + numNo + \", maybe=\" + (n - (numYes + numNo)));\n\n\t\t// Compute probabilities (if needed)\n\t\tif (numYes + numNo < n) {\n\t\t\tboolean termCritAbsolute = termCrit == TermCrit.ABSOLUTE;\n\t\t\tIterationMethod iterationMethod = null;\n\t\t\tswitch (linEqMethod) {\n\t\t\tcase POWER:\n\t\t\t\titerationMethod = new IterationMethodPower(termCritAbsolute, termCritParam);\n\t\t\t\tbreak;\n\t\t\tcase JACOBI:\n\t\t\t\titerationMethod = new IterationMethodJacobi(termCritAbsolute, termCritParam);\n\t\t\t\tbreak;\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\tcase BACKWARDS_GAUSS_SEIDEL: {\n\t\t\t\tboolean backwards = linEqMethod == LinEqMethod.BACKWARDS_GAUSS_SEIDEL;\n\t\t\t\titerationMethod = new IterationMethodGS(termCritAbsolute, termCritParam, backwards);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown linear equation solution method \" + linEqMethod.fullName());\n\t\t\t}\n\t\t\tif (doIntervalIteration) {\n\t\t\t\tres = doIntervalIterationReachProbs(dtmc, no, yes, init, known, iterationMethod, getDoTopologicalValueIteration());\n\t\t\t} else {\n\t\t\t\tres = doValueIterationReachProbs(dtmc, no, yes, init, known, iterationMethod, getDoTopologicalValueIteration());\n\t\t\t}\n\t\t} else {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(yes, n);\n\t\t\tres.accuracy = AccuracyFactory.doublesFromQualitative();\n\t\t}\n\n\t\t// Finished probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Probabilistic reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timeProb0 = timerProb0 / 1000.0;\n\t\tres.timePre = (timerProb0 + timerProb1) / 1000.0;\n\n\t\treturn res;\n\t}\n\n\n\t/**\n\t * Prob0 precomputation algorithm (using predecessor relation),\n\t * i.e. determine the states of a DTMC which, with probability 0,\n\t * reach a state in {@code target}, while remaining in those in {@code remain}.\n\t * @param dtmc The DTMC\n\t * @param remain Remain in these states (optional: {@code null} means \"all states\")\n\t * @param target Target states\n\t * @param pre The predecessor relation\n\t */\n\tpublic BitSet prob0(Model<?> dtmc, BitSet remain, BitSet target, PredecessorRelation pre)\n\t{\n\t\tBitSet canReachTarget, result;\n\t\tlong timer;\n\n\t\t// Start precomputation\n\t\ttimer = System.currentTimeMillis();\n\t\tif (!silentPrecomputations)\n\t\t\tmainLog.println(\"Starting Prob0...\");\n\n\t\t// Special case: no target states\n\t\tif (target.isEmpty()) {\n\t\t\tBitSet soln = new BitSet(dtmc.getNumStates());\n\t\t\tsoln.set(0, dtmc.getNumStates());\n\t\t\treturn soln;\n\t\t}\n\n\t\t// calculate all states that can reach 'target'\n\t\t// while remaining in 'remain' in the underlying graph,\n\t\t// where all the 'target' states are made absorbing\n\t\tcanReachTarget = pre.calculatePreStar(remain, target, target);\n\n\t\t// prob0 = complement of 'canReachTarget'\n\t\tresult = new BitSet();\n\t\tresult.set(0, dtmc.getNumStates(), true);\n\t\tresult.andNot(canReachTarget);\n\n\t\t// Finished precomputation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (!silentPrecomputations) {\n\t\t\tmainLog.print(\"Prob0\");\n\t\t\tmainLog.println(\" took \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Prob0 precomputation algorithm (using a fixed-point computation),\n\t * i.e. determine the states of a DTMC which, with probability 0,\n\t * reach a state in {@code target}, while remaining in those in {@code remain}.\n\t * @param dtmc The DTMC\n\t * @param remain Remain in these states (optional: {@code null} means \"all\")\n\t * @param target Target states\n\t */\n\tpublic BitSet prob0(Model<?> dtmc, BitSet remain, BitSet target)\n\t{\n\t\tint n, iters;\n\t\tBitSet u, soln, unknown;\n\t\tboolean u_done;\n\t\tlong timer;\n\n\t\t// Start precomputation\n\t\ttimer = System.currentTimeMillis();\n\t\tif (!silentPrecomputations)\n\t\t\tmainLog.println(\"Starting Prob0...\");\n\n\t\t// Special case: no target states\n\t\tif (target.cardinality() == 0) {\n\t\t\tsoln = new BitSet(dtmc.getNumStates());\n\t\t\tsoln.set(0, dtmc.getNumStates());\n\t\t\treturn soln;\n\t\t}\n\n\t\t// Initialise vectors\n\t\tn = dtmc.getNumStates();\n\t\tu = new BitSet(n);\n\t\tsoln = new BitSet(n);\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\n\t\t// Fixed point loop\n\t\titers = 0;\n\t\tu_done = false;\n\t\t// Least fixed point - should start from 0 but we optimise by\n\t\t// starting from 'target', thus bypassing first iteration\n\t\tu.or(target);\n\t\tsoln.or(target);\n\t\twhile (!u_done) {\n\t\t\titers++;\n\t\t\t// Single step of Prob0\n\t\t\tdtmc.prob0step(unknown, u, soln);\n\t\t\t// Check termination\n\t\t\tu_done = soln.equals(u);\n\t\t\t// u = soln\n\t\t\tu.clear();\n\t\t\tu.or(soln);\n\t\t}\n\n\t\t// Negate\n\t\tu.flip(0, n);\n\n\t\t// Finished precomputation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (!silentPrecomputations) {\n\t\t\tmainLog.print(\"Prob0\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\treturn u;\n\t}\n\n\t/**\n\t * Prob1 precomputation algorithm (using predecessor relation),\n\t * i.e. determine the states of a DTMC which, with probability 1,\n\t * reach a state in {@code target}, while remaining in those in {@code remain}.\n\t * @param dtmc The DTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param pre The predecessor relation of the DTMC\n\t */\n\tpublic BitSet prob1(Model<?> dtmc, BitSet remain, BitSet target, PredecessorRelation pre) {\n\t\t// Implements the constrained reachability algorithm from\n\t\t// Baier, Katoen: Principles of Model Checking (Corollary 10.31 Qualitative Constrained Reachability)\n\t\tlong timer;\n\n\t\t// Start precomputation\n\t\ttimer = System.currentTimeMillis();\n\t\tif (!silentPrecomputations)\n\t\t\tmainLog.println(\"Starting Prob1...\");\n\n\t\t// Special case: no 'target' states\n\t\tif (target.isEmpty()) {\n\t\t\t// empty set\n\t\t\treturn new BitSet();\n\t\t}\n\n\t\t// mark all states in 'target' and all states not in 'remain' as absorbing\n\t\tBitSet absorbing = new BitSet();\n\t\tif (remain != null) {\n\t\t\t// complement remain\n\t\t\tabsorbing.set(0, dtmc.getNumStates(), true);\n\t\t\tabsorbing.andNot(remain);\n\t\t} else {\n\t\t\t// for remain == null, remain consists of all states\n\t\t\t// thus, absorbing = the empty set is already the complementation of remain\n\t\t}\n\t\t// union with 'target'\n\t\tabsorbing.or(target);\n\n\t\t// M' = DTMC where all 'absorbing' states are considered to be absorbing\n\n\t\t// the set of states that satisfy E [ F target ] in M'\n\t\t// Pre*(target)\n\t\tBitSet canReachTarget = pre.calculatePreStar(null, target, absorbing);\n\n\t\t// complement canReachTarget\n\t\t// S\\Pre*(target)\n\t\tBitSet canNotReachTarget = new BitSet();\n\t\tcanNotReachTarget.set(0, dtmc.getNumStates(), true);\n\t\tcanNotReachTarget.andNot(canReachTarget);\n\n\t\t// the set of states that can reach a canNotReachTarget state in M'\n\t\t// Pre*(S\\Pre*(target))\n\t\tBitSet probTargetNot1 = pre.calculatePreStar(null, canNotReachTarget, absorbing);\n\n\t\t// complement probTargetNot1\n\t\t// S\\Pre*(S\\Pre*(target))\n\t\tBitSet result = new BitSet();\n\t\tresult.set(0, dtmc.getNumStates(), true);\n\t\tresult.andNot(probTargetNot1);\n\n\t\t// Finished precomputation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (!silentPrecomputations) {\n\t\t\tmainLog.print(\"Prob1\");\n\t\t\tmainLog.println(\" took \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Prob1 precomputation algorithm (using a fixed-point computation)\n\t * i.e. determine the states of a DTMC which, with probability 1,\n\t * reach a state in {@code target}, while remaining in those in {@code remain}.\n\t * @param dtmc The DTMC\n\t * @param remain Remain in these states (optional: {@code null} means \"all\")\n\t * @param target Target states\n\t */\n\tpublic BitSet prob1(Model<?> dtmc, BitSet remain, BitSet target)\n\t{\n\t\tint n, iters;\n\t\tBitSet u, v, soln, unknown;\n\t\tboolean u_done, v_done;\n\t\tlong timer;\n\n\t\t// Start precomputation\n\t\ttimer = System.currentTimeMillis();\n\t\tif (!silentPrecomputations)\n\t\t\tmainLog.println(\"Starting Prob1...\");\n\n\t\t// Special case: no target states\n\t\tif (target.cardinality() == 0) {\n\t\t\treturn new BitSet(dtmc.getNumStates());\n\t\t}\n\n\t\t// Initialise vectors\n\t\tn = dtmc.getNumStates();\n\t\tu = new BitSet(n);\n\t\tv = new BitSet(n);\n\t\tsoln = new BitSet(n);\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\n\t\t// Nested fixed point loop\n\t\titers = 0;\n\t\tu_done = false;\n\t\t// Greatest fixed point\n\t\tu.set(0, n);\n\t\twhile (!u_done) {\n\t\t\tv_done = false;\n\t\t\t// Least fixed point - should start from 0 but we optimise by\n\t\t\t// starting from 'target', thus bypassing first iteration\n\t\t\tv.clear();\n\t\t\tv.or(target);\n\t\t\tsoln.clear();\n\t\t\tsoln.or(target);\n\t\t\twhile (!v_done) {\n\t\t\t\titers++;\n\t\t\t\t// Single step of Prob1\n\t\t\t\tdtmc.prob1step(unknown, u, v, soln);\n\t\t\t\t// Check termination (inner)\n\t\t\t\tv_done = soln.equals(v);\n\t\t\t\t// v = soln\n\t\t\t\tv.clear();\n\t\t\t\tv.or(soln);\n\t\t\t}\n\t\t\t// Check termination (outer)\n\t\t\tu_done = v.equals(u);\n\t\t\t// u = v\n\t\t\tu.clear();\n\t\t\tu.or(v);\n\t\t}\n\n\t\t// Finished precomputation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (!silentPrecomputations) {\n\t\t\tmainLog.print(\"Prob1\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\treturn u;\n\t}\n\n\t/**\n\t * Compute reachability probabilities using value iteration.\n\t * @param dtmc The DTMC\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null), 'init' must also be given and is used for the exact values.\n\t * @param topological do topological value iteration?\n\t */\n\tprotected ModelCheckerResult doValueIterationReachProbs(DTMC<Double> dtmc, BitSet no, BitSet yes, double init[], BitSet known, IterationMethod iterationMethod, boolean topological) throws PrismException\n\t{\n\t\tBitSet unknown;\n\t\tint i, n;\n\t\tdouble initVal;\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString description = (topological ? \"topological, \" : \"\" ) + \"with \" + iterationMethod.getDescriptionShort();\n\t\tmainLog.println(\"Starting value iteration (\" + description + \")...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit DTMC ReachProbs value iteration (\" + description + \")\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Initialise solution vectors. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 1.0/0.0 if in yes/no; (3) passed in initial value; (4) initVal\n\t\t// where initVal is 0.0 or 1.0, depending on whether we converge from below/above. \n\t\tinitVal = (valIterDir == ValIterDir.BELOW) ? 0.0 : 1.0;\n\t\tif (init != null) {\n\t\t\tif (known != null) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tinit[i] = known.get(i) ? init[i] : yes.get(i) ? 1.0 : no.get(i) ? 0.0 : init[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tinit[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : init[i];\n\t\t\t}\n\t\t} else {\n\t\t\tinit = new double[n];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinit[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : initVal;\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(yes);\n\t\tunknown.andNot(no);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tIterationMethod.IterationValIter iterationReachProbs = iterationMethod.forMvMult(dtmc);\n\t\titerationReachProbs.init(init);\n\n\t\tif (iterationsExport != null)\n\t\t\titerationsExport.exportVector(init, 0);\n\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\tif (topological) {\n\t\t\t// Compute SCCInfo, including trivial SCCs in the subgraph obtained when only considering\n\t\t\t// states in unknown\n\t\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, dtmc, true, unknown::get);\n\n\t\t\tIterationMethod.SingletonSCCSolver singletonSCCSolver = (int s, double[] soln) -> {\n\t\t\t\tsoln[s] = dtmc.mvMultJacSingle(s, soln);\n\t\t\t};\n\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doTopologicalValueIteration(this, description, sccs, iterationReachProbs, singletonSCCSolver, timer, iterationsExport);\n\t\t} else {\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doValueIteration(this, description, iterationReachProbs, unknownStates, timer, iterationsExport);\n\t\t}\n\t}\n\n\n\t/**\n\t * Compute reachability probabilities using value iteration.\n\t * @param dtmc The DTMC\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null), 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult computeReachProbsValIter(DTMC<Double> dtmc, BitSet no, BitSet yes, double init[], BitSet known) throws PrismException\n\t{\n\t\tIterationMethodPower iterationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\treturn doValueIterationReachProbs(dtmc, no, yes, init, known, iterationMethod, false);\n\t}\n\n\t/**\n\t * Compute reachability probabilities using Gauss-Seidel (forward).\n\t * @param dtmc The DTMC\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null), 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult computeReachProbsGaussSeidel(DTMC<Double> dtmc, BitSet no, BitSet yes, double init[], BitSet known) throws PrismException\n\t{\n\t\treturn computeReachProbsGaussSeidel(dtmc, no, yes, init, known, false);\n\t}\n\n\t/**\n\t * Compute reachability probabilities using Gauss-Seidel.\n\t * @param dtmc The DTMC\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param init Optionally, an initial solution vector (will be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t * @param backwards do backward Gauss-Seidel?\n\t */\n\tprotected ModelCheckerResult computeReachProbsGaussSeidel(DTMC<Double> dtmc, BitSet no, BitSet yes, double init[], BitSet known, boolean backwards) throws PrismException\n\t{\n\t\tIterationMethodGS iterationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, backwards);\n\t\treturn doValueIterationReachProbs(dtmc, no, yes, init, known, iterationMethod, false);\n\t}\n\n\t/**\n\t * Compute reachability probabilities using power method (interval variant).\n\t * @param dtmc The DTMC\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param init Optionally, an initial solution vector (will be overwritten), will be ignored if known == null\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t * @param topological do topological interval iteration?\n\t */\n\tprotected ModelCheckerResult doIntervalIterationReachProbs(DTMC<Double> dtmc, BitSet no, BitSet yes, double init[], BitSet known, IterationMethod iterationMethod, boolean topological) throws PrismException\n\t{\n\t\tBitSet unknown;\n\t\tint i, n;\n\t\tdouble initBelow[], initAbove[];\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString description = (topological ? \"topological, \" : \"\" ) + \"with \" + iterationMethod.getDescriptionShort();\n\t\tmainLog.println(\"Starting interval iteration (\" + description + \")...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit DTMC ReachProbs interval iteration  (\" + description + \")\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tinitBelow = (init == null) ? new double[n] : init;\n\t\tinitAbove = new double[n];\n\n\t\t// Initialise solution vectors. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 1.0/0.0 if in yes/no; (3) initVal\n\t\t// where initVal is 0.0 or 1.0, depending on whether we converge from below/above.\n\t\tif (known != null && init != null) {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tinitBelow[i] = known.get(i) ? init[i] : yes.get(i) ? 1.0 : no.get(i) ? 0.0 : 0.0;\n\t\t\t\tinitAbove[i] = known.get(i) ? init[i] : yes.get(i) ? 1.0 : no.get(i) ? 0.0 : 1.0;\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tinitBelow[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 :  0.0;\n\t\t\t\tinitAbove[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 :  1.0;\n\t\t\t}\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(yes);\n\t\tunknown.andNot(no);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tif (iterationsExport != null) {\n\t\t\titerationsExport.exportVector(initBelow, 0);\n\t\t\titerationsExport.exportVector(initAbove, 1);\n\t\t}\n\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\tfinal boolean enforceMonotonicFromBelow = iiOptions.isEnforceMonotonicityFromBelow();\n\t\tfinal boolean enforceMonotonicFromAbove = iiOptions.isEnforceMonotonicityFromAbove();\n\t\tfinal boolean checkMonotonic = iiOptions.isCheckMonotonicity();\n\n\t\tif (!enforceMonotonicFromAbove) {\n\t\t\tgetLog().println(\"Note: Interval iteration is configured to not enforce monotonicity from above.\");\n\t\t}\n\t\tif (!enforceMonotonicFromBelow) {\n\t\t\tgetLog().println(\"Note: Interval iteration is configured to not enforce monotonicity from below.\");\n\t\t}\n\n\t\tIterationMethod.IterationIntervalIter below = iterationMethod.forMvMultInterval(dtmc, true, enforceMonotonicFromBelow, checkMonotonic);\n\t\tIterationMethod.IterationIntervalIter above = iterationMethod.forMvMultInterval(dtmc, false, enforceMonotonicFromAbove, checkMonotonic);\n\n\t\tbelow.init(initBelow);\n\t\tabove.init(initAbove);\n\n\t\tif (topological) {\n\t\t\t// Compute SCCInfo, including trivial SCCs in the subgraph obtained when only considering\n\t\t\t// states in unknown\n\t\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, dtmc, true, unknown::get);\n\n\t\t\tIterationMethod.SingletonSCCSolver singletonSCCSolver = (int s, double[] soln) -> {\n\t\t\t\tsoln[s] = dtmc.mvMultJacSingle(s, soln);\n\t\t\t};\n\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doTopologicalIntervalIteration(this, description, sccs, below, above, singletonSCCSolver, timer, iterationsExport);\n\t\t} else {\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doIntervalIteration(this, description, below, above, unknownStates, timer, iterationsExport);\n\t\t}\n\n\t}\n\n\t/**\n\t * Compute bounded reachability probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target} within k steps.\n\t * @param dtmc The DTMC\n\t * @param target Target states\n\t * @param k Bound\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(DTMC<Double> dtmc, BitSet target, int k) throws PrismException\n\t{\n\t\treturn computeBoundedReachProbs(dtmc, null, target, k, null, null);\n\t}\n\n\t/**\n\t * Compute bounded until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * within k steps, and while remaining in states in {@code remain}.\n\t * @param dtmc The DTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param k Bound\n\t */\n\tpublic ModelCheckerResult computeBoundedUntilProbs(DTMC<Double> dtmc, BitSet remain, BitSet target, int k) throws PrismException\n\t{\n\t\treturn computeBoundedReachProbs(dtmc, remain, target, k, null, null);\n\t}\n\n\t/**\n\t * Compute bounded reachability/until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * within k steps, and while remaining in states in {@code remain}.\n\t * @param dtmc The DTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param k Bound\n\t * @param init Initial solution vector - pass null for default\n\t * @param results Optional array of size b+1 to store (init state) results for each step (null if unused)\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(DTMC<Double> dtmc, BitSet remain, BitSet target, int k, double init[], double results[]) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet unknown;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\n\t\t// Start bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting bounded probabilistic reachability...\");\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = (init == null) ? new double[n] : init;\n\n\t\t// Initialise solution vectors. Use passed in initial vector, if present\n\t\tif (init != null) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : init[i];\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : 0.0;\n\t\t}\n\t\t// Store intermediate results if required\n\t\t// (compute min/max value over initial states for first step)\n\t\tif (results != null) {\n\t\t\t// TODO: whether this is min or max should be specified somehow\n\t\t\tresults[0] = Utils.minMaxOverArraySubset(soln2, dtmc.getInitialStates(), true);\n\t\t}\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\twhile (iters < k) {\n\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply\n\t\t\tdtmc.mvMult(soln, soln2, unknown, false);\n\t\t\t// Store intermediate results if required\n\t\t\t// (compute min/max value over initial states for this step)\n\t\t\tif (results != null) {\n\t\t\t\t// TODO: whether this is min or max should be specified somehow\n\t\t\t\tresults[iters] = Utils.minMaxOverArraySubset(soln2, dtmc.getInitialStates(), true);\n\t\t\t}\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Bounded probabilistic reachability\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.lastSoln = soln2;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward, using the variant specified in the settings.\n\t * @param dtmc the model\n\t * @param mcRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @param inf the infinity states\n\t * @return upper bound on R=?[ F target ] for all states\n\t */\n\tdouble computeReachRewardsUpperBound(DTMC<Double> dtmc, MCRewards<Double> mcRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\tif (unknown.isEmpty()) {\n\t\t\tmainLog.println(\"Skipping upper bound computation, no unknown states...\");\n\t\t\treturn 0;\n\t\t}\n\n\t\t// inf and target states become trap states (with self-loops)\n\t\tBitSet trapStates = (BitSet) target.clone();\n\t\ttrapStates.or(inf);\n\t\tDTMCAlteredDistributions<Double> cleanedDTMC = DTMCAlteredDistributions.addSelfLoops(dtmc, trapStates);\n\n\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\tdouble upperBound = 0.0;\n\t\tString method = null;\n\t\tswitch (iiOptions.getBoundMethod()) {\n\t\tcase VARIANT_1_COARSE:\n\t\t\tupperBound = computeReachRewardsUpperBoundVariant1Coarse(cleanedDTMC, mcRewards, target, unknown, inf);\n\t\t\tmethod = \"variant 1, coarse\";\n\t\t\tbreak;\n\t\tcase VARIANT_1_FINE:\n\t\t\tupperBound = computeReachRewardsUpperBoundVariant1Fine(cleanedDTMC, mcRewards, target, unknown, inf);\n\t\t\tmethod = \"variant 1, fine\";\n\t\t\tbreak;\n\t\tcase VARIANT_2:\n\t\t\tupperBound = computeReachRewardsUpperBoundVariant2(cleanedDTMC, mcRewards, target, unknown, inf);\n\t\t\tmethod = \"variant 2\";\n\t\t\tbreak;\n\t\tcase DEFAULT:\n\t\tcase DSMPI:\n\t\t{\n\t\t\tMDP<Double> mdp = new MDPFromDTMC<>(cleanedDTMC);\n\t\t\tMDPRewards<Double> mdpRewards = new MDPRewards<Double>() {\n\n\t\t\t\t@Override\n\t\t\t\tpublic Double getStateReward(int s)\n\t\t\t\t{\n\t\t\t\t\treturn mcRewards.getStateReward(s);\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic Double getTransitionReward(int s, int i)\n\t\t\t\t{\n\t\t\t\t\treturn 0.0;\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic MDPRewards<Double> liftFromModel(Product<?> product)\n\t\t\t\t{\n\t\t\t\t\tthrow new RuntimeException(\"Unsupported\");\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic boolean hasTransitionRewards()\n\t\t\t\t{\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t};\n\t\t\tupperBound = DijkstraSweepMPI.computeUpperBound(this, mdp, mdpRewards, target, unknown);\n\t\t\tmethod = \"Dijkstra Sweep MPI\";\n\t\t\tbreak;\n\t\t}\n\t\t}\n\n\t\tif (method == null) {\n\t\t\tthrow new PrismException(\"Unknown upper bound heuristic\");\n\t\t}\n\n\t\tmainLog.println(\"Upper bound for expectation (\" + method + \"): \" + upperBound);\n\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 1, coarse),\n\t * i.e., does not compute separate q_t / p_t per SCC.\n\t * Uses Rs = S, i.e., does not take reachability into account.\n\t * @param dtmc the model\n\t * @param mcRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @param inf the infinity states\n\t * @return upper bound on R=?[ F target ] for all states\n\t */\n\tdouble computeReachRewardsUpperBoundVariant1Coarse(DTMC<Double> dtmc, MCRewards<Double> mcRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\tdouble[] boundsOnExpectedVisits = new double[dtmc.getNumStates()];\n\t\tint[] Ct = new int[dtmc.getNumStates()];\n\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"computing an upper bound for expected reward\");\n\n\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, dtmc, true, null);\n\t\tBitSet trivial = new BitSet();\n\n\t\tdouble q = 0;\n\t\tfor (int scc = 0, numSCCs = sccs.getNumSCCs(); scc < numSCCs; scc++) {\n\t\t\tIntSet statesForSCC = sccs.getStatesForSCC(scc);\n\n\t\t\tint cardinality = Math.toIntExact(statesForSCC.cardinality());\n\n\t\t\tPrimitiveIterator.OfInt itSCC = statesForSCC.iterator();\n\t\t\twhile (itSCC.hasNext()) {\n\t\t\t\tint s = itSCC.nextInt();\n\t\t\t\tCt[s] = cardinality;\n\n\t\t\t\tif (target.get(s) || inf.get(s)) {\n\t\t\t\t\t// trap states\n\t\t\t\t\tassert(cardinality == 1);\n\t\t\t\t\tbreak;  // continue with next SCC\n\t\t\t\t}\n\n\t\t\t\tdouble probRemain = 0;\n\t\t\t\tboolean allRemain = true;  // all successors remain in the SCC?\n\t\t\t\tboolean hasSelfloop = false;\n\t\t\t\tfor (Iterator<Entry<Integer, Double>> it = dtmc.getTransitionsIterator(s); it.hasNext(); ) {\n\t\t\t\t\tEntry<Integer, Double> t = it.next();\n\t\t\t\t\tif (statesForSCC.get(t.getKey())) {\n\t\t\t\t\t\tprobRemain += t.getValue();\n\t\t\t\t\t\thasSelfloop = true;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tallRemain = false;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (!allRemain) { // action in the set X\n\t\t\t\t\tq = Math.max(q, probRemain);\n\t\t\t\t}\n\n\t\t\t\tif (cardinality == 1 && !hasSelfloop) {\n\t\t\t\t\ttrivial.set(s);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tdouble p = 1;\n\t\tfor (int s = 0; s < dtmc.getNumStates(); s++) {\n\t\t\tfor (Iterator<Entry<Integer, Double>> it = dtmc.getTransitionsIterator(s); it.hasNext(); ) {\n\t\t\t\tEntry<Integer, Double> t = it.next();\n\t\t\t\tp = Math.min(p, t.getValue());\n\t\t\t}\n\t\t}\n\n\t\tdouble upperBound = 0;\n\t\tfor (int s = 0; s < dtmc.getNumStates(); s++) {\n\t\t\tif (target.get(s) || inf.get(s)) {\n\t\t\t\t// inf or target states: not relevant, set visits to 0, ignore in summation\n\t\t\t\tboundsOnExpectedVisits[s] = 0.0;\n\t\t\t} else if (unknown.get(s)) {\n\t\t\t\tif (trivial.get(s)) {\n\t\t\t\t\t// s is a trivial SCC: seen at most once\n\t\t\t\t\tboundsOnExpectedVisits[s] = 1.0;\n\t\t\t\t} else {\n\t\t\t\t\tboundsOnExpectedVisits[s] = 1 / (Math.pow(p, Ct[s]-1) * (1.0-q));\n\t\t\t\t}\n\n\t\t\t\tupperBound += boundsOnExpectedVisits[s] * mcRewards.getStateReward(s);\n\t\t\t}\n\t\t}\n\n\t\ttimer.stop();\n\n\t\tif (OptionsIntervalIteration.from(this).isBoundComputationVerbose()) {\n\t\t\tmainLog.println(\"Upper bound for max expectation computation (variant 1, coarse):\");\n\t\t\tmainLog.println(\"p = \" + p);\n\t\t\tmainLog.println(\"q = \" + q);\n\t\t\tmainLog.println(\"|Ct| = \" + Arrays.toString(Ct));\n\t\t\tmainLog.println(\"ζ* = \" + Arrays.toString(boundsOnExpectedVisits));\n\t\t}\n\n\t\tif (!Double.isFinite(upperBound)) {\n\t\t\tthrow new PrismException(\"Problem computing an upper bound for the expectation, did not get finite result\");\n\t\t}\n\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 1, fine).\n\t * i.e., does compute separate q_t / p_t per SCC.\n\t * Uses Rs = S, i.e., does not take reachability into account.\n\t * @param dtmc the model\n\t * @param mcRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @param inf the infinity states\n\t * @return upper bound on R=?[ F target ] for all states\n\t */\n\tdouble computeReachRewardsUpperBoundVariant1Fine(DTMC<Double> dtmc, MCRewards<Double> mcRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\tdouble[] boundsOnExpectedVisits = new double[dtmc.getNumStates()];\n\t\tdouble[] qt = new double[dtmc.getNumStates()];\n\t\tdouble[] pt = new double[dtmc.getNumStates()];\n\t\tint[] Ct = new int[dtmc.getNumStates()];\n\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"computing an upper bound for expected reward\");\n\n\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, dtmc, true, null);\n\t\tBitSet trivial = new BitSet();\n\n\t\tfor (int scc = 0, numSCCs = sccs.getNumSCCs(); scc < numSCCs; scc++) {\n\t\t\tIntSet statesForSCC = sccs.getStatesForSCC(scc);\n\n\t\t\tdouble q = 0;\n\t\t\tdouble p = 1;\n\t\t\tint cardinality = Math.toIntExact(statesForSCC.cardinality());\n\n\t\t\tPrimitiveIterator.OfInt itSCC = statesForSCC.iterator();\n\t\t\twhile (itSCC.hasNext()) {\n\t\t\t\tint s = itSCC.nextInt();\n\t\t\t\tCt[s] = cardinality;\n\n\t\t\t\tdouble probRemain = 0;\n\t\t\t\tboolean allRemain = true;  // all successors remain in the SCC?\n\t\t\t\tboolean hasSelfloop = false;\n\t\t\t\tfor (Iterator<Entry<Integer, Double>> it = dtmc.getTransitionsIterator(s); it.hasNext(); ) {\n\t\t\t\t\tEntry<Integer, Double> t = it.next();\n\t\t\t\t\tif (statesForSCC.get(t.getKey())) {\n\t\t\t\t\t\tprobRemain += t.getValue();\n\t\t\t\t\t\tp = Math.min(p, t.getValue());\n\t\t\t\t\t\thasSelfloop = true;\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// outgoing edge\n\t\t\t\t\t\tallRemain = false;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (!allRemain) { // action in the set Xt\n\t\t\t\t\tq = Math.max(q, probRemain);\n\t\t\t\t}\n\n\t\t\t\tif (cardinality == 1 && !hasSelfloop) {\n\t\t\t\t\ttrivial.set(s);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tfor (int s : statesForSCC) {\n\t\t\t\tqt[s] = q;\n\t\t\t\tpt[s] = p;\n\t\t\t}\n\t\t}\n\n\t\tdouble upperBound = 0;\n\t\tfor (int s = 0; s < dtmc.getNumStates(); s++) {\n\t\t\tif (target.get(s) || inf.get(s)) {\n\t\t\t\t// inf or target states: not relevant, set visits to 0, ignore in summation\n\t\t\t\tboundsOnExpectedVisits[s] = 0.0;\n\t\t\t} else if (unknown.get(s)) {\n\t\t\t\tif (trivial.get(s)) {\n\t\t\t\t\t// s is a trivial SCC: seen at most once\n\t\t\t\t\tboundsOnExpectedVisits[s] = 1.0;\n\t\t\t\t} else {\n\t\t\t\t\tif (pt[s] == 1.0) {\n\t\t\t\t\t\t//throw new PrismException(\"Upper bound computation had p_t = 1 for state \" + s);\n\t\t\t\t\t}\n\t\t\t\t\tboundsOnExpectedVisits[s] = 1 / (Math.pow(pt[s], Ct[s]-1) * (1.0-qt[s]));\n\t\t\t\t}\n\n\t\t\t\tupperBound += boundsOnExpectedVisits[s] * mcRewards.getStateReward(s);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"Bogus arguments: inf/target/unknown should partition state space\");\n\t\t\t}\n\t\t}\n\n\t\ttimer.stop();\n\n\t\tif (OptionsIntervalIteration.from(this).isBoundComputationVerbose()) {\n\t\t\tmainLog.println(\"Upper bound for max expectation computation (variant 1, fine):\");\n\t\t\tmainLog.println(\"pt = \" + Arrays.toString(pt));\n\t\t\tmainLog.println(\"qt = \" + Arrays.toString(qt));\n\t\t\tmainLog.println(\"|Ct| = \" + Arrays.toString(Ct));\n\t\t\tmainLog.println(\"ζ* = \" + Arrays.toString(boundsOnExpectedVisits));\n\t\t}\n\n\t\tif (!Double.isFinite(upperBound)) {\n\t\t\tthrow new PrismException(\"Problem computing an upper bound for the expectation, did not get finite result\");\n\t\t}\n\n\t\treturn upperBound;\n\t}\n\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 2).\n\t * Uses Rs = S, i.e., does not take reachability into account.\n\t * @param dtmc the model\n\t * @param mcRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @param inf the infinity states\n\t * @return upper bound on R=?[ F target ] for all states\n\t */\n\tdouble computeReachRewardsUpperBoundVariant2(DTMC<Double> dtmc, MCRewards<Double> mcRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\tdouble[] dt = new double[dtmc.getNumStates()];\n\t\tdouble[] boundsOnExpectedVisits = new double[dtmc.getNumStates()];\n\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"computing an upper bound for expected reward\");\n\n\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, dtmc, true, unknown::get);\n\n\t\tBitSet T = (BitSet) target.clone();\n\n\t\t@SuppressWarnings(\"unused\")\n\t\tint i = 0;\n\t\twhile (true) {\n\t\t\tBitSet Si = new BitSet();\n\t\t\ti++;\n\n\t\t\t// TODO: might be inefficient, worst-case quadratic runtime...\n\t\t\tfor (PrimitiveIterator.OfInt it = IterableBitSet.getClearBits(T, dtmc.getNumStates() -1 ).iterator(); it.hasNext(); ) {\n\t\t\t\tint s = it.nextInt();\n//\t\t\t\tmainLog.println(\"Check \" + s + \" against \" + T);\n\t\t\t\tif (dtmc.someSuccessorsInSet(s, T)) {\n\t\t\t\t\tSi.set(s);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (Si.isEmpty()) {\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t// mainLog.println(\"S\" + i + \" = \" + Si);\n\t\t\t// mainLog.println(\"T = \" + T);\n\n\t\t\tfor (PrimitiveIterator.OfInt it = IterableBitSet.getSetBits(Si).iterator(); it.hasNext(); ) {\n\t\t\t\tfinal int t = it.nextInt();\n\t\t\t\tfinal int sccIndexForT = sccs.getSCCIndex(t);\n\t\t\t\tdouble d = dtmc.sumOverDoubleTransitions(t, (int __, int u, double prob) -> {\n\t\t\t\t\t// mainLog.println(\"t = \" + t + \", u = \" + u + \", prob = \" + prob);\n\t\t\t\t\tif (!T.get(u))\n\t\t\t\t\t\treturn 0.0;\n\n\t\t\t\t\tboolean inSameSCC = (sccs.getSCCIndex(u) == sccIndexForT);\n\t\t\t\t\tdouble d_u_t = inSameSCC ? dt[u] : 1.0;\n\t\t\t\t\t// mainLog.println(\"d_u_t = \" + d_u_t);\n\t\t\t\t\treturn d_u_t * prob;\n\t\t\t\t});\n\t\t\t\tdt[t] = d;\n\t\t\t\t// mainLog.println(\"d[\"+t+\"] = \" + d);\n\t\t\t}\n\n\t\t\tT.or(Si);\n\t\t}\n\n\t\tdouble upperBound = 0;\n\t\tfor (PrimitiveIterator.OfInt it = IterableBitSet.getSetBits(unknown).iterator(); it.hasNext();) {\n\t\t\tint s = it.nextInt();\n\t\t\tboundsOnExpectedVisits[s] = 1 / dt[s];\n\t\t\tupperBound += boundsOnExpectedVisits[s] * mcRewards.getStateReward(s);\n\t\t}\n\n\t\ttimer.stop();\n\n\t\tif (OptionsIntervalIteration.from(this).isBoundComputationVerbose()) {\n\t\t\tmainLog.println(\"Upper bound for max expectation computation (variant 2):\");\n\t\t\tmainLog.println(\"d_t = \" + Arrays.toString(dt));\n\t\t\tmainLog.println(\"ζ* = \" + Arrays.toString(boundsOnExpectedVisits));\n\t\t}\n\n\t\tif (!Double.isFinite(upperBound)) {\n\t\t\tthrow new PrismException(\"Problem computing an upper bound for the expectation, did not get finite result\");\n\t\t}\n\n\t\treturn upperBound;\n\t}\n\n\n\t/**\n\t * Compute expected reachability rewards.\n\t * @param dtmc The DTMC\n\t * @param mcRewards The rewards\n\t * @param target Target states\n\t */\n\tpublic ModelCheckerResult computeReachRewards(DTMC<Double> dtmc, MCRewards<Double> mcRewards, BitSet target) throws PrismException\n\t{\n\t\treturn computeReachRewards(dtmc, mcRewards, target, null, null);\n\t}\n\n\t/**\n\t * Compute expected reachability rewards.\n\t * @param dtmc The DTMC\n\t * @param mcRewards The rewards\n\t * @param target Target states\n\t * @param init Optionally, an initial solution vector (may be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tpublic ModelCheckerResult computeReachRewards(DTMC<Double> dtmc, MCRewards<Double> mcRewards, BitSet target, double init[], BitSet known) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet inf;\n\t\tint n, numTarget, numInf;\n\t\tlong timer, timerProb1;\n\t\t// Local copy of setting\n\t\tLinEqMethod linEqMethod = this.linEqMethod;\n\n\t\t// Switch to a supported method, if necessary\n\t\tswitch (linEqMethod)\n\t\t{\n\t\tcase POWER:\n\t\tcase GAUSS_SEIDEL:\n\t\tcase BACKWARDS_GAUSS_SEIDEL:\n\t\tcase JACOBI:\n\t\t\tbreak; // supported\n\t\tdefault:\n\t\t\tlinEqMethod = LinEqMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to linear equation solution method \\\"\" + linEqMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\t// Start expected reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting expected reachability...\");\n\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tdtmc.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Optimise by enlarging target set (if more info is available)\n\t\tif (init != null && known != null && !known.isEmpty()) {\n\t\t\tBitSet targetNew = (BitSet) target.clone();\n\t\t\tfor (int i : new IterableBitSet(known)) {\n\t\t\t\tif (init[i] == 1.0) {\n\t\t\t\t\ttargetNew.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\ttarget = targetNew;\n\t\t}\n\n\t\t// Precomputation (not optional)\n\t\ttimerProb1 = System.currentTimeMillis();\n\t\tif (preRel) {\n\t\t\t// prob1 via predecessor relation\n\t\t\tPredecessorRelation pre = dtmc.getPredecessorRelation(this, true);\n\t\t\tinf = prob1(dtmc, null, target, pre);\n\t\t} else {\n\t\t\t// prob1 via fixed-point algorithm\n\t\t\tinf = prob1(dtmc, null, target);\n\t\t}\n\t\tinf.flip(0, n);\n\t\ttimerProb1 = System.currentTimeMillis() - timerProb1;\n\n\t\t// Print results of precomputation\n\t\tnumTarget = target.cardinality();\n\t\tnumInf = inf.cardinality();\n\t\tmainLog.println(\"target=\" + numTarget + \", inf=\" + numInf + \", rest=\" + (n - (numTarget + numInf)));\n\n\t\t// Compute rewards (if needed)\n\t\tif (numTarget + numInf < n) {\n\t\t\tboolean termCritAbsolute = termCrit == TermCrit.ABSOLUTE;\n\t\t\tIterationMethod iterationMethod;\n\t\t\tswitch (linEqMethod) {\n\t\t\tcase POWER:\n\t\t\t\titerationMethod = new IterationMethodPower(termCritAbsolute, termCritParam);\n\t\t\t\tbreak;\n\t\t\tcase JACOBI:\n\t\t\t\titerationMethod = new IterationMethodJacobi(termCritAbsolute, termCritParam);\n\t\t\t\tbreak;\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\tcase BACKWARDS_GAUSS_SEIDEL: {\n\t\t\t\tboolean backwards = linEqMethod == LinEqMethod.BACKWARDS_GAUSS_SEIDEL;\n\t\t\t\titerationMethod = new IterationMethodGS(termCritAbsolute, termCritParam, backwards);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown linear equation solution method \" + linEqMethod.fullName());\n\t\t\t}\n\t\t\tif (doIntervalIteration) {\n\t\t\t\tres = doIntervalIterationReachRewards(dtmc, mcRewards, target, inf, init, known, iterationMethod, getDoTopologicalValueIteration());\n\t\t\t} else {\n\t\t\t\tres = doValueIterationReachRewards(dtmc, mcRewards, target, inf, init, known, iterationMethod, getDoTopologicalValueIteration());\n\t\t\t}\n\t\t} else {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(inf, n, Double.POSITIVE_INFINITY);\n\t\t\tres.accuracy = AccuracyFactory.doublesFromQualitative();\n\t\t}\n\n\t\t// Finished expected reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Expected reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = timerProb1 / 1000.0;\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using value iteration.\n\t * @param dtmc The DTMC\n\t * @param mcRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult computeReachRewardsValIter(DTMC<Double> dtmc, MCRewards<Double> mcRewards, BitSet target, BitSet inf, double init[], BitSet known)\n\t\t\tthrows PrismException\n\t{\n\t\tModelCheckerResult res;\n\t\tBitSet unknown;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tboolean done;\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"Starting value iteration...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit DTMC ReachRewards value iteration\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = (init == null) ? new double[n] : init;\n\n\t\t// Initialise solution vectors. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 0.0/infinity if in target/inf; (3) passed in initial value; (4) 0.0\n\t\tif (init != null) {\n\t\t\tif (known != null) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsoln[i] = soln2[i] = known.get(i) ? init[i] : target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : init[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : init[i];\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : 0.0;\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tunknown.andNot(inf);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tif (iterationsExport != null)\n\t\t\titerationsExport.exportVector(soln, 0);\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\tdone = false;\n\t\twhile (!done && iters < maxIters) {\n\t\t\t//mainLog.println(soln);\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply\n\t\t\tdtmc.mvMultRew(soln, mcRewards, soln2, unknown, false);\n\n\t\t\tif (iterationsExport != null)\n\t\t\t\titerationsExport.exportVector(soln, 0);\n\n\t\t\t// Check termination\n\t\t\tdone = PrismUtils.doublesAreClose(soln, soln2, termCritParam, termCrit == TermCrit.ABSOLUTE);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished value iteration\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Value iteration\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\n\t\tif (iterationsExport != null)\n\t\t\titerationsExport.close();\n\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\";\n\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tdouble maxDiff = PrismUtils.measureSupNorm(soln, soln2, termCrit == TermCrit.ABSOLUTE);\n\t\tres.accuracy = AccuracyFactory.valueIteration(termCritParam, maxDiff, termCrit == TermCrit.ABSOLUTE);\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using value iteration.\n\t * @param dtmc The DTMC\n\t * @param mcRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t * @param topological do topological value iteration?\n\t */\n\tprotected ModelCheckerResult doValueIterationReachRewards(DTMC<Double> dtmc, final MCRewards<Double> mcRewards, BitSet target, BitSet inf, double init[], BitSet known, IterationMethod iterationMethod, boolean topological) throws PrismException\n\t{\n\t\tBitSet unknown;\n\t\tint i, n;\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString description = (topological ? \"topological, \" : \"\" ) + \"with \" + iterationMethod.getDescriptionShort();\n\t\tmainLog.println(\"Starting value iteration (\" + description + \") ...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit DTMC ReachRewards value iteration (\" + description + \")\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Initialise solution vector. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 0.0/infinity if in target/inf; (3) passed in initial value; (4) 0.0\n\t\tif (init != null) {\n\t\t\tif (known != null) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tinit[i] = known.get(i) ? init[i] : target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : init[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tinit[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : init[i];\n\t\t\t}\n\t\t} else {\n\t\t\tinit = new double[n];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinit[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : 0.0;\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tunknown.andNot(inf);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tif (iterationsExport != null)\n\t\t\titerationsExport.exportVector(init, 0);\n\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\t\tIterationMethod.IterationValIter forMvMultRew = iterationMethod.forMvMultRew(dtmc, mcRewards);\n\t\tforMvMultRew.init(init);\n\n\t\tif (topological) {\n\t\t\tSCCInfo sccs = new SCCInfo(n);\n\t\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, dtmc, sccs);\n\t\t\t// Compute SCCInfo, including trivial SCCs in the subgraph obtained when only considering\n\t\t\t// states in unknown\n\t\t\tsccComputer.computeSCCs(false, unknown::get);\n\n\t\t\tIterationMethod.SingletonSCCSolver singletonSCCSolver = (int s, double[] soln) -> {\n\t\t\t\tsoln[s] = dtmc.mvMultRewJacSingle(s, soln, mcRewards);\n\t\t\t};\n\n\t\t\treturn iterationMethod.doTopologicalValueIteration(this, description, sccs, forMvMultRew, singletonSCCSolver, timer, iterationsExport);\n\t\t} else {\n\t\t\treturn iterationMethod.doValueIteration(this, description, forMvMultRew, unknownStates, timer, iterationsExport);\n\t\t}\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using interval iteration.\n\t * @param dtmc The DTMC\n\t * @param mcRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t * @param topological do topological interval iteration?\n\t */\n\tprotected ModelCheckerResult doIntervalIterationReachRewards(DTMC<Double> dtmc, MCRewards<Double> mcRewards, BitSet target, BitSet inf, double init[], BitSet known, IterationMethod iterationMethod, boolean topological)\n\t\t\tthrows PrismException\n\t{\n\t\tBitSet unknown;\n\t\tint i, n;\n\t\tdouble init_below[], init_above[];\n\t\tlong timer;\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tunknown.andNot(inf);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\tdouble upperBound;\n\t\tif (iiOptions.hasManualUpperBound()) {\n\t\t\tupperBound = iiOptions.getManualUpperBound();\n\t\t\tgetLog().printWarning(\"Upper bound for interval iteration manually set to \" + upperBound);\n\t\t} else {\n\t\t\tupperBound = computeReachRewardsUpperBound(dtmc, mcRewards, target, unknown, inf);\n\t\t}\n\n\t\tdouble lowerBound;\n\t\tif (iiOptions.hasManualLowerBound()) {\n\t\t\tlowerBound = iiOptions.getManualLowerBound();\n\t\t\tgetLog().printWarning(\"Lower bound for interval iteration manually set to \" + lowerBound);\n\t\t} else {\n\t\t\tlowerBound = 0.0;\n\t\t}\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString description = (topological ? \"topological, \" : \"\" ) + \"with \" + iterationMethod.getDescriptionShort();\n\t\tmainLog.println(\"Starting interval iteration (\" + description + \") ...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit DTMC ReachRewards interval iteration (\" + description + \") ...\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Create solution vector(s)\n\t\tinit_below = (init == null) ? new double[n] : init;\n\t\tinit_above = new double[n];\n\n\t\t// Initialise solution vector from below. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 0.0/infinity if in target/inf; (3) lowerBound\n\t\tif (init != null && known != null) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinit_below[i] = known.get(i) ? init[i] : target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : lowerBound;\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinit_below[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : lowerBound;\n\t\t}\n\n\t\t// Initialise solution vector from above. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 0.0/infinity if in target/inf; (3) upperBound\n\t\tif (init != null && known != null) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinit_above[i] = known.get(i) ? init[i] : target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : upperBound;\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinit_above[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : upperBound;\n\t\t}\n\n\n\t\tif (iterationsExport != null) {\n\t\t\titerationsExport.exportVector(init_below, 0);\n\t\t\titerationsExport.exportVector(init_above, 1);\n\t\t}\n\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\tfinal boolean enforceMonotonicFromBelow = iiOptions.isEnforceMonotonicityFromBelow();\n\t\tfinal boolean enforceMonotonicFromAbove = iiOptions.isEnforceMonotonicityFromAbove();\n\t\tfinal boolean checkMonotonic = iiOptions.isCheckMonotonicity();\n\n\t\tif (!enforceMonotonicFromAbove) {\n\t\t\tgetLog().println(\"Note: Interval iteration is configured to not enforce monotonicity from above.\");\n\t\t}\n\t\tif (!enforceMonotonicFromBelow) {\n\t\t\tgetLog().println(\"Note: Interval iteration is configured to not enforce monotonicity from below.\");\n\t\t}\n\n\t\tIterationMethod.IterationIntervalIter below = iterationMethod.forMvMultRewInterval(dtmc, mcRewards, true, enforceMonotonicFromBelow, checkMonotonic);\n\t\tIterationMethod.IterationIntervalIter above = iterationMethod.forMvMultRewInterval(dtmc, mcRewards, false, enforceMonotonicFromAbove, checkMonotonic);\n\n\t\tbelow.init(init_below);\n\t\tabove.init(init_above);\n\n\t\tModelCheckerResult rv;\n\t\tif (topological) {\n\t\t\t// Compute SCCInfo, including trivial SCCs in the subgraph obtained when only considering\n\t\t\t// states in unknown\n\t\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, dtmc, true, unknown::get);\n\n\t\t\tIterationMethod.SingletonSCCSolver singletonSCCSolver = (int s, double[] soln) -> {\n\t\t\t\tsoln[s] = dtmc.mvMultRewJacSingle(s, soln, mcRewards);\n\t\t\t};\n\n\t\t\t// run the actual value iteration\n\t\t\trv = iterationMethod.doTopologicalIntervalIteration(this, description, sccs, below, above, singletonSCCSolver, timer, iterationsExport);\n\t\t} else {\n\t\t\t// run the actual value iteration\n\t\t\trv = iterationMethod.doIntervalIteration(this, description, below, above, unknownStates, timer, iterationsExport);\n\t\t}\n\n\t\tdouble max_v = PrismUtils.findMaxFinite(rv.soln, unknownStates.iterator());\n\t\tif (max_v != Double.NEGATIVE_INFINITY) {\n\t\t\tmainLog.println(\"Maximum finite value in solution vector at end of interval iteration: \" + max_v);\n\t\t}\n\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Compute steady-state probabilities for an S operator, i.e., S=?[ b ].\n\t * @param dtmc the DTMC\n\t * @param b the satisfaction set of states for the inner state formula of the operators\n\t */\n\tprotected StateValues computeSteadyStateFormula(DTMC<Double> dtmc, BitSet b) throws PrismException\n\t{\n\t\tdouble multProbs[] = Utils.bitsetToDoubleArray(b, dtmc.getNumStates());\n\t\tModelCheckerResult res = computeSteadyStateBackwardsProbs(dtmc, multProbs);\n\t\treturn StateValues.createFromDoubleArray(res.soln, dtmc);\n\t}\n\n\t/**\n\t * An interface for a post-processor, taking a solution vector over\n\t * the whole state space and applying some post-processing on the\n\t * solution for a given BSCC (with the state indices given by a BitSet).\n\t * <br>\n\t * This post-processor may only assume that the values in the solution vector\n\t * corresponding to the BSCC states are valid and may only write to those values,\n\t * the other values in the vector should not be changed.\n\t */\n\t@FunctionalInterface\n\tpublic interface BSCCPostProcessor {\n\t\tpublic void apply(double soln[], BitSet bscc);\n\t};\n\n\t/**\n\t * Compute (forwards) steady-state probabilities\n\t * i.e. compute the long-run probability of being in each state,\n\t * assuming the initial distribution {@code initDist}.\n\t * For space efficiency, the initial distribution vector will be modified and values over-written,\n\t * so if you wanted it, take a copy.\n\t * @param dtmc The DTMC\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic ModelCheckerResult computeSteadyStateProbs(DTMC<Double> dtmc, double initDist[]) throws PrismException\n\t{\n\t\treturn computeSteadyStateProbs(dtmc, initDist, null);\n\t}\n\n\t/**\n\t * Compute (forwards) steady-state probabilities\n\t * i.e. compute the long-run probability of being in each state,\n\t * assuming the initial distribution {@code initDist}. \n\t * For space efficiency, the initial distribution vector will be modified and values over-written,  \n\t * so if you wanted it, take a copy. \n\t * @param dtmc The DTMC\n\t * @param initDist Initial distribution (will be overwritten)\n\t * @param bsccPostProcessor Post-processor for the values of each BSCC (optional: null means no post-processing)\n\t */\n\tpublic ModelCheckerResult computeSteadyStateProbs(DTMC<Double> dtmc, double initDist[], BSCCPostProcessor bsccPostProcessor) throws PrismException\n\t{\n\t\tStopWatch watch = new StopWatch().start();\n\n\t\t// Store num states\n\t\tint numStates = dtmc.getNumStates();\n\t\t// Create results vector\n\t\tdouble[] solnProbs = new double[numStates];\n\n\t\t// Compute bottom strongly connected components (BSCCs)\n\t\tSCCConsumerStore sccStore = new SCCConsumerStore();\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, dtmc, sccStore);\n\t\tsccComputer.computeSCCs();\n\t\tList<BitSet> bsccs = sccStore.getBSCCs();\n\t\tBitSet notInBSCCs = sccStore.getNotInBSCCs();\n\t\tint numBSCCs = bsccs.size();\n\n\t\t// Compute support of initial distribution\n\t\tint numInit = 0;\n\t\tBitSet init = new BitSet();\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (initDist[i] > 0)\n\t\t\t\tinit.set(i);\n\t\t\t\tnumInit++;\n\t\t}\n\t\t// Determine whether initial states are all in the same BSCC \n\t\tint initInOneBSCC = -1;\n\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t// test subset via setminus\n\t\t\tBitSet notInB = (BitSet) init.clone();\n\t\t\tnotInB.andNot(bsccs.get(b));\n\t\t\tif (notInB.isEmpty()) {\n\t\t\t\t// all init states in b\n\t\t\t\t// >> finish\n\t\t\t\tinitInOneBSCC = b;\n\t\t\t\tbreak;\n\t\t\t} else if (notInB.cardinality() < numInit) {\n\t\t\t\t// some init states in b and some not\n\t\t\t\t// >> abort\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t// no init state in b\n\t\t\t// >> try next BSCC\n\t\t}\n\n\t\t// If all initial states are in the same BSCC, it's easy...\n\t\t// Just compute steady-state probabilities for the BSCC\n\t\tif (initInOneBSCC > -1) {\n\t\t\tmainLog.println(\"\\nInitial states are all in one BSCC (so no reachability probabilities computed)\");\n\t\t\tBitSet bscc = bsccs.get(initInOneBSCC);\n\t\t\tcomputeSteadyStateProbsForBSCC(dtmc, bscc, solnProbs, bsccPostProcessor);\n\t\t}\n\n\t\t// Otherwise, have to consider all the BSCCs\n\t\telse {\n\t\t\t// Compute probability of reaching each BSCC from initial distribution \n\t\t\tdouble[] probBSCCs = new double[numBSCCs];\n\t\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t\tmainLog.println(\"\\nComputing probability of reaching BSCC \" + (b + 1));\n\t\t\t\tBitSet bscc = bsccs.get(b);\n\t\t\t\t// Compute probabilities\n\t\t\t\tdouble[] reachProbs = computeUntilProbs(dtmc, notInBSCCs, bscc).soln;\n\t\t\t\t// Compute probability of reaching BSCC, which is dot product of\n\t\t\t\t// vectors for initial distribution and probabilities of reaching it\n\t\t\t\tprobBSCCs[b] = 0.0;\n\t\t\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t\t\tprobBSCCs[b] += initDist[i] * reachProbs[i];\n\t\t\t\t}\n\t\t\t\tmainLog.print(\"\\nProbability of reaching BSCC \" + (b + 1) + \": \" + probBSCCs[b] + \"\\n\");\n\t\t\t}\n\n\t\t\t// Compute steady-state probabilities for each BSCC \n\t\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t\tmainLog.println(\"\\nComputing steady-state probabilities for BSCC \" + (b + 1));\n\t\t\t\tBitSet bscc = bsccs.get(b);\n\t\t\t\t// Compute steady-state probabilities for the BSCC\n\t\t\t\tcomputeSteadyStateProbsForBSCC(dtmc, bscc, solnProbs, bsccPostProcessor);\n\t\t\t\t// Multiply by BSCC reach prob\n\t\t\t\tfor (int i = bscc.nextSetBit(0); i >= 0; i = bscc.nextSetBit(i + 1))\n\t\t\t\t\tsolnProbs[i] *= probBSCCs[b];\n\t\t\t}\n\t\t}\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\tres.soln = solnProbs;\n\t\tres.timeTaken = watch.elapsedSeconds();\n\t\treturn res;\n\t}\n\n\t/**\n\t * Perform (backwards) steady-state probabilities, as required for (e.g. CSL) model checking.\n\t * Compute, for each initial state s, the sum over all states s'\n\t * of the steady-state probability of being in s'\n\t * multiplied by the corresponding probability in the vector {@code multProbs}.\n\t * If {@code multProbs} is null, it is assumed to be all 1s.\n\t * <br>\n\t * Note: This method can also be used to compute the steady-state backwards rewards, i.e.,\n\t * when mult contains the state rewards for the BSCC states.\n\t * @param dtmc The DTMC\n\t * @param mult Multiplication vector, used to weight the steady-state probabilities for BSCC states (optional: null means all 1s)\n\t */\n\tpublic ModelCheckerResult computeSteadyStateBackwardsProbs(DTMC<Double> dtmc, double mult[]) throws PrismException\n\t{\n\t\treturn computeSteadyStateBackwardsProbs(dtmc, mult, null);\n\t}\n\n\t/**\n\t * Perform (backwards) steady-state probabilities, as required for (e.g. CSL) model checking.\n\t * Compute, for each initial state s, the sum over all states s'\n\t * of the steady-state probability of being in s'\n\t * multiplied by the corresponding probability in the vector {@code multProbs}.\n\t * If {@code multProbs} is null, it is assumed to be all 1s.\n\t * <br>\n\t * Note: This method can also be used to compute the steady-state backwards rewards, i.e.,\n\t * when mult contains the state rewards for the BSCC states.\n\t * @param dtmc The DTMC\n\t * @param mult Multiplication vector, used to weight the steady-state probabilities for BSCC states (optional: null means all 1s)\n\t * @param bsccPostProcessor Post-processor for the values of each BSCC (optional: null means no post-processing)\n\t */\n\tpublic ModelCheckerResult computeSteadyStateBackwardsProbs(DTMC<Double> dtmc, double mult[], BSCCPostProcessor bsccPostProcessor) throws PrismException\n\t{\n\t\tStopWatch watch = new StopWatch().start();\n\n\t\t// Store num states\n\t\tint numStates = dtmc.getNumStates();\n\n\t\t// Compute bottom strongly connected components (BSCCs)\n\t\tSCCConsumerStore sccStore = new SCCConsumerStore();\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, dtmc, sccStore);\n\t\tsccComputer.computeSCCs();\n\t\tList<BitSet> bsccs = sccStore.getBSCCs();\n\t\tBitSet notInBSCCs = sccStore.getNotInBSCCs();\n\t\tint numBSCCs = bsccs.size();\n\n\t\t// Compute steady-state values for each BSCC...\n\t\tdouble[] valueBSCCs = new double[numBSCCs];\n\t\tdouble[] ssProbs = new double[numStates];\n\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\tmainLog.println(\"\\nComputing steady state probabilities for BSCC \" + (b + 1));\n\t\t\tBitSet bscc = bsccs.get(b);\n\t\t\t// Compute steady-state probabilities for the BSCC\n\t\t\tcomputeSteadyStateProbsForBSCC(dtmc, bscc, ssProbs, bsccPostProcessor);\n\t\t\t// Compute weighted sum of probabilities with mult\n\t\t\tvalueBSCCs[b] = 0.0;\n\t\t\tif (mult == null) {\n\t\t\t\tfor (int i = bscc.nextSetBit(0); i >= 0; i = bscc.nextSetBit(i + 1)) {\n\t\t\t\t\tvalueBSCCs[b] += ssProbs[i];\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tfor (int i = bscc.nextSetBit(0); i >= 0; i = bscc.nextSetBit(i + 1)) {\n\t\t\t\t\tvalueBSCCs[b] += mult[i] * ssProbs[i];\n\t\t\t\t}\n\t\t\t}\n\t\t\tmainLog.print(\"\\nValue for BSCC \" + (b + 1) + \": \" + valueBSCCs[b] + \"\\n\");\n\t\t}\n\n\t\t// Create/initialise solution vector\n\t\tdouble[] soln = new double[numStates];\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tsoln[i] = 0.0;\n\t\t}\n\n\t\t// If every state is in a BSCC, it's much easier...\n\t\tif (notInBSCCs.isEmpty()) {\n\t\t\tmainLog.println(\"\\nAll states are in BSCCs (so no reachability probabilities computed)\");\n\t\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t\tBitSet bscc = bsccs.get(b);\n\t\t\t\tfor (int i = bscc.nextSetBit(0); i >= 0; i = bscc.nextSetBit(i + 1))\n\t\t\t\t\tsoln[i] += valueBSCCs[b];\n\t\t\t}\n\t\t}\n\n\t\t// Otherwise we have to do more work...\n\t\telse {\n\t\t\t// Compute probabilities of reaching each BSCC...\n\t\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t\t// Skip BSCCs with zero value\n\t\t\t\tif (valueBSCCs[b] == 0.0)\n\t\t\t\t\tcontinue;\n\t\t\t\tmainLog.println(\"\\nComputing probabilities of reaching BSCC \" + (b + 1));\n\t\t\t\tBitSet bscc = bsccs.get(b);\n\t\t\t\t// Compute probabilities\n\t\t\t\tdouble[] reachProbs = computeUntilProbs(dtmc, notInBSCCs, bscc).soln;\n\t\t\t\t// Multiply by value for BSCC, add to total\n\t\t\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t\t\tsoln[i] += reachProbs[i] * valueBSCCs[b];\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.timeTaken = watch.elapsedSeconds();\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute steady-state rewards, i.e., R=?[ S ].\n\t * @param dtmc the DTMC\n\t * @param modelRewards the (state) rewards\n\t */\n\tpublic ModelCheckerResult computeSteadyStateRewards(DTMC<Double> dtmc, MCRewards<Double> modelRewards) throws PrismException\n\t{\n\t\tint n = dtmc.getNumStates();\n\t\tdouble multRewards[] = new double[n];\n\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tmultRewards[i] = modelRewards.getStateReward(i);\n\t\t}\n\n\t\treturn computeSteadyStateBackwardsProbs(dtmc, multRewards);\n\t}\n\n\t/**\n\t * @see DTMCModelChecker#computeSteadyStateProbsForBSCC(DTMC, BitSet, double[], BSCCPostProcessor)\n\t */\n\tpublic ModelCheckerResult computeSteadyStateProbsForBSCC(DTMC<Double> dtmc, BitSet states, double result[]) throws PrismException\n\t{\n\t\treturn computeSteadyStateProbsForBSCC(dtmc, states, result, null);\n\t}\n\n\t/**\n\t * Compute steady-state probabilities for a BSCC\n\t * i.e. compute the long-run probability of being in each state of the BSCC.\n\t * No initial distribution is specified since it does not affect the result.\n\t * The result will be stored in the relevant portion of a full vector,\n\t * whose size equals the number of states in the DTMC.\n\t * Optionally, pass in an existing vector to be used for this purpose;\n\t * only the entries of this vector are changed that correspond to the BSCC states.\n\t * <p>\n\t * To ensure convergence, we use the iteration matrix<br/>\n\t * {@code P = (Q * deltaT + I)} where<br/>\n\t * {@code Q} is the generator matrix,\n\t * {@code deltaT} a preconditioning factor and\n\t * {@code I} is the the identity matrix.<br/>\n\t * See <em>William J. Stewart: \"Introduction to the Numerical Solution of Markov Chains\"</em> p.124 for details.\n\t * </p>\n\t * @param dtmc The DTMC\n\t * @param states The BSCC to be analysed\n\t * @param bsccPostProcessor Post-processor for the values of each BSCC (optional: null means no post-processing)\n\t * @param result Storage for result (ignored if null)\n\t */\n\tpublic ModelCheckerResult computeSteadyStateProbsForBSCC(DTMC<Double> dtmc, BitSet states, double result[], BSCCPostProcessor bsccPostProcessor) throws PrismException\n\t{\n\t\tif (dtmc.getModelType() != ModelType.DTMC) {\n\t\t\tthrow new PrismNotSupportedException(\"Explicit engine currently does not support steady-state computation for \" + dtmc.getModelType());\n\t\t}\n\t\tIterableBitSet bscc = new IterableBitSet(states);\n\n\t\t// Start value iteration\n\t\tmainLog.println(\"Starting value iteration...\");\n\t\tStopWatch watch = new StopWatch(mainLog).start();\n\n\t\t// Store num states\n\t\tint numStates = dtmc.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\t// Use the passed in vector, if present\n\t\tdouble[] soln = result == null ? new double[numStates] : result;\n\t\tdouble[] diagsQ = new double[numStates];\n\t\tdouble maxDiagsQ = 0.0;\n\n\t\t// Initialise the solution vector with an equiprobable distribution\n\t\t// over the BSCC states.\n\t\t// Additionally, compute the diagonal entries of the generator matrix Q.\n\t\t// Recall that the entries of the generator matrix are given by\n\t\t//     Q(s,t) = prob(s,t)   for s != t\n\t\t// and Q(s,s) = -sum_{s!=t} prob(s,t),\n\t\t// i.e., diagsQ[s] = -sum_{s!=t} prob(s,t).\n\t\t// Furthermore, compute max |diagsQ[s]|.\n\t\tdouble equiprob = 1.0 / states.cardinality();\n\t\tfor (OfInt iter = bscc.iterator(); iter.hasNext();) {\n\t\t\tint state = iter.nextInt();\n\n\t\t\t// Equiprobable for BSCC states.\n\t\t\tsoln[state] = equiprob;\n\n\t\t\t// Note: diagsQ[state] = 0.0, as it was freshly created\n\t\t\t// Compute negative exit rate (ignoring a possible self-loop)\n\t\t\tdtmc.forEachDoubleTransition(state, (s, t, prob) -> {\n\t\t\t\tif (s != t) {\n\t\t\t\t\tdiagsQ[state] -= prob;\n\t\t\t\t}\n\t\t\t});\n\n\t\t\t// Note: If there are no outgoing transitions, diagsQ[state] = 0, which is fine\n\n\t\t\t// Update maximal absolute diagonal entry value of Q\n\t\t\t// As diagsQ[s] <= 0, Math.abs(diagsQ[s]) = -diagsQ[s]\n\t\t\tmaxDiagsQ = Math.max(maxDiagsQ, -diagsQ[state]);\n\t\t}\n\n\t\t// Compute preconditioning factor deltaT\n\t\t// In William J. Stewart: \"Introduction to the Numerical Solution of Markov Chains\",\n\t\t// deltaT = 0.99 / maxDiagsQ is proposed;\n\t\t// in the symbolic engines deltaT is computed as 0.99 / max exit[s], i.e., where\n\t\t// the denominator corresponds to the maximal exit rate (where self loops are included).\n\t\t// Currently, use the same deltaT values as in the symbolic engines,\n\t\t// so for DTMCs, as exit[s]=1 for all states, deltaT is 0.99:\n\t\tdouble deltaT = 0.99;\n\t\t// TODO: Test and switch to deltaT computed as below, should lead to faster convergence.\n\t\t// double deltaT = 0.99 / maxDiagsQ;\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = ExportIterations.createWithUniqueFilename(\"Explicit DTMC BSCC steady state value iteration\", \"iterations-ss-bscc\");\n\t\t\titerationsExport.exportVector(soln);\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// create copy of the solution vector\n\t\tdouble[] soln2 = soln.clone();\n\n\t\t// Start iterations\n\t\tint iters = 0;\n\t\tboolean done = false;\n\t\twhile (!done && iters < maxIters) {\n\t\t\titers++;\n\t\t\t// Do vector-matrix multiplication step in (deltaT*Q + I)\n\t\t\tdtmc.vmMultPowerSteadyState(soln, soln2, diagsQ, deltaT, bscc);\n\t\t\t// Check termination\n\t\t\tdone = PrismUtils.doublesAreClose(soln, soln2, bscc, termCritParam, termCrit == TermCrit.ABSOLUTE);\n\t\t\t// Swap vectors for next iter\n\t\t\tdouble[] tmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\n\t\t\tif (iterationsExport != null) {\n\t\t\t\titerationsExport.exportVector(soln);\n\t\t\t}\n\t\t}\n\n\t\t// Finished value iteration\n\t\twatch.stop();\n\t\tmainLog.println(\"Power method: \" + iters + \" iterations in \" + watch.elapsedSeconds() + \" seconds.\");\n\n\t\t// normalise solution\n\t\tPrismUtils.normalise(soln, bscc);\n\n\t\tif (iterationsExport != null) {\n\t\t\t// export the normalised vector\n\t\t\titerationsExport.exportVector(soln);\n\t\t\titerationsExport.close();\n\t\t}\n\n\t\t// Apply post processing on soln\n\t\tif (bsccPostProcessor != null) {\n\t\t\tbsccPostProcessor.apply(soln, states);\n\t\t}\n\n\t\tif (result != null && result != soln) {\n\t\t\t// If result vector was passed in as method argument,\n\t\t\t// it can be the case that result does not point to the current soln vector (most recent values)\n\t\t\t// but to the soln2 vector.\n\t\t\t// In that case, we copy the relevant values from soln to result.\n\t\t\tfor (OfInt iter = bscc.iterator(); iter.hasNext();) {\n\t\t\t\tint state = iter.nextInt();\n\t\t\t\tresult[state] = soln[state];\n\t\t\t}\n\t\t}\n\t\t//\n\t\t// NOTE: from here on, don't change the values of result/soln,\n\t\t// as the values may have already been copied to the result vector above\n\t\t//\n\t\t// store only one result vector, free temporary vectors\n\t\tresult = soln;\n\t\tsoln = soln2 = null;\n\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\\n\" +\n\t\t\t             \"Consider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\tres.soln = result;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = watch.elapsedSeconds();\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute transient probabilities\n\t * i.e. compute the probability of being in each state at time step {@code k},\n\t * assuming the initial distribution {@code initDist}. \n\t * For space efficiency, the initial distribution vector will be modified and values over-written,  \n\t * so if you wanted it, take a copy. \n\t * @param dtmc The DTMC\n\t * @param k Time step\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic ModelCheckerResult computeTransientProbs(DTMC<Double> dtmc, int k, double initDist[]) throws PrismException\n\t{\n\t\tModelCheckerResult res;\n\t\tint n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\n\t\t// Start transient probability computation\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"Starting transient probability computation...\");\n\n\t\t// Store num states\n\t\tn = dtmc.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\t// Use the passed in vector, if present\n\t\tsoln = initDist;\n\t\tsoln2 = new double[n];\n\n\t\t// Start iterations\n\t\tfor (iters = 0; iters < k; iters++) {\n\t\t\t// Matrix-vector multiply\n\t\t\tdtmc.vmMult(soln, soln2);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished transient probability computation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Transient probability computation\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Simple test program.\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tDTMCModelChecker mc;\n\t\tDTMCSimple<Double> dtmc;\n\t\tModelCheckerResult res;\n\t\ttry {\n\t\t\t// Two examples of building and solving a DTMC\n\n\t\t\tint version = 2;\n\t\t\tif (version == 1) {\n\n\t\t\t\t// 1. Read in from .tra and .lab files\n\t\t\t\t//    Run as: PRISM_MAINCLASS=explicit.DTMCModelChecker bin/prism dtmc.tra dtmc.lab target_label\n\t\t\t\tmc = new DTMCModelChecker(null);\n\t\t\t\tdtmc = new DTMCSimple<>();\n\t\t\t\tdtmc.buildFromPrismExplicit(args[0]);\n\t\t\t\tdtmc.addInitialState(0);\n\t\t\t\t//System.out.println(dtmc);\n\t\t\t\tMap<String, BitSet> labels = StateModelChecker.loadLabelsFile(args[1]);\n\t\t\t\t//System.out.println(labels);\n\t\t\t\tBitSet target = labels.get(args[2]);\n\t\t\t\tif (target == null)\n\t\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + args[2] + \"\\\"\");\n\t\t\t\tfor (int i = 3; i < args.length; i++) {\n\t\t\t\t\tif (args[i].equals(\"-nopre\"))\n\t\t\t\t\t\tmc.setPrecomp(false);\n\t\t\t\t}\n\t\t\t\tres = mc.computeReachProbs(dtmc, target);\n\t\t\t\tSystem.out.println(res.soln[0]);\n\n\t\t\t} else {\n\n\t\t\t\t// 2. Build DTMC directly\n\t\t\t\t//    Run as: PRISM_MAINCLASS=explicit.DTMCModelChecker bin/prism\n\t\t\t\t//    (example taken from p.14 of Lec 5 of http://www.prismmodelchecker.org/lectures/pmc/) \n\t\t\t\tmc = new DTMCModelChecker(null);\n\t\t\t\tdtmc = new DTMCSimple<>(6);\n\t\t\t\tdtmc.setProbability(0, 1, 0.1);\n\t\t\t\tdtmc.setProbability(0, 2, 0.9);\n\t\t\t\tdtmc.setProbability(1, 0, 0.4);\n\t\t\t\tdtmc.setProbability(1, 3, 0.6);\n\t\t\t\tdtmc.setProbability(2, 2, 0.1);\n\t\t\t\tdtmc.setProbability(2, 3, 0.1);\n\t\t\t\tdtmc.setProbability(2, 4, 0.5);\n\t\t\t\tdtmc.setProbability(2, 5, 0.3);\n\t\t\t\tdtmc.setProbability(3, 3, 1.0);\n\t\t\t\tdtmc.setProbability(4, 4, 1.0);\n\t\t\t\tdtmc.setProbability(5, 5, 0.3);\n\t\t\t\tdtmc.setProbability(5, 4, 0.7);\n\t\t\t\tSystem.out.println(dtmc);\n\t\t\t\tBitSet target = new BitSet();\n\t\t\t\ttarget.set(4);\n\t\t\t\tBitSet remain = new BitSet();\n\t\t\t\tremain.set(1);\n\t\t\t\tremain.flip(0, 6);\n\t\t\t\tSystem.out.println(target);\n\t\t\t\tSystem.out.println(remain);\n\t\t\t\tres = mc.computeUntilProbs(dtmc, remain, target);\n\t\t\t\tSystem.out.println(res.soln[0]);\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMCSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.*;\nimport java.util.Map.Entry;\nimport java.util.function.Function;\n\nimport common.iterable.Reducible;\nimport io.ExplicitModelImporter;\nimport prism.Evaluator;\nimport prism.Pair;\nimport prism.PrismException;\n\n/**\n * Simple explicit-state representation of a DTMC.\n */\npublic class DTMCSimple<Value> extends DTMCExplicit<Value> implements ModelSimple<Value>\n{\n\t// Transition successors\n\tprotected List<List<Integer>> succ;\n\t// Transition probabilities\n\tprotected List<List<Value>> trans;\n\t// Transition actions\n\t// (stored for each state-\"choice\", where a \"choice\" is an index into the above lists)\n\tprotected ChoiceActionsSimple actions;\n\n\t// Constructors\n\n\t/**\n\t * Constructor: empty DTMC.\n\t */\n\tpublic DTMCSimple()\n\t{\n\t\tinitialise(0);\n\t}\n\n\t/**\n\t * Constructor: new DTMC with fixed number of states.\n\t */\n\tpublic DTMCSimple(int numStates)\n\t{\n\t\tinitialise(numStates);\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic DTMCSimple(DTMCSimple<Value> dtmc)\n\t{\n\t\tthis(dtmc.numStates);\n\t\tcopyFrom(dtmc);\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tsucc.set(i, new ArrayList<>(dtmc.succ.get(i)));\n\t\t\ttrans.set(i, new ArrayList<>(dtmc.trans.get(i)));\n\t\t}\n\t\tactions = new ChoiceActionsSimple(dtmc.actions);\n\t}\n\n\t/**\n\t * Construct a DTMC from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t * Pointer to states list is NOT copied (since now wrong).\n\t */\n\tpublic DTMCSimple(DTMCSimple<Value> dtmc, int permut[])\n\t{\n\t\tthis(dtmc.numStates);\n\t\tcopyFrom(dtmc, permut);\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tint numSucc = dtmc.succ.get(i).size();\n\t\t\tfor (int j = 0; j < numSucc; j++) {\n\t\t\t\tsucc.get(permut[i]).add(permut[dtmc.succ.get(i).get(j)]);\n\t\t\t\ttrans.get(permut[i]).add(dtmc.trans.get(i).get(j));\n\t\t\t}\n\t\t}\n\t\tactions = new ChoiceActionsSimple(dtmc.actions, permut);\n\t}\n\n\t/**\n\t * Construct a DTMCSimple object from a DTMC object.\n\t */\n\tpublic DTMCSimple(DTMC<Value> dtmc)\n\t{\n\t\tthis(dtmc, p -> p);\n\t}\n\n\t/**\n\t * Construct a DTMCSimple object from a DTMC object,\n\t * mapping probability values using the provided function.\n\t * There is no attempt to check that distributions sum to one.\n\t */\n\tpublic DTMCSimple(DTMC<Value> dtmc, Function<? super Value, ? extends Value> probMap)\n\t{\n\t\tthis(dtmc, probMap, dtmc.getEvaluator());\n\t}\n\n\t/**\n\t * Construct a DTMCSimple object from a DTMC object,\n\t * mapping probability values using the provided function.\n\t * There is no attempt to check that distributions sum to one.\n\t * Since the type changes (T -> Value), an Evaluator for Value must be given.\n\t */\n\tpublic <T> DTMCSimple(DTMC<T> dtmc, Function<? super T, ? extends Value> probMap, Evaluator<Value> eval)\n\t{\n\t\tthis(dtmc.getNumStates());\n\t\tcopyFrom(dtmc);\n\t\tsetEvaluator(eval);\n\t\tint numStates = getNumStates();\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tIterator<Entry<Integer, Pair<T, Object>>> iter = dtmc.getTransitionsAndActionsIterator(i);\n\t\t\twhile (iter.hasNext()) {\n\t\t\t\tMap.Entry<Integer, Pair<T, Object>> e = iter.next();\n\t\t\t\taddToProbability(i, e.getKey(), probMap.apply(e.getValue().first), e.getValue().second );\n\t\t\t}\n\t\t}\n\t}\n\n\t// Mutators (for ModelSimple)\n\n\t@Override\n\tpublic void initialise(int numStates)\n\t{\n\t\tsuper.initialise(numStates);\n\t\tsucc = new ArrayList<>(numStates);\n\t\ttrans = new ArrayList<>(numStates);\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tsucc.add(new ArrayList<>());\n\t\t\ttrans.add(new ArrayList<>());\n\t\t}\n\t\tactions = new ChoiceActionsSimple();\n\t}\n\n\t@Override\n\tpublic void clearState(int i)\n\t{\n\t\t// Do nothing if state does not exist\n\t\tif (i >= numStates || i < 0)\n\t\t\treturn;\n\t\t// Clear data structures\n\t\tsucc.get(i).clear();\n\t\ttrans.get(i).clear();\n\t\tactions.clearState(i);\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t@Override\n\tpublic int addState()\n\t{\n\t\taddStates(1);\n\t\treturn numStates - 1;\n\t}\n\n\t@Override\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tfor (int i = 0; i < numToAdd; i++) {\n\t\t\tsucc.add(new ArrayList<>());\n\t\t\ttrans.add(new ArrayList<>());\n\t\t\tnumStates++;\n\t\t}\n\t}\n\n\t@Override\n\tpublic void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\tinitialise(modelImporter.getNumStates());\n\t\tmodelImporter.extractMCTransitions(this::setProbability, getEvaluator());\n\t}\n\n\t// Mutators (other)\n\n\t/**\n\t * Set the probability for a transition.\n\t */\n\tpublic void setProbability(int i, int j, Value prob)\n\t{\n\t\tsetProbability(i, j, prob, null);\n\t}\n\n\t/**\n\t * Set the probability for a transition.\n\t */\n\tpublic void setProbability(int i, int j, Value prob, Object action)\n\t{\n\t\tList<Integer> iSucc = succ.get(i);\n\t\tList<Value> iTrans = trans.get(i);\n\t\tint numSucc = succ.get(i).size();\n\t\t// Check for existing transition\n\t\tfor (int k = 0; k < numSucc; k++) {\n\t\t\tif (iSucc.get(k) == j && actions.actionMatches(i, k, action)) {\n\t\t\t\tif (getEvaluator().isZero(prob)) {\n\t\t\t\t\tiSucc.remove(k);\n\t\t\t\t\tiTrans.remove(k);\n\t\t\t\t} else {\n\t\t\t\t\tiTrans.set(k, prob);\n\t\t\t\t}\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\t// No existing transition\n\t\tiSucc.add(j);\n\t\tiTrans.add(prob);\n\t\tactions.setAction(i, numSucc, action);\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t/**\n\t * Add to the probability for a transition.\n\t */\n\tpublic void addToProbability(int i, int j, Value prob)\n\t{\n\t\taddToProbability(i, j, prob, null);\n\t}\n\n\t/**\n\t * Add to the probability for a transition.\n\t */\n\tpublic void addToProbability(int i, int j, Value prob, Object action)\n\t{\n\t\tif (getEvaluator().isZero(prob)) {\n\t\t\treturn;\n\t\t}\n\t\tList<Integer> iSucc = succ.get(i);\n\t\tList<Value> iTrans = trans.get(i);\n\t\tint numSucc = succ.get(i).size();\n\t\t// Check for existing transition\n\t\tfor (int k = 0; k < numSucc; k++) {\n\t\t\tif (iSucc.get(k) == j && actions.actionMatches(i, k, action)) {\n\t\t\t\tiTrans.set(k, getEvaluator().add(iTrans.get(k), prob));\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\t// No existing transition\n\t\tiSucc.add(j);\n\t\tiTrans.add(prob);\n\t\tactions.setAction(i, numSucc, action);\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t// Accessors (for Model)\n\n\t@Override\n\tpublic List<Object> findActionsUsed()\n\t{\n\t\treturn actions.findActionsUsed(getNumStates(), this::getNumTransitions);\n\t}\n\n\t@Override\n\tpublic boolean onlyNullActionUsed()\n\t{\n\t\treturn actions.onlyNullActionUsed();\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s)\n\t{\n\t\treturn succ.get(s).size();\n\t}\n\n\t/** Get an iterator over the successors of state s */\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int s)\n\t{\n\t\t// Remove duplicates\n\t\treturn succ.get(s).iterator();\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(int s)\n\t{\n\t\treturn SuccessorsIterator.from(getSuccessorsIterator(s), false);\n\t}\n\n\t@Override\n\tpublic boolean isSuccessor(int s1, int s2)\n\t{\n\t\treturn succ.get(s1).contains(s2);\n\t}\n\n\t@Override\n\tpublic boolean allSuccessorsInSet(int s, BitSet set)\n\t{\n\t\treturn Reducible.extend(succ.get(s)).allMatch(set::get);\n\t}\n\n\t@Override\n\tpublic boolean someSuccessorsInSet(int s, BitSet set)\n\t{\n\t\treturn Reducible.extend(succ.get(s)).anyMatch(set::get);\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tint fixed = 0;\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (succ.get(i).isEmpty()) {\n\t\t\t\taddDeadlockState(i);\n\t\t\t\tif (fix) {\n\t\t\t\t\tsetProbability(i, i, getEvaluator().one(), null);\n\t\t\t\t\tfixed++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Add the empty action (if missing), regardless of whether actionList needs recomputing\n\t\tif (fixed > 0) {\n\t\t\tactionList.addAction(null);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (succ.get(i).isEmpty() && (except == null || !except.get(i)))\n\t\t\t\tthrow new PrismException(\"DTMC has a deadlock in state \" + i);\n\t\t}\n\t}\n\n\t// Accessors (for DTMC)\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(int s)\n\t{\n\t\t// Create iterator (no removal of duplicates)\n\t\treturn new Iterator<>() {\n\t\t\tprivate final int n = succ.get(s).size();\n\t\t\tprivate int i = 0;\n\n\t\t\t@Override\n\t\t\tpublic Entry<Integer, Value> next()\n\t\t\t{\n\t\t\t\treturn new AbstractMap.SimpleImmutableEntry<>(succ.get(s).get(i), trans.get(s).get(i++));\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn i < n;\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Pair<Value, Object>>> getTransitionsAndActionsIterator(int s)\n\t{\n\t\t// Create iterator (no removal of duplicates)\n\t\treturn new Iterator<>() {\n\t\t\tprivate final int n = succ.get(s).size();\n\t\t\tprivate int i = 0;\n\n\t\t\t@Override\n\t\t\tpublic Entry<Integer, Pair<Value, Object>> next()\n\t\t\t{\n\t\t\t\tPair<Value, Object> probAction = new Pair<>(trans.get(s).get(i), actions.getAction(s, i));\n\t\t\t\treturn new AbstractMap.SimpleImmutableEntry<>(succ.get(s).get(i++), probAction);\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn i < n;\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic Iterator<Object> getActionsIterator(int s)\n\t{\n\t\t// Create iterator (no removal of duplicates)\n\t\treturn new Iterator<>() {\n\t\t\tprivate final int n = succ.get(s).size();\n\t\t\tprivate int i = 0;\n\n\t\t\t@Override\n\t\t\tpublic Object next()\n\t\t\t{\n\t\t\t\treturn actions.getAction(s, i++);\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn i < n;\n\t\t\t}\n\t\t};\n\t}\n\n\t// Accessors (other)\n\n\t/**\n\t * Get the transitions (a distribution) for state s.\n\t */\n\tpublic Distribution<Value> getTransitions(int s)\n\t{\n\t\treturn new Distribution<>(getTransitionsIterator(s), getEvaluator());\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn toStringDTMC();\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof DTMCSimple))\n\t\t\treturn false;\n\t\tif (!super.equals(o))\n\t\t\treturn false;\n\t\tDTMCSimple<?> dtmc = (DTMCSimple<?>) o;\n\t\tif (!succ.equals(dtmc.succ))\n\t\t\treturn false;\n\t\tif (!trans.equals(dtmc.trans))\n\t\t\treturn false;\n\t\tif (!actions.equals(dtmc.actions))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMCSparse.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Christian von Essen <christian.vonessen@imag.fr> (Verimag, Grenoble)\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.AbstractMap;\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.LinkedHashSet;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.PrimitiveIterator.OfInt;\nimport java.util.function.Function;\n\nimport common.IterableStateSet;\nimport common.iterable.PrimitiveIterable;\nimport explicit.rewards.MCRewards;\nimport io.ExplicitModelImporter;\nimport io.IOUtils;\nimport prism.ActionListOwner;\nimport prism.Pair;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Sparse matrix (non-mutable) explicit-state representation of a DTMC.\n * This is much faster to access than e.g. DTMCSimple and should also be more compact.\n * The catch is that you have to create the model all in one go and then can't modify it.\n */\npublic class DTMCSparse extends DTMCExplicit<Double>\n{\n\t// Sparse matrix storing transition function (Steps)\n\t/** Indices into probabilities/columns giving the start of the transitions for each state (distribution);\n\t * array is of size numStates+1 and last entry is always equal to getNumTransitions() */\n\tprivate int rows[];\n\t/** Column (destination) indices for each transition (array of size numTransitions) */\n\tprivate int columns[];\n\t/** Probabilities for each transition (array of size numTransitions) */\n\tprivate double probabilities[];\n\t/** Optionally, action labels for each transition (array of size numTransitions or null) */\n\tprivate Object actions[];\n\n\tpublic DTMCSparse(final DTMC<Double> dtmc)\n\t{\n\t\tinitialise(dtmc.getNumStates());\n\t\tif (dtmc instanceof ActionListOwner) {\n\t\t\tactionList.copyFrom(((ActionListOwner) dtmc).getActionList());\n\t\t}\n\t\tfor (Integer state : dtmc.getDeadlockStates()) {\n\t\t\tdeadlocks.add(state);\n\t\t}\n\t\tfor (Integer state : dtmc.getInitialStates()) {\n\t\t\tinitialStates.add(state);\n\t\t}\n\t\tconstantValues = dtmc.getConstantValues();\n\t\tvarList = dtmc.getVarList();\n\t\tstatesList = dtmc.getStatesList();\n\t\tfor (String label : dtmc.getLabels()) {\n\t\t\tlabels.put(label, dtmc.getLabelStates(label));\n\t\t}\n\n\t\t// Copy transition function\n\t\tfinal int numTransitions = dtmc.getNumTransitions();\n\t\trows = new int[numStates + 1];\n\t\trows[numStates] = numTransitions;\n\t\tcolumns = new int[numTransitions];\n\t\tprobabilities = new double[numTransitions];\n\t\tfor (int state=0, column=0; state<numStates; state++) {\n\t\t\trows[state] = column;\n\t\t\tfor (Iterator<Entry<Integer, Pair<Double, Object>>> transitions = dtmc.getTransitionsAndActionsIterator(state); transitions.hasNext();) {\n\t\t\t\tfinal Entry<Integer, Pair<Double, Object>> transition = transitions.next();\n\t\t\t\tfinal double probability = transition.getValue().first;\n\t\t\t\tif (probability > 0) {\n\t\t\t\t\tcolumns[column] = transition.getKey();\n\t\t\t\t\tprobabilities[column] = probability;\n\t\t\t\t\tif (transition.getValue().second != null) {\n\t\t\t\t\t\tif (actions == null) {\n\t\t\t\t\t\t\tactions = new Object[numTransitions];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tactions[column] = transition.getValue().second;\n\t\t\t\t\t}\n\t\t\t\t\tcolumn++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tpredecessorRelation = dtmc.hasStoredPredecessorRelation() ? dtmc.getPredecessorRelation(null, false) : null;\n\t}\n\n\tpublic DTMCSparse(final DTMC<Double> dtmc, int[] permut)\n\t{\n\t\tinitialise(dtmc.getNumStates());\n\t\tif (dtmc instanceof ActionListOwner) {\n\t\t\tactionList.copyFrom(((ActionListOwner) dtmc).getActionList());\n\t\t}\n\t\tfor (Integer state : dtmc.getDeadlockStates()) {\n\t\t\tdeadlocks.add(permut[state]);\n\t\t}\n\t\tfor (Integer state : dtmc.getInitialStates()) {\n\t\t\tinitialStates.add(permut[state]);\n\t\t}\n\t\tconstantValues = dtmc.getConstantValues();\n\t\tvarList = dtmc.getVarList();\n\t\tstatesList = null;\n\t\tlabels.clear();\n\n\t\t// Compute the inverse of the permutation\n\t\tint[] permutInv = new int[numStates];\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tpermutInv[permut[state]] = state;\n\t\t}\n\t\t// Copy transition function\n\t\tfinal int numTransitions = dtmc.getNumTransitions();\n\t\trows = new int[numStates + 1];\n\t\trows[numStates] = numTransitions;\n\t\tcolumns = new int[numTransitions];\n\t\tprobabilities = new double[numTransitions];\n\t\tfor (int state=0, column=0; state<numStates; state++) {\n\t\t\trows[state] = column;\n\t\t\tfinal int originalState = permutInv[state];\n\t\t\tfor (Iterator<Entry<Integer, Pair<Double, Object>>> transitions = dtmc.getTransitionsAndActionsIterator(originalState); transitions.hasNext();) {\n\t\t\t\tfinal Entry<Integer, Pair<Double, Object>> transition = transitions.next();\n\t\t\t\tfinal double probability = transition.getValue().first;\n\t\t\t\tif (probability > 0) {\n\t\t\t\t\tcolumns[column] = permut[transition.getKey()];\n\t\t\t\t\tprobabilities[column] = probability;\n\t\t\t\t\tif (transition.getValue().second != null) {\n\t\t\t\t\t\tif (actions == null) {\n\t\t\t\t\t\t\tactions = new Object[numTransitions];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tactions[column] = transition.getValue().second;\n\t\t\t\t\t}\n\t\t\t\t\tcolumn++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Construct an empty DTMC (e.g. for subsequent explicit import)\n\t */\n\tpublic DTMCSparse()\n\t{\n\t}\n\n\t//--- Model ---\n\n\t@Override\n\tpublic List<Object> findActionsUsed()\n\t{\n\t\tif (actions == null) {\n\t\t\treturn Collections.singletonList(null);\n\t\t} else {\n\t\t\tLinkedHashSet<Object> allActions = new LinkedHashSet<>();\n\t\t\tint n = actions.length;\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tallActions.add(actions[i]);\n\t\t\t}\n\t\t\treturn new ArrayList<>(allActions);\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean onlyNullActionUsed()\n\t{\n\t\treturn actions == null;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions()\n\t{\n\t\treturn rows[numStates];\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int state)\n\t{\n\t\treturn rows[state + 1] - rows[state];\n\t}\n\n\t@Override\n\tpublic OfInt getSuccessorsIterator(final int state)\n\t{\n\t\treturn Arrays.stream(columns, rows[state], rows[state+1]).iterator();\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(int state)\n\t{\n\t\treturn SuccessorsIterator.from(getSuccessorsIterator(state), false);\n\t}\n\n\t@Override\n\tpublic boolean isSuccessor(final int s1, final int s2)\n\t{\n\t\tfor (int i=rows[s1], stop=rows[s1+1]; i < stop; i++) {\n\t\t\tif (columns[i] == s2) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean allSuccessorsInSet(final int state, final BitSet set)\n\t{\n\t\tfor (int i=rows[state], stop=rows[state+1]; i < stop; i++) {\n\t\t\tif (!set.get(columns[i])) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean someSuccessorsInSet(final int state, final BitSet set)\n\t{\n\t\tfor (int i=rows[state], stop=rows[state+1]; i < stop; i++) {\n\t\t\tif (set.get(columns[i])) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tfor (int state=0; state<numStates; state++) {\n\t\t\tif (rows[state] == rows[state+1]) {\n\t\t\t\tif (fix) {\n\t\t\t\t\tthrow new PrismException(\"Can't fix deadlocks in an DTMCSparse since it cannot be modified after construction\");\n\t\t\t\t}\n\t\t\t\tdeadlocks.add(state);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tfor (int state=0; state < numStates; state++) {\n\t\t\tif (rows[state] == rows[state+1] && (except == null || !except.get(state)))\n\t\t\t\tthrow new PrismException(\"DTMC has a deadlock in state \" + state);\n\t\t}\n\t}\n\n\n\n\t//--- ModelExplicit ---\n\n\t@Override\n\tpublic void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\tinitialise(modelImporter.getNumStates());\n\t\tactionList.markNeedsRecomputing();\n\t\tint numTransitions = modelImporter.getNumTransitions();\n\t\trows = new int[numStates + 1];\n\t\tcolumns = new int[numTransitions];\n\t\tprobabilities = new double[numTransitions];\n\t\tactions = new Object[numTransitions];\n\t\tIOUtils.MCTransitionConsumer<Double> cons = new IOUtils.MCTransitionConsumer<>() {\n\t\t\tint sLast = -1;\n\t\t\tint count = 0;\n\t\t\t@Override\n\t\t\tpublic void accept(int s, int s2, Double d, Object a) throws PrismException\n\t\t\t{\n\t\t\t\tif (s < sLast) {\n\t\t\t\t\tthrow new PrismException(\"Imported states/transitions must be in ascending order\");\n\t\t\t\t}\n\t\t\t\tif (s != sLast) {\n\t\t\t\t\trows[s] = count;\n\t\t\t\t\tsLast = s;\n\t\t\t\t}\n\t\t\t\tcolumns[count] = s2;\n\t\t\t\tprobabilities[count] = d;\n\t\t\t\tactions[count] = a;\n\t\t\t\tcount++;\n\t\t\t}\n\t\t};\n\t\trows[numStates] = numTransitions;\n\t\tmodelImporter.extractMCTransitions(cons);\n\t}\n\n\n\n\t//--- DTMC ---\n\n\t@Override\n\tpublic void forEachTransition(int state, TransitionConsumer<Double> consumer)\n\t{\n\t\tfor (int col = rows[state], stop = rows[state+1]; col < stop; col++) {\n\t\t\tconsumer.accept(state, columns[col], probabilities[col]);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void forEachDoubleTransition(int state, DoubleTransitionConsumer consumer)\n\t{\n\t\tfor (int col = rows[state], stop = rows[state+1]; col < stop; col++) {\n\t\t\tconsumer.accept(state, columns[col], probabilities[col]);\n\t\t}\n\t}\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Double>> getTransitionsIterator(final int state)\n\t{\n\t\treturn new Iterator<Entry<Integer, Double>>()\n\t\t{\n\t\t\tfinal int start = rows[state];\n\t\t\tint col = start;\n\t\t\tfinal int end = rows[state + 1];\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn col < end;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Entry<Integer, Double> next()\n\t\t\t{\n\t\t\t\tassert (col < end);\n\t\t\t\tfinal int index = col;\n\t\t\t\tcol++;\n\t\t\t\treturn new AbstractMap.SimpleImmutableEntry<>(columns[index], probabilities[index]);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Pair<Double, Object>>> getTransitionsAndActionsIterator(int state)\n\t{\n\t\treturn new Iterator<Entry<Integer, Pair<Double, Object>>>()\n\t\t{\n\t\t\tfinal int start = rows[state];\n\t\t\tint col = start;\n\t\t\tfinal int end = rows[state + 1];\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn col < end;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Entry<Integer, Pair<Double, Object>> next()\n\t\t\t{\n\t\t\t\tassert (col < end);\n\t\t\t\tfinal int index = col;\n\t\t\t\tcol++;\n\t\t\t\tPair probAction = new Pair<>(probabilities[index], actions == null ? null : actions[index]);\n\t\t\t\treturn new AbstractMap.SimpleImmutableEntry<>(columns[index], probAction);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic Iterator<Object> getActionsIterator(int s)\n\t{\n\t\treturn new Iterator<>()\n\t\t{\n\t\t\tfinal int start = rows[s];\n\t\t\tint col = start;\n\t\t\tfinal int end = rows[s + 1];\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn col < end;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Object next()\n\t\t\t{\n\t\t\t\treturn actions == null ? null : actions[col++];\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic boolean prob0step(final int s, final BitSet u)\n\t{\n\t\tboolean hasTransitionToU = false;\n\t\tfor (int i=rows[s], stop=rows[s+1]; i < stop; i++) {\n\t\t\tfinal int successor = columns[i];\n\t\t\tif (u.get(successor)) {\n\t\t\t\thasTransitionToU = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn hasTransitionToU;\n\t}\n\n\t@Override\n\tpublic boolean prob1step(final int s, final BitSet u, final BitSet v)\n\t{\n\t\tboolean allTransitionsToU = true;\n\t\tboolean hasTransitionToV = false;\n\t\tfor (int i=rows[s], stop=rows[s+1]; i < stop; i++) {\n\t\t\tfinal int successor = columns[i];\n\t\t\tif (!u.get(successor)) {\n\t\t\t\t// early abort, as overall result is false\n\t\t\t\tallTransitionsToU = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\thasTransitionToV = hasTransitionToV || v.get(successor);\n\t\t}\n\t\treturn (allTransitionsToU && hasTransitionToV);\n\t}\n\n\t@Override\n\tpublic double mvMultSingle(final int state, final double[] vect)\n\t{\n\t\tdouble d = 0.0;\n\t\tfor (int i=rows[state], stop=rows[state+1]; i < stop; i++) {\n\t\t\tfinal int target = columns[i];\n\t\t\tfinal double probability = probabilities[i];\n\t\t\td += probability * vect[target];\n\t\t}\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double mvMultJacSingle(final int state, final double[] vect)\n\t{\n\t\tdouble diag = 1.0;\n\t\tdouble d = 0.0;\n\t\tfor (int i=rows[state], stop=rows[state+1]; i < stop; i++) {\n\t\t\tfinal int target = columns[i];\n\t\t\tfinal double probability = probabilities[i];\n\t\t\tif (target != state) {\n\t\t\t\td += probability * vect[target];\n\t\t\t} else {\n\t\t\t\tdiag -= probability;\n\t\t\t}\n\t\t}\n\t\tif (diag > 0) {\n\t\t\td /= diag;\n\t\t}\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double mvMultRewSingle(final int state, final double[] vect, final MCRewards<Double> mcRewards)\n\t{\n\t\tdouble d = mcRewards.getStateReward(state);\n\t\tfor (int i=rows[state], stop=rows[state+1]; i < stop; i++) {\n\t\t\tfinal int target = columns[i];\n\t\t\tfinal double probability = probabilities[i];\n\t\t\t//d += probability * (mcRewards.getTransitionReward(state, i-rows[state]) + vect[target]);\n\t\t\td += probability * vect[target];\n\t\t}\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic void vmMult(final double[] vect, final double[] result)\n\t{\n\t\t// Initialise result to 0\n\t\tArrays.fill(result, 0);\n\t\t// Go through matrix elements (by row)\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tfor (int i=rows[state], stop=rows[state+1]; i < stop; i++) {\n\t\t\t\tint target = columns[i];\n\t\t\t\tdouble probability = probabilities[i];\n\t\t\t\tresult[target] += probability * vect[state];\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void vmMultPowerSteadyState(double vect[], double result[], double[] diagsQ, double deltaT, PrimitiveIterable.OfInt states)\n\t{\n\t\t// Recall that the generator matrix Q has entries\n\t\t//       Q(s,s) = -sum_{t!=s} prob(s,t)\n\t\t// and   Q(s,t) = prob(s,t)  for s!=t\n\t\t// The values Q(s,s) are passed in via the diagsQ vector, while the\n\t\t// values Q(s,t) correspond to the normal transitions\n\n\t\t// Initialise result for relevant states to vect[s] * (deltaT * diagsQ[s] + 1),\n\t\t// i.e., handle the product with the diagonal entries of (deltaT * Q) + I\n\t\tfor (OfInt it = states.iterator(); it.hasNext(); ) {\n\t\t\tint state = it.nextInt();\n\t\t\tresult[state] = vect[state] * ((deltaT * diagsQ[state]) + 1.0);\n\t\t}\n\n\t\t// For each relevant state...\n\t\tfor (OfInt it = states.iterator(); it.hasNext(); ) {\n\t\t\tint state = it.nextInt();\n\n\t\t\t// ... handle all Q(state,t) entries of the generator matrix\n\t\t\tfor (int i=rows[state], stop=rows[state+1]; i < stop; i++) {\n\t\t\t\tint target = columns[i];\n\t\t\t\tdouble prob = probabilities[i];\n\t\t\t\tif (state != target) {\n\t\t\t\t\t// ignore self loop, diagonal entries of the generator matrix handled above\n\t\t\t\t\t// update result vector entry for the *successor* state\n\t\t\t\t\tresult[target] += deltaT * prob * vect[state];\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t//--- Object ---\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn toStringDTMC();\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof DTMCSparse))\n\t\t\treturn false;\n\t\tfinal DTMCSparse dtmc = (DTMCSparse) o;\n\t\tif (numStates != dtmc.numStates)\n\t\t\treturn false;\n\t\tif (!initialStates.equals(dtmc.initialStates))\n\t\t\treturn false;\n\t\tif (!Utils.doubleArraysAreEqual(probabilities, dtmc.probabilities))\n\t\t\treturn false;\n\t\tif (!Utils.intArraysAreEqual(columns, dtmc.columns))\n\t\t\treturn false;\n\t\tif (!Utils.intArraysAreEqual(rows, dtmc.rows))\n\t\t\treturn false;\n\t\t// TODO: compare actions (complicated: null = null,null,null,...)\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DTMCUniformisedSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Map.Entry;\n\nimport parser.State;\nimport parser.Values;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport explicit.rewards.MCRewards;\n\n/**\n* Simple explicit-state representation of a DTMC, constructed (implicitly) as the uniformised DTMC of a CTMC.\n* This class is read-only: most of data is pointers to other model info.\n* <br>\n* Note: This implicitly constructed DTMC does not provide implementations for\n* all methods of a full DTMCExplicit model. See {@link CTMCSimple#buildUniformisedDTMC} for\n* a method to obtain an explicit uniformised DTMC.\n*/\npublic class DTMCUniformisedSimple<Value> extends DTMCExplicit<Value>\n{\n\t// Parent CTMC\n\tprotected CTMCSimple<Value> ctmc;\n\t// Uniformisation rate\n\tprotected Value q;\n\t// Number of extra transitions added (just for stats)\n\tprotected int numExtraTransitions;\n\n\t/**\n\t * Constructor: create from CTMC and uniformisation rate q.\n\t */\n\tpublic DTMCUniformisedSimple(CTMCSimple<Value> ctmc, Value q)\n\t{\n\t\tthis.ctmc = ctmc;\n\t\tthis.numStates = ctmc.getNumStates();\n\t\tthis.q = q;\n\t\tnumExtraTransitions = 0;\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (!ctmc.getTransitions(i).contains(i) && !getEvaluator().geq(ctmc.getTransitions(i).sumAllBut(i), q)) {\n\t\t\t\tnumExtraTransitions++;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Constructor: create from CTMC and its default uniformisation rate.\n\t */\n\tpublic DTMCUniformisedSimple(CTMCSimple<Value> ctmc)\n\t{\n\t\tthis(ctmc, ctmc.getDefaultUniformisationRate());\n\t}\n\n\t@Override\n\tpublic void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Not supported\");\n\t}\n\t\n\t// Accessors (for Model)\n\n\tpublic int getNumStates()\n\t{\n\t\treturn ctmc.getNumStates();\n\t}\n\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn ctmc.getNumInitialStates();\n\t}\n\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn ctmc.getInitialStates();\n\t}\n\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn ctmc.getFirstInitialState();\n\t}\n\n\tpublic boolean isInitialState(int i)\n\t{\n\t\treturn ctmc.isInitialState(i);\n\t}\n\n\t@Override\n\tpublic int getNumDeadlockStates()\n\t{\n\t\treturn ctmc.getNumDeadlockStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getDeadlockStates()\n\t{\n\t\treturn ctmc.getDeadlockStates();\n\t}\n\n\t@Override\n\tpublic StateValues getDeadlockStatesList()\n\t{\n\t\treturn ctmc.getDeadlockStatesList();\n\t}\n\n\t@Override\n\tpublic int getFirstDeadlockState()\n\t{\n\t\treturn ctmc.getFirstDeadlockState();\n\t}\n\n\t@Override\n\tpublic boolean isDeadlockState(int i)\n\t{\n\t\treturn ctmc.isDeadlockState(i);\n\t}\n\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn ctmc.getStatesList();\n\t}\n\t\n\tpublic Values getConstantValues()\n\t{\n\t\treturn ctmc.getConstantValues();\n\t}\n\t\n\tpublic int getNumTransitions()\n\t{\n\t\treturn ctmc.getNumTransitions() + numExtraTransitions;\n\t}\n\n\tpublic int getNumTransitions(int s)\n\t{\n\t\t// TODO\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\tpublic SuccessorsIterator getSuccessors(final int s)\n\t{\n\t\t// TODO\n\t\tthrow new Error(\"Not yet supported\");\n\t}\n\n\tpublic int getNumChoices(int s)\n\t{\n\t\t// Always 1 for a DTMC\n\t\treturn 1;\n\t}\n\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\tpublic void checkForDeadlocks() throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\t// No deadlocks by definition\n\t}\n\n\t@Override\n\tpublic String infoString()\n\t{\n\t\tString s = \"\";\n\t\ts += getNumStates() + \" states (\" + getNumInitialStates() + \" initial)\";\n\t\ts += \", \" + getNumTransitions() + \" transitions (incl. \" + numExtraTransitions + \" self-loops)\";\n\t\treturn s;\n\t}\n\n\t// Accessors (for DTMC)\n\n\tpublic Iterator<Entry<Integer,Value>> getTransitionsIterator(int s)\n\t{\n\t\t// TODO\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t@Override\n\tpublic double mvMultSingle(int s, double vect[])\n\t{\n\t\tdouble qDouble = getEvaluator().toDouble(q);\n\t\tDistribution<Value> distr = ctmc.getTransitions(s);\n\t\tdouble sum = 0.0, d = 0.0;\n\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\tint k = e.getKey();\n\t\t\tdouble prob = getEvaluator().toDouble(e.getValue());\n\t\t\t// Non-diagonal entries\n\t\t\tif (k != s) {\n\t\t\t\tsum += prob;\n\t\t\t\td += (prob / qDouble) * vect[k];\n\t\t\t}\n\t\t}\n\t\t// Diagonal entry\n\t\tif (sum < qDouble) {\n\t\t\td += (1 - sum/qDouble) * vect[s];\n\t\t}\n\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double mvMultJacSingle(int s, double vect[])\n\t{\n\t\tdouble qDouble = getEvaluator().toDouble(q);\n\t\tDistribution<Value> distr = ctmc.getTransitions(s);\n\t\tdouble sum = 0.0, d = 0.0;\n\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\tint k = e.getKey();\n\t\t\tdouble prob = (Double) e.getValue();\n\t\t\t// Non-diagonal entries only\n\t\t\tif (k != s) {\n\t\t\t\tsum += prob;\n\t\t\t\td += (prob / qDouble) * vect[k];\n\t\t\t}\n\t\t}\n\t\t// Diagonal entry is 1 - sum/q\n\t\td /= (sum / qDouble);\n\n\t\treturn d;\n\t}\n\n\tpublic double mvMultRewSingle(int s, double vect[], MCRewards<Double> mcRewards)\n\t{\n\t\t// TODO\n\t\tthrow new Error(\"Not yet supported\");\n\t}\n\n\t@Override\n\tpublic void vmMult(double vect[], double result[])\n\t{\n\t\tdouble qDouble = getEvaluator().toDouble(q);\n\t\t// Initialise result to 0\n\t\tArrays.fill(result, 0);\n\t\t// Go through matrix elements (by row)\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tdouble sum = 0.0;\n\t\t\tfor (Iterator<Entry<Integer, Value>> transitions = ctmc.getTransitionsIterator(state); transitions.hasNext();) {\n\t\t\t\tEntry<Integer, Value> trans = transitions.next();\n\t\t\t\tint target  = trans.getKey();\n\t\t\t\tdouble prob = getEvaluator().toDouble(trans.getValue()) / qDouble;\n\t\t\t\t// Non-diagonal entries only\n\t\t\t\tif (target != state) {\n\t\t\t\t\tsum += prob;\n\t\t\t\t\tresult[target] += prob * vect[state];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Diagonal entry is 1 - sum\n\t\t\tresult[state] += (1 - sum) * vect[state];\n\t\t}\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\ts += \"ctmc: \" + ctmc;\n\t\ts = \", q: \" + q;\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof DTMCUniformisedSimple))\n\t\t\treturn false;\n\t\tDTMCUniformisedSimple<?> dtmc = (DTMCUniformisedSimple<?>) o;\n\t\tif (!ctmc.equals(dtmc.ctmc))\n\t\t\treturn false;\n\t\tif (q != dtmc.q)\n\t\t\treturn false;\n\t\tif (numExtraTransitions != dtmc.numExtraTransitions)\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DijkstraSweepMPI.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.PriorityQueue;\nimport java.util.function.IntPredicate;\n\nimport common.StopWatch;\nimport common.IterableBitSet;\nimport explicit.IncomingChoiceRelation.Choice;\nimport explicit.rewards.MDPRewards;\nimport prism.PrismComponent;\n\n/**\n * An implementation of the upper bound computation for Rmin as detailed in the\n * paper McMahan, Likhachev, Gordon \"Bounded Real-Time Dynamic Programming:\n * RTDP with monotone upper bounds and performance guarantees\" (International\n * Conference on Machine Learning, 2005).\n * */\npublic class DijkstraSweepMPI {\n\n\tprivate static class QueueEntry implements Comparable<QueueEntry> {\n\t\tpublic int y;\n\t\tpublic double p;\n\t\tpublic double w;\n\n\t\tpublic QueueEntry(int y, double p, double w)\n\t\t{\n\t\t\tthis.y = y;\n\t\t\tthis.p = p;\n\t\t\tthis.w = w;\n\t\t}\n\n\t\t@Override\n\t\tpublic int compareTo(QueueEntry o)\n\t\t{\n\t\t\tint r = Double.compare(p, o.p);\n\t\t\tif (r == 0) {\n\t\t\t\treturn Double.compare(w, o.w);\n\t\t\t} else {\n\t\t\t\treturn r;\n\t\t\t}\n\t\t}\n\t}\n\n\tprivate static class ChoiceValues {\n\t\tpublic double p;\n\t\tpublic double w;\n\n\t\tpublic ChoiceValues(double p, double w)\n\t\t{\n\t\t\tthis.p = p;\n\t\t\tthis.w = w;\n\t\t}\n\t}\n\n\tprivate static boolean debug = false;\n\tprivate MDP<Double> mdp;\n\tprivate MDPRewards<Double> rewards;\n\tprivate PriorityQueue<QueueEntry> queue;\n\tprivate double[] pState;\n\tprivate double[] wState;\n\tprivate HashMap<Choice, ChoiceValues> choiceValues = new HashMap<Choice, ChoiceValues>();\n\tprivate QueueEntry[] pri;\n\tprivate int[] pi;\n\tprivate BitSet unknown, target;\n\tprivate BitSet fin = new BitSet();\n\tprivate IncomingChoiceRelation incoming;\n\tprivate double lambda;\n\n\tprivate DijkstraSweepMPI(PrismComponent parent, MDP<Double> mdp, MDPRewards<Double> rewards, BitSet target, BitSet unknown)\n\t{\n\t\tthis.mdp = mdp;\n\t\tthis.unknown = unknown;\n\t\tthis.target = target;\n\t\tthis.rewards = rewards;\n\n\t\tincoming = IncomingChoiceRelation.forModel(parent, mdp);\n\n\t\tqueue = new PriorityQueue<QueueEntry>();\n\t\tpState = new double[mdp.getNumStates()];\n\t\twState = new double[mdp.getNumStates()];\n\t\tpri = new QueueEntry[mdp.getNumStates()];\n\t\tpi = new int[mdp.getNumStates()];\n\n\t\tfor (int s : IterableBitSet.getSetBits(unknown)) {\n\t\t\tfor (int choice = 0, numChoices = mdp.getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t\tChoice c = new Choice(s, choice);\n\t\t\t\tdouble rew = rewards.getStateReward(s);\n\t\t\t\trew += rewards.getTransitionReward(s, choice);\n\t\t\t\tchoiceValues.put(c, new ChoiceValues(0.0, rew));\n\t\t\t}\n\t\t}\n\n\t\tfor (int s : IterableBitSet.getSetBits(target)) {\n\t\t\tpState[s] = 1.0;\n\t\t}\n\n\t\tHashSet<Choice> preTarget = new HashSet<Choice>();\n\t\tfor (int t : IterableBitSet.getSetBits(target)) {\n\t\t\tfor (Choice c : incoming.getIncomingChoices(t)) {\n\t\t\t\tboolean newChoice = preTarget.add(c);\n\t\t\t\tif (newChoice) {\n\t\t\t\t\tif (!unknown.get(c.getState())) {\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\tif (!validChoice(c)) {\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\n\t\t\t\t\tupdate(c, target);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tpreTarget.clear();\n\n\t\tsweep();\n\n\t\tcomputeLambda();\n\t}\n\n\tprivate void sweep()\n\t{\n\t\twhile (!queue.isEmpty()) {\n\t\t\tint x = queue.poll().y;\n\t\t\tif (fin.get(x)) {\n\t\t\t\t// already handled\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tfin.set(x);\n\t\t\tChoiceValues v = choiceValues.get(new Choice(x, pi[x]));\n\t\t\twState[x] = v.w;\n\t\t\tpState[x] = v.p;\n\n\t\t\tfor (Choice c : incoming.getIncomingChoices(x)) {\n\t\t\t\tif (fin.get(c.getState())) {\n\t\t\t\t\t// already handled, skip\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\tif (!unknown.get(c.getState())) {\n\t\t\t\t\t// uninteresting state\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\tif (!validChoice(c)) {\n\t\t\t\t\t// some successor go outside unknown U target (e.g., to some infinity or undefined state)\n\t\t\t\t\t// skip\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\t// a relevant choice, update\n\t\t\t\tupdate(c, x);\n\t\t\t}\n\t\t}\n\t}\n\n\tprivate boolean validChoice(Choice choice)\n\t{\n\t\tIntPredicate outsideRelevant = (int t) -> {\n\t\t\tif (unknown.get(t) || target.get(t)) return false;\n\t\t\treturn true;\n\t\t};\n\n\t\treturn !mdp.someSuccessorsMatch(choice.getState(), choice.getChoice(), outsideRelevant);\n\t}\n\n\tprivate void update(Choice choice, int x)\n\t{\n\t\tdouble w_x = wState[x];\n\t\t// compute P^a_yx * w(x)\n\t\tdouble Pw = mdp.sumOverDoubleTransitions(choice.getState(), choice.getChoice(), (int s, int t, double p) -> {\n\t\t\tif (t != x) return 0.0;\n\t\t\treturn p * w_x;\n\t\t});\n\n\t\tdouble p_x = pState[x];\n\t\t// compute P^a_yx * p_g(x)\n\t\tdouble Pp = mdp.sumOverDoubleTransitions(choice.getState(), choice.getChoice(), (int s, int t, double p) -> {\n\t\t\tif (t != x) return 0.0;\n\t\t\treturn p * p_x;\n\t\t});\n\n\t\tChoiceValues c = choiceValues.get(choice);\n\t\tassert(c != null);\n\t\tc.p += Pp;\n\t\tc.w += Pw;\n\n\t\tQueueEntry newPri = new QueueEntry(choice.getState(), 1 - c.p, c.w);\n\t\tif (pri[choice.getState()] == null || newPri.compareTo(pri[choice.getState()]) < 0) {\n\t\t\tpri[choice.getState()] = newPri;\n\t\t\tpi[choice.getState()] = choice.getChoice();\n\t\t\tqueue.add(newPri);\n\t\t}\n\t}\n\n\tprivate void update(Choice choice, BitSet target)\n\t{\n\t\t// compute P^a_y->target\n\t\tdouble Pp = mdp.sumOverDoubleTransitions(choice.getState(), choice.getChoice(), (int s, int t, double p) -> {\n\t\t\tif (target.get(t)) return p;\n\t\t\treturn 0.0;\n\t\t});\n\n\t\tChoiceValues c = choiceValues.get(choice);\n\t\tc.p += Pp;\n\n\t\tQueueEntry newPri = new QueueEntry(choice.getState(), 1 - c.p, c.w);\n\t\tif (pri[choice.getState()] == null || newPri.compareTo(pri[choice.getState()]) < 0) {\n\t\t\tpri[choice.getState()] = newPri;\n\t\t\tpi[choice.getState()] = choice.getChoice();\n\t\t\tqueue.add(newPri);\n\t\t}\n\t}\n\n\tprivate double computeLambda()\n\t{\n\t\tlambda = 0.0;\n\n\t\tfor (int x : IterableBitSet.getSetBits(unknown)) {\n\t\t\tint a = pi[x];\n\t\t\tdouble lambda_x_a = Double.POSITIVE_INFINITY;\n\n\t\t\t// check condition (I)\n\t\t\tdouble I_sum = mdp.sumOverDoubleTransitions(x, a, (int s, int t, double p) -> {\n\t\t\t\treturn p * pState[t];\n\t\t\t});\n\n\t\t\tif (pState[x] < I_sum) {\n\t\t\t\t// condition (I) holds\n\t\t\t\tdouble den = rewards.getStateReward(x) + rewards.getTransitionReward(x, a); // c(x,a)\n\t\t\t\tden += mdp.sumOverDoubleTransitions(x, a, (int s, int t, double p) -> {\n\t\t\t\t\treturn p * wState[t];\n\t\t\t\t});\n\t\t\t\tden -= wState[x];\n\n\t\t\t\tdouble num = mdp.sumOverDoubleTransitions(x, a, (int s, int t, double p) -> {\n\t\t\t\t\treturn p * pState[t];\n\t\t\t\t});\n\t\t\t\tnum -= pState[x];\n\n\t\t\t\tlambda_x_a = den / num;\n\t\t\t} else {\n\t\t\t\t// TODO: check condition (II)\n\t\t\t\tlambda_x_a = 0;\n\t\t\t}\n\n\t\t\tlambda = Double.max(lambda, lambda_x_a);\n\t\t}\n\n\t\treturn lambda;\n\t}\n\n\tpublic static double[] computeUpperBounds(PrismComponent parent, MDP<Double> mdp, MDPRewards<Double> rewards, BitSet target, BitSet unknown)\n\t{\n\t\tStopWatch timer = new StopWatch(parent.getLog());\n\t\ttimer.start(\"computing upper bound(s) for Rmin using the DSI-MP algorithm\");\n\n\t\tparent.getLog().println(\"Computing upper bound(s) for Rmin using the Dijkstra Sweep for Monotone Pessimistic Initialization algorithm...\");\n\t\tdouble[] upperBounds = new double[mdp.getNumStates()];\n\t\tDijkstraSweepMPI dsmpi = new DijkstraSweepMPI(parent, mdp, rewards, target, unknown);\n\n\t\tfor (int x : IterableBitSet.getSetBits(unknown)) {\n\t\t\tupperBounds[x] = dsmpi.wState[x] + dsmpi.lambda*(1 - dsmpi.pState[x]);\n\t\t}\n\n\t\tif (debug) {\n\t\t\tparent.getLog().println(upperBounds);\n\t\t}\n\n\t\ttimer.stop();\n\t\treturn upperBounds;\n\t}\n\n\tpublic static double computeUpperBound(PrismComponent parent, MDP<Double> mdp, MDPRewards<Double> rewards, BitSet target, BitSet unknown)\n\t{\n\t\tdouble bound = 0.0;\n\t\tfinal double[] upperBounds = computeUpperBounds(parent, mdp, rewards, target, unknown);\n\t\tfor (int s : IterableBitSet.getSetBits(unknown)) {\n\t\t\tbound = Double.max(bound, upperBounds[s]);\n\t\t}\n\t\treturn bound;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DiscretizedBelief.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Xueyi Zou <xz972@york.ac.uk> (University of York)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Arrays;\n\npublic class DiscretizedBelief\n{\n\tpublic int[] intBeliefArray;\n\n\tpublic DiscretizedBelief(double[] belief, int D)\n\t{\n\t\tint beliefSize = belief.length;\n\t\tintBeliefArray = new int[beliefSize];\n\t\tfor (int i = 0; i < beliefSize; i++) {\n\t\t\tintBeliefArray[i] = (int) Math.ceil(belief[i] * D);\n\t\t}\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\treturn Arrays.hashCode(intBeliefArray);\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\n\t\tDiscretizedBelief other = (DiscretizedBelief) obj;\n\n\t\tif (intBeliefArray.length != other.intBeliefArray.length) {\n\t\t\treturn false;\n\t\t} else {\n\t\t\tfor (int i = 0; i < intBeliefArray.length; i++) {\n\t\t\t\tif (Math.abs(intBeliefArray[i] - other.intBeliefArray[i]) > 1e-6)\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn Arrays.toString(intBeliefArray);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/Distribution.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.Iterator;\nimport java.util.Map;\nimport java.util.Map.Entry;\nimport java.util.Set;\n\nimport common.iterable.FunctionalIterable;\nimport common.iterable.FunctionalIterator;\nimport common.iterable.Reducible;\nimport prism.Evaluator;\nimport simulator.RandomNumberGenerator;\n\n/**\n * Explicit representation of a probability distribution.\n * Basically, a mapping from (integer-valued) indices to (non-zero) probabilities.\n * This is a generic class where probabilities are of type {@code Value}.\n */\npublic class Distribution<Value> implements FunctionalIterable<Entry<Integer, Value>>\n{\n\t/** Mapping from indices to probability values */\n\tprotected final HashMap<Integer, Value> map;\n\t\n\t/** Evaluator for manipulating probability values in the distribution (of type {@code Value}) */\n\tprotected final Evaluator<Value> eval;\n\n\t/**\n\t * Create an empty distribution\n\t * (assumes an Evaluator of type Double, unless set afterwards).\n\t * This constructor is deprecated: it is preferable to either use the\n\t * static creation methods such as {@link #ofDouble()}, or pass an\n\t * evaluator, e.g., with {@link #Distribution(Evaluator)}.\n\t */\n\t@Deprecated\n\tpublic Distribution()\n\t{\n\t\tthis((Evaluator<Value>) Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Create an empty distribution.\n\t * (with an Evaluator to match the type parameter Value)\n\t */\n\tpublic Distribution(Evaluator<Value> eval)\n\t{\n\t\tthis.eval = eval;\n\t\tthis.map = new HashMap<>();\n\t}\n\n\t/**\n\t * Construct a distribution from an iterator over transitions\n\t * (with an Evaluator to match the type parameter Value).\n\t */\n\tpublic Distribution(Iterator<Entry<Integer, Value>> transitions, Evaluator<Value> eval)\n\t{\n\t\tthis(eval);\n\t\t// use #add to ensure probabilities sum up for any duplicated indices\n\t\ttransitions.forEachRemaining(t -> add(t.getKey(), t.getValue()));\n\t}\n\n\t/**\n\t * Copy constructor\n\t * (the Evaluator is also copied).\n\t */\n\tpublic Distribution(Distribution<Value> distr)\n\t{\n\t\tthis(distr.getEvaluator());\n\t\t// use Map#put since for each index we get only one probability\n\t\tdistr.forEach(t -> map.put(t.getKey(), t.getValue()));\n\t}\n\n\t/**\n\t * Construct a distribution from an existing one and an index permutation,\n\t * i.e. in which index i becomes index permut[i]\n\t * (the Evaluator is also copied).\n\t * Note: have to build the new distributions from scratch anyway to do this,\n\t * so may as well provide this functionality as a constructor.\n\t */\n\tpublic Distribution(Distribution<Value> distr, int permut[])\n\t{\n\t\tthis(distr.getEvaluator());\n\t\t// use #add to ensure probabilities sum up for each index\n\t\tdistr.forEach(t -> add(permut[t.getKey()], t.getValue()));\n\t}\n\n\t/**\n\t * Construct an empty distribution\n\t * assuming an Evaluator of type Double.\n\t */\n\tpublic static Distribution<Double> ofDouble()\n\t{\n\t\treturn new Distribution<>(Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Construct a distribution from an iterator over transitions\n\t * assuming an Evaluator of type Double.\n\t */\n\tpublic static Distribution<Double> ofDouble(Iterator<Entry<Integer, Double>> transitions)\n\t{\n\t\treturn new Distribution<Double>(transitions, Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Clear all entries of the distribution.\n\t */\n\tpublic void clear()\n\t{\n\t\tmap.clear();\n\t}\n\n\t/**\n\t * Add non-negative {@code prob} to the probability for index {@code j}.\n\t * Return boolean {@code true} if no new transition is created,\n\t * i.e., {@code false} indicates a new transition with prob > 0.\n\t *\n\t * @return {@code true} iff p(j) != 0 || prob == 0\n\t */\n\tpublic boolean add(int j, Value prob)\n\t{\n\t\tif (eval.isZero(prob)) {\n\t\t\treturn true;\n\t\t}\n\t\tValue sum = map.merge(j, prob, eval::add);\n\t\treturn sum != prob;\n\n\t}\n\n\t/**\n\t * Set the probability for index {@code j} to {@code prob}.\n\t */\n\tpublic void set(int j, Value prob)\n\t{\n\t\tif (eval.isZero(prob)) {\n\t\t\tmap.remove(j);\n\t\t} else {\n\t\t\tmap.put(j, prob);\n\t\t}\n\t}\n\n\t/**\n\t * Get the probability for index {@code j}.\n\t */\n\tpublic Value get(int j)\n\t{\n\t\treturn map.getOrDefault(j, eval.zero());\n\t}\n\n\t/**\n\t * Returns true if index {@code j} is in the support of the distribution.\n\t */\n\tpublic boolean contains(int j)\n\t{\n\t\treturn map.containsKey(j);\n\t}\n\n\t/**\n\t * Returns true if all indices in the support of the distribution are in the set. \n\t */\n\tpublic boolean isSubsetOf(BitSet set)\n\t{\n\t\treturn Reducible.extend(getSupport()).allMatch(set::get);\n\t}\n\n\t/**\n\t * Returns true if at least one index in the support of the distribution is in the set. \n\t */\n\tpublic boolean containsOneOf(BitSet set)\n\t{\n\t\treturn Reducible.extend(getSupport()).anyMatch(set::get);\n\t}\n\n\t/**\n\t * Get the support of the distribution.\n\t */\n\tpublic Set<Integer> getSupport()\n\t{\n\t\treturn map.keySet();\n\t}\n\n\t/**\n\t * Get an iterator over the entries of the map defining the distribution.\n\t */\n\tpublic FunctionalIterator<Entry<Integer, Value>> iterator()\n\t{\n\t\treturn Reducible.extend(map.entrySet().iterator());\n\t}\n\n\t/**\n\t * Returns true if the distribution is empty.\n\t */\n\tpublic boolean isEmpty()\n\t{\n\t\treturn map.isEmpty();\n\t}\n\n\t/**\n\t * Get the size of the support of the distribution.\n\t */\n\tpublic int size()\n\t{\n\t\treturn map.size();\n\t}\n\n\t/**\n\t * Sample an index at random from the distribution.\n\t * Returns -1 if the distribution is empty.\n\t */\n\tpublic int sample()\n\t{\n\t\treturn getValueByProbabilitySum(Math.random());\n\t}\n\t\n\t/**\n\t * Sample an index at random from the distribution, using the specified RandomNumberGenerator.\n\t * Returns -1 if the distribution is empty.\n\t */\n\tpublic int sample(RandomNumberGenerator rng)\n\t{\n\t\treturn getValueByProbabilitySum(rng.randomUnifDouble());\n\t}\n\t\n\t/**\n\t * Get the first index for which the sum of probabilities of that and all prior indices exceeds x.\n\t * Returns -1 if the distribution is empty.\n\t * @param x Probability sum\n\t */\n\tprivate int getValueByProbabilitySum(double x)\n\t{\n\t\tif (isEmpty()) {\n\t\t\treturn -1;\n\t\t}\n\t\tIterator<Entry<Integer, Value>> i = iterator();\n\t\tMap.Entry<Integer, Value> e = null;\n\t\tValue tot = eval.zero();\n\t\twhile (x >= eval.toDouble(tot) && i.hasNext()) {\n\t\t\te = i.next();\n\t\t\ttot = eval.add(tot, e.getValue());\n\t\t}\n\t\treturn e.getKey();\n\t}\n\n\t/**\n\t * Get the sum of the probabilities in the distribution.\n\t */\n\tpublic Value sum()\n\t{\n\t\treturn map(Entry::getValue).reduce(eval.zero(), eval::add);\n\t}\n\n\t/**\n\t * Get the sum of all the probabilities in the distribution except for index j.\n\t */\n\tpublic Value sumAllBut(int j)\n\t{\n\t\treturn filter(t -> t.getKey() != j).map(Entry::getValue).reduce(eval.zero(), eval::add);\n\t}\n\n\t/**\n\t * Create a new distribution, based on a mapping from the indices\n\t * used in this distribution to a different set of indices.\n\t */\n\tpublic Distribution<Value> map(int map[])\n\t{\n\t\treturn new Distribution<Value>(this, map);\n\t}\n\n\t/**\n\t * Get an Evaluator for the probability values stored in this distribution.\n\t * This is need, for example, to compute probability sums, check for equality to 0/1, etc.\n\t * By default, this is initialised to an evaluator for the (usual) case when Value is Double.\n\t */\n\tpublic Evaluator<Value> getEvaluator()\n\t{\n\t\treturn eval;\n\t}\n\t\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (! (o instanceof Distribution)) {\n\t\t\treturn false;\n\t\t}\n\t\t// Check elements of distribution using evaluator equals method\n\t\tHashMap<Integer,Value> oMap = ((Distribution<Value>) o).map;\n\t\tif (map.size() != oMap.size()) {\n\t\t\treturn false;\n\t\t}\n\t\tfor (Map.Entry<Integer,Value> entry : map.entrySet()) {\n\t\t\tInteger key = entry.getKey();\n\t\t\tValue value = entry.getValue(); // We assume nothing maps to null\n\t\t\tValue oValue = oMap.get(key);\n\t\t\tif (oValue == null || !getEvaluator().equals(value, oValue)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\t// Simple hash code\n\t\treturn map.size();\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn map.toString();\n\t}\n\t\n\tpublic String toStringCSV()\n\t{\n\t\tString s = \"Value\";\n\t\tIterator<Entry<Integer, Value>> i = iterator();\n\t\twhile (i.hasNext()) {\n\t\t\tMap.Entry<Integer, Value> e = i.next();\n\t\t\ts += \", \" + e.getKey();\n\t\t}\n\t\ts += \"\\nProbability\";\n\t\ti = iterator();\n\t\twhile (i.hasNext()) {\n\t\t\tMap.Entry<Integer, Value> e = i.next();\n\t\t\ts += \", \" + e.getValue();\n\t\t}\n\t\ts += \"\\n\";\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DistributionOver.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.AbstractMap;\nimport java.util.Iterator;\nimport java.util.Objects;\nimport java.util.Map.Entry;\nimport java.util.Set;\nimport java.util.function.Function;\nimport java.util.stream.Collectors;\nimport java.util.stream.StreamSupport;\n\nimport simulator.RandomNumberGenerator;\n\n/**\n * Explicit representation of a probability distribution over objects of type {@code T}.\n * This class is also generic in terms of the type for probabilities {@code Value}.\n */\npublic class DistributionOver<Value,T> implements Iterable<Entry<T, Value>>\n{\n\t// Stored as a Distribution (over integer indices) and a mapping from indices to Objects\n\tprivate Distribution<Value> distr;\n\tprivate Function<Integer, T> objects;\n\t\n\t/**\n\t * Create from a Distribution (over integer indices) and a mapping from indices to Objects\n\t */\n\tpublic static <Value,T> DistributionOver<Value,T> create(Distribution<Value> distr, Function<Integer, T> objects)\n\t{\n\t\tDistributionOver<Value,T> d = new DistributionOver<>();\n\t\td.distr = distr;\n\t\td.objects = objects;\n\t\treturn d;\n\t}\n\t\n\t/**\n\t * Get the probability assigned to a value\n\t */\n\tpublic Value getProbability(T val)\n\t{\n\t\tfor (Entry<Integer, Value> elem : distr) {\n\t\t\tT act = objects.apply(elem.getKey());\n\t\t\tif (Objects.equals(act, val)) {\n\t\t\t\treturn elem.getValue();\n\t\t\t}\n\t\t}\n\t\treturn distr.getEvaluator().zero();\n\t}\n\t\n\t/**\n\t * Get an iterator over the entries of the map defining the distribution.\n\t */\n\tpublic Iterator<Entry<T, Value>> iterator()\n\t{\n\t\treturn new Iterator<Entry<T, Value>>()\n\t\t{\n\t\t\tIterator<Entry<Integer, Value>> iter = distr.iterator();\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn iter.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Entry<T, Value> next()\n\t\t\t{\n\t\t\t\tEntry<Integer, Value> e = iter.next();\n\t\t\t\treturn new AbstractMap.SimpleImmutableEntry<>(objects.apply(e.getKey()), e.getValue());\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get the support of the distribution.\n\t */\n\tpublic Set<T> getSupport()\n\t{\n\t\treturn distr.getSupport().stream().map(objects::apply).collect(Collectors.toSet());\n\t}\n\n\t/**\n\t * Get the support of the distribution, as a string \"a,b,c\".\n\t */\n\tpublic String getSupportString()\n\t{\n\t\treturn distr.getSupport().stream().map(i -> objects.apply(i).toString()).collect(Collectors.joining(\",\"));\n\t}\n\n\t/**\n\t * Sample an index at random from the distribution.\n\t * Returns null if the distribution is empty.\n\t */\n\tpublic T sample()\n\t{\n\t\tint i = distr.sample();\n\t\treturn i == -1 ? null : objects.apply(i);\n\t}\n\t\n\t/**\n\t * Sample an index at random from the distribution, using the specified RandomNumberGenerator.\n\t * Returns null if the distribution is empty.\n\t */\n\tpublic T sample(RandomNumberGenerator rng)\n\t{\n\t\tint i = distr.sample(rng);\n\t\treturn i == -1 ? null : objects.apply(i);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn StreamSupport.stream(distr.spliterator(), false)\n\t\t\t\t.map(e -> e.getValue() + \":\" + objects.apply(e.getKey()))\n\t\t\t\t.collect(Collectors.joining(\"+\"));\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DistributionSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.*;\n\n/**\n * Represents a set of distributions.\n * The order in which distributions are inserted is preserved\n * (but does not affect equality of distributions sets).\n */\npublic class DistributionSet<Value> extends LinkedHashSet<Distribution<Value>>\n{\n\tprivate static final long serialVersionUID = 1L;\n\n\tpublic Object action;\n\n\tpublic DistributionSet(Object action)\n\t{\n\t\tsuper();\n\t\tthis.action = action;\n\t}\n\n\tpublic Object getAction()\n\t{\n\t\treturn action;\n\t}\n\n\tpublic void setAction(Object action)\n\t{\n\t\tthis.action = action;\n\t}\n\n\t/**\n\t * Returns true if all indices in the supports of all distributions are in the set. \n\t */\n\tpublic boolean isSubsetOf(BitSet set)\n\t{\n\t\tfor (Distribution<Value> itDist : this) {\n\t\t\tif (!itDist.isSubsetOf(set)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Returns true if at least one index in the support of some distribution is in the set. \n\t */\n\tpublic boolean containsOneOf(BitSet set)\n\t{\n\t\tfor (Distribution<Value> itDist : this) {\n\t\t\tif (itDist.containsOneOf(set)) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn (action == null ? \"\" : \"\\\"\" + action + \"\\\":\") + super.toString();\n\t}\n\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn super.equals(o) && action == ((DistributionSet<?>) o).action;\n\t}\n\n\t/**\n\t * Returns the index of the distribution {@code d}, i.e. the position in the order given by the iterator of this set\n\t * @param d the distribution to look up\n\t * @return the index of {@code d} or -1 if not found\n\t */\n\tpublic int indexOf(Distribution<Value> d)\n\t{\n\t\tint i = -1;\n\t\tfor (Distribution<Value> itDist : this) {\n\t\t\ti++;\n\t\t\tif (itDist.equals(d)) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/DoubleIntervalDistribution.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\n/**\n * Flat storage of a distribution with probabilities as intervals of doubles\n */\npublic class DoubleIntervalDistribution\n{\n\tpublic int size;\n\tpublic double[] lower;\n\tpublic double[] upper;\n\tpublic int[] index;\n\n\tpublic DoubleIntervalDistribution(int size)\n\t{\n\t\tthis.size = size;\n\t\tthis.lower = new double[size];\n\t\tthis.upper = new double[size];\n\t\tthis.index = new int[size];\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tif (i > 0) s += \" + \";\n\t\t\ts += \"[\" + lower[i] + \",\" + upper[i] + \"]:\" + index[i];\n\t\t}\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ECComputer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.List;\n\nimport prism.PrismComponent;\nimport prism.PrismException;\n\n/**\n * Abstract class for (explicit) classes that compute (M)ECs, i.e. (maximal) end components,\n * for a nondeterministic model such as an MDP.\n */\npublic abstract class ECComputer extends PrismComponent\n{\n\t/**\n\t * Static method to create a new ECComputer object, depending on current settings.\n\t */\n\tpublic static ECComputer createECComputer(PrismComponent parent, NondetModel<?> model) throws PrismException\n\t{\n\t\t// Only one algorithm implemented currently\n\t\treturn new ECComputerDefault(parent, model);\n\t}\n\n\t/**\n\t * Base constructor.\n\t */\n\tpublic ECComputer(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Compute states of maximal end components (MECs) and store them.\n\t * They can be retrieved using {@link #getMECStates()}.\n\t */\n\tpublic abstract void computeMECStates() throws PrismException;\n\n\t/**\n\t * Compute states of all maximal end components (MECs) in the submodel obtained\n\t * by restricting this one to the set of states {@code restrict}, and store them.\n\t * They can be retrieved using {@link #getMECStates()}.\n\t * If {@code restrict} is null, we look at the whole model, not a submodel.\n\t * @param restrict BitSet for the set of states to restrict to.\n\t */\n\tpublic abstract void computeMECStates(BitSet restrict) throws PrismException;\n\n\t/**\n\t * Compute states of all accepting maximal end components (MECs) in the submodel obtained\n\t * by restricting this one to the set of states {@code restrict}, and store them,\n\t * where acceptance is defined as those which intersect with {@code accept}.\n\t * They can be retrieved using {@link #getMECStates()}.\n\t * If {@code restrict} is null, we look at the whole model, not a submodel.\n\t * If {@code accept} is null, the acceptance condition is trivially satisfied.\n\t * @param restrict BitSet for the set of states to restrict to\n\t * @param accept BitSet for the set of accepting states\n\t */\n\tpublic abstract void computeMECStates(BitSet restrict, BitSet accept) throws PrismException;\n\t\n\t/**\n\t * Get the list of states for computed MECs.\n\t */\n\tpublic abstract List<BitSet> getMECStates();\n}\n"
  },
  {
    "path": "prism/src/explicit/ECComputerDefault.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Mateusz Ujma <mateusz.ujma@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\n\nimport prism.PrismComponent;\nimport prism.PrismException;\n\n/**\n * Explicit maximal end component computer for a nondeterministic model such as an MDP.\n * Implements the algorithm from p.48 of:\n * Luca de Alfaro. Formal Verification of Probabilistic Systems. Ph.D. thesis, Stanford University (1997)\n */\npublic class ECComputerDefault extends ECComputer\n{\n\t/** The model to compute (M)ECs for **/\n\tprivate NondetModel<?> model;\n\n\t/** Computed list of MECs **/\n\tprivate List<BitSet> mecs = new ArrayList<BitSet>();\n\n\t/**\n\t * Build (M)EC computer for a given model.\n\t */\n\tpublic ECComputerDefault(PrismComponent parent, NondetModel<?> model) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tthis.model = model;\n\t}\n\n\t// Methods for ECComputer interface\n\n\t@Override\n\tpublic void computeMECStates() throws PrismException\n\t{\n\t\tmecs = findEndComponents(null, null);\n\t}\n\n\t@Override\n\tpublic void computeMECStates(BitSet restrict) throws PrismException\n\t{\n\t\tmecs = findEndComponents(restrict, null);\n\t}\n\n\t@Override\n\tpublic void computeMECStates(BitSet restrict, BitSet accept) throws PrismException\n\t{\n\t\tmecs = findEndComponents(restrict, accept);\n\t}\n\n\t@Override\n\tpublic List<BitSet> getMECStates()\n\t{\n\t\treturn mecs;\n\t}\n\n\t// Computation\n\t\n\t/**\n\t * Find all accepting maximal end components (MECs) in the submodel obtained\n\t * by restricting this one to the set of states {@code restrict},\n\t * where acceptance is defined as those which intersect with {@code accept}.\n\t * If {@code restrict} is null, we look at the whole model, not a submodel.\n\t * If {@code accept} is null, the acceptance condition is trivially satisfied.\n\t * @param restrict BitSet for the set of states to restrict to\n\t * @param accept BitSet for the set of accepting states\n\t * @return a list of BitSets representing the MECs\n\t */\n\tprivate List<BitSet> findEndComponents(BitSet restrict, BitSet accept) throws PrismException\n\t{\n\t\t// If restrict is null, look within set of all reachable states\n\t\tif (restrict == null) {\n\t\t\trestrict = new BitSet();\n\t\t\trestrict.set(0, model.getNumStates());\n\t\t}\n\t\t// Initialise L with set of all states to look in (if non-empty)\n\t\tList<BitSet> L = new ArrayList<BitSet>();\n\t\tif (restrict.isEmpty())\n\t\t\treturn L;\n\t\tL.add(restrict);\n\t\t// Find MECs\n\t\tboolean changed = true;\n\t\twhile (changed) {\n\t\t\tchanged = false;\n\t\t\tBitSet E = L.remove(0);\n\t\t\tSubNondetModel<?> submodel = restrict(model, E);\n\t\t\tList<BitSet> sccs = translateStates(submodel, computeSCCs(submodel));\n\t\t\tL = replaceEWithSCCs(L, E, sccs);\n\t\t\tchanged = canLBeChanged(L, E);\n\t\t}\n\t\t// Filter and return those that contain a state in accept\n\t\tif (accept != null) {\n\t\t\tint i = 0;\n\t\t\twhile (i < L.size()) {\n\t\t\t\tif (!L.get(i).intersects(accept)) {\n\t\t\t\t\tL.remove(i);\n\t\t\t\t} else {\n\t\t\t\t\ti++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn L;\n\t}\n\n\tprivate Set<BitSet> processedSCCs = new HashSet<BitSet>();\n\n\tprivate boolean canLBeChanged(List<BitSet> L, BitSet E)\n\t{\n\t\tprocessedSCCs.add(E);\n\t\tfor (int i = 0; i < L.size(); i++) {\n\t\t\tif (!processedSCCs.contains(L.get(i))) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\tprivate List<BitSet> replaceEWithSCCs(List<BitSet> L, BitSet E, List<BitSet> sccs)\n\t{\n\t\tif (sccs.size() > 0) {\n\t\t\tList<BitSet> toAdd = new ArrayList<BitSet>();\n\t\t\tfor (int i = 0; i < sccs.size(); i++) {\n\t\t\t\tif (!L.contains(sccs.get(i))) {\n\t\t\t\t\ttoAdd.add(sccs.get(i));\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (toAdd.size() > 0) {\n\t\t\t\tL.addAll(toAdd);\n\t\t\t}\n\t\t}\n\t\treturn L;\n\t}\n\n\tprivate SubNondetModel<?> restrict(NondetModel<?> model, BitSet states)\n\t{\n\t\tMap<Integer, BitSet> actions = new HashMap<Integer, BitSet>();\n\t\tBitSet initialStates = new BitSet();\n\t\tinitialStates.set(states.nextSetBit(0));\n\n\t\tboolean changed = true;\n\t\twhile (changed) {\n\t\t\tchanged = false;\n\t\t\tactions.clear();\n\t\t\tfor (int i = 0; i < model.getNumStates(); i++) {\n\t\t\t\tBitSet act = new BitSet();\n\t\t\t\tif (states.get(i)) {\n\t\t\t\t\tfor (int j = 0; j < model.getNumChoices(i); j++) {\n\t\t\t\t\t\tif (model.allSuccessorsInSet(i, j, states)) {\n\t\t\t\t\t\t\tact.set(j);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (act.isEmpty()) {\n\t\t\t\t\t\tstates.clear(i);\n\t\t\t\t\t\tchanged = true;\n\t\t\t\t\t}\n\t\t\t\t\tactions.put(i, act);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn new SubNondetModel<>(model, states, actions, initialStates);\n\t}\n\n\tprivate List<BitSet> computeSCCs(NondetModel<?> model) throws PrismException\n\t{\n\t\tSCCConsumerStore sccs = new SCCConsumerStore();\n\t\tSCCComputer sccc = SCCComputer.createSCCComputer(this, model, sccs);\n\t\tsccc.computeSCCs();\n\t\treturn sccs.getSCCs();\n\t}\n\n\tprivate List<BitSet> translateStates(SubNondetModel<?> model, List<BitSet> sccs)\n\t{\n\t\tList<BitSet> r = new ArrayList<BitSet>();\n\t\tfor (int i = 0; i < sccs.size(); i++) {\n\t\t\tBitSet set = sccs.get(i);\n\t\t\tBitSet set2 = new BitSet();\n\t\t\tr.add(set2);\n\t\t\tfor (int j = set.nextSetBit(0); j >= 0; j = set.nextSetBit(j + 1)) {\n\t\t\t\tset2.set(model.translateState(j));\n\n\t\t\t}\n\t\t}\n\t\treturn r;\n\t}\n\n\tprivate boolean isMEC(BitSet b)\n\t{\n\t\tif (b.isEmpty())\n\t\t\treturn false;\n\n\t\tint state = b.nextSetBit(0);\n\t\twhile (state != -1) {\n\t\t\tboolean atLeastOneAction = false;\n\t\t\tfor (int i = 0; i < model.getNumChoices(state); i++) {\n\t\t\t\tif (model.allSuccessorsInSet(state, i, b)) {\n\t\t\t\t\tatLeastOneAction = true;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!atLeastOneAction) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tstate = b.nextSetBit(state + 1);\n\t\t}\n\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ExplicitFiles2Model.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham) \n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\nimport common.Interval;\nimport io.ExplicitModelImporter;\nimport parser.EvaluateContext;\nimport parser.State;\nimport parser.VarList;\nimport prism.Evaluator;\nimport prism.ModelInfo;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\n\n/**\n * Class to convert explicit-state file storage of a model to a model of the explicit engine.\n */\npublic class ExplicitFiles2Model extends PrismComponent\n{\n\t// Should deadlocks be fixed (by adding a self-loop) when detected?\n\tprivate boolean fixdl;\n\n\t// Label bitsets\n\tprivate List<BitSet> labelBitSets;\n\t\n\t/** Constructor */\n\tpublic ExplicitFiles2Model(PrismComponent parent)\n\t{\n\t\tsuper(parent);\n\t\tif (settings != null) {\n\t\t\tsetFixDeadlocks(settings.getBoolean(PrismSettings.PRISM_FIX_DEADLOCKS));\n\t\t}\n\t}\n\n\t/**\n\t * Are deadlocks fixed (by adding a self-loop) when detected?\n\t */\n\tpublic boolean getFixDeadlocks()\n\t{\n\t\treturn fixdl;\n\t}\n\n\t/**\n\t * Should deadlocks be fixed (by adding a self-loop) when detected?\n\t */\n\tpublic void setFixDeadlocks(boolean fixdl)\n\t{\n\t\tthis.fixdl = fixdl;\n\t}\n\n\t/**\n\t * Build a Model corresponding to the passed in explicit files importer.\n\t * The transition probabilities/rates are assumed to be of type double.\n\t * @param  modelImporter Importer from files\n\t */\n\tpublic Model<Double> build(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\treturn build(modelImporter, Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Build a Model corresponding to the passed in explicit files importer.\n\t * The transition probabilities/rates are assumed to be of type Value.\n\t * @param  modelImporter Importer from files\n\t * @param eval Evaluator for Value objects\n\t */\n\tpublic <Value> Model<Value> build(ExplicitModelImporter modelImporter, Evaluator<Value> eval) throws PrismException\n\t{\n\t\t// Check model is defined as doubles\n\t\tif (modelImporter.modelIsExact() && !eval.exact()) {\n\t\t\tthrow new PrismException(\"Cannot import an exact model unless in exact mode\");\n\t\t}\n\n\t\tmodelImporter.setFixDeadlocks(fixdl);\n\t\tModelExplicit<Value> model = null;\n\t\tModelInfo modelInfo = modelImporter.getModelInfo();\n\t\tboolean isDbl = eval.one() instanceof Double;\n\t\tswitch (modelInfo.getModelType()) {\n\t\tcase DTMC:\n\t\t\tDTMC<Value> dtmc = isDbl ? (DTMC<Value>) new DTMCSparse() : new DTMCSimple<>();\n\t\t\tmodel = (ModelExplicit<Value>) dtmc;\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tCTMCSimple<Value> ctmc = new CTMCSimple<>();\n\t\t\tmodel = ctmc;\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tMDP<Value> mdp = isDbl ? (MDP<Value>) new MDPSparse() : new MDPSimple<>();\n\t\t\tmodel = (ModelExplicit<Value>) mdp;\n\t\t\tbreak;\n\t\tcase POMDP:\n\t\t\tPOMDP<Value> pomdp = new POMDPSimple<>();\n\t\t\tmodel = (ModelExplicit<Value>) pomdp;\n\t\t\tbreak;\n\t\tcase IDTMC:\n\t\t\tIDTMCSimple<Value> idtmc = new IDTMCSimple<>();\n\t\t\tmodel = (ModelExplicit<Value>) idtmc;\n\t\t\tbreak;\n\t\tcase IMDP:\n\t\t\tIMDPSimple<Value> imdp = new IMDPSimple<>();\n\t\t\tmodel = (ModelExplicit<Value>) imdp;\n\t\t\tbreak;\n\t\tcase IPOMDP:\n\t\t\tIPOMDPSimple<Value> ipomdp = new IPOMDPSimple<>();\n\t\t\tmodel = (ModelExplicit<Value>) ipomdp;\n\t\t\tbreak;\n\t\tcase LTS:\n\t\t\tLTS<Value> lts = new LTSSimple<>();\n\t\t\tmodel = (ModelExplicit<Value>) lts;\n\t\t\tbreak;\n\t\tcase CTMDP:\n\t\tcase PTA:\n\t\tcase SMG:\n\t\tcase STPG:\n\t\t\tthrow new PrismNotSupportedException(\"Currently, importing \" + modelInfo.getModelType() + \" is not supported\");\n\t\t}\n\t\tif (model == null) {\n\t\t\tthrow new PrismException(\"Could not import \" + modelInfo.getModelType());\n\t\t}\n\t\tmodel.setEvaluator(eval);\n\t\tif (model instanceof IntervalModelExplicit) {\n\t\t\t((IntervalModelExplicit<Value>) model).setIntervalEvaluator(eval.createIntervalEvaluator());\n\t\t}\n\t\tList<Object> actions = modelInfo.getActions();\n\t\tif (actions != null) {\n\t\t\tmodel.setActions(actions);\n\t\t}\n\t\tmodel.buildFromExplicitImport(modelImporter);\n\n\t\tif (model.getNumStates() == 0) {\n\t\t\tthrow new PrismNotSupportedException(\"Imported model has no states, not supported\");\n\t\t}\n\n\t\tloadLabelsAndInitialStates(modelImporter, model);\n\t\tif (!model.getInitialStates().iterator().hasNext()) {\n\t\t\tthrow new PrismException(\"Imported model has no initial states\");\n\t\t}\n\t\tBitSet deadlocks = modelImporter.getDeadlockStates();\n\t\tfor (int s = deadlocks.nextSetBit(0); s >= 0; s = deadlocks.nextSetBit(s + 1)) {\n\t\t\tmodel.addDeadlockState(s);\n\t\t}\n\n\t\tloadStates(modelImporter, model);\n\t\tif (model.getModelType().partiallyObservable()) {\n\t\t\tloadObservationDefinitions(modelImporter, (PartiallyObservableModel<Value>) model);\n\t\t}\n\n\t\treturn model;\n\t}\n\n\t/**\n\t * Load the label information and attach to the model.\n\t * The \"init\" label states become the initial states of the model.\n\t * The \"deadlock\" label is ignored - this info is recomputed.\n\t */\n\tprivate void loadLabelsAndInitialStates(ExplicitModelImporter modelImporter, ModelExplicit<?> model) throws PrismException\n\t{\n\t\t// Create BitSets to store label info\n\t\tModelInfo modelInfo = modelImporter.getModelInfo();\n\t\tint numLabels = modelInfo.getNumLabels();\n\t\tlabelBitSets = new ArrayList<>(numLabels);\n\t\tfor (int l = 0; l < numLabels; l++) {\n\t\t\tlabelBitSets.add(new BitSet());\n\t\t}\n\t\t// Extract info\n\t\tmodelImporter.extractLabelsAndInitialStates((s, l) -> labelBitSets.get(l).set(s), model::addInitialState, model::addDeadlockState);\n\t\t// Attach labels to model\n\t\tfor (int l = 0; l < numLabels; l++) {\n\t\t\tmodel.addLabel(modelInfo.getLabelName(l), labelBitSets.get(l));\n\t\t}\n\t}\n\n\t/**\n\t * Load the state information, construct the statesList and attach to model\n\t */\n\tprivate void loadStates(ExplicitModelImporter modelImporter, ModelExplicit<?> model) throws PrismException\n\t{\n\t\tint numStates = model.getNumStates();\n\t\tint numVars = modelImporter.getModelInfo().getNumVars();\n\t\tList<State> statesList = new ArrayList<>(numStates);\n\t\tModelInfo modelInfo = modelImporter.getModelInfo();\n\t\tEvaluateContext.EvalMode evalMode = model.getEvaluator().evalMode();\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tstatesList.add(new State(numVars));\n\t\t}\n\t\tmodelImporter.extractStates(\n\t\t\t\t(s, i, v) -> statesList.get(s).setValue(i, modelInfo.getVarType(i).castValueTo(v, evalMode))\n\t\t);\n\t\tmodel.setStatesList(statesList);\n\t}\n\n\t/**\n\t * Load the observation information, and store in model\n\t */\n\tprivate void loadObservationDefinitions(ExplicitModelImporter modelImporter, PartiallyObservableModel<?> model) throws PrismException\n\t{\n\t\tint numObservations = model.getNumObservations();\n\t\tint numObservables = modelImporter.getModelInfo().getNumObservables();\n\t\tList<State> observationsList = new ArrayList<>(numObservations);\n\t\tfor (int i = 0; i < numObservations; i++) {\n\t\t\tobservationsList.add(new State(numObservables));\n\t\t}\n\t\tmodelImporter.extractObservationDefinitions((o, i, v) -> observationsList.get(o).setValue(i, v));\n\t\tmodel.setObservationsList(observationsList);\n\t\tList<State> statesList = model.getStatesList();\n\t\tif (statesList != null) {\n\t\t\tmodel.setUnobservationsList(new ArrayList<>(statesList));\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't load observation definitions without a states list\");\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ExplicitFiles2Rewards.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2019-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t* Ludwig Pauly <ludwigpauly@gmail.com> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport explicit.rewards.Rewards;\nimport explicit.rewards.Rewards2RewardGenerator;\nimport explicit.rewards.RewardsSimple;\nimport io.ExplicitModelImporter;\nimport io.IOUtils;\nimport prism.Evaluator;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.RewardGenerator;\n\n/**\n * Class to import rewards from explicit files and expose them via a {@link RewardGenerator}.\n */\npublic class ExplicitFiles2Rewards<Value> extends PrismComponent\n{\n\t// Importer from files\n\tprotected ExplicitModelImporter importer;\n\t// Model that rewards are for\n\tprotected Model<Value> model;\n\t// Evaluator for reward values\n\tprotected Evaluator<Value> eval;\n\t// Local reward storage\n\tprotected RewardsSimple<Value>[] rewards;\n\n\t/**\n\t * Construct a ExplicitFiles2Rewards object for a specified importer/model.\n\t * The rewards are actually imported/stored later, on demand.\n\t * The evaluator for rewards is extracted from the model.\n\t */\n\tpublic ExplicitFiles2Rewards(PrismComponent parent, ExplicitModelImporter importer, Model<Value> model) throws PrismException\n\t{\n\t\tthis(parent, importer, model, model.getEvaluator());\n\t}\n\n\t/**\n\t * Construct a ExplicitFiles2Rewards object for a specified importer.\n\t * The rewards are actually imported/stored later, on demand.\n\t */\n\tpublic ExplicitFiles2Rewards(PrismComponent parent, ExplicitModelImporter importer, Model<?> model, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tthis.importer = importer;\n\t\tthis.model = (Model<Value>) model;\n\t\tthis.eval = eval;\n\t\t// Pass model to importer\n\t\tthis.importer.setModel(this.model);\n\t\t// Initialise storage\n\t\trewards = new RewardsSimple[importer.getRewardInfo().getNumRewardStructs()];\n\t}\n\n\t/**\n\t * Get access to the rewards, as a {@link RewardGenerator}.\n\t */\n\tpublic RewardGenerator<Value> getRewardGenerator() throws PrismException\n\t{\n\t\treturn new Rewards2RewardGenerator<Value>(importer.getRewardInfo(), model, eval)\n\t\t{\n\t\t\t@Override\n\t\t\tpublic Rewards<Value> getTheRewardObject(int r) throws PrismException\n\t\t\t{\n\t\t\t\treturn ExplicitFiles2Rewards.this.getTheRewardObject(r);\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Provide the rewards when requested, importing them from the explicit files.\n\t */\n\tprotected Rewards<Value> getTheRewardObject(int r) throws PrismException\n\t{\n\t\t// Lazily load rewards from file when requested\n\t\tif (rewards[r] == null) {\n\t\t\trewards[r] = new RewardsSimple<>(importer.getNumStates());\n\t\t\trewards[r].setEvaluator(eval);\n\t\t\timporter.extractStateRewards(r, (i, v) -> storeStateReward(r, i, v), eval);\n\t\t\tif (!model.getModelType().nondeterministic()) {\n\t\t\t\timporter.extractMCTransitionRewards(r, (s, s2, v) -> storeMCTransitionReward(r, s, s2, v), eval);\n\t\t\t} else {\n\t\t\t\timporter.extractMDPTransitionRewards(r, (s, i, v) -> storeMDPTransitionReward(r, s, i, v), eval);\n\t\t\t}\n\t\t}\n\t\treturn rewards[r];\n\t}\n\n\t// Methods to create local reward storage\n\n\t/**\n\t * Store a state reward.\n\t * @param r Reward structure index\n\t * @param s State index\n\t * @param v Reward value\n\t */\n\tprotected void storeStateReward(int r, int s, Value v)\n\t{\n\t\trewards[r].setStateReward(s, v);\n\t}\n\n\t/**\n\t * Store a (Markov chain) transition reward.\n\t * @param r Reward structure index\n\t * @param s State index (source)\n\t * @param s2 State index (destination)\n\t * @param v Reward value\n\t */\n\tprotected void storeMCTransitionReward(int r, int s, int s2, Value v)\n\t{\n\t\trewards[r].setTransitionReward(s, s2, v);\n\t}\n\n\t/**\n\t * Store a (MDP) transition reward.\n\t * @param r Reward structure index\n\t * @param s State index (source)\n\t * @param i Choice index\n\t * @param v Reward value\n\t */\n\tprotected void storeMDPTransitionReward(int r, int s, int i, Value v)\n\t{\n\t\trewards[r].setTransitionReward(s, i, v);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ExportIterations.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.HashMap;\n\nimport dv.DoubleVector;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\n\n/**\n * Class for exporting / visualising the value vectors in\n * a numerical iteration algorithm.\n *\n */\npublic class ExportIterations {\n\tprivate static String defaultFilename = \"iterations.html\";\n\n\tprivate PrismLog log;\n\n\t/** A hashmap for generating unique filenames */\n\tprivate static HashMap<String, Integer> counts = new HashMap<>();\n\n\tpublic ExportIterations(String title) throws PrismException\n\t{\n\t\tthis(title, PrismFileLog.create(defaultFilename));\n\t}\n\n\t/**\n\t * Constructor.\n\t * @param log the log used for export\n\t */\n\tpublic ExportIterations(String title, PrismLog log)\n\t{\n\t\tthis.log = log;\n\n\t\tlog.println(\"<!DOCTYPE html>\");\n\t\tlog.println(\"<html><head>\");\n\t\tlog.println(\"<meta charset=\\\"utf-8\\\">\");\n\t\tlog.println(\"<!-- HTML file automatically generated by the PRISM model checker -->\");\n\t\tlog.println(\"<!-- For visualising the individual steps of a value iteration computation -->\");\n\t\tlog.println(\"<!-- Loads supporting Javascript and CSS from www.prismmodelchecker.org -->\");\n\t\tlog.println(\"<title>\" + title + \"</title>\");\n\t\tlog.println(\"<link rel='stylesheet' href='https://www.prismmodelchecker.org/js/res/iteration-vis-v1.css'>\");\n\t\tlog.println(\"<script src=\\\"https://www.prismmodelchecker.org/js/res/d3.js-v4/d3.min.js\\\"></script>\");\n\t\tlog.println(\"<body onload='init();'>\");\n\t\tlog.println(\"<h1>\" + title + \"</h1>\");\n\t\tlog.println(\"<svg></svg>\");\n\t\tlog.println(\"<script src=\\\"https://www.prismmodelchecker.org/js/res/iteration-vis-v1.js\\\"></script>\");\n\t\tlog.flush();\n\t}\n\n\t/**\n\t * Returns the name of the file used for exporting,\n\t * or {@code null} if it can not be determined.\n\t */\n\tpublic String getFileName()\n\t{\n\t\tif (log instanceof PrismFileLog) {\n\t\t\treturn ((PrismFileLog)log).getFileName();\n\t\t}\n\t\treturn null;\n\t}\n\n\t/**\n\t * Export the given vector.\n\t * @param soln the value vector\n\t */\n\tpublic void exportVector(double[] soln)\n\t{\n\t\texportVector(soln, 0);\n\t}\n\n\t/**\n\t * Export the given vector.\n\t * @param soln the value vector\n\t * @param type the vector type (0 = normal, VI from below, 1 = VI from above)\n\t */\n\tpublic void exportVector(double[] soln, int type)\n\t{\n\t\tlog.print(\"<script>addVector([\");\n\t\tfor (int i = 0; i < soln.length; i++) {\n\t\t\tif (i>0) log.print(\",\");\n\t\t\tdouble d = soln[i];\n\t\t\texportValue(d);\n\t\t}\n\t\tlog.print(\"],\" + type + \")</script>\\n\");\n\t\tlog.flush();\n\t}\n\n\t/**\n\t * Export the given vector.\n\t * @param soln the value vector\n\t */\n\tpublic void exportVector(DoubleVector soln)\n\t{\n\t\texportVector(soln, 0);\n\t}\n\n\t/**\n\t * Export the given vector.\n\t * @param soln the value vector\n\t * @param type the vector type (0 = normal, VI from below, 1 = VI from above)\n\t */\n\tpublic void exportVector(DoubleVector soln, int type)\n\t{\n\t\tlog.print(\"<script>addVector([\");\n\t\tfor (int i = 0, n = soln.getSize(); i < n; i++) {\n\t\t\tif (i>0) log.print(\",\");\n\t\t\tdouble d = soln.getElement(i);\n\t\t\texportValue(d);\n\t\t}\n\t\tlog.print(\"],\" + type + \")</script>\\n\");\n\t\tlog.flush();\n\t}\n\n\tprivate void exportValue(double d)\n\t{\n\t\tif (d == Double.POSITIVE_INFINITY) {\n\t\t\tlog.print(\"Infinity\");\n\t\t} else if (d == Double.NEGATIVE_INFINITY) {\n\t\t\tlog.print(\"-Infinity\");\n\t\t} else {\n\t\t\tlog.print(d);\n\t\t}\n\t}\n\n\t/** Print footer, export log */\n\tpublic void close()\n\t{\n\t\tlog.println(\"\\n</body></html>\");\n\t\tlog.flush();\n\t}\n\n\t/**\n\t * Get a unique HTML file name with the given prefix, of the form\n\t * 'prefix-counter.html', where counter starts with 0 and\n\t * is incremented each time a unique filename with the same prefix is\n\t * requested.\n\t */\n\tpublic static String getUniqueFilename(String prefix)\n\t{\n\t\tint count = counts.getOrDefault(prefix, 0);\n\t\tcounts.put(prefix, count+1);\n\t\treturn prefix + \"-\" + count + \".html\";\n\t}\n\n\t/**\n\t * Create an ExportIterations helper with a unique filename generated\n\t * from {@code prefix} (see getUniqueFilename).\n\t */\n\tpublic static ExportIterations createWithUniqueFilename(String title, String prefix) throws PrismException\n\t{\n\t\treturn new ExportIterations(title, PrismFileLog.create(getUniqueFilename(prefix)));\n\t}\n\n\tpublic static void setDefaultFilename(String newDefaultFilename)\n\t{\n\t\tdefaultFilename = newDefaultFilename;\n\t}\n\n\tpublic static String getDefaultFilename()\n\t{\n\t\treturn defaultFilename;\n\t}\n\n\tpublic static void resetDefaultFilename()\n\t{\n\t\tdefaultFilename = \"iterations.html\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/FastAdaptiveUniformisation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//  * Frits Dannenberg <frits.dannenberg@cs.ox.ac.uk> (University of Oxford)\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.LinkedHashMap;\nimport java.util.List;\nimport java.util.ListIterator;\nimport java.util.Map;\n\nimport parser.State;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionIdent;\nimport parser.ast.LabelList;\nimport parser.ast.RewardStruct;\nimport prism.ModelGenerator;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismSettings;\n\n/*\n * TODO\n * - add options for state removal, e.g.\n *   - by delta (as current)\n *   - by max probability loss per iteration (requires sort by prob)\n *   - by max number of states (requires sort by prob)\n * - compress states to Bitset (memory waste currently excessive e.g. for mapk)\n * - do not delete states immediately but only after they have been below\n *   delta for a specified number of iterations to avoid deleting and exploring\n *   the same states over and over again\n * - dynamic adaption of interval width (with of 1 seems to work best, however)\n * - improve birth process - only worth it if we find case study where it makes a\n *   difference, but could contribute to publicability then\n * - plot number of active states over time for mapk to get idea of model behaviour\n * - in gen-dat.pl, mark runs as dead if we can derive that they cannot succeed\n * - discuss public interface with Dave\n * - make stop of deletion after half of Birth threshold reached optional\n * - check whether it's worth storing incoming transitions rather than outgoing\n *   would be faster, but edges are more costly to remove\n * - if we reach a point where we only delete states and don't add new ones, it\n *   might make sense to switch to array representation and ignore the fact that\n *   we could delete further states\n */\n\n/**\n * Implementation of fast adaptive uniformisation (FAU).\n */\npublic final class FastAdaptiveUniformisation extends PrismComponent\n{\n\t/**\n\t * Stores properties of states needed for fast adaptive method.\n\t * This includes the current-step probability, next-state probability,\n\t * and the transient probability (sum of step probabilities weighted\n\t * with birth process distributions). It also contains the list of successor\n\t * states and the rates to them, the number of incoming transitions\n\t * (references) and a flag whether the state has a significant probability\n\t * mass (alive).\n\t */\n\tprivate final static class StateProp\n\t{\n\t\t/** current-step probability.\n\t\t * should contain initial probability before actual analysis is started.\n\t\t * will contain transient probability after analysis. */\n\t\tprivate double prob;\n\t\t/** next-state probability */\n\t\tprivate double nextProb;\n\t\t/** sum probability weighted with birth process distribution */\n\t\tprivate double sum;\n\t\t/** reward of this state */\n\t\tprivate double reward;\n\t\t/** rates to successor states */\n\t\tprivate double[] succRates;\n\t\t/** successor states */\n\t\tprivate StateProp[] succStates;\n\t\t/** number of incoming transitions of relevant states */\n\t\tprivate int references;\n\t\t/** true if and only if state probability above relevance threshold */\n\t\tprivate boolean alive;\n\t\t\n\t\t/**\n\t\t * Constructs a new state property object.\n\t\t */\n\t\tStateProp()\n\t\t{\n\t\t\tprob = 0.0;\n\t\t\tnextProb = 0.0;\n\t\t\tsum = 0.0;\n\t\t\treward = 0.0;\n\t\t\tsuccRates = null;\n\t\t\tsuccStates = null;\n\t\t\treferences = 0;\n\t\t\talive = true;\n\t\t}\n\t\t\n\t\t/**\n\t\t * Set current state probability.\n\t\t * \n\t\t * @param prob current state probability to set\n\t\t */\n\t\tvoid setProb(double prob)\n\t\t{\n\t\t\tthis.prob = prob;\n\t\t}\n\n\t\t/**\n\t\t * Gets current state probability.\n\t\t * \n\t\t * @return current state probability\n\t\t */\n\t\tdouble getProb()\n\t\t{\n\t\t\treturn prob;\n\t\t}\n\n\t\t/**\n\t\t * Sets next state probability.\n\t\t * \n\t\t * @param nextProb next state probability to set\n\t\t */\n\t\tvoid setNextProb(double nextProb)\n\t\t{\n\t\t\tthis.nextProb = nextProb;\n\t\t}\n\n\t\t/**\n\t\t * Adds value to next state probability.\n\t\t * \n\t\t * @param add value to add to next state probability\n\t\t */\n\t\tvoid addToNextProb(double add)\n\t\t{\n\t\t\tthis.nextProb += add;\n\t\t}\n\n\t\t/**\n\t\t * Sets weighted sum probability.\n\t\t * \n\t\t * @param sum weighted sum probability to set.\n\t\t */\n\t\tvoid setSum(double sum)\n\t\t{\n\t\t\tthis.sum = sum;\n\t\t}\n\n\t\t/**\n\t\t * Adds current probability times {@code poisson} to weighted sum probability.\n\t\t * \n\t\t * @param poisson this value times current probability will be added to sum probability\n\t\t */\n\t\tvoid addToSum(double poisson)\n\t\t{\n\t\t\tsum += poisson * prob;\n\t\t}\n\n\t\t/**\n\t\t * Gets weighted sum probability.\n\t\t * \n\t\t * @return weighted sum probability\n\t\t */\n\t\tdouble getSum()\n\t\t{\n\t\t\treturn sum;\n\t\t}\n\n\t\t/**\n\t\t * Prepares next iteration step.\n\t\t * Sets current probability to next probability, and sets next\n\t\t * probability to zero.\n\t\t */\n\t\tvoid prepareNextIteration()\n\t\t{\n\t\t\tprob = nextProb;\n\t\t\tnextProb = 0.0;\n\t\t}\n\n\t\t/**\n\t\t * Set state reward.\n\t\t * \n\t\t * @param reward state reward to set\n\t\t */\n\t\tvoid setReward(double reward)\n\t\t{\n\t\t\tthis.reward = reward;\n\t\t}\n\n\t\t/**\n\t\t * Get state reward.\n\t\t * \n\t\t * @return state reward\n\t\t */\n\t\tdouble getReward()\n\t\t{\n\t\t\treturn reward;\n\t\t}\n\n\t\t/**\n\t\t * Sets rates to successor states.\n\t\t * Expects an array of rates, so that the rate to the successor\n\t\t * state set by {@setSuccStates} is the one given by the corresponding\n\t\t * index. The value {@code null} is allowed here.\n\t\t * \n\t\t * @param succRates rates to successor states.\n\t\t */\n\t\tvoid setSuccRates(double[] succRates)\n\t\t{\n\t\t\tthis.succRates = succRates;\n\t\t}\n\n\t\t/**\n\t\t * Sets successor states.\n\t\t * Expects an array of successor states, so that the rate set by\n\t\t * {@setSuccRates} is the one given by the corresponding index.\n\t\t * The value {@code null} is allowed here.\n\t\t * \n\t\t * @param succStates successor states\n\t\t */\n\t\tvoid setSuccStates(StateProp[] succStates)\n\t\t{\n\t\t\tthis.succStates = succStates;\n\t\t\tif (succStates != null) {\n\t\t\t\tfor (int succNr = 0; succNr < succStates.length; succNr++) {\n\t\t\t\t\tsuccStates[succNr].incReferences();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Returns number of successor states of this state.\n\t\t * \n\t\t * @return number of successor states\n\t\t */\n\t\tint getNumSuccs()\n\t\t{\n\t\t\tif (succRates == null) {\n\t\t\t\treturn 0;\n\t\t\t} else {\n\t\t\t\treturn succRates.length;\n\t\t\t}\n\t\t}\n\t\t\n\t\t/**\n\t\t * Gets successor rates.\n\t\t * \n\t\t * @return successor rates\n\t\t */\n\t\tdouble[] getSuccRates()\n\t\t{\n\t\t\treturn succRates;\n\t\t}\n\n\t\t/**\n\t\t * Gets successor states.\n\t\t * \n\t\t * @return successor states\n\t\t */\n\t\tStateProp[] getSuccStates()\n\t\t{\n\t\t\treturn succStates;\n\t\t}\n\n\t\t/**\n\t\t * Sets whether state is alive.\n\t\t * \n\t\t * @param alive whether state should be set to being alive\n\t\t */\n\t\tvoid setAlive(boolean alive)\n\t\t{\n\t\t\tthis.alive = alive;\n\t\t}\n\n\t\t/**\n\t\t * Checks whether state is alive.\n\t\t * \n\t\t * @return true iff state is alive\n\t\t */\n\t\tboolean isAlive()\n\t\t{\n\t\t\treturn alive;\n\t\t}\n\n\t\t/**\n\t\t * Increments the number of references of this state.\n\t\t * The number of references should correspond to the number of alive\n\t\t * states which have this state as successor state.\n\t\t */\n\t\tvoid incReferences()\n\t\t{\n\t\t\treferences++;\n\t\t}\n\n\t\t/**\n\t\t * Decrements the number of references of this state.\n\t\t * The number of references should correspond to the number of alive\n\t\t * states which have this state as successor state.\n\t\t */\n\t\tvoid decReferences()\n\t\t{\n\t\t\treferences--;\n\t\t}\n\n\t\t/**\n\t\t * Deletes this state.\n\t\t * This means basically removing all of its successors. Beforehand,\n\t\t * their reference counter is decreased, because this state does no\n\t\t * longer count as a model state. It is left in the model however,\n\t\t * because it might still be the successor state of some alive state.\n\t\t */\n\t\tvoid delete()\n\t\t{\n\t\t\tif (null != succStates) {\n\t\t\t\tfor (int succNr = 0; succNr < succStates.length; succNr++) {\n\t\t\t\t\tsuccStates[succNr].decReferences();\n\t\t\t\t}\n\t\t\t}\n\t\t\tsuccStates = null;\n\t\t\tsuccRates = null;\n\t\t\talive = false;\n\t\t\tprob = 0.0;\n\t\t\tnextProb = 0.0;\n\t\t}\n\n\t\t/**\n\t\t * Checks whether this state can be removed.\n\t\t * This is only the case if its probability is below the threshold\n\t\t * specified, and then only if there are no transitions from alive\n\t\t * states into this state.\n\t\t * \n\t\t * @return true if and only if this state can be removed\n\t\t */\n\t\tboolean canRemove()\n\t\t{\n\t\t\treturn !alive && (0 == references);\n\t\t}\n\n\t\t/**\n\t\t * Checks whether this state has successors or not.\n\t\t * Will be true if and only if successor state array is nonnull.\n\t\t * \n\t\t * @return whether this state has successors or not\n\t\t */\n\t\tboolean hasSuccs()\n\t\t{\n\t\t\treturn succStates != null;\n\t\t}\n\n\t\t/**\n\t\t * Returns the sum of all rates leaving to successor states.\n\t\t * \n\t\t * @return sum of all rates leaving to successor states\n\t\t */\n\t\tdouble sumRates()\n\t\t{\n\t\t\tif (null == succRates) {\n\t\t\t\treturn 0.0;\n\t\t\t}\n\t\t\tdouble sumRates = 0.0;\n\t\t\tfor (int rateNr = 0; rateNr < succRates.length; rateNr++) {\n\t\t\t\tsumRates += succRates[rateNr];\n\t\t\t}\n\t\t\treturn sumRates;\n\t\t}\n\t}\n\t\n\t/**\n\t * Enum to store type of analysis to perform.\n\t */\n\tpublic enum AnalysisType {\n\t\t/** transient probability distribution */\n\t\tTRANSIENT,\n\t\t/** reachability, for \"F\" or \"U\" PCTL operators */\n\t\tREACH,\n\t\t/** instantaneous rewards */\n\t\tREW_INST,\n\t\t/** cumulative rewards */\n\t\tREW_CUMUL\n\t}\n\n\t/** model exploration component to generate new states */\n\tprivate ModelGenerator<Double> modelGen;\n\t/** probability allowed to drop birth process */\n\tprivate double epsilon;\n\t/** probability threshold when to drop states in discrete-time process */\n\tprivate double delta;\n\t/** number of intervals to divide time into */\n\tprivate int numIntervals;\n\t/** iterations after which switch to sparse matrix if no new/dropped states */\n\tprivate int arrayThreshold;\n\t\n\t/** reward structure to use for analysis */\n\tprivate RewardStruct rewStruct = null;\n\t/** result value of analysis */\n\tprivate double value;\n\t/** model constants */\n\tprivate Values constantValues = null;\n\t/** maps from state (assignment of variable values) to property object */\n\tprivate LinkedHashMap<State,StateProp> states;\n\t/** states for which successor rates are to be computed */\n\tprivate ArrayList<State> addDistr;\n\t/** states which are to be deleted */\n\tprivate ArrayList<State> deleteStates;\n\t/** initial size of state hash map */\n\tprivate final int initSize = 3000;\n\t/** maximal total leaving rate of all states alive */\n\tprivate double maxRate = 0.0;\n\t/** target state set - used for reachability (until or finally properties) */\n\tprivate Expression target;\n\t/** number of consecutive iterations without new states are state drops */\n\tprivate int itersUnchanged;\n\t/** sum of probabilities in stages of birth process seen so far */\n\tprivate double birthProbSum;\n\t/** birth process used for time discretisation */\n\tprivate BirthProcess birthProc;\n\t/** states which fulfill this will be made absorbing - for until props */\n\tprivate Expression sink;\n\t/** if true, don't drop further states.\n\t * Used to avoid excessive probability loss in some cases. */\n\tprivate boolean keepSumProb;\n\t/** maximal number of states ever stored during analysis */\n\tprivate int maxNumStates;\n\t/** list of special labels we need to maintain, like \"init\", \"deadlock\", etc. */\n\tprivate LabelList specialLabels;\n\t/** set of initial states of the model */\n\tprivate HashSet<State> initStates;\n\t/** type of analysis to perform */\n\tprivate AnalysisType analysisType;\n\t/** total loss of probability in discrete-time process */\n\tprivate double totalProbLoss;\n\t/** probability mass intentionally set to zero */\n\tprivate double totalProbSetZero;\n\t\n\t/**\n\t * Constructor.\n\t */\n\tpublic FastAdaptiveUniformisation(PrismComponent parent, ModelGenerator<Double> modelGen) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\t\n\t\tthis.modelGen = modelGen;\n\t\tmaxNumStates = 0;\n\n\t\tepsilon = settings.getDouble(PrismSettings.PRISM_FAU_EPSILON);\n\t\tdelta = settings.getDouble(PrismSettings.PRISM_FAU_DELTA);\n\t\tnumIntervals = settings.getInteger(PrismSettings.PRISM_FAU_INTERVALS);\n\t\tarrayThreshold = settings.getInteger(PrismSettings.PRISM_FAU_ARRAYTHRESHOLD);\n\t\tanalysisType = AnalysisType.TRANSIENT;\n\t\trewStruct = null;\n\t\ttarget = Expression.False();\n\t\tsink = Expression.False();\n\t\tspecialLabels = new LabelList();\n\t\tspecialLabels.addLabel(new ExpressionIdent(\"deadlock\"), new ExpressionIdent(\"deadlock\"));\n\t\tspecialLabels.addLabel(new ExpressionIdent(\"init\"), new ExpressionIdent(\"init\"));\n\t}\n\n\t/**\n\t * Sets analysis type to perform.\n\t * \n\t * @param analysisType analysis type to perform\n\t */\n\tpublic void setAnalysisType(AnalysisType analysisType)\n\t{\n\t\tthis.analysisType = analysisType;\n\t}\n\n\t/**\n\t * Sets values for model constants.\n\t * \n\t * @param constantValues values for model constants\n\t */\n\tpublic void setConstantValues(Values constantValues)\n\t{\n\t\tthis.constantValues = constantValues;\n\t}\n\n\t/**\n\t * Sets reward structure to use.\n\t * \n\t * @param rewStruct reward structure to use\n\t */\n\tpublic void setRewardStruct(RewardStruct rewStruct)\n\t{\n\t\tthis.rewStruct = rewStruct;\n\t}\n\n\t/**\n\t * \n\t * @param target\n\t */\n\tpublic void setTarget(Expression target)\n\t{\n\t\tthis.target = target;\n\t}\n\t\n\t/**\n\t * Returns maximal number of states used during analysis.\n\t * \n\t * @return maximal number of states used during analysis\n\t */\n\tpublic int getMaxNumStates()\n\t{\n\t\treturn maxNumStates;\n\t}\n\n\t/**\n\t * Returns the value of the analysis.\n\t * For reachability analyses, this is the probability to reach state in\n\t * the reach set, for instantaneous reward properties this is the\n\t * instantaneous reward and for cumulative reward analysis it is the\n\t * cumulative reward. For the computation of transient probabilities\n\t * without doing model checking, this value is not significant.\n\t * \n\t * @return value of the analysis\n\t */\n\tpublic double getValue()\n\t{\n\t\treturn value;\n\t}\n\n\t/**\n\t * Sets which states shall be treated as sink states.\n\t * To be used for properties like \"a U<=T b\" where states \"b || !a\" have\n\t * to be made absorbing.\n\t * \n\t * @param sink expressing stating which states are sink states\n\t * @throws PrismException thrown if problems in underlying function occurs\n\t */\n\tpublic void setSink(Expression sink) throws PrismException\n\t{\n\t\tthis.sink = sink;\n\t\tif (states != null) {\n\t\t\tfor (Map.Entry<State,StateProp> statePair : states.entrySet()) {\n\t\t\t\tState state = statePair.getKey();\n\t\t\t\tStateProp prop = statePair.getValue();\n\t\t\t\tmodelGen.exploreState(state);\n\t\t\t\tspecialLabels.setLabel(0, modelGen.getNumTransitions() == 0 ? Expression.True() : Expression.False());\n\t\t\t\tspecialLabels.setLabel(1, initStates.contains(state) ? Expression.True() : Expression.False());\n\t\t\t\tExpression evSink = sink.deepCopy();\n\t\t\t\tevSink = (Expression) evSink.expandLabels(specialLabels);\n\t\t\t\tif (evSink.evaluateBoolean(constantValues, state)) {\n\t\t\t\t\tdouble[] succRates = new double[1];\n\t\t\t\t\tStateProp[] succStates = new StateProp[1];\n\t\t\t\t\tsuccRates[0] = 1.0;\n\t\t\t\t\tsuccStates[0] = states.get(state);\n\t\t\t\t\tprop.setSuccRates(succRates);\n\t\t\t\t\tprop.setSuccStates(succStates);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Get the number of states in the current window.\n\t */\n\tpublic int getNumStates()\n\t{\n\t\treturn states.size();\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doTransient(double time) throws PrismException\n\t{\n\t\treturn doTransient(time, (StateValues) null);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Use the passed in vector initDist as the initial probability distribution (time 0).\n\t * In case initDist is null starts at the default initial state with prob 1.\n\t * \n\t * @param time Time point\n\t * @param initDist Initial distribution\n\t */\n\tpublic StateValues doTransient(double time, StateValues initDist) throws PrismException\n\t{\n\t\tif (!modelGen.hasSingleInitialState())\n\t\t\tthrow new PrismException(\"Fast adaptive uniformisation does not yet support models with multiple initial states\");\n\t\t\n\t\tmainLog.println(\"\\nComputing probabilities (fast adaptive uniformisation)...\");\n\t\t\n\t\tif (initDist == null) {\n\t\t\tList<State> initStatesList = new ArrayList<>();\n\t\t\tinitStatesList.add(modelGen.getInitialState());\n\t\t\tinitDist = StateValues.createFromDoubleArray(new double[] { 1.0 }, initStatesList);\n\t\t}\n\t\t\n\t\t/* prepare fast adaptive uniformisation */\n\t\taddDistr = new ArrayList<State>();\n\t\tdeleteStates = new ArrayList<State>();\n\t\tstates = new LinkedHashMap<State,StateProp>(initSize);\n\t\tvalue = 0.0;\n\t\tinitStates = new HashSet<State>();\n\t\tListIterator<State> it = initDist.statesList.listIterator();\n\t\tdouble[] values = initDist.getDoubleArray();\n\t\tmaxRate = 0.0;\n\t\tfor (int stateNr = 0; stateNr < initDist.size; stateNr++) {\n\t\t\tState initState = it.next();\n\t\t\taddToModel(initState);\n\t\t}\n\t\tit = initDist.statesList.listIterator();\n\t\tfor (int stateNr = 0; stateNr < initDist.size; stateNr++) {\n\t\t\tState initState = it.next();\n\t\t\tcomputeStateRatesAndRewards(initState);\n\t\t\tstates.get(initState).setProb(values[stateNr]);\n\t\t\tmaxRate = Math.max(maxRate, states.get(initState).sumRates() * 1.02);\t\t\t\n\t\t}\n\n\t\t/* run fast adaptive uniformisation */\n\t\tcomputeTransientProbsAdaptive(time);\n\n\t\t/* prepare and return results */\n\t\tArrayList<State> statesList = new ArrayList<State>(states.size());\n\t\tdouble[] probsArr = new double[states.size()];\n\t\tint probsArrEntry = 0;\n\t\tfor (Map.Entry<State,StateProp> statePair : states.entrySet()) {\n\t\t\tstatesList.add(statePair.getKey());\n\t\t\tprobsArr[probsArrEntry] = statePair.getValue().getProb();\n\t\t\tprobsArrEntry++;\n\t\t}\n\t\tStateValues probs = StateValues.createFromDoubleArray(probsArr, statesList);\n\n\t\tmainLog.println(\"\\nTotal probability lost is : \" + getTotalDiscreteLoss());\n\t\tmainLog.println(\"Maximal number of states stored during analysis : \" + getMaxNumStates());\n\t\t\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute transient probabilities using fast adaptive uniformisation\n\t * Compute the probability of being in each state at time {@code t}.\n\t * If corresponding options are set, also computes cumulative rewards.\n\t * For space efficiency, the initial distribution vector will be modified and values over-written,  \n\t * so if you wanted it, take a copy. \n\t * @param time time point\n\t */\n\tpublic void computeTransientProbsAdaptive(double time) throws PrismException\n\t{\n\t\tif (addDistr == null) {\n\t\t\taddDistr = new ArrayList<State>();\n\t\t\tdeleteStates = new ArrayList<State>();\n\t\t\tstates = new LinkedHashMap<State,StateProp>(initSize);\n\t\t\tvalue = 0.0;\n\t\t\tprepareInitialDistribution();\n\t\t}\n\n\t\tdouble initIval = settings.getDouble(PrismSettings.PRISM_FAU_INITIVAL);\n\t\tif (time - initIval < 0.0) {\n\t\t\tinitIval = 0.0;\n\t\t}\n\t\tif (initIval != 0.0) {\n\t\t\titerateAdaptiveInterval(initIval);\n\t\t\tfor (StateProp prop : states.values()) {\n\t\t\t\tprop.setProb(prop.getSum());\n\t\t\t\tprop.setSum(0.0);\n\t\t\t\tprop.setNextProb(0.0);\n\t\t\t}\n\t\t\tupdateStates();\n\t\t}\n\n\t\tfor (int ivalNr = 0; ivalNr < numIntervals; ivalNr++) {\n\t\t\tdouble interval = (time - initIval) / numIntervals;\n\t\t\titerateAdaptiveInterval(interval);\n\t\t\tfor (StateProp prop : states.values()) {\n\t\t\t\tprop.setProb(prop.getSum());\n\t\t\t\tprop.setSum(0.0);\n\t\t\t\tprop.setNextProb(0.0);\n\t\t\t}\n\t\t\tupdateStates();\n\t\t}\n\t\tif (AnalysisType.REW_INST == analysisType) {\n\t\t\tfor (StateProp prop : states.values()) {\n\t\t\t\tvalue += prop.getProb() * prop.getReward();\n\t\t\t}\n\t\t} else {\n\t\t\tfor (Map.Entry<State,StateProp> statePair : states.entrySet()) {\n\t\t\t\tState state = statePair.getKey();\n\t\t\t\tStateProp prop = statePair.getValue();\n\t\t\t\tmodelGen.exploreState(state);\n\t\t\t\tspecialLabels.setLabel(0, modelGen.getNumTransitions() == 0 ? Expression.True() : Expression.False());\n\t\t\t\tspecialLabels.setLabel(1, initStates.contains(state) ? Expression.True() : Expression.False());\n\t\t\t\tExpression evTarget = target.deepCopy();\n\t\t\t\tevTarget = (Expression) evTarget.expandLabels(specialLabels);\n\t\t\t\tif (AnalysisType.REACH == analysisType) {\n\t\t\t\t\tvalue += prop.getProb() * (evTarget.evaluateBoolean(constantValues, state) ? 1.0 : 0.0);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Performs fast adaptive uniformisation for a single time interval.\n\t * \n\t * @param interval duration of time interval\n\t * @throws PrismException\n\t */\n\tprivate void iterateAdaptiveInterval(double interval) throws PrismException\n\t{\n\t\tbirthProc = new BirthProcess();\n\t\tbirthProc.setTime(interval);\n\t\tbirthProc.setEpsilon(epsilon);\n\n\t\tint iters = 0;\n\t\tbirthProbSum = 0.0;\n\t\titersUnchanged = 0;\n\t\tkeepSumProb = false;\n\t\twhile (birthProbSum < (1 - epsilon)) {\n\t\t\tif (birthProbSum >= epsilon/2) {\n\t\t\t\tkeepSumProb = true;\n\t\t\t}\n\t\t\tif ((itersUnchanged == arrayThreshold)) {\n\t\t\t\titers = arrayIterate(iters);\n\t\t\t} else {\n\t\t\t    long birthProcTimer = System.currentTimeMillis();\n\t\t\t\tdouble prob = birthProc.calculateNextProb(maxRate);\n\t\t\t\tbirthProcTimer = System.currentTimeMillis() - birthProcTimer;\n\t\t\t\tbirthProbSum += prob;\n\t\t\t\tcollectValuePostIter(prob, birthProbSum);\n\t\t\t\tfor (StateProp prop : states.values()) {\n\t\t\t\t\tprop.addToSum(prob);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tmvMult(maxRate);\n\t\t\t\tupdateStates();\n\t\t\t\titers++;\n\t\t\t}\n\t\t}\n\n\t\tcomputeTotalDiscreteLoss();\n\t}\n\n\t/**\n\t * Transforms the current submodel to array form.\n\t * In case there are no further changes in the states discovered, or\n\t * further states only become relevant after a large number of\n\t * iterations, this allows the analysis to be performed much faster.\n\t * After the analysis has finished or after it has to be terminated as\n\t * formerly irrelevant states become relevant, results are mapped back\n\t * to the original data structure. The method returns the current\n\t * iteration.\n\t * \n\t * In case border states become\n\t * relevant, this data structure can \n\t * \n\t * @param iters current iteration number\n\t * @return current iteration after termination of this method\n\t * @throws PrismException thrown if problems in underlying methods occur\n\t */\n\tprivate int arrayIterate(int iters) throws PrismException\n\t{\n\t\t/* build backwards matrix and map values */\n\t\tint numStates = states.size();\n\t\tint numTransitions = 0;\n\t\tfor (StateProp prop : states.values()) {\n\t\t\tnumTransitions += prop.getNumSuccs() + 1;\n\t\t}\n\t\tint stateNr = 0;\n\t\tHashMap<StateProp,Integer> stateToNumber = new HashMap<StateProp,Integer>(numStates);\n\t\tStateProp[] numberToState = new StateProp[numStates];\n\t\tfor (StateProp prop : states.values()) {\n\t\t\tif (prop.isAlive()) {\n\t\t\t\tstateToNumber.put(prop, stateNr);\n\t\t\t\tnumberToState[stateNr] = prop;\n\t\t\t\tstateNr++;\n\t\t\t}\n\t\t}\n\t\tint numAlive = stateNr;\n\t\tfor (StateProp prop : states.values()) {\n\t\t\tif (!prop.isAlive()) {\n\t\t\t\tstateToNumber.put(prop, stateNr);\n\t\t\t\tnumberToState[stateNr] = prop;\n\t\t\t\tstateNr++;\n\t\t\t}\n\t\t}\n\n\t\tdouble[] inProbs = new double[numTransitions];\n\t\tint[] rows = new int[numStates + 1];\n\t\tint[] cols = new int[numTransitions];\n\t\tdouble[] outRates = new double[numStates];\n\t\tfor (StateProp prop : states.values()) {\n\t\t\tStateProp[] succStates = prop.getSuccStates();\n\t\t\tif (succStates != null) {\n\t\t\t\tfor (StateProp succ : succStates) {\n\t\t\t\t\trows[stateToNumber.get(succ) + 1]++;\n\t\t\t\t}\n\t\t\t}\n\t\t\trows[stateToNumber.get(prop) + 1]++;\n\t\t}\n\t\tfor (stateNr = 0; stateNr < numStates; stateNr++) {\n\t\t\trows[stateNr + 1] += rows[stateNr];\n\t\t}\n\n\t\tfor (StateProp prop : states.values()) {\n\t\t\tint stateNumber = stateToNumber.get(prop);\n\t\t\tStateProp[] succStates = prop.getSuccStates();\n\t\t\tdouble[] succRates = prop.getSuccRates();\n\t\t\tif (succStates != null) {\n\t\t\t\tfor (int i = 0; i < succStates.length; i++) {\n\t\t\t\t\tStateProp succState = succStates[i];\n\t\t\t\t\tint succStateNumber = stateToNumber.get(succState);\n\t\t\t\t\tdouble succRate = succRates[i];\n\t\t\t\t\tcols[rows[succStateNumber]] = stateNumber;\n\t\t\t\t\tinProbs[rows[succStateNumber]] = succRate / maxRate;\n\t\t\t\t\trows[succStateNumber]++;\n\t\t\t\t\toutRates[stateNumber] += succRate;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tfor (stateNr = 0; stateNr < numStates; stateNr++) {\n\t\t\tcols[rows[stateNr]] = stateNr;\n\t\t\tinProbs[rows[stateNr]] = (maxRate - outRates[stateNr]) / maxRate;\n\t\t}\n\n\t\tArrays.fill(rows, 0);\n\t\tfor (StateProp prop : states.values()) {\n\t\t\tStateProp[] succStates = prop.getSuccStates();\n\t\t\tif (succStates != null) {\n\t\t\t\tfor (StateProp succ : succStates) {\n\t\t\t\t\trows[stateToNumber.get(succ) + 1]++;\n\t\t\t\t}\n\t\t\t}\n\t\t\trows[stateToNumber.get(prop) + 1]++;\n\t\t}\n\t\tfor (stateNr = 0; stateNr < numStates; stateNr++) {\n\t\t\trows[stateNr + 1] += rows[stateNr];\n\t\t}\n\n\t\tdouble[] rewards = new double[numStates];\n\t\tdouble[] probs = new double[numStates];\n\t\tdouble[] nextProbs = new double[numStates];\n\t\tdouble[] sum = new double[numStates];\n\t\tfor (stateNr = 0; stateNr < numberToState.length; stateNr++) {\n\t\t\tStateProp prop = numberToState[stateNr];\n\t\t\tif (analysisType == AnalysisType.REW_CUMUL) {\n\t\t\t\trewards[stateNr] = prop.getReward();\n\t\t\t}\n\t\t\tprobs[stateNr] = prop.getProb();\n\t\t\tsum[stateNr] = prop.getSum();\n\t\t}\n\n\t\t/* iterate using matrix */\n\t\tboolean canArray = true;\n\t\twhile (birthProbSum < (1 - epsilon) && canArray) {\n\t\t\t//\t\t\ttimer2 = System.currentTimeMillis();\n\t\t\tdouble prob = birthProc.calculateNextProb(maxRate);\n\t\t\tbirthProbSum += prob;\n\t\t\tdouble mixed = (1.0 - birthProbSum) / maxRate;\n\t\t\tfor (stateNr = 0; stateNr < numStates; stateNr++) {\n\t\t\t\tvalue += probs[stateNr] * mixed * rewards[stateNr];\n\t\t\t\tsum[stateNr] += prob * probs[stateNr];\n\t\t\t\tnextProbs[stateNr] = 0.0;\n\t\t\t\tfor (int succNr = rows[stateNr]; succNr < rows[stateNr+1]; succNr++) {\n\t\t\t\t\tnextProbs[stateNr] += inProbs[succNr] * probs[cols[succNr]];\n\t\t\t\t}\n\t\t\t\tif ((stateNr < numAlive) != (nextProbs[stateNr] > delta)) {\n\t\t\t\t\tcanArray = false;\n\t\t\t\t} else if (stateNr >= numAlive) {\n\t\t\t\t    nextProbs[stateNr] = 0.0;\n\t\t\t\t}\n\t\t\t}\n\t\t\tdouble[] swap = probs;\n\t\t\tprobs = nextProbs;\n\t\t\tnextProbs = swap;\n\n\t\t\titers++;\n\t\t}\n\t\t\n\t\t/* map back, update states and return current iteration */\n\t\tfor (stateNr = 0; stateNr < numberToState.length; stateNr++) {\n\t\t\tStateProp prop = numberToState[stateNr];\n\t\t\tprop.setProb(probs[stateNr]);\n\t\t\tprop.setSum(sum[stateNr]);\n\t\t}\n\t\tupdateStates();\n\t\treturn iters;\n\t}\n\n\t/**\n\t * Update analysis value after iteration.\n\t * For certain analyses (currently cumulative rewards) we have to modify\n\t * the analysis value after each iteration.\n\t * \n\t * @param prob\n\t * @param probSum\n\t */\n\tprivate void collectValuePostIter(double prob, double probSum)\n\t{\n\t\tswitch (analysisType) {\n\t\tcase TRANSIENT:\n\t\t\t// nothing to do here, we're just computing distributions\n\t\t\tbreak;\n\t\tcase REACH:\n\t\t\t// nothing to do here, we're collecting values later on\n\t\t\tbreak;\n\t\tcase REW_INST:\n\t\t\t// nothing to do here, we're collecting rewards later on\n\t\t\tbreak;\n\t\tcase REW_CUMUL:\n\t\t\tdouble mixed = (1.0 - probSum) / maxRate;\n\t\t\tfor (StateProp prop : states.values()) {\n\t\t\t\tvalue += prop.getProb() * mixed * prop.getReward();\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\n\t}\n\n\t/**\n\t * Updates state values once a transient analysis of time interval finished.\n\t * Deletes states which can be deleted according to their current\n\t * probability and the threshold. Computes new maximal rate for remaining\n\t * states. Computes transitions to successors of states which have become\n\t * alive to to probability threshold only after a transient analysis has\n\t * finished.\n\t * \n\t * @throws PrismException thrown if something goes wrong\n\t */\n\tprivate void updateStates() throws PrismException\n\t{\n\t\tmaxRate = 0.0;\n\t\taddDistr.clear();\n\t\tfor (Map.Entry<State,StateProp> statePair : states.entrySet()) {\n\t\t\tState state = statePair.getKey();\n\t\t\tStateProp prop = statePair.getValue();\n\t\t\tif (prop.getProb() > delta) {\n\t\t\t\tprop.setAlive(true);\n\t\t\t\tif (!prop.hasSuccs()) {\n\t\t\t\t\titersUnchanged = 0;\n\t\t\t\t\taddDistr.add(state);\n\t\t\t\t} else {\n\t\t\t\t\tmaxRate = Math.max(maxRate, prop.sumRates());\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tprop.delete();\n\t\t\t}\n\t\t}\n\t\tfor (int stateNr = 0; stateNr < addDistr.size(); stateNr++) {\n\t\t\tcomputeStateRatesAndRewards(addDistr.get(stateNr));\n\t\t\tmaxRate = Math.max(maxRate, states.get(addDistr.get(stateNr)).sumRates());\n\t\t}\n\t\tmaxRate *= 1.02;\n\n\t\tremoveDeletedStates();\n\t}\n\n\t/**\n\t * Removes all states subject to removal.\n\t * This affects states which both have a present-state probability below\n\t * the given threshold, and do not have incoming transitions from states\n\t * with a relevant probability mass.\n\t */\n\tprivate void removeDeletedStates()\n\t{\n\t\tboolean unchanged = true;\n\t\tfor (Map.Entry<State,StateProp> statePair : states.entrySet()) {\n\t\t\tState state = statePair.getKey();\n\t\t\tStateProp prop = statePair.getValue();\n\t\t\tif (prop.canRemove()) {\n\t\t\t\tdeleteStates.add(state);\n\t\t\t\tunchanged = false;\n\t\t\t}\n\t\t}\n\t\tif (!keepSumProb) {\n\t\t\tfor (int i = 0; i < deleteStates.size(); i++) {\n\t\t\t\tstates.remove(deleteStates.get(i));\n\t\t\t}\n\t\t}\n\t\tif (unchanged) {\n\t\t\titersUnchanged++;\n\t\t} else {\n\t\t\titersUnchanged = 0;\n\t\t}\n\t\tdeleteStates.clear();\n\t}\n    \n\t/**\n\t * Prepares initial distribution for the case of a single initial state.\n\t * \n\t * @throws PrismException\n\t */\n    private void prepareInitialDistribution() throws PrismException\n    {\n    \tinitStates = new HashSet<State>();\n\t\tState initState = modelGen.getInitialState();\n\t\tinitStates.add(initState);\n\t\taddToModel(initState);\n\t\tcomputeStateRatesAndRewards(initState);\n\t\tstates.get(initState).setProb(1.0);\n\t\tmaxRate = states.get(initState).sumRates() * 1.02;\n\t}\n\n    /**\n     * Computes total sum of lost probabilities.\n     * \n     * @return total probability still in model\n     */\n\tpublic void computeTotalDiscreteLoss()\n\t{\n\t\tdouble totalProb = 0;\n\t\tfor (StateProp prop : states.values()) {\n\t\t\ttotalProb += prop.getSum();\n\t\t}\n\t\ttotalProb += totalProbSetZero;\n\t\t\n\t\ttotalProbLoss = 1.0 - totalProb;\n\t}\n\n\t/**\n\t * Returns the total probability loss.\n\t * \n\t * @return\n\t */\n\tpublic double getTotalDiscreteLoss()\n\t{\n\t\treturn totalProbLoss;\n\t}\n\n\t/**\n\t * Sets the probability of sink states to zero.\n\t * @throws PrismException \n\t */\n\tpublic void clearSinkStates() throws PrismException {\n\t\tfor (Map.Entry<State,StateProp> statePair : states.entrySet()) {\n\t\t\tState state = statePair.getKey();\n\t\t\tStateProp prop = statePair.getValue();\n\t\t\tmodelGen.exploreState(state);\n\t\t\tspecialLabels.setLabel(0, modelGen.getNumTransitions() == 0 ? Expression.True() : Expression.False());\n\t\t\tspecialLabels.setLabel(1, initStates.contains(state) ? Expression.True() : Expression.False());\n\t\t\tExpression evSink = sink.deepCopy();\n\t\t\tevSink = (Expression) evSink.expandLabels(specialLabels);\n\t\t\tif (evSink.evaluateBoolean(constantValues, state)) {\n\t\t\t\ttotalProbSetZero += prop.getProb();\n\t\t\t\tprop.setProb(0.0);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Adds @a state to model.\n\t * Computes reward for this states, creates entry in map of states,\n\t * and updates number of states\n\t * \n\t * @param state state to add\n\t * @throws PrismException thrown if something wrong happens in underlying methods\n\t */\n\tprivate void addToModel(State state) throws PrismException\n\t{\n\t\tStateProp prop = new StateProp();\n\t\tprop.setReward(computeRewards(state));\n\t\tstates.put(state, prop);\n\t\tmaxNumStates = Math.max(maxNumStates, states.size());\n\t}\n\n\t/**\n\t * Computes successor rates and rewards for a given state.\n\t * Rewards computed depend on the reward structure set by\n\t * {@code setRewardStruct}.\n\t * \n\t * @param state state to compute successor rates and rewards for\n\t * @throws PrismException thrown if something goes wrong\n\t */\n\tprivate void computeStateRatesAndRewards(State state) throws PrismException\n\t{\n\t\tdouble[] succRates;\n\t\tStateProp[] succStates;\n\t\tmodelGen.exploreState(state);\n\t\tspecialLabels.setLabel(0, modelGen.getNumTransitions() == 0 ? Expression.True() : Expression.False());\n\t\tspecialLabels.setLabel(1, initStates.contains(state) ? Expression.True() : Expression.False());\n\t\tExpression evSink = sink.deepCopy();\n\t\tevSink = (Expression) evSink.expandLabels(specialLabels);\n\t\tif (evSink.evaluateBoolean(constantValues, state)) {\n\t\t\tsuccRates = new double[1];\n\t\t\tsuccStates = new StateProp[1];\n\t\t\tsuccRates[0] = 1.0;\n\t\t\tsuccStates[0] = states.get(state);\n\t\t} else {\n\t\t\tint ntAll = modelGen.getNumTransitions();\n\t\t\tif (ntAll > 0) {\n\t\t\t\tsuccRates = new double[ntAll];\n\t\t\t\tsuccStates = new StateProp[ntAll];\n\n\t\t\t\tint t = 0;\n\t\t\t\tfor (int i = 0, nc = modelGen.getNumChoices(); i < nc; i++) {\n\t\t\t\t\tfor (int j = 0, ntChoice = modelGen.getNumTransitions(i); j < ntChoice; j++) {\n\t\t\t\t\t\tState succState = modelGen.computeTransitionTarget(i, j);\n\t\t\t\t\t\tStateProp succProp = states.get(succState);\n\t\t\t\t\t\tif (null == succProp) {\n\t\t\t\t\t\t\taddToModel(succState);\n\t\t\t\t\t\t\tsuccProp = states.get(succState);\n\n\t\t\t\t\t\t\t// re-explore state, as call to addToModel may have explored succState\n\t\t\t\t\t\t\tmodelGen.exploreState(state);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tsuccRates[t] = modelGen.getTransitionProbability(i, j);\n\t\t\t\t\t\tsuccStates[t] = succProp;\n\t\t\t\t\t\tt++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tsuccRates = new double[1];\n\t\t\t\tsuccStates = new StateProp[1];\n\t\t\t\tsuccRates[0] = 1.0;\n\t\t\t\tsuccStates[0] = states.get(state);\n\t\t\t}\n\t\t}\n\t\tstates.get(state).setSuccRates(succRates);\n\t\tstates.get(state).setSuccStates(succStates);\n\t}\n\n\t/**\n\t * Perform a single matrix-vector multiplication.\n\t * \n\t * @param maxRate maximal total leaving rate sum in living states\n\t */\n\tprivate void mvMult(double maxRate)\n\t{\n\t\tfor (StateProp prop : states.values()) {\n\t\t\tdouble[] succRates = prop.getSuccRates();\n\t\t\tStateProp[] succStates = prop.getSuccStates();\n\t\t\tdouble stateProb = prop.getProb();\n\t\t\tif (null != succStates) {\n\t\t\t\tdouble sumRates = 0.0;\n\t\t\t\tfor (int succ = 0; succ < succStates.length; succ++) {\n\t\t\t\t    double rate = succRates[succ];\n\t\t\t\t    sumRates += rate;\n\t\t\t\t    succStates[succ].addToNextProb((rate / maxRate) * stateProb);\n\t\t\t\t}\n\t\t\t\tprop.addToNextProb(((maxRate - sumRates) / maxRate) * prop.getProb());\n\t\t\t}\n\t\t}\n\t\tfor (StateProp prop : states.values()) {\n\t\t\tprop.prepareNextIteration();\n\t\t}\n\t}\n\n\t/**\n\t * Checks if rewards are needed for analysis.\n\t * \n\t * @return true if and only if rewards are needed\n\t */\n\tprivate boolean isRewardAnalysis()\n\t{\n\t\treturn (analysisType == AnalysisType.REW_INST)\n\t\t\t|| (analysisType == AnalysisType.REW_CUMUL);\n\t}\n\t\n\t/**\n\t * Computes the reward for a given state.\n\t * In case a cumulative reward analysis is to be performed, transition\n\t * rewards are transformed into equivalent state rewards.\n\t * \n\t * @param state the state to compute the reward of\n\t * @return the reward for state @a state\n\t * @throws PrismException thrown if problems occur in PRISM functions called\n\t */\n\tprivate double computeRewards(State state) throws PrismException\n\t{\n\t\tif (!isRewardAnalysis()) {\n\t\t\treturn 0.0;\n\t\t}\n\t\tint numChoices = 0;\n\t\tif (AnalysisType.REW_CUMUL == analysisType) {\n\t\t\tmodelGen.exploreState(state);\n\t\t\tnumChoices = modelGen.getNumChoices();\n\t\t}\n\t\tdouble sumReward = 0.0;\n\t\tint numStateItems = rewStruct.getNumItems();\n\t\tfor (int i = 0; i < numStateItems; i++) {\n\t\t\tExpression guard = rewStruct.getStates(i);\n\t\t\tif (guard.evaluateBoolean(constantValues, state)) {\n\t\t\t\tdouble reward = rewStruct.getReward(i).evaluateDouble(constantValues, state);\n\t\t\t\tString action = rewStruct.getSynch(i);\n\t\t\t\tif (action != null) {\n\t\t\t\t\tif (AnalysisType.REW_CUMUL == analysisType) {\n\t\t\t\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\t\t\t\tint numTransitions = modelGen.getNumTransitions(j);\n\t\t\t\t\t\t\tfor (int k = 0; k < numTransitions; k++) {\n\t\t\t\t\t\t\t\tObject tAction = modelGen.getTransitionAction(j, k);\n\t\t\t\t\t\t\t\tif (tAction == null) {\n\t\t\t\t\t\t\t\t\ttAction = \"\";\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tif (tAction.toString().equals(action)) {\n\t\t\t\t\t\t\t\t\tsumReward += reward * modelGen.getTransitionProbability(j, k);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tsumReward += reward;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn sumReward;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/FastAdaptiveUniformisationModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.LabelList;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport parser.ast.RewardStruct;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport prism.Result;\nimport simulator.ModulesFileModelGenerator;\n\n/**\n * CTMC model checker based on fast adaptive uniformisation.\n */\npublic class FastAdaptiveUniformisationModelChecker extends PrismComponent\n{\n\t// Model file\n\tprivate ModulesFile modulesFile;\n\t// Properties file\n\tprivate PropertiesFile propertiesFile;\n\t// Constants from model\n\tprivate Values constantValues;\n\t// Labels from the model\n\tprivate LabelList labelListModel;\n\t// Labels from the property file\n\tprivate LabelList labelListProp;\n\t\n\t/**\n\t * Constructor.\n\t */\n\tpublic FastAdaptiveUniformisationModelChecker(PrismComponent parent, ModulesFile modulesFile, PropertiesFile propertiesFile) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tthis.modulesFile = modulesFile;\n\t\tthis.propertiesFile = propertiesFile;\n\n\t\t// Get combined constant values from model/properties\n\t\tconstantValues = new Values();\n\t\tconstantValues.addValues(modulesFile.getConstantValues());\n\t\tif (propertiesFile != null)\n\t\t\tconstantValues.addValues(propertiesFile.getConstantValues());\n\t\tthis.labelListModel = modulesFile.getLabelList();\n\t\tthis.labelListProp = propertiesFile.getLabelList();\n\t}\n\n\t/**\n\t * Model check a property.\n\t */\n\tpublic Result check(Expression expr) throws PrismException\n\t{\n\t\tResult res;\n\t\tString resultString;\n\t\tlong timer;\n\n\t\t// Starting model checking\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Do model checking\n\t\tres = checkExpression(expr);\n\n\t\t// Model checking complete\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"\\nModel checking completed in \" + (timer / 1000.0) + \" secs.\");\n\n\t\t// Print result to log\n\t\tresultString = \"Result\";\n\t\tif (!(\"Result\".equals(expr.getResultName())))\n\t\t\tresultString += \" (\" + expr.getResultName().toLowerCase() + \")\";\n\t\tresultString += \": \" + res;\n\t\tmainLog.print(\"\\n\" + resultString + \"\\n\");\n\n\t\t// Return result\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check an expression (used recursively).\n\t */\n\tprivate Result checkExpression(Expression expr) throws PrismException\n\t{\n\t\tResult res;\n\n\t\t// Current range of supported properties is quite limited...\n\t\tif (expr instanceof ExpressionProb)\n\t\t\tres = checkExpressionProb((ExpressionProb) expr);\n\t\telse if (expr instanceof ExpressionReward)\n\t\t\tres = checkExpressionReward((ExpressionReward) expr);\n\t\telse\n\t\t\tthrow new PrismNotSupportedException(\"Fast adaptive uniformisation not yet supported for this operator\");\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check a P operator.\n\t */\n\tprivate Result checkExpressionProb(ExpressionProb expr) throws PrismException\n\t{\n\t\t// Check whether P=? (only case allowed)\n\t\tif (expr.getProb() != null) {\n\t\t\tthrow new PrismNotSupportedException(\"Fast adaptive uniformisation model checking currently only supports P=? properties\");\n\t\t}\n\n\t\tif (!(expr.getExpression() instanceof ExpressionTemporal)) {\n\t\t\tthrow new PrismNotSupportedException(\"Fast adaptive uniformisation model checking currently only supports simple path operators\");\n\t\t}\n\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr.getExpression();\n\t\tif (!exprTemp.isSimplePathFormula()) {\n\t\t\tthrow new PrismNotSupportedException(\"Fast adaptive uniformisation window model checking currently only supports simple until operators\");\n\t\t}\n\n\t\tdouble timeLower = 0.0;\n\t\tif (exprTemp.getLowerBound() != null) {\n\t\t\ttimeLower = exprTemp.getLowerBound().evaluateDouble(constantValues);\n\t\t}\n\t\tif (exprTemp.getUpperBound() == null) {\n\t\t\tthrow new PrismNotSupportedException(\"Fast adaptive uniformisation window model checking currently requires an upper time bound\");\n\t\t}\n\t\tdouble timeUpper = exprTemp.getUpperBound().evaluateDouble(constantValues);\n\n\t\tif (!exprTemp.hasBounds()) {\n\t\t\tthrow new PrismNotSupportedException(\"Fast adaptive uniformisation window model checking currently only supports timed properties\");\n\t\t}\n\n\t\tmainLog.println(\"Starting transient probability computation using fast adaptive uniformisation...\");\n\t\tModulesFileModelGenerator<Double> prismModelGen = ModulesFileModelGenerator.createForDoubles(modulesFile, this);\n\t\tFastAdaptiveUniformisation fau = new FastAdaptiveUniformisation(this, prismModelGen);\n\t\tfau.setConstantValues(constantValues);\n\n\t\tExpression op1 = exprTemp.getOperand1();\n\t\tif (op1 == null) {\n\t\t\top1 = Expression.True();\n\t\t}\n\t\tExpression op2 = exprTemp.getOperand2();\n\t\top1 = (Expression) op1.expandPropRefsAndLabels(propertiesFile, labelListModel);\n\t\top1 = (Expression) op1.expandPropRefsAndLabels(propertiesFile, labelListProp);\n\t\top2 = (Expression) op2.expandPropRefsAndLabels(propertiesFile, labelListModel);\n\t\top2 = (Expression) op2.expandPropRefsAndLabels(propertiesFile, labelListProp);\n\t\tint operator = exprTemp.getOperator();\n\n\t\tExpression sink = null;\n\t\tExpression target = null;\n\t\tswitch (operator) {\n\t\tcase ExpressionTemporal.P_U:\n\t\tcase ExpressionTemporal.P_F:\n\t\t\tsink = Expression.Not(op1);\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.P_G:\n\t\t\tsink = Expression.False();\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.P_W:\n\t\tcase ExpressionTemporal.P_R:\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"operator currently not supported for fast adaptive uniformisation\");\n\t\t}\n\t\tfau.setSink(sink);\n\t\tfau.computeTransientProbsAdaptive(timeLower);\n\t\tfau.clearSinkStates();\n\n\t\tswitch (operator) {\n\t\tcase ExpressionTemporal.P_U:\n\t\tcase ExpressionTemporal.P_F:\n\t\t\tsink = Expression.Or(Expression.Not(op1), op2);\n\t\t\ttarget = op2;\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.P_G:\n\t\t\tsink = Expression.Not(op2);\n\t\t\ttarget = op2;\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.P_W:\n\t\tcase ExpressionTemporal.P_R:\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"operator currently not supported for fast adaptive uniformisation\");\n\t\t}\n\t\tValues varValues = new Values();\n\t\tvarValues.addValue(\"deadlock\", \"true\");\n\t\tsink.replaceVars(varValues);\n\t\tfau.setAnalysisType(FastAdaptiveUniformisation.AnalysisType.REACH);\n\t\tfau.setSink(sink);\n\t\tfau.setTarget(target);\n\t\tfau.computeTransientProbsAdaptive(timeUpper - timeLower);\n\t\tmainLog.println(\"\\nTotal probability lost is : \" + fau.getTotalDiscreteLoss());\n\t\tmainLog.println(\"Maximal number of states stored during analysis : \" + fau.getMaxNumStates());\n\n\t\treturn new Result(Double.valueOf(fau.getValue()));\n\t}\n\n\t/**\n\t * Model check an R operator.\n\t */\n\tprivate Result checkExpressionReward(ExpressionReward expr) throws PrismException\n\t{\n\t\tmainLog.println(\"Starting transient probability computation using fast adaptive uniformisation...\");\n\t\tModulesFileModelGenerator<Double> prismModelGen = ModulesFileModelGenerator.createForDoubles(modulesFile, this);\n\t\tFastAdaptiveUniformisation fau = new FastAdaptiveUniformisation(this, prismModelGen);\n\t\tExpressionTemporal temporal = (ExpressionTemporal) expr.getExpression();\n\t\tswitch (temporal.getOperator()) {\n\t\tcase ExpressionTemporal.R_I:\n\t\t\tfau.setAnalysisType(FastAdaptiveUniformisation.AnalysisType.REW_INST);\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.R_C:\n\t\t\tfau.setAnalysisType(FastAdaptiveUniformisation.AnalysisType.REW_CUMUL);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Currently only instantaneous or cumulative rewards are allowed.\");\n\t\t}\n\t\tdouble time = temporal.getUpperBound().evaluateDouble(constantValues);\n\t\tRewardStruct rewStruct = modulesFile.getRewardStruct(expr.getRewardStructIndexByIndexObject(modulesFile.getRewardStructNames(), constantValues));\n\t\tfau.setRewardStruct(rewStruct);\n\t\tfau.setConstantValues(constantValues);\n\t\tfau.computeTransientProbsAdaptive(time);\n\t\tmainLog.println(\"\\nTotal probability lost is : \" + fau.getTotalDiscreteLoss());\n\t\tmainLog.println(\"Maximal number of states stored during analysis : \" + fau.getMaxNumStates());\n\t\treturn new Result(Double.valueOf(fau.getValue()));\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/FoxGlynn.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <forejt@fi.muni.cz> (Masaryk University)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport prism.PrismException;\n\n/**\n * Class to efficiently and reliably compute probabilities for the Poisson distribution,\n * truncating above and below for a provided error bound. Implements the algorithm from:\n * B. Fox and P. Glynn, Computing Poisson Probabilities, Communications of the ACM 31(4):440-445, 1988.\n */\npublic final class FoxGlynn\n{\n\t// constructor parameters\n\tprivate double underflow, overflow, accuracy;\n\tprivate double q_tmax;\n\n\t// returned values\n\tprivate int left, right;\n\tprivate double totalWeight;\n\tprivate double[] weights;\n\n\t/**\n\t * Computes the probabilities for the Poisson distribution with rate {@code qtmax}.\n\t * The {@code i}th probability is returned for {@code L<=i<=R}, where {@code L} and {@code R}\n\t * are determined according to the requested accuracy and are available from the methods\n\t * {@link #getLeftTruncationPoint()} and {@link #getRightTruncationPoint()}.\n\t * The probabilities are given in an array returned by {@link #getWeights()};\n\t * these should be normalised by dividing by {@link #getTotalWeight()}.\n\t * The sum of the probabilities will be greater than equal to {@code 1-acc}.\n\t * Furthermore, the sum of probabilities for {@code i<L} and {@code i>R} are both {@code <=acc/2}.\n\t * Thresholds for underflow ({@code uf}) and overflow ({@code ov}) should also be given.\n\t * Note that the Fox-Glynn method requires accuracy to be at least 1e-10.\n\t */\n\tpublic FoxGlynn(double qtmax, double uf, double of, double acc) throws PrismException\n\t{\n\t\tq_tmax = qtmax;\n\t\tunderflow = uf;\n\t\toverflow = of;\n\t\taccuracy = acc;\n\t\trun();\n\t}\n\n\tpublic final double[] getWeights()\n\t{\n\t\treturn weights;\n\t}\n\n\tpublic final int getLeftTruncationPoint()\n\t{\n\t\treturn left;\n\t}\n\n\tpublic final int getRightTruncationPoint()\n\t{\n\t\treturn right;\n\t}\n\n\tpublic final double getTotalWeight()\n\t{\n\t\treturn totalWeight;\n\t}\n\n\tprivate final void run() throws PrismException\n\t{\n\t\tif (q_tmax == 0.0) {\n\t\t\tthrow new PrismException(\"Overflow: TA parameter qtmax = time * maxExitRate = 0\");\n\t\t}\n\n\t\tif (accuracy < 1e-10) {\n\t\t\tthrow new PrismException(\"Overflow: Accuracy is smaller than Fox Glynn can handle (must be at least 1e-10)\");\n\t\t}\n\n\t\tif (q_tmax < 400)\n\t\t{ //here naive approach should have better performance than Fox Glynn\n\t\t\tfinal double expcoef = Math.exp(-q_tmax); //the \"e^-lambda\" part of p.m.f. of Poisson dist.\n\t\t\tint k; //denotes that we work with event \"k steps occur\"\n\t\t\tdouble lastval; //(probability that exactly k events occur)/expcoef\n\t\t\tdouble accum; //(probability that 0 to k events occur)/expcoef\n\t\t\tdouble desval = (1-(accuracy/2.0)) / expcoef; //value that we want to accumulate in accum before we stop\n\t\t\tjava.util.Vector<Double> w = new java.util.Vector<Double>(); //stores weights computed so far.\n\t\t\t\n\t\t\t//k=0 is simple\n\t\t\tlastval = 1;\n\t\t\taccum = lastval;\n\t\t\tw.add(lastval * expcoef);\n\t\t\t\n\t\t\t//add further steps until you have accumulated enough\n\t\t\tk = 1;\n\t\t\tdo {\n\t\t\t\t// TODO: catch case where lastval gets so small that\n\t\t\t\t// accnum never reaches desval due to rounding/floating point precision errors (infinite loop)\n\n\t\t\t\tlastval *= q_tmax / k; // invariant: lastval = q_tmax^k / k!\n\t\t\t\taccum += lastval;\n\t\t\t\tw.add(lastval * expcoef);\n\t\t\t\tk++;\n\t\t\t} while (accum < desval);\n\n\t\t\t//store all data\n\t\t\tthis.left=0;\n\t\t\tthis.right=k-1;\n\t\t\tthis.weights = new double[k];\n\n\t\t\tfor(int i = 0; i < w.size(); i++)\n\t\t\t{\n\t\t\t\tthis.weights[i] = w.get(i);\t\t\t\n\t\t\t}\n\n\t\t\t//we return actual weights, so no reweighting should be done\n\t\t\tthis.totalWeight = 1.0;\n\t\t}\n\t\telse\n\t\t{ //use actual Fox Glynn for q_tmax>400\n\t\t\tfinal double factor = 1e+10; //factor from the paper, it has no real explanation there\n\t\t\tfinal int m = (int) q_tmax; //mode\n\t\t\t//run FINDER to get left, right and weight[m]\n\t\t\t{\n\t\t\t\tfinal double sqrtpi = 1.7724538509055160; //square root of PI\n\t\t\t\tfinal double sqrt2 = 1.4142135623730950; //square root of 2\n\t\t\t\tfinal double sqrtq = Math.sqrt(q_tmax);\n\t\t\t\tfinal double aq = (1.0 + 1.0/q_tmax) * Math.exp(0.0625) * sqrt2; //a_\\lambda from the paper\t\t\t\n\t\t\t\tfinal double bq = (1.0 + 1.0/q_tmax) * Math.exp(0.125/q_tmax); //b_\\lambda from the paper\n\n\t\t\t\t//use Corollary 1 to find right truncation point\n\t\t\t\tfinal double lower_k_1 = 1.0 / (2.0*sqrt2*q_tmax); //lower bound on k from Corollary 1\n\t\t\t\tfinal double upper_k_1 = sqrtq / (2.0*sqrt2); //upper bound on k from Corollary 1\n\t\t\t\tdouble k;\n\n\t\t\t\t//justification for increment is in the paper:\n\t\t\t\t//\"increase k through the positive integers greater than 3\"\n\t\t\t\tfor(k=lower_k_1; k <= upper_k_1;\n\t\t\t\t\tk=(k==lower_k_1)? k+4 : k+1 )\n\t\t\t\t{\n\t\t\t\t\tdouble dkl = 1.0/(1 - Math.exp(-(2.0/9.0)*(k*sqrt2*sqrtq+1.5))); //d(k,\\lambda) from the paper\n\t\t\t\t\tdouble res = aq*dkl*Math.exp(-k*k/2.0)/(k*sqrt2*sqrtpi); //right hand side of the equation in Corollary 1\n\t\t\t\t\tif (res <= accuracy/2.0)\n\t\t\t\t\t{\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (k>upper_k_1)\n\t\t\t\t\tk=upper_k_1;\n\n\t\t\t\tthis.right = (int) Math.ceil(m+k*sqrt2*sqrtq + 1.5); \n\n\t\t\t\t//use Corollary 2 to find left truncation point\n\t\t\t\t//NOTE: the original implementation used some upper bound on k,\n\t\t\t\t//      however, I didn't find it in the paper and I think it is not needed\n\t\t\t\tfinal double lower_k_2 = 1.0/(sqrt2*sqrtq); //lower bound on k from Corollary 2\n\n\t\t\t\tdouble res;\n\t\t\t\tk=lower_k_2;\n\t\t\t\tdo\n\t\t\t\t{\n\t\t\t\t\tres = bq*Math.exp(-k*k/2.0)/(k*sqrt2*sqrtpi); //right hand side of the equation in Corollary 2\n\t\t\t\t\tk++;\t\t\t\n\t\t\t\t}\n\t\t\t\twhile (res > accuracy/2.0);\n\t\t\t\t\n\t\t\t\tthis.left = (int) (m - k*sqrtq - 1.5);\n\t\t\t\t\n\t\t\t\t//According to the paper, we should check underflow of lower bound.\n\t\t\t\t//However, it seems that for no reasonable values this can happen.\n\t\t\t\t//And neither the original implementation checked it\n\t\t\t\t\n\t\t\t\tdouble wm = overflow / (factor*(this.right - this.left));\n\n\t\t\t\tthis.weights = new double[this.right-this.left+1];\n\t\t\t\tthis.weights[m-this.left] = wm;\n\t\t\t}\n\t\t\t//end of FINDER\n\n\t\t\t//compute weights\n\t\t\t//(at this point this.left, this.right and this.weight[m] is known)\n\t\t\t\n\t\t\t//Down from m\n\t\t\tfor(int j=m; j>this.left; j--)\n\t\t\t\tthis.weights[j-1-this.left] = (j/q_tmax)*this.weights[j-this.left];\n\t\t\t//Up from m\n\t\t\tfor(int j=m; j<this.right; j++)\n\t\t\t\tthis.weights[j+1-this.left] = (q_tmax/(j+1))*this.weights[j-this.left];\n\n\t\t\t//Compute totalWeight (i.e. W in the paper)\n\t\t\t//instead of summing from left to right, start from smallest\n\t\t\t//and go to highest weights to prevent roundoff\n\t\t\tthis.totalWeight = 0.0;\n\t\t\tint s = this.left;\n\t\t\tint t = this.right;\n\t\t\twhile (s<t)\n\t\t\t{\n\t\t\t\tif(this.weights[s - this.left] <= this.weights[t - this.left])\n\t\t\t\t{\n\t\t\t\t\tthis.totalWeight += this.weights[s-this.left];\n\t\t\t\t\ts++;\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\tthis.totalWeight += this.weights[t-this.left];\n\t\t\t\t\tt--;\n\t\t\t\t}\n\t\t\t}\n\t\t\tthis.totalWeight += this.weights[s-this.left];\n\t\t}\n\t}\n\n\tpublic static void test()\n\t{\n\t\tdouble[] weights;\n\t\tdouble totalWeight = 0.0;\n\t\tint left, right;\n\n\t\tFoxGlynn w = null;\n\t\ttry {\n\t\t\t// q = maxDiagRate, time = time parameter (a U<time b)\n\t\t\tdouble q = 1, time = 1;\n\t\t\tw = new FoxGlynn(q * time, 1.0e-300, 1.0e+300, 1.0e-6);\n\t\t} catch (PrismException e) {\n\t\t\t// ...\n\t\t}\n\t\tweights = w.getWeights();\n\t\tleft = w.getLeftTruncationPoint();\n\t\tright = w.getRightTruncationPoint();\n\t\ttotalWeight = w.getTotalWeight();\n\t\tw = null;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/IDTMC.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.oc.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport common.Interval;\nimport prism.ModelType;\nimport prism.Pair;\n\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state interval DTMC.\n */\npublic interface IDTMC<Value> extends UDTMC<Value>, IntervalModel<Value>\n{\n\t// Accessors (for Model) - default implementations\n\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.IDTMC;\n\t}\n\n\t// Accessors\n\n\t/**\n\t * Get an iterator over the (interval) transitions from state {@code s}.\n\t */\n\tIterator<Map.Entry<Integer, Interval<Value>>> getIntervalTransitionsIterator(int s);\n\n\t/**\n\t * Get an iterator over the (interval) transitions from state {@code s}, with their attached actions if present.\n\t */\n\tIterator<Map.Entry<Integer, Pair<Interval<Value>, Object>>> getIntervalTransitionsAndActionsIterator(int s);\n\n\t/**\n\t * Get the (interval) DTMC representing this IDTMC.\n\t */\n\tDTMC<Interval<Value>> getIntervalModel();\n\n\t/**\n\t * Do a single row of matrix-vector multiplication followed by min/max,\n\t * i.e. return min/max_P { sum_j P(s,j)*vect[j] }\n\t * @param did The transition probability intervals\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t */\n\tstatic double mvMultUncSingle(DoubleIntervalDistribution did, double vect[], MinMax minMax)\n\t{\n\t\t// Trivial case: singleton interval (which must be [1.0,1.0])\n\t\tif (did.size == 1) {\n\t\t\treturn vect[did.index[0]];\n\t\t}\n\n\t\t// Avoid enumeration of all extreme distributions using optimisation from:\n\t\t// Three-valued abstraction for probabilistic systems,\n\t\t// Joost-Pieter Katoen, Daniel Klink, Martin Leucker and Verena Wolf\n\t\t// (Defn 17, p.372, and p.380)\n\n\t\t// Get a list of indices for the transitions,\n\t\t// sorted according to the successor values\n\t\tList<Integer> indices = new ArrayList<>();\n\t\tfor (int i = 0; i < did.size; i++) {\n\t\t\tindices.add(i);\n\t\t}\n\t\tif (minMax.isMaxUnc()) {\n\t\t\tCollections.sort(indices, (o1, o2) -> -Double.compare(vect[did.index[o1]], vect[did.index[o2]]));\n\t\t} else {\n\t\t\tCollections.sort(indices, (o1, o2) -> Double.compare(vect[did.index[o1]], vect[did.index[o2]]));\n\t\t}\n\t\t// First add products of probability lower bounds and successor values\n\t\tdouble res = 0.0;\n\t\tdouble totP = 1.0;\n\t\tfor (int i = 0; i < did.size; i++) {\n\t\t\tres += vect[did.index[i]] * did.lower[i];\n\t\t\ttotP -= did.lower[i];\n\t\t}\n\t\t// Then add remaining ones in descending order\n\t\tfor (int i = 0; i < did.size; i++) {\n\t\t\tint j = indices.get(i);\n\t\t\tdouble delta = did.upper[j] - did.lower[j];\n\t\t\tif (delta < totP) {\n\t\t\t\tres += delta * vect[did.index[j]];\n\t\t\t\ttotP -= delta;\n\t\t\t} else {\n\t\t\t\tres += totP * vect[did.index[j]];\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn res;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IDTMCModelChecker.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport prism.PrismComponent;\nimport prism.PrismException;\n\n/**\n * Explicit-state model checker for interval discrete-time Markov chains (IDTMCs).\n * Actually just an instance of UDTMCModelChecker - kept for backwards compatability.\n */\npublic class IDTMCModelChecker extends UDTMCModelChecker\n{\n\t/**\n\t * Create a new IDTMCModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic IDTMCModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IDTMCSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t* Alberto Puggelli <alberto.puggelli@gmail.com>\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport common.Interval;\nimport parser.State;\nimport prism.Evaluator;\nimport prism.Pair;\nimport prism.PrismException;\n\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\n/**\n * Simple explicit-state representation of an IDTMC.\n */\npublic class IDTMCSimple<Value> extends ModelExplicitWrapper<Value> implements ModelSimple<Value>, IntervalModelExplicit<Value>, IDTMC<Value>\n{\n\t/**\n\t * The IDTMC, stored as a DTMCSimple over Intervals.\n\t * Also stored in {@link ModelExplicitWrapper#model} as a ModelExplicit.\n\t */\n\tprotected DTMCSimple<Interval<Value>> dtmc;\n\n\t// Constructors\n\n\t/**\n\t * Constructor: empty IDTMC.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic IDTMCSimple()\n\t{\n\t\tthis.dtmc = new DTMCSimple<>();\n\t\tthis.model = (ModelExplicit<Value>) dtmc;\n\t\tcreateDefaultEvaluatorForDTMC();\n\t}\n\n\t/**\n\t * Constructor: new IDTMC with fixed number of states.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic IDTMCSimple(int numStates)\n\t{\n\t\tthis.dtmc = new DTMCSimple<>(numStates);\n\t\tthis.model = (ModelExplicit<Value>) dtmc;\n\t\tcreateDefaultEvaluatorForDTMC();\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic IDTMCSimple(IDTMCSimple<Value> idtmc)\n\t{\n\t\tsetEvaluator(idtmc.getEvaluator());\n\t\tthis.dtmc = new DTMCSimple<>(idtmc.dtmc);\n\t\tthis.model = (ModelExplicit<Value>) dtmc;\n\t}\n\n\t/**\n\t * Construct an IDTMC from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t * Pointer to states list is NOT copied (since now wrong).\n\t * Note: have to build new Distributions from scratch anyway to do this,\n\t * so may as well provide this functionality as a constructor.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic IDTMCSimple(IDTMCSimple<Value> idtmc, int permut[])\n\t{\n\t\tsetEvaluator(idtmc.getEvaluator());\n\t\tthis.dtmc = new DTMCSimple<>(idtmc.dtmc, permut);\n\t\tthis.model = (ModelExplicit<Value>) dtmc;\n\t}\n\n\t/**\n\t * Add a default (double interval) evaluator to the DTMC\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprivate void createDefaultEvaluatorForDTMC()\n\t{\n\t\t((IDTMCSimple<Double>) this).setIntervalEvaluator(Evaluator.forDoubleInterval());\n\t}\n\n\t// Mutators (for ModelSimple)\n\n\t@Override\n\tpublic void clearState(int s)\n\t{\n\t\tdtmc.clearState(s);\n\t}\n\n\t@Override\n\tpublic int addState()\n\t{\n\t\treturn dtmc.addState();\n\t}\n\n\t@Override\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tdtmc.addStates(numToAdd);\n\t}\n\n\t// Mutators (for IntervalModelExplicit)\n\n\t@Override\n\tpublic void setIntervalEvaluator(Evaluator<Interval<Value>> eval)\n\t{\n\t\tdtmc.setEvaluator(eval);\n\t}\n\n\t// Mutators (other)\n\n\t/**\n\t * Set the probability for a transition.\n\t */\n\tpublic void setProbability(int i, int j, Interval<Value> prob)\n\t{\n\t\tdtmc.setProbability(i, j, prob, null);\n\t}\n\n\t/**\n\t * Set the probability for a transition.\n\t */\n\tpublic void setProbability(int i, int j, Interval<Value> prob, Object action)\n\t{\n\t\tdtmc.setProbability(i, j, prob, action);\n\t}\n\n\t/**\n\t * Add to the probability for a transition.\n\t */\n\tpublic void addToProbability(int i, int j, Interval<Value> prob)\n\t{\n\t\tdtmc.addToProbability(i, j, prob, null);\n\t}\n\n\t/**\n\t * Add to the probability for a transition.\n\t */\n\tpublic void addToProbability(int i, int j, Interval<Value> prob, Object action)\n\t{\n\t\tdtmc.addToProbability(i, j, prob, action);\n\t}\n\n\t/**\n\t * Delimit the intervals for probabilities from state s,\n\t * i.e., trim the bounds of the intervals such that at least one\n\t * possible distribution takes each of the extremal values.\n\t * @param s The index of the state to delimit\n\t */\n\tpublic void delimit(int s) throws PrismException\n\t{\n\t\tIntervalUtils.delimit(dtmc.trans.get(s), getEvaluator());\n\t}\n\n\t// Accessors (for UDTMC)\n\n\t@Override\n\tpublic void checkLowerBoundsArePositive() throws PrismException\n\t{\n\t\tEvaluator<Interval<Value>> eval = dtmc.getEvaluator();\n\t\tint numStates = getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tIterator<Map.Entry<Integer, Interval<Value>>> iter = getIntervalTransitionsIterator(s);\n\t\t\twhile (iter.hasNext()) {\n\t\t\t\tMap.Entry<Integer, Interval<Value>> e = iter.next();\n\t\t\t\t// NB: we phrase the check as an operation on intervals, rather than\n\t\t\t\t// accessing the lower bound directly, to make use of the evaluator\n\t\t\t\tif (!eval.gt(e.getValue(), eval.zero())) {\n\t\t\t\t\tList<State> sl = getStatesList();\n\t\t\t\t\tString state = sl == null ? \"\" + s : sl.get(s).toString();\n\t\t\t\t\tthrow new PrismException(\"Transition probability has lower bound of 0 in state \" + state);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic double mvMultUncSingle(int s, double vect[], MinMax minMax)\n\t{\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tDoubleIntervalDistribution did = IntervalUtils.extractDoubleIntervalDistribution(((IDTMC<Double>) this).getIntervalTransitionsIterator(s), getNumTransitions(s));\n\t\treturn IDTMC.mvMultUncSingle(did, vect, minMax);\n\t}\n\n\t// Accessors (for IntervalModel)\n\n\t@Override\n\tpublic Evaluator<Interval<Value>> getIntervalEvaluator()\n\t{\n\t\treturn dtmc.getEvaluator();\n\t}\n\n\t@Override\n\tpublic DTMC<Interval<Value>> getIntervalModel()\n\t{\n\t\treturn dtmc;\n\t}\n\t\n\t// Accessors (for IDTMC)\n\n\t@Override\n\tpublic Iterator<Map.Entry<Integer, Interval<Value>>> getIntervalTransitionsIterator(int s)\n\t{\n\t\treturn dtmc.getTransitionsIterator(s);\n\t}\n\n\t@Override\n\tpublic Iterator<Map.Entry<Integer, Pair<Interval<Value>, Object>>> getIntervalTransitionsAndActionsIterator(int s)\n\t{\n\t\treturn dtmc.getTransitionsAndActionsIterator(s);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IMDP.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Iterator;\nimport java.util.Map;\n\nimport common.Interval;\nimport prism.ModelType;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state interval MDP.\n */\npublic interface IMDP<Value> extends UMDP<Value>, IntervalModel<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.IMDP;\n\t}\n\n\t// Accessors\n\n\t@Override\n\tMDP<Interval<Value>> getIntervalModel();\n\n\t/**\n\t * Get an iterator over the (interval) transitions from choice {@code i} of state {@code s}.\n\t */\n\tIterator<Map.Entry<Integer, Interval<Value>>> getIntervalTransitionsIterator(int s, int i);\n}\n"
  },
  {
    "path": "prism/src/explicit/IMDPModelChecker.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2023-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport prism.PrismComponent;\nimport prism.PrismException;\n\n/**\n * Explicit-state model checker for interval Markov decision prcoesses (IMDPs).\n * Actually just an instance of UMDPModelChecker - kept for backwards compatability.\n */\npublic class IMDPModelChecker extends UMDPModelChecker\n{\n\t/**\n\t * Create a new IMDPModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic IMDPModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IMDPSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t* Alberto Puggelli <alberto.puggelli@gmail.com>\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport common.Interval;\nimport parser.State;\nimport prism.Evaluator;\nimport prism.PrismException;\nimport strat.MDStrategy;\n\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\n/**\n * Simple explicit-state representation of an IMDP.\n */\npublic class IMDPSimple<Value> extends ModelExplicitWrapper<Value> implements NondetModelSimple<Value>, IntervalModelExplicit<Value>, IMDP<Value>\n{\n\t/**\n\t * The IMDP, stored as an MDPSimple over Intervals.\n\t * Also stored in {@link ModelExplicitWrapper#model} as a ModelExplicit.\n\t */\n\tprotected MDPSimple<Interval<Value>> mdp;\n\n\t// Constructors\n\n\t/**\n\t * Constructor: empty IMDP.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic IMDPSimple()\n\t{\n\t\tthis.mdp = new MDPSimple<>();\n\t\tthis.model = (ModelExplicit<Value>) mdp;\n\t\tcreateDefaultEvaluatorForMDP();\n\t}\n\n\t/**\n\t * Constructor: new IMDP with fixed number of states.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic IMDPSimple(int numStates)\n\t{\n\t\tthis.mdp = new MDPSimple<>(numStates);\n\t\tthis.model = (ModelExplicit<Value>) mdp;\n\t\tcreateDefaultEvaluatorForMDP();\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic IMDPSimple(IMDPSimple<Value> imdp)\n\t{\n\t\tsetEvaluator(imdp.getEvaluator());\n\t\tthis.mdp = new MDPSimple<>(imdp.mdp);\n\t\tthis.model = (ModelExplicit<Value>) mdp;\n\t}\n\n\t/**\n\t * Construct an IMDP from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t * Pointer to states list is NOT copied (since now wrong).\n\t * Note: have to build new Distributions from scratch anyway to do this,\n\t * so may as well provide this functionality as a constructor.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic IMDPSimple(IMDPSimple<Value> imdp, int permut[])\n\t{\n\t\tsetEvaluator(imdp.getEvaluator());\n\t\tthis.mdp = new MDPSimple<>(imdp.mdp, permut);\n\t\tthis.model = (ModelExplicit<Value>) mdp;\n\t}\n\n\t/**\n\t * Add a default (double interval) evaluator to the MDP\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprivate void createDefaultEvaluatorForMDP()\n\t{\n\t\t((IMDPSimple<Double>) this).setIntervalEvaluator(Evaluator.forDoubleInterval());\n\t}\n\n\t// Mutators (for ModelSimple)\n\n\t@Override\n\tpublic void clearState(int s)\n\t{\n\t\tmdp.clearState(s);\n\t}\n\n\t@Override\n\tpublic int addState()\n\t{\n\t\treturn mdp.addState();\n\t}\n\n\t@Override\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tmdp.addStates(numToAdd);\n\t}\n\n\t// Mutators (for IntervalModelExplicit)\n\n\t@Override\n\tpublic void setIntervalEvaluator(Evaluator<Interval<Value>> eval)\n\t{\n\t\tmdp.setEvaluator(eval);\n\t}\n\n\t// Mutators (other)\n\n\t/**\n\t * Add a choice (uncertain distribution {@code udistr}) to state {@code s} (which must exist).\n\t * Returns the index of the (newly added) distribution.\n\t * Returns -1 in case of error.\n\t */\n\tpublic int addChoice(int s, Distribution<Interval<Value>> udistr)\n\t{\n\t\treturn mdp.addChoice(s, udistr);\n\t}\n\n\t/**\n\t * Add a choice (uncertain distribution {@code udistr}) labelled with {@code action} to state {@code s} (which must exist).\n\t * Returns the index of the (newly added) distribution.\n\t * Returns -1 in case of error.\n\t */\n\tpublic int addActionLabelledChoice(int s, Distribution<Interval<Value>> udistr, Object action)\n\t{\n\t\treturn mdp.addActionLabelledChoice(s, udistr, action);\n\t}\n\n\t/**\n\t * Set the action label for choice i in some state s.\n\t */\n\tpublic void setAction(int s, int i, Object action)\n\t{\n\t\tmdp.setAction(s, i, action);\n\t}\n\n\t/**\n\t * Delimit the intervals for probabilities for the ith choice (distribution) for state s.\n\t * i.e., trim the bounds of the intervals such that at least one\n\t * possible distribution takes each of the extremal values.\n\t * @param s The index of the state to delimit\n\t * @param i The index of the choice to delimit\n\t */\n\tpublic void delimit(int s, int i)\n\t{\n\t\tIntervalUtils.delimit(mdp.trans.get(s).get(i), getEvaluator());\n\t}\n\n\t// Accessors (for NondetModel)\n\n\t@Override\n\tpublic int getNumChoices(int s)\n\t{\n\t\treturn mdp.getNumChoices(s);\n\t}\n\n\t@Override\n\tpublic Object getAction(int s, int i)\n\t{\n\t\treturn mdp.getAction(s, i);\n\t}\n\n\t@Override\n\tpublic boolean allSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn mdp.allSuccessorsInSet(s, i, set);\n\t}\n\n\t@Override\n\tpublic boolean someSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn mdp.someSuccessorsInSet(s, i, set);\n\t}\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int s, final int i)\n\t{\n\t\treturn mdp.getSuccessorsIterator(s, i);\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(final int s, final int i)\n\t{\n\t\treturn mdp.getSuccessors(s, i);\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s, int i)\n\t{\n\t\treturn mdp.getNumTransitions(s, i);\n\t}\n\n\t@Override\n\tpublic Model<Value> constructInducedModel(MDStrategy<Value> strat)\n\t{\n\t\tthrow new UnsupportedOperationException(\"Not yet implemented\");\n\t}\n\n\t// Accessors (for UMDP)\n\n\t@Override\n\tpublic void checkLowerBoundsArePositive() throws PrismException\n\t{\n\t\tEvaluator<Interval<Value>> eval = mdp.getEvaluator();\n\t\tint numStates = getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tint numChoices = getNumChoices(s);\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\tIterator<Map.Entry<Integer, Interval<Value>>> iter = getIntervalTransitionsIterator(s, j);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tMap.Entry<Integer, Interval<Value>> e = iter.next();\n\t\t\t\t\t// NB: we phrase the check as an operation on intervals, rather than\n\t\t\t\t\t// accessing the lower bound directly, to make use of the evaluator\n\t\t\t\t\tif (!eval.gt(e.getValue(), eval.zero())) {\n\t\t\t\t\t\tList<State> sl = getStatesList();\n\t\t\t\t\t\tString state = sl == null ? \"\" + s : sl.get(s).toString();\n\t\t\t\t\t\tthrow new PrismException(\"Transition probability has lower bound of 0 in state \" + state);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t@Override\n\tpublic double mvMultUncSingle(int s, int k, double vect[], MinMax minMax)\n\t{\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tDoubleIntervalDistribution did = IntervalUtils.extractDoubleIntervalDistribution(((IMDP<Double>) this).getIntervalTransitionsIterator(s, k), getNumTransitions(s, k));\n\t\treturn IDTMC.mvMultUncSingle(did, vect, minMax);\n\t}\n\n\t// Accessors (for IntervalModel)\n\n\t@Override\n\tpublic Evaluator<Interval<Value>> getIntervalEvaluator()\n\t{\n\t\treturn mdp.getEvaluator();\n\t}\n\n\t@Override\n\tpublic MDP<Interval<Value>> getIntervalModel()\n\t{\n\t\treturn mdp;\n\t}\n\n\t// Accessors (for IMDP)\n\n\t@Override\n\tpublic Iterator<Map.Entry<Integer, Interval<Value>>> getIntervalTransitionsIterator(int s, int i)\n\t{\n\t\treturn mdp.getTransitionsIterator(s, i);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IPOMDP.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Iterator;\nimport java.util.Map;\n\nimport common.Interval;\nimport prism.ModelType;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state interval POMDP.\n */\npublic interface IPOMDP<Value> extends UPOMDP<Value>, IntervalModel<Value>\n{\n    // Accessors (for Model) - default implementations\n\n    @Override\n    default ModelType getModelType()\n    {\n        return ModelType.IPOMDP;\n    }\n\n    // Accessors\n\n    @Override\n    POMDP<Interval<Value>> getIntervalModel();\n\n    /**\n     * Get an iterator over the (interval) transitions from choice {@code i} of state {@code s}.\n     */\n    Iterator<Map.Entry<Integer, Interval<Value>>> getIntervalTransitionsIterator(int s, int i);\n}\n"
  },
  {
    "path": "prism/src/explicit/IPOMDPSimple.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport common.Interval;\nimport io.ModelExportOptions;\nimport io.PrismExplicitExporter;\nimport parser.State;\nimport prism.Evaluator;\nimport prism.ModelInfo;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport strat.MDStrategy;\n\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\n/**\n * Simple explicit-state representation of an IPOMDP.\n */\npublic class IPOMDPSimple<Value> extends ModelExplicitWrapper<Value> implements NondetModelSimple<Value>, IntervalModelExplicit<Value>, IPOMDP<Value>\n{\n    /**\n     * The IPOMDP, stored as a POMDPSimple over Intervals.\n     * Also stored in {@link ModelExplicitWrapper#model} as a ModelExplicit.\n     */\n    protected POMDPSimple<Interval<Value>> pomdp;\n\n    // Constructors\n\n    /**\n     * Constructor: empty IPOMDP.\n     */\n    @SuppressWarnings(\"unchecked\")\n    public IPOMDPSimple()\n    {\n        this.pomdp = new POMDPSimple<>();\n        this.model = (ModelExplicit<Value>) pomdp;\n        createDefaultEvaluatorForPOMDP();\n    }\n\n    /**\n     * Constructor: new IPOMDP with fixed number of states.\n     */\n    @SuppressWarnings(\"unchecked\")\n    public IPOMDPSimple(int numStates)\n    {\n        this.pomdp = new POMDPSimple<>(numStates);\n        this.model = (ModelExplicit<Value>) pomdp;\n        createDefaultEvaluatorForPOMDP();\n    }\n\n    /**\n     * Copy constructor.\n     */\n    @SuppressWarnings(\"unchecked\")\n    public IPOMDPSimple(IPOMDPSimple<Value> ipomdp)\n    {\n        setEvaluator(ipomdp.getEvaluator());\n        this.pomdp = new POMDPSimple<>(ipomdp.pomdp);\n        this.model = (ModelExplicit<Value>) pomdp;\n    }\n\n    /**\n     * Construct an IPOMDP from an existing one and a state index permutation,\n     * i.e. in which state index i becomes index permut[i].\n     * Pointer to states list is NOT copied (since now wrong).\n     * Note: have to build new Distributions from scratch anyway to do this,\n     * so may as well provide this functionality as a constructor.\n     */\n    @SuppressWarnings(\"unchecked\")\n    public IPOMDPSimple(IPOMDPSimple<Value> ipomdp, int permut[])\n    {\n        setEvaluator(ipomdp.getEvaluator());\n        this.pomdp = new POMDPSimple<>(ipomdp.pomdp, permut);\n        this.model = (ModelExplicit<Value>) pomdp;\n    }\n\n    /**\n     * Add a default (double interval) evaluator to the POMDP\n     */\n    @SuppressWarnings(\"unchecked\")\n    private void createDefaultEvaluatorForPOMDP()\n    {\n        ((IPOMDPSimple<Double>) this).setIntervalEvaluator(Evaluator.forDoubleInterval());\n    }\n\n    // Mutators (for ModelSimple)\n\n    @Override\n    public void clearState(int s)\n    {\n        pomdp.clearState(s);\n    }\n\n    @Override\n    public int addState()\n    {\n        return pomdp.addState();\n    }\n\n    @Override\n    public void addStates(int numToAdd)\n    {\n        pomdp.addStates(numToAdd);\n    }\n\n    // Mutators (for IntervalModelExplicit)\n\n    @Override\n    public void setIntervalEvaluator(Evaluator<Interval<Value>> eval)\n    {\n        pomdp.setEvaluator(eval);\n    }\n\n    // Mutators (for PartiallyObservableModel)\n\n    @Override\n    public void setObservationsList(List<State> observationsList)\n    {\n        pomdp.setObservationsList(observationsList);\n    }\n\n    @Override\n    public void setUnobservationsList(List<State> unobservationsList)\n    {\n        pomdp.setUnobservationsList(unobservationsList);\n    }\n\n    @Override\n    public void setObservation(int s, State observ, State unobserv, List<String> observableNames) throws PrismException\n    {\n        pomdp.setObservation(s, observ, unobserv, observableNames);\n    }\n\n    @Override\n    public void setObservation(int s, int o) throws PrismException\n    {\n        pomdp.setObservation(s, o);\n    }\n\n    // Mutators (other)\n\n    /**\n     * Add a choice (uncertain distribution {@code udistr}) to state {@code s} (which must exist).\n     * Returns the index of the (newly added) distribution.\n     * Returns -1 in case of error.\n     */\n    public int addChoice(int s, Distribution<Interval<Value>> udistr)\n    {\n        return pomdp.addChoice(s, udistr);\n    }\n\n    /**\n     * Add a choice (uncertain distribution {@code udistr}) labelled with {@code action} to state {@code s} (which must exist).\n     * Returns the index of the (newly added) distribution.\n     * Returns -1 in case of error.\n     */\n    public int addActionLabelledChoice(int s, Distribution<Interval<Value>> udistr, Object action)\n    {\n        return pomdp.addActionLabelledChoice(s, udistr, action);\n    }\n\n    /**\n     * Set the action label for choice i in some state s.\n     */\n    public void setAction(int s, int i, Object action)\n    {\n        pomdp.setAction(s, i, action);\n    }\n\n    /**\n     * Delimit the intervals for probabilities for the ith choice (distribution) for state s.\n     * i.e., trim the bounds of the intervals such that at least one\n     * possible distribution takes each of the extremal values.\n     * @param s The index of the state to delimit\n     * @param i The index of the choice to delimit\n     */\n    public void delimit(int s, int i)\n    {\n        IntervalUtils.delimit(pomdp.trans.get(s).get(i), getEvaluator());\n    }\n\n    // Accessors (for PartiallyObservableModel)\n\n    @Override\n    public List<State> getObservationsList()\n    {\n        return pomdp.getObservationsList();\n    }\n\n    @Override\n    public List<State> getUnobservationsList()\n    {\n        return pomdp.getUnobservationsList();\n    }\n\n    @Override\n    public int getNumObservations()\n    {\n        return pomdp.getNumObservations();\n    }\n\n    @Override\n    public int getNumUnobservations()\n    {\n        return pomdp.getNumUnobservations();\n    }\n\n    @Override\n    public int getObservation(int s)\n    {\n        return pomdp.getObservation(s);\n    }\n\n    @Override\n    public State getObservationAsState(int s)\n    {\n        return pomdp.getObservationAsState(s);\n    }\n\n    @Override\n    public int getUnobservation(int s)\n    {\n        return pomdp.getUnobservation(s);\n    }\n\n    @Override\n    public State getUnobservationAsState(int s)\n    {\n        return pomdp.getUnobservationAsState(s);\n    }\n\n    @Override\n    public double getObservationProb(int s, int o)\n    {\n        return pomdp.getObservationProb(s, o);\n    }\n\n    @Override\n    public int getNumChoicesForObservation(int o)\n    {\n        return pomdp.getNumChoicesForObservation(o);\n    }\n\n    @Override\n    public void exportObservations(ModelInfo modelInfo, PrismLog out, ModelExportOptions exportOptions) throws PrismException\n    {\n        pomdp.exportObservations(modelInfo, out, exportOptions);\n    }\n\n    // Accessors (for NondetModel)\n\n    @Override\n    public int getNumChoices(int s)\n    {\n        return pomdp.getNumChoices(s);\n    }\n\n    @Override\n    public Object getAction(int s, int i)\n    {\n        return pomdp.getAction(s, i);\n    }\n\n    @Override\n    public boolean allSuccessorsInSet(int s, int i, BitSet set)\n    {\n        return pomdp.allSuccessorsInSet(s, i, set);\n    }\n\n    @Override\n    public boolean someSuccessorsInSet(int s, int i, BitSet set)\n    {\n        return pomdp.someSuccessorsInSet(s, i, set);\n    }\n\n    @Override\n    public Iterator<Integer> getSuccessorsIterator(final int s, final int i)\n    {\n        return pomdp.getSuccessorsIterator(s, i);\n    }\n\n    @Override\n    public SuccessorsIterator getSuccessors(final int s, final int i)\n    {\n        return pomdp.getSuccessors(s, i);\n    }\n\n    @Override\n    public int getNumTransitions(int s, int i)\n    {\n        return pomdp.getNumTransitions(s, i);\n    }\n\n    @Override\n    public Model<Value> constructInducedModel(MDStrategy<Value> strat)\n    {\n        throw new UnsupportedOperationException(\"Not yet implemented\");\n    }\n\n    // Accessors (for UMDP)\n\n    @Override\n    public void checkLowerBoundsArePositive() throws PrismException\n    {\n        Evaluator<Interval<Value>> eval = pomdp.getEvaluator();\n        int numStates = getNumStates();\n        for (int s = 0; s < numStates; s++) {\n            int numChoices = getNumChoices(s);\n            for (int j = 0; j < numChoices; j++) {\n                Iterator<Map.Entry<Integer, Interval<Value>>> iter = getIntervalTransitionsIterator(s, j);\n                while (iter.hasNext()) {\n                    Map.Entry<Integer, Interval<Value>> e = iter.next();\n                    // NB: we phrase the check as an operation on intervals, rather than\n                    // accessing the lower bound directly, to make use of the evaluator\n                    if (!eval.gt(e.getValue(), eval.zero())) {\n                        List<State> sl = getStatesList();\n                        String state = sl == null ? \"\" + s : sl.get(s).toString();\n                        throw new PrismException(\"Transition probability has lower bound of 0 in state \" + state);\n                    }\n                }\n            }\n        }\n    }\n\n    // Accessors (for IntervalModel)\n\n    @Override\n    public Evaluator<Interval<Value>> getIntervalEvaluator()\n    {\n        return pomdp.getEvaluator();\n    }\n\n    @Override\n    public POMDP<Interval<Value>> getIntervalModel()\n    {\n        return pomdp;\n    }\n\n    // Accessors (for IMDP)\n\n    @Override\n    public Iterator<Map.Entry<Integer, Interval<Value>>> getIntervalTransitionsIterator(int s, int i)\n    {\n        return pomdp.getTransitionsIterator(s, i);\n    }\n}\n"
  },
  {
    "path": "prism/src/explicit/IncomingChoiceRelation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.Iterator;\nimport java.util.List;\nimport prism.PrismComponent;\n\n/**\n * A class for storing and accessing the incoming choices of an explicit NondetModel.\n * This class can be seen as providing more detailed information than PredecessorRelation,\n * as that class only stores information about the states and not the choices linking them.\n * <p>\n * As NondetModel only provide easy access to successors of states,\n * the predecessor relation is computed and stored for subsequent efficient access.\n * <p>\n * Note: Naturally, if the NondetModel changes, the predecessor relation\n * has to be recomputed to remain accurate.\n */\npublic class IncomingChoiceRelation\n{\n\t/** An outgoing choice from a state, i.e., the source state and the choice index */\n\tpublic static final class Choice\n\t{\n\t\t/** the source state*/\n\t\tprivate int state;\n\t\t/** the choice index */\n\t\tprivate int choice;\n\n\t\t/** Constructor */\n\t\tpublic Choice(int state, int choice)\n\t\t{\n\t\t\tthis.state = state;\n\t\t\tthis.choice = choice;\n\t\t}\n\n\t\t/** The source state of this choice */\n\t\tpublic int getState()\n\t\t{\n\t\t\treturn state;\n\t\t}\n\n\t\t/** The choice index of this choice */\n\t\tpublic int getChoice()\n\t\t{\n\t\t\treturn choice;\n\t\t}\n\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn \"(\"+state+\",\"+choice+\")\";\n\t\t}\n\n\t\t@Override\n\t\tpublic int hashCode()\n\t\t{\n\t\t\tfinal int prime = 31;\n\t\t\tint result = 1;\n\t\t\tresult = prime * result + choice;\n\t\t\tresult = prime * result + state;\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(Object obj)\n\t\t{\n\t\t\tif (this == obj)\n\t\t\t\treturn true;\n\t\t\tif (obj == null)\n\t\t\t\treturn false;\n\t\t\tif (getClass() != obj.getClass())\n\t\t\t\treturn false;\n\t\t\tChoice other = (Choice) obj;\n\t\t\tif (choice != other.choice)\n\t\t\t\treturn false;\n\t\t\tif (state != other.state)\n\t\t\t\treturn false;\n\t\t\treturn true;\n\t\t}\n\n\t};\n\n\t/**\n\t * pre[i] provides the list of incoming choices of the state with index i.\n\t */\n\tList<ArrayList<Choice>> pre;\n\n\t/**\n\t * Constructor. Computes the predecessor relation for the given model\n\t * by considering the successors of each state.\n\t *\n\t * @param model the Model\n\t */\n\tpublic IncomingChoiceRelation(NondetModel<?> model)\n\t{\n\t\tpre = new ArrayList<ArrayList<Choice>>(model.getNumStates());\n\t\t// construct the (empty) array list for all states\n\t\tfor (int s = 0; s < model.getNumStates(); s++) {\n\t\t\tpre.add(s, new ArrayList<Choice>());\n\t\t}\n\n\t\tcompute(model);\n\t}\n\n\t/** Compute the predecessor relation using getSuccessorsIterator. */\n\tprivate void compute(NondetModel<?> model)\n\t{\n\t\tint n = model.getNumStates();\n\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tfor (int c = 0, m = model.getNumChoices(s); c < m; c++) {\n\t\t\t\tChoice choice = new Choice(s, c);\n\n\t\t\t\tIterator<Integer> it = model.getSuccessorsIterator(s, c);\n\t\t\t\twhile (it.hasNext()) {\n\t\t\t\t\tint successor = it.next();\n\n\t\t\t\t\t// Add the current choice s to pre[successor].\n\t\t\t\t\tpre.get(successor).add(choice);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Get an Iterable over the incoming choices of state {@code s}.\n\t */\n\tpublic Iterable<Choice> getIncomingChoices(int s)\n\t{\n\t\treturn pre.get(s);\n\t}\n\n\t/**\n\t * Get an Iterator over the incoming choices of state {@code s}.\n\t */\n\tpublic Iterator<Choice> getIncomingChoicesIterator(int s)\n\t{\n\t\treturn getIncomingChoices(s).iterator();\n\t}\n\n\t/**\n\t * Static constructor to compute the incoming choices information for the given model.\n\t * Logs diagnostic information to the log of the given PrismComponent.\n\t *\n\t * @param parent a PrismComponent (for obtaining the log and settings)\n\t * @param model the non-deterministic model for which the predecessor relation should be computed\n\t * @returns the incoming choices information\n\t **/\n\tpublic static IncomingChoiceRelation forModel(PrismComponent parent, NondetModel<?> model)\n\t{\n\t\tlong timer = System.currentTimeMillis();\n\n\t\tparent.getLog().print(\"Calculating incoming choices relation for \"+model.getModelType().fullName()+\"...  \");\n\t\tparent.getLog().flush();\n\n\t\tIncomingChoiceRelation pre = new IncomingChoiceRelation(model);\n\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tparent.getLog().println(\"done (\" + timer / 1000.0 + \" seconds)\");\n\n\t\treturn pre;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/IndexedSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.*;\n\n/**\n * Class storing an indexed set of objects of type T.\n * Typically used for storing state space during reachability.\n */\npublic class IndexedSet<T> implements StateStorage<T>\n{\n\tprotected Map<T, Integer> set;\n\tprotected int indexOfLastAdd;\n\n\tpublic IndexedSet()\n\t{\n\t\tthis(false);\n\t}\n\n\tpublic IndexedSet(boolean sorted)\n\t{\n\t\tindexOfLastAdd = -1;\n\t\tset = sorted ? new TreeMap<T, Integer>() : new HashMap<T, Integer>();\n\t}\n\t\n\tpublic IndexedSet(Comparator<T> comparator)\n\t{\n\t\tindexOfLastAdd = -1;\n\t\tset = new TreeMap<T, Integer>(comparator);\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tset.clear();\n\t}\n\t\n\t@Override\n\tpublic boolean add(T state)\n\t{\n\t\tInteger i = set.get(state);\n\t\tif (i != null) {\n\t\t\tindexOfLastAdd = i;\n\t\t\treturn false;\n\t\t} else {\n\t\t\tindexOfLastAdd = set.size();\n\t\t\tset.put(state, set.size());\n\t\t\treturn true;\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean contains(T state)\n\t{\n\t\t\treturn set.get(state) != null;\n\t}\n\n\t@Override\n\tpublic int getIndexOfLastAdd()\n\t{\n\t\treturn indexOfLastAdd;\n\t}\n\n\t@Override\n\tpublic boolean isEmpty()\n\t{\n\t\treturn set.isEmpty();\n\t}\n\n\t/**\n\t * Get the number of objects stored in the set.\n\t */\n\t@Override\n\tpublic int size()\n\t{\n\t\treturn set.size();\n\t}\n\n\t/**\n\t * Get access to the underlying set of map entries. \n\t */\n\t@Override\n\tpublic Set<Map.Entry<T, Integer>> getEntrySet()\n\t{\n\t\treturn set.entrySet();\n\t}\n\t\n\t/**\n\t * Create an ArrayList of the states, ordered by index.\n\t */\n\t@Override\n\tpublic ArrayList<T> toArrayList()\n\t{\n\t\tArrayList<T> list = new ArrayList<T>(set.size());\n\t\ttoArrayList(list);\n\t\treturn list;\n\t}\n\n\t/**\n\t * Create an ArrayList of the states, ordered by index, storing in the passed in list.\n\t * @param list An empty ArrayList in which to store the result.\n\t */\n\t@Override\n\tpublic void toArrayList(ArrayList<T> list)\n\t{\n\t\tint i, n;\n\n\t\tn = set.size();\n\t\tfor (i = 0; i < n ; i++)\n\t\t\tlist.add(null);\n\t\tfor (Map.Entry<T, Integer> e : set.entrySet()) {\n\t\t\tlist.set(e.getValue(), e.getKey());\n\t\t}\n\t}\n\t\n\t/**\n\t * Create an ArrayList of the states, ordered by permuted index.\n\t * Index in new list is permut[old_index].\n\t * @param permut Permutation to apply\n\t */\n\t@Override\n\tpublic ArrayList<T> toPermutedArrayList(int permut[])\n\t{\n\t\tArrayList<T> list = new ArrayList<T>(set.size());\n\t\ttoPermutedArrayList(permut, list);\n\t\treturn list;\n\t}\n\n\t/**\n\t * Create an ArrayList of the states, ordered by permuted index, storing in the passed in list.\n\t * Index in new list is permut[old_index].\n\t * @param permut Permutation to apply\n\t * @param list An empty ArrayList in which to store the result.\n\t */\n\t@Override\n\tpublic void toPermutedArrayList(int permut[], ArrayList<T> list)\n\t{\n\t\tint i, n;\n\n\t\tn = set.size();\n\t\tfor (i = 0; i < n ; i++)\n\t\t\tlist.add(null);\n\t\tfor (Map.Entry<T, Integer> e : set.entrySet()) {\n\t\t\tlist.set(permut[e.getValue()], e.getKey());\n\t\t}\n\t}\n\t\n\t/**\n\t * Build sort permutation. Assuming this was built as a sorted set,\n\t * this returns a permutation (integer array) mapping current indices\n\t * to new indices under the sorting order.\n\t */\n\t@Override\n\tpublic int[] buildSortingPermutation()\n\t{\n\t\tint i, n;\n\t\tint perm[];\n\t\t\n\t\tn = set.size();\n\t\tperm = new int[n];\n\t\ti = 0;\n\t\tfor (Map.Entry<T, Integer> e : set.entrySet()) {\n\t\t\tperm[e.getValue()] = i++;\n\t\t}\n\t\t\n\t\treturn perm;\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn set.toString();\n\t}\n\n\t@Override\n\tpublic int get(T t)\n\t{\n\t\treturn set.get(t);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IntervalModel.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport common.Interval;\nimport prism.Evaluator;\nimport prism.PrismException;\n\npublic interface IntervalModel<Value> extends Model<Value>\n{\n\t/**\n\t * Get an Evaluator for intervals of Value.\n\t * A default implementation tries to create one from the main iterator\n\t * (which itself by default exists for the (usual) case when Value is Double).\n\t */\n\tdefault Evaluator<Interval<Value>> getIntervalEvaluator() throws PrismException\n\t{\n\t\treturn getEvaluator().createIntervalEvaluator();\n\t}\n\n\t/**\n\t * Get the underlying model over Interval<Value>.\n\t */\n\tModel<Interval<Value>> getIntervalModel();\n}\n"
  },
  {
    "path": "prism/src/explicit/IntervalModelExplicit.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport common.Interval;\nimport prism.Evaluator;\nimport prism.PrismException;\n\npublic interface IntervalModelExplicit<Value> extends IntervalModel<Value>\n{\n\t/**\n\t * Set an Evaluator for intervals of Value.\n\t * The default is for the (usual) case when Value is Double.\n\t */\n\tvoid setIntervalEvaluator(Evaluator<Interval<Value>> eval);\n}\n"
  },
  {
    "path": "prism/src/explicit/IntervalUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\nimport common.Interval;\nimport prism.Evaluator;\nimport prism.PrismException;\n\n/**\n * Various utility methods for working with intervals\n */\npublic class IntervalUtils\n{\n\t/**\n\t * Extract the details of a distribution over double-valued intervals of probabilities\n\t */\n\tpublic static DoubleIntervalDistribution extractDoubleIntervalDistribution(Distribution<Interval<Double>> distr)\n\t{\n\t\treturn extractDoubleIntervalDistribution(distr.iterator(), distr.size());\n\t}\n\t\n\t/**\n\t * Extract the details of a distribution over double-valued intervals of probabilities\n\t */\n\tpublic static DoubleIntervalDistribution extractDoubleIntervalDistribution(Iterator<Map.Entry<Integer, Interval<Double>>> iter, int size)\n\t{\n\t\tDoubleIntervalDistribution did = new DoubleIntervalDistribution(size);\n\t\tint i = 0;\n\t\twhile (iter.hasNext()) {\n\t\t\tMap.Entry<Integer, Interval<Double>> e = iter.next();\n\t\t\tdid.lower[i] = e.getValue().getLower();\n\t\t\tdid.upper[i] = e.getValue().getUpper();\n\t\t\tdid.index[i] = e.getKey();\n\t\t\ti++;\n\t\t}\n\t\treturn did;\n\t}\n\t\n\t/**\n\t * Delimit a distribution with intervals of probabilities, i.e., trim the bounds of the\n\t * intervals such that at least one possible distribution takes each of the extremal values.\n\t * The Distribution is modified directly.\n\t * @param distr The distribution to delimit\n\t * @param eval An evaluator for the interval's child type (Value)\n\t */\n\tpublic static <Value> void delimit(Distribution<Interval<Value>> distr, Evaluator<Value> eval)\n\t{\n\t\t// Compute 1 minus the sum of all bounds\n\t\tEvaluator<Interval<Value>> evalInt = distr.getEvaluator();\n\t\tInterval<Value> oneMinusSum = evalInt.subtract(evalInt.one(), distr.sum());\n\t\tValue oneMinusSumLower = oneMinusSum.getLower();\n\t\tValue oneMinusSumUpper = oneMinusSum.getUpper();\n\t\t// For each interval\n\t\tIterator<Map.Entry<Integer, Interval<Value>>> iter = distr.iterator();\n\t\twhile (iter.hasNext()) {\n\t\t\tMap.Entry<Integer, Interval<Value>> e = iter.next();\n\t\t\tInterval<Value> ival = e.getValue();\n\t\t\tValue lower = ival.getLower();\n\t\t\tValue upper = ival.getUpper();\n\t\t\t// Adjust lower bound if needed\n\t\t\tValue upperTight = eval.add(oneMinusSumUpper, upper);\n\t\t\tif (eval.gt(upperTight, lower)) {\n\t\t\t\tival.setLower(upperTight);\n\t\t\t}\n\t\t\t// Adjust upper bound if needed\n\t\t\tValue lowerTight = eval.add(oneMinusSumLower, lower);\n\t\t\tif (eval.gt(upper, lowerTight)) {\n\t\t\t\tival.setUpper(lowerTight);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Delimit a distribution with intervals of probabilities, i.e., trim the bounds of the\n\t * intervals such that at least one possible distribution takes each of the extremal values.\n\t * The intervals (passed in a List) are modified directly.\n\t * @param distr The distribution to delimit\n\t * @param eval An evaluator for the interval's child type (Value)\n\t */\n\tpublic static <Value> void delimit(List<Interval<Value>> distr, Evaluator<Value> eval) throws PrismException\n\t{\n\t\t// Compute 1 minus the sum of all bounds\n\t\tEvaluator<Interval<Value>> evalInt = eval.createIntervalEvaluator();\n\t\tInterval<Value> oneMinusSum = evalInt.subtract(evalInt.one(), evalInt.sum(distr));\n\t\tValue oneMinusSumLower = oneMinusSum.getLower();\n\t\tValue oneMinusSumUpper = oneMinusSum.getUpper();\n\t\t// For each interval\n\t\tint size = distr.size();\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tInterval<Value> ival = distr.get(i);\n\t\t\tValue lower = ival.getLower();\n\t\t\tValue upper = ival.getUpper();\n\t\t\t// Adjust lower bound if needed\n\t\t\tValue upperTight = eval.add(oneMinusSumUpper, upper);\n\t\t\tif (eval.gt(upperTight, lower)) {\n\t\t\t\tival.setLower(upperTight);\n\t\t\t}\n\t\t\t// Adjust upper bound if needed\n\t\t\tValue lowerTight = eval.add(oneMinusSumLower, lower);\n\t\t\tif (eval.gt(upper, lowerTight)) {\n\t\t\t\tival.setUpper(lowerTight);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Delimit a distribution with over double-valued intervals of probabilities, i.e., trim the bounds of the\n\t * intervals such that at least one possible distribution takes each of the extremal values.\n\t * Returns a new Distribution if it changed, and the old one if not.\n\t * @param distr The distribution to delimit\n\t */\n\tpublic Distribution<Interval<Double>> delimitDoubles(Distribution<Interval<Double>> distr)\n\t{\n\t\tDoubleIntervalDistribution did = extractDoubleIntervalDistribution(distr);\n\t\tif (delimitDoubles(did)) {\n\t\t\t// Create a new Distribution if delimiting changed it\n\t\t\tDistribution<Interval<Double>> distrNew = new Distribution<>(distr.getEvaluator());\n\t\t\tfor (int i = 0; i < did.size; i++) {\n\t\t\t\tdistrNew.add(did.index[i], new Interval<Double>(did.lower[i], did.upper[i]));\n\t\t\t}\n\t\t\treturn distrNew;\n\t\t}\n\t\treturn distr;\n\t}\n\t\n\t/**\n\t * Delimit a distribution with over double-valued intervals of probabilities, i.e., trim the bounds of the\n\t * intervals such that at least one possible distribution takes each of the extremal values.\n\t * The DoubleIntervalDistribution is modified directly.\n\t * Returns true if changes were needed.\n\t * @param did The distribution to delimit\n\t */\n\tpublic static boolean delimitDoubles(DoubleIntervalDistribution did)\n\t{\n\t\tboolean changed = false;\n\t\tfor (int i = 0; i < did.size; i++) {\n\t\t\t// Adjust lower bound if needed\n\t\t\tdouble sumRest = 0.0;\n\t\t\tfor (int j = 0; j < did.size; j++) {\n\t\t\t\tif (j != i) sumRest += did.upper[i];\n\t\t\t}\n\t\t\tif (did.lower[i] < 1.0 - sumRest) {\n\t\t\t\tdid.lower[i] = 1.0 - sumRest;\n\t\t\t\tchanged |= true;\n\t\t\t}\n\t\t\t// Adjust upper bound if needed\n\t\t\tsumRest = 0.0;\n\t\t\tfor (int j = 0; j < did.size; j++) {\n\t\t\t\tif (j != i) sumRest += did.lower[i];\n\t\t\t}\n\t\t\tif (did.upper[i] > 1.0 - sumRest) {\n\t\t\t\tdid.upper[i] = 1.0 - sumRest;\n\t\t\t\tchanged |= true;\n\t\t\t}\n\t\t}\n\t\treturn changed;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IterationMethod.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage explicit;\n\nimport java.util.PrimitiveIterator;\n\nimport common.IntSet;\nimport common.PeriodicTimer;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport prism.AccuracyFactory;\nimport prism.OptionsIntervalIteration;\nimport prism.PrismException;\nimport prism.PrismUtils;\n\n/**\n * Abstract class that encapsulates the functionality for the different iteration methods\n * (e.g., Power, Jacobi, Gauss-Seidel, ...).\n * <p>\n * Provides methods as well to do the actual work in a (topological) value or interval iteration.\n */\npublic abstract class IterationMethod {\n\n\tpublic static final int LOGGING_PRECISION = 12;\n\n\t/**\n\t * Interface for an object that provides the basic steps for a value iteration.\n\t */\n\tpublic interface IterationValIter {\n\t\t/** Initialise the value iteration with the given solution vector */\n\t\tpublic void init(double[] soln);\n\t\t/** Get the current solution vector */\n\t\tpublic double[] getSolnVector();\n\t\t/** Get the error for the solution, or an estimate of it */\n\t\tpublic double getError();\n\n\t\t/** Perform one iteration (over the set of states) and return true if convergence has been detected. */\n\t\tpublic boolean iterateAndCheckConvergence(IntSet states) throws PrismException;\n\n\t\t/**\n\t\t * Notify that the given states are done (e.g., because the given SCC is finished\n\t\t * during a topological iteration).\n\t\t * <br>\n\t\t * This allows the two-vector iteration methods to store the current values for these\n\t\t * states into the second vector, so that switching the vector does not return to\n\t\t * previous values.\n\t\t */\n\t\tpublic void doneWith(IntSet states);\n\n\t\t/**\n\t\t * Solve for a given singleton SCC consisting of {@code state} using {@code solver},\n\t\t * store the result in the solution vector(s).\n\t\t */\n\t\tpublic void solveSingletonSCC(int state, SingletonSCCSolver solver);\n\n\t\t/** Return the underlying model */\n\t\tpublic Model<?> getModel();\n\t}\n\n\t/**\n\t * Interface for an object that provides the atomic steps for a value iteration\n\t * in the context of interval iteration, i.e., for the interval iteration\n\t * there are two IterationIntervalIter objects, one from below or from above.\n\t */\n\tpublic interface IterationIntervalIter {\n\t\t/** Initialise the value iteration with the given solution vector */\n\t\tpublic void init(double[] soln);\n\t\t/** Get the current solution vector */\n\t\tpublic double[] getSolnVector();\n\n\t\t/** Perform one iteration (over the set of states) */\n\t\tpublic void iterate(IntSet states) throws PrismException;\n\n\t\t/**\n\t\t * Notify that the given states are done (e.g., because the given SCC is finished\n\t\t * during a topological iteration).\n\t\t * <br>\n\t\t * This allows the two-vector iteration methods to store the current values for these\n\t\t * states into the second vector, so that switching the vector does not return to\n\t\t * previous values.\n\t\t */\n\t\tpublic void doneWith(IntSet states);\n\n\t\t/**\n\t\t * Solve for a given singleton SCC consisting of {@code state} using {@code solver},\n\t\t * store the result in the solution vector(s).\n\t\t */\n\t\tpublic void solveSingletonSCC(int s, SingletonSCCSolver solver);\n\n\t\t/** Return the underlying model */\n\t\tpublic Model<?> getModel();\n\t}\n\n\t/** Storage for a single solution vector */\n\tpublic class IterationBasic {\n\t\tprotected final Model<?> model;\n\t\tprotected double[] soln;\n\n\t\tpublic IterationBasic(Model<?> model)\n\t\t{\n\t\t\tthis.model = model;\n\t\t}\n\n\t\tpublic void init(double[] soln)\n\t\t{\n\t\t\tthis.soln = soln;\n\t\t}\n\n\t\tpublic double[] getSolnVector()\n\t\t{\n\t\t\treturn soln;\n\t\t}\n\n\t\t/* see IterationValIter.solveSingletonSCC() */\n\t\tpublic void solveSingletonSCC(int state, SingletonSCCSolver solver)\n\t\t{\n\t\t\tsolver.solveFor(state, soln);\n\t\t}\n\n\t\t/* see IterationValIter.doneWith() */\n\t\tpublic void doneWith(IntSet states)\n\t\t{\n\t\t\t// single vector, nothing to do\n\t\t}\n\n\t\tpublic Model<?> getModel()\n\t\t{\n\t\t\treturn model;\n\t\t}\n\t}\n\n\t/** Abstract base class for an IterationValIter with a single solution vector */\n\tprotected abstract class SingleVectorIterationValIter extends IterationBasic implements IterationValIter\n\t{\n\t\t/** Store error for accuracy info; unknown (infinite) initially */\n\t\tprotected double error = Double.POSITIVE_INFINITY;\n\t\t\n\t\t@Override\n\t\tpublic double getError()\n\t\t{\n\t\t\treturn error;\n\t\t}\n\n\t\tpublic SingleVectorIterationValIter(Model<?> model)\n\t\t{\n\t\t\tsuper(model);\n\t\t}\n\t}\n\n\t/** Abstract base class for an IterationIntervalIter with a single solution vector */\n\tprotected abstract class SingleVectorIterationIntervalIter extends IterationBasic implements IterationIntervalIter\n\t{\n\t\tpublic SingleVectorIterationIntervalIter(Model<?> model)\n\t\t{\n\t\t\tsuper(model);\n\t\t}\n\t}\n\n\t/**\n\t * Functional interface for a post-processing step after an iteration that involves\n\t * a pair of solution vectors.\n\t * <br>\n\t * This method may modify solnNew.\n\t *\n\t * @param solnOld the previous solution vector\n\t * @param solnNew the new solution vector\n\t * @param states the set of states that are the focus of the current iteration\n\t */\n\t@FunctionalInterface\n\tinterface IterationPostProcessor {\n\t\tvoid apply(double[] solnOld, double[] solnNew, IntSet states) throws PrismException;\n\t}\n\n\t/**\n\t * Abstract base class for an IterationValIter / IterationIntervalIter that\n\t * requires two solution vectors.\n\t * Optionally, a post processing step is performed after each iteration.\n\t */\n\tprotected abstract class TwoVectorIteration extends IterationBasic implements IterationValIter, IterationIntervalIter {\n\t\t/** The solution vector that serves as the target vector in the iteration step */\n\t\tprotected double[] soln2;\n\t\t/** Post processing, may be null */\n\t\tprotected final IterationPostProcessor postProcessor;\n\n\t\t/** Constructor */\n\t\tprotected TwoVectorIteration(Model<?> model, IterationMethod.IterationPostProcessor postProcessor)\n\t\t{\n\t\t\tsuper(model);\n\t\t\tthis.postProcessor = postProcessor;\n\t\t}\n\n\t\t@Override\n\t\tpublic void init(double[] soln)\n\t\t{\n\t\t\tsuper.init(soln);\n\n\t\t\t// create and initialise the second solution vector\n\t\t\tsoln2 = new double[soln.length];\n\t\t\tSystem.arraycopy(soln, 0, soln2, 0, soln.length);\n\t\t}\n\n\t\t/** Perform one iteration */\n\t\tpublic abstract void doIterate(IntSet states) throws PrismException;\n\n\t\t@Override\n\t\tpublic void iterate(IntSet states) throws PrismException\n\t\t{\n\t\t\t// do the iteration\n\t\t\tdoIterate(states);\n\t\t\t// optionally, post processing\n\t\t\tif (postProcessor != null) {\n\t\t\t\tpostProcessor.apply(soln, soln2, states);\n\t\t\t}\n\n\t\t\t// switch vectors\n\t\t\tdouble[] tmp = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmp;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean iterateAndCheckConvergence(IntSet states) throws PrismException\n\t\t{\n\t\t\t// do the iteration\n\t\t\tdoIterate(states);\n\t\t\t// optionally, post processing\n\t\t\tif (postProcessor != null) {\n\t\t\t\tpostProcessor.apply(soln, soln2, states);\n\t\t\t}\n\t\t\t// check convergence (on the set of states)\n\t\t\tboolean done = PrismUtils.doublesAreClose(soln, soln2, states.iterator(), termCritParam, absolute);\n\n\t\t\t// switch vectors\n\t\t\tdouble[] tmp = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmp;\n\n\t\t\treturn done;\n\t\t}\n\n\t\t@Override\n\t\tpublic double getError()\n\t\t{\n\t\t\treturn PrismUtils.measureSupNorm(soln, soln2, absolute);\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic void doneWith(IntSet states)\n\t\t{\n\t\t\t// we copy the values for the given states to the\n\t\t\t// second vector, so that switching between vectors\n\t\t\t// does not change their values\n\t\t\tPrimitiveIterator.OfInt it = states.iterator();\n\t\t\twhile (it.hasNext()) {\n\t\t\t\tint state = it.nextInt();\n\t\t\t\tsoln2[state] = soln[state];\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic void solveSingletonSCC(int state, SingletonSCCSolver solver)\n\t\t{\n\t\t\t// solve and store result in soln vector\n\t\t\tsuper.solveSingletonSCC(state, solver);\n\t\t\t// copy result to soln2 vector as well\n\t\t\tsoln2[state] = soln[state];\n\t\t}\n\n\t}\n\n\t/**\n\t * Functional interface for a method that allows to\n\t * determine the value for a singleton SCC in the model,\n\t * given that all successor value have already been computed.\n\t */\n\t@FunctionalInterface\n\tpublic interface SingletonSCCSolver {\n\t\t/**\n\t\t * Compute the value for state {@code state}, under the assumption\n\t\t * that it constitutes a (trivial or non-trivial) singleton SCC\n\t\t * and that all successor values have already been computed in {@code soln}.\n\t\t * Stores the result in {@code soln[state]}.\n\t\t */\n\t\tpublic void solveFor(int state, double[] soln);\n\t}\n\n\t/** Convergence check: absolute or relative? */\n\tprotected final boolean absolute;\n\t/** Convergence check: epsilon value */\n\tprotected final double termCritParam;\n\n\t/**\n\t * Constructor.\n\t * @param absolute For convergence check, perform absolute comparison?\n\t * @param termCritParam For convergence check, the epsilon value to use\n\t */\n\tprotected IterationMethod(boolean absolute, double termCritParam)\n\t{\n\t\tthis.absolute = absolute;\n\t\tthis.termCritParam = termCritParam;\n\t}\n\n\t// ------------ Abstract DTMC methods ----------------------------\n\n\t/** Obtain an Iteration object using mvMult (matrix-vector multiplication) in a DTMC */\n\tpublic abstract IterationValIter forMvMult(DTMC<Double> dtmc) throws PrismException;\n\n\t/**\n\t * Obtain an Iteration object (for interval iteration) using mvMult\n\t * (matrix-vector multiplication) in a DTMC.\n\t * @param fromBelow for interval iteration from below?\n\t * @param enforceMonotonic enforce element-wise monotonicity of the solution vector\n\t * @param checkMonotonic check the element-wise monotonicity of the solution vector, throw exception if violated\n\t */\n\tpublic abstract IterationIntervalIter forMvMultInterval(DTMC<Double> dtmc, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity) throws PrismException;\n\n\t/** Obtain an Iteration object using mvMultRew (matrix-vector multiplication with rewards) in a DTMC */\n\tpublic abstract IterationValIter forMvMultRew(DTMC<Double> dtmc, MCRewards<Double> rew) throws PrismException;\n\n\t/**\n\t * Obtain an Iteration object (for interval iteration) using mvMultRew\n\t * (matrix-vector multiplication with rewards) in a DTMC.\n\t * @param fromBelow for interval iteration from below?\n\t * @param enforceMonotonic enforce element-wise monotonicity of the solution vector\n\t * @param checkMonotonic check the element-wise monotonicity of the solution vector, throw exception if violated\n\t */\n\tpublic abstract IterationIntervalIter forMvMultRewInterval(DTMC<Double> dtmc, MCRewards<Double> rew, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity) throws PrismException;\n\n\t// ------------ Abstract MDP methods ----------------------------\n\n\t/**\n\t * Obtain an Iteration object using mvMultMinMax (matrix-vector multiplication, followed by min/max)\n\t * in an MDP.\n\t * @param mdp the MDP\n\t * @param min do min?\n\t * @param strat optional, storage for strategy, ignored if null\n\t */\n\tpublic abstract IterationValIter forMvMultMinMax(MDP<Double> mdp, boolean min, int[] strat) throws PrismException;\n\n\t/**\n\t * Obtain an Iteration object using mvMultMinMax (matrix-vector multiplication, followed by min/max)\n\t * in an MDP, for interval iteration.\n\t * @param mdp the MDP\n\t * @param min do min?\n\t * @param strat optional, storage for strategy, ignored if null\n\t * @param fromBelow for interval iteration from below?\n\t * @param enforceMonotonic enforce element-wise monotonicity of the solution vector\n\t * @param checkMonotonic check the element-wise monotonicity of the solution vector, throw exception if violated\n\t */\n\tpublic abstract IterationIntervalIter forMvMultMinMaxInterval(MDP<Double> mdp, boolean min, int[] strat, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity) throws PrismException;\n\n\t/**\n\t * Obtain an Iteration object using mvMultRewMinMax (matrix-vector multiplication with rewards, followed by min/max)\n\t * in an MDP.\n\t * @param mdp the MDP\n\t * @param rewards the reward structure\n\t * @param min do min?\n\t * @param strat optional, storage for strategy, ignored if null\n\t */\n\tpublic abstract IterationValIter forMvMultRewMinMax(MDP<Double> mdp, MDPRewards<Double> rewards, boolean min, int[] strat) throws PrismException;\n\n\t/**\n\t * Obtain an Iteration object using mvMultRewMinMax (matrix-vector multiplication with rewards, followed by min/max)\n\t * in an MDP, for interval iteration.\n\t * @param mdp the MDP\n\t * @param rewards the reward structure\n\t * @param min do min?\n\t * @param strat optional, storage for strategy, ignored if null\n\t * @param fromBelow for interval iteration from below?\n\t * @param enforceMonotonic enforce element-wise monotonicity of the solution vector\n\t * @param checkMonotonic check the element-wise monotonicity of the solution vector, throw exception if violated\n\t */\n\tpublic abstract IterationIntervalIter forMvMultRewMinMaxInterval(MDP<Double> mdp, MDPRewards<Double> rewards, boolean min, int[] strat, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity) throws PrismException;\n\n\t// ------------ Abstract IDTMC/MDP methods ----------------------------\n\n\t/**\n\t * Obtain an Iteration object using mvMultUnc (matrix-vector multiplication, followed by min/max)\n\t * in an UDTMC.\n\t * @param udtmc the UDTMC\n\t * @param minMax min/max info\n\t */\n\tpublic abstract IterationValIter forMvMultMinMaxUnc(UDTMC<Double> udtmc, MinMax minMax) throws PrismException;\n\t\n\t/**\n\t * Obtain an Iteration object using mvMultRewUnc (matrix-vector multiplication with rewards, followed by min/max)\n\t * in an UDTMC.\n\t * @param udtmc the UDTMC\n\t * @param mcRewards the reward structure\n\t * @param minMax min/max info\n\t */\n\tpublic abstract IterationValIter forMvMultRewMinMaxUnc(UDTMC<Double> udtmc, MCRewards<Double> mcRewards, MinMax minMax) throws PrismException;\n\t\n\t/**\n\t * Obtain an Iteration object using mvMultUnc (matrix-vector multiplication, followed by min/max)\n\t * in an IMDP.\n\t * @param imdp the IMDP\n\t * @param minMax min/max info\n\t * @param strat optional, storage for strategy, ignored if null\n\t */\n\tpublic abstract IterationValIter forMvMultMinMaxUnc(UMDP<Double> imdp, MinMax minMax, int[] strat) throws PrismException;\n\t\n\t/**\n\t * Obtain an Iteration object using mvMultRewUnc (matrix-vector multiplication with rewards, followed by min/max)\n\t * in an IMDP.\n\t * @param imdp the IMDP\n\t * @param mdpRewards the reward structure\n\t * @param minMax min/max info\n\t * @param strat optional, storage for strategy, ignored if null\n\t */\n\tpublic abstract IterationValIter forMvMultRewMinMaxUnc(UMDP<Double> imdp, MDPRewards<Double> mdpRewards, MinMax minMax, int[] strat) throws PrismException;\n\t\n\t// ------------ Abstract generic methods ----------------------------\n\n\t/**\n\t * Return a description of this iteration method for display.\n\t */\n\tpublic abstract String getDescriptionShort();\n\n\n\t// ------------ Value iteration implementations ----------------------------\n\n\t/**\n\t * Perform the actual work of a value iteration, i.e., iterate until convergence or abort.\n\t * @param mc ProbModelChecker (for log and settings)\n\t * @param description (for logging)\n\t * @param iteration The iteration object\n\t * @param unknownStates The set of unknown states, i.e., whose value should be determined\n\t * @param startTime The start time (for logging purposes, obtained from a call to System.currentTimeMillis())\n\t * @param iterationsExport an ExportIterations object (optional, ignored if null)\n\t * @return a ModelChecker result with the solution vector and statistics\n\t * @throws PrismException on non-convergence (if mc.errorOnNonConverge is set)\n\t */\n\tpublic ModelCheckerResult doValueIteration(ProbModelChecker mc, String description, IterationValIter iteration, IntSet unknownStates, long startTime, ExportIterations iterationsExport) throws PrismException\n\t{\n\t\tint iters = 0;\n\t\tfinal int maxIters = mc.maxIters;\n\t\tboolean done = false;\n\n\t\tPeriodicTimer updatesTimer = new PeriodicTimer(ProbModelChecker.UPDATE_DELAY);\n\t\tupdatesTimer.start();\n\n\t\twhile (!done && iters < maxIters) {\n\t\t\titers++;\n\t\t\t// do iteration step\n\t\t\tdone = iteration.iterateAndCheckConvergence(unknownStates);\n\n\t\t\tif (iterationsExport != null)\n\t\t\t\titerationsExport.exportVector(iteration.getSolnVector(), 0);\n\n\t\t\tif (!done && updatesTimer.triggered()) {\n\t\t\t\tmc.getLog().print(\"Iteration \" + iters + \": \");\n\t\t\t\tmc.getLog().println(PrismUtils.formatDouble2dp(updatesTimer.elapsedMillisTotal() / 1000.0) + \" sec so far\");\n\t\t\t}\n\t\t}\n\n\t\t// Finished value iteration\n\t\tlong mvCount = iters * iteration.getModel().getNumTransitions(unknownStates.iterator());\n\t\tlong timer = System.currentTimeMillis() - startTime;\n\t\tmc.getLog().print(\"Value iteration (\" + description + \")\");\n\t\tmc.getLog().print(\" took \" + iters + \" iterations, \");\n\t\tmc.getLog().print(mvCount + \" multiplications\");\n\t\tmc.getLog().println(\" and \" + timer / 1000.0 + \" seconds.\");\n\n\t\tif (iterationsExport != null)\n\t\t\titerationsExport.close();\n\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && mc.errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\";\n\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\tres.soln = iteration.getSolnVector();\n\t\tres.accuracy = AccuracyFactory.valueIteration(termCritParam, iteration.getError(), absolute);\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Perform the actual work of a topological value iteration, i.e., iterate until convergence or abort.\n\t *\n\t * @param mc ProbModelChecker (for log and settings)\n\t * @param description (for logging)\n\t * @param sccs The information about the SCCs and topological order\n\t * @param iteration The iteration object\n\t * @param singletonSCCSolver The solver for singleton SCCs\n\t * @param startTime The start time (for logging purposes, obtained from a call to System.currentTimeMillis())\n\t * @param iterationsExport an ExportIterations object (optional, ignored if null)\n\t * @return a ModelChecker result with the solution vector and statistics\n\t * @throws PrismException on non-convergence (if mc.errorOnNonConverge is set)\n\t */\n\tpublic ModelCheckerResult doTopologicalValueIteration(ProbModelChecker mc, String description, SCCInfo sccs, IterationMethod.IterationValIter iterator, SingletonSCCSolver singletonSCCSolver, long startTime, ExportIterations iterationsExport) throws PrismException\n\t{\n\t\t// Start iterations\n\t\tint iters = 0;\n\t\tlong mvCount = 0;\n\t\tfinal int maxIters = mc.maxIters;\n\t\tdouble error = 0.0;\n\n\t\tint numSCCs = sccs.getNumSCCs();\n\t\tint numNonSingletonSCCs = sccs.countNonSingletonSCCs();\n\t\tint finishedNonSingletonSCCs = 0;\n\n\t\tPeriodicTimer updatesTimer = new PeriodicTimer(ProbModelChecker.UPDATE_DELAY);\n\t\tupdatesTimer.start();\n\n\t\tboolean done = true;\n\t\tfor (int scc = 0; scc < numSCCs; scc++) {\n\t\t\tboolean doneSCC;\n\n\t\t\tif (sccs.isSingletonSCC(scc)) {\n\t\t\t\t// get the single state in this SCC\n\t\t\t\tint state = sccs.getStatesForSCC(scc).iterator().nextInt();\n\t\t\t\titerator.solveSingletonSCC(state, singletonSCCSolver);\n\n\t\t\t\t// no need to call doneWith(...), as solveSingletonSCC updates\n\t\t\t\t// both vectors for two-iteration methods\n\n\t\t\t\tmvCount += iterator.getModel().getNumTransitions(state);\n\n\t\t\t\titers++;\n\t\t\t\tif (iterationsExport != null)\n\t\t\t\t\titerationsExport.exportVector(iterator.getSolnVector(), 0);\n\n\t\t\t\tdoneSCC = true;\n\t\t\t} else {\n\t\t\t\t// complex SCC: do VI\n\t\t\t\tdoneSCC = false;\n\t\t\t\tIntSet statesForSCC = sccs.getStatesForSCC(scc);\n\t\t\t\tint itersInSCC = 0;\n\t\t\t\t// abort on convergence or if iterations *in this SCC* are above maxIters\n\t\t\t\twhile (!doneSCC && itersInSCC < maxIters) {\n\t\t\t\t\titers++;\n\t\t\t\t\titersInSCC++;\n\t\t\t\t\t// do iteration step\n\t\t\t\t\tdoneSCC = iterator.iterateAndCheckConvergence(statesForSCC);\n\n\t\t\t\t\tif (iterationsExport != null)\n\t\t\t\t\t\titerationsExport.exportVector(iterator.getSolnVector(), 0);\n\n\t\t\t\t\tif (!doneSCC && updatesTimer.triggered()) {\n\t\t\t\t\t\tmc.getLog().print(\"Iteration \" + iters + \": \");\n\t\t\t\t\t\tmc.getLog().print(\"Iteration \" + itersInSCC + \" in SCC \" + (finishedNonSingletonSCCs+1) + \" of \" + numNonSingletonSCCs);\n\t\t\t\t\t\tmc.getLog().println(\", \" + PrismUtils.formatDouble2dp(updatesTimer.elapsedMillisTotal() / 1000.0) + \" sec so far\");\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// keep track of the max error so far (because calling doneWith() below\n\t\t\t\t// makes parts of the two vectors equal and the error is lost)\n\t\t\t\terror = Math.max(error, iterator.getError());\n\t\t\t\t\n\t\t\t\t// notify the iterator that the states are done so that\n\t\t\t\t// their values can be copied to the second vector in a two-vector\n\t\t\t\t// iterator\n\t\t\t\titerator.doneWith(statesForSCC);\n\n\t\t\t\tmvCount += itersInSCC * iterator.getModel().getNumTransitions(statesForSCC.iterator());\n\t\t\t}\n\n\t\t\tif (!doneSCC) {\n\t\t\t\tdone = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\t// Finished value iteration\n\t\tlong timer = System.currentTimeMillis() - startTime;\n\t\tmc.getLog().print(\"Value iteration (\" + description + \", with \" + numNonSingletonSCCs + \" non-singleton SCCs)\");\n\t\tmc.getLog().print(\" took \" + iters + \" iterations, \");\n\t\tmc.getLog().print(mvCount + \" multiplications\");\n\t\tmc.getLog().println(\" and \" + timer / 1000.0 + \" seconds.\");\n\n\t\tif (iterationsExport != null)\n\t\t\titerationsExport.close();\n\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && mc.errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\";\n\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\tres.soln = iterator.getSolnVector();\n\t\tres.accuracy = AccuracyFactory.valueIteration(termCritParam, error, absolute);\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Perform the actual work of an interval iteration, i.e., iterate until convergence or abort.\n\t *\n\t * @param mc ProbModelChecker (for log and settings)\n\t * @param description Description (for logging)\n\t * @param below The iteration object for the iteration from below\n\t * @param above The iteration object for the iteration from above\n\t * @param unknownStates The set of unknown states, i.e., whose value should be determined\n\t * @param startTime The start time (for logging purposes, obtained from a call to System.currentTimeMillis())\n\t * @param iterationsExport an ExportIterations object (optional, ignored if null)\n\t * @return a ModelChecker result with the solution vector and statistics\n\t * @throws PrismException on non-convergence (if mc.errorOnNonConverge is set)\n\t */\n\tpublic ModelCheckerResult doIntervalIteration(ProbModelChecker mc, String description, IterationIntervalIter below, IterationIntervalIter above, IntSet unknownStates, long timer, ExportIterations iterationsExport) throws PrismException {\n\t\ttry {\n\t\t\t// Start iterations\n\t\t\tint iters = 0;\n\t\t\tfinal int maxIters = mc.maxIters;\n\t\t\tboolean done = false;\n\t\t\tdouble maxError = Double.POSITIVE_INFINITY;\n\n\t\t\tPeriodicTimer updatesTimer = new PeriodicTimer(ProbModelChecker.UPDATE_DELAY);\n\t\t\tupdatesTimer.start();\n\n\t\t\twhile (!done && iters < maxIters) {\n\t\t\t\titers++;\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\tbelow.iterate(unknownStates);\n\t\t\t\tabove.iterate(unknownStates);\n\n\t\t\t\tif (iterationsExport != null) {\n\t\t\t\t\titerationsExport.exportVector(below.getSolnVector(), 0);\n\t\t\t\t\titerationsExport.exportVector(above.getSolnVector(), 1);\n\t\t\t\t}\n\n\t\t\t\tintervalIterationCheckForProblems(below.getSolnVector(), above.getSolnVector(), unknownStates.iterator());\n\n\t\t\t\t// Check termination\n\t\t\t\tdone = PrismUtils.doublesAreClose(below.getSolnVector(), above.getSolnVector(), termCritParam, absolute);\n\n\t\t\t\tif (done) {\n\t\t\t\t\tmaxError = PrismUtils.measureSupNormInterval(below.getSolnVector(), above.getSolnVector(), absolute);\n\t\t\t\t\tmc.getLog().println(\"Max \" + (!absolute ? \"relative \": \"\") +\n\t\t\t\t\t\t\t\"diff between upper and lower bound on convergence: \" + PrismUtils.formatDouble(LOGGING_PRECISION, maxError));\n\t\t\t\t\tdone = true;\n\t\t\t\t}\n\n\t\t\t\tif (!done && updatesTimer.triggered()) {\n\t\t\t\t\tdouble diff = PrismUtils.measureSupNormInterval(below.getSolnVector(), above.getSolnVector(), absolute);\n\t\t\t\t\tmc.getLog().print(\"Iteration \" + iters + \": \");\n\t\t\t\t\tmc.getLog().print(\"max \" + (absolute ? \"\" : \"relative \") + \"diff=\" + PrismUtils.formatDouble(LOGGING_PRECISION, diff));\n\t\t\t\t\tmc.getLog().println(\", \" + PrismUtils.formatDouble2dp(updatesTimer.elapsedMillisTotal() / 1000.0) + \" sec so far\");\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Finished value iteration\n\t\t\tlong mvCount = 2 * iters * below.getModel().getNumTransitions(unknownStates.iterator());\n\t\t\ttimer = System.currentTimeMillis() - timer;\n\t\t\tmc.getLog().print(\"Interval iteration (\" + description + \")\");\n\t\t\tmc.getLog().print(\" took \" + iters + \" iterations, \");\n\t\t\tmc.getLog().print(mvCount + \" multiplications\");\n\t\t\tmc.getLog().println(\" and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t\tif (done && OptionsIntervalIteration.from(mc.getSettings()).isSelectMidpointForResult()) {\n\t\t\t\tPrismUtils.selectMidpoint(below.getSolnVector(), above.getSolnVector());\n\n\t\t\t\tif (iterationsExport != null) {\n\t\t\t\t\t// export midpoint\n\t\t\t\t\titerationsExport.exportVector(below.getSolnVector(), 0);\n\t\t\t\t\titerationsExport.exportVector(below.getSolnVector(), 1);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Non-convergence is an error (usually)\n\t\t\tif (!done && mc.errorOnNonConverge) {\n\t\t\t\tString msg = \"Iterative method (interval iteration) did not converge within \" + iters + \" iterations.\";\n\t\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\t\tthrow new PrismException(msg);\n\t\t\t}\n\n\t\t\t// Return results\n\t\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\t\tres.soln = below.getSolnVector();\n\t\t\tres.accuracy = AccuracyFactory.guaranteedNumericalIterative(maxError, absolute);\n\t\t\tres.numIters = iters;\n\t\t\tres.timeTaken = timer / 1000.0;\n\t\t\treturn res;\n\t\t} finally {\n\t\t\tif (iterationsExport != null)\n\t\t\t\titerationsExport.close();\n\t\t}\n\t}\n\n\t/**\n\t * Perform the actual work of a topological interval iteration, i.e., iterate until convergence or abort.\n\t *\n\t * @param mc ProbModelChecker (for log and settings)\n\t * @param description Description (for logging)\n\t * @param sccs The information about the SCCs and topological order\n\t * @param below The iteration object for the value iteration from below\n\t * @param above The iteration object for the value iteration from above\n\t * @param singletonSCCSolver The solver for singleton SCCs\n\t * @param startTime The start time (for logging purposes, obtained from a call to System.currentTimeMillis())\n\t * @param iterationsExport an ExportIterations object (optional, ignored if null)\n\t * @return a ModelChecker result with the solution vector and statistics\n\t * @throws PrismException on non-convergence (if mc.errorOnNonConverge is set)\n\t */\n\tpublic ModelCheckerResult doTopologicalIntervalIteration(ProbModelChecker mc, String description, SCCInfo sccs, IterationIntervalIter below, IterationIntervalIter above, SingletonSCCSolver singletonSCCSolver, long timer, ExportIterations iterationsExport) throws PrismException {\n\t\ttry {\n\t\t\t// Start iterations\n\t\t\tint iters = 0;\n\t\t\tlong mvCount = 0;\n\t\t\tfinal int maxIters = mc.maxIters;\n\t\t\tdouble maxError = Double.POSITIVE_INFINITY;\n\n\t\t\tPeriodicTimer updatesTimer = new PeriodicTimer(ProbModelChecker.UPDATE_DELAY);\n\t\t\tupdatesTimer.start();\n\n\t\t\tint numSCCs = sccs.getNumSCCs();\n\t\t\tint numNonSingletonSCCs = sccs.countNonSingletonSCCs();\n\t\t\tint finishedNonSingletonSCCs = 0;\n\n\t\t\tboolean done = true;\n\t\t\tfor (int scc = 0; scc < numSCCs; scc++) {\n\t\t\t\tboolean doneSCC;\n\n\t\t\t\tif (sccs.isSingletonSCC(scc)) {\n\t\t\t\t\t// get the single state in this SCC\n\t\t\t\t\tint state = sccs.getStatesForSCC(scc).iterator().nextInt();\n\t\t\t\t\tbelow.solveSingletonSCC(state, singletonSCCSolver);\n\t\t\t\t\tabove.solveSingletonSCC(state, singletonSCCSolver);\n\n\t\t\t\t\t// no need to call doneWith(...), as solveSingletonSCC updates\n\t\t\t\t\t// both vectors for two-iteration methods\n\n\t\t\t\t\titers++;\n\t\t\t\t\tmvCount += 2 * below.getModel().getNumTransitions(state);\n\n\t\t\t\t\tif (iterationsExport != null) {\n\t\t\t\t\t\titerationsExport.exportVector(below.getSolnVector(), 0);\n\t\t\t\t\t\titerationsExport.exportVector(above.getSolnVector(), 1);\n\t\t\t\t\t}\n\n\t\t\t\t\tintervalIterationCheckForProblems(below.getSolnVector(), above.getSolnVector(), IntSet.asIntSet(state).iterator());\n\n\t\t\t\t\tdoneSCC = true;\n\t\t\t\t} else {\n\t\t\t\t\t// complex SCC: do VI\n\t\t\t\t\tdoneSCC = false;\n\t\t\t\t\tint itersInSCC = 0;\n\n\t\t\t\t\tIntSet statesForSCC = sccs.getStatesForSCC(scc);\n\n\t\t\t\t\t// Adjust upper bound by adding 2*epsilon,\n\t\t\t\t\t// adding 1*epsilon would be fine, but we are a bit more conservative.\n\t\t\t\t\t// TODO: We also don't really need to do adjustment for bottom SCCs...\n\t\t\t\t\tPrimitiveIterator.OfInt it = statesForSCC.iterator();\n\t\t\t\t\tfinal double[] solnAbove = above.getSolnVector();\n\t\t\t\t\tfinal double adjustment = 2*termCritParam;\n\t\t\t\t\twhile (it.hasNext()) {\n\t\t\t\t\t\tsolnAbove[it.nextInt()] += adjustment;\n\t\t\t\t\t}\n\n\t\t\t\t\t// abort on convergence or if iterations *in this SCC* are above maxIters\n\t\t\t\t\twhile (!doneSCC && itersInSCC < maxIters) {\n\t\t\t\t\t\titers++;\n\t\t\t\t\t\titersInSCC++;\n\n\t\t\t\t\t\t// do iteration step\n\t\t\t\t\t\tbelow.iterate(statesForSCC);\n\t\t\t\t\t\tabove.iterate(statesForSCC);\n\n\t\t\t\t\t\tif (iterationsExport != null) {\n\t\t\t\t\t\t\titerationsExport.exportVector(below.getSolnVector(), 0);\n\t\t\t\t\t\t\titerationsExport.exportVector(above.getSolnVector(), 1);\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\tintervalIterationCheckForProblems(below.getSolnVector(), above.getSolnVector(), statesForSCC.iterator());\n\n\t\t\t\t\t\t// Check termination (inside SCC)\n\t\t\t\t\t\tdoneSCC = PrismUtils.doublesAreClose(below.getSolnVector(), above.getSolnVector(), statesForSCC.iterator(), termCritParam, absolute);\n\n\t\t\t\t\t\tif (!doneSCC && updatesTimer.triggered()) {\n\t\t\t\t\t\t\tdouble diff = PrismUtils.measureSupNormInterval(below.getSolnVector(), above.getSolnVector(), absolute, statesForSCC.iterator());\n\t\t\t\t\t\t\tmc.getLog().print(\"Iteration \" + iters + \": \");\n\t\t\t\t\t\t\tmc.getLog().print(\"max \" + (absolute ? \"\" : \"relative \") + \"diff (for iteration \" + itersInSCC + \" in current SCC \" + (finishedNonSingletonSCCs+1) + \" of \" + numNonSingletonSCCs + \") = \" + PrismUtils.formatDouble(LOGGING_PRECISION, diff));\n\t\t\t\t\t\t\tmc.getLog().println(\", \" + PrismUtils.formatDouble2dp(updatesTimer.elapsedMillisTotal() / 1000.0) + \" sec so far\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// notify the iterators that the states are done so that\n\t\t\t\t\t// their values can be copied to the second vector in a two-vector\n\t\t\t\t\t// iterator\n\t\t\t\t\tbelow.doneWith(statesForSCC);\n\t\t\t\t\tabove.doneWith(statesForSCC);\n\n\t\t\t\t\tmvCount += 2 * itersInSCC * below.getModel().getNumTransitions(statesForSCC.iterator());\n\t\t\t\t\tfinishedNonSingletonSCCs++;\n\t\t\t\t}\n\n\t\t\t\tif (!doneSCC) {\n\t\t\t\t\tdone = false;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (done) {\n\t\t\t\tmaxError = PrismUtils.measureSupNormInterval(below.getSolnVector(), above.getSolnVector(), absolute);\n\t\t\t\tmc.getLog().println(\"Max \" + (absolute ? \"\" : \"relative \") +\n\t\t\t\t\t\t\"diff between upper and lower bound on convergence: \" + PrismUtils.formatDouble(LOGGING_PRECISION, maxError));\n\t\t\t\tdone = true;\n\t\t\t}\n\n\t\t\t// Finished value iteration\n\t\t\ttimer = System.currentTimeMillis() - timer;\n\t\t\tmc.getLog().print(\"Interval iteration (\" + description + \", with \" + numNonSingletonSCCs + \" non-singleton SCCs)\");\n\t\t\tmc.getLog().print(\" took \" + iters + \" iterations, \");\n\t\t\tmc.getLog().print(mvCount + \" multiplications\");\n\t\t\tmc.getLog().println(\" and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t\tif (done && OptionsIntervalIteration.from(mc.getSettings()).isSelectMidpointForResult()) {\n\t\t\t\tPrismUtils.selectMidpoint(below.getSolnVector(), above.getSolnVector());\n\n\t\t\t\tif (iterationsExport != null) {\n\t\t\t\t\t// export midpoint\n\t\t\t\t\titerationsExport.exportVector(below.getSolnVector(), 0);\n\t\t\t\t\titerationsExport.exportVector(below.getSolnVector(), 1);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (iterationsExport != null)\n\t\t\t\titerationsExport.close();\n\n\t\t\t// Non-convergence is an error (usually)\n\t\t\tif (!done && mc.errorOnNonConverge) {\n\t\t\t\tString msg = \"Iterative method (interval iteration) did not converge within \" + iters + \" iterations.\";\n\t\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\t\tthrow new PrismException(msg);\n\t\t\t}\n\n\t\t\t// Return results\n\t\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\t\tres.soln = below.getSolnVector();\n\t\t\tres.accuracy = AccuracyFactory.guaranteedNumericalIterative(maxError, absolute);\n\t\t\tres.numIters = iters;\n\t\t\tres.timeTaken = timer / 1000.0;\n\t\t\treturn res;\n\t\t} finally {\n\t\t\tif (iterationsExport != null)\n\t\t\t\titerationsExport.close();\n\t\t}\n\t}\n\n\t/**\n\t * Compares the current lower and upper solution vectors in an interval iteration\n\t * and throws an exception if lower bound values are larger than upper bound values,\n\t * as this indicates problems.\n\t * @param lower the current lower iteration solution vector\n\t * @param upper the current upper iteration solution vector\n\t * @param states iterator over the states in question\n\t */\n\tprivate static void intervalIterationCheckForProblems(double[] lower, double[] upper, PrimitiveIterator.OfInt states) throws PrismException\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tif (lower[s] > upper[s]) {\n\t\t\t\tthrow new PrismException(\"In interval iteration, the lower value (\" + lower[s] + \") is larger than the upper value (\" + upper[s] + \").\\n\"\n\t\t\t\t\t\t+ \"This indicates either problems with numerical stability (rounding, precision of the floating-point representation) or that the initial bounds (for reward computations) are incorrect\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Perform a post-processing for a two-vector value iteration.\n\t * @param solnOld the previous solution vector\n\t * @param solnNew the newly computed solution vector\n\t * @param states the relevant set of states\n\t * @param fromBelow are we iterating from below?\n\t * @param enforceMonotonicity if true, enforces monotonicity\n\t * @param checkMonotonicity if true, checks for monotonicity (and throws error when non-monotonic)\n\t */\n\tpublic static void twoVectorPostProcessing(double[] solnOld, double[] solnNew, IntSet states, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity) throws PrismException\n\t{\n\t\t// TODO: use IntSet states\n\t\tif (enforceMonotonicity)\n\t\t\tif (fromBelow) {\n\t\t\t\tPrismUtils.ensureMonotonicityFromBelow(solnOld, solnNew);\n\t\t\t} else {\n\t\t\t\tPrismUtils.ensureMonotonicityFromAbove(solnOld, solnNew);\n\t\t\t}\n\n\t\tif (checkMonotonicity) {\n\t\t\tPrismUtils.checkMonotonicity(solnOld, solnNew, !fromBelow);\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/explicit/IterationMethodGS.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport common.IntSet;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport prism.PrismException;\n\n/**\n * IterationMethod that encapsulates the functionality of the Gauss-Seidel method (forward/backward).\n */\npublic class IterationMethodGS extends IterationMethod {\n\t/** Do backwards Gauss-Seidel? */\n\tprivate boolean backwards;\n\n\t/**\n\t * Constructor.\n\t * @param absolute For convergence check, perform absolute comparison?\n\t * @param termCritParam For convergence check, the epsilon value to use\n\t * @param backwards Do backwards Gauss-Seidel?\n\t */\n\tIterationMethodGS(boolean absolute, double epsilon, boolean backwards)\n\t{\n\t\tsuper(absolute, epsilon);\n\t\tthis.backwards = backwards;\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMult(DTMC<Double> dtmc)\n\t{\n\t\treturn new SingleVectorIterationValIter(dtmc) {\n\t\t\t@Override\n\t\t\tpublic boolean iterateAndCheckConvergence(IntSet states)\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\terror = dtmc.mvMultGS(soln,\n\t\t\t\t                               backwards ? states.reversedIterator() : states.iterator(),\n\t\t\t\t                               absolute);\n\n\t\t\t\t// Check termination\n\t\t\t\treturn (error < termCritParam);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultInterval(DTMC<Double> dtmc, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity)\n\t{\n\t\treturn new SingleVectorIterationIntervalIter(dtmc) {\n\t\t\t@Override\n\t\t\tpublic void iterate(IntSet states) throws PrismException\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\tdtmc.mvMultGSIntervalIter(soln,\n\t\t\t\t                          backwards ? states.reversedIterator() : states.iterator(),\n\t\t\t\t                          enforceMonotonicity,\n\t\t\t\t                          checkMonotonicity,\n\t\t\t\t                          fromBelow);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRew(DTMC<Double> dtmc, MCRewards<Double> rew)\n\t{\n\t\treturn new SingleVectorIterationValIter(dtmc) {\n\t\t\t@Override\n\t\t\tpublic boolean iterateAndCheckConvergence(IntSet states)\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\terror = dtmc.mvMultRewGS(soln,\n\t\t\t\t                                  rew,\n\t\t\t\t                                  backwards ? states.reversedIterator() : states.iterator(),\n\t\t\t\t                                  absolute);\n\n\t\t\t\t// Check termination\n\t\t\t\treturn (error < termCritParam);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultRewInterval(DTMC<Double> dtmc, MCRewards<Double> rew, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity)\n\t{\n\t\treturn new SingleVectorIterationIntervalIter(dtmc) {\n\t\t\t@Override\n\t\t\tpublic void iterate(IntSet states) throws PrismException\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\tdtmc.mvMultRewGSIntervalIter(soln,\n\t\t\t\t\t                          rew,\n\t\t\t\t\t                          backwards ? states.reversedIterator() : states.iterator(),\n\t\t\t\t\t                          enforceMonotonicity,\n\t\t\t\t\t                          checkMonotonicity,\n\t\t\t\t\t                          fromBelow);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultMinMax(MDP<Double> mdp, boolean min, int[] strat)\n\t{\n\t\treturn new SingleVectorIterationValIter(mdp) {\n\t\t\t@Override\n\t\t\tpublic boolean iterateAndCheckConvergence(IntSet states)\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\terror = mdp.mvMultGSMinMax(soln,\n\t\t\t\t                                    min,\n\t\t\t\t                                    backwards ? states.reversedIterator() : states.iterator(),\n\t\t\t\t                                    absolute,\n\t\t\t\t                                    strat);\n\n\t\t\t\t// Check termination\n\t\t\t\treturn (error < termCritParam);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultMinMaxInterval(MDP<Double> mdp, boolean min, int[] strat, boolean fromBelow, boolean enforceMonotonicity,\n\t\t\tboolean checkMonotonicity) throws PrismException\n\t{\n\t\treturn new SingleVectorIterationIntervalIter(mdp) {\n\t\t\t@Override\n\t\t\tpublic void iterate(IntSet states)\n\t\t\t{\n\t\t\t\t// TODO: check monotonic not yet supported\n\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\tmdp.mvMultGSMinMaxIntervalIter(soln,\n\t\t\t\t                               min,\n\t\t\t\t                               backwards ? states.reversedIterator() : states.iterator(),\n\t\t\t\t                               strat,\n\t\t\t\t                               enforceMonotonicity,\n\t\t\t\t                               fromBelow);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMax(MDP<Double> mdp, MDPRewards<Double> rewards, boolean min, int[] strat) throws PrismException\n\t{\n\t\treturn new SingleVectorIterationValIter(mdp) {\n\t\t\t@Override\n\t\t\tpublic boolean iterateAndCheckConvergence(IntSet states)\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\terror = mdp.mvMultRewGSMinMax(soln,\n\t\t\t\t                                       rewards,\n\t\t\t\t                                       min,\n\t\t\t\t                                       backwards ? states.reversedIterator() : states.iterator(),\n\t\t\t\t                                       absolute,\n\t\t\t\t                                       strat);\n\n\t\t\t\t// Check termination\n\t\t\t\treturn (error < termCritParam);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultRewMinMaxInterval(MDP<Double> mdp, MDPRewards<Double> rewards, boolean min, int[] strat, boolean fromBelow,\n\t\t\tboolean enforceMonotonicity, boolean checkMonotonicity) throws PrismException\n\t{\n\t\treturn new SingleVectorIterationIntervalIter(mdp) {\n\t\t\t@Override\n\t\t\tpublic void iterate(IntSet states)\n\t\t\t{\n\t\t\t\t// TODO: check monotonic not yet supported\n\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\tmdp.mvMultRewGSMinMaxIntervalIter(soln,\n\t\t\t\t                                  rewards,\n\t\t\t\t                                  min,\n\t\t\t\t                                  backwards ? states.reversedIterator() : states.iterator(),\n\t\t\t\t                                  strat,\n\t\t\t\t                                  enforceMonotonicity,\n\t\t\t\t                                  fromBelow);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultMinMaxUnc(UDTMC<Double> udtmc, MinMax minMax)\n\t{\n\t\treturn new SingleVectorIterationValIter(udtmc) {\n\t\t\t@Override\n\t\t\tpublic boolean iterateAndCheckConvergence(IntSet states)\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\terror = udtmc.mvMultUncGS(soln, minMax, states.iterator(), absolute);\n\t\t\t\t// Check termination\n\t\t\t\treturn (error < termCritParam);\n\t\t\t}\n\t\t};\n\t}\n\t\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMaxUnc(UDTMC<Double> udtmc, MCRewards<Double> mcRewards, MinMax minMax)\n\t{\n\t\treturn new SingleVectorIterationValIter(udtmc) {\n\t\t\t@Override\n\t\t\tpublic boolean iterateAndCheckConvergence(IntSet states)\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\terror = udtmc.mvMultRewUncGS(soln, mcRewards, minMax, states.iterator(), absolute);\n\t\t\t\t// Check termination\n\t\t\t\treturn (error < termCritParam);\n\t\t\t}\n\t\t};\n\t}\n\t\n\t@Override\n\tpublic IterationValIter forMvMultMinMaxUnc(UMDP<Double> imdp, MinMax minMax, int[] strat)\n\t{\n\t\treturn new SingleVectorIterationValIter(imdp) {\n\t\t\t@Override\n\t\t\tpublic boolean iterateAndCheckConvergence(IntSet states)\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\terror = imdp.mvMultUncGS(soln, minMax, states.iterator(), absolute, strat);\n\t\t\t\t// Check termination\n\t\t\t\treturn (error < termCritParam);\n\t\t\t}\n\t\t};\n\t}\n\t\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMaxUnc(UMDP<Double> imdp, MDPRewards<Double> mdpRewards, MinMax minMax, int[] strat)\n\t{\n\t\treturn new SingleVectorIterationValIter(imdp) {\n\t\t\t@Override\n\t\t\tpublic boolean iterateAndCheckConvergence(IntSet states)\n\t\t\t{\n\t\t\t\t// Matrix-vector multiply\n\t\t\t\terror = imdp.mvMultRewUncGS(soln, mdpRewards, minMax, states.iterator(), absolute, strat);\n\t\t\t\t// Check termination\n\t\t\t\treturn (error < termCritParam);\n\t\t\t}\n\t\t};\n\t}\n\t\n\t@Override\n\tpublic String getDescriptionShort()\n\t{\n\t\treturn (backwards ? \"Backwards \" : \"\") + \"Gauss-Seidel\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IterationMethodJacobi.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport common.IntSet;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * IterationMethod that encapsulates the functionality of the Jacobi method.\n */\nclass IterationMethodJacobi extends IterationMethod {\n\n\t/**\n\t * Constructor.\n\t * @param absolute For convergence check, perform absolute comparison?\n\t * @param termCritParam For convergence check, the epsilon value to use\n\t */\n\tpublic IterationMethodJacobi(boolean absolute, double epsilon)\n\t{\n\t\tsuper(absolute, epsilon);\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMult(DTMC<Double> dtmc)\n\t{\n\t\treturn new TwoVectorIteration(dtmc, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tdtmc.mvMultJac(soln, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultInterval(DTMC<Double> dtmc, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity)\n\t{\n\t\tIterationPostProcessor post = (soln, soln2, states) -> {\n\t\t\ttwoVectorPostProcessing(soln, soln2, states, fromBelow, enforceMonotonicity, checkMonotonicity);\n\t\t};\n\n\t\treturn new TwoVectorIteration(dtmc, post) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tdtmc.mvMultJac(soln, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRew(DTMC<Double> dtmc, MCRewards<Double> rew)\n\t{\n\t\treturn new TwoVectorIteration(dtmc, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tdtmc.mvMultRewJac(soln, rew, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultRewInterval(DTMC<Double> dtmc, MCRewards<Double> rew, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity)\n\t{\n\t\tIterationPostProcessor post = (soln, soln2, states) -> {\n\t\t\ttwoVectorPostProcessing(soln, soln2, states, fromBelow, enforceMonotonicity, checkMonotonicity);\n\t\t};\n\n\t\treturn new TwoVectorIteration(dtmc, post) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tdtmc.mvMultRewJac(soln, rew, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultMinMax(MDP<Double> mdp, boolean min, int[] strat) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Jacobi not supported for MDPs\");\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultMinMaxInterval(MDP<Double> mdp, boolean min, int[] strat, boolean fromBelow, boolean enforceMonotonicity,\n\t\t\tboolean checkMonotonicity) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Jacobi not supported for MDPs\");\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMax(MDP<Double> mdp, MDPRewards<Double> rewards, boolean min, int[] strat) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Jacobi not supported for MDPs\");\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultRewMinMaxInterval(MDP<Double> mdp, MDPRewards<Double> rewards, boolean min, int[] strat, boolean fromBelow,\n\t\t\tboolean enforceMonotonicity, boolean checkMonotonicity) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Jacobi not supported for MDPs\");\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultMinMaxUnc(UDTMC<Double> udtmc, MinMax minMax) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Jacobi not supported for UDTMCs\");\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMaxUnc(UDTMC<Double> udtmc, MCRewards<Double> mcRewards, MinMax minMax) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Jacobi not supported for UDTMCs\");\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultMinMaxUnc(UMDP<Double> imdp, MinMax minMax, int[] strat) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Jacobi not supported for IMDPs\");\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMaxUnc(UMDP<Double> imdp, MDPRewards<Double> mdpRewards, MinMax minMax, int[] strat) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Jacobi not supported for IMDPs\");\n\t}\n\n\t@Override\n\tpublic String getDescriptionShort()\n\t{\n\t\treturn \"Jacobi\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/IterationMethodPower.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport common.IntSet;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport prism.PrismException;\n\n/**\n * IterationMethod that encapsulates the functionality of the Power method.\n */\npublic class IterationMethodPower extends IterationMethod {\n\n\t/**\n\t * Constructor.\n\t * @param absolute For convergence check, perform absolute comparison?\n\t * @param termCritParam For convergence check, the epsilon value to use\n\t */\n\tpublic IterationMethodPower(boolean absolute, double epsilon)\n\t{\n\t\tsuper(absolute, epsilon);\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMult(DTMC<Double> dtmc)\n\t{\n\t\treturn new TwoVectorIteration(dtmc, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tdtmc.mvMult(soln, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultInterval(DTMC<Double> dtmc, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity)\n\t{\n\t\tIterationPostProcessor post = (soln, soln2, states) -> {\n\t\t\ttwoVectorPostProcessing(soln, soln2, states, fromBelow, enforceMonotonicity, checkMonotonicity);\n\t\t};\n\n\t\treturn new TwoVectorIteration(dtmc, post) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tdtmc.mvMult(soln, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRew(DTMC<Double> dtmc, MCRewards<Double> rew)\n\t{\n\t\treturn new TwoVectorIteration(dtmc, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tdtmc.mvMultRew(soln, rew, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultRewInterval(DTMC<Double> dtmc, MCRewards<Double> rew, boolean fromBelow, boolean enforceMonotonicity, boolean checkMonotonicity)\n\t{\n\t\tIterationPostProcessor post = (soln, soln2, states) -> {\n\t\t\ttwoVectorPostProcessing(soln, soln2, states, fromBelow, enforceMonotonicity, checkMonotonicity);\n\t\t};\n\n\t\treturn new TwoVectorIteration(dtmc, post) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tdtmc.mvMultRew(soln, rew, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultMinMax(MDP<Double> mdp, boolean min, int[] strat)\n\t{\n\t\treturn new TwoVectorIteration(mdp, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tmdp.mvMultMinMax(soln, min, soln2, states.iterator(), strat);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultMinMaxInterval(MDP<Double> mdp, boolean min, int[] strat, boolean fromBelow, boolean enforceMonotonicity,\n\t\t\tboolean checkMonotonicity) throws PrismException\n\t{\n\t\tIterationPostProcessor post = (soln, soln2, states) -> {\n\t\t\ttwoVectorPostProcessing(soln, soln2, states, fromBelow, enforceMonotonicity, checkMonotonicity);\n\t\t};\n\n\t\treturn new TwoVectorIteration(mdp, post) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tmdp.mvMultMinMax(soln, min, soln2, states.iterator(), strat);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic String getDescriptionShort()\n\t{\n\t\treturn \"Power method\";\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMax(MDP<Double> mdp, MDPRewards<Double> rewards, boolean min, int[] strat) throws PrismException\n\t{\n\t\treturn new TwoVectorIteration(mdp, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tmdp.mvMultRewMinMax(soln, rewards, min, soln2, states.iterator(), strat);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationIntervalIter forMvMultRewMinMaxInterval(MDP<Double> mdp, MDPRewards<Double> rewards, boolean min, int[] strat, boolean fromBelow,\n\t\t\tboolean enforceMonotonicity, boolean checkMonotonicity) throws PrismException\n\t{\n\t\tIterationPostProcessor post = (soln, soln2, states) -> {\n\t\t\ttwoVectorPostProcessing(soln, soln2, states, fromBelow, enforceMonotonicity, checkMonotonicity);\n\t\t};\n\n\t\treturn new TwoVectorIteration(mdp, post) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tmdp.mvMultRewMinMax(soln, rewards, min, soln2, states.iterator(), strat);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultMinMaxUnc(UDTMC<Double> udtmc, MinMax minMax)\n\t{\n\t\treturn new TwoVectorIteration(udtmc, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tudtmc.mvMultUnc(soln, minMax, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMaxUnc(UDTMC<Double> udtmc, MCRewards<Double> mcRewards, MinMax minMax)\n\t{\n\t\treturn new TwoVectorIteration(udtmc, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\tudtmc.mvMultRewUnc(soln, mcRewards, minMax, soln2, states.iterator());\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic IterationValIter forMvMultMinMaxUnc(UMDP<Double> imdp, MinMax minMax, int[] strat)\n\t{\n\t\treturn new TwoVectorIteration(imdp, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\timdp.mvMultUnc(soln, minMax, soln2, states.iterator(), strat);\n\t\t\t}\n\t\t};\n\t}\n\t\n\t@Override\n\tpublic IterationValIter forMvMultRewMinMaxUnc(UMDP<Double> imdp, MDPRewards<Double> mdpRewards, MinMax minMax, int[] strat)\n\t{\n\t\treturn new TwoVectorIteration(imdp, null) {\n\t\t\t@Override\n\t\t\tpublic void doIterate(IntSet states)\n\t\t\t{\n\t\t\t\timdp.mvMultRewUnc(soln, mdpRewards, minMax, soln2, states.iterator(), strat);\n\t\t\t}\n\t\t};\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/LTLModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.awt.Point;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.LinkedList;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Stack;\nimport java.util.Vector;\n\nimport common.Interval;\nimport parser.State;\nimport parser.VarList;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationInt;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.type.TypeBool;\nimport parser.type.TypePathBool;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismNotSupportedException;\nimport prism.PrismUtils;\nimport acceptance.AcceptanceBuchi;\nimport acceptance.AcceptanceGenRabin;\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceStreett;\nimport acceptance.AcceptanceType;\nimport automata.DA;\nimport automata.LTL2DA;\nimport automata.LTL2WDBA;\nimport jltl2ba.SimpleLTL;\nimport common.IterableStateSet;\nimport common.StopWatch;\n\n/**\n * LTL model checking functionality\n */\npublic class LTLModelChecker extends PrismComponent\n{\n\t/** Make LTL product accessible as a Product */\n\tpublic class LTLProduct<M extends Model<?>> extends Product<M>\n\t{\n\t\tprivate int daSize;\n\t\tprivate int invMap[];\n\t\tprivate AcceptanceOmega acceptance;\n\n\t\tpublic LTLProduct(M productModel, M originalModel, AcceptanceOmega acceptance, int daSize, int[] invMap)\n\t\t{\n\t\t\tsuper(productModel, originalModel);\n\t\t\tthis.daSize = daSize;\n\t\t\tthis.invMap = invMap;\n\t\t\tthis.acceptance = acceptance;\n\t\t}\n\n\t\t@Override\n\t\tpublic int getModelState(int productState)\n\t\t{\n\t\t\treturn invMap[productState] / daSize;\n\t\t}\n\n\t\t@Override\n\t\tpublic int getAutomatonState(int productState)\n\t\t{\n\t\t\treturn invMap[productState] % daSize;\n\t\t}\n\n\t\t@Override\n\t\tpublic int getAutomatonSize()\n\t\t{\n\t\t\treturn daSize;\n\t\t}\n\n\t\tpublic AcceptanceOmega getAcceptance() {\n\t\t\treturn acceptance;\n\t\t}\n\n\t\tpublic void setAcceptance(AcceptanceOmega acceptance) {\n\t\t\tthis.acceptance = acceptance;\n\t\t}\n\t}\n\n\t/**\n\t * Create a new LTLModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic LTLModelChecker(PrismComponent parent)\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Returns {@code true} if expression {@code expr} is a formula that can be handled by\n\t * LTLModelChecker for the given ModelType.\n\t */\n\tpublic static boolean isSupportedLTLFormula(ModelType modelType, Expression expr) throws PrismLangException\n\t{\n\t\tif (!expr.isPathFormula(true)) {\n\t\t\treturn false;\n\t\t}\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tif (modelType.continuousTime()) {\n\t\t\t\t// Only support temporal bounds for discrete time models\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\t\n\t\t\tif (!expr.isSimplePathFormula()) {\n\t\t\t\t// Only support temporal bounds for simple path formulas\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Extract maximal state formula from an LTL path formula, model check them (with passed in model checker) and\n\t * replace them with ExpressionLabel objects L0, L1, etc. Expression passed in is modified directly, but the result\n\t * is also returned. As an optimisation, expressions that results in true/false for all states are converted to an\n\t * actual true/false, and duplicate results (or their negations) reuse the same label. BitSets giving the states which\n\t * satisfy each label are put into the vector labelBS, which should be empty when this function is called.\n\t */\n\tpublic Expression checkMaximalStateFormulas(StateModelChecker mc, Model<?> model, Expression expr, Vector<BitSet> labelBS) throws PrismException\n\t{\n\t\t// A state formula\n\t\tif (expr.getType() instanceof TypeBool) {\n\t\t\t// Model check state formula for all states\n\t\t\tStateValues sv = mc.checkExpression(model, expr, null);\n\t\t\tBitSet bs = sv.getBitSet();\n\t\t\t// Detect special cases (true, false) for optimisation\n\t\t\tif (bs.isEmpty()) {\n\t\t\t\treturn Expression.False();\n\t\t\t}\n\t\t\tif (bs.cardinality() == model.getNumStates()) {\n\t\t\t\treturn Expression.True();\n\t\t\t}\n\t\t\t// See if we already have an identical result\n\t\t\t// (in which case, reuse it)\n\t\t\tint i = labelBS.indexOf(bs);\n\t\t\tif (i != -1) {\n\t\t\t\tsv.clear();\n\t\t\t\treturn new ExpressionLabel(\"L\" + i);\n\t\t\t}\n\t\t\t// Also, see if we already have the negation of this result\n\t\t\t// (in which case, reuse it)\n\t\t\tBitSet bsNeg = new BitSet(model.getNumStates());\n\t\t\tbsNeg.set(0, model.getNumStates());\n\t\t\tbsNeg.andNot(bs);\n\t\t\ti = labelBS.indexOf(bsNeg);\n\t\t\tif (i != -1) {\n\t\t\t\tsv.clear();\n\t\t\t\treturn Expression.Not(new ExpressionLabel(\"L\" + i));\n\t\t\t}\n\t\t\t// Otherwise, add result to list, return new label\n\t\t\tlabelBS.add(bs);\n\t\t\treturn new ExpressionLabel(\"L\" + (labelBS.size() - 1));\n\t\t}\n\t\t// A path formula (recurse, modify, return)\n\t\telse if (expr.getType() instanceof TypePathBool) {\n\t\t\tif (expr instanceof ExpressionBinaryOp) {\n\t\t\t\tExpressionBinaryOp exprBinOp = (ExpressionBinaryOp) expr;\n\t\t\t\texprBinOp.setOperand1(checkMaximalStateFormulas(mc, model, exprBinOp.getOperand1(), labelBS));\n\t\t\t\texprBinOp.setOperand2(checkMaximalStateFormulas(mc, model, exprBinOp.getOperand2(), labelBS));\n\t\t\t} else if (expr instanceof ExpressionUnaryOp) {\n\t\t\t\tExpressionUnaryOp exprUnOp = (ExpressionUnaryOp) expr;\n\t\t\t\texprUnOp.setOperand(checkMaximalStateFormulas(mc, model, exprUnOp.getOperand(), labelBS));\n\t\t\t} else if (expr instanceof ExpressionTemporal) {\n\t\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\t\tif (exprTemp.getOperand1() != null) {\n\t\t\t\t\texprTemp.setOperand1(checkMaximalStateFormulas(mc, model, exprTemp.getOperand1(), labelBS));\n\t\t\t\t}\n\t\t\t\tif (exprTemp.getOperand2() != null) {\n\t\t\t\t\texprTemp.setOperand2(checkMaximalStateFormulas(mc, model, exprTemp.getOperand2(), labelBS));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn expr;\n\t}\n\n\t/**\n\t * Construct a deterministic automaton (DA) for an LTL formula, having first extracted maximal state formulas\n\t * and model checked them with the passed in model checker. The maximal state formulas are assigned labels\n\t * (L0, L1, etc.) which become the atomic propositions in the resulting DA. BitSets giving the states which\n\t * satisfy each label are put into the vector {@code labelBS}, which should be empty when this function is called.\n\t *\n\t * @param mc a ProbModelChecker, used for checking maximal state formulas\n\t * @param model the model\n\t * @param expr a path expression, i.e. the LTL formula\n\t * @param labelBS empty vector to be filled with BitSets for subformulas \n\t * @param allowedAcceptance the allowed acceptance types\n\t * @return the DA\n\t */\n\tpublic DA<BitSet,? extends AcceptanceOmega> constructDAForLTLFormula(ProbModelChecker mc, Model<?> model, Expression expr, Vector<BitSet> labelBS, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tExpression ltl;\n\t\tDA<BitSet,? extends AcceptanceOmega> da;\n\t\tlong time;\n\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tif (model.getModelType().continuousTime()) {\n\t\t\t\tthrow new PrismException(\"Automaton construction for time-bounded operators not supported for \" + model.getModelType()+\".\");\n\t\t\t}\n\n\t\t\tif (!expr.isSimplePathFormula()) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Time-bounded operators not supported in LTL: \" + expr);\n\t\t\t}\n\t\t}\n\n\t\t// Model check maximal state formulas\n\t\tltl = checkMaximalStateFormulas(mc, model, expr.deepCopy(), labelBS);\n\n\t\t// Convert LTL formula to deterministic automaton\n\t\tmainLog.println(\"\\nBuilding deterministic automaton (for \" + ltl + \")...\");\n\t\ttime = System.currentTimeMillis();\n\t\tLTL2DA ltl2da = new LTL2DA(this);\n\t\tda = ltl2da.convertLTLFormulaToDA(ltl, mc.getConstantValues(), allowedAcceptance);\n\t\tmainLog.println(da.getAutomataType()+\" has \" + da.size() + \" states, \" + da.getAcceptance().getSizeStatistics() + \".\");\n\t\tda.checkForCanonicalAPs(labelBS.size());\n\t\ttime = System.currentTimeMillis() - time;\n\t\tmainLog.println(\"Time for \"+da.getAutomataType()+\" translation: \" + time / 1000.0 + \" seconds.\");\n\t\t// If required, export DA\n\t\tif (settings.getExportPropAut()) {\n\t\t\tmainLog.println(\"Exporting \" + da.getAutomataType() + \" to file \\\"\" + settings.getExportPropAutFilename() + \"\\\"...\");\n\t\t\tPrintStream out = PrismUtils.newPrintStream(settings.getExportPropAutFilename());\n\t\t\tda.print(out, settings.getExportPropAutType());\n\t\t\tout.close();\n\t\t}\n\t\t\n\t\treturn da;\n\t}\n\n\t/**\n\t * Constructs a deterministic finite automaton (DFA) for the given syntactically co-safe LTL formula.\n\t * <br>\n\t * First, extracted maximal state formulas are model checked with the passed in model checker.\n\t * The maximal state formulas are assigned labels (L0, L1, etc.) which become the atomic\n\t * propositions in the resulting DA. BitSets giving the states which satisfy each label\n\t * are put into the vector {@code labelBS}, which should be empty when this function is called.\n\t * <br>\n\t * This is for use when computing the probability of satisfaction;\n\t * use {@link #constructDFAForCosafetyRewardLTL()} for expected rewards.\n\t * @param mc the underlying model checker (for recursively handling maximal state formulas)\n\t * @param model the model\n\t * @param expr the co-safe LTL formula\n\t * @param labelBS empty vector to be filled with BitSets for subformulas\n\t * @return a DA with AcceptanceReach acceptance condition\n\t */\n\tpublic DA<BitSet, AcceptanceReach> constructDFAForCosafetyProbLTL(StateModelChecker mc, Model<?> model, Expression expr, Vector<BitSet> labelBS) throws PrismException\n\t{\n\t\t// Model check maximal state formulas\n\t\tExpression ltl = checkMaximalStateFormulas(mc, model, expr.deepCopy(), labelBS);\n\n\t\t// Convert and put in positive normal form (negation only in front of APs)\n\t\tSimpleLTL sltl = ltl.convertForJltl2ba();\n\t\tsltl = sltl.toBasicOperators();\n\t\tsltl = sltl.pushNegation();\n\n\t\t// Convert LTL formula to deterministic automaton, with Reach acceptance\n\t\tLTL2WDBA ltl2wdba = new LTL2WDBA(this);\n\t\tmainLog.println(\"\\nBuilding deterministic finite automaton via LTL2WDBA construction (for \" + sltl + \")...\");\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"constructing DFA\");\n\t\tDA<BitSet, AcceptanceReach> dfa = ltl2wdba.cosafeltl2dfa(sltl);\n\t\ttimer.stop(\"DFA has \" + dfa.size() + \" states\");\n\n\t\treturn dfa;\n\t}\n\n\t/**\n\t * Constructs a deterministic finite automaton (DFA) for the given syntactically co-safe\n\t * LTL formula, for use in reward computations for co-safe LTL.\n\t * <br>\n\t * First, extracted maximal state formulas are model checked with the passed in model checker.\n\t * The maximal state formulas are assigned labels (L0, L1, etc.) which become the atomic\n\t * propositions in the resulting DA. BitSets giving the states which satisfy each label\n\t * are put into the vector {@code labelBS}, which should be empty when this function is called.\n\t * <br>\n\t * To achieve \"strong\" semantics for the next-step operator, an additional atomic\n\t * proposition is added and X phi is transformed to X (phi & fresh_ap). This\n\t * ensures that, e.g., X X true results in two steps of accumulation.\n\t * @param mc the underlying model checker (for recursively handling maximal state formulas)\n\t * @param model the model\n\t * @param expr the co-safe LTL formula\n \t * @param labelBS empty vector to be filled with BitSets for subformulas\n\t * @return a DA with AcceptanceReach acceptance condition\n\t */\n\tpublic DA<BitSet, AcceptanceReach> constructDFAForCosafetyRewardLTL(StateModelChecker mc, Model<?> model, Expression expr, Vector<BitSet> labelBS) throws PrismException\n\t{\n\t\t// Model check maximal state formulas\n\t\tExpression ltl = checkMaximalStateFormulas(mc, model, expr.deepCopy(), labelBS);\n\n\t\tSimpleLTL sltl = ltl.convertForJltl2ba();\n\t\t// convert to positive normal form (negation only in front of APs)\n\t\tsltl = sltl.toBasicOperators();\n\t\tsltl = sltl.pushNegation();\n\t\tif (sltl.hasNextStep()) {\n\t\t\t// we have do add another atomic proposition to ensure \"strong\" semantics for\n\t\t\t// the X operator\n\t\t\tString stepLabel = \"L\" + labelBS.size();\n\t\t\tBitSet allStates = new BitSet();\n\t\t\tallStates.set(0, model.getNumStates(), true);\n\t\t\tlabelBS.add(allStates);\n\t\t\tsltl = sltl.extendNextStepWithAP(stepLabel);\n\t\t\t// mainLog.println(\"Adding step label \" + stepLabel);\n\t\t}\n\n\t\t// Convert LTL formula to deterministic automaton, with Reach acceptance\n\t\tLTL2WDBA ltl2wdba = new LTL2WDBA(this);\n\t\tmainLog.println(\"\\nBuilding deterministic finite automaton via LTL2WDBA construction (for \" + sltl + \")...\");\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"constructing DFA\");\n\t\tDA<BitSet, AcceptanceReach> dfa = ltl2wdba.cosafeltl2dfa(sltl);\n\t\ttimer.stop(\"DFA has \" + dfa.size() + \" states\");\n\n\t\treturn dfa;\n\t}\n\n\t/**\n\t * Generate a deterministic automaton for the given LTL formula\n\t * and construct the product of this automaton with a Markov chain.\n\t *\n\t * @param mc a ProbModelChecker, used for checking maximal state formulas\n\t * @param model the model\n\t * @param expr a path expression\n \t * @param statesOfInterest the set of states for which values should be calculated (null = all states)\n \t * @param allowedAcceptance the allowed acceptance types\n\t * @return the product with the DA\n\t */\n\tpublic <Value> LTLProduct<DTMC<Value>> constructProductMC(ProbModelChecker mc, DTMC<Value> model, Expression expr, BitSet statesOfInterest, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\treturn constructDAProductForLTLFormula(mc, model, expr, statesOfInterest, allowedAcceptance);\n\t}\n\n\t/**\n\t * Generate a deterministic automaton for the given LTL formula\n\t * and construct the product of this automaton with an MDP.\n\t *\n\t * @param mc a ProbModelChecker, used for checking maximal state formulas\n\t * @param model the model\n\t * @param expr a path expression\n\t * @param statesOfInterest the set of states for which values should be calculated (null = all states)\n\t * @param allowedAcceptance the allowed acceptance conditions\n\t * @return the product with the DA\n\t * @throws PrismException\n\t */\n\tpublic <Value> LTLProduct<MDP<Value>> constructProductMDP(ProbModelChecker mc, MDP<Value> model, Expression expr, BitSet statesOfInterest, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\treturn constructDAProductForLTLFormula(mc, model, expr, statesOfInterest, allowedAcceptance);\n\t}\n\n\t/**\n\t * Generate a deterministic automaton for the given LTL formula\n\t * and construct the product of this automaton with an STPG.\n\t *\n\t * @param mc a ProbModelChecker, used for checking maximal state formulas\n\t * @param model the model\n\t * @param expr a path expression\n\t * @param statesOfInterest the set of states for which values should be calculated (null = all states)\n\t * @param allowedAcceptance the allowed acceptance conditions\n\t * @return the product with the DA\n\t * @throws PrismException\n\t */\n\tpublic <Value> LTLProduct<STPG<Value>> constructProductSTPG(ProbModelChecker mc, STPG<Value> model, Expression expr, BitSet statesOfInterest, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\treturn constructDAProductForLTLFormula(mc, model, expr, statesOfInterest, allowedAcceptance);\n\t}\n\t\n\t/**\n\t * Generate a deterministic automaton (DA) for the given LTL formula, having first extracted maximal state formulas\n\t * and model checked them with the passed in model and model checker (see {@link #constructDAForLTLFormula}.\n\t * Then construct the product of this automaton with the model.\n\t *\n\t * @param mc a ProbModelChecker, used for checking maximal state formulas\n\t * @param model the model\n\t * @param expr a path expression\n\t * @param statesOfInterest the set of states for which values should be calculated (null = all states)\n\t * @param allowedAcceptance the allowed acceptance conditions\n\t * @return the product with the DA\n\t * @throws PrismException\n\t */\n\tpublic <Value,M extends Model<Value>> LTLProduct<M> constructDAProductForLTLFormula(ProbModelChecker mc, M model, Expression expr, BitSet statesOfInterest, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\t// Convert LTL formula to automaton\n\t\tVector<BitSet> labelBS = new Vector<BitSet>();\n\t\tDA<BitSet,? extends AcceptanceOmega> da = constructDAForLTLFormula(mc, model, expr, labelBS, allowedAcceptance);\n\n\t\t// Build product of model and automaton\n\t\tmainLog.println(\"Constructing \" + model.getModelType() + \"-\" + da.getAutomataType() + \" product...\");\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"product construction\");\n\t\tLTLProduct<M> product = constructProductModel(da, model, labelBS, statesOfInterest);\n\t\ttimer.stop(\"product has \" + product.getProductModel().infoString());\n\n\t\treturn product;\n\t}\n\t\n\t/**\n\t * Generate a deterministic finite automaton (DFA) for the given syntactically co-safe LTL formula,\n\t * for use in probability computations for co-safe LTL, having first extracted maximal state formulas\n\t * and model checked them with the passed in model and model checker (see {@link #constructDFAForCosafetyProbLTL}.\n\t * Then construct the product of this automaton with the model.\n\t *\n\t * @param mc a ProbModelChecker, used for checking maximal state formulas\n\t * @param model the model\n\t * @param expr a path expression\n\t * @param statesOfInterest the set of states for which values should be calculated (null = all states)\n\t * @return the product with the DA\n\t * @throws PrismException\n\t */\n\tpublic <Value,M extends Model<Value>> LTLProduct<M> constructDFAProductForCosafetyProbLTL(ProbModelChecker mc, M model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Convert LTL formula to DFA\n\t\tVector<BitSet> labelBS = new Vector<BitSet>();\n\t\tDA<BitSet, AcceptanceReach> da = constructDFAForCosafetyProbLTL(mc, model, expr, labelBS);\n\n\t\t// Build product of model and automaton\n\t\tmainLog.println(\"Constructing \" + model.getModelType() + \"-\" + da.getAutomataType() + \" product...\");\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"product construction\");\n\t\tLTLProduct<M> product = constructProductModel(da, model, labelBS, statesOfInterest);\n\t\ttimer.stop(\"product has \" + product.getProductModel().infoString());\n\n\t\treturn product;\n\t}\n\t\n\t/**\n\t * Generate a deterministic finite automaton (DFA) for the given syntactically co-safe LTL formula,\n\t * for use in reward computations for co-safe LTL, having first extracted maximal state formulas\n\t * and model checked them with the passed in model and model checker (see {@link #constructDFAForCosafetyRewardLTL}.\n\t * Then construct the product of this automaton with the model.\n\t *\n\t * @param mc a ProbModelChecker, used for checking maximal state formulas\n\t * @param model the model\n\t * @param expr a path expression\n\t * @param statesOfInterest the set of states for which values should be calculated (null = all states)\n\t * @return the product with the DA\n\t * @throws PrismException\n\t */\n\tpublic <Value,M extends Model<Value>> LTLProduct<M> constructDFAProductForCosafetyReward(ProbModelChecker mc, M model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Convert LTL formula to DFA, with the special\n\t\t// handling needed for cosafety reward translation\n\t\tVector<BitSet> labelBS = new Vector<BitSet>();\n\t\tDA<BitSet, AcceptanceReach> da = constructDFAForCosafetyRewardLTL(mc, model, expr, labelBS);\n\n\t\t// Build product of model and automaton\n\t\tmainLog.println(\"Constructing \" + model.getModelType() + \"-\" + da.getAutomataType() + \" product...\");\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"product construction\");\n\t\tLTLProduct<M> product = constructProductModel(da, model, labelBS, statesOfInterest);\n\t\ttimer.stop(\"product has \" + product.getProductModel().infoString());\n\n\t\treturn product;\n\t}\n\t\n\t/**\n\t * Construct the product of a DA and a model.\n\t * @param da The DA\n\t * @param model The model\n\t * @param labelBS BitSets giving the set of states for each AP in the DA\n\t * @param statesOfInterest the set of states for which values should be calculated (null = all states)\n\t * @return The product model\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <Value, M extends Model<Value>> LTLProduct<M> constructProductModel(DA<BitSet, ? extends AcceptanceOmega> da, M model, Vector<BitSet> labelBS, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// If the model has a VarList, we will create a new one\n\t\tVarList newVarList = null;\n\t\tif (model.getVarList() != null) {\n\t\t\tVarList varList = model.getVarList();\n\t\t\t// Create a (new, unique) name for the variable that will represent DA states\n\t\t\tString daVar = \"_da\";\n\t\t\twhile (varList.exists(daVar)) {\n\t\t\t\tdaVar = \"_\" + daVar;\n\t\t\t}\n\n\t\t\tnewVarList = (VarList) varList.clone();\n\t\t\t// NB: if DA only has one state, we add an extra dummy state\n\t\t\tDeclaration decl = new Declaration(daVar, new DeclarationInt(Expression.Int(0), Expression.Int(Math.max(da.size() - 1, 1))));\n\t\t\tnewVarList.addVarAtStart(decl, 1);\n\t\t}\n\n\t\t// Create a (simple, mutable) model of the appropriate type\n\t\tModelType modelType = model.getModelType();\n\t\tModelSimple<?> prodModel = ModelSimple.forModelType(modelType);\n\n\t\t// Attach evaluator and variable info\n\t\t((ModelExplicit<Value>) prodModel).setEvaluator(model.getEvaluator());\n\t\tif (prodModel instanceof IntervalModelExplicit) {\n\t\t\t((IntervalModelExplicit<Value>) prodModel).setIntervalEvaluator(((IntervalModel<Value>) model).getIntervalEvaluator());\n\t\t}\n\t\t((ModelExplicit<Value>) prodModel).setVarList(newVarList);\n\n\t\t// Now do the actual product model construction\n\t\treturn doConstructProductModel(modelType, prodModel, da, model, labelBS, statesOfInterest);\n\t}\n\t\n\t/**\n\t * Do the main part of the construction of the product of a DA and a model,\n\t * inserting states and transitions into the provided ModelSimple object.\n\t * @param modelType The type of the (original) model\n\t * @param prodModel The (empty) product model\n\t * @param da The DA\n\t * @param model The model\n\t * @param labelBS BitSets giving the set of states for each AP in the DA\n\t * @param statesOfInterest the set of states for which values should be calculated (null = all states)\n\t * @return The product model\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected <Value, M extends Model<Value>> LTLProduct<M> doConstructProductModel(ModelType modelType, ModelSimple<?> prodModel, DA<BitSet, ? extends AcceptanceOmega> da, M model, Vector<BitSet> labelBS, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tint daSize = da.size();\n\t\tint numAPs = da.getAPList().size();\n\t\tint modelNumStates = model.getNumStates();\n\t\tint prodNumStates = Math.multiplyExact(modelNumStates, daSize);\n\t\tBitSet s_labels = new BitSet(numAPs);\n\t\tList<State> prodStatesList, daStatesList;\n\n\t\t// Check size limits for this product construction approach\n\t\ttry {\n\t\t\tprodNumStates = Math.multiplyExact(modelNumStates, daSize);\n\t\t} catch (ArithmeticException e) {\n\t\t\tthrow new PrismException(\"Size of product state space of model and automaton is too large for explicit engine\");\n\t\t}\n\t\t\n\t\t// Encoding: \n\t\t// each state s' = <s, q> = s * daSize + q\n\t\t// s(s') = s' / daSize\n\t\t// q(s') = s' % daSize\n\n\t\t// Initialise state info storage\n\t\tLinkedList<Point> queue = new LinkedList<Point>();\n\t\tBitSet visited = new BitSet(prodNumStates);\n\t\tint map[] = new int[prodNumStates];\n\t\tArrays.fill(map, -1);\n\t\tif (model.getStatesList() != null) {\n\t\t\tprodStatesList = new ArrayList<State>();\n\t\t\tdaStatesList = new ArrayList<State>(da.size());\n\t\t\tfor (int i = 0; i < da.size(); i++) {\n\t\t\t\tdaStatesList.add(new State(1).setValue(0, i));\n\t\t\t}\n\t\t} else {\n\t\t\tprodStatesList = null;\n\t\t\tdaStatesList = null;\n\t\t}\n\n\t\t// Code to get the index for a new product state for model successor state s_2\n\t\t// assuming the current automaton state is q_1\n\t\tNewStateMap newStateMap = (q_1,s_2) -> {\n\t\t\t// Get BitSet representing APs (labels) satisfied by successor state s_2\n\t\t\tfor (int k = 0; k < numAPs; k++) {\n\t\t\t\ts_labels.set(k, labelBS.get(Integer.parseInt(da.getAPList().get(k).substring(1))).get(s_2));\n\t\t\t}\n\t\t\t// Find corresponding successor in DA\n\t\t\tint q_2 = da.getEdgeDestByLabel(q_1, s_labels);\n\t\t\tif (q_2 < 0) {\n\t\t\t\tthrow new PrismException(\"The deterministic automaton is not complete (state \" + q_1 + \")\");\n\t\t\t}\n\t\t\t// Add state/transition to model\n\t\t\tif (!visited.get(s_2 * daSize + q_2) && map[s_2 * daSize + q_2] == -1) {\n\t\t\t\tqueue.add(new Point(s_2, q_2));\n\t\t\t\tswitch (modelType) {\n\t\t\t\t\tcase STPG:\n\t\t\t\t\t\t((STPGSimple<Value>) prodModel).addState(((STPG<Value>) model).getPlayer(s_2));\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tprodModel.addState();\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tmap[s_2 * daSize + q_2] = prodModel.getNumStates() - 1;\n\t\t\t\tif (prodStatesList != null) {\n\t\t\t\t\t// Store state information for the product\n\t\t\t\t\tprodStatesList.add(new State(daStatesList.get(q_2), model.getStatesList().get(s_2)));\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn map[s_2 * daSize + q_2];\n\t\t};\n\n\t\t// Get initial states\n\t\t// We need results for all states of the original model in statesOfInterest\n\t\t// We thus explore states of the product starting from these states.\n\t\t// These are designated as initial states of the product model\n\t\t// (a) to ensure reachability is done for these states; and\n\t\t// (b) to later identify the corresponding product state for the original states\n\t\t//     of interest\n\t\tfor (int s_0 : new IterableStateSet(statesOfInterest, model.getNumStates())) {\n\t\t\tint map_0 = newStateMap.apply(da.getStartState(), s_0);\n\t\t\tprodModel.addInitialState(map_0);\n\t\t}\n\n\t\t// Explore product\n\t\twhile (!queue.isEmpty()) {\n\t\t\tPoint p = queue.pop();\n\t\t\tint s_1 = p.x;\n\t\t\tint q_1 = p.y;\n\t\t\tvisited.set(s_1 * daSize + q_1);\n\t\t\tint map_1 = map[s_1 * daSize + q_1];\n\n\t\t\t// Go through transitions from state s_1 in original model\n\t\t\tint numChoices = (model instanceof NondetModel) ? ((NondetModel<Value>) model).getNumChoices(s_1) : 1;\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\tIterator<Map.Entry<Integer, Value>> iter = null;\n\t\t\t\tIterator<Map.Entry<Integer, Interval<Value>>> iterIntv = null;\n\t\t\t\tswitch (modelType) {\n\t\t\t\tcase DTMC:\n\t\t\t\t\titer = ((DTMC<Value>) model).getTransitionsIterator(s_1);\n\t\t\t\t\tbreak;\n\t\t\t\tcase MDP:\n\t\t\t\t\titer = ((MDP<Value>) model).getTransitionsIterator(s_1, j);\n\t\t\t\t\tbreak;\n\t\t\t\tcase POMDP:\n\t\t\t\t\titer = ((POMDP<Value>) model).getTransitionsIterator(s_1, j);\n\t\t\t\t\tbreak;\n\t\t\t\tcase IDTMC:\n\t\t\t\t\titerIntv = ((IDTMC<Value>) model).getIntervalTransitionsIterator(s_1);\n\t\t\t\t\tbreak;\n\t\t\t\tcase IMDP:\n\t\t\t\t\titerIntv = ((IMDP<Value>) model).getIntervalTransitionsIterator(s_1, j);\n\t\t\t\t\tbreak;\n\t\t\t\tcase STPG:\n\t\t\t\t\titer = ((STPG<Value>) model).getTransitionsIterator(s_1, j);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Product construction not implemented for \" + modelType + \"s\");\n\t\t\t\t}\n\t\t\t\tDistribution<Value> prodDistr = null;\n\t\t\t\tDistribution<Interval<Value>> prodDistrIntv = null;\n\t\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\t\tif (modelType != ModelType.IMDP) {\n\t\t\t\t\t\tprodDistr = new Distribution<>(model.getEvaluator());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tprodDistrIntv = new Distribution<>(((IMDP<Value>) model).getIntervalEvaluator());\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (!(model instanceof IntervalModel)) {\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Value> e = iter.next();\n\t\t\t\t\t\tint s_2 = e.getKey();\n\t\t\t\t\t\tValue prob = e.getValue();\n\t\t\t\t\t\tint map_2 = newStateMap.apply(q_1, s_2);\n\n\t\t\t\t\t\tswitch (modelType) {\n\t\t\t\t\t\t\tcase DTMC:\n\t\t\t\t\t\t\t\t((DTMCSimple<Value>) prodModel).setProbability(map_1, map_2, prob);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tcase MDP:\n\t\t\t\t\t\t\tcase POMDP:\n\t\t\t\t\t\t\tcase STPG:\n\t\t\t\t\t\t\t\tprodDistr.set(map_2, prob);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tthrow new PrismNotSupportedException(\"Product construction not implemented for \" + modelType + \"s\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\twhile (iterIntv.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Interval<Value>> e = iterIntv.next();\n\t\t\t\t\t\tint s_2 = e.getKey();\n\t\t\t\t\t\tInterval<Value> prob = e.getValue();\n\t\t\t\t\t\tint map_2 = newStateMap.apply(q_1, s_2);\n\n\t\t\t\t\t\tswitch (modelType) {\n\t\t\t\t\t\t\tcase IDTMC:\n\t\t\t\t\t\t\t\t((IDTMCSimple<Value>) prodModel).setProbability(map_1, map_2, prob);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tcase IMDP:\n\t\t\t\t\t\t\t\tprodDistrIntv.set(map_2, prob);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\tthrow new PrismNotSupportedException(\"Product construction not implemented for \" + modelType + \"s\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tswitch (modelType) {\n\t\t\t\tcase MDP:\n\t\t\t\t\t((MDPSimple<Value>) prodModel).addActionLabelledChoice(map_1, prodDistr, ((MDP<Value>) model).getAction(s_1, j));\n\t\t\t\t\tbreak;\n\t\t\t\tcase POMDP:\n\t\t\t\t\t((POMDPSimple<Value>) prodModel).addActionLabelledChoice(map_1, prodDistr, ((POMDP<Value>) model).getAction(s_1, j));\n\t\t\t\t\tbreak;\n\t\t\t\tcase IMDP:\n\t\t\t\t\t((IMDPSimple<Value>) prodModel).addActionLabelledChoice(map_1, prodDistrIntv, ((IMDP<Value>) model).getAction(s_1, j));\n\t\t\t\t\tbreak;\n\t\t\t\tcase STPG:\n\t\t\t\t\t((STPGSimple<Value>) prodModel).addActionLabelledChoice(map_1, prodDistr, ((STPG<Value>) model).getAction(s_1, j));\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// For partially observable models, transfer observation info\n\t\t\t// (do it after transitions are added, since observation actions are checked)\n\t\t\tif (modelType == ModelType.POMDP) {\n\t\t\t\tState o = ((POMDP) model).getObservationAsState(s_1);\n\t\t\t\tState u = ((POMDP) model).getUnobservationAsState(s_1);\n\t\t\t\t((POMDPSimple) prodModel).setObservation(map_1, o, u, null);\n\t\t\t}\n\t\t}\n\n\t\t// Build a mapping from state indices to states (s,q), encoded as (s * daSize + q) \n\t\tint invMap[] = new int[prodModel.getNumStates()];\n\t\tfor (int i = 0; i < map.length; i++) {\n\t\t\tif (map[i] != -1) {\n\t\t\t\tinvMap[map[i]] = i;\n\t\t\t}\n\t\t}\n\n\t\tprodModel.findDeadlocks(false);\n\n\t\tif (prodStatesList != null) {\n\t\t\tprodModel.setStatesList(prodStatesList);\n\t\t}\n\n\t\tLTLProduct<M> product = new LTLProduct<M>((M) prodModel, model, null, daSize, invMap);\n\n\t\t// generate acceptance for the product model by lifting\n\t\tproduct.setAcceptance(liftAcceptance(product, da.getAcceptance()));\n\n\t\t// lift the labels\n\t\tfor (String label : model.getLabels()) {\n\t\t\tBitSet liftedLabel = product.liftFromModel(model.getLabelStates(label));\n\t\t\tprodModel.addLabel(label, liftedLabel);\n\t\t}\n\n\t\treturn product;\n\t}\n\n\t@FunctionalInterface\n\tinterface NewStateMap\n\t{\n\t\tint apply(int q_1, int s_2) throws PrismException;\n\t};\n\n\t/**\n\t * Find the set of states that belong to accepting BSCCs in a model wrt an acceptance condition.\n\t * @param model The model\n\t * @param acceptance The acceptance condition\n\t */\n\tpublic BitSet findAcceptingBSCCs(Model<?> model, AcceptanceOmega acceptance) throws PrismException\n\t{\n\t\t// Compute bottom strongly connected components (BSCCs)\n\t\tSCCConsumerStore sccStore = new SCCConsumerStore();\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, model, sccStore);\n\t\tsccComputer.computeSCCs();\n\t\tList<BitSet> bsccs = sccStore.getBSCCs();\n\n\t\tBitSet result = new BitSet();\n\n\t\tfor (BitSet bscc : bsccs) {\n\t\t\tif (acceptance.isBSCCAccepting(bscc)) {\n\t\t\t\t// this BSCC is accepting\n\t\t\t\tresult.or(bscc);\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Compute the set of states in end components of the model that are accepting\n\t * with regard to the acceptance condition.\n\t * @param model the model\n\t * @param acceptance the acceptance condition\n\t * @return BitSet with the set of states that are accepting\n\t */\n\tpublic BitSet findAcceptingECStates(NondetModel<?> model, AcceptanceOmega acceptance) throws PrismException\n\t{\n\t\tif (acceptance instanceof AcceptanceBuchi) {\n\t\t\treturn findAcceptingECStatesForBuchi(model, (AcceptanceBuchi) acceptance);\n\t\t} else if (acceptance instanceof AcceptanceRabin) {\n\t\t\treturn findAcceptingECStatesForRabin(model, (AcceptanceRabin) acceptance);\n\t\t} else if (acceptance instanceof AcceptanceStreett) {\n\t\t\treturn findAcceptingECStatesForStreett(model, (AcceptanceStreett) acceptance);\n\t\t} else if (acceptance instanceof AcceptanceGenRabin) {\n\t\t\treturn findAcceptingECStatesForGeneralizedRabin(model, (AcceptanceGenRabin) acceptance);\n\t\t}\n\t\tthrow new PrismNotSupportedException(\"Computing end components for acceptance type '\"+acceptance.getType()+\"' currently not supported (explicit engine).\");\n\t}\n\n\t/**\n\t * Find the set of states in accepting end components (ECs) in a nondeterministic model wrt a Büchi acceptance condition.\n\t * @param model The model\n\t * @param acceptance The acceptance condition\n\t */\n\tpublic BitSet findAcceptingECStatesForBuchi(NondetModel<?> model, AcceptanceBuchi acceptance) throws PrismException\n\t{\n\t\tBitSet allAcceptingStates = new BitSet();\n\n\t\tif (acceptance.getAcceptingStates().isEmpty()) {\n\t\t\treturn allAcceptingStates;\n\t\t}\n\n\t\t// Compute accepting maximum end components (MECs)\n\t\tECComputer ecComputer = ECComputer.createECComputer(this, model);\n\t\tecComputer.computeMECStates();\n\t\tList<BitSet> mecs = ecComputer.getMECStates();\n\t\t// Union of accepting MEC states\n\t\tfor (BitSet mec : mecs) {\n\t\t\tif (mec.intersects(acceptance.getAcceptingStates())) {\n\t\t\t\tallAcceptingStates.or(mec);\n\t\t\t}\n\t\t}\n\n\t\treturn allAcceptingStates;\n\t}\n\n\t/**\n\t * Find the set of states in accepting end components (ECs) in a nondeterministic model wrt a Rabin acceptance condition.\n\t * @param model The model\n\t * @param acceptance The acceptance condition\n\t */\n\tpublic BitSet findAcceptingECStatesForRabin(NondetModel<?> model, AcceptanceRabin acceptance) throws PrismException\n\t{\n\t\tBitSet allAcceptingStates = new BitSet();\n\t\tint numStates = model.getNumStates();\n\t\t\n\t\t// Go through the DRA acceptance pairs (L_i, K_i) \n\t\tfor (int i = 0; i < acceptance.size(); i++) {\n\t\t\t// Find model states *not* satisfying L_i\n\t\t\tBitSet bitsetLi = acceptance.get(i).getL();\n\t\t\tBitSet statesLi_not = new BitSet();\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tif (!bitsetLi.get(s)) {\n\t\t\t\t\tstatesLi_not.set(s);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Skip pairs with empty !L_i\n\t\t\tif (statesLi_not.cardinality() == 0)\n\t\t\t\tcontinue;\n\t\t\t// Compute accepting maximum end components (MECs) in !L_i\n\t\t\tECComputer ecComputer = ECComputer.createECComputer(this, model);\n\t\t\tecComputer.computeMECStates(statesLi_not, acceptance.get(i).getK());\n\t\t\tList<BitSet> mecs = ecComputer.getMECStates();\n\t\t\t// Union MEC states\n\t\t\tfor (BitSet mec : mecs) {\n\t\t\t\tallAcceptingStates.or(mec);\n\t\t\t}\n\t\t}\n\n\t\treturn allAcceptingStates;\n\t}\n\n\t/**\n\t * Find the set of states in accepting end components (ECs) in a nondeterministic model wrt a Streett acceptance condition.\n\t * @param model The model\n\t * @param acceptance The Streett acceptance condition\n\t */\n\tpublic BitSet findAcceptingECStatesForStreett(NondetModel<?> model, AcceptanceStreett acceptance) throws PrismException\n\t{\n\t\tclass ECandPairs {\n\t\t\tBitSet MEC;\n\t\t\tBitSet activePairs;\n\t\t}\n\n\t\tBitSet allAcceptingStates = new BitSet();\n\t\tBitSet allPairs = new BitSet();\n\t\tallPairs.set(0, acceptance.size());\n\n\t\tStack<ECandPairs> todo = new Stack<ECandPairs>();\n\t\tECComputer ecComputer = ECComputer.createECComputer(this, model);\n\t\tecComputer.computeMECStates();\n\t\tfor (BitSet mecs : ecComputer.getMECStates()) {\n\t\t\tECandPairs ecp = new ECandPairs();\n\t\t\tecp.MEC = mecs;\n\t\t\tecp.activePairs = allPairs;\n\t\t\ttodo.push(ecp);\n\t\t}\n\n\t\twhile (!todo.empty()) {\n\t\t\tECandPairs ecp = todo.pop();\n\t\t\tBitSet newActivePairs = (BitSet)ecp.activePairs.clone();\n\t\t\tBitSet restrict = null;\n\n\t\t\t// check for acceptance\n\t\t\tboolean allAccepting = true;\n\t\t\tfor (int pair = ecp.activePairs.nextSetBit(0);\n\t\t\t\t pair != -1;\n\t\t\t\t pair = ecp.activePairs.nextSetBit(pair + 1)) {\n\n\t\t\t\tif (!acceptance.get(pair).isBSCCAccepting(ecp.MEC)) {\n\t\t\t\t\t// this pair is not accepting\n\t\t\t\t\tif (restrict == null) {\n\t\t\t\t\t\trestrict = (BitSet)ecp.MEC.clone();\n\t\t\t\t\t}\n\t\t\t\t\trestrict.andNot(acceptance.get(pair).getR());\n\t\t\t\t\tnewActivePairs.clear(pair);\n\t\t\t\t\tallAccepting = false;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (allAccepting) {\n\t\t\t\tallAcceptingStates.or(ecp.MEC);\n\t\t\t} else if (restrict.isEmpty()) {\n\t\t\t\t// nothing to do\n\t\t\t} else {\n\t\t\t\tecComputer = ECComputer.createECComputer(this, model);\n\t\t\t\tecComputer.computeMECStates(restrict);\n\t\t\t\tfor (BitSet mecs : ecComputer.getMECStates()) {\n\t\t\t\t\tECandPairs newEcp = new ECandPairs();\n\t\t\t\t\tnewEcp.MEC = mecs;\n\t\t\t\t\tnewEcp.activePairs = newActivePairs;\n\t\t\t\t\ttodo.push(newEcp);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn allAcceptingStates;\n\t}\n\n\t/**\n\t * Find the set of states in accepting end components (ECs) in a nondeterministic model wrt a Generalized Rabin acceptance condition.\n\t * @param model The model\n\t * @param acceptance The acceptance condition\n\t */\n\tpublic BitSet findAcceptingECStatesForGeneralizedRabin(NondetModel<?> model, AcceptanceGenRabin acceptance) throws PrismException\n\t{\n\t\tBitSet allAcceptingStates = new BitSet();\n\t\tint numStates = model.getNumStates();\n\t\t\n\t\t// Go through the GR acceptance pairs (L_i, K_i_1, ..., K_i_n) \n\t\tfor (int i = 0; i < acceptance.size(); i++) {\n\t\t\t\n\t\t\t// Find model states *not* satisfying L_i\n\t\t\tBitSet bitsetLi = acceptance.get(i).getL();\n\t\t\tBitSet statesLi_not = new BitSet();\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tif (!bitsetLi.get(s)) {\n\t\t\t\t\tstatesLi_not.set(s);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Skip pairs with empty !L_i\n\t\t\tif (statesLi_not.cardinality() == 0)\n\t\t\t\tcontinue;\n\t\t\t// Compute maximum end components (MECs) in !L_i\n\t\t\tECComputer ecComputer = ECComputer.createECComputer(this, model);\n\t\t\tecComputer.computeMECStates(statesLi_not);\n\t\t\tList<BitSet> mecs = ecComputer.getMECStates();\n\t\t\t// Check which MECs contain a state from each K_i_j\n\t\t\tint n = acceptance.get(i).getNumK();\n\t\t\tfor (BitSet mec : mecs) {\n\t\t\t\tboolean allj = true;\n\t\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\t\tif (!mec.intersects(acceptance.get(i).getK(j))) {\n\t\t\t\t\t\tallj = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allj) {\n\t\t\t\t\tallAcceptingStates.or(mec);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn allAcceptingStates;\n\t}\n\n\t/** Lift the acceptance condition from the automaton to the product states. */\n\tprivate AcceptanceOmega liftAcceptance(final LTLProduct<?> product, AcceptanceOmega acceptance)\n\t{\n\t\t// make a copy of the acceptance condition\n\t\tAcceptanceOmega lifted = acceptance.clone();\n\n\t\t// lift state sets\n\t\tlifted.lift(new AcceptanceOmega.LiftBitSet() {\n\t\t\t@Override\n\t\t\tpublic BitSet lift(BitSet states)\n\t\t\t{\n\t\t\t\treturn product.liftFromAutomaton(states);\n\t\t\t}\n\t\t});\n\n\t\treturn lifted;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/LTS.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport prism.ModelType;\nimport prism.PrismException;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state labelled transition system (LTS).\n */\npublic interface LTS<Value> extends NondetModel<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.LTS;\n\t}\n\n\t@Override\n\tdefault void exportToPrismLanguage(String filename, int precision) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t// Accessors\n\t\n\t/**\n\t * Get the successor state for the {@code i}th choice/transition from state {@code s}.\n\t */\n\tpublic int getSuccessor(int s, int i);\n}\n"
  },
  {
    "path": "prism/src/explicit/LTSNBAProduct.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.Iterator;\nimport java.util.Stack;\nimport java.util.Vector;\n\nimport prism.PrismLog;\nimport common.IterableBitSet;\nimport common.IterableStateSet;\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport jltl2dstar.NBA;\nimport jltl2dstar.NBA_State;\n\n/**\n * Construction and storage for the product\n * of the underlying labeled transition system\n * of a model (i.e., the edge relation defined\n * by getSuccessorsIterator()) and a non-deterministic\n * Büchi automaton (NBA).\n */\npublic class LTSNBAProduct extends Product<Model<?>>\n{\n\t/** A product state */\n\tprivate static class ProductState {\n\t\t/** The model state */\n\t\tprivate int modelState;\n\t\t/** The automaton state */\n\t\tprivate int automatonState;\n\n\t\t/** Constructor */\n\t\tpublic ProductState(int modelState, int automatonState)\n\t\t{\n\t\t\tthis.modelState = modelState;\n\t\t\tthis.automatonState = automatonState;\n\t\t}\n\n\t\t/** Get model state */\n\t\tpublic int getModelState()\n\t\t{\n\t\t\treturn modelState;\n\t\t}\n\n\t\t/** Get automaton state */\n\t\tpublic int getAutomatonState()\n\t\t{\n\t\t\treturn automatonState;\n\t\t}\n\t\t\n\t\tpublic String toString() {\n\t\t\treturn \"(\" + getModelState() + \",\" + getAutomatonState() +\")\";\n\t\t}\n\n\t\t@Override\n\t\tpublic int hashCode()\n\t\t{\n\t\t\tfinal int prime = 31;\n\t\t\tint result = 1;\n\t\t\tresult = prime * result + automatonState;\n\t\t\tresult = prime * result + modelState;\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(Object obj)\n\t\t{\n\t\t\tif (this == obj)\n\t\t\t\treturn true;\n\t\t\tif (obj == null)\n\t\t\t\treturn false;\n\t\t\tif (!(obj instanceof ProductState))\n\t\t\t\treturn false;\n\t\t\tProductState other = (ProductState) obj;\n\t\t\tif (automatonState != other.automatonState)\n\t\t\t\treturn false;\n\t\t\tif (modelState != other.modelState)\n\t\t\t\treturn false;\n\t\t\treturn true;\n\t\t}\n\t}\n\n\t/** Map state in product -> product state information */\n\tprivate ArrayList<ProductState> productStates;\n\t/** Accepting Büchi states in the product */\n\tprivate BitSet acceptingStates;\n\t/** Number of states in the NBA */\n\tprivate int nbaSize;\n\n\t/** Constructor for storing the product */\n\tprivate LTSNBAProduct(LTS<?> productModel, Model<?> originalModel, ArrayList<ProductState> productStates, BitSet acceptingStates, int nbaSize)\n\t{\n\t\tsuper(productModel, originalModel);\n\t\tthis.productStates = productStates;\n\t\tthis.acceptingStates = acceptingStates;\n\t\tthis.nbaSize = nbaSize;\n\t}\n\n\t@Override\n\tpublic int getModelState(int productState)\n\t{\n\t\treturn productStates.get(productState).modelState;\n\t}\n\n\t@Override\n\tpublic int getAutomatonState(int productState)\n\t{\n\t\treturn productStates.get(productState).automatonState;\n\t}\n\n\t@Override\n\tpublic int getAutomatonSize()\n\t{\n\t\treturn nbaSize;\n\t}\n\n\t/** Print the mapping between product state indizes and product states */\n\tpublic void printStateMapping(PrismLog log)\n\t{\n\t\tfor (int i =0; i < productStates.size(); i++) {\n\t\t\tlog.println(i + \": \" + productStates.get(i) + (acceptingStates.get(i) ? \" !\":\"\"));\n\t\t}\n\t}\n\n\t/** Get the Büchi states for the product */\n\tpublic BitSet getAcceptingStates()\n\t{\n\t\treturn acceptingStates;\n\t}\n\n\t/**\n\t * Construct the product.\n\t *\n\t * @param model the model\n\t * @param nba the nondeterministic Büchi automaton\n\t * @param statesOfInterest the states in the model that serve as the starting point for the product\n\t * @param labelBS vector of state sets for the atomic propositions L0, L1, ... in the automaton\n\t */\n\tpublic static LTSNBAProduct doProduct(Model<?> model, NBA nba, BitSet statesOfInterest, Vector<BitSet> labelBS)\n\t{\n\t\t// map state index in product automaton -> ProductState\n\t\tArrayList<ProductState> productIdToProductState = new ArrayList<ProductState>();\n\t\t// map ProductState -> state index in product automaton\n\t\tHashMap<ProductState, Integer> productStateToProductId = new HashMap<ProductState, Integer>();\n\n\t\t// storage for the product model\n\t\tLTSSimple<?> productModel = new LTSSimple<>();\n\t\t// the accepting states in the product model\n\t\tBitSet acceptingStates = new BitSet();\n\n\t\t// the stack of product ids that potentially have to be expanded\n\t\tStack<Integer> todo = new Stack<Integer>();\n\n\t\t// product state ids that have already been expanded\n\t\tBitSet expanded = new BitSet();\n\n\t\t// Note: In contrast to the deterministic automaton product elsewhere in\n\t\t// PRISM, the automaton step delta(q,l(s)) is done when leaving the product\n\t\t// state, not when entering. As we are only interested in the infinite behaviour,\n\t\t// this doesn't change acceptance at all:\n\t\t//\n\t\t//     <s,q> -> <s',q'>  where s->s' in the model and q' in delta(q, l(s))\n\t\t//\n\t\t// Thus, the initial states in the product are <s, q_0> for s in the states of interest\n\t\t// of the model and q_0 the initial state of the NBA.\n\n\t\tNBA_State nbaStart = nba.getStartState();\n\t\tif (nbaStart == null) {\n\t\t\t// no start state = rejecting\n\t\t\t// to simplify treatment, add a dummy start state\n\t\t\t// with no outgoing transitions\n\t\t\tnbaStart = nba.newState();\n\t\t\tnba.setStartState(nbaStart);\n\t\t}\n\n\t\t// Note: As the NBA currently is guaranteed to have a single initial state,\n\t\t// the product has exactly one initial product state per model state of interest.\n\t\t// This allows the use of the \"normal\" projection back from the product result to\n\t\t// the original model. For multiple initial NBA states, it would be necessary\n\t\t// to aggregate the results over all initial NBA states when projecting back to\n\t\t// the original model.\n\n\t\t// for each model state of interest ...\n\t\tfor (int modelState : new IterableStateSet(statesOfInterest, model.getNumStates())) {\n\t\t\t// ... construct a product state (modelState, nbaStart)\n\t\t\tProductState p = new ProductState(modelState, nbaStart.getName());\n\n\t\t\tproductIdToProductState.add(p);\n\t\t\tint id = productModel.addState();\n\t\t\tproductModel.addInitialState(id);\n\t\t\tassert ( id == productIdToProductState.size()-1 );\n\t\t\tproductStateToProductId.put(p, id);\n\t\t\ttodo.push(id);\n\t\t\tif (nbaStart.isFinal()) {\n\t\t\t\tacceptingStates.set(id);\n\t\t\t}\n\t\t}\n\t\t\n\t\tfinal APSet nbaAPSet = nba.getAPSet();\n\n\t\twhile (!todo.isEmpty()) {\n\t\t\tint fromId = todo.pop();\n\t\t\tif (expanded.get(fromId))\n\t\t\t\tcontinue;\n\n\t\t\tProductState from = productIdToProductState.get(fromId);\n\n\t\t\t// construct edge label from the labeling of the model state\n\t\t\tAPElement label = new APElement(nbaAPSet.size());\n\t\t\tfor (int k = 0; k < nbaAPSet.size(); k++) {\n\t\t\t\tlabel.set(k, labelBS.get(Integer.parseInt(nbaAPSet.getAP(k).substring(1))).get(from.getModelState()));\n\t\t\t}\n\n\t\t\t// the current state in the NBA\n\t\t\tNBA_State fromNBA = nba.get(from.getAutomatonState());\n\t\t\t// the successors in the NBA for the label corresponding to the model state\n\t\t\tBitSet nbaSuccessors = fromNBA.getEdge(label);\n\t\t\t// for each successor of the model state ...\n\t\t\tfor (Iterator<Integer> it = model.getSuccessorsIterator(from.getModelState()); it.hasNext(); ) {\n\t\t\t\tInteger modelTo = it.next();\n\t\t\t\t// ... and NBA successor ...\n\t\t\t\tfor (Integer nbaSuccessor : IterableBitSet.getSetBits(nbaSuccessors)) {\n\t\t\t\t\t// ... construct product state\n\t\t\t\t\tProductState successor = new ProductState(modelTo, nbaSuccessor);\n\t\t\t\t\tInteger successorID = productStateToProductId.get(successor);\n\t\t\t\t\tif (successorID == null) {\n\t\t\t\t\t\t// newly discovered, add as state to the product model\n\t\t\t\t\t\tproductIdToProductState.add(successor);\n\t\t\t\t\t\tsuccessorID = productModel.addState();\n\t\t\t\t\t\tassert ( successorID == productIdToProductState.size()-1 );\n\t\t\t\t\t\tproductStateToProductId.put(successor, successorID);\n\t\t\t\t\t\t// mark as todo\n\t\t\t\t\t\ttodo.push(successorID);\n\t\t\t\t\t\tboolean isAccepting = nba.get(nbaSuccessor).isFinal();\n\t\t\t\t\t\tif (isAccepting) {\n\t\t\t\t\t\t\tacceptingStates.set(successorID);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// add the edge\n\t\t\t\t\tproductModel.addTransition(fromId, successorID);\n\t\t\t\t}\n\n\t\t\t\t// fromId is fully expanded in the product\n\t\t\t\texpanded.set(fromId);\n\t\t\t}\n\t\t}\n\n\t\treturn new LTSNBAProduct(productModel, model, productIdToProductState, acceptingStates, nba.size());\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/LTSSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\nimport io.ExplicitModelImporter;\nimport prism.PrismException;\nimport strat.MDStrategy;\n\n/**\n * Simple explicit-state representation of an LTS (labelled transition system).\n * \n * Each transition from a state is considered to be a separate (singleton) \"choice\",\n * following the terminology in other nondeterministic explicit-state models.\n */\npublic class LTSSimple<Value> extends ModelExplicit<Value> implements LTS<Value>, NondetModelSimple<Value>\n{\n\t// Transition relation\n\tprotected List<List<Integer>> trans;\n\t\n\t// Action labels\n\tprotected ChoiceActionsSimple actions;\n\n\t// Statistics: total number of transitions\n\tprotected int numTransitions;\n\n\t// Constructors\n\n\t/**\n\t * Constructor: empty LTS.\n\t */\n\tpublic LTSSimple()\n\t{\n\t\tinitialise(0);\n\t}\n\n\t/**\n\t * Constructor: new LTS with fixed number of states.\n\t */\n\tpublic LTSSimple(int numStates)\n\t{\n\t\tinitialise(numStates);\n\t}\n\n\t/**\n\t * Construct an LTS from an existing one.\n\t */\n\tpublic LTSSimple(LTSSimple<Value> lts)\n\t{\n\t\tthis(lts.getNumStates());\n\t\tcopyFrom(lts);\n\t\t// Copy storage directly\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tList<Integer> succs = trans.get(s);\n\t\t\tfor (int succ : lts.trans.get(s)) {\n\t\t\t\tsuccs.add(succ);\n\t\t\t}\n\t\t}\n\t\tactions = new ChoiceActionsSimple(lts.actions);\n\t\t// Copy stats too\n\t\tnumTransitions = lts.numTransitions;\n\t}\n\n\t/**\n\t * Construct an LTS from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t */\n\tpublic LTSSimple(LTSSimple<Value> lts, int permut[])\n\t{\n\t\tthis(lts.getNumStates());\n\t\tcopyFrom(lts, permut);\n\t\t// Copy storage directly\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tList<Integer> succs = trans.get(permut[s]);\n\t\t\tfor (int succ : lts.trans.get(s)) {\n\t\t\t\tsuccs.add(permut[succ]);\n\t\t\t}\n\t\t}\n\t\tactions = new ChoiceActionsSimple(lts.actions, permut);\n\t\t// Copy stats too\n\t\tnumTransitions = lts.numTransitions;\n\t}\n\n\t@Override\n\tpublic void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\tinitialise(modelImporter.getNumStates());\n\t\tmodelImporter.extractLTSTransitions((s, i, s2, a) -> {\n\t\t\tif (i > getNumChoices(s)) {\n\t\t\t\tthrow new PrismException(\"Missing choice indices in state \" + s + \" when importing transitions\");\n\t\t\t}\n\t\t\t// Then add transition\n\t\t\taddActionLabelledTransition(s, s2, a);\n\t\t});\n\t}\n\n\t// Mutators (for ModelSimple)\n\n\t@Override\n\tpublic void initialise(int numStates)\n\t{\n\t\tsuper.initialise(numStates);\n\t\ttrans = new ArrayList<List<Integer>>();\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\ttrans.add(new ArrayList<Integer>());\n\t\t}\n\t\tactions = new ChoiceActionsSimple();\n\t\tnumTransitions = 0;\n\t}\n\n\t@Override\n\tpublic void clearState(int s)\n\t{\n\t\t// Clear data structures and update stats\n\t\tList<Integer> list = trans.get(s);\n\t\tnumTransitions -= list.size();\n\t\tlist.clear();\n\t\tactions.clearState(s);\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t@Override\n\tpublic int addState()\n\t{\n\t\taddStates(1);\n\t\treturn numStates - 1;\n\t}\n\n\t@Override\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tfor (int i = 0; i < numToAdd; i++) {\n\t\t\ttrans.add(new ArrayList<Integer>());\n\t\t\tnumStates++;\n\t\t}\n\t}\n\n\t// Mutators (other)\n\t\n\t/**\n\t * Add a transition from state {@code s} (which must exist) to state {code t}.\n\t */\n\tpublic void addTransition(int s, int t)\n\t{\n\t\t// We don't care if a transition from s to t already exists\n\t\ttrans.get(s).add(t);\n\t\tnumTransitions++;\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t/**\n\t * Add a transition from state {@code s} (which must exist)\n\t * to state {code t}, labelled with {@code action}.\n\t */\n\tpublic void addActionLabelledTransition(int s, int t, Object action)\n\t{\n\t\t// We don't care if a transition from s to t already exists\n\t\ttrans.get(s).add(t);\n\t\tactions.setAction(s, trans.get(s).size() - 1, action);\n\t\tnumTransitions++;\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t/**\n\t * Set the action label for choice/transition i in some state s.\n\t * Note that i is the index of the choice/transition, not the destination.\n\t */\n\tpublic void setAction(int s, int i, Object action)\n\t{\n\t\tactions.setAction(s, i, action);\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t// Accessors (for Model)\n\n\t@Override\n\tpublic List<Object> findActionsUsed()\n\t{\n\t\treturn actions.findActionsUsed(getNumStates(), this::getNumChoices);\n\t}\n\n\t@Override\n\tpublic boolean onlyNullActionUsed()\n\t{\n\t\treturn actions.onlyNullActionUsed();\n\t}\n\n\t@Override\n\tpublic int getNumTransitions()\n\t{\n\t\treturn numTransitions;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s)\n\t{\n\t\treturn getNumChoices(s);\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tint fixed = 0;\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (trans.get(i).isEmpty()) {\n\t\t\t\taddDeadlockState(i);\n\t\t\t\tif (fix) {\n\t\t\t\t\taddTransition(i, i);\n\t\t\t\t\tfixed++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Add the empty action (if missing), regardless of whether actionList needs recomputing\n\t\tif (fixed > 0) {\n\t\t\tactionList.addAction(null);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (trans.get(i).isEmpty() && (except == null || !except.get(i)))\n\t\t\t\tthrow new PrismException(\"Model has a deadlock in state \" + i);\n\t\t}\n\t}\n\t\n\t// Accessors (for NondetModel)\n\n\t@Override\n\tpublic int getNumChoices(int s)\n\t{\n\t\t// one choice per successor for s\n\t\treturn trans.get(s).size();\n\t}\n\n\t@Override\n\tpublic int getNumChoices()\n\t{\n\t\treturn numTransitions;\n\t}\n\n\t@Override\n\tpublic Object getAction(int s, int i)\n\t{\n\t\treturn actions.getAction(s, i);\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s, int i)\n\t{\n\t\tif (i < getNumChoices(s)) {\n\t\t\t// one transition per choice\n\t\t\treturn 1;\n\t\t}\n\t\tthrow new IllegalArgumentException();\n\t}\n\n\t@Override\n\tpublic boolean allSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\t// single successor for s, i\n\t\treturn set.get(trans.get(s).get(i));\n\t}\n\n\t@Override\n\tpublic boolean someSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\t// single successor for s, i\n\t\treturn set.get(trans.get(s).get(i));\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(int s, int i)\n\t{\n\t\t// single successor for s, i\n\t\treturn SuccessorsIterator.fromSingleton(trans.get(s).get(i));\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(int s)\n\t{\n\t\treturn SuccessorsIterator.from(trans.get(s).iterator(), false);\n\t}\n\n\t@Override\n\tpublic Model<Value> constructInducedModel(MDStrategy<Value> strat)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\t\n\t// Accessors (for LTS)\n\t\n\t@Override\n\tpublic int getSuccessor(int s, int i)\n\t{\n\t\treturn trans.get(s).get(i); \n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ListNestedSimple.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.List;\nimport java.util.Objects;\nimport java.util.function.Function;\nimport java.util.function.Predicate;\n\n/**\n * A list of lists of values. Mutable, but not especially efficient.\n * Storage is minimised by only storing the list (and sublists) as needed.\n * This partly depends on the definition of a \"zero\" value (null by default).\n * The actual size of the list and sublists is not known/stored.\n */\npublic class ListNestedSimple<E>\n{\n\t/**\n\t * The values, stored as a list of lists.\n\t * Can be null, implying all zero. So can sublists.\n\t **/\n\tprotected List<List<E>> values;\n\n\t/** Value for \"zero\" entries (defaults to null) */\n\tprotected E zero = null;\n\n\t/** Test if a value is \"zero\" */\n\tprotected Predicate<E> isZero = Objects::isNull;\n\n\t/**\n\t * Constructor: zero list\n\t */\n\tpublic ListNestedSimple()\n\t{\n\t\tthis(null, Objects::isNull);\n\t}\n\n\t/**\n\t * Constructor: zero list\n\t * @param zero Zero value\n\t * @param isZero Test for zero\n\t */\n\tpublic ListNestedSimple(E zero, Predicate<E> isZero)\n\t{\n\t\t// Initially list is just null (denoting all zero)\n\t\tvalues = null;\n\t\tsetZero(zero, isZero);\n\t}\n\n\t/**\n\t * Copy constructor\n\t * @param listn ListNestedSimple to copy\n\t */\n\tpublic ListNestedSimple(ListNestedSimple<E> listn)\n\t{\n\t\tif (listn.values == null) {\n\t\t\tvalues = null;\n\t\t} else {\n\t\t\tint n = listn.values.size();\n\t\t\tvalues = new ArrayList<>(n);\n\t\t\tfor (List<E> list : listn.values) {\n\t\t\t\tvalues.add(list == null ? null : new ArrayList<>(list));\n\t\t\t}\n\t\t}\n\t\tsetZero(listn.zero, listn.isZero);\n\t}\n\n\t/**\n\t * Copy constructor with a value map, which is applied to values from the copied list.\n\t * A new zero and zero test is provided since it is likely different.\n\t * @param listn ListNestedSimple to copy\n\t * @param valMap The value map\n\t * @param zero Zero value\n\t * @param isZero Test for zero\n\t */\n\tpublic <T> ListNestedSimple(ListNestedSimple<T> listn, Function<? super T, ? extends E> valMap, E zero, Predicate<E> isZero)\n\t{\n\t\tif (listn.values == null) {\n\t\t\tvalues = null;\n\t\t} else {\n\t\t\tint n = listn.values.size();\n\t\t\tvalues = new ArrayList<>(n);\n\t\t\tfor (List<T> list : listn.values) {\n\t\t\t\tif (list == null) {\n\t\t\t\t\tvalues.add(null);\n\t\t\t\t} else {\n\t\t\t\t\tList<E> list2 = new ArrayList<>(list.size());\n\t\t\t\t\tvalues.add(list2);\n\t\t\t\t\tfor (T value : list) {\n\t\t\t\t\t\tlist2.add(valMap.apply(value));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tsetZero(zero, isZero);\n\t}\n\n\t/**\n\t * Copy constructor with index permutation,\n\t * i.e., in which index {@code i} becomes index {@code permut[i]}.\n\t * @param listn ListNestedSimple to copy\n\t * @param permut Index permutation\n\t */\n\tpublic ListNestedSimple(ListNestedSimple<E> listn, int permut[])\n\t{\n\t\tif (listn.values == null) {\n\t\t\tvalues = null;\n\t\t} else {\n\t\t\tint n = permut.length;\n\t\t\tvalues = new ArrayList<>(n);\n\t\t\tvalues.addAll(Collections.nCopies(n, null));\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tList<E> list = listn.getSubList(i);\n\t\t\t\tvalues.set(permut[i], list == null ? null : new ArrayList<>(list));\n\t\t\t}\n\t\t}\n\t\tsetZero(listn.zero, listn.isZero);\n\t}\n\n\t/**\n\t * Copy constructor with index permutation,\n\t * i.e., in which index {@code i} becomes index {@code permut[i]},\n\t * and a value map, which is applied to values from the copied list.\n\t * A new zero and zero test is provided since it is likely different.\n\t * @param listn ListNestedSimple to copy\n\t * @param permut Index permutation\n\t * @param valMap The value map\n\t * @param zero Zero value\n\t * @param isZero Test for zero\n\t */\n\tpublic <T> ListNestedSimple(ListNestedSimple<T> listn, int permut[], Function<? super T, ? extends E> valMap, E zero, Predicate<E> isZero)\n\t{\n\t\tif (listn.values == null) {\n\t\t\tvalues = null;\n\t\t} else {\n\t\t\tint n = permut.length;\n\t\t\tvalues = new ArrayList<>(n);\n\t\t\tvalues.addAll(Collections.nCopies(n, null));\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tList<T> list = listn.getSubList(i);\n\t\t\t\tif (list == null) {\n\t\t\t\t\tvalues.set(permut[i], null);\n\t\t\t\t} else {\n\t\t\t\t\tList<E> list2 = new ArrayList<>(list.size());\n\t\t\t\t\tvalues.set(permut[i], list2);\n\t\t\t\t\tfor (T value : list) {\n\t\t\t\t\t\tlist2.add(valMap.apply(value));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tsetZero(zero, isZero);\n\t}\n\n\t/**\n\t * Set the \"zero\" value for the list, and a test for it.\n\t * @param zero Zero value\n\t * @param isZero Test for zero\n\t */\n\tpublic void setZero(E zero, Predicate<E> isZero)\n\t{\n\t\tthis.zero = zero;\n\t\tthis.isZero = isZero;\n\t}\n\n\t/**\n\t * Set the value for index {@code i}, {@code j} to {@code value}.\n\t */\n\tpublic void setValue(int i, int j, E value)\n\t{\n\t\t// Create main list if not done yet\n\t\tif (values == null) {\n\t\t\tif (isZero.test(value)) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tvalues = new ArrayList<>();\n\t\t}\n\t\t// Expand main list up to index i if needed,\n\t\t// storing null for newly added items\n\t\tif (i >= values.size()) {\n\t\t\tif (isZero.test(value)) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tvalues.addAll(Collections.nCopies(i - values.size() + 1, null));\n\t\t\tint n = i - values.size() + 1;\n\t\t}\n\t\t// Create sublist for index i if needed\n\t\tList<E> list;\n\t\tif ((list = values.get(i)) == null) {\n\t\t\tif (isZero.test(value)) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tvalues.set(i, (list = new ArrayList<>()));\n\t\t}\n\t\t// Expand sublist up to index j if needed,\n\t\t// storing zero for newly added items\n\t\tif (j >= list.size()) {\n\t\t\tif (isZero.test(value)) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tint n = j - list.size() + 1;\n\t\t\tfor (int j2 = 0; j2 < n; j2++) {\n\t\t\t\tlist.add(zero);\n\t\t\t}\n\t\t}\n\t\t// Store the value\n\t\tlist.set(j, value);\n\t}\n\n\t/**\n\t * Set the list at index {@code i}, copy the list from index {code i2} of another {@link ListNestedSimple}.\n\t * @param i Index to set\n\t * @param listn ListNestedSimple to copy from\n\t * @param i2 Index to copy from\n\t */\n\tpublic void copyFrom(int i, ListNestedSimple<E> listn, int i2)\n\t{\n\t\t// Create main list if not done yet\n\t\tif (values == null) {\n\t\t\tvalues = new ArrayList<>();\n\t\t}\n\t\t// Expand main list up to index i if needed,\n\t\t// storing null for newly added items\n\t\tif (i >= values.size()) {\n\t\t\tvalues.addAll(Collections.nCopies(i - values.size() + 1, null));\n\t\t}\n\t\t// Copy list\n\t\tList<E> list = listn.getSubList(i2);\n\t\tvalues.set(i, list == null ? null : new ArrayList<>(list));\n\t}\n\n\t/**\n\t * Clear the list at index {@code i}.\n\t * @param i Index\n\t */\n\tpublic void clear(int i)\n\t{\n\t\tif (values != null && values.size() > i && values.get(i) != null) {\n\t\t\tvalues.set(i, null);\n\t\t}\n\t}\n\n\t/**\n\t * Get the value for index {@code i}, {@code j}.\n\t */\n\tpublic E getValue(int i, int j)\n\t{\n\t\tList<E> list;\n\t\tif (values == null || i >= values.size() || (list = values.get(i)) == null)\n\t\t\treturn zero;\n\t\tif (j >= list.size())\n\t\t\treturn zero;\n\t\treturn list.get(j);\n\t}\n\n\t/**\n\t * Get the sublist for index {@code i}.\n\t */\n\tprotected List<E> getSubList(int i)\n\t{\n\t\treturn (values == null || i >= values.size()) ? null : values.get(i);\n\t}\n\n\t/**\n\t * Returns true if the list is all zero.\n\t * BUT: This is done via a quick check. for efficiency.\n\t * If it returns true, the list is definitely all zero,\n\t * but the converse is not necessarily true.\n\t */\n\tpublic boolean allZero()\n\t{\n\t\treturn values == null;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn values == null ? \"[]\" : values.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ListSimple.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.List;\nimport java.util.Objects;\nimport java.util.function.Function;\nimport java.util.function.Predicate;\n\n/**\n * A list of values. Mutable, but not especially efficient.\n * Storage is minimised by only storing the list if needed.\n * This partly depends on the definition of a \"zero\" value (null by default).\n * The actual size of the list is not known/stored.\n */\npublic class ListSimple<E>\n{\n\t/**\n\t * The values, stored as a list.\n\t * Can be null, implying all zero.\n\t **/\n\tprotected List<E> values;\n\n\t/** Value for \"zero\" entries (defaults to null) */\n\tprotected E zero = null;\n\n\t/** Test if a value is \"zero\" */\n\tprotected Predicate<E> isZero = Objects::isNull;\n\n\t/**\n\t * Constructor: zero list\n\t */\n\tpublic ListSimple()\n\t{\n\t\tthis(null, Objects::isNull);\n\t}\n\n\t/**\n\t * Constructor: zero list\n\t * @param zero Zero value\n\t * @param isZero Test for zero\n\t */\n\tpublic ListSimple(E zero, Predicate<E> isZero)\n\t{\n\t\t// Initially list is just null (denoting all zero)\n\t\tvalues = null;\n\t\tsetZero(zero, isZero);\n\t}\n\n\t/**\n\t * Copy constructor\n\t * @param list ListSimple to copy\n\t */\n\tpublic ListSimple(ListSimple<E> list)\n\t{\n\t\tvalues = list.values == null ? null : new ArrayList<>(list.values);\n\t\tsetZero(list.zero, list.isZero);\n\t}\n\n\t/**\n\t * Copy constructor with a value map, which is applied to values from the copied list.\n\t * A new zero and zero test is provided since it is likely different.\n\t * @param list ListSimple to copy\n\t * @param valMap The value map\n\t * @param zero Zero value\n\t * @param isZero Test for zero\n\t */\n\tpublic <T> ListSimple(ListSimple<T> list, Function<? super T, ? extends E> valMap, E zero, Predicate<E> isZero)\n\t{\n\t\tif (list.values == null) {\n\t\t\tvalues = null;\n\t\t} else {\n\t\t\tvalues = new ArrayList<>(list.values.size());\n\t\t\tfor (T value : list.values) {\n\t\t\t\tvalues.add(valMap.apply(value));\n\t\t\t}\n\t\t}\n\t\tsetZero(zero, isZero);\n\t}\n\n\t/**\n\t * Copy constructor with index permutation,\n\t * i.e., in which index {@code i} becomes index {@code permut[i]}.\n\t * @param list ListSimple to copy\n\t * @param permut Index permutation\n\t */\n\tpublic ListSimple(ListSimple<E> list, int permut[])\n\t{\n\t\tif (list.values == null) {\n\t\t\tvalues = null;\n\t\t} else {\n\t\t\tint n = permut.length;\n\t\t\tvalues = new ArrayList<>(n);\n\t\t\tvalues.addAll(Collections.nCopies(n, null));\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tvalues.set(permut[i], list.values.get(i));\n\t\t\t}\n\t\t}\n\t\tsetZero(list.zero, list.isZero);\n\t}\n\n\t/**\n\t * Copy constructor with index permutation,\n\t * i.e., in which index {@code i} becomes index {@code permut[i]},\n\t * and a value map, which is applied to values from the copied list.\n\t * A new zero and zero test is provided since it is likely different.\n\t * @param list ListSimple to copy\n\t * @param permut Index permutation\n\t * @param valMap The value map\n\t * @param zero Zero value\n\t * @param isZero Test for zero\n\t */\n\tpublic <T> ListSimple(ListSimple<T> list, int permut[], Function<? super T, ? extends E> valMap, E zero, Predicate<E> isZero)\n\t{\n\t\tif (list.values == null) {\n\t\t\tvalues = null;\n\t\t} else {\n\t\t\tint n = permut.length;\n\t\t\tvalues = new ArrayList<>(n);\n\t\t\tvalues.addAll(Collections.nCopies(n, null));\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tvalues.set(permut[i], valMap.apply(list.values.get(i)));\n\t\t\t}\n\t\t}\n\t\tsetZero(zero, isZero);\n\t}\n\n\t/**\n\t * Set the \"zero\" value for the list, and a test for it.\n\t * @param zero Zero value\n\t * @param isZero Test for zero\n\t */\n\tpublic void setZero(E zero, Predicate<E> isZero)\n\t{\n\t\tthis.zero = zero;\n\t\tthis.isZero = isZero;\n\t}\n\n\t/**\n\t * Set the value for index {@code i} to {@code value}.\n\t */\n\tpublic void setValue(int i, E value)\n\t{\n\t\t// Create main list if not done yet\n\t\tif (values == null) {\n\t\t\tif (isZero.test(value)) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tvalues = new ArrayList<>(i + 1);\n\t\t}\n\t\t// Expand main list up to index i if needed,\n\t\t// storing zero for newly added items\n\t\tif (i >= values.size()) {\n\t\t\tif (isZero.test(value)) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tint n = i - values.size() + 1;\n\t\t\tfor (int i2 = 0; i2 < n; i2++) {\n\t\t\t\tvalues.add(zero);\n\t\t\t}\n\t\t}\n\t\t// Store the value\n\t\tvalues.set(i, value);\n\t}\n\n\t/**\n\t * Get the value for index {@code i}, {@code j}.\n\t */\n\tpublic E getValue(int i)\n\t{\n\t\treturn (values == null || i >= values.size()) ? zero : values.get(i);\n\t}\n\n\t/**\n\t * Returns true if the list is all zero.\n\t * BUT: This is done via a quick check. for efficiency.\n\t * If it returns true, the list is definitely all zero,\n\t * but the converse is not necessarily true.\n\t */\n\tpublic boolean allZero()\n\t{\n\t\treturn values == null;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn values == null ? \"[]\" : values.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/MDP.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.FileWriter;\nimport java.io.IOException;\nimport java.util.AbstractMap;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.PrimitiveIterator;\nimport java.util.TreeMap;\nimport java.util.PrimitiveIterator.OfInt;\nimport java.util.function.Function;\n\nimport common.IterableStateSet;\nimport common.IteratorTools;\nimport common.iterable.FunctionalIterator;\nimport common.iterable.Reducible;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismUtils;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state MDP.\n */\npublic interface MDP<Value> extends NondetModel<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.MDP;\n\t}\n\n\t@Override\n\tdefault void exportToPrismLanguage(final String filename, int precision) throws PrismException\n\t{\n\t\ttry (FileWriter out = new FileWriter(filename)) {\n\t\t\t// Output transitions to PRISM language file\n\t\t\tout.write(getModelType().keyword() + \"\\n\");\n\t\t\tfinal int numStates = getNumStates();\n\t\t\tout.write(\"module M\\nx : [0..\" + (numStates - 1) + \"];\\n\");\n\t\t\tfinal TreeMap<Integer, Value> sorted = new TreeMap<Integer, Value>();\n\t\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\t\tfor (int choice = 0, numChoices = getNumChoices(state); choice < numChoices; choice++) {\n\t\t\t\t\t// Extract transitions and sort by destination state index (to match PRISM-exported files)\n\t\t\t\t\tfor (Iterator<Entry<Integer, Value>> transitions = getTransitionsIterator(state, choice); transitions.hasNext();) {\n\t\t\t\t\t\tfinal Entry<Integer, Value> trans = transitions.next();\n\t\t\t\t\t\tsorted.put(trans.getKey(), trans.getValue());\n\t\t\t\t\t}\n\t\t\t\t\t// Print out (sorted) transitions\n\t\t\t\t\tfinal Object action = getAction(state, choice);\n\t\t\t\t\tout.write(action != null ? (\"[\" + action + \"]\") : \"[]\");\n\t\t\t\t\tout.write(\"x=\" + state + \"->\");\n\t\t\t\t\tboolean first = true;\n\t\t\t\t\tfor (Entry<Integer, Value> e : sorted.entrySet()) {\n\t\t\t\t\t\tif (first)\n\t\t\t\t\t\t\tfirst = false;\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\tout.write(\"+\");\n\t\t\t\t\t\tout.write(getEvaluator().toStringPrism(e.getValue(), precision) + \":(x'=\" + e.getKey() + \")\");\n\t\t\t\t\t}\n\t\t\t\t\tout.write(\";\\n\");\n\t\t\t\t\tsorted.clear();\n\t\t\t\t}\n\t\t\t}\n\t\t\tout.write(\"endmodule\\n\");\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"Could not export \" + getModelType() + \" to file \\\"\" + filename + \"\\\"\" + e);\n\t\t}\n\t}\n\n\t// Accessors (for NondetModel) - default implementations\n\t\n\t@Override\n\tdefault int getNumTransitions(final int s, final int i)\n\t{\n\t\treturn Math.toIntExact(IteratorTools.count(getTransitionsIterator(s, i)));\n\t}\n\t\n\t// Accessors\n\t\n\t/**\n\t * Get an iterator over the transitions from choice {@code i} of state {@code s}.\n\t */\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(int s, int i);\n\n\t/**\n\t * Get an iterator over the transitions from choice {@code i} of state {@code s},\n\t * after mapping probability values using the provided function.\n\t */\n\tpublic default <T> FunctionalIterator<Entry<Integer, T>> getTransitionsMappedIterator(int s, int i, Function<? super Value, ? extends T> function)\n\t{\n\t\treturn Reducible.extend(getTransitionsIterator(s, i)).map(t -> new AbstractMap.SimpleImmutableEntry<>(t.getKey(), function.apply(t.getValue())));\n\t}\n\n\t/**\n\t * Functional interface for a consumer,\n\t * accepting transitions (s,t,d), i.e.,\n\t * from state s to state t with value d.\n\t */\n\t@FunctionalInterface\n\tpublic interface TransitionConsumer<Value> {\n\t\tvoid accept(int s, int t, Value d);\n\t}\n\n\t/**\n\t * Iterate over the outgoing transitions of state {@code s} and choice {@code i}\n\t * and call the accept method of the consumer for each of them:\n\t * <br>\n\t * Call {@code accept(s,t,d)} where t is the successor state d = P(s,i,t)\n\t * is the probability from s to t with choice i.\n\t * <p>\n\t * <i>Default implementation</i>: The default implementation relies on iterating over the\n\t * iterator returned by {@code getTransitionsIterator()}.\n\t * <p><i>Note</i>: This method is the base for the default implementation of the numerical\n\t * computation methods (mvMult, etc). In derived classes, it may thus be worthwhile to\n\t * provide a specialised implementation for this method that avoids using the Iterator mechanism.\n\t *\n\t * @param s the state s\n\t * @param i the choice i\n\t * @param c the consumer\n\t */\n\tpublic default void forEachTransition(int s, int i, TransitionConsumer<Value> c)\n\t{\n\t\tfor (Iterator<Entry<Integer, Value>> it = getTransitionsIterator(s, i); it.hasNext(); ) {\n\t\t\tEntry<Integer, Value> e = it.next();\n\t\t\tc.accept(s, e.getKey(), e.getValue());\n\t\t}\n\t}\n\n\t/**\n\t * Functional interface for a function\n\t * mapping transitions (s,t,d), i.e.,\n\t * from state s to state t with value d,\n\t * to a numerical value.\n\t */\n\t@FunctionalInterface\n\tpublic interface TransitionToValueFunction<Value> {\n\t\tValue apply(int s, int t, Value d);\n\t}\n\n\t/**\n\t * Iterate over the outgoing transitions of state {@code s} and choice {@code i},\n\t * call the function {@code f} and return the sum of the result values:\n\t * <br>\n\t * Return sum_t f(s, t, P(s,i,t)), where t ranges over the i-successors of s.\n\t *\n\t * @param s the state s\n\t * @param i the choice i\n\t * @param f the function\n\t */\n\tpublic default Value sumOverTransitions(final int s, final int i, final TransitionToValueFunction<Value> f)\n\t{\n\t\tclass Sum {\n\t\t\tValue sum = getEvaluator().zero();\n\t\t\tvoid accept(int s, int t, Value d)\n\t\t\t{\n\t\t\t\tsum = getEvaluator().add(sum, f.apply(s, t, d));\n\t\t\t}\n\t\t}\n\n\t\tSum sum = new Sum();\n\t\tforEachTransition(s, i, sum::accept);\n\n\t\treturn sum.sum;\n\t}\n\n\t// Methods for case where Value is Double\n\t\n\t/**\n\t * Functional interface for a consumer,\n\t * accepting transitions (s,t,d), i.e.,\n\t * from state s to state t with value d.\n\t */\n\t@FunctionalInterface\n\tpublic interface DoubleTransitionConsumer {\n\t\tvoid accept(int s, int t, double d);\n\t}\n\n\t/**\n\t * Iterate over the outgoing transitions of state {@code s} and choice {@code i}\n\t * and call the accept method of the consumer for each of them:\n\t * <br>\n\t * Call {@code accept(s,t,d)} where t is the successor state d = P(s,i,t)\n\t * is the probability from s to t with choice i.\n\t * <p>\n\t * <i>Default implementation</i>: The default implementation relies on iterating over the\n\t * iterator returned by {@code getTransitionsIterator()}.\n\t * <p><i>Note</i>: This method is the base for the default implementation of the numerical\n\t * computation methods (mvMult, etc). In derived classes, it may thus be worthwhile to\n\t * provide a specialised implementation for this method that avoids using the Iterator mechanism.\n\t *\n\t * @param s the state s\n\t * @param i the choice i\n\t * @param c the consumer\n\t */\n\tpublic default void forEachDoubleTransition(int s, int i, DoubleTransitionConsumer c)\n\t{\n\t\tfor (Iterator<Entry<Integer, Value>> it = getTransitionsIterator(s, i); it.hasNext(); ) {\n\t\t\tEntry<Integer, Value> e = it.next();\n\t\t\tc.accept(s, e.getKey(), getEvaluator().toDouble(e.getValue()));\n\t\t}\n\t}\n\n\t/**\n\t * Functional interface for a function\n\t * mapping transitions (s,t,d), i.e.,\n\t * from state s to state t with value d,\n\t * to a double value.\n\t */\n\t@FunctionalInterface\n\tpublic interface DoubleTransitionToDoubleFunction {\n\t\tdouble apply(int s, int t, double d);\n\t}\n\n\t/**\n\t * Iterate over the outgoing transitions of state {@code s} and choice {@code i},\n\t * call the function {@code f} and return the sum of the result values:\n\t * <br>\n\t * Return sum_t f(s, t, P(s,i,t)), where t ranges over the i-successors of s.\n\t *\n\t * @param s the state s\n\t * @param i the choice i\n\t * @param f the function\n\t */\n\tpublic default double sumOverDoubleTransitions(final int s, final int i, final DoubleTransitionToDoubleFunction f)\n\t{\n\t\tclass Sum {\n\t\t\tdouble sum = 0.0;\n\n\t\t\tvoid accept(int s, int t, double d)\n\t\t\t{\n\t\t\t\tsum += f.apply(s, t, d);\n\t\t\t}\n\t\t}\n\n\t\tSum sum = new Sum();\n\t\tforEachDoubleTransition(s, i, sum::accept);\n\n\t\treturn sum.sum;\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication followed by min/max, i.e. one step of value iteration,\n\t * i.e. for all s: result[s] = min/max_k { sum_j P_k(s,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param min Min or max for (true=min, false=max)\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default void mvMultMinMax(double vect[], boolean min, double result[], BitSet subset, boolean complement, int strat[])\n\t{\n\t\tmvMultMinMax(vect, min, result, new IterableStateSet(subset, getNumStates(), complement).iterator(), strat);\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication followed by min/max, i.e. one step of value iteration,\n\t * i.e. for all s: result[s] = min/max_k { sum_j P_k(s,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param min Min or max for (true=min, false=max)\n\t * @param result Vector to store result in\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default void mvMultMinMax(double vect[], boolean min, double result[], PrimitiveIterator.OfInt states, int strat[])\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\tresult[s] = mvMultMinMaxSingle(s, vect, min, strat);\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication followed by min/max,\n\t * i.e. return min/max_k { sum_j P_k(s,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param min Min or max for (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default double mvMultMinMaxSingle(int s, double vect[], boolean min, int strat[])\n\t{\n\t\tint stratCh = -1;\n\t\tdouble minmax = 0;\n\t\tboolean first = true;\n\n\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t// Compute sum for this distribution\n\t\t\tdouble d = mvMultSingle(s, choice, vect);\n\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null)\n\t\t\t\t\tstratCh = choice;\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null && !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\t/**\n\t * Determine which choices result in min/max after a single row of matrix-vector multiplication.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param min Min or max (true=min, false=max)\n\t * @param val Min or max value to match\n\t */\n\tpublic default List<Integer> mvMultMinMaxSingleChoices(int s, double vect[], boolean min, double val)\n\t{\n\t\t// Create data structures to store strategy\n\t\tfinal List<Integer> result = new ArrayList<Integer>();\n\t\t// One row of matrix-vector operation\n\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t// Compute sum for this distribution\n\t\t\tdouble d = mvMultSingle(s, choice, vect);\n\n\t\t\t// Store strategy info if value matches\n\t\t\tif (PrismUtils.doublesAreEqual(val, d)) {\n\t\t\t\tresult.add(choice);\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication for a specific choice.\n\t * @param s State (row) index\n\t * @param i Choice index\n\t * @param vect Vector to multiply by\n\t */\n\tpublic default double mvMultSingle(int s, int i, double vect[])\n\t{\n\t\treturn sumOverDoubleTransitions(s, i, (int __, int t, double prob) -> {\n\t\t\treturn prob * vect[t];\n\t\t});\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication followed by min/max.\n\t * i.e. for all s: vect[s] = min/max_k { (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param min Min or max for (true=min, false=max)\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * @return The maximum difference between old/new elements of {@code vect}\n\t */\n\tpublic default double mvMultGSMinMax(double vect[], boolean min, BitSet subset, boolean complement, boolean absolute, int strat[])\n\t{\n\t\treturn mvMultGSMinMax(vect, min, new IterableStateSet(subset, getNumStates(), complement).iterator(), absolute, strat);\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication followed by min/max.\n\t * i.e. for all s: vect[s] = min/max_k { (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param min Min or max for (true=min, false=max)\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * @return The maximum difference between old/new elements of {@code vect}\n\t */\n\tpublic default double mvMultGSMinMax(double vect[], boolean min, PrimitiveIterator.OfInt states, boolean absolute, int strat[])\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\td = mvMultJacMinMaxSingle(s, vect, min, strat);\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication followed by min/max in the context of interval iteration.\n\t * i.e. for all s: vect[s] = min/max_k { (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * and store new values directly in {@code vect} as computed.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param min Min or max for (true=min, false=max)\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * @param ensureMonotonic ensure monotonicity\n\t * @param fromBelow iteration from below or from above? (for ensureMonotonicity)\n\t */\n\tpublic default void mvMultGSMinMaxIntervalIter(double vect[], boolean min, PrimitiveIterator.OfInt states, int strat[], boolean ensureMonotonic, boolean fromBelow)\n\t{\n\t\tdouble d;\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\td = mvMultJacMinMaxSingle(s, vect, min, strat);\n\t\t\tif (ensureMonotonic) {\n\t\t\t\tif (fromBelow) {\n\t\t\t\t\t// from below: do max old and new\n\t\t\t\t\tif (vect[s] > d) {\n\t\t\t\t\t\td = vect[s];\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// from above: do min old and new\n\t\t\t\t\tif (vect[s] < d) {\n\t\t\t\t\t\td = vect[s];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tvect[s] = d;\n\t\t\t} else {\n\t\t\t\tvect[s] = d;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of Jacobi-style matrix-vector multiplication followed by min/max.\n\t * i.e. return min/max_k { (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param min Min or max for (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default double mvMultJacMinMaxSingle(int s, double vect[], boolean min, int strat[])\n\t{\n\t\tint stratCh = -1;\n\t\tdouble minmax = 0;\n\t\tboolean first = true;\n\n\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\tdouble d = mvMultJacSingle(s, choice, vect);\n\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null) {\n\t\t\t\t\tstratCh = choice;\n\t\t\t\t}\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null && !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\n\t}\n\n\t/**\n\t * Do a single row of Jacobi-style matrix-vector multiplication for a specific choice.\n\t * i.e. return min/max_k { (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * @param s Row index\n\t * @param i Choice index\n\t * @param vect Vector to multiply by\n\t */\n\tpublic default double mvMultJacSingle(int s, int i, double vect[])\n\t{\n\t\tclass Jacobi {\n\t\t\tdouble diag = 1.0;\n\t\t\tdouble d = 0.0;\n\n\t\t\tvoid accept(int s, int t, double prob) {\n\t\t\t\tif (t != s) {\n\t\t\t\t\td += prob * vect[t];\n\t\t\t\t} else {\n\t\t\t\t\tdiag -= prob;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tJacobi jac = new Jacobi();\n\t\tforEachDoubleTransition(s, i, jac::accept);\n\n\t\tdouble d = jac.d;\n\t\tdouble diag = jac.diag;\n\t\tif (diag > 0)\n\t\t\td /= diag;\n\n\t\treturn d;\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of rewards followed by min/max, i.e. one step of value iteration.\n\t * i.e. for all s: result[s] = min/max_k { rew(s) + rew_k(s) + sum_j P_k(s,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param min Min or max for (true=min, false=max)\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default void mvMultRewMinMax(double vect[], MDPRewards<Double> mdpRewards, boolean min, double result[], BitSet subset, boolean complement, int strat[])\n\t{\n\t\tfor (OfInt it = new IterableStateSet(subset, getNumStates(), complement).iterator(); it.hasNext();) {\n\t\t\tfinal int s = it.nextInt();\n\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, mdpRewards, min, strat);\n\t\t}\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of rewards followed by min/max, i.e. one step of value iteration.\n\t * i.e. for all s: result[s] = min/max_k { rew(s) + rew_k(s) + sum_j P_k(s,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param min Min or max for (true=min, false=max)\n\t * @param result Vector to store result in\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default void mvMultRewMinMax(double vect[], MDPRewards<Double> mdpRewards, boolean min, double result[], PrimitiveIterator.OfInt states, int strat[])\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, mdpRewards, min, strat);\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication and sum of rewards followed by min/max.\n\t * i.e. return min/max_k { rew(s) + rew_k(s) + sum_j P_k(s,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param min Min or max for (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default double mvMultRewMinMaxSingle(int s, double vect[], MDPRewards<Double> mdpRewards, boolean min, int strat[])\n\t{\n\t\tint stratCh = -1;\n\t\tdouble minmax = 0;\n\t\tboolean first = true;\n\n\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\tdouble d = mvMultRewSingle(s, choice, vect, mdpRewards);\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null)\n\t\t\t\t\tstratCh = choice;\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null && !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication and sum of rewards for a specific choice.\n\t * i.e. rew(s) + rew_i(s) + sum_j P_i(s,j)*vect[j]\n\t * @param s State (row) index\n\t * @param i Choice index\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards (MDP rewards)\n\t */\n\tpublic default double mvMultRewSingle(int s, int i, double vect[], MDPRewards<Double> mdpRewards)\n\t{\n\t\tdouble d = mdpRewards.getStateReward(s);\n\t\td += mdpRewards.getTransitionReward(s, i);\n\t\td += sumOverDoubleTransitions(s, i, (__, t, prob) -> {\n\t\t\treturn prob * vect[t];\n\t\t});\n\t\treturn d;\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication and sum of rewards for a specific choice.\n\t * i.e. rew(s) + rew_k(s) + sum_j P_k(s,j)*vect[j]\n\t * @param s State (row) index\n\t * @param i Choice index\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards (DTMC rewards)\n\t */\n\tpublic default double mvMultRewSingle(int s, int i, double vect[], MCRewards<Double> mcRewards)\n\t{\n\t\tdouble d = mcRewards.getStateReward(s);\n\t\t// TODO: add transition rewards when added to MCRewards\n\t\td += sumOverDoubleTransitions(s, i, (__, t, prob) -> {\n\t\t\treturn prob * vect[t];\n\t\t});\n\t\treturn d;\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication and sum of rewards followed by min/max.\n\t * i.e. for all s: vect[s] = min/max_k { rew(s) + rew_k(s) + (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param mdpRewards The rewards\n\t * @param min Min or max for (true=min, false=max)\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t * @return The maximum difference between old/new elements of {@code vect}\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default double mvMultRewGSMinMax(double vect[], MDPRewards<Double> mdpRewards, boolean min, BitSet subset, boolean complement, boolean absolute, int strat[])\n\t{\n\t\treturn mvMultRewGSMinMax(vect, mdpRewards, min, new IterableStateSet(subset, getNumStates(), complement).iterator(), absolute, strat);\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication and sum of rewards followed by min/max.\n\t * i.e. for all s: vect[s] = min/max_k { rew(s) + rew_k(s) + (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param mdpRewards The rewards\n\t * @param min Min or max for (true=min, false=max)\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t * @return The maximum difference between old/new elements of {@code vect}\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default double mvMultRewGSMinMax(double vect[], MDPRewards<Double> mdpRewards, boolean min, PrimitiveIterator.OfInt states, boolean absolute, int strat[])\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\td = mvMultRewJacMinMaxSingle(s, vect, mdpRewards, min, strat);\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication and sum of rewards followed by min/max,\n\t * for interval iteration.\n\t * i.e. for all s: vect[s] = min/max_k { rew(s) + rew_k(s) + (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * and store new values directly in {@code vect} as computed.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param mdpRewards The rewards\n\t * @param min Min or max for (true=min, false=max)\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * @param ensureMonotonic enforce monotonicity?\n\t * @param fromBelow interval iteration from below? (for ensureMonotonic)\n\t */\n\tpublic default void mvMultRewGSMinMaxIntervalIter(double vect[], MDPRewards<Double> mdpRewards, boolean min, PrimitiveIterator.OfInt states, int strat[], boolean ensureMonotonic, boolean fromBelow)\n\t{\n\t\tdouble d;\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\td = mvMultRewJacMinMaxSingle(s, vect, mdpRewards, min, strat);\n\t\t\tif (ensureMonotonic) {\n\t\t\t\tif (fromBelow) {\n\t\t\t\t\t// from below: do max old and new\n\t\t\t\t\tif (vect[s] > d) {\n\t\t\t\t\t\td = vect[s];\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// from above: do min old and new\n\t\t\t\t\tif (vect[s] < d) {\n\t\t\t\t\t\td = vect[s];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tvect[s] = d;\n\t\t\t} else {\n\t\t\t\tvect[s] = d;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of Jacobi-style matrix-vector multiplication and sum of rewards followed by min/max.\n\t * i.e. return min/max_k { rew(s) + rew_k(s) + (sum_{j!=s} P_k(s,j)*vect[j]) / 1-P_k(s,s) }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param s State (row) index\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param min Min or max for (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default double mvMultRewJacMinMaxSingle(int s, double vect[], MDPRewards<Double> mdpRewards, boolean min, int strat[])\n\t{\n\t\tint stratCh = -1;\n\t\tdouble minmax = 0;\n\t\tboolean first = true;\n\n\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\tdouble d = mvMultRewJacSingle(s, choice, vect, mdpRewards);\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null) {\n\t\t\t\t\tstratCh = choice;\n\t\t\t\t}\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null && !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\n\t/**\n\t * Do a single row of Jacobi-style matrix-vector multiplication and sum of rewards,\n\t * for a specific choice.\n\t * i.e. return rew(s) + rew_i(s) + (sum_{j!=s} P_i(s,j)*vect[j]) / 1-P_i(s,s) }\n\t * @param s State (row) index\n\t * @param i the choice index\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t */\n\tpublic default double mvMultRewJacSingle(int s, int i, double vect[], MDPRewards<Double> mdpRewards)\n\t{\n\t\tclass Jacobi {\n\t\t\tdouble diag = 1.0;\n\t\t\tdouble d = mdpRewards.getStateReward(s) + mdpRewards.getTransitionReward(s, i);\n\t\t\tboolean onlySelfLoops = true;\n\n\t\t\tvoid accept(int s, int t, double prob) {\n\t\t\t\tif (t != s) {\n\t\t\t\t\td += prob * vect[t];\n\t\t\t\t\tonlySelfLoops = false;\n\t\t\t\t} else {\n\t\t\t\t\tdiag -= prob;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tJacobi jac = new Jacobi();\n\t\tforEachDoubleTransition(s, i, jac::accept);\n\n\t\tdouble d = jac.d;\n\t\tdouble diag = jac.diag;\n\n\t\tif (jac.onlySelfLoops) {\n\t\t\tif (d != 0) {\n\t\t\t\t// always choosing the selfloop-action will produce infinite reward\n\t\t\t\td = (d > 0 ? Double.POSITIVE_INFINITY : Double.NEGATIVE_INFINITY);\n\t\t\t} else {\n\t\t\t\t// no reward & only self-loops: d remains 0\n\t\t\t\td = 0;\n\t\t\t}\n\t\t} else {\n\t\t\t// not only self-loops, do Jacobi division\n\t\t\tif (diag > 0)\n\t\t\t\td /= diag;\n\t\t}\n\n\t\treturn d;\n\t}\n\n\t/**\n\t * Determine which choices result in min/max after a single row of matrix-vector multiplication and sum of rewards.\n\t * @param s State (row) index\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param min Min or max (true=min, false=max)\n\t * @param val Min or max value to match\n\t */\n\tpublic default List<Integer> mvMultRewMinMaxSingleChoices(int s, double vect[], MDPRewards<Double> mdpRewards, boolean min, double val)\n\t{\n\t\t// Create data structures to store strategy\n\t\tfinal List<Integer> result = new ArrayList<Integer>();\n\n\t\t// One row of matrix-vector operation\n\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\tdouble d = mvMultRewSingle(s, choice, vect, mdpRewards);\n\t\t\t// Store strategy info if value matches\n\t\t\tif (PrismUtils.doublesAreEqual(val, d)) {\n\t\t\t\tresult.add(choice);\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Multiply the probability matrix induced by the MDP and {@code strat}\n\t * to the right of {@code source}. Only those entries in {@code source}\n\t * and only those columns in the probability matrix are considered, that\n\t * are elements of {@code states}.\n\t * \n\t * The result of this multiplication is added to the contents of {@code dest}.\n\t *   \n\t * @param states States for which to multiply\n\t * @param strat (Memoryless) strategy to use\n\t * @param source Vector to multiply matrix with\n\t * @param dest Vector to write result to.\n\t */\n\tpublic default void mvMultRight(int[] states, int[] strat, double[] source, double[] dest)\n\t{\n\t\tfor (int state : states) {\n\t\t\tforEachDoubleTransition(state, strat[state], (int s, int t, double prob) -> {\n\t\t\t\tdest[t] += prob * source[s];\n\t\t\t});\n\t\t}\n\t}\n\n\t/**\n\t * Generate a string representation for an MDP.\n\t */\n\tdefault String toStringMDP()\n\t{\n\t\tStringBuilder str = new StringBuilder(\"[ \");\n\t\tint numStates = getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tif (s > 0) {\n\t\t\t\tstr.append(\", \");\n\t\t\t}\n\t\t\tstr.append(s).append(\": \").append(\"[\");\n\t\t\tint numChoices = getNumChoices(s);\n\t\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\t\tif (i > 0) {\n\t\t\t\t\tstr.append(\",\");\n\t\t\t\t}\n\t\t\t\tObject action = getAction(s, i);\n\t\t\t\tif (action != null) {\n\t\t\t\t\tstr.append(action).append(\":\");\n\t\t\t\t}\n\t\t\t\tstr.append(\"{\");\n\t\t\t\tIterator<Entry<Integer, Value>> iter = getTransitionsIterator(s, i);\n\t\t\t\tboolean first = true;\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tif (first) {\n\t\t\t\t\t\tfirst = false;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tstr.append(\",\");\n\t\t\t\t\t}\n\t\t\t\t\tEntry<Integer, Value> entry = iter.next();\n\t\t\t\t\tstr.append(entry.getValue()).append(\":\").append(entry.getKey());\n\t\t\t\t}\n\t\t\t\tstr.append(\"}\");\n\t\t\t}\n\t\t\tstr.append(\"]\");\n\t\t}\n\t\tstr.append(\" ]\\n\");\n\t\treturn str.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/MDPExplicit.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Christian von Essen <christian.vonessen@imag.fr> (Verimag, Grenoble)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport strat.MDStrategy;\n\n/**\n * Base class for explicit-state representations of an MDP.\n */\npublic abstract class MDPExplicit<Value> extends ModelExplicit<Value> implements MDP<Value>\n{\n\t// Accessors (for MDP)\n\n\t@Override\n\tpublic Model<Value> constructInducedModel(MDStrategy<Value> strat)\n\t{\n\t\tModelExplicit<Value> dtmcInduced = new DTMCFromMDPAndMDStrategy<Value>(this, strat);\n\t\tdtmcInduced.setEvaluator(getEvaluator());\n\t\treturn dtmcInduced;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/MDPModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Map.Entry;\nimport java.util.PrimitiveIterator;\n\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceType;\nimport common.IntSet;\nimport common.IterableBitSet;\nimport common.IterableStateSet;\nimport common.StopWatch;\nimport explicit.modelviews.EquivalenceRelationInteger;\nimport explicit.modelviews.MDPDroppedAllChoices;\nimport explicit.modelviews.MDPEquiv;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MCRewardsFromMDPRewards;\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.Rewards;\nimport io.ModelExportFormat;\nimport parser.ast.Expression;\nimport parser.type.TypeDouble;\nimport prism.AccuracyFactory;\nimport prism.OptionsIntervalIteration;\nimport prism.PrismComponent;\nimport prism.PrismDevNullLog;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport prism.PrismUtils;\nimport strat.FMDStrategyProduct;\nimport strat.FMDStrategyStep;\nimport strat.MDStrategy;\nimport strat.MDStrategyArray;\nimport strat.Strategy;\n\n/**\n * Explicit-state model checker for Markov decision processes (MDPs).\n */\npublic class MDPModelChecker extends ProbModelChecker\n{\n\t/**\n\t * Create a new MDPModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic MDPModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\t\n\t// Model checking functions\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tprotected StateValues checkProbPathFormulaLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// For min probabilities, need to negate the formula\n\t\t// (add parentheses to allow re-parsing if required)\n\t\tif (minMax.isMin()) {\n\t\t\texpr = Expression.Not(Expression.Parenth(expr.deepCopy()));\n\t\t}\n\n\t\t// Build product of MDP and DA for the LTL formula, and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tAcceptanceType[] allowedAcceptance = {\n\t\t\t\tAcceptanceType.BUCHI,\n\t\t\t\tAcceptanceType.RABIN,\n\t\t\t\tAcceptanceType.GENERALIZED_RABIN,\n\t\t\t\tAcceptanceType.REACH\n\t\t};\n\t\tLTLModelChecker.LTLProduct<MDP<Double>> product = mcLtl.constructDAProductForLTLFormula(this, (MDP<Double>) model, expr, statesOfInterest, allowedAcceptance);\n\t\tdoProductExports(product);\n\t\t\n\t\t// Find accepting states + compute reachability probabilities\n\t\tBitSet acc;\n\t\tif (product.getAcceptance() instanceof AcceptanceReach) {\n\t\t\tmainLog.println(\"\\nSkipping accepting MEC computation since acceptance is defined via goal states...\");\n\t\t\tacc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\t\t} else {\n\t\t\tmainLog.println(\"\\nFinding accepting MECs...\");\n\t\t\tacc = mcLtl.findAcceptingECStates(product.getProductModel(), product.getAcceptance());\n\t\t}\n\t\tmainLog.println(\"\\nComputing reachability probabilities...\");\n\t\tMDPModelChecker mcProduct = new MDPModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachProbs((MDP<Double>) product.getProductModel(), acc, false);\n\t\tStateValues probsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\n\t\t// Subtract from 1 if we're model checking a negated formula for regular Pmin\n\t\tif (minMax.isMin()) {\n\t\t\tprobsProduct.applyFunction(TypeDouble.getInstance(), v -> 1.0 - (double) v);\n\t\t}\n\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\t\tprobsProduct.print(out, false, false, false, false);\n\t\t\t\tout.close();\n\t\t}\n\t\t\n\t\t// If a strategy was generated, lift it to the product and store\n\t\tif (res.strat != null) {\n\t\t\tStrategy<Double> stratProduct = new FMDStrategyProduct<>(product, (MDStrategy<Double>) res.strat);\n\t\t\tresult.setStrategy(stratProduct);\n\t\t}\n\t\t\n\t\t// Mapping probabilities in the original model\n\t\tStateValues probs = product.projectToOriginalModel(probsProduct);\n\t\tprobsProduct.clear();\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute rewards for a co-safe LTL reward operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardCoSafeLTL(Model<?> model, Rewards<?> modelRewards, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of MDP and DFA for the LTL formula, convert rewards and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tLTLModelChecker.LTLProduct<MDP<Double>> product = mcLtl.constructDFAProductForCosafetyReward(this, (MDP<Double>) model, expr, statesOfInterest);\n\t\tMDPRewards<Double> productRewards = ((MDPRewards<Double>) modelRewards).liftFromModel(product);\n\t\tdoProductExports(product);\n\n\t\t// Find accepting states + compute reachability rewards\n\t\tBitSet acc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\n\t\tmainLog.println(\"\\nComputing reachability rewards...\");\n\t\tMDPModelChecker mcProduct = new MDPModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachRewards((MDP<Double>)product.getProductModel(), productRewards, acc, minMax.isMin());\n\t\tStateValues rewardsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\t\trewardsProduct.print(out, false, false, false, false);\n\t\t\t\tout.close();\n\t\t}\n\n\t\t// If a strategy was generated, lift it to the product and store\n\t\tif (res.strat != null) {\n\t\t\tStrategy<Double> stratProduct = new FMDStrategyProduct<>(product, (MDStrategy<Double>) res.strat);\n\t\t\tresult.setStrategy(stratProduct);\n\t\t}\n\t\t\n\t\t// Mapping rewards in the original model\n\t\tStateValues rewards = product.projectToOriginalModel(rewardsProduct);\n\t\trewardsProduct.clear();\n\n\t\treturn rewards;\n\t}\n\t\n\t// Numerical computation functions\n\n\t/**\n\t * Compute next=state probabilities.\n\t * i.e. compute the probability of being in a state in {@code target} in the next step.\n\t * @param mdp The MDP\n\t * @param target Target states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeNextProbs(MDP<Double> mdp, BitSet target, boolean min) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint n;\n\t\tdouble soln[], soln2[];\n\t\tlong timer;\n\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Create/initialise solution vector(s)\n\t\tsoln = Utils.bitsetToDoubleArray(target, n);\n\t\tsoln2 = new double[n];\n\n\t\t// If required, create/initialise strategy storage\n\t\t// Set choices to -1, denoting unknown\n\t\t// (except for target states, which are -2, denoting arbitrary)\n\t\tint strat[] = null;\n\t\tif (genStrat) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tstrat[i] = target.get(i) ? -2 : -1;\n\t\t\t}\n\t\t}\n\n\t\t// Next-step probabilities\n\t\tmdp.mvMultMinMax(soln, min, soln2, null, false, strat);\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.soln = soln2;\n\t\tres.numIters = 1;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tif (genStrat) {\n\t\t\tres.strat = new MDStrategyArray<>(mdp, strat);\n\t\t}\n\t\treturn res;\n\t}\n\n\t/**\n\t * Given a value vector x, compute the probability:\n\t *   v(s) = min/max sched [ Sum_s' P_sched(s,s')*x(s') ]  for s labeled with a,\n\t *   v(s) = 0   for s not labeled with a.\n\t *\n\t * Clears the StateValues object x.\n\t *\n\t * @param tr the transition matrix\n\t * @param a the set of states labeled with a\n\t * @param x the value vector\n\t * @param min compute min instead of max\n\t */\n\tpublic double[] computeRestrictedNext(MDP<Double> mdp, BitSet a, double[] x, boolean min)\n\t{\n\t\tint n;\n\t\tdouble soln[];\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// initialized to 0.0\n\t\tsoln = new double[n];\n\n\t\t// Next-step probabilities multiplication\n\t\t// restricted to a states\n\t\tmdp.mvMultMinMax(x, min, soln, a, false, null);\n\n\t\treturn soln;\n\t}\n\n\t/**\n\t * Compute reachability probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target}.\n\t * @param mdp The MDP\n\t * @param target Target states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeReachProbs(MDP<Double> mdp, BitSet target, boolean min) throws PrismException\n\t{\n\t\treturn computeReachProbs(mdp, null, target, min, null, null);\n\t}\n\n\t/**\n\t * Compute until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * while remaining in those in {@code remain}.\n\t * @param mdp The MDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeUntilProbs(MDP<Double> mdp, BitSet remain, BitSet target, boolean min) throws PrismException\n\t{\n\t\treturn computeReachProbs(mdp, remain, target, min, null, null);\n\t}\n\n\t/**\n\t * Compute reachability/until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * while remaining in those in {@code remain}.\n\t * @param mdp The MDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (may be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values).\n\t * Also, 'known' values cannot be passed for some solution methods, e.g. policy iteration.  \n\t */\n\tpublic ModelCheckerResult computeReachProbs(MDP<Double> mdp, BitSet remain, BitSet target, boolean min, double init[], BitSet known) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet no, yes;\n\t\tint n, numYes, numNo;\n\t\tlong timer, timerProb0, timerProb1;\n\t\tint strat[] = null;\n\t\t// Local copy of setting\n\t\tMDPSolnMethod mdpSolnMethod = this.mdpSolnMethod;\n\n\t\tboolean doPmaxQuotient = this.doPmaxQuotient;\n\n\t\t// Switch to a supported method, if necessary\n\t\tif (mdpSolnMethod == MDPSolnMethod.LINEAR_PROGRAMMING) {\n\t\t\tmdpSolnMethod = MDPSolnMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to MDP solution method \\\"\" + mdpSolnMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\t// Check for some unsupported combinations\n\t\tif (mdpSolnMethod == MDPSolnMethod.VALUE_ITERATION && valIterDir == ValIterDir.ABOVE) {\n\t\t\tif (!(precomp && prob0))\n\t\t\t\tthrow new PrismException(\"Precomputation (Prob0) must be enabled for value iteration from above\");\n\t\t\tif (!min)\n\t\t\t\tthrow new PrismException(\"Value iteration from above only works for minimum probabilities\");\n\t\t}\n\t\tif (doIntervalIteration) {\n\t\t\tif (!min && genStrat) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Currently, explicit engine does not support adversary construction for interval iteration and Pmax\");\n\t\t\t}\n\t\t\tif (mdpSolnMethod != MDPSolnMethod.VALUE_ITERATION && mdpSolnMethod != MDPSolnMethod.GAUSS_SEIDEL) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Currently, explicit engine only supports interval iteration with value iteration or Gauss-Seidel for MDPs\");\n\t\t\t}\n\t\t\tif (init != null)\n\t\t\t\tthrow new PrismNotSupportedException(\"Interval iteration currently not supported with provided initial values\");\n\t\t\tif (!(precomp && prob0 && prob1)) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Precomputations (Prob0 & Prob1) must be enabled for interval iteration\");\n\t\t\t}\n\n\t\t\tif (!min) {\n\t\t\t\tdoPmaxQuotient = true;\n\t\t\t}\n\t\t}\n\t\tif (mdpSolnMethod == MDPSolnMethod.POLICY_ITERATION || mdpSolnMethod == MDPSolnMethod.MODIFIED_POLICY_ITERATION) {\n\t\t\tif (known != null) {\n\t\t\t\tthrow new PrismException(\"Policy iteration methods cannot be passed 'known' values for some states\");\n\t\t\t}\n\t\t}\n\n\t\tif (doPmaxQuotient && min) {\n\t\t\t// for Pmin, don't do quotient\n\t\t\tdoPmaxQuotient = false;\n\t\t}\n\n\t\t// Start probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting probabilistic reachability (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tmdp.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Optimise by enlarging target set (if more info is available)\n\t\tif (init != null && known != null && !known.isEmpty()) {\n\t\t\tBitSet targetNew = (BitSet) target.clone();\n\t\t\tfor (int i : new IterableBitSet(known)) {\n\t\t\t\tif (init[i] == 1.0) {\n\t\t\t\t\ttargetNew.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\ttarget = targetNew;\n\t\t}\n\n\t\t// If required, export info about target states \n\t\tif (getExportTarget()) {\n\t\t\tBitSet bsInit = new BitSet(n);\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tbsInit.set(i, mdp.isInitialState(i));\n\t\t\t}\n\t\t\tList<BitSet> labels = Arrays.asList(bsInit, target);\n\t\t\tList<String> labelNames = Arrays.asList(\"init\", \"target\");\n\t\t\tmainLog.println(\"\\nExporting target states info to file \\\"\" + getExportTargetFilename() + \"\\\"...\");\n\t\t\texportLabels(mdp, labelNames, labels, new File(getExportTargetFilename()), ModelExportFormat.EXPLICIT);\n\t\t}\n\n\t\t// If required, create/initialise strategy storage\n\t\t// Set choices to -1, denoting unknown\n\t\t// (except for target states, which are -2, denoting arbitrary)\n\t\tif (genStrat) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tstrat[i] = target.get(i) ? -2 : -1;\n\t\t\t}\n\t\t}\n\n\t\t// Precomputation\n\t\ttimerProb0 = System.currentTimeMillis();\n\t\tif (precomp && prob0) {\n\t\t\tno = prob0(mdp, remain, target, min, strat);\n\t\t} else {\n\t\t\tno = new BitSet();\n\t\t\tif (remain != null) {\n\t\t\t\tno.or(remain);\n\t\t\t\tno.or(target);\n\t\t\t\tno.flip(0, n);\n\t\t\t}\n\t\t}\n\t\ttimerProb0 = System.currentTimeMillis() - timerProb0;\n\t\ttimerProb1 = System.currentTimeMillis();\n\t\tif (precomp && prob1) {\n\t\t\tyes = prob1(mdp, remain, target, min, strat);\n\t\t} else {\n\t\t\tyes = (BitSet) target.clone();\n\t\t}\n\t\ttimerProb1 = System.currentTimeMillis() - timerProb1;\n\n\t\t// Print results of precomputation\n\t\tnumYes = yes.cardinality();\n\t\tnumNo = no.cardinality();\n\t\tmainLog.println(\"target=\" + target.cardinality() + \", yes=\" + numYes + \", no=\" + numNo + \", maybe=\" + (n - (numYes + numNo)));\n\n\t\t// If still required, store strategy for no/yes (0/1) states.\n\t\t// This is just for the cases max=0 and min=1, where arbitrary choices suffice (denoted by -2)\n\t\tif (genStrat) {\n\t\t\tif (min) {\n\t\t\t\tfor (int i = yes.nextSetBit(0); i >= 0; i = yes.nextSetBit(i + 1)) {\n\t\t\t\t\tif (!target.get(i))\n\t\t\t\t\t\tstrat[i] = -2;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tfor (int i = no.nextSetBit(0); i >= 0; i = no.nextSetBit(i + 1)) {\n\t\t\t\t\tstrat[i] = -2;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Compute probabilities (if needed)\n\t\tif (numYes + numNo < n) {\n\n\t\t\tif (!min && doPmaxQuotient) {\n\t\t\t\tMDPEquiv<Double> maxQuotient = maxQuotient(mdp, yes, no);\n\t\t\t\t// MDPEquiv retains original state space, making the states that are not used\n\t\t\t\t// trap states.\n\t\t\t\t// yesInQuotient is the representative for the yes equivalence class\n\t\t\t\tBitSet yesInQuotient = new BitSet();\n\t\t\t\tyesInQuotient.set(maxQuotient.mapStateToRestrictedModel(yes.nextSetBit(0)));\n\t\t\t\t// noInQuotient is the representative for the no equivalence class as well\n\t\t\t\t// as the non-representative states (the states in any equivalence class\n\t\t\t\t// that are not the representative for the class). As the latter states\n\t\t\t\t// are traps, we can just add them to the no set\n\t\t\t\tBitSet noInQuotient = new BitSet();\n\t\t\t\tnoInQuotient.set(maxQuotient.mapStateToRestrictedModel(no.nextSetBit(0)));\n\t\t\t\tnoInQuotient.or(maxQuotient.getNonRepresentativeStates());\n\t\t\t\tMDPSparse quotientModel = new MDPSparse(maxQuotient);\n\n\t\t\t\tModelCheckerResult res1 = computeReachProbsNumeric(quotientModel,\n\t\t\t\t                                                   mdpSolnMethod,\n\t\t\t\t                                                   noInQuotient,\n\t\t\t\t                                                   yesInQuotient,\n\t\t\t\t                                                   min,\n\t\t\t\t                                                   init,\n\t\t\t\t                                                   known,\n\t\t\t\t                                                   strat);\n\n\t\t\t\tres = new ModelCheckerResult();\n\t\t\t\tres.numIters = res1.numIters;\n\t\t\t\tres.timeTaken = res1.timeTaken;\n\t\t\t\tres.soln = new double[mdp.getNumStates()];\n\t\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\t\tif (yes.get(i)) {\n\t\t\t\t\t\tres.soln[i] = 1.0;\n\t\t\t\t\t} else if (no.get(i)) {\n\t\t\t\t\t\tres.soln[i] = 0.0;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tres.soln[i] = res1.soln[maxQuotient.mapStateToRestrictedModel(i)];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tres.accuracy = res1.accuracy;\n\t\t\t} else {\n\t\t\t\tres = computeReachProbsNumeric(mdp, mdpSolnMethod, no, yes, min, init, known, strat);\n\t\t\t}\n\t\t} else {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(yes, n);\n\t\t\tres.accuracy = AccuracyFactory.doublesFromQualitative();\n\t\t}\n\n\t\t// Finished probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Probabilistic reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Store strategy\n\t\tif (genStrat) {\n\t\t\tres.strat = new MDStrategyArray<Double>(mdp, strat);\n\t\t}\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timeProb0 = timerProb0 / 1000.0;\n\t\tres.timePre = (timerProb0 + timerProb1) / 1000.0;\n\n\t\treturn res;\n\t}\n\n\tprotected ModelCheckerResult computeReachProbsNumeric(MDP<Double> mdp, MDPSolnMethod method, BitSet no, BitSet yes, boolean min, double init[], BitSet known, int strat[]) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\n\t\tIterationMethod iterationMethod = null;\n\t\tswitch (method) {\n\t\tcase VALUE_ITERATION:\n\t\t\titerationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\t\tbreak;\n\t\tcase GAUSS_SEIDEL:\n\t\t\titerationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, false);\n\t\t\tbreak;\n\t\tcase POLICY_ITERATION:\n\t\t\tif (doIntervalIteration) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Interval iteration currently not supported for policy iteration\");\n\t\t\t}\n\t\t\tres = computeReachProbsPolIter(mdp, no, yes, min, strat);\n\t\t\tbreak;\n\t\tcase MODIFIED_POLICY_ITERATION:\n\t\t\tif (doIntervalIteration) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Interval iteration currently not supported for policy iteration\");\n\t\t\t}\n\t\t\tres = computeReachProbsModPolIter(mdp, no, yes, min, strat);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown MDP solution method \" + mdpSolnMethod.fullName());\n\t\t}\n\n\t\tif (res == null) { // not yet computed, use iterationMethod\n\t\t\tif (!doIntervalIteration) {\n\t\t\t\tres = doValueIterationReachProbs(mdp, no, yes, min, init, known, iterationMethod, getDoTopologicalValueIteration(), strat);\n\t\t\t} else {\n\t\t\t\tres = doIntervalIterationReachProbs(mdp, no, yes, min, init, known, iterationMethod, getDoTopologicalValueIteration(), strat);\n\t\t\t}\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Prob0 precomputation algorithm.\n\t * i.e. determine the states of an MDP which, with min/max probability 0,\n\t * reach a state in {@code target}, while remaining in those in {@code remain}.\n\t * {@code min}=true gives Prob0E, {@code min}=false gives Prob0A. \n\t * Optionally, for min only, store optimal (memoryless) strategy info for 0 states. \n\t * @param mdp The MDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic BitSet prob0(NondetModel<?> mdp, BitSet remain, BitSet target, boolean min, int strat[])\n\t{\n\t\tint n, iters;\n\t\tBitSet u, soln, unknown;\n\t\tboolean u_done;\n\t\tlong timer;\n\n\t\t// Start precomputation\n\t\ttimer = System.currentTimeMillis();\n\t\tif (!silentPrecomputations)\n\t\t\tmainLog.println(\"Starting Prob0 (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Special case: no target states\n\t\tif (target.cardinality() == 0) {\n\t\t\tsoln = new BitSet(mdp.getNumStates());\n\t\t\tsoln.set(0, mdp.getNumStates());\n\n\t\t\t// for min, generate strategy, any choice (-2) is fine\n\t\t\tif (min && strat != null) {\n\t\t\t\tArrays.fill(strat, -2);\n\t\t\t}\n\t\t\treturn soln;\n\t\t}\n\n\t\t// Initialise vectors\n\t\tn = mdp.getNumStates();\n\t\tu = new BitSet(n);\n\t\tsoln = new BitSet(n);\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\n\t\t// Fixed point loop\n\t\titers = 0;\n\t\tu_done = false;\n\t\t// Least fixed point - should start from 0 but we optimise by\n\t\t// starting from 'target', thus bypassing first iteration\n\t\tu.or(target);\n\t\tsoln.or(target);\n\t\twhile (!u_done) {\n\t\t\titers++;\n\t\t\t// Single step of Prob0\n\t\t\tmdp.prob0step(unknown, u, min, soln);\n\t\t\t// Check termination\n\t\t\tu_done = soln.equals(u);\n\t\t\t// u = soln\n\t\t\tu.clear();\n\t\t\tu.or(soln);\n\t\t}\n\n\t\t// Negate\n\t\tu.flip(0, n);\n\n\t\t// Finished precomputation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (!silentPrecomputations) {\n\t\t\tmainLog.print(\"Prob0 (\" + (min ? \"min\" : \"max\") + \")\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\t// If required, generate strategy. This is for min probs,\n\t\t// so it can be done *after* the main prob0 algorithm (unlike for prob1).\n\t\t// We simply pick, for all \"no\" states, the first choice for which all transitions stay in \"no\"\n\t\tif (strat != null) {\n\t\t\tfor (int i = u.nextSetBit(0); i >= 0; i = u.nextSetBit(i + 1)) {\n\t\t\t\tint numChoices = mdp.getNumChoices(i);\n\t\t\t\tfor (int k = 0; k < numChoices; k++) {\n\t\t\t\t\tif (mdp.allSuccessorsInSet(i, k, u)) {\n\t\t\t\t\t\tstrat[i] = k;\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn u;\n\t}\n\n\t/**\n\t * Prob1 precomputation algorithm.\n\t * i.e. determine the states of an MDP which, with min/max probability 1,\n\t * reach a state in {@code target}, while remaining in those in {@code remain}.\n\t * {@code min}=true gives Prob1A, {@code min}=false gives Prob1E. \n\t * Optionally, for max only, store optimal (memoryless) strategy info for 1 states. \n\t * @param mdp The MDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic BitSet prob1(NondetModel<?> mdp, BitSet remain, BitSet target, boolean min, int strat[])\n\t{\n\t\tint n, iters;\n\t\tBitSet u, v, soln, unknown;\n\t\tboolean u_done, v_done;\n\t\tlong timer;\n\n\t\t// Start precomputation\n\t\ttimer = System.currentTimeMillis();\n\t\tif (!silentPrecomputations)\n\t\t\tmainLog.println(\"Starting Prob1 (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Special case: no target states\n\t\tif (target.cardinality() == 0) {\n\t\t\treturn new BitSet(mdp.getNumStates());\n\t\t}\n\n\t\t// Initialise vectors\n\t\tn = mdp.getNumStates();\n\t\tu = new BitSet(n);\n\t\tv = new BitSet(n);\n\t\tsoln = new BitSet(n);\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\n\t\t// Nested fixed point loop\n\t\titers = 0;\n\t\tu_done = false;\n\t\t// Greatest fixed point\n\t\tu.set(0, n);\n\t\twhile (!u_done) {\n\t\t\tv_done = false;\n\t\t\t// Least fixed point - should start from 0 but we optimise by\n\t\t\t// starting from 'target', thus bypassing first iteration\n\t\t\tv.clear();\n\t\t\tv.or(target);\n\t\t\tsoln.clear();\n\t\t\tsoln.or(target);\n\t\t\twhile (!v_done) {\n\t\t\t\titers++;\n\t\t\t\t// Single step of Prob1\n\t\t\t\tif (min)\n\t\t\t\t\tmdp.prob1Astep(unknown, u, v, soln);\n\t\t\t\telse\n\t\t\t\t\tmdp.prob1Estep(unknown, u, v, soln, null);\n\t\t\t\t// Check termination (inner)\n\t\t\t\tv_done = soln.equals(v);\n\t\t\t\t// v = soln\n\t\t\t\tv.clear();\n\t\t\t\tv.or(soln);\n\t\t\t}\n\t\t\t// Check termination (outer)\n\t\t\tu_done = v.equals(u);\n\t\t\t// u = v\n\t\t\tu.clear();\n\t\t\tu.or(v);\n\t\t}\n\n\t\t// If we need to generate a strategy, do another iteration of the inner loop for this\n\t\t// We could do this during the main double fixed point above, but we would generate surplus\n\t\t// strategy info for non-1 states during early iterations of the outer loop,\n\t\t// which are not straightforward to remove since this method does not know which states\n\t\t// already have valid strategy info from Prob0.\n\t\t// Notice that we only need to look at states in u (since we already know the answer),\n\t\t// so we restrict 'unknown' further \n\t\tunknown.and(u);\n\t\tif (!min && strat != null) {\n\t\t\tv_done = false;\n\t\t\tv.clear();\n\t\t\tv.or(target);\n\t\t\tsoln.clear();\n\t\t\tsoln.or(target);\n\t\t\twhile (!v_done) {\n\t\t\t\tmdp.prob1Estep(unknown, u, v, soln, strat);\n\t\t\t\tv_done = soln.equals(v);\n\t\t\t\tv.clear();\n\t\t\t\tv.or(soln);\n\t\t\t}\n\t\t\tu_done = v.equals(u);\n\t\t}\n\n\t\t// Finished precomputation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (!silentPrecomputations) {\n\t\t\tmainLog.print(\"Prob1 (\" + (min ? \"min\" : \"max\") + \")\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\treturn u;\n\t}\n\n\t/**\n\t * Compute reachability probabilities using value iteration.\n\t * Optionally, store optimal (memoryless) strategy info. \n\t * @param mdp The MDP\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tprotected ModelCheckerResult computeReachProbsValIter(MDP<Double> mdp, BitSet no, BitSet yes, boolean min, double init[], BitSet known, int strat[])\n\t\t\tthrows PrismException\n\t{\n\t\tIterationMethodPower iterationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\treturn doValueIterationReachProbs(mdp, no, yes, min, init, known, iterationMethod, false, strat);\n\t}\n\n\t/**\n\t * Compute reachability probabilities using value iteration.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param mdp The MDP\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * @param iterationMethod The iteration method\n\t * @param topological Do topological value iteration?\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * Note: if 'known' is specified (i.e. is non-null), 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult doValueIterationReachProbs(MDP<Double> mdp, BitSet no, BitSet yes, boolean min, double init[], BitSet known, IterationMethod iterationMethod, boolean topological, int strat[])\n\t\t\tthrows PrismException\n\t{\n\t\tBitSet unknown;\n\t\tint i, n;\n\t\tdouble initVal;\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString description = (min ? \"min\" : \"max\")\n\t\t\t\t+ (topological ? \", topological\": \"\" )\n\t\t\t\t+ \", with \" + iterationMethod.getDescriptionShort();\n\n\t\tmainLog.println(\"Starting value iteration (\" + description + \")...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings != null && settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit MDP ReachProbs value iteration (\" + description + \")\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Initialise solution vectors. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 1.0/0.0 if in yes/no; (3) passed in initial value; (4) initVal\n\t\t// where initVal is 0.0 or 1.0, depending on whether we converge from below/above. \n\t\tinitVal = (valIterDir == ValIterDir.BELOW) ? 0.0 : 1.0;\n\t\tif (init != null) {\n\t\t\tif (known != null) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tinit[i] = known.get(i) ? init[i] : yes.get(i) ? 1.0 : no.get(i) ? 0.0 : init[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tinit[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : init[i];\n\t\t\t}\n\t\t} else {\n\t\t\tinit = new double[n];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinit[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : initVal;\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(yes);\n\t\tunknown.andNot(no);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tif (iterationsExport != null)\n\t\t\titerationsExport.exportVector(init, 0);\n\n\t\tIterationMethod.IterationValIter iteration = iterationMethod.forMvMultMinMax(mdp, min, strat);\n\t\titeration.init(init);\n\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\tif (topological) {\n\t\t\t// Compute SCCInfo, including trivial SCCs in the subgraph obtained when only considering\n\t\t\t// states in unknown\n\t\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, mdp, true, unknown::get);\n\n\t\t\tIterationMethod.SingletonSCCSolver singletonSCCSolver = (int s, double[] soln) -> {\n\t\t\t\tsoln[s] = mdp.mvMultJacMinMaxSingle(s, soln, min, strat);\n\t\t\t};\n\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doTopologicalValueIteration(this, description, sccs, iteration, singletonSCCSolver, timer, iterationsExport);\n\t\t} else {\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doValueIteration(this, description, iteration, unknownStates, timer, iterationsExport);\n\t\t}\n\t}\n\n\t/**\n\t * Compute reachability probabilities using interval iteration.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param mdp The MDP\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * @param iterationMethod The iteration method\n\t * @param topological Do topological value iteration?\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult doIntervalIterationReachProbs(MDP<Double> mdp, BitSet no, BitSet yes, boolean min, double init[], BitSet known, IterationMethod iterationMethod, boolean topological, int strat[])\n\t\t\tthrows PrismException\n\t{\n\t\tBitSet unknown;\n\t\tint i, n;\n\t\tdouble initBelow[], initAbove[];\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString description = (min ? \"min\" : \"max\")\n\t\t\t\t+ (topological ? \", topological\": \"\" )\n\t\t\t\t+ \", with \" + iterationMethod.getDescriptionShort();\n\n\t\tmainLog.println(\"Starting interval iteration (\" + description + \")...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit MDP ReachProbs interval iteration (\" + description + \")\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tinitBelow = (init == null) ? new double[n] : init;\n\t\tinitAbove = new double[n];\n\n\t\t// Initialise solution vectors. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 1.0/0.0 if in yes/no; (3) initVal\n\t\t// where initVal is 0.0 or 1.0, depending on whether we converge from below/above.\n\t\tif (known != null && init != null) {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tinitBelow[i] = known.get(i) ? init[i] : yes.get(i) ? 1.0 : no.get(i) ? 0.0 : 0.0;\n\t\t\t\tinitAbove[i] = known.get(i) ? init[i] : yes.get(i) ? 1.0 : no.get(i) ? 0.0 : 1.0;\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tinitBelow[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 :  0.0;\n\t\t\t\tinitAbove[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 :  1.0;\n\t\t\t}\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(yes);\n\t\tunknown.andNot(no);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tif (iterationsExport != null) {\n\t\t\titerationsExport.exportVector(initBelow, 0);\n\t\t\titerationsExport.exportVector(initAbove, 1);\n\t\t}\n\n\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\tfinal boolean enforceMonotonicFromBelow = iiOptions.isEnforceMonotonicityFromBelow();\n\t\tfinal boolean enforceMonotonicFromAbove = iiOptions.isEnforceMonotonicityFromAbove();\n\t\tfinal boolean checkMonotonic = iiOptions.isCheckMonotonicity();\n\n\t\tif (!enforceMonotonicFromAbove) {\n\t\t\tgetLog().println(\"Note: Interval iteration is configured to not enforce monotonicity from above.\");\n\t\t}\n\t\tif (!enforceMonotonicFromBelow) {\n\t\t\tgetLog().println(\"Note: Interval iteration is configured to not enforce monotonicity from below.\");\n\t\t}\n\n\t\tIterationMethod.IterationIntervalIter below = iterationMethod.forMvMultMinMaxInterval(mdp, min, strat, true, enforceMonotonicFromBelow, checkMonotonic);\n\t\tIterationMethod.IterationIntervalIter above = iterationMethod.forMvMultMinMaxInterval(mdp, min, strat, false, enforceMonotonicFromAbove, checkMonotonic);\n\t\tbelow.init(initBelow);\n\t\tabove.init(initAbove);\n\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\tif (topological) {\n\t\t\t// Compute SCCInfo, including trivial SCCs in the subgraph obtained when only considering\n\t\t\t// states in unknown\n\t\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, mdp, true, unknown::get);\n\n\t\t\tIterationMethod.SingletonSCCSolver singletonSCCSolver = (int s, double[] soln) -> {\n\t\t\t\tsoln[s] = mdp.mvMultJacMinMaxSingle(s, soln, min, strat);\n\t\t\t};\n\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doTopologicalIntervalIteration(this, description, sccs, below, above, singletonSCCSolver, timer, iterationsExport);\n\t\t} else {\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doIntervalIteration(this, description, below, above, unknownStates, timer, iterationsExport);\n\t\t}\n\t}\n\n\t/**\n\t * Compute reachability probabilities using Gauss-Seidel (including Jacobi-style updates).\n\t * @param mdp The MDP\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tprotected ModelCheckerResult computeReachProbsGaussSeidel(MDP<Double> mdp, BitSet no, BitSet yes, boolean min, double init[], BitSet known, int strat[])\n\t\t\tthrows PrismException\n\t{\n\t\tIterationMethodGS iterationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, false);\n\t\treturn doValueIterationReachProbs(mdp, no, yes, min, init, known, iterationMethod, false, strat);\n\t}\n\n\t/**\n\t * Compute reachability probabilities using policy iteration.\n\t * Optionally, store optimal (memoryless) strategy info. \n\t * @param mdp: The MDP\n\t * @param no: Probability 0 states\n\t * @param yes: Probability 1 states\n\t * @param min: Min or max probabilities (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tprotected ModelCheckerResult computeReachProbsPolIter(MDP<Double> mdp, BitSet no, BitSet yes, boolean min, int strat[]) throws PrismException\n\t{\n\t\tModelCheckerResult res;\n\t\tint i, n, iters, totalIters;\n\t\tdouble soln[], soln2[];\n\t\tboolean done;\n\t\tlong timer;\n\t\tDTMCModelChecker mcDTMC;\n\t\tDTMC<Double> dtmc;\n\n\t\t// Re-use solution to solve each new policy (strategy)?\n\t\tboolean reUseSoln = true;\n\n\t\t// Start policy iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"Starting policy iteration (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Create a DTMC model checker (for solving policies)\n\t\tmcDTMC = new DTMCModelChecker(this);\n\t\tmcDTMC.inheritSettings(this);\n\t\tmcDTMC.setLog(new PrismDevNullLog());\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Create solution vectors\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = soln2[i] = yes.get(i) ? 1.0 : 0.0;\n\n\t\t// If not passed in, create new storage for strategy and initialise\n\t\t// Initial strategy just picks first choice (0) everywhere\n\t\tif (strat == null) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tstrat[i] = 0;\n\t\t}\n\t\t// Otherwise, just initialise for states not in yes/no\n\t\t// (Optimal choices for yes/no should already be known)\n\t\telse {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tif (!(no.get(i) || yes.get(i)))\n\t\t\t\t\tstrat[i] = 0;\n\t\t}\n\n\t\tboolean backwardsGS = (linEqMethod == LinEqMethod.BACKWARDS_GAUSS_SEIDEL);\n\n\t\t// Start iterations\n\t\titers = totalIters = 0;\n\t\tdone = false;\n\t\twhile (!done) {\n\t\t\titers++;\n\t\t\t// Solve induced DTMC for strategy\n\t\t\tdtmc = new DTMCFromMDPMemorylessAdversary<>(mdp, strat);\n\t\t\tres = mcDTMC.computeReachProbsGaussSeidel(dtmc, no, yes, reUseSoln ? soln : null, null, backwardsGS);\n\t\t\tsoln = res.soln;\n\t\t\ttotalIters += res.numIters;\n\t\t\t// Check if optimal, improve non-optimal choices\n\t\t\tmdp.mvMultMinMax(soln, min, soln2, null, false, null);\n\t\t\tdone = true;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t// Don't look at no/yes states - we may not have strategy info for them,\n\t\t\t\t// so they might appear non-optimal\n\t\t\t\tif (no.get(i) || yes.get(i))\n\t\t\t\t\tcontinue;\n\t\t\t\tif (!PrismUtils.doublesAreClose(soln[i], soln2[i], termCritParam, termCrit == TermCrit.ABSOLUTE)) {\n\t\t\t\t\tdone = false;\n\t\t\t\t\tList<Integer> opt = mdp.mvMultMinMaxSingleChoices(i, soln, min, soln2[i]);\n\t\t\t\t\t// Only update strategy if strictly better\n\t\t\t\t\tif (!opt.contains(strat[i]))\n\t\t\t\t\t\tstrat[i] = opt.get(0);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Finished policy iteration\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Policy iteration\");\n\t\tmainLog.println(\" took \" + iters + \" cycles (\" + totalIters + \" iterations in total) and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\t// (Note we don't add the strategy - the one passed in is already there\n\t\t// and might have some existing choices stored for other states).\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.numIters = totalIters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute reachability probabilities using modified policy iteration.\n\t * @param mdp: The MDP\n\t * @param no: Probability 0 states\n\t * @param yes: Probability 1 states\n\t * @param min: Min or max probabilities (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tprotected ModelCheckerResult computeReachProbsModPolIter(MDP<Double> mdp, BitSet no, BitSet yes, boolean min, int strat[]) throws PrismException\n\t{\n\t\tModelCheckerResult res;\n\t\tint i, n, iters, totalIters;\n\t\tdouble soln[], soln2[];\n\t\tboolean done;\n\t\tlong timer;\n\t\tDTMCModelChecker mcDTMC;\n\t\tDTMC<Double> dtmc;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"Starting modified policy iteration (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Create a DTMC model checker (for solving policies)\n\t\tmcDTMC = new DTMCModelChecker(this);\n\t\tmcDTMC.inheritSettings(this);\n\t\tmcDTMC.setLog(new PrismDevNullLog());\n\n\t\t// Limit iters for DTMC solution - this implements \"modified\" policy iteration\n\t\tmcDTMC.setMaxIters(100);\n\t\tmcDTMC.setErrorOnNonConverge(false);\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Create solution vectors\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = soln2[i] = yes.get(i) ? 1.0 : 0.0;\n\n\t\t// If not passed in, create new storage for strategy and initialise\n\t\t// Initial strategy just picks first choice (0) everywhere\n\t\tif (strat == null) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tstrat[i] = 0;\n\t\t}\n\t\t// Otherwise, just initialise for states not in yes/no\n\t\t// (Optimal choices for yes/no should already be known)\n\t\telse {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tif (!(no.get(i) || yes.get(i)))\n\t\t\t\t\tstrat[i] = 0;\n\t\t}\n\n\t\tboolean backwardsGS = (linEqMethod == LinEqMethod.BACKWARDS_GAUSS_SEIDEL);\n\n\t\t// Start iterations\n\t\titers = totalIters = 0;\n\t\tdone = false;\n\t\twhile (!done) {\n\t\t\titers++;\n\t\t\t// Solve induced DTMC for strategy\n\t\t\tdtmc = new DTMCFromMDPMemorylessAdversary<>(mdp, strat);\n\t\t\tres = mcDTMC.computeReachProbsGaussSeidel(dtmc, no, yes, soln, null, backwardsGS);\n\t\t\tsoln = res.soln;\n\t\t\ttotalIters += res.numIters;\n\t\t\t// Check if optimal, improve non-optimal choices\n\t\t\tmdp.mvMultMinMax(soln, min, soln2, null, false, null);\n\t\t\tdone = true;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t// Don't look at no/yes states - we don't store strategy info for them,\n\t\t\t\t// so they might appear non-optimal\n\t\t\t\tif (no.get(i) || yes.get(i))\n\t\t\t\t\tcontinue;\n\t\t\t\tif (!PrismUtils.doublesAreClose(soln[i], soln2[i], termCritParam, termCrit == TermCrit.ABSOLUTE)) {\n\t\t\t\t\tdone = false;\n\t\t\t\t\tList<Integer> opt = mdp.mvMultMinMaxSingleChoices(i, soln, min, soln2[i]);\n\t\t\t\t\tstrat[i] = opt.get(0);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Finished policy iteration\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Modified policy iteration\");\n\t\tmainLog.println(\" took \" + iters + \" cycles (\" + totalIters + \" iterations in total) and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\t// (Note we don't add the strategy - the one passed in is already there\n\t\t// and might have some existing choices stored for other states).\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.numIters = totalIters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Construct strategy information for min/max reachability probabilities.\n\t * (More precisely, list of indices of choices resulting in min/max.)\n\t * (Note: indices are guaranteed to be sorted in ascending order.)\n\t * @param mdp The MDP\n\t * @param state The state to generate strategy info for\n\t * @param target The set of target states to reach\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param lastSoln Vector of values from which to recompute in one iteration \n\t */\n\tpublic List<Integer> probReachStrategy(MDP<Double> mdp, int state, BitSet target, boolean min, double lastSoln[]) throws PrismException\n\t{\n\t\tdouble val = mdp.mvMultMinMaxSingle(state, lastSoln, min, null);\n\t\treturn mdp.mvMultMinMaxSingleChoices(state, lastSoln, min, val);\n\t}\n\n\t/**\n\t * Compute bounded reachability probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target} within k steps.\n\t * @param mdp The MDP\n\t * @param target Target states\n\t * @param k Bound\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(MDP<Double> mdp, BitSet target, int k, boolean min) throws PrismException\n\t{\n\t\treturn computeBoundedReachProbs(mdp, null, target, k, min, null, null);\n\t}\n\n\t/**\n\t * Compute bounded until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * within k steps, and while remaining in states in {@code remain}.\n\t * @param mdp The MDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param k Bound\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeBoundedUntilProbs(MDP<Double> mdp, BitSet remain, BitSet target, int k, boolean min) throws PrismException\n\t{\n\t\treturn computeBoundedReachProbs(mdp, remain, target, k, min, null, null);\n\t}\n\n\t/**\n\t * Compute bounded reachability/until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * within k steps, and while remaining in states in {@code remain}.\n\t * @param mdp The MDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param k Bound\n\t * @param min Min or max probabilities (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (may be overwritten) \n\t * @param results Optional array of size k+1 to store (init state) results for each step (null if unused)\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(MDP<Double> mdp, BitSet remain, BitSet target, int k, boolean min, double init[], double results[])\n\t\t\tthrows PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet unknown;\n\t\tint n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\t\tint strat[] = null;\n\t\tFMDStrategyStep<Double> fmdStrat = null;\n\n\t\t// Start bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting bounded probabilistic reachability (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = (init == null) ? new double[n] : init;\n\n\t\t// If required, create/initialise strategy storage\n\t\t// Set choices to -1, denoting unknown\n\t\t// (except for target states, which are -2, denoting arbitrary)\n\t\tif (genStrat) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tstrat[i] = target.get(i) ? -2 : -1;\n\t\t\t}\n\t\t\tfmdStrat = new FMDStrategyStep<Double>(mdp, k);\n\t\t}\n\t\t\n\t\t// Initialise solution vectors. Use passed in initial vector, if present\n\t\tif (init != null) {\n\t\t\tfor (int i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : init[i];\n\t\t} else {\n\t\t\tfor (int i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : 0.0;\n\t\t}\n\t\t// Store intermediate results if required\n\t\t// (compute min/max value over initial states for first step)\n\t\tif (results != null) {\n\t\t\t// TODO: whether this is min or max should be specified somehow\n\t\t\tresults[0] = Utils.minMaxOverArraySubset(soln2, mdp.getInitialStates(), true);\n\t\t}\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\twhile (iters < k) {\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tmdp.mvMultMinMax(soln, min, soln2, unknown, false, strat);\n\t\t\tif (genStrat) {\n\t\t\t\tfmdStrat.setStepChoices(k - iters, strat);\n\t\t\t}\n\t\t\t// Store intermediate results if required\n\t\t\t// (compute min/max value over initial states for this step)\n\t\t\tif (results != null) {\n\t\t\t\t// TODO: whether this is min or max should be specified somehow\n\t\t\t\tresults[iters] = Utils.minMaxOverArraySubset(soln2, mdp.getInitialStates(), true);\n\t\t\t}\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\t\t// Finished bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Bounded probabilistic reachability (\" + (min ? \"min\" : \"max\") + \")\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.lastSoln = soln2;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\tif (genStrat) {\n\t\t\tres.strat = fmdStrat;\n\t\t}\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected cumulative (step-bounded) rewards.\n\t * i.e. compute the min/max reward accumulated within {@code k} steps.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param min Min or max rewards (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeCumulativeRewards(MDP<Double> mdp, MDPRewards<Double> mdpRewards, int k, boolean min) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tlong timer;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\n\t\t// Start expected cumulative reward\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting expected cumulative reward (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Create/initialise solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = soln2[i] = 0.0;\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\twhile (iters < k) {\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tmdp.mvMultRewMinMax(soln, mdpRewards, min, soln2, null, false, null);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished value iteration\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Expected cumulative reward (\" + (min ? \"min\" : \"max\") + \")\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward, with the method specified in the settings.\n\t * @param mdp the model\n\t * @param mdpRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @param inf the infinite states\n\t * @return upper bound on Rmax=?[ F target ] for all states\n\t */\n\tdouble computeReachRewardsMaxUpperBound(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\tif (unknown.isEmpty()) {\n\t\t\tmainLog.println(\"Skipping upper bound computation, no unknown states...\");\n\t\t\treturn 0;\n\t\t}\n\n\t\t// inf and target states become trap states (with dropped choices)\n\t\tBitSet trapStates = (BitSet) target.clone();\n\t\ttrapStates.or(inf);\n\t\tMDP<Double> cleanedMDP = new MDPDroppedAllChoices<>(mdp, trapStates);\n\n\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\tdouble upperBound = 0.0;\n\t\tString method = null;\n\t\tswitch (iiOptions.getBoundMethod()) {\n\t\tcase VARIANT_1_COARSE:\n\t\t\tupperBound = computeReachRewardsMaxUpperBoundVariant1Coarse(cleanedMDP, mdpRewards, target, unknown, inf);\n\t\t\tmethod = \"variant 1, coarse\";\n\t\t\tbreak;\n\t\tcase VARIANT_1_FINE:\n\t\t\tupperBound = computeReachRewardsMaxUpperBoundVariant1Fine(cleanedMDP, mdpRewards, target, unknown, inf);\n\t\t\tmethod = \"variant 1, fine\";\n\t\t\tbreak;\n\t\tcase DEFAULT:\n\t\tcase VARIANT_2:\n\t\t\tupperBound = computeReachRewardsMaxUpperBoundVariant2(cleanedMDP, mdpRewards, target, unknown, inf);\n\t\t\tmethod = \"variant 2\";\n\t\t\tbreak;\n\t\tcase DSMPI:\n\t\t\tthrow new PrismNotSupportedException(\"Dijkstra Sweep MPI upper bound heuristic can not be used for Rmax\");\n\t\t}\n\n\t\tif (method == null) {\n\t\t\tthrow new PrismException(\"Unknown upper bound heuristic\");\n\t\t}\n\n\t\tmainLog.println(\"Upper bound for max expectation (\" + method + \"): \" + upperBound);\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute upper bound for minimum expected reward, with the method specified in the settings.\n\t * @param mdp the model\n\t * @param mdpRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @param inf the infinite states\n\t * @return upper bound on Rmin=?[ F target ] for all unknown states\n\t */\n\tdouble computeReachRewardsMinUpperBound(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\t// inf and target states become trap states (with dropped choices)\n\t\tBitSet trapStates = (BitSet) target.clone();\n\t\ttrapStates.or(inf);\n\t\tMDP<Double> cleanedMDP = new MDPDroppedAllChoices<>(mdp, trapStates);\n\n\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\tdouble upperBound = 0.0;\n\t\tString method = null;\n\t\tswitch (iiOptions.getBoundMethod()) {\n\t\tcase DEFAULT:\n\t\tcase DSMPI:\n\t\t\tupperBound = DijkstraSweepMPI.computeUpperBound(this, mdp, mdpRewards, target, unknown);\n\t\t\tmethod = \"Dijkstra Sweep MPI\";\n\t\t\tbreak;\n\t\tcase VARIANT_1_COARSE:\n\t\t\tupperBound = computeReachRewardsMaxUpperBoundVariant1Coarse(cleanedMDP, mdpRewards, target, unknown, inf);\n\t\t\tmethod = \"using Rmax upper bound via variant 1, coarse\";\n\t\t\tbreak;\n\t\tcase VARIANT_1_FINE:\n\t\t\tupperBound = computeReachRewardsMaxUpperBoundVariant1Fine(cleanedMDP, mdpRewards, target, unknown, inf);\n\t\t\tmethod = \"using Rmax upper bound via variant 1, fine\";\n\t\t\tbreak;\n\t\tcase VARIANT_2:\n\t\t\tupperBound = computeReachRewardsMaxUpperBoundVariant2(cleanedMDP, mdpRewards, target, unknown, inf);\n\t\t\tmethod = \"using Rmax upper bound via variant 2\";\n\t\t\tbreak;\n\t\t}\n\n\t\tif (method == null) {\n\t\t\tthrow new PrismException(\"Unknown upper bound heuristic\");\n\t\t}\n\n\t\tmainLog.println(\"Upper bound for min expectation (\" + method + \"): \" + upperBound);\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Return true if the MDP is contracting for all states in the 'unknown'\n\t * set, i.e., if Pmin=1( unknown U target) holds.\n\t */\n\tprivate boolean isContracting(MDP<?> mdp, BitSet unknown, BitSet target)\n\t{\n\t\t// compute Pmin=1( unknown U target )\n\t\tBitSet pmin1 = prob1(mdp, unknown, target, true, null);\n\t\tBitSet tmp = (BitSet) unknown.clone();\n\t\ttmp.andNot(pmin1);\n\t\tif (!tmp.isEmpty()) {\n\t\t\t// unknown is not contained in pmin1, not contracting\n\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 1, coarse),\n\t * i.e., does not compute separate q_t / p_t per SCC.\n\t * Uses Rs = S, i.e., does not take reachability into account.\n\t * @param mdp the model\n\t * @param mdpRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @return upper bound on Rmax=?[ F target ] for all states\n\t */\n\tdouble computeReachRewardsMaxUpperBoundVariant1Coarse(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\tdouble[] boundsOnExpectedVisits = new double[mdp.getNumStates()];\n\t\tdouble[] maxRews = new double[mdp.getNumStates()];\n\t\tint[] Ct = new int[mdp.getNumStates()];\n\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"computing an upper bound for maximal expected reward\");\n\n\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, mdp, true, null);\n\t\tBitSet trivial = new BitSet();\n\n\t\tdouble q = 0;\n\t\tfor (int scc = 0, numSCCs = sccs.getNumSCCs(); scc < numSCCs; scc++) {\n\t\t\tIntSet statesForSCC = sccs.getStatesForSCC(scc);\n\n\t\t\tint cardinality = Math.toIntExact(statesForSCC.cardinality());\n\n\t\t\tPrimitiveIterator.OfInt itSCC = statesForSCC.iterator();\n\t\t\twhile (itSCC.hasNext()) {\n\t\t\t\tint s = itSCC.nextInt();\n\t\t\t\tCt[s] = cardinality;\n\n\t\t\t\tboolean hasSelfloop = false;\n\t\t\t\tfor (int ch = 0; ch < mdp.getNumChoices(s); ch++) {\n\t\t\t\t\tdouble probRemain = 0;\n\t\t\t\t\tboolean allRemain = true;  // all successors remain in the SCC?\n\t\t\t\t\tfor (Iterator<Entry<Integer, Double>> it = mdp.getTransitionsIterator(s, ch); it.hasNext(); ) {\n\t\t\t\t\t\tEntry<Integer, Double> t = it.next();\n\t\t\t\t\t\tif (statesForSCC.get(t.getKey())) {\n\t\t\t\t\t\t\tprobRemain += t.getValue();\n\t\t\t\t\t\t\thasSelfloop = true;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tallRemain = false;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tif (!allRemain) { // action in the set X\n\t\t\t\t\t\tq = Math.max(q, probRemain);\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (cardinality == 1 && !hasSelfloop) {\n\t\t\t\t\ttrivial.set(s);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tdouble p = 1;\n\t\tfor (int s = 0; s < mdp.getNumStates(); s++) {\n\t\t\tdouble maxRew = 0;\n\t\t\tfor (int ch = 0; ch < mdp.getNumChoices(s); ch++) {\n\t\t\t\tfor (Iterator<Entry<Integer, Double>> it = mdp.getTransitionsIterator(s, ch); it.hasNext(); ) {\n\t\t\t\t\tEntry<Integer, Double> t = it.next();\n\t\t\t\t\tp = Math.min(p, t.getValue());\n\n\t\t\t\t\tdouble rew = mdpRewards.getStateReward(s) + mdpRewards.getTransitionReward(s, ch);\n\t\t\t\t\tmaxRew = Math.max(maxRew, rew);\n\t\t\t\t}\n\t\t\t}\n\t\t\tmaxRews[s] = maxRew;\n\t\t}\n\n\t\tdouble upperBound = 0;\n\t\tfor (int s = 0; s < mdp.getNumStates(); s++) {\n\t\t\tif (target.get(s) || inf.get(s)) {\n\t\t\t\t// inf or target states: not relevant, set visits to 0, ignore in summation\n\t\t\t\tboundsOnExpectedVisits[s] = 0.0;\n\t\t\t} else if (unknown.get(s)) {\n\t\t\t\tif (trivial.get(s)) {\n\t\t\t\t\t// s is a trivial SCC: seen at most once\n\t\t\t\t\tboundsOnExpectedVisits[s] = 1.0;\n\t\t\t\t} else {\n\t\t\t\t\tboundsOnExpectedVisits[s] = 1 / (Math.pow(p, Ct[s]-1) * (1.0-q));\n\t\t\t\t}\n\t\t\t\tupperBound += boundsOnExpectedVisits[s] * maxRews[s];\n\t\t\t}\n\t\t}\n\n\t\tif (OptionsIntervalIteration.from(this).isBoundComputationVerbose()) {\n\t\t\tmainLog.println(\"Upper bound for max expectation computation (variant 1, coarse):\");\n\t\t\tmainLog.println(\"p = \" + p);\n\t\t\tmainLog.println(\"q = \" + q);\n\t\t\tmainLog.println(\"|Ct| = \" + Arrays.toString(Ct));\n\t\t\tmainLog.println(\"ζ* = \" + Arrays.toString(boundsOnExpectedVisits));\n\t\t\tmainLog.println(\"maxRews = \" + Arrays.toString(maxRews));\n\t\t}\n\n\t\ttimer.stop();\n\t\t// mainLog.println(\"Upper bound for max expectation (variant 1, coarse): \" + upperBound);\n\n\t\tif (!Double.isFinite(upperBound)) {\n\t\t\tthrow new PrismException(\"Problem computing an upper bound for the expectation, did not get finite result\");\n\t\t}\n\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 1, fine).\n\t * i.e., does compute separate q_t / p_t per SCC.\n\t * Uses Rs = S, i.e., does not take reachability into account.\n\t * @param mdp the model\n\t * @param mdpRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @return upper bound on Rmax=?[ F target ] for all states\n\t */\n\tdouble computeReachRewardsMaxUpperBoundVariant1Fine(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\tdouble[] boundsOnExpectedVisits = new double[mdp.getNumStates()];\n\t\tdouble[] qt = new double[mdp.getNumStates()];\n\t\tdouble[] pt = new double[mdp.getNumStates()];\n\t\tdouble[] maxRews = new double[mdp.getNumStates()];\n\t\tint[] Ct = new int[mdp.getNumStates()];\n\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"computing an upper bound for maximal expected reward\");\n\n\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, mdp, true, null);\n\t\tBitSet trivial = new BitSet();\n\n\t\tfor (int scc = 0, numSCCs = sccs.getNumSCCs(); scc < numSCCs; scc++) {\n\t\t\tIntSet statesForSCC = sccs.getStatesForSCC(scc);\n\n\t\t\tdouble q = 0;\n\t\t\tdouble p = 1;\n\n\t\t\tint cardinality = Math.toIntExact(statesForSCC.cardinality());\n\n\t\t\tPrimitiveIterator.OfInt itSCC = statesForSCC.iterator();\n\t\t\twhile (itSCC.hasNext()) {\n\t\t\t\tint s = itSCC.nextInt();\n\n\t\t\t\tCt[s] = cardinality;\n\t\t\t\tboolean hasSelfloop = false;\n\n\t\t\t\tfor (int ch = 0; ch < mdp.getNumChoices(s); ch++) {\n\n\t\t\t\t\tdouble probRemain = 0;\n\t\t\t\t\tboolean allRemain = true;  // all successors remain in the SCC?\n\t\t\t\t\tfor (Iterator<Entry<Integer, Double>> it = mdp.getTransitionsIterator(s, ch); it.hasNext(); ) {\n\t\t\t\t\t\tEntry<Integer, Double> t = it.next();\n\t\t\t\t\t\tif (statesForSCC.get(t.getKey())) {\n\t\t\t\t\t\t\tprobRemain += t.getValue();\n\t\t\t\t\t\t\tp = Math.min(p, t.getValue());\n\t\t\t\t\t\t\thasSelfloop = true;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tallRemain = false;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tif (!allRemain) { // action in the set Xt\n\t\t\t\t\t\tq = Math.max(q, probRemain);\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (cardinality == 1 && !hasSelfloop) {\n\t\t\t\t\ttrivial.set(s);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tfor (int s : statesForSCC) {\n\t\t\t\tqt[s] = q;\n\t\t\t\tpt[s] = p;\n\t\t\t}\n\t\t}\n\n\t\tfor (int s = 0; s < mdp.getNumStates(); s++) {\n\t\t\tdouble maxRew = 0;\n\t\t\tfor (int ch = 0; ch < mdp.getNumChoices(s); ch++) {\n\t\t\t\tdouble rew = mdpRewards.getStateReward(s) + mdpRewards.getTransitionReward(s, ch);\n\t\t\t\tmaxRew = Math.max(maxRew, rew);\n\t\t\t}\n\t\t\tmaxRews[s] = maxRew;\n\t\t}\n\n\t\tdouble upperBound = 0;\n\t\tfor (int s = 0; s < mdp.getNumStates(); s++) {\n\t\t\tif (target.get(s) || inf.get(s)) {\n\t\t\t\t// inf or target states: not relevant, set visits to 0, ignore in summation\n\t\t\t\tboundsOnExpectedVisits[s] = 0.0;\n\t\t\t} else if (unknown.get(s)) {\n\t\t\t\tif (trivial.get(s)) {\n\t\t\t\t\t// s is a trivial SCC: seen at most once\n\t\t\t\t\tboundsOnExpectedVisits[s] = 1.0;\n\t\t\t\t} else {\n\t\t\t\t\tboundsOnExpectedVisits[s] = 1 / (Math.pow(pt[s], Ct[s]-1) * (1.0-qt[s]));\n\t\t\t\t}\n\t\t\t\tupperBound += boundsOnExpectedVisits[s] * maxRews[s];\n\t\t\t}\n\t\t}\n\n\t\ttimer.stop();\n\n\t\tif (OptionsIntervalIteration.from(this).isBoundComputationVerbose()) {\n\t\t\tmainLog.println(\"Upper bound for max expectation computation (variant 1, fine):\");\n\t\t\tmainLog.println(\"pt = \" + Arrays.toString(pt));\n\t\t\tmainLog.println(\"qt = \" + Arrays.toString(qt));\n\t\t\tmainLog.println(\"|Ct| = \" + Arrays.toString(Ct));\n\t\t\tmainLog.println(\"ζ* = \" + Arrays.toString(boundsOnExpectedVisits));\n\t\t\tmainLog.println(\"maxRews = \" + Arrays.toString(maxRews));\n\t\t}\n\n\t\t// mainLog.println(\"Upper bound for max expectation (variant 1, fine): \" + upperBound);\n\n\t\tif (!Double.isFinite(upperBound)) {\n\t\t\tthrow new PrismException(\"Problem computing an upper bound for the expectation, did not get finite result\");\n\t\t}\n\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 2).\n\t * Uses Rs = S, i.e., does not take reachability into account.\n\t * @param dtmc the model\n\t * @param mcRewards the rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @param inf the infinity states\n\t * @return upper bound on R=?[ F target ] for all states\n\t */\n\tdouble computeReachRewardsMaxUpperBoundVariant2(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, BitSet unknown, BitSet inf) throws PrismException\n\t{\n\t\tdouble[] dt = new double[mdp.getNumStates()];\n\t\tdouble[] boundsOnExpectedVisits = new double[mdp.getNumStates()];\n\t\tdouble[] maxRews = new double[mdp.getNumStates()];\n\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"computing an upper bound for expected reward\");\n\n\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, mdp, true, unknown::get);\n\n\t\tBitSet T = (BitSet) target.clone();\n\n\t\t@SuppressWarnings(\"unused\")\n\t\tint i = 0;\n\t\twhile (true) {\n\t\t\tBitSet Si = new BitSet();\n\t\t\ti++;\n\n\t\t\t// TODO: might be inefficient, worst-case quadratic runtime...\n\t\t\tfor (PrimitiveIterator.OfInt it = IterableBitSet.getClearBits(T, mdp.getNumStates() -1 ).iterator(); it.hasNext(); ) {\n\t\t\t\tint s = it.nextInt();\n\t\t\t\t// mainLog.println(\"Check \" + s + \" against \" + T);\n\t\t\t\tboolean allActionsReachT = true;\n\t\t\t\tfor (int choice = 0, choices = mdp.getNumChoices(s); choice < choices; choice++) {\n\t\t\t\t\tif (!mdp.someSuccessorsInSet(s, choice, T)) {\n\t\t\t\t\t\tallActionsReachT = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allActionsReachT) {\n\t\t\t\t\tSi.set(s);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (Si.isEmpty()) {\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t// mainLog.println(\"S\" + i + \" = \" + Si);\n\t\t\t// mainLog.println(\"T = \" + T);\n\n\t\t\tfor (PrimitiveIterator.OfInt it = IterableBitSet.getSetBits(Si).iterator(); it.hasNext(); ) {\n\t\t\t\tfinal int t = it.nextInt();\n\t\t\t\tfinal int sccIndexForT = sccs.getSCCIndex(t);\n\n\t\t\t\tdouble min = Double.POSITIVE_INFINITY;\n\t\t\t\tfor (int choice = 0, choices = mdp.getNumChoices(t); choice < choices; choice++) {\n\t\t\t\t\t// mainLog.println(\"State \" + t + \", choice = \" + choice);\n\t\t\t\t\tdouble d = mdp.sumOverDoubleTransitions(t, choice, (int __, int u, double prob) -> {\n\t\t\t\t\t\t// mainLog.println(\"t = \" + t + \", u = \" + u + \", prob = \" + prob);\n\t\t\t\t\t\tif (!T.get(u))\n\t\t\t\t\t\t\treturn 0.0;\n\n\t\t\t\t\t\tboolean inSameSCC = (sccs.getSCCIndex(u) == sccIndexForT);\n\t\t\t\t\t\tdouble d_u_t = inSameSCC ? dt[u] : 1.0;\n\t\t\t\t\t\t// mainLog.println(\"d_u_t = \" + d_u_t);\n\t\t\t\t\t\treturn d_u_t * prob;\n\t\t\t\t\t});\n\t\t\t\t\tif (d < min) {\n\t\t\t\t\t\tmin = d;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tdt[t] = min;\n\t\t\t\t// mainLog.println(\"d[\"+t+\"] = \" + dt[t]);\n\t\t\t}\n\n\t\t\tT.or(Si);\n\t\t}\n\n\t\tfor (int s = 0; s < mdp.getNumStates(); s++) {\n\t\t\tdouble maxRew = 0;\n\t\t\tfor (int ch = 0; ch < mdp.getNumChoices(s); ch++) {\n\t\t\t\tdouble rew = mdpRewards.getStateReward(s) + mdpRewards.getTransitionReward(s, ch);\n\t\t\t\tmaxRew = Math.max(maxRew, rew);\n\t\t\t}\n\t\t\tmaxRews[s] = maxRew;\n\t\t}\n\n\t\tdouble upperBound = 0;\n\t\tfor (PrimitiveIterator.OfInt it = IterableBitSet.getSetBits(unknown).iterator(); it.hasNext();) {\n\t\t\tint s = it.nextInt();\n\t\t\tboundsOnExpectedVisits[s] = 1 / dt[s];\n\t\t\tupperBound += boundsOnExpectedVisits[s] * maxRews[s];\n\t\t}\n\n\t\ttimer.stop();\n\n\t\tif (OptionsIntervalIteration.from(this).isBoundComputationVerbose()) {\n\t\t\tmainLog.println(\"Upper bound for max expectation computation (variant 2):\");\n\t\t\tmainLog.println(\"d_t = \" + Arrays.toString(dt));\n\t\t\tmainLog.println(\"ζ* = \" + Arrays.toString(boundsOnExpectedVisits));\n\t\t}\n\n\t\t// mainLog.println(\"Upper bound for expectation (variant 2): \" + upperBound);\n\n\t\tif (!Double.isFinite(upperBound)) {\n\t\t\tthrow new PrismException(\"Problem computing an upper bound for the expectation, did not get finite result\");\n\t\t}\n\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute expected instantaneous reward,\n\t * i.e. compute the min/max expected reward of the states after {@code k} steps.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param k the number of steps\n\t * @param min Min or max rewards (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeInstantaneousRewards(MDP<Double> mdp, MDPRewards<Double> mdpRewards, final int k, boolean min)\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Start backwards transient computation\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting backwards instantaneous rewards computation...\");\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = mdpRewards.getStateReward(i);\n\n\t\t// Start iterations\n\t\tfor (iters = 0; iters < k; iters++) {\n\t\t\t// Matrix-vector multiply\n\t\t\tmdp.mvMultMinMax(soln, min, soln2, null, false, null);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished backwards transient computation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Backwards transient instantaneous rewards computation\");\n\t\tmainLog.println(\" took \" + iters + \" iters and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.lastSoln = soln2;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute total expected rewards.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param min Min or max rewards (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeTotalRewards(MDP<Double> mdp, MDPRewards<Double> mdpRewards, boolean min) throws PrismException\n\t{\n\t\tif (min) {\n\t\t\tthrow new PrismNotSupportedException(\"Minimum total expected reward not supported in explicit engine\");\n\t\t} else {\n\t\t\t// max. We don't know if there are positive ECs, so we can't skip precomputation\n\t\t\treturn computeTotalRewardsMax(mdp, mdpRewards, false);\n\t\t}\n\t}\n\n\t/**\n\t * Compute maximal total expected rewards.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param noPositiveECs if true, there are no positive ECs, i.e., all states have finite values (skip precomputation)\n\t */\n\tpublic ModelCheckerResult computeTotalRewardsMax(MDP<Double> mdp, MDPRewards<Double> mdpRewards, boolean noPositiveECs) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint n;\n\t\tlong timer;\n\t\tBitSet inf;\n\t\tint strat[] = null;\n\n\t\t// Local copy of setting\n\t\tMDPSolnMethod mdpSolnMethod = this.mdpSolnMethod;\n\n\t\t// Switch to a supported method, if necessary\n\t\tif (!(mdpSolnMethod == MDPSolnMethod.VALUE_ITERATION || mdpSolnMethod == MDPSolnMethod.GAUSS_SEIDEL || mdpSolnMethod == MDPSolnMethod.POLICY_ITERATION)) {\n\t\t\tmdpSolnMethod = MDPSolnMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to MDP solution method \\\"\" + mdpSolnMethod.fullName() + \"\\\"\");\n\t\t}\n\t\tif (getDoIntervalIteration()) {\n\t\t\tthrow new PrismNotSupportedException(\"Interval iteration for total rewards is currently not supported\");\n\t\t}\n\n\t\t// Start expected total reward\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting total expected reward (max)...\");\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// If required, create/initialise strategy storage\n\t\t// Set choices to -1, denoting unknown\n\t\tif (genStrat) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tstrat[i] = -1;\n\t\t\t}\n\t\t}\n\n\t\t// Precomputation (not optional)\n\t\tlong timerPre;\n\t\tif (noPositiveECs) {\n\t\t\t// no inf states\n\t\t\tinf = new BitSet();\n\t\t\ttimerPre = 0;\n\t\t} else {\n\t\t\tmainLog.println(\"Precomputation: Find positive end components...\");\n\n\t\t\ttimerPre = System.currentTimeMillis();\n\n\t\t\tECComputer ecs = ECComputer.createECComputer(this, mdp);\n\t\t\tecs.computeMECStates();\n\t\t\tBitSet positiveECs = new BitSet();\n\t\t\tfor (BitSet ec : ecs.getMECStates()) {\n\t\t\t\t// check if this MEC is positive\n\t\t\t\tboolean positiveEC = false;\n\t\t\t\tfor (int state : new IterableStateSet(ec, n)) {\n\t\t\t\t\tif (mdpRewards.getStateReward(state) > 0) {\n\t\t\t\t\t\t// state with positive reward in this MEC\n\t\t\t\t\t\tpositiveEC = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t\tfor (int choice = 0, numChoices = mdp.getNumChoices(state); choice < numChoices; choice++) {\n\t\t\t\t\t\tif (mdpRewards.getTransitionReward(state, choice) > 0 &&\n\t\t\t\t\t\t\t\tmdp.allSuccessorsInSet(state, choice, ec)) {\n\t\t\t\t\t\t\t// choice from this state with positive reward back into this MEC\n\t\t\t\t\t\t\tpositiveEC = true;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (positiveEC) {\n\t\t\t\t\tpositiveECs.or(ec);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// inf = Pmax[ <> positiveECs ] > 0\n\t\t\t//     = ! (Pmax[ <> positiveECs ] = 0)\n\t\t\tinf = prob0(mdp, null, positiveECs, false, strat);  // Pmax[ <> positiveECs ] = 0\n\t\t\tinf.flip(0,n);  // !(Pmax[ <> positive ECs ] = 0) = Pmax[ <> positiveECs ] > 0\n\n\t\t\ttimerPre = System.currentTimeMillis() - timerPre;\n\t\t\tmainLog.println(\"Precomputation took \" + timerPre / 1000.0 + \" seconds, \" + inf.cardinality() + \" infinite states, \" + (n - inf.cardinality()) + \" states remaining.\");\n\t\t}\n\n\t\t// TODO: generate strategy for \"inf\" state (possibility to reach +ve EC)\n\n\t\t// Compute rewards\n\t\t// do standard max reward calculation, but with empty target set\n\t\tswitch (mdpSolnMethod) {\n\t\tcase VALUE_ITERATION:\n\t\t\tres = computeReachRewardsValIter(mdp, mdpRewards, new BitSet(), inf, false, null, null, strat);\n\t\t\tbreak;\n\t\tcase GAUSS_SEIDEL:\n\t\t\tres = computeReachRewardsGaussSeidel(mdp, mdpRewards, new BitSet(), inf, false, null, null, strat);\n\t\t\tbreak;\n\t\tcase POLICY_ITERATION:\n\t\t\tres = computeReachRewardsPolIter(mdp, mdpRewards, new BitSet(), inf, false, strat);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown MDP solution method \" + mdpSolnMethod.fullName());\n\t\t}\n\n\t\t// Store strategy\n\t\tif (genStrat) {\n\t\t\tres.strat = new MDStrategyArray<Double>(mdp, strat);\n\t\t}\n\n\t\t// Finished expected total reward\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Expected total reward took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = timerPre / 1000.0;\n\n\t\t// Return results\n\t\treturn res;\n\t}\n\n\n\t/**\n\t * Compute expected reachability rewards.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param min Min or max rewards (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeReachRewards(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, boolean min) throws PrismException\n\t{\n\t\treturn computeReachRewards(mdp, mdpRewards, target, min, null, null);\n\t}\n\n\t/**\n\t * Compute expected reachability rewards.\n\t * i.e. compute the min/max reward accumulated to reach a state in {@code target}.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (may be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values).  \n\t * Also, 'known' values cannot be passed for some solution methods, e.g. policy iteration.  \n\t */\n\tpublic ModelCheckerResult computeReachRewards(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, boolean min, double init[], BitSet known)\n\t\t\tthrows PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet inf;\n\t\tint n, numTarget, numInf;\n\t\tlong timer, timerProb1;\n\t\tint strat[] = null;\n\t\t// Local copy of setting\n\t\tMDPSolnMethod mdpSolnMethod = this.mdpSolnMethod;\n\n\t\t// Switch to a supported method, if necessary\n\t\tif (!(mdpSolnMethod == MDPSolnMethod.VALUE_ITERATION || mdpSolnMethod == MDPSolnMethod.GAUSS_SEIDEL || mdpSolnMethod == MDPSolnMethod.POLICY_ITERATION)) {\n\t\t\tmdpSolnMethod = MDPSolnMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to MDP solution method \\\"\" + mdpSolnMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\t// Check for some unsupported combinations\n\t\tif (mdpSolnMethod == MDPSolnMethod.POLICY_ITERATION) {\n\t\t\tif (known != null) {\n\t\t\t\tthrow new PrismException(\"Policy iteration methods cannot be passed 'known' values for some states\");\n\t\t\t}\n\t\t}\n\t\tif (doIntervalIteration) {\n\t\t\tif (mdpSolnMethod != MDPSolnMethod.VALUE_ITERATION && mdpSolnMethod != MDPSolnMethod.GAUSS_SEIDEL) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Currently, explicit engine only supports interval iteration with value iteration or Gauss-Seidel for MDPs\");\n\t\t\t}\n\t\t}\n\n\t\t// Start expected reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting expected reachability (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tmdp.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\t\t// Optimise by enlarging target set (if more info is available)\n\t\tif (init != null && known != null && !known.isEmpty()) {\n\t\t\tBitSet targetNew = (BitSet) target.clone();\n\t\t\tfor (int i : new IterableBitSet(known)) {\n\t\t\t\tif (init[i] == 1.0) {\n\t\t\t\t\ttargetNew.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\ttarget = targetNew;\n\t\t}\n\n\t\t// If required, export info about target states \n\t\tif (getExportTarget()) {\n\t\t\tBitSet bsInit = new BitSet(n);\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tbsInit.set(i, mdp.isInitialState(i));\n\t\t\t}\n\t\t\tList<BitSet> labels = Arrays.asList(bsInit, target);\n\t\t\tList<String> labelNames = Arrays.asList(\"init\", \"target\");\n\t\t\tmainLog.println(\"\\nExporting target states info to file \\\"\" + getExportTargetFilename() + \"\\\"...\");\n\t\t\texportLabels(mdp, labelNames, labels, new File(getExportTargetFilename()), ModelExportFormat.EXPLICIT);\n\t\t}\n\n\t\t// If required, create/initialise strategy storage\n\t\t// Set choices to -1, denoting unknown\n\t\t// (except for target states, which are -2, denoting arbitrary)\n\t\tif (genStrat || mdpSolnMethod == MDPSolnMethod.POLICY_ITERATION) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tstrat[i] = target.get(i) ? -2 : -1;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Precomputation (not optional)\n\t\ttimerProb1 = System.currentTimeMillis();\n\t\tinf = prob1(mdp, null, target, !min, strat);\n\t\tinf.flip(0, n);\n\t\ttimerProb1 = System.currentTimeMillis() - timerProb1;\n\t\t\n\t\t// Print results of precomputation\n\t\tnumTarget = target.cardinality();\n\t\tnumInf = inf.cardinality();\n\t\tmainLog.println(\"target=\" + numTarget + \", inf=\" + numInf + \", rest=\" + (n - (numTarget + numInf)));\n\n\t\t// If required, generate strategy for \"inf\" states.\n\t\tif (genStrat || mdpSolnMethod == MDPSolnMethod.POLICY_ITERATION) {\n\t\t\tif (min) {\n\t\t\t\t// If min reward is infinite, all choices give infinity\n\t\t\t\t// So the choice can be arbitrary, denoted by -2; \n\t\t\t\tfor (int i = inf.nextSetBit(0); i >= 0; i = inf.nextSetBit(i + 1)) {\n\t\t\t\t\tstrat[i] = -2;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\t// If max reward is infinite, there is at least one choice giving infinity.\n\t\t\t\t// So we pick, for all \"inf\" states, the first choice for which some transitions stays in \"inf\".\n\t\t\t\tfor (int i = inf.nextSetBit(0); i >= 0; i = inf.nextSetBit(i + 1)) {\n\t\t\t\t\tint numChoices = mdp.getNumChoices(i);\n\t\t\t\t\tfor (int k = 0; k < numChoices; k++) {\n\t\t\t\t\t\tif (mdp.someSuccessorsInSet(i, k, inf)) {\n\t\t\t\t\t\t\tstrat[i] = k;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Compute rewards (if needed)\n\t\tif (numTarget + numInf < n) {\n\t\t\t\n\t\t\tZeroRewardECQuotient<Double> quotient = null;\n\t\t\tboolean doZeroMECCheckForMin = true;\n\t\t\tif (min & doZeroMECCheckForMin) {\n\t\t\t\tStopWatch zeroMECTimer = new StopWatch(mainLog);\n\t\t\t\tzeroMECTimer.start(\"checking for zero-reward ECs\");\n\t\t\t\tmainLog.println(\"For Rmin, checking for zero-reward ECs...\");\n\t\t\t\tBitSet unknown = (BitSet) inf.clone();\n\t\t\t\tunknown.flip(0, mdp.getNumStates());\n\t\t\t\tunknown.andNot(target);\n\t\t\t\tquotient = ZeroRewardECQuotient.getQuotient(this, mdp, unknown, mdpRewards);\n\t\n\t\t\t\tif (quotient == null) {\n\t\t\t\t\tzeroMECTimer.stop(\"no zero-reward ECs found, proceeding normally\");\n\t\t\t\t} else {\n\t\t\t\t\tzeroMECTimer.stop(\"built quotient MDP with \" + quotient.getNumberOfZeroRewardMECs() + \" zero-reward MECs\");\n\t\t\t\t\tif (strat != null) {\n\t\t\t\t\t\tthrow new PrismException(\"Constructing a strategy for Rmin in the presence of zero-reward ECs is currently not supported\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\n\t\t\tif (quotient != null) {\n\t\t\t\tBitSet newInfStates = (BitSet)inf.clone();\n\t\t\t\tnewInfStates.or(quotient.getNonRepresentativeStates());\n\t\t\t\tint quotientModelStates = quotient.getModel().getNumStates() - newInfStates.cardinality();\n\t\t\t\tmainLog.println(\"Computing Rmin in zero-reward EC quotient model (\" + quotientModelStates + \" relevant states)...\");\n\t\t\t\tres = computeReachRewardsNumeric(quotient.getModel(), quotient.getRewards(), mdpSolnMethod, target, newInfStates, min, init, known, strat);\n\t\t\t\tquotient.mapResults(res.soln);\n\t\t\t} else {\n\t\t\t\tres = computeReachRewardsNumeric(mdp, mdpRewards, mdpSolnMethod, target, inf, min, init, known, strat);\n\t\t\t}\n\t\t} else {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(inf, n, Double.POSITIVE_INFINITY);\n\t\t\tres.accuracy = AccuracyFactory.doublesFromQualitative();\n\t\t}\n\t\t\n\t\t// Store strategy\n\t\tif (genStrat) {\n\t\t\tres.strat = new MDStrategyArray<Double>(mdp, strat);\n\t\t}\n\n\t\t// Finished expected reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Expected reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = timerProb1 / 1000.0;\n\n\t\treturn res;\n\t}\n\n\tprotected ModelCheckerResult computeReachRewardsNumeric(MDP<Double> mdp, MDPRewards<Double> mdpRewards, MDPSolnMethod method, BitSet target, BitSet inf, boolean min, double init[], BitSet known, int strat[]) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\n\t\tIterationMethod iterationMethod = null;\n\t\tswitch (method) {\n\t\tcase VALUE_ITERATION:\n\t\t\titerationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\t\tbreak;\n\t\tcase GAUSS_SEIDEL:\n\t\t\titerationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, false);\n\t\t\tbreak;\n\t\tcase POLICY_ITERATION:\n\t\t\tif (doIntervalIteration) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Interval iteration currently not supported for policy iteration\");\n\t\t\t}\n\t\t\tres = computeReachRewardsPolIter(mdp, mdpRewards, target, inf, min, strat);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown MDP solution method \" + method.fullName());\n\t\t}\n\n\t\tif (res == null) { // not yet computed, use iterationMethod\n\t\t\tif (!doIntervalIteration) {\n\t\t\t\tres = doValueIterationReachRewards(mdp, mdpRewards, iterationMethod, target, inf, min, init, known, getDoTopologicalValueIteration(), strat);\n\t\t\t} else {\n\t\t\t\tres = doIntervalIterationReachRewards(mdp, mdpRewards, iterationMethod, target, inf, min, init, known, getDoTopologicalValueIteration(), strat);\n\t\t\t}\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using value iteration.\n\t * Optionally, store optimal (memoryless) strategy info. \n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult computeReachRewardsValIter(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, BitSet inf, boolean min, double init[], BitSet known, int strat[])\n\t\t\tthrows PrismException\n\t{\n\t\tIterationMethodPower iterationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\treturn doValueIterationReachRewards(mdp, mdpRewards, iterationMethod, target, inf, min, init, known, false, strat);\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using value iteration.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * @param topological Do topological value iteration?\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult doValueIterationReachRewards(MDP<Double> mdp, MDPRewards<Double> mdpRewards, IterationMethod iterationMethod, BitSet target, BitSet inf, boolean min, double init[], BitSet known, boolean topological, int strat[])\n\t\t\tthrows PrismException\n\t{\n\t\tBitSet unknown;\n\t\tint i, n;\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString description = (min ? \"min\" : \"max\") + (topological ? \", topological\" : \"\" ) + \", with \" + iterationMethod.getDescriptionShort();\n\t\tmainLog.println(\"Starting value iteration (\" + description + \")...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit MDP ReachRewards value iteration (\" + description +\")\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Initialise solution vectors. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 0.0/infinity if in target/inf; (3) passed in initial value; (4) 0.0\n\t\tif (init != null) {\n\t\t\tif (known != null) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tinit[i] = known.get(i) ? init[i] : target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : init[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tinit[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : init[i];\n\t\t\t}\n\t\t} else {\n\t\t\tinit = new double[n];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinit[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : 0.0;\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tunknown.andNot(inf);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tif (iterationsExport != null)\n\t\t\titerationsExport.exportVector(init, 0);\n\n\t\tIterationMethod.IterationValIter forMvMultRewMinMax = iterationMethod.forMvMultRewMinMax(mdp, mdpRewards, min, strat);\n\t\tforMvMultRewMinMax.init(init);\n\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\tif (topological) {\n\t\t\t// Compute SCCInfo, including trivial SCCs in the subgraph obtained when only considering\n\t\t\t// states in unknown\n\t\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, mdp, true, unknown::get);\n\n\t\t\tIterationMethod.SingletonSCCSolver singletonSCCSolver = (int s, double[] soln) -> {\n\t\t\t\tsoln[s] = mdp.mvMultRewJacMinMaxSingle(s, soln, mdpRewards, min, strat);\n\t\t\t};\n\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doTopologicalValueIteration(this, description, sccs, forMvMultRewMinMax, singletonSCCSolver, timer, iterationsExport);\n\t\t} else {\n\t\t\t// run the actual value iteration\n\t\t\treturn iterationMethod.doValueIteration(this, description, forMvMultRewMinMax, unknownStates, timer, iterationsExport);\n\t\t}\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using Gauss-Seidel (including Jacobi-style updates).\n\t * Optionally, store optimal (memoryless) strategy info. \n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult computeReachRewardsGaussSeidel(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, BitSet inf, boolean min, double init[],\n\t\t\tBitSet known, int strat[]) throws PrismException\n\t{\n\t\tIterationMethodGS iterationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, false);\n\t\treturn doValueIterationReachRewards(mdp, mdpRewards, iterationMethod, target, inf, min, init, known, false, strat);\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using interval iteration\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten)\n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * @param topological do topological interval iteration\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult doIntervalIterationReachRewards(MDP<Double> mdp, MDPRewards<Double> mdpRewards, IterationMethod iterationMethod, BitSet target, BitSet inf, boolean min, double init[], BitSet known, boolean topological, int strat[])\n\t\t\tthrows PrismException\n\t{\n\t\tBitSet unknown;\n\t\tint i, n;\n\t\tdouble initBelow[], initAbove[];\n\t\tlong timer;\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tunknown.andNot(inf);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\tdouble upperBound;\n\t\tif (iiOptions.hasManualUpperBound()) {\n\t\t\tupperBound = iiOptions.getManualUpperBound();\n\t\t\tgetLog().printWarning(\"Upper bound for interval iteration manually set to \" + upperBound);\n\t\t} else {\n\t\t\tif (min) {\n\t\t\t\tupperBound = computeReachRewardsMinUpperBound(mdp, mdpRewards, target, unknown, inf);\n\t\t\t} else {\n\t\t\t\tupperBound = computeReachRewardsMaxUpperBound(mdp, mdpRewards, target, unknown, inf);\n\t\t\t}\n\t\t}\n\n\t\tdouble lowerBound;\n\t\tif (iiOptions.hasManualLowerBound()) {\n\t\t\tlowerBound = iiOptions.getManualLowerBound();\n\t\t\tgetLog().printWarning(\"Lower bound for interval iteration manually set to \" + lowerBound);\n\t\t} else {\n\t\t\tlowerBound = 0.0;\n\t\t}\n\n\t\tif (min) {\n\t\t\tif (!isContracting(mdp, unknown, target)) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Interval iteration for Rmin and non-contracting MDP currently not supported\");\n\t\t\t} else {\n\t\t\t\tmainLog.println(\"Relevant sub-MDP is contracting, proceed...\");\n\t\t\t}\n\t\t}\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString description = (min ? \"min\" : \"max\") + (topological ? \", topological\" : \"\") + \", with \" + iterationMethod.getDescriptionShort();\n\t\tmainLog.println(\"Starting interval iteration (\" + description + \")...\");\n\n\t\tExportIterations iterationsExport = null;\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\titerationsExport = new ExportIterations(\"Explicit MDP ReachRewards interval iteration (\" + description + \")\");\n\t\t\tmainLog.println(\"Exporting iterations to \" + iterationsExport.getFileName());\n\t\t}\n\n\t\t// Create initial solution vector(s)\n\t\tinitBelow = (init == null) ? new double[n] : init;\n\t\tinitAbove = new double[n];\n\n\t\t// Initialise solution vector from below. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 0.0/infinity if in target/inf; (3) lowerBound\n\t\tif (init != null && known != null) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinitBelow[i] = known.get(i) ? init[i] : target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : lowerBound;\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinitBelow[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : lowerBound;\n\t\t}\n\n\t\t// Initialise solution vector from above. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 0.0/infinity if in target/inf; (3) upperBound\n\t\tif (init != null && known != null) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinitAbove[i] = known.get(i) ? init[i] : target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : upperBound;\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tinitAbove[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : upperBound;\n\t\t}\n\n\t\tif (iterationsExport != null) {\n\t\t\titerationsExport.exportVector(initBelow, 0);\n\t\t\titerationsExport.exportVector(initAbove, 1);\n\t\t}\n\n\t\tfinal boolean enforceMonotonicFromBelow = iiOptions.isEnforceMonotonicityFromBelow();\n\t\tfinal boolean enforceMonotonicFromAbove = iiOptions.isEnforceMonotonicityFromAbove();\n\t\tfinal boolean checkMonotonic = iiOptions.isCheckMonotonicity();\n\n\t\tif (!enforceMonotonicFromAbove) {\n\t\t\tgetLog().println(\"Note: Interval iteration is configured to not enforce monotonicity from above.\");\n\t\t}\n\t\tif (!enforceMonotonicFromBelow) {\n\t\t\tgetLog().println(\"Note: Interval iteration is configured to not enforce monotonicity from below.\");\n\t\t}\n\n\t\tIterationMethod.IterationIntervalIter below = iterationMethod.forMvMultRewMinMaxInterval(mdp, mdpRewards, min, strat, true, enforceMonotonicFromBelow, checkMonotonic);\n\t\tIterationMethod.IterationIntervalIter above = iterationMethod.forMvMultRewMinMaxInterval(mdp, mdpRewards, min, strat, false, enforceMonotonicFromAbove, checkMonotonic);\n\t\tbelow.init(initBelow);\n\t\tabove.init(initAbove);\n\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\tModelCheckerResult rv;\n\t\tif (topological) {\n\t\t\t// Compute SCCInfo, including trivial SCCs in the subgraph obtained when only considering\n\t\t\t// states in unknown\n\t\t\tSCCInfo sccs = SCCComputer.computeTopologicalOrdering(this, mdp, true, unknown::get);\n\n\t\t\tIterationMethod.SingletonSCCSolver singletonSCCSolver = (int s, double[] soln) -> {\n\t\t\t\tsoln[s] = mdp.mvMultRewJacMinMaxSingle(s, soln, mdpRewards, min, strat);\n\t\t\t};\n\n\t\t\t// run the actual value iteration\n\t\t\trv = iterationMethod.doTopologicalIntervalIteration(this, description, sccs, below, above, singletonSCCSolver, timer, iterationsExport);\n\t\t} else {\n\t\t\t// run the actual value iteration\n\t\t\trv = iterationMethod.doIntervalIteration(this, description, below, above, unknownStates, timer, iterationsExport);\n\t\t}\n\n\t\tdouble max_v = PrismUtils.findMaxFinite(rv.soln, unknownStates.iterator());\n\t\tif (max_v != Double.NEGATIVE_INFINITY) {\n\t\t\tmainLog.println(\"Maximum finite value in solution vector at end of interval iteration: \" + max_v);\n\t\t}\n\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using policy iteration.\n\t * The array {@code strat} is used both to pass in the initial strategy for policy iteration,\n\t * and as storage for the resulting optimal strategy (if needed).\n\t * Passing in an initial strategy is required when some states have infinite reward,\n\t * to avoid the possibility of policy iteration getting stuck on an infinite-value strategy.\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tprotected ModelCheckerResult computeReachRewardsPolIter(MDP<Double> mdp, MDPRewards<Double> mdpRewards, BitSet target, BitSet inf, boolean min, int strat[])\n\t\t\tthrows PrismException\n\t{\n\t\tModelCheckerResult res;\n\t\tint i, n, iters, totalIters;\n\t\tdouble soln[], soln2[];\n\t\tboolean done;\n\t\tlong timer;\n\t\tDTMCModelChecker mcDTMC;\n\t\tDTMC<Double> dtmc;\n\t\tMCRewards<Double> mcRewards;\n\n\t\t// Re-use solution to solve each new policy (strategy)?\n\t\tboolean reUseSoln = true;\n\n\t\t// Start policy iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"Starting policy iteration (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Create a DTMC model checker (for solving policies)\n\t\tmcDTMC = new DTMCModelChecker(this);\n\t\tmcDTMC.inheritSettings(this);\n\t\tmcDTMC.setLog(new PrismDevNullLog());\n\n\t\t// Store num states\n\t\tn = mdp.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = soln2[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : 0.0;\n\n\t\t// If not passed in, create new storage for strategy and initialise\n\t\t// Initial strategy just picks first choice (0) everywhere\n\t\tif (strat == null) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tstrat[i] = 0;\n\t\t}\n\t\t\t\n\t\t// Start iterations\n\t\titers = totalIters = 0;\n\t\tdone = false;\n\t\twhile (!done && iters < maxIters) {\n\t\t\titers++;\n\t\t\t// Solve induced DTMC for strategy\n\t\t\tdtmc = new DTMCFromMDPMemorylessAdversary<>(mdp, strat);\n\t\t\tmcRewards = new MCRewardsFromMDPRewards<>(mdpRewards, strat);\n\t\t\tres = mcDTMC.computeReachRewardsValIter(dtmc, mcRewards, target, inf, reUseSoln ? soln : null, null);\n\t\t\tsoln = res.soln;\n\t\t\ttotalIters += res.numIters;\n\t\t\t// Check if optimal, improve non-optimal choices\n\t\t\tmdp.mvMultRewMinMax(soln, mdpRewards, min, soln2, null, false, null);\n\t\t\tdone = true;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t// Don't look at target/inf states - we may not have strategy info for them,\n\t\t\t\t// so they might appear non-optimal\n\t\t\t\tif (target.get(i) || inf.get(i))\n\t\t\t\t\tcontinue;\n\t\t\t\tif (!PrismUtils.doublesAreClose(soln[i], soln2[i], termCritParam, termCrit == TermCrit.ABSOLUTE)) {\n\t\t\t\t\tdone = false;\n\t\t\t\t\tList<Integer> opt = mdp.mvMultRewMinMaxSingleChoices(i, soln, mdpRewards, min, soln2[i]);\n\t\t\t\t\t// Only update strategy if strictly better\n\t\t\t\t\tif (!opt.contains(strat[i]))\n\t\t\t\t\t\tstrat[i] = opt.get(0);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Finished policy iteration\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Policy iteration\");\n\t\tmainLog.println(\" took \" + iters + \" cycles (\" + totalIters + \" iterations in total) and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.numIters = totalIters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Construct strategy information for min/max expected reachability.\n\t * (More precisely, list of indices of choices resulting in min/max.)\n\t * (Note: indices are guaranteed to be sorted in ascending order.)\n\t * @param mdp The MDP\n\t * @param mdpRewards The rewards\n\t * @param state The state to generate strategy info for\n\t * @param target The set of target states to reach\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param lastSoln Vector of values from which to recompute in one iteration \n\t */\n\tpublic List<Integer> expReachStrategy(MDP<Double> mdp, MDPRewards<Double> mdpRewards, int state, BitSet target, boolean min, double lastSoln[]) throws PrismException\n\t{\n\t\tdouble val = mdp.mvMultRewMinMaxSingle(state, lastSoln, mdpRewards, min, null);\n\t\treturn mdp.mvMultRewMinMaxSingleChoices(state, lastSoln, mdpRewards, min, val);\n\t}\n\n\t/**\n\t * Restrict a (memoryless) strategy for an MDP, stored as an integer array of choice indices,\n\t * to the states of the MDP that are reachable under that strategy.  \n\t * @param mdp The MDP\n\t * @param strat The strategy\n\t */\n\tpublic <Value> void restrictStrategyToReachableStates(MDP<Value> mdp, int strat[])\n\t{\n\t\tBitSet restrict = new BitSet();\n\t\tBitSet explore = new BitSet();\n\t\t// Get initial states\n\t\tfor (int is : mdp.getInitialStates()) {\n\t\t\trestrict.set(is);\n\t\t\texplore.set(is);\n\t\t}\n\t\t// Compute reachable states (store in 'restrict') \n\t\tboolean foundMore = true;\n\t\twhile (foundMore) {\n\t\t\tfoundMore = false;\n\t\t\tfor (int s = explore.nextSetBit(0); s >= 0; s = explore.nextSetBit(s + 1)) {\n\t\t\t\texplore.set(s, false);\n\t\t\t\tif (strat[s] >= 0) {\n\t\t\t\t\tIterator<Map.Entry<Integer, Value>> iter = mdp.getTransitionsIterator(s, strat[s]);\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Value> e = iter.next();\n\t\t\t\t\t\tint dest = e.getKey();\n\t\t\t\t\t\tif (!restrict.get(dest)) {\n\t\t\t\t\t\t\tfoundMore = true;\n\t\t\t\t\t\t\trestrict.set(dest);\n\t\t\t\t\t\t\texplore.set(dest);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Set strategy choice for non-reachable state to -1\n\t\tint n = mdp.getNumStates();\n\t\tfor (int s = restrict.nextClearBit(0); s < n; s = restrict.nextClearBit(s + 1)) {\n\t\t\tstrat[s] = -3;\n\t\t}\n\t}\n\n\t/**\n\t * Compute the end component quotient (for use with PMax),\n\t * each maximal end component is collapsed to a single state,\n\t * likewise the yes and no regions, respectively.\n\t */\n\tprivate <Value> MDPEquiv<Value> maxQuotient(MDP<Value> mdp, BitSet yes, BitSet no) throws PrismException\n\t{\n\t\tBitSet maybe = new BitSet();\n\t\tmaybe.set(0, mdp.getNumStates());\n\t\tmaybe.andNot(yes);\n\t\tmaybe.andNot(no);\n\n\t\tECComputer ec = ECComputer.createECComputer(this, mdp);\n\n\t\tec.computeMECStates(maybe);\n\t\tList<BitSet> mecs = ec.getMECStates();\n\t\tmecs.add(yes);\n\t\tmecs.add(no);\n\n\t\tEquivalenceRelationInteger eq = new EquivalenceRelationInteger(mecs);\n\t\tBasicModelTransformation<MDP<Value>, MDPEquiv<Value>> quotientTransform = MDPEquiv.transformDroppingLoops(mdp, eq);\n\t\tMDPEquiv<Value> quotient = quotientTransform.getTransformedModel();\n\n\t\t//mdp.exportToDotFile(\"original.dot\");\n\t\t//quotient.exportToDotFile(\"maxQuotient.dot\");\n\n\t\tint realStates = quotient.getNumStates() - quotient.getNonRepresentativeStates().cardinality();\n\t\tmainLog.println(\"Max-Quotient MDP: \" + realStates + \" equivalence classes / non-trap states.\");\n\n\t\treturn quotient;\n\t}\n\n\t/**\n\t * Simple test program.\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tMDPModelChecker mc;\n\t\tMDPSimple<Double> mdp;\n\t\tModelCheckerResult res;\n\t\tBitSet init, target;\n\t\tMap<String, BitSet> labels;\n\t\tboolean min = true;\n\t\ttry {\n\t\t\tmc = new MDPModelChecker(null);\n\t\t\tmdp = new MDPSimple<>();\n\t\t\tmdp.buildFromPrismExplicit(args[0]);\n\t\t\tmdp.addInitialState(0);\n\t\t\t//System.out.println(mdp);\n\t\t\tlabels = StateModelChecker.loadLabelsFile(args[1]);\n\t\t\t//System.out.println(labels);\n\t\t\tinit = labels.get(\"init\");\n\t\t\ttarget = labels.get(args[2]);\n\t\t\tif (target == null)\n\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + args[2] + \"\\\"\");\n\t\t\tfor (int i = 3; i < args.length; i++) {\n\t\t\t\tif (args[i].equals(\"-min\"))\n\t\t\t\t\tmin = true;\n\t\t\t\telse if (args[i].equals(\"-max\"))\n\t\t\t\t\tmin = false;\n\t\t\t\telse if (args[i].equals(\"-nopre\"))\n\t\t\t\t\tmc.setPrecomp(false);\n\t\t\t}\n\t\t\tres = mc.computeReachProbs(mdp, target, min);\n\t\t\tSystem.out.println(res.soln[init.nextSetBit(0)]);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(e);\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/MDPSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Christian von Essen <christian.vonessen@imag.fr> (Verimag, Grenoble)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Map.Entry;\nimport java.util.function.Function;\n\nimport io.ExplicitModelImporter;\nimport prism.Evaluator;\nimport prism.PrismException;\n\n/**\n * Simple explicit-state representation of an MDP.\n * The implementation is far from optimal, both in terms of memory usage and speed of access.\n * The model is, however, easy to manipulate. For a static model (i.e. one that does not change\n * after creation), consider MDPSparse, which is more efficient. \n */\npublic class MDPSimple<Value> extends MDPExplicit<Value> implements NondetModelSimple<Value>\n{\n\t// Transition function (Steps)\n\tprotected List<List<Distribution<Value>>> trans;\n\n\t// Action labels\n\tprotected ChoiceActionsSimple actions;\n\n\t// Flag: allow duplicates in distribution sets?\n\tprotected boolean allowDupes = false;\n\n\t// Other statistics\n\tprotected int numDistrs;\n\tprotected int numTransitions;\n\tprotected int maxNumDistrs;\n\tprotected boolean maxNumDistrsOk;\n\n\t// Constructors\n\n\t/**\n\t * Constructor: empty MDP.\n\t */\n\tpublic MDPSimple()\n\t{\n\t\tinitialise(0);\n\t}\n\n\t/**\n\t * Constructor: new MDP with fixed number of states.\n\t */\n\tpublic MDPSimple(int numStates)\n\t{\n\t\tinitialise(numStates);\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic MDPSimple(MDPSimple<Value> mdp)\n\t{\n\t\tthis(mdp.numStates);\n\t\tcopyFrom(mdp);\n\t\t// Copy storage directly to avoid worrying about duplicate distributions (and for efficiency) \n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tList<Distribution<Value>> distrs = trans.get(s);\n\t\t\tfor (Distribution<Value> distr : mdp.trans.get(s)) {\n\t\t\t\tdistrs.add(new Distribution<>(distr));\n\t\t\t}\n\t\t}\n\t\tactions = new ChoiceActionsSimple(mdp.actions);\n\t\t// Copy flags/stats too\n\t\tallowDupes = mdp.allowDupes;\n\t\tnumDistrs = mdp.numDistrs;\n\t\tnumTransitions = mdp.numTransitions;\n\t\tmaxNumDistrs = mdp.maxNumDistrs;\n\t\tmaxNumDistrsOk = mdp.maxNumDistrsOk;\n\t}\n\n\t/**\n\t * Constructor: new MDP copied from an existing DTMC.\n\t */\n\tpublic MDPSimple(DTMCSimple<Value> dtmc)\n\t{\n\t\tthis(dtmc.getNumStates());\n\t\tcopyFrom(dtmc);\n\t\t// NB: actions (on transitions) from the DTMC are not copied to (choices of) the MDP\n\t\tactionList.clear();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\taddChoice(s, new Distribution<Value>(dtmc.getTransitions(s)));\n\t\t}\n\t}\n\n\t/**\n\t * Construct an MDP from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t * Note: have to build new Distributions from scratch anyway to do this,\n\t * so may as well provide this functionality as a constructor.\n\t */\n\tpublic MDPSimple(MDPSimple<Value> mdp, int permut[])\n\t{\n\t\tthis(mdp.numStates);\n\t\tcopyFrom(mdp, permut);\n\t\t// Copy storage directly to avoid worrying about duplicate distributions (and for efficiency)\n\t\t// (Since permut is a bijection, all structures and statistics are identical)\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tList<Distribution<Value>> distrs = trans.get(permut[s]);\n\t\t\tfor (Distribution<Value> distr : mdp.trans.get(s)) {\n\t\t\t\tdistrs.add(new Distribution<>(distr, permut));\n\t\t\t}\n\t\t}\n\t\tactions = new ChoiceActionsSimple(mdp.actions, permut);\n\t\t// Copy flags/stats too\n\t\tallowDupes = mdp.allowDupes;\n\t\tnumDistrs = mdp.numDistrs;\n\t\tnumTransitions = mdp.numTransitions;\n\t\tmaxNumDistrs = mdp.maxNumDistrs;\n\t\tmaxNumDistrsOk = mdp.maxNumDistrsOk;\n\t}\n\n\t/**\n\t * Construct an MDPSimple object from an MDP object.\n\t */\n\tpublic MDPSimple(MDP<Value> mdp)\n\t{\n\t\tthis(mdp, p -> p);\n\t}\n\n\t/**\n\t * Construct an MDPSimple object from an MDP object,\n\t * mapping probability values using the provided function.\n\t * There is no attempt to check that distributions sum to one,\n\t * but empty choices (all probabilities mapped to zero) are removed.\n\t */\n\tpublic MDPSimple(MDP<Value> mdp, Function<? super Value, ? extends Value> probMap)\n\t{\n\t\tthis(mdp, probMap, mdp.getEvaluator());\n\t}\n\n\t/**\n\t * Construct an MDPSimple object from an MDP object,\n\t * mapping probability values using the provided function.\n\t * There is no attempt to check that distributions sum to one,\n\t * but empty choices (all probabilities mapped to zero) are removed.\n\t * Since the type changes (T -> Value), an Evaluator for Value must be given.\n\t */\n\tpublic <T> MDPSimple(MDP<T> mdp, Function<? super T, ? extends Value> probMap, Evaluator<Value> eval)\n\t{\n\t\tthis(mdp.getNumStates());\n\t\tcopyFrom(mdp);\n\t\tsetEvaluator(eval);\n\t\tint numStates = getNumStates();\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tint numChoices = mdp.getNumChoices(i);\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\tObject action = mdp.getAction(i, j);\n\t\t\t\tDistribution<Value> distr = new Distribution<>(eval);\n\t\t\t\tIterator<Map.Entry<Integer, T>> iter = mdp.getTransitionsIterator(i, j);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tMap.Entry<Integer, T> e = iter.next();\n\t\t\t\t\tdistr.set(e.getKey(), probMap.apply(e.getValue()));\n\t\t\t\t}\n\t\t\t\tif (!distr.isEmpty()) {\n\t\t\t\t\tif (action != null) {\n\t\t\t\t\t\taddActionLabelledChoice(i, distr, action);\n\t\t\t\t\t} else {\n\t\t\t\t\t\taddChoice(i, distr);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// Mutators (for ModelSimple)\n\n\t@Override\n\tpublic void initialise(int numStates)\n\t{\n\t\tsuper.initialise(numStates);\n\t\tnumDistrs = numTransitions = maxNumDistrs = 0;\n\t\tmaxNumDistrsOk = true;\n\t\ttrans = new ArrayList<List<Distribution<Value>>>(numStates);\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\ttrans.add(new ArrayList<Distribution<Value>>());\n\t\t}\n\t\tactions = new ChoiceActionsSimple();\n\t}\n\n\t@Override\n\tpublic void clearState(int s)\n\t{\n\t\t// Do nothing if state does not exist\n\t\tif (s >= numStates || s < 0)\n\t\t\treturn;\n\t\t// Clear data structures and update stats\n\t\tList<Distribution<Value>> list = trans.get(s);\n\t\tnumDistrs -= list.size();\n\t\tfor (Distribution<Value> distr : list) {\n\t\t\tnumTransitions -= distr.size();\n\t\t}\n\t\tmaxNumDistrsOk = false;\n\t\ttrans.get(s).clear();\n\t\tactions.clearState(s);\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t@Override\n\tpublic int addState()\n\t{\n\t\taddStates(1);\n\t\treturn numStates - 1;\n\t}\n\n\t@Override\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tfor (int i = 0; i < numToAdd; i++) {\n\t\t\ttrans.add(new ArrayList<Distribution<Value>>());\n\t\t\tnumStates++;\n\t\t}\n\t}\n\n\t@Override\n\tpublic void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\t// To preserve file exactly, allow duplicate choices\n\t\tallowDupes = true;\n\t\tinitialise(modelImporter.getNumStates());\n\t\tmodelImporter.extractMDPTransitions((s, i, s2, v, a) -> {\n\t\t\t// Add empty distributions as needed\n\t\t\twhile (i >= getNumChoices(s)) {\n\t\t\t\taddChoice(s, new Distribution<>(getEvaluator()));\n\t\t\t}\n\t\t\t// Then add transition (update stats since Distribution modified directly)\n\t\t\tif (!getChoice(s, i).add(s2, v)) {\n\t\t\t\tnumTransitions++;\n\t\t\t}\n\t\t\tif (a != null) {\n\t\t\t\tsetAction(s, i, a);\n\t\t\t}\n\t\t}, getEvaluator());\n\t\t// Check for empty choice distributions (this not the same as a deadlock)\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tfor (Distribution<?> distr : getChoices(s)) {\n\t\t\t\tif (distr.isEmpty()) {\n\t\t\t\t\tthrow new PrismException(\"Empty distribution in state \" + s + \" when importing transitions\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// Mutators (other)\n\n\t/**\n\t * Add a choice (distribution {@code distr}) to state {@code s} (which must exist).\n\t * Distribution is only actually added if it does not already exists for state {@code s}.\n\t * (Assuming {@code allowDupes} flag is not enabled.)\n\t * Returns the index of the (existing or newly added) distribution.\n\t * Returns -1 in case of error.\n\t */\n\tpublic int addChoice(int s, Distribution<Value> distr)\n\t{\n\t\tList<Distribution<Value>> set;\n\t\t// Check state exists\n\t\tif (s >= numStates || s < 0)\n\t\t\treturn -1;\n\t\t// Add distribution (if new)\n\t\tif (!allowDupes) {\n\t\t\tint i = indexOfChoice(s, distr);\n\t\t\tif (i != -1)\n\t\t\t\treturn i;\n\t\t}\n\t\tset = trans.get(s);\n\t\tset.add(distr);\n\t\tactionList.markNeedsRecomputing();\n\t\t// Update stats\n\t\tnumDistrs++;\n\t\tmaxNumDistrs = Math.max(maxNumDistrs, set.size());\n\t\tnumTransitions += distr.size();\n\t\treturn set.size() - 1;\n\t}\n\n\t/**\n\t * Add a choice (distribution {@code distr}) labelled with {@code action} to state {@code s} (which must exist).\n\t * Action/distribution is only actually added if it does not already exists for state {@code s}.\n\t * (Assuming {@code allowDupes} flag is not enabled.)\n\t * Returns the index of the (existing or newly added) distribution.\n\t * Returns -1 in case of error.\n\t */\n\tpublic int addActionLabelledChoice(int s, Distribution<Value> distr, Object action)\n\t{\n\t\tList<Distribution<Value>> set;\n\t\t// Check state exists\n\t\tif (s >= numStates || s < 0)\n\t\t\treturn -1;\n\t\t// Add distribution/action (if new)\n\t\tif (!allowDupes) {\n\t\t\tint i = indexOfActionLabelledChoice(s, distr, action);\n\t\t\tif (i != -1)\n\t\t\t\treturn i;\n\t\t}\n\t\tset = trans.get(s);\n\t\tset.add(distr);\n\t\t// Set action\n\t\tactions.setAction(s, set.size() - 1, action);\n\t\tactionList.markNeedsRecomputing();\n\t\t// Update stats\n\t\tnumDistrs++;\n\t\tmaxNumDistrs = Math.max(maxNumDistrs, set.size());\n\t\tnumTransitions += distr.size();\n\t\treturn set.size() - 1;\n\t}\n\n\t/**\n\t * Set the action label for choice i in some state s.\n\t * This method does not know about duplicates (i.e. if setting an action causes\n\t * two choices to be identical, one will not be removed).\n\t * Use {@link #addActionLabelledChoice(int, Distribution, Object)} which is more reliable.\n\t */\n\tpublic void setAction(int s, int i, Object o)\n\t{\n\t\tactions.setAction(s, i, o);\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t// Accessors (for Model)\n\n\t@Override\n\tpublic List<Object> findActionsUsed()\n\t{\n\t\treturn actions.findActionsUsed(getNumStates(), this::getNumChoices);\n\t}\n\n\t@Override\n\tpublic boolean onlyNullActionUsed()\n\t{\n\t\treturn actions.onlyNullActionUsed();\n\t}\n\n\t@Override\n\tpublic int getNumTransitions()\n\t{\n\t\treturn numTransitions;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s)\n\t{\n\t\tint numTransitions = 0;\n\t\tint numChoices = getNumChoices(s);\n\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\tnumTransitions += trans.get(s).get(j).size();\n\t\t}\n\t\treturn numTransitions; \n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tint fixed = 0;\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t// Note that no distributions is a deadlock, not an empty distribution\n\t\t\tif (trans.get(i).isEmpty()) {\n\t\t\t\taddDeadlockState(i);\n\t\t\t\tif (fix) {\n\t\t\t\t\tDistribution<Value> distr = new Distribution<>(getEvaluator());\n\t\t\t\t\tdistr.add(i, getEvaluator().one());\n\t\t\t\t\taddChoice(i, distr);\n\t\t\t\t\tfixed++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Add the empty action (if missing), regardless of whether actionList needs recomputing\n\t\tif (fixed > 0) {\n\t\t\tactionList.addAction(null);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (trans.get(i).isEmpty() && (except == null || !except.get(i)))\n\t\t\t\tthrow new PrismException(\"MDP has a deadlock in state \" + i);\n\t\t}\n\t}\n\n\t// Accessors (for NondetModel)\n\n\t@Override\n\tpublic int getNumChoices(int s)\n\t{\n\t\treturn trans.get(s).size();\n\t}\n\n\t@Override\n\tpublic int getMaxNumChoices()\n\t{\n\t\t// Recompute if necessary\n\t\tif (!maxNumDistrsOk) {\n\t\t\tmaxNumDistrs = 0;\n\t\t\tfor (int s = 0; s < numStates; s++)\n\t\t\t\tmaxNumDistrs = Math.max(maxNumDistrs, getNumChoices(s));\n\t\t}\n\t\treturn maxNumDistrs;\n\t}\n\n\t@Override\n\tpublic int getNumChoices()\n\t{\n\t\treturn numDistrs;\n\t}\n\n\t@Override\n\tpublic Object getAction(int s, int i)\n\t{\n\t\treturn actions.getAction(s, i);\n\t}\n\n\t@Override\n\tpublic boolean allSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn trans.get(s).get(i).isSubsetOf(set);\n\t}\n\n\t@Override\n\tpublic boolean someSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn trans.get(s).get(i).containsOneOf(set);\n\t}\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int s, final int i)\n\t{\n\t\treturn trans.get(s).get(i).getSupport().iterator();\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(final int s, final int i)\n\t{\n\t\treturn SuccessorsIterator.from(getSuccessorsIterator(s, i), true);\n\t}\n\n\t// Accessors (for MDP)\n\n\t@Override\n\tpublic int getNumTransitions(int s, int i)\n\t{\n\t\treturn trans.get(s).get(i).size();\n\t}\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(int s, int i)\n\t{\n\t\treturn trans.get(s).get(i).iterator();\n\t}\n\n\t\n\n\t// Accessors (other)\n\n\t/**\n\t * Get the list of choices (distributions) for state s.\n\t */\n\tpublic List<Distribution<Value>> getChoices(int s)\n\t{\n\t\treturn trans.get(s);\n\t}\n\n\t/**\n\t * Get the ith choice (distribution) for state s.\n\t */\n\tpublic Distribution<Value> getChoice(int s, int i)\n\t{\n\t\treturn trans.get(s).get(i);\n\t}\n\n\t/**\n\t * Returns the index of the choice {@code distr} for state {@code s}, if it exists.\n\t * If none, -1 is returned. If there are multiple (i.e. allowDupes is true), the first is returned. \n\t */\n\tpublic int indexOfChoice(int s, Distribution<Value> distr)\n\t{\n\t\treturn trans.get(s).indexOf(distr);\n\t}\n\n\t/**\n\t * Returns the index of the {@code action}-labelled choice {@code distr} for state {@code s}, if it exists.\n\t * If none, -1 is returned. If there are multiple (i.e. allowDupes is true), the first is returned. \n\t */\n\tpublic int indexOfActionLabelledChoice(int s, Distribution<Value> distr, Object action)\n\t{\n\t\tList<Distribution<Value>> set = trans.get(s);\n\t\tint i, n = set.size();\n\t\tif (distr == null) {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (set.get(i) == null) {\n\t\t\t\t\tObject a = getAction(s, i);\n\t\t\t\t\tif (action == null) {\n\t\t\t\t\t\tif (a == null)\n\t\t\t\t\t\t\treturn i;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (action.equals(a))\n\t\t\t\t\t\t\treturn i;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (distr.equals(set.get(i))) {\n\t\t\t\t\tObject a = getAction(s, i);\n\t\t\t\t\tif (action == null) {\n\t\t\t\t\t\tif (a == null)\n\t\t\t\t\t\t\treturn i;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (action.equals(a))\n\t\t\t\t\t\t\treturn i;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn toStringMDP();\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof MDPSimple))\n\t\t\treturn false;\n\t\tMDPSimple<?> mdp = (MDPSimple<?>) o;\n\t\tif (numStates != mdp.numStates)\n\t\t\treturn false;\n\t\tif (!initialStates.equals(mdp.initialStates))\n\t\t\treturn false;\n\t\tif (!trans.equals(mdp.trans))\n\t\t\treturn false;\n\t\t// TODO: compare actions (complicated: null = null,null,null,...)\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/MDPSparse.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Christian von Essen <christian.vonessen@imag.fr> (Verimag, Grenoble)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.AbstractMap;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.LinkedHashSet;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Map.Entry;\nimport java.util.TreeMap;\n\nimport common.IterableStateSet;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport io.ExplicitModelImporter;\nimport io.IOUtils;\nimport parser.State;\nimport prism.ActionListOwner;\nimport prism.PrismException;\nimport prism.PrismUtils;\n\n/**\n * Sparse matrix (non-mutable) explicit-state representation of an MDP.\n * This is much faster to access than e.g. MDPSimple and should also be more compact.\n * The catch is that you have to create the model all in one go and then can't modify it.\n */\npublic class MDPSparse extends MDPExplicit<Double>\n{\n\t// Sparse matrix storing transition function (Steps)\n\t/** Probabilities for each transition (array of size numTransitions) */\n\tprotected double nonZeros[];\n\t/** Column (destination) indices for each transition (array of size numTransitions) */\n\tprotected int cols[];\n\t/** Indices into nonZeros/cols giving the start of the transitions for each choice (distribution);\n\t * array is of size numDistrs+1 and last entry is always equal to numTransitions */\n\tprotected int choiceStarts[];\n\t/** Indices into choiceStarts giving the start of the choices for each state;\n\t * array is of size numStates+1 and last entry is always equal to numDistrs */\n\tprotected int rowStarts[];\n\n\t// Action labels\n\t/** Array of action labels for choices;\n\t * if null, there are no actions; otherwise, is an array of size numDistrs */\n\tprotected Object actions[];\n\n\t// Other statistics\n\tprotected int numDistrs;\n\tprotected int numTransitions;\n\tprotected int maxNumDistrs;\n\n\t// Constructors\n\n\t/**\n\t * Constructor: Build new MDPSparse from arbitrary MDP type.\n\t *\n\t * @param mdp some MDP\n\t */\n\tpublic MDPSparse(final MDP<Double> mdp)\n\t{\n\t\tthis(mdp, false);\n\t}\n\n\t/**\n\t * Constructor: Build new MDPSparse from arbitrary MDP type.\n\t *\n\t * @param mdp some MDP\n\t * @param sort Whether or not to sort column indices\n\t */\n\tpublic MDPSparse(final MDP<Double> mdp, boolean sort)\n\t{\n\t\tinitialise(mdp.getNumStates());\n\t\tif (mdp instanceof ActionListOwner) {\n\t\t\tactionList.copyFrom(((ActionListOwner) mdp).getActionList());\n\t\t}\n\t\tsetStatesList(mdp.getStatesList());\n\t\tsetConstantValues(mdp.getConstantValues());\n\t\tfor (String label : mdp.getLabels()) {\n\t\t\taddLabel(label, mdp.getLabelStates(label));\n\t\t}\n\n\t\t// Copy stats\n\t\tnumDistrs = mdp.getNumChoices();\n\t\tnumTransitions = mdp.getNumTransitions();\n\t\tmaxNumDistrs = mdp.getMaxNumChoices();\n\t\t// Initialise transition function\n\t\tnonZeros = new double[numTransitions];\n\t\tcols = new int[numTransitions];\n\t\tchoiceStarts = new int[numDistrs + 1];\n\t\trowStarts = new int[numStates + 1];\n\t\tactions = hasActionLabels(mdp) ? new Object[numDistrs] : null;\n\n\t\t// Copy transition function\n\t\tfinal TreeMap<Integer, Double> sorted = sort ? new TreeMap<Integer, Double>() : null;\n\t\tint rowIndex = 0, choiceIndex = 0;\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tif (mdp.isInitialState(state)) {\n\t\t\t\taddInitialState(state);\n\t\t\t}\n\t\t\tif (mdp.isDeadlockState(state)) {\n\t\t\t\tdeadlocks.add(state);\n\t\t\t}\n\n\t\t\trowStarts[state] = rowIndex;\n\t\t\tif (actions != null) {\n\t\t\t\tfor (int choice = 0, numChoices = mdp.getNumChoices(state); choice < numChoices; choice++) {\n\t\t\t\t\tactions[rowIndex + choice] = mdp.getAction(state, choice);\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (int choice = 0, numChoices = mdp.getNumChoices(state); choice < numChoices; choice++) {\n\t\t\t\tchoiceStarts[rowIndex] = choiceIndex;\n\t\t\t\tfor (Iterator<Entry<Integer, Double>> transitions = mdp.getTransitionsIterator(state, choice); transitions.hasNext();) {\n\t\t\t\t\tfinal Map.Entry<Integer, Double> trans = transitions.next();\n\t\t\t\t\tif (sort) {\n\t\t\t\t\t\tsorted.put(trans.getKey(), trans.getValue());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tcols[choiceIndex] = trans.getKey();\n\t\t\t\t\t\tnonZeros[choiceIndex] = trans.getValue();\n\t\t\t\t\t\tchoiceIndex++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (sort) {\n\t\t\t\t\tfor (Map.Entry<Integer, Double> e : sorted.entrySet()) {\n\t\t\t\t\t\tcols[choiceIndex] = e.getKey();\n\t\t\t\t\t\tnonZeros[choiceIndex] = e.getValue();\n\t\t\t\t\t\tchoiceIndex++;\n\t\t\t\t\t}\n\t\t\t\t\tsorted.clear();\n\t\t\t\t}\n\t\t\t\trowIndex++;\n\t\t\t}\n\t\t}\n\t\tchoiceStarts[numDistrs] = numTransitions;\n\t\trowStarts[numStates] = numDistrs;\n\t}\n\n\t/** Helper: Does the given MDP have action labels on any of the choices? */\n\tprivate static boolean hasActionLabels(final MDP<?> mdp)\n\t{\n\t\tfor (int state = 0, numStates = mdp.getNumStates(); state < numStates; state++) {\n\t\t\tfor (int choice = 0, numChoices = mdp.getNumChoices(state); choice < numChoices; choice++) {\n\t\t\t\tif (mdp.getAction(state, choice) != null) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Copy constructor (from MDPSimple).\n\t */\n\tpublic MDPSparse(MDPSimple<Double> mdp)\n\t{\n\t\tthis(mdp, false);\n\t}\n\n\t/**\n\t * Copy constructor (from MDPSimple). Optionally, transitions within choices\n\t * are sorted (by ascending order of column index).\n\t * @param mdp The MDP to copy\n\t * @param sort Whether or not to sort column indices\n\t */\n\tpublic MDPSparse(MDPSimple<Double> mdp, boolean sort)\n\t{\n\t\tint i, j, k;\n\t\tTreeMap<Integer, Double> sorted = null;\n\t\tinitialise(mdp.getNumStates());\n\t\tcopyFrom(mdp);\n\t\t// Copy stats\n\t\tnumDistrs = mdp.getNumChoices();\n\t\tnumTransitions = mdp.getNumTransitions();\n\t\tmaxNumDistrs = mdp.getMaxNumChoices();\n\t\t// Copy transition function\n\t\tif (sort) {\n\t\t\tsorted = new TreeMap<Integer, Double>();\n\t\t}\n\t\tnonZeros = new double[numTransitions];\n\t\tcols = new int[numTransitions];\n\t\tchoiceStarts = new int[numDistrs + 1];\n\t\trowStarts = new int[numStates + 1];\n\t\tj = k = 0;\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\trowStarts[i] = j;\n\t\t\tfor (Distribution<Double> distr : mdp.trans.get(i)) {\n\t\t\t\tchoiceStarts[j] = k;\n\t\t\t\tfor (Map.Entry<Integer, Double> e : distr) {\n\t\t\t\t\tif (sort) {\n\t\t\t\t\t\tsorted.put(e.getKey(), e.getValue());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tcols[k] = e.getKey();\n\t\t\t\t\t\tnonZeros[k] = e.getValue();\n\t\t\t\t\t\tk++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (sort) {\n\t\t\t\t\tfor (Map.Entry<Integer, Double> e : sorted.entrySet()) {\n\t\t\t\t\t\tcols[k] = e.getKey();\n\t\t\t\t\t\tnonZeros[k] = e.getValue();\n\t\t\t\t\t\tk++;\n\t\t\t\t\t}\n\t\t\t\t\tsorted.clear();\n\t\t\t\t}\n\t\t\t\tj++;\n\t\t\t}\n\t\t}\n\t\tchoiceStarts[numDistrs] = numTransitions;\n\t\trowStarts[numStates] = numDistrs;\n\t\t// Copy the actions too\n\t\t// Note: could pass 'mdp' or 'this' to convertToSparseStorage (use latter for consistency)\n\t\tactions = mdp.actions.convertToSparseStorage(this);\n\t}\n\n\t/**\n\t * Copy constructor (from MDPSimple). Optionally, transitions within choices\n\t * are sorted (by ascending order of column index). Also, optionally, a state\n\t * index permutation can be provided, i.e. old state index i becomes index permut[i].\n\t * Note: a states list, if present, will not be permuted and should be set\n\t * separately afterwards if required.\n\t * @param mdp The MDP to copy\n\t * @param sort Whether or not to sort column indices\n\t * @param permut State space permutation\n\t */\n\tpublic MDPSparse(MDPSimple<Double> mdp, boolean sort, int permut[])\n\t{\n\t\tint i, j, k;\n\t\tTreeMap<Integer, Double> sorted = null;\n\t\tint permutInv[];\n\t\tinitialise(mdp.getNumStates());\n\t\tcopyFrom(mdp, permut);\n\t\t// Copy stats\n\t\tnumDistrs = mdp.getNumChoices();\n\t\tnumTransitions = mdp.getNumTransitions();\n\t\tmaxNumDistrs = mdp.getMaxNumChoices();\n\t\t// Compute the inverse of the permutation\n\t\tpermutInv = new int[numStates];\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tpermutInv[permut[i]] = i;\n\t\t}\n\t\t// Copy transition function\n\t\tif (sort) {\n\t\t\tsorted = new TreeMap<Integer, Double>();\n\t\t}\n\t\tnonZeros = new double[numTransitions];\n\t\tcols = new int[numTransitions];\n\t\tchoiceStarts = new int[numDistrs + 1];\n\t\trowStarts = new int[numStates + 1];\n\t\tj = k = 0;\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\trowStarts[i] = j;\n\t\t\tfor (Distribution<Double> distr : mdp.trans.get(permutInv[i])) {\n\t\t\t\tchoiceStarts[j] = k;\n\t\t\t\tfor (Map.Entry<Integer, Double> e : distr) {\n\t\t\t\t\tif (sort) {\n\t\t\t\t\t\tsorted.put(permut[e.getKey()], e.getValue());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tcols[k] = (Integer) permut[e.getKey()];\n\t\t\t\t\t\tnonZeros[k] = (Double) e.getValue();\n\t\t\t\t\t\tk++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (sort) {\n\t\t\t\t\tfor (Map.Entry<Integer, Double> e : sorted.entrySet()) {\n\t\t\t\t\t\tcols[k] = (Integer) e.getKey();\n\t\t\t\t\t\tnonZeros[k] = (Double) e.getValue();\n\t\t\t\t\t\tk++;\n\t\t\t\t\t}\n\t\t\t\t\tsorted.clear();\n\t\t\t\t}\n\t\t\t\tj++;\n\t\t\t}\n\t\t}\n\t\tchoiceStarts[numDistrs] = numTransitions;\n\t\trowStarts[numStates] = numDistrs;\n\t\t// Copy the actions too (after permuting)\n\t\t// Note: we pass _this_ new, permuted model to convertToSparseStorage\n\t\tactions = new ChoiceActionsSimple(mdp.actions, permut).convertToSparseStorage(this);\n\t}\n\n\t/**\n\t * Copy constructor for a (sub-)MDP from a given MDP.\n\t * The states and actions will be indexed as given by the order\n\t * of the lists {@code states} and {@code actions}.\n\t * @param mdp MDP to copy from\n\t * @param states States to copy\n\t * @param actions Actions to copy\n\t */\n\tpublic MDPSparse(MDP<Double> mdp, List<Integer> states, List<List<Integer>> actions)\n\t{\n\t\tinitialise(states.size());\n\t\tif (mdp instanceof ActionListOwner) {\n\t\t\tactionList.copyFrom(((ActionListOwner) mdp).getActionList());\n\t\t}\n\t\tfor (int in : mdp.getInitialStates()) {\n\t\t\taddInitialState(in);\n\t\t}\n\t\tfor (int dl : mdp.getDeadlockStates()) {\n\t\t\taddDeadlockState(dl);\n\t\t}\n\t\tstatesList = new ArrayList<State>();\n\t\tfor (int s : states) {\n\t\t\tstatesList.add(mdp.getStatesList().get(s));\n\t\t}\n\t\tnumDistrs = 0;\n\t\tnumTransitions = 0;\n\t\tmaxNumDistrs = 0;\n\t\tfor (int i = 0; i < states.size(); i++) {\n\t\t\tint s = states.get(i);\n\t\t\tfinal int numChoices = actions.get(s).size();\n\t\t\tnumDistrs += numChoices;\n\t\t\tif (numChoices > maxNumDistrs) {\n\t\t\t\tmaxNumDistrs = numChoices;\n\t\t\t}\n\t\t\tfor (int a : actions.get(s)) {\n\t\t\t\tnumTransitions += mdp.getNumTransitions(s, a);\n\t\t\t}\n\t\t}\n\t\tnonZeros = new double[numTransitions];\n\t\tcols = new int[numTransitions];\n\t\tchoiceStarts = new int[numDistrs + 1];\n\t\trowStarts = new int[numStates + 1];\n\t\tthis.actions = new Object[numDistrs];\n\t\tint choiceIndex = 0;\n\t\tint colIndex = 0;\n\t\tint[] reverseStates = new int[mdp.getNumStates()];\n\t\tfor (int i = 0; i < states.size(); i++) {\n\t\t\treverseStates[states.get(i)] = i;\n\t\t}\n\t\tfor (int i = 0; i < states.size(); i++) {\n\t\t\tint s = states.get(i);\n\t\t\trowStarts[i] = choiceIndex;\n\t\t\tfor (int a : actions.get(s)) {\n\t\t\t\tchoiceStarts[choiceIndex] = colIndex;\n\t\t\t\tthis.actions[choiceIndex] = mdp.getAction(s, a);\n\t\t\t\tchoiceIndex++;\n\t\t\t\tIterator<Entry<Integer, Double>> it = mdp.getTransitionsIterator(s, a);\n\t\t\t\twhile (it.hasNext()) {\n\t\t\t\t\tEntry<Integer, Double> next = it.next();\n\t\t\t\t\tcols[colIndex] = reverseStates[next.getKey()];\n\t\t\t\t\tnonZeros[colIndex] = next.getValue();\n\t\t\t\t\tcolIndex++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tchoiceStarts[numDistrs] = numTransitions;\n\t\trowStarts[numStates] = numDistrs;\n\t}\n\n\t/**\n\t * Construct an empty MDP (e.g. for subsequent explicit import)\n\t */\n\tpublic MDPSparse()\n\t{\n\t}\n\n\t// Mutators (other)\n\n\t@Override\n\tpublic void initialise(int numStates)\n\t{\n\t\tsuper.initialise(numStates);\n\t\tnumDistrs = numTransitions = maxNumDistrs = 0;\n\t\tactions = null;\n\t}\n\n\t@Override\n\tpublic void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\tinitialise(modelImporter.getNumStates());\n\t\tnumDistrs = modelImporter.getNumChoices();\n\t\tnumTransitions = modelImporter.getNumTransitions();\n\t\trowStarts = new int[numStates + 1];\n\t\tchoiceStarts = new int[numDistrs + 1];\n\t\tcols = new int[numTransitions];\n\t\tnonZeros = new double[numTransitions];\n\t\tactions = new Object[numDistrs];\n\t\tIOUtils.MDPTransitionConsumer<Double> cons = new IOUtils.MDPTransitionConsumer<>() {\n\t\t\tint sLast = -1;\n\t\t\tint iLast = -1;\n\t\t\tint count = 0;\n\t\t\tint countCh = 0;\n\n\t\t\t@Override\n\t\t\tpublic void accept(int s, int i, int s2, Double d, Object a) throws PrismException\n\t\t\t{\n\t\t\t\tif (s < sLast) {\n\t\t\t\t\tthrow new PrismException(\"Imported states/transitions must be in ascending order\");\n\t\t\t\t}\n\t\t\t\tif (s != sLast) {\n\t\t\t\t\trowStarts[s] = countCh;\n\t\t\t\t\tsLast = s;\n\t\t\t\t\tiLast = -1;\n\t\t\t\t}\n\t\t\t\tif (i < iLast) {\n\t\t\t\t\tthrow new PrismException(\"Imported states/transitions must be in ascending order\");\n\t\t\t\t}\n\t\t\t\tif (i != iLast) {\n\t\t\t\t\tchoiceStarts[countCh] = count;\n\t\t\t\t\tactions[countCh] = a;\n\t\t\t\t\tcountCh++;\n\t\t\t\t\tiLast = i;\n\t\t\t\t}\n\t\t\t\tcols[count] = s2;\n\t\t\t\tnonZeros[count] = d;\n\t\t\t\tcount++;\n\t\t\t}\n\t\t};\n\t\trowStarts[numStates] = numDistrs;\n\t\tchoiceStarts[numDistrs] = numTransitions;\n\t\tmodelImporter.extractMDPTransitions(cons);\n\t\tactionList.markNeedsRecomputing();\n\t\t// Compute maxNumDistrs\n\t\tmaxNumDistrs = 0;\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tmaxNumDistrs = Math.max(maxNumDistrs, getNumChoices(s));\n\t\t}\n\t}\n\n\t// Accessors (for Model)\n\n\t@Override\n\tpublic List<Object> findActionsUsed()\n\t{\n\t\tif (actions == null) {\n\t\t\treturn Collections.singletonList(null);\n\t\t} else {\n\t\t\tLinkedHashSet<Object> allActions = new LinkedHashSet<>();\n\t\t\tint n = actions.length;\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tallActions.add(actions[i]);\n\t\t\t}\n\t\t\treturn new ArrayList<>(allActions);\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean onlyNullActionUsed()\n\t{\n\t\treturn actions == null;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions()\n\t{\n\t\treturn numTransitions;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s)\n\t{\n\t\treturn choiceStarts[rowStarts[s + 1]] - choiceStarts[rowStarts[s]];\n\t}\n\n\tprivate SuccessorsIterator colsIterator(int start, int end, boolean distinct)\n\t{\n\t\treturn new SuccessorsIterator() {\n\t\t\tint cur = start;\n\n\t\t\t@Override\n\t\t\tpublic boolean successorsAreDistinct()\n\t\t\t{\n\t\t\t\treturn distinct;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn cur < end;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\treturn cols[cur++];\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(final int s)\n\t{\n\t\t// Assumes that only non-zero entries are stored\n\t\tint start = choiceStarts[rowStarts[s]];\n\t\tint end = choiceStarts[rowStarts[s + 1]];\n\t\t// we can guarantee that the successors are distinct if there is at most one successor...\n\t\tboolean distinct = (start == end || start + 1 == end);\n\t\treturn colsIterator(start, end, distinct);\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t// Note that no distributions is a deadlock, not an empty distribution\n\t\t\tif (getNumChoices(i) == 0) {\n\t\t\t\taddDeadlockState(i);\n\t\t\t\tif (fix) {\n\t\t\t\t\tthrow new PrismException(\"Can't fix deadlocks in an MDPSparse since it cannot be modified after construction\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (getNumChoices(i) == 0 && (except == null || !except.get(i)))\n\t\t\t\tthrow new PrismException(\"MDP has a deadlock in state \" + i);\n\t\t}\n\t}\n\n\t// Accessors (for NondetModel)\n\n\t@Override\n\tpublic int getNumChoices(int s)\n\t{\n\t\treturn rowStarts[s + 1] - rowStarts[s];\n\t}\n\n\t@Override\n\tpublic int getMaxNumChoices()\n\t{\n\t\treturn maxNumDistrs;\n\t}\n\n\t@Override\n\tpublic int getNumChoices()\n\t{\n\t\treturn numDistrs;\n\t}\n\n\t@Override\n\tpublic Object getAction(int s, int i)\n\t{\n\t\treturn i < 0 || actions == null ? null : actions[rowStarts[s] + i];\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(final int s, final int i)\n\t{\n\t\tint start = choiceStarts[rowStarts[s] + i];\n\t\tint end = choiceStarts[rowStarts[s] + i + 1];\n\t\t// we assume here that the successors for a single choice are distinct\n\t\treturn colsIterator(start, end, true);\n\t}\n\n\t// Accessors (for MDP)\n\n\t@Override\n\tpublic int getNumTransitions(int s, int i)\n\t{\n\t\treturn choiceStarts[rowStarts[s] + i + 1] - choiceStarts[rowStarts[s] + i];\n\t}\n\n\t@Override\n\tpublic void forEachTransition(int s, int i, TransitionConsumer<Double> c)\n\t{\n\t\tfor (int col = choiceStarts[rowStarts[s] + i], stop = choiceStarts[rowStarts[s] + i + 1]; col < stop; col++) {\n\t\t\tc.accept(s, cols[col], nonZeros[col]);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void forEachDoubleTransition(int s, int i, DoubleTransitionConsumer c)\n\t{\n\t\tfor (int col = choiceStarts[rowStarts[s] + i], stop = choiceStarts[rowStarts[s] + i + 1]; col < stop; col++) {\n\t\t\tc.accept(s, cols[col], nonZeros[col]);\n\t\t}\n\t}\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Double>> getTransitionsIterator(final int s, final int i)\n\t{\n\t\treturn new Iterator<Entry<Integer, Double>>()\n\t\t{\n\t\t\tfinal int start = choiceStarts[rowStarts[s] + i];\n\t\t\tint col = start;\n\t\t\tfinal int end = choiceStarts[rowStarts[s] + i + 1];\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn col < end;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Entry<Integer, Double> next()\n\t\t\t{\n\t\t\t\tassert (col < end);\n\t\t\t\tfinal int i = col;\n\t\t\t\tcol++;\n\t\t\t\treturn new AbstractMap.SimpleImmutableEntry<Integer, Double>(cols[i], nonZeros[i]);\n\t\t\t}\n\t\t};\n\t}\n\n\t@Override\n\tpublic void prob0step(BitSet subset, BitSet u, boolean forall, BitSet result)\n\t{\n\t\tint j, k, l1, h1, l2, h2;\n\t\tboolean b1, some;\n\t\tfor (int i : new IterableStateSet(subset, numStates)) {\n\t\t\tb1 = forall; // there exists or for all\n\t\t\tl1 = rowStarts[i];\n\t\t\th1 = rowStarts[i + 1];\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\tsome = false;\n\t\t\t\tl2 = choiceStarts[j];\n\t\t\t\th2 = choiceStarts[j + 1];\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// Assume that only non-zero entries are stored\n\t\t\t\t\tif (u.get(cols[k])) {\n\t\t\t\t\t\tsome = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (forall) {\n\t\t\t\t\tif (!some) {\n\t\t\t\t\t\tb1 = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (some) {\n\t\t\t\t\t\tb1 = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.set(i, b1);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void prob1Astep(BitSet subset, BitSet u, BitSet v, BitSet result)\n\t{\n\t\tint j, k, l1, h1, l2, h2;\n\t\tboolean b1, some, all;\n\t\tfor (int i : new IterableStateSet(subset, numStates)) {\n\t\t\tb1 = true;\n\t\t\tl1 = rowStarts[i];\n\t\t\th1 = rowStarts[i + 1];\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\tsome = false;\n\t\t\t\tall = true;\n\t\t\t\tl2 = choiceStarts[j];\n\t\t\t\th2 = choiceStarts[j + 1];\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// Assume that only non-zero entries are stored\n\t\t\t\t\tif (!u.get(cols[k])) {\n\t\t\t\t\t\tall = false;\n\t\t\t\t\t\tbreak; // Stop early (already know b1 will be set to false)\n\t\t\t\t\t}\n\t\t\t\t\tif (v.get(cols[k])) {\n\t\t\t\t\t\tsome = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (!(some && all)) {\n\t\t\t\t\tb1 = false;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.set(i, b1);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void prob1Estep(BitSet subset, BitSet u, BitSet v, BitSet result, int strat[])\n\t{\n\t\tint j, k, l1, h1, l2, h2, stratCh = -1;\n\t\tboolean b1, some, all;\n\t\tfor (int i : new IterableStateSet(subset, numStates)) {\n\t\t\tb1 = false;\n\t\t\tl1 = rowStarts[i];\n\t\t\th1 = rowStarts[i + 1];\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\tsome = false;\n\t\t\t\tall = true;\n\t\t\t\tl2 = choiceStarts[j];\n\t\t\t\th2 = choiceStarts[j + 1];\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// Assume that only non-zero entries are stored\n\t\t\t\t\tif (!u.get(cols[k])) {\n\t\t\t\t\t\tall = false;\n\t\t\t\t\t\tbreak; // Stop early (already know b1 will not be set to true)\n\t\t\t\t\t}\n\t\t\t\t\tif (v.get(cols[k])) {\n\t\t\t\t\t\tsome = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (some && all) {\n\t\t\t\t\tb1 = true;\n\t\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\t\tif (strat != null)\n\t\t\t\t\t\tstratCh = j - l1;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// If strategy generation is enabled, store optimal choice\n\t\t\t// (only if this the first time we add the state to S^yes)\n\t\t\tif (strat != null & b1 & !result.get(i)) {\n\t\t\t\tstrat[i] = stratCh;\n\t\t\t}\n\t\t\t// Store result\n\t\t\tresult.set(i, b1);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void prob1step(BitSet subset, BitSet u, BitSet v, boolean forall, BitSet result)\n\t{\n\t\tint j, k, l1, h1, l2, h2;\n\t\tboolean b1, some, all;\n\t\tfor (int i : new IterableStateSet(subset, numStates)) {\n\t\t\tb1 = forall; // there exists or for all\n\t\t\tl1 = rowStarts[i];\n\t\t\th1 = rowStarts[i + 1];\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\tsome = false;\n\t\t\t\tall = true;\n\t\t\t\tl2 = choiceStarts[j];\n\t\t\t\th2 = choiceStarts[j + 1];\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// Assume that only non-zero entries are stored\n\t\t\t\t\tif (v.get(cols[k])) {\n\t\t\t\t\t\tsome = true;\n\t\t\t\t\t}\n\t\t\t\t\tif (!u.get(cols[k])) {\n\t\t\t\t\t\tall = false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (forall) {\n\t\t\t\t\tif (!(some && all)) {\n\t\t\t\t\t\tb1 = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (some && all) {\n\t\t\t\t\t\tb1 = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.set(i, b1);\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean prob1stepSingle(int s, int i, BitSet u, BitSet v)\n\t{\n\t\tint j, k, l2, h2;\n\t\tboolean some, all;\n\n\t\tj = rowStarts[s] + i;\n\t\tsome = false;\n\t\tall = true;\n\t\tl2 = choiceStarts[j];\n\t\th2 = choiceStarts[j + 1];\n\t\tfor (k = l2; k < h2; k++) {\n\t\t\t// Assume that only non-zero entries are stored\n\t\t\tif (v.get(cols[k])) {\n\t\t\t\tsome = true;\n\t\t\t}\n\t\t\tif (!u.get(cols[k])) {\n\t\t\t\tall = false;\n\t\t\t}\n\t\t}\n\t\treturn some && all;\n\t}\n\n\t@Override\n\tpublic double mvMultMinMaxSingle(int s, double vect[], boolean min, int strat[])\n\t{\n\t\tint j, k, l1, h1, l2, h2, stratCh = -1;\n\t\tdouble d, minmax;\n\t\tboolean first;\n\n\t\tminmax = 0;\n\t\tfirst = true;\n\t\tl1 = rowStarts[s];\n\t\th1 = rowStarts[s + 1];\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\t// Compute sum for this distribution\n\t\t\td = 0.0;\n\t\t\tl2 = choiceStarts[j];\n\t\t\th2 = choiceStarts[j + 1];\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t\t}\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null)\n\t\t\t\t\tstratCh = j - l1;\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null & !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\t@Override\n\tpublic List<Integer> mvMultMinMaxSingleChoices(int s, double vect[], boolean min, double val)\n\t{\n\t\tint j, k, l1, h1, l2, h2;\n\t\tdouble d;\n\t\tList<Integer> res;\n\n\t\t// Create data structures to store strategy\n\t\tres = new ArrayList<Integer>();\n\t\t// One row of matrix-vector operation\n\t\tl1 = rowStarts[s];\n\t\th1 = rowStarts[s + 1];\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\t// Compute sum for this distribution\n\t\t\td = 0.0;\n\t\t\tl2 = choiceStarts[j];\n\t\t\th2 = choiceStarts[j + 1];\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t\t}\n\t\t\t// Store strategy info if value matches\n\t\t\tif (PrismUtils.doublesAreEqual(val, d)) {\n\t\t\t\tres.add(j - l1);\n\t\t\t}\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t@Override\n\tpublic double mvMultSingle(int s, int i, double vect[])\n\t{\n\t\tint j, k, l2, h2;\n\t\tdouble d;\n\n\t\tj = rowStarts[s] + i;\n\t\t// Compute sum for this distribution\n\t\td = 0.0;\n\t\tl2 = choiceStarts[j];\n\t\th2 = choiceStarts[j + 1];\n\t\tfor (k = l2; k < h2; k++) {\n\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t}\n\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double mvMultJacMinMaxSingle(int s, double vect[], boolean min, int strat[])\n\t{\n\t\tint j, k, l1, h1, l2, h2, stratCh = -1;\n\t\tdouble diag, d, minmax;\n\t\tboolean first;\n\n\t\tminmax = 0;\n\t\tfirst = true;\n\t\tl1 = rowStarts[s];\n\t\th1 = rowStarts[s + 1];\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\tdiag = 1.0;\n\t\t\t// Compute sum for this distribution\n\t\t\td = 0.0;\n\t\t\tl2 = choiceStarts[j];\n\t\t\th2 = choiceStarts[j + 1];\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\tif (cols[k] != s) {\n\t\t\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t\t\t} else {\n\t\t\t\t\tdiag -= nonZeros[k];\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (diag > 0)\n\t\t\t\td /= diag;\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null)\n\t\t\t\t\tstratCh = j - l1;\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null & !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\t@Override\n\tpublic double mvMultJacSingle(int s, int i, double vect[])\n\t{\n\t\tint j, k, l2, h2;\n\t\tdouble diag, d;\n\n\t\tj = rowStarts[s] + i;\n\t\tdiag = 1.0;\n\t\t// Compute sum for this distribution\n\t\td = 0.0;\n\t\tl2 = choiceStarts[j];\n\t\th2 = choiceStarts[j + 1];\n\t\tfor (k = l2; k < h2; k++) {\n\t\t\tif (cols[k] != s) {\n\t\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t\t} else {\n\t\t\t\tdiag -= nonZeros[k];\n\t\t\t}\n\t\t}\n\t\tif (diag > 0)\n\t\t\td /= diag;\n\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double mvMultRewMinMaxSingle(int s, double vect[], MDPRewards<Double> mdpRewards, boolean min, int strat[])\n\t{\n\t\tint j, k, l1, h1, l2, h2, stratCh = -1;\n\t\tdouble d, minmax;\n\t\tboolean first;\n\n\t\tminmax = 0;\n\t\tfirst = true;\n\t\tl1 = rowStarts[s];\n\t\th1 = rowStarts[s + 1];\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\t// Compute sum for this distribution\n\t\t\td = mdpRewards.getTransitionReward(s, j - l1);\n\t\t\tl2 = choiceStarts[j];\n\t\t\th2 = choiceStarts[j + 1];\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t\t}\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null)\n\t\t\t\t\tstratCh = j - l1;\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// Add state reward (doesn't affect min/max)\n\t\tminmax += mdpRewards.getStateReward(s);\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null & !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\t@Override\n\tpublic double mvMultRewSingle(int s, int i, double[] vect, MCRewards<Double> mcRewards)\n\t{\n\t\tint j, k, l2, h2;\n\t\tdouble d;\n\n\t\tj = rowStarts[s] + i;\n\t\t// Compute sum for this distribution\n\t\t// TODO: use transition rewards when added to DTMCss\n\t\t// d = mcRewards.getTransitionReward(s);\n\t\td = 0;\n\t\tl2 = choiceStarts[j];\n\t\th2 = choiceStarts[j + 1];\n\t\tfor (k = l2; k < h2; k++) {\n\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t}\n\t\td += mcRewards.getStateReward(s);\n\t\treturn d;\n\t}\n\t\n\t@Override\n\tpublic double mvMultRewJacMinMaxSingle(int s, double vect[], MDPRewards<Double> mdpRewards, boolean min, int strat[])\n\t{\n\t\tint j, k, l1, h1, l2, h2, stratCh = -1;\n\t\tdouble diag, d, minmax;\n\t\tboolean first;\n\n\t\tminmax = 0;\n\t\tfirst = true;\n\t\tl1 = rowStarts[s];\n\t\th1 = rowStarts[s + 1];\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\tdiag = 1.0;\n\t\t\tboolean onlySelfloops = true;\n\t\t\t// Compute sum for this distribution\n\t\t\t// (note: have to add state rewards in the loop for Jacobi)\n\t\t\td = mdpRewards.getStateReward(s);\n\t\t\td += mdpRewards.getTransitionReward(s, j - l1);\n\t\t\tl2 = choiceStarts[j];\n\t\t\th2 = choiceStarts[j + 1];\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\tif (cols[k] != s) {\n\t\t\t\t\tonlySelfloops = false;\n\t\t\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t\t\t} else {\n\t\t\t\t\tdiag -= nonZeros[k];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Catch special case of probability 1 self-loop (Jacobi does it wrong)\n\t\t\tif (onlySelfloops) {\n\t\t\t\tif (d != 0) {\n\t\t\t\t\t// always choosing the selfloop-action will produce infinite reward\n\t\t\t\t\td = (d>0 ? Double.POSITIVE_INFINITY : Double.NEGATIVE_INFINITY);\n\t\t\t\t} else {\n\t\t\t\t\t// no reward & only self-loops: d remains 0\n\t\t\t\t\td = 0;\n\t\t\t\t}\n\t\t\t} else if (diag > 0) {\n\t\t\t\t// not only self-loops, do Jacobi division\n\t\t\t\td /= diag;\n\t\t\t}\n\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null)\n\t\t\t\t\tstratCh = j - l1;\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null & !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\t@Override\n\tpublic List<Integer> mvMultRewMinMaxSingleChoices(int s, double vect[], MDPRewards<Double> mdpRewards, boolean min, double val)\n\t{\n\t\tint j, k, l1, h1, l2, h2;\n\t\tdouble d;\n\t\tList<Integer> res;\n\n\t\t// Create data structures to store strategy\n\t\tres = new ArrayList<Integer>();\n\t\t// One row of matrix-vector operation\n\t\tl1 = rowStarts[s];\n\t\th1 = rowStarts[s + 1];\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\t// Compute sum for this distribution\n\t\t\td = mdpRewards.getTransitionReward(s, j - l1);\n\t\t\tl2 = choiceStarts[j];\n\t\t\th2 = choiceStarts[j + 1];\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\td += nonZeros[k] * vect[cols[k]];\n\t\t\t}\n\t\t\td += mdpRewards.getStateReward(s);\n\t\t\t// Store strategy info if value matches\n\t\t\tif (PrismUtils.doublesAreEqual(val, d)) {\n\t\t\t\tres.add(j - l1);\n\t\t\t}\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t@Override\n\tpublic void mvMultRight(int[] states, int[] strat, double[] source, double[] dest)\n\t{\n\t\tfor (int s : states) {\n\t\t\tint j, l2, h2;\n\t\t\tint k = strat[s];\n\t\t\tj = rowStarts[s] + k;\n\t\t\tl2 = choiceStarts[j];\n\t\t\th2 = choiceStarts[j + 1];\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\tdest[cols[k]] += nonZeros[k] * source[s];\n\t\t\t}\n\t\t}\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn toStringMDP();\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof MDPSparse))\n\t\t\treturn false;\n\t\tMDPSparse mdp = (MDPSparse) o;\n\t\tif (numStates != mdp.numStates)\n\t\t\treturn false;\n\t\tif (!initialStates.equals(mdp.initialStates))\n\t\t\treturn false;\n\t\tif (!Utils.doubleArraysAreEqual(nonZeros, mdp.nonZeros))\n\t\t\treturn false;\n\t\tif (!Utils.intArraysAreEqual(cols, mdp.cols))\n\t\t\treturn false;\n\t\tif (!Utils.intArraysAreEqual(choiceStarts, mdp.choiceStarts))\n\t\t\treturn false;\n\t\tif (!Utils.intArraysAreEqual(rowStarts, mdp.rowStarts))\n\t\t\treturn false;\n\t\t// TODO: compare actions (complicated: null = null,null,null,...)\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/MinMax.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\n/**\n * Class to store info about types of probabilities that are to be computed\n * (typically how to quantify over strategies, e.g. \"min\" or \"max\"). \n */\npublic class MinMax\n{\n\t/** How players are quantified over? **/\n\tprotected int numPlayers;\n\t/** Is quantification over (epistemic) uncertainty included? */\n\tprotected boolean unc;\n\n\t/**\n\t * Create a blank MinMax object\n\t */\n\tpublic MinMax()\n\t{\n\t}\n\n\t/**\n\t * Copy constructor\n\t */\n\tpublic MinMax(MinMax other)\n\t{\n\t\tthis.numPlayers = other.numPlayers;\n\t\tthis.unc = other.unc;\n\t\tthis.min = other.min;\n\t\tthis.min1 = other.min1;\n\t\tthis.min2 = other.min2;\n\t\tthis.minUnc = other.minUnc;\n\t}\n\n\t// Info about quantification over a single class of strategies/adversaries\n\n\t/** Min (true) or max (false) over strategies? */\n\tprotected boolean min;\n\t\n\tpublic MinMax setMin(boolean min)\n\t{\n\t\tnumPlayers = 1;\n\t\tthis.min = min;\n\t\treturn this;\n\t}\n\t\n\tpublic boolean isMin()\n\t{\n\t\treturn min;\n\t}\n\t\n\tpublic boolean isMax()\n\t{\n\t\treturn !min;\n\t}\n\t\n\t// Info about quantification over a two classes of strategies (e.g. for 2-player games)\n\n\t/** Min (true) or max (false) over strategies for player 1? */\n\tprotected boolean min1;\n\t/** Min (true) or max (false) over strategies for player 2? */\n\tprotected boolean min2;\n\t\n\tpublic MinMax setMinMin(boolean min1, boolean min2)\n\t{\n\t\tnumPlayers = 2;\n\t\tthis.min1 = min1;\n\t\tthis.min2 = min2;\n\t\treturn this;\n\t}\n\t\n\tpublic boolean isMin1()\n\t{\n\t\treturn min1;\n\t}\n\t\n\tpublic boolean isMin2()\n\t{\n\t\treturn min2;\n\t}\n\t\n\t// Additional info about quantification over uncertainty\n\n\t/** Min (true) or max (false) over epistemic uncertainty? */\n\tprotected boolean minUnc;\n\t\n\tpublic MinMax setMinUnc(boolean minUnc)\n\t{\n\t\tunc = true;\n\t\tthis.minUnc = minUnc;\n\t\treturn this;\n\t}\n\t\n\tpublic boolean isMinUnc()\n\t{\n\t\treturn minUnc;\n\t}\n\t\n\tpublic boolean isMaxUnc()\n\t{\n\t\treturn !minUnc;\n\t}\n\t\n\t// Create a new instance by applying some operation\n\t\n\tpublic MinMax negate()\n\t{\n\t\tMinMax neg = new MinMax();\n\t\tif (numPlayers == 1) {\n\t\t\tneg.setMin(!isMin());\n\t\t} else if (numPlayers == 2) {\n\t\t\tneg.setMinMin(!isMin1(), !isMin2());\n\t\t}\n\t\tif (unc) {\n\t\t\tneg.setMinUnc(!isMinUnc());\n\t\t}\n\t\treturn neg;\n\t}\n\t\n\t// Utility methods to create instances of this class\n\t\n\tpublic static MinMax blank()\n\t{\n\t\treturn new MinMax();\n\t}\n\t\n\tpublic static MinMax min()\n\t{\n\t\treturn new MinMax().setMin(true);\n\t}\n\t\n\tpublic static MinMax max()\n\t{\n\t\treturn new MinMax().setMin(false);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tif (numPlayers == 1) {\n\t\t\ts += min ? \"min\" : \"max\";\n\t\t} else if (numPlayers == 2) {\n\t\t\ts += min1 ? \"min\" : \"max\";\n\t\t\ts += min2 ? \"min\" : \"max\";\n\t\t}\n\t\tif (unc) {\n\t\t\ts += minUnc ? \"min\" : \"max\";\n\t\t}\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/Model.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.PrimitiveIterator;\nimport java.util.Set;\nimport java.util.TreeMap;\nimport java.util.function.IntPredicate;\n\nimport common.IterableStateSet;\nimport common.IteratorTools;\nimport io.DotExporter;\nimport io.ModelExportOptions;\nimport io.PrismExplicitExporter;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport prism.Evaluator;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\nimport prism.PrismUtils;\n\nimport static prism.PrismSettings.DEFAULT_EXPORT_MODEL_PRECISION;\n\n/**\n * Interface for (abstract) classes that provide (read-only) access to an explicit-state model.\n * This is generic, where probabilities/rates/etc. are of type {@code Value}.\n */\npublic interface Model<Value> extends prism.Model<Value>\n{\n\t// Accessors\n\n\t/**\n\t * Get iterator over initial state list.\n\t */\n\tIterable<Integer> getInitialStates();\n\n\t/**\n\t * Get the index of the first initial state\n\t * (i.e. the one with the lowest index).\n\t * Returns -1 if there are no initial states.\n\t */\n\tint getFirstInitialState();\n\n\t/**\n\t * Check whether a state is an initial state.\n\t */\n\tboolean isInitialState(int i);\n\n\t/**\n\t * Get the number of states that are/were deadlocks.\n\t * (Such states may have been fixed at build-time by adding self-loops)\n\t */\n\tint getNumDeadlockStates();\n\n\t/**\n\t * Get iterator over states that are/were deadlocks.\n\t * (Such states may have been fixed at build-time by adding self-loops)\n\t */\n\tIterable<Integer> getDeadlockStates();\n\t\n\t/**\n\t * Get list of states that are/were deadlocks.\n\t * (Such states may have been fixed at build-time by adding self-loops)\n\t */\n\tStateValues getDeadlockStatesList();\n\t\n\t/**\n\t * Get the index of the first state that is/was a deadlock.\n\t * (i.e. the one with the lowest index).\n\t * Returns -1 if there are no initial states.\n\t */\n\tint getFirstDeadlockState();\n\n\t/**\n\t * Check whether a state is/was deadlock.\n\t * (Such states may have been fixed at build-time by adding self-loops)\n\t */\n\tboolean isDeadlockState(int i);\n\t\n\t/**\n\t * Get access to a list of states (optionally stored).\n\t */\n\tList<State> getStatesList();\n\n\t/** Get access to the VarList (optionally stored) */\n\tVarList getVarList();\n\n\t/**\n\t * Get access to a list of constant values (optionally stored).\n\t */\n\tValues getConstantValues();\n\t\n\t/**\n\t * Get the states that satisfy a label in this model (optionally stored).\n\t * Returns null if there is no label of this name.\n\t */\n\tBitSet getLabelStates(String name);\n\t\n\t/**\n\t * Get the labels that are (optionally) stored.\n\t * Returns an empty set if there are no labels.\n\t */\n\tSet<String> getLabels();\n\n\t/**\n\t * Returns true if a label with the given name is attached to this model\n\t */\n\tboolean hasLabel(String name);\n\n\t/**\n\t * Get the mapping from labels that are (optionally) stored\n\t * to the sets of states that satisfy them.\n\t */\n\tdefault Map<String, BitSet> getLabelToStatesMap()\n\t{\n\t\t// Default implementation creates a new map on demand\n\t\tMap<String, BitSet> labels = new TreeMap<>();\n\t\tfor (String name : getLabels()) {\n\t\t\tlabels.put(name, getLabelStates(name));\n\t\t}\n\t\treturn labels;\n\t}\n\t\n\t@Override\n\tdefault int getNumTransitions()\n\t{\n\t\tint numStates = getNumStates();\n\t\tint numTransitions = 0;\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tnumTransitions += getNumTransitions(s);\n\t\t}\n\t\treturn numTransitions;\n\t}\n\n\t/**\n\t * Get the number of transitions from state s.\n\t */\n\tdefault int getNumTransitions(int s)\n\t{\n\t\treturn Math.toIntExact(IteratorTools.count(getSuccessorsIterator(s)));\n\t}\n\n\t/**\n\t * Get the number of transitions leaving a set of states.\n\t * <br>\n\t * Default implementation: Iterator over the states and sum the result of getNumTransitions(s).\n\t * @param states The set of states, specified by an OfInt iterator\n\t * @return the number of transitions\n\t */\n\tdefault long getNumTransitions(PrimitiveIterator.OfInt states)\n\t{\n\t\tlong count = 0;\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tcount += getNumTransitions(s);\n\t\t}\n\t\treturn count;\n\t}\n\n\t/**\n\t * Get an iterator over the successors of state s.\n\t * Default implementation via the SuccessorsIterator returned\n\t * from {@code getSuccessors}, ensuring that there are no\n\t * duplicates.\n\t */\n\tdefault Iterator<Integer> getSuccessorsIterator(int s)\n\t{\n\t\tSuccessorsIterator successors = getSuccessors(s);\n\t\treturn successors.distinct();\n\t}\n\n\t/**\n\t * Get a SuccessorsIterator for state s.\n\t */\n\tSuccessorsIterator getSuccessors(int s);\n\n\t/**\n\t * Returns true if state s2 is a successor of state s1.\n\t */\n\tdefault boolean isSuccessor(int s1, int s2)\n\t{\n\t\t// the code for this method is equivalent to the following stream expression,\n\t\t// but kept explicit for performance\n\t\t//\n\t\t// return getSuccessors(s1).stream().anyMatch(\n\t\t//           (t) -> {return t == s2;}\n\t\t// );\n\n\t\tSuccessorsIterator it = getSuccessors(s1);\n\t\twhile (it.hasNext()) {\n\t\t\tint t = it.nextInt();\n\t\t\tif (t == s2)\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Check if all the successor states of a state are in a set.\n\t * @param s The state to check\n\t * @param set The set to test for inclusion\n\t */\n\tdefault boolean allSuccessorsInSet(int s, BitSet set)\n\t{\n\t\treturn allSuccessorsMatch(s, set::get);\n\t}\n\n\t/**\n\t * Check if any successor states of a state are in a set.\n\t * @param s The state to check\n\t * @param set The set to test for inclusion\n\t */\n\tdefault boolean someSuccessorsInSet(int s, BitSet set)\n\t{\n\t\treturn someSuccessorsMatch(s, set::get);\n\t}\n\n\t/**\n\t * Check if all the successor states of a state match the predicate.\n\t * @param s The state to check\n\t * @param p the predicate\n\t */\n\tdefault boolean allSuccessorsMatch(int s, IntPredicate p)\n\t{\n\t\t// the code for this method is equivalent to the following stream expression,\n\t\t// but kept explicit for performance\n\t\t//\n\t\t// return getSuccessors(s).stream().allMatch(p);\n\n\t\tSuccessorsIterator it = getSuccessors(s);\n\t\twhile (it.hasNext()) {\n\t\t\tint t = it.nextInt();\n\t\t\tif (!p.test(t))\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Check if any successor states of a state match the predicate.\n\t * @param s The state to check\n\t * @param p the predicate\n\t */\n\tdefault boolean someSuccessorsMatch(int s, IntPredicate p)\n\t{\n\t\t// the code for this method is equivalent to the following stream expression,\n\t\t// but kept explicit for performance\n\t\t//\n\t\t// return getSuccessors(s).stream().anyMatch(p);\n\n\t\tSuccessorsIterator it = getSuccessors(s);\n\t\twhile (it.hasNext()) {\n\t\t\tint t = it.nextInt();\n\t\t\tif (p.test(t))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob0 for a single state,\n\t * i.e., for the state {@code s} returns true iff there is a transition from\n\t * {@code s} to a state in {@code u}.\n\t * <br>\n\t * <i>Default implementation</i>: Iterates using {@code getSuccessors()} and performs the check.\n\t * @param s The state in question\n\t * @param u Set of states {@code u}\n\t * @return true iff there is a transition from s to a state in u\n\t */\n\tdefault boolean prob0step(int s, BitSet u)\n\t{\n\t\tfor (SuccessorsIterator succ = getSuccessors(s); succ.hasNext(); ) {\n\t\t\tint t = succ.nextInt();\n\t\t\tif (u.get(t))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob0, i.e., for states i in {@code subset},\n\t * set bit i of {@code result} iff there is a transition to a state in {@code u}.\n\t * <br>\n\t * <i>Default implementation</i>: Iterate over {@code subset} and use {@code prob0step(s,u)}\n\t * to determine result for {@code s}.\n\t * @param subset Only compute for these states\n\t * @param u Set of states {@code u}\n\t * @param result Store results here\n\t */\n\tdefault void prob0step(BitSet subset, BitSet u, BitSet result)\n\t{\n\t\tfor (PrimitiveIterator.OfInt it = new IterableStateSet(subset, getNumStates()).iterator(); it.hasNext();) {\n\t\t\tint s = it.nextInt();\n\t\t\tresult.set(s, prob0step(s,u));\n\t\t}\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob1 for a single state,\n\t * i.e., for states s return true iff there is a transition to a state in\n\t * {@code v} and all transitions go to states in {@code u}.\n\t * @param s The state in question\n\t * @param u Set of states {@code u}\n\t * @param v Set of states {@code v}\n\t * @return true iff there is a transition from s to a state in v and all transitions go to u.\n\t */\n\tdefault boolean prob1step(int s, BitSet u, BitSet v)\n\t{\n\t\tboolean allTransitionsToU = true;\n\t\tboolean hasTransitionToV = false;\n\t\tfor (SuccessorsIterator succ = getSuccessors(s); succ.hasNext(); ) {\n\t\t\tint t = succ.nextInt();\n\t\t\tif (!u.get(t)) {\n\t\t\t\tallTransitionsToU = false;\n\t\t\t\t// early abort, as overall result is false\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\thasTransitionToV = hasTransitionToV || v.get(t);\n\t\t}\n\t\treturn (allTransitionsToU && hasTransitionToV);\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob1, i.e., for states i in {@code subset},\n\t * set bit i of {@code result} iff there is a transition to a state in {@code v} and all transitions go to states in {@code u}.\n\t * @param subset Only compute for these states\n\t * @param u Set of states {@code u}\n\t * @param v Set of states {@code v}\n\t * @param result Store results here\n\t */\n\tdefault void prob1step(BitSet subset, BitSet u, BitSet v, BitSet result)\n\t{\n\t\tfor (PrimitiveIterator.OfInt it = new IterableStateSet(subset, getNumStates()).iterator(); it.hasNext();) {\n\t\t\tint s = it.nextInt();\n\t\t\tresult.set(s, prob1step(s,u,v));\n\t\t}\n\t}\n\n\t/**\n\t * Find all deadlock states and store this information in the model.\n\t * If requested (if fix=true) and if needed (i.e. for DTMCs/CTMCs),\n\t * fix deadlocks by adding self-loops in these states.\n\t * The set of deadlocks (before any possible fixing) can be obtained from {@link #getDeadlockStates()}.\n\t * @throws PrismException if the model is unable to fix deadlocks because it is non-mutable.\n\t */\n\tvoid findDeadlocks(boolean fix) throws PrismException;\n\n\t/**\n\t * Checks for deadlocks and throws an exception if any exist.\n\t */\n\tvoid checkForDeadlocks() throws PrismException;\n\n\t/**\n\t * Checks for deadlocks and throws an exception if any exist.\n\t * States in 'except' (If non-null) are excluded from the check.\n\t */\n\tvoid checkForDeadlocks(BitSet except) throws PrismException;\n\n\t// Export methods (explicit files)\n\n\t/**\n\t * Export to explicit format readable by PRISM (i.e. a .tra file, etc.).\n\t */\n\tdefault void exportToPrismExplicit(String baseFilename) throws PrismException\n\t{\n\t\texportToPrismExplicit(baseFilename, DEFAULT_EXPORT_MODEL_PRECISION);\n\t}\n\n\t/**\n\t * Export to explicit format readable by PRISM (i.e. a .tra file, etc.).\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToPrismExplicit(String baseFilename, int precision) throws PrismException\n\t{\n\t\t// Default implementation - just output .tra file\n\t\t// (some models might override this)\n\t\texportToPrismExplicitTra(baseFilename + \".tra\", precision);\n\t}\n\n\t/**\n\t * Export transition matrix to explicit format readable by PRISM (i.e. a .tra file).\n\t */\n\tdefault void exportToPrismExplicitTra(PrismLog out, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tnew PrismExplicitExporter<Value>(exportOptions).exportTransitions(this, out);\n\t}\n\n\t/**\n\t * Export transition matrix to explicit format readable by PRISM (i.e. a .tra file).\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToPrismExplicitTra(PrismLog out, int precision) throws PrismException\n\t{\n\t\texportToPrismExplicitTra(out, new ModelExportOptions().setModelPrecision(precision));\n\t}\n\n\t/**\n\t * Export transition matrix to explicit format readable by PRISM (i.e. a .tra file).\n\t */\n\tdefault void exportToPrismExplicitTra(PrismLog out) throws PrismException\n\t{\n\t\texportToPrismExplicitTra(out, new ModelExportOptions());\n\t}\n\n\t/**\n\t * Export transition matrix to explicit format readable by PRISM (i.e. a .tra file).\n\t */\n\tdefault void exportToPrismExplicitTra(String filename) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(filename)) {\n\t\t\texportToPrismExplicitTra(out);\n\t\t}\n\t}\n\n\t/**\n\t * Export transition matrix to explicit format readable by PRISM (i.e. a .tra file).\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToPrismExplicitTra(String filename, int precision) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(filename)) {\n\t\t\texportToPrismExplicitTra(out, precision);\n\t\t}\n\t}\n\n\t/**\n\t * Export transition matrix to explicit format readable by PRISM (i.e. a .tra file).\n\t */\n\tdefault void exportToPrismExplicitTra(File file) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(file.getPath())) {\n\t\t\texportToPrismExplicitTra(out);\n\t\t}\n\t}\n\n\t/**\n\t * Export transition matrix to explicit format readable by PRISM (i.e. a .tra file).\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToPrismExplicitTra(File file, int precision) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(file.getPath())) {\n\t\t\texportToPrismExplicitTra(out, precision);\n\t\t}\n\t}\n\n\t// Export methods (dot files)\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark'.\n\t * @param out PrismLog to export to\n\t * @param exportOptions Options for export\n\t * @param decorators Any Dot decorators to add (ignored if null)\n\t */\n\tdefault void exportToDotFile(PrismLog out, ModelExportOptions exportOptions, Iterable<explicit.graphviz.Decorator> decorators) throws PrismException\n\t{\n\t\tnew DotExporter<Value>(exportOptions).exportModel(this, out, decorators);\n\t}\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark'.\n\t * @param out PrismLog to export to\n\t * @param exportOptions Options for export\n\t */\n\tdefault void exportToDotFile(PrismLog out, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tnew DotExporter<Value>(exportOptions).exportModel(this, out, null);\n\t}\n\n\t/**\n\t * Export to a dot file.\n\t * @param out PrismLog to export to\n\t */\n\tdefault void exportToDotFile(PrismLog out) throws PrismException\n\t{\n\t\texportToDotFile(out, new ModelExportOptions());\n\t}\n\n\t/**\n\t * Export to a dot file.\n\t * @param out PrismLog to export to\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToDotFile(PrismLog out, int precision) throws PrismException\n\t{\n\t\texportToDotFile(out, new ModelExportOptions().setModelPrecision(precision));\n\t}\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark'.\n\t * @param out PrismLog to export to\n\t * @param mark States to highlight (ignored if null)\n\t */\n\tdefault void exportToDotFile(PrismLog out, BitSet mark) throws PrismException\n\t{\n\t\tIterable<explicit.graphviz.Decorator> decorators = (mark == null) ? null : Collections.singleton(new explicit.graphviz.MarkStateSetDecorator(mark));\n\t\texportToDotFile(out, new ModelExportOptions(), decorators);\n\t}\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark'.\n\t * @param out PrismLog to export to\n\t * @param mark States to highlight (ignored if null)\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToDotFile(PrismLog out, BitSet mark, int precision) throws PrismException\n\t{\n\t\tIterable<explicit.graphviz.Decorator> decorators = (mark == null) ? null : Collections.singleton(new explicit.graphviz.MarkStateSetDecorator(mark));\n\t\texportToDotFile(out, new ModelExportOptions().setModelPrecision(precision), decorators);\n\t}\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark'.\n\t * @param out PrismLog to export to\n\t * @param mark States to highlight (ignored if null)\n\t * @param showStates Show state info on nodes?\n\t */\n\tdefault void exportToDotFile(PrismLog out, BitSet mark, boolean showStates) throws PrismException\n\t{\n\t\tIterable<explicit.graphviz.Decorator> decorators = (mark == null) ? null : Collections.singleton(new explicit.graphviz.MarkStateSetDecorator(mark));\n\t\texportToDotFile(out, new ModelExportOptions().setShowStates(showStates), decorators);\n\t}\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark'.\n\t * @param out PrismLog to export to\n\t * @param mark States to highlight (ignored if null)\n\t * @param showStates Show state info on nodes?\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToDotFile(PrismLog out, BitSet mark, boolean showStates, int precision) throws PrismException\n\t{\n\t\tIterable<explicit.graphviz.Decorator> decorators = (mark == null) ? null : Collections.singleton(new explicit.graphviz.MarkStateSetDecorator(mark));\n\t\texportToDotFile(out, new ModelExportOptions().setShowStates(showStates).setModelPrecision(precision), decorators);\n\t}\n\n\t/**\n\t * Export to a dot file, decorating states and transitions with the provided decorators\n\t * @param out PrismLog to export to\n\t */\n\tdefault void exportToDotFile(PrismLog out, Iterable<explicit.graphviz.Decorator> decorators) throws PrismException\n\t{\n\t\texportToDotFile(out, new ModelExportOptions(), decorators);\n\t}\n\n\t/**\n\t * Export to a dot file, decorating states and transitions with the provided decorators\n\t * @param out PrismLog to export to\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToDotFile(PrismLog out, Iterable<explicit.graphviz.Decorator> decorators, int precision) throws PrismException\n\t{\n\t\texportToDotFile(out, new ModelExportOptions().setModelPrecision(precision), decorators);\n\t}\n\n\t/**\n\t * Export to a dot file.\n\t * @param filename Name of file to export to\n\t */\n\tdefault void exportToDotFile(String filename) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(filename)) {\n\t\t\texportToDotFile(out);\n\t\t}\n\t}\n\n\t/**\n\t * Export to a dot file.\n\t * @param filename Name of file to export to\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToDotFile(String filename, int precision) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(filename)) {\n\t\t\texportToDotFile(out, precision);\n\t\t}\n\t}\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark'.\n\t * @param filename Name of file to export to\n\t * @param mark States to highlight (ignored if null)\n\t */\n\tdefault void exportToDotFile(String filename, BitSet mark) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(filename)) {\n\t\t\texportToDotFile(out, mark);\n\t\t}\n\t}\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark'.\n\t * @param filename Name of file to export to\n\t * @param mark States to highlight (ignored if null)\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToDotFile(String filename, BitSet mark, int precision) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(filename)) {\n\t\t\texportToDotFile(out, mark, precision);\n\t\t}\n\t}\n\n\t/**\n\t * Export to a dot file, decorating states and transitions with the provided decorators\n\t * @param filename Name of the file to export to\n\t */\n\tdefault void exportToDotFile(String filename, Iterable<explicit.graphviz.Decorator> decorators) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(filename)) {\n\t\t\texportToDotFile(out, decorators);\n\t\t}\n\t}\n\n\t/**\n\t * Export to a dot file, decorating states and transitions with the provided decorators\n\t * @param filename Name of the file to export to\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToDotFile(String filename, Iterable<explicit.graphviz.Decorator> decorators, int precision) throws PrismException\n\t{\n\t\ttry (PrismFileLog out = PrismFileLog.create(filename)) {\n\t\t\texportToDotFile(out, decorators, precision);\n\t\t}\n\t}\n\n\t@Deprecated\n\tdefault void exportTransitionsToDotFile(int i, PrismLog out, Iterable<explicit.graphviz.Decorator> decorators)\n\t{\n\t\t// This does not need to be implemented (it will be ignored)\n\t}\n\n\t@Deprecated\n\tdefault void exportTransitionsToDotFile(int i, PrismLog out, Iterable<explicit.graphviz.Decorator> decorators, int precision)\n\t{\n\t\t// This no longer needs to be implemented (it will be ignored)\n\t}\n\n\t/**\n\t * Export to a equivalent PRISM language model description.\n\t */\n\tdefault void exportToPrismLanguage(String filename) throws PrismException\n\t{\n\t\texportToPrismLanguage(filename, DEFAULT_EXPORT_MODEL_PRECISION);\n\t}\n\n\t/**\n\t * Export to a equivalent PRISM language model description.\n\t * @param precision number of significant digits >= 1\n\t */\n\tvoid exportToPrismLanguage(String filename, int precision) throws PrismException;\n\t\n\t/**\n\t * Export states list.\n\t */\n\tdefault void exportStates(VarList varList, PrismLog out, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tnew PrismExplicitExporter<Value>(exportOptions).exportStates(this, varList, out);\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export states list.\n\t */\n\t@Deprecated\n\tdefault void exportStates(int exportType, VarList varList, PrismLog out) throws PrismException\n\t{\n\t\texportStates(varList, out, Prism.convertExportType(exportType));\n\t}\n\n\t/**\n\t * Report info/stats about the model as a string.\n\t */\n\tdefault String infoString()\n\t{\n\t\tfinal int numStates = getNumStates();\n\t\tString s = \"\";\n\t\ts += numStates + \" states (\" + getNumInitialStates() + \" initial)\";\n\t\tif (this instanceof PartiallyObservableModel) {\n\t\t\ts += \", \" + ((PartiallyObservableModel<?>) this).getNumObservations() + \" observables\";\n\t\t\ts += \", \" + ((PartiallyObservableModel<?>) this).getNumUnobservations() + \" unobservables\";\n\t\t}\n\t\ts += \", \" + getNumTransitions() + \" transitions\";\n\t\tif (this instanceof NondetModel) {\n\t\t\ts += \", \" + ((NondetModel<?>) this).getNumChoices() + \" choices\";\n\t\t\ts += \", dist max/avg = \" + ((NondetModel<?>) this).getMaxNumChoices() + \"/\" + PrismUtils.formatDouble2dp(((double) ((NondetModel<?>) this).getNumChoices()) / numStates);\n\t\t}\n\t\treturn s;\n\t}\n\n\t/**\n\t * Report info/stats about the model, tabulated, as a string.\n\t */\n\tdefault String infoStringTable()\n\t{\n\t\tfinal int numStates = getNumStates();\n\t\tString s = \"\";\n\t\ts += \"States:      \" + numStates + \" (\" + getNumInitialStates() + \" initial)\\n\";\n\t\tif (this instanceof PartiallyObservableModel) {\n\t\t\ts += \"Obs/unobs:   \" + ((PartiallyObservableModel<?>) this).getNumObservations() + \"/\" + ((PartiallyObservableModel<?>) this).getNumUnobservations() + \"\\n\";\n\t\t}\n\t\ts += \"Transitions: \" + getNumTransitions() + \"\\n\";\n\t\tif (this instanceof NondetModel) {\n\t\t\ts += \"Choices:     \" + ((NondetModel<?>) this).getNumChoices() + \"\\n\";\n\t\t\ts += \"Max/avg:     \" + ((NondetModel<?>) this).getMaxNumChoices() + \"/\" + PrismUtils.formatDouble2dp(((double) ((NondetModel<?>) this).getNumChoices()) / numStates) + \"\\n\";\n\t\t}\n\t\treturn s;\n\t}\n\n\t/** Has this model a stored PredecessorRelation? */\n\tboolean hasStoredPredecessorRelation();\n\n\t/**\n\t * If there is a PredecessorRelation stored for this model, return that.\n\t * Otherwise, create one and return that. If {@code storeIfNew},\n\t * store it for later use.\n\t *\n\t * @param parent a PrismComponent (for obtaining the log)\n\t * @param storeIfNew if the predecessor relation is newly created, store it\n\t */\n\tPredecessorRelation getPredecessorRelation(prism.PrismComponent parent, boolean storeIfNew);\n\n\t/** Clear any stored predecessor relation, e.g., because the model was modified */\n\tvoid clearPredecessorRelation();\n\n\t/**\n\t * Get an Evaluator for the values stored in this Model for probabilities etc.\n\t * This is needed, for example, to compute probability sums, check for equality to 0/1, etc.\n\t * A default implementation provides an evaluator for the (usual) case when Value is Double.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tdefault Evaluator<Value> getEvaluator()\n\t{\n\t\treturn (Evaluator<Value>) Evaluator.forDouble();\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ModelCheckerResult.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport prism.Accuracy;\nimport strat.Strategy;\n\n/**\n * Class storing some info/data from a call to a model checking or\n * numerical computation method in the explicit engine. \n */\npublic class ModelCheckerResult\n{\n\t// Solution vector (doubles)\n\tpublic double[] soln = null;\n\t// Solution vector (objects)\n\tpublic Object[] solnObj = null;\n\t// Accuracy info\n\tpublic Accuracy accuracy = null;\n\t// Solution vector from previous iteration\n\tpublic double[] lastSoln = null;\n\t// Iterations performed\n\tpublic int numIters = 0;\n\t// Total time taken (secs)\n\tpublic double timeTaken = 0.0;\n\t// Time taken for any precomputation (secs)\n\tpublic double timePre = 0.0;\n\t// Time taken for Prob0-type precomputation (secs)\n\tpublic double timeProb0 = 0.0;\n\t// Strategy\n\tpublic Strategy<?> strat = null;\n\n\t/**\n\t * Clear all stored data, including setting of array pointers to null\n\t * (which may be helpful for garbage collection purposes).\n\t */\n\tpublic void clear()\n\t{\n\t\tsoln = lastSoln = null;\n\t\tsolnObj = null;\n\t\tnumIters = 0;\n\t\ttimeTaken = timePre = timeProb0 = 0.0;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ModelExplicit.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\nimport java.util.TreeMap;\nimport java.util.TreeSet;\n\nimport io.ExplicitModelImporter;\nimport io.PrismExplicitImporter;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport prism.ActionList;\nimport prism.ActionListOwner;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.PrismException;\n\n/**\n * Base class for explicit-state model representations.\n */\npublic abstract class ModelExplicit<Value> implements Model<Value>, ActionListOwner\n{\n\t/**\n\t * Evaluator for manipulating values in the model (of type {@code Value})\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected Evaluator<Value> eval = (Evaluator<Value>) Evaluator.forDouble();\n\n\t// Basic model information\n\n\t/**\n\t * Action list\n\t */\n\tprotected ActionList actionList = new ActionList(this::findActionsUsed);;\n\t/**\n\t * Number of states\n\t */\n\tprotected int numStates;\n\t/**\n\t * Which states are initial states\n\t */\n\tprotected List<Integer> initialStates; // TODO: should be a (linkedhash?) set really\n\t/**\n\t * States that are/were deadlocks. Where requested and where appropriate (DTMCs/MDPs),\n\t * these states may have been fixed at build time by adding self-loops.\n\t */\n\tprotected TreeSet<Integer> deadlocks;\n\n\t// Additional, optional information associated with the model\n\n\t/**\n\t * (Optionally) information about the states of this model,\n\t * i.e. the State object corresponding to each state index.\n\t */\n\tprotected List<State> statesList;\n\t/**\n\t * (Optionally) a list of values for constants associated with this model.\n\t */\n\tprotected Values constantValues;\n\t/**\n\t * (Optionally) the list of variables\n\t */\n\tprotected VarList varList;\n\t/**\n\t * (Optionally) some labels (atomic propositions) associated with the model,\n\t * represented as a String->BitSet mapping from their names to the states that satisfy them.\n\t */\n\tprotected Map<String, BitSet> labels = new TreeMap<String, BitSet>();\n\n\t/**\n\t * (Optionally) the stored predecessor relation. Becomes inaccurate after the model is changed!\n\t */\n\tprotected PredecessorRelation predecessorRelation = null;\n\n\t// Mutators\n\n\t/**\n\t * Set the {@link Evaluator} object for manipulating values in the model\n\t */\n\tpublic void setEvaluator(Evaluator<Value> eval)\n\t{\n\t\tthis.eval = eval;\n\t}\n\n\t/**\n\t * Copy data from another Model (used by superclass copy constructors).\n\t * Assumes that this has already been initialise()ed.\n\t */\n\tpublic void copyFrom(Model<?> model)\n\t{\n\t\tsetEvaluator((Evaluator<Value>) model.getEvaluator());\n\t\tif (model instanceof ActionListOwner) {\n\t\t\tactionList.copyFrom(((ActionListOwner) model).getActionList());\n\t\t}\n\t\tnumStates = model.getNumStates();\n\t\tfor (int in : model.getInitialStates()) {\n\t\t\taddInitialState(in);\n\t\t}\n\t\tfor (int dl : model.getDeadlockStates()) {\n\t\t\taddDeadlockState(dl);\n\t\t}\n\t\t// Shallow copy of read-only stuff\n\t\tstatesList = model.getStatesList();\n\t\tconstantValues = model.getConstantValues();\n\t\tlabels = model.getLabelToStatesMap();\n\t\tvarList = model.getVarList();\n\t}\n\n\t/**\n\t * Copy data from another Model and a state index permutation,\n\t * i.e. state index i becomes index permut[i]\n\t * (used by superclass copy constructors).\n\t * Assumes that this has already been initialise()ed.\n\t * Pointer to states list is NOT copied (since now wrong).\n\t */\n\tpublic void copyFrom(Model<Value> model, int permut[])\n\t{\n\t\tsetEvaluator(model.getEvaluator());\n\t\tif (model instanceof ActionListOwner) {\n\t\t\tactionList.copyFrom(((ActionListOwner) model).getActionList());\n\t\t}\n\t\tnumStates = model.getNumStates();\n\t\tfor (int in : model.getInitialStates()) {\n\t\t\taddInitialState(permut[in]);\n\t\t}\n\t\tfor (int dl : model.getDeadlockStates()) {\n\t\t\taddDeadlockState(permut[dl]);\n\t\t}\n\t\t// Shallow copy of (some) read-only stuff\n\t\t// (i.e. info that is not broken by permute)\n\t\tstatesList = null;\n\t\tconstantValues = model.getConstantValues();\n\t\tlabels.clear();\n\t\tvarList = model.getVarList();\n\t}\n\n\t/**\n\t * Initialise: create new model with fixed number of states.\n\t */\n\tpublic void initialise(int numStates)\n\t{\n\t\tthis.numStates = numStates;\n\t\tinitialStates = new ArrayList<Integer>();\n\t\tdeadlocks = new TreeSet<Integer>();\n\t\tstatesList = null;\n\t\tconstantValues = null;\n\t\tvarList = null;\n\t\tlabels = new TreeMap<String, BitSet>();\n\t}\n\n\t/**\n\t * Set the list of all action labels\n\t */\n\tpublic void setActions(List<Object> actions)\n\t{\n\t\tactionList.setActions(actions);\n\t}\n\n\t/**\n\t * Add a state to the list of initial states.\n\t */\n\tpublic void addInitialState(int i)\n\t{\n\t\tinitialStates.add(i);\n\t}\n\n\t/**\n\t * Empty the list of initial states.\n\t */\n\tpublic void clearInitialStates()\n\t{\n\t\tinitialStates.clear();\n\t}\n\n\t/**\n\t * Add a state to the list of deadlock states.\n\t */\n\tpublic void addDeadlockState(int i)\n\t{\n\t\tdeadlocks.add(i);\n\t}\n\n\t/**\n\t * Build (anew) from a list of transitions provided by an explicit model importer.\n\t * Note that initial states are not configured\n\t * so this needs to be done separately (using {@link #addInitialState(int)}.\n\t */\n\tpublic void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\t// Not implemented by default\n\t\tthrow new PrismException(\"Explicit model import not yet supported for this model\");\n\t}\n\n\t/**\n\t * Build (anew) from a list of transitions exported explicitly by PRISM (i.e. a .tra file).\n\t * Note that initial states are not configured (since this info is not in the file),\n\t * so this needs to be done separately (using {@link #addInitialState(int)}.\n\t */\n\tpublic void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tExplicitModelImporter modelImporter = new PrismExplicitImporter(null, new File(filename), null, null, null, ModelType.DTMC);\n\t\tbuildFromExplicitImport(modelImporter);\n\t}\n\n\n\t/**\n\t * Set the associated (read-only) state list.\n\t */\n\tpublic void setStatesList(List<State> statesList)\n\t{\n\t\tthis.statesList = statesList;\n\t}\n\n\t/**\n\t * Set the associated (read-only) constant values.\n\t */\n\tpublic void setConstantValues(Values constantValues)\n\t{\n\t\tthis.constantValues = constantValues;\n\t}\n\n\t/**\n\t * Sets the VarList for this model (may be {@code null}).\n\t */\n\tpublic void setVarList(VarList varList)\n\t{\n\t\tthis.varList = varList;\n\t}\n\n\t/**\n\t * Adds a label and the set the states that satisfy it.\n\t * Any existing label with the same name is overwritten.\n\t *\n\t * @param name   The name of the label\n\t * @param states The states that satisfy the label\n\t */\n\tpublic void addLabel(String name, BitSet states)\n\t{\n\t\tlabels.put(name, states);\n\t}\n\n\t/**\n\t * Add a label with corresponding state set, ensuring a unique, non-existing label.\n\t * The label will be either \"X\" or \"X_i\" where X is the content of the {@code prefix} argument\n\t * and i is a non-negative integer.\n\t * <br>\n\t * Optionally, a set of defined label names can be passed so that those labels\n\t * can be avoided. This can be obtained from the model checker via {@code getDefinedLabelNames()}.\n\t * <br>\n\t * Note that a stored label takes precedence over the on-the-fly calculation\n\t * of an ExpressionLabel, cf. {@link explicit.StateModelChecker#checkExpressionLabel}\n\t *\n\t * @param prefix            the prefix for the unique label\n\t * @param labelStates       the BitSet with the state set for the label\n\t * @param definedLabelNames set of names (optional, may be {@code null}) to check for existing labels\n\t * @return the generated unique label\n\t */\n\tpublic String addUniqueLabel(String prefix, BitSet labelStates, Set<String> definedLabelNames)\n\t{\n\t\tString label;\n\t\tint i = 0;\n\t\tlabel = prefix;  // first, try without appending _i\n\t\twhile (true) {\n\t\t\tboolean labelOk = !hasLabel(label);  // not directly attached to model\n\t\t\tif (definedLabelNames != null) {\n\t\t\t\tlabelOk &= !definedLabelNames.contains(label);  // not defined\n\t\t\t}\n\n\t\t\tif (labelOk) {\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t// prepare next label to try\n\t\t\tlabel = prefix + \"_\" + i;\n\t\t\tif (i == Integer.MAX_VALUE)\n\t\t\t\tthrow new UnsupportedOperationException(\"Integer overflow trying to add unique label\");\n\n\t\t\ti++;\n\t\t}\n\n\t\taddLabel(label, labelStates);\n\t\treturn label;\n\t}\n\n\t// Accessors (for Model interface)\n\n\t@Override\n\tpublic Evaluator<Value> getEvaluator()\n\t{\n\t\treturn eval;\n\t}\n\n\t@Override\n\tpublic ActionList getActionList()\n\t{\n\t\treturn actionList;\n\t}\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\treturn actionList.getActions();\n\t}\n\n\t@Override\n\tpublic int actionIndex(Object action)\n\t{\n\t\tint actionIndex = actionList.actionIndex(action);\n\t\tif (actionIndex == -1) {\n\t\t\tthrow new RuntimeException(\"Action storage error: \" + action + \" not found\");\n\t\t}\n\t\treturn actionIndex;\n\t}\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn numStates;\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn initialStates.size();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn initialStates;\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn initialStates.isEmpty() ? -1 : initialStates.get(0);\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(int i)\n\t{\n\t\treturn initialStates.contains(i);\n\t}\n\n\t@Override\n\tpublic int getNumDeadlockStates()\n\t{\n\t\treturn deadlocks.size();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getDeadlockStates()\n\t{\n\t\treturn deadlocks;\n\t}\n\n\t@Override\n\tpublic StateValues getDeadlockStatesList()\n\t{\n\t\tBitSet bs = new BitSet();\n\t\tfor (int dl : deadlocks) {\n\t\t\tbs.set(dl);\n\t\t}\n\n\t\treturn StateValues.createFromBitSet(bs, this);\n\t}\n\n\t@Override\n\tpublic int getFirstDeadlockState()\n\t{\n\t\treturn deadlocks.isEmpty() ? -1 : deadlocks.first();\n\t}\n\n\t@Override\n\tpublic boolean isDeadlockState(int i)\n\t{\n\t\treturn deadlocks.contains(i);\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn statesList;\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn constantValues;\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn varList;\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(String name)\n\t{\n\t\treturn labels.get(name);\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn labels.containsKey(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn labels.keySet();\n\t}\n\n\t@Override\n\tpublic Map<String, BitSet> getLabelToStatesMap()\n\t{\n\t\treturn labels;\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks() throws PrismException\n\t{\n\t\tcheckForDeadlocks(null);\n\t}\n\n\t@Override\n\tpublic abstract void checkForDeadlocks(BitSet except) throws PrismException;\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof ModelExplicit))\n\t\t\treturn false;\n\t\tModelExplicit<?> model = (ModelExplicit<?>) o;\n\t\tif (numStates != model.numStates)\n\t\t\treturn false;\n\t\tif (!initialStates.equals(model.initialStates))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean hasStoredPredecessorRelation()\n\t{\n\t\treturn (predecessorRelation != null);\n\t}\n\n\t@Override\n\tpublic PredecessorRelation getPredecessorRelation(prism.PrismComponent parent, boolean storeIfNew)\n\t{\n\t\tif (predecessorRelation != null) {\n\t\t\treturn predecessorRelation;\n\t\t}\n\n\t\tPredecessorRelation pre = PredecessorRelation.forModel(parent, this);\n\n\t\tif (storeIfNew) {\n\t\t\tpredecessorRelation = pre;\n\t\t}\n\t\treturn pre;\n\t}\n\n\t@Override\n\tpublic void clearPredecessorRelation()\n\t{\n\t\tpredecessorRelation = null;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ModelExplicitWrapper.java",
    "content": "package explicit;\n\nimport io.ExplicitModelImporter;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport prism.ActionList;\nimport prism.PrismException;\n\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\n\n/**\n * Base class for explicit-state models that wrap around another model,\n * represented by an instance of {@link ModelExplicit<Value>}.\n *\n * Note: this extends  {@link ModelExplicit<Value>} but the fields in that\n * class are completely ignored; instead those of the wrapped model are used.\n * The exception is the evaluator, which may differ and so is stored.\n */\npublic abstract class ModelExplicitWrapper<Value> extends ModelExplicit<Value>\n{\n\t/** The wrapped model */\n\tprotected ModelExplicit<Value> model;\n\n\t// Mutators (for ModelExplicit)\n\n\t@Override\n\tpublic void copyFrom(Model<?> model)\n\t{\n\t\tthis.model.copyFrom(model);\n\t}\n\n\t@Override\n\tpublic void copyFrom(Model<Value> model, int permut[])\n\t{\n\t\tthis.model.copyFrom(model, permut);\n\t}\n\n\t@Override\n\tpublic void initialise(int numStates)\n\t{\n\t\tthis.model.initialise(numStates);\n\t}\n\n\t@Override\n\tpublic void setActions(List<Object> actions)\n\t{\n\t\tthis.model.setActions(actions);\n\t}\n\n\t@Override\n\tpublic void addInitialState(int i)\n\t{\n\t\tthis.model.addInitialState(i);\n\t}\n\n\t@Override\n\tpublic void clearInitialStates()\n\t{\n\t\tthis.model.clearInitialStates();\n\t}\n\n\t@Override\n\tpublic void addDeadlockState(int i)\n\t{\n\t\tthis.model.addDeadlockState(i);\n\t}\n\n\t@Override\n\tpublic void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\tthis.model.buildFromExplicitImport(modelImporter);\n\t}\n\n\t@Override\n\tpublic void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tthis.model.buildFromPrismExplicit(filename);\n\t}\n\n\t@Override\n\tpublic void setStatesList(List<State> statesList)\n\t{\n\t\tthis.model.setStatesList(statesList);\n\t}\n\n\t@Override\n\tpublic void setConstantValues(Values constantValues)\n\t{\n\t\tthis.model.setConstantValues(constantValues);\n\t}\n\n\t@Override\n\tpublic void setVarList(VarList varList)\n\t{\n\t\tthis.model.setVarList(varList);\n\t}\n\n\t@Override\n\tpublic void addLabel(String name, BitSet states)\n\t{\n\t\tthis.model.addLabel(name, states);\n\t}\n\n\t@Override\n\tpublic String addUniqueLabel(String prefix, BitSet labelStates, Set<String> definedLabelNames)\n\t{\n\t\treturn this.model.addUniqueLabel(prefix, labelStates, definedLabelNames);\n\t}\n\n\t// Accessors (for Model)\n\n\t@Override\n\tpublic ActionList getActionList()\n\t{\n\t\treturn this.model.getActionList();\n\t}\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\treturn this.model.getActions();\n\t}\n\n\t@Override\n\tpublic List<Object> findActionsUsed()\n\t{\n\t\treturn this.model.findActionsUsed();\n\t}\n\n\t@Override\n\tpublic boolean onlyNullActionUsed()\n\t{\n\t\treturn this.model.onlyNullActionUsed();\n\t}\n\n\t@Override\n\tpublic int actionIndex(Object action)\n\t{\n\t\treturn this.model.actionIndex(action);\n\t}\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn this.model.getNumStates();\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn this.model.getNumInitialStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn this.model.getInitialStates();\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn this.model.getFirstInitialState();\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(int i)\n\t{\n\t\treturn this.model.isInitialState(i);\n\t}\n\n\t@Override\n\tpublic int getNumDeadlockStates()\n\t{\n\t\treturn this.model.getNumDeadlockStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getDeadlockStates()\n\t{\n\t\treturn this.model.getDeadlockStates();\n\t}\n\n\t@Override\n\tpublic StateValues getDeadlockStatesList()\n\t{\n\t\treturn this.model.getDeadlockStatesList();\n\t}\n\n\t@Override\n\tpublic int getFirstDeadlockState()\n\t{\n\t\treturn this.model.getFirstDeadlockState();\n\t}\n\n\t@Override\n\tpublic boolean isDeadlockState(int i)\n\t{\n\t\treturn this.model.isDeadlockState(i);\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn this.model.getStatesList();\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn this.model.getConstantValues();\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn this.model.getVarList();\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(String name)\n\t{\n\t\treturn this.model.getLabelStates(name);\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn this.model.hasLabel(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn this.model.getLabels();\n\t}\n\n\t@Override\n\tpublic Map<String, BitSet> getLabelToStatesMap()\n\t{\n\t\treturn this.model.getLabelToStatesMap();\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(int s)\n\t{\n\t\treturn this.model.getSuccessors(s);\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tthis.model.findDeadlocks(fix);\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks() throws PrismException\n\t{\n\t\tthis.model.checkForDeadlocks();\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tthis.model.checkForDeadlocks(except);\n\t}\n\n\t@Override\n\tpublic void exportToPrismLanguage(String filename, int precision) throws PrismException\n\t{\n\t\tthis.model.exportToPrismLanguage(filename, precision);\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn model.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ModelModelGenerator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2019-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\nimport parser.EvaluateContext;\nimport parser.State;\nimport parser.VarList;\nimport parser.ast.DeclarationType;\nimport parser.type.Type;\nimport prism.ModelGenerator;\nimport prism.ModelInfo;\nimport prism.ModelType;\nimport prism.Pair;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Class that implements the ModelGenerator interface using an explicit model.\n * Allows e.g. simulation of a built model.\n */\npublic class ModelModelGenerator<Value> implements ModelGenerator<Value>\n{\n\t// Explicit model + info\n\tprivate Model<Value> model;\n\tprivate ModelInfo modelInfo;\n\t\n\t/** Index of the state current being explored */\n\tprivate int sExplore = -1;\n\t\n\t// Temporary storage of transitions for a state\n\t\n\tprivate class Transitions\n\t{\n\t\tObject choiceAction;\n\t\tList<Integer> succs;\n\t\tList<Value> probs;\n\t\tList<Object> transActions;\n\n\t\tpublic Transitions()\n\t\t{\n\t\t\tchoiceAction = null;\n\t\t\tsuccs = new ArrayList<>();\n\t\t\tprobs = new ArrayList<>();\n\t\t\ttransActions = null;\n\t\t}\n\t}\n\t\n\tprivate List<Transitions> trans = new ArrayList<>();\n\t\n\tpublic ModelModelGenerator(Model<Value> model, ModelInfo modelInfo)\n\t{\n\t\tthis.model = model;\n\t\tthis.modelInfo = modelInfo; \n\t}\n\t\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn model.getModelType();\n\t}\n\n\t@Override\n\tpublic void setSomeUndefinedConstants(EvaluateContext ecUndefined) throws PrismException\n\t{\n\t\tmodelInfo.setSomeUndefinedConstants(ecUndefined);\n\t}\n\n\t@Override\n\tpublic EvaluateContext getEvaluateContext()\n\t{\n\t\treturn modelInfo.getEvaluateContext();\n\t}\n\n\t@Override\n\tpublic List<String> getVarNames()\n\t{\n\t\treturn modelInfo.getVarNames();\n\t}\n\n\t@Override\n\tpublic List<Type> getVarTypes()\n\t{\n\t\treturn modelInfo.getVarTypes();\n\t}\n\n\t@Override\n\tpublic DeclarationType getVarDeclarationType(int i) throws PrismException\n\t{\n\t\treturn modelInfo.getVarDeclarationType(i);\n\t}\n\n\t@Override\n\tpublic int getVarModuleIndex(int i)\n\t{\n\t\treturn modelInfo.getVarModuleIndex(i);\n\t}\n\t\n\t@Override\n\tpublic String getModuleName(int i)\n\t{\n\t\treturn modelInfo.getModuleName(i);\n\t}\n\t\n\t@Override\n\tpublic VarList createVarList() throws PrismException\n\t{\n\t\treturn modelInfo.createVarList();\n\t}\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\t// Use actions from model (not guaranteed to be present in the model source)\n\t\t// (nor guaranteed to be consistent if present, currently)\n\t\treturn model.getActions();\n\t}\n\n\t@Override\n\tpublic State getInitialState() throws PrismException\n\t{\n\t\tint sInitial = model.getFirstInitialState();\n\t\treturn model.getStatesList().get(sInitial);\n\t}\n\n\t@Override\n\tpublic void exploreState(State exploreState) throws PrismException\n\t{\n\t\t// Look up index of state to explore\n\t\tsExplore = model.getStatesList().indexOf(exploreState);\n\t\t// Extract transitions and store \n\t\ttrans.clear();\n\t\tswitch (model.getModelType()) {\n\t\tcase CTMC:\n\t\t\tstoreTransitionsAndActions(((CTMC<Value>) model).getTransitionsAndActionsIterator(sExplore));\n\t\t\tbreak;\n\t\tcase DTMC:\n\t\t\tstoreTransitionsAndActions(((DTMC<Value>) model).getTransitionsAndActionsIterator(sExplore));\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tint numChoices = ((MDP<Value>) model).getNumChoices(sExplore);\n\t\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\t\tObject action = ((MDP<Value>) model).getAction(sExplore, i);\n\t\t\t\tstoreTransitions(action, ((MDP<Value>) model).getTransitionsIterator(sExplore, i));\n\t\t\t}\n\t\t\tbreak;\n\t\tcase CTMDP:\n\t\tcase LTS:\n\t\tcase PTA:\n\t\tcase SMG:\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Model generation not supported for \" + model.getModelType() + \"s\");\n\t\t}\n\t}\n\n\t/**\n\t * Store the transitions extracted from an action and Model-provided iterator.\n\t */\n\tprivate void storeTransitions(Object choiceAction, Iterator<Map.Entry<Integer, Value>> transitionsIterator)\n\t{\n\t\tTransitions t = new Transitions();\n\t\tt.choiceAction = choiceAction;\n\t\twhile (transitionsIterator.hasNext()) {\n\t\t\tMap.Entry<Integer, Value> e = transitionsIterator.next();\n\t\t\tt.succs.add(e.getKey());\n\t\t\tt.probs.add(e.getValue());\n\t\t}\n\t\ttrans.add(t);\n\t}\n\n\tprivate void storeTransitionsAndActions(Iterator<java.util.Map.Entry<Integer, Pair<Value, Object>>> transitionsAndActionsIterator)\n\t{\n\t\tTransitions t = new Transitions();\n\t\tt.transActions = new ArrayList<>();\n\t\twhile (transitionsAndActionsIterator.hasNext()) {\n\t\t\tMap.Entry<Integer, Pair<Value, Object>> e = transitionsAndActionsIterator.next();\n\t\t\tt.succs.add(e.getKey());\n\t\t\tt.probs.add(e.getValue().first);\n\t\t\tt.transActions.add(e.getValue().second);\n\t\t}\n\t\ttrans.add(t);\n\t}\n\n\t@Override\n\tpublic int getNumChoices() throws PrismException\n\t{\n\t\treturn trans.size();\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int i) throws PrismException\n\t{\n\t\treturn trans.get(i).succs.size();\n\t}\n\n\t@Override\n\tpublic Object getChoiceAction(int i) throws PrismException\n\t{\n\t\treturn trans.get(i).choiceAction;\n\t}\n\n\t@Override\n\tpublic Object getTransitionAction(int i, int offset) throws PrismException\n\t{\n\t\tList<Object> transActions = trans.get(i).transActions;\n\t\treturn transActions == null ? null : transActions.get(offset);\n\t}\n\n\t@Override\n\tpublic Value getTransitionProbability(int i, int offset) throws PrismException\n\t{\n\t\treturn trans.get(i).probs.get(offset);\n\t}\n\n\t@Override\n\tpublic State computeTransitionTarget(int i, int offset) throws PrismException\n\t{\n\t\treturn model.getStatesList().get(trans.get(i).succs.get(offset));\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ModelSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.function.Function;\n\nimport io.ExplicitModelImporter;\nimport io.PrismExplicitImporter;\nimport parser.State;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Interface for simple mutable explicit-state model representations.\n */\npublic interface ModelSimple<Value> extends Model<Value>\n{\n\t/**\n\t * Add a state to the list of initial states.\n\t */\n\tpublic abstract void addInitialState(int i);\n\n\t/**\n\t * Build (anew) from a list of transitions provided by an explicit model importer.\n\t * Note that initial states are not configured\n\t * so this needs to be done separately (using {@link #addInitialState(int)}.\n\t */\n\tdefault void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\t// Not implemented by default\n\t\tthrow new PrismException(\"Explicit model not yet supported for this model\");\n\t}\n\n\t/**\n\t * Build (anew) from a list of transitions exported explicitly by PRISM (i.e. a .tra file).\n\t * Note that initial states are not configured (since this info is not in the file),\n\t * so this needs to be done separately (using {@link #addInitialState(int)}.\n\t */\n\tdefault void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tExplicitModelImporter modelImporter = new PrismExplicitImporter(null, new File(filename), null, null, null, ModelType.DTMC);\n\t\tbuildFromExplicitImport(modelImporter);\n\t}\n\n\t/**\n\t * Clear all information for a state (i.e. remove all transitions).\n\t */\n\tpublic abstract void clearState(int i);\n\n\t/**\n\t * Add a new state and return its index.\n\t */\n\tpublic abstract int addState();\n\n\t/**\n\t * Add multiple new states.\n\t */\n\tpublic abstract void addStates(int numToAdd);\n\n\t/**\n\t * Set the associated (read-only) state list.\n\t */\n\tpublic void setStatesList(List<State> statesList);\n\n\t/**\n\t * Adds a label and the set the states that satisfy it.\n\t * Any existing label with the same name is overwritten.\n\t * @param name The name of the label\n\t * @param states The states that satisfy the label \n\t */\n\tpublic void addLabel(String name, BitSet states);\n\n\t// Static helper methods\n\n\t/**\n\t * Create a new ModelSimple object of the appropriate kind for a given model type\n\t */\n\tpublic static ModelSimple<?> forModelType(ModelType modelType) throws PrismException\n\t{\n\t\tModelSimple<?> prodModel = null;\n\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\t\tprodModel = new DTMCSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\t\tprodModel = new MDPSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase POMDP:\n\t\t\t\tprodModel = new POMDPSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase IDTMC:\n\t\t\t\tprodModel = new IDTMCSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase IMDP:\n\t\t\t\tprodModel = new IMDPSimple<>();\n\t\t\t\tbreak;\n\t\t\tcase STPG:\n\t\t\t\tprodModel = new STPGSimple<>();\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Model construction not supported for \" + modelType + \"s\");\n\t\t}\n\t\treturn prodModel;\n\t}\n\n\t/**\n\t * Copy a model, creating a new {@link ModelSimple} of the appropriate type.\n\t * @param model The model to copy\n\t */\n\tstatic <V> ModelSimple<V> copy(Model<V> model) throws PrismException\n\t{\n\t\tModelType modelType = model.getModelType();\n\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\t\treturn new DTMCSimple<>((DTMC<V>) model);\n\t\t\tcase CTMC:\n\t\t\t\treturn new DTMCSimple<>((CTMC<V>) model);\n\t\t\tcase MDP:\n\t\t\t\treturn new MDPSimple<>((MDP<V>) model);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Model copy not supported for \" + modelType + \"s\");\n\t\t}\n\n\t}\n\n\t/**\n\t * Copy a model, mapping probability values using the provided function.\n\t * creating a new {@link ModelSimple} of the appropriate type.\n\t * There is no attempt to check that distributions sum to one.\n\t * @param model The model to copy\n\t */\n\tstatic <V> ModelSimple<V> copy(Model<V> model, Function<? super V, ? extends V> probMap) throws PrismException\n\t{\n\t\tModelType modelType = model.getModelType();\n\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\t\treturn new DTMCSimple<>((DTMC<V>) model, probMap);\n\t\t\tcase CTMC:\n\t\t\t\treturn new CTMCSimple<>((CTMC<V>) model, probMap);\n\t\t\tcase MDP:\n\t\t\t\treturn new MDPSimple<>((MDP<V>) model, probMap);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Model copy not supported for \" + modelType + \"s\");\n\t\t}\n\n\t}\n\n\t/**\n\t * Copy a model, mapping probability values using the provided function,\n\t * creating a new {@link ModelSimple} of the appropriate type.\n\t * There is no attempt to check that distributions sum to one.\n\t * Since the type changes (V -> V2), an Evaluator for Value must be given.\n\t * creating a new {@link ModelSimple} of the appropriate type.\n\t * @param model The model to copy\n\t */\n\tstatic <V, V2> ModelSimple<V2> copy(Model<V> model, Function<? super V, ? extends V2> probMap, Evaluator<V2> eval) throws PrismException\n\t{\n\t\tModelType modelType = model.getModelType();\n\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\t\treturn new DTMCSimple<>((DTMC<V>) model, probMap, eval);\n\t\t\tcase CTMC:\n\t\t\t\treturn new CTMCSimple<>((CTMC<V>) model, probMap, eval);\n\t\t\tcase MDP:\n\t\t\t\treturn new MDPSimple<>((MDP<V>) model, probMap, eval);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Model copy not supported for \" + modelType + \"s\");\n\t\t}\n\n\t}\n}"
  },
  {
    "path": "prism/src/explicit/ModelTransformation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport prism.PrismException;\n\n/**\n * Interface for a model transformation.\n */\npublic interface ModelTransformation<OriginalModel extends Model<?>, TransformedModel extends Model<?>> {\n\n\t/** Get the original model. */\n\tpublic OriginalModel getOriginalModel();\n\n\t/** Get the transformed model. */\n\tpublic TransformedModel getTransformedModel();\n\n\t/**\n\t * Take a {@code StateValues} object for the transformed model and\n\t * project the values to the original model.\n\t * @param svTransformedModel a {@code StateValues} object for the transformed model\n\t * @return a corresponding {@code StateValues} object for the original model.\n\t **/\n\tpublic StateValues projectToOriginalModel(StateValues svTransformedModel) throws PrismException;\n}\n"
  },
  {
    "path": "prism/src/explicit/NonProbModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.PrintStream;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.Vector;\n\nimport automata.LTL2NBA;\nimport jltl2dstar.NBA;\nimport common.IterableBitSet;\nimport common.IterableStateSet;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionExists;\nimport parser.ast.ExpressionForAll;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport prism.PrismUtils;\n\n/**\n * Explicit-state, non-probabilistic model checker.\n */\npublic class NonProbModelChecker extends StateModelChecker\n{\n\t/**\n\t * Create a new NonProbModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic NonProbModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\t\n\t@Override\n\tpublic StateValues checkExpression(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res;\n\n\t\t// E operator\n\t\tif (expr instanceof ExpressionExists) {\n\t\t\treturn checkExpressionExists(model, ((ExpressionExists)expr).getExpression(), statesOfInterest);\n\t\t}\n\t\t// A operator\n\t\telse if (expr instanceof ExpressionForAll) {\n\t\t\treturn checkExpressionForAll(model, ((ExpressionForAll)expr).getExpression(), statesOfInterest);\n\t\t}\n\t\t// Otherwise, use the superclass\n\t\telse {\n\t\t\tres = super.checkExpression(model, expr, statesOfInterest);\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ expr ].\n\t * <br>\n\t * 'expr' has to be a simple path formula.\n\t *\n\t * @param model the model\n\t * @param expr the expression for 'expr'\n\t * @param statesOfInterest the states of interest ({@code null} = all states)\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ expr ]\n\t */\n\tprotected StateValues checkExpressionExists(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Check whether we have to use LTL path formula handling\n\t\tif (getSettings().getBoolean(PrismSettings.PRISM_PATH_VIA_AUTOMATA)\n\t\t    || !expr.isSimplePathFormula() ) {\n\t\t\treturn checkExistsLTL(model, expr, statesOfInterest);\n\t\t}\n\n\t\t// We have a simple path formula, convert to either\n\t\t// (1) a U b\n\t\t// (2) !(a U b)\n\t\t// (3) X a\n\t\texpr = Expression.convertSimplePathFormulaToCanonicalForm(expr);\n\n\t\t// next-step (3)\n\t\tif (expr instanceof ExpressionTemporal &&\n\t\t    ((ExpressionTemporal) expr).getOperator() == ExpressionTemporal.P_X) {\n\t\t\tif (((ExpressionTemporal)expr).hasBounds()) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Model checking of bounded CTL operators is not supported\");\n\t\t\t}\n\t\t\treturn checkExistsNext(model, ((ExpressionTemporal) expr).getOperand2(), statesOfInterest);\n\t\t}\n\n\t\t// until\n\t\tboolean negated = false;\n\t\tif (Expression.isNot(expr)) {\n\t\t\t// (2) !(a U b)\n\t\t\tnegated = true;\n\t\t\texpr = ((ExpressionUnaryOp)expr).getOperand();\n\t\t}\n\n\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\tassert (exprTemp.getOperator() == ExpressionTemporal.P_U);\n\n\t\tif (exprTemp.hasBounds()) {\n\t\t\tthrow new PrismNotSupportedException(\"Model checking of bounded CTL operators is not supported\");\n\t\t}\n\n\t\tStateValues result;\n\n\t\tif (negated) {\n\t\t\t// compute E[ !a R !b ] instead of E[ !(a U b) ]\n\t\t\tresult = checkExistsRelease(model,\n\t\t\t                            Expression.Not(exprTemp.getOperand1()),\n\t\t\t                            Expression.Not(exprTemp.getOperand2()));\n\t\t} else {\n\t\t\t// compute E[ a U b ]\n\t\t\tresult = checkExistsUntil(model, exprTemp.getOperand1(), exprTemp.getOperand2());\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Compute the set of states satisfying A[ expr ].\n\t * <br>\n\t * This is computed by determining the set of states not satisfying E[ !expr ].\n\t * 'expr' has to be a simple path formula.\n\t *\n\t * @param model the model\n\t * @param expr the expression for 'expr'\n\t * @param statesOfInterest the states of interest ({@code null} = all states)\n\t * @return a boolean StateValues, with {@code true} for all states satisfying A[ expr ]\n\t */\n\tprotected StateValues checkExpressionForAll(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tStateValues result = checkExpressionExists(model, Expression.Not(expr), statesOfInterest);\n\t\tresult.complement();\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ X expr ].\n\t * @param model the model\n\t * @param expr the expression for 'expr'\n\t * @param statesOfInterest the states of interest ({@code null} = all states)\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ X expr ]\n\t */\n\tprotected StateValues checkExistsNext(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tBitSet target = checkExpression(model, expr, null).getBitSet();\n\t\tBitSet result = computeExistsNext(model, target, statesOfInterest);\n\n\t\treturn StateValues.createFromBitSet(result, model);\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ X \"target\" ].\n\t * @param model the model\n\t * @param target the BitSet of states for target\n\t * @param statesOfInterest the states of interest ({@code null} = all states)\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ X \"target\" ]\n\t */\n\tpublic BitSet computeExistsNext(Model<?> model, BitSet target, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tBitSet result = new BitSet();\n\n\t\tfor (int s : new IterableStateSet(statesOfInterest, model.getNumStates())) {\n\t\t\t// for each state of interest, check whether there is a transition to the 'target'\n\t\t\tif (model.someSuccessorsInSet(s, target)) {\n\t\t\t\tresult.set(s);\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Compute the set of states satisfying A[ X expr ].\n\t * @param model the model\n\t * @param expr the expression for 'expr'\n\t * @param statesOfInterest the states of interest ({@code null} = all states)\n\t * @return a boolean StateValues, with {@code true} for all states satisfying A[ X expr ]\n\t */\t\n\tprotected StateValues checkForAllNext(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tBitSet target = checkExpression(model, expr, null).getBitSet();\n\t\tBitSet result = new BitSet();\n\n\t\tfor (int s : new IterableStateSet(statesOfInterest, model.getNumStates())) {\n\t\t\t// for each state of interest, check whether all transitions go to 'target'\n\t\t\tif (model.allSuccessorsInSet(s, target)) {\n\t\t\t\tresult.set(s);\n\t\t\t}\n\t\t}\n\n\t\treturn StateValues.createFromBitSet(result, model);\n\t}\n\n\t/**\n\t * Compute the set of states satisfying A[ X \"target\" ].\n\t * @param model the model\n\t * @param target the BitSet of states in target\n\t * @param statesOfInterest the states of interest ({@code null} = all states)\n\t * @return a boolean StateValues, with {@code true} for all states satisfying A[ X \"target\" ]\n\t */\n\tpublic BitSet computeForAllNext(Model<?> model, BitSet target, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tBitSet result = new BitSet();\n\n\t\tfor (int s : new IterableStateSet(statesOfInterest, model.getNumStates())) {\n\t\t\t// for each state of interest, check whether all transitions go to 'target'\n\t\t\tif (model.allSuccessorsInSet(s, target)) {\n\t\t\t\tresult.set(s);\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t\n\t/**\n\t * Compute the set of states satisfying E[ a U b ].\n\t * @param model the model\n\t * @param exprA the expression for 'a'\n\t * @param exprB the expression for 'b'\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ a U b ]\n\t */\n\tprotected StateValues checkExistsUntil(Model<?> model, Expression exprA, Expression exprB) throws PrismException {\n\t\t// the set of states satisfying exprA\n\t\tBitSet A = checkExpression(model, exprA, null).getBitSet();\n\t\t// the set of states satisfying exprB\n\t\tBitSet B = checkExpression(model, exprB, null).getBitSet();\n\n\t\tBitSet result = computeExistsUntil(model, A, B);\n\n\t\treturn StateValues.createFromBitSet(result, model);\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ \"a\" U \"b\" ].\n\t * @param model the model\n\t * @param A the BitSet of states for \"a\"\n\t * @param B the BitSet of states for \"b\"\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ \"a\" U \"b\" ]\n\t */\n\tpublic BitSet computeExistsUntil(Model<?> model, BitSet A, BitSet B) throws PrismException\n\t{\n \t\tPredecessorRelation pre = model.getPredecessorRelation(this, true);\n \t\treturn pre.calculatePreStar(A, B, B);\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ G a ].\n\t * @param model the model\n\t * @param exprA the expression for 'a'\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ G a ]\n\t */\n\tprotected StateValues checkExistsGlobally(Model<?> model, Expression exprA) throws PrismException\n\t{\n\t\treturn checkExistsRelease(model, Expression.False(), exprA);\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ G \"a\" ].\n\t * @param model the model\n\t * @param A the BitSet of states for \"a\"\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ G \"a\" ]\n\t */\n\tpublic BitSet computeExistsGlobally(Model<?> model, BitSet A) throws PrismException\n\t{\n\t\treturn computeExistsRelease(model, new BitSet(), A);\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ a R b ], i.e., from which there\n\t * exists a path satisfying G b or b U (a&b)\n\t * @param model the model\n\t * @param exprA the expression for 'a'\n\t * @param exprB the expression for 'b'\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ a R b ]\n\t */\n\tprotected StateValues checkExistsRelease(Model<?> model, Expression exprA, Expression exprB) throws PrismException\n\t{\n\t\t// the set of states satisfying exprA\n\t\tBitSet A = checkExpression(model, exprA, null).getBitSet();\n\t\t// the set of states satisfying exprB\n\t\tBitSet B = checkExpression(model, exprB, null).getBitSet();\n\n\t\tPredecessorRelation pre = model.getPredecessorRelation(this, true);\n\n\t\t// the intersection of A and B\n\t\t// these states surely satisfy E[ a R b ]\n\t\tBitSet AandB = (BitSet) A.clone();\n\t\tAandB.and(B);\n\n\t\t// The set T contains all states for which E[ a R b ] has not yet been disproven\n\t\t// Initially, this contains all 'B' states\n\t\tBitSet T = (BitSet) B.clone();\n\n\t\t// the set E contains all states that have not yet been visited\n\t\t// and for which we have proven that they do not satisfy E[ a R b ]\n\t\t// Initially, it contains the complement of 'T'\n\t\tBitSet E = (BitSet) T.clone();\n\t\tE.flip(0, model.getNumStates());\n\n\t\t// NOTE: The correctness relies on the fact that both\n\t\t// getSuccessorsIterator and pre.getPre are exactly the two sides\n\t\t// of the underlying edge relation, i.e., that the number of entries\n\t\t// is consistent. If the PredecessorRelation semantics are changed\n\t\t// later on, we have to adapt here as well...\n\n\t\t// for all states s in T \\ AandB, we compute count[s], the number of successors\n\t\t// according to getSuccessorsIterator\n\t\tint count[] = new int[model.getNumStates()];\n\t\tfor (int s : IterableBitSet.getSetBits(T)) {\n\t\t\tif (AandB.get(s)) continue;\n\n\t\t\tint i=0;\n\t\t\tfor (Iterator<Integer> it = model.getSuccessorsIterator(s); it.hasNext(); it.next()) {\n\t\t\t\ti++;\n\t\t\t}\n\t\t\tcount[s]=i;\n\t\t}\n\t\t\n\t\twhile (!E.isEmpty()) {\n\t\t\t// get the first element of E\n\t\t\tint t = E.nextSetBit(0);\n\t\t\t// and mark it as processed\n\t\t\tE.clear(t);\n\n\t\t\t// We know that t does not satisfy E[ a R b ].\n\t\t\t// Any predecessor s of t can be shown to not satisfy E[ a R b ]\n\t\t\t// if there are no remaining successors into T, i.e, if count[s]==0\n\n\t\t\t// For all predecessors s of t....\n\t\t\tfor (int s : pre.getPre(t)) {\n\t\t\t\t// ... ignore if we have already proven that it does not satisfy E[ a R b ]\n\t\t\t\tif (!T.get(s)) continue;\n\n\t\t\t\t// decrement count, because s can not use t to stay in T\n\t\t\t\tcount[s]--;\n\t\t\t\tif (count[s] == 0 && !AandB.get(s)) {\n\t\t\t\t\t// the count is zero and s is not safe because it's in AandB\n\t\t\t\t\t//  -> remove from T and add to E\n\t\t\t\t\tT.clear(s);\n\t\t\t\t\tE.set(s);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn StateValues.createFromBitSet(T, model);\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ \"a\" R \"b\" ], i.e., from which there\n\t * exists a path satisfying G \"b\" or \"b\" U (\"a&b\")\n\t * @param model the model\n\t * @param A the BitSet for the states in \"a\"\n\t * @param A the BitSet for the states in \"a\"\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ \"a\" R \"b\" ]\n\t */\n\tpublic BitSet computeExistsRelease(Model<?> model, BitSet A, BitSet B) throws PrismException\n\t{\n\t\tPredecessorRelation pre = model.getPredecessorRelation(this, true);\n\n\t\t// the intersection of A and B\n\t\t// these states surely satisfy E[ a R b ]\n\t\tBitSet AandB = (BitSet) A.clone();\n\t\tAandB.and(B);\n\n\t\t// The set T contains all states for which E[ a R b ] has not yet been disproven\n\t\t// Initially, this contains all 'B' states\n\t\tBitSet T = (BitSet) B.clone();\n\n\t\t// the set E contains all states that have not yet been visited\n\t\t// and for which we have proven that they do not satisfy E[ a R b ]\n\t\tBitSet E = new BitSet();\n\t\t// Initially, it contains the complement of 'T'\n\t\tE.set(0, model.getNumStates(), true);\n\t\tE.andNot(T);\n\n\t\t// TODO: Important: The correctness relies on the fact that\n\t\t// the number of predecessors provided by pre.getPre()\n\t\t// and the number of successors provided by getSuccessorsIterator()\n\t\t// mirror each other. If PredecessorRelation is changed later on,\n\t\t// take this into account...\n\n\t\t// for all states s in T \\ AandB, we compute count[s], the number of (unique) successors\n\t\tint count[] = new int[model.getNumStates()];\n\t\tfor (int s : IterableBitSet.getSetBits(T)) {\n\t\t\tif (AandB.get(s)) continue;\n\n\t\t\tint i=0;\n\t\t\tfor (Iterator<Integer> it = model.getSuccessorsIterator(s); it.hasNext(); it.next()) {\n\t\t\t\ti++;\n\t\t\t}\n\t\t\tcount[s]=i;\n\t\t}\n\n\t\twhile (!E.isEmpty()) {\n\t\t\t// get the first element of E\n\t\t\tint t = E.nextSetBit(0);\n\t\t\t// and mark it as processed\n\t\t\tE.clear(t);\n\n\t\t\t// We know that t does not satisfy E[ a R b ].\n\t\t\t// Any predecessor s of t can be shown to not satisfy E[ a R b ]\n\t\t\t// if there are no remaining successors into T, i.e, if count[s]==0\n\n\t\t\t// For all predecessors s of t....\n\n\t\t\tfor (int s : pre.getPre(t)) {\n\t\t\t\t// ... ignore if we have already proven that it does not satisfy E[ a R b ]\n\t\t\t\tif (!T.get(s)) continue;\n\n\t\t\t\t// decrement count, because s can not use t to stay in T\n\t\t\t\tcount[s]--;\n\t\t\t\tif (count[s] == 0 && !AandB.get(s)) {\n\t\t\t\t\t// the count is zero and s is not safe because it's in AandB\n\t\t\t\t\t//  -> remove from T and add to E\n\t\t\t\t\tT.clear(s);\n\t\t\t\t\tE.set(s);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn T;\n\t}\n\n\t/**\n\t * Compute the set of states satisfying E[ phi ] for an LTL formula phi.\n\t * The LTL formula can have nested P or R operators, as well as nested CTL formulas.\n\t * @param model the model\n\t * @param expr the LTL formula\n\t * @param statesofInterest the states of interest\n\t * @return a boolean StateValues, with {@code true} for all states satisfying E[ phi ]\n\t */\n\tprotected StateValues checkExistsLTL(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tthrow new PrismNotSupportedException(\"Time-bounded operators not supported in LTL: \" + expr);\n\t\t}\n\n\t\tLTLModelChecker ltlMC = new LTLModelChecker(this);\n\t\tVector<BitSet> labelBS = new Vector<BitSet>();\n\t\texpr = ltlMC.checkMaximalStateFormulas(this, model, expr.deepCopy(), labelBS);\n\n\t\t// We are doing existential LTL checking:\n\t\t//  - Construct an NBA for the LTL formula\n\t\t//  - Construct product M' = M x NBA\n\t\t//  - Search for an accepting lasso in M', i.e., a reachable cycle\n\t\t//    that visits F infinitely often\n\n\t\tmainLog.println(\"Non-probabilistic LTL model checking for E[ \" +expr + \" ]\");\n\t\tmainLog.print(\"Constructing NBA...\");\n\t\tmainLog.flush();\n\t\tLTL2NBA ltl2nba = new LTL2NBA(this);\n\t\tNBA nba = ltl2nba.convertLTLFormulaToNBA(expr, this.getConstantValues());\n\t\tmainLog.println(\" NBA has \" + nba.size() + \" states\");\n\t\t// If required, export DA\n\t\tif (settings.getExportPropAut()) {\n\t\t\tmainLog.println(\"Exporting \" + \"NBA\" + \" to file \\\"\" + settings.getExportPropAutFilename() + \"\\\"...\");\n\t\t\tPrintStream out = PrismUtils.newPrintStream(settings.getExportPropAutFilename());\n\t\t\tnba.print(out, settings.getExportPropAutType());\n\t\t\tout.close();\n\t\t}\n\n\t\t// If we only care about a few states in the model,\n\t\t// it would make sense to do a nested DFS and construct the product on the fly.\n\t\t// But for now it's easier to rely on the existing infrastructure,\n\t\t// construct the full product and just compute the SCCs.\n\t\tmainLog.print(\"Constructing \" + model.getModelType()+ \"-NBA product as LTS...\");\n\t\tmainLog.flush();\n\t\tLTSNBAProduct product = LTSNBAProduct.doProduct(model, nba, statesOfInterest, labelBS);\n\t\tmainLog.println(\" \"+product.getProductModel().infoString()+\", \"+product.getAcceptingStates().cardinality()+\" states accepting\");\n\n\t\t// Note: As the NBA is not guaranteed to be complete, the product may contain\n\t\t// terminal states. The SCC computer can correctly deal with that.\n\n\t\tif (product.getAcceptingStates().isEmpty()) {\n\t\t\tmainLog.print(\"None of the states in the product are accepting, skipping further computations\");\n\t\t\t// If there are no accepting states, there is no accepting run, return all-false result\n\t\t\t// Note: In the dual case, where all states are accepting, we nevertheless have to do the\n\t\t\t// SCC analysis below, as there is no guarantee that there is actually a cycle (i.e., when\n\t\t\t// eventually all runs reach terminal states in the product)\n\t\t\treturn StateValues.createFromBitSet(new BitSet(), model);\n\t\t}\n\n\t\tmainLog.print(\"Searching for non-trivial, accepting SCCs in product LTS...\");\n\t\tmainLog.flush();\n\t\tSCCConsumerStore sccConsumerStore = new SCCConsumerStore();\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, product.getProductModel(), sccConsumerStore);\n\t\tsccComputer.computeSCCs();\n\n\t\t// We determine the SCCs that intersect F, as those are guaranteed to\n\t\t// have at least one accepting cycle. This crucially relies on the fact\n\t\t// that the SCC computer returns only non-trivial SCCs.\n\t\tint accepting = 0;\n\t\tint sccs = 0;\n\t\tBitSet acceptingSCCs = new BitSet();\n\t\tfor (BitSet scc : sccConsumerStore.getSCCs()) {\n\t\t\tsccs++;\n\t\t\tif (scc.intersects(product.getAcceptingStates())) {\n\t\t\t\tacceptingSCCs.or(scc);\n\t\t\t\taccepting++;\n\t\t\t}\n\t\t}\n\t\tmainLog.println(\" \"+accepting+\" of \"+sccs+\" non-trivial SCCs are accepting\");\n\n\t\tBitSet allStates = new BitSet();\n\t\tallStates.set(0, product.getProductModel().getNumStates());\n\n\t\t// compute the set of states that can reach an accepting cycle,\n\t\t// i.e., satisfy E[ true U acceptingSCCs ], using the CTL checker\n\t\tmainLog.println(\"Computing reachability of accepting SCCs...\");\n\t\tBitSet resultProduct = computeExistsUntil(product.getProductModel(), allStates, acceptingSCCs);\n\t\tStateValues svProduct = StateValues.createFromBitSet(resultProduct, product.getProductModel());\n\n\t\t// we project to the original model\n\t\tStateValues result = product.projectToOriginalModel(svProduct);\n\n\t\treturn result;\n\t}\n\n}\n\n"
  },
  {
    "path": "prism/src/explicit/NondetModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.HashSet;\nimport java.util.Iterator;\nimport java.util.LinkedHashSet;\nimport java.util.List;\nimport java.util.Objects;\nimport java.util.PrimitiveIterator;\nimport java.util.function.IntPredicate;\n\nimport common.IterableStateSet;\nimport explicit.graphviz.Decoration;\nimport explicit.graphviz.Decorator;\nimport io.ModelExportOptions;\nimport prism.ActionList;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport strat.MDStrategy;\n\nimport static prism.PrismSettings.DEFAULT_EXPORT_MODEL_PRECISION;\n\n/**\n * Interface for (abstract) classes that provide (read-only) access to an explicit-state model with nondeterminism.\n */\npublic interface NondetModel<Value> extends Model<Value>\n{\n\t// Accessors\n\n\t@Override\n\tdefault List<Object> findActionsUsed()\n\t{\n\t\t// Find unique actions across all choices\n\t\tif (onlyNullActionUsed()) {\n\t\t\treturn Collections.singletonList(null);\n\t\t}\n\t\tLinkedHashSet<Object> actions = new LinkedHashSet<>();\n\t\tint numStates = getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tint numChoices = getNumChoices(s);\n\t\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\t\tactions.add(getAction(s, i));\n\t\t\t}\n\t\t}\n\t\treturn new ArrayList<>(actions);\n\t}\n\n\t/**\n\t * Get the number of nondeterministic choices in state s.\n\t */\n\tint getNumChoices(int s);\n\n\t/**\n\t * Get the maximum number of nondeterministic choices in any state.\n\t */\n\tdefault int getMaxNumChoices()\n\t{\n\t\tint maxNumChoices = 0;\n\t\tfor (int state = 0, numStates = getNumStates(); state < numStates; state++) {\n\t\t\tmaxNumChoices = Math.max(maxNumChoices, getNumChoices(state));\n\t\t}\n\t\treturn maxNumChoices;\n\t}\n\n\t/**\n\t * Get the total number of nondeterministic choices over all states.\n\t */\n\tdefault int getNumChoices()\n\t{\n\t\tint numChoices = 0;\n\t\tfor (int state = 0, numStates = getNumStates(); state < numStates; state++) {\n\t\t\tnumChoices += getNumChoices(state);\n\t\t}\n\t\treturn numChoices;\n\t}\n\n\t/**\n\t * Get the action label for choice {@code i} of state {@code s}.\n\t * The action is null for an unlabelled choice.\n\t */\n\tObject getAction(int s, int i);\n\n\t/**\n\t * Get the string representation of the action label for choice {@code i} of state {@code s}.\n\t * The string is \"\" for an unlabelled choice.\n\t */\n\tdefault String getActionString(int s, int i)\n\t{\n\t\treturn ActionList.actionString(getAction(s, i));\n\t}\n\n\t/**\n\t * Get the index of the action label for choice {@code i} of state {@code s}.\n\t * Indices are into the list given by {@link #getActions()},\n\t * which includes null if there are unlabelled choices,\n\t * so this method should always return a value >= 0.\n\t */\n\tdefault int getActionIndex(int s, int i)\n\t{\n\t\treturn actionIndex(getAction(s, i));\n\t}\n\n\t/**\n\t * Get a list of the actions labelling the choices of state {@code s}.\n\t */\n\tdefault List<Object> getAvailableActions(int s)\n\t{\n\t\tList<Object> actions = new ArrayList<>();\n\t\tint numChoices = getNumChoices(s);\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tactions.add(getAction(s, i));\n\t\t}\n\t\treturn actions;\n\t}\n\n\t/**\n\t * Get the index of the (first) choice in state {@code s} with action label {@code action}.\n\t * Action labels (which are {@link Object}s) are tested for equality using\n\t * {@link Objects#equals(Object, Object)}, i.e., including null matching null.\n\t * Returns -1 if there is no matching action.\n\t */\n\tdefault int getChoiceByAction(int s, Object action)\n\t{\n\t\tint numChoices = getNumChoices(s);\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tif (Objects.equals(getAction(s, i), action)) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Do all choices in each state have a unique action label?\n\t * <br><br>\n\t * NB: \"true\" does not imply that all choices are labelled,\n\t * e.g., an a-labelled choice and an unlabelled one _are_ considered unique;\n\t * multiple unlabelled choices are _not_ considered unique.\n\t */\n\tdefault boolean areAllChoiceActionsUnique()\n\t{\n\t\tint numStates = getNumStates();\n\t\tHashSet<Object> sActions = new HashSet<>();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tint n = getNumChoices(s);\n\t\t\tif (n > 1) {\n\t\t\t\tsActions.clear();\n\t\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\t\tif (!sActions.add(getAction(s, i))) {\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Check that the available actions and their ordering\n\t * in states {@code s1} and {@code s2} match, and throw an exception if not.\n\t */\n\tdefault void checkActionsMatchExactly(int s1, int s2) throws PrismException\n\t{\n\t\tint numChoices = getNumChoices(s1);\n\t\tif (numChoices != getNumChoices(s2)) {\n\t\t\tthrow new PrismException(\"Differing actions found in states: \" + getAvailableActions(s1) + \" vs. \" + getAvailableActions(s2));\n\t\t}\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tObject action1 = getAction(s1, i);\n\t\t\tObject action2 = getAction(s2, i);\n\t\t\tif (action1 == null) {\n\t\t\t\tif (action2 != null) {\n\t\t\t\t\tthrow new PrismException(\"Differing actions found in states: \" + getAvailableActions(s1) + \" vs. \" + getAvailableActions(s2));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (!action1.equals(action2)) {\n\t\t\t\t\tthrow new PrismException(\"Differing actions found in states: \" + getAvailableActions(s1) + \" vs. \" + getAvailableActions(s2));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Check that the *sets* of available actions in states {@code s1} and {@code s2} match,\n\t * and throw an exception if not.\n\t */\n\tdefault void checkActionsMatch(int s1, int s2) throws PrismException\n\t{\n\t\t// Get and sort action strings for s1\n\t\tList<String> s1Actions = new ArrayList<>();\n\t\tint numChoices = getNumChoices(s1);\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tObject action = getAction(s1, i);\n\t\t\ts1Actions.add(action == null ? \"\" : action.toString());\n\t\t}\n\t\tCollections.sort(s1Actions);\n\t\t// Get and sort action strings for s2\n\t\tList<String> s2Actions = new ArrayList<>();\n\t\tnumChoices = getNumChoices(s2);\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tObject action = getAction(s2, i);\n\t\t\ts2Actions.add(action == null ? \"\" : action.toString());\n\t\t}\n\t\tCollections.sort(s2Actions);\n\t\t// Check match\n\t\tif (!(s1Actions.equals(s2Actions))) {\n\t\t\tthrow new PrismException(\"Differing actions found in states: \" + s1Actions + \" vs. \" + s2Actions);\n\t\t}\n\t}\n\n\t/**\n\t * Get the number of transitions from choice {@code i} of state {@code s}.\n\t */\n\tint getNumTransitions(int s, int i);\n\n\t@Override\n\tdefault int getNumTransitions(int s)\n\t{\n\t\t// Re-implement this because the method in the superclass (Model)\n\t\t// would not count successors duplicated across choices\n\t\tint numTransitions = 0;\n\t\tint n = getNumChoices(s);\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tnumTransitions += getNumTransitions(s, i);\n\t\t}\n\t\treturn numTransitions;\n\t}\n\n\t/**\n\t * Check if all the successor states from choice {@code i} of state {@code s} are in the set {@code set}.\n\t * @param s The state to check\n\t * @param i Choice index\n\t * @param set The set to test for inclusion\n\t */\n\tdefault boolean allSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn allSuccessorsMatch(s, i, set::get);\n\t}\n\t\n\t/**\n\t * Check if some successor state from choice {@code i} of state {@code s} is in the set {@code set}.\n\t * @param s The state to check\n\t * @param i Choice index\n\t * @param set The set to test for inclusion\n\t */\n\tdefault boolean someSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn someSuccessorsMatch(s, i, set::get);\n\t}\n\n\t/**\n\t * Check the successor states from choice {@code i} of state {@code s}:\n\t * Return {@code true} iff all successors are contained in {@code u}\n\t * (remain in a \"safe\" region) and at least one is contained in {@code v}\n\t * (can reach the region defined by v).\n\t * @param s The state to check\n\t * @param i Choice index\n\t * @param u The BitSet that all successors have to be in\n\t * @param v The BitSet that some successors have to be in\n\t */\n\tdefault boolean successorsSafeAndCanReach(int s, int i, BitSet u, BitSet v)\n\t{\n\t\treturn successorsSafeAndCanReach(s, i, u::get, v::get);\n\t}\n\n\t/**\n\t * Check if all the successor states from choice {@code i} of state {@code s} match the predicate.\n\t * @param s The state to check\n\t * @param i Choice index\n\t * @param p The predicate\n\t */\n\tdefault boolean allSuccessorsMatch(int s, int i, IntPredicate p)\n\t{\n\t\t// the code for this method is equivalent to the following stream expression,\n\t\t// but kept explicit for performance\n\t\t//\n\t\t// return getSuccessors(s,i).stream().allMatch(p);\n\n\t\tSuccessorsIterator it = getSuccessors(s,i);\n\t\twhile (it.hasNext()) {\n\t\t\tint t = it.nextInt();\n\t\t\tif (!p.test(t))\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Check if some successor state from choice {@code i} of state {@code s} match the predicate.\n\t * @param s The state to check\n\t * @param i Choice index\n\t * @param p The predicate\n\t */\n\tdefault boolean someSuccessorsMatch(int s, int i, IntPredicate p)\n\t{\n\t\t// the code for this method is equivalent to the following stream expression,\n\t\t// but kept explicit for performance\n\t\t//\n\t\t// return getSuccessors(s,i).stream().anyMatch(p);\n\n\t\tSuccessorsIterator it = getSuccessors(s, i);\n\t\twhile (it.hasNext()) {\n\t\t\tint t = it.nextInt();\n\t\t\tif (p.test(t))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Check the successor states from choice {@code i} of state {@code s}:\n\t * Return {@code true} iff all successors match the predicate {@code u}\n\t * (remain in a \"safe\" region) and at least one matches predicate {@code v}\n\t * (can reach the region defined by v).\n\t * @param s The state to check\n\t * @param i Choice index\n\t * @param u The first predicate (all successors have to match)\n\t * @param v The second predicate (some successors have to match)\n\t */\n\tdefault boolean successorsSafeAndCanReach(int s, int i, IntPredicate u, IntPredicate v)\n\t{\n\t\tSuccessorsIterator it = getSuccessors(s, i);\n\t\tboolean hadTransitionToV = false;\n\t\twhile (it.hasNext()) {\n\t\t\tint t = it.nextInt();\n\t\t\tif (!u.test(t))\n\t\t\t\treturn false;\n\t\t\tif (!hadTransitionToV) {\n\t\t\t\thadTransitionToV = v.test(t);\n\t\t\t}\n\t\t}\n\t\treturn hadTransitionToV;\n\t}\n\n\t/**\n\t * Get an iterator over the successor states from choice {@code i} of state {@code s}.\n\t * @param s The state\n\t * @param i Choice index\n\t */\n\tdefault Iterator<Integer> getSuccessorsIterator(int s, int i)\n\t{\n\t\tSuccessorsIterator successors = getSuccessors(s, i);\n\t\treturn successors.distinct();\n\t}\n\n\t/**\n\t * Get a SuccessorsIterator for state s and choice i.\n\t * @param s The state\n\t * @param i Choice index\n\t */\n\tSuccessorsIterator getSuccessors(int s, int i);\n\n\t@Override\n\tdefault SuccessorsIterator getSuccessors(final int s)\n\t{\n\t\treturn SuccessorsIterator.chain(new Iterator<>() {\n\t\t\tprivate int choice = 0;\n\t\t\tprivate final int choices = getNumChoices(s);\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn choice < choices;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic SuccessorsIterator next()\n\t\t\t{\n\t\t\t\treturn getSuccessors(s, choice++);\n\t\t\t}\n\t\t});\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob0, i.e., for states i in {@code subset},\n\t * set bit i of {@code result} iff, for all/some choices,\n\t * there is a transition to a state in {@code u}.\n\t * Quantification over choices is determined by {@code forall}.\n\t * @param subset Only compute for these states\n\t * @param u Set of states {@code u}\n\t * @param forall For-all or there-exists (true=for-all, false=there-exists)\n\t * @param result Store results here\n\t */\n\tdefault void prob0step(final BitSet subset, final BitSet u, final boolean forall, final BitSet result)\n\t{\n\t\tfor (PrimitiveIterator.OfInt it = new IterableStateSet(subset, getNumStates()).iterator(); it.hasNext();) {\n\t\t\tfinal int s = it.nextInt();\n\t\t\tboolean b1 = forall; // there exists or for all\n\t\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t\tboolean b2 = someSuccessorsInSet(s, choice, u);\n\t\t\t\tif (forall) {\n\t\t\t\t\tif (!b2) {\n\t\t\t\t\t\tb1 = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (b2) {\n\t\t\t\t\t\tb1 = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.set(s, b1);\n\t\t}\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob1A, i.e., for states i in {@code subset},\n\t * set bit i of {@code result} iff, for all choices,\n\t * there is a transition to a state in {@code v} and all transitions go to states in {@code u}.\n\t * @param subset Only compute for these states\n\t * @param u Set of states {@code u}\n\t * @param v Set of states {@code v}\n\t * @param result Store results here\n\t */\n\tdefault void prob1Astep(BitSet subset, BitSet u, BitSet v, BitSet result)\n\t{\n\t\tboolean b1;\n\t\tfor (PrimitiveIterator.OfInt it = new IterableStateSet(subset, getNumStates()).iterator(); it.hasNext();) {\n\t\t\tfinal int s = it.nextInt();\n\t\t\tb1 = true;\n\t\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t\tif (!(successorsSafeAndCanReach(s, choice, u, v))) {\n\t\t\t\t\tb1 = false;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.set(s, b1);\n\t\t}\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob1E, i.e., for states i in {@code subset},\n\t * set bit i of {@code result} iff, for some choice,\n\t * there is a transition to a state in {@code v} and all transitions go to states in {@code u}.\n\t * Optionally, store optimal (memoryless) strategy info for 1 states.\n\t * @param subset Only compute for these states\n\t * @param u Set of states {@code u}\n\t * @param v Set of states {@code v}\n\t * @param result Store results here\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tdefault void prob1Estep(BitSet subset, BitSet u, BitSet v, BitSet result, int[] strat)\n\t{\n\t\tint stratCh = -1;\n\t\tboolean b1;\n\t\tfor (PrimitiveIterator.OfInt it = new IterableStateSet(subset, getNumStates()).iterator(); it.hasNext();) {\n\t\t\tfinal int s = it.nextInt();\n\t\t\tb1 = false;\n\t\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t\tif (successorsSafeAndCanReach(s, choice, u, v)) {\n\t\t\t\t\tb1 = true;\n\t\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\t\tif (strat != null)\n\t\t\t\t\t\tstratCh = choice;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// If strategy generation is enabled, store optimal choice\n\t\t\t// (only if this the first time we add the state to S^yes)\n\t\t\tif (strat != null & b1 & !result.get(s)) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t\t// Store result\n\t\t\tresult.set(s, b1);\n\t\t}\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob1, i.e., for states i in {@code subset},\n\t * set bit i of {@code result} iff, for all/some choices,\n\t * there is a transition to a state in {@code v} and all transitions go to states in {@code u}.\n\t * Quantification over choices is determined by {@code forall}.\n\t * @param subset Only compute for these states\n\t * @param u Set of states {@code u}\n\t * @param v Set of states {@code v}\n\t * @param forall For-all or there-exists (true=for-all, false=there-exists)\n\t * @param result Store results here\n\t */\n\tdefault void prob1step(BitSet subset, BitSet u, BitSet v, boolean forall, BitSet result)\n\t{\n\t\tboolean b1, b2;\n\t\tfor (PrimitiveIterator.OfInt it = new IterableStateSet(subset, getNumStates()).iterator(); it.hasNext();) {\n\t\t\tfinal int s = it.nextInt();\n\t\t\tb1 = forall; // there exists or for all\n\t\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t\tb2 = successorsSafeAndCanReach(s, choice, u, v);\n\t\t\t\tif (forall) {\n\t\t\t\t\tif (!b2) {\n\t\t\t\t\t\tb1 = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (b2) {\n\t\t\t\t\t\tb1 = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.set(s, b1);\n\t\t}\n\t}\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob1 for a single state/choice,\n\t * i.e., return whether there is a transition to a state in {@code v} and all transitions go to states in {@code u}.\n\t * @param s State (row) index\n\t * @param i Choice index\n\t * @param u Set of states {@code u}\n\t * @param v Set of states {@code v}\n\t */\n\tdefault boolean prob1stepSingle(int s, int i, BitSet u, BitSet v)\n\t{\n\t\treturn successorsSafeAndCanReach(s, i, u, v);\n\t}\n\n\t/**\n\t * Construct a model that is induced by applying strategy {@code strat} to this model.\n\t * Note that the \"new\" model may be just an implicit (read-only) representation. \n\t * @param strat (Memoryless) strategy to use\n\t */\n\tModel<Value> constructInducedModel(MDStrategy<Value> strat);\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark' and choices for a (memoryless) strategy.\n\t */\n\tdefault void exportToDotFileWithStrat(PrismLog out, BitSet mark, int[] strat) throws PrismException\n\t{\n\t\texportToDotFileWithStrat(out, mark, strat, DEFAULT_EXPORT_MODEL_PRECISION);\n\t}\n\n\t/**\n\t * Export to a dot file, highlighting states in 'mark' and choices for a (memoryless) strategy.\n\t *\n\t * @param precision number of significant digits >= 1\n\t */\n\tdefault void exportToDotFileWithStrat(PrismLog out, BitSet mark, int[] strat, int precision) throws PrismException\n\t{\n\t\tList<Decorator> decorators = new ArrayList<>();\n\t\tif (mark != null) {\n\t\t\tdecorators.add(new Decorator()\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic Decoration decorateState(int state, Decoration d)\n\t\t\t\t{\n\t\t\t\t\tif (mark.get(state)) {\n\t\t\t\t\t\td.attributes().put(\"style\", \"filled\");\n\t\t\t\t\t\td.attributes().put(\"fillcolor\", \"#cccccc\");\n\t\t\t\t\t}\n\t\t\t\t\treturn d;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\tif (strat != null) {\n\t\t\tdecorators.add(new Decorator()\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic Decoration decorateTransition(int state, int choice, Decoration d)\n\t\t\t\t{\n\t\t\t\t\tif (strat[state] == choice) {\n\t\t\t\t\t\td.attributes().put(\"color\", \"#ff0000\");\n\t\t\t\t\t\td.attributes().put(\"fontcolor\", \"#ff0000\");\n\t\t\t\t\t}\n\t\t\t\t\treturn d;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\texportToDotFile(out, new ModelExportOptions().setModelPrecision(precision), decorators);\n\t}\n}"
  },
  {
    "path": "prism/src/explicit/NondetModelSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\n/**\n * Interface for simple mutable explicit-state nondeterministic model representations\n * (i.e. classes that implement both {@link explicit.NondetModel} and {@link explicit.ModelSimple}).\n */\npublic interface NondetModelSimple<Value> extends NondetModel<Value>, ModelSimple<Value>\n{\n}"
  },
  {
    "path": "prism/src/explicit/ObservationsSimple.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport parser.State;\nimport prism.PrismException;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\n/**\n * Explicit-state storage of the info about observations in a (partially observable) model.\n *\n * Uses simple, mutable data structures, matching the \"Simple\" range of models.\n */\npublic class ObservationsSimple\n{\n\t/**\n\t * Number of states in the parent model\n\t */\n\tprotected int numStates;\n\n\t/**\n\t * Information about the observations of this model.\n\t * Each observation is a State containing the value for each observable.\n\t */\n\tprotected List<State> observationsList;\n\n\t/**\n\t * Information about the unobservations of this model.\n\t * Each observation is a State containing the value of variables that are not observable.\n\t */\n\tprotected List<State> unobservationsList;\n\n\t/** One state corresponding to each observation (used to look up info about it) */\n\tprotected List<Integer> observationStates;\n\n\t/** Observable assigned to each state */\n\tprotected List<Integer> observablesMap;\n\n\t/** Unobservable assigned to each state */\n\tprotected List<Integer> unobservablesMap;\n\n\t/**\n\t * Constructor: empty observation info\n\t */\n\tpublic ObservationsSimple()\n\t{\n\t\tnumStates = 0;\n\t\tobservationsList = new ArrayList<>();\n\t\tunobservationsList = new ArrayList<>();\n\t\tobservationStates = new ArrayList<>();\n\t\tobservablesMap = new ArrayList<>();\n\t\tunobservablesMap = new ArrayList<>();\n\t}\n\n\t/**\n\t * Constructor: initialise storage for observable info when the model has {@code numStates} states\n\t */\n\tpublic ObservationsSimple(int numStates)\n\t{\n\t\tthis();\n\t\taddStates(numStates);\n\t}\n\n\t/**\n\t * Constructor: initialise storage for observable info when the model has\n\t * {@code numStates} states and {@code numObservations} observations.\n\t */\n\tpublic ObservationsSimple(int numStates, int numObservations)\n\t{\n\t\tthis();\n\t\taddStates(numStates);\n\t\taddObservations(numObservations);\n\t}\n\n\t/**\n\t * Copy constructor\n\t */\n\tpublic ObservationsSimple(ObservationsSimple obs)\n\t{\n\t\tthis.numStates = obs.numStates;\n\t\tobservationsList = new ArrayList<>(obs.observationsList);\n\t\tunobservationsList = new ArrayList<>(obs.unobservationsList);\n\t\tobservationStates = new ArrayList<>(obs.observationStates);\n\t\tobservablesMap = new ArrayList<>(obs.observablesMap);\n\t\tunobservablesMap = new ArrayList<>(obs.unobservablesMap);\n\t}\n\n\t/**\n\t * Copy constructor, but with a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t */\n\tpublic ObservationsSimple(ObservationsSimple obs, int permut[])\n\t{\n\t\tthis.numStates = obs.numStates;\n\t\tobservationsList = new ArrayList<>(obs.observationsList);\n\t\tunobservationsList = new ArrayList<>(obs.unobservationsList);\n\t\tint numObservations = obs.observationsList.size();\n\t\tobservationStates = new ArrayList<>(numObservations);\n\t\tfor (int o = 0; o < numObservations; o++) {\n\t\t\tint s = obs.observationStates.get(o);\n\t\t\tobservationStates.add(s == -1 ? -1 : permut[s]);\n\t\t}\n\t\tobservablesMap = new ArrayList<Integer>(numStates);\n\t\tunobservablesMap = new ArrayList<Integer>(numStates);\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tobservablesMap.add(-1);\n\t\t\tunobservablesMap.add(-1);\n\t\t}\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tobservablesMap.set(permut[s], obs.observablesMap.get(s));\n\t\t\tunobservablesMap.set(permut[s], obs.unobservablesMap.get(s));\n\t\t}\n\t}\n\n\t// Mutators\n\n\t/**\n\t * Initialise observation info for {@code numToAdd} new observations.\n\t */\n\tpublic void addObservations(int numToAdd)\n\t{\n\t\tfor (int i = 0; i < numToAdd; i++) {\n\t\t\tobservationsList.add(null);\n\t\t\tobservationStates.add(-1);\n\t\t}\n\t}\n\n\t/**\n\t * Clear observation info for state {@code s}.\n\t */\n\tpublic void clearState(int s)\n\t{\n\t\tobservablesMap.set(s, -1);\n\t\tunobservablesMap.set(s, -1);\n\t}\n\n\n\t/**\n\t * Initialise observation info for {@code numToAdd} new states.\n\t */\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tnumStates += numToAdd;\n\t\tfor (int i = 0; i < numToAdd; i++) {\n\t\t\tobservablesMap.add(-1);\n\t\t\tunobservablesMap.add(-1);\n\t\t}\n\t}\n\n\t/**\n\t * Set the associated (read-only) observation list.\n\t */\n\tpublic void setObservationsList(List<State> observationsList)\n\t{\n\t\tthis.observationsList = observationsList;\n\t}\n\n\t/**\n\t * Set the associated (read-only) unobservation list.\n\t */\n\tpublic void setUnobservationsList(List<State> unobservationsList)\n\t{\n\t\tthis.unobservationsList = unobservationsList;\n\t}\n\n\t/**\n\t * Set the observation info for a state.\n\t * If the actions for existing states with this observation do not match,\n\t * an explanatory exception is thrown (so this should be done after transitions\n\t * have been added to the state). Optionally, a list of names of the\n\t * observables can be passed for error reporting.\n\t * @param s State\n\t * @param observ Observation\n\t * @param unobserv Unobservation\n\t * @param observableNames Names of observables (optional)\n\t * @param model Parent model (for action checks, optional)\n\t */\n\tpublic void setObservation(int s, State observ, State unobserv, List<String> observableNames, NondetModel model) throws PrismException\n\t{\n\t\t// See if the observation already exists and add it if not\n\t\tint oIndex = observationsList.indexOf(observ);\n\t\tif (oIndex == -1) {\n\t\t\t// Add new observation\n\t\t\tobservationsList.add(observ);\n\t\t\toIndex = observationsList.size() - 1;\n\t\t\t// Also extend the observationStates list, to be filled shortly\n\t\t\tobservationStates.add(-1);\n\t\t}\n\t\t// Assign the observation (index) to the state\n\t\ttry {\n\t\t\tsetObservation(s, oIndex, model);\n\t\t} catch (PrismException e) {\n\t\t\tString sObs = observableNames == null ? observ.toString() : observ.toString(observableNames);\n\t\t\tthrow new PrismException(\"Problem with observation \" + sObs + \": \" + e.getMessage());\n\t\t}\n\t\t// See if the unobservation already exists and add it if not\n\t\tint unobservIndex = unobservationsList.indexOf(unobserv);\n\t\tif (unobservIndex == -1) {\n\t\t\tunobservationsList.add(unobserv);\n\t\t\tunobservIndex = unobservationsList.size() - 1;\n\t\t}\n\t\t// Assign the unobservation (index) to the state\n\t\tsetUnobservation(s, unobservIndex);\n\t}\n\n\t/**\n\t * Assign observation with index o to state s.\n\t * (assumes observation has already been added to the list)\n\t * If the actions for existing states with this observation do not match,\n\t * an explanatory exception is thrown (so this should be done after transitions\n\t * have been added to the state).\n\t * @param s State\n\t * @param o Observation\n\t * @param model Parent model (for action checks, optional)\n\t */\n\tprotected void setObservation(int s, int o, NondetModel model) throws PrismException\n\t{\n\t\t// Set observation\n\t\tobservablesMap.set(s, o);\n\t\t// If this is first state with this observation, store its index\n\t\tint observationState = observationStates.get(o);\n\t\tif (observationState == -1) {\n\t\t\tobservationStates.set(o, s);\n\t\t}\n\t\t// Otherwise, check that the actions for existing states with\n\t\t// the same observation match this one\n\t\telse {\n\t\t\tif (model != null) {\n\t\t\t\tmodel.checkActionsMatchExactly(s, observationState);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Assign unobservation with index u to state s.\n\t * (assumes unobservation has already been added to the list)\n\t * @param s State\n\t * @param u Unobservation\n\t */\n\tprotected void setUnobservation(int s, int u)\n\t{\n\t\tunobservablesMap.set(s, u);\n\t}\n\n\t/**\n\t * Set the observation for each state {@code s} to be {@code s}.\n\t */\n\tprotected void setIdentityObservations()\n\t{\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t// Observation of a state is the state itself\n\t\t\ttry {\n\t\t\t\tsetObservation(s, s, null);\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// Won't happen\n\t\t\t}\n\t\t\t// Unobservation of a state is null\n\t\t\tunobservablesMap.set(s, null);\n\t\t}\n\t}\n\n\t// Accessors\n\n\t/**\n\t * Get access to a list of observations (optionally stored).\n\t */\n\tpublic List<State> getObservationsList()\n\t{\n\t\treturn observationsList;\n\t}\n\n\t/**\n\t * Get access to a list of unobservations (optionally stored).\n\t */\n\tpublic List<State> getUnobservationsList()\n\t{\n\t\treturn unobservationsList;\n\t}\n\n\t/**\n\t * Get the observation of state {@code s}.\n\t */\n\tpublic int getObservation(int s)\n\t{\n\t\treturn observablesMap == null ? -1 : observablesMap.get(s);\n\t}\n\n\t/**\n\t * Get the unobservation of state {@code s}.\n\t */\n\tpublic int getUnobservation(int s)\n\t{\n\t\treturn unobservablesMap.get(s);\n\t}\n\n\t/**\n\t * Get the index of one state corresponding to observation {@code o}.\n\t */\n\tpublic int getObservationState(int o)\n\t{\n\t\treturn observationStates.get(o);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/POMDP.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Xueyi Zou <xz972@york.ac.uk> (University of York)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.HashMap;\nimport java.util.Iterator;\nimport java.util.Map;\nimport java.util.TreeMap;\n\nimport explicit.rewards.MDPRewards;\nimport prism.ModelType;\nimport prism.PrismLog;\nimport prism.PrismUtils;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state POMDP.\n * <br><br>\n * POMDPs require that states with the same observation have the same set of\n * available actions. Class implementing this interface must further ensure\n * that these actions appear in the same order (in terms of choice indexing)\n * in each observationally equivalent state.\n */\npublic interface POMDP<Value> extends MDP<Value>, PartiallyObservableModel<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.POMDP;\n\t}\n\n\t// Accessors\n\t\n\t/**\n\t * Get the action label (if any) for choice {@code i} of observation {@code o}\n\t * (this is the same for all states with this observation).\n\t */\n\tpublic Object getActionForObservation(int o, int i);\n\t\n\t/**\n\t * Get the index of the (first) choice of observation {@code o} with action label {@code action}.\n\t * Action labels (which are {@link Object}s) are tested for equality using {@link Object#equals(Object)}.\n\t * Returns -1 if there is no matching action.\n\t */\n\tpublic default int getChoiceByActionForObservation(int o, Object action)\n\t{\n\t\tint numChoices = getNumChoicesForObservation(o);\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tObject a = getActionForObservation(o, i);\n\t\t\tif (a == null) {\n\t\t\t\tif (action == null) {\n\t\t\t\t\treturn i;\n\t\t\t\t}\n\t\t\t} else if (a.equals(action)) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Get the initial belief state, as a {@link Belief} object.\n\t */\n\tpublic Belief getInitialBelief();\n\n\t/**\n\t * Get the initial belief state, as an array of probabilities over all states.\n\t */\n\tpublic double[] getInitialBeliefInDist();\n\n\t/**\n\t * Get the belief state (as a {@link Belief} object)\n\t * after taking the {@code i}th choice from belief state {@code belief}.\n\t */\n\tpublic Belief getBeliefAfterChoice(Belief belief, int i);\n\n\t/**\n\t * Get the belief state (as an array of probabilities over all states)\n\t * after taking the {@code i}th choice from belief state {@code belief}.\n\t */\n\tpublic double[] getBeliefInDistAfterChoice(double[] belief, int i);\n\n\t/**\n\t * Get the belief state (as a {@link Belief} object)\n\t * after taking the {@code i}th choice from belief state {@code belief}\n\t * and seeing observation {@code o} in the next state.\n\t */\n\tpublic Belief getBeliefAfterChoiceAndObservation(Belief belief, int i, int o);\n\n\t/**\n\t * Get the belief state (as an array of probabilities over all states)\n\t * after taking the {@code i}th choice from belief state {@code belief}\n\t * and seeing observation {@code o} in the next state.\n\t */\n\tpublic double[] getBeliefInDistAfterChoiceAndObservation(double[] belief, int i, int o);\n\n\t/**\n\t * Get the probability of seeing observation {@code o} after taking the\n\t * {@code i}th choice from belief state {@code belief}.\n\t */\n\tpublic double getObservationProbAfterChoice(Belief belief, int i, int o);\n\n\t/**\n\t * Get the probability of seeing observation {@code o} after taking the\n\t * {@code i}th choice from belief state {@code belief}.\n\t * The belief state is given as an array of probabilities over all states.\n\t */\n\tpublic double getObservationProbAfterChoice(double[] belief, int i, int o);\n\n\t/**\n\t * Get the (non-zero) probabilities of seeing each observation after taking the\n\t * {@code i}th choice from belief state {@code belief}.\n\t * The belief state is given as an array of probabilities over all states.\n\t */\n\tpublic HashMap<Integer, Double> computeObservationProbsAfterAction(double[] belief, int i);\n\t\n\t/**\n\t * Get the expected (state and transition) reward value when taking the\n\t * {@code i}th choice from belief state {@code belief}.\n\t */\n\tpublic double getRewardAfterChoice(Belief belief, int i, MDPRewards<Double> mdpRewards);\n\n\t/**\n\t * Get the expected (state and transition) reward value when taking the\n\t * {@code i}th choice from belief state {@code belief}.\n\t * The belief state is given as an array of probabilities over all states.\n\t */\n\tpublic double getRewardAfterChoice(double[] belief, int i, MDPRewards<Double> mdpRewards);\n}\n"
  },
  {
    "path": "prism/src/explicit/POMDPModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Xueyi Zou <xz972@york.ac.uk> (University of York)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.HashMap;\nimport java.util.LinkedList;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\nimport java.util.function.BiFunction;\nimport java.util.function.Function;\n\nimport explicit.graphviz.Decoration;\nimport explicit.graphviz.Decorator;\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.StateRewardsSimple;\nimport prism.*;\nimport strat.FMDObsStrategyBeliefs;\nimport strat.StrategyExportOptions;\n\n/**\n * Explicit-state model checker for partially observable Markov decision processes (POMDPs).\n */\npublic class POMDPModelChecker extends ProbModelChecker\n{\n\t// Some local data structures for convenience\n\t\n\t/**\n\t * Info for a single state of a belief MDP:\n\t * (1) a list (over choices in the state) of distributions over beliefs, stored as hashmap;\n\t * (2) optionally, a list (over choices in the state) of rewards\n\t */\n\tclass BeliefMDPState\n\t{\n\t\tpublic List<HashMap<Belief, Double>> trans;\n\t\tpublic List<Double> rewards;\n\t\tpublic BeliefMDPState()\n\t\t{\n\t\t\ttrans = new ArrayList<>();\n\t\t\trewards = new ArrayList<>();\n\t\t}\n\t}\n\t\n\t/**\n\t * Value backup function for belief state value iteration:\n\t * mapping from a state and its definition (reward + transitions)\n\t * to a pair of the optimal value + choice index. \n\t */\n\t@FunctionalInterface\n\tinterface BeliefMDPBackUp extends BiFunction<Belief, BeliefMDPState, Pair<Double, Integer>> {}\n\t\n\t/**\n\t * A model constructed to represent a fragment of a belief MDP induced by a strategy:\n\t * (1) the model (represented as an MDP for ease of storing actions labels)\n\t * (2) states of the MDP, of the form (o,m) where o is the index of an observable\n\t *     and m is the index (into unobsBeliefs) of a distribution over unobservables\n\t * (3) list of distributions over unobservables appearing in belief states\n\t * (4) optionally, a reward structure\n\t */\n\tclass POMDPStrategyModel\n\t{\n\t\tpublic MDP<Double> mdp;\n\t\tpublic List<int[]> mdpStates;\n\t\tpublic List<double[]> unobsBeliefs;\n\t\tpublic MDPRewards<Double> mdpRewards;\n\t}\n\t\n\t/**\n\t * Create a new POMDPModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic POMDPModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Compute reachability/until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * while remaining in those in @{code remain}.\n\t * @param pomdp The POMDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeReachProbs(POMDP<Double> pomdp, BitSet remain, BitSet target, boolean min, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tlong timer;\n\n\t\t// Check we are only computing for a single state (and use initial state if unspecified)\n\t\tif (statesOfInterest == null) {\n\t\t\tstatesOfInterest = new BitSet();\n\t\t\tstatesOfInterest.set(pomdp.getFirstInitialState());\n\t\t} else if (statesOfInterest.cardinality() > 1) {\n\t\t\tthrow new PrismNotSupportedException(\"POMDPs can only be solved from a single start state\");\n\t\t}\n\t\t\n\t\t// Start probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting probabilistic reachability (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Compute rewards\n\t\tres = computeReachProbsFixedGrid(pomdp, remain, target, min, statesOfInterest.nextSetBit(0));\n\n\t\t// Finished probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Probabilistic reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute reachability/until probabilities,\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * while remaining in those in @{code remain},\n\t * using Lovejoy's fixed-resolution grid approach.\n\t * This only computes the probabiity from a single start state\n\t * @param pomdp The POMDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param sInit State to compute for\n\t */\n\tprotected ModelCheckerResult computeReachProbsFixedGrid(POMDP<Double> pomdp, BitSet remain, BitSet target, boolean min, int sInit) throws PrismException\n\t{\n\t\t// Start fixed-resolution grid approximation\n\t\tlong timer = System.currentTimeMillis();\n\t\tmainLog.println(\"Starting fixed-resolution grid approximation (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Find out the observations for the target/remain states\n\t\tBitSet targetObs = getObservationsMatchingStates(pomdp, target);;\n\t\tif (targetObs == null) {\n\t\t\tthrow new PrismException(\"Target for reachability is not observable\");\n\t\t}\n\t\tBitSet remainObs = (remain == null) ? null : getObservationsMatchingStates(pomdp, remain);\n\t\tif (remain != null && remainObs == null) {\n\t\t\tthrow new PrismException(\"Left-hand side of until is not observable\");\n\t\t}\n\t\tmainLog.println(\"target obs=\" + targetObs.cardinality() + (remainObs == null ? \"\" : \", remain obs=\" + remainObs.cardinality()));\n\t\t\n\t\t// Determine set of observations actually need to perform computation for\n\t\tBitSet unknownObs = new BitSet();\n\t\tunknownObs.set(0, pomdp.getNumObservations());\n\t\tunknownObs.andNot(targetObs);\n\t\tif (remainObs != null) {\n\t\t\tunknownObs.and(remainObs);\n\t\t}\n\n\t\t// Initialise the grid points (just for unknown beliefs)\n\t\tList<Belief> gridPoints = initialiseGridPoints(pomdp, unknownObs);\n\t\tmainLog.println(\"Grid statistics: resolution=\" + gridResolution + \", points=\" + gridPoints.size());\n\t\t// Construct grid belief \"MDP\"\n\t\tmainLog.println(\"Building belief space approximation...\");\n\t\tList<BeliefMDPState> beliefMDP = buildBeliefMDP(pomdp, null, gridPoints);\n\t\t\n\t\t// Initialise hashmaps for storing values for the unknown belief states\n\t\tHashMap<Belief, Double> vhash = new HashMap<>();\n\t\tHashMap<Belief, Double> vhash_backUp = new HashMap<>();\n\t\tfor (Belief belief : gridPoints) {\n\t\t\tvhash.put(belief, 0.0);\n\t\t\tvhash_backUp.put(belief, 0.0);\n\t\t}\n\t\t// Define value function for the full set of belief states\n\t\tFunction<Belief, Double> values = belief -> approximateReachProb(belief, vhash_backUp, targetObs, unknownObs);\n\t\t// Define value backup function\n\t\tBeliefMDPBackUp backup = (belief, beliefState) -> approximateReachProbBackup(belief, beliefState, values, min);\n\t\t\n\t\t// Start iterations\n\t\tmainLog.println(\"Solving belief space approximation...\");\n\t\tlong timer2 = System.currentTimeMillis();\n\t\tint iters = 0;\n\t\tboolean done = false;\n\t\twhile (!done && iters < maxIters) {\n\t\t\t// Iterate over all (unknown) grid points\n\t\t\tint unK = gridPoints.size();\n\t\t\tfor (int b = 0; b < unK; b++) {\n\t\t\t\tBelief belief = gridPoints.get(b);\n\t\t\t\tPair<Double, Integer> valChoice = backup.apply(belief, beliefMDP.get(b));\n\t\t\t\tvhash.put(belief, valChoice.first);\n\t\t\t}\n\t\t\t// Check termination\n\t\t\tdone = PrismUtils.doublesAreClose(vhash, vhash_backUp, termCritParam, termCrit == TermCrit.RELATIVE);\n\t\t\t// back up\t\n\t\t\tSet<Map.Entry<Belief, Double>> entries = vhash.entrySet();\n\t\t\tfor (Map.Entry<Belief, Double> entry : entries) {\n\t\t\t\tvhash_backUp.put(entry.getKey(), entry.getValue());\n\t\t\t}\n\t\t\titers++;\n\t\t}\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\";\n\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\t\ttimer2 = System.currentTimeMillis() - timer2;\n\t\tmainLog.print(\"Belief space value iteration (\" + (min ? \"min\" : \"max\") + \")\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer2 / 1000.0 + \" seconds.\");\n\t\t\n\t\t// Extract (approximate) solution value for the initial belief\n\t\t// Also get (approximate) accuracy of result from value iteration\n\t\tBelief initialBelief = Belief.pointDistribution(sInit, pomdp);\n\t\tdouble outerBound = values.apply(initialBelief);\n\t\tdouble outerBoundMaxDiff = PrismUtils.measureSupNorm(vhash, vhash_backUp, termCrit == TermCrit.RELATIVE);\n\t\tAccuracy outerBoundAcc = AccuracyFactory.valueIteration(termCritParam, outerBoundMaxDiff, termCrit == TermCrit.RELATIVE);\n\t\t// Print result\n\t\tmainLog.println(\"Outer bound: \" + outerBound + \" (\" + outerBoundAcc.toString(outerBound) + \")\");\n\t\t\n\t\t// Build DTMC to get inner bound (and strategy)\n\t\tmainLog.println(\"\\nBuilding strategy-induced model...\");\n\t\tPOMDPStrategyModel psm = buildStrategyModel(pomdp, sInit, null, targetObs, unknownObs, backup);\n\t\tMDP<Double> mdp = psm.mdp;\n\t\tmainLog.print(\"Strategy-induced model: \" + mdp.infoString());\n\n\t\t// Create/export strategy if requested\n\t\t// (exporting in Dot format if filename extension is .dot, otherwise .tra format)\n\t\tFMDObsStrategyBeliefs stratFmdObs = null;\n\t\tif (genStrat) {\n\t\t\tstratFmdObs = new FMDObsStrategyBeliefs<>(pomdp, psm.mdp, psm.mdpStates, psm.unobsBeliefs);\n\t\t}\n\n\t\t// Create MDP model checker (disable strat generation - if enabled, we want the POMDP one)\n\t\tMDPModelChecker mcMDP = new MDPModelChecker(this);\n\t\tmcMDP.setGenStrat(false);\n\t\t// Solve MDP to get inner bound\n\t\t// (just reachability: can ignore \"remain\" since violating states are absent)\n\t\tModelCheckerResult mcRes = mcMDP.computeReachProbs(mdp, mdp.getLabelStates(\"target\"), true);\n\t\tdouble innerBound = mcRes.soln[0];\n\t\tAccuracy innerBoundAcc = mcRes.accuracy;\n\t\t// Print result\n\t\tString innerBoundStr = \"\" + innerBound;\n\t\tif (innerBoundAcc != null) {\n\t\t\tinnerBoundStr += \" (\" + innerBoundAcc.toString(innerBound) + \")\";\n\t\t}\n\t\tmainLog.println(\"Inner bound: \" + innerBoundStr);\n\n\t\t// Finished fixed-resolution grid approximation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"\\nFixed-resolution grid approximation (\" + (min ? \"min\" : \"max\") + \")\");\n\t\tmainLog.println(\" took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Extract and store result\n\t\tPair<Double,Accuracy> resultValAndAcc;\n\t\tif (min) {\n\t\t\tresultValAndAcc = AccuracyFactory.valueAndAccuracyFromInterval(outerBound, outerBoundAcc, innerBound, innerBoundAcc);\n\t\t} else {\n\t\t\tresultValAndAcc = AccuracyFactory.valueAndAccuracyFromInterval(innerBound, innerBoundAcc, outerBound, outerBoundAcc);\n\t\t}\n\t\tdouble resultVal = resultValAndAcc.first;\n\t\tAccuracy resultAcc = resultValAndAcc.second;\n\t\tmainLog.println(\"Result bounds: [\" + resultAcc.getResultLowerBound(resultVal) + \",\" + resultAcc.getResultUpperBound(resultVal) + \"]\");\n\t\tdouble soln[] = new double[pomdp.getNumStates()];\n\t\tsoln[sInit] = resultVal;\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\t\n\t\tif (genStrat) {\n\t\t\tres.strat = stratFmdObs;\n\t\t}\n\t\t\n\t\tres.soln = soln;\n\t\tres.accuracy = resultAcc;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards,\n\t * i.e. compute the min/max reward accumulated to reach a state in {@code target}.\n\t * @param pomdp The POMDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param min Min or max rewards (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeReachRewards(POMDP<Double> pomdp, MDPRewards<Double> mdpRewards, BitSet target, boolean min, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tlong timer;\n\t\t\n\t\t// Check we are only computing for a single state (and use initial state if unspecified)\n\t\tif (statesOfInterest == null) {\n\t\t\tstatesOfInterest = new BitSet();\n\t\t\tstatesOfInterest.set(pomdp.getFirstInitialState());\n\t\t} else if (statesOfInterest.cardinality() > 1) {\n\t\t\tthrow new PrismNotSupportedException(\"POMDPs can only be solved from a single start state\");\n\t\t}\n\t\t\n\t\t// Start expected reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting expected reachability (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Compute rewards\n\t\tres = computeReachRewardsFixedGrid(pomdp, mdpRewards, target, min, statesOfInterest.nextSetBit(0));\n\n\t\t// Finished expected reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Expected reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using Lovejoy's fixed-resolution grid approach.\n\t * This only computes the expected reward from a single start state\n\t * @param pomdp The POMMDP\n\t * @param mdpRewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param min Min or max rewards (true=min, false=max)\n\t * @param sInit State to compute for\n\t */\n\tprotected ModelCheckerResult computeReachRewardsFixedGrid(POMDP<Double> pomdp, MDPRewards<Double> mdpRewards, BitSet target, boolean min, int sInit) throws PrismException\n\t{\n\t\t// Start fixed-resolution grid approximation\n\t\tlong timer = System.currentTimeMillis();\n\t\tmainLog.println(\"Starting fixed-resolution grid approximation (\" + (min ? \"min\" : \"max\") + \")...\");\n\n\t\t// Find out the observations for the target states\n\t\tBitSet targetObs = getObservationsMatchingStates(pomdp, target);;\n\t\tif (targetObs == null) {\n\t\t\tthrow new PrismException(\"Target for expected reachability is not observable\");\n\t\t}\n\t\t\n\t\t// Find _some_ of the states with infinite reward\n\t\t// (those from which *every* MDP strategy has prob<1 of reaching the target,\n\t\t// and therefore so does every POMDP strategy)\n\t\tMDPModelChecker mcProb1 = new MDPModelChecker(this);\n\t\tBitSet inf = mcProb1.prob1(pomdp, null, target, false, null);\n\t\tinf.flip(0, pomdp.getNumStates());\n\t\t// Find observations for which all states are known to have inf reward\n\t\tBitSet infObs = getObservationsCoveredByStates(pomdp, inf);\n\t\tmainLog.println(\"target obs=\" + targetObs.cardinality() + \", inf obs=\" + infObs.cardinality());\n\t\t\n\t\t// Determine set of observations actually need to perform computation for\n\t\tBitSet unknownObs = new BitSet();\n\t\tunknownObs.set(0, pomdp.getNumObservations());\n\t\tunknownObs.andNot(targetObs);\n\t\tunknownObs.andNot(infObs);\n\n\t\t// Initialise the grid points (just for unknown beliefs)\n\t\tList<Belief> gridPoints = initialiseGridPoints(pomdp, unknownObs);\n\t\tmainLog.println(\"Grid statistics: resolution=\" + gridResolution + \", points=\" + gridPoints.size());\n\t\t// Construct grid belief \"MDP\"\n\t\tmainLog.println(\"Building belief space approximation...\");\n\t\tList<BeliefMDPState> beliefMDP = buildBeliefMDP(pomdp, mdpRewards, gridPoints);\n\t\t\n\t\t// Initialise hashmaps for storing values for the unknown belief states\n\t\tHashMap<Belief, Double> vhash = new HashMap<>();\n\t\tHashMap<Belief, Double> vhash_backUp = new HashMap<>();\n\t\tfor (Belief belief : gridPoints) {\n\t\t\tvhash.put(belief, 0.0);\n\t\t\tvhash_backUp.put(belief, 0.0);\n\t\t}\n\t\t// Define value function for the full set of belief states\n\t\tFunction<Belief, Double> values = belief -> approximateReachReward(belief, vhash_backUp, targetObs, infObs);\n\t\t// Define value backup function\n\t\tBeliefMDPBackUp backup = (belief, beliefState) -> approximateReachRewardBackup(belief, beliefState, values, min);\n\t\t\n\t\t// Start iterations\n\t\tmainLog.println(\"Solving belief space approximation...\");\n\t\tlong timer2 = System.currentTimeMillis();\n\t\tint iters = 0;\n\t\tboolean done = false;\n\t\twhile (!done && iters < maxIters) {\n\t\t\t// Iterate over all (unknown) grid points\n\t\t\tint unK = gridPoints.size();\n\t\t\tfor (int b = 0; b < unK; b++) {\n\t\t\t\tBelief belief = gridPoints.get(b);\n\t\t\t\tPair<Double, Integer> valChoice = backup.apply(belief, beliefMDP.get(b));\n\t\t\t\tvhash.put(belief, valChoice.first);\n\t\t\t}\n\t\t\t// Check termination\n\t\t\tdone = PrismUtils.doublesAreClose(vhash, vhash_backUp, termCritParam, termCrit == TermCrit.RELATIVE);\n\t\t\t// back up\t\n\t\t\tSet<Map.Entry<Belief, Double>> entries = vhash.entrySet();\n\t\t\tfor (Map.Entry<Belief, Double> entry : entries) {\n\t\t\t\tvhash_backUp.put(entry.getKey(), entry.getValue());\n\t\t\t}\n\t\t\titers++;\n\t\t}\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\";\n\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\t\ttimer2 = System.currentTimeMillis() - timer2;\n\t\tmainLog.print(\"Belief space value iteration (\" + (min ? \"min\" : \"max\") + \")\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer2 / 1000.0 + \" seconds.\");\n\n\t\t// Extract (approximate) solution value for the initial belief\n\t\t// Also get (approximate) accuracy of result from value iteration\n\t\tBelief initialBelief = Belief.pointDistribution(sInit, pomdp);\n\t\tdouble outerBound = values.apply(initialBelief);\n\t\tdouble outerBoundMaxDiff = PrismUtils.measureSupNorm(vhash, vhash_backUp, termCrit == TermCrit.RELATIVE);\n\t\tAccuracy outerBoundAcc = AccuracyFactory.valueIteration(termCritParam, outerBoundMaxDiff, termCrit == TermCrit.RELATIVE);\n\t\t// Print result\n\t\tmainLog.println(\"Outer bound: \" + outerBound + \" (\" + outerBoundAcc.toString(outerBound) + \")\");\n\t\t\n\t\t// Build DTMC to get inner bound (and strategy)\n\t\tmainLog.println(\"\\nBuilding strategy-induced model...\");\n\t\tPOMDPStrategyModel psm = buildStrategyModel(pomdp, sInit, mdpRewards, targetObs, unknownObs, backup);\n\t\tMDP<Double> mdp = psm.mdp;\n\t\tMDPRewards<Double> mdpRewardsNew = psm.mdpRewards;\n\t\tmainLog.print(\"Strategy-induced model: \" + mdp.infoString());\n\t\t\n\t\t// Create/export strategy if requested\n\t\t// (exporting in Dot format if filename extension is .dot, otherwise .tra format)\n\t\tFMDObsStrategyBeliefs stratFmdObs = null;\n\t\tif (genStrat) {\n\t\t\tstratFmdObs = new FMDObsStrategyBeliefs<>(pomdp, psm.mdp, psm.mdpStates, psm.unobsBeliefs);\n\t\t}\n\n\t\t// Create MDP model checker (disable strat generation - if enabled, we want the POMDP one) \n\t\tMDPModelChecker mcMDP = new MDPModelChecker(this);\n\t\tmcMDP.setGenStrat(false);\n\t\t// Solve MDP to get inner bound\n\t\tModelCheckerResult mcRes = mcMDP.computeReachRewards(mdp, mdpRewardsNew, mdp.getLabelStates(\"target\"), true);\n\t\tdouble innerBound = mcRes.soln[0];\n\t\tAccuracy innerBoundAcc = mcRes.accuracy;\n\t\t// Print result\n\t\tString innerBoundStr = \"\" + innerBound;\n\t\tif (innerBoundAcc != null) {\n\t\t\tinnerBoundStr += \" (\" + innerBoundAcc.toString(innerBound) + \")\";\n\t\t}\n\t\tmainLog.println(\"Inner bound: \" + innerBoundStr);\n\n\t\t// Finished fixed-resolution grid approximation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"\\nFixed-resolution grid approximation (\" + (min ? \"min\" : \"max\") + \")\");\n\t\tmainLog.println(\" took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Extract and store result\n\t\tPair<Double,Accuracy> resultValAndAcc;\n\t\tif (min) {\n\t\t\tresultValAndAcc = AccuracyFactory.valueAndAccuracyFromInterval(outerBound, outerBoundAcc, innerBound, innerBoundAcc);\n\t\t} else {\n\t\t\tresultValAndAcc = AccuracyFactory.valueAndAccuracyFromInterval(innerBound, innerBoundAcc, outerBound, outerBoundAcc);\n\t\t}\n\t\tdouble resultVal = resultValAndAcc.first;\n\t\tAccuracy resultAcc = resultValAndAcc.second;\n\t\tmainLog.println(\"Result bounds: [\" + resultAcc.getResultLowerBound(resultVal) + \",\" + resultAcc.getResultUpperBound(resultVal) + \"]\");\n\t\tdouble soln[] = new double[pomdp.getNumStates()];\n\t\tsoln[sInit] = resultVal;\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\tif (genStrat) {\n\t\t\tres.strat = stratFmdObs;\n\t\t}\n\t\tres.soln = soln;\n\t\tres.accuracy = resultAcc;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Get a list of observations from a set of states\n\t * (both are represented by BitSets over their indices).\n\t * The states should correspond exactly to a set of observations,\n\t * i.e., if a state corresponding to an observation is in the set,\n\t * then all other states corresponding to it should also be.\n\t * Returns null if not.\n\t */\n\tprotected BitSet getObservationsMatchingStates(POMDP<Double> pomdp, BitSet set)\n\t{\n\t\t// Find observations corresponding to each state in the set\n\t\tBitSet setObs = new BitSet();\n\t\tfor (int s = set.nextSetBit(0); s >= 0; s = set.nextSetBit(s + 1)) {\n\t\t\tsetObs.set(pomdp.getObservation(s));\n\t\t}\n\t\t// Recreate the set of states from the observations and make sure it matches\n\t\tBitSet set2 = new BitSet();\n\t\tint numStates = pomdp.getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tif (setObs.get(pomdp.getObservation(s))) {\n\t\t\t\tset2.set(s);\n\t\t\t}\n\t\t}\n\t\tif (!set.equals(set2)) {\n\t\t\treturn null;\n\t\t}\n\t\treturn setObs;\n\t}\n\t\n\t/**\n\t * Get a list of observations from a set of states\n\t * (both are represented by BitSets over their indices).\n\t * Observations are included only if all their corresponding states\n\t * are included in the passed in set.\n\t */\n\tprotected BitSet getObservationsCoveredByStates(POMDP<Double> pomdp, BitSet set) throws PrismException\n\t{\n\t\t// Find observations corresponding to each state in the set\n\t\tBitSet setObs = new BitSet();\n\t\tfor (int s = set.nextSetBit(0); s >= 0; s = set.nextSetBit(s + 1)) {\n\t\t\tsetObs.set(pomdp.getObservation(s));\n\t\t}\n\t\t// Find observations for which not all states are in the set\n\t\t// and remove them from the observation set to be returned\n\t\tint numStates = pomdp.getNumStates();\n\t\tfor (int o = setObs.nextSetBit(0); o >= 0; o = setObs.nextSetBit(o + 1)) {\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tif (pomdp.getObservation(s) == o && !set.get(s)) {\n\t\t\t\t\tsetObs.set(o, false);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn setObs;\n\t}\n\t\n\t/**\n\t * Construct a list of beliefs for a grid-based approximation of the belief space.\n\t * Only beliefs with observable values from {@code unknownObs) are added.\n\t */\n\tprotected List<Belief> initialiseGridPoints(POMDP<Double> pomdp, BitSet unknownObs)\n\t{\n\t\tList<Belief> gridPoints = new ArrayList<>();\n\t\tArrayList<ArrayList<Double>> assignment;\n\t\tint numUnobservations = pomdp.getNumUnobservations();\n\t\tint numStates = pomdp.getNumStates();\n\t\tfor (int so = unknownObs.nextSetBit(0); so >= 0; so = unknownObs.nextSetBit(so + 1)) {\n\t\t\tArrayList<Integer> unobservsForObserv = new ArrayList<>();\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tif (so == pomdp.getObservation(s)) {\n\t\t\t\t\tunobservsForObserv.add(pomdp.getUnobservation(s));\n\t\t\t\t}\n\t\t\t}\n\t\t\tassignment = fullAssignment(unobservsForObserv.size(), gridResolution);\n\t\t\tfor (ArrayList<Double> inner : assignment) {\n\t\t\t\tdouble[] bu = new double[numUnobservations];\n\t\t\t\tint k = 0;\n\t\t\t\tfor (int unobservForObserv : unobservsForObserv) {\n\t\t\t\t\tbu[unobservForObserv] = inner.get(k);\n\t\t\t\t\tk++;\n\t\t\t\t}\n\t\t\t\tgridPoints.add(new Belief(so, bu));\n\t\t\t}\n\t\t}\n\t\treturn gridPoints;\n\t}\n\t\n\t/**\n\t * Construct (part of) a belief MDP, just for the set of passed in belief states.\n\t * If provided, also construct a list of rewards for each state.\n\t * It is stored as a list (over source beliefs) of BeliefMDPState objects.\n\t */\n\tprotected List<BeliefMDPState> buildBeliefMDP(POMDP<Double> pomdp, MDPRewards<Double> mdpRewards, List<Belief> beliefs)\n\t{\n\t\tList<BeliefMDPState> beliefMDP = new ArrayList<>();\n\t\tfor (Belief belief: beliefs) {\n\t\t\tbeliefMDP.add(buildBeliefMDPState(pomdp, mdpRewards, belief));\n\t\t}\n\t\treturn beliefMDP;\n\t}\n\t\n\t/**\n\t * Construct a single single state (belief) of a belief MDP, stored as a\n\t * list (over choices) of distributions over target beliefs.\n\t * If provided, also construct a list of rewards for the state.\n\t * It is stored as a BeliefMDPState object.\n\t */\n\tprotected BeliefMDPState buildBeliefMDPState(POMDP<Double> pomdp, MDPRewards<Double> mdpRewards, Belief belief)\n\t{\n\t\tdouble[] beliefInDist = belief.toDistributionOverStates(pomdp);\n\t\tBeliefMDPState beliefMDPState = new BeliefMDPState();\n\t\t// And for each choice\n\t\tint numChoices = pomdp.getNumChoicesForObservation(belief.so);\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\t// Get successor observations and their probs\n\t\t\tHashMap<Integer, Double> obsProbs = pomdp.computeObservationProbsAfterAction(beliefInDist, i);\n\t\t\tHashMap<Belief, Double> beliefDist = new HashMap<>();\n\t\t\t// Find the belief for each observation\n\t\t\tfor (Map.Entry<Integer, Double> entry : obsProbs.entrySet()) {\n\t\t\t\tint o = entry.getKey();\n\t\t\t\tBelief nextBelief = pomdp.getBeliefAfterChoiceAndObservation(belief, i, o);\n\t\t\t\tbeliefDist.put(nextBelief, entry.getValue());\n\t\t\t}\n\t\t\tbeliefMDPState.trans.add(beliefDist);\n\t\t\t// Store reward too, if required\n\t\t\tif (mdpRewards != null) {\n\t\t\t\tbeliefMDPState.rewards.add(pomdp.getRewardAfterChoice(belief, i, mdpRewards));\n\t\t\t}\n\t\t}\n\t\treturn beliefMDPState;\n\t}\n\t\n\t/**\n\t * Perform a single backup step of (approximate) value iteration for probabilistic reachability\n\t */\n\tprotected Pair<Double, Integer> approximateReachProbBackup(Belief belief, BeliefMDPState beliefMDPState, Function<Belief, Double> values, boolean min)\n\t{\n\t\tint numChoices = beliefMDPState.trans.size();\n\t\tdouble chosenValue = min ? Double.POSITIVE_INFINITY : Double.NEGATIVE_INFINITY;\n\t\tint chosenActionIndex = -1;\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tdouble value = 0;\n\t\t\tfor (Map.Entry<Belief, Double> entry : beliefMDPState.trans.get(i).entrySet()) {\n\t\t\t\tdouble nextBeliefProb = entry.getValue();\n\t\t\t\tBelief nextBelief = entry.getKey();\n\t\t\t\tvalue += nextBeliefProb * values.apply(nextBelief);\n\t\t\t}\n\t\t\tif ((min && chosenValue - value > 1.0e-6) || (!min && value - chosenValue > 1.0e-6)) {\n\t\t\t\tchosenValue = value;\n\t\t\t\tchosenActionIndex = i;\n\t\t\t} else if (Math.abs(value - chosenValue) < 1.0e-6) {\n\t\t\t\tchosenActionIndex = i;\n\t\t\t}\n\t\t}\n\t\treturn new Pair<Double, Integer>(chosenValue, chosenActionIndex);\n\t}\n\t\n\t/**\n\t * Perform a single backup step of (approximate) value iteration for reward reachability\n\t */\n\tprotected Pair<Double, Integer> approximateReachRewardBackup(Belief belief, BeliefMDPState beliefMDPState, Function<Belief, Double> values, boolean min)\n\t{\n\t\tint numChoices = beliefMDPState.trans.size();\n\t\tdouble chosenValue = min ? Double.POSITIVE_INFINITY : Double.NEGATIVE_INFINITY;\n\t\tint chosenActionIndex = 0;\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tdouble value = beliefMDPState.rewards.get(i);\n\t\t\tfor (Map.Entry<Belief, Double> entry : beliefMDPState.trans.get(i).entrySet()) {\n\t\t\t\tdouble nextBeliefProb = entry.getValue();\n\t\t\t\tBelief nextBelief = entry.getKey();\n\t\t\t\tvalue += nextBeliefProb * values.apply(nextBelief);\n\t\t\t}\n\t\t\tif ((min && chosenValue - value > 1.0e-6) || (!min && value - chosenValue > 1.0e-6)) {\n\t\t\t\tchosenValue = value;\n\t\t\t\tchosenActionIndex = i;\n\t\t\t} else if (Math.abs(value - chosenValue) < 1.0e-6) {\n\t\t\t\tchosenActionIndex = i;\n\t\t\t}\n\t\t}\n\t\treturn new Pair<Double, Integer>(chosenValue, chosenActionIndex);\n\t}\n\t\n\t/**\n\t * Compute the grid-based approximate value for a belief for probabilistic reachability\n\t */\n\tprotected double approximateReachProb(Belief belief, HashMap<Belief, Double> gridValues, BitSet targetObs, BitSet unknownObs)\n\t{\n\t\t// 1 for target states\n\t\tif (targetObs.get(belief.so)) {\n\t\t\treturn 1.0;\n\t\t}\n\t\t// 0 for other non-unknown states\n\t\telse if (!unknownObs.get(belief.so)) {\n\t\t\treturn 0.0;\n\t\t}\n\t\t// Otherwise approximate vie interpolation over grid points\n\t\telse {\n\t\t\treturn interpolateOverGrid(belief, gridValues);\n\t\t}\n\t}\n\t\n\t/**\n\t * Compute the grid-based approximate value for a belief for reward reachability\n\t */\n\tprotected double approximateReachReward(Belief belief, HashMap<Belief, Double> gridValues, BitSet targetObs, BitSet infObs)\n\t{\n\t\t// 0 for target states\n\t\tif (targetObs.get(belief.so)) {\n\t\t\treturn 0.0;\n\t\t}\n\t\t// +Inf for states in \"inf\"\n\t\telse if (infObs.get(belief.so)) {\n\t\t\treturn Double.POSITIVE_INFINITY;\n\t\t}\n\t\t// Otherwise approximate vie interpolation over grid points\n\t\telse {\n\t\t\treturn interpolateOverGrid(belief, gridValues);\n\t\t}\n\t}\n\t\n\t/**\n\t * Approximate the value for a belief {@code belief} by interpolating over values {@code gridValues}\n\t * for a representative set of beliefs whose convex hull is the full belief space.\n\t */\n\tprotected double interpolateOverGrid(Belief belief, HashMap<Belief, Double> gridValues)\n\t{\n\t\tArrayList<double[]> subSimplex = new ArrayList<>();\n\t\tdouble[] lambdas = new double[belief.bu.length];\n\t\tgetSubSimplexAndLambdas(belief.bu, subSimplex, lambdas, gridResolution);\n\t\tdouble val = 0;\n\t\tfor (int j = 0; j < lambdas.length; j++) {\n\t\t\tif (lambdas[j] >= 1e-6) {\n\t\t\t\tval += lambdas[j] * gridValues.get(new Belief(belief.so, subSimplex.get(j)));\n\t\t\t}\n\t\t}\n\t\treturn val;\n\t}\n\t\n\t/**\n\t * Build a (Markov chain) model representing the fragment of the belief MDP induced by an optimal strategy.\n\t * The model is stored as an MDP to allow easier attachment of optional actions.\n\t * @param pomdp\n\t * @param sInit\n\t * @param mdpRewards\n\t * @param vhash\n\t * @param vhash_backUp\n\t * @param target\n\t * @param min\n\t * @param listBeliefs\n\t */\n\tprotected POMDPStrategyModel buildStrategyModel(POMDP<Double> pomdp, int sInit, MDPRewards<Double> mdpRewards, BitSet targetObs, BitSet unknownObs, BeliefMDPBackUp backup) throws PrismException\n\t{\n\t\t// Initialise model/state/rewards storage\n\t\tMDPSimple<Double> mdp = new MDPSimple<>();\n\t\tIndexedSet<double[]> unobsBeliefs = new IndexedSet<>((a, b) -> Arrays.compare(a, b));\n\t\tIndexedSet<int[]> exploredBeliefs = new IndexedSet<>((a, b) -> Arrays.compare(a, b));\n\t\tLinkedList<Belief> toBeExploredBeliefs = new LinkedList<>();\n\t\tBitSet mdpTarget = new BitSet();\n\t\tStateRewardsSimple<Double> stateRewards = new StateRewardsSimple<>();\n\t\t// Add initial state\n\t\tBelief initialBelief = Belief.pointDistribution(sInit, pomdp);\n\t\tunobsBeliefs.add(initialBelief.bu);\n\t\texploredBeliefs.add(new int[] {initialBelief.so, unobsBeliefs.getIndexOfLastAdd()});\n\t\ttoBeExploredBeliefs.offer(initialBelief);\n\t\tmdp.addState();\n\t\tmdp.addInitialState(0);\n\t\t\n\t\t// Explore model\n\t\tint src = -1;\n\t\twhile (!toBeExploredBeliefs.isEmpty()) {\n\t\t\tBelief belief = toBeExploredBeliefs.pollFirst();\n\t\t\tsrc++;\n\t\t\t// Remember if this is a target state\n\t\t\tif (targetObs.get(belief.so)) {\n\t\t\t\tmdpTarget.set(src);\n\t\t\t}\n\t\t\t// Only explore \"unknown\" states\n\t\t\tif (unknownObs.get(belief.so)) {\n\t\t\t\t// Build the belief MDP for this belief state and solve\n\t\t\t\tBeliefMDPState beliefMDPState = buildBeliefMDPState(pomdp, mdpRewards, belief);\n\t\t\t\tPair<Double, Integer> valChoice = backup.apply(belief, beliefMDPState);\n\t\t\t\tint chosenActionIndex = valChoice.second;\n\t\t\t\t// Build a distribution over successor belief states and add to MDP\n\t\t\t\tDistribution<Double> distr = Distribution.ofDouble();\n\t\t\t\tfor (Map.Entry<Belief, Double> entry : beliefMDPState.trans.get(chosenActionIndex).entrySet()) {\n\t\t\t\t\tdouble nextBeliefProb = entry.getValue();\n\t\t\t\t\tBelief nextBelief = entry.getKey();\n\t\t\t\t\tunobsBeliefs.add(nextBelief.bu);\n\t\t\t\t\tint[] next = new int[] {nextBelief.so, unobsBeliefs.getIndexOfLastAdd()};\n\t\t\t\t\t// Add each successor belief to the MDP and the \"to explore\" set if new\n\t\t\t\t\tif (exploredBeliefs.add(next)) {\n\t\t\t\t\t\ttoBeExploredBeliefs.add(nextBelief);\n\t\t\t\t\t\tmdp.addState();\n\t\t\t\t\t}\n\t\t\t\t\t// Get index of state in state set\n\t\t\t\t\tint dest = exploredBeliefs.getIndexOfLastAdd();\n\t\t\t\t\tdistr.add(dest, nextBeliefProb);\n\t\t\t\t}\n\t\t\t\t// Add transition distribution, with choice _index_ encoded as action\n\t\t\t\tmdp.addActionLabelledChoice(src, distr, pomdp.getActionForObservation(belief.so, chosenActionIndex));\n\t\t\t\t// Store reward too, if needed\n\t\t\t\tif (mdpRewards != null) {\n\t\t\t\t\tstateRewards.setStateReward(src, pomdp.getRewardAfterChoice(belief, chosenActionIndex, mdpRewards));\n\t\t\t\t} else {\n\t\t\t\t\tstateRewards.setStateReward(src, 0.0);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tstateRewards.setStateReward(src, 0.0);\n\t\t\t}\n\t\t}\n\t\t// Add deadlocks to unexplored (known-value) states\n\t\tmdp.findDeadlocks(true);\n\t\t// Attach a label marking target states\n\t\tmdp.addLabel(\"target\", mdpTarget);\n\t\t// Return\n\t\tPOMDPStrategyModel psm = new POMDPStrategyModel();\n\t\tpsm.mdp = mdp;\n\t\tpsm.mdpStates = new ArrayList<>();\n\t\tpsm.mdpStates.addAll(exploredBeliefs.toArrayList());\n\t\tpsm.unobsBeliefs = new ArrayList<>();\n\t\tpsm.unobsBeliefs.addAll(unobsBeliefs.toArrayList());\n\t\tpsm.mdpRewards = stateRewards;\n\t\treturn psm;\n\t}\n\t\n\tprotected ArrayList<ArrayList<Integer>> assignGPrime(int startIndex, int min, int max, int length)\n\t{\n\t\tArrayList<ArrayList<Integer>> result = new ArrayList<ArrayList<Integer>>();\n\t\tif (startIndex == length - 1) {\n\t\t\tfor (int i = min; i <= max; i++) {\n\t\t\t\tArrayList<Integer> innerList = new ArrayList<>();\n\t\t\t\tinnerList.add(i);\n\t\t\t\tresult.add(innerList);\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int i = min; i <= max; i++) {\n\t\t\t\tArrayList<ArrayList<Integer>> nextResult = assignGPrime(startIndex + 1, 0, i, length);\n\t\t\t\tfor (ArrayList<Integer> nextReulstInner : nextResult) {\n\t\t\t\t\tArrayList<Integer> innerList = new ArrayList<>();\n\t\t\t\t\tinnerList.add(i);\n\t\t\t\t\tfor (Integer a : nextReulstInner) {\n\t\t\t\t\t\tinnerList.add(a);\n\t\t\t\t\t}\n\t\t\t\t\tresult.add(innerList);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\tprivate ArrayList<ArrayList<Double>> fullAssignment(int length, int resolution)\n\t{\n\t\tArrayList<ArrayList<Integer>> GPrime = assignGPrime(0, resolution, resolution, length);\n\t\tArrayList<ArrayList<Double>> result = new ArrayList<ArrayList<Double>>();\n\t\tfor (ArrayList<Integer> GPrimeInner : GPrime) {\n\t\t\tArrayList<Double> innerList = new ArrayList<>();\n\t\t\tint i;\n\t\t\tfor (i = 0; i < length - 1; i++) {\n\t\t\t\tint temp = GPrimeInner.get(i) - GPrimeInner.get(i + 1);\n\t\t\t\tinnerList.add((double) temp / resolution);\n\t\t\t}\n\t\t\tinnerList.add((double) GPrimeInner.get(i) / resolution);\n\t\t\tresult.add(innerList);\n\t\t}\n\t\treturn result;\n\t}\n\n\tprivate int[] getSortedPermutation(double[] inputArray)\n\t{\n\t\tint n = inputArray.length;\n\t\tdouble[] inputCopy = new double[n];\n\t\tint[] permutation = new int[n];\n\t\tint iState = 0, iIteration = 0;\n\t\tint iNonZeroEntry = 0, iZeroEntry = n - 1;\n\t\tboolean bDone = false;\n\n\t\tfor (iState = n - 1; iState >= 0; iState--) {\n\t\t\tif (inputArray[iState] == 0.0) {\n\t\t\t\tinputCopy[iZeroEntry] = 0.0;\n\t\t\t\tpermutation[iZeroEntry] = iState;\n\t\t\t\tiZeroEntry--;\n\t\t\t}\n\n\t\t}\n\n\t\tfor (iState = 0; iState < n; iState++) {\n\t\t\tif (inputArray[iState] != 0.0) {\n\t\t\t\tinputCopy[iNonZeroEntry] = inputArray[iState];\n\t\t\t\tpermutation[iNonZeroEntry] = iState;\n\t\t\t\tiNonZeroEntry++;\n\t\t\t}\n\t\t}\n\n\t\twhile (!bDone) {\n\t\t\tbDone = true;\n\t\t\tfor (iState = 0; iState < iNonZeroEntry - iIteration - 1; iState++) {\n\t\t\t\tif (inputCopy[iState] < inputCopy[iState + 1]) {\n\t\t\t\t\tswap(inputCopy, iState, iState + 1);\n\t\t\t\t\tswap(permutation, iState, iState + 1);\n\t\t\t\t\tbDone = false;\n\t\t\t\t}\n\t\t\t}\n\t\t\tiIteration++;\n\t\t}\n\n\t\treturn permutation;\n\t}\n\n\tprivate void swap(int[] aiArray, int i, int j)\n\t{\n\t\tint temp = aiArray[i];\n\t\taiArray[i] = aiArray[j];\n\t\taiArray[j] = temp;\n\t}\n\n\tprivate void swap(double[] aiArray, int i, int j)\n\t{\n\t\tdouble temp = aiArray[i];\n\t\taiArray[i] = aiArray[j];\n\t\taiArray[j] = temp;\n\t}\n\n\tprotected boolean getSubSimplexAndLambdas(double[] b, ArrayList<double[]> subSimplex, double[] lambdas, int resolution)\n\t{\n\t\tint n = b.length;\n\t\tint M = resolution;\n\n\t\tdouble[] X = new double[n];\n\t\tint[] V = new int[n];\n\t\tdouble[] D = new double[n];\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tX[i] = 0;\n\t\t\tfor (int j = i; j < n; j++) {\n\t\t\t\tX[i] += M * b[j];\n\t\t\t}\n\t\t\tX[i] = Math.round(X[i] * 1e6) / 1e6;\n\t\t\tV[i] = (int) Math.floor(X[i]);\n\t\t\tD[i] = X[i] - V[i];\n\t\t}\n\n\t\tint[] P = getSortedPermutation(D);\n\t\t//\t\tmainLog.println(\"X: \"+ Arrays.toString(X));\n\t\t//\t\tmainLog.println(\"V: \"+ Arrays.toString(V));\n\t\t//\t\tmainLog.println(\"D: \"+ Arrays.toString(D));\n\t\t//\t\tmainLog.println(\"P: \"+ Arrays.toString(P));\n\n\t\tArrayList<int[]> Qs = new ArrayList<>();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tint[] Q = new int[n];\n\t\t\tif (i == 0) {\n\t\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\t\tQ[j] = V[j];\n\t\t\t\t}\n\t\t\t\tQs.add(Q);\n\t\t\t} else {\n\t\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\t\tif (j == P[i - 1]) {\n\t\t\t\t\t\tQ[j] = Qs.get(i - 1)[j] + 1;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tQ[j] = Qs.get(i - 1)[j];\n\t\t\t\t\t}\n\n\t\t\t\t}\n\t\t\t\tQs.add(Q);\n\t\t\t}\n\t\t\t//\t\t\tmainLog.println(Arrays.toString(Q));\n\t\t}\n\n\t\tfor (int[] Q : Qs) {\n\t\t\tdouble[] node = new double[n];\n\t\t\tint i;\n\t\t\tfor (i = 0; i < n - 1; i++) {\n\t\t\t\tint temp = Q[i] - Q[i + 1];\n\t\t\t\tnode[i] = (double) temp / M;\n\t\t\t}\n\t\t\tnode[i] = (double) Q[i] / M;\n\t\t\tsubSimplex.add(node);\n\t\t}\n\n\t\tdouble sum = 0;\n\t\tfor (int i = 1; i < n; i++) {\n\t\t\tdouble lambda = D[P[i - 1]] - D[P[i]];\n\t\t\tlambdas[i] = lambda;\n\t\t\tsum = sum + lambda;\n\t\t}\n\t\tlambdas[0] = 1 - sum;\n\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tdouble sum2 = 0;\n\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\tsum2 += lambdas[j] * subSimplex.get(j)[i];\n\t\t\t}\n\t\t\t//\t\t\tmainLog.println(\"b[\"+i+\"]: \"+b[i]+\"  b^[i]:\"+sum2);\n\t\t\tif (Math.abs(b[i] - sum2) > 1e-4) {\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t}\n\t\treturn true;\n\t}\n\n\tpublic static boolean isTargetBelief(double[] belief, BitSet target)\n\t{\n\t\t double prob=0;\n\t\t for (int i = target.nextSetBit(0); i >= 0; i = target.nextSetBit(i+1)) \n\t\t {\n\t\t\t prob+=belief[i];\n\t\t }\n\t\t if(Math.abs(prob-1.0)<1.0e-6)\n\t\t {\n\t\t\t return true;\n\t\t }\n\t\t return false;\n\t}\t\n\n\t/**\n\t * Simple test program.\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tPOMDPModelChecker mc;\n\t\tPOMDPSimple<Double> pomdp;\n\t\tModelCheckerResult res;\n\t\tBitSet init, target;\n\t\tMap<String, BitSet> labels;\n\t\tboolean min = true;\n\t\ttry {\n\t\t\tmc = new POMDPModelChecker(null);\n\t\t\tMDPSimple<Double> mdp = new MDPSimple<>();\n\t\t\tmdp.buildFromPrismExplicit(args[0]);\n\t\t\t//mainLog.println(mdp);\n\t\t\tlabels = mc.loadLabelsFile(args[1]);\n\t\t\t//mainLog.println(labels);\n\t\t\tinit = labels.get(\"init\");\n\t\t\ttarget = labels.get(args[2]);\n\t\t\tif (target == null)\n\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + args[2] + \"\\\"\");\n\t\t\tfor (int i = 3; i < args.length; i++) {\n\t\t\t\tif (args[i].equals(\"-min\"))\n\t\t\t\t\tmin = true;\n\t\t\t\telse if (args[i].equals(\"-max\"))\n\t\t\t\t\tmin = false;\n\t\t\t\telse if (args[i].equals(\"-nopre\"))\n\t\t\t\t\tmc.setPrecomp(false);\n\t\t\t}\n\t\t\tpomdp = new POMDPSimple<>(mdp);\n\t\t\tres = mc.computeReachRewards(pomdp, null, target, min, null);\n\t\t\tSystem.out.println(res.soln[init.nextSetBit(0)]);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(e);\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/explicit/POMDPSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Xueyi Zou <xz972@york.ac.uk> (University of York)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.Map;\n\nimport explicit.rewards.MDPRewards;\nimport io.ExplicitModelImporter;\nimport parser.State;\nimport prism.PrismException;\nimport prism.PrismUtils;\n\n/**\n * Simple explicit-state representation of a POMDP.\n * Basically a {@link MDPSimple} with observability info.\n * <br><br>\n * POMDPs require that states with the same observation have\n * the same set of available actions. This class further requires\n * that these actions appear in the same order (in terms of\n * choice indexing) in each equivalent state. This is enforced\n * when calling setObservation().\n */\npublic class POMDPSimple<Value> extends MDPSimple<Value> implements POMDP<Value>\n{\n\t// Observations\n\tprotected ObservationsSimple observations;\n\n\t// Constructors\n\n\t/**\n\t * Constructor: empty POMDP.\n\t */\n\tpublic POMDPSimple()\n\t{\n\t\tsuper();\n\t\tobservations = new ObservationsSimple();\n\t}\n\n\t/**\n\t * Constructor: new POMDP with fixed number of states.\n\t */\n\tpublic POMDPSimple(int numStates)\n\t{\n\t\tsuper(numStates);\n\t\tobservations = new ObservationsSimple(numStates);\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic POMDPSimple(POMDPSimple<Value> pomdp)\n\t{\n\t\tsuper(pomdp);\n\t\tobservations = new ObservationsSimple(pomdp.observations);\n\t}\n\n\t/**\n\t * Construct a POMDP from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t */\n\tpublic POMDPSimple(POMDPSimple<Value> pomdp, int permut[])\n\t{\n\t\tsuper(pomdp, permut);\n\t\tobservations = new ObservationsSimple(pomdp.observations, permut);\n\t}\n\n\t/**\n\t * Construct a POMDP from an existing MDP.\n\t */\n\tpublic POMDPSimple(MDPSimple<Value> mdp)\n\t{\n\t\tsuper(mdp);\n\t\tobservations = new ObservationsSimple(mdp.numStates);\n\t\tobservations.setIdentityObservations();\n\t}\n\n\t// Mutators (for ModelSimple)\n\n\t@Override\n\tpublic void clearState(int s)\n\t{\n\t\tsuper.clearState(s);\n\t\tobservations.clearState(s);\n\t}\n\n\t@Override\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tsuper.addStates(numToAdd);\n\t\tobservations.addStates(numToAdd);\n\t}\n\n\t@Override\n\tpublic void buildFromExplicitImport(ExplicitModelImporter modelImporter) throws PrismException\n\t{\n\t\tsuper.buildFromExplicitImport(modelImporter);\n\t\tobservations = new ObservationsSimple(modelImporter.getNumStates(), modelImporter.getNumObservations());\n\t\tmodelImporter.extractObservations(this::setObservation);\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tobservations.setUnobservation(s, s);\n\t\t}\n\t}\n\n\t// Mutators (for PartiallyObservableModel)\n\t\n\t@Override\n\tpublic void setObservationsList(List<State> observationsList)\n\t{\n\t\tobservations.setObservationsList(observationsList);\n\t}\n\n\t@Override\n\tpublic void setUnobservationsList(List<State> unobservationsList)\n\t{\n\t\tobservations.setUnobservationsList(unobservationsList);\n\t}\n\n\t@Override\n\tpublic void setObservation(int s, State observ, State unobserv, List<String> observableNames) throws PrismException\n\t{\n\t\tobservations.setObservation(s, observ, unobserv, observableNames, this);\n\t}\n\n\t@Override\n\tpublic void setObservation(int s, int o) throws PrismException\n\t{\n\t\tobservations.setObservation(s, o, this);\n\t}\n\t\n\t// Accessors (for PartiallyObservableModel)\n\t\n\t@Override\n\tpublic List<State> getObservationsList()\n\t{\n\t\treturn observations.getObservationsList();\n\t}\n\n\t@Override\n\tpublic List<State> getUnobservationsList()\n\t{\n\t\treturn observations.getUnobservationsList();\n\t}\n\n\t@Override\n\tpublic int getObservation(int s)\n\t{\n\t\treturn observations.getObservation(s);\n\t}\n\n\t@Override\n\tpublic int getUnobservation(int s)\n\t{\n\t\treturn observations.getUnobservation(s);\n\t}\n\n\t@Override\n\tpublic int getNumChoicesForObservation(int o)\n\t{\n\t\treturn getNumChoices(observations.getObservationState(o));\n\t}\n\t\n\t// Accessors (for POMDP)\n\n\t@Override\n\tpublic Object getActionForObservation(int o, int i)\n\t{\n\t\treturn getAction(observations.getObservationState(o), i);\n\t}\n\t\n\t@Override\n\tpublic Belief getInitialBelief()\n\t{\n\t\tdouble[] initialBeliefInDist = new double[numStates];\n\t\tfor (Integer i : initialStates) {\n\t\t\tinitialBeliefInDist[i] = 1;\n\t\t}\n\t\tPrismUtils.normalise(initialBeliefInDist);\n\t\treturn new Belief(initialBeliefInDist, this);\n\t}\n\n\t@Override\n\tpublic double[] getInitialBeliefInDist()\n\t{\n\t\tdouble[] initialBeliefInDist = new double[numStates];\n\t\tfor (Integer i : initialStates) {\n\t\t\tinitialBeliefInDist[i] = 1;\n\t\t}\n\t\tPrismUtils.normalise(initialBeliefInDist);\n\t\treturn initialBeliefInDist;\n\t}\n\n\t@Override\n\tpublic Belief getBeliefAfterChoice(Belief belief, int i)\n\t{\n\t\tdouble[] beliefInDist = belief.toDistributionOverStates(this);\n\t\tdouble[] nextBeliefInDist = getBeliefInDistAfterChoice(beliefInDist, i);\n\t\treturn new Belief(nextBeliefInDist, this);\n\t}\n\n\t@Override\n\tpublic double[] getBeliefInDistAfterChoice(double[] beliefInDist, int i)\n\t{\n\t\tint n = beliefInDist.length;\n\t\tdouble[] nextBeliefInDist = new double[n];\n\t\tfor (int sp = 0; sp < n; sp++) {\n\t\t\tif (beliefInDist[sp] >= 1.0e-6) {\n\t\t\t\t@SuppressWarnings(\"unchecked\")\n\t\t\t\tDistribution<Double> distr = (Distribution<Double>) getChoice(sp, i);\n\t\t\t\tfor (Map.Entry<Integer, Double> e : distr) {\n\t\t\t\t\tint s = (Integer) e.getKey();\n\t\t\t\t\tdouble prob = (Double) e.getValue();\n\t\t\t\t\tnextBeliefInDist[s] += beliefInDist[sp] * prob;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn nextBeliefInDist;\n\t}\n\n\t@Override\n\tpublic Belief getBeliefAfterChoiceAndObservation(Belief belief, int i, int o)\n\t{\n\t\tdouble[] beliefInDist = belief.toDistributionOverStates(this);\n\t\tdouble[] nextBeliefInDist = getBeliefInDistAfterChoiceAndObservation(beliefInDist, i, o);\n\t\tBelief nextBelief = new Belief(nextBeliefInDist, this);\n\t\tassert(nextBelief.so == o);\n\t\treturn nextBelief;\n\t}\n\n\t@Override\n\tpublic double[] getBeliefInDistAfterChoiceAndObservation(double[] beliefInDist, int i, int o)\n\t{\n\t\tint n = beliefInDist.length;\n\t\tdouble[] nextBelief = new double[n];\n\t\tdouble[] beliefAfterAction = this.getBeliefInDistAfterChoice(beliefInDist, i);\n\t\tdouble prob;\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tprob = beliefAfterAction[s] * getObservationProb(s, o);\n\t\t\tnextBelief[s] = prob;\n\t\t}\n\t\tPrismUtils.normalise(nextBelief);\n\t\treturn nextBelief;\n\t}\n\n\t@Override // SLOW\n\tpublic double getObservationProbAfterChoice(Belief belief, int i, int o)\n\t{\n\t\tdouble[] beliefInDist = belief.toDistributionOverStates(this);\n\t\tdouble prob = getObservationProbAfterChoice(beliefInDist, i, o);\n\t\treturn prob;\n\t}\n\n\t@Override // SLOW\n\tpublic double getObservationProbAfterChoice(double[] beliefInDist, int i, int o)\n\t{\n\t\tdouble[] beliefAfterAction = this.getBeliefInDistAfterChoice(beliefInDist, i);\n\t\tint s;\n\t\tdouble prob = 0;\n\t\tfor (s = 0; s < beliefAfterAction.length; s++) {\n\t\t\tprob += beliefAfterAction[s] * getObservationProb(s, o);\n\t\t}\n\t\treturn prob;\n\t}\n\n\t@Override\n\tpublic HashMap<Integer, Double> computeObservationProbsAfterAction(double[] belief, int i)\n\t{\n\t\tHashMap<Integer, Double> probs = new HashMap<>();\n\t\tdouble[] beliefAfterAction = this.getBeliefInDistAfterChoice(belief, i);\n\t\tfor (int s = 0; s < beliefAfterAction.length; s++) {\n\t\t\tint o = getObservation(s);\n\t\t\tdouble probToAdd = beliefAfterAction[s];\n\t\t\tif (probToAdd > 1e-6) {\n\t\t\t\tDouble lookup = probs.get(o);\n\t\t\t\tif (lookup == null) {\n\t\t\t\t\tprobs.put(o, probToAdd);\n\t\t\t\t} else {\n\t\t\t\t\tprobs.put(o, lookup + probToAdd);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn probs;\n\t}\n\t\n\t@Override\n\tpublic double getRewardAfterChoice(Belief belief, int i, MDPRewards<Double> mdpRewards)\n\t{\n\t\tdouble[] beliefInDist = belief.toDistributionOverStates(this);\n\t\tdouble cost = getRewardAfterChoice(beliefInDist, i, mdpRewards);\n\t\treturn cost;\n\t}\n\n\t@Override\n\tpublic double getRewardAfterChoice(double[] beliefInDist, int i, MDPRewards<Double> mdpRewards)\n\t{\n\t\tdouble cost = 0;\n\t\tfor (int s = 0; s < beliefInDist.length; s++) {\n\t\t\tif (beliefInDist[s] == 0) {\n\t\t\t\tcost += 0;\n\t\t\t} else {\n\t\t\t\tcost += beliefInDist[s] * (mdpRewards.getTransitionReward(s, i) + mdpRewards.getStateReward(s));\n\t\t\t}\n\n\t\t}\n\t\treturn cost;\n\t}\n\n\t// Helpers\n\t\n\tprotected Belief beliefInDistToBelief(double[] beliefInDist)\n\t{\n\t\tint so = -1;\n\t\tdouble[] bu = new double[this.getNumUnobservations()];\n\t\tfor (int s = 0; s < beliefInDist.length; s++) {\n\t\t\tif (beliefInDist[s] != 0) {\n\t\t\t\tso = this.getObservation(s);\n\t\t\t\tbu[this.getUnobservation(s)] += beliefInDist[s];\n\t\t\t}\n\t\t}\n\t\tBelief belief = null;\n\t\tif (so != -1) {\n\t\t\tbelief = new Belief(so, bu);\n\t\t} else {\n\t\t\tSystem.err.println(\"Something wrong in POMDPSimple.beliefInDistToBelief(double[] beliefInDist)\");\n\t\t}\n\t\treturn belief;\n\t}\n\t\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, j, n;\n\t\tObject o;\n\t\tString s = \"\";\n\t\ts = \"[ \";\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tif (i > 0)\n\t\t\t\ts += \", \";\n\t\t\ts += i + \"(\" + getObservation(i) + \"/\" + getUnobservation(i) + \"): \";\n\t\t\ts += \"[\";\n\t\t\tn = getNumChoices(i);\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tif (j > 0)\n\t\t\t\t\ts += \",\";\n\t\t\t\to = getAction(i, j);\n\t\t\t\tif (o != null)\n\t\t\t\t\ts += o + \":\";\n\t\t\t\ts += trans.get(i).get(j);\n\t\t\t}\n\t\t\ts += \"]\";\n\t\t}\n\t\ts += \" ]\\n\";\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof POMDPSimple))\n\t\t\treturn false;\n\t\tPOMDPSimple<?> mdp = (POMDPSimple<?>) o;\n\t\tif (numStates != mdp.numStates)\n\t\t\treturn false;\n\t\tif (!initialStates.equals(mdp.initialStates))\n\t\t\treturn false;\n\t\tif (!trans.equals(mdp.trans))\n\t\t\treturn false;\n\t\t// TODO: compare actions (complicated: null = null,null,null,...)\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/PartiallyObservableModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Xueyi Zou <xz972@york.ac.uk> (University of York)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.List;\n\nimport io.ModelExportOptions;\nimport io.PrismExplicitExporter;\nimport parser.State;\nimport prism.ModelInfo;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLog;\n\n/**\n * Interface for classes representing an explicit-state model with partial observability.\n */\npublic interface PartiallyObservableModel<Value> extends Model<Value>\n{\n\t// Mutators (other)\n\n\t/**\n\t * Set the associated (read-only) observation list.\n\t */\n\tvoid setObservationsList(List<State> observationsList);\n\n\t/**\n\t * Set the associated (read-only) unobservation list.\n\t */\n\tvoid setUnobservationsList(List<State> unobservationsList);\n\n\t/**\n\t * Set the observation info for a state.\n\t * If the actions for existing states with this observation do not match,\n\t * an explanatory exception is thrown (so this should be done after transitions\n\t * have been added to the state). Optionally, a list of names of the\n\t * observables can be passed for error reporting.\n\t * @param s State\n\t * @param observ Observation\n\t * @param unobserv Unobservation\n\t * @param observableNames Names of observables (optional)\n\t */\n\tvoid setObservation(int s, State observ, State unobserv, List<String> observableNames) throws PrismException;\n\n\t/**\n\t * Assign observation with index o to state s.\n\t * (assumes observation has already been added to the list)\n\t * If the actions for existing states with this observation do not match,\n\t * an explanatory exception is thrown (so this should be done after transitions\n\t * have been added to the state).\n\t */\n\tvoid setObservation(int s, int o) throws PrismException;\n\n\t// Accessors\n\n\t/**\n\t * Get access to a list of observations (optionally stored).\n\t */\n\tpublic List<State> getObservationsList();\n\n\t/**\n\t * Get access to a list of unobservations (optionally stored).\n\t */\n\tpublic List<State> getUnobservationsList();\n\n\t/**\n\t * Get the total number of observations over all states.\n\t */\n\tpublic default int getNumObservations()\n\t{\n\t\treturn getObservationsList().size();\n\t}\n\n\t/**\n\t * Get the total number of unobservations over all states.\n\t */\n\tpublic default int getNumUnobservations()\n\t{\n\t\treturn getUnobservationsList().size();\n\t}\n\n\t/**\n\t * Get the observation of state {@code s}.\n\t */\n\tpublic int getObservation(int s);\n\n\t/**\n\t * Get the observation of state {@code s} as a {@code State}.\n\t * Equivalent to calling {@link #getObservation(int)}\n\t * and then looking up via {@link #getObservationsList()}.\n\t * Returns null if the observation is unavailable.\n\t */\n\tpublic default State getObservationAsState(int s)\n\t{\n\t\tint o = getObservation(s);\n\t\tList<State> obsList = getObservationsList();\n\t\tif (obsList != null && obsList.size() > o) {\n\t\t\treturn obsList.get(o);\n\t\t}\n\t\treturn null;\n\t}\n\n\t/**\n\t * Get the unobservation of state {@code s}.\n\t */\n\tpublic int getUnobservation(int s);\n\n\t/**\n\t * Get the unobservation of state {@code s} as a {@code State}.\n\t * Equivalent to calling {@link #getUnobservation(int)}\n\t * and then looking up via {@link #getUnobservationsList()}.\n\t * Returns null if the unobservation is unavailable.\n\t */\n\tpublic default State getUnobservationAsState(int s)\n\t{\n\t\tint u = getUnobservation(s);\n\t\tList<State> unobsList = getUnobservationsList();\n\t\tif (unobsList != null && unobsList.size() > u) {\n\t\t\treturn unobsList.get(u);\n\t\t}\n\t\treturn null;\n\t}\n\n\t/**\n\t * Get the probability of observing observation {@code o} in state {@code s}.\n\t */\n\tpublic default double getObservationProb(int s, int o)\n\t{\n\t\treturn this.getObservation(s) == o ? 1.0 : 0.0;\n\t}\n\n\t/**\n\t * Get the number of choices for observation {@code o}.\n\t */\n\tpublic int getNumChoicesForObservation(int o);\n\n\t/**\n\t * Export observations list.\n\t */\n\tpublic default void exportObservations(ModelInfo modelInfo, PrismLog out, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tnew PrismExplicitExporter<Value>(exportOptions).exportObservations(this, modelInfo, out);\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export observations list.\n\t */\n\t@Deprecated\n\tpublic default void exportObservations(int exportType, ModelInfo modelInfo, PrismLog out) throws PrismException\n\t{\n\t\texportObservations(modelInfo, out, Prism.convertExportType(exportType));\n\t}\n}"
  },
  {
    "path": "prism/src/explicit/PredecessorRelation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Stack;\n\nimport prism.PrismComponent;\nimport common.IterableBitSet;\n\n/**\n * A class for storing and accessing the predecessor relation of an explicit Model.\n * <p>\n * As Model only provide easy access to successors of states,\n * the predecessor relation is computed and stored for subsequent efficient access.\n * <p>\n * Note: Naturally, if the model changes, the predecessor relation\n * has to be recomputed to remain accurate.\n */\npublic class PredecessorRelation\n{\n\t/**\n\t * pre[i] provides the list of predecessors of state with index i.\n\t */\n\tList<ArrayList<Integer>> pre;\n\n\t/**\n\t * Constructor. Computes the predecessor relation for the given model\n\t * by considering the successors of each state.\n\t *\n\t * @param model the Model\n\t */\n\tpublic PredecessorRelation(Model<?> model)\n\t{\n\t\tpre = new ArrayList<ArrayList<Integer>>(model.getNumStates());\n\t\t// construct the (empty) array list for all states\n\t\tfor (int s = 0; s < model.getNumStates(); s++) {\n\t\t\tpre.add(s, new ArrayList<Integer>());\n\t\t}\n\n\t\tcompute(model);\n\t}\n\n\t/** Compute the predecessor relation using getSuccessorsIterator. */\n\tprivate void compute(Model<?> model)\n\t{\n\t\tint n = model.getNumStates();\n\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tIterator<Integer> it = model.getSuccessorsIterator(s);\n\t\t\twhile (it.hasNext()) {\n\t\t\t\tInteger successor = it.next();\n\n\t\t\t\t// Add the current state s to pre[successor].\n\t\t\t\t//\n\t\t\t\t// As getSuccessorsIterator guarantees that\n\t\t\t\t// there are no duplicates in the successors,\n\t\t\t\t// s will be added to successor exactly once.\n\t\t\t\tpre.get(successor).add(s);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Get an Iterable over the predecessor states of {@code s}.\n\t */\n\tpublic Iterable<Integer> getPre(int s)\n\t{\n\t\treturn pre.get(s);\n\t}\n\n\t/**\n\t * Get an Iterator over the predecessor states of {@code s}.\n\t */\n\tpublic Iterator<Integer> getPredecessorsIterator(int s)\n\t{\n\t\treturn getPre(s).iterator();\n\t}\n\n\t/**\n\t * Static constructor to compute the predecessor relation for the given model.\n\t * Logs diagnostic information to the log of the given PrismComponent.\n\t *\n\t * @param parent a PrismComponent (for obtaining the log and settings)\n\t * @param model the model for which the predecessor relation should be computed\n\t * @returns the predecessor relation\n\t **/\n\tpublic static PredecessorRelation forModel(PrismComponent parent, Model<?> model)\n\t{\n\t\tlong timer = System.currentTimeMillis();\n\t\t\n\t\tparent.getLog().print(\"Calculating predecessor relation for \"+model.getModelType().fullName()+\"...  \");\n\t\tparent.getLog().flush();\n\n\t\tPredecessorRelation pre = new PredecessorRelation(model);\n\t\t\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tparent.getLog().println(\"done (\" + timer / 1000.0 + \" seconds)\");\n\n\t\treturn pre;\n\t}\n\n\n\t/**\n\t * Computes the set Pre*(target) via a DFS, i.e., all states that\n\t * are in {@code target} or can reach {@code target} via one or more transitions\n\t * from states contained in {@code remain}.\n\t * <br/>\n\t * If the parameter {@code remain} is {@code null}, then\n\t * {@code remain} is considered to include all states in the model.\n\t * <br/>\n\t * If the parameter {@code absorbing} is not {@code null},\n\t * then the states in {@code absorbing} are considered to be absorbing,\n\t * i.e., to have a single self-loop, disregarding other outgoing edges.\n\n\t * @param remain restriction on the states that may occur\n\t *               on the path to target, {@code null} = all states\n\t * @param target The set of target states\n\t * @param absorbing (optional) set of states that should be considered to be absorbing,\n\t *               i.e., their outgoing edges are ignored, {@code null} = no states\n\t * @return the set of states Pre*(target)\n\t */\n\tpublic BitSet calculatePreStar(BitSet remain, BitSet target, BitSet absorbing)\n\t{\n\t\tBitSet result;\n\n\t\t// all target states are in Pre*\n\t\tresult = (BitSet)target.clone();\n\n\t\t// the stack of states whose predecessors have to be considered\n\t\tStack<Integer> todo = new Stack<Integer>();\n\n\t\t// initial todo: all the target states\n\t\tfor (Integer s : IterableBitSet.getSetBits(target)) {\n\t\t\ttodo.add(s);\n\t\t};\n\n\t\t// the set of states that are finished\n\t\tBitSet done = new BitSet();\n\n\t\twhile (!todo.isEmpty()) {\n\t\t\tint s = todo.pop();\n\t\t\t// already considered?\n\t\t\tif (done.get(s)) continue;\n\n\t\t\tdone.set(s);\n\n\t\t\t// for each predecessor in the graph\n\t\t\tfor (int p : getPre(s)) {\n\t\t\t\tif (absorbing != null && absorbing.get(p)) {\n\t\t\t\t\t// predecessor is absorbing, thus the edge is considered to not exist\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (remain == null || remain.get(p)) {\n\t\t\t\t\t// can reach result (and is in remain)\n\t\t\t\t\tresult.set(p);\n\t\t\t\t\tif (!done.get(p)) {\n\t\t\t\t\t\t// add to stack\n\t\t\t\t\t\ttodo.add(p);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/PrismSTPGAbstractRefine.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.*;\n\nimport common.IterableStateSet;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\npublic class PrismSTPGAbstractRefine extends QuantAbstractRefine\n{\n\t// Inputs\n\tprotected String traFile; // Model file for concrete model (PRISM explicit output)\n\tprotected String labFile; // Labels file for concrete model (PRISM explicit output)\n\tprotected String rewsFile; // State rewards file for concrete model (PRISM explicit output)\n\tprotected String rewtFile; // Transition rewards file for concrete model (PRISM explicit output)\n\tprotected String targetLabel; // PRISM label denoting target stares\n\n\t// Flags/settings\n\tprotected boolean exact = false; // Do model checking on the full concrete model?\n\tprotected boolean exactCheck = false; // Use exact result to check A-R result? (or just skip A-R?)\n\tprotected boolean rebuildImmed = false; // Rebuild split states immediately\n\n\t// Concrete model\n\tprotected ModelSimple<Double> modelConcrete;\n\tprotected int nConcrete; // Number of (concrete) states\n\tprotected BitSet initialConcrete; // Initial (concrete) states\n\tprotected BitSet targetConcrete; // Target (concrete) states\n\tprotected double exactInit; // Exact result for concrete model\n\n\t// Abstraction info\n\t// Map from concrete to abstract states\n\tprotected int concreteToAbstract[];\n\t// Map from abstract P1 choices to concrete state sets\n\tprotected List<List<Set<Integer>>> abstractToConcrete;\n\n\t/**\n\t * Default constructor.\n\t */\n\tpublic PrismSTPGAbstractRefine(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t// Implementation of initialise() for abstraction-refinement loop; see superclass for details \n\n\tprotected void initialise() throws PrismException\n\t{\n\t\tMap<String, BitSet> labels;\n\t\tDistributionSet set;\n\t\tDistribution distr;\n\t\tList<Set<Integer>> list;\n\t\tboolean isTarget, isInitial, existsInitial, existsTargetAndInitial, existsRest;\n\t\tint c, a, j, nAbstract;\n\n\t\t// Build concrete model\n\t\tmainLog.println(\"Building concrete \" + (buildEmbeddedDtmc ? \"(embedded) \" : \"\") + modelType + \"...\");\n\t\tswitch (modelType) {\n\t\tcase DTMC:\n\t\t\tmodelConcrete = buildEmbeddedDtmc ? new CTMCSimple() : new DTMCSimple();\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tmodelConcrete = new CTMCSimple();\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tmodelConcrete = new MDPSimple();\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot handle model type \" + modelType);\n\t\t}\n\t\tmodelConcrete.buildFromPrismExplicit(traFile);\n\t\tif (buildEmbeddedDtmc) {\n\t\t\t// TODO: do more efficiently (straight from tra file?)\n\t\t\tmainLog.println(\"Concrete \" + \"CTMC\" + \": \" + modelConcrete.infoString());\n\t\t\t//mainLog.println(modelConcrete);\n\t\t\tmodelConcrete = ((CTMCSimple) modelConcrete).buildEmbeddedDTMC();\n\t\t\t//mainLog.println(modelConcrete);\n\t\t}\n\t\t//if (propertyType == PropertyType.EXP_REACH)\n\t\t//modelConcrete.buildTransitionRewardsFromFile(rewtFile);\n\t\t//modelConcrete.setConstantTransitionReward(1.0);\n\t\tmainLog.println(\"Concrete \" + modelType + \": \" + modelConcrete.infoString());\n\t\tnConcrete = modelConcrete.getNumStates();\n\n\t\t// For a CTMC and time-bounded properties, we need to uniformise\n\t\tif (modelType == ModelType.CTMC) {\n\t\t\tif (propertyType != PropertyType.PROB_REACH) {\n\t\t\t\t((CTMCSimple) modelConcrete).uniformise(((CTMCSimple) modelConcrete).getDefaultUniformisationRate());\n\t\t\t}\n\t\t}\n\n\t\t// Get initial/target (concrete) states\n\t\tlabels = StateModelChecker.loadLabelsFile(labFile);\n\t\tinitialConcrete = labels.get(\"init\");\n\t\ttargetConcrete = labels.get(targetLabel);\n\t\tif (targetConcrete == null)\n\t\t\tthrow new PrismException(\"Unknown label \\\"\" + targetLabel + \"\\\"\");\n\n\t\t// set the initial states from the set initialConcrete\n\t\tfor (int state : new IterableStateSet(initialConcrete, modelConcrete.getNumStates())) {\n\t\t\tmodelConcrete.addInitialState(state);\n\t\t}\n\n\t\t// If the 'exact' flag is set, just do model checking on the concrete model (no abstraction)\n\t\tif (exact) {\n\t\t\tdoExactModelChecking();\n\t\t\tif (!exactCheck)\n\t\t\t\tthrow new PrismException(\"Terminated early after exact verification\");\n\t\t}\n\n\t\t// Build a mapping between concrete/abstract states\n\t\t// Initial abstract states: 0: initial, 1: target, 2:rest\n\t\tconcreteToAbstract = new int[nConcrete];\n\t\texistsInitial = existsTargetAndInitial = existsRest = false;\n\t\tfor (c = 0; c < nConcrete; c++) {\n\t\t\tisTarget = targetConcrete.get(c);\n\t\t\tisInitial = initialConcrete.get(c);\n\t\t\texistsInitial |= (!isTarget && isInitial);\n\t\t\texistsTargetAndInitial |= (isTarget && isInitial);\n\t\t\texistsRest |= (!isTarget && !isInitial);\n\t\t\tconcreteToAbstract[c] = isTarget ? 1 : isInitial ? 0 : 2;\n\t\t}\n\t\tif (!existsInitial)\n\t\t\tthrow new PrismException(\"No non-target initial states\");\n\n\t\tif (verbosity >= 10) {\n\t\t\tmainLog.print(\"Initial concreteToAbstract: \");\n\t\t\tmainLog.println(concreteToAbstract);\n\t\t}\n\n\t\t// Create (empty) abstraction and store initial states info\n\t\tnAbstract = existsRest ? 3 : 2;\n\t\tswitch (modelType) {\n\t\tcase DTMC:\n\t\t\tabstraction = new MDPSimple(nAbstract);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tabstraction = new CTMDPSimple(nAbstract);\n\t\t\t// TODO: ((CTMDP) abstraction).unif = ((CTMCSimple) modelConcrete).unif;\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tabstraction = new STPGAbstrSimple(nAbstract);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot handle model type \" + modelType);\n\t\t}\n\t\tabstraction.addInitialState(0);\n\t\tif (existsTargetAndInitial)\n\t\t\tabstraction.addInitialState(1);\n\n\t\t// Build target set\n\t\ttarget = new BitSet(nAbstract);\n\t\ttarget.set(1);\n\n\t\t// Construct initial abstraction.\n\t\t// Simultaneously, build abstractToConcrete,\n\t\t// which records which concrete states correspond to each game choice.\n\t\tabstractToConcrete = new ArrayList<List<Set<Integer>>>(nAbstract);\n\t\tfor (a = 0; a < nAbstract; a++)\n\t\t\tabstractToConcrete.add(new ArrayList<Set<Integer>>());\n\t\tfor (c = 0; c < nConcrete; c++) {\n\t\t\ta = concreteToAbstract[c];\n\t\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\t\tdistr = buildAbstractDistribution(c, (DTMCSimple) modelConcrete);\n\t\t\t\tj = ((MDPSimple) abstraction).addChoice(a, distr);\n\t\t\t\t//((MDPSimple) abstraction).setTransitionReward(a, j, ((DTMC) modelConcrete).getTransitionReward(c));\n\t\t\t\tbreak;\n\t\t\tcase CTMC:\n\t\t\t\tdistr = buildAbstractDistribution(c, (CTMCSimple) modelConcrete);\n\t\t\t\tj = ((CTMDPSimple) abstraction).addChoice(a, distr);\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\t\tset = buildAbstractDistributionSet(c, (MDPSimple) modelConcrete, (STPG) abstraction);\n\t\t\t\tj = ((STPGAbstrSimple) abstraction).addDistributionSet(a, set);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Cannot handle model type \" + modelType);\n\t\t\t}\n\t\t\tlist = abstractToConcrete.get(a);\n\t\t\tif (j >= list.size())\n\t\t\t\tlist.add(new HashSet<Integer>(1));\n\t\t\tlist.get(j).add(c);\n\t\t}\n\t}\n\n\t/**\n\t * Abstract a concrete state c of a DTMC ready to add to an MDP state.\n\t */\n\tprotected Distribution buildAbstractDistribution(int c, DTMCSimple<Double> dtmc)\n\t{\n\t\treturn dtmc.getTransitions(c).map(concreteToAbstract);\n\t}\n\n\t/**\n\t * Abstract a concrete state c of an MDP ready to add to an STPG state.\n\t */\n\tprotected DistributionSet buildAbstractDistributionSet(int c, MDPSimple<Double> mdp, STPG stpg)\n\t{\n\t\tDistributionSet set = ((STPGAbstrSimple) stpg).newDistributionSet(null);\n\t\tfor (Distribution<Double> distr : mdp.getChoices(c)) {\n\t\t\tset.add(distr.map(concreteToAbstract));\n\t\t}\n\t\treturn set;\n\t}\n\n\t// Implementation of splitState(...) for abstraction-refinement loop; see superclass for details \n\n\tprotected int splitState(int splitState, List<List<Integer>> choiceLists, Set<Integer> rebuiltStates,\n\t\t\tSet<Integer> rebuildStates) throws PrismException\n\t{\n\t\tList<Set<Integer>> list, listNew;\n\t\tSet<Integer> concreteStates, concreteStatesNew;\n\t\tint i, a, nAbstract, numNewStates;\n\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Splitting: #\" + splitState);\n\n\t\t// Add an element to the list of choices\n\t\t// corresponding to all remaining choices\n\t\taddRemainderIntoChoiceLists(splitState, choiceLists);\n\n\t\t// Do split...\n\t\tnAbstract = abstraction.getNumStates();\n\t\tnumNewStates = choiceLists.size();\n\t\tlist = abstractToConcrete.get(splitState);\n\t\ti = 0;\n\t\tfor (List<Integer> choiceList : choiceLists) {\n\t\t\t// Build...\n\t\t\tlistNew = new ArrayList<Set<Integer>>(1);\n\t\t\tconcreteStatesNew = new HashSet<Integer>();\n\t\t\tlistNew.add(concreteStatesNew);\n\t\t\t// Compute index 'a' of new abstract state\n\t\t\t// (first one reuses splitState, rest go on the end)\n\t\t\t// Also add new list to abstractToConcrete\n\t\t\tif (i == 0) {\n\t\t\t\ta = splitState;\n\t\t\t\tabstractToConcrete.set(a, listNew);\n\t\t\t} else {\n\t\t\t\ta = nAbstract + i - 1;\n\t\t\t\tabstractToConcrete.add(listNew);\n\t\t\t}\n\t\t\t//log.println(choiceList);\n\t\t\tfor (int j : choiceList) {\n\t\t\t\tconcreteStates = list.get(j);\n\t\t\t\tfor (int c : concreteStates) {\n\t\t\t\t\t//log.println(c);\n\t\t\t\t\tconcreteToAbstract[c] = a;\n\t\t\t\t\tconcreteStatesNew.add(c);\n\t\t\t\t}\n\t\t\t}\n\t\t\ti++;\n\t\t}\n\n\t\tif (verbosity >= 10) {\n\t\t\tmainLog.print(\"New concreteToAbstract: \");\n\t\t\tmainLog.println(concreteToAbstract);\n\t\t}\n\n\t\t// Add new states to the abstraction\n\t\tabstraction.addStates(numNewStates - 1);\n\t\t// Add new states to initial state set if needed\n\t\t// Note: we assume any abstract state contains either all/no initial states\n\t\tif (abstraction.isInitialState(splitState)) {\n\t\t\tfor (i = 1; i < numNewStates; i++) {\n\t\t\t\tabstraction.addInitialState(nAbstract + i - 1);\n\t\t\t}\n\t\t}\n\n\t\tfor (i = 0; i < nAbstract; i++) {\n\t\t\tif (i == splitState || abstraction.isSuccessor(i, splitState)) {\n\t\t\t\tif (rebuildImmed) {\n\t\t\t\t\trebuildAbstractionState(i);\n\t\t\t\t\trebuiltStates.add(i);\n\t\t\t\t} else {\n\t\t\t\t\trebuildStates.add(i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tfor (i = 1; i < numNewStates; i++) {\n\t\t\tif (rebuildImmed) {\n\t\t\t\trebuildAbstractionState(nAbstract + i - 1);\n\t\t\t\trebuiltStates.add(i);\n\t\t\t} else {\n\t\t\t\trebuildStates.add(nAbstract + i - 1);\n\t\t\t}\n\t\t}\n\n\t\treturn numNewStates;\n\t}\n\n\t// Implementation of rebuildAbstraction(...) for abstraction-refinement loop; see superclass for details \n\n\tprotected void rebuildAbstraction(Set<Integer> rebuildStates) throws PrismException\n\t{\n\t\tfor (int a : rebuildStates) {\n\t\t\trebuildAbstractionState(a);\n\t\t}\n\t}\n\n\tprotected void rebuildAbstractionState(int i) throws PrismException\n\t{\n\t\tList<Set<Integer>> list, listNew;\n\t\tDistribution distr;\n\t\tDistributionSet set;\n\t\tint j, a;\n\n\t\tlist = abstractToConcrete.get(i);\n\t\tlistNew = new ArrayList<Set<Integer>>();\n\t\tabstraction.clearState(i);\n\t\tfor (Set<Integer> concreteStates : list) {\n\t\t\tfor (int c : concreteStates) {\n\t\t\t\ta = concreteToAbstract[c];\n\t\t\t\t// ASSERT: a = i ???\n\t\t\t\tif (a != i)\n\t\t\t\t\tthrow new PrismException(\"Oops\");\n\t\t\t\tswitch (modelType) {\n\t\t\t\tcase DTMC:\n\t\t\t\t\tdistr = buildAbstractDistribution(c, (DTMCSimple) modelConcrete);\n\t\t\t\t\tj = ((MDPSimple) abstraction).addChoice(a, distr);\n\t\t\t\t\t//((MDPSimple) abstraction).setTransitionReward(a, j, ((DTMC) modelConcrete).getTransitionReward(c));\n\t\t\t\t\tbreak;\n\t\t\t\tcase CTMC:\n\t\t\t\t\tdistr = buildAbstractDistribution(c, (CTMCSimple) modelConcrete);\n\t\t\t\t\tj = ((CTMDPSimple) abstraction).addChoice(a, distr);\n\t\t\t\t\t// TODO: recompute unif?\n\t\t\t\t\tbreak;\n\t\t\t\tcase MDP:\n\t\t\t\t\tset = buildAbstractDistributionSet(c, (MDPSimple) modelConcrete, (STPG) abstraction);\n\t\t\t\t\tj = ((STPGAbstrSimple) abstraction).addDistributionSet(a, set);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Cannot handle model type \" + modelType);\n\t\t\t\t}\n\t\t\t\tif (j >= listNew.size())\n\t\t\t\t\tlistNew.add(new HashSet<Integer>(1));\n\t\t\t\tlistNew.get(j).add(c);\n\t\t\t\t//TODO: if (initialConcrete.get(c))\n\t\t\t\t//TODO: \tstpg.initialStates.add(a);\n\t\t\t}\n\t\t}\n\t\tabstractToConcrete.set(i, listNew);\n\t}\n\n\t/**\n\t * Just do model checking on the concrete model (no abstraction)\n\t */\n\tpublic void doExactModelChecking() throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tswitch (modelType) {\n\t\tcase DTMC:\n\t\t\tDTMCModelChecker mcDtmc = new DTMCModelChecker(null);\n\t\t\tmcDtmc.inheritSettings(mcOptions);\n\t\t\tswitch (propertyType) {\n\t\t\tcase PROB_REACH:\n\t\t\t\tres = mcDtmc.computeReachProbs((DTMC) modelConcrete, targetConcrete);\n\t\t\t\tbreak;\n\t\t\tcase PROB_REACH_BOUNDED:\n\t\t\t\tres = mcDtmc.computeBoundedReachProbs((DTMC) modelConcrete, targetConcrete, reachBound);\n\t\t\t\tbreak;\n\t\t\tcase EXP_REACH:\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tCTMCModelChecker mcCtmc = new CTMCModelChecker(null);\n\t\t\tmcCtmc.inheritSettings(mcOptions);\n\t\t\tswitch (propertyType) {\n\t\t\t/*case PROB_REACH:\n\t\t\t\tres = mcDtmc.probReach((DTMC) modelConcrete, targetConcrete);\n\t\t\t\tbreak;\n\t\t\tcase PROB_REACH_BOUNDED:\n\t\t\t\tres = mcDtmc.probReachBounded((DTMC) modelConcrete, targetConcrete, reachBound);\n\t\t\t\tbreak;\n\t\t\tcase EXP_REACH:\n\t\t\t\tbreak;*/\n\t\t\t}\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tMDPModelChecker mcMdp = new MDPModelChecker(null);\n\t\t\tmcMdp.inheritSettings(mcOptions);\n\t\t\tswitch (propertyType) {\n\t\t\tcase PROB_REACH:\n\t\t\t\tres = mcMdp.computeReachProbs((MDP) modelConcrete, targetConcrete, min);\n\t\t\t\tbreak;\n\t\t\tcase PROB_REACH_BOUNDED:\n\t\t\t\tres = mcMdp.computeBoundedReachProbs((MDP) modelConcrete, targetConcrete, reachBound, min);\n\t\t\t\tbreak;\n\t\t\tcase EXP_REACH:\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\n\t\t// Unhandled cases\n\t\tif (res == null) {\n\t\t\tString s = \"Cannot do exact model checking for\";\n\t\t\ts += \" model type \" + modelType + \" and property type \" + propertyType;\n\t\t\tthrow new PrismException(s);\n\t\t}\n\n\t\t// Display results for all initial states\n\t\tmainLog.print(\"Results for initial state(s):\");\n\t\tfor (int j : modelConcrete.getInitialStates()) {\n\t\t\tmainLog.print(\" \" + res.soln[j]);\n\t\t}\n\t\tmainLog.println();\n\n\t\t// Pick min/max value over all initial states\n\t\texactInit = min ? Double.POSITIVE_INFINITY : Double.NEGATIVE_INFINITY;\n\t\tfor (int j : modelConcrete.getInitialStates()) {\n\t\t\tif (min) {\n\t\t\t\texactInit = Math.min(exactInit, res.soln[j]);\n\t\t\t} else {\n\t\t\t\texactInit = Math.max(exactInit, res.soln[j]);\n\t\t\t}\n\t\t}\n\t}\n\n\t// Override this to also print out concrete model details at the end\n\t@Override\n\tprotected void printFinalSummary(String initAbstractionInfo, boolean canRefine)\n\t{\n\t\tmainLog.println(\"\\nConcrete \" + modelType + \": \" + modelConcrete.infoString());\n\t\tsuper.printFinalSummary(initAbstractionInfo, canRefine);\n\t\tmainLog.print(\"Exact (concrete) result: \" + exactInit);\n\t\tmainLog.println(\" (diff = \" + Math.abs(exactInit - ((lbInit + ubInit) / 2)) + \")\");\n\t}\n\n\tpublic static void main(String args[])\n\t{\n\t\tPrismSTPGAbstractRefine abstractRefine;\n\t\tboolean min = false;\n\t\tArrayList<String> nonSwitches;\n\t\tString s, sw, sOpt, filenameBase;\n\t\tint i, j;\n\n\t\ttry {\n\t\t\t// Create abstraction-refinement engine\n\t\t\tabstractRefine = new PrismSTPGAbstractRefine(null);\n\t\t\tabstractRefine.sanityChecks = true;\n\n\t\t\t// Parse command line args\n\t\t\tif (args.length < 3) {\n\t\t\t\tSystem.err.println(\"Usage: java ... [options] <tra file> <lab file> <target label>\");\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t\tnonSwitches = new ArrayList<String>();\n\t\t\tfor (i = 0; i < args.length; i++) {\n\t\t\t\ts = args[i];\n\t\t\t\t// Process a non-switch\n\t\t\t\tif (s.charAt(0) != '-') {\n\t\t\t\t\tnonSwitches.add(s);\n\t\t\t\t}\n\t\t\t\t// Process a switch\n\t\t\t\telse {\n\t\t\t\t\ts = s.substring(1);\n\t\t\t\t\t// Break switch up into parts if contains =\n\t\t\t\t\tif ((j = s.indexOf('=')) != -1) {\n\t\t\t\t\t\tsOpt = s.substring(j + 1);\n\t\t\t\t\t\tsw = s.substring(0, j);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tsOpt = null;\n\t\t\t\t\t\tsw = s;\n\t\t\t\t\t}\n\t\t\t\t\t// Local options\n\t\t\t\t\tif (sw.equals(\"min\")) {\n\t\t\t\t\t\tmin = true;\n\t\t\t\t\t} else if (sw.equals(\"max\")) {\n\t\t\t\t\t\tmin = false;\n\t\t\t\t\t} else if (sw.equals(\"dtmc\")) {\n\t\t\t\t\t\tabstractRefine.setModelType(ModelType.DTMC);\n\t\t\t\t\t} else if (sw.equals(\"ctmc\")) {\n\t\t\t\t\t\tabstractRefine.setModelType(ModelType.CTMC);\n\t\t\t\t\t} else if (sw.equals(\"mdp\")) {\n\t\t\t\t\t\tabstractRefine.setModelType(ModelType.MDP);\n\t\t\t\t\t} else if (sw.equals(\"probreach\")) {\n\t\t\t\t\t\tabstractRefine.setPropertyType(PropertyType.PROB_REACH);\n\t\t\t\t\t} else if (sw.equals(\"expreach\")) {\n\t\t\t\t\t\tabstractRefine.setPropertyType(PropertyType.EXP_REACH);\n\t\t\t\t\t} else if (sw.equals(\"probreachbnd\")) {\n\t\t\t\t\t\tabstractRefine.setPropertyType(PropertyType.PROB_REACH_BOUNDED);\n\t\t\t\t\t\tif (sOpt != null) {\n\t\t\t\t\t\t\tabstractRefine.setReachBound(Integer.parseInt(sOpt));\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (sw.equals(\"exact\")) {\n\t\t\t\t\t\tabstractRefine.exact = true;\n\t\t\t\t\t} else if (sw.equals(\"exactcheck\")) {\n\t\t\t\t\t\tabstractRefine.exact = true;\n\t\t\t\t\t\tabstractRefine.exactCheck = true;\n\t\t\t\t\t} else if (sw.equals(\"rebuild\") && sOpt.equals(\"immed\")) {\n\t\t\t\t\t\tabstractRefine.rebuildImmed = true;\n\t\t\t\t\t}\n\n\t\t\t\t\t// Otherwise, try passing to abstraction-refinement engine\n\t\t\t\t\telse {\n\t\t\t\t\t\tabstractRefine.parseOption(s);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Store params\n\t\t\tfilenameBase = nonSwitches.get(0);\n\t\t\tabstractRefine.targetLabel = nonSwitches.get(1);\n\t\t\tabstractRefine.traFile = filenameBase + \".tra\";\n\t\t\tabstractRefine.labFile = filenameBase + \".lab\";\n\t\t\tabstractRefine.rewsFile = filenameBase + \".rews\";\n\t\t\tabstractRefine.rewtFile = filenameBase + \".rewt\";\n\t\t\t// Display command-line args and settings:\n\t\t\tSystem.out.print(\"Command:\");\n\t\t\tfor (i = 0; i < args.length; i++)\n\t\t\t\tSystem.out.print(\" \" + args[i]);\n\t\t\tSystem.out.println();\n\t\t\tabstractRefine.printSettings();\n\t\t\t// Go...\n\t\t\tabstractRefine.abstractRefine(min);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage() + \".\");\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ProbModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport static prism.PrismSettings.DEFAULT_EXPORT_MODEL_PRECISION;\n\nimport java.io.File;\nimport java.util.BitSet;\nimport java.util.List;\n\nimport explicit.rewards.ConstructRewards;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.Rewards;\nimport explicit.rewards.STPGRewards;\nimport parser.ast.Coalition;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionSS;\nimport parser.ast.ExpressionStrategy;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypePathBool;\nimport parser.type.TypePathDouble;\nimport prism.AccuracyFactory;\nimport prism.Evaluator;\nimport prism.IntegerBound;\nimport prism.OpRelOpBound;\nimport prism.Prism;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport prism.RewardGenerator;\n\n/**\n * Super class for explicit-state probabilistic model checkers.\n */\npublic class ProbModelChecker extends NonProbModelChecker\n{\n\t// Flags/settings\n\t// (NB: defaults do not necessarily coincide with PRISM)\n\n\t// Method used to solve linear equation systems\n\tprotected LinEqMethod linEqMethod = LinEqMethod.GAUSS_SEIDEL;\n\t// Method used to solve MDPs\n\tprotected MDPSolnMethod mdpSolnMethod = MDPSolnMethod.GAUSS_SEIDEL;\n\t// Method used to solve IMDPs (and IDTMCs)\n\tprotected IMDPSolnMethod imdpSolnMethod = IMDPSolnMethod.GAUSS_SEIDEL;\n\t// Iterative numerical method termination criteria\n\tprotected TermCrit termCrit = TermCrit.RELATIVE;\n\t// Parameter for iterative numerical method termination criteria\n\tprotected double termCritParam = 1e-8;\n\t// Max iterations for numerical solution\n\tprotected int maxIters = 100000;\n\t// Resolution for POMDP fixed grid approximation algorithm\n\tprotected int gridResolution = 10;\n\t// Use precomputation algorithms in model checking?\n\tprotected boolean precomp = true;\n\tprotected boolean prob0 = true;\n\tprotected boolean prob1 = true;\n\t// should we suppress log output during precomputations?\n\tprotected boolean silentPrecomputations = false;\n\t// Use predecessor relation? (e.g. for precomputation)\n\tprotected boolean preRel = true;\n\t// Direction of convergence for value iteration (lfp/gfp)\n\tprotected ValIterDir valIterDir = ValIterDir.BELOW;\n\t// Method used for numerical solution\n\tprotected SolnMethod solnMethod = SolnMethod.VALUE_ITERATION;\n\t// Is non-convergence of an iterative method an error?\n\tprotected boolean errorOnNonConverge = true;\n\n\t// Delay between occasional updates for slow processes, e.g. numerical solution (milliseconds)\n\tpublic static final int UPDATE_DELAY = 5000;\n\n\n\t// Enums for flags/settings\n\n\t// Method used for numerical solution\n\tpublic enum LinEqMethod {\n\t\tPOWER, JACOBI, GAUSS_SEIDEL, BACKWARDS_GAUSS_SEIDEL, JOR, SOR, BACKWARDS_SOR;\n\t\tpublic String fullName()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\tcase POWER:\n\t\t\t\treturn \"Power method\";\n\t\t\tcase JACOBI:\n\t\t\t\treturn \"Jacobi\";\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\t\treturn \"Gauss-Seidel\";\n\t\t\tcase BACKWARDS_GAUSS_SEIDEL:\n\t\t\t\treturn \"Backwards Gauss-Seidel\";\n\t\t\tcase JOR:\n\t\t\t\treturn \"JOR\";\n\t\t\tcase SOR:\n\t\t\t\treturn \"SOR\";\n\t\t\tcase BACKWARDS_SOR:\n\t\t\t\treturn \"Backwards SOR\";\n\t\t\tdefault:\n\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t};\n\n\t// Method used for solving MDPs\n\tpublic enum MDPSolnMethod {\n\t\tVALUE_ITERATION, GAUSS_SEIDEL, POLICY_ITERATION, MODIFIED_POLICY_ITERATION, LINEAR_PROGRAMMING;\n\t\tpublic String fullName()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\tcase VALUE_ITERATION:\n\t\t\t\treturn \"Value iteration\";\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\t\treturn \"Gauss-Seidel\";\n\t\t\tcase POLICY_ITERATION:\n\t\t\t\treturn \"Policy iteration\";\n\t\t\tcase MODIFIED_POLICY_ITERATION:\n\t\t\t\treturn \"Modified policy iteration\";\n\t\t\tcase LINEAR_PROGRAMMING:\n\t\t\t\treturn \"Linear programming\";\n\t\t\tdefault:\n\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t};\n\n\t// Method used for solving IMDPs (and IDTMCs)\n\tpublic enum IMDPSolnMethod {\n\t\tVALUE_ITERATION, GAUSS_SEIDEL;\n\t\tpublic String fullName()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\tcase VALUE_ITERATION:\n\t\t\t\treturn \"Value iteration\";\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\t\treturn \"Gauss-Seidel\";\n\t\t\tdefault:\n\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t};\n\n\t// Iterative numerical method termination criteria\n\tpublic enum TermCrit {\n\t\tABSOLUTE, RELATIVE\n\t};\n\n\t// Direction of convergence for value iteration (lfp/gfp)\n\tpublic enum ValIterDir {\n\t\tBELOW, ABOVE\n\t};\n\n\t// Method used for numerical solution\n\tpublic enum SolnMethod {\n\t\tVALUE_ITERATION, GAUSS_SEIDEL, POLICY_ITERATION, MODIFIED_POLICY_ITERATION, LINEAR_PROGRAMMING\n\t};\n\n\t/**\n\t * Create a new ProbModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic ProbModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\n\t\t// If present, initialise settings from PrismSettings\n\t\tif (settings != null) {\n\t\t\tString s;\n\t\t\t// PRISM_LIN_EQ_METHOD\n\t\t\ts = settings.getString(PrismSettings.PRISM_LIN_EQ_METHOD);\n\t\t\tif (s.equals(\"Power\")) {\n\t\t\t\tsetLinEqMethod(LinEqMethod.POWER);\n\t\t\t} else if (s.equals(\"Jacobi\")) {\n\t\t\t\tsetLinEqMethod(LinEqMethod.JACOBI);\n\t\t\t} else if (s.equals(\"Gauss-Seidel\")) {\n\t\t\t\tsetLinEqMethod(LinEqMethod.GAUSS_SEIDEL);\n\t\t\t} else if (s.equals(\"Backwards Gauss-Seidel\")) {\n\t\t\t\tsetLinEqMethod(LinEqMethod.BACKWARDS_GAUSS_SEIDEL);\n\t\t\t} else if (s.equals(\"JOR\")) {\n\t\t\t\tsetLinEqMethod(LinEqMethod.JOR);\n\t\t\t} else if (s.equals(\"SOR\")) {\n\t\t\t\tsetLinEqMethod(LinEqMethod.SOR);\n\t\t\t} else if (s.equals(\"Backwards SOR\")) {\n\t\t\t\tsetLinEqMethod(LinEqMethod.BACKWARDS_SOR);\n\t\t\t} else {\n\t\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not support linear equation solution method \\\"\" + s + \"\\\"\");\n\t\t\t}\n\t\t\t// PRISM_MDP_SOLN_METHOD\n\t\t\ts = settings.getString(PrismSettings.PRISM_MDP_SOLN_METHOD);\n\t\t\tif (s.equals(\"Value iteration\")) {\n\t\t\t\tsetMDPSolnMethod(MDPSolnMethod.VALUE_ITERATION);\n\t\t\t} else if (s.equals(\"Gauss-Seidel\")) {\n\t\t\t\tsetMDPSolnMethod(MDPSolnMethod.GAUSS_SEIDEL);\n\t\t\t} else if (s.equals(\"Policy iteration\")) {\n\t\t\t\tsetMDPSolnMethod(MDPSolnMethod.POLICY_ITERATION);\n\t\t\t} else if (s.equals(\"Modified policy iteration\")) {\n\t\t\t\tsetMDPSolnMethod(MDPSolnMethod.MODIFIED_POLICY_ITERATION);\n\t\t\t} else if (s.equals(\"Linear programming\")) {\n\t\t\t\tsetMDPSolnMethod(MDPSolnMethod.LINEAR_PROGRAMMING);\n\t\t\t} else {\n\t\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not support MDP solution method \\\"\" + s + \"\\\"\");\n\t\t\t}\n\t\t\t// PRISM_IMDP_SOLN_METHOD\n\t\t\ts = settings.getString(PrismSettings.PRISM_IMDP_SOLN_METHOD);\n\t\t\tif (s.equals(\"Value iteration\")) {\n\t\t\t\tsetIMDPSolnMethod(IMDPSolnMethod.VALUE_ITERATION);\n\t\t\t} else if (s.equals(\"Gauss-Seidel\")) {\n\t\t\t\tsetIMDPSolnMethod(IMDPSolnMethod.GAUSS_SEIDEL);\n\t\t\t} else {\n\t\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not support IMDP solution method \\\"\" + s + \"\\\"\");\n\t\t\t}\n\t\t\t// PRISM_TERM_CRIT\n\t\t\ts = settings.getString(PrismSettings.PRISM_TERM_CRIT);\n\t\t\tif (s.equals(\"Absolute\")) {\n\t\t\t\tsetTermCrit(TermCrit.ABSOLUTE);\n\t\t\t} else if (s.equals(\"Relative\")) {\n\t\t\t\tsetTermCrit(TermCrit.RELATIVE);\n\t\t\t} else {\n\t\t\t\tthrow new PrismNotSupportedException(\"Unknown termination criterion \\\"\" + s + \"\\\"\");\n\t\t\t}\n\t\t\t// PRISM_TERM_CRIT_PARAM\n\t\t\tsetTermCritParam(settings.getDouble(PrismSettings.PRISM_TERM_CRIT_PARAM));\n\t\t\t// PRISM_MAX_ITERS\n\t\t\tsetMaxIters(settings.getInteger(PrismSettings.PRISM_MAX_ITERS));\n\t\t\t// PRISM_GRID_RESOLUTION\n\t\t\tsetGridResolution(settings.getInteger(PrismSettings.PRISM_GRID_RESOLUTION));\n\t\t\t// PRISM_PRECOMPUTATION\n\t\t\tsetPrecomp(settings.getBoolean(PrismSettings.PRISM_PRECOMPUTATION));\n\t\t\t// PRISM_PROB0\n\t\t\tsetProb0(settings.getBoolean(PrismSettings.PRISM_PROB0));\n\t\t\t// PRISM_PROB1\n\t\t\tsetProb1(settings.getBoolean(PrismSettings.PRISM_PROB1));\n\t\t\t// PRISM_USE_PRE\n\t\t\tsetPreRel(settings.getBoolean(PrismSettings.PRISM_PRE_REL));\n\t\t\t// PRISM_FAIRNESS\n\t\t\tif (settings.getBoolean(PrismSettings.PRISM_FAIRNESS)) {\n\t\t\t\tthrow new PrismNotSupportedException(\"The explicit engine does not support model checking MDPs under fairness\");\n\t\t\t}\n\t\t}\n\t}\n\n\t// Settings methods\n\n\t/**\n\t * Inherit settings (and the log) from another ProbModelChecker object.\n\t * For model checker objects that inherit a PrismSettings object, this is superfluous\n\t * since this has been done already.\n\t */\n\tpublic void inheritSettings(ProbModelChecker other)\n\t{\n\t\tsuper.inheritSettings(other);\n\t\tsetLinEqMethod(other.getLinEqMethod());\n\t\tsetMDPSolnMethod(other.getMDPSolnMethod());\n\t\tsetIMDPSolnMethod(other.getIMDPSolnMethod());\n\t\tsetTermCrit(other.getTermCrit());\n\t\tsetTermCritParam(other.getTermCritParam());\n\t\tsetMaxIters(other.getMaxIters());\n\t\tsetGridResolution(other.getGridResolution());\n\t\tsetPrecomp(other.getPrecomp());\n\t\tsetProb0(other.getProb0());\n\t\tsetProb1(other.getProb1());\n\t\tsetValIterDir(other.getValIterDir());\n\t\tsetSolnMethod(other.getSolnMethod());\n\t\tsetErrorOnNonConverge(other.geterrorOnNonConverge());\n\t}\n\n\t/**\n\t * Print summary of current settings.\n\t */\n\tpublic void printSettings()\n\t{\n\t\tsuper.printSettings();\n\t\tmainLog.print(\"linEqMethod = \" + linEqMethod + \" \");\n\t\tmainLog.print(\"mdpSolnMethod = \" + mdpSolnMethod + \" \");\n\t\tmainLog.print(\"imdpSolnMethod = \" + imdpSolnMethod + \" \");\n\t\tmainLog.print(\"termCrit = \" + termCrit + \" \");\n\t\tmainLog.print(\"termCritParam = \" + termCritParam + \" \");\n\t\tmainLog.print(\"maxIters = \" + maxIters + \" \");\n\t\tmainLog.print(\"gridResolution = \" + gridResolution + \" \");\n\t\tmainLog.print(\"precomp = \" + precomp + \" \");\n\t\tmainLog.print(\"prob0 = \" + prob0 + \" \");\n\t\tmainLog.print(\"prob1 = \" + prob1 + \" \");\n\t\tmainLog.print(\"valIterDir = \" + valIterDir + \" \");\n\t\tmainLog.print(\"solnMethod = \" + solnMethod + \" \");\n\t\tmainLog.print(\"errorOnNonConverge = \" + errorOnNonConverge + \" \");\n\t}\n\n\t// Set methods for flags/settings\n\n\t/**\n\t * Set verbosity level, i.e. amount of output produced.\n\t */\n\tpublic void setVerbosity(int verbosity)\n\t{\n\t\tthis.verbosity = verbosity;\n\t}\n\n\t/**\n\t * Set flag for suppressing log output during precomputations (prob0, prob1, ...)\n\t * @param value silent?\n\t * @return the previous value of this flag\n\t */\n\tpublic boolean setSilentPrecomputations(boolean value)\n\t{\n\t\tboolean old = silentPrecomputations;\n\t\tsilentPrecomputations = value;\n\t\treturn old;\n\t}\n\n\t/**\n\t * Set method used to solve linear equation systems.\n\t */\n\tpublic void setLinEqMethod(LinEqMethod linEqMethod)\n\t{\n\t\tthis.linEqMethod = linEqMethod;\n\t}\n\n\t/**\n\t * Set method used to solve MDPs.\n\t */\n\tpublic void setMDPSolnMethod(MDPSolnMethod mdpSolnMethod)\n\t{\n\t\tthis.mdpSolnMethod = mdpSolnMethod;\n\t}\n\n\t/**\n\t * Set method used to solve IMDPs (and IDTMCs).\n\t */\n\tpublic void setIMDPSolnMethod(IMDPSolnMethod imdpSolnMethod)\n\t{\n\t\tthis.imdpSolnMethod = imdpSolnMethod;\n\t}\n\n\t/**\n\t * Set termination criteria type for numerical iterative methods.\n\t */\n\tpublic void setTermCrit(TermCrit termCrit)\n\t{\n\t\tthis.termCrit = termCrit;\n\t}\n\n\t/**\n\t * Set termination criteria parameter (epsilon) for numerical iterative methods.\n\t */\n\tpublic void setTermCritParam(double termCritParam)\n\t{\n\t\tthis.termCritParam = termCritParam;\n\t}\n\n\t/**\n\t * Set maximum number of iterations for numerical iterative methods.\n\t */\n\tpublic void setMaxIters(int maxIters)\n\t{\n\t\tthis.maxIters = maxIters;\n\t}\n\n\t/**\n\t * Set resolution for POMDP fixed grid approximation algorithm.\n\t */\n\tpublic void setGridResolution(int gridResolution)\n\t{\n\t\tthis.gridResolution = gridResolution;\n\t}\n\n\t/**\n\t * Set whether or not to use precomputation (Prob0, Prob1, etc.).\n\t */\n\tpublic void setPrecomp(boolean precomp)\n\t{\n\t\tthis.precomp = precomp;\n\t}\n\n\t/**\n\t * Set whether or not to use Prob0 precomputation\n\t */\n\tpublic void setProb0(boolean prob0)\n\t{\n\t\tthis.prob0 = prob0;\n\t}\n\n\t/**\n\t * Set whether or not to use Prob1 precomputation\n\t */\n\tpublic void setProb1(boolean prob1)\n\t{\n\t\tthis.prob1 = prob1;\n\t}\n\n\t/**\n\t * Set whether or not to use pre-computed predecessor relation\n\t */\n\tpublic void setPreRel(boolean preRel)\n\t{\n\t\tthis.preRel = preRel;\n\t}\n\n\t/**\n\t * Set direction of convergence for value iteration (lfp/gfp).\n\t */\n\tpublic void setValIterDir(ValIterDir valIterDir)\n\t{\n\t\tthis.valIterDir = valIterDir;\n\t}\n\n\t/**\n\t * Set method used for numerical solution.\n\t */\n\tpublic void setSolnMethod(SolnMethod solnMethod)\n\t{\n\t\tthis.solnMethod = solnMethod;\n\t}\n\n\t/**\n\t * Set whether non-convergence of an iterative method an error\n\t */\n\tpublic void setErrorOnNonConverge(boolean errorOnNonConverge)\n\t{\n\t\tthis.errorOnNonConverge = errorOnNonConverge;\n\t}\n\n\t// Get methods for flags/settings\n\n\tpublic int getVerbosity()\n\t{\n\t\treturn verbosity;\n\t}\n\n\tpublic LinEqMethod getLinEqMethod()\n\t{\n\t\treturn linEqMethod;\n\t}\n\n\tpublic MDPSolnMethod getMDPSolnMethod()\n\t{\n\t\treturn mdpSolnMethod;\n\t}\n\n\tpublic IMDPSolnMethod getIMDPSolnMethod()\n\t{\n\t\treturn imdpSolnMethod;\n\t}\n\n\tpublic TermCrit getTermCrit()\n\t{\n\t\treturn termCrit;\n\t}\n\n\tpublic double getTermCritParam()\n\t{\n\t\treturn termCritParam;\n\t}\n\n\tpublic int getMaxIters()\n\t{\n\t\treturn maxIters;\n\t}\n\n\tpublic int getGridResolution()\n\t{\n\t\treturn gridResolution;\n\t}\n\n\tpublic boolean getPrecomp()\n\t{\n\t\treturn precomp;\n\t}\n\n\tpublic boolean getProb0()\n\t{\n\t\treturn prob0;\n\t}\n\n\tpublic boolean getProb1()\n\t{\n\t\treturn prob1;\n\t}\n\n\tpublic boolean getPreRel()\n\t{\n\t\treturn preRel;\n\t}\n\n\tpublic ValIterDir getValIterDir()\n\t{\n\t\treturn valIterDir;\n\t}\n\n\tpublic SolnMethod getSolnMethod()\n\t{\n\t\treturn solnMethod;\n\t}\n\n\t/**\n\t * Is non-convergence of an iterative method an error?\n\t */\n\tpublic boolean geterrorOnNonConverge()\n\t{\n\t\treturn errorOnNonConverge;\n\t}\n\n\t// Model checking functions\n\n\t@Override\n\tpublic StateValues checkExpression(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res;\n\n\t\t// <<>> or [[]] operator\n\t\tif (expr instanceof ExpressionStrategy) {\n\t\t\tres = checkExpressionStrategy(model, (ExpressionStrategy) expr, statesOfInterest);\n\t\t}\n\t\t// P operator\n\t\telse if (expr instanceof ExpressionProb) {\n\t\t\tres = checkExpressionProb(model, (ExpressionProb) expr, statesOfInterest);\n\t\t}\n\t\t// R operator\n\t\telse if (expr instanceof ExpressionReward) {\n\t\t\tres = checkExpressionReward(model, (ExpressionReward) expr, statesOfInterest);\n\t\t}\n\t\t// S operator\n\t\telse if (expr instanceof ExpressionSS) {\n\t\t\tres = checkExpressionSteadyState(model, (ExpressionSS) expr);\n\t\t}\n\t\t// Otherwise, use the superclass\n\t\telse {\n\t\t\tres = super.checkExpression(model, expr, statesOfInterest);\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check a <<>> or [[]] operator expression and return the values for the statesOfInterest.\n\t * * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionStrategy(Model<?> model, ExpressionStrategy expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Only support <<>>/[[]] for MDPs right now\n\t\tif (!(this instanceof MDPModelChecker))\n\t\t\tthrow new PrismNotSupportedException(\"The \" + expr.getOperatorString() + \" operator is only supported for MDPs currently\");\n\n\t\t// Will we be quantifying universally or existentially over strategies/adversaries?\n\t\tboolean forAll = !expr.isThereExists();\n\t\t\n\t\t// Extract coalition info\n\t\tCoalition coalition = expr.getCoalition();\n\t\t// For non-games (i.e., models with a single player), deal with the coalition operator here and then remove it\n\t\tif (coalition != null && !model.getModelType().multiplePlayers()) {\n\t\t\tif (coalition.isEmpty()) {\n\t\t\t\t// An empty coalition negates the quantification (\"*\" has no effect)\n\t\t\t\tforAll = !forAll;\n\t\t\t}\n\t\t\tcoalition = null;\n\t\t}\n\n\t\t// For now, just support a single expression (which may encode a Boolean combination of objectives)\n\t\tList<Expression> exprs = expr.getOperands();\n\t\tif (exprs.size() > 1) {\n\t\t\tthrow new PrismException(\"Cannot currently check strategy operators wth lists of expressions\");\n\t\t}\n\t\tExpression exprSub = exprs.get(0);\n\t\t// Pass onto relevant method:\n\t\t// P operator\n\t\tif (exprSub instanceof ExpressionProb) {\n\t\t\treturn checkExpressionProb(model, (ExpressionProb) exprSub, forAll, coalition, statesOfInterest);\n\t\t}\n\t\t// R operator\n\t\telse if (exprSub instanceof ExpressionReward) {\n\t\t\treturn checkExpressionReward(model, (ExpressionReward) exprSub, forAll, coalition, statesOfInterest);\n\t\t}\n\t\t// Anything else is an error \n\t\telse {\n\t\t\tthrow new PrismException(\"Unexpected operators in \" + expr.getOperatorString() + \" operator\");\n\t\t}\n\t}\n\n\t/**\n\t * Model check a P operator expression and return the values for the statesOfInterest.\n \t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionProb(Model<?> model, ExpressionProb expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Use the default semantics for a standalone P operator\n\t\t// (i.e. quantification over all strategies, and no game-coalition info)\n\t\treturn checkExpressionProb(model, expr, true, null, statesOfInterest);\n\t}\n\t\n\t/**\n\t * Model check a P operator expression and return the values for the states of interest.\n\t * @param model The model\n\t * @param expr The P operator expression\n\t * @param forAll Are we checking \"for all strategies\" (true) or \"there exists a strategy\" (false)? [irrelevant for numerical (=?) queries] \n\t * @param coalition If relevant, info about which set of players this P operator refers to (null if irrelevant)\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionProb(Model<?> model, ExpressionProb expr, boolean forAll, Coalition coalition, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Get info from P operator\n\t\tOpRelOpBound opInfo = expr.getRelopBoundInfo(constantValues);\n\t\tMinMax minMax = opInfo.getMinMax(model.getModelType(), forAll);\n\n\t\t// Compute probabilities\n\t\tStateValues probs = checkProbPathFormula(model, expr.getExpression(), minMax, statesOfInterest);\n\n\t\t// Print out probabilities\n\t\tif (getVerbosity() > 5) {\n\t\t\tmainLog.print(\"\\nProbabilities (non-zero only) for all states:\\n\");\n\t\t\tprobs.print(mainLog);\n\t\t}\n\n\t\t// For =? properties, just return values; otherwise compare against bound\n\t\tif (!opInfo.isNumeric()) {\n\t\t\tprobs.applyPredicate(v -> opInfo.apply((double) v, probs.getAccuracy()));\n\t\t}\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute probabilities for the contents of a P operator.\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkProbPathFormula(Model<?> model, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Test whether this is a simple path formula (i.e. PCTL)\n\t\t// and whether we want to use the corresponding algorithms\n\t\tboolean useSimplePathAlgo = expr.isSimplePathFormula();\n\n\t\tif (useSimplePathAlgo &&\n\t\t    settings.getBoolean(PrismSettings.PRISM_PATH_VIA_AUTOMATA) &&\n\t\t    LTLModelChecker.isSupportedLTLFormula(model.getModelType(), expr)) {\n\t\t\t// If PRISM_PATH_VIA_AUTOMATA is true, we want to use the LTL engine\n\t\t\t// whenever possible\n\t\t\tuseSimplePathAlgo = false;\n\t\t}\n\n\t\tif (useSimplePathAlgo) {\n\t\t\treturn checkProbPathFormulaSimple(model, expr, minMax, statesOfInterest);\n\t\t} else {\n\t\t\t// Some model checkers will behave differently for cosafe vs full LTL\n\t\t\tif (Expression.isCoSafeLTLSyntactic(expr, true)) {\n\t\t\t\treturn checkProbPathFormulaCosafeLTL(model, expr, false, minMax, statesOfInterest);\n\t\t\t} else {\n\t\t\t\treturn checkProbPathFormulaLTL(model, expr, false, minMax, statesOfInterest);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Compute probabilities for a simple, non-LTL path operator.\n\t */\n\tprotected StateValues checkProbPathFormulaSimple(Model<?> model, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tboolean negated = false;\n\t\tStateValues probs = null;\n\n\t\texpr = Expression.convertSimplePathFormulaToCanonicalForm(expr);\n\n\t\t// Negation\n\t\tif (expr instanceof ExpressionUnaryOp &&\n\t\t    ((ExpressionUnaryOp)expr).getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\tnegated = true;\n\t\t\tminMax = minMax.negate();\n\t\t\texpr = ((ExpressionUnaryOp)expr).getOperand();\n\t\t}\n\n\t\tif (expr instanceof ExpressionTemporal) {\n \t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\n\t\t\t// Next\n\t\t\tif (exprTemp.getOperator() == ExpressionTemporal.P_X) {\n\t\t\t\tprobs = checkProbNext(model, exprTemp, minMax, statesOfInterest);\n\t\t\t}\n\t\t\t// Until\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\t\tprobs = checkProbBoundedUntil(model, exprTemp, minMax, statesOfInterest);\n\t\t\t\t} else {\n\t\t\t\t\tprobs = checkProbUntil(model, exprTemp, minMax, statesOfInterest);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (probs == null)\n\t\t\tthrow new PrismException(\"Unrecognised path operator in P operator\");\n\n\t\tif (negated) {\n\t\t\t// Subtract from 1 for negation\n\t\t\tprobs.applyFunction(TypeDouble.getInstance(), v -> 1.0 - (double) v);\n\t\t}\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute probabilities for a next operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkProbNext(Model<?> model, ExpressionTemporal expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Model check the operand for all states\n\t\tBitSet target = checkExpression(model, expr.getOperand2(), null).getBitSet();\n\n\t\t// Compute/return the probabilities\n\t\tModelCheckerResult res = null;\n\t\tswitch (model.getModelType()) {\n\t\tcase CTMC:\n\t\t\tres = ((CTMCModelChecker) this).computeNextProbs((CTMC<Double>) model, target);\n\t\t\tbreak;\n\t\tcase DTMC:\n\t\t\tres = ((DTMCModelChecker) this).computeNextProbs((DTMC<Double>) model, target);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tres = ((MDPModelChecker) this).computeNextProbs((MDP<Double>) model, target, minMax.isMin());\n\t\t\tbreak;\n\t\tcase STPG:\n\t\t\tres = ((STPGModelChecker) this).computeNextProbs((STPG<Double>) model, target, minMax.isMin1(), minMax.isMin2());\n\t\t\tbreak;\n\t\tcase IDTMC:\n\t\tcase UDTMC:\n\t\t\tres = ((UDTMCModelChecker) this).computeNextProbs((UDTMC<Double>) model, target, minMax);\n\t\t\tbreak;\n\t\tcase IMDP:\n\t\tcase UMDP:\n\t\t\tres = ((UMDPModelChecker) this).computeNextProbs((UMDP<Double>) model, target, minMax);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + expr + \" for \" + model.getModelType() + \"s\");\n\t\t}\n\t\tresult.setStrategy(res.strat);\n\t\treturn StateValues.createFromArrayResult(res, model);\n\t}\n\n\t/**\n\t * Compute probabilities for a bounded until operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkProbBoundedUntil(Model<?> model, ExpressionTemporal expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// This method just handles discrete time\n\t\t// Continuous-time model checkers will override this method\n\n\t\t// Get info from bounded until\n\t\tInteger lowerBound;\n\t\tIntegerBound bounds;\n\t\tint i;\n\n\t\t// get and check bounds information\n\t\tbounds = IntegerBound.fromExpressionTemporal(expr, constantValues, true);\n\n\t\t// Model check operands for all states\n\t\tBitSet remain = checkExpression(model, expr.getOperand1(), null).getBitSet();\n\t\tBitSet target = checkExpression(model, expr.getOperand2(), null).getBitSet();\n\n\t\tif (bounds.hasLowerBound()) {\n\t\t\tlowerBound = bounds.getLowestInteger();\n\t\t} else {\n\t\t\tlowerBound = 0;\n\t\t}\n\n\t\tInteger windowSize = null;  // unbounded\n\n\t\tif (bounds.hasUpperBound()) {\n\t\t\twindowSize = bounds.getHighestInteger() - lowerBound;\n\t\t}\n\n\t\t// compute probabilities for Until<=windowSize\n\t\tStateValues sv = null;\n\n\t\tif (windowSize == null) {\n\t\t\t// unbounded\n\t\t\tModelCheckerResult res = null;\n\t\t\tswitch (model.getModelType()) {\n\t\t\tcase DTMC:\n\t\t\t\tres = ((DTMCModelChecker) this).computeUntilProbs((DTMC<Double>) model, remain, target);\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\t\tres = ((MDPModelChecker) this).computeUntilProbs((MDP<Double>) model, remain, target, minMax.isMin());\n\t\t\t\tbreak;\n\t\t\tcase STPG:\n\t\t\t\tres = ((STPGModelChecker) this).computeUntilProbs((STPG<Double>) model, remain, target, minMax.isMin1(), minMax.isMin2());\n\t\t\t\tbreak;\n\t\t\tcase IDTMC:\n\t\t\tcase UDTMC:\n\t\t\t\tres = ((UDTMCModelChecker) this).computeUntilProbs((UDTMC<Double>) model, remain, target, minMax);\n\t\t\t\tbreak;\n\t\t\tcase IMDP:\n\t\t\tcase UMDP:\n\t\t\t\tres = ((UMDPModelChecker) this).computeUntilProbs((UMDP<Double>) model, remain, target, minMax);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Cannot model check \" + expr + \" for \" + model.getModelType() + \"s\");\n\t\t\t}\n\t\t\tresult.setStrategy(res.strat);\n\t\t\tsv = StateValues.createFromArrayResult(res, model);\n\t\t} else if (windowSize == 0) {\n\t\t\t// A trivial case: windowSize=0 (prob is 1 in target states, 0 otherwise)\n\t\t\tsv = StateValues.createFromBitSetAsDoubles(target, model);\n\t\t} else {\n\t\t\t// Otherwise: numerical solution\n\t\t\tModelCheckerResult res = null;\n\n\t\t\tswitch (model.getModelType()) {\n\t\t\tcase DTMC:\n\t\t\t\tres = ((DTMCModelChecker) this).computeBoundedUntilProbs((DTMC<Double>) model, remain, target, windowSize);\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\t\tres = ((MDPModelChecker) this).computeBoundedUntilProbs((MDP<Double>) model, remain, target, windowSize, minMax.isMin());\n\t\t\t\tbreak;\n\t\t\tcase STPG:\n\t\t\t\tres = ((STPGModelChecker) this).computeBoundedUntilProbs((STPG<Double>) model, remain, target, windowSize, minMax.isMin1(), minMax.isMin2());\n\t\t\t\tbreak;\n\t\t\tcase IDTMC:\n\t\t\tcase UDTMC:\n\t\t\t\tres = ((UDTMCModelChecker) this).computeBoundedUntilProbs((UDTMC<Double>) model, remain, target, windowSize, minMax);\n\t\t\t\tbreak;\n\t\t\tcase IMDP:\n\t\t\tcase UMDP:\n\t\t\t\tres = ((UMDPModelChecker) this).computeBoundedUntilProbs((UMDP<Double>) model, remain, target, windowSize, minMax);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + expr + \" for \" + model.getModelType() + \"s\");\n\t\t\t}\n\t\t\tresult.setStrategy(res.strat);\n\t\t\tsv = StateValues.createFromArrayResult(res, model);\n\t\t}\n\n\t\t// perform lowerBound restricted next-step computations to\n\t\t// deal with lower bound.\n\t\tif (lowerBound > 0) {\n\t\t\tdouble[] probs = sv.getDoubleArray();\n\n\t\t\tfor (i = 0; i < lowerBound; i++) {\n\t\t\t\tswitch (model.getModelType()) {\n\t\t\t\tcase DTMC:\n\t\t\t\t\tprobs = ((DTMCModelChecker) this).computeRestrictedNext((DTMC<Double>) model, remain, probs);\n\t\t\t\t\tbreak;\n\t\t\t\tcase MDP:\n\t\t\t\t\tprobs = ((MDPModelChecker) this).computeRestrictedNext((MDP<Double>) model, remain, probs, minMax.isMin());\n\t\t\t\t\tbreak;\n\t\t\t\tcase STPG:\n\t\t\t\t\t// TODO (JK): Figure out if we can handle lower bounds for STPG in the same way\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Lower bounds not yet supported for STPGModelChecker\");\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + expr + \" for \" + model.getModelType() + \"s\");\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tsv = StateValues.createFromDoubleArray(probs, model);\n\t\t\tsv.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\t}\n\n\t\treturn sv;\n\t}\n\n\t/**\n\t * Compute probabilities for an (unbounded) until operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkProbUntil(Model<?> model, ExpressionTemporal expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Model check operands for all states\n\t\tBitSet remain = checkExpression(model, expr.getOperand1(), null).getBitSet();\n\t\tBitSet target = checkExpression(model, expr.getOperand2(), null).getBitSet();\n\n\t\t// Compute/return the probabilities\n\t\tModelCheckerResult res = null;\n\t\tswitch (model.getModelType()) {\n\t\tcase CTMC:\n\t\t\tres = ((CTMCModelChecker) this).computeUntilProbs((CTMC<Double>) model, remain, target);\n\t\t\tbreak;\n\t\tcase DTMC:\n\t\t\tres = ((DTMCModelChecker) this).computeUntilProbs((DTMC<Double>) model, remain, target);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tres = ((MDPModelChecker) this).computeUntilProbs((MDP<Double>) model, remain, target, minMax.isMin());\n\t\t\tbreak;\n\t\tcase POMDP:\n\t\t\tres = ((POMDPModelChecker) this).computeReachProbs((POMDP<Double>) model, remain, target, minMax.isMin(), statesOfInterest);\n\t\t\tbreak;\n\t\tcase STPG:\n\t\t\tres = ((STPGModelChecker) this).computeUntilProbs((STPG<Double>) model, remain, target, minMax.isMin1(), minMax.isMin2());\n\t\t\tbreak;\n\t\tcase IDTMC:\n\t\tcase UDTMC:\n\t\t\tres = ((UDTMCModelChecker) this).computeUntilProbs((UDTMC<Double>) model, remain, target, minMax);\n\t\t\tbreak;\n\t\tcase IMDP:\n\t\tcase UMDP:\n\t\t\tres = ((UMDPModelChecker) this).computeUntilProbs((UMDP<Double>) model, remain, target, minMax);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + expr + \" for \" + model.getModelType() + \"s\");\n\t\t}\n\t\tresult.setStrategy(res.strat);\n\t\treturn StateValues.createFromArrayResult(res, model);\n\t}\n\n\t/**\n\t * Compute probabilities for an LTL path formula\n\t */\n\tprotected StateValues checkProbPathFormulaLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// To be overridden by subclasses\n\t\tthrow new PrismNotSupportedException(\"Computation not implemented yet\");\n\t}\n\n\t/**\n\t * Compute probabilities for a co-safe LTL path formula\n\t */\n\tprotected StateValues checkProbPathFormulaCosafeLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Just treat as an arbitrary LTL formula by default\n\t\treturn checkProbPathFormulaLTL(model, expr, qual, minMax, statesOfInterest);\n\t}\n\n\t/**\n\t * Model check an R operator expression and return the values for all states.\n\t */\n\tprotected StateValues checkExpressionReward(Model<?> model, ExpressionReward expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Use the default semantics for a standalone R operator\n\t\t// (i.e. quantification over all strategies, and no game-coalition info)\n\t\treturn checkExpressionReward(model, expr, true, null, statesOfInterest);\n\t}\n\t\n\t/**\n\t * Model check an R operator expression and return the values for all states.\n\t */\n\tprotected StateValues checkExpressionReward(Model<?> model, ExpressionReward expr, boolean forAll, Coalition coalition, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Get info from R operator\n\t\tOpRelOpBound opInfo = expr.getRelopBoundInfo(constantValues);\n\t\tMinMax minMax = opInfo.getMinMax(model.getModelType(), forAll);\n\n\t\t// Build rewards\n\t\tint r = expr.getRewardStructIndexByIndexObject(rewardGen, constantValues);\n\t\tmainLog.println(\"Building reward structure...\");\n\t\tRewards<?> rewards = Expression.usesInstantaneousReward(expr.getExpression()) ? constructRewards(model, r) : constructExpectedRewards(model, r);\n\n\t\t// Compute rewards\n\t\tStateValues rews = checkRewardFormula(model, rewards, expr.getExpression(), minMax, statesOfInterest);\n\n\t\t// Print out rewards\n\t\tif (getVerbosity() > 5) {\n\t\t\tmainLog.print(\"\\nRewards (non-zero only) for all states:\\n\");\n\t\t\trews.print(mainLog);\n\t\t}\n\n\t\t// For =? properties, just return values; otherwise compare against bound\n\t\tif (!opInfo.isNumeric()) {\n\t\t\trews.applyPredicate(v -> opInfo.apply((double) v, rews.getAccuracy()));\n\t\t}\n\t\treturn rews;\n\t}\n\n\t/**\n\t * Compute rewards for the contents of an R operator.\n\t */\n\tprotected StateValues checkRewardFormula(Model<?> model, Rewards<?> modelRewards, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tStateValues rewards = null;\n\n\t\tif (expr.getType() instanceof TypePathDouble) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\tswitch (exprTemp.getOperator()) {\n\t\t\tcase ExpressionTemporal.R_I:\n\t\t\t\trewards = checkRewardInstantaneous(model, modelRewards, exprTemp, minMax, statesOfInterest);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionTemporal.R_C:\n\t\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\t\trewards = checkRewardCumulative(model, modelRewards, exprTemp, minMax);\n\t\t\t\t} else {\n\t\t\t\t\trewards = checkRewardTotal(model, modelRewards, exprTemp, minMax);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ExpressionTemporal.R_S:\n\t\t\t\trewards = checkRewardSteady(model, modelRewards);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not yet handle the \" + exprTemp.getOperatorSymbol() + \" reward operator\");\n\t\t\t}\n\t\t} else if (expr.getType() instanceof TypePathBool || expr.getType() instanceof TypeBool) {\n\t\t\trewards = checkRewardPathFormula(model, modelRewards, expr, minMax, statesOfInterest);\n\t\t}\n\n\t\tif (rewards == null)\n\t\t\tthrow new PrismException(\"Unrecognised operator in R operator\");\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute rewards for an instantaneous reward operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardInstantaneous(Model<?> model, Rewards<?> modelRewards, ExpressionTemporal expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Compute/return the rewards\n\t\tModelCheckerResult res = null;\n\t\tswitch (model.getModelType()) {\n\t\tcase DTMC: {\n\t\t\tint k = expr.getUpperBound().evaluateInt(constantValues);\n\t\t\tres = ((DTMCModelChecker) this).computeInstantaneousRewards((DTMC<Double>) model, (MCRewards<Double>) modelRewards, k, statesOfInterest);\n\t\t\tbreak;\n\t\t}\n\t\tcase CTMC: {\n\t\t\tdouble t = expr.getUpperBound().evaluateDouble(constantValues);\n\t\t\tres = ((CTMCModelChecker) this).computeInstantaneousRewards((CTMC<Double>) model, (MCRewards<Double>) modelRewards, t);\n\t\t\tbreak;\n\t\t}\n\t\tcase MDP: {\n\t\t\tint k = expr.getUpperBound().evaluateInt(constantValues);\n\t\t\tres = ((MDPModelChecker) this).computeInstantaneousRewards((MDP<Double>) model, (MDPRewards<Double>) modelRewards, k, minMax.isMin());\n\t\t\tbreak;\n\t\t}\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not yet handle the \" + expr.getOperatorSymbol() + \" reward operator for \" + model.getModelType()\n\t\t\t\t\t+ \"s\");\n\t\t}\n\t\tresult.setStrategy(res.strat);\n\t\treturn StateValues.createFromArrayResult(res, model);\n\t}\n\n\t/**\n\t * Compute rewards for a cumulative reward operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardCumulative(Model<?> model, Rewards<?> modelRewards, ExpressionTemporal expr, MinMax minMax) throws PrismException\n\t{\n\t\tint timeInt = -1;\n\t\tdouble timeDouble = -1;\n\n\t\t// Check that there is an upper time bound\n\t\tif (expr.getUpperBound() == null) {\n\t\t\tthrow new PrismNotSupportedException(\"This is not a cumulative reward operator\");\n\t\t}\n\n\t\t// Get time bound\n\t\tif (model.getModelType().continuousTime()) {\n\t\t\ttimeDouble = expr.getUpperBound().evaluateDouble(constantValues);\n\t\t\tif (timeDouble < 0) {\n\t\t\t\tthrow new PrismException(\"Invalid time bound \" + timeDouble + \" in cumulative reward formula\");\n\t\t\t}\n\t\t} else {\n\t\t\ttimeInt = expr.getUpperBound().evaluateInt(constantValues);\n\t\t\tif (timeInt < 0) {\n\t\t\t\tthrow new PrismException(\"Invalid time bound \" + timeInt + \" in cumulative reward formula\");\n\t\t\t}\n\t\t}\n\n\t\t// Compute/return the rewards\n\t\t// A trivial case: \"C<=0\" (prob is 1 in target states, 0 otherwise)\n\t\tif (timeInt == 0 || timeDouble == 0) {\n\t\t\tStateValues res = StateValues.createFromSingleValue(TypeDouble.getInstance(), 0.0, model);\n\t\t\tres.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t\treturn res;\n\t\t}\n\t\t// Otherwise: numerical solution\n\t\tModelCheckerResult res = null;\n\t\tswitch (model.getModelType()) {\n\t\tcase DTMC:\n\t\t\tres = ((DTMCModelChecker) this).computeCumulativeRewards((DTMC<Double>) model, (MCRewards<Double>) modelRewards, timeInt);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tres = ((CTMCModelChecker) this).computeCumulativeRewards((CTMC<Double>) model, (MCRewards<Double>) modelRewards, timeDouble);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tres = ((MDPModelChecker) this).computeCumulativeRewards((MDP<Double>) model, (MDPRewards<Double>) modelRewards, timeInt, minMax.isMin());\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not yet handle the \" + expr.getOperatorSymbol() + \" reward operator for \" + model.getModelType()\n\t\t\t\t\t+ \"s\");\n\t\t}\n\t\tresult.setStrategy(res.strat);\n\t\treturn StateValues.createFromArrayResult(res, model);\n\t}\n\n\t/**\n\t * Compute expected rewards for a total reward operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardTotal(Model<?> model, Rewards<?> modelRewards, ExpressionTemporal expr, MinMax minMax) throws PrismException\n\t{\n\t\t// Check that there is no upper time bound\n\t\tif (expr.getUpperBound() != null) {\n\t\t\tthrow new PrismException(\"This is not a total reward operator\");\n\t\t}\n\n\t\t// Compute/return the rewards\n\t\tModelCheckerResult res = null;\n\t\tswitch (model.getModelType()) {\n\t\tcase DTMC:\n\t\t\tres = ((DTMCModelChecker) this).computeTotalRewards((DTMC<Double>) model, (MCRewards<Double>) modelRewards);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tres = ((CTMCModelChecker) this).computeTotalRewards((CTMC<Double>) model, (MCRewards<Double>) modelRewards);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tres = ((MDPModelChecker) this).computeTotalRewards((MDP<Double>) model, (MDPRewards<Double>) modelRewards, minMax.isMin());\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not yet handle the \" + expr.getOperatorSymbol() + \" reward operator for \" + model.getModelType()\n\t\t\t\t\t+ \"s\");\n\t\t}\n\t\tresult.setStrategy(res.strat);\n\t\treturn StateValues.createFromArrayResult(res, model);\n\t}\n\n\t/**\n\t * Compute expected rewards for a steady-state reward operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardSteady(Model<?> model, Rewards<?> modelRewards) throws PrismException\n\t{\n\t\t// Compute/return the rewards\n\t\tModelCheckerResult res = null;\n\t\tswitch (model.getModelType()) {\n\t\tcase DTMC:\n\t\t\tres = ((DTMCModelChecker) this).computeSteadyStateRewards((DTMC<Double>) model, (MCRewards<Double>) modelRewards);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tres = ((CTMCModelChecker) this).computeSteadyStateRewards((CTMC<Double>) model, (MCRewards<Double>) modelRewards);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not yet handle the steady-state reward operator for \" + model.getModelType() + \"s\");\n\t\t}\n\t\tresult.setStrategy(res.strat);\n\t\treturn StateValues.createFromArrayResult(res, model);\n\t}\n\n\t/**\n\t * Compute rewards for a path formula in a reward operator.\n\t */\n\tprotected StateValues checkRewardPathFormula(Model<?> model, Rewards<?> modelRewards, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tif (Expression.isReach(expr)) {\n\t\t\treturn checkRewardReach(model, modelRewards, (ExpressionTemporal) expr, minMax, statesOfInterest);\n\t\t}\n\t\telse if (Expression.isCoSafeLTLSyntactic(expr, true)) {\n\t\t\treturn checkRewardCoSafeLTL(model, modelRewards, expr, minMax, statesOfInterest);\n\t\t}\n\t\tthrow new PrismException(\"R operator contains a path formula that is not syntactically co-safe: \" + expr);\n\t}\n\t\n\t/**\n\t * Compute rewards for a reachability reward operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardReach(Model<?> model, Rewards<?> modelRewards, ExpressionTemporal expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// No time bounds allowed\n\t\tif (expr.hasBounds()) {\n\t\t\tthrow new PrismNotSupportedException(\"R operator cannot contain a bounded F operator: \" + expr);\n\t\t}\n\t\t\n\t\t// Model check the operand for all states\n\t\tBitSet target = checkExpression(model, expr.getOperand2(), null).getBitSet();\n\n\t\t// Compute/return the rewards\n\t\tModelCheckerResult res = null;\n\t\tswitch (model.getModelType()) {\n\t\tcase DTMC:\n\t\t\tres = ((DTMCModelChecker) this).computeReachRewards((DTMC<Double>) model, (MCRewards<Double>) modelRewards, target);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tres = ((CTMCModelChecker) this).computeReachRewards((CTMC<Double>) model, (MCRewards<Double>) modelRewards, target);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tres = ((MDPModelChecker) this).computeReachRewards((MDP<Double>) model, (MDPRewards<Double>) modelRewards, target, minMax.isMin());\n\t\t\tbreak;\n\t\tcase POMDP:\n\t\t\tres = ((POMDPModelChecker) this).computeReachRewards((POMDP<Double>) model, (MDPRewards<Double>) modelRewards, target, minMax.isMin(), statesOfInterest);\n\t\t\tbreak;\n\t\tcase STPG:\n\t\t\tres = ((STPGModelChecker) this).computeReachRewards((STPG<Double>) model, (STPGRewards<Double>) modelRewards, target, minMax.isMin1(), minMax.isMin2());\n\t\t\tbreak;\n\t\tcase IDTMC:\n\t\tcase UDTMC:\n\t\t\tres = ((UDTMCModelChecker) this).computeReachRewards((UDTMC<Double>) model, (MCRewards<Double>) modelRewards, target, minMax);\n\t\t\tbreak;\n\t\tcase IMDP:\n\t\tcase UMDP:\n\t\t\tres = ((UMDPModelChecker) this).computeReachRewards((UMDP<Double>) model, (MDPRewards<Double>) modelRewards, target, minMax);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not yet handle the \" + expr.getOperatorSymbol() + \" reward operator for \" + model.getModelType()\n\t\t\t\t\t+ \"s\");\n\t\t}\n\t\tresult.setStrategy(res.strat);\n\t\treturn StateValues.createFromArrayResult(res, model);\n\t}\n\n\t/**\n\t * Compute rewards for a co-safe LTL reward operator.\n\t */\n\tprotected StateValues checkRewardCoSafeLTL(Model<?> model, Rewards<?> modelRewards, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// To be overridden by subclasses\n\t\tthrow new PrismException(\"Computation not implemented yet\");\n\t}\n\n\t/**\n\t * Model check an S operator expression and return the values for all states.\n\t */\n\tprotected StateValues checkExpressionSteadyState(Model<?> model, ExpressionSS expr) throws PrismException\n\t{\n\t\t// Get info from S operator\n\t\tOpRelOpBound opInfo = expr.getRelopBoundInfo(constantValues);\n\t\tMinMax minMax = opInfo.getMinMax(model.getModelType());\n\n\t\t// Compute probabilities\n\t\tStateValues probs = checkSteadyStateFormula(model, expr.getExpression(), minMax);\n\n\t\t// Print out probabilities\n\t\tif (getVerbosity() > 5) {\n\t\t\tmainLog.print(\"\\nProbabilities (non-zero only) for all states:\\n\");\n\t\t\tprobs.print(mainLog);\n\t\t}\n\n\t\t// For =? properties, just return values; otherwise compare against bound\n\t\tif (!opInfo.isNumeric()) {\n\t\t\tprobs.applyPredicate(v -> opInfo.apply((double) v, probs.getAccuracy()));\n\t\t}\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute steady-state probabilities for an S operator.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkSteadyStateFormula(Model<?> model, Expression expr, MinMax minMax) throws PrismException\n\t{\n\t\t// Model check operand for all states\n\t\tBitSet b = checkExpression(model, expr, null).getBitSet();\n\n\t\t// Compute/return the probabilities\n\t\tswitch (model.getModelType()) {\n\t\tcase DTMC:\n\t\t\treturn ((DTMCModelChecker) this).computeSteadyStateFormula((DTMC<Double>) model, b);\n\t\tcase CTMC:\n\t\t\treturn ((CTMCModelChecker) this).computeSteadyStateFormula((CTMC<Double>) model, b);\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not yet handle the S operator for \" + model.getModelType() + \"s\");\n\t\t}\n\t}\n\n\t// Utility methods for probability distributions\n\n\t/**\n\t * Generate a probability distribution, stored as a StateValues object, from a file.\n\t * If {@code distFile} is null, so is the return value.\n\t */\n\tpublic StateValues readDistributionFromFile(File distFile, Model<?> model) throws PrismException\n\t{\n\t\tStateValues dist = null;\n\n\t\tif (distFile != null) {\n\t\t\tmainLog.println(\"\\nImporting probability distribution from file \\\"\" + distFile + \"\\\"...\");\n\t\t\tdist = StateValues.createFromFile(TypeDouble.getInstance(), distFile, model);\n\t\t}\n\n\t\treturn dist;\n\t}\n\n\t/**\n\t * Build a probability distribution, stored as a StateValues object,\n\t * from the initial states info of the current model: either probability 1 for\n\t * the (single) initial state or equiprobable over multiple initial states.\n\t */\n\tpublic StateValues buildInitialDistribution(Model<?> model) throws PrismException\n\t{\n\t\tint numInitStates = model.getNumInitialStates();\n\t\tif (numInitStates == 1) {\n\t\t\tint sInit = model.getFirstInitialState();\n\t\t\treturn StateValues.create(TypeDouble.getInstance(), s -> s == sInit ? 1.0 : 0.0, model);\n\t\t} else {\n\t\t\tdouble pInit = 1.0 / numInitStates;\n\t\t\treturn StateValues.create(TypeDouble.getInstance(), s -> model.isInitialState(s) ? pInit : 0.0, model);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/Product.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage explicit;\n\nimport java.util.BitSet;\n\nimport prism.PrismException;\n\n/**\n * Base class for the results of a product operation between a model and\n * an automaton. Provides infrastructure for converting information on the\n * states between the original model, the automaton and the product model.\n *\n * The mapping between product states and the constituent parts is\n * specified via the (abstract) functions getModelState() and getAutomatonState().\n *\n * @param <M> The type of the product model, e.g, DTMC, MDP, ...\n */\npublic abstract class Product<M extends Model<?>> implements ModelTransformation<M, M>\n{\n\tprotected M originalModel = null;\n\tprotected M productModel = null;\n\n\t/**\n\t * For the given productState index, return the corresponding\n\t * state index in the original model.\n\t */\n\tpublic abstract int getModelState(int productState);\n\n\t/**\n\t * For the given productState index, return the corresponding\n\t * state index in the automaton.\n\t */\n\tpublic abstract int getAutomatonState(int productState);\n\n\t/**\n\t * Return the number of states in the automaton.\n\t */\n\tpublic abstract int getAutomatonSize();\n\n\t/**\n\t * Constructor.\n \t * @param originalModel the original model\n\t */\n\tpublic Product(M originalModel)\n\t{\n\t\tthis.originalModel = originalModel;\n\t}\n\n\t/**\n\t * Constructor.\n \t * @param productModel the product model\n \t * @param originalModel the original model\n\t */\n\tpublic Product(M productModel, M originalModel)\n\t{\n\t\tthis.originalModel = originalModel;\n\t\tthis.productModel = productModel;\n\t}\n\n\t/**\n\t * Get the product model.\n\t */\n\tpublic M getProductModel()\n\t{\n\t\treturn productModel;\n\t}\n\n\t@Override\n\tpublic M getTransformedModel()\n\t{\n\t\treturn getProductModel();\n\t}\n\n\t@Override\n\tpublic M getOriginalModel()\n\t{\n\t\treturn originalModel;\n\t}\n\n\t/**\n\t * Lifts a BitSet over states in the automaton to a BitSet\n\t * over states in the product model: A bit is set in the\n\t * result for a product state if the bit is set in the parameter\n\t * for the corresponding automaton state.\n\t * @param automataStates a BitSet over states of the automaton for this product.\n\t */\n\tpublic BitSet liftFromAutomaton(BitSet automataStates)\n\t{\n\t\tBitSet result = new BitSet();\n\n\t\tfor (int productState = 0; productState < productModel.getNumStates(); productState++) {\n\t\t\tif (automataStates.get(getAutomatonState(productState))) {\n\t\t\t\tresult.set(productState, true);\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Lifts a BitSet over states in the original model to a BitSet\n\t * over states in the product model: A bit is set in the\n\t * result for a product state if the bit is set in the parameter\n\t * for the corresponding original model state.\n\t * @param modelStates a BitSet over states of the original model for this product.\n\t */\n\tpublic BitSet liftFromModel(BitSet modelStates)\n\t{\n\t\tBitSet result = new BitSet();\n\n\t\tfor (int productState = 0; productState < productModel.getNumStates(); productState++) {\n\t\t\tif (modelStates.get(getModelState(productState))) {\n\t\t\t\tresult.set(productState, true);\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Project state values from the product model back to the original model. This function\n\t * assumes that the product model has at most one initial state per state in the original\n\t * model. The value of this state is then projected to the corresponding state of the\n\t * original model.\n\t * @param sv the state values in the product model\n\t * @return the corresponding state values in the original model\n\t * @throws PrismException\n\t */\n\t@Override\n\tpublic StateValues projectToOriginalModel(final StateValues sv) throws PrismException\n\t{\n\t\treturn sv.projectToOriginalModel(this);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/QuantAbstractRefine.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.*;\nimport java.util.*;\n\nimport prism.*;\nimport explicit.ProbModelChecker.TermCrit;\nimport explicit.ProbModelChecker.ValIterDir;\n\n/**\n * Base class for implementing quantitative abstraction-refinement loop.\n * Subclasses need to implement the following abstract methods:\n * <ul>\n * <li> {@link #initialise}\n * <li> {@link #splitState}\n * <li> {@link #rebuildAbstraction}\n * </ul>\n * Various settings are available. In particular, model/property type should be set with:\n * <ul>\n * <li> {@link #setModelType}\n * <li> {@link #setPropertyType}\n * </ul>\n * See other setXXX methods for further configuration options.\n * <br><br>\n * The abstraction-refinement loop can then be started with {@link #abstractRefine}.\n */\npublic abstract class QuantAbstractRefine extends PrismComponent\n{\n\t// Model checker\n\tprotected ProbModelChecker mc;\n\t// Dummy model checker to store options\n\tprotected ProbModelChecker mcOptions;\n\n\t// Flags/settings\n\n\t// Verbosity level\n\tprotected int verbosity = 0;\n\t// Maximum number of refinement iterations\n\tprotected int maxRefinements = 1000;\n\t// Export abstractions to dot files at each refinement?\n\tprotected boolean exportDot = false;\n\t// Optimise by reusing numerical solution etc.\n\tprotected boolean optimise = true;\n\t// Refinement termination criteria\n\tprotected RefineTermCrit refineTermCrit = RefineTermCrit.ABSOLUTE;\n\t// Parameter for refinement termination criteria\n\tprotected double refineTermCritParam = 1e-6;\n\t// Use convergence from above for value iteration?\n\tprotected boolean above = false;\n\t// Abstraction-refinement settings\n\tprotected RefineStratWhere refineStratWhere = RefineStratWhere.ALL;\n\tprotected RefineStratHow refineStratHow = RefineStratHow.VAL;\n\n\t// Private flags/settings\n\tprotected boolean sanityChecks = false;\n\n\t// Enums for flags/settings\n\n\t// Property type\n\tpublic enum PropertyType {\n\t\tPROB_REACH, EXP_REACH, PROB_REACH_BOUNDED;\n\t};\n\n\t// Refinement termination criteria\n\tpublic enum RefineTermCrit {\n\t\tABSOLUTE, RELATIVE\n\t};\n\n\tpublic enum RefineStratWhere {\n\t\tALL, ALL_MAX, FIRST, FIRST_MAX, LAST, LAST_MAX\n\t};\n\n\tpublic enum RefineStratHow {\n\t\tALL, VAL\n\t};\n\n\t// Concrete model info\n\t/** Type of (concrete) model; default is MDP. */\n\tprotected ModelType modelType = ModelType.MDP;\n\t\n\t// Property info\n\t/** Property type; default is PROB_REACH */\n\tprotected PropertyType propertyType = PropertyType.PROB_REACH;\n\t/** For nondeterministic (concrete) models, compute min? (or max?) */\n\tprotected boolean min;\n\t/** Bound for when property is bounded reachability */\n\tprotected int reachBound = 0;\n\t\n\t// Abstract model info (updated by subclasses)\n\t/** Abstract model */\n\tprotected NondetModelSimple<Double> abstraction;\n\t/** BitSet of (abstract) target states for property to drive refinement */\n\tprotected BitSet target;\n\t\n\t// Stuff for refinement loop\n\tprotected ModelType abstractionType;\n\tprotected double[] lbSoln;\n\tprotected double[] ubSoln;\n\tprotected double[] lbLastSoln;\n\tprotected double[] ubLastSoln;\n\tprotected double lbInit;\n\tprotected double ubInit;\n\tprotected BitSet known;\n\tprotected List<Integer> refineStates;\n\tprotected boolean buildEmbeddedDtmc = false; // Construct DTMC from CTMC?\n\t// Timing info, etc.\n\tprotected double timeBuild;\n\tprotected double timeRebuild;\n\tprotected double timeCheck;\n\tprotected double timeCheckLb;\n\tprotected double timeCheckUb;\n\tprotected double timeCheckPre;\n\tprotected double timeCheckProb0;\n\tprotected double timeRefine;\n\tprotected double timeTotal;\n\tprotected int itersTotal;\n\tprotected int refinementNum;\n\n\t/**\n\t * Default constructor.\n\t */\n\tpublic QuantAbstractRefine(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\t// Create dummy model checker to store options\n\t\ttry {\n\t\t\tmcOptions = new ProbModelChecker(null);\n\t\t} catch (PrismException e) {\n\t\t\t// Won't happen\n\t\t}\n\t}\n\n\t/**\n\t * Provides access to the underlying model checker for the purpose of setting options. \n\t */\n\tpublic ProbModelChecker getModelChecker()\n\t{\n\t\treturn mcOptions;\n\t}\n\n\t/**\n\t * Print summary of current settings.\n\t */\n\tpublic void printSettings()\n\t{\n\t\tmainLog.print(\"\\nAR Settings:\");\n\t\tmainLog.print(\" modelType = \" + modelType);\n\t\tmainLog.print(\" propertyType = \" + propertyType);\n\t\tmainLog.print(\" reachBound = \" + reachBound);\n\t\tmainLog.print(\" verbosity = \" + verbosity);\n\t\tmainLog.print(\" maxRefinements = \" + maxRefinements);\n\t\tmainLog.print(\" exportDot = \" + exportDot);\n\t\tmainLog.print(\" optimise = \" + optimise);\n\t\tmainLog.print(\" refineTermCrit = \" + refineTermCrit);\n\t\tmainLog.print(\" refineTermCritParam = \" + refineTermCritParam);\n\t\tmainLog.print(\" above = \" + above);\n\t\tmainLog.print(\" refineStratWhere = \" + refineStratWhere);\n\t\tmainLog.print(\" refineStratHow = \" + refineStratHow);\n\t\tmainLog.println();\n\t\tmainLog.print(\"\\nMC Settings: \");\n\t\tmcOptions.printSettings();\n\t\tmainLog.println();\n\t}\n\n\t// Set methods for flags/settings, etc.\n\n\tpublic void setModelType(ModelType modelType)\n\t{\n\t\tthis.modelType = modelType;\n\t}\n\n\tpublic void setPropertyType(PropertyType propertyType)\n\t{\n\t\tthis.propertyType = propertyType;\n\t}\n\n\tpublic void setReachBound(int reachBound)\n\t{\n\t\tthis.reachBound = reachBound;\n\t}\n\n\tpublic void setVerbosity(int verbosity)\n\t{\n\t\tthis.verbosity = verbosity;\n\t\t// Store this in model checker options too\n\t\tif (mcOptions != null)\n\t\t\tmcOptions.setVerbosity(verbosity);\n\t}\n\n\tpublic void setMaxRefinements(int maxRefinements)\n\t{\n\t\tthis.maxRefinements = maxRefinements;\n\t}\n\n\tpublic void setExportDot(boolean exportDot)\n\t{\n\t\tthis.exportDot = exportDot;\n\t}\n\n\tpublic void setOptimise(boolean optimise)\n\t{\n\t\tthis.optimise = optimise;\n\t}\n\n\tpublic void setRefineTermCrit(RefineTermCrit refineTermCrit)\n\t{\n\t\tthis.refineTermCrit = refineTermCrit;\n\t}\n\n\tpublic void setRefineTermCritParam(double refineTermCritParam)\n\t{\n\t\tthis.refineTermCritParam = refineTermCritParam;\n\t}\n\n\tpublic void setAbove(boolean above)\n\t{\n\t\tthis.above = above;\n\t}\n\n\tpublic void setRefineStratWhere(RefineStratWhere refineStratWhere)\n\t{\n\t\tthis.refineStratWhere = refineStratWhere;\n\t}\n\n\tpublic void setRefineStratHow(RefineStratHow refineStratHow)\n\t{\n\t\tthis.refineStratHow = refineStratHow;\n\t}\n\n\t/**\n\t * Convenience method: parse an option specified as a (command-line style) string\n\t */\n\tpublic void parseOption(String opt) throws PrismException\n\t{\n\t\tint j;\n\t\tString optVal;\n\n\t\t// Ignore empty option\n\t\tif (\"\".equals(opt))\n\t\t\treturn;\n\n\t\t// Break switch up into parts if contains =\n\t\tif ((j = opt.indexOf('=')) != -1) {\n\t\t\toptVal = opt.substring(j + 1);\n\t\t\topt = opt.substring(0, j);\n\t\t} else {\n\t\t\toptVal = null;\n\t\t}\n\t\t// Parse\n\t\tif (opt.equals(\"verbose\") || opt.equals(\"v\")) {\n\t\t\ttry {\n\t\t\t\tsetVerbosity((optVal == null) ? 10 : Integer.parseInt(optVal));\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Invalid value \\\"\" + optVal + \"\\\" for abstraction-refinement setting \\\"\" + opt + \"\\\"\");\n\t\t\t}\n\t\t} else if (opt.matches(\"refine\")) {\n\t\t\tif (optVal != null) {\n\t\t\t\tString ss[] = optVal.split(\",\");\n\t\t\t\tif (ss.length > 0) {\n\t\t\t\t\tif (ss[0].equals(\"all\"))\n\t\t\t\t\t\tsetRefineStratWhere(RefineStratWhere.ALL);\n\t\t\t\t\telse if (ss[0].equals(\"allmax\"))\n\t\t\t\t\t\tsetRefineStratWhere(RefineStratWhere.ALL_MAX);\n\t\t\t\t\telse if (ss[0].equals(\"first\"))\n\t\t\t\t\t\tsetRefineStratWhere(RefineStratWhere.FIRST);\n\t\t\t\t\telse if (ss[0].equals(\"firstmax\"))\n\t\t\t\t\t\tsetRefineStratWhere(RefineStratWhere.FIRST_MAX);\n\t\t\t\t\telse if (ss[0].equals(\"last\"))\n\t\t\t\t\t\tsetRefineStratWhere(RefineStratWhere.LAST);\n\t\t\t\t\telse if (ss[0].equals(\"lastmax\"))\n\t\t\t\t\t\tsetRefineStratWhere(RefineStratWhere.LAST_MAX);\n\t\t\t\t\telse\n\t\t\t\t\t\tthrow new PrismException(\"Unknown refinement option \\\"\" + ss[0] + \"\\\"\");\n\t\t\t\t}\n\t\t\t\tif (ss.length > 1) {\n\t\t\t\t\tif (ss[1].equals(\"all\"))\n\t\t\t\t\t\tsetRefineStratHow(RefineStratHow.ALL);\n\t\t\t\t\telse if (ss[1].equals(\"val\"))\n\t\t\t\t\t\tsetRefineStratHow(RefineStratHow.VAL);\n\t\t\t\t\telse\n\t\t\t\t\t\tthrow new PrismException(\"Unknown refinement option \\\"\" + ss[1] + \"\\\"\");\n\t\t\t\t}\n\t\t\t}\n\t\t} else if (opt.equals(\"epsilonref\") || opt.equals(\"eref\")) {\n\t\t\tif (optVal != null) {\n\t\t\t\ttry {\n\t\t\t\t\tsetRefineTermCritParam(Double.parseDouble(optVal));\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value \\\"\" + optVal + \"\\\" for abstraction-refinement setting \\\"\" + opt + \"\\\"\");\n\t\t\t\t}\n\t\t\t}\n\t\t} else if (opt.equals(\"nopre\")) {\n\t\t\tgetModelChecker().setPrecomp(false);\n\t\t} else if (opt.equals(\"pre\")) {\n\t\t\tgetModelChecker().setPrecomp(true);\n\t\t} else if (opt.equals(\"noprob0\")) {\n\t\t\tgetModelChecker().setProb0(false);\n\t\t} else if (opt.equals(\"noprob1\")) {\n\t\t\tgetModelChecker().setProb1(false);\n\t\t} else if (opt.equals(\"epsilon\")) {\n\t\t\tif (optVal != null) {\n\t\t\t\ttry {\n\t\t\t\t\tgetModelChecker().setTermCritParam(Double.parseDouble(optVal));\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value \\\"\" + optVal + \"\\\" for abstraction-refinement setting \\\"\" + opt + \"\\\"\");\n\t\t\t\t}\n\t\t\t}\n\t\t} else if (opt.equals(\"maxrefs\")) {\n\t\t\tif (optVal != null) {\n\t\t\t\ttry {\n\t\t\t\t\tsetMaxRefinements(Integer.parseInt(optVal));\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value \\\"\" + optVal + \"\\\" for abstraction-refinement setting \\\"\" + opt + \"\\\"\");\n\t\t\t\t}\n\t\t\t}\n\t\t} else if (opt.equals(\"opt\")) {\n\t\t\tsetOptimise(true);\n\t\t} else if (opt.equals(\"noopt\")) {\n\t\t\tsetOptimise(false);\n\t\t} else if (opt.equals(\"exportdot\")) {\n\t\t\tsetExportDot(true);\n\t\t} else if (opt.equals(\"above\")) {\n\t\t\tsetAbove(true);\n\t\t} else if (opt.equals(\"below\")) {\n\t\t\tsetAbove(false);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Unknown switch \" + opt);\n\t\t}\n\t}\n\n\t/**\n\t * Convenience method: parse multiple options specified as a (command-line style) string\n\t */\n\tpublic void parseOptions(String[] opts) throws PrismException\n\t{\n\t\tif (opts.length > 0)\n\t\t\tfor (String opt : opts)\n\t\t\t\tparseOption(opt);\n\t}\n\n\t/**\n\t * Print bulleted list of options to a log (used by -help switch). \n\t */\n\tpublic static void printOptions(PrismLog mainLog)\n\t{\n\t\tmainLog.println(\" * verbose=<n> (or v=<n>) - verbosity level\");\n\t\tmainLog.println(\" * refine=<where,how> - which states to refine and how\");\n\t\tmainLog.println(\"     <where> = all, allmax, first, firstmax, last, lastmax\");\n\t\tmainLog.println(\"     <how> = all, val\");\n\t\tmainLog.println(\" * epsilonref=<x> (or eref=<x>) - epsilon for refinement\");\n\t\tmainLog.println(\" * nopre  - disable precomputation\");\n\t\tmainLog.println(\" * pre - use precomputation\");\n\t\tmainLog.println(\" * noprob0 - disable prob0 precomputation\");\n\t\tmainLog.println(\" * noprob1 - disable prob1 precomputation\");\n\t\tmainLog.println(\" * epsilon=<x> - epsilon for numerical convergence\");\n\t\tmainLog.println(\" * maxref=<n> - maximum number of refinements\");\n\t\tmainLog.println(\" * opt - use optimisations\");\n\t\tmainLog.println(\" * noopt - disable optimisations\");\n\t\tmainLog.println(\" * exportdot - export dot files for each refinement\");\n\t\tmainLog.println(\" * above - start numerical soluton from above\");\n\t\tmainLog.println(\" * below - start numerical soluton from below\");\n\t}\n\t\n\t// Abstract methods that must be implemented for abstraction-refinement loop\n\n\t/**\n\t * Initialise: Build initial abstraction and set of target abstract states\n\t * (storing in {@link #abstraction} and {@link #target}, respectively).\n\t * Note: {@link #abstraction} must respect initial states,\n\t * i.e. any abstract state contains either all/no initial states. \n\t */\n\tprotected abstract void initialise() throws PrismException;\n\n\t/**\n\t * Split an abstract state for refinement, based on sets of nondeterministic choices.\n\t * This function should add new states to the abstract model ({@link #abstraction}),\n\t * update its initial states and update the {@link #target}. Any information stored locally\n\t * about abstract state space etc. should also be updated at this point.\n\t * <br><br>\n\t * One of the new states should replace the state being split;\n\t * the rest should be appended to the list of abstract states.\n\t * Abstract states that need to be rebuilt (either because they are new, or because\n\t * one of their successors has been split) can either be rebuilt at this point,\n\t * or left until later. If the former, the state should be added to the list {@code rebuiltStates};\n\t * if the latter, it should be added to {@code rebuildStates}.\n\t * The total number of new states should be returned.\n\t * <br><br>\n\t * Notes:\n\t * <ul>\n\t * <li> The union of all the sets in {@link #choiceLists} may not cover all choices in the state to be split.\n\t *      This is because there may be more efficient ways to compute the remainder of the abstract state.\n\t *      If not, use the utility function {@link #addRemainderIntoChoiceLists}.\n\t * </ul>\n\t * @param splitState State to split.\n\t * @param choiceLists Lists of nondeterministic choices defining split.\n\t * @param rebuildStates States that need rebuilding as a result should be added here.\n\t * @return Number of states into which split (i.e. 1 denotes split failed).\n\t */\n\tprotected abstract int splitState(int splitState, List<List<Integer>> choiceLists, Set<Integer> rebuiltStates,\n\t\t\tSet<Integer> rebuildStates) throws PrismException;\n\n\t/**\n\t * Rebuild the abstraction after a refinement.\n\t * @param rebuildStates States that need rebuilding.\n\t */\n\tprotected abstract void rebuildAbstraction(Set<Integer> rebuildStates) throws PrismException;\n\n\t// Remaining implementation of abstraction refinement loop.\n\n\t/**\n\t * Execute abstraction-refinement loop.\n\t * Return result for initial state(s).\n\t */\n\tpublic double abstractRefine(boolean min) throws PrismException\n\t{\n\t\tint i, n;\n\t\tboolean canRefine = false;\n\t\tlong timer, timerTotal;\n\t\tString initAbstractionInfo;\n\n\t\t// Store whether min/max\n\t\tthis.min = min;\n\n\t\t// For some models, properties, we might need to change\n\t\t// what the model/abstraction type is\n\t\tif (modelType == ModelType.CTMC && propertyType == PropertyType.PROB_REACH) {\n\t\t\tbuildEmbeddedDtmc = true;\n\t\t\tmodelType = ModelType.DTMC;\n\t\t}\n\n\t\t// Store what abstract model type is\n\t\t// and create appropriate model checker\n\t\t// (which inherits log/options from mcOptions)\n\t\tswitch (modelType) {\n\t\tcase DTMC:\n\t\t\tabstractionType = ModelType.MDP;\n\t\t\tmc = new MDPModelChecker(null);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tabstractionType = ModelType.CTMDP;\n\t\t\tmc = new CTMDPModelChecker(null);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tabstractionType = ModelType.STPG;\n\t\t\tmc = new STPGModelChecker(null);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot handle model type \" + modelType);\n\t\t}\n\t\tmc.inheritSettings(mcOptions);\n\t\t// But limit verbosity (since model checking will be done many times)\n\t\t//mc.setVerbosity(verbosity - 1);\n\n\t\t// Init timers, etc.\n\t\ttimerTotal = System.currentTimeMillis();\n\t\ttimeBuild = timeRebuild = timeCheck = timeRefine = 0;\n\t\ttimeCheckLb = timeCheckUb = timeCheckPre = timeCheckProb0 = 0;\n\t\titersTotal = 0;\n\n\t\t// Build first abstraction (and state sets)\n\t\tmainLog.println(\"\\nBuilding initial \" + abstractionType + \"...\");\n\t\ttimer = System.currentTimeMillis();\n\t\tinitialise();\n\t\tinitAbstractionInfo = abstraction.infoString();\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\ttimeBuild += timer / 1000.0;\n\t\tif (verbosity >= 2) {\n\t\t\tmainLog.println(abstractionType + \" constructed in \" + (timer / 1000.0) + \" secs.\");\n\t\t\tmainLog.println(abstractionType + \": \" + abstraction.infoString());\n\t\t}\n\t\tif (verbosity >= 10) {\n\t\t\tmainLog.println(abstractionType + \": \" + abstraction);\n\t\t}\n\n\t\t// Initialise model checking info\n\t\tn = abstraction.getNumStates();\n\t\tlbSoln = Utils.bitsetToDoubleArray(target, n);\n\t\tubSoln = new double[n];\n\t\tfor (i = 0; i < n; i++)\n\t\t\tubSoln[i] = 1.0;\n\t\tknown = (BitSet) target.clone();\n\n\t\t// Refinement loop\n\t\trefinementNum = 0;\n\t\twhile (true) {\n\t\t\tif (exportDot)\n\t\t\t\texportToDotFile(\"abstr\" + refinementNum + \".dot\", abstraction, known, lbSoln, ubSoln);\n\t\t\t//while (cheapCheckRefine() > 0) ;\n\t\t\tmodelCheckAbstraction(min);\n\t\t\tif (refinementNum >= maxRefinements)\n\t\t\t\tbreak;\n\t\t\tcanRefine = chooseStatesToRefine();\n\t\t\tif (!canRefine)\n\t\t\t\tbreak;\n\t\t\trefinementNum++;\n\t\t\trefine(refineStates);\n\t\t\tif (verbosity >= 10) {\n\t\t\t\tmainLog.println(abstractionType + \": \" + abstraction);\n\t\t\t}\n\t\t}\n\n\t\t// Finish up\n\t\ttimerTotal = System.currentTimeMillis() - timerTotal;\n\t\ttimeTotal = timerTotal / 1000.0;\n\t\tprintFinalSummary(initAbstractionInfo, canRefine);\n\n\t\t// Return result (avg of lower/upper bounds)\n\t\treturn (lbInit + ubInit) / 2;\n\t}\n\n\tprotected int cheapCheckRefine() throws PrismException\n\t{\n\t\tif (propertyType != PropertyType.PROB_REACH)\n\t\t\treturn 0;\n\n\t\tmainLog.println(\"cheap...\");\n\t\tint i, n, count, numNewStates;\n\t\tdouble lb, ub;\n\t\tlong timer;\n\t\tn = abstraction.getNumStates();\n\t\tcount = 0;\n\t\ti = -1;\n\t\twhile (i < n) {\n\t\t\t// Pick next state\n\t\t\ti = (known == null) ? i + 1 : known.nextClearBit(i + 1);\n\t\t\t// TODO: check use of nextClearBit here\n\t\t\tif (i < 0)\n\t\t\t\tbreak;\n\n\t\t\t//log.println(\"YY \"+i+\" \"+((STPG)abstraction).steps.get(i));\n\t\t\tif (((STPG) abstraction).allSuccessorsInSet(i, known)) {\n\t\t\t\t// Compute... note lbsoln for both is ok sinec = ubsoln\n\t\t\t\tlb = ((STPG) abstraction).mvMultMinMaxSingle(i, lbSoln, true, min);\n\t\t\t\tub = ((STPG) abstraction).mvMultMinMaxSingle(i, lbSoln, false, min);\n\t\t\t\tmainLog.println(((STPGAbstrSimple) abstraction).getChoices(i));\n\t\t\t\tmainLog.println(\"XX \" + i + \": old=[\" + lbSoln[i] + \",\" + ubSoln[i] + \"], new=[\" + lb + \",\" + ub + \"]\");\n\t\t\t\tif (PrismUtils.doublesAreClose(ub, lb, refineTermCritParam, refineTermCrit == RefineTermCrit.ABSOLUTE)) {\n\t\t\t\t\tlbSoln[i] = ubSoln[i] = lb;\n\t\t\t\t\tknown.set(i);\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t\t//\n\t\t\t\telse {\n\t\t\t\t\tHashSet<Integer> rebuildStates = new HashSet<Integer>();\n\t\t\t\t\ttimer = System.currentTimeMillis();\n\t\t\t\t\tnumNewStates = refineState(i, null, rebuildStates);\n\t\t\t\t\ttimer = System.currentTimeMillis() - timer;\n\t\t\t\t\ttimeRefine += timer / 1000.0;\n\t\t\t\t\tif (numNewStates > 1) {\n\t\t\t\t\t\ttimer = System.currentTimeMillis();\n\t\t\t\t\t\trebuildAbstraction(rebuildStates);\n\t\t\t\t\t\ttimer = System.currentTimeMillis() - timer;\n\t\t\t\t\t\ttimeRebuild += timer / 1000.0;\n\t\t\t\t\t\tmainLog.println(\"rebuildStates: \" + rebuildStates);\n\t\t\t\t\t\tcount++;\n\t\t\t\t\t\tfor (int j = 0; j < numNewStates; j++) {\n\t\t\t\t\t\t\tint a = (j == 0) ? i : abstraction.getNumStates() - numNewStates + j;\n\t\t\t\t\t\t\tlb = ((STPG) abstraction).mvMultMinMaxSingle(a, lbSoln, true, min);\n\t\t\t\t\t\t\tub = ((STPG) abstraction).mvMultMinMaxSingle(a, lbSoln, false, min);\n\t\t\t\t\t\t\tmainLog.println(\"XXX \" + a + \": old=[\" + lbSoln[a] + \",\" + ubSoln[a] + \"], new=[\" + lb\n\t\t\t\t\t\t\t\t\t+ \",\" + ub + \"]\");\n\t\t\t\t\t\t\tlbSoln[a] = lbLastSoln[a] = lb;\n\t\t\t\t\t\t\tubSoln[a] = ubLastSoln[a] = ub;\n\t\t\t\t\t\t\tif (PrismUtils.doublesAreClose(ub, lb, refineTermCritParam,\n\t\t\t\t\t\t\t\t\trefineTermCrit == RefineTermCrit.ABSOLUTE)) {\n\t\t\t\t\t\t\t\tlbSoln[a] = ubSoln[a] = lb;\n\t\t\t\t\t\t\t\tknown.set(a);\n\t\t\t\t\t\t\t\tcount++;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t//\treturn count;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn count;\n\t}\n\n\t/**\n\t * Model check the abstraction; store results in lbSoln, ubSoln.\n\t */\n\tprotected void modelCheckAbstraction(boolean min) throws PrismException\n\t{\n\t\tint i, n, numInitialStates;\n\t\tlong timer;\n\n\t\t// Start model checking\n\t\tmainLog.println(\"\\nModel checking \" + abstractionType + \"...\");\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Do model checking to compute lower/upper bounds\n\t\t// (depends on type of property being checked)\n\t\tswitch (propertyType) {\n\t\tcase PROB_REACH:\n\t\t\tmodelCheckAbstractionProbReach(min);\n\t\t\tbreak;\n\t\tcase PROB_REACH_BOUNDED:\n\t\t\tmodelCheckAbstractionReachBounded(min);\n\t\t\tbreak;\n\t\tcase EXP_REACH:\n\t\t\tmodelCheckAbstractionExpReach(min);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Property type \" + propertyType + \" not supported\");\n\t\t}\n\n\t\t// See if each state has \"converged\", i.e. bounds are close enough to assume exact\n\t\tn = abstraction.getNumStates();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tknown.set(i, PrismUtils.doublesAreClose(ubSoln[i], lbSoln[i], refineTermCritParam,\n\t\t\t\t\trefineTermCrit == RefineTermCrit.ABSOLUTE));\n\t\t}\n\n\t\t// Compute bounds for initial states\n\t\tlbInit = ubInit = min ? Double.POSITIVE_INFINITY : Double.NEGATIVE_INFINITY;\n\t\tfor (int j : abstraction.getInitialStates()) {\n\t\t\tif (verbosity >= 10)\n\t\t\t\tmainLog.println(\"Init \" + j + \": \" + lbSoln[j] + \"-\" + ubSoln[j]);\n\t\t\tif (min) {\n\t\t\t\tlbInit = Math.min(lbInit, lbSoln[j]);\n\t\t\t\tubInit = Math.min(ubInit, ubSoln[j]);\n\t\t\t} else {\n\t\t\t\tlbInit = Math.max(lbInit, lbSoln[j]);\n\t\t\t\tubInit = Math.max(ubInit, ubSoln[j]);\n\t\t\t}\n\t\t}\n\n\t\t// Model checking done\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\ttimeCheck += timer / 1000.0;\n\t\tmainLog.println(abstractionType + \" model checked in \" + (timer / 1000.0) + \" secs.\");\n\n\t\t// Display results\n\t\tmainLog.println(known.cardinality() + \"/\" + n + \" states converged.\");\n\t\tnumInitialStates = abstraction.getNumInitialStates();\n\t\tmainLog.print(\"Diff across \");\n\t\tmainLog.print(numInitialStates + \" initial state\" + (numInitialStates == 1 ? \"\" : \"s\") + \": \");\n\t\tmainLog.println(ubInit - lbInit);\n\t\tmainLog.print(\"Lower/upper bounds for \");\n\t\tmainLog.print(numInitialStates + \" initial state\" + (numInitialStates == 1 ? \"\" : \"s\") + \": \");\n\t\tmainLog.println(lbInit + \" - \" + ubInit);\n\t}\n\n\t/**\n\t * Do model checking for probabilistic reachability; store results in lbSoln, ubSoln.\n\t */\n\tprotected void modelCheckAbstractionProbReach(boolean min) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n;\n\n\t\t// Compute lower bounds\n\t\tswitch (abstractionType) {\n\t\tcase MDP:\n\t\t\tif (optimise && refinementNum > 0) {\n\t\t\t\tmc.setValIterDir(MDPModelChecker.ValIterDir.BELOW);\n\t\t\t\t// TODO\n\t\t\t} else {\n\t\t\t\tres = ((MDPModelChecker) mc).computeReachProbs((MDP) abstraction, target, true);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase CTMDP:\n\t\t\tif (optimise && refinementNum > 0) {\n\t\t\t\tmc.setValIterDir(MDPModelChecker.ValIterDir.BELOW);\n\t\t\t\t// TODO\n\t\t\t} else {\n\t\t\t\tres = ((CTMDPModelChecker) mc).computeReachProbs((CTMDP) abstraction, target, true);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase STPG:\n\t\t\tif (optimise && refinementNum > 0) {\n\t\t\t\tmc.setValIterDir(MDPModelChecker.ValIterDir.BELOW);\n\t\t\t\tres = ((STPGModelChecker) mc).computeReachProbs((STPG) abstraction, null, target, true, min, lbSoln, known);\n\t\t\t} else {\n\t\t\t\tres = ((STPGModelChecker) mc).computeReachProbs((STPG) abstraction, null, target, true, min, null, null);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + abstractionType);\n\t\t}\n\t\tlbSoln = res.soln;\n\t\tlbLastSoln = lbSoln; // TODO: fix (if nec.)\n\t\ttimeCheckLb += res.timeTaken;\n\t\ttimeCheckProb0 += res.timeProb0;\n\t\ttimeCheckPre += res.timePre;\n\t\titersTotal += res.numIters;\n\t\t//mainLog.println(lbSoln);\n\n\t\t// Compute upper bounds\n\t\tswitch (abstractionType) {\n\t\tcase MDP:\n\t\t\tif (optimise) {\n\t\t\t\t// TODO\n\t\t\t} else {\n\t\t\t\tres = ((MDPModelChecker) mc).computeReachProbs((MDP) abstraction, target, false);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase CTMDP:\n\t\t\tif (optimise) {\n\t\t\t\t// TODO\n\t\t\t} else {\n\t\t\t\tres = ((CTMDPModelChecker) mc).computeReachProbs((CTMDP) abstraction, target, false);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase STPG:\n\t\t\tif (optimise) {\n\t\t\t\tif (above) {\n\t\t\t\t\tmc.setValIterDir(ValIterDir.ABOVE);\n\t\t\t\t\tres = ((STPGModelChecker) mc).computeReachProbs((STPG) abstraction, null, target, false, min, ubSoln, known);\n\t\t\t\t} else {\n\t\t\t\t\tmc.setValIterDir(ValIterDir.BELOW);\n\t\t\t\t\tdouble lbCopy[] = Utils.cloneDoubleArray(lbSoln);\n\t\t\t\t\tres = ((STPGModelChecker) mc).computeReachProbs((STPG) abstraction, null, target, false, min, lbCopy, known);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tres = ((STPGModelChecker) mc).computeReachProbs((STPG) abstraction, null, target, false, min, null, null);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + abstractionType);\n\t\t}\n\t\tubSoln = res.soln;\n\t\tubLastSoln = ubSoln; // TODO: fix (if nec.)\n\t\ttimeCheckUb += res.timeTaken;\n\t\ttimeCheckProb0 += res.timeProb0;\n\t\ttimeCheckPre += res.timePre;\n\t\titersTotal += res.numIters;\n\t\t//mainLog.println(ubSoln);\n\t}\n\n\t/*\n\t * Do model checking for bounded probabilistic reachability; store results in lbSoln, ubSoln.\n\t */\n\tprotected void modelCheckAbstractionReachBounded(boolean min) throws PrismException\n\t{\n\t\tModelCheckerResult res;\n\t\tdouble results[] = new double[reachBound + 1];\n\n\t\t// Compute lower bounds\n\t\tswitch (abstractionType) {\n\t\tcase MDP:\n\t\t\tres = ((MDPModelChecker) mc).computeBoundedReachProbs((MDP) abstraction, null, target, reachBound, true, null, results);\n\t\t\tbreak;\n\t\tcase CTMDP:\n\t\t\tres = ((CTMDPModelChecker) mc).computeBoundedReachProbs((CTMDP) abstraction, null, target, (double) reachBound, true,\n\t\t\t\t\tnull, results);\n\t\t\tbreak;\n\t\tcase STPG:\n\t\t\tres = ((STPGModelChecker) mc).computeBoundedReachProbs((STPG) abstraction, null, target, reachBound, true, min, null,\n\t\t\t\t\tresults);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + abstractionType);\n\t\t}\n\t\tlbSoln = res.soln;\n\t\tlbLastSoln = res.lastSoln;\n\t\ttimeCheckLb += res.timeTaken;\n\t\ttimeCheckProb0 += res.timeProb0;\n\t\ttimeCheckPre += res.timePre;\n\t\titersTotal += res.numIters;\n\n\t\tmainLog.print(\"#\");\n\t\tfor (int i = 0; i < reachBound + 1; i++)\n\t\t\tmainLog.print(\" \" + results[i]);\n\t\tmainLog.println();\n\n\t\t// Compute upper bounds\n\t\tswitch (abstractionType) {\n\t\tcase MDP:\n\t\t\tres = ((MDPModelChecker) mc).computeBoundedReachProbs((MDP) abstraction, null, target, reachBound, false, null, results);\n\t\t\tbreak;\n\t\tcase CTMDP:\n\t\t\tres = ((CTMDPModelChecker) mc).computeBoundedReachProbs((CTMDP) abstraction, null, target, (double) reachBound, false,\n\t\t\t\t\tnull, results);\n\t\t\tbreak;\n\t\tcase STPG:\n\t\t\tres = ((STPGModelChecker) mc).computeBoundedReachProbs((STPG) abstraction, null, target, reachBound, false, min, null,\n\t\t\t\t\tresults);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + abstractionType);\n\t\t}\n\t\tubSoln = res.soln;\n\t\tubLastSoln = res.lastSoln;\n\t\ttimeCheckUb += res.timeTaken;\n\t\ttimeCheckProb0 += res.timeProb0;\n\t\ttimeCheckPre += res.timePre;\n\t\titersTotal += res.numIters;\n\n\t\tmainLog.print(\"#\");\n\t\tfor (int i = 0; i < reachBound + 1; i++)\n\t\t\tmainLog.print(\" \" + results[i]);\n\t\tmainLog.println();\n\t}\n\n\t/**\n\t * Do model checking for expected reachability; store results in lbSoln, ubSoln.\n\t */\n\tprotected void modelCheckAbstractionExpReach(boolean min) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint i, n;\n\n\t\t// Pass settings to model checker\n\t\tmc.termCrit = TermCrit.RELATIVE;\n\t\tmc.termCritParam = 1e-8;\n\n\t\t// Value iteration parameters depend on optimisations used \n\t\tswitch (abstractionType) {\n\t\tcase MDP:\n\t\t\tif (optimise && refinementNum > 0) {\n\t\t\t\tres = ((MDPModelChecker) mc).computeReachRewards((MDP) abstraction, null, target, true, lbSoln, known);\n\t\t\t} else {\n\t\t\t\tres = ((MDPModelChecker) mc).computeReachRewards((MDP) abstraction, null, target, true, null, null);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + abstractionType);\n\t\t}\n\t\tlbSoln = res.soln;\n\t\tlbLastSoln = lbSoln; // TODO: fix (if nec.)\n\t\ttimeCheckLb += res.timeTaken;\n\t\ttimeCheckProb0 += res.timeProb0;\n\t\ttimeCheckPre += res.timePre;\n\t\titersTotal += res.numIters;\n\n\t\t// Compute upper bounds\n\t\tswitch (abstractionType) {\n\t\tcase MDP:\n\t\t\tif (optimise) {\n\t\t\t\tdouble lbCopy[] = Utils.cloneDoubleArray(lbSoln);\n\t\t\t\tres = ((MDPModelChecker) mc).computeReachRewards((MDP) abstraction, null, target, false, lbCopy, known);\n\t\t\t} else {\n\t\t\t\tres = ((MDPModelChecker) mc).computeReachRewards((MDP) abstraction, null, target, false, null, null);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check \" + abstractionType);\n\t\t}\n\t\tubSoln = res.soln;\n\t\tubLastSoln = ubSoln; // TODO: fix (if nec.)\n\t\ttimeCheckUb += res.timeTaken;\n\t\ttimeCheckProb0 += res.timeProb0;\n\t\ttimeCheckPre += res.timePre;\n\t\titersTotal += res.numIters;\n\t}\n\n\t/*\n\t * Pick states to refine.\n\t */\n\tprotected boolean chooseStatesToRefine() throws PrismException\n\t{\n\t\tArrayList<Integer> refinableStates;\n\t\tdouble maxDiff, bound;\n\t\tint i, numStates;\n\n\t\t// Empty refinement states lists\n\t\trefinableStates = new ArrayList<Integer>();\n\t\trefineStates = new ArrayList<Integer>();\n\n\t\t// Check max diff in bounds over initial states\n\t\t// (computed after numerical solution)\n\t\tif (PrismUtils.doublesAreClose(ubInit, lbInit, refineTermCritParam, refineTermCrit == RefineTermCrit.ABSOLUTE))\n\t\t\treturn false;\n\n\t\t// Compute max diff in bounds over all states\n\t\tnumStates = abstraction.getNumStates();\n\t\tmaxDiff = ubSoln[0] - lbSoln[0];\n\t\tfor (i = 1; i < numStates; i++)\n\t\t\tif (ubSoln[i] - lbSoln[i] > maxDiff)\n\t\t\t\tmaxDiff = ubSoln[i] - lbSoln[i];\n\t\tmainLog.println(\"Max diff over all states: \" + maxDiff);\n\n\t\t// Find all states with suitably high diff *and* a game choice\n\t\tswitch (refineStratWhere) {\n\t\tcase ALL_MAX:\n\t\tcase FIRST_MAX:\n\t\tcase LAST_MAX:\n\t\t\tbound = Math.max(0, maxDiff - refineTermCritParam);\n\t\t\t// TODO: resolve issue of what to do here if relative error\n\t\t\tbreak;\n\t\tcase ALL:\n\t\tcase FIRST:\n\t\tcase LAST:\n\t\tdefault:\n\t\t\tbound = refineTermCritParam;\n\t\t\t// TODO: resolve issue of what to do here if relative error\n\t\t\tbreak;\n\t\t}\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\t// Note: Need to do comparison with >= below for case where maxdiff=infinity\n\t\t\tif (ubSoln[i] - lbSoln[i] >= bound && abstraction.getNumChoices(i) > 1)\n\t\t\t\trefinableStates.add(i);\n\t\t}\n\t\tmainLog.println(refinableStates.size() + \" refineable states.\");\n\t\tif (verbosity >= 1) {\n\t\t\tmainLog.println(\"Refinable states: \" + refinableStates);\n\t\t}\n\n\t\t// If no states to refine, return false \n\t\tif (refinableStates.size() == 0) {\n\t\t\treturn false;\n\t\t}\n\n\t\t// Pick state(s) to refine according to strategy\n\t\tswitch (refineStratWhere) {\n\t\tcase ALL:\n\t\tcase ALL_MAX:\n\t\t\trefineStates.addAll(refinableStates);\n\t\t\tbreak;\n\t\tcase FIRST:\n\t\tcase FIRST_MAX:\n\t\t\trefineStates.add(refinableStates.get(0));\n\t\t\tbreak;\n\t\tcase LAST:\n\t\tcase LAST_MAX:\n\t\t\trefineStates.add(refinableStates.get(refinableStates.size() - 1));\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown (where) refinement strategy \\\"\" + refineStratWhere.name() + \"\\\"\");\n\t\t}\n\n\t\treturn true;\n\t}\n\n\t/**\n\t * Refine a set of states.\n\t * @param refineState States to refine.\n\t */\n\tprotected void refine(List<Integer> refineStates) throws PrismException\n\t{\n\t\tSet<Integer> rebuiltStates, rebuildStates;\n\t\tint i, n, refineState, numNewStates, numSuccRefines;\n\t\tlong timer;\n\n\t\tmainLog.println(\"\\nRefinement \" + refinementNum + \"...\");\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Store lists of game states that have been or will need to be rebuilt\n\t\trebuiltStates = new LinkedHashSet<Integer>();\n\t\trebuildStates = new LinkedHashSet<Integer>();\n\n\t\tnumSuccRefines = 0;\n\t\tn = refineStates.size();\n\t\t// Go through list in reverse order\n\t\tfor (i = n - 1; i >= 0; i--) {\n\t\t\tif (verbosity >= 1)\n\t\t\t\tmainLog.println(\"Refinement \" + refinementNum + \".\" + (n - i) + \"...\");\n\t\t\trefineState = refineStates.get(i);\n\t\t\tnumNewStates = refineState(refineState, rebuiltStates, rebuildStates);\n\t\t\tif (numNewStates > 1)\n\t\t\t\tnumSuccRefines++;\n\t\t}\n\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\ttimeRefine += timer / 1000.0;\n\t\tmainLog.print(numSuccRefines + \" states successfully refined\");\n\t\tmainLog.println(\" in \" + (timer / 1000.0) + \" secs.\");\n\n\t\t// Rebuild any states as necessary\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Rebuilding states: \" + rebuildStates);\n\t\trebuildAbstraction(rebuildStates);\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\ttimeRebuild += timer / 1000.0;\n\t\tmainLog.print(rebuiltStates.size() + \"+\" + rebuildStates.size() + \"=\");\n\t\tmainLog.print((rebuiltStates.size() + rebuildStates.size()));\n\t\tmainLog.println(\" states of \" + abstractionType + \" rebuilt in \" + (timer / 1000.0) + \" secs.\");\n\t\tmainLog.println(\"New \" + abstractionType + \" has \" + abstraction.getNumStates() + \" states.\");\n\t}\n\n\t/**\n\t * Refine a single state, by splitting using the current refinement strategy.\n\t * Adds new states to abstraction (and updates initial states), updates target states,\n\t * and resizes/updates lb/ub solution vectors and 'known' set.\n\t * Also keeps track of which states have been or will need to be rebuilt as a result.\n\t * @param refineState State to refine.\n\t * @param rebuiltStates States that have been rebuilt as a result will be added here.\n\t * @param rebuildStates States that need rebuilding as a result will be added here.\n\t * @return Number of states into which split (i.e. 1 denotes refinement failed).\n\t */\n\tprotected int refineState(int refineState, Set<Integer> rebuiltStates, Set<Integer> rebuildStates)\n\t\t\tthrows PrismException\n\t{\n\t\tList<List<Integer>> choiceLists;\n\t\tList<Integer> lbStrat = null, ubStrat = null;\n\t\tint i, n, numStates, numNewStates;\n\n\t\t// Sanity checks - pointless refinements...\n\t\tif (sanityChecks) {\n\t\t\t// Check that state to refine is not a target state (shouldn't happen\n\t\t\t// because diff in bounds should always be 0 in such states)\n\t\t\tif (target.get(refineState)) {\n\t\t\t\tthrow new PrismException(\"Why would I want to refine a target state?\");\n\t\t\t}\n\t\t\t// Likewise for states where lower/upper bounds have already converged\n\t\t\tif (known.get(refineState)) {\n\t\t\t\tthrow new PrismException(\"Why would I want to refine a state that has already converged?\");\n\t\t\t}\n\t\t}\n\n\t\t// Don't refine a state that we have already modified through refinement\n\t\tif (rebuiltStates.contains(refineState)) {\n\t\t\tif (verbosity >= 1)\n\t\t\t\tmainLog.printWarning(\"Skipping refinement of #\" + refineState\n\t\t\t\t\t\t+ \" which has already been modified by refinement.\");\n\t\t\treturn 1;\n\t\t}\n\n\t\t// Decide how this state will be split up (in terms of player 1 choices)\n\t\tchoiceLists = new ArrayList<List<Integer>>();\n\t\tswitch (refineStratHow) {\n\t\tcase VAL:\n\t\t\tlbStrat = ubStrat = null;\n\t\t\tswitch (abstractionType) {\n\t\t\tcase MDP:\n\t\t\t\tswitch (propertyType) {\n\t\t\t\tcase PROB_REACH:\n\t\t\t\t\tlbStrat = ((MDPModelChecker) mc).probReachStrategy((MDP) abstraction, refineState, target, true,\n\t\t\t\t\t\t\tlbLastSoln);\n\t\t\t\t\tubStrat = ((MDPModelChecker) mc).probReachStrategy((MDP) abstraction, refineState, target, false,\n\t\t\t\t\t\t\tubLastSoln);\n\t\t\t\t\tbreak;\n\t\t\t\tcase PROB_REACH_BOUNDED:\n\t\t\t\t\tlbStrat = ((MDPModelChecker) mc).probReachStrategy((MDP) abstraction, refineState, target, true,\n\t\t\t\t\t\t\tlbLastSoln);\n\t\t\t\t\tubStrat = ((MDPModelChecker) mc).probReachStrategy((MDP) abstraction, refineState, target, false,\n\t\t\t\t\t\t\tubLastSoln);\n\t\t\t\t\tbreak;\n\t\t\t\tcase EXP_REACH:\n\t\t\t\t\tlbStrat = ((MDPModelChecker) mc).expReachStrategy((MDP) abstraction, null, refineState, target, true,\n\t\t\t\t\t\t\tlbLastSoln);\n\t\t\t\t\tubStrat = ((MDPModelChecker) mc).expReachStrategy((MDP) abstraction, null, refineState, target, false,\n\t\t\t\t\t\t\tubLastSoln);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase CTMDP:\n\t\t\t\tlbStrat = ((CTMDPModelChecker) mc).probReachStrategy((CTMDP) abstraction, refineState, target, true,\n\t\t\t\t\t\tlbLastSoln);\n\t\t\t\tubStrat = ((CTMDPModelChecker) mc).probReachStrategy((CTMDP) abstraction, refineState, target, false,\n\t\t\t\t\t\tubLastSoln);\n\t\t\t\tbreak;\n\t\t\tcase STPG:\n\t\t\t\tlbStrat = ((STPGModelChecker) mc).probReachStrategy((STPG) abstraction, refineState, target, true, min,\n\t\t\t\t\t\tlbLastSoln);\n\t\t\t\tubStrat = ((STPGModelChecker) mc).probReachStrategy((STPG) abstraction, refineState, target, false,\n\t\t\t\t\t\tmin, ubLastSoln);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (lbStrat == null || ubStrat == null) {\n\t\t\t\tString s = \"Cannot generate strategy information for\";\n\t\t\t\ts += \" model type \" + abstractionType + \" and property type \" + propertyType;\n\t\t\t\tthrow new PrismException(s);\n\t\t\t}\n\n\t\t\tif (sanityChecks && (lbStrat.isEmpty() || ubStrat.isEmpty()))\n\t\t\t\tthrow new PrismException(\"Empty strategy generated for state \" + refineState);\n\t\t\t// Check if lb/ub are identical (just use equals() since lists are sorted)\n\t\t\tif (lbStrat.equals(ubStrat) && lbStrat.size() == abstraction.getNumChoices(refineState)) {\n\t\t\t\tif (verbosity >= 1)\n\t\t\t\t\tmainLog.printWarning(\"Skipping refinement of #\" + refineState\n\t\t\t\t\t\t\t+ \" for which lb/ub strategy sets are equal and covering.\");\n\t\t\t\treturn 1;\n\t\t\t}\n\t\t\tif (verbosity >= 1)\n\t\t\t\tmainLog.println(\"lbStrat: \" + lbStrat + \", ubStrat: \" + ubStrat);\n\t\t\t// Make disjoint\n\t\t\tint method = 1;\n\t\t\tswitch (method) {\n\t\t\t// Remove intersection of lb/ub from larger\n\t\t\tcase 1:\n\t\t\t\tif (lbStrat.containsAll(ubStrat)) {\n\t\t\t\t\tlbStrat.removeAll(ubStrat);\n\t\t\t\t} else {\n\t\t\t\t\tubStrat.removeAll(lbStrat);\n\t\t\t\t}\n\t\t\t\tif (!lbStrat.isEmpty())\n\t\t\t\t\tchoiceLists.add(lbStrat);\n\t\t\t\tif (!ubStrat.isEmpty())\n\t\t\t\t\tchoiceLists.add(ubStrat);\n\t\t\t\tbreak;\n\t\t\tcase 2:\n\t\t\t\t// Remove intersection of lb/ub from both\n\t\t\t\tlbStrat.removeAll(ubStrat);\n\t\t\t\tubStrat.removeAll(lbStrat);\n\t\t\t\tchoiceLists.add(lbStrat);\n\t\t\t\tchoiceLists.add(ubStrat);\n\t\t\t\tbreak;\n\t\t\tcase 3:\n\t\t\t\t// Pick a single (unique) choice from lb/ub\n\t\t\t\tif (lbStrat.containsAll(ubStrat)) {\n\t\t\t\t\tlbStrat.removeAll(ubStrat);\n\t\t\t\t} else {\n\t\t\t\t\tubStrat.removeAll(lbStrat);\n\t\t\t\t}\n\t\t\t\tList<Integer> newChoiceList;\n\t\t\t\tnewChoiceList = new ArrayList<Integer>();\n\t\t\t\tnewChoiceList.add(lbStrat.get(0));\n\t\t\t\tchoiceLists.add(newChoiceList);\n\t\t\t\tnewChoiceList = new ArrayList<Integer>();\n\t\t\t\tnewChoiceList.add(ubStrat.get(0));\n\t\t\t\tchoiceLists.add(newChoiceList);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (verbosity >= 1)\n\t\t\t\tmainLog.println(\"split: \" + choiceLists);\n\t\t\tbreak;\n\t\tcase ALL:\n\t\t\tn = abstraction.getNumChoices(refineState);\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tList<Integer> newChoiceList;\n\t\t\t\tnewChoiceList = new ArrayList<Integer>();\n\t\t\t\tnewChoiceList.add(i);\n\t\t\t\tchoiceLists.add(newChoiceList);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown (how) refinement strategy \\\"\" + refineStratWhere.name() + \"\\\"\");\n\t\t}\n\n\t\t// Get (old) number of states\n\t\tnumStates = abstraction.getNumStates();\n\n\t\t// Split the state, based on nondet choices selected above\n\t\tnumNewStates = splitState(refineState, choiceLists, rebuiltStates, rebuildStates);\n\n\t\t// Update existing solution vectors (if any)\n\t\tlbSoln = Utils.extendDoubleArray(lbSoln, numStates, numStates + numNewStates - 1, lbSoln[refineState]);\n\t\tlbLastSoln = Utils.extendDoubleArray(lbLastSoln, numStates, numStates + numNewStates - 1,\n\t\t\t\tlbLastSoln[refineState]);\n\t\tubSoln = Utils.extendDoubleArray(ubSoln, numStates, numStates + numNewStates - 1, ubSoln[refineState]);\n\t\tubLastSoln = Utils.extendDoubleArray(ubLastSoln, numStates, numStates + numNewStates - 1,\n\t\t\t\tubLastSoln[refineState]);\n\n\t\t// Note: we don't have to update 'known' since implicit new elements of a BitSet are assumed false\n\n\t\treturn numNewStates;\n\t}\n\n\t/**\n\t * Utility function to add, into the sets of choices passed to splitState(...),\n\t * an additional set comprising the remainder of the nondeterministic choices.  \n\t */\n\tpublic void addRemainderIntoChoiceLists(int splitState, List<List<Integer>> choiceLists)\n\t{\n\t\tint nChoices;\n\t\tBitSet included;\n\t\tArrayList<Integer> otherChoices;\n\t\tint i;\n\n\t\tnChoices = abstraction.getNumChoices(splitState);\n\t\tincluded = new BitSet(nChoices);\n\t\tfor (List<Integer> choiceList : choiceLists) {\n\t\t\tfor (int j : choiceList) {\n\t\t\t\tincluded.set(j);\n\t\t\t}\n\t\t}\n\t\totherChoices = new ArrayList<Integer>();\n\t\ti = included.nextClearBit(0);\n\t\twhile (i < nChoices) {\n\t\t\totherChoices.add(i);\n\t\t\ti = included.nextClearBit(i + 1);\n\t\t}\n\t\tif (otherChoices.size() > 0)\n\t\t\tchoiceLists.add(otherChoices);\n\t}\n\n\t/**\n\t * Display final summary about the abstraction-refinement loop.\n\t */\n\tprotected void printFinalSummary(String initAbstractionInfo, boolean canRefine)\n\t{\n\t\t// Print abstraction summary\n\t\tmainLog.println(\"\\nInitial \" + abstractionType + \": \" + initAbstractionInfo);\n\t\tmainLog.println(\"Final \" + abstractionType + \": \" + abstraction.infoString());\n\n\t\t// Print termination info\n\t\tmainLog.print(\"\\nTerminated \" + (canRefine ? \"(early) \" : \"\"));\n\t\tmainLog.print(\"after \" + refinementNum + \" refinements\");\n\t\tmainLog.print(\" in \" + PrismUtils.formatDouble2dp(timeTotal) + \" secs.\");\n\t\tmainLog.println();\n\n\t\t// Print breakdown of timings\n\t\t// (Note: format times to 2 d.p. for alignment)\n\t\tmainLog.println(\"\\nAbstraction-refinement time breakdown:\");\n\t\tmainLog.print(\"* \" + PrismUtils.formatDouble2dp(timeBuild) + \" secs\");\n\t\tmainLog.print(\" (\" + PrismUtils.formatPercent1dp(timeBuild / timeTotal) + \")\");\n\t\tmainLog.print(\" = Building initial \" + abstractionType);\n\t\tmainLog.println();\n\t\tmainLog.print(\"* \" + PrismUtils.formatDouble2dp(timeRebuild) + \" secs\");\n\t\tmainLog.print(\" (\" + PrismUtils.formatPercent1dp(timeRebuild / timeTotal) + \")\");\n\t\tmainLog.print(\" = Rebuilding \" + abstractionType + \" (\");\n\t\tmainLog.print(refinementNum + \" x avg \" + PrismUtils.formatDouble2dp(refinementNum > 0 ? (timeRebuild / (refinementNum)) : 0) + \" secs)\");\n\t\tmainLog.println();\n\t\tmainLog.print(\"* \" + PrismUtils.formatDouble2dp(timeCheck) + \" secs\");\n\t\tmainLog.print(\" (\" + PrismUtils.formatPercent1dp(timeCheck / timeTotal) + \")\");\n\t\tmainLog.print(\" = model checking \" + abstractionType + \" (\" + (refinementNum + 1) + \" x avg \");\n\t\tmainLog.print(PrismUtils.formatDouble2dp(timeCheck / (refinementNum + 1)) + \" secs)\");\n\t\tmainLog.print(\" (lb=\" + PrismUtils.formatPercent1dp(timeCheckLb / (timeCheckLb + timeCheckUb)) + \")\");\n\t\tmainLog.print(\" (prob0=\" + PrismUtils.formatPercent1dp(timeCheckProb0 / timeCheck) + \")\");\n\t\tmainLog.print(\" (pre=\" + PrismUtils.formatPercent1dp(timeCheckPre / timeCheck) + \")\");\n\t\tmainLog.print(\" (iters=\" + itersTotal + \")\");\n\t\tmainLog.println();\n\t\tmainLog.print(\"* \" + PrismUtils.formatDouble2dp(timeRefine) + \" secs\");\n\t\tmainLog.print(\" (\" + PrismUtils.formatPercent1dp(timeRefine / timeTotal) + \")\");\n\t\tmainLog.print(\" = refinement (\");\n\t\tmainLog.print(refinementNum + \" x avg \" + PrismUtils.formatDouble2dp(refinementNum > 0 ? (timeRefine / refinementNum) : 0) + \" secs)\");\n\t\tmainLog.println();\n\n\t\t// Print result info for initial states\n\t\tint numInitialStates = abstraction.getNumInitialStates();\n\t\tmainLog.print(\"\\nFinal diff across \");\n\t\tmainLog.print(numInitialStates + \" initial state\" + (numInitialStates == 1 ? \"\" : \"s\") + \": \");\n\t\tmainLog.println(ubInit - lbInit);\n\t\tmainLog.print(\"Final lower/upper bounds for \");\n\t\tmainLog.print(numInitialStates + \" initial state\" + (numInitialStates == 1 ? \"\" : \"s\") + \": \");\n\t\tmainLog.println(lbInit + \" - \" + ubInit);\n\t}\n\n\t// Private utility methods\n\n\t/**\n\t * Export abstract model to a dot file with additional annotated info \n\t */\n\tprivate static void exportToDotFile(String filename, Model abstraction, BitSet known, double lbSoln[],\n\t\t\tdouble ubSoln[]) throws PrismException\n\t{\n\t\tSTPGAbstrSimple<?> stpg;\n\t\tint i, j, k;\n\t\tString nij, nijk;\n\t\t\n\t\tif (abstraction instanceof STPG) {\n\t\t\tstpg = (STPGAbstrSimple) abstraction;\n\t\t} else if (abstraction instanceof MDPSimple) {\n\t\t\tstpg = new STPGAbstrSimple((MDPSimple) abstraction);\n\t\t} else {\n\t\t\tthrow new PrismNotSupportedException(\"Cannot export this model type to a dot file\");\n\t\t}\n\n\t\ttry {\n\t\t\tFileWriter out = new FileWriter(filename);\n\t\t\tout.write(\"digraph \" + \"STPG\" + \" {\\nnode [shape=box];\\n\");\n\t\t\tfor (i = 0; i < stpg.getNumStates(); i++) {\n\t\t\t\tif (known.get(i))\n\t\t\t\t\tout.write(i + \" [label=\\\"\" + i + \" {\" + lbSoln[i] + \"}\" + \"\\\" style=filled  fillcolor=\\\"#cccccc\\\"\");\n\t\t\t\telse\n\t\t\t\t\tout.write(i + \" [label=\\\"\" + i + \" [\" + (ubSoln[i] - lbSoln[i]) + \"]\" + \"\\\"\");\n\t\t\t\tout.write(\"]\\n\");\n\t\t\t\tj = -1;\n\t\t\t\tfor (DistributionSet<?> distrs : stpg.getChoices(i)) {\n\t\t\t\t\tj++;\n\t\t\t\t\tnij = \"n\" + i + \"_\" + j;\n\t\t\t\t\tout.write(i + \" -> \" + nij + \" [ arrowhead=none,label=\\\"\" + j + \"\\\" ];\\n\");\n\t\t\t\t\tout.write(nij + \" [ shape=circle,width=0.1,height=0.1,label=\\\"\\\" ];\\n\");\n\t\t\t\t\tk = -1;\n\t\t\t\t\tfor (Distribution<?> distr : distrs) {\n\t\t\t\t\t\tk++;\n\t\t\t\t\t\tnijk = \"n\" + i + \"_\" + j + \"_\" + k;\n\t\t\t\t\t\tout.write(nij + \" -> \" + nijk + \" [ arrowhead=none,label=\\\"\" + k + \"\\\" ];\\n\");\n\t\t\t\t\t\tout.write(nijk + \" [ shape=point,label=\\\"\\\" ];\\n\");\n\t\t\t\t\t\tfor (Map.Entry<Integer, ?> e : distr) {\n\t\t\t\t\t\t\tout.write(nijk + \" -> \" + e.getKey() + \" [ label=\\\"\" + e.getValue() + \"\\\" ];\\n\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tout.write(\"}\\n\");\n\t\t\tout.close();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"Could not write abstraction to file \\\"\" + filename + \"\\\"\" + e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/QuantAbstractRefineExample.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.*;\n\nimport parser.State;\nimport parser.ast.*;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismPrintStreamLog;\nimport prism.PrismNotSupportedException;\nimport prism.UndefinedConstants;\nimport simulator.ModulesFileModelGenerator;\n\npublic class QuantAbstractRefineExample extends QuantAbstractRefine\n{\n\t// Flags/settings\n\tprotected boolean rebuildImmed = false; // Rebuild split states immediately\n\n\t// Concrete model\n\tprotected ModelSimple<Double> modelConcrete;\n\tprotected ModulesFile modulesFile;\n\tprotected int nConcrete; // Number of (concrete) states\n\tprotected BitSet initialConcrete; // Initial (concrete) states\n\tprotected BitSet targetConcrete; // Target (concrete) states\n\tprotected String targetLabel; // PRISM label denoting target states\n\n\t// Abstraction info\n\t// Map from concrete to abstract states\n\tprotected int concreteToAbstract[];\n\t// Map from abstract P1 choices to concrete state sets\n\tprotected List<List<Set<Integer>>> abstractToConcrete;\n\n\t/**\n\t * Default constructor.\n\t */\n\tpublic QuantAbstractRefineExample(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t// Implementation of initialise() for abstraction-refinement loop; see superclass for details \n\n\t@Override\n\tprotected void initialise() throws PrismException\n\t{\n\t\tExpression targetExpr;\n\t\tList<State> statesList;\n\t\tDistributionSet set;\n\t\tList<Set<Integer>> list;\n\t\tboolean isTarget, isInitial, existsInitial, existsTargetAndInitial, existsRest;\n\t\tint i, c, a, j, nAbstract;\n\n\t\t// Build concrete model\n\t\tmainLog.println(\"Concrete \" + modelType + \": \" + modelConcrete.infoString());\n\t\tnConcrete = modelConcrete.getNumStates();\n\n\t\t// Get initial (concrete) states\n\t\tinitialConcrete = new BitSet(nConcrete);\n\t\tfor (int in: modelConcrete.getInitialStates())\n\t\t\tinitialConcrete.set(in, 1);\n\t\t\n\t\t// Get target (concrete) states\n\t\tstatesList = modelConcrete.getStatesList();\n\t\ti = modulesFile.getLabelList().getLabelIndex(targetLabel);\n\t\tif (i == -1l)\n\t\t\tthrow new PrismException(\"Unknown label \\\"\" + targetLabel + \"\\\"\");\n\t\ttargetExpr = modulesFile.getLabelList().getLabel(i);\n\t\ttargetConcrete = new BitSet(nConcrete);\n\t\tfor (i = 0; i < nConcrete; i++) {\n\t\t\ttargetConcrete.set(i, targetExpr.evaluateBoolean(statesList.get(i)));\n\t\t}\n\t\t\n\t\t// Build a mapping between concrete/abstract states\n\t\t// Initial abstract states: 0: initial, 1: target, 2:rest\n\t\tconcreteToAbstract = new int[nConcrete];\n\t\texistsInitial = existsTargetAndInitial = existsRest = false;\n\t\tfor (c = 0; c < nConcrete; c++) {\n\t\t\tisTarget = targetConcrete.get(c);\n\t\t\tisInitial = initialConcrete.get(c);\n\t\t\texistsInitial |= (!isTarget && isInitial);\n\t\t\texistsTargetAndInitial |= (isTarget && isInitial);\n\t\t\texistsRest |= (!isTarget && !isInitial);\n\t\t\tconcreteToAbstract[c] = isTarget ? 1 : isInitial ? 0 : 2;\n\t\t}\n\t\tif (!existsInitial)\n\t\t\tthrow new PrismException(\"No non-target initial states\");\n\n\t\tif (verbosity >= 10) {\n\t\t\tmainLog.print(\"Initial concreteToAbstract: \");\n\t\t\tmainLog.println(concreteToAbstract);\n\t\t}\n\n\t\t// Create (empty) abstraction and store initial states info\n\t\tnAbstract = existsRest ? 3 : 2;\n\t\tswitch (modelType) {\n\t\tcase MDP:\n\t\t\tabstraction = new STPGAbstrSimple(nAbstract);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Cannot handle model type \" + modelType);\n\t\t}\n\t\tabstraction.addInitialState(0);\n\t\tif (existsTargetAndInitial)\n\t\t\tabstraction.addInitialState(1);\n\n\t\t// Build target set\n\t\ttarget = new BitSet(nAbstract);\n\t\ttarget.set(1);\n\n\t\t// Construct initial abstraction.\n\t\t// Simultaneously, build abstractToConcrete,\n\t\t// which records which concrete states correspond to each game choice.\n\t\tabstractToConcrete = new ArrayList<List<Set<Integer>>>(nAbstract);\n\t\tfor (a = 0; a < nAbstract; a++)\n\t\t\tabstractToConcrete.add(new ArrayList<Set<Integer>>());\n\t\tfor (c = 0; c < nConcrete; c++) {\n\t\t\ta = concreteToAbstract[c];\n\t\t\tswitch (modelType) {\n\t\t\tcase MDP:\n\t\t\t\tset = buildAbstractDistributionSet(c, (MDPSimple) modelConcrete, (STPG) abstraction);\n\t\t\t\tj = ((STPGAbstrSimple) abstraction).addDistributionSet(a, set);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Cannot handle model type \" + modelType);\n\t\t\t}\n\t\t\tlist = abstractToConcrete.get(a);\n\t\t\tif (j >= list.size())\n\t\t\t\tlist.add(new HashSet<Integer>(1));\n\t\t\tlist.get(j).add(c);\n\t\t}\n\t}\n\n\t/**\n\t * Abstract a concrete state c of an MDP ready to add to an STPG state.\n\t */\n\tprotected DistributionSet buildAbstractDistributionSet(int c, MDPSimple<Double> mdp, STPG stpg)\n\t{\n\t\tDistributionSet set = ((STPGAbstrSimple) stpg).newDistributionSet(null);\n\t\tfor (Distribution<Double> distr : mdp.getChoices(c)) {\n\t\t\tset.add(distr.map(concreteToAbstract));\n\t\t}\n\t\treturn set;\n\t}\n\n\t// Implementation of splitState(...) for abstraction-refinement loop; see superclass for details \n\n\t@Override\n\tprotected int splitState(int splitState, List<List<Integer>> choiceLists, Set<Integer> rebuiltStates,\n\t\t\tSet<Integer> rebuildStates) throws PrismException\n\t{\n\t\tList<Set<Integer>> list, listNew;\n\t\tSet<Integer> concreteStates, concreteStatesNew;\n\t\tint i, a, nAbstract, numNewStates;\n\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Splitting: #\" + splitState);\n\n\t\t// Add an element to the list of choices\n\t\t// corresponding to all remaining choices\n\t\taddRemainderIntoChoiceLists(splitState, choiceLists);\n\n\t\t// Do split...\n\t\tnAbstract = abstraction.getNumStates();\n\t\tnumNewStates = choiceLists.size();\n\t\tlist = abstractToConcrete.get(splitState);\n\t\ti = 0;\n\t\tfor (List<Integer> choiceList : choiceLists) {\n\t\t\t// Build...\n\t\t\tlistNew = new ArrayList<Set<Integer>>(1);\n\t\t\tconcreteStatesNew = new HashSet<Integer>();\n\t\t\tlistNew.add(concreteStatesNew);\n\t\t\t// Compute index 'a' of new abstract state\n\t\t\t// (first one reuses splitState, rest go on the end)\n\t\t\t// Also add new list to abstractToConcrete\n\t\t\tif (i == 0) {\n\t\t\t\ta = splitState;\n\t\t\t\tabstractToConcrete.set(a, listNew);\n\t\t\t} else {\n\t\t\t\ta = nAbstract + i - 1;\n\t\t\t\tabstractToConcrete.add(listNew);\n\t\t\t}\n\t\t\t//log.println(choiceList);\n\t\t\tfor (int j : choiceList) {\n\t\t\t\tconcreteStates = list.get(j);\n\t\t\t\tfor (int c : concreteStates) {\n\t\t\t\t\t//log.println(c);\n\t\t\t\t\tconcreteToAbstract[c] = a;\n\t\t\t\t\tconcreteStatesNew.add(c);\n\t\t\t\t}\n\t\t\t}\n\t\t\ti++;\n\t\t}\n\n\t\tif (verbosity >= 10) {\n\t\t\tmainLog.print(\"New concreteToAbstract: \");\n\t\t\tmainLog.println(concreteToAbstract);\n\t\t}\n\n\t\t// Add new states to the abstraction\n\t\tabstraction.addStates(numNewStates - 1);\n\t\t// Add new states to initial state set if needed\n\t\t// Note: we assume any abstract state contains either all/no initial states\n\t\tif (abstraction.isInitialState(splitState)) {\n\t\t\tfor (i = 1; i < numNewStates; i++) {\n\t\t\t\tabstraction.addInitialState(nAbstract + i - 1);\n\t\t\t}\n\t\t}\n\n\t\tfor (i = 0; i < nAbstract; i++) {\n\t\t\tif (i == splitState || abstraction.isSuccessor(i, splitState)) {\n\t\t\t\tif (rebuildImmed) {\n\t\t\t\t\trebuildAbstractionState(i);\n\t\t\t\t\trebuiltStates.add(i);\n\t\t\t\t} else {\n\t\t\t\t\trebuildStates.add(i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tfor (i = 1; i < numNewStates; i++) {\n\t\t\tif (rebuildImmed) {\n\t\t\t\trebuildAbstractionState(nAbstract + i - 1);\n\t\t\t\trebuiltStates.add(i);\n\t\t\t} else {\n\t\t\t\trebuildStates.add(nAbstract + i - 1);\n\t\t\t}\n\t\t}\n\n\t\treturn numNewStates;\n\t}\n\n\t// Implementation of rebuildAbstraction(...) for abstraction-refinement loop; see superclass for details \n\n\t@Override\n\tprotected void rebuildAbstraction(Set<Integer> rebuildStates) throws PrismException\n\t{\n\t\tfor (int a : rebuildStates) {\n\t\t\trebuildAbstractionState(a);\n\t\t}\n\t}\n\n\tprotected void rebuildAbstractionState(int i) throws PrismException\n\t{\n\t\tList<Set<Integer>> list, listNew;\n\t\tDistributionSet set;\n\t\tint j, a;\n\n\t\tlist = abstractToConcrete.get(i);\n\t\tlistNew = new ArrayList<Set<Integer>>();\n\t\tabstraction.clearState(i);\n\t\tfor (Set<Integer> concreteStates : list) {\n\t\t\tfor (int c : concreteStates) {\n\t\t\t\ta = concreteToAbstract[c];\n\t\t\t\t// ASSERT: a = i ???\n\t\t\t\tif (a != i)\n\t\t\t\t\tthrow new PrismException(\"Oops\");\n\t\t\t\tswitch (modelType) {\n\t\t\t\tcase MDP:\n\t\t\t\t\tset = buildAbstractDistributionSet(c, (MDPSimple) modelConcrete, (STPG) abstraction);\n\t\t\t\t\tj = ((STPGAbstrSimple) abstraction).addDistributionSet(a, set);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Cannot handle model type \" + modelType);\n\t\t\t\t}\n\t\t\t\tif (j >= listNew.size())\n\t\t\t\t\tlistNew.add(new HashSet<Integer>(1));\n\t\t\t\tlistNew.get(j).add(c);\n\t\t\t\t//TODO: if (initialConcrete.get(c))\n\t\t\t\t//TODO: \tstpg.initialStates.add(a);\n\t\t\t}\n\t\t}\n\t\tabstractToConcrete.set(i, listNew);\n\t}\n\n\t// Override this to also print out concrete model details at the end\n\t@Override\n\tprotected void printFinalSummary(String initAbstractionInfo, boolean canRefine)\n\t{\n\t\tmainLog.println(\"\\nConcrete \" + modelType + \": \" + modelConcrete.infoString());\n\t\tsuper.printFinalSummary(initAbstractionInfo, canRefine);\n\t}\n\n\tpublic static void main(String args[])\n\t{\n\t\t// Parse command line args\n\t\tif (args.length < 2) {\n\t\t\tSystem.err.println(\"Usage: java ... <PRISM model> <target label>\");\n\t\t\tSystem.exit(1);\n\t\t}\n\t\ttry {\n\t\t\t// Load/parse a PRISM model description\n\t\t\tPrismLog mainLog = new PrismPrintStreamLog(System.out);\n\t\t\tPrism prism = new Prism(mainLog);\n\t\t\tModulesFile modulesFile = prism.parseModelFile(new File(args[0]));\n\t\t\tUndefinedConstants undefinedConstants = new UndefinedConstants(modulesFile, null);\n\t\t\tundefinedConstants.defineUsingConstSwitch(\"\");\n\t\t\tmodulesFile.setSomeUndefinedConstants(undefinedConstants.getMFConstantValues());\n\t\t\tmodulesFile = (ModulesFile) modulesFile.deepCopy().expandConstants(modulesFile.getConstantList());\n\t\t\t\n\t\t\t// Build the model (explicit-state reachability) \n\t\t\tConstructModel constructModel = new ConstructModel(prism);\n\t\t\tconstructModel.setBuildSparse(false);\n\t\t\tModelSimple model = (ModelSimple) constructModel.constructModel(new ModulesFileModelGenerator(modulesFile, prism));\n\t\t\tmodel.exportToPrismExplicitTra(args[1]);\n\t\t\t\n\t\t\t// Create/initialise abstraction-refinement engine\n\t\t\tQuantAbstractRefineExample abstractRefine = new QuantAbstractRefineExample(prism);\n\t\t\tabstractRefine.setModelType(ModelType.MDP);\n\t\t\tabstractRefine.setPropertyType(PropertyType.PROB_REACH);\n\t\t\tabstractRefine.sanityChecks = true;\n\t\t\tabstractRefine.modelConcrete = model;\n\t\t\tabstractRefine.modulesFile = modulesFile;\n\t\t\tabstractRefine.targetLabel = args[1];\n\t\t\t\n\t\t\t// Do abstraction-refinement\n\t\t\tabstractRefine.printSettings();\n\t\t\tboolean min = true;\n\t\t\tabstractRefine.abstractRefine(min);\n\t\t\t\n\t\t} catch (FileNotFoundException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/SCCComputer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Christian von Essen <christian.vonessen@imag.fr> (Verimag, Grenoble)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//  * Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.function.Consumer;\nimport java.util.function.IntPredicate;\n\nimport prism.PrismComponent;\nimport prism.PrismException;\n\n/**\n * Abstract class for (explicit) classes that compute (B)SCCs,\n * i.e. (bottom) strongly connected components, for a model's transition graph.\n */\npublic abstract class SCCComputer extends PrismComponent\n{\n\t/** The consumer */\n\tprotected SCCConsumer consumer;\n\n\t// Method used for finding (B)SCCs\n\tpublic enum SCCMethod {\n\t\tTARJAN;\n\t\tpublic String fullName()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\tcase TARJAN:\n\t\t\t\treturn \"Tarjan\";\n\t\t\tdefault:\n\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t};\n\n\t/**\n\t * Static method to create a new SCCComputer object, depending on current settings.\n\t */\n\tpublic static SCCComputer createSCCComputer(PrismComponent parent, Model<?> model, SCCConsumer consumer) throws PrismException\n\t{\n\t\t// Only one algorithm implemented currently\n\t\treturn new SCCComputerTarjan(parent, model, consumer);\n\t}\n\n\t/**\n\t * Compute an SCCInfo data structure (topological ordering).\n\t * @param parent PrismComponent (for settings)\n\t * @param model the model\n\t * @param withTrivialSCCs include trivial SCCs?\n\t */\n\tpublic static SCCInfo computeTopologicalOrdering(PrismComponent parent, Model<?> model, boolean withTrivialSCCs) throws PrismException\n\t{\n\t\treturn computeTopologicalOrdering(parent, model, withTrivialSCCs, null);\n\t}\n\n\t/**\n\t * Compute an SCCInfo data structure (topological ordering).\n\t * <br>\n\t * If {@code restrict != null}, restricts the underlying graph to only those states s\n\t * for which {@code restrict.test(s)} evaluates to true (\"relevant states\").\n\t * Edges to non-relevant states are ignored and the non-relevant\n\t * states are not considered as potential initial states.\n\t * @param parent PrismComponent (for settings)\n\t * @param model the model\n\t * @param withTrivialSCCs include trivial SCCs?\n\t * @param restrict predicate that indicates that a state is relevant ({@code null}: all states are relevant)\n\t */\n\tpublic static SCCInfo computeTopologicalOrdering(PrismComponent parent, Model<?> model, boolean withTrivialSCCs, IntPredicate restrict) throws PrismException\n\t{\n\t\tSCCInfo sccs = new SCCInfo(model.getNumStates());\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(parent, model, sccs);\n\t\t// Compute SCCInfo, possibly including trivial SCCs,\n\t\t// restricted to the sub-graph obtained when only considering\n\t\t// states in restrict (if not-null)\n\t\tsccComputer.computeSCCs(!withTrivialSCCs, restrict);\n\n\t\treturn sccs;\n\t}\n\n\t/**\n\t * Convenience method for functional iteration over the SCCs of a model.\n\t * <br>\n\t * For each non-trivial SCC, the given consumer's accept method is called\n\t * with a BitSet containing the state indizes of the states in the SCC.\n\t * <br>\n\t * Note: The BitSet may be reused during calls to {@code accept}. So,\n\t * if you need to store it, clone it.\n\t *\n\t * @param parent the parent PrismComponent (for access to settings)\n\t * @param model the model\n\t * @param sccConsumer the consumer\n\t */\n\tpublic static void forEachSCC(PrismComponent parent, Model<?> model, Consumer<BitSet> sccConsumer) throws PrismException\n\t{\n\t\t// use consumer that reuses the BitSet\n\t\tSCCComputer sccComputer = createSCCComputer(parent, model, new SCCConsumerBitSet(true) {\n\t\t\t@Override\n\t\t\tpublic void notifyNextSCC(BitSet scc) throws PrismException\n\t\t\t{\n\t\t\t\tsccConsumer.accept(scc);\n\t\t\t}\n\t\t});\n\t\tsccComputer.computeSCCs();\n\t}\n\n\t/**\n\t * Base constructor.\n\t */\n\tpublic SCCComputer(PrismComponent parent, SCCConsumer consumer) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tthis.consumer = consumer;\n\t}\n\n\t/**\n\t * Compute strongly connected components (SCCs) and notify the consumer.\n\t * This will only report non-trivial SCCs\n\t */\n\tpublic void computeSCCs() throws PrismException\n\t{\n\t\tcomputeSCCs(true);\n\t}\n\n\t/**\n\t * Compute strongly connected components (SCCs) and notify the consumer.\n\t * Ignores trivial SCCS if {@code filterTrivialSCCs} is set to true.\n\t */\n\tpublic void computeSCCs(boolean filterTrivialSCCs) throws PrismException\n\t{\n\t\tcomputeSCCs(filterTrivialSCCs, null);\n\t}\n\n\t/**\n\t * Compute strongly connected components (SCCs) and notify the consumer.\n\t * Ignores trivial SCCS if {@code filterTrivialSCCs} is set to true.\n\t * If {@code restrict != null}, restricts the underlying graph to only those states s\n\t * for which {@code restrict.test(s)} evaluates to true (\"relevant states\").\n\t * Edges to non-relevant states are ignored and the non-relevant\n\t * states are not considered as potential initial states.\n\t * @param filterTrivialSCCs ignore trivial SCCs\n\t * @param restrict predicate that indicates that a state is relevant ({@code null}: all states are relevant)\n\t */\n\tpublic abstract void computeSCCs(boolean filterTrivialSCCs, IntPredicate restrictStates) throws PrismException;\n\n\t/**\n\t * Returns true if {@code state}, assumed to be an SCC, is a trivial SCC,\n\t * i.e., has no self lopp.\n\t * @param model the model\n\t * @param state the state index\n\t */\n\tprotected boolean isTrivialSCC(Model<?> model, int state)\n\t{\n\t\t// false if there is a self-loop, i.e., a successor t == state\n\t\treturn !(model.someSuccessorsMatch(state, (t) -> {return t == state;}));\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/SCCComputerTarjan.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Christian von Essen <christian.vonessen@imag.fr> (Verimag, Grenoble)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.LinkedList;\nimport java.util.List;\nimport java.util.function.IntPredicate;\n\nimport prism.PrismComponent;\nimport prism.PrismException;\n\n/**\n * Tarjan's SCC algorithm operating on a Model object.\n */\npublic class SCCComputerTarjan extends SCCComputer\n{\n\t/* The model to compute (B)SCCs for */\n\tprivate Model<?> model;\n\t/* Number of nodes (model states) */\n\tprivate int numNodes;\n\n\t/* Next index to give to a node */\n\tprivate int index = 0;\n\t/* Stack of nodes */\n\tprivate List<Integer> stack = new LinkedList<Integer>();\n\t/* List of nodes in the graph. Invariant: {@code nodeList.get(i).id == i} */\n\tprivate ArrayList<Node> nodeList;\n\t/* Nodes currently on the stack. */\n\tprivate BitSet onStack;\n\t/** Should we filter trivial SCCs? */\n\tprivate boolean filterTrivialSCCs;\n\tprivate IntPredicate restrict;\n\n\t/**\n\t * Build (B)SCC computer for a given model.\n\t */\n\tpublic SCCComputerTarjan(PrismComponent parent, Model<?> model, SCCConsumer consumer) throws PrismException\n\t{\n\t\tsuper(parent, consumer);\n\t\tthis.model = model;\n\t\tthis.numNodes = model.getNumStates();\n\t\tthis.nodeList = new ArrayList<Node>(numNodes);\n\t\tfor (int i = 0; i < numNodes; i++) {\n\t\t\tnodeList.add(new Node(i));\n\t\t}\n\t\tonStack = new BitSet();\n\t}\n\n\t// Methods for SCCComputer interface\n\n\t@Override\n\tpublic void computeSCCs(boolean filterTrivialSCCs, IntPredicate restrict) throws PrismException\n\t{\n\t\tthis.filterTrivialSCCs = filterTrivialSCCs;\n\t\tconsumer.notifyStart(model);\n\t\tthis.restrict = restrict;\n\t\ttarjan();\n\t\tconsumer.notifyDone();\n\t}\n\n\t// SCC Computation\n\n\t/**\n\t * Execute Tarjan's algorithm. Determine maximal strongly connected components\n\t * (SCCS) for the graph of the model and stored in {@code sccs}.\n\t */\n\tpublic void tarjan() throws PrismException\n\t{\n\t\tfor (int i = 0; i < numNodes; i++) {\n\t\t\tif (restrict != null && !restrict.test(i))\n\t\t\t\tcontinue; // skip state if not one of the relevant states\n\t\t\tif (nodeList.get(i).lowlink == -1)\n\t\t\t\ttarjan(i);\n\t\t}\n\n\t}\n\n\tprivate void tarjan(int i) throws PrismException\n\t{\n\t\tfinal Node v = nodeList.get(i);\n\t\tv.index = index;\n\t\tv.lowlink = index;\n\t\tindex++;\n\t\tstack.add(0, i);\n\t\tonStack.set(i);\n\n\t\tboolean hadSelfloop = false;\n\t\tSuccessorsIterator it = model.getSuccessors(i);\n\t\twhile (it.hasNext()) {\n\t\t\tint e = it.nextInt();\n\n\t\t\tif (e == i) {\n\t\t\t\thadSelfloop = true;\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tif (restrict != null && !restrict.test(e)) {\n\t\t\t\tcontinue; // ignore edge to state that is not relevant\n\t\t\t}\n\n\t\t\tNode n = nodeList.get(e);\n\t\t\tif (n.index == -1) {\n\t\t\t\ttarjan(e);\n\t\t\t\tv.lowlink = Math.min(v.lowlink, n.lowlink);\n\t\t\t} else if (onStack.get(e)) {\n\t\t\t\tv.lowlink = Math.min(v.lowlink, n.index);\n\t\t\t}\n\t\t}\n\t\tif (v.lowlink == v.index) {\n\t\t\t// this is a singleton SCC if the top of the stack equals i\n\t\t\tboolean singletonSCC = (stack.get(0) == i);\n\t\t\tif (singletonSCC && filterTrivialSCCs) {\n\t\t\t\tif (!hadSelfloop) { // singleton SCC & no selfloop -> trivial\n\t\t\t\t\tstack.remove(0);\n\t\t\t\t\tonStack.set(i, false);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tint n;\n\t\t\tconsumer.notifyStartSCC();\n\t\t\tdo {\n\t\t\t\tn = stack.remove(0);\n\t\t\t\tonStack.set(n, false);\n\t\t\t\tconsumer.notifyStateInSCC(n);\n\t\t\t} while (n != i);\n\t\t\tconsumer.notifyEndSCC();\n\t\t}\n\t}\n\n\t/**\n\t * A small class wrapping a node.\n\t * It carries extra information necessary for Tarjan's algorithm.\n\t */\n\tprotected static class Node\n\t{\n\t\tpublic int lowlink = -1;\n\t\tpublic int index = -1;\n\t\tpublic int id;\n\n\t\tpublic Node(int id)\n\t\t{\n\t\t\tthis.id = id;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/SCCConsumer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport prism.PrismException;\n\n/**\n * Interface for a consumer of SCC information, for use with an {@code SCCComputer}.\n * When a new SCC is discovered, first {@code notifyStartSCC()} will be called.\n * Subsequently, for each state of the SCC, {@code notifyStateInSCC()} will be called.\n * When all states of the SCC have been notified, {@code notifyEndSCC()} will be called.\n * When the whole SCC computation is finished, {@code notifyDone()} will be called once.\n */\npublic interface SCCConsumer {\n\t/**\n\t * Call-back function, will be called once at the start.\n\t * Default implementation: Ignore.\n\t */\n\tpublic default void notifyStart(Model<?> model)\n\t{\n\t\t// ignore\n\t}\n\n\t/**\n\t * Call-back function, will be called when a new SCC is discovered.\n\t **/\n\tpublic void notifyStartSCC() throws PrismException;\n\n\t/**\n\t * Call-back function, will be called once for each state in the SCC.\n\t */\n\tpublic void notifyStateInSCC(int stateIndex) throws PrismException;\n\n\t/**\n\t * Call-back function, will be called when all states of the SCC have been\n\t * discovered.\n\t **/\n\tpublic void notifyEndSCC() throws PrismException;\n\n\t/**\n\t * Call-back function. Will be called after SCC computation is complete.\n\t */\n\tpublic default void notifyDone() {}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/SCCConsumerBSCCs.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\n\nimport prism.PrismException;\n\n/**\n * Abstract base class for an SCC consumer that is only interested in\n * the bottom strongly-connected components (BSCCs). <br/>\n *\n * Intercepts the {@code notifyNextSCC()} call, checks whether the SCC\n * is a BSCC and calls {@code notifyNextBSCC()} if that is the case.\n */\npublic abstract class SCCConsumerBSCCs extends SCCConsumerBitSet {\n\n\tprotected Model<?> model;\n\n\t/** Constructor */\n\tpublic SCCConsumerBSCCs()\n\t{\n\t\tmodel = null;  // will be set by notifyStart call\n\t}\n\n\tpublic  void notifyStart(Model<?> model)\n\t{\n\t\tthis.model = model;\n\t}\n\n\t/**\n\t * Call-back function. Called upon discovery of a BSCC.\n\t */\n\tpublic abstract void notifyNextBSCC(BitSet bscc) throws PrismException;\n\n\t@Override\n\tpublic void notifyNextSCC(BitSet scc) throws PrismException\n\t{\n\t\tboolean bottom = true;\n\t\t// BSCC <=> for all states s, all successors are again in the SCC.\n\t\tfor (int s = scc.nextSetBit(0); s >= 0; s = scc.nextSetBit(s + 1)) {\n\t\t\tif (!model.allSuccessorsInSet(s, scc)) {\n\t\t\t\tbottom = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\tif (bottom) {\n\t\t\tnotifyNextBSCC(scc);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/SCCConsumerBitSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\n\nimport prism.PrismException;\n\n/**\n * Abstract base class for a consumer of SCC information, for use with an {@code SCCComputer},\n * where each SCC is stored as a BitSet.\n * <br>\n * When a new SCC is discovered, {@code notifyNextSCC()} will be called with a {@code BitSet} of the\n * states in the SCC. When the SCC computation is finished, {@code notifyDone()} will be\n * called once.\n * <br>\n * By default, for each SCC a fresh BitSet is created. If the BitSets that are\n * passed to {@code notifyNextSCC} can be reused for the next call, the {@code reuseBitSet}\n * flag can be set in the constructor.\n */\npublic abstract class SCCConsumerBitSet implements SCCConsumer\n{\n\tprivate BitSet curSCC = null;\n\tprivate boolean reuseBitSet = false;\n\n\t/** Default constructor. Don't reuse the BitSets */\n\tpublic SCCConsumerBitSet()\n\t{\n\t\tthis(false);\n\t}\n\n\t/**\n\t * Constructor. If {@code reuseBitSet} is set, reuse the same BitSet for all\n\t * calls to {@code notifyNextSCC}.\n\t * @param reuseBitSet allow reuse of BitSets\n\t */\n\tpublic SCCConsumerBitSet(boolean reuseBitSet)\n\t{\n\t\tthis.reuseBitSet = reuseBitSet;\n\t\tif (reuseBitSet)\n\t\t\tcurSCC = new BitSet();\n\t}\n\n\t@Override\n\tpublic void notifyStartSCC() throws PrismException\n\t{\n\t\tif (reuseBitSet) {\n\t\t\tcurSCC.clear();\n\t\t} else {\n\t\t\tcurSCC = new BitSet();\n\t\t}\n\t}\n\n\t@Override\n\tpublic void notifyStateInSCC(int stateIndex) throws PrismException\n\t{\n\t\tcurSCC.set(stateIndex);\n\t}\n\n\t@Override\n\tpublic void notifyEndSCC() throws PrismException\n\t{\n\t\tnotifyNextSCC(curSCC);\n\t\tif (!reuseBitSet) {\n\t\t\tcurSCC = null;\n\t\t}\n\t}\n\n\tpublic abstract void notifyNextSCC(BitSet scc) throws PrismException;\n}\n"
  },
  {
    "path": "prism/src/explicit/SCCConsumerStore.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\n/**\n * SCC consumer that stores lists of the discovered SCCs and BSCCs.\n * The list of BSCCs is computed on demand from the list of SCCs.\n */\npublic class SCCConsumerStore extends SCCConsumerBitSet {\n\t/* Computed list of SCCs */\n\tprivate List<BitSet> sccs = new ArrayList<BitSet>();\n\t/* Computed list of BSCCs */\n\tprivate List<BitSet> bsccs;\n\t/* States not in any BSCC */\n\tprivate BitSet notInBSCCs;\n\t/* States not in any SCC */\n\tprivate BitSet notInSCCs;\n\n\t/** Is the SCC computation finished? */\n\tprivate boolean finished = false;\n\n\tprivate Model<?> model;\n\n\t/** Constructor */\n\tpublic SCCConsumerStore()\n\t{\n\t\tmodel = null;  // will be set by notifyStart call\n\t}\n\n\t@Override\n\tpublic void notifyStart(Model<?> model)\n\t{\n\t\tthis.model = model;\n\t}\n\n\t@Override\n\tpublic void notifyNextSCC(BitSet scc)\n\t{\n\t\tsccs.add(scc);\n\t}\n\n\t@Override\n\tpublic void notifyDone()\n\t{\n\t\tfinished = true;\n\t}\n\n\t/**\n\t * Get a list of the SCCs. Can only be called once the SCC computation is finished.\n\t */\n\tpublic List<BitSet> getSCCs()\n\t{\n\t\tif (!finished)\n\t\t\tthrow new UnsupportedOperationException(\"SCC computation is not yet finished.\");\n\n\t\treturn sccs;\n\t}\n\n\t/**\n\t * Get a list of the BSCCs. Can only be called once the SCC computation is finished.\n\t */\n\tpublic List<BitSet> getBSCCs()\n\t{\n\t\tif (!finished)\n\t\t\tthrow new UnsupportedOperationException(\"SCC computation is not yet finished.\");\n\n\t\t// If we don't have the list of BSCCs already, compute it.\n\t\tif (bsccs == null) {\n\t\t\tcomputeBSCCs();\n\t\t}\n\t\treturn bsccs;\n\t}\n\n\t/**\n\t * Get the set of states not in any BSCCs. Can only be called once the SCC computation is finished.\n\t */\n\tpublic BitSet getNotInBSCCs()\n\t{\n\t\tif (!finished)\n\t\t\tthrow new UnsupportedOperationException(\"SCC computation is not yet finished.\");\n\n\t\t// If we don't have the set already, compute it.\n\t\tif (notInBSCCs == null) {\n\t\t\tcomputeBSCCs();\n\t\t}\n\t\treturn notInBSCCs;\n\t}\n\n\t/**\n\t * Compute the list of BSCCs from the list of SCCs.\n\t */\n\tprivate void computeBSCCs()\n\t{\n\t\tif (!finished)\n\t\t\tthrow new UnsupportedOperationException(\"SCC computation is not yet finished.\");\n\n\t\tbsccs = new ArrayList<BitSet>();\n\t\tnotInBSCCs = (BitSet) getNotInSCCs().clone();\n\t\tfor (BitSet scc : sccs) {\n\t\t\tboolean bottom = true;\n\t\t\t// BSCC <=> for all states s, all successors are again in SCC\n\t\t\tfor (int s = scc.nextSetBit(0); s >= 0; s = scc.nextSetBit(s + 1)) {\n\t\t\t\tif (!model.allSuccessorsInSet(s, scc)) {\n\t\t\t\t\tbottom = false;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (bottom)\n\t\t\t\t// store SCC as a BSCC\n\t\t\t\tbsccs.add(scc);\n\t\t\telse\n\t\t\t\t// add states in scc to notInBSCCs\n\t\t\t\tnotInBSCCs.or(scc);\n\t\t}\n\t}\n\n\tpublic BitSet getNotInSCCs()\n\t{\n\t\tif (!finished)\n\t\t\tthrow new UnsupportedOperationException(\"SCC computation is not yet finished.\");\n\n\t\tif (notInSCCs != null) {\n\t\t\treturn notInSCCs;\n\t\t}\n\t\tBitSet result = new BitSet();\n\t\tfor (BitSet scc : getSCCs()) {\n\t\t\tresult.or(scc);\n\t\t}\n\t\tresult.flip(0, model.getNumStates());\n\t\tnotInSCCs = result;\n\t\treturn notInSCCs;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/SCCInfo.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Arrays;\nimport java.util.PrimitiveIterator;\n\nimport common.IntSet;\nimport common.iterable.FunctionalPrimitiveIterator;\nimport prism.PrismLog;\n\n/**\n * Storage of the SCC information, with a topological order of the SCCs.\n * <br>\n * Provides IntSet-based access to the states in the SCCs.\n */\npublic class SCCInfo implements SCCConsumer\n{\n\t/** The number of states in the model */\n\tprivate int numStates;\n\t/** List of state indizes, in order of SCC membership */\n\tprivate int[] stateList;\n\t/** Index into stateList: sccEnd[i] points to the last state in the SCC */\n\tprivate int[] sccEnd;\n\t/** Mapping from state index to the SCC index */\n\tprivate int[] stateToSCCIndex;\n\t/** Number of SCCs that are stored */\n\tprivate int storedSCCCount;\n\t/** Number of states that are stored */\n\tprivate int storedStateCount;\n\n\t/**\n\t * Constructor.\n\t *\n\t * @param numStates number of states in the model (used for allocating data structures)\n\t */\n\tpublic SCCInfo(int numStates) {\n\t\tthis.numStates = numStates;\n\t\tstateList = new int[numStates];\n\t\tsccEnd = new int[numStates];\n\t\tstateToSCCIndex = new int[numStates];\n\t\tArrays.fill(stateToSCCIndex, -1);\n\t\tstoredSCCCount = 0;\n\t\tstoredStateCount = 0;\n\t}\n\n\t/** SCCConsumer interface: Notification about start of SCC */\n\t@Override\n\tpublic void notifyStartSCC()\n\t{\n\t}\n\n\t/** SCCConsumer interface: Notification about end of SCC */\n\tpublic void notifyEndSCC()\n\t{\n\t\t// store index of last state of SCC\n\t\tint curSCC = storedSCCCount;\n\t\tsccEnd[curSCC] = storedStateCount - 1;\n\t\tstoredSCCCount++;\n\t}\n\n\t/** SCCConsumer interface: Notification about state in SCC */\n\tpublic void notifyStateInSCC(int stateIndex)\n\t{\n\t\tint curSCC = storedSCCCount;\n\t\tstateList[storedStateCount] = stateIndex;\n\t\tstateToSCCIndex[stateIndex] = curSCC;\n\t\tstoredStateCount++;\n\t}\n\n\t/** Returns the number of SCCs */\n\tpublic int getNumSCCs()\n\t{\n\t\treturn storedSCCCount;\n\t}\n\n\t/** Compute and return the number of SCCs with at least 2 states. */\n\tpublic int countNonSingletonSCCs()\n\t{\n\t\tint nonSingletonSCCs = 0;\n\t\tfor (int i = 0; i < getNumSCCs(); i++) {\n\t\t\tif (!isSingletonSCC(i)) {\n\t\t\t\tnonSingletonSCCs++;\n\t\t\t}\n\t\t}\n\t\treturn nonSingletonSCCs;\n\t}\n\n\t/** Returns the number of states in the SCC with index {@code sccIndex} */\n\tpublic int getNumStatesInSCC(int sccIndex)\n\t{\n\t\tcheckSCCIndex(sccIndex);\n\t\treturn endOfSCC(sccIndex) - startOfSCC(sccIndex) + 1;\n\t}\n\n\t/** Returns true if the given SCC is a singleton SCC */\n\tpublic boolean isSingletonSCC(int sccIndex)\n\t{\n\t\tcheckSCCIndex(sccIndex);\n\t\treturn getNumStatesInSCC(sccIndex) == 1;\n\t}\n\n\t/**\n\t * Returns the index of the SCC containing the given state,\n\t * or -1 if the state does not belong to an SCC.\n\t */\n\tpublic int getSCCIndex(int stateIndex)\n\t{\n\t\tcheckStateIndex(stateIndex);\n\t\treturn stateToSCCIndex[stateIndex];\n\t}\n\n\t/** Returns an IntSet for the states in the given SCC */\n\tpublic IntSet getStatesForSCC(final int sccIndex)\n\t{\n\t\tcheckSCCIndex(sccIndex);\n\n\t\tfinal int start = startOfSCC(sccIndex);\n\t\tfinal int end = endOfSCC(sccIndex);\n\n\t\treturn new IntSet() {\n\n\t\t\t@Override\n\t\t\tpublic FunctionalPrimitiveIterator.OfInt iterator()\n\t\t\t{\n\t\t\t\treturn new FunctionalPrimitiveIterator.OfInt() {\n\t\t\t\t\tint cur = start;\n\n\t\t\t\t\t@Override\n\t\t\t\t\tpublic boolean hasNext()\n\t\t\t\t\t{\n\t\t\t\t\t\treturn cur <= end;\n\t\t\t\t\t}\n\n\t\t\t\t\t@Override\n\t\t\t\t\tpublic int nextInt()\n\t\t\t\t\t{\n\t\t\t\t\t\treturn stateList[cur++];\n\t\t\t\t\t}\n\t\t\t\t};\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic FunctionalPrimitiveIterator.OfInt reversedIterator()\n\t\t\t{\n\t\t\t\treturn new FunctionalPrimitiveIterator.OfInt() {\n\t\t\t\t\tint cur = end;\n\n\t\t\t\t\t@Override\n\t\t\t\t\tpublic boolean hasNext()\n\t\t\t\t\t{\n\t\t\t\t\t\treturn cur >= start;\n\t\t\t\t\t}\n\n\t\t\t\t\t@Override\n\t\t\t\t\tpublic int nextInt()\n\t\t\t\t\t{\n\t\t\t\t\t\treturn stateList[cur--];\n\t\t\t\t\t}\n\t\t\t\t};\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic long count()\n\t\t\t{\n\t\t\t\treturn getNumStatesInSCC(sccIndex);\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean contains(int stateIndex)\n\t\t\t{\n\t\t\t\tint sccForState = getSCCIndex(stateIndex);\n\t\t\t\treturn sccForState == sccIndex;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic String toString()\n\t\t\t{\n\t\t\t\treturn asString();\n\t\t\t}\n\t\t};\n\t}\n\n\t/** Prints the SCC info to the log */\n\tpublic void print(PrismLog log)\n\t{\n\t\tfor (int scc = 0; scc < getNumSCCs(); scc++) {\n\t\t\tlog.println(\"SCC \" + scc + \" (\" + getNumStatesInSCC(scc) + \"):\");\n\t\t\tfor (PrimitiveIterator.OfInt states = getStatesForSCC(scc).iterator(); states.hasNext();) {\n\t\t\t\tint state = states.nextInt();\n\t\t\t\tlog.print(\" \");\n\t\t\t\tlog.print(state);\n\t\t\t}\n\t\t\tlog.println();\n\t\t}\n\t}\n\n\tprivate void checkStateIndex(int stateIndex)\n\t{\n\t\tif (stateIndex < 0 || stateIndex >= numStates)\n\t\t\tthrow new IllegalArgumentException(\"SCCInfo: State index \" + stateIndex + \" is out of range\");\n\t}\n\n\tprivate void checkSCCIndex(int sccIndex)\n\t{\n\t\tif (sccIndex < 0 || sccIndex >= storedSCCCount)\n\t\t\tthrow new IllegalArgumentException(\"SCCInfo: SCC index \" + sccIndex + \" is out of range\");\n\t}\n\n\t/** Compute the index in stateList of the first state in the given SCC */\n\tprivate int startOfSCC(int sccIndex)\n\t{\n\t\tif (sccIndex == 0) {\n\t\t\treturn 0;\n\t\t} else {\n\t\t\treturn sccEnd[sccIndex - 1] + 1;\n\t\t}\n\t}\n\n\t/** Compute the index in stateList of the last state in the given SCC */\n\tprivate int endOfSCC(int sccIndex)\n\t{\n\t\treturn sccEnd[sccIndex];\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/STPG.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\n\nimport explicit.graphviz.StateOwnerDecorator;\nimport explicit.rewards.STPGRewards;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismUtils;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state stochastic two-player game (STPG).\n * <br><br>\n * These are turn-based STPGs, i.e. at most one player controls each state.\n * Probabilistic states do not need to be stored explicitly; instead, like in an MDP,\n * players have several 'choices', each of which is a probability distribution over successor states.\n */\npublic interface STPG<Value> extends MDP<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tdefault ModelType getModelType()\n\t{\n\t\treturn ModelType.STPG;\n\t}\n\n\t@Override\n\tdefault void exportToDotFile(PrismLog out, Iterable<explicit.graphviz.Decorator> decorators, int precision) throws PrismException\n\t{\n\t\t// Copy any existing decorators\n\t\tList<explicit.graphviz.Decorator> decoratorsNew = new ArrayList<>();\n\t\tif (decorators != null) {\n\t\t\tfor (explicit.graphviz.Decorator decorator : decorators) {\n\t\t\t\tdecoratorsNew.add(decorator);\n\t\t\t}\n\t\t}\n\t\t// And add a new one that draws states according to player owner\n\t\tdecoratorsNew.add(new StateOwnerDecorator(this::getPlayer));\n\t\tMDP.super.exportToDotFile(out, decoratorsNew, precision);\n\t}\n\t\n\t@Override\n\tdefault void exportToPrismLanguage(final String filename, int precision) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\t\n\t// Accessors\n\t\n\t/**\n\t * Get the player that owns state {@code s}.\n\t * Returns the index of the player (0-indexed).\n\t * @param s Index of state (0-indexed)\n\t */\n\tpublic int getPlayer(int s);\n\t\n\t/**\n\t * Perform a single step of precomputation algorithm Prob0, i.e., for states i in {@code subset},\n\t * set bit i of {@code result} iff, for all/some player 1 choices, for all/some player 2 choices,\n\t * there is a transition to a state in {@code u}.\n\t * Quantification over player 1/2 choices is determined by {@code forall1}, {@code forall2}.\n\t * @param subset Only compute for these states\n\t * @param u Set of states {@code u}\n\t * @param forall1 For-all or there-exists for player 1 (true=for-all, false=there-exists)\n\t * @param forall2 For-all or there-exists for player 2 (true=for-all, false=there-exists)\n\t * @param result Store results here\n\t */\n\tpublic void prob0step(BitSet subset, BitSet u, boolean forall1, boolean forall2, BitSet result);\n\n\t/**\n\t * Perform a single step of precomputation algorithm Prob1, i.e., for states i in {@code subset},\n\t * set bit i of {@code result} iff, for all/some player 1 choices, for all/some player 2 choices,\n\t * there is a transition to a state in {@code v} and all transitions go to states in {@code u}.\n\t * Quantification over player 1/2 choices is determined by {@code forall1}, {@code forall2}.\n\t * @param subset Only compute for these states\n\t * @param u Set of states {@code u}\n\t * @param v Set of states {@code v}\n\t * @param forall1 For-all or there-exists for player 1 (true=for-all, false=there-exists)\n\t * @param forall2 For-all or there-exists for player 2 (true=for-all, false=there-exists)\n\t * @param result Store results here\n\t */\n\tpublic void prob1step(BitSet subset, BitSet u, BitSet v, boolean forall1, boolean forall2, BitSet result);\n\n\t/**\n\t * Do a matrix-vector multiplication followed by two min/max ops, i.e. one step of value iteration,\n\t * i.e. for all s: result[s] = min/max_{k1,k2} { sum_j P_{k1,k2}(s,j)*vect[j] }\n\t * @param vect Vector to multiply by\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param adv Storage for adversary choice indices (ignored if null)\n\t */\n\tpublic void mvMultMinMax(double vect[], boolean min1, boolean min2, double result[], BitSet subset, boolean complement, int adv[]);\n\n\t/**\n\t * Do a single row of matrix-vector multiplication followed by min/max,\n\t * i.e. return min/max_{k1,k2} { sum_j P_{k1,k2}(s,j)*vect[j] }\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t */\n\tpublic double mvMultMinMaxSingle(int s, double vect[], boolean min1, boolean min2);\n\n\t/**\n\t * Determine which choices result in min/max after a single row of matrix-vector multiplication.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t * @param val Min or max value to match\n\t */\n\tpublic List<Integer> mvMultMinMaxSingleChoices(int s, double vect[], boolean min1, boolean min2, double val);\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication followed by min/max.\n\t * i.e. for all s: vect[s] = min/max_{k1,k2} { (sum_{j!=s} P_{k1,k2}(s,j)*vect[j]) / P_{k1,k2}(s,s) }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * @param vect Vector to multiply by (and store the result in)\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t * @return The maximum difference between old/new elements of {@code vect}\n\t */\n\tpublic double mvMultGSMinMax(double vect[], boolean min1, boolean min2, BitSet subset, boolean complement, boolean absolute, int adv[]);\n\n\t/**\n\t * Do a single row of Jacobi-style matrix-vector multiplication followed by min/max.\n\t * i.e. return min/max_{k1,k2} { (sum_{j!=s} P_{k1,k2}(s,j)*vect[j]) / P_{k1,k2}(s,s) }\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t */\n\tpublic double mvMultJacMinMaxSingle(int s, double vect[], boolean min1, boolean min2, int[] adv);\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of action reward followed by min/max, i.e. one step of value iteration.\n\t * i.e. for all s: result[s] = min/max_{k1,k2} { rew(s) + sum_j P_{k1,k2}(s,j)*vect[j] }\n\t * @param vect Vector to multiply by\n\t * @param rewards The rewards\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param adv Storage for adversary choice indices (ignored if null)\n\t */\n\tpublic void mvMultRewMinMax(double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, double result[], BitSet subset, boolean complement, int adv[]);\n\n\t/**\n\t * Do a single row of matrix-vector multiplication and sum of action reward followed by min/max.\n\t * i.e. return min/max_{k1,k2} { rew(s) + sum_j P_{k1,k2}(s,j)*vect[j] }\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param rewards The rewards\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t * @param adv Storage for adversary choice indices (ignored if null)\n\t */\n\tpublic double mvMultRewMinMaxSingle(int s, double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, int adv[]);\n\n\t/**\n\t * Determine which choices result in min/max after a single row of matrix-vector multiplication and sum of action reward.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param rewards The rewards\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t * @param val Min or max value to match\n\t */\n\tpublic List<Integer> mvMultRewMinMaxSingleChoices(int s, double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, double val);\n\n\t/**\n\t * Do a single row of (discounted) matrix-vector multiplication and sum of action reward followed by min/max.\n\t * i.e. return min/max_{k1,k2} { rew(s) + sum_j P_{k1,k2}(s,j)*vect[j] }\n\t * @param vect Vector to multiply by\n\t * @param rewards The rewards\n\t * @param min1 Min or max for player 1 (true=min, false=max)\n\t * @param min2 Min or max for player 2 (true=min, false=max)\n\t * @param adv Storage for adversary choice indices (ignored if null)\n\t * @param disc Discount factor\n\t */\n\tvoid mvMultRewMinMax(double[] vect, STPGRewards<Double> rewards, boolean min1, boolean min2, double[] result, BitSet subset, boolean complement, int[] adv, double disc);\n\n\t/**\n\t * Checks  whether all successors of action c in state s are in a given set\n\t * @param s state\n\t * @param c choice\n\t * @param set target set\n\t * @return true if all successors are, false otherwise\n\t */\n\tpublic boolean allSuccessorsInSet(int s, int c, BitSet set);\n}\n"
  },
  {
    "path": "prism/src/explicit/STPGAbstrSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.BufferedReader;\nimport java.io.File;\nimport java.io.FileReader;\nimport java.io.IOException;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Map.Entry;\n\nimport common.IterableStateSet;\nimport explicit.rewards.STPGRewards;\nimport explicit.rewards.STPGRewardsNestedSimple;\nimport prism.PrismException;\nimport prism.PrismUtils;\nimport strat.MDStrategy;\n\n/**\n * Simple explicit-state representation of a stochastic two-player game (STPG),\n * as used for abstraction of MDPs, i.e. with strict cycling between player 1,\n * player 2 and probabilistic states. Thus, we store this a set of sets of\n * distributions for each state. This means that the player 2 states are not true\n * states, i.e. they don't count for statistics and player 1 states are treated\n * as successors of each other.\n * <br><br>\n * For this reason, methods to provide direct access transitions in an {@link STPG}\n * ({@link #getNumChoices(int)}, {@link #getAction(int, int)} and {@link #getTransitionsIterator(int, int)})\n * are not supported and \"nested\" variants are provided instead.\n * If the {@code i}th choice of state {@code s} is nested (always true for this class),\n * then {@link #isChoiceNested(int, int)} is true and transition info is available via methods\n * Use {@link #getNumNestedChoices(int, int)}, {@link #getNestedAction(int, int, int)}\n * and {@link #getNestedTransitionsIterator(int, int, int)}.\n */\npublic class STPGAbstrSimple<Value> extends ModelExplicit<Value> implements STPG<Value>, NondetModelSimple<Value>\n{\n\t// Transition function (Steps)\n\tprotected List<ArrayList<DistributionSet<Value>>> trans;\n\n\t// Flag: allow dupes in distribution sets?\n\tpublic boolean allowDupes = false;\n\n\t// Other statistics\n\tprotected int numDistrSets;\n\tprotected int numDistrs;\n\tprotected int numTransitions;\n\tprotected int maxNumDistrSets;\n\tprotected int maxNumDistrs;\n\n\t/**\n\t * Constructor: empty STPG.\n\t */\n\tpublic STPGAbstrSimple()\n\t{\n\t\tinitialise(0);\n\t}\n\n\t/**\n\t * Constructor: new STPG with fixed number of states.\n\t */\n\tpublic STPGAbstrSimple(int numStates)\n\t{\n\t\tinitialise(numStates);\n\t}\n\n\t/**\n\t * Constructor: build an STPG from an MDP.\n\t * Data is copied directly from the MDP so take a copy first if you plan to keep/modify the MDP.\n\t */\n\tpublic STPGAbstrSimple(MDPSimple<Value> m)\n\t{\n\t\tDistributionSet<Value> set;\n\t\tint i;\n\t\t// TODO: actions?\n\t\tinitialise(m.getNumStates());\n\t\tcopyFrom(m);\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tset = newDistributionSet(null);\n\t\t\tset.addAll(m.getChoices(i));\n\t\t\taddDistributionSet(i, set);\n\t\t}\n\t}\n\n\t// Mutators (for ModelSimple)\n\n\t@Override\n\tpublic void initialise(int numStates)\n\t{\n\t\tsuper.initialise(numStates);\n\t\tnumDistrSets = numDistrs = numTransitions = 0;\n\t\tmaxNumDistrSets = maxNumDistrs = 0;\n\t\ttrans = new ArrayList<ArrayList<DistributionSet<Value>>>(numStates);\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\ttrans.add(new ArrayList<>());\n\t\t}\n\t}\n\n\t@Override\n\tpublic void clearState(int i)\n\t{\n\t\t// Do nothing if state does not exist\n\t\tif (i >= numStates || i < 0)\n\t\t\treturn;\n\t\t// Clear data structures and update stats\n\t\tList<DistributionSet<Value>> list = trans.get(i);\n\t\tnumDistrSets -= list.size();\n\t\tfor (DistributionSet<Value> set : list) {\n\t\t\tnumDistrs -= set.size();\n\t\t\tfor (Distribution<Value> distr : set)\n\t\t\t\tnumTransitions -= distr.size();\n\t\t}\n\t\t//TODO: recompute maxNumDistrSets\n\t\t//TODO: recompute maxNumDistrs\n\t\t// Remove all distribution sets\n\t\ttrans.set(i, new ArrayList<>(0));\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t@Override\n\tpublic int addState()\n\t{\n\t\taddStates(1);\n\t\treturn numStates - 1;\n\t}\n\n\t@Override\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tfor (int i = 0; i < numToAdd; i++) {\n\t\t\ttrans.add(new ArrayList<>());\n\t\t}\n\t\tnumStates += numToAdd;\n\t}\n\n\t@Override\n\tpublic void buildFromPrismExplicit(String filename) throws PrismException\n\t{\n\t\tBufferedReader in;\n\t\tDistribution<Value> distr;\n\t\tDistributionSet<Value> distrs;\n\t\tString s, ss[];\n\t\tint i, j, k1, k2, iLast, k1Last, k2Last, n, lineNum = 0;\n\n\t\ttry {\n\t\t\t// Open file\n\t\t\tin = new BufferedReader(new FileReader(new File(filename)));\n\t\t\t// Parse first line to get num states\n\t\t\ts = in.readLine();\n\t\t\tlineNum = 1;\n\t\t\tif (s == null) {\n\t\t\t\tin.close();\n\t\t\t\tthrow new PrismException(\"Missing first line of .tra file\");\n\t\t\t}\n\t\t\tss = s.split(\" \");\n\t\t\tn = Integer.parseInt(ss[0]);\n\t\t\t// Initialise\n\t\t\tinitialise(n);\n\t\t\t// Go though list of transitions in file\n\t\t\tiLast = -1;\n\t\t\tk1Last = -1;\n\t\t\tk2Last = -1;\n\t\t\tdistrs = null;\n\t\t\tdistr = null;\n\t\t\ts = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\ts = s.trim();\n\t\t\t\tif (s.length() > 0) {\n\t\t\t\t\tss = s.split(\" \");\n\t\t\t\t\ti = Integer.parseInt(ss[0]);\n\t\t\t\t\tk1 = Integer.parseInt(ss[1]);\n\t\t\t\t\tk2 = Integer.parseInt(ss[2]);\n\t\t\t\t\tj = Integer.parseInt(ss[3]);\n\t\t\t\t\tValue prob = getEvaluator().fromString(ss[4]);\n\t\t\t\t\t// For a new state or distribution set or distribution\n\t\t\t\t\tif (i != iLast || k1 != k1Last || k2 != k2Last) {\n\t\t\t\t\t\t// Add any previous distribution to the last set, create new one\n\t\t\t\t\t\tif (distrs != null) {\n\t\t\t\t\t\t\tdistrs.add(distr);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tdistr = new Distribution<>(getEvaluator());\n\t\t\t\t\t\t// Only for a new state or distribution set...\n\t\t\t\t\t\tif (i != iLast || k1 != k1Last) {\n\t\t\t\t\t\t\t// Add any previous distribution set to the last state, create new one\n\t\t\t\t\t\t\tif (distrs != null) {\n\t\t\t\t\t\t\t\taddDistributionSet(iLast, distrs);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tdistrs = newDistributionSet(null);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Add transition to the current distribution\n\t\t\t\t\tdistr.add(j, prob);\n\t\t\t\t\t// Prepare for next iter\n\t\t\t\t\tiLast = i;\n\t\t\t\t\tk1Last = k1;\n\t\t\t\t\tk2Last = k2;\n\t\t\t\t}\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t\t// Add previous distribution to the last set\n\t\t\tdistrs.add(distr);\n\t\t\t// Add previous distribution set to the last state\n\t\t\taddDistributionSet(iLast, distrs);\n\t\t\t// Close file\n\t\t\tin.close();\n\t\t\tactionList.markNeedsRecomputing();\n\t\t} catch (IOException e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Problem in .tra file (line \" + lineNum + \") for \" + getModelType());\n\t\t}\n\t}\n\n\t// Mutators (other)\n\n\t/**\n\t * Creates a new distribution set suitable for passing to addDistributionSet(...)\n\t * i.e. a data structure consistent with the internals of the this class.\n\t * An optional action label (any Object type) can be specified; null if not needed.\n\t */\n\tpublic DistributionSet<Value> newDistributionSet(Object action)\n\t{\n\t\treturn new DistributionSet<>(action);\n\t}\n\n\t/**\n\t * Add distribution set 'newSet' to state s (which must exist).\n\t * Distribution set is only actually added if it does not already exists for state s.\n\t * (Assuming 'allowDupes' flag is not enabled.)\n\t * Returns the index of the (existing or newly added) set.\n\t * Returns -1 in case of error.\n\t */\n\tpublic int addDistributionSet(int s, DistributionSet<Value> newSet)\n\t{\n\t\tArrayList<DistributionSet<Value>> set;\n\t\t// Check state exists\n\t\tif (s >= numStates || s < 0)\n\t\t\treturn -1;\n\t\t// Add distribution set (if new)\n\t\tset = trans.get(s);\n\t\tif (!allowDupes) {\n\t\t\tint i = set.indexOf(newSet);\n\t\t\tif (i != -1)\n\t\t\t\treturn i;\n\t\t}\n\t\tset.add(newSet);\n\t\t// Update stats\n\t\tnumDistrSets++;\n\t\tmaxNumDistrSets = Math.max(maxNumDistrSets, set.size());\n\t\tnumDistrs += newSet.size();\n\t\tmaxNumDistrs = Math.max(maxNumDistrs, newSet.size());\n\t\tfor (Distribution<Value> distr : newSet)\n\t\t\tnumTransitions += distr.size();\n\t\tactionList.markNeedsRecomputing();\n\t\treturn set.size() - 1;\n\t}\n\n\t// Accessors (for ModelSimple)\n\n\t@Override\n\tpublic int getNumTransitions()\n\t{\n\t\treturn numTransitions;\n\t}\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int s)\n\t{\n\t\t// Need to build set to avoid duplicates\n\t\t// So not necessarily the fastest method to access successors\n\t\tHashSet<Integer> succs = new HashSet<Integer>();\n\t\tfor (DistributionSet<Value> distrs : trans.get(s)) {\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\tsuccs.addAll(distr.getSupport());\n\t\t\t}\n\t\t}\n\t\treturn succs.iterator();\n\t}\n\n\t@Override\n\tpublic boolean isSuccessor(int s1, int s2)\n\t{\n\t\tfor (DistributionSet<Value> distrs : trans.get(s1)) {\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\tif (distr.contains(s2))\n\t\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean allSuccessorsInSet(int s, BitSet set)\n\t{\n\t\tfor (DistributionSet<Value> distrs : trans.get(s)) {\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\tif (!distr.isSubsetOf(set))\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean someSuccessorsInSet(int s, BitSet set)\n\t{\n\t\tfor (DistributionSet<Value> distrs : trans.get(s)) {\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\tif (distr.isSubsetOf(set))\n\t\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tint fixed = 0;\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t// Note that no distributions is a deadlock, not an empty distribution\n\t\t\tif (trans.get(i).isEmpty()) {\n\t\t\t\taddDeadlockState(i);\n\t\t\t\tif (fix) {\n\t\t\t\t\tDistributionSet<Value> distrs = newDistributionSet(null);\n\t\t\t\t\tDistribution<Value> distr = new Distribution<>(getEvaluator());\n\t\t\t\t\tdistr.add(i, getEvaluator().one());\n\t\t\t\t\tdistrs.add(distr);\n\t\t\t\t\taddDistributionSet(i, distrs);\n\t\t\t\t\tfixed++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Add the empty action (if missing), regardless of whether actionList needs recomputing\n\t\tif (fixed > 0) {\n\t\t\tactionList.addAction(null);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (trans.get(i).isEmpty() && (except == null || !except.get(i)))\n\t\t\t\tthrow new PrismException(\"STPG has a deadlock in state \" + i);\n\t\t}\n\t\t// TODO: Check for empty distributions sets too?\n\t}\n\n\t@Override\n\tpublic String infoString()\n\t{\n\t\tString s = \"\";\n\t\ts += numStates + \" states (\" + getNumInitialStates() + \" initial)\";\n\t\ts += \", \" + numTransitions + \" transitions\";\n\t\ts += \", \" + numDistrs + \" choices\";\n\t\ts += \", \" + numDistrSets + \" choice sets\";\n\t\ts += \", p1max/avg = \" + maxNumDistrSets + \"/\" + PrismUtils.formatDouble2dp(((double) numDistrSets) / numStates);\n\t\ts += \", p2max/avg = \" + maxNumDistrs + \"/\" + PrismUtils.formatDouble2dp(((double) numDistrs) / numDistrSets);\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic String infoStringTable()\n\t{\n\t\tString s = \"\";\n\t\ts += \"States:      \" + numStates + \" (\" + getNumInitialStates() + \" initial)\\n\";\n\t\ts += \"Transitions: \" + numTransitions + \"\\n\";\n\t\ts += \"Choices:     \" + numDistrs + \"\\n\";\n\t\ts += \"P1 max/avg:  \" + maxNumDistrSets + \"/\" + PrismUtils.formatDouble2dp(((double) numDistrSets) / numStates) + \"\\n\";\n\t\ts += \"P2 max/avg:  \" + maxNumDistrs + \"/\" + PrismUtils.formatDouble2dp(((double) numDistrs) / numDistrSets) + \"\\n\";\n\t\treturn s;\n\t}\n\n\t// Accessors (for NondetModel)\n\n\t@Override\n\tpublic int getNumChoices(int s)\n\t{\n\t\treturn trans.get(s).size();\n\t}\n\n\t@Override\n\tpublic int getMaxNumChoices()\n\t{\n\t\treturn maxNumDistrSets;\n\t}\n\n\t@Override\n\tpublic int getNumChoices()\n\t{\n\t\treturn numDistrSets;\n\t}\n\n\t@Override\n\tpublic Object getAction(int s, int i)\n\t{\n\t\t// No actions stored currently\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic boolean allSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn trans.get(s).get(i).isSubsetOf(set);\n\t}\n\n\t@Override\n\tpublic boolean someSuccessorsInSet(int s, int i, BitSet set)\n\t{\n\t\treturn trans.get(s).get(i).containsOneOf(set);\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(final int s, final int i)\n\t{\n\t\treturn SuccessorsIterator.chain(new Iterator<SuccessorsIterator>() {\n\t\t\tprivate Iterator<Distribution<Value>> iterator = trans.get(s).get(i).iterator();\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn iterator.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic SuccessorsIterator next()\n\t\t\t{\n\t\t\t\tDistribution<Value> dist = iterator.next();\n\t\t\t\treturn SuccessorsIterator.from(dist.getSupport().iterator(), true);\n\t\t\t}\n\t\t});\n\t}\n\n\t// Accessors (for STPG)\n\n\t@Override\n\tpublic int getPlayer(int s)\n\t{\n\t\t// All states are player 1\n\t\treturn 1;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s, int i)\n\t{\n\t\t// All choices are nested\n\t\treturn 0;\n\t}\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(int s, int i)\n\t{\n\t\t// All choices are nested\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic Model<Value> constructInducedModel(MDStrategy<Value> strat)\n\t{\n\t\tthrow new RuntimeException(\"Not implemented\");\n\t}\n\t\n\t@Override\n\tpublic void prob0step(BitSet subset, BitSet u, boolean forall1, boolean forall2, BitSet result)\n\t{\n\t\tboolean b1, b2, b3;\n\t\tfor (int i : new IterableStateSet(subset, numStates)) {\n\t\t\tb1 = forall1; // there exists or for all player 1 choices\n\t\t\tfor (DistributionSet<Value> distrs : trans.get(i)) {\n\t\t\t\tb2 = forall2; // there exists or for all player 2 choices\n\t\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\t\tb3 = distr.containsOneOf(u);\n\t\t\t\t\tif (forall2) {\n\t\t\t\t\t\tif (!b3)\n\t\t\t\t\t\t\tb2 = false;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (b3)\n\t\t\t\t\t\t\tb2 = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (forall1) {\n\t\t\t\t\tif (!b2)\n\t\t\t\t\t\tb1 = false;\n\t\t\t\t} else {\n\t\t\t\t\tif (b2)\n\t\t\t\t\t\tb1 = true;\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.set(i, b1);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void prob1step(BitSet subset, BitSet u, BitSet v, boolean forall1, boolean forall2, BitSet result)\n\t{\n\t\tboolean b1, b2, b3;\n\t\tfor (int i : new IterableStateSet(subset, numStates)) {\n\t\t\tb1 = forall1; // there exists or for all player 1 choices\n\t\t\tfor (DistributionSet<Value> distrs : trans.get(i)) {\n\t\t\t\tb2 = forall2; // there exists or for all player 2 choices\n\t\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\t\tb3 = distr.containsOneOf(v) && distr.isSubsetOf(u);\n\t\t\t\t\tif (forall2) {\n\t\t\t\t\t\tif (!b3)\n\t\t\t\t\t\t\tb2 = false;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (b3)\n\t\t\t\t\t\t\tb2 = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (forall1) {\n\t\t\t\t\tif (!b2)\n\t\t\t\t\t\tb1 = false;\n\t\t\t\t} else {\n\t\t\t\t\tif (b2)\n\t\t\t\t\t\tb1 = true;\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.set(i, b1);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void mvMultMinMax(double vect[], boolean min1, boolean min2, double result[], BitSet subset, boolean complement, int adv[])\n\t{\n\t\tfor (int s : new IterableStateSet(subset, numStates, complement)) {\n\t\t\tresult[s] = mvMultMinMaxSingle(s, vect, min1, min2);\n\t\t}\n\t}\n\n\t@Override\n\tpublic double mvMultMinMaxSingle(int s, double vect[], boolean min1, boolean min2)\n\t{\n\t\tint k;\n\t\tdouble d, prob, minmax1, minmax2;\n\t\tboolean first1, first2;\n\t\tArrayList<DistributionSet<Value>> step;\n\n\t\tminmax1 = 0;\n\t\tfirst1 = true;\n\t\tstep = trans.get(s);\n\t\tfor (DistributionSet<Value> distrs : step) {\n\t\t\tminmax2 = 0;\n\t\t\tfirst2 = true;\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\t// Compute sum for this distribution\n\t\t\t\td = 0.0;\n\t\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\t\tk = e.getKey();\n\t\t\t\t\tprob = getEvaluator().toDouble(e.getValue());\n\t\t\t\t\td += prob * vect[k];\n\t\t\t\t}\n\t\t\t\t// Check whether we have exceeded min/max so far\n\t\t\t\tif (first2 || (min2 && d < minmax2) || (!min2 && d > minmax2))\n\t\t\t\t\tminmax2 = d;\n\t\t\t\tfirst2 = false;\n\t\t\t}\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first1 || (min1 && minmax2 < minmax1) || (!min1 && minmax2 > minmax1))\n\t\t\t\tminmax1 = minmax2;\n\t\t\tfirst1 = false;\n\t\t}\n\n\t\treturn minmax1;\n\t}\n\n\t@Override\n\tpublic List<Integer> mvMultMinMaxSingleChoices(int s, double vect[], boolean min1, boolean min2, double val)\n\t{\n\t\tint j, k;\n\t\tdouble d, prob, minmax2;\n\t\tboolean first2;\n\t\tList<Integer> res;\n\t\tArrayList<DistributionSet<Value>> step;\n\n\t\t// Create data structures to store strategy\n\t\tres = new ArrayList<Integer>();\n\t\t// One row of matrix-vector operation \n\t\tj = -1;\n\t\tstep = trans.get(s);\n\t\tfor (DistributionSet<Value> distrs : step) {\n\t\t\tj++;\n\t\t\tminmax2 = 0;\n\t\t\tfirst2 = true;\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\t// Compute sum for this distribution\n\t\t\t\td = 0.0;\n\t\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\t\tk = e.getKey();\n\t\t\t\t\tprob = getEvaluator().toDouble(e.getValue());\n\t\t\t\t\td += prob * vect[k];\n\t\t\t\t}\n\t\t\t\t// Check whether we have exceeded min/max so far\n\t\t\t\tif (first2 || (min2 && d < minmax2) || (!min2 && d > minmax2))\n\t\t\t\t\tminmax2 = d;\n\t\t\t\tfirst2 = false;\n\t\t\t}\n\t\t\t// Store strategy info if value matches\n\t\t\t//if (PrismUtils.doublesAreClose(val, d, termCritParam, termCrit == TermCrit.ABSOLUTE)) {\n\t\t\tif (PrismUtils.doublesAreEqual(val, minmax2)) {\n\t\t\t\tres.add(j);\n\t\t\t\t//res.add(distrs.getAction());\n\t\t\t}\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t@Override\n\tpublic double mvMultGSMinMax(double vect[], boolean min1, boolean min2, BitSet subset, boolean complement, boolean absolute, int[] adv)\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\tfor (int s : new IterableStateSet(subset, numStates, complement)) {\n\t\t\td = mvMultJacMinMaxSingle(s, vect, min1, min2, adv);\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n\n\t@Override\n\tpublic double mvMultJacMinMaxSingle(int s, double vect[], boolean min1, boolean min2, int[] adv)\n\t{\n\t\tint k;\n\t\tdouble diag, d, prob, minmax1, minmax2;\n\t\tboolean first1, first2;\n\t\tArrayList<DistributionSet<Value>> step;\n\n\t\tminmax1 = 0;\n\t\tfirst1 = true;\n\t\tstep = trans.get(s);\n\t\tfor (DistributionSet<Value> distrs : step) {\n\t\t\tminmax2 = 0;\n\t\t\tfirst2 = true;\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\tdiag = 1.0;\n\t\t\t\t// Compute sum for this distribution\n\t\t\t\td = 0.0;\n\t\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\t\tk = e.getKey();\n\t\t\t\t\tprob = getEvaluator().toDouble(e.getValue());\n\t\t\t\t\tif (k != s) {\n\t\t\t\t\t\td += prob * vect[k];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tdiag -= prob;\n\t\t\t\t\t}\n\t\t\t\t\tif (diag > 0)\n\t\t\t\t\t\td /= diag;\n\t\t\t\t}\n\t\t\t\t// Check whether we have exceeded min/max so far\n\t\t\t\tif (first2 || (min2 && d < minmax2) || (!min2 && d > minmax2))\n\t\t\t\t\tminmax2 = d;\n\t\t\t\tfirst2 = false;\n\t\t\t}\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first1 || (min1 && minmax2 < minmax1) || (!min1 && minmax2 > minmax1))\n\t\t\t\tminmax1 = minmax2;\n\t\t\tfirst1 = false;\n\t\t}\n\n\t\treturn minmax1;\n\t}\n\n\t@Override\n\tpublic void mvMultRewMinMax(double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, double result[], BitSet subset, boolean complement, int adv[])\n\t{\n\t\tfor (int s : new IterableStateSet(subset, numStates, complement)) {\n\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, rewards, min1, min2, adv);\n\t\t}\n\t}\n\n\t@Override\n\tpublic double mvMultRewMinMaxSingle(int s, double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, int adv[])\n\t{\n\t\tint dsIter, dIter, k;\n\t\tdouble d, prob, minmax1, minmax2;\n\t\tboolean first1, first2;\n\t\tArrayList<DistributionSet<Value>> step;\n\n\t\tminmax1 = 0;\n\t\tfirst1 = true;\n\t\tdsIter = -1;\n\t\tstep = trans.get(s);\n\t\tfor (DistributionSet<Value> distrs : step) {\n\t\t\tdsIter++;\n\t\t\tminmax2 = 0;\n\t\t\tfirst2 = true;\n\t\t\tdIter = -1;\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\tdIter++;\n\t\t\t\t// Compute sum for this distribution\n\t\t\t\td = ((STPGRewardsNestedSimple<Double>) rewards).getNestedTransitionReward(s, dsIter, dIter);\n\t\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\t\tk = e.getKey();\n\t\t\t\t\tprob = getEvaluator().toDouble(e.getValue());\n\t\t\t\t\td += prob * vect[k];\n\t\t\t\t}\n\t\t\t\t// Check whether we have exceeded min/max so far\n\t\t\t\tif (first2 || (min2 && d < minmax2) || (!min2 && d > minmax2))\n\t\t\t\t\tminmax2 = d;\n\t\t\t\tfirst2 = false;\n\t\t\t}\n\t\t\tminmax2 += rewards.getTransitionReward(s, dsIter);\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first1 || (min1 && minmax2 < minmax1) || (!min1 && minmax2 > minmax1))\n\t\t\t\tminmax1 = minmax2;\n\t\t\tfirst1 = false;\n\t\t}\n\n\t\treturn minmax1;\n\t}\n\n\t@Override\n\tpublic List<Integer> mvMultRewMinMaxSingleChoices(int s, double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, double val)\n\t{\n\t\tint dsIter, dIter, k;\n\t\tdouble d, prob, minmax2;\n\t\tboolean first2;\n\t\tList<Integer> res;\n\t\tArrayList<DistributionSet<Value>> step;\n\n\t\t// Create data structures to store strategy\n\t\tres = new ArrayList<Integer>();\n\t\t// One row of matrix-vector operation \n\t\tdsIter = -1;\n\t\tstep = trans.get(s);\n\t\tfor (DistributionSet<Value> distrs : step) {\n\t\t\tdsIter++;\n\t\t\tminmax2 = 0;\n\t\t\tfirst2 = true;\n\t\t\tdIter = -1;\n\t\t\tfor (Distribution<Value> distr : distrs) {\n\t\t\t\tdIter++;\n\t\t\t\t// Compute sum for this distribution\n\t\t\t\td = ((STPGRewardsNestedSimple<Double>) rewards).getNestedTransitionReward(s, dsIter, dIter);\n\t\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\t\tk = e.getKey();\n\t\t\t\t\tprob = getEvaluator().toDouble(e.getValue());\n\t\t\t\t\td += prob * vect[k];\n\t\t\t\t}\n\t\t\t\t// Check whether we have exceeded min/max so far\n\t\t\t\tif (first2 || (min2 && d < minmax2) || (!min2 && d > minmax2))\n\t\t\t\t\tminmax2 = d;\n\t\t\t\tfirst2 = false;\n\t\t\t}\n\t\t\tminmax2 += rewards.getTransitionReward(s, dsIter);\n\t\t\t// Store strategy info if value matches\n\t\t\t//if (PrismUtils.doublesAreClose(val, d, termCritParam, termCrit == TermCrit.ABSOLUTE)) {\n\t\t\tif (PrismUtils.doublesAreEqual(val, minmax2)) {\n\t\t\t\tres.add(dsIter);\n\t\t\t\t//res.add(distrs.getAction());\n\t\t\t}\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t@Override\n\tpublic void mvMultRewMinMax(double[] vect, STPGRewards<Double> rewards, boolean min1, boolean min2, double[] result, BitSet subset, boolean complement, int[] adv, double disc)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\t\n\t// Additional accessor that extended STPG with a \"nested view\"\n\n\t/**\n\t * Is choice {@code i} of state {@code s} in nested form? (See {@link explicit.STPG} for details)\n\t */\n\tpublic boolean isChoiceNested(int s, int i)\n\t{\n\t\t// All choices are nested\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get the number of (nested) choices in choice {@code i} of state {@code s}.\n\t */\n\tpublic int getNumNestedChoices(int s, int i)\n\t{\n\t\treturn trans.get(s).get(i).size();\n\t}\n\n\t/**\n\t * Get the action label (if any) for nested choice {@code i,j} of state {@code s}.\n\t */\n\tpublic Object getNestedAction(int s, int i, int j)\n\t{\n\t\treturn trans.get(s).get(i).getAction();\n\t}\n\n\t/**\n\t * Get the number of transitions from nested choice {@code i,j} of state {@code s}.\n\t */\n\tpublic int getNumNestedTransitions(int s, int i, int j)\n\t{\n\t\tDistributionSet<Value> ds = trans.get(s).get(i);\n\t\tIterator<Distribution<Value>> iter = ds.iterator();\n\t\tDistribution<Value> distr = null;\n\t\tint k = 0;\n\t\twhile (iter.hasNext() && k <= j) {\n\t\t\tdistr = iter.next();\n\t\t\tk++;\n\t\t}\n\t\tif (k <= j)\n\t\t\treturn 0;\n\t\telse\n\t\t\treturn distr.size();\n\t}\n\n\t/**\n\t * Get an iterator over the transitions from nested choice {@code i,j} of state {@code s}.\n\t */\n\tpublic Iterator<Entry<Integer, Value>> getNestedTransitionsIterator(int s, int i, int j)\n\t{\n\t\tDistributionSet<Value> ds = trans.get(s).get(i);\n\t\tIterator<Distribution<Value>> iter = ds.iterator();\n\t\tDistribution<Value> distr = null;\n\t\tint k = 0;\n\t\twhile (iter.hasNext() && k <= j) {\n\t\t\tdistr = iter.next();\n\t\t\tk++;\n\t\t}\n\t\tif (k <= j)\n\t\t\treturn null;\n\t\telse\n\t\t\treturn distr.iterator();\n\t}\n\n\t// Accessors (other)\n\n\t/**\n\t * Get the list of choices (distribution sets) for state s.\n\t */\n\tpublic List<DistributionSet<Value>> getChoices(int s)\n\t{\n\t\treturn trans.get(s);\n\t}\n\n\t/**\n\t * Get the ith choice (distribution set) for state s.\n\t */\n\tpublic DistributionSet<Value> getChoice(int s, int i)\n\t{\n\t\treturn trans.get(s).get(i);\n\t}\n\n\t/**\n\t * Get the total number of player 1 choices (distribution sets) over all states.\n\t */\n\tpublic int getNumPlayer1Choices()\n\t{\n\t\treturn numDistrSets;\n\t}\n\n\t/**\n\t * Get the total number of player 2 choices (distributions) over all states.\n\t */\n\tpublic int getNumPlayer2Choices()\n\t{\n\t\treturn numDistrs;\n\t}\n\n\t/**\n\t * Get the maximum number of player 1 choices (distribution sets) in any state.\n\t */\n\tpublic int getMaxNumPlayer1Choices()\n\t{\n\t\t// TODO: Recompute if necessary\n\t\treturn maxNumDistrSets;\n\t}\n\n\t/**\n\t * Get the maximum number of player 2 choices (distributions) in any state.\n\t */\n\tpublic int getMaxNumPlayer2Choices()\n\t{\n\t\t// TODO: Recompute if necessary\n\t\treturn maxNumDistrs;\n\t}\n\n\t// Standard methods\n\n\t// @Override // Move to superclass later\n\tpublic String toStringGeneric()\n\t{\n\t\t// General purpose toString(), based on STPG access methods\n\t\tint s, i, j, ni, nj;\n\t\tboolean first, firsti, firstTr;\n\t\tIterator<Entry<Integer, Value>> it;\n\t\tString str = \"\";\n\t\tfirst = true;\n\t\tstr = \"[ \";\n\t\tfor (s = 0; s < numStates; s++) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\tstr += \", \";\n\t\t\tstr += s + \": \";\n\t\t\tni = getNumChoices(s);\n\t\t\tstr += \"[\";\n\t\t\tfirsti = true;\n\t\t\tfor (i = 0; i < ni; i++) {\n\t\t\t\t// Do non-nested choices\n\t\t\t\tit = getTransitionsIterator(s, i);\n\t\t\t\tif (it == null)\n\t\t\t\t\tcontinue;\n\t\t\t\tif (firsti)\n\t\t\t\t\tfirsti = false;\n\t\t\t\telse\n\t\t\t\t\tstr += \", \";\n\t\t\t\tstr += \"{\";\n\t\t\t\tfirstTr = true;\n\t\t\t\twhile (it.hasNext()) {\n\t\t\t\t\tEntry<Integer, Value> next = it.next();\n\t\t\t\t\tif (firstTr)\n\t\t\t\t\t\tfirstTr = false;\n\t\t\t\t\telse\n\t\t\t\t\t\tstr += \", \";\n\t\t\t\t\tstr += next.getKey() + \"=\" + next.getValue();\n\t\t\t\t}\n\t\t\t\tstr += \"}\";\n\t\t\t\t// Do nested choices\n\t\t\t\tnj = getNumNestedChoices(s, i);\n\t\t\t\tif (nj == 0)\n\t\t\t\t\tcontinue;\n\t\t\t\tif (firsti)\n\t\t\t\t\tfirsti = false;\n\t\t\t\telse\n\t\t\t\t\tstr += \", \";\n\t\t\t\tstr += \"[\";\n\t\t\t\tfor (j = 0; j < nj; j++) {\n\t\t\t\t\tit = getNestedTransitionsIterator(s, i, j);\n\t\t\t\t\tif (it == null)\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\tif (j > 0)\n\t\t\t\t\t\tstr += \", \";\n\t\t\t\t\tstr += \"{\";\n\t\t\t\t\tfirstTr = true;\n\t\t\t\t\twhile (it.hasNext()) {\n\t\t\t\t\t\tEntry<Integer, Value> next = it.next();\n\t\t\t\t\t\tif (firstTr)\n\t\t\t\t\t\t\tfirstTr = false;\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\tstr += \", \";\n\t\t\t\t\t\tstr += next.getKey() + \"=\" + next.getValue();\n\t\t\t\t\t}\n\t\t\t\t\tstr += \"}\";\n\t\t\t\t}\n\t\t\t\tstr += \"]\";\n\t\t\t}\n\t\t\tstr += \"]\";\n\t\t}\n\t\tstr += \" ]\";\n\t\treturn str;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\t// Custom toString()\n\t\tint i;\n\t\tboolean first;\n\t\tString s = \"\";\n\t\tfirst = true;\n\t\ts = \"[ \";\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\ts += \", \";\n\t\t\ts += i + \": \" + trans.get(i);\n\t\t}\n\t\ts += \" ]\";\n\t\treturn s;\n\t}\n\n\t/**\n\t * Equality check.\n\t */\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof STPGAbstrSimple))\n\t\t\treturn false;\n\t\tSTPGAbstrSimple<?> stpg = (STPGAbstrSimple<?>) o;\n\t\tif (numStates != stpg.numStates)\n\t\t\treturn false;\n\t\tif (!initialStates.equals(stpg.initialStates))\n\t\t\treturn false;\n\t\tif (!trans.equals(stpg.trans))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n\n\t/**\n\t * Simple test program\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tSTPGModelChecker mc;\n\t\tSTPGAbstrSimple<Double> stpg;\n\t\tDistributionSet<Double> set;\n\t\tDistribution<Double> distr;\n\t\t//ModelCheckerResult res;\n\t\tBitSet target;\n\n\t\t// Simple example: Create and solve the stochastic game from:\n\t\t// Mark Kattenbelt, Marta Kwiatkowska, Gethin Norman, David Parker\n\t\t// A Game-based Abstraction-Refinement Framework for Markov Decision Processes\n\t\t// Formal Methods in System Design 36(3): 246-280, 2010\n\n\t\ttry {\n\t\t\t// Build game\n\t\t\tstpg = new STPGAbstrSimple<>();\n\t\t\tstpg.addStates(4);\n\t\t\t// State 0 (s_0)\n\t\t\tset = stpg.newDistributionSet(null);\n\t\t\tdistr = Distribution.ofDouble();\n\t\t\tdistr.set(1, 1.0);\n\t\t\tset.add(distr);\n\t\t\tstpg.addDistributionSet(0, set);\n\t\t\t// State 1 (s_1,s_2,s_3)\n\t\t\tset = stpg.newDistributionSet(null);\n\t\t\tdistr = Distribution.ofDouble();\n\t\t\tdistr.set(2, 1.0);\n\t\t\tset.add(distr);\n\t\t\tdistr = Distribution.ofDouble();\n\t\t\tdistr.set(1, 1.0);\n\t\t\tset.add(distr);\n\t\t\tstpg.addDistributionSet(1, set);\n\t\t\tset = stpg.newDistributionSet(null);\n\t\t\tdistr = Distribution.ofDouble();\n\t\t\tdistr.set(2, 0.5);\n\t\t\tdistr.set(3, 0.5);\n\t\t\tset.add(distr);\n\t\t\tdistr = Distribution.ofDouble();\n\t\t\tdistr.set(3, 1.0);\n\t\t\tset.add(distr);\n\t\t\tstpg.addDistributionSet(1, set);\n\t\t\t// State 2 (s_4,s_5)\n\t\t\tset = stpg.newDistributionSet(null);\n\t\t\tdistr = Distribution.ofDouble();\n\t\t\tdistr.set(2, 1.0);\n\t\t\tset.add(distr);\n\t\t\tstpg.addDistributionSet(2, set);\n\t\t\t// State 3 (s_6)\n\t\t\tset = stpg.newDistributionSet(null);\n\t\t\tdistr = Distribution.ofDouble();\n\t\t\tdistr.set(3, 1.0);\n\t\t\tset.add(distr);\n\t\t\tstpg.addDistributionSet(3, set);\n\t\t\t// Print game\n\t\t\tSystem.out.println(stpg);\n\n\t\t\t// Model check\n\t\t\tmc = new STPGModelChecker(null);\n\t\t\t//mc.setVerbosity(2);\n\t\t\ttarget = new BitSet();\n\t\t\ttarget.set(3);\n\t\t\tstpg.exportToDotFile(\"stpg.dot\", target);\n\t\t\tSystem.out.println(\"min min: \" + mc.computeReachProbs(stpg, target, true, true).soln[0]);\n\t\t\tSystem.out.println(\"max min: \" + mc.computeReachProbs(stpg, target, false, true).soln[0]);\n\t\t\tSystem.out.println(\"min max: \" + mc.computeReachProbs(stpg, target, true, false).soln[0]);\n\t\t\tSystem.out.println(\"max max: \" + mc.computeReachProbs(stpg, target, false, false).soln[0]);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/STPGModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Map;\n\nimport common.IterableBitSet;\n\nimport parser.ast.Expression;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismUtils;\nimport explicit.rewards.STPGRewards;\nimport strat.MDStrategyArray;\n\n/**\n * Explicit-state model checker for two-player stochastic games (STPGs).\n */\npublic class STPGModelChecker extends ProbModelChecker\n{\n\t/**\n\t * Create a new STPGModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic STPGModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t// Model checking functions\n\n\t@Override\n\tprotected StateValues checkProbPathFormulaLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"LTL model checking not yet supported for stochastic games\");\n\t}\n\n\t// Numerical computation functions\n\n\t/**\n\t * Compute next=state probabilities.\n\t * i.e. compute the probability of being in a state in {@code target} in the next step.\n\t * @param stpg The STPG\n\t * @param target Target states\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeNextProbs(STPG<Double> stpg, BitSet target, boolean min1, boolean min2) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tint n;\n\t\tdouble soln[], soln2[];\n\t\tlong timer;\n\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Store num states\n\t\tn = stpg.getNumStates();\n\n\t\t// Create/initialise solution vector(s)\n\t\tsoln = Utils.bitsetToDoubleArray(target, n);\n\t\tsoln2 = new double[n];\n\n\t\t// Next-step probabilities \n\t\tstpg.mvMultMinMax(soln, min1, min2, soln2, null, false, null);\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln2;\n\t\tres.numIters = 1;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute reachability probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target}.\n\t * @param stpg The STPG\n\t * @param target Target states\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeReachProbs(STPG<Double> stpg, BitSet target, boolean min1, boolean min2) throws PrismException\n\t{\n\t\treturn computeReachProbs(stpg, null, target, min1, min2, null, null);\n\t}\n\n\t/**\n\t * Compute until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * while remaining in those in {@code remain}.\n\t * @param stpg The STPG\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeUntilProbs(STPG<Double> stpg, BitSet remain, BitSet target, boolean min1, boolean min2) throws PrismException\n\t{\n\t\treturn computeReachProbs(stpg, remain, target, min1, min2, null, null);\n\t}\n\n\t/**\n\t * Compute reachability/until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * while remaining in those in {@code remain}.\n\t * @param stpg The STPG\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (may be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tpublic ModelCheckerResult computeReachProbs(STPG<Double> stpg, BitSet remain, BitSet target, boolean min1, boolean min2, double init[], BitSet known)\n\t\t\tthrows PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet no, yes;\n\t\tint n, numYes, numNo;\n\t\tlong timer, timerProb0, timerProb1;\n\n\t\t// Check for some unsupported combinations\n\t\tif (solnMethod == SolnMethod.VALUE_ITERATION && valIterDir == ValIterDir.ABOVE && !(precomp && prob0)) {\n\t\t\tthrow new PrismException(\"Precomputation (Prob0) must be enabled for value iteration from above\");\n\t\t}\n\n\t\t// Start probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"\\nStarting probabilistic reachability...\");\n\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tstpg.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tn = stpg.getNumStates();\n\n\t\t// Optimise by enlarging target set (if more info is available)\n\t\tif (init != null && known != null && !known.isEmpty()) {\n\t\t\tBitSet targetNew = (BitSet) target.clone();\n\t\t\tfor (int i : new IterableBitSet(known)) {\n\t\t\t\tif (init[i] == 1.0) {\n\t\t\t\t\ttargetNew.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\ttarget = targetNew;\n\t\t}\n\n\t\t// Precomputation\n\t\ttimerProb0 = System.currentTimeMillis();\n\t\tif (precomp && prob0) {\n\t\t\tno = prob0(stpg, remain, target, min1, min2);\n\t\t} else {\n\t\t\tno = new BitSet();\n\t\t\tif (remain != null) {\n\t\t\t\tno.or(remain);\n\t\t\t\tno.or(target);\n\t\t\t\tno.flip(0, n);\n\t\t\t}\n\t\t}\n\t\ttimerProb0 = System.currentTimeMillis() - timerProb0;\n\t\ttimerProb1 = System.currentTimeMillis();\n\t\tif (precomp && prob1 && !genStrat) {\n\t\t\tyes = prob1(stpg, remain, target, min1, min2);\n\t\t} else {\n\t\t\tyes = (BitSet) target.clone();\n\t\t}\n\t\ttimerProb1 = System.currentTimeMillis() - timerProb1;\n\n\t\t// Print results of precomputation\n\t\tnumYes = yes.cardinality();\n\t\tnumNo = no.cardinality();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"target=\" + target.cardinality() + \", yes=\" + numYes + \", no=\" + numNo + \", maybe=\" + (n - (numYes + numNo)));\n\n\t\t// Compute probabilities\n\t\tswitch (solnMethod) {\n\t\tcase VALUE_ITERATION:\n\t\t\tres = computeReachProbsValIter(stpg, no, yes, min1, min2, init, known);\n\t\t\tbreak;\n\t\tcase GAUSS_SEIDEL:\n\t\t\tres = computeReachProbsGaussSeidel(stpg, no, yes, min1, min2, init, known);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown STPG solution method \" + solnMethod);\n\t\t}\n\n\t\t// Finished probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Probabilistic reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timeProb0 = timerProb0 / 1000.0;\n\t\tres.timePre = (timerProb0 + timerProb1) / 1000.0;\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Prob0 precomputation algorithm.\n\t * i.e. determine the states of an STPG which, with min/max probability 0,\n\t * reach a state in {@code target}, while remaining in those in {@code remain}.\n\t * {@code min}=true gives Prob0E, {@code min}=false gives Prob0A. \n\t * @param stpg The STPG\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t */\n\tpublic BitSet prob0(STPG<?> stpg, BitSet remain, BitSet target, boolean min1, boolean min2)\n\t{\n\t\tint n, iters;\n\t\tBitSet u, soln, unknown;\n\t\tboolean u_done;\n\t\tlong timer;\n\n\t\t// Start precomputation\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Starting Prob0 (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")...\");\n\n\t\t// Special case: no target states\n\t\tif (target.cardinality() == 0) {\n\t\t\tsoln = new BitSet(stpg.getNumStates());\n\t\t\tsoln.set(0, stpg.getNumStates());\n\t\t\treturn soln;\n\t\t}\n\n\t\t// Initialise vectors\n\t\tn = stpg.getNumStates();\n\t\tu = new BitSet(n);\n\t\tsoln = new BitSet(n);\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\n\t\t// Fixed point loop\n\t\titers = 0;\n\t\tu_done = false;\n\t\t// Least fixed point - should start from 0 but we optimise by\n\t\t// starting from 'target', thus bypassing first iteration\n\t\tu.or(target);\n\t\tsoln.or(target);\n\t\twhile (!u_done) {\n\t\t\titers++;\n\t\t\t// Single step of Prob0\n\t\t\tstpg.prob0step(unknown, u, min1, min2, soln);\n\t\t\t// Check termination\n\t\t\tu_done = soln.equals(u);\n\t\t\t// u = soln\n\t\t\tu.clear();\n\t\t\tu.or(soln);\n\t\t}\n\n\t\t// Negate\n\t\tu.flip(0, n);\n\n\t\t// Finished precomputation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (verbosity >= 1) {\n\t\t\tmainLog.print(\"Prob0 (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\treturn u;\n\t}\n\n\t/**\n\t * Prob1 precomputation algorithm.\n\t * i.e. determine the states of an STPG which, with min/max probability 1,\n\t * reach a state in {@code target}, while remaining in those in {@code remain}.\n\t * @param stpg The STPG\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t */\n\tpublic BitSet prob1(STPG<?> stpg, BitSet remain, BitSet target, boolean min1, boolean min2)\n\t{\n\t\tint n, iters;\n\t\tBitSet u, v, soln, unknown;\n\t\tboolean u_done, v_done;\n\t\tlong timer;\n\n\t\t// Start precomputation\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Starting Prob1 (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")...\");\n\n\t\t// Special case: no target states\n\t\tif (target.cardinality() == 0) {\n\t\t\treturn new BitSet(stpg.getNumStates());\n\t\t}\n\n\t\t// Initialise vectors\n\t\tn = stpg.getNumStates();\n\t\tu = new BitSet(n);\n\t\tv = new BitSet(n);\n\t\tsoln = new BitSet(n);\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\n\t\t// Nested fixed point loop\n\t\titers = 0;\n\t\tu_done = false;\n\t\t// Greatest fixed point\n\t\tu.set(0, n);\n\t\twhile (!u_done) {\n\t\t\tv_done = false;\n\t\t\t// Least fixed point - should start from 0 but we optimise by\n\t\t\t// starting from 'target', thus bypassing first iteration\n\t\t\tv.clear();\n\t\t\tv.or(target);\n\t\t\tsoln.clear();\n\t\t\tsoln.or(target);\n\t\t\twhile (!v_done) {\n\t\t\t\titers++;\n\t\t\t\t// Single step of Prob1\n\t\t\t\tstpg.prob1step(unknown, u, v, min1, min2, soln);\n\t\t\t\t// Check termination (inner)\n\t\t\t\tv_done = soln.equals(v);\n\t\t\t\t// v = soln\n\t\t\t\tv.clear();\n\t\t\t\tv.or(soln);\n\t\t\t}\n\t\t\t// Check termination (outer)\n\t\t\tu_done = v.equals(u);\n\t\t\t// u = v\n\t\t\tu.clear();\n\t\t\tu.or(v);\n\t\t}\n\n\t\t// Finished precomputation\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (verbosity >= 1) {\n\t\t\tmainLog.print(\"Prob1 (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\treturn u;\n\t}\n\n\t/**\n\t * Compute reachability probabilities using value iteration.\n\t * @param stpg The STPG\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tprotected ModelCheckerResult computeReachProbsValIter(STPG<Double> stpg, BitSet no, BitSet yes, boolean min1, boolean min2, double init[], BitSet known)\n\t\t\tthrows PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet unknown;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[], initVal;\n\t\tint adv[] = null;\n\t\tboolean done;\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Starting value iteration (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")...\");\n\n\t\t// Store num states\n\t\tn = stpg.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = (init == null) ? new double[n] : init;\n\n\t\t// Initialise solution vectors. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 1.0/0.0 if in yes/no; (3) passed in initial value; (4) initVal\n\t\t// where initVal is 0.0 or 1.0, depending on whether we converge from below/above. \n\t\tinitVal = (valIterDir == ValIterDir.BELOW) ? 0.0 : 1.0;\n\t\tif (init != null) {\n\t\t\tif (known != null) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsoln[i] = soln2[i] = known.get(i) ? init[i] : yes.get(i) ? 1.0 : no.get(i) ? 0.0 : init[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsoln[i] = soln2[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : init[i];\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : initVal;\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(yes);\n\t\tunknown.andNot(no);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\t// Create/initialise adversary storage\n\t\tif (genStrat) {\n\t\t\tadv = new int[n];\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tadv[i] = -1;\n\t\t\t}\n\t\t}\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\tdone = false;\n\t\twhile (!done && iters < maxIters) {\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tstpg.mvMultMinMax(soln, min1, min2, soln2, unknown, false, genStrat ? adv : null);\n\t\t\t// Check termination\n\t\t\tdone = PrismUtils.doublesAreClose(soln, soln2, termCritParam, termCrit == TermCrit.ABSOLUTE);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished value iteration\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (verbosity >= 1) {\n\t\t\tmainLog.print(\"Value iteration (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\";\n\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tif (genStrat) {\n\t\t\tres.strat = new MDStrategyArray<>(stpg, adv);\n\t\t}\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute reachability probabilities using Gauss-Seidel.\n\t * @param stpg The STPG\n\t * @param no Probability 0 states\n\t * @param yes Probability 1 states\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tprotected ModelCheckerResult computeReachProbsGaussSeidel(STPG<Double> stpg, BitSet no, BitSet yes, boolean min1, boolean min2, double init[], BitSet known)\n\t\t\tthrows PrismException\n\t{\n\t\tModelCheckerResult res;\n\t\tBitSet unknown;\n\t\tint i, n, iters;\n\t\tdouble soln[], initVal, maxDiff;\n\t\tboolean done;\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Starting value iteration (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")...\");\n\n\t\t// Store num states\n\t\tn = stpg.getNumStates();\n\n\t\t// Create solution vector\n\t\tsoln = (init == null) ? new double[n] : init;\n\n\t\t// Initialise solution vector. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 1.0/0.0 if in yes/no; (3) passed in initial value; (4) initVal\n\t\t// where initVal is 0.0 or 1.0, depending on whether we converge from below/above. \n\t\tinitVal = (valIterDir == ValIterDir.BELOW) ? 0.0 : 1.0;\n\t\tif (init != null) {\n\t\t\tif (known != null) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsoln[i] = known.get(i) ? init[i] : yes.get(i) ? 1.0 : no.get(i) ? 0.0 : init[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsoln[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : init[i];\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : initVal;\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(yes);\n\t\tunknown.andNot(no);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\tdone = false;\n\t\twhile (!done && iters < maxIters) {\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tmaxDiff = stpg.mvMultGSMinMax(soln, min1, min2, unknown, false, termCrit == TermCrit.ABSOLUTE, null);\n\t\t\t// Check termination\n\t\t\tdone = maxDiff < termCritParam;\n\t\t}\n\n\t\t// Finished Gauss-Seidel\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (verbosity >= 1) {\n\t\t\tmainLog.print(\"Value iteration (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\";\n\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Construct strategy information for min/max reachability probabilities.\n\t * (More precisely, list of indices of player 1 choices resulting in min/max.)\n\t * (Note: indices are guaranteed to be sorted in ascending order.)\n\t * @param stpg The STPG\n\t * @param state The state to generate strategy info for\n\t * @param target The set of target states to reach\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t * @param lastSoln Vector of probabilities from which to recompute in one iteration \n\t */\n\tpublic List<Integer> probReachStrategy(STPG<Double> stpg, int state, BitSet target, boolean min1, boolean min2, double lastSoln[]) throws PrismException\n\t{\n\t\tdouble val = stpg.mvMultMinMaxSingle(state, lastSoln, min1, min2);\n\t\treturn stpg.mvMultMinMaxSingleChoices(state, lastSoln, min1, min2, val);\n\t}\n\n\t/**\n\t * Compute bounded reachability probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target} within k steps.\n\t * @param stpg The STPG\n\t * @param target Target states\n\t * @param k Bound\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(STPG<Double> stpg, BitSet target, int k, boolean min1, boolean min2) throws PrismException\n\t{\n\t\treturn computeBoundedReachProbs(stpg, null, target, k, min1, min2, null, null);\n\t}\n\n\t/**\n\t * Compute bounded until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * within k steps, and while remaining in states in {@code remain}.\n\t * @param stpg The STPG\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param k Bound\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeBoundedUntilProbs(STPG<Double> stpg, BitSet remain, BitSet target, int k, boolean min1, boolean min2) throws PrismException\n\t{\n\t\treturn computeBoundedReachProbs(stpg, remain, target, k, min1, min2, null, null);\n\t}\n\n\t/**\n\t * Compute bounded reachability/until probabilities.\n\t * i.e. compute the min/max probability of reaching a state in {@code target},\n\t * within k steps, and while remaining in states in {@code remain}.\n\t * @param stpg The STPG\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param k Bound\n\t * @param min1 Min or max probabilities for player 1 (true=min, false=max)\n\t * @param min2 Min or max probabilities for player 2 (true=min, false=max)\n\t * @param init Initial solution vector - pass null for default\n\t * @param results Optional array of size k+1 to store (init state) results for each step (null if unused)\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(STPG<Double> stpg, BitSet remain, BitSet target, int k, boolean min1, boolean min2, double init[],\n\t\t\tdouble results[]) throws PrismException\n\t{\n\t\t// TODO: implement until\n\n\t\tModelCheckerResult res = null;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\n\t\t// Start bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"\\nStarting bounded probabilistic reachability...\");\n\n\t\t// Store num states\n\t\tn = stpg.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = (init == null) ? new double[n] : init;\n\n\t\t// Initialise solution vectors. Use passed in initial vector, if present\n\t\tif (init != null) {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : init[i];\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : 0.0;\n\t\t}\n\t\t// Store intermediate results if required\n\t\t// (compute min/max value over initial states for first step)\n\t\tif (results != null) {\n\t\t\tresults[0] = Utils.minMaxOverArraySubset(soln2, stpg.getInitialStates(), min2);\n\t\t}\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\twhile (iters < k) {\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tstpg.mvMultMinMax(soln, min1, min2, soln2, target, true, null);\n\t\t\t// Store intermediate results if required\n\t\t\t// (compute min/max value over initial states for this step)\n\t\t\tif (results != null) {\n\t\t\t\tresults[iters] = Utils.minMaxOverArraySubset(soln2, stpg.getInitialStates(), min2);\n\t\t\t}\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Print vector (for debugging)\n\t\t//mainLog.println(soln);\n\n\t\t// Finished bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (verbosity >= 1) {\n\t\t\tmainLog.print(\"Bounded probabilistic reachability (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.lastSoln = soln2;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards.\n\t * @param stpg The STPG\n\t * @param rewards The rewards\n\t * @param target Target states\n\t * @param min1 Min or max rewards for player 1 (true=min, false=max)\n\t * @param min2 Min or max rewards for player 2 (true=min, false=max)\n\t */\n\tpublic ModelCheckerResult computeReachRewards(STPG<Double> stpg, STPGRewards<Double> rewards, BitSet target, boolean min1, boolean min2) throws PrismException\n\t{\n\t\treturn computeReachRewards(stpg, rewards, target, min1, min2, null, null);\n\t}\n\n\t/**\n\t * Compute expected reachability rewards.\n\t * i.e. compute the min/max reward accumulated to reach a state in {@code target}.\n\t * @param stpg The STPG\n\t * @param rewards The rewards\n\t * @param target Target states\n\t * @param min1 Min or max rewards for player 1 (true=min, false=max)\n\t * @param min2 Min or max rewards for player 2 (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (may be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.  \n\t */\n\tpublic ModelCheckerResult computeReachRewards(STPG<Double> stpg, STPGRewards<Double> rewards, BitSet target, boolean min1, boolean min2, double init[], BitSet known)\n\t\t\tthrows PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet inf;\n\t\tint n, numTarget, numInf;\n\t\tlong timer, timerProb1;\n\n\t\t// Start expected reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"\\nStarting expected reachability...\");\n\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tstpg.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tn = stpg.getNumStates();\n\n\t\t// Optimise by enlarging target set (if more info is available)\n\t\tif (init != null && known != null && !known.isEmpty()) {\n\t\t\tBitSet targetNew = (BitSet) target.clone();\n\t\t\tfor (int i : new IterableBitSet(known)) {\n\t\t\t\tif (init[i] == 1.0) {\n\t\t\t\t\ttargetNew.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\ttarget = targetNew;\n\t\t}\n\n\t\t// Precomputation (not optional)\n\t\ttimerProb1 = System.currentTimeMillis();\n\t\tinf = prob1(stpg, null, target, !min1, !min2);\n\t\tinf.flip(0, n);\n\t\ttimerProb1 = System.currentTimeMillis() - timerProb1;\n\n\t\t// Print results of precomputation\n\t\tnumTarget = target.cardinality();\n\t\tnumInf = inf.cardinality();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"target=\" + numTarget + \", inf=\" + numInf + \", rest=\" + (n - (numTarget + numInf)));\n\n\t\t// Compute rewards\n\t\tswitch (solnMethod) {\n\t\tcase VALUE_ITERATION:\n\t\t\tres = computeReachRewardsValIter(stpg, rewards, target, inf, min1, min2, init, known);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown STPG solution method \" + solnMethod);\n\t\t}\n\n\t\t// Finished expected reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Expected reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = timerProb1 / 1000.0;\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards using value iteration.\n\t * @param stpg The STPG\n\t * @param rewards The rewards\n\t * @param target Target states\n\t * @param inf States for which reward is infinite\n\t * @param min1 Min or max rewards for player 1 (true=min, false=max)\n\t * @param min2 Min or max rewards for player 2 (true=min, false=max)\n\t * @param init Optionally, an initial solution vector (will be overwritten) \n\t * @param known Optionally, a set of states for which the exact answer is known\n\t * Note: if 'known' is specified (i.e. is non-null, 'init' must also be given and is used for the exact values.\n\t */\n\tprotected ModelCheckerResult computeReachRewardsValIter(STPG<Double> stpg, STPGRewards<Double> rewards, BitSet target, BitSet inf, boolean min1, boolean min2,\n\t\t\tdouble init[], BitSet known) throws PrismException\n\t{\n\t\tModelCheckerResult res;\n\t\tBitSet unknown;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tboolean done;\n\t\tlong timer;\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Starting value iteration (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")...\");\n\n\t\t// Store num states\n\t\tn = stpg.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = (init == null) ? new double[n] : init;\n\n\t\t// Initialise solution vectors. Use (where available) the following in order of preference:\n\t\t// (1) exact answer, if already known; (2) 0.0/infinity if in target/inf; (3) passed in initial value; (4) 0.0\n\t\tif (init != null) {\n\t\t\tif (known != null) {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsoln[i] = soln2[i] = known.get(i) ? init[i] : target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : init[i];\n\t\t\t} else {\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : init[i];\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tsoln[i] = soln2[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : 0.0;\n\t\t}\n\n\t\t// Determine set of states actually need to compute values for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tunknown.andNot(inf);\n\t\tif (known != null)\n\t\t\tunknown.andNot(known);\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\tdone = false;\n\t\twhile (!done && iters < maxIters) {\n\t\t\t//mainLog.println(soln);\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tstpg.mvMultRewMinMax(soln, rewards, min1, min2, soln2, unknown, false, null);\n\t\t\t// Check termination\n\t\t\tdone = PrismUtils.doublesAreClose(soln, soln2, termCritParam, termCrit == TermCrit.ABSOLUTE);\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished value iteration\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tif (verbosity >= 1) {\n\t\t\tmainLog.print(\"Value iteration (\" + (min1 ? \"min\" : \"max\") + (min2 ? \"min\" : \"max\") + \")\");\n\t\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\t\t}\n\n\t\t// Non-convergence is an error (usually)\n\t\tif (!done && errorOnNonConverge) {\n\t\t\tString msg = \"Iterative method did not converge within \" + iters + \" iterations.\";\n\t\t\tmsg += \"\\nConsider using a different numerical method or increasing the maximum number of iterations\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Simple test program.\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tSTPGModelChecker mc;\n\t\tSTPGAbstrSimple<Double> stpg;\n\t\tModelCheckerResult res;\n\t\tBitSet target;\n\t\tMap<String, BitSet> labels;\n\t\tboolean min1 = true, min2 = true;\n\t\ttry {\n\t\t\tmc = new STPGModelChecker(null);\n\t\t\tstpg = new STPGAbstrSimple<>();\n\t\t\tstpg.buildFromPrismExplicit(args[0]);\n\t\t\tstpg.addInitialState(0);\n\t\t\t//System.out.println(stpg);\n\t\t\tlabels = StateModelChecker.loadLabelsFile(args[1]);\n\t\t\t//System.out.println(labels);\n\t\t\ttarget = labels.get(args[2]);\n\t\t\tif (target == null)\n\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + args[2] + \"\\\"\");\n\t\t\tfor (int i = 3; i < args.length; i++) {\n\t\t\t\tif (args[i].equals(\"-minmin\")) {\n\t\t\t\t\tmin1 = true;\n\t\t\t\t\tmin2 = true;\n\t\t\t\t} else if (args[i].equals(\"-maxmin\")) {\n\t\t\t\t\tmin1 = false;\n\t\t\t\t\tmin2 = true;\n\t\t\t\t} else if (args[i].equals(\"-minmax\")) {\n\t\t\t\t\tmin1 = true;\n\t\t\t\t\tmin2 = false;\n\t\t\t\t} else if (args[i].equals(\"-maxmax\")) {\n\t\t\t\t\tmin1 = false;\n\t\t\t\t\tmin2 = false;\n\t\t\t\t}\n\t\t\t}\n\t\t\t//stpg.exportToDotFile(\"stpg.dot\", target);\n\t\t\t//stpg.exportToPrismExplicit(\"stpg\");\n\t\t\tres = mc.computeReachProbs(stpg, target, min1, min2);\n\t\t\tSystem.out.println(res.soln[0]);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/STPGSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Map;\n\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.STPGRewards;\nimport prism.ModelType;\nimport prism.PrismException;\n\n/**\n * Simple explicit-state representation of a (turn-based) stochastic two-player game (STPG).\n */\npublic class STPGSimple<Value> extends MDPSimple<Value> implements STPG<Value>\n{\n\t/**\n\t * Which player owns each state\n\t */\n\tprotected StateOwnersSimple stateOwners;\n\t\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn ModelType.STPG;\n\t}\n\n\t/**\n\t * Constructor: empty STPG.\n\t */\n\tpublic STPGSimple()\n\t{\n\t\tsuper();\n\t\tstateOwners = new StateOwnersSimple();\n\t}\n\n\t/**\n\t * Constructor: new STPG with fixed number of states.\n\t */\n\tpublic STPGSimple(int numStates)\n\t{\n\t\tsuper(numStates);\n\t\tstateOwners = new StateOwnersSimple(numStates);\n\t}\n\n\t/**\n\t * Copy constructor\n\t */\n\tpublic STPGSimple(STPGSimple<Value> stpg)\n\t{\n\t\tsuper(stpg);\n\t\tstateOwners = new StateOwnersSimple(stpg.stateOwners);\n\t}\n\t\n\t/**\n\t * Construct an STPG from an existing one and a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t * Player and coalition info is also copied across.\n\t */\n\tpublic STPGSimple(STPGSimple<Value> stpg, int permut[])\n\t{\n\t\tsuper(stpg, permut);\n\t\tstateOwners = new StateOwnersSimple(stpg.stateOwners, permut);\n\t}\n\n\t// Mutators\n\n\t@Override\n\tpublic void clearState(int s)\n\t{\n\t\tsuper.clearState(s);\n\t\tstateOwners.clearState(s);\n\t\tactionList.markNeedsRecomputing();\n\t}\n\n\t@Override\n\tpublic void addStates(int numToAdd)\n\t{\n\t\tsuper.addStates(numToAdd);\n\t\t// Assume all player 1\n\t\tfor (int i = 0; i < numToAdd; i++) {\n\t\t\tstateOwners.addState(0);\n\t\t}\n\t}\n\n\t/**\n\t * Add a new (player {@code p}) state and return its index.\n\t * @param p Player who owns the new state (0-indexed)\n\t */\n\tpublic int addState(int p)\n\t{\n\t\tint s = super.addState();\n\t\tstateOwners.setPlayer(s, p);\n\t\treturn s;\n\t}\n\n\t/**\n\t * Set the player that owns state {@code s} to {@code p}.\n\t * @param s State to be modified (0-indexed)\n\t * @param p Player who owns the state (0-indexed)\n\t */\n\tpublic void setPlayer(int s, int p)\n\t{\n\t\tstateOwners.setPlayer(s, p);\n\t}\n\n\t// Accessors (for Model)\n\t\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tif (trans.get(i).isEmpty() && (except == null || !except.get(i)))\n\t\t\t\tthrow new PrismException(\"Game has a deadlock in state \" + i + (statesList == null ? \"\" : \": \" + statesList.get(i)));\n\t\t}\n\t}\n\t\n\t// Accessors (for STPG)\n\t\n\t@Override\n\tpublic int getPlayer(int s)\n\t{\n\t\treturn stateOwners.getPlayer(s);\n\t}\n\t\n\t@Override\n\tpublic void prob0step(BitSet subset, BitSet u, boolean forall1, boolean forall2, BitSet result)\n\t{\n\t\tint i;\n\t\tboolean b1, b2;\n\t\tboolean forall = false;\n\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tif (subset.get(i)) {\n\t\t\t\tforall = (getPlayer(i) == 0) ? forall1 : forall2;\n\t\t\t\tb1 = forall; // there exists or for all\n\t\t\t\tfor (Distribution<?> distr : trans.get(i)) {\n\t\t\t\t\tb2 = distr.containsOneOf(u);\n\t\t\t\t\tif (forall) {\n\t\t\t\t\t\tif (!b2) {\n\t\t\t\t\t\t\tb1 = false;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (b2) {\n\t\t\t\t\t\t\tb1 = true;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tresult.set(i, b1);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void prob1step(BitSet subset, BitSet u, BitSet v, boolean forall1, boolean forall2, BitSet result)\n\t{\n\t\tint i;\n\t\tboolean b1, b2;\n\t\tboolean forall = false;\n\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tif (subset.get(i)) {\n\t\t\t\tforall = (getPlayer(i) == 0) ? forall1 : forall2;\n\t\t\t\tb1 = forall; // there exists or for all\n\t\t\t\tfor (Distribution<?> distr : trans.get(i)) {\n\t\t\t\t\tb2 = distr.containsOneOf(v) && distr.isSubsetOf(u);\n\t\t\t\t\tif (forall) {\n\t\t\t\t\t\tif (!b2) {\n\t\t\t\t\t\t\tb1 = false;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (b2) {\n\t\t\t\t\t\t\tb1 = true;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tresult.set(i, b1);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void mvMultMinMax(double vect[], boolean min1, boolean min2, double result[], BitSet subset, boolean complement, int adv[])\n\t{\n\t\tint s;\n\t\tboolean min = false;\n\t\t// Loop depends on subset/complement arguments\n\t\tif (subset == null) {\n\t\t\tfor (s = 0; s < numStates; s++) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\tresult[s] = mvMultMinMaxSingle(s, vect, min, adv);\n\t\t\t}\n\t\t} else if (complement) {\n\t\t\tfor (s = subset.nextClearBit(0); s < numStates; s = subset.nextClearBit(s + 1)) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\tresult[s] = mvMultMinMaxSingle(s, vect, min, adv);\n\t\t\t}\n\t\t} else {\n\t\t\tfor (s = subset.nextSetBit(0); s >= 0; s = subset.nextSetBit(s + 1)) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\tresult[s] = mvMultMinMaxSingle(s, vect, min, adv);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic double mvMultMinMaxSingle(int s, double vect[], boolean min1, boolean min2)\n\t{\n\t\tboolean min = (getPlayer(s) == 0) ? min1 : min2;\n\t\treturn mvMultMinMaxSingle(s, vect, min, null);\n\t}\n\n\t@Override\n\tpublic List<Integer> mvMultMinMaxSingleChoices(int s, double vect[], boolean min1, boolean min2, double val)\n\t{\n\t\tboolean min = (getPlayer(s) == 0) ? min1 : min2;\n\t\treturn mvMultMinMaxSingleChoices(s, vect, min, val);\n\t}\n\n\t@Override\n\tpublic double mvMultGSMinMax(double vect[], boolean min1, boolean min2, BitSet subset, boolean complement, boolean absolute, int[] adv)\n\t{\n\t\tint s;\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\t// Loop depends on subset/complement arguments\n\t\tif (subset == null) {\n\t\t\tfor (s = 0; s < numStates; s++) {\n\t\t\t\td = mvMultJacMinMaxSingle(s, vect, min1, min2, adv);\n\t\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\t\tvect[s] = d;\n\t\t\t}\n\t\t} else if (complement) {\n\t\t\tfor (s = subset.nextClearBit(0); s < numStates; s = subset.nextClearBit(s + 1)) {\n\t\t\t\td = mvMultJacMinMaxSingle(s, vect, min1, min2, adv);\n\t\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\t\tvect[s] = d;\n\t\t\t}\n\t\t} else {\n\t\t\tfor (s = subset.nextSetBit(0); s >= 0; s = subset.nextSetBit(s + 1)) {\n\t\t\t\td = mvMultJacMinMaxSingle(s, vect, min1, min2, adv);\n\t\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\t\tvect[s] = d;\n\t\t\t}\n\t\t}\n\t\treturn maxDiff;\n\t}\n\n\t@Override\n\tpublic double mvMultJacMinMaxSingle(int s, double vect[], boolean min1, boolean min2, int[] adv)\n\t{\n\t\tboolean min = (getPlayer(s) == 0) ? min1 : min2;\n\t\treturn mvMultJacMinMaxSingle(s, vect, min, adv);\n\t}\n\n\t@Override\n\tpublic void mvMultRewMinMax(double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, double result[], BitSet subset, boolean complement, int adv[])\n\t{\n\t\tint s;\n\t\tboolean min = false;\n\t\t// Loop depends on subset/complement arguments\n\t\tif (subset == null) {\n\t\t\tfor (s = 0; s < numStates; s++) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, rewards, min, adv, 1.0);\n\t\t\t}\n\t\t} else if (complement) {\n\t\t\tfor (s = subset.nextClearBit(0); s < numStates; s = subset.nextClearBit(s + 1)) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, rewards, min, adv, 1.0);\n\t\t\t}\n\t\t} else {\n\t\t\tfor (s = subset.nextSetBit(0); s >= 0; s = subset.nextSetBit(s + 1)) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, rewards, min, adv, 1.0);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic double mvMultRewMinMaxSingle(int s, double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, int adv[])\n\t{\n\t\tboolean min = (getPlayer(s) == 0) ? min1 : min2;\n\t\treturn mvMultRewMinMaxSingle(s, vect, rewards, min, adv);\n\t}\n\n\t@Override\n\tpublic List<Integer> mvMultRewMinMaxSingleChoices(int s, double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, double val)\n\t{\n\t\tboolean min = (getPlayer(s) == 0) ? min1 : min2;\n\t\treturn mvMultRewMinMaxSingleChoices(s, vect, rewards, min, val);\n\t}\n\n\t@Override\n\tpublic void mvMultRewMinMax(double vect[], STPGRewards<Double> rewards, boolean min1, boolean min2, double result[], BitSet subset, boolean complement, int adv[], double disc)\n\t{\n\t\tint s;\n\t\tboolean min = false;\n\t\t// Loop depends on subset/complement arguments\n\t\tif (subset == null) {\n\t\t\tfor (s = 0; s < numStates; s++) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, rewards, min, adv, disc);\n\t\t\t}\n\t\t} else if (complement) {\n\t\t\tfor (s = subset.nextClearBit(0); s < numStates; s = subset.nextClearBit(s + 1)) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, rewards, min, adv, disc);\n\t\t\t}\n\t\t} else {\n\t\t\tfor (s = subset.nextSetBit(0); s >= 0; s = subset.nextSetBit(s + 1)) {\n\t\t\t\tmin = (getPlayer(s) == 0) ? min1 : min2;\n\t\t\t\t//System.out.printf(\"s: %s, min1: %s, min2: %s, min: %s, player: %d\\n\", s, min1, min2, min, getPlayer(s));\n\t\t\t\tresult[s] = mvMultRewMinMaxSingle(s, vect, rewards, min, adv, disc);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of (discounted) matrix-vector multiplication and sum of action reward followed by min/max.\n\t * i.e. return min/max_{k1,k2} { rew(s) + disc * sum_j P_{k1,k2}(s,j)*vect[j] }\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param min Min or max (true=min, false=max)\n\t * @param adv Storage for adversary choice indices (ignored if null)\n\t * @param disc Discount factor\n\t */\n\tpublic double mvMultRewMinMaxSingle(int s, double vect[], MDPRewards<Double> mdpRewards, boolean min, int adv[], double disc)\n\t{\n\t\tint j, k, advCh = -1;\n\t\tdouble d, prob, minmax;\n\t\tboolean first;\n\t\tList<Distribution<Value>> step;\n\n\t\tminmax = 0;\n\t\tfirst = true;\n\t\tj = -1;\n\t\tstep = trans.get(s);\n\t\tfor (Distribution<Value> distr : step) {\n\t\t\tj++;\n\t\t\t// Compute sum for this distribution\n\t\t\td = mdpRewards.getTransitionReward(s, j);\n\n\t\t\tfor (Map.Entry<Integer, Value> e : distr) {\n\t\t\t\tk = e.getKey();\n\t\t\t\tprob = getEvaluator().toDouble(e.getValue());\n\t\t\t\td += prob * vect[k] * disc;\n\t\t\t}\n\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If adversary generation is enabled, remember optimal choice\n\t\t\t\tif (adv != null) {\n\t\t\t\t\tadvCh = j;\n\t\t\t\t}\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If adversary generation is enabled, store optimal choice\n\t\tif (adv != null & !first) {\n\t\t\t// Only remember strictly better choices (required for max)\n\t\t\tif (adv[s] == -1 || (min && minmax < vect[s]) || (!min && minmax > vect[s]) || this instanceof STPG) {\n\t\t\t\tadv[s] = advCh;\n\t\t\t}\n\t\t}\n\n\t\t// Add state reward (doesn't affect min/max)\n\t\tminmax += mdpRewards.getStateReward(s);\n\n\t\treturn minmax;\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, j, n;\n\t\tObject o;\n\t\tString s = \"\";\n\t\ts = \"[ \";\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tif (i > 0)\n\t\t\t\ts += \", \";\n\t\t\tif (statesList.size() > i)\n\t\t\t\ts += i + \"(P-\" + (stateOwners.getPlayer(i)+1) + \" \" + statesList.get(i) + \"): \";\n\t\t\telse\n\t\t\t\ts += i + \"(P-\" + (stateOwners.getPlayer(i)+1) + \"): \";\n\t\t\ts += \"[\";\n\t\t\tn = getNumChoices(i);\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tif (j > 0)\n\t\t\t\t\ts += \",\";\n\t\t\t\to = getAction(i, j);\n\t\t\t\tif (o != null)\n\t\t\t\t\ts += o + \":\";\n\t\t\t\ts += trans.get(i).get(j);\n\t\t\t}\n\t\t\ts += \"]\";\n\t\t}\n\t\ts += \" ]\\n\";\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/StateModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.File;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\nimport java.util.TreeSet;\nimport java.util.Vector;\n\nimport common.Interval;\nimport explicit.rewards.ConstructRewards;\nimport explicit.rewards.Rewards;\nimport io.DotExporter;\nimport io.DRNExporter;\nimport io.UMBExporter;\nimport io.MatlabExporter;\nimport io.ModelExportFormat;\nimport io.ModelExportOptions;\nimport io.ModelExportTask;\nimport io.ModelExporter;\nimport io.PrismExplicitExporter;\nimport io.PrismExplicitImporter;\nimport parser.EvaluateContext.EvalMode;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationIntUnbounded;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.ExpressionFilter;\nimport parser.ast.ExpressionFilter.FilterOperator;\nimport parser.ast.ExpressionFormula;\nimport parser.ast.ExpressionFunc;\nimport parser.ast.ExpressionITE;\nimport parser.ast.ExpressionIdent;\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionLiteral;\nimport parser.ast.ExpressionObs;\nimport parser.ast.ExpressionProp;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.ast.ExpressionVar;\nimport parser.ast.LabelList;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.visitor.ASTTraverseModify;\nimport parser.visitor.ReplaceLabels;\nimport prism.Accuracy;\nimport prism.Evaluator;\nimport prism.Filter;\nimport prism.ModelInfo;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLangException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport prism.Result;\nimport prism.RewardGenerator;\n\n/**\n * Super class for explicit-state model checkers.\n * <br>\n * This model checker class and its subclasses store their settings locally so\n * that they can be configured and used without a PrismSettings object.\n * Pass in null as a parent on creation to bypass the use of PrismSettings.\n */\npublic class StateModelChecker extends PrismComponent\n{\n\t// Flags/settings that can be extracted from PrismSettings\n\t// (NB: defaults do not necessarily coincide with PRISM)\n\n\t// Verbosity level\n\tprotected int verbosity = 0;\n\n\t// Additional flags/settings not included in PrismSettings\n\n\t// Export target state info?\n\tprotected boolean exportTarget = false;\n\tprotected String exportTargetFilename = null;\n\t\n\t// Export product model info?\n\tprotected boolean exportProductTrans = false;\n\tprotected String exportProductTransFilename = null;\n\tprotected boolean exportProductStates = false;\n\tprotected String exportProductStatesFilename = null;\n\tprotected boolean exportProductVector = false;\n\tprotected String exportProductVectorFilename = null;\n\t\n\t// Store the final results vector after model checking?\n\tprotected boolean storeVector = false;\n\n\t// Generate/store a strategy during model checking?\n\tprotected boolean genStrat = false;\n\t// Should any generated strategies should be restricted to the states reachable under them?\n\tprotected boolean restrictStratToReach = true;\n\n\t// Do bisimulation minimisation before model checking?\n\tprotected boolean doBisim = false;\n\n\t// Do topological value iteration?\n\tprotected boolean doTopologicalValueIteration = false;\n\n\t// For Pmax computation, collapse MECs to quotient MDP?\n\tprotected boolean doPmaxQuotient = false;\n\n\t// Do interval iteration?\n\tprotected boolean doIntervalIteration = false;\n\n\t// Model info (for reward structures, etc.)\n\tprotected ModulesFile modulesFile = null;\n\tprotected ModelInfo modelInfo = null;\n\tprotected RewardGenerator<?> rewardGen = null;\n\n\t// Properties file (for labels, constants, etc.)\n\tprotected PropertiesFile propertiesFile = null;\n\n\t// Constants (extracted from model/properties)\n\tprotected Values constantValues;\n\n\t// The filter to be applied to the current property\n\tprotected Filter currentFilter;\n\n\t// The result of model checking will be stored here\n\tprotected Result result;\n\n\t/**\n\t * Create a new StateModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic StateModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\n\t\t// For explicit.StateModelChecker and its subclasses, we explicitly set 'settings'\n\t\t// to null if there is no parent or if the parent has a null 'settings'.\n\t\t// This allows us to choose to ignore the default one created by PrismComponent.\n\t\tif (parent == null || parent.getSettings() == null)\n\t\t\tsetSettings(null);\n\n\t\t// If present, initialise settings from PrismSettings\n\t\tif (settings != null) {\n\t\t\tverbosity = settings.getBoolean(PrismSettings.PRISM_VERBOSE) ? 10 : 1;\n\t\t\tsetDoIntervalIteration(settings.getBoolean(PrismSettings.PRISM_INTERVAL_ITER));\n\t\t\tsetDoTopologicalValueIteration(settings.getBoolean(PrismSettings.PRISM_TOPOLOGICAL_VI));\n\t\t\tsetDoPmaxQuotient(settings.getBoolean(PrismSettings.PRISM_PMAX_QUOTIENT));\n\t\t}\n\t}\n\n\t/**\n\t * Create a model checker (a subclass of this one) for a given model type.\n\t */\n\tpublic static StateModelChecker createModelChecker(ModelType modelType) throws PrismException\n\t{\n\t\treturn createModelChecker(modelType, null);\n\t}\n\n\t/**\n\t * Create a model checker (a subclass of this one) for a given model type\n\t */\n\tpublic static StateModelChecker createModelChecker(ModelType modelType, PrismComponent parent) throws PrismException\n\t{\n\t\texplicit.StateModelChecker mc = null;\n\t\tswitch (modelType) {\n\t\tcase DTMC:\n\t\t\tmc = new DTMCModelChecker(parent);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tmc = new MDPModelChecker(parent);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tmc = new CTMCModelChecker(parent);\n\t\t\tbreak;\n\t\tcase POMDP:\n\t\t\tmc = new POMDPModelChecker(parent);\n\t\t\tbreak;\n\t\tcase CTMDP:\n\t\t\tmc = new CTMDPModelChecker(parent);\n\t\t\tbreak;\n\t\tcase STPG:\n\t\t\tmc = new STPGModelChecker(parent);\n\t\t\tbreak;\n\t\tcase IDTMC:\n\t\t\tmc = new UDTMCModelChecker(parent);\n\t\t\tbreak;\n\t\tcase IMDP:\n\t\t\tmc = new UMDPModelChecker(parent);\n\t\t\tbreak;\n\t\tcase IPOMDP:\n\t\t\t// For model construction, this suffices\n\t\t\tmc = new UMDPModelChecker(parent);\n\t\t\tbreak;\n\t\tcase LTS:\n\t\t\tmc = new NonProbModelChecker(parent);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Cannot create model checker for model type \" + modelType);\n\t\t}\n\t\treturn mc;\n\t}\n\n\t// Settings methods\n\n\t/**\n\t * Inherit settings (and the log) from another StateModelChecker object.\n\t * For model checker objects that inherit a PrismSettings object, this is superfluous\n\t * since this has been done already.\n\t */\n\tpublic void inheritSettings(StateModelChecker other)\n\t{\n\t\tsetModelCheckingInfo(other.modelInfo, other.propertiesFile, other.rewardGen);\n\t\tsetLog(other.getLog());\n\t\tresult = other.result;\n\t\tsetVerbosity(other.getVerbosity());\n\t\tsetExportTarget(other.getExportTarget());\n\t\tsetExportTargetFilename(other.getExportTargetFilename());\n\t\tsetExportProductTrans(other.getExportProductTrans());\n\t\tsetExportProductTransFilename(other.getExportProductTransFilename());\n\t\tsetExportProductStates(other.getExportProductStates());\n\t\tsetExportProductStatesFilename(other.getExportProductStatesFilename());\n\t\tsetExportProductVector(other.getExportProductVector());\n\t\tsetExportProductVectorFilename(other.getExportProductVectorFilename());\n\t\tsetStoreVector(other.getStoreVector());\n\t\tsetGenStrat(other.getGenStrat());\n\t\tsetRestrictStratToReach(other.getRestrictStratToReach());\n\t\tsetDoBisim(other.getDoBisim());\n\t\tsetDoIntervalIteration(other.getDoIntervalIteration());\n\t\tsetDoPmaxQuotient(other.getDoPmaxQuotient());\n\t}\n\n\t/**\n\t * Print summary of current settings.\n\t */\n\tpublic void printSettings()\n\t{\n\t\tmainLog.print(\"verbosity = \" + verbosity + \" \");\n\t}\n\n\t// Set methods for flags/settings\n\n\t/**\n\t * Set verbosity level, i.e. amount of output produced.\n\t */\n\tpublic void setVerbosity(int verbosity)\n\t{\n\t\tthis.verbosity = verbosity;\n\t}\n\n\tpublic void setExportTarget(boolean b)\n\t{\n\t\texportTarget = b;\n\t}\n\n\tpublic void setExportTargetFilename(String s)\n\t{\n\t\texportTargetFilename = s;\n\t}\n\n\tpublic void setExportProductTrans(boolean b)\n\t{\n\t\texportProductTrans = b;\n\t}\n\n\tpublic void setExportProductTransFilename(String s)\n\t{\n\t\texportProductTransFilename = s;\n\t}\n\n\tpublic void setExportProductStates(boolean b)\n\t{\n\t\texportProductStates = b;\n\t}\n\n\tpublic void setExportProductStatesFilename(String s)\n\t{\n\t\texportProductStatesFilename = s;\n\t}\n\n\tpublic void setExportProductVector(boolean b)\n\t{\n\t\texportProductVector = b;\n\t}\n\n\tpublic void setExportProductVectorFilename(String s)\n\t{\n\t\texportProductVectorFilename = s;\n\t}\n\n\t/**\n\t * Specify whether or not to store the final results vector after model checking.\n\t */\n\tpublic void setStoreVector(boolean storeVector)\n\t{\n\t\tthis.storeVector = storeVector;\n\t}\n\n\t/**\n\t * Specify whether or not a strategy should be generated during model checking.\n\t */\n\tpublic void setGenStrat(boolean genStrat)\n\t{\n\t\tthis.genStrat = genStrat;\n\t}\n\n\t/**\n\t * Specify whether or not any generated strategies should be restricted to the states reachable under them.\n\t */\n\tpublic void setRestrictStratToReach(boolean restrictStratToReach)\n\t{\n\t\tthis.restrictStratToReach = restrictStratToReach;\n\t}\n\n\t/**\n\t * Specify whether or not to do bisimulation minimisation before model checking.\n\t */\n\tpublic void setDoBisim(boolean doBisim)\n\t{\n\t\tthis.doBisim = doBisim;\n\t}\n\n\t/**\n\t * Specify whether or not to do topological value iteration.\n\t */\n\tpublic void setDoTopologicalValueIteration(boolean doTopologicalValueIteration)\n\t{\n\t\tthis.doTopologicalValueIteration = doTopologicalValueIteration;\n\t}\n\n\t/**\n\t * Specify whether or not to perform MEC quotienting for Pmax.\n\t */\n\tpublic void setDoPmaxQuotient(boolean doPmaxQuotient)\n\t{\n\t\tthis.doPmaxQuotient = doPmaxQuotient;\n\t}\n\n\t/**\n\t * Specify whether or not to use interval iteration.\n\t */\n\tpublic void setDoIntervalIteration(boolean doIntervalIteration)\n\t{\n\t\tthis.doIntervalIteration = doIntervalIteration;\n\t}\n\n\t// Get methods for flags/settings\n\n\tpublic int getVerbosity()\n\t{\n\t\treturn verbosity;\n\t}\n\n\tpublic boolean getExportTarget()\n\t{\n\t\treturn exportTarget;\n\t}\n\n\tpublic String getExportTargetFilename()\n\t{\n\t\treturn exportTargetFilename;\n\t}\n\n\tpublic boolean getExportProductTrans()\n\t{\n\t\treturn exportProductTrans;\n\t}\n\n\tpublic String getExportProductTransFilename()\n\t{\n\t\treturn exportProductTransFilename;\n\t}\n\n\tpublic boolean getExportProductStates()\n\t{\n\t\treturn exportProductStates;\n\t}\n\n\tpublic String getExportProductStatesFilename()\n\t{\n\t\treturn exportProductStatesFilename;\n\t}\n\n\tpublic boolean getExportProductVector()\n\t{\n\t\treturn exportProductVector;\n\t}\n\n\tpublic String getExportProductVectorFilename()\n\t{\n\t\treturn exportProductVectorFilename;\n\t}\n\n\t/**\n\t * Whether or not to store the final results vector after model checking.\n\t */\n\tpublic boolean getStoreVector()\n\t{\n\t\treturn storeVector;\n\t}\n\n\t/**\n\t * Whether or not a strategy should be generated during model checking.\n\t */\n\tpublic boolean getGenStrat()\n\t{\n\t\treturn genStrat;\n\t}\n\n\t/**\n\t * Whether or not any generated strategies should be restricted to the states reachable under them.\n\t */\n\tpublic boolean getRestrictStratToReach()\n\t{\n\t\treturn restrictStratToReach;\n\t}\n\n\t/**\n\t * Whether or not to do bisimulation minimisation before model checking.\n\t */\n\tpublic boolean getDoBisim()\n\t{\n\t\treturn doBisim;\n\t}\n\n\t/**\n\t * Whether or not to do topological value iteration.\n\t */\n\tpublic boolean getDoTopologicalValueIteration()\n\t{\n\t\treturn doTopologicalValueIteration;\n\t}\n\n\t/**\n\t * Whether or not to do MEC quotient for Pmax\n\t */\n\tpublic boolean getDoPmaxQuotient()\n\t{\n\t\treturn doPmaxQuotient;\n\t}\n\n\t/**\n\t * Whether or not to use interval iteration.\n\t */\n\tpublic boolean getDoIntervalIteration()\n\t{\n\t\treturn doIntervalIteration;\n\t}\n\n\t/** Get the constant values (both from the modules file and the properties file) */\n\tpublic Values getConstantValues()\n\t{\n\t\treturn constantValues;\n\t}\n\n\t/**\n\t * Get the label list (from properties file and modules file, if they are attached).\n\t * @return the label list for the properties/modules file, or {@code null} if not available.\n\t */\n\tpublic LabelList getLabelList()\n\t{\n\t\tif (propertiesFile != null) {\n\t\t\treturn propertiesFile.getCombinedLabelList(); // combined list from properties and modules file\n\t\t} else if (modulesFile != null) {\n\t\t\treturn modulesFile.getLabelList();\n\t\t} else {\n\t\t\treturn null;\n\t\t}\n\t}\n\n\t/**\n\t * Return the set of label names that are defined\n\t * either by the model (from the model info or modules file)\n\t * or properties file (if attached to the model checker).\n\t */\n\tpublic Set<String> getDefinedLabelNames()\n\t{\n\t\tTreeSet<String> definedLabelNames = new TreeSet<String>();\n\n\t\t// labels from the label list\n\t\tLabelList labelList = getLabelList();\n\t\tif (labelList != null) {\n\t\t\tdefinedLabelNames.addAll(labelList.getLabelNames());\n\t\t}\n\n\t\t// labels from the model info\n\t\tif (modelInfo != null) {\n\t\t\tdefinedLabelNames.addAll(modelInfo.getLabelNames());\n\t\t}\n\n\t\treturn definedLabelNames;\n\t}\n\n\t// Other setters/getters\n\n\t/**\n\t * Set the attached model file (for e.g. reward structures when model checking)\n\t * and the attached properties file (for e.g. constants/labels when model checking)\n\t */\n\tpublic void setModelCheckingInfo(ModelInfo modelInfo, PropertiesFile propertiesFile, RewardGenerator<?> rewardGen)\n\t{\n\t\tthis.modelInfo = modelInfo;\n\t\tif (modelInfo instanceof ModulesFile) {\n\t\t\tthis.modulesFile = (ModulesFile) modelInfo;\n\t\t}\n\t\tthis.propertiesFile = propertiesFile;\n\t\tthis.rewardGen = rewardGen;\n\t\t// Get combined constant values from model/properties\n\t\tconstantValues = new Values();\n\t\tif (modelInfo != null)\n\t\t\tconstantValues.addValues(modelInfo.getConstantValues());\n\t\tif (propertiesFile != null)\n\t\t\tconstantValues.addValues(propertiesFile.getConstantValues());\n\t}\n\n\t// Model checking functions\n\n\t/**\n\t * Model check an expression, process and return the result.\n\t * Information about states and model constants should be attached to the model.\n\t * For other required info (labels, reward structures, etc.), use the method\n\t * {@link #setModelCheckingInfo(ModelInfo, PropertiesFile, RewardGenerator)}.\n\t * to attach the original model/properties files.\n\t */\n\tpublic <Value> Result check(Model<Value> model, Expression expr) throws PrismException\n\t{\n\t\tlong timer = 0;\n\t\tStateValues vals;\n\t\tString resultString;\n\n\t\t// Create storage for result\n\t\tresult = new Result();\n\n\t\t// Remove any existing filter info\n\t\tcurrentFilter = null;\n\n\t\t// If we need to store a copy of the results vector, add a \"store\" filter to represent this\n\t\tif (storeVector) {\n\t\t\tExpressionFilter exprFilter = new ExpressionFilter(\"store\", expr);\n\t\t\texprFilter.setInvisible(true);\n\t\t\texprFilter.typeCheck();\n\t\t\texpr = exprFilter;\n\t\t}\n\t\t// Wrap a filter round the property, if needed\n\t\t// (in order to extract the final result of model checking) \n\t\texpr = ExpressionFilter.addDefaultFilterIfNeeded(expr, model.getNumInitialStates() == 1);\n\n\t\t// If required, do bisimulation minimisation\n\t\tif (doBisim) {\n\t\t\tmainLog.println(\"\\nPerforming bisimulation minimisation...\");\n\t\t\tArrayList<String> propNames = new ArrayList<String>();\n\t\t\tArrayList<BitSet> propBSs = new ArrayList<BitSet>();\n\t\t\tExpression exprNew = checkMaximalPropositionalFormulas(model, expr.deepCopy(), propNames, propBSs);\n\t\t\tBisimulation<Value> bisim = new Bisimulation<>(this);\n\t\t\tmodel = bisim.minimise(model, propNames, propBSs);\n\t\t\tmainLog.println(\"Modified property: \" + exprNew);\n\t\t\texpr = exprNew;\n\t\t\t//model.exportToPrismExplicitTra(\"bisim.tra\");\n\t\t\t//model.exportStates(modelInfo.createVarList(), new PrismFileLog(\"bisim.sta\"), new ModelExportOptions());\n\t\t}\n\n\t\t// Do model checking and store result vector\n\t\ttimer = System.currentTimeMillis();\n\t\t// check expression for all states (null => statesOfInterest=all)\n\t\tvals = checkExpression(model, expr, null);\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"\\nTime for model checking: \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Print result to log\n\t\tresultString = \"Result\";\n\t\tif (!(\"Result\".equals(expr.getResultName())))\n\t\t\tresultString += \" (\" + expr.getResultName().toLowerCase() + \")\";\n\t\tresultString += \": \" + result.getResultAndAccuracy();\n\t\tmainLog.print(\"\\n\" + resultString + \"\\n\");\n\n\t\t// Clean up\n\t\t//vals.clear();\n\n\t\t// Return result\n\t\treturn result;\n\t}\n\n\t/**\n\t * Model check an expression and return a vector result values over all states.\n\t * Information about states and model constants should be attached to the model.\n\t * For other required info (labels, reward structures, etc.), use the method\n\t * {@link #setModelCheckingInfo(ModelInfo, PropertiesFile, RewardGenerator)}.\n\t * @param statesOfInterest a set of states for which results should be calculated (null = all states).\n\t *        The calculated values for states not of interest are arbitrary and should to be ignored.\n\t */\n\tpublic StateValues checkExpression(Model<?> model, Expression expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res = null;\n\n\t\t// If-then-else\n\t\tif (expr instanceof ExpressionITE) {\n\t\t\tres = checkExpressionITE(model, (ExpressionITE) expr, statesOfInterest);\n\t\t}\n\t\t// Binary ops\n\t\telse if (expr instanceof ExpressionBinaryOp) {\n\t\t\tres = checkExpressionBinaryOp(model, (ExpressionBinaryOp) expr, statesOfInterest);\n\t\t}\n\t\t// Unary ops\n\t\telse if (expr instanceof ExpressionUnaryOp) {\n\t\t\tres = checkExpressionUnaryOp(model, (ExpressionUnaryOp) expr, statesOfInterest);\n\t\t}\n\t\t// Functions\n\t\telse if (expr instanceof ExpressionFunc) {\n\t\t\tres = checkExpressionFunc(model, (ExpressionFunc) expr, statesOfInterest);\n\t\t}\n\t\t// Identifiers\n\t\telse if (expr instanceof ExpressionIdent) {\n\t\t\t// Should never happen\n\t\t\tthrow new PrismException(\"Unknown identifier \\\"\" + ((ExpressionIdent) expr).getName() + \"\\\"\");\n\t\t}\n\t\t// Literals\n\t\telse if (expr instanceof ExpressionLiteral) {\n\t\t\tres = checkExpressionLiteral(model, (ExpressionLiteral) expr);\n\t\t}\n\t\t// Constants\n\t\telse if (expr instanceof ExpressionConstant) {\n\t\t\tres = checkExpressionConstant(model, (ExpressionConstant) expr);\n\t\t}\n\t\t// Formulas\n\t\telse if (expr instanceof ExpressionFormula) {\n\t\t\t// This should have been defined or expanded by now.\n\t\t\tif (((ExpressionFormula) expr).getDefinition() != null)\n\t\t\t\treturn checkExpression(model, ((ExpressionFormula) expr).getDefinition(), statesOfInterest);\n\t\t\telse\n\t\t\t\tthrow new PrismException(\"Unexpanded formula \\\"\" + ((ExpressionFormula) expr).getName() + \"\\\"\");\n\t\t}\n\t\t// Variables\n\t\telse if (expr instanceof ExpressionVar) {\n\t\t\tres = checkExpressionVar(model, (ExpressionVar) expr, statesOfInterest);\n\t\t}\n\t\t// Observables\n\t\telse if (expr instanceof ExpressionObs) {\n\t\t\tres = checkExpressionObs(model, (ExpressionObs) expr, statesOfInterest);\n\t\t}\n\t\t// Labels\n\t\telse if (expr instanceof ExpressionLabel) {\n\t\t\tres = checkExpressionLabel(model, (ExpressionLabel) expr, statesOfInterest);\n\t\t}\n\t\t// Property refs\n\t\telse if (expr instanceof ExpressionProp) {\n\t\t\tres = checkExpressionProp(model, (ExpressionProp) expr, statesOfInterest);\n\t\t}\n\t\t// Filter\n\t\telse if (expr instanceof ExpressionFilter) {\n\t\t\tres = checkExpressionFilter(model, (ExpressionFilter) expr, statesOfInterest);\n\t\t}\n\t\t// Anything else - error\n\t\telse {\n\t\t\tthrow new PrismNotSupportedException(\"Couldn't check \" + expr.getClass());\n\t\t}\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check a binary operator.\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionITE(Model<?> model, ExpressionITE expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null, res2 = null, res3 = null;\n\n\t\ttry {\n\t\t\t// Check operand 1 (condition) recursively\n\t\t\tres1 = checkExpression(model, expr.getOperand1(), statesOfInterest);\n\t\t\t// Compute new statesOfInterest sets to implement short-circuiting\n\t\t\tBitSet statesOfInterestThen = (BitSet) res1.getBitSet().clone();\n\t\t\tBitSet statesOfInterestElse = (BitSet) statesOfInterestThen.clone();\n\t\t\tstatesOfInterestElse.flip(0, model.getNumStates());\n\t\t\tif (statesOfInterest != null) {\n\t\t\t\tstatesOfInterestThen.and(statesOfInterest);\n\t\t\t\tstatesOfInterestElse.and(statesOfInterest);\n\t\t\t}\n\t\t\t// Check operands 2 and 3 (then/else) recursively,\n\t\t\t// but only where needed, to implement short-circuiting\n\t\t\tres2 = checkExpression(model, expr.getOperand2(), statesOfInterestThen);\n\t\t\tres3 = checkExpression(model, expr.getOperand3(), statesOfInterestElse);\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tif (res2 != null)\n\t\t\t\tres2.clear();\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Apply operation\n\t\tres1.applyFunction(expr.getType(), (v1, v2, v3) -> expr.apply(v1, v2, v3, EvalMode.FP), res2, res3, statesOfInterest);\n\t\tres2.clear();\n\t\tres3.clear();\n\n\t\treturn res1;\n\t}\n\n\t/**\n\t * Model check a binary operator.\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionBinaryOp(Model<?> model, ExpressionBinaryOp expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null, res2 = null;\n\n\t\t// Check operands recursively\n\t\ttry {\n\t\t\t// Check operand 1 recursively\n\t\t\tres1 = checkExpression(model, expr.getOperand1(), statesOfInterest);\n\t\t\t// Where short-circuiting is needed, see which states remain to be considered\n\t\t\tBitSet statesOfInterestRhs = null;\n\t\t\tswitch (expr.getOperator()) {\n\t\t\tcase ExpressionBinaryOp.IMPLIES:\n\t\t\tcase ExpressionBinaryOp.AND:\n\t\t\t\tstatesOfInterestRhs = (BitSet) res1.getBitSet().clone();\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.OR:\n\t\t\t\tstatesOfInterestRhs = (BitSet) res1.getBitSet().clone();\n\t\t\t\tstatesOfInterestRhs.flip(0, model.getNumStates());\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tstatesOfInterestRhs = statesOfInterest;\n\t\t\t}\n\t\t\tif (statesOfInterestRhs != null && statesOfInterest != null) {\n\t\t\t\tstatesOfInterestRhs.and(statesOfInterest);\n\t\t\t}\n\t\t\t// Check operand 2 recursively, but only where needed, to implement short-circuiting\n\t\t\tres2 = checkExpression(model, expr.getOperand2(), statesOfInterestRhs);\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Apply operation\n\t\tres1.applyFunction(expr.getType(), (v1, v2) -> expr.apply(v1, v2, EvalMode.FP), res2, statesOfInterest);\n\t\tres2.clear();\n\n\t\treturn res1;\n\t}\n\n\t/**\n\t * Model check a unary operator.\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionUnaryOp(Model<?> model, ExpressionUnaryOp expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null;\n\t\tint op = expr.getOperator();\n\n\t\t// Check operand recursively\n\t\tres1 = checkExpression(model, expr.getOperand(), statesOfInterest);\n\n\t\t// Parentheses are easy - nothing to do:\n\t\tif (op == ExpressionUnaryOp.PARENTH)\n\t\t\treturn res1;\n\n\t\t// Apply operation\n\t\tres1.applyFunction(expr.getType(), v -> expr.apply(v, EvalMode.FP), statesOfInterest);\n\n\t\treturn res1;\n\t}\n\n\t/**\n\t * Model check a function.\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionFunc(Model<?> model, ExpressionFunc expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tswitch (expr.getNameCode()) {\n\t\tcase ExpressionFunc.MIN:\n\t\tcase ExpressionFunc.MAX:\n\t\t\treturn checkExpressionFuncNary(model, expr, statesOfInterest);\n\t\tcase ExpressionFunc.FLOOR:\n\t\tcase ExpressionFunc.CEIL:\n\t\tcase ExpressionFunc.ROUND:\n\t\t\treturn checkExpressionFuncUnary(model, expr, statesOfInterest);\n\t\tcase ExpressionFunc.POW:\n\t\tcase ExpressionFunc.MOD:\n\t\tcase ExpressionFunc.LOG:\n\t\t\treturn checkExpressionFuncBinary(model, expr, statesOfInterest);\n\t\tcase ExpressionFunc.MULTI:\n\t\t\tthrow new PrismNotSupportedException(\"Multi-objective model checking is not supported for \" + model.getModelType() + \"s with the explicit engine\");\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unrecognised function \\\"\" + expr.getName() + \"\\\"\");\n\t\t}\n\t}\n\n\tprotected StateValues checkExpressionFuncUnary(Model<?> model, ExpressionFunc expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Check operand recursively\n\t\tStateValues res1 = checkExpression(model, expr.getOperand(0), statesOfInterest);\n\n\t\t// Apply operation\n\t\ttry {\n\t\t\tres1.applyFunction(expr.getType(), v -> expr.applyUnary(v, EvalMode.FP), statesOfInterest);\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tif (e instanceof PrismLangException)\n\t\t\t\t((PrismLangException) e).setASTElement(expr);\n\t\t\tthrow e;\n\t\t}\n\n\t\treturn res1;\n\t}\n\n\tprotected StateValues checkExpressionFuncBinary(Model<?> model, ExpressionFunc expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Check operands recursively\n\t\tStateValues res1 = null, res2 = null;\n\t\ttry {\n\t\t\tres1 = checkExpression(model, expr.getOperand(0), statesOfInterest);\n\t\t\tres2 = checkExpression(model, expr.getOperand(1), statesOfInterest);\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Apply operation\n\t\ttry {\n\t\t\tres1.applyFunction(expr.getType(), (v1, v2) -> expr.applyBinary(v1, v2, EvalMode.FP), res2, statesOfInterest);\n\t\t\tres2.clear();\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tif (res2 != null)\n\t\t\t\tres2.clear();\n\t\t\tif (e instanceof PrismLangException)\n\t\t\t\t((PrismLangException) e).setASTElement(expr);\n\t\t\tthrow e;\n\t\t}\n\n\t\treturn res1;\n\t}\n\n\tprotected StateValues checkExpressionFuncNary(Model<?> model, ExpressionFunc expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Check first operand recursively\n\t\tStateValues res1 = null, res2 = null;\n\t\tres1 = checkExpression(model, expr.getOperand(0), statesOfInterest);\n\t\t// Go through remaining operands\n\t\tint n = expr.getNumOperands();\n\t\tfor (int i = 1; i < n; i++) {\n\t\t\t// Check next operand recursively\n\t\t\ttry {\n\t\t\t\tres2 = checkExpression(model, expr.getOperand(i), statesOfInterest);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tif (res2 != null)\n\t\t\t\t\tres2.clear();\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t\t// Apply operation\n\t\t\ttry {\n\t\t\t\tres1.applyFunction(expr.getType(), (v1, v2) -> expr.applyBinary(v1, v2, EvalMode.FP), res2, statesOfInterest);\n\t\t\t\tres2.clear();\n\t\t\t} catch (PrismException e) {\n\t\t\t\tif (res1 != null)\n\t\t\t\t\tres1.clear();\n\t\t\t\tif (res2 != null)\n\t\t\t\t\tres2.clear();\n\t\t\t\tif (e instanceof PrismLangException)\n\t\t\t\t\t((PrismLangException) e).setASTElement(expr);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\treturn res1;\n\t}\n\n\t/**\n\t * Model check a literal.\n\t */\n\tprotected StateValues checkExpressionLiteral(Model<?> model, ExpressionLiteral expr) throws PrismException\n\t{\n\t\treturn StateValues.createFromSingleValue(expr.getType(), expr.evaluate(), model);\n\t}\n\n\t/**\n\t * Model check a constant.\n\t */\n\tprotected StateValues checkExpressionConstant(Model<?> model, ExpressionConstant expr) throws PrismException\n\t{\n\t\treturn StateValues.createFromSingleValue(expr.getType(), expr.evaluate(constantValues), model);\n\t}\n\n\t/**\n\t * Model check a variable reference.\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionVar(Model<?> model, ExpressionVar expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// TODO (JK): optimize evaluation using statesOfInterest\n\t\tList<State> statesList = model.getStatesList();\n\t\treturn StateValues.create(expr.getType(), i -> expr.evaluate(statesList.get(i)), model);\n\t}\n\n\t/**\n\t * Model check an observable reference.\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionObs(Model<?> model, ExpressionObs expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\tPartiallyObservableModel<?> poModel = (PartiallyObservableModel<?>) model;\n\t\tint iObservable = modelInfo.getObservableIndex(expr.getName());\n\t\treturn StateValues.create(expr.getType(), i -> poModel.getObservationAsState(i).varValues[iObservable], model);\n\t}\n\t\n\t/**\n\t * Model check a label.\n\t * @param statesOfInterest the states of interest, see checkExpression()\n\t */\n\tprotected StateValues checkExpressionLabel(Model<?> model, ExpressionLabel expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// TODO: optimize evaluation using statesOfInterest\n\n\t\tLabelList ll;\n\t\tint i;\n\n\t\t// treat special cases\n\t\tif (expr.isDeadlockLabel()) {\n\t\t\tint numStates = model.getNumStates();\n\t\t\tBitSet bs = new BitSet(numStates);\n\t\t\tfor (i = 0; i < numStates; i++) {\n\t\t\t\tbs.set(i, model.isDeadlockState(i));\n\t\t\t}\n\t\t\treturn StateValues.createFromBitSet(bs, model);\n\t\t} else if (expr.isInitLabel()) {\n\t\t\tint numStates = model.getNumStates();\n\t\t\tBitSet bs = new BitSet(numStates);\n\t\t\tfor (i = 0; i < numStates; i++) {\n\t\t\t\tbs.set(i, model.isInitialState(i));\n\t\t\t}\n\t\t\treturn StateValues.createFromBitSet(bs, model);\n\t\t} else {\n\t\t\t// First look at labels attached directly to model\n\t\t\tBitSet bs = model.getLabelStates(expr.getName());\n\t\t\tif (bs != null) {\n\t\t\t\treturn StateValues.createFromBitSet((BitSet) bs.clone(), model);\n\t\t\t}\n\t\t\t// Failing that, look in the label list (from properties file / modules file)\n\t\t\tll = getLabelList();\n\t\t\tif (ll != null) {\n\t\t\t\ti = ll.getLabelIndex(expr.getName());\n\t\t\t\tif (i != -1) {\n\t\t\t\t\t// check recursively\n\t\t\t\t\treturn checkExpression(model, ll.getLabel(i), statesOfInterest);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tthrow new PrismException(\"Unknown label \\\"\" + expr.getName() + \"\\\"\");\n}\n\n\t// Check property ref\n\n\tprotected StateValues checkExpressionProp(Model<?> model, ExpressionProp expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Look up property and check recursively\n\t\tProperty prop = propertiesFile.lookUpPropertyObjectByName(expr.getName());\n\t\tif (prop != null) {\n\t\t\tmainLog.println(\"\\nModel checking : \" + prop);\n\t\t\treturn checkExpression(model, prop.getExpression(), statesOfInterest);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Unknown property reference \" + expr);\n\t\t}\n\t}\n\n\t// Check filter\n\n\tprotected StateValues checkExpressionFilter(Model<?> model, ExpressionFilter expr, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Translate filter\n\t\tExpression filter = expr.getFilter();\n\t\t// Create default filter (true) if none given\n\t\tif (filter == null)\n\t\t\tfilter = Expression.True();\n\t\t// Remember whether filter is \"true\"\n\t\tboolean filterTrue = Expression.isTrue(filter);\n\t\t// Store some more info\n\t\tString filterStatesString = filterTrue ? \"all states\" : \"states satisfying filter\";\n\n\t\t// get the BitSet of states matching the filter, without taking statesOfInterest into account\n\t\tBitSet bsFilter = checkExpression(model, filter, null).getBitSet();\n\n\t\t// Check if filter state set is empty; we treat this as an error\n\t\tif (bsFilter.isEmpty()) {\n\t\t\tthrow new PrismException(\"Filter satisfies no states\");\n\t\t}\n\t\t// Remember whether filter is for the initial state and, if so, whether there's just one\n\t\tboolean filterInit = (filter instanceof ExpressionLabel && ((ExpressionLabel) filter).isInitLabel());\n\t\tboolean filterInitSingle = filterInit & model.getNumInitialStates() == 1;\n\t\t// Print out number of states satisfying filter\n\t\tif (!filterInit && !expr.isInvisible()) {\n\t\t\tmainLog.println(\"\\nStates satisfying filter \" + filter + \": \" + bsFilter.cardinality());\n\t\t}\n\t\t// Possibly optimise filter\n\t\tFilterOperator op = expr.getOperatorType();\n\t\tif (op == FilterOperator.FIRST) {\n\t\t\tbsFilter.clear(bsFilter.nextSetBit(0) + 1, bsFilter.length());\n\t\t}\n\n\t\t// For some types of filter, store info that may be used to optimise model checking\n\t\tif (op == FilterOperator.STATE) {\n\t\t\t// Check filter satisfied by exactly one state\n\t\t\tif (bsFilter.cardinality() != 1) {\n\t\t\t\tString s = \"Filter should be satisfied in exactly 1 state\";\n\t\t\t\ts += \" (but \\\"\" + filter + \"\\\" is true in \" + bsFilter.cardinality() + \" states)\";\n\t\t\t\tthrow new PrismException(s);\n\t\t\t}\n\t\t\tcurrentFilter = new Filter(Filter.FilterOperator.STATE, bsFilter.nextSetBit(0));\n\t\t} else if (op == FilterOperator.FORALL && filterInit && filterInitSingle) {\n\t\t\tcurrentFilter = new Filter(Filter.FilterOperator.STATE, bsFilter.nextSetBit(0));\n\t\t} else if (op == FilterOperator.FIRST && filterInit && filterInitSingle) {\n\t\t\tcurrentFilter = new Filter(Filter.FilterOperator.STATE, bsFilter.nextSetBit(0));\n\t\t} else {\n\t\t\tcurrentFilter = null;\n\t\t}\n\t\t// Check operand recursively, using bsFilter as statesOfInterest\n\t\tStateValues vals = checkExpression(model, expr.getOperand(), bsFilter);\n\n\t\t// Compute result according to filter type\n\t\tStateValues resVals = null;\n\t\tBitSet bsMatch = null, bs = null;\n\t\tboolean b = false;\n\t\tString resultExpl = null;\n\t\tObject resObj = null;\n\t\tAccuracy resAcc = null; \n\t\tswitch (op) {\n\t\tcase PRINT:\n\t\tcase PRINTALL:\n\t\t\t// Format of print-out depends on type\n\t\t\tif (expr.getType() instanceof TypeBool) {\n\t\t\t\t// NB: 'usual' case for filter(print,...) on Booleans is to use no filter\n\t\t\t\tmainLog.print(\"\\nSatisfying states\");\n\t\t\t\tmainLog.println(filterTrue ? \":\" : \" that are also in filter \" + filter + \":\");\n\t\t\t\tvals.printFiltered(mainLog, bsFilter);\n\t\t\t} else {\n\t\t\t\tif (op == FilterOperator.PRINT) {\n\t\t\t\t\tmainLog.println(\"\\nResults (non-zero only) for filter \" + filter + \":\");\n\t\t\t\t\tvals.printFiltered(mainLog, bsFilter);\n\t\t\t\t} else {\n\t\t\t\t\tmainLog.println(\"\\nResults (including zeros) for filter \" + filter + \":\");\n\t\t\t\t\tvals.printFiltered(mainLog, bsFilter, false, false, true, true);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Result vector is unchanged; for PRINT/PRINTALL, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = vals;\n\t\t\t// Set vals to null to stop it being cleared below\n\t\t\tvals = null;\n\t\t\tbreak;\n\t\tcase STORE:\n\t\t\t// Not much to do here - will be handled below when we store in the Result object\n\t\t\t// Result vector is unchanged; like PRINT/PRINTALL, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = vals;\n\t\t\t// Set vals to null to stop it being cleared below\n\t\t\tvals = null;\n\t\t\tbreak;\n\t\tcase MIN:\n\t\t\t// Compute min\n\t\t\t// Store as object/vector\n\t\t\tresObj = expr.apply(vals.filtered(bsFilter));\n\t\t\tresVals = StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Minimum value over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\t// Also find states that (are close to) selected value for display to log\n\t\t\tbsMatch = vals.getBitSetFromCloseValue(resObj);\n\t\t\tbsMatch.and(bsFilter);\n\t\t\tbreak;\n\t\tcase MAX:\n\t\t\t// Compute max\n\t\t\t// Store as object/vector\n\t\t\tresObj = expr.apply(vals.filtered(bsFilter));\n\t\t\tresVals = StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Maximum value over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\t// Also find states that (are close to) selected value for display to log\n\t\t\tbsMatch = vals.getBitSetFromCloseValue(resObj);\n\t\t\tbsMatch.and(bsFilter);\n\t\t\tbreak;\n\t\tcase ARGMIN:\n\t\t\t// Compute/display min\n\t\t\tresObj = ExpressionFilter.applyMin(vals.filtered(bsFilter), vals.getType());\n\t\t\tmainLog.print(\"\\nMinimum value over \" + filterStatesString + \": \" + resObj);\n\t\t\t// Find states that (are close to) selected value\n\t\t\tbsMatch = vals.getBitSetFromCloseValue(resObj);\n\t\t\tbsMatch.and(bsFilter);\n\t\t\t// Store states in vector; for ARGMIN, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = StateValues.createFromBitSet(bsMatch, model);\n\t\t\t// Print out number of matching states, but not the actual states\n\t\t\tmainLog.println(\"\\nNumber of states with minimum value: \" + bsMatch.cardinality());\n\t\t\tbsMatch = null;\n\t\t\tbreak;\n\t\tcase ARGMAX:\n\t\t\t// Compute/display max\n\t\t\tresObj = ExpressionFilter.applyMax(vals.filtered(bsFilter), vals.getType());\n\t\t\tmainLog.print(\"\\nMaximum value over \" + filterStatesString + \": \" + resObj);\n\t\t\t// Find states that (are close to) selected value\n\t\t\tbsMatch = vals.getBitSetFromCloseValue(resObj);\n\t\t\tbsMatch.and(bsFilter);\n\t\t\t// Store states in vector; for ARGMAX, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = StateValues.createFromBitSet(bsMatch, model);\n\t\t\t// Print out number of matching states, but not the actual states\n\t\t\tmainLog.println(\"\\nNumber of states with maximum value: \" + bsMatch.cardinality());\n\t\t\tbsMatch = null;\n\t\t\tbreak;\n\t\tcase COUNT:\n\t\t\t// Compute count\n\t\t\t// Store as object/vector\n\t\t\tresObj = expr.apply(vals.filtered(bsFilter));\n\t\t\tresVals =  StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = filterTrue ? \"Count of satisfying states\" : \"Count of satisfying states also in filter\";\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase SUM:\n\t\t\t// Compute sum\n\t\t\t// Store as object/vector\n\t\t\tresObj = expr.apply(vals.filtered(bsFilter));\n\t\t\tresVals = StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Sum over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase AVG:\n\t\t\t// Compute average\n\t\t\t// Store as object/vector\n\t\t\tresObj = expr.apply(vals.filtered(bsFilter));\n\t\t\tresVals = StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Average over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase FIRST:\n\t\t\t// Find first value\n\t\t\tresObj = vals.firstFromBitSet(bsFilter);\n\t\t\tresVals = StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Value in \";\n\t\t\tif (filterInit) {\n\t\t\t\tresultExpl += filterInitSingle ? \"the initial state\" : \"first initial state\";\n\t\t\t} else {\n\t\t\t\tresultExpl += filterTrue ? \"the first state\" : \"first state satisfying filter\";\n\t\t\t}\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase RANGE:\n\t\t\t// Find range of values\n\t\t\tresObj = expr.apply(vals.filtered(bsFilter));\n\t\t\t// Leave result vector unchanged: for a range, result is only available from Result object\n\t\t\tresVals = vals;\n\t\t\t// Set vals to null to stop it being cleared below\n\t\t\tvals = null;\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Range of values over \";\n\t\t\tresultExpl += filterInit ? \"initial states\" : filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase FORALL:\n\t\t\t// Get access to BitSet for this\n\t\t\tbs = vals.getBitSet();\n\t\t\t// Check \"for all\" over filter\n\t\t\tb = (boolean) expr.apply(vals.filtered(bsFilter));\n\t\t\t// Store as object/vector\n\t\t\tresObj = b;\n\t\t\tresVals = StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Property \" + (b ? \"\" : \"not \") + \"satisfied in \";\n\t\t\tmainLog.print(\"\\nProperty satisfied in \" + ExpressionFilter.applyCount(vals.filtered(bsFilter), vals.getType()));\n\t\t\tif (filterInit) {\n\t\t\t\tif (filterInitSingle) {\n\t\t\t\t\tresultExpl += \"the initial state\";\n\t\t\t\t} else {\n\t\t\t\t\tresultExpl += \"all initial states\";\n\t\t\t\t}\n\t\t\t\tmainLog.println(\" of \" + model.getNumInitialStates() + \" initial states.\");\n\t\t\t} else {\n\t\t\t\tif (filterTrue) {\n\t\t\t\t\tresultExpl += \"all states\";\n\t\t\t\t\tmainLog.println(\" of all \" + model.getNumStates() + \" states.\");\n\t\t\t\t} else {\n\t\t\t\t\tresultExpl += \"all filter states\";\n\t\t\t\t\tmainLog.println(\" of \" + bsFilter.cardinality() + \" filter states.\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\t\tcase EXISTS:\n\t\t\t// Get access to BitSet for this\n\t\t\tbs = vals.getBitSet();\n\t\t\t// Check \"there exists\" over filter\n\t\t\tb = (boolean) expr.apply(vals.filtered(bsFilter));\n\t\t\t// Store as object/vector\n\t\t\tresObj = b;\n\t\t\tresVals = StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Property satisfied in \";\n\t\t\tif (filterTrue) {\n\t\t\t\tresultExpl += b ? \"at least one state\" : \"no states\";\n\t\t\t} else {\n\t\t\t\tresultExpl += b ? \"at least one filter state\" : \"no filter states\";\n\t\t\t}\n\t\t\tmainLog.println(\"\\n\" + resultExpl);\n\t\t\tbreak;\n\t\tcase STATE:\n\t\t\t// Find first (only) value\n\t\t\t// Store as object/vector\n\t\t\tresObj = vals.firstFromBitSet(bsFilter);\n\t\t\tresAcc = vals.accuracy;\n\t\t\tresVals = StateValues.createFromSingleValue(expr.getType(), resObj, model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Value in \";\n\t\t\tif (filterInit) {\n\t\t\t\tresultExpl += \"the initial state\";\n\t\t\t} else {\n\t\t\t\tresultExpl += \"the filter state\";\n\t\t\t}\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unrecognised filter type \\\"\" + expr.getOperatorName() + \"\\\"\");\n\t\t}\n\n\t\t// For some operators, print out some matching states\n\t\tif (bsMatch != null) {\n\t\t\tStateValues states = StateValues.createFromBitSet(bsMatch, model);\n\t\t\tmainLog.print(\"\\nThere are \" + bsMatch.cardinality() + \" states with \");\n\t\t\tmainLog.print((expr.getType() instanceof TypeDouble ? \"(approximately) \" : \"\") + \"this value\");\n\t\t\tboolean verbose = verbosity > 0; // TODO\n\t\t\tif (!verbose && bsMatch.cardinality() > 10) {\n\t\t\t\tmainLog.print(\".\\nThe first 10 states are displayed below. To view them all, enable verbose mode or use a print filter.\\n\");\n\t\t\t\tstates.print(mainLog, 10);\n\t\t\t} else {\n\t\t\t\tmainLog.print(\":\\n\");\n\t\t\t\tstates.print(mainLog);\n\t\t\t}\n\t\t}\n\n\t\t// Store result\n\t\tresult.setResult(resObj);\n\t\tresult.setAccuracy(resAcc);\n\t\t// Set result explanation (if none or disabled, clear)\n\t\tif (expr.getExplanationEnabled() && resultExpl != null) {\n\t\t\tresult.setExplanation(resultExpl.toLowerCase());\n\t\t} else {\n\t\t\tresult.setExplanation(null);\n\t\t}\n\t\t// Store vector if requested\n\t\tif (op == FilterOperator.STORE) {\n\t\t\tresult.setVector(resVals);\n\t\t}\n\t\t// Clear old vector if present\n\t\t// (and if the vector was not stored previously)\n\t\tif (vals != null && !(Expression.isFilter(expr.getOperand(), FilterOperator.STORE))) {\n\t\t\tvals.clear();\n\t\t}\n\n\t\treturn resVals;\n\t}\n\n\t\n\t/**\n\t * Method for handling the recursive part of PCTL* checking, i.e.,\n\t * recursively checking maximal state subformulas and replacing them\n\t * with labels and the corresponding satisfaction sets.\n\t * <br>\n\t * Extracts maximal state formula from an LTL path formula,\n\t * model checks them (with the current model checker) and\n\t * replaces them with ExpressionLabel objects that correspond\n\t * to freshly generated labels attached to the model.\n\t * <br>\n\t * Returns the modified Expression.\n\t */\n\tpublic Expression handleMaximalStateFormulas(ModelExplicit<?> model, Expression expr) throws PrismException\n\t{\n\t\tVector<BitSet> labelBS = new Vector<BitSet>();\n\n\t\tLTLModelChecker ltlMC = new LTLModelChecker(this);\n\t\t// check the maximal state subformulas and gather\n\t\t// the satisfaction sets in labelBS, with index i\n\t\t// in the vector corresponding to label Li in the\n\t\t// returned formula\n\t\tExpression exprNew = ltlMC.checkMaximalStateFormulas(this, model, expr.deepCopy(), labelBS);\n\n\t\tHashMap<String, String> labelReplacements = new HashMap<String, String>();\n\t\tfor (int i=0; i < labelBS.size(); i++) {\n\t\t\tString currentLabel = \"L\"+i;\n\t\t\t// Attach satisfaction set for Li to the model, record necessary\n\t\t\t// label renaming\n\t\t\tString newLabel = model.addUniqueLabel(\"phi\", labelBS.get(i), getDefinedLabelNames());\n\t\t\tlabelReplacements.put(currentLabel, newLabel);\n\t\t}\n\t\t// rename the labels\n\t\treturn (Expression) exprNew.accept(new ReplaceLabels(labelReplacements));\n\t}\n\n\t/**\n\t * Extract maximal propositional subformulas of an expression, model check them and\n\t * replace them with ExpressionLabel objects (L0, L1, etc.) Expression passed in is modified directly, but the result\n\t * is also returned. As an optimisation, model checking that results in true/false for all states is converted to an\n\t * actual true/false, and duplicate results are given the same proposition. BitSets giving the states which satisfy each proposition\n\t * are put into the list {@code propBSs}, which should be empty when this function is called.\n\t * The names of the labels (L0, L1, etc. by default) are put into {@code propNames}, which should also be empty. \n\t */\n\tpublic Expression checkMaximalPropositionalFormulas(Model<?> model, Expression expr, List<String> propNames, List<BitSet> propBSs) throws PrismException\n\t{\n\t\tExpression exprNew = (Expression) expr.accept(new CheckMaximalPropositionalFormulas(this, model, propNames, propBSs));\n\t\treturn exprNew;\n\t}\n\n\t/**\n\t * Class to replace maximal propositional subformulas of an expression\n\t * with labels corresponding to BitSets for the states that satisfy them.\n\t */\n\tclass CheckMaximalPropositionalFormulas extends ASTTraverseModify\n\t{\n\t\tprivate StateModelChecker mc;\n\t\tprivate Model<?> model;\n\t\tprivate List<String> propNames;\n\t\tprivate List<BitSet> propBSs;\n\n\t\tpublic CheckMaximalPropositionalFormulas(StateModelChecker mc, Model<?> model, List<String> propNames, List<BitSet> propBSs)\n\t\t{\n\t\t\tthis.mc = mc;\n\t\t\tthis.model = model;\n\t\t\tthis.propNames = propNames;\n\t\t\tthis.propBSs = propBSs;\n\t\t}\n\n\t\tpublic Object visit(ExpressionITE e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionBinaryOp e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionUnaryOp e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionFunc e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionIdent e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionLiteral e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionConstant e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionFormula e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\tpublic Object visit(ExpressionProp e) throws PrismLangException\n\t\t{\n\t\t\t// Look up property and recurse\n\t\t\tProperty prop = propertiesFile.lookUpPropertyObjectByName(e.getName());\n\t\t\tif (prop != null) {\n\t\t\t\treturn e.accept(this);\n\t\t\t} else {\n\t\t\t\tthrow new PrismLangException(\"Unknown property reference \" + e, e);\n\t\t\t}\n\t\t}\n\n\t\tpublic Object visit(ExpressionFilter e) throws PrismLangException\n\t\t{\n\t\t\treturn (e.getType() instanceof TypeBool && e.isProposition()) ? replaceWithLabel(e) : super.visit(e);\n\t\t}\n\n\t\t/**\n\t\t * Evaluate this expression in all states (i.e. model check it),\n\t\t * store the resulting BitSet in the list {@code propBSs},\n\t\t * and return an ExpressionLabel with name Li to replace it\n\t\t * (where i denotes the 0-indexed index into the list propBSs).\n\t\t */\n\t\tprivate Object replaceWithLabel(Expression e) throws PrismLangException\n\t\t{\n\t\t\t// Model check\n\t\t\tStateValues sv;\n\t\t\ttry {\n\t\t\t\tsv = mc.checkExpression(model, e, null);\n\t\t\t} catch (PrismException ex) {\n\t\t\t\tthrow new PrismLangException(ex.getMessage());\n\t\t\t}\n\t\t\tBitSet bs = sv.getBitSet();\n\t\t\t// Detect special cases (true, false) for optimisation\n\t\t\tif (bs.isEmpty()) {\n\t\t\t\treturn Expression.False();\n\t\t\t}\n\t\t\tif (bs.cardinality() == model.getNumStates()) {\n\t\t\t\treturn Expression.True();\n\t\t\t}\n\t\t\t// See if we already have an identical result\n\t\t\t// (in which case, reuse it)\n\t\t\tint i = propBSs.indexOf(bs);\n\t\t\tif (i != -1) {\n\t\t\t\tsv.clear();\n\t\t\t\treturn new ExpressionLabel(\"L\" + i);\n\t\t\t}\n\t\t\t// Otherwise, add result to list, return new label\n\t\t\tString newLabelName = \"L\" + propBSs.size();\n\t\t\tpropNames.add(newLabelName);\n\t\t\tpropBSs.add(bs);\n\t\t\treturn new ExpressionLabel(newLabelName);\n\t\t}\n\t}\n\n\t/**\n\t * Construct rewards for the reward structure with index r of the reward generator and a model.\n\t * Ensures non-negative rewards.\n\t * <br>\n\t * Note: Relies on the stored RewardGenerator for constructing the reward structure.\n\t */\n\tprotected <Value> Rewards<Value> constructRewards(Model<Value> model, int r) throws PrismException\n\t{\n\t\treturn constructRewards(model, r, false);\n\t}\n\n\t/**\n\t * Construct rewards for the reward structure with index r of the reward generator and a model.\n\t * <br>\n\t * If {@code allowNegativeRewards} is true, the rewards may be positive and negative, i.e., weights.\n\t * <br>\n\t * Note: Relies on the stored RewardGenerator for constructing the reward structure.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected <Value> Rewards<Value> constructRewards(Model<Value> model, int r, boolean allowNegativeRewards) throws PrismException\n\t{\n\t\tConstructRewards constructRewards = new ConstructRewards(this);\n\t\tif (allowNegativeRewards)\n\t\t\tconstructRewards.allowNegativeRewards();\n\t\treturn constructRewards.buildRewardStructure(model, (RewardGenerator<Value>) rewardGen, r);\n\t}\n\n\t/**\n\t * Construct expected rewards for the reward structure with index r of the reward generator and a model,\n\t * i.e., using probability-weighted sum for any rewards attached to transitions,\n\t * assigning them to states/choices.\n\t * Ensures non-negative rewards.\n\t * <br>\n\t * Note: Relies on the stored RewardGenerator for constructing the reward structure.\n\t */\n\tprotected <Value> Rewards<Value> constructExpectedRewards(Model<Value> model, int r) throws PrismException\n\t{\n\t\tif (model.getModelType() == ModelType.IDTMC && rewardGen.rewardStructHasTransitionRewards(r)) {\n\t\t\tthrow new PrismNotSupportedException(\"Transition rewards not supported for \" + model.getModelType() + \"s\");\n\n\t\t}\n\t\tConstructRewards constructRewards = new ConstructRewards(this);\n\t\tconstructRewards.setExpectedRewards(true);\n\t\treturn constructRewards.buildRewardStructure(model, (RewardGenerator<Value>) rewardGen, r);\n\t}\n\n\t/**\n\t * Load all labels from a PRISM labels (.lab) file and store them in BitSet objects.\n\t * Return a map from label name Strings to BitSets.\n\t * This is for all labels in the file, including \"init\", \"deadlock\".\n\t * Note: the size of the BitSet may be smaller than the number of states.\n\t */\n\tpublic static Map<String, BitSet> loadLabelsFile(String filename) throws PrismException\n\t{\n\t\tPrismExplicitImporter modelImporter = new PrismExplicitImporter(null, null, new File(filename), null, null, null);\n\t\treturn modelImporter.extractAllLabels();\n\t}\n\n\t/**\n\t * Export a model.\n\t * @param model The model\n\t * @param exportTask Export task (destination, which parts of the model to export, options)\n\t */\n\tpublic <Value> void exportModel(Model<Value> model, ModelExportTask exportTask) throws PrismException\n\t{\n\t\tModelExportOptions exportOptions = exportTask.getExportOptions();\n\t\t// Build an exporter of the required type\n\t\tModelExporter<Value> exporter;\n\t\tswitch (exportOptions.getFormat()) {\n\t\t\tcase EXPLICIT:\n\t\t\t\tif (exportOptions.getExplicitRows()) {\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Export in rows format not yet supported by explicit engine\");\n\t\t\t\t}\n\t\t\t\texporter = new PrismExplicitExporter<>(exportOptions);\n\t\t\t\tbreak;\n\t\t\tcase DOT:\n\t\t\t\texporter = new DotExporter<>(exportOptions);\n\t\t\t\tbreak;\n\t\t\tcase DRN:\n\t\t\t\texporter = new DRNExporter<>(exportOptions);\n\t\t\t\tbreak;\n\t\t\tcase UMB:\n\t\t\t\texporter = new UMBExporter<>(exportOptions);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(\"Export \" + exportOptions.getFormat().description() + \" not supported by explicit engine\");\n\t\t}\n\t\texporter.setModelInfo(modelInfo);\n\t\tFile file = exportTask.getFile();\n\t\t// Disallow stdout export for binary formats\n\t\tif (exportOptions.getFormat().isBinary() && !exportOptions.getBinaryAsText() && file == null) {\n\t\t\tthrow new PrismNotSupportedException(\"Export \" + exportOptions.getFormat().description() + \" must be to a file\");\n\t\t}\n\t\t// If needed, add label/reward info\n\t\tif (exportOptions.getFormat() == ModelExportFormat.DRN || exportOptions.getFormat() == ModelExportFormat.UMB) {\n\t\t\t// Get rewards/labels\n\t\t\tList<Rewards<Value>> rewards = new ArrayList<>();\n\t\t\tfor (int r = 0; r < rewardGen.getNumRewardStructs(); r++) {\n\t\t\t\trewards.add(constructRewards(model, r, true));\n\t\t\t}\n\t\t\tList<String> labelNames = new ArrayList<>();\n\t\t\tif (exportTask.initLabelIncluded()) {\n\t\t\t\tlabelNames.add(\"init\");\n\t\t\t}\n\t\t\tif (exportTask.deadlockLabelIncluded() && model.getNumDeadlockStates() > 0) {\n\t\t\t\tlabelNames.add(\"deadlock\");\n\t\t\t}\n\t\t\tlabelNames.addAll(modelInfo.getLabelNames());\n\t\t\tList<BitSet> labelStates = checkLabels(model, labelNames);\n\t\t\t// Add to exporter\n\t\t\texporter.addRewards(rewards, rewardGen.getRewardStructNames());\n\t\t\texporter.setRewardEvaluator((Evaluator<Value>) rewardGen.getRewardEvaluator());\n\t\t\texporter.addLabels(labelStates, labelNames);\n\t\t}\n\t\t// Export to file/log\n\t\tif (exportOptions.getFormat().isBinary() && !exportOptions.getBinaryAsText()) {\n\t\t\texporter.exportModel(model, file);\n\t\t} else {\n\t\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\t\texporter.exportModel(model, out);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Export the transition function/matrix of a model.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic <Value> void exportTransitions(Model<Value> model, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\texportModel(model, ModelExportTask.fromOptions(file, exportOptions));\n\t}\n\n\t/**\n\t * Export the state rewards for one reward structure of a model.\n\t * @param model The model\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic <Value> void exportStateRewards(Model<Value> model, int r, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tif (exportOptions.getFormat() != ModelExportFormat.EXPLICIT) {\n\t\t\tthrow new PrismNotSupportedException(\"Exporting state rewards in the requested format is currently not supported by the explicit engine\");\n\t\t}\n\n\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\tRewards<Value> modelRewards = constructRewards(model, r, true);\n\t\t\tPrismExplicitExporter<Value> exporter = new PrismExplicitExporter<>(exportOptions);\n\t\t\texporter.exportStateRewards(model, modelRewards, rewardGen.getRewardStructName(r), out);\n\t\t}\n\t}\n\n\t/**\n\t * Export the transition rewards for one reward structure of a model.\n\t * @param model The model\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic <Value> void exportTransRewards(Model<Value> model, int r, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tif (exportOptions.getFormat() != ModelExportFormat.EXPLICIT) {\n\t\t\tthrow new PrismNotSupportedException(\"Exporting transition rewards in the requested format is currently not supported by the explicit engine\");\n\t\t}\n\n\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\tRewards<Value> modelRewards = constructRewards(model, r, true);\n\t\t\tPrismExplicitExporter<Value> exporter = new PrismExplicitExporter<>(exportOptions);\n\t\t\texporter.exportTransRewards(model, modelRewards, rewardGen.getRewardStructName(r), out);\n\t\t}\n\t}\n\n\t/**\n\t * Export the set of states for a model.\n\t * @param model The model\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic <Value> void exportStates(Model<Value> model, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\tswitch (exportOptions.getFormat()) {\n\t\t\t\tcase EXPLICIT:\n\t\t\t\t\tnew PrismExplicitExporter<Value>(exportOptions).exportStates(model, modelInfo.createVarList(), out);\n\t\t\t\t\tbreak;\n\t\t\t\tcase MATLAB:\n\t\t\t\t\tnew MatlabExporter<Value>(exportOptions).exportStates(model, modelInfo.createVarList(), out);\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Export the observations for a (partially observable) model.\n\t * @param model The model\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic <Value> void exportObservations(Model<Value> model, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\tswitch (exportOptions.getFormat()) {\n\t\t\t\tcase EXPLICIT:\n\t\t\t\t\tnew PrismExplicitExporter<Value>(exportOptions).exportObservations((PartiallyObservableModel<Value>) model, modelInfo, out);\n\t\t\t\t\tbreak;\n\t\t\t\tcase MATLAB:\n\t\t\t\t\tnew MatlabExporter<Value>(exportOptions).exportObservations((PartiallyObservableModel<Value>) model, modelInfo, out);\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Export a set of labels and the states that satisfy them.\n\t * @param model The model\n\t * @param labelNames The names of the labels to export\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic <Value> void exportLabels(Model<Value> model, List<String> labelNames, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tList<BitSet> labelStates = checkLabels(model, labelNames);\n\t\texportLabels(model, labelNames, labelStates, file, exportOptions);\n\t}\n\n\t/**\n\t * Determine the set of states that satisfy a specified list of labels,\n\t * and return the states sets as a corresponding list of BitSets.\n\t * @param model The model\n\t * @param labelNames The names of the labels to export\n\t */\n\tprivate List<BitSet> checkLabels(Model<?> model, List<String> labelNames) throws PrismException\n\t{\n\t\tList<BitSet> labelStates = new ArrayList<BitSet>();\n\t\tfor (String labelName : labelNames) {\n\t\t\tStateValues sv = checkExpression(model, new ExpressionLabel(labelName), null);\n\t\t\tlabelStates.add(sv.getBitSet());\n\t\t}\n\t\treturn labelStates;\n\t}\n\n\t/**\n\t * Export a set of labels and the states that satisfy them.\n\t * @param model The model\n\t * @param labelNames The names of the labels to export\n\t * @param labelStates The states that satisfy each label, specified as a BitSet\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param format The format in which to export\n\t */\n\tpublic <Value> void exportLabels(Model<Value> model, List<String> labelNames, List<BitSet> labelStates, File file, ModelExportFormat format) throws PrismException\n\t{\n\t\texportLabels(model, labelNames, labelStates, file, new ModelExportOptions(format));\n\t}\n\n\t/**\n\t * Export a set of labels and the states that satisfy them.\n\t * @param model The model\n\t * @param labelNames The names of the labels to export\n\t * @param labelStates The states that satisfy each label, specified as a BitSet\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic <Value> void exportLabels(Model<Value> model, List<String> labelNames, List<BitSet> labelStates, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\tswitch (exportOptions.getFormat()) {\n\t\t\t\tcase EXPLICIT:\n\t\t\t\t\tnew PrismExplicitExporter<Value>(exportOptions).exportLabels(model, labelNames, labelStates, out);\n\t\t\t\t\tbreak;\n\t\t\t\tcase MATLAB:\n\t\t\t\t\tnew MatlabExporter<Value>(exportOptions).exportLabels(model, labelNames, labelStates, out);\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Do any exports after a model-automaton product construction, if requested\n\t */\n\tpublic void doProductExports(Product<?> product) throws PrismException\n\t{\n\t\tif (getExportProductTrans()) {\n\t\t\tmainLog.println(\"\\nExporting product transition matrix to file \\\"\" + getExportProductTransFilename() + \"\\\"...\");\n\t\t\tint precision = settings.getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION);\n\t\t\tproduct.getProductModel().exportToPrismExplicitTra(getExportProductTransFilename(), precision);\n\t\t}\n\t\tif (getExportProductStates()) {\n\t\t\tmainLog.println(\"\\nExporting product state space to file \\\"\" + getExportProductStatesFilename() + \"\\\"...\");\n\t\t\tPrismFileLog out = new PrismFileLog(getExportProductStatesFilename());\n\t\t\tVarList newVarList = (VarList) modelInfo.createVarList().clone();\n\t\t\tString daVar = \"_da\";\n\t\t\twhile (newVarList.exists(daVar)) {\n\t\t\t\tdaVar = \"_\" + daVar;\n\t\t\t}\n\t\t\tnewVarList.addVarAtStart(new Declaration(daVar, new DeclarationIntUnbounded()), 1);\n\t\t\tproduct.getProductModel().exportStates(newVarList, out, new ModelExportOptions());\n\t\t\tout.close();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/StateOwnersSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\n/**\n * Explicit-state storage of which player owns each state in a turn-based game.\n * \n * Uses simple, mutable data structures, matching the \"Simple\" range of models.\n */\npublic class StateOwnersSimple\n{\n\t/**\n\t * Mapping from states to the player that owns them\n\t * NB: states are 0-indexed; players are 0-indexed\n\t */\n\tprotected List<Integer> stateOwners;\n\t\n\t// Constructors\n\t\n\t/**\n\t * Constructor: empty list (no states).\n\t */\n\tpublic StateOwnersSimple()\n\t{\n\t\tstateOwners = new ArrayList<Integer>();\n\t}\n\n\t/**\n\t * Constructor: new list with fixed number of states.\n\t */\n\tpublic StateOwnersSimple(int numStates)\n\t{\n\t\tstateOwners = new ArrayList<Integer>(numStates);\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tstateOwners.add(-1);\n\t\t}\n\t}\n\n\t/**\n\t * Copy constructor\n\t */\n\tpublic StateOwnersSimple(StateOwnersSimple stateOwnersSimple)\n\t{\n\t\tstateOwners = new ArrayList<Integer>(stateOwnersSimple.stateOwners);\n\t}\n\t\n\t/**\n\t * Copy constructor, but with a state index permutation,\n\t * i.e. in which state index i becomes index permut[i].\n\t */\n\tpublic StateOwnersSimple(StateOwnersSimple stateOwnersSimple, int permut[])\n\t{\n\t\t// Create blank list of correct size\n\t\tint numStates = stateOwnersSimple.stateOwners.size();\n\t\tstateOwners = new ArrayList<Integer>(numStates);\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tstateOwners.add(-1);\n\t\t}\n\t\t// Copy permuted player info\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tstateOwners.set(permut[i], stateOwnersSimple.stateOwners.get(i));\n\t\t}\n\t}\n\t\n\t// Mutators\n\t\n\t/**\n\t * Clear all information for a state (i.e., assign no player).\n\t */\n\tpublic void clearState(int s)\n\t{\n\t\tstateOwners.set(s, -1);\n\t}\n\t\n\n\t/**\n\t * Add a new state owned by player {@code p}.\n\t * @param p Player who owns the new state (0-indexed)\n\t */\n\tpublic void addState(int p)\n\t{\n\t\tstateOwners.add(p);\n\t}\n\t\n\t/**\n\t * Set the player that owns state {@code s} to {@code p}.\n\t * @param s State to be modified (0-indexed)\n\t * @param p Player who owns the state (0-indexed)\n\t */\n\tpublic void setPlayer(int s, int p)\n\t{\n\t\tstateOwners.set(s, p);\n\t}\n\t\n\t// Accessors\n\t\n\t/**\n\t * Get the player that owns state {@code s}.\n\t * Returns the index of the player (0-indexed).\n\t * @param s Index of state (0-indexed)\n\t */\n\tpublic int getPlayer(int s)\n\t{\n\t\treturn stateOwners.get(s);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/StateStorage.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mateusz Ujma <mateusz.ujma@cs.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.*;\n\n/**\n * Interface for storing a set of objects of type T.\n * Typically used for storing states during reachability.\n */\npublic interface StateStorage<T>\n{\n\tpublic int get(T t);\n\t\n\tpublic boolean add(T state);\n\t\n\tpublic void clear();\n\n\tpublic boolean contains(T state);\n\n\tpublic int getIndexOfLastAdd();\n\n\tpublic boolean isEmpty();\n\n\t/**\n\t * Get the number of objects stored in the set.\n\t */\n\tpublic int size();\n\n\t/**\n\t * Get access to the underlying set of map entries. \n\t */\n\tpublic Set<Map.Entry<T, Integer>> getEntrySet();\n\t\n\t/**\n\t * Create an ArrayList of the states, ordered by index.\n\t */\n\tpublic ArrayList<T> toArrayList();\n\n\t/**\n\t * Create an ArrayList of the states, ordered by index, storing in the passed in list.\n\t * @param list An empty ArrayList in which to store the result.\n\t */\n\tpublic void toArrayList(ArrayList<T> list);\n\t\n\t/**\n\t * Create an ArrayList of the states, ordered by permuted index.\n\t * Index in new list is permut[old_index].\n\t * @param permut Permutation to apply\n\t */\n\tpublic ArrayList<T> toPermutedArrayList(int permut[]);\n\n\t/**\n\t * Create an ArrayList of the states, ordered by permuted index, storing in the passed in list.\n\t * Index in new list is permut[old_index].\n\t * @param permut Permutation to apply\n\t * @param list An empty ArrayList in which to store the result.\n\t */\n\tpublic void toPermutedArrayList(int permut[], ArrayList<T> list);\n\t\n\t/**\n\t * Build sort permutation. Assuming this was built as a sorted set,\n\t * this returns a permutation (integer array) mapping current indices\n\t * to new indices under the sorting order.\n\t */\n\tpublic int[] buildSortingPermutation();\n}\n"
  },
  {
    "path": "prism/src/explicit/StateValues.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.io.BufferedReader;\nimport java.io.File;\nimport java.io.FileReader;\nimport java.io.IOException;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.function.IntFunction;\n\nimport common.IterableStateSet;\nimport common.iterable.FunctionalPrimitiveIterator;\nimport parser.State;\nimport parser.ast.ExpressionFilter;\nimport parser.type.Type;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport prism.Accuracy;\nimport prism.AccuracyFactory;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismLog;\nimport prism.ResultTesting;\nimport prism.StateVector;\n\n/**\n * Class for explicit-state storage of a state-indexed vector of values.\n * <br><br>\n * The values can be of any supported {@link Type}.\n * They are stored as the corresponding {@link Object}\n * as specified by the return type of {@link Type#castValueTo(Object)}.\n */\npublic class StateValues implements StateVector, Iterable<Object>\n{\n\t// Vector info\n\t\n\t/** Type of value stored */\n\tprotected Type type;\n\t/** Size of vector */\n\tprotected int size;\n\t/** Computed accuracy of stored values (optional) */\n\tpublic Accuracy accuracy = null;\n\t\n\t// Model info\n\t\n\t/** Corresponding list of State objects */\n\tprotected List<State> statesList;\n\n\t// Vector storage (only one used, depending on type)\n\t\n\t/** Specialised storage for boolean values */\n\tprotected BitSet valuesB;\n\t/** General purpose storage for other value types */\n\tprotected Object[] valuesO;\n\t\n\t// Functional interfaces\n\t\n\t@FunctionalInterface\n\tpublic interface Predicate\n\t{\n\t\tpublic boolean test(Object v) throws PrismException;\n\t}\n\t\n\t@FunctionalInterface\n\tpublic interface UnaryFunction\n\t{\n\t\tpublic Object apply(Object v) throws PrismException;\n\t}\n\t\n\t@FunctionalInterface\n\tpublic interface BinaryFunction\n\t{\n\t\tpublic Object apply(Object v1, Object v2) throws PrismException;\n\t}\n\t\n\t@FunctionalInterface\n\tpublic interface TernaryFunction\n\t{\n\t\tpublic Object apply(Object v1, Object v2, Object v3) throws PrismException;\n\t}\n\t\n\t@FunctionalInterface\n\tpublic interface ValueDefinition\n\t{\n\t\tpublic Object apply(int i) throws PrismException;\n\t}\n\t\n\t// Constructors\n\n\t/**\n\t * Construct a new empty state values vector of unspecified type.\n\t * (Mostly for internal use.)\n\t */\n\tpublic StateValues()\n\t{\n\t\ttype = null;\n\t\tsize = 0;\n\t\tvaluesB = null;\n\t\tvaluesO = null;\n\t}\n\n\t/**\n\t * Construct a new state values vector for values of a specified type.\n\t * The values for states are provided as a mapping from integer index to Object.\n\t * The passed in model determines the vector size (and states list).\n\t */\n\tpublic StateValues(Type type, ValueDefinition values, Model<?> model) throws PrismException\n\t{\n\t\tinitialise(type, model);\n\t\tsetFromValueDefinition(values);\n\t}\n\t\n\t/**\n\t * Construct a new state values vector with the same value in every state.\n\t * The passed in model determines the vector size (and states list).\n\t */\n\tpublic StateValues(Type type, Object value, Model<?> model) throws PrismException\n\t{\n\t\tinitialise(type, model);\n\t\tsetToSingleValue(value);\n\t}\n\n\t/**\n\t * Construct a new state values vector for values of a specified type.\n\t * The value for all states is set to the default value for the type.\n\t * The passed in model determines the vector size (and states list).\n\t */\n\tpublic StateValues(Type type, Model<?> model) throws PrismException\n\t{\n\t\tthis(type, type.defaultValue(), model);\n\t}\n\n\t// Utility methods for initialisation/construction\n\t\n\t/**\n\t * Initialise the vector/model info (but not the value storage)\n\t */\n\tprivate void initialise(Type type, Model<?> model)\n\t{\n\t\tthis.type = type;\n\t\tthis.size = model.getNumStates();\n\t\tthis.statesList = model.getStatesList();\n\t\tthis.valuesB = null;\n\t\tthis.valuesO = null;\n\t}\n\n\t/**\n\t * Initialise the vector/model info (but not the value storage)\n\t */\n\tprivate void initialise(Type type, List<State> statesList)\n\t{\n\t\tthis.type = type;\n\t\tthis.size = statesList.size();\n\t\tthis.statesList = statesList;\n\t\tthis.valuesB = null;\n\t\tthis.valuesO = null;\n\t}\n\n\t/**\n\t * Initialise value storage based on a ValueDefinition\n\t */\n\tprivate void setFromValueDefinition(ValueDefinition values) throws PrismException\n\t{\n\t\t// Assumed to be called straight after initialise\n\t\t// (so size/type is known, but all storage is null)\n\t\tinitStorage(type);\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tsetValue(i, values.apply(i));\n\t\t}\n\t}\n\n\t/**\n\t * Initialise value storage based on a single value\n\t */\n\tprivate void setToSingleValue(Object value) throws PrismException\n\t{\n\t\t// Assumed to be called straight after initialise\n\t\t// (so size is known, but all storage is null)\n\t\tinitStorage(type);\n\t\tif (type instanceof TypeBool) {\n\t\t\tif ((boolean) value) {\n\t\t\t\tvaluesB = new BitSet(size);\n\t\t\t\tvaluesB.set(0, size);\n\t\t\t} else {\n\t\t\t\tvaluesB = new BitSet();\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int i = 0; i < size; i++) {\n\t\t\t\tvaluesO[i] = value;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Create (or recreate) the storage for values of the specified type\n\t * Uses existing storage if possible (assumes no change in size)\n\t */\n\tprivate void initStorage(Type typeNew)\n\t{\n\t\tif (typeNew instanceof TypeBool) {\n\t\t\tif (valuesB == null) {\n\t\t\t\tvaluesB = new BitSet();\n\t\t\t}\n\t\t} else {\n\t\t\tif (valuesO == null) {\n\t\t\t\tvaluesO = new Object[size];\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Cleared un-needed value storage (if the type has changed)\n\t */\n\tprivate void clearOldStorage()\n\t{\n\t\tif (type != null) {\n\t\t\tif (type instanceof TypeBool) {\n\t\t\t\tvaluesO = null;\n\t\t\t} else {\n\t\t\t\tvaluesB = null;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// Static creation methods\n\t\n\t/**\n\t * Create a new state values vector for values of a specified type.\n\t * The values for states are provided as a mapping from integer index to Object.\n\t * The passed in model determines the vector size (and states list).\n\t */\n\tpublic static StateValues create(Type type, ValueDefinition values, Model<?> model) throws PrismException\n\t{\n\t\tStateValues sv = new StateValues();\n\t\tsv.initialise(type, model);\n\t\tsv.setFromValueDefinition(values);\n\t\treturn sv;\n\t}\n\t\n\t/**\n\t * Create a new state values vector for values of a specified type,\n\t * where the value is the same for every state.\n\t * The passed in model determines the vector size (and states list).\n\t */\n\tpublic static StateValues createFromSingleValue(Type type, Object value, Model<?> model) throws PrismException\n\t{\n\t\tStateValues sv = new StateValues();\n\t\tsv.initialise(type, model);\n\t\tsv.setToSingleValue(value);\n\t\treturn sv;\n\t}\n\n\t/**\n\t * Create a new state values vector from an existing array of values.\n\t * The array is stored directly, not copied.\n\t * Also set associated model (whose state space size should match vector size).\n\t */\n\tpublic static StateValues createFromObjectArray(Type type, Object[] array, Model<?> model)\n\t{\n\t\tStateValues sv = new StateValues();\n\t\tsv.initialise(type, model);\n\t\tsv.valuesO = array;\n\t\treturn sv;\n\t}\n\n\t/**\n\t * Create a new (double-valued) state values vector from an existing array of doubles.\n\t * Also set associated model (whose state space size should match vector size).\n\t */\n\tpublic static StateValues createFromDoubleArray(double[] array, Model<?> model) throws PrismException\n\t{\n\t\treturn create(TypeDouble.getInstance(), i -> array[i], model);\n\t}\n\n\t/**\n\t * Create a new (double-valued) state values vector from an existing array of doubles.\n\t */\n\tpublic static StateValues createFromDoubleArray(double[] array, List<State> statesList) throws PrismException\n\t{\n\t\tStateValues sv = new StateValues();\n\t\tsv.initialise(TypeDouble.getInstance(), statesList);\n\t\tsv.setFromValueDefinition(i -> array[i]);\n\t\treturn sv;\n\t}\n\n\t/**\n\t * Create a new (double-valued) state values vector from an existing array of doubles,\n\t * stored in a ModelCheckerResult object. Accuracy information is also extracted.\n\t * Also set associated model (whose state space size should match vector size).\n\t */\n\tpublic static StateValues createFromDoubleArrayResult(ModelCheckerResult res, Model<?> model) throws PrismException\n\t{\n\t\tStateValues sv = createFromDoubleArray(res.soln, model);\n\t\tsv.setAccuracy(res.accuracy);\n\t\treturn sv;\n\t}\n\t\n\t/**\n\t * Create a new (Boolean-valued) state values vector from an existing BitSet.\n\t * The BitSet is stored directly, not copied.\n\t * Also set associated model (and this determines the vector size).\n\t */\n\tpublic static StateValues createFromBitSet(BitSet bs, Model<?> model)\n\t{\n\t\tStateValues sv = new StateValues();\n\t\tsv.initialise(TypeBool.getInstance(), model);\n\t\tsv.valuesB = bs;\n\t\treturn sv;\n\t}\n\n\t/**\n\t * Create a new (double-valued) state values vector from a BitSet,\n\t * where each entry is 1.0 if in the bitset, 0.0 otherwise.\n\t * Also set associated model (and this determines the vector size).\n\t * The bitset is not modified or stored.\n\t * The accuracy for the result is also set automatically.\n\t */\n\tpublic static StateValues createFromBitSetAsDoubles(BitSet bitset, Model<?> model) throws PrismException\n\t{\n\t\tStateValues sv = create(TypeDouble.getInstance(), i -> bitset.get(i) ? 1.0 : 0.0, model);\n\t\tsv.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\treturn sv;\n\t}\n\n\t/**\n\t * Create a new state values vector from an existing array of values,\n\t * stored in a ModelCheckerResult object. Accuracy information is also extracted.\n\t * Also set associated model (whose state space size should match vector size).\n\t */\n\tpublic static StateValues createFromArrayResult(ModelCheckerResult res, Model<?> model) throws PrismException\n\t{\n\t\tStateValues sv = null;\n\t\tif (res.solnObj != null) {\n\t\t\tsv = createFromObjectArray(TypeDouble.getInstance(), res.solnObj, model);\n\t\t} else {\n\t\t\tsv = createFromDoubleArray(res.soln, model);\n\t\t}\n\t\tsv.setAccuracy(res.accuracy);\n\t\treturn sv;\n\t}\n\n\t/**\n\t * Create a new state values vector, reading in the values from a file.\n\t */\n\tpublic static StateValues createFromFile(Type type, File file, Model<?> model) throws PrismException\n\t{\n\t\tStateValues sv = new StateValues();\n\t\tsv.initialise(type, model);\n\t\tsv.readFromFile(file);\n\t\treturn sv;\n\t}\n\t\n\t// Other methods to create new vectors\n\t\n\t/**\n\t * Create a new StateValues, copied from this one, but mapped to a new model.\n\t * @param newModel The new model\n\t * @param reverseStateMapping Mapping from indices of the new model to the old one\n\t */\n\tpublic StateValues mapToNewModel(Model<?> newModel, IntFunction<Integer> reverseStateMapping) throws PrismException\n\t{\n\t\tint numStates = newModel.getNumStates();\n\t\tStateValues sv = create(type, i -> {\n\t\t\tfinal Integer j = reverseStateMapping.apply(i);\n\t\t\tif (j != null) {\n\t\t\t\tif (j >= numStates) {\n\t\t\t\t\tthrow new IndexOutOfBoundsException(\"State index error when mapping between models\");\n\t\t\t\t}\n\t\t\t\treturn getValue(j);\n\t\t\t} else {\n\t\t\t\treturn type.defaultValue();\n\t\t\t}\n\t\t}, newModel);\n\t\tsv.setAccuracy(getAccuracy());\n\t\treturn sv;\n\t}\n\n\t/**\n\t * Create a new StateValues, copied from this one, but mapped to the original model\n\t * that was used to construct a product. This function assumes that the product model\n\t * has at most one initial state per state in the original model. The value of this\n\t * state is then projected to the corresponding state of the original model.\n\t * @param product The product object\n\t */\n\tpublic StateValues projectToOriginalModel(final Product<?> product) throws PrismException\n\t{\n\t\tModel<?> productModel = product.getProductModel();\n\t\tModel<?> originalModel = product.getOriginalModel();\n\t\tStateValues sv = new StateValues(type, originalModel);\n\t\tfor (int productState : productModel.getInitialStates()) {\n\t\t\tint modelState = product.getModelState(productState);\n\t\t\tsv.setValue(modelState, getValue(productState));\n\t\t}\n\t\tsv.setAccuracy(getAccuracy());\n\t\treturn sv;\n\t}\n\t\n\t// Other set methods\n\t\n\t/**\n\t * Set the accuracy.\n\t */\n\tpublic void setAccuracy(Accuracy accuracy)\n\t{\n\t\tthis.accuracy = accuracy;\n\t}\n\t\n\t// Methods to modify vector values\n\t\n\t@Override\n\tpublic void clear()\n\t{\n\t\t// Actually, just set pointers to null and wait for later garbage collection.\n\t\tvaluesB = null;\n\t\tvaluesO = null;\n\t}\n\t\n\t/**\n\t * Set the value for state index {@code i} to {@code value}.\n\t * The type of Object passed in for {@code value} should be the\n\t * appropriate one for the type of this StateValues.\n\t */\n\tpublic void setValue(int i, Object value) throws PrismLangException\n\t{\n\t\tif (type instanceof TypeBool) {\n\t\t\tvaluesB.set(i, (boolean) value);\n\t\t} else {\n\t\t\tvaluesO[i] = value;\n\t\t}\n\t}\n\n\t/**\n\t * Set the value for state index {@code i} to {@code value},\n\t * assuming that the type of the StateValues is going to become\n\t * {@code typeOverride}, even if it is not right now.\n\t * The type of Object passed in for {@code value} should be the\n\t * appropriate one for {@code typeOverride}.\n\t * For internal use.\n\t */\n\tprivate void setValue(int i, Object value, Type typeOverride) throws PrismLangException\n\t{\n\t\tif (typeOverride instanceof TypeBool) {\n\t\t\tvaluesB.set(i, (boolean) value);\n\t\t} else {\n\t\t\tvaluesO[i] = value;\n\t\t}\n\t}\n\n\t/**\n\t * Modify the vector by applying (pointwise) a predicate, i.e., each element\n\t * of the vector will become the result of applying the predicate to itself.\n\t * @param predicate Predicate definition\n\t */\n\tpublic void applyPredicate(Predicate predicate) throws PrismException\n\t{\n\t\tinitStorage(TypeBool.getInstance());\n\t\tvaluesB = getBitSetFromPredicate(predicate);\n\t\ttype = TypeBool.getInstance();\n\t\tclearOldStorage();\n\t}\n\t\n\t/**\n\t * Modify the vector by applying (pointwise) a unary function.\n\t * @param retType Function return type\n\t * @param func Function definition\n\t */\n\tpublic void applyFunction(Type retType, UnaryFunction func) throws PrismException\n\t{\n\t\tinitStorage(retType);\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tsetValue(i, func.apply(getValue(i)), retType);\n\t\t}\n\t\ttype = retType;\n\t\tclearOldStorage();\n\t}\n\n\t/**\n\t * Modify the vector by applying (pointwise) a unary function, only over the states in {@code subset}.\n\t * @param retType Function return type\n\t * @param func Function definition\n\t * @param subset Subset of states for application (all if null)\n\t */\n\tpublic void applyFunction(Type retType, UnaryFunction func, BitSet subset) throws PrismException\n\t{\n\t\tinitStorage(retType);\n\t\tfor (FunctionalPrimitiveIterator.OfInt iter = new IterableStateSet(subset, size).iterator(); iter.hasNext();) {\n\t\t\tint i = iter.nextInt();\n\t\t\tsetValue(i, func.apply(getValue(i)), retType);\n\t\t}\n\t\ttype = retType;\n\t\tclearOldStorage();\n\t}\n\n\t/**\n\t * Modify the vector by applying (pointwise) a binary function\n\t * to this and another vector.\n\t * @param retType Function return type\n\t * @param func Function definition\n\t * @param sv2 Vector 2\n\t */\n\tpublic void applyFunction(Type retType, BinaryFunction func, StateValues sv2) throws PrismException\n\t{\n\t\tinitStorage(retType);\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tsetValue(i, func.apply(getValue(i), sv2.getValue(i)), retType);\n\t\t}\n\t\ttype = retType;\n\t\tclearOldStorage();\n\t}\n\t\n\t/**\n\t * Modify the vector by applying (pointwise) a binary function\n\t * to this and another vector, only over the states in {@code subset}.\n\t * @param retType Function return type\n\t * @param func Function definition\n\t * @param sv2 Vector 2\n\t * @param subset Subset of states for application (all if null)\n\t */\n\tpublic void applyFunction(Type retType, BinaryFunction func, StateValues sv2, BitSet subset) throws PrismException\n\t{\n\t\tinitStorage(retType);\n\t\tfor (FunctionalPrimitiveIterator.OfInt iter = new IterableStateSet(subset, size).iterator(); iter.hasNext();) {\n\t\t\tint i = iter.nextInt();\n\t\t\tsetValue(i, func.apply(getValue(i), sv2.getValue(i)), retType);\n\t\t}\n\t\ttype = retType;\n\t\tclearOldStorage();\n\t}\n\t\n\t/**\n\t * Modify the vector by applying (pointwise) a ternary function\n\t * to this and two other vectors.\n\t * @param retType Function return type\n\t * @param func Function definition\n\t * @param sv2 Vector 2\n\t * @param sv3 Vector 3\n\t */\n\tpublic void applyFunction(Type retType, TernaryFunction func, StateValues sv2, StateValues sv3) throws PrismException\n\t{\n\t\tinitStorage(retType);\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tsetValue(i, func.apply(getValue(i), sv2.getValue(i), sv3.getValue(i)), retType);\n\t\t}\n\t\ttype = retType;\n\t\tclearOldStorage();\n\t}\n\t\n\t/**\n\t * Modify the vector by applying (pointwise) a ternary function\n\t * to this and two other vectors, only over the states in {@code subset}.\n\t * @param retType Function return type\n\t * @param func Function definition\n\t * @param sv2 Vector 2\n\t * @param sv3 Vector 3\n\t * @param subset Subset of states for application (all if null)\n\t */\n\tpublic void applyFunction(Type retType, TernaryFunction func, StateValues sv2, StateValues sv3, BitSet subset) throws PrismException\n\t{\n\t\tinitStorage(retType);\n\t\tfor (FunctionalPrimitiveIterator.OfInt iter = new IterableStateSet(subset, size).iterator(); iter.hasNext();) {\n\t\t\tint i = iter.nextInt();\n\t\t\tsetValue(i, func.apply(getValue(i), sv2.getValue(i), sv3.getValue(i)), retType);\n\t\t}\n\t\ttype = retType;\n\t\tclearOldStorage();\n\t}\n\t\n\t/**\n\t * Set the elements of this vector by reading them in from a file.\n\t * The values in the file should match the existing type of this StateValues.\n\t */\n\tpublic void readFromFile(File file) throws PrismException\n\t{\n\t\tinitStorage(type);\n\t\tint lineNum = 0, count = 0;\n\t\tboolean hasIndices = false;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(file))) {\n\t\t\tString s = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\ts = s.trim();\n\t\t\t\tif (!(\"\".equals(s))) {\n\t\t\t\t\t// If entry is of form \"i=x\", use i as index not count\n\t\t\t\t\t// (otherwise, assume line i contains value for state index i)\n\t\t\t\t\tif (s.contains(\"=\")) {\n\t\t\t\t\t\thasIndices = true;\n\t\t\t\t\t\tString ss[] = s.split(\"=\");\n\t\t\t\t\t\tcount = Integer.parseInt(ss[0]);\n\t\t\t\t\t\ts = ss[1];\n\t\t\t\t\t}\n\t\t\t\t\tif (count + 1 > size) {\n\t\t\t\t\t\tin.close();\n\t\t\t\t\t\tthrow new PrismException(\"Too many values in file \\\"\" + file + \"\\\" (more than \" + size + \")\");\n\t\t\t\t\t}\n\t\t\t\t\tif (type instanceof TypeInt) {\n\t\t\t\t\t\tsetValue(count, Integer.parseInt(s));\n\t\t\t\t\t} else if (type instanceof TypeDouble) {\n\t\t\t\t\t\tsetValue(count, Double.parseDouble(s));\n\t\t\t\t\t} else if (type instanceof TypeBool) {\n\t\t\t\t\t\tsetValue(count, Boolean.parseBoolean(s));\n\t\t\t\t\t}\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t\t// Check size\n\t\t\tif (!hasIndices && count < size) {\n\t\t\t\tthrow new PrismException(\"Too few values in file \\\"\" + file + \"\\\" (\" + count + \", not \" + size + \")\");\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error detected at line \" + lineNum + \" of file \\\"\" + file + \"\\\"\");\n\t\t}\n\t}\n\n\t// Methods to modify vector values storing Boolean values\n\t\n\t/**\n\t * Modify the vector by applying 'implies' with operand {@code sv}.\n\t */\n\tpublic void implies(StateValues sv) throws PrismException\n\t{\n\t\tif (!(type instanceof TypeBool) || !(sv.getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismException(\"Operator => can only be applied to Boolean vectors\");\n\t\t}\n\t\tvaluesB.flip(0, size);\n\t\tvaluesB.or(sv.valuesB);\n\t}\n\n\t/**\n\t * Modify the vector by applying 'iff' with operand {@code sv}.\n\t */\n\tpublic void iff(StateValues sv) throws PrismException\n\t{\n\t\tif (!(type instanceof TypeBool) || !(sv.getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismException(\"Operator <=> can only be applied to Boolean vectors\");\n\t\t}\n\t\tvaluesB.xor(sv.valuesB);\n\t\tvaluesB.flip(0, size);\n\t}\n\n\t/**\n\t * Modify the vector by applying 'or' with operand {@code sv}.\n\t */\n\tpublic void or(StateValues sv) throws PrismException\n\t{\n\t\tif (!(type instanceof TypeBool) || !(sv.getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismException(\"Operator | can only be applied to Boolean vectors\");\n\t\t}\n\t\tvaluesB.or(sv.valuesB);\n\t}\n\n\t/**\n\t * Modify the vector by applying 'and' with operand {@code sv}.\n\t */\n\tpublic void and(StateValues sv) throws PrismException\n\t{\n\t\tif (!(type instanceof TypeBool) || !(sv.getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismException(\"Operator & can only be applied to Boolean vectors\");\n\t\t}\n\t\tvaluesB.and(sv.valuesB);\n\t}\n\n\t/**\n\t * Complement the (boolean) vector.\n\t */\n\tpublic void complement() throws PrismException\n\t{\n\t\tif (!(type instanceof TypeBool)) {\n\t\t\tthrow new PrismException(\"Can only complement Boolean vectors\");\n\t\t}\n\n\t\tvaluesB.flip(0, size);\n\t}\n\t\n\t/**\n\t * Modify the vector by applying 'not'\n\t */\n\tpublic void not() throws PrismException\n\t{\n\t\tif (!(type instanceof TypeBool)) {\n\t\t\tthrow new PrismException(\"Operator ! can only be applied to Boolean vectors\");\n\t\t}\n\t\tvaluesB.flip(0, size);\n\t}\n\n\t// Accessors\n\t\n\t/**\n\t * Get the type of the values stored\n\t */\n\tpublic Type getType()\n\t{\n\t\treturn type;\n\t}\n\t\n\t@Override\n\tpublic int getSize()\n\t{\n\t\treturn size;\n\t}\n\n\t/**\n\t * Get the accuracy.\n\t */\n\tpublic Accuracy getAccuracy()\n\t{\n\t\treturn accuracy;\n\t}\n\n\t@Override\n\tpublic Object getValue(int i)\n\t{\n\t\tif (type instanceof TypeBool) {\n\t\t\treturn valuesB.get(i);\n\t\t} else {\n\t\t\treturn valuesO[i];\n\t\t}\n\t}\n\n\t/**\n\t * Get the value of first vector element that is in the (BitSet) filter.\n\t */\n\tpublic Object firstFromBitSet(BitSet filter)\n\t{\n\t\treturn getValue(filter.nextSetBit(0));\n\t}\n\n\t@Override\n\tpublic Iterator<Object> iterator()\n\t{\n\t\treturn new Iterator<Object>()\n\t\t{\n\t\t\tint i = 0;\n\t\t\t\n\t\t\t@Override\n\t\t\tpublic Object next()\n\t\t\t{\n\t\t\t\treturn getValue(i++);\n\t\t\t}\n\t\t\t\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn i < size;\n\t\t\t}\n\t\t};\n\t}\n\t\n\t/**\n\t * Return a filtered view of this vector, only including\n\t * the values for states whose index is set in {@code filter}.\n\t */\n\tpublic Iterable<Object> filtered(BitSet filter)\n\t{\n\t\treturn new Iterable<Object>()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic Iterator<Object> iterator()\n\t\t\t{\n\t\t\t\treturn new Iterator<Object>()\n\t\t\t\t{\n\t\t\t\t\tint i = filter.nextSetBit(0);\n\t\t\t\t\t\n\t\t\t\t\t@Override\n\t\t\t\t\tpublic Object next()\n\t\t\t\t\t{\n\t\t\t\t\t\tObject o = getValue(i);\n\t\t\t\t\t\ti = filter.nextSetBit(i + 1);\n\t\t\t\t\t\treturn o;\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\t@Override\n\t\t\t\t\tpublic boolean hasNext()\n\t\t\t\t\t{\n\t\t\t\t\t\treturn i >= 0;\n\t\t\t\t\t}\n\t\t\t\t};\n\t\t\t}\n\t\t};\n\t}\n\t\n\t/**\n\t * For Boolean-valued vectors, get the BitSet storing the data.\n\t */\n\tpublic BitSet getBitSet()\n\t{\n\t\treturn valuesB;\n\t}\n\n\t/**\n\t * For double-valued vectors, get a double array storing the data.\n\t */\n\tpublic double[] getDoubleArray()\n\t{\n\t\tdouble[] valuesD = new double[size];\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tvaluesD[i] = (double) valuesO[i];\n\t\t}\n\t\treturn valuesD;\n\t}\n\n\t/**\n\t * Get a BitSet representing the states which satisfy a predicate.\n\t */\n\tpublic BitSet getBitSetFromPredicate(Predicate predicate) throws PrismException\n\t{\n\t\tBitSet bs = new BitSet();\n\t\tfor (int i = 0; i < size; i++) {\n\t\t\tbs.set(i, predicate.test(getValue(i)));\n\t\t}\n\t\treturn bs;\n\t}\n\t\n\t/**\n\t * Get a BitSet for the states whose value is (approximately) equal to {@code value}.\n\t * For double values, equality is only checked approximately, either using the stored\n\t * accuracy for the vector, if present, or a default accuracy level otherwise.\n\t * For other types, values must be identical.\n\t * The type of {@code value} is assumed to match that of the vector.\n\t */\n\tpublic BitSet getBitSetFromCloseValue(Object value) throws PrismException\n\t{\n\t\tAccuracy accuracy = ResultTesting.getTestingAccuracy(getAccuracy());\n\t\treturn getBitSetFromCloseValue(value, accuracy);\n\t}\n\n\t/**\n\t * Get a BitSet for the states whose value is (approximately) equal to {@code value}.\n\t * For double values, equality is only checked approximately, either using the specified\n\t * accuracy (within either absolute or relative error {@code epsilon}).\n\t * The type of {@code value} is assumed to match that of the vector.\n\t */\n\tpublic BitSet getBitSetFromCloseValue(Object value, double epsilon, boolean abs) throws PrismException\n\t{\n\t\tAccuracy accuracy = new Accuracy(Accuracy.AccuracyLevel.BOUNDED, epsilon, abs);\n\t\treturn getBitSetFromCloseValue(value, accuracy);\n\t}\n\n\t/**\n\t * Get a BitSet for the states whose value is (approximately) equal to {@code value}.\n\t * For double values, equality is only checked approximately, either using the accuracy.\n\t * For other types, values must be identical.\n\t * The type of {@code value} is assumed to match that of the vector.\n\t */\n\tpublic BitSet getBitSetFromCloseValue(Object value, Accuracy accMatch) throws PrismException\n\t{\n\t\treturn getBitSetFromPredicate(v -> ExpressionFilter.isClose(v, value, getType(), accMatch));\n\t}\n\n\t// Printing methods\n\n\t/**\n\t * Print vector to a log/file (non-zero/non-false entries only).\n\t */\n\tpublic void print(PrismLog log)\n\t{\n\t\tdoPrinting(log, -1, null, true, false, true, true);\n\t}\n\n\t/**\n\t * Print up to {@code limit} entries of a vector to a log/file (non-zero/non-false entries only).\n\t */\n\tpublic void print(PrismLog log, int limit)\n\t{\n\t\tdoPrinting(log, limit, null, true, false, true, true);\n\t}\n\n\t/**\n\t * Print vector to a log/file.\n\t * @param log The log\n\t * @param printSparse Print non-zero/non-false elements only? \n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print states (variable values) for each element? \n\t * @param printIndices Print state indices for each element? \n\t */\n\tpublic void print(PrismLog log, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices)\n\t{\n\t\tdoPrinting(log, -1, null, printSparse, printMatlab, printStates, printIndices);\n\t}\n\n\t/**\n\t * Print part of vector to a log/file (non-zero/non-false entries only).\n\t * @param log The log\n\t * @param filter A BitSet specifying which states to print for.\n\t */\n\tpublic void printFiltered(PrismLog log, BitSet filter)\n\t{\n\t\tdoPrinting(log, -1, filter, true, false, true, true);\n\t}\n\n\t/**\n\t * Print part of vector to a log/file.\n\t * @param log The log\n\t * @param filter A BitSet specifying which states to print for (null if all).\n\t * @param printSparse Print non-zero/non-false elements only? \n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print states (variable values) for each element? \n\t * @param printIndices Print state indices for each element? \n\t */\n\tpublic void printFiltered(PrismLog log, BitSet filter, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices)\n\t{\n\t\tdoPrinting(log, -1, filter, printSparse, printMatlab, printStates, printIndices);\n\t}\n\n\t/**\n\t * Print part of vector to a log/file.\n\t * @param log The log\n\t * @param limit Maximum number of entries to print (-1 = no limit)\n\t * @param filter A BitSet specifying which states to print for (null if all).\n\t * @param printSparse Print non-zero/non-false elements only? \n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print states (variable values) for each element? \n\t * @param printIndices Print state indices for each element? \n\t */\n\tprivate void doPrinting(PrismLog log, int limit, BitSet filter, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices)\n\t{\n\t\tint i, count = 0;\n\n\t\tif (limit == -1)\n\t\t\tlimit = Integer.MAX_VALUE;\n\n\t\t// Header for Matlab format\n\t\tif (printMatlab)\n\t\t\tlog.println(!printSparse ? \"v = [\" : \"v = sparse(\" + size + \",1);\");\n\n\t\t// Print vector\n\t\tif (filter == null) {\n\t\t\tfor (i = 0; i < size & count < limit; i++) {\n\t\t\t\tif (printLine(log, i, printSparse, printMatlab, printStates, printIndices))\n\t\t\t\t\tcount++;\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = filter.nextSetBit(0); i >= 0 && count < limit; i = filter.nextSetBit(i + 1)) {\n\t\t\t\tif (printLine(log, i, printSparse, printMatlab, printStates, printIndices))\n\t\t\t\t\tcount++;\n\t\t\t}\n\t\t}\n\n\t\t// Check if all zero\n\t\tif (printSparse && !printMatlab && count == 0) {\n\t\t\tlog.println(type == TypeBool.getInstance() ? \"(none)\" : \"(all zero)\");\n\t\t\treturn;\n\t\t}\n\n\t\t// Footer for Matlab format\n\t\tif (printMatlab && !printSparse)\n\t\t\tlog.println(\"];\");\n\t}\n\n\tprivate boolean printLine(PrismLog log, int n, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices)\n\t{\n\t\tif (!printSparse || isValueNonZero(getValue(n))) {\n\t\t\tif (printMatlab) {\n\t\t\t\tif (printSparse) {\n\t\t\t\t\tlog.println(\"v(\" + (n + 1) + \")=\" + getValue(n) + \";\");\n\t\t\t\t} else {\n\t\t\t\t\tlog.println(getValue(n));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (printIndices) {\n\t\t\t\t\tlog.print(n);\n\t\t\t\t}\n\t\t\t\tif (printStates && statesList != null) {\n\t\t\t\t\tif (printIndices) {\n\t\t\t\t\t\tlog.print(\":\");\n\t\t\t\t\t}\n\t\t\t\t\tlog.print(statesList.get(n).toString());\n\t\t\t\t}\n\t\t\t\tif (printSparse && type instanceof TypeBool) {\n\t\t\t\t\tlog.println();\n\t\t\t\t} else {\n\t\t\t\t\tif (printIndices || printStates) {\n\t\t\t\t\t\tlog.print(\"=\");\n\t\t\t\t\t}\n\t\t\t\t\tlog.println(getValue(n));\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn true;\n\t\t} else {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\t/**\n\t * Is the given vector value non-zero/non-false? (for sparse printing)\n\t */\n\tprivate boolean isValueNonZero(Object value)\n\t{\n\t\tif (value instanceof Integer) {\n\t\t\treturn ((int) value) != 0;\n\t\t} else if (value instanceof Double) {\n\t\t\treturn ((double) value) != 0.0;\n\t\t} else if (value instanceof Boolean) {\n\t\t\treturn (boolean) value;\n\t\t}\n\t\treturn true;\n\t}\n\n\t// Standard methods\n\t\n\t/**\n\t * Make a (deep) copy of this vector\n\t */\n\tpublic StateValues deepCopy() throws PrismException\n\t{\n\t\tStateValues sv = new StateValues();\n\t\tsv.type = type;\n\t\tsv.size = size;\n\t\tsv.accuracy = accuracy;\n\t\tsv.statesList = statesList;\n\t\tif (valuesB != null) {\n\t\t\tsv.valuesB = (BitSet) valuesB.clone();\n\t\t}\n\t\tif (valuesO != null) {\n\t\t\tsv.valuesO = valuesO.clone();\n\t\t}\n\t\treturn sv;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tif (type instanceof TypeBool) {\n\t\t\treturn valuesB.toString();\n\t\t} else {\n\t\t\treturn Arrays.toString(valuesO);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/SubNondetModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Mateusz Ujma <mateusz.ujma@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\n\nimport common.IterableStateSet;\nimport io.ModelExportOptions;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport prism.ActionList;\nimport prism.ActionListOwner;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport strat.MDStrategy;\n\n/**\n * Class for creating a sub-model of any NondetModel, please note the translate* methods\n * used to translate between state ids for model and sub-model. Created sub-model will have new \n * state numbering from 0 to number of states in the sub model.\n */\npublic class SubNondetModel<Value> implements NondetModel<Value>, ActionListOwner\n{\n\n\tprivate NondetModel<Value> model = null;\n\tprivate ActionList actionList;\n\tprivate BitSet states = null;\n\tprivate Map<Integer, BitSet> actions = null;\n\tprivate BitSet initialStates = null;\n\tprivate List<State> statesList = null;\n\tprivate Map<Integer, Integer> stateLookupTable = new HashMap<Integer, Integer>();\n\tprivate Map<Integer, Map<Integer, Integer>> actionLookupTable = new HashMap<Integer, Map<Integer, Integer>>();\n\tprivate Map<Integer, Integer> inverseStateLookupTable = new HashMap<Integer, Integer>();\n\n\t/**\n\t * (Optionally) the stored predecessor relation. Becomes inaccurate after the model is changed!\n\t */\n\tprotected PredecessorRelation predecessorRelation;\n\n\tprivate int numTransitions = 0;\n\tprivate int maxNumChoices = 0;\n\tprivate int numChoices = 0;\n\n\tpublic SubNondetModel(NondetModel<Value> model, BitSet states, Map<Integer, BitSet> actions, BitSet initialStates)\n\t{\n\t\tthis.model = model;\n\t\tactionList = new ActionList(this::findActionsUsed);\n\t\tthis.states = states;\n\t\tthis.actions = actions;\n\t\tthis.initialStates = initialStates;\n\n\t\tgenerateStatistics();\n\t\tgenerateLookupTable(states, actions);\n\t}\n\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn model.getModelType();\n\t}\n\n\t@Override\n\tpublic ActionList getActionList()\n\t{\n\t\treturn actionList;\n\t}\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\treturn actionList.getActions();\n\t}\n\n\t@Override\n\tpublic int actionIndex(Object action)\n\t{\n\t\treturn actionList.actionIndex(action);\n\t}\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn states.cardinality();\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn initialStates.cardinality();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\tList<Integer> is = new ArrayList<Integer>();\n\t\tfor (int i = initialStates.nextSetBit(0); i >= 0; i = initialStates.nextSetBit(i + 1)) {\n\t\t\tis.add(translateState(i));\n\t\t}\n\n\t\treturn is;\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn translateState(initialStates.nextSetBit(0));\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(int i)\n\t{\n\t\treturn initialStates.get(translateState(i));\n\t}\n\n\t@Override\n\tpublic int getNumDeadlockStates()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getDeadlockStates()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic StateValues getDeadlockStatesList()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic int getFirstDeadlockState()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic boolean isDeadlockState(int i)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\t// We use lazy generation because in many cases the state list is not needed\n\t\tif (statesList == null) {\n\t\t\tstatesList = generateSubStateList(states);\n\t\t}\n\t\treturn statesList;\n\t}\n\n\tprivate List<State> generateSubStateList(BitSet states)\n\t{\n\t\tList<State> statesList = new ArrayList<State>();\n\t\tfor (int i : new IterableStateSet(states, model.getNumStates())){\n\t\t\tstatesList.add(model.getStatesList().get(i));\n\t\t}\n\t\treturn statesList;\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\t// we can return the varList of the model, as we do not change\n\t\t// the variables in the model\n\t\treturn model.getVarList();\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\t\n\t@Override\n\tpublic Set<String> getLabels() {\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(String name)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic int getNumTransitions()\n\t{\n\t\treturn numTransitions;\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks() throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(BitSet except) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void exportToPrismExplicitTra(PrismLog log, int precision)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void exportToPrismLanguage(String filename, int precision) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void exportStates(VarList varList, PrismLog out, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic String infoString()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic String infoStringTable()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic int getNumChoices(int s)\n\t{\n\t\ts = translateState(s);\n\t\treturn actions.get(s).cardinality();\n\t}\n\n\t@Override\n\tpublic int getMaxNumChoices()\n\t{\n\t\treturn maxNumChoices;\n\t}\n\n\t@Override\n\tpublic int getNumChoices()\n\t{\n\t\treturn numChoices;\n\t}\n\n\t@Override\n\tpublic Object getAction(int s, int i)\n\t{\n\t\tint sOriginal = translateState(s);\n\t\tint iOriginal = translateAction(s, i);\n\n\t\treturn model.getAction(sOriginal, iOriginal);\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int s, int i)\n\t{\n\t\tint sOriginal = translateState(s);\n\t\tint iOriginal = translateAction(s, i);\n\t\treturn model.getNumTransitions(sOriginal, iOriginal);\n\t}\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(int s, int i)\n\t{\n\t\tint sOriginal = translateState(s);\n\t\tint iOriginal = translateAction(s, i);\n\n\t\tSuccessorsIterator it = model.getSuccessors(sOriginal, iOriginal);\n\t\treturn new SuccessorsIterator() {\n\n\t\t\t@Override\n\t\t\tpublic boolean successorsAreDistinct()\n\t\t\t{\n\t\t\t\treturn it.successorsAreDistinct();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn it.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\treturn inverseTranslateState(it.next());\n\t\t\t}\n\n\t\t};\n\t}\n\n\tprivate BitSet translateSet(BitSet set)\n\t{\n\t\tBitSet translatedBitSet = new BitSet();\n\t\tfor (int i = set.nextSetBit(0); i >= 0; i = set.nextSetBit(i + 1)) {\n\t\t\ttranslatedBitSet.set(translateState(i));\n\t\t}\n\t\treturn translatedBitSet;\n\t}\n\n\tprivate void generateStatistics()\n\t{\n\t\tfor (int i : new IterableStateSet(states, model.getNumStates())){\n\t\t\tnumTransitions += getTransitions(i);\n\t\t\tnumChoices += actions.get(i).cardinality();\n\t\t\tmaxNumChoices = Math.max(maxNumChoices, model.getNumChoices(i));\n\t\t}\n\t}\n\n\tprivate int getTransitions(int state)\n\t{\n\t\tint transitions = 0;\n\t\tfor (int i : new IterableStateSet(actions.get(state), model.getNumChoices(state))){\n\t\t\ttransitions += model.getNumTransitions(state, i);\n\t\t}\n\t\treturn transitions;\n\t}\n\n\t@Override\n\tpublic Model<Value> constructInducedModel(MDStrategy<Value> strat)\n\t{\n\t\tthrow new RuntimeException(\"Not implemented\");\n\t}\n\n\tprivate void generateLookupTable(BitSet states, Map<Integer, BitSet> actions)\n\t{\n\t\tfor (int i : new IterableStateSet(states, model.getNumStates())){\n\t\t\tinverseStateLookupTable.put(i, stateLookupTable.size());\n\t\t\tstateLookupTable.put(stateLookupTable.size(), i);\n\t\t\tMap<Integer, Integer> r = new HashMap<Integer, Integer>();\n\t\t\tfor (int j : new IterableStateSet(actions.get(i), model.getNumChoices(i))){\n\t\t\t\tr.put(r.size(), j);\n\t\t\t}\n\t\t\tactionLookupTable.put(actionLookupTable.size(), r);\n\t\t}\n\t}\n\n\tpublic int translateState(int s)\n\t{\n\t\treturn stateLookupTable.get(s);\n\t}\n\n\tprivate int inverseTranslateState(int s)\n\t{\n\t\treturn inverseStateLookupTable.get(s);\n\t}\n\n\tpublic int translateAction(int s, int i)\n\t{\n\t\treturn actionLookupTable.get(s).get(i);\n\t}\n\n\t@Override\n\tpublic boolean hasStoredPredecessorRelation() {\n\t\treturn (predecessorRelation != null);\n\t}\n\n\t@Override\n\tpublic PredecessorRelation getPredecessorRelation(prism.PrismComponent parent, boolean storeIfNew) {\n\t\tif (predecessorRelation != null) {\n\t\t\treturn predecessorRelation;\n\t\t}\n\n\t\tPredecessorRelation pre = PredecessorRelation.forModel(parent, this);\n\n\t\tif (storeIfNew) {\n\t\t\tpredecessorRelation = pre;\n\t\t}\n\t\treturn pre;\n\t}\n\n\t@Override\n\tpublic void clearPredecessorRelation() {\n\t\tpredecessorRelation = null;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/SuccessorsIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Iterator;\nimport java.util.NoSuchElementException;\nimport java.util.PrimitiveIterator;\nimport java.util.Spliterator;\nimport java.util.Spliterators;\nimport java.util.stream.IntStream;\nimport java.util.stream.StreamSupport;\n\nimport common.iterable.FunctionalIterator;\nimport common.iterable.Reducible;\nimport common.iterable.SingletonIterator;\n\n/**\n * Base class and static helpers for iterators over successor states.\n * <br>\n * Carries information whether the successors are known to be distinct\n * and helpers to ensure that this is the case, i.e., allowing iteration\n * over the set of successors or the multiset of successors. The latter\n * might have better performance, as no deduplication is needed.\n  */\npublic abstract class SuccessorsIterator implements PrimitiveIterator.OfInt\n{\n\t/** Is it guaranteed that every successor will occur only once? */\n\tpublic abstract boolean successorsAreDistinct();\n\n\t@Override\n\tpublic abstract boolean hasNext();\n\n\t@Override\n\tpublic abstract int nextInt();\n\n\t/**\n\t * Return a SuccessorsIterator that guarantees that there\n\t * are no duplicates in the successor states, i.e., iterating\n\t * over the set of successors instead of a multiset.\n\t * <br>\n\t * The iterator this method is called on can not be used afterwards,\n\t * only the returned iterator.\n\t */\n\tpublic SuccessorsIterator distinct()\n\t{\n\t\tif (successorsAreDistinct()) {\n\t\t\treturn this;\n\t\t} else {\n\t\t\treturn new SuccessorsIteratorFromOfInt(Reducible.extend(this).distinct(), true);\n\t\t}\n\t}\n\n\t/** Provide an IntStream */\n\tpublic IntStream stream()\n\t{\n\t\treturn StreamSupport.intStream(\n\t\t\t\tSpliterators.spliteratorUnknownSize(this, successorsAreDistinct() ? Spliterator.DISTINCT : 0),\n\t\t\t\tfalse);\n\t}\n\n\t/** Wrapper, underlying iterator is an OfInt iterator */\n\tprivate static class SuccessorsIteratorFromOfInt extends SuccessorsIterator {\n\t\tprivate java.util.PrimitiveIterator.OfInt it;\n\t\tprivate boolean distinct;\n\n\t\tpublic SuccessorsIteratorFromOfInt(PrimitiveIterator.OfInt it, boolean distinct)\n\t\t{\n\t\t\tthis.it = it;\n\t\t\tthis.distinct = distinct;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean successorsAreDistinct()\n\t\t{\n\t\t\treturn distinct;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn it.hasNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\treturn it.nextInt();\n\t\t}\n\t}\n\n\t/** Wrapper, underlying iterator is an Iterator<Integer> iterator */\n\tprivate static class SuccessorsIteratorFromIterator extends SuccessorsIterator {\n\t\tprivate Iterator<Integer> it;\n\t\tprivate boolean distinct;\n\n\t\tpublic SuccessorsIteratorFromIterator(Iterator<Integer> it, boolean distinct)\n\t\t{\n\t\t\tthis.it = it;\n\t\t\tthis.distinct = distinct;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn it.hasNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic Integer next()\n\t\t{\n\t\t\treturn it.next();\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\treturn it.next();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean successorsAreDistinct()\n\t\t{\n\t\t\treturn distinct;\n\t\t}\n\t};\n\n\t/** Helper, empty iterator */\n\tprivate static class SuccessorsIteratorEmpty extends SuccessorsIterator {\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tthrow new NoSuchElementException();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean successorsAreDistinct()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t};\n\n\t/** Helper, chain multiple SuccessorsIterators */\n\tprivate static class ChainedSuccessorsIterator extends SuccessorsIterator {\n\t\tprivate Iterator<SuccessorsIterator> iterators;\n\t\tprivate SuccessorsIterator current;\n\t\tprivate boolean distinct;\n\n\t\tpublic ChainedSuccessorsIterator(Iterator<SuccessorsIterator> iterators)\n\t\t{\n\t\t\tthis.iterators = iterators;\n\t\t\tcurrent = iterators.hasNext() ? iterators.next() : null;\n\t\t\tif (current != null && !iterators.hasNext()) {\n\t\t\t\t// only a single successor iterator, can inherit elementsAreDistinct\n\t\t\t\tdistinct = current.successorsAreDistinct();\n\t\t\t} else {\n\t\t\t\t// can not guarantee that successors are distinct\n\t\t\t\tdistinct = false;\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\tif (current == null) {\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\tif (current.hasNext()) {\n\t\t\t\t// the current iterator has another element\n\t\t\t\treturn true;\n\t\t\t}\n\n\t\t\t// the current iterator has no more elements,\n\t\t\t// search for the next iterator that as an element\n\t\t\twhile (iterators.hasNext()) {\n\t\t\t\t// consider the next iterator\n\t\t\t\tcurrent = iterators.next();\n\t\t\t\tif (current.hasNext()) {\n\t\t\t\t\t// iterator has element, keep current and return true\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// there are no more iterators / elements\n\t\t\tcurrent = null;\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tif (!hasNext()) {\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\t}\n\t\t\treturn current.nextInt();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean successorsAreDistinct()\n\t\t{\n\t\t\treturn distinct;\n\t\t}\n\t};\n\n\t/** Obtain a SuccessorsIterator with the given distinctness guarantee from an Iterator<Integer> */\n\tpublic static SuccessorsIterator from(Iterator<Integer> it, boolean distinctElements)\n\t{\n\t\treturn new SuccessorsIteratorFromIterator(it, distinctElements);\n\t}\n\n\t/** Obtain a SuccessorsIterator with the given distinctness guarantee from an OfInt */\n\tpublic static SuccessorsIterator from(PrimitiveIterator.OfInt it, boolean distinctElements)\n\t{\n\t\treturn new SuccessorsIteratorFromOfInt(it, distinctElements);\n\t}\n\n\t/** Obtain a SuccessorsIterator for a single state */\n\tpublic static SuccessorsIterator fromSingleton(int i)\n\t{\n\t\treturn new SuccessorsIteratorFromOfInt(new SingletonIterator.OfInt(i), true);\n\t}\n\n\t/** Obtain an empty SuccessorsIterator */\n\tpublic static SuccessorsIterator empty()\n\t{\n\t\treturn new SuccessorsIteratorEmpty();\n\t}\n\n\t/** Obtain a SuccessorsIterator, chaining multiple SuccessorsIterators one after the other */\n\tpublic static SuccessorsIterator chain(Iterator<SuccessorsIterator> iterators)\n\t{\n\t\treturn new ChainedSuccessorsIterator(iterators);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/UDTMC.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.PrimitiveIterator;\n\nimport common.Interval;\nimport common.IterableStateSet;\nimport explicit.rewards.MCRewards;\nimport parser.State;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.PrismException;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state uncertain DTMC.\n */\npublic interface UDTMC<Value> extends Model<Value>\n{\n\t// Accessors (for Model) - default implementations\n\t\n\t@Override\n\tpublic default ModelType getModelType()\n\t{\n\t\treturn ModelType.UDTMC;\n\t}\n\n\t// Accessors\n\t\n\t/**\n\t * Checks that transition probability interval lower bounds are positive\n\t * and throws an exception if any are not.\n\t */\n\tpublic default void checkLowerBoundsArePositive() throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\t\n\t/**\n\t * Do a matrix-vector multiplication followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_P { sum_j P(s,j)*vect[j] }\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t */\n\tpublic default void mvMultUnc(double vect[], MinMax minMax, double result[], BitSet subset, boolean complement)\n\t{\n\t\tmvMultUnc(vect, minMax, result, new IterableStateSet(subset, getNumStates(), complement).iterator());\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_P { sum_j P(s,j)*vect[j] }\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t * @param result Vector to store result in\n\t * @param states Perform computation for these rows, in the iteration order\n\t */\n\tpublic default void mvMultUnc(double vect[], MinMax minMax, double result[], PrimitiveIterator.OfInt states)\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tresult[s] = mvMultUncSingle(s, vect, minMax);\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication followed by min/max,\n\t * i.e. return min/max_P { sum_j P(s,j)*vect[j] }\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t */\n\tpublic double mvMultUncSingle(int s, double vect[], MinMax minMax);\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of rewards followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_P { rew(s) + sum_j P(s,j)*vect[j] }\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t */\n\tpublic default void mvMultRewUnc(double vect[], MCRewards<Double> mcRewards, MinMax minMax, double result[], BitSet subset, boolean complement)\n\t{\n\t\tmvMultRewUnc(vect, mcRewards, minMax, result, new IterableStateSet(subset, getNumStates(), complement).iterator());\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of rewards followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_P { rew(s) + sum_j P(s,j)*vect[j] }\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t * @param result Vector to store result in\n\t * @param states Perform computation for these rows, in the iteration order\n\t */\n\tpublic default void mvMultRewUnc(double vect[], MCRewards<Double> mcRewards, MinMax minMax, double result[], PrimitiveIterator.OfInt states)\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tresult[s] = mvMultRewUncSingle(s, vect, mcRewards, minMax);\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication and sum of rewards followed by min/max,\n\t * i.e. return min/max_P { rew(s) + sum_j P(s,j)*vect[j] }\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t */\n\tpublic default double mvMultRewUncSingle(int s, double vect[], MCRewards<Double> mcRewards, MinMax minMax)\n\t{\n\t\tdouble d = mcRewards.getStateReward(s);\n\t\t// TODO d += mcRewards.getTransitionReward(s);\n\t\td += mvMultUncSingle(s, vect, minMax);\n\t\treturn d;\n\t}\n\t\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_P { sum_j P(s,j)*vect[j] }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t */\n\tpublic default double mvMultUncGS(double vect[], MinMax minMax, PrimitiveIterator.OfInt states, boolean absolute)\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\t//d = mvMultJacSingle(s, vect, minMax);\n\t\t\t// Just do a normal (non-Jacobi) state update - not so easy to adapt for intervals\n\t\t\td = mvMultUncSingle(s, vect, minMax);\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication and sum of rewards followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_P { rew(s) + sum_j P(s,j)*vect[j] }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * @param vect Vector to multiply by\n\t * @param mcRewards The rewards\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t */\n\tpublic default double mvMultRewUncGS(double vect[], MCRewards<Double> mcRewards, MinMax minMax, PrimitiveIterator.OfInt states, boolean absolute)\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\t//d = mvMultJacSingle(s, vect, minMax);\n\t\t\t// Just do a normal (non-Jacobi) state update - not so easy to adapt for intervals\n\t\t\td = mvMultRewUncSingle(s, vect, mcRewards, minMax);\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/UDTMCModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.PrimitiveIterator;\n\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceType;\nimport common.IntSet;\nimport common.IterableStateSet;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.Rewards;\nimport parser.ast.Expression;\nimport prism.AccuracyFactory;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismFileLog;\n\n/**\n * Explicit-state model checker for uncertain discrete-time Markov chains (UDTMCs).\n */\npublic class UDTMCModelChecker extends ProbModelChecker\n{\n\t// DTMCModelChecker in order to use e.g. precomputation algorithms\n\tprotected DTMCModelChecker mcDTMC = null; \n\t\n\t/**\n\t * Create a new UDTMCModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic UDTMCModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tmcDTMC = new DTMCModelChecker(this);\n\t\tmcDTMC.inheritSettings(this);\n\t}\n\n\t// Model checking functions\n\n\t@Override\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkProbPathFormulaLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of UDTMC and DA for the LTL formula, and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tAcceptanceType[] allowedAcceptance = {\n\t\t\t\tAcceptanceType.RABIN,\n\t\t\t\tAcceptanceType.REACH,\n\t\t\t\tAcceptanceType.BUCHI,\n\t\t\t\tAcceptanceType.STREETT,\n\t\t\t\tAcceptanceType.GENERIC\n\t\t};\n\t\tLTLModelChecker.LTLProduct<UDTMC<Double>> product = mcLtl.constructDAProductForLTLFormula(this, (UDTMC<Double>) model, expr, statesOfInterest, allowedAcceptance);\n\t\tdoProductExports(product);\n\n\t\t// Find accepting states + compute reachability probabilities\n\t\tBitSet acc;\n\t\tif (product.getAcceptance() instanceof AcceptanceReach) {\n\t\t\tmainLog.println(\"\\nSkipping BSCC computation since acceptance is defined via goal states...\");\n\t\t\tacc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\t\t} else {\n\t\t\tmainLog.println(\"\\nFinding accepting BSCCs...\");\n\t\t\tacc = mcLtl.findAcceptingBSCCs(product.getProductModel(), product.getAcceptance());\n\t\t}\n\t\tmainLog.println(\"\\nComputing reachability probabilities...\");\n\t\tUDTMCModelChecker mcProduct = new UDTMCModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachProbs(product.getProductModel(), acc, minMax);\n\t\tStateValues probsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\tprobsProduct.print(out, false, false, false, false);\n\t\t\tout.close();\n\t\t}\n\n\t\t// Mapping probabilities in the original model\n\t\tStateValues probs = product.projectToOriginalModel(probsProduct);\n\t\tprobsProduct.clear();\n\n\t\treturn probs;\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardCoSafeLTL(Model<?> model, Rewards<?> modelRewards, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of UDTMC and DFA for the LTL formula, convert rewards and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tLTLModelChecker.LTLProduct<UDTMC<Double>> product = mcLtl.constructDFAProductForCosafetyReward(this, (UDTMC<Double>) model, expr, statesOfInterest);\n\t\tMCRewards<Double> productRewards = ((MCRewards<Double>) modelRewards).liftFromModel(product);\n\t\tdoProductExports(product);\n\n\t\t// Find accepting states + compute reachability rewards\n\t\tBitSet acc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\t\tmainLog.println(\"\\nComputing reachability rewards...\");\n\t\tUDTMCModelChecker mcProduct = new UDTMCModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachRewards(product.getProductModel(), productRewards, acc, minMax);\n\t\tStateValues rewardsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\t\t\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\t\trewardsProduct.print(out, false, false, false, false);\n\t\t\t\tout.close();\n\t\t}\n\n\t\t// Mapping rewards in the original model\n\t\tStateValues rewards = product.projectToOriginalModel(rewardsProduct);\n\t\trewardsProduct.clear();\n\t\t\n\t\treturn rewards;\n\t}\n\t\n\t// Numerical computation functions\n\n\t/**\n\t * Compute next-state probabilities.\n\t * i.e. compute the probability of being in a state in {@code target} in the next step.\n\t * @param udtmc The UDTMC\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeNextProbs(UDTMC<Double> udtmc, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\tlong timer = System.currentTimeMillis();\n\n\t\t// Check for any zero lower probability bounds (not supported\n\t\t// since this approach assumes the graph structure remains static)\n\t\tudtmc.checkLowerBoundsArePositive();\n\t\t\n\t\t// Store num states\n\t\tint n = udtmc.getNumStates();\n\t\tPrimitiveIterator.OfInt statesAll = new IterableStateSet(n).iterator();\n\n\t\t// Create/initialise solution vector(s)\n\t\tdouble[] soln = Utils.bitsetToDoubleArray(target, n);\n\t\tdouble[] soln2 = new double[n];\n\n\t\t// Next-step probabilities\n\t\tudtmc.mvMultUnc(soln, minMax, soln2, statesAll);\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\tres.soln = soln2;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = 1;\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute bounded reachability probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target} within k steps.\n\t * @param udtmc The UDTMC\n\t * @param target Target states\n\t * @param k Bound\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(UDTMC<Double> udtmc, BitSet target, int k, MinMax minMax) throws PrismException\n\t{\n\t\treturn computeBoundedUntilProbs(udtmc, null, target, k, minMax);\n\t}\n\n\t/**\n\t * Compute bounded until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * within k steps, and while remaining in states in {@code remain}.\n\t * @param udtmc The UDTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param k Bound\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeBoundedUntilProbs(UDTMC<Double> udtmc, BitSet remain, BitSet target, int k, MinMax minMax) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet unknown;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\n\t\t// Start bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting bounded probabilistic reachability...\");\n\n\t\t// Check for any zero lower probability bounds (not supported\n\t\t// since this approach assumes the graph structure remains static)\n\t\tudtmc.checkLowerBoundsArePositive();\n\t\t\n\t\t// Store num states\n\t\tn = udtmc.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : 0.0;\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\twhile (iters < k) {\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tudtmc.mvMultUnc(soln, minMax, soln2, unknownStates.iterator());\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Bounded probabilistic reachability\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.lastSoln = soln2;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\treturn res;\n\t}\n\t\n\t/**\n\t * Compute reachability probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target}.\n\t * @param udtmc The UDTMC\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeReachProbs(UDTMC<Double> udtmc, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\treturn computeReachProbs(udtmc, null, target, minMax);\n\t}\n\n\t/**\n\t * Compute until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target}.\n\t * @param udtmc The UDTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeUntilProbs(UDTMC<Double> udtmc, BitSet remain, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\treturn computeReachProbs(udtmc, remain, target, minMax);\n\t}\n\n\t/**\n\t * Compute reachability/until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * while remaining in those in {@code remain}.\n\t * @param udtmc The UDTMC\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeReachProbs(UDTMC<Double> udtmc, BitSet remain, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\t// Switch to a supported method, if necessary\n\t\tIMDPSolnMethod imdpSolnMethod = this.imdpSolnMethod;\n\t\tswitch (imdpSolnMethod)\n\t\t{\n\t\tcase VALUE_ITERATION:\n\t\tcase GAUSS_SEIDEL:\n\t\t\tbreak; // supported\n\t\tdefault:\n\t\t\timdpSolnMethod = IMDPSolnMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to solution method \\\"\" + imdpSolnMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\t// Start probabilistic reachability\n\t\tlong timer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting probabilistic reachability...\");\n\n\t\t// Check for any zero lower probability bounds (not supported\n\t\t// since this approach assumes the graph structure remains static)\n\t\tudtmc.checkLowerBoundsArePositive();\n\t\t\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tudtmc.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tint n = udtmc.getNumStates();\n\n\t\t// Precomputation\n\t\tBitSet no, yes;\n\t\tPredecessorRelation pre = null;\n\t\tif (precomp && (prob0 || prob1) && preRel) {\n\t\t\tpre = udtmc.getPredecessorRelation(this, true);\n\t\t}\n\t\tif (precomp && prob0) {\n\t\t\tif (preRel) {\n\t\t\t\tno = mcDTMC.prob0(udtmc, remain, target, pre);\n\t\t\t} else {\n\t\t\t\tno = mcDTMC.prob0(udtmc, remain, target);\n\t\t\t}\n\t\t} else {\n\t\t\tno = new BitSet();\n\t\t\tif (remain != null) {\n\t\t\t\tno.or(remain);\n\t\t\t\tno.or(target);\n\t\t\t\tno.flip(0, n);\n\t\t\t}\n\t\t}\n\t\tif (precomp && prob1) {\n\t\t\tif (preRel) {\n\t\t\t\tyes = mcDTMC.prob1(udtmc, remain, target, pre);\n\t\t\t} else {\n\t\t\t\tyes = mcDTMC.prob1(udtmc, remain, target);\n\t\t\t}\n\t\t} else {\n\t\t\tyes = (BitSet) target.clone();\n\t\t}\n\n\t\t// Print results of precomputation\n\t\tint numYes = yes.cardinality();\n\t\tint numNo = no.cardinality();\n\t\tmainLog.println(\"target=\" + target.cardinality() + \", yes=\" + numYes + \", no=\" + numNo + \", maybe=\" + (n - (numYes + numNo)));\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString sMinMax = minMax.isMinUnc() ? \"min\" : \"max\";\n\t\tmainLog.println(\"Starting value iteration (\" + sMinMax + \")...\");\n\n\t\t// Store num states\n\t\tn = udtmc.getNumStates();\n\n\t\t// Initialise solution vectors\n\t\tdouble[] init = new double[n];\n\t\tfor (int i = 0; i < n; i++)\n\t\t\tinit[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : 0.0;\n\n\t\t// Determine set of states actually need to compute values for\n\t\tBitSet unknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(yes);\n\t\tunknown.andNot(no);\n\n\t\t// Compute probabilities (if needed)\n\t\tModelCheckerResult res;\n\t\tif (numYes + numNo < n) {\n\t\t\tIterationMethod iterationMethod = null;\n\t\t\tswitch (imdpSolnMethod) {\n\t\t\tcase VALUE_ITERATION:\n\t\t\t\titerationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\t\t\tbreak;\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\t\titerationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, false);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown solution method \" + imdpSolnMethod.fullName());\n\t\t\t}\n\t\t\tIterationMethod.IterationValIter iterationReachProbs = iterationMethod.forMvMultMinMaxUnc(udtmc, minMax);\n\t\t\titerationReachProbs.init(init);\n\t\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\t\t\tString description = sMinMax + \", with \" + iterationMethod.getDescriptionShort();\n\t\t\tres = iterationMethod.doValueIteration(this, description, iterationReachProbs, unknownStates, timer, null);\n\t\t} else {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(yes, n);\n\t\t\tres.accuracy = AccuracyFactory.doublesFromQualitative();\n\t\t}\n\t\t\n\t\t// Finished probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Probabilistic reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\n\t\treturn res;\n\t}\n\t\n\t/**\n\t * Compute expected reachability rewards.\n\t * @param udtmc The UDTMC\n\t * @param udtmcRewards The rewards\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeReachRewards(UDTMC<Double> udtmc, MCRewards<Double> udtmcRewards, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\t// Switch to a supported method, if necessary\n\t\tIMDPSolnMethod imdpSolnMethod = this.imdpSolnMethod;\n\t\tswitch (imdpSolnMethod)\n\t\t{\n\t\tcase VALUE_ITERATION:\n\t\tcase GAUSS_SEIDEL:\n\t\t\tbreak; // supported\n\t\tdefault:\n\t\t\timdpSolnMethod = IMDPSolnMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to solution method \\\"\" + imdpSolnMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\t// Start probabilistic reachability\n\t\tlong timer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting expected reachability...\");\n\n\t\t// Check for any zero lower probability bounds (not supported\n\t\t// since this approach assumes the graph structure remains static)\n\t\tudtmc.checkLowerBoundsArePositive();\n\t\t\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tudtmc.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tint n = udtmc.getNumStates();\n\n\t\t// Precomputation (not optional)\n\t\tBitSet inf;\n\t\tif (preRel) {\n\t\t\t// prob1 via predecessor relation\n\t\t\tPredecessorRelation pre = udtmc.getPredecessorRelation(this, true);\n\t\t\tinf = mcDTMC.prob1(udtmc, null, target, pre);\n\t\t} else {\n\t\t\t// prob1 via fixed-point algorithm\n\t\t\tinf = mcDTMC.prob1(udtmc, null, target);\n\t\t}\n\t\tinf.flip(0, n);\n\n\t\t// Print results of precomputation\n\t\tint numTarget = target.cardinality();\n\t\tint numInf = inf.cardinality();\n\t\tmainLog.println(\"target=\" + numTarget + \", inf=\" + numInf + \", rest=\" + (n - (numTarget + numInf)));\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString sMinMax = minMax.isMinUnc() ? \"min\" : \"max\";\n\t\tmainLog.println(\"Starting value iteration (\" + sMinMax + \")...\");\n\n\t\t// Store num states\n\t\tn = udtmc.getNumStates();\n\n\t\t// Initialise solution vectors\n\t\tdouble[] init = new double[n];\n\t\tfor (int i = 0; i < n; i++)\n\t\t\tinit[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : 0.0;\n\n\t\t// Determine set of states actually need to compute values for\n\t\tBitSet unknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tunknown.andNot(inf);\n\n\t\t// Compute probabilities (if needed)\n\t\tModelCheckerResult res;\n\t\tif (numTarget + numInf < n) {\n\t\t\tIterationMethod iterationMethod = null;\n\t\t\tswitch (imdpSolnMethod) {\n\t\t\tcase VALUE_ITERATION:\n\t\t\t\titerationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\t\t\tbreak;\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\t\titerationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, false);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown solution method \" + imdpSolnMethod.fullName());\n\t\t\t}\n\t\t\tIterationMethod.IterationValIter iterationReachProbs = iterationMethod.forMvMultRewMinMaxUnc(udtmc, udtmcRewards, minMax);\n\t\t\titerationReachProbs.init(init);\n\t\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\t\t\tString description = sMinMax + \", with \" + iterationMethod.getDescriptionShort();\n\t\t\tres = iterationMethod.doValueIteration(this, description, iterationReachProbs, unknownStates, timer, null);\n\t\t} else {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(inf, n, Double.POSITIVE_INFINITY);\n\t\t\tres.accuracy = AccuracyFactory.doublesFromQualitative();\n\t\t}\n\t\t\n\t\t// Finished probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Probabilistic reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\n\t\treturn res;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/UMDP.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.PrimitiveIterator;\n\nimport common.IterableStateSet;\nimport explicit.rewards.MDPRewards;\nimport prism.ModelType;\nimport prism.PrismException;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state uncertain MDP.\n */\npublic interface UMDP<Value> extends NondetModel<Value>\n{\n\t// Accessors (for Model) - default implementations\n\n\t@Override\n\tpublic default ModelType getModelType()\n\t{\n\t\treturn ModelType.UMDP;\n\t}\n\n\t@Override\n\tdefault void exportToPrismLanguage(final String filename, int precision) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException(\"UMDP model export not implemented\");\n\t}\n\n\t// Accessors\n\n\t/**\n\t * Checks that transition probability lower bounds are positive\n\t * and throws an exception if any are not.\n\t */\n\tpublic default void checkLowerBoundsArePositive() throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_k min/max_P { sum_j P(s,k,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max info (strategy and uncertainty)\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default void mvMultUnc(double vect[], MinMax minMax, double result[], BitSet subset, boolean complement, int[] strat)\n\t{\n\t\tmvMultUnc(vect, minMax, result, new IterableStateSet(subset, getNumStates(), complement).iterator(), strat);\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_k min/max_P { sum_j P(s,k,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max info (strategy and uncertainty)\n\t * @param result Vector to store result in\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default void mvMultUnc(double vect[], MinMax minMax, double result[], PrimitiveIterator.OfInt states, int[] strat)\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tresult[s] = mvMultUncSingle(s, vect, minMax, strat);\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication followed by min/max,\n\t * i.e. return min/max_k min/max_P { sum_j P(s,k,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default double mvMultUncSingle(int s, double vect[], MinMax minMax, int[] strat)\n\t{\n\t\tint stratCh = -1;\n\t\tdouble minmax = 0;\n\t\tboolean first = true;\n\t\tboolean min = minMax.isMin();\n\n\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t// Compute sum for this distribution\n\t\t\tdouble d = mvMultUncSingle(s, choice, vect, minMax);\n\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null)\n\t\t\t\t\tstratCh = choice;\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null && !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication for a specific choice k\n\t * i.e. return min/max_P { sum_j P(s,k,j)*vect[j] }\n\t * @param s State (row) index\n\t * @param k Choice index\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t */\n\tpublic double mvMultUncSingle(int s, int k, double vect[], MinMax minMax);\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of rewards followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_k min/max_P { rew(s) + rew_k(s) + sum_j P(s,k,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param minMax Min/max info (strategy and uncertainty)\n\t * @param result Vector to store result in\n\t * @param subset Only do multiplication for these rows (ignored if null)\n\t * @param complement If true, {@code subset} is taken to be its complement (ignored if {@code subset} is null)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default void mvMultRewUnc(double vect[], MDPRewards<Double> mdpRewards, MinMax minMax, double result[], BitSet subset, boolean complement, int[] strat)\n\t{\n\t\tmvMultRewUnc(vect, mdpRewards, minMax, result, new IterableStateSet(subset, getNumStates(), complement).iterator(), strat);\n\t}\n\n\t/**\n\t * Do a matrix-vector multiplication and sum of rewards followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_k min/max_P { rew(s) + rew_k(s) + sum_j P(s,k,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param minMax Min/max info (strategy and uncertainty)\n\t * @param result Vector to store result in\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default void mvMultRewUnc(double vect[], MDPRewards<Double> mdpRewards, MinMax minMax, double result[], PrimitiveIterator.OfInt states, int[] strat)\n\t{\n\t\twhile (states.hasNext()) {\n\t\t\tint s = states.nextInt();\n\t\t\tresult[s] = mvMultRewUncSingle(s, vect, mdpRewards, minMax, strat);\n\t\t}\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication and sum of rewards followed by min/max,\n\t * i.e. return min/max_k min/max_P { rew(s) + rew_k(s) + sum_j P(s,k,j)*vect[j] }\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param s Row index\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param minMax Min/max info (strategy and uncertainty)\n\t * @param strat Storage for (memoryless) strategy choice indices (ignored if null)\n\t */\n\tpublic default double mvMultRewUncSingle(int s, double vect[], MDPRewards<Double> mdpRewards, MinMax minMax, int[] strat)\n\t{\n\t\tint stratCh = -1;\n\t\tdouble minmax = 0;\n\t\tboolean first = true;\n\t\tboolean min = minMax.isMin();\n\n\t\tfor (int choice = 0, numChoices = getNumChoices(s); choice < numChoices; choice++) {\n\t\t\tdouble d = mvMultRewUncSingle(s, choice, vect, mdpRewards, minMax);\n\t\t\t// Check whether we have exceeded min/max so far\n\t\t\tif (first || (min && d < minmax) || (!min && d > minmax)) {\n\t\t\t\tminmax = d;\n\t\t\t\t// If strategy generation is enabled, remember optimal choice\n\t\t\t\tif (strat != null)\n\t\t\t\t\tstratCh = choice;\n\t\t\t}\n\t\t\tfirst = false;\n\t\t}\n\t\t// If strategy generation is enabled, store optimal choice\n\t\tif (strat != null && !first) {\n\t\t\t// For max, only remember strictly better choices\n\t\t\tif (min) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t} else if (strat[s] == -1 || minmax > vect[s]) {\n\t\t\t\tstrat[s] = stratCh;\n\t\t\t}\n\t\t}\n\n\t\treturn minmax;\n\t}\n\n\t/**\n\t * Do a single row of matrix-vector multiplication for a specific choice k\n\t * i.e. return min/max_P { rew(s) + rew_k(s) + sum_j P(s,k,j)*vect[j] }\n\t * @param s State (row) index\n\t * @param k Choice index\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards (MDP rewards)\n\t * @param minMax Min/max uncertainty (via isMinUnc/isMaxUnc)\n\t */\n\tpublic default double mvMultRewUncSingle(int s, int k, double vect[], MDPRewards<Double> mdpRewards, MinMax minMax)\n\t{\n\t\tdouble d = mdpRewards.getStateReward(s);\n\t\td += mdpRewards.getTransitionReward(s, k);\n\t\td += mvMultUncSingle(s, k, vect, minMax);\n\t\treturn d;\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_k min/max_P { rew(s) + rew_k(s) + sum_j P(s,k,j)*vect[j] }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param minMax Min/max info (strategy and uncertainty)\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t */\n\tpublic default double mvMultUncGS(double vect[], MinMax minMax, PrimitiveIterator.OfInt states, boolean absolute, int[] strat)\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\t//d = mvMultJacSingle(s, vect, minMax);\n\t\t\t// Just do a normal (non-Jacobi) state update - not so easy to adapt for intervals\n\t\t\td = mvMultUncSingle(s, vect, minMax, strat);\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n\n\t/**\n\t * Do a Gauss-Seidel-style matrix-vector multiplication and sum of rewards followed by min/max, i.e. one step of value iteration,\n\t * i.e. for each s: result[s] = min/max_k min/max_P { rew(s) + rew_k(s) + sum_j P(s,k,j)*vect[j] }\n\t * and store new values directly in {@code vect} as computed.\n\t * The maximum (absolute/relative) difference between old/new\n\t * elements of {@code vect} is also returned.\n\t * Optionally, store optimal (memoryless) strategy info.\n\t * @param vect Vector to multiply by\n\t * @param mdpRewards The rewards\n\t * @param minMax Min/max info (strategy and uncertainty)\n\t * @param states Perform computation for these rows, in the iteration order\n\t * @param absolute If true, compute absolute, rather than relative, difference\n\t */\n\tpublic default double mvMultRewUncGS(double vect[], MDPRewards<Double> mdpRewards, MinMax minMax, PrimitiveIterator.OfInt states, boolean absolute, int[] strat)\n\t{\n\t\tdouble d, diff, maxDiff = 0.0;\n\t\twhile (states.hasNext()) {\n\t\t\tfinal int s = states.nextInt();\n\t\t\t//d = mvMultJacSingle(s, vect, minMax);\n\t\t\t// Just do a normal (non-Jacobi) state update - not so easy to adapt for intervals\n\t\t\td = mvMultRewUncSingle(s, vect, mdpRewards, minMax, strat);\n\t\t\tdiff = absolute ? (Math.abs(d - vect[s])) : (Math.abs(d - vect[s]) / d);\n\t\t\tmaxDiff = diff > maxDiff ? diff : maxDiff;\n\t\t\tvect[s] = d;\n\t\t}\n\t\treturn maxDiff;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/UMDPModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.PrimitiveIterator;\n\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceType;\nimport common.IntSet;\nimport common.Interval;\nimport common.IterableStateSet;\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.Rewards;\nimport parser.ast.Expression;\nimport parser.type.TypeDouble;\nimport prism.AccuracyFactory;\nimport prism.Evaluator;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport strat.FMDStrategyStep;\nimport prism.PrismFileLog;\nimport strat.FMDStrategyProduct;\nimport strat.MDStrategy;\nimport strat.MDStrategyArray;\nimport strat.Strategy;\n\n/**\n * Explicit-state model checker for uncertain Markov decision prcoesses (UMDPs).\n */\npublic class UMDPModelChecker extends ProbModelChecker\n{\n\t// MDPModelChecker in order to use e.g. precomputation algorithms\n\tprotected MDPModelChecker mcMDP = null; \n\t\n\t/**\n\t * Create a new UMDPModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic UMDPModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tmcMDP = new MDPModelChecker(this);\n\t\tmcMDP.inheritSettings(this);\n\t}\n\n\t// Model checking functions\n\n\t@Override\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkProbPathFormulaLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// For min probabilities, need to negate the formula\n\t\t// (add parentheses to allow re-parsing if required)\n\t\tif (minMax.isMin()) {\n\t\t\texpr = Expression.Not(Expression.Parenth(expr.deepCopy()));\n\t\t}\n\n\t\t// Build product of UMDP and DA for the LTL formula, and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tAcceptanceType[] allowedAcceptance = {\n\t\t\t\tAcceptanceType.BUCHI,\n\t\t\t\tAcceptanceType.RABIN,\n\t\t\t\tAcceptanceType.GENERALIZED_RABIN,\n\t\t\t\tAcceptanceType.REACH\n\t\t};\n\t\tLTLModelChecker.LTLProduct<UMDP<Double>> product = mcLtl.constructDAProductForLTLFormula(this, (UMDP<Double>) model, expr, statesOfInterest, allowedAcceptance);\n\t\tdoProductExports(product);\n\n\t\t// Find accepting states + compute reachability probabilities\n\t\tBitSet acc;\n\t\tif (product.getAcceptance() instanceof AcceptanceReach) {\n\t\t\tmainLog.println(\"\\nSkipping accepting MEC computation since acceptance is defined via goal states...\");\n\t\t\tacc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\t\t} else {\n\t\t\tmainLog.println(\"\\nFinding accepting MECs...\");\n\t\t\tacc = mcLtl.findAcceptingECStates(product.getProductModel(), product.getAcceptance());\n\t\t}\n\t\tmainLog.println(\"\\nComputing reachability probabilities...\");\n\t\tUMDPModelChecker mcProduct = new UMDPModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachProbs((UMDP<Double>) product.getProductModel(), acc, minMax.isMax() ? minMax : minMax.negate());\n\t\tStateValues probsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\n\t\t// Subtract from 1 if we're model checking a negated formula for regular Pmin\n\t\tif (minMax.isMin()) {\n\t\t\tprobsProduct.applyFunction(TypeDouble.getInstance(), v -> 1.0 - (double) v);\n\t\t}\n\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\tprobsProduct.print(out, false, false, false, false);\n\t\t\tout.close();\n\t\t}\n\n\t\t// If a strategy was generated, lift it to the product and store\n\t\tif (res.strat != null) {\n\t\t\tStrategy<Double> stratProduct = new FMDStrategyProduct<>(product, (MDStrategy<Double>) res.strat);\n\t\t\tresult.setStrategy(stratProduct);\n\t\t}\n\n\t\t// Mapping probabilities in the original model\n\t\tStateValues probs = product.projectToOriginalModel(probsProduct);\n\t\tprobsProduct.clear();\n\n\t\treturn probs;\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkProbPathFormulaCosafeLTL(Model<?> model, Expression expr, boolean qual, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of UMDP and DFA for the LTL formula, and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tLTLModelChecker.LTLProduct<UMDP<Double>> product = mcLtl.constructDFAProductForCosafetyProbLTL(this, (UMDP<Double>) model, expr, statesOfInterest);\n\t\tdoProductExports(product);\n\t\t\n\t\t// Find accepting states + compute reachability probabilities\n\t\tBitSet acc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\t\tmainLog.println(\"\\nComputing reachability probabilities...\");\n\t\tUMDPModelChecker mcProduct = new UMDPModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachProbs(product.getProductModel(), acc, minMax);\n\t\tStateValues probsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\t\tprobsProduct.print(out, false, false, false, false);\n\t\t\t\tout.close();\n\t\t}\n\n\t\t// If a strategy was generated, lift it to the product and store\n\t\tif (res.strat != null) {\n\t\t\tStrategy<Double> stratProduct = new FMDStrategyProduct<>(product, (MDStrategy<Double>) res.strat);\n\t\t\tresult.setStrategy(stratProduct);\n\t\t}\n\t\t\n\t\t// Mapping probabilities in the original model\n\t\tStateValues probs = product.projectToOriginalModel(probsProduct);\n\t\tprobsProduct.clear();\n\n\t\treturn probs;\n\t}\n\t\n\t@Override\n\t@SuppressWarnings(\"unchecked\")\n\tprotected StateValues checkRewardCoSafeLTL(Model<?> model, Rewards<?> modelRewards, Expression expr, MinMax minMax, BitSet statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of UMDP and DFA for the LTL formula, convert rewards and do any required exports\n\t\tLTLModelChecker mcLtl = new LTLModelChecker(this);\n\t\tLTLModelChecker.LTLProduct<UMDP<Double>> product = mcLtl.constructDFAProductForCosafetyReward(this, (UMDP<Double>) model, expr, statesOfInterest);\n\t\tMDPRewards<Double> productRewards = ((MDPRewards<Double>) modelRewards).liftFromModel(product);\n\t\tdoProductExports(product);\n\n\t\t// Find accepting states + compute reachability rewards\n\t\tBitSet acc = ((AcceptanceReach)product.getAcceptance()).getGoalStates();\n\t\tmainLog.println(\"\\nComputing reachability rewards...\");\n\t\tUMDPModelChecker mcProduct = new UMDPModelChecker(this);\n\t\tmcProduct.inheritSettings(this);\n\t\tModelCheckerResult res = mcProduct.computeReachRewards(product.getProductModel(), productRewards, acc, minMax);\n\t\tStateValues rewardsProduct = StateValues.createFromArrayResult(res, product.getProductModel());\n\t\t\n\t\t// Output vector over product, if required\n\t\tif (getExportProductVector()) {\n\t\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + getExportProductVectorFilename() + \"\\\"...\");\n\t\t\t\tPrismFileLog out = new PrismFileLog(getExportProductVectorFilename());\n\t\t\t\trewardsProduct.print(out, false, false, false, false);\n\t\t\t\tout.close();\n\t\t}\n\n\t\t// If a strategy was generated, lift it to the product and store\n\t\tif (res.strat != null) {\n\t\t\tStrategy<Double> stratProduct = new FMDStrategyProduct<>(product, (MDStrategy<Double>) res.strat);\n\t\t\tresult.setStrategy(stratProduct);\n\t\t}\n\t\t\n\t\t// Mapping rewards in the original model\n\t\tStateValues rewards = product.projectToOriginalModel(rewardsProduct);\n\t\trewardsProduct.clear();\n\t\t\n\t\treturn rewards;\n\t}\n\t\n\t// Numerical computation functions\n\n\t/**\n\t * Compute next-state probabilities.\n\t * i.e. compute the probability of being in a state in {@code target} in the next step.\n\t * @param umdp The UMDP\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeNextProbs(UMDP<Double> umdp, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\tlong timer = System.currentTimeMillis();\n\n\t\t// Check for any zero lower probability bounds (not supported\n\t\t// since this approach assumes the graph structure remains static)\n\t\tumdp.checkLowerBoundsArePositive();\n\t\t\n\t\t// Store num states\n\t\tint n = umdp.getNumStates();\n\t\tPrimitiveIterator.OfInt statesAll = new IterableStateSet(n).iterator();\n\n\t\t// Create/initialise solution vector(s)\n\t\tdouble[] soln = Utils.bitsetToDoubleArray(target, n);\n\t\tdouble[] soln2 = new double[n];\n\n\t\t// Next-step probabilities\n\t\tumdp.mvMultUnc(soln, minMax, soln2, statesAll, null);\n\n\t\t// Return results\n\t\tModelCheckerResult res = new ModelCheckerResult();\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.soln = soln2;\n\t\tres.numIters = 1;\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tres.timeTaken = timer / 1000.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute bounded reachability probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target} within k steps.\n\t * @param umdp The UMDP\n\t * @param target Target states\n\t * @param k Bound\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeBoundedReachProbs(UMDP<Double> umdp, BitSet target, int k, MinMax minMax) throws PrismException\n\t{\n\t\treturn computeBoundedUntilProbs(umdp, null, target, k, minMax);\n\t}\n\n\t/**\n\t * Compute bounded until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * within k steps, and while remaining in states in {@code remain}.\n\t * @param umdp The UMDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param k Bound\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeBoundedUntilProbs(UMDP<Double> umdp, BitSet remain, BitSet target, int k, MinMax minMax) throws PrismException\n\t{\n\t\tModelCheckerResult res = null;\n\t\tBitSet unknown;\n\t\tint i, n, iters;\n\t\tdouble soln[], soln2[], tmpsoln[];\n\t\tlong timer;\n\t\tint strat[] = null;\n\t\tFMDStrategyStep<Double> fmdStrat = null;\n\n\t\t// Start bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting bounded probabilistic reachability...\");\n\n\t\t// Check for any zero lower probability bounds (not supported\n\t\t// since this approach assumes the graph structure remains static)\n\t\tumdp.checkLowerBoundsArePositive();\n\t\t\n\t\t// Store num states\n\t\tn = umdp.getNumStates();\n\n\t\t// Create solution vector(s)\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\n\t\t// If required, create/initialise strategy storage\n\t\t// Set choices to -1, denoting unknown\n\t\t// (except for target states, which are -2, denoting arbitrary)\n\t\tif (genStrat) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tstrat[i] = target.get(i) ? -2 : -1;\n\t\t\t}\n\t\t\tfmdStrat = new FMDStrategyStep<>(umdp, k);\n\t\t}\n\n\t\t// Initialise solution vectors.\n\t\tfor (i = 0; i < n; i++)\n\t\t\tsoln[i] = soln2[i] = target.get(i) ? 1.0 : 0.0;\n\n\t\t// Determine set of states actually need to perform computation for\n\t\tunknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tif (remain != null)\n\t\t\tunknown.and(remain);\n\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\n\t\t// Start iterations\n\t\titers = 0;\n\t\twhile (iters < k) {\n\t\t\titers++;\n\t\t\t// Matrix-vector multiply and min/max ops\n\t\t\tumdp.mvMultUnc(soln, minMax, soln2, unknownStates.iterator(), strat);\n\t\t\tif (genStrat) {\n\t\t\t\tfmdStrat.setStepChoices(k - iters, strat);\n\t\t\t}\n\t\t\t// Swap vectors for next iter\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t}\n\n\t\t// Finished bounded probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.print(\"Bounded probabilistic reachability\");\n\t\tmainLog.println(\" took \" + iters + \" iterations and \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Return results\n\t\tres = new ModelCheckerResult();\n\t\tres.soln = soln;\n\t\tres.lastSoln = soln2;\n\t\tres.accuracy = AccuracyFactory.boundedNumericalIterations();\n\t\tres.numIters = iters;\n\t\tres.timeTaken = timer / 1000.0;\n\t\tres.timePre = 0.0;\n\t\tif (genStrat) {\n\t\t\tres.strat = fmdStrat;\n\t\t}\n\t\treturn res;\n\t}\n\t\n\t/**\n\t * Compute reachability probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target}.\n\t * @param umdp The UMDP\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeReachProbs(UMDP<Double> umdp, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\treturn computeReachProbs(umdp, null, target, minMax);\n\t}\n\n\t/**\n\t * Compute until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target}.\n\t * @param umdp The UMDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeUntilProbs(UMDP<Double> umdp, BitSet remain, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\treturn computeReachProbs(umdp, remain, target, minMax);\n\t}\n\n\t/**\n\t * Compute reachability/until probabilities.\n\t * i.e. compute the probability of reaching a state in {@code target},\n\t * while remaining in those in {@code remain}.\n\t * @param umdp The UMDP\n\t * @param remain Remain in these states (optional: null means \"all\")\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeReachProbs(UMDP<Double> umdp, BitSet remain, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\tint strat[] = null;\n\t\t// Switch to a supported method, if necessary\n\t\tIMDPSolnMethod imdpSolnMethod = this.imdpSolnMethod;\n\t\tswitch (imdpSolnMethod)\n\t\t{\n\t\tcase VALUE_ITERATION:\n\t\tcase GAUSS_SEIDEL:\n\t\t\tbreak; // supported\n\t\tdefault:\n\t\t\timdpSolnMethod = IMDPSolnMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to solution method \\\"\" + imdpSolnMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\t// Start probabilistic reachability\n\t\tlong timer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting probabilistic reachability...\");\n\n\t\t// Check for any zero lower probability bounds (not supported\n\t\t// since this approach assumes the graph structure remains static)\n\t\tumdp.checkLowerBoundsArePositive();\n\t\t\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tumdp.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tint n = umdp.getNumStates();\n\n\t\t// If required, create/initialise strategy storage\n\t\t// Set choices to -1, denoting unknown\n\t\t// (except for target states, which are -2, denoting arbitrary)\n\t\tif (genStrat) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tstrat[i] = target.get(i) ? -2 : -1;\n\t\t\t}\n\t\t}\n\n\t\t// Precomputation\n\t\tBitSet no, yes;\n\t\tif (precomp && prob0) {\n\t\t\tno = mcMDP.prob0(umdp, remain, target, minMax.isMin(), strat);\n\t\t} else {\n\t\t\tno = new BitSet();\n\t\t\tif (remain != null) {\n\t\t\t\tno.or(remain);\n\t\t\t\tno.or(target);\n\t\t\t\tno.flip(0, n);\n\t\t\t}\n\t\t}\n\t\tif (precomp && prob1) {\n\t\t\tyes = mcMDP.prob1(umdp, remain, target, minMax.isMin(), strat);\n\t\t} else {\n\t\t\tyes = (BitSet) target.clone();\n\t\t}\n\n\t\t// Print results of precomputation\n\t\tint numYes = yes.cardinality();\n\t\tint numNo = no.cardinality();\n\t\tmainLog.println(\"target=\" + target.cardinality() + \", yes=\" + numYes + \", no=\" + numNo + \", maybe=\" + (n - (numYes + numNo)));\n\n\t\t// If still required, store strategy for no/yes (0/1) states.\n\t\t// This is just for the cases max=0 and min=1, where arbitrary choices suffice (denoted by -2)\n\t\tif (genStrat) {\n\t\t\tif (minMax.isMin()) {\n\t\t\t\tfor (int i = yes.nextSetBit(0); i >= 0; i = yes.nextSetBit(i + 1)) {\n\t\t\t\t\tif (!target.get(i))\n\t\t\t\t\t\tstrat[i] = -2;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tfor (int i = no.nextSetBit(0); i >= 0; i = no.nextSetBit(i + 1)) {\n\t\t\t\t\tstrat[i] = -2;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString sMinMax = minMax.isMin() ? \"min\" : \"max\";\n\t\tsMinMax += minMax.isMinUnc() ? \"min\" : \"max\";\n\t\tmainLog.println(\"Starting value iteration (\" + sMinMax + \")...\");\n\n\t\t// Store num states\n\t\tn = umdp.getNumStates();\n\n\t\t// Initialise solution vectors\n\t\tdouble[] init = new double[n];\n\t\tfor (int i = 0; i < n; i++)\n\t\t\tinit[i] = yes.get(i) ? 1.0 : no.get(i) ? 0.0 : 0.0;\n\n\t\t// Determine set of states actually need to compute values for\n\t\tBitSet unknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(yes);\n\t\tunknown.andNot(no);\n\n\t\t// Compute probabilities (if needed)\n\t\tModelCheckerResult res;\n\t\tif (numYes + numNo < n) {\n\t\t\tIterationMethod iterationMethod = null;\n\t\t\tswitch (imdpSolnMethod) {\n\t\t\tcase VALUE_ITERATION:\n\t\t\t\titerationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\t\t\tbreak;\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\t\titerationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, false);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown solution method \" + imdpSolnMethod.fullName());\n\t\t\t}\n\t\t\tIterationMethod.IterationValIter iterationReachProbs = iterationMethod.forMvMultMinMaxUnc(umdp, minMax, strat);\n\t\t\titerationReachProbs.init(init);\n\t\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\t\t\tString description = sMinMax + \", with \" + iterationMethod.getDescriptionShort();\n\t\t\tres = iterationMethod.doValueIteration(this, description, iterationReachProbs, unknownStates, timer, null);\n\t\t} else {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(yes, n);\n\t\t\tres.accuracy = AccuracyFactory.doublesFromQualitative();\n\t\t}\n\t\t\n\t\t// Store strategy\n\t\tif (genStrat) {\n\t\t\tres.strat = new MDStrategyArray<>(umdp, strat);\n\t\t}\n\t\t\n\t\t// Finished probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Probabilistic reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Compute expected reachability rewards.\n\t * i.e. compute the min/max reward accumulated to reach a state in {@code target}.\n\t * @param umdp The UMDP\n\t * @param umdpRewards The rewards\n\t * @param target Target states\n\t * @param minMax Min/max info\n\t */\n\tpublic ModelCheckerResult computeReachRewards(UMDP<Double> umdp, MDPRewards<Double> umdpRewards, BitSet target, MinMax minMax) throws PrismException\n\t{\n\t\tint strat[] = null;\n\t\t// Switch to a supported method, if necessary\n\t\tIMDPSolnMethod imdpSolnMethod = this.imdpSolnMethod;\n\t\tswitch (imdpSolnMethod)\n\t\t{\n\t\tcase VALUE_ITERATION:\n\t\tcase GAUSS_SEIDEL:\n\t\t\tbreak; // supported\n\t\tdefault:\n\t\t\timdpSolnMethod = IMDPSolnMethod.GAUSS_SEIDEL;\n\t\t\tmainLog.printWarning(\"Switching to solution method \\\"\" + imdpSolnMethod.fullName() + \"\\\"\");\n\t\t}\n\n\t\t// Start probabilistic reachability\n\t\tlong timer = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nStarting expected reachability...\");\n\n\t\t// Check for any zero lower probability bounds (not supported\n\t\t// since this approach assumes the graph structure remains static)\n\t\tumdp.checkLowerBoundsArePositive();\n\t\t\n\t\t// Check for deadlocks in non-target state (because breaks e.g. prob1)\n\t\tumdp.checkForDeadlocks(target);\n\n\t\t// Store num states\n\t\tint n = umdp.getNumStates();\n\n\t\t// If required, create/initialise strategy storage\n\t\t// Set choices to -1, denoting unknown\n\t\t// (except for target states, which are -2, denoting arbitrary)\n\t\tif (genStrat) {\n\t\t\tstrat = new int[n];\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tstrat[i] = target.get(i) ? -2 : -1;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Precomputation (not optional)\n\t\tBitSet inf = mcMDP.prob1(umdp, null, target, !minMax.isMin(), strat);\n\t\tinf.flip(0, n);\n\n\t\t// Print results of precomputation\n\t\tint numTarget = target.cardinality();\n\t\tint numInf = inf.cardinality();\n\t\tmainLog.println(\"target=\" + numTarget + \", inf=\" + numInf + \", rest=\" + (n - (numTarget + numInf)));\n\n\t\t// If required, generate strategy for \"inf\" states.\n\t\tif (genStrat) {\n\t\t\tif (minMax.isMin()) {\n\t\t\t\t// If min reward is infinite, all choices give infinity\n\t\t\t\t// So the choice can be arbitrary, denoted by -2; \n\t\t\t\tfor (int i = inf.nextSetBit(0); i >= 0; i = inf.nextSetBit(i + 1)) {\n\t\t\t\t\tstrat[i] = -2;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\t// If max reward is infinite, there is at least one choice giving infinity.\n\t\t\t\t// So we pick, for all \"inf\" states, the first choice for which some transitions stays in \"inf\".\n\t\t\t\tfor (int i = inf.nextSetBit(0); i >= 0; i = inf.nextSetBit(i + 1)) {\n\t\t\t\t\tint numChoices = umdp.getNumChoices(i);\n\t\t\t\t\tfor (int k = 0; k < numChoices; k++) {\n\t\t\t\t\t\tif (umdp.someSuccessorsInSet(i, k, inf)) {\n\t\t\t\t\t\t\tstrat[i] = k;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Start value iteration\n\t\ttimer = System.currentTimeMillis();\n\t\tString sMinMax = minMax.isMin() ? \"min\" : \"max\";\n\t\tsMinMax += minMax.isMinUnc() ? \"min\" : \"max\";\n\t\tmainLog.println(\"Starting value iteration (\" + sMinMax + \")...\");\n\n\t\t// Store num states\n\t\tn = umdp.getNumStates();\n\n\t\t// Initialise solution vectors\n\t\tdouble[] init = new double[n];\n\t\tfor (int i = 0; i < n; i++)\n\t\t\tinit[i] = target.get(i) ? 0.0 : inf.get(i) ? Double.POSITIVE_INFINITY : 0.0;\n\n\t\t// Determine set of states actually need to compute values for\n\t\tBitSet unknown = new BitSet();\n\t\tunknown.set(0, n);\n\t\tunknown.andNot(target);\n\t\tunknown.andNot(inf);\n\n\t\t// Compute probabilities (if needed)\n\t\tModelCheckerResult res;\n\t\tif (numTarget + numInf < n) {\n\t\t\tIterationMethod iterationMethod = null;\n\t\t\tswitch (imdpSolnMethod) {\n\t\t\tcase VALUE_ITERATION:\n\t\t\t\titerationMethod = new IterationMethodPower(termCrit == TermCrit.ABSOLUTE, termCritParam);\n\t\t\t\tbreak;\n\t\t\tcase GAUSS_SEIDEL:\n\t\t\t\titerationMethod = new IterationMethodGS(termCrit == TermCrit.ABSOLUTE, termCritParam, false);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown solution method \" + imdpSolnMethod.fullName());\n\t\t\t}\n\t\t\tIterationMethod.IterationValIter iterationReachProbs = iterationMethod.forMvMultRewMinMaxUnc(umdp, umdpRewards, minMax, strat);\n\t\t\titerationReachProbs.init(init);\n\t\t\tIntSet unknownStates = IntSet.asIntSet(unknown);\n\t\t\tString description = sMinMax + \", with \" + iterationMethod.getDescriptionShort();\n\t\t\tres = iterationMethod.doValueIteration(this, description, iterationReachProbs, unknownStates, timer, null);\n\t\t} else {\n\t\t\tres = new ModelCheckerResult();\n\t\t\tres.soln = Utils.bitsetToDoubleArray(inf, n, Double.POSITIVE_INFINITY);\n\t\t\tres.accuracy = AccuracyFactory.doublesFromQualitative();\n\t\t}\n\t\t\n\t\t// Store strategy\n\t\tif (genStrat) {\n\t\t\tres.strat = new MDStrategyArray<>(umdp, strat);\n\t\t}\n\t\t\n\t\t// Finished probabilistic reachability\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Probabilistic reachability took \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Update time taken\n\t\tres.timeTaken = timer / 1000.0;\n\n\t\treturn res;\n\t}\n\t\n\t/**\n\t * Simple test program.\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\ttry {\n\t\t\tUMDPModelChecker mc = new UMDPModelChecker(null);\n\t\t\tEvaluator<Interval<Double>> eval = Evaluator.forDoubleInterval();\n\t\t\tIMDPSimple<Double> imdp = new IMDPSimple<>();\n\t\t\timdp.setIntervalEvaluator(eval);\n\t\t\timdp.addState();\n\t\t\timdp.addState();\n\t\t\timdp.addState();\n\t\t\timdp.addInitialState(0);\n\t\t\tDistribution<Interval<Double>> distr;\n\t\t\tdistr = new Distribution<>(eval);\n\t\t\tdistr.add(1, new Interval<Double>(0.2, 0.4));\n\t\t\tdistr.add(2, new Interval<Double>(0.6, 0.8));\n\t\t\timdp.addActionLabelledChoice(0, distr, \"a\");\n\t\t\tdistr = new Distribution<>(eval);\n\t\t\tdistr.add(1, new Interval<Double>(0.1, 0.3));\n\t\t\tdistr.add(2, new Interval<Double>(0.7, 0.9));\n\t\t\timdp.addActionLabelledChoice(0, distr, \"b\");\n\t\t\timdp.findDeadlocks(true);\n\t\t\timdp.exportToDotFile(\"imdp.dot\");\n\t\t\tBitSet target = new BitSet();\n\t\t\ttarget.set(2);\n\t\t\tModelCheckerResult res;\n\t\t\tres = mc.computeReachProbs(imdp, target, MinMax.min().setMinUnc(true));\n\t\t\tSystem.out.println(\"minmin: \" + res.soln[0]);\n\t\t\tres = mc.computeReachProbs(imdp, target, MinMax.min().setMinUnc(false));\n\t\t\tSystem.out.println(\"minmax: \" + res.soln[0]);\n\t\t\tres = mc.computeReachProbs(imdp, target, MinMax.max().setMinUnc(true));\n\t\t\tSystem.out.println(\"maxmin: \" + res.soln[0]);\n\t\t\tres = mc.computeReachProbs(imdp, target, MinMax.max().setMinUnc(false));\n\t\t\tSystem.out.println(\"maxmax: \" + res.soln[0]);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/UPOMDP.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit;\n\nimport prism.ModelType;\nimport prism.PrismException;\n\n/**\n * Interface for classes that provide (read) access to an explicit-state uncertain POMDP.\n */\npublic interface UPOMDP<Value> extends NondetModel<Value>, PartiallyObservableModel<Value>\n{\n    // Accessors (for Model) - default implementations\n\n    @Override\n    public default ModelType getModelType()\n    {\n        return ModelType.UPOMDP;\n    }\n\n    @Override\n    default void exportToPrismLanguage(final String filename, int precision) throws PrismException\n    {\n        throw new UnsupportedOperationException(\"UPOMDP model export not implemented\");\n    }\n\n    // Accessors\n\n    /**\n     * Checks that transition probability lower bounds are positive\n     * and throws an exception if any are not.\n     */\n    public default void checkLowerBoundsArePositive() throws PrismException\n    {\n        throw new UnsupportedOperationException();\n    }\n}\n"
  },
  {
    "path": "prism/src/explicit/Utils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.BitSet;\nimport java.util.PrimitiveIterator;\n\npublic class Utils\n{\n\t/**\n\t * Compute the minimum or maximum value over a subset of an array of doubles.\n\t * @param array The array\n\t * @param subset The subset\n\t * @param min Min or max (true = min, false = max) \n\t */\n\tpublic static double minMaxOverArraySubset(double[] array, Iterable<Integer> subset, boolean min)\n\t{\n\t\tif (min)\n\t\t\treturn minOverArraySubset(array, subset);\n\t\telse\n\t\t\treturn maxOverArraySubset(array, subset);\n\t}\n\n\t/**\n\t * Compute the minimum value over a subset of an array of doubles.\n\t * @param array The array\n\t * @param subset The subset\n\t */\n\tpublic static double minOverArraySubset(double[] array, Iterable<Integer> subset)\n\t{\n\t\tdouble d;\n\t\td = Double.POSITIVE_INFINITY;\n\t\tfor (int j : subset) {\n\t\t\tif (array[j] < d)\n\t\t\t\td = array[j];\n\t\t}\n\t\treturn d;\n\t}\n\n\t/**\n\t * Compute the maximum value over a subset of an array of doubles.\n\t * @param array The array\n\t * @param subset The subset\n\t */\n\tpublic static double maxOverArraySubset(double[] array, Iterable<Integer> subset)\n\t{\n\t\tdouble d;\n\t\td = Double.NEGATIVE_INFINITY;\n\t\tfor (int j : subset) {\n\t\t\tif (array[j] > d)\n\t\t\t\td = array[j];\n\t\t}\n\t\treturn d;\n\t}\n\n\t/**\n\t * Create an n-element array of doubles (0s and 1s) from a BitSet.\n\t *  @param bs The bitset specifying 0s and 1s\n\t *  @param n The size of the array.\n\t */\n\tpublic static double[] bitsetToDoubleArray(BitSet bs, int n)\n\t{\n\t\treturn bitsetToDoubleArray(bs, n, 1.0);\n\t}\n\n\t/**\n\t * Create an n-element array of doubles from a BitSet,\n\t * setting elements whose index is set in the BitSet to {@code val}, and otherwise 0.0.\n\t *  @param bs The bitset specifying set elements\n\t *  @param n The size of the array.\n\t *  @param val The value for \"set\" elements\n\t */\n\tpublic static double[] bitsetToDoubleArray(BitSet bs, int n, double val)\n\t{\n\t\tint i;\n\t\tdouble res[] = new double[n];\n\t\tfor (i = 0; i < n; i++)\n\t\t\tres[i] = bs.get(i) ? val : 0.0;\n\t\treturn res;\n\t}\n\n\t/**\n\t * Extend a double array to be at least as big as requested size.\n\t * @param array The array to be resized\n\t * @param nOld The size of the old array (not necessarily array.length)\n\t * @param nNew The desired new size\n\t * @param valNew Value to initialise new elements with\n\t * @return The new array\n\t */\n\tpublic static double[] extendDoubleArray(double array[], int nOld, int nNew, double valNew)\n\t{\n\t\tint i, n, n2;\n\t\tdouble[] arrayNew;\n\t\t// Do nothing for null pointers\n\t\tif (array == null)\n\t\t\treturn null;\n\t\t// If array already long enough, just return \n\t\tn = array.length;\n\t\tif (n > nNew)\n\t\t\treturn array;\n\t\t// Create new array (of size nNew + some spare)\n\t\tn2 = nNew + 100;\n\t\tarrayNew = new double[n2];\n\t\t// Copy across old values\n\t\tfor (i = 0; i < nOld; i++) {\n\t\t\tarrayNew[i] = array[i];\n\t\t}\n\t\t// Initialise new values\n\t\tfor (i = nOld; i < nNew; i++) {\n\t\t\tarrayNew[i] = valNew;\n\t\t}\n\t\treturn arrayNew;\n\t}\n\n\t/**\n\t * Clone a double array.\n\t * @param array The array to be cloned\n\t * @return The new array\n\t */\n\tpublic static double[] cloneDoubleArray(double array[])\n\t{\n\t\tint i, n;\n\t\tdouble[] arrayNew;\n\t\t// Do nothing for null pointers\n\t\tif (array == null)\n\t\t\treturn null;\n\t\t// Otherwise copy and return\n\t\tn = array.length;\n\t\tarrayNew = new double[n];\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tarrayNew[i] = array[i];\n\t\t}\n\t\treturn arrayNew;\n\t}\n\n\t/**\n\t * Clone an integer array.\n\t * @param array The array to be cloned\n\t * @return The new array\n\t */\n\tpublic static int[] cloneIntArray(int array[])\n\t{\n\t\tint i, n;\n\t\tint[] arrayNew;\n\t\t// Do nothing for null pointers\n\t\tif (array == null)\n\t\t\treturn null;\n\t\t// Otherwise copy and return\n\t\tn = array.length;\n\t\tarrayNew = new int[n];\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tarrayNew[i] = array[i];\n\t\t}\n\t\treturn arrayNew;\n\t}\n\n\t/**\n\t * Copy a double array.\n\t * @param array The array to be cloned\n\t * @param copy The destination array (should exist and be same size)\n\t */\n\tpublic static void copyDoubleArray(double array[], double copyTo[])\n\t{\n\t\tint i, n;\n\t\t// Do nothing for null pointers\n\t\tif (array == null)\n\t\t\treturn;\n\t\t// Otherwise copy\n\t\tn = array.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tcopyTo[i] = array[i];\n\t\t}\n\t}\n\n\t/**\n\t * Copy an integer array.\n\t * @param array The array to be cloned\n\t * @param copy The destination array (should exist and be same size)\n\t */\n\tpublic static void copyIntArray(int array[], int copyTo[])\n\t{\n\t\tint i, n;\n\t\t// Do nothing for null pointers\n\t\tif (array == null)\n\t\t\treturn;\n\t\t// Otherwise copy\n\t\tn = array.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tcopyTo[i] = array[i];\n\t\t}\n\t}\n\n\t/**\n\t * Test if two double arrays are equal.\n\t */\n\tpublic static boolean doubleArraysAreEqual(double array1[], double array2[])\n\t{\n\t\tint i, n;\n\t\tif (array1 == null)\n\t\t\treturn (array2 == null);\n\t\tn = array1.length;\n\t\tif (n != array2.length)\n\t\t\treturn false;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (array1[i] != array2[i])\n\t\t\t\treturn false;\n\t\t\t;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Test if two int arrays are equal.\n\t */\n\tpublic static boolean intArraysAreEqual(int array1[], int array2[])\n\t{\n\t\tint i, n;\n\t\tif (array1 == null)\n\t\t\treturn (array2 == null);\n\t\tn = array1.length;\n\t\tif (n != array2.length)\n\t\t\treturn false;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (array1[i] != array2[i])\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Returns true if int array 'array' contains value 'val'.\n\t */\n\tpublic static boolean intArrayContains(int val, int[] array)\n\t{\n\t\tfor (int i = 0; i < array.length; i++)\n\t\t\tif (val == array[i])\n\t\t\t\treturn true;\n\t\treturn false;\n\t}\n\n\t/**\n\t * Create an (int) iterator that returns {@code n} copies of {@code i}.\n\t * Like {@code Collections.nCopies(n, i).iterator()} but for ints.\n\t */\n\tpublic static PrimitiveIterator.OfInt nCopiesIntIterator(int n, int i)\n\t{\n\t\treturn new PrimitiveIterator.OfInt()\n\t\t{\n\t\t\tprivate int count = 0;\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\tcount++;\n\t\t\t\treturn i;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn count < n;\n\t\t\t}\n\t\t};\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/ZeroRewardECQuotient.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit;\n\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.List;\n\nimport common.functions.PairPredicateInt;\nimport common.IterableBitSet;\nimport explicit.graphviz.Decorator;\nimport explicit.graphviz.ShowRewardDecorator;\nimport explicit.modelviews.EquivalenceRelationInteger;\nimport explicit.modelviews.MDPDroppedChoicesCached;\nimport explicit.modelviews.MDPEquiv;\nimport explicit.modelviews.StateChoicePair;\nimport explicit.rewards.MDPRewards;\nimport prism.PrismComponent;\nimport prism.PrismException;\n\n/**\n * Helper class for obtaining the zero-reward EC quotient of an MDP.\n * <br>\n * In the original MDP, the zero-reward maximal end components are identified, i.e.,\n * those end components where there is a strategy to stay infinitely without ever\n * seeing another reward.\n * <br>\n * In the quotient, those zero-reward MECs are each collapsed to a single state,\n * with choices that have transitions outside the MEC preserved.\n */\npublic class ZeroRewardECQuotient<Value>\n{\n\tprivate MDPEquiv<Value> quotient;\n\tprivate MDPRewards<Value> quotientRewards;\n\tprivate int numberOfZMECs;\n\n\tprivate static final boolean debug = false;\n\n\tprivate ZeroRewardECQuotient(MDPEquiv<Value> quotient, MDPRewards<Value> quotientRewards, int numberOfZMECs)\n\t{\n\t\tthis.quotient = quotient;\n\t\tthis.quotientRewards = quotientRewards;\n\t\tthis.numberOfZMECs = numberOfZMECs;\n\t}\n\n\tpublic MDP<Value> getModel()\n\t{\n\t\treturn quotient;\n\t}\n\n\tpublic MDPRewards<Value> getRewards()\n\t{\n\t\treturn quotientRewards;\n\t}\n\n\tpublic int getNumberOfZeroRewardMECs()\n\t{\n\t\treturn numberOfZMECs;\n\t}\n\n\tpublic BitSet getNonRepresentativeStates()\n\t{\n\t\treturn quotient.getNonRepresentativeStates();\n\t}\n\n\tpublic void mapResults(double[] soln) {\n\t\tfor (int s : new IterableBitSet(quotient.getNonRepresentativeStates())) {\n\t\t\tint representative = quotient.mapStateToRestrictedModel(s);\n\t\t\tsoln[s] = soln[representative];\n\t\t}\n\t}\n\n\tpublic static <Value> ZeroRewardECQuotient<Value> getQuotient(PrismComponent parent, MDP<Value> mdp, BitSet restrict, MDPRewards<Value> rewards) throws PrismException\n\t{\n\t\tPairPredicateInt positiveRewardChoice = (int s, int i) -> {\n\t\t\tif (mdp.getEvaluator().gt(rewards.getStateReward(s), mdp.getEvaluator().zero())) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t\tif (mdp.getEvaluator().gt(rewards.getTransitionReward(s, i), mdp.getEvaluator().zero())) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t\treturn false;\n\t\t};\n\n\t\t// drop positive reward choices\n\t\tMDPDroppedChoicesCached<Value> zeroRewMDP = new MDPDroppedChoicesCached<>(mdp, positiveRewardChoice);\n\t\t// compute the MECs in the zero-reward sub-MDP\n\t\tECComputer ecComputer = ECComputerDefault.createECComputer(parent, zeroRewMDP);\n\t\tecComputer.computeMECStates(restrict);\n\n\t\tList<BitSet> mecs = ecComputer.getMECStates();\n\n\t\tif (mecs.isEmpty()) {\n\t\t\treturn null;\n\t\t}\n\n\t\t// the equivalence relation on the states\n\t\tEquivalenceRelationInteger equiv = new EquivalenceRelationInteger(mecs);\n\n\t\t// we drop zero reward loops on the equivalence classes\n\t\tPairPredicateInt zeroRewardECloop = (int s, int i) -> {\n\t\t\tif (positiveRewardChoice.test(s, i)) {\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\t// return true if all successors t of state s for choice i are in the\n\t\t\t// same equivalence class\n\t\t\tboolean rv = mdp.allSuccessorsMatch(s, i, (int t) -> equiv.test(s,t));\n\t\t\treturn rv;\n\t\t};\n\n\t\tfinal MDPDroppedChoicesCached<Value> droppedZeroRewardLoops = new MDPDroppedChoicesCached<>(mdp, zeroRewardECloop);\n\t\tif (debug)\n\t\t\tdroppedZeroRewardLoops.exportToDotFile(\"zero-mec-loops-dropped.dot\");\n\n\t\tBasicModelTransformation<MDP<Value>, MDPEquiv<Value>> transform = MDPEquiv.transform(droppedZeroRewardLoops, equiv);\n\t\tfinal MDPEquiv<Value> quotient = transform.getTransformedModel();\n\n\t\tMDPRewards<Value> quotientRewards = new MDPRewards<Value>() {\n\t\t\t@Override\n\t\t\tpublic Value getStateReward(int s)\n\t\t\t{\n\t\t\t\treturn rewards.getStateReward(s);\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Value getTransitionReward(int s, int i)\n\t\t\t{\n\t\t\t\tStateChoicePair mapped = quotient.mapToOriginalModel(s, i);\n\t\t\t\tint mappedChoiceInOriginal = droppedZeroRewardLoops.mapChoiceToOriginalModel(mapped.getState(), mapped.getChoice());\n\t\t\t\treturn rewards.getTransitionReward(mapped.getState(), mappedChoiceInOriginal);\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic MDPRewards<Value> liftFromModel(Product<?> product)\n\t\t\t{\n\t\t\t\tthrow new RuntimeException(\"Not implemented\");\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic boolean hasTransitionRewards()\n\t\t\t{\n\t\t\t\treturn rewards.hasTransitionRewards();\n\t\t\t}\n\t\t};\n\n\t\tif (debug) {\n\t\t\tList<Decorator> decorators = Arrays.asList(new ShowRewardDecorator<>(quotientRewards));\n\t\t\tquotient.exportToDotFile(\"zero-mec-quotient.dot\", decorators);\n\t\t}\n\n\t\treturn new ZeroRewardECQuotient<>(quotient, quotientRewards, mecs.size());\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/graphviz/Decoration.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.graphviz;\n\nimport java.util.Collections;\nimport java.util.Map;\nimport java.util.Map.Entry;\nimport java.util.TreeMap;\n\n/**\n * A Decoration stores the attributes (label and style information)\n * that can be attached to a GraphViz node or edge.\n */\npublic class Decoration\n{\n\t/** An indication of how the node or edge's label should be rendered by Graphviz */\n\tpublic static enum LabelType\n\t{\n\t\t/**\n\t\t * Plain text\n\t\t * */\n\t\tPLAIN(\"\\\"\", \"\\\"\", \"\\\\n\"),\n\n\t\t/**\n\t\t * HTML-like (a restricted subset of HTML supported by Graphviz, as documented in the\n\t\t * <a href=\"https://graphviz.gitlab.io/_pages/doc/info/shapes.html#html\">Node Shapes</a>\n\t\t * section of the Graphviz manual)\n\t\t */\n\t\t HTML(\"<\", \">\", \"<br/>\");\n\n\t\t/** The symbol to start the label text (for this label type) */\n\t\tprivate final String labelOpen;\n\t\t/** The symbol to end the label text (for this label type) */\n\t\tprivate final String labelClose;\n\t\t/** The symbol for creating a new line (for this label type) */\n\t\tprivate final String newLine;\n\n\t\t/** Constructor, set the correct delimiter symbols */\n\t\tprivate LabelType(String labelOpen, String labelClose, String newLine)\n\t\t{\n\t\t\t this.labelOpen = labelOpen;\n\t\t\t this.labelClose = labelClose;\n\t\t\t this.newLine = newLine;\n\t\t }\n\n\t\t/** Returns the symbol for starting the label text */\n\t\tpublic String getOpen()\n\t\t{\n\t\t\treturn labelOpen;\n\t\t}\n\n\t\t/** Returns the symbol for ending the label text */\n\t\tpublic String getClose()\n\t\t{\n\t\t\treturn labelClose;\n\t\t}\n\n\t\t/** Returns the symbol for creating a new line in the label text */\n\t\tpublic String getNewLine()\n\t\t{\n\t\t\treturn newLine;\n\t\t}\n\t}\n\n\t/** The label */\n\tprivate String label;\n\t/** How the label should be rendered by Graphviz (by plain text, as default) */\n\tprivate LabelType labelType = LabelType.PLAIN;\n\t/** Map from attribute keys to values (apart from the label attribute) */\n\tprivate TreeMap<String, String> attributes;\n\n\t/** A Decoration that provides default attributes, e.g., node shape */\n\tprivate Decoration defaults;\n\n\t/** Constructor, no defaults */\n\tpublic Decoration()\n\t{\n\t\tthis.defaults = null;\n\t\tthis.label = \"\";\n\t}\n\n\t/** Constructor, with defaults decoration */\n\tpublic Decoration(Decoration defaults)\n\t{\n\t\tthis.defaults = defaults;\n\t}\n\n\t/**\n\t * Returns a map for accessing attributes (apart from the label attribute)\n\t */\n\tpublic Map<String, String> attributes()\n\t{\n\t\tif (attributes == null) {\n\t\t\t// If there have been no attributes before, initialise empty map\n\t\t\tattributes = new TreeMap<String, String>();\n\t\t}\n\t\treturn attributes;\n\t}\n\n\t/**\n\t * Returns a read-only map for accessing attributes (apart from the label attribute).\n\t * <br>\n\t * Note: If you only need read access, it might be more efficient to use this\n\t * method instead of {@code attributes()}.\n\t */\n\tpublic Map<String, String> attributesRO()\n\t{\n\t\tif (attributes == null) {\n\t\t\t// If there have been no attributes before, return empty map\n\t\t\treturn Collections.emptyMap();\n\t\t} else {\n\t\t\treturn Collections.unmodifiableMap(attributes);\n\t\t}\n\t}\n\n\t/**\n\t * Get the effective value for the given key.\n\t * <br>\n\t * If the key equals \"label\", returns the label.\n\t * Otherwise, if there is an attribute with the given key,\n\t * return its value. If there is none, try the defaults\n\t * decoration.\n\t * @param key the attribute key\n\t * @return the value, if there is one ({@code null} otherwise)\n\t */\n\tpublic String getEffectiveValue(String key)\n\t{\n\t\tif (key.equals(\"label\")) {\n\t\t\treturn label;\n\t\t}\n\n\t\tString value = attributesRO().get(key);\n\t\tif (value == null && defaults != null) {\n\t\t\treturn defaults.getEffectiveValue(key);\n\t\t}\n\t\treturn value;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuffer buf = new StringBuffer();\n\n\t\tappend(buf, \"label\", labelType.getOpen() + label + labelType.getClose());\n\n\t\tfor (Entry<String, String> e : attributesRO().entrySet()) {\n\t\t\tif (defaults != null) {\n\t\t\t\tString defaultValue = defaults.getEffectiveValue(e.getKey());\n\t\t\t\tif (defaultValue != null && defaultValue.equals(e.getValue())) {\n\t\t\t\t\t// skip, as it's the default value and we don't want to pollute the output\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tString value = e.getValue();\n\t\t\tvalue = \"\\\"\" + value + \"\\\"\";\n\t\t\tappend(buf, e.getKey(), value);\n\t\t}\n\n\t\tif (buf.length() == 0) {\n\t\t\treturn \"\";\n\t\t} else {\n\t\t\treturn \"[\" + buf.toString() + \"]\";\n\t\t}\n\t}\n\n\t/** Append the given key/value pair to the StringBuffer, with a ',' if necessary */\n\tprotected void append(StringBuffer buffer, String key, String value)\n\t{\n\t\tif (buffer.length() != 0) {\n\t\t\tbuffer.append(\",\");\n\t\t}\n\t\tbuffer.append(key);\n\t\tbuffer.append(\"=\");\n\t\tbuffer.append(value);\n\t}\n\n\t/** Get the label text */\n\tpublic String getLabel()\n\t{\n\t\treturn label;\n\t}\n\n\t/** Set the label text. Note: Ensure that the label text is properly quoted for the used label type. */\n\tpublic void setLabel(String label)\n\t{\n\t\tthis.label = label;\n\t}\n\n\t/** Get the label type */\n\tpublic LabelType getLabelType()\n\t{\n\t\treturn labelType;\n\t}\n\n\t/**\n\t * Set the label type (this should be done before calling the {@link labelAddBelow(String) labelAddBelow}\n\t * or {@link labelAddAbove(String) labelAddAbove} methods, to ensure that the correct line delimiter is\n\t * inserted)\n\t */\n\tpublic void setLabelType(LabelType labelType)\n\t{\n\t\tthis.labelType = labelType;\n\t}\n\n\t/**\n\t * Add some additional information below the currently existing label.\n\t * Note: Ensure that the label text is properly quoted for the used label type.\n\t */\n\tpublic void labelAddBelow(String additional)\n\t{\n\t\tsetLabel(getLabel() + labelType.getNewLine() + additional);\n\t}\n\n\t/**\n\t * Add some additional information above the currently existing label.\n\t * Note: Ensure that the label text is properly quoted for the used label type.\n\t * @param additional the additional text\n\t */\n\tpublic void labelAddAbove(String additional)\n\t{\n\t\tsetLabel(additional + labelType.getNewLine() + getLabel());\n\t}\n\n\t/**\n\t * Add some additional information to the right of the currently existing label.\n\t * Note: Ensure that the label text is properly quoted for the used label type.\n\t * @param additional the additional text\n\t * @param separator the separator between the old label and the additional text (may be {@code null})\n\t */\n\tpublic void labelAddRight(String additional, String separator)\n\t{\n\t\tsetLabel(getLabel() + (separator == null ? \" \" : separator) + additional);\n\t}\n\n\t/**\n\t * Add some additional information to the left of the currently existing label.\n\t * Note: Ensure that the label text is properly quoted for the used label type.\n\t * @param additional the additional text\n\t * @param separator the separator between the old label and the additional text (may be {@code null})\n\t */\n\tpublic void labelAddLeft(String additional, String separator)\n\t{\n\t\tsetLabel(additional + (separator == null ? \" \" : separator) + getLabel());\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/graphviz/Decorator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.graphviz;\n\nimport java.util.BitSet;\n\n/**\n * A Decorator is called from the DOT output routines and\n * can modify the decoration that is attached at the\n * given node or edge in the GraphViz file.\n * <br>\n * Default implementations are provided that simply pass\n * through the decoration given as input, without any modification.\n */\npublic interface Decorator\n{\n\t/**\n\t * Called to allow modification of the decoration\n\t * attached to a state.\n\t * @param state the state index in the model\n\t * @param d the current decoration\n\t * @return an updated decoration (may return {@code d} and modify it)\n\t */\n\tdefault Decoration decorateState(int state, Decoration d)\n\t{\n\t\treturn d;\n\t}\n\n\t/**\n\t * Called to allow modification of the decoration\n\t * attached to non-deterministic transition choice.\n\t * @param from the state index in the model of the originating state\n\t * @param choice the choice index\n\t * @param d the current decoration\n\t * @return an updated decoration (may return {@code d} and modify it)\n\t */\n\tdefault Decoration decorateTransition(int from, int choice, Decoration d)\n\t{\n\t\treturn d;\n\t}\n\n\t/**\n\t * Called to allow modification of the decoration\n\t * attached to a probabilistic transition for a non-deterministic choice.\n\t * @param from the state index in the model of the originating state\n\t * @param to the state index in the model of the target state\n\t * @param choice the choice index\n\t * @param probability the probability (e.g., a Double, param.BigRational, param.Function)\n\t * @param d the current decoration\n\t * @return an updated decoration (may return {@code d} and modify it)\n\t */\n\tdefault Decoration decorateProbability(int from, int to, int choice, Object probability, Decoration d)\n\t{\n\t\treturn d;\n\t}\n\n\t/**\n\t * Called to allow modification of the decoration\n\t * attached to a probabilistic transition in a model without non-deterministic choices (e.g., DTMC, CTMC).\n\t * @param from the state index in the model of the originating state\n\t * @param to the state index in the model of the target state\n\t * @param probability the probability (e.g., a Double, param.BigRational, param.Function)\n\t * @param d the current decoration\n\t * @return an updated decoration (may return {@code d} and modify it)\n\t */\n\tdefault Decoration decorateProbability(int from, int to, Object probability, Decoration d)\n\t{\n\t\treturn d;\n\t}\n\n\t/**\n\t * Called to allow modification of the decoration\n\t * attached to an automaton edge.\n\t * @param from the state index in the automaton of the originating state\n\t * @param to the state index in the automaton of the target state\n\t * @param apElement a BitSet representing the current element of the alphabet (2^AP)\n\t * @param d the current decoration\n\t * @return an updated decoration (may return {@code d} and modify it)\n\t */\n\tdefault Decoration decorateAutomatonEdge(int from, int to, BitSet apElement, Decoration d)\n\t{\n\t\treturn d;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/graphviz/MarkStateSetDecorator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.graphviz;\n\nimport java.util.BitSet;\n\n/**\n * A decorator for states: Given a BitSet of state indizes, fills\n * the nodes corresponding to these states with a given color.\n */\npublic class MarkStateSetDecorator implements Decorator\n{\n\t/** The set of states to be marked */\n\tprivate BitSet stateSet;\n\t/** The fill colour for the node */\n\tprivate String fillColour = \"#cccccc\";\n\n\t/**\n\t * Constructor, default colour grey.\n\t * @param stateSet the set of state indices to be marked.\n\t */\n\tpublic MarkStateSetDecorator(BitSet stateSet)\n\t{\n\t\tthis.stateSet = stateSet;\n\t}\n\n\t/**\n\t * Constructor, default colour grey.\n\t * @param stateSet the set of state indices to be marked.\n\t * @param fillColor HTML colour string for the fill colour\n\t */\n\tpublic MarkStateSetDecorator(BitSet set, String fillColor)\n\t{\n\t\tthis.stateSet = set;\n\t\tthis.fillColour = fillColor;\n\t}\n\n\t/**\n\t * Add \"style=filled\" and \"fillcolor=...\" attributes\n\t * to the decoration.\n\t */\n\t@Override\n\tpublic Decoration decorateState(int state, Decoration d)\n\t{\n\t\tif (stateSet.get(state)) {\n\t\t\td.attributes().put(\"style\", \"filled\");\n\t\t\td.attributes().put(\"fillcolor\", fillColour);\n\t\t}\n\t\treturn d;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/graphviz/ShowRewardDecorator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.graphviz;\n\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.Rewards;\n\n/**\n * A decorator that attaches rewards\n * to the labels of nodes / edges, according to the\n * given reward structure.\n */\npublic class ShowRewardDecorator<Value> implements Decorator\n{\n\t/** The reward structure */\n\tprivate Rewards<Value> rewards;\n\t/** Flag: should zero rewards be output? */\n\tprivate boolean showZero;\n\n\t/**\n\t * Constructor, suppress zero rewards in output.\n\t * @param rewards the reward structure\n\t */\n\tpublic ShowRewardDecorator(Rewards<Value> rewards)\n\t{\n\t\tthis(rewards, false);\n\n\t}\n\n\t/**\n\t * Constructor.\n\t * @param rewards the reward structure\n\t * @param showZero should zero rewards be output?\n\t */\n\tpublic ShowRewardDecorator(Rewards<Value> rewards, boolean showZero)\n\t{\n\t\tthis.rewards = rewards;\n\t\tthis.showZero = showZero;\n\t}\n\n\t/**\n\t * Decorate state node by appending state reward to state label.\n\t */\n\t@Override\n\tpublic Decoration decorateState(int state, Decoration d)\n\t{\n\t\tValue reward = rewards.getEvaluator().zero();\n\t\tif (rewards instanceof MCRewards) {\n\t\t\treward = ((MCRewards<Value>) rewards).getStateReward(state);\n\t\t} else if (rewards instanceof MDPRewards) {\n\t\t\treward = ((MDPRewards<Value>) rewards).getStateReward(state);\n\t\t}\n\t\tif (rewards.getEvaluator().isZero(reward) && !showZero) {\n\t\t\treturn d;\n\t\t}\n\t\td.labelAddBelow(\"+\" + reward);\n\t\treturn d;\n\t}\n\n\t/**\n\t * Decorate choice edge by appending transition reward to transition label.\n\t */\n\t@Override\n\tpublic Decoration decorateTransition(int state, int choice, Decoration d)\n\t{\n\t\tif (!(rewards instanceof MDPRewards)) {\n\t\t\t// transition rewards are only there for MDPRewards\n\t\t\treturn d;\n\t\t}\n\t\tValue reward = ((MDPRewards<Value>) rewards).getTransitionReward(state, choice);\n\t\tif (rewards.getEvaluator().isZero(reward) && !showZero) {\n\t\t\treturn d;\n\t\t}\n\n\t\td.labelAddBelow(\"+\" + reward);\n\t\treturn d;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/graphviz/ShowStateRewardsDecorator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.graphviz;\n\nimport java.util.Collections;\nimport java.util.List;\n\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.Rewards;\n\n/**\n * A decorator that attaches state rewards\n * to the labels of nodes, according to the\n * given reward structure(s).\n */\npublic class ShowStateRewardsDecorator<Value> implements Decorator\n{\n\t/** List of state reward structures */\n\tprivate List<Rewards<Value>> rewards;\n\t/** Output state rewards even if they are all zero for a state? */\n\tprivate boolean showAllZero;\n\n\t/** Constructor, single reward structure */\n\tpublic ShowStateRewardsDecorator(Rewards<Value> rewards, boolean showZero)\n\t{\n\t\tthis(Collections.singletonList(rewards), showZero);\n\t}\n\n\t/** Constructor, multiple reward structures */\n\tpublic ShowStateRewardsDecorator(List<Rewards<Value>> rewards, boolean showAllZero)\n\t{\n\t\tthis.rewards = rewards;\n\t\tthis.showAllZero = showAllZero;\n\t}\n\n\t/** Attach state rewards for the given state */\n\t@Override\n\tpublic Decoration decorateState(int state, Decoration d)\n\t{\n\t\tboolean allZero = true;\n\n\t\tfor (Rewards<Value> rew : rewards) {\n\t\t\tValue reward = rew.getStateReward(state);\n\t\t\tif (!rew.getEvaluator().isZero(reward)) {\n\t\t\t\tallZero = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\tif (allZero && !showAllZero)\n\t\t\treturn d;\n\n\t\tString values = \"\";\n\t\tfor (Rewards<Value> rew : rewards) {\n\t\t\tValue reward = rew.getStateReward(state);\n\t\t\tif (!values.isEmpty())\n\t\t\t\tvalues += \",\";\n\t\t\tvalues += reward;\n\t\t}\n\n\t\td.labelAddBelow(values);\n\t\treturn d;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/graphviz/ShowStatesDecorator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.graphviz;\n\nimport java.util.List;\nimport java.util.function.Function;\n\nimport parser.State;\n\n/**\n * Decorator which show the state variable valuation for a given state.\n */\npublic class ShowStatesDecorator implements Decorator\n{\n\t/** The state list, i.e., the variable valuation information for each state index */\n\tprivate List<State> stateList;\n\n\t/** Optionally, an observation map, i.e., the observable valuation information for each state index */\n\tprivate Function<Integer, State> obsList;\n\n\t/**\n\t * Constructor.\n\t * @param stateList the variable valuation information for each state index\n\t */\n\tpublic ShowStatesDecorator(List<State> stateList)\n\t{\n\t\tthis.stateList = stateList;\n\t}\n\n\t/**\n\t * Constructor.\n\t * @param stateList the variable valuation information for each state index\n\t * @param obsList optionally, the observable valuation information for each state index\n\t */\n\tpublic ShowStatesDecorator(List<State> stateList, Function<Integer, State> obsList)\n\t{\n\t\tthis.stateList = stateList;\n\t\tthis.obsList = obsList;\n\t}\n\n\t/** Decorate state label by appending the variable information */\n\tpublic Decoration decorateState(int state, Decoration d)\n\t{\n\t\tif (stateList != null) {\n\t\t\td.labelAddBelow(stateList.get(state).toString());\n\t\t}\n\t\tif (obsList != null) {\n\t\t\tState o = obsList.apply(state);\n\t\t\tif (o != null) {\n\t\t\t\td.labelAddBelow(o.toString());\n\t\t\t}\n\t\t}\n\t\treturn d;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/graphviz/StateOwnerDecorator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.graphviz;\n\nimport java.util.Arrays;\nimport java.util.List;\nimport java.util.function.Function;\n\n/**\n * A decorator that sets the shape of each state in a game model\n * to reflect the player that owns it.\n */\npublic class StateOwnerDecorator implements Decorator\n{\n\t/**\n\t * Shapes for players (Graphviz keywords).\n\t */\n\tpublic static final List<String> playerShapes = Arrays.asList(\"diamond\", \"box\", \"oval\", \"hexagon\");\n\n\t/**\n\t * State ownership function: state (0-indexed) to player (0-indexed)\n\t */\n\tprotected Function<Integer, Integer> stateOwners;\n\n\t/** Constructor, single reward structure */\n\tpublic StateOwnerDecorator(Function<Integer, Integer> stateOwners)\n\t{\n\t\tthis.stateOwners = stateOwners;\n\t}\n\n\t@Override\n\tpublic Decoration decorateState(int state, Decoration d)\n\t{\n\t\tint player = stateOwners.apply(state);\n\t\td.attributes().put(\"shape\", playerShapes.get(player % playerShapes.size()));\n\t\treturn d;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/modelviews/DTMCAlteredDistributions.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.AbstractMap;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.Set;\nimport java.util.function.IntFunction;\nimport java.util.function.Predicate;\n\nimport common.iterable.Reducible;\nimport common.iterable.SingletonIterator;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport explicit.DTMC;\n\n/**\n * A view of a DTMC where for selected states the transitions are changed.\n * <br>\n * The new transitions are given by a function (int state) -> Iterator<Entry<Integer, Value>,\n * i.e., providing an iterator over the outgoing transitions. A return value of {@code null}\n * is interpreted as \"keep the original transitions\".\n */\npublic class DTMCAlteredDistributions<Value> extends DTMCView<Value>\n{\n\tprivate DTMC<Value> model;\n\tprivate IntFunction<Iterator<Entry<Integer, Value>>> mapping;\n\n\tprivate Predicate<Entry<Integer, Value>> nonZero;\n\t\n\t/**\n\t * If {@code mapping} returns {@code null} for a state, the original transitions are preserved.\n\t *\n\t * @param model a DTMC\n\t * @param mapping from states to (new) distributions or null\n\t */\n\tpublic DTMCAlteredDistributions(final DTMC<Value> model, final IntFunction<Iterator<Entry<Integer, Value>>> mapping)\n\t{\n\t\tthis.model = model;\n\t\tthis.mapping = mapping;\n\t\tnonZero = (Entry<Integer, Value> e) -> { return model.getEvaluator().gt(e.getValue(), model.getEvaluator().zero()); };\n\t}\n\n\tpublic DTMCAlteredDistributions(final DTMCAlteredDistributions<Value> altered)\n\t{\n\t\tsuper(altered);\n\t\tmodel = altered.model;\n\t\tmapping = altered.mapping;\n\t\tnonZero = (Entry<Integer, Value> e) -> { return model.getEvaluator().gt(e.getValue(), model.getEvaluator().zero()); };\n\t}\n\n\n\n\t//--- Cloneable ---\n\n\t@Override\n\tpublic DTMCAlteredDistributions<Value> clone()\n\t{\n\t\treturn new DTMCAlteredDistributions<>(this);\n\t}\n\n\n\n\t//--- Model ---\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn model.getNumStates();\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn model.getNumInitialStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn model.getInitialStates();\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn model.getFirstInitialState();\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(final int state)\n\t{\n\t\treturn model.isInitialState(state);\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn model.getStatesList();\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn model.getVarList();\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn model.getConstantValues();\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(final String name)\n\t{\n\t\treturn model.getLabelStates(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn model.getLabels();\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn model.hasLabel(name);\n\t}\n\n\n\n\t//--- DTMC ---\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(final int state)\n\t{\n\t\tfinal Iterator<Entry<Integer, Value>> transitions = mapping.apply(state);\n\t\tif (transitions == null) {\n\t\t\treturn model.getTransitionsIterator(state);\n\t\t}\n\t\treturn Reducible.extend(transitions).filter(nonZero);\n\t}\n\n\n\n\t//--- DTMCView ---\n\n\t@Override\n\tprotected void fixDeadlocks()\n\t{\n\t\tassert !fixedDeadlocks : \"deadlocks already fixed\";\n\n\t\tmodel = fixDeadlocks(this.clone());\n\t\tmapping = state -> null;\n\t}\n\n\n\n\t//--- static methods ---\n\n\tpublic static <Value> DTMCAlteredDistributions<Value> fixDeadlocks(final DTMC<Value> model)\n\t{\n\t\tfinal BitSet deadlockStates = new BitSet();\n\t\tmodel.getDeadlockStates().forEach(deadlockStates::set);\n\t\tfinal DTMCAlteredDistributions<Value> fixed = addSelfLoops(model, deadlockStates);\n\t\tfixed.deadlockStates = deadlockStates;\n\t\tfixed.fixedDeadlocks = true;\n\t\treturn fixed;\n\t}\n\n\t/**\n\t * Return a view where the outgoing transitions for all states in the given set\n\t * are replaced by probability 1 self-loops.\n\t */\n\tpublic static <Value> DTMCAlteredDistributions<Value> addSelfLoops(final DTMC<Value> model, final BitSet states)\n\t{\n\t\tfinal IntFunction<Iterator<Entry<Integer, Value>>> addLoops = new IntFunction<Iterator<Entry<Integer, Value>>>()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic Iterator<Entry<Integer, Value>> apply(final int state)\n\t\t\t{\n\t\t\t\tif (states.get(state)) {\n\t\t\t\t\tEntry<Integer,Value> transition = new AbstractMap.SimpleImmutableEntry<>(state, model.getEvaluator().one());\n\t\t\t\t\treturn new SingletonIterator.Of<>(transition);\n\t\t\t\t}\n\t\t\t\treturn null;\n\t\t\t}\n\t\t};\n\t\treturn new DTMCAlteredDistributions<>(model, addLoops);\n\t}\n}"
  },
  {
    "path": "prism/src/explicit/modelviews/DTMCView.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.AbstractMap;\nimport java.util.Iterator;\nimport java.util.Map.Entry;\nimport java.util.PrimitiveIterator;\nimport java.util.function.IntFunction;\n\nimport common.IterableStateSet;\nimport explicit.DTMC;\nimport explicit.Distribution;\nimport explicit.SuccessorsIterator;\n\n/**\n * Base class for a DTMC view, i.e., a virtual DTMC that is obtained\n * by mapping from some other model on-the-fly.\n * <br>\n * The main job of sub-classes is to provide an appropriate\n * getTransitionsIterator() method. Several other methods, providing\n * meta-data on the model have to be provided as well. For examples,\n * see the sub-classes contained in this package.\n */\npublic abstract class DTMCView<Value> extends ModelView<Value> implements DTMC<Value>, Cloneable\n{\n\tpublic DTMCView()\n\t{\n\t\tsuper();\n\t}\n\n\tpublic DTMCView(final ModelView<Value> model)\n\t{\n\t\tsuper(model);\n\t}\n\n\n\n\t//--- Object ---\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tfinal IntFunction<Entry<Integer, Distribution<Value>>> getDistribution = new IntFunction<Entry<Integer, Distribution<Value>>>()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic final Entry<Integer, Distribution<Value>> apply(final int state)\n\t\t\t{\n\t\t\t\tfinal Distribution<Value> distribution = new Distribution<Value>(getTransitionsIterator(state), getEvaluator());\n\t\t\t\treturn new AbstractMap.SimpleImmutableEntry<>(state, distribution);\n\t\t\t}\n\t\t};\n\t\tString s = \"trans: [ \";\n\t\tIterableStateSet states = new IterableStateSet(getNumStates());\n\t\tIterator<Entry<Integer, Distribution<Value>>> distributions = states.iterator().map(getDistribution);\n\t\twhile (distributions.hasNext()) {\n\t\t\tfinal Entry<Integer, Distribution<Value>> dist = distributions.next();\n\t\t\ts += dist.getKey() + \": \" + dist.getValue();\n\t\t\tif (distributions.hasNext()) {\n\t\t\t\ts += \", \";\n\t\t\t}\n\t\t}\n\t\treturn s + \" ]\";\n\t}\n\n\n\n\t//--- Model ---\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(final int state)\n\t{\n\t\tfinal Iterator<Entry<Integer, Value>> transitions = getTransitionsIterator(state);\n\n\t\treturn SuccessorsIterator.from(new PrimitiveIterator.OfInt() {\n\t\t\tpublic boolean hasNext() {return transitions.hasNext();}\n\t\t\tpublic int nextInt() {return transitions.next().getKey();}\n\t\t}, true);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/modelviews/EquivalenceRelationInteger.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.Map;\n\nimport common.functions.PairPredicateInt;\nimport common.IterableBitSet;\n\n/**\n * An object representing an equivalence relation between integers (typically state indices),\n * from a given list of equivalent classes (each represented by a BitSet).\n */\npublic class EquivalenceRelationInteger implements PairPredicateInt\n{\n\tfinal protected Map<Integer, BitSet> classes = new HashMap<Integer, BitSet>();\n\tfinal protected BitSet nonRepresentatives    = new BitSet();\n\n\tpublic EquivalenceRelationInteger() {}\n\n\tpublic EquivalenceRelationInteger(final Iterable<BitSet> equivalenceClasses)\n\t{\n\t\tfor (BitSet equivalenceClass : equivalenceClasses) {\n\t\t\tswitch (equivalenceClass.cardinality()) {\n\t\t\tcase 0:\n\t\t\t\tthrow new IllegalArgumentException(\"expected non-empty classes\");\n\t\t\tcase 1:\n\t\t\t\tcontinue;\n\t\t\tdefault:\n\t\t\t\tfor (Integer i : new IterableBitSet(equivalenceClass)) {\n\t\t\t\t\tif (classes.put(i, equivalenceClass) != null) {\n\t\t\t\t\t\tthrow new IllegalArgumentException(\"expected disjoint classes\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tnonRepresentatives.or(equivalenceClass);\n\t\t\t\tnonRepresentatives.clear(equivalenceClass.nextSetBit(0));\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean test(final int i, final int j)\n\t{\n\t\tif (i == j) {\n\t\t\treturn true;\n\t\t}\n\t\tfinal BitSet equivalenceClass = classes.get(i);\n\t\treturn equivalenceClass != null && equivalenceClass.get(j);\n\t}\n\n\tpublic int getRepresentative(final int i)\n\t{\n\t\tfinal BitSet equivalenceClass = classes.get(i);\n\t\treturn equivalenceClass == null ? i : equivalenceClass.nextSetBit(0);\n\t}\n\n\tpublic BitSet getEquivalenceClass(final int i)\n\t{\n\t\tBitSet equivalenceClass = getEquivalenceClassOrNull(i);\n\t\tif (equivalenceClass == null) {\n\t\t\tequivalenceClass = new BitSet(i + 1);\n\t\t\tequivalenceClass.set(i);\n\t\t}\n\t\treturn equivalenceClass;\n\t}\n\n\t/**\n\t * Return the equivalence class of {@code i} if {@code i} is no singleton, otherwise {@code null}.\n\t * @param i a number\n\t * @return {@code null} if [i] is a singleton, otherwise [i]\n\t */\n\tpublic BitSet getEquivalenceClassOrNull(final int i)\n\t{\n\t\treturn classes.get(i);\n\t}\n\n\tpublic BitSet getNonRepresentatives()\n\t{\n\t\treturn nonRepresentatives;\n\t}\n\n\tpublic boolean isRepresentative(final int i)\n\t{\n\t\treturn ! nonRepresentatives.get(i);\n\t}\n\n\n\n\tpublic static class KeepSingletons extends EquivalenceRelationInteger\n\t{\n\t\tpublic KeepSingletons(Iterable<BitSet> equivalenceClasses)\n\t\t{\n\t\t\tfor (BitSet equivalenceClass : equivalenceClasses) {\n\t\t\t\tswitch (equivalenceClass.cardinality()) {\n\t\t\t\tcase 0:\n\t\t\t\t\tthrow new IllegalArgumentException(\"expected non-empty classes\");\n\t\t\t\tdefault:\n\t\t\t\t\tfor (Integer i : new IterableBitSet(equivalenceClass)) {\n\t\t\t\t\t\tif (classes.put(i, equivalenceClass) != null) {\n\t\t\t\t\t\t\tthrow new IllegalArgumentException(\"expected disjoint classes\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tnonRepresentatives.or(equivalenceClass);\n\t\t\t\t\tnonRepresentatives.clear(equivalenceClass.nextSetBit(0));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic BitSet getEquivalenceClassOrNull(int i)\n\t\t{\n\t\t\tBitSet equivalenceClass = super.getEquivalenceClassOrNull(i);\n\t\t\tif (equivalenceClass == null) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\treturn (equivalenceClass.cardinality() == 1) ? null : equivalenceClass;\n\t\t}\n\n\t\tpublic BitSet getOriginalEquivalenceClass(int i)\n\t\t{\n\t\t\treturn classes.get(i);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/modelviews/MDPAdditionalChoices.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.AbstractMap;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.Set;\nimport java.util.function.IntFunction;\nimport java.util.function.IntPredicate;\n\nimport common.iterable.SingletonIterator;\nimport explicit.MDP;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\n\n/**\n * An MDPView that takes an existing MDP and\n * adds additional choices to certain states.\n */\npublic class MDPAdditionalChoices<Value> extends MDPView<Value>\n{\n\tprivate MDP<Value> model;\n\tprivate IntFunction<List<Iterator<Entry<Integer, Value>>>> choices;\n\tprivate IntFunction<List<Object>> actions;\n\n\t/**\n\t * If {@code choices} returns {@code null} for a state and a choice, no additional choice is added.\n\t * If {@code actions} is {@code null} or returns {@code null} for a state, no additional action is attached.\n\t *\n\t * @param model\n\t * @param choices\n\t * @param actions\n\t */\n\tpublic MDPAdditionalChoices(final MDP<Value> model, final IntFunction<List<Iterator<Entry<Integer, Value>>>> choices,\n\t\t\tIntFunction<List<Object>> actions)\n\t{\n\t\tthis.model = model;\n\t\tthis.choices = choices;\n\t\tthis.actions = actions;\n\t}\n\n\tpublic MDPAdditionalChoices(final MDPAdditionalChoices<Value> additional)\n\t{\n\t\tsuper(additional);\n\t\tmodel = additional.model;\n\t\tchoices = additional.choices;\n\t\tactions = additional.actions;\n\t}\n\n\n\n\t//--- Cloneable ---\n\n\t@Override\n\tpublic MDPView<Value> clone()\n\t{\n\t\treturn new MDPAdditionalChoices<>(this);\n\t}\n\n\n\n\t//--- Model ---\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn model.getNumStates();\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn model.getNumInitialStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn model.getInitialStates();\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn model.getFirstInitialState();\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(final int state)\n\t{\n\t\treturn model.isInitialState(state);\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn model.getStatesList();\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn model.getVarList();\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn model.getConstantValues();\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(final String name)\n\t{\n\t\treturn model.getLabelStates(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn model.getLabels();\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn model.hasLabel(name);\n\t}\n\n\n\t//--- NondetModel ---\n\n\t@Override\n\tpublic int getNumChoices(final int state)\n\t{\n\t\treturn model.getNumChoices(state) + getNumAdditionalChoices(state);\n\t}\n\n\t@Override\n\tpublic Object getAction(final int state, final int choice)\n\t{\n\t\tfinal int numOriginalChoices = model.getNumChoices(state);\n\t\tif (choice < numOriginalChoices) {\n\t\t\treturn model.getAction(state, choice);\n\t\t}\n\t\tif (actions == null) {\n\t\t\tfinal int numChoices = numOriginalChoices + getNumAdditionalChoices(state);\n\t\t\tif (choice < numChoices) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\n\t\tfinal List<Object> additional = actions.apply(state);\n\t\treturn (additional == null) ?  null : additional.get(choice - numOriginalChoices);\n\t}\n\n\n\t//--- MDP ---\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(final int state, final int choice)\n\t{\n\t\tfinal int numOriginalChoices = model.getNumChoices(state);\n\t\tif (choice < numOriginalChoices) {\n\t\t\treturn model.getTransitionsIterator(state, choice);\n\t\t}\n\t\ttry {\n\t\t\treturn choices.apply(state).get(choice - numOriginalChoices);\n\t\t} catch (NullPointerException | IndexOutOfBoundsException e)\n\t\t{\n\t\t\t// alter message of exception\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\t}\n\n\t//--- MDPView ---\n\n\t@Override\n\tprotected void fixDeadlocks()\n\t{\n\t\tassert !fixedDeadlocks : \"deadlocks already fixed\";\n\n\t\tmodel = fixDeadlocks((MDP<Value>) this.clone());\n\t\tchoices = (int element) -> {return (List<Iterator<Entry<Integer, Value>>>)null;};\n\t\tactions = null;\n\t}\n\n\n\n\t//--- instance methods ---\n\n\tprivate int getNumAdditionalChoices(final int state)\n\t{\n\t\tfinal List<Iterator<Entry<Integer, Value>>> additional = choices.apply(state);\n\t\treturn (additional == null) ? 0 : additional.size();\n\t}\n\n\n\n\t//--- static methods ---\n\n\tpublic static <Value> MDPView<Value> fixDeadlocks(final MDP<Value> model)\n\t{\n\t\tfinal BitSet deadlockStates = new BitSet();\n\t\tmodel.getDeadlockStates().forEach(deadlockStates::set);\n\t\tfinal MDPView<Value> fixed = addSelfLoops(model, deadlockStates);\n\t\tfixed.deadlockStates = deadlockStates;\n\t\tfixed.fixedDeadlocks = true;\n\t\treturn fixed;\n\t}\n\n\tpublic static <Value> MDPView<Value> addSelfLoops(final MDP<Value> model, final BitSet states)\n\t{\n\t\treturn addSelfLoops(model, states::get);\n\t}\n\n\tpublic static <Value> MDPView<Value> addSelfLoops(final MDP<Value> model, final IntPredicate states)\n\t{\n\t\tfinal IntFunction<List<Iterator<Entry<Integer, Value>>>> addSelfLoops = new IntFunction<List<Iterator<Entry<Integer, Value>>>>()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic List<Iterator<Entry<Integer, Value>>> apply(final int state)\n\t\t\t{\n\t\t\t\tif (states.test(state)) {\n\t\t\t\t\tEntry<Integer,Value> transition = new AbstractMap.SimpleImmutableEntry<>(state, model.getEvaluator().one());\n\t\t\t\t\treturn Collections.singletonList(new SingletonIterator.Of<>(transition));\n\t\t\t\t}\n\t\t\t\treturn null;\n\t\t\t}\n\t\t};\n\t\treturn new MDPAdditionalChoices<Value>(model, addSelfLoops, null);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/modelviews/MDPDroppedAllChoices.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.Set;\n\nimport common.iterable.EmptyIterator;\nimport explicit.MDP;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\n\n/**\n * An MDPView that takes an existing MDP and removes\n * all outgoing choices for certain states.\n */\npublic class MDPDroppedAllChoices<Value> extends MDPView<Value>\n{\n\tprivate MDP<Value> model;\n\tprivate BitSet states;\n\n\n\n\tpublic MDPDroppedAllChoices(final MDP<Value> model, final BitSet dropped)\n\t{\n\t\tthis.model = model;\n\t\tthis.states = dropped;\n\t}\n\n\tpublic MDPDroppedAllChoices(final MDPDroppedAllChoices<Value> dropped)\n\t{\n\t\tsuper(dropped);\n\t\tmodel = dropped.model;\n\t\tstates = dropped.states;\n\t}\n\n\n\n\t//--- Cloneable ---\n\n\t@Override\n\tpublic MDPDroppedAllChoices<Value> clone()\n\t{\n\t\treturn new MDPDroppedAllChoices<>(this);\n\t}\n\n\n\n\t//--- Model ---\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn model.getNumStates();\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn model.getNumInitialStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn model.getInitialStates();\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn model.getFirstInitialState();\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(final int state)\n\t{\n\t\treturn model.isInitialState(state);\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn model.getStatesList();\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn model.getVarList();\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn model.getConstantValues();\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(final String name)\n\t{\n\t\treturn model.getLabelStates(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn model.getLabels();\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn model.hasLabel(name);\n\t}\n\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int state)\n\t{\n\t\treturn states.get(state) ? EmptyIterator.of() : model.getSuccessorsIterator(state);\n\t}\n\n\n\n\t//--- NondetModel ---\n\n\t@Override\n\tpublic int getNumChoices(final int state)\n\t{\n\t\treturn states.get(state) ? 0 : model.getNumChoices(state);\n\t}\n\n\t@Override\n\tpublic Object getAction(final int state, final int choice)\n\t{\n\t\tif (states.get(state)) {\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\t\treturn model.getAction(state, choice);\n\t}\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int state, final int choice)\n\t{\n\t\tif (states.get(state)) {\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\t\treturn model.getSuccessorsIterator(state, choice);\n\t}\n\n\n\n\t//--- MDP ---\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(final int state, final int choice)\n\t{\n\t\tif (states.get(state)) {\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\t\treturn model.getTransitionsIterator(state, choice);\n\t}\n\n\n\n\t//--- MDPView ---\n\n\t@Override\n\tprotected void fixDeadlocks()\n\t{\n\t\tassert !fixedDeadlocks : \"deadlocks already fixed\";\n\n\t\tmodel = MDPAdditionalChoices.fixDeadlocks(this.clone());\n\t\tstates = new BitSet();\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/modelviews/MDPDroppedChoicesCached.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.Set;\n\nimport common.functions.PairPredicateInt;\nimport explicit.Distribution;\nimport explicit.MDP;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\n\n/**\n * An MDPView that takes an existing MDP and removes certain choices.\n */\npublic class MDPDroppedChoicesCached<Value> extends MDPView<Value>\n{\n\tprivate MDP<Value> model;\n\n\t/** pointer to first for state s */\n\tprivate int[] startChoice;\n\t/** mapping of choice to choice in original MDP */\n\tprivate int[] mapping;\n\n\tpublic MDPDroppedChoicesCached(final MDP<Value> model, final PairPredicateInt dropped)\n\t{\n\t\tthis.model = model;\n\n\t\tint n = model.getNumStates();\n\t\tstartChoice = new int[model.getNumStates()+1];\n\t\t// number of choices in original model is an upper bound\n\t\tmapping = new int[model.getNumChoices()];\n\t\tint j = 0;\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tstartChoice[s] = j;\n\t\t\tfor (int choice = 0, numChoices = model.getNumChoices(s); choice < numChoices; choice++) {\n\t\t\t\tif (!dropped.test(s, choice)) {\n\t\t\t\t\tmapping[j] = choice;\n\t\t\t\t\tj++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tstartChoice[n] = j;\n\t\tint numPreservedChoices = j;\n\n\t\tif (numPreservedChoices < mapping.length) {\n\t\t\t// truncate mapping array\n\t\t\tmapping = Arrays.copyOf(mapping, numPreservedChoices);\n\t\t}\n\t}\n\n\tpublic MDPDroppedChoicesCached(final MDPDroppedChoicesCached<Value> dropped)\n\t{\n\t\tsuper(dropped);\n\t\tmodel = dropped.model;\n\t\tstartChoice = dropped.startChoice;\n\t\tmapping = dropped.mapping;\n\t}\n\n\t//--- Cloneable ---\n\n\t@Override\n\tpublic MDPDroppedChoicesCached<Value> clone()\n\t{\n\t\treturn new MDPDroppedChoicesCached<>(this);\n\t}\n\n\t//--- Model ---\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn model.getNumStates();\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn model.getNumInitialStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn model.getInitialStates();\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn model.getFirstInitialState();\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(final int state)\n\t{\n\t\treturn model.isInitialState(state);\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn model.getStatesList();\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn model.getVarList();\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn model.getConstantValues();\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(final String name)\n\t{\n\t\treturn model.getLabelStates(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn model.getLabels();\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn model.hasLabel(name);\n\t}\n\n\n\t//--- NondetModel ---\n\n\t@Override\n\tpublic int getNumChoices()\n\t{\n\t\treturn mapping.length;\n\t}\n\n\t@Override\n\tpublic int getNumChoices(final int state)\n\t{\n\t\treturn startChoice[state + 1] - startChoice[state];\n\t}\n\n\t@Override\n\tpublic Object getAction(final int state, final int choice)\n\t{\n\t\tfinal int originalChoice = mapChoiceToOriginalModel(state, choice);\n\t\treturn model.getAction(state, originalChoice);\n\t}\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int state, final int choice)\n\t{\n\t\tfinal int originalChoice = mapChoiceToOriginalModel(state, choice);\n\t\treturn model.getSuccessorsIterator(state, originalChoice);\n\t}\n\n\n\n\t//--- MDP ---\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(final int state, final int choice)\n\t{\n\t\tfinal int originalChoice = mapChoiceToOriginalModel(state, choice);\n\t\treturn model.getTransitionsIterator(state, originalChoice);\n\t}\n\n\n\n\t//--- MDPView ---\n\n\t@Override\n\tprotected void fixDeadlocks()\n\t{\n\t\tassert !fixedDeadlocks : \"deadlocks already fixed\";\n\n\t\tmodel = MDPAdditionalChoices.fixDeadlocks(this.clone());\n\t}\n\n\n\n\t//--- static methods\n\n\tpublic static <Value> MDPDroppedChoicesCached<Value> dropDenormalizedDistributions(final MDP<Value> model)\n\t{\n\t\tfinal PairPredicateInt denormalizedChoices = new PairPredicateInt()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic boolean test(int state, int choice)\n\t\t\t{\n\t\t\t\tfinal Distribution<Value> distribution = new Distribution<>(model.getTransitionsIterator(state, choice), model.getEvaluator());\n\t\t\t\treturn !model.getEvaluator().geq(distribution.sum(), model.getEvaluator().one());\n\t\t\t}\n\t\t};\n\t\treturn new MDPDroppedChoicesCached<>(model, denormalizedChoices);\n\t}\n\n\tpublic int mapChoiceToOriginalModel(final int state, final int choice)\n\t{\n\t\tint first = startChoice[state];\n\t\tif (choice >= getNumChoices(state)) {\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\n\t\treturn mapping[first + choice];\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/explicit/modelviews/MDPEquiv.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.AbstractMap.SimpleImmutableEntry;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.PrimitiveIterator.OfInt;\nimport java.util.Set;\nimport java.util.function.IntUnaryOperator;\n\nimport common.functions.PairPredicateInt;\nimport common.IterableBitSet;\nimport common.IterableStateSet;\nimport common.iterable.Reducible;\nimport explicit.BasicModelTransformation;\nimport explicit.MDP;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\n\n/**\n * An MDPView that provides a quotient view\n * on the original MDP, given an equivalence relation.\n * <br>\n * Note: The states that are not chosen as the representatives\n * for their equivalence class remain in the MDP, but their\n * choices are transferred / mapped to the representative state.\n */\npublic class MDPEquiv<Value> extends MDPView<Value>\n{\n\tprotected MDP<Value> model;\n\tprotected EquivalenceRelationInteger identify;\n\tprotected int[] numChoices;\n\tprotected StateChoicePair[][] originalChoices;\n\tprotected BitSet hasTransitionToNonRepresentative;\n\n\tprotected MDPEquiv(){/* only here to satisfy the compiler */}\n\n\tpublic MDPEquiv(final MDP<Value> model, final EquivalenceRelationInteger identify)\n\t{\n\t\tthis.model = model;\n\t\tthis.identify = identify;\n\t\tfinal int numStates = model.getNumStates();\n\t\tthis.numChoices = new int[numStates];\n\t\tthis.originalChoices = new StateChoicePair[numStates][];\n\t\tfor (OfInt representativeIterator = new IterableStateSet(identify.nonRepresentatives, numStates, true).iterator(); representativeIterator.hasNext();){\n\t\t\tfinal int representative = representativeIterator.nextInt();\n\t\t\tBitSet equivalenceClass = this.identify.getEquivalenceClassOrNull(representative);\n\t\t\tif (equivalenceClass == null || equivalenceClass.cardinality() == 1) {\n\t\t\t\t//the equivalence-class consists only of one state\n\t\t\t\t// => leave it as it is\n\t\t\t\tnumChoices[representative] = model.getNumChoices(representative);\n\t\t\t} else {\n\t\t\t\tIterableBitSet eqStates = new IterableBitSet(equivalenceClass);\n\t\t\t\tnumChoices[representative] = Math.toIntExact(eqStates.mapToInt((IntUnaryOperator) model::getNumChoices).sum());\n\t\t\t\tStateChoicePair[] choices = originalChoices[representative] = new StateChoicePair[numChoices[representative]];\n\t\t\t\tassert representative == equivalenceClass.nextSetBit(0);\n\t\t\t\tint choice = model.getNumChoices(representative);\n\t\t\t\tOfInt others = eqStates.iterator();\n\t\t\t\t// skip representative\n\t\t\t\tothers.nextInt();\n\t\t\t\twhile (others.hasNext()) {\n\t\t\t\t\tfinal int eqState = others.nextInt();\n\t\t\t\t\tfor (int eqChoice=0, numChoices=model.getNumChoices(eqState); eqChoice < numChoices; eqChoice++) {\n\t\t\t\t\t\tchoices[choice++] = new StateChoicePair(eqState, eqChoice);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// compute states that have a transition to a non-representative state\n\t\thasTransitionToNonRepresentative = new BitSet();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tif (model.someSuccessorsInSet(s, identify.getNonRepresentatives())) {\n\t\t\t\thasTransitionToNonRepresentative.set(s, true);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic MDPEquiv(MDPEquiv<Value> mdpEquiv)\n\t{\n\t\tsuper(mdpEquiv);\n\t\tmodel = mdpEquiv.model;\n\t\tidentify = mdpEquiv.identify;\n\t\tnumChoices = mdpEquiv.numChoices;\n\t\toriginalChoices = mdpEquiv.originalChoices;\n\t\thasTransitionToNonRepresentative = mdpEquiv.hasTransitionToNonRepresentative;\n\t}\n\n\n\n\t//--- Cloneable ---\n\n\t@Override\n\tpublic MDPEquiv<Value> clone()\n\t{\n\t\treturn new MDPEquiv<>(this);\n\t}\n\n\n\n\t//--- Model ---\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn model.getNumStates();\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn model.getNumInitialStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn model.getInitialStates();\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn model.getFirstInitialState();\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(int state)\n\t{\n\t\treturn model.isInitialState(state);\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn model.getStatesList();\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn model.getVarList();\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn model.getConstantValues();\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(String name)\n\t{\n\t\treturn model.getLabelStates(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn model.getLabels();\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn model.hasLabel(name);\n\t}\n\n\t//--- NondetModel ---\n\n\t@Override\n\tpublic int getNumChoices(final int state)\n\t{\n\t\treturn numChoices[state];\n\t}\n\n\t@Override\n\tpublic Object getAction(final int state, final int choice)\n\t{\n\t\tfinal StateChoicePair originals = mapToOriginalModelOrNull(state, choice);\n\t\treturn (originals == null) ? model.getAction(state, choice) : model.getAction(originals.state, originals.choice);\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(final int state, final int choice)\n\t{\n\t\tfinal StateChoicePair originals = mapToOriginalModelOrNull(state, choice);\n\t\treturn (originals == null) ? model.getNumTransitions(state, choice) : model.getNumTransitions(originals.state, originals.choice);\n\t}\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int state, final int choice)\n\t{\n\t\tStateChoicePair originals = mapToOriginalModelOrNull(state, choice);\n\t\tfinal int originalState, originalChoice;\n\t\tif (originals == null) {\n\t\t\toriginalState = state;\n\t\t\toriginalChoice = choice;\n\t\t} else {\n\t\t\toriginalState = originals.state;\n\t\t\toriginalChoice = originals.choice;\n\t\t}\n\t\tIterator<Integer> successors = model.getSuccessorsIterator(originalState, originalChoice);\n\t\tif (hasTransitionToNonRepresentative.get(originalState)) {\n\t\t\treturn Reducible.extend(successors).map(this::mapStateToRestrictedModel).distinct();\n\t\t}\n\t\treturn successors;\n\t}\n\n\n\n\t//--- MDP ---\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(final int state, final int choice)\n\t{\n\t\tStateChoicePair originals = mapToOriginalModelOrNull(state, choice);\n\t\tfinal int originalState, originalChoice;\n\t\tif (originals == null) {\n\t\t\toriginalState = state;\n\t\t\toriginalChoice = choice;\n\t\t} else {\n\t\t\toriginalState = originals.state;\n\t\t\toriginalChoice = originals.choice;\n\t\t}\n\t\tIterator<Entry<Integer, Value>> transitions = model.getTransitionsIterator(originalState, originalChoice);\n\t\tif (hasTransitionToNonRepresentative.get(originalState)) {\n\t\t\treturn Reducible.extend(transitions).map(this::mapTransitionToRestrictedModel);\n\t\t}\n\t\treturn transitions;\n\t}\n\n\n\n\t//--- MDPView ---\n\n\t@Override\n\tprotected void fixDeadlocks()\n\t{\n\t\tassert !fixedDeadlocks : \"deadlocks already fixed\";\n\t\tmodel = MDPAdditionalChoices.fixDeadlocks(this.clone());\n\t\tidentify = new EquivalenceRelationInteger();\n\t\tfinal int numStates = model.getNumStates();\n\t\tnumChoices = new int[numStates];\n\t\tfor (int state=0; state<numStates; state++) {\n\t\t\tnumChoices[state] = model.getNumChoices(state);\n\t\t}\n\t\toriginalChoices = new StateChoicePair[numStates][];\n\t\thasTransitionToNonRepresentative = new BitSet();\n\t}\n\n\n\n\t//--- instance methods ---\n\n\tpublic Integer mapStateToRestrictedModel(final int state)\n\t{\n\t\treturn identify.getRepresentative(state);\n\t}\n\n\tpublic SimpleImmutableEntry<Integer, Value> mapTransitionToRestrictedModel(final Entry<Integer, Value> transition)\n\t{\n\t\tfinal Integer target = identify.getRepresentative(transition.getKey());\n\t\tfinal Value probability = transition.getValue();\n\t\treturn new SimpleImmutableEntry<>(target, probability);\n\t}\n\n\tpublic StateChoicePair mapToOriginalModel(final int state, final int choice)\n\t{\n\t\tStateChoicePair mapped = mapToOriginalModelOrNull(state, choice);\n\t\tif (mapped == null)\n\t\t\tmapped = new StateChoicePair(state, choice);\n\t\treturn mapped;\n\t}\n\n\tpublic StateChoicePair mapToOriginalModelOrNull(final int state, final int choice)\n\t{\n\t\tStateChoicePair[] stateChoicePairs = originalChoices[state];\n\t\tif (stateChoicePairs == null) {\n\t\t\treturn null;\n\t\t}\n\t\treturn stateChoicePairs[choice];\n\t}\n\n\tpublic BitSet getNonRepresentativeStates()\n\t{\n\t\treturn identify.getNonRepresentatives();\n\t}\n\n\t//--- static methods ---\n\n\tpublic static <Value> BasicModelTransformation<MDP<Value>, MDPEquiv<Value>> transform(MDP<Value> model, EquivalenceRelationInteger identify)\n\t{\n\t\treturn new BasicModelTransformation<>(model, new MDPEquiv<>(model, identify));\n\t}\n\n\tpublic static <Value> BasicModelTransformation<MDP<Value>, MDPEquiv<Value>> transformDroppingLoops(MDP<Value> model, EquivalenceRelationInteger identify)\n\t{\n\t\tfinal MDPDroppedChoicesCached<Value> dropped = new MDPDroppedChoicesCached<>(model, new PairPredicateInt()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic boolean test(final int state, final int choice)\n\t\t\t{\n\t\t\t\tIterator<Integer> successors = model.getSuccessorsIterator(state, choice);\n\t\t\t\twhile (successors.hasNext()){\n\t\t\t\t\tif (! identify.test(state, (int) successors.next())){\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\treturn true;\n\t\t\t}\n\t\t});\n\t\treturn new BasicModelTransformation<>(model, new MDPEquiv<Value>(dropped, identify));\n\t}\n\n}"
  },
  {
    "path": "prism/src/explicit/modelviews/MDPFromDTMC.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\nimport java.util.Set;\n\nimport explicit.DTMC;\nimport explicit.DTMCSimple;\nimport explicit.MDP;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport prism.PrismException;\n\n/**\n * An MDPView that takes an existing DTMC and pretends it\n * is actually an MDP, i.e., in every state there is a single choice.\n */\npublic class MDPFromDTMC<Value> extends MDPView<Value>\n{\n\tprivate DTMC<Value> model;\n\n\n\n\tpublic MDPFromDTMC(final DTMC<Value> model)\n\t{\n\t\tthis.model = model;\n\t}\n\n\tpublic MDPFromDTMC(final MDPFromDTMC<Value> mdp)\n\t{\n\t\tsuper(mdp);\n\t\tmodel = mdp.model;\n\t}\n\n\n\n\t//--- Cloneable ---\n\n\t@Override\n\tpublic MDPFromDTMC<Value> clone()\n\t{\n\t\treturn new MDPFromDTMC<>(this);\n\t}\n\n\n\n\t//--- Model ---\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn model.getNumStates();\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn model.getNumInitialStates();\n\t}\n\n\t@Override\n\tpublic Iterable<Integer> getInitialStates()\n\t{\n\t\treturn model.getInitialStates();\n\t}\n\n\t@Override\n\tpublic int getFirstInitialState()\n\t{\n\t\treturn model.getFirstInitialState();\n\t}\n\n\t@Override\n\tpublic boolean isInitialState(final int state)\n\t{\n\t\treturn model.isInitialState(state);\n\t}\n\n\t@Override\n\tpublic List<State> getStatesList()\n\t{\n\t\treturn model.getStatesList();\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn model.getVarList();\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn model.getConstantValues();\n\t}\n\n\t@Override\n\tpublic BitSet getLabelStates(final String name)\n\t{\n\t\treturn model.getLabelStates(name);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn model.getLabels();\n\t}\n\n\t@Override\n\tpublic boolean hasLabel(String name)\n\t{\n\t\treturn model.hasLabel(name);\n\t}\n\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int state)\n\t{\n\t\treturn model.getSuccessorsIterator(state);\n\t}\n\n\n\n\t//--- NondetModel ---\n\n\t@Override\n\tpublic int getNumChoices(final int state)\n\t{\n\t\treturn model.getTransitionsIterator(state).hasNext() ? 1 : 0;\n\t}\n\n\t@Override\n\tpublic Object getAction(final int state, final int choice)\n\t{\n\t\tif (choice >= getNumChoices(state)) {\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic boolean areAllChoiceActionsUnique()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic Iterator<Integer> getSuccessorsIterator(final int state, final int choice)\n\t{\n\t\tif (choice >= getNumChoices(state)) {\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\t\treturn model.getSuccessorsIterator(state);\n\t}\n\n\n\n\t//--- MDP ---\n\n\t@Override\n\tpublic Iterator<Entry<Integer, Value>> getTransitionsIterator(final int state, final int choice)\n\t{\n\t\tif (choice > 0) {\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\t\tfinal Iterator<Entry<Integer, Value>> transitions = model.getTransitionsIterator(state);\n\t\tif (!transitions.hasNext()) {\n\t\t\tthrow new IndexOutOfBoundsException(\"choice index out of bounds\");\n\t\t}\n\t\treturn transitions;\n\t}\n\n\n\n\t//--- MDPView ---\n\n\t@Override\n\tprotected void fixDeadlocks()\n\t{\n\t\tassert !fixedDeadlocks : \"deadlocks already fixed\";\n\n\t\ttry {\n\t\t\tmodel.findDeadlocks(false);\n\t\t} catch (final PrismException e) {\n\t\t\tassert false : \"no attempt to fix deadlocks\";\n\t\t}\n\t\tmodel = DTMCAlteredDistributions.fixDeadlocks(model);\n\t}\n\n\n\n\t//--- static methods ---\n\n\tpublic static void main(final String[] args) throws PrismException\n\t{\n\t\tfinal DTMCSimple<Double> original = new DTMCSimple<>(4);\n\t\toriginal.addInitialState(1);\n\t\toriginal.setProbability(0, 1, 0.1);\n\t\toriginal.setProbability(0, 2, 0.9);\n\t\toriginal.setProbability(1, 2, 0.2);\n\t\toriginal.setProbability(1, 3, 0.8);\n\t\toriginal.setProbability(2, 1, 0.3);\n\t\toriginal.setProbability(2, 2, 0.7);\n\t\toriginal.findDeadlocks(false);\n\t\tSystem.out.println(original);\n\n\t\tfinal MDP<Double> mdp = new MDPFromDTMC<>(original);\n\t\tmdp.findDeadlocks(true);\n\t\tSystem.out.println(mdp);\n\t}\n}"
  },
  {
    "path": "prism/src/explicit/modelviews/MDPView.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.Iterator;\nimport java.util.Map.Entry;\nimport java.util.PrimitiveIterator;\n\nimport explicit.DTMCFromMDPAndMDStrategy;\nimport explicit.Distribution;\nimport explicit.MDP;\nimport explicit.Model;\nimport explicit.SuccessorsIterator;\nimport strat.MDStrategy;\n\n/**\n * Base class for an MDP view, i.e., a virtual MDP that is obtained\n * by mapping from some other model on-the-fly.\n * <br>\n * The main job of sub-classes is to provide an appropriate\n * getTransitionsIterator() method. Several other methods, providing\n * meta-data on the model have to be provided as well. For examples,\n * see the sub-classes contained in this package.\n */\npublic abstract class MDPView<Value> extends ModelView<Value> implements MDP<Value>, Cloneable\n{\n\tpublic MDPView()\n\t{\n\t\tsuper();\n\t}\n\n\tpublic MDPView(final MDPView<Value> model)\n\t{\n\t\tsuper(model);\n\t}\n\n\n\n\t//--- Object ---\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"[ \";\n\t\tfor (int state = 0, numStates = getNumStates(); state < numStates; state++) {\n\t\t\tif (state > 0)\n\t\t\t\ts += \", \";\n\t\t\ts += state + \": \";\n\t\t\ts += \"[\";\n\t\t\tfor (int choice = 0, numChoices = getNumChoices(state); choice < numChoices; choice++) {\n\t\t\t\tif (choice > 0)\n\t\t\t\t\ts += \",\";\n\t\t\t\tfinal Object action = getAction(state, choice);\n\t\t\t\tif (action != null)\n\t\t\t\t\ts += action + \":\";\n\t\t\t\ts += new Distribution<Value>(getTransitionsIterator(state, choice), getEvaluator());\n\t\t\t}\n\t\t\ts += \"]\";\n\t\t}\n\t\ts += \" ]\";\n\t\treturn s;\n\t}\n\n\t//--- NondetModel ---\n\n\t@Override\n\tpublic SuccessorsIterator getSuccessors(final int state, final int choice)\n\t{\n\t\tfinal Iterator<Entry<Integer, Value>> transitions = getTransitionsIterator(state, choice);\n\n\t\treturn SuccessorsIterator.from(new PrimitiveIterator.OfInt() {\n\t\t\tpublic boolean hasNext() {return transitions.hasNext();}\n\t\t\tpublic int nextInt() {return transitions.next().getKey();}\n\t\t}, true);\n\t}\n\n\t@Override\n\tpublic Model<Value> constructInducedModel(final MDStrategy<Value> strat)\n\t{\n\t\treturn new DTMCFromMDPAndMDStrategy<>(this, strat);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/modelviews/ModelView.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.PrimitiveIterator.OfInt;\n\nimport common.iterable.FilteringIterable;\nimport common.iterable.FunctionalPrimitiveIterable;\nimport common.IterableBitSet;\nimport common.IterableStateSet;\nimport explicit.Model;\nimport explicit.PredecessorRelation;\nimport explicit.StateValues;\nimport parser.State;\nimport parser.VarList;\nimport prism.ActionList;\nimport prism.ActionListOwner;\nimport prism.Prism;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLog;\n\n/**\n * Base class for an DTMCView or MDPView,\n * handling common tasks.\n */\npublic abstract class ModelView<Value> implements Model<Value>, ActionListOwner\n{\n\tprotected ActionList actionList = new ActionList(this::findActionsUsed);\n\tprotected BitSet deadlockStates = new BitSet();\n\tprotected boolean fixedDeadlocks = false;\n\tprotected PredecessorRelation predecessorRelation;\n\n\tpublic ModelView()\n\t{\n\t}\n\n\tpublic ModelView(final ModelView<Value> model)\n\t{\n\t\tdeadlockStates = (BitSet) model.deadlockStates.clone();\n\t\tfixedDeadlocks = model.fixedDeadlocks;\n\t}\n\n\t//--- Model ---\n\n\t@Override\n\tpublic ActionList getActionList()\n\t{\n\t\treturn actionList;\n\t}\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\treturn actionList.getActions();\n\t}\n\n\t@Override\n\tpublic int actionIndex(Object action)\n\t{\n\t\treturn actionList.actionIndex(action);\n\t}\n\n\t@Override\n\tpublic int getNumDeadlockStates()\n\t{\n\t\treturn deadlockStates.cardinality();\n\t}\n\n\t@Override\n\tpublic FunctionalPrimitiveIterable.OfInt getDeadlockStates()\n\t{\n\t\treturn new IterableBitSet(deadlockStates);\n\t}\n\n\t@Override\n\tpublic StateValues getDeadlockStatesList()\n\t{\n\t\treturn StateValues.createFromBitSet(deadlockStates, this);\n\t}\n\n\t@Override\n\tpublic int getFirstDeadlockState()\n\t{\n\t\treturn deadlockStates.nextSetBit(0);\n\t}\n\n\t@Override\n\tpublic boolean isDeadlockState(final int state)\n\t{\n\t\treturn deadlockStates.get(state);\n\t}\n\n\n\t@Override\n\tpublic void findDeadlocks(final boolean fix) throws PrismException\n\t{\n\t\tfor (int s : findDeadlocks(new BitSet())) {\n\t\t\tdeadlockStates.set(s);\n\t\t}\n\n\t\tif (fix && !fixedDeadlocks) {\n\t\t\tfixDeadlocks();\n\t\t\tfixedDeadlocks = true;\n\t\t}\n\t}\n\n\tpublic FunctionalPrimitiveIterable.OfInt findDeadlocks(final BitSet except)\n\t{\n\t\tIterableStateSet states = new IterableStateSet(except, getNumStates(), true);\n\t\treturn new FilteringIterable.OfInt(states, state -> !getSuccessorsIterator(state).hasNext());\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks() throws PrismException\n\t{\n\t\tcheckForDeadlocks(null);\n\t}\n\n\t@Override\n\tpublic void checkForDeadlocks(final BitSet except) throws PrismException\n\t{\n\t\tOfInt deadlocks = findDeadlocks(except).iterator();\n\t\tif (deadlocks.hasNext()) {\n\t\t\tthrow new PrismException(getModelType() + \" has a deadlock in state \" + deadlocks.nextInt());\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean hasStoredPredecessorRelation()\n\t{\n\t\treturn (predecessorRelation != null);\n\t}\n\n\t@Override\n\tpublic PredecessorRelation getPredecessorRelation(PrismComponent parent, boolean storeIfNew)\n\t{\n\t\tif (predecessorRelation != null) {\n\t\t\treturn predecessorRelation;\n\t\t}\n\n\t\tfinal PredecessorRelation pre = PredecessorRelation.forModel(parent, this);\n\n\t\tif (storeIfNew) {\n\t\t\tpredecessorRelation = pre;\n\t\t}\n\t\treturn pre;\n\t}\n\n\t@Override\n\tpublic void clearPredecessorRelation()\n\t{\n\t\tpredecessorRelation = null;\n\t}\n\n\n\n\t//--- instance methods ---\n\n\tprotected abstract void fixDeadlocks();\n\n\t/**\n\t * Tell whether the receiver is a virtual or explicit model.\n\t * Virtual models may impose a significant overhead on any computations.\n\t *\n\t * @return true iff model is a virtual model\n\t */\n\tpublic boolean isVirtual()\n\t{\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/modelviews/StateChoicePair.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Steffen Maercker <maercker@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.modelviews;\n\npublic class StateChoicePair\n{\n\tfinal int state;\n\tfinal int choice;\n\n\tprotected StateChoicePair(final int theState, final int theChoice)\n\t{\n\t\tstate = theState;\n\t\tchoice = theChoice;\n\t}\n\n\tpublic int getState()\n\t{\n\t\treturn state;\n\t}\n\n\tpublic int getChoice()\n\t{\n\t\treturn choice;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/package-info.java",
    "content": "/**\n * Explicit-state probabilistic model checking engine, implemented in Java, and quantitative abstraction refinement techniques (see {@link explicit.QuantAbstractRefine}).\n */\npackage explicit;\n"
  },
  {
    "path": "prism/src/explicit/rewards/ConstructRewards.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport java.io.BufferedReader;\nimport java.io.File;\nimport java.io.FileReader;\nimport java.io.IOException;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\n\nimport common.Interval;\nimport explicit.DTMC;\nimport explicit.IDTMC;\nimport explicit.MDP;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport parser.State;\nimport parser.Values;\nimport parser.ast.ASTElement;\nimport parser.ast.Expression;\nimport parser.ast.RewardStruct;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.Pair;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismNotSupportedException;\nimport prism.RewardGenerator;\nimport prism.RewardGenerator.RewardLookup;\n\npublic class ConstructRewards extends PrismComponent\n{\n\tpublic ConstructRewards(PrismComponent parent)\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/** Allow negative rewards, i.e., weights. Defaults to false. */\n\tprotected boolean allowNegative = false;\n\n\t/** Set flag that negative rewards are allowed, i.e., weights */\n\tpublic void allowNegativeRewards()\n\t{\n\t\tallowNegative = true;\n\t}\n\n\t/**\n\t * Construct expected reward, i.e., using probability-weighted sum for any rewards\n\t * attached to transitions, assigning them to states/choices. Defaults to false.\n\t */\n\tprotected boolean expectedRewards = false;\n\n\t/**\n\t * Specify whether to construct expected reward, i.e., using probability-weighted sum for any rewards\n\t * attached to transitions, assigning them to states/choices. Defaults to false.\n\t */\n\tpublic void setExpectedRewards(boolean expectedRewards)\n\t{\n\t\tthis.expectedRewards = expectedRewards;\n\t}\n\n\t/**\n\t * Construct the rewards for a model from a reward generator. \n\t * @param model The model\n\t * @param rewardGen The RewardGenerator defining the rewards\n\t * @param r The index of the reward structure to build\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <Value> Rewards<Value> buildRewardStructure(Model<Value> model, RewardGenerator<Value> rewardGen, int r) throws PrismException\n\t{\n\t\t// If the RewardGenerator already has the rewards built, use this (after checking)\n\t\tif (rewardGen.isRewardLookupSupported(RewardLookup.BY_REWARD_OBJECT)) {\n\t\t\tRewards<Value> rewardsObj = rewardGen.getRewardObject(r);\n\t\t\trewardsObj = checkRewardObject(rewardsObj, rewardGen.getRewardObjectModel(), rewardGen.getRewardEvaluator());\n\t\t\treturn rewardsObj;\n\t\t}\n\t\t// Extract some model info\n\t\tint numStates = model.getNumStates();\n\t\tList<State> statesList = model.getStatesList();\n\t\t// Create reward structure object of appropriate type\n\t\t// (can be more efficient if just double-valued state rewards)\n\t\tRewardsExplicit<Value> rewards;\n\t\tboolean nondet = model.getModelType().nondeterministic();\n\t\tboolean dbl = rewardGen.getRewardEvaluator().one() instanceof Double;\n\t\tboolean sr = !(rewardGen.rewardStructHasTransitionRewards(r) && !(expectedRewards && !nondet));\n\t\tif (dbl && sr) {\n\t\t\trewards = (RewardsExplicit<Value>) new StateRewardsArray(numStates);\n\t\t} else {\n\t\t\trewards = new RewardsSimple<>(numStates);\n\t\t}\n\t\trewards.setEvaluator(rewardGen.getRewardEvaluator());\n\t\t// Add rewards\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t// State rewards\n\t\t\tif (rewardGen.rewardStructHasStateRewards(r)) {\n\t\t\t\tValue rew = getAndCheckStateReward(s, rewardGen, r, statesList);\n\t\t\t\trewards.addToStateReward(s, rew);\n\t\t\t}\n\t\t\t// Transition rewards\n\t\t\tif (rewardGen.rewardStructHasTransitionRewards(r)) {\n\t\t\t\t// Don't add rewards to transitions added to \"fix\" deadlock states\n\t\t\t\tif (model.isDeadlockState(s)) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t// Nondet models (reward on choice/action)\n\t\t\t\tif (nondet) {\n\t\t\t\t\tNondetModel<Value> nondetModel = (NondetModel<Value>) model;\n\t\t\t\t\tint numChoices = nondetModel.getNumChoices(s);\n\t\t\t\t\tfor (int k = 0; k < numChoices; k++) {\n\t\t\t\t\t\tValue rew = getAndCheckStateActionReward(s, nondetModel.getAction(s, k), rewardGen, r, statesList);\n\t\t\t\t\t\trewards.addToTransitionReward(s, k, rew);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Markov chain models (rewards on transitions)\n\t\t\t\telse if (model instanceof DTMC) {\n\t\t\t\t\tDTMC<Value> mcModel = (DTMC<Value>) model;\n\t\t\t\t\tIterator<Map.Entry<Integer, Pair<Value, Object>>> iter = mcModel.getTransitionsAndActionsIterator(s);\n\t\t\t\t\tint i = 0;\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Pair<Value, Object>> e = iter.next();\n\t\t\t\t\t\tValue rew = getAndCheckStateActionReward(s, e.getValue().second, rewardGen, r, statesList);\n\t\t\t\t\t\tif (rewardGen.getRewardEvaluator().isZero(rew)) {\n\t\t\t\t\t\t\ti++;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (expectedRewards) {\n\t\t\t\t\t\t\tValue rewWeighted = rewardGen.getRewardEvaluator().multiply(e.getValue().first, rew);\n\t\t\t\t\t\t\trewards.addToStateReward(s, rewWeighted);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\trewards.addToTransitionReward(s, i, rew);\n\t\t\t\t\t\t}\n\t\t\t\t\t\ti++;\n\t\t\t\t\t}\n\t\t\t\t} else if (model.getModelType() == ModelType.IDTMC) {\n\t\t\t\t\tIDTMC<Value> mcModel = (IDTMC<Value>) model;\n\t\t\t\t\tIterator<Map.Entry<Integer, Pair<Interval<Value>, Object>>> iter = mcModel.getIntervalTransitionsAndActionsIterator(s);\n\t\t\t\t\tint i = 0;\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Pair<Interval<Value>, Object>> e = iter.next();\n\t\t\t\t\t\tValue rew = getAndCheckStateActionReward(s, e.getValue().second, rewardGen, r, statesList);\n\t\t\t\t\t\tif (rewardGen.getRewardEvaluator().isZero(rew)) {\n\t\t\t\t\t\t\ti++;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (expectedRewards) {\n\t\t\t\t\t\t\tthrow new PrismException(\"Can't construct expected rewards for IDTMCs\");\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\trewards.addToTransitionReward(s, i, rew);\n\t\t\t\t\t\t}\n\t\t\t\t\t\ti++;\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tthrow new PrismException(\"Cannot build rewards for \" + model.getModelType() + \"s\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Get a state reward for a specific state and reward structure from a RewardGenerator.\n\t * Also check that the state reward is legal. Throw an exception if not.\n\t * @param s The index of the state\n\t * @param rewardGen The RewardGenerator defining the rewards\n\t * @param r The index of the reward structure to build\n\t * @param statesList List of states (maybe needed for state look up)\n\t */\n\tprivate <Value> Value getAndCheckStateReward(int s, RewardGenerator<Value> rewardGen, int r, List<State> statesList) throws PrismException\n\t{\n\t\tEvaluator<Value> eval = rewardGen.getRewardEvaluator();\n\t\tValue rew = eval.zero();\n\t\tObject stateIndex = null;\n\t\tif (rewardGen.isRewardLookupSupported(RewardLookup.BY_STATE)) {\n\t\t\tState state = statesList.get(s);\n\t\t\tstateIndex = state;\n\t\t\trew = rewardGen.getStateReward(r, state, allowNegative);\n\t\t} else if (rewardGen.isRewardLookupSupported(RewardLookup.BY_STATE_INDEX)) {\n\t\t\tstateIndex = s;\n\t\t\trew = rewardGen.getStateReward(r, s, allowNegative);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Unknown reward lookup mechanism for reward generator\");\n\t\t}\n\t\tcheckStateReward(rew, eval, stateIndex, null);\n\t\treturn rew;\n\t}\n\n\t/**\n\t * Get a state-action reward for a specific state and reward structure from a RewardGenerator.\n\t * Also check that the state reward is legal. Throw an exception if not.\n\t * @param s The index of the state\n\t * @param rewardGen The RewardGenerator defining the rewards\n\t * @param r The index of the reward structure to build\n\t * @param statesList List of states (maybe needed for state look up)\n\t */\n\tprivate <Value> Value getAndCheckStateActionReward(int s, Object action, RewardGenerator<Value> rewardGen, int r, List<State> statesList) throws PrismException\n\t{\n\t\tEvaluator<Value> eval = rewardGen.getRewardEvaluator();\n\t\tValue rew = eval.zero();\n\t\tObject stateIndex = null;\n\t\tif (rewardGen.isRewardLookupSupported(RewardLookup.BY_STATE)) {\n\t\t\tState state = statesList.get(s);\n\t\t\tstateIndex = state;\n\t\t\trew = rewardGen.getStateActionReward(r, state, action, allowNegative);\n\t\t} else if (rewardGen.isRewardLookupSupported(RewardLookup.BY_STATE_INDEX)) {\n\t\t\tstateIndex = s;\n\t\t\trew = rewardGen.getStateActionReward(r, s, action, allowNegative);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Unknown reward lookup mechanism for reward generator\");\n\t\t}\n\t\tcheckTransitionReward(rew, eval, stateIndex, null);\n\t\treturn rew;\n\t}\n\n\t/**\n\t * Construct rewards from a model and reward structure. \n\t * @param model The model\n\t * @param rewStr The reward structure\n\t * @param constantValues Values for any undefined constants needed\n\t */\n\tpublic Rewards<Double> buildRewardStructure(Model<Double> model, RewardStruct rewStr, Values constantValues) throws PrismException\n\t{\n\t\t// Special case: constant rewards\n\t\tif (rewStr.getNumStateItems() == 1 && Expression.isTrue(rewStr.getStates(0)) && rewStr.getReward(0).isConstant()) {\n\t\t\tdouble rew = rewStr.getReward(0).evaluateDouble(constantValues);\n\t\t\tcheckStateReward(rew, null, rewStr.getReward(0));\n\t\t\treturn new StateRewardsConstant<>(rew);\n\t\t}\n\t\t// Extract some model info\n\t\tint numStates = model.getNumStates();\n\t\tList<State> statesList = model.getStatesList();\n\t\t// Create reward structure object of appropriate type\n\t\t// (can be more efficient if just (double-valued) state rewards)\n\t\tRewardsExplicit<Double> rewards;\n\t\tboolean nondet = model.getModelType().nondeterministic();\n\t\tboolean sr = !(rewStr.getNumTransItems() > 0 && !(expectedRewards && !nondet));\n\t\tif (sr) {\n\t\t\trewards = new StateRewardsArray(numStates);\n\t\t} else {\n\t\t\trewards = new RewardsSimple<>(numStates);\n\t\t}\n\t\t// Add rewards\n\t\tint n = rewStr.getNumItems();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tExpression guard = rewStr.getStates(i);\n\t\t\tString action = rewStr.getSynch(i);\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\t// Is guard satisfied?\n\t\t\t\tif (guard.evaluateBoolean(constantValues, statesList.get(s))) {\n\t\t\t\t\t// Transition reward\n\t\t\t\t\tif (rewStr.getRewardStructItem(i).isTransitionReward()) {\n\t\t\t\t\t\t// Don't add rewards to transitions added to \"fix\" deadlock states\n\t\t\t\t\t\tif (model.isDeadlockState(s)) {\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// Nondet models (reward on choice/action)\n\t\t\t\t\t\tif (nondet) {\n\t\t\t\t\t\t\tNondetModel<Double> nondetModel = (NondetModel<Double>) model;\n\t\t\t\t\t\t\tint numChoices = nondetModel.getNumChoices(s);\n\t\t\t\t\t\t\tfor (int k = 0; k < numChoices; k++) {\n\t\t\t\t\t\t\t\tObject mdpAction = nondetModel.getAction(s, k);\n\t\t\t\t\t\t\t\tif (mdpAction == null ? (action.isEmpty()) : mdpAction.equals(action)) {\n\t\t\t\t\t\t\t\t\tdouble rew = rewStr.getReward(i).evaluateDouble(constantValues, statesList.get(s));\n\t\t\t\t\t\t\t\t\tcheckTransitionReward(rew, statesList.get(s), rewStr.getReward(i));\n\t\t\t\t\t\t\t\t\trewards.addToTransitionReward(s, k, rew);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tDTMC<Double> mcModel = (DTMC<Double>) model;\n\t\t\t\t\t\t\tIterator<Map.Entry<Integer, Pair<Double, Object>>> iter = mcModel.getTransitionsAndActionsIterator(s);\n\t\t\t\t\t\t\tint j = 0;\n\t\t\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\t\t\tMap.Entry<Integer, Pair<Double, Object>> e = iter.next();\n\t\t\t\t\t\t\t\tObject mcAction = e.getValue().second;\n\t\t\t\t\t\t\t\tif (mcAction == null ? (action.isEmpty()) : mcAction.equals(action)) {\n\t\t\t\t\t\t\t\t\tdouble rew = rewStr.getReward(i).evaluateDouble(constantValues, statesList.get(s));\n\t\t\t\t\t\t\t\t\tif (expectedRewards) {\n\t\t\t\t\t\t\t\t\t\tdouble rewWeighted = e.getValue().first * rew;\n\t\t\t\t\t\t\t\t\t\trewards.addToStateReward(s, rewWeighted);\n\t\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\t\trewards.addToTransitionReward(s, j, rew);\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tj++;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// State reward\n\t\t\t\t\telse {\n\t\t\t\t\t\tdouble rew = rewStr.getReward(i).evaluateDouble(constantValues, statesList.get(s));\n\t\t\t\t\t\tcheckStateReward(rew, statesList.get(s), rewStr.getReward(i));\n\t\t\t\t\t\trewards.addToStateReward(s, rew);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Construct the rewards for a Markov chain (DTMC or CTMC) from files exported explicitly by PRISM. \n\t * @param mc The DTMC or CTMC\n\t * @param rews The file containing state rewards (ignored if null)\n\t * @param rewt The file containing transition rewards (ignored if null)\n\t */\n\tpublic MCRewards<Double> buildMCRewardsFromPrismExplicit(DTMC<Double> mc, File rews, File rewt) throws PrismException\n\t{\n\t\tString s, ss[];\n\t\tint i, lineNum = 0;\n\t\tdouble reward;\n\t\tStateRewardsArray rewSA = new StateRewardsArray(mc.getNumStates());\n\n\t\tif (rews != null) {\n\t\t\t// Open state rewards file, automatic close\n\t\t\ttry (BufferedReader in = new BufferedReader(new FileReader(rews))) {\n\t\t\t\t// Ignore first line\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum = 1;\n\t\t\t\tif (s == null) {\n\t\t\t\t\tthrow new PrismException(\"Missing first line of state rewards file\");\n\t\t\t\t}\n\t\t\t\t// Go though list of state rewards in file\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t\twhile (s != null) {\n\t\t\t\t\ts = s.trim();\n\t\t\t\t\tif (s.length() > 0) {\n\t\t\t\t\t\tss = s.split(\" \");\n\t\t\t\t\t\ti = Integer.parseInt(ss[0]);\n\t\t\t\t\t\treward = Double.parseDouble(ss[1]);\n\t\t\t\t\t\tcheckStateReward(reward, i, null);\n\t\t\t\t\t\trewSA.setStateReward(i, reward);\n\t\t\t\t\t}\n\t\t\t\t\ts = in.readLine();\n\t\t\t\t\tlineNum++;\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new PrismException(\"Could not read state rewards from file \\\"\" + rews + \"\\\"\" + e);\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Problem in state rewards file (line \" + lineNum + \") for MDP\");\n\t\t\t}\n\t\t}\n\n\t\tif (rewt != null) {\n\t\t\tthrow new PrismNotSupportedException(\"Explicit engine does not yet handle transition rewards for D/CTMCs\");\n\t\t}\n\n\t\treturn rewSA;\n\t}\n\t\n\t/**\n\t * Construct the rewards for an MDP from files exported explicitly by PRISM.\n\t * @param mdp The MDP\n\t * @param rews The file containing state rewards (ignored if null)\n\t * @param rewt The file containing transition rewards (ignored if null)\n\t */\n\tpublic MDPRewards<Double> buildMDPRewardsFromPrismExplicit(MDP<Double> mdp, File rews, File rewt) throws PrismException\n\t{\n\t\tString s, ss[];\n\t\tint i, j, lineNum = 0;\n\t\tdouble reward;\n\t\tMDPRewardsSimple<Double> rs = new MDPRewardsSimple<>(mdp.getNumStates());\n\n\t\tif (rews != null) {\n\t\t\t// Open state rewards file, automatic close\n\t\t\ttry (BufferedReader in = new BufferedReader(new FileReader(rews))) {\n\t\t\t\t// Ignore first line\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum = 1;\n\t\t\t\tif (s == null) {\n\t\t\t\t\tthrow new PrismException(\"Missing first line of state rewards file\");\n\t\t\t\t}\n\t\t\t\t// Go though list of state rewards in file\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t\twhile (s != null) {\n\t\t\t\t\ts = s.trim();\n\t\t\t\t\tif (s.length() > 0) {\n\t\t\t\t\t\tss = s.split(\" \");\n\t\t\t\t\t\ti = Integer.parseInt(ss[0]);\n\t\t\t\t\t\treward = Double.parseDouble(ss[1]);\n\t\t\t\t\t\tcheckStateReward(reward, i, null);\n\t\t\t\t\t\trs.setStateReward(i, reward);\n\t\t\t\t\t}\n\t\t\t\t\ts = in.readLine();\n\t\t\t\t\tlineNum++;\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new PrismException(\"Could not read state rewards from file \\\"\" + rews + \"\\\"\" + e);\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Problem in state rewards file (line \" + lineNum + \") for MDP\");\n\t\t\t}\n\t\t}\n\n\t\tif (rewt != null) {\n\t\t\t// Open transition rewards file, automatic close\n\t\t\ttry (BufferedReader in = new BufferedReader(new FileReader(rewt))) {\n\t\t\t\t// Ignore first line\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum = 1;\n\t\t\t\tif (s == null) {\n\t\t\t\t\tthrow new PrismException(\"Missing first line of transition rewards file\");\n\t\t\t\t}\n\t\t\t\t// Go though list of transition rewards in file\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t\twhile (s != null) {\n\t\t\t\t\ts = s.trim();\n\t\t\t\t\tif (s.length() > 0) {\n\t\t\t\t\t\tss = s.split(\" \");\n\t\t\t\t\t\ti = Integer.parseInt(ss[0]);\n\t\t\t\t\t\tj = Integer.parseInt(ss[1]);\n\t\t\t\t\t\treward = Double.parseDouble(ss[3]);\n\t\t\t\t\t\tcheckTransitionReward(reward, i, null);\n\t\t\t\t\t\trs.setTransitionReward(i, j, reward);\n\t\t\t\t\t}\n\t\t\t\t\ts = in.readLine();\n\t\t\t\t\tlineNum++;\n\t\t\t\t}\n\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new PrismException(\"Could not read transition rewards from file \\\"\" + rewt + \"\\\"\" + e);\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Problem in transition rewards file (line \" + lineNum + \") for MDP\");\n\t\t\t}\n\t\t}\n\n\t\treturn rs;\n\t}\n\n\t/**\n\t * Check that a state reward is legal. Throw an exception if not.\n\t * Optionally, provide a state where the error occurs (as an Object),\n\t * and/or a pointer to where the error occurs syntactically (as an ASTElement) \n\t * @param rew The reward value\n\t * @param eval Evaluator matching the type {@code Value} of the reward value\n\t * @param stateIndex The index of the state, for error reporting (optional)\n\t * @param ast Where the error occurred, for error reporting (optional)\n\t */\n\tprivate <Value> void checkStateReward(Value rew, Evaluator<Value> eval, Object stateIndex, ASTElement ast) throws PrismException\n\t{\n\t\tString error = null;\n\t\t// We omit the check in symbolic (parametric) cases - too expensive\n\t\tif (!eval.isSymbolic()) {\n\t\t\tif (!eval.isFinite(rew)) {\n\t\t\t\terror = \"State reward is not finite\";\n\t\t\t} else if (!allowNegative && !eval.geq(rew, eval.zero())) {\n\t\t\t\terror = \"State reward is negative (\" + rew + \")\";\n\t\t\t}\n\t\t}\n\t\tif (error != null) {\n\t\t\tif (stateIndex != null) {\n\t\t\t\terror += \" at state \" + stateIndex;\n\t\t\t}\n\t\t\tif (ast != null) {\n\t\t\t\tthrow new PrismLangException(error, ast);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(error);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Check that a transition reward is legal. Throw an exception if not.\n\t * Optionally, provide a state where the error occurs (as an Object),\n\t * and/or a pointer to where the error occurs syntactically (as an ASTElement) \n\t * @param rew The reward value\n\t * @param eval Evaluator matching the type {@code Value} of the reward value\n\t * @param stateIndex The index of the state, for error reporting (optional)\n\t * @param ast Where the error occurred, for error reporting (optional)\n\t */\n\tprivate <Value> void checkTransitionReward(Value rew, Evaluator<Value> eval, Object stateIndex, ASTElement ast) throws PrismException\n\t{\n\t\tString error = null;\n\t\t// We omit the check in symbolic (parametric) cases - too expensive\n\t\tif (!eval.isSymbolic()) {\n\t\t\tif (!eval.isFinite(rew)) {\n\t\t\t\terror = \"Transition reward is not finite\";\n\t\t\t} else if (!allowNegative && !eval.geq(rew, eval.zero())) {\n\t\t\t\terror = \"Transition reward is negative (\" + rew + \")\";\n\t\t\t}\n\t\t}\n\t\tif (error != null) {\n\t\t\tif (stateIndex != null) {\n\t\t\t\terror += \" at state \" + stateIndex;\n\t\t\t}\n\t\t\tif (ast != null) {\n\t\t\t\tthrow new PrismLangException(error, ast);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(error);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Check that all state/transition rewards in a Rewards object are legal. Throw an exception if not.\n\t * Optionally, provide a state where the error occurs (as an Object),\n\t * and/or a pointer to where the error occurs syntactically (as an ASTElement)\n\t * @param rewards The rewards\n\t * @param model The model for the rewards\n\t * @param eval Evaluator matching the type {@code Value} of the reward value\n\t */\n\tprivate <Value> Rewards<Value> checkRewardObject(Rewards<Value> rewards, Model<Value> model, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tint numStates = model.getNumStates();\n\t\t// In some cases, we need to create a new Rewards object\n\t\t// in which (Markov chain) transition rewards are converted to expected rewards\n\t\tRewardsExplicit<Value> rewardsRet = null;\n\t\tboolean convertToExpected = !model.getModelType().nondeterministic() && rewards.hasTransitionRewards() && expectedRewards;\n\t\tif (convertToExpected) {\n\t\t\trewardsRet = new RewardsSimple<>(numStates);\n\t\t\trewardsRet.setEvaluator(rewards.getEvaluator());\n\t\t}\n\t\t// State rewards\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tValue rew = rewards.getStateReward(s);\n\t\t\tcheckStateReward(rew, eval, s, null);\n\t\t\tif (convertToExpected) {\n\t\t\t\trewardsRet.setStateReward(s, rew);\n\t\t\t}\n\t\t}\n\t\t// Transition rewards (nondet models)\n\t\tif (model.getModelType().nondeterministic()) {\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tint numChoices = ((NondetModel<?>) model).getNumChoices(s);\n\t\t\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\t\t\tcheckTransitionReward(rewards.getTransitionReward(s, i), eval, s, null);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Transition rewards (Markov chain like models)\n\t\telse {\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tif (!convertToExpected) {\n\t\t\t\t\tint numTrans = model.getNumTransitions(s);\n\t\t\t\t\tfor (int i = 0; i < numTrans; i++) {\n\t\t\t\t\t\tcheckTransitionReward(rewards.getTransitionReward(s, i), eval, s, null);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tDTMC<Value> mcModel = (DTMC<Value>) model;\n\t\t\t\t\tIterator<Map.Entry<Integer, Value>> iter = mcModel.getTransitionsIterator(s);\n\t\t\t\t\tint i = 0;\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Value> e = iter.next();\n\t\t\t\t\t\tValue rew = rewards.getTransitionReward(s, i);\n\t\t\t\t\t\tcheckTransitionReward(rew, eval, s, null);\n\t\t\t\t\t\tif (rewards.getEvaluator().isZero(rew)) {\n\t\t\t\t\t\t\ti++;\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tValue rewWeighted = rewards.getEvaluator().multiply(e.getValue(), rew);\n\t\t\t\t\t\trewardsRet.addToStateReward(s, rewWeighted);\n\t\t\t\t\t\ti++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn convertToExpected ? rewardsRet : rewards;\n\t}\n\n\t/**\n\t * Check that a (double-valued) state reward is legal. Throw an exception if not.\n\t * Optionally, provide a state where the error occurs (as an Object),\n\t * and/or a pointer to where the error occurs syntactically (as an ASTElement) \n\t * @param rew The reward value\n\t * @param stateIndex The index of the state, for error reporting (optional)\n\t * @param ast Where the error occurred, for error reporting (optional)\n\t */\n\tprivate <Value> void checkStateReward(double rew, Object stateIndex, ASTElement ast) throws PrismException\n\t{\n\t\tcheckStateReward(rew, Evaluator.forDouble(), stateIndex, ast);\n\t}\n\n\t/**\n\t * Check that a (double-valued) transition reward is legal. Throw an exception if not.\n\t * Optionally, provide a state where the error occurs (as an Object),\n\t * and/or a pointer to where the error occurs syntactically (as an ASTElement) \n\t * @param rew The reward value\n\t * @param stateIndex The index of the state, for error reporting (optional)\n\t * @param ast Where the error occurred, for error reporting (optional)\n\t */\n\tprivate <Value> void checkTransitionReward(double rew, Object stateIndex, ASTElement ast) throws PrismException\n\t{\n\t\tcheckTransitionReward(rew, Evaluator.forDouble(), stateIndex, ast);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/MCRewards.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.Product;\n\n/**\n * Classes that provide (read) access to explicit-state rewards for a Markov chain (DTMC/CTMC).\n * This is no longer needed - just use {@link Rewards}.\n */\npublic interface MCRewards<Value> extends Rewards<Value>\n{\n\t@Override\n\tMCRewards<Value> liftFromModel(Product<?> product);\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/MCRewardsFromMDPRewards.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.Product;\nimport prism.Evaluator;\n\n\n/**\n * Explicit-state representation of a DTMC rewards structure, constructed (implicitly)\n * from an MDP rewards structure and a memoryless deterministic strategy, specified as an array of integer indices.\n * This class is read-only: most of data is pointers to other model info.\n */\npublic class MCRewardsFromMDPRewards<Value> extends RewardsExplicit<Value> implements MCRewards<Value>\n{\n\t// MDP rewards\n\tprotected MDPRewards<Value> mdpRewards;\n\t// Strategy (array of choice indices; -1 denotes no choice)\n\tprotected int[] strat;\n\n\t/**\n\t * Constructor: create from MDP rewards and memoryless adversary.\n\t */\n\tpublic MCRewardsFromMDPRewards(MDPRewards<Value> mdpRewards, int[] strat)\n\t{\n\t\tthis.mdpRewards = mdpRewards;\n\t\tthis.strat = strat;\n\t}\n\n\t@Override\n\tpublic Evaluator<Value> getEvaluator()\n\t{\n\t\treturn mdpRewards.getEvaluator();\n\t}\n\n\t@Override\n\tpublic boolean hasTransitionRewards()\n\t{\n\t\t// Only state rewards\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic Value getStateReward(int s)\n\t{\n\t\t// For now, state/transition rewards from MDP are both put into state reward\n\t\t// This works fine for cumulative rewards, but not instantaneous ones\n\t\treturn getEvaluator().add(mdpRewards.getStateReward(s), mdpRewards.getTransitionReward(s, strat[s]));\n\t}\n\n\t@Override\n\tpublic MCRewardsFromMDPRewards<Value> liftFromModel(Product<?> product)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/MDPRewards.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.Product;\n\n/**\n * Classes that provide (read) access to explicit-state rewards for an MDP.\n * This is no longer needed - just use {@link Rewards}.\n */\npublic interface MDPRewards<Value> extends Rewards<Value>\n{\n\t@Override\n\tMDPRewards<Value> liftFromModel(Product<?> product);\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/MDPRewardsSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport java.util.function.Function;\n\nimport explicit.NondetModel;\nimport prism.Evaluator;\n\n/**\n * Simple explicit-state storage of rewards for an MDP.\n * Like the related class MDPSimple, this is not especially efficient, but mutable (in terms of size).\n * This is no longer needed - just use {@link RewardsSimple}.\n */\npublic class MDPRewardsSimple<Value> extends RewardsSimple<Value>\n{\n\t/**\n\t * Constructor: all zero rewards.\n\t * @param numStates Number of states\n\t */\n\tpublic MDPRewardsSimple(int numStates)\n\t{\n\t\tsuper(numStates);\n\t}\n\n\t/**\n\t * Copy constructor\n\t * @param rews Rewards to copy\n\t */\n\tpublic MDPRewardsSimple(MDPRewardsSimple<Value> rews)\n\t{\n\t\tsuper(rews);\n\t}\n\n\t/**\n\t * Copy constructor.\n\t * @param rews Rewards to copy\n\t * @param model Associated model (needed for sizes)\n\t */\n\tpublic MDPRewardsSimple(MDPRewards<Value> rews, NondetModel<?> model)\n\t{\n\t\tthis(rews, model, r -> r);\n\t}\n\n\t/**\n\t * Copy constructor, mapping reward values using the provided function.\n\t * Since the type changes (T -> Value), an Evaluator for Value must be given.\n\t * @param rews Rewards to copy\n\t * @param model Associated model (needed for sizes)\n\t * @param rewMap Reward value map\n\t */\n\tpublic MDPRewardsSimple(MDPRewards<Value> rews, NondetModel<?> model, Function<? super Value, ? extends Value> rewMap)\n\t{\n\t\tthis(rews, model, rewMap, rews.getEvaluator());\n\t}\n\n\t/**\n\t * Copy constructor, mapping reward values using the provided function.\n\t * Since the type changes (T -> Value), an Evaluator for Value must be given.\n\t * @param rews Rewards to copy\n\t * @param model Associated model (needed for sizes)\n\t * @param rewMap Reward value map\n\t * @param eval Evaluator for Value\n\t */\n\tpublic <T> MDPRewardsSimple(MDPRewards<T> rews, NondetModel<?> model, Function<? super T, ? extends Value> rewMap, Evaluator<Value> eval)\n\t{\n\t\tsuper(rews, model, rewMap, eval);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/Rewards.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.Product;\nimport prism.Evaluator;\n\n/**\n * Interface implemented by all reward classes.\n */\npublic interface Rewards<Value>\n{\n\t/**\n\t * Get an Evaluator for the reward values stored in this class.\n\t * This is needed, for example, to compute sums, check for equality to 0/1, etc.\n\t * A default implementation provides an evaluator for the (usual) case when Value is Double.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tdefault Evaluator<Value> getEvaluator()\n\t{\n\t\treturn (Evaluator<Value>) Evaluator.forDouble();\n\t}\n\n\t/**\n\t * Returns true if this reward structure has state rewards.\n\t * This method can sometimes return true even if there are none,\n\t * but a value of false always indicates that none are present.\n\t */\n\tdefault boolean hasStateRewards()\n\t{\n\t\t// Safe to assume true by default\n\t\treturn true;\n\t}\n\n\t/**\n\t * Returns true if this reward structure has transition rewards.\n\t * This method can sometimes return true even if there are none,\n\t * but a value of false always indicates that none are present.\n\t */\n\tdefault boolean hasTransitionRewards()\n\t{\n\t\t// Safe to assume true by default\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get the state reward for state {@code s}.\n\t */\n\tdefault Value getStateReward(int s)\n\t{\n\t\t// Default implementation assumes all zero rewards\n\t\treturn getEvaluator().zero();\n\t}\n\n\t/**\n\t * Get the transition reward with index {@code i} from state {@code s}.\n\t * For a nondeterministic model, this refers to the {@code i}th choice,\n\t * for a Markov chain like model, it refers to the {@code i}th transition.\n\t */\n\tdefault Value getTransitionReward(int s, int i)\n\t{\n\t\t// Default implementation assumes all zero rewards\n\t\treturn getEvaluator().zero();\n\t}\n\n\t/**\n\t * Create a new reward structure that lifts this one such that it is defined over states of a\n\t * model that is a product of the one that this reward structure is defined over.\n\t */\n\tRewards<Value> liftFromModel(Product<?> product);\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/Rewards2RewardGenerator.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2019-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.DTMC;\nimport explicit.IDTMC;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport parser.State;\nimport prism.Evaluator;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.RewardGenerator;\nimport prism.RewardInfo;\n\nimport java.util.List;\n\n/**\n * Base class for exposing {@link Rewards} as a {@link RewardGenerator}.\n * Also needed are: syntactic information about reward (e.g., names),\n * provided as a {@link RewardInfo}; the {@link Model} corresponding\n * to the {@link Rewards} ;and an {@link Evaluator} for reward values.\n * The latter three are provided when this class is constructed;\n * the rewards themselves are provided by subclasses implementing\n * {@link #getTheRewardObject(int)}, allowing them to be built lazily.\n */\npublic abstract class Rewards2RewardGenerator<Value> implements RewardGenerator<Value>\n{\n\t// Reward info from importer\n\tprotected RewardInfo rewardInfo;\n\t// Model that rewards are for\n\tprotected Model<Value> model;\n\t// Evaluator for reward values\n\tprotected Evaluator<Value> eval;\n\t// State list (optionally)\n\tprotected List<State> statesList;\n\n\t/**\n\t * Construct a Rewards2RewardGenerator object, storing the reward info and model.\n\t * The evaluator for rewards is extracted from the model.\n\t */\n\tpublic Rewards2RewardGenerator(RewardGenerator<?> rewardInfo, Model<Value> model) throws PrismException\n\t{\n\t\tthis(rewardInfo, model, model.getEvaluator());\n\t}\n\n\t/**\n\t * Construct a Rewards2RewardGenerator object, storing the reward info, model and evaluator.\n\t */\n\tpublic Rewards2RewardGenerator(RewardInfo rewardInfo, Model<Value> model, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tthis.rewardInfo = rewardInfo;\n\t\tthis.model = model;\n\t\tthis.eval = eval;\n\t\t// Also store the model's states list. If present, it can be used\n\t\t// to support reward look up by State, rather than just state index.\n\t\tstatesList = model.getStatesList();\n\t}\n\n\t/**\n\t * Provide a {@link Rewards} object representing the {@code r}th reward structure\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t */\n\tpublic abstract Rewards<Value> getTheRewardObject(int r) throws PrismException;\n\n\t// Methods to implement RewardGenerator\n\n\t@Override\n\tpublic Evaluator<Value> getRewardEvaluator()\n\t{\n\t\treturn eval;\n\t}\n\n\t@Override\n\tpublic List<String> getRewardStructNames()\n\t{\n\t\treturn rewardInfo.getRewardStructNames();\n\t}\n\n\t@Override\n\tpublic int getNumRewardStructs()\n\t{\n\t\treturn rewardInfo.getNumRewardStructs();\n\t}\n\n\t@Override\n\tpublic boolean rewardStructHasTransitionRewards(int r)\n\t{\n\t\treturn rewardInfo.rewardStructHasTransitionRewards(r);\n\t}\n\n\t@Override\n\tpublic boolean isRewardLookupSupported(RewardLookup lookup)\n\t{\n\t\treturn (lookup == RewardLookup.BY_STATE_INDEX) || (lookup == RewardLookup.BY_STATE && statesList != null) || (lookup == RewardLookup.BY_REWARD_OBJECT);\n\t}\n\n\t@Override\n\tpublic Value getStateReward(int r, State state, boolean allowNegative) throws PrismException\n\t{\n\t\tif (statesList == null) {\n\t\t\tthrow new PrismException(\"Reward lookup by State not possible since state list is missing\");\n\t\t}\n\t\tint s = statesList.indexOf(state);\n\t\tif (s == -1) {\n\t\t\tthrow new PrismException(\"Unknown state \" + state);\n\t\t}\n\t\treturn getStateReward(r, s, allowNegative);\n\t}\n\n\t@Override\n\tpublic Value getStateReward(int r, int s, boolean allowNegative) throws PrismException\n\t{\n\t\tValue rew = getRewardObject(r).getStateReward(s);\n\t\tif (!allowNegative && !eval.geq(rew, eval.zero())) {\n\t\t\tthrow new PrismException(\"Reward is negative (\" + rew + \") at state \" + s);\n\t\t}\n\t\treturn rew;\n\t}\n\n\t@Override\n\tpublic Value getStateActionReward(int r, State state, Object action, boolean allowNegative) throws PrismException\n\t{\n\t\tif (statesList == null) {\n\t\t\tthrow new PrismException(\"Reward lookup by State not possible since state list is missing\");\n\t\t}\n\t\tint s = statesList.indexOf(state);\n\t\tif (s == -1) {\n\t\t\tthrow new PrismException(\"Unknown state \" + state);\n\t\t}\n\t\treturn getStateActionReward(r, s, action, allowNegative);\n\t}\n\n\t@Override\n\tpublic Value getStateActionReward(int r, int s, Object action, boolean allowNegative) throws PrismException\n\t{\n\t\tint i;\n\t\tif (model instanceof NondetModel) {\n\t\t\ti = ((NondetModel<Value>) model).getChoiceByAction(s, action);\n\t\t} else if (model instanceof DTMC) {\n\t\t\ti = ((DTMC<Value>) model).getTransitionByAction(s, action);\n\t\t} else if (model instanceof IDTMC) {\n\t\t\ti = ((IDTMC<Value>) model).getIntervalModel().getTransitionByAction(s, action);\n\t\t} else {\n\t\t\tthrow new PrismException(\"State-action reward lookup not supported for model type \" + model.getModelType() + \"s\");\n\t\t}\n\t\tValue rew = getRewardObject(r).getTransitionReward(s, i);\n\t\tif (!allowNegative && !eval.geq(rew, eval.zero())) {\n\t\t\tthrow new PrismException(\"Reward is negative (\" + rew + \") at state \" + s);\n\t\t}\n\t\treturn rew;\n\t}\n\n\t@Override\n\tpublic Rewards<Value> getRewardObject(int r) throws PrismException\n\t{\n\t\treturn getTheRewardObject(r);\n\t}\n\n\t@Override\n\tpublic Model<Value> getRewardObjectModel() throws PrismException\n\t{\n\t\treturn model;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/RewardsExplicit.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.Product;\nimport prism.Evaluator;\n\n/**\n * Base class for mutable reward classes.\n */\npublic abstract class RewardsExplicit<Value> implements Rewards<Value>, MCRewards<Value>, MDPRewards<Value>, STPGRewards<Value>\n{\n\t/** Evaluator for manipulating reward values stored here (of type {@code Value}) */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected Evaluator<Value> eval = (Evaluator<Value>) Evaluator.forDouble();\n\n\t// Mutators\n\n\t/**\n\t * Set the {@link Evaluator} object for manipulating reward values\n\t */\n\tpublic void setEvaluator(Evaluator<Value> eval)\n\t{\n\t\tthis.eval = eval;\n\t}\n\n\t/**\n\t * Set the state reward for state {@code s} to {@code r}.\n\t */\n\tpublic void setStateReward(int s, Value r)\n\t{\n\t\tthrow new UnsupportedOperationException(\"Setting of state rewards not supported\");\n\t}\n\n\t/**\n\t * Add {@code r} to the state reward for state {@code s}.\n\t */\n\tpublic void addToStateReward(int s, Value r)\n\t{\n\t\tsetStateReward(s, getEvaluator().add(getStateReward(s), r));\n\t}\n\n\t/**\n\t * Set the transition reward with index {@code i} of state {@code s} to {@code r}.\n\t * For a nondeterministic model, this refers to the {@code i}th choice,\n\t * for a Markov chain like model, it refers to the {@code i}th transition.\n\t */\n\tpublic void setTransitionReward(int s, int i, Value r)\n\t{\n\t\tthrow new UnsupportedOperationException(\"Setting of transition rewards not supported\");\n\t}\n\n\t/**\n\t * Add {@code r} to the transition reward with index {@code i} of state {@code s}.\n\t * For a nondeterministic model, this refers to the {@code i}th choice,\n\t * for a Markov chain like model, it refers to the {@code i}th transition.\n\t */\n\tpublic void addToTransitionReward(int s, int i, Value r)\n\t{\n\t\tsetTransitionReward(s, i, getEvaluator().add(getTransitionReward(s, i), r));\n\t}\n\n\t// Accessors\n\n\t@Override\n\tpublic Evaluator<Value> getEvaluator()\n\t{\n\t\treturn eval;\n\t}\n\n\t@Override\n\tpublic abstract RewardsExplicit<Value> liftFromModel(Product<?> product);\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/RewardsSimple.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.ListNestedSimple;\nimport explicit.ListSimple;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport explicit.Product;\nimport prism.Evaluator;\n\nimport java.util.function.Function;\n\n/**\n * Simple explicit-state storage of rewards for a model.\n * Like the related class *Simple classes, this is not especially efficient, but mutable.\n */\npublic class RewardsSimple<Value> extends RewardsExplicit<Value>\n{\n\t/** Number of states */\n\tprotected int numStates;\n\t/** State rewards */\n\tprotected ListSimple<Value> stateRewards;\n\t/** Transition rewards */\n\tprotected ListNestedSimple<Value> transRewards;\n\n\t/**\n\t * Constructor: all zero rewards.\n\t * @param numStates Number of states\n\t */\n\tpublic RewardsSimple(int numStates)\n\t{\n\t\tthis.numStates = numStates;\n\t\tstateRewards = new ListSimple<>(getEvaluator().zero(), getEvaluator()::isZero);\n\t\ttransRewards = new ListNestedSimple<>(getEvaluator().zero(), getEvaluator()::isZero);\n\t}\n\n\t/**\n\t * Copy constructor\n\t * @param rews RewardsSimple to copy\n\t */\n\tpublic RewardsSimple(RewardsSimple<Value> rews)\n\t{\n\t\tnumStates = rews.numStates;\n\t\tstateRewards = new ListSimple<>(rews.stateRewards);\n\t\ttransRewards = new ListNestedSimple<>(rews.transRewards);\n\t\tsetEvaluator(rews.getEvaluator());\n\t}\n\n\t/**\n\t * Copy constructor, mapping reward values using the provided function.\n\t * Since the type changes (T -> Value), an Evaluator for Value must be given.\n\t * @param rews Rewards to copy\n\t * @param model Associated model (needed for sizes)\n\t * @param rewMap Reward value map\n\t * @param eval Evaluator for Value\n\t */\n\tpublic <T> RewardsSimple(Rewards<T> rews, Model<?> model, Function<? super T, ? extends Value> rewMap, Evaluator<Value> eval)\n\t{\n\t\tnumStates = model.getNumStates();\n\t\tstateRewards = new ListSimple<>(eval.zero(), eval::isZero);\n\t\tif (rews.hasStateRewards()) {\n\t\t\tfor (int s = numStates - 1; s >= 0; s--) {\n\t\t\t\tstateRewards.setValue(s, rewMap.apply(rews.getStateReward(s)));\n\t\t\t}\n\t\t}\n\t\ttransRewards = new ListNestedSimple<>(eval.zero(), eval::isZero);\n\t\tif (rews.hasTransitionRewards()) {\n\t\t\tfor (int s = numStates - 1; s >= 0; s--) {\n\t\t\t\tint n;\n\t\t\t\tif (model.getModelType().nondeterministic()) {\n\t\t\t\t\tn = ((NondetModel<?>) model).getNumChoices(s);\n\t\t\t\t} else {\n\t\t\t\t\tn = model.getNumTransitions(s);\n\t\t\t\t}\n\t\t\t\tfor (int j = n; j >= 0; j--) {\n\t\t\t\t\ttransRewards.setValue(s, j, rewMap.apply(rews.getTransitionReward(s, j)));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tsetEvaluator(eval);\n\t}\n\n\t// Mutators\n\n\t@Override\n\tpublic void setEvaluator(Evaluator<Value> eval)\n\t{\n\t\tsuper.setEvaluator(eval);\n\t\tstateRewards.setZero(getEvaluator().zero(), getEvaluator()::isZero);\n\t\ttransRewards.setZero(getEvaluator().zero(), getEvaluator()::isZero);\n\t}\n\n\t@Override\n\tpublic void setStateReward(int s, Value r)\n\t{\n\t\tstateRewards.setValue(s, r);\n\t}\n\n\t@Override\n\tpublic void setTransitionReward(int s, int i, Value r)\n\t{\n\t\ttransRewards.setValue(s, i, r);\n\t}\n\n\t/**\n\t * Clear all rewards for state s.\n\t */\n\tpublic void clearRewards(int s)\n\t{\n\t\tsetStateReward(s, getEvaluator().zero());\n\t\ttransRewards.clear(s);\n\t}\n\n\t// Accessors\n\n\t@Override\n\tpublic boolean hasStateRewards()\n\t{\n\t\treturn !stateRewards.allZero();\n\t}\n\n\t@Override\n\tpublic boolean hasTransitionRewards()\n\t{\n\t\treturn !transRewards.allZero();\n\t}\n\n\t@Override\n\tpublic Value getStateReward(int s)\n\t{\n\t\treturn stateRewards.getValue(s);\n\t}\n\n\t@Override\n\tpublic Value getTransitionReward(int s, int i)\n\t{\n\t\treturn transRewards.getValue(s, i);\n\t}\n\n\t@Override\n\tpublic RewardsSimple<Value> liftFromModel(Product<?> product)\n\t{\n\t\tModel<?> modelProd = product.getProductModel();\n\t\tint numStatesProd = modelProd.getNumStates();\n\t\tRewardsSimple<Value> rewardsProd = new RewardsSimple<>(numStatesProd);\n\t\trewardsProd.setEvaluator(getEvaluator());\n\t\tif (!stateRewards.allZero()) {\n\t\t\tfor (int s = 0; s < numStatesProd; s++) {\n\t\t\t\trewardsProd.setStateReward(s, stateRewards.getValue(product.getModelState(s)));\n\t\t\t}\n\t\t}\n\t\tif (!transRewards.allZero()) {\n\t\t\tfor (int s = 0; s < numStatesProd; s++) {\n\t\t\t\trewardsProd.transRewards.copyFrom(s, transRewards, product.getModelState(s));\n\t\t\t}\n\t\t}\n\t\treturn rewardsProd;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"st: \" + this.stateRewards + \"; tr: \" + this.transRewards;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/STPGRewards.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.Model;\nimport explicit.Product;\n\n/**\n * Classes that provide (read) access to explicit-state rewards for an STPG.\n * This is no longer needed - just use {@link Rewards}.\n */\npublic interface STPGRewards<Value> extends MDPRewards<Value>\n{\n\t@Override\n\tSTPGRewards<Value> liftFromModel(Product<?> product);\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/STPGRewardsNestedSimple.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage explicit.rewards;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport explicit.Model;\nimport explicit.Product;\n\n/**\n * Variant of STPGRewards storage with support for nested transitions,\n * as found in the STPGAbstrSimple model class. Not currently used.\n */\npublic class STPGRewardsNestedSimple<Value> extends MDPRewardsSimple<Value> implements STPGRewards<Value>\n{\n\t/** Nested transition rewards */\n\tprotected List<List<List<Value>>> nestedTransRewards;\n\n\t/**\n\t * Constructor: all zero rewards.\n\t * @param numStates Number of states\n\t */\n\tpublic STPGRewardsNestedSimple(int numStates)\n\t{\n\t\tsuper(numStates);\n\t\t// Initially list is just null (denoting all 0)\n\t\tnestedTransRewards = null;\n\t}\n\n\t/**\n\t * Constructor: copy MDP rewards, other rewards zero\n\t * @param rews MPD rewards to copy\n\t */\n\tpublic STPGRewardsNestedSimple(MDPRewardsSimple<Value> rews)\n\t{\n\t\tsuper(rews);\n\t\t// Initially list is just null (denoting all 0)\n\t\tnestedTransRewards = null;\n\t}\n\n\t// Mutators\n\n\t/**\n\t * Set the reward for the {@code i},{@code j}th nested transition of state {@code s} to {@code r}.\n\t */\n\tpublic void setNestedTransitionReward(int s, int i, int j, Value r)\n\t{\n\t\tList<List<Value>> list1;\n\t\tList<Value> list2;\n\t\t// Nothing to do for zero reward\n\t\tif (getEvaluator().isZero(r))\n\t\t\treturn;\n\t\t// If no rewards array created yet, create it\n\t\tif (nestedTransRewards == null) {\n\t\t\tnestedTransRewards = new ArrayList<List<List<Value>>>(numStates);\n\t\t\tfor (int k = 0; k < numStates; k++)\n\t\t\t\tnestedTransRewards.add(null);\n\t\t}\n\t\t// If no rewards for state s yet, create list1\n\t\tif (nestedTransRewards.get(s) == null) {\n\t\t\tlist1 = new ArrayList<List<Value>>();\n\t\t\tnestedTransRewards.set(s, list1);\n\t\t} else {\n\t\t\tlist1 = nestedTransRewards.get(s);\n\t\t}\n\t\t// If list1 not big enough, extend\n\t\tint n1 = i - list1.size() + 1;\n\t\tif (n1 > 0) {\n\t\t\tfor (int k = 0; k < n1; k++) {\n\t\t\t\tlist1.add(null);\n\t\t\t}\n\t\t}\n\t\t// If no rewards for state s, choice i, create list2\n\t\tif (list1.get(i) == null) {\n\t\t\tlist2 = new ArrayList<Value>();\n\t\t\tlist1.set(i, list2);\n\t\t} else {\n\t\t\tlist2 = list1.get(i);\n\t\t}\n\t\t// If list2 not big enough, extend\n\t\tint n2 = j - list2.size() + 1;\n\t\tif (n2 > 0) {\n\t\t\tfor (int k = 0; k < n2; k++) {\n\t\t\t\tlist2.add(null);\n\t\t\t}\n\t\t}\n\t\t// Set reward\n\t\tlist2.set(j, r);\n\t}\n\n\t/**\n\t * Clear all rewards for state s.\n\t */\n\tpublic void clearRewards(int s)\n\t{\n\t\tsuper.clearRewards(s);\n\t\tif (nestedTransRewards != null && nestedTransRewards.size() > s) {\n\t\t\tnestedTransRewards.set(s, null);\n\t\t}\n\t}\n\n\t// Accessors\n\n\tpublic Value getNestedTransitionReward(int s, int i, int j)\n\t{\n\t\tList<List<Value>> list1;\n\t\tList<Value> list2;\n\t\tif (nestedTransRewards == null || (list1 = nestedTransRewards.get(s)) == null)\n\t\t\treturn getEvaluator().zero();\n\t\tif (list1.size() <= i || (list2 = list1.get(i)) == null)\n\t\t\treturn getEvaluator().zero();\n\t\tif (list2.size() <= j)\n\t\t\treturn getEvaluator().zero();\n\t\treturn list2.get(j);\n\t}\n\n\t// Converters\n\n\t@Override\n\tpublic STPGRewardsNestedSimple<Value> liftFromModel(Product<?> product)\n\t{\n\t\t// Lift MDP part\n\t\tMDPRewardsSimple<Value> rewardsProdMDP = (MDPRewardsSimple<Value>) ((MDPRewardsSimple<Value>) this).liftFromModel(product);\n\t\tSTPGRewardsNestedSimple<Value> rewardsProd = new STPGRewardsNestedSimple<>(rewardsProdMDP);\n\t\t// Lift nested transition rewards\n\t\tModel<?> modelProd = product.getProductModel();\n\t\tint numStatesProd = modelProd.getNumStates();\n\t\tif (nestedTransRewards != null) {\n\t\t\tfor (int s = 0; s < numStatesProd; s++) {\n\t\t\t\tList<List<Value>> list1 = nestedTransRewards.get(product.getModelState(s));\n\t\t\t\tif (list1 != null) {\n\t\t\t\t\tint n1 = list1.size();\n\t\t\t\t\tfor (int i = 0; i < n1; i++) {\n\t\t\t\t\t\tList<Value> list2 = list1.get(i);\n\t\t\t\t\t\tint n2 = list2.size();\n\t\t\t\t\t\tfor (int j = 0; j < n2; j++) {\n\t\t\t\t\t\t\trewardsProd.setNestedTransitionReward(s, i, j, list2.get(j));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn rewardsProd;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn super.toString() + \"; ntr:\" + nestedTransRewards;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/STPGRewardsSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\n/**\n * Simple explicit-state storage of rewards for an STPG.\n * This is no longer needed - just use {@link RewardsSimple}.\n */\npublic class STPGRewardsSimple<Value> extends RewardsSimple<Value>\n{\n\t/**\n\t * Constructor: all zero rewards.\n\t * @param numStates Number of states\n\t */\n\tpublic STPGRewardsSimple(int numStates)\n\t{\n\t\tsuper(numStates);\n\t}\n\n\t/**\n\t * Constructor: copy MDP rewards\n\t * @param rews MPD rewards to copy\n\t */\n\tpublic STPGRewardsSimple(MDPRewardsSimple<Value> rews)\n\t{\n\t\tsuper(rews);\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/StateRewardsArray.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.Model;\nimport explicit.Product;\n\nimport java.util.Arrays;\n\n/**\n * Explicit-state storage of just state rewards (as an array).\n */\npublic class StateRewardsArray extends RewardsExplicit<Double>\n{\n\t/** Array of state rewards **/\n\tprotected double stateRewards[];\n\n\t/**\n\t * Constructor: all zero rewards.\n\t * @param numStates Number of states\n\t */\n\tpublic StateRewardsArray(int numStates)\n\t{\n\t\t// Default to all zero\n\t\tstateRewards = new double[numStates];\n\t}\n\n\t/**\n\t * Copy constructor\n\t * @param rews Rewards to copy\n\t */\n\tpublic StateRewardsArray(StateRewardsArray rews)\n\t{\n\t\tstateRewards = Arrays.copyOf(rews.stateRewards, rews.stateRewards.length);\n\t}\n\n\t// Mutators\n\t\n\t/**\n\t * Set the reward for state {@code s} to {@code r}.\n\t */\n\tpublic void setStateReward(int s, Double r)\n\t{\n\t\tstateRewards[s] = r;\n\t}\n\t\n\t/**\n\t * Add {@code r} to the state reward for state {@code s} .\n\t */\n\tpublic void addToStateReward(int s, Double r)\n\t{\n\t\tstateRewards[s] += r;\n\t}\n\t\n\t// Accessors\n\n\t@Override\n\tpublic boolean hasTransitionRewards()\n\t{\n\t\t// Only state rewards\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic Double getStateReward(int s)\n\t{\n\t\treturn stateRewards[s];\n\t}\n\t\n\t@Override\n\tpublic StateRewardsArray liftFromModel(Product<?> product)\n\t{\n\t\tModel<?> modelProd = product.getProductModel();\n\t\tint numStatesProd = modelProd.getNumStates();\n\t\tStateRewardsArray rewardsProd = new StateRewardsArray(numStatesProd);\n\t\tfor (int s = 0; s < numStatesProd; s++) {\n\t\t\trewardsProd.setStateReward(s, stateRewards[product.getModelState(s)]);\n\t\t}\n\t\treturn rewardsProd;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/StateRewardsConstant.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport explicit.Product;\n\n/**\n * Explicit-state storage of constant state rewards.\n */\npublic class StateRewardsConstant<Value> extends RewardsExplicit<Value>\n{\n\tprotected Value stateReward;\n\n\t/**\n\t * Constructor: all rewards equal to {@code r}\n\t */\n\tpublic StateRewardsConstant(Value r)\n\t{\n\t\tstateReward = r;\n\t}\n\n\t// Accessors\n\n\t@Override\n\tpublic boolean hasTransitionRewards()\n\t{\n\t\t// Only state rewards\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic Value getStateReward(int s)\n\t{\n\t\treturn stateReward;\n\t}\n\n\t@Override\n\tpublic StateRewardsConstant<Value> liftFromModel(Product<?> product)\n\t{\n\t\tStateRewardsConstant<Value> rews = new StateRewardsConstant<>(stateReward);\n\t\trews.setEvaluator(getEvaluator());\n\t\treturn rews;\n\t}\n}\n"
  },
  {
    "path": "prism/src/explicit/rewards/StateRewardsSimple.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage explicit.rewards;\n\nimport java.util.function.Function;\n\nimport explicit.Model;\nimport prism.Evaluator;\n\n/**\n * Explicit-state storage of just state rewards (mutable).\n */\npublic class StateRewardsSimple<Value> extends RewardsSimple<Value>\n{\n\t/**\n\t * Constructor: all zero rewards.\n\t */\n\tpublic StateRewardsSimple()\n\t{\n\t\tsuper(0);\n\t}\n\n\t/**\n\t * Copy constructor\n\t * @param rews Rewards to copy\n\t */\n\tpublic StateRewardsSimple(StateRewardsSimple<Value> rews)\n\t{\n\t\tsuper(rews);\n\t}\n\n\t/**\n\t * Copy constructor.\n\t * @param rews Rewards to copy\n\t * @param model Associated model (needed for sizes)\n\t */\n\tpublic StateRewardsSimple(StateRewardsSimple<Value> rews, Model<?> model)\n\t{\n\t\tthis(rews, model, r -> r);\n\t}\n\n\t/**\n\t * Copy constructor, mapping reward values using the provided function.\n\t * Since the type changes (T -> Value), an Evaluator for Value must be given.\n\t * @param rews Rewards to copy\n\t * @param model Associated model (needed for sizes)\n\t * @param rewMap Reward value map\n\t */\n\tpublic StateRewardsSimple(StateRewardsSimple<Value> rews, Model<?> model, Function<? super Value, ? extends Value> rewMap)\n\t{\n\t\tthis(rews, model, rewMap, rews.getEvaluator());\n\t}\n\n\t/**\n\t * Copy constructor, mapping reward values using the provided function.\n\t * Since the type changes (T -> Value), an Evaluator for Value must be given.\n\t * @param rews Rewards to copy\n\t * @param model Associated model (needed for sizes)\n\t * @param rewMap Reward value map\n\t * @param eval Evaluator for Value\n\t */\n\tpublic <T> StateRewardsSimple(StateRewardsSimple<T> rews, Model<?> model, Function<? super T, ? extends Value> rewMap, Evaluator<Value> eval)\n\t{\n\t\tsuper(rews, model, rewMap, eval);\n\t}\n\n\t@Override\n\tpublic void setTransitionReward(int s, int i, Value r)\n\t{\n\t\tthrow new UnsupportedOperationException(\"StateRewardsSimple does not support transition rewards\");\n\t}\n\n\t@Override\n\tpublic boolean hasTransitionRewards()\n\t{\n\t\t// Only state rewards\n\t\treturn false;\n\t}\n}\n"
  },
  {
    "path": "prism/src/hybrid/PH_JOR.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <new>\n#include <memory>\n\n// local prototypes\nstatic void jor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose);\nstatic void jor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void jor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Jacobi/JOR\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1JOR\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble omega\t\t// omega (over-relaxation parameter)\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_d, compact_b;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *diags_vec = NULL, *b_vec = NULL, *tmpsoln = NULL;\n\tDistVector *diags_dist = NULL, *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tdouble x, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true, transpose);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false, transpose);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix (and then setting to 1 if sum is 0)\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = hdd_negative_row_sums(hddm, n, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete[] b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, init, rvars, num_rvars, odd);\n\t\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PH_JOR (\");\n\t\ttitle += (omega == 1.0)?\"Jacobi\": (\"JOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// matrix multiply\n\t\t\n\t\t// initialise vector\n\t\tif (b == NULL) {\n\t\t\tfor (i = 0; i < n; i++) { soln2[i] = 0.0; }\n\t\t} else if (!compact_b) {\n\t\t\tfor (i = 0; i < n; i++) { soln2[i] = b_vec[i]; }\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) { soln2[i] = b_dist->dist[b_dist->ptrs[i]]; }\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tjor_rec(hdd, 0, 0, 0, transpose);\n\t\t\n\t\t// divide by diagonal\n\t\tif (!compact_d) {\n\t\t\tfor (i = 0; i < n; i++) { soln2[i] *= diags_vec[i]; }\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) { soln2[i] *= diags_dist->dist[diags_dist->ptrs[i]]; }\n\t\t}\n\t\t\n\t\t// do over-relaxation if necessary\n\t\tif (omega != 1) {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tsoln2[i] = ((1-omega) * soln[i]) + (omega * soln2[i]);\n\t\t\t}\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln2, n, 0);\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln, soln2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", (omega == 1.0)?\"Jacobi\":\"JOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (hddm) delete hddm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void jor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tjor_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tjor_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] -= soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tif (!transpose) {\n\t\t\tjor_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tjor_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, transpose);\n\t\t} else {\n\t\t\tjor_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tjor_rec(e->type.kids.t, level+1, row_offset+e->off.val, col_offset, transpose);\n\t\t}\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tif (!transpose) {\n\t\t\tjor_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, transpose);\n\t\t\tjor_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, transpose);\n\t\t} else {\n\t\t\tjor_rec(t->type.kids.e, level+1, row_offset, col_offset+hdd->off.val, transpose);\n\t\t\tjor_rec(t->type.kids.t, level+1, row_offset+t->off.val, col_offset+hdd->off.val, transpose);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void jor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] -= soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void jor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] -= soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_JORInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n// local prototypes\nstatic void jor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose);\nstatic void jor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void jor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Jacobi/JOR, interval variant\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1JORInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble omega,\t\t// omega (over-relaxation parameter)\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t// upper bound values\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_d, compact_b;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *diags_vec = NULL, *b_vec = NULL, *tmpsoln = NULL;\n\tDistVector *diags_dist = NULL, *b_dist = NULL;\n\tdouble *soln_below = NULL, *soln_below2 = NULL, *soln_above = NULL, *soln_above2 = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tdouble kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNormInterval measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tif (omega <= 0.0 || omega > 1.0) {\n\t\tPN_SetErrorMessage(\"Interval iteration requires 0 < omega <= 1.0, have omega = %g\", omega);\n\t\treturn ptr_to_jlong(NULL);\n\t}\n\n\tIntervalIteration helper(flags);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true, transpose);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false, transpose);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix (and then setting to 1 if sum is 0)\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = hdd_negative_row_sums(hddm, n, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete[] b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tsoln_above = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tsoln_below2 = new double[n];\n\tsoln_above2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 4*kb;\n\tPN_PrintMemoryToMainLog(env, \"[4 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PH_JOR_Interval (\");\n\t\ttitle += (omega == 1.0)?\"Jacobi\": (\"JOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// matrix multiply\n\t\t\n\t\t// initialise vector\n\t\tif (b == NULL) {\n\t\t\tfor (i = 0; i < n; i++) { soln_below2[i] = soln_above2[i] = 0.0; }\n\t\t} else if (!compact_b) {\n\t\t\tfor (i = 0; i < n; i++) { soln_below2[i] = soln_above2[i] = b_vec[i]; }\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) { soln_below2[i] = soln_above2[i] = b_dist->dist[b_dist->ptrs[i]]; }\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit (below)\n\t\tsoln = soln_below;\n\t\tsoln2 = soln_below2;\n\t\tjor_rec(hdd, 0, 0, 0, transpose);\n\n\t\t// do matrix vector multiply bit (above)\n\t\tsoln = soln_above;\n\t\tsoln2 = soln_above2;\n\t\tjor_rec(hdd, 0, 0, 0, transpose);\n\t\t\n\t\t// divide by diagonal\n\t\tif (!compact_d) {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tsoln_below2[i] *= diags_vec[i];\n\t\t\t\tsoln_above2[i] *= diags_vec[i];\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tsoln_below2[i] *= diags_dist->dist[diags_dist->ptrs[i]];\n\t\t\t\tsoln_above2[i] *= diags_dist->dist[diags_dist->ptrs[i]];\n\t\t\t}\n\t\t}\n\t\t\n\t\t// do over-relaxation if necessary\n\t\tif (omega != 1) {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tsoln_below2[i] = ((1-omega) * soln_below[i]) + (omega * soln_below2[i]);\n\t\t\t\tsoln_above2[i] = ((1-omega) * soln_above[i]) + (omega * soln_above2[i]);\n\t\t\t}\n\t\t}\n\n\t\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\t\thelper.ensureMonotonicityFromBelow(soln_below, soln_below2, n);\n\t\t}\n\t\tif (helper.flag_ensure_monotonic_from_above()) {\n\t\t\thelper.ensureMonotonicityFromAbove(soln_above, soln_above2, n);\n\t\t}\n\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below2, n, 0);\n\t\t\titerationExport->exportVector(soln_above2, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below2, soln_above2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln_below;\n\t\tsoln_below = soln_below2;\n\t\tsoln_below2 = tmpsoln;\n\t\ttmpsoln = soln_above;\n\t\tsoln_above = soln_above2;\n\t\tsoln_above2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", (omega == 1.0)?\"Jacobi\":\"JOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (hddm) delete hddm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln_below2) delete soln_below2;\n\tif (soln_above) delete soln_above;\n\tif (soln_above2) delete soln_above2;\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void jor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tjor_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tjor_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] -= soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tif (!transpose) {\n\t\t\tjor_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tjor_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, transpose);\n\t\t} else {\n\t\t\tjor_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tjor_rec(e->type.kids.t, level+1, row_offset+e->off.val, col_offset, transpose);\n\t\t}\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tif (!transpose) {\n\t\t\tjor_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, transpose);\n\t\t\tjor_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, transpose);\n\t\t} else {\n\t\t\tjor_rec(t->type.kids.e, level+1, row_offset, col_offset+hdd->off.val, transpose);\n\t\t\tjor_rec(t->type.kids.t, level+1, row_offset+t->off.val, col_offset+hdd->off.val, transpose);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void jor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] -= soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void jor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] -= soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_NondetBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL, *soln3 = NULL;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1NondetBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t\t// trans matrix\njlong __jlongpointer od,\t\t// odd\njlong __jlongpointer rv,\t\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t\t// 'yes' states\njlong __jlongpointer m,\t\t// 'maybe' states\njint bound,\t\t// time bound\njboolean min\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a = NULL;\n\t// model stats\n\tint n, nm;\n\t// flags\n\tbool compact_y;\n\t// matrix mtbdds\n\tHDDMatrices *hddms = NULL;\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *yes_vec = NULL, *tmpsoln = NULL;\n\tDistVector *yes_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, iters;\n\tdouble kb, kbt;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get a - filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build hdds for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrices... \");\n\thddms = build_hdd_matrices_mdp(a, NULL, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tnm = hddms->nm;\n\tkb = hddms->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[nm=%d, levels=%d, nodes=%d] \", hddms->nm, hddms->num_levels, hddms->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse bits\n\tPN_PrintToMainLog(env, \"Adding sparse bits... \");\n\tadd_sparse_matrices_mdp(hddms, compact);\n\tkb = hddms->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d-%d, num=%d, compact=%d/%d] \", hddms->l_sm_min, hddms->l_sm_max, hddms->num_sm, hddms->compact_sm, hddms->nm);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of yes\n\tPN_PrintToMainLog(env, \"Creating vector for yes... \");\n\tyes_vec = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tcompact_y = false;\n\t// try and convert to compact form if required\n\tif (compact) {\n\t\tif ((yes_dist = double_vector_to_dist(yes_vec, n))) {\n\t\t\tcompact_y = true;\n\t\t\tdelete[] yes_vec; yes_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_y) ? n*8.0/1024.0 : (yes_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_y) PN_PrintToMainLog(env, \"[dist=%d, compact] \", yes_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t//for(i = 0; i < n; i++) printf(\"%f \", (!compact_y)?(yes_vec[i]):(yes_dist->dist[yes_dist->ptrs[i]])); printf(\"\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tsoln3 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is yes\n\tif (!compact_y) {\n\t\tfor (i = 0; i < n; i++) { soln[i] = yes_vec[i]; }\n\t} else {\n\t\tfor (i = 0; i < n; i++) { soln[i] = yes_dist->dist[yes_dist->ptrs[i]]; }\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\n\t\t// initialise array for storing mins/maxs to -1s\n\t\t// (allows us to keep track of rows not visited)\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln2[i] = -1;\n\t\t}\n\t\t\n\t\t// do matrix multiplication and min/max\n\t\tfor (i = 0; i < nm; i++) {\n\t\t\t\n\t\t\t// store stuff to be used globally\n\t\t\thddm = hddms->choices[i];\n\t\t\thdd = hddm->top;\n\t\t\tzero = hddm->zero;\n\t\t\tnum_levels = hddm->num_levels;\n\t\t\tcompact_sm = hddm->compact_sm;\n\t\t\tif (compact_sm) {\n\t\t\t\tsm_dist = hddm->dist;\n\t\t\t\tsm_dist_shift = hddm->dist_shift;\n\t\t\t\tsm_dist_mask = hddm->dist_mask;\n\t\t\t}\n\t\t\t\n\t\t\t// start off all -1\n\t\t\t// (allows us to keep track of rows not visited)\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tsoln3[j] = -1;\n\t\t\t}\n\t\t\t\n\t\t\t// matrix multiply\n\t\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\t\n\t\t\t// min/max\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tif (soln3[j] >= 0) {\n\t\t\t\t\tif (soln2[j] < 0) {\n\t\t\t\t\t\tsoln2[j] = soln3[j];\n\t\t\t\t\t} else if (min) {\n\t\t\t\t\t\tif (soln3[j] < soln2[j]) soln2[j] = soln3[j];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (soln3[j] > soln2[j]) soln2[j] = soln3[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t// sort out anything that's still -1\n\t\t// (should just be yes/no states)\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (soln2[i] < 0) {\n\t\t\t\tsoln2[i] = (!compact_y) ? (yes_vec[i]) : (yes_dist->dist[yes_dist->ptrs[i]]);\n\t\t\t}\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (hddms) delete hddms;\n\tif (yes_vec) delete[] yes_vec;\n\tif (yes_dist) delete yes_dist;\n\tif (soln2) delete[] soln2;\n\tif (soln3) delete[] soln3;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tif (soln3[row_offset] < 0) soln3[row_offset] = 0;\n\t\tsoln3[row_offset] += soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tint r = row_offset + i2;\n\t\t\tif (soln3[r] < 0) soln3[r] = 0;\n\t\t\tsoln3[r] += soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tint r = row_offset + i2;\n\t\t\tif (soln3[r] < 0) soln3[r] = 0;\n\t\t\tsoln3[r] += soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_NondetReachReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <new>\n#include <memory>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset, int code);\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, int code);\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, int code);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL, *soln3 = NULL;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1NondetReachReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t// 'maybe' states\njboolean min\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL;\n\t// model stats\n\tint n, nm;\n\t// flags\n\tbool compact_r;\n\t// hybrid stuff\t\n\tHDDMatrices *hddms = NULL, *hddms2 = NULL;\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *rew_vec = NULL, *tmpsoln = NULL;\n\tDistVector *rew_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, k, iters;\n\tdouble d, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// build hdds for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrices... \");\n\thddms = build_hdd_matrices_mdp(a, NULL, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tnm = hddms->nm;\n\tkb = hddms->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[nm=%d, levels=%d, nodes=%d] \", hddms->nm, hddms->num_levels, hddms->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse bits\n\tPN_PrintToMainLog(env, \"Adding sparse bits... \");\n\tadd_sparse_matrices_mdp(hddms, compact);\n\tkb = hddms->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d-%d, num=%d, compact=%d/%d] \", hddms->l_sm_min, hddms->l_sm_max, hddms->num_sm, hddms->compact_sm, hddms->nm);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, DD_SetVectorElement(ddman, DD_Constant(ddman, 0), cvars, num_cvars, 0, 1));\n\t\n\t// build hdds for transition rewards matrix\n\tPN_PrintToMainLog(env, \"Building hybrid MTBDD matrices for rewards... \");\n\thddms2 = build_hdd_matrices_mdp(trans_rewards, hddms, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tkb = hddms2->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[nm=%d, levels=%d, nodes=%d] \", hddms2->nm, hddms2->num_levels, hddms2->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse bits\n\tPN_PrintToMainLog(env, \"Adding sparse bits... \");\n\tadd_sparse_matrices_mdp(hddms2, compact);\n\tkb = hddms2->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d-%d, num=%d, compact=%d/%d] \", hddms2->l_sm_min, hddms2->l_sm_max, hddms2->num_sm, hddms2->compact_sm, hddms2->nm);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// remove goal and infinity states from state rewards vector\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// put state rewards in a vector\n\tPN_PrintToMainLog(env, \"Creating rewards vector... \");\n\trew_vec = mtbdd_to_double_vector(ddman, state_rewards, rvars, num_rvars, odd);\n\t// try and convert to compact form if required\n\tcompact_r = false;\n\tif (compact) {\n\t\tif ((rew_dist = double_vector_to_dist(rew_vec, n))) {\n\t\t\tcompact_r = true;\n\t\t\tdelete rew_vec; rew_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_r) ? n*8.0/1024.0 : (rew_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_r) PN_PrintToMainLog(env, \"[dist=%d, compact] \", rew_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tsoln3 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is zero\n\tfor (i = 0; i < n; i++) {\n\t\tsoln[i] = 0;\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PH_NondetReachReward\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// initialise array for storing mins/maxs to -1s\n\t\t// (allows us to keep track of rows not visited)\n\t\tfor (i = 0; i < n; i++) {\t\n\t\t\tsoln2[i] = -1;\n\t\t}\n\t\t\n\t\t// do matrix multiplication and min/max\n\t\tfor (i = 0; i < nm; i++) {\n\t\t\t\n\t\t\t// start off all negative\n\t\t\t// (need to keep track of rows not visited)\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tsoln3[j] = -1;\n\t\t\t}\n\t\t\t\n\t\t\t// matrix multiply\n\t\t\t// store stuff to be used globally\n\t\t\thddm = hddms->choices[i];\n\t\t\thdd = hddm->top;\n\t\t\tzero = hddm->zero;\n\t\t\tnum_levels = hddm->num_levels;\n\t\t\tcompact_sm = hddm->compact_sm;\n\t\t\tif (compact_sm) {\n\t\t\t\tsm_dist = hddm->dist;\n\t\t\t\tsm_dist_shift = hddm->dist_shift;\n\t\t\t\tsm_dist_mask = hddm->dist_mask;\n\t\t\t}\n\t\t\t// do traversal\n\t\t\tmult_rec(hdd, 0, 0, 0, 1);\n\t\t\t\n\t\t\t// add transition rewards\n\t\t\t// store stuff to be used globally\n\t\t\thddm = hddms2->choices[i];\n\t\t\thdd = hddm->top;\n\t\t\tzero = hddm->zero;\n\t\t\tnum_levels = hddm->num_levels;\n\t\t\tcompact_sm = hddm->compact_sm;\n\t\t\tif (compact_sm) {\n\t\t\t\tsm_dist = hddm->dist;\n\t\t\t\tsm_dist_shift = hddm->dist_shift;\n\t\t\t\tsm_dist_mask = hddm->dist_mask;\n\t\t\t}\n\t\t\t// do traversal\n\t\t\tmult_rec(hdd, 0, 0, 0, 2);\n\t\t\t\n\t\t\t// min/max\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tif (soln3[j] >= 0) {\n\t\t\t\t\tif (soln2[j] < 0) {\n\t\t\t\t\t\tsoln2[j] = soln3[j];\n\t\t\t\t\t} else if (min) {\n\t\t\t\t\t\tif (soln3[j] < soln2[j]) soln2[j] = soln3[j];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (soln3[j] > soln2[j]) soln2[j] = soln3[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t// add state rewards\n\t\tif (!compact_r) {\n\t\t\tfor (i = 0; i < n; i++) { if(soln2[i] < 0) soln2[i] = 0; soln2[i] += rew_vec[i]; }\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) { if(soln2[i] < 0) soln2[i] = 0; soln2[i] += rew_dist->dist[rew_dist->ptrs[i]]; }\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln2, n, 0);\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln, soln2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (state_rewards) Cudd_RecursiveDeref(ddman, state_rewards);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\tif (hddms) delete hddms;\n\tif (hddms2) delete hddms2;\n\tif (rew_vec) delete[] rew_vec;\n\tif (rew_dist) delete rew_dist;\n\tif (soln2) delete[] soln2;\n\tif (soln3) delete[] soln3;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset, int code)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset, code);\n\t\t} else {\n\t\t\tmult_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset, code);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tswitch (code) {\n\t\tcase 1:\n\t\t\tif (soln3[row_offset] < 0) soln3[row_offset] = 0;\n\t\t\tsoln3[row_offset] += soln[col_offset] * hdd->type.val;\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\tif (soln3[row_offset] < 0) soln3[row_offset] = 0;\n\t\t\tsoln3[row_offset] += hdd->type.val;\n\t\t\tbreak;\n\t\t}\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset, code);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, code);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, code);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, code);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, int code)\n{\n\tint i2, j2, l2, h2, r;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tswitch (code) {\n\t\t\tcase 1:\n\t\t\t\tr = row_offset + i2;\n\t\t\t\tif (soln3[r] < 0) soln3[r] = 0;\n\t\t\t\tsoln3[r] += soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t\tbreak;\n\t\t\tcase 2:\n\t\t\t\tr = row_offset + i2;\n\t\t\t\tif (soln3[r] < 0) soln3[r] = 0;\n\t\t\t\tsoln3[r] += sm_non_zeros[j2];\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, int code)\n{\n\tint i2, j2, l2, h2, r;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tswitch (code) {\n\t\t\tcase 1:\n\t\t\t\tr = row_offset + i2;\n\t\t\t\tif (soln3[r] < 0) soln3[r] = 0;\n\t\t\t\tsoln3[r] += soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t\tbreak;\n\t\t\tcase 2:\n\t\t\t\tr = row_offset + i2;\n\t\t\t\tif (soln3[r] < 0) soln3[r] = 0;\n\t\t\t\tsoln3[r] += sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t//`(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_NondetReachRewardInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include \"Measures.h\"\n#include \"IntervalIteration.h\"\n#include <new>\n#include <memory>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset, int code);\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, int code);\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, int code);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln_below = NULL, *soln_below2 = NULL, *soln_below3 = NULL;\nstatic double *soln_above = NULL, *soln_above2 = NULL, *soln_above3 = NULL;\n\n//------------------------------------------------------------------------------\n\n// TODO: Not yet tested, based on PH_NondetReachReward, which is currently not\n// exposed in PRISM...\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1NondetReachRewardInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t// 'maybe' states\njlong __jlongpointer l,\t\t// lower bound\njlong __jlongpointer u,\t\t// upper bound\njboolean min,\t\t// min or max probabilities (true = min, false = max)\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\tDdNode *lower = jlong_to_DdNode(l); \t\t\t// lower bound\n\tDdNode *upper = jlong_to_DdNode(u); \t\t\t// upper bound\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL;\n\t// model stats\n\tint n, nm;\n\t// flags\n\tbool compact_r;\n\t// hybrid stuff\t\n\tHDDMatrices *hddms = NULL, *hddms2 = NULL;\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *rew_vec = NULL, *tmpsoln = NULL;\n\tDistVector *rew_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, k, iters;\n\tdouble d, x, sup_norm, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// build hdds for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrices... \");\n\thddms = build_hdd_matrices_mdp(a, NULL, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tnm = hddms->nm;\n\tkb = hddms->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[nm=%d, levels=%d, nodes=%d] \", hddms->nm, hddms->num_levels, hddms->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse bits\n\tPN_PrintToMainLog(env, \"Adding sparse bits... \");\n\tadd_sparse_matrices_mdp(hddms, compact);\n\tkb = hddms->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d-%d, num=%d, compact=%d/%d] \", hddms->l_sm_min, hddms->l_sm_max, hddms->num_sm, hddms->compact_sm, hddms->nm);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, DD_SetVectorElement(ddman, DD_Constant(ddman, 0), cvars, num_cvars, 0, 1));\n\t\n\t// build hdds for transition rewards matrix\n\tPN_PrintToMainLog(env, \"Building hybrid MTBDD matrices for rewards... \");\n\thddms2 = build_hdd_matrices_mdp(trans_rewards, hddms, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tkb = hddms2->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[nm=%d, levels=%d, nodes=%d] \", hddms2->nm, hddms2->num_levels, hddms2->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse bits\n\tPN_PrintToMainLog(env, \"Adding sparse bits... \");\n\tadd_sparse_matrices_mdp(hddms2, compact);\n\tkb = hddms2->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d-%d, num=%d, compact=%d/%d] \", hddms2->l_sm_min, hddms2->l_sm_max, hddms2->num_sm, hddms2->compact_sm, hddms2->nm);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// remove goal and infinity states from state rewards vector\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// put state rewards in a vector\n\tPN_PrintToMainLog(env, \"Creating rewards vector... \");\n\trew_vec = mtbdd_to_double_vector(ddman, state_rewards, rvars, num_rvars, odd);\n\t// try and convert to compact form if required\n\tcompact_r = false;\n\tif (compact) {\n\t\tif ((rew_dist = double_vector_to_dist(rew_vec, n))) {\n\t\t\tcompact_r = true;\n\t\t\tdelete rew_vec; rew_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_r) ? n*8.0/1024.0 : (rew_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_r) PN_PrintToMainLog(env, \"[dist=%d, compact] \", rew_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\t// initial solution from below is lower\n\tsoln_below = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tsoln_below2 = new double[n];\n\tsoln_below3 = new double[n];\n\t// initial solution from above is upper\n\tsoln_below = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tsoln_above2 = new double[n];\n\tsoln_above3 = new double[n];\n\n\tkb = n*8.0/1024.0;\n\tkbt += 6*kb;\n\tPN_PrintMemoryToMainLog(env, \"[6 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PH_NondetReachReward (interval)\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations (interval iteration)...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// initialise array for storing mins/maxs to -1s\n\t\t// (allows us to keep track of rows not visited)\n\t\tfor (i = 0; i < n; i++) {\t\n\t\t\tsoln_below2[i] = -1;\n\t\t\tsoln_above2[i] = -1;\n\t\t}\n\t\t\n\t\t// do matrix multiplication and min/max\n\t\tfor (i = 0; i < nm; i++) {\n\t\t\t\n\t\t\t// start off all negative\n\t\t\t// (need to keep track of rows not visited)\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tsoln_below3[j] = -1;\n\t\t\t\tsoln_above3[j] = -1;\n\t\t\t}\n\t\t\t\n\t\t\t// matrix multiply\n\t\t\t// store stuff to be used globally\n\t\t\thddm = hddms->choices[i];\n\t\t\thdd = hddm->top;\n\t\t\tzero = hddm->zero;\n\t\t\tnum_levels = hddm->num_levels;\n\t\t\tcompact_sm = hddm->compact_sm;\n\t\t\tif (compact_sm) {\n\t\t\t\tsm_dist = hddm->dist;\n\t\t\t\tsm_dist_shift = hddm->dist_shift;\n\t\t\t\tsm_dist_mask = hddm->dist_mask;\n\t\t\t}\n\t\t\t// do traversal\n\t\t\tmult_rec(hdd, 0, 0, 0, 1);\n\t\t\t\n\t\t\t// add transition rewards\n\t\t\t// store stuff to be used globally\n\t\t\thddm = hddms2->choices[i];\n\t\t\thdd = hddm->top;\n\t\t\tzero = hddm->zero;\n\t\t\tnum_levels = hddm->num_levels;\n\t\t\tcompact_sm = hddm->compact_sm;\n\t\t\tif (compact_sm) {\n\t\t\t\tsm_dist = hddm->dist;\n\t\t\t\tsm_dist_shift = hddm->dist_shift;\n\t\t\t\tsm_dist_mask = hddm->dist_mask;\n\t\t\t}\n\t\t\t// do traversal\n\t\t\tmult_rec(hdd, 0, 0, 0, 2);\n\t\t\t\n\t\t\t// min/max\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tif (soln_below3[j] >= 0) {\n\t\t\t\t\tif (soln_below2[j] < 0) {\n\t\t\t\t\t\tsoln_below2[j] = soln_below3[j];\n\t\t\t\t\t} else if (min) {\n\t\t\t\t\t\tif (soln_below3[j] < soln_below2[j]) soln_below2[j] = soln_below3[j];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (soln_below3[j] > soln_below2[j]) soln_below2[j] = soln_below3[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (soln_above3[j] >= 0) {\n\t\t\t\t\tif (soln_above2[j] < 0) {\n\t\t\t\t\t\tsoln_above2[j] = soln_above3[j];\n\t\t\t\t\t} else if (min) {\n\t\t\t\t\t\tif (soln_above3[j] < soln_above2[j]) soln_above2[j] = soln_above3[j];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (soln_above3[j] > soln_above2[j]) soln_above2[j] = soln_above3[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t// add state rewards\n\t\tif (!compact_r) {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif(soln_below2[i] < 0) soln_below2[i] = 0; soln_below2[i] += rew_vec[i];\n\t\t\t\tif(soln_above2[i] < 0) soln_above2[i] = 0; soln_above2[i] += rew_vec[i];\n\t\t\t}\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif(soln_below2[i] < 0) soln_below2[i] = 0; soln_below2[i] += rew_dist->dist[rew_dist->ptrs[i]];\n\t\t\t\tif(soln_above2[i] < 0) soln_above2[i] = 0; soln_above2[i] += rew_dist->dist[rew_dist->ptrs[i]];\n\t\t\t}\n\t\t}\n\n\t\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\t\thelper.ensureMonotonicityFromBelow(soln_below, soln_below2, n);\n\t\t}\n\t\tif (helper.flag_ensure_monotonic_from_above()) {\n\t\t\thelper.ensureMonotonicityFromAbove(soln_above, soln_above2, n);\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below2, n, 0);\n\t\t\titerationExport->exportVector(soln_above2, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below2, soln_above2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln_below;\n\t\tsoln_below = soln_below2;\n\t\tsoln_below2 = tmpsoln;\n\t\ttmpsoln = soln_above;\n\t\tsoln_above = soln_above2;\n\t\tsoln_above2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (state_rewards) Cudd_RecursiveDeref(ddman, state_rewards);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\tif (hddms) delete hddms;\n\tif (hddms2) delete hddms2;\n\tif (rew_vec) delete[] rew_vec;\n\tif (rew_dist) delete rew_dist;\n\tif (soln_below2) delete[] soln_below2;\n\tif (soln_below3) delete[] soln_below3;\n\tif (soln_above) delete[] soln_above;\n\tif (soln_above2) delete[] soln_above2;\n\tif (soln_above3) delete[] soln_above3;\n\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset, int code)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset, code);\n\t\t} else {\n\t\t\tmult_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset, code);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tswitch (code) {\n\t\tcase 1:\n\t\t\tif (soln_below3[row_offset] < 0) soln_below3[row_offset] = 0;\n\t\t\tsoln_below3[row_offset] += soln_below[col_offset] * hdd->type.val;\n\t\t\tif (soln_above3[row_offset] < 0) soln_above3[row_offset] = 0;\n\t\t\tsoln_above3[row_offset] += soln_above[col_offset] * hdd->type.val;\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\tif (soln_below3[row_offset] < 0) soln_above3[row_offset] = 0;\n\t\t\tsoln_below3[row_offset] += hdd->type.val;\n\t\t\tif (soln_above3[row_offset] < 0) soln_above3[row_offset] = 0;\n\t\t\tsoln_above3[row_offset] += hdd->type.val;\n\t\t\tbreak;\n\t\t}\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset, code);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, code);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, code);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, code);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, int code)\n{\n\tint i2, j2, l2, h2, r;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tswitch (code) {\n\t\t\tcase 1:\n\t\t\t\tr = row_offset + i2;\n\t\t\t\tif (soln_below3[r] < 0) soln_below3[r] = 0;\n\t\t\t\tsoln_below3[r] += soln_below[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t\tif (soln_above3[r] < 0) soln_above3[r] = 0;\n\t\t\t\tsoln_above3[r] += soln_above[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t\tbreak;\n\t\t\tcase 2:\n\t\t\t\tr = row_offset + i2;\n\t\t\t\tif (soln_below3[r] < 0) soln_below3[r] = 0;\n\t\t\t\tsoln_below3[r] += sm_non_zeros[j2];\n\t\t\t\tif (soln_above3[r] < 0) soln_above3[r] = 0;\n\t\t\t\tsoln_above3[r] += sm_non_zeros[j2];\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, int code)\n{\n\tint i2, j2, l2, h2, r;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tswitch (code) {\n\t\t\tcase 1:\n\t\t\t\tr = row_offset + i2;\n\t\t\t\tif (soln_below3[r] < 0) soln_below3[r] = 0;\n\t\t\t\tsoln_below3[r] += soln_below[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t\tif (soln_above3[r] < 0) soln_above3[r] = 0;\n\t\t\t\tsoln_above3[r] += soln_above[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t\tbreak;\n\t\t\tcase 2:\n\t\t\t\tr = row_offset + i2;\n\t\t\t\tif (soln_below3[r] < 0) soln_below3[r] = 0;\n\t\t\t\tsoln_below3[r] += sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t\tif (soln_above3[r] < 0) soln_above3[r] = 0;\n\t\t\t\tsoln_above3[r] += sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t//`(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_NondetUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <new>\n#include <memory>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL, *soln3 = NULL;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1NondetUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njboolean min\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a = NULL;\n\t// model stats\n\tint n, nm;\n\t// flags\n\tbool compact_y;\n\t// matrix mtbdds\n\tHDDMatrices *hddms = NULL;\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *yes_vec = NULL, *tmpsoln = NULL;\n\tDistVector *yes_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, iters;\n\tdouble x, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get a - filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build hdds for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrices... \");\n\thddms = build_hdd_matrices_mdp(a, NULL, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tnm = hddms->nm;\n\tkb = hddms->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[nm=%d, levels=%d, nodes=%d] \", hddms->nm, hddms->num_levels, hddms->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse bits\n\tPN_PrintToMainLog(env, \"Adding sparse bits... \");\n\tadd_sparse_matrices_mdp(hddms, compact);\n\tkb = hddms->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d-%d, num=%d, compact=%d/%d] \", hddms->l_sm_min, hddms->l_sm_max, hddms->num_sm, hddms->compact_sm, hddms->nm);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of yes\n\tPN_PrintToMainLog(env, \"Creating vector for yes... \");\n\tyes_vec = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tcompact_y = false;\n\t// try and convert to compact form if required\n\tif (compact) {\n\t\tif ((yes_dist = double_vector_to_dist(yes_vec, n))) {\n\t\t\tcompact_y = true;\n\t\t\tdelete[] yes_vec; yes_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_y) ? n*8.0/1024.0 : (yes_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_y) PN_PrintToMainLog(env, \"[dist=%d, compact] \", yes_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t//for(i = 0; i < n; i++) printf(\"%f \", (!compact_y)?(yes_vec[i]):(yes_dist->dist[yes_dist->ptrs[i]])); printf(\"\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tsoln3 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is yes\n\tif (!compact_y) {\n\t\tfor (i = 0; i < n; i++) { soln[i] = yes_vec[i]; }\n\t} else {\n\t\tfor (i = 0; i < n; i++) { soln[i] = yes_dist->dist[yes_dist->ptrs[i]]; }\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PH_NondetUntil\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// initialise array for storing mins/maxs to -1s\n\t\t// (allows us to keep track of rows not visited)\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln2[i] = -1;\n\t\t}\n\t\t\n\t\t// do matrix multiplication and min/max\n\t\tfor (i = 0; i < nm; i++) {\n\t\t\t\n\t\t\t// store stuff to be used globally\n\t\t\thddm = hddms->choices[i];\n\t\t\thdd = hddm->top;\n\t\t\tzero = hddm->zero;\n\t\t\tnum_levels = hddm->num_levels;\n\t\t\tcompact_sm = hddm->compact_sm;\n\t\t\tif (compact_sm) {\n\t\t\t\tsm_dist = hddm->dist;\n\t\t\t\tsm_dist_shift = hddm->dist_shift;\n\t\t\t\tsm_dist_mask = hddm->dist_mask;\n\t\t\t}\n\t\t\t\n\t\t\t// start off all -1\n\t\t\t// (allows us to keep track of rows not visited)\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tsoln3[j] = -1;\n\t\t\t}\n\t\t\t\n\t\t\t// matrix multiply\n\t\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\t\n\t\t\t// min/max\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tif (soln3[j] >= 0) {\n\t\t\t\t\tif (soln2[j] < 0) {\n\t\t\t\t\t\tsoln2[j] = soln3[j];\n\t\t\t\t\t} else if (min) {\n\t\t\t\t\t\tif (soln3[j] < soln2[j]) soln2[j] = soln3[j];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (soln3[j] > soln2[j]) soln2[j] = soln3[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t// sort out anything that's still -1\n\t\t// (should just be yes/no states)\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (soln2[i] < 0) {\n\t\t\t\tsoln2[i] = (!compact_y) ? (yes_vec[i]) : (yes_dist->dist[yes_dist->ptrs[i]]);\n\t\t\t}\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln2, n, 0);\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln, soln2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (hddms) delete hddms;\n\tif (yes_vec) delete[] yes_vec;\n\tif (yes_dist) delete yes_dist;\n\tif (soln2) delete[] soln2;\n\tif (soln3) delete[] soln3;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tif (soln3[row_offset] < 0) soln3[row_offset] = 0;\n\t\tsoln3[row_offset] += soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tint r = row_offset + i2;\n\t\t\tif (soln3[r] < 0) soln3[r] = 0;\n\t\t\tsoln3[r] += soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tint r = row_offset + i2;\n\t\t\tif (soln3[r] < 0) soln3[r] = 0;\n\t\t\tsoln3[r] += soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_NondetUntilInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln_below = NULL, *soln_below2 = NULL, *soln_below3 = NULL;\nstatic double *soln_above = NULL, *soln_above2 = NULL, *soln_above3 = NULL;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1NondetUntilInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njboolean min,\t\t// min or max probabilities (true = min, false = max)\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a = NULL;\n\t// model stats\n\tint n, nm;\n\t// flags\n\tbool compact_y;\n\tbool compact_maybe;\n\t// matrix mtbdds\n\tHDDMatrices *hddms = NULL;\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *yes_vec = NULL, *maybe_vec = NULL, *tmpsoln = NULL;\n\tDistVector *yes_dist = NULL;\n\tDistVector *maybe_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, iters;\n\tdouble kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNormInterval measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get a - filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build hdds for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrices... \");\n\thddms = build_hdd_matrices_mdp(a, NULL, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tnm = hddms->nm;\n\tkb = hddms->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[nm=%d, levels=%d, nodes=%d] \", hddms->nm, hddms->num_levels, hddms->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse bits\n\tPN_PrintToMainLog(env, \"Adding sparse bits... \");\n\tadd_sparse_matrices_mdp(hddms, compact);\n\tkb = hddms->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d-%d, num=%d, compact=%d/%d] \", hddms->l_sm_min, hddms->l_sm_max, hddms->num_sm, hddms->compact_sm, hddms->nm);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of yes\n\tPN_PrintToMainLog(env, \"Creating vector for yes... \");\n\tyes_vec = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tcompact_y = false;\n\t// try and convert to compact form if required\n\tif (compact) {\n\t\tif ((yes_dist = double_vector_to_dist(yes_vec, n))) {\n\t\t\tcompact_y = true;\n\t\t\tdelete[] yes_vec; yes_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_y) ? n*8.0/1024.0 : (yes_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_y) PN_PrintToMainLog(env, \"[dist=%d, compact] \", yes_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t//for(i = 0; i < n; i++) printf(\"%f \", (!compact_y)?(yes_vec[i]):(yes_dist->dist[yes_dist->ptrs[i]])); printf(\"\\n\");\n\n\t// get vector of maybe\n\tPN_PrintToMainLog(env, \"Creating vector for maybe... \");\n\tmaybe_vec = mtbdd_to_double_vector(ddman, maybe, rvars, num_rvars, odd);\n\tcompact_maybe = false;\n\t// try and convert to compact form if required\n\tif (compact) {\n\t\tif ((maybe_dist = double_vector_to_dist(maybe_vec, n))) {\n\t\t\tcompact_maybe = true;\n\t\t\tdelete[] maybe_vec; maybe_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_maybe) ? n*8.0/1024.0 : (maybe_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_maybe) PN_PrintToMainLog(env, \"[dist=%d, compact] \", maybe_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t//for(i = 0; i < n; i++) printf(\"%f \", (!compact_maybe)?(maybe_vec[i]):(maybe_dist->dist[maybe_dist->ptrs[i]])); printf(\"\\n\");\n\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = new double[n];\n\tsoln_below2 = new double[n];\n\tsoln_below3 = new double[n];\n\tsoln_above = new double[n];\n\tsoln_above2 = new double[n];\n\tsoln_above3 = new double[n];\n\n\tkb = n*8.0/1024.0;\n\tkbt += 6*kb;\n\tPN_PrintMemoryToMainLog(env, \"[6 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution from below is yes, from above 1 for yes or maybe states\n\tdouble yes_val, maybe_val;\n\tfor (i = 0; i < n; i++) {\n\t\tif (!compact_y) {\n\t\t\tyes_val = yes_vec[i];\n\t\t} else {\n\t\t\tyes_val = yes_dist->dist[yes_dist->ptrs[i]];\n\t\t}\n\t\tif (!compact_maybe) {\n\t\t\tmaybe_val = maybe_vec[i];\n\t\t} else {\n\t\t\tmaybe_val = maybe_dist->dist[maybe_dist->ptrs[i]];\n\t\t}\n\n\t\tsoln_below[i] = yes_val;\n\t\tsoln_above[i] = yes_val > 0 ? yes_val : maybe_val;\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PH_NondetUntil_Interval\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations (interval iteration)...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// initialise array for storing mins/maxs to -1s\n\t\t// (allows us to keep track of rows not visited)\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln_below2[i] = -1;\n\t\t\tsoln_above2[i] = -1;\n\t\t}\n\t\t\n\t\t// do matrix multiplication and min/max\n\t\tfor (i = 0; i < nm; i++) {\n\t\t\t\n\t\t\t// store stuff to be used globally\n\t\t\thddm = hddms->choices[i];\n\t\t\thdd = hddm->top;\n\t\t\tzero = hddm->zero;\n\t\t\tnum_levels = hddm->num_levels;\n\t\t\tcompact_sm = hddm->compact_sm;\n\t\t\tif (compact_sm) {\n\t\t\t\tsm_dist = hddm->dist;\n\t\t\t\tsm_dist_shift = hddm->dist_shift;\n\t\t\t\tsm_dist_mask = hddm->dist_mask;\n\t\t\t}\n\t\t\t\n\t\t\t// start off all -1\n\t\t\t// (allows us to keep track of rows not visited)\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tsoln_below3[j] = -1;\n\t\t\t\tsoln_above3[j] = -1;\n\t\t\t}\n\t\t\t\n\t\t\t// matrix multiply\n\t\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\t\n\t\t\t// min/max\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tif (soln_below3[j] >= 0) {\n\t\t\t\t\tif (soln_below2[j] < 0) {\n\t\t\t\t\t\tsoln_below2[j] = soln_below3[j];\n\t\t\t\t\t} else if (min) {\n\t\t\t\t\t\tif (soln_below3[j] < soln_below2[j]) soln_below2[j] = soln_below3[j];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (soln_below3[j] > soln_below2[j]) soln_below2[j] = soln_below3[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (soln_above3[j] >= 0) {\n\t\t\t\t\tif (soln_above2[j] < 0) {\n\t\t\t\t\t\tsoln_above2[j] = soln_above3[j];\n\t\t\t\t\t} else if (min) {\n\t\t\t\t\t\tif (soln_above3[j] < soln_above2[j]) soln_above2[j] = soln_above3[j];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (soln_above3[j] > soln_above2[j]) soln_above2[j] = soln_above3[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\t\t\n\t\t// sort out anything that's still -1\n\t\t// (should just be yes/no states)\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (soln_below2[i] < 0) {\n\t\t\t\tsoln_below2[i] = (!compact_y) ? (yes_vec[i]) : (yes_dist->dist[yes_dist->ptrs[i]]);\n\t\t\t}\n\t\t\tif (soln_above2[i] < 0) {\n\t\t\t\tsoln_above2[i] = (!compact_y) ? (yes_vec[i]) : (yes_dist->dist[yes_dist->ptrs[i]]);\n\t\t\t}\n\t\t}\n\n\t\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\t\thelper.ensureMonotonicityFromBelow(soln_below, soln_below2, n);\n\t\t}\n\t\tif (helper.flag_ensure_monotonic_from_above()) {\n\t\t\thelper.ensureMonotonicityFromAbove(soln_above, soln_above2, n);\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below2, n, 0);\n\t\t\titerationExport->exportVector(soln_above2, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below2, soln_above2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln_below;\n\t\tsoln_below = soln_below2;\n\t\tsoln_below2 = tmpsoln;\n\t\ttmpsoln = soln_above;\n\t\tsoln_above = soln_above2;\n\t\tsoln_above2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (hddms) delete hddms;\n\tif (yes_vec) delete[] yes_vec;\n\tif (yes_dist) delete yes_dist;\n\tif (maybe_vec) delete[] maybe_vec;\n\tif (maybe_dist) delete maybe_dist;\n\tif (soln_below2) delete soln_below2;\n\tif (soln_below3) delete soln_below3;\n\tif (soln_above) delete soln_above;\n\tif (soln_above2) delete soln_above2;\n\tif (soln_above3) delete soln_above3;\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tif (soln_below3[row_offset] < 0) soln_below3[row_offset] = 0;\n\t\tsoln_below3[row_offset] += soln_below[col_offset] * hdd->type.val;\n\n\t\tif (soln_above3[row_offset] < 0) soln_above3[row_offset] = 0;\n\t\tsoln_above3[row_offset] += soln_above[col_offset] * hdd->type.val;\n\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tint r = row_offset + i2;\n\t\t\tif (soln_below3[r] < 0) soln_below3[r] = 0;\n\t\t\tsoln_below3[r] += soln_below[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\tif (soln_above3[r] < 0) soln_above3[r] = 0;\n\t\t\tsoln_above3[r] += soln_above[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tint r = row_offset + i2;\n\t\t\tif (soln_below3[r] < 0) soln_below3[r] = 0;\n\t\t\tsoln_below3[r] += soln_below[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\tif (soln_above3[r] < 0) soln_above3[r] = 0;\n\t\t\tsoln_above3[r] += soln_above[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_PSOR.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Rashid Mehmood <rxm@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <new>\n#include <memory>\n\n// local prototypes\nstatic void psor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose);\nstatic void psor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void psor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Pseudo Gauss-Seidel/SOR\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1PSOR\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble omega,\t\t// omega (over-relaxation parameter)\njboolean forwards\t// forwards or backwards?\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_d, compact_b;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *diags_vec = NULL, *b_vec = NULL;\n\tDistVector *diags_dist = NULL, *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, fb, l, h, i2, h2, iters;\n\tdouble x, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true, transpose);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// split hdd matrix into blocks\n\t// nb: in terms of memory, this gets precedence over sparse matrices\n\tPN_PrintToMainLog(env, \"Splitting into blocks... \");\n\tsplit_hdd_matrix(hddm, compact, false, transpose);\n\tcompact_b = hddm->compact_b;\n\tkb = hddm->mem_b;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, n=%d, nnz=%d%s] \", hddm->l_b, hddm->blocks->n, hddm->blocks->nnz, compact_b?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false, transpose);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix (and then setting to 1 if sum is 0)\n\t// (the latter is a fix for steady-state solution of a subsystem e.g. a BSCC)\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = hdd_negative_row_sums(hddm, n, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete[] b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, init, rvars, num_rvars, odd);\n\tsoln2 = new double[hddm->blocks->max];\n\tfor (i = 0; i < hddm->blocks->max; i++) soln2[i] = 0;\n\tkb = (n*8.0/1024.0)+(hddm->blocks->max*8.0/1024.0);\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", (n*8.0/1024.0), \"\");\n\tPN_PrintMemoryToMainLog(env, \" + \", (hddm->blocks->max*8.0/1024.0), \"\");\n\tPN_PrintMemoryToMainLog(env, \" = \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PH_PSOR (\");\n\t\ttitle += (omega == 1.0)?\"Pseudo Gauss-Seidel\": (\"Pseudo SOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n//\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n//\t\tstart3 = util_cpu_time();\n\t\t\n\t\tmeasure.reset();\n\t\t\n\t\t// stuff for block storage\n\t\tint b_n = hddm->blocks->n;\n\t\tint b_nnz = hddm->blocks->nnz;\n\t\tHDDNode **b_blocks = hddm->blocks->blocks;\n\t\tunsigned int *b_rowscols = hddm->blocks->rowscols;\n\t\tunsigned char *b_counts = hddm->blocks->counts;\n\t\tint *b_starts = (int *)hddm->blocks->counts;\n\t\tbool b_use_counts = hddm->blocks->use_counts;\n\t\tint *b_offsets = hddm->blocks->offsets;\n\t\tHDDNode **b_nodes = hddm->row_tables[hddm->l_b];\n\t\tint b_dist_shift = hddm->blocks->dist_shift;\n\t\tint b_dist_mask = hddm->blocks->dist_mask;\n\t\tint row_offset, col_offset;\n\t\tHDDNode *node;\n\t\t\n\t\t// loop through rows of blocks\n\t\tl = b_nnz; h = 0;\n\t\tfor(fb = 0; fb < b_n; fb++)\n\t\t{\n\t\t\t// loop actually over i (can do forwards or backwards psor/pgs)\n\t\t\ti = (forwards) ? fb : b_n-1-fb;\n\t\t\t\n\t\t\t// store block row offset\n\t\t\trow_offset = b_offsets[i];\n\t\t\t\n\t\t\t// initialise (partial) solution vector\n\t\t\th2 = b_offsets[i+1] - b_offsets[i];\n\t\t\t// initialise vector\n\t\t\tif (b == NULL) {\n\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = 0.0; }\n\t\t\t} else if (!compact_b) {\n\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = b_vec[row_offset + i2]; }\n\t\t\t} else {\n\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = b_dist->dist[b_dist->ptrs[row_offset + i2]]; }\n\t\t\t}\n\t\t\t\n\t\t\t// loop through blocks in this row of blocks\n\t\t\tif (!b_use_counts) { l = b_starts[i]; h = b_starts[i+1]; }\n\t\t\telse if (forwards) { l = h; h += b_counts[i]; }\n\t\t\telse { h = l; l -= b_counts[i]; }\n\t\t\tfor(j = l; j < h; j++)\n\t\t\t{\n\t\t\t\t// get node for block and its col offset\n\t\t\t\tif (!compact_b) {\n\t\t\t\t\tnode = b_blocks[j];\n\t\t\t\t\tcol_offset = b_offsets[b_rowscols[j]];\n\t\t\t\t} else {\n\t\t\t\t\tnode = b_nodes[(int)(b_rowscols[j] & b_dist_mask)];\n\t\t\t\t\tcol_offset = b_offsets[(int)(b_rowscols[j] >> b_dist_shift)];\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// recursively traverse block\n\t\t\t\tpsor_rec(node, hddm->l_b, 0, col_offset, transpose);\n\t\t\t}\n\t\t\t\n\t\t\t// do convergence check/update/etc.\n\t\t\th2 = b_offsets[i+1] - b_offsets[i];\n\t\t\tfor (i2 = 0; i2 < h2; i2++) {\n\t\t\t\t// divide by diagonal\n\t\t\t\tif (!compact_d) {\n\t\t\t\t\tsoln2[i2] *= diags_vec[row_offset + i2];\n\t\t\t\t} else {\n\t\t\t\t\tsoln2[i2] *= (diags_dist->dist[(int)diags_dist->ptrs[row_offset + i2]]);\n\t\t\t\t}\n\t\t\t\t// do over-relaxation if necessary\n\t\t\t\tif (omega != 1) {\n\t\t\t\t\tsoln2[i2] = ((1-omega) * soln[row_offset + i2]) + (omega * soln2[i2]);\n\t\t\t\t}\n\t\t\t\t// compute norm for convergence\n\t\t\t\tmeasure.measure(soln[row_offset + i2], soln2[i2]);\n\t\t\t\t// set vector element\n\t\t\t\tsoln[row_offset + i2] = soln2[i2];\n\t\t\t}\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln, n, 0);\n\n\t\t// check convergence\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\n//\t\tPN_PrintToMainLog(env, \"%.2f %.2f sec\\n\", ((double)(util_cpu_time() - start3)/1000), ((double)(util_cpu_time() - start2)/1000)/iters);\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%sPseudo %s: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", forwards?\"\":\"Backwards \", (omega == 1.0)?\"Gauss-Seidel\":\"SOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (hddm) delete hddm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void psor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tpsor_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tpsor_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] -= soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tif (!transpose) {\n\t\t\tpsor_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tpsor_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, transpose);\n\t\t} else {\n\t\t\tpsor_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tpsor_rec(e->type.kids.t, level+1, row_offset+e->off.val, col_offset, transpose);\n\t\t}\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tif (!transpose) {\n\t\t\tpsor_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, transpose);\n\t\t\tpsor_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, transpose);\n\t\t} else {\n\t\t\tpsor_rec(t->type.kids.e, level+1, row_offset, col_offset+hdd->off.val, transpose);\n\t\t\tpsor_rec(t->type.kids.t, level+1, row_offset+t->off.val, col_offset+hdd->off.val, transpose);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void psor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] -= soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void psor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] -= soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_PSORInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Rashid Mehmood <rxm@cs.bham.ac.uk> (University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n// local prototypes\nstatic void psor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose);\nstatic void psor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void psor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Pseudo Gauss-Seidel/SOR, interval variant\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1PSORInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble omega,\t\t// omega (over-relaxation parameter)\njboolean forwards,\t// forwards or backwards?\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t// upper bound values\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_d, compact_b;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *diags_vec = NULL, *b_vec = NULL;\n\tDistVector *diags_dist = NULL, *b_dist = NULL;\n\tdouble *soln_below = NULL, *soln_above = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, fb, l, h, i2, h2, iters;\n\tdouble kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNormInterval measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tif (omega <= 0.0 || omega > 1.0) {\n\t\tPN_SetErrorMessage(\"Interval iteration requires 0 < omega <= 1.0, have omega = %g\", omega);\n\t\treturn ptr_to_jlong(NULL);\n\t}\n\n\tIntervalIteration helper(flags);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true, transpose);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// split hdd matrix into blocks\n\t// nb: in terms of memory, this gets precedence over sparse matrices\n\tPN_PrintToMainLog(env, \"Splitting into blocks... \");\n\tsplit_hdd_matrix(hddm, compact, false, transpose);\n\tcompact_b = hddm->compact_b;\n\tkb = hddm->mem_b;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, n=%d, nnz=%d%s] \", hddm->l_b, hddm->blocks->n, hddm->blocks->nnz, compact_b?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false, transpose);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix (and then setting to 1 if sum is 0)\n\t// (the latter is a fix for steady-state solution of a subsystem e.g. a BSCC)\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = hdd_negative_row_sums(hddm, n, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete[] b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tsoln_above = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tsoln2 = new double[hddm->blocks->max];\n\tfor (i = 0; i < hddm->blocks->max; i++) soln2[i] = 0;\n\tkb = 2*(n*8.0/1024.0)+(hddm->blocks->max*8.0/1024.0);\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", (n*8.0/1024.0), \"\");\n\tPN_PrintMemoryToMainLog(env, \" + \", (hddm->blocks->max*8.0/1024.0), \"\");\n\tPN_PrintMemoryToMainLog(env, \" = \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PH_PSOR_Interval (Pseudo \");\n\t\ttitle += (omega == 1.0)?\"Gauss-Seidel\": (\"SOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n//\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n//\t\tstart3 = util_cpu_time();\n\t\t\n\t\t// stuff for block storage\n\t\tint b_n = hddm->blocks->n;\n\t\tint b_nnz = hddm->blocks->nnz;\n\t\tHDDNode **b_blocks = hddm->blocks->blocks;\n\t\tunsigned int *b_rowscols = hddm->blocks->rowscols;\n\t\tunsigned char *b_counts = hddm->blocks->counts;\n\t\tint *b_starts = (int *)hddm->blocks->counts;\n\t\tbool b_use_counts = hddm->blocks->use_counts;\n\t\tint *b_offsets = hddm->blocks->offsets;\n\t\tHDDNode **b_nodes = hddm->row_tables[hddm->l_b];\n\t\tint b_dist_shift = hddm->blocks->dist_shift;\n\t\tint b_dist_mask = hddm->blocks->dist_mask;\n\t\tint row_offset, col_offset;\n\t\tHDDNode *node;\n\t\tint it;\n\n\t\tfor (it = 0; it <= 1; it++) {\n\t\t\tbool from_below;\n\n\t\t\tif (it == 0) {\n\t\t\t\t// from below\n\t\t\t\tfrom_below = true;\n\t\t\t\tsoln = soln_below;\n\t\t\t} else {\n\t\t\t\t// from above\n\t\t\t\tfrom_below = false;\n\t\t\t\tsoln = soln_above;\n\t\t\t}\n\n\t\t\t// loop through rows of blocks\n\t\t\tl = b_nnz; h = 0;\n\t\t\tfor(fb = 0; fb < b_n; fb++)\n\t\t\t{\n\t\t\t\t// loop actually over i (can do forwards or backwards psor/pgs)\n\t\t\t\ti = (forwards) ? fb : b_n-1-fb;\n\n\t\t\t\t// store block row offset\n\t\t\t\trow_offset = b_offsets[i];\n\n\t\t\t\t// initialise (partial) solution vector\n\t\t\t\th2 = b_offsets[i+1] - b_offsets[i];\n\t\t\t\t// initialise vector\n\t\t\t\tif (b == NULL) {\n\t\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = 0.0; }\n\t\t\t\t} else if (!compact_b) {\n\t\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = b_vec[row_offset + i2]; }\n\t\t\t\t} else {\n\t\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = b_dist->dist[b_dist->ptrs[row_offset + i2]]; }\n\t\t\t\t}\n\n\t\t\t\t// loop through blocks in this row of blocks\n\t\t\t\tif (!b_use_counts) { l = b_starts[i]; h = b_starts[i+1]; }\n\t\t\t\telse if (forwards) { l = h; h += b_counts[i]; }\n\t\t\t\telse { h = l; l -= b_counts[i]; }\n\t\t\t\tfor(j = l; j < h; j++)\n\t\t\t\t{\n\t\t\t\t\t// get node for block and its col offset\n\t\t\t\t\tif (!compact_b) {\n\t\t\t\t\t\tnode = b_blocks[j];\n\t\t\t\t\t\tcol_offset = b_offsets[b_rowscols[j]];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tnode = b_nodes[(int)(b_rowscols[j] & b_dist_mask)];\n\t\t\t\t\t\tcol_offset = b_offsets[(int)(b_rowscols[j] >> b_dist_shift)];\n\t\t\t\t\t}\n\n\t\t\t\t\t// recursively traverse block\n\t\t\t\t\tpsor_rec(node, hddm->l_b, 0, col_offset, transpose);\n\t\t\t\t}\n\n\t\t\t\t// do update/etc.\n\t\t\t\th2 = b_offsets[i+1] - b_offsets[i];\n\t\t\t\tfor (i2 = 0; i2 < h2; i2++) {\n\t\t\t\t\t// divide by diagonal\n\t\t\t\t\tif (!compact_d) {\n\t\t\t\t\t\tsoln2[i2] *= diags_vec[row_offset + i2];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tsoln2[i2] *= (diags_dist->dist[(int)diags_dist->ptrs[row_offset + i2]]);\n\t\t\t\t\t}\n\t\t\t\t\t// do over-relaxation if necessary\n\t\t\t\t\tif (omega != 1) {\n\t\t\t\t\t\tsoln2[i2] = ((1-omega) * soln[row_offset + i2]) + (omega * soln2[i2]);\n\t\t\t\t\t}\n\t\t\t\t\t// set vector element\n\t\t\t\t\thelper.updateValue(soln[row_offset + i2], soln[row_offset + i2], soln2[i2], from_below);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_above, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below, soln_above, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\t\t\n//\t\tPN_PrintToMainLog(env, \"%.2f %.2f sec\\n\", ((double)(util_cpu_time() - start3)/1000), ((double)(util_cpu_time() - start2)/1000)/iters);\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%sPseudo %s (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", forwards?\"\":\"Backwards \", (omega == 1.0)?\"Gauss-Seidel\":\"SOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (hddm) delete hddm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete[] soln2;\n\tif (soln_above) delete[] soln_above;\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void psor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tpsor_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tpsor_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] -= soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tif (!transpose) {\n\t\t\tpsor_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tpsor_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, transpose);\n\t\t} else {\n\t\t\tpsor_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tpsor_rec(e->type.kids.t, level+1, row_offset+e->off.val, col_offset, transpose);\n\t\t}\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tif (!transpose) {\n\t\t\tpsor_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, transpose);\n\t\t\tpsor_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, transpose);\n\t\t} else {\n\t\t\tpsor_rec(t->type.kids.e, level+1, row_offset, col_offset+hdd->off.val, transpose);\n\t\t\tpsor_rec(t->type.kids.t, level+1, row_offset+t->off.val, col_offset+hdd->off.val, transpose);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void psor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] -= soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void psor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] -= soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_Power.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <new>\n#include <memory>\n\n// local prototypes\nstatic void power_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose);\nstatic void power_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void power_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=x with the Power method\n// in addition, solutions may be provided for additional states in the vector b\n// these states are assumed not to have non-zero rows in the matrix A\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1Power\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose\t// transpose A? (i.e. solve xA=x not Ax=x?)\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_b;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *b_vec = NULL, *tmpsoln = NULL;\n\tDistVector *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tdouble x, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true, transpose);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false, transpose);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete[] b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, init, rvars, num_rvars, odd);\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PH_Power\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// matrix multiply\n\t\t\n\t\t// initialise vector\n\t\tif (b == NULL) {\n\t\t\tfor (i = 0; i < n; i++) { soln2[i] = 0.0; }\n\t\t} else if (!compact_b) {\n\t\t\tfor (i = 0; i < n; i++) { soln2[i] = b_vec[i]; }\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) { soln2[i] = b_dist->dist[b_dist->ptrs[i]]; }\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tpower_rec(hdd, 0, 0, 0, transpose);\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln2, n, 0);\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln, soln2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\nPower method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (hddm) delete hddm;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void power_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tpower_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tpower_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] += soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tif (!transpose) {\n\t\t\tpower_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tpower_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, transpose);\n\t\t} else {\n\t\t\tpower_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tpower_rec(e->type.kids.t, level+1, row_offset+e->off.val, col_offset, transpose);\n\t\t}\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tif (!transpose) {\n\t\t\tpower_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, transpose);\n\t\t\tpower_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, transpose);\n\t\t} else {\n\t\t\tpower_rec(t->type.kids.e, level+1, row_offset, col_offset+hdd->off.val, transpose);\n\t\t\tpower_rec(t->type.kids.t, level+1, row_offset+t->off.val, col_offset+hdd->off.val, transpose);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void power_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void power_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_PowerInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n// local prototypes\nstatic void power_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose);\nstatic void power_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void power_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=x with the Power method, interval variant\n// in addition, solutions may be provided for additional states in the vector b\n// these states are assumed not to have non-zero rows in the matrix A\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1PowerInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=x not Ax=x?)\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t// upper bound values\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_b;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *b_vec = NULL, *tmpsoln = NULL;\n\tdouble *soln_below = NULL, *soln_below2 = NULL, *soln_above = NULL, *soln_above2 = NULL;\n\tDistVector *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tdouble kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNormInterval measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tIntervalIteration helper(flags);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true, transpose);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false, transpose);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete[] b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tsoln_above = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tsoln_below2 = new double[n];\n\tsoln_above2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 4*kb;\n\tPN_PrintMemoryToMainLog(env, \"[4 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PH_Power_Interval\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// matrix multiply\n\n\t\t// initialise vector (below & above)\n\t\tif (b == NULL) {\n\t\t\tfor (i = 0; i < n; i++) { soln_below2[i] = soln_above2[i] = 0.0; }\n\t\t} else if (!compact_b) {\n\t\t\tfor (i = 0; i < n; i++) { soln_below2[i] = soln_above2[i] = b_vec[i]; }\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) { soln_below2[i] = soln_above2[i] = b_dist->dist[b_dist->ptrs[i]]; }\n\t\t}\n\n\t\t// set global solution vector to below\n\t\tsoln = soln_below;\n\t\tsoln2 = soln_below2;\n\t\t// do matrix vector multiply bit (below)\n\t\tpower_rec(hdd, 0, 0, 0, transpose);\n\n\t\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\t\thelper.ensureMonotonicityFromBelow(soln, soln2, n);\n\t\t}\n\n\n\t\t// set global solution vector to above\n\t\tsoln = soln_above;\n\t\tsoln2 = soln_above2;\n\t\t// do matrix vector multiply bit (above)\n\t\tpower_rec(hdd, 0, 0, 0, transpose);\n\n\t\tif (helper.flag_ensure_monotonic_from_above()) {\n\t\t\thelper.ensureMonotonicityFromAbove(soln, soln2, n);\n\t\t}\n\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_above, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below2, soln_above2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln_below;\n\t\tsoln_below = soln_below2;\n\t\tsoln_below2 = tmpsoln;\n\t\ttmpsoln = soln_above;\n\t\tsoln_above = soln_above2;\n\t\tsoln_above2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\nPower method (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (hddm) delete hddm;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete soln_below2;\n\tif (soln_above) delete soln_above;\n\tif (soln_above2) delete soln_above2;\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void power_rec(HDDNode *hdd, int level, int row_offset, int col_offset, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tpower_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tpower_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] += soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tif (!transpose) {\n\t\t\tpower_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tpower_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, transpose);\n\t\t} else {\n\t\t\tpower_rec(e->type.kids.e, level+1, row_offset, col_offset, transpose);\n\t\t\tpower_rec(e->type.kids.t, level+1, row_offset+e->off.val, col_offset, transpose);\n\t\t}\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tif (!transpose) {\n\t\t\tpower_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, transpose);\n\t\t\tpower_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, transpose);\n\t\t} else {\n\t\t\tpower_rec(t->type.kids.e, level+1, row_offset, col_offset+hdd->off.val, transpose);\n\t\t\tpower_rec(t->type.kids.t, level+1, row_offset+t->off.val, col_offset+hdd->off.val, transpose);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void power_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void power_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_ProbBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln, *soln2;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1ProbBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njint bound\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_y;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *yes_vec = NULL, *tmpsoln = NULL;\n\tDistVector *yes_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tdouble kb, kbt;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get a - filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of yes\n\tPN_PrintToMainLog(env, \"Creating vector for yes... \");\n\tyes_vec = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tcompact_y = false;\n\t// try and convert to compact form if required\n\tif (compact) {\n\t\tif ((yes_dist = double_vector_to_dist(yes_vec, n))) {\n\t\t\tcompact_y = true;\n\t\t\tdelete[] yes_vec; yes_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_y) ? n*8.0/1024.0 : (yes_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_y) PN_PrintToMainLog(env, \"[dist=%d, compact] \", yes_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t//for(i = 0; i < n; i++) printf(\"%f \", (!compact_y)?(yes_vec[i]):(yes_dist->dist[yes_dist->ptrs[i]])); printf(\"\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is yes\n\tif (!compact_y) {\n\t\tfor (i = 0; i < n; i++) { soln[i] = yes_vec[i]; }\n\t} else {\n\t\tfor (i = 0; i < n; i++) { soln[i] = yes_dist->dist[yes_dist->ptrs[i]]; }\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\n\t\t// initialise vector\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln2[i] = 0;\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\n\t\tif (!compact_y) {\n\t\t\tfor (i = 0; i < n; i++) { if (yes_vec[i]) soln2[i] = 1.0; }\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) { if (yes_dist->dist[yes_dist->ptrs[i]]) soln2[i] = 1.0; }\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (hddm) delete hddm;\n\tif (yes_vec) delete[] yes_vec;\n\tif (yes_dist) delete yes_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] += soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_ProbCumulReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1ProbCumulReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njint bound\t\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *all_rewards = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_r;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *rew_vec = NULL, *tmpsoln = NULL;\n\tDistVector *rew_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tdouble kb, kbt;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(trans, rvars, cvars, num_rvars, odd, true);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// then combine state and transition rewards and put in a vector\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(trans);\n\tall_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, trans);\n\tall_rewards = DD_SumAbstract(ddman, all_rewards, cvars, num_cvars);\n\tCudd_Ref(state_rewards);\n\tall_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, all_rewards);\n\n\t// get vector of rewards\n\tPN_PrintToMainLog(env, \"Creating vector for rewards... \");\n\trew_vec = mtbdd_to_double_vector(ddman, all_rewards, rvars, num_rvars, odd);\n\t// try and convert to compact form if required\n\tcompact_r = false;\n\tif (compact) {\n\t\tif ((rew_dist = double_vector_to_dist(rew_vec, n))) {\n\t\t\tcompact_r = true;\n\t\t\tdelete[] rew_vec; rew_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_r) ? n*8.0/1024.0 : (rew_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_r) PN_PrintToMainLog(env, \"[dist=%d, compact] \", rew_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is zero\n\tfor (i = 0; i < n; i++) {\n\t\tsoln[i] = 0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\n\t\t// initialise vector\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln2[i] = (!compact_r) ? rew_vec[i] : rew_dist->dist[rew_dist->ptrs[i]];\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (all_rewards) Cudd_RecursiveDeref(ddman, all_rewards);\n\tif (hddm) delete hddm;\n\tif (rew_vec) delete[] rew_vec;\n\tif (rew_dist) delete rew_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] += soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_ProbInstReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset);\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1ProbInstReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njint bound\t\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\t\n\t// model stats\n\tint n;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *tmpsoln = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tdouble kb, kbt;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(trans, rvars, cvars, num_rvars, odd, true);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\t// (solution is initialised to the state rewards)\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, state_rewards, rvars, num_rvars, odd);\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\n\t\t// initialise vector\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln2[i] = 0.0;\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (hddm) delete hddm;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] += soln[col_offset] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + i2] += soln[col_offset + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + i2, col_offset + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_ProbReachReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1ProbReachReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m\t// 'maybe' states\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n;\n\t// vectors\n\tdouble *soln = NULL, *inf_vec = NULL;\n\t// misc\n\tint i;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// take copy of state/trans rewards\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(trans_rewards);\n\t\n\t// remove goal and infinity states from state rewards vector\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\t\n\t// combine state and transition rewards and put in a vector\n\tCudd_Ref(trans_rewards);\n\tstate_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, trans_rewards);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, 1.0)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_PGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BPGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, lin_eq_method_param)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, lin_eq_method_param, false)); break;\n\t\tcase LIN_EQ_METHOD_PSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BPSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, lin_eq_method_param, false)); break;\n\t}\n\t\n\t// set reward for infinity states to infinity\n\tif (soln != NULL) {\n\t\t// first, generate vector for inf\n\t\tinf_vec = mtbdd_to_double_vector(ddman, inf, rvars, num_rvars, odd);\n\t\t// go thru setting elements of soln to infinity\n\t\tfor (i = 0; i < n; i++) if (inf_vec[i] > 0) soln[i] = HUGE_VAL;\n\t\tdelete[] inf_vec;\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free remaining memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (state_rewards) Cudd_RecursiveDeref(ddman, state_rewards);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_ProbReachRewardInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"IntervalIteration.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1ProbReachRewardInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t// 'maybe' states\njlong __jlongpointer l,  // lower bound\njlong __jlongpointer u,   // upper bound\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\tDdNode *lower = jlong_to_DdNode(l);\t\t// lower bound\n\tDdNode *upper = jlong_to_DdNode(u);\t\t// upper bound\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n;\n\t// vectors\n\tdouble *soln = NULL, *inf_vec = NULL;\n\t// misc\n\tint i;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// take copy of state/trans rewards\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(trans_rewards);\n\t\n\t// remove goal and infinity states from state rewards vector\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\t\n\t// combine state and transition rewards and put in a vector\n\tCudd_Ref(trans_rewards);\n\tstate_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, trans_rewards);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PowerInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, flags)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, flags)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, false, flags)); break;\n\t\tcase LIN_EQ_METHOD_PGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BPGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, false, flags)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, flags)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, false, flags)); break;\n\t\tcase LIN_EQ_METHOD_PSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BPSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, false, flags)); break;\n\t}\n\t\n\t// set reward for infinity states to infinity\n\tif (soln != NULL) {\n\t\t// first, generate vector for inf\n\t\tinf_vec = mtbdd_to_double_vector(ddman, inf, rvars, num_rvars, odd);\n\t\t// go thru setting elements of soln to infinity\n\t\tfor (i = 0; i < n; i++) if (inf_vec[i] > 0) soln[i] = HUGE_VAL;\n\t\tdelete[] inf_vec;\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free remaining memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (state_rewards) Cudd_RecursiveDeref(ddman, state_rewards);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_ProbTransient.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include <prism.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset);\nstatic void mult_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1ProbTransient\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer in,\t// initial distribution (note: this will be deleted afterwards)\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njint time\t\t// time\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tdouble *init = jlong_to_double(in);\t\t\t// initial distribution\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// model stats\n\tint n;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *tmpsoln = NULL, *sum = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint i, iters;\n\tdouble kb, kbt;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states from odd\n\tn = odd->eoff + odd->toff;\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(trans, rvars, cvars, num_rvars, odd, false);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\t// for soln, we just use init (since we are free to modify/delete this vector)\n\t// we also report the memory usage of this vector here, even though it has already been created\n\tsoln = init;\n\tsoln2 = new double[n];\n\tsum = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start transient analysis\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < time && !done; iters++) {\n\t\t\n\t\t// initialise vector\n\t\tfor (i = 0; i < n; i++) soln2[i] = 0.0;\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) {\n\t\t\tmeasure.reset();\n\t\t\tmeasure.measure(soln, soln2, n);\n\t\t\tif (measure.value() < term_crit_param) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)time);\n\t\t\tif (do_ss_detect) PN_PrintToMainLog(env, \"max %sdiff=%f, \", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (done) PN_PrintToMainLog(env, \"\\nSteady state detected at iteration %d\\n\", iters);\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (hddm) delete hddm;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_cm((CMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsc((CMSCSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", col_offset, row_offset, hdd->type.val);\n\t\tsoln2[col_offset] += soln[row_offset] * (hdd->type.val);\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsm->n;\n\tint sm_nnz = cmsm->nnz;\n\tdouble *sm_non_zeros = cmsm->non_zeros;\n\tunsigned char *sm_col_counts = cmsm->col_counts;\n\tint *sm_col_starts = (int *)cmsm->col_counts;\n\tbool sm_use_counts = cmsm->use_counts;\n\tunsigned int *sm_rows = cmsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[col_offset + i2] += soln[row_offset + sm_rows[j2]] * (sm_non_zeros[j2]);\n\t\t\t//printf(\"(%d,%d)=%f\\n\", col_offset + sm_rows[j2], row_offset + i2, sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmscsm->n;\n\tint sm_nnz = cmscsm->nnz;\n\tunsigned char *sm_col_counts = cmscsm->col_counts;\n\tint *sm_col_starts = (int *)cmscsm->col_counts;\n\tbool sm_use_counts = cmscsm->use_counts;\n\tunsigned int *sm_rows = cmscsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[col_offset + i2] += soln[row_offset + (int)(sm_rows[j2] >> sm_dist_shift)] * (sm_dist[(int)(sm_rows[j2] & sm_dist_mask)]);\n\t\t\t//printf(\"(%d,%d)=%f\\n\", col_offset + (int)(sm_rows[j2] >> sm_dist_shift), row_offset + i2, sm_dist[(int)(sm_rows[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_ProbUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1ProbUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m\t// 'maybe' states\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL, *b = NULL, *tmp = NULL;\n\t// vectors\n\tdouble *soln = NULL;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp = DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// build b\n\tCudd_Ref(yes);\n\tb = yes;\n\t\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, 1.0)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_PGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BPGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, lin_eq_method_param)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, lin_eq_method_param, false)); break;\n\t\tcase LIN_EQ_METHOD_PSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BPSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, lin_eq_method_param, false)); break;\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (b) Cudd_RecursiveDeref(ddman, b);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_ProbUntilInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"IntervalIteration.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1ProbUntilInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL, *b = NULL, *lower = NULL, *upper = NULL, *tmp = NULL;\n\t// vectors\n\tdouble *soln = NULL;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp = DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// build b\n\tCudd_Ref(yes);\n\tb = yes;\n\t// lower bounds = b\n\tCudd_Ref(b);\n\tlower = b;\n\n\t// build upper (yes and maybe = 1)\n\tCudd_Ref(yes);\n\tCudd_Ref(maybe);\n\tupper = DD_Or(ddman, yes, maybe);\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PowerInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, flags)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, flags)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, false, flags)); break;\n\t\tcase LIN_EQ_METHOD_PGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BPGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, false, flags)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, flags)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, false, flags)); break;\n\t\tcase LIN_EQ_METHOD_PSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BPSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, false, flags)); break;\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (b) Cudd_RecursiveDeref(ddman, b);\n\tif (lower) Cudd_RecursiveDeref(ddman, lower);\n\tif (upper) Cudd_RecursiveDeref(ddman, upper);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_SOR.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Rashid Mehmood <rxm@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <new>\n#include <memory>\n\n// local prototypes\nstatic void sor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, int r, int c, bool transpose);\nstatic void sor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, int r, int c, bool is_diag);\nstatic void sor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, int r, int c, bool is_diag);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_d, compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *diags_vec = NULL;\nstatic DistVector *diags_dist = NULL;\nstatic double *soln = NULL, *soln2 = NULL;\nstatic double omega;\nstatic bool forwards; \nstatic MeasureSupNorm* measure = NULL;\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Gauss-Seidel/SOR\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1SOR\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble om,\t\t\t// omega (over-relaxation parameter)\njboolean fwds\t\t// forwards or backwards?\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\n\tomega = om;\n\tforwards = fwds;\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_b, l_b_max;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *b_vec = NULL;\n\tDistVector *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, fb, l, h, i2, h2, iters;\n\tdouble kb, kbt;\n\tbool done, diag_done;\n\t// measure for convergence termination check\n\t// dynamically allocated so sor_rm and sor_cmsr have access as well\n\tmeasure = new MeasureSupNorm(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true, transpose);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// split hdd matrix into blocks\n\t// nb: in terms of memory, this gets precedence over sparse matrices\n\tPN_PrintToMainLog(env, \"Splitting into blocks... \");\n\tsplit_hdd_matrix(hddm, compact, false, transpose);\n\tcompact_b = hddm->compact_b;\n\trearrange_hdd_blocks(hddm, false);\n\tkb = hddm->mem_b;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, n=%d, nnz=%d%s] \", hddm->l_b, hddm->blocks->n, hddm->blocks->nnz, compact_b?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, true, transpose);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tl_b_max = (hddm->l_b == hddm->num_levels);\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix (and then setting to 1 if sum is 0)\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = hdd_negative_row_sums(hddm, n, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete[] b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, init, rvars, num_rvars, odd);\n\tsoln2 = new double[hddm->blocks->max];\n\tfor (i = 0; i < hddm->blocks->max; i++) soln2[i] = 0;\n\tkb = (n*8.0/1024.0)+(hddm->blocks->max*8.0/1024.0);\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", (n*8.0/1024.0), \"\");\n\tPN_PrintMemoryToMainLog(env, \" + \", (hddm->blocks->max*8.0/1024.0), \"\");\n\tPN_PrintMemoryToMainLog(env, \" = \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PH_SOR (\");\n\t\ttitle += (omega == 1.0)?\"Gauss-Seidel\": (\"SOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\tmeasure->reset();\n\t\t\n\t\t// stuff for block storage\n\t\tint b_n = hddm->blocks->n;\n\t\tint b_nnz = hddm->blocks->nnz;\n\t\tHDDNode **b_blocks = hddm->blocks->blocks;\n\t\tunsigned int *b_rowscols = hddm->blocks->rowscols;\n\t\tunsigned char *b_counts = hddm->blocks->counts;\n\t\tint *b_starts = (int *)hddm->blocks->counts;\n\t\tbool b_use_counts = hddm->blocks->use_counts;\n\t\tint *b_offsets = hddm->blocks->offsets;\n\t\tHDDNode **b_nodes = hddm->row_tables[hddm->l_b];\n\t\tint b_dist_shift = hddm->blocks->dist_shift;\n\t\tint b_dist_mask = hddm->blocks->dist_mask;\n\t\tint row_offset, col_offset;\n\t\tHDDNode *node;\n\t\t\n\t\t// loop through rows of blocks\n\t\tl = b_nnz; h = 0;\n\t\tfor(fb = 0; fb < b_n; fb++)\n\t\t{\n\t\t\t// loop actually over i (can do forwards or backwards sor/gs)\n\t\t\ti = (forwards) ? fb : b_n-1-fb;\n\t\t\t\n\t\t\t// store block row offset\n\t\t\trow_offset = b_offsets[i];\n\t\t\t\n\t\t\t// initialise (partial) solution vector\n\t\t\th2 = b_offsets[i+1] - b_offsets[i];\n\t\t\t// initialise vector\n\t\t\tif (b == NULL) {\n\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = 0.0; }\n\t\t\t} else if (!compact_b) {\n\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = b_vec[row_offset + i2]; }\n\t\t\t} else {\n\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = b_dist->dist[b_dist->ptrs[row_offset + i2]]; }\n\t\t\t}\n\t\t\t\n\t\t\t// loop through blocks in this row of blocks\n\t\t\tif (!b_use_counts) { l = b_starts[i]; h = b_starts[i+1]; }\n\t\t\telse if (forwards) { l = h; h += b_counts[i]; }\n\t\t\telse { h = l; l -= b_counts[i]; }\n\t\t\tdiag_done = false;\n\t\t\tfor(j = l; j < h; j++)\n\t\t\t{\n\t\t\t\t// get node for block and its col offset\n\t\t\t\tif (!compact_b) {\n\t\t\t\t\tnode = b_blocks[j];\n\t\t\t\t\tcol_offset = b_offsets[b_rowscols[j]];\n\t\t\t\t} else {\n\t\t\t\t\tnode = b_nodes[(int)(b_rowscols[j] & b_dist_mask)];\n\t\t\t\t\tcol_offset = b_offsets[(int)(b_rowscols[j] >> b_dist_shift)];\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// trivial case where we are the bottom of the mtbdd already\n\t\t\t\tif (l_b_max) {\n\t\t\t\t\tsoln2[0] -= soln[col_offset] * node->type.val;\n\t\t\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, node->type.val);\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// non-diagonal blocks treated normally\n\t\t\t\t// (diagonal should be the last block, unless it is absent because empty)\n\t\t\t\tif ((j != h-1) || (j == h-1 && row_offset !=col_offset)) {\n\t\t\t\t\tsor_rec(node, hddm->l_b, row_offset, col_offset, 0, 0, transpose);\n\t\t\t\t}\n\t\t\t\t// diagonal blocks (last blocks in row/col) are different\n\t\t\t\t// call sparse matrix traversal directly with \"is_diag\" flag = true\n\t\t\t\telse {\n\t\t\t\t\tdiag_done = true;\n\t\t\t\t\tif (!compact_sm) {\n\t\t\t\t\t\tsor_rm((RMSparseMatrix *)node->sm.ptr, row_offset, col_offset, 0, 0, true);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tsor_cmsr((CMSRSparseMatrix *)node->sm.ptr, row_offset, col_offset, 0, 0, true);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// if we never found a diagonal block (because it is empty and so not there),\n\t\t\t// then we do the stuff that should have been done after the processing of the diagonal block\n\t\t\tif (!l_b_max && !diag_done) for (i2 = 0; i2 < h2; i2++) {\n\t\t\t\t// divide by diagonal\n\t\t\t\tif (!compact_d) {\n\t\t\t\t\tsoln2[i2] *= diags_vec[row_offset + i2];\n\t\t\t\t} else {\n\t\t\t\t\tsoln2[i2] *= (diags_dist->dist[(int)diags_dist->ptrs[row_offset + i2]]);\n\t\t\t\t}\n\t\t\t\t// do over-relaxation if necessary\n\t\t\t\tif (omega != 1) {\n\t\t\t\t\tsoln2[i2] = ((1-omega) * soln[row_offset + i2]) + (omega * soln2[i2]);\n\t\t\t\t}\n\t\t\t\t// compute norm for convergence\n\t\t\t\tmeasure->measure(soln[row_offset + i2], soln2[i2]);\n\t\t\t\t// set vector element\n\t\t\t\tsoln[row_offset + i2] = soln2[i2];\n\t\t\t}\n\n\t\t\t// trivial case where we are the bottom of the mtbdd already\n\t\t\tif (l_b_max) {\n\t\t\t\tsoln2[0] *= ((!compact_d)?(diags_vec[row_offset]):(diags_dist->dist[(int)diags_dist->ptrs[row_offset]]));\n\t\t\t\tif (omega != 1) soln2[0] = ((1-omega) * soln[row_offset]) + (omega * soln2[0]);\n\t\t\t\tmeasure->measure(soln[row_offset], soln2[0]);\n\t\t\t\tsoln[row_offset] = soln2[0];\n\t\t\t}\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln, n, 0);\n\n\t\t// check convergence\n\t\tif (measure->value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure->isRelative()?\"relative \":\"\", measure->value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s%s: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", forwards?\"\":\"Backwards \", (omega == 1.0)?\"Gauss-Seidel\":\"SOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure->value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (hddm) delete hddm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete[] soln2;\n\tif (measure) delete measure;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void sor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, int r, int c, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tsor_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset, r, c, false);\n\t\t} else {\n\t\t\tsor_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset, r, c, false);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[r] -= soln[col_offset+c] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tif (!transpose) {\n\t\t\tsor_rec(e->type.kids.e, level+1, row_offset, col_offset, r, c, transpose);\n\t\t\tsor_rec(e->type.kids.t, level+1, row_offset, col_offset, r, c+e->off.val, transpose);\n\t\t} else {\n\t\t\tsor_rec(e->type.kids.e, level+1, row_offset, col_offset, r, c, transpose);\n\t\t\tsor_rec(e->type.kids.t, level+1, row_offset, col_offset, r+e->off.val, c, transpose);\n\t\t}\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tif (!transpose) {\n\t\t\tsor_rec(t->type.kids.e, level+1, row_offset, col_offset, r+hdd->off.val, c, transpose);\n\t\t\tsor_rec(t->type.kids.t, level+1, row_offset, col_offset, r+hdd->off.val, c+t->off.val, transpose);\n\t\t} else {\n\t\t\tsor_rec(t->type.kids.e, level+1, row_offset, col_offset, r, c+hdd->off.val, transpose);\n\t\t\tsor_rec(t->type.kids.t, level+1, row_offset, col_offset, r+t->off.val, c+hdd->off.val, transpose);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void sor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, int r, int c, bool is_diag)\n{\n\tint fb2, i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (fb2 = 0; fb2 < sm_n; fb2++) {\n\t\t\n\t\t// loop actually over i2 (can do forwards or backwards sor/gs)\n\t\ti2 = (forwards) ? fb2 : sm_n-1-fb2;\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse if (forwards) { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\telse { h2 = l2; l2 -= sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[r + i2] -= soln[col_offset + c + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", r + i2, col_offset + c + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t\t\n\t\tif (is_diag) {\n\t\t\t// divide by diagonal\n\t\t\tif (!compact_d) {\n\t\t\t\tsoln2[r + i2] *= diags_vec[row_offset + r + i2];\n\t\t\t} else {\n\t\t\t\tsoln2[r + i2] *= (diags_dist->dist[(int)diags_dist->ptrs[row_offset + r + i2]]);\n\t\t\t}\n\t\t\t// do over-relaxation if necessary\n\t\t\tif (omega != 1) {\n\t\t\t\tsoln2[r + i2] = ((1-omega) * soln[row_offset + r + i2]) + (omega * soln2[r + i2]);\n\t\t\t}\n\t\t\t// compute norm for convergence\n\t\t\tmeasure->measure(soln[row_offset + r + i2], soln2[r + i2]);\n\t\t\t// set vector element\n\t\t\tsoln[row_offset + r + i2] = soln2[r + i2];\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void sor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, int r, int c, bool is_diag)\n{\n\tint fb2, i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (fb2 = 0; fb2 < sm_n; fb2++) {\n\t\t\n\t\t// loop actually over i2 (can do forwards or backwards sor/gs)\n\t\ti2 = (forwards) ? fb2 : sm_n-1-fb2;\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse if (forwards) { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\telse { h2 = l2; l2 -= sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[r + i2] -= soln[col_offset + c + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + r + i2, col_offset + c + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t\t\n\t\tif (is_diag) {\n\t\t\t// divide by diagonal\n\t\t\tif (!compact_d) {\n\t\t\t\tsoln2[r + i2] *= diags_vec[row_offset + r + i2];\n\t\t\t} else {\n\t\t\t\tsoln2[r + i2] *= (diags_dist->dist[(int)diags_dist->ptrs[row_offset + r + i2]]);\n\t\t\t}\n\t\t\t// do over-relaxation if necessary\n\t\t\tif (omega != 1) {\n\t\t\t\tsoln2[r + i2] = ((1-omega) * soln[row_offset + r + i2]) + (omega * soln2[r + i2]);\n\t\t\t}\n\t\t\t// compute norm for convergence\n\t\t\tmeasure->measure(soln[row_offset + r + i2], soln2[r + i2]);\n\t\t\t// set vector element\n\t\t\tsoln[row_offset + r + i2] = soln2[r + i2];\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_SORInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Rashid Mehmood <rxm@cs.bham.ac.uk> (University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n// local prototypes\nstatic void sor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, int r, int c, bool transpose);\nstatic void sor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, int r, int c, bool is_diag);\nstatic void sor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, int r, int c, bool is_diag);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_d, compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *diags_vec = NULL;\nstatic DistVector *diags_dist = NULL;\nstatic double *soln = NULL, *soln2 = NULL;\nstatic double omega;\nstatic bool forwards;\nstatic IntervalIteration* _helper = NULL;\nstatic bool from_below;\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Gauss-Seidel/SOR, interval variant\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1SORInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble om,\t\t\t// omega (over-relaxation parameter)\njboolean fwds,\t\t// forwards or backwards?\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t// upper bound values\n\n\tomega = om;\n\tforwards = fwds;\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_b, l_b_max;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *b_vec = NULL;\n\tDistVector *b_dist = NULL;\n\tdouble *soln_below = NULL, *soln_above = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, fb, l, h, i2, h2, iters;\n\tdouble kb, kbt;\n\tbool done, diag_done;\n\t// measure for convergence termination check\n\tMeasureSupNormInterval measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tif (omega <= 0.0 || omega > 1.0) {\n\t\tPN_SetErrorMessage(\"Interval iteration requires 0 < omega <= 1.0, have omega = %g\", omega);\n\t\treturn ptr_to_jlong(NULL);\n\t}\n\n\tIntervalIteration helper(flags);\n\t_helper = &helper; // store globally for recursion\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(a, rvars, cvars, num_rvars, odd, true, transpose);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// split hdd matrix into blocks\n\t// nb: in terms of memory, this gets precedence over sparse matrices\n\tPN_PrintToMainLog(env, \"Splitting into blocks... \");\n\tsplit_hdd_matrix(hddm, compact, false, transpose);\n\tcompact_b = hddm->compact_b;\n\trearrange_hdd_blocks(hddm, false);\n\tkb = hddm->mem_b;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, n=%d, nnz=%d%s] \", hddm->l_b, hddm->blocks->n, hddm->blocks->nnz, compact_b?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, true, transpose);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tl_b_max = (hddm->l_b == hddm->num_levels);\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix (and then setting to 1 if sum is 0)\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = hdd_negative_row_sums(hddm, n, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete[] b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tsoln_above = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tsoln2 = new double[hddm->blocks->max];\n\tfor (i = 0; i < hddm->blocks->max; i++) soln2[i] = 0;\n\tkb = 2*(n*8.0/1024.0)+(hddm->blocks->max*8.0/1024.0);\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", (n*8.0/1024.0), \"\");\n\tPN_PrintMemoryToMainLog(env, \" + \", (hddm->blocks->max*8.0/1024.0), \"\");\n\tPN_PrintMemoryToMainLog(env, \" = \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PH_SORInterval (\");\n\t\ttitle += (omega == 1.0)?\"Gauss-Seidel\": (\"SOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// stuff for block storage\n\t\tint b_n = hddm->blocks->n;\n\t\tint b_nnz = hddm->blocks->nnz;\n\t\tHDDNode **b_blocks = hddm->blocks->blocks;\n\t\tunsigned int *b_rowscols = hddm->blocks->rowscols;\n\t\tunsigned char *b_counts = hddm->blocks->counts;\n\t\tint *b_starts = (int *)hddm->blocks->counts;\n\t\tbool b_use_counts = hddm->blocks->use_counts;\n\t\tint *b_offsets = hddm->blocks->offsets;\n\t\tHDDNode **b_nodes = hddm->row_tables[hddm->l_b];\n\t\tint b_dist_shift = hddm->blocks->dist_shift;\n\t\tint b_dist_mask = hddm->blocks->dist_mask;\n\t\tint row_offset, col_offset;\n\t\tHDDNode *node;\n\t\tint it;\n\n\t\tfor (it = 0; it <= 1; it++) {\n\t\t\tif (it == 0) {\n\t\t\t\t// from below\n\t\t\t\tfrom_below = true;\n\t\t\t\tsoln = soln_below;\n\t\t\t} else {\n\t\t\t\t// from above\n\t\t\t\tfrom_below = false;\n\t\t\t\tsoln = soln_above;\n\t\t\t}\n\n\t\t\t// loop through rows of blocks\n\t\t\tl = b_nnz; h = 0;\n\t\t\tfor(fb = 0; fb < b_n; fb++)\n\t\t\t{\n\t\t\t\t// loop actually over i (can do forwards or backwards sor/gs)\n\t\t\t\ti = (forwards) ? fb : b_n-1-fb;\n\n\t\t\t\t// store block row offset\n\t\t\t\trow_offset = b_offsets[i];\n\n\t\t\t\t// initialise (partial) solution vector\n\t\t\t\th2 = b_offsets[i+1] - b_offsets[i];\n\t\t\t\t// initialise vector\n\t\t\t\tif (b == NULL) {\n\t\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = 0.0; }\n\t\t\t\t} else if (!compact_b) {\n\t\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = b_vec[row_offset + i2]; }\n\t\t\t\t} else {\n\t\t\t\t\tfor (i2 = 0; i2 < h2; i2++) { soln2[i2] = b_dist->dist[b_dist->ptrs[row_offset + i2]]; }\n\t\t\t\t}\n\n\t\t\t\t// loop through blocks in this row of blocks\n\t\t\t\tif (!b_use_counts) { l = b_starts[i]; h = b_starts[i+1]; }\n\t\t\t\telse if (forwards) { l = h; h += b_counts[i]; }\n\t\t\t\telse { h = l; l -= b_counts[i]; }\n\t\t\t\tdiag_done = false;\n\t\t\t\tfor(j = l; j < h; j++)\n\t\t\t\t{\n\t\t\t\t\t// get node for block and its col offset\n\t\t\t\t\tif (!compact_b) {\n\t\t\t\t\t\tnode = b_blocks[j];\n\t\t\t\t\t\tcol_offset = b_offsets[b_rowscols[j]];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tnode = b_nodes[(int)(b_rowscols[j] & b_dist_mask)];\n\t\t\t\t\t\tcol_offset = b_offsets[(int)(b_rowscols[j] >> b_dist_shift)];\n\t\t\t\t\t}\n\n\t\t\t\t\t// trivial case where we are the bottom of the mtbdd already\n\t\t\t\t\tif (l_b_max) {\n\t\t\t\t\t\tsoln2[0] -= soln[col_offset] * node->type.val;\n\t\t\t\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, node->type.val);\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\n\t\t\t\t\t// non-diagonal blocks treated normally\n\t\t\t\t\t// (diagonal should be the last block, unless it is absent because empty)\n\t\t\t\t\tif ((j != h-1) || (j == h-1 && row_offset !=col_offset)) {\n\t\t\t\t\t\tsor_rec(node, hddm->l_b, row_offset, col_offset, 0, 0, transpose);\n\t\t\t\t\t}\n\t\t\t\t\t// diagonal blocks (last blocks in row/col) are different\n\t\t\t\t\t// call sparse matrix traversal directly with \"is_diag\" flag = true\n\t\t\t\t\telse {\n\t\t\t\t\t\tdiag_done = true;\n\t\t\t\t\t\tif (!compact_sm) {\n\t\t\t\t\t\t\tsor_rm((RMSparseMatrix *)node->sm.ptr, row_offset, col_offset, 0, 0, true);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tsor_cmsr((CMSRSparseMatrix *)node->sm.ptr, row_offset, col_offset, 0, 0, true);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// if we never found a diagonal block (because it is empty and so not there),\n\t\t\t\t// then we do the stuff that should have been done after the processing of the diagonal block\n\t\t\t\tif (!l_b_max && !diag_done) for (i2 = 0; i2 < h2; i2++) {\n\t\t\t\t\t// divide by diagonal\n\t\t\t\t\tif (!compact_d) {\n\t\t\t\t\t\tsoln2[i2] *= diags_vec[row_offset + i2];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tsoln2[i2] *= (diags_dist->dist[(int)diags_dist->ptrs[row_offset + i2]]);\n\t\t\t\t\t}\n\t\t\t\t\t// do over-relaxation if necessary\n\t\t\t\t\tif (omega != 1) {\n\t\t\t\t\t\tsoln2[i2] = ((1-omega) * soln[row_offset + i2]) + (omega * soln2[i2]);\n\t\t\t\t\t}\n\t\t\t\t\t// set vector element\n\t\t\t\t\thelper.updateValue(soln[row_offset + i2], soln[row_offset + i2], soln2[i2], from_below);\n\t\t\t\t}\n\n\t\t\t\t// trivial case where we are the bottom of the mtbdd already\n\t\t\t\tif (l_b_max) {\n\t\t\t\t\tsoln2[0] *= ((!compact_d)?(diags_vec[row_offset]):(diags_dist->dist[(int)diags_dist->ptrs[row_offset]]));\n\t\t\t\t\tif (omega != 1) soln2[0] = ((1-omega) * soln[row_offset]) + (omega * soln2[0]);\n\t\t\t\t\t// set vector element\n\t\t\t\t\thelper.updateValue(soln[row_offset], soln[row_offset], soln2[0], from_below);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_above, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below, soln_above, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s%s (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", forwards?\"\":\"Backwards \", (omega == 1.0)?\"Gauss-Seidel\":\"SOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (hddm) delete hddm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete[] soln2;\n\tif (soln_above) delete[] soln_above;\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void sor_rec(HDDNode *hdd, int level, int row_offset, int col_offset, int r, int c, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tsor_rm((RMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset, r, c, false);\n\t\t} else {\n\t\t\tsor_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, row_offset, col_offset, r, c, false);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[r] -= soln[col_offset+c] * hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tif (!transpose) {\n\t\t\tsor_rec(e->type.kids.e, level+1, row_offset, col_offset, r, c, transpose);\n\t\t\tsor_rec(e->type.kids.t, level+1, row_offset, col_offset, r, c+e->off.val, transpose);\n\t\t} else {\n\t\t\tsor_rec(e->type.kids.e, level+1, row_offset, col_offset, r, c, transpose);\n\t\t\tsor_rec(e->type.kids.t, level+1, row_offset, col_offset, r+e->off.val, c, transpose);\n\t\t}\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tif (!transpose) {\n\t\t\tsor_rec(t->type.kids.e, level+1, row_offset, col_offset, r+hdd->off.val, c, transpose);\n\t\t\tsor_rec(t->type.kids.t, level+1, row_offset, col_offset, r+hdd->off.val, c+t->off.val, transpose);\n\t\t} else {\n\t\t\tsor_rec(t->type.kids.e, level+1, row_offset, col_offset, r, c+hdd->off.val, transpose);\n\t\t\tsor_rec(t->type.kids.t, level+1, row_offset, col_offset, r+t->off.val, c+hdd->off.val, transpose);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void sor_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, int r, int c, bool is_diag)\n{\n\tint fb2, i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (fb2 = 0; fb2 < sm_n; fb2++) {\n\t\t\n\t\t// loop actually over i2 (can do forwards or backwards sor/gs)\n\t\ti2 = (forwards) ? fb2 : sm_n-1-fb2;\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse if (forwards) { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\telse { h2 = l2; l2 -= sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[r + i2] -= soln[col_offset + c + sm_cols[j2]] * sm_non_zeros[j2];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", r + i2, col_offset + c + sm_cols[j2], sm_non_zeros[j2]);\n\t\t}\n\t\t\n\t\tif (is_diag) {\n\t\t\t// divide by diagonal\n\t\t\tif (!compact_d) {\n\t\t\t\tsoln2[r + i2] *= diags_vec[row_offset + r + i2];\n\t\t\t} else {\n\t\t\t\tsoln2[r + i2] *= (diags_dist->dist[(int)diags_dist->ptrs[row_offset + r + i2]]);\n\t\t\t}\n\t\t\t// do over-relaxation if necessary\n\t\t\tif (omega != 1) {\n\t\t\t\tsoln2[r + i2] = ((1-omega) * soln[row_offset + r + i2]) + (omega * soln2[r + i2]);\n\t\t\t}\t\n\t\t\t// set vector element\n\t\t\t_helper->updateValue(soln[row_offset + r + i2], soln[row_offset + r + i2], soln2[r + i2], from_below);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void sor_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, int r, int c, bool is_diag)\n{\n\tint fb2, i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (fb2 = 0; fb2 < sm_n; fb2++) {\n\t\t\n\t\t// loop actually over i2 (can do forwards or backwards sor/gs)\n\t\ti2 = (forwards) ? fb2 : sm_n-1-fb2;\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse if (forwards) { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\telse { h2 = l2; l2 -= sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[r + i2] -= soln[col_offset + c + (int)(sm_cols[j2] >> sm_dist_shift)] * sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + r + i2, col_offset + c + (int)(sm_cols[j2] >> sm_dist_shift), sm_dist[(int)(sm_cols[j2] & sm_dist_mask)]);\n\t\t}\n\t\t\n\t\tif (is_diag) {\n\t\t\t// divide by diagonal\n\t\t\tif (!compact_d) {\n\t\t\t\tsoln2[r + i2] *= diags_vec[row_offset + r + i2];\n\t\t\t} else {\n\t\t\t\tsoln2[r + i2] *= (diags_dist->dist[(int)diags_dist->ptrs[row_offset + r + i2]]);\n\t\t\t}\n\t\t\t// do over-relaxation if necessary\n\t\t\tif (omega != 1) {\n\t\t\t\tsoln2[r + i2] = ((1-omega) * soln[row_offset + r + i2]) + (omega * soln2[r + i2]);\n\t\t\t}\t\n\t\t\t// set vector element\n\t\t\t_helper->updateValue(soln[row_offset + r + i2], soln[row_offset + r + i2], soln2[r + i2], from_below);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_StochBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include <prism.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset);\nstatic void mult_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\nstatic double unif;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1StochBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ye,\t// 'yes' states\njlong __jlongpointer ma,\t// 'maybe' states\njdouble time,\t\t// time bound\njlong __jlongpointer mu\t// probs for multiplying\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(ye);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(ma);\t\t// 'maybe' states\n\tdouble *mult = jlong_to_double(mu);\t\t// probs for multiplying\n\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_d;\n\t// matrix mtbdd\n\tDdNode *r = NULL;\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *diags = NULL, *tmpsoln = NULL, *sum = NULL;\n\tDistVector *diags_dist = NULL;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tlong i, iters, num_iters;\n\tdouble x, kb, kbt, max_diag, weight, term_crit_param_unif;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states from odd\n\tn = odd->eoff + odd->toff;\n\t\n\t// count number of states to be made absorbing\n\tx = DD_GetNumMinterms(ddman, maybe, num_rvars);\n\tPN_PrintToMainLog(env, \"\\nNumber of non-absorbing states: %.0f of %d (%.1f%%)\\n\", x,  n, 100.0*(x/n));\n\t\n\t// filter out rows from rate matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\tr = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(r, rvars, cvars, num_rvars, odd, false);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diagonals\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tdiags = hdd_negative_row_sums(hddm, n);\n\tcompact_d = false;\n\t// try and convert to compact form if required\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags; diags = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t//for(i = 0; i < n; i++) printf(\"%f \", (!compact_d)?(diags[i]):(diags_dist->dist[diags_dist->ptrs[i]])); printf(\"\\n\");\n\t\n\t// find max diagonal element\n\tif (!compact_d) {\n\t\tmax_diag = diags[0];\n\t\tfor (i = 1; i < n; i++) if (diags[i] < max_diag) max_diag = diags[i];\n\t} else {\n\t\tmax_diag = diags_dist->dist[0];\n\t\tfor (i = 1; i < diags_dist->num_dist; i++) if (diags_dist->dist[i] < max_diag) max_diag = diags_dist->dist[i];\n\t}\n\tmax_diag = -max_diag;\n\t\n\t// constant for uniformization\n\tunif = 1.02*max_diag;\n\n\t// modify diagonals\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags[i] = diags[i] / unif + 1;\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = diags_dist->dist[i] / unif + 1;\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tsoln2 = new double[n];\n\tsum = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// multiply initial solution by 'mult' probs\n\tif (mult != NULL) {\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln[i] *= mult[i];\n\t\t}\n\t}\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) throw \"Overflow in Fox-Glynn computation (time bound too big?)\";\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n\t// set up vectors\n\tfor (i = 0; i < n; i++) {\n\t\tsum[i] = 0.0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start transient analysis\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// if necessary, do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) for (i = 0; i < n; i++) {\n\t\tsum[i] += fgw.weights[0] * soln[i];\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\t\n\t\t// initialise vector\n\t\tif (!compact_d) {\n\t\t\tfor (i = 0; i < n; i++) soln2[i] = diags[i] * soln[i];\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) soln2[i] = diags_dist->dist[diags_dist->ptrs[i]] * soln[i];\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) {\n\t\t\tmeasure.reset();\n\t\t\tmeasure.measure(soln, soln2, n);\n\t\t\tif (measure.value() < term_crit_param_unif) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = 1.0;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tfor (i = 0; i < n; i++) sum[i] += weight * soln2[i];\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tif (do_ss_detect) PN_PrintToMainLog(env, \"max %sdiff=%f, \", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t\t\n\t\t// add to sum\n\t\tif (iters >= fgw.left) {\n\t\t\tfor (i = 0; i < n; i++) sum[i] += fgw.weights[iters-fgw.left] * soln[i];\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t} catch (const char *err) {\n\t\tPN_SetErrorMessage(\"%s\", err);\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t}\n\t\n\t// free memory\n\tif (r) Cudd_RecursiveDeref(ddman, r);\n\tif (hddm) delete hddm;\n\tif (diags) delete[] diags;\n\tif (diags_dist) delete diags_dist;\n\tif (soln) delete[] soln;\n\tif (soln2) delete[] soln2;\n\tif (fgw.weights) delete[] fgw.weights;\n\t\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_cm((CMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsc((CMSCSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] += soln[col_offset] * (hdd->type.val / unif);\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsm->n;\n\tint sm_nnz = cmsm->nnz;\n\tdouble *sm_non_zeros = cmsm->non_zeros;\n\tunsigned char *sm_col_counts = cmsm->col_counts;\n\tint *sm_col_starts = (int *)cmsm->col_counts;\n\tbool sm_use_counts = cmsm->use_counts;\n\tunsigned int *sm_rows = cmsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + sm_rows[j2]] += soln[col_offset + i2] * (sm_non_zeros[j2] / unif);\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + sm_rows[j2], col_offset + i2, sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmscsm->n;\n\tint sm_nnz = cmscsm->nnz;\n\tunsigned char *sm_col_counts = cmscsm->col_counts;\n\tint *sm_col_starts = (int *)cmscsm->col_counts;\n\tbool sm_use_counts = cmscsm->use_counts;\n\tunsigned int *sm_rows = cmscsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + (int)(sm_rows[j2] >> sm_dist_shift)] += soln[col_offset + i2] * (sm_dist[(int)(sm_rows[j2] & sm_dist_mask)] / unif);\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + (int)(sm_rows[j2] >> sm_dist_shift), col_offset + i2, sm_dist[(int)(sm_rows[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_StochCumulReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include <prism.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset);\nstatic void mult_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\nstatic double unif;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1StochCumulReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njdouble time\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); // row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); // col vars\n\n\t// mtbdds\n\tDdNode *tmp = NULL;\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_d;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *diags = NULL, *tmpsoln = NULL, *sum = NULL;\n\tDistVector *diags_dist = NULL;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tlong i, iters, num_iters;\n\tdouble max_diag, weight, kb, kbt, term_crit_param_unif;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(trans, rvars, cvars, num_rvars, odd, false);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diagonals\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tdiags = hdd_negative_row_sums(hddm, n);\n\tcompact_d = false;\n\t// try and convert to compact form if required\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags; diags = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// find max diagonal element\n\tif (!compact_d) {\n\t\tmax_diag = diags[0];\n\t\tfor (i = 1; i < n; i++) if (diags[i] < max_diag) max_diag = diags[i];\n\t} else {\n\t\tmax_diag = diags_dist->dist[0];\n\t\tfor (i = 1; i < diags_dist->num_dist; i++) if (diags_dist->dist[i] < max_diag) max_diag = diags_dist->dist[i];\n\t}\n\tmax_diag = -max_diag;\n\t\n\t// constant for uniformization\n\tunif = 1.02*max_diag;\n\n\t// modify diagonals\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags[i] = diags[i] / unif + 1;\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = diags_dist->dist[i] / unif + 1;\n\t}\n\t\n\t// combine state/transition rewards into a single vector\n\t// new state rewards = c + (R.C)1\n\t// first, multiply transition rates by transition rewards and sum rows\n\t// = (R.C)1\n\tCudd_Ref(trans);\n\tCudd_Ref(trans_rewards);\n\ttmp = DD_Apply(ddman, APPLY_TIMES, trans, trans_rewards);\n\ttmp = DD_SumAbstract(ddman, tmp, cvars, num_cvars);\n\t// then add state rewards\n\t// = c + (R.C)1\n\tCudd_Ref(state_rewards);\n\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, state_rewards);\n\tsoln = mtbdd_to_double_vector(ddman, tmp, rvars, num_rvars, odd);\n\tCudd_RecursiveDeref(ddman, tmp);\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\t// soln has already been created and initialised to rewards vector as required\n\t// need to create soln2 and sum\n\tsoln2 = new double[n];\n\tsum = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) throw \"Overflow in Fox-Glynn computation (time bound too big?)\";\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n\t// modify the poisson probabilities to what we need for this computation\n\t// first make the kth value equal to the sum of the values for 0...k\n\tfor (i = fgw.left+1; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] += fgw.weights[i-1-fgw.left];\n\t}\n\t// then subtract from 1 and divide by uniformisation constant (q) to give mixed poisson probabilities\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] = (1 - fgw.weights[i-fgw.left]) / unif;\n\t}\n\t\n\t// set up vectors\n\tfor (i = 0; i < n; i++) {\n\t\tsum[i] = 0.0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start transient analysis\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) {\n\t\tfor (i = 0; i < n; i++) sum[i] += fgw.weights[0] * soln[i];\n\t} else {\n\t\tfor (i = 0; i < n; i++) sum[i] += soln[i] / unif;\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\t\n\t\t// initialise vector\n\t\tif (!compact_d) {\n\t\t\tfor (i = 0; i < n; i++) soln2[i] = diags[i] * soln[i];\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) soln2[i] = diags_dist->dist[diags_dist->ptrs[i]] * soln[i];\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) {\n\t\t\tmeasure.reset();\n\t\t\tmeasure.measure(soln, soln2, n);\n\t\t\tif (measure.value() < term_crit_param_unif) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = time - iters/unif;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tfor (i = 0; i < n; i++) sum[i] += weight * soln2[i];\n\t\t\t\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tif (do_ss_detect) PN_PrintToMainLog(env, \"max %sdiff=%f, \", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t\t\n\t\t// add to sum\n\t\tif (iters < fgw.left) {\n\t\t\tfor (i = 0; i < n; i++) sum[i] += soln[i] / unif;\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) sum[i] += fgw.weights[iters-fgw.left] * soln[i];\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t} catch (const char *err) {\n\t\tPN_SetErrorMessage(\"%s\", err);\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t}\n\t\n\t// free memory\n\tif (hddm) delete hddm;\n\tif (diags) delete[] diags;\n\tif (diags_dist) delete diags_dist;\n\tif (soln) delete[] soln;\n\tif (soln2) delete[] soln2;\n\tif (fgw.weights) delete[] fgw.weights;\n\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_cm((CMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsc((CMSCSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tsoln2[row_offset] += soln[col_offset] * (hdd->type.val / unif);\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsm->n;\n\tint sm_nnz = cmsm->nnz;\n\tdouble *sm_non_zeros = cmsm->non_zeros;\n\tunsigned char *sm_col_counts = cmsm->col_counts;\n\tint *sm_col_starts = (int *)cmsm->col_counts;\n\tbool sm_use_counts = cmsm->use_counts;\n\tunsigned int *sm_rows = cmsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + sm_rows[j2]] += soln[col_offset + i2] * (sm_non_zeros[j2] / unif);\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + sm_rows[j2], col_offset + i2, sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmscsm->n;\n\tint sm_nnz = cmscsm->nnz;\n\tunsigned char *sm_col_counts = cmscsm->col_counts;\n\tint *sm_col_starts = (int *)cmscsm->col_counts;\n\tbool sm_use_counts = cmscsm->use_counts;\n\tunsigned int *sm_rows = cmscsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[row_offset + (int)(sm_rows[j2] >> sm_dist_shift)] += soln[col_offset + i2] * (sm_dist[(int)(sm_rows[j2] & sm_dist_mask)] / unif);\n\t\t\t//printf(\"(%d,%d)=%f\\n\", row_offset + (int)(sm_rows[j2] >> sm_dist_shift), col_offset + i2, sm_dist[(int)(sm_rows[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_StochSteadyState.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1StochSteadyState\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer in,\t// init soln\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *init = jlong_to_DdNode(in);\t\t// init soln\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *diags = NULL, *q = NULL, *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n;\n\t// vectors\n\tdouble *soln = NULL;\n\t// misc\n\tint i;\n\tdouble deltat, d;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// if we are going to solve with the power method, we have to modify the matrix a bit\n\tif (lin_eq_method == LIN_EQ_METHOD_POWER) {\n\t\t\n\t\t// technically, this is a little bit wasteful\n\t\t// for sparse/hybrid, we can avoid constructing the diagonals and rate matrix as mtbdds\n\t\t// (as used to be done in version <=2.1 before the power method was generic)\n\t\t// shouldn't be too disasterous though\n\t\t// and if you are that bothered about efficiency, you won't be using the power method anyway...\n\t\t\n\t\t// compute diagonals\n\t\tCudd_Ref(trans);\n\t\tdiags = DD_SumAbstract(ddman, trans, cvars, num_rvars);\n\t\tdiags = DD_Apply(ddman, APPLY_TIMES, diags, DD_Constant(ddman, -1));\n\t\t\n\t\t// choose deltat\n\t\tdeltat = -0.99 / DD_FindMin(ddman, diags);\n\t\t\n\t\t// build generator matrix q from trans and diags\n\t\t// note that any self loops are effectively removed because we include their rates\n\t\t// in the 'diags' row sums and then subtract these from the original rate matrix\n\t\tCudd_Ref(trans);\n\t\tCudd_Ref(diags);\n\t\tq = DD_Apply(ddman, APPLY_PLUS, trans, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), diags));\n\t\t\n\t\t// build iteration matrix\n\t\tPN_PrintToMainLog(env, \"\\nBuilding power method iteration matrix MTBDD... \");\n\t\t// (includes a \"fix\" for when we are solving a subsystem e.g. BSCC)\n\t\t// (although i don't think we actually need this for the power method)\n\t\tCudd_Ref(diags);\n\t\ttmp = DD_LessThan(ddman, diags, 0);\n\t\tCudd_Ref(q);\n\t\ta = DD_Apply(ddman, APPLY_PLUS, DD_Apply(ddman, APPLY_TIMES, DD_Constant(ddman, deltat), q), DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), tmp));\n\t\ti = DD_GetNumNodes(ddman, a);\n\t\tPN_PrintToMainLog(env, \"[nodes=%d] [%.1f Kb]\", i, i*20.0/1024.0);\n\t\t\n\t\t// deref unneeded mtbdds\n\t\tCudd_RecursiveDeref(ddman, diags);\n\t\tCudd_RecursiveDeref(ddman, q);\n\t}\n\telse {\n\t\t// technically, we should remove self-loops (i.e. diagonals) from the rate matrix\n\t\t// but the iterative solution methods remove all diagonals before doing\n\t\t// solution (and before doing row sums) so we don't need to bother\n\t\tCudd_Ref(trans);\n\t\ta = trans;\n\t}\n\t\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, 1.0)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_PGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BPGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, lin_eq_method_param)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, lin_eq_method_param, false)); break;\n\t\tcase LIN_EQ_METHOD_PSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BPSOR:\n\t\t\tsoln = jlong_to_double(Java_hybrid_PrismHybrid_PH_1PSOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, lin_eq_method_param, false)); break;\n\t}\n\t\n\t// normalise\n\tif (soln != NULL) {\n\t\td = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td += soln[i];\n\t\t}\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln[i] /= d;\n\t\t}\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PH_StochTransient.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismHybrid.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include <prism.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include <new>\n\n// local prototypes\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset);\nstatic void mult_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset);\nstatic void mult_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset);\n\n// globals (used by local functions)\nstatic HDDNode *zero;\nstatic int num_levels;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\nstatic double *soln = NULL, *soln2 = NULL;\nstatic double unif;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_hybrid_PrismHybrid_PH_1StochTransient\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer in,\t// initial distribution (note: this will be deleted afterwards)\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njdouble time\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tdouble *init = jlong_to_double(in);\t\t\t// initial distribution\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// model stats\n\tint n;\n\t// flags\n\tbool compact_d;\n\t// matrix mtbdd\n\tHDDMatrix *hddm = NULL;\n\tHDDNode *hdd = NULL;\n\t// vectors\n\tdouble *diags = NULL, *tmpsoln = NULL, *sum = NULL;\n\tDistVector *diags_dist = NULL;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tlong i, iters, num_iters;\n\tdouble kb, kbt, max_diag, weight, term_crit_param_unif;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states from odd\n\tn = odd->eoff + odd->toff;\n\t\n\t// build hdd for matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding hybrid MTBDD matrix... \");\n\thddm = build_hdd_matrix(trans, rvars, cvars, num_rvars, odd, false);\n\thdd = hddm->top;\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\tkb = hddm->mem_nodes;\n\tkbt = kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, nodes=%d] \", hddm->num_levels, hddm->num_nodes);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// add sparse matrices\n\tPN_PrintToMainLog(env, \"Adding explicit sparse matrices... \");\n\tadd_sparse_matrices(hddm, compact, false);\n\tcompact_sm = hddm->compact_sm;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tkb = hddm->mem_sm;\n\tkbt += kb;\n\tPN_PrintToMainLog(env, \"[levels=%d, num=%d%s] \", hddm->l_sm, hddm->num_sm, compact_sm?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diagonals\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tdiags = hdd_negative_row_sums(hddm, n);\n\tcompact_d = false;\n\t// try and convert to compact form if required\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete[] diags; diags = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t//for(i = 0; i < n; i++) printf(\"%f \", (!compact_d)?(diags[i]):(diags_dist->dist[diags_dist->ptrs[i]])); printf(\"\\n\");\n\t\n\t// find max diagonal element\n\tif (!compact_d) {\n\t\tmax_diag = diags[0];\n\t\tfor (i = 1; i < n; i++) if (diags[i] < max_diag) max_diag = diags[i];\n\t} else {\n\t\tmax_diag = diags_dist->dist[0];\n\t\tfor (i = 1; i < diags_dist->num_dist; i++) if (diags_dist->dist[i] < max_diag) max_diag = diags_dist->dist[i];\n\t}\n\tmax_diag = -max_diag;\n\t\n\t// constant for uniformization\n\tunif = 1.02*max_diag;\n\n\t// modify diagonals\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags[i] = diags[i] / unif + 1;\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = diags_dist->dist[i] / unif + 1;\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\t// for soln, we just use init (since we are free to modify/delete this vector)\n\t// we also report the memory usage of this vector here, even though it has already been created\n\tsoln = init;\n\tsoln2 = new double[n];\n\tsum = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) throw \"Overflow in Fox-Glynn computation (time bound too big?)\";\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n\t// set up vectors\n\tfor (i = 0; i < n; i++) {\n\t\tsum[i] = 0.0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start transient analysis\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// if necessary, do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) for (i = 0; i < n; i++) {\n\t\tsum[i] += fgw.weights[0] * soln[i];\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\t\n\t\t// initialise vector\n\t\tif (!compact_d) {\n\t\t\tfor (i = 0; i < n; i++) soln2[i] = diags[i] * soln[i];\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) soln2[i] = diags_dist->dist[diags_dist->ptrs[i]] * soln[i];\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\tmult_rec(hdd, 0, 0, 0);\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) {\n\t\t\tmeasure.reset();\n\t\t\tmeasure.measure(soln, soln2, n);\n\t\t\tif (measure.value() < term_crit_param_unif) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = 1.0;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tfor (i = 0; i < n; i++) sum[i] += weight * soln2[i];\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tif (do_ss_detect) PN_PrintToMainLog(env, \"max %sdiff=%f, \", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t\t\n\t\t// add to sum\n\t\tif (iters >= fgw.left) {\n\t\t\tfor (i = 0; i < n; i++) sum[i] += fgw.weights[iters-fgw.left] * soln[i];\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t} catch (const char *err) {\n\t\tPN_SetErrorMessage(\"%s\", err);\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t}\n\t\n\t// free memory\n\tif (hddm) delete hddm;\n\tif (diags) delete[] diags;\n\tif (diags_dist) delete diags_dist;\n\t// nb: we *do* free soln (which was originally init)\n\tif (soln) delete[] soln;\n\tif (soln2) delete[] soln2;\n\tif (fgw.weights) delete[] fgw.weights;\n\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n\nstatic void mult_rec(HDDNode *hdd, int level, int row_offset, int col_offset)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (!compact_sm) {\n\t\t\tmult_cm((CMSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t} else {\n\t\t\tmult_cmsc((CMSCSparseMatrix *)hdd->sm.ptr, row_offset, col_offset);\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", col_offset, row_offset, hdd->type.val);\n\t\tsoln2[col_offset] += soln[row_offset] * (hdd->type.val / unif);\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\tmult_rec(e->type.kids.e, level+1, row_offset, col_offset);\n\t\tmult_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\tmult_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset);\n\t\tmult_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsm->n;\n\tint sm_nnz = cmsm->nnz;\n\tdouble *sm_non_zeros = cmsm->non_zeros;\n\tunsigned char *sm_col_counts = cmsm->col_counts;\n\tint *sm_col_starts = (int *)cmsm->col_counts;\n\tbool sm_use_counts = cmsm->use_counts;\n\tunsigned int *sm_rows = cmsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[col_offset + i2] += soln[row_offset + sm_rows[j2]] * (sm_non_zeros[j2] / unif);\n\t\t\t//printf(\"(%d,%d)=%f\\n\", col_offset + sm_rows[j2], row_offset + i2, sm_non_zeros[j2]);\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nstatic void mult_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmscsm->n;\n\tint sm_nnz = cmscsm->nnz;\n\tunsigned char *sm_col_counts = cmscsm->col_counts;\n\tint *sm_col_starts = (int *)cmscsm->col_counts;\n\tbool sm_use_counts = cmscsm->use_counts;\n\tunsigned int *sm_rows = cmscsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tsoln2[col_offset + i2] += soln[row_offset + (int)(sm_rows[j2] >> sm_dist_shift)] * (sm_dist[(int)(sm_rows[j2] & sm_dist_mask)] / unif);\n\t\t\t//printf(\"(%d,%d)=%f\\n\", col_offset + (int)(sm_rows[j2] >> sm_dist_shift), row_offset + i2, sm_dist[(int)(sm_rows[j2] & sm_dist_mask)]);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/PrismHybrid.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage hybrid;\n\nimport prism.*;\nimport jdd.*;\nimport dv.*;\nimport odd.*;\n\n//------------------------------------------------------------------------------\n\npublic class PrismHybrid\n{\n\t//------------------------------------------------------------------------------\n\t// load jni stuff from shared library\n\t//------------------------------------------------------------------------------\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\t\n\t//------------------------------------------------------------------------------\n\t// Local utility methods\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Check that number of reachable states is in a range that can be handled by\n\t * the hybrid engine methods.\n\t * @throws PrismNotSupportedException if that is not the case\n\t */\n\tprivate static void checkNumStates(ODDNode odd) throws PrismNotSupportedException\n\t{\n\t\t// currently, the hybrid engine internally uses int (signed 32bit) index values\n\t\t// so, if the number of states is larger than Integer.MAX_VALUE, there is a problem\n\t\tODDUtils.checkInt(odd, \"Currently, the hybrid engine cannot handle models\");\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// error message\n\t//------------------------------------------------------------------------------\n\t\n\tpublic static String getErrorMessage()\n\t{\n\t\treturn PrismNative.PN_GetErrorMessage();\n\t}\n\n\t/**\n\t * Generate the proper exception for an error from the native layer.\n\t * Gets the error message and returns the corresponding exception,\n\t * i.e., if the message contains \"not supported\" then a PrismNotSupportedException\n\t * is returned, otherwise a plain PrismException.\n\t */\n\tprivate static PrismException generateExceptionForError()\n\t{\n\t\tString msg = getErrorMessage();\n\t\tif (msg.contains(\"not supported\")) {\n\t\t\treturn new PrismNotSupportedException(msg);\n\t\t} else {\n\t\t\treturn new PrismException(msg);\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// JNI wrappers for blocks of hybrid code\n\t//------------------------------------------------------------------------------\n\n\t//------------------------------------------------------------------------------\n\t// probabilistic/dtmc stuff\n\t//------------------------------------------------------------------------------\n\n\t// pctl bounded until (probabilistic/dtmc)\n\tprivate static native long PH_ProbBoundedUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe, int bound);\n\tpublic static DoubleVector ProbBoundedUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, int bound) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_ProbBoundedUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), bound);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// pctl until (probabilistic/dtmc)\n\tprivate static native long PH_ProbUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe);\n\tpublic static DoubleVector ProbUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_ProbUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl until (probabilistic/dtmc), interval variant\n\tprivate static native long PH_ProbUntilInterval(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe, int flags);\n\tpublic static DoubleVector ProbUntilInterval(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_ProbUntilInterval(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl cumulative reward (probabilistic/dtmc)\n\tprivate static native long PH_ProbCumulReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, int bound);\n\tpublic static DoubleVector ProbCumulReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, int bound) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_ProbCumulReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), bound);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl cumulative reward (probabilistic/dtmc)\n\tprivate static native long PH_ProbInstReward(long trans, long sr, long odd, long rv, int nrv, long cv, int ncv, int time);\n\tpublic static DoubleVector ProbInstReward(JDDNode trans, JDDNode sr, ODDNode odd, JDDVars rows, JDDVars cols, int time) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_ProbInstReward(trans.ptr(), sr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl reach reward (probabilistic/dtmc)\n\tprivate static native long PH_ProbReachReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long goal, long inf, long maybe);\n\tpublic static DoubleVector ProbReachReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode goal, JDDNode inf, JDDNode maybe) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_ProbReachReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), goal.ptr(), inf.ptr(), maybe.ptr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl reach reward (probabilistic/dtmc), interval variant\n\tprivate static native long PH_ProbReachRewardInterval(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long goal, long inf, long maybe, long lower, long upper, int flags);\n\tpublic static DoubleVector ProbReachRewardInterval(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode goal, JDDNode inf, JDDNode maybe, JDDNode lower, JDDNode upper, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_ProbReachRewardInterval(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), goal.ptr(), inf.ptr(), maybe.ptr(), lower.ptr(), upper.ptr(), flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// transient (probabilistic/dtmc)\n\tprivate static native long PH_ProbTransient(long trans, long odd, long init, long rv, int nrv, long cv, int ncv, int time);\n\tpublic static DoubleVector ProbTransient(JDDNode trans, ODDNode odd, DoubleVector init, JDDVars rows, JDDVars cols, int time) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_ProbTransient(trans.ptr(), odd.ptr(), init.getPtr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t//----------------------------------------------------------------------------------------------\n\t// nondeterministic/mdp stuff\n\t//----------------------------------------------------------------------------------------------\n\n\t// pctl bounded until (nondeterministic/mdp)\n\tprivate static native long PH_NondetBoundedUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, int time, boolean minmax);\n\tpublic static DoubleVector NondetBoundedUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, int time, boolean minmax) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_NondetBoundedUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), time, minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// pctl until (nondeterministic/mdp)\n\tprivate static native long PH_NondetUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, boolean minmax);\n\tpublic static DoubleVector NondetUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, boolean minmax) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_NondetUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// pctl until (nondeterministic/mdp), interval iteration\n\tprivate static native long PH_NondetUntilInterval(long trans, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, boolean minmax, int flags);\n\tpublic static DoubleVector NondetUntilInterval(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, boolean minmax, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_NondetUntilInterval(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), minmax, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// pctl reach reward (nondeterministic/mdp)\n\tprivate static native long PH_NondetReachReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long goal, long inf, long maybe, boolean minmax);\n\tpublic static DoubleVector NondetReachReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode goal, JDDNode inf, JDDNode maybe, boolean minmax) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_NondetReachReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), goal.ptr(), inf.ptr(), maybe.ptr(), minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// stochastic/ctmc stuff\n\t//------------------------------------------------------------------------------\n\n\t// csl bounded until (stochastic/ctmc)\n\tprivate static native long PH_StochBoundedUntil(long trans, long od, long rv, int nrv, long cv, int ncv, long yes, long maybe, double time, long mult);\n\tpublic static DoubleVector StochBoundedUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, double time, DoubleVector multProbs) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong mult = (multProbs == null) ? 0 : multProbs.getPtr();\n\t\tlong ptr = PH_StochBoundedUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), time, mult);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// csl cumulative reward (stochastic/ctmc)\n\tprivate static native long PH_StochCumulReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, double time);\n\tpublic static DoubleVector StochCumulReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, double time) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_StochCumulReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// steady state (stochastic/ctmc)\n\tprivate static native long PH_StochSteadyState(long trans, long od, long init, long rv, int nrv, long cv, int ncv);\n\tpublic static DoubleVector StochSteadyState(JDDNode trans, ODDNode odd, JDDNode init, JDDVars rows, JDDVars cols) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_StochSteadyState(trans.ptr(), odd.ptr(), init.ptr(), rows.array(), rows.n(), cols.array(), cols.n());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// transient (stochastic/ctmc)\n\tprivate static native long PH_StochTransient(long trans, long odd, long init, long rv, int nrv, long cv, int ncv, double time);\n\tpublic static DoubleVector StochTransient(JDDNode trans, ODDNode odd, DoubleVector init, JDDVars rows, JDDVars cols, double time) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_StochTransient(trans.ptr(), odd.ptr(), init.getPtr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t//------------------------------------------------------------------------------\n\t// generic iterative solution methods\n\t//------------------------------------------------------------------------------\n\n\t// power method\n\tprivate static native long PH_Power(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose);\n\tpublic static DoubleVector Power(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_Power(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// power method (interval variant)\n\tprivate static native long PH_PowerInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, int flags);\n\tpublic static DoubleVector PowerInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_PowerInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// jor method\n\tprivate static native long PH_JOR(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose, boolean row_sums, double omega);\n\tpublic static DoubleVector JOR(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose, boolean row_sums, double omega) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_JOR(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose, row_sums, omega);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// jor method (interval variant)\n\tprivate static native long PH_JORInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, boolean row_sums, double omega, int flags);\n\tpublic static DoubleVector JORInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, boolean row_sums, double omega, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_JORInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, row_sums, omega, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// sor method\n\tprivate static native long PH_SOR(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose, boolean row_sums, double omega, boolean backwards);\n\tpublic static DoubleVector SOR(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose, boolean row_sums, double omega, boolean backwards) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_SOR(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose, row_sums, omega, backwards);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// sor method (interval variant)\n\tprivate static native long PH_SORInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, boolean row_sums, double omega, boolean backwards, int flags);\n\tpublic static DoubleVector SORInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, boolean row_sums, double omega, boolean backwards, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_SORInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, row_sums, omega, backwards, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// psor method\n\tprivate static native long PH_PSOR(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose, boolean row_sums, double omega, boolean backwards);\n\tpublic static DoubleVector PSOR(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose, boolean row_sums, double omega, boolean backwards) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_PSOR(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose, row_sums, omega, backwards);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// psor method (interval variant)\n\tprivate static native long PH_PSORInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, boolean row_sums, double omega, boolean backwards, int flags);\n\tpublic static DoubleVector PSORInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, boolean row_sums, double omega, boolean backwards, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PH_PSORInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, row_sums, omega, backwards, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t//------------------------------------------------------------------------------\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/hybrid.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Rashid Mehmood <rxm@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <dv.h>\n#include \"sparse.h\"\n#include \"hybrid.h\"\n#include \"PrismHybrid.h\"\n#include \"PrismNativeGlob.h\"\n#include <cmath>\n#include <new>\n\n// globals (used by local functions)\nstatic HDDMatrix *hddm;\nstatic HDDNode *zero;\nstatic int *starts;\nstatic RMSparseMatrix *rmsm;\nstatic CMSparseMatrix *cmsm;\nstatic CMSRSparseMatrix *cmsrsm;\nstatic CMSCSparseMatrix *cmscsm;\nstatic int num_levels;\nstatic bool row_major;\nstatic bool compact_sm;\nstatic double *sm_dist;\nstatic int sm_dist_shift;\nstatic int sm_dist_mask;\n\n// local prototypes\nstatic HDDNode *build_hdd_matrix_rowrec(DdNode *dd, DdNode **rvars, DdNode **cvars, int num_vars, int level, ODDNode *row, ODDNode *col);\nstatic HDDNode *build_hdd_matrix_colrec(DdNode *dd, DdNode **rvars, DdNode **cvars, int num_vars, int level, ODDNode *row, ODDNode *col);\nstatic void traverse_hdd_rec(HDDNode *hdd, int level, int stop, int r, int c, int code, bool transpose);\nstatic void traverse_odd_rec(ODDNode *odd, int level, int stop, int index, int code);\nstatic int compute_n_and_nnz_rec(HDDNode *hdd, int level, int num_levels, ODDNode *row, ODDNode *col, bool transpose);\nstatic RMSparseMatrix *build_rm_sparse_matrix(HDDNode *hdd, int level, bool transpose);\nstatic CMSparseMatrix *build_cm_sparse_matrix(HDDNode *hdd, int level, bool transpose);\nstatic CMSRSparseMatrix *build_cmsr_sparse_matrix(HDDNode *hdd, int level, bool transpose);\nstatic CMSCSparseMatrix *build_cmsc_sparse_matrix(HDDNode *hdd, int level, bool transpose);\nstatic void build_mdp_cubes_rec(DdNode *dd, DdNode *cube, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, int level, ODDNode *odd, HDDMatrices *hddms);\nstatic void hdd_negative_row_sums_rec(HDDNode *hdd, int level, int row_offset, int col_offset, double *diags, bool transpose);\nstatic void hdd_negative_row_sums_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, double *diags, bool transpose);\nstatic void hdd_negative_row_sums_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset, double *diags, bool transpose);\nstatic void hdd_negative_row_sums_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, double *diags, bool transpose);\nstatic void hdd_negative_row_sums_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset, double *diags, bool transpose);\n\n//------------------------------------------------------------------------------\n// Data structure constructors/deconstructors\n//------------------------------------------------------------------------------\n\nHDDMatrix::HDDMatrix()\n{\n\tnum_levels = 0;\n\t// make sure pointers are init'ed to null\n\trow_lists = NULL;\n\tcol_lists = NULL;\n\trow_tables = NULL;\n\tcol_tables = NULL;\n\trow_sizes = NULL;\n\tcol_sizes = NULL;\n\ttop = NULL;\n\tzero = NULL;\n\todd = NULL;\n\tblocks = NULL;\n\tdist = NULL;\n}\n\nHDDMatrix::~HDDMatrix()\n{\n\tint i, j;\n\t\n\t// free all row nodes\n\tif (row_sizes && row_tables) {\n\t\tfor (i = 0; i < num_levels; i++) {\n\t\t\tif (!row_tables[i]) continue;\n\t\t\tfor (j = 0; j < row_sizes[i]; j++) {\n\t\t\t\t// free sparse matrix if there is one\n\t\t\t\tif (row_tables[i][j] && row_tables[i][j]->sm.ptr) {\n\t\t\t\t\tif (row_major) {\n\t\t\t\t\t\tif (!compact_sm) delete (RMSparseMatrix *)row_tables[i][j]->sm.ptr;\n\t\t\t\t\t\telse delete (CMSRSparseMatrix *)row_tables[i][j]->sm.ptr;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (!compact_sm) delete (CMSparseMatrix *)row_tables[i][j]->sm.ptr;\n\t\t\t\t\t\telse delete (CMSCSparseMatrix *)row_tables[i][j]->sm.ptr;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// free node\n\t\t\t\tif (row_tables[i][j]) delete row_tables[i][j];\n\t\t\t}\n\t\t\t// free node table\n\t\t\tif (row_tables[i]) delete[] row_tables[i];\n\t\t}\n\t\t// free all terminal nodes\n\t\ti = num_levels;\n\t\tfor (j = 0; j < row_sizes[i]; j++) {\n\t\t\tif (row_tables[i][j]) delete row_tables[i][j];\n\t\t}\n\t\tif (row_tables[i]) delete[] row_tables[i];\n\t}\n\t// free all column nodes\n\tif (col_sizes && col_tables) {\n\t\tfor (i = 0; i < num_levels; i++) {\n\t\t\tif (!col_tables[i]) continue;\n\t\t\tfor (j = 0; j < col_sizes[i]; j++) {\n\t\t\t\tif (col_tables[i][j]) delete col_tables[i][j];\n\t\t\t}\n\t\t\tif (col_tables[i]) delete[] col_tables[i];\n\t\t}\n\t}\n\t// free other tables\n\tif (row_lists) delete[] row_lists;\n\tif (col_lists) delete[] col_lists;\n\tif (row_tables) delete[] row_tables;\n\tif (col_tables) delete[] col_tables;\n\tif (row_sizes) delete[] row_sizes;\n\tif (col_sizes) delete[] col_sizes;\n\t// free block storage\n\tif (blocks) delete blocks;\n\t// free distinct matrix values\n\tif (dist) delete[] dist;\n}\n\nHDDBlocks::HDDBlocks()\n{\n\t// make sure pointers are init'ed to null\n\tblocks = NULL;\n\trowscols = NULL;\n\tcounts = NULL;\n\toffsets = NULL;\n}\n\nHDDBlocks::~HDDBlocks()\n{\n\tif (blocks) delete blocks;\n\tif (rowscols) delete rowscols;\n\tif (counts) { if (use_counts) delete counts; else delete (int*)counts; }\n\tif (offsets) delete offsets;\n}\n\nHDDMatrices::HDDMatrices()\n{\n\tnm = 0;\n\t// make sure pointers are init'ed to null\n\tchoices = NULL;\n\tcubes = NULL;\n}\n\nHDDMatrices::~HDDMatrices()\n{\n\tint i;\n\t\n\t// go thru all choices\n\tfor (i = 0; i < nm; i++) {\n\t\tif (choices[i]) delete choices[i];\n\t\tif (cubes[i]) Cudd_RecursiveDeref(ddman, cubes[i]);\n\t}\n\t// free arrays\n\tif (choices) delete[] choices;\n\tif (cubes) delete[] cubes;\n}\n\n//-----------------------------------------------------------------------------------\n// Methods for constructing offset-labelled MTBBDs\n//-----------------------------------------------------------------------------------\n\n// builds an offset-labelled mtbbd for a matrix (from an mtbdd)\n// throws std::bad_alloc on out-of-memory\n\nHDDMatrix *build_hdd_matrix(DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool row_major)\n{ return build_hdd_matrix(matrix, rvars, cvars, num_vars, odd, row_major, false); }\n\nHDDMatrix *build_hdd_matrix(DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool row_major, bool transpose)\n{\n\tint i, j;\n\tHDDMatrix *res = NULL;\n\tHDDNode *ptr = NULL;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create data structure and store global pointer to it\n\tres = new HDDMatrix();\n\thddm = res;\n\t\n\t// build lists to store hdd nodes\n\tres->row_lists = new HDDNode*[num_vars+1];\n\tfor (i = 0; i < num_vars+1; i++) res->row_lists[i] = NULL;\n\tres->col_lists = new HDDNode*[num_vars];\n\tfor (i = 0; i < num_vars; i++) res->col_lists[i] = NULL;\n\tres->row_tables = new HDDNode**[num_vars+1];\n\tfor (i = 0; i < num_vars+1; i++) res->row_tables[i] = NULL;\n\tres->col_tables = new HDDNode**[num_vars];\n\tfor (i = 0; i < num_vars; i++) res->col_tables[i] = NULL;\n\tres->row_sizes = new int[num_vars+1];\n\tfor (i = 0; i < num_vars+1; i++) res->row_sizes[i] = 0;\n\tres->col_sizes = new int[num_vars];\n\tfor (i = 0; i < num_vars; i++) res->col_sizes[i] = 0;\n\t// reset node counter\n\tres->num_nodes = 0;\n\t\n\t// create zero constant (special case)\n\tres->num_nodes++;\n\tres->zero = new HDDNode();\n\tres->zero->type.kids.e = NULL;\n\tres->zero->type.kids.t = NULL;\n\tres->zero->off.val = 0;\n\tres->zero->off2.val = 0;\n\tres->zero->sm.ptr = NULL;\n\tres->zero->next = NULL;\n\t// and store global copy of pointer\n\tzero = res->zero;\n\t\n\t// call recursive bit\n\tres->top = build_hdd_matrix_rowrec(matrix, rvars, cvars, num_vars, 0, odd, odd);\n\t\n\t// convert node storage from linked lists to arrays\n\tfor (i = 0; i < num_vars+1; i++) {\n\t\tres->row_tables[i] = new HDDNode*[res->row_sizes[i]];\n\t\tj = 0;\n\t\tptr = res->row_lists[i];\n\t\twhile (ptr != NULL) {\n\t\t\tres->row_tables[i][j++] = ptr;\n\t\t\tptr = ptr->next;\n\t\t}\n\t}\n\tfor (i = 0; i < num_vars; i++) {\n\t\tres->col_tables[i] = new HDDNode*[res->col_sizes[i]];\n\t\tj = 0;\n\t\tptr = res->col_lists[i];\n\t\twhile (ptr != NULL) {\n\t\t\tres->col_tables[i][j++] = ptr;\n\t\t\tptr = ptr->next;\n\t\t}\n\t}\n\t\n\t// go thru all nodes and\n\t// (1) store actual offset (int) not odd ptr\n\t// (2) set sparse matrix pointer to null\n\tfor (i = 0; i < num_vars+1; i++) {\n\t\tfor (j = 0; j < res->row_sizes[i]; j++) {\n\t\t\tres->row_tables[i][j]->off.val = res->row_tables[i][j]->off.ptr->eoff;\n\t\t\tres->row_tables[i][j]->sm.ptr = NULL;\n\t\t}\n\t}\n\tfor (i = 0; i < num_vars; i++) {\n\t\tfor (j = 0; j < res->col_sizes[i]; j++) {\n\t\t\tres->col_tables[i][j]->off.val = res->col_tables[i][j]->off.ptr->eoff;\n\t\t\tres->col_tables[i][j]->sm.ptr = NULL;\n\t\t}\n\t}\n\t\n\t// fill up other fields with info/defaults\n\tres->row_major = row_major;\n\tres->compact_b = true;\n\tres->compact_sm = true;\n\tres->num_levels = num_vars;\n\tres->l_b = 0;\n\tres->l_sm = 0;\n\tres->num_b = 0;\n\tres->num_sm = 0;\n\tres->mem_nodes = (res->num_nodes * sizeof(HDDNode)) / 1024.0;\n\tres->mem_b = 0;\n\tres->mem_sm = 0;\n\tres->odd = odd;\n\tres->blocks = NULL;\n\tres->dist = NULL;\n\tres->dist_num = 0;\n\tres->dist_shift = 0;\n\tres->dist_mask = 0;\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (res) delete res;\n\t\tthrow e;\n\t}\n\t\n\treturn res;\n}\n\n//-----------------------------------------------------------------------------------\n\n// recursive part of build_hdd_matrix\n\nHDDNode *build_hdd_matrix_rowrec(DdNode *dd, DdNode **rvars, DdNode **cvars, int num_vars, int level, ODDNode *row, ODDNode *col)\n{\n\tHDDNode *ptr, *hdd_e, *hdd_t;\n\tDdNode *e, *t;\n\t\n\t// check for zero terminal\n\tif (dd == Cudd_ReadZero(ddman)) {\n\t\treturn zero;\n\t}\n\t\n\t// see if we already have the required node stored\n\tptr = hddm->row_lists[level];\n\twhile (ptr != NULL) {\n\t\tif (((DdNode*)(ptr->sm.ptr) == dd) && (ptr->off.ptr == row) && (ptr->off2.ptr == col)) break;\n\t\t// use this instead to check effect on node increase\n\t\t// if (((DdNode*)(ptr->sm.ptr) == dd)) break;\n\t\tptr = ptr->next;\n\t}\n\t// if so, return it\n\tif (ptr != NULL) {\n\t\treturn ptr;\n\t}\n\t\n\t// otherwise go on and create it...\n\t\n\t// if it's a terminal node, it's easy...\n\tif (level == num_vars) {\n\t\thddm->num_nodes++;\n\t\tptr = new HDDNode();\n\t\tptr->type.val = Cudd_V(dd);\n\t\tptr->off.ptr = row;\n\t\tptr->off2.ptr = col;\n\t\tptr->sm.ptr = (void *)dd;\n\t\tptr->next = hddm->row_lists[num_vars];\n\t\thddm->row_lists[num_vars] = ptr;\n\t\thddm->row_sizes[num_vars]++;\n\t\treturn ptr;\n\t}\n\t\n\t// if not, have to recurse before creation\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(rvars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\thdd_e = build_hdd_matrix_colrec(e, rvars, cvars, num_vars, level, row->e, col);\n\thdd_t = build_hdd_matrix_colrec(t, rvars, cvars, num_vars, level, row->t, col);\n\thddm->num_nodes++;\n\tptr = new HDDNode();\n\tptr->type.kids.e = hdd_e;\n\tptr->type.kids.t = hdd_t;\n\tptr->off.ptr = row;\n\tptr->off2.ptr = col;\n\tptr->sm.ptr = (void *)dd;\n\tptr->next = hddm->row_lists[level];\n\thddm->row_lists[level] = ptr;\n\thddm->row_sizes[level]++;\n\treturn ptr;\n}\n\nHDDNode *build_hdd_matrix_colrec(DdNode *dd, DdNode **rvars, DdNode **cvars, int num_vars, int level, ODDNode *row, ODDNode *col)\n{\n\tHDDNode *ptr, *hdd_e, *hdd_t;\n\tDdNode *e, *t;\n\t\n\t// check for zero terminal\n\tif (dd == Cudd_ReadZero(ddman)) {\n\t\treturn zero;\n\t}\n\t\n\t// see if we already have the required node stored\n\tptr = hddm->col_lists[level];\n\twhile (ptr != NULL) {\n\t\tif (((DdNode*)(ptr->sm.ptr) == dd) && (ptr->off.ptr == col) && (ptr->off2.ptr == row)) break;\n\t\t// use this instead to check effect on node increase\n\t\t// if (((DdNode*)(ptr->sm.ptr) == dd)) break;\n\t\tptr = ptr->next;\n\t}\n\t// if so, return it\n\tif (ptr != NULL) {\n\t\treturn ptr;\n\t}\n\t\n\t// otherwise go on and create it...\n\t\n\t// can't be a terminal node so recurse before creation\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(cvars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\thdd_e = build_hdd_matrix_rowrec(e, rvars, cvars, num_vars, level+1, row, col->e);\n\thdd_t = build_hdd_matrix_rowrec(t, rvars, cvars, num_vars, level+1, row, col->t);\n\thddm->num_nodes++;\n\tptr = new HDDNode();\n\tptr->type.kids.e = hdd_e;\n\tptr->type.kids.t = hdd_t;\n\tptr->off.ptr = col;\n\tptr->off2.ptr = row;\n\tptr->sm.ptr = (void *)dd;\n\tptr->next = hddm->col_lists[level];\n\thddm->col_lists[level] = ptr;\n\thddm->col_sizes[level]++;\n\t\n\treturn ptr;\n}\n\n//-----------------------------------------------------------------------------------\n\n// split offset-labelled mtbdd into blocks\n\nvoid split_hdd_matrix(HDDMatrix *hm, bool compact_b, bool meet)\n{ return split_hdd_matrix(hm, compact_b, meet, false); }\n\nvoid split_hdd_matrix(HDDMatrix *hm, bool compact_b, bool meet, bool transpose)\n{\n\tint i, n, max;\n\tHDDBlocks *blocks = NULL;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// store some info globally\n\thddm = hm;\n\tzero = hddm->zero;\n\t\n\t// initialise variables\n\thddm->compact_b = compact_b;\n\thddm->num_b = 0;\n\thddm->mem_b = 0;\n\t\n\t// now we choose a value for l_b\n\t// first priority is given to the 'meet' flag: if true, l_b and l_sm must meet\n\t// failing that, if the user specified a value, we use that (reducing if necessary)\n\t// lastly, we compute the max level we can afford without exceeding mem limits\n\tif (meet) {\n\t\thddm->l_b = hddm->num_levels - hddm->l_sm;\n\t}\n\telse if (num_sor_levels != -1) {\n\t\thddm->l_b = num_sor_levels;\n\t\tif (hddm->l_b + hddm->l_sm > hddm->num_levels) hddm->l_b = hddm->num_levels - hddm->l_sm;\n\t}\n\telse {\n\t\t// no memory-based heuristic yet - just use 2/5\n\t\thddm->l_b = hddm->num_levels*2/5;\n\t\tif (hddm->l_b + hddm->l_sm > hddm->num_levels) hddm->l_b = hddm->num_levels - hddm->l_sm;\n\t}\n\t\n\t// allocate storage\n\tblocks = new HDDBlocks();\n\thddm->blocks = blocks;\n\t\n\t// if necessary, store number of distinct pointers and related info\n\tif (hddm->compact_b) {\n\t\tblocks->dist_num = hddm->row_sizes[hddm->l_b];\n\t\tblocks->dist_shift = (int)ceil(logtwo(blocks->dist_num));\n\t\tif (blocks->dist_shift == 0) blocks->dist_shift++;\n\t\tblocks->dist_mask = (1 << blocks->dist_shift) - 1;\n\t}\n\t\n\t// compute n\n\tblocks->n = 0;\n\ttraverse_odd_rec(hddm->odd, 0, hddm->num_levels, 0, 1);\n\tn = blocks->n;\n\t\n\t// see if compact storage is feasible; if not, abandon it\n\tif (hddm->compact_b) {\n\t\tif (blocks->dist_shift + (int)ceil(logtwo(n)) > 8*sizeof(unsigned int)) {\n\t\t\thddm->compact_b = false;\n\t\t}\n\t}\n\t\n\t// compute block offsets\n\tblocks->offsets = new int[n+1];\n\thddm->mem_b += (((n+1) * sizeof(int)) / 1024.0);\n\tfor (i = 0; i < n+1; i++) blocks->offsets[i] = 0;\n\t// last offset will always be num states\n\tblocks->offsets[n] = hddm->odd->eoff+hddm->odd->toff;\n\t// compute offsets recursively\n\tblocks->n = 0;\n\ttraverse_odd_rec(hddm->odd, 0, hddm->num_levels, 0, 2);\n\t\n\t// compute max block size (gap b/e offsets)\n\tblocks->max = blocks->offsets[1] - blocks->offsets[0];\n\tfor (i = 1; i < blocks->n; i++) {\n\t\tif( blocks->offsets[i+1] - blocks->offsets[i] > blocks->max) {\n\t\t\tblocks->max = blocks->offsets[i+1] - blocks->offsets[i] ;\n\t\t}\n\t}\n\t\n\t// allocate temporary array to store start of each row/col\n\tstarts = NULL; starts = new int[n+1];\n\t// see how many nonzeros are in each row/column (depending on row_major flag)\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\tblocks->nnz = 0;\n\ttraverse_hdd_rec(hddm->top, 0, hddm->l_b, 0, 0, hddm->row_major?1:2, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a row/col)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\tblocks->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// traversal above also computed nnz so now allocate arrays\n\tblocks->rowscols = new unsigned int[blocks->nnz];\n\thddm->mem_b += ((blocks->nnz * sizeof(unsigned int)) / 1024.0);\n\tfor (i = 0; i < blocks->nnz; i++) blocks->rowscols[i] = 0;\n\tif (!hddm->compact_b) {\n\t\tblocks->blocks = new HDDNode*[blocks->nnz];\n\t\thddm->mem_b += ((blocks->nnz * sizeof(HDDNode *)) / 1024.0);\n\t\tfor (i = 0; i < blocks->nnz; i++) blocks->blocks[i] = NULL;\n\t}\n\t\n\t// then fill it up\n\tif (!hddm->compact_b) {\n\t\ttraverse_hdd_rec(hddm->top, 0, hddm->l_b, 0, 0, hddm->row_major?3:4, transpose);\n\t} else {\n\t\ttraverse_hdd_rec(hddm->top, 0, hddm->l_b, 0, 0, hddm->row_major?5:6, transpose);\n\t}\n\t\n\t// recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// assuming it's safe to do so, replace starts with (smaller) array of counts\n\t// if not, we keep the starts array and use that\n\tif (blocks->use_counts) {\n\t\tblocks->counts = new unsigned char[blocks->n];\n\t\thddm->mem_b += ((n * sizeof(unsigned char)) / 1024.0);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tblocks->counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\t}\n\t\tdelete[] starts; starts = NULL;\n\t}\n\telse {\n\t\tblocks->counts = (unsigned char*)starts;\n\t\thddm->mem_b += ((n * sizeof(int)) / 1024.0);\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (blocks) delete blocks;\n\t\thddm->blocks = NULL;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\n// add explicit sparse matrices on to the hdd\n\nvoid add_sparse_matrices(HDDMatrix *hm, bool compact_sm, bool diags_meet)\n{ return add_sparse_matrices(hm, compact_sm, diags_meet, false); }\n\nvoid add_sparse_matrices(HDDMatrix *hm, bool compact_sm, bool diags_meet, bool transpose)\n{\n\tint i, j, k, n, nnz, l, h, i_sm, rowcol;\n\tdouble mem_est;\n\tbool mem_out;\n\tHDDNode *node = NULL;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// store some info globally\n\thddm = hm;\n\tzero = hddm->zero;\n\t\n\t// initialise variables\n\thddm->compact_sm = compact_sm;\n\thddm->num_sm = 0;\n\thddm->mem_sm = 0;\n\t\n\t// first, we initialise all sm/off2\n\t// (they may have been used to store other things previously)\n\t// (sm is set to -1 because we need to know when we visit for the first time, off2 is set to 0)\n\tfor (i = 0; i < hddm->num_levels+1; i++) {\n\t\tfor (j = 0; j < hddm->row_sizes[i]; j++) {\n\t\t\thddm->row_tables[i][j]->sm.val = -1;\n\t\t\thddm->row_tables[i][j]->off2.val = 0;\n\t\t}\n\t}\n\tfor (i = 0; i < hddm->num_levels; i++) {\n\t\tfor (j = 0; j < hddm->col_sizes[i]; j++) {\n\t\t\thddm->col_tables[i][j]->sm.val = -1;\n\t\t\thddm->col_tables[i][j]->off2.val = 0;\n\t\t}\n\t}\n\t\n\t// store size (num states and nnz) of each node's matrix\n\t// (putting them in the sm and off2 fields, respectively)\n\tcompute_n_and_nnz_rec(hddm->top, 0, hddm->num_levels, hddm->odd, hddm->odd, transpose);\n\t\n\t// now we choose a value for l_sm\n\t// if the user specified a value, we use that (reducing if necessary)\n\t// if not, we compute the max level we can afford without exceeding mem limits\n\tif (num_sb_levels != -1) {\n\t\thddm->l_sm = num_sb_levels;\n\t\tif (hddm->l_sm + hddm->l_b > hddm->num_levels) hddm->l_sm = hddm->num_levels - hddm->l_b;\n\t}\n\telse {\n\t\t// estimate memory required for each level\n\t\t// and select the last level for which we don't exceed the limit\n\t\tmem_out = false;\n\t\tfor (i = 1; i <= hddm->num_levels - hddm->l_b; i++) {\n\t\t\tj = hddm->num_levels - i;\n\t\t\tmem_est = 0;\n\t\t\tfor (k = 0; k < hddm->row_sizes[j]; k++) {\n\t\t\t\tn = hddm->row_tables[j][k]->sm.val;\n\t\t\t\tnnz = hddm->row_tables[j][k]->off2.val;\n\t\t\t\tif (!compact_sm) mem_est += ((nnz*(sizeof(double)+sizeof(unsigned int))+n*sizeof(unsigned char)) / 1024.0);\n\t\t\t\telse mem_est += ((nnz*(sizeof(unsigned int))+n*sizeof(unsigned char)) / 1024.0);\n\t\t\t\tif (mem_est > sb_max_mem) {\n\t\t\t\t\tmem_out = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (mem_out) break;\n\t\t}\n\t\thddm->l_sm = mem_out ? i-1 : hddm->num_levels - hddm->l_b;\n\t}\n\t\n\t// compute index of level corresponding to l_sm\n\ti_sm = hddm->num_levels - hddm->l_sm;\n\t\n\t// if diagonal blocks will be created anyway, don't bother\n\tif (diags_meet) if (hddm->l_sm + hddm->l_b >= hddm->num_levels) {\n\t\tdiags_meet = false;\n\t}\n\t\n\t// only actually add sparse matrices if there are any to add\n\tif (diags_meet || hddm->l_sm > 0) {\n\t\t\n\t\t// see if compact storage is feasible; if not, abandon it\n\t\tif (hddm->compact_sm) {\n\t\t\t// this is how many bits are free to store row/column indices\n\t\t\tint sparebits = 8*sizeof(unsigned int) - (int)ceil(logtwo(hddm->row_sizes[hddm->num_levels]));\n\t\t\tif (sparebits == 8*sizeof(unsigned int)) sparebits--;\n\t\t\t// so this is the max size of sparse matrix we can afford\n\t\t\tunsigned int maxsize = 1 << sparebits;\n\t\t\t// go thru all sparse matrices we are about to create and make sure they're not too big\n\t\t\t// in fact, for the case where diag_meet=true, this would be complicated and messy\n\t\t\t// hence, in this case, we resort to an over-approximation and look at all matrices on that level (l_b)\n\t\t\tj = diags_meet ? hddm->l_b : i_sm;\n\t\t\tfor (i = 0; i < hddm->row_sizes[j]; i++) {\n\t\t\t\t// size is curently stored in sm pointer\n\t\t\t\tif (hddm->row_tables[j][i]->sm.val > maxsize) {\n\t\t\t\t\thddm->compact_sm = false;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t// if we're creating a \"compact modified\" sparse matrix,\n\t\t// store info about the distinct values in the matrix\n\t\tif (hddm->compact_sm) {\n\t\t\thddm->dist_num = hddm->row_sizes[hddm->num_levels];\n\t\t\thddm->dist_shift = (int)ceil(logtwo(hddm->dist_num));\n\t\t\tif (hddm->dist_shift == 0) hddm->dist_shift++;\n\t\t\thddm->dist_mask = (1 << hddm->dist_shift) - 1;\n\t\t\t// store all the distinct values in the matrix\n\t\t\thddm->dist = new double[hddm->dist_num];\n\t\t\thddm->mem_sm += ((hddm->dist_num * sizeof(double)) / 1024.0);\n\t\t\tfor (j = 0; j < hddm->row_sizes[hddm->num_levels]; j++) {\n\t\t\t\thddm->dist[j] = hddm->row_tables[hddm->num_levels][j]->type.val;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// now actually add the sparse matrices\n\t\t\n\t\t// first the diagonal blocks (if necessary)\n\t\tif (diags_meet) {\n\t\t\t\n\t\t\t// stuff for block storage\n\t\t\tint b_n = hddm->blocks->n;\n\t\t\tHDDNode **b_blocks = hddm->blocks->blocks;\n\t\t\tunsigned int *b_rowscols = hddm->blocks->rowscols;\n\t\t\tunsigned char *b_counts = hddm->blocks->counts;\n\t\t\tint *b_starts = (int *)hddm->blocks->counts;\n\t\t\tbool b_use_counts = hddm->blocks->use_counts;\n\t\t\tHDDNode **b_nodes = hddm->row_tables[hddm->l_b];\n\t\t\tint b_dist_shift = hddm->blocks->dist_shift;\n\t\t\tint b_dist_mask = hddm->blocks->dist_mask;\n\t\t\t\n\t\t\t// go through each row/column of blocks\n\t\t\th = 0;\n\t\t\tfor(i = 0; i < b_n; i++) {\n\t\t\t\tif (!b_use_counts) { l = b_starts[i]; h = b_starts[i+1]; }\n\t\t\t\telse { l = h; h += b_counts[i]; }\n\t\t\t\t// go along this row/column\n\t\t\t\tfor(j = l; j < h; j++) {\n\t\t\t\t\t// get column/row index of block\n\t\t\t\t\trowcol = (!hddm->compact_b) ? b_rowscols[j] : ((unsigned int)(b_rowscols[j] >> b_dist_shift));\n\t\t\t\t\t// if it's the diagonal...\n\t\t\t\t\tif (rowcol == i) {\n\t\t\t\t\t\t// if there is no sparse matrix there already, add a sparse matrix\n\t\t\t\t\t\t// (we mark nodes we have done already by setting off2 to -1)\n\t\t\t\t\t\tnode = (!hddm->compact_b) ? b_blocks[j] : (b_nodes[(int)(b_rowscols[j] & b_dist_mask)]);\n\t\t\t\t\t\tif (node->off2.val != -1) {\n\t\t\t\t\t\t\tif (!hddm->compact_sm) {\n\t\t\t\t\t\t\t\tif (hddm->row_major) {\n\t\t\t\t\t\t\t\t\tnode->sm.ptr = (void *)build_rm_sparse_matrix(node, hddm->l_b, transpose);\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tnode->sm.ptr = (void *)build_cm_sparse_matrix(node, hddm->l_b, transpose);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tif (hddm->row_major) {\n\t\t\t\t\t\t\t\t\tnode->sm.ptr = (void *)build_cmsr_sparse_matrix(node, hddm->l_b, transpose);\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tnode->sm.ptr = (void *)build_cmsc_sparse_matrix(node, hddm->l_b, transpose);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// set off2 to -1 to indicate we have added a sparse matrix here\n\t\t\t\t\t\t\tnode->off2.val = -1;\n\t\t\t\t\t\t\t// increment matrix count\n\t\t\t\t\t\t\thddm->num_sm++;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t// then all blocks at level i_sm\n\t\tif (hddm->l_sm > 0) {\n\t\t\tfor (i = 0; i < hddm->row_sizes[i_sm]; i++) {\n\t\t\t\tnode = hddm->row_tables[i_sm][i];\n\t\t\t\tif (!hddm->compact_sm) {\n\t\t\t\t\tif (hddm->row_major) {\n\t\t\t\t\t\tnode->sm.ptr = (void *)build_rm_sparse_matrix(node, i_sm, transpose);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tnode->sm.ptr = (void *)build_cm_sparse_matrix(node, i_sm, transpose);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (hddm->row_major) {\n\t\t\t\t\t\tnode->sm.ptr = (void *)build_cmsr_sparse_matrix(node, i_sm, transpose);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tnode->sm.ptr = (void *)build_cmsc_sparse_matrix(node, i_sm, transpose);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// set off2 to -1 to indicate we have added a sparse matrix here\n\t\t\t\tnode->off2.val = -1;\n\t\t\t\t// increment matrix count\n\t\t\t\thddm->num_sm++;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// finally, set all sparse matrix pointers back to null\n\t// (except on the nodes where we have just put sparse matrices)\n\tfor (i = 0; i < hddm->num_levels+1; i++) {\n\t\tfor (j = 0; j < hddm->row_sizes[i]; j++) {\n\t\t\tif (hddm->row_tables[i][j]->off2.val != -1) hddm->row_tables[i][j]->sm.ptr = NULL;\n\t\t}\n\t}\n\tfor (i = 0; i < hddm->num_levels; i++) {\n\t\tfor (j = 0; j < hddm->col_sizes[i]; j++) {\n\t\t\thddm->col_tables[i][j]->sm.ptr = NULL;\n\t\t}\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\t// if we run out of memory during this function, it is going to be\n\t\t// very difficult to deallocate memory cleanly (mainly because we\n\t\t// have abused various pointer variables by temporarily storing\n\t\t// integers in them). So, at the expense of a small memory leak...\n\t\thddm->row_tables = NULL;\n\t\tthrow e;\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n// Utility methods for methods which construct offset-labelled MTBDDS\n//-----------------------------------------------------------------------------------\n\n// generic function for recursive traversal of offset-labelled MTBDD\n\nvoid traverse_hdd_rec(HDDNode *hdd, int level, int stop, int r, int c, int code, bool transpose)\n{\n\tHDDNode *e, *t;\n\tint i, l, h, r2, c2, dist_num, dist_shift;\n\tdouble *dist;\n\t\n\t// if it's zero, return\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t\n\t// or if we've gone down far enough\n\telse if (level == stop) {\n\t\t\n\t\t// for code values of 1-6, we need to determine the row and/or column index\n\t\t// of the current block. we do this here to avoid repetition/cluttering in\n\t\t// the code below. since we only know the row/column offset for the block,\n\t\t// each index is determined via a binary seacrh over the offsets array.\n\t\t// the results are stored in r2 and c2, respectively.\n\t\tif (code >=1 && code <=6) {\n\t\t\t// determine row index\n\t\t\tl=0; h=hddm->blocks->n;\n\t\t\twhile (l<h) {\n\t\t\t\tr2 = (h-l)/2+l;\n\t\t\t\tif (hddm->blocks->offsets[r2] == r) break;\n\t\t\t\telse if (hddm->blocks->offsets[r2] < r) l = r2; else h = r2;\n\t\t\t}\n\t\t\t// determine column index\n\t\t\tl=0; h=hddm->blocks->n;\n\t\t\twhile (l<h) {\n\t\t\t\tc2 = (h-l)/2+l;\n\t\t\t\tif (hddm->blocks->offsets[c2] == c) break;\n\t\t\t\telse if (hddm->blocks->offsets[c2] < c) l = c2; else h = c2;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// do different things on the code passed in\n\t\tswitch (code) {\n\t\t\n\t\t// count blocks in each row of blocks (rm/cmsr)\n\t\tcase 1:\n\t\t\tstarts[(transpose?c2:r2)+1]++;\n\t\t\thddm->blocks->nnz++;\n\t\t\tbreak;\n\t\t\n\t\t// count blocks in each column of blocks (cm/cmsc)\n\t\tcase 2:\n\t\t\tstarts[(transpose?r2:c2)+1]++;\n\t\t\thddm->blocks->nnz++;\n\t\t\tbreak;\n\t\t\n\t\t// store blocks (rm)\n\t\tcase 3:\n\t\t\thddm->blocks->blocks[starts[(transpose?c2:r2)]] = hdd;\n\t\t\thddm->blocks->rowscols[starts[(transpose?c2:r2)]] = (transpose?r2:c2);\n\t\t\tstarts[(transpose?c2:r2)]++;\n\t\t\tbreak;\n\t\t\n\t\t// store blocks (cm)\n\t\tcase 4:\n\t\t\thddm->blocks->blocks[starts[(transpose?r2:c2)]] = hdd;\n\t\t\thddm->blocks->rowscols[starts[(transpose?r2:c2)]] = (transpose?c2:r2);\n\t\t\tstarts[(transpose?r2:c2)]++;\n\t\t\tbreak;\n\t\t\n\t\t// store blocks (cmsr)\n\t\tcase 5:\n\t\t\t// find block\n\t\t\tfor (i = 0; i < hddm->row_sizes[level]; i++) {\n\t\t\t\tif (hddm->row_tables[level][i] == hdd) break;\n\t\t\t}\n\t\t\t// store block\n\t\t\thddm->blocks->rowscols[starts[(transpose?c2:r2)]] = (unsigned int)(((unsigned int)(transpose?r2:c2) << (unsigned int)hddm->blocks->dist_shift) + (unsigned int)i);\n\t\t\tstarts[(transpose?c2:r2)]++;\n\t\t\tbreak;\n\t\t\n\t\t// store blocks (cmsc)\n\t\tcase 6:\n\t\t\t// find block\n\t\t\tfor (i = 0; i < hddm->row_sizes[level]; i++) {\n\t\t\t\tif (hddm->row_tables[level][i] == hdd) break;\n\t\t\t}\n\t\t\t// store block\n\t\t\thddm->blocks->rowscols[starts[(transpose?r2:c2)]] = (unsigned int)(((unsigned int)(transpose?c2:r2) << (unsigned int)hddm->blocks->dist_shift) + (unsigned int)i);\n\t\t\tstarts[(transpose?r2:c2)]++;\n\t\t\tbreak;\n\t\t\n\t\t// count entries in each row (rm)\n\t\tcase 7:\n\t\t\tstarts[(transpose?c:r)+1]++;\n\t\t\tbreak;\n\t\t\n\t\t// count entries in each column (cm)\n\t\tcase 8:\n\t\t\tstarts[(transpose?r:c)+1]++;\n\t\t\tbreak;\n\t\t\n\t\t// store entries (rm)\n\t\tcase 9:\n\t\t\trmsm->non_zeros[starts[(transpose?c:r)]] = hdd->type.val;\n\t\t\trmsm->cols[starts[(transpose?c:r)]] = (transpose?r:c);\n\t\t\tstarts[(transpose?c:r)]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// store entries (cm)\n\t\tcase 10:\n\t\t\tcmsm->non_zeros[starts[(transpose?r:c)]] = hdd->type.val;\n\t\t\tcmsm->rows[starts[(transpose?r:c)]] = (transpose?c:r);\n\t\t\tstarts[(transpose?r:c)]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// store entries (cmsr)\n\t\tcase 11:\n\t\t\tdist = hddm->dist;\n\t\t\tdist_num = hddm->dist_num;\n\t\t\tdist_shift = hddm->dist_shift;\n\t\t\tfor (i = 0; i < dist_num; i++) if (dist[i] == hdd->type.val) break;\n\t\t\tcmsrsm->cols[starts[(transpose?c:r)]] = (unsigned int)(((unsigned int)(transpose?r:c) << dist_shift) + (unsigned int)i);\n\t\t\tstarts[(transpose?c:r)]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// store entries (cmsc)\n\t\tcase 12:\n\t\t\tdist = hddm->dist;\n\t\t\tdist_num = hddm->dist_num;\n\t\t\tdist_shift = hddm->dist_shift;\n\t\t\tfor (i = 0; i < dist_num; i++) if (dist[i] == hdd->type.val) break;\n\t\t\tcmscsm->rows[starts[(transpose?r:c)]] = (unsigned int)(((unsigned int)(transpose?c:r) << dist_shift) + (unsigned int)i);\n\t\t\tstarts[(transpose?r:c)]++;\n\t\t\tbreak;\n\t\t}\n\t\treturn;\n\t}\n\t\n\t// recurse - split four ways\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\ttraverse_hdd_rec(e->type.kids.e, level+1, stop, r, c, code, transpose);\n\t\ttraverse_hdd_rec(e->type.kids.t, level+1, stop, r, c+e->off.val, code, transpose);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\ttraverse_hdd_rec(t->type.kids.e, level+1, stop, r+hdd->off.val, c, code, transpose);\n\t\ttraverse_hdd_rec(t->type.kids.t, level+1, stop, r+hdd->off.val, c+t->off.val, code, transpose);\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\n// generic function for recursive traversal of offset-labelled BDD\n\nvoid traverse_odd_rec(ODDNode *odd, int level, int stop, int index, int code)\n{\n\t// (if either we've gone down enough levels...)\n\t// (or there's no child node - i.e. points to zero terminal)\n\tif (odd->dd == Cudd_ReadZero(ddman)) {\n\t\treturn;\n\t}\n\tif (level == hddm->l_b) {\n\t\tswitch (code) {\n\t\t\n\t\t// compute n\n\t\tcase 1:\n\t\t\thddm->blocks->n++; break;\n\t\t\t\n\t\t// fill up offsets array\n\t\tcase 2:\n\t\t\thddm->blocks->offsets[hddm->blocks->n] = (int)index;\n\t\t\thddm->blocks->n++;\n\t\t\tbreak;\n\t\t}\n\t\treturn;\n\t}\n\t\n\t// recurse\n\ttraverse_odd_rec(odd->e, level+1, stop, index, code);\n\ttraverse_odd_rec(odd->t, level+1, stop, index+odd->eoff, code);\n}\n\n//-----------------------------------------------------------------------------------\n\n// compute the size (num states and nnz) of matrix corresponding to each offset-labelled MTBDD node\n// (and store in sm and off2 fields, respectively)\n\nint compute_n_and_nnz_rec(HDDNode *hdd, int level, int num_levels, ODDNode *row, ODDNode *col, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node... \n\tif (hdd == zero) {\n\t\thdd->sm.val = 0;\n\t\thdd->off2.val = 0;\n\t\treturn 0;\n\t}\n\t// if it's at the bottom...\n\tif (level == num_levels) {\n\t\thdd->sm.val = 0;\n\t\thdd->off2.val = 1;\n\t\treturn 1;\n\t}\n\t\n\t// check if we've already done this node\n\tif (hdd->sm.val != -1) {\n\t\treturn hdd->off2.val;\n\t}\n\t\n\t// store n (note we count rows or columns depending on transpose/row_major)\n\tif ((hddm->row_major && !transpose) || (!hddm->row_major && transpose)) {\n\t\thdd->sm.val = row->eoff + row->toff;\n\t} else {\n\t\thdd->sm.val = col->eoff + col->toff;\n\t}\n\t// recurse and store nnz\n\thdd->off2.val = 0;\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\thdd->off2.val += compute_n_and_nnz_rec(e->type.kids.e, level+1, num_levels, row->e, col->e, transpose);\n\t\thdd->off2.val += compute_n_and_nnz_rec(e->type.kids.t, level+1, num_levels, row->e, col->t, transpose);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\thdd->off2.val += compute_n_and_nnz_rec(t->type.kids.e, level+1, num_levels, row->t, col->e, transpose);\n\t\thdd->off2.val += compute_n_and_nnz_rec(t->type.kids.t, level+1, num_levels, row->t, col->t, transpose);\n\t}\n\treturn hdd->off2.val;\n}\n\n//-----------------------------------------------------------------------------------\n\n// build the explicit sparse matrix for a hdd node: 4 cases, one for each type\n\nRMSparseMatrix *build_rm_sparse_matrix(HDDNode *hdd, int level, bool transpose)\n{\n\tint i, n, nnz, max;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create the data structure\n\trmsm = NULL; rmsm = new RMSparseMatrix();\n\trmsm->n = n = hdd->sm.val;\n\trmsm->nnz = nnz = hdd->off2.val;\n\t\n\t// allocate temporary array to store start of each row\n\tstarts = NULL; starts = new int[n+1];\n\t// see how many nonzeros are in each row\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\ttraverse_hdd_rec(hdd, level, hddm->num_levels, 0, 0, 7, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a row)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\trmsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// allocate arrays\n\trmsm->non_zeros = new double[nnz];\n\thddm->mem_sm += ((nnz * sizeof(double)) / 1024.0);\n\trmsm->cols = new unsigned int[nnz];\n\thddm->mem_sm += ((nnz * sizeof(unsigned int)) / 1024.0);\n\t\n\t// fill up arrays\n\ttraverse_hdd_rec(hdd, level, hddm->num_levels, 0, 0, 9, transpose);\n\t\n\t// recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// assuming it's safe to do so, replace starts with (smaller) array of counts\n\t// if not, we keep the starts array and use that\n\tif (rmsm->use_counts) {\n\t\trmsm->row_counts = new unsigned char[n];\n\t\thddm->mem_sm += ((n * sizeof(unsigned char)) / 1024.0);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\trmsm->row_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\t}\n\t\tdelete[] starts; starts = NULL;\n\t}\n\telse {\n\t\trmsm->row_counts = (unsigned char*)starts;\n\t\thddm->mem_sm += ((n * sizeof(int)) / 1024.0);\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (rmsm) delete rmsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn rmsm;\n}\n\nCMSparseMatrix *build_cm_sparse_matrix(HDDNode *hdd, int level, bool transpose)\n{\n\tint i, n, nnz, max;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create the data structure\n\tcmsm = NULL; cmsm = new CMSparseMatrix();\n\tcmsm->n = n = hdd->sm.val;\n\tcmsm->nnz = nnz = hdd->off2.val;\n\t\n\t// allocate temporary array to store start of each col\n\tstarts = NULL; starts = new int[n+1];\n\t// see how many nonzeros are in each column\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\ttraverse_hdd_rec(hdd, level, hddm->num_levels, 0, 0, 8, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a col)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\tcmsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// allocate arrays\n\tcmsm->non_zeros = new double[nnz];\n\thddm->mem_sm += ((nnz * sizeof(double)) / 1024.0);\n\tcmsm->rows = new unsigned int[nnz];\n\thddm->mem_sm += ((nnz * sizeof(unsigned int)) / 1024.0);\n\t\n\t// fill up arrays\n\ttraverse_hdd_rec(hdd, level, hddm->num_levels, 0, 0, 10, transpose);\n\t\n\t// recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// assuming it's safe to do so, replace starts with (smaller) array of counts\n\t// if not, we keep the starts array and use that\n\tif (cmsm->use_counts) {\n\t\tcmsm->col_counts = new unsigned char[n];\n\t\thddm->mem_sm += ((n * sizeof(unsigned char)) / 1024.0);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tcmsm->col_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\t}\n\t\tdelete[] starts; starts = NULL;\n\t}\n\telse {\n\t\tcmsm->col_counts = (unsigned char*)starts;\n\t\thddm->mem_sm += ((n * sizeof(int)) / 1024.0);\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (cmsm) delete cmsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn cmsm;\n}\n\nCMSRSparseMatrix *build_cmsr_sparse_matrix(HDDNode *hdd, int level, bool transpose)\n{\n\tint i, n, nnz, max;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create the data structure\n\tcmsrsm = NULL; cmsrsm = new CMSRSparseMatrix();\n\tcmsrsm->n = n = hdd->sm.val;\n\tcmsrsm->nnz = nnz = hdd->off2.val;\n\t// info about distinct vals will be shared across the sparse matrices\n\t// so set this array to null to indicate that we don't use it\n\tcmsrsm->dist = NULL;\n\t\n\t// allocate temporary array to store start of each row\n\tstarts = NULL; starts = new int[n+1];\n\t// see how many nonzeros are in each row\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\ttraverse_hdd_rec(hdd, level, hddm->num_levels, 0, 0, 7, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a row)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\tcmsrsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// allocate arrays\n\tcmsrsm->cols = new unsigned int[nnz];\n\thddm->mem_sm += ((nnz * sizeof(unsigned int)) / 1024.0);\n\t\n\t// fill up arrays\n\ttraverse_hdd_rec(hdd, level, hddm->num_levels, 0, 0, 11, transpose);\n\t\n\t// recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// assuming it's safe to do so, replace starts with (smaller) array of counts\n\t// if not, we keep the starts array and use that\n\tif (cmsrsm->use_counts) {\n\t\tcmsrsm->row_counts = new unsigned char[n];\n\t\thddm->mem_sm += ((n * sizeof(unsigned char)) / 1024.0);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tcmsrsm->row_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\t}\n\t\tdelete[] starts; starts = NULL;\n\t}\n\telse {\n\t\tcmsrsm->row_counts = (unsigned char*)starts;\n\t\thddm->mem_sm += ((n * sizeof(int)) / 1024.0);\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (cmsrsm) delete cmsrsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn cmsrsm;\n}\n\nCMSCSparseMatrix *build_cmsc_sparse_matrix(HDDNode *hdd, int level, bool transpose)\n{\n\tint i, n, nnz, max;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create the data structure\n\tcmscsm = NULL; cmscsm = new CMSCSparseMatrix();\n\tcmscsm->n = n = hdd->sm.val;\n\tcmscsm->nnz = nnz = hdd->off2.val;\n\t// info about distinct vals will be shared across the sparse matrices\n\t// so set this array to null to indicate that we don't use it\n\tcmscsm->dist = NULL;\n\t\n\t// allocate temporary array to store start of each col\n\tstarts = NULL; starts = new int[n+1];\n\t// see how many nonzeros are in each column\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\ttraverse_hdd_rec(hdd, level, hddm->num_levels, 0, 0, 8, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a col)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\tcmscsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// allocate arrays\n\tcmscsm->rows = new unsigned int[nnz];\n\thddm->mem_sm += ((nnz * sizeof(unsigned int)) / 1024.0);\n\t\n\t// fill up arrays\n\ttraverse_hdd_rec(hdd, level, hddm->num_levels, 0, 0, 12, transpose);\n\t\n\t// recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// assuming it's safe to do so, replace starts with (smaller) array of counts\n\t// if not, we keep the starts array and use that\n\tif (cmscsm->use_counts) {\n\t\tcmscsm->col_counts = new unsigned char[n];\n\t\thddm->mem_sm += ((n * sizeof(unsigned char)) / 1024.0);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tcmscsm->col_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\t}\n\t\tdelete[] starts; starts = NULL;\n\t}\n\telse {\n\t\tcmscsm->col_counts = (unsigned char*)starts;\n\t\thddm->mem_sm += ((n * sizeof(int)) / 1024.0);\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (cmscsm) delete cmscsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn cmscsm;\n}\n\n//-----------------------------------------------------------------------------------\n// MDP variants of methods for constructing offset-labelled MTBDDs\n//-----------------------------------------------------------------------------------\n\n// builds hybrid mtbdd matrices from mtbdd (for mdp models)\n// if existing_mdp is non-null, use this for nm, cubes, etc.\n\nHDDMatrices *build_hdd_matrices_mdp(DdNode *mdp, HDDMatrices *existing_mdp, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, ODDNode *odd)\n{\n\tint i;\n\tDdNode *tmp;\n\tHDDMatrix *hddm = NULL;\n\tHDDMatrices *res = NULL;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\tres = new HDDMatrices();\n\t\n\t// get nm (number of matrices to split into)\n\tif (existing_mdp != NULL) {\n\t\t// just copy existing stats if appropriate\n\t\tres->nm = existing_mdp->nm;\n\t} else {\n\t\t// otherwise compute nm from scratch\n\t\tCudd_Ref(mdp);\n\t\ttmp = DD_GreaterThan(ddman, mdp, 0);\n\t\ttmp = DD_ThereExists(ddman, tmp, rvars, num_vars);\n\t\ttmp = DD_ThereExists(ddman, tmp, cvars, num_vars);\n\t\tres->nm = (int)DD_GetNumMinterms(ddman, tmp, num_ndvars);\n\t\tCudd_RecursiveDeref(ddman, tmp);\n\t}\n\t\n\t// allocate/init arrays\n\tres->choices = new HDDMatrix*[res->nm];\n\tres->cubes = new DdNode*[res->nm];\n\tfor (i = 0; i < res->nm; i++) {\n\t\tres->choices[i] = NULL;\n\t\tres->cubes[i] = NULL;\n\t}\n\t\n\t// initialise other fields/stats\n\tres->compact_sm = false;\n\tres->num_levels = 0;\n\tres->l_sm_min = 0;\n\tres->l_sm_max = 0;\n\tres->num_nodes = 0;\n\tres->num_sm = 0;\n\tres->mem_nodes = 0;\n\tres->mem_sm = 0;\n\t\n\t// get cubes to extract sub-mtbdds\n\tif (existing_mdp != NULL) {\n\t\t// just copy existing cubes if appropriate\n\t\tfor (i = 0; i < res->nm; i++) {\n\t\t\tCudd_Ref(existing_mdp->cubes[i]);\n\t\t\tres->cubes[i] = existing_mdp->cubes[i];\n\t\t}\n\t} else {\n\t\t// otherwise build them\n\t\t// (first resetting nm so can use as counter)\n\t\tres->nm = 0;\n\t\tbuild_mdp_cubes_rec(mdp, DD_Constant(ddman, 1), rvars, cvars, num_vars, ndvars, num_ndvars, 0, odd, res);\n\t}\n\t\n\t// extract sub-mtbdds using cubes\n\tfor (i = 0; i < res->nm; i++) {\n\t\t// extract each part of the mtbdd using its cube\n\t\tCudd_Ref(mdp);\n\t\tCudd_Ref(res->cubes[i]);\n\t\ttmp = DD_Apply(ddman, APPLY_TIMES, mdp, res->cubes[i]);\n\t\ttmp = DD_SumAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t// then build hybrid mtbdd and store it\n\t\thddm = build_hdd_matrix(tmp, rvars, cvars, num_vars, odd, true);\n\t\t//printf(\"%d -> %d\\n\", DD_GetNumNodes(ddman, tmp), hddm->num_nodes);\n\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\tres->choices[i] = hddm;\n\t\t// update stats\n\t\tres->num_levels = hddm->num_levels;\n\t\tres->num_nodes += hddm->num_nodes;\n\t}\n\t\n\t// compute memory for nodes\n\tres->mem_nodes = (res->num_nodes * sizeof(HDDNode)) / 1024.0;\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (res) delete res;\n\t\tthrow e;\n\t}\n\t\n\treturn res;\n}\n\n//-----------------------------------------------------------------------------------\n\nvoid build_mdp_cubes_rec(DdNode *dd, DdNode *cube, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, int level, ODDNode *odd, HDDMatrices *hddms)\n{\n\tDdNode *e, *t, *cube_e, *cube_t;\n\t\n\t// base case - empty choice (matrix)\n\tif (dd == Cudd_ReadZero(ddman)) {\n\t\tCudd_RecursiveDeref(ddman, cube);\n\t\treturn;\n\t}\n\t\n\t// base case - nonempty choice (matrix)\n\tif (level == num_ndvars) {\n\t\thddms->cubes[hddms->nm] = cube;\n\t\thddms->nm++;\n\t\treturn;\n\t}\n\t\n\t// recurse\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(ndvars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\tCudd_Ref(cube);\n\tCudd_Ref(ndvars[level]);\n\tcube_e = DD_And(ddman, cube, DD_Not(ddman, ndvars[level]));\n\tCudd_Ref(cube);\n\tCudd_Ref(ndvars[level]);\n\tcube_t = DD_And(ddman, cube, ndvars[level]);\n\tCudd_RecursiveDeref(ddman, cube);\n\t\n\tbuild_mdp_cubes_rec(e, cube_e, rvars, cvars, num_vars, ndvars, num_ndvars, level+1, odd, hddms);\n\tbuild_mdp_cubes_rec(t, cube_t, rvars, cvars, num_vars, ndvars, num_ndvars, level+1, odd, hddms);\n}\n\n//-----------------------------------------------------------------------------------\n\n// adds sparse matrices on to several hdds (for mdps)\n\nvoid add_sparse_matrices_mdp(HDDMatrices *hddms, bool compact_sm)\n{\n\tint i;\n\t\n\t// initialise sparse matrix stats\n\thddms->compact_sm = 0;\n\thddms->l_sm_min = 0;\n\thddms->l_sm_max = 0;\n\thddms->num_sm = 0;\n\thddms->mem_sm = 0;\n\t\n\t// add sparse matrices separately for each matrix\n\tfor (i = 0; i < hddms->nm; i++) {\n\t\t// add sparse matrix\n\t\tadd_sparse_matrices(hddms->choices[i], compact_sm, false);\n\t\t// update stats\n\t\tif (hddms->choices[i]->compact_sm) hddms->compact_sm++;\n\t\tif (i == 0) {\n\t\t\thddms->l_sm_min = hddms->l_sm_max = hddms->choices[i]->l_sm;\n\t\t} else {\n\t\t\tif (hddms->choices[i]->l_sm < hddms->l_sm_min) hddms->l_sm_min = hddms->choices[i]->l_sm;\n\t\t\tif (hddms->choices[i]->l_sm > hddms->l_sm_max) hddms->l_sm_max = hddms->choices[i]->l_sm;\n\t\t}\n\t\thddms->num_sm += hddms->choices[i]->num_sm;\n\t\thddms->mem_sm += hddms->choices[i]->mem_sm;\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n// Methods which manipulate/use offset-labelled MTBBDs\n//-----------------------------------------------------------------------------------\n\n// rearrange matrix blocks:\n// 1. put diagonal block at end of row/col (need like that for gauss-seidel)\n// 2. if ooc flag set, put block before diag at start (helps for out-of-core)\n\nvoid rearrange_hdd_blocks(HDDMatrix *hddm, bool ooc)\n{\n\tint i, j, l, h, rowcol, iminus1;\n\t\n\tint b_n = hddm->blocks->n;\n\tHDDNode **b_blocks = hddm->blocks->blocks;\n\tunsigned int *b_rowscols = hddm->blocks->rowscols;\n\tunsigned char *b_counts = hddm->blocks->counts;\n\tint *b_starts = (int *)hddm->blocks->counts;\n\tbool b_use_counts = hddm->blocks->use_counts;\n\tint b_dist_shift = hddm->blocks->dist_shift;\n\t\t\n\t// go through each row/column of blocks\n\th = 0;\n\tfor(i = 0; i < b_n; i++) {\n\t\timinus1 = (i==0)?b_n-1:i-1;\n\t\tif (!b_use_counts) { l = b_starts[i]; h = b_starts[i+1]; }\n\t\telse { l = h; h += b_counts[i]; }\n\t\t// go along this row/column\n\t\tfor(j = l; j < h; j++) {\n\t\t\t\n\t\t\t// get column/row index of block\n\t\t\tif (!hddm->compact_b) {\n\t\t\t\trowcol = b_rowscols[j];\n\t\t\t} else {\n\t\t\t\trowcol = (unsigned int)(b_rowscols[j] >> b_dist_shift);\n\t\t\t}\n\t\t\t// if it's the diagonal, put it at the end\n\t\t\tif (rowcol == i) {\n\t\t\t\tunsigned int tmp = b_rowscols[j];\n\t\t\t\tb_rowscols[j] = b_rowscols[h-1];\n\t\t\t\tb_rowscols[h-1] = tmp;\n\t\t\t\tif (!hddm->compact_b) {\n\t\t\t\t\tHDDNode *tmp = b_blocks[j];\n\t\t\t\t\tb_blocks[j] = b_blocks[h-1];\n\t\t\t\t\tb_blocks[h-1] = tmp;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// if it's the one before the diagonal and the ooc flag is set, put it at the start\n\t\t\tif (rowcol == iminus1) {\n\t\t\t\tunsigned int tmp = b_rowscols[j];\n\t\t\t\tb_rowscols[j] = b_rowscols[l];\n\t\t\t\tb_rowscols[l] = tmp;\n\t\t\t\tif (!hddm->compact_b) {\n\t\t\t\t\tHDDNode *tmp = b_blocks[j];\n\t\t\t\t\tb_blocks[j] = b_blocks[l];\n\t\t\t\t\tb_blocks[l] = tmp;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\n// compute negative sum of elements in each row\n// if transpose flag is true, matrix was previously transposed so,\n// where sparse matrix based storage used (top-level block storage\n// and bottom-level submatrix storage), sum for columns instead\n\n// throws std::bad_alloc on out-of-memory\n\ndouble *hdd_negative_row_sums(HDDMatrix *hddm, int n)\n{ return hdd_negative_row_sums(hddm, n, false); }\n\ndouble *hdd_negative_row_sums(HDDMatrix *hddm, int n, bool transpose)\n{\n\tint i, j, l, h;\n\tdouble *diags = NULL;\n\tbool compact_b = hddm->compact_b;\n\tcompact_sm = hddm->compact_sm;\n\trow_major = hddm->row_major;\n\tif (compact_sm) {\n\t\tsm_dist = hddm->dist;\n\t\tsm_dist_shift = hddm->dist_shift;\n\t\tsm_dist_mask = hddm->dist_mask;\n\t}\n\tzero = hddm->zero;\n\tnum_levels = hddm->num_levels;\n\t\n\t// allocate/initialise array\n\tdiags = new double[n];\n\tfor (int i = 0; i < n; i++) diags[i] = 0;\n\t\n\t// if the matrix hasn't been split into blocks, jump straight to traversal\n\tif (!hddm->blocks) {\n\t\thdd_negative_row_sums_rec(hddm->top, 0, 0, 0, diags, transpose);\n\t\treturn diags;\n\t}\n\t\n\t// stuff for block storage\n\tint b_n = hddm->blocks->n;\n\tHDDNode **b_blocks = hddm->blocks->blocks;\n\tunsigned int *b_rowscols = hddm->blocks->rowscols;\n\tunsigned char *b_counts = hddm->blocks->counts;\n\tint *b_starts = (int *)hddm->blocks->counts;\n\tbool b_use_counts = hddm->blocks->use_counts;\n\tint *b_offsets = hddm->blocks->offsets;\n\tHDDNode **b_nodes = hddm->row_tables[hddm->l_b];\n\tint b_dist_shift = hddm->blocks->dist_shift;\n\tint b_dist_mask = hddm->blocks->dist_mask;\n\tint row_offset;\n\tint col_offset;\n\tHDDNode *node;\n\n\t// TODO: it looks like col_offset is not actually used during the various\n\t// recursion steps (including swapping when transpose is set);\n\t// candidate for removal / refactoring\n\t// initialise col_offset\n\tcol_offset = 0;\n\n\t// loop through rows/columns of blocks\n\th = 0;\n\tfor (i = 0; i < b_n; i++) {\n\t\t\n\t\t// loop through blocks in this row/column of blocks\n\t\tif (!b_use_counts) { l = b_starts[i]; h = b_starts[i+1]; }\n\t\telse { l = h; h += b_counts[i]; }\n\t\tfor (j = l; j < h; j++) {\n\t\t\t\n\t\t\t// get node for block and its row offset\n\t\t\tif (!compact_b) {\n\t\t\t\tnode = b_blocks[j];\n\t\t\t\trow_offset = b_offsets[b_rowscols[j]];\n\t\t\t} else {\n\t\t\t\tnode = b_nodes[(int)(b_rowscols[j] & b_dist_mask)];\n\t\t\t\trow_offset = b_offsets[(int)(b_rowscols[j] >> b_dist_shift)];\n\t\t\t}\n\t\t\t\n\t\t\t// recursively traverse block\n\t\t\thdd_negative_row_sums_rec(node, hddm->l_b, row_offset, col_offset, diags, transpose);\n\t\t}\n\t}\n\t\n\treturn diags;\n}\n\nvoid hdd_negative_row_sums_rec(HDDNode *hdd, int level, int row_offset, int col_offset, double *diags, bool transpose)\n{\n\tHDDNode *e, *t;\n\t\n\t// if it's the zero node\n\tif (hdd == zero) {\n\t\treturn;\n\t}\n\t// or if we've reached a submatrix\n\t// (check for non-null ptr but, equivalently, we could just check if level==l_sm)\n\telse if (hdd->sm.ptr) {\n\t\tif (row_major) {\n\t\t\tif (!compact_sm) {\n\t\t\t\thdd_negative_row_sums_rm((RMSparseMatrix *)hdd->sm.ptr, (transpose?col_offset:row_offset), (transpose?row_offset:col_offset), diags, transpose);\n\t\t\t} else {\n\t\t\t\thdd_negative_row_sums_cmsr((CMSRSparseMatrix *)hdd->sm.ptr, (transpose?col_offset:row_offset), (transpose?row_offset:col_offset), diags, transpose);\n\t\t\t}\n\t\t} else {\n\t\t\tif (!compact_sm) {\n\t\t\t\thdd_negative_row_sums_cm((CMSparseMatrix *)hdd->sm.ptr, (transpose?col_offset:row_offset), (transpose?row_offset:col_offset), diags, transpose);\n\t\t\t} else {\n\t\t\t\thdd_negative_row_sums_cmsc((CMSCSparseMatrix *)hdd->sm.ptr, (transpose?col_offset:row_offset), (transpose?row_offset:col_offset), diags, transpose);\n\t\t\t}\n\t\t}\n\t\treturn;\n\t}\n\t// or if we've reached the bottom\n\telse if (level == num_levels) {\n\t\t//printf(\"(%d,%d)=%f\\n\", row_offset, col_offset, hdd->type.val);\n\t\tdiags[row_offset] -= hdd->type.val;\n\t\treturn;\n\t}\n\t// otherwise recurse\n\te = hdd->type.kids.e;\n\tif (e != zero) {\n\t\thdd_negative_row_sums_rec(e->type.kids.e, level+1, row_offset, col_offset, diags, transpose);\n\t\thdd_negative_row_sums_rec(e->type.kids.t, level+1, row_offset, col_offset+e->off.val, diags, transpose);\n\t}\n\tt = hdd->type.kids.t;\n\tif (t != zero) {\n\t\thdd_negative_row_sums_rec(t->type.kids.e, level+1, row_offset+hdd->off.val, col_offset, diags, transpose);\n\t\thdd_negative_row_sums_rec(t->type.kids.t, level+1, row_offset+hdd->off.val, col_offset+t->off.val, diags, transpose);\n\t}\n}\n\nvoid hdd_negative_row_sums_rm(RMSparseMatrix *rmsm, int row_offset, int col_offset, double *diags, bool transpose)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = rmsm->n;\n\tint sm_nnz = rmsm->nnz;\n\tdouble *sm_non_zeros = rmsm->non_zeros;\n\tunsigned char *sm_row_counts = rmsm->row_counts;\n\tint *sm_row_starts = (int *)rmsm->row_counts;\n\tbool sm_use_counts = rmsm->use_counts;\n\tunsigned int *sm_cols = rmsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tdiags[(transpose?col_offset+sm_cols[j2]:row_offset + i2)] -= sm_non_zeros[j2];\n\t\t}\n\t}\n}\n\nvoid hdd_negative_row_sums_cm(CMSparseMatrix *cmsm, int row_offset, int col_offset, double *diags, bool transpose)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsm->n;\n\tint sm_nnz = cmsm->nnz;\n\tdouble *sm_non_zeros = cmsm->non_zeros;\n\tunsigned char *sm_col_counts = cmsm->col_counts;\n\tint *sm_col_starts = (int *)cmsm->col_counts;\n\tbool sm_use_counts = cmsm->use_counts;\n\tunsigned int *sm_rows = cmsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tdiags[(transpose?col_offset + i2:row_offset + sm_rows[j2])] -= sm_non_zeros[j2];\n\t\t}\n\t}\n}\n\nvoid hdd_negative_row_sums_cmsr(CMSRSparseMatrix *cmsrsm, int row_offset, int col_offset, double *diags, bool transpose)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmsrsm->n;\n\tint sm_nnz = cmsrsm->nnz;\n\tunsigned char *sm_row_counts = cmsrsm->row_counts;\n\tint *sm_row_starts = (int *)cmsrsm->row_counts;\n\tbool sm_use_counts = cmsrsm->use_counts;\n\tunsigned int *sm_cols = cmsrsm->cols;\n\t\n\t// loop through rows of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this row\n\t\tif (!sm_use_counts) { l2 = sm_row_starts[i2]; h2 = sm_row_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_row_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tdiags[(transpose?col_offset + ((int)(sm_cols[j2] >> sm_dist_shift)):row_offset + i2)] -= sm_dist[(int)(sm_cols[j2] & sm_dist_mask)];\n\t\t}\n\t}\n}\n\nvoid hdd_negative_row_sums_cmsc(CMSCSparseMatrix *cmscsm, int row_offset, int col_offset, double *diags, bool transpose)\n{\n\tint i2, j2, l2, h2;\n\tint sm_n = cmscsm->n;\n\tint sm_nnz = cmscsm->nnz;\n\tunsigned char *sm_col_counts = cmscsm->col_counts;\n\tint *sm_col_starts = (int *)cmscsm->col_counts;\n\tbool sm_use_counts = cmscsm->use_counts;\n\tunsigned int *sm_rows = cmscsm->rows;\n\t\n\t// loop through columns of submatrix\n\tl2 = sm_nnz; h2 = 0;\n\tfor (i2 = 0; i2 < sm_n; i2++) {\n\t\t\n\t\t// loop through entries in this column\n\t\tif (!sm_use_counts) { l2 = sm_col_starts[i2]; h2 = sm_col_starts[i2+1]; }\n\t\telse { l2 = h2; h2 += sm_col_counts[i2]; }\n\t\tfor (j2 = l2; j2 < h2; j2++) {\n\t\t\tdiags[(transpose?col_offset + i2:row_offset + ((int)(sm_rows[j2] >> sm_dist_shift)))] -= sm_dist[(int)(sm_rows[j2] & sm_dist_mask)];\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/hybrid/package-info.java",
    "content": "/**\n * Access to the \"Hybrid\" engine: data structures and model checking algorithms that mix MTBDDs and explicit-state techniques.\n */\npackage hybrid;\n"
  },
  {
    "path": "prism/src/io/DRNExporter.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport explicit.CTMC;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport explicit.PartiallyObservableModel;\nimport explicit.rewards.Rewards;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismUtils;\nimport prism.RewardGenerator;\n\nimport java.util.BitSet;\nimport java.util.List;\n\n/**\n * Class to manage export of built models to Storm's DRN file format.\n */\npublic class DRNExporter<Value> extends ModelExporter<Value>\n{\n\t/**\n\t * Construct a DRNExporter with default export options.\n\t */\n\tpublic DRNExporter()\n\t{\n\t\tsuper();\n\t}\n\n\t/**\n\t * Construct a DRNExporter with the specified export options.\n\t */\n\tpublic DRNExporter(ModelExportOptions modelExportOptions)\n\t{\n\t\tsuper(modelExportOptions);\n\t}\n\n\t@Override\n\tpublic void exportModel(Model<Value> model, PrismLog out) throws PrismException\n\t{\n\t\t// Get model info and options\n\t\tsetEvaluator(model.getEvaluator());\n\t\tEvaluator<Value> evalRewards = getRewardEvaluator();\n\t\tModelType modelType = model.getModelType();\n\t\tint numRewards = getNumRewards();\n\t\tint numLabels = getNumLabels();\n\t\tint numStates = model.getNumStates();\n\t\t// By default, we only show actions for nondeterministic models\n\t\tboolean showActions = modelExportOptions.getShowActions(modelType.nondeterministic());\n\n\t\t// Output header\n\t\tout.println(\"// Exported by prism\");\n\t\tout.println(\"// Original model type: \" + modelType);\n\t\tout.println(\"@type: \" + modelType);\n\n\t\t// No parameters\n\t\tout.println(\"@parameters\");\n\t\tout.println();\n\n\t\t// Output reward structure info\n\t\tout.println(\"@reward_models\");\n\t\tout.println(String.join(\" \", PrismUtils.listReversed(getRewardNames())));\n\n\t\t// Output model stats\n\t\tout.println(\"@nr_states\");\n\t\tout.println(model.getNumStates());\n\t\tout.println(\"@nr_choices\");\n\t\tif (modelType.nondeterministic()) {\n\t\t\tout.println(((NondetModel<Value>) model).getNumChoices());\n\t\t} else {\n\t\t\tout.println(model.getNumStates());\n\t\t}\n\n\t\t// Output states and transitions\n\t\tout.println(\"@model\");\n\n\t\t// Iterate through states\n\t\tfor (int s = 0; s < numStates; s++) {\n\n\t\t\t// Output state info\n\t\t\tout.print(\"state \" + s);\n\t\t\tif (modelType.partiallyObservable()) {\n\t\t\t\tout.print(\" {\" + ((PartiallyObservableModel<Value>) model).getObservation(s) +\"}\");\n\t\t\t}\n\t\t\tif (modelType.continuousTime()) {\n\t\t\t\tout.print(\" !\" + ((CTMC<Value>) model).getExitRate(s));\n\t\t\t}\n\t\t\tif (numRewards > 0) {\n\t\t\t\tout.print(\" \" + getStateRewardTuple(getRewards(), s).toStringReversed(e -> formatValue(e, evalRewards), \", \"));\n\t\t\t}\n\t\t\tfor (int i = 0; i < numLabels; i++) {\n\t\t\t\tif (getLabel(i).get(s)) {\n\t\t\t\t\tout.print(\" \" + getLabelName(i));\n\t\t\t\t}\n\t\t\t}\n\t\t\tout.println();\n\n\t\t\t// Iterate through choices\n\t\t\tint numChoices = 1;\n\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\tnumChoices = ((NondetModel<Value>) model).getNumChoices(s);\n\t\t\t}\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\tout.print(\"\\taction \");\n\t\t\t\tif (modelType.nondeterministic() && showActions) {\n\t\t\t\t\tObject action = ((NondetModel<Value>) model).getAction(s, j);\n\t\t\t\t\tout.print(action != null ? action : \"__NOLABEL__\");\n\t\t\t\t} else {\n\t\t\t\t\tout.print(j);\n\t\t\t\t}\n\t\t\t\tif (numRewards > 0) {\n\t\t\t\t\tout.print(\" \" + getTransitionRewardTuple(getRewards(), s, j).toStringReversed(e -> formatValue(e, evalRewards), \", \"));\n\t\t\t\t}\n\t\t\t\tout.println();\n\t\t\t\t// Print out (sorted) transitions\n\t\t\t\tfor (Transition<?> transition : getSortedTransitionsIterator(model, s, j, showActions)) {\n\t\t\t\t\tout.println(\"\\t\\t\" + transition.target + \" : \" + transition.toString(modelExportOptions));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/DotExporter.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport explicit.Model;\nimport explicit.NondetModel;\nimport explicit.PartiallyObservableModel;\nimport explicit.graphviz.Decorator;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLog;\n\n/**\n * Class to manage export of built models to Dot format.\n */\npublic class DotExporter<Value> extends ModelExporter<Value>\n{\n\tpublic DotExporter()\n\t{\n\t\tsuper();\n\t}\n\n\tpublic DotExporter(ModelExportOptions modelExportOptions)\n\t{\n\t\tsuper(modelExportOptions);\n\t}\n\n\t@Override\n\tpublic void exportModel(Model<Value> model, PrismLog out) throws PrismException\n\t{\n\t\texportModel(model, out, null);\n\t}\n\n\t/**\n\t * Export a model in Dot format.\n\t * @param model Model to export\n\t * @param out PrismLog to export to\n\t * @param decorators Any Dot decorators to add (ignored if null)\n\t */\n\tpublic void exportModel(Model<Value> model, PrismLog out, Iterable<explicit.graphviz.Decorator> decorators) throws PrismException\n\t{\n\t\t// Get model info and exportOptions\n\t\tsetEvaluator(model.getEvaluator());\n\t\tModelType modelType = model.getModelType();\n\t\tint numStates = model.getNumStates();\n\t\tboolean showActions = modelExportOptions.getShowActions();\n\n\t\t// Get default Dot formatting info\n\t\texplicit.graphviz.Decoration defaults = new explicit.graphviz.Decoration();\n\t\tdefaults.attributes().put(\"shape\", \"box\");\n\n\t\t// Output header\n\t\tout.println(\"digraph \" + \"M\" + \" {\");\n\t\tout.println(\"node \" + defaults + \";\");\n\n\t\t// Output transitions in Dot format\n\t\t// Iterate through states\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t// Set up Dot Decoration\n\t\t\texplicit.graphviz.Decoration d = new explicit.graphviz.Decoration(defaults);\n\t\t\td.setLabel(Integer.toString(s));\n\t\t\tboolean showStates = modelExportOptions.getShowStates() && model.getStatesList() != null;\n\t\t\tboolean showObs = modelType.partiallyObservable() && modelExportOptions.getShowObservations();\n\t\t\tif (showStates && showObs) {\n\t\t\t\td = new explicit.graphviz.ShowStatesDecorator(model.getStatesList(), ((PartiallyObservableModel<Value>) model)::getObservationAsState).decorateState(s, d);\n\t\t\t} else if (showStates) {\n\t\t\t\td = new explicit.graphviz.ShowStatesDecorator(model.getStatesList()).decorateState(s, d);\n\t\t\t} else if (showObs) {\n\t\t\t\td = new explicit.graphviz.ShowStatesDecorator(null, ((PartiallyObservableModel<Value>) model)::getObservationAsState).decorateState(s, d);\n\t\t\t}\n\t\t\tif (decorators != null) {\n\t\t\t\tfor (Decorator decorator : decorators) {\n\t\t\t\t\td = decorator.decorateState(s, d);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Output state details\n\t\t\tString nodeSrc = Integer.toString(s);\n\t\t\tString nodeMid = Integer.toString(s);\n\t\t\tString decoration = d.toString();\n\t\t\tout.println(nodeSrc + \" \" + decoration + \";\");\n\n\t\t\t// Iterate through choices\n\t\t\tint numChoices = 1;\n\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\tnumChoices = ((NondetModel<Value>) model).getNumChoices(s);\n\t\t\t}\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\n\t\t\t\t// For nondeterministic models, display the choice\n\t\t\t\tif (modelType.nondeterministic() && modelType.isProbabilistic()) {\n\t\t\t\t\t// Print a new dot file line for the initial line fragment for this choice\n\t\t\t\t\tnodeMid = \"n\" + s + \"_\" + j;\n\t\t\t\t\tout.print(nodeSrc + \" -> \" + nodeMid + \" \");\n\t\t\t\t\t// Annotate this with the choice index/action\n\t\t\t\t\texplicit.graphviz.Decoration d2 = new explicit.graphviz.Decoration();\n\t\t\t\t\td2.attributes().put(\"arrowhead\", \"none\");\n\t\t\t\t\tif (showActions) {\n\t\t\t\t\t\tObject action = ((NondetModel<Value>) model).getAction(s, j);\n\t\t\t\t\t\tif (showActions && action != null && !\"\".equals(action)) {\n\t\t\t\t\t\t\td2.setLabel(j + \":\" + action);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\td2.setLabel(Integer.toString(j));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Apply any other decorators requested\n\t\t\t\t\tif (decorators != null) {\n\t\t\t\t\t\tfor (Decorator decorator : decorators) {\n\t\t\t\t\t\t\td2 = decorator.decorateTransition(s, j, d2);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Append to the dot file line\n\t\t\t\t\tout.println(\" \" + d2.toString() + \";\");\n\t\t\t\t\t// Print a new dot file line for the point where this choice branches\n\t\t\t\t\tout.print(nodeMid + \" [ shape=point,width=0.1,height=0.1,label=\\\"\\\" ];\\n\");\n\t\t\t\t}\n\n\t\t\t\t// Print out (sorted) transitions\n\t\t\t\tfor (Transition<?> transition : getSortedTransitionsIterator(model, s, j, showActions && !modelType.nondeterministic())) {\n\t\t\t\t\t// Print a new Dot file line for the arrow for this transition\n\t\t\t\t\tout.print(nodeMid + \" -> \" + transition.target);\n\t\t\t\t\t// Annotate this arrow with the probability\n\t\t\t\t\texplicit.graphviz.Decoration d3 = new explicit.graphviz.Decoration();\n\t\t\t\t\tif (modelType.isProbabilistic()) {\n\t\t\t\t\t\tif (showActions && transition.action != null && !\"\".equals(transition.action)) {\n\t\t\t\t\t\t\td3.setLabel(transition.toString(modelExportOptions) + \":\" + transition.action);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\td3.setLabel(transition.toString(modelExportOptions));\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tObject action = ((NondetModel<Value>) model).getAction(s, j);\n\t\t\t\t\t\tif (showActions && action != null && !\"\".equals(action)) {\n\t\t\t\t\t\t\td3.setLabel(j + \":\" + action);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\td3.setLabel(Integer.toString(j));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Apply any other decorators requested\n\t\t\t\t\tif (decorators != null) {\n\t\t\t\t\t\tfor (Decorator decorator : decorators) {\n\t\t\t\t\t\t\td3 = decorator.decorateProbability(s, transition.target, transition.value, d3);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Append to the Dot file line for this transition\n\t\t\t\t\tout.println(\" \" + d3.toString() + \";\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Output footer\n\t\tout.print(\"}\\n\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/ExplicitModelImporter.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.oc.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport parser.ast.DeclarationInt;\nimport parser.ast.DeclarationType;\nimport parser.ast.Expression;\nimport parser.type.Type;\nimport parser.type.TypeInt;\nimport prism.Evaluator;\nimport prism.ModelInfo;\nimport prism.PrismException;\nimport prism.RewardInfo;\n\nimport java.util.BitSet;\nimport java.util.function.BiConsumer;\nimport java.util.function.Consumer;\nimport java.util.function.IntConsumer;\n\n/**\n * Base class for importers from explicit model sources.\n */\npublic abstract class ExplicitModelImporter\n{\n\t// Importer config or cached information\n\n\t/** How transition rewards are indexed */\n\tpublic enum TransitionRewardIndexing {\n\t\tOFFSET, // Offset within rewards for state/choice\n\t\tSTATE // Index of successor state\n\t};\n\tprotected TransitionRewardIndexing transitionRewardIndexing = TransitionRewardIndexing.OFFSET;\n\n\t/** Should deadlocks be detected and fixed (by adding a self-loop) on import? */\n\tprotected boolean fixdl;\n\n\t/**\n\t * Specify whether should deadlocks be detected and fixed (by adding a self-loop) on import\n\t */\n\tpublic void setFixDeadlocks(boolean fixdl)\n\t{\n\t\tthis.fixdl = fixdl;\n\t}\n\n\t/**\n\t * Specify how transition rewards should be supplied when extracted.\n\t */\n\tpublic void setTransitionRewardIndexing(TransitionRewardIndexing transitionRewardIndexing)\n\t{\n\t\tthis.transitionRewardIndexing = transitionRewardIndexing;\n\t}\n\n\t/**\n\t * Access provide to a model (usually constructed earlier using this importer)\n\t * which can be looked up to identify transition info (usually for extracting rewards).\n\t */\n\tprotected explicit.Model modelLookup;\n\n\t/**\n\t * Provide access to a model (usually constructed earlier using this importer)\n\t * which can be looked up to identify transition info (usually for extracting rewards).\n\t */\n\tpublic void setModel(explicit.Model modelLookup)\n\t{\n\t\tthis.modelLookup = modelLookup;\n\t}\n\n\t// Methods to be implemented by an importer\n\n\t/**\n\t * Is this model represented exactly (rationals), rather than doubles?\n\t */\n\tpublic boolean modelIsExact()\n\t{\n\t\t// By default, assume not exact\n\t\treturn false;\n\t}\n\n\t/**\n\t * Does this importer provide info about state definitions?\n\t */\n\tpublic abstract boolean providesStates();\n\n\t/**\n\t * Does this importer provide info about observation definitions?\n\t */\n\tpublic abstract boolean providesObservations();\n\n\t/**\n\t * Does this importer provide info about labels?\n\t */\n\tpublic abstract boolean providesLabels();\n\n\t/**\n\t * Get a string summarising the source, e.g. the list of files read in.\n\t */\n\tpublic abstract String sourceString();\n\n\t/**\n\t * Get info about the model (type, variables, labels, etc.).\n\t * If {@link #providesLabels()} returns false, this will report zero labels.\n\t * If {@link #providesStates()} returns false, this will report a single\n\t * integer-valued variable with name {@link #defaultVariableName()}.\n\t */\n\tpublic abstract ModelInfo getModelInfo() throws PrismException;\n\n\t/**\n\t * Get the number of states.\n\t */\n\tpublic abstract int getNumStates() throws PrismException;\n\n\t/**\n\t * Get the total number of choices (for nondeterministic models).\n\t */\n\tpublic abstract int getNumChoices() throws PrismException;\n\n\t/**\n\t * Get the total number of transitions.\n\t */\n\tpublic abstract int getNumTransitions() throws PrismException;\n\n\t/**\n\t * Get the number of observations.\n\t */\n\tpublic abstract int getNumObservations() throws PrismException;\n\n\t/**\n\t * Get the indices of the states which are/were deadlocks.\n\t */\n\tpublic abstract BitSet getDeadlockStates() throws PrismException;\n\n\t/**\n\t * Get the number of states which are/were deadlocks.\n\t */\n\tpublic abstract int getNumDeadlockStates() throws PrismException;\n\n\t/**\n\t * Get a string stating the model type and how it was obtained.\n\t */\n\tpublic String getModelTypeString() throws PrismException\n\t{\n\t\t// By default, just return the type, no explanation\n\t\treturn getModelInfo().getModelType().toString();\n\t}\n\n\t/**\n\t * Get info about the rewards.\n\t */\n\tpublic abstract RewardInfo getRewardInfo() throws PrismException;\n\n\t/**\n\t * Extract state definitions (variable values).\n\t * Calls {@code storeStateDefn(s, i, v)} for each state s, variable (index) i and variable value v.\n\t * If {@link #providesStates()} returns false, this should report a single\n\t * integer-valued variable ranging between 0 and {@link #getNumStates()} - 1.\n\t * @param storeStateDefn Function to be called for each variable value of each state\n\t */\n\tpublic void extractStates(IOUtils.StateDefnConsumer storeStateDefn) throws PrismException\n\t{\n\t\t// Default implementation - assume one integer variable\n\t\tint numStates = getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tstoreStateDefn.accept(s, 0, s);\n\t\t}\n\t}\n\n\t/**\n\t * Extract observation definitions (observable values).\n\t * Calls {@code storeObservationDefn(o, i, v)} for each observation o, observable (index) i and observable value v.\n\t * If {@link #providesObservations()} returns false, this should report a single\n\t * integer-valued observable ranging between 0 and {@link #getNumObservations()} - 1.\n\t * @param storeObservationDefn Function to be called for each variable value of each state\n\t */\n\tpublic void extractObservationDefinitions(IOUtils.StateDefnConsumer storeObservationDefn) throws PrismException\n\t{\n\t\t// Default implementation - assume one integer observable\n\t\tint numObs = getNumObservations();\n\t\tfor (int o = 0; o < numObs; o++) {\n\t\t\tstoreObservationDefn.accept(o, 0, o);\n\t\t}\n\t}\n\n\t/**\n\t * Compute the maximum number of choices (in a nondeterministic model).\n\t */\n\tpublic abstract int computeMaxNumChoices() throws PrismException;\n\n\t/**\n\t * Extract the (Markov chain) transitions.\n\t * The transition probabilities/rates are assumed to be of type double.\n\t * @param storeTransition Function to be called for each transition\n\t */\n\tpublic void extractMCTransitions(IOUtils.MCTransitionConsumer<Double> storeTransition) throws PrismException\n\t{\n\t\textractMCTransitions(storeTransition, Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Extract the (Markov chain) transitions.\n\t * The transition probabilities/rates are assumed to be of type Value.\n\t * @param storeTransition Function to be called for each transition\n\t * @param eval Evaluator for Value objects\n\t */\n\tpublic abstract <Value> void extractMCTransitions(IOUtils.MCTransitionConsumer<Value> storeTransition, Evaluator<Value> eval) throws PrismException;\n\n\t/**\n\t * Extract the (Markov decision process) transitions.\n\t * The transition probabilities/rates are assumed to be of type double.\n\t * @param storeTransition Function to be called for each transition\n\t */\n\tpublic void extractMDPTransitions(IOUtils.MDPTransitionConsumer<Double> storeTransition) throws PrismException\n\t{\n\t\textractMDPTransitions(storeTransition, Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Extract the (Markov decision process) transitions.\n\t * The transition probabilities/rates are assumed to be of type Value.\n\t * @param storeTransition Function to be called for each transition\n\t * @param eval Evaluator for Value objects\n\t */\n\tpublic abstract <Value> void extractMDPTransitions(IOUtils.MDPTransitionConsumer<Value> storeTransition, Evaluator<Value> eval) throws PrismException;\n\n\t/**\n\t * Extract the (labelled transition system) transitions.\n\t * @param storeTransition Function to be called for each transition\n\t */\n\tpublic abstract void extractLTSTransitions(IOUtils.LTSTransitionConsumer storeTransition) throws PrismException;\n\n\t/**\n\t * Extract info about state labellings and initial states.\n\t * Calls {@code storeLabel(s, i)} for each state s satisfying label l,\n\t * where l is 0-indexed and matches the label list from {@link #getModelInfo()}.\n\t * Calls {@code storeInit(s)} for each initial state s.\n\t * Any \"deadlock\" labels are ignored.\n\t * @param storeLabel Function to be called for each state satisfying a label\n\t * @param storeInit Function to be called for each initial stat\n\t */\n\tpublic void extractLabelsAndInitialStates(BiConsumer<Integer, Integer> storeLabel, Consumer<Integer> storeInit) throws PrismException\n\t{\n\t\textractLabelsAndInitialStates(storeLabel, storeInit, null);\n\t}\n\n\t/**\n\t * Extract info about state labellings and initial states.\n\t * Calls {@code storeLabel(s, i)} for each state s satisfying label l,\n\t * where l is 0-indexed and matches the label list from {@link #getModelInfo()}.\n\t * Calls {@code storeInit(s)} for each initial state s.\n\t * If {@code storeDeadlock} is non-null, it will be called for each state labelled\n\t * with \"deadlock\", regardless of whether it has been detected as a deadlock and/or fixed.\n\t * @param storeLabel Function to be called for each state satisfying a label\n\t * @param storeInit Function to be called for each initial state\n\t * @param storeDeadlock Function to be called for each state marked as a deadlock\n\t */\n\tpublic abstract void extractLabelsAndInitialStates(BiConsumer<Integer, Integer> storeLabel, Consumer<Integer> storeInit, Consumer<Integer> storeDeadlock) throws PrismException;\n\n\t/**\n\t * Extract info about (deterministic, state-based) observations.\n\t * Calls {@code storeObservation(s, o)} for each state s giving its observation o.\n\t * @param storeObservation Function to be called for each state\n\t */\n\tpublic abstract void extractObservations(IOUtils.StateIntConsumer storeObservation) throws PrismException;\n\n\t/**\n\t * Extract the state rewards for a given reward structure index.\n\t * The transition probabilities/rates are assumed to be of type double.\n\t * @param rewardIndex Index of reward structure to extract (0-indexed)\n\t * @param storeReward Function to be called for each reward\n\t */\n\tpublic void extractStateRewards(int rewardIndex, BiConsumer<Integer, Double> storeReward) throws PrismException\n\t{\n\t\textractStateRewards(rewardIndex, storeReward, Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Extract the state rewards for a given reward structure index.\n\t * The transition probabilities/rates are assumed to be of type Value.\n\t * @param rewardIndex Index of reward structure to extract (0-indexed)\n\t * @param storeReward Function to be called for each reward\n\t * @param eval Evaluator for Value objects\n\t */\n\tpublic abstract <Value> void extractStateRewards(int rewardIndex, BiConsumer<Integer, Value> storeReward, Evaluator<Value> eval) throws PrismException;\n\n\t/**\n\t * Extract the (Markov chain) transition rewards for a given reward structure index.\n\t * These are supplied as tuples (s,i,v) where s is the (source) state and v is the reward value.\n\t * The index i is either the offset within the state or the index of the successor state,\n\t * depending on what has been specified with {@link #setTransitionRewardIndexing(TransitionRewardIndexing)}.\n\t * The reward values are assumed to be of type double.\n\t * @param rewardIndex Index of reward structure to extract (0-indexed)\n\t * @param storeReward Function to be called for each reward\n\t */\n\tpublic void extractMCTransitionRewards(int rewardIndex, IOUtils.TransitionRewardConsumer<Double> storeReward) throws PrismException\n\t{\n\t\textractMCTransitionRewards(rewardIndex, storeReward, Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Extract the (Markov chain) transition rewards for a given reward structure index.\n\t * These are supplied as tuples (s,i,v) where s is the (source) state and v is the reward value.\n\t * The index i is either the offset within the state or the index of the successor state,\n\t * depending on what has been specified with {@link #setTransitionRewardIndexing(TransitionRewardIndexing)}.\n\t * The reward values are assumed to be of type Value.\n\t * @param rewardIndex Index of reward structure to extract (0-indexed)\n\t * @param storeReward Function to be called for each reward\n\t * @param eval Evaluator for Value objects\n\t */\n\tpublic abstract <Value> void extractMCTransitionRewards(int rewardIndex, IOUtils.TransitionRewardConsumer<Value> storeReward, Evaluator<Value> eval) throws PrismException;\n\n\t/**\n\t * Extract the (Markov decision process) transition rewards for a given reward structure index.\n\t * These are supplied as tuples (s,i,v) where s is the (source) state,\n\t * i is the choice index and v is the reward value.\n\t * The reward values are assumed to be of type double.\n\t * @param rewardIndex Index of reward structure to extract (0-indexed)\n\t * @param storeReward Function to be called for each reward\n\t */\n\tpublic void extractMDPTransitionRewards(int rewardIndex, IOUtils.TransitionRewardConsumer<Double> storeReward) throws PrismException\n\t{\n\t\textractMDPTransitionRewards(rewardIndex, storeReward, Evaluator.forDouble());\n\t}\n\n\t/**\n\t * Extract the (Markov decision process) transition rewards for a given reward structure index.\n\t * These are supplied as tuples (s,i,v) where s is the (source) state,\n\t * i is the choice index and v is the reward value.\n\t * The reward values are assumed to be of type Value.\n\t * @param rewardIndex Index of reward structure to extract (0-indexed)\n\t * @param storeReward Function to be called for each reward\n\t * @param eval Evaluator for Value objects\n\t */\n\tpublic abstract <Value> void extractMDPTransitionRewards(int rewardIndex, IOUtils.TransitionRewardConsumer<Value> storeReward, Evaluator<Value> eval) throws PrismException;\n\n\t// Defaults for a single variable when none is specified\n\n\t/**\n\t * Get the default name for the (single) variable when none is specified.\n\t * By default, this is \"x\".\n\t */\n\tpublic String defaultVariableName()\n\t{\n\t\treturn \"x\";\n\t}\n\n\t/**\n\t * Get the default type for the (single) variable when none is specified.\n\t * By default, this is {@code int}.\n\t */\n\tpublic Type defaultVariableType()\n\t{\n\t\treturn TypeInt.getInstance();\n\t}\n\n\t/**\n\t * Get the default type declaration for the (single) variable when none is specified.\n\t * By default, this is {@code [0..(numStates-1)]}.\n\t */\n\tpublic DeclarationType defaultVariableDeclarationType() throws PrismException\n\t{\n\t\treturn new DeclarationInt(Expression.Int(0), Expression.Int(getNumStates() - 1));\n\t}\n\n\t// Defaults for a single observable when none is specified\n\n\t/**\n\t * Get the default name for the (single) observable when none is specified.\n\t * By default, this is \"o\".\n\t */\n\tpublic String defaultObservableName()\n\t{\n\t\treturn \"o\";\n\t}\n\n\t/**\n\t * Get the default type for the (single) observable when none is specified.\n\t * By default, this is {@code int}.\n\t */\n\tpublic Type defaultObservableType()\n\t{\n\t\treturn TypeInt.getInstance();\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/IOUtils.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport prism.PrismException;\n\n/**\n * Various utilities for input-output functionality\n */\npublic class IOUtils\n{\n\t/**\n\t * Functional interface for a consumer accepting state variable values (s,i,v),\n\t * i.e., state s, variable index i, value v.\n\t */\n\t@FunctionalInterface\n\tpublic interface StateDefnConsumer {\n\t\tvoid accept(int s, int i, Object v) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting Markov chain like transitions (s,s2,v,a),\n\t * i.e., source state s, target state s2, probability v, (optional) action a.\n\t */\n\t@FunctionalInterface\n\tpublic interface MCTransitionConsumer<V> {\n\t\tvoid accept(int s, int s2, V v, Object a) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting MDP-like transitions (s,i,s2,v,a),\n\t * i.e., source state s, index i, target state s2, probability v, (optional) action a.\n\t */\n\t@FunctionalInterface\n\tpublic interface MDPTransitionConsumer<V> {\n\t\tvoid accept(int s, int i, int s2, V v, Object a) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting LTS-like transitions (s,i,s2,a),\n\t * i.e., source state s, index i, target state s2, (optional) action a.\n\t */\n\t@FunctionalInterface\n\tpublic interface LTSTransitionConsumer {\n\t\tvoid accept(int s, int i, int s2, Object a) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting integer state values (s,v),\n\t * i.e., state s, value v.\n\t */\n\t@FunctionalInterface\n\tpublic interface StateIntConsumer {\n\t\tvoid accept(int s, int v) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting state values (s,v),\n\t * i.e., state s, value v.\n\t */\n\t@FunctionalInterface\n\tpublic interface StateValueConsumer<V> {\n\t\tvoid accept(int s, V v) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting state rewards (s,v),\n\t * i.e., state s, value v.\n\t */\n\t@FunctionalInterface\n\tpublic interface StateRewardConsumer<V> {\n\t\tvoid accept(int s, V v) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting transition rewards (s,i,v),\n\t * i.e., source state s, index i, value v.\n\t */\n\t@FunctionalInterface\n\tpublic interface TransitionRewardConsumer<V> {\n\t\tvoid accept(int s, int i, V v) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting transition-successor-state rewards (s,i,s2,v),\n\t * i.e., source state s, index i, target state s2, value v.\n\t */\n\t// TODO REMOVE\n\t@FunctionalInterface\n\tpublic interface TransitionStateRewardConsumer<V> {\n\t\tvoid accept(int s, int i, int s2, V v) throws PrismException;\n\t}\n\n\t/**\n\t * Functional interface for a consumer accepting transition-successor-state rewards (s,i,j,v),\n\t * i.e., source state s, index one i, index two j, target state s2, value v.\n\t */\n\t@FunctionalInterface\n\tpublic interface TransitionSuccRewardConsumer<V> {\n\t\tvoid accept(int s, int i, int j, V v) throws PrismException;\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/MatlabExporter.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport explicit.Model;\nimport explicit.PartiallyObservableModel;\nimport parser.State;\nimport parser.VarList;\nimport prism.ModelInfo;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\n\nimport java.util.BitSet;\nimport java.util.List;\n\n/**\n * Class to manage export of built models to Matlab format.\n */\npublic class MatlabExporter<Value> extends ModelExporter<Value>\n{\n\tpublic MatlabExporter()\n\t{\n\t\tsuper();\n\t}\n\n\tpublic MatlabExporter(ModelExportOptions modelExportOptions)\n\t{\n\t\tsuper(modelExportOptions);\n\t}\n\n\t@Override\n\tpublic void exportModel(Model<Value> model, PrismLog out) throws PrismException\n\t{\n\t\tthrow new PrismNotSupportedException(\"Model export not supported in Matlab format\");\n\t}\n\n\t/**\n\t * Export the states for a model.\n\t * @param model The model\n\t * @param varList The VarList for the model\n\t * @param out Where to export\n\t */\n\tpublic void exportStates(Model<Value> model, VarList varList, PrismLog out) throws PrismException\n\t{\n\t\tList<State> statesList = model.getStatesList();\n\t\tif (statesList == null)\n\t\t\treturn;\n\n\t\t// Print header: list of model vars\n\t\tout.print(\"% (\");\n\t\tint numVars = varList.getNumVars();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tout.print(varList.getName(i));\n\t\t\tif (i < numVars - 1)\n\t\t\t\tout.print(\",\");\n\t\t}\n\t\tout.println(\")\");\n\n\t\t// Print states\n\t\tout.println(\"states=[\");\n\t\tint numStates = statesList.size();\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tout.println(statesList.get(i).toStringNoParentheses());\n\t\t}\n\n\t\t// Print footer\n\t\tout.println(\"];\");\n\t}\n\n\t/**\n\t * Export the observations for a (partially observable) model.\n\t * @param model The model\n\t * @param modelInfo The ModelInfo for the model\n\t * @param out Where to export\n\t */\n\tpublic void exportObservations(PartiallyObservableModel<Value> model, ModelInfo modelInfo, PrismLog out) throws PrismException\n\t{\n\t\tList<State> observationsList =  model.getObservationsList();\n\n\t\t// Print header: list of observables\n\t\tout.print(\"% (\");\n\t\tint numObservables = modelInfo.getNumObservables();\n\t\tfor (int i = 0; i < numObservables; i++) {\n\t\t\tout.print(modelInfo.getObservableName(i));\n\t\t\tif (i < numObservables - 1)\n\t\t\t\tout.print(\",\");\n\t\t}\n\t\tout.println(\")\");\n\n\t\t// Print states + observations\n\t\tout.println(\"obs=[\");\n\t\tint numObservations = model.getNumObservations();\n\t\tfor (int i = 0; i < numObservations; i++) {\n\t\t\tout.println(observationsList.get(i).toStringNoParentheses());\n\t\t}\n\n\t\t// Print footer\n\t\tout.println(\"];\");\n\t}\n\n\t/**\n\t * Export a set of labels and the states that satisfy them.\n\t * @param model The model\n\t * @param labelNames The names of the labels to export\n\t * @param labelStates The states that satisfy each label, specified as a BitSet\n\t * @param out Where to export\n\t */\n\tpublic void exportLabels(Model<Value> model, List<String> labelNames, List<BitSet> labelStates, PrismLog out) throws PrismException\n\t{\n\t\t// Get model info and exportOptions\n\t\tsetEvaluator(model.getEvaluator());\n\t\tint numStates = model.getNumStates();\n\n\t\t// Print list of labels\n\t\tString varName = \"l\";\n\t\tint numLabels = labelNames.size();\n\t\tfor (int s = 0; s < numLabels; s++) {\n\t\t\tout.println(varName + \"_\" + labelNames.get(s) + \"=sparse(\" + numStates + \",1);\");\n\t\t}\n\t\tout.println();\n\n\t\t// Go through states and print satisfying label indices for each one\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tboolean first = true;\n\t\t\tfor (int i = 0; i < numLabels; i++) {\n\t\t\t\tif (labelStates.get(i).get(s)) {\n\t\t\t\t\tout.println(varName + \"_\" + labelNames.get(i) + \"(\" + (s + 1) + \")=1;\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/ModelAccess.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport common.Interval;\nimport common.iterable.SingletonIterator;\nimport explicit.*;\nimport explicit.rewards.Rewards;\nimport it.unimi.dsi.fastutil.doubles.DoubleArrayList;\nimport it.unimi.dsi.fastutil.doubles.DoubleIterators;\nimport it.unimi.dsi.fastutil.doubles.DoubleList;\nimport it.unimi.dsi.fastutil.ints.IntIterators;\nimport param.BigRational;\nimport prism.Evaluator;\nimport prism.ModelType;\n\nimport java.util.*;\nimport java.util.function.Consumer;\n\n/**\n * Interface for (read-only) access to model data, unified across all model types.\n * Also provides compressed spare row (CSR) style access to the data.\n * This is generic, where probabilities/rates/etc. are of type {@code Value}.\n */\npublic interface ModelAccess<Value>\n{\n\t/**\n\t * Get the type of this model.\n\t */\n\tModelType getModelType();\n\n\t/**\n\t * Get an Evaluator for the values stored in this Model for probabilities etc.\n\t */\n\tEvaluator<Value> getEvaluator();\n\n\t/**\n\t * Get a list of the action labels attached to choices/transitions.\n\t * This can be a superset of the action labels that are actually used in the model.\n\t * Action labels can be any Object, but will often be treated as a string,\n\t * so should at least have a meaningful toString() method implemented.\n\t * Absence of an action label is denoted by null,\n\t * and null is also included in this list if there are unlabelled choices/transitions.\n\t */\n\tList<Object> getActions();\n\n\t/**\n\t * Get strings for the action labels attached to choices/transitions.\n\t * The empty/absent action (null) is included here as \"\".\n\t */\n\tList<String> getActionStrings();\n\n\t/**\n\t * Get the number of players.\n\t */\n\tint getNumPlayers();\n\n\t/**\n\t * Get the number of observations.\n\t */\n\tint getNumObservations();\n\n\t/**\n\t * Get the number of states.\n\t */\n\tint getNumStates();\n\n\t/**\n\t * Get the number of nondeterministic choices in state s.\n\t */\n\tint getNumChoices(int s);\n\n\t/**\n\t * Get the total number of nondeterministic choices over all states.\n\t */\n\tdefault int getNumChoices()\n\t{\n\t\tint numChoices = 0;\n\t\tfor (int s = 0, numStates = getNumStates(); s < numStates; s++) {\n\t\t\tnumChoices += getNumChoices(s);\n\t\t}\n\t\treturn numChoices;\n\t}\n\t/**\n\t * Get the number of transitions from choice {@code i} of state {@code s}.\n\t */\n\tint getNumTransitions(int s, int i);\n\n\t/**\n\t * Get the number of transitions from state s.\n\t */\n\tdefault int getNumTransitions(int s)\n\t{\n\t\tint numChoices = getNumChoices(s);\n\t\tint numTransitions = 0;\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tnumTransitions += getNumTransitions(s, i);\n\t\t}\n\t\treturn numTransitions;\n\t}\n\n\t/**\n\t * Get the total number of transitions.\n\t */\n\tdefault int getNumTransitions()\n\t{\n\t\tint numStates = getNumStates();\n\t\tint numTransitions = 0;\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tnumTransitions += getNumTransitions(s);\n\t\t}\n\t\treturn numTransitions;\n\t}\n\n\t/**\n\t * Get an iterator over the transitions from choice {@code i} of state {@code s}.\n\t * For CTMCs, this returns the embedded DTMC transitions.\n\t * For interval models, this returns just the lower bound of each probability interval.\n\t * For LTSs, this returns a singleton iterator with a null probability value.\n\t */\n\tIterator<Map.Entry<Integer, Value>> getTransitionsIterator(int s, int i);\n\n\t/**\n\t * Get the successor (target state) of the {@code j}th transition from choice {@code i} of state {@code s}.\n\t */\n\tint getTransitionSuccessor(int s, int i, int j);\n\n\t/**\n\t * Get the exit rate for state {@code s} of a CTMC (returns null for other models).\n\t */\n\tValue getExitRate(int s);\n\n\t/**\n\t * Get the action label for choice {@code i} of state {@code s}.\n\t * This is null if unlabelled.\n\t */\n\tObject getChoiceAction(int s, int i);\n\n\t/**\n\t * Get the index of the action label for choice {@code i} of state {@code s}.\n\t * This is 0 if unlabelled.\n\t */\n\tint getChoiceActionIndex(int s, int i);\n\n\t/**\n\t * Get the action labels for the transitions from choice {@code i} of state {@code s}.\n\t * These are null if unlabelled.\n\t */\n\tIterator<Object> getTransitionActionsIterator(int s, int i);\n\n\t/**\n\t * Get the indices of the action labels for transitions from choice {@code i} of state {@code s}.\n\t * These are 0 if unlabelled.\n\t */\n\tPrimitiveIterator.OfInt getTransitionActionIndicesIterator(int s, int i);\n\n\t/**\n\t * Get the number of initial states.\n\t */\n\tint getNumInitialStates();\n\n\t/**\n\t * Get the initial states.\n\t */\n\tPrimitiveIterator.OfInt getInitialStates();\n\n\t/**\n\t * Get the (deterministic) observation for state {@code s}\n\t * of a partially observable model (returns -1 for other models).\n\t */\n\tint getStateObservation(int s);\n\n\t/**\n\t * For interval models, Get the underlying model over {@code Interval<Value>}.\n\t */\n\tModelAccess<Interval<Value>> getIntervalModel();\n\n\t// Wrapper around existing model classes (for now)\n\n\t/**\n\t * Create a {@link ModelAccess} wrapped around a {@link Model}.\n\t * @param model The model\n\t */\n\tstatic <Value> ModelAccess<Value> wrap(Model<Value> model)\n\t{\n\t\treturn new ModelAccess<>() {\n\n\t\t\t@Override\n\t\t\tpublic ModelType getModelType()\n\t\t\t{\n\t\t\t\treturn model.getModelType();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Evaluator<Value> getEvaluator()\n\t\t\t{\n\t\t\t\treturn model.getEvaluator();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic List<Object> getActions()\n\t\t\t{\n\t\t\t\treturn model.getActions();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic List<String> getActionStrings()\n\t\t\t{\n\t\t\t\treturn model.getActionStrings();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getNumPlayers()\n\t\t\t{\n\t\t\t\treturn model.getNumPlayers();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getNumObservations()\n\t\t\t{\n\t\t\t\tif (getModelType().partiallyObservable()) {\n\t\t\t\t\treturn ((PartiallyObservableModel<?>) model).getNumObservations();\n\t\t\t\t} else {\n\t\t\t\t\treturn 0;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getNumStates()\n\t\t\t{\n\t\t\t\treturn model.getNumStates();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getNumChoices(int s)\n\t\t\t{\n\t\t\t\tif (model instanceof NondetModel) {\n\t\t\t\t\treturn ((NondetModel<Value>) model).getNumChoices(s);\n\t\t\t\t} else {\n\t\t\t\t\treturn 1;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getNumTransitions(int s, int i)\n\t\t\t{\n\t\t\t\tif (model instanceof NondetModel) {\n\t\t\t\t\treturn ((NondetModel<Value>) model).getNumTransitions(s, i);\n\t\t\t\t} else {\n\t\t\t\t\t// assume i==0\n\t\t\t\t\treturn model.getNumTransitions(s);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getTransitionSuccessor(int s, int i, int j)\n\t\t\t{\n\t\t\t\t// TODO: Inefficient!\n\t\t\t\tIterator<Map.Entry<Integer, Value>> iter = getTransitionsIterator(s, i);\n\t\t\t\tfor (int k = 0; k < j; k++) {\n\t\t\t\t\titer.next();\n\t\t\t\t}\n\t\t\t\treturn iter.next().getKey();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Value getExitRate(int s)\n\t\t\t{\n\t\t\t\tif (model instanceof CTMC) {\n\t\t\t\t\treturn ((CTMC<Value>) model).getExitRate(s);\n\t\t\t\t} else {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Iterator<Map.Entry<Integer, Value>> getTransitionsIterator(int s, int i)\n\t\t\t{\n\t\t\t\tif (model instanceof MDP) {\n\t\t\t\t\treturn ((MDP<Value>) model).getTransitionsIterator(s, i);\n\t\t\t\t} else if (model instanceof CTMC) {\n\t\t\t\t\t// assume i==0\n\t\t\t\t\treturn ((CTMC<Value>) model).getEmbeddedTransitionsIterator(s);\n\t\t\t\t} else if (model instanceof DTMC) {\n\t\t\t\t\t// assume i==0\n\t\t\t\t\treturn ((DTMC<Value>) model).getTransitionsIterator(s);\n\t\t\t\t} else if (model instanceof LTS) {\n\t\t\t\t\treturn new SingletonIterator.Of<>(new AbstractMap.SimpleImmutableEntry<>(((LTS<Value>) model).getSuccessor(s, i), (Value) null));\n\t\t\t\t} else if (model instanceof IMDP) {\n\t\t\t\t\treturn ((IMDP<Value>) model).getIntervalModel().getTransitionsMappedIterator(s, i, Interval::getLower);\n\t\t\t\t} else if (model instanceof IDTMC) {\n\t\t\t\t\treturn ((IDTMC<Value>) model).getIntervalModel().getTransitionsMappedIterator(s, Interval::getLower);\n\t\t\t\t} else if (model instanceof IPOMDP) {\n\t\t\t\t\treturn ((IPOMDP<Value>) model).getIntervalModel().getTransitionsMappedIterator(s, i, Interval::getLower);\n\t\t\t\t} else {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Object getChoiceAction(int s, int i)\n\t\t\t{\n\t\t\t\tif (model instanceof NondetModel) {\n\t\t\t\t\treturn ((NondetModel<Value>) model).getAction(s, i);\n\t\t\t\t} else {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getChoiceActionIndex(int s, int i)\n\t\t\t{\n\t\t\t\tif (model instanceof NondetModel) {\n\t\t\t\t\treturn ((NondetModel<Value>) model).getActionIndex(s, i);\n\t\t\t\t} else {\n\t\t\t\t\treturn -1;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Iterator<Object> getTransitionActionsIterator(int s, int i)\n\t\t\t{\n\t\t\t\tif (model instanceof DTMC) {\n\t\t\t\t\t// assume i==0\n\t\t\t\t\treturn ((DTMC<Value>) model).getActionsIterator(s);\n\t\t\t\t} else if (model instanceof IDTMC) {\n\t\t\t\t\t\t// assume i==0\n\t\t\t\t\t\treturn ((IDTMC<Value>) model).getIntervalModel().getActionsIterator(s);\n\t\t\t\t} else {\n\t\t\t\t\treturn Collections.nCopies(getNumTransitions(s, i), null).iterator();\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic PrimitiveIterator.OfInt getTransitionActionIndicesIterator(int s, int i)\n\t\t\t{\n\t\t\t\tif (model instanceof DTMC) {\n\t\t\t\t\t// assume i==0\n\t\t\t\t\treturn ((DTMC<Value>) model).getActionIndicesIterator(s);\n\t\t\t\t} else if (model instanceof IDTMC) {\n\t\t\t\t\t// assume i==0\n\t\t\t\t\treturn ((IDTMC<Value>) model).getIntervalModel().getActionIndicesIterator(s);\n\t\t\t\t} else {\n\t\t\t\t\treturn Utils.nCopiesIntIterator(getNumTransitions(s, i), -1);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getNumInitialStates()\n\t\t\t{\n\t\t\t\treturn model.getNumInitialStates();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic PrimitiveIterator.OfInt getInitialStates()\n\t\t\t{\n\t\t\t\treturn IntIterators.asIntIterator(model.getInitialStates().iterator());\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getStateObservation(int s)\n\t\t\t{\n\t\t\t\tif (model instanceof PartiallyObservableModel) {\n\t\t\t\t\treturn ((PartiallyObservableModel<Value>) model).getObservation(s);\n\t\t\t\t} else {\n\t\t\t\t\treturn -1;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic ModelAccess<Interval<Value>> getIntervalModel()\n\t\t\t{\n\t\t\t\tif (model instanceof IntervalModel){\n\t\t\t\t\treturn ModelAccess.wrap(((IntervalModel<Value>) model).getIntervalModel());\n\t\t\t\t} else {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t}\n\n\t\t};\n\t}\n\n\t// Various iterators, with default implementations\n\n\t/**\n\t * Get, for all states, the offset at which its choices start, as an iterator.\n\t * The iterator returns {@code }numStates+1} values, with the final value\n\t * equalling the total count of all choices. As used in column sparse row format.\n\t */\n\tdefault PrimitiveIterator.OfInt getStateChoiceOffsets()\n\t{\n\t\treturn new ModelAccessIterators.GetStateChoiceCounts<>(this)\n\t\t{\n\t\t\tboolean first = true;\n\t\t\tint iCount = 0;\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\tif (first) {\n\t\t\t\t\tfirst = false;\n\t\t\t\t\treturn 0;\n\t\t\t\t}\n\t\t\t\tiCount += super.nextInt();\n\t\t\t\treturn iCount;\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get, for all states, the offset at which its transitions start, as an iterator.\n\t * The iterator returns {@code }numStates+1} values, with the final value\n\t * equalling the total count of all transitions. As used in column sparse row format.\n\t */\n\tdefault PrimitiveIterator.OfInt getStateTransitionOffsets()\n\t{\n\t\treturn new ModelAccessIterators.GetStateTransitionCounts<>(this)\n\t\t{\n\t\t\tboolean first = true;\n\t\t\tint jCount = 0;\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\tif (first) {\n\t\t\t\t\tfirst = false;\n\t\t\t\t\treturn 0;\n\t\t\t\t}\n\t\t\t\tjCount += super.nextInt();\n\t\t\t\treturn jCount;\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get, for all choices, the offset at which its transitions start, as an iterator.\n\t * The iterator returns {@code }numChoices+1} values, with the final value\n\t * equalling the total count of all transitions. As used in column sparse row format.\n\t */\n\tdefault PrimitiveIterator.OfInt getChoiceTransitionOffsets()\n\t{\n\t\treturn new ModelAccessIterators.GetChoiceTransitionCounts<>(this)\n\t\t{\n\t\t\tboolean first = true;\n\t\t\tint jCount = 0;\n\n\t\t\t@Override\n\t\t\tpublic int nextInt()\n\t\t\t{\n\t\t\t\tif (first) {\n\t\t\t\t\tfirst = false;\n\t\t\t\t\treturn 0;\n\t\t\t\t}\n\t\t\t\tjCount += super.nextInt();\n\t\t\t\treturn jCount;\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get the probabilities for all transitions, as an iterator.\n\t * For interval models, this returns two probabilities (lower then upper bound) for each transition.\n\t */\n\tdefault Iterator<Value> getTransitionProbabilities()\n\t{\n\t\tif (getModelType().intervals()) {\n\t\t\treturn new ModelAccessIterators.UnpackIntervals<>(getIntervalModel().getTransitionProbabilities());\n\t\t} else {\n\t\t\treturn new ModelAccessIterators.GetTransitionValues<>(this)\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic Value getValue()\n\t\t\t\t{\n\t\t\t\t\treturn transition.getValue();\n\t\t\t\t}\n\t\t\t};\n\t\t}\n\t}\n\n\t/**\n\t * Get the probabilities for all transitions, as an iterator,\n\t * encoded into primitive types (see {@link #valuesToPrimitives(Iterator)}).\n\t * For interval models, this returns two probabilities (lower then upper bound) for each transition.\n\t */\n\tdefault Iterator<?> getTransitionProbabilitiesAsPrimitives()\n\t{\n\t\treturn valuesToPrimitives(getTransitionProbabilities());\n\t}\n\n\t/**\n\t * Get the successor states for all transitions, as an iterator.\n\t */\n\tdefault PrimitiveIterator.OfInt getTransitionSuccessors()\n\t{\n\t\treturn new ModelAccessIterators.GetTransitionIntValues<>(this)\n\t\t{\n\t\t\t@Override\n\t\t\tpublic int getIntValue()\n\t\t\t{\n\t\t\t\treturn transition.getKey();\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get the exit rates for all states, as an iterator.\n\t */\n\tdefault Iterator<Value> getExitRates()\n\t{\n\t\treturn new ModelAccessIterators.GetStateValues<>(this)\n\t\t{\n\t\t\t@Override\n\t\t\tpublic Value getValue()\n\t\t\t{\n\t\t\t\treturn model.getExitRate(s);\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get the exit rates for all states, as an iterator,\n\t * encoded into primitive types (see {@link #valuesToPrimitives(Iterator)}).\n\t */\n\tdefault Iterator<?> getExitRatesAsPrimitives()\n\t{\n\t\treturn valuesToPrimitives(getExitRates());\n\t}\n\n\t/**\n\t * Get the actions for all choices, as an iterator.\n\t */\n\tdefault Iterator<Object> getChoiceActions()\n\t{\n\t\tif (getModelType().nondeterministic()) {\n\t\t\treturn new ModelAccessIterators.GetChoiceValues<>(this)\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic Object getValue()\n\t\t\t\t{\n\t\t\t\t\treturn model.getChoiceAction(s, i);\n\t\t\t\t}\n\t\t\t};\n\t\t} else {\n\t\t\treturn Collections.nCopies(getNumChoices(), null).iterator();\n\t\t}\n\t}\n\n\t/**\n\t * Get the action indices for all choices, as an iterator.\n\t */\n\tdefault PrimitiveIterator.OfInt getChoiceActionIndices()\n\t{\n\t\tif (getModelType().nondeterministic()) {\n\t\t\treturn new ModelAccessIterators.GetChoiceIntValues<>(this)\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic int getIntValue()\n\t\t\t\t{\n\t\t\t\t\treturn model.getChoiceActionIndex(s, i);\n\t\t\t\t}\n\t\t\t};\n\t\t} else {\n\t\t\treturn Utils.nCopiesIntIterator(getNumChoices(), -1);\n\t\t}\n\t}\n\n\t/**\n\t * Get the action indices for all transitions, as an iterator.\n\t */\n\tdefault PrimitiveIterator.OfInt getTransitionActionIndices()\n\t{\n\t\treturn new ModelAccessIterators.GetTransitionIntValues<>(this, true)\n\t\t{\n\t\t\t@Override\n\t\t\tpublic int getIntValue()\n\t\t\t{\n\t\t\t\treturn actionIndex;\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get the observations for all states, as an iterator.\n\t */\n\tdefault PrimitiveIterator.OfInt getStateObservations()\n\t{\n\t\treturn new ModelAccessIterators.GetStateIntValues<>(this)\n\t\t{\n\t\t\t@Override\n\t\t\tpublic int getIntValue()\n\t\t\t{\n\t\t\t\treturn model.getStateObservation(s);\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get all state rewards from a {@link Rewards} object, as an iterator.\n\t * @param rewards The rewards\n\t */\n\tdefault <E> Iterator<E> getStateRewards(Rewards<E> rewards)\n\t{\n\t\treturn new ModelAccessIterators.GetStateValues<>(this)\n\t\t{\n\t\t\t@Override\n\t\t\tpublic E getValue()\n\t\t\t{\n\t\t\t\treturn rewards.getStateReward(s);\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get all state rewards from a {@link Rewards} object, as an iterator,\n\t * encoded into primitive types (see {@link #valuesToPrimitives(Iterator)}).\n\t * @param rewards The rewards\n\t */\n\tdefault <E> Iterator<?> getStateRewardsAsPrimitives(Rewards<E> rewards)\n\t{\n\t\treturn valuesToPrimitives(getStateRewards(rewards));\n\t}\n\n\t/**\n\t * Get all transition rewards from a {@link Rewards} object, as an iterator.\n\t * @param rewards The rewards\n\t */\n\tdefault <E> Iterator<E> getTransitionRewards(Rewards<E> rewards)\n\t{\n\t\tif (getModelType().nondeterministic()) {\n\t\t\treturn new ModelAccessIterators.GetChoiceValues<>(this)\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic E getValue()\n\t\t\t\t{\n\t\t\t\t\treturn rewards.getTransitionReward(s, i);\n\t\t\t\t}\n\t\t\t};\n\t\t} else {\n\t\t\treturn new ModelAccessIterators.GetTransitionValues<>(this)\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic E getValue()\n\t\t\t\t{\n\t\t\t\t\treturn rewards.getTransitionReward(s, j);\n\t\t\t\t}\n\t\t\t};\n\t\t}\n\t}\n\n\t/**\n\t * Get all transition rewards from a {@link Rewards} object, as an iterator,\n\t * encoded into primitive types (see {@link #valuesToPrimitives(Iterator)}).\n\t * @param rewards The rewards\n\t */\n\tdefault <E> Iterator<?> getTransitionRewardsAsPrimitives(Rewards<E> rewards)\n\t{\n\t\treturn valuesToPrimitives(getTransitionRewards(rewards));\n\t}\n\n\t// Utility methods\n\n\t/**\n\t * Convert (continuous numerical) values, supplied via an iterator,\n\t * to an encoding into primitive types, also as an iterator.\n\t * Double values are returned as-is, while BigRational values are unpacked into pairs of longs\n\t * @param values The values to encode\n\t */\n\tdefault Iterator<?> valuesToPrimitives(Iterator<?> values)\n\t{\n\t\tif (getEvaluator().exact()) {\n\t\t\treturn new ModelAccessIterators.UnpackBigRationals((Iterator<BigRational>) values);\n\t\t} else {\n\t\t\treturn DoubleIterators.asDoubleIterator(values);\n\t\t}\n\t}\n\n\t/**\n\t * Decode (continuous numerical) values, supplied via a consumer,\n\t * from an encoding into primitive types, and pass to a Value consumer.\n\t * Double values are passed as-is, while BigRational values are converted to pairs of longs\n\t * @param eval Evaluator for the values\n\t * @param valueConsumer The consumer for the values to encode\n\t */\n\tstatic <Value> Consumer<?> primitivesToValues(Evaluator<Value> eval, Consumer<Value> valueConsumer)\n\t{\n\t\tif (eval.exact()) {\n\t\t\tConsumer<BigRational> consumerBigRationals = (Consumer<BigRational>) valueConsumer;\n\t\t\treturn new ModelAccessIterators.PackBigRationals(consumerBigRationals);\n\t\t} else {\n\t\t\treturn valueConsumer;\n\t\t}\n\t}\n\n\t// Utility classes\n\n\t/**\n\t * Helper class to create a list of Values, decoded from their\n\t * encoding into primitives (see {@link #valuesToPrimitives(Iterator)}).\n\t */\n\tclass ValueListFromPrimitives<Value>\n\t{\n\t\tList<Value> valueList;\n\t\tConsumer<?> primitiveConsumer;\n\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tValueListFromPrimitives(Evaluator<Value> eval, int size)\n\t\t{\n\t\t\tif (eval.exact()) {\n\t\t\t\t//LongList valueListLongs = new LongArrayList(numTransitions);\n\t\t\t\tList<BigRational> valueListBigRationals = new ArrayList<>(size);\n\t\t\t\tvalueList = (List<Value>) valueListBigRationals;\n\t\t\t\tprimitiveConsumer = new ModelAccessIterators.PackBigRationals(valueListBigRationals::add);\n\t\t\t} else {\n\t\t\t\tDoubleList valueListDoubles = new DoubleArrayList(size);\n\t\t\t\tvalueList = (List<Value>) valueListDoubles;\n\t\t\t\tprimitiveConsumer = (it.unimi.dsi.fastutil.doubles.DoubleConsumer) valueListDoubles::add;\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/ModelAccessIterators.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport common.Interval;\nimport it.unimi.dsi.fastutil.longs.LongConsumer;\nimport param.BigRational;\n\nimport java.util.Iterator;\nimport java.util.Map;\nimport java.util.NoSuchElementException;\nimport java.util.PrimitiveIterator;\nimport java.util.function.Consumer;\n\npublic class ModelAccessIterators\n{\n\t// Iterators over states\n\n\t/**\n\t * An iterator over values of type {@code E} for each state of a {@link ModelAccess<Value>}.\n\t */\n\tpublic abstract static class GetStateValues<Value, E> implements Iterator<E>\n\t{\n\t\tfinal ModelAccess<Value> model;\n\t\tfinal int numStates;\n\t\tint s; // current state: s<numStates or hasNext = false\n\t\tboolean hasNext;\n\t\tint numChoices;\n\t\tE value;\n\n\t\tGetStateValues(ModelAccess<Value> model)\n\t\t{\n\t\t\tthis.model = model;\n\t\t\tnumStates = model.getNumStates();\n\t\t\thasNext = numStates > 0;\n\t\t}\n\n\t\t/**\n\t\t * Increment iterator counters\n\t\t */\n\t\tprotected void incr()\n\t\t{\n\t\t\ts++;\n\t\t\tif (s >= numStates) {\n\t\t\t\thasNext = false;\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Get the value for the current state.\n\t\t */\n\t\tprotected abstract E getValue();\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn hasNext;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\tif (!hasNext) {\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\t}\n\t\t\tvalue = getValue();\n\t\t\tincr();\n\t\t\treturn value;\n\t\t}\n\t}\n\n\t/**\n\t * An iterator over integer values for each state of a {@link ModelAccess<Value>}.\n\t */\n\tpublic abstract static class GetStateIntValues<Value> extends GetStateValues<Value,Integer> implements PrimitiveIterator.OfInt\n\t{\n\t\tint intValue;\n\n\t\tGetStateIntValues(ModelAccess<Value> model)\n\t\t{\n\t\t\tsuper(model);\n\t\t}\n\n\t\t/**\n\t\t * Get the integer value for the current state.\n\t\t */\n\t\tprotected abstract int getIntValue();\n\n\t\t@Override\n\t\tpublic Integer getValue()\n\t\t{\n\t\t\treturn getIntValue();\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tif (!hasNext) {\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\t}\n\t\t\tintValue = getIntValue();\n\t\t\tincr();\n\t\t\treturn intValue;\n\t\t}\n\t}\n\n\t/**\n\t * An iterator over the choice counts for each state of a {@link ModelAccess<Value>}.\n\t */\n\tpublic static class GetStateChoiceCounts<Value> extends ModelAccessIterators.GetStateIntValues<Value>\n\t{\n\t\tGetStateChoiceCounts(ModelAccess<Value> model)\n\t\t{\n\t\t\tsuper(model);\n\t\t}\n\n\t\t@Override\n\t\tpublic int getIntValue()\n\t\t{\n\t\t\treturn model.getNumChoices(s);\n\t\t}\n\t}\n\n\t/**\n\t * An iterator over the transition counts for each state of a {@link ModelAccess<Value>}.\n\t * Deals with empty (no choice) states.\n\t */\n\tpublic static class GetStateTransitionCounts<Value> extends ModelAccessIterators.GetStateIntValues<Value>\n\t{\n\t\tGetStateTransitionCounts(ModelAccess<Value> model)\n\t\t{\n\t\t\tsuper(model);\n\t\t}\n\n\t\t@Override\n\t\tpublic int getIntValue()\n\t\t{\n\t\t\treturn model.getNumTransitions(s);\n\t\t}\n\t}\n\n\t// Iterators over choices\n\n\t/**\n\t * An iterator over values of type {@code E} for each choice of a {@link ModelAccess<Value>}.\n\t * Deals with empty (no choice) states.\n\t */\n\tpublic abstract static class GetChoiceValues<Value, E> implements Iterator<E>\n\t{\n\t\tfinal ModelAccess<Value> model;\n\t\tfinal int numStates;\n\t\tint s; // current state: s<numStates or hasNext = false\n\t\tint numChoices; // num choices in state s (0 if s==numStates)\n\t\tint i; // current choice: i<numChoices or i==0==numChoices\n\t\tboolean hasNext;\n\t\tE value;\n\n\t\tGetChoiceValues(ModelAccess<Value> model)\n\t\t{\n\t\t\tthis.model = model;\n\t\t\tnumStates = model.getNumStates();\n\t\t\tnumChoices = numStates > 0 ? model.getNumChoices(0) : 0;\n\t\t\thasNext = numStates > 0;\n\t\t\tskipEmpty();\n\t\t}\n\n\t\t/**\n\t\t * Advance to the next available choice, skipping empty states.\n\t\t * After this, either {@code (s,i)} is the next available choice,\n\t\t * or there are no more and {@code hasNext} is false.\n\t\t */\n\t\tprotected void skipEmpty()\n\t\t{\n\t\t\twhile (hasNext) {\n\t\t\t\tif (s < numStates && numChoices > 0) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tincr();\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Increment iterator counters\n\t\t */\n\t\tprotected void incr()\n\t\t{\n\t\t\ti++;\n\t\t\tif (i >= numChoices) {\n\t\t\t\ts++;\n\t\t\t\tif (s >= numStates) {\n\t\t\t\t\thasNext = false;\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tnumChoices = model.getNumChoices(s);\n\t\t\t\ti = 0;\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Get the value for the current choice.\n\t\t */\n\t\tprotected abstract E getValue();\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn hasNext;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\tif (!hasNext) {\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\t}\n\t\t\tvalue = getValue();\n\t\t\tincr();\n\t\t\tskipEmpty();\n\t\t\treturn value;\n\t\t}\n\t}\n\n\t/**\n\t * An iterator over integer values for each choice of a {@link ModelAccess<Value>}.\n\t */\n\tpublic abstract static class GetChoiceIntValues<Value> extends GetChoiceValues<Value,Integer> implements PrimitiveIterator.OfInt\n\t{\n\t\tint intValue;\n\n\t\tGetChoiceIntValues(ModelAccess<Value> model)\n\t\t{\n\t\t\tsuper(model);\n\t\t}\n\n\t\t/**\n\t\t * Get the integer value for the current state.\n\t\t */\n\t\tprotected abstract int getIntValue();\n\n\t\t@Override\n\t\tpublic Integer getValue()\n\t\t{\n\t\t\treturn getIntValue();\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tif (!hasNext) {\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\t}\n\t\t\tintValue = getIntValue();\n\t\t\tincr();\n\t\t\treturn intValue;\n\t\t}\n\t}\n\n\t/**\n\t * An iterator over the transition counts for each choice of a {@link ModelAccess<Value>}.\n\t * Deals with empty (no choice) states.\n\t */\n\tpublic static class GetChoiceTransitionCounts<Value> extends ModelAccessIterators.GetChoiceIntValues<Value>\n\t{\n\t\tGetChoiceTransitionCounts(ModelAccess<Value> model)\n\t\t{\n\t\t\tsuper(model);\n\t\t}\n\n\t\t@Override\n\t\tpublic int getIntValue()\n\t\t{\n\t\t\treturn model.getNumTransitions(s, i);\n\t\t}\n\t}\n\n\t// Iterators over transitions\n\n\t/**\n\t * An iterator over values associated to each transition of a {@link ModelAccess<Value>}.\n\t * Deals with empty (no choice) states amd empty (no transition) choices.\n\t */\n\tpublic abstract static class GetTransitionValues<Value,E> implements Iterator<E>\n\t{\n\t\tfinal ModelAccess<Value> model;\n\t\tfinal boolean storeActions;\n\t\tfinal int numStates;\n\t\tint s; // current state: s<numStates or hasNext = false\n\t\tint numChoices; // num choices in state s (0 if s==numStates)\n\t\tint i; // current choice: i<numChoices or i==0==numChoices\n\t\tIterator<Map.Entry<Integer, Value>> itTransitions; // transitions iterator (null if numChoices==0)\n\t\tPrimitiveIterator.OfInt itActionIndices; // (optional) transition action indices iterator (null if numChoices==0)\n\t\tint j; // current transition index\n\t\tMap.Entry<Integer, Value> transition; // current transition\n\t\tint actionIndex; // (optional) current transition action index\n\t\tboolean hasNext;\n\t\tE value;\n\n\t\tGetTransitionValues(ModelAccess<Value> model)\n\t\t{\n\t\t\tthis(model, false);\n\t\t}\n\n\t\tGetTransitionValues(ModelAccess<Value> model, boolean storeActions)\n\t\t{\n\t\t\tthis.model = model;\n\t\t\tthis.storeActions = storeActions;\n\t\t\tnumStates = model.getNumStates();\n\t\t\tnumChoices = numStates > 0 ? model.getNumChoices(0) : 0;\n\t\t\titTransitions = numChoices > 0 ? model.getTransitionsIterator(s, i) : null;\n\t\t\tif (storeActions) {\n\t\t\t\titActionIndices = numChoices > 0 ? model.getTransitionActionIndicesIterator(s, i) : null;\n\t\t\t}\n\t\t\thasNext = numStates > 0;\n\t\t\tskipEmpty();\n\t\t}\n\n\t\t/**\n\t\t * Advance to the next available transition, skipping empty states/choices.\n\t\t * After this, either {@code itTransitions.next()} gives the next transition,\n\t\t * or there are no more and {@code hasNext} is false.\n\t\t */\n\t\tprotected void skipEmpty()\n\t\t{\n\t\t\twhile (hasNext) {\n\t\t\t\tif (s < numStates && numChoices > 0 && itTransitions.hasNext()) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tincr();\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Increment iterator counters\n\t\t */\n\t\tprotected void incr()\n\t\t{\n\t\t\ti++;\n\t\t\tif (i >= numChoices) {\n\t\t\t\ts++;\n\t\t\t\tif (s >= numStates) {\n\t\t\t\t\thasNext = false;\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tnumChoices = model.getNumChoices(s);\n\t\t\t\ti = 0;\n\t\t\t}\n\t\t\titTransitions = numChoices > 0 ? model.getTransitionsIterator(s, i) : null;\n\t\t\tif (storeActions) {\n\t\t\t\titActionIndices = numChoices > 0 ? model.getTransitionActionIndicesIterator(s, i) : null;\n\t\t\t}\n\t\t\tj = 0;\n\t\t}\n\n\t\t/**\n\t\t * Get the value for the current transition.\n\t\t */\n\t\tprotected abstract E getValue();\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn hasNext;\n\t\t}\n\n\t\t@Override\n\t\tpublic E next()\n\t\t{\n\t\t\tif (!hasNext) {\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\t}\n\t\t\t// Store value for transition and move on to the next one\n\t\t\ttransition = itTransitions.next();\n\t\t\tif (storeActions) {\n\t\t\t\tactionIndex = itActionIndices.next();\n\t\t\t}\n\t\t\tvalue = getValue();\n\t\t\tif (!itTransitions.hasNext()) {\n\t\t\t\tincr();\n\t\t\t\tskipEmpty();\n\t\t\t} else {\n\t\t\t\tj++;\n\t\t\t}\n\t\t\treturn value;\n\t\t}\n\t}\n\n\t/**\n\t * An iterator over integer values for each transition of a {@link ModelAccess<Value>}.\n\t */\n\tpublic abstract static class GetTransitionIntValues<Value> extends GetTransitionValues<Value,Integer> implements PrimitiveIterator.OfInt\n\t{\n\t\tint intValue;\n\n\t\tGetTransitionIntValues(ModelAccess<Value> model)\n\t\t{\n\t\t\tsuper(model);\n\t\t}\n\n\t\tGetTransitionIntValues(ModelAccess<Value> model, boolean storeActions)\n\t\t{\n\t\t\tsuper(model, storeActions);\n\t\t}\n\n\t\t/**\n\t\t * Get the integer value for the current state.\n\t\t */\n\t\tprotected abstract int getIntValue();\n\n\t\t@Override\n\t\tpublic Integer getValue()\n\t\t{\n\t\t\treturn getIntValue();\n\t\t}\n\n\t\t@Override\n\t\tpublic int nextInt()\n\t\t{\n\t\t\tif (!hasNext) {\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\t}\n\t\t\t// Store value for transition and move on to the next one\n\t\t\ttransition = itTransitions.next();\n\t\t\tif (storeActions) {\n\t\t\t\tactionIndex = itActionIndices.next();\n\t\t\t}\n\t\t\tintValue = getIntValue();\n\t\t\tif (!itTransitions.hasNext()) {\n\t\t\t\tincr();\n\t\t\t\tskipEmpty();\n\t\t\t}\n\t\t\treturn intValue;\n\t\t}\n\t}\n\n\t/**\n\t * Class to unpack intervals of values, supplied as an iterator, and return\n\t * as an iterator over all values, i.e., both the lower and upper bounds.\n\t */\n\tpublic static class UnpackIntervals<V> implements Iterator<V>\n\t{\n\t\tIterator<Interval<V>> iter;\n\t\tInterval<V> next;\n\t\tboolean first = true;\n\n\t\tpublic UnpackIntervals(Iterator<Interval<V>> iter)\n\t\t{\n\t\t\tthis.iter = iter;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn !first || iter.hasNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic V next()\n\t\t{\n\t\t\tif (first) {\n\t\t\t\tnext = iter.next();\n\t\t\t\tfirst = false;\n\t\t\t\treturn next.getLower();\n\t\t\t} else {\n\t\t\t\tfirst = true;\n\t\t\t\treturn next.getUpper();\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Class to unpack big rationals, supplied as an iterator, and return\n\t * as an iterator over longs, i.e., both the numerator and denominator.\n\t */\n\tpublic static class UnpackBigRationals implements PrimitiveIterator.OfLong\n\t{\n\t\tIterator<BigRational> iter;\n\t\tBigRational next;\n\t\tboolean first = true;\n\n\t\tpublic UnpackBigRationals(Iterator<BigRational> iter)\n\t\t{\n\t\t\tthis.iter = iter;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn !first || iter.hasNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\tif (first) {\n\t\t\t\tnext = iter.next();\n\t\t\t\tfirst = false;\n\t\t\t\treturn next.getNum().longValueExact();\n\t\t\t} else {\n\t\t\t\tfirst = true;\n\t\t\t\treturn next.getDen().longValueExact();\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Class to provide a list of big rationals, provided as a list of longs\n\t * representing the numerators and denominators, successively.\n\t */\n\tpublic static class PackBigRationals implements LongConsumer\n\t{\n\t\tConsumer<BigRational> cons;\n\t\tlong num;\n\t\tboolean first = true;\n\n\t\tpublic PackBigRationals(Consumer<BigRational> cons)\n\t\t{\n\t\t\tthis.cons = cons;\n\t\t}\n\n\t\t@Override\n\t\tpublic void accept(long value)\n\t\t{\n\t\t\tif (first) {\n\t\t\t\tnum = value;\n\t\t\t\tfirst = false;\n\t\t\t} else {\n\t\t\t\tfirst = true;\n\t\t\t\tcons.accept(new BigRational(num, value));\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/ModelExportFormat.java",
    "content": "package io;\n\n/**\n * Model export formats\n */\npublic enum ModelExportFormat\n{\n\tEXPLICIT, MATLAB, DOT, DD_DOT, DRN, UMB;\n\n\tpublic String description()\n\t{\n\t\tswitch (this) {\n\t\t\tcase EXPLICIT:\n\t\t\t\treturn \"in plain text format\";\n\t\t\tcase MATLAB:\n\t\t\t\treturn \"in Matlab format\";\n\t\t\tcase DOT:\n\t\t\t\treturn \"in Dot format\";\n\t\t\tcase DD_DOT:\n\t\t\t\treturn \"in DD Dot format\";\n\t\t\tcase DRN:\n\t\t\t\treturn \"in DRN format\";\n\t\t\tcase UMB:\n\t\t\t\treturn \"in UMB format\";\n\t\t\tdefault:\n\t\t\t\treturn this.toString();\n\t\t}\n\t}\n\n\tpublic boolean isBinary()\n\t{\n\t\treturn this == UMB;\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/ModelExportOptions.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport io.github.pmctools.umbj.UMBFormat;\n\nimport java.util.Optional;\n\nimport static prism.PrismSettings.DEFAULT_EXPORT_MODEL_PRECISION;\n\n/**\n * Class to represent options for exporting models.\n */\npublic class ModelExportOptions implements Cloneable\n{\n\t/** File compression formats */\n\tpublic enum CompressionFormat {\n\t\tGZIP,\n\t\tXZ;\n\t\tpublic String extension()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase GZIP: return \"gz\";\n\t\t\t\tcase XZ: return \"xz\";\n\t\t\t\tdefault: throw new IllegalStateException(\"Unknown compression format: \" + this);\n\t\t\t}\n\t\t}\n\n\t\tpublic static CompressionFormat fromUMB(UMBFormat.CompressionFormat compressionFormat)\n\t\t{\n\t\t\tswitch (compressionFormat) {\n\t\t\t\tcase GZIP: return GZIP;\n\t\t\t\tcase XZ: return XZ;\n\t\t\t\tdefault: throw new IllegalStateException(\"Unknown compression format: \" + compressionFormat);\n\t\t\t}\n\t\t}\n\n\t\tpublic UMBFormat.CompressionFormat toUMB()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase GZIP: return UMBFormat.CompressionFormat.GZIP;\n\t\t\t\tcase XZ: return UMBFormat.CompressionFormat.XZ;\n\t\t\t\tdefault: throw new IllegalStateException(\"Unknown compression format: \" + this);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Model export format\n\t */\n\tprivate Optional<ModelExportFormat> format = Optional.empty();\n\n\t/**\n\t * Precision to export probabilities/etc. (number of significant decimal places)\n\t */\n\tprivate Optional<Integer> modelPrecision = Optional.empty();\n\n\t/**\n\t * Whether to show labels\n\t */\n\tprivate Optional<Boolean> showLabels = Optional.empty();\n\n\t/**\n\t * Whether to show rewards\n\t */\n\tprivate Optional<Boolean> showRewards = Optional.empty();\n\n\t/**\n\t * Whether to show full state details\n\t */\n\tprivate Optional<Boolean> showStates = Optional.empty();\n\n\t/**\n\t * Whether to show full observation details\n\t */\n\tprivate Optional<Boolean> showObservations = Optional.empty();\n\n\t/**\n\t * Whether to show actions\n\t */\n\tprivate Optional<Boolean> showActions = Optional.empty();\n\n\t/**\n\t * Whether to print (optional, commented) headers\n\t */\n\tprivate Optional<Boolean> printHeaders = Optional.empty();\n\n\t/**\n\t * Whether to show transitions in rows in explicit format\n\t */\n\tprivate Optional<Boolean> explicitRows = Optional.empty();\n\n\t/**\n\t * For binary formats, whether to show in textual form\n\t */\n\tprivate Optional<Boolean> binaryAsText = Optional.empty();\n\n\t/**\n\t * For formats that support it, whether to zip\n\t */\n\tprivate Optional<Boolean> zipped = Optional.empty();\n\n\t/**\n\t * Compression format to use (if zipping)\n\t */\n\tprivate Optional<CompressionFormat> zipFormat = Optional.empty();\n\n\t// Constructors\n\n\t/**\n\t * Construct a StrategyExportOptions with default options.\n\t */\n\tpublic ModelExportOptions()\n\t{\n\t}\n\n\t/**\n\t * Construct a StrategyExportOptions with specified format and default options.\n\t */\n\tpublic ModelExportOptions(ModelExportFormat format)\n\t{\n\t\tsetFormat(format);\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic ModelExportOptions(ModelExportOptions exportOptions)\n\t{\n\t\tapply(exportOptions);\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Set the model export format.\n\t */\n\tpublic ModelExportOptions setFormat(ModelExportFormat format)\n\t{\n\t\tthis.format = Optional.of(format);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set precision to export probabilities/etc. (number of significant decimal places).\n\t */\n\tpublic ModelExportOptions setModelPrecision(int modelPrecision)\n\t{\n\t\tthis.modelPrecision = Optional.of(modelPrecision);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to show labels\n\t */\n\tpublic ModelExportOptions setShowLabels(boolean showLabels)\n\t{\n\t\tthis.showLabels = Optional.of(showLabels);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to show rewards\n\t */\n\tpublic ModelExportOptions setShowRewards(boolean showRewards)\n\t{\n\t\tthis.showRewards = Optional.of(showRewards);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to show full state details.\n\t */\n\tpublic ModelExportOptions setShowStates(boolean showStates)\n\t{\n\t\tthis.showStates = Optional.of(showStates);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to show full observation details.\n\t */\n\tpublic ModelExportOptions setShowObservations(boolean showObservations)\n\t{\n\t\tthis.showObservations = Optional.of(showObservations);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to show actions.\n\t */\n\tpublic ModelExportOptions setShowActions(boolean showActions)\n\t{\n\t\tthis.showActions = Optional.of(showActions);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to print (optional, commented) headers.\n\t */\n\tpublic ModelExportOptions setPrintHeaders(boolean printHeaders)\n\t{\n\t\tthis.printHeaders = Optional.of(printHeaders);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to show transitions in rows in explicit format\n\t */\n\tpublic ModelExportOptions setExplicitRows(boolean explicitRows)\n\t{\n\t\tthis.explicitRows = Optional.of(explicitRows);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to show binary formats in textual form\n\t */\n\tpublic ModelExportOptions setBinaryAsText(boolean binaryAsText)\n\t{\n\t\tthis.binaryAsText = Optional.of(binaryAsText);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to zip the output file (for formats that support it)\n\t */\n\tpublic ModelExportOptions setZipped(boolean zipped)\n\t{\n\t\tthis.zipped = Optional.of(zipped);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set compression format to use (if zipping)\n\t */\n\tpublic ModelExportOptions setCompressionFormat(CompressionFormat compressionFormat)\n\t{\n\t\tthis.zipFormat = Optional.of(compressionFormat);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Apply any options that have been set in another {@link ModelExportOptions} to this one.\n\t */\n\tpublic void apply(ModelExportOptions other)\n\t{\n\t\tif (other.format.isPresent()) {\n\t\t\tsetFormat(other.getFormat());\n\t\t}\n\t\tif (other.modelPrecision.isPresent()) {\n\t\t\tsetModelPrecision(other.getModelPrecision());\n\t\t}\n\t\tif (other.showLabels.isPresent()) {\n\t\t\tsetShowLabels(other.getShowLabels());\n\t\t}\n\t\tif (other.showRewards.isPresent()) {\n\t\t\tsetShowRewards(other.getShowRewards());\n\t\t}\n\t\tif (other.showStates.isPresent()) {\n\t\t\tsetShowStates(other.getShowStates());\n\t\t}\n\t\tif (other.showObservations.isPresent()) {\n\t\t\tsetShowObservations(other.getShowObservations());\n\t\t}\n\t\tif (other.showActions.isPresent()) {\n\t\t\tsetShowActions(other.getShowActions());\n\t\t}\n\t\tif (other.printHeaders.isPresent()) {\n\t\t\tsetPrintHeaders(other.getPrintHeaders());\n\t\t}\n\t\tif (other.explicitRows.isPresent()) {\n\t\t\tsetExplicitRows(other.getExplicitRows());\n\t\t}\n\t\tif (other.binaryAsText.isPresent()) {\n\t\t\tsetBinaryAsText(other.getBinaryAsText());\n\t\t}\n\t\tif (other.zipped.isPresent()) {\n\t\t\tsetZipped(other.getZipped());\n\t\t}\n\t\tif (other.zipFormat.isPresent()) {\n\t\t\tsetCompressionFormat(other.getCompressionFormat());\n\t\t}\n\t}\n\n\t/**\n\t * Apply any options set here on top of those set in another {@link ModelExportOptions}.\n\t * The resulting (fresh) {@link ModelExportOptions} is returned.\n\t */\n\tpublic ModelExportOptions applyTo(ModelExportOptions other)\n\t{\n\t\tModelExportOptions optionsNew = other.clone();\n\t\toptionsNew.apply(this);\n\t\treturn optionsNew;\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the model export format.\n\t */\n\tpublic ModelExportFormat getFormat()\n\t{\n\t\treturn format.orElse(ModelExportFormat.EXPLICIT);\n\t}\n\n\t/**\n\t * Precision to export probabilities/etc. (number of significant decimal places).\n\t */\n\tpublic int getModelPrecision()\n\t{\n\t\treturn modelPrecision.orElse(DEFAULT_EXPORT_MODEL_PRECISION);\n\t}\n\n\t/**\n\t * Whether to show labels.\n\t */\n\tpublic boolean getShowLabels()\n\t{\n\t\treturn showLabels.orElse(true);\n\t}\n\n\t/**\n\t * Whether to show rewards.\n\t */\n\tpublic boolean getShowRewards()\n\t{\n\t\treturn showRewards.orElse(true);\n\t}\n\n\t/**\n\t * Whether to show full state details.\n\t */\n\tpublic boolean getShowStates()\n\t{\n\t\treturn showStates.orElse(true);\n\t}\n\n\t/**\n\t * Whether to show full observation details.\n\t */\n\tpublic boolean getShowObservations()\n\t{\n\t\treturn showObservations.orElse(true);\n\t}\n\n\t/**\n\t * Whether to show actions.\n\t */\n\tpublic boolean getShowActions()\n\t{\n\t\treturn showActions.orElse(true);\n\t}\n\n\t/**\n\t * Whether to show actions.\n\t * If has not been set, returned {@code orElse} as a default.\n\t */\n\tpublic boolean getShowActions(boolean orElse)\n\t{\n\t\treturn showActions.orElse(orElse);\n\t}\n\n\t/**\n\t * Whether to print (optional, commented) headers.\n\t */\n\tpublic boolean getPrintHeaders()\n\t{\n\t\treturn printHeaders.orElse(true);\n\t}\n\n\t/**\n\t * Whether to show transitions in rows in explicit format\n\t */\n\tpublic boolean getExplicitRows()\n\t{\n\t\treturn explicitRows.orElse(false);\n\t}\n\n\t/**\n\t * Whether to show binary formats in textual form.\n\t */\n\tpublic boolean getBinaryAsText()\n\t{\n\t\treturn binaryAsText.orElse(false);\n\t}\n\n\t/**\n\t * Whether to zip the output file (for formats that support it)\n\t */\n\tpublic boolean getZipped()\n\t{\n\t\t// Only UMB defaults to zipped\n\t\treturn zipped.orElse(getFormat() == ModelExportFormat.UMB);\n\t}\n\n\t/**\n\t * Compression format to use (if zipping)\n\t */\n\tpublic CompressionFormat getCompressionFormat()\n\t{\n\t\treturn getCompressionFormat(CompressionFormat.GZIP);\n\t}\n\n\t/**\n\t * Compression format to use (if zipping)\n\t * @param orElse Default to use if has not been specified\n\t */\n\tpublic CompressionFormat getCompressionFormat(CompressionFormat orElse)\n\t{\n\t\treturn zipFormat.orElse(CompressionFormat.GZIP);\n\t}\n\n\t/**\n\t * Perform a shallow copy of the options.\n\t */\n\t@Override\n\tpublic ModelExportOptions clone()\n\t{\n\t\ttry {\n\t\t\treturn (ModelExportOptions) super.clone();\n\t\t} catch (CloneNotSupportedException e) {\n\t\t\tthrow new InternalError(\"Object#clone is expected to work for Cloneable objects\", e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/ModelExportTask.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport parser.ast.PropertiesFile;\nimport prism.ModelInfo;\nimport prism.PrismException;\n\nimport java.io.File;\n\n/**\n * Class to represent a task related to exporting models.\n */\npublic class ModelExportTask\n{\n\t/**\n\t * Model export entities\n\t */\n\tpublic enum ModelExportEntity {\n\t\tMODEL, // Core part of the model (transition function/matrix)\n\t\tSTATE_REWARDS, // State rewards\n\t\tTRANSITION_REWARDS, // Transition rewards\n\t\tSTATES, // State definitions (variable values)\n\t\tOBSERVATIONS, // Observation definitions (observable values)\n\t\tLABELS; // Labels (atomic propositions)\n\t\tpublic String description()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase MODEL:\n\t\t\t\t\treturn \"model\";\n\t\t\t\tcase STATE_REWARDS:\n\t\t\t\t\treturn \"state rewards\";\n\t\t\t\tcase TRANSITION_REWARDS:\n\t\t\t\t\treturn \"transition rewards\";\n\t\t\t\tcase STATES:\n\t\t\t\t\treturn \"reachable states\";\n\t\t\t\tcase OBSERVATIONS:\n\t\t\t\t\treturn \"observations\";\n\t\t\t\tcase LABELS:\n\t\t\t\t\treturn \"labels and satisfying states\";\n\t\t\t\tdefault:\n\t\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Model export entity (what to export)\n\t */\n\tprivate ModelExportEntity entity;\n\n\t/**\n\t * File to export to (null means stdout)\n\t */\n\tprivate File file;\n\n\t/**\n\t * Model export options\n\t */\n\tprivate ModelExportOptions exportOptions;\n\n\t/**\n\t * Which labels to export\n\t */\n\tpublic enum LabelExportSet {\n\t\tMODEL, // Just those in the model\n\t\tEXTRA, // Just those in the \"extra\" source of labels\n\t\tALL // All (model and extra)\n\t}\n\n\t/**\n\t * When exporting labels, which ones to include\n\t */\n\tprivate LabelExportSet labelExportSet = LabelExportSet.MODEL;\n\n\t/**\n\t * Optionally, a source of extra labels for label export\n\t */\n\tprivate PropertiesFile extraLabelsSource;\n\n\t// Constructors\n\n\t/**\n\t * Construct a ModelExportTask with default options.\n\t * @param entity What to export\n\t * @param file File to export to (null means stdout)\n\t */\n\tpublic ModelExportTask(ModelExportEntity entity, File file)\n\t{\n\t\tthis(entity, file, new ModelExportOptions());\n\t}\n\n\t/**\n\t * Construct a ModelExportTask with specified options.\n\t * @param entity What to export\n\t * @param file File to export to (null means stdout)\n\t * @param exportOptions The options for export\n\t */\n\tpublic ModelExportTask(ModelExportEntity entity, File file, ModelExportOptions exportOptions)\n\t{\n\t\tthis.entity = entity;\n\t\tthis.file = file;\n\t\tthis.exportOptions = exportOptions;\n\t}\n\n\t/**\n\t * Construct a ModelExportTask with specified options.\n\t * @param entity What to export\n\t * @param filename Name of file to export to (can be \"stdout\")\n\t */\n\tpublic ModelExportTask(ModelExportEntity entity, String filename)\n\t{\n\t\tthis(entity, filename, new ModelExportOptions());\n\t}\n\n\t/**\n\t * Construct a ModelExportTask with specified options.\n\t * @param entity What to export\n\t * @param filename Name of file to export to (can be \"stdout\")\n\t * @param exportOptions The options for export\n\t */\n\tpublic ModelExportTask(ModelExportEntity entity, String filename, ModelExportOptions exportOptions)\n\t{\n\t\tthis.entity = entity;\n\t\tthis.file = \"stdout\".equals(filename) ? null : new File(filename);\n\t\tthis.exportOptions = exportOptions;\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic ModelExportTask(ModelExportTask exportTask)\n\t{\n\t\tthis(exportTask, new ModelExportOptions(exportTask.exportOptions));\n\t}\n\n\t/**\n\t * Copy constructor, but with a specified ModelExportOptions.\n\t */\n\tpublic ModelExportTask(ModelExportTask exportTask, ModelExportOptions exportOptions)\n\t{\n\t\tthis.entity = exportTask.entity;\n\t\tthis.file = exportTask.file;\n\t\tthis.exportOptions = exportOptions;\n\t\tthis.labelExportSet = exportTask.labelExportSet;\n\t\tthis.extraLabelsSource = exportTask.extraLabelsSource;\n\t}\n\n\t/**\n\t * Create a ModelExportTask based on a filename, supplied as separate basename and extension.\n\t * The basename can also be \"stdout\". It can also be left empty (\"\") and later replaced\n\t * (e.g. with the model basename) using {@link #replaceEmptyFileBasename(String)}.\n\t * An unknown (or missing) extension is treated as \".tra\".\n\t */\n\tpublic static ModelExportTask fromFilename(String basename, String ext) throws PrismException\n\t{\n\t\tif (ext == null || ext.equals(\"\")) {\n\t\t\treturn new ModelExportTask(ModelExportEntity.MODEL, basename);\n\t\t}\n\t\tString filename = \"stdout\".equals(basename) ? \"stdout\" : basename + \".\" + ext;\n\t\tswitch (ext) {\n\t\t\tcase \"tra\":\n\t\t\t\treturn new ModelExportTask(ModelExportEntity.MODEL, filename);\n\t\t\tcase \"srew\":\n\t\t\t\treturn new ModelExportTask(ModelExportEntity.STATE_REWARDS, filename);\n\t\t\tcase \"trew\":\n\t\t\t\treturn new ModelExportTask(ModelExportEntity.TRANSITION_REWARDS, filename);\n\t\t\tcase \"sta\":\n\t\t\t\treturn new ModelExportTask(ModelExportEntity.STATES, filename);\n\t\t\tcase \"obs\":\n\t\t\t\treturn new ModelExportTask(ModelExportEntity.OBSERVATIONS, filename);\n\t\t\tcase \"lab\":\n\t\t\t\treturn new ModelExportTask(ModelExportEntity.LABELS, filename);\n\t\t\tcase \"dot\":\n\t\t\t\treturn fromFormat(filename, ModelExportFormat.DOT);\n\t\t\tcase \"drn\":\n\t\t\t\treturn fromFormat(filename, ModelExportFormat.DRN);\n\t\t\tcase \"m\":\n\t\t\t\treturn fromFormat(filename, ModelExportFormat.MATLAB);\n\t\t\tcase \"umb\":\n\t\t\t\treturn fromFormat(filename, ModelExportFormat.UMB);\n\t\t\tcase \"umbt\":\n\t\t\t\treturn fromOptions(filename, new ModelExportOptions(ModelExportFormat.UMB).setBinaryAsText(true));\n\t\t\tdefault:\n\t\t\t\t// Treat unknown extensions as .tra\n\t\t\t\treturn new ModelExportTask(ModelExportEntity.MODEL, filename);\n\t\t}\n\t}\n\n\t/**\n\t * Create a ModelExportTask to export a model to a file in the specified format.\n\t * @param filename Name of file to export to (can be \"stdout\")\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic static ModelExportTask fromFormat(String filename, ModelExportFormat exportFormat) throws PrismException\n\t{\n\t\tFile file = \"stdout\".equals(filename) ? null : new File(filename);\n\t\treturn fromOptions(file, new ModelExportOptions(exportFormat));\n\t}\n\n\t/**\n\t * Create a ModelExportTask to export a model to a file in the specified format.\n\t * @param file File to export to (null means stdout)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic static ModelExportTask fromFormat(File file, ModelExportFormat exportFormat) throws PrismException\n\t{\n\t\treturn fromOptions(file, new ModelExportOptions(exportFormat));\n\t}\n\n\t/**\n\t * Create a ModelExportTask to export a model to a file,\n\t * using the supplied export options (which includes the format).\n\t * @param filename Name of file to export to (can be \"stdout\")\n\t * @param exportOptions The options for export\n\t */\n\tpublic static ModelExportTask fromOptions(String filename, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tFile file = \"stdout\".equals(filename) ? null : new File(filename);\n\t\treturn fromOptions(file, exportOptions);\n\t}\n\n\t/**\n\t * Create a ModelExportTask to export a model to a file,\n\t * using the supplied export options (which includes the format).\n\t * @param file File to export to (null means stdout)\n\t * @param exportOptions The options for export\n\t */\n\tpublic static ModelExportTask fromOptions(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tModelExportTask exportTask;\n\t\tswitch (exportOptions.getFormat()) {\n\t\t\tcase EXPLICIT:\n\t\t\tcase MATLAB:\n\t\t\t\texportTask = new ModelExportTask(ModelExportEntity.MODEL, file);\n\t\t\t\tbreak;\n\t\t\tcase DOT:\n\t\t\t\texportTask = new ModelExportTask(ModelExportEntity.MODEL, file);\n\t\t\t\tbreak;\n\t\t\tcase DRN:\n\t\t\t\texportTask = new ModelExportTask(ModelExportEntity.MODEL, file);\n\t\t\t\tbreak;\n\t\t\tcase UMB:\n\t\t\t\texportTask = new ModelExportTask(ModelExportEntity.MODEL, file);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t}\n\t\texportTask.getExportOptions().apply(exportOptions);\n\t\treturn exportTask;\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Set what is to be exported.\n\t * @param entity What to export\n\t */\n\tpublic void setEntity(ModelExportEntity entity)\n\t{\n\t\tthis.entity = entity;\n\t}\n\n\t/**\n\t * Set where to export to.\n\t * @param file File to export to (null means stdout)\n\t */\n\tpublic void setFile(File file)\n\t{\n\t\tthis.file = file;\n\t}\n\n\t/**\n\t * Set the export options.\n\t * @param exportOptions Export options\n\t */\n\tpublic void setExportOptions(ModelExportOptions exportOptions)\n\t{\n\t\tthis.exportOptions = exportOptions;\n\t}\n\n\t/**\n\t * Set, when exporting labels, which ones to export.\n\t * @param labelExportSet Which set of labels to export\n\t */\n\tpublic void setLabelExportSet(LabelExportSet labelExportSet)\n\t{\n\t\tthis.labelExportSet = labelExportSet;\n\t}\n\n\t/**\n\t * Set a source of extra labels\n\t * @param extraLabelsSource Extra labels source\n\t */\n\tpublic void setExtraLabelsSource(PropertiesFile extraLabelsSource)\n\t{\n\t\tthis. extraLabelsSource = extraLabelsSource;\n\t}\n\n\t/**\n\t * If the file to be exported to is of the form \".ext\", plug in the supplied basename,\n\t * i.e., make the new filename \"basename.ext\".\n\t */\n\tpublic void replaceEmptyFileBasename(String basename)\n\t{\n\t\tif (file != null && file.getName().matches(\"\\\\.[a-zA-Z]+\")) {\n\t\t\tfile = new File(basename + file.getName());\n\t\t}\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get what is to be exported.\n\t */\n\tpublic ModelExportEntity getEntity()\n\t{\n\t\treturn entity;\n\t}\n\n\t/**\n\t * Is this export task applicable for a given model?\n\t */\n\tpublic boolean isApplicable(ModelInfo modelInfo)\n\t{\n\t\tif (entity == ModelExportEntity.OBSERVATIONS && !modelInfo.getModelType().partiallyObservable()) {\n\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get where to export to (null means stdout).\n\t */\n\tpublic File getFile()\n\t{\n\t\treturn file;\n\t}\n\n\t/**\n\t * Get the export options.\n\t */\n\tpublic ModelExportOptions getExportOptions()\n\t{\n\t\treturn exportOptions;\n\t}\n\n\t/**\n\t * Get which ones to export when exporting labels.\n\t */\n\tpublic LabelExportSet getLabelExportSet()\n\t{\n\t\treturn labelExportSet;\n\t}\n\n\t/**\n\t * Get an (optional) source of extra labels\n\t */\n\tpublic PropertiesFile getExtraLabelsSource()\n\t{\n\t\treturn extraLabelsSource;\n\t}\n\n\t/**\n\t * Get whether extra labels are used for this export task.\n\t */\n\tpublic boolean extraLabelsUsed()\n\t{\n\t\treturn labelExportSet == LabelExportSet.EXTRA || labelExportSet == LabelExportSet.ALL;\n\t}\n\n\t/**\n\t * Get whether \"init\" should be included with model labels.\n\t */\n\tpublic boolean initLabelIncluded()\n\t{\n\t\treturn getExportOptions().getFormat() != ModelExportFormat.UMB;\n\t}\n\n\t/**\n\t * Get whether \"deadlock\" should be included with model labels.\n\t */\n\tpublic boolean deadlockLabelIncluded()\n\t{\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get a message describing the export task to be done.\n\t */\n\tpublic String getMessage()\n\t{\n\t\tString s = \"Exporting \" + entity.description();\n\t\ts += \" \" + exportOptions.getFormat().description();\n\t\ts += \" \" + getDestinationStringForFile(file);\n\t\treturn s;\n\t}\n\n\t// Utility methods\n\n\t/**\n\t * Get a string describing the output destination specified by a File:\n\t * \"to file \\\"filename\\\"...\" if non-null; \"below:\" if null\n\t */\n\tprivate static String getDestinationStringForFile(File file)\n\t{\n\t\treturn (file == null) ? \"below:\" : \"to file \\\"\" + file + \"\\\"...\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/ModelExporter.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport common.Interval;\nimport explicit.*;\nimport explicit.rewards.Rewards;\nimport prism.Evaluator;\nimport prism.ModelInfo;\nimport prism.Pair;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\n\nimport java.io.File;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.TreeSet;\n\n/**\n * Base class for model exporter classes.\n */\npublic abstract class ModelExporter<Value>\n{\n\t/** Evaluator for model (defaults to one for doubles if not provided). */\n\t@SuppressWarnings(\"unchecked\")\n\tprotected Evaluator<Value> eval = (Evaluator<Value>) Evaluator.forDouble();\n\n\t/** Model export options */\n\tprotected ModelExportOptions modelExportOptions;\n\n\t// Model annotations\n\n\tprotected List<Rewards<Value>> rewards = new ArrayList<>();\n\tprotected List<String> rewardNames = new ArrayList<>();\n\tprotected Evaluator<Value> evalRewards = null;\n\n\tprotected List<BitSet> labels = new ArrayList<>();\n\tprotected List<String> labelNames = new ArrayList<>();\n\n\tprotected ModelInfo modelInfo;\n\n\t/**\n\t * Construct a ModelExporter with default export options.\n\t */\n\tpublic ModelExporter()\n\t{\n\t\tthis(new ModelExportOptions());\n\t}\n\n\t/**\n\t * Construct a ModelExporter with the specified export options.\n\t */\n\tpublic ModelExporter(ModelExportOptions modelExportOptions)\n\t{\n\t\tsetModelExportOptions(modelExportOptions);\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Set the evaluator for dealing with model values.\n\t */\n\tpublic void setEvaluator(Evaluator<Value> eval)\n\t{\n\t\tthis.eval = eval;\n\t}\n\n\t/**\n\t * Set the export options.\n\t */\n\tpublic void setModelExportOptions(ModelExportOptions modelExportOptions)\n\t{\n\t\tthis.modelExportOptions = modelExportOptions;\n\t}\n\n\t/**\n\t * Add an unnamed reward to be exported.\n\t */\n\tpublic void addReward(Rewards<Value> rew)\n\t{\n\t\taddReward(rew, \"\");\n\t}\n\n\t/**\n\t * Add a reward to be exported.\n\t * {@code rewName} can be null or \"\" if the reward is unnamed.\n\t */\n\tpublic void addReward(Rewards<Value> rew, String rewName)\n\t{\n\t\trewards.add(rew);\n\t\trewardNames.add(rewName == null ? \"\" : rewName);\n\t}\n\n\t/**\n\t * Add multiple rewards to be exported.\n\t * Strings in {@code rewName} can be null or \"\" if the reward is unnamed.\n\t */\n\tpublic void addRewards(List<Rewards<Value>> rews, List<String> rewNames)\n\t{\n\t\tint numRewards = rews.size();\n\t\tfor (int i = 0; i < numRewards; i++) {\n\t\t\taddReward(rews.get(i), rewNames.get(i));\n\t\t}\n\t}\n\n\t/**\n\t * Set a separate evaluator for dealing with reward values.\n\t * If not set, the evaluator for model values is used.\n\t */\n\tpublic void setRewardEvaluator(Evaluator<Value> evalRewards)\n\t{\n\t\tthis.evalRewards = evalRewards;\n\t}\n\n\t/**\n\t * Add a label to be exported.\n\t */\n\tpublic void addLabel(BitSet label, String labelName)\n\t{\n\t\tlabels.add(label);\n\t\tlabelNames.add(labelName);\n\t}\n\n\t/**\n\t * Add multiple labels to be exported.\n\t */\n\tpublic void addLabels(List<BitSet> labels, List<String> labelNames)\n\t{\n\t\tint numLabels = labels.size();\n\t\tfor (int i = 0; i < numLabels; i++) {\n\t\t\taddLabel(labels.get(i), labelNames.get(i));\n\t\t}\n\t}\n\n\t/**\n\t * Provide information about the model,\n\t * e.g., for variable/observable annotations.\n\t */\n\tpublic void setModelInfo(ModelInfo modelInfo)\n\t{\n\t\tthis.modelInfo = modelInfo;\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the evaluator for dealing with model values.\n\t */\n\tpublic Evaluator<Value> getEvaluator()\n\t{\n\t\treturn eval;\n\t}\n\n\t/**\n\t * Get the export options.\n\t */\n\tpublic ModelExportOptions getModelExportOptions()\n\t{\n\t\treturn modelExportOptions;\n\t}\n\n\t/**\n\t * Get the number of rewards to be exported.\n\t */\n\tpublic int getNumRewards()\n\t{\n\t\treturn rewards.size();\n\t}\n\n\t/**\n\t * Get the rewards to be exported.\n\t */\n\tpublic List<Rewards<Value>> getRewards()\n\t{\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Get the ith reward to be exported.\n\t */\n\tpublic Rewards<Value> getReward(int i)\n\t{\n\t\treturn rewards.get(i);\n\t}\n\n\t/**\n\t * Get the names of the rewards to be exported.\n\t * Some names may be empty (\"\");\n\t */\n\tpublic List<String> getRewardNames()\n\t{\n\t\treturn rewardNames;\n\t}\n\n\t/**\n\t * Get the names of the ith reward to be exported.\n\t * May be empty (\"\");\n\t */\n\tpublic String getRewardName(int i)\n\t{\n\t\treturn rewardNames.get(i);\n\t}\n\n\t/**\n\t * Get a separate evaluator for dealing with reward values.\n\t */\n\tpublic Evaluator<Value> getRewardEvaluator()\n\t{\n\t\treturn evalRewards == null ? getEvaluator() : evalRewards;\n\t}\n\n\t/**\n\t * Get the number of labels to be exported.\n\t */\n\tpublic int getNumLabels()\n\t{\n\t\treturn labels.size();\n\t}\n\n\t/**\n\t * Get the labels to be exported.\n\t */\n\tpublic List<BitSet> getLabels()\n\t{\n\t\treturn labels;\n\t}\n\n\t/**\n\t * Get the ith label to be exported.\n\t */\n\tpublic BitSet getLabel(int i)\n\t{\n\t\treturn labels.get(i);\n\t}\n\n\t/**\n\t * Get the names of the labels to be exported.\n\t */\n\tpublic List<String> getLabelNames()\n\t{\n\t\treturn labelNames;\n\t}\n\n\t/**\n\t * Get the name of the ith label to be exported.\n\t */\n\tpublic String getLabelName(int i)\n\t{\n\t\treturn labelNames.get(i);\n\t}\n\n\t/**\n\t * Get information about the model,\n\t * e.g., for variable/observable annotations.\n\t * May be null.\n\t */\n\tpublic ModelInfo getModelInfo()\n\t{\n\t\treturn modelInfo;\n\t}\n\n\t/**\n\t * Export a model to a {@link PrismLog}.\n\t * @param model The model\n\t * @param out Where to export\n\t */\n\tpublic abstract void exportModel(Model<Value> model, PrismLog out) throws PrismException;\n\n\t/**\n\t * Export a model to a file.\n\t * @param model The model\n\t * @param fileOut File to export to\n\t */\n\tpublic void exportModel(Model<Value> model, File fileOut) throws PrismException\n\t{\n\t\ttry (PrismLog out = new PrismFileLog(fileOut.getPath())) {\n\t\t\texportModel(model, out);\n\t\t}\n\t}\n\n\t// Utility functions\n\n\t/**\n\t * Format a {@code Value} as a string, based on the {@link Evaluator} and {@link ModelExportOptions}.\n\t */\n\tpublic String formatValue(Value value, Evaluator<Value> theEval)\n\t{\n\t\treturn theEval.toStringExport(value, modelExportOptions.getModelPrecision());\n\t}\n\n\t/**\n\t * Format a {@code Value} as a string, based on the {@link Evaluator} and {@link ModelExportOptions}.\n\t */\n\tpublic String formatValue(Value value)\n\t{\n\t\treturn eval.toStringExport(value, modelExportOptions.getModelPrecision());\n\t}\n\n\t/**\n\t * Get access to a sorted list of transitions for a choice of a state of a model.\n\t * Transitions are sorted by successor state and then (if present) action string.\n\t * Note that this means duplicate transitions are removed too.\n\t * @param model The model\n\t * @param s The state\n\t * @param j The choice\n\t * @param includeActions Whether to include actions\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <ValueM> Iterable<Transition<Object>> getSortedTransitionsIterator(Model<ValueM> model, int s, int j, boolean includeActions) throws PrismException\n\t{\n\t\tTreeSet<Transition<Object>> sorted = new TreeSet<>(Transition::compareTo);\n\t\t// Get action (if attached to choice)\n\t\tObject action = null;\n\t\tif (model.getModelType().nondeterministic() && includeActions) {\n\t\t\taction = ((NondetModel<ValueM>) model).getAction(s, j);\n\t\t}\n\t\t// Extract transitions\n\t\tif (!model.getModelType().uncertain()) {\n\t\t\t// DTMCs\n\t\t\tif (model instanceof DTMC) {\n\t\t\t\tIterator<Map.Entry<Integer, Pair<ValueM, Object>>> iter = ((DTMC<ValueM>) model).getTransitionsAndActionsIterator(s);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tMap.Entry<Integer, Pair<ValueM, Object>> e = iter.next();\n\t\t\t\t\tif (includeActions) {\n\t\t\t\t\t\taction = e.getValue().second;\n\t\t\t\t\t}\n\t\t\t\t\tsorted.add((Transition<Object>) new Transition<>(e.getKey(), e.getValue().first, action, model.getEvaluator()));\n\t\t\t\t}\n\t\t\t}\n\t\t\t// LTS-like (non-probabilistic, nondeterministic) models\n\t\t\telse if (model instanceof LTS) {\n\t\t\t\tint succ = ((LTS<ValueM>) model).getSuccessor(s, j);\n\t\t\t\tsorted.add((Transition<Object>) new Transition<>(succ, model.getEvaluator().one(), action, model.getEvaluator()));\n\t\t\t}\n\t\t\t// MDP-like (probabilistic, nondeterministic) models\n\t\t\telse {\n\t\t\t\tIterator<Map.Entry<Integer, ValueM>> iter = ((MDP<ValueM>) model).getTransitionsIterator(s, j);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tMap.Entry<Integer, ValueM> e = iter.next();\n\t\t\t\t\tsorted.add((Transition<Object>) new Transition<>(e.getKey(), e.getValue(), action, model.getEvaluator()));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Interval models\n\t\telse {\n\t\t\t// IDTMCs\n\t\t\tif (model instanceof IDTMC) {\n\t\t\t\tIterator<Map.Entry<Integer, Pair<Interval<ValueM>, Object>>> iter = ((IDTMC<ValueM>) model).getIntervalTransitionsAndActionsIterator(s);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tMap.Entry<Integer, Pair<Interval<ValueM>, Object>> e = iter.next();\n\t\t\t\t\tif (includeActions) {\n\t\t\t\t\t\taction = e.getValue().second;\n\t\t\t\t\t}\n\t\t\t\t\tsorted.add((Transition<Object>) (Transition<? extends Object>) new Transition<>(e.getKey(), e.getValue().first, action, ((IDTMC<ValueM>) model).getIntervalEvaluator()));\n\t\t\t\t}\n\t\t\t}\n\t\t\t// IMDP-like models\n\t\t\telse {\n\t\t\t\tIterator<Map.Entry<Integer, Interval<ValueM>>> iter = ((MDP<Interval<ValueM>>) (((IntervalModel<ValueM>) model).getIntervalModel())).getTransitionsIterator(s, j);\n\t\t\t\tEvaluator<Interval<ValueM>> evalIntv = ((IntervalModel<ValueM>) model).getIntervalEvaluator();\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tMap.Entry<Integer, Interval<ValueM>> e = iter.next();\n\t\t\t\t\tsorted.add((Transition<Object>) (Transition<? extends Object>) new Transition<>(e.getKey(), e.getValue(), action, evalIntv));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn sorted;\n\t}\n\n\t/**\n\t * Get access to a sorted list of transitions rewards for a state of a (Markov chain) model.\n\t * Transitions are sorted by successor state and then (if present) action string.\n\t * Note that this means duplicate transitions are removed too.\n\t * @param model The model\n\t * @param s The state\n\t * @param includeActions Whether to include actions\n\t */\n\tpublic <ValueM> Iterable<Transition<Value>> getSortedTransitionRewardsIterator(DTMC<ValueM> model, Rewards<Value> rewards, int s, boolean includeActions)\n\t{\n\t\tTreeSet<Transition<Value>> sorted = new TreeSet<>(Transition::compareTo);\n\t\tObject action = null;\n\t\tIterator<Map.Entry<Integer, Pair<ValueM, Object>>> iter = model.getTransitionsAndActionsIterator(s);\n\t\tint k = 0;\n\t\twhile (iter.hasNext()) {\n\t\t\tMap.Entry<Integer, Pair<ValueM, Object>> e = iter.next();\n\t\t\tif (includeActions) {\n\t\t\t\taction = e.getValue().second;\n\t\t\t}\n\t\t\tsorted.add(new Transition<>(e.getKey(), rewards.getTransitionReward(s, k), action, rewards.getEvaluator()));\n\t\t\tk++;\n\t\t}\n\t\treturn sorted;\n\t}\n\n\t/**\n\t * Get a tuple comprising the state rewards for state {@code s}.\n\t * @param allRewards The list of rewards\n\t * @param s The state\n\t */\n\tprotected RewardTuple<Value> getStateRewardTuple(List<Rewards<Value>> allRewards, int s)\n\t{\n\t\tint numRewards = allRewards.size();\n\t\tRewardTuple<Value> tuple = new RewardTuple<>(numRewards);\n\t\tfor (Rewards<Value> rewards : allRewards) {\n\t\t\ttuple.add(rewards.getStateReward(s));\n\t\t}\n\t\treturn tuple;\n\t}\n\n\t/**\n\t * Get a tuple comprising the transition rewards for index {@code j} of state {@code s}.\n\t * @param allRewards The list of rewards\n\t * @param s The state\n\t * @param j The choice/transition index\n\t */\n\tprotected RewardTuple<Value> getTransitionRewardTuple(List<Rewards<Value>> allRewards, int s, int j)\n\t{\n\t\tint numRewards = allRewards.size();\n\t\tRewardTuple<Value> tuple = new RewardTuple<>(numRewards);\n\t\tfor (Rewards<Value> rewards : allRewards) {\n\t\t\ttuple.add(rewards.getTransitionReward(s, j));\n\t\t}\n\t\treturn tuple;\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/PrismExplicitExporter.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport common.IteratorTools;\nimport explicit.DTMC;\nimport explicit.IDTMC;\nimport explicit.IntervalModel;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport explicit.PartiallyObservableModel;\nimport explicit.SuccessorsIterator;\nimport explicit.rewards.Rewards;\nimport parser.State;\nimport parser.VarList;\nimport prism.Evaluator;\nimport prism.ModelInfo;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLog;\n\nimport java.util.BitSet;\nimport java.util.List;\n\n/**\n * Class to manage export of built models to PRISM's explicit file formats.\n */\npublic class PrismExplicitExporter<Value> extends ModelExporter<Value>\n{\n\tpublic PrismExplicitExporter()\n\t{\n\t\tsuper();\n\t}\n\n\tpublic PrismExplicitExporter(ModelExportOptions modelExportOptions)\n\t{\n\t\tsuper(modelExportOptions);\n\t}\n\n\t@Override\n\tpublic void exportModel(Model<Value> model, PrismLog out) throws PrismException\n\t{\n\t\texportTransitions(model, out);\n\t}\n\n\t/**\n\t * Export a model in PRISM's .tra format.\n\t * @param model Model to export\n\t * @param out PrismLog to export to\n\t */\n\tpublic <ValueM> void exportTransitions(Model<ValueM> model, PrismLog out) throws PrismException\n\t{\n\t\t// Get model info and exportOptions\n\t\tModelType modelType = model.getModelType();\n\t\tboolean showActions = modelExportOptions.getShowActions();\n\t\t// Currently, we only include initial state info here for POMDPs\n\t\tboolean showInit = modelType.partiallyObservable();\n\n\t\t// Output .tra file file header\n\t\tint numStates = model.getNumStates();\n\t\tout.print(numStates);\n\t\tif (modelType.nondeterministic()) {\n\t\t\tout.print(\" \" + ((NondetModel<ValueM>) model).getNumChoices());\n\t\t}\n\t\tout.print(\" \" + model.getNumTransitions());\n\t\tif (modelType.partiallyObservable()) {\n\t\t\tout.print(\" \" + ((PartiallyObservableModel<ValueM>) model).getNumObservations());\n\t\t}\n\t\tout.print(\"\\n\");\n\n\t\t// Output initial states, if required\n\t\tif (showInit) {\n\t\t\tfor (int s : model.getInitialStates()) {\n\t\t\t\tout.print(\"-\");\n\t\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\t\tout.print(\" -\");\n\t\t\t\t}\n\t\t\t\tout.print(\" \" + s);\n\t\t\t\tif (modelType.isProbabilistic()) {\n\t\t\t\t\tout.print(\" -\");\n\t\t\t\t}\n\t\t\t\tif (modelType.partiallyObservable()) {\n\t\t\t\t\tout.print(\" \" + ((PartiallyObservableModel<ValueM>) model).getObservation(s));\n\t\t\t\t}\n\t\t\t\tout.print(\"\\n\");\n\t\t\t}\n\t\t}\n\n\t\t// Output transitions in .tra format\n\t\t// Iterate through states\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tint numChoices = 1;\n\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\tnumChoices = ((NondetModel<ValueM>) model).getNumChoices(s);\n\t\t\t}\n\t\t\t// Iterate through choices\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\t// Print out (sorted) transitions\n\t\t\t\tfor (Transition<?> transition : getSortedTransitionsIterator(model, s, j, showActions)) {\n\t\t\t\t\tout.print(s);\n\t\t\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\t\t\tout.print(\" \" + j);\n\t\t\t\t\t}\n\t\t\t\t\tout.print(\" \" + transition.target);\n\t\t\t\t\tif (modelType.isProbabilistic()) {\n\t\t\t\t\t\tout.print(\" \" + transition.toString(modelExportOptions));\n\t\t\t\t\t}\n\t\t\t\t\tif (modelType.partiallyObservable()) {\n\t\t\t\t\t\tout.print(\" \" + ((PartiallyObservableModel<ValueM>) model).getObservation(transition.target));\n\t\t\t\t\t}\n\t\t\t\t\tif (showActions && transition.action != null && !\"\".equals(transition.action)) {\n\t\t\t\t\t\tout.print(\" \" + transition.action);\n\t\t\t\t\t}\n\t\t\t\t\tout.print(\"\\n\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Export (non-zero) state rewards from a Rewards object.\n\t * @param model The model\n\t * @param rewards The rewards\n\t * @param rewardStructName The name of the reward structure\n\t * @param out Where to export\n\t */\n\tpublic void exportStateRewards(Model<Value> model, Rewards<Value> rewards, String rewardStructName, PrismLog out) throws PrismException\n\t{\n\t\t// Get model info and exportOptions\n\t\tsetEvaluator(model.getEvaluator());\n\t\tEvaluator<Value> evalRewards = rewards.getEvaluator();\n\t\tboolean noexportheaders = !getModelExportOptions().getPrintHeaders();\n\t\tint numStates = model.getNumStates();\n\t\t// Count non-zero rewards\n\t\tint nonZeroRews = 0;\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tValue d = rewards.getStateReward(s);\n\t\t\tif (!evalRewards.isZero(d)) {\n\t\t\t\tnonZeroRews++;\n\t\t\t}\n\t\t}\n\t\t// Output non-zero rewards\n\t\tprintStateRewardsHeader(out, rewardStructName, noexportheaders);\n\t\tout.println(numStates + \" \" + nonZeroRews);\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tValue d = rewards.getStateReward(s);\n\t\t\tif (!evalRewards.isZero(d)) {\n\t\t\t\tout.println(s + \" \" + formatValue(d, evalRewards));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Print header to srew file, when not disabled.\n\t * Header format with optional reward struct name:\n\t * <pre>\n\t *   # Reward structure &lt;double-quoted-name&gt;\n\t *   # State rewards\n\t * </pre>\n\t * where &lt;double-quoted-name&gt; (\"<name>\") is omitted if the reward structure is not named.\n\t *\n\t * @param out Where to export\n\t * @param rewardStructName The name of the reward structure\n\t * @param noexportheaders Disable export of the header?\n\t */\n\tpublic void printStateRewardsHeader(PrismLog out, String rewardStructName, boolean noexportheaders)\n\t{\n\t\tif (noexportheaders) {\n\t\t\treturn;\n\t\t}\n\t\tout.print(\"# Reward structure\");\n\t\tif (!\"\".equals(rewardStructName)) {\n\t\t\tout.print(\" \\\"\" + rewardStructName + \"\\\"\");\n\t\t}\n\t\tout.println(\"\\n# State rewards\");\n\t}\n\n\t/**\n\t * Export (non-zero) transition rewards from a Rewards object.\n\t * @param model The model\n\t * @param rewards The rewards\n\t * @param rewardStructName The name of the reward structure\n\t * @param out Where to export\n\t */\n\tpublic void exportTransRewards(Model<Value> model, Rewards<Value> rewards, String rewardStructName, PrismLog out) throws PrismException\n\t{\n\t\t// Get model info and exportOptions\n\t\tsetEvaluator(model.getEvaluator());\n\t\tEvaluator<Value> evalRewards = rewards.getEvaluator();\n\t\tboolean noexportheaders = !getModelExportOptions().getPrintHeaders();\n\t\tboolean nondet = model.getModelType().nondeterministic();\n\t\tint numStates = model.getNumStates();\n\t\t// Count non-zero rewards\n\t\tint nonZeroRews = 0;\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tif (nondet) {\n\t\t\t\tint numChoices = ((NondetModel<Value>) model).getNumChoices();\n\t\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\t\tValue d = rewards.getTransitionReward(s, j);\n\t\t\t\t\tif (!evalRewards.isZero(d)) {\n\t\t\t\t\t\tnonZeroRews += ((NondetModel<Value>) model).getNumTransitions(s, j);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tDTMC<?> mcModel = (model instanceof IDTMC) ? ((IDTMC<Value>) model).getIntervalModel() : (DTMC<Value>) model;\n\t\t\t\tnonZeroRews += Math.toIntExact(IteratorTools.count(getSortedTransitionRewardsIterator(mcModel, rewards, s,true), t -> !t.isZero()));\n\t\t\t}\n\t\t}\n\t\t// Output non-zero rewards\n\t\tprintTransRewardsHeader(out, rewardStructName, noexportheaders);\n\t\tout.print(numStates);\n\t\tif (nondet) {\n\t\t\tout.print(\" \" + ((NondetModel<Value>) model).getNumChoices());\n\t\t}\n\t\tout.println(\" \" + nonZeroRews);\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tif (nondet) {\n\t\t\t\tint numChoices = ((NondetModel<Value>) model).getNumChoices();\n\t\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\t\tValue d = rewards.getTransitionReward(s, j);\n\t\t\t\t\tif (!evalRewards.isZero(d)) {\n\t\t\t\t\t\t// For nondet models, the choice reward is displayed by all transitions\n\t\t\t\t\t\t// (which we sort, in order to match the output for the model)\n\t\t\t\t\t\tfor (Transition<?> transition : getSortedTransitionsIterator(model, s, j, modelExportOptions.getShowActions())) {\n\t\t\t\t\t\t\tout.println(s + \" \" + j + \" \" + transition.target + \" \" + formatValue(d, evalRewards));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tDTMC<?> mcModel = (model instanceof IDTMC) ? ((IDTMC<Value>) model).getIntervalModel() : (DTMC<Value>) model;\n\t\t\t\tfor (Transition<Value> transition : getSortedTransitionRewardsIterator(mcModel, rewards, s, true)) {\n\t\t\t\t\tif (!transition.isZero()) {\n\t\t\t\t\t\tout.println(s + \" \" + transition.target + \" \" + transition.toString(modelExportOptions));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Print header to trew file, when not disabled.\n\t * Header format with optional reward struct name:\n\t * <pre>\n\t *   # Reward structure &lt;double-quoted-name&gt;\n\t *   # State rewards\n\t * </pre>\n\t * where &lt;double-quoted-name&gt; (\"<name>\") is omitted if the reward structure is not named.\n\t *\n\t * @param out Where to export\n\t * @param rewardStructName The name of the reward structure\n\t * @param noexportheaders Disable export of the header?\n\t */\n\tpublic void printTransRewardsHeader(PrismLog out, String rewardStructName, boolean noexportheaders)\n\t{\n\t\tif (noexportheaders) {\n\t\t\treturn;\n\t\t}\n\t\tout.print(\"# Reward structure\");\n\t\tif (!\"\".equals(rewardStructName)) {\n\t\t\tout.print(\" \\\"\" + rewardStructName + \"\\\"\");\n\t\t}\n\t\tout.println(\"\\n# Transition rewards\");\n\t}\n\n\t/**\n\t * Export the states for a model.\n\t * @param model The model\n\t * @param varList The VarList for the model\n\t * @param out Where to export\n\t */\n\tpublic void exportStates(Model<Value> model, VarList varList, PrismLog out) throws PrismException\n\t{\n\t\tList<State> statesList = model.getStatesList();\n\t\tif (statesList == null)\n\t\t\treturn;\n\n\t\t// Print header: list of model vars\n\t\tout.print(\"(\");\n\t\tint numVars = varList.getNumVars();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tout.print(varList.getName(i));\n\t\t\tif (i < numVars - 1)\n\t\t\t\tout.print(\",\");\n\t\t}\n\t\tout.println(\")\");\n\n\t\t// Print states\n\t\tint numStates = statesList.size();\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tout.println(i + \":\" + statesList.get(i).toString());\n\t\t}\n\t}\n\n\t/**\n\t * Export the observations for a (partially observable) model.\n\t * @param model The model\n\t * @param modelInfo The ModelInfo for the model\n\t * @param out Where to export\n\t */\n\tpublic void exportObservations(PartiallyObservableModel<Value> model, ModelInfo modelInfo, PrismLog out) throws PrismException\n\t{\n\t\tList<State> observationsList =  model.getObservationsList();\n\n\t\t// Print header: list of observables\n\t\tout.print(\"(\");\n\t\tint numObservables = modelInfo.getNumObservables();\n\t\tfor (int i = 0; i < numObservables; i++) {\n\t\t\tout.print(modelInfo.getObservableName(i));\n\t\t\tif (i < numObservables - 1)\n\t\t\t\tout.print(\",\");\n\t\t}\n\t\tout.println(\")\");\n\n\t\t// Print states + observations\n\t\tint numObservations = model.getNumObservations();\n\t\tfor (int i = 0; i < numObservations; i++) {\n\t\t\tout.println(i + \":\" + observationsList.get(i).toString());\n\t\t}\n\t}\n\n\t/**\n\t * Export a set of labels and the states that satisfy them.\n\t * @param model The model\n\t * @param labelNames The names of the labels to export\n\t * @param labelStates The states that satisfy each label, specified as a BitSet\n\t * @param out Where to export\n\t */\n\tpublic void exportLabels(Model<Value> model, List<String> labelNames, List<BitSet> labelStates, PrismLog out) throws PrismException\n\t{\n\t\t// Get model info and exportOptions\n\t\tsetEvaluator(model.getEvaluator());\n\t\tint numStates = model.getNumStates();\n\n\t\t// Print list of labels\n\t\tint numLabels = labelNames.size();\n\t\tfor (int s = 0; s < numLabels; s++) {\n\t\t\tout.print((s > 0 ? \" \" : \"\") + s + \"=\\\"\" + labelNames.get(s) + \"\\\"\");\n\t\t}\n\t\tout.println();\n\n\t\t// Go through states and print satisfying label indices for each one\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tboolean first = true;\n\t\t\tfor (int i = 0; i < numLabels; i++) {\n\t\t\t\tif (labelStates.get(i).get(s)) {\n\t\t\t\t\tif (first) {\n\t\t\t\t\t\tout.print(s + \":\");\n\t\t\t\t\t\tfirst = false;\n\t\t\t\t\t}\n\t\t\t\t\tout.print(\" \" + i);\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!first) {\n\t\t\t\tout.println();\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/PrismExplicitImporter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2019-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage io;\n\nimport java.io.BufferedReader;\nimport java.io.File;\nimport java.io.FileReader;\nimport java.io.IOException;\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Objects;\nimport java.util.Optional;\nimport java.util.function.BiConsumer;\nimport java.util.function.Consumer;\nimport java.util.regex.Matcher;\nimport java.util.regex.Pattern;\nimport java.util.stream.Collectors;\n\nimport csv.BasicReader;\nimport csv.CsvFormatException;\nimport csv.CsvReader;\nimport explicit.DTMCSimple;\nimport explicit.ModelExplicit;\nimport explicit.NondetModel;\nimport explicit.SuccessorsIterator;\nimport param.BigRational;\nimport parser.State;\nimport parser.ast.DeclarationBool;\nimport parser.ast.DeclarationInt;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionIdent;\nimport parser.type.Type;\nimport parser.type.TypeBool;\nimport parser.type.TypeInt;\nimport prism.BasicModelInfo;\nimport prism.BasicRewardInfo;\nimport prism.Evaluator;\nimport prism.ModelInfo;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.RewardInfo;\n\nimport static csv.BasicReader.LF;\n\n/**\n * Class to manage importing models from PRISM explicit files (.tra, .sta, etc.)\n */\npublic class PrismExplicitImporter extends ExplicitModelImporter\n{\n\t// What to import: files and type override\n\tprivate File statesFile;\n\tprivate File transFile;\n\tprivate File observationsFile;\n\tprivate File labelsFile;\n\tprivate List<File> stateRewardsFiles;\n\tprivate List<File> transRewardsFiles;\n\tprivate ModelType typeOverride;\n\t// Does the transitions file store initial states info?\n\tprivate boolean transFileStoresInitialStates;\n\n\t// Model info extracted from files and then stored in a BasicModelInfo object\n\tprivate BasicModelInfo basicModelInfo;\n\n\t// String stating the model type and how it was obtained\n\tprivate String modelTypeString;\n\n\t// Model statistics (num states/choices/transitions)\n\tprivate class ModelStats\n\t{\n\t\tint numStates = 0;\n\t\tint numChoices = 0;\n\t\tint numTransitions = 0;\n\t\tint numObservations = 0;\n\t}\n\tprivate ModelStats modelStats;\n\n\t// Info about deadlocks\n\tprivate class DeadlockInfo\n\t{\n\t\tBitSet deadlocks = new BitSet();\n\t\tint numDeadlocks = 0;\n\t}\n\tprivate DeadlockInfo deadlockInfo;\n\n\t// Mapping from label indices in file to (non-built-in) label indices (also: -1=init, -2=deadlock)\n\tprivate List<Integer> labelMap;\n\n\t// Reward info extracted from files and then stored in a BasicRewardInfo object\n\tprivate BasicRewardInfo basicRewardInfo;\n\n\t// File(s) to read in rewards from\n\tprivate List<PrismExplicitImporter.RewardFile> stateRewardsReaders = new ArrayList<>();\n\tprivate List<PrismExplicitImporter.RewardFile> transRewardsReaders = new ArrayList<>();\n\n\t// Regex for comments\n\tprotected static final Pattern COMMENT_PATTERN = Pattern.compile(\"#.*\");\n\t// Regex for reward name\n\tprotected static final Pattern REWARD_NAME_PATTERN = Pattern.compile(\"# Reward structure (\\\"([_a-zA-Z0-9]*)\\\")$\");\n\n\t/**\n\t * Constructor\n\t * @param statesFile States file (may be {@code null})\n\t * @param transFile Transitions file\n\t * @param labelsFile Labels file (may be {@code null})\n\t * @param stateRewardsFiles State rewards files list (can be null/empty)\n\t * @param transRewardsFiles Transition rewards files list (can be null/empty)\n\t * @param typeOverride Specified model type (null mean auto-detect it, or default to MDP if that cannot be done).\n\t */\n\tpublic PrismExplicitImporter(File statesFile, File transFile, File labelsFile, List<File> stateRewardsFiles, List<File> transRewardsFiles, ModelType typeOverride) throws PrismException\n\t{\n\t\tsetStatesFile(statesFile);\n\t\tsetTransFile(transFile);\n\t\tsetLabelsFile(labelsFile);\n\t\tthis.stateRewardsFiles = new ArrayList<>();\n\t\tthis.stateRewardsReaders = new ArrayList<>();\n\t\tif (stateRewardsFiles != null) {\n\t\t\tfor (File stateRewardsFile : stateRewardsFiles) {\n\t\t\t\taddStateRewardsFile(stateRewardsFile);\n\t\t\t}\n\t\t}\n\t\tthis.transRewardsFiles = new ArrayList<>();\n\t\tthis.transRewardsReaders = new ArrayList<>();\n\t\tif (transRewardsFiles != null) {\n\t\t\tfor (File transRewardsFile : transRewardsFiles) {\n\t\t\t\taddTransitionRewardsFile(transRewardsFile);\n\t\t\t}\n\t\t}\n\t\tthis.typeOverride = typeOverride;\n\t}\n\n\t/**\n\t * Constructor\n\t * @param transFile Transitions file\n\t * @param typeOverride Specified model type (null mean auto-detect it, or default to MDP if that cannot be done).\n\t */\n\tpublic PrismExplicitImporter(File transFile, ModelType typeOverride) throws PrismException\n\t{\n\t\tthis(null, transFile, null, null, null, typeOverride);\n\t}\n\n\t/**\n\t * Constructor\n\t * @param transFile Transitions file\n\t */\n\tpublic PrismExplicitImporter(File transFile) throws PrismException\n\t{\n\t\tthis(null, null);\n\t}\n\n\t/**\n\t * Set the states file.\n\t * @param statesFile States file (may be {@code null})\n\t */\n\tpublic void setStatesFile(File statesFile)\n\t{\n\t\tthis.statesFile = statesFile;\n\t}\n\n\t/**\n\t * Set the transitions file.\n\t * @param transFile Transitions file\n\t */\n\tpublic void setTransFile(File transFile)\n\t{\n\t\tthis.transFile = transFile;\n\t}\n\n\t/**\n\t * Set the observations file.\n\t * @param observationsFile Observations file (may be {@code null})\n\t */\n\tpublic void setObservationsFile(File observationsFile)\n\t{\n\t\tthis.observationsFile = observationsFile;\n\t}\n\n\t/**\n\t * Set the labels file.\n\t * @param labelsFile Labels file (may be {@code null})\n\t */\n\tpublic void setLabelsFile(File labelsFile)\n\t{\n\t\tthis.labelsFile = labelsFile;\n\t}\n\n\t/**\n\t * Add a state rewards file.\n\t * @param stateRewardsFile State rewards file\n\t */\n\tpublic void addStateRewardsFile(File stateRewardsFile) throws PrismException\n\t{\n\t\tstateRewardsFiles.add(stateRewardsFile);\n\t\tstateRewardsReaders.add(new RewardFile(stateRewardsFile));\n\t}\n\n\t/**\n\t * Add a transition rewards file.\n\t * @param transitionRewardsFile Transition rewards file\n\t */\n\tpublic void addTransitionRewardsFile(File transitionRewardsFile) throws PrismException\n\t{\n\t\ttransRewardsFiles.add(transitionRewardsFile);\n\t\ttransRewardsReaders.add(new RewardFile(transitionRewardsFile));\n\t}\n\n\t/**\n\t * Get the states file (null if not used).\n\t */\n\tpublic File getStatesFile()\n\t{\n\t\treturn statesFile;\n\t}\n\n\t/**\n\t * Get the transitions file\n\t */\n\tpublic File getTransFile()\n\t{\n\t\treturn transFile;\n\t}\n\n\t/**\n\t * Get the observations file (null if not used).\n\t */\n\tpublic File getObservationsFile()\n\t{\n\t\treturn observationsFile;\n\t}\n\n\t/**\n\t * Get the labels file (null if not used).\n\t */\n\tpublic File getLabelsFile()\n\t{\n\t\treturn labelsFile;\n\t}\n\n\t/**\n\t * Get a list of all files being imported from.\n\t */\n\tpublic List<File> getAllFiles()\n\t{\n\t\tArrayList<File> allFiles = new ArrayList<>();\n\t\tif (transFile != null) {\n\t\t\tallFiles.add(transFile);\n\t\t}\n\t\tif (statesFile != null) {\n\t\t\tallFiles.add(statesFile);\n\t\t}\n\t\tif (observationsFile != null) {\n\t\t\tallFiles.add(observationsFile);\n\t\t}\n\t\tif (labelsFile != null) {\n\t\t\tallFiles.add(labelsFile);\n\t\t}\n\t\tif (stateRewardsFiles != null) {\n\t\t\tallFiles.addAll(stateRewardsFiles);\n\t\t}\n\t\tif (transRewardsFiles != null) {\n\t\t\tallFiles.addAll(transRewardsFiles);\n\t\t}\n\t\treturn allFiles;\n\t}\n\n\t@Override\n\tpublic boolean providesStates()\n\t{\n\t\treturn getStatesFile() != null;\n\t}\n\n\t@Override\n\tpublic boolean providesObservations()\n\t{\n\t\treturn getObservationsFile() != null;\n\t}\n\n\t@Override\n\tpublic boolean providesLabels()\n\t{\n\t\treturn getLabelsFile() != null;\n\t}\n\n\t/**\n\t * Does the transitions file store initial states info?\n\t */\n\tprivate boolean transFileProvidesInitialStates() throws PrismException\n\t{\n\t\tif (modelStats == null) {\n\t\t\tbuildModelStats();\n\t\t}\n\t\treturn transFileStoresInitialStates;\n\t}\n\n\t@Override\n\tpublic String sourceString()\n\t{\n\t\treturn getAllFiles().stream().map(f -> \"\\\"\"+f.toString()+\"\\\"\").collect(Collectors.joining(\", \"));\n\t}\n\n\t@Override\n\tpublic ModelInfo getModelInfo() throws PrismException\n\t{\n\t\t// Construct lazily, as needed\n\t\tif (basicModelInfo == null) {\n\t\t\tbuildModelInfo();\n\t\t}\n\t\treturn basicModelInfo;\n\t}\n\n\t@Override\n\tpublic int getNumStates() throws PrismException\n\t{\n\t\t// Construct lazily, as needed\n\t \t// (determined from either states file or transitions file)\n\t\tif (modelStats == null) {\n\t\t\tbuildModelStats();\n\t\t}\n\t\treturn modelStats.numStates;\n\t}\n\n\t@Override\n\tpublic int getNumChoices() throws PrismException\n\t{\n\t\t// Construct lazily, as needed\n\t\t// (determined from transitions file)\n\t\tif (modelStats == null) {\n\t\t\tbuildModelStats();\n\t\t}\n\t\tint numChoices = modelStats.numChoices;\n\t\t// Add extras if deadlocks are being fixed\n\t\tif (fixdl) {\n\t\t\tnumChoices += getNumDeadlockStates();\n\t\t}\n\t\treturn numChoices;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions() throws PrismException\n\t{\n\t\t// Construct lazily, as needed\n\t\t// (determined from transitions file)\n\t\tif (modelStats == null) {\n\t\t\tbuildModelStats();\n\t\t}\n\t\tint numTransitions = modelStats.numTransitions;\n\t\t// Add extras if deadlocks are being fixed\n\t\tif (fixdl) {\n\t\t\tnumTransitions += getNumDeadlockStates();\n\t\t}\n\t\treturn numTransitions;\n\t}\n\n\t@Override\n\tpublic int getNumObservations() throws PrismException\n\t{\n\t\t// Construct lazily, as needed\n\t\t// (determined from transitions file, if needed)\n\t\tif (!getModelInfo().getModelType().partiallyObservable()) {\n\t\t\treturn 0;\n\t\t}\n\t\tif (modelStats == null) {\n\t\t\tbuildModelStats();\n\t\t}\n\t\treturn modelStats.numObservations;\n\t}\n\n\t@Override\n\tpublic BitSet getDeadlockStates() throws PrismException\n\t{\n\t\t// Do deadlock state detection lazily, as needed\n\t\tif (deadlockInfo == null) {\n\t\t\tfindDeadlocks();\n\t\t}\n\t\treturn deadlockInfo.deadlocks;\n\t}\n\n\t@Override\n\tpublic int getNumDeadlockStates() throws PrismException\n\t{\n\t\t// Do deadlock state detection lazily, as needed\n\t\tif (deadlockInfo == null) {\n\t\t\tfindDeadlocks();\n\t\t}\n\t\treturn deadlockInfo.numDeadlocks;\n\t}\n\n\t@Override\n\tpublic String getModelTypeString()\n\t{\n\t\treturn modelTypeString;\n\t}\n\n\t@Override\n\tpublic RewardInfo getRewardInfo() throws PrismException\n\t{\n\t\t// Construct lazily, as needed\n\t\tif (basicRewardInfo == null) {\n\t\t\tbuildRewardInfo();\n\t\t}\n\t\treturn basicRewardInfo;\n\t}\n\n\t/**\n\t * Build/store model stats (from the transitions file).\n\t * Can then be accessed via {@link #getNumStates()}, {@link #getNumChoices()}, {@link #getNumTransitions()}.\n\t */\n\tprivate void buildModelStats() throws PrismException\n\t{\n\t\t// Extract model stats from header of transitions file\n\t\textractModelStatsFromTransFile(transFile);\n\t}\n\n\t/**\n\t * Build/store model info from the states/transitions/labels files.\n\t * Can then be accessed via {@link #getModelInfo()}.\n\t * Also calls {@link #buildModelStats()} if needed.\n\t * Which makes available {@link #getNumStates()}, {@link #getNumChoices()}, {@link #getNumTransitions()}.\n\t */\n\tprivate void buildModelInfo() throws PrismException\n\t{\n\t\t// Build model stats, if not already done\n\t\tif (modelStats == null) {\n\t\t\tbuildModelStats();\n\t\t}\n\n\t\t// Set model type: if no preference stated, try to autodetect\n\t\tModelType modelType;\n\t\tif (typeOverride == null) {\n\t\t\tModelType typeAutodetect = autodetectModelType(transFile);\n\t\t\tif (typeAutodetect != null) {\n\t\t\t\tmodelTypeString = typeAutodetect + \" (auto-detected)\";\n\t\t\t} else {\n\t\t\t\ttypeAutodetect = ModelType.MDP;\n\t\t\t\tmodelTypeString = typeAutodetect + \" (default)\";\n\t\t\t}\n\t\t\tmodelType = typeAutodetect;\n\t\t} else {\n\t\t\tmodelTypeString = typeOverride + \" (user-specified)\";\n\t\t\tmodelType = typeOverride;\n\t\t}\n\n\t\t// Store model info\n\t\tbasicModelInfo = new BasicModelInfo(modelType);\n\n\t\t// Extract variable info from states, if available\n\t\tif (statesFile != null) {\n\t\t\textractVarInfoFromStatesFile(statesFile);\n\t\t}\n\t\t// Otherwise store default variable info\n\t\telse {\n\t\t\tbasicModelInfo.getVarList().addVar(defaultVariableName(), defaultVariableDeclarationType(), -1);\n\t\t}\n\n\t\t// Extract observable info from observations, if available\n\t\tif (modelType.partiallyObservable() && observationsFile != null) {\n\t\t\textractObservableInfoFromObservationsFile(observationsFile);\n\t\t}\n\t\t// Otherwise store default observable info\n\t\telse {\n\t\t\tbasicModelInfo.getObservableNames().add(defaultObservableName());\n\t\t\tbasicModelInfo.getObservableTypeList().add(defaultObservableType());\n\t\t}\n\n\t\t// Generate and store label names from the labels file, if available.\n\t\t// This way, expressions can refer to the labels later on.\n\t\tif (labelsFile != null) {\n\t\t\textractLabelNamesFromLabelsFile(labelsFile);\n\t\t} else {\n\t\t\tlabelMap = new ArrayList<>();\n\t\t}\n\t}\n\n\t/**\n\t * Extract variable info from a states file.\n\t */\n\tprivate void extractVarInfoFromStatesFile(File statesFile) throws PrismException\n\t{\n\t\textractVarInfoFromFile(statesFile, ModelExportTask.ModelExportEntity.STATES);\n\t}\n\n\t/**\n\t * Extract observable info from an observations file.\n\t */\n\tprivate void extractObservableInfoFromObservationsFile(File observationsFile) throws PrismException\n\t{\n\t\textractVarInfoFromFile(observationsFile, ModelExportTask.ModelExportEntity.OBSERVATIONS);\n\t}\n\n\t/**\n\t * Extract variable/observable info from a states/observations file.\n\t * The info is stored in {@code basicModelInfo}, which should already exist.\n\t * @param file States/observations file\n\t * @param entity State or observations?\n\t */\n\tprivate void extractVarInfoFromFile(File file, ModelExportTask.ModelExportEntity entity) throws PrismException\n\t{\n\t\tString entityString = (entity == ModelExportTask.ModelExportEntity.STATES) ? \"state\" : \"observation\";\n\t\t// open file for reading, automatic close when done\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(file))) {\n\t\t\t// read first line and extract var names\n\t\t\tString s = in.readLine();\n\t\t\tlineNum = 1;\n\t\t\tif (s == null)\n\t\t\t\tthrow new PrismException(\"empty \" + entityString + \"s file\");\n\t\t\ts = s.trim();\n\t\t\tif (s.charAt(0) != '(' || s.charAt(s.length() - 1) != ')')\n\t\t\t\tthrow new PrismException(\"badly formatted \" + entityString);\n\t\t\ts = s.substring(1, s.length() - 1);\n\t\t\tList<String> varNames = new ArrayList<>(Arrays.asList(s.split(\",\")));\n\t\t\tint numVars = varNames.size();\n\t\t\t// create arrays to (temporarily) store info about vars\n\t\t\tint[] varMins = new int[numVars];\n\t\t\tint[] varMaxs = new int[numVars];\n\t\t\tList<Type> varTypes = new ArrayList<>();\n\t\t\t// read remaining lines\n\t\t\ts = in.readLine();\n\t\t\tlineNum++;\n\t\t\tint counter = 0;\n\t\t\twhile (s != null) {\n\t\t\t\t// skip blank lines\n\t\t\t\ts = s.trim();\n\t\t\t\tif (s.length() > 0) {\n\t\t\t\t\tcounter++;\n\t\t\t\t\t// split string\n\t\t\t\t\ts = s.substring(s.indexOf('(') + 1, s.indexOf(')'));\n\t\t\t\t\tString[] ss = s.split(\",\");\n\t\t\t\t\tif (ss.length != numVars)\n\t\t\t\t\t\tthrow new PrismException(\"wrong number of variables\");\n\t\t\t\t\t// for each variable...\n\t\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\t\t// if this is the first state/observation, establish variable type\n\t\t\t\t\t\tif (counter == 1) {\n\t\t\t\t\t\t\tif (ss[i].equals(\"true\") || ss[i].equals(\"false\")) {\n\t\t\t\t\t\t\t\tvarTypes.add(TypeBool.getInstance());\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tvarTypes.add(TypeInt.getInstance());\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// check for new min/max values (ints only)\n\t\t\t\t\t\tif (varTypes.get(i) instanceof TypeInt) {\n\t\t\t\t\t\t\tint j = Integer.parseInt(ss[i]);\n\t\t\t\t\t\t\tif (counter == 1) {\n\t\t\t\t\t\t\t\tvarMins[i] = varMaxs[i] = j;\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tif (j < varMins[i])\n\t\t\t\t\t\t\t\t\tvarMins[i] = j;\n\t\t\t\t\t\t\t\tif (j > varMaxs[i])\n\t\t\t\t\t\t\t\t\tvarMaxs[i] = j;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// read next line\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\n\t\t\tif (entity == ModelExportTask.ModelExportEntity.STATES) {\n\t\t\t\t// Add variables to the VarList\n\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\tif (varTypes.get(i) instanceof TypeBool) {\n\t\t\t\t\t\tbasicModelInfo.getVarList().addVar(varNames.get(i), new DeclarationBool(), -1);\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// Note: we do not yet allow 0-range variables\n\t\t\t\t\t\tif (varMins[i] == varMaxs[i]) {\n\t\t\t\t\t\t\tvarMaxs[i]++;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbasicModelInfo.getVarList().addVar(varNames.get(i), new DeclarationInt(Expression.Int(varMins[i]), Expression.Int(varMaxs[i])), -1);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else if (entity == ModelExportTask.ModelExportEntity.OBSERVATIONS) {\n\t\t\t\t// Add observables to the model info\n\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\tbasicModelInfo.getObservableNameList().add(varNames.get(i));\n\t\t\t\t\tbasicModelInfo.getObservableTypeList().add(varTypes.get(i));\n\t\t\t\t}\n\t\t\t}\n\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error detected at line \" + lineNum + \" of \" + entityString + \"s file \\\"\" + file + \"\\\"\");\n\t\t} catch (PrismException e) {\n\t\t\tthrow new PrismException(\"Error detected (\" + e.getMessage() + \") at line \" + lineNum + \" of \" + entityString + \"s file \\\"\" + file + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Extract model stats (number of states/transitions) from a transitions file header.\n\t */\n\tprivate void extractModelStatsFromTransFile(File transFile) throws PrismException\n\t{\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tmodelStats = new ModelStats();\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tif (!csv.hasNextRecord()) {\n\t\t\t\tthrow new PrismException(\"empty transitions file\");\n\t\t\t}\n\t\t\tString[] record = csv.nextRecord();\n\t\t\tcheckLineSize(record, 2, 4);\n\t\t\tmodelStats.numStates = Integer.parseInt(record[0]);\n\t\t\tif (record.length == 2) {\n\t\t\t\t// Markov chain\n\t\t\t\tmodelStats.numChoices = modelStats.numStates;\n\t\t\t\tmodelStats.numTransitions = Integer.parseInt(record[1]);\n\t\t\t} else if (record.length == 3) {\n\t\t\t\t// MDP/LTS\n\t\t\t\tmodelStats.numChoices = Integer.parseInt(record[1]);\n\t\t\t\tmodelStats.numTransitions = Integer.parseInt(record[2]);\n\t\t\t} else {\n\t\t\t\t// POMDP\n\t\t\t\tmodelStats.numChoices = Integer.parseInt(record[1]);\n\t\t\t\tmodelStats.numTransitions = Integer.parseInt(record[2]);\n\t\t\t\tmodelStats.numObservations = Integer.parseInt(record[3]);\n\t\t\t}\n\t\t\t// Also peek at the next line to see if initial states info is provided\n\t\t\tif (csv.hasNextRecord()) {\n\t\t\t\trecord = csv.nextRecord();\n\t\t\t\tif (record.length >= 1 && record[0].equals(\"-\")) {\n\t\t\t\t\ttransFileStoresInitialStates = true;\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tmodelStats = null;\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\tmodelStats = null;\n\t\t\tint lineNum = 1;\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transitions file \\\"\" + transFile + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Extract names of labels from the labels file.\n\t * The \"init\" and \"deadlock\" labels are skipped, as they have special\n\t * meaning and are implicitly defined for all models.\n\t * The info is stored in {@code basicModelInfo} and {@code labelMap}.\n\t * {@code basicModelInfo} would usually already exist but is created if not\n\t * (this is only really for the case where this class is extracting labels in isolation);\n\t * {@code labelMap} is created by this method.\n\t */\n\tprivate void extractLabelNamesFromLabelsFile(File labelsFile) throws PrismException\n\t{\n\t\tint lineNum = 1;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(labelsFile))) {\n\t\t\t// Read/parse first line (label names)\n\t\t\t// Looks like, e.g.: 0=\"init\" 1=\"deadlock\" 2=\"heads\" 3=\"tails\" 4=\"end\"\n\t\t\tString labelsString = in.readLine();\n\t\t\tPattern label = Pattern.compile(\"(\\\\d+)=\\\"([^\\\"]+)\\\"\\\\s*\");\n\t\t\tMatcher matcher = label.matcher(labelsString);\n\t\t\tif (basicModelInfo == null) {\n\t\t\t\tbasicModelInfo = new BasicModelInfo();\n\t\t\t}\n\t\t\tList<String> labelNames = basicModelInfo.getLabelNameList();\n\t\t\tlabelMap = new ArrayList<>();\n\t\t\twhile (matcher.find()) {\n\t\t\t\t// Check indices are ascending/contiguous\n\t\t\t\tint labelIndex = checkLabelIndex(matcher.group(1));\n\t\t\t\tif (labelIndex != labelMap.size()) {\n\t\t\t\t\tthrow new PrismException(\"unexpected label index \" + labelIndex);\n\t\t\t\t}\n\t\t\t\t// Skip built-in labels\n\t\t\t\tString labelName = matcher.group(2);\n\t\t\t\tif (labelName.equals(\"init\")) {\n\t\t\t\t\tlabelMap.add(-1);\n\t\t\t\t\tcontinue;\n\t\t\t\t} else if (labelName.equals(\"deadlock\")) {\n\t\t\t\t\tlabelMap.add(-2);\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t// Check name legal and non-dupe\n\t\t\t\tif (!ExpressionIdent.isLegalIdentifierName(labelName)) {\n\t\t\t\t\tthrow new PrismException(\"illegal label name \\\"\" + labelName + \"\\\"\");\n\t\t\t\t}\n\t\t\t\tif (labelNames.contains(labelName)) {\n\t\t\t\t\tthrow new PrismException(\"duplicate label name \\\"\" + labelName + \"\\\"\");\n\t\t\t\t}\n\t\t\t\tlabelMap.add(labelNames.size());\n\t\t\t\tlabelNames.add(labelName);\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + labelsFile + \"\\\"\");\n\t\t} catch (PrismException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of labels file \\\"\" + labelsFile + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Autodetect the model type based on a sample of the lines from a transitions file.\n\t * If not possible, return null;\n\t * @param transFile transitions file\n\t */\n\tprivate ModelType autodetectModelType(File transFile)\n\t{\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tboolean nondet;\n\t\t\tboolean partObs;\n\t\t\tboolean nonprob;\n\t\t\t// Examine first line\n\t\t\t// 3 numbers should indicate a nondeterministic model, e.g., MDP\n\t\t\t// 2 numbers should indicate a probabilistic model, e.g., DTMC\n\t\t\t// Anything else, give up\n\t\t\tif (!csv.hasNextRecord()) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\t// Detect if model is nondeterministic\n\t\t\tString[] recordFirst = csv.nextRecord();\n\t\t\tif (recordFirst.length == 4) {\n\t\t\t\tnondet = true;\n\t\t\t\tpartObs = true;\n\t\t\t} else if (recordFirst.length == 3) {\n\t\t\t\tnondet = true;\n\t\t\t\tpartObs = false;\n\t\t\t} else if (recordFirst.length == 2) {\n\t\t\t\tnondet = false;\n\t\t\t\tpartObs = false;\n\t\t\t} else {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\t// Read up to max remaining lines\n\t\t\tint lines = 0;\n\t\t\tint max = 5;\n\t\t\tfor (String[] record : csv) {\n\t\t\t\tif (lines > max) {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\t// Skip blank lines or initial states lines\n\t\t\t\tif (\"\".equals(record[0]) || \"-\".equals(record[0])) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tlines++;\n\t\t\t\t// Detect if model is non-probabilistic (e.g. LTS)\n\t\t\t\tnonprob = false;\n\t\t\t\tif (nondet) {\n\t\t\t\t\tif (record.length == 3) {\n\t\t\t\t\t\t// LTS\n\t\t\t\t\t\tnonprob = true;\n\t\t\t\t\t} else if (record.length >= 4) {\n\t\t\t\t\t\t// LTS with actions or MDP\n\t\t\t\t\t\tnonprob = Prism.isValidIdentifier(record[3]);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (nonprob) {\n\t\t\t\t\treturn ModelType.LTS;\n\t\t\t\t}\n\t\t\t\t// Look at probability/rate\n\t\t\t\t// (give up if line is in unexpected format)\n\t\t\t\tString probOrRate;\n\t\t\t\tif (nondet && record.length >= 4) {\n\t\t\t\t\tprobOrRate = record[3];\n\t\t\t\t} else if (!nondet && record.length >= 3) {\n\t\t\t\t\tprobOrRate = record[2];\n\t\t\t\t} else {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t\t// Interval: guess IMDP/IDTMC\n\t\t\t\tif (probOrRate.matches(\"\\\\[.+,.+\\\\]\")) {\n\t\t\t\t\treturn nondet ? ModelType.IMDP : ModelType.IDTMC;\n\t\t\t\t}\n\t\t\t\t// Get value as double\n\t\t\t\tdouble d;\n\t\t\t\tif (probOrRate.matches(\"[0-9]+/[0-9]+\")) {\n\t\t\t\t\td = new BigRational(probOrRate).doubleValue();\n\t\t\t\t} else {\n\t\t\t\t\td = Double.parseDouble(probOrRate);\n\t\t\t\t}\n\t\t\t\t// Looks like a rate: guess CTMC\n\t\t\t\tif (d > 1) {\n\t\t\t\t\treturn ModelType.CTMC;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// All non-rates seen: guess (PO)MDP/DTMC\n\t\t\treturn nondet ? (partObs ? ModelType.POMDP : ModelType.MDP) : ModelType.DTMC;\n\t\t} catch (NumberFormatException | CsvFormatException | IOException e) {\n\t\t\treturn null;\n\t\t}\n\t}\n\n\t/**\n\t * Traverse the transitions file to detect any deadlock states\n\t * and then store the details in deadlockInfo.\n\t */\n\tprivate void findDeadlocks() throws PrismException\n\t{\n\t\t// Record which states have transitions\n\t\tBitSet statesWithTransitions = new BitSet();\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tfor (String[] record : csv) {\n\t\t\t\tlineNum++;\n\t\t\t\t// Skip blank lines or initial states lines\n\t\t\t\tif (\"\".equals(record[0]) || \"-\".equals(record[0])) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t// Lines should be 3-6 long (LTS/MDP/POMDP with/without actions)\n\t\t\t\tcheckLineSize(record, 3, 6);\n\t\t\t\t// Extract/store source state\n\t\t\t\tint s = checkStateIndex(Integer.parseInt(record[0]), modelStats.numStates);\n\t\t\t\tstatesWithTransitions.set(s);\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\": \" + e.getMessage());\n\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transitions file \\\"\" + transFile + \"\\\"\");\n\t\t}\n\t\t// Store deadlock info\n\t\tdeadlockInfo = new DeadlockInfo();\n\t\tif (statesWithTransitions.cardinality() != modelStats.numStates) {\n\t\t\tfor (int s = statesWithTransitions.nextClearBit(0); s < modelStats.numStates; s = statesWithTransitions.nextClearBit(s + 1)) {\n\t\t\t\tdeadlockInfo.deadlocks.set(s);\n\t\t\t\tdeadlockInfo.numDeadlocks++;\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractStates(IOUtils.StateDefnConsumer storeStateDefn) throws PrismException\n\t{\n\t\t// If there is no info, just assume that states comprise a single integer value\n\t\tif (getStatesFile() == null) {\n\t\t\tsuper.extractStates(storeStateDefn);\n\t\t\treturn;\n\t\t}\n\t\t// Otherwise extract from .sta file\n\t\textractStateDefinitions(statesFile, getModelInfo().getNumVars(), storeStateDefn);\n\t}\n\n\t@Override\n\tpublic void extractObservationDefinitions(IOUtils.StateDefnConsumer storeObservationDefn) throws PrismException\n\t{\n\t\t// If there is no info, just assume that observations comprise a single integer observable\n\t\tif (getObservationsFile() == null) {\n\t\t\tsuper.extractObservationDefinitions(storeObservationDefn);\n\t\t\treturn;\n\t\t}\n\t\t// Otherwise extract from .obs file\n\t\textractStateDefinitions(observationsFile, getModelInfo().getNumObservables(), storeObservationDefn);\n\t}\n\n\t/**\n\t * Extract state definitions from a states/observables (.sta/.obs) file.\n\t * Calls {@code storeStateDefn(s, i, v)} for each state s, variable (index) i and variable value v.\n\t * @param file States/observations  (.sta/.obs) file\n\t * @param numVars Number of variables/observables\n\t * @param storeStateDefn Consumer to store state/observation definitions\n\t */\n\tprivate void extractStateDefinitions(File file, int numVars, IOUtils.StateDefnConsumer storeStateDefn) throws PrismException\n\t{\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(file))) {\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tString st = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (st != null) {\n\t\t\t\tst = st.trim();\n\t\t\t\tif (!st.isEmpty()) {\n\t\t\t\t\t// Split into two parts\n\t\t\t\t\tString[] ss = st.split(\":\");\n\t\t\t\t\t// Determine which state this line describes\n\t\t\t\t\tint s = checkStateIndex(Integer.parseInt(ss[0]), modelStats.numStates);\n\t\t\t\t\t// Now split up middle bit and extract var info\n\t\t\t\t\tss = ss[1].substring(ss[1].indexOf('(') + 1, ss[1].indexOf(')')).split(\",\");\n\n\t\t\t\t\tState state = new State(numVars);\n\t\t\t\t\tif (ss.length != numVars)\n\t\t\t\t\t\tthrow new PrismException(\"(wrong number of variable values) \");\n\t\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\t\tif (ss[i].equals(\"true\")) {\n\t\t\t\t\t\t\tstoreStateDefn.accept(s, i, Boolean.TRUE);\n\t\t\t\t\t\t} else if (ss[i].equals(\"false\")) {\n\t\t\t\t\t\t\tstoreStateDefn.accept(s, i, Boolean.FALSE);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tstoreStateDefn.accept(s, i, Integer.parseInt(ss[i]));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tst = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of states file \\\"\" + file + \"\\\"\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic int computeMaxNumChoices() throws PrismException\n\t{\n\t\tint lineNum = 0;\n\t\tint maxNumChoices = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tfor (String[] record : csv) {\n\t\t\t\tlineNum++;\n\t\t\t\t// Skip blank lines or initial states lines\n\t\t\t\tif (\"\".equals(record[0]) || \"-\".equals(record[0])) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t// Lines should be 3-5 long (LTS/MDP/POMDP with/without actions)\n\t\t\t\tcheckLineSize(record, 3, 6);\n\t\t\t\tint j = checkChoiceIndex(Integer.parseInt(record[1]));\n\t\t\t\tif (j + 1 > maxNumChoices) {\n\t\t\t\t\tmaxNumChoices = j + 1;\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\": \" + e.getMessage());\n\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transitions file \\\"\" + transFile + \"\\\"\");\n\t\t}\n\t\tif (fixdl && getNumDeadlockStates() > 0) {\n\t\t\tmaxNumChoices = Math.max(maxNumChoices, 1);\n\t\t}\n\t\treturn maxNumChoices;\n\t}\n\n\t@Override\n\tpublic <Value> void extractMCTransitions(IOUtils.MCTransitionConsumer<Value> storeTransition, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tBitSet deadlocks = new BitSet();\n\t\tint nextDeadlock = -1;\n\t\tif (fixdl) {\n\t\t\tdeadlocks = getDeadlockStates();\n\t\t\tnextDeadlock = deadlocks.nextSetBit(0);\n\t\t}\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tfor (String[] record : csv) {\n\t\t\t\tlineNum++;\n\t\t\t\t// Skip blank lines or initial states lines\n\t\t\t\tif (\"\".equals(record[0]) || \"-\".equals(record[0])) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tcheckLineSize(record, 3, 4);\n\t\t\t\tint s = checkStateIndex(Integer.parseInt(record[0]), modelStats.numStates);\n\t\t\t\tint s2 = checkStateIndex(Integer.parseInt(record[1]), modelStats.numStates);\n\t\t\t\tValue v = checkValue(record[2], eval);\n\t\t\t\tObject a = (record.length > 3) ? checkAction(record[3]) : null;\n\t\t\t\t// Add self-loops for any deadlock states before s\n\t\t\t\twhile (nextDeadlock != -1 && nextDeadlock < s) {\n\t\t\t\t\tstoreTransition.accept(nextDeadlock, nextDeadlock, eval.one(), null);\n\t\t\t\t\tnextDeadlock = deadlocks.nextSetBit(nextDeadlock + 1);\n\t\t\t\t}\n\t\t\t\t// Add transition\n\t\t\t\tstoreTransition.accept(s, s2, v, a);\n\t\t\t}\n\t\t\t// Add self-loops for any remaining deadlock states\n\t\t\twhile (nextDeadlock != -1) {\n\t\t\t\tstoreTransition.accept(nextDeadlock, nextDeadlock, eval.one(), null);\n\t\t\t\tnextDeadlock = deadlocks.nextSetBit(nextDeadlock + 1);\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transitions file \\\"\" + transFile + \"\\\"\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractMDPTransitions(IOUtils.MDPTransitionConsumer<Value> storeTransition, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tBitSet deadlocks = new BitSet();\n\t\tint nextDeadlock = -1;\n\t\tif (fixdl) {\n\t\t\tdeadlocks = getDeadlockStates();\n\t\t\tnextDeadlock = deadlocks.nextSetBit(0);\n\t\t}\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tfor (String[] record : csv) {\n\t\t\t\tlineNum++;\n\t\t\t\t// Skip blank lines or initial states lines\n\t\t\t\tif (\"\".equals(record[0]) || \"-\".equals(record[0])) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t// Lines should be 4-6 long (MDP/POMDP with/without actions)\n\t\t\t\tcheckLineSize(record, 4, 6);\n\t\t\t\tint s = checkStateIndex(Integer.parseInt(record[0]), modelStats.numStates);\n\t\t\t\tint i = checkChoiceIndex(Integer.parseInt(record[1]));\n\t\t\t\tint s2 = checkStateIndex(Integer.parseInt(record[2]), modelStats.numStates);\n\t\t\t\tValue v = checkValue(record[3], eval);\n\t\t\t\tint actIndex = getModelInfo().getModelType().partiallyObservable() ? 5 : 4;\n\t\t\t\tObject a = (record.length > actIndex) ? checkAction(record[actIndex]) : null;\n\t\t\t\t// Add self-loops for any deadlock states before s\n\t\t\t\twhile (nextDeadlock != -1 && nextDeadlock < s) {\n\t\t\t\t\tstoreTransition.accept(nextDeadlock, 0, nextDeadlock, eval.one(), null);\n\t\t\t\t\tnextDeadlock = deadlocks.nextSetBit(nextDeadlock + 1);\n\t\t\t\t}\n\t\t\t\t// Add transition\n\t\t\t\tstoreTransition.accept(s, i, s2, v, a);\n\t\t\t}\n\t\t\t// Add self-loops for any remaining deadlock states\n\t\t\twhile (nextDeadlock != -1) {\n\t\t\t\tstoreTransition.accept(nextDeadlock, 0, nextDeadlock, eval.one(), null);\n\t\t\t\tnextDeadlock = deadlocks.nextSetBit(nextDeadlock + 1);\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transitions file \\\"\" + transFile + \"\\\"\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractLTSTransitions(IOUtils.LTSTransitionConsumer storeTransition) throws PrismException\n\t{\n\t\tBitSet deadlocks = new BitSet();\n\t\tint nextDeadlock = -1;\n\t\tif (fixdl) {\n\t\t\tdeadlocks = getDeadlockStates();\n\t\t\tnextDeadlock = deadlocks.nextSetBit(0);\n\t\t}\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tfor (String[] record : csv) {\n\t\t\t\tlineNum++;\n\t\t\t\t// Skip blank lines or initial states lines\n\t\t\t\tif (\"\".equals(record[0]) || \"-\".equals(record[0])) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tcheckLineSize(record, 3, 4);\n\t\t\t\tint s = checkStateIndex(Integer.parseInt(record[0]), modelStats.numStates);\n\t\t\t\tint i = checkChoiceIndex(Integer.parseInt(record[1]));\n\t\t\t\tint s2 = checkStateIndex(Integer.parseInt(record[2]), modelStats.numStates);\n\t\t\t\tObject a = (record.length > 3) ? checkAction(record[3]) : null;\n\t\t\t\t// Add self-loops for any deadlock states before s\n\t\t\t\twhile (nextDeadlock != -1 && nextDeadlock < s) {\n\t\t\t\t\tstoreTransition.accept(nextDeadlock, 0, nextDeadlock, null);\n\t\t\t\t\tnextDeadlock = deadlocks.nextSetBit(nextDeadlock + 1);\n\t\t\t\t}\n\t\t\t\t// Add transition\n\t\t\t\tstoreTransition.accept(s, i, s2, a);\n\t\t\t}\n\t\t\t// Add self-loops for any remaining deadlock states\n\t\t\twhile (nextDeadlock != -1) {\n\t\t\t\tstoreTransition.accept(nextDeadlock, 0, nextDeadlock, null);\n\t\t\t\tnextDeadlock = deadlocks.nextSetBit(nextDeadlock + 1);\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transitions file \\\"\" + transFile + \"\\\"\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractLabelsAndInitialStates(BiConsumer<Integer, Integer> storeLabel, Consumer<Integer> storeInit, Consumer<Integer> storeDeadlock) throws PrismException\n\t{\n\t\t// Extract any initial states info from the .tra file first\n\t\tBitSet initialStatesTra = new BitSet();\n\t\tif (transFileProvidesInitialStates()) {\n\t\t\textractInitialStatesFromTransFile(initialStatesTra::set);\n\t\t}\n\n\t\t// If there is no .lab file, we are done; just store initial states\n\t\t// Assume that 0 is the initial state in the absence of any other info\n\t\tif (getLabelsFile() == null) {\n\t\t\tif (transFileProvidesInitialStates()) {\n\t\t\t\tfor (int s = initialStatesTra.nextSetBit(0); s >= 0; s = initialStatesTra.nextSetBit(s + 1)) {\n\t\t\t\t\tstoreInit.accept(s);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tstoreInit.accept(0);\n\t\t\t}\n\t\t\treturn;\n\t\t}\n\n\t\t// Otherwise extract from .lab file\n\t\tBitSet initialStatesLab = new BitSet();\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(labelsFile))) {\n\t\t\t// Skip first file (label names extracted earlier with model info)\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tString st = in.readLine();\n\t\t\twhile (st != null) {\n\t\t\t\t// Skip blank lines\n\t\t\t\tst = st.trim();\n\t\t\t\tif (!st.isEmpty()) {\n\t\t\t\t\t// Split line\n\t\t\t\t\tString[] ss = st.split(\":\");\n\t\t\t\t\tint s = checkStateIndex(Integer.parseInt(ss[0].trim()), modelStats.numStates);\n\t\t\t\t\tss = ss[1].trim().split(\" \");\n\t\t\t\t\tfor (int j = 0; j < ss.length; j++) {\n\t\t\t\t\t\tif (ss[j].isEmpty()) {\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// Store label info\n\t\t\t\t\t\tint i = checkLabelIndex(ss[j]);\n\t\t\t\t\t\tint l = labelMap.get(i);\n\t\t\t\t\t\tif (l == -2) {\n\t\t\t\t\t\t\tif (storeDeadlock != null) {\n\t\t\t\t\t\t\t\tstoreDeadlock.accept(s);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} else if (l == -1) {\n\t\t\t\t\t\t\tinitialStatesLab.set(s);\n\t\t\t\t\t\t} else if (l > -1) {\n\t\t\t\t\t\t\tstoreLabel.accept(s, l);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Prepare for next iter\n\t\t\t\tst = in.readLine();\n\t\t\t}\n\n\t\t\t// If initial states were provided in .tra file, we check for consistency with .lab file\n\t\t\tif (transFileProvidesInitialStates()) {\n\t\t\t\tif (!initialStatesTra.equals(initialStatesLab)) {\n\t\t\t\t\tthrow new PrismException(\"Inconsistent initial states information between transitions and labels files\");\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Finally, store initial states\n\t\t\tfor (int s = initialStatesLab.nextSetBit(0); s >= 0; s = initialStatesLab.nextSetBit(s + 1)) {\n\t\t\t\tstoreInit.accept(s);\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + labelsFile + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of labels file \\\"\" + labelsFile + \"\\\"\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractObservations(IOUtils.StateIntConsumer storeObservation) throws PrismException\n\t{\n\t\t// Skip this if model is not partially observable\n\t\tif (!getModelInfo().getModelType().partiallyObservable()) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Extract observations from transitions file\n\t\t// Temporarily store in an array to check for conflicting info\n\t\tint observations[] = new int[modelStats.numStates];\n\t\tArrays.fill(observations, -1);\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tfor (String[] record : csv) {\n\t\t\t\tlineNum++;\n\t\t\t\tif (\"\".equals(record[0])) {\n\t\t\t\t\t// Skip blank lines\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\t// Lines should be 5-6 long (POMDP with/without actions)\n\t\t\t\tcheckLineSize(record, 5, 6);\n\t\t\t\tint s2 = checkStateIndex(Integer.parseInt(record[2]), modelStats.numStates);\n\t\t\t\tint o = checkStateIndex(Integer.parseInt(record[4]), modelStats.numStates);\n\t\t\t\t// Check/store observation\n\t\t\t\tif (observations[s2] != -1 && observations[s2] != o) {\n\t\t\t\t\tthrow new PrismException(\"Conflicting observation information for state \" + s2);\n\t\t\t\t}\n\t\t\t\tobservations[s2] = o;\n\t\t\t}\n\t\t\t// Finally, store observations in the model\n\t\t\tfor (int s = 0; s < modelStats.numStates; s++) {\n\t\t\t\tif (observations[s] == -1) {\n\t\t\t\t\tthrow new PrismException(\"No observation information for state \" + s);\n\t\t\t\t} else {\n\t\t\t\t\tstoreObservation.accept(s, observations[s]);\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transitions file \\\"\" + transFile + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Extract any info about initial states stored in the .tra file.\n\t * Calls {@code storeInit(s)} for each initial state s.\n\t * @param storeInit Function to be called for each initial state\n\t */\n\tprivate void extractInitialStatesFromTransFile(Consumer<Integer> storeInit) throws PrismException\n\t{\n\t\tModelType modelType = getModelInfo().getModelType();\n\t\tint stateField = modelType.nondeterministic() ? 2 : 1;\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(transFile))) {\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\tfor (String[] record : csv) {\n\t\t\t\tlineNum++;\n\t\t\t\t// Skip blank lines\n\t\t\t\tif (\"\".equals(record[0])) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tcheckLineSize(record, 3, 6);\n\t\t\t\t// Break as soon as a non-initial states line is found\n\t\t\t\tif (!\"-\".equals(record[0])) {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tint s2 = checkStateIndex(Integer.parseInt(record[stateField]), modelStats.numStates);\n\t\t\t\tstoreInit.accept(s2);\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transitions file \\\"\" + transFile + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Load all labels from a PRISM labels (.lab) file and store them in BitSet objects.\n\t * Return a map from label name Strings to BitSets.\n\t * This is for all labels in the file, including \"init\", \"deadlock\".\n\t * Note: the size of the BitSet may be smaller than the number of states.\n\t */\n\tpublic Map<String, BitSet> extractAllLabels() throws PrismException\n\t{\n\t\t// This method only needs the label file\n\t\tif (getLabelsFile() == null) {\n\t\t\tthrow new PrismException(\"No labels information available\");\n\t\t}\n\t\t// Extract names first\n\t\textractLabelNamesFromLabelsFile(labelsFile);\n\t\t// Build list of bitsets\n\t\tBitSet[] bitsets = new BitSet[labelMap.size()];\n\t\tfor (int i = 0; i < bitsets.length; i++) {\n\t\t\tbitsets[i] = new BitSet();\n\t\t}\n\t\t// Otherwise extract from .lab file\n\t\tint lineNum = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(labelsFile))) {\n\t\t\t// Skip first file (label names extracted earlier)\n\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\tString st = in.readLine();\n\t\t\twhile (st != null) {\n\t\t\t\t// Skip blank lines\n\t\t\t\tst = st.trim();\n\t\t\t\tif (!st.isEmpty()) {\n\t\t\t\t\t// Split line\n\t\t\t\t\tString[] ss = st.split(\":\");\n\t\t\t\t\tint s = checkStateIndex(Integer.parseInt(ss[0].trim()));\n\t\t\t\t\tss = ss[1].trim().split(\" \");\n\t\t\t\t\tfor (int j = 0; j < ss.length; j++) {\n\t\t\t\t\t\tif (ss[j].isEmpty()) {\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// Store label info\n\t\t\t\t\t\tint i = checkLabelIndex(ss[j]);\n\t\t\t\t\t\tbitsets[i].set(s);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Prepare for next iter\n\t\t\t\tst = in.readLine();\n\t\t\t}\n\t\t\t// Build BitSet map\n\t\t\tMap<String, BitSet> map = new HashMap<>();\n\t\t\tfor (int i = 0; i < bitsets.length; i++) {\n\t\t\t\tint l = labelMap.get(i);\n\t\t\t\tif (l == -1) {\n\t\t\t\t\tmap.put(\"init\", bitsets[i]);\n\t\t\t\t} else if (l  == -2) {\n\t\t\t\t\tmap.put(\"deadlock\", bitsets[i]);\n\t\t\t\t} else if (l > -1) {\n\t\t\t\t\tmap.put(basicModelInfo.getLabelNameList().get(l), bitsets[i]);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn map;\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + labelsFile + \"\\\"\");\n\t\t} catch (PrismException | NumberFormatException e) {\n\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of labels file \\\"\" + labelsFile + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Build/store rewards info from the input files.\n\t * Can then be accessed via {@link #getRewardInfo()}.\n\t */\n\tprivate void buildRewardInfo() throws PrismException\n\t{\n\t\tbasicRewardInfo = new BasicRewardInfo();\n\t\tint numRewards = Math.max(stateRewardsReaders.size(), transRewardsReaders.size());\n\t\tfor (int r = 0; r < numRewards; r++) {\n\t\t\tString stateRewardName = null;\n\t\t\tString transRewardName = null;\n\t\t\tif (r < stateRewardsReaders.size()) {\n\t\t\t\tstateRewardName = stateRewardsReaders.get(r).getName().orElse(\"\");\n\t\t\t}\n\t\t\tif (r < transRewardsReaders.size()) {\n\t\t\t\ttransRewardName = transRewardsReaders.get(r).getName().orElse(\"\");\n\t\t\t}\n\t\t\tif (transRewardName != null && stateRewardName != null && !transRewardName.equals(stateRewardName)) {\n\t\t\t\tthrow new PrismException(\"Reward structure names do not match for state/transition rewards\");\n\t\t\t}\n\t\t\tbasicRewardInfo.addReward(stateRewardName != null ? stateRewardName : transRewardName);\n\t\t\tbasicRewardInfo.setHasStateRewards(r, r < stateRewardsReaders.size());\n\t\t\tbasicRewardInfo.setHasTransitionRewards(r, r < transRewardsReaders.size());\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractStateRewards(int rewardIndex, BiConsumer<Integer, Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tif (rewardIndex < stateRewardsReaders.size()) {\n\t\t\tRewardFile file = stateRewardsReaders.get(rewardIndex);\n\t\t\tfile.extractStateRewards(storeReward, eval);\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractMCTransitionRewards(int rewardIndex, IOUtils.TransitionRewardConsumer<Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tif (rewardIndex < transRewardsReaders.size()) {\n\t\t\tRewardFile file = transRewardsReaders.get(rewardIndex);\n\t\t\tfile.extractMCTransitionRewards(storeReward, eval);\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractMDPTransitionRewards(int rewardIndex, IOUtils.TransitionRewardConsumer<Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tif (rewardIndex < transRewardsReaders.size()) {\n\t\t\tRewardFile file = transRewardsReaders.get(rewardIndex);\n\t\t\tfile.extractMDPTransitionRewards(storeReward, eval);\n\t\t}\n\t}\n\n\tpublic class RewardFile\n\t{\n\t\tprotected final File file;\n\t\tprotected final Optional<String> name;\n\n\t\tpublic RewardFile(File file) throws PrismException\n\t\t{\n\t\t\tthis.file = Objects.requireNonNull(file);\n\t\t\tthis.name = extractRewardStructureName(file);\n\t\t}\n\n\t\tpublic Optional<String> getName()\n\t\t{\n\t\t\treturn name;\n\t\t}\n\n\t\t/**\n\t\t * Extract the state rewards from a .srew file.\n\t\t * The rewards are assumed to be of type double.\n\t\t * @param storeReward Function to be called for each reward\n\t\t */\n\t\tprotected void extractStateRewards(BiConsumer<Integer, Double> storeReward) throws PrismException\n\t\t{\n\t\t\textractStateRewards(storeReward, Evaluator.forDouble());\n\t\t}\n\n\t\t/**\n\t\t * Extract the state rewards from a .srew file.\n\t\t * The rewards are assumed to be of type Value.\n\t\t * @param storeReward Function to be called for each reward\n\t\t * @param eval Evaluator for Value objects\n\t\t */\n\t\tprotected <Value> void extractStateRewards(BiConsumer<Integer, Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t\t{\n\t\t\tint lineNum = 0;\n\t\t\ttry (BufferedReader in = new BufferedReader(new FileReader(file))) {\n\t\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\t\tfor (String[] record : csv) {\n\t\t\t\t\tlineNum++;\n\t\t\t\t\tif (\"\".equals(record[0])) {\n\t\t\t\t\t\t// Skip blank lines\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\tcheckLineSize(record, 2, 2);\n\t\t\t\t\tint s = checkStateIndex(Integer.parseInt(record[0]), modelStats.numStates);\n\t\t\t\t\tValue v = checkValue(record[1], eval);\n\t\t\t\t\tstoreReward.accept(s, v);\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of state rewards file \\\"\" + file + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Extract the (Markov chain) transition rewards from a .trew file.\n\t\t * The rewards are assumed to be of type double.\n\t\t * @param storeReward Function to be called for each reward\n\t\t */\n\t\tprotected void extractMCTransitionRewards(IOUtils.TransitionRewardConsumer<Double> storeReward) throws PrismException\n\t\t{\n\t\t\textractMCTransitionRewards(storeReward, Evaluator.forDouble());\n\t\t}\n\n\t\t/**\n\t\t * Extract the (Markov chain) transition rewards from a .trew file.\n\t\t * The rewards are assumed to be of type Value.\n\t\t * @param storeReward Function to be called for each reward\n\t\t * @param eval Evaluator for Value objects\n\t\t */\n\t\tprotected <Value> void extractMCTransitionRewards(IOUtils.TransitionRewardConsumer<Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t\t{\n\t\t\t// Check that we have access to a model if needed for transition indexing\n\t\t\t// If not, we build one via this importer\n\t\t\tif (transitionRewardIndexing == TransitionRewardIndexing.OFFSET && modelLookup == null) {\n\t\t\t\tmodelLookup = new DTMCSimple<>();\n\t\t\t\t((ModelExplicit) modelLookup).setEvaluator(eval);\n\t\t\t\t((ModelExplicit) modelLookup).buildFromExplicitImport(PrismExplicitImporter.this);\n\t\t\t}\n\n\t\t\tint lineNum = 0;\n\t\t\ttry (BufferedReader in = new BufferedReader(new FileReader(file))) {\n\t\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\t\tfor (String[] record : csv) {\n\t\t\t\t\tlineNum++;\n\t\t\t\t\tif (\"\".equals(record[0])) {\n\t\t\t\t\t\t// Skip blank lines\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\tcheckLineSize(record, 3, 3);\n\t\t\t\t\tint s = checkStateIndex(Integer.parseInt(record[0]), modelStats.numStates);\n\t\t\t\t\tint s2 = checkStateIndex(Integer.parseInt(record[1]), modelStats.numStates);\n\t\t\t\t\tValue v = checkValue(record[2], eval);\n\n\t\t\t\t\tswitch (transitionRewardIndexing) {\n\t\t\t\t\t\tcase STATE:\n\t\t\t\t\t\t\tstoreReward.accept(s, s2, v);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase OFFSET:\n\t\t\t\t\t\t\t// Need to look up transition offset from successor state\n\t\t\t\t\t\t\tSuccessorsIterator it = modelLookup.getSuccessors(s);\n\t\t\t\t\t\t\tint i = 0;\n\t\t\t\t\t\t\twhile (it.hasNext()) {\n\t\t\t\t\t\t\t\tif (it.nextInt() == s2) {\n\t\t\t\t\t\t\t\t\tstoreReward.accept(s, i, v);\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\ti++;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tif (i > modelLookup.getNumTransitions(s)) {\n\t\t\t\t\t\t\t\tthrow new PrismException(\"No matching transition for transition reward \" + s + \"->\" + s2);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tthrow new PrismException(\"Unknown transition reward indexing \" + transitionRewardIndexing);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transition rewards file \\\"\" + file + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Extract the (Markov decision process) transition rewards from a .trew file.\n\t\t * The rewards are assumed to be of type double.\n\t\t * @param storeReward Function to be called for each reward\n\t\t */\n\t\tprotected void extractMDPTransitionRewards(IOUtils.TransitionRewardConsumer<Double> storeReward) throws PrismException\n\t\t{\n\t\t\textractMDPTransitionRewards(storeReward, Evaluator.forDouble());\n\t\t}\n\n\t\t/**\n\t\t * Extract the (Markov decision process) transition rewards from a .trew file.\n\t\t * The rewards are assumed to be of type Value.\n\t\t * @param storeReward Function to be called for each reward\n\t\t * @param eval Evaluator for Value objects\n\t\t */\n\t\tprotected <Value> void extractMDPTransitionRewards(IOUtils.TransitionRewardConsumer<Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t\t{\n\t\t\tint lineNum = 0;\n\t\t\ttry (BufferedReader in = new BufferedReader(new FileReader(file))) {\n\t\t\t\tlineNum += skipCommentAndFirstLine(in);\n\t\t\t\tBasicReader reader = BasicReader.wrap(in).normalizeLineEndings();\n\t\t\t\tCsvReader csv = new CsvReader(reader, false, false, false, ' ', LF);\n\t\t\t\tint count = 0;\n\t\t\t\tint sLast = -1;\n\t\t\t\tint iLast = -1;\n\t\t\t\tValue vLast = null;\n\t\t\t\tfor (String[] record : csv) {\n\t\t\t\t\tlineNum++;\n\t\t\t\t\tif (\"\".equals(record[0])) {\n\t\t\t\t\t\t// Skip blank lines\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\tcheckLineSize(record, 4, 4);\n\t\t\t\t\tint s = checkStateIndex(Integer.parseInt(record[0]), modelStats.numStates);\n\t\t\t\t\tint i = checkChoiceIndex(Integer.parseInt(record[1]));\n\t\t\t\t\tint s2 = checkStateIndex(Integer.parseInt(record[2]), modelStats.numStates);\n\t\t\t\t\tValue v = checkValue(record[3], eval);\n\t\t\t\t\t// Check that transition rewards for the same state/choice are the same\n\t\t\t\t\t// (currently no support for state-choice-state rewards)\n\t\t\t\t\tif (s == sLast && i == iLast) {\n\t\t\t\t\t\tif (!eval.equals(vLast, v)) {\n\t\t\t\t\t\t\tthrow new PrismException(\"mismatching transition rewards \" + vLast + \" and \" + v + \" in choice \" + i + \" of state \" + s);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// If possible, check that were rewards on all successors for each choice\n\t\t\t\t\t// (for speed, we just check that the right number were present)\n\t\t\t\t\t// For now, don't bother to check that the reward is the same for all s2\n\t\t\t\t\t// for a given state s and index i (so the first one in the file will define it)\n\t\t\t\t\telse {\n\t\t\t\t\t\tif (modelLookup != null && modelLookup instanceof NondetModel && sLast != -1 && count != ((NondetModel<?>) modelLookup).getNumTransitions(sLast, iLast)) {\n\t\t\t\t\t\t\tthrow new PrismException(\"wrong number of transition rewards in choice \" + iLast + \" of state \" + sLast);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tsLast = s;\n\t\t\t\t\t\tiLast = i;\n\t\t\t\t\t\tvLast = v;\n\t\t\t\t\t\tcount = 0;\n\t\t\t\t\t}\n\t\t\t\t\t// Only store the reward for the first instance of state-choice (s,i)\n\t\t\t\t\tif (count == 0) {\n\t\t\t\t\t\tstoreReward.accept(s, i, v);\n\t\t\t\t\t}\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t\t} catch (PrismException | NumberFormatException | CsvFormatException e) {\n\t\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of transition rewards file \\\"\" + file + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Extract the name of the state rewards structure if present.\n\t\t *\n\t\t * @param rewardFile a state rewards file\n\t\t * @return name of the state rewards structure if present\n\t\t * @throws PrismException if an I/O error occurs or the name is not a unique identifier\n\t\t */\n\t\tprotected Optional<String> extractRewardStructureName(File rewardFile) throws PrismException\n\t\t{\n\t\t\tint lineNum = 0;\n\t\t\tOptional<String> name = Optional.empty();\n\t\t\ttry (BufferedReader in = new BufferedReader(new FileReader(rewardFile))) {\n\t\t\t\tfor (String line = in.readLine(); line != null; line = in.readLine()) {\n\t\t\t\t\tlineNum++;\n\t\t\t\t\t// Process only initial comment block\n\t\t\t\t\tif (!COMMENT_PATTERN.matcher(line).matches()) {\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t\t// Look for reward name in header\n\t\t\t\t\tMatcher headerMatcher = REWARD_NAME_PATTERN.matcher(line);\n\t\t\t\t\tif (headerMatcher.matches()) {\n\t\t\t\t\t\tif (name.isPresent()) {\n\t\t\t\t\t\t\tthrow new PrismException(\"multiple reward structure names\");\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// check if reward struct name is an identifier\n\t\t\t\t\t\tname = Optional.of(checkRewardName(headerMatcher.group(2)));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t\t} catch (PrismException e) {\n\t\t\t\tString expl = (e.getMessage() == null || e.getMessage().isEmpty()) ? \"\" : (\" (\" + e.getMessage() + \")\");\n\t\t\t\tthrow new PrismException(\"Error detected\" + expl + \" at line \" + lineNum + \" of rewards file \\\"\" + file + \"\\\"\");\n\t\t\t}\n\t\t\treturn name;\n\t\t}\n\t}\n\n\t/**\n\t * Skip the next block of lines starting with # and the first line after.\n\t *\n\t * @param in reader\n\t * @return number of lines read\n\t * @throws IOException if an I/O error occurs\n\t */\n\tprotected static int skipCommentAndFirstLine(BufferedReader in) throws IOException\n\t{\n\t\tint lineNum = 0;\n\t\tString line;\n\t\tdo {\n\t\t\tline = in.readLine();\n\t\t\tlineNum++;\n\t\t} while (line != null && COMMENT_PATTERN.matcher(line).matches());\n\t\treturn lineNum;\n\t}\n\n\t// Utility method to check inputs and generate errors\n\n\tprotected static void checkLineSize(String[] record, int min, int max) throws PrismException\n\t{\n\t\tif (record.length < min) {\n\t\t\tthrow new PrismException(\"too few entries\");\n\t\t}\n\t\tif (record.length > max) {\n\t\t\tthrow new PrismException(\"too many entries\");\n\t\t}\n\t}\n\n\tprotected static void checkLineSize(String[] record, int min) throws PrismException\n\t{\n\t\tif (record.length < min) {\n\t\t\tthrow new PrismException(\"too few entries\");\n\t\t}\n\t}\n\n\tprotected static int checkStateIndex(int s) throws PrismException\n\t{\n\t\tif (s < 0) {\n\t\t\tthrow new PrismException(\"state index \" + s + \" is invalid\");\n\t\t}\n\t\treturn s;\n\t}\n\n\tprotected static int checkStateIndex(int s, int numStates) throws PrismException\n\t{\n\t\tif (s < 0) {\n\t\t\tthrow new PrismException(\"state index \" + s + \" is invalid\");\n\t\t}\n\t\tif (s > numStates) {\n\t\t\tthrow new PrismException(\"state index \" + s + \" exceeds number of states\");\n\t\t}\n\t\treturn s;\n\t}\n\n\tprotected static int checkChoiceIndex(int i) throws PrismException\n\t{\n\t\tif (i < 0) {\n\t\t\tthrow new PrismException(\"choice index \" + i + \" is invalid\");\n\t\t}\n\t\treturn i;\n\t}\n\n\tprotected static int checkLabelIndex(String s) throws PrismException\n\t{\n\t\ttry {\n\t\t\tint i = Integer.parseInt(s);\n\t\t\tif (i < 0) {\n\t\t\t\tthrow new PrismException(\"label index \" + i + \" is invalid\");\n\t\t\t}\n\t\t\treturn i;\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"label index \\\"\" + s + \"\\\" is invalid\");\n\t\t}\n\t}\n\n\tprotected static <Value> Value checkValue(String v, Evaluator<Value> eval) throws PrismException\n\t{\n\t\ttry {\n\t\t\treturn eval.fromString(v);\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"invalid value \\\"\" + v + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Check that a (string) action label is legal and return it if so.\n\t * Otherwise, an explanatory exception is thrown.\n\t * A legal action label is either \"\" (unlabelled) or a legal PRISM identifier.\n\t * In the case of an empty (\"\") action, this returns null.\n\t */\n\tprotected static String checkAction(String a) throws PrismException\n\t{\n\t\tif (a == null || a.isEmpty()) {\n\t\t\treturn null;\n\t\t}\n\t\tif (!Prism.isValidIdentifier(a)) {\n\t\t\tthrow new PrismException(\"invalid action name \\\"\" + a + \"\\\"\");\n\t\t}\n\t\treturn a;\n\t}\n\n\tprotected static String checkRewardName(String rewardStructName) throws PrismException\n\t{\n\t\tif (rewardStructName == null) {\n\t\t\tthrow new PrismException(\"missing reward name\");\n\t\t}\n\t\tif (!Prism.isValidIdentifier(rewardStructName)) {\n\t\t\tthrow new PrismLangException(\"invalid reward name \\\"\" + rewardStructName + \"\\\"\");\n\t\t}\n\t\treturn rewardStructName;\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/RewardTuple.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport prism.PrismUtils;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.function.Function;\nimport java.util.stream.Collectors;\n\n/**\n * Storage of values for reward structures, for the purposes of import/export.\n */\npublic class RewardTuple<Value>\n{\n\tprivate List<Value> values;\n\n\tpublic RewardTuple()\n\t{\n\t\tvalues = new ArrayList<>();\n\t}\n\n\tpublic RewardTuple(int numRewardStructs)\n\t{\n\t\tvalues = new ArrayList<>(numRewardStructs);\n\t}\n\n\tpublic void add(Value value)\n\t{\n\t\tvalues.add(value);\n\t}\n\n\tpublic Value get(int i)\n\t{\n\t\treturn values.get(i);\n\t}\n\n\tpublic String toString(Function<Value, String> valueFormatter, String sep)\n\t{\n\t\treturn \"[\" + values.stream().map(e -> valueFormatter.apply(e)).collect(Collectors.joining(sep)) + \"]\";\n\t}\n\n\tpublic String toStringReversed(Function<Value, String> valueFormatter, String sep)\n\t{\n\t\treturn \"[\" + PrismUtils.listReversedStream(values).map(e -> valueFormatter.apply(e)).collect(Collectors.joining(sep)) + \"]\";\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + values.stream().map(e -> e.toString()).collect(Collectors.joining(\",\")) + \"]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/Transition.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport prism.Evaluator;\n\nimport java.util.Objects;\n\n/**\n * Storage of info about a model transition, for the purposes of import/export.\n * Often, but not always, this will be the probability for the transition.\n */\npublic class Transition<V> implements Comparable<Transition<V>>\n{\n\t/** Index of the target state */\n\tprotected int target;\n\t/** An attached value, e.g. probability */\n\tprotected V value;\n\t/** An attached action label */\n\tprotected Object action;\n\t/** Evaluator for the stored value */\n\tprotected Evaluator<V> evaluator;\n\n\tpublic Transition(int target, V value, Object action, Evaluator<V> evaluator)\n\t{\n\t\tthis.target = target;\n\t\tthis.value = value;\n\t\tthis.action = action;\n\t\tthis.evaluator = evaluator;\n\t}\n\n\t/**\n\t * Is the value for this transition zero?\n\t */\n\tpublic boolean isZero()\n\t{\n\t\treturn evaluator.isZero(value);\n\t}\n\n\t@Override\n\tpublic int compareTo(Transition<V> o)\n\t{\n\t\tint compTarget = Integer.compare(target, o.target);\n\t\tif (compTarget != 0) {\n\t\t\treturn compTarget;\n\t\t}\n\t\treturn Objects.compare(Objects.toString(action), Objects.toString(o.action), String::compareTo);\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (this == o) return true;\n\t\tif (o == null || getClass() != o.getClass()) return false;\n\t\tTransition<?> that = (Transition<?>) o;\n\t\treturn target == that.target && Objects.equals(value, that.value) && Objects.equals(action, that.action);\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\treturn Objects.hash(target, value, action);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString ret = target + \", \" + value;\n\t\tif (action != null) {\n\t\t\tret += \", \" + action;\n\t\t}\n\t\treturn ret;\n\t}\n\n\t/**\n\t * Returns a string representation, formatted according to the provided export options.\n\t */\n\tpublic String toString(ModelExportOptions exportOptions)\n\t{\n\t\treturn evaluator.toStringExport(value, exportOptions.getModelPrecision());\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/UMBExporter.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport explicit.Model;\n\nimport explicit.PartiallyObservableModel;\nimport explicit.rewards.Rewards;\nimport io.github.pmctools.umbj.*;\nimport parser.EvaluateContext;\nimport parser.State;\nimport parser.VarList;\nimport parser.ast.DeclarationBool;\nimport parser.ast.DeclarationDoubleUnbounded;\nimport parser.ast.DeclarationInt;\nimport parser.ast.DeclarationIntUnbounded;\nimport parser.ast.DeclarationType;\nimport parser.type.Type;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismUtils;\n\nimport java.io.File;\nimport java.util.Collections;\nimport java.util.Iterator;\nimport java.util.List;\n\n/**\n * Class to manage export of built models to the UMB file format.\n */\npublic class UMBExporter<Value> extends ModelExporter<Value>\n{\n\t/**\n\t * Construct a UMBExporter with default export options.\n\t */\n\tpublic UMBExporter()\n\t{\n\t\tsuper();\n\t}\n\n\t/**\n\t * Construct a UMBExporter with the specified export options.\n\t */\n\tpublic UMBExporter(ModelExportOptions modelExportOptions)\n\t{\n\t\tsuper(modelExportOptions);\n\t}\n\n\t@Override\n\tpublic void exportModel(Model<Value> model, PrismLog out) throws PrismException\n\t{\n\t\t// Export to PrismLog only for text mode\n\t\tif (!modelExportOptions.getBinaryAsText()) {\n\t\t\tthrow new PrismException(\"Export in UMB binary format must be to a file\");\n\t\t}\n\t\t// Load all model info into a UMBWriter, then export\n\t\tUMBWriter umbWriter = createUMBWriter(model);\n\t\ttry {\n\t\t\tStringBuffer sb = new StringBuffer();\n\t\t\tumbWriter.exportAsText(sb);\n\t\t\tout.print(sb.toString());\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportModel(Model<Value> model, File fileOut) throws PrismException\n\t{\n\t\t// Text mode: write to a PrismLog\n\t\tif (modelExportOptions.getBinaryAsText()) {\n\t\t\ttry (PrismFileLog out = new PrismFileLog(fileOut.getPath())) {\n\t\t\t\texportModel(model, out);\n\t\t\t}\n\t\t}\n\t\t// Otherwise export in binary mode\n\t\t// Load all model info into a UMBWriter, then export\n\t\tUMBWriter umbWriter = createUMBWriter(model);\n\t\ttry {\n\t\t\tModelExportOptions.CompressionFormat compressionDefault = ModelExportOptions.CompressionFormat.fromUMB(UMBFormat.DEFAULT_COMPRESSION_FORMAT);\n\t\t\tUMBFormat.CompressionFormat compressionFormat = modelExportOptions.getCompressionFormat(compressionDefault).toUMB();\n\t\t\tumbWriter.export(fileOut, modelExportOptions.getZipped(), compressionFormat);\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Crate a {@link UMBWriter} to export the specified model to UMB format.\n\t * @param model The model\n\t */\n\tprivate UMBWriter createUMBWriter(Model<Value> model) throws PrismException\n\t{\n\t\t// Get some model info\n\t\tsetEvaluator(model.getEvaluator());\n\t\tEvaluator<Value> evalRewards = getRewardEvaluator();\n\t\tModelType modelType = model.getModelType();\n\t\tint numStates = model.getNumStates();\n\t\tboolean showActions = modelExportOptions.getShowActions();\n\n\t\t// Omit action export if missing or all null\n\t\tList<Object> actions = model.getActions();\n\t\tif (actions.isEmpty() || actions.size() == 1 && actions.get(0) == null) {\n\t\t\tshowActions = false;\n\t\t}\n\n\t\t// Check for currently unsupported cases\n\t\tif (modelType.uncertain() && !modelType.intervals()) {\n\t\t\tthrow new PrismNotSupportedException(modelType + \"s cannot yet be exported to UMB\");\n\t\t}\n\t\tif (model.getEvaluator().isSymbolic()) {\n\t\t\tthrow new PrismNotSupportedException(\"Parametric models cannot yet be exported to UMB\");\n\t\t}\n\n\t\t// Create a ModelAccess object to access the model data in a uniform way\n\t\tModelAccess<Value> modelAccess = ModelAccess.wrap(model);\n\n\t\ttry {\n\n\t\t\t// Create the writer and build the index\n\t\t\tUMBWriter umbWriter = new UMBWriter();\n\t\t\tbuildIndex(modelAccess, umbWriter.getUmbIndex());\n\n\t\t\t// Add core transition info\n\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\tumbWriter.addStateChoiceOffsets(modelAccess.getStateChoiceOffsets());\n\t\t\t\tif (modelType.isProbabilistic()) {\n\t\t\t\t\tumbWriter.addChoiceBranchOffsets(modelAccess.getChoiceTransitionOffsets());\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tumbWriter.addChoiceBranchOffsets(modelAccess.getStateTransitionOffsets());\n\t\t\t}\n\t\t\tif (model.getModelType().isProbabilistic()) {\n\t\t\t\tumbWriter.addBranchProbabilities(modelAccess.getTransitionProbabilitiesAsPrimitives());\n\t\t\t\tif (model.getModelType() == ModelType.CTMC) {\n\t\t\t\t\tumbWriter.addExitRates(modelAccess.getExitRatesAsPrimitives());\n\t\t\t\t}\n\t\t\t}\n\t\t\tumbWriter.addBranchTargets(modelAccess.getTransitionSuccessors());\n\n\t\t\t// Add initial states info\n\t\t\tumbWriter.addInitialStates(modelAccess.getInitialStates());\n\n\t\t\t// Add action labelling info\n\t\t\tif (showActions) {\n\t\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\t\tif (model.getActions().size() > 1) {\n\t\t\t\t\t\tumbWriter.addChoiceActions(modelAccess.getChoiceActionIndices(), modelAccess.getActionStrings());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tumbWriter.addSingleChoiceAction(modelAccess.getActionStrings().get(0));\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (model.getActions().size() > 1) {\n\t\t\t\t\t\tumbWriter.addBranchActions(modelAccess.getTransitionActionIndices(), modelAccess.getActionStrings());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tumbWriter.addSingleBranchAction(modelAccess.getActionStrings().get(0));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Add observation info\n\t\t\tif (modelType.partiallyObservable()) {\n\t\t\t\tumbWriter.addStateObservations(modelAccess.getStateObservations());\n\t\t\t}\n\n\t\t\t// Add label info\n\t\t\tboolean showLabels = modelExportOptions.getShowLabels();\n\t\t\tif (showLabels) {\n\t\t\t\tint numLabels = getNumLabels();\n\t\t\t\tfor (int i = 0; i < numLabels; i++) {\n\t\t\t\t\tumbWriter.addStateAP(getLabelName(i), getLabel(i));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Add reward info\n\t\t\tboolean showRewards = modelExportOptions.getShowRewards();\n\t\t\tif (showRewards) {\n\t\t\t\tint numRewards = getNumRewards();\n\t\t\t\tfor (int r = 0; r < numRewards; r++) {\n\t\t\t\t\tRewards<Value> reward = getReward(r);\n\t\t\t\t\tString id = umbWriter.addRewards(getRewardName(r), evalRewards.exact());\n\t\t\t\t\tif (reward.hasStateRewards()) {\n\t\t\t\t\t\tumbWriter.addStateRewardsByID(id, modelAccess.getStateRewardsAsPrimitives(getReward(r)));\n\t\t\t\t\t}\n\t\t\t\t\tif (reward.hasTransitionRewards()) {\n\t\t\t\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\t\t\t\tumbWriter.addChoiceRewardsByID(id, modelAccess.getTransitionRewardsAsPrimitives(getReward(r)));\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tumbWriter.addBranchRewardsByID(id, modelAccess.getTransitionRewardsAsPrimitives(getReward(r)));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// If there are no rewards, add some dummy zero state rewards\n\t\t\t\t\tif (!(reward.hasStateRewards() || reward.hasTransitionRewards())) {\n\t\t\t\t\t\tumbWriter.addStateRewardsByID(id, Collections.nCopies(numStates, 0.0).iterator());\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Add variable info\n\t\t\tboolean showStates = modelExportOptions.getShowStates();\n\t\t\tif (showStates && modelInfo != null && model.getStatesList() != null) {\n\t\t\t\tVarList varList = modelInfo.createVarList();\n\t\t\t\tstoreVarInfo(varList, model.getStatesList(), UMBIndex.UMBEntity.STATES, umbWriter);\n\t\t\t}\n\n\t\t\t// Add observable info\n\t\t\tboolean showObservations = modelExportOptions.getShowObservations();\n\t\t\tif (showObservations && modelInfo != null && modelInfo.getModelType().partiallyObservable()) {\n\t\t\t\t// Create a VarList for the observables\n\t\t\t\tVarList obsVarList = new VarList();\n\t\t\t\tobsVarList.setEvaluateContext(modelInfo.getEvaluateContext());\n\t\t\t\tint numObservables = modelInfo.getNumObservables();\n\t\t\t\tfor (int i = 0; i < numObservables; i++) {\n\t\t\t\t\tString obsName = modelInfo.getObservableName(i);\n\t\t\t\t\tType obsType = modelInfo.getObservableType(i);\n\t\t\t\t\tDeclarationType obsDecl = obsType.defaultDeclarationType();\n\t\t\t\t\tobsVarList.addVar(obsName, obsDecl, -1);\n\t\t\t\t}\n\t\t\t\t// Store observables\n\t\t\t\tstoreVarInfo(obsVarList, ((PartiallyObservableModel<Value>) model).getObservationsList(), UMBIndex.UMBEntity.OBSERVATIONS, umbWriter);\n\t\t\t}\n\n\t\t\treturn umbWriter;\n\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Build the index for the UMB file, storing model type and stats.\n\t * @param model The model\n\t * @param umbIndex The UMB index to build\n\t */\n\tprivate void buildIndex(ModelAccess<Value> model, UMBIndex umbIndex)\n\t{\n\t\tumbIndex.fileData.tool = Prism.getToolName();\n\t\tumbIndex.fileData.toolVersion = Prism.getVersion();\n\t\tstoreModelTypeInIndex(model, umbIndex);\n\t\tstoreModelStatsInIndex(model, umbIndex);\n\t}\n\n\t/**\n\t * Store info about the model type in the index for the UMB file.\n\t * @param model The model\n\t * @param umbIndex The UMB index to build\n\t */\n\tprivate void storeModelTypeInIndex(ModelAccess<Value> model, UMBIndex umbIndex)\n\t{\n\t\tModelType modelType = model.getModelType();\n\t\tumbIndex.setTime(modelType.continuousTime() ? UMBIndex.Time.STOCHASTIC : UMBIndex.Time.DISCRETE);\n\t\tumbIndex.setNumPlayers(model.getNumPlayers());\n\t\tumbIndex.setNumObservations(model.getNumObservations());\n\t\tif (model.getNumObservations() > 0) {\n\t\t\tumbIndex.setObservationsApplyTo(UMBIndex.UMBEntity.STATES);\n\t\t}\n\t\tboolean rational = model.getEvaluator().exact();\n\t\tif (modelType.isProbabilistic()) {\n\t\t\tumbIndex.setBranchProbabilityType(UMBType.contNum(rational, modelType.intervals()));\n\t\t\tif (!modelType.choicesSumToOne()) {\n\t\t\t\tumbIndex.setExitRateType(UMBType.contNum(rational, modelType.intervals()));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Store stats about the model in the index for the UMB file.\n\t * @param model The model\n\t * @param umbIndex The UMB index to build\n\t */\n\tprivate void storeModelStatsInIndex(ModelAccess<Value> model, UMBIndex umbIndex)\n\t{\n\t\tumbIndex.setNumStates(model.getNumStates());\n\t\tumbIndex.setNumInitialStates(model.getNumInitialStates());\n\t\tumbIndex.setNumChoices(model.getNumChoices());\n\t\tumbIndex.setNumBranches(model.getNumTransitions());\n\t\tif (modelExportOptions.getShowActions()) {\n\t\t\tList<Object> actions = model.getActions();\n\t\t\tint numActions = actions.size();\n\t\t\t// Treat a single 'null' action as no actions\n\t\t\tif (numActions == 1 && actions.get(0) == null) {\n\t\t\t\tnumActions = 0;\n\t\t\t}\n\t\t\tif (model.getModelType().nondeterministic()) {\n\t\t\t\tumbIndex.setNumChoiceActions(numActions);\n\t\t\t\tumbIndex.setNumBranchActions(0);\n\t\t\t} else {\n\t\t\t\tumbIndex.setNumChoiceActions(0);\n\t\t\t\tumbIndex.setNumBranchActions(numActions);\n\t\t\t}\n\t\t} else {\n\t\t\tumbIndex.setNumChoiceActions(0);\n\t\t\tumbIndex.setNumBranchActions(0);\n\t\t}\n\t}\n\n\t/**\n\t * Extract variable/observable info from a VarList and State list and store in UMBWriter.\n\t * @param varList Variable/observable info\n\t * @param statesList List of states/observations\n\t * @param umbWriter The UMBWriter to store info in\n\t */\n\tprivate void storeVarInfo(VarList varList, List<State> statesList, UMBIndex.UMBEntity entity, UMBWriter umbWriter) throws PrismException\n\t{\n\t\ttry {\n\t\t\tint numVars = varList.getNumVars();\n\n\t\t\t// Create bit-packing for variable/observable values, store metadata in index\n\t\t\tboolean storeOffsets = false;\n\t\t\tUMBBitPacking bitPacking = new UMBBitPacking();\n\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\tDeclarationType varDecl = varList.getDeclarationType(i);\n\t\t\t\tUMBType varTypeUMB;\n\t\t\t\tif (varDecl instanceof DeclarationBool) {\n\t\t\t\t\tvarTypeUMB = UMBType.create(UMBType.Type.BOOL, 1);\n\t\t\t\t} else if (varDecl instanceof DeclarationInt) {\n\t\t\t\t\tif (storeOffsets) {\n\t\t\t\t\t\tvarTypeUMB = UMBType.create(UMBType.Type.INT, varList.getRangeLogTwo(i)); // TODO\n\t\t\t\t\t} else {\n\t\t\t\t\t\tint varLow = varList.getLow(i);\n\t\t\t\t\t\tint varHigh = varList.getHigh(i);\n\t\t\t\t\t\tif (varLow < 0) {\n\t\t\t\t\t\t\tint varMaxAbs = Math.abs(varLow);\n\t\t\t\t\t\t\tif (varHigh > 0) {\n\t\t\t\t\t\t\t\tvarMaxAbs = Math.max(varMaxAbs, varHigh + 1);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tvarTypeUMB = UMBType.create(UMBType.Type.INT, (int) Math.ceil(PrismUtils.log2(varMaxAbs)) + 1);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tvarTypeUMB = UMBType.create(UMBType.Type.UINT, (int) Math.ceil(PrismUtils.log2(varHigh + 1)));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else if (varDecl instanceof DeclarationIntUnbounded) {\n\t\t\t\t\tvarTypeUMB = UMBType.create(UMBType.Type.INT, 32);\n\t\t\t\t} else if (varDecl instanceof DeclarationDoubleUnbounded) {\n\t\t\t\t\tvarTypeUMB = UMBType.create(UMBType.Type.DOUBLE, 64);\n\t\t\t\t} else {\n\t\t\t\t\tthrow new PrismException(\"Unsupported variable type in UMB export: \" + varDecl);\n\t\t\t\t}\n\t\t\t\tbitPacking.addVariable(varList.getName(i), varTypeUMB);\n\t\t\t}\n\t\t\tbitPacking.padToByteBoundary();\n\t\t\tumbWriter.addValuationDescription(entity, true, bitPacking);\n\n\t\t\t// Build an iterator to supply the bit-packed variable/observable values, add data\n\t\t\tIterator<UMBBitString> iter = statesList.stream()\n\t\t\t\t\t.map(s -> {\n\t\t\t\t\t\tUMBBitString bitString = bitPacking.newBitString();\n\t\t\t\t\t\tObject v = null;\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\t\t\t\tUMBType.Type varTypeUMB = bitPacking.getVariable(i).getType().type;\n\t\t\t\t\t\t\t\tv = s.varValues[i];\n\t\t\t\t\t\t\t\tv = varList.getType(i).castValueTo(v, EvaluateContext.EvalMode.FP);\n\t\t\t\t\t\t\t\tswitch (varTypeUMB) {\n\t\t\t\t\t\t\t\t\tcase BOOL:\n\t\t\t\t\t\t\t\t\t\tbitPacking.setBooleanVariableValue(bitString, i, (boolean) v);\n\t\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t\tcase INT:\n\t\t\t\t\t\t\t\t\t\tbitPacking.setIntVariableValue(bitString, i, (int) v);\n\t\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t\tcase UINT:\n\t\t\t\t\t\t\t\t\t\tbitPacking.setUIntVariableValue(bitString, i, (int) v);\n\t\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t\tcase DOUBLE:\n\t\t\t\t\t\t\t\t\t\tbitPacking.setDoubleVariableValue(bitString, i, (double) v);\n\t\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\t\t\tthrow new PrismException(\"Unsupported variable type in UMB export: \" + varTypeUMB);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} catch (ClassCastException e) {\n\t\t\t\t\t\t\tthrow new RuntimeException(\"Was not expecting data as \" + v.getClass().getSimpleName());\n\t\t\t\t\t\t} catch (UMBException | PrismException e) {\n\t\t\t\t\t\t\tthrow new RuntimeException(e);\n\t\t\t\t\t\t}\n\t\t\t\t\t\treturn bitString;\n\t\t\t\t\t})\n\t\t\t\t\t.iterator();\n\t\t\tumbWriter.addValuations(entity, iter, bitPacking);\n\t} catch (UMBException | RuntimeException e) {\n\t\t\tthrow new PrismException(\"UMB export problem: \" + e.getMessage());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/UMBImporter.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage io;\n\nimport common.Interval;\nimport common.SafeCast;\nimport io.github.pmctools.umbj.*;\nimport it.unimi.dsi.fastutil.ints.IntArrayList;\nimport it.unimi.dsi.fastutil.ints.IntList;\nimport parser.EvaluateContext;\nimport parser.VarList;\nimport parser.ast.DeclarationBool;\nimport parser.ast.DeclarationDoubleUnbounded;\nimport parser.ast.DeclarationInt;\nimport parser.ast.DeclarationType;\nimport parser.ast.Expression;\nimport prism.BasicModelInfo;\nimport prism.BasicRewardInfo;\nimport prism.Evaluator;\nimport prism.ModelInfo;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.RewardInfo;\n\nimport java.io.File;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.concurrent.atomic.AtomicInteger;\nimport java.util.function.BiConsumer;\nimport java.util.function.Consumer;\nimport java.util.function.DoubleConsumer;\nimport java.util.function.IntConsumer;\nimport java.util.function.LongConsumer;\nimport java.util.stream.IntStream;\n\n/**\n * Class to manage importing models from UMB binary files.\n */\npublic class UMBImporter extends ExplicitModelImporter\n{\n\tprivate File umbFile;\n\tprivate UMBReader umbReader;\n\tprivate UMBIndex umbIndex;\n\n\t// Model info extracted from file and then stored in a BasicModelInfo object\n\tprivate BasicModelInfo basicModelInfo;\n\n\t// Links between model info to UMB file\n\tprivate List<String> labelIDs;\n\tprivate List<String> rewardIDs;\n\tprivate List<String> varIDs;\n\n\t// Num states/transitions/etc.\n\tprivate int numStates = 0;\n\tprivate int numChoices = 0;\n\tprivate int numTransitions = 0;\n\tprivate int numObservations = 0;\n\n\t// Reward info extracted from files and then stored in a BasicRewardInfo object\n\tprivate BasicRewardInfo basicRewardInfo;\n\n\tpublic UMBImporter(File umbFile) throws PrismException\n\t{\n\t\tthis.umbFile = umbFile;\n\n\t\ttry {\n\t\t\tumbReader = new UMBReader(umbFile);\n\t\t\t// Extract index and store model stats\n\t\t\tumbIndex = umbReader.getUMBIndex();\n\t\t\tnumStates = SafeCast.toIntExact(umbIndex.getNumStates());\n\t\t\tnumChoices = SafeCast.toIntExact(umbIndex.getNumChoices());\n\t\t\tnumTransitions = SafeCast.toIntExact(umbIndex.getNumBranches());\n\t\t\tnumObservations = SafeCast.toIntExact(umbIndex.getNumObservations());\n\t\t} catch (ArithmeticException e) {\n\t\t\tthrow new PrismException(\"UMB model is too large to be imported\");\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"Error importing from UMB: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean modelIsExact()\n\t{\n\t\t// For now, assume that if transition probabilities are rationals, so is everything else\n\t\treturn umbIndex.getBranchProbabilityType() != null && umbIndex.getBranchProbabilityType().type.isRational();\n\t}\n\n\t@Override\n\tpublic boolean providesStates()\n\t{\n\t\treturn umbIndex.hasValuations(UMBIndex.UMBEntity.STATES);\n\t}\n\n\t@Override\n\tpublic boolean providesObservations()\n\t{\n\t\treturn umbIndex.hasValuations(UMBIndex.UMBEntity.OBSERVATIONS);\n\t}\n\n\t@Override\n\tpublic boolean providesLabels()\n\t{\n\t\treturn umbIndex.hasAPAnnotations();\n\t}\n\n\t@Override\n\tpublic String sourceString()\n\t{\n\t\treturn \"\\\"\" + umbFile.getName() + \"\\\"\";\n\t}\n\n\t@Override\n\tpublic ModelInfo getModelInfo() throws PrismException\n\t{\n\t\t// Construct lazily, as needed\n\t\tif (basicModelInfo == null) {\n\t\t\tbuildModelInfo();\n\t\t}\n\t\treturn basicModelInfo;\n\t}\n\n\t@Override\n\tpublic int getNumStates() throws PrismException\n\t{\n\t\treturn numStates;\n\t}\n\n\t@Override\n\tpublic int getNumChoices() throws PrismException\n\t{\n\t\treturn numChoices;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions() throws PrismException\n\t{\n\t\treturn numTransitions;\n\t}\n\n\t@Override\n\tpublic int getNumObservations() throws PrismException\n\t{\n\t\treturn numObservations;\n\t}\n\n\t@Override\n\tpublic BitSet getDeadlockStates() throws PrismException\n\t{\n\t\t// TODO\n\t\treturn new BitSet();\n\t}\n\n\t@Override\n\tpublic int getNumDeadlockStates() throws PrismException\n\t{\n\t\t// TODO\n\t\treturn 0;\n\t}\n\n\t@Override\n\tpublic RewardInfo getRewardInfo() throws PrismException\n\t{\n\t\t// Construct lazily, as needed\n\t\tif (basicRewardInfo == null) {\n\t\t\tbuildRewardInfo();\n\t\t}\n\t\treturn basicRewardInfo;\n\t}\n\n\t/**\n\t * Build/store model info from the UMB index file.\n\t * Can then be accessed via {@link #getModelInfo()}.\n\t */\n\tprivate void buildModelInfo() throws PrismException\n\t{\n\t\t// Create BasicModelInfo object\n\t\tModelType modelType = getModelTypeFromIndex(umbIndex);\n\t\tbasicModelInfo = new BasicModelInfo(modelType);\n\t\t// Extract/initialise action list\n\t\tArrayList<Object> actionStrings = new ArrayList<>();\n\t\ttry {\n\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\tif (umbReader.hasChoiceActionStrings()) {\n\t\t\t\t\tumbReader.extractChoiceActionStrings(actionStrings::add);\n\t\t\t\t} else {\n\t\t\t\t\t// No strings provided: use default action strings _1, _2, ...\n\t\t\t\t\tIntStream.rangeClosed(1, umbIndex.getNumChoiceActions()).mapToObj(i -> \"_\" + i).forEach(actionStrings::add);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (umbReader.hasBranchActionStrings()) {\n\t\t\t\t\tumbReader.extractBranchActionStrings(actionStrings::add);\n\t\t\t\t} else {\n\t\t\t\t\t// No strings provided: use default action strings _1, _2, ...\n\t\t\t\t\tIntStream.rangeClosed(1, umbIndex.getNumBranchActions()).mapToObj(i -> \"_\" + i).forEach(actionStrings::add);\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (actionStrings.isEmpty()) {\n\t\t\t\tactionStrings.add(null);\n\t\t\t}\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"Could not extract actions from UMB file\");\n\t\t}\n\t\tbasicModelInfo.setActionList(actionStrings);\n\t\t// Add variable info, extracting from UMB file if provided\n\t\tVarList varList = basicModelInfo.getVarList();\n\t\tif (providesStates()) {\n\t\t\tbuildVarInfo(UMBIndex.UMBEntity.STATES, varList);\n\t\t} else {\n\t\t\tvarList.addVar(defaultVariableName(), defaultVariableDeclarationType(), -1);\n\t\t}\n\t\t// Add observable info, extracting from UMB file if provided\n\t\tif (providesObservations()) {\n\t\t\tVarList obsVarList = new VarList();\n\t\t\tobsVarList.setEvaluateContext(basicModelInfo.getEvaluateContext());\n\t\t\tbuildVarInfo(UMBIndex.UMBEntity.OBSERVATIONS, obsVarList);\n\t\t\tfor (int i = 0; i < obsVarList.getNumVars(); i++) {\n\t\t\t\tbasicModelInfo.getObservableNames().add(obsVarList.getName(i));\n\t\t\t\tbasicModelInfo.getObservableTypeList().add(obsVarList.getType(i));\n\t\t\t}\n\t\t} else {\n\t\t\tbasicModelInfo.getObservableNames().add(defaultObservableName());\n\t\t\tbasicModelInfo.getObservableTypeList().add(defaultObservableType());\n\t\t}\n\t\t// Add label info\n\t\t// We extract all labels (AP) annotations from the UMB file, ignoring \"deadlock\" if present\n\t\t// IDs are stores in labelIDs and (valid) names go in basicModelInfo\n\t\tlabelIDs = new ArrayList<>();\n\t\tList<String> labelList = basicModelInfo.getLabelNameList();\n\t\tfor (UMBIndex.Annotation apAnnotation : umbIndex.getAPAnnotationsList()) {\n\t\t\tString apName = apAnnotation.getName();\n\t\t\tif (!apName.equals(\"deadlock\")) {\n\t\t\t\tlabelIDs.add(apAnnotation.id);\n\t\t\t\t// Get valid, unique label name (usually just the AP annotation alias)\n\t\t\t\tString labelName = Prism.toIdentifier(apName);\n\t\t\t\twhile (labelList.contains(labelName)) {\n\t\t\t\t\tlabelName = \"_\" + labelName;\n\t\t\t\t}\n\t\t\t\tlabelList.add(labelName);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Determine ModelType from UMBIndex metadata.\n\t */\n\tprivate static ModelType getModelTypeFromIndex(UMBIndex umbIndex) throws PrismException\n\t{\n\t\tUMBIndex.ModelType modelType = umbIndex.getModelType();\n\t\tif (modelType == null) {\n\t\t\tthrow new PrismException(\"Unsupported model type in UMB file\");\n\t\t}\n\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\t\treturn ModelType.DTMC;\n\t\t\tcase CTMC:\n\t\t\t\treturn ModelType.CTMC;\n\t\t\tcase MDP:\n\t\t\t\treturn ModelType.MDP;\n\t\t\tcase POMDP:\n\t\t\t\treturn ModelType.POMDP;\n\t\t\tcase LTS:\n\t\t\t\treturn ModelType.LTS;\n\t\t\tcase IDTMC:\n\t\t\t\treturn ModelType.IDTMC;\n\t\t\tcase IMDP:\n\t\t\t\treturn ModelType.IMDP;\n\t\t\tcase IPOMDP:\n\t\t\t\treturn ModelType.IPOMDP;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unsupported model type \" + modelType + \" in UMB file\");\n\t\t}\n\t}\n\n\t/**\n\t * Build/store reward info from the UMB index file.\n\t * Can then be accessed via {@link #getRewardInfo()}.\n\t */\n\tprivate void buildRewardInfo() throws PrismException\n\t{\n\t\tModelType modelType = getModelInfo().getModelType();\n\t\tbasicRewardInfo = new BasicRewardInfo();\n\t\tint numRewards = umbIndex.getNumRewardAnnotations();\n\t\tfor (int r = 0; r < numRewards; r++) {\n\t\t\tbasicRewardInfo.addReward(umbIndex.getRewardAnnotation(r).getName());\n\t\t\tbasicRewardInfo.setHasStateRewards(r, umbIndex.hasStateRewards(r));\n\t\t\tif (modelType.nondeterministic()) {\n\t\t\t\tbasicRewardInfo.setHasTransitionRewards(r, umbIndex.hasChoiceRewards(r));\n\t\t\t} else {\n\t\t\t\tbasicRewardInfo.setHasTransitionRewards(r, umbIndex.hasBranchRewards(r));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Extract info about variables/observables for states/observations and store in the provided VarList.\n\t * @param entity State or observations?\n\t * @param varList Storage for variable/observable info\n\t */\n\tprivate void buildVarInfo(UMBIndex.UMBEntity entity, VarList varList) throws PrismException\n\t{\n\t\ttry {\n\t\t\tif (!umbIndex.hasValuations(entity)) {\n\t\t\t\tthrow new PrismException(\"Missing UMB valuation data for \" + entity);\n\t\t\t} else {\n\t\t\t\tif (umbIndex.getNumValuationClasses(entity) > 1) {\n\t\t\t\t\tthrow new PrismException(\"Import of multiple valuation classes not yet supported\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tUMBBitPacking bitPacking = umbIndex.getValuationBitPacking(entity);\n\t\t\tint numVars = bitPacking.getNumVariables();\n\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\tUMBBitPacking.BitPackedVariable var = bitPacking.getVariable(i);\n\t\t\t\t// Get valid, unique variable name (usually just the provided variable name)\n\t\t\t\tString varName = Prism.toIdentifier(var.name);\n\t\t\t\twhile (varList.getIndex(varName) != -1) {\n\t\t\t\t\tvarName = \"_\" + varName;\n\t\t\t\t}\n\t\t\t\t// Determine type, range, etc. of variable\n\t\t\t\tDeclarationType varDecl = null;\n\t\t\t\tswitch (var.getType().type) {\n\t\t\t\t\tcase BOOL:\n\t\t\t\t\t\tvarDecl = new DeclarationBool();\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase INT:\n\t\t\t\t\tcase UINT:\n\t\t\t\t\t\tboolean computeRange = true;\n\t\t\t\t\t\tint varIntMin;\n\t\t\t\t\t\tint varIntMax;\n\t\t\t\t\t\tif (computeRange) {\n\t\t\t\t\t\t\tUMBReader.LongRange varLongRange = umbReader.getValuationLongRange(entity, bitPacking, i);\n\t\t\t\t\t\t\tlong varLongMin = varLongRange.getMin();\n\t\t\t\t\t\t\tlong varLongMax = varLongRange.getMax();\n\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\tvarIntMin = SafeCast.toIntExact(varLongMin);\n\t\t\t\t\t\t\t\tvarIntMax = SafeCast.toIntExact(varLongMax);\n\t\t\t\t\t\t\t} catch (ArithmeticException e) {\n\t\t\t\t\t\t\t\tthrow new PrismException(\"UMB variable \" + var.name + \" exceeds the range of an int\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t// Default to min/max values for (u)ints\n\t\t\t\t\t\t\tif (var.getType().type == UMBType.Type.INT) {\n\t\t\t\t\t\t\t\tif (bitPacking.getVariableSize(i) > 32) {\n\t\t\t\t\t\t\t\t\tthrow new PrismException(\"UMB variable \" + var.name + \" exceeds the range of an int\");\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tvarIntMin = -(1 << (bitPacking.getVariableSize(i) - 1));\n\t\t\t\t\t\t\t\tvarIntMax = (1 << (bitPacking.getVariableSize(i) - 1)) -1;\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tif (bitPacking.getVariableSize(i) >= 32) {\n\t\t\t\t\t\t\t\t\tthrow new PrismException(\"UMB variable \" + var.name + \" exceeds the range of an int\");\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tvarIntMin = 0;\n\t\t\t\t\t\t\t\tvarIntMax = (1 << bitPacking.getVariableSize(i)) - 1;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// Note: we do not yet allow 0-range variables\n\t\t\t\t\t\tif (varIntMin == varIntMax) {\n\t\t\t\t\t\t\tvarIntMax++;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tvarDecl = new DeclarationInt(Expression.Int(varIntMin), Expression.Int(varIntMax));\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase DOUBLE:\n\t\t\t\t\t\tvarDecl = new DeclarationDoubleUnbounded();\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tthrow new PrismException(\"Unknown variable type in UMB index: \" + var.getType().type);\n\t\t\t\t}\n\t\t\t\tvarList.addVar(varName, varDecl, -1);\n\t\t\t}\n\t\t} catch (UMBException e) {\n\t\t\tthrow new RuntimeException(e);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractStates(IOUtils.StateDefnConsumer storeStateDefn) throws PrismException\n\t{\n\t\t// If there is no info, just assume that states comprise a single integer value\n\t\tif (!providesStates()) {\n\t\t\tsuper.extractStates(storeStateDefn);\n\t\t\treturn;\n\t\t}\n\t\t// Otherwise, extract state variable info\n\t\ttry {\n\t\t\tUMBBitPacking bitPacking = umbIndex.getValuationBitPacking(UMBIndex.UMBEntity.STATES);\n\t\t\tAtomicInteger s = new AtomicInteger(0);\n\t\t\tint numVars = bitPacking.getNumVariables();\n\t\t\tumbReader.extractStateValuations(bitString -> {\n\t\t\t\ttry {\n\t\t\t\t\t//System.out.println(s + \":\" + bitPacking.decodeBitString(bitString));\n\t\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\t\tstoreStateDefn.accept(s.get(), i, getBitStringValue(bitPacking, bitString, i));\n\t\t\t\t\t}\n\t\t\t\t\ts.incrementAndGet();\n\t\t\t\t} catch (UMBException | PrismException e) {\n\t\t\t\t\tthrow new RuntimeException(e.getMessage());\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (UMBException | RuntimeException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractObservationDefinitions(IOUtils.StateDefnConsumer storeObservationDefn) throws PrismException\n\t{\n\t\t// If there is no info, just assume that states comprise a single integer value\n\t\tif (!providesObservations()) {\n\t\t\tsuper.extractObservationDefinitions(storeObservationDefn);\n\t\t\treturn;\n\t\t}\n\t\t// Otherwise, extract observation observable info\n\t\ttry {\n\t\t\tUMBBitPacking bitPacking = umbIndex.getValuationBitPacking(UMBIndex.UMBEntity.OBSERVATIONS);\n\t\t\tAtomicInteger s = new AtomicInteger(0);\n\t\t\tint numVars = bitPacking.getNumVariables();\n\t\t\tumbReader.extractObservationValuations(bitString -> {\n\t\t\t\ttry {\n\t\t\t\t\t//System.out.println(s + \":\" + bitPacking.decodeBitString(bitString));\n\t\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\t\tstoreObservationDefn.accept(s.get(), i, getBitStringValue(bitPacking, bitString, i));\n\t\t\t\t\t}\n\t\t\t\t\ts.incrementAndGet();\n\t\t\t\t} catch (UMBException | PrismException e) {\n\t\t\t\t\tthrow new RuntimeException(e.getMessage());\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (UMBException | RuntimeException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Get the value of the {@code i}th variable, from a bit string, as an Object\n\t */\n\tprivate Object getBitStringValue(UMBBitPacking bitPacking, UMBBitString bitString, int i) throws UMBException\n\t{\n\t\tUMBBitPacking.BitPackedVariable var = bitPacking.getVariable(i);\n\t\tswitch (var.getType().type) {\n\t\t\tcase BOOL:\n\t\t\t\treturn bitPacking.getBooleanVariableValue(bitString, i);\n\t\t\tcase INT:\n\t\t\t\ttry {\n\t\t\t\t\treturn SafeCast.toIntExact(bitPacking.getLongVariableValue(bitString, i));\n\t\t\t\t} catch (ArithmeticException e) {\n\t\t\t\t\tthrow new UMBException(\"UMB variable \" + var.name + \" exceeds the range of an int\");\n\t\t\t\t}\n\t\t\tcase UINT:\n\t\t\t\ttry {\n\t\t\t\t\treturn SafeCast.toIntExact(bitPacking.getULongVariableValue(bitString, i));\n\t\t\t\t} catch (ArithmeticException e) {\n\t\t\t\t\tthrow new UMBException(\"UMB variable \" + var.name + \" exceeds the range of an int\");\n\t\t\t\t}\n\t\t\tcase DOUBLE:\n\t\t\t\treturn bitPacking.getDoubleVariableValue(bitString, i);\n\t\t\tdefault:\n\t\t\t\tthrow new UMBException(\"Unknown UMB variable type: \" + var.getType().type);\n\t\t}\n\t}\n\n\t@Override\n\tpublic int computeMaxNumChoices() throws PrismException\n\t{\n\t\ttry {\n\t\t\treturn SafeCast.toInt(umbReader.extractMaxStateChoiceCount());\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractMCTransitions(IOUtils.MCTransitionConsumer<Value> storeTransition, Evaluator<Value> eval) throws PrismException\n\t{\n\t\ttry {\n\t\t\t// Extract transition info\n\t\t\tIntList choiceTransitionOffsets = new IntArrayList(numChoices + 1);\n\t\t\tumbReader.extractChoiceBranchOffsets(l -> choiceTransitionOffsets.add((int) l));\n\t\t\tIntList transitionSuccessors = new IntArrayList(numTransitions);\n\t\t\tumbReader.extractBranchTargets(l -> transitionSuccessors.add((int) l));\n\t\t\tModelAccess.ValueListFromPrimitives<Value> valueListFromPrimitives = new ModelAccess.ValueListFromPrimitives<>(eval, numTransitions);\n\t\t\tList<Value> transitionProbabilities = valueListFromPrimitives.valueList;\n\t\t\tumbReader.extractBranchProbabilities(valueListFromPrimitives.primitiveConsumer);\n\n\t\t\t// For CTMCs, extract exit rates\n\t\t\tList<Value> exitRates = null;\n\t\t\tboolean ctmc = getModelInfo().getModelType() == ModelType.CTMC;\n\t\t\tif (ctmc) {\n\t\t\t\tvalueListFromPrimitives = new ModelAccess.ValueListFromPrimitives<>(eval, numStates);\n\t\t\t\texitRates = valueListFromPrimitives.valueList;\n\t\t\t\tumbReader.extractExitRates(valueListFromPrimitives.primitiveConsumer);\n\t\t\t}\n\n\t\t\t// Extract action info\n\t\t\tObject firstAction = getModelInfo().getActions().get(0);\n\t\t\tIntList transitionActionIndices = null;\n\t\t\tboolean hasActions = umbReader.hasBranchActionIndices();\n\t\t\tif (hasActions) {\n\t\t\t\ttransitionActionIndices = new IntArrayList(numTransitions);\n\t\t\t\tumbReader.extractBranchActionIndices(transitionActionIndices::add);\n\t\t\t}\n\n\t\t\t// Convert sparse storage to transitions and store\n\t\t\tint jLo = 0, jHi = 0;\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tjLo = jHi;\n\t\t\t\tjHi = choiceTransitionOffsets.getInt(s + 1);\n\t\t\t\tfor (int j = jLo; j < jHi; j++) {\n\t\t\t\t\tObject action = hasActions ? getModelInfo().getActions().get(transitionActionIndices.getInt(j)) : firstAction;\n\t\t\t\t\tif (getModelInfo().getModelType() == ModelType.IDTMC) {\n\t\t\t\t\t\tInterval<Double> dIntv = new Interval<>((Double) transitionProbabilities.get(2 * j), (Double) transitionProbabilities.get(2 * j + 1));\n\t\t\t\t\t\t((IOUtils.MCTransitionConsumer<Interval<Double>>) storeTransition).accept(s, transitionSuccessors.getInt(j), dIntv, action);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tValue v = transitionProbabilities.get(j);\n\t\t\t\t\t\tif (ctmc) {\n\t\t\t\t\t\t\tv = eval.multiply(v, exitRates.get(s));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tstoreTransition.accept(s, transitionSuccessors.getInt(j), v, action);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractMDPTransitions(IOUtils.MDPTransitionConsumer<Value> storeTransition, Evaluator<Value> eval) throws PrismException\n\t{\n\t\ttry {\n\t\t\t// Extract transition info\n\t\t\tIntList stateChoiceOffsets = new IntArrayList(numStates + 1);\n\t\t\tumbReader.extractStateChoiceOffsets(l -> stateChoiceOffsets.add((int) l));\n\t\t\tIntList choiceTransitionOffsets = new IntArrayList(numChoices + 1);\n\t\t\tumbReader.extractChoiceBranchOffsets(l -> choiceTransitionOffsets.add((int) l));\n\t\t\tIntList transitionSuccessors = new IntArrayList(numTransitions);\n\t\t\tumbReader.extractBranchTargets(l -> transitionSuccessors.add((int) l));\n\t\t\tModelAccess.ValueListFromPrimitives<Value> valueListFromPrimitives = new ModelAccess.ValueListFromPrimitives<>(eval, numTransitions);\n\t\t\tList<Value> transitionProbabilities = valueListFromPrimitives.valueList;\n\t\t\tumbReader.extractBranchProbabilities(valueListFromPrimitives.primitiveConsumer);\n\n\t\t\t// Extract action info\n\t\t\tObject firstAction = getModelInfo().getActions().get(0);\n\t\t\tIntList choiceActionIndices = null;\n\t\t\tboolean hasActions = umbReader.hasChoiceActionIndices();\n\t\t\tif (hasActions) {\n\t\t\t\tchoiceActionIndices = new IntArrayList(numChoices);\n\t\t\t\tumbReader.extractChoiceActionIndices(choiceActionIndices::add);\n\t\t\t}\n\n\t\t\t// Convert sparse storage to transitions and store\n\t\t\tint iLo = 0, iHi = 0;\n\t\t\tint jLo = 0, jHi = 0;\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tiLo = iHi;\n\t\t\t\tiHi = stateChoiceOffsets.getInt(s + 1);\n\t\t\t\tint iCount = 0;\n\t\t\t\tfor (int i = iLo; i < iHi; i++) {\n\t\t\t\t\tjLo = jHi;\n\t\t\t\t\tjHi = choiceTransitionOffsets.getInt(i + 1);\n\t\t\t\t\tfor (int j = jLo; j < jHi; j++) {\n\t\t\t\t\t\tObject action = hasActions ? getModelInfo().getActions().get(choiceActionIndices.getInt(i)) : firstAction;\n\t\t\t\t\t\tif (getModelInfo().getModelType().intervals()) {\n\t\t\t\t\t\t\tInterval<Value> vIntv = new Interval<>(transitionProbabilities.get(2 * j), transitionProbabilities.get(2 * j + 1));\n\t\t\t\t\t\t\t((IOUtils.MDPTransitionConsumer<Interval<Value>>) storeTransition).accept(s, iCount, transitionSuccessors.getInt(j), vIntv, action);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tValue v = transitionProbabilities.get(j);\n\t\t\t\t\t\t\tstoreTransition.accept(s, iCount, transitionSuccessors.getInt(j), v, action);\n\t\t\t\t\t\t}\n\n\t\t\t\t\t}\n\t\t\t\t\tiCount++;\n\t\t\t\t}\n\t\t\t}\n\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractLTSTransitions(IOUtils.LTSTransitionConsumer storeTransition) throws PrismException\n\t{\n\t\ttry {\n\t\t\t// Extract transition info\n\t\t\tIntList stateChoiceOffsets = new IntArrayList(numStates + 1);\n\t\t\tumbReader.extractStateChoiceOffsets(l -> stateChoiceOffsets.add((int) l));\n\t\t\tIntList transitionSuccessors = new IntArrayList(numTransitions);\n\t\t\tumbReader.extractBranchTargets(l -> transitionSuccessors.add((int) l));\n\n\t\t\t// Extract action info\n\t\t\tObject firstAction = getModelInfo().getActions().get(0);\n\t\t\tIntList choiceActionIndices = null;\n\t\t\tboolean hasActions = umbReader.hasChoiceActionIndices();\n\t\t\tif (hasActions) {\n\t\t\t\tchoiceActionIndices = new IntArrayList(numChoices);\n\t\t\t\tumbReader.extractChoiceActionIndices(choiceActionIndices::add);\n\t\t\t}\n\n\t\t\t// Convert sparse storage to transitions and store\n\t\t\tint iLo = 0, iHi = 0;\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tiLo = iHi;\n\t\t\t\tiHi = stateChoiceOffsets.getInt(s + 1);\n\t\t\t\tint iCount = 0;\n\t\t\t\tfor (int i = iLo; i < iHi; i++) {\n\t\t\t\t\tObject action = hasActions ? getModelInfo().getActions().get(choiceActionIndices.getInt(i)) : firstAction;\n\t\t\t\t\tstoreTransition.accept(s, iCount, transitionSuccessors.getInt(i), action);\n\t\t\t\t\tiCount++;\n\t\t\t\t}\n\t\t\t}\n\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractLabelsAndInitialStates(BiConsumer<Integer, Integer> storeLabel, Consumer<Integer> storeInit, Consumer<Integer> storeDeadlock) throws PrismException\n\t{\n\t\ttry {\n\t\t\t// Extract initial states\n\t\t\tumbReader.extractInitialStates(s -> storeInit.accept(SafeCast.toIntExact(s)));\n\t\t\t// Extract labels\n\t\t\tint numLabels = labelIDs.size();\n\t\t\tfor (int i = 0; i < numLabels; i++) {\n\t\t\t\tint finalI = i;\n\t\t\t\tumbReader.extractStateAP(labelIDs.get(i), s -> storeLabel.accept(SafeCast.toIntExact(s), finalI));\n\t\t\t}\n\t\t\t// If a \"deadlock\" AP is stored, use it to store deadlock state info\n\t\t\tif (storeDeadlock != null) {\n\t\t\t\tString deadlockId = null;\n\t\t\t\tif (umbIndex.hasAPAnnotationWithAlias(\"deadlock\")) {\n\t\t\t\t\tdeadlockId = umbIndex.getAPAnnotationByAlias(\"deadlock\").id;\n\t\t\t\t} else if (umbIndex.getAPAnnotations().get(\"deadlock\") != null) {\n\t\t\t\t\tdeadlockId = \"deadlock\";\n\t\t\t\t}\n\t\t\t\tif (deadlockId != null) {\n\t\t\t\t\tumbReader.extractStateAP(deadlockId, s -> storeDeadlock.accept(SafeCast.toIntExact(s)));\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic void extractObservations(IOUtils.StateIntConsumer storeObservation) throws PrismException\n\t{\n\t\ttry {\n\t\t\t// Extract observations from UMB\n\t\t\tIntList stateObservations = new IntArrayList(numStates);\n\t\t\tumbReader.extractStateObservations(l -> stateObservations.add((int) l));\n\t\t\t// Store observations in model\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tstoreObservation.accept(s, stateObservations.getInt(s));\n\t\t\t}\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractStateRewards(int rewardIndex, BiConsumer<Integer, Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t{\n\t\ttry {\n\t\t\tif (!basicRewardInfo.rewardStructHasStateRewards(rewardIndex)) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tumbReader.extractStateRewards(rewardIndex, ModelAccess.primitivesToValues(eval, new IndexedConsumer<>(storeReward)));\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractMCTransitionRewards(int rewardIndex, IOUtils.TransitionRewardConsumer<Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tif (!basicRewardInfo.rewardStructHasTransitionRewards(rewardIndex)) {\n\t\t\treturn;\n\t\t}\n\n\t\ttry {\n\t\t\t// Extract transition rewards from UMB\n\t\t\tModelAccess.ValueListFromPrimitives<Value> valueListFromPrimitives = new ModelAccess.ValueListFromPrimitives<>(eval, numTransitions);\n\t\t\tList<Value> transRewards = valueListFromPrimitives.valueList;\n\t\t\tumbReader.extractBranchRewards(rewardIndex, valueListFromPrimitives.primitiveConsumer);\n\n\t\t\t// Convert sparse storage to reward list and store\n\t\t\t// If the model has already been built and provided, use this to look for transition indexing\n\t\t\tif (modelLookup != null) {\n\t\t\t\tModelAccess<Value> modelAccess = ModelAccess.wrap(modelLookup);\n\t\t\t\tint iLo = 0, iHi = 0;\n\t\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\t\tiLo = iHi;\n\t\t\t\t\tiHi = iLo + modelAccess.getNumTransitions(s, 0);\n\t\t\t\t\tfor (int i = iLo; i < iHi; i++) {\n\t\t\t\t\t\tValue v = transRewards.get(i);\n\t\t\t\t\t\tif (eval.gt(v, eval.zero())) {\n\t\t\t\t\t\t\tswitch (transitionRewardIndexing) {\n\t\t\t\t\t\t\t\tcase STATE:\n\t\t\t\t\t\t\t\t\tstoreReward.accept(s, modelAccess.getTransitionSuccessor(s, 0, i - iLo), v);\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\tcase OFFSET:\n\t\t\t\t\t\t\t\t\tstoreReward.accept(s, i - iLo, v);\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\t\tthrow new PrismException(\"Unknown transition reward indexing \" + transitionRewardIndexing);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// If there is no model available, we extract transition info from UMB first\n\t\t\telse {\n\t\t\t\tIntList stateTransitionOffsets = new IntArrayList(numStates + 1);\n\t\t\t\tumbReader.extractChoiceBranchOffsets(l -> stateTransitionOffsets.add((int) l));\n\t\t\t\tIntList transitionSuccessors;\n\t\t\t\tif (transitionRewardIndexing == TransitionRewardIndexing.STATE) {\n\t\t\t\t\ttransitionSuccessors = new IntArrayList(numTransitions);\n\t\t\t\t\tumbReader.extractBranchTargets(l -> transitionSuccessors.add((int) l));\n\t\t\t\t} else {\n\t\t\t\t\ttransitionSuccessors = null;\n\t\t\t\t}\n\n\t\t\t\tint iLo = 0, iHi = 0;\n\t\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\t\tiLo = iHi;\n\t\t\t\t\tiHi = stateTransitionOffsets.getInt(s + 1);\n\t\t\t\t\tfor (int i = iLo; i < iHi; i++) {\n\t\t\t\t\t\tValue v = transRewards.get(i);\n\t\t\t\t\t\tif (eval.gt(v, eval.zero())) {\n\t\t\t\t\t\t\tswitch (transitionRewardIndexing) {\n\t\t\t\t\t\t\t\tcase STATE:\n\t\t\t\t\t\t\t\t\tstoreReward.accept(s, transitionSuccessors.getInt(i), v);\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\tcase OFFSET:\n\t\t\t\t\t\t\t\t\tstoreReward.accept(s, i - iLo, v);\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\t\tthrow new PrismException(\"Unknown transition reward indexing \" + transitionRewardIndexing);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t@Override\n\tpublic <Value> void extractMDPTransitionRewards(int rewardIndex, IOUtils.TransitionRewardConsumer<Value> storeReward, Evaluator<Value> eval) throws PrismException\n\t{\n\t\tif (!basicRewardInfo.rewardStructHasTransitionRewards(rewardIndex)) {\n\t\t\treturn;\n\t\t}\n\n\t\ttry {\n\t\t\t// Extract transition rewards from UMB\n\t\t\tModelAccess.ValueListFromPrimitives<Value> valueListFromPrimitives = new ModelAccess.ValueListFromPrimitives<>(eval, numChoices);\n\t\t\tList<Value> transRewards = valueListFromPrimitives.valueList;\n\t\t\tumbReader.extractChoiceRewards(rewardIndex, valueListFromPrimitives.primitiveConsumer);\n\n\t\t\t// Convert sparse storage to reward list and store\n\t\t\t// If the model has already been built and provided, use this to look for transition indexing\n\t\t\tModelAccess<Value> modelAccess = null;\n\t\t\tIntList stateChoiceOffsets;\n\t\t\tif (modelLookup != null) {\n\t\t\t\tstateChoiceOffsets = null;\n\t\t\t\tmodelAccess = ModelAccess.wrap(modelLookup);\n\t\t\t}\n\t\t\t// If there is no model available, we extract transition info from UMB first\n\t\t\telse {\n\t\t\t\tstateChoiceOffsets = new IntArrayList(numStates + 1);\n\t\t\t\tumbReader.extractStateChoiceOffsets(l -> stateChoiceOffsets.add((int) l));\n\t\t\t}\n\n\t\t\t// Convert sparse storage to reward list and store\n\t\t\tint iLo = 0, iHi = 0;\n\t\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\t\tiLo = iHi;\n\t\t\t\tif (modelLookup != null) {\n\t\t\t\t\tiHi = iLo + modelAccess.getNumChoices(s);\n\t\t\t\t} else {\n\t\t\t\t\tiHi = stateChoiceOffsets.getInt(s + 1);\n\t\t\t\t}\n\t\t\t\tfor (int i = iLo; i < iHi; i++) {\n\t\t\t\t\tValue v = transRewards.get(i);\n\t\t\t\t\tif (eval.gt(v, eval.zero())) {\n\t\t\t\t\t\tstoreReward.accept(s, i - iLo, v);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (UMBException e) {\n\t\t\tthrow new PrismException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t}\n\n\t// Utility classes\n\n\t/**\n\t * Class to map a long consumer to an int consumer.\n\t */\n\tprivate static class LongConsumerToIntConsumer implements LongConsumer\n\t{\n\t\tIntConsumer out;\n\n\t\tLongConsumerToIntConsumer(IntConsumer out)\n\t\t{\n\t\t\tthis.out = out;\n\t\t}\n\n\t\t@Override\n\t\tpublic void accept(long v)\n\t\t{\n\t\t\tout.accept(SafeCast.toIntExact(v));\n\t\t}\n\t}\n\n\t/**\n\t * Class to add an increasing index to values from a Value consumer.\n\t */\n\tprivate static class IndexedConsumer<Value> implements Consumer<Value>\n\t{\n\t\tBiConsumer<Integer, Value> out;\n\t\tint index;\n\n\t\tIndexedConsumer(BiConsumer<Integer, Value> out)\n\t\t{\n\t\t\tthis.out = out;\n\t\t}\n\n\t\t@Override\n\t\tpublic void accept(Value v)\n\t\t{\n\t\t\tout.accept(index++, v);\n\t\t}\n\t}\n\n\t/**\n\t * Class to add an increasing index to values from a double consumer.\n\t */\n\tprivate static class IndexedDoubleConsumer implements DoubleConsumer\n\t{\n\t\tBiConsumer<Integer, Double> out;\n\t\tint index;\n\n\t\tIndexedDoubleConsumer(BiConsumer<Integer, Double> out)\n\t\t{\n\t\t\tthis.out = out;\n\t\t}\n\n\t\t@Override\n\t\tpublic void accept(double d)\n\t\t{\n\t\t\tout.accept(index++, d);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBBitPacking.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\n/**\n * Stores information about how a list of typed variables (with optional padding) are packed into a bit string.\n */\npublic class UMBBitPacking\n{\n\t/** Items stored (variables or padding) */\n\tprivate final List<BitPackedItem> items = new ArrayList<>();\n\t/** Starting bit offsets for each item */\n\tprivate final List<Integer> itemOffsets = new ArrayList<>();\n\t/** Indices (into the item list) of the variables */\n\tprivate final List<Integer> varIndices = new ArrayList<>();\n\t/** Total number of bits used */\n\tprivate int totalNumBits = 0;\n\n\t/**\n\t * Construct a new UMBBitPacking object, based on a UMB valuation description (from JSON).\n\t * @param valuationDescr The valuation description\n\t */\n\tpublic UMBBitPacking(UMBIndex.ValuationClassDescription valuationDescr)\n\t{\n\t\tfor (UMBIndex.ValuationVariable item : valuationDescr.variables) {\n\t\t\tif (item.isVariable()) {\n\t\t\t\taddVariable(item.name, item.type);\n\t\t\t}\n\t\t\telse if (item.isPadding()) {\n\t\t\t\taddPadding(item.padding);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Construct a new, empty UMBBitPacking object.\n\t */\n\tpublic UMBBitPacking()\n\t{\n\t}\n\n\t/**\n\t * Add a variable.\n\t * @param name Variable name\n\t * @param type Variable type (including size, in bits)\n\t */\n\tpublic void addVariable(String name, UMBType type)\n\t{\n\t\taddItem(new BitPackedVariable(name, type));\n\t\tvarIndices.add(items.size() - 1);\n\t}\n\n\t/**\n\t * Add padding.\n\t * @param size Padding size (in bits)\n\t */\n\tpublic void addPadding(int size)\n\t{\n\t\taddItem(new BitPackedPadding(size));\n\t}\n\n\t/**\n\t * Add an item (variable or padding) and update internal state.\n\t * @param item The item to add\n\t */\n\tprivate void addItem(BitPackedItem item)\n\t{\n\t\t// Compute offset (starting bit) for new item\n\t\tif (items.isEmpty()) {\n\t\t\titemOffsets.add(0);\n\t\t} else {\n\t\t\titemOffsets.add(itemOffsets.get(itemOffsets.size() - 1) + items.get(items.size() - 1).size);\n\t\t}\n\t\t// Add to list\n\t\titems.add(item);\n\t\t// Update total size\n\t\ttotalNumBits += item.size;\n\t}\n\n\t/**\n\t * Add padding to align to the next byte boundary, if needed.\n\t */\n\tpublic void padToByteBoundary()\n\t{\n\t\tif (getTotalNumBits() % 8 != 0) {\n\t\t\taddPadding(8 - (getTotalNumBits() % 8));\n\t\t}\n\t}\n\n\t/**\n\t * Create a UMB valuation class description corresponding to this bit packing.\n\t */\n\tpublic UMBIndex.ValuationClassDescription toValuationClassDescription()\n\t{\n\t\tUMBIndex.ValuationClassDescription valuationClassDescr = new UMBIndex.ValuationClassDescription();\n\t\t// Create an item for each variable or padding\n\t\tint numItems = getNumItems();\n\t\tfor (int i = 0; i < numItems; i++) {\n\t\t\tBitPackedItem item = getItem(i);\n\t\t\tUMBIndex.ValuationVariable var = new UMBIndex.ValuationVariable();\n\t\t\tif (item instanceof BitPackedVariable) {\n\t\t\t\tBitPackedVariable varItem = (BitPackedVariable) item;\n\t\t\t\tvar.name = varItem.name;\n\t\t\t\tvar.type = varItem.type;\n\t\t\t} else if (item instanceof BitPackedPadding) {\n\t\t\t\tvar.padding = item.size;\n\t\t\t}\n\t\t\tvaluationClassDescr.variables.add(var);\n\t\t}\n\t\t// Add final padding to align to byte boundary, if needed\n\t\tif (getTotalNumBits() % 8 != 0) {\n\t\t\tUMBIndex.ValuationVariable var = new UMBIndex.ValuationVariable();\n\t\t\tvar.padding = 8 - (getTotalNumBits() % 8);\n\t\t\tvaluationClassDescr.variables.add(var);\n\t\t}\n\t\treturn valuationClassDescr;\n\t}\n\n\t// Getters for information about the packing\n\n\t/**\n\t * Get the number of items (variables or padding) in the packing.\n\t */\n\tpublic int getNumItems()\n\t{\n\t\treturn items.size();\n\t}\n\n\t/**\n\t * Get the {@code i}th item (variable or padding).\n\t */\n\tpublic BitPackedItem getItem(int i)\n\t{\n\t\treturn items.get(i);\n\t}\n\n\t/**\n\t * Get the starting bit offset of the {@code i}th item (variable or padding).\n\t */\n\tpublic int getItemOffset(int i)\n\t{\n\t\treturn itemOffsets.get(i);\n\t}\n\n\t/**\n\t * Get the size (in bits) of the {@code i}th item (variable or padding).\n\t */\n\tpublic int getItemSize(int i)\n\t{\n\t\treturn getItem(i).size;\n\t}\n\n\t/**\n\t * Get the total number of bits used in the packing (including padding).\n\t */\n\tpublic int getTotalNumBits()\n\t{\n\t\treturn totalNumBits;\n\t}\n\n\t/**\n\t * Get the total number of bytes used in the packing (including padding to byte boundary).\n\t */\n\tpublic int getTotalNumBytes()\n\t{\n\t\tint totalNumBitsNeeded = totalNumBits;\n\t\tif (totalNumBitsNeeded % 8 != 0) {\n\t\t\ttotalNumBitsNeeded += (8 - totalNumBitsNeeded % 8);\n\t\t}\n\t\treturn totalNumBitsNeeded / 8;\n\t}\n\n\t/**\n\t * Get the number of variables in the packing.\n\t */\n\tpublic int getNumVariables()\n\t{\n\t\treturn varIndices.size();\n\t}\n\n\t/**\n\t * Get the {@code i}th variable.\n\t */\n\tpublic BitPackedVariable getVariable(int i)\n\t{\n\t\treturn (BitPackedVariable) items.get(varIndices.get(i));\n\t}\n\n\t/**\n\t * Get the starting bit offset of the {@code i}th variable.\n\t */\n\tpublic int getVariableOffset(int i)\n\t{\n\t\treturn itemOffsets.get(varIndices.get(i));\n\t}\n\n\t/**\n\t * Get the size (in bits) of the {@code i}th variable.\n\t */\n\tpublic int getVariableSize(int i)\n\t{\n\t\treturn getVariable(i).size;\n\t}\n\n\t// Methods to create and manipulate bit strings according to this packing\n\n\t/**\n\t * Create a new UMBBitString of the appropriate size for this packing.\n\t */\n\tpublic UMBBitString newBitString()\n\t{\n\t\treturn new UMBBitString(getTotalNumBytes());\n\t}\n\n\t/**\n\t * Set the value of the {@code i}th variable, which must be a (signed) integer, in a bit string.\n\t * This assumes that the integer needs at most 32 bits, so that it can be stored in an {@code int}.\n\t * @param bitString The bit string to modify\n\t * @param i The index of the variable\n\t * @param value The value to set\n\t */\n\tpublic void setIntVariableValue(UMBBitString bitString, int i, int value) throws UMBException\n\t{\n\t\tbitString.setInt(getVariableOffset(i), getVariableSize(i), value);\n\t}\n\n\t/**\n\t * Set the value of the {@code i}th variable, which must be an (unsigned) integer, in a bit string.\n\t * This assumes that the integer needs at most 32 bits, so that it can be stored in an {@code int}.\n\t * @param bitString The bit string to modify\n\t * @param i The index of the variable\n\t * @param value The value to set\n\t */\n\tpublic void setUIntVariableValue(UMBBitString bitString, int i, int value) throws UMBException\n\t{\n\t\tbitString.setUInt(getVariableOffset(i), getVariableSize(i), value);\n\t}\n\n\t/**\n\t * Set the value of the {@code i}th variable, which must be a (signed) integer, in a bit string.\n\t * This assumes that the integer needs at most 64 bits, so that it can be stored in a {@code long}.\n\t * @param bitString The bit string to modify\n\t * @param i The index of the variable\n\t * @param value The value to set\n\t */\n\tpublic void setLongVariableValue(UMBBitString bitString, int i, long value) throws UMBException\n\t{\n\t\tbitString.setLong(getVariableOffset(i), getVariableSize(i), value);\n\t}\n\n\t/**\n\t * Set the value of the {@code i}th variable, which must be an (unsigned) integer, in a bit string.\n\t * This assumes that the integer needs at most 64 bits, so that it can be stored in a {@code long}.\n\t * @param bitString The bit string to modify\n\t * @param i The index of the variable\n\t * @param value The value to set\n\t */\n\tpublic void setULongVariableValue(UMBBitString bitString, int i, long value) throws UMBException\n\t{\n\t\tbitString.setULong(getVariableOffset(i), getVariableSize(i), value);\n\t}\n\n\t/** Set the value of the {@code i}th variable, which must be a double, in a bit string.\n\t * @param bitString The bit string to modify\n\t * @param i The index of the variable\n\t * @param value The value to set\n\t */\n\tpublic void setDoubleVariableValue(UMBBitString bitString, int i, double value) throws UMBException\n\t{\n\t\tbitString.setDouble(getVariableOffset(i), getVariableSize(i), value);\n\t}\n\n\t/** Set the value of the {@code i}th variable, which must be a boolean, in a bit string.\n\t * @param bitString The bit string to modify\n\t * @param i The index of the variable\n\t * @param value The value to set\n\t */\n\tpublic void setBooleanVariableValue(UMBBitString bitString, int i, boolean value) throws UMBException\n\t{\n\t\tbitString.setBoolean(getVariableOffset(i), getVariableSize(i), value);\n\t}\n\n\t// Methods to extract values stored in bit strings according to this packing\n\n\t/**\n\t * Get the value of the {@code i}th variable, from a bit string, as an Object\n\t */\n\tpublic Object getVariableValue(UMBBitString bitString, int i) throws UMBException\n\t{\n\t\tBitPackedVariable var = getVariable(i);\n\t\tswitch (var.getType().type) {\n\t\t\tcase BOOL:\n\t\t\t\treturn getBooleanVariableValue(bitString, i);\n\t\t\tcase INT:\n\t\t\t\treturn getIntVariableValue(bitString, i);\n\t\t\tcase UINT:\n\t\t\t\treturn getUIntVariableValue(bitString, i);\n\t\t\tcase DOUBLE:\n\t\t\t\treturn getDoubleVariableValue(bitString, i);\n\t\t\tdefault:\n\t\t\t\tthrow new UMBException(\"Unknown variable type: \" + var.getType().type);\n\t\t}\n\t}\n\n\t/**\n\t * Get the value of the {@code i}th variable, which must be a (signed) integer, from a bit string.\n\t * This assumes that the integer needs at most 32 bits, so that it can be stored in an {@code int}.\n\t */\n\tpublic int getIntVariableValue(UMBBitString bitString, int i) throws UMBException\n\t{\n\t\treturn bitString.getInt(getVariableOffset(i), getVariableSize(i));\n\t}\n\n\t/**\n\t * Get the value of the {@code i}th variable, which must be an (unsigned) integer, from a bit string.\n\t * This assumes that the integer needs at most 32 bits, so that it can be stored in an {@code int}.\n\t */\n\tpublic int getUIntVariableValue(UMBBitString bitString, int i) throws UMBException\n\t{\n\t\treturn bitString.getUInt(getVariableOffset(i), getVariableSize(i));\n\t}\n\n\t/**\n\t * Get the value of the {@code i}th variable, which must be a (signed) integer, from a bit string.\n\t * This assumes that the integer needs at most 64 bits, so that it can be stored in a {@code long}.\n\t */\n\tpublic long getLongVariableValue(UMBBitString bitString, int i) throws UMBException\n\t{\n\t\treturn bitString.getLong(getVariableOffset(i), getVariableSize(i));\n\t}\n\n\t/**\n\t * Get the value of the {@code i}th variable, which must be an (unsigned) integer, from a bit string.\n\t * This assumes that the integer needs at most 64 bits, so that it can be stored in a {@code long}.\n\t */\n\tpublic long getULongVariableValue(UMBBitString bitString, int i) throws UMBException\n\t{\n\t\treturn bitString.getULong(getVariableOffset(i), getVariableSize(i));\n\t}\n\n\t/**\n\t * Get the value of the {@code i}th variable, which must be a double, from a bit string.\n\t */\n\tpublic double getDoubleVariableValue(UMBBitString bitString, int i) throws UMBException\n\t{\n\t\treturn bitString.getDouble(getVariableOffset(i), getVariableSize(i));\n\t}\n\n\t/**\n\t * Get the value of the {@code i}th variable, which must be a boolean, from a bit string.\n\t */\n\tpublic boolean getBooleanVariableValue(UMBBitString bitString, int i) throws UMBException\n\t{\n\t\treturn bitString.getBoolean(getVariableOffset(i), getVariableSize(i));\n\t}\n\n\t/**\n\t * Create a string representation of values stored in a bit string according to the packing,\n\t * showing divisions into variables and padding.\n\t * @param bitString The bit string to format\n\t */\n\tpublic String decodeBitString(UMBBitString bitString) throws UMBException\n\t{\n\t\tStringBuilder sb = new StringBuilder();\n\t\tsb.append(\"(\");\n\t\tint numVars = getNumVariables();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tBitPackedVariable var = getVariable(i);\n\t\t\tint offset = getVariableOffset(i);\n\t\t\tint size = getVariableSize(i);\n\t\t\tswitch (var.getType().type) {\n\t\t\t\tcase BOOL:\n\t\t\t\t\tsb.append(bitString.getBoolean(offset, size));\n\t\t\t\t\tbreak;\n\t\t\t\tcase INT:\n\t\t\t\t\tsb.append(bitString.getInt(offset, size));\n\t\t\t\t\tbreak;\n\t\t\t\tcase UINT:\n\t\t\t\t\tsb.append(bitString.getUInt(offset, size));\n\t\t\t\t\tbreak;\n\t\t\t\tcase DOUBLE:\n\t\t\t\t\tsb.append(bitString.getDouble(offset, size));\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new UMBException(\"Unknown variable type: \" + var.type);\n\t\t\t}\n\t\t\tif (i < numVars - 1) {\n\t\t\t\tsb.append(\",\");\n\t\t\t}\n\t\t}\n\t\tsb.append(\")\");\n\t\treturn sb.toString();\n\t}\n\n\t/**\n\t * Create a string representation of a bit string according to the packing,\n\t * showing divisions into variables and padding.\n\t * @param bitString The bit string to format\n\t */\n\tpublic String formatBitString(UMBBitString bitString)\n\t{\n\t\tStringBuilder sb = new StringBuilder();\n\t\tint numItems = getNumItems();\n\t\t// Go through items in reverse order (most significant first)\n\t\tfor (int i = numItems - 1; i >= 0; i--) {\n\t\t\tBitPackedItem item = getItem(i);\n\t\t\tint offset = getItemOffset(i);\n\t\t\tint size = getItemSize(i);\n\t\t\tif (item instanceof BitPackedVariable) {\n\t\t\t\tsb.append(bitString.toString(offset, size));\n\t\t\t} else if (item instanceof BitPackedPadding) {\n\t\t\t\tfor (int j = 0; j < size; j++) {\n\t\t\t\t\tsb.append(\".\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (i > 0) {\n\t\t\t\tsb.append(\"|\");\n\t\t\t}\n\t\t}\n\t\treturn sb.toString();\n\t}\n\n\t// Classes for items in the packing\n\n\t/**\n\t * An item in the packing (either a variable or padding).\n\t */\n\tpublic static class BitPackedItem\n\t{\n\t\t/** Size (in bits) of this item */\n\t\tpublic int size;\n\t}\n\n\t/**\n\t * A variable in the packing.\n\t */\n\tpublic static class BitPackedVariable extends BitPackedItem\n\t{\n\t\t/** Name of the variable */\n\t\tpublic String name;\n\t\t/** Type of the variable */\n\t\tprivate UMBType type;\n\n\t\tpublic BitPackedVariable(String name, UMBType type)\n\t\t{\n\t\t\tthis.name = name;\n\t\t\tsetType(type);\n\t\t}\n\n\t\tpublic void setType(UMBType type)\n\t\t{\n\t\t\tthis.type = type;\n\t\t\tthis.size = type.size;\n\t\t}\n\n\t\tpublic UMBType getType()\n\t\t{\n\t\t\treturn type;\n\t\t}\n\t}\n\n\t/**\n\t * Padding in the packing.\n\t */\n\tpublic static class BitPackedPadding extends BitPackedItem\n\t{\n\t\tpublic BitPackedPadding(int size)\n\t\t{\n\t\t\tthis.size = size;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBBitString.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\n/**\n * Class representing a bit string, allowing portions of it to be read/written as various data types.\n */\npublic class UMBBitString\n{\n\t/** Bytes storing the bit string */\n\tpublic byte[] bytes;\n\n\t/**\n\t * Construct a new UMBBitString object, with space for the given number of bytes.\n\t * @param numBytes The number of bytes to allocate\n\t */\n\tpublic UMBBitString(int numBytes)\n\t{\n\t\tbytes = new byte[numBytes];\n\t}\n\n\t/**\n\t * Store the value of an {@code n}-bit (signed) integer in a portion of the bit string.\n\t * This assumes that the integer needs at most 32 bits, so that it can be stored in an {@code int}.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t * @param value The value to store\n\t */\n\tpublic void setInt(int offset, int n, int value) throws UMBException\n\t{\n\t\tif (n > 32) {\n\t\t\tthrow new UMBException(\"Cannot store integer of \" + n + \" bits (too large for Java int)\");\n\t\t}\n\t\t// Store bits into the byte array\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\t// Copy the i-th (least significant) bit of value to the appropriate bit in bytes\n\t\t\tchar valueBitShifted = (char) (((value >>> i) & 1) << ((offset + i) & 7));\n\t\t\tchar byteMask = (char) ('\\u0001' << ((offset + i) & 7));\n\t\t\tbytes[(offset + i) >> 3] = (byte) ((bytes[(offset + i) >> 3] & ~(byteMask)) | (valueBitShifted));\n\t\t}\n\t}\n\n\t/**\n\t * Store the value of an {@code n}-bit unsigned integer in a portion of the bit string.\n\t * This assumes that the integer needs at most 32 bits, so that it can be stored in an {@code int}.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t * @param value The value to store\n\t */\n\tpublic void setUInt(int offset, int n, int value) throws UMBException\n\t{\n\t\tif (n >= 32) {\n\t\t\tthrow new UMBException(\"Cannot store unsigned integer of \" + n + \" bits (too large for Java int)\");\n\t\t}\n\t\t// Storing (including bit truncation) is the same as for signed integers\n\t\tsetInt(offset, n, value);\n\t}\n\n\t/**\n\t * Store the value of an {@code n}-bit (signed) integer in a portion of the bit string.\n\t * This assumes that the integer needs at most 64 bits, so that it can be stored in a {@code long}.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t * @param value The value to store\n\t */\n\tpublic void setLong(int offset, int n, long value) throws UMBException\n\t{\n\t\tif (n > 64) {\n\t\t\tthrow new UMBException(\"Cannot store integer of \" + n + \" bits (too large for Java long)\");\n\t\t}\n\t\t// Store bits into the byte array\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\t// Copy the i-th (least significant) bit of value to the appropriate bit in bytes\n\t\t\tchar valueBitShifted = (char) (((value >>> i) & 1) << ((offset + i) & 7));\n\t\t\tchar byteMask = (char) ('\\u0001' << ((offset + i) & 7));\n\t\t\tbytes[(offset + i) >> 3] = (byte) ((bytes[(offset + i) >> 3] & ~(byteMask)) | (valueBitShifted));\n\t\t}\n\t}\n\n\t/**\n\t * Store the value of an {@code n}-bit unsigned integer in a portion of the bit string.\n\t * This assumes that the integer needs at most 64 bits, so that it can be stored in a {@code long}.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t * @param value The value to store\n\t */\n\tpublic void setULong(int offset, int n, long value) throws UMBException\n\t{\n\t\tif (n >= 64) {\n\t\t\tthrow new UMBException(\"Cannot store unsigned integer of \" + n + \" bits (too large for Java long)\");\n\t\t}\n\t\t// Storing (including bit truncation) is the same as for signed integers\n\t\tsetLong(offset, n, value);\n\t}\n\n\t/**\n\t * Store the value of a (64-bit) double in a portion of the bit string.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion (should be 64)\n\t * @param value The value to store\n\t */\n\tpublic void setDouble(int offset, int n, double value) throws UMBException\n\t{\n\t\tif (n != 64) {\n\t\t\tthrow new UMBException(\"Cannot store double of \" + n + \" bits (should be 64)\");\n\t\t}\n\t\t// Store bits in a long and then copy to the byte array\n\t\tlong valueLong = Double.doubleToLongBits(value);\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\t// Copy the i-th (least significant) bit of valueLong to the appropriate bit in bytes\n\t\t\tchar valueBitShifted = (char) (((valueLong >>> i) & 1) << ((offset + i) & 7));\n\t\t\tchar byteMask = (char) ('\\u0001' << ((offset + i) & 7));\n\t\t\tbytes[(offset + i) >> 3] = (byte) ((bytes[(offset + i) >> 3] & ~(byteMask)) | (valueBitShifted));\n\t\t}\n\t}\n\n\t/**\n\t * Store the value of a boolean in a portion of the bit string.\n\t * The boolean is stored as an {@code n}-bit unsigned integer and is false iff == 0\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t * @param value The value to store\n\t */\n\tpublic void setBoolean(int offset, int n, boolean value) throws UMBException\n\t{\n\t\tif (n >= 32) {\n\t\t\tthrow new UMBException(\"Cannot store unsigned integer of \" + n + \" bits (too large for Java int)\");\n\t\t}\n\t\tsetUInt(offset, n, value ? 1 : 0);\n\t}\n\n\t/**\n\t * Get the value of an {@code n}-bit (signed) integer, extracted from a portion of the bit string.\n\t * If the value does not fit into a standard Java (32-bit) signed int, an exception is thrown.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t */\n\tpublic int getInt(int offset, int n) throws UMBException\n\t{\n\t\tif (n > 32) {\n\t\t\tthrow new UMBException(\"Cannot extract integer of \" + n + \" bits (too large for Java int)\");\n\t\t}\n\t\t// Extract bits into an int\n\t\tint value = 0;\n\t\tfor (int i = offset + n - 1; i >= offset; i--) {\n\t\t\tvalue = (value << 1) | ((bytes[i >> 3] & (1L << (i & 7))) != 0 ? 1 : 0);\n\t\t}\n\t\t// Sign extend if necessary\n\t\tif ((value & (1 << (n - 1))) != 0) {\n\t\t\tvalue -= (1 << n);\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Get the value of an {@code n}-bit unsigned integer, extracted from a portion of the bit string.\n\t * If the value does not fit into a standard Java (32-bit) signed int, an exception is thrown.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t */\n\tpublic int getUInt(int offset, int n) throws UMBException\n\t{\n\t\tif (n >= 32) {\n\t\t\tthrow new UMBException(\"Cannot extract unsigned integer of \" + n + \" bits (too large for Java int)\");\n\t\t}\n\t\t// Extract bits into an int\n\t\tint value = 0;\n\t\tfor (int i = offset + n - 1; i >= offset; i--) {\n\t\t\tvalue = (value << 1) | ((bytes[i >> 3] & (1L << (i & 7))) != 0 ? 1 : 0);\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Get the value of an {@code n}-bit (signed) integer, extracted from a portion of the bit string.\n\t * If the value does not fit into a standard Java (64-bit) signed long, an exception is thrown.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t */\n\tpublic long getLong(int offset, int n) throws UMBException\n\t{\n\t\tif (n > 64) {\n\t\t\tthrow new UMBException(\"Cannot extract integer of \" + n + \" bits (too large for Java long)\");\n\t\t}\n\t\t// Extract bits into a long\n\t\tlong value = 0;\n\t\tfor (int i = offset + n - 1; i >= offset; i--) {\n\t\t\tvalue = (value << 1) | ((bytes[i >> 3] & (1L << (i & 7))) != 0 ? 1 : 0);\n\t\t}\n\t\t// Sign extend if necessary\n\t\tif (n < 64 && (value & (1L << (n - 1))) != 0) {\n\t\t\tvalue -= (1L << n);\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Get the value of an {@code n}-bit unsigned integer, extracted from a portion of the bit string.\n\t * If the value does not fit into a standard Java (64-bit) signed long, an exception is thrown.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t */\n\tpublic long getULong(int offset, int n) throws UMBException\n\t{\n\t\tif (n >= 64) {\n\t\t\tthrow new UMBException(\"Cannot extract unsigned integer of \" + n + \" bits (too large for Java long)\");\n\t\t}\n\t\t// Extract bits into a long\n\t\tlong value = 0;\n\t\tfor (int i = offset + n - 1; i >= offset; i--) {\n\t\t\tvalue = (value << 1) | ((bytes[i >> 3] & (1L << (i & 7))) != 0 ? 1 : 0);\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Get the value of a (64-bit) double, extracted from a portion of the bit string.\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion (should be 64)\n\t */\n\tpublic double getDouble(int offset, int n) throws UMBException\n\t{\n\t\tif (n != 64) {\n\t\t\tthrow new UMBException(\"Cannot extract double of \" + n + \" bits (should be 64)\");\n\t\t}\n\t\t// Extract bits into a long\n\t\tlong value = 0;\n\t\tfor (int i = offset + n - 1; i >= offset; i--) {\n\t\t\tvalue = (value << 1) | ((bytes[i >> 3] & (1L << (i & 7))) != 0 ? 1 : 0);\n\t\t}\n\t\treturn Double.longBitsToDouble(value);\n\t}\n\n\t/**\n\t * Get the value of a boolean, extracted from a portion of the bit string.\n\t * The boolean is stored as an {@code n}-bit unsigned integer and is false iff == 0\n\t * @param offset The first bit of the bitstring portion\n\t * @param n The size (in bits) of the bitstring portion\n\t */\n\tpublic boolean getBoolean(int offset, int n) throws UMBException\n\t{\n\t\tif (n >= 32) {\n\t\t\tthrow new UMBException(\"Cannot extract boolean of \" + n + \" bits (too large for Java int)\");\n\t\t}\n\t\treturn getUInt(offset, n) != 0;\n\t}\n\n\t/**\n\t * Create a string representation of a portion of the bit string.\n\t * @param offset The first bit of the portion\n\t * @param size The size (in bits) of the portion\n\t */\n\tpublic String toString(int offset, int size)\n\t{\n\t\tStringBuilder sb = new StringBuilder();\n\t\tint end = offset + size;\n\t\tfor (int i = end - 1; i >= offset; i--) {\n\t\t\tsb.append((bytes[i >> 3] & (1L << (i & 7))) != 0 ? \"1\" : \"0\");\n\t\t}\n\t\treturn sb.toString();\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn toString(0, bytes.length * 8);\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBException.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\npublic class UMBException extends Exception\n{\n\t/**\n\t * Constructs a new UMBException with the provided message.\n\t * @param message Message\n\t */\n\tpublic UMBException(String message)\n\t{\n\t\tsuper(message);\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBFormat.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\nimport java.util.List;\nimport java.util.function.Predicate;\n\n/**\n * Class storing conventions about how/where entities are stored in a UMB file.\n */\npublic class UMBFormat\n{\n\t/** Filename for (JSON) index */\n\tpublic static final String INDEX_FILE = \"index.json\";\n\n\t/** File extension for binary files in the archive */\n\tpublic static final String BIN_FILE_EXT = \".bin\";\n\n\t// Core model information\n\n\tpublic static final String STATE_CHOICE_OFFSETS_FILE = \"state-to-choices\" + BIN_FILE_EXT;\n\tpublic static final String STATE_PLAYERS = \"state-to-player\" + BIN_FILE_EXT;\n\tpublic static final String INITIAL_STATES_FILE = \"state-is-initial\" + BIN_FILE_EXT;\n\tpublic static final String MARKOVIAN_STATES_FILE = \"state-is-markovian\" + BIN_FILE_EXT;\n\tpublic static final String STATE_EXIT_RATES_FILE = \"state-to-exit-rate\" + BIN_FILE_EXT;\n\tpublic static final String CHOICE_BRANCH_OFFSETS_FILE = \"choice-to-branches\" + BIN_FILE_EXT;\n\tpublic static final String BRANCH_TARGETS_FILE = \"branch-to-target\" + BIN_FILE_EXT;\n\tpublic static final String BRANCH_PROBABILITIES_FILE = \"branch-to-probability\" + BIN_FILE_EXT;\n\tpublic static final String ACTIONS_FOLDER = \"actions\";\n\tpublic static final String OBSERVATIONS_FOLDER = \"observations\";\n\tpublic static final String OBSERVATIONS_FILE = \"values\" + BIN_FILE_EXT;\n\n\t// String list storage info\n\n\tpublic static final String STRING_OFFSETS_FILE = \"string-mapping\" + BIN_FILE_EXT;\n\tpublic static final String STRINGS_FILE = \"strings\" + BIN_FILE_EXT;\n\n\t// Annotations\n\n\t/** Location for annotations (folder in zip) */\n\tpublic static final String ANNOTATIONS_FOLDER = \"annotations\";\n\n\t/** Filename for storing an annotation's values */\n\tpublic static final String ANNOTATION_VALUES_FILE = \"values\" + BIN_FILE_EXT;\n\n\t/** Filename for storing a stochastic annotation's distribution mapping */\n\tpublic static final String ANNOTATION_DISTRIBUTION_FILE = \"distribution-mapping\" + BIN_FILE_EXT;\n\n\t/** Filename for storing a stochastic annotation's distribution mapping */\n\tpublic static final String ANNOTATION_PROBABILITIES_FILE = \"probabilities\" + BIN_FILE_EXT;\n\n\t// Subfolders for built-in annotation groups\n\n\tpublic static final String AP_ANNOTATIONS_GROUP = \"aps\";\n\tpublic static final String REWARD_ANNOTATIONS_GROUP = \"rewards\";\n\n\t// Valuations\n\n\t/** Location for valuations (folder in zip) */\n\tpublic static final String VALUATIONS_FOLDER = \"valuations\";\n\n\t/** Filename for storing valuation data (variable values) */\n\tpublic static final String VALUATIONS_FILE = \"valuations\" + BIN_FILE_EXT;\n\n\t/** Filename for storing valuation classes */\n\tpublic static final String VALUATION_CLASSES = \"valuation-to-class\" + BIN_FILE_EXT;\n\n\t// Default values for binary files\n\n\tpublic enum BinFileDefaultValue\n\t{\n\t\tIDENTITY, ZERO, ONE\n\t}\n\n\t// Allowable compression formats\n\n\tpublic enum CompressionFormat\n\t{\n\t\tGZIP,\n\t\tXZ;\n\t\tpublic String extension() {\n\t\t\tswitch (this) {\n\t\t\t\tcase GZIP: return \"gz\";\n\t\t\t\tcase XZ: return \"xz\";\n\t\t\t\tdefault: throw new IllegalStateException(\"Unknown compression format: \" + this);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Allowable compression formats (strict) */\n\tpublic static final List<CompressionFormat> ALLOWED_COMPRESSION_FORMATS = List.of(CompressionFormat.GZIP, CompressionFormat.XZ);\n\n\t/** Default compression format */\n\tpublic static final CompressionFormat DEFAULT_COMPRESSION_FORMAT = CompressionFormat.GZIP;\n\n\t/**\n\t * Get the filename for the offsets mapping string indices to string data within some folder\n\t */\n\tpublic static String stringOffsetsFile(String folderName)\n\t{\n\t\treturn folderName + \"/\" + STRING_OFFSETS_FILE;\n\t}\n\n\t/**\n\t * Get the filename for the string data within some folder\n\t */\n\tpublic static String stringsFile(String folderName)\n\t{\n\t\treturn folderName + \"/\" + STRINGS_FILE;\n\t}\n\n\t/**\n\t * Get the folder name for observations\n\t */\n\tpublic static String observationsFolder(UMBIndex.UMBEntity entity)\n\t{\n\t\treturn OBSERVATIONS_FOLDER + \"/\" + entity;\n\t}\n\n\t/**\n\t * Get the filename for observations\n\t */\n\tpublic static String observationsFile(UMBIndex.UMBEntity entity)\n\t{\n\t\treturn observationsFolder(entity) + \"/\" + OBSERVATIONS_FILE;\n\t}\n\n\t/**\n\t * Get the folder name for an annotation\n\t */\n\tpublic static String annotationFolder(String group, String id, UMBIndex.UMBEntity entity)\n\t{\n\t\treturn ANNOTATIONS_FOLDER + \"/\" + group + \"/\" + id + \"/\" + entity;\n\t}\n\n\t/**\n\t * Get the filename for an annotation\n\t */\n\tpublic static String annotationFile(String group, String id, UMBIndex.UMBEntity entity)\n\t{\n\t\treturn annotationFolder(group, id, entity) + \"/\" + ANNOTATION_VALUES_FILE;\n\t}\n\n\t/**\n\t * Get the filename for a stochastic annotation's distribution mapping\n\t */\n\tpublic static String annotationDistributionFile(String group, String id, UMBIndex.UMBEntity entity)\n\t{\n\t\treturn annotationFolder(group, id, entity) + \"/\" + ANNOTATION_DISTRIBUTION_FILE;\n\t}\n\n\t/**\n\t * Get the filename for a stochastic annotation's probabilities\n\t */\n\tpublic static String annotationProbabilitiesFile(String group, String id, UMBIndex.UMBEntity entity)\n\t{\n\t\treturn annotationFolder(group, id, entity) + \"/\" + ANNOTATION_PROBABILITIES_FILE;\n\t}\n\n\t/**\n\t * Get the folder name for the valuations for some entity\n\t */\n\tpublic static String valuationsFolder(UMBIndex.UMBEntity entity)\n\t{\n\t\treturn VALUATIONS_FOLDER + \"/\" + entity;\n\t}\n\n\t/**\n\t * Get the filename for the valuation data for some entity\n\t */\n\tpublic static String valuationsFile(UMBIndex.UMBEntity entity)\n\t{\n\t\treturn valuationsFolder(entity) + \"/\" + VALUATIONS_FILE;\n\t}\n\n\t/**\n\t * Get the filename for the valuation classes for some entity\n\t */\n\tpublic static String valuationClassesFile(UMBIndex.UMBEntity entity)\n\t{\n\t\treturn valuationsFolder(entity) + \"/\" + VALUATION_CLASSES;\n\t}\n\n\t// Utility functions\n\n\t/**\n\t * Check whether a string represents a valid ID.\n\t * @param id Proposed ID\n\t */\n\tpublic static boolean isValidID(String id)\n\t{\n\t\treturn id.matches(\"[a-z0-9_-]+\");\n\t}\n\n\t/**\n\t * Convert a string to a valid ID.\n\t * @param s String to convert\n\t */\n\tpublic static String toValidID(String s)\n\t{\n\t\treturn s.toLowerCase().replaceAll(\"[^a-z0-9_-]\", \"_\").replace(\"^[0-9]\", \"_\");\n\t}\n\n\t/**\n\t * Convert a string to a unique valid ID.\n\t * @param s String to convert\n\t * @param idExists Predicate defining what IDs already exist\n\t */\n\tpublic static String toValidUniqueID(String s, Predicate<String> idExists)\n\t{\n\t\tString id = toValidID(s);\n\t\twhile (idExists.test(id)) {\n\t\t\tid += \"_\";\n\t\t}\n\t\treturn id;\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBIndex.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\nimport io.github.pmctools.umbj.UMBType.Type;\n\nimport com.google.gson.FieldNamingPolicy;\nimport com.google.gson.Gson;\nimport com.google.gson.GsonBuilder;\nimport com.google.gson.JsonDeserializationContext;\nimport com.google.gson.JsonDeserializer;\nimport com.google.gson.JsonElement;\nimport com.google.gson.JsonParseException;\nimport com.google.gson.JsonPrimitive;\nimport com.google.gson.JsonSerializationContext;\nimport com.google.gson.JsonSerializer;\nimport com.google.gson.annotations.SerializedName;\n\nimport java.time.Instant;\nimport java.util.*;\nimport java.util.stream.Collectors;\n\n/**\n * Representation of the (JSON) index for a UMB file.\n */\npublic class UMBIndex\n{\n\t// Index data, stored in a form that allows JSON import/export via GSON\n\n\t/** Major version of the UMB format used for this file */\n\tpublic Integer formatVersion = UMBVersion.MAJOR;\n\t/** Minor version of the UMB format used for this file */\n\tpublic Integer formatRevision = UMBVersion.MINOR;\n\t/** Model metadata */\n\tpublic ModelData modelData = new ModelData();\n\t/** File metadata */\n\tpublic FileData fileData = new FileData();\n\t/** Transition system details */\n\tpublic TransitionSystem transitionSystem = new TransitionSystem();\n\t/** Annotations, arranged by group and then by annotation ID, in ordered maps */\n\tpublic LinkedHashMap<String, LinkedHashMap<String, Annotation>> annotations = new LinkedHashMap<>();\n\t/** Valuation descriptions, arranged by entity type */\n\tpublic LinkedHashMap<UMBEntity, ValuationDescription> valuations = new LinkedHashMap<>();\n\n\t// Further info about annotations\n\n\t/** Names of groups into which annotations are organised */\n\tpublic transient List<String> annotationGroups = new ArrayList<>();\n\t/** Map from annotation aliases to IDs for each annotation group */\n\tpublic transient Map<String, Map<String, String>> annotationAliasMaps = new LinkedHashMap<>();\n\n\t// Fake annotation objects for some data\n\n\t/** Annotation object for actions (stored in a similar way to annotations) */\n\tpublic transient Annotation actionsAnnotation = createStandaloneAnnotation(UMBFormat.ACTIONS_FOLDER, UMBType.create(Type.STRING));\n\t/** Annotation object for observations (stored in a similar way to annotations) */\n\tpublic transient Annotation observationsAnnotation = createStandaloneAnnotation(UMBFormat.OBSERVATIONS_FOLDER, UMBType.create(Type.INT));\n\n\t// Enums\n\n\t/** UMB file entities which can be annotated/indexed */\n\tpublic enum UMBEntity implements UMBField\n\t{\n\t\tSTATES, CHOICES, BRANCHES, OBSERVATIONS, PLAYERS;\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase STATES: return \"states\";\n\t\t\t\tcase CHOICES: return \"choices\";\n\t\t\t\tcase BRANCHES: return \"branches\";\n\t\t\t\tcase OBSERVATIONS: return \"observations\";\n\t\t\t\tcase PLAYERS: return \"players\";\n\t\t\t\tdefault: return \"?\";\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Notions of time */\n\tpublic enum Time implements UMBField\n\t{\n\t\tDISCRETE, STOCHASTIC, URGENT_STOCHASTIC\n\t}\n\n\t/** Common model types */\n\tpublic enum ModelType implements UMBField\n\t{\n\t\tDTMC, CTMC, MDP, POMDP, CTMDP, MA, TSG, LTS, TG,\n\t\tIDTMC, IMDP, IPOMDP, ITSG\n\t}\n\n\t// Index contents\n\n\t/** Model metadata */\n\tpublic static class ModelData\n\t{\n\t\t/** (Short) name of the model */\n\t\tpublic String name;\n\t\t/** Version info for the model */\n\t\tpublic String version;\n\t\t/** Model author(s) */\n\t\tpublic List<String> authors;\n\t\t/** Model description */\n\t\tpublic String description;\n\t\t/** Additional comments about the model */\n\t\tpublic String comment;\n\t\t/** DOI of the paper where the model was introduced/used/described */\n\t\tpublic String doi;\n\t\t/** URL pointing to more information about the model */\n\t\tpublic String url;\n\n\t\t/**\n\t\t * Check this object is valid; throw an exception if not.\n\t\t */\n\t\tpublic void validate() throws UMBException\n\t\t{\n\t\t\t// All optional: nothing to do\n\t\t}\n\t}\n\n\t/** File metadata */\n\tpublic static class FileData\n\t{\n\t\t/** The tool used to create this file */\n\t\tpublic String tool;\n\t\t/** Version of the tool used to create this file */\n\t\tpublic String toolVersion;\n\t\t/** Date of file creation */\n\t\tpublic Long creationDate = Instant.now().getEpochSecond();\n\t\t/** Tool parameters (e.g. string or list of command-line arguments) used */\n\t\tpublic Object parameters;\n\n\t\t/**\n\t\t * Check this object is valid; throw an exception if not.\n\t\t */\n\t\tpublic void validate() throws UMBException\n\t\t{\n\t\t\t// All optional: nothing to do\n\t\t}\n\t}\n\n\t/** Transition system details */\n\tpublic static class TransitionSystem\n\t{\n\t\t/** Notion of time used */\n\t\tpublic Time time;\n\t\t/** Number of players */\n\t\t@SerializedName(\"#players\")\n\t\tpublic Integer numPlayers;\n\t\t/** Number of states */\n\t\t@SerializedName(\"#states\")\n\t\tpublic Long numStates;\n\t\t/** Number of initial states */\n\t\t@SerializedName(\"#initial-states\")\n\t\tpublic Long numInitialStates;\n\t\t/** Number of choices */\n\t\t@SerializedName(\"#choices\")\n\t\tpublic Long numChoices;\n\t\t/** Number of choice actions */\n\t\t@SerializedName(\"#choice-actions\")\n\t\tpublic Integer numChoiceActions;\n\t\t/** Number of branches */\n\t\t@SerializedName(\"#branches\")\n\t\tpublic Long numBranches;\n\t\t/** Number of branch actions */\n\t\t@SerializedName(\"#branch-actions\")\n\t\tpublic Integer numBranchActions;\n\t\t/** Number of observations */\n\t\t@SerializedName(\"#observations\")\n\t\tpublic Integer numObservations;\n\t\t/** Observation style */\n\t\tpublic UMBEntity observationsApplyTo;\n\t\t/** Type of branch probabilities */\n\t\tpublic UMBType branchProbabilityType;\n\t\t/** Type of exit rates */\n        public UMBType exitRateType;\n\t\t/** Type of probabilities for stochastic observations */\n\t\tpublic UMBType observationProbabilityType;\n\t\t/** Names of players (for games) */\n\t\tpublic List<String> playerNames;\n\n\t\t/**\n\t\t * Check this object is valid; throw an exception if not.\n\t\t */\n\t\tpublic void validate() throws UMBException\n\t\t{\n\t\t\tcheckFieldExists(time, \"time\");\n\t\t\tcheckFieldExists(numPlayers, \"numPlayers\");\n\t\t\tif (numPlayers < 0) {\n\t\t\t\tthrow new UMBException(\"Number of players must be non-negative\");\n\t\t\t}\n\t\t\tcheckFieldExists(numStates, \"numStates\");\n\t\t\tif (numStates < 0) {\n\t\t\t\tthrow new UMBException(\"Number of states must be at least 1\");\n\t\t\t}\n\t\t\tcheckFieldExists(numInitialStates, \"numInitialStates\");\n\t\t\tif (numInitialStates < 0) {\n\t\t\t\tthrow new UMBException(\"Number of initial states must be non-negative\");\n\t\t\t}\n\t\t\tcheckFieldExists(numChoices, \"numChoices\");\n\t\t\tif (numChoices < 0) {\n\t\t\t\tthrow new UMBException(\"Number of choices must be non-negative\");\n\t\t\t}\n\t\t\tcheckFieldExists(numChoiceActions, \"numChoiceActions\");\n\t\t\tif (numChoiceActions < 0) {\n\t\t\t\tthrow new UMBException(\"Number of choice actions must be non-negative\");\n\t\t\t}\n\t\t\tcheckFieldExists(numBranches, \"numBranches\");\n\t\t\tif (numBranches < 0) {\n\t\t\t\tthrow new UMBException(\"Number of branches must be non-negative\");\n\t\t\t}\n\t\t\tcheckFieldExists(numBranchActions, \"numBranchActions\");\n\t\t\tif (numBranchActions < 0) {\n\t\t\t\tthrow new UMBException(\"Number of branch actions must be non-negative\");\n\t\t\t}\n\t\t\tcheckFieldExists(numObservations, \"numObservations\");\n\t\t\tif (numObservations < 0) {\n\t\t\t\tthrow new UMBException(\"Number of observations must be non-negative\");\n\t\t\t}\n\t\t\tif (numObservations > 0) {\n\t\t\t\tcheckFieldExists(observationsApplyTo, \"observationsApplyTo\");\n\t\t\t\tif (!EnumSet.of(UMBEntity.STATES, UMBEntity.BRANCHES).contains(observationsApplyTo)) {\n\t\t\t\t\tthrow new UMBException(\"Invalid value \\\" + observationsApplyTo\" + \"\\\" for \" + fieldNameToUMB(\"observationsApplyTo\"));\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (branchProbabilityType != null) {\n\t\t\t\tif (!branchProbabilityType.type.isContinuousNumeric()) {\n\t\t\t\t\tthrow new UMBException(\"Branch probability type must be a continuous numeric type\");\n\t\t\t\t}\n\t\t\t\tif (!branchProbabilityType.isDefaultSize()) {\n\t\t\t\t\tthrow new UMBException(\"Branch probability type must have default size\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tcheckFieldExistsIff(exitRateType, \"exitRateType\", time == Time.STOCHASTIC || time == Time.URGENT_STOCHASTIC);\n\t\t\tif (exitRateType != null) {\n\t\t\t\tif (!exitRateType.type.isContinuousNumeric()) {\n\t\t\t\t\tthrow new UMBException(\"Exit rate type must be a continuous numeric type\");\n\t\t\t\t}\n\t\t\t\tif (!exitRateType.isDefaultSize()) {\n\t\t\t\t\tthrow new UMBException(\"Exit rate type must have default size\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (observationProbabilityType != null) {\n\t\t\t\tif (!observationProbabilityType.type.isContinuousNumeric()) {\n\t\t\t\t\tthrow new UMBException(\"Observation probability type must be a continuous numeric type\");\n\t\t\t\t}\n\t\t\t\tif (!observationProbabilityType.isDefaultSize()) {\n\t\t\t\t\tthrow new UMBException(\"Observation probability type must have default size\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (numPlayers > 1) {\n\t\t\t\tcheckFieldExists(playerNames, \"playerNames\");\n\t\t\t\tif (playerNames.size() != numPlayers) {\n\t\t\t\t\tthrow new UMBException(\"Player name list does not match number of players\");\n\t\t\t\t}\n\t\t\t\t// check names are unique\n\t\t\t\tif (!playerNames.stream().allMatch(new HashSet<>()::add)) {\n\t\t\t\t\tthrow new UMBException(\"Player names must be unique\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (playerNames != null) {\n\t\t\t\t\tthrow new UMBException(\"Player names should be omitted in non-game models\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Representation of a model annotation */\n\tpublic static class Annotation\n\t{\n\t\t/** Group ID (duplicated for convenience; same as map key) */\n\t\tpublic transient String group;\n\t\t/** ID (duplicated for convenience; same as map key) */\n\t\tpublic transient String id;\n\t\t/** Alias (name) */\n\t\tpublic String alias;\n\t\t/** Description */\n\t\tpublic String description;\n\t\t/** List of entities to which this annotation applies */\n\t\tpublic List<UMBEntity> appliesTo = new ArrayList<>();\n\t\t/** Type of values stored */\n\t\tpublic UMBType type;\n\t\t/** For string annotations, the number of strings */\n\t\t@SerializedName(\"#strings\")\n\t\tpublic Integer numStrings;\n\t\t/** For stochastic annotations, the type for probability values */\n\t\tpublic UMBType probabilityType;\n\t\t/** For stochastic annotations, the sum of the supports of the distributions */\n\t\t@SerializedName(\"#probabilities\")\n\t\tpublic Integer numProbabilities;\n\n\t\t/**\n\t\t * Add an entity to which this annotation applies.\n\t\t * @param entity The entity to add\n\t\t */\n\t\tpublic void addAppliesTo(UMBEntity entity)\n\t\t{\n\t\t\tappliesTo.add(entity);\n\t\t}\n\n\t\t/**\n\t\t * Check this object is valid; throw an exception if not.\n\t\t */\n\t\tpublic void validate() throws UMBException\n\t\t{\n\t\t\tcheckFieldExists(appliesTo, \"appliesTo\");\n\t\t\tif (appliesTo.isEmpty()) {\n\t\t\t\tthrow new UMBException(\"Annotation \\\"\" + id + \"\\\" in group \\\"\" + group + \"\\\" is empty\");\n\t\t\t}\n\t\t\tcheckFieldExists(type, \"type\");\n\t\t\tcheckFieldExistsIff(numStrings, \"numStrings\", type.type == Type.STRING);\n\t\t\tif (type.type == Type.STRING) {\n\t\t\t\tif (numStrings <= 0) {\n\t\t\t\t\tthrow new UMBException(\"Number of strings must be positive\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tcheckFieldExistsIff(numProbabilities, \"#probabilities\", probabilityType != null);\n\t\t\tif (probabilityType != null) {\n\t\t\t\tif (numProbabilities <= 0) {\n\t\t\t\t\tthrow new UMBException(\"Number of probabilities must be positive\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Get the \"name\" of this annotation, i.e., the alias if present or the ID if not.\n\t\t */\n\t\tpublic String getName()\n\t\t{\n\t\t\treturn alias == null ? id : alias;\n\t\t}\n\n\t\t/**\n\t\t * Check whether this annotation applies to the specified entity.\n\t\t * @param entity The entity to check\n\t\t */\n\t\tpublic boolean appliesTo(UMBEntity entity)\n\t\t{\n\t\t\treturn appliesTo.contains(entity);\n\t\t}\n\n\t\t/**\n\t\t * Get the type of the values stored in the annotation\n\t\t */\n\t\tpublic UMBType getType()\n\t\t{\n\t\t\treturn type;\n\t\t}\n\n\t\t/**\n\t\t * Get the number of strings (only valid for string annotations)\n\t\t */\n\t\tpublic int getNumStrings()\n\t\t{\n\t\t\treturn numStrings;\n\t\t}\n\n\t\t/**\n\t\t * Get the type for probability values (for stochastic annotations)\n\t\t */\n\t\tpublic UMBType getProbabilityType()\n\t\t{\n\t\t\treturn probabilityType;\n\t\t}\n\n\t\t/**\n\t\t * Get the name of the folder to store this annotation, for the specified entity.\n\t\t * @param entity The entity\n\t\t */\n\t\tpublic String getFolderName(UMBEntity entity)\n\t\t{\n\t\t\treturn UMBFormat.annotationFolder(group, id, entity);\n\t\t}\n\n\t\t/**\n\t\t * Get the name of the file to store this annotation, for the specified entity.\n\t\t * @param entity The entity\n\t\t */\n\t\tpublic String getFilename(UMBEntity entity)\n\t\t{\n\t\t\treturn UMBFormat.annotationFile(group, id, entity);\n\t\t}\n\n\t\t/**\n\t\t * Get the filename for the distribution mapping if this is a stochastic annotation, for the specified entity.\n\t\t * @param entity The entity\n\t\t */\n\t\tpublic String getDistributionFilename(UMBEntity entity)\n\t\t{\n\t\t\treturn UMBFormat.annotationDistributionFile(group, id, entity);\n\t\t}\n\n\t\t/**\n\t\t * Get the filename for the probabilities if this is a stochastic annotation, for the specified entity.\n\t\t * @param entity The entity\n\t\t */\n\t\tpublic String getProbabilitiesFilename(UMBEntity entity)\n\t\t{\n\t\t\treturn UMBFormat.annotationProbabilitiesFile(group, id, entity);\n\t\t}\n\t}\n\n\t/**\n\t * Annotation object for data stored in the same style as an annotation,\n\t * but without the usual conventions regarding group, id, folder, etc.\n\t */\n\tpublic static class StandaloneAnnotation extends Annotation\n\t{\n\t\t/** Folder where data is stored */\n\t\tpublic String folderName;\n\n\t\t@Override\n\t\tpublic String getFolderName(UMBEntity entity)\n\t\t{\n\t\t\treturn folderName + \"/\" + entity;\n\t\t}\n\n\t\t@Override\n\t\tpublic String getFilename(UMBEntity entity)\n\t\t{\n\t\t\treturn getFolderName(entity) + \"/\" + UMBFormat.ANNOTATION_VALUES_FILE;\n\t\t}\n\t}\n\n\t/** Info about valuations (for e.g. states, observations) */\n\tpublic static class ValuationDescription\n\t{\n\t\t/** If true, valuations are unique within their entity */\n\t\tpublic Boolean unique;\n\t\t/** If there are any string variables, the number of strings */\n\t\t@SerializedName(\"#strings\")\n\t\tpublic Integer numStrings;\n\t\t/** Descriptions for each class of valuations for an entity */\n\t\tpublic List<ValuationClassDescription> classes = new ArrayList<>();\n\n\t\tpublic ValuationDescription(boolean unique)\n\t\t{\n\t\t\tthis.unique = unique;\n\t\t}\n\t}\n\n\t/** Info about a class of valuation (for e.g. states, observations) */\n\tpublic static class ValuationClassDescription\n\t{\n\t\t/** List of variables/padding making up each state valuation */\n\t\tpublic List<ValuationVariable> variables = new ArrayList<>();\n\n\t\t/**\n\t\t * Get the total size of the variables/padding (in bits).\n\t\t */\n\t\tpublic int numBits()\n\t\t{\n\t\t\tint numBits = 0;\n\t\t\tfor (ValuationVariable variable : variables) {\n\t\t\t\tnumBits += variable.numBits();\n\t\t\t}\n\t\t\treturn numBits;\n\t\t}\n\t}\n\n\t/** Info about a valuation variable/padding */\n\tpublic static class ValuationVariable\n\t{\n\t\t// For variables\n\t\t/** Variable name */\n\t\tpublic String name;\n\t\t/** Is the variable optional */\n\t\tpublic Boolean isOptional;\n\t\t/** Variable type (including size) */\n\t\tpublic UMBType type;\n\t\t// For padding\n\t\t/** Amount of padding (number of bits) */\n\t\tpublic Integer padding;\n\n\t\t/**\n\t\t * Is this a variable (as opposed to padding)?\n\t\t */\n\t\tpublic boolean isVariable()\n\t\t{\n\t\t\treturn padding == null;\n\t\t}\n\n\t\t/**\n\t\t * Is this padding (as opposed to a variable)?\n\t\t */\n\t\tpublic boolean isPadding()\n\t\t{\n\t\t\treturn padding != null;\n\t\t}\n\n\t\t/**\n\t\t * Get the size of this variable/padding (in bits).\n\t\t */\n\t\tpublic int numBits()\n\t\t{\n\t\t\tif (padding != null) {\n\t\t\t\treturn padding;\n\t\t\t} else if (type.size != null) {\n\t\t\t\treturn type.size;\n\t\t\t} else {\n\t\t\t\treturn 0;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Perform validation of this object\n\t */\n\tpublic void validate() throws UMBException\n\t{\n\t\tcheckFieldExists(formatVersion, \"formatVersion\");\n\t\tcheckFieldExists(formatRevision, \"formatVersion\");\n\t\tif (modelData != null) {\n\t\t\tmodelData.validate();\n\t\t}\n\t\tif (fileData != null) {\n\t\t\tfileData.validate();\n\t\t}\n\t\tcheckFieldExists(transitionSystem, \"transitionSystem\");\n\t\ttransitionSystem.validate();\n\t\tif (annotations != null) {\n\t\t\tfor (Map.Entry<String, LinkedHashMap<String, Annotation>> entry : annotations.entrySet()) {\n\t\t\t\tvalidateAnnotations(entry.getKey(), entry.getValue());\n\t\t\t}\n\t\t}\n\t\tif (valuations != null) {\n\t\t\tfor (Map.Entry<UMBEntity, ValuationDescription> entry : valuations.entrySet()) {\n\t\t\t\tcheckFieldExists(entry.getValue().unique, \"valuations.\" + entry.getKey() + \".unique\");\n\t\t\t\tfor (ValuationClassDescription valuationClassDescription : entry.getValue().classes) {\n\t\t\t\t\tvalidateValuationDescription(valuationClassDescription, \"valuations.classes.\" + entry.getKey());\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Perform validation of the annotations\n\t */\n\tpublic void validateAnnotations(String group, Map<String, Annotation> annotations) throws UMBException\n\t{\n\t\tfor (Map.Entry<String, Annotation> entry : annotations.entrySet()) {\n\t\t\tif (\"\".equals(entry.getKey())) {\n\t\t\t\tthrow new UMBException(\"Empty annotation ID in group \\\"\" + group + \"\\\"\");\n\t\t\t}\n\t\t\tif (!UMBFormat.isValidID(entry.getKey())) {\n\t\t\t\tthrow new UMBException(\"\\\"\" + entry.getKey() + \"\\\" is not a valid annotation ID in group \\\"\" + group + \"\\\"\");\n\t\t\t}\n\t\t\tAnnotation a = entry.getValue();\n\t\t\ta.validate();\n\t\t}\n\t}\n\n\t/**\n\t * Perform validation of a valuation description\n\t */\n\tpublic void validateValuationDescription(ValuationClassDescription valuationDescr, String fieldName) throws UMBException\n\t{\n\t\tcheckFieldExists(valuationDescr.variables, fieldName + \".variables\");\n\t\tfor (ValuationVariable var : valuationDescr.variables) {\n\t\t\tvalidateValuationVariable(var);\n\t\t}\n\t\t// TODO: If strict and (valuations.numBits() % 8 != 0)\n\t}\n\n\t/**\n\t * Perform validation of an individual valuation variable\n\t */\n\tpublic void validateValuationVariable(ValuationVariable var) throws UMBException\n\t{\n\t\t// Should either be padding or a named variable\n\t\tif (var.padding != null) {\n\t\t\tif (var.name != null || var.type != null) {\n\t\t\t\tthrow new UMBException(\"Malformed variable/padding in state valuation metadata\");\n\t\t\t}\n\t\t} else {\n\t\t\tif (var.name == null) {\n\t\t\t\tthrow new UMBException(\"Unnamed variable in state valuation metadata\");\n\t\t\t}\n\t\t\tif (var.type == null) {\n\t\t\t\tthrow new UMBException(\"Untyped variable in state valuation metadata\");\n\t\t\t}\n\t\t\tif (var.type.size == null) {\n\t\t\t\tthrow new UMBException(\"Only fixed size variables are currently supported for state valuations\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Create an empty UMBIndex.\n\t */\n\tpublic UMBIndex()\n\t{\n\t\t// Default no-argument constructor needed for JSON deserialisation\n\t}\n\n\t// Setters\n\n\t/**\n\t * Set the notion of time used for the model.\n\t * @param time Notion of time\n\t */\n\tpublic void setTime(Time time)\n\t{\n\t\ttransitionSystem.time = time;\n\t}\n\n\t/**\n\t * Set the number of players in the model.\n\t * @param numPlayers The number of players\n\t */\n\tpublic void setNumPlayers(int numPlayers)\n\t{\n\t\ttransitionSystem.numPlayers = numPlayers;\n\t}\n\n\t/**\n\t * Set the number of states in the model.\n\t * @param numStates The number of states\n\t */\n\tpublic void setNumStates(long numStates)\n\t{\n\t\ttransitionSystem.numStates = numStates;\n\t}\n\n\t/**\n\t * Set the number of initial states in the model.\n\t * @param numInitialStates The number of initial states\n\t */\n\tpublic void setNumInitialStates(long numInitialStates)\n\t{\n\t\ttransitionSystem.numInitialStates = numInitialStates;\n\t}\n\n\t/**\n\t * Set the number of choices in the model.\n\t * @param numChoices The number of choices\n\t */\n\tpublic void setNumChoices(long numChoices)\n\t{\n\t\ttransitionSystem.numChoices = numChoices;\n\t}\n\n\t/**\n\t * Set the number of branches in the model.\n\t * @param numBranches The number of branches\n\t */\n\tpublic void setNumBranches(long numBranches)\n\t{\n\t\ttransitionSystem.numBranches = numBranches;\n\t}\n\n\t/**\n\t * Set the number of choice actions in the model.\n\t * @param numChoiceActions The number of choice actions\n\t */\n\tpublic void setNumChoiceActions(int numChoiceActions)\n\t{\n\t\ttransitionSystem.numChoiceActions = numChoiceActions;\n\t}\n\n\t/**\n\t * Set the number of branch actions in the model.\n\t * @param numBranchActions The number of choice actions\n\t */\n\tpublic void setNumBranchActions(int numBranchActions)\n\t{\n\t\ttransitionSystem.numBranchActions = numBranchActions;\n\t}\n\n\t/**\n\t * Set the number of observations in the model.\n\t * @param numObservations The number of observations\n\t */\n\tpublic void setNumObservations(int numObservations)\n\t{\n\t\ttransitionSystem.numObservations = numObservations;\n\t}\n\n\t/**\n\t * Set the entity (e.g. states/branches) observations are attached to.\n\t * @param observationsApplyTo The entity\n\t */\n\tpublic void setObservationsApplyTo(UMBEntity observationsApplyTo)\n\t{\n\t\ttransitionSystem.observationsApplyTo = observationsApplyTo;\n\t}\n\n\t/**\n\t * Set the type of branch probabilities used in the model.\n\t * @param branchProbabilityType The type of branch probabilities\n\t */\n\tpublic void setBranchProbabilityType(UMBType branchProbabilityType)\n\t{\n\t\ttransitionSystem.branchProbabilityType = branchProbabilityType;\n\t}\n\n\t/**\n\t * Set the type of exit rates used in the model.\n\t * @param exitRateType The type of exit rates\n\t */\n\tpublic void setExitRateType(UMBType exitRateType)\n\t{\n\t\ttransitionSystem.exitRateType = exitRateType;\n\t}\n\n\t/**\n\t * Set the type of probabilities for stochastic observations in the model.\n\t * @param observationProbabilityType The type of observation probabilities\n\t */\n\tpublic void setObservationProbabilityType(UMBType observationProbabilityType)\n\t{\n\t\ttransitionSystem.observationProbabilityType = observationProbabilityType;\n\t}\n\n\t/**\n\t * Set the names of players in the model (for games\n\t * @param playerNames The list of player names\n\t */\n\tpublic void setPlayerNames(List<String> playerNames)\n\t{\n\t\ttransitionSystem.playerNames = new ArrayList<>(playerNames);\n\t}\n\n\t/**\n\t * Convenience method to set model metadata for a range of common models,\n\t * i.e., those that are included in the {@link ModelType} enum.\n\t * For some models (games, POMDPs), further configuration will be needed\n\t * since fields are just set to defaults (players = 2, observations = 1).\n\t * @param modelType The model type\n\t * @param rational Are probabilities rationals (as opposed to doubles)?\n\t */\n\tpublic void setModelType(ModelType modelType, boolean rational) throws UMBException\n\t{\n\t\tswitch (modelType) {\n\t\t\tcase DTMC:\n\t\t\tcase IDTMC:\n\t\t\t\tsetTime(Time.DISCRETE);\n\t\t\t\tsetNumPlayers(0);\n\t\t\t\tsetBranchProbabilityType(rational ? UMBType.create(Type.RATIONAL) : UMBType.create(Type.DOUBLE));\n\t\t\t\tsetExitRateType(null);\n\t\t\t\tbreak;\n\t\t\tcase CTMC:\n\t\t\t\tsetTime(Time.STOCHASTIC);\n\t\t\t\tsetNumPlayers(0);\n\t\t\t\tsetBranchProbabilityType(rational ? UMBType.create(Type.RATIONAL) : UMBType.create(Type.DOUBLE));\n\t\t\t\tsetExitRateType(rational ? UMBType.create(Type.RATIONAL) : UMBType.create(Type.DOUBLE));\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\tcase POMDP:\n\t\t\t\tsetTime(Time.DISCRETE);\n\t\t\t\tsetNumPlayers(1);\n\t\t\t\tsetBranchProbabilityType(rational ? UMBType.create(Type.RATIONAL) : UMBType.create(Type.DOUBLE));\n\t\t\t\tsetExitRateType(null);\n\t\t\t\tbreak;\n\t\t\tcase IMDP:\n\t\t\tcase IPOMDP:\n\t\t\t\tsetTime(Time.DISCRETE);\n\t\t\t\tsetNumPlayers(1);\n\t\t\t\tsetBranchProbabilityType(rational ? UMBType.create(Type.RATIONAL_INTERVAL) : UMBType.create(Type.DOUBLE_INTERVAL));\n\t\t\t\tsetExitRateType(null);\n\t\t\t\tbreak;\n\t\t\tcase CTMDP:\n\t\t\t\tsetTime(Time.STOCHASTIC);\n\t\t\t\tsetNumPlayers(1);\n\t\t\t\tsetBranchProbabilityType(rational ? UMBType.create(Type.RATIONAL) : UMBType.create(Type.DOUBLE));\n\t\t\t\tsetExitRateType(rational ? UMBType.create(Type.RATIONAL) : UMBType.create(Type.DOUBLE));\n\t\t\t\tbreak;\n\t\t\tcase MA:\n\t\t\t\tsetTime(Time.URGENT_STOCHASTIC);\n\t\t\t\tsetNumPlayers(1);\n\t\t\t\tsetBranchProbabilityType(rational ? UMBType.create(Type.RATIONAL) : UMBType.create(Type.DOUBLE));\n\t\t\t\tsetExitRateType(rational ? UMBType.create(Type.RATIONAL) : UMBType.create(Type.DOUBLE));\n\t\t\t\tbreak;\n\t\t\tcase TSG:\n\t\t\tcase ITSG:\n\t\t\t\tsetTime(Time.DISCRETE);\n\t\t\t\tsetNumPlayers(2);\n\t\t\t\tsetBranchProbabilityType(null);\n\t\t\t\tsetExitRateType(null);\n\t\t\t\tbreak;\n\t\t\tcase LTS:\n\t\t\t\tsetTime(Time.DISCRETE);\n\t\t\t\tsetNumPlayers(1);\n\t\t\t\tsetBranchProbabilityType(null);\n\t\t\t\tsetExitRateType(null);\n\t\t\t\tbreak;\n\t\t\tcase TG:\n\t\t\t\tsetTime(Time.DISCRETE);\n\t\t\t\tsetNumPlayers(2);\n\t\t\t\tsetBranchProbabilityType(null);\n\t\t\t\tsetExitRateType(null);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new UMBException(\"Unsupported model type \\\"\" + modelType + \"\\\"\");\n\t\t}\n\t\tif (EnumSet.of(ModelType.POMDP, ModelType.IPOMDP).contains(modelType)) {\n\t\t\tsetNumObservations(1);\n\t\t\tsetObservationsApplyTo(UMBEntity.STATES);\n\t\t} else {\n\t\t\tsetNumObservations(0);\n\t\t}\n\t}\n\n\t/**\n\t * Add a new annotation, for now without any data attached.\n\t * If an alias is provided, there should not already exist\n\t * an annotation in the same group with the same alias.\n\t * @param group The ID of the group\n\t * @param alias Optional alias (name) for the annotation (\"\" or null if not needed)\n\t * @param type The type of the values to be stored in the annotation\n\t */\n\tpublic Annotation addAnnotation(String group, String alias, UMBType type) throws UMBException\n\t{\n\t\t// Check type\n\t\tif (!type.type.isRational() && !type.isDefaultSize()) {\n\t\t\tthrow new UMBException(\"Annotation type must have default size unless it is rational\");\n\t\t}\n\t\t// Check if group exists; create if not\n\t\tif (!annotationGroups.contains(group)) {\n\t\t\tif (!UMBFormat.isValidID(group)) {\n\t\t\t\tthrow new UMBException(\"Invalid group ID \\\"\" + group + \"\\\"\");\n\t\t\t}\n\t\t\tannotationGroups.add(group);\n\t\t\tannotationAliasMaps.put(group, new LinkedHashMap<>());\n\t\t\tannotations.put(group, new LinkedHashMap<>());\n\t\t}\n\t\t// If alias is present, check it does not already exist\n\t\tif (alias != null && !alias.isEmpty()) {\n\t\t\tMap<String, String> nameMap = annotationAliasMaps.get(group);\n\t\t\tif (nameMap.containsKey(alias)) {\n\t\t\t\tthrow new UMBException(\"Duplicate alias \\\"\" + alias + \"\\\" in group \\\"\" + group + \"\\\"\");\n\t\t\t}\n\t\t}\n\t\t// Create/store annotation\n\t\t// (ID is based on alias if present; if not, just use integer, 1-indexed indices)\n\t\tLinkedHashMap<String, Annotation> grpAnnotations = annotations.get(group);\n\t\tAnnotation annotation = new Annotation();\n\t\tannotation.group = group;\n\t\tString id = Integer.toString(grpAnnotations.size() + 1);\n\t\tif (alias != null && !alias.isEmpty()) {\n\t\t\tid = UMBFormat.toValidUniqueID(alias, grpAnnotations::containsKey);\n\t\t\tannotation.alias = alias;\n\t\t\tannotationAliasMaps.get(group).put(alias, id);\n\t\t}\n\t\tannotation.id = id;\n\t\tannotation.type = type;\n\t\tgrpAnnotations.put(id, annotation);\n\t\treturn annotation;\n\t}\n\n\t/**\n\t * Create a standalone annotation object without adding it to the index.\n\t */\n\tpublic static Annotation createStandaloneAnnotation(String folderName, UMBType type)\n\t{\n\t\tStandaloneAnnotation annotation = new StandaloneAnnotation();\n\t\tannotation.type = type;\n\t\tannotation.folderName = folderName;\n\t\treturn annotation;\n\t}\n\n\t/**\n\t * Add a new description for (a single class of) valuations to be attached to some model entity,\n\t * extracted from a {@link UMBBitPacking} object.\n\t * @param entity The entity to which the valuations apply\n\t * @param unique Whether valuations are unique within the entity\n\t * @param bitPacking Definition of valuation contents\n\t */\n\tpublic void addSingleValuationDescription(UMBEntity entity, boolean unique, UMBBitPacking bitPacking) throws UMBException\n\t{\n\t\taddValuationDescriptions(entity, unique);\n\t\taddValuationDescriptionClass(entity, bitPacking);\n\t}\n\n\t/**\n\t * Specify that valuations are to be attached to some model entity,\n\t * and whether they are unique, without adding any descriptions.\n\t * This is done subsequently via calls to {@link #addValuationDescriptionClass(UMBEntity, UMBBitPacking)}.\n\t * extracted from a list of {@link UMBBitPacking} objects.\n\t * @param entity The entity to which the valuations apply\n\t * @param unique Whether valuations are unique within the entity\n\t */\n\tpublic void addValuationDescriptions(UMBEntity entity, boolean unique) throws UMBException\n\t{\n\t\tif (valuations.containsKey(entity)) {\n\t\t\tthrow new UMBException(\"Valuations have already been added for \" + entity + \"\");\n\t\t} else {\n\t\t\tvaluations.put(entity, new ValuationDescription(unique));\n\t\t}\n\t}\n\n\t/**\n\t * Add a new description for a class of valuations to be attached to some model entity,\n\t * extracted from a {@link UMBBitPacking} object.\n\t * Returns the index of the class within those that exist for the entity.\n\t * @param entity The entity to which the valuations apply\n\t * @param bitPacking Definition of valuation contents\n\t */\n\tpublic int addValuationDescriptionClass(UMBEntity entity, UMBBitPacking bitPacking) throws UMBException\n\t{\n\t\tValuationDescription valuationDescr = valuations.get(entity);\n\t\tvaluationDescr.classes.add(bitPacking.toValuationClassDescription());\n\t\treturn valuationDescr.classes.size() - 1;\n\t}\n\n\t// Getters\n\n\t/**\n\t * Get the notion of time used for the model.\n\t */\n\tpublic Time getTime()\n\t{\n\t\treturn transitionSystem.time;\n\t}\n\n\t/**\n\t * Get the number of players in the model.\n\t */\n\tpublic int getNumPlayers()\n\t{\n\t\treturn transitionSystem.numPlayers;\n\t}\n\n\t/**\n\t * Get the number of states in the model.\n\t */\n\tpublic long getNumStates()\n\t{\n\t\treturn transitionSystem.numStates;\n\t}\n\n\t/**\n\t * Get the number of initial states in the model.\n\t */\n\tpublic long getNumInitialStates()\n\t{\n\t\treturn transitionSystem.numInitialStates;\n\t}\n\n\t/**\n\t * Get the number of choices in the model.\n\t */\n\tpublic long getNumChoices()\n\t{\n\t\treturn transitionSystem.numChoices;\n\t}\n\n\t/**\n\t * Get the number of branches in the model.\n\t */\n\tpublic long getNumBranches()\n\t{\n\t\treturn transitionSystem.numBranches;\n\t}\n\n\t/**\n\t * Get the number of choice actions in the model.\n\t */\n\tpublic int getNumChoiceActions()\n\t{\n\t\treturn transitionSystem.numChoiceActions;\n\t}\n\n\t/**\n\t * Get the number of branch actions in the model.\n\t */\n\tpublic int getNumBranchActions()\n\t{\n\t\treturn transitionSystem.numBranchActions;\n\t}\n\n\t/**\n\t * Get the number of observations in the model.\n\t */\n\tpublic int getNumObservations()\n\t{\n\t\treturn transitionSystem.numObservations;\n\t}\n\n\t/**\n\t * Get the entity (e.g. states/branches) observations are attached to.\n\t */\n\tpublic UMBEntity getObservationsApplyTo()\n\t{\n\t\treturn transitionSystem.observationsApplyTo;\n\t}\n\n\t/**\n\t * Get the type of branch probabilities used in the model.\n\t */\n\tpublic UMBType getBranchProbabilityType()\n\t{\n\t\treturn transitionSystem.branchProbabilityType;\n\t}\n\n\t/**\n\t * Get the type of exit rates used in the model.\n\t */\n\tpublic UMBType getExitRateType()\n\t{\n\t\treturn transitionSystem.exitRateType;\n\t}\n\n\t/**\n\t * Get the type of probabilities for stochastic observations in the model.\n\t */\n\tpublic UMBType getObservationProbabilityType()\n\t{\n\t\treturn transitionSystem.observationProbabilityType;\n\t}\n\n\t/**\n\t * Get the names of the players in the model (for games).\n\t * Only present if {@link #getNumPlayers()} is greater than one.\n\t */\n\tpublic List<String> getPlayerNames()\n\t{\n\t\treturn transitionSystem.playerNames;\n\t}\n\n\t/**\n\t * Get the number of the specified entity (states, choices, etc.).\n\t */\n\tpublic long getEntityCount(UMBEntity entity) throws UMBException\n\t{\n\t\tswitch (entity) {\n\t\t\tcase STATES:\n\t\t\t\treturn getNumStates();\n\t\t\tcase CHOICES:\n\t\t\t\treturn getNumChoices();\n\t\t\tcase BRANCHES:\n\t\t\t\treturn getNumBranches();\n\t\t\tcase OBSERVATIONS:\n\t\t\t\treturn getNumObservations();\n\t\t\tcase PLAYERS:\n\t\t\t\treturn getNumPlayers();\n\t\t\tdefault:\n\t\t\t\tthrow new UMBException(\"Unsupported entity \\\"\" + entity + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Convenience method to get the model type, for a range of common models,\n\t * i.e., those that are included in the {@link ModelType} enum.\n\t * Returns null if the model type is not one of the common types.\n\t */\n\tpublic ModelType getModelType()\n\t{\n\t\tboolean prob = transitionSystem.branchProbabilityType != null;\n\t\tint numPlayers = getNumPlayers();\n\t\tboolean pObs = getNumObservations() > 0;\n\t\tTime time = getTime();\n\t\tboolean intv = transitionSystem.branchProbabilityType != null && transitionSystem.branchProbabilityType.type.isInterval();\n\n\t\tModelType modelType = null;\n\t\t// Probabilistic models\n\t\tif (prob) {\n\t\t\tif (numPlayers == 0) {\n\t\t\t\tif (pObs) {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t\tswitch (time) {\n\t\t\t\t\tcase DISCRETE:\n\t\t\t\t\t\tmodelType = ModelType.DTMC;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase STOCHASTIC:\n\t\t\t\t\t\tmodelType = ModelType.CTMC;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase URGENT_STOCHASTIC:\n\t\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t} else if (numPlayers == 1) {\n\t\t\t\tswitch (time) {\n\t\t\t\t\tcase DISCRETE:\n\t\t\t\t\t\tmodelType = pObs ? ModelType.POMDP : ModelType.MDP;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase STOCHASTIC:\n\t\t\t\t\t\tmodelType = pObs ? null: ModelType.CTMDP;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase URGENT_STOCHASTIC:\n\t\t\t\t\t\tmodelType = pObs ? null: ModelType.MA;\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (pObs) {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t\tswitch (time) {\n\t\t\t\t\tcase DISCRETE:\n\t\t\t\t\t\tmodelType = ModelType.TSG;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase STOCHASTIC:\n\t\t\t\t\tcase URGENT_STOCHASTIC:\n\t\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Non-probabilistic models\n\t\telse {\n\t\t\tif (pObs) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\t// Ignore time/intervals\n\t\t\tif (numPlayers == 0) {\n\t\t\t\treturn null;\n\t\t\t} else if (numPlayers == 1) {\n\t\t\t\treturn ModelType.LTS;\n\t\t\t} else {\n\t\t\t\treturn ModelType.TG;\n\t\t\t}\n\t\t}\n\t\t// If still unknown, give up\n\t\tif (modelType == null) {\n\t\t\treturn null;\n\t\t}\n\t\t// Deal with interval variants\n\t\tif (!intv) {\n\t\t\treturn modelType;\n\t\t} else {\n\t\t\tswitch (modelType) {\n\t\t\t\tcase DTMC:\n\t\t\t\t\treturn ModelType.IDTMC;\n\t\t\t\tcase MDP:\n\t\t\t\t\treturn ModelType.IMDP;\n\t\t\t\tcase POMDP:\n\t\t\t\t\treturn ModelType.IPOMDP;\n\t\t\t\tcase TSG:\n\t\t\t\t\treturn ModelType.ITSG;\n\t\t\t\tdefault:\n\t\t\t\t\treturn null;\n\t\t\t}\n\t\t}\n\t}\n\n\t// Methods to get info about annotations\n\n\t/**\n\t * Get a stored model annotation\n\t * @param group The ID of the group containing the annotation\n\t * @param id The ID of the annotation within the group\n\t */\n\tpublic Annotation getAnnotation(String group, String id) throws UMBException\n\t{\n\t\tLinkedHashMap<String, Annotation> grpAnnotations = annotations.get(group);\n\t\tif (grpAnnotations == null) {\n\t\t\tthrow new UMBException(\"Unknown annotation group ID \\\"\" + group + \"\\\"\");\n\t\t}\n\t\tAnnotation annotation = grpAnnotations.get(id);\n\t\tif (annotation == null) {\n\t\t\tthrow new UMBException(\"Unknown annotation ID \\\"\" + id + \"\\\" in group \\\"\" + group + \"\\\"\");\n\t\t}\n\t\treturn annotation;\n\t}\n\n\t/**\n\t * See if a stored model annotation with a given alias exists.\n\t * @param group The ID of the group containing the annotation\n\t * @param alias The alias of the annotation\n\t */\n\tpublic boolean annotationWithAliasExists(String group, String alias)\n\t{\n\t\tMap<String, String> aliasMap = annotationAliasMaps.get(group);\n\t\tif (aliasMap == null) {\n\t\t\treturn false;\n\t\t}\n\t\treturn aliasMap.containsKey(alias);\n\t}\n\n\t/**\n\t * Get a stored model annotation by its alias.\n\t * Throws an exception if no such annotation exists.\n\t * @param group The ID of the group containing the annotation\n\t * @param alias The alias of the annotation\n\t */\n\tpublic String getAnnotationIdForAlias(String group, String alias) throws UMBException\n\t{\n\t\tMap<String, String> aliasMap = annotationAliasMaps.get(group);\n\t\tif (aliasMap == null) {\n\t\t\tthrow new UMBException(\"Annotation group \\\"\" + group + \"\\\" does not exist\");\n\t\t}\n\t\tString id = aliasMap.get(alias);\n\t\tif (id == null) {\n\t\t\tthrow new UMBException(\"No annotation with alias \\\"\" + alias + \"\\\" in group \\\"\" + group + \"\\\" exists\");\n\t\t}\n\t\treturn id;\n\t}\n\n\t// Methods to get info about AP annotations\n\n\t/**\n\t * Get all AP annotations, as an ordered map from ID to {@link Annotation}.\n\t * This is guaranteed to return a non-null map, but it may be empty.\n\t */\n\tpublic LinkedHashMap<String, Annotation> getAPAnnotations()\n\t{\n\t\treturn annotations.getOrDefault(UMBFormat.AP_ANNOTATIONS_GROUP, new LinkedHashMap<>());\n\t}\n\n\t/**\n\t * Get all AP annotations as a list.\n\t */\n\tpublic List<Annotation> getAPAnnotationsList()\n\t{\n\t\treturn new ArrayList<>(getAPAnnotations().values());\n\t}\n\n\t/**\n\t * Does this UMB file have any AP annotations?\n\t */\n\tpublic boolean hasAPAnnotations()\n\t{\n\t\treturn !getAPAnnotations().isEmpty();\n\t}\n\n\t/**\n\t * Get the number of AP annotations.\n\t */\n\tpublic int getNumAPAnnotations()\n\t{\n\t\treturn getAPAnnotations().size();\n\t}\n\n\t/**\n\t * Get the {@code i}th AP annotation.\n\t */\n\tpublic Annotation getAPAnnotation(int i)\n\t{\n\t\treturn getAPAnnotationsList().get(i);\n\t}\n\n\t/**\n\t * Get an AP annotation by its ID\n\t * Throws an exception if no such annotation exists.\n\t */\n\tpublic Annotation getAPAnnotationByID(String apID) throws UMBException\n\t{\n\t\tAnnotation annotation = getAPAnnotations().get(apID);\n\t\tif (annotation == null) {\n\t\t\tthrow new UMBException(\"Unknown AP annotation ID \\\"\" + apID + \"\\\"\");\n\t\t}\n\t\treturn annotation;\n\t}\n\n\t/**\n\t * Does this UMB file have an AP annotation with the specified alias?\n\t */\n\tpublic boolean hasAPAnnotationWithAlias(String apAlias)\n\t{\n\t\treturn annotationWithAliasExists(UMBFormat.AP_ANNOTATIONS_GROUP, apAlias);\n\t}\n\n\t/**\n\t * Get an AP annotation by its alias.\n\t * Throws an exception if no such annotation exists.\n\t */\n\tpublic Annotation getAPAnnotationByAlias(String apAlias) throws UMBException\n\t{\n\t\tString apID = getAnnotationIdForAlias(UMBFormat.AP_ANNOTATIONS_GROUP, apAlias);\n\t\treturn getAPAnnotationByID(apID);\n\t}\n\n\t/**\n\t * Get the names of all AP annotations (name is alias if present or ID if not)\n\t */\n\tpublic List<String> getAPNames()\n\t{\n\t\treturn getAPAnnotationsList().stream()\n\t\t\t\t.map(Annotation::getName)\n\t\t\t\t.collect(Collectors.toCollection(ArrayList::new));\n\t}\n\n\t// Methods to get info about reward annotations\n\n\t/**\n\t * Get all reward annotations, as an ordered map from ID to {@link Annotation}.\n\t * This is guaranteed to return a non-null map, but it may be empty.\n\t */\n\tpublic LinkedHashMap<String, Annotation> getRewardAnnotations()\n\t{\n\t\treturn annotations.getOrDefault(UMBFormat.REWARD_ANNOTATIONS_GROUP, new LinkedHashMap<>());\n\t}\n\n\t/**\n\t * Get all reward annotations as a list.\n\t */\n\tpublic List<Annotation> getRewardAnnotationsList()\n\t{\n\t\treturn new ArrayList<>(getRewardAnnotations().values());\n\t}\n\n\t/**\n\t * Does this UMB file have any reward annotations?\n\t */\n\tpublic boolean hasRewardAnnotations()\n\t{\n\t\treturn !getRewardAnnotations().isEmpty();\n\t}\n\n\t/**\n\t * Get the number of reward annotations.\n\t */\n\tpublic int getNumRewardAnnotations()\n\t{\n\t\treturn getRewardAnnotations().size();\n\t}\n\n\t/**\n\t * Get the {@code i}th reward annotation.\n\t */\n\tpublic Annotation getRewardAnnotation(int i)\n\t{\n\t\treturn getRewardAnnotationsList().get(i);\n\t}\n\n\t/**\n\t * Get a reward annotation by its ID\n\t * Throws an exception if no such annotation exists.\n\t */\n\tpublic Annotation getRewardAnnotationByID(String rewardID) throws UMBException\n\t{\n\t\tAnnotation annotation = getRewardAnnotations().get(rewardID);\n\t\tif (annotation == null) {\n\t\t\tthrow new UMBException(\"Unknown reward annotation ID \\\"\" + rewardID + \"\\\"\");\n\t\t}\n\t\treturn annotation;\n\t}\n\n\t/**\n\t * Does this UMB file have a reward annotation with the specified alias?\n\t */\n\tpublic boolean hasRewardAnnotationWithAlias(String rewardAlias)\n\t{\n\t\treturn annotationWithAliasExists(UMBFormat.REWARD_ANNOTATIONS_GROUP, rewardAlias);\n\t}\n\n\t/**\n\t * Get a reward annotation by its alias.\n\t * Throws an exception if no such annotation exists.\n\t */\n\tpublic Annotation getRewardAnnotationByAlias(String rewardAlias) throws UMBException\n\t{\n\t\tString rewardID = getAnnotationIdForAlias(UMBFormat.REWARD_ANNOTATIONS_GROUP, rewardAlias);\n\t\treturn getRewardAnnotationByID(rewardID);\n\t}\n\n\t/**\n\t * Get the names of all reward annotations (name is alias if present or ID if not)\n\t */\n\tpublic List<String> getRewardNames()\n\t{\n\t\treturn getRewardAnnotationsList().stream()\n\t\t\t\t.map(Annotation::getName)\n\t\t\t\t.collect(Collectors.toCollection(ArrayList::new));\n\t}\n\n\tpublic boolean hasStateRewards(int i)\n\t{\n\t\treturn getRewardAnnotation(i).appliesTo(UMBEntity.STATES);\n\t}\n\n\tpublic boolean hasChoiceRewards(int i)\n\t{\n\t\treturn getRewardAnnotation(i).appliesTo(UMBEntity.CHOICES);\n\t}\n\n\tpublic boolean hasBranchRewards(int i)\n\t{\n\t\treturn getRewardAnnotation(i).appliesTo(UMBEntity.BRANCHES);\n\t}\n\n\t// Methods to get info about valuations\n\n\t/**\n\t * Does this UMB file have any valuations for the specified entity?\n\t */\n\tpublic boolean hasValuations(UMBEntity entity)\n\t{\n\t\treturn valuations != null && valuations.containsKey(entity) && !valuations.get(entity).classes.isEmpty();\n\t}\n\n\t/**\n\t * Does this UMB file have unique valuations for the specified entity?\n\t */\n\tpublic boolean areValuationsUnique(UMBEntity entity)\n\t{\n\t\treturn valuations != null && valuations.containsKey(entity) && valuations.get(entity).unique;\n\t}\n\n\t/**\n\t * Get a {@link UMBBitPacking} object describing the valuations for the specified entity.\n\t * If there is more than one class of valuation for the entity, it returns the first one.\n\t * Use {@link #getValuationBitPacking(UMBEntity, int)} to get others.\n\t * Throws an exception if no such metadata is present.\n\t */\n\tpublic UMBBitPacking getValuationBitPacking(UMBEntity entity) throws UMBException\n\t{\n\t\treturn getValuationBitPacking(entity, 0);\n\t}\n\n\t/**\n\t * Get a {@link UMBBitPacking} object for the {@code i}th class of valuation for the specified entity.\n\t * Throws an exception if no such metadata is present.\n\t */\n\tpublic UMBBitPacking getValuationBitPacking(UMBEntity entity, int i) throws UMBException\n\t{\n\t\tif (valuations == null || !valuations.containsKey(entity) || valuations.get(entity).classes.size() <= i) {\n\t\t\tthrow new UMBException(\"No valuation metadata present\");\n\t\t}\n\t\treturn new UMBBitPacking(valuations.get(entity).classes.get(i));\n\t}\n\n\t/**\n\t * Get the number of classes of valuations for the specified entity.\n\t * Throws an exception if no such metadata is present.\n\t */\n\tpublic int getNumValuationClasses(UMBEntity entity) throws UMBException\n\t{\n\t\tif (valuations == null || !valuations.containsKey(entity)) {\n\t\t\tthrow new UMBException(\"No valuation metadata present\");\n\t\t}\n\t\treturn valuations.get(entity).classes.size();\n\t}\n\n\t// Validation methods\n\n\t/**\n\t * Check whether a field exists (is non-null) and throw an exception if not.\n\t * @param field The field, as stored in {@link UMBIndex}\n\t * @param fieldName The name of the field, as stored in {@link UMBIndex} (not JSON/UMB)\n\t */\n\tprivate static void checkFieldExists(Object field, String fieldName) throws UMBException\n\t{\n\t\tcheckFieldExistsIff(field, fieldName, true);\n\t}\n\n\t/**\n\t * Check whether a field exists (is non-null) iff {@code condition} is true and throw an exception if not.\n\t * @param field The field, as stored in {@link UMBIndex}\n\t * @param fieldName The name of the field, as stored in {@link UMBIndex} (not JSON/UMB)\n\t * @param condition The condition\n\t */\n\tprivate static void checkFieldExistsIff(Object field, String fieldName, boolean condition) throws UMBException\n\t{\n\t\tif (condition && field == null) {\n\t\t\tthrow new UMBException(\"Required field \\\"\" + fieldNameToUMB(fieldName) + \"\\\" is missing\");\n\t\t}\n\t\tif (!condition && field != null) {\n\t\t\tthrow new UMBException(\"Field \\\"\" + fieldNameToUMB(fieldName) + \"\\\" should not be present\");\n\t\t}\n\t}\n\n\t// Import/export from/to JSON\n\n\t/**\n\t * Convert this index to JSON format.\n\t */\n\tpublic String toJSON()\n\t{\n\t\treturn gsonBuilder().toJson(this);\n\t}\n\n\t/**\n\t * Parse an index from JSON format.\n\t */\n\tpublic static UMBIndex fromJSON(String json) throws UMBException\n\t{\n\t\ttry {\n\t\t\tUMBIndex umbIndex = gsonBuilder().fromJson(json, UMBIndex.class);\n\t\t\tumbIndex.buildAnnotationInfo();\n\t\t\treturn umbIndex;\n\t\t} catch (JsonParseException e) {\n\t\t\tthrow new UMBException(e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Build derived info {@code annotationGroups} and {@code annotationAliasMaps}\n\t * from the list of annotations in {@code annotations}.\n\t */\n\tprivate void buildAnnotationInfo()\n\t{\n\t\tannotationGroups = new ArrayList<>();\n\t\tannotationAliasMaps = new LinkedHashMap<>();\n\t\tannotationGroups.addAll(annotations.keySet());\n\t\tfor (Map.Entry<String, LinkedHashMap<String, Annotation>> entry2 : annotations.entrySet()) {\n\t\t\tString group = entry2.getKey();\n\t\t\tMap<String, String> aliasMap = new LinkedHashMap<>();\n\t\t\tannotationAliasMaps.put(group, aliasMap);\n\t\t\tfor (Map.Entry<String, Annotation> entry : entry2.getValue().entrySet()) {\n\t\t\t\tentry.getValue().group = group;\n\t\t\t\tentry.getValue().id = entry.getKey();\n\t\t\t\tif (entry.getValue().alias != null) {\n\t\t\t\t\taliasMap.put(entry.getValue().alias, entry.getKey());\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Configure a Gson object for UMB import/export.\n\t */\n\tprivate static Gson gsonBuilder()\n\t{\n\t\treturn new GsonBuilder()\n\t\t\t.setFieldNamingPolicy(FieldNamingPolicy.LOWER_CASE_WITH_DASHES)\n\t\t\t.registerTypeHierarchyAdapter(UMBField.class, new EnumSerializer<>())\n\t\t\t.registerTypeHierarchyAdapter(UMBField.class, new EnumDeserializer<>())\n\t\t\t.setPrettyPrinting()\n\t\t\t.create();\n\t}\n\n\t/**\n\t * Customised enum behaviour for UMB field (de)serialisation.\n\t */\n\tinterface UMBField\n\t{\n\t\tdefault String description()\n\t\t{\n\t\t\treturn toUMB(((Enum) this).name());\n\t\t}\n\n\t\t/**\n\t\t * Convert to UMB-style field values (lower case, hyphenated)\n\t\t */\n\t\tstatic String toUMB(String value)\n\t\t{\n\t\t\treturn value.toLowerCase().replace(\"_\", \"-\");\n\t\t}\n\t}\n\n\t/**\n\t * Convert the name of a field, as stored in {@link UMBIndex} to its name in UMB JSON,\n\t * i.e., converting (possibly capitalised) camel case to lower case hyphenated.\n\t * Actual serialisation is done with {@link FieldNamingPolicy#LOWER_CASE_WITH_DASHES}\n\t * but this should match closely enough for error reporting etc.\n\t */\n\tpublic static String fieldNameToUMB(String field)\n\t{\n\t\treturn field.replaceAll(\"([a-z])([A-Z])\", \"$1-$2\").replaceAll(\"^([A-Z])\", \"$1\").toLowerCase();\n\t}\n\n\t/**\n\t * Custom JSON serializer for enums, following style of UMB specification\n\t */\n\tstatic class EnumSerializer<T extends Enum<T>> implements JsonSerializer<T>\n\t{\n\t\t@Override\n\t\tpublic JsonElement serialize(T t, java.lang.reflect.Type type, JsonSerializationContext jsonSerializationContext)\n\t\t{\n\t\t\t// Format for UMB (lower case, hyphenated)\n\t\t\treturn new JsonPrimitive(UMBField.toUMB(t.name()));\n\t\t}\n\t}\n\n\t/**\n\t * Custom JSON deserializer for enums, following style of UMB specification\n\t */\n\tstatic class EnumDeserializer<T extends Enum<T>> implements JsonDeserializer<T>\n\t{\n\t\t@Override\n\t\tpublic T deserialize(JsonElement json, java.lang.reflect.Type typeOfT, JsonDeserializationContext context)\n\t\t{\n\t\t\tString fieldValue = json.getAsString();\n\t\t\ttry {\n\t\t\t\t// Look up enum, ignoring UMB field style conversion (lower case, hyphenated))\n\t\t\t\t// And throw an exception if lookup fails (GSON default is to just store null)\n\t\t\t\tif (!json.isJsonPrimitive()) {\n\t\t\t\t\tthrow new IllegalArgumentException();\n\t\t\t\t}\n\t\t\t\tfor (T enumConstant : ((Class<T>) typeOfT).getEnumConstants()) {\n\t\t\t\t\tif (UMBField.toUMB(enumConstant.name()).equals(UMBField.toUMB(fieldValue))) {\n\t\t\t\t\t\treturn enumConstant;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException();\n\t\t\t} catch (IllegalArgumentException e) {\n\t\t\t\tString fieldName = fieldNameToUMB(((Class<T>) typeOfT).getSimpleName());\n\t\t\t\tthrow new JsonParseException(\"Invalid value \\\"\" + fieldValue + \"\\\" for \" + fieldName, e);\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBReader.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\nimport it.unimi.dsi.fastutil.booleans.BooleanConsumer;\nimport org.apache.commons.compress.archivers.tar.TarArchiveEntry;\nimport org.apache.commons.compress.archivers.tar.TarArchiveInputStream;\nimport org.apache.commons.compress.compressors.CompressorException;\nimport org.apache.commons.compress.compressors.CompressorInputStream;\nimport org.apache.commons.compress.compressors.CompressorStreamFactory;\n\nimport java.io.BufferedInputStream;\nimport java.io.File;\nimport java.io.IOException;\nimport java.io.InputStream;\nimport java.nio.ByteBuffer;\nimport java.nio.ByteOrder;\nimport java.nio.charset.StandardCharsets;\nimport java.nio.file.Files;\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.function.Consumer;\nimport java.util.function.DoubleConsumer;\nimport java.util.function.IntConsumer;\nimport java.util.function.LongConsumer;\n\n/**\n * Class to handle reading from UMB files.\n */\npublic class UMBReader\n{\n\t/**\n\t * File to be read from.\n\t */\n\tprivate final File fileIn;\n\n\t/**\n\t * The (JSON) index extracted from the UMB file.\n\t */\n\tprivate UMBIndex umbIndex;\n\n\t/**\n\t * Default buffer size (in bytes) for reading from UMB file.\n\t */\n\tprivate static int BUFFER_SIZE = 64 * 1024;\n\n\t/**\n\t * Construct a new {@link UMBReader} reading from the specified file.\n\t * @param fileIn The UMB file to read from.\n\t */\n\tpublic UMBReader(File fileIn) throws UMBException\n\t{\n\t\tthis.fileIn = fileIn;\n\t\textractIndex();\n\t}\n\n\t/**\n\t * Extract, parse, validate and store the JSON index.\n\t */\n\tprivate void extractIndex() throws UMBException\n\t{\n\t\t// Extract index JSON as string\n\t\tUMBIn umbIn = open();\n\t\tumbIn.findArchiveEntry(UMBFormat.INDEX_FILE);\n\t\tString json = umbIn.readAsString();\n\t\tumbIn.close();\n\n\t\t// Parse/validate JSON\n\t\t// Note that we check for required fields, but do not complain about unexpected ones\n\t\t// (GSON does not make the latter process very easy)\n\t\tumbIndex = UMBIndex.fromJSON(json);\n\t\tumbIndex.validate();\n\t}\n\n\t/**\n\t * Get the (JSON) index of the UMB file.\n\t */\n\tpublic UMBIndex getUMBIndex()\n\t{\n\t\treturn umbIndex;\n\t}\n\n\t// Methods to extract core model info\n\n\t/**\n\t * Extract the state choice offsets.\n\t */\n\tpublic void extractStateChoiceOffsets(LongConsumer longConsumer) throws UMBException\n\t{\n\t\tif (!fileExists(UMBFormat.STATE_CHOICE_OFFSETS_FILE)) {\n\t\t\t// Indices default to identities if requested when absent\n\t\t\textractDefaultLongArray(umbIndex.getNumStates() + 1, UMBFormat.BinFileDefaultValue.IDENTITY, longConsumer);\n\t\t} else {\n\t\t\textractLongArray(UMBFormat.STATE_CHOICE_OFFSETS_FILE, umbIndex.getNumStates() + 1, longConsumer);\n\t\t}\n\t}\n\n\t/**\n\t * Extract the players that own states (turn-based game models)\n\t */\n\tpublic void extractStatePlayers(IntConsumer intConsumer) throws UMBException\n\t{\n\t\tif (!fileExists(UMBFormat.STATE_PLAYERS)) {\n\t\t\t// Players default to 0 if requested when absent\n\t\t\textractDefaultIntArray(umbIndex.getNumStates(), UMBFormat.BinFileDefaultValue.ZERO, intConsumer);\n\t\t} else {\n\t\t\textractIntArray(UMBFormat.STATE_PLAYERS, umbIndex.getNumStates(), intConsumer);\n\t\t}\n\t}\n\n\t/**\n\t * Extract the initial states, in sparse form, i.e., a list of state indices\n\t */\n\tpublic void extractInitialStates(LongConsumer longConsumer) throws UMBException\n\t{\n\t\tif (!fileExists(UMBFormat.INITIAL_STATES_FILE)) {\n\t\t\t// Default to no initial states if requested when absent\n\t\t} else {\n\t\t\textractBooleanArraySparse(UMBFormat.INITIAL_STATES_FILE, umbIndex.getNumStates(), longConsumer);\n\t\t}\n\t}\n\n\t/**\n\t * Extract the Markovian states (for Markov automata), in sparse form, i.e., a list of state indices\n\t */\n\tpublic void extractMarkovianStates(LongConsumer longConsumer) throws UMBException\n\t{\n\t\tif (!fileExists(UMBFormat.MARKOVIAN_STATES_FILE)) {\n\t\t\t// Default to no Markovian states if requested when absent\n\t\t} else {\n\t\t\textractBooleanArraySparse(UMBFormat.MARKOVIAN_STATES_FILE, umbIndex.getNumStates(), longConsumer);\n\t\t}\n\t}\n\n\t/**\n\t * Extract the exit rates for all states (for continuous-time models).\n\t * The type of the values depends on {@link UMBIndex#getExitRateType()}.\n\t */\n\tpublic void extractExitRates(Consumer<?> consumer) throws UMBException\n\t{\n\t\textractContinuousNumericArray(UMBFormat.STATE_EXIT_RATES_FILE, umbIndex.getExitRateType(), umbIndex.getNumStates(), consumer);\n\t}\n\n\t/**\n\t * Extract the choice branch offsets.\n\t */\n\tpublic void extractChoiceBranchOffsets(LongConsumer longConsumer) throws UMBException\n\t{\n\t\tif (!fileExists(UMBFormat.CHOICE_BRANCH_OFFSETS_FILE)) {\n\t\t\t// Indices default to identities if requested when absent\n\t\t\textractDefaultLongArray(umbIndex.getNumChoices() + 1, UMBFormat.BinFileDefaultValue.IDENTITY, longConsumer);\n\t\t} else {\n\t\t\textractLongArray(UMBFormat.CHOICE_BRANCH_OFFSETS_FILE, umbIndex.getNumChoices() + 1, longConsumer);\n\t\t}\n\t}\n\n\t/**\n\t * Extract the branch targets.\n\t */\n\tpublic void extractBranchTargets(LongConsumer longConsumer) throws UMBException\n\t{\n\t\textractLongArray(UMBFormat.BRANCH_TARGETS_FILE, umbIndex.getNumBranches(), longConsumer);\n\t}\n\n\t/**\n\t * Extract the branch probabilities.\n\t * The type (and number) of values provided depends on {@link UMBIndex#getBranchProbabilityType()}.\n\t * For interval types, this method will extract two values (lower/upper bound, successively) for each branch.\n\t * If values are rationals, this method will extract two values (numerator/denominator, successively) for each one.\n\t */\n\tpublic void extractBranchProbabilities(Consumer<?> consumer) throws UMBException\n\t{\n\t\tif (!fileExists(UMBFormat.BRANCH_PROBABILITIES_FILE)) {\n\t\t\t// Branch probabilities default to 1 if requested when absent\n\t\t\textractDefaultContinuousNumericArray(umbIndex.getBranchProbabilityType(), umbIndex.getNumBranches(), UMBFormat.BinFileDefaultValue.ONE, consumer);\n\t\t} else {\n\t\t\textractContinuousNumericArray(UMBFormat.BRANCH_PROBABILITIES_FILE, umbIndex.getBranchProbabilityType(), umbIndex.getNumBranches(), consumer);\n\t\t}\n\t}\n\n\t/**\n\t * Does this file store actions for choices?\n\t */\n\tpublic boolean hasChoiceActionIndices() throws UMBException\n\t{\n\t\treturn fileExists(umbIndex.actionsAnnotation.getFilename(UMBIndex.UMBEntity.CHOICES));\n\t}\n\n\t/**\n\t * Extract the indices for actions of all choices\n\t */\n\tpublic void extractChoiceActionIndices(IntConsumer intConsumer) throws UMBException\n\t{\n\t\t// ACTIONS_ANNOTATION is a string annotation but we just extract the indices here\n\t\textractIntAnnotation(umbIndex.actionsAnnotation, UMBIndex.UMBEntity.CHOICES, intConsumer);\n\t}\n\n\t/**\n\t * Does this file store actions for branches?\n\t */\n\tpublic boolean hasBranchActionIndices() throws UMBException\n\t{\n\t\treturn fileExists(umbIndex.actionsAnnotation.getFilename(UMBIndex.UMBEntity.BRANCHES));\n\t}\n\n\t/**\n\t * Extract the indices for actions of all branches\n\t */\n\tpublic void extractBranchActionIndices(IntConsumer intConsumer) throws UMBException\n\t{\n\t\t// ACTIONS_ANNOTATION is a string annotation but we just extract the indices here\n\t\textractIntAnnotation(umbIndex.actionsAnnotation, UMBIndex.UMBEntity.BRANCHES, intConsumer);\n\t}\n\n\t/**\n\t * Does this file store a list of choice action strings?\n\t */\n\tpublic boolean hasChoiceActionStrings() throws UMBException\n\t{\n\t\treturn fileExists(UMBFormat.stringOffsetsFile(umbIndex.actionsAnnotation.getFolderName(UMBIndex.UMBEntity.CHOICES)))\n\t\t\t&& fileExists(UMBFormat.stringsFile(umbIndex.actionsAnnotation.getFolderName(UMBIndex.UMBEntity.CHOICES)));\n\t}\n\n\t/**\n\t * Extract the choice action strings\n\t */\n\tpublic void extractChoiceActionStrings(Consumer<String> stringConsumer) throws UMBException\n\t{\n\t\tString folderName = umbIndex.actionsAnnotation.getFolderName(UMBIndex.UMBEntity.CHOICES);\n\t\textractStrings(folderName, umbIndex.getNumChoiceActions(), stringConsumer);\n\t}\n\n\t/**\n\t * Does this file store a list of branch action strings?\n\t */\n\tpublic boolean hasBranchActionStrings() throws UMBException\n\t{\n\t\treturn fileExists(UMBFormat.stringOffsetsFile(umbIndex.actionsAnnotation.getFolderName(UMBIndex.UMBEntity.BRANCHES)))\n\t\t\t\t&& fileExists(UMBFormat.stringsFile(umbIndex.actionsAnnotation.getFolderName(UMBIndex.UMBEntity.BRANCHES)));\n\t}\n\n\t/**\n\t * Extract the branch action strings\n\t */\n\tpublic void extractBranchActionStrings(Consumer<String> stringConsumer) throws UMBException\n\t{\n\t\tString folderName = umbIndex.actionsAnnotation.getFolderName(UMBIndex.UMBEntity.BRANCHES);\n\t\textractStrings(folderName, umbIndex.getNumBranchActions(), stringConsumer);\n\t}\n\n\t/**\n\t * Extract the (deterministic) observations for all states\n\t * @param longConsumer Consumer to receive the observation indices\n\t */\n\tpublic void extractStateObservations(LongConsumer longConsumer) throws UMBException\n\t{\n\t\textractObservations(UMBIndex.UMBEntity.STATES, longConsumer);\n\t}\n\n\t/**\n\t * Extract the (deterministic) observations for all branches\n\t * @param longConsumer Consumer to receive the observation indices\n\t */\n\tpublic void extractBranchObservations(LongConsumer longConsumer) throws UMBException\n\t{\n\t\textractObservations(UMBIndex.UMBEntity.BRANCHES, longConsumer);\n\t}\n\n\t/**\n\t * Extract the (deterministic) observations for some entity (states, branches)\n\t * @param entity The entity for which observations are being extracted\n\t * @param longConsumer Consumer to receive the observation indices\n\t */\n\tpublic void extractObservations(UMBIndex.UMBEntity entity, LongConsumer longConsumer) throws UMBException\n\t{\n\t\textractLongArray(umbIndex.observationsAnnotation.getFilename(entity), umbIndex.getEntityCount(entity), longConsumer);\n\t}\n\n\t// Utility methods for extracting date\n\n\tpublic <T extends LongConsumer> T extractStateChoiceCounts(T longConsumer) throws UMBException\n\t{\n\t\textractStateChoiceOffsets(new OffsetsToCounts(longConsumer));\n\t\treturn longConsumer;\n\t}\n\n\tpublic long extractMaxStateChoiceCount() throws UMBException\n\t{\n\t\treturn extractStateChoiceCounts(new LongMax()).getMax();\n\t}\n\n\t// Methods to extract standard annotations\n\n\t/**\n\t * Extract a state AP annotation via its index.\n\t * @param i AP annotation index\n\t * @param longConsumer Consumer to receive the indices of states satisfying the AP\n\t */\n\tpublic void extractStateAP(int i, LongConsumer longConsumer) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = getUMBIndex().getAPAnnotation(i);\n\t\textractBooleanAnnotationSparse(annotation, UMBIndex.UMBEntity.STATES, longConsumer);\n\t}\n\n\t/**\n\t * Extract a state AP annotation via its ID.\n\t * @param apID AP annotation ID\n\t * @param longConsumer Consumer to receive the indices of states satisfying the AP\n\t */\n\tpublic void extractStateAP(String apID, LongConsumer longConsumer) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = getUMBIndex().getAPAnnotationByID(apID);\n\t\textractBooleanAnnotationSparse(annotation, UMBIndex.UMBEntity.STATES, longConsumer);\n\t}\n\n\t/**\n\t * Extract a state reward annotation via its index.\n\t * @param i Reward annotation index\n\t * @param consumer Consumer to receive the values of the rewards\n\t */\n\tpublic void extractStateRewards(int i, Consumer<?> consumer) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = getUMBIndex().getRewardAnnotation(i);\n\t\textractContinuousNumericAnnotation(annotation, UMBIndex.UMBEntity.STATES, consumer);\n\t}\n\n\t/**\n\t * Extract a state reward annotation from its alias.\n\t * @param rewardID Reward annotation ID\n\t * @param consumer Consumer to receive the values of the rewards\n\t */\n\tpublic void extractStateRewards(String rewardID, Consumer<?> consumer) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = getUMBIndex().getRewardAnnotationByID(rewardID);\n\t\textractContinuousNumericAnnotation(annotation, UMBIndex.UMBEntity.STATES, consumer);\n\t}\n\n\t/**\n\t * Extract a choice reward annotation via its index.\n\t * @param i Reward annotation index\n\t * @param consumer Consumer to receive the values of the rewards\n\t */\n\tpublic void extractChoiceRewards(int i, Consumer<?> consumer) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = getUMBIndex().getRewardAnnotation(i);\n\t\textractContinuousNumericAnnotation(annotation, UMBIndex.UMBEntity.CHOICES, consumer);\n\t}\n\n\t/**\n\t * Extract a choice reward annotation via its ID.\n\t * @param rewardID Reward annotation ID\n\t * @param consumer Consumer to receive the values of the rewards\n\t */\n\tpublic void extractChoiceRewards(String rewardID, Consumer<?> consumer) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = getUMBIndex().getRewardAnnotationByID(rewardID);\n\t\textractContinuousNumericAnnotation(annotation, UMBIndex.UMBEntity.CHOICES, consumer);\n\t}\n\n\t/**\n\t * Extract a branch reward annotation via its index.\n\t * @param i Reward annotation index\n\t * @param consumer Consumer to receive the values of the rewards\n\t */\n\tpublic void extractBranchRewards(int i, Consumer<?> consumer) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = getUMBIndex().getRewardAnnotation(i);\n\t\textractContinuousNumericAnnotation(annotation, UMBIndex.UMBEntity.BRANCHES, consumer);\n\t}\n\n\t/**\n\t * Extract a branch reward annotation via its ID.\n\t * @param rewardID Reward annotation ID\n\t * @param consumer Consumer to receive the values of the rewards\n\t */\n\tpublic void extractBranchRewards(String rewardID, Consumer<?> consumer) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = getUMBIndex().getRewardAnnotationByID(rewardID);\n\t\textractContinuousNumericAnnotation(annotation, UMBIndex.UMBEntity.BRANCHES, consumer);\n\t}\n\n\t// Methods to extract annotations\n\n\tpublic void extractBooleanAnnotationSparse(String group, String id, UMBIndex.UMBEntity appliesTo, LongConsumer longConsumer) throws UMBException\n\t{\n\t\textractBooleanAnnotationSparse(umbIndex.getAnnotation(group, id), appliesTo, longConsumer);\n\t}\n\n\tpublic void extractBooleanAnnotationSparse(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, LongConsumer longConsumer) throws UMBException\n\t{\n\t\tString filename = annotation.getFilename(appliesTo);\n\t\textractBooleanArraySparse(filename, getUMBIndex().getEntityCount(appliesTo), longConsumer);\n\t}\n\n\tpublic void extractIndexedBooleanAnnotation(String group, String id, UMBIndex.UMBEntity appliesTo, LongBooleanConsumer longBooleanConsumer) throws UMBException\n\t{\n\t\textractIndexedBooleanAnnotation(umbIndex.getAnnotation(group, id), appliesTo, longBooleanConsumer);\n\t}\n\n\tpublic void extractIndexedBooleanAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, LongBooleanConsumer longBooleanConsumer) throws UMBException\n\t{\n\t\tString filename = annotation.getFilename(appliesTo);\n\t\textractBooleanArray(filename, getUMBIndex().getEntityCount(appliesTo), new IndexedBooleanConsumer(longBooleanConsumer));\n\t}\n\n\tpublic void extractIntAnnotation(String group, String id, UMBIndex.UMBEntity appliesTo, IntConsumer intConsumer) throws UMBException\n\t{\n\t\textractIntAnnotation(umbIndex.getAnnotation(group, id), appliesTo, intConsumer);\n\t}\n\n\tpublic void extractIntAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, IntConsumer intConsumer) throws UMBException\n\t{\n\t\tString filename = annotation.getFilename(appliesTo);\n\t\textractIntArray(filename, getUMBIndex().getEntityCount(appliesTo), intConsumer);\n\t}\n\n\tpublic void extractIndexedIntAnnotation(String group, String id, UMBIndex.UMBEntity appliesTo, LongIntConsumer longIntConsumer) throws UMBException\n\t{\n\t\textractIndexedIntAnnotation(umbIndex.getAnnotation(group, id), appliesTo, longIntConsumer);\n\t}\n\n\tpublic void extractIndexedIntAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, LongIntConsumer longIntConsumer) throws UMBException\n\t{\n\t\tString filename = annotation.getFilename(appliesTo);\n\t\textractIntArray(filename, getUMBIndex().getEntityCount(appliesTo), new IndexedIntConsumer(longIntConsumer));\n\t}\n\n\tpublic void extractDoubleAnnotation(String group, String id, UMBIndex.UMBEntity appliesTo, DoubleConsumer doubleConsumer) throws UMBException\n\t{\n\t\textractDoubleAnnotation(umbIndex.getAnnotation(group, id), appliesTo, doubleConsumer);\n\t}\n\n\tpublic void extractDoubleAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, DoubleConsumer doubleConsumer) throws UMBException\n\t{\n\t\tString filename = annotation.getFilename(appliesTo);\n\t\textractDoubleArray(filename, getUMBIndex().getEntityCount(appliesTo), doubleConsumer);\n\t}\n\n\tpublic void extractContinuousNumericAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, Consumer<?> consumer) throws UMBException\n\t{\n\t\tString filename = annotation.getFilename(appliesTo);\n\t\textractContinuousNumericArray(filename, annotation.getType(), getUMBIndex().getEntityCount(appliesTo), consumer);\n\t}\n\n\tpublic void extractStringAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, Consumer<String> stringConsumer) throws UMBException\n\t{\n\t\tString folderName = annotation.getFolderName(appliesTo);\n\t\textractStrings(folderName, annotation.getNumStrings(), stringConsumer);\n\t}\n\n\t/**\n\t * Extract the state valuations (variable values), one bitstring per state.\n\t * @param bitstringConsumer Bitstring consumer\n\t */\n\tpublic void extractStateValuations(Consumer<UMBBitString> bitstringConsumer) throws UMBException\n\t{\n\t\textractValuations(UMBIndex.UMBEntity.STATES, bitstringConsumer);\n\t}\n\n\t/**\n\t * Extract the observation valuations (observable values), one bitstring per observation.\n\t * @param bitstringConsumer Bitstring consumer\n\t */\n\tpublic void extractObservationValuations(Consumer<UMBBitString> bitstringConsumer) throws UMBException\n\t{\n\t\textractValuations(UMBIndex.UMBEntity.OBSERVATIONS, bitstringConsumer);\n\t}\n\n\t/**\n\t * Extract the class of valuations (variable values) used for each one of the specified entity type.\n\t * @param entity The entity to which the valuations apply\n\t * @param intConsumer Integer class consumer\n\t */\n\tpublic void extractValuationClasses(UMBIndex.UMBEntity entity, IntConsumer intConsumer) throws UMBException\n\t{\n\t\textractIntArray(UMBFormat.valuationClassesFile(entity), umbIndex.getEntityCount(entity), intConsumer);\n\t}\n\n\t/**\n\t * Extract the valuations (variable values) for an entity, as bitstrings.\n\t * @param entity The entity to which the valuations apply\n\t * @param bitstringConsumer Bitstring consumer\n\t */\n\tpublic void extractValuations(UMBIndex.UMBEntity entity, Consumer<UMBBitString> bitstringConsumer) throws UMBException\n\t{\n\t\tUMBBitPacking bitPacking = umbIndex.getValuationBitPacking(entity);\n\t\textractBitStringArray(UMBFormat.valuationsFile(entity), umbIndex.getEntityCount(entity), bitPacking.getTotalNumBytes(), bitstringConsumer);\n\t}\n\n\t/**\n\t * Compute the range of a (signed or unsigned) integer variable, from the values stored for it in a list of valuations.\n\t * This assumes that the min/max values needs at most 32 bits, so that they can be stored in an {@code int}.\n\t * @param entity The entity to which the valuations apply\n\t * @param bitPacking The bit-packing for the valuations\n\t * @param i Index of the variable (in the bit-packing)\n\t */\n\tpublic UMBReader.IntRange getValuationIntRange(UMBIndex.UMBEntity entity, UMBBitPacking bitPacking, int i) throws UMBException\n\t{\n\t\tUMBReader.IntRangeComputer varRange = new UMBReader.IntRangeComputer();\n\t\ttry {\n\t\t\textractValuations(entity, bitString -> {\n\t\t\t\ttry {\n\t\t\t\t\tswitch (bitPacking.getVariable(i).getType().type) {\n\t\t\t\t\t\tcase INT:\n\t\t\t\t\t\t\tvarRange.accept(bitPacking.getIntVariableValue(bitString, i));\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase UINT:\n\t\t\t\t\t\t\tvarRange.accept(bitPacking.getUIntVariableValue(bitString, i));\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tthrow new UMBException(\"Cannot compute the integer range of a \" + bitPacking.getVariable(i).getType().type);\n\t\t\t\t\t}\n\t\t\t\t} catch (UMBException e) {\n\t\t\t\t\tthrow new RuntimeException(e);\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (UMBException | RuntimeException e) {\n\t\t\tthrow new UMBException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t\treturn varRange;\n\t}\n\n\t/**\n\t * Compute the range of a (signed or unsigned) integer variable, from the values stored for it in a list of valuations.\n\t * This assumes that the min/max values needs at most 64 bits, so that they can be stored in a {@code long}.\n\t * @param entity The entity to which the valuations apply\n\t * @param bitPacking The bit-packing for the valuations\n\t * @param i Index of the variable (in the bit-packing)\n\t */\n\tpublic UMBReader.LongRange getValuationLongRange(UMBIndex.UMBEntity entity, UMBBitPacking bitPacking, int i) throws UMBException\n\t{\n\t\tUMBReader.LongRangeComputer varRange = new UMBReader.LongRangeComputer();\n\t\ttry {\n\t\t\textractValuations(entity, bitString -> {\n\t\t\t\ttry {\n\t\t\t\t\tswitch (bitPacking.getVariable(i).getType().type) {\n\t\t\t\t\t\tcase INT:\n\t\t\t\t\t\t\tvarRange.accept(bitPacking.getLongVariableValue(bitString, i));\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase UINT:\n\t\t\t\t\t\t\tvarRange.accept(bitPacking.getULongVariableValue(bitString, i));\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tthrow new UMBException(\"Cannot compute the integer range of a \" + bitPacking.getVariable(i).getType().type);\n\t\t\t\t\t}\n\t\t\t\t} catch (UMBException e) {\n\t\t\t\t\tthrow new RuntimeException(e);\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (UMBException | RuntimeException e) {\n\t\t\tthrow new UMBException(\"UMB import problem: \" + e.getMessage());\n\t\t}\n\t\treturn varRange;\n\t}\n\n\t// Local methods for extracting data\n\n\tprivate boolean fileExists(String filename) throws UMBException\n\t{\n\t\tUMBIn umbIn = open();\n\t\tboolean exists = umbIn.archiveEntryExists(filename);\n\t\tumbIn.close();\n\t\treturn exists;\n\t}\n\n\tprivate void extractBooleanArraySparse(String filename, long size, LongConsumer longConsumer) throws UMBException\n\t{\n\t\tUMBIn umbIn = open();\n\t\ttry {\n\t\t\tlong entrySize = umbIn.findArchiveEntry(filename);\n\t\t\t//long minExpectedSize = (size + 7) / 8;\n\t\t\tlong expectedSize = ((size + 63) / 64) * 8;\n\t\t\tif (entrySize != expectedSize) {\n\t\t\t\tthrow new UMBException(\"File \" + filename + \" has unexpected size (\" + entrySize + \" bytes)\");\n\t\t\t}\n\t\t\tByteBuffer bytes;\n\t\t\tint numBytes = Long.BYTES;\n\t\t\tlong leftToRead = ((size + 63) / 64);\n\t\t\tint cacheSize = (int) Math.min((BUFFER_SIZE) / numBytes, leftToRead);\n\t\t\tlong[] cache = new long[cacheSize];\n\t\t\tint toRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\tlong index = 0;\n\t\t\twhile (toRead > 0 && (bytes = umbIn.readBytes(toRead * numBytes)) != null) {\n\t\t\t\t// Cache data\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tcache[i] = bytes.getLong();\n\t\t\t\t}\n\t\t\t\t// Pass data to consumer\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tlong l = cache[i];\n\t\t\t\t\t// Find local index j of each 1 bit within 64-bit block\n\t\t\t\t\tint blockSize = index + Long.BYTES * 8 <= size ? Long.BYTES * 8 : (int) (size - index);\n\t\t\t\t\tfor (int j = 0; j < blockSize; j++) {\n\t\t\t\t\t\tif ((l & (1L << j)) != 0) {\n\t\t\t\t\t\t\tlongConsumer.accept(index + j);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tindex += Long.BYTES * 8;\n\t\t\t\t}\n\t\t\t\tleftToRead -= toRead;\n\t\t\t\ttoRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\t}\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in consumers so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error extracting from UMB file: \" + e.getMessage());\n\t\t} finally {\n\t\t\tumbIn.close();\n\t\t}\n\t}\n\n\tprivate void extractBooleanArray(String filename, long size, BooleanConsumer booleanConsumer) throws UMBException\n\t{\n\t\tUMBIn umbIn = open();\n\t\ttry {\n\t\t\tlong entrySize = umbIn.findArchiveEntry(filename);\n\t\t\t//long minExpectedSize = (size + 7) / 8;\n\t\t\tlong expectedSize = ((size + 63) / 64) * 8;\n\t\t\tif (entrySize != expectedSize) {\n\t\t\t\tthrow new UMBException(\"File \" + filename + \" has unexpected size (\" + entrySize + \" bytes)\");\n\t\t\t}\n\t\t\tByteBuffer bytes;\n\t\t\tint numBytes = Long.BYTES;\n\t\t\tlong leftToRead = ((size + 63) / 64);\n\t\t\tint cacheSize = (int) Math.min((BUFFER_SIZE) / numBytes, leftToRead);\n\t\t\tlong[] cache = new long[cacheSize];\n\t\t\tint toRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\tlong index = 0;\n\t\t\twhile (toRead > 0 && (bytes = umbIn.readBytes(toRead * numBytes)) != null) {\n\t\t\t\t// Cache data\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tcache[i] = bytes.getLong();\n\t\t\t\t}\n\t\t\t\t// Pass data to consumer\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tlong l = cache[i];\n\t\t\t\t\t// Find local index j of each 1 bit within 64-bit block\n\t\t\t\t\tint blockSize = index + Long.BYTES * 8 <= size ? Long.BYTES * 8 : (int) (size - index);\n\t\t\t\t\tfor (int j = 0; j < blockSize; j++) {\n\t\t\t\t\t\tbooleanConsumer.accept((l & (1L << j)) != 0);\n\t\t\t\t\t}\n\t\t\t\t\tindex += Long.BYTES * 8;\n\t\t\t\t}\n\t\t\t\tleftToRead -= toRead;\n\t\t\t\ttoRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\t}\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in consumers so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error extracting from UMB file: \" + e.getMessage());\n\t\t} finally {\n\t\t\tumbIn.close();\n\t\t}\n\t}\n\n\tprivate void extractIntArray(String filename, long size, IntConsumer intConsumer) throws UMBException\n\t{\n\t\tUMBIn umbIn = open();\n\t\ttry {\n\t\t\tlong entrySize = umbIn.findArchiveEntry(filename);\n\t\t\tif (entrySize != size * Integer.BYTES) {\n\t\t\t\tthrow new UMBException(\"File \" + filename + \" has unexpected size (\" + entrySize + \" bytes, not \" + (size * Integer.BYTES) + \")\");\n\t\t\t}\n\t\t\tByteBuffer bytes;\n\t\t\tint numBytes = Integer.BYTES;\n\t\t\tlong leftToRead = size;\n\t\t\tint cacheSize = (int) Math.min((BUFFER_SIZE) / numBytes, leftToRead);\n\t\t\tint[] cache = new int[cacheSize];\n\t\t\tint toRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\twhile (toRead > 0 && (bytes = umbIn.readBytes(toRead * numBytes)) != null) {\n\t\t\t\t// Cache data\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tcache[i] = bytes.getInt();\n\t\t\t\t}\n\t\t\t\t// Pass data to consumer\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tintConsumer.accept(cache[i]);\n\t\t\t\t}\n\t\t\t\tleftToRead -= toRead;\n\t\t\t\ttoRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\t}\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in consumers so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error extracting from UMB file: \" + e.getMessage());\n\t\t} finally {\n\t\t\tumbIn.close();\n\t\t}\n\t}\n\n\tprivate void extractLongArray(String filename, long size, LongConsumer longConsumer) throws UMBException\n\t{\n\t\tUMBIn umbIn = open();\n\t\ttry {\n\t\t\tlong entrySize = umbIn.findArchiveEntry(filename);\n\t\t\tif (entrySize != size * Long.BYTES) {\n\t\t\t\tthrow new UMBException(\"File \" + filename + \" has unexpected size (\" + entrySize + \" bytes, not \" + (size * Long.BYTES) + \")\");\n\t\t\t}\n\t\t\tByteBuffer bytes;\n\t\t\tint numBytes = Long.BYTES;\n\t\t\tlong leftToRead = size;\n\t\t\tint cacheSize = (int) Math.min((BUFFER_SIZE) / numBytes, leftToRead);\n\t\t\tlong[] cache = new long[cacheSize];\n\t\t\tint toRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\twhile (toRead > 0 && (bytes = umbIn.readBytes(toRead * numBytes)) != null) {\n\t\t\t\t// Cache data\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tcache[i] = bytes.getLong();\n\t\t\t\t}\n\t\t\t\t// Pass data to consumer\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tlongConsumer.accept(cache[i]);\n\t\t\t\t}\n\t\t\t\tleftToRead -= toRead;\n\t\t\t\ttoRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\t}\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in consumers so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error extracting from UMB file: \" + e.getMessage());\n\t\t} finally {\n\t\t\tumbIn.close();\n\t\t}\n\t}\n\n\tprivate void extractDoubleArray(String filename, long size, DoubleConsumer doubleConsumer) throws UMBException\n\t{\n\t\tUMBIn umbIn = open();\n\t\ttry {\n\t\t\tlong entrySize = umbIn.findArchiveEntry(filename);\n\t\t\tif (entrySize != size * Double.BYTES) {\n\t\t\t\tthrow new UMBException(\"File \" + filename + \" has unexpected size (\" + entrySize + \" bytes, not \" + (size * Double.BYTES) + \")\");\n\t\t\t}\n\t\t\tByteBuffer bytes;\n\t\t\tint numBytes = Double.BYTES;\n\t\t\tlong leftToRead = size;\n\t\t\tint cacheSize = (int) Math.min((BUFFER_SIZE) / numBytes, leftToRead);\n\t\t\tdouble[] cache = new double[cacheSize];\n\t\t\tint toRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\twhile (toRead > 0 && (bytes = umbIn.readBytes(toRead * numBytes)) != null) {\n\t\t\t\t// Cache data\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tcache[i] = bytes.getDouble();\n\t\t\t\t}\n\t\t\t\t// Pass data to consumer\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tdoubleConsumer.accept(cache[i]);\n\t\t\t\t}\n\t\t\t\tleftToRead -= toRead;\n\t\t\t\ttoRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\t}\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in consumers so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error extracting from UMB file: \" + e.getMessage());\n\t\t} finally {\n\t\t\tumbIn.close();\n\t\t}\n\t}\n\n\tprivate void extractContinuousNumericArray(String filename, UMBType type, long size, Consumer<?> consumer) throws UMBException\n\t{\n\t\tlong sizeNew = type.type.isInterval() ? size * 2 : size;\n\t\tif (type.type.isDouble()) {\n\t\t\textractDoubleArray(filename, sizeNew, (it.unimi.dsi.fastutil.doubles.DoubleConsumer) ((Consumer<Double>) consumer)::accept);\n\t\t} else if (type.type.isRational()) {\n\t\t\tif (!type.isDefaultSize()) {\n\t\t\t\tthrow new UMBException(\"Non-default sized rationals are not yet supported\");\n\t\t\t}\n\t\t\textractLongArray(filename, sizeNew * 2, (it.unimi.dsi.fastutil.longs.LongConsumer) ((Consumer<Long>) consumer)::accept);\n\t\t} else {\n\t\t\tthrow new UMBException(\"Unsupported continuous numeric type \" + type);\n\t\t}\n\t}\n\n\tprivate void extractBitStringArray(String filename, long size, int numBytes, Consumer<UMBBitString> bitstringConsumer) throws UMBException\n\t{\n\t\tUMBIn umbIn = open();\n\t\ttry {\n\t\t\tlong entrySize = umbIn.findArchiveEntry(filename);\n\t\t\tif (entrySize != size * numBytes) {\n\t\t\t\tthrow new UMBException(\"File \" + filename + \" has unexpected size (\" + entrySize + \" bytes, not \" + (size * numBytes) + \")\");\n\t\t\t}\n\t\t\tByteBuffer bytes;\n\t\t\tlong leftToRead = size;\n\t\t\tint cacheSize = (int) Math.min((BUFFER_SIZE) / numBytes, leftToRead);\n\t\t\tUMBBitString[] cache = new UMBBitString[cacheSize];\n\t\t\tfor (int i = 0; i < cacheSize; i++) {\n\t\t\t\tcache[i] = new UMBBitString(numBytes);\n\t\t\t}\n\t\t\tint toRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\twhile (toRead > 0 && (bytes = umbIn.readBytes(toRead * numBytes)) != null) {\n\t\t\t\t// Cache data\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tbytes.get(cache[i].bytes);\n\t\t\t\t}\n\t\t\t\t// Pass data to consumer\n\t\t\t\tfor (int i = 0; i < toRead; i++) {\n\t\t\t\t\tbitstringConsumer.accept(cache[i]);\n\t\t\t\t}\n\t\t\t\tleftToRead -= toRead;\n\t\t\t\ttoRead = (int) (Math.min(leftToRead, cacheSize));\n\t\t\t}\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in consumers so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error extracting from UMB file: \" + e.getMessage());\n\t\t} finally {\n\t\t\tumbIn.close();\n\t\t}\n\t}\n\n\t/**\n\t * Extract strings, as stored in a files for string offsets and data in a folder\n\t */\n\tprivate void extractStrings(String folderName, int numStrings, Consumer<String> stringConsumer) throws UMBException\n\t{\n\t\tList<Long> stringOffsets = new ArrayList<>(numStrings);\n\t\textractLongArray(UMBFormat.stringOffsetsFile(folderName), numStrings + 1, stringOffsets::add);\n\t\textractStringList(UMBFormat.stringsFile(folderName), stringOffsets, stringConsumer);\n\t}\n\n\tprivate void extractStringList(String filename, List<Long> stringOffsets, Consumer<String> stringConsumer) throws UMBException\n\t{\n\t\tUMBIn umbIn = open();\n\t\ttry {\n\t\t\tint numStrings = stringOffsets.size() - 1;\n\t\t\tlong entrySize = umbIn.findArchiveEntry(filename);\n\t\t\tif (entrySize != stringOffsets.get(numStrings)) {\n\t\t\t\tthrow new UMBException(\"File \" + filename + \" has unexpected size (\" + entrySize + \" bytes, not \" + stringOffsets.get(numStrings) + \")\");\n\t\t\t}\n\t\t\tfor (int i = 0; i < numStrings; i++) {\n\t\t\t\tlong sLen = stringOffsets.get(i + 1) - stringOffsets.get(i);\n\t\t\t\tif (sLen > Integer.MAX_VALUE) {\n\t\t\t\t\tthrow new UMBException(\"Could not read overlength string (\" + sLen + \"bytes) from file \" + filename);\n\t\t\t\t}\n\t\t\t\tString s = umbIn.readString((int) sLen);\n\t\t\t\tif (s == null) {\n\t\t\t\t\tthrow new UMBException(\"Could not read string of length \" + sLen + \" from file \" + filename);\n\t\t\t\t}\n\t\t\t\tstringConsumer.accept(s);\n\t\t\t}\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in consumers so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error extracting from UMB file: \" + e.getMessage());\n\t\t} finally {\n\t\t\tumbIn.close();\n\t\t}\n\t}\n\n\t/**\n\t * Simulate extraction of a missing int array by filling the consumer with a default value.\n\t */\n\tprivate void extractDefaultIntArray(long size, UMBFormat.BinFileDefaultValue value, IntConsumer intConsumer) throws UMBException\n\t{\n\t\tswitch (value) {\n\t\t\tcase IDENTITY:\n\t\t\t\tfor (long i = 0; i < size; i++) {\n\t\t\t\t\tintConsumer.accept((int) i);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ZERO:\n\t\t\t\tfor (long i = 0; i < size; i++) {\n\t\t\t\t\tintConsumer.accept(0);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ONE:\n\t\t\t\tfor (long i = 0; i < size; i++) {\n\t\t\t\t\tintConsumer.accept(1);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new UMBException(\"Unsupported default value \" + value);\n\t\t}\n\t}\n\n\t/**\n\t * Simulate extraction of a missing long array by filling the consumer with a default value.\n\t */\n\tprivate void extractDefaultLongArray(long size, UMBFormat.BinFileDefaultValue value, LongConsumer longConsumer) throws UMBException\n\t{\n\t\tswitch (value) {\n\t\t\tcase IDENTITY:\n\t\t\t\tfor (long i = 0; i < size; i++) {\n\t\t\t\t\tlongConsumer.accept(i);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ZERO:\n\t\t\t\tfor (long i = 0; i < size; i++) {\n\t\t\t\t\tlongConsumer.accept(0L);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ONE:\n\t\t\t\tfor (long i = 0; i < size; i++) {\n\t\t\t\t\tlongConsumer.accept(1L);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new UMBException(\"Unsupported default value \" + value);\n\t\t}\n\t}\n\n\t/**\n\t * Simulate extraction of a missing continuous numeric array by filling the consumer with a default value.\n\t */\n\tprivate void extractDefaultContinuousNumericArray(UMBType type, long size, UMBFormat.BinFileDefaultValue value, Consumer<?> consumer) throws UMBException\n\t{\n\t\tlong sizeNew = type.type.isInterval() ? size * 2 : size;\n\t\tif (type.type.isDouble()) {\n\t\t\tDoubleConsumer doubleConsumer = (DoubleConsumer) consumer;\n\t\t\tdouble doubleValue;\n\t\t\tswitch (value) {\n\t\t\t\tcase ZERO:\n\t\t\t\t\tdoubleValue = 0.0;\n\t\t\t\t\tbreak;\n\t\t\t\tcase ONE:\n\t\t\t\t\tdoubleValue = 1.0;\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new UMBException(\"Unsupported default value \" + value);\n\t\t\t}\n\t\t\tfor (long i = 0; i < sizeNew; i++) {\n\t\t\t\tdoubleConsumer.accept(doubleValue);\n\t\t\t}\n\t\t} else if (type.type.isRational()) {\n\t\t\tif (!type.isDefaultSize()) {\n\t\t\t\tthrow new UMBException(\"Non-default sized rationals are not yet supported\");\n\t\t\t}\n\t\t\tLongConsumer longConsumer = (it.unimi.dsi.fastutil.longs.LongConsumer) consumer;\n\t\t\tlong longValue1;\n\t\t\tlong longValue2;\n\t\t\tswitch (value) {\n\t\t\t\tcase ZERO:\n\t\t\t\t\tlongValue1 = 0L;\n\t\t\t\t\tlongValue2 = 1L;\n\t\t\t\t\tbreak;\n\t\t\t\tcase ONE:\n\t\t\t\t\tlongValue1 = 1L;\n\t\t\t\t\tlongValue2 = 1L;\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new UMBException(\"Unsupported default value \" + value);\n\t\t\t}\n\t\t\tfor (long i = 0; i < sizeNew; i++) {\n\t\t\t\tlongConsumer.accept(longValue1);\n\t\t\t\tlongConsumer.accept(longValue2);\n\t\t\t}\n\t\t} else {\n\t\t\tthrow new UMBException(\"Unsupported continuous numeric type \" + type);\n\t\t}\n\t}\n\n\tUMBIn umbInCached = null;\n\n\tprivate UMBIn open() throws UMBException\n\t{\n\t\tif (umbInCached != null) {\n\t\t\treturn umbInCached;\n\t\t} else {\n//\t\t\tumbInCached = new UMBIn(fileIn);;\n//\t\t\treturn umbInCached;\n\t\t\treturn new UMBIn(fileIn);\n\t\t}\n\t}\n\n\t//\n\n\t/**\n\t * Class to manage reading from the zipped archive for a UMB file\n\t */\n\tprivate static class UMBIn\n\t{\n\t\t/** Input stream from zip file */\n\t\tprivate final InputStream fsIn;\n\t\t/** Input stream after unzipping */\n\t\tprivate CompressorInputStream zipIn;\n\t\t/** Input stream from tar file */\n\t\tprivate TarArchiveInputStream tarIn;\n\n\t\t/** Byte buffer used to return file contents */\n\t\tprivate ByteBuffer byteBuffer;\n\t\t/** Initial size of byte buffer */\n\t\tprivate static final int DEFAULT_BUFFER_SIZE = 1024;\n\n\t\t/**\n\t\t * Open a new UMB file for reading\n\t\t */\n\t\tpublic UMBIn(File fileIn) throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\t// Open file/zip/tar and create buffer\n\t\t\t\tfsIn = new BufferedInputStream(Files.newInputStream(fileIn.toPath()));\n\t\t\t\ttry {\n\t\t\t\t\t// Any supported zip format is fine\n\t\t\t\t\tzipIn = new CompressorStreamFactory().createCompressorInputStream(fsIn);\n\t\t\t\t\ttarIn = new TarArchiveInputStream(zipIn);\n\t\t\t\t} catch (CompressorException e) {\n\t\t\t\t\t// No zipping also fine\n\t\t\t\t\tzipIn = null;\n\t\t\t\t\ttarIn = new TarArchiveInputStream(fsIn);\n\t\t\t\t}\n\t\t\t\tbyteBuffer = ByteBuffer.allocate(DEFAULT_BUFFER_SIZE).order(ByteOrder.LITTLE_ENDIAN);\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"Could not open UMB file: \" + e.getMessage());\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Check if an entry (file) exists within the archive.\n\t\t * @param name Name of the file\n\t\t */\n\t\tpublic boolean archiveEntryExists(String name) throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\tTarArchiveEntry entry;\n\t\t\t\twhile ((entry = tarIn.getNextTarEntry()) != null) {\n\t\t\t\t\tif (!tarIn.canReadEntryData(entry)) {\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\tif (entry.getName().equals(name)) {\n\t\t\t\t\t\treturn true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error extracting from UMB file\");\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\t/**\n\t\t * Find an entry (file) within the archive for subsequent reading.\n\t\t * Returns the size (number of bytes) of the entry if it is found,\n\t\t * or throws an exception if not.\n\t\t * @param name Name of the file\n\t\t */\n\t\tpublic long findArchiveEntry(String name) throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\tTarArchiveEntry entry;\n\t\t\t\twhile ((entry = tarIn.getNextTarEntry()) != null) {\n\t\t\t\t\tif (!tarIn.canReadEntryData(entry)) {\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\tif (entry.getName().equals(name)) {\n\t\t\t\t\t\treturn entry.getSize();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error extracting from UMB file\");\n\t\t\t}\n\t\t\tthrow new UMBException(\"UMB archive entry \\\"\" + name + \"\\\" not found\");\n\t\t}\n\n\t\tpublic TarArchiveInputStream getInputStream()\n\t\t{\n\t\t\treturn tarIn;\n\t\t}\n\n\t\t/**\n\t\t * Read the specified number of bytes from the current entry (file) of the archive.\n\t\t * Returns the bytes in a {@link ByteBuffer}, or returns null if no or too few bytes are available.\n\t\t */\n\t\tpublic ByteBuffer readBytes(int numBytes) throws UMBException\n\t\t{\n\t\t\t// Ensure buffer is big enough\n\t\t\tif (numBytes > byteBuffer.capacity()) {\n\t\t\t\tbyteBuffer = ByteBuffer.allocate(numBytes).order(ByteOrder.LITTLE_ENDIAN);\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tbyte[] bytes = byteBuffer.array();\n\t\t\t\tint bytesRead = tarIn.read(bytes, 0, numBytes);\n\t\t\t\tbyteBuffer.position(numBytes);\n\t\t\t\tif (bytesRead < numBytes) {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t\t// Prepare buffer for reading and return\n\t\t\t\tbyteBuffer.flip();\n\t\t\t\treturn byteBuffer;\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error extracting \" + numBytes + \" bytes from UMB entry \\\"\" + tarIn.getCurrentEntry().getName() + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Read the specified number of bytes from the current entry (file) of the archive.\n\t\t * Returns the bytes in a {@link ByteBuffer}. Returns null if there are no bytes\n\t\t * to read (or none were requested). If there are less than {@code numBytes} bytes,\n\t\t * the result is padded with zero bytes.\n\t\t */\n\t\tpublic ByteBuffer readBytesPadded(int numBytes) throws UMBException\n\t\t{\n\t\t\t// Ensure buffer is big enough\n\t\t\tif (numBytes > byteBuffer.capacity()) {\n\t\t\t\tbyteBuffer = ByteBuffer.allocate(numBytes).order(ByteOrder.LITTLE_ENDIAN);\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tbyte[] bytes = byteBuffer.array();\n\t\t\t\tint bytesRead = tarIn.read(bytes, 0, numBytes);\n\t\t\t\tbyteBuffer.position(numBytes);\n\t\t\t\tif (bytesRead <= 0) {\n\t\t\t\t\treturn null;\n\t\t\t\t} else if (bytesRead < numBytes) {\n\t\t\t\t\tfor (int i = bytesRead; i < numBytes; i++) {\n\t\t\t\t\t\tbytes[i] = (byte) 0;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Prepare buffer for reading and return\n\t\t\t\tbyteBuffer.flip();\n\t\t\t\treturn byteBuffer;\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error extracting \" + numBytes + \" bytes from UMB entry \\\"\" + tarIn.getCurrentEntry().getName() + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Read a string of the specified length from the current entry (file) of the archive.\n\t\t */\n\t\tpublic String readString(int length) throws UMBException\n\t\t{\n\t\t\t// Ensure buffer is big enough\n\t\t\tif (length > byteBuffer.capacity()) {\n\t\t\t\tbyteBuffer = ByteBuffer.allocate(length).order(ByteOrder.LITTLE_ENDIAN);\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tbyte[] bytes = byteBuffer.array();\n\t\t\t\tint bytesRead = tarIn.read(bytes, 0, length);\n\t\t\t\tbyteBuffer.position(length);\n\t\t\t\tif (bytesRead < length) {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t\treturn new String(bytes, 0, bytesRead, StandardCharsets.UTF_8);\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error extracting string from UMB entry \\\"\" + tarIn.getCurrentEntry().getName() + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Read the whole of the current entry (file) of the archive as a string.\n\t\t */\n\t\tpublic String readAsString() throws UMBException\n\t\t{\n\t\t\tStringBuilder sb = new StringBuilder();\n\t\t\ttry {\n\t\t\t\tbyte[] bytes = byteBuffer.array();\n\t\t\t\tint bytesRead;\n\t\t\t\twhile ((bytesRead = tarIn.read(bytes)) != -1) {\n\t\t\t\t\tsb.append(new String(bytes, 0, bytesRead, StandardCharsets.UTF_8));\n\t\t\t\t}\n\t\t\t\treturn sb.toString();\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error extracting string from UMB entry \\\"\" + tarIn.getCurrentEntry().getName() + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Close the UMB file.\n\t\t */\n\t\tpublic void close() throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\tif (tarIn != null) {\n\t\t\t\t\ttarIn.close();\n\t\t\t\t}\n\t\t\t\tif (zipIn != null) {\n\t\t\t\t\tzipIn.close();\n\t\t\t\t}\n\t\t\t\tif (fsIn != null) {\n\t\t\t\t\tfsIn.close();\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error closing UMB file\");\n\t\t\t}\n\t\t}\n\t}\n\n\t// Utility classes\n\n\t@FunctionalInterface\n\tpublic interface LongBooleanConsumer\n\t{\n\t\tvoid accept(long index, boolean value);\n\t}\n\n\t@FunctionalInterface\n\tpublic interface LongIntConsumer\n\t{\n\t\tvoid accept(long index, int value);\n\t}\n\n\t@FunctionalInterface\n\tpublic interface LongLongConsumer\n\t{\n\t\tvoid accept(long index, long value);\n\t}\n\n\t/**\n\t * Class to convert a sequence of ints to a sequence of (long) indexed ints.\n\t */\n\tpublic static class IndexedIntConsumer implements IntConsumer\n\t{\n\t\tprivate final LongIntConsumer longIntConsumer;\n\t\tprivate long index = 0;\n\n\t\tpublic IndexedIntConsumer(LongIntConsumer longIntConsumer)\n\t\t{\n\t\t\tthis.longIntConsumer = longIntConsumer;\n\t\t}\n\n\t\t@Override\n\t\tpublic void accept(int intValue)\n\t\t{\n\t\t\tlongIntConsumer.accept(index++, intValue);\n\t\t}\n\t}\n\n\t/**\n\t * Class to convert a sequence of booleans to a sequence of (long) indexed booleans.\n\t */\n\tpublic static class IndexedBooleanConsumer implements BooleanConsumer\n\t{\n\t\tprivate final LongBooleanConsumer longBooleanConsumer;\n\t\tprivate long index = 0;\n\n\t\tpublic IndexedBooleanConsumer(LongBooleanConsumer longBooleanConsumer)\n\t\t{\n\t\t\tthis.longBooleanConsumer = longBooleanConsumer;\n\t\t}\n\n\t\t@Override\n\t\tpublic void accept(boolean booleanValue)\n\t\t{\n\t\t\tlongBooleanConsumer.accept(index++, booleanValue);\n\t\t}\n\t}\n\n\t/**\n\t * Class to convert a non-decreasing sequence of n+1 non-negative (long) offsets\n\t * to a corresponding sequence of n (long) counts. Both via consumers of longs.\n\t */\n\tpublic static class OffsetsToCounts implements LongConsumer\n\t{\n\t\tLongConsumer out;\n\t\tlong offsetLast;\n\n\t\tOffsetsToCounts(LongConsumer out)\n\t\t{\n\t\t\tthis.out = out;\n\t\t}\n\n\t\t@Override\n\t\tpublic void accept(long offset)\n\t\t{\n\t\t\tif (offsetLast != -1) {\n\t\t\t\tout.accept(offset - offsetLast);\n\t\t\t}\n\t\t\toffsetLast = offset;\n\t\t}\n\t}\n\n\t/**\n\t * Class to represent the minimum/maximum value of a set of ints.\n\t */\n\tpublic static class IntRange\n\t{\n\t\tint min = Integer.MAX_VALUE;\n\t\tint max = Integer.MIN_VALUE;\n\n\t\tpublic int getMin()\n\t\t{\n\t\t\treturn min;\n\t\t}\n\n\t\tpublic int getMax()\n\t\t{\n\t\t\treturn max;\n\t\t}\n\t}\n\n\t/**\n\t * Class to represent the minimum/maximum value of a set of longs.\n\t */\n\tpublic static class LongRange\n\t{\n\t\tlong min = Long.MAX_VALUE;\n\t\tlong max = Long.MIN_VALUE;\n\n\t\tpublic long getMin()\n\t\t{\n\t\t\treturn min;\n\t\t}\n\n\t\tpublic long getMax()\n\t\t{\n\t\t\treturn max;\n\t\t}\n\t}\n\n\t/**\n\t * Class to compute the minimum/maximum value of a sequence of ints, provided via a consumer.\n\t */\n\tpublic static class IntRangeComputer extends IntRange implements IntConsumer\n\t{\n\t\t@Override\n\t\tpublic void accept(int i)\n\t\t{\n\t\t\tmin = Integer.min(min, i); max = Integer.max(max, i);\n\t\t}\n\t}\n\n\t/**\n\t * Class to compute the minimum/maximum value of a sequence of longs, provided via a consumer.\n\t */\n\tpublic static class LongRangeComputer extends LongRange implements LongConsumer\n\t{\n\t\t@Override\n\t\tpublic void accept(long i)\n\t\t{\n\t\t\tmin = Long.min(min, i); max = Long.max(max, i);\n\t\t}\n\t}\n\n\t/**\n\t * Class to compute the maximum value of a sequence of longs, provided via a consumer.\n\t */\n\tpublic static class LongMax implements LongConsumer\n\t{\n\t\tlong max = Long.MIN_VALUE;\n\n\t\tpublic long getMax()\n\t\t{\n\t\t\treturn max;\n\t\t}\n\n\t\t@Override\n\t\tpublic void accept(long l)\n\t\t{\n\t\t\tmax = Long.max(max, l);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBType.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\nimport java.util.Objects;\n\n/**\n * Class representing a UMB data type.\n */\npublic class UMBType\n{\n    /** UMB types */\n    public enum Type implements UMBIndex.UMBField\n    {\n        BOOL,\n        INT, UINT, INT_INTERVAL, UINT_INTERVAL,\n        DOUBLE, DOUBLE_INTERVAL, RATIONAL, RATIONAL_INTERVAL,\n        STRING;\n        @Override\n        public String toString()\n        {\n            return description();\n        }\n\n        public boolean isContinuousNumeric()\n        {\n            switch (this) {\n                case DOUBLE:\n                case DOUBLE_INTERVAL:\n                case RATIONAL:\n                case RATIONAL_INTERVAL:\n                    return true;\n                default:\n                    return false;\n            }\n        }\n\n        public boolean isDouble()\n        {\n            switch (this) {\n                case DOUBLE:\n                case DOUBLE_INTERVAL:\n                    return true;\n                default:\n                    return false;\n            }\n        }\n\n        public boolean isRational()\n        {\n            switch (this) {\n                case RATIONAL:\n                case RATIONAL_INTERVAL:\n                    return true;\n                default:\n                    return false;\n            }\n        }\n\n        public boolean isInterval()\n        {\n            switch (this) {\n                case DOUBLE_INTERVAL:\n                case RATIONAL_INTERVAL:\n                    return true;\n                default:\n                    return false;\n            }\n        }\n\n        /**\n         * Get the default size (in bits) for this type.\n         */\n        public Integer defaultSize()\n        {\n            switch (this) {\n                case BOOL:\n                    return 1;\n                case INT:\n                case UINT:\n                case DOUBLE:\n                    return 64;\n                case INT_INTERVAL:\n                case UINT_INTERVAL:\n                case DOUBLE_INTERVAL:\n                    return 128;\n                case RATIONAL:\n                    return 128;\n                case RATIONAL_INTERVAL:\n                    return 256;\n                case STRING:\n                    return 64;\n                default:\n                    return null;\n            }\n        }\n    }\n\n    /** The type */\n    public Type type;\n\n    /** Size (number of bits) for the type; optional */\n    public Integer size;\n\n    public static UMBType create(Type type)\n    {\n        UMBType t = new UMBType();\n        t.type = type;\n        t.size = type.defaultSize();\n        return t;\n    }\n\n    public static UMBType create(Type type, Integer size)\n    {\n        UMBType t = new UMBType();\n        t.type = type;\n        t.size = size;\n        return t;\n    }\n\n    public static UMBType contNum(boolean rational)\n    {\n        return contNum(rational, false);\n    }\n\n    public static UMBType contNum(boolean rational, boolean interval)\n    {\n        if (rational) {\n            if (interval) {\n                return create(Type.RATIONAL_INTERVAL);\n            } else {\n                return create(Type.RATIONAL);\n            }\n        } else {\n            if (interval) {\n                return create(Type.DOUBLE_INTERVAL);\n            } else {\n                return create(Type.DOUBLE);\n            }\n        }\n    }\n\n    /**\n     * Is the size of this type equal to the default size?\n     * (either because it is not specified, or it matches the default)\n     */\n    public boolean isDefaultSize()\n    {\n        return size == null || Objects.equals(size, type.defaultSize());\n    }\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBUtils.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\nimport java.util.PrimitiveIterator;\nimport java.util.function.LongConsumer;\n\n/**\n * Miscellaneous utilities for working with UMB files.\n */\npublic class UMBUtils\n{\n\t/**\n\t * Class to convert a primitive operator (int to long).\n\t */\n\tpublic static class IntToLongIteratorAdapter implements PrimitiveIterator.OfLong\n\t{\n\t\tprivate final PrimitiveIterator.OfInt intIterator;\n\n\t\tpublic IntToLongIteratorAdapter(PrimitiveIterator.OfInt intIterator)\n\t\t{\n\t\t\tthis.intIterator = intIterator;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn intIterator.hasNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic long nextLong()\n\t\t{\n\t\t\treturn intIterator.nextInt();\n\t\t}\n\n\t\t@Override\n\t\tpublic void forEachRemaining(LongConsumer action)\n\t\t{\n\t\t\tintIterator.forEachRemaining((int value) -> action.accept(value));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBVersion.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\n/**\n * Version information\n */\npublic class UMBVersion\n{\n\tpublic static final int MAJOR = 1;\n\tpublic static final int MINOR = 0;\n\n\tpublic static String versionString()\n\t{\n\t\treturn MAJOR + \".\" + MINOR;\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/github/pmctools/umbj/UMBWriter.java",
    "content": "/*\n * Copyright 2025 Dave Parker (University of Oxford)\n *\n * Licensed under the Apache License, Version 2.0 (the \"License\");\n * you may not use this file except in compliance with the License.\n * You may obtain a copy of the License at\n *\n *     http://www.apache.org/licenses/LICENSE-2.0\n *\n * Unless required by applicable law or agreed to in writing, software\n * distributed under the License is distributed on an \"AS IS\" BASIS,\n * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n * See the License for the specific language governing permissions and\n * limitations under the License.\n */\n\npackage io.github.pmctools.umbj;\n\nimport it.unimi.dsi.fastutil.doubles.DoubleIterators;\nimport it.unimi.dsi.fastutil.longs.LongIterators;\nimport org.apache.commons.compress.archivers.ArchiveOutputStream;\nimport org.apache.commons.compress.archivers.tar.TarArchiveEntry;\nimport org.apache.commons.compress.archivers.tar.TarArchiveOutputStream;\nimport org.apache.commons.compress.compressors.CompressorException;\nimport org.apache.commons.compress.compressors.CompressorOutputStream;\nimport org.apache.commons.compress.compressors.CompressorStreamFactory;\n\nimport java.io.BufferedOutputStream;\nimport java.io.File;\nimport java.io.IOException;\nimport java.io.OutputStream;\nimport java.math.BigInteger;\nimport java.nio.ByteBuffer;\nimport java.nio.ByteOrder;\nimport java.nio.charset.StandardCharsets;\nimport java.nio.file.Files;\nimport java.util.*;\n\n/**\n * Class to handle writing to UMB files.\n */\npublic class UMBWriter\n{\n\t/**\n\t * The (JSON) index to be included in the UMB file.\n\t */\n\tprivate final UMBIndex umbIndex;\n\n\t/**\n\t * Representations of the data to be included in the UMB file.\n\t */\n\tprivate final List<UMBDataFile> umbDataFiles = new ArrayList<>();\n\n\t/**\n\t * Default buffer size (in bytes) for writing to UMB file.\n\t */\n\tprivate static int BUFFER_SIZE = 64 * 1024;\n\n\t/**\n\t * Construct a new {@link UMBWriter} to create a UMB file.\n\t */\n\tpublic UMBWriter()\n\t{\n\t\tumbIndex = new UMBIndex();\n\t}\n\n\t/**\n\t * Get access to the index that will be included in the export file.\n\t */\n\tpublic UMBIndex getUmbIndex()\n\t{\n\t\treturn umbIndex;\n\t}\n\n\t// Methods to add core model info\n\n\t/**\n\t * Add the state choice offsets, as an iterator of longs\n\t */\n\tpublic void addStateChoiceOffsets(PrimitiveIterator.OfLong stateChoiceOffsets)\n\t{\n\t\taddLongArray(UMBFormat.STATE_CHOICE_OFFSETS_FILE, stateChoiceOffsets, umbIndex.getNumStates() + 1);\n\t}\n\n\t/**\n\t * Add the state choice offsets, as an iterator of ints\n\t */\n\tpublic void addStateChoiceOffsets(PrimitiveIterator.OfInt stateChoiceOffsets)\n\t{\n\t\taddLongArray(UMBFormat.STATE_CHOICE_OFFSETS_FILE, new UMBUtils.IntToLongIteratorAdapter(stateChoiceOffsets), umbIndex.getNumStates() + 1);\n\t}\n\n\t/**\n\t * Add the players that own states (turn-based game models)\n\t */\n\tpublic void addStatePlayers(PrimitiveIterator.OfInt statePlayers)\n\t{\n\t\taddIntArray(UMBFormat.STATE_PLAYERS, statePlayers, umbIndex.getNumStates());\n\t}\n\n\t/**\n\t * Add the initial states, as a BitSet\n\t */\n\tpublic void addInitialStates(BitSet initialStates) throws UMBException\n\t{\n\t\taddBooleanArray(UMBFormat.INITIAL_STATES_FILE, initialStates, umbIndex.getNumStates());\n\t}\n\n\t/**\n\t * Add the initial states, in sparse form, i.e., a list of (long) state indices\n\t */\n\tpublic void addInitialStates(PrimitiveIterator.OfLong initStates) throws UMBException\n\t{\n\t\t// TODO - can't use BitSet; need BooleanArraySparse\n\t\tBitSet bsInitStates = new BitSet();\n\t\tinitStates.forEachRemaining((long s) -> bsInitStates.set((int) s));\n\t\taddBooleanArray(UMBFormat.INITIAL_STATES_FILE, bsInitStates, umbIndex.getNumStates());\n\t}\n\n\t/**\n\t * Add the initial states, in sparse form, i.e., a list of (int) state indices\n\t */\n\tpublic void addInitialStates(PrimitiveIterator.OfInt initStates) throws UMBException\n\t{\n\t\tBitSet bsInitStates = new BitSet();\n\t\tinitStates.forEachRemaining((int s) -> bsInitStates.set(s));\n\t\taddBooleanArray(UMBFormat.INITIAL_STATES_FILE, bsInitStates, umbIndex.getNumStates());\n\t}\n\n\t/**\n\t * Add the Markovian states (for Markov automata), as a BitSet\n\t */\n\tpublic void addMarkovianStates(BitSet markovianStates) throws UMBException\n\t{\n\t\taddBooleanArray(UMBFormat.MARKOVIAN_STATES_FILE, markovianStates, umbIndex.getNumStates());\n\t}\n\n\t/**\n\t * Add the Markovian states (for Markov automata), in sparse form, i.e., a list of (long) state indices\n\t */\n\tpublic void addMarkovianStates(PrimitiveIterator.OfLong markovianStates) throws UMBException\n\t{\n\t\t// TODO - can't use BitSet; need BooleanArraySparse\n\t\tBitSet bsMarkovianStates = new BitSet();\n\t\tmarkovianStates.forEachRemaining((long s) -> bsMarkovianStates.set((int) s));\n\t\taddBooleanArray(UMBFormat.MARKOVIAN_STATES_FILE, bsMarkovianStates, umbIndex.getNumStates());\n\t}\n\n\t/**\n\t * Add the Markovian states (for Markov automata), in sparse form, i.e., a list of (int) state indices\n\t */\n\tpublic void addMarkovianStates(PrimitiveIterator.OfInt markovianStates) throws UMBException\n\t{\n\t\tBitSet bsMarkovianStates = new BitSet();\n\t\tmarkovianStates.forEachRemaining((int s) -> bsMarkovianStates.set(s));\n\t\taddBooleanArray(UMBFormat.MARKOVIAN_STATES_FILE, bsMarkovianStates, umbIndex.getNumStates());\n\t}\n\n\t/**\n\t * Add the exit rates for each state of a CTMC.\n\t * The type of the values depends on {@link UMBIndex#getExitRateType()}.\n\t */\n\tpublic void addExitRates(Iterator<?> exitRates) throws UMBException\n\t{\n\t\taddContinuousNumericArray(UMBFormat.STATE_EXIT_RATES_FILE, exitRates, umbIndex.getExitRateType(), umbIndex.getNumStates());\n\t}\n\n\t/**\n\t * Add the choice branch offsets, as an iterator of longs\n\t */\n\tpublic void addChoiceBranchOffsets(PrimitiveIterator.OfLong choiceBranchOffsets)\n\t{\n\t\taddLongArray(UMBFormat.CHOICE_BRANCH_OFFSETS_FILE, choiceBranchOffsets, umbIndex.getNumChoices() + 1);\n\t}\n\n\t/**\n\t * Add the choice branch offsets, as an iterator of ints\n\t */\n\tpublic void addChoiceBranchOffsets(PrimitiveIterator.OfInt choiceBranchOffsets)\n\t{\n\t\taddLongArray(UMBFormat.CHOICE_BRANCH_OFFSETS_FILE, new UMBUtils.IntToLongIteratorAdapter(choiceBranchOffsets), umbIndex.getNumChoices() + 1);\n\t}\n\n\t/**\n\t * Add the branch targets, as an iterator of long\n\t */\n\tpublic void addBranchTargets(PrimitiveIterator.OfLong branchTargets)\n\t{\n\t\taddLongArray(UMBFormat.BRANCH_TARGETS_FILE, branchTargets, umbIndex.getNumBranches());\n\t}\n\n\t/**\n\t * Add the branch targets, as an iterator of ints\n\t */\n\tpublic void addBranchTargets(PrimitiveIterator.OfInt branchTargets)\n\t{\n\t\taddLongArray(UMBFormat.BRANCH_TARGETS_FILE, new UMBUtils.IntToLongIteratorAdapter(branchTargets), umbIndex.getNumBranches());\n\t}\n\n\t/**\n\t * Add the branch probabilities, as an iterator of values\n\t * The type (and number) of values provided depends on {@link UMBIndex#getBranchProbabilityType()}.\n\t * For interval types, this method will expect two values (lower/upper bound, successively) for each branch.\n\t * If values are rationals, this method will expect two values (numerator/denominator, successively) for each one.\n\t */\n\tpublic void addBranchProbabilities(Iterator<?> branchValues) throws UMBException\n\t{\n\t\taddContinuousNumericArray(UMBFormat.BRANCH_PROBABILITIES_FILE, branchValues, umbIndex.getBranchProbabilityType(), umbIndex.getNumBranches());\n\t}\n\n\t/**\n\t * Add actions for all choices\n\t * @param choiceActionIndices Iterator providing the indices for actions of all choices\n\t * @param choiceActionStrings Names of the actions\n\t */\n\tpublic void addChoiceActions(PrimitiveIterator.OfInt choiceActionIndices, List<String> choiceActionStrings) throws UMBException\n\t{\n\t\taddStringDataToAnnotation(umbIndex.actionsAnnotation, UMBIndex.UMBEntity.CHOICES, choiceActionIndices, choiceActionStrings);\n\t}\n\n\t/**\n\t * Add (unnamed) actions for all choices\n\t * @param choiceActionIndices Iterator providing the indices for actions of all choices\n\t */\n\tpublic void addChoiceActions(PrimitiveIterator.OfInt choiceActionIndices) throws UMBException\n\t{\n\t\t// ACTIONS_ANNOTATION is a string annotation but we can just store the indices in this case\n\t\taddIntDataToAnnotation(umbIndex.actionsAnnotation, UMBIndex.UMBEntity.CHOICES, choiceActionIndices);\n\t}\n\n\t/**\n\t * Add the same action for all choices\n\t * @param choiceActionString Name of the action\n\t */\n\tpublic void addSingleChoiceAction(String choiceActionString) throws UMBException\n\t{\n\t\taddChoiceActions(null, Collections.singletonList(choiceActionString));\n\t}\n\n\t/**\n\t * Add actions for all branches\n\t * @param branchActionIndices Iterator providing the indices for actions of all branches\n\t * @param branchActionStrings Names of the actions\n\t */\n\tpublic void addBranchActions(PrimitiveIterator.OfInt branchActionIndices, List<String> branchActionStrings) throws UMBException\n\t{\n\t\taddStringDataToAnnotation(umbIndex.actionsAnnotation, UMBIndex.UMBEntity.BRANCHES, branchActionIndices, branchActionStrings);\n\t}\n\n\t/**\n\t * Add (unnamed) actions for all branches\n\t * @param branchActionIndices Iterator providing the indices for actions of all branches\n\t */\n\tpublic void addBranchActions(PrimitiveIterator.OfInt branchActionIndices) throws UMBException\n\t{\n\t\t// ACTIONS_ANNOTATION is a string annotation but we can just store the indices in this case\n\t\taddIntDataToAnnotation(umbIndex.actionsAnnotation, UMBIndex.UMBEntity.BRANCHES, branchActionIndices);\n\t}\n\n\t/**\n\t * Add the same action for all branches\n\t * @param branchActionString Name of the action\n\t */\n\tpublic void addSingleBranchAction(String branchActionString) throws UMBException\n\t{\n\t\taddBranchActions(null, Collections.singletonList(branchActionString));\n\t}\n\n\t/**\n\t * Add the (deterministic) observations for all states, as an iterator of longs\n\t * @param stateObservations Iterator providing the observations for all states\n\t */\n\tpublic void addStateObservations(PrimitiveIterator.OfLong stateObservations) throws UMBException\n\t{\n\t\taddObservations(UMBIndex.UMBEntity.STATES, stateObservations);\n\t}\n\n\t/**\n\t * Add the (deterministic) observations for all states, as an iterator of ints\n\t * @param stateObservations Iterator providing the observations for all states\n\t */\n\tpublic void addStateObservations(PrimitiveIterator.OfInt stateObservations) throws UMBException\n\t{\n\t\taddObservations(UMBIndex.UMBEntity.STATES, stateObservations);\n\t}\n\n\t/**\n\t * Add the (deterministic) observations for all branches, as an iterator of longs\n\t * @param branchObservations Iterator providing the observations for all branches\n\t */\n\tpublic void addBranchObservations(PrimitiveIterator.OfLong branchObservations) throws UMBException\n\t{\n\t\taddObservations(UMBIndex.UMBEntity.BRANCHES, branchObservations);\n\t}\n\n\t/**\n\t * Add the (deterministic) observations for all branches, as an iterator of ints\n\t * @param branchObservations Iterator providing the observations for all branches\n\t */\n\tpublic void addBranchObservations(PrimitiveIterator.OfInt branchObservations) throws UMBException\n\t{\n\t\taddObservations(UMBIndex.UMBEntity.BRANCHES, branchObservations);\n\t}\n\n\t/**\n\t * Add the (deterministic) observations for some entity (states, branches), as an iterator of longs\n\t * @param entity The entity for which observations are being added\n\t * @param observations Iterator providing the observations\n\t */\n\tpublic void addObservations(UMBIndex.UMBEntity entity, PrimitiveIterator.OfLong observations) throws UMBException\n\t{\n\t\taddLongDataToAnnotation(umbIndex.observationsAnnotation, entity, observations);\n\t}\n\n\t/**\n\t * Add the (deterministic) observations for some entity (states, branches), as an iterator of ints\n\t * @param entity The entity for which observations are being added\n\t * @param observations Iterator providing the observations\n\t */\n\tpublic void addObservations(UMBIndex.UMBEntity entity, PrimitiveIterator.OfInt observations) throws UMBException\n\t{\n\t\taddLongDataToAnnotation(umbIndex.observationsAnnotation, entity, new UMBUtils.IntToLongIteratorAdapter(observations));\n\t}\n\n\t// Methods to add standard annotations\n\n\t/**\n\t * Add a new state AP annotation.\n\t * @param apAlias AP annotation alias\n\t * @param apStates BitSet providing indices of states satisfying the AP\n\t */\n\tpublic void addStateAP(String apAlias, BitSet apStates) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = umbIndex.addAnnotation(UMBFormat.AP_ANNOTATIONS_GROUP, apAlias, UMBType.create(UMBType.Type.BOOL));\n\t\taddBooleanDataToAnnotation(annotation, UMBIndex.UMBEntity.STATES, apStates);\n\t}\n\n\t/**\n\t * Add a new reward annotation, for now without any data attached.\n\t * If the alias (name) is non-empty, there should not already exist a reward annotation with the same alias.\n\t * @param rewardAlias Optional alias (name) for the rewards (can be omitted: \"\" or null)\n\t * @param rational Whether the reward values are rational numbers\n\t */\n\tpublic String addRewards(String rewardAlias, boolean rational) throws UMBException\n\t{\n\t\tUMBType type = UMBType.contNum(rational);\n\t\tUMBIndex.Annotation annotation = umbIndex.addAnnotation(UMBFormat.REWARD_ANNOTATIONS_GROUP, rewardAlias, type);\n\t\treturn annotation.id;\n\t}\n\n\t/**\n\t * Add state rewards to a previously created reward annotation.\n\t * @param rewardID Reward annotation ID\n\t * @param stateRewards Iterator providing values defining the reward\n\t */\n\tpublic void addStateRewardsByID(String rewardID, Iterator<?> stateRewards) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = umbIndex.getAnnotation(UMBFormat.REWARD_ANNOTATIONS_GROUP, rewardID);\n\t\taddContinuousNumericDataToAnnotation(annotation, UMBIndex.UMBEntity.STATES, stateRewards, annotation.getType());\n\t}\n\n\t/**\n\t * Add choice rewards to a previously created reward annotation.\n\t * @param rewardID Reward annotation ID\n\t * @param choiceRewards Iterator providing values defining the reward\n\t */\n\tpublic void addChoiceRewardsByID(String rewardID, Iterator<?> choiceRewards) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = umbIndex.getAnnotation(UMBFormat.REWARD_ANNOTATIONS_GROUP, rewardID);\n\t\taddContinuousNumericDataToAnnotation(annotation, UMBIndex.UMBEntity.CHOICES, choiceRewards, annotation.getType());\n\t}\n\n\t/**\n\t * Add branch rewards to a previously created reward annotation.\n\t * @param rewardID Reward annotation ID\n\t * @param branchRewards Iterator providing values defining the reward\n\t */\n\tpublic void addBranchRewardsByID(String rewardID, Iterator<?> branchRewards) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = umbIndex.getAnnotation(UMBFormat.REWARD_ANNOTATIONS_GROUP, rewardID);\n\t\taddContinuousNumericDataToAnnotation(annotation, UMBIndex.UMBEntity.BRANCHES, branchRewards, annotation.getType());\n\t}\n\n\t/**\n\t * Add a new reward annotation, applied to states.\n\t * If the alias (name) is non-empty, there should not already exist a reward annotation with the same alias.\n\t * If you want to add a reward annotation that applies to multiple entities,\n\t * e.g., to both states and branches, use first {@link #addRewards(String, boolean)}\n\t * and then {@link #addStateRewardsByID} and {@link #addBranchRewardsByID}.\n\t * @param rewardAlias Optional alias (name) for the rewards (can be omitted: \"\" or null)\n\t * @param rational Whether the reward values are rational numbers\n\t * @param stateRewards Iterator providing values defining the reward\n\t */\n\tpublic void addStateRewards(String rewardAlias, boolean rational, Iterator<?> stateRewards) throws UMBException\n\t{\n\t\taddStateRewardsByID(addRewards(rewardAlias, rational), stateRewards);\n\t}\n\n\t/**\n\t * Add a new reward annotation, applied to choices.\n\t * If the alias (name) is non-empty, there should not already exist a reward annotation with the same alias.\n\t * If you want to add a reward annotation that applies to multiple entities,\n\t * e.g., to both states and branches, use first {@link #addRewards(String, boolean)}\n\t * and then {@link #addStateRewardsByID} and {@link #addBranchRewardsByID}.\n\t * @param rewardAlias Optional alias (name) for the rewards (can be omitted: \"\" or null)\n\t * @param rational Whether the reward values are rational numbers\n\t * @param choiceRewards Iterator providing values defining the reward\n\t */\n\tpublic void addChoiceRewards(String rewardAlias, boolean rational, Iterator<?> choiceRewards) throws UMBException\n\t{\n\t\taddChoiceRewardsByID(addRewards(rewardAlias, rational), choiceRewards);\n\t}\n\n\t/**\n\t * Add a new reward annotation, applied to branches.\n\t * If the alias (name) is non-empty, there should not already exist a reward annotation with the same alias.\n\t * If you want to add a reward annotation that applies to multiple entities,\n\t * e.g., to both states and branches, use first {@link #addRewards(String, boolean)}\n\t * and then {@link #addStateRewardsByID} and {@link #addBranchRewardsByID}.\n\t * @param rewardAlias Optional alias (name) for the rewards (can be omitted: \"\" or null)\n\t * @param rational Whether the reward values are rational numbers\n\t * @param branchRewards Iterator providing values defining the reward\n\t */\n\tpublic void addBranchRewards(String rewardAlias, boolean rational, Iterator<?> branchRewards) throws UMBException\n\t{\n\t\taddBranchRewardsByID(addRewards(rewardAlias, rational), branchRewards);\n\t}\n\n\t// Methods to add annotations\n\n\t/**\n\t * Add a new annotation, for now without any data attached.\n\t * If an alias is provided, there should not already exist\n\t * an annotation in the same group with the same alias.\n\t * @param group The ID of the group\n\t * @param alias Optional alias (name) for the annotation (\"\" or null if not needed)\n\t * @param type The type of the values to be stored in the annotation\n\t */\n\tpublic UMBIndex.Annotation addAnnotation(String group, String alias, UMBType type) throws UMBException\n\t{\n\t\treturn umbIndex.addAnnotation(group, alias, type);\n\t}\n\n\t/**\n\t * Add a new Boolean-valued annotation.\n\t * If an alias is provided, there should not already exist\n\t * an annotation in the same group with the same alias.\n\t * @param group The ID of the group\n\t * @param alias Optional alias (name) for the annotation (\"\" or null if not needed)\n\t * @param appliesTo The entity to which the annotation applies\n\t * @param bitset BitSet providing data\n\t */\n\tpublic void addBooleanAnnotation(String group, String alias, UMBIndex.UMBEntity appliesTo, BitSet bitset) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = addAnnotation(group, alias, UMBType.create(UMBType.Type.BOOL));\n\t\taddBooleanDataToAnnotation(annotation, appliesTo, bitset);\n\t}\n\n\t/**\n\t * Add a new double-valued annotation.\n\t * If an alias is provided, there should not already exist\n\t * an annotation in the same group with the same alias.\n\t * @param group The ID of the group\n\t * @param alias Optional alias (name) for the annotation (\"\" or null if not needed)\n\t * @param appliesTo The entity to which the annotation applies\n\t * @param doubleValues Iterator providing data\n\t */\n\tpublic void addDoubleAnnotation(String group, String alias, UMBIndex.UMBEntity appliesTo, PrimitiveIterator.OfDouble doubleValues) throws UMBException\n\t{\n\t\tUMBIndex.Annotation annotation = addAnnotation(group, alias, UMBType.create(UMBType.Type.DOUBLE));\n\t\taddDoubleDataToAnnotation(annotation, appliesTo, doubleValues);\n\t}\n\n\t/**\n\t * Add new boolean-valued data to an existing annotation.\n\t * @param annotation The annotation\n\t * @param appliesTo The entity to which the annotation applies\n\t * @param bitset BitSet providing data\n\t */\n\tpublic void addBooleanDataToAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, BitSet bitset) throws UMBException\n\t{\n\t\tif (annotation.appliesTo(appliesTo)) {\n\t\t\tthrow new UMBException(\"Duplicate data for \" + appliesTo + \"s in annotation \\\"\" + annotation.id + \"\\\" in group \\\"\" + annotation.group + \"\\\"\");\n\t\t}\n\t\tannotation.addAppliesTo(appliesTo);\n\t\tlong annotationSize = umbIndex.getEntityCount(appliesTo);\n\t\taddBooleanArray(annotation.getFilename(appliesTo), bitset, annotationSize);\n\t}\n\n\t/**\n\t * Add new int-valued data to an existing annotation.\n\t * @param annotation The annotation\n\t * @param appliesTo The entity to which the annotation applies\n\t * @param intValues Iterator providing data\n\t */\n\tpublic void addIntDataToAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, PrimitiveIterator.OfInt intValues) throws UMBException\n\t{\n\t\tif (annotation.appliesTo(appliesTo)) {\n\t\t\tthrow new UMBException(\"Duplicate data for \" + appliesTo + \"s in annotation \\\"\" + annotation.id + \"\\\" in group \\\"\" + annotation.group + \"\\\"\");\n\t\t}\n\t\tannotation.addAppliesTo(appliesTo);\n\t\tlong annotationSize = umbIndex.getEntityCount(appliesTo);\n\t\taddIntArray(annotation.getFilename(appliesTo), intValues, annotationSize);\n\t}\n\n\t/**\n\t * Add new long-valued data to an existing annotation.\n\t * @param annotation The annotation\n\t * @param appliesTo The entity to which the annotation applies\n\t * @param longValues Iterator providing data\n\t */\n\tpublic void addLongDataToAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, PrimitiveIterator.OfLong longValues) throws UMBException\n\t{\n\t\tif (annotation.appliesTo(appliesTo)) {\n\t\t\tthrow new UMBException(\"Duplicate data for \" + appliesTo + \"s in annotation \\\"\" + annotation.id + \"\\\" in group \\\"\" + annotation.group + \"\\\"\");\n\t\t}\n\t\tannotation.addAppliesTo(appliesTo);\n\t\tlong annotationSize = umbIndex.getEntityCount(appliesTo);\n\t\taddLongArray(annotation.getFilename(appliesTo), longValues, annotationSize);\n\t}\n\n\t/**\n\t * Add new double-valued data to an existing annotation.\n\t * @param annotation The annotation\n\t * @param appliesTo The entity to which the annotation applies\n\t * @param doubleValues Iterator providing data\n\t */\n\tpublic void addDoubleDataToAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, PrimitiveIterator.OfDouble doubleValues) throws UMBException\n\t{\n\t\tif (annotation.appliesTo(appliesTo)) {\n\t\t\tthrow new UMBException(\"Duplicate data for \" + appliesTo + \"s in annotation \\\"\" + annotation.id + \"\\\" in group \\\"\" + annotation.group + \"\\\"\");\n\t\t}\n\t\tannotation.addAppliesTo(appliesTo);\n\t\tlong annotationSize = umbIndex.getEntityCount(appliesTo);\n\t\taddDoubleArray(annotation.getFilename(appliesTo), doubleValues, annotationSize);\n\t}\n\n\tpublic void addContinuousNumericDataToAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, Iterator<?> values, UMBType valueType) throws UMBException\n\t{\n\t\tif (annotation.appliesTo(appliesTo)) {\n\t\t\tthrow new UMBException(\"Duplicate data for \" + appliesTo + \"s in annotation \\\"\" + annotation.id + \"\\\" in group \\\"\" + annotation.group + \"\\\"\");\n\t\t}\n\t\tannotation.addAppliesTo(appliesTo);\n\t\tlong annotationSize = umbIndex.getEntityCount(appliesTo);\n\t\taddContinuousNumericArray(annotation.getFilename(appliesTo), values, valueType, annotationSize);\n\t}\n\n\tpublic void addStringDataToAnnotation(UMBIndex.Annotation annotation, UMBIndex.UMBEntity appliesTo, PrimitiveIterator.OfInt indices, List<String> strings) throws UMBException\n\t{\n\t\tif (annotation.appliesTo(appliesTo)) {\n\t\t\tthrow new UMBException(\"Duplicate data for \" + appliesTo + \"s in annotation \\\"\" + annotation.id + \"\\\" in group \\\"\" + annotation.group + \"\\\"\");\n\t\t}\n\t\tannotation.addAppliesTo(appliesTo);\n\t\tString folderName = annotation.getFolderName(appliesTo);\n\t\taddStringsFiles(strings, UMBFormat.stringOffsetsFile(folderName), UMBFormat.stringsFile(folderName));\n\t\tif (indices != null) {\n\t\t\tlong annotationSize = umbIndex.getEntityCount(appliesTo);\n\t\t\taddIntArray(annotation.getFilename(appliesTo), indices, annotationSize);\n\t\t}\n\t}\n\n\t/**\n\t * Add the files encoding a list of strings.\n\t * @param strings The strings\n\t * @param stringOffsetsFilename The name of the file to contain the string offsets\n\t * @param stringsFilename The name of file to contain the string data\n\t */\n\tprivate void addStringsFiles(List<String> strings, String stringOffsetsFilename, String stringsFilename) throws UMBException\n\t{\n\t\tint numStrings = strings.size();\n\t\tlong[] stringOffsets = new long[numStrings + 1];\n\t\tstringOffsets[0] = 0;\n\t\tfor (int i = 0; i < numStrings; i++) {\n\t\t\tstringOffsets[i + 1] = stringOffsets[i] + strings.get(i).getBytes().length;\n\t\t}\n\t\tPrimitiveIterator.OfLong it = Arrays.stream(stringOffsets).iterator();\n\t\taddLongArray(stringOffsetsFilename, it, strings.size() + 1);\n\t\taddStringList(stringsFilename, strings);\n\t}\n\n\t// Methods to add valuations\n\n\t/**\n\t * Add a new description for the valuations to be attached to states,\n\t * extracted from a {@link UMBBitPacking} object.\n\t * @param unique Whether the valuations are unique across states\n\t * @param bitPacking Definition of valuation contents\n\t */\n\tpublic void addStateValuationDescription(boolean unique, UMBBitPacking bitPacking) throws UMBException\n\t{\n\t\taddValuationDescription(UMBIndex.UMBEntity.STATES, unique, bitPacking);\n\t}\n\n\t/**\n\t * Add state valuations, i.e., variable values for each state, encoded as a bitstring\n\t * @param stateValuations Iterator providing bitstrings defining the state valuations\n\t * @param numBytes Number of bytes in each bitstring\n\t */\n\tpublic void addStateValuations(Iterator<UMBBitString> stateValuations, int numBytes) throws UMBException\n\t{\n\t\taddValuations(UMBIndex.UMBEntity.STATES, stateValuations, numBytes);\n\t}\n\n\t/**\n\t * Add state valuations, i.e., variable values for each state, encoded as a bitstring\n\t * @param stateValuations Iterator providing bitstrings defining the state valuations\n\t * @param bitPacking Information about how the bitstrings are packed\n\t */\n\tpublic void addStateValuations(Iterator<UMBBitString> stateValuations, UMBBitPacking bitPacking) throws UMBException\n\t{\n\t\taddValuations(UMBIndex.UMBEntity.STATES, stateValuations, bitPacking);\n\t}\n\n\t/**\n\t * Add a new description for the valuations to be attached to observations,\n\t * extracted from a {@link UMBBitPacking} object.\n\t * @param unique Whether the valuations are unique across states\n\t * @param bitPacking Definition of valuation contents\n\t */\n\tpublic void addObservationValuationDescription(boolean unique, UMBBitPacking bitPacking) throws UMBException\n\t{\n\t\taddValuationDescription(UMBIndex.UMBEntity.OBSERVATIONS, unique, bitPacking);\n\t}\n\n\t/**\n\t * Add observation valuations, i.e., observable values for each observation, encoded as a bitstring\n\t * @param observationValuations Iterator providing bitstrings defining the observation valuations\n\t * @param numBytes Number of bytes in each bitstring\n\t */\n\tpublic void addObservationValuations(Iterator<UMBBitString> observationValuations, int numBytes) throws UMBException\n\t{\n\t\taddValuations(UMBIndex.UMBEntity.OBSERVATIONS, observationValuations, numBytes);\n\t}\n\n\t/**\n\t * Add observation valuations, i.e., observable values for each observation, encoded as a bitstring\n\t * @param observationValuations Iterator providing bitstrings defining the observation valuations\n\t * @param bitPacking Information about how the bitstrings are packed\n\t */\n\tpublic void addObservationValuations(Iterator<UMBBitString> observationValuations, UMBBitPacking bitPacking) throws UMBException\n\t{\n\t\taddValuations(UMBIndex.UMBEntity.OBSERVATIONS, observationValuations, bitPacking);\n\t}\n\n\t/**\n\t * Add a new description for the valuations to be attached to some model entity,\n\t * extracted from a {@link UMBBitPacking} object.\n\t * @param entity The entity to which the valuations apply\n\t * @param unique Whether the valuations are unique across the entity\n\t * @param bitPacking Definition of valuation contents\n\t */\n\tpublic void addValuationDescription(UMBIndex.UMBEntity entity, boolean unique, UMBBitPacking bitPacking) throws UMBException\n\t{\n\t\tumbIndex.addSingleValuationDescription(entity, unique, bitPacking);\n\t}\n\n\t/**\n\t * Add valuations for an entity, i.e., variable values for each one, encoded as a bitstring\n\t * @param valuations Iterator providing bitstrings defining the valuations\n\t * @param entity The entity to which the valuations apply\n\t * @param numBytes Number of bytes in each bitstring\n\t */\n\tpublic void addValuations(UMBIndex.UMBEntity entity, Iterator<UMBBitString> valuations, int numBytes) throws UMBException\n\t{\n\t\taddBitStringArray(UMBFormat.valuationsFile(entity), valuations, numBytes, umbIndex.getEntityCount(entity));\n\t}\n\n\t/**\n\t * Add valuations for an entity, i.e., variable values for each one, encoded as a bitstring\n\t * @param entity The entity to which the valuations apply\n\t * @param valuations Iterator providing bitstrings defining the valuations\n\t * @param bitPacking Information about how the bitstrings are packed\n\t */\n\tpublic void addValuations(UMBIndex.UMBEntity entity, Iterator<UMBBitString> valuations, UMBBitPacking bitPacking) throws UMBException\n\t{\n\t\taddBitStringArray(UMBFormat.valuationsFile(entity), valuations, bitPacking, umbIndex.getEntityCount(entity));\n\t}\n\n\t// Methods to add binary files\n\n\tpublic void addBooleanArray(String name, BitSet booleanValues, long size)\n\t{\n\t\tumbDataFiles.add(new BooleanArray(booleanValues, size, name));\n\t}\n\n\tpublic void addCharArray(String name, PrimitiveIterator.OfLong longValues, long size)\n\t{\n\t\tumbDataFiles.add(new LongArray(longValues, size, name));\n\t}\n\n\tpublic void addIntArray(String name, PrimitiveIterator.OfInt intValues, long size)\n\t{\n\t\tumbDataFiles.add(new IntArray(intValues, size, name));\n\t}\n\n\tpublic void addLongArray(String name, PrimitiveIterator.OfLong longValues, long size)\n\t{\n\t\tumbDataFiles.add(new LongArray(longValues, size, name));\n\t}\n\n\tpublic void addDoubleArray(String name, PrimitiveIterator.OfDouble doubleValues, long size)\n\t{\n\t\tumbDataFiles.add(new DoubleArray(doubleValues, size, name));\n\t}\n\n\tpublic void addBigIntegerArray(String name, Iterator<BigInteger> bigIntegerValues, int numLongs, long size)\n\t{\n\t\tumbDataFiles.add(new BigIntegerArray(bigIntegerValues, numLongs, size, name));\n\t}\n\n\tprivate void addContinuousNumericArray(String name, Iterator<?> values, UMBType type, long size) throws UMBException\n\t{\n\t\tlong sizeNew = type.type.isInterval() ? size * 2 : size;\n\t\tif (type.type.isDouble()) {\n\t\t\taddDoubleArray(name, DoubleIterators.asDoubleIterator(values), sizeNew);\n\t\t} else if (type.type.isRational()) {\n\t\t\taddLongArray(name, LongIterators.asLongIterator(values), sizeNew * 2);\n\t\t} else {\n\t\t\tthrow new UMBException(\"Unsupported continuous numeric type \" + type);\n\t\t}\n\t}\n\n\tpublic void addBitStringArray(String name, Iterator<UMBBitString> bitStrings, int numBytes, long size)\n\t{\n\t\tumbDataFiles.add(new BitStringArray(bitStrings, numBytes, size, name));\n\t}\n\n\tpublic void addBitStringArray(String name, Iterator<UMBBitString> bitStrings, UMBBitPacking bitPacking, long size)\n\t{\n\t\tumbDataFiles.add(new BitStringArray(bitStrings, bitPacking, size, name));\n\t}\n\n\tpublic void addStringList(String name, List<String> strings)\n\t{\n\t\tumbDataFiles.add(new StringListFile(strings, name));\n\t}\n\n\t/**\n\t * Export content to a UMB file.\n\t * @param fileOut The file to export to.\n\t */\n\tpublic void export(File fileOut) throws UMBException\n\t{\n\t\texport(fileOut, true);\n\t}\n\n\t/**\n\t * Export content to a UMB file.\n\t * @param fileOut The file to export to.\n\t * @param zipped Whether to zip the file\n\t */\n\tpublic void export(File fileOut, boolean zipped) throws UMBException\n\t{\n\t\texport(fileOut, zipped, null);\n\t}\n\n\t/**\n\t * Export content to a UMB file.\n\t * @param fileOut The file to export to.\n\t * @param zipped Whether to zip the file\n\t * @param compressionFormat How to zip the file (null means use default)\n\t */\n\tpublic void export(File fileOut, boolean zipped, UMBFormat.CompressionFormat compressionFormat) throws UMBException\n\t{\n\t\tUMBOut umbOut = new UMBOut(fileOut, zipped, compressionFormat);\n\t\texportIndex(umbOut);\n\t\tfor (UMBDataFile umbDataFile : umbDataFiles) {\n\t\t\texportUMBFile(umbDataFile, umbOut);\n\t\t}\n\t\tumbOut.close();\n\t}\n\n\t/**\n\t * Export content to a textual representation of a UMB file.\n\t * @param sb Where to write the text to.\n\t */\n\tpublic void exportAsText(StringBuffer sb) throws UMBException\n\t{\n\t\texportIndexToText(sb);\n\t\tfor (UMBDataFile umbDataFile : umbDataFiles) {\n\t\t\texportUMBFileToText(umbDataFile, sb);\n\t\t}\n\t}\n\n\t/**\n\t * Export the index to a UMB file.\n\t */\n\tprivate void exportIndex(UMBOut umbOut) throws UMBException\n\t{\n\t\texportTextToTar(umbIndex.toJSON(), UMBFormat.INDEX_FILE, umbOut);\n\t}\n\n\t/**\n\t * Export the index to a StringBuffer\n\t */\n\tprivate void exportIndexToText(StringBuffer sb)\n\t{\n\t\texportTextToText(umbIndex.toJSON(), new File(UMBFormat.INDEX_FILE), sb);\n\t}\n\n\tprivate void exportTextToTar(String text, String filename, UMBOut umbOut) throws UMBException\n\t{\n\t\tbyte[] bytes = text.getBytes();\n\t\tumbOut.createArchiveEntry(filename, bytes.length);\n\t\tumbOut.write(bytes, 0, bytes.length);\n\t\tumbOut.closeArchiveEntry();\n\t}\n\n\tprivate void exportUMBFile(UMBDataFile umbDataFile, UMBOut umbOut) throws UMBException\n\t{\n\t\ttry {\n\t\t\tumbOut.createArchiveEntry(umbDataFile.name, umbDataFile.totalBytes());\n\t\t\tIterator<ByteBuffer> byteIter = umbDataFile.byteIterator();\n\t\t\tByteBuffer buffer;\n\t\t\twhile (byteIter.hasNext()) {\n\t\t\t\tbuffer = byteIter.next();\n\t\t\t\tumbOut.write(buffer.array(), 0, buffer.position());\n\t\t\t}\n\t\t\tumbOut.closeArchiveEntry();\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in iterators so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error exporting UMB file: \" + e.getMessage());\n\t\t}\n\t}\n\n\tprivate void exportTextToText(String text, File file, StringBuffer sb)\n\t{\n\t\tsb.append(\"/\" + file.getName() + \":\\n\");\n\t\tsb.append(text);\n\t\tsb.append(\"\\n\");\n\t}\n\n\tprivate void exportUMBFileToText(UMBDataFile umbDataFile, StringBuffer sb) throws UMBException\n\t{\n\t\ttry {\n\t\t\tsb.append(\"/\" + umbDataFile.name + \":\\n\");\n\t\t\tsb.append(umbDataFile.toText());\n\t\t\tsb.append(\"\\n\");\n\t\t} catch (RuntimeException e) {\n\t\t\t// Errors may occur in iterators so catch runtime exceptions here\n\t\t\tthrow new UMBException(\"Error exporting UMB file: \" + e.getMessage());\n\t\t}\n\t}\n\n\tprivate static String toArrayString(Iterator<?> iter)\n\t{\n\t\tStringJoiner sj = new StringJoiner(\",\", \"[\", \"]\");\n\t\titer.forEachRemaining(o -> sj.add(o.toString()));\n\t\treturn sj.toString();\n\t}\n\n\t/**\n\t * Class to manage writing to the zipped archive for a UMB file\n\t */\n\tprivate static class UMBOut\n\t{\n\t\t/** Output stream for zip file */\n\t\tprivate final OutputStream fsOut;\n\t\t/** Output stream for zipping */\n\t\tprivate final CompressorOutputStream zipOut;\n\t\t/** Output stream for tar file */\n\t\tprivate final ArchiveOutputStream tarOut;\n\n\t\t/**\n\t\t * Open a new UMB file for writing\n\t\t * @param fileOut The file to write to\n\t\t */\n\t\tpublic UMBOut(File fileOut) throws UMBException\n\t\t{\n\t\t\tthis(fileOut, true);\n\t\t}\n\n\t\t/**\n\t\t * Open a new UMB file for writing\n\t\t * @param fileOut The file to write to\n\t\t * @param zipped Whether to zip the file\n\t\t */\n\t\tpublic UMBOut(File fileOut, boolean zipped) throws UMBException\n\t\t{\n\t\t\tthis(fileOut, zipped, null);\n\t\t}\n\n\t\t/**\n\t\t * Open a new UMB file for writing\n\t\t * @param fileOut The file to write to\n\t\t * @param zipped Whether to zip the file\n\t\t * @param compressionFormat How to zip the file (null means use the default)\n\t\t */\n\t\tpublic UMBOut(File fileOut, boolean zipped, UMBFormat.CompressionFormat compressionFormat) throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\t// Open file/zip/tar\n\t\t\t\tfsOut = new BufferedOutputStream(Files.newOutputStream(fileOut.toPath()));\n\t\t\t\tif (zipped) {\n\t\t\t\t\tif (compressionFormat == null) {\n\t\t\t\t\t\tcompressionFormat = UMBFormat.DEFAULT_COMPRESSION_FORMAT;\n\t\t\t\t\t}\n\t\t\t\t\tzipOut = new CompressorStreamFactory().createCompressorOutputStream(compressionFormat.extension(), fsOut);\n\t\t\t\t\ttarOut = new TarArchiveOutputStream(zipOut);\n\t\t\t\t} else {\n\t\t\t\t\tzipOut = null;\n\t\t\t\t\ttarOut = new TarArchiveOutputStream(fsOut);\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"Could not create UMB file: \" + e.getMessage());\n\t\t\t} catch (CompressorException e) {\n\t\t\t\tthrow new UMBException(\"Could not create zip for UMB file: \" + e.getMessage());\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Create an entry (a file) within the archive for subsequent writing.\n\t\t * @param name Name of the file\n\t\t * @param size Size of the file (number of bytes)\n\t\t */\n\t\tpublic void createArchiveEntry(String name, long size) throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\tFile file = new File(name);\n\t\t\t\tTarArchiveEntry entry = new TarArchiveEntry(file);\n\t\t\t\tentry.setSize(size);\n\t\t\t\ttarOut.putArchiveEntry(entry);\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error writing \\\"\" + name + \"\\\" to UMB file: \" + e.getMessage());\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Close the current entry (file) of the archive.\n\t\t */\n\t\tpublic void closeArchiveEntry() throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\ttarOut.closeArchiveEntry();\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error writing to UMB file: \" + e.getMessage());\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Write some data (bytes) to the current entry.\n\t\t * @param bytes The data, as an array of bytes\n\t\t * @param off The offset into the array to start from\n\t\t * @param len The number of bytes to write\n\t\t */\n\t\tpublic void write(byte[] bytes, int off, int len) throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\ttarOut.write(bytes, off, len);\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error writing to UMB file\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Close the UMB file.\n\t\t */\n\t\tpublic void close() throws UMBException\n\t\t{\n\t\t\ttry {\n\t\t\t\tif (tarOut != null) {\n\t\t\t\t\ttarOut.finish();\n\t\t\t\t}\n\t\t\t\tif (zipOut != null) {\n\t\t\t\t\tzipOut.close();\n\t\t\t\t}\n\t\t\t\tif (fsOut != null) {\n\t\t\t\t\tfsOut.close();\n\t\t\t\t}\n\t\t\t} catch (IOException e) {\n\t\t\t\tthrow new UMBException(\"I/O error closing UMB file\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Classes representing the various data files stored in a UMB file.\n\t */\n\tabstract static class UMBDataFile\n\t{\n\t\tprotected String name;\n\t\tprotected ByteBuffer buffer;\n\n\t\tpublic abstract long totalBytes();\n\t\tpublic abstract Iterator<ByteBuffer> byteIterator();\n\t\tpublic abstract String toText() throws UMBException;\n\t}\n\n\t/**\n\t * A UMB data file to be stored containing an array of values.\n\t */\n\tabstract static class Array extends UMBDataFile\n\t{\n\t\tprotected long size;\n\t\tprotected int bufferSize;\n\n\t\tpublic abstract int numBytes();\n\t\tpublic abstract boolean hasNextBytes();\n\t\tpublic abstract void encodeNextBytes();\n\n\t\tpublic long totalBytes()\n\t\t{\n\t\t\treturn size * numBytes();\n\t\t}\n\n\t\tpublic abstract Iterator<? extends Object> iterator();\n\n\t\t@Override\n\t\tpublic Iterator<ByteBuffer> byteIterator()\n\t\t{\n\t\t\treturn new Iterator<>()\n\t\t\t{\n\t\t\t\t{\n\t\t\t\t\tbuffer = ByteBuffer.allocate(BUFFER_SIZE).order(ByteOrder.LITTLE_ENDIAN);\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic boolean hasNext()\n\t\t\t\t{\n\t\t\t\t\treturn hasNextBytes();\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic ByteBuffer next()\n\t\t\t\t{\n\t\t\t\t\tbuffer.clear();\n\t\t\t\t\tencodeNextBytes();\n\t\t\t\t\treturn buffer;\n\t\t\t\t}\n\n\t\t\t};\n\t\t}\n\n\t\tpublic String nextAsText() throws UMBException\n\t\t{\n\t\t\treturn iterator().next().toString();\n\t\t}\n\n\t\tpublic String toText() throws UMBException\n\t\t{\n\t\t\tStringJoiner sj = new StringJoiner(\",\", \"[\", \"]\");\n\t\t\twhile (hasNextBytes()) {\n\t\t\t\tsj.add(nextAsText());\n\t\t\t}\n\t\t\treturn sj.toString();\n\t\t}\n\t}\n\n\t/**\n\t * A UMB data file to be stored containing an array of booleans.\n\t */\n\tstatic class BooleanArray extends Array\n\t{\n\t\tprotected BitSet booleanValues;\n\t\tprotected long[] booleanLongs;\n\t\tprotected int posn;\n\n\t\tpublic BooleanArray(BitSet booleanValues, long size, String name)\n\t\t{\n\t\t\tthis.booleanValues = booleanValues;\n\t\t\tbooleanLongs = booleanValues.toLongArray();\n\t\t\tthis.size = size;\n\t\t\tthis.name = name;\n\t\t\tposn = 0;\n\t\t}\n\n\t\t@Override\n\t\tpublic long totalBytes()\n\t\t{\n\t\t\treturn 8 * (((size - 1)/ 64) + 1);\n\t\t}\n\n\t\t@Override\n\t\tpublic Iterator<Boolean> iterator()\n\t\t{\n\t\t\treturn new Iterator<>()\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic boolean hasNext()\n\t\t\t\t{\n\t\t\t\t\treturn posn < size;\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic Boolean next()\n\t\t\t\t{\n\t\t\t\t\treturn booleanValues.get(posn++);\n\t\t\t\t}\n\t\t\t};\n\t\t}\n\n\t\t@Override\n\t\tpublic int numBytes()\n\t\t{\n\t\t\treturn Long.BYTES; // 8\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNextBytes()\n\t\t{\n\t\t\treturn posn < size;\n\t\t}\n\n\t\t@Override\n\t\tpublic void encodeNextBytes()\n\t\t{\n\t\t\twhile (posn < size && buffer.remaining() >= numBytes()) {\n\t\t\t\tint posn2 = posn / 64;\n\t\t\t\tbuffer.putLong(booleanLongs.length > posn2 ? booleanLongs[posn2] : 0);\n\t\t\t\tposn += 64;\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic String toText()\n\t\t{\n\t\t\tStringJoiner sj = new StringJoiner(\"\", \"[\", \"]\");\n\t\t\titerator().forEachRemaining(b -> sj.add(b ? \"1\" : \"0\"));\n\t\t\treturn sj.toString();\n\t\t}\n\t}\n\n\t/**\n\t * A UMB data file to be stored containing an array of ints.\n\t */\n\tstatic class IntArray extends Array\n\t{\n\t\tprotected PrimitiveIterator.OfInt intValues;\n\n\t\tpublic IntArray(PrimitiveIterator.OfInt intValues, long size, String name)\n\t\t{\n\t\t\tthis.intValues = intValues;\n\t\t\tthis.size = size;\n\t\t\tthis.name = name;\n\t\t}\n\n\t\t@Override\n\t\tpublic PrimitiveIterator.OfInt iterator()\n\t\t{\n\t\t\treturn intValues;\n\t\t}\n\n\t\t@Override\n\t\tpublic int numBytes()\n\t\t{\n\t\t\treturn Integer.BYTES; // 4\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNextBytes()\n\t\t{\n\t\t\treturn intValues.hasNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic void encodeNextBytes()\n\t\t{\n\t\t\twhile (intValues.hasNext() && buffer.remaining() >= numBytes()) {\n\t\t\t\tbuffer.putInt(intValues.nextInt());\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * A UMB data file to be stored containing an array of longs.\n\t */\n\tstatic class LongArray extends Array\n\t{\n\t\tprotected PrimitiveIterator.OfLong longValues;\n\n\t\tpublic LongArray(PrimitiveIterator.OfLong longValues, long size, String name)\n\t\t{\n\t\t\tthis.longValues = longValues;\n\t\t\tthis.size = size;\n\t\t\tthis.name = name;\n\t\t}\n\n\t\t@Override\n\t\tpublic PrimitiveIterator.OfLong iterator()\n\t\t{\n\t\t\treturn longValues;\n\t\t}\n\n\t\t@Override\n\t\tpublic int numBytes()\n\t\t{\n\t\t\treturn Long.BYTES; // 8\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNextBytes()\n\t\t{\n\t\t\treturn longValues.hasNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic void encodeNextBytes()\n\t\t{\n\t\t\twhile (longValues.hasNext() && buffer.remaining() >= numBytes()) {\n\t\t\t\tbuffer.putLong(longValues.nextLong());\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * A UMB data file to be stored containing an array of BigIntegers.\n\t */\n\tstatic class BigIntegerArray extends Array\n\t{\n\t\tprotected Iterator<BigInteger> bigIntegerValues;\n\t\tprotected int intSize;\n\n\t\tpublic BigIntegerArray(Iterator<BigInteger> bigIntegerValues, int numLongs, long size, String name)\n\t\t{\n\t\t\tthis.bigIntegerValues = bigIntegerValues;\n\t\t\tthis.intSize = numLongs;\n\t\t\tthis.size = size;\n\t\t\tthis.name = name;\n\t\t}\n\n\t\t@Override\n\t\tpublic Iterator<BigInteger> iterator()\n\t\t{\n\t\t\treturn bigIntegerValues;\n\t\t}\n\n\t\t@Override\n\t\tpublic int numBytes()\n\t\t{\n\t\t\treturn intSize * Long.BYTES;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNextBytes()\n\t\t{\n\t\t\treturn bigIntegerValues.hasNext();\n\t\t}\n\n\t\t@Override\n\t\tpublic void encodeNextBytes()\n\t\t{\n\t\t\twhile (bigIntegerValues.hasNext() && buffer.remaining() >= numBytes()) {\n\t\t\t\tBigInteger b = bigIntegerValues.next();\n\t\t\t\tfor (int i = 0; i < intSize; i++) {\n\t\t\t\t\tbuffer.putLong(b.longValue());\n\t\t\t\t\tb = b.shiftRight(64);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * A UMB data file to be stored containing an array of doubles.\n\t */\n\tclass DoubleArray extends Array\n\t{\n\t\tprotected PrimitiveIterator.OfDouble doubleValues;\n\n\t\tpublic DoubleArray(PrimitiveIterator.OfDouble doubleValues, long size, String name)\n\t\t{\n\t\t\tthis.doubleValues = doubleValues;\n\t\t\tthis.size = size;\n\t\t\tthis.name = name;\n\t\t}\n\n\t\t@Override\n\t\tpublic PrimitiveIterator.OfDouble iterator()\n\t\t{\n\t\t\treturn doubleValues;\n\t\t}\n\n\t\t@Override\n\t\tpublic int numBytes()\n\t\t{\n\t\t\treturn Double.BYTES; // 8\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNextBytes()\n\t\t{\n\t\t\treturn doubleValues.hasNext();\n\t\t}\n\n\t\tpublic String nextAsText()\n\t\t{\n\t\t\treturn formatDouble(doubleValues.nextDouble());\n\t\t}\n\n\t\t@Override\n\t\tpublic void encodeNextBytes()\n\t\t{\n\t\t\twhile (doubleValues.hasNext() && buffer.remaining() >= numBytes()) {\n\t\t\t\tbuffer.putDouble(doubleValues.nextDouble());\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * A UMB data file to be stored containing an array of (fixed size) bit strings.\n\t */\n\tclass BitStringArray extends Array\n\t{\n\t\tprotected Iterator<UMBBitString> bitStrings;\n\t\tprotected UMBBitPacking bitPacking; // optional\n\t\tprotected int numBytes;\n\n\t\tpublic BitStringArray(Iterator<UMBBitString> bitStrings, int numBytes, long size, String name)\n\t\t{\n\t\t\tthis.bitStrings = bitStrings;\n\t\t\tthis.bitPacking = null;\n\t\t\tthis.numBytes = numBytes;\n\t\t\tthis.size = size;\n\t\t\tthis.name = name;\n\t\t}\n\n\t\tpublic BitStringArray(Iterator<UMBBitString> bitStrings, UMBBitPacking bitPacking, long size, String name)\n\t\t{\n\t\t\tthis.bitStrings = bitStrings;\n\t\t\tthis.bitPacking = bitPacking;\n\t\t\tthis.numBytes = bitPacking.getTotalNumBytes();\n\t\t\tthis.size = size;\n\t\t\tthis.name = name;\n\t\t}\n\n\t\t@Override\n\t\tpublic Iterator<UMBBitString> iterator()\n\t\t{\n\t\t\treturn bitStrings;\n\t\t}\n\n\t\t@Override\n\t\tpublic int numBytes()\n\t\t{\n\t\t\treturn numBytes;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNextBytes()\n\t\t{\n\t\t\treturn bitStrings.hasNext();\n\t\t}\n\n\t\tpublic String nextAsText() throws UMBException\n\t\t{\n\t\t\tUMBBitString bitString = bitStrings.next();\n\t\t\t//return bitPacking == null ? bitString.toString() : bitPacking.formatBitString(bitString);\n\t\t\treturn bitPacking == null ? bitString.toString() : bitPacking.decodeBitString(bitString);\n\t\t}\n\n\t\t@Override\n\t\tpublic void encodeNextBytes()\n\t\t{\n\t\t\twhile (bitStrings.hasNext() && buffer.remaining() >= numBytes()) {\n\t\t\t\tbuffer.put(bitStrings.next().bytes);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * A UMB data file containing a list of strings\n\t */\n\tstatic class StringListFile extends UMBDataFile\n\t{\n\t\tprotected List<String> strings;\n\t\tprotected int totalBytes;\n\t\tprotected byte[] stringBytes;\n\n\t\tpublic StringListFile(List<String> strings, String name)\n\t\t{\n\t\t\tthis.name = name;\n\t\t\tthis.strings = strings;\n\t\t\tint numStrings = strings.size();\n\t\t\tbyte[][] stringsAsBytes = new byte[numStrings][];\n\t\t\ttotalBytes = 0;\n\t\t\tfor (int i = 0; i < numStrings; i++) {\n\t\t\t\tstringsAsBytes[i] = strings.get(i).getBytes(StandardCharsets.UTF_8);\n\t\t\t\ttotalBytes += stringsAsBytes[i].length;\n\t\t\t}\n\t\t\tstringBytes = new byte[totalBytes];\n\t\t\tint count = 0;\n\t\t\tfor (int i = 0; i < numStrings; i++) {\n\t\t\t\tSystem.arraycopy(stringsAsBytes[i], 0, stringBytes, count, stringsAsBytes[i].length);\n\t\t\t\tcount += stringsAsBytes[i].length;\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic long totalBytes()\n\t\t{\n\t\t\treturn totalBytes;\n\t\t}\n\n\t\t@Override\n\t\tpublic Iterator<ByteBuffer> byteIterator()\n\t\t{\n\t\t\treturn new Iterator<>()\n\t\t\t{\n\t\t\t\tboolean hasNext = true;\n\t\t\t\t{\n\t\t\t\t\tbuffer = ByteBuffer.wrap(stringBytes);\n\t\t\t\t\tbuffer.position(totalBytes);\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic boolean hasNext()\n\t\t\t\t{\n\t\t\t\t\treturn hasNext;\n\t\t\t\t}\n\n\t\t\t\t@Override\n\t\t\t\tpublic ByteBuffer next()\n\t\t\t\t{\n\t\t\t\t\thasNext = false;\n\t\t\t\t\treturn buffer;\n\t\t\t\t}\n\t\t\t};\n\t\t}\n\n\t\t@Override\n\t\tpublic String toText()\n\t\t{\n\t\t\treturn \"[\" + String.join(\",\", strings) + \"]\";\n\t\t}\n\t}\n\n\t// Utility methods\n\n\tpublic final static int FORMAT_DOUBLE_PRECISION = 14;\n\n\t/**\n\t * Format a double as a string for use in the textual version of UMB\n\t * @param d Double to format\n\t */\n\tpublic String formatDouble(double d)\n\t{\n\t\treturn formatDouble(d, FORMAT_DOUBLE_PRECISION);\n\t}\n\n\t/**\n\t * Format a double as a string for use in the textual version of UMB\n\t * @param d Double to format\n\t * @param precision Precision (nymber of significant figures)\n\t */\n\tpublic String formatDouble(double d, int precision)\n\t{\n\t\t// Format as either decimal or scientific notation, depending on precision\n\t\tString result = String.format((Locale) null, \"%.\" + precision + \"g\", d);\n\t\t// Remove trailing zeros (keep one if of form x.000...)\n\t\tresult = result.replaceFirst(\"(\\\\.[0-9]*?)0+(e|$)\", \"$1$2\");\n\t\treturn result.replaceFirst(\"\\\\.(e|$)\", \".0$1\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/io/package-info.java",
    "content": "/**\n * Functionality for exporting to and importing from various file formats.\n */\npackage io;\n"
  },
  {
    "path": "prism/src/jdd/DebugJDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t* Christian von Essen <christian.vonessen@imag.fr> (VERIMAG)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jdd;\n\nimport java.util.ArrayList;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.LinkedHashMap;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Map.Entry;\nimport java.util.TreeMap;\n\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\n\n/**\n * Framework for debugging JDDNode and CUDD reference counting.\n * <br>\n * If DebugJDD is enabled (via calling DebugJDD.enabled()),\n * instead of normal JDDNodes, DebugJDDNodes are used. These\n * track the balance of referencing and dereferencing, etc and\n * throw errors or provide warnings if something problematic\n * occurs.\n * <br>\n * In addition, each DebugJDDNode carries a unique ID, which\n * is persistent over multiple invocations of PRISM, in contrast\n * to the DdNode pointers of CUDD, which are raw C/C++ pointers\n * and can differ between multiple PRISM runs, making tracking\n * more difficult.\n * <br>\n * You can enable tracing for a particular ID, which will print\n * status messages for each event for this particular JDDNode,\n * e.g., whenever the node is referenced, dereferenced, consumed\n * in a JDD method, copied, etc.\n * <br>\n * In the end, if there are reference leaks, a list of potential\n * JDDNode IDs is printed. These can then be used for tracing\n * the referencing and dereferencing of these nodes in a subsequent\n * run of PRISM to debug the reference leak.\n * <br>\n * Note: For the JDDNodes that are returned by JDDNode.getThen() and\n * JDDNode.getElse(), a different handling applies. As these are\n * generally only used for traversing an MTBDD and are not referenced\n * (beyond the internal CUDD references that are there due to the\n * fact that they are internal nodes of some MTBDD), they are\n * wrapped in a \"light-weight\" variant of DebugJDDNode called\n * DebugJDDNodeLight. They are not fully functional and\n * should never be used for JDD.Ref, JDD.Deref or as the argument\n * of a JDD method, except to compare for equality,\n * getting the variable index, getThen() and getElse() and obtaining\n * constant value of a terminal node. You can also call copy() on\n * them to obtain a \"proper\" node.\n */\npublic class DebugJDD\n{\n\t/**\n\t * A DebugJDDNode extends a JDDNode with additional information\n\t * useful for tracking refs/derefs and tracing.\n\t */\n\tprotected static class DebugJDDNode extends JDDNode\n\t{\n\n\t\t/** A static counter that is used to provide a unique ID for each JDDNode */\n\t\tprivate static long nextId = 0;\n\n\t\t/**\n\t\t * The ID for this JDDNode. In contrast with the CUDD DdNode* ptr,\n\t\t * this will be stable across PRISM invocations and can thus be\n\t\t * used for tracing.\n\t\t */\n\t\tprivate long id;\n\n\t\t/**\n\t\t * The balance of reference and dereference calls for\n\t\t * this specific JDDNode object.\n\t\t */\n\t\tprivate int nodeRefs = 0;\n\n\t\t/**\n\t\t * Constructor, with DdNode* ptr.\n\t\t * <br>\n\t\t * Registers the node with the DebugJDD infrastructure.\n\t\t * @param ptr the DdNode pointer in CUDD\n\t\t * @param isReferenced Does this JDDNode already have a reference\n\t\t *                     (like for ptrToNode) or not (like for getThen / getElse)\n\t\t */\n\t\tpublic DebugJDDNode(long ptr, boolean isReferenced)\n\t\t{\n\t\t\t// instantiate underlying JDDNode\n\t\t\tsuper(ptr);\n\t\t\t// generate and store globally unique ID\n\t\t\tid = nextId++;\n\t\t\t// the initial number of references for this JDDNode\n\t\t\tnodeRefs = 0;\n\t\t\tif (isReferenced) {\n\t\t\t\tincRef();\n\t\t\t}\n\t\t\t// store to keep track of this DebugJDDNode\n\t\t\tDebugJDD.addToSet(this);\n\t\t}\n\n\t\t/** Get the ID of this node */\n\t\tpublic long getID()\n\t\t{\n\t\t\treturn id;\n\t\t}\n\n\t\t/** Increment the reference count for this DebugJDDNode */\n\t\tpublic void incRef()\n\t\t{\n\t\t\t// increment count for node\n\t\t\tnodeRefs++;\n\t\t\t// increment javaRefs counter for this ptr\n\t\t\tint jrefs = getJavaRefCount(ptr());\n\t\t\tjavaRefs.put(ptr(), jrefs + 1);\n\t\t}\n\n\t\t/** Decrement the reference count for this DebugJDDNode */\n\t\tpublic void decRef()\n\t\t{\n\t\t\t// decrement count for node\n\t\t\tnodeRefs--;\n\t\t\t// decrement javaRefs counter for this ptr\n\t\t\tint jrefs = getJavaRefCount(ptr()) - 1;\n\t\t\tjavaRefs.put(ptr(), jrefs);\n\n\t\t\t// Checks:\n\t\t\t// (1) There is a negative number of Java references for the DdNode pointer\n\t\t\tif (jrefs < 0) {\n\t\t\t\treportError(\"DebugJDD: The number of Java references is negative for\\n \" + toStringVerbose());\n\t\t\t}\n\t\t\t// (2) There are more Java references than CUDD references\n\t\t\tif (jrefs > JDD.DebugJDD_GetRefCount(ptr())) {\n\t\t\t\treportError(\"DebugJDD: More Java refs than CUDD refs for\\n \" + toStringVerbose());\n\t\t\t}\n\t\t\t// (3) This node has more refs than there are Java refs in total\n\t\t\tif (jrefs < getNodeRefs()) {\n\t\t\t\treportError(\"DebugJDD: JDDNode has more refs than Java refs in total?!\\n \" + toStringVerbose());\n\t\t\t}\n\t\t}\n\n\t\t/** Get the number of active references for this JDDNode */\n\t\tpublic int getNodeRefs()\n\t\t{\n\t\t\treturn nodeRefs;\n\t\t}\n\n\t\tpublic String toStringVerbose()\n\t\t{\n\t\t\treturn \"ID = \" + getID()\n\t\t\t       + \", CUDD ptr = \" + ptrAsHex()\n\t\t\t       + \", refs for this JDDNode = \" + getNodeRefs()\n\t\t\t       + \", refs from Java = \" + getJavaRefCount(ptr())\n\t\t\t       + \", refs from CUDD (including internal MTBDD refs) = \"\n\t\t\t       + JDD.DebugJDD_GetRefCount(ptr());\n\t\t}\n\n\t\tpublic String ptrAsHex()\n\t\t{\n\t\t\treturn \"0x\" + Long.toHexString(ptr());\n\t\t}\n\t}\n\n\t\n\t/**\n\t * A \"light-weight\" DebugJDDNode, for marking JDDNodes\n\t * that have been obtained by a call from getThen()/getElse()\n\t * and thus don't take part in the usual reference counting\n\t * scheme.\n\t */\n\tprotected static class DebugJDDNodeLight extends JDDNode {\n\t\t/**\n\t\t * Constructor, with DdNode* ptr.\n\t\t * <br>\n\t\t * @param ptr the DdNode pointer in CUDD\n\t\t */\n\t\tpublic DebugJDDNodeLight(long ptr)\n\t\t{\n\t\t\t// instantiate underlying JDDNode\n\t\t\tsuper(ptr);\n\t\t}\n\t}\n\n\t/* ----- Settings ------ */\n\n\t/**\n\t * Flag, determines if the debugging of JDD nodes is enabled.\n\t * Default off.\n\t */\n\tpublic static boolean debugEnabled = false;\n\n\t/**\n\t * Flag, determines if all nodes should be traced (in contrast to only those\n\t * specified using enableTracingForID().\n\t * Default off.\n\t */\n\tpublic static boolean traceAll = false;\n\n\t/**\n\t * Flag, determines if copies of traced nodes should be traced as well.\n\t * Default off.\n\t */\n\tpublic static boolean traceFollowCopies = false;\n\n\t/**\n\t * Flag, determines if warnings should be promoted to\n\t * errors, i.e., throwing an exception.\n\t * Default off.\n\t */\n\tpublic static boolean warningsAreFatal = false;\n\n\t/**\n\t * Flag, determines if warnings should be suppressed.\n\t * Default off.\n\t */\n\tpublic static boolean warningsOff = false;\n\n\t/**\n\t * Map from DebugJDDNode IDs to DebugJDDNode.\n\t * LinkedHashMap to ensure that iterating over the map returns the\n\t * DebugJDDNodes in a consistent order, sorted by ID.\n\t */\n\tprotected static LinkedHashMap<Long, DebugJDDNode> nodes = new LinkedHashMap<Long, DebugJDDNode>();\n\n\t/** A map from DdNode pointers to the current sum of the nodeRefs of all JDDNodes for that pointer */\n\tprotected static HashMap<Long, Integer> javaRefs = new HashMap<Long, Integer>();\n\n\t/** An optional set of DebugJDDNode IDs that will be traced */\n\tprotected static HashSet<Long> traceIDs = null;\n\n\t/** Did we raise an error? */\n\tprotected static boolean raisedError = false;\n\n\t/** Enable debugging */\n\tpublic static void enable()\n\t{\n\t\tdebugEnabled = true;\n\t}\n\n\t/** Activate tracing for the DebugJDDNode with ID id */\n\tpublic static void enableTracingForID(long id)\n\t{\n\t\tif (traceIDs == null) {\n\t\t\ttraceIDs = new HashSet<Long>();\n\t\t}\n\t\ttraceIDs.add(id);\n\t\tSystem.out.println(\"DebugJDD: Enable tracing for ID \" + id);\n\t\tenable(); // tracing implies debugging\n\t}\n\n\t/** Returns true if this node should be traced */\n\tprivate static boolean isTraced(DebugJDDNode dNode)\n\t{\n\t\tif (traceAll) {\n\t\t\treturn true;\n\t\t}\n\n\t\tif (traceIDs != null && traceIDs.contains(dNode.getID())) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** Store a DebugJDDNode for tracking of the references */\n\tprivate static void addToSet(DebugJDDNode node)\n\t{\n\t\tif (nodes.put(node.getID(), node) != null) {\n\t\t\t// implementation error, should not happen\n\t\t\treportError(\"DebugJDD: Internal error, adding the same JDDNode multiple times, ID=\" + node.getID());\n\t\t}\n\t}\n\n\t/**\n\t * Called when CUDD is shutdown.\n\t * <br>\n\t * Analyzes the reference counting situation\n\t * and prints diagnostics in case of a leak.\n\t */\n\tpublic static void endLifeCycle()\n\t{\n\t\tif (raisedError) {\n\t\t\tSystem.out.println(\"There was a fatal error, skipping DDNode leak checking...\");\n\t\t\treturn;\n\t\t}\n\n\t\t// Get the external reference count from CUDD\n\t\tMap<Long, Integer> externalRefCounts = getExternalRefCounts();\n\t\tif (externalRefCounts.size() == 0) {\n\t\t\t// everthing is fine\n\t\t\treturn;\n\t\t}\n\n\t\tSystem.out.println(\"\\nWarning: Found \" + externalRefCounts.size() + \" leaked JDDNode references.\");\n\t\tSystem.out.flush();\n\t\tfor (Entry<Long, Integer> extRef : externalRefCounts.entrySet()) {\n\t\t\tlong ptr = extRef.getKey();\n\t\t\tList<DebugJDDNode> matchingNodes = new ArrayList<DebugJDDNode>();\n\t\t\tList<DebugJDDNode> posRefNodes = new ArrayList<DebugJDDNode>();\n\t\t\tfor (DebugJDDNode node : nodes.values()) {\n\t\t\t\tif (node.ptr() == ptr) {\n\t\t\t\t\t// node matches\n\t\t\t\t\tmatchingNodes.add(node);\n\t\t\t\t\t// node still has positive reference count\n\t\t\t\t\tif (node.getNodeRefs() > 0) {\n\t\t\t\t\t\tposRefNodes.add(node);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tSystem.out.println(\"DdNode ptr=0x\" + Long.toHexString(ptr)\n\t\t\t                   + \", \" + nodeInfo(ptr) + \" has \" + extRef.getValue() + \" remaining external references.\");\n\t\t\tif (posRefNodes.size() > 0) {\n\t\t\t\tSystem.out.println(\" Candidates:\");\n\t\t\t\tfor (DebugJDDNode node : posRefNodes) {\n\t\t\t\t\tSystem.out.println(\"  ID=\" + node.getID() + \" with \" + node.getNodeRefs() + \" references  (\" + node.toStringVerbose() + \")\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tSystem.out.println(\" No candidates, here are all JDDNodes for that DdNode:\");\n\t\t\t\tfor (DebugJDDNode node : matchingNodes) {\n\t\t\t\t\tSystem.out.println(\"  ID=\" + node.getID() + \" with \" + node.getNodeRefs() + \" references  (\" + node.toStringVerbose() + \")\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// clean-up data structures\n\t\tnodes.clear();\n\t\tjavaRefs.clear();\n\t\t// reset ID counter\n\t\tDebugJDDNode.nextId = 0;\n\n\t\tif (warningsAreFatal) {\n\t\t\treportError(\"DebugJDD: Leaked references\");\n\t\t}\n\t}\n\n\t/** Throw an exception with the given message, remember that we have raised an error */\n\tprivate static void reportError(String message)\n\t{\n\t\traisedError = true;\n\t\tthrow new RuntimeException(message);\n\t}\n\n\t/** Get the CUDD reference count for the pointer of the JDDNode */\n\tpublic static int getRefCount(JDDNode n)\n\t{\n\t\treturn JDD.DebugJDD_GetRefCount(n.ptr());\n\t}\n\n\t/** Get the number of DebugJDDNodes that reference the pointer */\n\tpublic static int getJavaRefCount(long ptr)\n\t{\n\t\tInteger jrefs = javaRefs.get(ptr);\n\t\tif (jrefs == null)\n\t\t\treturn 0;\n\t\treturn jrefs;\n\t}\n\n\t/** Get a map, mapping DdNode pointers to the external reference counts expected by CUDD */\n\tpublic static Map<Long, Integer> getExternalRefCounts()\n\t{\n\t\tMap<Long, Integer> result = new TreeMap<Long, Integer>();\n\t\t// Array consists of (pointer, count) pairs\n\t\tlong[] externalRefCounts = JDD.DebugJDD_GetExternalRefCounts();\n\t\tint i = 0;\n\t\twhile (i < externalRefCounts.length) {\n\t\t\tlong node = externalRefCounts[i++];\n\t\t\tint count = (int) externalRefCounts[i++];\n\t\t\tresult.put(node, count);\n\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/** Get a string with more detailed info for a DdNode pointer */\n\tprivate static String nodeInfo(long ptr)\n\t{\n\t\tif (JDDNode.DDN_IsConstant(ptr)) {\n\t\t\treturn \"constant(\" + JDDNode.DDN_GetValue(ptr) + \"), CUDD refs=\" + JDD.DebugJDD_GetRefCount(ptr);\n\t\t} else {\n\t\t\treturn \"var(\" + JDDNode.DDN_GetIndex(ptr) + \"), CUDD refs=\" + JDD.DebugJDD_GetRefCount(ptr);\n\t\t}\n\t}\n\n\t/** Log information about the action performed on the DebugJDDNode */\n\tprivate static void trace(String action, DebugJDDNode dNode)\n\t{\n\t\tSystem.out.println(\"\\ntrace(\" + action\n\t\t                   + \", ID=\" + dNode.getID() + \") => \" + dNode.getNodeRefs()\n\t\t                   + \" refs for this JDDNode\\n \" + dNode.toStringVerbose());\n\t\tprintStack(0);\n\t}\n\n\t/** Print the current stack trace, omitting initial java.lang and jdd.DebugJDD frames.\n\t * @param limit Limit on the number of frames to print, 0 = no limit\n\t */\n\tprivate static void printStack(int limit)\n\t{\n\t\t// apparently, the following is more efficient than calling Thread.currentThread.getStackTrace()\n\t\tStackTraceElement[] stack = (new Throwable()).getStackTrace();\n\t\tboolean foundStart = false;\n\t\tint printed = 0;\n\t\tfor (StackTraceElement ste : stack) {\n\t\t\tString st = ste.toString();\n\t\t\tif (!foundStart) {\n\t\t\t\tif (st.startsWith(\"java.lang\") || st.startsWith(\"jdd.DebugJDD\")) {\n\t\t\t\t\t// skip\n\t\t\t\t\tcontinue;\n\t\t\t\t} else {\n\t\t\t\t\tfoundStart = true;\n\t\t\t\t\t// continue below\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (limit > 0 && printed++ >= limit) {\n\t\t\t\tSystem.out.println(\"  ...\");\n\t\t\t\tbreak;\n\t\t\t} else {\n\t\t\t\tSystem.out.println(\"  at \" + st);\n\t\t\t}\n\t\t}\n\t\tSystem.out.println();\n\t\tSystem.out.flush();\n\t}\n\n\t/**\n\t * DebugJDD implementation of JDD.Ref.\n\t * <br>\n\t * Increments both the CUDD reference counter and the reference counter for the JDDNode.\n\t */\n\tprotected static void Ref(JDDNode node)\n\t{\n\t\tif (node instanceof DebugJDDNodeLight) {\n\t\t\treportError(\"DebugJDD: Illegal operation, trying to reference a light-weight JDDNode (obtained from getThen()/getElse()) directly. Use copy() instead\");\n\t\t}\n\n\t\tif (!(node instanceof DebugJDDNode)) {\n\t\t\t// using a node that is not wrapped in a DebugJDDNode, but when debugging is\n\t\t\t// enabled all nodes should be either DebugJDDNodeLight or DebugJDDNode\n\t\t\treportError(\"DebugJDD: Internal error, encountered a node object of type \" + node.getClass().getName() + \" in debug mode\");\n\t\t}\n\n\t\tDebugJDDNode dNode = (DebugJDDNode) node;\n\n\t\t// increment reference in DebugJDD\n\t\tdNode.incRef();\n\t\t// increment reference in CUDD\n\t\tJDD.DD_Ref(node.ptr());\n\n\t\tif (isTraced(dNode)) {\n\t\t\ttrace(\"Ref\", dNode);\n\t\t}\n\t}\n\n\t/**\n\t * DebugJDD implementation of JDD.Deref.\n\t * <br>\n\t * Decrements both the CUDD reference counter and the reference counter for the JDDNode,\n\t * performing a variety of sanity checks.\n\t */\n\tprotected static void Deref(JDDNode node)\n\t{\n\t\tif (node instanceof DebugJDDNodeLight) {\n\t\t\treportError(\"DebugJDD: Illegal operation, trying to dereference a light-weight JDDNode (obtained from getThen()/getElse()) directly\");\n\t\t}\n\n\t\tif (!(node instanceof DebugJDDNode)) {\n\t\t\t// using a node that is not wrapped in a DebugJDDNode, but when debugging is\n\t\t\t// enabled all nodes should be either DebugJDDNodeLight or DebugJDDNode\n\t\t\treportError(\"DebugJDD: Internal error, encountered a node object of type \" + node.getClass().getName() + \" in debug mode\");\n\t\t}\n\n\t\tDebugJDDNode dNode = (DebugJDDNode) node;\n\t\tif (dNode.getNodeRefs() <= 0 && getJavaRefCount(node.ptr()) > 0) {\n\t\t\t// This is only a warning as currently there are places\n\t\t\t// where referencing / dereferencing happens across multiple JDDNodes,\n\t\t\t// which is not pretty but not necessarily problematic, as long as\n\t\t\t// the total number of references from Java remains positive\n\t\t\tString warning = \"DebugJDD: Deref of a JDDNode with non-positive ref count:\\n \" + dNode.toStringVerbose();\n\t\t\tif (!warningsOff && !warningsAreFatal) {\n\t\t\t\tSystem.out.println(\"Warning, \" + warning);\n\t\t\t\tprintStack(0);\n\t\t\t} else if (!warningsOff && warningsAreFatal) {\n\t\t\t\treportError(warning);\n\t\t\t}\n\t\t}\n\n\t\tif (getJavaRefCount(node.ptr()) <= 0) {\n\t\t\treportError(\"DebugJDD: Trying to Deref a JDDNode with non-positive Java ref count:\\n \" + dNode.toStringVerbose());\n\t\t}\n\n\t\tint cuddRefCount = JDD.DebugJDD_GetRefCount(node.ptr());\n\t\tif (cuddRefCount <= 0) {\n\t\t\treportError(\"DebugJDD: Trying to Deref a JDDNode with a non-positive CUDD ref count\\n \" + dNode.toStringVerbose());\n\t\t}\n\n\t\t// decrement reference in DebugJDD\n\t\tdNode.decRef();\n\t\t// decrement reference in CUDD\n\t\tJDD.DD_Deref(node.ptr());\n\n\t\tif (isTraced(dNode)) {\n\t\t\ttrace(\"Deref\", dNode);\n\t\t}\n\t}\n\n\t/**\n\t * DebugJDD implementation of JDDNode.copy().\n\t * <br>\n\t * Increments the reference count for the copy and handles tracing.\n\t */\n\tprotected static JDDNode Copy(JDDNode node)\n\t{\n\t\tif (node instanceof DebugJDDNodeLight) {\n\t\t\t// copy from a light-weight node (result of getThen()/getElse())\n\t\t\tDebugJDDNode result = new DebugJDD.DebugJDDNode(node.ptr(), true);\n\t\t\tJDD.DD_Ref(result.ptr());\n\n\t\t\tif (isTraced(result)) {\n\t\t\t\ttrace(\"Copied from light-weight node\", result);\n\t\t\t}\n\t\t\treturn result;\n\t\t}\n\n\t\tif (!(node instanceof DebugJDDNode)) {\n\t\t\t// using a node that is not wrapped in a DebugJDDNode, but when debugging is\n\t\t\t// enabled all nodes should be either DebugJDDNodeLight or DebugJDDNode\n\t\t\treportError(\"DebugJDD: Internal error, encountered a node object of type \" + node.getClass().getName() + \" in debug mode\");\n\t\t}\n\n\t\tDebugJDDNode dNode = (DebugJDDNode) node;\n\n\t\tif (dNode.getNodeRefs() <= 0) {\n\t\t\treportError(\"DebugJDD: Trying to copy a JDDNode with non-positive ref count:\\n \" + dNode.toStringVerbose());\n\t\t}\n\n\t\tif (getRefCount(dNode) <= 0) {\n\t\t\treportError(\"DebugJDD: Trying to copy a JDDNode with non-positive CUDD ref count:\\n \" + dNode.toStringVerbose());\n\t\t}\n\n\t\tDebugJDDNode result = new DebugJDD.DebugJDDNode(dNode.ptr(), true);\n\t\tJDD.DD_Ref(result.ptr());\n\n\t\tif (isTraced(dNode)) {\n\t\t\ttrace(\"Copy to \" + result.getID(), dNode);\n\t\t}\n\n\t\tif (!traceAll && traceFollowCopies && isTraced(dNode)) {\n\t\t\t// if we are not tracing everything anyway and we should follow copies:\n\t\t\t// enable tracing for the copy if the original node is traced\n\t\t\tenableTracingForID(result.getID());\n\t\t}\n\n\t\tif (isTraced(result)) {\n\t\t\ttrace(\"Copied from \" + dNode.getID(), result);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * DebugJDD implementation of JDD.ptrToNode, i.e.,\n\t * converting a (referenced) DdNode ptr returned by\n\t * the DD_* CUDD abstraction layer into a proper JDDNode.\n\t */\n\tprotected static JDDNode ptrToNode(long ptr)\n\t{\n\t\tDebugJDDNode dNode = new DebugJDD.DebugJDDNode(ptr, true);\n\n\t\tif (isTraced(dNode)) {\n\t\t\ttrace(\"ptrToNode\", dNode);\n\t\t}\n\n\t\treturn dNode;\n\t}\n\n\t/**\n\t * Common checks for the case where a DebugJDDNode is used (passed as a method\n\t * argument or with getThen(), getElse() or getValue()).\n\t * @throws RuntimeException in case of a problem\n\t */\n\tprivate static void useNode(DebugJDDNode node)\n\t{\n\t\tDebugJDDNode dNode = (DebugJDDNode) node;\n\t\tif (dNode.getNodeRefs() <= 0 && getJavaRefCount(node.ptr()) > 0) {\n\t\t\t// This is only a warning as currently there are places\n\t\t\t// where referencing / dereferencing happens across multiple JDDNodes,\n\t\t\t// which is not pretty but not necessarily problematic, as long as\n\t\t\t// the total number of references from Java remains positive\n\t\t\tString warning = \"DebugJDD: Trying to use a JDDNode with non-positive ref count:\\n \" + dNode.toStringVerbose();\n\t\t\tif (!warningsOff && !warningsAreFatal) {\n\t\t\t\tSystem.out.println(\"Warning, \" + warning);\n\t\t\t\tprintStack(0);\n\t\t\t} else if (!warningsOff && warningsAreFatal) {\n\t\t\t\treportError(warning);\n\t\t\t}\n\t\t}\n\n\t\tif (getJavaRefCount(node.ptr()) <= 0) {\n\t\t\treportError(\"DebugJDD: Trying to use a JDDNode with non-positive Java ref count in a method call:\\n \" + dNode.toStringVerbose());\n\t\t}\n\n\t\tint cuddRefCount = JDD.DebugJDD_GetRefCount(node.ptr());\n\t\tif (cuddRefCount <= 0) {\n\t\t\treportError(\"DebugJDD: Trying to use a JDDNode with a non-positive CUDD ref count in a method call:\\n \" + dNode.toStringVerbose());\n\t\t}\n\t}\n\n\t/**\n\t * DebugJDD handling of passing JDDNodes as arguments to the\n\t * DD_* layer, where they will be ultimately dereferenced.\n\t * <br>\n\t * As the actual dereferencing in CUDD will only happen\n\t * after the given MTBDD method is finished, we only\n\t * decrement the reference counter on the DebugJDD side.\n\t */\n\tprotected static void DD_Method_Argument(JDDNode node)\n\t{\n\t\tif (node instanceof DebugJDDNodeLight) {\n\t\t\treportError(\"DebugJDD: Illegal operation, trying to use a light-weight JDDNode (obtained from getThen()/getElse()) in a method call\");\n\t\t}\n\t\tif (!(node instanceof DebugJDDNode)) {\n\t\t\t// using a node that is not wrapped in a DebugJDDNode, but when debugging is\n\t\t\t// enabled all nodes should be either DebugJDDNodeLight or DebugJDDNode\n\t\t\treportError(\"DebugJDD: Internal error, encountered a node object of type \" + node.getClass().getName() + \" in debug mode\");\n\t\t}\n\n\t\tDebugJDDNode dNode = (DebugJDDNode) node;\n\t\t// do standard \"use node\" checks\n\t\tuseNode(dNode);\n\n\t\t// decrement reference in DebugJDD\n\t\tdNode.decRef();\n\t\t// ... but don't dereference in CUDD yet. This will\n\t\t// be done in the DD_* methods after the actual\n\t\t// processing has happened and the result is referenced,\n\t\t// as then this argument does not have to be protected\n\t\t// anymore\n\n\t\tif (isTraced(dNode)) {\n\t\t\ttrace(\"Deref (as method argument)\", dNode);\n\t\t}\n\t}\n\n\t/**\n\t * DebugJDD handling of JDDNode.getThen().\n\t * Returns a DebugJDDNodeLight wrapper around the result.\n\t */\n\tprotected static JDDNode nodeGetThen(JDDNode node)\n\t{\n\t\tif (node instanceof DebugJDDNode) {\n\t\t\tDebugJDDNode dNode = (DebugJDDNode) node;\n\t\t\tuseNode(dNode);\n\t\t} else if (node instanceof DebugJDDNodeLight) {\n\t\t\t// nothing to do\n\t\t} else {\n\t\t\treportError(\"DebugJDD: Internal error, encountered a node object of type \" + node.getClass().getName() + \" in debug mode\");\n\t\t}\n\n\t\tlong ptr = JDDNode.DDN_GetThen(node.ptr());\n\t\tif (ptr == 0) {\n\t\t\tif (node.isConstant()) {\n\t\t\t\treportError(\"Trying to access the 'then' child of a constant MTBDD node\");\n\t\t\t} else {\n\t\t\t\treportError(\"getThen: CUDD returned NULL, but node is not a constant node. Out of memory or corrupted MTBDD?\");\n\t\t\t}\n\t\t}\n \t\treturn new DebugJDDNodeLight(ptr);\n\t}\n\n\t/**\n\t * DebugJDD handling of JDDNode.getElse().\n\t * Returns a DebugJDDNodeLight wrapper around the result.\n\t */\n\tprotected static JDDNode nodeGetElse(JDDNode node)\n\t{\n\t\tif (node instanceof DebugJDDNode) {\n\t\t\tDebugJDDNode dNode = (DebugJDDNode) node;\n\t\t\tuseNode(dNode);\n\t\t} else if (node instanceof DebugJDDNodeLight) {\n\t\t\t// nothing to do\n\t\t} else {\n\t\t\treportError(\"DebugJDD: Internal error, encountered a node object of type \" + node.getClass().getName() + \" in debug mode\");\n\t\t}\n\n\t\tlong ptr = JDDNode.DDN_GetElse(node.ptr());\n\t\tif (ptr == 0) {\n\t\t\tif (node.isConstant()) {\n\t\t\t\treportError(\"Trying to access the 'else' child of a constant MTBDD node\");\n\t\t\t} else {\n\t\t\t\treportError(\"getElse: CUDD returned NULL, but node is not a constant node. Out of memory or corrupted MTBDD?\");\n\t\t\t}\n\t\t}\n \t\treturn new DebugJDDNodeLight(ptr);\n\t}\n\n\t/**\n\t * DebugJDD handling of JDDNode.getValue().\n\t * Performs check to ensure that the reference counting\n\t * is fine and that the node is actually a constant node.\n\t */\n\tprotected static double nodeGetValue(JDDNode node)\n\t{\n\t\tif (node instanceof DebugJDDNode) {\n\t\t\tDebugJDDNode dNode = (DebugJDDNode) node;\n\t\t\tuseNode(dNode);\n\t\t} else if (node instanceof DebugJDDNodeLight) {\n\t\t\t// nothing to do\n\t\t} else {\n\t\t\treportError(\"DebugJDD: Internal error, encountered a node object of type \" + node.getClass().getName() + \" in debug mode\");\n\t\t}\n\n\t\tif (!node.isConstant()) {\n\t\t\treportError(\"Trying to get value of MTBDD node, but is not a constant node\");\n\t\t}\n\t\treturn JDDNode.DDN_GetValue(node.ptr());\n\t}\n\n\t/* --------------------- TESTING --------------------------------------------\n\t *\n\t * The methods below provide simple test cases that can be executed from\n\t * the command line to study the behaviour of the debugging functionality\n\t * and of the tracing mechanism.\n\t */\n\n\t@SuppressWarnings(\"unused\")\n\tprivate static void test_1()\n\t{\n\t\t// test case: missing dereference\n\t\tJDDNode const2 = JDD.Constant(2.0);\n\t}\n\n\tprivate static void test_2()\n\t{\n\t\t// test case: additional dereference\n\t\tJDDNode const2 = JDD.Constant(2.0);\n\t\tJDD.Deref(const2);\n\t\tJDD.Deref(const2);\n\t}\n\n\tprivate static void test_3()\n\t{\n\t\t// test case: use of a JDDNode with 0 references\n\t\tJDDNode const2 = JDD.Constant(2.0);\n\t\tJDD.Deref(const2);\n\t\tJDDNode t = JDD.ITE(JDD.Constant(1), const2, JDD.Constant(0));\n\t\tJDD.Deref(t);\n\t}\n\n\t@SuppressWarnings(\"unused\")\n\tprivate static void test_4()\n\t{\n\t\t// test case: use of a JDDNode with 0 references, but which has other\n\t\t// Java references\n\t\tJDDNode const2 = JDD.Constant(2.0);\n\t\tJDDNode copy = const2.copy();\n\t\tJDD.Deref(const2);\n\t\tJDDNode t = JDD.ITE(JDD.Constant(1), const2, JDD.Constant(0));\n\t\tJDD.Deref(t);\n\t}\n\n\tprivate static void test_5()\n\t{\n\t\t// test case: more complex example with no problems\n\t\t// can be used with -ddtraceall to look at tracing\n\t\tJDDNode v = JDD.Var(0);\n\t\tJDDVars vars = new JDDVars();\n\t\tvars.addVar(v);\n\n\t\tJDDNode t = JDD.ITE(v.copy(), JDD.Constant(2.0), JDD.Constant(1.0));\n\t\tJDDNode c = JDD.Constant(2.0);\n\n\t\tt = JDD.Times(t, c);\n\t\tt = JDD.SumAbstract(t, vars);\n\n\t\tJDD.Deref(t);\n\t\tvars.derefAll();\n\t}\n\n\t@SuppressWarnings(\"unused\")\n\tprivate static void test_6()\n\t{\n\t\t// test case: getThen of a constant\n\t\tJDDNode const2 = JDD.Constant(2);\n\t\tJDDNode t = const2.getThen();\n\t}\n\n\t@SuppressWarnings(\"unused\")\n\tprivate static void test_7()\n\t{\n\t\t// test case: getElse of a constant\n\t\tJDDNode const2 = JDD.Constant(2);\n\t\tJDDNode t = const2.getElse();\n\t}\n\n\t@SuppressWarnings(\"unused\")\n\tprivate static void test_8()\n\t{\n\t\t// test case: getValue of an internal node\n\t\tJDDNode v = JDD.Var(0);\n\t\tdouble value = v.getValue();\n\t}\n\n\tprivate static void test_9()\n\t{\n\t\t// test case: use of a light-weight node as a\n\t\t// method argument\n\t\tJDDNode v = JDD.Var(0);\n\t\tJDDNode result = JDD.Apply(JDD.MAX, v.getThen(), v.getElse());\n\t\tJDD.Deref(result);\n\t}\n\n\tprivate static void test_10()\n\t{\n\t\t// test case: deref of a light-weight node as a\n\t\t// method argument\n\t\tJDDNode v = JDD.Var(0);\n\t\tJDD.Deref(v.getThen());\n\t\tJDD.Deref(v);\n\t}\n\n\tprivate static void test_11()\n\t{\n\t\t// test case: ref of a light-weight node as a\n\t\t// method argument\n\t\tJDDNode v = JDD.Var(0);\n\t\tJDDNode t = v.getThen();\n\t\tJDD.Ref(t);\n\t\tJDD.Deref(t);\n\t\tJDD.Deref(v);\n\t}\n\n\tprivate static void test_12()\n\t{\n\t\t// test case: proper use of a light-weight node as a\n\t\t// method argument by using copy()\n\t\tJDDNode v = JDD.Var(0);\n\t\tJDDNode result = JDD.Apply(JDD.MAX, v.getThen().copy(), v.getElse().copy());\n\t\tJDD.Deref(result);\n\t\tJDD.Deref(v);\n\t}\n\n\tprivate static void usage()\n\t{\n\t\tSystem.out.println(\"\\nUsage: PRISM_MAINCLASS=jdd.DebugJDD prism [arguments] [test cases]\");\n\t\tSystem.out.println(\"\\nExample: PRISM_MAINCLASS=jdd.DebugJDD prism -dddebug 1 4\");\n\t\tSystem.out.println(\"   Run test cases 1 and 4, with debugging enabled\");\n\t\tSystem.out.println(\"\\nArguments:\");\n\t\tSystem.out.println(\" -dddebug                 Enabled JDD debugging\");\n\t\tSystem.out.println(\" -ddtraceall              Trace all JDD nodes\");\n\t\tSystem.out.println(\" -ddtracefollowcopies     Trace copies of traced JDD nodes as well\");\n\t\tSystem.out.println(\" -dddebugwarnfatal        Treat warnings as errors\");\n\t\tSystem.out.println(\" -dddebugwarnoff          Turn off warnings\");\n\t\tSystem.out.println(\" -ddtrace n               Trace JDDNode with ID=n\");\n\t\tSystem.out.println(\"\\nFor the test cases, look at the source code in jdd/DebugJDD.java\");\n\t}\n\n\tprivate static void errorAndExit(String error)\n\t{\n\t\tSystem.out.println(error);\n\t\tusage();\n\t\tSystem.exit(1);\n\t}\n\n\t/** Command-line entry point */\n\tpublic static void main(String[] args)\n\t{\n\t\tSystem.out.println(\"PRISM [jdd.DebugJDD test bed / demonstrator]\");\n\t\tSystem.out.println(\"============================================\\n\");\n\n\t\tArrayList<String> testCases = new ArrayList<String>();\n\n\t\t// Parse the arguments\n\t\tfor (int i = 0; i < args.length; i++) {\n\n\t\t\t// if is a switch...\n\t\t\tif (args[i].length() > 0 && args[i].charAt(0) == '-') {\n\n\t\t\t\t// Remove \"-\"\n\t\t\t\tString sw = args[i].substring(1);\n\t\t\t\tif (sw.length() == 0) {\n\t\t\t\t\terrorAndExit(\"Invalid empty switch\");\n\t\t\t\t}\n\t\t\t\t// Remove optional second \"-\" (i.e. we allow switches of the form --sw too)\n\t\t\t\tif (sw.charAt(0) == '-')\n\t\t\t\t\tsw = sw.substring(1);\n\n\t\t\t\t// DD Debugging options\n\t\t\t\tif (sw.equals(\"dddebug\")) {\n\t\t\t\t\tjdd.DebugJDD.enable();\n\t\t\t\t} else if (sw.equals(\"ddtraceall\")) {\n\t\t\t\t\tjdd.DebugJDD.traceAll = true;\n\t\t\t\t} else if (sw.equals(\"ddtracefollowcopies\")) {\n\t\t\t\t\tjdd.DebugJDD.traceFollowCopies = true;\n\t\t\t\t} else if (sw.equals(\"dddebugwarnfatal\")) {\n\t\t\t\t\tjdd.DebugJDD.warningsAreFatal = true;\n\t\t\t\t} else if (sw.equals(\"dddebugwarnoff\")) {\n\t\t\t\t\tjdd.DebugJDD.warningsOff = true;\n\t\t\t\t} else if (sw.equals(\"ddtrace\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tString idString = args[++i];\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tint id = Integer.parseInt(idString);\n\t\t\t\t\t\t\tjdd.DebugJDD.enableTracingForID(id);\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"The -\" + sw + \" switch requires an integer argument (JDDNode ID)\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"The -\" + sw + \" switch requires an additional argument (JDDNode ID)\");\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\terrorAndExit(\"Unknown switch: -\" + sw);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\t// not a switch, assume is a test case\n\t\t\t\ttestCases.add(args[i]);\n\t\t\t}\n\t\t}\n\n\t\ttry {\n\t\t\t// initialise Prism/CUDD\n\t\t\tPrismLog mainLog = new PrismFileLog(\"stdout\");\n\n\t\t\tmainLog.println(\"\\n[Initializing PRISM]\\n\");\n\n\t\t\t// create prism object(s)\n\t\t\tPrism prism = new Prism(mainLog);\n\n\t\t\tprism.initialise();\n\n\t\t\tint i = 1;\n\t\t\tfor (String testCase : testCases) {\n\t\t\t\tmainLog.print(\"\\n[Running test case \" + testCase);\n\t\t\t\tif (testCases.size() > 1) {\n\t\t\t\t\tmainLog.print(\" (\" + i + \"/\" + testCases.size() + \")\");\n\t\t\t\t}\n\t\t\t\tmainLog.println(\"]\\n\");\n\t\t\t\ti++;\n\n\t\t\t\tswitch (testCase) {\n\t\t\t\tcase \"1\":\n\t\t\t\t\ttest_1();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"2\":\n\t\t\t\t\ttest_2();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"3\":\n\t\t\t\t\ttest_3();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"4\":\n\t\t\t\t\ttest_4();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"5\":\n\t\t\t\t\ttest_5();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"6\":\n\t\t\t\t\ttest_6();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"7\":\n\t\t\t\t\ttest_7();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"8\":\n\t\t\t\t\ttest_8();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"9\":\n\t\t\t\t\ttest_9();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"10\":\n\t\t\t\t\ttest_10();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"11\":\n\t\t\t\t\ttest_11();\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"12\":\n\t\t\t\t\ttest_12();\n\t\t\t\t\tbreak;\n\n\t\t\t\tdefault:\n\t\t\t\t\terrorAndExit(\"Unknown test case: \" + testCase);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tmainLog.println(\"\\n[Closing down PRISM/CUDD]\\n\");\n\n\t\t\t// clear up and close down\n\t\t\tprism.closeDown(true);\n\n\t\t\tmainLog.println();\n\t\t\t// Close logs (in case they are files)\n\t\t\tmainLog.close();\n\t\t} catch (PrismException e) {\n\t\t\te.printStackTrace();\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/jdd/JDD.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"JDD.h\"\n#include \"JDDNode.h\"\n#include \"JDDVars.h\"\n#include \"jnipointer.h\"\n#include \"cuddInt.h\"\n\n#include <cstdio>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n\n//------------------------------------------------------------------------------\n\n// CUDD manager: cached here locally, so that it doesn't have to be passed to every\n// CUDD/dd call. Extracted from underlying CUDD lib on call to InitialiseCUDD\nstatic DdManager *ddman;\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_GetCUDDManager(JNIEnv *env, jclass cls)\n{\n\treturn ptr_to_jlong(ddman);\n}\n\n//==============================================================================\n//\n//\tWrapper functions for dd\n//\t\n//==============================================================================\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1SetOutputStream(JNIEnv *env, jclass cls, jlong __jlongpointer fp)\n{\n\tDD_SetOutputStream(jlong_to_FILE(fp));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1GetOutputStream(JNIEnv *env, jclass cls)\n{\n\treturn ptr_to_jlong(DD_GetOutputStream());\n}\n\n//==============================================================================\n//\n//\tWrapper functions for dd_cudd\n//\t\n//==============================================================================\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1InitialiseCUDD__(JNIEnv *env, jclass cls)\n{\n\tddman = DD_InitialiseCUDD();\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1InitialiseCUDD__JD(JNIEnv *env, jclass cls, jlong max_mem, jdouble epsilon)\n{\n\tddman = DD_InitialiseCUDD(max_mem, epsilon);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1SetCUDDMaxMem(JNIEnv *env, jclass cls, jlong max_mem)\n{\n\tDD_SetCUDDMaxMem(ddman, max_mem);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1SetCUDDEpsilon(JNIEnv *env, jclass cls, jdouble epsilon)\n{\n\tDD_SetCUDDEpsilon(ddman, epsilon);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1CloseDownCUDD(JNIEnv *env, jclass cls, jboolean check)\n{\n\tDD_CloseDownCUDD(ddman, check);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1Ref(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\tCudd_Ref(jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1Deref(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\tCudd_RecursiveDeref(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintCacheInfo(JNIEnv *env, jclass cls)\n{\n\tDD_PrintCacheInfo(ddman);\n}\n\n//==============================================================================\n//\n//\tWrapper functions for dd_basics\n//\t\n//==============================================================================\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Create(JNIEnv *env, jclass cls)\n{\n\treturn ptr_to_jlong(DD_Create(ddman));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Constant(JNIEnv *env, jclass cls, jdouble value)\n{\n\treturn ptr_to_jlong(DD_Constant(ddman, value));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1PlusInfinity(JNIEnv *env, jclass cls)\n{\n\treturn ptr_to_jlong(DD_PlusInfinity(ddman));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1MinusInfinity(JNIEnv *env, jclass cls)\n{\n\treturn ptr_to_jlong(DD_MinusInfinity(ddman));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Var(JNIEnv *env, jclass cls, jint i)\n{\n\treturn ptr_to_jlong(DD_Var(ddman, i));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Not(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn ptr_to_jlong(DD_Not(ddman, jlong_to_DdNode(dd)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Or(JNIEnv *env, jclass cls, jlong __jlongpointer dd1, jlong __jlongpointer dd2)\n{\n\treturn ptr_to_jlong(DD_Or(ddman, jlong_to_DdNode(dd1), jlong_to_DdNode(dd2)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1And(JNIEnv *env, jclass cls, jlong __jlongpointer dd1, jlong __jlongpointer dd2)\n{\n\treturn ptr_to_jlong(DD_And(ddman, jlong_to_DdNode(dd1), jlong_to_DdNode(dd2)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Xor(JNIEnv *env, jclass cls, jlong __jlongpointer dd1, jlong __jlongpointer dd2)\n{\n\treturn ptr_to_jlong(DD_Xor(ddman, jlong_to_DdNode(dd1), jlong_to_DdNode(dd2)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Implies(JNIEnv *env, jclass cls, jlong __jlongpointer dd1, jlong __jlongpointer dd2)\n{\n\treturn ptr_to_jlong(DD_Implies(ddman, jlong_to_DdNode(dd1), jlong_to_DdNode(dd2)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Apply(JNIEnv *env, jclass cls, jint op, jlong __jlongpointer dd1, jlong __jlongpointer dd2)\n{\n\treturn ptr_to_jlong(DD_Apply(ddman, op, jlong_to_DdNode(dd1), jlong_to_DdNode(dd2)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1MonadicApply(JNIEnv *env, jclass cls, jint op, jlong __jlongpointer dd)\n{\n\treturn ptr_to_jlong(DD_MonadicApply(ddman, op, jlong_to_DdNode(dd)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Restrict(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer cube)\n{\n\treturn ptr_to_jlong(DD_Restrict(ddman, jlong_to_DdNode(dd), jlong_to_DdNode(cube)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1ITE(JNIEnv *env, jclass cls, jlong __jlongpointer dd1, jlong __jlongpointer dd2, jlong __jlongpointer dd3)\n{\n\treturn ptr_to_jlong(DD_ITE(ddman, jlong_to_DdNode(dd1), jlong_to_DdNode(dd2), jlong_to_DdNode(dd3)));\n}\n\n//==============================================================================\n//\n//\tWrapper functions for dd_vars\n//\t\n//==============================================================================\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1PermuteVariables(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer old_vars, jlong __jlongpointer new_vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_PermuteVariables(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(old_vars), jlong_to_DdNode_array(new_vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1SwapVariables(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer old_vars, jlong __jlongpointer new_vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_SwapVariables(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(old_vars), jlong_to_DdNode_array(new_vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1VariablesGreaterThan(JNIEnv *env, jclass cls, jlong __jlongpointer x_vars, jlong __jlongpointer y_vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_VariablesGreaterThan(ddman, jlong_to_DdNode_array(x_vars), jlong_to_DdNode_array(y_vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1VariablesGreaterThanEquals(JNIEnv *env, jclass cls, jlong __jlongpointer x_vars, jlong __jlongpointer y_vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_VariablesGreaterThanEquals(ddman, jlong_to_DdNode_array(x_vars), jlong_to_DdNode_array(y_vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1VariablesLessThan(JNIEnv *env, jclass cls, jlong __jlongpointer x_vars, jlong __jlongpointer y_vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_VariablesLessThan(ddman, jlong_to_DdNode_array(x_vars), jlong_to_DdNode_array(y_vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1VariablesLessThanEquals(JNIEnv *env, jclass cls, jlong __jlongpointer x_vars, jlong __jlongpointer y_vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_VariablesLessThanEquals(ddman, jlong_to_DdNode_array(x_vars), jlong_to_DdNode_array(y_vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1VariablesEquals(JNIEnv *env, jclass cls, jlong __jlongpointer x_vars, jlong __jlongpointer y_vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_VariablesEquals(ddman, jlong_to_DdNode_array(x_vars), jlong_to_DdNode_array(y_vars), num_vars));\n}\n\n//==============================================================================\n//\n//\tWrapper functions for dd_abstr\n//\t\n//==============================================================================\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1ThereExists(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_ThereExists(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1ForAll(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_ForAll(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1SumAbstract(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_SumAbstract(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1ProductAbstract(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_ProductAbstract(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1MinAbstract(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_MinAbstract(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1MaxAbstract(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_MaxAbstract(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars));\n}\n\n//==============================================================================\n//\n//\tWrapper functions for dd_term\n//\t\n//==============================================================================\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1GreaterThan(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jdouble threshold)\n{\n\treturn ptr_to_jlong(DD_GreaterThan(ddman, jlong_to_DdNode(dd), threshold));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1GreaterThanEquals(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jdouble threshold)\n{\n\treturn ptr_to_jlong(DD_GreaterThanEquals(ddman, jlong_to_DdNode(dd), threshold));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1LessThan(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jdouble threshold)\n{\n\treturn ptr_to_jlong(DD_LessThan(ddman, jlong_to_DdNode(dd), threshold));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1LessThanEquals(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jdouble threshold)\n{\n\treturn ptr_to_jlong(DD_LessThanEquals(ddman, jlong_to_DdNode(dd), threshold));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Equals(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jdouble value)\n{\n\treturn ptr_to_jlong(DD_Equals(ddman, jlong_to_DdNode(dd), value));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Interval(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jdouble lower, jdouble upper)\n{\n\treturn ptr_to_jlong(DD_Interval(ddman, jlong_to_DdNode(dd), lower, upper));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1RoundOff(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jint places)\n{\n\treturn ptr_to_jlong(DD_RoundOff(ddman, jlong_to_DdNode(dd), places));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jboolean JNICALL Java_jdd_JDD_DD_1EqualSupNorm(JNIEnv *env, jclass cls, jlong __jlongpointer dd1, jlong __jlongpointer dd2, jdouble epsilon)\n{\n\treturn DD_EqualSupNorm(ddman, jlong_to_DdNode(dd1), jlong_to_DdNode(dd2), epsilon);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1FindMin(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn DD_FindMin(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1FindMinPositive(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn DD_FindMinPositive(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1FindMax(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn DD_FindMax(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1FindMaxFinite(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn DD_FindMaxFinite(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1RestrictToFirst(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_RestrictToFirst(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jboolean JNICALL Java_jdd_JDD_DD_1IsZeroOneMTBDD(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn DD_IsZeroOneMTBDD(ddman, jlong_to_DdNode(dd));\n}\n\n\n//==============================================================================\n//\n//\tWrapper functions for dd_info\n//\t\n//==============================================================================\n\nJNIEXPORT jint JNICALL Java_jdd_JDD_DD_1GetNumNodes(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn DD_GetNumNodes(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jint JNICALL Java_jdd_JDD_DD_1GetNumTerminals(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn DD_GetNumTerminals(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1GetNumMinterms(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jint num_vars)\n{\n\treturn DD_GetNumMinterms(ddman, jlong_to_DdNode(dd), num_vars);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1GetNumPaths(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn DD_GetNumPaths(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintInfo(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jint num_vars)\n{\n\tDD_PrintInfo(ddman, jlong_to_DdNode(dd), num_vars);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintInfoBrief(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jint num_vars)\n{\n\tDD_PrintInfoBrief(ddman, jlong_to_DdNode(dd), num_vars);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintSupport(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\tDD_PrintSupport(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintSupportNames(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jobject var_names)\n{\n\t// If no var names passed in, don't use them\n\tif (!var_names) {\n\t\tDD_PrintSupport(ddman, jlong_to_DdNode(dd));\n\t}\n\t// Otherwise, need to convert Java array to C array first\n\telse {\n\t\tint i;\n\t\tjint size;\n\t\tjclass vn_cls;\n\t\tjmethodID vn_mid;\n\t\tconst char **names;\n\t\tjstring *names_jstrings;\n\t\t// get size of vector of names\n\t\tvn_cls = env->GetObjectClass(var_names);\n\t\tvn_mid = env->GetMethodID(vn_cls, \"size\", \"()I\");\n\t\tif (vn_mid == 0) {\n\t\t\treturn;\n\t\t}\n\t\tsize = env->CallIntMethod(var_names,vn_mid);\n\t\t// put names from vector into array\n\t\tnames = new const char*[size];\n\t\tnames_jstrings = new jstring[size];\n\t\tvn_mid = env->GetMethodID(vn_cls, \"get\", \"(I)Ljava/lang/Object;\");\n\t\tif (vn_mid == 0) {\n\t\t\treturn;\n\t\t}\n\t\tfor (i = 0; i < size; i++) {\n\t\t\tnames_jstrings[i] = (jstring)env->CallObjectMethod(var_names, vn_mid, i);\n\t\t\tnames[i] = env->GetStringUTFChars(names_jstrings[i], 0);\n\t\t}\n\t\t// call the function\n\t\tDD_PrintSupportNames(ddman, jlong_to_DdNode(dd), (char **)names);\n\t\t// release memory\n\t\tfor (i = 0; i < size; i++) {\n\t\t\tenv->ReleaseStringUTFChars(names_jstrings[i], names[i]);\n\t\t}\n\t\tdelete[] names;\n\t\tdelete[] names_jstrings;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong JNICALL Java_jdd_JDD_DD_1GetSupport(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn ptr_to_jlong(DD_GetSupport(ddman, jlong_to_DdNode(dd)));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintTerminals(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\tDD_PrintTerminals(ddman, jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintTerminalsAndNumbers(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jint num_vars)\n{\n\tDD_PrintTerminalsAndNumbers(ddman, jlong_to_DdNode(dd), num_vars);\n}\n\n//==============================================================================\n//\n//\tWrapper functions for dd_matrix\n//\t\n//==============================================================================\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1SetVectorElement(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars, jlong index, jdouble value)\n{\n\treturn ptr_to_jlong(DD_SetVectorElement(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars, index, value));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1SetMatrixElement(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer rvars, jint num_rvars, jlong __jlongpointer cvars, jint num_cvars, jlong rindex, jlong cindex, jdouble value)\n{\n\treturn ptr_to_jlong(DD_SetMatrixElement(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(rvars), num_rvars, jlong_to_DdNode_array(cvars), num_cvars, rindex, cindex, value));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Set3DMatrixElement(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer rvars, jint num_rvars, jlong __jlongpointer cvars, jint num_cvars, jlong __jlongpointer lvars, jint num_lvars, jlong rindex, jlong cindex, jlong lindex, jdouble value)\n{\n\treturn ptr_to_jlong(DD_Set3DMatrixElement(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(rvars), num_rvars, jlong_to_DdNode_array(cvars), num_cvars, jlong_to_DdNode_array(lvars), num_lvars, rindex, cindex, lindex, value));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jdouble JNICALL Java_jdd_JDD_DD_1GetVectorElement(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars, jlong index)\n{\n\treturn DD_GetVectorElement(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars, index);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Identity(JNIEnv *env, jclass cls, jlong __jlongpointer rvars, jlong __jlongpointer cvars, jint num_vars)\n{\n\treturn ptr_to_jlong(DD_Identity(ddman, jlong_to_DdNode_array(rvars), jlong_to_DdNode_array(cvars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1Transpose(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer rvars, jlong __jlongpointer cvars, jint num_vars, jint lvars, jint num_lvars)\n{\n\treturn ptr_to_jlong(DD_Transpose(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(rvars), jlong_to_DdNode_array(cvars), num_vars));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDD_DD_1MatrixMultiply(JNIEnv *env, jclass cls, jlong __jlongpointer dd1, jlong __jlongpointer dd2, jlong __jlongpointer vars, jint num_vars, jint method)\n{\n\treturn ptr_to_jlong(DD_MatrixMultiply(ddman, jlong_to_DdNode(dd1), jlong_to_DdNode(dd2), jlong_to_DdNode_array(vars), num_vars, method));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintVector(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer vars, jint num_vars, jint acc)\n{\n\tDD_PrintVector(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(vars), num_vars, acc);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintMatrix(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer rvars, jint num_rvars, jlong __jlongpointer cvars, jint num_cvars, jint acc)\n{\n\tDD_PrintMatrix(ddman, jlong_to_DdNode(dd), jlong_to_DdNode_array(rvars), num_rvars, jlong_to_DdNode_array(cvars), num_cvars, acc);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1PrintVectorFiltered(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer filter, jlong __jlongpointer vars, jint num_vars, jint acc)\n{\n\tDD_PrintVectorFiltered(ddman, jlong_to_DdNode(dd), jlong_to_DdNode(filter), jlong_to_DdNode_array(vars), num_vars, acc);\n}\n\n//==============================================================================\n//\n//\tWrapper functions for dd_export\n//\t\n//==============================================================================\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportDDToDotFile(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jstring filename)\n{\n\tconst char *str = env->GetStringUTFChars(filename, 0);\n\tDD_ExportDDToDotFile(ddman, jlong_to_DdNode(dd), (char *)str);\n\tenv->ReleaseStringUTFChars(filename, str);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportDDToDotFileLabelled(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jstring filename, jobject var_names)\n{\n\tint i;\n\tjint size;\n\tjclass vn_cls;\n\tjmethodID vn_mid;\n\tconst char **names;\n\tjstring *names_strings;\n\tconst char *filenamestr;\n\n\t// get size of vector of names\n\tvn_cls = env->GetObjectClass(var_names);\n\tvn_mid = env->GetMethodID(vn_cls, \"size\", \"()I\");\n\tif (vn_mid == 0) {\n\t\treturn;\n\t}\n\tsize = env->CallIntMethod(var_names,vn_mid);\n\t// put names from vector into array\n\tnames = new const char*[size];\n\tnames_strings = new jstring[size];\n\tvn_mid = env->GetMethodID(vn_cls, \"elementAt\", \"(I)Ljava/lang/Object;\");\n\tif (vn_mid == 0) {\n\t\treturn;\n\t}\n\tfor (i = 0; i < size; i++) {\n\t\tnames_strings[i] = (jstring)env->CallObjectMethod(var_names, vn_mid, i);\n\t\tnames[i] = env->GetStringUTFChars(names_strings[i], 0);\n\t}\n\n\t// get filename string\n\tfilenamestr = env->GetStringUTFChars(filename, 0);\n\n\t// call dd_export... function\n\tDD_ExportDDToDotFileLabelled(ddman, jlong_to_DdNode(dd), (char *)filenamestr, (char **)names);\n\n\t// release memory\n\tfor (i = 0; i < size; i++) {\n\t\tenv->ReleaseStringUTFChars(names_strings[i], names[i]);\n\t}\n\tenv->ReleaseStringUTFChars(filename, filenamestr);\n\tdelete[] names;\n\tdelete[] names_strings;\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportMatrixToPPFile(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer rvars, jint num_rvars, jlong __jlongpointer cvars, jint num_cvars, jstring filename)\n{\n\tconst char *str = env->GetStringUTFChars(filename, 0);\n\tDD_ExportMatrixToPPFile(\n\t\tddman, jlong_to_DdNode(dd),\n\t\tjlong_to_DdNode_array(rvars), num_rvars,\n\t\tjlong_to_DdNode_array(cvars), num_cvars,\n\t\t(char *)str\n\t);\n\tenv->ReleaseStringUTFChars(filename, str);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1Export3dMatrixToPPFile(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer rvars, jint num_rvars, jlong __jlongpointer cvars, jint num_cvars, jlong __jlongpointer nvars, jint num_nvars, jstring filename)\n{\n\tconst char *str = env->GetStringUTFChars(filename, 0);\n\tDD_Export3dMatrixToPPFile(\n\t\tddman, jlong_to_DdNode(dd),\n\t\tjlong_to_DdNode_array(rvars), num_rvars,\n\t\tjlong_to_DdNode_array(cvars), num_cvars,\n\t\tjlong_to_DdNode_array(nvars), num_nvars,\n\t\t(char *)str\n\t);\n\tenv->ReleaseStringUTFChars(filename, str);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportMatrixToMatlabFile(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer rvars, jint num_rvars, jlong __jlongpointer cvars, jint num_cvars, jstring name, jstring filename)\n{\n\tconst char *str1 = env->GetStringUTFChars(name, 0);\n\tconst char *str2 = env->GetStringUTFChars(filename, 0);\n\tDD_ExportMatrixToMatlabFile(\n\t\tddman, jlong_to_DdNode(dd),\n\t\tjlong_to_DdNode_array(rvars), num_rvars,\n\t\tjlong_to_DdNode_array(cvars), num_cvars,\n\t\t(char *)str1, (char *)str2\n\t);\n\tenv->ReleaseStringUTFChars(name, str1);\n\tenv->ReleaseStringUTFChars(filename, str2);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDD_DD_1ExportMatrixToSpyFile(JNIEnv *env, jclass cls, jlong __jlongpointer dd, jlong __jlongpointer rvars, jint num_rvars, jlong __jlongpointer cvars, jint num_cvars, jint depth, jstring filename)\n{\n\tconst char *str = env->GetStringUTFChars(filename, 0);\n\tDD_ExportMatrixToSpyFile(\n\t\tddman, jlong_to_DdNode(dd),\n\t\tjlong_to_DdNode_array(rvars), num_rvars,\n\t\tjlong_to_DdNode_array(cvars), num_cvars,\n\t\tdepth, (char *)str\n\t);\n\tenv->ReleaseStringUTFChars(filename, str);\n}\n\n//==============================================================================\n//\n//\tFunctions for JDDNode class\n//\t\n//==============================================================================\n\nJNIEXPORT jboolean JNICALL Java_jdd_JDDNode_DDN_1IsConstant(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn Cudd_IsConstant(jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jint JNICALL Java_jdd_JDDNode_DDN_1GetIndex(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn Cudd_NodeReadIndex(jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jdouble JNICALL Java_jdd_JDDNode_DDN_1GetValue(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn Cudd_V(jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDDNode_DDN_1GetThen(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\tDdNode *node = jlong_to_DdNode(dd);\n\tif (Cudd_IsConstant(node)) return ptr_to_jlong(NULL);\n\treturn ptr_to_jlong(Cudd_T(node));\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDDNode_DDN_1GetElse(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\tDdNode *node = jlong_to_DdNode(dd);\n\tif (Cudd_IsConstant(node)) return ptr_to_jlong(NULL);\n\treturn ptr_to_jlong(Cudd_E(node));\n}\n\n//==============================================================================\n//\n//\tFunctions for JDDVars class\n//\t\n//==============================================================================\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_jdd_JDDVars_DDV_1BuildArray(JNIEnv *env, jobject obj)\n{\n\tjclass cls;\n\tjmethodID mid;\n\tDdNode **arr;\n\tint i, n;\n\t\n\tcls = env->GetObjectClass(obj);\n\tmid = env->GetMethodID(cls, \"getNumVars\", \"()I\");\n\tif (mid == 0) {\n\t\treturn 0;\n\t}\n\tn = env->CallIntMethod(obj, mid);\n\tarr = new DdNode*[n];\n\tmid = env->GetMethodID(cls, \"getVarPtr\", \"(I)J\");\n\tif (mid == 0) {\n\t\tdelete[] arr;\n\t\treturn 0;\n\t}\n\tfor (i = 0; i < n; i++) {\n\t\tarr[i] = jlong_to_DdNode(env->CallLongMethod(obj, mid, i));\n\t}\n\t\n\treturn ptr_to_jlong(arr);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_jdd_JDDVars_DDV_1FreeArray(JNIEnv *env, jobject obj, jlong __jlongpointer arr)\n{\n\tdelete[] jlong_to_DdNode_array(arr);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jint JNICALL Java_jdd_JDDVars_DDV_1GetIndex(JNIEnv *env, jobject obj, jlong __jlongpointer dd)\n{\n\treturn Cudd_NodeReadIndex(jlong_to_DdNode(dd));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_jdd_JDD_DebugJDD_1GetRefCount(JNIEnv *env, jclass cls, jlong __jlongpointer dd)\n{\n\treturn (jlong_to_DdNode(dd))->ref;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlongArray JNICALL Java_jdd_JDD_DebugJDD_1GetExternalRefCounts(JNIEnv *env, jclass cls)\n{\n\t// get external reference counts and return as a long[] Java array\n\t// the entries of the array will be alternating ptr / count values\n\tstd::map<DdNode*, int> external_refs;\n\tDD_GetExternalRefCounts(ddman, external_refs);\n\tstd::size_t v_size = 2 * external_refs.size();\n\n\tjlong* v = new jlong[v_size];\n\tstd::size_t i = 0;\n\tfor (std::map<DdNode*,int>::iterator it = external_refs.begin();\n\t     it != external_refs.end();\n\t     ++it) {\n\t\tDdNode *node = it->first;\n\t\tint refs = it->second;\n\n\t\tv[i++] = ptr_to_jlong(node);\n\t\tv[i++] = refs;\n\t}\n\n\t// printf(\"v_size = %lu\\n\", v_size);\n\tjlongArray result = env->NewLongArray(v_size);\n\tenv->SetLongArrayRegion(result, 0, v_size, v);\n\tdelete[] v;\n\n\treturn result;\n}\n//------------------------------------------------------------------------------\n\nJNIEXPORT jboolean JNICALL Java_jdd_JDD_DD_1GetErrorFlag(JNIEnv *env, jclass cls)\n{\n\treturn DD_GetErrorFlag(ddman);\n}\n"
  },
  {
    "path": "prism/src/jdd/JDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t* Christian von Essen <christian.vonessen@imag.fr> (VERIMAG)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jdd;\n\nimport java.util.*;\n\nimport prism.PrismLog;\n\npublic class JDD\n{\n\t// dd library functions\n\tpublic static native long GetCUDDManager();\n\t// dd\n\tprivate static native void DD_SetOutputStream(long fp);\n\tprivate static native long DD_GetOutputStream();\n\t// dd_cudd\n\tprivate static native void DD_InitialiseCUDD();\n\tprivate static native void DD_InitialiseCUDD(long max_mem, double epsilon);\n\tprivate static native void DD_SetCUDDMaxMem(long max_mem);\n\tprivate static native void DD_SetCUDDEpsilon(double epsilon);\n\tprivate static native void DD_CloseDownCUDD(boolean check);\n\tstatic native void DD_Ref(long dd);\n\tstatic native void DD_Deref(long dd);\n\tprivate static native void DD_PrintCacheInfo();\n\tprivate static native boolean DD_GetErrorFlag();\n\t// dd_basics\n\tprivate static native long DD_Create();\n\tprivate static native long DD_Constant(double value);\n\tprivate static native long DD_PlusInfinity();\n\tprivate static native long DD_MinusInfinity();\n\tprivate static native long DD_Var(int i);\n\tprivate static native long DD_Not(long dd);\n\tprivate static native long DD_Or(long dd1, long dd2);\n\tprivate static native long DD_And(long dd1, long dd2);\n\tprivate static native long DD_Xor(long dd1, long dd2);\n\tprivate static native long DD_Implies(long dd1, long dd2);\n\tprivate static native long DD_Apply(int op, long dd1, long dd2);\n\tprivate static native long DD_MonadicApply(int op, long dd);\n\tprivate static native long DD_Restrict(long dd, long cube);\n\tprivate static native long DD_ITE(long dd1, long dd2, long dd3);\n\t// dd_vars\n\tprivate static native long DD_PermuteVariables(long dd, long old_vars, long new_vars, int num_vars);\n\tprivate static native long DD_SwapVariables(long dd, long old_vars, long new_vars, int num_vars);\n\tprivate static native long DD_VariablesGreaterThan(long x_vars, long y_vars, int num_vars);\n\tprivate static native long DD_VariablesGreaterThanEquals(long x_vars, long y_vars, int num_vars);\n\tprivate static native long DD_VariablesLessThan(long x_vars, long y_vars, int num_vars);\n\tprivate static native long DD_VariablesLessThanEquals(long x_vars, long y_vars, int num_vars);\n\tprivate static native long DD_VariablesEquals(long x_vars, long y_vars, int num_vars);\n\t// dd_abstr\n\tprivate static native long DD_ThereExists(long dd, long vars, int num_vars);\n\tprivate static native long DD_ForAll(long dd, long vars, int num_vars);\n\tprivate static native long DD_SumAbstract(long dd, long vars, int num_vars);\n\tprivate static native long DD_ProductAbstract(long dd, long vars, int num_vars);\n\tprivate static native long DD_MinAbstract(long dd, long vars, int num_vars);\n\tprivate static native long DD_MaxAbstract(long dd, long vars, int num_vars);\n\t// dd_term\n\tprivate static native long DD_GreaterThan(long dd, double threshold);\n\tprivate static native long DD_GreaterThanEquals(long dd, double threshold);\n\tprivate static native long DD_LessThan(long dd, double threshold);\n\tprivate static native long DD_LessThanEquals(long dd, double threshold);\n\tprivate static native long DD_Equals(long dd, double value);\n\tprivate static native long DD_Interval(long dd, double lower, double upper);\n\tprivate static native long DD_RoundOff(long dd, int places);\n\tprivate static native boolean DD_EqualSupNorm(long dd1, long dd2, double epsilon);\n\tprivate static native double DD_FindMin(long dd);\n\tprivate static native double DD_FindMinPositive(long dd);\n\tprivate static native double DD_FindMax(long dd);\n\tprivate static native double DD_FindMaxFinite(long dd);\n\tprivate static native long DD_RestrictToFirst(long dd, long vars, int num_vars);\n\tprivate static native boolean DD_IsZeroOneMTBDD(long dd);\n\t// dd_info\n\tprivate static native int DD_GetNumNodes(long dd);\n\tprivate static native int DD_GetNumTerminals(long dd);\n\tprivate static native double DD_GetNumMinterms(long dd, int num_vars);\n\tprivate static native double DD_GetNumPaths(long dd);\n\tprivate static native void DD_PrintInfo(long dd, int num_vars);\n\tprivate static native void DD_PrintInfoBrief(long dd, int num_vars);\n\tprivate static native void DD_PrintSupport(long dd);\n\tprivate static native void DD_PrintSupportNames(long dd, List<String> var_names);\n\tprivate static native long DD_GetSupport(long dd);\n\tprivate static native void DD_PrintTerminals(long dd);\n\tprivate static native void DD_PrintTerminalsAndNumbers(long dd, int num_vars);\n\t// dd_matrix\n\tprivate static native long DD_SetVectorElement(long dd, long vars, int num_vars, long index, double value);\n\tprivate static native long DD_SetMatrixElement(long dd, long rvars, int num_rvars, long cvars, int num_cvars, long rindex, long cindex, double value);\n\tprivate static native long DD_Set3DMatrixElement(long dd, long rvars, int num_rvars, long cvars, int num_cvars, long lvars, int num_lvars, long rindex, long cindex, long lindex, double value);\n\tprivate static native double DD_GetVectorElement(long dd, long vars, int num_vars, long index);\n\tprivate static native long DD_Identity(long rvars, long cvars, int num_vars);\n\tprivate static native long DD_Transpose(long dd, long rvars, long cvars, int num_vars);\n\tprivate static native long DD_MatrixMultiply(long dd1, long dd2, long vars, int num_vars, int method);\n\tprivate static native void DD_PrintVector(long dd, long vars, int num_vars, int accuracy);\n\tprivate static native void DD_PrintMatrix(long dd, long rvars, int num_rvars, long cvars, int num_cvars, int accuracy);\n\tprivate static native void DD_PrintVectorFiltered(long dd, long filter, long vars, int num_vars, int accuracy);\n\t// dd_export\n\tprivate static native void DD_ExportDDToDotFile(long dd, String filename);\n\tprivate static native void DD_ExportDDToDotFileLabelled(long dd, String filename, List<String> var_names);\n\tprivate static native void DD_ExportMatrixToPPFile(long dd, long rvars, int num_rvars, long cvars, int num_cvars, String filename);\n\tprivate static native void DD_Export3dMatrixToPPFile(long dd, long rvars, int num_rvars, long cvars, int num_cvars, long nvars, int num_nvars, String filename);\n\tprivate static native void DD_ExportMatrixToMatlabFile(long dd, long rvars, int num_rvars, long cvars, int num_cvars, String name, String filename);\n\tprivate static native void DD_ExportMatrixToSpyFile(long dd, long rvars, int num_rvars, long cvars, int num_cvars, int depth, String filename);\n\n\t// helpers for DebugJDD, package visibility\n\tstatic native int DebugJDD_GetRefCount(long dd);\n\tstatic native long[] DebugJDD_GetExternalRefCounts();\n\n\t/**\n\t * An exception indicating that CUDD ran out of memory or that another internal error\n\t * occurred.\n\t * <br>\n\t * This exception is thrown by ptrToNode if a NULL pointer is returned by one of the native\n\t * DD methods. It is generally not safe to use the CUDD library after this error occurred,\n\t * so the program should quit as soon as feasible.\n\t */\n\tpublic static class CuddOutOfMemoryException extends RuntimeException {\n\t\tprivate static final long serialVersionUID = -3094099053041270477L;\n\n\t\t/** Constructor */\n\t\tCuddOutOfMemoryException() {\n\t\t\tsuper(\"Out of memory (or other internal error) in the CUDD library\");\n\t\t}\n\t}\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t// apply operations\n\tpublic static final int PLUS = 1;\n\tpublic static final int MINUS = 2;\n\tpublic static final int TIMES = 3;\n\tpublic static final int DIVIDE = 4;\n\tpublic static final int MIN = 5;\n\tpublic static final int MAX = 6;\n\tpublic static final int EQUALS = 7;\n\tpublic static final int NOTEQUALS = 8;\n\tpublic static final int GREATERTHAN = 9;\n\tpublic static final int GREATERTHANEQUALS = 10;\n\tpublic static final int LESSTHAN = 11;\n\tpublic static final int LESSTHANEQUALS = 12;\n\tpublic static final int FLOOR = 13;\n\tpublic static final int CEIL = 14;\n\tpublic static final int POW = 15;\n\tpublic static final int MOD = 16;\n\tpublic static final int LOGXY = 17;\n\n\t// print vector/matrix accuracy\n\tpublic static final int ZERO_ONE = 1;\n\tpublic static final int LOW = 2;\n\tpublic static final int NORMAL = 3;\n\tpublic static final int HIGH = 4;\n\tpublic static final int LIST = 5;\n\t\n\t// matrix multiply methods\n\tpublic static final int CMU = 1;\n\tpublic static final int BOULDER = 2;\n\t\n\t// constant dds\n\tpublic static JDDNode ZERO;\n\tpublic static JDDNode ONE;\n\tpublic static JDDNode PLUS_INFINITY;\n\tpublic static JDDNode MINUS_INFINITY;\n\t\t\n\t// wrapper methods for dd\n\n\t/**\n\t * Set the default output stream for DD (native) code.\n\t * This mainly used for printing diagnostic/error messages.\n\t * @param fp C++ file pointer (e.g., to stdout or a file), cast to a long.\n\t */\n\tpublic static void SetOutputStream(long fp)\n\t{\n\t\tDD_SetOutputStream(fp);\n\t}\n\n\t/**\n\t * Get the default output stream for DD (native) code.\n\t * This mainly used for printing diagnostic/error messages.\n\t * It is a C++ file pointer (e.g., to stdout or a file), cast to a long.\n\t */\n\tpublic static long GetOutputStream()\n\t{\n\t\treturn DD_GetOutputStream();\n\t}\n\t\n\t// wrapper methods for dd_cudd\n\n\t/**\n\t * initialise cudd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void InitialiseCUDD()\n\t{\n\t\tDD_InitialiseCUDD();\n\t\tZERO = Constant(0);\n\t\tONE = Constant(1);\n\t\tPLUS_INFINITY = JDD.PlusInfinity();\n\t\tMINUS_INFINITY = JDD.MinusInfinity();\n\t}\n\t\t\n\t/**\n\t * initialise cudd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void InitialiseCUDD(long max_mem, double epsilon)\n\t{\n\t\tDD_InitialiseCUDD(max_mem, epsilon);\n\t\tZERO = Constant(0);\n\t\tONE = Constant(1);\n\t\tPLUS_INFINITY = JDD.PlusInfinity();\n\t\tMINUS_INFINITY = JDD.MinusInfinity();\n\t}\n\t\t\n\t/**\n\t * set cudd max memory\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void SetCUDDMaxMem(long max_mem)\n\t{\n\t\tDD_SetCUDDMaxMem(max_mem);\n\t}\n\t\t\n\t/**\n\t * set cudd epsilon\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void SetCUDDEpsilon(double epsilon)\n\t{\n\t\tDD_SetCUDDEpsilon(epsilon);\n\t}\n\t\t\n\t/**\n\t * close down cudd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void CloseDownCUDD() { CloseDownCUDD(true); }\n\tpublic static void CloseDownCUDD(boolean check)\n\t{\n\t\tDeref(ZERO);\n\t\tDeref(ONE);\n\t\tDeref(PLUS_INFINITY);\n\t\tDeref(MINUS_INFINITY);\n\t\tif (jdd.DebugJDD.debugEnabled)\n\t\t\tDebugJDD.endLifeCycle();\n\t\tDD_CloseDownCUDD(check);\n\t}\n\t\n\t/**\n\t * reference dd\n\t * <br>[ REFS: dd, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void Ref(JDDNode dd)\n\t{\n\t\tlong ptr = dd.ptr();\n\t\t// For robustness, catch NULL pointer\n\t\t// In general, this should not happen,\n\t\t// as constructing a JDDNode with NULL\n\t\t// pointer should not happen...\n\t\tif (ptr == 0) {\n\t\t\tthrow new CuddOutOfMemoryException();\n\t\t}\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.Ref(dd);\n\t\t} else {\n\t\t\tDD_Ref(ptr);\n\t\t}\n\t}\n\t\n\t/**\n\t * dereference dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: dd ]\n\t */\n\tpublic static void Deref(JDDNode dd)\n\t{\n\t\tlong ptr = dd.ptr();\n\t\t// For robustness, catch NULL pointer\n\t\t// In general, this should not happen,\n\t\t// as constructing a JDDNode with NULL\n\t\t// pointer should not happen...\n\t\tif (ptr == 0) {\n\t\t\tthrow new CuddOutOfMemoryException();\n\t\t}\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.Deref(dd);\n\t\t} else {\n\t\t\tDD_Deref(ptr);\n\t\t}\n\t}\n\n\t/**\n\t * Dereference dds, multi-argument variant.\n\t * The dds have to be non-{@code null}.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>all argument dds</i> ]\n\t */\n\tpublic static void Deref(JDDNode... dds)\n\t{\n\t\tfor (JDDNode d : dds) {\n\t\t\tJDD.Deref(d);\n\t\t}\n\t}\n\n\t/**\n\t * Dereference dd, if the JDDNode is not {@code null}.\n\t * @param dd a JDDNode (may be {@code null})\n\t * <br>[ REFS: <i>none</i>, DEREFS: dd ]\n\t */\n\tpublic static void DerefNonNull(JDDNode dd)\n\t{\n\t\tif (dd != null)\n\t\t\tJDD.Deref(dd);\n\t}\n\n\t/**\n\t * Dereference dds (if the given JDDNode is not {@code null}), multi-argument variant.\n\t * @param dds a list of JDDNode (some of which may be {@code null})\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>all argument dds</i> ]\n\t */\n\tpublic static void DerefNonNull(JDDNode... dds)\n\t{\n\t\tfor (JDDNode d : dds) {\n\t\t\tJDD.DerefNonNull(d);\n\t\t}\n\t}\n\n\t/**\n\t * Dereference array of JDDNodes, by dereferencing all (non-null) elements.\n\t * <br>[ REFS: <i>none</i>, DEREFS: all elements of dds ]\n\t * @param dds the array of JDDNodes\n\t * @param n the expected length of the array (for detecting problems with refactoring)\n\t */\n\tpublic static void DerefArray(JDDNode[] dds, int n)\n\t{\n\t\tif (n != dds.length) {\n\t\t\tthrow new RuntimeException(\"Mismatch in length of dd array and expected length!\");\n\t\t}\n\t\tfor (JDDNode dd : dds) {\n\t\t\tJDD.DerefNonNull(dd);\n\t\t}\n\t}\n\n\t/**\n\t * Dereference array of JDDNodes, by dereferencing all (non-null) elements.\n\t * This is a convenience wrapper around JDD.DerefArray that results in a no-op if {@code dds == null}.\n\t * <br>[ REFS: <i>none</i>, DEREFS: all elements of dds ]\n\t * @param dds the array of JDDNodes (may be {@code null}.\n\t */\n\tpublic static void DerefArrayNonNull(JDDNode[] dds)\n\t{\n\t\tif (dds != null)\n\t\t\tDerefArray(dds, dds.length);\n\t}\n\n\t/**\n\t * Dereference array of JDDNodes, by dereferencing all (non-null) elements.\n\t * This is a convenience wrapper around JDD.DerefArray that results in a no-op if {@code dds == null}.\n\t * <br>[ REFS: <i>none</i>, DEREFS: all elements of dds ]\n\t * @param dds the array of JDDNodes (may be {@code null}.\n\t * @param n the expected length of the array (for detecting problems with refactoring)\n\t */\n\t\n\tpublic static void DerefArrayNonNull(JDDNode[] dds, int n)\n\t{\n\t\tif (dds != null)\n\t\t\tDerefArray(dds, n);\n\t}\n\n\t/**\n\t * print cudd cache info\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintCacheInfo()\n\t{\n\t\tDD_PrintCacheInfo();\n\t}\n\t\n\t// wrapper methods for dd_basics\n\n\t/**\n\t * create new (zero) dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode Create()\n\t{\n\t\treturn ptrToNode(DD_Create());\n\t}\n\t\n\t/**\n\t * create new constant dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode Constant(double value)\n\t{\n\t\tif (Double.isInfinite(value))\n\t\t\treturn value > 0 ? JDD.PlusInfinity() : JDD.MinusInfinity();\n\t\telse\n\t\t\treturn ptrToNode(DD_Constant(value));\n\t}\n\t\t\n\t/**\n\t * create new constant (plus infinity)\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode PlusInfinity()\n\t{\n\t\treturn ptrToNode(DD_PlusInfinity());\n\t}\n\t\n\t/**\n\t * create new constant (minus infinity)\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode MinusInfinity()\n\t{\n\t\treturn ptrToNode(DD_MinusInfinity());\n\t}\n\t\n\t/**\n\t * create new variable dd (1 if var i is true, 0 if not)\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode Var(int i)\n\t{\n\t\treturn ptrToNode(DD_Var(i));\n\t}\n\t\n\t/**\n\t * not of dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode Not(JDDNode dd)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd);\n\t\t}\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_Not(dd.ptr()));\n\t}\n\t\n\t/**\n\t * or of dd1, dd2\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd1, dd2 ]\n\t */\n\tpublic static JDDNode Or(JDDNode dd1, JDDNode dd2)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd1);\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd2);\n\t\t}\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.DD_Method_Argument(dd1);\n\t\t\tDebugJDD.DD_Method_Argument(dd2);\n\t\t}\n\t\treturn ptrToNode(DD_Or(dd1.ptr(), dd2.ptr()));\n\t}\n\n\t/**\n\t * Multi-operand Or (0/1-MTBDD disjunction) operation.\n\t * Operands are processed from left-to-right.\n\t * <br>\n\t * Returns JDD.Constant(0) for empty argument list\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>all arguments</i> ]\n\t */\n\tpublic static JDDNode Or(JDDNode... nodes)\n\t{\n\t\tif (nodes.length == 0)\n\t\t\treturn JDD.Constant(0);\n\n\t\tJDDNode result = nodes[0];\n\t\tfor (int i = 1; i < nodes.length; i++) {\n\t\t\t// note: Java overloading rules ensure that fixed arity\n\t\t\t// methods take precedence. So, for two-operand Or,\n\t\t\t// the Or(JDDNode,JDDNode) method above is called and we don't\n\t\t\t// run into an infinite recursion\n\t\t\tresult = Or(result, nodes[i]);\n\t\t}\n\n\t\treturn result;\n\t}\n\t\n\t/**\n\t * and of dd1, dd2\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd1, dd2 ]\n\t */\n\tpublic static JDDNode And(JDDNode dd1, JDDNode dd2)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd1);\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd2);\n\t\t}\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.DD_Method_Argument(dd1);\n\t\t\tDebugJDD.DD_Method_Argument(dd2);\n\t\t}\n\t\t\t\n\t\treturn ptrToNode(DD_And(dd1.ptr(), dd2.ptr()));\n\t}\n\n\t/**\n\t * Multi-operand And (0/1-MTBDD conjunction) operation.\n\t * Operands are processed from left-to-right.\n\t * <br>\n\t * Returns JDD.Constant(1) for empty argument list\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>all arguments</i> ]\n\t */\n\tpublic static JDDNode And(JDDNode... nodes)\n\t{\n\t\tif (nodes.length == 0)\n\t\t\treturn JDD.Constant(1);\n\n\t\tJDDNode result = nodes[0];\n\t\tfor (int i = 1; i < nodes.length; i++) {\n\t\t\t// note: Java overloading rules ensure that fixed arity\n\t\t\t// methods take precedence. So, for two-operand And,\n\t\t\t// the And(JDDNode,JDDNode) method above is called and we don't\n\t\t\t// run into an infinite recursion\n\t\t\tresult = And(result, nodes[i]);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * xor of dd1, dd2\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd1, dd2 ]\n\t */\n\tpublic static JDDNode Xor(JDDNode dd1, JDDNode dd2)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd1);\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd2);\n\t\t}\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.DD_Method_Argument(dd1);\n\t\t\tDebugJDD.DD_Method_Argument(dd2);\n\t\t}\n\t\treturn ptrToNode(DD_Xor(dd1.ptr(), dd2.ptr()));\n\t}\n\t\n\t/**\n\t * implies of dd1, dd2\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd1, dd2 ]\n\t */\n\tpublic static JDDNode Implies(JDDNode dd1, JDDNode dd2)\n\t{\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.DD_Method_Argument(dd1);\n\t\t\tDebugJDD.DD_Method_Argument(dd2);\n\t\t}\n\t\treturn ptrToNode(DD_Implies(dd1.ptr(), dd2.ptr()));\n\t}\n\t\n\t/**\n\t * equivalence of dd1, dd2 (have to be 0/1-MTBDDs)\n\t * [ REFS: <i>result</i>, DEREFS: dd1, dd2 ]\n\t */\n\tpublic static JDDNode Equiv(JDDNode dd1, JDDNode dd2)\n\t{\n\t\treturn Not(Xor(dd1, dd2));\n\t}\n\t\n\t/**\n\t * generic apply operation\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd1, dd2 ]\n\t */\n\tpublic static JDDNode Apply(int op, JDDNode dd1, JDDNode dd2)\n\t{\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.DD_Method_Argument(dd1);\n\t\t\tDebugJDD.DD_Method_Argument(dd2);\n\t\t}\n\t\treturn ptrToNode(DD_Apply(op, dd1.ptr(), dd2.ptr()));\n\t}\n\n\t/**\n\t * Multi-operand Apply(JDD.TIMES) (multiplication) operation.\n\t * Operands are processed from left-to-right.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>all arguments</i> ]\n\t */\n\tpublic static JDDNode Times(JDDNode node, JDDNode... nodes) {\n\t\tJDDNode result = node;\n\t\tfor (JDDNode n : nodes) {\n\t\t\tresult = Apply(JDD.TIMES, result, n);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Multi-operand Apply(JDD.PLUS) (addition) operation.\n\t * Operands are processed from left-to-right.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>all arguments</i> ]\n\t */\n\tpublic static JDDNode Plus(JDDNode node, JDDNode... nodes) {\n\t\tJDDNode result = node;\n\t\tfor (JDDNode n : nodes) {\n\t\t\tresult = Apply(JDD.PLUS, result, n);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Multi-operand Apply(JDD.MAX) (maximum) operation.\n\t * Operands are processed from left-to-right.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>all arguments</i> ]\n\t */\n\tpublic static JDDNode Max(JDDNode node, JDDNode... nodes) {\n\t\tJDDNode result = node;\n\t\tfor (JDDNode n : nodes) {\n\t\t\tresult = Apply(JDD.MAX, result, n);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Multi-operand Apply(JDD.MIN) (minimum) operation.\n\t * Operands are processed from left-to-right.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>all arguments</i> ]\n\t */\n\tpublic static JDDNode Min(JDDNode node, JDDNode... nodes) {\n\t\tJDDNode result = node;\n\t\tfor (JDDNode n : nodes) {\n\t\t\tresult = Apply(JDD.MIN, result, n);\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * generic monadic apply operation\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode MonadicApply(int op, JDDNode dd)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_MonadicApply(op, dd.ptr()));\n\t}\n\t\n\t/**\n\t * restrict dd based on cube\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd, cube ]\n\t */\n\tpublic static JDDNode Restrict(JDDNode dd, JDDNode cube)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd);\n\t\t}\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\t\tDebugJDD.DD_Method_Argument(cube);\n\t\t}\n\t\treturn ptrToNode(DD_Restrict(dd.ptr(), cube.ptr()));\n\t}\n\t\n\t/**\n\t * ITE (if-then-else) operation\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd1, dd2, dd3 ]\n\t */\n\tpublic static JDDNode ITE(JDDNode dd1, JDDNode dd2, JDDNode dd3)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd1);\n\t\t}\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.DD_Method_Argument(dd1);\n\t\t\tDebugJDD.DD_Method_Argument(dd2);\n\t\t\tDebugJDD.DD_Method_Argument(dd3);\n\t\t}\n\t\treturn ptrToNode(DD_ITE(dd1.ptr(), dd2.ptr(), dd3.ptr()));\n\t}\n\t\t\n\t/**\n\t * Returns true if the two BDDs intersect (i.e. conjunction is non-empty).\n\t * [ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static boolean AreIntersecting(JDDNode dd1, JDDNode dd2)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd1);\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd2);\n\t\t}\n\t\tJDDNode tmp;\n\t\tboolean res;\n\t\tJDD.Ref(dd1);\n\t\tJDD.Ref(dd2);\n\t\ttmp = JDD.And(dd1, dd2);\n\t\tres = !tmp.equals(JDD.ZERO);\n\t\tJDD.Deref(tmp);\n\t\treturn res;\n\t}\n\t\n\t/**\n\t * Returns true if {@code dd1} is contained in {@code dd2}.\n\t * [ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static boolean IsContainedIn(JDDNode dd1, JDDNode dd2)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd1);\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd2);\n\t\t}\n\t\tJDDNode tmp;\n\t\tboolean res;\n\t\tJDD.Ref(dd1);\n\t\tJDD.Ref(dd2);\n\t\t/*tmp = JDD.Implies(dd1, dd2);\n\t\tres = tmp.equals(JDD.ONE);*/\n\t\ttmp = JDD.And(dd1, dd2);\n\t\tres = tmp.equals(dd1);\n\t\tJDD.Deref(tmp);\n\t\treturn res;\n\t}\n\t\n\t// wrapper methods for dd_vars\n\t\n\t/**\n\t * permute (-&gt;) variables in dd (cf. swap)\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode PermuteVariables(JDDNode dd, JDDVars old_vars, JDDVars new_vars)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_PermuteVariables(dd.ptr(), old_vars.array(), new_vars.array(), old_vars.n()));\n\t}\n\n\t/**\n\t * swap (&lt;-&gt;) variables in dd (cf. permute)\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode SwapVariables(JDDNode dd, JDDVars old_vars, JDDVars new_vars)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_SwapVariables(dd.ptr(), old_vars.array(), new_vars.array(), old_vars.n()));\n\t}\n\n\t/**\n\t * build x &gt; y for variables x, y\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode VariablesGreaterThan(JDDVars x_vars, JDDVars y_vars)\n\t{\n\t\treturn ptrToNode(DD_VariablesGreaterThan(x_vars.array(), y_vars.array(), x_vars.n()));\n\t}\n\n\t/**\n\t * build x &gt;= y for variables x, y\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode VariablesGreaterThanEquals(JDDVars x_vars, JDDVars y_vars)\n\t{\n\t\treturn ptrToNode(DD_VariablesGreaterThanEquals(x_vars.array(), y_vars.array(), x_vars.n()));\n\t}\n\n\t/**\n\t * build x &lt; y for variables x, y\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode VariablesLessThan(JDDVars x_vars, JDDVars y_vars)\n\t{\n\t\treturn ptrToNode(DD_VariablesLessThan(x_vars.array(), y_vars.array(), x_vars.n()));\n\t}\n\n\t/**\n\t * build x &lt;= y for variables x, y\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode VariablesLessThanEquals(JDDVars x_vars, JDDVars y_vars)\n\t{\n\t\treturn ptrToNode(DD_VariablesLessThanEquals(x_vars.array(), y_vars.array(), x_vars.n()));\n\t}\n\n\t/**\n\t * build x == y for variables x, y\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode VariablesEquals(JDDVars x_vars, JDDVars y_vars)\n\t{\n\t\treturn ptrToNode(DD_VariablesEquals(x_vars.array(), y_vars.array(), x_vars.n()));\n\t}\n\n\t// wrapper methods for dd_abstr\n\n\t/**\n\t * existential abstraction of vars from dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode ThereExists(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd);\n\t\t}\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_ThereExists(dd.ptr(), vars.array(), vars.n()));\n\t}\n\t\n\t/**\n\t * universal abstraction of vars from dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode ForAll(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd);\n\t\t}\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_ForAll(dd.ptr(), vars.array(), vars.n()));\n\t}\n\t\n\t/**\n\t * sum abstraction of vars from dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode SumAbstract(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_SumAbstract(dd.ptr(), vars.array(), vars.n()));\n\t}\n\t\n\t/**\n\t * product abstraction of vars from dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode ProductAbstract(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_ProductAbstract(dd.ptr(), vars.array(), vars.n()));\n\t}\n\t\n\t/**\n\t * min abstraction of vars from dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode MinAbstract(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_MinAbstract(dd.ptr(), vars.array(), vars.n()));\n\t}\n\t\n\t/**\n\t * max abstraction of vars from dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode MaxAbstract(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_MaxAbstract(dd.ptr(), vars.array(), vars.n()));\n\t}\n\t\n\t// wrapper methods for dd_term\n\n\t/**\n\t * converts dd to a 0-1 dd, based on the interval (threshold, +inf)\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode GreaterThan(JDDNode dd, double threshold)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_GreaterThan(dd.ptr(), threshold));\n\t}\n\t\n\t/**\n\t * converts dd to a 0-1 dd, based on the interval [threshold, +inf)\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode GreaterThanEquals(JDDNode dd, double threshold)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_GreaterThanEquals(dd.ptr(), threshold));\n\t}\n\t\n\t/**\n\t * converts dd to a 0-1 dd, based on the interval (-inf, threshold)\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode LessThan(JDDNode dd, double threshold)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_LessThan(dd.ptr(), threshold));\n\t}\n\t\n\t/**\n\t * converts dd to a 0-1 dd, based on the interval (-inf, threshold]\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode LessThanEquals(JDDNode dd, double threshold)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_LessThanEquals(dd.ptr(), threshold));\n\t}\n\t\n\t/**\n\t * converts dd to a 0-1 dd, based on the interval [threshold, threshold]\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode Equals(JDDNode dd, double value)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_Equals(dd.ptr(), value));\n\t}\n\t\n\t/**\n\t * converts dd to a 0-1 dd, based on the interval [lower, upper]\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode Interval(JDDNode dd, double lower, double upper)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_Interval(dd.ptr(), lower, upper));\n\t}\n\t\n\t/**\n\t * rounds terminals in dd to a certain number of decimal places\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode RoundOff(JDDNode dd, int places)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_RoundOff(dd.ptr(), places));\n\t}\n\t\n\t/**\n\t * returns true if sup norm of dd1 and dd2 is less than epsilon, returns false otherwise\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static boolean EqualSupNorm(JDDNode dd1, JDDNode dd2, double epsilon)\n\t{\n\t\tboolean rv = DD_EqualSupNorm(dd1.ptr(), dd2.ptr(), epsilon);\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\n\t/**\n\t * returns true if dd is a 0/1-MTBDD, i.e., all terminal nodes are either 0 or 1\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static boolean IsZeroOneMTBDD(JDDNode dd)\n\t{\n\t\treturn DD_IsZeroOneMTBDD(dd.ptr());\n\t}\n\n\t/**\n\t * returns minimum terminal in dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static double FindMin(JDDNode dd)\n\t{\n\t\tdouble rv = DD_FindMin(dd.ptr());\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Returns minimal positive terminal in dd, i.e.,\n\t * the smallest constant greater than zero.\n\t * If there is none, returns +infinity.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static double FindMinPositive(JDDNode dd)\n\t{\n\t\tdouble rv = DD_FindMinPositive(dd.ptr());\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Returns the minimum terminal in the part of\n\t * dd that overlaps with filter.\n\t * If filter is empty, returns +infinity.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>filter</i> ]\n\t */\n\tpublic static double FindMinOver(JDDNode dd, JDDNode filter)\n\t{\n\t\tJDDNode filtered = JDD.ITE(filter, dd.copy(), JDD.PlusInfinity());\n\t\tdouble rv = FindMin(filtered);\n\t\tJDD.Deref(filtered);\n\t\treturn rv;\n\t}\n\n\t/**\n\t * returns maximum terminal in dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static double FindMax(JDDNode dd)\n\t{\n\t\tdouble rv = DD_FindMax(dd.ptr());\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Returns maximal finite positive terminal in dd, i.e.,\n\t * If there is none, returns -infinity.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static double FindMaxFinite(JDDNode dd)\n\t{\n\t\tdouble rv = DD_FindMaxFinite(dd.ptr());\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Returns the maximum terminal in the part of\n\t * dd that overlaps with filter.\n\t * If filter is empty, returns -infinity.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>filter</i> ]\n\t */\n\tpublic static double FindMaxOver(JDDNode dd, JDDNode filter)\n\t{\n\t\tJDDNode filtered = JDD.ITE(filter, dd.copy(), JDD.MinusInfinity());\n\t\tdouble rv = FindMax(filtered);\n\t\tJDD.Deref(filtered);\n\t\treturn rv;\n\t}\n\n\t/**\n\t * returns dd restricted to first non-zero path (cube)\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode RestrictToFirst(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_RestrictToFirst(dd.ptr(), vars.array(), vars.n()));\n\t}\n\n\t/**\n\t * Returns the value in dd of the first non-zero path (cube) of filter.\n\t * <br>\n\t * This method handles NaN values correctly.\n\t * <br>[ REFS: <i>none</i>, DEREFS: dd, filter ]\n\t */\n\tpublic static double RestrictToFirstValue(JDDNode dd, JDDNode filter)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(filter);\n\t\t}\n\n\t\ttry {\n\t\t\tJDDNode d = dd;\n\t\t\tJDDNode f = filter;\n\n\t\t\twhile (!d.isConstant()) {\n\t\t\t\tif (f.isConstant()) {\n\t\t\t\t\tthrow new RuntimeException(\"Invalid filter\");\n\t\t\t\t}\n\t\t\t\tboolean chooseThen = f.getElse().equals(JDD.ZERO);\n\n\t\t\t\tif (d.getIndex() == f.getIndex()) {\n\t\t\t\t\td = chooseThen ? d.getThen() : d.getElse();\n\t\t\t\t} else if (d.getIndex() < f.getIndex()) {\n\t\t\t\t\tthrow new RuntimeException(\"Invalid filter\");\n\t\t\t\t}\n\t\t\t\tf = chooseThen ? f.getThen() : f.getElse();\n\t\t\t}\n\n\t\t\treturn d.getValue();\n\t\t} finally {\n\t\t\tJDD.Deref(dd, filter);\n\t\t}\n\t}\n\n\t// wrapper methods for dd_info\n\n\t/**\n\t * returns number of nodes in dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static int GetNumNodes(JDDNode dd)\n\t{\n\t\tint rv = DD_GetNumNodes(dd.ptr());\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\t\n\t/**\n\t * returns number of terminals in dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static int GetNumTerminals(JDDNode dd)\n\t{\n\t\tint rv = DD_GetNumTerminals(dd.ptr());\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\t\n\t/**\n\t * returns number of minterms in dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static double GetNumMinterms(JDDNode dd, int num_vars)\n\t{\n\t\tdouble rv = DD_GetNumMinterms(dd.ptr(), num_vars);\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\t\n\t/**\n\t * get number of minterms as a string (have to store as a double\n\t * because can be very big but want to print out as a decimal)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static String GetNumMintermsString(JDDNode dd, int num_vars)\n\t{\n\t\tdouble minterms;\n\t\t\n\t\tminterms = GetNumMinterms(dd, num_vars);\n\t\tif (minterms <= Long.MAX_VALUE) {\n\t\t\treturn \"\" + (long)minterms;\n\t\t}\n\t\telse {\n\t\t\treturn \"\" + minterms;\n\t\t}\n\t}\n\n\t/**\n\t * returns number of paths in dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static double GetNumPaths(JDDNode dd)\n\t{\n\t\tdouble rv = DD_GetNumPaths(dd.ptr());\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\t\n\t/**\n\t * get number of paths as a string (have to store as a double\n\t * because can be very big but want to print out as a decimal)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static String GetNumPathsString(JDDNode dd)\n\t{\n\t\tdouble paths;\n\t\t\n\t\tpaths = GetNumPaths(dd);\n\t\tif (paths <= Long.MAX_VALUE) {\n\t\t\treturn \"\" + (long)paths;\n\t\t}\n\t\telse {\n\t\t\treturn \"\" + paths;\n\t\t}\n\t}\n\n\t/**\n\t * Returns {@true} if {@code dd} is a single satisfying\n\t * assignment to the variables in {@code vars}.\n\t * <br>\n\t * This is the case if there is a single path to the ONE constant\n\t * and exactly the variables of {@code vars} occur on the path.\n\t * <br>\n\t * <b>Note:</b> The variables in {@code vars} have to sorted\n\t * in increasing index order! Use JDDVars.sortByIndex() to achieve this\n\t * if the ordering is not guaranteed by construction.\n\t * @param dd the DD\n\t * @param vars the variables\n\t */\n\tpublic static boolean isSingleton(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsZeroOneMTBDD(dd);\n\t\t\tSanityJDD.checkVarsAreSorted(vars);\n\t\t}\n\n\t\tfor (int i = 0; i < vars.n(); i++) {\n\t\t\tif (dd.isConstant())\n\t\t\t\treturn false;\n\n\t\t\tif (vars.getVar(i).getIndex() != dd.getIndex())\n\t\t\t\treturn false;\n\n\t\t\tJDDNode t = dd.getThen();\n\t\t\tJDDNode e = dd.getElse();\n\n\t\t\tif (t.equals(JDD.ZERO)) {\n\t\t\t\tdd = e;\n\t\t\t} else if (e.equals(JDD.ZERO)) {\n\t\t\t\tdd = t;\n\t\t\t} else {\n\t\t\t\t// then or else have to be ZERO\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\treturn dd.equals(JDD.ONE);\n\t}\n\n\t/**\n\t * prints out info for dd (nodes, terminals, minterms)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintInfo(JDDNode dd, int num_vars)\n\t{\t\t\n\t\tDD_PrintInfo(dd.ptr(), num_vars);\n\t}\n\t\n\t/**\n\t * prints out compact info for dd (nodes, terminals, minterms)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintInfoBrief(JDDNode dd, int num_vars)\n\t{\n\t\tDD_PrintInfoBrief(dd.ptr(), num_vars);\n\t}\n\t\n\t/**\n\t * gets info for dd as string (nodes, terminals, minterms)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static String GetInfoString(JDDNode dd, int num_vars)\n\t{\n\t\treturn GetNumNodes(dd)+\" nodes (\"+GetNumTerminals(dd)+\" terminal), \"+GetNumMintermsString(dd, num_vars)+\" minterms\";\n\t}\n\t\n\t/**\n\t * gets compact info for dd as string (nodes, terminals, minterms)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static String GetInfoBriefString(JDDNode dd, int num_vars)\n\t{\n\t\treturn \"[\"+GetNumNodes(dd)+\",\"+GetNumTerminals(dd)+\",\"+GetNumMintermsString(dd, num_vars)+\"]\";\n\t}\n\t\n\t/**\n\t * Prints out the support of a DD (i.e. all DD variables that are actually present).\n\t * [ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintSupport(JDDNode dd)\n\t{\n\t\tDD_PrintSupport(dd.ptr());\n\t}\n\t\n\t/**\n\t * Prints out the support of a DD (i.e. all DD variables that are actually present),\n\t * using the passed in list of DD variable names.\n\t * [ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintSupportNames(JDDNode dd, List<String> varNames)\n\t{\n\t\tDD_PrintSupportNames(dd.ptr(), varNames);\n\t}\n\t\n\t/**\n\t * returns support for dd (all dd variables present) as a cube of the dd vars\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode GetSupport(JDDNode dd)\n\t{\n\t\treturn ptrToNode(DD_GetSupport(dd.ptr()));\n\t}\n\t\n\t/**\n\t * print out all values of all terminals in dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintTerminals(JDDNode dd)\n\t{\n\t\tDD_PrintTerminals(dd.ptr());\n\t}\n\t\n\t/**\n\t * get list of values of all terminals in dd as string (native method sends to stdout)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static String GetTerminalsString(JDDNode dd)\n\t{\n\t\treturn GetTerminalsString(dd, 0, false);\n\t}\n\t\n\t/**\n\t * print out all values of all terminals (and number of each) in dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintTerminalsAndNumbers(JDDNode dd, int num_vars)\n\t{\n\t\tDD_PrintTerminalsAndNumbers(dd.ptr(), num_vars);\n\t}\n\t\n\t/**\n\t * get list of values of all terminals (and number of each) in dd (native method sends to stdout)\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static String GetTerminalsAndNumbersString(JDDNode dd, int num_vars)\n\t{\n\t\treturn GetTerminalsString(dd, num_vars, true);\n\t}\n\t\n\t// Generic code for two GetTerminals...String methods above\n\t\n\tpublic static String GetTerminalsString(JDDNode dd, int num_vars, boolean and_numbers)\n\t{\n\t\tJDDNode tmp, tmp2;\n\t\tdouble min, max, num, count = 0.0;\n\t\tString s = \"\";\n\n\t\t// Take a copy of dd\t\n\t\tJDD.Ref(dd);\n\t\ttmp = dd;\n\t\t// Check the min (will use at end)\n\t\tmin = JDD.FindMin(tmp);\n\t\t// Loop through terminals in descending order\n\t\twhile (!tmp.equals(JDD.MINUS_INFINITY)) {\n\t\t\t// Find next (max) terminal and display\n\t\t\tmax = JDD.FindMax(tmp);\n\t\t\ts += max + \" \";\n\t\t\t// Remove the terminals, counting/displaying number if required\n\t\t\tJDD.Ref(tmp);\n\t\t\ttmp2 = JDD.Equals(tmp, max);\n\t\t\tif (and_numbers) {\n\t\t\t\tnum = JDD.GetNumMinterms(tmp2, num_vars);\n\t\t\t\tcount += num;\n\t\t\t\ts += \"(\" + (long)num + \") \";\n\t\t\t}\n\t\t\ttmp = JDD.ITE(tmp2, JDD.MinusInfinity(), tmp);\n\t\t}\n\t\tJDD.Deref(tmp);\n\t\t// Finally, print if there are (and possibly how many) minus infinities\n\t\tif (and_numbers) {\n\t\t\tif (count < (1<<num_vars)) s += \"-inf (\" + ((1<<num_vars)-count) + \")\";\n\t\t} else {\n\t\t\tif (min == -Double.POSITIVE_INFINITY) s += \"-inf\";\n\t\t}\n\t\t\n\t\treturn s;\n\t}\n\n\t// wrapper methods for dd_matrix\n\n\t/**\n\t * sets element in vector dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode SetVectorElement(JDDNode dd, JDDVars vars, long index, double value)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, vars);\n\t\t}\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_SetVectorElement(dd.ptr(), vars.array(), vars.n(), index, value));\n\t}\n\t\n\t/**\n\t * sets element in matrix dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode SetMatrixElement(JDDNode dd, JDDVars rvars, JDDVars cvars, long rindex, long cindex, double value)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars);\n\t\t}\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_SetMatrixElement(dd.ptr(), rvars.array(), rvars.n(), cvars.array(), cvars.n(), rindex, cindex, value));\n\t}\n\t\n\t/**\n\t * sets element in 3d matrix dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode Set3DMatrixElement(JDDNode dd, JDDVars rvars, JDDVars cvars, JDDVars lvars, long rindex, long cindex, long lindex, double value)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars, lvars);\n\t\t}\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_Set3DMatrixElement(dd.ptr(), rvars.array(), rvars.n(), cvars.array(), cvars.n(), lvars.array(), lvars.n(), rindex, cindex, lindex, value));\n\t}\n\t\n\t/**\n\t * get element in vector dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static double GetVectorElement(JDDNode dd, JDDVars vars, long index)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, vars);\n\t\t}\n\t\tdouble rv = DD_GetVectorElement(dd.ptr(), vars.array(), vars.n(), index);\n\t\tcheckForCuddError();\n\t\treturn rv;\n\t}\n\t\n\t/**\n\t * creates dd for identity matrix\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode Identity(JDDVars rvars, JDDVars cvars)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.check(rvars.n() == cvars.n(), \"Mismatch of JDDVars sizes\");\n\t\t}\n\t\treturn ptrToNode(DD_Identity(rvars.array(), cvars.array(), rvars.n()));\n\t}\n\t\n\t/**\n\t * returns transpose of matrix dd\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd ]\n\t */\n\tpublic static JDDNode Transpose(JDDNode dd, JDDVars rvars, JDDVars cvars)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars);\n\t\t}\n\n\t\tif (DebugJDD.debugEnabled)\n\t\t\tDebugJDD.DD_Method_Argument(dd);\n\t\treturn ptrToNode(DD_Transpose(dd.ptr(), rvars.array(), cvars.array(), rvars.n()));\n\t}\n\t\n\t/**\n\t * returns matrix multiplication of matrices dd1 and dd2\n\t * <br>[ REFS: <i>result</i>, DEREFS: dd1, dd2 ]\n\t */\n\tpublic static JDDNode MatrixMultiply(JDDNode dd1, JDDNode dd2, JDDVars vars, int method)\n\t{\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\tDebugJDD.DD_Method_Argument(dd1);\n\t\t\tDebugJDD.DD_Method_Argument(dd2);\n\t\t}\n\t\treturn ptrToNode(DD_MatrixMultiply(dd1.ptr(), dd2.ptr(), vars.array(), vars.n(), method));\n\t}\n\n\t/**\n\t * Print the minterms for a JDDNode (using the support of dd as variables).\n\t * <br>\n\t * Positive variables are marked with 1, negatives with 0 and don't cares are marked with -\n \t * <br>[ REFS: <i>none</i>, DEREFS: dd ]\n \t *\n\t * @param log the output log\n\t * @param dd the MTBDD\n\t */\n\tpublic static void PrintMinterms(PrismLog log, JDDNode dd)\n\t{\n\t\tPrintMinterms(log, dd, null);\n\t}\n\n\t/**\n\t * Print the minterms for a JDDNode (using the support of dd as variables).\n\t * <br>\n\t * Positive variables are marked with 1, negatives with 0 and don't cares are marked with -\n\t * <br>[ REFS: <i>none</i>, DEREFS: dd ]\n \t *\n\t * @param log the output log\n\t * @param dd the MTBDD\n\t * @param description an optional description to be printed ({@code null} for none)\n\t */\n\tpublic static void PrintMinterms(PrismLog log, JDDNode dd, String description)\n\t{\n\t\tJDDNode csSupport = GetSupport(dd);\n\t\tJDDVars vars = JDDVars.fromCubeSet(csSupport);\n\t\tPrintMinterms(log, dd, vars, description);\n\t\tvars.derefAll();\n\t}\n\n\t/**\n\t * Print the minterms for a JDDNode over the variables {@code vars}.\n\t * <br>\n\t * Positive variables are marked with 1, negatives with 0 and don't cares are marked with -\n\t * <br>\n\t * {@code vars} has to be ordered with increasing variable indizes and\n\t * has to contain all variables in the support of {@code dd}.\n \t * <br>[ REFS: <i>none</i>, DEREFS: dd ]\n \t *\n\t * @param log the output log\n\t * @param dd the MTBDD\n\t * @param vars JDDVars of the relevant variables\n\t * @param description an optional description to be printed ({@code null} for none)\n\t * @throws IllegalArgumentException if {@code vars} does not fullfil the constraints\n\t */\n\tpublic static void PrintMinterms(PrismLog log, JDDNode dd, JDDVars vars, String description)\n\t{\n\t\ttry {\n\t\t\tif (description != null)\n\t\t\t\tlog.println(description+\":\");\n\t\t\tlog.print(\" Variables: (\");\n\t\t\tboolean first = true;\n\t\t\tfor (JDDNode var : vars) {\n\t\t\t\tif (!first) log.print(\",\");\n\t\t\t\tfirst = false;\n\t\t\t\tlog.print(var.getIndex());\n\t\t\t}\n\t\t\tlog.println(\")\");\n\t\t\tchar[] minterm = new char[vars.n()];\n\t\t\tfor (int i = 0; i< minterm.length; i++) {\n\t\t\t\tminterm[i] = '-';\n\t\t\t}\n\t\t\tPrintMintermsRec(log, dd, vars, 0, minterm);\n\t\t} finally {\n\t\t\tJDD.Deref(dd);\n\t\t}\n\t}\n\n\t/**\n\t * Recursively print the minterms for a JDDNode over the variables {@code vars}.\n\t * <br>\n\t * Positive variables are marked with 1, negatives with 0 and don't cares are marked with -\n\t * <br>\n\t * {@code vars} has to be ordered with increasing variable indizes and\n\t * has to contain all variables in the support of {@code dd}.\n \t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n \t *\n\t * @param log the output log\n\t * @param dd the MTBDD\n\t * @param vars JDDVars of the relevant variables\n\t * @param cur_index the current index into {@code vars}\n\t * @param minterm character array of length {@code vars.n()} storing the current (partial) minterm\n\t * @throws IllegalArgumentException if {@code vars} does not fullfil the constraints\n\t */\n\tprivate static void PrintMintermsRec(PrismLog log, JDDNode dd, JDDVars vars, int cur_index, char[] minterm)\n\t{\n\t\tif (dd.isConstant()) {\n\t\t\t// base case: we are at the ZERO sink, don't print\n\t\t\tif (dd.equals(JDD.ZERO))\n\t\t\t\treturn;\n\n\t\t\t// print the current minterm buffer\n\t\t\tlog.print(\" |\");\n\t\t\tfor (char c : minterm) {\n\t\t\t\tlog.print(c);\n\t\t\t}\n\t\t\t// ... and the constant value\n\t\t\tlog.println(\"| = \" +dd.getValue());\n\t\t} else {\n\t\t\t// Get the current variable index\n\t\t\tint index = dd.getIndex();\n\t\t\t// As long as there are variables left in vars\n\t\t\twhile (cur_index < vars.n()) {\n\t\t\t\tint var_index = vars.getVar(cur_index).getIndex();\n\t\t\t\t// We are at the level of the next var in vars\n\t\t\t\tif (var_index == index) {\n\t\t\t\t\t// Recurse for else\n\t\t\t\t\tminterm[cur_index]='0';\n\t\t\t\t\tPrintMintermsRec(log, dd.getElse(), vars, cur_index+1, minterm);\n\t\t\t\t\t// Recurse for then\n\t\t\t\t\tminterm[cur_index]='1';\n\t\t\t\t\tPrintMintermsRec(log, dd.getThen(), vars, cur_index+1, minterm);\n\t\t\t\t\t// ... and we are done\n\t\t\t\t\tminterm[cur_index]='-';\n\t\t\t\t\treturn;\n\t\t\t\t} else if (var_index < index) {\n\t\t\t\t\t// The next variable in vars is less then the current dd index\n\t\t\t\t\t//  -> don't care\n\t\t\t\t\tminterm[cur_index]='-';\n\t\t\t\t\t// Go to next variable in vars\n\t\t\t\t\t++cur_index;\n\t\t\t\t\t// ... and continue\n\t\t\t\t\tcontinue;\n\t\t\t\t} else {\n\t\t\t\t\t// var_index > index\n\t\t\t\t\t// Either the vars are not ordered correctly or\n\t\t\t\t\t// the dd has relevant variables not included in vars\n\t\t\t\t\t// To help with debugging, differentiate between the two cases...\n\t\t\t\t\tfor (JDDNode var : vars) {\n\t\t\t\t\t\tif (var.getIndex() == index) {\n\t\t\t\t\t\t\t// There is a var with the current index in vars, but\n\t\t\t\t\t\t\t// not at the correct position\n\t\t\t\t\t\t\tthrow new IllegalArgumentException(\"PrintMinterms: vars array does not appear to be sorted correctly (DD index = \"+index+\", var index = \"+var_index+\")\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// otherwise, the dd depends on a variable not in vars\n\t\t\t\t\tthrow new IllegalArgumentException(\"PrintMinterms: MTBDD depends on variable \"+index+\", not included in vars\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (vars.n() == 0) {\n\t\t\t\tthrow new IllegalArgumentException(\"PrintMinterms: MTBDD depends on variable \"+index+\", not included in vars\");\n\t\t\t}\n\t\t\tthrow new UnsupportedOperationException(\"PrintMinterms: Implementation error\");\n\t\t}\n\t}\n\n\t/**\n\t * prints out vector dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintVector(JDDNode dd, JDDVars vars)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, vars);\n\t\t}\n\t\tDD_PrintVector(dd.ptr(), vars.array(), vars.n(), NORMAL);\n\t}\n\t\n\t/**\n\t * prints out vector dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintVector(JDDNode dd, JDDVars vars, int accuracy)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, vars);\n\t\t}\n\t\tDD_PrintVector(dd.ptr(), vars.array(), vars.n(), accuracy);\n\t}\n\t\n\t/**\n\t * prints out matrix dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintMatrix(JDDNode dd, JDDVars rvars, JDDVars cvars)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars);\n\t\t}\n\t\tDD_PrintMatrix(dd.ptr(), rvars.array(), rvars.n(), cvars.array(), cvars.n(), NORMAL);\n\t}\n\t\n\t/**\n\t * prints out matrix dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintMatrix(JDDNode dd, JDDVars rvars, JDDVars cvars, int accuracy)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars);\n\t\t}\n\t\tDD_PrintMatrix(dd.ptr(), rvars.array(), rvars.n(), cvars.array(), cvars.n(), accuracy);\n\t}\n\t\n\t/**\n\t * prints out vector dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintVectorFiltered(JDDNode dd, JDDNode filter, JDDVars vars)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, vars);\n\t\t\tSanityJDD.checkIsDDOverVars(filter, vars);\n\t\t}\n\t\tDD_PrintVectorFiltered(dd.ptr(), filter.ptr(), vars.array(), vars.n(), NORMAL);\n\t}\n\t\n\t/**\n\t * prints out vector dd\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void PrintVectorFiltered(JDDNode dd, JDDNode filter, JDDVars vars, int accuracy)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, vars);\n\t\t\tSanityJDD.checkIsDDOverVars(filter, vars);\n\t\t}\n\t\tDD_PrintVectorFiltered(dd.ptr(), filter.ptr(), vars.array(), vars.n(), accuracy);\n\t}\n\t\n\t/**\n\t * traverse vector dd and call setElement method of VectorConsumer for each non zero element\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void TraverseVector(JDDNode dd, JDDVars vars, JDDVectorConsumer vc, int code)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, vars);\n\t\t}\n\t\tTraverseVectorRec(dd, vars, 0, 0, vc, code);\n\t}\n\t\n\t// recursive part of TraverseVector\n\t\n\tprivate static void TraverseVectorRec(JDDNode dd, JDDVars vars, int varStart, long count, JDDVectorConsumer vc, int code)\n\t{\n\t\tJDDNode n, s;\n\t\t\n\t\tif (dd.equals(JDD.ZERO)) {\n\t\t\treturn;\n\t\t}\n\t\t\t\t\n\t\tif (varStart == vars.getNumVars()) {\n\t\t\tvc.setElement(count, dd.getValue(), code);\n\t\t}\n\t\telse {\n\t\t\t// split into 2 cases\n\t\t\tJDD.Ref(dd);\n\t\t\tJDD.Ref(vars.getVar(varStart));\n\t\t\tn = JDD.Restrict(dd, JDD.Not(vars.getVar(varStart)));\n\t\t\tJDD.Ref(dd);\n\t\t\tJDD.Ref(vars.getVar(varStart));\n\t\t\ts = JDD.Restrict(dd, vars.getVar(varStart));\n\t\t\t\n\t\t\tTraverseVectorRec(n, vars, varStart+1, count, vc, code);\n\t\t\tTraverseVectorRec(s, vars, varStart+1, count+(1l << (vars.getNumVars()-varStart-1)), vc, code);\n\t\t\t\n\t\t\tJDD.Deref(n);\n\t\t\tJDD.Deref(s);\n\t\t}\n\t}\n\n\t// wrapper methods for dd_export\n\n\t/**\n\t * export dd to a dot file\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void ExportDDToDotFile(JDDNode dd, String filename)\n\t{\n\t\tDD_ExportDDToDotFile(dd.ptr(), filename);\n\t}\n\t\n\t/**\n\t * export dd to a dot file\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void ExportDDToDotFileLabelled(JDDNode dd, String filename, List<String> varNames)\n\t{\n\t\tDD_ExportDDToDotFileLabelled(dd.ptr(), filename, varNames);\n\t}\n\t\n\t/**\n\t * export matrix dd to a pp file\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void ExportMatrixToPPFile(JDDNode dd, JDDVars rvars, JDDVars cvars, String filename)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars);\n\t\t\tSanityJDD.check(rvars.n() == cvars.n(), \"Mismatch of JDDVars sizes\");\n\t\t}\n\t\tDD_ExportMatrixToPPFile(dd.ptr(), rvars.array(), rvars.n(), cvars.array(), cvars.n(), filename);\n\t}\n\t\n\t/**\n\t * Given a BDD that represents transition matrices of an MDP, this method\n     * outputs one matrix for every action. Note that the output is in fact\n     * not a PP file, but several PP files concatenated into one file.\n\t *\n\t * For example, for a model with the variable\n\t * \tx : [0..2];\n\t * and transitions\n\t *  [a] (x=0) -&gt; 0.3:(x'=1) + 0.7:(x'=2);\n\t *  [b] (x=0) -&gt; 1:(x'=2);\n\t *  [a] (x=2) -&gt; (x'=1);\n\t *  [a] (x=1) -&gt; (x'=0);\n\t * the output would be (e.g.)\n \t *  4\n\t *\t4\n\t *\t0 2 1.000000\n\t *\t4\n\t *\t0 1 0.300000\n\t *\t1 0 1.000000\n\t *\t0 2 0.700000\n\t *\t2 1 1.000000\n\t *  4\n\t *\n\t * [ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void Export3dMatrixToPPFile(JDDNode dd, JDDVars rvars, JDDVars cvars, JDDVars nvars, String filename)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars, nvars);\n\t\t\tSanityJDD.check(rvars.n() == cvars.n(), \"Mismatch of JDDVars sizes\");\n\t\t}\n\t\tDD_Export3dMatrixToPPFile(dd.ptr(), rvars.array(), rvars.n(), cvars.array(), cvars.n(), nvars.array(), nvars.n(), filename);\n\t}\n\n\t/**\n\t * export matrix dd to a matlab file\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void ExportMatrixToMatlabFile(JDDNode dd, JDDVars rvars, JDDVars cvars, String name, String filename)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars);\n\t\t\tSanityJDD.check(rvars.n() == cvars.n(), \"Mismatch of JDDVars sizes\");\n\t\t}\n\t\tDD_ExportMatrixToMatlabFile(dd.ptr(), rvars.array(), rvars.n(), cvars.array(), cvars.n(), name, filename);\n\t}\n\n\t/**\n\t * export matrix dd to a spy file\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void ExportMatrixToSpyFile(JDDNode dd, JDDVars rvars, JDDVars cvars, int depth, String filename)\n\t{\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(dd, rvars, cvars);\n\t\t\tSanityJDD.check(rvars.n() == cvars.n(), \"Mismatch of JDDVars sizes\");\n\t\t}\n\t\tDD_ExportMatrixToSpyFile(dd.ptr(), rvars.array(), rvars.n(), cvars.array(), cvars.n(), depth, filename);\n\t}\n\n\t/**\n\t * Convert a (referenced) ptr returned from Cudd into a JDDNode.\n\t * <br>Throws a CuddOutOfMemoryException if the pointer is NULL.\n\t * <br>[ REFS: <i>none</i> ]\n\t */\n\tpublic static JDDNode ptrToNode(long ptr)\n\t{\n\t\tif (ptr == 0L) {\n\t\t\tthrow new CuddOutOfMemoryException();\n\t\t}\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\treturn DebugJDD.ptrToNode(ptr);\n\t\t} else {\n\t\t\treturn new JDDNode(ptr);\n\t\t}\n\t}\n\n\t/**\n\t * Check whether the DD error flag is set, indicating an\n\t * out-of-memory situation in CUDD or another internal error.\n\t * If the flag is set, throws a {@code CuddOutOfMemoryException}.\n\t */\n\tpublic static void checkForCuddError()\n\t{\n\t\tif (DD_GetErrorFlag())\n\t\t\tthrow new CuddOutOfMemoryException();\n\t}\n\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/jdd/JDDLibrary.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2026-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage jdd;\n\nimport prism.*;\n\n/**\n * A {@code PrismLibrary} wrapper around native code in the JDD library.\n */\npublic class JDDLibrary implements PrismLibrary\n{\n    /** Has CUDD been initialised? */\n    private static boolean cuddInitialised = false;\n\n    @Override\n    public void initialise(Prism prism) throws PrismException\n    {\n        long cuddMaxMem = PrismUtils.convertMemoryStringtoKB(prism.getCUDDMaxMem());\n        JDD.InitialiseCUDD(cuddMaxMem, prism.getCUDDEpsilon());\n        cuddInitialised = true;\n    }\n\n    @Override\n    public void setMainLog(PrismLog mainLog) throws PrismException\n    {\n        // If possible, we ensure that the log is using native code\n        // and pass the (file/stdout) pointer to JDD.\n        // This is mainly so that diagnostic/error messages from the\n        // DD native code end up in the same place as the rest of the log output.\n        if (mainLog instanceof PrismFileLog) {\n            ((PrismFileLog) mainLog).useNative();\n        }\n        long fp = mainLog.getFilePointer();\n        if (fp > 0) {\n            JDD.SetOutputStream(fp);\n        }\n    }\n\n    @Override\n    public void notifySettings(PrismSettings settings)\n    {\n        if (cuddInitialised) {\n            JDD.SetCUDDEpsilon(settings.getDouble(PrismSettings.PRISM_CUDD_EPSILON));\n            try {\n                long cuddMaxMem = PrismUtils.convertMemoryStringtoKB(settings.getString(PrismSettings.PRISM_CUDD_MAX_MEM));\n                JDD.SetCUDDMaxMem(cuddMaxMem);\n            } catch (PrismException e) {\n                // Fail silently if memory string is invalid\n            }\n            jdd.SanityJDD.enabled = settings.getBoolean(PrismSettings.PRISM_JDD_SANITY_CHECKS);\n        }\n    }\n\n    @Override\n    public void closeDown(boolean check)\n    {\n        if (cuddInitialised) {\n            JDD.CloseDownCUDD(check);\n            cuddInitialised = false;\n        }\n    }\n}\n"
  },
  {
    "path": "prism/src/jdd/JDDNode.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Christian von Essen <christian.vonessen@imag.fr> (VERIMAG)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jdd;\n\npublic class JDDNode\n{\n\tprivate long ptr;\n\t\n\t// native methods (jni)\n\tprotected static native boolean DDN_IsConstant(long dd);\n\tprotected static native int DDN_GetIndex(long dd);\n\tprotected static native double DDN_GetValue(long dd);\n\tprotected static native long DDN_GetThen(long dd);\n\tprotected static native long DDN_GetElse(long dd);\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t/**\n\t * Protected constructor from a DdNode pointer.\n\t * In general, to get a JDDNode from a pointer,\n\t * use JDD.ptrToNode().\n\t */\n\tprotected JDDNode(long p)\n\t{\n\t\tptr = p;\n\t}\n\t\n\tpublic long ptr()\n\t{\n\t\treturn ptr;\n\t}\n\n\tpublic boolean isConstant()\n\t{\n\t\treturn DDN_IsConstant(ptr);\n\t}\n\n\tpublic int getIndex()\n\t{\t\n\t\treturn DDN_GetIndex(ptr);\n\t}\n\n\tpublic double getValue()\n\t{\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\treturn DebugJDD.nodeGetValue(this);\n\t\t}\n\t\treturn DDN_GetValue(ptr);\n\t}\n\n\t/**\n\t * Returns the Then child of a (non-constant) JDDNode.\n\t * <br>\n\t * This method does NOT increase the reference count of the returned\n\t * node, it is therefore illegal to call JDD.Deref on the result.\n\t * Additionally, it is recommended to not use the returned node\n\t * as the argument to the JDD methods or call JDD.Ref on it.\n\t * Instead, if you need to obtain a \"proper\" node, call copy()\n\t * on the returned node.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getThen()\n\t{\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\treturn DebugJDD.nodeGetThen(this);\n\t\t}\n\n\t\tlong thenPtr = DDN_GetThen(ptr);\n\t\tif (thenPtr == 0) {\n\t\t\tif (isConstant()) {\n\t\t\t\tthrow new RuntimeException(\"Trying to access the 'then' child of a constant MTBDD node\");\n\t\t\t} else {\n\t\t\t\tthrow new RuntimeException(\"getThen: CUDD returned NULL, but node is not a constant node. Out of memory or corrupted MTBDD?\");\n\t\t\t}\n\t\t}\n\t\treturn new JDDNode(thenPtr);\n\t}\n\n\t/**\n\t * Returns the Else child of a (non-constant) JDDNode.\n\t * <br>\n\t * This method does NOT increase the reference count of the returned\n\t * node, it is therefore illegal to call JDD.Deref on the result.\n\t * Additionally, it is recommended to not use the returned node\n\t * as the argument to the JDD methods or call JDD.Ref on it.\n\t * Instead, if you need to obtain a \"proper\" node, call copy()\n\t * on the returned node.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getElse()\n\t{\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\treturn DebugJDD.nodeGetElse(this);\n\t\t}\n\n\t\tlong elsePtr = DDN_GetElse(ptr);\n\t\tif (elsePtr == 0) {\n\t\t\tif (isConstant()) {\n\t\t\t\tthrow new RuntimeException(\"Trying to access the 'else' child of a constant MTBDD node\");\n\t\t\t} else {\n\t\t\t\tthrow new RuntimeException(\"getElse: CUDD returned NULL, but node is not a constant node. Out of memory or corrupted MTBDD?\");\n\t\t\t}\n\t\t}\n\t\treturn new JDDNode(elsePtr);\n\t}\n\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof JDDNode) && (((JDDNode) o).ptr == ptr);\n\t}\n\t\n\tpublic int hashCode()\n\t{\n\t\treturn (int)ptr; \n\t}\n\t\n\tpublic String toString()\n\t{\n\t\tString result = \"\" + ptr;\n\t\tif (ptr != 0) {\n\t\t\tif (this.isConstant()) result += \" value=\" + this.getValue();\n\t\t\tresult += \" references=\" + DebugJDD.getRefCount(this);\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Returns a referenced copy of this node.\n\t * This has the effect of increasing the reference count\n\t * for the underlying MTBDD.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode copy()\n\t{\n\t\tif (DebugJDD.debugEnabled) {\n\t\t\treturn DebugJDD.Copy(this);\n\t\t} else {\n\t\t\tJDDNode result = new JDDNode(ptr());\n\t\t\tJDD.Ref(result);\n\t\t\treturn result;\n\t\t}\n\t}\n\n\t/**\n\t * Helper method to get the pointers for all JDDNodes in an array.\n\t */\n\tpublic static long[] ptrs(JDDNode[] dds)\n\t{\n\t\tif (dds == null) {\n\t\t\treturn null;\n\t\t}\n\t\tlong[] ptrs = new long[dds.length];\n\t\tfor (int i = 0; i < dds.length; i++) {\n\t\t\tptrs[i] = dds[i] != null ? dds[i].ptr() : 0;\n\t\t}\n\t\treturn ptrs;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/jdd/JDDTest.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jdd;\n\npublic class JDDTest\n{\n\tpublic static void main(String[] args)\n\t{\n\t\tJDDNode a, b, c;\n\t\tJDDVars vars;\t\t\n\t\t\n\t\tSystem.out.println(\"\\nTest program for JDD\\n====================\");\n\t\t\n\t\t// initialise cudd\n\t\tJDD.InitialiseCUDD();\n\t\t\n\t\t// set up some variables\n\t\tvars = new JDDVars();\n\t\tvars.addVar(JDD.Var(0));\n\t\tvars.addVar(JDD.Var(2));\n\t\t\n\t\t// blank dd\n\t\ta = JDD.Create();\n\t\tSystem.out.println(\"\\nCreate()\");\n\t\tJDD.PrintVector(a, vars);\n\t\tJDD.Deref(a);\n\t\t\n\t\t// constant\n\t\ta = JDD.Constant(1.5);\n\t\tSystem.out.println(\"\\nConstant(1.5)\");\n\t\tJDD.PrintVector(a, vars);\n\t\tJDD.Deref(a);\n\t\t\n\t\t// plus infinity\n\t\ta = JDD.PlusInfinity();\n\t\tSystem.out.println(\"\\nPlusInfinity()\");\n\t\tJDD.PrintVector(a, vars);\n\t\tJDD.Deref(a);\n\t\t\n\t\t// minus infinity\n\t\ta = JDD.MinusInfinity();\n\t\tSystem.out.println(\"\\nMinusInfinity()\");\n\t\tJDD.PrintVector(a, vars);\n\t\tJDD.Deref(a);\n\t\t\n\t\t// var\n\t\ta = JDD.Var(0);\n\t\tSystem.out.println(\"\\nVar(0)\");\n\t\tJDD.PrintVector(a, vars);\n\t\tJDD.Deref(a);\n\t\t\t\t\n\t\ta = JDD.Var(0);\n\t\tb = JDD.Var(2);\n\t\tSystem.out.print(\"\\na: \");\n\t\tJDD.PrintVector(a, vars);\n\t\tSystem.out.print(\"b: \");\n\t\tJDD.PrintVector(b, vars);\n\n\t\t// not\n\t\tJDD.Ref(a);\n\t\tc = JDD.Not(a);\n\t\tSystem.out.println(\"\\nNot(a)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\t\n\t\t// or\n\t\tJDD.Ref(a);\n\t\tJDD.Ref(b);\n\t\tc = JDD.Or(a, b);\n\t\tSystem.out.println(\"\\nOr(a, b)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\t\n\t\t// and\n\t\tJDD.Ref(a);\n\t\tJDD.Ref(b);\n\t\tc = JDD.And(a, b);\n\t\tSystem.out.println(\"\\nAnd(a, b)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\t\n\t\t// xor\n\t\tJDD.Ref(a);\n\t\tJDD.Ref(b);\n\t\tc = JDD.Xor(a, b);\n\t\tSystem.out.println(\"\\nXor(a, b)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\t\n\t\t// implies\n\t\tJDD.Ref(a);\n\t\tJDD.Ref(b);\n\t\tc = JDD.Implies(a, b);\n\t\tSystem.out.println(\"\\nImplies(a, b)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\t\n\t\tJDD.Deref(a);\n\t\tJDD.Deref(b);\n\t\t\n\t\ta = JDD.Create();\n\t\ta = JDD.SetVectorElement(a, vars, 0, 1);\n\t\ta = JDD.SetVectorElement(a, vars, 1, 2);\n\t\ta = JDD.SetVectorElement(a, vars, 2, 3);\n\t\ta = JDD.SetVectorElement(a, vars, 3, 4);\n\t\tb = JDD.Create();\n\t\tb = JDD.SetVectorElement(b, vars, 0, 0);\n\t\tb = JDD.SetVectorElement(b, vars, 1, 2);\n\t\tb = JDD.SetVectorElement(b, vars, 2, 4);\n\t\tb = JDD.SetVectorElement(b, vars, 3, 6);\n\t\tSystem.out.print(\"\\na: \");\n\t\tJDD.PrintVector(a, vars);\n\t\tSystem.out.print(\"b: \");\n\t\tJDD.PrintVector(b, vars);\n\t\t\n\t\t// apply\n\t\tJDD.Ref(a);\n\t\tJDD.Ref(b);\n\t\tc = JDD.Apply(JDD.PLUS, a, b);\n\t\tSystem.out.println(\"\\nApply(+, a, b)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\tJDD.Ref(a);\n\t\tJDD.Ref(b);\n\t\tc = JDD.Apply(JDD.MINUS, a, b);\n\t\tSystem.out.println(\"\\nApply(-, a, b)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\tJDD.Ref(a);\n\t\tJDD.Ref(b);\n\t\tc = JDD.Apply(JDD.TIMES, a, b);\n\t\tSystem.out.println(\"\\nApply(*, a, b)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\tJDD.Ref(a);\n\t\tJDD.Ref(b);\n\t\tc = JDD.Apply(JDD.DIVIDE, a, b);\n\t\tSystem.out.println(\"\\nApply(/, a, b)\");\n\t\tJDD.PrintVector(c, vars);\n\t\tJDD.Deref(c);\n\t\t\n\t\t\n\t\tJDD.Deref(a);\n\t\tJDD.Deref(b);\n\n\t\t// dereference variables\n\t\tvars.derefAll();\n\t\t\n\t\t// close down cudd\n\t\tJDD.CloseDownCUDD();\n\t\tSystem.out.println();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/jdd/JDDVars.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jdd;\n\nimport java.util.Collections;\nimport java.util.Comparator;\nimport java.util.Iterator;\nimport java.util.Vector;\n\n/**\n * Container for MTBDD variables.\n * Each variable is represented by a JDDNode (result of JDD.Var(), a projection function).\n *\n * It is assumed in general that each JDDNode held in a JDDVars container\n * counts as a single reference and that a JDDVars object is cleared using derefAll()\n * when no longer used. This will dereference all the variables contained in the JDDVars\n * object.\n */\npublic class JDDVars implements Iterable<JDDNode>\n{\n\tprivate Vector<JDDNode> vars;\n\tprivate long array;\n\tprivate boolean arrayBuilt;\n\t\n\tprivate native long DDV_BuildArray();\n\tprivate native void DDV_FreeArray(long a);\n\tprivate native int DDV_GetIndex(long dd);\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t/**\n\t * Constructor.\n\t */\n\tpublic JDDVars()\n\t{\n\t\tvars = new Vector<JDDNode>();\n\t\tarray = 0;\n\t\tarrayBuilt = false;\n\t}\n\n\t/**\n\t * Appends a variable to this JDDVars container.\n\t * <br>\n\t * [ DEREFs: var (on derefAll call) ]\n\t */\n\tpublic void addVar(JDDNode var)\n\t{\n\t\tvars.addElement(var);\n\t\tif (arrayBuilt) DDV_FreeArray(array);\n\t\tarrayBuilt = false;\n\t}\n\t\n\t/**\n\t * Appends the variables of another JDDVars container to this container.\n\t * Does not increase the refcount of the JDDNodes!\n\t * <br>\n\t * This method is deprecated, better use copy() or copyVarsFrom() instead.\n\t * These simplify variable reference count debugging.\n\t */\n\t@Deprecated\n\tpublic void addVars(JDDVars ddv)\n\t{\n\t\tvars.addAll(ddv.vars);\n\t\tif (arrayBuilt) DDV_FreeArray(array);\n\t\tarrayBuilt = false;\n\t}\n\n\t/**\n\t * Creates a copy of this JDDVars container,\n\t * containing referenced copies of each variable JDDNode in this container.\n\t */\n\tpublic JDDVars copy()\n\t{\n\t\tJDDVars result = new JDDVars();\n\t\tfor (JDDNode var : this) {\n\t\t\tresult.addVar(var.copy());\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Copies variables from another JDDVars container,\n\t * appending to this container.\n\t * Does a (referencing) copy of each of the variable JDDNodes.\n\t */\n\tpublic void copyVarsFrom(JDDVars ddv) {\n\t\tfor (JDDNode var : ddv) {\n\t\t\taddVar(var.copy());\n\t\t}\n\t}\n\t\n\t/**\n\t * Copy an array of JDDVars[] by copying each JDDVars container.\n\t * The copy will have fully referenced JDDNodes.\n\t */\n\tpublic static JDDVars[] copyArray(JDDVars[] vararray)\n\t{\n\t\tJDDVars[] result = new JDDVars[vararray.length];\n\t\tfor (int i = 0;  i< vararray.length; i++) {\n\t\t\tresult[i] = vararray[i].copy();\n\t\t}\n\t\treturn result;\n\t}\n\n\n\t/**\n\t * Copy JDDNodes from another JDDVars, merge into the existing variables,\n\t * sorting by the variable indices. Afterwards, this JDDVars container\n\t * is fully sorted by variable indices, i.e., the existing variables are\n\t * sorted as well.\n\t * @param ddv the new variables\n\t */\n\tpublic void mergeVarsFrom(JDDVars ddv) {\n\t\tcopyVarsFrom(ddv);\n\t\tsortByIndex();\n\t}\n\n\t/**\n\t * Remove variable v from container. Does not decrease the refcount.\n\t */\n\tpublic void removeVar(JDDNode v)\n\t{\n\t\tvars.remove(v);\n\t\tif (arrayBuilt) DDV_FreeArray(array);\n\t\tarrayBuilt = false;\n\t}\n\n\t/**\n\t * Removes the JDDNodes contained in ddv from this JDDVars container.\n\t * Does not decrease the refcount!\n\t */\n\tpublic void removeVars(JDDVars ddv)\n\t{\n\t\tvars.removeAll(ddv.vars);\n\t\tif (arrayBuilt) DDV_FreeArray(array);\n\t\tarrayBuilt = false;\n\t}\n\n\t/** Returns the number of variables stored in this JDDVars container. */\n\tpublic int getNumVars()\n\t{\n\t\treturn vars.size();\n\t}\n\n\t/**\n\t * Returns the JDDNode for the i-th stored variable.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getVar(int i)\n\t{\n\t\treturn (JDDNode)vars.elementAt(i);\n\t}\n\n\t/**\n\t * Returns the internal Cudd pointer for the i-th stored variable.\n\t */\n\tpublic long getVarPtr(int i)\n\t{\n\t\treturn ((JDDNode)vars.elementAt(i)).ptr();\n\t}\n\n\t/**\n\t * Returns the Cudd variable index for the i-th stored variable.\n\t */\n\tpublic int getVarIndex(int i)\n\t{\n\t\treturn DDV_GetIndex(((JDDNode)vars.elementAt(i)).ptr());\n\t}\n\n\t/**\n\t * Returns the minimal Cudd variable index for the stored variables,\n\t * or -1 if there are no stored variables.\n\t */\n\tpublic int getMinVarIndex()\n\t{\n\t\tint i, j, n, min;\n\t\tn = vars.size();\n\t\tif (n == 0) return -1;\n\t\tmin = getVarIndex(0);\n\t\tfor (i = 1; i < n; i++) {\n\t\t\tj = getVarIndex(i);\n\t\t\tif (j < min) min = j;\n\t\t}\n\t\treturn min;\n\t}\n\n\t/**\n\t * Returns the maximal Cudd variable index for the stored variables,\n\t * or -1 if there are no stored variables.\n\t */\n\tpublic int getMaxVarIndex()\n\t{\n\t\tint i, j, n, max;\n\t\tn = vars.size();\n\t\tif (n == 0) return -1;\n\t\tmax = getVarIndex(0);\n\t\tfor (i = 1; i < n; i++) {\n\t\t\tj = getVarIndex(i);\n\t\t\tif (j > max) max = j;\n\t\t}\n\t\treturn max;\n\t}\n\n\t/**\n\t * Increases the refcount of all contained JDDNodes.\n\t * <br>\n\t * This method is deprecated, please use copy() and\n\t * copyVarsFrom() instead.\n\t * This simplifies reference counting debugging.\n\t */\n\t@Deprecated\n\tpublic void refAll()\n\t{\n\t\tint i;\n\t\t\n\t\tfor (i = 0; i < vars.size(); i++) {\n\t\t\tJDD.Ref((JDDNode)vars.elementAt(i));\n\t\t}\n\t}\n\n\t/**\n\t * Decreases the refcount of all contained JDDNodes.\n\t */\n\tpublic void derefAll()\n\t{\n\t\tint i;\n\n\t\tfor (i = 0; i < vars.size(); i++) {\n\t\t\tJDD.Deref((JDDNode)vars.elementAt(i));\n\t\t}\n\t}\n\n\t/**\n\t * Calls derefAll on all JDDVars elements of a JDDVars[] array.\n\t */\n\tpublic static void derefAllArray(JDDVars[] vars)\n\t{\n\t\tfor (JDDVars v : vars) {\n\t\t\tv.derefAll();\n\t\t}\n\t}\n\n\t/**\n\t * Constructs a JNI array for the stored variables\n\t * that can be passed to the C-based functions.\n\t */\n\tpublic long array()\n\t{\n\t\tif (arrayBuilt) {\n\t\t\treturn array;\n\t\t}\n\t\telse {\n\t\t\tarray = DDV_BuildArray();\n\t\t\tarrayBuilt = true;\n\t\t\treturn array;\n\t\t}\n\t}\n\n\t/**\n\t * Returns the number of stored variables.\n\t */\n\tpublic int n()\n\t{\n\t\treturn vars.size();\n\t}\n\n\t@Override\n\tpublic Iterator<JDDNode> iterator()\n\t{\n\t\treturn vars.iterator();\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i;\n\t\tString s = \"{\";\n\t\t\n\t\tfor (i = 0; i < vars.size() - 1; i++) {\n\t\t\ts = s + getVarIndex(i) + \", \";\n\t\t}\n\t\tif (vars.size() > 0) {\n\t\t\ts = s + getVarIndex(vars.size() - 1);\n\t\t}\n\t\ts += \"}\";\n\t\t\n\t\treturn s;\n\t}\n\t\n\t\n\t/**\n\t * Converts a DD cubeset (conjunction of variables)\n\t * to a corresponding JDDVars array.<br>\n\t * <br> [ REFS: <i>the variables in the returned JDDVars container</i>, DEREFS: cubeSet ]\n\t */\n\tpublic static JDDVars fromCubeSet(JDDNode cubeSet)\n\t{\n\t\ttry {\n\t\t\tJDDVars result = new JDDVars();\n\n\t\t\tJDDNode current = cubeSet;\n\t\t\t// We do not need to bother with reference manipulation,\n\t\t\t// as we only call getThen() and getElse(), which do not increase\n\t\t\t// the refcount\n\t\t\twhile (!current.equals(JDD.ONE)) {\n\t\t\t\tif (current.isConstant()) {\n\t\t\t\t\t// may not be any other constant than ONE\n\t\t\t\t\tthrow new IllegalArgumentException(\"JDDVars.fromCubeSet: The argument is not a cubeset\");\n\t\t\t\t}\n\t\t\t\tif (!current.getElse().equals(JDD.ZERO)) {\n\t\t\t\t\t// else always has to point to ZERO\n\t\t\t\t\tthrow new IllegalArgumentException(\"JDDVars.fromCubeSet: The argument is not a cubeset\");\n\t\t\t\t}\n\n\t\t\t\tint index = current.getIndex();\n\t\t\t\tJDDNode var = JDD.Var(index);\n\t\t\t\tresult.addVar(var);\n\n\t\t\t\tcurrent = current.getThen();\n\t\t\t}\n\n\t\t\treturn result;\n\t\t} finally {\n\t\t\tJDD.Deref(cubeSet);\n\t\t}\n\t}\n\n\t/**\n\t * Constructs a DD cubeset (conjunction of variables)\n\t * corresponding to this JDDVars container.<br>\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode toCubeSet()\n\t{\n\t\tJDDNode result = JDD.Constant(1);\n\t\tfor (JDDNode var : vars) {\n\t\t\tresult = JDD.And(result, var.copy());\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Constructs a 0/1-ADD that is the conjunction of\n\t * the negated variables, i.e.,\n\t * And(Not(v_1), Not(v_2), ..., Not(v_n))\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode allZero()\n\t{\n\t\tJDDNode result = JDD.Constant(1);\n\t\tfor (JDDNode var : vars) {\n\t\t\tresult = JDD.And(result, JDD.Not(var.copy()));\n\t\t}\n\t\treturn result;\n\t}\n\n\t/** Sort the variables in this container by their variable index. */\n\tpublic void sortByIndex()\n\t{\n\t\tif (arrayBuilt) DDV_FreeArray(array);\n\t\tarrayBuilt = false;\n\n\t\tCollections.sort(vars, new Comparator<JDDNode>() {\n\t\t\t@Override\n\t\t\tpublic int compare(JDDNode a, JDDNode b)\n\t\t\t{\n\t\t\t\treturn Integer.valueOf(a.getIndex()).compareTo(b.getIndex());\n\t\t\t}\n\t\t});\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/jdd/JDDVectorConsumer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jdd;\n\npublic interface JDDVectorConsumer\n{\n\tvoid setElement(long x, double d, int code);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/jdd/README",
    "content": "JDD\n===\n\nTo add new functions:\n---------------------\n\n- Add Java wrapper method to JDD.java\n- Add native method prototype to JDD.java\n- javac jdd/JDD.java\n- javah -jni jdd.JDD -o jdd/JDD.h\n- Add C++ wrapper to jdd.cc (get prototype from jdd/JDD.h)\n- cd jdd\n- make clean\n- cd ..\n- make\n"
  },
  {
    "path": "prism/src/jdd/SanityJDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jdd;\n\n/**\n * Helper class for doing sanity checks in the symbolic engines.\n * <br>\n * As the sanity checks perform various MTBDD operations, which\n * can be costly and can lead to a significant slow-down, the\n * sanity checks should only be enabled for debugging purposes.\n * <br>\n * The sanity checks are globally enabled by setting the\n * {@code static boolean enabled} to true.\n * <br>\n * In your code, check this variable before calling one\n * of the check methods. However, the methods themselves\n * do not check the {@code enabled} flag and can therefore\n * also be used when the global sanity check is disabled.\n */\npublic class SanityJDD\n{\n\t/** Global flag: is sanity checking enabled? */\n\tpublic static boolean enabled = false;\n\n\t/**\n\t * Perform sanity check: Is a contained in b?\n\t * <br>\n\t * a and b have to be 0/1 MTBDDs.\n\t * <br>\n\t * Throws a RuntimeException if the test fails.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void checkIsContainedIn(JDDNode a, JDDNode b)\n\t{\n\t\tcheckIsZeroOneMTBDD(a);\n\t\tcheckIsZeroOneMTBDD(b);\n\n\t\tif (!JDD.IsContainedIn(a, b)) {\n\t\t\terror(\"a is not contained in b\");\n\t\t}\n\t}\n\n\t/**\n\t * Perform sanity check:\n\t * Is node a 0/1-MTBDD, i.e., has only 0 and 1 as constants.\n\t * <br>\n\t * Throws a RuntimeException if the test fails.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void checkIsZeroOneMTBDD(JDDNode node)\n\t{\n\t\tif (!JDD.IsZeroOneMTBDD(node)) {\n\t\t\terror(\"MTBDD is not a 0/1-MTBDD\");\n\t\t}\n\t}\n\n\t/**\n\t * Perform sanity check:\n\t * Are the variable indizes for the vars vector\n\t * in increasing order?\n\t * <br>\n\t * This is an assumption for various methods\n\t * taking a list of variables as argument.\n\t * <br>\n\t * Throws a RuntimeException if the test fails.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void checkVarsAreSorted(JDDVars vars)\n\t{\n\t\tint lastIndex = -1;\n\t\tfor (JDDNode var : vars) {\n\t\t\tint index = var.getIndex();\n\t\t\tif (index < lastIndex) {\n\t\t\t\terror(\"JDDVars are not sorted: \" + vars);\n\t\t\t}\n\t\t\tlastIndex = index;\n\t\t}\n\t}\n\n\t/**\n\t * Perform sanity check:\n\t * Ensure that node has no relevant variables outside of the allowedVars.\n\t * <br>\n\t * Throws a RuntimeException if the test fails.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void checkIsDDOverVars(JDDNode node, JDDVars... allowedVars)\n\t{\n\t\tJDDNode cube = null;\n\t\tJDDNode support = null;\n\t\tJDDNode combined = null;\n\n\t\ttry {\n\t\t\t// cube of the combined JDDVars\n\t\t\tcube = JDD.Constant(1);\n\t\t\tfor (JDDVars vars : allowedVars) {\n\t\t\t\tcube = JDD.And(cube, vars.toCubeSet());\n\t\t\t}\n\n\t\t\t// the support of the node, a cube as well\n\t\t\tsupport = JDD.GetSupport(node);\n\t\t\t// If all variables in the support of node are also\n\t\t\t// variables in the cube, ANDing them will not change\n\t\t\t// the cube. If this is not the case, then there are\n\t\t\t// variables in the support that are not in the cube\n\t\t\tcombined = JDD.And(support.copy(), cube.copy());\n\t\t\tif (!combined.equals(cube)) {\n\t\t\t\terror(\"MTBDD has unexpected essential variables\");\n\t\t\t}\n\t\t} finally {\n\t\t\tif (support != null)\n\t\t\t\tJDD.Deref(support);\n\t\t\tif (cube != null)\n\t\t\t\tJDD.Deref(cube);\n\t\t\tif (combined != null)\n\t\t\t\tJDD.Deref(combined);\n\t\t}\n\t}\n\t\n\t/**\n\t * Perform sanity check:\n\t * Ensure that node is a state set over the given state variables.\n\t * <br>\n\t * Throws a RuntimeException if the test fails.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static void checkIsStateSet(JDDNode node, JDDVars vars)\n\t{\n\t\tcheckIsZeroOneMTBDD(node);\n\t\tcheckIsDDOverVars(node, vars);\n\t}\n\n\t/** Generic check method, raise error with the given message if value is false */\n\tpublic static void check(boolean value, String message)\n\t{\n\t\tif (!value) {\n\t\t\terror(message);\n\t\t}\n\t}\n\n\t/** Throw error */\n\tprivate static void error(String message)\n\t{\n\t\tthrow new RuntimeException(message);\n\t}\n}\n"
  },
  {
    "path": "prism/src/jdd/package-info.java",
    "content": "/**\n * A Java library providing a wrapper around the dd library and hence Java access to CUDD via JNI.\n */\npackage jdd;\n"
  },
  {
    "path": "prism/src/jltl2ba/APElement.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2007 Carlos Bederian\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jltl2ba;\n\nimport java.util.BitSet;\n\n/**\n * Class representing an element of 2^AP. \n */\npublic class APElement extends MyBitSet {\n\t\n\tpublic APElement() {\n\t\tsuper();\n\t}\n\t\n\tpublic APElement(int size) {\n\t\tsuper(size);\n\t}\n\t\n\tpublic APElement(MyBitSet m) {\n\t\tsuper(m.size());\n\t\tfor (Integer i : m) {\n\t\t\tthis.set(i);\n\t\t}\n\t}\n\t\n\tpublic String toString(APSet ap_set, boolean spaces) \n\t{\n\t\tif (ap_set.size()==0) {return \"true\";}\n\t\tString r = \"\";\n\t\tfor (int i = 0; i < ap_set.size(); i++) {\n\t\t\tif (i>=1) {\n\t\t\t\tr += \"&\";\n\t\t\t}\n\t\t\tif (!this.get(i)) {\n\t\t\t\tr += \"!\";\n\t\t\t} else {\n\t\t\t\tif (spaces) {\n\t\t\t\t\tr +=\" \";\n\t\t\t\t}\n\t\t\t}\n\t\t\tr += ap_set.getAP(i);\n\t\t}\n\t\treturn r;\n\t}\n\n\t/**\n\t * Return a string representation of this APElement in LBTT format (transition label)\n\t * @param ap_set the underlying AP set\n\t */\n\tpublic String toStringLBTT(APSet ap_set)\n\t{\n\t\tif (ap_set.size()==0) {return \"t\";}\n\t\tStringBuilder sb = new StringBuilder();\n\t\tfor (int i = 1; i < ap_set.size(); i++) {\n\t\t\tsb.append(\"& \");\n\t\t}\n\t\tfor (int i = 0; i < ap_set.size(); i++) {\n\t\t\tif (!this.get(i)) {\n\t\t\t\tsb.append(\"!\");\n\t\t\t}\n\t\t\tsb.append(ap_set.getAP(i));\n\t\t\tsb.append(\" \");\n\t\t}\n\t\treturn sb.toString();\n\t}\n\n\t/**\n\t * Return a string representation of this APElement in HOA format (transition label)\n\t * @param apSetSize the size of the underlying AP set\n\t */\n\tpublic String toStringHOA(int apSetSize)\n\t{\n\t\treturn toStringHOA(this, apSetSize);\n\t}\n\n\t/**\n\t * Return a string representation of a transition label in HOA format,\n\t * where the active/inactive APs are given as a BitSet.\n\t * @param label the set of APs that are active\n\t * @param apSetSize the size of the underlying AP set\n\t */\n\tpublic static String toStringHOA(BitSet label, int apSetSize)\n\t{\n\t\tif (apSetSize == 0) {\n\t\t\treturn \"t\";\n\t\t}\n\n\t\tStringBuilder sb = new StringBuilder();\n\t\tfor (int i=0; i < apSetSize; i++) {\n\t\t\tif (i > 0) sb.append(\"&\");\n\t\t\tif (label.get(i)) {\n\t\t\t\tsb.append(\" \"+i);\n\t\t\t} else {\n\t\t\t\tsb.append(\"!\"+i);\n\t\t\t}\n\t\t}\n\t\treturn sb.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/APElementIterator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2007 Carlos Bederian\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jltl2ba;\n\nimport java.util.Iterator;\nimport java.util.NoSuchElementException;\n\npublic class APElementIterator implements Iterator<APElement> {\n\t\n\tprivate APElement it;\n\tprivate int _size;\n\t\n\t// Iterator linked to a bitset\n\tpublic APElementIterator(APElement ap_elem) {\n\t\t_size = ap_elem.size();\n\t\tit = new APElement(_size);\n\t}\n\t\n\t// Iterator to 2^size elements\n\tpublic APElementIterator(int size) {\n\t\t_size = size;\n\t\tit = new APElement(size);\n\t}\n\t\n\tpublic boolean hasNext() {\n\t\treturn !it.get(_size); \n\t}\n\t\n\tpublic APElement next() throws NoSuchElementException {\n\t\tif (hasNext()) {\n\t\t\tAPElement tmp = (APElement) it.clone();\n\t\t\tit.increment();\n\t\t\treturn tmp;\n\t\t}\n\t\telse throw new NoSuchElementException();\n\t}\n\t\n\tpublic void remove() throws UnsupportedOperationException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/APSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2007 Carlos Bederian\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jltl2ba;\n\nimport java.util.Collections;\nimport java.util.List;\nimport java.util.Vector;\nimport java.util.Iterator;\nimport java.io.PrintStream;\n\n/**\n * Class representing a set of atomic propositions (AP).\n * The APs are ordered, in insertion order.\n */\npublic class APSet implements Iterable<String>\n{\n\n\tprivate Vector<String> vector;\n\n\t/**\n\t * Constructor.\n\t */\n\tpublic APSet()\n\t{\n\t\tvector = new Vector<String>();\n\t}\n\n\t/**\n\t * Adds a new AP to the set.\n\t * @param name the name of the AP\n\t * @return the index of the added AP\n\t */\n\tpublic int addAP(String name)\n\t{\n\t\tint i = vector.indexOf(name);\n\n\t\tif (i == -1) {\n\t\t\tvector.add(name);\n\t\t\treturn vector.size() - 1;\n\t\t} else\n\t\t\treturn i;\n\t}\n\n\t/**\n\t * Gets the name of a certain AP.\n\t * @param index index of the AP\n\t * @return string-ref with the name\n\t */\n\tpublic String getAP(int index)\n\t{\n\t\treturn vector.elementAt(index);\n\t}\n\n\t/**\n\t * Searches for an existing AP in the APSet and returns the index.\n\t * @return the index of the AP, or -1 if not found.\n\t */\n\tpublic int indexOf(String s)\n\t{\n\t\treturn vector.indexOf(s);\n\t}\n\n\tpublic boolean hasAP(String s)\n\t{\n\t\treturn vector.contains(s);\n\t}\n\n\t/**\n\t * Returns an (unmodifiable) List view of this AP set.\n\t * To modify this APSet, use the {@code addAP} method.\n\t */\n\tpublic List<String> asList()\n\t{\n\t\treturn Collections.unmodifiableList(vector);\n\t}\n\n\t/**\n\t * Get the size of this set\n\t * @return the number of APs in this set.\n\t */\n\tpublic int size()\n\t{\n\t\treturn vector.size();\n\t}\n\n\t/**\n\t * Get the size of the powerset 2^APSet\n\t * @return the size of 2^AP\n\t */\n\tpublic int powersetSize()\n\t{\n\t\treturn (1 << size());\n\t}\n\n\t/**\n\t * Equality check.\n\t * @param other the other APSet\n\t * @return <b>true</b> if this and the other APSet are equal\n\t */\n\tpublic boolean equals(APSet other)\n\t{\n\t\treturn this.vector.equals(other.vector);\n\t}\n\n\tpublic boolean equals(Object other)\n\t{\n\t\treturn ((other instanceof APSet) && this.equals((APSet) other));\n\t}\n\n\t/**\n\t * Create a new APSet with the same number of\n\t * atomic propositions, but named 'p0', 'p1', 'p2', ...\n\t * @return the newly created APSet\n\t */\n\tpublic APSet createCanonical()\n\t{\n\t\tAPSet canonical = new APSet();\n\t\tfor (int i = 0; i < size(); i++)\n\t\t\tcanonical.addAP(\"p\" + i);\n\t\treturn canonical;\n\t}\n\n\t/** Returns an iterator over the atomic propositions in this set */\n\tpublic Iterator<String> iterator()\n\t{\n\t\treturn vector.iterator();\n\t}\n\n\t/**\n\t * Returns an Iterator over the APElements induced by this AP set,\n\t * i.e., all possible subsets for the AP set.\n\t */\n\tpublic Iterator<APElement> elementIterator()\n\t{\n\t\treturn new APElementIterator(vector.size());\n\t}\n\n\t/**\n\t * Returns an Iterable over the APElements induced by this AP set,\n\t * i.e., all possible subsets for the AP set.\n\t */\n\tpublic Iterable<APElement> elements()\n\t{\n\t\treturn new Iterable<APElement>()\n\t\t{\n\t\t\t@Override\n\t\t\tpublic Iterator<APElement> iterator()\n\t\t\t{\n\t\t\t\treturn elementIterator();\n\t\t\t}\n\n\t\t};\n\t}\n\n\t/** Print this AP set */\n\tpublic void print(PrintStream out)\n\t{\n\t\tfor (int i = 0; i < size(); i++) {\n\t\t\tout.println(i + \": \" + getAP(i));\n\t\t}\n\t}\n\n\t/** Print this APSet as a HOA AP: header */\n\tpublic void print_hoa(PrintStream out)\n\t{\n\t\tout.print(\"AP: \");\n\t\tout.print(size());\n\t\tfor (String ap : this) {\n\t\t\t// TODO(JK): proper quoting\n\t\t\tout.print(\" \\\"\" + ap + \"\\\"\");\n\t\t}\n\t\tout.println();\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString rv = \"{\";\n\t\tfor (Iterator<String> it = this.iterator(); it.hasNext();) {\n\t\t\trv = rv + it.next();\n\t\t\tif (it.hasNext()) {\n\t\t\t\trv = rv + \",\";\n\t\t\t}\n\t\t}\n\t\treturn rv + \"}\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/Alternating.java",
    "content": "/* Written by Denis Oddoux, LIAFA, France                                 *\n * Copyright (c) 2001  Denis Oddoux                                       *\n * Modified by Paul Gastin, LSV, France                                   *\n * Copyright (c) 2007  Paul Gastin                                        *\n * Ported by Carlos Bederian, FaMAF, Argentina                            *\n * Copyright (c) 2007  Carlos Bederian                                    *\n *                                                                        *\n * This program is free software; you can redistribute it and/or modify   *\n * it under the terms of the GNU General Public License as published by   *\n * the Free Software Foundation; either version 2 of the License, or      *\n * (at your option) any later version.                                    *\n *                                                                        *\n * This program is distributed in the hope that it will be useful,        *\n * but WITHOUT ANY WARRANTY; without even the implied warranty of         *\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the          *\n * GNU General Public License for more details.                           *\n *                                                                        *\n * You should have received a copy of the GNU General Public License      *\n * along with this program; if not, write to the Free Software            *\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA*\n *                                                                        *\n * Based on the translation algorithm by Gastin and Oddoux,               *\n * presented at the 13th International Conference on Computer Aided       *\n * Verification, CAV 2001, Paris, France.                                 *\n * Proceedings - LNCS 2102, pp. 53-65                                     *\n *                                                                        */\n\npackage jltl2ba;\n\nimport java.util.Vector;\nimport java.io.PrintStream;\n\nimport jltl2ba.SimpleLTL;\nimport prism.PrismException;\n\npublic class Alternating {\n\tpublic int astate_count;\n\tpublic int atrans_count;\n\tprivate Vector<SimpleLTL> done;\n\tpublic Vector<ATrans> transition;\n\tpublic MyBitSet final_set;\n\tpublic APSet sym_table;\n\n\tpublic static class ATrans {\n\t\tpublic MyBitSet to; // nodes\n\t\tpublic MyBitSet pos; // syms\n\t\tpublic MyBitSet neg; // syms\n\t\tpublic ATrans nxt;\n\n\t\tpublic ATrans() {\n\t\t\tto = new MyBitSet();\n\t\t\tpos = new MyBitSet();\n\t\t\tneg = new MyBitSet();\n\t\t\tnxt = null;\n\t\t}\n\n\t\tpublic ATrans(MyBitSet _to, MyBitSet _pos, MyBitSet _neg) {\n\t\t\tto = (MyBitSet) _to.clone();\n\t\t\tpos = (MyBitSet) _pos.clone();\n\t\t\tneg = (MyBitSet) _neg.clone();\n\t\t\tnxt = null;\n\t\t}\n\n\t\tpublic ATrans clone() {\n\t\t\tATrans rv = new ATrans(to, pos, neg);\n\t\t\trv.nxt = nxt;\n\t\t\treturn rv;\n\t\t}\n\t}\n\t\n\tpublic static ATrans do_merge_atrans(ATrans first, ATrans second) {\n\t\tif (first == null || second == null)\n\t\t\treturn null;\n\n\t\tATrans rv = first.clone();\n\t\trv.nxt = null;\n\n\t\trv.to.or(second.to);\n\t\trv.pos.or(second.pos);\n\t\trv.neg.or(second.neg);\n\n\t\tif (rv.pos.intersects(rv.neg))\n\t\t\trv = null;\n\t\treturn rv;\n\t}\n\n\tpublic static class AProd {\n\t\tpublic int astate;\n\t\tpublic ATrans prod;\n\t\tpublic ATrans trans;\n\t\tpublic AProd nxt;\n\t\tpublic AProd prv;\n\n\t\tpublic AProd() {\n\t\t\t;\n\t\t}\n\t}\n\n\tpublic Alternating(SimpleLTL formula, APSet apset) throws PrismException {\n\t\tastate_count = 0;\n\t\tatrans_count = 0;\n\t\tfinal_set = new MyBitSet();\n\t\ttransition = new Vector<ATrans>();\n\t\tdone = new Vector<SimpleLTL>();\n\t\tsym_table = apset;\n\t\tSimpleLTL p = formula.clone();\n\t\t// System.out.println(\"formula: \" + p.toString());\n\t\tp = p.simplify();\n\t\t// System.out.println(\"after simplification: \" + p.toString());\n\n\t\tdone.add(null); // Reserve 0\n\t\ttransition.add(null);\n\t\ttransition.set(0, _boolean(p));\n\t\t// System.out.println(\"Alternating automaton before simplification\");\n\t\t// print(System.out);\n\t\tsimplifyAStates();\n\t\t// System.out.println(\"Alternating automaton after simplification\");\n\t\t// print(System.out);\n\t\tdone.clear();\n\t}\n\n\t/* computes the transitions to boolean nodes -> next & init */\n\tprivate ATrans _boolean(SimpleLTL p) {\n\t\tATrans t1, t2, lft, rgt, result = null;\n\n\t\tswitch (p.kind) {\n\t\tcase TRUE:\n\t\t\tresult = new ATrans();\n\t\t\tbreak;\n\t\tcase FALSE:\n\t\t\tbreak;\n\t\tcase AND:\n\t\t\tlft = _boolean(p.left);\n\t\t\trgt = _boolean(p.right);\n\t\t\tfor (t1 = lft; t1 != null; t1 = t1.nxt) {\n\t\t\t\tfor (t2 = rgt; t2 != null; t2 = t2.nxt) {\n\t\t\t\t\tATrans tmp = do_merge_atrans(t1, t2);\n\t\t\t\t\tif (tmp != null) {\n\t\t\t\t\t\ttmp.nxt = result;\n\t\t\t\t\t\tresult = tmp;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\t\tcase OR:\n\t\t\tlft = _boolean(p.left);\n\t\t\tfor (t1 = lft; t1 != null; t1 = t1.nxt) {\n\t\t\t\tATrans tmp = t1.clone();\n\t\t\t\ttmp.nxt = result;\n\t\t\t\tresult = tmp;\n\t\t\t}\n\t\t\trgt = _boolean(p.right);\n\t\t\tfor (t1 = rgt; t1 != null; t1 = t1.nxt) {\n\t\t\t\tATrans tmp = t1.clone();\n\t\t\t\ttmp.nxt = result;\n\t\t\t\tresult = tmp;\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tbuildAlternating(p);\n\t\t\tresult = new ATrans();\n\t\t\tresult.to.set(done.indexOf(p));\n\t\t}\n\t\treturn result;\n\t}\n\n\tprivate int getSymID(String ap) {\n\t\treturn sym_table.addAP(ap);\n\t}\n\n\t/* builds an alternating automaton for p */\n\tprivate ATrans buildAlternating(SimpleLTL p) {\n\t\tATrans t1, t2, t = null;\n\n\t\tif (done.contains(p))\n\t\t\treturn transition.get(done.indexOf(p));\n\n\t\tswitch (p.kind) {\n\n\t\tcase TRUE:\n\t\t\tt = new ATrans();\n\t\t\tbreak;\n\n\t\tcase FALSE:\n\t\t\tbreak;\n\n\t\tcase AP:\n\t\t\tt = new ATrans();\n\t\t\tt.pos.set(getSymID(p.ap));\n\t\t\tbreak;\n\n\t\tcase NOT:\n\t\t\tt = new ATrans();\n\t\t\tt.neg.set(getSymID(p.left.ap)); // Should be in negated normal form\n\t\t\tbreak;\n\n\t\tcase NEXT:\n\t\t\tt = _boolean(p.left);\n\t\t\tbreak;\n\n\t\tcase UNTIL: /* p U q <-> q || (p && X (p U q)) */\n\t\t\tfor (t2 = buildAlternating(p.right); t2 != null; t2 = t2.nxt) {\n\t\t\t\tATrans tmp = t2.clone(); /* q */\n\t\t\t\ttmp.nxt = t;\n\t\t\t\tt = tmp;\n\t\t\t}\n\t\t\tfor (t1 = buildAlternating(p.left); t1 != null; t1 = t1.nxt) {\n\t\t\t\tATrans tmp = t1.clone(); /* p */\n\t\t\t\ttmp.to.set(done.size()); /* X (p U q) */\n\t\t\t\ttmp.nxt = t;\n\t\t\t\tt = tmp;\n\t\t\t}\n\t\t\tfinal_set.set(done.size());\n\t\t\tbreak;\n\n\t\tcase RELEASE: /* p V q <-> (p && q) || (q && X (p V q)) */\n\t\t\tfor (t1 = buildAlternating(p.right); t1 != null; t1 = t1.nxt) {\n\t\t\t\tATrans tmp;\n\n\t\t\t\tfor (t2 = buildAlternating(p.left); t2 != null; t2 = t2.nxt) {\n\t\t\t\t\ttmp = do_merge_atrans(t1, t2); /* p && q */\n\t\t\t\t\tif (tmp != null) {\n\t\t\t\t\t\ttmp.nxt = t;\n\t\t\t\t\t\tt = tmp;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\ttmp = t1.clone(); /* q */\n\t\t\t\ttmp.to.set(done.size()); /* X (p V q) */\n\t\t\t\ttmp.nxt = t;\n\t\t\t\tt = tmp;\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase AND:\n\t\t\tfor (t1 = buildAlternating(p.left); t1 != null; t1 = t1.nxt) {\n\t\t\t\tfor (t2 = buildAlternating(p.right); t2 != null; t2 = t2.nxt) {\n\t\t\t\t\tATrans tmp = do_merge_atrans(t1, t2);\n\t\t\t\t\tif (tmp != null) {\n\t\t\t\t\t\ttmp.nxt = t;\n\t\t\t\t\t\tt = tmp;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase OR:\n\t\t\tfor (t1 = buildAlternating(p.left); t1 != null; t1 = t1.nxt) {\n\t\t\t\tATrans tmp = t1.clone();\n\t\t\t\ttmp.nxt = t;\n\t\t\t\tt = tmp;\n\t\t\t}\n\t\t\tfor (t1 = buildAlternating(p.right); t1 != null; t1 = t1.nxt) {\n\t\t\t\tATrans tmp = t1.clone();\n\t\t\t\ttmp.nxt = t;\n\t\t\t\tt = tmp;\n\t\t\t}\n\t\t\tbreak;\n\n\t\tdefault:\n\t\t\tbreak;\n\t\t}\n\t\ttransition.add(t);\n\t\tdone.add(p);\n\t\treturn t;\n\t}\n\n\tprivate ATrans simplifyATrans(ATrans trans) {\n\t\tATrans t, father = null;\n\t\tATrans _trans = trans;\n\t\tfor (t = _trans; t != null;) {\n\t\t\tATrans t1;\n\t\t\tfor (t1 = _trans; t1 != null; t1 = t1.nxt) {\n\t\t\t\tif ((t1 != t) && t.to.containsAll(t1.to)\n\t\t\t\t\t\t&& t.pos.containsAll(t1.pos)\n\t\t\t\t\t\t&& t.neg.containsAll(t1.neg))\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (t1 != null) {\n\t\t\t\tif (father != null)\n\t\t\t\t\tfather.nxt = t.nxt;\n\t\t\t\telse\n\t\t\t\t\t_trans = t.nxt;\n\t\t\t\tif (father != null)\n\t\t\t\t\tt = father.nxt;\n\t\t\t\telse\n\t\t\t\t\tt = _trans;\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tatrans_count++;\n\t\t\tfather = t;\n\t\t\tt = t.nxt;\n\t\t}\n\t\treturn _trans;\n\t}\n\n\t/* simplifies the alternating automaton */\n\tprivate void simplifyAStates() {\n\t\tATrans t;\n\t\tint i;\n\t\tMyBitSet acc = new MyBitSet(); /* no state is accessible initially */\n\n\t\tfor (t = transition.get(0); t != null; t = t.nxt, i = 0)\n\t\t\tacc.or(t.to); /* all initial states are accessible */\n\n\t\tfor (i = transition.size() - 1; i > 0; i--) {\n\t\t\tif (!acc.get(i)) { // frees unaccessible states\n\t\t\t\tdone.set(i, null);\n\t\t\t\ttransition.set(i, null);\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tastate_count++;\n\t\t\ttransition.set(i, simplifyATrans(transition.get(i)));\n\t\t\tfor (t = transition.get(i); t != null; t = t.nxt)\n\t\t\t\tacc.or(t.to);\n\t\t}\n\t}\n\n\t/* dumps the alternating automaton */\n\tpublic void print(PrintStream out) {\n\t\tint i;\n\t\tATrans t;\n\n\t\tout.print(\"init :\\n\");\n\t\tfor (t = transition.get(0); t != null; t = t.nxt) {\n\t\t\tt.to.print(out);\n\t\t\tout.println();\n\t\t}\n\n\t\tfor (i = done.size() - 1; i > 0; i--) {\n\t\t\tif (done.get(i) == null)\n\t\t\t\tcontinue;\n\t\t\tout.format(\"state %d : \", i);\n\t\t\tout.print(done.get(i).toString());\n\t\t\tout.println();\n\t\t\tfor (t = transition.get(i); t != null; t = t.nxt) {\n\t\t\t\tif (t.pos.isEmpty() && t.neg.isEmpty())\n\t\t\t\t\tout.print(\"1\");\n\t\t\t\tt.pos.print(out, sym_table, true);\n\t\t\t\tif (!t.pos.isEmpty() && !t.neg.isEmpty())\n\t\t\t\t\tout.print(\" & \");\n\t\t\t\tt.neg.print(out, sym_table, false);\n\t\t\t\tout.print(\" -> \");\n\t\t\t\tt.to.print(out);\n\t\t\t\tout.println();\n\t\t\t}\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/jltl2ba/Buchi.java",
    "content": "/* Written by Denis Oddoux, LIAFA, France                                 *\n * Copyright (c) 2001  Denis Oddoux                                       *\n * Modified by Paul Gastin, LSV, France                                   *\n * Copyright (c) 2007  Paul Gastin                                        *\n * Ported by Carlos Bederian, FaMAF, Argentina                            *\n * Copyright (c) 2007  Carlos Bederian                                    *\n *                                                                        *\n * This program is free software; you can redistribute it and/or modify   *\n * it under the terms of the GNU General Public License as published by   *\n * the Free Software Foundation; either version 2 of the License, or      *\n * (at your option) any later version.                                    *\n *                                                                        *\n * This program is distributed in the hope that it will be useful,        *\n * but WITHOUT ANY WARRANTY; without even the implied warranty of         *\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the          *\n * GNU General Public License for more details.                           *\n *                                                                        *\n * You should have received a copy of the GNU General Public License      *\n * along with this program; if not, write to the Free Software            *\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA*\n *                                                                        *\n * Based on the translation algorithm by Gastin and Oddoux,               *\n * presented at the 13th International Conference on Computer Aided       *\n * Verification, CAV 2001, Paris, France.                                 *\n * Proceedings - LNCS 2102, pp. 53-65                                     *\n *                                                                        */\n\npackage jltl2ba;\n\nimport java.util.Vector;\nimport java.util.HashMap;\nimport java.io.PrintStream;\n\nimport jltl2dstar.APMonom;\nimport jltl2dstar.NBA;\n\nimport prism.PrismException;\n\npublic class Buchi {\n\n\tprivate int init_size;\n\tprivate Vector<Generalized.GState> g_init;\n\tprivate Vector<Integer> _final;\n\t// private Generalized.GState gstates;\n\t\n\tprivate BState bstack;\n\tprivate BState bstates;\n\tprivate BState bremoved;\n\tprivate BScc scc_stack;\n\tprivate int accept;\n\tprivate int bstate_count;\n\tprivate int btrans_count;\n\tprivate int rank;\n\t\n\t// the highest id used for a BState.id\n\tprivate int max_id;\n\n\tpublic static class BState {\n\t\tGeneralized.GState gstate;\n\t\tpublic int id;\n\t\tpublic int incoming;\n\t\tpublic int _final;\n\t\tBTrans trans;\n\t\tBState nxt;\n\t\tBState prv;\n\t\t\n\t\tpublic BState() { ; }\n\t\t\n\t\tpublic void free()\n\t\t{\n\t\t\tif (trans.nxt != null)\n\t\t\t\ttrans.nxt.free(trans, true);\n\t\t}\n\t}\n\n\tpublic static class BScc {\n\t\tBState bstate;\n\t\tint rank;\n\t\tint theta;\n\t\tBScc nxt;\n\t\t\n\t\tpublic BScc() { ; }\n\t}\n\n\tpublic class BTrans {\n\t\tpublic MyBitSet pos;\n\t\tpublic MyBitSet neg;\n\t\tpublic BState to;\n\t\tpublic BTrans nxt;\n\t\t\n\t\tpublic BTrans()\n\t\t{\n\t\t\tpos = new MyBitSet();\n\t\t\tneg = new MyBitSet();\n\t\t\tnxt = null;\n\t\t\tto = null;\n\t\t}\n\t\t\n\t\tpublic BTrans(MyBitSet _pos, MyBitSet _neg)\n\t\t{\n\t\t\tpos = (MyBitSet) _pos.clone();\n\t\t\tneg = (MyBitSet) _neg.clone();\n\t\t\tnxt = null;\n\t\t\tto = null;\n\t\t}\n\t\t\n\t\tpublic BTrans clone()\n\t\t{\n\t\t\tBTrans rv = new BTrans(pos, neg);\n\t\t\trv.to = to;\n\t\t\trv.nxt = nxt;\n\t\t\treturn rv;\n\t\t}\n\t\t\n\t\tpublic void copyTo(BTrans b)\n\t\t{\n\t\t\tb.pos = (MyBitSet) pos.clone();\n\t\t\tb.neg = (MyBitSet) neg.clone();\n\t\t\tb.to = to;\n\t\t}\n\t\t\n\t\tpublic void free(BTrans sentinel, boolean fly)\n\t\t{\n\t\t\tif (this != sentinel) {\n\t\t\t\tnxt.free(sentinel, fly);\n\t\t\t\tif (fly)\n\t\t\t\t\tto.incoming--;\n\t\t\t}\n\t\t}\n\t}\n\t\n\tpublic Buchi(Generalized g)\n\t{\t\t\t\t/* generates a Buchi automaton from the generalized Buchi automaton */\n\t\tinit_size = g.init_size;\n\t\tg_init = g.g_init;\n\t\t_final = g._final;\n\t\t// gstates = g.gstates;\n\t\tmax_id = g.getGStateID();\n\t\t\n\t\tint i;\n\t\tBState s = new BState();\n\t\tGeneralized.GTrans t;\n\t\tBTrans t1;\n\t\taccept = g._final.size();\n\t\tbstate_count = 0;\n\t\tbtrans_count = 0;\n\n\t\tbstack = new BState();\n\t\tbstack.nxt = bstack;\n\t\tbremoved = new BState();\n\t\tbremoved.nxt = bremoved;\n\t\tbstates = new BState();\n\t\tbstates.nxt = s;\n\t\tbstates.prv = s;\n\n\t\ts.nxt = bstates;\t/* creates (unique) inital state */\n\t\ts.prv = bstates;\n\t\ts.id = -1;\n\t\ts.incoming = 1;\n\t\ts._final = 0;\n\t\ts.gstate = null;\n\t\ts.trans = new BTrans();\t/* sentinel */\n\t\ts.trans.nxt = s.trans;\n\t\tfor (i = 0; i < init_size; i++) {\n\t\t\tif (g_init.get(i) != null) {\n\t\t\t\tfor (t = g_init.get(i).trans.nxt; t != g_init.get(i).trans; t = t.nxt) {\n\t\t\t\t\tint fin = nextFinal(t._final, 0);\n\t\t\t\t\tBState to = findBState(t.to, fin, s);\n\t\t\t\t\tfor (t1 = s.trans.nxt; t1 != s.trans;) {\n\t\t\t\t\t\tif ((to == t1.to) && t1.pos.containsAll(t.pos) && t1.neg.containsAll(t.neg)) {\t/* t1 is redundant */\n\t\t\t\t\t\t\tBTrans free = t1.nxt;\n\t\t\t\t\t\t\tt1.to.incoming--;\n\t\t\t\t\t\t\tt1.to = free.to;\n\t\t\t\t\t\t\tt1.pos = (MyBitSet) free.pos.clone();\n\t\t\t\t\t\t\tt1.neg = (MyBitSet) free.neg.clone();\n\t\t\t\t\t\t\tt1.nxt = free.nxt;\n\t\t\t\t\t\t\tif (free == s.trans)\n\t\t\t\t\t\t\t\ts.trans = t1;\n\t\t\t\t\t\t\tfree = null;\n\t\t\t\t\t\t} else if ((t1.to == to) && t.pos.containsAll(t1.pos) && t.neg.containsAll(t1.neg))\t/* t is redundant */\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\tt1 = t1.nxt;\n\t\t\t\t\t}\n\t\t\t\t\tif (t1 == s.trans) {\n\t\t\t\t\t\tBTrans trans = new BTrans();\n\t\t\t\t\t\ttrans.to = to;\n\t\t\t\t\t\ttrans.to.incoming++;\n\t\t\t\t\t\ttrans.pos = (MyBitSet) t.pos.clone();\n\t\t\t\t\t\ttrans.neg = (MyBitSet) t.neg.clone();\n\t\t\t\t\t\ttrans.nxt = s.trans.nxt;\n\t\t\t\t\t\ts.trans.nxt = trans;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\twhile (bstack.nxt != bstack) {\t/* solves all states in the stack until it is empty */\n\t\t\ts = bstack.nxt;\n\t\t\tbstack.nxt = bstack.nxt.nxt;\n\t\t\tif (s.incoming == 0) {\n\t\t\t\ts.free();\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tmakeBTrans(s);\n\t\t}\n\t\tretargetAllBTrans();\n\t\t\n\t\t// System.out.println(\"Buchi automaton before simplification:\");\n\t\t// print_spin(System.out, symtab);\n\n\t\tsimplifyBTrans();\n\t\tsimplifyBScc();\n\t\twhile (simplifyBStates() != 0) {\t/* simplifies as much as possible */\n\t\t\tsimplifyBTrans();\n\t\t\tsimplifyBScc();\n\t\t}\n\t\t// System.out.println(\"Buchi automaton after simplification:\");\n\t\t// print_spin(System.out, symtab);\n\n\t}\n\n\tprivate int nextFinal(MyBitSet set, int fin)\n\t{\t\t\t\t/* computes the 'final' value */\n\t\tif ((fin != accept) && set.get(_final.get(fin)))\n\t\t\treturn nextFinal(set, fin + 1);\n\t\treturn fin;\n\t}\n\n\tprivate BState findBState(Generalized.GState state, int _final, BState s)\n\t{\t\n\t\t/* finds the corresponding state, or creates it */\n\t\tif ((s.gstate == state) && (s._final == _final))\n\t\t\treturn s;\t/* same state */\n\n\t\ts = bstack.nxt;\t/* in the stack */\n\t\tbstack.gstate = state;\n\t\tbstack._final = _final;\n\t\twhile (!(s.gstate == state) || !(s._final == _final))\n\t\t\ts = s.nxt;\n\t\tif (s != bstack)\n\t\t\treturn s;\n\n\t\ts = bstates.nxt;\t/* in the solved states */\n\t\tbstates.gstate = state;\n\t\tbstates._final = _final;\n\t\twhile (!(s.gstate == state) || !(s._final == _final))\n\t\t\ts = s.nxt;\n\t\tif (s != bstates)\n\t\t\treturn s;\n\n\t\ts = bremoved.nxt;\t/* in the removed states */\n\t\tbremoved.gstate = state;\n\t\tbremoved._final = _final;\n\t\twhile (!(s.gstate == state) || !(s._final == _final))\n\t\t\ts = s.nxt;\n\t\tif (s != bremoved)\n\t\t\treturn s;\n\n\t\ts = new BState();\n\t\ts.gstate = state;\n\t\ts.id = state.id;\n\t\ts.incoming = 0;\n\t\ts._final = _final;\n\t\ts.trans = new BTrans();\n\t\ts.trans.nxt = s.trans;\n\t\ts.nxt = bstack.nxt;\n\t\tbstack.nxt = s;\n\t\treturn s;\n\t}\n\t\n\tprivate boolean sameBTrans(BTrans s, BTrans t)\n\t{\t\n\t\t/* returns 1 if the transitions are identical */\n\t\treturn ((s.to == t.to) &&\n\t\t\ts.pos.equals(t.pos) && s.neg.equals(t.neg));\n\t}\n\t\n\tprivate boolean allBTransMatch(BState a, BState b)\n\t{\t\n\t\t/* decides if the states are equivalent */\n\t\tBTrans s, t;\n\t\t\n\t\t/* the states have to be both final or both non final,\n\t\t * or at least one of them has to be in a trivial SCC\n\t\t * (incoming == -1), as the acceptance condition of\n\t\t * such a state can be modified without changing the\n\t\t * language of the automaton\n\t\t */\n\t\tif (((a._final == accept) || (b._final == accept)) &&\n\t\t    (a._final + b._final != 2 * accept) /* final condition of a and b differs */\n\t\t    && a.incoming >= 0   /* a is not in a trivial SCC */\n\t\t    && b.incoming >= 0)  /* b is not in a trivial SCC */\n\t\t\treturn false;   /* states can not be matched */\n\n\t\tfor (s = a.trans.nxt; s != a.trans; s = s.nxt) {\n\t\t\t/* all transitions from a appear in b */\n\t\t\ts.copyTo(b.trans);\n\t\t\tt = b.trans.nxt;\n\t\t\twhile (!sameBTrans(s, t))\n\t\t\t\tt = t.nxt;\n\t\t\tif (t == b.trans)\n\t\t\t\treturn false;\n\t\t}\n\t\tfor (s = b.trans.nxt; s != b.trans; s = s.nxt) {\n\t\t\t/* all transitions from b appear in a */\n\t\t\ts.copyTo(a.trans);\n\t\t\tt = a.trans.nxt;\n\t\t\twhile (!sameBTrans(s, t))\n\t\t\t\tt = t.nxt;\n\t\t\tif (t == a.trans)\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\tprivate void makeBTrans(BState s)\n\t{\t\t\t\t/* creates all the transitions from a state */\n\t\tint state_trans = 0;\n\t\tGeneralized.GTrans t;\n\t\tBTrans t1;\n\t\tBState s1;\n\t\tif (s.gstate.trans != null)\n\t\t\tfor (t = s.gstate.trans.nxt; t != s.gstate.trans;\n\t\t\t     t = t.nxt) {\n\t\t\t\tint fin = nextFinal(t._final, (s._final == accept) ? 0 : s._final);\n\t\t\t\tBState to = findBState(t.to, fin, s);\n\n\t\t\t\tfor (t1 = s.trans.nxt; t1 != s.trans;) {\n\t\t\t\t\tif ((to == t1.to) && t1.pos.containsAll(t.pos) && t1.neg.containsAll(t.neg)) {\t/* t1 is redundant */\n\t\t\t\t\t\tBTrans free = t1.nxt;\n\t\t\t\t\t\tt1.to.incoming--;\n\t\t\t\t\t\tt1.to = free.to;\n\t\t\t\t\t\tt1.pos = (MyBitSet) free.pos.clone();\n\t\t\t\t\t\tt1.neg = (MyBitSet) free.neg.clone();\n\t\t\t\t\t\tt1.nxt = free.nxt;\n\t\t\t\t\t\tif (free == s.trans)\n\t\t\t\t\t\t\ts.trans = t1;\n\t\t\t\t\t\tfree = null;\n\t\t\t\t\t\tstate_trans--;\n\t\t\t\t\t} else if ((t1.to == to) && t.pos.containsAll(t1.pos) && t.neg.containsAll(t1.neg))\t/* t is redundant */\n\t\t\t\t\t\tbreak;\n\t\t\t\t\telse\n\t\t\t\t\t\tt1 = t1.nxt;\n\t\t\t\t}\n\t\t\t\tif (t1 == s.trans) {\n\t\t\t\t\tBTrans trans = new BTrans();\n\t\t\t\t\ttrans.to = to;\n\t\t\t\t\ttrans.to.incoming++;\n\t\t\t\t\ttrans.pos = (MyBitSet) t.pos.clone();\n\t\t\t\t\ttrans.neg = (MyBitSet) t.neg.clone();\n\t\t\t\t\ttrans.nxt = s.trans.nxt;\n\t\t\t\t\ts.trans.nxt = trans;\n\t\t\t\t\tstate_trans++;\n\t\t\t\t}\n\t\t\t}\n\n\t\tif (s.trans == s.trans.nxt) {\t/* s has no transitions */\n\t\t\ts.trans.nxt.free(s.trans, true);\n\t\t\ts.trans = null;\n\t\t\ts.prv = null;\n\t\t\ts.nxt = bremoved.nxt;\n\t\t\tbremoved.nxt = s;\n\t\t\tfor (s1 = bremoved.nxt; s1 != bremoved; s1 = s1.nxt)\n\t\t\t\tif (s1.prv == s)\n\t\t\t\t\ts1.prv = null;\n\t\t\treturn;\n\t\t}\n\t\tbstates.trans = s.trans;\n\t\tbstates._final = s._final;\n\t\ts1 = bstates.nxt;\n\t\twhile (!allBTransMatch(s, s1))\n\t\t\ts1 = s1.nxt;\n\t\tif (s1 != bstates) {\t/* s and s1 are equivalent */\n\t\t\ts.trans.nxt.free(s.trans, true);\n\t\t\ts.trans = null;\n\t\t\ts.prv = s1;\n\t\t\ts.nxt = bremoved.nxt;\n\t\t\tbremoved.nxt = s;\n\t\t\tfor (s1 = bremoved.nxt; s1 != bremoved; s1 = s1.nxt)\n\t\t\t\tif (s1.prv == s)\n\t\t\t\t\ts1.prv = s.prv;\n\t\t\treturn;\n\t\t}\n\t\ts.nxt = bstates.nxt;\t/* adds the current state to 'bstates' */\n\t\ts.prv = bstates;\n\t\ts.nxt.prv = s;\n\t\tbstates.nxt = s;\n\t\tbtrans_count += state_trans;\n\t\tbstate_count++;\n\t}\n\t\n\tprivate void retargetAllBTrans()\n\t{\t\n\t\t/* redirects transitions before removing a state from the automaton */\n\t\tBState s;\n\t\tBTrans t;\n\t\tfor (s = bstates.nxt; s != bstates; s = s.nxt)\n\t\t\tfor (t = s.trans.nxt; t != s.trans; t = t.nxt)\n\t\t\t\tif (t.to.trans == null) {\t/* t.to has been removed */\n\t\t\t\t\tt.to = t.to.prv;\n\t\t\t\t\tif (t.to == null) {\t/* t.to has no transitions */\n\t\t\t\t\t\tBTrans free = t.nxt;\n\t\t\t\t\t\tt.to = free.to;\n\t\t\t\t\t\tt.pos = (MyBitSet) free.pos.clone();\n\t\t\t\t\t\tt.neg = (MyBitSet) free.neg.clone();\n\t\t\t\t\t\tt.nxt = free.nxt;\n\t\t\t\t\t\tif (free == s.trans)\n\t\t\t\t\t\t\ts.trans = t;\n\t\t\t\t\t\tfree = null;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\twhile (bremoved.nxt != bremoved) {\t/* clean the 'removed' list */\n\t\t\ts = bremoved.nxt;\n\t\t\tbremoved.nxt = bremoved.nxt.nxt;\n\t\t\ts = null;\n\t\t}\n\t}\n\n\tprivate int simplifyBTrans()\n\t{\t\t\t\t/* simplifies the transitions */\n\t\tBState s;\n\t\tBTrans t, t1;\n\t\tint changed = 0;\n\n\t\tfor (s = bstates.nxt; s != bstates; s = s.nxt)\n\t\t\tfor (t = s.trans.nxt; t != s.trans;) {\n\t\t\t\tt1 = s.trans.nxt;\n\t\t\t\tt.copyTo(s.trans);\n\t\t\t\twhile ((t == t1) || (t.to != t1.to) ||\n\t\t\t\t       !t.pos.containsAll(t1.pos) ||\n\t\t\t\t       !t.neg.containsAll(t1.neg))\n\t\t\t\t\tt1 = t1.nxt;\n\t\t\t\tif (t1 != s.trans) {\n\t\t\t\t\tBTrans free = t.nxt;\n\t\t\t\t\tt.to = free.to;\n\t\t\t\t\tt.pos = (MyBitSet) free.pos.clone();\n\t\t\t\t\tt.neg = (MyBitSet) free.neg.clone();\n\t\t\t\t\tt.nxt = free.nxt;\n\t\t\t\t\tif (free == s.trans)\n\t\t\t\t\t\ts.trans = t;\n\t\t\t\t\tfree = null;\n\t\t\t\t\tchanged++;\n\t\t\t\t} else\n\t\t\t\t\tt = t.nxt;\n\t\t\t}\n\t\treturn changed;\n\t}\n\n\tprivate int bdfs(BState s)\n\t{\n\t\tBTrans t;\n\t\tBScc c;\n\t\tBScc scc = new BScc();\n\t\tscc.bstate = s;\n\t\tscc.rank = rank;\n\t\tscc.theta = rank++;\n\t\tscc.nxt = scc_stack;\n\t\tscc_stack = scc;\n\n\t\ts.incoming = 1;\n\n\t\tfor (t = s.trans.nxt; t != s.trans; t = t.nxt) {\n\t\t\tif (t.to.incoming == 0) {\n\t\t\t\tint result = bdfs(t.to);\n\t\t\t\tscc.theta = scc.theta < result ? scc.theta : result;\n\t\t\t} else {\n\t\t\t\tfor (c = scc_stack.nxt; c != null; c = c.nxt)\n\t\t\t\t\tif (c.bstate == t.to) {\n\t\t\t\t\t\tscc.theta = scc.theta < c.rank ? scc.theta : c.rank;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (scc.rank == scc.theta) {\n\t\t\tif (scc_stack == scc) {\t/* s is alone in a scc */\n\t\t\t\ts.incoming = -1;\n\t\t\t\tfor (t = s.trans.nxt; t != s.trans; t = t.nxt)\n\t\t\t\t\tif (t.to == s)\n\t\t\t\t\t\ts.incoming = 1;\n\t\t\t}\n\t\t\tscc_stack = scc.nxt;\n\t\t}\n\t\treturn scc.theta;\n\t}\n\t\n\tprivate BState removeBState(BState s, BState s1)\n\t{\t\t\t\t/* removes a state */\n\t\tBState prv = s.prv;\n\t\ts.prv.nxt = s.nxt;\n\t\ts.nxt.prv = s.prv;\n\t\ts.trans.nxt.free(s.trans, false);\n\t\ts.trans = null;\n\t\ts.nxt = bremoved.nxt;\n\t\tbremoved.nxt = s;\n\t\ts.prv = s1;\n\t\tfor (s1 = bremoved.nxt; s1 != bremoved; s1 = s1.nxt)\n\t\t\tif (s1.prv == s)\n\t\t\t\ts1.prv = s.prv;\n\t\treturn prv;\n\t}\n\n\tprivate void simplifyBScc()\n\t{\n\t\tBState s;\n\t\trank = 1;\n\t\tscc_stack = null;\n\n\t\tif (bstates == bstates.nxt)\n\t\t\treturn;\n\n\t\tfor (s = bstates.nxt; s != bstates; s = s.nxt)\n\t\t\ts.incoming = 0;\t/* state color = white */\n\n\t\tbdfs(bstates.prv);\n\n\t\tfor (s = bstates.nxt; s != bstates; s = s.nxt)\n\t\t\tif (s.incoming == 0)\n\t\t\t\tremoveBState(s, null);\n\t}\n\n\tprivate int simplifyBStates()\n\t{\t\n\t\t/* eliminates redundant states */\n\t\tBState s, s1;\n\t\tint changed = 0;\n\n\t\tfor (s = bstates.nxt; s != bstates; s = s.nxt) {\n\t\t\tif (s.trans == s.trans.nxt) {\t/* s has no transitions */\n\t\t\t\ts = removeBState(s, null);\n\t\t\t\tchanged++;\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tbstates.trans = s.trans;\n\t\t\tbstates._final = s._final;\n\t\t\ts1 = s.nxt;\n\t\t\twhile (!allBTransMatch(s, s1))\n\t\t\t\ts1 = s1.nxt;\n\t\t\tif (s1 != bstates) {\t/* s and s1 are equivalent */\n\t\t\t\t/* we now want to remove s and replace it by s1 */\n\t\t\t\tif (s1.incoming == -1) {  /* s1 is in a trivial SCC */\n\t\t\t\t\ts1._final = s._final;  /* change the final condition of s1 to that of s */\n\n\t\t\t\t\t/* We may have to update the SCC status of s1\n\t\t\t\t\t * stored in s1->incoming, because we will retarget the incoming\n\t\t\t\t\t * transitions of s to s1.\n\t\t\t\t\t *\n\t\t\t\t\t * If both s1 and s are in trivial SCC, then retargeting\n\t\t\t\t\t * the incoming transitions does not change the status of s1,\n\t\t\t\t\t * it remains in a trivial SCC.\n\t\t\t\t\t *\n\t\t\t\t\t * If s1 was in a trivial SCC, but s was not, then\n\t\t\t\t\t * s1 has to have a transition to s that corresponds to a\n\t\t\t\t\t * self-loop of s (as both states have the same outgoing transitions).\n\t\t\t\t\t * But then, s1 will not remain a trivial SCC after retargeting.\n\t\t\t\t\t * In particular, afterwards the final condition of s1 may not be\n\t\t\t\t\t * changed anymore.\n\t\t\t\t\t *\n\t\t\t\t\t * If both s1 and s are in non-trivial SCC, merging does not\n\t\t\t\t\t * change the SCC status of s1.\n\t\t\t\t\t *\n\t\t\t\t\t * If we are here, s1->incoming==1 and thus s1 forms a trivial SCC.\n\t\t\t\t\t * We therefore can set the status of s1 to that of s,\n\t\t\t\t\t * which correctly handles the first two cases above.\n\t\t\t\t\t */\n\t\t\t\t\ts1.incoming = s.incoming;\n\t\t\t\t}\n\t\t\t\ts = removeBState(s, s1);\n\t\t\t\tchanged++;\n\t\t\t}\n\t\t}\n\t\tretargetAllBTrans();\n\n\t\t /*\n\t\t  * As merging equivalent states can change the 'final' attribute of\n\t\t  * the remaining state, it is possible that now there are two\n\t\t  * different states with the same id and final values.\n\t\t  * This would lead to multiply-defined labels in the generated neverclaim.\n\t\t  * We iterate over all states and assign new ids (previously unassigned)\n\t\t  * to these states to disambiguate.\n\t\t  * Fix from ltl3ba.\n\t\t  */\n\t\tfor (s = bstates.nxt; s != bstates; s = s.nxt) {          /* For all states s*/\n\t\t\tfor (BState s2 = s.nxt; s2 != bstates; s2 = s2.nxt) { /*  and states s2 to the right of s */\n\t\t\t\tif(s._final == s2._final && s.id == s2.id) {      /* if final and id match */\n\t\t\t\t\ts.id = ++max_id;                              /* disambiguate by assigning unused id */\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn changed;\n\t}\n\n\tprivate void spin_print_sets(PrintStream out, APSet apset, MyBitSet pos, MyBitSet neg)\n\t{\t\t\t\t/* prints the content of a set for spin */\n\t\tint i;\n\t\tboolean start = true;\n\t\tfor (i = 0; i < (pos.size() > neg.size() ? pos.size() : neg.size()); i++) {\n\t\t\tif (pos.get(i)) {\n\t\t\t\tif (!start)\n\t\t\t\t\tout.print(\" && \");\n\t\t\t\tout.print(apset.getAP(i));\n\t\t\t\tstart = false;\n\t\t\t}\n\t\t\tif (neg.get(i)) {\n\t\t\t\tif (!start)\n\t\t\t\t\tout.print(\" && \");\n\t\t\t\tout.print(\"!\");\n\t\t\t\tout.print(apset.getAP(i));\n\t\t\t\tstart = false;\n\t\t\t}\n\t\t}\n\t\tif (start)\n\t\t\tout.print(\"1\");\n\t}\n\t\n\t\n\tpublic void print_spin(PrintStream out, APSet apset)\n\t{\n\t\tBTrans t;\n\t\tBState s;\n\t\tint accept_all = 0;\n\t\tif (bstates.nxt == bstates) {\t/* empty automaton */\n\t\t\tout.println(\"never {\");\n\t\t\tout.println(\"T0_init:\");\n\t\t\tout.println(\"\\tfalse;\");\n\t\t\tout.println(\"}\");\n\t\t\treturn;\n\t\t}\n\t\tif (bstates.nxt.nxt == bstates && bstates.nxt.id == 0) {\t/* true */\n\t\t\tout.println(\"never {\");\n\t\t\tout.println(\"accept_init:\");\n\t\t\tout.println(\"\\tif\");\n\t\t\tout.println(\"\\t:: (1) . goto accept_init\");\n\t\t\tout.println(\"\\tfi;\");\n\t\t\tout.println(\"}\");\n\t\t\treturn;\n\t\t}\n\n\t\tout.println(\"never {\");\n\t\tfor (s = bstates.prv; s != bstates; s = s.prv) {\n\t\t\tif (s.id == 0) {\t/* accept_all at the end */\n\t\t\t\taccept_all = 1;\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tif (s._final == accept)\n\t\t\t\tout.print(\"accept_\");\n\t\t\telse\n\t\t\t\tout.format(\"T%d_\", s._final);\n\t\t\tif (s.id == -1)\n\t\t\t\tout.println(\"init:\");\n\t\t\telse {\n\t\t\t\tout.format(\"S%d:\", s.id);\n\t\t\t\tout.println();\n\t\t\t}\n\t\t\tif (s.trans.nxt == s.trans) {\n\t\t\t\tout.println(\"\\tfalse;\");\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tout.println(\"\\tif\");\n\t\t\tfor (t = s.trans.nxt; t != s.trans; t = t.nxt) {\n\t\t\t\tBTrans t1;\n\t\t\t\tout.print(\"\\t:: (\");\n\t\t\t\tspin_print_sets(out, apset, t.pos, t.neg);\n\t\t\t\tfor (t1 = t; t1.nxt != s.trans;)\n\t\t\t\t\tif (t1.nxt.to.id == t.to.id &&\n\t\t\t\t\t    t1.nxt.to._final == t.to._final) {\n\t\t\t\t\t\tout.print(\") || (\");\n\t\t\t\t\t\tspin_print_sets(out, apset, t1.nxt.pos, t1.nxt.neg);\n\t\t\t\t\t\tt1.nxt = t1.nxt.nxt;\n\t\t\t\t\t} else\n\t\t\t\t\t\tt1 = t1.nxt;\n\t\t\t\tout.print(\") . goto \");\n\t\t\t\tif (t.to._final == accept)\n\t\t\t\t\tout.print(\"accept_\");\n\t\t\t\telse\n\t\t\t\t\tout.format(\"T%d_\", t.to._final);\n\t\t\t\tif (t.to.id == 0)\n\t\t\t\t\tout.println(\"all\");\n\t\t\t\telse if (t.to.id == -1)\n\t\t\t\t\tout.println(\"init\");\n\t\t\t\telse {\n\t\t\t\t\tout.format(\"S%d\", t.to.id);\n\t\t\t\t\tout.println();\n\t\t\t\t}\n\t\t\t}\n\t\t\tout.println(\"\\tfi;\");\n\t\t}\n\t\tif (accept_all != 0) {\n\t\t\tout.println(\"accept_all:\");\n\t\t\tout.println(\"\\tskip\");\n\t\t}\n\t\tout.println(\"}\");\n\t}\n\t\n\tprivate static class LTL2BAState {\n\t\tpublic int index;\n\t\tpublic int fin;\n\t\t\n\t\tpublic LTL2BAState(int index_, int fin_) { index = index_; fin = fin_; }\n\t\tpublic boolean equals(Object o) { return (o instanceof LTL2BAState) && this.equals((LTL2BAState) o); }\n\t\tpublic boolean equals(LTL2BAState s) { return (index == s.index) && (fin == s.fin); }\n\t\tpublic int hashCode() { return index * 31 + fin; }\n\t}\n\t\n\tpublic NBA toNBA(APSet apset) throws PrismException\n\t{\n\t\tNBA nba = new NBA(apset);\n\t\tHashMap<LTL2BAState,Integer> map = new HashMap<LTL2BAState,Integer>();\n\t\tint stateindex;\n\t\tboolean accept_all = false;\n\t\t\n\t\tBTrans t;\n\t\tBState s;\n\t\t\n\t\tif (bstates.nxt == bstates) {\t/* empty automaton */\n\t\t\tstateindex = nba.nba_i_newState();\n\t\t\tnba.nba_i_setStartState(stateindex);\n\t\t\tnba.nba_i_setFinal(stateindex, false);\n\t\t\treturn nba;\n\t\t}\n\t\t\n\t\tif (bstates.nxt.nxt == bstates && bstates.nxt.id == 0) {\t/* singleton */\n\t\t\tstateindex = nba.nba_i_newState();\n\t\t\tnba.nba_i_setStartState(stateindex);\n\t\t\tnba.nba_i_setFinal(stateindex, true);\n\t\t\tnba.nba_i_addEdge(stateindex, new APMonom(true), stateindex);\n\t\t\treturn nba;\n\t\t}\n\t\t\n\t\t// Map states, set initial and final states\n\t\tfor (s = bstates.prv; s != bstates; s = s.prv) {\n\t\t\tstateindex = nba.nba_i_newState();\n\t\t\t// System.out.println(\"Seen ltl2ba state \" + s.id + \", mapped to \" + stateindex);\n\t\t\tmap.put(new LTL2BAState(s.id, s._final), Integer.valueOf(stateindex));\n\t\t\t\n\t\t\tif (s.id == -1)\n\t\t\t\tnba.nba_i_setStartState(stateindex);\n\t\t\telse if (s.id == 0) {\t/* accept_all */\n\t\t\t\taccept_all = true;\n\t\t\t\tnba.nba_i_setFinal(stateindex, true);\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\t\n\t\t\tif (s._final == accept)\n\t\t\t\tnba.nba_i_setFinal(stateindex, true);\n\t\t\telse nba.nba_i_setFinal(stateindex, false);\n\t\t}\n\t\t\n\t\t// Copy transitions\n\t\tfor (s = bstates.prv; s != bstates; s = s.prv) {\n\t\t\tif (s.trans.nxt == s.trans) {\n\t\t\t\t// no transitions\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tfor (t = s.trans.nxt; t != s.trans; t = t.nxt) {\n\t\t\t\tBTrans t1;\n\t\t\t\tAPMonom transMonom = new APMonom();\n\t\t\t\ttransMonom.setFromPosNeg(t.pos, t.neg);\n\t\t\t\t// System.out.println(\"Seen ltl2ba transition \" + s.id + \" -|\" + transMonom.toString() + \"|-> \" + t.to.id + \", mapped to \" + map.get(Integer.valueOf(s.id)) + \" -> \" + map.get(Integer.valueOf(t.to.id)));\n\t\t\t\tnba.nba_i_addEdge(map.get(new LTL2BAState(s.id, s._final)), transMonom, map.get(new LTL2BAState(t.to.id, t.to._final)));\n\t\t\t\tfor (t1 = t; t1.nxt != s.trans;) {\n\t\t\t\t\tif (t1.nxt.to.id == t.to.id && t1.nxt.to._final == t.to._final) {\n\t\t\t\t\t\ttransMonom = new APMonom();\n\t\t\t\t\t\ttransMonom.setFromPosNeg(t1.nxt.pos, t1.nxt.neg);\n\t\t\t\t\t\t// System.out.println(\"Seen ltl2ba transition \" + s.id + \" -|\" + transMonom.toString() + \"|-> \" + t.to.id + \", mapped to \" + map.get(Integer.valueOf(s.id)) + \" -> \" + map.get(Integer.valueOf(t.to.id)));\n\t\t\t\t\t\tnba.nba_i_addEdge(map.get(new LTL2BAState(s.id, s._final)), transMonom, map.get(new LTL2BAState(t.to.id, t.to._final)));\n\t\t\t\t\t\tt1.nxt = t1.nxt.nxt;\n\t\t\t\t\t} \n\t\t\t\t\telse {\n\t\t\t\t\t\tt1 = t1.nxt;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// FIXME: check if this works\n\t\tif (accept_all)\n\t\t\tnba.nba_i_addEdge(map.get(new LTL2BAState(0, accept)), new APMonom(true), map.get(new LTL2BAState(0, accept)));\n\t\t\n\t\treturn nba;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/Generalized.java",
    "content": "/* Written by Denis Oddoux, LIAFA, France                                 *\n * Copyright (c) 2001  Denis Oddoux                                       *\n * Modified by Paul Gastin, LSV, France                                   *\n * Copyright (c) 2007  Paul Gastin                                        *\n * Ported by Carlos Bederian, FaMAF, Argentina                            *\n * Copyright (c) 2007  Carlos Bederian                                    *\n *                                                                        *\n * This program is free software; you can redistribute it and/or modify   *\n * it under the terms of the GNU General Public License as published by   *\n * the Free Software Foundation; either version 2 of the License, or      *\n * (at your option) any later version.                                    *\n *                                                                        *\n * This program is distributed in the hope that it will be useful,        *\n * but WITHOUT ANY WARRANTY; without even the implied warranty of         *\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the          *\n * GNU General Public License for more details.                           *\n *                                                                        *\n * You should have received a copy of the GNU General Public License      *\n * along with this program; if not, write to the Free Software            *\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA*\n *                                                                        *\n * Based on the translation algorithm by Gastin and Oddoux,               *\n * presented at the 13th International Conference on Computer Aided       *\n * Verification, CAV 2001, Paris, France.                                 *\n * Proceedings - LNCS 2102, pp. 53-65                                     *\n *                                                                        */\n\npackage jltl2ba;\n\nimport java.util.Vector;\nimport java.io.PrintStream;\n\n\npublic class Generalized {\n\n\tpublic int init_size;\n\tpublic Vector<GState> g_init;\n\tpublic Vector<Integer> _final;\n\tpublic GState gstates;\n\t\n\tprivate GState gstack;\n\tprivate GState gremoved;\n\tprivate GScc scc_stack;\n\tprivate int gstate_id;\n\tprivate int gstate_count;\n\tprivate int gtrans_count;\n\tprivate int rank;\n\tprivate int scc_id;\n\tprivate MyBitSet fin;\n\tprivate MyBitSet bad_scc;\n\t\n\tpublic static class GScc {\n\t\tpublic GState gstate;\n\t\tpublic int rank;\n\t\tpublic int theta;\n\t\tpublic GScc nxt;\n\t\t\n\t\tpublic GScc() {}\n\t}\n\n\tpublic static class GState {\n\t\tpublic int id;\n\t\tpublic int incoming;\n\t\tpublic MyBitSet nodes_set;\n\t\tpublic GTrans trans;\n\t\tpublic GState nxt;\n\t\tpublic GState prv;\n\t\t\n\t\tpublic GState()\n\t\t{\n\t\t\tnodes_set = new MyBitSet();\n\t\t}\n\t\t\n\t\tpublic void free()\n\t\t{\n\t\t\tif (trans.nxt != null)\n\t\t\t\ttrans.nxt.free(trans, true);\n\t\t\tnodes_set = null;\n\t\t}\n\t}\n\n\tpublic static class GTrans {\n\t\tpublic MyBitSet pos;\n\t\tpublic MyBitSet neg;\n\t\tpublic MyBitSet _final;\n\t\tpublic GState to;\n\t\tpublic GTrans nxt;\n\t\t\n\t\tpublic GTrans()\n\t\t{\n\t\t\tpos = new MyBitSet();\n\t\t\tneg = new MyBitSet();\n\t\t\t_final = new MyBitSet();\n\t\t\tnxt = null;\n\t\t\tto = null;\n\t\t}\n\t\t\n\t\tpublic GTrans(MyBitSet _pos, MyBitSet _neg, MyBitSet _fin)\n\t\t{\n\t\t\tpos = (MyBitSet) _pos.clone();\n\t\t\tneg = (MyBitSet) _neg.clone();\n\t\t\t_final = (MyBitSet) _fin.clone();\n\t\t\tnxt = null;\n\t\t\tto = null;\n\t\t}\n\t\t\n\t\tpublic GTrans clone()\n\t\t{\n\t\t\tGTrans rv = new GTrans(pos, neg, _final);\n\t\t\trv.to = to;\n\t\t\trv.nxt = nxt;\n\t\t\treturn rv;\n\t\t}\n\t\t\n\t\tpublic void copyTo(GTrans g)\n\t\t{\n\t\t\tg.pos = (MyBitSet) pos.clone();\n\t\t\tg.neg = (MyBitSet) neg.clone();\n\t\t\tg._final = (MyBitSet) _final.clone();\n\t\t\tg.to = to;\n\t\t}\n\t\t\n\t\tpublic void free(GTrans sentinel, boolean fly)\n\t\t{\n\t\t\tif (this != sentinel) {\n\t\t\t\tnxt.free(sentinel, fly);\n\t\t\t\tif (fly)\n\t\t\t\t\tto.incoming--;\n\t\t\t}\n\t\t}\n\t}\n\n\t/* generates a generalized Buchi automaton from the alternating automaton */\n\tpublic Generalized(Alternating a)\n\t{\n\t\tAlternating.ATrans t;\n\t\tGState s;\n\t\t\n\t\tinit_size = 0;\n\t\tgstate_id = 1;\n\t\tgstate_count = 0;\n\t\tgtrans_count = 0;\n\n\t\tfin = new MyBitSet();\n\t\tbad_scc = new MyBitSet();\n\t\t_final = a.final_set.IntegerList();\n\n\t\tgstack = new GState();\n\t\tgstack.nxt = gstack;\n\t\tgremoved = new GState();\n\t\tgremoved.nxt = gremoved;\n\t\tgstates = new GState();\n\t\tgstates.nxt = gstates;\n\t\tgstates.prv = gstates;\n\n\t\tfor (t = a.transition.get(0); t != null; t = t.nxt) {\t/* puts initial states in the stack */\n\t\t\ts = new GState();\n\t\t\ts.id = t.to.isEmpty() ? 0 : gstate_id++;\n\t\t\ts.incoming = 1;\n\t\t\ts.nodes_set.or(t.to);\n\t\t\ts.trans = new GTrans();\n\t\t\ts.trans.nxt = s.trans;\n\t\t\ts.nxt = gstack.nxt;\n\t\t\tgstack.nxt = s;\n\t\t\tinit_size++;\n\t\t}\n\n\t\tif (init_size != 0)\n\t\t\tg_init = new Vector<GState>();\n\t\tinit_size = 0;\n\t\tfor (s = gstack.nxt; s != gstack; s = s.nxt) {\n\t\t\tg_init.add(s);\n\t\t\tinit_size++;\n\t\t}\n\t\twhile (gstack.nxt != gstack) {\t/* solves all states in the stack until it is empty */\n\t\t\ts = gstack.nxt;\n\t\t\tgstack.nxt = gstack.nxt.nxt;\n\t\t\tif (s.incoming == 0) {\n\t\t\t\ts.free();\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tmake_gtrans(a, s);\n\t\t}\n\n\t\tretarget_all_gtrans();\n\t\tgstack = null;\n\t\t\n\t\t// System.out.println(\"Generalized Buchi automaton before simplification:\");\n\t\t// print(System.out, a.sym_table);\n\n\t\tsimplify_gscc(a);\n\t\tsimplifyGTrans();\n\t\tsimplify_gscc(a);\n\t\twhile (simplifyGStates() != 0) {\t/* simplifies as much as possible */\n\t\t\tsimplify_gscc(a);\n\t\t\tsimplifyGTrans();\n\t\t\tsimplify_gscc(a);\n\t\t}\n\t\t// System.out.println(\"Generalized Buchi automaton after simplification:\");\n\t\t// print(System.out, a.sym_table);\n\t}\n\t\n\t/** Get the highest ID of a GState */\n\tpublic int getGStateID()\n\t{\n\t\treturn gstate_id;\n\t}\n\n\t/*is the transition final for i ? */\n\tprivate boolean isFinal(Alternating a, MyBitSet from, Alternating.ATrans at, int i)\n\t{\n\t\tAlternating.ATrans t;\n\t\tboolean in_to;\n\t\tif (!at.to.get(i))\n\t\t    return true;\n\t\tin_to = at.to.get(i);\n\t\tat.to.clear(i);\n\t\tfor (t = a.transition.get(i); t != null; t = t.nxt)\n\t\t\tif (at.to.containsAll(t.to) &&\n\t\t\t    at.pos.containsAll(t.pos) &&\n\t\t\t    at.neg.containsAll(t.neg)) {\n\t\t\t\tif (in_to)\n\t\t\t\t\tat.to.set(i);\n\t\t\t\treturn true;\n\t\t\t}\n\t\tif (in_to)\n\t\t\tat.to.set(i);\n\t\treturn false;\n\t}\n\t\n\t/* finds the corresponding state, or creates it */\n\tprivate GState findGState(MyBitSet set, GState s)\n\t{\n\t\tif (set.equals(s.nodes_set))\n\t\t\treturn s;\t/* same state */\n\n\t\ts = gstack.nxt;\t/* in the stack */\n\t\tgstack.nodes_set = set;\n\t\twhile (!set.equals(s.nodes_set))\n\t\t\ts = s.nxt;\n\t\tif (s != gstack)\n\t\t\treturn s;\n\n\t\ts = gstates.nxt;\t/* in the solved states */\n\t\tgstates.nodes_set = set;\n\t\twhile (!set.equals(s.nodes_set))\n\t\t\ts = s.nxt;\n\t\tif (s != gstates)\n\t\t\treturn s;\n\n\t\ts = gremoved.nxt;\t/* in the removed states */\n\t\tgremoved.nodes_set = set;\n\t\twhile (!set.equals(s.nodes_set))\n\t\t\ts = s.nxt;\n\t\tif (s != gremoved)\n\t\t\treturn s;\n\n\t\ts = new GState();\n\t\ts.id = set.isEmpty() ? 0 : gstate_id++;\n\t\ts.incoming = 0;\n\t\ts.nodes_set = (MyBitSet) set.clone();\n\t\ts.trans = new GTrans();\n\t\ts.trans.nxt = s.trans;\n\t\ts.nxt = gstack.nxt;\n\t\tgstack.nxt = s;\n\t\treturn s;\n\t}\n\n\t/* returns 1 if the transitions are identical */\n\tprivate boolean same_gtrans(GState a, GTrans s, GState b, GTrans t, boolean use_scc)\n\t{\n\t\tif ((s.to != t.to) ||\n\t\t\t!s.pos.equals(t.pos) ||\n\t\t\t!s.neg.equals(t.neg))\n\t\t\treturn false;\t/* transitions differ */\n\t\tif (s._final.equals(t._final))\n\t\t\treturn true;\t/* same transitions exactly */\n\t\t/* next we check whether acceptance conditions may be ignored */\n\t\tif (use_scc && ( bad_scc.get(a.incoming)\n\t\t\t\t\t\t|| bad_scc.get(b.incoming)\n\t\t\t\t\t\t|| (a.incoming != s.to.incoming)\n\t\t\t\t\t\t|| (b.incoming != t.to.incoming)))\n\t\t\treturn true;\n\t\t\n\t\treturn false;\n\t\t\n\t\t/* below is the old test to check whether acceptance conditions may be ignored */\n\t\t//if (!use_scc)\n\t\t//\treturn 0;\t/* transitions differ */\n\t\t// if ((a.incoming == b.incoming) && (a.incoming == s.to.incoming))\n\t\t// \treturn 0;\t/* same scc: acceptance conditions must be taken into account */\n\t\t/* if scc(a)=scc(b)>scc(s->to) then acceptance conditions need not be taken into account */\n\t\t/* if scc(a)>scc(b) and scc(a) is non-trivial then all_gtrans_match(a,b,use_scc) will fail */\n\t\t/* if scc(a) is trivial then acceptance conditions of transitions from a need not be taken into account */\n\t\t// return 1;\t/* same transitions up to acceptance conditions */\n\t\t\n\t}\n\t\n\t/* decides if the states are equivalent */\n\tprivate int allGTransMatch(GState a, GState b, boolean use_scc)\n\t{\n\t\tGTrans s, t;\n\t\tfor (s = a.trans.nxt; s != a.trans; s = s.nxt) {\n\t\t\t/* all transitions from a appear in b */\n\t\t\ts.copyTo(b.trans);\n\t\t\tt = b.trans.nxt;\n\t\t\twhile (!same_gtrans(a, s, b, t, use_scc))\n\t\t\t\tt = t.nxt;\n\t\t\tif (t == b.trans)\n\t\t\t\treturn 0;\n\t\t}\n\t\tfor (t = b.trans.nxt; t != b.trans; t = t.nxt) {\n\t\t\t/* all transitions from b appear in a */\n\t\t\tt.copyTo(a.trans);\n\t\t\ts = a.trans.nxt;\n\t\t\twhile (!same_gtrans(a, s, b, t, use_scc))\n\t\t\t\ts = s.nxt;\n\t\t\tif (s == a.trans)\n\t\t\t\treturn 0;\n\t\t}\n\t\treturn 1;\n\t}\n\n\t/* creates all the transitions from a state */\n\tprivate void make_gtrans(Alternating a, GState s)\n\t{\n\t\tint i, state_trans = 0, trans_exist = 1;\n\t\tVector<Integer> list;\n\t\tGState s1;\n\t\tAlternating.ATrans t1;\n\t\tAlternating.AProd prod = new Alternating.AProd();\t/* initialization */\n\t\tprod.nxt = prod;\n\t\tprod.prv = prod;\n\t\tprod.prod = new Alternating.ATrans();\n\t\tprod.trans = prod.prod;\n\t\tprod.trans.nxt = prod.prod;\n\t\tlist = s.nodes_set.IntegerList();\n\n\t\tfor (i = 0; i < list.size(); i++) {\n\t\t\tAlternating.AProd p = new Alternating.AProd();\n\t\t\tp.astate = list.get(i);\n\t\t\tp.trans = a.transition.get(list.get(i));\n\t\t\tif (p.trans == null)\n\t\t\t\ttrans_exist = 0;\n\t\t\tp.prod = Alternating.do_merge_atrans(prod.nxt.prod, p.trans);\n\t\t\tp.nxt = prod.nxt;\n\t\t\tp.prv = prod;\n\t\t\tp.nxt.prv = p;\n\t\t\tp.prv.nxt = p;\n\t\t}\n\n\t\twhile (trans_exist != 0) {\t/* calculates all the transitions */\n\t\t\tAlternating.AProd p = prod.nxt;\n\t\t\tt1 = p.prod;\n\t\t\tif (t1 != null) {\t/* solves the current transition */\n\t\t\t\tGTrans trans, t2;\n\t\t\t\tfin.clear();\n\t\t\t\tfor (i = 0; i < _final.size(); i++)\n\t\t\t\t\tif (isFinal(a, s.nodes_set, t1, _final.get(i)))\n\t\t\t\t\t\tfin.set(_final.get(i));\n\t\t\t\tfor (t2 = s.trans.nxt; t2 != s.trans;) {\n\t\t\t\t\tif (t2.to.nodes_set.containsAll(t1.to) && \n\t\t\t\t\t\tt2.pos.containsAll(t1.pos) && \n\t\t\t\t\t\tt2.neg.containsAll(t1.neg) &&\n\t\t\t\t\t\tfin.equals(t2._final)) {\t/* t2 is redundant */\n\t\t\t\t\t\tGTrans free = t2.nxt;\n\t\t\t\t\t\tt2.to.incoming--;\n\t\t\t\t\t\tt2.to = free.to;\n\t\t\t\t\t\tt2.pos = (MyBitSet) free.pos.clone();\n\t\t\t\t\t\tt2.neg = (MyBitSet) free.neg.clone();\n\t\t\t\t\t\tt2._final = (MyBitSet) free._final.clone();\n\t\t\t\t\t\tt2.nxt = free.nxt;\n\t\t\t\t\t\tif (free == s.trans)\n\t\t\t\t\t\t\ts.trans = t2;\n\t\t\t\t\t\tfree = null;\n\t\t\t\t\t\tstate_trans--;\n\t\t\t\t\t} else if (t1.to.containsAll(t2.to.nodes_set) && t1.pos.containsAll(t2.pos) && t1.neg.containsAll(t2.neg) && t2._final.equals(fin)) {\t/* t1 is redundant */\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tt2 = t2.nxt;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (t2 == s.trans) {\t/* adds the transition */\n\t\t\t\t\ttrans = new GTrans();\n\t\t\t\t\ttrans.to = findGState(t1.to, s);\n\t\t\t\t\ttrans.to.incoming++;\n\t\t\t\t\ttrans.pos = (MyBitSet) t1.pos.clone();\n\t\t\t\t\ttrans.neg = (MyBitSet) t1.neg.clone();\n\t\t\t\t\ttrans._final = (MyBitSet) fin.clone();\n\t\t\t\t\ttrans.nxt = s.trans.nxt;\n\t\t\t\t\ts.trans.nxt = trans;\n\t\t\t\t\tstate_trans++;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (p.trans == null)\n\t\t\t\tbreak;\n\t\t\twhile (p.trans.nxt == null)\t/* calculates the next transition */\n\t\t\t\tp = p.nxt;\n\t\t\tif (p == prod)\n\t\t\t\tbreak;\n\t\t\tp.trans = p.trans.nxt;\n\t\t\tp.prod = Alternating.do_merge_atrans(p.nxt.prod, p.trans);\n\t\t\tp = p.prv;\n\t\t\twhile (p != prod) {\n\t\t\t\tp.trans = a.transition.get(p.astate);\n\t\t\t\tp.prod = Alternating.do_merge_atrans(p.nxt.prod, p.trans);\n\t\t\t\tp = p.prv;\n\t\t\t}\n\t\t}\n\n\t\tlist.clear();\n\t\twhile (prod.nxt != prod) {\n\t\t\tAlternating.AProd p = prod.nxt;\n\t\t\tprod.nxt = p.nxt;\n\t\t\tp.prod = null;\n\t\t\tp = null;\n\t\t}\n\t\tprod.prod = null;\n\t\tprod = null;\n\n\t\tif (s.trans == s.trans.nxt) {\t/* s has no transitions */\n\t\t\ts.trans.nxt.free(s.trans, true);\n\t\t\ts.trans = null;\n\t\t\ts.prv = null;\n\t\t\ts.nxt = gremoved.nxt;\n\t\t\tgremoved.nxt = s;\n\t\t\tfor (s1 = gremoved.nxt; s1 != gremoved; s1 = s1.nxt)\n\t\t\t\tif (s1.prv == s)\n\t\t\t\t\ts1.prv = null;\n\t\t\treturn;\n\t\t}\n\n\t\tgstates.trans = s.trans;\n\t\ts1 = gstates.nxt;\n\t\twhile (allGTransMatch(s, s1, false) == 0)\n\t\t\ts1 = s1.nxt;\n\t\tif (s1 != gstates) {\t/* s and s1 are equivalent */\n\t\t\ts.trans.nxt.free(s.trans, true);\n\t\t\ts.trans = null;\n\t\t\ts.prv = s1;\n\t\t\ts.nxt = gremoved.nxt;\n\t\t\tgremoved.nxt = s;\n\t\t\tfor (s1 = gremoved.nxt; s1 != gremoved; s1 = s1.nxt)\n\t\t\t\tif (s1.prv == s)\n\t\t\t\t\ts1.prv = s.prv;\n\t\t\treturn;\n\t\t}\n\n\t\ts.nxt = gstates.nxt;\t/* adds the current state to 'gstates' */\n\t\ts.prv = gstates;\n\t\ts.nxt.prv = s;\n\t\tgstates.nxt = s;\n\t\tgtrans_count += state_trans;\n\t\tgstate_count++;\n\t}\n\n\t/* redirects transitions before removing a state from the automaton */\n\tprivate void retarget_all_gtrans()\n\t{\n\t\tGState s;\n\t\tGTrans t;\n\t\tint i;\n\t\tfor (i = 0; i < init_size; i++)\n\t\t\tif (g_init.get(i) != null && (g_init.get(i).trans == null))\t/* g_init[i] has been removed */\n\t\t\t\tg_init.set(i, g_init.get(i).prv);\n\t\tfor (s = gstates.nxt; s != gstates; s = s.nxt)\n\t\t\tfor (t = s.trans.nxt; t != s.trans;)\n\t\t\t\tif (t.to.trans == null) {\t/* t->to has been removed */\n\t\t\t\t\tt.to = t.to.prv;\n\t\t\t\t\tif (t.to == null) {\t/* t->to has no transitions */\n\t\t\t\t\t\tGTrans free = t.nxt;\n\t\t\t\t\t\tt.to = free.to;\n\t\t\t\t\t\tt.pos = (MyBitSet) free.pos.clone();\n\t\t\t\t\t\tt.neg = (MyBitSet) free.neg.clone();\n\t\t\t\t\t\tt._final = (MyBitSet) free._final.clone();\n\t\t\t\t\t\tt.nxt = free.nxt;\n\t\t\t\t\t\tif (free == s.trans)\n\t\t\t\t\t\t\ts.trans = t;\n\t\t\t\t\t\tfree = null;\n\t\t\t\t\t} else\n\t\t\t\t\t\tt = t.nxt;\n\t\t\t\t} else\n\t\t\t\t\tt = t.nxt;\n\t\twhile (gremoved.nxt != gremoved) {\t/* clean the 'removed' list */\n\t\t\ts = gremoved.nxt;\n\t\t\tgremoved.nxt = gremoved.nxt.nxt;\n\t\t\tif (s.nodes_set != null)\n\t\t\t\t\ts.nodes_set = null;\n\t\t\ts = null;\n\t\t}\n\t}\n\n\t/* removes a state */\n\tprivate GState removeGState(GState s, GState s1)\n\t{\n\t\tGState prv = s.prv;\n\t\ts.prv.nxt = s.nxt;\n\t\ts.nxt.prv = s.prv;\n\t\ts.trans.nxt.free(s.trans, false);\n\t\ts.trans = null;\n\t\ts.nodes_set = null;\n\t\ts.nxt = gremoved.nxt;\n\t\tgremoved.nxt = s;\n\t\ts.prv = s1;\n\t\tfor (s1 = gremoved.nxt; s1 != gremoved; s1 = s1.nxt)\n\t\t\tif (s1.prv == s)\n\t\t\t\ts1.prv = s.prv;\n\t\treturn prv;\n\t}\n\n\t/* simplifies the transitions */\n\tprivate int simplifyGTrans()\n\t{\n\t\tint changed = 0;\n\t\tGState s;\n\t\tGTrans t;\n\t\tGTrans t1;\n\n\t\tfor (s = gstates.nxt; s != gstates; s = s.nxt) {\n\t\t\tt = s.trans.nxt;\n\t\t\twhile (t != s.trans) {\t// tries to remove t\n\t\t\t\tt.copyTo(s.trans);\n\t\t\t\tt1 = s.trans.nxt;\n\t\t\t\twhile (!((t != t1)\n\t\t\t\t\t\t&& (t1.to == t.to)\n\t\t\t\t\t\t&& t.pos.containsAll(t1.pos)\n\t\t\t\t\t\t&& t.neg.containsAll(t1.neg)\n\t\t\t\t\t\t&& (t1._final.containsAll(t._final) ||\n\t\t\t\t\t\t\t(s.incoming != t.to.incoming) || bad_scc.get(s.incoming)))\n\t\t\t\t\t\t)\n\t\t\t\t\tt1 = t1.nxt;\n\t\t\t\n\t\t\tif (t1 != s.trans) {\n\t\t\t\t\tGTrans free = t.nxt;\n\t\t\t\t\tt.to = free.to;\n\t\t\t\t\tt.pos = (MyBitSet) free.pos.clone();\n\t\t\t\t\tt.neg = (MyBitSet) free.neg.clone();\n\t\t\t\t\tt._final = (MyBitSet) free._final.clone();\n\t\t\t\t\tt.nxt = free.nxt;\n\t\t\t\t\tif (free == s.trans)\n\t\t\t\t\t\ts.trans = t;\n\t\t\t\t\tfree = null;\n\t\t\t\t\tchanged++;\n\t\t\t\t} else\n\t\t\t\t\tt = t.nxt;\n\t\t\t}\n\t\t}\n\t\treturn changed;\n\t}\n\n\t/* eliminates redundant states */\n\tprivate int simplifyGStates()\n\t{\n\t\tint changed = 0;\n\t\tGState a, b;\n\n\t\tfor (a = gstates.nxt; a != gstates; a = a.nxt) {\n\t\t\tif (a.trans == a.trans.nxt) {\t/* a has no transitions */\n\t\t\t\ta = removeGState(a, null);\n\t\t\t\tchanged++;\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tgstates.trans = a.trans;\n\t\t\tb = a.nxt;\n\t\t\twhile (allGTransMatch(a, b, true) == 0)\t/* = and not == */\n\t\t\t\tb = b.nxt;\n\t\t\tif (b != gstates) {\t/* a and b are equivalent */\n\t\t\t\t/* if scc(a)>scc(b) and scc(a) is non-trivial then all_gtrans_match(a,b,use_scc) must fail */\n\t\t\t\tif (a.incoming > b.incoming) // scc(a) is trivial\n\t\t\t\t\ta = removeGState(a, b);\n\t\t\t\telse\t// either scc(a)=scc(b) or scc(b) is trivial\n\t\t\t\t\tremoveGState(b, a);\n\t\t\t\tchanged++;\n\t\t\t}\n\t\t}\n\t\tretarget_all_gtrans();\n\n\t\treturn changed;\n\t}\n\n\tprivate int gdfs(GState s)\n\t{\n\t\tGTrans t;\n\t\tGScc c;\n\t\tGScc scc = new GScc();\n\t\tscc.gstate = s;\n\t\tscc.rank = rank;\n\t\tscc.theta = rank++;\n\t\tscc.nxt = scc_stack;\n\t\tscc_stack = scc;\n\n\t\ts.incoming = 1;\n\n\t\tfor (t = s.trans.nxt; t != s.trans; t = t.nxt) {\n\t\t\tif (t.to.incoming == 0) {\n\t\t\t\tint result = gdfs(t.to);\n\t\t\t\tscc.theta = scc.theta < result ? scc.theta : result;\n\t\t\t} else {\n\t\t\t\tfor (c = scc_stack.nxt; c != null; c = c.nxt) {\n\t\t\t\t\tif (c.gstate == t.to) {\n\t\t\t\t\t\tscc.theta = scc.theta < c.rank ? scc.theta : c.rank;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (scc.rank == scc.theta) {\n\t\t\twhile (scc_stack != scc) {\n\t\t\t\tscc_stack.gstate.incoming = scc_id;\n\t\t\t\tscc_stack = scc_stack.nxt;\n\t\t\t}\n\t\t\tscc.gstate.incoming = scc_id++;\n\t\t\tscc_stack = scc.nxt;\n\t\t}\n\t\treturn scc.theta;\n\t}\n\n\tprivate void simplify_gscc(Alternating a)\n\t{\n\t\tGState s;\n\t\tGTrans t;\n\t\tint i;\n\t\tVector<MyBitSet> scc_final;\n\t\t\n\t\trank = 1;\n\t\tscc_stack = null;\n\t\tscc_id = 1;\n\n\t\tif (gstates == gstates.nxt)\treturn;\n\n\t\tfor (s = gstates.nxt; s != gstates; s = s.nxt) {\n\t\t\ts.incoming = 0;\t/* state color = white */\n\t\t}\n\n\t\tfor (i = 0; i < init_size; i++) {\n\t\t\tif ((g_init.get(i) != null) && g_init.get(i).incoming == 0) {\n\t\t\t\tgdfs(g_init.get(i));\n\t\t\t}\n\t\t}\n\n\t\tscc_final = new Vector<MyBitSet>();\n\t\tfor (i = 0; i < scc_id; i++) {\n\t\t\tscc_final.add(new MyBitSet());\n\t\t}\n\t\tfor (s = gstates.nxt; s != gstates; s = s.nxt) {\n\t\t\tif (s.incoming == 0) {\n\t\t\t\ts = removeGState(s, null);\n\t\t\t}\n\t\t\telse {\n\t\t\t\tfor (t = s.trans.nxt; t != s.trans; t = t.nxt) {\n\t\t\t\t\tif (t.to.incoming == s.incoming) {\n\t\t\t\t\t\tscc_final.get(s.incoming).or(t._final);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tbad_scc.clear();\n\n\t\tfor (i = 0; i < scc_id; i++) {\n\t\t\tif (!scc_final.get(i).containsAll(a.final_set)) {\n\t\t\t\tbad_scc.set(i);\n\t\t\t}\n\t\t}\n\t\tscc_final.clear();\n\t}\n\t\n\tprivate void reverse_print_generalized(PrintStream out, GState s, APSet symtab)\n\t{\t\t\t\t/* dumps the generalized Buchi automaton */\n\t\tGTrans t;\n\t\tif (s == gstates)\n\t\t\treturn;\n\n\t\treverse_print_generalized(out, s.nxt, symtab);\t/* begins with the last state */\n\n\t\tout.format(\"state %d (\", s.id);\n\t\ts.nodes_set.print(out);\n\t\tout.format(\") : %d\", s.incoming);\n\t\tout.println();\n\t\tfor (t = s.trans.nxt; t != s.trans; t = t.nxt) {\n\t\t\tif (t.pos.isEmpty() && t.neg.isEmpty())\n\t\t\t\tout.print(\"1\");\n\t\t\tt.pos.print(out, symtab, true);\n\t\t\tif (!t.pos.isEmpty() && !t.neg.isEmpty())\n\t\t\t\tout.print(\" & \");\n\t\t\tt.neg.print(out, symtab, false);\n\t\t\tout.format(\" -> %d : \", t.to.id);\n\t\t\tt._final.print(out);\n\t\t\tout.println();\n\t\t}\n\t}\n\n\t/* prints intial states and calls 'reverse_print' */\n\tpublic void print(PrintStream out, APSet symtab)\n\t{\n\t\tint i;\n\t\tout.println(\"init :\");\n\t\tfor (i = 0; i < init_size; i++)\n\t\t\tif (g_init.get(i) != null)\n\t\t\t\tout.println(g_init.get(i).id);\n\t\treverse_print_generalized(out, gstates.nxt, symtab);\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/Jltl2baCmdLine.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jltl2ba;\n\nimport java.io.BufferedReader;\nimport java.io.FileReader;\nimport java.io.InputStreamReader;\nimport java.io.PrintStream;\n\nimport jltl2dstar.NBA;\n\n/**\n * Command-line interface to the jltl2ba LTL->NBA translator.\n */\npublic class Jltl2baCmdLine {\n\n\tpublic int run(String formula, PrintStream output) throws Exception {\n\t\tformula = formula.trim();\n\t\tSimpleLTL ltl = SimpleLTL.parseFormulaLBT(formula);\n\t\tltl = ltl.simplify();\n\t\t\n\t\tNBA nba = ltl.toNBA();\n\t\t// nba.print_lbtt(output);\n\t\tnba.print_hoa(output);\n\t\treturn 0;\n\t}\n\n\tpublic static void main(String[] args) {\n\t\tint rv = 0;\n\t\tint outfile_pos = 1;\n\t\tBufferedReader r = null;\n\t\ttry {\n\t\t\tString formula;\n\t\t\tif (args.length == 0) {\n\t\t\t\tusage(\"\");\n\t\t\t}\n\t\t\tif (args[0].equals(\"--ltl\")) {\n\t\t\t\tif (args.length <= 1)\n\t\t\t\t\tusage(\"Missing formula\");\n\t\t\t\tformula = args[1];\n\t\t\t\toutfile_pos++;\n\t\t\t} else {\n\t\t\t\tif (args[0].equals(\"-\")) {\n\t\t\t\t\tr = new BufferedReader(new InputStreamReader(System.in));\n\t\t\t\t} else {\n\t\t\t\t\tr = new BufferedReader(new FileReader(args[0]));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (outfile_pos >= args.length) {\n\t\t\t\tusage(\"Missing output file\");\n\t\t\t}\n\t\t\tPrintStream output;\n\t\t\tString outfile = args[outfile_pos];\n\t\t\tif (outfile.equals(\"-\")) {\n\t\t\t\toutput = System.out;\n\t\t\t} else {\n\t\t\t\toutput = new PrintStream(outfile);\n\t\t\t}\n\n\t\t\tformula = r.readLine();\n\t\t\tr.close();\n\n\t\t\tJltl2baCmdLine jltl2ba = new Jltl2baCmdLine();\n\t\t\trv = jltl2ba.run(formula, output);\n\t\t\toutput.close();\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(e.toString());\n\t\t\trv = 1;\n\t\t}\n\t\t\n\t\tif (rv != 0) {\n\t\t\tSystem.exit(rv);\n\t\t}\n\t}\n\n\tprivate static void usage(String error)\n\t{\n\t\tif (!error.isEmpty()) {\n\t\t\tSystem.err.println(\"Error: \" + error);\n\t\t\tSystem.err.println();\n\t\t}\n\t\tSystem.err.println(\"Usage:\");\n\t\tSystem.err.println(\"  --ltl formula out-file\");\n\t\tSystem.err.println(\" or\");\n\t\tSystem.err.println(\"  in-file out-file\");\n\t\tSystem.err.println(\"\\n  Filename of '-' stands for standard input/output\");\n\t\tSystem.exit(1);\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/LTLFragments.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jltl2ba;\n\n/**\n * Helper to determine syntactic fragments of LTL formulas.\n * <br>\n * Each object stores information about membership in the\n * \"safety\", \"guarantee/co-safety\", \"obligation\", \"recurrence\" and \"persistence\"\n * fragments of LTL.\n */\npublic class LTLFragments\n{\n\tprivate boolean syntacticSafety;\n\tprivate boolean syntacticGuarantee;\n\tprivate boolean syntacticObligation;\n\tprivate boolean syntacticRecurrence;\n\tprivate boolean syntacticPersistence;\n\n\t/**\n\t * Constructor for basic formula (true, false, atomic proposition),\n\t * contained in all fragments.\n\t */\n\tprivate LTLFragments()\n\t{\n\t\tsyntacticSafety = true;\n\t\tsyntacticGuarantee = true;\n\t\tsyntacticObligation = true;\n\t\tsyntacticRecurrence = true;\n\t\tsyntacticPersistence = true;\n\t}\n\n\t/** Copy constructor */\n\tprivate LTLFragments(LTLFragments other)\n\t{\n\t\tsyntacticSafety = other.syntacticSafety;\n\t\tsyntacticGuarantee = other.syntacticGuarantee;\n\t\tsyntacticObligation = other.syntacticObligation;\n\t\tsyntacticRecurrence = other.syntacticRecurrence;\n\t\tsyntacticPersistence = other.syntacticPersistence;\n\t}\n\n\t/** Do we belong to the syntactic safety fragment? */\n\tpublic boolean isSyntacticSafety()\n\t{\n\t\treturn syntacticSafety;\n\t}\n\n\t/** Do we belong to the syntactic guarantee (co-safety) fragment? */\n\tpublic boolean isSyntacticGuarantee()\n\t{\n\t\treturn syntacticGuarantee;\n\t}\n\n\t/** Do we belong to the syntactic obligation fragment? */\n\tpublic boolean isSyntacticObligation()\n\t{\n\t\treturn syntacticObligation;\n\t}\n\n\t/** Do we belong to the syntactic recurrence fragment? */\n\tpublic boolean isSyntacticRecurrence()\n\t{\n\t\treturn syntacticRecurrence;\n\t}\n\n\t/** Do we belong to the syntactic persistence fragment? */\n\tpublic boolean isSyntacticPersistence()\n\t{\n\t\treturn syntacticPersistence;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"[\";\n\t\tboolean first = true;\n\n\t\tif (isSyntacticSafety()) {\n\t\t\tif (!first) s+=\",\";\n\t\t\tfirst = false;\n\t\t\ts+=\"syntactic safety\";\n\t\t}\n\n\t\tif (isSyntacticGuarantee()) {\n\t\t\tif (!first) s+=\",\";\n\t\t\tfirst = false;\n\t\t\ts+=\"syntactic guarantee\";\n\t\t}\n\n\t\tif (isSyntacticObligation()) {\n\t\t\tif (!first) s+=\",\";\n\t\t\tfirst = false;\n\t\t\ts+=\"syntactic obligation\";\n\t\t}\n\n\t\tif (isSyntacticRecurrence()) {\n\t\t\tif (!first) s+=\",\";\n\t\t\tfirst = false;\n\t\t\ts+=\"syntactic recurrence\";\n\t\t}\n\n\t\tif (isSyntacticPersistence()) {\n\t\t\tif (!first) s+=\",\";\n\t\t\tfirst = false;\n\t\t\ts+=\"syntactic persistence\";\n\t\t}\n\n\t\treturn s+\"]\";\n\t}\n\n\t/**\n\t * Apply the Boolean AND operator (i.e., corresponding to this & other),\n\t * returning the result.\n\t */\n\tprivate LTLFragments and(LTLFragments other)\n\t{\n\t\tLTLFragments result = new LTLFragments(this);\n\n\t\tresult.syntacticSafety &= other.syntacticSafety;\n\t\tresult.syntacticGuarantee &= other.syntacticGuarantee;\n\t\tresult.syntacticObligation &= other.syntacticObligation;\n\t\tresult.syntacticRecurrence &= other.syntacticRecurrence;\n\t\tresult.syntacticPersistence &= other.syntacticPersistence;\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Apply the Boolean OR operator (i.e., corresponding to this | other),\n\t * returning the result.\n\t */\n\tprivate LTLFragments or(LTLFragments other)\n\t{\n\t\tLTLFragments result = new LTLFragments(this);\n\n\t\tresult.syntacticSafety &= other.syntacticSafety;\n\t\tresult.syntacticGuarantee &= other.syntacticGuarantee;\n\t\tresult.syntacticObligation &= other.syntacticObligation;\n\t\tresult.syntacticRecurrence &= other.syntacticRecurrence;\n\t\tresult.syntacticPersistence &= other.syntacticPersistence;\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Apply the Boolean NOT operator (i.e., corresponding to !this),\n\t * returning the result.\n\t */\n\tprivate LTLFragments not()\n\t{\n\t\tLTLFragments result = new LTLFragments();\n\n\t\t// take opposites\n\t\tresult.syntacticSafety = this.syntacticGuarantee;\n\t\tresult.syntacticGuarantee = this.syntacticSafety;\n\n\t\t// obligation stays the same\n\t\tresult.syntacticObligation = this.syntacticObligation;\n\n\t\t// take opposites\n\t\tresult.syntacticRecurrence = this.syntacticPersistence;\n\t\tresult.syntacticPersistence = this.syntacticRecurrence;\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Apply the temporal \"nextstep\" operator (i.e., corresponding to X this),\n\t * returning the result.\n\t */\n\tprivate LTLFragments nextstep()\n\t{\n\t\treturn new LTLFragments(this);  // just a copy\n\t}\n\n\t/**\n\t * Apply the temporal \"eventually\" operator (i.e., corresponding to F this),\n\t * returning the result.\n\t */\n\tprivate LTLFragments eventually()\n\t{\n\t\tLTLFragments result = new LTLFragments(this);  // copy\n\n\t\tresult.syntacticSafety = false;\n\t\t// syntacticGuarantee inherited\n\t\tresult.syntacticObligation = syntacticGuarantee;\n\t\tresult.syntacticRecurrence = syntacticGuarantee;\n\t\t// syntacticPersistence inherited\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Apply the temporal \"always\" operator (i.e., corresponding to G this),\n\t * returning the result.\n\t */\n\tprivate LTLFragments always()\n\t{\n\t\tLTLFragments result = new LTLFragments(this);  // copy\n\n\t\t// syntacticSafety inherited\n\t\tresult.syntacticGuarantee = false;\n\t\tresult.syntacticObligation = syntacticSafety;\n\t\t// syntacticRecurrence inherited\n\t\tresult.syntacticPersistence = syntacticSafety;\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Apply the temporal \"until\" operator (i.e., corresponding to this U other),\n\t * returning the result.\n\t */\n\tprivate LTLFragments until(LTLFragments other)\n\t{\n\t\tLTLFragments result = new LTLFragments();\n\t\t\n\t\tresult.syntacticSafety = false;\n\t\tresult.syntacticGuarantee = this.syntacticGuarantee & other.syntacticGuarantee;\n\t\tresult.syntacticObligation = this.syntacticObligation & other.syntacticGuarantee;\n\t\tresult.syntacticRecurrence = this.syntacticRecurrence & other.syntacticGuarantee;\n\t\tresult.syntacticPersistence = this.syntacticPersistence & other.syntacticPersistence;\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Apply the temporal \"release\" operator (i.e., corresponding to this R other),\n\t * returning the result.\n\t */\n\tprivate LTLFragments release(LTLFragments other)\n\t{\n\t\tLTLFragments result = new LTLFragments();\n\n\t\tresult.syntacticSafety = this.syntacticSafety & other.syntacticSafety;\n\t\tresult.syntacticGuarantee = false;\n\t\tresult.syntacticObligation = this.syntacticObligation & other.syntacticSafety;\n\t\tresult.syntacticRecurrence = this.syntacticRecurrence & other.syntacticRecurrence;\n\t\tresult.syntacticPersistence = this.syntacticPersistence & other.syntacticSafety;\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Apply the Boolean EQUIV operator (i.e., corresponding to this &lt;-&gt; other),\n\t * returning the result.\n\t */\n\tprivate LTLFragments equiv(LTLFragments other)\n\t{\n\t\tLTLFragments left = and(other);\n\t\tLTLFragments right = not().and(other.not());\n\n\t\treturn left.or(right);\n\t}\n\n\t/**\n\t * Apply the Boolean IMPLIES operator (i.e., corresponding to this -&gt; other),\n\t * returning the result.\n\t */\n\tprivate LTLFragments implies(LTLFragments other)\n\t{\n\t\tLTLFragments result = not().or(other);\n\t\treturn result;\n\t}\n\n\t/**\n\t * Analyse a given LTL formula and return the syntactic LTL fragments it belongs to.\n\t * @param root the root of the LTL formula\n\t * @return the LTLFragments it belongs to\n\t */\n\tpublic static LTLFragments analyse(SimpleLTL root)\n\t{\n\t\tswitch (root.kind) {\n\t\tcase TRUE:\n\t\tcase FALSE:\n\t\t\treturn new LTLFragments(); // all true\n\t\tcase AP:\n\t\t\treturn new LTLFragments(); // all true\n\t\tcase NOT:\n\t\t\treturn analyse(root.left).not();\n\n\t\tcase AND:\n\t\t\treturn analyse(root.left).and(analyse(root.right));\n\t\tcase OR:\n\t\t\treturn analyse(root.left).or(analyse(root.right));\n\n\t\tcase FINALLY:\n\t\t\treturn analyse(root.left).eventually();\n\t\tcase GLOBALLY:\n\t\t\treturn analyse(root.left).always();\n\t\tcase NEXT:\n\t\t\treturn analyse(root.left).nextstep();\n\t\tcase UNTIL:\n\t\t\treturn analyse(root.left).until(analyse(root.right));\n\t\tcase RELEASE:\n\t\t\treturn analyse(root.left).release(analyse(root.right));\n\n\t\tcase EQUIV:\n\t\t\treturn analyse(root.left).equiv(analyse(root.right));\n\t\tcase IMPLIES:\n\t\t\treturn analyse(root.left).implies(analyse(root.right));\n\t\t}\n\t\tthrow new UnsupportedOperationException();\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/MyBitSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2007 Carlos Bederian\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jltl2ba;\n\nimport java.util.BitSet;\nimport java.util.Vector;\nimport java.util.Iterator;\nimport java.io.PrintStream;\n\n\npublic class MyBitSet extends BitSet implements Comparable<BitSet>, Iterable<Integer> {\n\n\tprivate int _size;\t// workaround for default bitset size, resizing breaks stuff later!\n\t\n\tpublic MyBitSet()\n\t{\n\t\tsuper();\n\t\t_size = 0;\n\t}\n\n\tpublic MyBitSet(int size)\n\t{\n\t\tsuper(size);\n\t\tif (size > 0)\n\t\t\t_size = size;\n\t\telse _size = 0;\n\t}\n\t\n\tpublic int size() {\n\t\tif (_size > 0)\n\t\t\treturn _size;\n\t\telse return super.size();\n\t}\n\n\tpublic boolean containsAll(BitSet b) {\n\t\tBitSet tmp = (BitSet)this.clone();\n\t\ttmp.or(b);\n\t\treturn tmp.equals(this);\n\t}\n\n\t// ugly\n\tpublic Vector<Integer> IntegerList()\n\t{\n\t\tVector<Integer> tmp = new Vector<Integer>();\n\t\tfor (int i = 0; i < this.size(); i++)\n\t\t\tif (this.get(i))\n\t\t\t\ttmp.add(Integer.valueOf(i));\n\t\treturn tmp;\n\t}\n\n\tpublic void print(PrintStream out)\n\t{\t\t\t\t/* prints the content of a set */\n\t\tint i;\n\t\tboolean start = true;\n\n\t\tout.print(\"{\");\n\t\tfor (i = 0; i < size(); i++) {\n\t\t\tif (get(i)) {\n\t\t\t\tif (!start)\n\t\t\t\t\tout.print(\",\");\n\t\t\t\tout.print(i);\n\n\t\t\t\tstart = false;\n\t\t\t}\n\t\t}\n\t\tout.print(\"}\");\n\t}\n\n\tpublic void print(PrintStream out, APSet symtable, boolean pos)\n\t{\t\t\t\t/* prints the content of an ap set */\n\t\tint i;\n\t\tboolean start = true;\n\t\tfor (i = 0; i < size(); i++) {\n\t\t\tif (get(i)) {\n\t\t\t\tif (!start)\n\t\t\t\t\tout.print(\" & \");\n\t\t\t\tif (!pos)\n\t\t\t\t\tout.print(\"!\");\n\t\t\t\tout.print(symtable.getAP(i));\n\t\t\t\tstart = false;\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic int compareTo(BitSet o)\n\t{\n\t\tBitSet tmp1 = (BitSet) this.clone();\n\t\ttmp1.andNot(o);\n\t\tBitSet tmp2 = (BitSet) o.clone();\n\t\ttmp2.andNot(this);\n\t\treturn (tmp1.length() - tmp2.length());\n\t}\n\n\tpublic void increment() {\n\t\tint i = this.nextClearBit(0);\n\t\tthis.clear(0,i);\n\t\tthis.set(i);\n\t}\n\n\t/* An iterator over the set bits of a bitset */\n\tpublic Iterator<Integer> iterator() {\n\t\treturn new MyBitSetIterator(this);\n\t}\n\n\tpublic static class MyBitSetIterator implements Iterator<Integer> {\n\n\t\tprivate MyBitSet _bitset;\n\t\tprivate int index;\n\t\t\n\t\tpublic MyBitSetIterator(MyBitSet bitset) {\n\t\t\t_bitset = bitset;\n\t\t\tindex = _bitset.nextSetBit(0);\n\t\t}\n\t\t\n\t\tpublic boolean hasNext() {\n\t\t\treturn (index >= 0);\n\t\t}\n\t\t\n\t\tpublic Integer next() {\n\t\t\tInteger rv = Integer.valueOf(index);\n\t\t\tindex = _bitset.nextSetBit(index + 1);\n\t\t\treturn rv;\n\t\t}\n\t\t\n\t\tpublic void remove() {\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/README",
    "content": "LTL2BA - Version 1.0 - October 2001\nWritten by Denis Oddoux, LIAFA, France                                 \nCopyright (c) 2001  Denis Oddoux                                       \n     \nLTL2BA - Version 1.1 - August 2007\nModified by Paul Gastin, LSV, France                                 \nCopyright (c) 2007  Paul Gastin                                       \nAvailable at http://www.lsv.ens-cachan.fr/~gastin/ltl2ba\n\njltl2ba - November 2007\nPorted by Carlos S. Bederian, FaMAF, Argentina\nCopyright (c) 2007 Carlos S. Bederian\n                                                                  \nThis package is a Java port of LTL2BA 1.1 by Carlos Bederian\nfor use with PRISM.\n\nThe LTL2BA software was written by Denis Oddoux and modified by Paul\nGastin.  It is based on the translation algorithm presented at CAV '01:\n\tP.Gastin and D.Oddoux\n\t\"Fast LTL to B�chi Automata Translation\" \n\tin 13th International Conference on Computer Aided Verification, CAV 2001, \n\tG. Berry, H. Comon, A. Finkel (Eds.)\n\tParis, France, July 18-22, 2001, \n\tProceedings - LNCS 2102, pp. 53-65\n\nPart of the code included is issued from the SPIN software Version 3.4.1\nThe SPIN software is written by Gerard J. Holzmann, originally as part\nof ``Design and Validation of Protocols,'' ISBN 0-13-539925-4,\n1991, Prentice Hall, Englewood Cliffs, NJ, 07632\n"
  },
  {
    "path": "prism/src/jltl2ba/SimpleLTL.java",
    "content": "/* Written by Denis Oddoux, LIAFA, France                                 *\n * Copyright (c) 2001  Denis Oddoux                                       *\n * Modified by Paul Gastin, LSV, France                                   *\n * Copyright (c) 2007  Paul Gastin                                        *\n * Ported by Carlos Bederian, FaMAF, Argentina                            *\n * Copyright (c) 2007  Carlos Bederian                                    *\n *                                                                        *\n * This program is free software; you can redistribute it and/or modify   *\n * it under the terms of the GNU General Public License as published by   *\n * the Free Software Foundation; either version 2 of the License, or      *\n * (at your option) any later version.                                    *\n *                                                                        *\n * This program is distributed in the hope that it will be useful,        *\n * but WITHOUT ANY WARRANTY; without even the implied warranty of         *\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the          *\n * GNU General Public License for more details.                           *\n *                                                                        *\n * You should have received a copy of the GNU General Public License      *\n * along with this program; if not, write to the Free Software            *\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA*\n *                                                                        *\n * Based on the translation algorithm by Gastin and Oddoux,               *\n * presented at the 13th International Conference on Computer Aided       *\n * Verification, CAV 2001, Paris, France.                                 *\n * Proceedings - LNCS 2102, pp. 53-65                                     *\n *                                                                        */\n\npackage jltl2ba;\n\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.HashMap;\nimport java.util.IdentityHashMap;\nimport java.util.List;\nimport java.util.Map;\n\nimport jltl2dstar.APMonom;\nimport jltl2dstar.NBA;\nimport prism.PrismException;\n\npublic class SimpleLTL {\n\n\tpublic enum LTLType { \n\t\tFALSE, TRUE,\n\t\tAP,\n\t\tNOT, NEXT, \n\t\tOR, AND, EQUIV, IMPLIES,\n\t\tUNTIL, RELEASE,\n\t\tGLOBALLY, FINALLY\n\t};\n\n\tpublic SimpleLTL left;\n\tpublic SimpleLTL right;\n\tpublic LTLType kind;\n\tpublic String ap;\n\n\tpublic SimpleLTL(boolean v)\n\t{\n\t\tleft = null;\n\t\tright = null;\n\t\tkind = v ? LTLType.TRUE : LTLType.FALSE;\n\t\tap = null;\n\t}\n\n\tpublic SimpleLTL(String prop)\n\t{\n\t\tleft = null;\n\t\tright = null;\n\t\tkind = LTLType.AP;\n\t\tap = prop;\n\t}\n\n\tpublic SimpleLTL(LTLType type, SimpleLTL lft)\n\t{\n\t\tswitch (type) {\n\t\tcase NOT:\n\t\tcase NEXT:\n\t\tcase GLOBALLY:\n\t\tcase FINALLY:\n\t\t\tleft = lft;\n\t\t\tright = null;\n\t\t\tkind = type;\n\t\t\tap = null;\n\t\t\tbreak;\n\t\tdefault:\n\t\t//\tthrow new PrismException(\"Trying to build invalid SimpleLTL\");\n\t\t}\n\t}\n\n\tpublic SimpleLTL(LTLType type, SimpleLTL lft, SimpleLTL rgt)\n\t{\n\t\tswitch (type) {\n\t\tcase AND:\n\t\tcase OR:\n\t\tcase IMPLIES:\n\t\tcase EQUIV:\n\t\tcase UNTIL:\n\t\tcase RELEASE:\n\t\t\tleft = lft;\n\t\t\tright = rgt;\n\t\t\tkind = type;\n\t\t\tap = null;\n\t\t\tbreak;\n\t\tdefault:\n\t\t//\tthrow new PrismException(\"Trying to build invalid SimpleLTL\");\n\t\t}\n\t}\n\n\tpublic SimpleLTL(LTLType type, SimpleLTL lft, SimpleLTL rgt, String prop)\n\t{\n\t\tkind = type;\n\t\tleft = lft;\n\t\tright = rgt;\n\t\tap = null;\n\t\tif (prop != null) { ap = prop; }\n\t}\n\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o instanceof SimpleLTL) {\n\t\t\tSimpleLTL other = (SimpleLTL) o;\n\t\t\tif (kind == other.kind) {\n\t\t\t\tswitch (kind) {\n\t\t\t\tcase FALSE:case TRUE:\n\t\t\t\t\treturn true;\n\t\t\t\tcase NOT:case NEXT:case GLOBALLY:case FINALLY:\n\t\t\t\t\treturn left.equals(other.left);\n\t\t\t\tcase OR:case AND:case EQUIV:case IMPLIES:case UNTIL:case RELEASE:\n\t\t\t\t\treturn (left.equals(other.left) && right.equals(other.right));\n\t\t\t\tcase AP:\n\t\t\t\t\treturn ap.equals(other.ap);\n\t\t\t\tdefault:\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t\telse return false;\n\t\t}\n\t\telse return false;\n\t}\n\n\tpublic APSet getAPs()\n\t{\n\t\tAPSet rv;\n\n\t\tswitch (kind) {\n\t\tcase NOT:case NEXT:\n\t\tcase GLOBALLY:case FINALLY:\n\t\t\trv = left.getAPs();\n\t\t\tbreak;\n\t\tcase OR:case AND:\n\t\tcase EQUIV:case IMPLIES:\n\t\tcase UNTIL:case RELEASE:\n\t\t\trv = left.getAPs();\n\t\t\tfor (String s : right.getAPs())\n\t\t\t\trv.addAP(s);\n\t\t\tbreak;\n\t\t\t// terminals\n\t\tcase FALSE:case TRUE:\n\t\t\trv = new APSet();\n\t\t\tbreak;\n\t\tcase AP:\n\t\t\trv = new APSet();\n\t\t\trv.addAP(ap);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\trv = new APSet();\n\t\tbreak;\n\t\t}\n\t\treturn rv;\n\t}\n\n\tpublic SimpleLTL clone()\n\t{\n\t\tSimpleLTL rv = new SimpleLTL(kind,\n\t\t\t\tleft != null ? left.clone() : null,\n\t\t\t\t\t\tright != null ? right.clone() : null,\n\t\t\t\t\t\t\t\tap);\n\t\treturn rv;\n\t}\n\n\tprivate boolean implies(SimpleLTL b)\n\t{\n\t\treturn\n\t\t(this.equals(b) ||\n\t\t\t\tb.kind == LTLType.TRUE ||\n\t\t\t\tkind == LTLType.FALSE ||\n\t\t\t\t(b.kind == LTLType.AND && this.implies(b.left) && this.implies(b.right)) ||\n\t\t\t\t(kind == LTLType.OR && left.implies(b) && right.implies(b)) ||\n\t\t\t\t(kind == LTLType.AND && (left.implies(b) || right.implies(b))) ||\n\t\t\t\t(b.kind == LTLType.OR && (this.implies(b.left) || this.implies(b.right))) ||\n\t\t\t\t(b.kind == LTLType.UNTIL && this.implies(b.right)) ||\n\t\t\t\t(kind == LTLType.RELEASE && right.implies(b)) ||\n\t\t\t\t(kind == LTLType.UNTIL && left.implies(b) && right.implies(b)) ||\n\t\t\t\t(b.kind == LTLType.RELEASE && this.implies(b.left) && this.implies(b.right)) ||\n\t\t\t\t((kind == LTLType.UNTIL || kind == LTLType.RELEASE) && kind == b.kind &&\n\t\t\t\t\t\tleft.implies(b.left) && right.implies(b.right)));\n\t}\n\n\t/**\n\t * Construct simplified PNF form.\n\t *\n\t * Currently, this requires that the SimpleLTL formula is a tree, i.e., that\n\t * subtrees are not shared. If this is not the case,\n\t * an {@code IllegalArgumentException} is thrown.\n\t */\n\tpublic SimpleLTL simplify()\n\t{\n\t\tif (!this.isTree()) {\n\t\t\tthrow new IllegalArgumentException(\"Implementation error: SimpleLTL.simplify() requires that the formula is a tree, not a DAG\");\n\t\t}\n\t\treturn this.simplified();\n\t}\n\t\n\tprivate SimpleLTL simplified()\n\t{\n\t\tSimpleLTL tmp, tmp2, a, b;\n\t\tSimpleLTL rv = this;\n\t\t\n\t\tswitch (kind) {\n\t\tcase AND:\n\t\tcase OR:\n\t\tcase IMPLIES:\n\t\tcase EQUIV:\n\t\tcase UNTIL:\n\t\tcase RELEASE:\n\t\t\tright = right.simplified();\n\t\t\tleft = left.simplified();\n\t\t\tbreak;\n\n\t\tcase NOT:\n\t\tcase NEXT:\n\t\tcase FINALLY:\n\t\tcase GLOBALLY:\n\t\t\tleft = left.simplified();\n\t\t\tbreak;\n\n\t\tdefault:\n\t\t\t// do nothing\n\t\t}\n\n\t\tswitch (kind) {\n\t\tcase NOT:\n\t\t\ttmp = this.pushNegation();\n\t\t\tif (tmp.kind != LTLType.NOT)\n\t\t\t\trv = tmp.simplified();\n\t\t\telse rv = tmp;\n\t\t\tbreak;\n\t\t\t\n\t\tcase FINALLY:\n\t\t\tif (left.kind == LTLType.TRUE || left.kind == LTLType.FALSE) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\telse if (left.kind == LTLType.UNTIL) {\n\t\t\t\tif (left.left.kind == LTLType.TRUE) {\n\t\t\t\t\trv = left;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tleft = left.right;\n\t\t\t\t/* fall thru */\n\t\t\t}\n\t\t\ttmp = new SimpleLTL(LTLType.UNTIL, new SimpleLTL(true), left);\n\t\t\trv = tmp.simplified();\n\t\t\tbreak;\n\n\t\tcase GLOBALLY:\n\t\t\tif (left.kind == LTLType.FALSE || left.kind == LTLType.TRUE) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\telse if (left.kind == LTLType.RELEASE) {\n\t\t\t\tif (left.left.kind == LTLType.FALSE) {\n\t\t\t\t\trv = left;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tleft = left.right;\t/* [] (p V q) = [] q */\n\t\t\t\t/* fall thru */\n\t\t\t}\n\t\t\ttmp = new SimpleLTL(LTLType.RELEASE, new SimpleLTL(false), left);\n\t\t\trv = tmp.simplified();\n\t\t\tbreak;\n\n\t\tcase UNTIL:\n\t\t\tif (right.kind == LTLType.TRUE\n\t\t\t\t\t|| right.kind == LTLType.FALSE\n\t\t\t\t\t|| left.kind == LTLType.FALSE) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (left.implies(right)) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t/* (p U q) U p = (q U p) */\n\t\t\tif (left.kind == LTLType.UNTIL && left.left.equals(right)) {\t\n\t\t\t\tleft = left.right;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (right.kind == LTLType.UNTIL && left.implies(right.left)) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t/* X p U X q == X (p U q) */\n\t\t\tif (right.kind == LTLType.NEXT && left.kind == LTLType.NEXT) {\n\t\t\t\trv = new SimpleLTL(LTLType.NEXT, \n\t\t\t\t\t\tnew SimpleLTL(LTLType.UNTIL, left.left, right.left));\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* F X p == X F p */\n\t\t\tif (left.kind == LTLType.TRUE && right.kind == LTLType.NEXT) {\n\t\t\t\trv = new SimpleLTL(LTLType.NEXT,\n\t\t\t\t\t\tnew SimpleLTL(LTLType.UNTIL, new SimpleLTL(true), right.left));\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* F G F p == G F p */\n\t\t\tif (left.kind == LTLType.TRUE &&\n\t\t\t\t\tright.kind == LTLType.RELEASE &&\n\t\t\t\t\tright.left.kind == LTLType.FALSE &&\n\t\t\t\t\tright.right.kind == LTLType.UNTIL &&\n\t\t\t\t\tright.right.left.kind == LTLType.TRUE) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tif (left.kind != LTLType.TRUE) {\n\t\t\t\ttmp = new SimpleLTL(LTLType.NOT, right.clone());\n\t\t\t\tif (tmp.pushNegation().implies(left))\n\t\t\t\t\tleft = new SimpleLTL(true); \n\t\t\t\tbreak;\n\t\t\t}\t    \n\t\t\tbreak;\n\n\t\tcase RELEASE:\n\t\t\tif (right.kind == LTLType.FALSE\n\t\t\t\t\t|| right.kind == LTLType.TRUE\n\t\t\t\t\t|| left.kind == LTLType.TRUE) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t/* p V p = p */\n\t\t\tif (right.implies(left)) {\t\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t/* F V (p V q) == F V q */\n\t\t\tif (left.kind == LTLType.FALSE && right.kind == LTLType.RELEASE) {\n\t\t\t\tright = right.right;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* G X p == X G p */\n\t\t\tif (left.kind == LTLType.FALSE && right.kind == LTLType.NEXT) {\n\t\t\t\trv = new SimpleLTL(LTLType.NEXT,\n\t\t\t\t\t\tnew SimpleLTL(LTLType.RELEASE,\n\t\t\t\t\t\t\t\tnew SimpleLTL(false), right.left));\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t/* G F G p == F G p */\n\t\t\tif (left.kind == LTLType.FALSE &&\n\t\t\t\t\tright.kind == LTLType.UNTIL &&\n\t\t\t\t\tright.left.kind == LTLType.TRUE &&\n\t\t\t\t\tright.right.kind == LTLType.RELEASE &&\n\t\t\t\t\tright.right.left.kind == LTLType.FALSE) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tif (right.kind == LTLType.RELEASE\n\t\t\t\t\t&& right.left.implies(left)) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tif (left.kind != LTLType.FALSE) {\n\t\t\t\ttmp = new SimpleLTL(LTLType.NOT, right.clone());\n\t\t\t\tif (left.implies(tmp.pushNegation()))\n\t\t\t\t\tleft = new SimpleLTL(false);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase NEXT:\n\t\t\tif (left.kind == LTLType.TRUE || left.kind == LTLType.FALSE) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* X G F p == G F p */\n\t\t\tif (left.kind == LTLType.RELEASE &&\n\t\t\t\t\tleft.left.kind == LTLType.FALSE &&\n\t\t\t\t\tleft.right.kind == LTLType.UNTIL &&\n\t\t\t\t\tleft.right.left.kind == LTLType.TRUE) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t/* X F G p == F G p */\n\t\t\tif (left.kind == LTLType.UNTIL &&\n\t\t\t\t\tleft.left.kind == LTLType.TRUE &&\n\t\t\t\t\tleft.right.kind == LTLType.RELEASE &&\n\t\t\t\t\tleft.right.left.kind == LTLType.FALSE) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase IMPLIES:\n\t\t\tif (left.implies(right)) {\n\t\t\t\trv = new SimpleLTL(true);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\ttmp = new SimpleLTL(LTLType.NOT, left);\n\t\t\ttmp = new SimpleLTL(LTLType.OR, tmp.pushNegation(), right);\n\t\t\trv = tmp.rewrite();\n\t\t\tbreak;\n\n\t\tcase EQUIV:\n\t\t\tif (left.implies(right) &&\n\t\t\t\t\tright.implies(left)) {\n\t\t\t\trv = new SimpleLTL(true);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\ta = new SimpleLTL(LTLType.AND, left.clone(), right.clone());\n\t\t\ttmp = new SimpleLTL(LTLType.NOT, left);\n\t\t\ttmp2 = new SimpleLTL(LTLType.NOT, right);\n\t\t\tb = new SimpleLTL(LTLType.AND, tmp.pushNegation(), tmp2.pushNegation());\n\t\t\trv = new SimpleLTL(LTLType.OR, a.rewrite(), b.rewrite());\n\t\t\trv = rv.rewrite();\n\t\t\tbreak;\n\n\t\tcase AND:\n\t\t\t/* p && (q U p) = p */\n\t\t\tif (right.kind == LTLType.UNTIL\n\t\t\t\t\t&& right.right.equals(left)) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (left.kind == LTLType.UNTIL\n\t\t\t\t\t&& left.right.equals(right)) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* p && (q V p) == q V p */\n\t\t\tif (right.kind == LTLType.RELEASE\n\t\t\t\t\t&& right.right.equals(left)) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (left.kind == LTLType.RELEASE\n\t\t\t\t\t&& left.right.equals(right)) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* (p U q) && (r U q) = (p && r) U q */\n\t\t\tif (right.kind == LTLType.UNTIL\n\t\t\t\t\t&& left.kind == LTLType.UNTIL\n\t\t\t\t\t&& right.right.equals(left.right)) {\n\t\t\t\trv = new SimpleLTL(LTLType.UNTIL,\n\t\t\t\t\t\tnew SimpleLTL(LTLType.AND, left.left, right.left),\n\t\t\t\t\t\tleft.right);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* (p V q) && (p V r) = p V (q && r) */\n\t\t\tif (right.kind == LTLType.RELEASE\n\t\t\t\t\t&& left.kind == LTLType.RELEASE\n\t\t\t\t\t&& right.left.equals(left.left)) {\n\t\t\t\trv = new SimpleLTL(LTLType.RELEASE,\n\t\t\t\t\t\tright.left,\n\t\t\t\t\t\tnew SimpleLTL(LTLType.AND, left.right, right.right)); \n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* X p && X q == X (p && q) */\n\t\t\tif (right.kind == LTLType.NEXT && left.kind == LTLType.NEXT) {\n\t\t\t\trv = new SimpleLTL(LTLType.NEXT,\n\t\t\t\t\t\tnew SimpleLTL(LTLType.AND, left.left, right.left));\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* (p V q) && (r U q) == p V q */\n\t\t\tif (right.kind == LTLType.UNTIL\n\t\t\t\t\t&& left.kind == LTLType.RELEASE\n\t\t\t\t\t&& left.right.equals(right.right)) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tif (left.equals(right)\t/* (p && p) == p */\n\t\t\t\t\t||right.kind == LTLType.FALSE\t/* (p && F) == F */\n\t\t\t\t\t|| left.kind == LTLType.TRUE\t/* (T && p) == p */\n\t\t\t\t\t|| right.implies(left)) {\t/* NEW */\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (right.kind == LTLType.TRUE\t/* (p && T) == p */\n\t\t\t\t\t|| left.kind == LTLType.FALSE\t/* (F && p) == F */\n\t\t\t\t\t|| left.implies(right)) {\t/* NEW */\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* F G p && F G q == F G (p && q) */\n\t\t\tif (left.kind == LTLType.UNTIL &&\n\t\t\t\t\tleft.left.kind == LTLType.TRUE &&\n\t\t\t\t\tleft.right.kind == LTLType.RELEASE &&\n\t\t\t\t\tleft.right.left.kind == LTLType.FALSE &&\n\t\t\t\t\tright.kind == LTLType.UNTIL &&\n\t\t\t\t\tright.left.kind == LTLType.TRUE &&\n\t\t\t\t\tright.right.kind == LTLType.RELEASE &&\n\t\t\t\t\tright.right.left.kind == LTLType.FALSE) {\n\t\t\t\trv = new SimpleLTL(LTLType.UNTIL, \n\t\t\t\t\t\tnew SimpleLTL(true),\n\t\t\t\t\t\tnew SimpleLTL(LTLType.RELEASE, \n\t\t\t\t\t\t\t\tnew SimpleLTL(false),\n\t\t\t\t\t\t\t\tnew SimpleLTL(LTLType.AND,\n\t\t\t\t\t\t\t\t\t\tleft.right.right,\n\t\t\t\t\t\t\t\t\t\tright.right.right)));\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\ttmp = new SimpleLTL(LTLType.NOT, right.clone());\n\t\t\tif (left.implies(tmp.pushNegation())) {\n\t\t\t\trv = new SimpleLTL(false);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\ttmp = new SimpleLTL(LTLType.NOT, left.clone());\n\t\t\tif (right.implies(tmp.pushNegation())) {\n\t\t\t\trv = new SimpleLTL(false);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase OR:\n\t\t\t/* p || (q U p) == q U p */\n\t\t\tif (right.kind == LTLType.UNTIL\n\t\t\t\t\t&& right.right.equals(left)) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* p || (q V p) == p */\n\t\t\tif (right.kind == LTLType.RELEASE\n\t\t\t\t\t&& right.right.equals(left)) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* (p U q) || (p U r) = p U (q || r) */\n\t\t\tif (right.kind == LTLType.UNTIL\n\t\t\t\t\t&& left.kind == LTLType.UNTIL\n\t\t\t\t\t&& right.left.equals(left.left)) {\n\t\t\t\trv = new SimpleLTL(LTLType.UNTIL,\n\t\t\t\t\t\tright.left,\n\t\t\t\t\t\tnew SimpleLTL(LTLType.OR, left.right, right.right));\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tif (left.equals(right)\t/* (p || p) == p */\n\t\t\t\t\t||right.kind == LTLType.FALSE\t/* (p || F) == p */\n\t\t\t\t\t|| left.kind == LTLType.TRUE\t/* (T || p) == T */\n\t\t\t\t\t|| right.implies(left)) {\n\t\t\t\trv = left;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (right.kind == LTLType.TRUE\t/* (p || T) == T */\n\t\t\t\t\t|| left.kind == LTLType.FALSE\t/* (F || p) == p */\n\t\t\t\t\t|| left.implies(right)) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* (p V q) || (r V q) = (p || r) V q */\n\t\t\tif (right.kind == LTLType.RELEASE\n\t\t\t\t\t&& left.kind == LTLType.RELEASE\n\t\t\t\t\t&& left.right.equals(right.right)) {\n\t\t\t\trv = new SimpleLTL(LTLType.RELEASE,\n\t\t\t\t\t\tnew SimpleLTL(LTLType.OR, left.left, right.left),\n\t\t\t\t\t\tright.right);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* (p V q) || (r U q) == r U q */\n\t\t\tif (right.kind == LTLType.UNTIL\n\t\t\t\t\t&& left.kind == LTLType.RELEASE\n\t\t\t\t\t&& left.right.equals(right.right)) {\n\t\t\t\trv = right;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t/* G F p || G F q == G F (p || q) */\n\t\t\tif (left.kind == LTLType.RELEASE &&\n\t\t\t\t\tleft.left.kind == LTLType.FALSE &&\n\t\t\t\t\tleft.right.kind == LTLType.UNTIL &&\n\t\t\t\t\tleft.right.left.kind == LTLType.TRUE &&\n\t\t\t\t\tright.kind == LTLType.RELEASE &&\n\t\t\t\t\tright.left.kind == LTLType.FALSE &&\n\t\t\t\t\tright.right.kind == LTLType.UNTIL &&\n\t\t\t\t\tright.right.left.kind == LTLType.TRUE) {\n\t\t\t\trv = new SimpleLTL(LTLType.RELEASE,\n\t\t\t\t\t\tnew SimpleLTL(false),\n\t\t\t\t\t\tnew SimpleLTL(LTLType.UNTIL,\n\t\t\t\t\t\t\t\tnew SimpleLTL(true),\n\t\t\t\t\t\t\t\tnew SimpleLTL(LTLType.OR,left.right.right,right.right.right)));\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\ttmp = new SimpleLTL(LTLType.NOT, right.clone());\n\t\t\tif (tmp.pushNegation().implies(left)) {\n\t\t\t\trv = new SimpleLTL(true);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\ttmp = new SimpleLTL(LTLType.NOT, left.clone());\n\t\t\tif (tmp.pushNegation().implies(right)) {\n\t\t\t\trv = new SimpleLTL(true);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Returns an equivalent SimpleLTL formula with a\n\t * basic set of operators:\n\t *   AP, TRUE, FALSE, AND, OR, NOT, UNTIL, FINALLY, GLOBALLY, NEXT\n\t */\n\tpublic SimpleLTL toBasicOperators() {\n\t\tswitch (kind) {\n\t\tcase AP:\n\t\tcase TRUE:\n\t\tcase FALSE:\n\t\t\treturn this;\n\t\tcase AND:\n\t\tcase OR:\n\t\tcase UNTIL:\n\t\t\treturn new SimpleLTL(kind, left.toBasicOperators(), right.toBasicOperators());\n\t\tcase FINALLY:\n\t\tcase GLOBALLY:\n\t\tcase NEXT:\n\t\tcase NOT:\n\t\t\treturn new SimpleLTL(kind, left.toBasicOperators());\n\t\tcase EQUIV: {\n\t\t\tSimpleLTL newLeft = left.toBasicOperators();\n\t\t\tSimpleLTL newRight = right.toBasicOperators();\n\t\t\tSimpleLTL bothTrue = new SimpleLTL(LTLType.AND, newLeft, newRight);\n\t\t\tSimpleLTL bothFalse = new SimpleLTL(LTLType.AND,\n\t\t\t                                    new SimpleLTL(LTLType.NOT, newLeft),\n\t\t\t                                    new SimpleLTL(LTLType.NOT, newRight));\n\t\t\treturn new SimpleLTL(LTLType.OR, bothTrue, bothFalse);\n\t\t}\n\t\tcase IMPLIES: {\n\t\t\tSimpleLTL newLeft = new SimpleLTL(LTLType.NOT, left.toBasicOperators());\n\t\t\treturn new SimpleLTL(LTLType.OR, newLeft, right.toBasicOperators());\n\t\t}\n\t\tcase RELEASE: {\n\t\t\tSimpleLTL newLeft = new SimpleLTL(LTLType.NOT, left.toBasicOperators());\n\t\t\tSimpleLTL newRight = new SimpleLTL(LTLType.NOT, right.toBasicOperators());\n\t\t\treturn new SimpleLTL(LTLType.UNTIL, newLeft, newRight);\n\t\t}\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unknown operator in SimpleLTL\");\n\t}\n\n\tpublic SimpleLTL negate() {\n\t\treturn new SimpleLTL(LTLType.NOT, this);\n\t}\n\n\tpublic SimpleLTL pushNegation()\n\t{\t\n\t\tSimpleLTL m;\n\t\tboolean pushBothOperands = false;\n\n\t\tif (kind != LTLType.NOT)\n\t\t\treturn this;\n\t\t\t// throw new PrismException(\"No NOT to push!\");\n\n\t\tswitch (left.kind) {\n\t\tcase TRUE:\n\t\t\tleft = null;\n\t\t\tkind = LTLType.FALSE;\n\t\t\tbreak;\n\t\tcase FALSE:\n\t\t\tleft = null;\n\t\t\tkind = LTLType.TRUE;\n\t\t\tbreak;\n\t\tcase NOT:\n\t\t\tm = left.left;\n\t\t\tleft = m.left;\n\t\t\tright = m.right;\n\t\t\tkind = m.kind;\n\t\t\tif (kind == LTLType.AP) { ap = m.ap; }\n\t\t\tbreak;\n\t\tcase RELEASE:\n\t\t\tkind = LTLType.UNTIL;\n\t\t\tpushBothOperands = true;\n\t\t\tbreak;\n\t\tcase UNTIL:\n\t\t\tkind = LTLType.RELEASE;\n\t\t\tpushBothOperands = true;\n\t\t\tbreak;\n\t\tcase NEXT:\n\t\t\tkind = LTLType.NEXT;\n\t\t\tleft.kind = LTLType.NOT;\n\t\t\tleft = left.pushNegation();\n\t\t\tbreak;\n\t\tcase AND:\n\t\t\tkind = LTLType.OR;\n\t\t\tpushBothOperands = true;\n\t\t\tbreak;\n\t\tcase OR:\n\t\t\tkind = LTLType.AND;\n\t\t\tpushBothOperands = true;\n\t\t\tbreak;\n\t\tcase IMPLIES:\n\t\t\tkind = LTLType.AND;\n\t\t\tm = new SimpleLTL(LTLType.NOT, left.right);\n\t\t\tright = m.pushNegation();\n\t\t\tleft = left.left;\n\t\t\tbreak;\n\t\tcase EQUIV:\n\t\t\tkind = LTLType.OR;\n\t\t\tm = new SimpleLTL(LTLType.NOT, left.left.clone());\n\t\t\tright = new SimpleLTL(LTLType.AND, m.pushNegation(), left.right.clone());\n\t\t\tleft.kind = LTLType.AND;\n\t\t\tm = new SimpleLTL(LTLType.NOT, left.right);\n\t\t\tleft.right = m.pushNegation();\n\t\t\tbreak;\n\t\tcase FINALLY:\n\t\t\tkind = LTLType.GLOBALLY;\n\t\t\tleft.kind = LTLType.NOT;\n\t\t\tleft = left.pushNegation();\n\t\t\tbreak;\n\t\tcase GLOBALLY:\n\t\t\tkind = LTLType.FINALLY;\n\t\t\tleft.kind = LTLType.NOT;\n\t\t\tleft = left.pushNegation();\n\t\t\tbreak;\n\t\tcase AP:\n\t\t\treturn this;\n\t\t}\n\t\tif (pushBothOperands) {\n\t\t\tm = new SimpleLTL(LTLType.NOT, left.right);\n\t\t\tright = m.pushNegation();\n\t\t\tleft.kind = LTLType.NOT;\n\t\t\tleft.right = null;\n\t\t\tleft = left.pushNegation();\n\t\t}\n\t\treturn this.rewrite();\n\t}\n\t\n\tpublic SimpleLTL rewrite()\n\t{\n\t\treturn this.rightLinked().canonical();\n\t}\n\n\tpublic SimpleLTL rightLinked()\n\t{\n\t\tSimpleLTL tmp;\n\t\tSimpleLTL n = this;\n\n\t\tif (n.kind == LTLType.AND || n.kind == LTLType.OR) {\n\t\t\twhile (n.left != null && n.left.kind == n.kind) {\n\t\t\t\ttmp = n.left;\n\t\t\t\tn.left = tmp.right;\n\t\t\t\ttmp.right = n;\n\t\t\t\tn = tmp;\n\t\t\t}\n\t\t}\n\t\tif (n.left != null)\n\t\t\tn.left = n.left.rightLinked();\n\t\tif (n.right != null)\n\t\t\tn.right = n.right.rightLinked();\n\n\t\treturn n;\n\t}\n\n\tpublic SimpleLTL canonical()\n\t{\n\t\treturn this;\t// No caches here, yet\n\n\t\t/* SimpleLTL m;\t\t// assumes input is right_linked\n\n\t\tif ((m = in_cache(n)) != ZN)\n\t\t\treturn m;\n\n\t\tn->rgt = canonical(n->rgt);\n\t\tn->lft = canonical(n->lft);\n\n\t\treturn cached(n);\n\t\t */\n\t}\n\n\tpublic int countNodes()\n\t{\n\t\tswitch (kind) {\n\t\tcase AND:\n\t\tcase OR:\n\t\tcase IMPLIES:\n\t\tcase EQUIV:\n\t\tcase UNTIL:\n\t\tcase RELEASE:\n\t\t\treturn left.countNodes() + right.countNodes() + 1;\n\t\tcase NEXT:\n\t\tcase FINALLY:\n\t\tcase GLOBALLY:\n\t\tcase NOT:\n\t\t\treturn left.countNodes() + 1;\n\t\tdefault:\n\t\t\treturn 1;\n\t\t}\n\t}\n\n\tpublic int countPredicates()\n\t{\n\t\tswitch (kind) {\n\t\tcase AND:\n\t\tcase OR:\n\t\tcase IMPLIES:\n\t\tcase EQUIV:\n\t\tcase UNTIL:\n\t\tcase RELEASE:\n\t\t\treturn left.countPredicates() + right.countPredicates();\n\t\tcase NEXT:\n\t\tcase FINALLY:\n\t\tcase GLOBALLY:\n\t\tcase NOT:\n\t\t\treturn left.countPredicates();\n\t\tcase AP:\n\t\t\treturn 1;\n\t\tdefault:\n\t\t\treturn 0;\n\t\t}\n\t}\n\n\tpublic String toString()\n\t{\n\t\tString rv = \"\";\n\n\t\tswitch (kind) {\n\t\tcase OR:\n\t\t\trv = \"(\" + left.toString() + \" || \" + right.toString() + \")\";\n\t\t\tbreak;\n\t\tcase AND:\n\t\t\trv = \"(\" + left.toString() + \" && \" + right.toString() + \")\";\n\t\t\tbreak;\n\t\tcase UNTIL:\n\t\t\trv = \"(\" + left.toString() + \" U \" + right.toString() + \")\";\n\t\t\tbreak;\n\t\tcase RELEASE:\n\t\t\trv = \"(\" + left.toString() + \" V \" + right.toString() + \")\";\n\t\t\tbreak;\n\t\tcase IMPLIES:\n\t\t\trv = \"(\" + left.toString() + \" -> \" + right.toString() + \")\";\n\t\t\tbreak;\n\t\tcase EQUIV:\n\t\t\trv = \"(\" + left.toString() + \" <-> \" + right.toString() + \")\";\n\t\t\tbreak;\n\t\tcase NEXT:\n\t\t\trv = \"X \" + left.toString();\n\t\t\tbreak;\n\t\tcase FINALLY:\n\t\t\trv = \"F \" + left.toString();\n\t\t\tbreak;\n\t\tcase GLOBALLY:\n\t\t\trv = \"G \" + left.toString();\n\t\t\tbreak;\n\t\tcase NOT:\n\t\t\trv = \"! \" + left.toString();\n\t\t\tbreak;\n\t\tcase FALSE:\n\t\t\trv = \"false\";\n\t\t\tbreak;\n\t\tcase TRUE:\n\t\t\trv = \"true\";\n\t\t\tbreak;\n\t\tcase AP:\n\t\t\trv = ap;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\trv = null;\n\t\t}\n\t\treturn rv;\n\t}\n\n\t// ltl2dstar stuff\n\tpublic boolean isCoSafe()\n\t{\n\t\tswitch(kind) {\n\t\tcase RELEASE:\n\t\tcase GLOBALLY:\n\t\t\treturn false;\n\t\tdefault:\n\t\t\tif (left != null && !left.isCoSafe()) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\tif (right != null && !right.isCoSafe()) {\n\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t\t}\n\t}\n\n\tpublic boolean hasNextStep()\n\t{\n\t\tif (kind == LTLType.NEXT) {\n\t\t\treturn true;\n\t\t}\n\t\tif (left != null && left.hasNextStep()) {\n\t\t\treturn true;\n\t\t}\n\t\tif (right != null && right.hasNextStep()) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Returns true if this SimpleLTL structure is a tree, i.e., not a\n\t * directed acyclical graph (DAG) where sharing of subtrees is allowed.\n\t */\n\tpublic boolean isTree()\n\t{\n\t\t// use an IdentityHashMap with (formula,formula) pairs indicating that formula\n\t\t// has already been seen (due to lack of IdentityHashSet)\n\t\tIdentityHashMap<SimpleLTL, SimpleLTL> seen = new IdentityHashMap<SimpleLTL, SimpleLTL>();\n\t\treturn isTree(seen);\n\t}\n\n\t/**\n\t * Recursive function for checking if this SimpleLTL structure is a tree, i.e., not a\n\t * directed acyclical graph (DAG) where sharing of subtrees is allowed.\n\t *\n\t * The already seen SimpleLTL subtrees are tracked in {@code seen}.\n\t */\n\tprivate boolean isTree(IdentityHashMap<SimpleLTL,SimpleLTL> seen)\n\t{\n\t\tif (seen.containsKey(this)) {\n\t\t\treturn false;\n\t\t}\n\t\tseen.put(this, this);\n\n\t\tif (left != null && !left.isTree(seen)) {\n\t\t\t// left child exists and is not a tree\n\t\t\treturn false;\n\t\t}\n\t\tif (right != null && !right.isTree(seen)) {\n\t\t\t// right child exists and is not a tree\n\t\t\treturn false;\n\t\t}\n\n\t\treturn true;\n\t}\n\n\t/**\n\t * Transform LTL formula by extend each<br>\n\t * X phi<br>\n\t * node in the syntax tree to<br>\n\t * X (label & phi).\n\t * <br>\n\t * The LTL formula has to consist only of basic operators (see toBasicOperators()).\n\t * @param label the label of the atomic proposition\n\t * @return the transformed LTL formula\n\t */\n\tpublic SimpleLTL extendNextStepWithAP(String label)\n\t{\n\t\tswitch (kind) {\n\t\tcase TRUE:\n\t\tcase FALSE:\n\t\tcase AP:\n\t\t\treturn this.clone();\n\t\tcase NOT: {\n\t\t\tSimpleLTL newLeft = left.extendNextStepWithAP(label);\n\t\t\treturn new SimpleLTL(kind, newLeft);\n\t\t}\n\t\tcase NEXT: {\n\t\t\tSimpleLTL newLeft = left.extendNextStepWithAP(label);\n\t\t\t// transform X phi to X (\"label\" & phi)\n\t\t\treturn new SimpleLTL(LTLType.NEXT,\n\t\t\t\t\tnew SimpleLTL(LTLType.AND, new SimpleLTL(label), newLeft));\n\t\t}\n\t\tcase OR:\n\t\tcase AND:\n\t\tcase RELEASE:\n\t\tcase UNTIL: {\n\t\t\tSimpleLTL newLeft = left.extendNextStepWithAP(label);\n\t\t\tSimpleLTL newRight = right.extendNextStepWithAP(label);\n\t\t\treturn new SimpleLTL(kind, newLeft, newRight);\n\t\t}\n\t\tcase FINALLY:\n\t\tcase GLOBALLY: {\n\t\t\tSimpleLTL newLeft = left.extendNextStepWithAP(label);\n\t\t\treturn new SimpleLTL(kind, newLeft);\n\t\t}\n\t\tcase EQUIV:\n\t\tcase IMPLIES:\n\t\t\tthrow new UnsupportedOperationException(\"Extending Next operator with AP not supported for \" + kind.toString() + \" operator, only for basic operators: \" + this);\n\t\t}\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\tpublic SimpleLTL toDNF() throws PrismException\n\t{\n\t\tswitch (kind) {\n\t\tcase TRUE:\n\t\t\treturn new SimpleLTL(true);\n\t\tcase FALSE:\n\t\t\treturn new SimpleLTL(false);\n\t\tcase NOT:\n\t\t\treturn new SimpleLTL(LTLType.NOT, left.toDNF());\n\t\tcase AP:\n\t\t\treturn new SimpleLTL(ap);\n\t\tcase OR:\n\t\t\treturn new SimpleLTL(LTLType.OR, left.toDNF(), right.toDNF());\n\t\tcase AND:\n\t\t\tSimpleLTL l = left.toDNF();\n\t\t\tSimpleLTL r = right.toDNF();\n\n\t\t\tif (l.kind == LTLType.OR) {\n\t\t\t\tSimpleLTL a, b;\n\t\t\t\ta = l.left;\n\t\t\t\tb = l.right;\n\n\t\t\t\tif (r.kind == LTLType.OR) {\n\t\t\t\t\tSimpleLTL c, d;\n\t\t\t\t\tc=r.left;\n\t\t\t\t\td=r.right;\n\n\t\t\t\t\tSimpleLTL a_c = new SimpleLTL(LTLType.AND, a, c);\n\t\t\t\t\tSimpleLTL b_c = new SimpleLTL(LTLType.AND, b, c);\n\t\t\t\t\tSimpleLTL a_d = new SimpleLTL(LTLType.AND, a, d);\n\t\t\t\t\tSimpleLTL b_d = new SimpleLTL(LTLType.AND, b, d);\n\n\t\t\t\t\treturn new SimpleLTL(LTLType.OR,\n\t\t\t\t\t\t\t(new SimpleLTL(LTLType.OR, a_c, b_c)).toDNF(),\n\t\t\t\t\t\t\t(new SimpleLTL(LTLType.OR, a_d, b_d)).toDNF());\t  \n\t\t\t\t} else {\n\t\t\t\t\tSimpleLTL a_c = new SimpleLTL(LTLType.AND, a, r);\n\t\t\t\t\tSimpleLTL b_c = new SimpleLTL(LTLType.AND, b, r);\n\n\t\t\t\t\treturn new SimpleLTL(LTLType.OR, a_c.toDNF(), b_c.toDNF());\n\t\t\t\t}\n\t\t\t} else if (r.kind == LTLType.OR) {\n\t\t\t\tSimpleLTL a, b;\n\t\t\t\ta = r.left;\n\t\t\t\tb = r.right;\n\n\t\t\t\tSimpleLTL a_c = new SimpleLTL(LTLType.AND, l, a);\n\t\t\t\tSimpleLTL b_c = new SimpleLTL(LTLType.AND, l, b);\n\n\t\t\t\treturn new SimpleLTL(LTLType.OR, a_c.toDNF(), b_c.toDNF());\n\t\t\t} else {\n\t\t\t\treturn new SimpleLTL(LTLType.AND, l, r);\n\t\t\t}\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Illegal operator for DNF!\");\n\t\t}\n\t}\n\n\t/** Returns an APMonom representing the formula rooted at\n\t * this node. Formula has to be in DNF. */\n\tpublic APMonom toMonom(APSet apset) throws PrismException\n\t{\n\t\tAPMonom result = new APMonom(true);\n\n\t\tswitch (kind) {\n\t\tcase AND: {\n\t\t\tAPMonom l = left.toMonom(apset);\n\t\t\tAPMonom r = right.toMonom(apset);\n\n\t\t\tresult = l.and(r);\n\t\t\treturn result;\n\t\t}\n\t\tcase NOT:\n\t\t\tswitch (left.kind) {\n\t\t\tcase AP:\n\t\t\t\tresult.setValue(apset.indexOf(left.ap), false);\n\t\t\t\treturn result;\n\t\t\tcase FALSE:\n\t\t\t\treturn new APMonom(true);\n\t\t\tcase TRUE:\n\t\t\t\treturn new APMonom(false);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Formula not in DNF!\");\n\t\t\t}\t  \n\t\tcase AP:\n\t\t\tresult.setValue(apset.indexOf(ap), true);\n\t\t\treturn result;\n\t\tcase FALSE:\n\t\t\treturn new APMonom(false);\n\t\tcase TRUE:\n\t\t\treturn new APMonom(true);\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Formula not in DNF!\");\n\t\t}\n\t}\n\n\t/**\n\t * Renames the atomic propositions apparing in the formula that\n\t * start with {@code prefixFrom}. For these, the prefix is replaced\n\t * by prefixTo. For example, with prefixFrom = \"L\" and prefixTo = \"p\",\n\t * \"L3\" will be renamed to \"p3\", but \"T2\" will be left as-is.\n\t */\n\tpublic void renameAP(String prefixFrom, String prefixTo)\n\t{\n\t\tswitch (kind) {\n\t\tcase AP:\n\t\t\tif (ap.startsWith(prefixFrom)) {\n\t\t\t\tap = prefixTo + ap.substring(prefixFrom.length());\n\t\t\t}\n\t\t\treturn;\n\t\tcase AND:\n\t\tcase OR:\n\t\tcase EQUIV:\n\t\tcase IMPLIES:\n\t\tcase RELEASE:\n\t\tcase UNTIL:\n\t\t\tleft.renameAP(prefixFrom, prefixTo);\n\t\t\tright.renameAP(prefixFrom, prefixTo);\n\t\t\treturn;\n\t\tcase FINALLY:\n\t\tcase GLOBALLY:\n\t\tcase NEXT:\n\t\tcase NOT:\n\t\t\tleft.renameAP(prefixFrom, prefixTo);\n\t\t\treturn;\n\t\tcase TRUE:\n\t\tcase FALSE:\n\t\t\treturn;\n\t\t}\n\t\tthrow new UnsupportedOperationException(\"Unknown operator in SimpleLTL formula: \"+this);\n\t}\n\t\n\t/**\n\t * Render this LTL formula in LBT syntax, i.e., in prefix notation.\n\t */\n\tpublic String toStringLBT()\n\t{\n\t\tString rv = \"\";\n\n\t\tswitch (kind) {\n\t\tcase OR:\n\t\t\trv = \"| \" + left.toStringLBT() + \" \" + right.toStringLBT();\n\t\t\tbreak;\n\t\tcase AND:\n\t\t\trv = \"& \" + left.toStringLBT() + \" \" + right.toStringLBT();\n\t\t\tbreak;\n\t\tcase UNTIL:\n\t\t\trv = \"U \" + left.toStringLBT() + \" \" + right.toStringLBT();\n\t\t\tbreak;\n\t\tcase RELEASE:\n\t\t\trv = \"V \" + left.toStringLBT() + \" \" + right.toStringLBT();\n\t\t\tbreak;\n\t\tcase IMPLIES:\n\t\t\trv = \"i \" + left.toStringLBT() + \" \" + right.toStringLBT();\n\t\t\tbreak;\n\t\tcase EQUIV:\n\t\t\trv = \"e \" + left.toStringLBT() + \" \" + right.toStringLBT();\n\t\t\tbreak;\n\t\tcase NEXT:\n\t\t\trv = \"X \" + left.toStringLBT();\n\t\t\tbreak;\n\t\tcase FINALLY:\n\t\t\trv = \"F \" + left.toStringLBT();\n\t\t\tbreak;\n\t\tcase GLOBALLY:\n\t\t\trv = \"G \" + left.toStringLBT();\n\t\t\tbreak;\n\t\tcase NOT:\n\t\t\trv = \"! \" + left.toStringLBT();\n\t\t\tbreak;\n\t\tcase FALSE:\n\t\t\trv = \"f\";\n\t\t\tbreak;\n\t\tcase TRUE:\n\t\t\trv = \"t\";\n\t\t\tbreak;\n\t\tcase AP:\n\t\t\trv = ap;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\trv = null;\n\t\t}\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Render this LTL formula in Spin syntax.\n\t */\n\tpublic String toStringSpin()\n\t{\n\t\tString rv = \"\";\n\n\t\tswitch (kind) {\n\t\tcase OR:\n\t\t\trv = \"(\" + left.toStringSpin() + \") || (\" + right.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase AND:\n\t\t\trv = \"(\" + left.toStringSpin() + \") && (\" + right.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase UNTIL:\n\t\t\trv = \"(\" + left.toStringSpin() + \") U (\" + right.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase RELEASE:\n\t\t\trv = \"(\" + left.toStringSpin() + \") V (\" + right.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase IMPLIES:\n\t\t\trv = \"(\" + left.toStringSpin() + \") -> (\" + right.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase EQUIV:\n\t\t\trv = \"(\" + left.toStringSpin() + \") <-> (\" + right.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase NEXT:\n\t\t\trv = \"X (\" + left.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase FINALLY:\n\t\t\trv = \"<> (\" + left.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase GLOBALLY:\n\t\t\trv = \"[] (\" + left.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase NOT:\n\t\t\trv = \"! (\" + left.toStringSpin() + \")\";\n\t\t\tbreak;\n\t\tcase FALSE:\n\t\t\trv = \"false\";\n\t\t\tbreak;\n\t\tcase TRUE:\n\t\t\trv = \"true\";\n\t\t\tbreak;\n\t\tcase AP:\n\t\t\trv = ap;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\trv = null;\n\t\t}\n\t\treturn rv;\n\t}\n\n\t\n\t/**\n\t * Render this LTL formula in Spot syntax.\n\t */\n\tpublic String toStringSpot()\n\t{\n\t\tString rv = \"\";\n\n\t\tswitch (kind) {\n\t\tcase OR:\n\t\t\trv = \"(\" + left.toStringSpot() + \") | (\" + right.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase AND:\n\t\t\trv = \"(\" + left.toStringSpot() + \") & (\" + right.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase UNTIL:\n\t\t\trv = \"(\" + left.toStringSpot() + \") U (\" + right.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase RELEASE:\n\t\t\trv = \"(\" + left.toStringSpot() + \") R (\" + right.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase IMPLIES:\n\t\t\trv = \"(\" + left.toStringSpot() + \") -> (\" + right.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase EQUIV:\n\t\t\trv = \"(\" + left.toStringSpot() + \") <-> (\" + right.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase NEXT:\n\t\t\trv = \"X (\" + left.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase FINALLY:\n\t\t\trv = \"F (\" + left.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase GLOBALLY:\n\t\t\trv = \"G (\" + left.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase NOT:\n\t\t\trv = \"! (\" + left.toStringSpot() + \")\";\n\t\t\tbreak;\n\t\tcase FALSE:\n\t\t\trv = \"false\";\n\t\t\tbreak;\n\t\tcase TRUE:\n\t\t\trv = \"true\";\n\t\t\tbreak;\n\t\tcase AP:\n\t\t\trv = ap;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\trv = null;\n\t\t}\n\t\treturn rv;\n\t}\n\n\t/** Parse a formula in LBT (prefix format) */\n\tpublic static SimpleLTL parseFormulaLBT(String formula) throws Exception\n\t{\n\t\tformula=formula.trim();  // remove leading, trailing spaces\n\t\tString[] split = formula.split(\"[ ]+\");\n\t\tList<String> formulaList = new ArrayList<String>();\n\t\tfor (String s : split) formulaList.add(s);\n\n\t\t// set up operator -> SimpleLTL.LTLType mapping for the standard operators\n\t\tMap<String, SimpleLTL.LTLType> unaryOps  = new HashMap<String, SimpleLTL.LTLType>();\n\t\tMap<String, SimpleLTL.LTLType> binaryOps = new HashMap<String, SimpleLTL.LTLType>();\n\t\tunaryOps.put(\"!\", SimpleLTL.LTLType.NOT);\n\t\tunaryOps.put(\"F\", SimpleLTL.LTLType.FINALLY);\n\t\tunaryOps.put(\"G\", SimpleLTL.LTLType.GLOBALLY);\n\t\tunaryOps.put(\"X\", SimpleLTL.LTLType.NEXT);\n\t\tbinaryOps.put(\"|\", SimpleLTL.LTLType.OR);\n\t\tbinaryOps.put(\"&\", SimpleLTL.LTLType.AND);\n\t\tbinaryOps.put(\"i\", SimpleLTL.LTLType.IMPLIES);\n\t\tbinaryOps.put(\"e\", SimpleLTL.LTLType.EQUIV);\n\t\tbinaryOps.put(\"U\", SimpleLTL.LTLType.UNTIL);\n\t\tbinaryOps.put(\"V\", SimpleLTL.LTLType.RELEASE);\n\n\t\tSimpleLTL result = parseFormulaLBT(formulaList, unaryOps, binaryOps);\n\n\t\tif (formulaList.size()>0) {\n\t\t\tString remainingFormula = \"\";\n\t\t\tfor (String op : formulaList) remainingFormula += \" \"+op;\n\t\t\tthrow new RuntimeException(\"Malformed formula, extra information after end of formula: \"+remainingFormula);\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Parse a formula in LBT format, where the formula is already split into a list of operators / APs\n\t * @param formulaList sequence of operators / APs\n\t * @param unaryOps map for the standard unary ops\n\t * @param binaryOps map for the standard binary ops\n\t * @throws RuntimeException on parse error\n\t */\n\tprivate static SimpleLTL parseFormulaLBT(List<String> formulaList,\n\t                                         Map<String, SimpleLTL.LTLType> unaryOps,\n\t                                         Map<String, SimpleLTL.LTLType> binaryOps) throws RuntimeException\n\t{\n\t\tif (formulaList.size() == 0) {\n\t\t\tthrow new RuntimeException(\"Malformed formula, premature ending\");\n\t\t}\n\t\tString current = formulaList.get(0);\n\t\tformulaList.remove(0);\n\n\t\tif (current.equals(\"t\")) {\n\t\t\treturn new SimpleLTL(true);\n\t\t} else if (current.equals(\"f\")) {\n\t\t\treturn new SimpleLTL(false);\n\t\t} else if (unaryOps.containsKey(current)) {\n\t\t\t// standard unary op\n\t\t\tSimpleLTL operand = parseFormulaLBT(formulaList, unaryOps, binaryOps);\n\t\t\treturn new SimpleLTL(unaryOps.get(current), operand);\n\t\t} else if (binaryOps.containsKey(current)) {\n\t\t\t// standard binary op\n\t\t\tSimpleLTL operand1 = parseFormulaLBT(formulaList, unaryOps, binaryOps);\n\t\t\tSimpleLTL operand2 = parseFormulaLBT(formulaList, unaryOps, binaryOps);\n\t\t\treturn new SimpleLTL(binaryOps.get(current), operand1, operand2);\n\t\t} else if (current.equals(\"W\")) {\n\t\t\t// a W b == !(a&!b U !a&!b)\n\t\t\tSimpleLTL operand1 = parseFormulaLBT(formulaList, unaryOps, binaryOps);\n\t\t\tSimpleLTL operand2 = parseFormulaLBT(formulaList, unaryOps, binaryOps);\n\n\t\t\tSimpleLTL aAndNotb =\n\t\t\t   new SimpleLTL(SimpleLTL.LTLType.AND, operand1.clone(),\n\t\t\t     new SimpleLTL(SimpleLTL.LTLType.NOT, operand2.clone()));\n\t\t\t\n\t\t\tSimpleLTL NotaAndNotb =\n\t\t\t   new SimpleLTL(SimpleLTL.LTLType.AND,\n\t\t\t     new SimpleLTL(SimpleLTL.LTLType.NOT, operand1.clone()),\n\t\t\t     new SimpleLTL(SimpleLTL.LTLType.NOT, operand2.clone()));\n\n\t\t\treturn new SimpleLTL(SimpleLTL.LTLType.NOT,\n\t\t\t   new SimpleLTL(SimpleLTL.LTLType.UNTIL, aAndNotb, NotaAndNotb));\n\t\t} else if (current.equals(\"^\")) {\n\t\t\t// a xor b == !(a equiv b)\n\t\t\tSimpleLTL operand1 = parseFormulaLBT(formulaList, unaryOps, binaryOps);\n\t\t\tSimpleLTL operand2 = parseFormulaLBT(formulaList, unaryOps, binaryOps);\n\n\t\t\treturn new SimpleLTL(SimpleLTL.LTLType.NOT,\n\t\t\t    new SimpleLTL(SimpleLTL.LTLType.EQUIV, operand1, operand2));\n\t\t} else if (current.equals(\"M\") || current.equals(\"B\")) {\n\t\t\tthrow new RuntimeException(\"Operator \"+current+\" currently not supported.\");\n\t\t} else if (current.matches(\"[a-zA-Z].*\")) {\n\t\t\t// atomic proposition\n\t\t\treturn new SimpleLTL(current);\n\t\t} else {\n\t\t\tthrow new RuntimeException(\"Illegal/unsupported operator: \"+current);\n\t\t}\n\t}\n\n\tpublic NBA toNBA(APSet apset) throws PrismException\n\t{\n\t\tAlternating a = new Alternating(this, apset);\n\t\t// a.print(System.out);\n\t\tGeneralized g = new Generalized(a);\n\t\t// g.print(System.out, apset);\n\t\tBuchi b = new Buchi(g);\n\t\t// b.print_spin(System.out, apset);\n\t\tNBA nba = b.toNBA(apset);\n\t\t// nba.print(System.out);\n\n\t\t// jltl2ba should never produce disjoint NBA,\n\t\t// i.e., where some states are not reachable\n\t\t// from the intial state, so we want to fail\n\t\t// later if the NBA is discovered to be disjoint:\n\t\tnba.setFailIfDisjoint(true);\n\n\t\treturn nba;\n\t}\n\t\n\tpublic NBA toNBA() throws PrismException\n\t{\n\t\treturn this.toNBA(new APSet());\n\t}\n\n\t/** Print a DOT representation of the syntax tree of this SimpleLTL formula */\n\tpublic void toDot(PrintStream out) {\n\t\tIdentityHashMap<SimpleLTL, String> map = new IdentityHashMap<SimpleLTL, String>();\n\n\t\tout.println(\"digraph {\");\n\t\ttoDot(out, map);\n\t\tout.println(\"}\");\n\t}\n\n\t/**\n\t * Print a DOT representation of the syntax tree of this SimpleLTL formula.\n\t *\n\t * @param out the output print stream\n\t * @param seen a map storing an identifier for each subformula that has already been seen / printed\n\t */\n\tprivate String toDot(PrintStream out, IdentityHashMap<SimpleLTL, String> seen)\n\t{\n\t\tString id = seen.get(this);\n\t\tif (id != null) {\n\t\t\treturn id;\n\t\t}\n\n\t\tid = Integer.toString(seen.size());\n\t\tseen.put(this, id);\n\t\tout.println(id + \" [label=\\\"\"+toStringLBT()+\"\\\"]\");\n\n\t\tswitch (kind) {\n\t\tcase AND:\n\t\tcase EQUIV:\n\t\tcase OR:\n\t\tcase UNTIL:\n\t\tcase RELEASE:\n\t\tcase IMPLIES: {\n\t\t\tString leftID = left.toDot(out, seen);\n\t\t\tString rightID = right.toDot(out, seen);\n\t\t\tout.println(id + \" -> \" + leftID);\n\t\t\tout.println(id + \" -> \" + rightID);\n\t\t\tbreak;\n\t\t}\n\t\tcase FINALLY:\n\t\tcase GLOBALLY:\n\t\tcase NEXT:\n\t\tcase NOT: {\n\t\t\tString leftID = left.toDot(out, seen);\n\t\t\tout.println(id + \" -> \" + leftID);\n\t\t\tbreak;\n\t\t}\n\n\t\tcase AP:\n\t\tcase TRUE:\n\t\tcase FALSE:\n\t\t\tbreak;\n\n\t\tdefault:\n\t\t\tbreak;\n\t\t}\n\n\t\treturn id;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/jltl2ba/package-info.java",
    "content": "/**\n * Java port of the LTL to Buchi automata conversion library.\n */\npackage jltl2ba;\n"
  },
  {
    "path": "prism/src/jltl2dstar/APMonom.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport prism.PrismException;\nimport java.util.Iterator;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport jltl2ba.MyBitSet;\n\n/**\n * Class representing a subset of 2^AP where AP is the set of \n * atomic propositions (APSet). It stores two bits per AP: \n * One bit to determine if the value of this AP is set, \n * the second bit to store the value.<br>\n * Additionally, the APMonom can have the special values\n * TRUE or FALSE.<br>\n */\npublic class APMonom {\n\n\tprivate MyBitSet bits_set;\n\tprivate MyBitSet bits_value;\n\tprivate boolean booleanValue;\n\n\tpublic APMonom()\n\t{\n\t\tbits_set = new MyBitSet();\n\t\tbits_value = new MyBitSet();\n\t\tbooleanValue = true;\n\t}\n\n\tpublic APMonom(boolean b) {\n\t\tbits_set = new MyBitSet();\n\t\tbits_value = new MyBitSet();\n\t\tbooleanValue = b;\n\t}\n\n\tpublic APMonom(MyBitSet set, MyBitSet value)\n\t{\n\t\tbits_set = set;\n\t\tbits_value = value;\n\t}\n\n\t/**\n\t * Is the AP set?\n\t * @param index index of AP\n\t * @return <b>true</b> if AP is set\n\t */\n\tpublic boolean isSet(int index) throws PrismException {\n\t\tif (!isNormal()) {\n\t\t\t// TRUE / FALSE -> the bit is not set\n\t\t\treturn false;\n\t\t}\n\t\treturn bits_set.get(index);\n\t}\n\n\t/**\n\t * Gets the value for this AP. You can't get the value if the AP is not set.\n\t * @param index index of AP\n\t * @return <b>true</b> if AP is true\n\t */\n\tpublic boolean getValue(int index) throws PrismException {\n\t\tif (!isNormal()) {\n\t\t\tthrow new PrismException(\"Can't get AP, is either TRUE/FALSE!\");\n\t\t}\n\n\t\tif (!bits_set.get(index)) {\n\t\t\tthrow new PrismException(\"Can't get value: AP not set!\");\n\t\t}\n\n\t\treturn bits_value.get(index);\n\t}\n\n\t/**\n\t * Sets the value for this AP. Implicitly, it also sets the AP to 'set'.\n\t * @param index index of AP\n\t * @param value value of AP\n\t */\n\tpublic void setValue(int index, boolean value) {\n\t\tbits_set.set(index, true);\n\t\tbits_value.set(index, value);\n\t}\n\n\n\t/**\n\t * Perform a logical AND operation of this APMonom with a single AP.\n\t * @param index index index of AP\n\t * @param value value of AP\n\t */\n\tpublic void andAP(int index, boolean value) {\n\t\tif (isFalse()) {return;}\n\n\t\tif (!isTrue()) {\n\t\t\tif (bits_set.get(index) && bits_value.get(index) != value) {\n\t\t\t\t// contradiction\n\t\t\t\tbooleanValue = false;\n\t\t\t\tbits_set.clear();\n\t\t\t\tbits_value.clear();\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\tsetValue(index, value);\n\t}\n\n\n\t/**\n\t * Unsets this AP.\n\t * @param index index of AP\n\t */\n\tpublic void unset(int index) {\n\t\tbits_value.set(index,false);\n\t\tbits_set.set(index, false);\n\t}\n\n\n\t/**\n\t * Checks if this APMonom is equivalent to TRUE.\n\t * @return <b>true</b> if this APMonom is TRUE\n\t */\n\tpublic boolean isTrue() {\n\t\treturn (!isNormal() && booleanValue);\n\t}\n\n\t/**\n\t * Checks if this APMonom is equivalent to FALSE.\n\t * @return <b>true</b> if this APMonom is FALSE\n\t */\n\tpublic boolean isFalse() {\n\t\treturn (!isNormal() && !booleanValue);\n\t}\n\n\t/**\n\t * Checks if this APMonom is a normal APMonon (not equivalent to TRUE or FALSE).\n\t * @return <b>true</b> if this APMonom is normal (not TRUE/FALSE).\n\t */\n\tpublic boolean isNormal() {\n\t\treturn !bits_set.isEmpty();\n\t}\n\n\t/**\n\t * Provides access to the underlying MyBitSet representing the\n\t * value (AP occurs in positive or negative form).\n\t * @return the SimpleBitSet of the values\n\t */\n\tpublic MyBitSet getValueBits() {\n\t\treturn bits_value;\n\t}\n\n\t/**\n\t * Provides access to the underlying MyBitSet representing the\n\t * bits that are set (AP occurs).\n\t * @return the SimpleBitSet of the occuring APs\n\t */\n\tpublic MyBitSet getSetBits() {\n\t\treturn bits_set;\n\t}\n\n\t/** Checks to see if the MyBitSet representation is normalized. */\n\tpublic boolean isNormalized() {\n\t\tif (isTrue() || isFalse()) {\n\t\t\treturn true;\n\t\t}\n\t\tMyBitSet tmp = getValueBits();\n\t\ttmp.andNot(bits_set);\n\t\treturn tmp.isEmpty();\n\t}\n\n\t/**\n\t * Output APMonom\n\t */\n\tpublic String toString()\n\t{\n\t\tString rv = \"\";\n\t\tif (isTrue()) {\n\t\t\treturn \"true\";\n\t\t} else if (isFalse()) {\n\t\t\treturn \"false\";\n\t\t} else {\n\t\t\tfor (int i = 0; i < bits_set.size(); i++) {\n\t\t\t\tif (bits_set.get(i)) {\n\t\t\t\t\tif (bits_value.get(i)) {\n\t\t\t\t\t\trv = rv + \"+\" + i;\n\t\t\t\t\t} else {\n\t\t\t\t\t\trv = rv + \"-\" + i;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Performs an intersection check.\n\t * @param m1 the first APMonom\n\t * @param m2 the second APMonom\n\t * @return <b>true</b> if the intersection of <i>m1</i> and <i>m2</i> is empty.\n\t * \n\t * FIXME: I'm not sure if this does what it says it does, but ltl2dstar does it this way.\n\t */\n\tpublic boolean isIntersectionEmpty(APMonom m2) {\n\t\t// check if there are contradicting values \n\t\tMyBitSet set_in_both = getSetBits();\n\t\tset_in_both.and(m2.getSetBits());\n\n\t\tMyBitSet maskedm1 = getValueBits();\n\t\tmaskedm1.and(set_in_both);\n\n\t\tMyBitSet maskedm2 = m2.getValueBits();\n\t\tmaskedm2.and(set_in_both);\n\n\t\treturn ! maskedm1.equals(maskedm2);\n\t}\n\n\t/**\n\t * Perform logical conjunction with other APMonom.\n\t * @param other the other APMonom\n\t */\n\tpublic APMonom and(APMonom other) {\n\t\tif (this.isFalse() || other.isFalse()) {\n\t\t\treturn new APMonom(false);\n\t\t}\n\n\t\tif (this.isTrue()) {return other;}\n\t\tif (other.isTrue()) {return this;}\n\n\t\t// both are not TRUE/FALSE:\n\n\t\tif (this.isIntersectionEmpty(other)) {\n\t\t\t//  return APMonom equivalent to false\n\t\t\treturn new APMonom(false);\n\t\t}\n\n\t\t// both Monoms are not contradicting...\n\t\tMyBitSet result_set = this.getSetBits();\n\t\tresult_set.or(other.getSetBits());\n\n\t\tMyBitSet result_value = this.getValueBits();\n\t\tresult_value.or(other.getValueBits());\n\n\t\treturn new APMonom(result_set, result_value);\n\t}\n\n\t/**\n\t * Perform 'minus' operation (equal to *this & !other).\n\t * @param other the other APMonom\n\t */\n\tAPMonom andNot(APMonom other) {\n\t\tif (this.isFalse()) {\n\t\t\t// false & anything == false\n\t\t\treturn new APMonom(false);\n\t\t}\n\n\t\tif (other.isFalse()) {\n\t\t\t// *this & !(false) == *this & true == *this\n\t\t\treturn this;\n\t\t}\n\n\t\tif (other.isTrue()) {\n\t\t\t// *this & !(true) == *this & false == false\n\t\t\treturn new APMonom(false);\n\t\t}\n\n\t\t// the result will be false, if there are two set bits\n\t\t// with equal value\n\t\tMyBitSet set_in_both= getSetBits();\n\t\tset_in_both.and(other.getSetBits());\n\n\t\tMyBitSet maskedm1 = getValueBits();\n\t\tmaskedm1.and(set_in_both);\n\n\t\tMyBitSet maskedm2 = other.getValueBits();\n\t\tmaskedm2.and(set_in_both);\n\t\tmaskedm2.flip(0,maskedm2.size());\n\n\t\tif (!maskedm1.equals(maskedm2)) {\n\t\t\t// return false;\n\t\t\treturn new APMonom(false);\n\t\t}\n\t\tMyBitSet result_set = getSetBits();\n\t\tresult_set.or(other.getSetBits());\n\n\t\tMyBitSet result_value = getValueBits();\n\t\tresult_value.andNot(other.getValueBits());\n\n\t\treturn new APMonom(result_set, result_value);\n\t}\n\n\n\t/**\n\t * Checks for equality.\n\t * @param other the other APMonom\n\t * @return <b>true</b> if this and the other APMonom are equal\n\t */\n\tpublic boolean equals(APMonom other) {\n\t\treturn (isNormal() && other.isNormal() &&\n\t\t\t\tgetValueBits().equals(other.getValueBits()) && \n\t\t\t\tgetSetBits().equals(other.getSetBits()) ||\n\t\t\t\tisTrue() && other.isTrue() ||\n\t\t\t\tisFalse() && other.isFalse());\n\t}\n\n\tpublic boolean equals(Object other) {\n\t\treturn ((other instanceof APMonom) && this.equals((APMonom) other));\n\t}\n\n\tpublic Iterator<APElement> APElementIterator(APSet s)\n\t{\n\t\treturn (Iterator<APElement>) new APMonom2APElements(s, this);  \n\t}\n\n\tpublic void setFromPosNeg(MyBitSet pos, MyBitSet neg) throws PrismException\n\t{\n\t\tint sz = pos.size() > neg.size() ? pos.size() : neg.size();\n\n\t\tif (pos.intersects(neg)) {\n\t\t\tthrow new PrismException(\"MyBitSet contradiction\");\n\t\t}\n\t\tif ((pos.cardinality() == sz)\n\t\t\t\t|| (pos.cardinality() == 0 && neg.cardinality() == 0)) {\n\t\t\tbits_set = new MyBitSet(sz);\n\t\t\tbits_value = new MyBitSet(sz);\n\t\t\tbooleanValue = true;\n\t\t}\n\t\telse if (neg.cardinality() == sz) {\n\t\t\tbits_set = new MyBitSet(sz);\n\t\t\tbits_value = new MyBitSet(sz);\n\t\t\tbooleanValue = false;\n\t\t}\n\t\telse {\n\t\t\tif (pos.size() == sz) {\n\t\t\t\tbits_set = (MyBitSet) pos.clone();\n\t\t\t\tbits_set.or(neg);  \n\t\t\t\tbits_value = (MyBitSet) pos.clone();\n\t\t\t}\n\t\t\telse {\n\t\t\t\tbits_set = (MyBitSet) neg.clone();\n\t\t\t\tbits_set.or(pos);  \n\t\t\t\tbits_value = new MyBitSet(sz); \n\t\t\t\tbits_value.or(pos);\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/APMonom2APElements.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.Iterator;\nimport java.util.NoSuchElementException;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport jltl2ba.MyBitSet;\n\n/**\n * Iterator over all APElements that are represented by an APMonom.\n * As every APMonom represents a subset of 2^AP, this allows access\n * to all of the members of this subset.<br>\n */\npublic class APMonom2APElements implements Iterator<APElement> {\n\t\n\t/** The underlying APSet. */\n\tprivate APSet _ap_set;    \n\t  \n\t/** The underlying APMonom. */\n\tprivate APMonom _m;       \n\n\t/** The current APElement. */\n\tprivate APElement _cur_e;\n\t\n\t/** Bits that are set */\n\tprivate MyBitSet set_mask;\n\n\t/** Marker, true if end was reached */\n\tprivate boolean _end_marker;\n\n\tpublic APMonom2APElements(APSet s, APMonom m)\n\t{\n\t\t_m = m;\n\t\t_ap_set = s;\n\t\t_cur_e = new APElement(m.getValueBits());\n\t\t_end_marker = m.isFalse();\n\t\t\n\t\tif (m.isTrue()) {\n\t\t\tset_mask = new MyBitSet(_ap_set.size());\n\t\t}\n\t\telse {\n\t\t\tset_mask = _m.getSetBits();\n\t\t}\n\t}\n\t\n\tprivate void increment() {\n\t    for (int i = set_mask.nextClearBit(0); i < _ap_set.size(); i = set_mask.nextClearBit(i+1)) {\n\t    \tif (_cur_e.get(i) == false) {\n\t    \t\t_cur_e.set(i, true);\n\t    \t\treturn;\n\t    \t} else {\n\t    \t\t_cur_e.set(i, false);\n\t    \t}\n\t    }\n\t    // overflow -> end\n\t    _end_marker = true;\n\t}\n\t\n\tpublic boolean hasNext()\n\t{\n\t\treturn !_end_marker;\n\t}\n\t\n\tpublic APElement next() throws NoSuchElementException\n\t{\n\t\tif (hasNext()) {\n\t\t\tAPElement rv = (APElement) _cur_e.clone();\n\t\t\tincrement();\n\t\t\treturn rv;\n\t\t}\n\t\telse throw new NoSuchElementException();\n\t}\n\t\n\tpublic void remove() throws UnsupportedOperationException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/AcceptanceForState.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport prism.PrismException;\n\n/** Accessor for the acceptance signature for a state \n *  (part of AcceptanceCondition interface)\n */\npublic class AcceptanceForState {\n\n\t/** Reference to the underlying RabinAcceptance */\n\tprivate RabinAcceptance _acceptance;\n\t/** The state index for this accessor */\n\tprivate int _state_index;\n\n\t/** Constructor */\n\tpublic AcceptanceForState(RabinAcceptance acceptance, int state_index) {\n\t\t_acceptance = acceptance;\n\t\t_state_index = state_index;\n\t}\n\n\t/** Add this state to L[pair_index] */\n\tpublic void addTo_L(int pair_index) {\n\t\t_acceptance.getAcceptance_L(pair_index).set(_state_index);\n\t\t_acceptance.getAcceptance_U(pair_index).set(_state_index, false);\n\t}\n\n\t/** Add this state to U[pair_index] */\n\tpublic void addTo_U(int pair_index) {\n\t\t_acceptance.getAcceptance_U(pair_index).set(_state_index);\n\t\t_acceptance.getAcceptance_L(pair_index).set(_state_index, false);\n\t}\n\n\t/** Is this state in L[pair_index] */\n\tpublic boolean isIn_L(int pair_index) {\n\t\treturn _acceptance.isStateInAcceptance_L(pair_index, _state_index);\n\t}\n\n\t/** Is this state in U[pair_index] */\n\tpublic boolean isIn_U(int pair_index) {\n\t\treturn _acceptance.isStateInAcceptance_U(pair_index, _state_index);\n\t}\n\n\t/** Set L and U for this state according to RabinSignature */\n\tpublic void setSignature(RabinSignature signature) {\n\t\tfor (int i = 0; i < signature.size(); i++) {\n\t\t\tif (signature.getL().get(i)) {\n\t\t\t\taddTo_L(i);\n\t\t\t}\n\t\t\tif (signature.getU().get(i)) {\n\t\t\t\taddTo_U(i);\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Get number of acceptance pairs */\n\tpublic int size() throws PrismException {\n\t\treturn _acceptance.size();\n\t}\n\n\t/** Get the signature for this state */\n\tRabinSignature getSignature() throws PrismException {\n\t\treturn new RabinSignature(_acceptance.getAcceptance_L_forState(_state_index),\n\t\t\t\t_acceptance.getAcceptance_U_forState(_state_index),\n\t\t\t\t_acceptance.size());\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/DA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n * Copyright (c) 2011- Hongyang Qu\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.io.PrintStream;\nimport java.util.*;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\npublic class DA {\n\n\t/**\n\t * A class representing a deterministic omega automaton.\n\t * <p>\n\t * The template parameters:<br>\n\t * Label: the type of the labeling on the edges<br>\n\t * EdgeContainer: a template (taking the DA_State class as parameter)\n\t *                providing an EdgeContainer for holding the edges in \n\t *                the states.<br>\n\t * </p>\n\t * <p>\n\t *  Each state is identified by an index.<br>\n\t *  There exists one start state.<br>\n\t *  There exists an acceptance condition <br>\n\t *  The DA is <i>compact</i>, if there are no holes in the indexes of the\n\t *  states and the acceptance condition is compact as well.\n\t * </p>\n\t */\n\n\t/** The storage index for the states. */\n\tprivate Vector<DA_State> _index;\n\n\t/** The underlying APset. */\n\tprivate APSet _ap_set;\n\n\t/** The start state. */\n\tprivate DA_State _start_state;\n\n\t/** Flag to mark that the automaton is compact. */\n\tprivate boolean _is_compact;\n\n\t/** A comment */\n\tprivate String _comment;\n\n\t/** The acceptance condition for this automaton. */\n\tprivate RabinAcceptance _acceptance;\n\n\t/**\n\t * Constructor.\n\t * @param ap_set the underlying APSet.\n\t */\n\tpublic DA(APSet ap_set)\n\t{\n\t\t_ap_set = ap_set; \n\t\t_start_state = null; \n\t\t_is_compact = true;\n\t\t_comment = \"\";\n\t\t_index = new Vector<DA_State>();\n\t\t_acceptance = new RabinAcceptance();\n\t}\n\t\n\tpublic static DA newInstance(APSet ap_set) {\n\t\treturn new DA(ap_set);\n\t}\n\n\t/**\n\t * Create a new state.\n\t * @return a pointer to the new state.\n\t */\n\tpublic DA_State newState()\n\t{\n\t\tDA_State state = new DA_State(this);\n\t\tint name = _index.size();\n\t\tstate.setName(name);\n\t\t_index.add(state);\n\t\t_acceptance.addState(name);\n\t\treturn state;\n\t}\n\n\t/** Make this automaton into an never accepting automaton */\n\tpublic void constructEmpty() {\n\t\tDA_State n = newState();\n\t\tsetStartState(n);\n\n\t\tfor (Iterator<APElement> it = getAPSet().elementIterator(); it.hasNext(); ){\n\t\t\tn.edges().put(it.next(), n);\n\t\t}\n\t}\n\n\t/** The number of states in the automaton.*/\n\tpublic int size()\n\t{\n\t\treturn _index.size();\n\t}\n\n\t/** The type of an iterator over the states */\n\tpublic Iterator<DA_State> iterator()\n\t{\n\t\treturn _index.iterator();\n\t}\n\n\t/**\n\t * Array index operator, get the state with index i.\n\t */\n\tpublic DA_State get(int i)\n\t{\n\t\treturn _index.get(i);\n\t}\n\n\t/**\n\t * Get the size of the underlying APSet.\n\t */\n\tpublic int getAPSize()\n\t{\n\t\treturn _ap_set.size();\n\t}\n\n\t/**\n\t * Get a const reference to the underlying APSet.\n\t */\n\tpublic APSet getAPSet()\n\t{\n\t\treturn _ap_set;\n\t}\n\n\t/**\n\t * Switch the APSet to another with the same number of APs.\n\t */\n\tpublic void switchAPSet(APSet new_apset) throws PrismException\n\t{\n\t\tif (new_apset.size() != _ap_set.size()) {\n\t\t\tthrow new PrismException(\"New APSet has to have the same size as the old APSet!\");\n\t\t}\n\t\t_ap_set=new_apset;\n\t}\n\n\t/**\n\t * Get the index for a state.\n\t */\n\tpublic int getIndexForState(DA_State state)\n\t{\n\t\treturn _index.indexOf(state);\n\t}\n\n\t/** Set the start state. */\n\tpublic void setStartState(DA_State state)\n\t{\n\t\t_start_state=state;\n\t}\n\n\t/**\n\t * Get the start state.\n\t * @return the start state, or NULL if it wasn't set.\n\t */\n\tpublic DA_State getStartState()\n\t{\n\t\treturn _start_state;\n\t}\n\n\t/** Checks if the automaton is compact. */\n\tpublic boolean isCompact()\n\t{\n\t\treturn _is_compact && acceptance().isCompact();\n\t}\n\n\t/** Set a comment for the automaton. */\n\tpublic void setComment(String comment)\n\t{\n\t\t_comment=comment;\n\t}\n\n\t/** Get the comment for the automaton. */\n\tpublic String getComment()\n\t{\n\t\treturn _comment;\n\t}\n\n\t/** Return reference to the acceptance condition for this automaton.\n\t * @return reference to the acceptance condition\n\t */\n\tpublic RabinAcceptance acceptance()\n\t{\n\t\treturn _acceptance;\n\t}\n\n\t/**\n\t * Reorder states and acceptance conditions so that\n\t * the automaton becomes compact.\n\t */\n\tpublic void makeCompact() throws PrismException {\n\t\tacceptance().makeCompact();\n\n\t\tif (!_is_compact) {\n\t\t\tint i, j;\n\t\t\tboolean moved = false;\n\n\t\t\tVector<Integer> mapping = new Vector<Integer>(_index.size());\n\t\t\tfor (i = 0, j = 0; i < _index.size(); i++) {\n\t\t\t\tif (_index.get(i) != null) {\n\t\t\t\t\tmapping.set(i, Integer.valueOf(j));\n\t\t\t\t\tif (j != i) {\n\t\t\t\t\t\t_index.set(j, _index.get(i));\n\t\t\t\t\t\t_index.set(i, null);\n\t\t\t\t\t\tmoved = true;\n\t\t\t\t\t}\n\t\t\t\t\tj++;\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\twhile (_index.get(i) == null && i < _index.size()) {\n\t\t\t\t\t\ti++;\n\t\t\t\t\t}\n\t\t\t\t\tif (i < _index.size())\n\t\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (moved) {\n\t\t\t\t_index.setSize(j);\n\t\t\t\tacceptance().moveStates(mapping);\n\t\t\t}\n\t\t\t_is_compact=true;\n\t\t}\n\t}\n\n\n\t/**\n\t * Print the DA in v2 format to the output stream.\n\t * This functions expects that the DA is compact.\n\t * @param da_type a string specifying the type of automaton (\"DRA\", \"DSA\").\n\t * @param out the output stream \n\t */\n\tpublic void\tprint(String da_type, PrintStream out) throws PrismException {\n\t\t// Ensure that this DA is compact...\n\t\tif (!this.isCompact()) {\n\t\t\tthrow new PrismException(\"DA is not compact!\");\n\t\t}\n\n\t\tif (this.getStartState() == null) {\n\t\t\t// No start state! \n\t\t\tthrow new PrismException(\"No start state in DA!\");\n\t\t}\n\n\t\tout.println(da_type+\" v2 explicit\");\n\t\t\n\t\tif (_comment != \"\") {\n\t\t\tout.println(\"Comment: \\\"\" + _comment + \"\\\"\");\n\t\t}\n\t\tout.println(\"States: \" + _index.size());\n\t\t_acceptance.outputAcceptanceHeader(out);\n\n\t\tint start_state = this.getStartState().getName();\n\t\tout.println(\"Start: \" + start_state);\n\n\t\t// Enumerate APSet\n\t\tout.print(\"AP: \" + getAPSize());\n\t\tfor (int ap_i = 0; ap_i < getAPSize(); ap_i++) {\n\t\t\tout.print(\" \\\"\" + getAPSet().getAP(ap_i) + \"\\\"\");\n\t\t}\n\t\tout.println();\n\n\t\tout.println(\"---\");\n\n\t\tfor (int i_state = 0; i_state < _index.size(); i_state++) {\n\t\t\tDA_State cur_state = _index.get(i_state);\n\t\t\tout.print(\"State: \" + i_state);\n\t\t\tif (cur_state.hasDescription()) {\n\t\t\t\tout.print(\" \\\"\" + cur_state.getDescription() + \"\\\"\");\n\t\t\t}\n\t\t\tout.println();\n\n\t\t\t_acceptance.outputAcceptanceForState(out, i_state);\n\t\t\t\n\t\t\tIterator<APElement> it = _ap_set.elementIterator();\n\t\t\twhile (it.hasNext()) {\n\t\t\t\tAPElement e = it.next();\n\t\t\t\tDA_State to = cur_state.edges().get(e);\n\t\t\t\tout.println(to.getName());\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Print the DA in HOA format to the output stream.\n\t * This functions expects that the DA is compact.\n\t * @param da_type a string specifying the type of automaton (\"DRA\", \"DSA\").\n\t * @param out the output stream\n\t */\n\tpublic void printHOA(String da_type, PrintStream out) throws PrismException {\n\t\tif (!da_type.equals(\"DRA\")) throw new PrismNotSupportedException(\"HOA printing for \"+da_type+\" currently not supported\");\n\n\t\tout.println(\"HOA: v1\");\n\t\tout.println(\"States: \"+size());\n\t\t_ap_set.print_hoa(out);\n\t\tout.println(\"Start: \"+getStartState().getName());\n\t\t_acceptance.outputAcceptanceHeaderHOA(out);\n\t\tout.println(\"properties: trans-labels explicit-labels state-acc no-univ-branch deterministic\");\n\t\tout.println(\"--BODY--\");\n\t\tfor (DA_State state : _index) {\n\t\t\tout.print(\"State: \"+state.getName()+ \" \");  // id\n\t\t\t_acceptance.outputAcceptanceForStateHOA(out, state.getName());\n\n\t\t\tfor (Map.Entry<APElement, DA_State> edge : state.edges().entrySet()) {\n\t\t\t\tAPElement label = edge.getKey();\n\t\t\t\tString labelString = \"[\"+label.toStringHOA(_ap_set.size())+\"]\";\n\t\t\t\tDA_State to = edge.getValue();\n\t\t\t\tout.print(labelString);\n\t\t\t\tout.print(\" \");\n\t\t\t\tout.println(to);\n\t\t\t}\n\t\t}\n\t\tout.println(\"--END--\");\n\t}\n\n\t/**\n\t * Print the DA in dot format to the output stream.\n\t * This functions expects that the DA is compact.\n\t * @param da_type a string specifying the type of automaton (\"DRA\", \"DSA\").\n\t * @param out the output stream \n\t */\n\tpublic void\tprintDot(String da_type, PrintStream out) throws PrismException {\n\t\t// Ensure that this DA is compact...\n\t\tif (!this.isCompact()) {\n\t\t\tthrow new PrismException(\"DA is not compact!\");\n\t\t}\n\n\t\tif (this.getStartState() == null) {\n\t\t\t// No start state! \n\t\t\tthrow new PrismException(\"No start state in DA!\");\n\t\t}\n\n\t\tint start_state = this.getStartState().getName();\n\n\t\tout.println(\"digraph model {\");\n\t\tfor (int i_state = 0; i_state < _index.size(); i_state++) {\n\t\t\tif(i_state == start_state)\n\t\t\t\tout.println(\"\t\" + i_state + \" [label=\\\"\" + i_state + \"\\\", shape=ellipse]\");\n\t\t\telse {\n\t\t\t\tboolean isAcceptance = false;\n\t\t\t\tfor (int ap_i = 0; ap_i < _acceptance.size(); ap_i++) {\n\t\t\t\t\tif(_acceptance.isStateInAcceptance_L(ap_i, i_state)) {\n\t\t\t\t\t\tout.println(\"\t\" + i_state + \" [label=\\\"\" + i_state + \"\\\", shape=doublecircle]\");\n\t\t\t\t\t\tisAcceptance = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t} else if(_acceptance.isStateInAcceptance_U(ap_i, i_state)) {\n\t\t\t\t\t\tout.println(\"\t\" + i_state + \" [label=\\\"\" + i_state + \"\\\", shape=box]\");\n\t\t\t\t\t\tisAcceptance = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif(!isAcceptance)\n\t\t\t\t\tout.println(\"\t\" + i_state + \" [label=\\\"\" + i_state + \"\\\", shape=circle]\");\n\t\t\t}\n\t\t}\n\t\tfor (int i_state = 0; i_state < _index.size(); i_state++) {\n\t\t\tDA_State cur_state = _index.get(i_state);\n\t\t\tfor (Map.Entry<APElement, DA_State> transition : cur_state.edges().entrySet()) {\n\t\t\t\tout.println(\"\t\" + i_state + \" -> \" + transition.getValue().getName() + \n\t\t\t\t\t\t\" [label=\\\"\" + transition.getKey().toString(_ap_set, true) + \"\\\"]\");\n\t\t\t}\n\t\t}\n\t\tout.println(\"}\");\n\t\t\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/DAUnionAlgorithm.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport prism.PrismException;\n\n/** @file\n * Provides DAUnionAlgorithm for calculating the union of two DA.\n */\n\n/**\n * An algorithm calculating the union of two DA. Requires the existance of a UnionAcceptanceCalculator for the\n * AcceptanceCondition.\n * @param DA_t the Deterministic Automaton class.\n */\n\npublic class DAUnionAlgorithm {\n\n\t/** The first DA */\n\tprivate DRA _da_1;\n\t/** The second DA */\n\tprivate DRA _da_2;\n\t/** The result DA */\n\tprivate DRA _result_da;\n\n\t/** The acceptance calculator */\n\tprivate UnionAcceptanceCalculator _acceptance_calculator;\n\n\t/** Perform trueloop check? */\n\t// private boolean _trueloop_check;\t\n\t/** Generate detailed descriptions? */\n\tprivate boolean _detailed_states;\n\n\n\t/** Constructor. \n\t * @param da_1 The first DA\n\t * @param da_2 the second DA\n\t * @param trueloop_check Check for trueloops?\n\t * @param detailed_states Generate detailed descriptions of the states? */\n\tpublic DAUnionAlgorithm(DRA da_1, DRA da_2, boolean trueloop_check, boolean detailed_states) throws PrismException {\n\t\t_da_1 = da_1;\n\t\t_da_2 = da_2;\n\t\t// _trueloop_check = trueloop_check;\n\t\t_detailed_states = detailed_states;\n\t\t_acceptance_calculator = new UnionAcceptanceCalculator(da_1.acceptance(), da_2.acceptance());\n\n\t\tif (! (_da_1.getAPSet() == _da_2.getAPSet()) ) {\n\t\t\tthrow new PrismException(\"Can't create union of DAs: APSets don't match\");\n\t\t}\n\n\t\tAPSet combined_ap = da_1.getAPSet();\n\n\t\tif (! _da_1.isCompact() || ! _da_2.isCompact()) {\n\t\t\tthrow new PrismException(\"Can't create union of DAs: Not compact\");\n\t\t}\n\t\t\n\t\t_result_da = new DRA(combined_ap);\n\t}\n\n\t/** Get the resulting DA \n\t * @return a shared_ptr to the resulting union DA.\n\t */\n\tDRA getResultDA() {\n\t\treturn _result_da;\n\t}\n\n\t/** Calculate the successor state.\n\t * @param from_state The from state\n\t * @param elem The edge label \n\t * @return result_t the shared_ptr of the successor state\n\t */\n\tpublic UnionState.Result delta(UnionState from_state, APElement elem) throws PrismException {\n\t\tDA_State state1_to = _da_1.get(from_state.da_state_1).edges().get(elem);\n\t\tDA_State state2_to = _da_2.get(from_state.da_state_2).edges().get(elem);\n\n\t\tUnionState to = createState(state1_to.getName(), state2_to.getName());\n\t\treturn new UnionState.Result(to);\n\t}\n\n\n\t/** Get the start state.\n\t * @return a shared_ptr to the start state \n\t */\n\tpublic UnionState getStartState() throws PrismException {\n\t\tif (_da_1.getStartState() == null || _da_2.getStartState() == null) {\n\t\t\tthrow new PrismException(\"DA has no start state!\");\n\t\t}\n\n\t\treturn createState(_da_1.getStartState().getName(), _da_2.getStartState().getName());\n\t}\n\n\t/** Prepare the acceptance condition \n\t * @param acceptance the acceptance condition in the result DA\n\t */\n\tpublic void prepareAcceptance(RabinAcceptance acceptance) {\n\t\t_acceptance_calculator.prepareAcceptance(acceptance);\n\t}\n\n\t/** Check if the automaton is a-priori empty */\n\tpublic boolean checkEmpty() {\n\t\treturn false;\n\t}\n\n\t/** Calculate the union of two DA. If the DAs are not compact, they are made compact.\n\t * @param da_1 The first DA\n\t * @param da_2 the second DA\n\t * @param trueloop_check Check for trueloops?\n\t * @param detailed_states Generate detailed descriptions of the states?\n\t * @return shared_ptr to result DA\n\t */\n\tpublic static DRA calculateUnion(DRA da_1, DRA da_2, boolean trueloop_check, boolean detailed_states) throws PrismException {\n\t\tif (!da_1.isCompact()) {\n\t\t\tda_1.makeCompact();\n\t\t}\n\n\t\tif (!da_2.isCompact()) {\n\t\t\tda_2.makeCompact();\n\t\t}\n\n\t\tDAUnionAlgorithm dua = new DAUnionAlgorithm(da_1, da_2, trueloop_check, detailed_states);\n\t\tUnionNBA2DRA generator = new UnionNBA2DRA(detailed_states);\n\t\tgenerator.convert(dua, dua.getResultDA(), 0, new StateMapper<UnionState.Result,UnionState,DA_State>());\n\n\t\treturn dua.getResultDA();\n\t}\n\n\n\t/** Calculate the union of two DA, using stuttering if possible. If the DAs are not compact, they are made compact.\n\t * @param da_1 The first DA\n\t * @param da_2 the second DA\n\t * @param stutter_information information about the symbols where stuttering is allowed\n\t * @param trueloop_check Check for trueloops?\n\t * @param detailed_states Generate detailed descriptions of the states? */\n/*\tpublic DRA calculateUnionStuttered(DRA da_1, DRA da_2, \n\t\t\tStutterSensitivenessInformation stutter_information,\n\t\t\tboolean trueloop_check, boolean detailed_states) {\n\t\tif (!da_1.isCompact()) {\n\t\t\tda_1.makeCompact();\n\t\t}\n\n\t\tif (!da_2.isCompact()) {\n\t\t\tda_2.makeCompact();\n\t\t}\n\n\t\tDAUnionAlgorithm dua(da_1, da_2, trueloop_check, detailed_states);\n\n\t\tStutteredNBA2DA<DAUnionAlgorithm, DA_t> generator(detailed_states, stutter_information);\n\t\tgenerator.convert(dua, dua.getResultDA(), 0);\n\n\t\treturn dua.getResultDA();\n\t}\n*/\t\n\t\t/** Create a UnionState \n\t\t * @param da_state_1\n\t\t * @param da_state_2\n\t\t * @return the corresponding UnionState\n\t\t */\n\tprivate UnionState createState(int da_state_1, int da_state_2) {\n\t\t\n\t\tUnionState state = new UnionState(da_state_1, da_state_2, _acceptance_calculator);\n\n\t\t// Generate detailed description\n\t\tif (_detailed_states) {\n\t\t\tString s;\n\n\t\t\ts = \"<TABLE BORDER=\\\"1\\\" CELLBORDER=\\\"0\\\"><TR><TD>\";\n\n\t\t\tif (_da_1.get(da_state_1).hasDescription()) {\n\t\t\t\ts += _da_1.get(da_state_1).getDescription();\n\t\t\t} else {\n\t\t\t\ts += da_state_1;\n\t\t\t}\n\n\t\t\ts += \"</TD><TD>U</TD><TD>\";\n\n\t\t\tif (_da_2.get(da_state_2).hasDescription()) {\n\t\t\t\ts += _da_2.get(da_state_2).getDescription();\n\t\t\t} else {\n\t\t\t\ts += da_state_2;\n\t\t\t}\n\n\t\t\ts += \"</TD></TR></TABLE>\";\n\n\t\t\tstate.setDescription(s);\n\t\t}\n\t\treturn state;\n\t}\n}\n\n//TODO: trueloop again\n\n"
  },
  {
    "path": "prism/src/jltl2dstar/DA_State.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.HashMap;\n\nimport jltl2ba.APElement;\n\n/**\n * A state of a deterministic omega-automaton.\n * For a description of the template parameters, see class DA.\n */\n\t\npublic class DA_State {\n\n\t/** The automaton of which this state is a part. */\n\tprivate\tDA _graph;\n\t\n\tprivate int _name; \n\n\t/** The edges */\n\tprivate HashMap<APElement, DA_State> _edges;\n\n\t/** A description */\n\tprivate String _description;\n\n\t/** \n\t * Constructor.\n\t * @param graph The automaton (DA) that contains this state.\n\t */\n\tpublic DA_State(DA graph)\n\t{\n\t\t_graph = graph;\n\t\t_edges = new HashMap<APElement, DA_State>();\n\t\t_description = \"\";\n\t}\n  \n\t/** Get the EdgeContainer to access the edges. */\n\tpublic HashMap<APElement, DA_State> edges()\n\t{\n\t\treturn _edges;\n\t}\n  \n\t/** Get the name (index) of this state. */\n\tpublic int getName() \n\t{\n\t\t// return _graph.getIndexForState(this);\n\t\treturn _name;\n\t}\n\n\t/** Set the name (index) of this state. */\n\tpublic void setName(int name) \n\t{\n\t\t// return _graph.getIndexForState(this);\n\t\t_name = name;\n\t}\n\n\t/** Print the name of the state on an output stream. */\n\tpublic String toString() \n\t{\n\t\treturn Integer.toString(getName());\n\t}\n \n\t/** Set an description for the state */\n\tpublic void setDescription(String s) \n\t{\n\t\t_description = s;\n\t}\n\n\t/**\n\t * Get an description for the state (previously set using setDescription()).\n\t * Should only be called after verifying that the state hasDescription()\n\t * @return a const string ref to the description\n\t */\n\tpublic String getDescription() \n\t{\n\t\treturn _description;\n\t}\n\n\t/**\n\t * Check whether the state has a description.\n\t */\n\tpublic boolean hasDescription() \n\t{\n\t\treturn _description != \"\";\n\t}\n\n\t/**\n\t * Checks if all transitions originating in this state\n\t * leed back to itself. \n\t */\n\tpublic boolean hasOnlySelfLoop() \n\t{\n\t\tfor (DA_State dest : edges().values())\n\t\t{\n\t\t\tif (dest != this) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/** Get the AcceptanceForState access functor for this state */\n\tpublic AcceptanceForState acceptance() {\n\t\tAcceptanceForState acc = new AcceptanceForState(_graph.acceptance(), this.getName());\n\t\treturn acc;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/DBA2DRA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport prism.PrismException;\nimport java.util.Iterator;\nimport java.util.BitSet;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\n\n/** @file \n * Provides class DBA2DRA, which can convert a \n * deterministic Büchi automaton to a deterministic Rabin\n * automaton.\n */\n\n/**\n * Provides conversion from deterministic Büchi to \n * deterministic Rabin.\n */\npublic class DBA2DRA {\n\t/**\n\t * Convert a deterministic Büchi automaton\n\t * (a nondeterministic Büchi automaton NBA, where every transition\n\t * has at most one target state) to an equivalent deterministic \n\t * Rabin automaton.\n\t * <p>\n\t * This involves generation of the appropriate acceptance condition\n\t * and making sure that the transition function is complete.\n\t * </p>\n\t * <p>\n\t * The DBA can also be complemented on the fly \n\t * (by modifying the acceptance condition of the DRA). The resulting DRA can then be\n\t * regarded as a Streett automaton of the original DBA.\n\t * @param nba the NBA, the transitions have to be deterministic!\n\t * @param complement complement the DBA?\n\t * @return a shared_ptr to the created DRA\n\t */\n\tpublic static DRA dba2dra(NBA nba, boolean complement) throws PrismException {\n\t\tAPSet ap_set = nba.getAPSet();\n\t\tDRA dra = new DRA(ap_set);\n\n\t\tdra.acceptance().newAcceptancePair();\n\n\t\tfor (int i = 0; i < nba.size(); i++) {\n\t\t\tdra.newState();\n\n\t\t\tif (complement) {\n\t\t\t\t// Final states -> U_0, all states -> L_0\n\t\t\t\tif (nba.get(i).isFinal()) {\n\t\t\t\t\tdra.acceptance().stateIn_U(0, i, true);\n\t\t\t\t}\n\t\t\t\tdra.acceptance().stateIn_L(0, i, true);\n\t\t\t} else {\n\t\t\t\t// Final states -> L_0, U_0 is empty\n\t\t\t\tif (nba.get(i).isFinal()) {\n\t\t\t\t\tdra.acceptance().stateIn_L(0, i, true);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (nba.getStartState() != null) {\n\t\t\tdra.setStartState(dra.get(nba.getStartState().getName()));\n\t\t}\n\n\t\tDA_State sink_state = null;\n\n\t\tfor (int i = 0; i < nba.size();\ti++) {\n\t\t\tNBA_State nba_state = nba.get(i);\n\t\t\tDA_State dra_from = dra.get(i);\n\n\t\t\tfor (Iterator<APElement> it = ap_set.elementIterator(); it.hasNext(); ) {\n\t\t\t\tAPElement label = it.next(); \n\t\t\t\tBitSet to = nba_state.getEdge(label);\n\n\t\t\t\tint to_cardinality = 0;\n\t\t\t\tif (to != null) {\n\t\t\t\t\tto_cardinality = to.cardinality();\n\t\t\t\t}\n\n\t\t\t\tDA_State dra_to = null;\n\t\t\t\tif (to == null || to_cardinality == 0) {\n\t\t\t\t\t// empty to -> go to sink state\n\t\t\t\t\tif (sink_state == null) {\n\t\t\t\t\t\t// we have to create the sink\n\t\t\t\t\t\tsink_state = dra.newState();\n\n\t\t\t\t\t\t// if we complement, we have to add the sink to\n\t\t\t\t\t\t// L_0 \n\t\t\t\t\t\tif (complement) {\n\t\t\t\t\t\t\tsink_state.acceptance().addTo_L(0);\n\t\t\t\t\t\t}\t    \n\t\t\t\t\t}\n\t\t\t\t\tdra_to = sink_state;\n\t\t\t\t} else if (to_cardinality == 1) {\n\t\t\t\t\tint to_index = to.nextSetBit(0);\n\n\t\t\t\t\t//\t  std::cerr << \"to: \" << to_index << std::endl;\n\n\t\t\t\t\tdra_to = dra.get(to_index);\n\t\t\t\t} else {\n\t\t\t\t\t// to_cardinality>1 !\n\t\t\t\t\tthrow new PrismException(\"NBA is no DBA!\");\n\t\t\t\t}\n\n\t\t\t\tdra_from.edges().put(label, dra_to);\n\t\t\t}\n\t\t}\n\n\t\tif (sink_state != null) {\n\t\t\t// there is a sink state\n\t\t\t// make true-loop from sink state to itself\n\t\t\tfor (Iterator<APElement> it = ap_set.elementIterator(); it.hasNext(); ) {\n\t\t\t\tsink_state.edges().put(it.next(), sink_state);\n\t\t\t}\n\t\t}\n\t\treturn dra;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/DRA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n * Copyright (c) 2011- David Parker, Hongyang Qu\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.io.FileNotFoundException;\nimport java.io.FileWriter;\nimport java.io.PrintStream;\nimport java.util.*;\n\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceStreett;\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport prism.PrismException;\n\n/**\n * A class representing a deterministic Rabin automaton.\n * <p>\n * For details on the template parameters, see class DA.\n * </p>\n * The DRA can be considered as a Streett automaton, if\n * a flag is set.\n */\npublic class DRA extends DA {\n\n\t/** Marker, is this DRA considered as a Streett automaton? */\n\tprivate boolean _isStreett;\n\n\t/**\n\t * Constructor.\n\t * @param ap_set the underlying APSet\n\t */\n\tpublic DRA(APSet ap_set) {\n\t\tsuper(ap_set);\n\t\t_isStreett = false;\n\t}\n\t\n\tpublic static DRA newInstance(APSet ap_set) {\n\t\treturn new DRA(ap_set);\n\t}\n\n\tprivate String typeID() {\n\t\tif (isStreett()) {\n\t\t\treturn \"DSA\";\n\t\t} else {\n\t\t\treturn \"DRA\";\n\t\t}\n\t}\n\n\t/** Is this DRA considered as a Streett automaton? */\n\tpublic boolean isStreett()\n\t{\n\t\treturn _isStreett;\n\t}\n\n\t/** Consider this DRA as a Streett automaton. */\n\tpublic void considerAsStreett(boolean flag)\n\t{\n\t\t_isStreett=flag;\n\t}\n\n\n\t/**\n\t * Print the DRA/DSA in v2 format to the output stream.\n\t * This function can compact the automaton, which may invalidate iterators!\n\t */\n\tpublic void print(PrintStream out) throws PrismException {\n\t\tif (!this.isCompact()) {\n\t\t\tthis.makeCompact();\n\t\t}\n\n\t\tthis.print(typeID(), out);\n\t}\n\t\n\t/**\n\t * Print the DRA/DSA in dot format to the output stream.\n\t * This function can compact the automaton, which may invalidate iterators!\n\t */\n\tpublic void printDot(PrintStream out) throws PrismException {\n\t\tif (!this.isCompact()) {\n\t\t\tthis.makeCompact();\n\t\t}\n\n\t\tthis.printDot(typeID(), out);\n\t}\n\n\t/**\n\t * Print the DRA/DSA in DOT format to the output stream.\n\t * This function can compact the automaton, which may invalidate iterators!\n\t */\n\t// void print_dot(std::ostream& out)\n\t\n\t/**\n\t * Optimizes the acceptance condition.\n\t * This function may delete acceptance pairs,\n\t * which can invalidate iterators.\n\t */\n\tpublic void optimizeAcceptanceCondition() throws PrismException {\n\t\t\n\t\tfor (Iterator<Integer> it = this.acceptance().iterator(); it.hasNext(); ) {\n\t\t\tInteger id = it.next();\n\n\t\t\tif (this.acceptance().getAcceptance_L(id) == null)\n\t\t\t\tcontinue;\n\n\t\t\t// L = L \\ U\n\t\t\tif (this.acceptance().getAcceptance_L(id).intersects(this.acceptance().getAcceptance_U(id))) {\n\t\t\t\tthis.acceptance().getAcceptance_L(id).andNot(this.acceptance().getAcceptance_U(id));\n\t\t\t}\n\n\t\t\t// remove if L is empty\n\t\t\tif (this.acceptance().getAcceptance_L(id).isEmpty()) {\n\t\t\t\t// no state is in L(id) -> remove\n\t\t\t\tthis.acceptance().removeAcceptancePair(id);\n\t\t\t}\n\t\t}\n\t}\n\n\n\tpublic DRA calculateUnion(DRA other, boolean trueloop_check, boolean detailed_states) throws PrismException {\n\t\tif (this.isStreett() || other.isStreett()) {\n\t\t\tthrow new PrismException(\"Can not calculate union for Streett automata\");\n\t\t}\n\n\t\treturn DAUnionAlgorithm.calculateUnion(this, other, trueloop_check, detailed_states);\n\t}\n\n\t/**\n\t * Convert this jltl2dstar deterministic automaton to PRISM data structures.\n\t */\n\tpublic automata.DA<BitSet,? extends AcceptanceOmega> createPrismDA() throws PrismException\n\t{\n\t\tint numStates = size();\n\t\tif (!isStreett()) {\n\t\t\t// Rabin\n\t\t\tautomata.DA<BitSet, AcceptanceRabin> draNew;\n\n\t\t\tdraNew = new automata.DA<BitSet, AcceptanceRabin>(numStates);\n\t\t\tcreatePrismDA(draNew);\n\t\t\tAcceptanceRabin accNew = createRabinAcceptance();\n\t\t\tdraNew.setAcceptance(accNew);\n\n\t\t\treturn draNew;\n\t\t} else {\n\t\t\t// Streett\n\t\t\tautomata.DA<BitSet, AcceptanceStreett> dsaNew;\n\n\t\t\tdsaNew = new automata.DA<BitSet, AcceptanceStreett>(numStates);\n\t\t\tcreatePrismDA(dsaNew);\n\t\t\tAcceptanceStreett accNew = createStreettAcceptance();\n\t\t\tdsaNew.setAcceptance(accNew);\n\n\t\t\treturn dsaNew;\n\t\t}\n\t}\n\n\t/**\n\t * Convert the state and transition structure of this jltl2dstar deterministic automaton\n\t * to the PRISM data structures.\n\t */\n\tprivate void createPrismDA(automata.DA<BitSet, ?> da) throws PrismException\n\t{\n\t\tint i, k, numLabels, numStates, src, dest;\n\t\tList<String> apList;\n\t\tBitSet bitset;\n\t\t\n\t\tnumLabels = getAPSize();\n\t\tnumStates = size();\n\t\t// Copy AP set\n\t\tapList = new ArrayList<String>(numLabels);\n\t\tfor (i = 0; i < numLabels; i++) {\n\t\t\tapList.add(getAPSet().getAP(i));\n\t\t}\n\t\tda.setAPList(apList);\n\t\t// Copy start state\n\t\tda.setStartState(getStartState().getName());\n\t\t// Copy edges\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tDA_State cur_state = get(i);\n\t\t\tsrc = cur_state.getName();\n\t\t\tfor (Map.Entry<APElement, DA_State> transition : cur_state.edges().entrySet()) {\n\t\t\t\tdest = transition.getValue().getName();\n\t\t\t\tbitset = new BitSet();\n\t\t\t\tfor (k = 0; k < numLabels; k++) {\n\t\t\t\t\tbitset.set(k, transition.getKey().get(k));\n\t\t\t\t}\n\t\t\t\tda.addEdge(src, bitset, dest);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Create an AcceptanceRabin acceptance condition from the acceptance condition\n\t * of this jltl2dstar deterministic automaton.\n\t */\n\tprivate AcceptanceRabin createRabinAcceptance() throws PrismException {\n\t\tAcceptanceRabin accNew = new AcceptanceRabin();\n\n\t\t// Copy acceptance pairs\n\t\tRabinAcceptance acc = acceptance();\n\t\tfor (int i = 0; i < acc.size(); i++) {\n\t\t\t// Note: Pairs (U_i,L_i) become (L_i,K_i) in PRISM's notation\n\t\t\tBitSet newL = (BitSet)acc.getAcceptance_U(i).clone();\n\t\t\tBitSet newK = (BitSet)acc.getAcceptance_L(i).clone();\n\t\t\tAcceptanceRabin.RabinPair pair = new AcceptanceRabin.RabinPair(newL, newK);\n\t\t\taccNew.add(pair);\n\t\t}\n\t\treturn accNew;\n\t}\n\n\t/**\n\t * Create an AcceptanceStreett acceptance condition from the acceptance condition\n\t * of this jltl2dstar deterministic automaton.\n\t */\n\tprivate AcceptanceStreett createStreettAcceptance() throws PrismException {\n\t\tAcceptanceStreett accNew = new AcceptanceStreett();\n\t\t\n\t\t// Copy acceptance pairs, interpreting the RabinAcceptance from this automaton\n\t\t// as Streett acceptance\n\t\tRabinAcceptance acc = acceptance();\n\t\tfor (int i = 0; i < acc.size(); i++) {\n\t\t\t// Note: Pairs (U_i,L_i) become (G_i,R_i) in PRISM's notation\n\t\t\tBitSet newR = (BitSet)acc.getAcceptance_L(i).clone();\n\t\t\tBitSet newG = (BitSet)acc.getAcceptance_U(i).clone();\n\t\t\tAcceptanceStreett.StreettPair pair = new AcceptanceStreett.StreettPair(newR, newG);\n\n\t\t\taccNew.add(pair);\n\t\t}\n\t\treturn accNew;\n\t}\n\n\t\n\t//\tpublic DRA calculateUnionStuttered(DRA other,\n\t//\t\t\tStutterSensitivenessInformation stutter_information,\n\t//\t\t\tboolean trueloop_check,\n\t//\t\t\tboolean detailed_states) {\n\t//\t\tif (this.isStreett() ||\tother.isStreett()) {\n\t//\t\t\tthrow new PrismException(\"Can not calculate union for Streett automata\");\n\t//\t\t}\n\t//\n\t//\t\treturn DAUnionAlgorithm<DRA>.calculateUnionStuttered(this, other, stutter_information, trueloop_check, detailed_states);\n\t//\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/DRAOptimizations.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** @file\n * Provides optimizations on complete DRAs, notably quotienting using bisimulation.\n */\nimport java.util.*;\nimport java.io.PrintStream;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APElementIterator;\nimport jltl2ba.MyBitSet;\nimport prism.PrismException;\n\n/**\n * Provides optimizations on complete DRAs, notably quotienting using bisimulation.\n */\npublic class DRAOptimizations {\n\n\t/** type of a color */\n\t// typedef unsigned int color_t;\n\t/** type of vector state indizes */\n\t// typedef std::vector<unsigned int> state_vector;\n\n\t/** Helper class, storing a coloring of the states */\n\tpublic static class Coloring {\n\n\t\t/** The number of colors */\n\t\tprivate int _nr_of_colors;\n\n\t\t/** mapping state_id -> color */\n\t\tprivate Vector<Integer> _coloring;\n\n\t\t/** Keep detailed information of the equivalence classes? */\n\t\tprivate boolean _detailed;\n\n\t\t/** \n\t\t * mapping from color \n\t\t * -> the state ids which are colored alike\n\t\t * only used when _detailed=true */\n\t\tprivate Vector<MyBitSet> _color2states;\n\n\t\t/** \n\t\t * mapping from color -> one representative state\n\t\t */\n\t\tprivate Vector<Integer> _color2state;\n\n\t\t/** \n\t\t * Constructor, get initial size of the coloring from DRA.\n\t\t * @param dra the DRA\n\t\t * @param detailed Keep detailed information on the equivalence classes? (default: false)\n\t\t */\n\t\tpublic Coloring(DRA dra, boolean detailed) {\n\t\t\t_nr_of_colors = 0;\n\t\t\t_detailed = detailed; \n\t\t\t_coloring = new Vector<Integer>(dra.size());\n\t\t\t_coloring.setSize(dra.size());\n\t\t\t_color2state = new Vector<Integer>();\n\t\t\tif (_detailed) {\n\t\t\t\t_color2states = new Vector<MyBitSet>();\n\t\t\t} else {\n\t\t\t\t_color2states = null;\n\t\t\t}\n\t\t}\n\n\t\t/** \n\t\t * Constructor, explicitly set initial size of the coloring\n\t\t * @param size the initial size\n\t\t * @param detailed Keep detailed information on the equivalence classes? (default: false)\n\t\t */\n\t\tpublic Coloring(int size, boolean detailed) {\n\t\t\t_nr_of_colors = 0;\n\t\t\t_detailed = detailed;\n\t\t\t_coloring = new Vector<Integer>(size);\n\t\t\t_coloring.setSize(size);\n\t\t\t_color2state = new Vector<Integer>();\n\n\t\t\tif (_detailed) {\n\t\t\t\t_color2states = new Vector<MyBitSet>();\n\t\t\t} else {\n\t\t\t\t_color2states = null;\n\t\t\t}\n\t\t}\n\n\t\t/** Reset (clear) coloring. */\n\t\tpublic void reset() {_nr_of_colors = 0;}\n\n\t\t/** Get the flag 'detailed' */\n\t\tpublic boolean getFlagDetailed() {return _detailed;}\n\n\t\t/** Returns the size (number of states) of this coloring. */\n\t\tpublic int size() {return _coloring.size();}\n\n\t\t/** \n\t\t * Create a new color\n\t\t * @return the newly created color\n\t\t */\n\t\tpublic int newColor() {\n\t\t\t_nr_of_colors++;\n\n\t\t\t_color2state.setSize(_nr_of_colors);\n\n\t\t\tif (_detailed) {\n\t\t\t\t_color2states.setSize(_nr_of_colors);\n\t\t\t\t_color2states.set(_nr_of_colors - 1, new MyBitSet());\n\t\t\t}\n\n\t\t\treturn _nr_of_colors - 1;\n\t\t}\n\n\t\t/** Return the current (last created) color */\n\t\tpublic int currentColor() {\n\t\t\tassert(_nr_of_colors > 0);\n\t\t\treturn _nr_of_colors - 1;\n\t\t}\n\n\t\t/** Return the number of colors */\n\t\tpublic int countColors() {\n\t\t\treturn _nr_of_colors;\n\t\t}\n\n\t\t/** Set the color of a state */\n\t\tpublic void setColor(int state, int color) {\n\t\t\tassert(color < _nr_of_colors);\n\n\t\t\t_coloring.set(state, Integer.valueOf(color));\n\t\t\t_color2state.set(color, Integer.valueOf(state));\n\n\t\t\tif (_detailed) {\n\t\t\t\t_color2states.get(color).set(state);\n\t\t\t}\n\t\t}\n\n\t\t/** Get the color for a state */\n\t\tpublic int state2color(int state) {\n\t\t\treturn _coloring.get(state);\n\t\t}\n\n\t\t/**\n\t\t *Get one representative state for the equivalence class with the \n\t\t * specified color. \n\t\t */\n\t\tpublic int color2state(int color) {\n\t\t\tassert(color < _nr_of_colors);\n\t\t\treturn _color2state.get(color);\n\t\t}\n\n\t\t/** \n\t\t * Get the state indizes (in a BitSet) that have the specified color. \n\t\t * Can only be called, when the 'detailed' flag is activated in the\n\t\t * constructor.\n\t\t */\n\t\tpublic MyBitSet color2states(int color) {\n\t\t\tassert(color < _nr_of_colors);\n\t\t\tassert(_detailed && _color2states != null);\n\t\t\treturn _color2states.get(color);\n\t\t}\n\n\t\t/** Print the coloring */\n\t\tpublic void print(PrintStream out) {\n\t\t\tfor (int i = 0; i < this.size(); i++) {\n\t\t\t\tout.println(\"color[\" + i + \"] = \" + this.state2color(i));\n\t\t\t}\n\t\t}\n\t}\n\n\t/** \n\t * Functor, provides a 'less-than' Comparator \n\t * for the states of the DRA, using the color of \n\t * the states themself and the colors of the\n\t * to-states of the edges.\n\t */\n\tpublic static class ColoredStateComparator implements Comparator<Integer> {\n\n\t\t/** The coloring */\n\t\tprivate Coloring _coloring;\n\t\t/** The DRA */\n\t\tprivate DRA _dra;\n\n\t\t/** Constructor */\n\t\tpublic ColoredStateComparator(Coloring coloring, DRA dra) {\n\t\t\t_coloring = coloring;\n\t\t\t_dra = dra;\n\t\t}\n\t\t\n\t\t/**\n\t\t * Compares two states 'less-than' using the\n\t\t * coloring, uses the bisimulation\n\t\t * equivalence relation to determine\n\t\t * equality.\n\t\t */\n\t\tpublic int compare(Integer state_x, Integer state_y) {\n\t\t\tint cx = _coloring.state2color(state_x);\n\t\t\tint cy = _coloring.state2color(state_y);\n\n\t\t\tif (cx < cy) {\n\t\t\t\treturn -1;\n\t\t\t} else if (cx > cy) {\n\t\t\t\treturn 1;\n\t\t\t}\n\n\t\t\tfor (APElementIterator it = new APElementIterator(_dra.getAPSize()); it.hasNext(); ) {\n\t\t\t\tAPElement label = it.next();\n\t\t\t\tDA_State to_x =\t_dra.get(state_x).edges().get(label);\n\t\t\t\tDA_State to_y =\t_dra.get(state_y).edges().get(label);\n\n\t\t\t\tint ctx = _coloring.state2color(to_x.getName());\n\t\t\t\tint cty = _coloring.state2color(to_y.getName());\n\n\t\t\t\tif (ctx < cty) {\n\t\t\t\t\treturn -1;\n\t\t\t\t} else if (ctx > cty) {\n\t\t\t\t\treturn 1;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// we get here only if x and y are equal with this\n\t\t\t// coloring -> return false\n\t\t\treturn 0;\n\t\t}\n\t}\n\n\t/** Type of an acceptance signature */\n\t// public typedef std::pair<BitSet*, BitSet*> acceptance_signature_t;\n\tpublic static class AcceptanceSignature {\n\t\tpublic MyBitSet l;\n\t\tpublic MyBitSet u;\n\t\t\n\t\tpublic AcceptanceSignature() {;}\n\t}\n\t\n\t/** \n\t * A container that stores (caches) the acceptance signatures of\n\t * all the states in a DRA.\n\t */\n\tpublic static class AcceptanceSignatureContainer {\n\t\t\n\t\t/** Storage for the acceptance signatures */\n\t\tprivate Vector<AcceptanceSignature> _acceptancesig_vector;\n\n\t\t/** \n\t\t * Constructor, fills the container with the acceptance signatures of the states.\n\t\t * @param dra the DRA\n\t\t */\n\t\tpublic AcceptanceSignatureContainer(DRA dra) {\n\t\t\t_acceptancesig_vector = new Vector<AcceptanceSignature>(dra.size());\n\n\t\t\tfor (int i = 0; i < dra.size();\ti++) {\n\t\t\t\t_acceptancesig_vector.add(new AcceptanceSignature());\n\t\t\t\t_acceptancesig_vector.get(i).l = (MyBitSet) dra.acceptance().getAcceptance_L_forState(i).clone();\n\t\t\t\t_acceptancesig_vector.get(i).u = (MyBitSet) dra.acceptance().getAcceptance_U_forState(i).clone();\n\t\t\t}\n\t\t}\n\n\t\t/** \n\t\t * Get the acceptance signature for state i.\n\t\t * @param i the state index\n\t\t */\n\t\tpublic AcceptanceSignature get(int i) {\n\t\t\treturn _acceptancesig_vector.get(i);\n\t\t}\n\t}\n\n\t/** \n\t * Functor that compares two DRA states based on their\n\t * acceptance signature.\n\t */\n\tpublic static class AcceptanceSignatureComparator implements Comparator<Integer> {\n\t\t/** The acceptance signature container */\n\t\tprivate AcceptanceSignatureContainer _container;\n\n\t\t/** Constructor */\n\t\tpublic AcceptanceSignatureComparator(AcceptanceSignatureContainer container) {\n\t\t\t_container = container;\n\t\t}\n\n\t\t/** \n\t\t * Compares (less-than) two DRAState indizes based on their\n\t\t * acceptance signature.\n\t\t */\n\t\tpublic int compare(Integer x, Integer y) {\n\t\t\tAcceptanceSignature px = _container.get(x);\n\t\t\tAcceptanceSignature py = _container.get(y);\n\n\t\t\treturn (px.l.compareTo(py.l) == 0 ? px.u.compareTo(py.u) : px.l.compareTo(py.l));\n\t\t}\n\t\t\n\t\tpublic boolean equals(Integer x, Integer y) {\n\t\t\treturn compare(x,y) == 0;\n\t\t}\n\t}\n\n\n\t/** \n\t * Perform quotienting using bisimulation\n\t * @param dra the DRA to be optimized\n\t * @param printColoring print colorings on std::cerr? (default: false)\n\t * @param detailedStates save detailed information on the interals in the state? (default: false)\n\t * @param printStats print statistics on std::cerr? (default: false)\n\t * @return shared_ptr to the quotiented DRA\n\t */\n\tpublic DRA optimizeBisimulation(DRA dra, boolean printColoring, boolean detailedStates, boolean printStats) throws PrismException {\n\t\tif (!dra.isCompact()) \n\t\t\tdra.makeCompact();\n\n\t\tVector<Integer> states = new Vector<Integer>(dra.size());\n\t\tstates.setSize(dra.size());\n\n\t\tfor (int i = 0; i < dra.size(); i++) {\n\t\t\tstates.set(i, Integer.valueOf(i));\n\t\t}\n\n\t\tAcceptanceSignatureContainer accsig_container = new AcceptanceSignatureContainer(dra);\n\t\tAcceptanceSignatureComparator accsig_comp = new AcceptanceSignatureComparator(accsig_container);\n\n\n\t\tColoring tmpcoloring = new Coloring(dra, detailedStates);\n\t\t// generate initial coloring by running with the \n\t\t// different acceptance signature\n\t\tColoring coloring = generateColoring(states, tmpcoloring, accsig_comp);\n\n\t\tint old_size = dra.size();\n\t\tint initial_partition = coloring.countColors();\n\n\t\tint oldColors;\n\t\tdo {\n\t\t\toldColors = coloring.countColors();\n\n\t\t\tColoredStateComparator cnc = new ColoredStateComparator(coloring, dra);      \n\n\t\t\ttmpcoloring = generateColoring(states, coloring, cnc);\n\t\t\tcoloring = tmpcoloring;      \n\t\t} while (oldColors != coloring.countColors());\n\n\t\tif (printColoring) {\n\t\t\tcoloring.print(System.err);\n\t\t}\n\n\t\tDRA dra_new = generateDRAfromColoring(dra, coloring, detailedStates);\n\n\t\tint new_size=dra_new.size();\n\n\t\tif (printStats) {\n\t\t\tSystem.err.println(\"Bisimulation: From (\" + old_size + \") To (\" + new_size + \") Initial: (\" + initial_partition + \")\");\n\t\t}\n\t\treturn dra_new;\n\t}\n\n\n\n\t/**\n\t * Generate a new coloring based on the Comparator comp \n\t * (one iteration of refinement)\n\t * @param states A vector of the states\n\t * @param coloring The current coloring\n\t * @param comp the Comparator\n\t * @return a pointer to a newly created Coloring, memory ownership\n\t *         passes to the caller\n\t */\n\tprivate <T extends Comparator<Integer>>Coloring generateColoring(Vector<Integer> states, Coloring coloring, T comp) {\n\t\tInteger[] statearray = (Integer[]) states.toArray(new Integer[0]);\n\t\tArrays.sort(statearray, comp);\n\t\tVector<Integer> sortedstates = new Vector<Integer>(Arrays.asList(statearray)); \n\n\t\tColoring result = new Coloring(coloring.size(), coloring.getFlagDetailed());\n\n\t\tif (sortedstates.size() == 0) {return result;}\n\t\t\n\t\t// reverse iterators\n\t\tListIterator<Integer> current = sortedstates.listIterator(sortedstates.size());\n\t\tListIterator<Integer> last = sortedstates.listIterator(sortedstates.size());\n\t\t\n\t\tresult.setColor(current.previous(), result.newColor());\n\n\t\t// 0 .. n-3 n-2 n-1\n\t\t//                 ^ last\n\t\t//             ^     current\n\t\twhile (current.hasPrevious()) {\n\t\t\tInteger curr = current.previous();\n\t\t\t// because states is sorted and we traverse \n\t\t\t// from the end, either:\n\t\t\t//    *current  < *last with comp(current,last)==true\n\t\t\t// or *current == *last with !comp(current,last)\n\t\t\t\n\t\t\tif (comp.compare(curr, last.previous()) < 0) {\n\t\t\t\t// -> we have to start a new color\n\t\t\t\tresult.setColor(curr, result.newColor());\n\t\t\t} else {\n\t\t\t\t// -> more of the same, we stay with this color\n\t\t\t\tresult.setColor(curr, result.currentColor());\n\t\t\t}\n\t\t}\n\t\treturn result;\n\t}\n\n\n\t/**\n\t * Generate a new DRA from a coloring\n\t */\n\tprivate DRA generateDRAfromColoring(DRA oldDRA, Coloring coloring, boolean detailedStates) throws PrismException {\n\t\tDRA newDRA = new DRA(oldDRA.getAPSet());\n\n\t\tnewDRA.acceptance().newAcceptancePairs(oldDRA.acceptance().size());\n\n\t\tfor (int color = 0;\tcolor < coloring.countColors();\t++color) {\n\t\t\tnewDRA.newState();\n\t\t}\n\n\t\tint old_start_state = oldDRA.getStartState().getName();\n\t\tint start_state_color = coloring.state2color(old_start_state);\n\n\t\tnewDRA.setStartState(newDRA.get(start_state_color));\n\n\t\tfor (int color = 0; color < coloring.countColors();\t++color) {\n\t\t\tDA_State new_state = newDRA.get(color);\n\n\t\t\tint old_state_representative = coloring.color2state(color);\n\n\t\t\tDA_State old_state = oldDRA.get(old_state_representative);\n\n\t\t\tif (detailedStates) {\n\t\t\t\tMyBitSet old_states = coloring.color2states(color);\n\n\t\t\t\t// create new description...\n\t\t\t\tif (old_states.cardinality() == 1) {\n\t\t\t\t\tif (old_state.hasDescription()) {\n\t\t\t\t\t\tnew_state.setDescription(old_state.getDescription());\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tString s = \"<TABLE BORDER=\\\"1\\\" CELLBORDER=\\\"0\\\"><TR><TD>{</TD>\";\n\n\t\t\t\t\tboolean first = true;\n\t\t\t\t\tfor (Integer state : old_states) {\n\t\t\t\t\t\tif (first) {\n\t\t\t\t\t\t\tfirst = false; \n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\ts += \"<TD>,</TD>\";\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\ts += \"<TD>\";\n\t\t\t\t\t\tif (!oldDRA.get(state).hasDescription()) {\n\t\t\t\t\t\t\ts += state;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\ts += oldDRA.get(state).getDescription();\n\t\t\t\t\t\t}\n\t\t\t\t\t\ts += \"</TD>\";\n\t\t\t\t\t}\n\t\t\t\t\ts += \"<TD>}</TD></TR></TABLE>\";\n\n\t\t\t\t\tnew_state.setDescription(s);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Create appropriate acceptance conditions\n\t\t\tint old_state_index = old_state.getName();\n\t\t\tfor (int i = 0; i < oldDRA.acceptance().size();\t++i) {\n\t\t\t\tif (oldDRA.acceptance().isStateInAcceptance_L(i, old_state_index)) {\n\t\t\t\t\tnew_state.acceptance().addTo_L(i);\n\t\t\t\t}\n\n\t\t\t\tif (oldDRA.acceptance().isStateInAcceptance_U(i, old_state_index)) {\n\t\t\t\t\tnew_state.acceptance().addTo_U(i);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tfor (Map.Entry<APElement,DA_State> edge : old_state.edges().entrySet()) {\n\n\t\t\t\tint to_color = coloring.state2color(edge.getValue().getName());\n\n\t\t\t\tnew_state.edges().put(edge.getKey(), newDRA.get(to_color));\n\t\t\t}\n\t\t}\n\n\t\treturn newDRA;\n\t}\n}"
  },
  {
    "path": "prism/src/jltl2dstar/GraphAlgorithms.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.Vector;\nimport java.util.Stack;\nimport java.util.Iterator;\n\nimport jltl2ba.MyBitSet;\n\n/** @file\n * Provides algorithms to be used on graphs (automata), notably the calculation\n * of Strongly Connected Components (SCCs).\n */\n\npublic class GraphAlgorithms {\n\t\n\t/** \n\t * Calculate the SCCs for Graph graph and save in result.\n\t * disjoint default = false \n\t */\n\tpublic static void calculateSCCs(NBA graph, SCCs result, boolean disjoint) {\n\t\tSCC_DFS scc_dfs = new SCC_DFS(graph, result);\n\t\tscc_dfs.calculate(disjoint);\n\t}\n\t\n\tpublic static class SCC_DFS {\n\t\t\n\t\tpublic static class SCC_DFS_Data {\n\t\t\t/** A class for saving DFS state information */\n\t\t\tpublic int dfs_nr;\n\t\t\tpublic int root_index;\n\t\t\tpublic boolean inComponent;\n\t\t}\n\n\t\t/** The graph */\n\t\tprivate NBA _graph;\n\n\t\t/** The SCCs */\n\t\tprivate SCCs _result;\n\n\t\t/** The current DFS number */\n\t\tprivate int current_dfs_nr;\n\n\t\t/** The DFS stack */\n\t\tprivate Stack<Integer> _stack;\n\n\t\t/** The SCC_DFS_Data for every state (state index -> DFS_DATA) */\n\t\tprivate Vector<SCC_DFS_Data> _dfs_data;\n\n\t\t/** The current scc number */\n\t\tprivate int scc_nr;\n\n\t\t/** Constructor */\n\t\tpublic SCC_DFS(NBA graph, SCCs result) {\n\t\t\t_graph = graph;\n\t\t\t_result = result;\n\t\t\t_stack = new Stack<Integer>();\n\t\t\t_dfs_data = new Vector<SCC_DFS_Data>();\n\t\t}\n\n\t\t/** Calculate the SCCs*/\n\t\tpublic void calculate(boolean disjoint) {\n\t\t\tcurrent_dfs_nr = 0;\n\t\t\t_dfs_data.clear();\n\t\t\t// Ensure there are as many entries as there are graph-states\n\t\t\t_dfs_data.setSize(_graph.size());\n\t\t\tscc_nr = 0;\n\n\t\t\tNBA_State start_state = _graph.getStartState();\n\t\t\tif (start_state == null) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tint start_idx = start_state.getName();\n\t\t\tvisit(start_idx);\n\t\t\tif (disjoint) {\n\t\t\t\t// The Graph may be disjoint -> restart DFS on every not yet visited state \n\t\t\t\tfor (int v = 0; v < _graph.size(); ++v) {\n\t\t\t\t\tif (_dfs_data.get(v) == null) {\n\t\t\t\t\t\t// not yet visited, i.e., not reachable from the start state\n\t\t\t\t\t\t_result.setGraphIsDisjoint();\n\t\t\t\t\t\tvisit(v);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tcalculateDAG();\n\t\t}\n\n\t\t/** Visit a state (perform DFS) */\n\t\tprivate void visit(int v) {\n\t\t\tSCC_DFS_Data sdd = new SCC_DFS_Data();\n\t\t\tsdd.dfs_nr = current_dfs_nr++;\n\t\t\tsdd.root_index = v;\n\t\t\tsdd.inComponent = false;\n\n\t\t\t_stack.push(v);\n\t\t\t_dfs_data.set(v, sdd);\n\n\t\t\tfor (Iterator<Integer> it = _graph.get(v).successorIterator(); it.hasNext(); ) {\n\t\t\t\tint w = it.next();\n\n\t\t\t\tif (_dfs_data.get(w) == null) {\n\t\t\t\t\t// not yet visited\n\t\t\t\t\tvisit(w);\n\t\t\t\t}\n\n\t\t\t\tSCC_DFS_Data sdd_w = _dfs_data.get(w);\n\t\t\t\tif (sdd_w.inComponent == false) {\n\t\t\t\t\tint dfs_nr_root_v = _dfs_data.get(sdd.root_index).dfs_nr;\n\t\t\t\t\tint dfs_nr_root_w = _dfs_data.get(sdd_w.root_index).dfs_nr;\n\n\t\t\t\t\tif (dfs_nr_root_v > dfs_nr_root_w) {\n\t\t\t\t\t\tsdd.root_index = sdd_w.root_index;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (sdd.root_index == v) {\n\t\t\t\tMyBitSet set = new MyBitSet();\n\n\t\t\t\tint w;\n\t\t\t\tdo {\n\t\t\t\t\tw = _stack.pop();\n\n\t\t\t\t\tset.set(w);\n\t\t\t\t\t_result.setState2SCC(w, scc_nr);\n\n\t\t\t\t\tSCC_DFS_Data sdd_w = _dfs_data.get(w);\n\t\t\t\t\tsdd_w.inComponent=true;\n\t\t\t\t} while (w != v);\n\n\t\t\t\tscc_nr = _result.addSCC(set) + 1;\n\t\t\t}\n\t\t}\n\n\t\t/** Calculate the Directed Acyclical Graph (DAG) */\n\t\tprivate void calculateDAG() {\n\t\t\t_result._dag.clear();\n\t\t\t_result._dag.setSize(_result.countSCCs());\n\t\t\t_result._reachability.setSize(_result.countSCCs());\n\n\t\t\tint[] in_degree = new int[_result.countSCCs()];\n\n\t\t\tfor (int scc = 0; scc < _result.countSCCs(); ++scc) {\n\t\t\t\t// Init\n\t\t\t\t_result._dag.set(scc, new MyBitSet());\n\t\t\t\t_result._reachability.set(scc, new MyBitSet());\n\t\t\t\t\n\t\t\t\tMyBitSet states_in_scc = _result.get(scc);\n\n\t\t\t\tfor (int from_state = states_in_scc.nextSetBit(0); from_state >= 0; from_state = states_in_scc.nextSetBit(from_state + 1)) {\n\t\t\t\t\tfor (Iterator<Integer> succ_it = _graph.get(from_state).successorIterator(); succ_it.hasNext(); ) {\n\t\t\t\t\t\tint to_state = succ_it.next();\n\t\t\t\t\t\tint to_scc = _result.state2scc(to_state);\n\n\t\t\t\t\t\tif (to_scc != scc) {\n\t\t\t\t\t\t\t// Only successor in the DAG if not the same scc\n\t\t\t\t\t\t\tif (!_result._dag.get(scc).get(to_scc)) {\n\t\t\t\t\t\t\t\t// This SCC is a new successor, increment in_degree\n\t\t\t\t\t\t\t\tin_degree[to_scc]++;\n\t\t\t\t\t\t\t\t_result._dag.get(scc).set(to_scc);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// Reachability\n\t\t\t\t\t\t_result._reachability.get(scc).set(to_scc);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tboolean progress = true;\n\t\t\tint cnt = 0;\n\t\t\t_result._topological_order.clear();\n\t\t\t_result._topological_order.setSize(_result.countSCCs());\n\n\t\t\tint[] sort = new int[_result.countSCCs()];\n\t\t\twhile (progress) {\n\t\t\t\tprogress=false;\n\n\t\t\t\tfor (int scc = 0; scc < _result.countSCCs(); ++scc) {\n\t\t\t\t\tif (in_degree[scc] == 0) {\n\t\t\t\t\t\tsort[scc] = cnt++;\n\t\t\t\t\t\tprogress = true;\n\t\t\t\t\t\tin_degree[scc] = -1;\n\n\t\t\t\t\t\tfor (Integer scc_to : _result._dag.get(scc)) {\n\t\t\t\t\t\t\tin_degree[scc_to]--;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tfor (int i = 0; i < _result.countSCCs(); i++) {\n\t\t\t\t_result._topological_order.set(sort[i], i);\n\t\t\t}\n\n\n\t\t\t// traverse SCCs in reverse topological order\n\t\t\tfor (int i = _result.countSCCs(); i > 0; --i) {\n\t\t\t\tint cur_scc = _result._topological_order.get(i-1);\n\n\t\t\t\tMyBitSet reaches = _result._reachability.get(cur_scc);\n\n\t\t\t\tfor (Integer scc_to : _result._dag.get(cur_scc)) {\n\t\t\t\t\treaches.or(_result._reachability.get(scc_to));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/Jltl2dstarCmdLine.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage jltl2dstar;\n\nimport java.io.BufferedReader;\nimport java.io.FileReader;\nimport java.io.InputStreamReader;\nimport java.io.PrintStream;\nimport java.util.BitSet;\n\nimport acceptance.AcceptanceRabin;\nimport automata.DA;\nimport jltl2ba.SimpleLTL;\n\n/**\n * Command-line interface to the jltl2dstar LTL->DRA translator.\n */\npublic class Jltl2dstarCmdLine {\n\n\tpublic int run(String formula, PrintStream output) throws Exception {\n\t\tSimpleLTL ltl = SimpleLTL.parseFormulaLBT(formula);\n\t\tltl = ltl.simplify();\n\n\t\tDA<BitSet, AcceptanceRabin> dra = LTL2Rabin.ltl2rabin(ltl);\n\t\tdra.printHOA(output);\n\t\t//DA.printLtl2dstar(dra, output);\n\t\treturn 0;\n\t}\n\t\n\tpublic static void main(String[] args) {\n\t\tint rv = 0;\n\t\tint outfile_pos = 1;\n\t\tBufferedReader r = null;\n\t\ttry {\n\t\t\tString formula;\n\t\t\tif (args.length == 0) {\n\t\t\t\tusage(\"\");\n\t\t\t}\n\t\t\tif (args[0].equals(\"--ltl\")) {\n\t\t\t\tif (args.length <= 1)\n\t\t\t\t\tusage(\"Missing formula\");\n\t\t\t\tformula = args[1];\n\t\t\t\toutfile_pos++;\n\t\t\t} else {\n\t\t\t\tif (args[0].equals(\"-\")) {\n\t\t\t\t\tr = new BufferedReader(new InputStreamReader(System.in));\n\t\t\t\t} else {\n\t\t\t\t\tr = new BufferedReader(new FileReader(args[0]));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (outfile_pos >= args.length) {\n\t\t\t\tusage(\"Missing output file\");\n\t\t\t}\n\t\t\tPrintStream output;\n\t\t\tString outfile = args[outfile_pos];\n\t\t\tif (outfile.equals(\"-\")) {\n\t\t\t\toutput = System.out;\n\t\t\t} else {\n\t\t\t\toutput = new PrintStream(outfile);\n\t\t\t}\n\n\t\t\tformula = r.readLine();\n\t\t\tr.close();\n\n\t\t\tJltl2dstarCmdLine jltl2dstar = new Jltl2dstarCmdLine();\n\t\t\trv = jltl2dstar.run(formula, output);\n\t\t\toutput.close();\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(e.toString());\n\t\t\trv = 1;\n\t\t}\n\t\t\n\t\tif (rv != 0) {\n\t\t\tSystem.exit(rv);\n\t\t}\n\t}\n\n\tprivate static void usage(String error)\n\t{\n\t\tif (!error.isEmpty()) {\n\t\t\tSystem.err.println(\"Error: \" + error);\n\t\t\tSystem.err.println();\n\t\t}\n\t\tSystem.err.println(\"Usage:\");\n\t\tSystem.err.println(\"  --ltl formula out-file\");\n\t\tSystem.err.println(\" or\");\n\t\tSystem.err.println(\"  in-file out-file\");\n\t\tSystem.err.println(\"\\n  Filename of '-' stands for standard input/output\");\n\t\tSystem.exit(1);\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/LTL2DRA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport jltl2ba.APSet;\nimport jltl2ba.SimpleLTL;\nimport jltl2ba.SimpleLTL.LTLType;\nimport prism.PrismException;\n\npublic class LTL2DRA {\n\n\tprivate Options_Safra _safra_opt;\n\n\tpublic LTL2DRA(Options_Safra safra_opt) {\n\t\t_safra_opt = safra_opt;\n\t}\n\n\t/**\n\t * Convert an LTL formula to a DRA.\n\t * @param ltl the LTL formula\n\t * @param options which operators are allowed\n\t * @return a shared_ptr to the DRA\n\t */\n\tprivate DRA LTLtoDRA_rec(SimpleLTL ltl, APSet apset, Options_LTL2DRA options) throws PrismException\n\t{\n\t\tSimpleLTL ltl_pnf = ((SimpleLTL)ltl.clone()).simplify();\n\t\t\n\t\tif (options.allow_union && ltl_pnf.kind == LTLType.OR) {\n\t\t\tSimpleLTL ltl_left = ltl_pnf.left;\n\t\t\tSimpleLTL ltl_right = ltl_pnf.right;\n\n\t\t\tOptions_LTL2DRA rec_opt = options.clone();\n\t\t\trec_opt.recursion();\n\n\t\t\tDRA dra_left = LTLtoDRA_rec(ltl_left, apset, rec_opt);\n\t\t\tDRA dra_right = LTLtoDRA_rec(ltl_right, apset, rec_opt);\n\n\t\t\treturn dra_left.calculateUnion(dra_right, options.opt_safra.union_trueloop, options.detailed_states);\n\t\t}\n\n\t\t/*  if (options.safety) {\n\t    LTLSafetyAutomata lsa;\n\n\t    DRA_ptr safety_dra(lsa.ltl2dra<DRA_t>(ltl,\n\t\t\t\t\t\t  options.scheck_path));\n\n\t    if (safety_dra.get()!=0) {\n\t      return safety_dra;\n\t    }\n\t  \t}\n\t\t */  \n\t\tNBA nba = ltl_pnf.toNBA(apset);\n\n\t\tif (nba == null) {\n\t\t\tthrow new PrismException(\"Couldn't create NBA from LTL formula\");\n\t\t}\n\n\t\tNBA2DRA nba2dra = new NBA2DRA(options.opt_safra, false);\n\n\t\tDRA dra = nba2dra.convert(nba, 0);\n\n\t\tif (options.optimizeAcceptance) {\n\t\t\tdra.optimizeAcceptanceCondition();\n\t\t}\n\n\t\tif (options.bisim) {\n\t\t\tDRAOptimizations dra_optimizer = new DRAOptimizations();\n\t\t\tdra = dra_optimizer.optimizeBisimulation(dra, false, false, false);\n\t\t}\n\n\t\treturn dra;\n\n\t}\n\n\t/* public DRA LTLtoDRA(SimpleLTL ltl, Options_LTL2DRA options) throws PrismException {\n\t\treturn LTLtoDRA_rec(ltl, ltl.getAPs(), options);\n\t} */\n\t\n\tpublic DRA LTLtoDRA(SimpleLTL ltl, APSet apset, Options_LTL2DRA options) throws PrismException {\n\t\treturn LTLtoDRA_rec(ltl, apset, options);\n\t}\n\n\n\n\t/**\n\t * Convert an NBA to a DRA using Safra's algorithm.\n\t * If limit is specified (>0), the conversion is \n\t * aborted with LimitReachedException when the number of \n\t * states exceeds the limit.\n\t * @param nba the formula\n\t * @param limit a limit on the number of states (0 for no limit)\n\t * @param detailedStates save detailed interal information (Safra trees) \n\t *                       in the generated states\n\t * @param stutter_information Information about the symbols that can be stuttered\n\t * @return a shared_ptr to the created DRA\n\t */\n\t// DRA nba2dra(NBA nba, int limit, boolean detailedStates, StutterSensitivenessInformation::ptr stutter_information) {\n\tDRA nba2dra(NBA nba, int limit, boolean detailedStates) throws PrismException {\n\n\t\tDRA dra = null;\n\t\tNBA2DRA nba2dra = new NBA2DRA(_safra_opt, detailedStates);\n\n\t\ttry {\n\t\t\tdra = nba2dra.convert(nba, limit);\n\t\t} catch (PrismException e) {\n\t\t\tdra = null;\n\t\t\t// rethrow to notify caller\n\t\t\tthrow e;\n\t\t}\n\t\treturn dra;  \n\t}\n\n\n\t/** Get the options for Safra's algorithm */\n\tpublic Options_Safra getOptions() {\n\t\treturn _safra_opt;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/LTL2Rabin.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n * Copyright (c) 2011- David Parker\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport jltl2ba.APSet;\nimport jltl2ba.SimpleLTL;\nimport prism.PrismException;\n\nimport java.util.BitSet;\n\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceStreett;\nimport acceptance.AcceptanceType;\nimport automata.DA;\n\npublic class LTL2Rabin {\n\n\t@SuppressWarnings(\"unchecked\")\n\tpublic static automata.DA<BitSet,AcceptanceRabin> ltl2rabin(SimpleLTL ltlFormula) throws PrismException\n\t{\n\t\tDA<BitSet, ? extends AcceptanceOmega> result;\n\t\tresult = ltl2da(ltlFormula, AcceptanceType.RABIN);\n\t\treturn (DA<BitSet, AcceptanceRabin>)result;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\tpublic static automata.DA<BitSet, AcceptanceStreett> ltl2streett(SimpleLTL ltlFormula) throws PrismException\n\t{\n\t\tDA<BitSet, ? extends AcceptanceOmega> result;\n\t\tresult = ltl2da(ltlFormula, AcceptanceType.STREETT);\n\t\treturn (DA<BitSet, AcceptanceStreett>)result;\n\t}\n\t\n\tpublic static automata.DA<BitSet, ? extends AcceptanceOmega> ltl2da(SimpleLTL ltlFormula, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tSimpleLTL ltl = ltlFormula.simplify();\n\n\t\tboolean allowRabin=AcceptanceType.contains(allowedAcceptance, AcceptanceType.RABIN);\n\t\tboolean allowStreett=AcceptanceType.contains(allowedAcceptance, AcceptanceType.STREETT);\n\n\t\tif (allowRabin && allowStreett) {\n\t\t\t// currently, disable opportunistic generation of either Rabin or Streett automaton\n\t\t\tallowStreett = false;\n\t\t}\n\n\t\treturn ltl2da(ltl, ltl.getAPs(), allowRabin, allowStreett).createPrismDA();\n\t}\n\n\tprivate static DRA ltl2da(SimpleLTL ltl, APSet apset, boolean allowRabin, boolean allowStreett) throws PrismException {\n\t\tDRA dra = null;\n\t\tOptions_LTL2DRA opt_ltl2rabin = new Options_LTL2DRA();\n\t\t\n\t\t// boolean flag_dra2nba=false;\n\t\tboolean flag_sched_limits=false;\n\t\t// boolean flag_print_ltl_nba=false;\n\t\tboolean flag_stat_nba=false;\n\t\tdouble alpha=10.0;\n\n\t\topt_ltl2rabin.allow_union = true;\n\t\topt_ltl2rabin.recursive_union = true;\n\t\topt_ltl2rabin.only_union = false;\n\t\topt_ltl2rabin.optimizeAcceptance = true;\n\t\topt_ltl2rabin.bisim = true;\n\t\topt_ltl2rabin.recursive_bisim = true;\n\t\t// opt_ltl2dstar.safety=false;\n\t\t// opt_ltl2dstar.only_safety=false;\n\t\t// opt_ltl2dstar.scheck_path=\"\";\n\t\t// stuttercheck_timekeep = true;\n\t\t// stuttercheck_print = false;\n\t\tif (allowRabin) {\n\t\t\tif (allowStreett)\n\t\t\t\topt_ltl2rabin.automata = Options_LTL2DRA.AutomataType.RABIN_AND_STREETT;\n\t\t\telse\n\t\t\t\topt_ltl2rabin.automata = Options_LTL2DRA.AutomataType.RABIN;\n\t\t} else if (allowStreett) {\n\t\t\topt_ltl2rabin.automata = Options_LTL2DRA.AutomataType.STREETT;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can not generate deterministic automata if neither Rabin nor Streett is allowed.\");\n\t\t}\n\t\topt_ltl2rabin.detailed_states = false;\n\t\topt_ltl2rabin.verbose_scheduler = false;\n\t\topt_ltl2rabin.opt_safra.opt_accloop = true;\n\t\topt_ltl2rabin.opt_safra.opt_accsucc = true;\n\t\topt_ltl2rabin.opt_safra.opt_rename = true;\n\t\topt_ltl2rabin.opt_safra.opt_reorder = true;\n\t\topt_ltl2rabin.opt_safra.dba_check = false;\n\t\topt_ltl2rabin.opt_safra.stat = false;\n\t\topt_ltl2rabin.opt_safra.union_trueloop = true;\n\t\t// opt_ltl2rabin.opt_safra.stutter = false;\n\t\t// opt_ltl2rabin.opt_safra.partial_stutter_check = false;\n\t\t// opt_ltl2rabin.opt_safra.stutter_closure = false;\n\n\t\t/* if (stuttercheck_timekeep) {\n\t\t\tStutterSensitivenessInformation::enableTimekeeping();\n\t\t}\n\t\tif (stuttercheck_print) {\n\t\t\tStutterSensitivenessInformation::enablePrintInfo();\n\t\t}\n\t\t*/\n\t\t\n\t\tLTL2DRA ltl2dra = new LTL2DRA(opt_ltl2rabin.opt_safra);\n\t\tScheduler sched = new Scheduler(ltl2dra, flag_sched_limits, alpha);\n\t\tsched.flagStatNBA(flag_stat_nba);\n\t\tdra = sched.calculate(ltl, apset, opt_ltl2rabin);\n\n\t\tif (dra == null) {\n\t\t\tthrow new PrismException(\"Couldn't generate DRA!\");\n\t\t}\n\n\t\tif (!dra.isCompact()) {\n\t\t\tdra.makeCompact();\n\t\t}\n\t\t\n\t\treturn dra;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/NBA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.*;\n\nimport common.IterableBitSet;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\nimport java.io.PrintStream;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport jltl2ba.MyBitSet;\n\n\n/** @file\n * Provides class NBA to store a nondeterministic Büchi automaton.\n */\n\n/**\n * A nondeterministic Büchi automaton.\n * See class DA for description of template parameters.\n */\n\npublic class NBA implements Iterable<NBA_State> {\n\n\t/** Number of states */\n\t  private int _state_count;\n\t  \n\t  /** Storage for the states */\n\t  private Vector<NBA_State> _index;\n\n\t  /** The underlying APSet */\n\t  private APSet _apset;\n\t  \n\t  /** The start states */\n\t  private NBA_State _start_state;\n\n\t  /** The states that are accepting (final) */\n\t  private MyBitSet _final_states;\n\n\t  /**\n\t   * Flag, telling whether to fail later on if the NBA is discovered\n\t   * to be disjoint, as this is indicative of a malfunctioning\n\t   * NBA generator.\n\t   */\n\t  private boolean _fail_if_disjoint = false;\n\t\n\t/**\n\t * Constructor.\n\t * @param apset The underlying APSet\n\t */\n\tpublic NBA (APSet apset)\n\t{\n\t\t_state_count = 0;\n\t\t_start_state = null;\n\t\t_apset = apset;\n\t\t_index = new Vector<NBA_State>();\n\t\t_final_states = new MyBitSet();\n\t}\n\t\n\t/**\n\t * Add a new state.\n\t * @return a pointer to the newly generated state\n\t */\n\tpublic NBA_State newState()\n\t{\n\t\t_state_count++;\n\t\tNBA_State state = new NBA_State(this);\n\t  \n\t\t_index.add(state);\n\t\treturn state;\n\t}\n\n\t/** Get number of states. */\n\tpublic int size()\n\t{\n\t\treturn _index.size();\n\t}\n\n\t//FIXME: ref_iterator\n  \n\t/** Array index operator, get the state with index i. */\n\tpublic NBA_State get(int i)\n\t{\n\t\treturn _index.get(i);\n\t}\n\n\t/** Get the size of the underlying APSet. */\n\tpublic int getAPSize()\n\t{\n\t\treturn _apset.size();\n\t}\n\n\t/** Get a const reference to the underlying APSet. */\n\tpublic APSet getAPSet()\n\t{\n\t\treturn _apset;\n\t}\n\n\t/** Switch the APSet to another with the same number of APs. */\n\tpublic void switchAPSet(APSet new_apset) throws PrismException\n\t{\n\t\tif (new_apset.size() != _apset.size()) {\n\t\t\tthrow new PrismException(\"New APSet has to have the same size as the old APSet!\");\n\t\t}\n\t\t_apset = new_apset;\n\t}\n\n\t/** Get the index for a state. */\n\tpublic int getIndexForState(NBA_State state)\n\t{\n\t\treturn _index.indexOf(state);\n\t}\n\n\t/** Set the start state. */\n\tpublic void setStartState(NBA_State state)\n\t{\n\t\t_start_state = state;\n\t}\n\n\t/**\n\t * Get the start state.\n\t * @return the start state, or NULL if it wasn't set.\n\t */\n\tpublic NBA_State getStartState()\n\t{\n\t\treturn _start_state;\n\t}\n\n\t/** Get the set of final (accepting) states in the NBA */\n\tpublic MyBitSet getFinalStates()\n\t{\n\t\treturn _final_states;\n\t}\n\n\t/**\n\t * Get the set of successor states for the given set of from states\n\t * and the element of the alphabet.\n\t */\n\tpublic MyBitSet getSuccessors(MyBitSet fromStates, APElement elem)\n\t{\n\t\tMyBitSet result = new MyBitSet(fromStates.size());\n\t\tfor (int s : IterableBitSet.getSetBits(fromStates)) {\n\t\t\t// for each state s, do union of successors for elem.\n\t\t\tresult.or(get(s).getEdge(elem));\n\t\t}\n\t\treturn result;\n\t}\n\n\t// public MyBitSet calculateFinalTrueLoops(SCCs sccs);\n\n\t/** \n\t * Remove states from the set of accepting (final) states when this is redundant.\n\t * @param sccs the SCCs of the NBA\n\t */\n\tpublic void removeRedundantFinalStates(SCCs sccs) {\n\t\tfor (int scc = 0; scc < sccs.countSCCs(); ++scc) {\n\t\t\tif (sccs.get(scc).cardinality() == 1) {\n\t\t\t\tint state_id = sccs.get(scc).nextSetBit(0);\n\t\t\t\tNBA_State state = this.get(state_id);\n\n\t\t\t\tif (state.isFinal()) {\n\t\t\t\t\tif (!sccs.stateIsReachable(state_id, state_id)) {\n\t\t\t\t\t\t// The state is final and has no self-loop\n\t\t\t\t\t\t//  -> the final flag is redundant\n\t\t\t\t\t\tstate.setFinal(false);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Checks if the NBA is deterministic (every edge has at most one target state).\n\t */\n\tpublic boolean isDeterministic() {\n\t\tfor (NBA_State state : _index) {\n\t\t\tfor (Map.Entry<APElement, MyBitSet> edge : state) {\n\t\t\t\tif (edge.getValue().cardinality() > 1) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\t\n\tpublic NBA product_automaton(NBA nba_2) {\n\t\t\n\t\tNBA nba_1 = this;\n\t\t\n\t\tNBA product_nba = new NBA(nba_1.getAPSet());\n\t  \n\t\tAPSet apset = nba_1.getAPSet();\n\n\t\tfor (int s_1 = 0; s_1 < nba_1.size(); s_1++) {\n\t\t\tfor (int s_2 = 0; s_2 < nba_2.size(); s_2++) {\n\t\t\t\tfor (int copy = 0; copy < 2; copy++) {\n\t\t\t\t\tint s_r = product_nba.nba_i_newState();\n\t\t\t\t\tint to_copy = copy;\n\t\t\n\t\t\t\t\tif (copy == 0 && nba_1.get(s_1).isFinal()) {\n\t\t\t\t\t\tto_copy=1;\n\t\t\t\t\t}\n\t\t\t\t\tif (copy == 1 && nba_2.get(s_2).isFinal()) {\n\t\t\t\t\t\tproduct_nba.get(s_r).setFinal(true);\n\t\t\t\t\t\tto_copy = 0;\n\t\t\t\t\t}\n\t\t\n\t\t\t\t\tAPElement label = new APElement(apset.size());\n\t\t\t\t\tfor (int i = 0; i < (1<<apset.size()); i++) {\n\t\t\t\t\t\tMyBitSet to_s1 = nba_1.get(s_1).getEdge(label);\n\t\t\t\t\t\tMyBitSet to_s2 = nba_2.get(s_2).getEdge(label);\n\t\t\t\t\t\tMyBitSet to_set = new MyBitSet();\n\t\t\t\t\t\tfor (int it_e_1 = to_s1.nextSetBit(0); it_e_1 != -1; it_e_1 = to_s1.nextSetBit(it_e_1)) {\n\t\t\t\t\t\t\tfor (int it_e_2 = to_s2.nextSetBit(0); it_e_2 != -1; it_e_2 = to_s2.nextSetBit(it_e_2)) {\n\t\t\t\t\t\t\t\tint to = 2 * (it_e_1 * nba_2.size() + it_e_2) + to_copy;\n\t\t\t\t\t\t\t\tto_set.set(to);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\tproduct_nba.get(s_r).addEdges(label, to_set);\n\t\t\t\t\t\tlabel.increment();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tint start_1 = nba_1.getStartState().getName();\n\t\tint start_2 = nba_2.getStartState().getName();\n\t\tproduct_nba.setStartState(product_nba.get(start_1 * nba_2.size() + start_2));\n\t  \n\t\treturn product_nba;\n\t}\n\n\t/**\n\t * Print automaton to a PrintStream in a specified format (\"dot\", \"txt\", \"lbtt\" or \"hoa\").\n\t */\n\tpublic void print(PrintStream out, String type) throws PrismException\n\t{\n\t\tswitch (type) {\n\t\tcase \"txt\":\n\t\t\tprint(out);\n\t\t\tbreak;\n\t\tcase \"dot\":\n\t\t\tprint_dot(out);\n\t\t\tbreak;\n\t\tcase \"lbtt\":\n\t\t\tprint_lbtt(out);\n\t\t\tbreak;\n\t\tcase \"hoa\":\n\t\t\tprint_hoa(out);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Can not print NBA in '\"+type+\"' format\");\n\t\t}\n\t}\n\n\t/**\n\t * Print the NBA on the output stream.\n\t */\n\tpublic void print(PrintStream out) {\n\t\tfor (NBA_State state : _index){\n\t\t\tout.print(\"State \" + state.getName());\n\t\t\tif (getStartState() == state) {\n\t\t\t\tout.print(\" *\");\n\t\t\t}\n\t\t\tif (state.isFinal()) {\n\t\t\t\tout.print(\" !\");\n\t\t\t}\n\t\t\tout.println();\n\n\t\t\tfor (Map.Entry<APElement, MyBitSet> edge : state) {\n\t\t\t\tAPElement label = edge.getKey();\n\t\t\t\tMyBitSet to_states = edge.getValue();\n\t\t\t\tout.println(\" \" + label.toString(getAPSet(),true) + \" -> \" + to_states.toString());\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Print the NBA as an LBTT automaton to out */\n\tpublic void print_lbtt(PrintStream out) {\n\t\tout.println(getStateCount()+\" 1s\");\n\t\tfor (NBA_State state : _index) {\n\t\t\tout.print(state.getName());  // id\n\t\t\tout.print(\" \");\n\t\t\tout.print((getStartState() == state ? \"1\" : \"0\"));\n\t\t\tout.print(\" \");\n\t\t\tout.println((state.isFinal() ? \"0 -1\" : \"-1\"));\n\t\t\t\n\t\t\tfor (Map.Entry<APElement, MyBitSet> edge : state) {\n\t\t\t\tAPElement label = edge.getKey();\n\t\t\t\tMyBitSet to_states = edge.getValue();\n\t\t\t\tfor (Integer to : to_states) {\n\t\t\t\t\tout.print(to);\n\t\t\t\t\tout.print(\" \");\n\t\t\t\t\tout.println(label.toStringLBTT(getAPSet()));\n\t\t\t\t}\n\n\t\t\t}\n\t\t\tout.println(\"-1\");\n\t\t}\n\t}\n\n\t/** Print the NBA as a HOA automaton to out */\n\tpublic void print_hoa(PrintStream out) {\n\t\tout.println(\"HOA: v1\");\n\t\tout.println(\"States: \"+size());\n\t\t_apset.print_hoa(out);\n\t\tout.println(\"Start: \"+getStartState().getName());\n\t\tout.println(\"Acceptance: 1 Inf(0)\");\n\t\tout.println(\"acc-name: Buchi\");\n\t\tout.println(\"properties: trans-labels explicit-labels state-acc no-univ-branch\");\n\t\tout.println(\"--BODY--\");\n\t\tfor (NBA_State state : _index) {\n\t\t\tout.print(\"State: \"+state.getName());  // id\n\t\t\tout.println((state.isFinal() ? \" {0}\" : \"\"));\n\n\t\t\tfor (Map.Entry<APElement, MyBitSet> edge : state) {\n\t\t\t\tAPElement label = edge.getKey();\n\t\t\t\tString labelString = \"[\"+label.toStringHOA(_apset.size())+\"]\";\n\t\t\t\tMyBitSet to_states = edge.getValue();\n\t\t\t\tfor (Integer to : to_states) {\n\t\t\t\t\tout.print(labelString);\n\t\t\t\t\tout.print(\" \");\n\t\t\t\t\tout.println(to);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tout.println(\"--END--\");\n\t}\n\n\t/** Print the NBA as a Graphviz (DOT) graph to out */\n\tpublic void print_dot(PrintStream out) {\n\t\tout.println(\"digraph nba {\");\n\t\tout.println(\" node [fontname=Helvetica]\");\n\t\tout.println(\" edge [constraints=false, fontname=Helvetica]\");\n\n\t\tfor (NBA_State state : _index) {\n\t\t\tout.print(\" \" + state.getName());  // id\n\t\t\tout.print(\" [shape=\");\n\t\t\tout.print((state.isFinal() ? \"box\" : \"circle\"));\n\t\t\tif (state == getStartState()) {\n\t\t\t\tout.print(\", style=filled, color=black, fillcolor=grey\");\n\t\t\t}\n\t\t\tout.println(\"]\");\n\n\t\t\tfor (Map.Entry<APElement, MyBitSet> edge : state) {\n\t\t\t\tAPElement label = edge.getKey();\n\t\t\t\t//String labelString = \"[\"+label.toStringHOA(_apset.size())+\"]\";\n\t\t\t\tString labelString = label.toString(getAPSet(),true);\n\t\t\t\tMyBitSet to_states = edge.getValue();\n\t\t\t\tfor (Integer to : to_states) {\n\t\t\t\t\tout.print(\"  \" + state.getName() + \" -> \" + to);\n\t\t\t\t\tout.println(\" [label=\\\"\" + labelString + \"\\\"]\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tout.println(\"}\");\n\t}\n\n\t/** Return number of states. */\n\tpublic int getStateCount()\n\t{\n\t\treturn _state_count;\n\t}\n\t\n\t/** Set fail_if_disjoint flag */\n\tpublic void setFailIfDisjoint(boolean value)\n\t{\n\t\t_fail_if_disjoint = value;\n\t}\n\t\n\t/** Get fail_if_disjoint flag */\n\tpublic boolean getFailIfDisjoint()\n\t{\n\t\treturn _fail_if_disjoint;\n\t}\n\t\n\t/** \n\t * Create a new state.\n\t * @return the index of the new state\n\t */\n\tpublic int nba_i_newState()\n\t{ \n\t\treturn newState().getName();\n\t}\n\n\t/**\n\t * Add an edge from state <i>from</i> to state <i>to</i>\n\t * for the edges covered by the APMonom.\n\t * @param from the index of the 'from' state\n\t * @param m the APMonom\n\t * @param to the index of the 'to' state\n\t */\n\tpublic void nba_i_addEdge(int from, APMonom m, int to)\n\t{\n\t\tthis.get(from).addEdge(m, this.get(to));\n\t}\n\n\t/**\n\t * Get the underlying APSet \n\t * @return a const pointer to the APSet\n\t */\n\tpublic APSet nba_i_getAPSet()\n\t{\n\t\treturn getAPSet();\n\t}\n\n\t/** \n\t * Set the final flag (accepting) for a state.\n\t * @param state the state index\n\t * @param final the flag\n\t */\n\tpublic void nba_i_setFinal(int state, boolean f)\n\t{\n\t\tthis.get(state).setFinal(f);\n\t}\n\n\t/**\n\t * Set the state as the start state.\n\t * @param state the state index\n\t */\n\tpublic void nba_i_setStartState(int state)\n\t{\n\t\tsetStartState(this.get(state));\n\t}\n\t\n\tpublic Iterator<NBA_State> iterator()\n\t{\n\t\treturn _index.iterator();\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/NBA2DAResult.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\npublic interface NBA2DAResult<S extends NBA2DAState> {\n\tpublic S getState();\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/NBA2DAState.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\npublic interface NBA2DAState {\n\tpublic void generateAcceptance(AcceptanceForState acceptance);\n\tpublic String toHTML();\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/NBA2DRA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport jltl2ba.APSet;\nimport prism.PrismException;\n\n/**\n * Convert an NBA to a DRA using Safra's algorithm\n */\npublic class NBA2DRA {\n\n\t/** The options */\n\tprivate Options_Safra _options;\n\t/** Save detailed information on the Safra trees in the states? */\n\tprivate boolean _detailed_states;\n\n\t// stuttering\n\t// private StutterSensitivenessInformation _stutter_information;\n\n\n\t/** Constructor */\n\tpublic NBA2DRA() {\n\t\t_detailed_states = false;\n\t}\n\n\t/** Constructor.\n\t * @param options Options_Safra specifying whether to stutter, etc...\n\t * @param detailedStates generate detailed descriptions for the states?\n\t * @param stutter_information Information about the symbols that may be stuttered\n\t */\n\tpublic NBA2DRA(Options_Safra options, boolean detailedStates) {\n//\tpublic NBA2DRA(Options_Safra options, boolean detailedStates, StutterSensitivenessInformation stutter_information) {\n\t\t\n\t\t_options = options;\n\t\t_detailed_states = detailedStates;\n\t// _stutter_information = stutter_information;\n\t}\n\n\t/**\n\t * Convert an NBA to an DRA (having APElements as edge labels).\n\t * Throws LimitReachedException if a limit is set (>0) and\n\t * there are more states in the generated DRA than the limit. \n\t * @param nba the NBA\n\t * @param dra_result the DRA where the result is stored \n\t *        (has to have same APSet as the nba)\n\t * @param limit a limit for the number of states (0 disables the limit).\n\t */\n\tpublic DRA convert(NBA nba, int limit) throws PrismException {\n\n\t\tif (nba.size() == 0 || nba.getStartState() == null ) {\n\t\t\t// the NBA is empty -> construct DRA that is empty\n\n\t\t\tAPSet ap_set = nba.getAPSet();\n\t\t\tDRA dra_result = new DRA(ap_set);\n\n\t\t\tdra_result.constructEmpty();\n\t\t\treturn dra_result;\n\t\t}\n\t\t// nba.print(System.out);\n\n\t\tif (_options.dba_check && nba.isDeterministic()) {\n\t\t\treturn DBA2DRA.dba2dra(nba, false);\n\t\t}\n\n\t\t/*\t\tif (_options.stutter_closure) {\n\t\t\tif (_stutter_information != null &&\t!_stutter_information.isCompletelyInsensitive()) {\n\t\t\t\tSystem.err.println(\"WARNING: NBA might not be 100% stutter insensitive, applying stutter closure can create invalid results!\");\n\t\t\t}\n\n\t\t\tboost::shared_ptr<NBA_t> nba_closed=\n\t\t\t\tNBAStutterClosure::stutter_closure(nba);\n\n\t\t\tif (can_stutter()) {      \n\t\t\t\tconvert_safra_stuttered(*nba_closed, dra_result, limit);\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tconvert_safra(*nba_closed,dra_result,limit);\n\t\t\treturn;\n\t\t}\n\n\n\t\tif (can_stutter()) {      \n\t\t\tconvert_safra_stuttered(nba, dra_result, limit);\n\t\t\treturn;\n\t\t}\n\t\t */\n\t\treturn convert_safra(nba, limit);\n\t}\n\n\t/** \n\t * Is stuttering allowed?\n\t */\n/*\tpublic boolean can_stutter() {\n\t\tif (_stutter_information == null) {\n\t\t\treturn false;\n\t\t}\n\n\t\tif (_options.stutter && _stutter_information.isCompletelyInsensitive()) {\n\t\t\treturn true;\n\t\t}\n\n\t\tif (_options.stutter && _stutter_information.isPartiallyInsensitive()) {\n\t\t\treturn true;\n\t\t}\n\n\t\treturn false;\n\t}\n*/\n\n\t/**\n\t * Provides CandidateMatcher for SafraTrees\n\t */\n\t/*\tclass SafraTreeCandidateMatcher {\n\t\tpublic:\n\t\t\tstatic bool isMatch(const SafraTreeTemplate_ptr temp, const SafraTree_ptr tree) {\n\t\treturn temp->matches(*tree);\n\t};\n\n\tstatic bool abstract_equal_to(const SafraTree_ptr t1, const SafraTree_ptr t2) {\n\t\treturn t1->structural_equal_to(*t2);\n\t}\n\n\tstatic bool abstract_less_than(const SafraTree_ptr t1, const SafraTree_ptr t2) {\n\t\treturn t1->structural_less_than(*t2);\n\t}\n\n\ttemplate <typename HashFunction>\n\tstatic void abstract_hash_code(HashFunction& hash, SafraTree_ptr t) {\n\t\tt->hashCode(hash, true);\n\t}\n\t};\n\t */\n\n\n\t/**\n\t * Convert the NBA to a DRA using Safra's algorithm\n\t * @param nba the NBA\n\t * @param dra_result the result DRA\n\t * @param limit limit for the size of the DRA\n\t */\n\tpublic DRA convert_safra(NBA nba, int limit) throws PrismException {\n\n\t\tSafrasAlgorithm safras_algo = new SafrasAlgorithm(nba, _options);\n\t\t\n\t\tAPSet ap_set = nba.getAPSet();\n\t\tDRA dra_result = new DRA(ap_set);\n\n\t\tif (!_options.opt_rename) {\n\t\t\tSafraNBA2DRA nba2da = new SafraNBA2DRA(_detailed_states);\n\t\t\tnba2da.convert(safras_algo, dra_result, limit, new StateMapper<SafraTreeTemplate,SafraTree,DA_State>());\n\t\t\treturn dra_result;\n\t\t} else {\n\t\t\tSafraNBA2DRA nba2da_fuzzy = new SafraNBA2DRA(_detailed_states);\n\t\t\tnba2da_fuzzy.convert(safras_algo, dra_result, limit, new StateMapperFuzzy<SafraTreeCandidateMatcher>());\n\t\t\treturn dra_result;\n\t\t}\n\t}\n\n\n\t/**\n\t * Convert the NBA to a DRA using Safra's algorithm, using stuttering\n\t * @param nba the NBA\n\t * @param dra_result the result DRA\n\t * @param limit limit for the size of the DRA\n\t */  \n/*\tpublic DRA convert_safra_stuttered(NBA nba, unsigned int limit) {\n\t\tStutteredNBA2DA<safra_t, DRA_t> nba2dra_stuttered = new StutteredNBA2DA(_detailed_states, _stutter_information);\n\t\treturn nba2dra_stuttered.convert(safras_algo, limit);\n\t}\n*/\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/NBAAnalysis.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** @file\n * Provides class NBAAnalysis for performing analysis on non-deterministic Büchi automata.\n */\n\nimport java.util.*;\n\nimport jltl2ba.APElementIterator;\nimport jltl2ba.MyBitSet;\n\n\npublic class NBAAnalysis {\n\n\t/** \n\t * Perform (and cache) analysis for a given NBA.\n\t */\n\tprivate NBA _nba;\n\n\t/** Information about the SCCs of the NBA (cached) */\n\tprivate SCCs _sccs;\n\t/** Information about the states where all the successor states are accepting (cached) */\n\tprivate MyBitSet _allSuccAccepting;\n\t/** Information about the states that have an accepting true self-loop (cached) */\n\tprivate MyBitSet _accepting_true_loops;\n\t/** Information about the reachability of states (cached) */\n\tprivate Vector<MyBitSet> _reachability;\n\n\n\t/** Constructor.\n\t * @param nba the NBA to be analyzed\n\t */\n\tpublic NBAAnalysis(NBA nba) {\n\t\t_sccs = null;\n\t\t_allSuccAccepting = null;\n\t\t_accepting_true_loops = null;\n\t\t_nba = nba;\n\t}\t\t\t\t\t\t\n\n\t/** Get the SCCs for the NBA \n\t * @return the SCCs\n\t */\n\tpublic SCCs getSCCs() {\n\t\tif (_sccs == null) {\n\t\t\t_sccs = new SCCs();\n\t\t\tGraphAlgorithms.calculateSCCs(_nba, _sccs, true);\n\t\t}\n\t\treturn _sccs;\n\t}\n\n\t/** Get the states for which all successor states are accepting.\n\t * @return BitSet with the information\n\t */\n\tpublic MyBitSet getStatesWithAllSuccAccepting() {\n\t\tif (_allSuccAccepting == null) {\n\t\t\tcalculateStatesWithAllSuccAccepting();\n\t\t}\n\t\treturn _allSuccAccepting;\n\t}\n\n\t/** Get the states with accepting true self loops\n\t * @return BitSet with the information\n\t */\n\tpublic MyBitSet getStatesWithAcceptingTrueLoops() {\n\t\tif (_accepting_true_loops == null) {\n\t\t\tcalculateAcceptingTrueLoops();\n\t\t}\n\t\treturn _accepting_true_loops;\n\t}\n\n\n\t/** Checks to see if NBA has only accepting (final) states.\n\t * @return true iff all states are accepting\n\t */\n\tpublic boolean areAllStatesFinal() {\n\t\tfor (NBA_State state : _nba) {\n\t\t\tif (!state.isFinal()) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/** Get the accepting states from the NBA\n\t * @return BitSet with the information\n\t */\n\tpublic MyBitSet getFinalStates() {\n\t\treturn _nba.getFinalStates();\n\t}\n\n\t/**\n\t * Returns true if the NBA is disjoint, i.e., there are states\n\t * that are not reachable from the initial state\n\t */\n\tpublic boolean isNBADisjoint() {\n\t\treturn getSCCs().getGraphIsDisjoint();\n\t}\n\t\n\t/** Get the reachability analysis for the NBA\n\t * @return vector of BitSets representing the set of state which are reachable from a given state.\n\t */\n\tpublic Vector<MyBitSet> getReachability() {\n\t\tif (_reachability == null) {\n\t\t\t_reachability = getSCCs().getReachabilityForAllStates();\n\t\t}\n\n\t\treturn _reachability;\n\t}\n\n\n\t/** Check if the NBA is empty.\n\t * @return true iff the NBA has no accepting run.\n\t */\n\tpublic boolean emptinessCheck() {\n\t\tSCCs sccs = getSCCs();\n\n\t\tfor (int scc = 0; scc < sccs.countSCCs(); ++scc) {\n\t\t\tMyBitSet states_in_scc = sccs.get(scc);\n\n\t\t\t// check to see if there is an accepting state in this SCC\n\t\t\tfor (int state = states_in_scc.nextSetBit(0); state >= 0; state = states_in_scc.nextSetBit(state+1)) {\n\t\t\t\tif (_nba.get(state).isFinal()) {\n\t\t\t\t\t// check to see if this SCC is a trivial SCC (can't reach itself)\n\n\t\t\t\t\tif (states_in_scc.cardinality() == 1) {\n\t\t\t\t\t\t// there is only one state in this scc ...\n\n\t\t\t\t\t\tif (sccs.stateIsReachable(state,state) == false) {\n\t\t\t\t\t\t\t// ... and it doesn't loop to itself\n\t\t\t\t\t\t\t// -> can not guarantee accepting run\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// if we are here, the SCC has more than 1 state or \n\t\t\t\t\t// exactly one self-looping state\n\t\t\t\t\t//  -> accepting run\n\n\t\t\t\t\t// check that SCC can be reached from initial state\n\t\t\t\t\tassert(_nba.getStartState() != null);\n\t\t\t\t\tif (sccs.stateIsReachable(_nba.getStartState().getName(), state)) {\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\n\t/** \n\t * Calculates BitSet which specifies which states in the NBA \n\t * only have accepting successors.\n\t */\n\tprivate void calculateStatesWithAllSuccAccepting() {\n\t\t_allSuccAccepting = new MyBitSet();\n\t\tMyBitSet result = _allSuccAccepting;\n\t\tSCCs sccs = getSCCs();\n\n\t\tMyBitSet scc_all_final = new MyBitSet(sccs.countSCCs());\n\n\t\tfor (int sccIndex = sccs.countSCCs(); sccIndex > 0; --sccIndex) {\n\t\t\t// go backward in topological order...\n\t\t\tint scc = sccs.topologicalOrder().get(sccIndex-1);\n\n\t\t\tMyBitSet states_in_scc = sccs.get(scc);\n\n\t\t\t// check to see if all states in this SCC are final\n\t\t\tscc_all_final.set(scc);\n\t\t\tfor (int it = states_in_scc.nextSetBit(0); it >= 0; it = states_in_scc.nextSetBit(it+1)) {\n\t\t\t\tif (!_nba.get(it).isFinal()) {\n\t\t\t\t\tscc_all_final.clear(scc);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tboolean might_be_final = false;\n\t\t\tif (!scc_all_final.get(scc)) {\n\t\t\t\tif (states_in_scc.cardinality() == 1) {\n\t\t\t\t\t// there is only one state in this scc ...\n\t\t\t\t\tint state = states_in_scc.nextSetBit(0);\n\n\t\t\t\t\tif (!sccs.stateIsReachable(state,state)) {\n\t\t\t\t\t\t// ... and it doesn't loop to itself\n\t\t\t\t\t\tmight_be_final = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (scc_all_final.get(scc) || might_be_final) {\n\t\t\t\t// Check to see if all successors are final...\n\t\t\t\tboolean all_successors_are_final = true;\n\t\t\t\tMyBitSet scc_succ = sccs.successors(scc);\n\t\t\t\tfor (int it = scc_succ.nextSetBit(0); it >= 0; it = scc_succ.nextSetBit(it+1)) {\n\t\t\t\t\tif (!scc_all_final.get(it)) {\n\t\t\t\t\t\tall_successors_are_final = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (all_successors_are_final) {\n\t\t\t\t\t// Add all states in this SCC to the result-set\n\t\t\t\t\tresult.or(states_in_scc);\n\n\t\t\t\t\tif (might_be_final) {\n\t\t\t\t\t\tscc_all_final.set(scc);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/** \n\t * Calculate the set of states that are accepting and have a true self loop.\n\t */\n\tprivate void calculateAcceptingTrueLoops() {\n\t\t_accepting_true_loops = new MyBitSet();\n\t\tSCCs sccs = getSCCs();\n\n\t\tfor (int scc = 0; scc < sccs.countSCCs(); ++scc) {\n\t\t\tif (sccs.get(scc).cardinality() == 1) {\n\t\t\t\tint state_id = sccs.get(scc).nextSetBit(0);\n\t\t\t\tNBA_State state = _nba.get(state_id);\n\n\t\t\t\tif (!state.isFinal()) {\n\t\t\t\t\t// not final, consider next\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\tif (!sccs.successors(scc).isEmpty()) {\n\t\t\t\t\t// there are edges leaving this state, consider next\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\tboolean no_empty_to = true;\n\t\t\t\tif (sccs.stateIsReachable(state_id, state_id)) {\n\t\t\t\t\t// state has at least one self-loop\n\t\t\t\t\t// we have to check that there is no edge with empty To\n\t\t\t\t\tfor (APElementIterator it = new APElementIterator(_nba.getAPSize()); it.hasNext(); ) {\n\t\t\t\t\t\t// FIXME: this fills the state with null edges because of getEdge() sideeffects\n\t\t\t\t\t\tif (state.getEdge(it.next()).isEmpty()) {\n\t\t\t\t\t\t\t// not all edges lead back to the state...\n\t\t\t\t\t\t\tno_empty_to = false;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tif (no_empty_to) {\n\t\t\t\t\t\t// When we are here the state is a final true loop\n\t\t\t\t\t\t_accepting_true_loops.set(state_id);\n\t\t\t\t\t\t//\t  std::cerr << \"True Loop: \" << state_id << std::endl;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/jltl2dstar/NBA_State.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.*;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APSet;\nimport jltl2ba.MyBitSet;\nimport jltl2ba.MyBitSet.MyBitSetIterator;\n\n\n/** @file\n * Provides class NBA_State for storing a state of a nondeterministic Büchi automaton.\n */\n\n/**\n * A state of a deterministic omega-automaton.\n * For a description of the template parameters, see class NBA.\n */\npublic class NBA_State implements Iterable<Map.Entry<APElement,MyBitSet>> {\n\n\t /** The automaton */\n\tprivate NBA _graph;\n\n\t/** Is this state accepting */\n\tboolean _isFinal;\n\n\t/** A description. */\n\tString _description;\n\n\t/** The EdgeManager*/\n\tEdgeManager _edge_manager;\n\n\t\n  /**\n   * Constructor.\n   * @param graph The automaton (NBA) that contains this state.\n   */\n\tpublic NBA_State(NBA graph)\n\t{\n\t\t_graph = graph;\n\t\t_isFinal = false;\n\t\t_edge_manager = new EdgeManager(this, graph.getAPSet());\n\t\t_description = \"\";\n\t}\n\n\n\t/** \n\t * Add an edge from this state to the other state\n\t * @param label the label for the edge\n\t * @param state the target state \n\t */\n\tpublic void addEdge(APElement label, NBA_State state) {\n\t\t_edge_manager.addEdge(label, state);\n\t}\n\n\n\t/** \n\t * Add edge(s) from this state to the other state\n\t * @param monom an APMonom for the label(s)\n\t * @param to_state the target state\n\t */\n\tpublic void addEdge(APMonom monom, NBA_State to_state) {\n\t\t_edge_manager.addEdge(monom, to_state);\n\t}\n\t\n\t/** \n\t * Add edge(s) from this state to the other state\n\t * @param monom an APMonom for the label(s)\n\t * @param to_state the target state\n\t */\n\tpublic void addEdges(APElement monom, MyBitSet to_states) {\n\t\t_edge_manager.addEdges(monom, to_states);\n\t}\n\n\t/** \n\t * Get the target states of the labeled edge.\n\t * @return a pointer to a BitSet with the indizes of the target states.\n\t */\n\tpublic MyBitSet getEdge(APElement label) {\n\t\treturn _edge_manager.getEdge(label);\n\t}\n\n\t/** Get the name (index) of this state. */\n\tpublic int getName() {\n\t\treturn _graph.getIndexForState(this);\n\t}\n\n\t// FIXME: operator<<\n\n\t/** Is this state accepting (final)? */\n\tpublic boolean isFinal()\n\t{\n\t\treturn _isFinal;\n\t}\n  \n\t/** Set the value of the final flag for this state */\n\tpublic void setFinal(boolean f) {\n\t\t_isFinal=f;\n\t\t_graph.getFinalStates().set(_graph.getIndexForState(this), f);\n\t}\n\n\t// FIXME: ForEachSuccessor\n  \t// FIXME: edge_to_bitset_iterator\n  \t// FIXME: successor_iterator\n  \n\t/** Set the description for this state. */\n\tpublic void setDescription(String s) {\n\t\t_description = s;\n\t}\n\t\n\t/** Get the description for this state. */\n\tString getDescription() {\n\t\treturn _description;\n\t}\n\n\t/** Check if this state has a description. */\n\tpublic boolean hasDescription() {\n\t\treturn (_description.length() != 0);\n\t}\n\n\t/** Get the automaton owning this state. */\n\tpublic NBA getGraph()\n\t{\n\t\treturn _graph;\n\t}\n\t\n\tpublic Iterator<Map.Entry<APElement,MyBitSet>> iterator()\n\t{\n\t\treturn _edge_manager.getEdgeContainer().entrySet().iterator();\n\t}\n\t\n\tpublic Iterator<Integer> successorIterator()\n\t{\t\n\t\tMyBitSet successors = new MyBitSet(_graph.getStateCount());\n\t\tfor (MyBitSet dest : _edge_manager.getEdgeContainer().values()) {\n\t\t\tsuccessors.or(dest);\n\t\t}\n\t\treturn new MyBitSet.MyBitSetIterator(successors);\n\t}\n\t\n\t/** The EdgeManager for the NBA_State */\n\tpublic static class EdgeManager {\n\n\t\t/** The state owning this EdgeManager */\n\t\tprivate NBA_State _state;\n\t\t/** The EdgeContainer */\n\t\tprivate HashMap<APElement, MyBitSet> _container;\n\t\tprivate int _apset_size;\n\n\t\t/**\n\t\t * Constructor.\n\t\t * @param state the NBA_State owning this EdgeManager\n\t\t * @param apset the underlying APSet   \n\t\t */\n\t\tpublic EdgeManager(NBA_State state, APSet apset) \n\t\t{\n\t\t\t_apset_size = apset.size();\n\t\t\t_state = state;\n\t\t\t_container = new HashMap<APElement, MyBitSet>();\n\t\t}\n\n\t\t/** Get the target states */\n\t\tpublic MyBitSet getEdge(APElement label) {\n\t\t\tif (_container.get(label) == null)\n\t\t\t\t_container.put(label, new MyBitSet(_apset_size));\n\t\t\treturn _container.get(label);\n\t\t}\n\n\t\tpublic void addEdges(APElement label, MyBitSet to)\n\t\t{\n\t\t\t_container.put(label, to);\n\t\t}\n\n\t\t/** Add an edge. */\n\t\tpublic void addEdge(APElement label, NBA_State state) {\n\t\t\tif (_container.get(label) == null)\n\t\t\t\t_container.put(label, new MyBitSet(_apset_size));\n\t\t\t_container.get(label).set(state.getName());\n\t\t}\n\n\t\t/** Add an edge. */\n\t\tpublic void addEdge(APMonom label, NBA_State state) {\n\t\t\tAPSet ap_set = _state.getGraph().getAPSet();\n\t\t\t\n\t\t\tfor (Iterator<APElement> it = label.APElementIterator(ap_set); it.hasNext(); ) {\n\t\t\t\tAPElement cur = it.next();\n\t\t\t\taddEdge(cur, state);\n\t\t\t\t// System.out.println(\"State \" + _state.getName() + \" added edge to \" + state.getName() + \" through \" + cur);\n\t\t\t}\n\t\t}\n\n\t\t/** Get the EdgeContainer. */\n\t\tpublic HashMap<APElement, MyBitSet> getEdgeContainer() {\n\t\t\treturn _container;\n\t\t}\n\t}\n }\n"
  },
  {
    "path": "prism/src/jltl2dstar/Options_LTL2DRA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/**\n * Options for the LTL2DRA scheduler.\n */\npublic class Options_LTL2DRA implements Cloneable {\n\n\t/** Constructor */\n\tpublic Options_LTL2DRA() {\n\t\t// Defaults...\n\t\tallow_union=true;\n\t\trecursive_union=true;\n\t\toptimizeAcceptance=true;\n\t\tbisim=false;\n\t\trecursive_bisim=true;\n\t\t// safety=false;\n\n\t\tautomata=AutomataType.RABIN;\n\t\tonly_union=false;\n\t\t// only_safety=false;\n\n\t\tdetailed_states=false;\n\t\tverbose_scheduler=false;\n\t\topt_safra=new Options_Safra();\n\t\t// scheck_path=\"\";\n\t}\n\t\n\tpublic Options_LTL2DRA clone()\n\t{\n\t\tOptions_LTL2DRA rv = new Options_LTL2DRA();\n\t\trv.allow_union = allow_union;\n\t\trv.recursive_union = recursive_union;\n\t\trv.optimizeAcceptance = optimizeAcceptance;\n\t\trv.bisim = bisim;\n\t\trv.recursive_bisim = recursive_bisim;\n\t\t// rv.safety = false;\n\n\t\trv.automata=automata;\n\t\trv.only_union = only_union;\n\t\t// rv.only_safety = false;\n\n\t\trv.detailed_states = detailed_states;\n\t\trv.verbose_scheduler = verbose_scheduler;\n\t\trv.opt_safra = opt_safra.clone(); \n\t\t// rv.scheck_path=scheck_path;\n\t\t\n\t\treturn rv;\n\t}\n\n\t/** Disable all options */\n\tpublic void allFalse() {\n\t\tallow_union\n\t\t=recursive_union\n\n\t\t// =safety\n\n\t\t=optimizeAcceptance\n\t\t=bisim\n\t\t=recursive_bisim\n\n\t\t=only_union\n\t\t// =only_safety\n\t\t=detailed_states\n\t\t=verbose_scheduler\n\t\t=false;\n\t}\n\n\t/** Change options for next level of recursion */\n\tpublic void recursion() {\n\t\tallow_union = allow_union && recursive_union;\n\t\tonly_union = false;\n\n\t\tbisim = bisim && recursive_bisim;\n\t}\n\n\t/** Safra Options */\n\tpublic Options_Safra opt_safra;\n\n\t/** Allow union construction */\n\tpublic boolean allow_union;\n\n\t/** Allow union construction on next levels */\n\tpublic boolean recursive_union;\n\n\t/** Allow using scheck for (co-)safety LTL formulas */\n\t// public boolean safety;\n\n\t/** Allow optimization of acceptance conditions */\n\tpublic boolean optimizeAcceptance;\n\n\t/** Allow bisimulation */\n\tpublic boolean bisim;\n\n\t/** Allow bisimulation on all levels. */\n\tpublic boolean recursive_bisim;\n\n\t/** Provide detailed internal description in the states */\n\tpublic boolean detailed_states;\n\n\t/** Type of the automata that should be generated */\n\tpublic static enum AutomataType {STREETT, RABIN, RABIN_AND_STREETT};\n\tpublic AutomataType automata;\n\n\t/** Use union construction exclusively */\n\tpublic boolean only_union;\n\n\t/** Debug information from the scheduler */\n\tpublic boolean verbose_scheduler;\n\n\t/** Use scheck exclusively */\n\t// public boolean only_safety;\n\t/** Path to scheck */\n\t// String scheck_path;\n}\n\n"
  },
  {
    "path": "prism/src/jltl2dstar/Options_Safra.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/**\n * Options for Safra's algorithm\n */\n\npublic class Options_Safra implements Cloneable {\n\t/** Optimize accepting true loops */\n\tpublic boolean opt_accloop; \n\t/** Optimize all successor accepting */\n\tpublic boolean opt_accsucc; \n\t/** Renaming optimization (templates) */\n\tpublic boolean opt_rename;  \n\t/** Try to reorder Safra trees */\n\tpublic boolean opt_reorder; \n\t/** Use stuttering */\n\tpublic boolean stutter;\n\t/** Check for stutter insensitive */\n\tpublic boolean partial_stutter_check;\n\t/** Perform stutter closure on NBA before conversion */\n\tpublic boolean stutter_closure;\n\t/** Check for DBA */\n\tpublic boolean dba_check;\n\t/** Provide statistics */\n\tpublic boolean stat;\n\t/** Optimize accepting true loops in union construction */\n\tpublic boolean union_trueloop;\n\n\t/** Constructor */\n\tpublic Options_Safra() {\n\t\topt_none();\n\n\t\tdba_check=false;\n\t\t//    tree_verbose=false;\n\t\tstat=false;\n\t\tunion_trueloop=true;\n\n\t\tstutter=false;\n\t\tpartial_stutter_check=false;\n\t\tstutter_closure=false;\n\t}\n\t\n\tpublic Options_Safra clone()\n\t{\n\t\tOptions_Safra rv = new Options_Safra();\n\t\t\n\t\trv.opt_accloop = opt_accloop; \n\t\trv.opt_accsucc = opt_accsucc; \n\t\trv.opt_rename = opt_rename;  \n\t\trv.opt_reorder = opt_reorder; \n\t\trv.stutter = stutter;\n\t\trv.partial_stutter_check = partial_stutter_check;\n\t\trv.stutter_closure = stutter_closure;\n\t\trv.dba_check = dba_check;\n\t\trv.stat = stat;\n\t\trv.union_trueloop = union_trueloop;\n\t\treturn rv;\n\t}\n\n\t/** Enable all opt_ options */\n\tpublic void opt_all() {\n\t\topt_accloop\n\t\t=opt_accsucc\n\t\t=opt_rename\n\t\t=opt_reorder\n\t\t=true;\n\t}\n\n\t/** Disable all opt_ options */\n\tpublic void opt_none() {\n\t\topt_accloop\n\t\t=opt_accsucc\n\t\t=opt_rename\n\t\t=opt_reorder\n\t\t=false;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/RabinAcceptance.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.Vector;\nimport java.util.Iterator;\nimport java.util.NoSuchElementException;\nimport java.io.PrintStream;\n\nimport jltl2ba.MyBitSet;\nimport prism.PrismException;\n\npublic class RabinAcceptance implements Iterable<Integer> {\n\n/**\n * Class storing a Rabin acceptance condition.\n * Contains a number k of pairs of MyBitSets (L_i,U_i), where the states\n * in the acceptance sets L_i and U_i are set.\n */\n\n\t/** The 3 different colors for RabinAcceptance */\n\tpublic enum RabinColor {RABIN_WHITE, RABIN_GREEN, RABIN_RED};\n\t\n\t/** The number of acceptance pairs */\n\tprivate int _acceptance_count;\n\t\t    \n\t/** A vector of MyBitSet* representing the L part of the acceptance pairs. */\n\tprivate Vector<MyBitSet> _acceptance_L;\n\t/** A vector of MyBitSet* representing the U part of the acceptance pairs. */\n\tprivate Vector<MyBitSet> _acceptance_U;\n\n\tboolean _is_compact;\n\t\n\t/**\n\t * Constructor\n\t * @param number_of_initial_pairs The initial numbers of pairs to allocate\n\t */\n\tpublic RabinAcceptance()\n\t{\n\t\t_is_compact = true;\n\t\t_acceptance_L = new Vector<MyBitSet>();\n\t\t_acceptance_U = new Vector<MyBitSet>();\n\t}\n  \n\t/**\n\t * Check if this RabinAcceptance is compact (part of interface AcceptanceCondition).\n\t * @return true iff compact\n\t */\n\tpublic boolean isCompact()\n\t{\n\t\treturn _is_compact;\n\t}\n\n\t/**\n\t * Make this RabinAcceptance compact (part of interface AcceptanceCondition).\n\t */\n\tpublic void makeCompact()\n\t{\n\t\tif (isCompact()) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Compress Acceptance-Pairs \n\t\tint pair_to = 0;\n\t\tfor (int pair_from = 0; pair_from < _acceptance_L.size(); pair_from++) {\n\t\t\tif (_acceptance_L.get(pair_from) != null) {\n\t\t\t\tif (pair_from == pair_to) {\n\t\t\t\t\t// nothing to do\n\t\t\t\t} else {\n\t\t\t\t\t_acceptance_L.set(pair_to, _acceptance_L.get(pair_from));\n\t\t\t\t\t_acceptance_U.set(pair_to, _acceptance_U.get(pair_from));\n\t\t\t\t}\n\t\t\t\tpair_to++;\n\t\t\t}\n\t\t}\n   \n\t\tint new_acceptance_count=pair_to;\n    \n\t\t_acceptance_L.setSize(new_acceptance_count);\n\t\t_acceptance_U.setSize(new_acceptance_count);\n\n\t\t_is_compact = true;\n\t}\n\n\t/** Update the acceptance condition upon renaming of states acording\n\t *  to the mapping (part of AcceptanceCondition interface).\n\t *  Assumes that states can only get a lower name.\n\t * @param mapping vector with mapping a[i] -> j\n\t */\n\tpublic void moveStates(Vector<Integer> mapping) throws PrismException\n\t{\n\t\tif (!isCompact()) {\n\t\t\tmakeCompact();\n\t\t}\n\n\t\tfor (int i = 0; i < size(); i++) {\n\t\t\tmove_acceptance_bits(_acceptance_L.get(i), mapping);\n\t\t\tmove_acceptance_bits(_acceptance_U.get(i), mapping);\n\t\t}\n\t}\n\n\t/**\n\t * Print the Acceptance-Pairs: header (part of interface AcceptanceCondition).\n\t * @param out the output stream.\n\t */\n\tpublic void outputAcceptanceHeader(PrintStream out) throws PrismException {\n\t\tout.println(\"Acceptance-Pairs: \" + size());\n\t}\n\n\t/**\n\t * Print the Acceptance: header in the HOA format\n\t * @param out the output stream.\n\t */\n\tpublic void outputAcceptanceHeaderHOA(PrintStream out) throws PrismException\n\t{\n\t\tout.println(\"acc-name: Rabin \"+size());\n\t\tout.print(\"Acceptance: \" + (size()*2)+\" \");\n\t\tif (size() == 0) {\n\t\t\tout.println(\"f\");\n\t\t\treturn;\n\t\t}\n\n\t\tfor (int pair = 0; pair < size(); pair++) {\n\t\t\tif (pair > 0) out.print(\" | \");\n\t\t\tout.print(\"( Fin(\" + (2*pair) + \") & Inf(\" + (2*pair+1) +\") )\");\n\t\t}\n\t\tout.println();\n\t}\n\n\t/**\n\t * Print the Acc-Sig: line for a state (part of interface AcceptanceCondition).\n\t * @param out the output stream.\n\t * @param state_index the state\n\t */\n\tpublic void outputAcceptanceForState(PrintStream out, int state_index) throws PrismException {\n\t\tout.print(\"Acc-Sig:\");\n\t\tfor (int pair_index = 0; pair_index < size(); pair_index++) {\n\t\t\tif (isStateInAcceptance_L(pair_index, state_index)) {\n\t\t\t\tout.print(\" +\" + pair_index);\n\t\t\t}\n\t\t\tif (isStateInAcceptance_U(pair_index, state_index)) {\n\t\t\t\tout.print(\" -\" + pair_index);\n\t\t\t}\n\t\t}\n\t\tout.println();\n\t}\n\n\t/**\n\t * Print the acceptance signature for a state (HOA format)\n\t * @param out the output stream.\n\t * @param state_index the state\n\t */\n\tpublic void outputAcceptanceForStateHOA(PrintStream out, int state_index) throws PrismException\n\t{\n\t\tString signature = \"\";\n\t\tfor (int pair_index = 0; pair_index < size(); pair_index++) {\n\t\t\tif (isStateInAcceptance_L(pair_index, state_index)) {\n\t\t\t\tsignature += (!signature.isEmpty() ? \" \" :\"\")+(pair_index*2+1);\n\t\t\t}\n\t\t\tif (isStateInAcceptance_U(pair_index, state_index)) {\n\t\t\t\tsignature += (!signature.isEmpty() ? \" \" :\"\")+(pair_index*2);\n\t\t\t}\n\t\t}\n\n\t\tif (!signature.isEmpty()) {\n\t\t\tout.println(\"{\" + signature + \"}\");\n\t\t}\n\t}\n\n\t/**\n\t * Add a state (part of interface AcceptanceCondition).\n\t * @param state_index the index of the added state.\n\t */\n\tpublic void addState(int state_index) {\n\t\t// TODO: Assert that state_index > highest set bit\n\t\t;\n\t}\n\n\t// ---- Rabin/Streett acceptance specific\n\n\t/**\n\t * Creates a new acceptance pair.\n\t * @return the index of the new acceptance pair.\n\t */\n\tpublic int newAcceptancePair() {\n\t\tMyBitSet l = new MyBitSet();\n\t\tMyBitSet u = new MyBitSet();\n\n\t\t_acceptance_L.add(l);\n\t\t_acceptance_U.add(u);\n\n\t\t_acceptance_count++;  \n\t\treturn _acceptance_L.size()-1;\n\t}\n\n\t/**\n\t * Creates count new acceptance pairs.\n\t * @return the index of the first new acceptance pair.\n\t */\n\tpublic int newAcceptancePairs(int count) {\n\t\tint rv = _acceptance_L.size();\n\n\t\tfor (int i = 0; i < count; i++) {\n\t\t\tnewAcceptancePair();\n\t\t}\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Delete an acceptance pair.\n\t */\n\tpublic void removeAcceptancePair(int pair_index) {\n\t\tif (_acceptance_L.get(pair_index) != null) {\n\t\t\t_acceptance_count--;\n\t\t}\n\n\t\t_acceptance_L.set(pair_index, null);\n\t\t_acceptance_U.set(pair_index, null);\n\n\t\t_is_compact = false;\n\t}\n\n\t/**\n\t * Get a reference to the MyBitSet representing L[pair_index], \n\t * allowing changes to this set.\n\t */\n\tpublic MyBitSet getAcceptance_L(int pair_index) {\n\t\treturn _acceptance_L.get(pair_index);\n\t}\n\n\t/**\n\t * Get a reference to the MyBitSet representing U[pair_index], \n\t * allowing changes to this set.\n\t */\n\tpublic MyBitSet getAcceptance_U(int pair_index) {\n\t\treturn _acceptance_U.get(pair_index);\n\t}\n\n\n\t/**\n\t * Get the L part of the acceptance signature for a state (changes to the\n\t * MyBitSet do not affect the automaton).\n\t */\n\tpublic MyBitSet getAcceptance_L_forState(int state_index) {\n\t\treturn getMyBitSetForState(state_index, _acceptance_L);\n\t}\n\n\t/**\n\t * Get the U part of the acceptance signature for a state (changes to the\n\t * MyBitSet do not affect the automaton).\n\t */\n\tpublic MyBitSet getAcceptance_U_forState(int state_index) {\n\t\treturn getMyBitSetForState(state_index, _acceptance_U);\n\t}\n\n\t/** Is a certain state in L[pair_index]? */\n\tpublic boolean isStateInAcceptance_L(int pair_index, int state_index) {\n\t\treturn _acceptance_L.get(pair_index).get(state_index);\n\t}\n\n\t/** Is a certain state in U[pair_index]? */\n\tpublic boolean isStateInAcceptance_U(int pair_index, int state_index) {\n\t\treturn _acceptance_U.get(pair_index).get(state_index);\n\t}\n\n\t/** Set L[pair_index] for this state to value. */\n\tvoid stateIn_L(int pair_index, int state_index,\tboolean value) {\n\t\tgetAcceptance_L(pair_index).set(state_index,value);\n\t}\n\n\t/** Set U[pair_index] for this state to value. */\n\tvoid stateIn_U(int pair_index, int state_index, boolean value) {\n\t\tgetAcceptance_U(pair_index).set(state_index,value);\n\t}\n\n\t/** Get the number of acceptance pairs. \n\t *  Requires the acceptance pairs to be compact. */\n\tpublic int size() throws PrismException {\n\t\tif (!isCompact()) {\n\t\t\tthrow new PrismException(\"Can't give acceptance pair count for uncompacted condition\");\n\t\t}\n\t\treturn _acceptance_L.size();\n\t}\n\n\t/** Calculate the MyBitSet for a state from the acceptance pairs, store\n\t *  result in result.\n\t *  @param state_index the state\n\t *  @param acc the MyBitSetVector (either _L or _U)\n\t *  @param result the MyBitSet where the results are stored, has to be clear \n\t *                at the beginning!\n\t */\n\tprivate MyBitSet getMyBitSetForState(int state_index, Vector<MyBitSet> acc) {\n\t\t\n\t\tMyBitSet result = new MyBitSet(acc.size());\n\n\t\tfor (int i = 0; i < acc.size(); i++) {\n\t\t\tif (acc.get(i) != null) {\n\t\t\t\tif (acc.get(i).get(state_index)) {\n\t\t\t\t\tresult.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn result;\n\t}\n\n\t/** \n\t * Move the bits set in acc to the places specified by mapping.\n\t */\n\tprivate void move_acceptance_bits(MyBitSet acc, Vector<Integer> mapping) throws PrismException {\n\t\t\n\t\tint i = acc.nextSetBit(0);\n\t\twhile (i != -1) {\n\t\t\tint j = mapping.get(i);\n\t\t\t// :: j is always <= i\n\t\t\tif (j > i) {\n\t\t\t\tthrow new PrismException(\"Wrong mapping in move_acceptance_bits\");\n\t\t\t}\n\n\t\t\tif (i == j) {\n\t\t\t\t// do nothing\n\t\t\t} else {\n\t\t\t\t// move bit from i->j\n\t\t\t\tacc.set(j);\n\t\t\t\tacc.clear(i);\n\t\t\t}\n\t\t\ti = acc.nextSetBit(i + 1);\n\t\t}\n\t}\n\t\n\tpublic Iterator<Integer> iterator() {\n\t\treturn new AcceptancePairIterator(_acceptance_L);\n\t}\n\t\n\tpublic static class AcceptancePairIterator implements Iterator<Integer> {\n\t\tprivate Vector<MyBitSet> _acceptance_vector;\n\t\tprivate int index;\n\t\t\n\t\tpublic AcceptancePairIterator(Vector<MyBitSet> acceptance_vector) {\n\t\t\t_acceptance_vector = acceptance_vector;\n\t\t\tindex = 0;\n\t\t}\n\t\t\n\t\tpublic boolean hasNext() {\n\t\t\treturn (index < _acceptance_vector.size());\n\t\t}\n\t\t\n\t\tpublic Integer next() throws NoSuchElementException {\n\t\t\tif (hasNext()) {\n\t\t\t\tInteger rv = Integer.valueOf(index);\n\t\t\t\tincrement();\n\t\t\t\treturn rv;\n\t\t\t}\n\t\t\telse throw new NoSuchElementException();\n\t\t}\n\t\t\t\n\t\tprivate void increment() {\n\t\t\tindex++;\n\t\t\twhile ((index < _acceptance_vector.size()) && (_acceptance_vector.get(index) == null))\n\t\t\t\tindex++;\n\t\t}\n\t\t\n\t\tpublic void remove() throws UnsupportedOperationException {\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/RabinSignature.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport jltl2ba.MyBitSet;\n\n/** A class storing the acceptance signature for a state\n * (for every acceptance pair one color).\n */\npublic class RabinSignature implements Comparable<RabinSignature> {\n\n\t/** The L part */\n    private MyBitSet _L;\n    /** The U part */\n    private MyBitSet _U;    \n    /** The number of acceptance pairs */\n    private int _size;\n    \n\t/** Constructor \n\t * @param size the number of acceptance pairs \n\t */\n\tpublic RabinSignature(int size) {\n\t\t_size = size;\n\t\t_L = new MyBitSet(size);\n\t\t_U = new MyBitSet(size);\n\t}\n\n\t/** Constructor\n\t * @param other another RabinSignature\n\t */\n\tpublic RabinSignature(RabinSignature other) {\n\t\t_L = (MyBitSet) other._L.clone();\n\t\t_U = (MyBitSet) other._U.clone();\n\t\t_size = other._size;\n\t}\n\n\t/** Constructor\n\t * @param L the L part of the acceptance signature.\n\t * @param U the U part of the acceptance signature.\n\t * @param size the number of acceptance pairs\n\t */\n\tpublic RabinSignature(MyBitSet L, MyBitSet U, int size) { \n\t  _L = L;\n\t  _U = U;\n\t  _size = size;\n\t}\n\t    \n\t/** Constructor for getting the acceptance signature for a Tree.\n\t * @param tree the Tree, get acceptance signature from \n\t *    tree.generateAcceptance(*this).\n\t */\n\tpublic <Tree extends SafraTree> RabinSignature(Tree tree) {\n\t\tthis(0);\n\t\ttree.generateAcceptance(this);\n\t}\n\n\t/** Clear the acceptance signature */\n\tpublic void clear() {\n\t\t_L.clear();\n\t\t_U.clear();\n\t}\n\n\t/** Get the L part of this acceptance signature */\n\tpublic MyBitSet getL() {return _L;}    \n\t/** Get the U part of this acceptance signature */\n\tpublic MyBitSet getU() {return _U;}\n\n\t/** Set index to value in the L part of this acceptance signature. */\n\tpublic void setL(int index, boolean value) {\n\t\t_L.set(index, value);\n\t}\n\n\t/** Set index to value. in the U part of this acceptance signature. */\n\tpublic void setU(int index, boolean value) {\n\t\t_U.set(index, value);\n\t}\n\n\t/** Set the L and U parts according to RabinColor c. \n\t * @param i The pair index\n\t * @param c the RabinColor\n\t */\n\tpublic void setColor(int i, RabinAcceptance.RabinColor c) {\n\t\tswitch (c) {\n\t\tcase RABIN_RED:\n\t\t\t_U.set(i, true);\n\t\t\t_L.set(i, false);\n\t\t\tbreak;\n\n\t\tcase RABIN_GREEN:\n\t\t\t_U.set(i, false);\n\t\t\t_L.set(i, true);\n\t\t\tbreak;\n\n\t\tcase RABIN_WHITE:\n\t\t\t_U.set(i, false);\n\t\t\t_L.set(i, false);\n\t\t\tbreak;\n\t\t}\n\t}\n\n\t/** Get the RabinColor for a pair i */\n\tpublic RabinAcceptance.RabinColor getColor(int i) {\n\t\treturn _U.get(i) ? RabinAcceptance.RabinColor.RABIN_RED : (_L.get(i) ? RabinAcceptance.RabinColor.RABIN_GREEN : RabinAcceptance.RabinColor.RABIN_WHITE);\n\t}\n\n\t/** Get string representation of this signature. */\n\tpublic String toString() {\n\t\tString a;\n\t\ta=\"{\";\n\t\tfor (int i = 0; i < size(); i++) {\n\t\t\tswitch (getColor(i)) {\n\t\t\tcase RABIN_RED:\n\t\t\t\ta += \"-\" + i;\n\t\t\t\tbreak;\n\t\t\tcase RABIN_GREEN:\n\t\t\t\ta += \"+\" + i;\n\t\t\t\tbreak;\n\t\t\tcase RABIN_WHITE:\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\ta += \"}\";\n\t      \n\t\treturn a;\n\t}\n\n\t    /** Compare to other signature for equality. */\n\tpublic boolean equals(RabinSignature other) {\n\t\treturn (_L.equals(other.getL()) &&  _U.equals(other.getU()));\n\t}\n\t\n\tpublic boolean equals(Object other)\t{\n\t\treturn ((other instanceof RabinSignature) && this.equals((RabinSignature) other));\n\t}\n\n\t/** Compare to other signature */\n\tpublic int compareTo(RabinSignature other) {\n\t\tint i = _L.compareTo(other.getL());\n\t\tif (i != 0)\n\t\t\treturn i;\n\t\telse \n\t\t\treturn _U.compareTo(other.getU());\n\t}\n\t\n\t/** Get the number of acceptance pairs */\n\tpublic int getSize() {return _size;}\n\t/** Get the number of acceptance pairs */\n\tpublic int size() {return _size;}\n\n\t/** Set the number of acceptance pairs */\n\tpublic void setSize(int size) {_size=size;}\n\n\t/** Merge this acceptance signature with other signature,\n\t *  for each tuple element calculate the maximum of the\n\t *  colors according to the order \n\t * RABIN_WHITE < RABIN_GREEN < RABIN_RED */\n\tpublic void maxMerge(RabinSignature other) {\n\t\tfor (int i = 0; i < _size; i++) {\n\t\t\tif (getColor(i).compareTo(other.getColor(i)) < 0) {\n\t\t\t\tsetColor(i, other.getColor(i));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Calculate a hash value using HashFunction\n\t * @param hashfunction the HashFunction\n\t */\n\t// public int hashCode() {\n\t// return _L.hashCode() + _U.hashCode();\n\t// }\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/SCCs.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.Vector;\nimport java.io.PrintStream;\n\nimport jltl2ba.MyBitSet;\n\n\npublic class SCCs {\n\n\t/**\n\t * A class for storing information about the Strongly Connected Components (SCCs)\n\t * of a graph\n\t */\n\tpublic Vector<MyBitSet> _sccs;\n\tpublic Vector<Integer> _state_to_scc;\n\tpublic Vector<MyBitSet> _dag;\n\tpublic Vector<Integer> _topological_order;\n\tpublic Vector<MyBitSet> _reachability;\n\tpublic boolean _graph_is_disjoint;\n\n\n\t/** Constructor */\n\tpublic SCCs() {\n\t\t_sccs = new Vector<MyBitSet>();\n\t\t_state_to_scc = new Vector<Integer>();\n\t\t_dag = new Vector<MyBitSet>();\n\t\t_topological_order = new Vector<Integer>();\n\t\t_reachability = new Vector<MyBitSet>();\n\t\t_graph_is_disjoint = false;\n\t}\n\t\n\t/** Get the states that are in SCC scc_index */\n\tpublic MyBitSet get(int scc_index) {\n\t\treturn _sccs.get(scc_index);\n\t}\n\n\t/** Get the number of SCCs */\n\tpublic int countSCCs() {return _sccs.size();}\n\n\t/** Get the SCC index for state */\n\tpublic int state2scc(int state) {\n\t\treturn _state_to_scc.get(state);\n\t}\n\n\t/** Get a vector with a topological order of the states*/\n\tVector<Integer> topologicalOrder() {\n\t\treturn _topological_order;\n\t}\n\n\t/** Get a set of SCCs that are successors of the SCC scc_index */\n\tMyBitSet successors(int scc_index) {\n\t\treturn _dag.get(scc_index);\n\t}\n\n\t/** Return true, if state_to is reachable from state_from */\n\tpublic boolean stateIsReachable(int state_from, int state_to) {\n\t\treturn isReachable(state2scc(state_from), state2scc(state_to));\n\t}\n\n\t/** Return true, if SCC scc_to is reachable from SCC_fromom */\n\tpublic boolean isReachable(int scc_from, int scc_to) {\n\t\treturn _reachability.get(scc_from).get(scc_to);\n\t}\n\n\t/** Print the SCCs on the output stream */\n\tpublic void print(PrintStream out) {\n\t\tout.println(\"SCC:\");\n\n\t\tfor (int i = 0; i < this.countSCCs(); i++) {\n\t\t\tint scc_i = this._topological_order.get(i);\n\n\t\t\tout.println(scc_i + \" : \" + get(scc_i));\n\t\t}\n\t}\n\n\t/** Get a vector of BitSets with reachability information \n\t * (state -> reachable_states)\n\t */\n\tpublic Vector<MyBitSet> getReachabilityForAllStates() {\n\t\tVector<MyBitSet> v = new Vector<MyBitSet>();\n\t\tv.setSize(_state_to_scc.size());\n\n\t\tfor (int i = 0; i < _state_to_scc.size(); ++i) {\n\t\t\tint scc = state2scc(i);\n\t\t\tMyBitSet reachable_sccs = _reachability.get(scc);\n\n\t\t\tMyBitSet reachable_states = new MyBitSet();\n\t\t\tfor (Integer it : reachable_sccs) {\n\t\t\t\t// union with all states from the reachable scc\n\t\t\t\treachable_states.or(_sccs.get(it));\n\t\t\t}      \n\n\t\t\tv.set(i, reachable_states);\n\n\t\t\t//      std::cerr << \"from \"<<i<<\": \"<<reachable_states<<std::endl;\n\t\t}\n\t\treturn v;\n\t}\n\n\t//  friend class GraphAlgorithms::SCC_DFS;\n\n\t/** Add a new SCC */\n\tpublic int addSCC(MyBitSet scc) {\n\t\t_sccs.add(scc);\n\t\treturn _sccs.size() - 1;\n\t}\n\n\t/** Set the SCC for a state */\n\tpublic void setState2SCC(int state, int scc) {\n\t\tif (_state_to_scc.size() <= state) {\n\t\t\t_state_to_scc.setSize(state + 1);\n\t\t}\n\t\t_state_to_scc.set(state, Integer.valueOf(scc));\n\t}\n\n\t/** Set flag that the graph was discovered to be disjoint */\n\tpublic void setGraphIsDisjoint() {\n\t\t_graph_is_disjoint = true;\n\t}\n\t\n\t/** Get flag wether the graph was discovered to be disjoint */\n\tpublic boolean getGraphIsDisjoint() {\n\t\treturn _graph_is_disjoint;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/SafraNBA2DRA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** @file\n * Provides class NBA2DA, which converts an NBA to a DA\n */\nimport java.util.Stack;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APElementIterator;\nimport jltl2ba.APSet;\nimport prism.PrismException;\n\n/**\n * Convert an NBA to a DA using the specified Algorithm_t and StateMapper_t\n */\n//template < typename Algorithm_t, \n//typename DA_t,\n//typename StateMapper_t=StateMapper<typename Algorithm_t::result_t,\n//typename Algorithm_t::state_t,\n//typename DA_t::state_type> >\npublic class SafraNBA2DRA {\n\t\n\t/** Save detailed information on the Safra trees in the states? */\n\tprivate boolean _detailed_states;\n\n\t/** \n\t * Constructor\n\t * detailedStates default = false \n\t */\n\tpublic SafraNBA2DRA(boolean detailedStates) {\n\t\t_detailed_states = detailedStates;\n\t}\n\n\t/**\n\t * Generate a DA using the Algorithm\n\t * Throws LimitReachedException if a limit is set (>0) and\n\t * there are more states in the generated DA than the limit. \n\t * @param algo the algorithm \n\t * @param da_result the DA where the result is stored \n\t *        (has to have same APSet as the nba)\n\t * @param limit a limit for the number of states (0 disables the limit - default).\n\t */\n\tpublic void convert(SafrasAlgorithm algo, DRA da_result, int limit, StateMapperInterface<SafraTreeTemplate,SafraTree,DA_State> state_mapper) throws PrismException {\n\n\t\tAPSet ap_set = da_result.getAPSet();\n\n\t\tif (algo.checkEmpty()) {\n\t\t\tda_result.constructEmpty();\n\t\t\treturn;\n\t\t}\n\n//\t\ttypedef typename DA_t::state_type da_state_t;\n//\t\ttypedef typename Algorithm_t::state_t algo_state_t;\n//\t\ttypedef typename Algorithm_t::result_t algo_result_t;\n\n\t\talgo.prepareAcceptance(da_result.acceptance());\n\n\t\tSafraTree start = algo.getStartState();\n\t\tDA_State start_state = da_result.newState();\n\t\tstart.generateAcceptance(start_state.acceptance());\n\t\tif (_detailed_states) {\n\t\t\tstart_state.setDescription(start.toHTML());\n\t\t}\n\n\t\tstate_mapper.add(start, start_state);\n\t\tda_result.setStartState(start_state);\n\n\t\tStack<unprocessed_value> unprocessed = new Stack<unprocessed_value>();\n\t\tunprocessed.push(new unprocessed_value(start, start_state));\n\n\t\twhile (!unprocessed.empty()) {\n\t\t\t// System.out.println(\"Stack: \" + unprocessed.size());\n\t\t\tunprocessed_value top = unprocessed.pop();\n\n\t\t\tSafraTree cur = top.algo_state;\n\t\t\tDA_State from = top.da_state;\n\t\t\t\n\t\t\t// System.out.println(\"Powerset size \" + ap_set.powersetSize());\n\t\t\tfor (APElementIterator it_elem = new APElementIterator(ap_set.size()); it_elem.hasNext(); ) {\n\t\t\t\tAPElement elem = it_elem.next();\n\t\t\t\tSafraTreeTemplate result = algo.delta(cur, elem);\n\t\t\t\tDA_State to = state_mapper.find(result);\n\t\t\t\tif (to == null) {\n\t\t\t\t\tto = da_result.newState();\n\t\t\t\t\tresult.getState().generateAcceptance(to.acceptance());\n\t\t\t\t\tif (_detailed_states) {\n\t\t\t\t\t\tto.setDescription(result.getState().toHTML());\n\t\t\t\t\t}\n\t\t\t\t\tstate_mapper.add(result.getState(), to);\n\t\t\t\t\tunprocessed.push(new unprocessed_value(result.getState(), to));\n\t\t\t\t}\n\t\t\t\tfrom.edges().put(elem, to);\n\t\t\t\tif (limit != 0 && da_result.size() > limit) {\n\t\t\t\t\tthrow new PrismException(\"State limit reached\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t}\n\n\tprivate class unprocessed_value {\n\t\tpublic SafraTree algo_state;\n\t\tpublic DA_State da_state;\n\t\t\n\t\tpublic unprocessed_value(SafraTree _algo_state, DA_State _da_state) {\n\t\t\talgo_state = _algo_state;\n\t\t\tda_state = _da_state;\n\t\t}\n\t}\n}\n\n\n\n"
  },
  {
    "path": "prism/src/jltl2dstar/SafraTree.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.Vector;\nimport java.io.PrintStream;\n\nimport jltl2ba.MyBitSet;\n\n/** \n * A Safra tree, an ordered tree of SafraTreeNodes.\n */\npublic class SafraTree implements NBA2DAState {\n\n\t/** The maximum number of nodes */\n\tprivate int MAX_NODES;\n\t/** An array to store the nodes */\n\tprivate Vector<SafraTreeNode> _nodes;\n\n\t/** \n\t * Constructor.\n\t * @param N the maximum number of nodes.\n\t */\n\tpublic SafraTree(int N) {\n\t\tMAX_NODES = (N == 0 ? 1 : N);\n\t\t_nodes = new Vector<SafraTreeNode>(MAX_NODES);\n\t\t_nodes.setSize(MAX_NODES);\n\n\t\t// create root-node\n\t\tnewNode(0);\n\t}\n\n\t/** Copy constructor. */\n\tpublic SafraTree(SafraTree other) {\n\t\tMAX_NODES = other.MAX_NODES;\n\n\t\t_nodes = new Vector<SafraTreeNode>(MAX_NODES);\n\t\t_nodes.setSize(MAX_NODES);\n\t\tfor (int i = 0; i < MAX_NODES; i++) {\n\t\t\tif (other._nodes.get(i) != null) {\n\t\t\t\tnewNode(i);\n\t\t\t\t_nodes.get(i).setLabeling((MyBitSet) other._nodes.get(i).getLabeling().clone());\n\t\t\t\t_nodes.get(i).setFinalFlag(other._nodes.get(i).hasFinalFlag());\n\t\t\t}\n\t\t}\n\n\t\tcopySubTree(_nodes.get(0), other._nodes.get(0));\n\t}\n\t\n\t/** Get the root node of the tree. */\n\tpublic SafraTreeNode getRootNode() {return _nodes.get(0);}\n\n\t/** Create a new node. The name is the next free node name. */\n\tpublic SafraTreeNode newNode() {\n\t\tif (_nodes.indexOf(null) != -1)\n\t\t\treturn newNode(_nodes.indexOf(null));\t// FIXME: hmm, inconsistent with newNode(int)\n\t\telse return null;\n\t}\n\n\t/** Create a new node with name <i>id</i>. */\n\tpublic SafraTreeNode newNode(int id) {\n\t\tassert(id < MAX_NODES);\n\t\tassert(_nodes.get(id) == null);\n\n\t\t_nodes.set(id,new SafraTreeNode(id));\n\n\t\treturn _nodes.get(id);\n\t}\n\n\t/** \n\t * Remove a SafraTreeNode from the tree, \n\t * the node can have no children.\n\t */\n\tpublic void remove(SafraTreeNode node) {\n\t\tassert(_nodes.get(node.getID()) == node);\n\t\tremove(node.getID());\n\t}\n\n\t/** \n\t * Remove the SafraTreeNode <i>id</i> from the tree,\n\t * the node can have no children.\n\t */\n\tpublic void remove(int id) {\n\t\tassert(id >= 0 && id < MAX_NODES);\n\n\t\t_nodes.get(id).removeFromTree();\n\t\t_nodes.set(id, null);\n\t}\n\n\n\t/**\n\t * Remove all children of the SafraTreeNode <i>id</i>.\n\t */\n\tpublic void removeAllChildren(int id) {\n\t\tassert(id < MAX_NODES);\n\n\t\tSafraTreeNode n = _nodes.get(id);\n\t\tSafraTreeNode child;\n\t\twhile ((child = n.getOldestChild()) != null) {\n\t\t\tremoveAllChildren(child.getID());\n\t\t\tremove(child.getID());\n\t\t}\n\t}\n\n\t/** \n\t * Walk the tree post-order, calling the function \n\t * void visit(SafraTree& tree, SafraTreeNode *node) \n\t * in the SafraTreeVisitor on each node.\n\t */\n\tpublic <V extends SafrasAlgorithm.SafraTreeVisitor> void walkTreePostOrder(V visitor) {\n\t\tSafraTreeWalker<V> stw = new SafraTreeWalker<V>(visitor);\n\t\tstw.walkTreePostOrder(this);\n\t}\n\n\t/** \n\t * Walk the subtree rooted under node *top post-order, \n\t * calling the function void visit(SafraTree& tree, SafraTreeNode *node) \n\t * in the SafraTreeVisitor on each node.\n\t */\n\tpublic <V extends SafrasAlgorithm.SafraTreeVisitor> void walkSubTreePostOrder(V visitor, SafraTreeNode top) {\n\t\tSafraTreeWalker<V> stw = new SafraTreeWalker<V>(visitor);\n\t\tstw.walkSubTreePostOrder(this, top, true);\n\t}\n\n\t/** \n\t * Walk the subtree rooted under node *top (only the children, not *top itself) \n\t * post-order, calling the function void visit(SafraTree& tree, SafraTreeNode *node) \n\t * in the SafraTreeVisitor on each node.\n\t */\n\tpublic <V extends SafrasAlgorithm.SafraTreeVisitor> void walkChildrenPostOrder(V visitor, SafraTreeNode top) {\n\t\tSafraTreeWalker<V> stw = new SafraTreeWalker<V>(visitor);\n\t\tstw.walkSubTreePostOrder(this, top, false); // = don't visit top\n\t}\n\n\n\t/**\n\t * Calculate the height of the tree.\n\t */\n\tpublic int treeHeight() {\n\t\tif (getRootNode() != null) {\n\t\t\treturn getRootNode().treeHeight();\n\t\t}\n\t\treturn 0;\n\t}\n\n\n\t/**\n\t * Calculate the width of the tree.\n\t */\n\tpublic int treeWidth() {\n\t\tif (getRootNode() != null) {\n\t\t\treturn getRootNode().treeWidth();\n\t\t}\n\t\treturn 0;\n\t}\n\n\t/**\n\t * Equality operator.\n\t */\n\tpublic boolean equals(SafraTree other) {\n\t\tif (other.MAX_NODES != MAX_NODES) {return false;}\n\t\treturn _nodes.equals(other._nodes);\n\t}\n\n\tpublic boolean equals(Object other) {\n\t\tif (other instanceof SafraTree)\n\t\t\treturn this.equals((SafraTree) other);\n\t\telse return false;\n\t}\n\t\t\n\t/**\n\t * Checks equality when ignoring the node names.\n\t */\n\tpublic boolean structural_equal_to(SafraTree other) {\n\t\tif (other.MAX_NODES!=MAX_NODES) {return false;}\n\n\t\tSafraTreeNode this_root = this.getRootNode();\n\t\tSafraTreeNode other_root = other.getRootNode();\n\n\t\tif (this_root == null || other_root == null) {\n\t\t\t// return true if both are 0\n\t\t\treturn (this_root==other_root);\n\t\t}\n\n\t\treturn this_root.structuralEquals(other_root);\n\t}\n\n\t/**\n\t * Less-than operator when ignoring the node names.\n\t */\n\tpublic boolean structural_less_than(SafraTree other) {\n\t\tif (other.MAX_NODES<MAX_NODES) {return true;}\n\n\t\tSafraTreeNode this_root = this.getRootNode();\n\t\tSafraTreeNode other_root = other.getRootNode();\n\n\t\tif (this_root == null) {\n\t\t\tif (other_root!= null) {\n\t\t\t\treturn true;\n\t\t\t} else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t} else { // this_root !=0 \n\t\t\tif (other_root == null) {return false;}\n\n\t\t\treturn this_root.structuralLessThan(other_root);\n\t\t}\n\t}\n\n\t/**\n\t * Less-than operator\n\t */\n\tpublic boolean lessThan(SafraTree other) {\n\t\tif (MAX_NODES < other.MAX_NODES) {return true;}\n\n\t\tfor (int i = 0; i < MAX_NODES; i++) {\n\t\t\tif (_nodes.get(i) == null && other._nodes.get(i) == null) {\n\t\t\t\t;\n\t\t\t} else if (_nodes.get(i) == null) {\n\t\t\t\treturn true;\n\t\t\t} else if (other._nodes.get(i) == null) {\n\t\t\t\treturn false;\n\t\t\t} else {\n\t\t\t\tif (_nodes.get(i).lessThan(other._nodes.get(i))) {\n\t\t\t\t\treturn true;\n\t\t\t\t} else if (_nodes.get(i).equals(other._nodes.get(i))) {\n\t\t\t\t\t;\n\t\t\t\t} else {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** Get the maximum number of nodes. */\n\tpublic int getNodeMax() {return MAX_NODES;}\n\n\t/** Get SafraTreeNode with index <i>i</i>*/\n\tpublic SafraTreeNode get(int i) {\n\t\treturn _nodes.get(i);\n\t}\n\n\tpublic void set(int i, SafraTreeNode node) {\n\t\t_nodes.set(i, node);\n\t}\n\n\t/** Print the SafraTree on an output stream. */\n\tpublic void print(PrintStream out) {\n\t\tif (getRootNode() == null) {\n\t\t\tout.println(\"<empty>\");\n\t\t} else {\n\t\t\tprintSubTree(out, 0, getRootNode());\n\t\t}\n\t}\n\n\t/** Returns a string representation of the SafraTree */\n\t// public String toString() {\n\t// std::ostringstream buf;\n\t// buf << *this;\n\t// return buf.str();\n\t// }\n\n\t/** Returns a string representation in HTML of the SafraTree */\n\tpublic String toHTML() {\n\t\tif (getRootNode() == null) {\n\t\t\treturn \"<TABLE><TR><TD>[empty]</TD></TR></TABLE>\";\n\t\t} else {\n\t\t\treturn getRootNode().toHTMLString();\n\t\t}\n\t}\n\n\t/**\n\t * Calculate a hash value using HashFunction\n\t * @param hashfunction the HashFunction\n\t * @param only_structure ignore the nameing of the nodes\n\t */\n\t// template <class HashFunction>\n\t// public void hashCode(HashFunction& hashfunction,\n\t// \t\tbool only_structure=false) {\n\t// SafraTreeNode* root=getRootNode();\n\t// \n\t// \t\tif (root!=0) {\n\t// \t\t\troot->hashCode(hashfunction, only_structure);\n\t// \t\t}\n\t// }\n\t\n\tpublic int hashCode() {\n\t\tif (getRootNode() != null)\n\t\t\treturn getRootNode().hashCode();\n\t\telse return 0;\n\t}\n\n\t/**\n\t * Generate the appropriate acceptance signature for Rabin Acceptance for this tree  \n\t */\n\tpublic void generateAcceptance(AcceptanceForState acceptance) {\n\t\tfor (int i = 0; i < getNodeMax(); i++) {\n\t\t\tSafraTreeNode stn = this.get(i);\n\t\t\tif (stn == null) {\n\t\t\t\tacceptance.addTo_U(i);\n\t\t\t} else {\n\t\t\t\tif (stn.hasFinalFlag()) {\n\t\t\t\t\tacceptance.addTo_L(i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void generateAcceptance(RabinSignature acceptance) {\n\t\tacceptance.setSize(getNodeMax());\n\t\tfor (int i = 0; i < getNodeMax(); i++) {\n\t\t\tSafraTreeNode  stn = this.get(i);\n\t\t\tif (stn == null) {\n\t\t\t\tacceptance.setColor(i, RabinAcceptance.RabinColor.RABIN_RED);\n\t\t\t} else {\n\t\t\t\tif (stn.hasFinalFlag()) {\n\t\t\t\t\tacceptance.setColor(i, RabinAcceptance.RabinColor.RABIN_GREEN);\n\t\t\t\t} else {\n\t\t\t\t\tacceptance.setColor(i, RabinAcceptance.RabinColor.RABIN_WHITE);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic RabinSignature generateAcceptance() {\n\t\tRabinSignature s = new RabinSignature(getNodeMax());\n\t\tgenerateAcceptance(s);\n\t\treturn s;\n\t}\n\n\n\t/**\n\t * Copy the subtree (the children) of *other\n\t * to *top, becoming the children of *top\n\t */\n\tprivate void copySubTree(SafraTreeNode top, SafraTreeNode other) {\n\t\tif (other == null) {return;}\n\n\t\tfor (SafraTreeNode child : other) {\n\t\t\tSafraTreeNode n = _nodes.get(child.getID());\n\t\t\ttop.addAsYoungestChild(n);\n\t\t\tcopySubTree(n, child);\n\t\t}\n\t}\n\n\t/**\n\t * Print the subtree rooted at node *top to the output stream\n\t * @param out the output stream\n\t * @param prefix the number of spaces ' ' in front of each node\n\t * @param top the current tree sub root\n\t */\n\tprivate void printSubTree(PrintStream out, int prefix, SafraTreeNode top) {\n\t\tfor (int i = 0; i < prefix; i++) {\n\t\t\tout.print(\" \");\n\t\t}\n\t\ttop.print(out);\n\t\tout.println();\n\n\t\tfor (SafraTreeNode child : top) {\n\t\t\tprintSubTree(out, prefix+1, child);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/SafraTreeCandidateMatcher.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/**\n * Provides CandidateMatcher for SafraTrees\n */\npublic class SafraTreeCandidateMatcher {\n\n\tpublic static boolean isMatch(SafraTreeTemplate temp, SafraTree tree) {\n\t\treturn temp.matches(tree);\n\t}\n\n\tpublic static boolean abstract_equal_to(SafraTree t1, SafraTree t2) {\n\t\treturn t1.structural_equal_to(t2);\n\t}\n\n\tpublic static boolean abstract_less_than(SafraTree t1, SafraTree t2) {\n\t\treturn t1.structural_less_than(t2);\n\t}\n\t\n\tpublic static int hash(SafraTree t1) {\n\t\treturn t1.hashCode();\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/SafraTreeNode.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.Iterator;\nimport java.io.PrintStream;\n\nimport jltl2ba.MyBitSet;\n\n/** @file\n * Provides class SafraTreeNode.\n */\n\n/**\n * A node in a SafraTree.\n * Each node has: <br>\n * - a name/id (integer)<br>\n * - a final flag (bool)<br>\n * - a parent (NULL for root node)<br>\n * - an older brother (NULL if node is oldest)<br>\n * - a younger brother (NULL if node is youngest)<br>\n * - an oldestChild (NULL if node has no children<br>\n * - a youngestChild (NULL if node has no children<br>\n * - a label (BitSet) for the powerset \n */\npublic class SafraTreeNode implements Iterable<SafraTreeNode> {\n\n\t/** The node name */\n\tprivate int _id;\n\n\t/** The label of the node (powerset) */\n\tprivate MyBitSet _labeling;\n\n\t/** The final flag */\n\tprivate boolean _final_flag;\n\n\t/** The parent node */\n\tprivate SafraTreeNode _parent;\n\n\t/** The older brother */\n\tprivate SafraTreeNode _olderBrother;\n\n\t/** The younger brother */\n\tprivate SafraTreeNode _youngerBrother;\n\n\t/** The oldest child */\n\tprivate SafraTreeNode _oldestChild;\n\n\t/** The youngest child */\n\tprivate SafraTreeNode _youngestChild;\n\n\t/** The number of children */\n\tprivate int _childCount;\n\n\t/** \n\t * Constructor \n\t * @param id the name of the node\n\t */\n\tpublic SafraTreeNode(int id) {\n\t\t_id = id;\n\t\t_final_flag = false;\n\t\t_parent = null;\n\t\t_olderBrother = null;\n\t\t_youngerBrother = null;\n\t\t_oldestChild = null;\n\t\t_youngestChild = null;\n\t\t_childCount = 0;\n\t\t_labeling = new MyBitSet();\n\t}\n\n\t/** Get the name of the node*/\n\tpublic int getID() {return _id;}\n\n\t/** Get the final flag */\n\tpublic boolean hasFinalFlag() {return _final_flag;}\n\n\t/** Get the number of children. */\n\tpublic int getChildCount() {return _childCount;}\n\n\t/** Get the labeling */\n\tpublic MyBitSet getLabeling() {return _labeling;}\n\n\t/** \n\t * Get the older brother.\n\t * @return the older brother, or NULL if node is oldest child.\n\t */\n\tpublic SafraTreeNode getOlderBrother() {return _olderBrother;}\n\n\t/** \n\t * Get the younger brother.\n\t * @return the younger brother, or NULL if node is youngest child.\n\t */\n\tpublic SafraTreeNode getYoungerBrother() {return _youngerBrother;}\n\n\t/** \n\t * Get the oldest child.\n\t * @return the oldest child, or NULL if node has no children\n\t */\n\tpublic SafraTreeNode getOldestChild() {return _oldestChild;}\n\n\t/** \n\t * Get the youngest child.\n\t * @return the youngest child, or NULL if node has no children\n\t */\n\tpublic SafraTreeNode getYoungestChild() {return _youngestChild;}\n\n\t/** \n\t * Get the parent of the node.\n\t * @return the parent, or NULL if node has no parent (is root node)\n\t */\n\tpublic SafraTreeNode getParent() {return _parent;}\n\n\t/** \n\t * Set the final flag.\n\t * @param finalFlag the value\n\t */\n\tpublic void setFinalFlag(boolean finalFlag) {_final_flag=finalFlag;}\n\t\n\t/** \n\t * Set the labeling \n\t * @param labeling the new labeling\n\t */\n\tpublic void setLabeling(MyBitSet labeling) {_labeling=labeling;}\n\n\tprivate boolean null_or_eq(SafraTreeNode a, SafraTreeNode b) {\n\t\treturn (a == null && b == null) || ((a != null && b != null) && (a.getID() == b.getID()));\n\t}\n\n\t/** Equality operator. Does not do a deep compare */\n\tpublic boolean equals(SafraTreeNode other) {\n\t\tif (_id != other._id) {return false;}\n\t\tif (_final_flag != other._final_flag) {return false;}\n\t\tif (_childCount != other._childCount) {return false;}\n\t\tif (!_labeling.equals(other._labeling)) {return false;}\n\t\tif (!null_or_eq(_parent, other._parent)) {return false;}\n\t\tif (!null_or_eq(_olderBrother, other._olderBrother)) {return false;}\n\t\tif (!null_or_eq(_youngerBrother, other._youngerBrother)) {return false;}\n\t\tif (!null_or_eq(_oldestChild, other._oldestChild)) {return false;}\n\t\tif (!null_or_eq(_youngestChild, other._youngestChild)) {return false;}\n\n\t\treturn true;\n\t}\n\t\n\tpublic boolean equals(Object other) {\n\t\tif (other instanceof SafraTreeNode) {\n\t\t\treturn this.equals((SafraTreeNode) other);\n\t\t}\n\t\telse return false;\n\t}\n\n\t/** \n\t * Equality operator ignoring the name of the nodes, doing a deep compare\n\t * (checks that all children are also structurally equal.\n\t */\n\tpublic boolean structuralEquals(SafraTreeNode other) {\n\t\tif (!(_final_flag == other._final_flag)) {return false;}\n\t\tif (!(_childCount == other._childCount)) {return false;}\n\t\tif (!(_labeling.equals(other._labeling))) {return false;}\n\n\t\tif (_childCount > 0) {\n\t\t\tSafraTreeNode this_child = getOldestChild();\n\t\t\tSafraTreeNode other_child = other.getOldestChild();\n\n\t\t\tdo {\n\t\t\t\tif (!this_child.structuralEquals(other_child)) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\n\t\t\t\tthis_child = this_child.getYoungerBrother();\n\t\t\t\tother_child = other_child.getYoungerBrother();\n\t\t\t} while (this_child != null && other_child != null);\n\n\t\t\tassert(this_child == null && other_child == null);\n\t\t}\n\t\treturn true;\n\t}\n\n\tprivate int null_or_cmpID(SafraTreeNode a, SafraTreeNode b) {\n\t\tif (a == null) {\n\t\t\tif (b == null) return 0;\n\t\t\telse return -1;\n\t\t}\n\t\telse {\n\t\t\tif (b == null) return 1;\n\t\t\treturn a.getID() - b.getID();\n\t\t}\n\t}\n\t/** Less-than operator. Does not do deep compare */\n\tpublic boolean lessThan(SafraTreeNode other) {\n\t\t\n\t\tif (_id < other._id) return true;\n\t\tif (!_final_flag && other._final_flag) return true;\n\t\tif (_childCount < other._childCount) return true;\n\t\tif (_labeling.compareTo(other._labeling) < 0) return true;\n\t\t\n\t\tif (null_or_cmpID(_parent, other._parent) != 0)\n\t\t\treturn (null_or_cmpID(_parent, other._parent) < 0);\n\t\tif (null_or_cmpID(_olderBrother, other._olderBrother) != 0)\n\t\t\treturn (null_or_cmpID(_olderBrother, other._olderBrother) < 0);\n\t\tif (null_or_cmpID(_youngerBrother, other._youngerBrother) != 0)\n\t\t\treturn (null_or_cmpID(_youngerBrother, other._youngerBrother) < 0);\n\t\tif (null_or_cmpID(_oldestChild, other._oldestChild) != 0)\n\t\t\treturn (null_or_cmpID(_oldestChild, other._oldestChild) < 0);\n\t\tif (null_or_cmpID(_youngestChild, other._youngestChild) != 0)\n\t\t\treturn (null_or_cmpID(_youngestChild, other._youngestChild) < 0);\n\t\treturn false;\n\t}\n\n\t/** \n\t * Less-than operator ignoring the name of the nodes, doing a deep compare\n\t * (applies recursively on the children).\n\t */\n\tpublic boolean structuralLessThan(SafraTreeNode other) {\n\t\treturn (this.compareTo(other) < 0);\n\t}\n\t\n\t/** Do a structural comparison */\n\tpublic int compareTo(SafraTreeNode other) {\n\t\tint cmp;\n\t\t\n\t\tif (_final_flag ^ other._final_flag)\n\t\t\treturn (_final_flag ? 1 : -1);\n\t\t\n\t\tcmp = _childCount - other._childCount;\n\t\tif (cmp != 0) {return cmp;}\n\t\t\n\t\tcmp = _labeling.compareTo(other._labeling);\n\t\tif (cmp != 0) {return cmp;}\n\t\t\n\t\t// if we are here, this and other have the same number of children\n\t\tif (_childCount > 0) {\n\t\t\tSafraTreeNode this_child = getOldestChild();\n\t\t\tSafraTreeNode other_child = other.getOldestChild();\n\n\t\t\tdo {\n\t\t\t\tcmp = this_child.compareTo(other_child);\n\t\t\t\tif (cmp != 0) {return cmp;}\n\n\t\t\t\tthis_child = this_child.getYoungerBrother();\n\t\t\t\tother_child = other_child.getYoungerBrother();\n\t\t\t} while (this_child != null && other_child != null);\n\n\t\t\t// assert that there was really the same number of children\n\t\t\tassert(this_child == null && other_child == null);\n\t\t}\n\n\t\t// when we are here, all children were equal\n\t\treturn 0;\n\t}\n\n\t/** Add a node as the youngest child */\n\tpublic void addAsYoungestChild(SafraTreeNode other) {\n\t\tassert(other != null);\n\t\tassert(other.getParent() == null);\n\t\tassert(other.getOlderBrother() == null);\n\t\tassert(other.getYoungerBrother() == null);\n\n\t\tif (_youngestChild != null) {\n\t\t\tassert(_youngestChild._youngerBrother == null);\n\t\t\t_youngestChild._youngerBrother = other;\n\t\t\tother._olderBrother = _youngestChild;\n\t\t}\n\n\t\tother._parent = this;\n\t\t_youngestChild = other;\n\t\tif (_oldestChild == null) {\n\t\t\t_oldestChild = other;\n\t\t}\n\t\t_childCount++;\n\t}\n\n\t/** Add a node as the oldest child */\n\tpublic void addAsOldestChild(SafraTreeNode other) {\n\t\tassert(other.getParent() == null);\n\t\tassert(other.getOlderBrother() == null);\n\t\tassert(other.getYoungerBrother() == null);\n\n\t\tif (_oldestChild != null) {\n\t\t\tassert(_oldestChild._olderBrother == null);\n\t\t\t_oldestChild._olderBrother = other;\n\t\t\tother._youngerBrother = _oldestChild;\n\t\t}\n\n\t\tother._parent = this;\n\t\t_oldestChild = other;\n\t\tif (_youngestChild == null) {\n\t\t\t_youngestChild = other;\n\t\t}\n\t\t_childCount++;\n\t}\n\n\t/** Remove this node from the tree (relink siblings). The node is not allowed \n\t * to have children! */\n\tpublic void removeFromTree() {\n\t\tassert(_childCount == 0);\n\n\t\tif (_parent == null) {\n\t\t\t// Root-Node or already removed from tree, nothing to do\n\t\t\treturn;\n\t\t}\n\n\t\t// Relink siblings\n\t\tif (_olderBrother != null) {\n\t\t\t_olderBrother._youngerBrother = _youngerBrother;\n\t\t}\n\t\tif (_youngerBrother != null) {\n\t\t\t_youngerBrother._olderBrother = _olderBrother;\n\t\t}\n\n\t\t// Relink child-pointers in _parent\n\t\tif (_parent._oldestChild == this) {\n\t\t\t// this node is oldest child\n\t\t\t_parent._oldestChild = this._youngerBrother;\n\t\t}\n\n\t\tif (_parent._youngestChild == this) {\n\t\t\t// this node is youngest child\n\t\t\t_parent._youngestChild = this._olderBrother;\n\t\t}\n\n\t\t_parent._childCount--;\n\n\t\t_youngerBrother = null;\n\t\t_olderBrother = null;\n\t\t_parent = null;\n\t}\n\n\t/**\n\t * Swap the places of two child nodes \n\t */\n\tpublic void swapChildren(SafraTreeNode a, SafraTreeNode b) {\n\t\tassert(a.getParent() == b.getParent() && a.getParent() == this);\n\n\t\tif (a == b) {return;}\n\n\t\tif (_oldestChild == a) {\n\t\t\t_oldestChild = b;\n\t\t} else if (_oldestChild == b) {\n\t\t\t_oldestChild = a;\n\t\t}\n\n\t\tif (_youngestChild == a) {\n\t\t\t_youngestChild = b;\n\t\t} else if (_youngestChild == b) {\n\t\t\t_youngestChild = a;\n\t\t}\n\n\t\tSafraTreeNode a_left = a._olderBrother;\n\t\tSafraTreeNode b_left = b._olderBrother;\n\t\tSafraTreeNode a_right = a._youngerBrother;\n\t\tSafraTreeNode b_right = b._youngerBrother;\n\n\t\tif (a_left != null) {a_left._youngerBrother = b;}\n\t\tif (b_left != null) {b_left._youngerBrother = a;}\n\t\tif (a_right != null) {a_right._olderBrother = b;}\n\t\tif (b_right != null) {b_right._olderBrother = a;}\n\n\t\ta._olderBrother = b_left;\n\t\ta._youngerBrother = b_right;\n\t\tb._olderBrother = a_left;\n\t\tb._youngerBrother = a_right;\n\n\t\tif (a_right == b) {\n\t\t\t// a & b are direct neighbours, a to the left of b\n\t\t\ta._olderBrother = b;\n\t\t\tb._youngerBrother = a;\n\t\t} else if (b_right == a) {\n\t\t\t// a & b are direct neighbours, b to the left of a\n\t\t\ta._youngerBrother = b;\n\t\t\tb._olderBrother = a;\n\t\t}\n\t}\n\n\tpublic Iterator<SafraTreeNode> iterator() {\n\t\treturn new SafraTreeNodeIterator(this);\n\t}\n\t\n\tpublic static class SafraTreeNodeIterator implements Iterator<SafraTreeNode> {\n\n\t\tprivate SafraTreeNode _current;\n\t\t\n\t\tpublic SafraTreeNodeIterator(SafraTreeNode node) {\n\t\t\t_current = node.getOldestChild();\n\t\t}\n\t\t\n\t\tpublic SafraTreeNode next() {\n\t\t\tSafraTreeNode tmp = _current;\n\t\t\t_current = _current.getYoungerBrother();\n\t\t\treturn tmp;\n\t\t}\n\t\t\n\t\tpublic boolean hasNext() {\n\t\t\treturn (_current != null);\n\t\t}\n\t\t\n\t\tpublic void remove() {\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\t}\n\t\n\t/** Calculate the height of the subtree rooted at this node. */\n\tpublic int treeHeight() {\n\t\tint height = 0;\n\n\t\tif (getChildCount() > 0) {\n\t\t\tfor (SafraTreeNode cur_child : this) {\n\t\t\t\tint child_height = cur_child.treeHeight();\n\t\t\t\tif (child_height > height) {\n\t\t\t\t\theight = child_height;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn height + 1;\n\t}\n\n\t/** Calculate the width of the subtree rooted at this node. */\n\tpublic int treeWidth() {\n\t\tint width = 0;\n\n\t\tif (getChildCount() > 0) {\n\t\t\tfor (SafraTreeNode cur_child : this) {\n\t\t\t\twidth += cur_child.treeWidth();\n\t\t\t}\n\t\t} \n\t\telse width = 1;\n\n\t\treturn width;\n\t}\n\n\t/** \n\t * Calculate a hashvalue using HashFunction for this node.\n\t * @param hashfunction the HashFunction functor\n\t * @param only_structure Ignore naming of the nodes?\n\t */\n\t/* public void hashCode(HashFunction hashfunction,\tboolean only_structure) {\n\t\tif (!only_structure) {\n\t\t\thashfunction.hash(getID());\n\t\t}\n\n\t\tgetLabeling().hashCode(hashfunction);\n\t\thashfunction.hash(hasFinalFlag());\n\n\t\tif (getChildCount () >0) {\n\t\t\tfor (SafraTreeNode c : this) { \n\t\t\t\tc.hashCode(hashfunction, only_structure);\n\t\t\t}\n\t\t}\n\t}*/\n\t\n\tpublic int hashCode() {\n\t\tint hash = 1;\n\t\thash += (hasFinalFlag() ? 1 : 0);\n\t\thash = hash * 31 + getLabeling().hashCode();\n\t\tif (getChildCount () > 0) {\n\t\t\tfor (SafraTreeNode c : this) { \n\t\t\t\thash = hash * 31 + c.hashCode();\n\t\t\t}\n\t\t}\n\t\treturn hash;\n\t}\n\t\n\t/**\n\t * Print node to output stream\n\t */\n\tpublic void print(PrintStream out) {\n\t\tout.print(_id + \" \");\n\t\t_labeling.print(out);\n\t\tif (_final_flag) {out.print(\" !\");}\n\t}\n\n\t/** Print HTML version of this node to output stream */\n\tpublic void toHTML(PrintStream out) {\n\t\tout.print(this.toHTMLString());\n\t}\n\t\n\tpublic String toHTMLString() {\n\t\tStringBuffer buf = new StringBuffer(\"<TABLE><TR>\");\n\t\t\n\t\tif (getChildCount() <= 1) {\n\t\t\tbuf.append(\"<TD>\");\n\t\t} else {\n\t\t\tbuf.append(\"<TD COLSPAN=\\\"\");\n\t\t\tbuf.append(getChildCount());\n\t\t\tbuf.append(\"\\\">\");\n\t\t}\n\n\t\tbuf.append(getID());\n\t\tbuf.append(\" \");\n\t\tbuf.append(_labeling);\n\t\tif (_final_flag) {buf.append(\"!\");}\n\t\tbuf.append(\"</TD></TR>\");\n\t\tif (getChildCount() > 0) {\n\t\t\tbuf.append(\"<TR>\");\n\t\t\tfor (SafraTreeNode child : this) {\n\t\t\t\tbuf.append(\"<TD>\");\n\t\t\t\tbuf.append(child.toHTMLString());\n\t\t\t\tbuf.append(\"</TD>\");\n\t\t\t}\n\t\t\tbuf.append(\"</TR>\");\n\t\t}\n\t\tbuf.append(\"</TABLE>\");\n\t\t\n\t\treturn buf.toString();\n\t}\n\n}"
  },
  {
    "path": "prism/src/jltl2dstar/SafraTreeTemplate.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport jltl2ba.MyBitSet;\n\n/** @file\n * Provides the class SafraTreeTemplate\n */\n\n/**\n * A SafraTreeTemplate consists of a SafraTree and two BitSets,\n * one containing the names of nodes that may be renamed and on\n * containing the names that are not allowed in the tree.\n */\npublic class SafraTreeTemplate implements NBA2DAResult<SafraTree> {\n\n\tprivate SafraTree _safraTree;\n\tprivate MyBitSet _renameableNames;\n\tprivate MyBitSet _restrictedNames;\n\n\t/**\n\t * Constructor.\n\t * @param safraTree the SafraTree\n\t */\n\tpublic SafraTreeTemplate(SafraTree safraTree)\n\t{\n\t\t_safraTree = safraTree;\n\t\t_renameableNames = new MyBitSet();\n\t\t_restrictedNames = new MyBitSet();\n\t}\n\n\t/** Get the SafraTree */\n\tpublic SafraTree getSafraTree() {return _safraTree;}\n\n\t/** Get the SafraTree */\n\tpublic SafraTree getState() {return _safraTree;}\n\n\t/** Get the names of nodes that may be renamed. */\n\tpublic MyBitSet renameableNames() {return _renameableNames;}\n\n\t/** Get the names that can are not allowed to be used in the Safra tree */\n\tpublic MyBitSet restrictedNames() {return _restrictedNames;}\n\n\t/** Set the 'renameable' flag for a name (former flag default: true) */\n\tpublic void setRenameable(int name, boolean flag) { _renameableNames.set(name, flag); }\n\n\t/** Get the 'renameable' flag for a name */\n\tpublic boolean isRenameable(int name) { return _renameableNames.get(name); }\n\n\t/** Set the 'restricted' flag for a name (former flag default: true) */\n\tpublic void setRestricted(int name, boolean flag) { _restrictedNames.set(name, flag); }\n\n\t/** Get the 'restricted' flag for a name */\n\tpublic boolean isRestricted(int name) { return _restrictedNames.get(name); }\n\n\n\t/**\n\t * Return true if this tree (taking into account the renameableNames and the restrictedNames) \n\t * can be renamed to match the SafraTree other.\n\t * Can only be called for trees that are structural_equal!!!\n\t */\n\tpublic boolean matches(SafraTree other) {\n\t\tSafraTreeNode this_root = _safraTree.getRootNode();\n\t\tSafraTreeNode other_root = other.getRootNode();\n\n\t\tif (this_root == null || other_root == null) {\n\t\t\tassert(this_root == null && other_root == null);\n\t\t\treturn true;\n\t\t}\n\n\t\treturn matches(this_root, other_root);\n\t}\n\n\n\t/**\n\t * Compare two subtrees to see if they match (taking into account the renameableNames\n\t * and the restrictedNames).\n\t */\n\tprivate boolean matches(SafraTreeNode this_node, SafraTreeNode other_node) {\n\t\tassert(this_node != null && other_node != null);\n\n\t\tif (this_node == null || other_node == null) {\n\t\t\treturn false;\n\t\t}\n\n\t\tif (!renameableNames().get(this_node.getID())) {\n\t\t\t// this is not a new node, so we require a perfect match..\n\t\t\tif (other_node.getID() != this_node.getID()) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t} else {\n\t\t\t// we are flexible with the id, as long as the id wasn't removed\n\t\t\t//  in the tree\n\t\t\tif (restrictedNames().get(other_node.getID())) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\tassert(this_node.getLabeling().equals(other_node.getLabeling()));\n\t\tassert(this_node.hasFinalFlag() == other_node.hasFinalFlag());\n\n\t\t// this node looks good, now the children\n\t\tSafraTreeNode this_child = this_node.getOldestChild();\n\t\tSafraTreeNode other_child = other_node.getOldestChild();\n\n\t\twhile (this_child != null && other_child != null) {\n\t\t\tif (!matches(this_child, other_child)) {\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\tthis_child = this_child.getYoungerBrother();\n\t\t\tother_child = other_child.getYoungerBrother();\n\t\t}\n\t\tassert(this_child == null && other_child == null);\n\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/SafraTreeWalker.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** @file \n * Provides class SafraTreeWalker  */\n\n/** \n * Walk a SafraTree and invoke the function \n * <code>void visit(SafraTree& tree, SafraTreeNode *node)</code>\n * of the SafraTreeVisitor on each node of the tree.\n */\npublic class SafraTreeWalker<Visitor extends SafrasAlgorithm.SafraTreeVisitor> {\n\n\t/** The Visitor */\n\tprivate Visitor _visitor;\n\n\t/** Constructor.\n\t *  @param visitor the visitor functor\n\t */\n\tpublic SafraTreeWalker(Visitor visitor) {\n\t\t_visitor = visitor;\n\t}\n\n\t/** \n\t * Walk the tree post-order and call visit() on each node.\n\t * @param tree the SafraTree\n\t */\n\tpublic void walkTreePostOrder(SafraTree tree) {\n\t\tif (tree.getRootNode() == null) {return;}\n\t\twalkSubTreePostOrder(tree, tree.getRootNode(), true);\n\t}\n\n\t/** \n\t * Walk the subtree rooted at *top post-order and call visit() on each node.\n\t * @param tree the SafraTree\n\t * @param top the current subroot \n\t * @param visit_top if true, *top is visited too (former default: true)\n\t */\n\tpublic void walkSubTreePostOrder(SafraTree tree, \n\t\t\tSafraTreeNode top,\n\t\t\tboolean visit_top) {\n\t\tif (top.getChildCount() > 0) {\n\t\t\tfor (SafraTreeNode cur_child : top)\n\t\t\t\twalkSubTreePostOrder(tree, cur_child, true);\n\t\t}\n\n\t\tif (visit_top) {\n\t\t\t_visitor.visit(tree, top);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/SafrasAlgorithm.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** @file \n * Provides an implementation of the transition function of Safra's algorithm. \n */\nimport java.util.Vector;\n\nimport jltl2ba.APElement;\nimport jltl2ba.MyBitSet;\nimport prism.PrismException;\n\n/**\n * A class which calculates the transition function of Safra's algorithm.\n * You have to provide at least the final states of the NBA, the other\n * values have to be set, if the corresponding option is set.\n */\npublic class SafrasAlgorithm {\n\n\tprivate Options_Safra _options;\n\tprivate NBAAnalysis _nba_analysis;\n\tprivate NBA _nba;\n\tprivate int _NODES;\n\n\tprivate Vector<MyBitSet> _next;\n\n\t/** Caching the STVisitor_reorder_children, as it's initialization is complex. */\n\tprivate STVReorderChildren stv_reorder;\n\n\t/**\n\t * Constructor\n\t * @param nba The NBA\n\t * @param options The options for Safra's algorithm\n\t */\n\tpublic SafrasAlgorithm(NBA nba, Options_Safra options) throws PrismException {\n\t\t_options = options; \n\t\t_nba_analysis = new NBAAnalysis(nba);\n\t\t_nba = nba;\n\t\t\n\t\tif (_nba.getFailIfDisjoint() && _nba_analysis.isNBADisjoint()) {\n\t\t\tthrow new PrismException(\"The NBA generated for the LTL formula was discovered to be disjoint,\\n\"\n\t\t\t                       + \"i.e., some states were not reachable from the initial state. This likely\\n\"\n\t\t\t                       + \"indicates a problem in the translation. Please report the formula to the\\n\"\n\t\t\t                       + \"PRISM developers\");\n\t\t}\n\t\t\n\t\t_NODES = 2 * nba.getStateCount();\n\t\tstv_reorder = null; \n\t\t_next = new Vector<MyBitSet>();\n\t\t_next.setSize(nba.getStateCount());\n\t}\n\n\t\n\t// typedef SafraTreeTemplate_ptr result_t;\n\t// typedef SafraTree_ptr state_t;\n\n\tpublic SafraTreeTemplate delta(SafraTree tree, APElement elem) throws PrismException {\n\t\treturn process(tree, elem);\n\t}\n\n\tpublic SafraTree getStartState() {\n\t\tSafraTree start = new SafraTree(_NODES);\n\t\tif (_nba.getStartState() != null) {\n\t\t\tstart.getRootNode().getLabeling().set(_nba.getStartState().getName());\n\t\t}\n\n\t\treturn start;\n\t}\n\n\tpublic void prepareAcceptance(RabinAcceptance acceptance) {\n\t\tacceptance.newAcceptancePairs(_NODES);\n\t}\n\n\tpublic boolean checkEmpty() {\n\t\tif (_nba.size() == 0 || _nba.getStartState() == null) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** \n\t * Get the next Safra tree using the\n\t * transition function as described by Safra.\n\t * @param tree the original tree\n\t * @param elem the edge label\n\t * @return a SafraTreeTemplate containing the new tree and \n\t *         bookkeeping which states were created/deleted.\n\t */\n\tpublic SafraTreeTemplate process(SafraTree tree, APElement elem) {\n\t\t// Make copy of original tree\n\t\tSafraTree cur = new SafraTree(tree);\n\t\tSafraTreeTemplate tree_template = new SafraTreeTemplate(cur);\n\t\t// System.out.print(\"Init: \"); tree_template.getState().print(System.out); System.out.println();\n\n\t\tSTVResetFinalFlag stv_reset_flag = new STVResetFinalFlag();\n\t\tcur.walkTreePostOrder(stv_reset_flag);\n\t\t// System.out.print(\"Reset: \"); tree_template.getState().print(System.out); System.out.println();\n\t\t\n\t\tSTVCheckFinalSet stv_final = new STVCheckFinalSet(_nba_analysis.getFinalStates(), tree_template);\n\t\tcur.walkTreePostOrder(stv_final);\n\t\t// System.out.print(\"Final: \"); tree_template.getState().print(System.out); System.out.println();\n\n\t\tSTVPowerset stv_powerset = new STVPowerset(_nba, elem);\n\t\tcur.walkTreePostOrder(stv_powerset);\n\t\t// System.out.print(\"Powerset: \"); tree_template.getState().print(System.out); System.out.println();\n\n\n\t\t/*\n\t\t * Optimization: ACCEPTING_TRUE_LOOPS\n\t\t */\n\t\tif (_options.opt_accloop) {\n\t\t\tif (cur.getRootNode() != null) {\n\t\t\t\tSafraTreeNode root = cur.getRootNode();\n\n\t\t\t\tif (_nba_analysis.getStatesWithAcceptingTrueLoops().intersects(root.getLabeling())) {\n\t\t\t\t\t// True Loop\n\t\t\t\t\tSTVRemoveSubtree stv_remove = new STVRemoveSubtree(tree_template);\n\t\t\t\t\tcur.walkChildrenPostOrder(stv_remove, root);\n\n\t\t\t\t\troot.getLabeling().clear();\n\n\t\t\t\t\tint canonical_true_loop = _nba_analysis.getStatesWithAcceptingTrueLoops().nextSetBit(0);\n\t\t\t\t\troot.getLabeling().set(canonical_true_loop);\n\t\t\t\t\troot.setFinalFlag(true);\n\n\t\t\t\t\t// System.out.print(\"Accloop: \"); tree_template.getState().print(System.out); System.out.println();\n\t\t\t\t\treturn tree_template;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tSTVCheckChildrenHorizontal stv_horizontal = new STVCheckChildrenHorizontal();\n\t\tcur.walkTreePostOrder(stv_horizontal);\n\t\t// System.out.print(\"Horizontal: \"); tree_template.getState().print(System.out); System.out.println();\n\t\t\n\t\tSTVRemoveEmpty stv_empty = new STVRemoveEmpty(tree_template);\n\t\tcur.walkTreePostOrder(stv_empty);\n\t\t// System.out.print(\"Empty: \"); tree_template.getState().print(System.out); System.out.println();\n\n\t\tSTVCheckChildrenVertical stv_vertical = new STVCheckChildrenVertical(tree_template);\n\t\tcur.walkTreePostOrder(stv_vertical);\n\t\t// System.out.print(\"Vertical: \"); tree_template.getState().print(System.out); System.out.println();\n\n\t\t/*\n\t\t * Optimization: REORDER\n\t\t */\n\t\tif (_options.opt_reorder) {\n\t\t\tif (stv_reorder == null) {\n\t\t\t\tstv_reorder = new STVReorderChildren(_nba_analysis.getReachability(), cur.getNodeMax());\n\t\t\t}\n\n\t\t\tcur.walkTreePostOrder(stv_reorder);\n\t\t}\n\t\t// System.out.print(\"Reorder: \"); tree_template.getState().print(System.out); System.out.println();\n\n\t\t/*\n\t\t * Optimization: ALL SUCCESSORS ARE ACCEPTING\n\t\t */\n\t\tif (_options.opt_accsucc) {\n\t\t\tSTVCheckForFinalSucc stv_succ = new STVCheckForFinalSucc(_nba_analysis.getStatesWithAllSuccAccepting(), tree_template);\n\n\t\t\tcur.walkTreePostOrder(stv_succ);\n\t\t}\n\t\t// System.out.print(\"Accsucc: \"); tree_template.getState().print(System.out); System.out.println();\n\t\treturn tree_template;\n\t}\n\n\t/** Visitors */\n\tpublic interface SafraTreeVisitor {\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node);\n\t}\n\t\n\t/**\n\t * A Safra tree visitor that modifies the\n\t * children so that all children have\n\t * disjoint labels\n\t */\n\tpublic class STVCheckChildrenHorizontal implements SafraTreeVisitor {\n\n\t\t/** Node visitor */\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tif (node.getChildCount() <= 1) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tMyBitSet already_seen = new MyBitSet();\t// FIXME: although it's not used, hmph warnings\n\t\t\tboolean first = true;\n\t\t\tfor (SafraTreeNode cur_child : node) {\n\t\t\t\tif (first) {\n\t\t\t\t\talready_seen = (MyBitSet) cur_child.getLabeling().clone();\n\t\t\t\t\tfirst = false;\n\t\t\t\t} else {\n\t\t\t\t\tMyBitSet current = cur_child.getLabeling();\n\n\t\t\t\t\tMyBitSet intersection = (MyBitSet) already_seen.clone(); // make copy\n\t\t\t\t\tif (intersection.intersects(current)) {\n\t\t\t\t\t\t// There are some labels, which occur in older brothers,\n\t\t\t\t\t\t// remove them from current node and its children\n\t\t\t\t\t\tSTVSubstractLabeling stv_sub = new STVSubstractLabeling(intersection);\n\t\t\t\t\t\ttree.walkSubTreePostOrder(stv_sub, cur_child);\n\t\t\t\t\t}\n\t\t\t\t\talready_seen.or(current);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * A Safra tree visitor that ensures that \n\t * the union of the labels of the children\n\t * are a proper subset of the label of the\n\t * parents. Otherwise, the children are\n\t * removed and the final flag is set on\n\t * the tree node.\n\t */\n\tpublic class STVCheckChildrenVertical implements SafraTreeVisitor {\n\n\t\tprivate SafraTreeTemplate _tree_template;\n\n\t\tpublic STVCheckChildrenVertical(SafraTreeTemplate tree_template) { \n\t\t\t_tree_template = tree_template;\n\t\t}\n\n\t\t/** Node visitor */\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tif (node.getChildCount() == 0) {return;}\n\n\t\t\tMyBitSet labeling_union = new MyBitSet();\n\t\t\tfor (SafraTreeNode child : node) {\n\t\t\t\tlabeling_union.or(child.getLabeling());\n\t\t\t}\n\n\t\t\tif (labeling_union.equals(node.getLabeling())) {\n\t\t\t\t// The union of the labelings of the children is exactly the \n\t\t\t\t// same as the labeling of the parent ->\n\t\t\t\t//  remove children\n\t\t\t\tSTVRemoveSubtree stv_remove = new STVRemoveSubtree(_tree_template);\n\t\t\t\ttree.walkChildrenPostOrder(stv_remove, node);\n\n\t\t\t\tnode.setFinalFlag(true);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Safra tree visitor that creates a new child node if\n\t * the label of the node and the set of final states in the\n\t * NBA intersect.\n\t */\n\tpublic class STVCheckFinalSet implements SafraTreeVisitor {\n\n\t\tprivate MyBitSet _final_states;\n\t\tprivate SafraTreeTemplate _tree_template;\n\n\n\t\t/**\n\t\t * Constructor.\n\t\t * @param final_states the states that are accepting (final) in the NBA\n\t\t * @param tree_template the tree template to keep track of new nodes\n\t\t */\n\t\tpublic STVCheckFinalSet(MyBitSet final_states, SafraTreeTemplate tree_template) {\n\n\t\t\t_final_states = final_states;\n\t\t\t_tree_template = tree_template;\n\t\t}\n\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tif (_final_states.intersects(node.getLabeling())) {\n\t\t\t\tMyBitSet q_and_f = (MyBitSet) _final_states.clone();\n\t\t\t\tq_and_f.and(node.getLabeling());\n\n\t\t\t\tSafraTreeNode new_child = tree.newNode();\n\t\t\t\tnode.addAsYoungestChild(new_child);\n\n\t\t\t\t_tree_template.setRenameable(new_child.getID(), true);\n\n\t\t\t\tnew_child.setLabeling(q_and_f);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * A Safra tree visitor that checks if all\n\t * the successor states in the NBA of the label\n\t * are accepting. If this is the case, all\n\t * children are removed, and the final flag is set.\n\t */\n\tpublic class STVCheckForFinalSucc implements SafraTreeVisitor {\n\t\tprivate boolean _success;\n\t\tprivate MyBitSet _nba_states_with_all_succ_final;\n\t\tprivate SafraTreeTemplate _tree_template;\n\n\n\t\t/** \n\t\t * Constructor \n\t\t * @param nba_states_with_all_succ_final A BitSet with the indizes of the\n\t\t *                                       NBA states that only have accepting (final)\n\t\t *                                       successors.\n\t\t * @param tree_template                  SafraTreeTemplate to keep track of removed nodes\n\t\t */\n\t\tpublic STVCheckForFinalSucc(MyBitSet nba_states_with_all_succ_final, SafraTreeTemplate tree_template) {\n\t\t\t_success = false; \n\t\t\t_nba_states_with_all_succ_final = nba_states_with_all_succ_final;\n\t\t\t_tree_template = tree_template;\n\t\t}\n\n\t\t/** Returns true if the condition was triggered. */\n\t\tpublic boolean wasSuccessful() {return _success;}\n\n\t\t/** Node visitor */\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\n\t\t\tboolean all_final = true;\n\t\t\tfor (int i = node.getLabeling().nextSetBit(0); i >= 0; i = node.getLabeling().nextSetBit(i+1)) {\n\t\t\t\tif (! _nba_states_with_all_succ_final.get(i)) {\n\t\t\t\t\tall_final = false;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (all_final) {\n\t\t\t\t// remove all children of node & set final flag\n\t\t\t\tSTVRemoveSubtree stv_remove = new STVRemoveSubtree(_tree_template);\n\t\t\t\ttree.walkChildrenPostOrder(stv_remove, node);\n\t\t\t\tnode.setFinalFlag(true);\n\t\t\t\t_success=true;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Safra tree visitor that performs the powerset construction\n\t * on the label of the Safra tree node.\n\t */\n\tpublic class STVPowerset implements SafraTreeVisitor {\n\n\t\tprivate NBA _nba;\n\t\tprivate APElement _elem;\n\n\t\t/**\n\t\t * Constructor.\n\t\t */\n\t\tpublic STVPowerset(NBA nba, APElement elem) {\n\t\t\t_nba = nba;\n\t\t\t_elem = elem;\n\t\t}\n\n\t\t/** Node visitor */  \n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tMyBitSet old_labeling = node.getLabeling();\n\t\t\tMyBitSet new_labeling = new MyBitSet(old_labeling.size());\n\t\t\tfor (int i = old_labeling.nextSetBit(0); i >= 0; i = old_labeling.nextSetBit(i+1)) {\n\t\t\t\tnew_labeling.or(_nba.get(i).getEdge(_elem));\n\t\t\t}\n\t\t\tnode.setLabeling(new_labeling);\n\t\t}\n\t}\n\n\t/**\n\t * A Safra tree visitor that removes tree nodes\n\t * with empty labels.\n\t */\n\tpublic class STVRemoveEmpty implements SafraTreeVisitor {\n\n\t\tprivate\tSafraTreeTemplate _tree_template;\n\n\t\tpublic STVRemoveEmpty(SafraTreeTemplate tree_template) {\n\t\t\t_tree_template = tree_template;\n\t\t}\n\n\t\t/** Node visitor */\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tif (node.getLabeling().isEmpty()) {\n\t\t\t\tint id = node.getID();\n\t\t\t\tif (_tree_template.isRenameable(id)) {\n\t\t\t\t\t// this node was created recently, so we only delete it in\n\t\t\t\t\t// renameableNames, but don't mark it in restrictedNodes\n\t\t\t\t\t_tree_template.setRenameable(id, false);\n\t\t\t\t} else {\n\t\t\t\t\t_tree_template.setRestricted(id, true);\n\t\t\t\t}\n\n\t\t\t\ttree.remove(node);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * A Safra tree visitor that removes all \n\t * children of the node.\n\t */\n\tpublic class STVRemoveSubtree implements SafraTreeVisitor {\n\n\t\tprivate SafraTreeTemplate _tree_template;\n\n\t\tpublic STVRemoveSubtree(SafraTreeTemplate tree_template) {\n\t\t\t_tree_template = tree_template;\t\n\t\t}\n\n\t\t/** Node visitor */\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tint id = node.getID();\n\t\t\tif (_tree_template.isRenameable(id)) {\n\t\t\t\t// this node was created recently, so we only delete it from\n\t\t\t\t// the renameableNames, but don't mark it in restrictedNames\n\t\t\t\t_tree_template.setRenameable(id, false);\n\t\t\t} else {\n\t\t\t\t_tree_template.setRestricted(id, true);\n\t\t\t}\n\n\t\t\ttree.remove(node);\n\t\t}\n\t}\n\n\t/**\n\t * Safra tree visitor that attempts\n\t * to reorder the independant children \n\t * into a canonical order.\n\t * Two children are independet if\n\t * their is no state that is reachable by \n\t * states in both labels.\n\t */\n\tpublic class STVReorderChildren implements SafraTreeVisitor {\n\n\t\tprivate Vector<MyBitSet> _nba_reachability;\n\t\tprivate MyBitSet[] _node_reachability;\n\t\tprivate int[] _node_order;\n\n\t\t/**\n\t\t * Constructor\n\t\t * nba_reachability A vector of BitSets (state index -> BitSet) of states\n\t\t *                  in the NBA that are reachable from a state.\n\t\t * N                the maximum number of nodes in the Safra tree\n\t\t */\n\t\tpublic STVReorderChildren(Vector<MyBitSet> nba_reachability, int N) {\n\t\t\t_nba_reachability = nba_reachability;\n\t\t\t_node_order = new int[N];\n\t\t\t_node_reachability = new MyBitSet[N];\n\t\t\tfor (int i = 0; i < N; i++) {\n\t\t\t\t_node_reachability[i] = new MyBitSet();\n\t\t\t}\n\t\t}\n\n\t\t/** Node visitor */\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tif (node.getChildCount() <= 1) {return;}\n\n\t\t\tint i = 0;\n\t\t\tfor (SafraTreeNode child : node) {\n\t\t\t\tMyBitSet reachable_this = _node_reachability[child.getID()];\n\t\t\t\treachable_this.clear();\n\t\t\t\t_node_order[child.getID()] = i++;\n\n\t\t\t\tMyBitSet label_this = child.getLabeling();\n\t\t\t\tfor (int setbit = label_this.nextSetBit(0); setbit >= 0; setbit = label_this.nextSetBit(setbit+1)) {\n\t\t\t\t\treachable_this.or(_nba_reachability.get(setbit));\n\t\t\t\t}\n\t\t\t\t//      std::cerr << \"reachability_this: \"<<reachable_this << std::endl; \n\t\t\t}\n\n\t\t\t// reorder...\n\t\t\t//    std::cerr << \"Sorting!\" << std::endl;\n\n\t\t\t// Bubble sort, ough!\n\t\t\tboolean finished = false;\n\t\t\twhile (!finished) {\n\t\t\t\tfinished=true;\n\n\t\t\t\tfor (SafraTreeNode a = node.getOldestChild();\n\t\t\t\ta != null && a.getYoungerBrother() != null;\n\t\t\t\ta = a.getYoungerBrother()) {\n\n\t\t\t\t\tSafraTreeNode b = a.getYoungerBrother();\n\n\t\t\t\t\tMyBitSet reach_a = _node_reachability[a.getID()];\n\t\t\t\t\tMyBitSet reach_b = _node_reachability[b.getID()];\n\n\t\t\t\t\tif (reach_a.intersects(reach_b)) {\n\t\t\t\t\t\t// a and b are not independant...\n\t\t\t\t\t\t// --> keep relative order...\n\t\t\t\t\t\tassert(_node_order[a.getID()] < _node_order[b.getID()]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// a and b are independant...\n\t\t\t\t\t\tif (a.getLabeling().compareTo(b.getLabeling()) >= 0) {\n\t\t\t\t\t\t\t// swap\n\t\t\t\t\t\t\tnode.swapChildren(a,b);\n\t\t\t\t\t\t\ta=b;\n\t\t\t\t\t\t\tfinished=false;\t    \n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Safra tree visitor that resets the final flag on the Safra tree node.\n\t */\n\tpublic class STVResetFinalFlag implements SafraTreeVisitor {\n\t\t\n\t\t/** Node visitor */\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tnode.setFinalFlag(false);\n\t\t}\n\t}\n\t\n\t/**\n\t * A Safra tree visitor that subtracts (minus operator) a BitSet from\n\t * the label of the tree node.\n\t */\n\tpublic class STVSubstractLabeling implements SafraTreeVisitor {\n\n\t\tprivate MyBitSet _bitset;\n\n\t\tpublic STVSubstractLabeling(MyBitSet bitset) {\n\t\t\t_bitset = bitset;\n\t\t}\n\t\t\n\t\tpublic void visit(SafraTree tree, SafraTreeNode node) {\n\t\t\tnode.getLabeling().andNot(_bitset);\n\t\t}  \n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/Scheduler.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** @file\n * Implementation of LTL2DSTAR_Scheduler\n */\nimport java.util.Vector;\nimport java.io.PrintStream;\n\nimport jltl2ba.APSet;\nimport jltl2ba.SimpleLTL;\nimport prism.PrismException;\n\n/**\n * Allows translation of LTL to DRA/DSA\n * in multiple ways and combines the basic building blocks to choose the most\n * efficient.\n */\npublic class Scheduler {\n\n\t/** The LTL2DRA wrapper for Safra's algorithm and the external LTL->NBA translator */\n\tprivate LTL2DRA _ltl2dra;\n\n\t/** Use limiting? */\n\tprivate boolean _opt_limits;\n\n\t/** The limiting factor */\n\tprivate double _alpha;\n\n\t/** Print stats on the NBA? */\n\tprivate boolean _stat_NBA;\n\t\n\t/** Base class for the building blocks for the scheduler */\n\tpublic abstract static class Tree {\n\t\tprotected SimpleLTL _ltl;    \n\t\tprotected Options_LTL2DRA _options;\n\t\tprotected int priority;\n\t\tprotected DRA _automaton;\n\t\tprotected String _comment;\n\t\tprotected Scheduler _sched;\n\t\tprotected APSet _apset;\n\n\t\tprotected Vector<Tree> children;\n\n\t\t/**\n\t\t * Constructor \n\t\t * @param ltl The LTL formula\n\t\t * @param options the LTL2DSTAR options\n\t\t * @param sched a reference back to the scheduler \n\t\t */\n\t\tpublic Tree(SimpleLTL ltl, APSet apset, Options_LTL2DRA options, Scheduler sched) {\n\t\t\t_ltl = ltl;\n\t\t\t_apset = apset;\n\t\t\t_options = options;\n\t\t\t_sched = sched;\n\t\t\tchildren = new Vector<Tree>();\n\t\t}\n\n\t\t/** Print the tree on output stream (default level: 0) */\n\t\tpublic void printTree(PrintStream out, int level) {\n\t\t\tfor (int i = 0; i < level; i++) {\n\t\t\t\tout.print(\" \");\n\t\t\t}\n\t\t\tout.println(this.getClass().getName() + \" = \" + this + \"(\" + _ltl + \")\");\n\t\t\tfor (Tree child : children) {\n\t\t\t\tchild.printTree(out, level + 1);\n\t\t\t}\n\t\t}\n\n\t\t/** Abstract virtual function for tree generation */\n\t\tpublic abstract void generateTree();\n\n\t\t/** Estimate the size of the automaton */\n\t\tpublic int guestimate() {\n\t\t\treturn 0;\n\t\t}\n\n\t\t/** Hook that is called after calculate() finishes */\n\t\tpublic void hook_after_calculate() {};\n\n\t\t/** Calculate the automaton for this building block, by default\n\t\t * calculate the automata for the children and then choose the smallest.\n\t\t * (default level: 0, default limit: 0 */\n\t\tpublic void calculate(int level, int limit) throws PrismException {\n\t\t\tif (_options.verbose_scheduler) {\n\t\t\t\tSystem.err.println(\"Calculate (\" + level + \"): \" + this.getClass().getName());\n\t\t\t}\n\n\t\t\tcalculateChildren(level, limit);\n\n\t\t\tboolean first = true;\n\t\t\tfor (Tree child : children) {\n\t\t\t\tif (child._automaton == null) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\tif (first) {\n\t\t\t\t\t_automaton = child._automaton;\n\t\t\t\t\t_comment = child._comment;\n\t\t\t\t} else {\n\t\t\t\t\tif (_automaton.size() > child._automaton.size()) {\n\t\t\t\t\t\t_automaton = child._automaton;\n\t\t\t\t\t\t_comment = child._comment;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tfirst = false;\n\t\t\t}\n\n\t\t\thook_after_calculate();\n\t\t}\n\n\t\t/** Add a new child */\n\t\tpublic void addChild(Tree child) {\n\t\t\tif (child == null) {return;}\n\n\t\t\tchildren.add(child);\n\t\t}\n\n\t\t/** Calculate the automata for the children\n\t\t *  (default level: 0, default limit: 0 */\n\t\tprivate void calculateChildren(int level, int limit) throws PrismException {\n\t\t\tif (_sched.flagOptLimits()) {\n\t\t\t\tDRA _min_automaton;\n\t\t\t\tint _min_size = 0;\n\n\t\t\t\tfor (Tree child : children) {\n\t\t\t\t\tint child_limit;\n\t\t\t\t\tif (_min_size != 0) {\n\t\t\t\t\t\tif (limit > 0) {\n\t\t\t\t\t\t\tchild_limit = _sched.calcLimit(_min_size) < limit ? _sched.calcLimit(_min_size) : limit;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tchild_limit = _sched.calcLimit(_min_size);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tchild_limit = limit;\n\t\t\t\t\t}\n\t\t\t\t\tif (_options.verbose_scheduler) {\n\t\t\t\t\t\tSystem.err.println(\" Limit (with alpha) = \" + child_limit);\n\t\t\t\t\t}\n\t\t\t\t\ttry {\n\t\t\t\t\t\tchild.calculate(level + 1, child_limit);\n\n\t\t\t\t\t\tif (child._automaton != null) {\n\t\t\t\t\t\t\tif (_min_size == 0 || child._automaton.size() < _min_size) {\n\t\t\t\t\t\t\t\t_min_automaton = child._automaton;\n\t\t\t\t\t\t\t\t_min_size = _min_automaton.size();\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t// delete automaton as it is bigger\n\t\t\t\t\t\t\t\t// than necessary\n\t\t\t\t\t\t\t\tchild._automaton = null;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\tchild._automaton = null;\n\t\t\t\t\t\tthrow e;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tfor (Tree child : children) {\n\t\t\t\t\tchild.calculate(level + 1, limit);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/** The root building block for the calculation of DRA/DSA */\n\tpublic static class Tree_Start extends Tree {\n\t\t/**\n\t\t * Constructor \n\t\t * @param ltl The LTL formula\n\t\t * @param options the LTL2DSTAR options\n\t\t * @param sched a reference back to the scheduler \n\t\t */\n\t\tpublic Tree_Start(SimpleLTL ltl, APSet apset, Options_LTL2DRA options, Scheduler sched) {\n\t\t\tsuper(ltl, apset, options, sched);\n\t\t\tgenerateTree();\n\t\t}\n\n\t\t/** Generate the tree */\n\t\tpublic void generateTree() {\n\t\t\tTree_Rabin rabin = null;\n\t\t\tTree_Streett streett = null;\n\n\t\t\tif (_options.automata == Options_LTL2DRA.AutomataType.RABIN ||\n\t\t\t\t\t_options.automata == Options_LTL2DRA.AutomataType.RABIN_AND_STREETT) {\n\t\t\t\trabin = new Tree_Rabin(_ltl, _apset, _options, _sched);\n\t\t\t}\n\n\t\t\tif (_options.automata == Options_LTL2DRA.AutomataType.STREETT ||\n\t\t\t\t\t_options.automata == Options_LTL2DRA.AutomataType.RABIN_AND_STREETT) {\n\t\t\t\tstreett = new Tree_Streett(_ltl.negate().simplify(), _apset, _options, _sched);\n\t\t\t}\n\n\t\t\tif (rabin != null && streett != null) {\n\t\t\t\tint rabin_est = rabin.guestimate();\n\t\t\t\tint streett_est = streett.guestimate();\n\n\t\t\t\tif (_options.verbose_scheduler) {\n\t\t\t\t\tSystem.err.println(\"NBA-Estimates: Rabin: \" + rabin_est + \" Streett: \" + streett_est);\n\t\t\t\t}\n\n\t\t\t\tif (rabin_est <= streett_est) {\n\t\t\t\t\taddChild(rabin);\n\t\t\t\t\taddChild(streett);\n\t\t\t\t} else {\n\t\t\t\t\taddChild(streett);\n\t\t\t\t\taddChild(rabin);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (rabin != null)\n\t\t\t\t\taddChild(rabin);\n\t\t\t\tif (streett != null) \n\t\t\t\t\taddChild(streett);\n\t\t\t}\n\n\n\t\t\t/*\t\t\tif (_options.opt_safra.stutter) {\n\t\t\t\tStutterSensitivenessInformation::ptr stutter_information(new StutterSensitivenessInformation);\n\t\t\t\tstutter_information->checkLTL(_ltl);\n\n\t\t\t\tif (!stutter_information->isCompletelyInsensitive() && _options.opt_safra.partial_stutter_check) {\n\t\t\t\t\tNBA_ptr nba, complement_nba;\n\t\t\t\t\tif (rabin) {\n\t\t\t\t\t\tnba=rabin->getNBA();\n\t\t\t\t\t} else if (streett) {\n\t\t\t\t\t\tnba=streett->getNBA();\n\t\t\t\t\t}\n\n\t\t\t\t\tif (rabin && streett) {\n\t\t\t\t\t\tcomplement_nba=streett->getNBA();\n\t\t\t\t\t}\n\n\t\t\t\t\tif (!nba) {\n\t\t\t\t\t\tstutter_information->checkPartial(*_ltl, _sched.getLTL2DRA());\n\t\t\t\t\t} else if (!complement_nba) {\n\t\t\t\t\t\tstutter_information->checkPartial(*nba, *_ltl->negate()->toPNF(), _sched.getLTL2DRA());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tstutter_information->checkNBAs(*nba, *complement_nba);\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (rabin) {\n\t\t\t\t\trabin->setStutterInformation(stutter_information);\n\t\t\t\t}\n\t\t\t\tif (streett) {\n\t\t\t\t\tstreett->setStutterInformation(stutter_information);\n\t\t\t\t}\n\t\t\t}\n\t\t\t */\n\t\t}\n\t}\n\n\t/** A building block for the calculation of a Rabin automaton \n\t * (via Safra, Scheck or Union) */\n\tpublic static class Tree_Rabin extends Tree {\n\n\t\tprivate Tree_Safra _tree_normal;\n\t\tprivate Tree_Union _tree_union;\n\n\t\t// private StutterSensitivenessInformation::ptr _stutter_information;\n\n\n\t\t/**\n\t\t * Constructor \n\t\t * @param ltl The LTL formula\n\t\t * @param options the LTL2DSTAR options\n\t\t * @param sched a reference back to the scheduler \n\t\t */\n\t\tpublic Tree_Rabin(SimpleLTL ltl, APSet apset, Options_LTL2DRA options, Scheduler sched) {\n\t\t\tsuper(ltl, apset, options, sched);\n\t\t\t_tree_normal = null;\n\t\t\t_tree_union = null;\n\t\t\tgenerateTree();\n\t\t}\n\n\t\t/** Estimate the size of the automaton (use the estimate of Safra's\n\t\t * building block ) */\n\t\tpublic int guestimate() {\n\t\t\tif (_tree_normal != null) {\n\t\t\t\treturn _tree_normal.guestimate();\n\t\t\t}\n\t\t\treturn 0;\n\t\t}\n\n\t\t/** Hook after calculation */\n\t\tpublic void hook_after_calculate() {\n\t\t\tif (_tree_normal != null && _sched.flagStatNBA()) {\n\t\t\t\t_comment = _comment + \"+NBAstd=\" + guestimate();\n\t\t\t}\n\t\t}\n\n\t\t/** Generate the tree */\n\t\tpublic void generateTree() {\n\t\t\t/* if (_options.scheck_path!=\"\") {\n\t\t\t\tif (LTL2DSTAR_Tree_Scheck::worksWith(*_ltl, _options.verbose_scheduler)) {\n\t  \t\t\t\taddChild(new LTL2DSTAR_Tree_Scheck(_ltl, _options, _sched));\n\t\t\t\t}\n\t\t\t\t// add stuff for path. check here\n      \t\t}*/\n\t\t\tif (_options.allow_union &&\t_ltl.kind == SimpleLTL.LTLType.OR) {\n\t\t\t\t_tree_union = new Tree_Union(_ltl, _apset, _options, _sched);\n\t\t\t\taddChild(_tree_union);\n\t\t\t}\n\n\t\t\t//\tif (!((_options.only_union && _options.allow_union) || (_options.only_safety && _options.safety))) {\n\t\t\tif (!((_options.only_union && _options.allow_union))) {\n\t\t\t\t_tree_normal = new Tree_Safra(_ltl, _apset, _options, _sched);\n\t\t\t\taddChild(_tree_normal);\n\t\t\t}\n\t\t}\n\n\t\tpublic NBA getNBA() {\n\t\t\tif (_tree_normal != null) {\n\t\t\t\treturn _tree_normal.getNBA();\n\t\t\t}\n\t\t\treturn null;\n\t\t}\n\n\t\t/* public void setStutterInformation(StutterSensitivenessInformation::ptr stutter_information) {\n\t\t\t_stutter_information=stutter_information;\n\t\t\tif (_tree_normal) {\n\t\t\t\t_tree_normal->setStutterInformation(_stutter_information);\n\t\t\t}\n\n\t\t\tif (_tree_union) {\n\t\t\t\t_tree_union->setStutterInformation(_stutter_information);\n\t\t\t}\n\t\t}*/\n\t}\n\n\n\t/** Building block for the translation from LTL to DRA using Safra's algorithm */\n\tpublic static class Tree_Safra extends Tree {\n\n\t\tprivate NBA _nba;\n\t\t// private StutterSensitivenessInformation::ptr _stutter_information;\n\n\t\t/**\n\t\t * Constructor \n\t\t * @param ltl The LTL formula\n\t\t * @param options the LTL2DSTAR options\n\t\t * @param sched a reference back to the scheduler \n\t\t */\n\t\tpublic Tree_Safra(SimpleLTL ltl, APSet apset, Options_LTL2DRA options, Scheduler sched) {\n\t\t\tsuper(ltl, apset, options, sched);\n\t\t\tgenerateTree();\n\t\t}\n\n\t\t/** Generate the tree */\n\t\tpublic void generateTree() {}\n\n\t\t/** Translate LTL -> NBA */\n\t\tpublic void generateNBA() {\n\t\t\tif (_nba == null) {\n\t\t\t\ttry {\n\t\t\t\t\t_nba = _ltl.toNBA(_apset);\n\t\t\t\t}\n\t\t\t\tcatch (PrismException e) {\n\t\t\t\t\t_nba = null;\n\t\t\t\t\tSystem.err.println(\"Scheduler.generateNBA() : \" + e);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tpublic NBA getNBA() {\n\t\t\tgenerateNBA();\n\t\t\treturn _nba;\n\t\t}\n\n\t\t/** Estimate the size of the DRA (returns the size of the NBA) */\n\t\tpublic int guestimate() {\n\t\t\tgenerateNBA();\n\t\t\tif (_nba != null) {\n\t\t\t\treturn _nba.size();\n\t\t\t}\n\t\t\treturn 0;\n\t\t}\n\n\t\t/** Translate the LTL formula to DRA using Safra's algorithm */\n\t\tpublic void calculate(int level, int limit) throws PrismException {\n\t\t\tif (_options.verbose_scheduler) {\n\t\t\t\tSystem.err.println(\"Calculate (\" + level + \"): \" + this.getClass().getName());\n\t\t\t\tSystem.err.println(\" Limit = \" + limit);\n\t\t\t}\n\n\t\t\tgenerateNBA();\n\n\t\t\tif (_nba == null) {\n\t\t\t\tthrow new PrismException(\"Couldn't create NBA from LTL formula\");\n\t\t\t}\n\t\t\t\n\t\t\t// _automaton = _sched.getLTL2DRA().nba2dra(_nba, limit, _options.detailed_states,\t_stutter_information);\n\t\t\t_automaton = _sched.getLTL2DRA().nba2dra(_nba, limit, _options.detailed_states);\n\t\t\t_comment = \"Safra[NBA=\" + _nba.size() +\t\"]\";\n\n\t\t\tif (_options.optimizeAcceptance) {\n\t\t\t\t_automaton.optimizeAcceptanceCondition();\n\t\t\t}\n\n\t\t\tif (_options.bisim) {\n\t\t\t\tDRAOptimizations dra_optimizer = new DRAOptimizations();\n\t\t\t\t_automaton = dra_optimizer.optimizeBisimulation(_automaton,\tfalse, _options.detailed_states, false);\n\t\t\t}\n\t\t}\n\n\t\t/*public void setStutterInformation(StutterSensitivenessInformation::ptr stutter_information) {\n\t\t\t_stutter_information=stutter_information;\n\t\t}\n\t\t */\n\t}\n\n\n\t/** Generate DRA by using the union construction on two DRAs */\n\tpublic static class Tree_Union extends Tree {\n\n\t\t/**\n\t\t * Constructor \n\t\t * @param ltl The LTL formula\n\t\t * @param options the LTL2DSTAR options\n\t\t * @param sched a reference back to the scheduler \n\t\t */\n\n\t\tpublic Tree_Union(SimpleLTL ltl, APSet apset, Options_LTL2DRA options, Scheduler sched) {\n\n\t\t\tsuper(ltl, apset, options, sched);\n\t\t\t_left_tree = null;\n\t\t\t_right_tree = null;\n\n\t\t\t_left = _ltl.left;\n\t\t\t_right = _ltl.right;\n\n\t\t\tgenerateTree();\n\t\t}\n\n\t\t/**\n\t\t * Generate the tree\n\t\t */\n\t\tpublic void generateTree() {\n\t\t\tOptions_LTL2DRA rec_opt = _options.clone();\n\t\t\trec_opt.recursion();\n\t\t\t_left_tree = new Tree_Rabin(_left, _apset, rec_opt, _sched);\n\t\t\taddChild(_left_tree);\n\t\t\t_right_tree = new Tree_Rabin(_right, _apset, rec_opt, _sched);\n\t\t\taddChild(_right_tree);\n\t\t}\n\n\t\t/**\n\t\t * Perform union construction\n\t\t */\n\t\tpublic void calculate(int level, int limit) throws PrismException {\n\t\t\tif (_options.verbose_scheduler) {\n\t\t\t\tSystem.err.println(\"Calculate (\" + level + \"): \" + this.getClass().getName());\n\t\t\t}\n\n\t\t\ttry {\n\t\t\t\tchildren.get(0).calculate(level + 1, limit);\n\t\t\t\tchildren.get(1).calculate(level + 1, limit);\n\t\t\t} catch (PrismException e) {\n\t\t\t\t_automaton = null;\n\t\t\t\tthrow e;\n\t\t\t}      \n\n\t\t\tif (children.get(0)._automaton == null || children.get(1)._automaton == null) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tboolean union_trueloop = _sched.getLTL2DRA().getOptions().union_trueloop;\n\t\t\t/* if (_sched.getLTL2DRA().getOptions().stutter) {\n\t\t\t\t_automaton=DRA_t::calculateUnionStuttered(*children[0]->_automaton,\n\t\t\t *children[1]->_automaton,\n\t\t\t\t\t\t_stutter_information,\n\t\t\t\t\t\tunion_trueloop,\n\t\t\t\t\t\t_options.detailed_states);\n\t\t\t} else {\n\t\t\t*/\t\t\t\n\t\t\t_automaton = children.get(0)._automaton.calculateUnion(children.get(1)._automaton,\tunion_trueloop,\t_options.detailed_states);\n\t\t\t/*      _automaton=DRAOperations::dra_union(*children[0]->_automaton, \n\t\t\t *children[1]->_automaton,\n\t\t\t\t\t  union_trueloop,\n\t\t\t\t\t  _options.detailed_states); */\n\t\t\t// }\n\t\t\t_comment = \"Union{\" + children.get(0)._comment + \",\" +\tchildren.get(1)._comment + \"}\";\n\n\t\t\tif (_options.optimizeAcceptance) {\n\t\t\t\t_automaton.optimizeAcceptanceCondition();\n\t\t\t}\n\n\t\t\tif (_options.bisim) {\n\t\t\t\tDRAOptimizations dra_optimizer = new DRAOptimizations();\n\t\t\t\t_automaton = dra_optimizer.optimizeBisimulation(_automaton,\tfalse, _options.detailed_states, false);\n\t\t\t}\n\t\t\thook_after_calculate();\n\t\t}\n\n\n\t\t/* public void setStutterInformation(StutterSensitivenessInformation::ptr stutter_information) {\n\t\t\t_stutter_information=stutter_information;\n\n\t\t\tStutterSensitivenessInformation::ptr \n\t\t\tleft_stutter_info(new StutterSensitivenessInformation(*stutter_information));\n\t\t\tStutterSensitivenessInformation::ptr \n\t\t\tright_stutter_info(new StutterSensitivenessInformation(*stutter_information));\n\n\t\t\tif (!stutter_information->isCompletelyInsensitive()) {\n\t\t\t\tleft_stutter_info->checkLTL(_left);\n\t\t\t\tright_stutter_info->checkLTL(_right);\n\t\t\t}\n\n\t\t\tif (!left_stutter_info->isCompletelyInsensitive()) {\n\t\t\t\tleft_stutter_info->checkPartial(*_left_tree->getNBA(), \n\t\t *_left->negate()->toPNF(), \n\t\t\t\t\t\t_sched.getLTL2DRA());\n\t\t\t}\n\n\t\t\tif (!right_stutter_info->isCompletelyInsensitive()) {\n\t\t\t\tright_stutter_info->checkPartial(*_right_tree->getNBA(), \n\t\t *_right->negate()->toPNF(), \n\t\t\t\t\t\t_sched.getLTL2DRA());\n\t\t\t}\n\n\t\t\t_left_tree->setStutterInformation(left_stutter_info);\n\t\t\t_right_tree->setStutterInformation(right_stutter_info); \n\t\t}\n\t\t */\n\n\t\tprivate Tree_Rabin _left_tree;\n\t\tprivate Tree_Rabin _right_tree;\n\n\t\tprivate SimpleLTL _left;\n\t\tprivate SimpleLTL _right;\n\n\t\t// private StutterSensitivenessInformation::ptr _stutter_information;\n\t}\n\n\n\t/**\n\t * Generate Streett automaton by calculating the Rabin automaton\n\t * for the negated formula\n\t */  \n\tpublic static class Tree_Streett extends Tree {\n\n\t\tprivate Tree_Rabin _tree_rabin;\n\t\t// private StutterSensitivenessInformation::ptr _stutter_information;\n\n\t\t/**\n\t\t * Constructor \n\t\t * @param ltl The LTL formula\n\t\t * @param options the LTL2DSTAR options\n\t\t * @param sched a reference back to the scheduler \n\t\t */\n\n\t\tpublic Tree_Streett(SimpleLTL ltl, APSet apset, Options_LTL2DRA options, Scheduler sched) {\n\t\t\tsuper(ltl, apset, options, sched);\n\t\t\tgenerateTree();\n\t\t}\n\n\t\t/** Estimate automaton size (use estimate of Rabin building block) */\n\t\tpublic int guestimate() {\n\t\t\tif (children.get(0) != null) {\n\t\t\t\treturn children.get(0).guestimate();\n\t\t\t}\n\t\t\treturn 0;\n\t\t}\n\n\t\tpublic NBA getNBA() {\n\t\t\tif (_tree_rabin != null) {\n\t\t\t\treturn _tree_rabin.getNBA();\n\t\t\t}\n\t\t\treturn null;\n\t\t}\n\n\t\t/** Generate tree */\n\t\tpublic void generateTree() {\n\t\t\tOptions_LTL2DRA opt = _options;\n\t\t\topt.automata = Options_LTL2DRA.AutomataType.RABIN;\n\t\t\t// opt.scheck_path=\"\"; // disable scheck\n\t\t\t_tree_rabin = new Tree_Rabin(_ltl, _apset, opt, _sched);\n\t\t\taddChild(_tree_rabin);\n\t\t}    \n\n\t\t/** Calculate */\n\t\tpublic void calculate(int level, int limit) throws PrismException {\n\t\t\tif (_options.verbose_scheduler) {\n\t\t\t\tSystem.err.println(\"Calculate (\" + level + \"): \" + this.getClass().getName());\n\t\t\t}\n\n\t\t\ttry {\n\t\t\t\tchildren.get(0).calculate(level, limit);\n\t\t\t} catch (PrismException e) {\n\t\t\t\t_automaton = null;\n\t\t\t\tthrow e;\n\t\t\t}\n\n\t\t\t_automaton = children.get(0)._automaton;\n\t\t\t_comment = \"Streett{\" +\tchildren.get(0)._comment + \"}\";\n\n\t\t\tif (_automaton != null) {\n\t\t\t\t_automaton.considerAsStreett(true);\n\t\t\t}\n\n\t\t\thook_after_calculate();\n\t\t}\n\n\t\t/* void setStutterInformation(StutterSensitivenessInformation::ptr stutter_information) {\n\t\t\t_stutter_information=stutter_information;\n\t\t\t_tree_rabin->setStutterInformation(stutter_information);\n\t\t}*/\n\n\t}\n\n\t/** Constructor\n\t * @param ltl2dra the wrapper for LTL->NBA and NBA->DRA \n\t * @param opt_limits use limiting?\n\t * @param alpha the limiting factor \n\t */\n\tpublic Scheduler(LTL2DRA ltl2dra, boolean opt_limits, double alpha) {\n\t\t_ltl2dra = ltl2dra;\n\t\t_opt_limits = opt_limits;\n\t\t_alpha = alpha;\n\t\t_stat_NBA = false;\n\t}\n\n\n\n\t/** Calculate the new limit using factor alpha (returns 0 if no limit) */\n\tpublic int calcLimit(int limit) {\n\t\tif (limit == 0) {return limit;}\n\t\tif (flagOptLimits()) {\n\t\t\tdouble new_limit = (limit * _alpha) + 1.0;\n\t\t\tif (new_limit > Integer.MAX_VALUE) {\n\t\t\t\tlimit = 0;\n\t\t\t} else {\n\t\t\t\tlimit = (int)new_limit;\n\t\t\t}\n\t\t}\n\t\treturn limit;\n\t}\n\n\t/** \n\t * Generate a DRA/DSA for the LTL formula \n\t */\n\tpublic DRA calculate(SimpleLTL ltl, APSet apset, Options_LTL2DRA ltl_opt) throws PrismException {\n\n\t\tif (ltl_opt.verbose_scheduler) {\n\t\t\tSystem.err.println(ltl);\n\t\t}\n\n\t\tTree root = new Tree_Start(ltl, apset, ltl_opt, this);\n\n\t\tif (ltl_opt.verbose_scheduler) {\n\t\t\troot.printTree(System.err, 0);\n\t\t}\n\n\t\troot.calculate(0,0);\n\n\t\tDRA result = root._automaton;\n\t\tif (result != null) {\n\t\t\tresult.setComment(root._comment + getTimingInformation());\n\t\t}\n\t\treturn result;\n\t}\n\n\tpublic String getTimingInformation() {\n\t\t/* if (StutterSensitivenessInformation::hasTimekeeping()) {\n\t\t\tunsigned long ms=StutterSensitivenessInformation::getTimeKeeper().getElapsedMilliseconds();\n\t\t\treturn \" TIME(stuttercheck)=:\"+ \n\t\t\tboost::lexical_cast<std::string>(ms)+\n\t\t\t\":\";\n\t\t} else {\n\t\t */\n\t\treturn \"\";\n\t\t// }\n\t}\n\n\t/** Get the LTL2DRA wrapper class */\n\tpublic LTL2DRA getLTL2DRA() {\n\t\treturn _ltl2dra;\n\t}\n\n\tpublic boolean flagOptLimits() {return _opt_limits;}\n\n\t/** Get the state of the StatNBA flag */\n\tpublic boolean flagStatNBA() {return _stat_NBA;}\n\n\t/** Set the value of the StatNBA flag */\n\tpublic void flagStatNBA(boolean value) {_stat_NBA=value;}\n\t\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/StateMapper.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport java.util.HashMap;\n\n/** @file\n * Provides StateMapper\n */\n\n/** A mapper from KeyType to StateType, ResultType can be used as an alternative key type. */\npublic class StateMapper <R extends NBA2DAResult<K>, K extends NBA2DAState, S extends DA_State> implements StateMapperInterface<R,K,S> {\n\n\t/** The hash map from StateType to MappedStateType */\n\tprivate HashMap<K,S> _map;\n\t/** The number of mappings */\n\tprivate int _count;\n\n\t/** Constructor. */\n\tpublic StateMapper() {\n\t\t_count = 0;\n\t\t_map = new HashMap<K,S>();\n\t}\n\t\t\n\t/** Clear the mapping */\n\tpublic void clear() {\n\t\t_map.clear();\n\t\t_count = 0;\n\t}\n\n\t/** Add a mapping. \n\t * @param key the key\n\t * @param state the state\n\t */\n\t// public StateType add(KeyType key, StateType state) {\n\tpublic void add(K key, S state) {\n\t\t// System.out.println(\"Adding hash \" + key.hashCode());\n\t\tif (!_map.containsKey(key))\n\t\t\t++_count;\n\t\t_map.put(key, state);\n\t\t// return state; // different semantics than java hashmaps\n\t\t// System.out.println(\"Item count: \" + _count);\n\t}\n\n\n\t/** Find a mapping. \n\t * @param key the key\n\t * @return the state (or the NULL pointer if not found)\n\t */\n\tpublic S find(K key) {\n\t\t// System.out.println(\"Looking for hash \" + key.hashCode());\n\t\t// if (_map.containsKey(key)) System.out.println(\"Match\");\n\t\t// else System.out.println(\"Miss\");\n\t\treturn _map.get(key);\n\t}\n\n\t/** Find a mapping using ResultType. \n\t * @param result\n\t * @return the state (or the NULL pointer if not found)\n\t */\n\tpublic S find(R result) {\n\t\treturn find(result.getState());\n\t}\n\n\t/** Get number of mappings.\n\t * @return the number of mappings\n\t */\n\tpublic int size() {\n\t\treturn _count;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/StateMapperFuzzy.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** @file\n * Provide class StateMapperFuzzy\n */\n\nimport java.util.HashMap;\nimport java.util.Vector;\n\n/**\n * A mapping from KeyType to StateType, with ResultType as an alternative key type, which can be fuzzily matched\n * using CandidateMatcher.\n */\npublic class StateMapperFuzzy <CandidateMatcher extends SafraTreeCandidateMatcher> implements StateMapperInterface<SafraTreeTemplate, SafraTree, DA_State>\n{\n\tprivate class ListValue {\n\t\tSafraTree _key;\n\t\tDA_State _state;\n\t}\n\n\t/** The hash map from StateType to MappedStateType */\n\tprivate HashMap<AbstractedKeyType, Vector<ListValue>> _map;\n\tprivate int _count;\n\n\t/** Constructor. */\n\tpublic StateMapperFuzzy() {\n\t\t_count = 0;\n\t\t_map = new HashMap<AbstractedKeyType, Vector<ListValue>>();\n\t}\n\n\t/** Clear the mapping. */\n\tpublic void clear() {\n\t\t_map.clear();\n\t\t_count = 0;\n\t}\n\n\t/** \n\t * Search for a mapping, fuzzily\n\t * @param result the query\n\t * @return the corresponding state or NULL otherwise\n\t */\n\tpublic DA_State find(SafraTreeTemplate result) {\n\n\t\tAbstractedKeyType search_key = new AbstractedKeyType(result.getState());\n\n\t\tVector<ListValue> list = _map.get(search_key);\n\t\tif (list != null) {\n\t\t\tfor (ListValue elem : list) {\n\t\t\t\tif (CandidateMatcher.isMatch(result, elem._key)) {\n\t\t\t\t\treturn elem._state;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// not found\n\t\treturn null;\n\t}\n\n\n\t/** \n\t * Add a mapping\n\t * @param key the key\n\t * @param state the state\n\t */\n\tpublic void add(SafraTree key, DA_State state) {\n\t\t\n\t\tAbstractedKeyType akey = new AbstractedKeyType(key);\n\n\t\tListValue item = new ListValue();\n\n\t\titem._key = key;\n\t\titem._state = state;\n\n\t\tif (_map.get(akey) == null) {\n\t\t\t_map.put(akey, new Vector<ListValue>());\n\t\t}\n\t\t_map.get(akey).add(item);\n\n\t\t_count++;\n\t}\n\n\t/** Get the number of trees */\n\tpublic int size() {return _count;}\n\n\n\n\t/** \n\t * A structure that abstracts the Keytype to its abstracted properties\n\t */\n\tprivate class AbstractedKeyType {\n\n\t\tprivate SafraTree _key;\n\n\t\tpublic AbstractedKeyType(SafraTree key) {_key = key;}\n\t\t\n\t\tpublic int hashCode() {\n\t\t\treturn CandidateMatcher.hash(_key);\n\t\t}\n\n\t\tpublic boolean equals(AbstractedKeyType other) {\n\t\t\treturn CandidateMatcher.abstract_equal_to(_key, other._key);\n\t\t}\n\t\t\n\t\tpublic boolean equals(Object o) {\n\t\t\treturn (o.getClass() == this.getClass()) && this.equals((AbstractedKeyType) o);\n\t\t}\n\n\t\tpublic boolean lessThan(AbstractedKeyType other) {\n\t\t\treturn CandidateMatcher.abstract_less_than(_key, other._key);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/StateMapperInterface.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\npublic interface StateMapperInterface<R extends NBA2DAResult<K>, K extends NBA2DAState, S extends DA_State> {\n\n\t/** Clear the mapping */\n\tpublic abstract void clear();\n\t\n\t/** Add a mapping. \n\t * @param key the key\n\t * @param state the state\n\t */\n\tpublic abstract void add(K key, S state);\n\t\n\t/** Find a mapping using ResultType. \n\t * @param result\n\t * @return the state (or the NULL pointer if not found)\n\t */\n\tpublic abstract S find(R result);\n\n\t/** Get number of mappings.\n\t * @return the number of mappings\n\t */\n\tpublic abstract int size();\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/UnionAcceptanceCalculator.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\nimport prism.PrismException;\n\n/**\n * Specialized UnionAcceptanceCalculator for RabinAcceptance, for calculating the acceptance in the union automaton.\n * This approach merges the acceptance signatures of the two states in the union tuple, the union is provided by\n * the semantics of the Rabin acceptance condition (There <i>exists</i> an acceptance pair ....)\n */\npublic class UnionAcceptanceCalculator {\n\n\t/** The acceptance condition of the first automaton. */\n\tprivate RabinAcceptance _acc_1;\n\t/** The acceptance condition of the second automaton. */\n\tprivate RabinAcceptance _acc_2;\n\n\t/** The size of the acceptance condition in the original automaton. */\n\tprivate int _acc_size_1, _acc_size_2;\n\n\t/**\n\t * Constructor. \n\t * @param acc_1 The RabinAcceptance condition from automaton 1\n\t * @param acc_2 The RabinAcceptance condition from automaton 2\n\t */\n\tpublic UnionAcceptanceCalculator(RabinAcceptance acc_1,\tRabinAcceptance acc_2) throws PrismException {\n\t\t_acc_1 = acc_1;\n\t\t_acc_2  = acc_2;\n\t\t_acc_size_1 = _acc_1.size();\n\t\t_acc_size_2 = _acc_2.size();\n\t}\n\n\t/**\n\t * Prepares the acceptance condition in the result union automaton. If the two automata have k1 and k2 \n\t * acceptance pairs, this function allocates k1+k2 acceptance pairs in the result automaton.\n\t * @param acceptance_result The acceptance condition in the result automaton.\n\t */\n\tpublic void prepareAcceptance(RabinAcceptance acceptance_result) {\n\t\tacceptance_result.newAcceptancePairs(_acc_size_1+_acc_size_2);\n\t}\n\n\n\t/**\n\t * Calculate the acceptance signature for the union of two states.\n\t * @param da_state_1 index of the state in the first automaton\n\t * @param da_state_2 index of the state in the second automaton\n\t * @return A Rabin acceptance signature\n\t */\n\tRabinSignature calculateAcceptance(int da_state_1, int da_state_2) {\n\t\tRabinSignature signature = new RabinSignature(_acc_size_1 + _acc_size_2);\n\n\t\tfor (int i = 0; i < _acc_size_1; i++) {\n\t\t\tif (_acc_1.isStateInAcceptance_L(i, da_state_1)) {\n\t\t\t\tsignature.setL(i, true);\n\t\t\t}\n\t\t\tif (_acc_1.isStateInAcceptance_U(i, da_state_1)) {\n\t\t\t\tsignature.setU(i, true);\n\t\t\t}\n\t\t}\n\n\t\tfor (int j=0; j < _acc_size_2; j++) {\n\t\t\tif (_acc_2.isStateInAcceptance_L(j, da_state_2)) {\n\t\t\t\tsignature.setL(j + _acc_size_1, true);\n\t\t\t}\n\t\t\tif (_acc_2.isStateInAcceptance_U(j, da_state_2)) {\n\t\t\t\tsignature.setU(j + _acc_size_1, true);\n\t\t\t}\n\t\t}\n\t\treturn signature;\n\t}\n}\n"
  },
  {
    "path": "prism/src/jltl2dstar/UnionNBA2DRA.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** @file\n * Provides class NBA2DA, which converts an NBA to a DA\n */\nimport java.util.Stack;\n\nimport jltl2ba.APElement;\nimport jltl2ba.APElementIterator;\nimport jltl2ba.APSet;\nimport prism.PrismException;\n\n/**\n * Convert an NBA to a DA using the specified Algorithm_t and StateMapper_t\n */\n//template < typename Algorithm_t, \n//typename DA_t,\n//typename StateMapper_t=StateMapper<typename Algorithm_t::result_t,\n//typename Algorithm_t::state_t,\n//typename DA_t::state_type> >\npublic class UnionNBA2DRA {\n\t\n\t/** Save detailed information on the Safra trees in the states? */\n\tprivate boolean _detailed_states;\n\n\t/** \n\t * Constructor\n\t * detailedStates default = false \n\t */\n\tpublic UnionNBA2DRA(boolean detailedStates) {\n\t\t_detailed_states = detailedStates;\n\t}\n\n\t/**\n\t * Generate a DA using the Algorithm\n\t * Throws LimitReachedException if a limit is set (>0) and\n\t * there are more states in the generated DA than the limit. \n\t * @param algo the algorithm \n\t * @param da_result the DA where the result is stored \n\t *        (has to have same APSet as the nba)\n\t * @param limit a limit for the number of states (0 disables the limit - default).\n\t */\n\tpublic void convert(DAUnionAlgorithm algo, DRA da_result, int limit, StateMapper<UnionState.Result,UnionState,DA_State> state_mapper) throws PrismException {\n\n\t\tAPSet ap_set = da_result.getAPSet();\n\n\t\tif (algo.checkEmpty()) {\n\t\t\tda_result.constructEmpty();\n\t\t\treturn;\n\t\t}\n\n\t\talgo.prepareAcceptance(da_result.acceptance());\n\n\t\tUnionState start = algo.getStartState();\n\t\tDA_State start_state = da_result.newState();\n\t\tstart.generateAcceptance(start_state.acceptance());\n\t\tif (_detailed_states) {\n\t\t\tstart_state.setDescription(start.toHTML());\n\t\t}\n\n\t\tstate_mapper.add(start, start_state);\n\t\tda_result.setStartState(start_state);\n\n\t\tStack<unprocessed_value> unprocessed = new Stack<unprocessed_value>();\n\t\tunprocessed.push(new unprocessed_value(start, start_state));\n\n\t\twhile (!unprocessed.empty()) {\n\t\t\tunprocessed_value top = unprocessed.pop();\n\n\t\t\tUnionState cur = top.algo_state;\n\t\t\tDA_State from = top.da_state;\n\t\t\t\n\t\t\tfor (APElementIterator it_elem = new APElementIterator(ap_set.size()); it_elem.hasNext(); ) {\n\n\t\t\t\tAPElement elem = it_elem.next();\n\n\t\t\t\tUnionState.Result result = algo.delta(cur, elem);\n\n\t\t\t\tDA_State to = state_mapper.find(result);\n\n\t\t\t\tif (to == null) {\n\t\t\t\t\tto = da_result.newState();\n\t\t\t\t\tresult.getState().generateAcceptance(to.acceptance());\n\n\t\t\t\t\tif (_detailed_states) {\n\t\t\t\t\t\tto.setDescription(result.getState().toHTML());\n\t\t\t\t\t}\n\n\t\t\t\t\tstate_mapper.add(result.getState(), to);\n\t\t\t\t\tunprocessed.push(new unprocessed_value(result.getState(), to));\n\t\t\t\t}\n\n\t\t\t\tfrom.edges().put(elem, to);\n\n\t\t\t\tif (limit != 0 && da_result.size() > limit) {\n\t\t\t\t\tthrow new PrismException(\"State limit reached\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t}\n\n\tprivate class unprocessed_value {\n\t\tpublic UnionState algo_state;\n\t\tpublic DA_State da_state;\n\t\t\n\t\tpublic unprocessed_value(UnionState _algo_state, DA_State _da_state) {\n\t\t\talgo_state = _algo_state;\n\t\t\tda_state = _da_state;\n\t\t}\n\t}\n}\n\n\n\n"
  },
  {
    "path": "prism/src/jltl2dstar/UnionState.java",
    "content": "/*\n * This file is part of a Java port of the program ltl2dstar\n * (http://www.ltl2dstar.de/) for PRISM (http://www.prismmodelchecker.org/)\n * Copyright (C) 2005-2007 Joachim Klein <j.klein@ltl2dstar.de>\n * Copyright (c) 2007 Carlos Bederian\n *\n * This program is free software; you can redistribute it and/or modify\n * it under the terms of the GNU General Public License version 2 as \n *  published by the Free Software Foundation.\n *\n * This program is distributed in the hope that it will be useful,\n * but WITHOUT ANY WARRANTY; without even the implied warranty of\n * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n * GNU General Public License for more details.\n *\n * You should have received a copy of the GNU General Public License\n * along with this program; if not, write to the Free Software\n * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n */\n\npackage jltl2dstar;\n\n/** A state representing a union state from two DA. */\npublic class UnionState implements Comparable<UnionState>,NBA2DAState {\n\t\n\tpublic static class Result implements NBA2DAResult<UnionState> {\n\t\tprivate UnionState state;\n\t\tpublic Result(UnionState state_) {\n\t\t\tstate = state_;\n\t\t}\n\t\tpublic UnionState getState() {\n\t\t\treturn state;\n\t\t}\n\t}\n\t\n\t/** Index of the state from the first automaton */\n\tprotected int da_state_1;\n\t/** Index of the state from the second automaton */\n\tprotected int da_state_2;\n\t/** A shared_ptr with the acceptance signature of this state */\n\tRabinSignature signature;\n\t/** A shared_ptr to a string containing a detailed description of this state */\n\tString description;\n\n\t/** Constructor.\n\t * @param da_state_1_ index of the state in the first automaton\n\t * @param da_state_2_ index of the state in the second automaton\n\t * @param acceptance_calculator UnionAcceptanceCalculator\n\t */\n\tpublic UnionState(int da_state_1_, int da_state_2_,\tUnionAcceptanceCalculator acceptance_calculator) {\n\t\tda_state_1 = da_state_1_;\n\t\tda_state_2 = da_state_2_;\n\t\tsignature = acceptance_calculator.calculateAcceptance(da_state_1, da_state_2);\n\t\tdescription = \"\";\n\t}\n\n\tpublic int compareTo(UnionState other) {\n\t\tif (da_state_1 != other.da_state_1)\n\t\t\treturn da_state_1 - other.da_state_1;\n\t\telse return da_state_2 - other.da_state_2;\n\t}\n\t\n\tpublic boolean equals(UnionState other) {\n\t\treturn ((da_state_1 == other.da_state_1) && (da_state_2 == other.da_state_2));\n\t}\n\t\n\tpublic boolean equals(Object o) {\n\t\treturn (o instanceof UnionState && this.equals((UnionState) o));\n\t}\n\t\n\t/** Copy acceptance signature for this state\n\t * @param acceptance (<b>out</b>) AcceptanceForState for the state in the result automaton \n\t */\n\tpublic void generateAcceptance(AcceptanceForState acceptance) {\n\t\tacceptance.setSignature(signature);\n\t}\n\n\t/** Copy acceptance signature for this state\n\t * @param acceptance (<b>out</b>) acceptance signature for the state in the result automaton \n\t */\n\t// void generateAcceptance(da_signature_t& acceptance) const {\n//\t\tacceptance=*signature;\n//\t}\n\n\t/** Return the acceptance acceptance signature for this state\n\t * @return the acceptance signature for this state\n\t */\n\tpublic RabinSignature generateAcceptance() {\n\t\treturn signature;\n\t}\n\n\t/**\n\t * Set the detailed description for this state\n\t * @param description_ the description\n\t */\n\tpublic void setDescription(String description_) {\n\t\tdescription = description_;\n\t}\n\n\t/** Generate a simple representation of this state \n\t * @return a string with the representation\n\t */\n\tpublic String toString() {\n\t\treturn \"(\" + da_state_1 + \",\" + da_state_1 + \")\";\n\t}\n\t\n    /** Return the detailed description \n     * @return the detailed description\n     */\n    public String toHTML() {\n        return description;\n    }\n\n\t/** Calculates the hash for the union state. \n\t * @param hash the HashFunction functor used for the calculation\n\t */\n\t// template <class HashFunction>\n\t// void hashCode(HashFunction& hash) {\n\t// \t\thash.hash(da_state_1);\n\t// \t\thash.hash(da_state_2);\n\t\t// we don't have to consider the signature as there is a \n\t\t// 1-on-1 mapping between <da_state_1, da_state_2> -> signature\n\t// }\n    public int hashCode() {\n    \treturn da_state_1 + da_state_2 * 31;\n    }\n\n}"
  },
  {
    "path": "prism/src/jltl2dstar/package-info.java",
    "content": "/**\n * Java port of the LTL to deterministic Rabin automata conversion library.\n */\npackage jltl2dstar;\n"
  },
  {
    "path": "prism/src/manifest.txt",
    "content": "Main-Class: userinterface.GUIPrism\r\nClass-Path: pepa.zip\r\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ExportLabels.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cinttypes>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// local function prototypes\nstatic void export_rec(DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t index);\n\n// globals\nstatic const char *export_name;\nstatic int num_labels;\nstatic const char **label_strings;\nstatic DdNode ***dd_array;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_mtbdd_PrismMTBDD_PM_1ExportLabels\n(\nJNIEnv *env,\njclass cls,\njlongArray __jlongpointer la,\t\t// labels\njobjectArray ln,\t// label names\njstring na,\t\t// export name\njlong __jlongpointer v,\t// (row) vars\njint num_vars,\njlong __jlongpointer od,\t// odd\njint et,\t\t// export type\njstring fn\t\t// filename\n)\n{\n\tjlong *labels;\n\tjobject *label_names;\n\tDdNode **vars = jlong_to_DdNode_array(v);\n\tODDNode *odd = jlong_to_ODDNode(od);\n\tint i;\n\t\n\t// unpack jni arrays\n\tnum_labels = env->GetArrayLength(la);\n\tlabels = env->GetLongArrayElements(la, 0);\n\tlabel_names = new jobject[num_labels];\n\tfor (i = 0; i < num_labels; i++) label_names[i] = env->GetObjectArrayElement(ln, i);\n\tlabel_strings = new const char*[num_labels];\n\tfor (i = 0; i < num_labels; i++) label_strings[i] = env->GetStringUTFChars((jstring)label_names[i], 0);\n\t// should be fine to cast jobject to jstring as we know type is ok\n\t// could check for failure with env->ExceptionCheck() if necessary\n\t\n\t// store export info\n\tif (!store_export_info(et, fn, env)) return -1;\n\texport_name = na ? env->GetStringUTFChars(na, 0) : \"V\";\n\t\n\t// print file header\n\tswitch (export_type) {\n\tcase EXPORT_PLAIN:\n\t\tfor (i = 0; i < num_labels; i++)\n\t\t\texport_string(\"%s%d=\\\"%s\\\"\", ((i>0)?\" \":\"\"), i, label_strings[i]);\n\t\texport_string(\"\\n\");\n\t\tbreak;\n\tcase EXPORT_MATLAB:\n\t\tfor (i = 0; i < num_labels; i++)\n\t\t\texport_string(\"%s_%s=sparse(%\" PRId64 \",1);\\n\", export_name, label_strings[i], odd->eoff+odd->toff);\n\t\texport_string(\"\\n\");\n\t\tbreak;\n\tcase EXPORT_MRMC:\n\t\texport_string(\"#DECLARATION\\n\");\n\t\tfor (i = 0; i < num_labels; i++)\n\t\t\texport_string(\"%s%s\", ((i>0)?\" \":\"\"), label_strings[i]);\n\t\texport_string(\"\\n#END\\n\");\n\t\tbreak;\n\t}\n\t\n\t// set up global arrays used for recursive traversal of set of dds\n\tdd_array = new DdNode**[num_vars+1];\n\tfor (i = 0; i < num_vars+1; i++) {\n\t\tdd_array[i] = new DdNode*[num_labels];\n\t}\n\tfor (i = 0; i < num_labels; i++) {\n\t\tdd_array[0][i] = jlong_to_DdNode(labels[i]);\n\t}\n\t\n\t// print main part of file\n\texport_rec(vars, num_vars, 0, odd, 0);\n\t\n\t// free memory\n\tfor (i = 0; i < num_vars+1; i++) {\n\t\tdelete[] dd_array[i];\n\t}\n\tdelete[] dd_array;\n\t\n\t// clean up jni stuff\n\tfor (i = 0; i < num_labels; i++) env->ReleaseStringUTFChars((jstring)label_names[i], label_strings[i]);\n\tdelete[] label_strings;\n\tdelete[] label_names;\n\tenv->ReleaseLongArrayElements(la, labels, 0);\n\t\n\t// close file, etc.\n\tif (export_file) fclose(export_file);\n\tif (na) env->ReleaseStringUTFChars(na, export_name);\n\t\n\treturn 0;\n}\n\n//------------------------------------------------------------------------------\n\nstatic void export_rec(DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t index)\n{\n\tint i;\n\tbool all_zero;\n\t\n\t// base case - all zero terminals\n\tall_zero = true;\n\tfor (i = 0; i < num_labels; i++) {\n\t\tif (dd_array[level][i] != Cudd_ReadZero(ddman)) { all_zero = false; break; }\n\t}\n\tif (all_zero) return;\n\t\n\t// base case - non zero terminal\n\tif (level == num_vars) {\n\t\t// print state index\n\t\tswitch (export_type) {\n\t\tcase EXPORT_PLAIN: export_string(\"%\" PRId64 \":\", index); break;\n\t\tcase EXPORT_MRMC: export_string(\"%\" PRId64, index+1); break;\n\t\t}\n\t\t// print labels\n\t\tfor (i = 0; i < num_labels; i++) {\n\t\t\tif (dd_array[level][i] != Cudd_ReadZero(ddman)) {\n\t\t\t\tswitch (export_type) {\n\t\t\t\tcase EXPORT_PLAIN: export_string(\" %d\", i); break;\n\t\t\t\tcase EXPORT_MATLAB: export_string(\"%s_%s(%\" PRId64 \")=1;\\n\", export_name, label_strings[i], index+1); break;\n\t\t\t\tcase EXPORT_MRMC: export_string(\" %s\", label_strings[i]); break;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tswitch (export_type) {\n\t\tcase EXPORT_PLAIN: export_string(\"\\n\"); break;\n\t\tcase EXPORT_MRMC: export_string(\"\\n\"); break;\n\t\t}\n\t\treturn;\n\t}\n\t\n\t// recurse - elses\n\tfor (i = 0; i < num_labels; i++) {\n\t\tif (Cudd_NodeReadIndex(dd_array[level][i]) > Cudd_NodeReadIndex(vars[level])) {\n\t\t\tdd_array[level+1][i] = dd_array[level][i];\n\t\t} else {\n\t\t\tdd_array[level+1][i] = Cudd_E(dd_array[level][i]);\n\t\t}\n\t}\n\texport_rec(vars, num_vars, level+1, odd->e, index);\n\t\n\t// recurse - thens\n\tfor (i = 0; i < num_labels; i++) {\n\t\tif (Cudd_NodeReadIndex(dd_array[level][i]) > Cudd_NodeReadIndex(vars[level])) {\n\t\t\tdd_array[level+1][i] = dd_array[level][i];\n\t\t} else {\n\t\t\tdd_array[level+1][i] = Cudd_T(dd_array[level][i]);\n\t\t}\n\t}\n\texport_rec(vars, num_vars, level+1, odd->t, index+odd->eoff);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ExportMatrix.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cinttypes>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// local function prototypes\nstatic void export_rec(DdNode *dd, DdNode **rvars, DdNode **cvars, int num_vars, int level, ODDNode *row, ODDNode *col, int64_t r, int64_t c);\n\n// globals\nstatic const char *export_name;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_mtbdd_PrismMTBDD_PM_1ExportMatrix\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer m,\t// matrix\njstring na,\t\t// matrix name\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer od,\t// odd\njint et,\t\t// export type\njstring fn,\t\t// filename\njstring rsn,    // reward struct name\njboolean neh    // noexportheaders\n)\n{\n\tDdNode *matrix = jlong_to_DdNode(m);\t\t// matrix\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tODDNode *odd = jlong_to_ODDNode(od);\n\t\n\t// store export info\n\tif (!store_export_info(et, fn, env)) return -1;\n\texport_name = na ? env->GetStringUTFChars(na, 0) : \"M\";\n\t\n\t// print file header\n\tif (export_type == EXPORT_PLAIN && !neh) {\n\t\texport_string(\"# Reward structure\");\n\t\tif (env->GetStringUTFLength(rsn) > 0) {\n\t\t\tconst char *header = env->GetStringUTFChars(rsn,0);\n\t\t\texport_string(\" \\\"%s\\\"\", header);\n\t\t\tenv->ReleaseStringUTFChars(rsn, header);\n\t\t}\n\t\texport_string(\"\\n\");\n\t\texport_string(\"# Transition rewards\\n\");\n\t}\n\tswitch (export_type) {\n\tcase EXPORT_PLAIN: export_string(\"%\" PRId64 \" %.0f\\n\", odd->eoff+odd->toff, DD_GetNumMinterms(ddman, matrix, num_rvars+num_cvars)); break;\n\tcase EXPORT_MATLAB: export_string(\"%s = sparse(%\" PRId64 \",%\" PRId64 \");\\n\", export_name, odd->eoff+odd->toff, odd->eoff+odd->toff); break;\n\tcase EXPORT_DOT: case EXPORT_DOT_STATES: export_string(\"digraph %s {\\nnode [shape = box];\\n\", export_name); break;\n\t}\n\t\n\t// print main part of file\n\texport_rec(matrix, rvars, cvars, num_rvars, 0, odd, odd, 0, 0);\n\t\n\t// print file footer\n\tswitch (export_type) {\n\t// Note: no footer for EXPORT_DOT_STATES\n\tcase EXPORT_DOT: export_string(\"}\\n\"); break;\n\t}\n\t\n\t// close file, etc.\n\tif (export_file) fclose(export_file);\n\tif (na) env->ReleaseStringUTFChars(na, export_name);\n\t\n\treturn 0;\n}\n\n//------------------------------------------------------------------------------\n\nstatic void export_rec(DdNode *dd, DdNode **rvars, DdNode **cvars, int num_vars, int level, ODDNode *row, ODDNode *col, int64_t r, int64_t c)\n{\n\tDdNode *e, *t, *ee, *et, *te, *tt;\n\t\n\t// base case - zero terminal\n\tif (dd == Cudd_ReadZero(ddman)) return;\n\t\n\t// base case - non zero terminal\n\tif (level == num_vars) {\n\t\tswitch (export_type) {\n\t\tcase EXPORT_PLAIN: export_string(\"%\" PRId64 \" %\" PRId64 \" %.*g\\n\", r, c, export_model_precision, Cudd_V(dd)); break;\n\t\tcase EXPORT_MATLAB: export_string(\"%s(%\" PRId64 \",%\" PRId64 \")=%.*g;\\n\", export_name, r+1, c+1, export_model_precision, Cudd_V(dd)); break;\n\t\tcase EXPORT_DOT: case EXPORT_DOT_STATES: export_string(\"%\" PRId64 \" -> %\" PRId64 \" [ label=\\\"%.*g\\\" ];\\n\", r, c, export_model_precision, Cudd_V(dd)); break;\n\t\t}\n\t\treturn;\n\t}\n\t\n\t// recurse\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(cvars[level])) {\n\t\tee = et = te = tt = dd;\n\t}\n\telse if (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(rvars[level])) {\n\t\tee = te = Cudd_E(dd);\n\t\tet = tt = Cudd_T(dd);\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tif (Cudd_NodeReadIndex(e) > Cudd_NodeReadIndex(cvars[level])) {\n\t\t\tee = et = e;\n\t\t}\n\t\telse {\n\t\t\tee = Cudd_E(e);\n\t\t\tet = Cudd_T(e);\n\t\t}\n\t\tt = Cudd_T(dd);\n\t\tif (Cudd_NodeReadIndex(t) > Cudd_NodeReadIndex(cvars[level])) {\n\t\t\tte = tt = t;\n\t\t}\n\t\telse {\n\t\t\tte = Cudd_E(t);\n\t\t\ttt = Cudd_T(t);\n\t\t}\n\t}\n\n\texport_rec(ee, rvars, cvars, num_vars, level+1, row->e, col->e, r, c);\n\texport_rec(et, rvars, cvars, num_vars, level+1, row->e, col->t, r, c+col->eoff);\n\texport_rec(te, rvars, cvars, num_vars, level+1, row->t, col->e, r+row->eoff, c);\n\texport_rec(tt, rvars, cvars, num_vars, level+1, row->t, col->t, r+row->eoff, c+col->eoff);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ExportVector.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cinttypes>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// local function prototypes\nstatic void export_rec(DdNode *dd, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t index);\n\n// globals\nstatic const char *export_name;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_mtbdd_PrismMTBDD_PM_1ExportVector\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer ve,\t// vector\njstring na,\t\t// vector name\njlong __jlongpointer va,\t// vars\njint num_vars,\njlong __jlongpointer od,\t// odd\njint et,\t\t// export type\njstring fn,\t\t// filename\njstring rsn,    // reward struct name\njboolean neh    // noexportheaders\n)\n{\n\tDdNode *vector = jlong_to_DdNode(ve);\t\t// vector\n\tDdNode **vars = jlong_to_DdNode_array(va);\t// vars\n\tODDNode *odd = jlong_to_ODDNode(od);\n\t\n\t// store export info\n\tif (!store_export_info(et, fn, env)) return -1;\n\texport_name = na ? env->GetStringUTFChars(na, 0) : \"v\";\n\t\n\t// print file header\n\tswitch (export_type) {\n\tcase EXPORT_PLAIN:  // add header to srew file, when not disabled\n\tif (!neh) {\n\t\texport_string(\"# Reward structure\");\n\t\tif (env->GetStringUTFLength(rsn) > 0) {\n\t\t\tconst char *header = env->GetStringUTFChars(rsn,0);\n\t\t\texport_string(\" \\\"%s\\\"\", header);\n\t\t\tenv->ReleaseStringUTFChars(rsn, header);\n\t\t}\n\t\texport_string(\"\\n\");\n\t\texport_string(\"# State rewards\\n\");\n\t}\n\texport_string(\"%\" PRId64 \" %.0f\\n\", odd->eoff+odd->toff, DD_GetNumMinterms(ddman, vector, num_vars));\n                        break;\n\tcase EXPORT_MATLAB: export_string(\"%s = sparse(%\" PRId64 \",1);\\n\", export_name, odd->eoff+odd->toff); break;\n\t}\n\t\n\t// print main part of file\n\texport_rec(vector, vars, num_vars, 0, odd, 0);\n\t\n\t// close file, etc.\n\tif (export_file) fclose(export_file);\n\tif (na) env->ReleaseStringUTFChars(na, export_name);\n\t\n\treturn 0;\n}\n\n//------------------------------------------------------------------------------\n\nstatic void export_rec(DdNode *dd, DdNode **vars, int num_vars, int level, ODDNode *odd, int64_t index)\n{\n\tDdNode *e, *t;\n\t\n\t// base case - zero terminal\n\tif (dd == Cudd_ReadZero(ddman)) return;\n\t\n\t// base case - non zero terminal\n\tif (level == num_vars) {\n\t\tswitch (export_type) {\n\t\tcase EXPORT_PLAIN: export_string(\"%\" PRId64 \" %.*g\\n\", index, export_model_precision, Cudd_V(dd)); break;\n\t\tcase EXPORT_MATLAB: export_string(\"%s(%\" PRId64 \")=%.*g;\\n\", export_name, index+1, export_model_precision, Cudd_V(dd)); break;\n\t\tcase EXPORT_MRMC: export_string(\"%\" PRId64 \" %.*g\\n\", index+1, export_model_precision, Cudd_V(dd)); break;\n\t\t}\n\t\treturn;\n\t}\n\t\n\t// recurse\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(vars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\texport_rec(e, vars, num_vars, level+1, odd->e, index);\n\texport_rec(t, vars, num_vars, level+1, odd->t, index+odd->eoff);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_JOR.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include <memory>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Jacobi/JOR\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1JOR\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njdouble omega\t\t// omega (jor parameter)\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\n\t// mtbdds\n\tDdNode *reach, *diags, *id, *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tbool done;\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a,b\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// put diagonals in a vector\n\tdiags = DD_SumAbstract(ddman, diags, (transpose?rvars:cvars), num_cvars);\n\t\n\t// negate a\n\ta = DD_Apply(ddman, APPLY_TIMES, DD_Constant(ddman, -1), a);\n\t\n\t// transpose b if necessary\n\tif (transpose) {\n\t\tb = DD_PermuteVariables(ddman, b, rvars, cvars, num_rvars);\n\t}\n\t\n\t// divide a,b by diagonal\n\tCudd_Ref(diags);\n\ta = DD_Apply(ddman, APPLY_DIVIDE, a, diags);\n\tCudd_Ref(diags);\n\tb = DD_Apply(ddman, APPLY_DIVIDE, b, diags);\n\t\n\t// print out some memory usage\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"\\nIteration matrix MTBDD... [nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\ti = DD_GetNumNodes(ddman, diags);\n\tPN_PrintToMainLog(env, \"Diagonals MTBDD... [nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\n\t// store initial solution, transposing if necessary\n\tCudd_Ref(init);\n\tsol = init;\n\tif (transpose) {\n\t\tsol = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t}\n\t\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PM_JOR (\");\n\t\ttitle += (omega == 1.0)?\"Jacobi\": (\"JOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(sol, (transpose?cvars:rvars), num_rvars, odd, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// matrix multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, (transpose?cvars:rvars), (transpose?rvars:cvars), num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, (transpose?rvars:cvars), num_cvars, MM_BOULDER);\n\t\tCudd_Ref(b);\n\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, b);\n\t\tif (omega != 1.0) {\n\t\t\ttmp = DD_Apply(ddman, APPLY_TIMES, tmp, DD_Constant(ddman, omega));\n\t\t\tCudd_Ref(sol);\n\t\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, DD_Apply(ddman, APPLY_TIMES, sol, DD_Constant(ddman, 1-omega)));\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(tmp, (transpose?cvars:rvars), num_rvars, odd, 0);\n\n\t\t// check convergence\n\t\tswitch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// store accuracy info, once converged\n\t\t// the difference between vector values is not a reliable error bound\n\t\t// but we store it anyway in case it is useful for estimating a bound\n\t\t// TODO: handle cases where result is zero\n\t\tif (done) {\n\t\t\tCudd_Ref(tmp);\n\t\t\tCudd_Ref(sol);\n\t\t\tDdNode* difference = DD_Apply(ddman, APPLY_MINUS, tmp, sol);\n\t\t\tif (term_crit == TERM_CRIT_RELATIVE) {\n\t\t\t\tCudd_Ref(tmp);\n\t\t\t\tdifference = DD_Apply(ddman, APPLY_DIVIDE, difference, tmp);\n\t\t\t}\n\t\t\t// No DD absolute operator so check most +ve/-ve\n\t\t\tdouble max_diff = fabs(DD_FindMax(ddman, difference));\n\t\t\tdouble min_diff = fabs(DD_FindMin(ddman, difference));\n\t\t\tlast_error_bound = max_diff > min_diff ? max_diff : min_diff;\n\t\t\tCudd_RecursiveDeref(ddman, difference);\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\n\t// transpose solution if necessary\n\tif (transpose) {\n\t\tsol = DD_PermuteVariables(ddman, sol, cvars, rvars, num_rvars);\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", (omega == 1.0)?\"Jacobi\":\"JOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, id);\n\tCudd_RecursiveDeref(ddman, diags);\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, b);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { Cudd_RecursiveDeref(ddman, sol); PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); return 0; }\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_JORInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Jacobi/JOR (interval variant)\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1JORInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njdouble omega,\t\t// omega (jor parameter)\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t\t// upper bound values\n\n\t// mtbdds\n\tDdNode *reach, *diags, *id, *sol_below, *sol_above, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tbool done;\n\n\tif (omega <= 0.0 || omega > 1.0) {\n\t\tPN_SetErrorMessage(\"Interval iteration requires 0 < omega <= 1.0, have omega = %g\", omega);\n\t\treturn ptr_to_jlong(NULL);\n\t}\n\n\tIntervalIteration helper(flags);\n\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a,b\n\tCudd_Ref(a);\n\tCudd_Ref(b);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// put diagonals in a vector\n\tdiags = DD_SumAbstract(ddman, diags, (transpose?rvars:cvars), num_cvars);\n\t\n\t// negate a\n\ta = DD_Apply(ddman, APPLY_TIMES, DD_Constant(ddman, -1), a);\n\t\n\t// transpose b if necessary\n\tif (transpose) {\n\t\tb = DD_PermuteVariables(ddman, b, rvars, cvars, num_rvars);\n\t}\n\t\n\t// divide a,b by diagonal\n\tCudd_Ref(diags);\n\ta = DD_Apply(ddman, APPLY_DIVIDE, a, diags);\n\tCudd_Ref(diags);\n\tb = DD_Apply(ddman, APPLY_DIVIDE, b, diags);\n\t\n\t// print out some memory usage\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"\\nIteration matrix MTBDD... [nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\ti = DD_GetNumNodes(ddman, diags);\n\tPN_PrintToMainLog(env, \"Diagonals MTBDD... [nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\n\t// store initial solutions, transposing if necessary\n\tCudd_Ref(lower);\n\tsol_below = lower;\n\tCudd_Ref(upper);\n\tsol_above = upper;\n\tif (transpose) {\n\t\tsol_below = DD_PermuteVariables(ddman, sol_below, rvars, cvars, num_rvars);\n\t\tsol_above = DD_PermuteVariables(ddman, sol_above, rvars, cvars, num_rvars);\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PM_JOR (\");\n\t\ttitle += (omega == 1.0)?\"Jacobi\": (\"JOR omega=\" + std::to_string(omega));\n\t\ttitle += \"), interval\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(sol_below, (transpose?cvars:rvars), num_rvars, odd, 0);\n\t\titerationExport->exportVector(sol_above, (transpose?cvars:rvars), num_rvars, odd, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\tbool below_unchanged = false, above_unchanged = false;\n\n\twhile (!done && iters < max_iters) {\n\t\tbelow_unchanged = above_unchanged = false;\n\n\t\titers++;\n\t\t\n\t\t// matrix multiply (lower)\n\t\tCudd_Ref(sol_below);\n\t\ttmp = DD_PermuteVariables(ddman, sol_below, (transpose?cvars:rvars), (transpose?rvars:cvars), num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, (transpose?rvars:cvars), num_cvars, MM_BOULDER);\n\t\tCudd_Ref(b);\n\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, b);\n\t\tif (omega != 1.0) {\n\t\t\ttmp = DD_Apply(ddman, APPLY_TIMES, tmp, DD_Constant(ddman, omega));\n\t\t\tCudd_Ref(sol_below);\n\t\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, DD_Apply(ddman, APPLY_TIMES, sol_below, DD_Constant(ddman, 1-omega)));\n\t\t}\n\t\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\t\t// below: do max of tmp with old solution\n\t\t\tCudd_Ref(sol_below);\n\t\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, sol_below);\n\t\t}\n\t\tif (sol_below == tmp) below_unchanged = true;\n\t\tCudd_RecursiveDeref(ddman, sol_below);\n\t\tsol_below = tmp;\n\n\t\t// matrix multiply (upper)\n\t\tCudd_Ref(sol_above);\n\t\ttmp = DD_PermuteVariables(ddman, sol_above, (transpose?cvars:rvars), (transpose?rvars:cvars), num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, (transpose?rvars:cvars), num_cvars, MM_BOULDER);\n\t\tCudd_Ref(b);\n\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, b);\n\t\tif (omega != 1.0) {\n\t\t\ttmp = DD_Apply(ddman, APPLY_TIMES, tmp, DD_Constant(ddman, omega));\n\t\t\tCudd_Ref(sol_above);\n\t\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, DD_Apply(ddman, APPLY_TIMES, sol_above, DD_Constant(ddman, 1-omega)));\n\t\t}\n\t\tif (helper.flag_ensure_monotonic_from_above()) {\n\t\t\t// below: do min of tmp with old solution\n\t\t\tCudd_Ref(sol_above);\n\t\t\ttmp = DD_Apply(ddman, APPLY_MIN, tmp, sol_above);\n\t\t}\n\t\tif (sol_above == tmp) above_unchanged = true;\n\t\tCudd_RecursiveDeref(ddman, sol_above);\n\t\tsol_above = tmp;\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(sol_below, (transpose?cvars:rvars), num_rvars, odd, 0);\n\t\t\titerationExport->exportVector(sol_above, (transpose?cvars:rvars), num_rvars, odd, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tswitch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, sol_above, sol_below, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, sol_above, sol_below, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\n\t\tif (!done && below_unchanged && above_unchanged) {\n\t\t\tbreak;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t}\n\t\n\t// transpose solution if necessary\n\tif (transpose) {\n\t\tsol_below = DD_PermuteVariables(ddman, sol_below, cvars, rvars, num_rvars);\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", (omega == 1.0)?\"Jacobi\":\"JOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\tDdNode *result;\n\tif (helper.flag_select_midpoint() && done) { // we did converge, select midpoint\n\t\tCudd_Ref(sol_below);\n\t\tCudd_Ref(sol_above);\n\n\t\t// compute midpoint for result\n\t\t// use x + ( y - x ) / 2 instead of (x+y)/2 for better numerical stability\n\t\t// TODO: ensure that below <= result <= above?\n\t\tDdNode* difference = DD_Apply(ddman, APPLY_MINUS, sol_above, sol_below);\n\t\tCudd_Ref(sol_below);\n\t\tCudd_Ref(difference);\n\t\tresult = DD_Apply(ddman, APPLY_PLUS, sol_below, DD_Apply(ddman, APPLY_DIVIDE, difference, DD_Constant(ddman, 2.0)));\n\t\t\n\t\t// also compute/store accuracy\n\t\t// TODO: handle cases where result is zero\n\t\tif (term_crit == TERM_CRIT_RELATIVE) {\n\t\t\tCudd_Ref(result);\n\t\t\tdifference = DD_Apply(ddman, APPLY_DIVIDE, difference, result);\n\t\t}\n\t\tlast_error_bound = DD_FindMax(ddman, difference);\n\t\tCudd_RecursiveDeref(ddman, difference);\n\n\t\t// export midpoint as vector above and below\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(result, rvars, num_rvars, odd, 0);\n\t\t\titerationExport->exportVector(result, rvars, num_rvars, odd, 1);\n\t\t}\n\t} else {\n\t\tresult = sol_below;\n\t\tCudd_Ref(result);\n\t}\n\n\t// free memory\n\tCudd_RecursiveDeref(ddman, id);\n\tCudd_RecursiveDeref(ddman, diags);\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, b);\n\tCudd_RecursiveDeref(ddman, sol_below);\n\tCudd_RecursiveDeref(ddman, sol_above);\n\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tCudd_RecursiveDeref(ddman, result);\n\t\tif (below_unchanged && above_unchanged) {\n\t\t\tPN_SetErrorMessage(\"In interval iteration, after %d iterations, both lower and upper iteration did not change anymore but don't have the required precision yet.\\nThis could be caused by the MTBDD's engine collapsing of similar constants, consider setting a smaller value for -cuddepsilon or -cuddepsilon 0 to disable collapsing\", iters);\n\t\t} else {\n\t\t\tPN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\t}\n\t\treturn 0;\n\t}\n\n\treturn ptr_to_jlong(result);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_NondetBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer ndm,\t// nondeterminism mask\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njint bound,\t\t// time bound\njboolean min\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *mask = jlong_to_DdNode(ndm);\t\t// nondeterminism mask\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a, *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint iters, i;\n\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\n\t// get a - filter out rows\n\tPN_PrintToMainLog(env, \"\\nBuilding iteration matrix MTBDD... \");\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"[nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\t\t\n\t// initial solution\n\t// (prob in 0 steps given by yes)\n\tCudd_Ref(yes);\n\tsol = yes;\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\t\n//\t\tDD_PrintInfoBrief(ddman, sol, num_rvars);\n\n\t\t// matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, cvars, num_cvars, MM_BOULDER);\n\n//\t\tDD_PrintInfoBrief(ddman, tmp, num_rvars+num_ndvars);\n\t\t\n\t\t// do min/max\n\t\tif (min) {\n\t\t\t// mask stuff\n\t\t\tCudd_Ref(mask);\n\t\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, mask);\n\t\t\t// abstract\n\t\t\ttmp = DD_MinAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t}\n\t\telse {\n\t\t\t// abstract\n\t\t\ttmp = DD_MaxAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t}\n\t\t\n\t\t// put 1s (for 'yes' states) back into into solution vector\t\t\n\t\tCudd_Ref(yes);\n\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, yes);\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"sol=%d nodes\", DD_GetNumNodes(ddman, sol));\n\t\t\t// NB: but tmp was probably bigger than sol (pre min/max-abstract)\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_NondetInstReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetInstReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer ndm,\t// nondeterminism mask\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njint bound,\t\t\t// time bound\njboolean min,\t\t// min or max probabilities (true = min, false = max)\njlong __jlongpointer in\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *mask = jlong_to_DdNode(ndm);\t\t// nondeterminism mask\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *init = jlong_to_DdNode(in);\n\n\t// mtbdds\n\tDdNode *new_mask, *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint iters;\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// need to change mask because rewards are not necessarily in the range 0..1\n\tCudd_Ref(mask);\n\tnew_mask = DD_ITE(ddman, mask, DD_PlusInfinity(ddman), DD_Constant(ddman, 0));\n\t\n\t// initial solution is the state rewards\n\tCudd_Ref(state_rewards);\n\tsol = state_rewards;\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how many iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\t\n\t\t// matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tCudd_Ref(trans);\n\t\ttmp = DD_MatrixMultiply(ddman, trans, tmp, cvars, num_cvars, MM_BOULDER);\n\t\t\n\t\t// do min/max\n\t\tif (min) {\n\t\t\t// mask stuff\n\t\t\tCudd_Ref(new_mask);\n\t\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, new_mask);\n\t\t\t// abstract\n\t\t\ttmp = DD_MinAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t}\n\t\telse {\n\t\t\t// abstract\n\t\t\ttmp = DD_MaxAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t\t\n//\t\tCudd_Ref(sol);\n//\t\tCudd_Ref(init);\n//\t\ttmp = DD_Apply(ddman, APPLY_TIMES, sol, init);\n//\t\ttmp = DD_SumAbstract(ddman, tmp, rvars, num_rvars);\n//\t\tPN_PrintToMainLog(env, \"%i: %f (%0.f, %0d)\\n\", iters, Cudd_V(tmp), DD_GetNumMinterms(ddman, sol, num_rvars), DD_GetNumNodes(ddman, sol));\n//\t\tCudd_RecursiveDeref(ddman, tmp);\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, new_mask);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_NondetReachReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include <memory>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetReachReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// state rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer ndm,\t// nondeterminism mask\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t// 'maybe' states\njboolean min\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *mask = jlong_to_DdNode(ndm);\t\t// nondeterminism mask\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach, *a, *all_rewards, *new_mask, *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint iters, i;\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\tPN_PrintToMainLog(env, \"\\nBuilding iteration matrix MTBDD... \");\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// also remove goal and infinity states from state rewards vector\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\t\n\t// combine state and transition rewards\n\tall_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, trans_rewards);\n\t\n\t// need to change mask because rewards are not necessarily in the range 0..1\n\tCudd_Ref(mask);\n\tnew_mask = DD_ITE(ddman, mask, DD_PlusInfinity(ddman), DD_Constant(ddman, 0));\n\t\n\t// initial solution is infinity in 'inf' states, zero elsewhere\n\t// note: ok to do this because cudd matrix-multiply (and other ops)\n\t// treat 0 * inf as 0, unlike in IEEE 754 rules\n\tCudd_Ref(inf);\n\tsol = DD_ITE(ddman, inf, DD_PlusInfinity(ddman), DD_Constant(ddman, 0));\n\t\n\t// print memory usage\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"[nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PM_NondetReachReward\"));\n\t\titerationExport->exportVector(sol, rvars, num_rvars, odd, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, cvars, num_cvars, MM_BOULDER);\n\t\t\n\t\t// add rewards\n\t\tCudd_Ref(all_rewards);\n\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, all_rewards);\n\t\t\n\t\t// do min/max\n\t\tif (min) {\n\t\t\t// mask stuff\n\t\t\tCudd_Ref(new_mask);\n\t\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, new_mask);\n\t\t\t// abstract\n\t\t\ttmp = DD_MinAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t}\n\t\telse {\n\t\t\t// abstract\n\t\t\ttmp = DD_MaxAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t}\n\t\t\n\t\t// put infinities (for 'inf' states) back into into solution vector\t\t\n\t\tCudd_Ref(inf);\n\t\ttmp = DD_ITE(ddman, inf, DD_PlusInfinity(ddman), tmp);\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(tmp, rvars, num_rvars, odd, 0);\n\n\t\t// check convergence\n\t\tswitch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// store accuracy info, once converged\n\t\t// the difference between vector values is not a reliable error bound\n\t\t// but we store it anyway in case it is useful for estimating a bound\n\t\t// TODO: handle cases where result is zero\n\t\tif (done) {\n\t\t\tCudd_Ref(tmp);\n\t\t\tCudd_Ref(sol);\n\t\t\tDdNode* difference = DD_Apply(ddman, APPLY_MINUS, tmp, sol);\n\t\t\tif (term_crit == TERM_CRIT_RELATIVE) {\n\t\t\t\tCudd_Ref(tmp);\n\t\t\t\tdifference = DD_Apply(ddman, APPLY_DIVIDE, difference, tmp);\n\t\t\t}\n\t\t\t// No DD absolute operator so check most +ve/-ve\n\t\t\tdouble max_diff = fabs(DD_FindMax(ddman, difference));\n\t\t\tdouble min_diff = fabs(DD_FindMin(ddman, difference));\n\t\t\tlast_error_bound = max_diff > min_diff ? max_diff : min_diff;\n\t\t\tCudd_RecursiveDeref(ddman, difference);\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, all_rewards);\n\tCudd_RecursiveDeref(ddman, new_mask);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { Cudd_RecursiveDeref(ddman, sol); PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); return 0; }\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_NondetReachRewardInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetReachRewardInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// state rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer ndm,\t// nondeterminism mask\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t// 'maybe' states\njlong __jlongpointer l,  // lower bound\njlong __jlongpointer u,  // uper bound\njboolean min,\t\t// min or max probabilities (true = min, false = max)\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *mask = jlong_to_DdNode(ndm);\t\t// nondeterminism mask\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\tDdNode *lower = jlong_to_DdNode(l); \t\t// lower bound\n\tDdNode *upper = jlong_to_DdNode(u); \t\t// upper bound\n\n\t// mtbdds\n\tDdNode *reach, *a, *all_rewards, *new_mask, *sol_below, *sol_above, *tmp_below, *tmp_above;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint iters, i;\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\tPN_PrintToMainLog(env, \"\\nBuilding iteration matrix MTBDD... \");\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// also remove goal and infinity states from state rewards vector\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\t\n\t// combine state and transition rewards\n\tall_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, trans_rewards);\n\t\n\t// need to change mask because rewards are not necessarily in the range 0..1\n\tCudd_Ref(mask);\n\tnew_mask = DD_ITE(ddman, mask, DD_PlusInfinity(ddman), DD_Constant(ddman, 0));\n\t\n\t// initial solution (below) is infinity in 'inf' states, lower elsewhere\n\t// note: ok to do this because cudd matrix-multiply (and other ops)\n\t// treat 0 * inf as 0, unlike in IEEE 754 rules\n\tCudd_Ref(inf);\n\tCudd_Ref(lower);\n\tsol_below = DD_ITE(ddman, inf, DD_PlusInfinity(ddman), lower);\n\n\t// initial solution (above) is infinity in 'inf' states, upper elsewhere\n\t// note: ok to do this because cudd matrix-multiply (and other ops)\n\t// treat 0 * inf as 0, unlike in IEEE 754 rules\n\tCudd_Ref(inf);\n\tCudd_Ref(upper);\n\tsol_above = DD_ITE(ddman, inf, DD_PlusInfinity(ddman), upper);\n\n\t// print memory usage\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"[nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PM_NondetReachReward (interval)\"));\n\t\titerationExport->exportVector(sol_below, rvars, num_rvars, odd, 0);\n\t\titerationExport->exportVector(sol_above, rvars, num_rvars, odd, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\tbool below_unchanged = false, above_unchanged = false;\n\n\twhile (!done && iters < max_iters) {\n\t\tbelow_unchanged = above_unchanged = false;\n\n\t\titers++;\n\t\t\n\t\t// matrix-vector multiply (below)\n\t\tCudd_Ref(sol_below);\n\t\ttmp_below = DD_PermuteVariables(ddman, sol_below, rvars, cvars, num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp_below = DD_MatrixMultiply(ddman, a, tmp_below, cvars, num_cvars, MM_BOULDER);\n\n\t\t// matrix-vector multiply (above)\n\t\tCudd_Ref(sol_above);\n\t\ttmp_above = DD_PermuteVariables(ddman, sol_above, rvars, cvars, num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp_above = DD_MatrixMultiply(ddman, a, tmp_above, cvars, num_cvars, MM_BOULDER);\n\n\t\t// add rewards\n\t\tCudd_Ref(all_rewards);\n\t\ttmp_below = DD_Apply(ddman, APPLY_PLUS, tmp_below, all_rewards);\n\t\tCudd_Ref(all_rewards);\n\t\ttmp_above = DD_Apply(ddman, APPLY_PLUS, tmp_above, all_rewards);\n\n\t\t// do min/max\n\t\tif (min) {\n\t\t\t// mask stuff\n\t\t\tCudd_Ref(new_mask);\n\t\t\ttmp_below = DD_Apply(ddman, APPLY_MAX, tmp_below, new_mask);\n\t\t\t// abstract\n\t\t\ttmp_below = DD_MinAbstract(ddman, tmp_below, ndvars, num_ndvars);\n\n\t\t\t// mask stuff\n\t\t\tCudd_Ref(new_mask);\n\t\t\ttmp_above = DD_Apply(ddman, APPLY_MAX, tmp_above, new_mask);\n\t\t\t// abstract\n\t\t\ttmp_above = DD_MinAbstract(ddman, tmp_above, ndvars, num_ndvars);\n\t\t}\n\t\telse {\n\t\t\t// abstract\n\t\t\ttmp_below = DD_MaxAbstract(ddman, tmp_below, ndvars, num_ndvars);\n\n\t\t\t// abstract\n\t\t\ttmp_above = DD_MaxAbstract(ddman, tmp_above, ndvars, num_ndvars);\n\t\t}\n\t\t\n\t\t// put infinities (for 'inf' states) back into into solution vectors\n\t\tCudd_Ref(inf);\n\t\ttmp_below = DD_ITE(ddman, inf, DD_PlusInfinity(ddman), tmp_below);\n\n\t\tCudd_Ref(inf);\n\t\ttmp_above = DD_ITE(ddman, inf, DD_PlusInfinity(ddman), tmp_above);\n\n\t\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\t\t// below: do max of tmp_below with old solution\n\t\t\tCudd_Ref(sol_below);\n\t\t\ttmp_below = DD_Apply(ddman, APPLY_MAX, tmp_below, sol_below);\n\t\t}\n\t\tif (helper.flag_ensure_monotonic_from_above()) {\n\t\t\t// above: do min of tmp_below with old solution\n\t\t\tCudd_Ref(sol_above);\n\t\t\ttmp_above = DD_Apply(ddman, APPLY_MIN, tmp_above, sol_above);\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(tmp_below, rvars, num_rvars, odd, 0);\n\t\t\titerationExport->exportVector(tmp_above, rvars, num_rvars, odd, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tswitch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp_below, tmp_above, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp_below, tmp_above, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\n\t\tif (sol_below == tmp_below) below_unchanged = true;\n\t\tif (sol_above == tmp_above) above_unchanged = true;\n\n\t\tif (!done && below_unchanged && above_unchanged) {\n\t\t\tbreak;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n\t\t\tPN_PrintToMainLog(env, \"sol_below=%d nodes sol_above=%d nodes\", DD_GetNumNodes(ddman, sol_below), DD_GetNumNodes(ddman, sol_above));\n\t\t\t// NB: but tmp was probably bigger than sol (pre min/max-abstract)\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol_below);\n\t\tCudd_RecursiveDeref(ddman, sol_above);\n\t\tsol_below = tmp_below;\n\t\tsol_above = tmp_above;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\tDdNode *result;\n\tif (helper.flag_select_midpoint() && done) { // we did converge, select midpoint\n\t\tCudd_Ref(sol_below);\n\t\tCudd_Ref(sol_above);\n\n\t\t// compute midpoint for result\n\t\t// use x + ( y - x ) / 2 instead of (x+y)/2 for better numerical stability\n\t\t// TODO: ensure that below <= result <= above?\n\t\tDdNode* difference = DD_Apply(ddman, APPLY_MINUS, sol_above, sol_below);\n\t\tCudd_Ref(sol_below);\n\t\tCudd_Ref(difference);\n\t\tresult = DD_Apply(ddman, APPLY_PLUS, sol_below, DD_Apply(ddman, APPLY_DIVIDE, difference, DD_Constant(ddman, 2.0)));\n\t\t\n\t\t// also compute/store accuracy\n\t\t// TODO: handle cases where result is zero\n\t\tif (term_crit == TERM_CRIT_RELATIVE) {\n\t\t\tCudd_Ref(result);\n\t\t\tdifference = DD_Apply(ddman, APPLY_DIVIDE, difference, result);\n\t\t}\n\t\tlast_error_bound = DD_FindMax(ddman, difference);\n\t\tCudd_RecursiveDeref(ddman, difference);\n\n\t\t// export midpoint as vector above and below\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(result, rvars, num_rvars, odd, 0);\n\t\t\titerationExport->exportVector(result, rvars, num_rvars, odd, 1);\n\t\t}\n\t} else {\n\t\tresult = sol_below;\n\t\tCudd_Ref(result);\n\t}\n\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, all_rewards);\n\tCudd_RecursiveDeref(ddman, new_mask);\n\tCudd_RecursiveDeref(ddman, sol_below);\n\tCudd_RecursiveDeref(ddman, sol_above);\n\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tCudd_RecursiveDeref(ddman, result);\n\t\tif (below_unchanged && above_unchanged) {\n\t\t\tPN_SetErrorMessage(\"In interval iteration, after %d iterations, both lower and upper iteration did not change anymore but don't have the required precision yet.\\nThis could be caused by the MTBDD's engine collapsing of similar constants, consider setting a smaller value for -cuddepsilon or -cuddepsilon 0 to disable collapsing\", iters);\n\t\t} else {\n\t\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\t}\n\t\treturn 0;\n\t}\n\n\treturn ptr_to_jlong(result);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_NondetUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include <memory>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer ndm,\t// nondeterminism mask\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njboolean min\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *mask = jlong_to_DdNode(ndm);\t\t// nondeterminism mask\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a, *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint iters, i;\n\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\n\t// get a - filter out rows\n\tPN_PrintToMainLog(env, \"\\nBuilding iteration matrix MTBDD... \");\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"[nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\t\t\n\t// initial solution\n\t// (prob in 0 steps given by yes)\n\tCudd_Ref(yes);\n\tsol = yes;\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PM_NondetUntil\"));\n\t\titerationExport->exportVector(sol, rvars, num_rvars, odd, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\twhile (!done && iters < max_iters) {\n\t\t\n//\t\tif (iters%20==0) {\n//\t\t\tPN_PrintToMainLog(env, \"Iteration %d:\\n\", iters);\n//\t\t\tDD_PrintTerminalsAndNumbers(ddman, sol, num_rvars);\n//\t\t}\n\t\n\t\titers++;\n\t\t\n//\t\tDD_PrintInfoBrief(ddman, sol, num_rvars);\n\n\t\t// matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, cvars, num_cvars, MM_BOULDER);\n\n//\t\tDD_PrintInfoBrief(ddman, tmp, num_rvars+num_ndvars);\n\t\t\n\t\t// do min/max\n\t\tif (min) {\n\t\t\t// mask stuff\n\t\t\tCudd_Ref(mask);\n\t\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, mask);\n\t\t\t// abstract\n\t\t\ttmp = DD_MinAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t}\n\t\telse {\n\t\t\t// abstract\n\t\t\ttmp = DD_MaxAbstract(ddman, tmp, ndvars, num_ndvars);\n\t\t}\n\n\t\t// put 1s (for 'yes' states) back into into solution vector\t\t\n\t\tCudd_Ref(yes);\n\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, yes);\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(tmp, rvars, num_rvars, odd, 0);\n\n\t\t// check convergence\n\t\tswitch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n\t\t\tPN_PrintToMainLog(env, \"sol=%d nodes\", DD_GetNumNodes(ddman, sol));\n\t\t\t// NB: but tmp was probably bigger than sol (pre min/max-abstract)\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// store accuracy info, once converged\n\t\t// the difference between vector values is not a reliable error bound\n\t\t// but we store it anyway in case it is useful for estimating a bound\n\t\t// TODO: handle cases where result is zero\n\t\tif (done) {\n\t\t\tCudd_Ref(tmp);\n\t\t\tCudd_Ref(sol);\n\t\t\tDdNode* difference = DD_Apply(ddman, APPLY_MINUS, tmp, sol);\n\t\t\tif (term_crit == TERM_CRIT_RELATIVE) {\n\t\t\t\tCudd_Ref(tmp);\n\t\t\t\tdifference = DD_Apply(ddman, APPLY_DIVIDE, difference, tmp);\n\t\t\t}\n\t\t\t// No DD absolute operator so check most +ve/-ve\n\t\t\tdouble max_diff = fabs(DD_FindMax(ddman, difference));\n\t\t\tdouble min_diff = fabs(DD_FindMin(ddman, difference));\n\t\t\tlast_error_bound = max_diff > min_diff ? max_diff : min_diff;\n\t\t\tCudd_RecursiveDeref(ddman, difference);\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\t\t\t\t\t\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\t\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { Cudd_RecursiveDeref(ddman, sol); PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); return 0; }\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_NondetUntilInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1NondetUntilInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer ndm,\t// nondeterminism mask\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njboolean min,\t\t// min or max probabilities (true = min, false = max)\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *mask = jlong_to_DdNode(ndm);\t\t// nondeterminism mask\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a, *sol_above, *tmp_above, *sol_below, *tmp_below;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint iters, i;\n\n\tIntervalIteration helper(flags);\n\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\n\t// get a - filter out rows\n\tPN_PrintToMainLog(env, \"\\nBuilding iteration matrix MTBDD... \");\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"[nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\t\t\n\t// initial solution\n\t// (prob in 0 steps given by yes)\n\tCudd_Ref(yes);\n\tsol_below = yes;\n\n\t// initial solution from above: 1 for yes and maybe states\n\tCudd_Ref(yes);\n\tCudd_Ref(maybe);\n\tsol_above = DD_Or(ddman, yes, maybe);\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PM_NondetUntilInterval\"));\n\t\titerationExport->exportVector(sol_below, rvars, num_rvars, odd, 0);\n\t\titerationExport->exportVector(sol_above, rvars, num_rvars, odd, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations (interval iteration)...\\n\");\n\n\tbool below_unchanged = false, above_unchanged = false;\n\n\twhile (!done && iters < max_iters) {\n\t\tbelow_unchanged = above_unchanged = false;\n\n//\t\tif (iters%20==0) {\n//\t\t\tPN_PrintToMainLog(env, \"Iteration %d:\\n\", iters);\n//\t\t\tDD_PrintTerminalsAndNumbers(ddman, sol, num_rvars);\n//\t\t}\n\t\n\t\titers++;\n\t\t\n//\t\tDD_PrintInfoBrief(ddman, sol, num_rvars);\n\n\t\t// matrix-vector multiply (below)\n\t\tCudd_Ref(sol_below);\n\t\ttmp_below = DD_PermuteVariables(ddman, sol_below, rvars, cvars, num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp_below = DD_MatrixMultiply(ddman, a, tmp_below, cvars, num_cvars, MM_BOULDER);\n\n\t\t// matrix-vector multiply (above)\n\t\tCudd_Ref(sol_above);\n\t\ttmp_above = DD_PermuteVariables(ddman, sol_above, rvars, cvars, num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp_above = DD_MatrixMultiply(ddman, a, tmp_above, cvars, num_cvars, MM_BOULDER);\n\n//\t\tDD_PrintInfoBrief(ddman, tmp, num_rvars+num_ndvars);\n\t\t\n\t\t// do min/max\n\t\tif (min) {\n\t\t\t// mask stuff\n\t\t\tCudd_Ref(mask);\n\t\t\ttmp_below = DD_Apply(ddman, APPLY_MAX, tmp_below, mask);\n\t\t\t// abstract\n\t\t\ttmp_below = DD_MinAbstract(ddman, tmp_below, ndvars, num_ndvars);\n\n\t\t\t// mask stuff\n\t\t\tCudd_Ref(mask);\n\t\t\ttmp_above = DD_Apply(ddman, APPLY_MAX, tmp_above, mask);\n\t\t\t// abstract\n\t\t\ttmp_above = DD_MinAbstract(ddman, tmp_above, ndvars, num_ndvars);\n\t\t}\n\t\telse {\n\t\t\t// abstract\n\t\t\ttmp_below = DD_MaxAbstract(ddman, tmp_below, ndvars, num_ndvars);\n\t\t\t// abstract\n\t\t\ttmp_above = DD_MaxAbstract(ddman, tmp_above, ndvars, num_ndvars);\n\t\t}\n\n\t\t// put 1s (for 'yes' states) back into into solution vector\t\t\n\t\tCudd_Ref(yes);\n\t\ttmp_below = DD_Apply(ddman, APPLY_MAX, tmp_below, yes);\n\t\tCudd_Ref(yes);\n\t\ttmp_above = DD_Apply(ddman, APPLY_MAX, tmp_above, yes);\n\n\t\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\t\t// below: do max of tmp_below with old solution\n\t\t\tCudd_Ref(sol_below);\n\t\t\ttmp_below = DD_Apply(ddman, APPLY_MAX, tmp_below, sol_below);\n\t\t}\n\t\tif (helper.flag_ensure_monotonic_from_above()) {\n\t\t\t// above: do min of tmp_below with old solution\n\t\t\tCudd_Ref(sol_above);\n\t\t\ttmp_above = DD_Apply(ddman, APPLY_MIN, tmp_above, sol_above);\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(tmp_below, rvars, num_rvars, odd, 0);\n\t\t\titerationExport->exportVector(tmp_above, rvars, num_rvars, odd, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tswitch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp_below, tmp_above, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp_below, tmp_above, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\n\t\tif (sol_below == tmp_below) below_unchanged = true;\n\t\tif (sol_above == tmp_above) above_unchanged = true;\n\n\t\tif (!done && below_unchanged && above_unchanged) {\n\t\t\tbreak;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n\t\t\tPN_PrintToMainLog(env, \"sol_below=%d nodes sol_above=%d nodes\", DD_GetNumNodes(ddman, sol_below), DD_GetNumNodes(ddman, sol_above));\n\t\t\t// NB: but tmp was probably bigger than sol (pre min/max-abstract)\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol_below);\n\t\tCudd_RecursiveDeref(ddman, sol_above);\n\t\tsol_below = tmp_below;\n\t\tsol_above = tmp_above;\n\t}\n\t\t\t\t\t\t\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\tDdNode *result;\n\tif (helper.flag_select_midpoint() && done) { // we did converge, select midpoint\n\t\tCudd_Ref(sol_below);\n\t\tCudd_Ref(sol_above);\n\n\t\t// compute midpoint for result\n\t\t// use x + ( y - x ) / 2 instead of (x+y)/2 for better numerical stability\n\t\t// TODO: ensure that below <= result <= above?\n\t\tDdNode* difference = DD_Apply(ddman, APPLY_MINUS, sol_above, sol_below);\n\t\tCudd_Ref(sol_below);\n\t\tCudd_Ref(difference);\n\t\tresult = DD_Apply(ddman, APPLY_PLUS, sol_below, DD_Apply(ddman, APPLY_DIVIDE, difference, DD_Constant(ddman, 2.0)));\n\t\t\n\t\t// also compute/store accuracy\n\t\t// TODO: handle cases where result is zero\n\t\tif (term_crit == TERM_CRIT_RELATIVE) {\n\t\t\tCudd_Ref(result);\n\t\t\tdifference = DD_Apply(ddman, APPLY_DIVIDE, difference, result);\n\t\t}\n\t\tlast_error_bound = DD_FindMax(ddman, difference);\n\t\tCudd_RecursiveDeref(ddman, difference);\n\n\t\t// export midpoint as vector above and below\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(result, rvars, num_rvars, odd, 0);\n\t\t\titerationExport->exportVector(result, rvars, num_rvars, odd, 1);\n\t\t}\n\t} else {\n\t\tresult = sol_below;\n\t\tCudd_Ref(result);\n\t}\n\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, sol_below);\n\tCudd_RecursiveDeref(ddman, sol_above);\n\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tCudd_RecursiveDeref(ddman, result);\n\t\tif (below_unchanged && above_unchanged) {\n\t\t\tPN_SetErrorMessage(\"In interval iteration, after %d iterations, both lower and upper iteration did not change anymore but don't have the required precision yet.\\nThis could be caused by the MTBDD's engine collapsing of similar constants, consider setting a smaller value for -cuddepsilon or -cuddepsilon 0 to disable collapsing\", iters);\n\t\t} else {\n\t\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\t}\n\t\treturn 0;\n\t}\n\n\treturn ptr_to_jlong(result);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_Power.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include <memory>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=x with the Power method\n// in addition, solutions may be provided for additional states in the vector b\n// these states are assumed not to have non-zero rows in the matrix A\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1Power\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose\t// transpose A? (i.e. solve xA=b not Ax=b?)\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\n\t// mtbdds\n\tDdNode *reach, *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tbool done;\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// make local copy of b\n\tCudd_Ref(b);\n\t\n\t// print out some memory usage\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"\\nIteration matrix MTBDD... [nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\n\t// transpose b if necessary\n\tif (transpose) {\n\t\tb = DD_PermuteVariables(ddman, b, rvars, cvars, num_rvars);\n\t}\n\t\n\t// store initial solution, transposing if necessary\n\tCudd_Ref(init);\n\tsol = init;\n\tif (transpose) {\n\t\tsol = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PM_Power\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(sol, (transpose?cvars:rvars), num_rvars, odd, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// matrix multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, (transpose?cvars:rvars), (transpose?rvars:cvars), num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, (transpose?rvars:cvars), num_cvars, MM_BOULDER);\n\t\tCudd_Ref(b);\n\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, b);\n\t\t\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(tmp, (transpose?cvars:rvars), num_rvars, odd, 0);\n\n\t\t// check convergence\n\t\tswitch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// store accuracy info, once converged\n\t\t// the difference between vector values is not a reliable error bound\n\t\t// but we store it anyway in case it is useful for estimating a bound\n\t\t// TODO: handle cases where result is zero\n\t\tif (done) {\n\t\t\tCudd_Ref(tmp);\n\t\t\tCudd_Ref(sol);\n\t\t\tDdNode* difference = DD_Apply(ddman, APPLY_MINUS, tmp, sol);\n\t\t\tif (term_crit == TERM_CRIT_RELATIVE) {\n\t\t\t\tCudd_Ref(tmp);\n\t\t\t\tdifference = DD_Apply(ddman, APPLY_DIVIDE, difference, tmp);\n\t\t\t}\n\t\t\t// No DD absolute operator so check most +ve/-ve\n\t\t\tdouble max_diff = fabs(DD_FindMax(ddman, difference));\n\t\t\tdouble min_diff = fabs(DD_FindMin(ddman, difference));\n\t\t\tlast_error_bound = max_diff > min_diff ? max_diff : min_diff;\n\t\t\tCudd_RecursiveDeref(ddman, difference);\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\n\t// transpose solution if necessary\n\tif (transpose) {\n\t\tsol = DD_PermuteVariables(ddman, sol, cvars, rvars, num_rvars);\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\nPower method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, b);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { Cudd_RecursiveDeref(ddman, sol); PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); return 0; }\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_PowerInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=x with the Power method (interval variant)\n// in addition, solutions may be provided for additional states in the vector b\n// these states are assumed not to have non-zero rows in the matrix A\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1PowerInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t\t// upper bound values\n\n\t// mtbdds\n\tDdNode *reach, *sol_below, *sol_above, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, iters;\n\tbool done;\n\n\tIntervalIteration helper(flags);\n\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// make local copy of b\n\tCudd_Ref(b);\n\t\n\t// print out some memory usage\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"\\nIteration matrix MTBDD... [nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\n\t// transpose b if necessary\n\tif (transpose) {\n\t\tb = DD_PermuteVariables(ddman, b, rvars, cvars, num_rvars);\n\t}\n\t\n\t// store initial solution vectors, transposing if necessary\n\tCudd_Ref(lower);\n\tsol_below = lower;\n\tCudd_Ref(upper);\n\tsol_above = upper;\n\tif (transpose) {\n\t\tsol_below = DD_PermuteVariables(ddman, sol_below, rvars, cvars, num_rvars);\n\t\tsol_above = DD_PermuteVariables(ddman, sol_above, rvars, cvars, num_rvars);\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PM_Power (interval)\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(sol_below, (transpose?cvars:rvars), num_rvars, odd, 0);\n\t\titerationExport->exportVector(sol_above, (transpose?cvars:rvars), num_rvars, odd, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\tbool below_unchanged = false, above_unchanged = false;\n\n\twhile (!done && iters < max_iters) {\n\t\tbelow_unchanged = above_unchanged = false;\n\n\t\titers++;\n\t\t\n\t\t// matrix multiply (below)\n\t\tCudd_Ref(sol_below);\n\t\ttmp = DD_PermuteVariables(ddman, sol_below, (transpose?cvars:rvars), (transpose?rvars:cvars), num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, (transpose?rvars:cvars), num_cvars, MM_BOULDER);\n\t\tCudd_Ref(b);\n\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, b);\n\t\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\t\t// below: do max of tmp with old solution\n\t\t\tCudd_Ref(sol_below);\n\t\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, sol_below);\n\t\t}\n\t\tif (sol_below == tmp) below_unchanged = true;\n\t\tCudd_RecursiveDeref(ddman, sol_below);\n\t\tsol_below = tmp;\n\n\t\t// matrix multiply (above)\n\t\tCudd_Ref(sol_above);\n\t\ttmp = DD_PermuteVariables(ddman, sol_above, (transpose?cvars:rvars), (transpose?rvars:cvars), num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, (transpose?rvars:cvars), num_cvars, MM_BOULDER);\n\t\tCudd_Ref(b);\n\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, b);\n\t\tif (helper.flag_ensure_monotonic_from_above()) {\n\t\t\t// below: do min of tmp with old solution\n\t\t\tCudd_Ref(sol_above);\n\t\t\ttmp = DD_Apply(ddman, APPLY_MIN, tmp, sol_above);\n\t\t}\n\t\tif (sol_above == tmp) above_unchanged = true;\n\t\tCudd_RecursiveDeref(ddman, sol_above);\n\t\tsol_above = tmp;\n\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(sol_below, (transpose?cvars:rvars), num_rvars, odd, 0);\n\t\t\titerationExport->exportVector(sol_above, (transpose?cvars:rvars), num_rvars, odd, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tswitch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, sol_above, sol_below, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, sol_above, sol_below, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\n\t\tif (!done && below_unchanged && above_unchanged) {\n\t\t\tbreak;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: \", iters);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t}\n\t\n\t// transpose solution if necessary\n\tif (transpose) {\n\t\tsol_below = DD_PermuteVariables(ddman, sol_below, cvars, rvars, num_rvars);\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\nPower method (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\tDdNode *result;\n\tif (helper.flag_select_midpoint() && done) { // we did converge, select midpoint\n\t\tCudd_Ref(sol_below);\n\t\tCudd_Ref(sol_above);\n\n\t\t// compute midpoint for result\n\t\t// use x + ( y - x ) / 2 instead of (x+y)/2 for better numerical stability\n\t\t// TODO: ensure that below <= result <= above?\n\t\tDdNode* difference = DD_Apply(ddman, APPLY_MINUS, sol_above, sol_below);\n\t\tCudd_Ref(sol_below);\n\t\tCudd_Ref(difference);\n\t\tresult = DD_Apply(ddman, APPLY_PLUS, sol_below, DD_Apply(ddman, APPLY_DIVIDE, difference, DD_Constant(ddman, 2.0)));\n\t\t\n\t\t// also compute/store accuracy\n\t\t// TODO: handle cases where result is zero\n\t\tif (term_crit == TERM_CRIT_RELATIVE) {\n\t\t\tCudd_Ref(result);\n\t\t\tdifference = DD_Apply(ddman, APPLY_DIVIDE, difference, result);\n\t\t}\n\t\tlast_error_bound = DD_FindMax(ddman, difference);\n\t\tCudd_RecursiveDeref(ddman, difference);\n\n\t\t// export midpoint as vector above and below\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(result, rvars, num_rvars, odd, 0);\n\t\t\titerationExport->exportVector(result, rvars, num_rvars, odd, 1);\n\t\t}\n\t} else {\n\t\tresult = sol_below;\n\t\tCudd_Ref(result);\n\t}\n\n\t// free memory\n\tCudd_RecursiveDeref(ddman, b);\n\tCudd_RecursiveDeref(ddman, sol_below);\n\tCudd_RecursiveDeref(ddman, sol_above);\n\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tCudd_RecursiveDeref(ddman, result);\n\t\tif (below_unchanged && above_unchanged) {\n\t\t\tPN_SetErrorMessage(\"In interval iteration, after %d iterations, both lower and upper iteration did not change anymore but don't have the required precision yet.\\nThis could be caused by the MTBDD's engine collapsing of similar constants, consider setting a smaller value for -cuddepsilon or -cuddepsilon 0 to disable collapsing\", iters);\n\t\t} else {\n\t\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\t}\n\t\treturn 0;\n\t}\n\n\treturn ptr_to_jlong(result);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_Prob0.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// PCTL until probability 0 precomputation (probabilistic/dtmc) (mtbdd)\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob0\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t01, \t// 0-1 trans matrix\njlong __jlongpointer r,\t\t// all reachable states\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer phi,\t// phi(b1)\njlong __jlongpointer psi\t// psi(b2)\n)\n{\n\tDdNode *trans01 = jlong_to_DdNode(t01);\t\t// 0-1 trans matrix\n\tDdNode *reach = jlong_to_DdNode(r);\t\t\t// all reachable states\n\tDdNode *b1 = jlong_to_DdNode(phi);\t\t\t// b1\n\tDdNode *b2 = jlong_to_DdNode(psi);\t\t\t// b2\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\t\n\tDdNode *sol, *tmp;\n\tbool done;\n\tint iters;\n\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\n\t// start clock\n\tstart1 = util_cpu_time();\n\t\n\t// reachability fixpoint loop\n\tCudd_Ref(b2);\n\tsol = b2;\n\tdone = false;\n\titers = 0;\n\twhile (!done) {\n\t\n\t\titers++;\n\t\t\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(trans01);\n\t\ttmp = DD_And(ddman, tmp, trans01);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\ttmp = DD_ThereExists(ddman, tmp, cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tCudd_Ref(b1);\n\t\ttmp = DD_And(ddman, b1, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(b2);\n\t\ttmp = DD_Or(ddman, b2, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tif (tmp == sol) {\n\t\t\tdone = true;\n\t\t}\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\tsol = DD_PermuteVariables(ddman, sol, cvars, rvars, num_cvars);\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\t\n\t// actual answer is states NOT reachable\n\tCudd_Ref(reach);\n\tsol = DD_And(ddman, reach, DD_Not(ddman, sol));\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\n\t// stop clock\n\ttime_taken = (double)(util_cpu_time() - start1)/1000;\n\ttime_for_setup = 0;\n\ttime_for_iters = time_taken;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nProb0: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_Prob0A.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// PCTL until probability 0 precomputation\n// (for all = max) (nondeterministic/mdp) (mtbdd)\n// (i.e. compute states FOR which ALL probabilities are 0)\n// (NB: actually compute states where THERE EXISTS a probability >0 and then do a NOT)\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob0A\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t01,\t// 0-1 trans matrix\njlong __jlongpointer r,\t// reachable states\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer phi,\t// phi(b1)\njlong __jlongpointer psi\t// psi(b2)\n)\n{\n\tDdNode *trans01 = jlong_to_DdNode(t01);\t\t// 0-1 trans matrix\n\tDdNode *reach = jlong_to_DdNode(r);\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *b1 = jlong_to_DdNode(phi);\t\t// b1\n\tDdNode *b2 = jlong_to_DdNode(psi);\t\t// b2\n\t\n\tDdNode *sol, *tmp;\n\tbool done;\n\tint iters;\n\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\n\t// start clock\n\tstart1 = util_cpu_time();\n\t\n\t// reachability fixpoint loop\n\tCudd_Ref(b2);\n\tsol = b2;\n\tdone = false;\n\titers = 0;\n\twhile (!done) {\n\t\n\t\titers++;\n\t\t\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(trans01);\n\t\ttmp = DD_And(ddman, tmp, trans01);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\ttmp = DD_ThereExists(ddman, tmp, cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\ttmp = DD_ThereExists(ddman, tmp, ndvars, num_ndvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tCudd_Ref(b1);\n\t\ttmp = DD_And(ddman, b1, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(b2);\n\t\ttmp = DD_Or(ddman, b2, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tif (tmp == sol) {\n\t\t\tdone = true;\n\t\t}\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\tsol = DD_PermuteVariables(ddman, sol, cvars, rvars, num_cvars);\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\t\n\t// actual answer is states NOT reachable\n\tCudd_Ref(reach);\n\tsol = DD_And(ddman, reach, DD_Not(ddman, sol));\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\n\t// stop clock\n\ttime_taken = (double)(util_cpu_time() - start1)/1000;\n\ttime_for_setup = 0;\n\ttime_for_iters = time_taken;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nProb0A: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_Prob0E.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// PCTL until probability 0 precomputation\n// (there exists = min) (nondeterministic/mdp) (mtbdd)\n// (i.e. compute states where THERE EXISTS a probability 0)\n// (NB: actually compute states FOR which ALL probabilities are >0 and then do a NOT)\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob0E\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t01, \t// 0-1 trans matrix\njlong __jlongpointer r,\t// reachable states\njlong __jlongpointer ndm,\t// nondeterminism mask\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer phi,\t// phi(b1)\njlong __jlongpointer psi\t// psi(b2)\n)\n{\n\tDdNode *trans01 = jlong_to_DdNode(t01);\t\t// 0-1 trans matrix\n\tDdNode *reach = jlong_to_DdNode(r);\t\t// reachable states\n\tDdNode *mask = jlong_to_DdNode(ndm);\t\t// nondeterminism mask\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\t\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *b1 = jlong_to_DdNode(phi);\t\t// b1\n\tDdNode *b2 = jlong_to_DdNode(psi);\t\t// b2\n\t\n\tDdNode *sol, *tmp;\n\tbool done;\n\tint iters;\n\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\n\t// start clock\n\tstart1 = util_cpu_time();\n\t\n\t// reachability fixpoint loop\n\tCudd_Ref(b2);\n\tsol = b2;\n\tdone = false;\n\titers = 0;\n\twhile (!done) {\n\t\n\t\titers++;\n\t\t\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(trans01);\n\t\ttmp = DD_And(ddman, tmp, trans01);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\ttmp = DD_ThereExists(ddman, tmp, cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tCudd_Ref(mask);\n\t\ttmp = DD_Or(ddman, tmp, mask);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\ttmp = DD_ForAll(ddman, tmp, ndvars, num_ndvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tCudd_Ref(b1);\n\t\ttmp = DD_And(ddman, b1, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(b2);\n\t\ttmp = DD_Or(ddman, b2, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tif (tmp == sol) {\n\t\t\tdone = true;\n\t\t}\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\tsol = DD_PermuteVariables(ddman, sol, cvars, rvars, num_cvars);\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\t\n\t// actual answer is states NOT reachable\n\tCudd_Ref(reach);\n\tsol = DD_And(ddman, reach, DD_Not(ddman, sol));\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\n\t// stop clock\n\ttime_taken = (double)(util_cpu_time() - start1)/1000;\n\ttime_for_setup = 0;\n\ttime_for_iters = time_taken;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nProb0E: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_Prob1.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// PCTL until probability 1 precomputation (probabilistic/dtmc) (mtbdd)\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob1\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t01, \t// 0-1 trans matrix\njlong __jlongpointer r,\t\t// all reachable states\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer phi,\t// phi(b1)\njlong __jlongpointer psi,\t// psi(b2)\njlong __jlongpointer _no\t// no\n)\n{\n\tDdNode *trans01 = jlong_to_DdNode(t01);\t\t// 0-1 trans matrix\n\tDdNode *reach = jlong_to_DdNode(r);\t\t\t// all reachable states\n\tDdNode *b1 = jlong_to_DdNode(phi);\t\t\t// b1\n\tDdNode *b2 = jlong_to_DdNode(psi);\t\t\t// b2\n\tDdNode *no = jlong_to_DdNode(_no);\t\t\t// no\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\t\n\tDdNode *sol, *tmp;\n\tbool done;\n\tint iters;\n\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\n\t// start clock\n\tstart1 = util_cpu_time();\n\t\n\t// reachability fixpoint loop\n\tCudd_Ref(no);\n\tsol = no;\n\tdone = false;\n\titers = 0;\n\twhile (!done) {\n\t\n\t\titers++;\n\t\t\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(trans01);\n\t\ttmp = DD_And(ddman, tmp, trans01);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\ttmp = DD_ThereExists(ddman, tmp, cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tCudd_Ref(b1);\n\t\ttmp = DD_And(ddman, b1, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(b2);\n\t\ttmp = DD_And(ddman, DD_Not(ddman, b2), tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(no);\n\t\ttmp = DD_Or(ddman, no, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tif (tmp == sol) {\n\t\t\tdone = true;\n\t\t}\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\tsol = DD_PermuteVariables(ddman, sol, cvars, rvars, num_cvars);\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\t\n\t// actual answer is states NOT reachable\n\tCudd_Ref(reach);\n\tsol = DD_And(ddman, reach, DD_Not(ddman, sol));\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\n\t// stop clock\n\ttime_taken = (double)(util_cpu_time() - start1)/1000;\n\ttime_for_setup = 0;\n\ttime_for_iters = time_taken;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nProb1: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_Prob1A.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Gethin Norman <gethin.norman@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// PCTL until probability 1 precomputation\n// (for all = min) (nondeterministic/mdp) (mtbdd)\n// (i.e. compute states FOR which ALL probabilities are 1)\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob1A\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t01, \t// 0-1 trans matrix\njlong __jlongpointer r,\t// reachable states\njlong __jlongpointer ndm,\t// nondeterminism mask\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer n,\t// no\njlong __jlongpointer psi\t// psi(b2)\n)\n{\n\tDdNode *trans01 = jlong_to_DdNode(t01);\t\t// 0-1 trans matrix\n\tDdNode *reach = jlong_to_DdNode(r);\t\t// reachable states\n\tDdNode *mask = jlong_to_DdNode(ndm);\t\t// nondeterminism mask\n\tDdNode *no = jlong_to_DdNode(n);\t\t// no\n\tDdNode *b2 = jlong_to_DdNode(psi);\t\t// b2\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\t\n\tDdNode  *sol, *tmp, *notno;\n\tbool done;\n\tint iters;\n\t\n\t// timing stuff\n\tlong start, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t\n\t// start clock\n\tstart = util_cpu_time();\n\t\n\t// negate set \"no\" (\"there exists an adversary with prob=0\") to get set \"for all adversaries prob>0\"\n\tCudd_Ref(reach);\n\tCudd_Ref(no);\n\tnotno = DD_And(ddman, reach, DD_Not(ddman, no));\n\tif (notno == NULL) return ptr_to_jlong(NULL);\n\t\n\t// greatest fixed point loop\n\tCudd_Ref(b2);\n\tCudd_Ref(notno);\n\tsol = DD_Or(ddman, b2, notno);\n\tif (sol == NULL) return ptr_to_jlong(NULL);\n\t\n\tdone = false;\n\titers = 0;\n\t\n\twhile (!done) {\n\t\t\n\t\titers++;\n\t\t\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_SwapVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(trans01);\n\t\ttmp = DD_ForAll(ddman, DD_Implies(ddman, trans01, tmp), cvars, num_cvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tCudd_Ref(mask);\n\t\ttmp = DD_Or(ddman, tmp, mask);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\ttmp = DD_ForAll(ddman, tmp, ndvars, num_ndvars);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tCudd_Ref(notno);\n\t\ttmp = DD_And(ddman, notno, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_Ref(b2);\n\t\ttmp = DD_Or(ddman, b2, tmp);\n\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\tif (tmp == sol) {\n\t\t\tdone = true;\n\t\t}\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\n\t// stop clock\n\ttime_taken = (double)(util_cpu_time() - start)/1000;\n\ttime_for_setup = 0;\n\ttime_for_iters = time_taken;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nProb1A: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\tCudd_RecursiveDeref(ddman, notno);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_Prob1E.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// PCTL until probability 1 precomputation\n// (there exists = max) (nondeterministic/mdp) (mtbdd)\n// (i.e. compute states where THERE EXISTS a probability 1)\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1Prob1E\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t01, \t// 0-1 trans matrix\njlong __jlongpointer r,\t// reachable states\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer phi,\t// phi(b1)\njlong __jlongpointer psi,\t// psi(b2)\njlong __jlongpointer _no\t// no\n)\n{\n\tDdNode *trans01 = jlong_to_DdNode(t01);\t\t// 0-1 trans matrix\n\tDdNode *reach = jlong_to_DdNode(r);\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *b1 = jlong_to_DdNode(phi);\t\t// b1\n\tDdNode *b2 = jlong_to_DdNode(psi);\t\t// b2\n\tDdNode *no = jlong_to_DdNode(_no);\t\t\t// no\n\t\n\tDdNode *u, *v, *tmp, *tmp2;\n\tbool u_done, v_done;\n\tint iters;\n\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\n\t// start clock\n\tstart1 = util_cpu_time();\n\t\n\t// greatest fixed point so should start from true,\n\t// but for efficiency we use the passed in \"no\", which will\n\t// be the result of the first (outer) iteration\n\tCudd_Ref(reach);\n\tCudd_Ref(no);\n\tu = DD_And(ddman, reach, DD_Not(ddman, no));\n\tif (u == NULL) return ptr_to_jlong(NULL);\n\t//u = DD_Constant(ddman, 1);\n\tu_done = false;\n\titers = 0;\n\t\n\twhile (!u_done) {\n\t\n\t\t// least fixed point - start from false\n\t\tv = DD_Constant(ddman, 0);\n\t\tv_done = false;\n\t\t\n\t\twhile (!v_done) {\n\t\t\t\t\n\t\t\titers++;\n\t\t\t\t\n\t\t\tCudd_Ref(u);\n\t\t\ttmp = DD_SwapVariables(ddman, u, rvars, cvars, num_rvars);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\tCudd_Ref(trans01);\n\t\t\ttmp = DD_ForAll(ddman, DD_Implies(ddman, trans01, tmp), cvars, num_cvars);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\n\t\t\tCudd_Ref(v);\n\t\t\ttmp2 = DD_SwapVariables(ddman, v, rvars, cvars, num_rvars);\n\t\t\tif (tmp2 == NULL) return ptr_to_jlong(NULL);\n\t\t\tCudd_Ref(trans01);\n\t\t\ttmp2 = DD_ThereExists(ddman, DD_And(ddman, tmp2, trans01), cvars, num_cvars);\n\t\t\tif (tmp2 == NULL) return ptr_to_jlong(NULL);\n\n\t\t\ttmp = DD_And(ddman, tmp, tmp2);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\ttmp = DD_ThereExists(ddman, tmp, ndvars, num_ndvars);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\n\t\t\tCudd_Ref(b1);\n\t\t\ttmp = DD_And(ddman, b1, tmp);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\tCudd_Ref(b2);\n\t\t\ttmp = DD_Or(ddman, b2, tmp);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\t\n\t\t\tif (tmp == v) {\n\t\t\t\tv_done = true;\n\t\t\t}\n\t\t\tCudd_RecursiveDeref(ddman, v);\n\t\t\tv = tmp;\n\t\t}\n\t\tif (v == u) {\n\t\t\tu_done = true;\n\t\t}\n\t\tCudd_RecursiveDeref(ddman, u);\n\t\tu = v;\n\t}\n\t\n\t// stop clock\n\ttime_taken = (double)(util_cpu_time() - start1)/1000;\n\ttime_for_setup = 0;\n\ttime_for_iters = time_taken;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nProb1E: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\treturn ptr_to_jlong(u);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ProbBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t\t// trans matrix\njlong __jlongpointer od,\t\t// odd\njlong __jlongpointer rv,\t\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t\t// 'yes' states\njlong __jlongpointer m,\t\t// 'maybe' states\njint bound\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a, *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint iters, i;\n\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\n\t// get a - filter out rows\n\tPN_PrintToMainLog(env, \"\\nBuilding iteration matrix MTBDD... \");\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\ti = DD_GetNumNodes(ddman, a);\n\tPN_PrintToMainLog(env, \"[nodes=%d] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\n\t// initial solution\n\t// (prob in 0 steps given by yes)\n\tCudd_Ref(yes);\n\tsol = yes;\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\n\t\t// matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tCudd_Ref(a);\n\t\ttmp = DD_MatrixMultiply(ddman, a, tmp, cvars, num_cvars, MM_BOULDER);\n\t\t// put 1s (for 'yes' states) back into into solution vector\n\t\tCudd_Ref(yes);\n\t\ttmp = DD_Apply(ddman, APPLY_MAX, tmp, yes);\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ProbCumulReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbCumulReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t\t// trans matrix\njlong __jlongpointer sr,\t\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t\t// odd\njlong __jlongpointer rv,\t\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t\t// col vars\njint num_cvars,\njint bound\t\t\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *all_rewards, *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint iters;\n\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\n\t// multiply transition rewards by transition probs and sum rows\n\t// then combine state and transition rewards and put in a vector\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(trans);\n\tall_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, trans);\n\tall_rewards = DD_SumAbstract(ddman, all_rewards, cvars, num_cvars);\n\tCudd_Ref(state_rewards);\n\tall_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, all_rewards);\n\n\t// initial solution is zero\n\tsol = DD_Constant(ddman, 0);\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\n\t\t// matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tCudd_Ref(trans);\n\t\ttmp = DD_MatrixMultiply(ddman, trans, tmp, cvars, num_cvars, MM_BOULDER);\n\t\t// add in (combined state and transition) rewards\n\t\tCudd_Ref(all_rewards);\n\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, all_rewards);\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, all_rewards);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ProbInstReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbInstReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njint bound\t\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint iters;\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// initial solution is the state rewards\n\tCudd_Ref(state_rewards);\n\tsol = state_rewards;\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\t\n\t\t// matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tCudd_Ref(trans);\n\t\ttmp = DD_MatrixMultiply(ddman, trans, tmp, cvars, num_cvars, MM_BOULDER);\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ProbReachReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbReachReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m\t// 'maybe' states\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in);\t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach, *a, *sol, *tmp;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// take copy of state/trans rewards\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(trans_rewards);\n\t\n\t// also remove goal and infinity states from state rewards vector\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\t\n\t// combine state and transition rewards\n\tCudd_Ref(trans_rewards);\n\tstate_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, trans_rewards);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// call iterative method\n\tsol = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsol = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsol = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, 1.0));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsol = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, lin_eq_method_param));\n\t\t\tbreak;\n\t\tdefault:\n\t\t\t// set error message and return NULL pointer after cleanup, below\n\t\t\tPN_SetErrorMessage(\"Gauss-Seidel and its variants are currently not supported by the MTBDD engine\");\n\t\t\tbreak;\n\t}\n\t\n\t// set reward for infinity states to infinity\n\tif (sol != NULL) {\n\t\tCudd_Ref(inf);\n\t\tsol = DD_ITE(ddman, inf, DD_PlusInfinity(ddman), sol);\n\t}\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, state_rewards);\n\tCudd_RecursiveDeref(ddman, trans_rewards);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ProbReachRewardInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"IntervalIteration.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbReachRewardInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t// 'maybe' states\njlong __jlongpointer l,  // lower bound\njlong __jlongpointer u,   // upper bound\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in);\t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\tDdNode *lower = jlong_to_DdNode(l);\t\t// lower bound\n\tDdNode *upper = jlong_to_DdNode(u);\t\t// upper bound\n\n\t// mtbdds\n\tDdNode *reach, *a, *sol, *tmp;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// take copy of state/trans rewards\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(trans_rewards);\n\t\n\t// also remove goal and infinity states from state rewards vector\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\t\n\t// combine state and transition rewards\n\tCudd_Ref(trans_rewards);\n\tstate_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, trans_rewards);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// call iterative method\n\tsol = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsol = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1PowerInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, flags));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsol = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, 1.0, flags));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsol = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, lin_eq_method_param, flags));\n\t\t\tbreak;\n\t\tdefault:\n\t\t\t// set error message and return NULL pointer after cleanup, below\n\t\t\tPN_SetErrorMessage(\"Gauss-Seidel and its variants are currently not supported by the MTBDD engine\");\n\t\t\tbreak;\n\t}\n\t\n\t// set reward for infinity states to infinity\n\tif (sol != NULL) {\n\t\tCudd_Ref(inf);\n\t\tsol = DD_ITE(ddman, inf, DD_PlusInfinity(ddman), sol);\n\t}\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, state_rewards);\n\tCudd_RecursiveDeref(ddman, trans_rewards);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ProbTransient.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <prism.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbTransient\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// rate matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer in,\t// initial distribution (note: this will be derefed afterwards)\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njint time\t\t// time\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *init = jlong_to_DdNode(in);\t\t// initial distribution\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *sol, *tmp;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint iters;\n\tbool done;\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// set up vectors\n\tCudd_Ref(init);\n\tsol = init;\n\tsol = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < time && !done; iters++) {\n\t\t\n\t\t//matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, cvars, rvars, num_rvars);\n\t\tCudd_Ref(trans);\n\t\ttmp = DD_MatrixMultiply(ddman, tmp, trans, rvars, num_rvars, MM_BOULDER);\n\t\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) switch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp, sol, term_crit_param)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)time);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t}\n\t\n\t// convert to row vector\n\tsol = DD_PermuteVariables(ddman, sol, cvars, rvars, num_rvars);\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tif (done) PN_PrintToMainLog(env, \"\\nSteady state detected at iteration %d\\n\", iters);\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// derefs\n\t// nb: we deref init, even though it is passed in as a param\n\tCudd_RecursiveDeref(ddman, init);\n\t\n\treturn ptr_to_jlong(sol);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ProbUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m\t// 'maybe' states\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach, *a, *b, *soln, *tmp;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp = DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// build b\n\tCudd_Ref(yes);\n\tb = yes;\n\t\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, 1.0));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, lin_eq_method_param));\n\t\t\tbreak;\n\t\tdefault:\n\t\t\t// set error message and return NULL pointer after cleanup, below\n\t\t\tPN_SetErrorMessage(\"Gauss-Seidel and its variants are currently not supported by the MTBDD engine\");\n\t\t\tbreak;\n\t}\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, b);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_ProbUntilInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"IntervalIteration.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1ProbUntilInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach, *a, *b, *lower, *upper, *soln, *tmp;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp = DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// build b\n\tCudd_Ref(yes);\n\tb = yes;\n\t// lower bounds = b\n\tCudd_Ref(b);\n\tlower = b;\n\t\n\t// build upper (yes and maybe = 1)\n\tCudd_Ref(yes);\n\tCudd_Ref(maybe);\n\tupper = DD_Or(ddman, yes, maybe);\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1PowerInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, flags));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, 1.0, flags));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, lin_eq_method_param, flags));\n\t\t\tbreak;\n\t\tdefault:\n\t\t\t// set error message and return NULL pointer after cleanup, below\n\t\t\tPN_SetErrorMessage(\"Gauss-Seidel and its variants are currently not supported by the MTBDD engine\");\n\t\t\tbreak;\n\t}\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, b);\n\tCudd_RecursiveDeref(ddman, lower);\n\tCudd_RecursiveDeref(ddman, upper);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_Reachability.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\n// Calculates states reachable from the given subset (s)\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1Reachability\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t01,\t// 0-1 trans matrix\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer s\t// start state\n)\n{\n\tDdNode *trans01 = jlong_to_DdNode(t01);\t\t// 0-1 trans matrix\n\tDdNode *init = jlong_to_DdNode(s);\t\t// start state\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\t\n\tDdNode *reach, *frontier, *tmp;\n\tbool done;\n\tint iters;\n\t\n\t// get PRISM options\n\tint reach_method = env->CallIntMethod(prism_obj, env->GetMethodID(prism_cls, \"getReachMethod\", \"()I\"));\n\tint info = env->CallIntMethod(prism_obj, env->GetMethodID(prism_cls, \"getExtraReachInfo\", \"()Z\"));\n\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\n\t// start clocks\n\tstart1 = util_cpu_time();\n\t\n\tif (reach_method == REACH_BFS) {\n\t\n\t\t// initialise\n\t\tdone = false;\n\t\titers = 0;\n\t\tCudd_Ref(init);\n\t\treach = DD_PermuteVariables(ddman, init, rvars, cvars, num_rvars);\n\t\tif (reach == NULL) return ptr_to_jlong(NULL);\n\t\t\n\t\twhile (!done) {\n\t\t\titers++;\n\t\t\t// output info on progress\n\t\t\tif (info > 0) {\n\t\t\t\tPN_PrintToMainLog(env, \"Iteration %d:\", iters);\n\t\t\t\tPN_PrintToMainLog(env, \" %0.f states\", DD_GetNumMinterms(ddman, reach, num_rvars));\n\t\t\t\tPN_PrintToMainLog(env, \" (%d nodes)\", DD_GetNumNodes(ddman, reach));\n\t\t\t\tstart2 = util_cpu_time();\n\t\t\t}\n\t\t\t// perform iteration\n\t\t\tCudd_Ref(reach);\n\t\t\ttmp = DD_PermuteVariables(ddman, reach, cvars, rvars, num_cvars);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\tCudd_Ref(trans01);\n\t\t\ttmp = DD_And(ddman, tmp, trans01);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\ttmp = DD_ThereExists(ddman, tmp, rvars, num_rvars);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\tCudd_Ref(reach);\n\t\t\ttmp = DD_Or(ddman, reach, tmp);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\t// check convergence\n\t\t\tif (tmp == reach) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tCudd_RecursiveDeref(ddman, reach);\n\t\t\treach = tmp;\n\t\t\t// output info on progress\n\t\t\tif (info > 0) {\n\t\t\t\tstop = util_cpu_time();\n\t\t\t\tPN_PrintToMainLog(env, \" (%.2f seconds)\\n\", (double)(stop - start2)/1000);\n\t\t\t}\n\t\t}\n\t\treach = DD_PermuteVariables(ddman, reach, cvars, rvars, num_cvars);\n\t\tif (reach == NULL) return ptr_to_jlong(NULL);\n\t}\n\telse {\n\t\t// initialise\n\t\tdone = false;\n\t\titers = 0;\n\t\tCudd_Ref(init);\n\t\treach = init;\n\t\tCudd_Ref(reach);\n\t\tfrontier = reach;\n\t\t\n\t\twhile (!done) {\n\t\t\titers++;\n\t\t\t// output info on progress\n\t\t\tif (info > 0) {\n\t\t\t\tPN_PrintToMainLog(env, \"Iteration %d:\", iters);\n\t\t\t\tPN_PrintToMainLog(env, \" %0.f states\", DD_GetNumMinterms(ddman, reach, num_rvars));\n\t\t\t\tPN_PrintToMainLog(env, \" (%d nodes)\", DD_GetNumNodes(ddman, reach));\n\t\t\t\tstart2 = util_cpu_time();\n\t\t\t}\n\t\t\t// perform iteration\n\t\t\tCudd_Ref(frontier);\n\t\t\ttmp = DD_PermuteVariables(ddman, frontier, cvars, rvars, num_cvars);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\tCudd_Ref(trans01);\n\t\t\ttmp = DD_And(ddman, tmp, trans01);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\ttmp = DD_ThereExists(ddman, tmp, rvars, num_rvars);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\tCudd_Ref(reach);\n\t\t\ttmp = DD_Or(ddman, reach, tmp);\n\t\t\tif (tmp == NULL) return ptr_to_jlong(NULL);\n\t\t\tCudd_RecursiveDeref(ddman, frontier);\n\t\t\tCudd_Ref(tmp);\n\t\t\tCudd_Ref(reach);\n\t\t\tfrontier = DD_And(ddman, tmp, DD_Not(ddman, reach));\n\t\t\tif (frontier) return ptr_to_jlong(NULL);\n\t\t\t// check convergence\n\t\t\tif (frontier == Cudd_ReadZero(ddman)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tCudd_RecursiveDeref(ddman, reach);\n\t\t\treach = tmp;\n\t\t\t// output info on progress\n\t\t\tif (info > 0) {\n\t\t\t\tstop = util_cpu_time();\n\t\t\t\tPN_PrintToMainLog(env, \" (%.2f seconds)\\n\", (double)(stop - start2)/1000);\n\t\t\t}\n\t\t}\n\t\treach = DD_PermuteVariables(ddman, reach, cvars, rvars, num_cvars);\n\t\tif (reach == NULL) return ptr_to_jlong(NULL);\n\t\tCudd_RecursiveDeref(ddman, frontier);\n\t}\n\t\n\t// stop clock\n\tstop = util_cpu_time();\n\ttime_taken = (double)(stop - start1)/1000;\n\ttime_for_setup = 0;\n\ttime_for_iters = time_taken;\n\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nReachability (%s): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", reach_method==REACH_BFS?\"BFS\":\"frontier\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\n\treturn ptr_to_jlong(reach);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_StochBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <prism.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1StochBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// rate matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ye,\t// 'yes' states\njlong __jlongpointer ma,\t// 'maybe' states\njdouble time,\t\t// time bound\njlong __jlongpointer mu\t// probs for multiplying\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(ye);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(ma);\t\t// 'maybe' states\n\tDdNode *mult = jlong_to_DdNode(mu);\t\t// probs for multiplying\n\n\t// model stats\n\tint n;\n\t// mtbdds\n\tDdNode *reach, *diags, *q, *r, *d, *sol, *tmp, *tmp2, *sum;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tlong i, iters, num_iters;\n\tdouble x, max_diag, weight, unif, term_crit_param_unif;\n\tbool done, combine;\n\t\n\t// METHOD 1 or METHOD 2? (combine rate matrix and diagonals or keep separate?)\n\tcombine = true; // 1\n//\tcombine = false; // 2\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// count number of states to be made absorbing\n\tx = DD_GetNumMinterms(ddman, maybe, num_cvars);\n\tPN_PrintToMainLog(env, \"\\nNumber of non-absorbing states: %.0f of %d (%.1f%%)\\n\", x,  n, 100.0*x/n);\n\t\n\t// compute diagonals\n\tPN_PrintToMainLog(env, \"\\nComputing diagonals MTBDD... \");\n\tCudd_Ref(trans);\n\tdiags = DD_SumAbstract(ddman, trans, cvars, num_rvars);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, diags, DD_Constant(ddman, -1));\n\ti = DD_GetNumNodes(ddman, diags);\n\tPN_PrintToMainLog(env, \"[nodes=%ld] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\n\tif (combine) {\n\t\t\n\t\tPN_PrintToMainLog(env, \"Building iteration matrix MTBDD... \");\n\t\t\n\t\t// METHOD 1 (combine rate matrix and diagonals)\n\t\t\n\t\t// build generator matrix q from trans and diags\n\t\t// note that any self loops are effectively removed because we include their rates\n\t\t// in the 'diags' row sums and then subtract these from the original rate matrix\n\t\t// same applies in the \"!combine\" case below\n\t\tCudd_Ref(trans);\n\t\tCudd_Ref(diags);\n\t\tq = DD_Apply(ddman, APPLY_PLUS, trans, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), diags));\n//\t\tPN_PrintToMainLog(env, \"Q = %d %d %.0f\\n\", DD_GetNumNodes(ddman, q), DD_GetNumTerminals(ddman, q), DD_GetNumMinterms(ddman, q, num_rvars+num_cvars));\n\t\t\n\t\t// filter out rows\n\t\tCudd_Ref(maybe);\n\t\tq = DD_Apply(ddman, APPLY_TIMES, q, maybe);\n\t\t\n\t\t// find max diagonal element\n\t\tCudd_Ref(diags);\n\t\tCudd_Ref(maybe);\n\t\td = DD_Apply(ddman, APPLY_TIMES, diags, maybe);\n\t\tmax_diag = -DD_FindMin(ddman, d);\n\t\tCudd_RecursiveDeref(ddman, d);\n\t\t\n\t\t// constant for uniformization\n\t\tunif = 1.02*max_diag;\n\t\t\n\t\t// uniformization\t\n\t\tq = DD_Apply(ddman, APPLY_DIVIDE, q, DD_Constant(ddman, unif));\n\t\tCudd_Ref(reach);\n\t\tq = DD_Apply(ddman, APPLY_PLUS, q, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), reach));\n//\t\tPN_PrintToMainLog(env, \"Q (final) = %d %d %.0f\\n\", DD_GetNumNodes(ddman, q), DD_GetNumTerminals(ddman, q), DD_GetNumMinterms(ddman, q, num_rvars+num_cvars));\n\t\t\n\t\ti = DD_GetNumNodes(ddman, q);\n\t\tPN_PrintToMainLog(env, \"[nodes=%ld] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t}\n\telse {\n\t\t\n\t\t// METHOD 2 (keep rate matrix and diagonals separate)\n\t\t\n\t\tPN_PrintToMainLog(env, \"Building iteration matrix MTBDD... \");\n\t\t\n\t\t// copy trans/diags\n\t\tCudd_Ref(trans);\n\t\tr = trans;\n\t\tCudd_Ref(diags);\n\t\td = diags;\n//\t\tPN_PrintToMainLog(env, \"r = %d %d %.0f\\n\", DD_GetNumNodes(ddman, r), DD_GetNumTerminals(ddman, r), DD_GetNumMinterms(ddman, r, num_rvars+num_cvars));\n//\t\tPN_PrintToMainLog(env, \"diags = %d %d %.0f\\n\", DD_GetNumNodes(ddman, d), DD_GetNumTerminals(ddman, d), DD_GetNumMinterms(ddman, d, num_rvars));\n\t\t\n\t\t// filter out rows\n\t\tCudd_Ref(maybe);\n\t\tr = DD_Apply(ddman, APPLY_TIMES, r, maybe);\n\t\tCudd_Ref(maybe);\n\t\td = DD_Apply(ddman, APPLY_TIMES, d, maybe);\n\t\t\n\t\t// find max diagonal element\n\t\tmax_diag = -DD_FindMin(ddman, d);\n\t\t\n\t\t// constant for uniformization\n\t\tunif = 1.02*max_diag;\n\t\t\n\t\t// uniformization\t\n\t\tr = DD_Apply(ddman, APPLY_DIVIDE, r, DD_Constant(ddman, unif));\n\t\td = DD_Apply(ddman, APPLY_DIVIDE, d, DD_Constant(ddman, unif));\n\t\tCudd_Ref(reach);\n\t\td = DD_Apply(ddman, APPLY_PLUS, d, reach);\n//\t\tPN_PrintToMainLog(env, \"r (final) = %d %d %.0f\\n\", DD_GetNumNodes(ddman, r), DD_GetNumTerminals(ddman, r), DD_GetNumMinterms(ddman, r, num_rvars+num_cvars));\n//\t\tPN_PrintToMainLog(env, \"diags (final) = %d %d %.0f\\n\", DD_GetNumNodes(ddman, d), DD_GetNumTerminals(ddman, d), DD_GetNumMinterms(ddman, d, num_rvars));\n\t\t\n\t\ti = DD_GetNumNodes(ddman, r);\n\t\tPN_PrintToMainLog(env, \"[nodes=%ld] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t}\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) {\n\t\tPN_SetErrorMessage(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\n\t\tif (combine) {\n\t\t\t// METHOD 1\n\t\t\tCudd_RecursiveDeref(ddman, q);\n\t\t}\n\t\telse {\n\t\t\t// METHOD 2\n\t\t\tCudd_RecursiveDeref(ddman, r);\n\t\t\tCudd_RecursiveDeref(ddman, d);\n\t\t}\n\t\tCudd_RecursiveDeref(ddman, diags);\n\t\treturn 0;\n\t}\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n//\tPN_PrintToMainLog(env, \"right-left = %d\\n\", fgw.right-fgw.left);\n//\tPN_PrintToMainLog(env, \"total_weight = %f\\n\", fgw.total_weight);\n//\tfor (int i = 0; i < (fgw.right-fgw.left+1); i++) {\n//\t\tPN_PrintToMainLog(env, \"%.20f\\n\", fgw.weights[i]/fgw.total_weight);\n//\t}\n\t\n\t// set up vectors\n\tCudd_Ref(yes);\n\tsol = yes;\n\tsum = DD_Constant(ddman, 0);\n\t\n\t// multiply initial solution by 'mult' probs\n\tif (mult != NULL) {\n\t\tCudd_Ref(mult);\n\t\tsol = DD_Apply(ddman, APPLY_TIMES, sol, mult);\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n//\tPN_PrintToMainLog(env, \"Iteration 0: (%d %d %.0f)\", DD_GetNumNodes(ddman, sol), DD_GetNumTerminals(ddman, sol), DD_GetNumMinterms(ddman, sol, num_rvars));\n//\tPN_PrintToMainLog(env, \" (%d %d %.0f)\\n\", DD_GetNumNodes(ddman, sum), DD_GetNumTerminals(ddman, sum), DD_GetNumMinterms(ddman, sum, num_rvars));\n\t\n\t// if necessary, do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) {\n\t\tCudd_Ref(sol);\n\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, sol, DD_Constant(ddman, fgw.weights[0])));\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\n\t\tif (combine) {\n\t\t\t\n\t\t\t// METHOD 1 (combine rate matrix and diagonals)\n\t\t\t\n\t\t\t//matrix-vector multiply\n\t\t\tCudd_Ref(sol);\n\t\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\t\tCudd_Ref(q);\n\t\t\ttmp = DD_MatrixMultiply(ddman, q, tmp, cvars, num_cvars, MM_BOULDER);\n\t\t\n\t\t}\n\t\telse {\n\t\t\n\t\t\t// METHOD 2 (combine rate matrix and diagonals)\n\t\t\t\n\t\t\t//matrix-vector multiply\n\t\t\tCudd_Ref(sol);\n\t\t\tCudd_Ref(d);\n\t\t\ttmp2 = DD_Apply(ddman, APPLY_TIMES, sol, d);\n\t\t\tCudd_Ref(sol);\n\t\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\t\tCudd_Ref(r);\n\t\t\ttmp = DD_MatrixMultiply(ddman, r, tmp, cvars, num_cvars, MM_BOULDER);\n\t\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, tmp2);\n\t\t\n\t\t}\n\t\t\n//\t\tPN_PrintToMainLog(env, \"(%d %d %.0f) \", DD_GetNumNodes(ddman, sol), DD_GetNumTerminals(ddman, sol), DD_GetNumMinterms(ddman, sol, num_rvars));\n//\t\tPN_PrintToMainLog(env, \"(%d %d %.0f)\\n\", DD_GetNumNodes(ddman, sum), DD_GetNumTerminals(ddman, sum), DD_GetNumMinterms(ddman, sum, num_rvars));\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) switch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp, sol, term_crit_param_unif)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp, sol, term_crit_param_unif)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = 1.0;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tCudd_Ref(tmp);\n\t\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, tmp, DD_Constant(ddman, weight)));\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t\t\n\t\t// add to sum\n\t\tif (iters >= fgw.left) {\n\t\t\tCudd_Ref(sol);\n\t\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, sol, DD_Constant(ddman, fgw.weights[iters-fgw.left])));\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// free memory\n\tif (combine) {\n\t\t// METHOD 1\n\t\tCudd_RecursiveDeref(ddman, q);\n\t}\n\telse {\n\t\t// METHOD 2\n\t\tCudd_RecursiveDeref(ddman, r);\n\t\tCudd_RecursiveDeref(ddman, d);\n\t}\n\tCudd_RecursiveDeref(ddman, diags);\n\tCudd_RecursiveDeref(ddman, sol);\n\tif (fgw.weights) delete[] fgw.weights;\n\t\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_StochCumulReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <prism.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1StochCumulReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njdouble time\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *reach, *diags, *q, *sol, *tmp, *sum;\n\t// model stats\n//\tint n;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tlong i, iters, num_iters;\n\tdouble max_diag, weight, unif, term_crit_param_unif;\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n//\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// compute diagonals\n\tPN_PrintToMainLog(env, \"\\nComputing diagonals MTBDD... \");\n\tCudd_Ref(trans);\n\tdiags = DD_SumAbstract(ddman, trans, cvars, num_rvars);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, diags, DD_Constant(ddman, -1));\n\ti = DD_GetNumNodes(ddman, diags);\n\tPN_PrintToMainLog(env, \"[nodes=%ld] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\n\tPN_PrintToMainLog(env, \"Building iteration matrix MTBDD... \");\n\t\n\t// build generator matrix q from trans and diags\n\t// note that any self loops are effectively removed because we include their rates\n\t// in the 'diags' row sums and then subtract these from the original rate matrix\n\t// same applies in the \"!combine\" case below\n\tCudd_Ref(trans);\n\tCudd_Ref(diags);\n\tq = DD_Apply(ddman, APPLY_PLUS, trans, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), diags));\n\t\n\t// find max diagonal element\n\tmax_diag = -DD_FindMin(ddman, diags);\n\t\n\t// constant for uniformization\n\tunif = 1.02*max_diag;\n\t\n\t// uniformization\n\tq = DD_Apply(ddman, APPLY_DIVIDE, q, DD_Constant(ddman, unif));\n\tCudd_Ref(reach);\n\tq = DD_Apply(ddman, APPLY_PLUS, q, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), reach));\n\ti = DD_GetNumNodes(ddman, q);\n\tPN_PrintToMainLog(env, \"[nodes=%ld] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\n\t// combine state/transition rewards into a single vector - this is the initial solution vector\n\tCudd_Ref(trans);\n\tCudd_Ref(trans_rewards);\n\tsol = DD_Apply(ddman, APPLY_TIMES, trans, trans_rewards);\n\tsol = DD_SumAbstract(ddman, sol, cvars, num_cvars);\n\tCudd_Ref(state_rewards);\n\tsol = DD_Apply(ddman, APPLY_PLUS, sol, state_rewards);\n\t\n\t// set up sum vector\n\tsum = DD_Constant(ddman, 0);\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) {\n\t\tPN_SetErrorMessage(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\t\tCudd_RecursiveDeref(ddman, q);\n\t\tCudd_RecursiveDeref(ddman, diags);\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tCudd_RecursiveDeref(ddman, sum);\n\t\treturn 0;\n\t}\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n\t// modify the poisson probabilities to what we need for this computation\n\t// first make the kth value equal to the sum of the values for 0...k\n\tfor (i = fgw.left+1; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] += fgw.weights[i-1-fgw.left];\n\t}\n\t// then subtract from 1 and divide by uniformisation constant (q) to give mixed poisson probabilities\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] = (1 - fgw.weights[i-fgw.left]) / unif;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start transient analysis\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) {\n\t\tCudd_Ref(sol);\n\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, sol, DD_Constant(ddman, fgw.weights[0])));\n\t} else {\n\t\tCudd_Ref(sol);\n\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_DIVIDE, sol, DD_Constant(ddman, unif)));\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\t\n\t\t//matrix-vector multiply\n\t\tCudd_Ref(sol);\n\t\ttmp = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\t\tCudd_Ref(q);\n\t\ttmp = DD_MatrixMultiply(ddman, q, tmp, cvars, num_cvars, MM_BOULDER);\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) switch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp, sol, term_crit_param_unif)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp, sol, term_crit_param_unif)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = time - iters/unif;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tCudd_Ref(tmp);\n\t\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, tmp, DD_Constant(ddman, weight)));\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t\t\n\t\t// add to sum\n\t\tif (iters < fgw.left) {\n\t\t\tCudd_Ref(sol);\n\t\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_DIVIDE, sol, DD_Constant(ddman, unif)));\n\t\t} else {\n\t\t\tCudd_Ref(sol);\n\t\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, sol, DD_Constant(ddman, fgw.weights[iters-fgw.left])));\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, q);\n\tCudd_RecursiveDeref(ddman, diags);\n\tCudd_RecursiveDeref(ddman, sol);\n\tif (fgw.weights) delete[] fgw.weights;\n\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_StochSteadyState.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1StochSteadyState\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer in,\t// init soln\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *init = jlong_to_DdNode(in);\t\t// init soln\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\t// mtbdds\n\tDdNode *diags, *q, *a, *b, *soln;\n\t// misc\n\tdouble deltat;\n\t\n\t// compute diagonals\n\tCudd_Ref(trans);\n\tdiags = DD_SumAbstract(ddman, trans, cvars, num_rvars);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, diags, DD_Constant(ddman, -1));\n\t\n\t// if diagonal is 0 set it to -1\n\t// (fix for when we are solving subsystem e.g. BSCC)\n\tCudd_Ref(diags);\n\tdiags = DD_ITE(ddman, DD_LessThan(ddman, diags, 0), diags, DD_Constant(ddman, -1));\n\t\n\t// build generator matrix q from trans and diags\n\t// note that any self loops are effectively removed because we include their rates\n\t// in the 'diags' row sums and then subtract these from the original rate matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(diags);\n\tq = DD_Apply(ddman, APPLY_PLUS, trans, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), diags));\n\t\n\t// If we are going to solve with the power method, we have to modify the matrix a bit\n\t// in order to guarantee convergence. Hence, we compute the iteration matrix\n\t// a = q * deltaT + I\n\t// where I is the identity matrix.\n\t// Please refer to \"William J. Stewart: Introduction to the Numerical Solution of Markov Chains\" p. 124. for details.\n\tif (lin_eq_method == LIN_EQ_METHOD_POWER) {\n\t\t// choose deltat\n\t\tdeltat = -0.99 / DD_FindMin(ddman, diags);\n\t\t// build iteration matrix\n\t\tCudd_Ref(q);\n\t\ta = DD_Apply(ddman, APPLY_PLUS, DD_Apply(ddman, APPLY_TIMES, DD_Constant(ddman, deltat), q), DD_Identity(ddman, rvars, cvars, num_rvars));\n\t}\n\telse {\n\t\tCudd_Ref(q);\n\t\ta = q;\n\t}\n\t\n\t// b vector is all zeros\n\tb = DD_Constant(ddman, 0);\n\t\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(init), true));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(init), true, 1.0));\n\t\t\tbreak;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_DdNode(Java_mtbdd_PrismMTBDD_PM_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(init), true, lin_eq_method_param));\n\t\t\tbreak;\n\t\tdefault:\n\t\t\t// set error message and return NULL pointer after cleanup, below\n\t\t\tPN_SetErrorMessage(\"Gauss-Seidel and its variants are currently not supported by the MTBDD engine\");\n\t\t\tbreak;\n\t}\n\t\n\t// normalise\n\tif (soln != NULL) {\n\t\tCudd_Ref(soln);\n\t\tsoln = DD_Apply(ddman, APPLY_DIVIDE, soln, DD_SumAbstract(ddman, soln, rvars, num_rvars));\n\t}\n\t\n\t// free memory\n\tCudd_RecursiveDeref(ddman, diags);\n\tCudd_RecursiveDeref(ddman, q);\n\tCudd_RecursiveDeref(ddman, a);\n\tCudd_RecursiveDeref(ddman, b);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PM_StochTransient.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismMTBDD.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <prism.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_mtbdd_PrismMTBDD_PM_1StochTransient\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// rate matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer in,\t// initial distribution (note: this will be derefed afterwards)\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njdouble time\t\t\t\t// time\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *init = jlong_to_DdNode(in);\t\t// initial distribution\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// model stats\n\tint n;\n\t// mtbdds\n\tDdNode *reach, *diags, *q, *r, *d, *sol, *tmp, *tmp2, *sum;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tlong i, iters, num_iters;\n\tdouble max_diag, weight, unif, term_crit_param_unif;\n\tbool done, combine;\n\t\n\t// METHOD 1 or METHOD 2? (combine rate matrix and diagonals or keep separate?)\n\tcombine = true; // 1\n//\tcombine = false; // 2\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// compute diagonals\n\tPN_PrintToMainLog(env, \"\\nComputing diagonals MTBDD... \");\n\tCudd_Ref(trans);\n\tdiags = DD_SumAbstract(ddman, trans, cvars, num_rvars);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, diags, DD_Constant(ddman, -1));\n\ti = DD_GetNumNodes(ddman, diags);\n\tPN_PrintToMainLog(env, \"[nodes=%ld] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t\n\tif (combine) {\n\t\t\n\t\tPN_PrintToMainLog(env, \"Building iteration matrix MTBDD... \");\n\t\t\n\t\t// METHOD 1 (combine rate matrix and diagonals)\n\t\t\n\t\t// build generator matrix q from trans and diags\n\t\t// note that any self loops are effectively removed because we include their rates\n\t\t// in the 'diags' row sums and then subtract these from the original rate matrix\n\t\t// same applies in the \"!combine\" case below\n\t\tCudd_Ref(trans);\n\t\tCudd_Ref(diags);\n\t\tq = DD_Apply(ddman, APPLY_PLUS, trans, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), diags));\n//\t\tPN_PrintToMainLog(env, \"Q = %d %d %.0f\\n\", DD_GetNumNodes(ddman, q), DD_GetNumTerminals(ddman, q), DD_GetNumMinterms(ddman, q, num_rvars+num_cvars));\n\t\t\n\t\t// find max diagonal element\n\t\tmax_diag = -DD_FindMin(ddman, diags);\n\t\t\n\t\t// constant for uniformization\n\t\tunif = 1.02*max_diag;\n\t\t\n\t\t// uniformization\t\n\t\tq = DD_Apply(ddman, APPLY_DIVIDE, q, DD_Constant(ddman, unif));\n\t\tCudd_Ref(reach);\n\t\tq = DD_Apply(ddman, APPLY_PLUS, q, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), reach));\n//\t\tPN_PrintToMainLog(env, \"Q (final) = %d %d %.0f\\n\", DD_GetNumNodes(ddman, q), DD_GetNumTerminals(ddman, q), DD_GetNumMinterms(ddman, q, num_rvars+num_cvars));\n\t\t\n\t\ti = DD_GetNumNodes(ddman, q);\n\t\tPN_PrintToMainLog(env, \"[nodes=%ld] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t}\n\telse {\n\t\t\n\t\t// METHOD 2 (keep rate matrix and diagonals separate)\n\t\t\n\t\tPN_PrintToMainLog(env, \"Building iteration matrix MTBDD... \");\n\t\t\n\t\t// copy trans/diags\n\t\tCudd_Ref(trans);\n\t\tr = trans;\n\t\tCudd_Ref(diags);\n\t\td = diags;\n//\t\tPN_PrintToMainLog(env, \"r = %d %d %.0f\\n\", DD_GetNumNodes(ddman, r), DD_GetNumTerminals(ddman, r), DD_GetNumMinterms(ddman, r, num_rvars+num_cvars));\n//\t\tPN_PrintToMainLog(env, \"diags = %d %d %.0f\\n\", DD_GetNumNodes(ddman, d), DD_GetNumTerminals(ddman, d), DD_GetNumMinterms(ddman, d, num_rvars));\n\t\t\n\t\t// find max diagonal element\n\t\tmax_diag = -DD_FindMin(ddman, d);\n\t\t\n\t\t// constant for uniformization\n\t\tunif = 1.02*max_diag;\n\t\t\n\t\t// uniformization\t\n\t\tr = DD_Apply(ddman, APPLY_DIVIDE, r, DD_Constant(ddman, unif));\n\t\td = DD_Apply(ddman, APPLY_DIVIDE, d, DD_Constant(ddman, unif));\n\t\tCudd_Ref(reach);\n\t\td = DD_Apply(ddman, APPLY_PLUS, d, reach);\n//\t\tPN_PrintToMainLog(env, \"r (final) = %d %d %.0f\\n\", DD_GetNumNodes(ddman, r), DD_GetNumTerminals(ddman, r), DD_GetNumMinterms(ddman, r, num_rvars+num_cvars));\n//\t\tPN_PrintToMainLog(env, \"diags (final) = %d %d %.0f\\n\", DD_GetNumNodes(ddman, d), DD_GetNumTerminals(ddman, d), DD_GetNumMinterms(ddman, d, num_rvars));\n\t\t\n\t\t// transpose diagonals\n\t\tdiags = DD_PermuteVariables(ddman, diags, rvars, cvars, num_rvars);\n\t\t\n\t\ti = DD_GetNumNodes(ddman, r);\n\t\tPN_PrintToMainLog(env, \"[nodes=%ld] [%.1f Kb]\\n\", i, i*20.0/1024.0);\n\t}\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) {\n\t\tPN_SetErrorMessage(\"Overflow in Fox-Glynn computation (time bound too big?)\");\n\n\t\tif (combine) {\n\t\t\t// METHOD 1\n\t\t\tCudd_RecursiveDeref(ddman, q);\n\t\t}\n\t\telse {\n\t\t\t// METHOD 2\n\t\t\tCudd_RecursiveDeref(ddman, r);\n\t\t\tCudd_RecursiveDeref(ddman, d);\n\t\t}\n\t\tCudd_RecursiveDeref(ddman, diags);\n\t\t// nb: we deref init, even though it is passed in as a param\n\t\tCudd_RecursiveDeref(ddman, init);\n\n\t\treturn 0;\n\t}\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n//\tPN_PrintToMainLog(env, \"right-left = %d\\n\", fgw.right-fgw.left);\n//\tPN_PrintToMainLog(env, \"total_weight = %f\\n\", fgw.total_weight);\n//\tfor (int i = 0; i < (fgw.right-fgw.left+1); i++) {\n//\t\tPN_PrintToMainLog(env, \"%.20f\\n\", fgw.weights[i]/fgw.total_weight);\n//\t}\n\t\n\t// set up vectors\n\tCudd_Ref(init);\n\tsol = init;\n\tsol = DD_PermuteVariables(ddman, sol, rvars, cvars, num_rvars);\n\tsum = DD_Constant(ddman, 0);\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n//\tPN_PrintToMainLog(env, \"Iteration 0: (%d %d %.0f)\", DD_GetNumNodes(ddman, sol), DD_GetNumTerminals(ddman, sol), DD_GetNumMinterms(ddman, sol, num_rvars));\n//\tPN_PrintToMainLog(env, \" (%d %d %.0f)\\n\", DD_GetNumNodes(ddman, sum), DD_GetNumTerminals(ddman, sum), DD_GetNumMinterms(ddman, sum, num_rvars));\n\t\n\t// if necessary, do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) {\n\t\tCudd_Ref(sol);\n\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, sol, DD_Constant(ddman, fgw.weights[0])));\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\t\n\t\tif (combine) {\n\t\t\t\n\t\t\t// METHOD 1 (combine rate matrix and diagonals)\n\t\t\t\n\t\t\t//matrix-vector multiply\n\t\t\tCudd_Ref(sol);\n\t\t\ttmp = DD_PermuteVariables(ddman, sol, cvars, rvars, num_rvars);\n\t\t\tCudd_Ref(q);\n\t\t\ttmp = DD_MatrixMultiply(ddman, tmp, q, rvars, num_rvars, MM_BOULDER);\n\t\t\t\n\t\t}\n\t\telse {\n\t\t\t\n\t\t\t// METHOD 2 (combine rate matrix and diagonals)\n\t\t\t\n\t\t\t//matrix-vector multiply\n\t\t\tCudd_Ref(sol);\n\t\t\tCudd_Ref(d);\n\t\t\ttmp2 = DD_Apply(ddman, APPLY_TIMES, sol, d);\n\t\t\tCudd_Ref(sol);\n\t\t\ttmp = DD_PermuteVariables(ddman, sol, cvars, rvars, num_rvars);\n\t\t\tCudd_Ref(r);\n\t\t\ttmp = DD_MatrixMultiply(ddman, tmp, r, rvars, num_rvars, MM_BOULDER);\n\t\t\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, tmp2);\n\t\t\t\n\t\t}\n\t\t\n//\t\tPN_PrintToMainLog(env, \"(%d %d %.0f) \", DD_GetNumNodes(ddman, sol), DD_GetNumTerminals(ddman, sol), DD_GetNumMinterms(ddman, sol, num_rvars));\n//\t\tPN_PrintToMainLog(env, \"(%d %d %.0f)\\n\", DD_GetNumNodes(ddman, sum), DD_GetNumTerminals(ddman, sum), DD_GetNumMinterms(ddman, sum, num_rvars));\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) switch (term_crit) {\n\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\tif (DD_EqualSupNorm(ddman, tmp, sol, term_crit_param_unif)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TERM_CRIT_RELATIVE:\n\t\t\tif (DD_EqualSupNormRel(ddman, tmp, sol, term_crit_param_unif)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = 1.0;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tCudd_Ref(tmp);\n\t\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, tmp, DD_Constant(ddman, weight)));\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\tCudd_RecursiveDeref(ddman, sol);\n\t\tsol = tmp;\n\t\t\n\t\t// add to sum\n\t\tif (iters >= fgw.left) {\n\t\t\tCudd_Ref(sol);\n\t\t\tsum = DD_Apply(ddman, APPLY_PLUS, sum, DD_Apply(ddman, APPLY_TIMES, sol, DD_Constant(ddman, fgw.weights[iters-fgw.left])));\n\t\t}\n\t}\n\t\n\t// convert to row vector\n\tsum = DD_PermuteVariables(ddman, sum, cvars, rvars, num_rvars);\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// free memory\n\tif (combine) {\n\t\t// METHOD 1\n\t\tCudd_RecursiveDeref(ddman, q);\n\t}\n\telse {\n\t\t// METHOD 2\n\t\tCudd_RecursiveDeref(ddman, r);\n\t\tCudd_RecursiveDeref(ddman, d);\n\t}\n\tCudd_RecursiveDeref(ddman, diags);\n\tCudd_RecursiveDeref(ddman, sol);\n\t// nb: we deref init, even though it is passed in as a param\n\tCudd_RecursiveDeref(ddman, init);\n\tif (fgw.weights) delete[] fgw.weights;\n\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/mtbdd/PrismMTBDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Gethin Norman <gethin.norman@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage mtbdd;\n\nimport java.io.FileNotFoundException;\n\nimport prism.*;\nimport jdd.*;\nimport odd.*;\n\n//------------------------------------------------------------------------------\n\npublic class PrismMTBDD\n{\n\t//------------------------------------------------------------------------------\n\t// load jni stuff from shared library\n\t//------------------------------------------------------------------------------\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\t\n\t//------------------------------------------------------------------------------\n\t// error message\n\t//------------------------------------------------------------------------------\n\t\n\tpublic static String getErrorMessage()\n\t{\n\t\treturn PrismNative.PN_GetErrorMessage();\n\t}\n\n\t/**\n\t * Generate the proper exception for an error from the native layer.\n\t * Gets the error message and returns the corresponding exception,\n\t * i.e., if the message contains \"not supported\" then a PrismNotSupportedException\n\t * is returned, otherwise a plain PrismException.\n\t */\n\tprivate static PrismException generateExceptionForError()\n\t{\n\t\tString msg = getErrorMessage();\n\t\tif (msg.contains(\"not supported\")) {\n\t\t\treturn new PrismNotSupportedException(msg);\n\t\t} else {\n\t\t\treturn new PrismException(msg);\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// JNI wrappers for blocks of mtbdd code\n\t//------------------------------------------------------------------------------\n\n\t//------------------------------------------------------------------------------\n\t// reachability based stuff\n\t//------------------------------------------------------------------------------\n\n\tprivate static native long PM_Reachability(long trans01, long rv, int nrv, long cv, int ncv, long start);\n\t/**\n\t * Reachability computation, computes the set Post*(start).\n\t * <br>\n\t * Note: For non-deterministic models, take the transition matrix\n\t * with the non-deterministic choices removed, i.e., getTransReln().\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param trans01 the 0/1-transition matrix of the model (over rows, cols)\n\t * @param rows the row variables of the model\n\t * @param cols the col variables of the model\n\t * @param start the starting states for the reachability computation\n\t * @return the set of states that can be reached from start\n\t */\n\tpublic static JDDNode Reachability(JDDNode trans01, JDDVars rows, JDDVars cols, JDDNode start)\n\t{\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsZeroOneMTBDD(trans01);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, rows, cols);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(start, rows);\n\t\t}\n\n\t\tlong ptr = PM_Reachability(trans01.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), start.ptr());\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\tprivate static native long PM_Prob1(long trans01, long reach, long rv, int nrv, long cv, int ncv, long b1, long b2, long no);\n\t/**\n\t * PCTL until probability 1 precomputation (probabilistic/dtmc)\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param trans01 the 0/1-transition matrix of the DTMC (trans01, over rows, cols)\n\t * @param reach the set of reachable states in the DTMC\n\t * @param rows the row variables of the model\n\t * @param cols the col variables of the model\n\t * @param b1 the set of b1 states (needs to be contained in reach)\n\t * @param b2 the set of b2 states (needs to be contained in reach)\n\t * @param no the set of states with 'P[ b1 U b2 ] = 0'\n\t * @return the set of states with 'P[ b1 U b2 ] = 1'\n\t */\n\tpublic static JDDNode Prob1(JDDNode trans01, JDDNode reach, JDDVars rows, JDDVars cols, JDDNode b1, JDDNode b2, JDDNode no)// throws PrismException\n\t{\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsZeroOneMTBDD(trans01);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, rows, cols);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(reach, rows);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b1, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b1, reach);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b2, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b2, reach);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(no, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(no, reach);\n\t\t}\n\n\t\tlong ptr = PM_Prob1(trans01.ptr(), reach.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), b1.ptr(), b2.ptr(), no.ptr());\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\tprivate static native long PM_Prob0(long trans01, long reach, long rv, int nrv, long cv, int ncv, long b1, long b2);\n\t/**\n\t * PCTL until probability 0 precomputation (probabilistic/dtmc)\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param trans01 the 0/1-transition matrix of the DTMC (trans01, over rows, cols)\n\t * @param reach the set of reachable states in the DTMC\n\t * @param rows the row variables of the model\n\t * @param cols the col variables of the model\n\t * @param b1 the set of b1 states (needs to be contained in reach)\n\t * @param b2 the set of b2 states (needs to be contained in reach)\n\t * @return the set of states with 'P[ b1 U b2 ] = 0'\n\t */\n\tpublic static JDDNode Prob0(JDDNode trans01, JDDNode reach, JDDVars rows, JDDVars cols, JDDNode b1, JDDNode b2)// throws PrismException\n\t{\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsZeroOneMTBDD(trans01);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, rows, cols);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(reach, rows);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b1, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b1, reach);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b2, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b2, reach);\n\t\t}\n\n\t\tlong ptr = PM_Prob0(trans01.ptr(), reach.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), b1.ptr(), b2.ptr());\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\tprivate static native long PM_Prob1E(long trans01, long reach, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long b1, long b2, long no);\n\t/**\n\t * PCTL until probability 1 precomputation - there exists (nondeterministic/mdp).\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param trans01 the 0/1-transition matrix of the MDP (trans01, over rows, cols, nd)\n\t * @param reach the set of reachable states in the MDP\n\t * @param rows the row variables of the model\n\t * @param cols the col variables of the model\n\t * @param nd the nondeterministic choice variables of the model\n\t * @param b1 the set of b1 states (needs to be contained in reach)\n\t * @param b2 the set of b2 states (needs to be contained in reach)\n\t * @param no the set of states with 'for all strategies P[ b1 U b2 ] = 0' (needs to be contained in reach)\n\t * @return the set of states with 'there exists a strategy with P[ b1 U b2 ] = 1'\n\t */\n\tpublic static JDDNode Prob1E(JDDNode trans01, JDDNode reach, JDDVars rows, JDDVars cols, JDDVars nd, JDDNode b1, JDDNode b2, JDDNode no)// throws PrismException\n\t{\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsZeroOneMTBDD(trans01);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, rows, cols, nd);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(reach, rows);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b1, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b1, reach);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b2, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b2, reach);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(no, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(no, reach);\n\t\t}\n\n\t\tlong ptr = PM_Prob1E(trans01.ptr(), reach.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nd.array(), nd.n(), b1.ptr(), b2.ptr(), no.ptr());\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\tprivate static native long PM_Prob1A(long trans01, long reach, long mask, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long no, long b2);\n\t/**\n\t * PCTL until probability 1 precomputation - for all (nondeterministic/mdp).\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param trans01 the 0/1-transition matrix of the MDP (trans01, over rows, cols, nd)\n\t * @param reach the set of reachable states in the model\n\t * @param nondetMask nondetMask of the model\n\t * @param rows the row variables of the model\n\t * @param cols the col variables of the model\n\t * @param nd the nondeterministic choice variables of the model\n\t * @param no the set of states with 'there exists a strategy for P[ b1 U b2 ] = 0' (needs to be contained in reach)\n\t * @param b2 the set of b2 states (needs to be contained in reach)\n\t * @return the set of states with 'for all strategies P[ b1 U b2 ] = 1'\n\t */\n\tpublic static JDDNode Prob1A(JDDNode trans01, JDDNode reach, JDDNode nondetMask, JDDVars rows, JDDVars cols, JDDVars nd, JDDNode no, JDDNode b2)// throws PrismException\n\t{\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsZeroOneMTBDD(trans01);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, rows, cols, nd);\n\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(nondetMask, rows, nd);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(reach, rows);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b2, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b2, reach);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(no, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(no, reach);\n\t\t}\n\t\tlong ptr = PM_Prob1A(trans01.ptr(), reach.ptr(), nondetMask.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nd.array(), nd.n(), no.ptr(), b2.ptr());\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\tprivate static native long PM_Prob0E(long trans01, long reach, long mask, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long b1, long b2);\n\t/**\n\t * PCTL until probability 0 precomputation - there exists (nondeterministic/mdp).\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param trans01 the 0/1-transition matrix of the MDP (trans01, over rows, cols, nd)\n\t * @param reach the set of reachable states in the model\n\t * @param nondetMask nondetMask of the model\n\t * @param rows the row variables of the model\n\t * @param cols the col variables of the model\n\t * @param nd the nondeterministic choice variables of the model\n\t * @param b1 the set of b1 states (needs to be contained in reach)\n\t * @param b2 the set of b2 states (needs to be contained in reach)\n\t * @return the set of states with 'there exists a strategy with P[ b1 U b2 ] = 0'\n\t */\n\tpublic static JDDNode Prob0E(JDDNode trans01, JDDNode reach, JDDNode nondetMask, JDDVars rows, JDDVars cols, JDDVars nd, JDDNode b1, JDDNode b2)// throws PrismException\n\t{\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsZeroOneMTBDD(trans01);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, rows, cols, nd);\n\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(nondetMask, rows, nd);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(reach, rows);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b1, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b1, reach);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b2, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b2, reach);\n\t\t}\n\n\t\tlong ptr = PM_Prob0E(trans01.ptr(), reach.ptr(), nondetMask.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nd.array(), nd.n(), b1.ptr(), b2.ptr());\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\tprivate static native long PM_Prob0A(long trans01, long reach, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long b1, long b2);\n\t/**\n\t * PCTL until probability 0 precomputation - for all (nondeterministic/mdp).\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param trans01 the 0/1-transition matrix of the MDP (trans01, over rows, cols, nd)\n\t * @param reach the set of reachable states in the model\n\t * @param rows the row variables of the model\n\t * @param cols the col variables of the model\n\t * @param nd the nondeterministic choice variables of the model\n\t * @param b1 the set of b1 states (needs to be contained in reach)\n\t * @param b2 the set of b2 states (needs to be contained in reach)\n\t * @return the set of states with 'for all strategies P[ b1 U b2 ] = 0'\n\t */\n\tpublic static JDDNode Prob0A(JDDNode trans01, JDDNode reach, JDDVars rows, JDDVars cols, JDDVars nd, JDDNode b1, JDDNode b2)// throws PrismException\n\t{\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsZeroOneMTBDD(trans01);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, rows, cols, nd);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(reach, rows);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b1, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b1, reach);\n\n\t\t\tjdd.SanityJDD.checkIsStateSet(b2, rows);\n\t\t\tjdd.SanityJDD.checkIsContainedIn(b2, reach);\n\t\t}\n\n\t\tlong ptr = PM_Prob0A(trans01.ptr(), reach.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nd.array(), nd.n(), b1.ptr(), b2.ptr());\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\t\n\t//------------------------------------------------------------------------------\n\t// probabilistic/dtmc stuff\n\t//------------------------------------------------------------------------------\n\n\t// pctl bounded until (probabilistic/dtmc)\n\tprivate static native long PM_ProbBoundedUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe, int bound);\n\tpublic static JDDNode ProbBoundedUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, int bound) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_ProbBoundedUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), bound);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\t\n\t// pctl until (probabilistic/dtmc)\n\tprivate static native long PM_ProbUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe);\n\tpublic static JDDNode ProbUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_ProbUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl until (probabilistic/dtmc), interval variant\n\tprivate static native long PM_ProbUntilInterval(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe, int flags);\n\tpublic static JDDNode ProbUntilInterval(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, int flags) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_ProbUntilInterval(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl cumulative reward (probabilistic/dtmc)\n\tprivate static native long PM_ProbCumulReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, int bound);\n\tpublic static JDDNode ProbCumulReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, int bound) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_ProbCumulReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), bound);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl inst reward (probabilistic/dtmc)\n\tprivate static native long PM_ProbInstReward(long trans, long sr, long odd, long rv, int nrv, long cv, int ncv, int time);\n\tpublic static JDDNode ProbInstReward(JDDNode trans, JDDNode sr, ODDNode odd, JDDVars rows, JDDVars cols, int time) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_ProbInstReward(trans.ptr(), sr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl reach reward (probabilistic/dtmc)\n\tprivate static native long PM_ProbReachReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long goal, long inf, long maybe);\n\tpublic static JDDNode ProbReachReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode goal, JDDNode inf, JDDNode maybe) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_ProbReachReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), goal.ptr(), inf.ptr(), maybe.ptr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl reach reward (probabilistic/dtmc), interval iteration\n\tprivate static native long PM_ProbReachRewardInterval(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long goal, long inf, long maybe, long lower, long upper, int flags);\n\tpublic static JDDNode ProbReachRewardInterval(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode goal, JDDNode inf, JDDNode maybe, JDDNode lower, JDDNode upper, int flags) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_ProbReachRewardInterval(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), goal.ptr(), inf.ptr(), maybe.ptr(), lower.ptr(), upper.ptr(), flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// transient (probabilistic/dtmc)\n\tprivate static native long PM_ProbTransient(long trans, long odd, long init, long rv, int nrv, long cv, int ncv, int time);\n\tpublic static JDDNode ProbTransient(JDDNode trans, ODDNode odd, JDDNode init, JDDVars rows, JDDVars cols, int time) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_ProbTransient(trans.ptr(), odd.ptr(), init.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// nondeterministic/mdp stuff\n\t//------------------------------------------------------------------------------\n\n\t// pctl bounded until (nondeterministic/mdp)\n\tprivate static native long PM_NondetBoundedUntil(long trans, long odd, long mask, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, int bound, boolean minmax);\n\tpublic static JDDNode NondetBoundedUntil(JDDNode trans, ODDNode odd, JDDNode nondetMask, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, int bound, boolean minmax) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_NondetBoundedUntil(trans.ptr(), odd.ptr(), nondetMask.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), bound, minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\t\n\t// pctl until (nondeterministic/mdp)\n\tprivate static native long PM_NondetUntil(long trans, long odd, long mask, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, boolean minmax);\n\tpublic static JDDNode NondetUntil(JDDNode trans, ODDNode odd, JDDNode nondetMask, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, boolean minmax) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_NondetUntil(trans.ptr(), odd.ptr(), nondetMask.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl until (nondeterministic/mdp), interval iteration\n\tprivate static native long PM_NondetUntilInterval(long trans, long odd, long mask, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, boolean minmax, int flags);\n\tpublic static JDDNode NondetUntilInterval(JDDNode trans, ODDNode odd, JDDNode nondetMask, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, boolean minmax, int flags) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_NondetUntilInterval(trans.ptr(), odd.ptr(), nondetMask.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), minmax, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl inst reward (nondeterministic/mdp)\n\tprivate static native long PM_NondetInstReward(long trans, long sr, long odd, long mask, long rv, int nrv, long cv, int ncv, long ndv, int nndv, int time, boolean minmax, long init);\n\tpublic static JDDNode NondetInstReward(JDDNode trans, JDDNode sr, ODDNode odd, JDDNode nondetMask, JDDVars rows, JDDVars cols, JDDVars nondet, int time, boolean minmax, JDDNode init) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_NondetInstReward(trans.ptr(), sr.ptr(), odd.ptr(), nondetMask.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), time, minmax, init.ptr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl reach reward (nondeterministic/mdp)\n\tprivate static native long PM_NondetReachReward(long trans, long sr, long trr, long odd, long mask, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long goal, long inf, long maybe, boolean minmax);\n\tpublic static JDDNode NondetReachReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDNode nondetMask, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode goal, JDDNode inf, JDDNode maybe, boolean minmax) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_NondetReachReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), nondetMask.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), goal.ptr(), inf.ptr(), maybe.ptr(), minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// pctl reach reward (nondeterministic/mdp), interval iteration\n\tprivate static native long PM_NondetReachRewardInterval(long trans, long sr, long trr, long odd, long mask, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long goal, long inf, long maybe, long lower, long upper, boolean minmax, int flags);\n\tpublic static JDDNode NondetReachRewardInterval(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDNode nondetMask, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode goal, JDDNode inf, JDDNode maybe, JDDNode lower, JDDNode upper, boolean minmax, int flags) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_NondetReachRewardInterval(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), nondetMask.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), goal.ptr(), inf.ptr(), maybe.ptr(), lower.ptr(), upper.ptr(), minmax, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// stochastic/ctmc stuff\n\t//------------------------------------------------------------------------------\n\n\t// csl time bounded until (stochastic/ctmc)\n\tprivate static native long PM_StochBoundedUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe, double time, long mult);\n\tpublic static JDDNode StochBoundedUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, double time, JDDNode multProbs) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong mult = (multProbs == null) ? 0 : multProbs.ptr();\n\t\tlong ptr = PM_StochBoundedUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), time, mult);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\t\n\t// csl cumulative reward (stochastic/ctmc)\n\tprivate static native long PM_StochCumulReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, double time);\n\tpublic static JDDNode StochCumulReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, double time) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_StochCumulReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\t\n\t// steady state (stochastic/ctmc)\n\tprivate static native long PM_StochSteadyState(long trans, long odd, long init, long rv, int nrv, long cv, int ncv);\n\tpublic static JDDNode StochSteadyState(JDDNode trans, ODDNode odd, JDDNode init, JDDVars rows, JDDVars cols) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_StochSteadyState(trans.ptr(), odd.ptr(), init.ptr(), rows.array(), rows.n(), cols.array(), cols.n());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\t\n\t// transient (stochastic/ctmc)\n\tprivate static native long PM_StochTransient(long trans, long odd, long init, long rv, int nrv, long cv, int ncv, double time);\n\tpublic static JDDNode StochTransient(JDDNode trans, ODDNode odd, JDDNode init, JDDVars rows, JDDVars cols, double time) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_StochTransient(trans.ptr(), odd.ptr(), init.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// export methods\n\t//------------------------------------------------------------------------------\n\n\t// export vector\n\tprivate static native int PM_ExportVector(long vector, String name, long vars, int nv, long odd, int exportType, String filename, String rewardStructName, boolean noexportheaders);\n\tpublic static void ExportVector(JDDNode vector, String name, JDDVars vars, ODDNode odd, int exportType, String filename, int precision, String rewardStructName, boolean noexportheaders) throws FileNotFoundException\n\t{\n\t\tPrismNative.setExportModelPrecision(precision);\n\t\tint res = PM_ExportVector(vector.ptr(), name, vars.array(), vars.n(), odd.ptr(), exportType, filename, rewardStructName, noexportheaders);\n\t\tif (res == -1) {\n\t\t\tthrow new FileNotFoundException();\n\t\t}\n\t}\n\t\n\t// export matrix\n\tprivate static native int PM_ExportMatrix(long matrix, String name, long rv, int nrv, long cv, int ncv, long odd, int exportType, String filename, String rewardStructName, boolean noexportheaders);\n\tpublic static void ExportMatrix(JDDNode matrix, String name, JDDVars rows, JDDVars cols, ODDNode odd, int exportType, String filename, int precision, String rewardStructName, boolean noexportheaders) throws FileNotFoundException\n\t{\n\t\tPrismNative.setExportModelPrecision(precision);\n\t\tint res = PM_ExportMatrix(matrix.ptr(), name, rows.array(), rows.n(), cols.array(), cols.n(), odd.ptr(), exportType, filename, rewardStructName, noexportheaders);\n\t\tif (res == -1) {\n\t\t\tthrow new FileNotFoundException();\n\t\t}\n\t}\n\t\n\t// export labels\n\tprivate static native int PM_ExportLabels(long labels[], String labelNames[], String name, long vars, int nv, long odd, int exportType, String filename);\n\tpublic static void ExportLabels(JDDNode labels[], String labelNames[], String name, JDDVars vars, ODDNode odd, int exportType, String filename) throws FileNotFoundException\n\t{\n\t\tlong ptrs[] = new long[labels.length];\n\t\tfor (int i = 0; i < labels.length; i++)\n\t\t\tptrs[i] = labels[i].ptr();\n\t\tint res = PM_ExportLabels(ptrs, labelNames, name, vars.array(), vars.n(), odd.ptr(), exportType, filename);\n\t\tif (res == -1) {\n\t\t\tthrow new FileNotFoundException();\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// generic iterative solution methods\n\t//------------------------------------------------------------------------------\n\n\t// power method\n\tprivate static native long PM_Power(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose);\n\tpublic static JDDNode Power(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_Power(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// power method (interval variant)\n\tprivate static native long PM_PowerInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, int flags);\n\tpublic static JDDNode PowerInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, int flags) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_PowerInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// jor method\n\tprivate static native long PM_JOR(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose, double omega);\n\tpublic static JDDNode JOR(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose, double omega) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_JOR(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose, omega);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t// jor method (interval variant)\n\tprivate static native long PM_JORInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, double omega, int flags);\n\tpublic static JDDNode JORInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, double omega, int flags) throws PrismException\n\t{\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PM_JORInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, omega, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn JDD.ptrToNode(ptr);\n\t}\n\n\t//------------------------------------------------------------------------------\n}\n"
  },
  {
    "path": "prism/src/mtbdd/package-info.java",
    "content": "/**\n * Access to the \"MTBDD\" engine: fully symbolic implementations of model checking algorithms.\n */\npackage mtbdd;\n"
  },
  {
    "path": "prism/src/nsis_script.nsi",
    "content": ";==============================================================================\r\n\r\n; You should always call makensis in the following way:\r\n;\r\n; > makensis /NOCD /DPRISM_NAME=\"PRISM X.y\" /DPRISM_BUILD=\"prism-X.y\"\r\n;   /DPRISM_BINDISTSUFFIX=\"winXX\" /DPRISM_BINDISTARCH=\"x86\" /DPRISM_DIR=\"\" installer_script.nsi\r\n;\r\n; where:\r\n; * PRISM X.y\" is the name of the program displayed to the user\r\n; * prism-3.0 is the4 name of the build (no spaces)\r\n; * winXX is win32 or win6\r\n; The PRISM_DIR variable should be set to the top-level PRISM dir (usually ..)\r\n\r\n# --------------------------------------------------------------------------- #\r\n\r\n;Page license \t; Uncomment if you want the license page to be shown. \r\nPage components\t; Choice in components (shortcuts mostly).\r\nPage directory\t; Prompts for directory of installation.\r\nPage instfiles\t; Copies the files.\r\n\r\nUninstPage uninstConfirm\r\nUninstPage instfiles\r\n\r\n# --------------------------------------------------------------------------- #\r\n\r\nName            \"${PRISM_NAME}\"\r\nOutFile         \"..\\${PRISM_BUILD}-${PRISM_BINDISTSUFFIX}-${PRISM_BINDISTARCH}-installer.exe\"\r\n\r\nCRCCheck        on\r\n\r\nLicenseText     \"For your information:\" \"Next >\"\r\nLicenseData     \"${PRISM_DIR}\\COPYING.txt\"\r\n\r\nInstallDir      \"$PROGRAMFILES64\\${PRISM_BUILD}\"\r\n\r\nSubCaption\t\t0 \": Licensing Information\"\r\n\r\nDirText         \"Please select an installation folder for ${PRISM_NAME}.\"\r\n\r\nUninstallText   \"This will uninstall ${PRISM_NAME}, including any examples.\"\r\n\r\nComponentText \t\"Please select the components you wish to install.\"\r\n\t\t\t\r\n# --------------------------------------------------------------------------- #\r\n\r\nSection \"\"\r\n    SetOutPath \"$INSTDIR\"\r\n\r\n    ;WriteRegStr HKEY_LOCAL_MACHINE \"SOFTWARE\\University of Oxford\\${PRISM_BUILD}\" \"\" \"$INSTDIR\"\r\n    ;WriteRegStr HKEY_LOCAL_MACHINE \"Software\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\${PRISM_BUILD}\" \"DisplayName\" \"${PRISM_NAME}(remove only)\"\r\n    ;WriteRegStr HKEY_LOCAL_MACHINE \"Software\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\${PRISM_BUILD}\" \"UninstallString\" '\"$INSTDIR\\uninstall.exe\"'\r\n\r\n    WriteUninstaller \"$INSTDIR\\uninstall.exe\"\r\n\r\nSectionEnd\r\n\r\nSection \"${PRISM_NAME}\"\r\n\tSectionIn RO ; RO=compulsory\r\n\t\r\n    SetOutPath \"$INSTDIR\\etc\"\r\n    File /r etc\\*.*\r\n    \r\n    SetOutPath \"$INSTDIR\\lib\"\r\n    File /r lib\\*.*\r\n    \r\n    SetOutPath \"$INSTDIR\"\r\n    File \"..\\CHANGELOG.txt\"\r\n    File \"..\\COPYING.txt\"\r\n    FILE \"install.sh\"\r\n    FILE \"..\\README.md\"\r\n\r\n    SetOutPath \"$INSTDIR\\bin\"\r\n    File bin\\prism.bat\r\n    File bin\\xprism.bat\r\n    \r\n    SetOutPath \"$INSTDIR\\prism-examples\"\r\n    File /r ..\\prism-examples\\*.*\r\n\r\n    SetOutPath \"$INSTDIR\\manual\"\r\n    File /r ..\\manual\\*.*\r\nSectionEnd\r\n\r\nSection \"Desktop shortcut\"\r\n\t\r\n\tSetOutPath \"$INSTDIR\\bin\"\r\n\t\r\n\tCreateShortCut  \"$DESKTOP\\${PRISM_NAME}.lnk\" \\\r\n                    \"$INSTDIR\\bin\\xprism.bat\" \"\"                            \\\r\n                    \"$INSTDIR\\etc\\icons\\prism.ico\" 0                                \\\r\n                    SW_SHOWMINIMIZED \"\" \"${PRISM_NAME} (GUI mode)\"\r\n                    \r\nSectionEnd\r\n\r\nSection \"Start menu shortcuts\"\r\n                    \r\n    CreateDirectory \"$SMPROGRAMS\\${PRISM_NAME}\"\r\n\r\n    SetOutPath \"$INSTDIR\\bin\"\r\n\r\n    CreateShortCut  \"$SMPROGRAMS\\${PRISM_NAME}\\PRISM (GUI).lnk\" \\\r\n                    \"$INSTDIR\\bin\\xprism.bat\" \"\"                            \\\r\n                    \"$INSTDIR\\etc\\icons\\prism.ico\" 0                                \\\r\n                    SW_SHOWMINIMIZED \"\" \"Runs the PRISM GUI\"\r\n\r\n    CreateShortCut  \"$SMPROGRAMS\\${PRISM_NAME}\\PRISM (console).lnk\" \\\r\n                    \"$SYSDIR\\cmd.exe\" \"\"                            \\\r\n                    \"$SYSDIR\\cmd.exe\" 0                             \\\r\n                    SW_SHOWNORMAL \"\" \"Opens a console for command-line usage of PRISM\"\r\n\r\n    SetOutPath \"$INSTDIR\\doc\"\r\n\r\n    CreateShortCut  \"$SMPROGRAMS\\${PRISM_NAME}\\Manual (local).lnk\" \\\r\n                    \"$INSTDIR\\manual\\index.html\" \"\"                            \\\r\n                    \"\" 0                             \\\r\n                    SW_SHOWNORMAL \"\" \"The PRISM manual (local copy)\"\r\n\r\n    CreateShortCut  \"$SMPROGRAMS\\${PRISM_NAME}\\Manual (online).lnk\" \\\r\n                    \"http://www.prismmodelchecker.org/manual/\" \"\"                            \\\r\n                    \"\" \"\"                             \\\r\n                    SW_SHOWNORMAL \"\" \"The PRISM manual (online version)\"\r\n\r\n    CreateShortCut  \"$SMPROGRAMS\\${PRISM_NAME}\\Web site.lnk\" \\\r\n                    \"http://www.prismmodelchecker.org/\" \"\"                            \\\r\n                    \"\" 0                             \\\r\n                    SW_SHOWNORMAL \"\" \"The PRISM web site\"\r\n\r\n    SetOutPath \"$INSTDIR\"\r\n\r\n    CreateShortCut  \"$SMPROGRAMS\\${PRISM_NAME}\\Uninstall.lnk\" \\\r\n                    \"$INSTDIR\\uninstall.exe\" \"\"                             \\\r\n                    \"$INSTDIR\\uninstall.exe\" 0                              \\\r\n                    SW_SHOWNORMAL \"\" \"Uninstalls ${PRISM_NAME} from your system\"\r\n    SectionEnd\r\n\r\nSection Uninstall\r\n\r\n    RMDir /r \"$INSTDIR\\bin\\\"\r\n    RMDIR /r \"$INSTDIR\\etc\\\"\r\n    RMDIR /r \"$INSTDIR\\lib\\\"\r\n\r\n    Delete \"$INSTDIR\\CHANGELOG.txt\"\r\n    Delete \"$INSTDIR\\COPYING.txt\"\r\n    Delete \"$INSTDIR\\install.sh\"\r\n    Delete \"$INSTDIR\\README.md\"\r\n\r\n    RMDir /r \"$INSTDIR\\prism-examples\\\"\r\n\r\n    RMDIR /r \"$INSTDIR\\doc\\\"\r\n\r\n    RMDir /r \"$SMPROGRAMS\\${PRISM_NAME}\"\r\n\r\n    Delete \"$DESKTOP\\${PRISM_NAME}.lnk\"\r\n\r\n    ;DeleteRegKey HKEY_LOCAL_MACHINE \"SOFTWARE\\Microsoft\\Windows\\CurrentVersion\\Uninstall\\${PRISM_BUILD}\"\r\n\r\n    Delete $INSTDIR\\uninstall.exe\r\n\r\n    RMDir \"$INSTDIR\"\r\n\r\nSectionEnd\r\n\r\n\r\n\r\n\r\n"
  },
  {
    "path": "prism/src/odd/ODDNode.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage odd;\n\npublic class ODDNode\n{\n\tprivate long ptr;\n\t\n\tpublic ODDNode(long p)\n\t{\n\t\tptr = p;\n\t}\n\t\n\tpublic ODDNode(ODDNode odd)\n\t{\n\t\tptr = odd.ptr;\n\t}\n\t\n\tpublic long ptr()\n\t{\n\t\treturn ptr;\n\t}\n\n\tpublic long getTOff()\n\t{\t\n\t\treturn ODDUtils.ODD_GetTOff(ptr);\n\t}\n\n\tpublic long getEOff()\n\t{\t\n\t\treturn ODDUtils.ODD_GetEOff(ptr);\n\t}\n\n\t/**\n\t * Returns the number of states for this ODD node.\n\t * Throws an arithmetic exception if the number of states\n\t * does not fit in a Java long (should not occur as that is\n\t * caught during ODD construction).\n\t */\n\tpublic long getNumStates()\n\t{\n\t\treturn Math.addExact(getTOff(), getEOff());\n\t}\n\n\tpublic ODDNode getThen()\n\t{\n\t\treturn new ODDNode(ODDUtils.ODD_GetThen(ptr));\n\t}\n\t\n\tpublic ODDNode getElse()\n\t{\n\t\treturn new ODDNode(ODDUtils.ODD_GetElse(ptr));\n\t}\n\n\tpublic boolean equals(ODDNode odd)\n\t{\n\t\treturn ptr == odd.ptr;\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"\" + ptr;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/odd/ODDUtils.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"odd.h\"\n#include \"ODDUtils.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n// build odd\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_odd_ODDUtils_ODD_1BuildODD\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer dd,\t// trans matrix\njlong __jlongpointer vars,\t// row vars\njint num_vars\n)\n{\n\treturn ptr_to_jlong(\n\t\tbuild_odd(\n\t\t\tddman,\n\t\t\tjlong_to_DdNode(dd),\n\t\t\tjlong_to_DdNode_array(vars), num_vars\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n// clear odd\n//------------------------------------------------------------------------------\nJNIEXPORT void JNICALL Java_odd_ODDUtils_ODD_1ClearODD\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer odd)\n{\n\tclear_odd(jlong_to_ODDNode(odd));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_odd_ODDUtils_ODD_1GetNumODDNodes\n(\nJNIEnv *env,\njclass cls\n)\n{\n\treturn get_num_odd_nodes();\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_odd_ODDUtils_ODD_1GetIndexOfFirstFromDD\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer dd,\njlong __jlongpointer odd,\njlong __jlongpointer vars,\njint num_vars\n)\n{\n\treturn get_index_of_first_from_bdd(\n\t\tddman,\n\t\tjlong_to_DdNode(dd),\n\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\tjlong_to_ODDNode(odd)\n\t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer  JNICALL Java_odd_ODDUtils_ODD_1SingleIndexToDD\n(\nJNIEnv *env,\njclass cls,\njint i,\njlong __jlongpointer odd,\njlong __jlongpointer vars,\njint num_vars\n)\n{\n\treturn ptr_to_jlong(\n\t\tsingle_index_to_bdd(\n\t\t\tddman,\n\t\t\ti,\n\t\t\tjlong_to_DdNode_array(vars), num_vars,\n\t\t\tjlong_to_ODDNode(odd)\n\t\t)\n\t);\n}\n\n//------------------------------------------------------------------------------\n// ODDNode methods\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_odd_ODDUtils_ODD_1GetTOff(JNIEnv *env, jclass cls, jlong __jlongpointer odd)\n{\n\treturn (jlong_to_ODDNode(odd))->toff;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_odd_ODDUtils_ODD_1GetEOff(JNIEnv *env, jclass cls, jlong __jlongpointer odd)\n{\n\treturn (jlong_to_ODDNode(odd))->eoff;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_odd_ODDUtils_ODD_1GetThen(JNIEnv *env, jclass cls, jlong __jlongpointer odd)\n{\n\treturn ptr_to_jlong((jlong_to_ODDNode(odd))->t);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_odd_ODDUtils_ODD_1GetElse(JNIEnv *env, jclass cls, jlong __jlongpointer odd)\n{\n\treturn ptr_to_jlong((jlong_to_ODDNode(odd))->e);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/odd/ODDUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage odd;\n\nimport jdd.*;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\npublic class ODDUtils\n{\n\t//------------------------------------------------------------------------------\n\t// load jni stuff from shared library\n\t//------------------------------------------------------------------------------\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// JNI wrappers\n\t//------------------------------------------------------------------------------\n\t\n\tprivate static native long ODD_BuildODD(long dd, long vars, int num_vars);\n\t/**\n\t *  Build an ODD.\n\t *  If the ODD could not be constructed, returns {@code null}.\n\t */\n\tpublic static ODDNode BuildODD(JDDNode dd, JDDVars vars) throws PrismException\n\t{\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\t// ODD construction requires the JDDVars to be in ascending order\n\t\t\tjdd.SanityJDD.checkVarsAreSorted(vars);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(dd, vars);\n\t\t}\n\n\t\tlong res = ODD_BuildODD(dd.ptr(), vars.array(), vars.n());\n\t\tif (res == 0) {\n\t\t\t// we could not build the ODD (i.e., we had more than Long.MAX_LONG states\n\t\t\t// we return null and will have to live with the limited functionality\n\t\t\treturn null;\n\t\t}\n\t\treturn new ODDNode(res);\n\t}\n\n\tprivate static native void ODD_ClearODD(long ptr);\n\t/**\n\t * Clear the ODD with root node {@code odd}.\n\t *<br>\n\t * Note: {@code odd} has to be an ODDNode previously returned by a\n\t * call to the {@code BuildODD} method. Any other odd will\n\t * lead to unexpected behaviour, possibly including crash, etc.\n\t */\n\tpublic static void ClearODD(ODDNode odd)\n\t{\n\t\tODD_ClearODD(odd.ptr());\n\t}\n\n\tprivate static native int ODD_GetNumODDNodes();\n\t/**\n\t *  Get the number of nodes in the ODD just built.\n\t */\n\tpublic static int GetNumODDNodes()\n\t{\n\t\treturn ODD_GetNumODDNodes();\n\t}\n\t\n\tpublic static native int ODD_GetIndexOfFirstFromDD(long dd, long odd, long vars, int num_vars);\n\t/**\n\t *  Get the index of the first non-zero element of a 0-1 MTBDD, according to an ODD.\n\t */\n\tpublic static int GetIndexOfFirstFromDD(JDDNode dd, ODDNode odd, JDDVars vars)\n\t{\n\t\treturn ODD_GetIndexOfFirstFromDD(dd.ptr(), odd.ptr(), vars.array(), vars.n());\n\t}\n\t\n\tpublic static native long ODD_SingleIndexToDD(int i, long odd, long vars, int num_vars);\n\t/**\n\t *  Convert a state index to a 0-1 MTBDD representing it, according to an ODD.\n\t */\n\tpublic static JDDNode SingleIndexToDD(int i, ODDNode odd, JDDVars vars)\n\t{\n\t\treturn JDD.ptrToNode(ODD_SingleIndexToDD(i, odd.ptr(), vars.array(), vars.n()));\n\t}\n\n\t/**\n\t * Checks that the given ODD has indices that can be represented by\n\t * Java integers. If that is not the case, or the ODD is {@code null},\n\t * a PrismNotSupportedException is thrown.\n\t * @param odd the ODD (may be {@code null})\n\t * @param msg Initial part of error message, will be extended with\n\t *        \" with more than X states, have Y states\"\n\t */\n\tpublic static void checkInt(ODDNode odd, String msg) throws PrismNotSupportedException\n\t{\n\t\tif (odd != null) {\n\t\t\ttry {\n\t\t\t\tlong numStates = odd.getNumStates();\n\t\t\t\tif (numStates > Integer.MAX_VALUE) {\n\t\t\t\t\t// number of states fit in long, but not in int\n\t\t\t\t\tthrow new PrismNotSupportedException(msg + \" with more than \" + Integer.MAX_VALUE + \" states, have \" + numStates + \" states\");\n\t\t\t\t} else {\n\t\t\t\t\t// everything is fine\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t} catch (ArithmeticException e) {\n\t\t\t\t// number of states does not fit into long, ignore here, handled below\n\t\t\t}\n\t\t}\n\n\t\t// we either have no ODD or eoff + toff does not fit into long\n\t\tthrow new PrismNotSupportedException(msg + \" with more than \" + Integer.MAX_VALUE + \" states, have at least \" + Long.MAX_VALUE + \" states\");\n\t}\n\n\t/**\n\t * Returns true if the given ODD has indices that can be represented by\n\t * Java integers. If the odd is {@code null}, returns false as well.\n\t * @param odd the ODD (may be {@code null})\n\t */\n\tpublic static boolean hasIntValue(ODDNode odd)\n\t{\n\t\tif (odd == null)\n\t\t\treturn false;\n\n\t\ttry {\n\t\t\tlong numStates = odd.getNumStates();\n\t\t\tif (numStates <= Integer.MAX_VALUE) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t} catch (ArithmeticException e) {\n\t\t\t// number of states does not fit into long, ignore here, handled below\n\t\t}\n\t\treturn false;\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// ODDNode methods\n\t//------------------------------------------------------------------------------\n\n\tpublic static native long ODD_GetTOff(long odd);\n\tpublic static native long ODD_GetEOff(long odd);\n\tpublic static native long ODD_GetThen(long odd);\n\tpublic static native long ODD_GetElse(long odd);\n\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/odd/odd.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"odd.h\"\n\n// static variables\nstatic int num_odd_nodes = 0;\n\n// local prototypes\nstatic ODDNode *build_odd_rec(DdManager *ddman, DdNode *dd, int level, DdNode **vars, int num_vars, ODDNode **tables);\nstatic int64_t add_offsets(DdManager *ddman, ODDNode *dd, int level, int num_vars);\nstatic DdNode *single_index_to_bdd_rec(DdManager *ddman, int i, DdNode **vars, int num_vars, int level, ODDNode *odd, long o);\n\n//------------------------------------------------------------------------------\n\nODDNode *build_odd(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars)\n{\n\tint i;\n\tODDNode **tables;\n\tODDNode *res;\n\n\t// build tables to store odd nodes during construction\n\ttables = new ODDNode*[num_vars+1];\n\tfor (i = 0; i < num_vars+1; i++) {\n\t\ttables[i] = NULL;\n\t}\n\n\t// reset node counter\n\tnum_odd_nodes = 0;\n\n\t// call recursive bit\n\tres = build_odd_rec(ddman, dd, 0, vars, num_vars, tables);\n\n\t// At this point, all the allocated ODDNodes for this ODD are\n\t// chained by linked lists (ODD->next), one for each non-empty tables[i].\n\t// To facilitate deallocation later on, we chain all these\n\t// individual linked lists together.\n\t// By construction, the root node (res) is the only node in\n\t// the top-most, non-empty table and is thus at the\n\t// start of the resulting chain.\n\n\t// The current end of the linked list\n\tODDNode *last = NULL;\n\tfor (i = 0; i < num_vars+1; i++) {\n\t\tif (tables[i] != NULL) {\n\t\t\t// non-empty tables slot\n\t\t\tif (last != NULL) {\n\t\t\t\t// chain the first node in this tables slot to\n\t\t\t\t// the last one above\n\t\t\t\tlast->next = tables[i];\n\t\t\t}\n\t\t\t// search for last node in this tables slot\n\t\t\tlast = tables[i];\n\t\t\twhile (last->next != NULL) {\n\t\t\t\tlast = last->next;\n\t\t\t}\n\t\t}\n\t}\n\n\t// add offsets to odd\n\tif (add_offsets(ddman, res, 0, num_vars) < 0) {\n\t\t// negative value indicates that there was an arithmetic overflow\n\t\t// cleanup and return 0\n\t\tclear_odd(res);\n\t\tres = 0;\n\t}\n\n\t// free memory\n\tdelete tables;\n\n\treturn res;\n}\n\n//------------------------------------------------------------------------------\n\nstatic ODDNode *build_odd_rec(DdManager *ddman, DdNode *dd, int level, DdNode **vars, int num_vars, ODDNode **tables)\n{\n\tODDNode *ptr;\n\t\n\t// see if we already have odd in the tables\n\tptr = tables[level];\n\twhile (ptr != NULL) {\n\t\tif (ptr->dd == dd) break;\n\t\tptr = ptr->next;\n\t}\n\t\n\t// if not, add it\n\tif (ptr == NULL) {\n\t\tnum_odd_nodes++;\n\t\tptr = new ODDNode();\n\t\tptr->dd = dd;\t\t\n\t\tptr->next = tables[level];\n\t\ttables[level] = ptr;\n\t\t// and recurse...\n\t\t\n// should be able to add this because will never traverse a path to the\n// zeros temrinal - always look at states that exist\n// can we assume this?\n//\tif (dd == Cudd_ReadZero(ddman)) return;\n\n\t\tif (level == num_vars) {\n\t\t\tptr->e = NULL;\n\t\t\tptr->t = NULL;\n\t\t}\n\t\telse if (Cudd_NodeReadIndex(vars[level]) < Cudd_NodeReadIndex(dd)) {\n\t\t\tptr->e = build_odd_rec(ddman, dd, level+1, vars, num_vars, tables);\n\t\t\tptr->t = ptr->e;\n\t\t}\n\t\telse {\n\t\t\tptr->e = build_odd_rec(ddman, Cudd_E(dd), level+1, vars, num_vars, tables);\n\t\t\tptr->t = build_odd_rec(ddman, Cudd_T(dd), level+1, vars, num_vars, tables);\n\t\t}\n\t\tptr->eoff = -1;\n\t\tptr->toff = -1;\n\t}\n\t\n\treturn ptr;\n}\n\n//------------------------------------------------------------------------------\n\n//\n// Compute the actual eoff and toff values.\n// Returns eoff + toff for this odd node or -1 if there is an arithmetic overflow\n// (can not store eoff+toff in an int64_t)\nint64_t add_offsets(DdManager *ddman, ODDNode *odd, int level, int num_vars)\n{\n\tif ((odd->eoff == -1) || (odd->toff == -1)) {\n\t\t// this node has not yet been seen\n\t\tif (level == num_vars) {\n\t\t\tif (odd->dd == Cudd_ReadZero(ddman)) {\n\t\t\t\todd->eoff = 0;\n\t\t\t\todd->toff = 0;\n\t\t\t}\n\t\t\telse {\n\t\t\t\todd->eoff = 0;\n\t\t\t\todd->toff = 1;\n\t\t\t}\n\t\t}\n\t\telse {\n\t\t\todd->eoff = add_offsets(ddman, odd->e, level+1, num_vars);\n\t\t\tif (odd->eoff < 0) return -1;\n\t\t\todd->toff = add_offsets(ddman, odd->t, level+1, num_vars);\n\t\t\tif (odd->toff < 0) return -1;\n\t\t}\n\n\t\t// overflow check for sum\n\t\t// do unsigned addition, guaranteed to not overflow\n\t\t// as eoff and toff are signed and positive, cast sum to signed and\n\t\t// check that it is larger than one of the summands\n\t\tint64_t tmp = (int64_t)((uint64_t)odd->eoff + (uint64_t)odd->toff);\n\t\tif (tmp < odd->eoff) {\n\t\t\t// we have an overflow\n\t\t\treturn -1;\n\t\t}\n\t}\n\n\treturn odd->eoff + odd->toff;\n}\n\n//------------------------------------------------------------------------------\n\nvoid clear_odd(ODDNode *odd) {\n\t// We assume that odd is the root node of an ODD, i.e.,\n\t// was returned previously from a build_odd call.\n\t// It is thus the first element of the linked list\n\t// (with ODDNode->next pointers) that references all the\n\t// allocated ODDNodes of this ODD and we can simply\n\t// delete each ODDNode in turn.\n\twhile (odd != NULL) {\n\t\tODDNode *next = odd->next;\n\t\tdelete odd;\n\t\todd = next;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\n// Get the index (according to an ODD) of the first non-zero enetry of a BDD\n\nint get_index_of_first_from_bdd(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\tDdNode *ptr, *ptr_next;;\n\tODDNode *odd_ptr;\n\tint i, index;\n\t\n\t// Go down dd along first non-zero path\n\tindex = 0;\n\tptr = dd;\n\todd_ptr = odd;\n\tfor (i = 0; i < num_vars; i++) {\n\t\tptr_next = (Cudd_NodeReadIndex(ptr) > Cudd_NodeReadIndex(vars[i])) ? ptr : Cudd_E(ptr);\n\t\tif (ptr_next != Cudd_ReadZero(ddman)) {\n\t\t\todd_ptr = odd_ptr->e;\n\t\t}\n\t\telse {\n\t\t\tptr_next = (Cudd_NodeReadIndex(ptr) > Cudd_NodeReadIndex(vars[i])) ? ptr : Cudd_T(ptr);\n\t\t\tindex += odd_ptr->eoff;\n\t\t\todd_ptr = odd_ptr->t;\n\t\t}\n\t\tptr = ptr_next;\n\t}\n\n\treturn index;\n}\n\n// Get a BDD for a single state given its index and the accompanying ODD.\n\nEXPORT DdNode *single_index_to_bdd(DdManager *ddman, int i, DdNode **vars, int num_vars, ODDNode *odd)\n{\n\treturn single_index_to_bdd_rec(ddman, i, vars, num_vars, 0, odd, 0);\n}\n\nDdNode *single_index_to_bdd_rec(DdManager *ddman, int i, DdNode **vars, int num_vars, int level, ODDNode *odd, long o)\n{\n\tDdNode *dd;\n\n\tif (level == num_vars) {\n\t\treturn DD_Constant(ddman, 1);\n\t}\n\telse {\n\t\tif (odd->eoff > i - o) {\n\t\t\tdd = single_index_to_bdd_rec(ddman, i, vars, num_vars, level+1, odd->e, o);\n\t\t\tCudd_Ref(vars[level]);\n\t\t\treturn DD_And(ddman, DD_Not(ddman, vars[level]), dd);\n\t\t}\n\t\telse {\n\t\t\tdd = single_index_to_bdd_rec(ddman, i, vars, num_vars, level+1, odd->t, o+odd->eoff);\n\t\t\tCudd_Ref(vars[level]);\n\t\t\treturn DD_And(ddman, vars[level], dd);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nint get_num_odd_nodes()\n{\n\treturn num_odd_nodes;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/odd/package-info.java",
    "content": "/**\n * Access to ODDs (offset-labelled BDDs), used to facilitate indexing of states between BDDs and explicit-state data structures.\n */\npackage odd;\n"
  },
  {
    "path": "prism/src/overview.html",
    "content": "<html><head></head><body>\nThis is the documentation for <a href=\"http://www.prismmodelchecker.org/\">PRISM<a>'s Java code: for the discrete-event simulation engine, see {@link simulator.SimulatorEngine}; for the explicit-state probabilistic model checking and abstraction-refinement, see package {@link explicit}.\n</body></html>\n"
  },
  {
    "path": "prism/src/param/BigRational.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.math.BigInteger;\n\nimport prism.PrismLangException;\n\n/**\n * Provides a class to store big rational numbers.\n * Numerator and denominator of a number stored using this class are not\n * necessarily coprime. However, cancellation is applied by default.\n * The special values infinity (INF), minus infinity (MINF) and not a number\n * (NAN)are provided. For them, the usual rules apply (INF * INF = INF,\n * MINF&INF=MINF, etc.), with the exception that INF+MINF=0, INF-INF=0, etc\n * rather than NAN.\n *\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\npublic final class BigRational extends Number implements Comparable<BigRational>\n{\n\t/** Serial version for serialisation */\n\tprivate static final long serialVersionUID = 8273185089413305187L;\n\n\t/** the BigInteger \"-1\" */\n\tprivate final static BigInteger BMONE = BigInteger.ONE.negate();\n\t/** the BigInteger \"2\" */\n\tprivate final static BigInteger BITWO = BigInteger.TWO;\n\t/** the BigInteger \"10\" */\n\tprivate final static BigInteger BITEN = BigInteger.TEN;\n\n\t/** the BigRational \"1\" */\n\tpublic final static BigRational ONE = new BigRational(BigInteger.ONE);\n\t/** the BigRational \"2\" */\n\tpublic final static BigRational TWO = new BigRational(BigInteger.valueOf(2));\n\t/** the BigRational \"-1\" */\n\tpublic final static BigRational MONE = new BigRational(BigInteger.ONE).negate();\n\t/** the BigRational \"0\" */\n\tpublic final static BigRational ZERO = new BigRational(BigInteger.ZERO);\n\t/** the BigRational \"1/2\" */\n\tpublic final static BigRational HALF = ONE.divide(TWO);\n\t/** the BigRational \"infinity\" */\n\tpublic final static BigRational INF = new BigRational(BigInteger.ONE, BigInteger.ZERO);\n\t/** the BigRational \"-infinity\" */\n\tpublic final static BigRational MINF = new BigRational(BMONE, BigInteger.ZERO);\n\t/** the BigRational \"not a number\" */\n\tpublic final static BigRational NAN = new BigRational(BigInteger.ZERO, BigInteger.ZERO);\n\n\t/** numerator */\n\tprivate BigInteger num;\n\t/** denominator */\n\tprivate BigInteger den;\n\n\t// constructors\n\n\t/**\n\t * Creates a new BigRational with value 0.\n\t */\n\tpublic BigRational()\n\t{\n\t\tthis.num = BigInteger.ZERO;\n\t\tthis.den = BigInteger.ONE;\n\t}\n\n\t/**\n\t * Creates a new BigRational with value {@code num}.\n\t *\n\t * @param num value of new rational as an integer value\n\t */\n\tpublic BigRational(BigInteger num)\n\t{\n\t\tthis.num = num;\n\t\tthis.den = BigInteger.ONE;\n\t}\n\n\t/**\n\t * Creates a new BigRational with value {@code num} / {@code den}.\n\t * Cancellation of {@code num} and {@code den} is applied.\n\t *\n\t * @param num numerator of this BigRational\n\t * @param den denominator of this BigRational\n\t */\n\tpublic BigRational(BigInteger num, BigInteger den)\n\t{\n\t\tthis(num, den, true);\n\t}\n\n\t/**\n\t * Creates a new BigRational with value {@code num} / {@code den}.\n\t * Whether cancellation between {@code num} and {@code den} is applied depends\n\t * on {@code cancel}.\n\t *\n\t * @param num numerator of this BigRational\n\t * @param den denominator of this BigRational\n\t * @param cancel true to ensure resulting BigRational is coprime\n\t */\n\tpublic BigRational(BigInteger num, BigInteger den, boolean cancel)\n\t{\n\t\tif (den.equals(BigInteger.ZERO)) {\n\t\t\tint cmp = num.compareTo(BigInteger.ZERO);\n\t\t\tswitch (cmp) {\n\t\t\tcase -1:\n\t\t\t\tnum = BMONE;\n\t\t\t\tbreak;\n\t\t\tcase 1:\n\t\t\t\tnum = BigInteger.ONE;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\tif (cancel) {\n\t\t\tcanceled(num, den);\n\t\t} else {\n\t\t\tthis.num = num;\n\t\t\tthis.den = den;\n\t\t}\n\t}\n\n\tprotected void canceled(BigInteger num, BigInteger den)\n\t{\n\t\tif (num.equals(BigInteger.ZERO)) {\n\t\t\tif (!den.equals(BigInteger.ZERO)) {\n\t\t\t\t// not NaN (= 0/0), so this is a real zero:\n\t\t\t\t// normalise by setting denominator to 1\n\t\t\t\tnum = BigInteger.ZERO;\n\t\t\t\tden = BigInteger.ONE;\n\t\t\t}\n\t\t} else {\n\t\t\tBigInteger gcd = num.gcd(den);\n\t\t\tnum = num.divide(gcd);\n\t\t\tden = den.divide(gcd);\n\t\t\tif (den.signum() == -1) {\n\t\t\t\tnum = num.negate();\n\t\t\t\tden = den.negate();\n\t\t\t}\n\t\t}\n\t\tthis.num = num;\n\t\tthis.den = den;\n\t}\n\n\t/**\n\t * Creates a new BigRational with value {@code num} / {@code den}.\n\t * Cancellation of {@code num} and {@code den} is applied.\n\t *\n\t * @param num numerator of this BigRational\n\t * @param den denominator of this BigRational\n\t */\n\tpublic BigRational(long num, long den)\n\t{\n\t\tthis(BigInteger.valueOf(num), BigInteger.valueOf(den));\n\t}\n\n\t/**\n\t * Creates a new BigRational with value {@code num}.\n\t *\n\t * @param num value of new rational as an integer value\n\t */\n\tpublic BigRational(long num)\n\t{\n\t\tthis(num, 1);\n\t}\n\n\t/**\n\t * Creates a new BigRational by converting {@code value} to a fraction.\n\t * The algorithm uses iterated multiplication with 2 to determine the exponent of the argument.\n\t *\n\t * @param num value of new rational as an integer value\n\t */\n\tpublic  BigRational(double value)\n\t{\n\t\tif (java.lang.Double.isNaN(value)) {\n\t\t\tthis.num = BigInteger.ZERO;\n\t\t\tthis.den = BigInteger.ZERO;\n\t\t}\n\t\tif (value == java.lang.Double.POSITIVE_INFINITY) {\n\t\t\tthis.num = BigInteger.ONE;\n\t\t\tthis.den = BigInteger.ZERO;\n\t\t}\n\t\tif (value == java.lang.Double.NEGATIVE_INFINITY) {\n\t\t\tthis.num = BMONE;\n\t\t\tthis.den = BigInteger.ZERO;\n\t\t}\n\t\t// Test whether value must be an integer\n\t\tif (value <= -0x1.0P52 || value >= 0x1.0P52) {\n\t\t\t// Determine smallest exponent such that value = long_value * 2^exp\n\t\t\tint exp = 0;\n\t\t\t// Terminate as soon as value is a long\n\t\t\twhile ((long) value != value) {\n\t\t\t\tvalue /= 2;\n\t\t\t\texp += 1;\n\t\t\t}\n\t\t\t// No need to cancel as denumerator is one\n\t\t\tthis.num = BigInteger.valueOf((long) value).shiftLeft(exp);\n\t\t\tthis.den = BigInteger.ONE;\n\t\t} else {\n\t\t\t// Determine smallest exponent such that value = long_value / 2^exp\n\t\t\tint exp = 0;\n\t\t\t// Terminate as soon as value is an integer\n\t\t\twhile ((long) value != value) {\n\t\t\t\tvalue *= 2;\n\t\t\t\texp += 1;\n\t\t\t}\n\t\t\t// No need to cancel as exp is the smallest exponent\n\t\t\tthis.num = BigInteger.valueOf((long) value);\n\t\t\tthis.den = BigInteger.ONE.shiftLeft(exp);\n\t\t}\n\t}\n\n\t/**\n\t * Creates a new BigRational from string {@code string}.\n\t * Formats supported are num / den where num and den are integers,\n\t * and scientific notation.\n\t *\n\t * @param string string to create BigRational from\n\t */\n\tpublic BigRational(String string)\n\t{\n\t\tif (string.equals(\"Infinity\") || string.equals(\"+Infinity\") || string.equals(\"Inf\") || string.equals(\"+Inf\")) {\n\t\t\tthis.num = BigInteger.ONE;\n\t\t\tthis.den = BigInteger.ZERO;\n\t\t\treturn;\n\t\t} else if (string.equals(\"-Infinity\") || string.equals(\"-Inf\")) {\n\t\t\tthis.num = BigInteger.ONE.negate();\n\t\t\tthis.den = BigInteger.ZERO;\n\t\t\treturn;\n\t\t} else if (string.equals(\"NaN\")) {\n\t\t\tthis.num = BigInteger.ZERO;\n\t\t\tthis.den = BigInteger.ZERO;\n\t\t\treturn;\n\t\t}\n\t\tstring = string.trim();\n\t\tint slashIdx = string.lastIndexOf('/');\n\t\tif (slashIdx < 0) {\n\t\t\t// decimal point notation\n\t\t\tDouble.parseDouble(string); // ensures correctness of format\n\t\t\tboolean negate = false;\n\t\t\tif (string.charAt(0) == '-') {\n\t\t\t\tnegate = true;\n\t\t\t\tstring = string.substring(1);\n\t\t\t}\n\t\t\tint ePos = string.indexOf(\"e\");\n\t\t\tif (ePos < 0) {\n\t\t\t\tePos = string.indexOf(\"E\");\n\t\t\t}\n\t\t\tString coefficient = string.substring(0, ePos >= 0 ? ePos : string.length());\n\t\t\tint dotIdx = coefficient.indexOf('.');\n\t\t\tint expo = 0;\n\t\t\tString noDotCoeff;\n\t\t\tif (dotIdx >= 0) {\n\t\t\t\tnoDotCoeff = coefficient.substring(0, dotIdx);\n\t\t\t\tnoDotCoeff += coefficient.substring(dotIdx + 1);\n\t\t\t\texpo = -coefficient.substring(dotIdx + 1).length();\n\t\t\t} else {\n\t\t\t\tnoDotCoeff = coefficient;\n\t\t\t}\n\t\t\tif (ePos >= 0) {\n\t\t\t\tString eStr = string.substring(ePos + 1);\n\t\t\t\tint eInt = Integer.parseInt(eStr);\n\t\t\t\texpo += eInt;\n\t\t\t}\n\t\t\tBigInteger num = new BigInteger((negate ? \"-\" : \"\") + noDotCoeff);\n\t\t\tBigInteger den;\n\t\t\tBigInteger ten = BITEN;\n\t\t\tif (expo == 0) {\n\t\t\t\tden = BigInteger.ONE;\n\t\t\t} else if (expo > 0) {\n\t\t\t\tden = BigInteger.ONE;\n\t\t\t\tnum = num.multiply(ten.pow(expo));\n\t\t\t} else { // expo < 0\n\t\t\t\tden = ten.pow(-expo);\n\t\t\t}\n\t\t\tBigRational result = new BigRational(num, den, true);\n\t\t\tthis.num = result.num;\n\t\t\tthis.den = result.den;\n\t\t} else {\n\t\t\t// fractional\n\t\t\tif (slashIdx == 0 || slashIdx == string.length()-1) {\n\t\t\t\tthrow new NumberFormatException(\"Illegal fraction syntax\");\n\t\t\t}\n\t\t\t// because we use lastIndexOf, we obtain left-associativity,\n\t\t\t// i.e. a/b/c is interpreted as (a/b)/c\n\t\t\tBigRational num = new BigRational(string.substring(0, slashIdx));\n\t\t\tBigRational den = new BigRational(string.substring(slashIdx + 1, string.length()));\n\t\t\tBigRational r = num.divide(den);\n\t\t\tthis.num = r.num;\n\t\t\tthis.den = r.den;\n\t\t\treturn;\n\t\t}\n\t}\n\n\t/**\n\t * Construct a BigRational from the given object.\n\t * Throws an IllegalArgumentException if there is no\n\t * known conversion.\n\t */\n\tpublic static BigRational from(Object value)\n\t{\n\t\tif (value instanceof BigRational) {\n\t\t\tBigRational v = (BigRational)value;\n\t\t\treturn new BigRational(v.num, v.den);\n\t\t} else if (value instanceof BigInteger) {\n\t\t\treturn new BigRational((BigInteger) value);\n\t\t} else if (value instanceof Integer) {\n\t\t\treturn new BigRational((int) value);\n\t\t} else if (value instanceof Long) {\n\t\t\treturn new BigRational((long) value);\n\t\t} else if (value instanceof Boolean) {\n\t\t\tboolean v = (Boolean)value;\n\t\t\treturn v ? BigRational.ONE : BigRational.ZERO;\n\t\t} else if (value instanceof Double) {\n\t\t\treturn new BigRational((Double)value);\n\t\t} else if (value instanceof String) {\n\t\t\treturn new BigRational((String)value);\n\t\t}\n\t\tthrow new IllegalArgumentException(\"Can not convert from \" + value.getClass() + \" to BigRational\");\n\t}\n\n\t// helper functions\n\n\t/**\n\t * Negates this number.\n\t * Negation of INF, MINF are as usual, negation of NAN is NAN.\n\t *\n\t * @return negated BigRational\n\t */\n\tpublic BigRational negate()\n\t{\n\t\treturn new BigRational(num.negate(), den, false);\n\t}\n\n\t/**\n\t * Convert to coprime BigRational.\n\t *\n\t * @return coprime rational with the same value as this object\n\t */\n\tpublic BigRational cancel()\n\t{\n\t\treturn new BigRational(this.num, this.den, true);\n\t}\n\n\t// operations\n\n\tpublic BigRational add(BigRational other, boolean cancel)\n\t{\n\t\tif (this.isNaN() || other.isNaN()) {\n\t\t\treturn NAN;\n\t\t}\n\t\tif (this.isInf() || other.isInf()) {\n\t\t\tif (this.isMInf() || other.isMInf()) {\n\t\t\t\treturn ZERO;\n\t\t\t}\n\t\t\treturn INF;\n\t\t}\n\t\tif (this.isMInf() || other.isMInf()) {\n\t\t\treturn MINF;\n\t\t}\n\t\tBigInteger num = this.num.multiply(other.den).add(other.num.multiply(this.den));\n\t\tBigInteger den = this.den.multiply(other.den);\n\t\treturn new BigRational(num, den, cancel);\n\t}\n\n\tpublic BigRational add(BigRational other)\n\t{\n\t\treturn add(other, true);\n\t}\n\n\tpublic BigRational subtract(BigRational other)\n\t{\n\t\tif (this.isNaN() || other.isNaN()) {\n\t\t\treturn NAN;\n\t\t}\n\t\tif ((this.isInf() && other.isInf()) || (this.isMInf() && other.isMInf())) {\n\t\t\treturn ZERO;\n\t\t}\n\t\tif (this.isInf()) {\n\t\t\treturn INF;\n\t\t}\n\t\tif (this.isMInf()) {\n\t\t\treturn MINF;\n\t\t}\n\t\tif (other.isInf()) {\n\t\t\treturn INF;\n\t\t}\n\t\tif (other.isMInf()) {\n\t\t\treturn MINF;\n\t\t}\n\t\tBigInteger num = this.num.multiply(other.den).subtract(other.num.multiply(this.den));\n\t\tBigInteger den = this.den.multiply(other.den);\n\t\treturn new BigRational(num, den);\n\t}\n\n\t/**\n\t * Multiply this BigRational with {@code other}.\n\t *\n\t * @param other BigRational to multiply with\n\t * @return result of the multiplication\n\t */\n\tpublic BigRational multiply(BigRational other, boolean cancel)\n\t{\n\t\tif (this.isNaN() || other.isNaN()) {\n\t\t\treturn NAN;\n\t\t}\n\t\tif (this.isZero() || other.isZero()) {\n\t\t\treturn ZERO;\n\t\t}\n\t\tif (this.isInf() || other.isInf()) {\n\t\t\treturn this.signum() * other.signum() == 1 ? INF : MINF;\n\t\t}\n\t\tBigInteger num = this.num.multiply(other.num);\n\t\tBigInteger den = this.den.multiply(other.den);\n\t\treturn new BigRational(num, den, cancel);\n\t}\n\n\tpublic BigRational multiply(BigRational other)\n\t{\n\t\treturn multiply(other, true);\n\t}\n\n\t/**\n\t * Multiply this BigRational with {@code other}.\n\t *\n\t * @param other long to multiply with\n\t * @param cancel whether ensure result rational is comprime\n\t * @return result of the multiplication\n\t */\n\tpublic BigRational multiply(long other, boolean cancel)\n\t{\n\t\treturn multiply(new BigRational(other), cancel);\n\t}\n\n\t/**\n\t * Multiply this BigRational with {@code other}.\n\t * Ensures result rational is coprime\n\t *\n\t * @param other long to multiply with\n\t * @return result of the multiplication\n\t */\n\tpublic BigRational multiply(long other)\n\t{\n\t\treturn multiply(other, true);\n\t}\n\n\t/**\n\t * Divide this BigRational by {@code other}.\n\t *\n\t * @param other BigRational to divide by\n\t * @param cancel whether ensure result rational is coprime\n\t * @return result of the division\n\t */\n\tpublic BigRational divide(BigRational other, boolean cancel)\n\t{\n\t\tif (other.isInf() || other.isMInf()) {\n\t\t\treturn NAN;\n\t\t}\n\n\t\tif (other.isZero()) {\n\t\t\tif (this.isZero() || this.isNaN()) {\n\t\t\t\treturn BigRational.NAN;\n\t\t\t} else {\n\t\t\t\tif (this.signum() > 0) {\n\t\t\t\t\treturn BigRational.INF;\n\t\t\t\t} else {\n\t\t\t\t\treturn BigRational.MINF;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tBigRational inverseOther = new BigRational(other.den, other.num, cancel);\n\t\treturn multiply(inverseOther, cancel);\n\t}\n\n\t/**\n\t * Divide this BigRational by {@code other}.\n\t * Ensures result rational is coprime\n\t *\n\t * @param other long to divide by\n\t * @return result of the division\n\t */\n\tpublic BigRational divide(BigRational other)\n\t{\n\t\treturn divide(other, true);\n\t}\n\n\t/**\n\t * Divide this BigRational by {@code other}.\n\t * Ensures result rational is coprime\n\t *\n\t * @param other long to divide by\n\t * @return result of the division\n\t */\n\tpublic BigRational divide(long other)\n\t{\n\t\treturn divide(new BigRational(other));\n\t}\n\n\t/**\n\t * Returns the signum function of this BigRational.\n\t *\n\t * @return -1, 0 or 1 as the value of this BigRational is negative, zero or positive.\n\t */\n\tpublic int signum()\n\t{\n\t\tif (isInf()) return 1;\n\t\tif (isMInf()) return -1;\n\t\treturn num.signum() * den.signum();\n\t}\n\n\t/**\n\t * Returns a BigRational whose value is {@code this} to the {@code exponent}.\n\t *\n\t * @param exponent exponent to which this number is raised\n\t * @return {@code this} to the {@code exponent}\n\t */\n\tpublic BigRational pow(int exponent)\n\t{\n\t\tBigInteger num;\n\t\tBigInteger den;\n\t\tif (exponent == 0) {\n\t\t\treturn ONE;\n\t\t} else if (exponent > 0) {\n\t\t\tnum = this.num.pow(exponent);\n\t\t\tden = this.den.pow(exponent);\n\t\t} else { // exponent < 0\n\t\t\texponent = -exponent;\n\t\t\tnum = this.den.pow(exponent);\n\t\t\tden = this.num.pow(exponent);\n\t\t}\n\t\treturn new BigRational(num, den, false);\n\t}\n\n\t/**\n\t * Compares {@code this} to {@code obj}.\n\t * Returns true iff {@code obj} is a BigRational which represents\n\t * the same rational number as {@code this}.\n\t *\n\t * @param obj object to compare to\n\t * @return true iff {@code obj} is a BigRational which represents the same rational number as {@code this}.\n\t */\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (!(obj instanceof BigRational)) {\n\t\t\treturn false;\n\t\t}\n\t\tBigRational other = (BigRational) obj;\n\t\tif (isNaN()) {\n\t\t\treturn other.isNaN();\n\t\t}\n\t\tif (isInf()) {\n\t\t\treturn other.isInf();\n\t\t}\n\t\tif (isMInf()) {\n\t\t\treturn other.isMInf();\n\t\t}\n\t\treturn this.num.equals(other.num) && this.den.equals(other.den);\n\t}\n\n\t/**\n\t * Returns a hash code for this object.\n\t *\n\t * @return has code\n\t */\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\treturn 37 * num.hashCode() + den.hashCode();\n\t}\n\n\t/**\n\t * Returns a double approximation of value represented by this BigRational.\n\t * There are no guarantees on preciseness currently, so this function\n\t * should be mainly used for plotting graphs, etc. Can return\n\t * {@code Double.NaN}, {@code Double.POSITIVE_INFINITY},\n\t * {@code Double.NEGATIVE_INFINITY} in case this BigRational represents\n\t * not-a-number, positive infinity or negative infinitey respectively.\n\t *\n\t * @return a double approximation of the rational represented by this object\n\t */\n\tpublic double doubleValue()\n\t{\n\t\tif (isNaN()) {\n\t\t\treturn Double.NaN;\n\t\t} else if (isInf()) {\n\t\t\treturn Double.POSITIVE_INFINITY;\n\t\t} else if (isMInf()) {\n\t\t\treturn Double.NEGATIVE_INFINITY;\n\t\t} else if (isOne()) {\n\t\t\treturn 1.0;\n\t\t} else if (isZero()) {\n\t\t\treturn 0.0;\n\t\t}\n\t\tBigInteger shiftedNum;\n\t\tint signum = num.signum() * den.signum();\n\t\tBigInteger posNum = num.abs();\n\t\tBigInteger posDen = den.abs();\n\t\tshiftedNum = posNum.shiftLeft(55);\n\t\tBigInteger div = shiftedNum.divide(posDen);\n\t\tif (shiftedNum.remainder(posDen).multiply(BITWO).compareTo(posDen) == 1) {\n\t\t\tdiv = div.add(BigInteger.ONE);\n\t\t}\n\t\treturn signum * div.doubleValue() / Math.pow(2.0, 55);\n\t}\n\n\t/**\n\t * Returns the value of the specified number as an {@code int},\n\t * which may involve rounding or truncation.\n\t * <br>\n\t * Note: In contrast to the standard Number.intValue() behaviour,\n\t * this implementation throws an Arithmetic exception if the underlying\n\t * rational number is not an integer or if representing as an {@code int}\n\t * overflows.\n\t * <br>\n\t * Positive and negative infinity are mapped to Integer.MAX_VALUE and Integer.MIN_VALUE,\n\t * respectively, NaN is mapped to 0 (per the Java Language Specification).\n\t *\n\t * @return  the numeric value represented by this object after conversion\n\t *          to type {@code int}.\n\t */\n\t@Override\n\tpublic int intValue()\n\t{\n\t\tif (isSpecial()) {\n\t\t\tif (isInf()) return Integer.MAX_VALUE;\n\t\t\tif (isMInf()) return Integer.MIN_VALUE;\n\t\t\tif (isNaN()) return 0;  // per Java Language Specification\n\t\t}\n\n\t\t// TODO JK: In case of fraction / overflow, this method should not throw an\n\t\t// exception but return some imprecise result. We are conservative here.\n\t\t// In the future, it may make sense to have an intValueExact (similar to BigInteger)\n\t\tif (!isInteger()) {\n\t\t\tthrow new ArithmeticException(\"Can not convert fractional number to int\");\n\t\t}\n\t\tint value = getNum().intValue();\n\t\tif (!getNum().equals(BigInteger.valueOf(value))) {\n\t\t\tthrow new ArithmeticException(\"Can not convert BigInteger to int, value \" + this + \" out of range\");\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Returns the value of the specified number as a {@code long},\n\t * which may involve rounding or truncation.\n\t * <br>\n\t * Note: In contrast to the standard Number.longValue() behaviour,\n\t * this implementation throws an Arithmetic exception if the underlying\n\t * rational number is not an integer or if representing as a {@code long}\n\t * overflows.\n\t * <br>\n\t * Positive and negative infinity are mapped to Long.MAX_VALUE and Long.MIN_VALUE,\n\t * respectively, NaN is mapped to 0 (per the Java Language Specification).\n\t *\n\t * @return  the numeric value represented by this object after conversion\n\t *          to type {@code int}.\n\t */\n\t@Override\n\tpublic long longValue()\n\t{\n\t\tif (isSpecial()) {\n\t\t\tif (isInf()) return Long.MAX_VALUE;\n\t\t\tif (isMInf()) return Long.MIN_VALUE;\n\t\t\tif (isNaN()) return 0;  // per Java Language Specification\n\t\t}\n\n\t\t// TODO JK: In case of fraction / overflow, this method should not throw an\n\t\t// exception but return some imprecise result. We are conservative here. In the future,\n\t\t// it may make sense to have a longValueExact (similar to BigInteger)\n\t\tif (!isInteger()) {\n\t\t\tthrow new ArithmeticException(\"Can not convert fractional number to long\");\n\t\t}\n\t\tlong value = getNum().longValue();\n\t\tif (!getNum().equals(BigInteger.valueOf(value))) {\n\t\t\tthrow new ArithmeticException(\"Can not convert BigInteger to long, value \" + this + \" out of range\");\n\t\t}\n\t\treturn value;\n\t}\n\n\t@Override\n\tpublic float floatValue()\n\t{\n\t\t// TODO JK: Better precision?\n\t\treturn (float)doubleValue();\n\t}\n\n\t/**\n\t * Returns the value of the specified number as a {code BigInteger},\n\t * which may involve rounding or truncation.\n\t * <br>\n\t * Note: In contrast to the standard Number.intValue() behaviour,\n\t * this implementation throws an Arithmetic exception if the underlying\n\t * rational number is not an integer.\n\t * <br>\n\t * Since {code BigInteger} cannot represent infinity,\n\t * Positive and negative infinity are mapped to Long.MAX_VALUE and Long.MIN_VALUE,\n\t * respectively, NaN is mapped to 0 (per the Java Language Specification).\n\t *\n\t * @return  the numeric value represented by this object after conversion\n\t *          to type {code BigInteger}.\n\t */\n\tpublic BigInteger bigIntegerValue()\n\t{\n\t\tif (isSpecial()) {\n\t\t\tif (isInf()) return BigInteger.valueOf(Long.MAX_VALUE);\n\t\t\tif (isMInf()) return BigInteger.valueOf(Long.MIN_VALUE);\n\t\t\tif (isNaN()) return BigInteger.ZERO;  // per Java Language Specification\n\t\t}\n\n\t\tif (!isInteger()) {\n\t\t\tthrow new ArithmeticException(\"Can not convert fractional number to int\");\n\t\t}\n\t\treturn getNum();\n\t}\n\n\t/**\n\t * Returns a string representation of this BigRational.\n\t *\n\t * @return string representation of this rational number\n\t */\n\t@Override\n\tpublic String toString()\n\t{\n\t\tif (isNaN()) {\n\t\t\treturn \"NaN\";\n\t\t} else if (isInf()) {\n\t\t\treturn \"Inf\";\n\t\t} else if (isMInf()) {\n\t\t\treturn \"-Inf\";\n\t\t} else if (den.equals(BigInteger.ONE)) {\n\t\t\treturn num.toString();\n\t\t} else {\n\t\t\treturn num + \"/\" + den;\n\t\t}\n\t}\n\n\t/**\n\t * Compares this BigRational to another BigRational other.\n\t *\n\t * @return -1, 0 or 1 as this BigRational is numerically less than, equal to, or greater than {@code other}.\n\t */\n\t@Override\n\tpublic int compareTo(BigRational other)\n\t{\n\t\tif (this.isInf()) {\n\t\t\tif (other.isInf()) {\n\t\t\t\treturn 0;\n\t\t\t} else {\n\t\t\t\treturn 1;\n\t\t\t}\n\t\t}\n\t\tif (this.isMInf()) {\n\t\t\tif (other.isMInf()) {\n\t\t\t\treturn 0;\n\t\t\t} else {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\t\treturn this.num.multiply(other.den).compareTo(other.num.multiply(this.den));\n\t}\n\n\t/**\n\t * Compares this BigRational to the long other.\n\t *\n\t * @return -1, 0 or 1 as this BigRational is numerically less than, equal to, or greater than {@code other}.\n\t */\n\tpublic int compareTo(long i)\n\t{\n\t\treturn this.compareTo(new BigRational(i));\n\t}\n\n\t/** Returns true if this number is less than the other number */\n\tpublic boolean lessThan(BigRational other)\n\t{\n\t\treturn this.compareTo(other) < 0;\n\t}\n\n\t/** Returns true if this number is less than or equal the other number */\n\tpublic boolean lessThanEquals(BigRational other)\n\t{\n\t\treturn this.compareTo(other) <= 0;\n\t}\n\n\t/** Returns true if this number is greater than the other number */\n\tpublic boolean greaterThan(BigRational other)\n\t{\n\t\treturn this.compareTo(other) > 0;\n\t}\n\n\t/** Returns true if this number is greater than or equal the other number */\n\tpublic boolean greaterThanEquals(BigRational other)\n\t{\n\t\treturn this.compareTo(other) >= 0;\n\t}\n\n\t/**\n\t * Return numerator of this BigRational as a BigInteger.\n\t *\n\t * @return numerator of this BigRational as a BigInteger\n\t */\n\tpublic BigInteger getNum()\n\t{\n\t\treturn num;\n\t}\n\n\t/**\n\t * Return denominator of this BigRational as a BigInteger.\n\t *\n\t * @return denominator of this BigRational as a BigInteger\n\t */\n\tpublic BigInteger getDen()\n\t{\n\t\treturn den;\n\t}\n\n\t/**\n\t * Return absolute value of this BigRational.\n\t *\n\t * @return absolute value of this BigRational\n\t */\n\tpublic BigRational abs()\n\t{\n\t\tif (num.signum() == -1) {\n\t\t\treturn new BigRational(num.negate(), den);\n\t\t} else {\n\t\t\treturn this;\n\t\t}\n\t}\n\n\t/**\n\t * Return ceil(value), i.e., the smallest integer >= value.\n\t * @throws PrismLangException for special values (NaN, infinity)\n\t */\n\tpublic BigRational ceil() throws PrismLangException\n\t{\n\t\tif (isSpecial()) {\n\t\t\tthrow new PrismLangException(\"Can not compute ceil of \" + this);\n\t\t}\n\n\t\tBigInteger[] divideAndRemainder = getNum().divideAndRemainder(getDen());\n\n\t\tswitch (divideAndRemainder[1].compareTo(BigInteger.ZERO)) {\n\t\tcase 0:   // no remainder\n\t\tcase -1:  // negative remainder: value was negative, so we ignore the remainder\n\t\t\treturn new BigRational(divideAndRemainder[0]);\n\t\tcase 1:   // positive remainder: return next-largest integer\n\t\t\treturn new BigRational(divideAndRemainder[0].add(BigInteger.ONE));\n\t\tdefault:\n\t\t\tthrow new IllegalStateException(\"Should not be reached\");\n\t\t}\n\t}\n\n\t/**\n\t * Return floor(value), i.e., the largest integer <= value.\n\t * @throws PrismLangException for special values (NaN, infinity)\n\t */\n\tpublic BigRational floor() throws PrismLangException\n\t{\n\t\tif (isSpecial()) {\n\t\t\tthrow new PrismLangException(\"Can not compute floor of \" + this);\n\t\t}\n\n\t\tBigInteger[] divideAndRemainder = getNum().divideAndRemainder(getDen());\n\t\tswitch (divideAndRemainder[1].compareTo(BigInteger.ZERO)) {\n\t\tcase 0:   // no remainder\n\t\tcase 1:   // positive remainder: value was positive, so we ignore the remainder\n\t\t\treturn new BigRational(divideAndRemainder[0]);\n\t\tcase -1:  // negative remainder: value was negative, return next-smallest integer\n\t\t\treturn new BigRational(divideAndRemainder[0].subtract(BigInteger.ONE));\n\t\tdefault:\n\t\t\tthrow new IllegalStateException(\"Should not be reached\");\n\t\t}\n\t}\n\n\t/**\n\t * Return round(value), i.e., the integer closest to value with\n\t * ties rounding towards positive infinity.\n\t * @throws PrismLangException for special values (NaN, infinity)\n\t */\n\tpublic BigRational round() throws PrismLangException\n\t{\n\t\tif (isSpecial()) {\n\t\t\tthrow new PrismLangException(\"Can not compute round of \" + this);\n\t\t}\n\n\t\treturn this.add(HALF).floor();\n\t}\n\n\t/**\n\t * Returns larger value of {@code this} and {@code other}.\n\t *\n\t * @param other rational number to compare to\n\t * @return {@code other} if {@code other} this is larger than {@code this} and {@code this} otherwise\n\t */\n\tpublic BigRational max(BigRational other)\n\t{\n\t\tif (this.compareTo(other) >= 0) {\n\t\t\treturn this;\n\t\t} else {\n\t\t\treturn other;\n\t\t}\n\t}\n\n\t/**\n\t * Returns smaller value of {@code this} and {@code other}.\n\t *\n\t * @param other rational number to compare to\n\t * @return {@code other} if {@code other} this is smaller than {@code this} and {@code this} otherwise\n\t */\n\tpublic BigRational min(BigRational other)\n\t{\n\t\tif (this.compareTo(other) <= 0) {\n\t\t\treturn this;\n\t\t} else {\n\t\t\treturn other;\n\t\t}\n\t}\n\n\t/**\n\t * Returns true iff this BigRational represents the number zero.\n\t *\n\t * @return true iff this BigRational represents the number zero\n\t */\n\tpublic boolean isZero()\n\t{\n\t\treturn num.equals(BigInteger.ZERO) && den.equals(BigInteger.ONE);\n\t}\n\n\t/**\n\t * Returns true iff this BigRational represents the number one.\n\t *\n\t * @return true iff this BigRational represents the number one\n\t */\n\tpublic boolean isOne()\n\t{\n\t\treturn num.equals(BigInteger.ONE) && den.equals(BigInteger.ONE);\n\t}\n\n\t/**\n\t * Returns true iff this BigRational represents the special value not-a-number.\n\t *\n\t * @return true iff this BigRational represents the special value not-a-number\"\n\t */\n\tpublic boolean isNaN()\n\t{\n\t\treturn num.equals(BigInteger.ZERO) && den.equals(BigInteger.ZERO);\n\t}\n\n\t/**\n\t * Returns true iff this BigRational represents positive infinity.\n\t *\n\t * @return true iff this BigRational represents positive infinity\n\t */\n\tpublic boolean isInf()\n\t{\n\t\treturn num.equals(BigInteger.ONE) && den.equals(BigInteger.ZERO);\n\t}\n\n\t/**\n\t * Returns true iff this BigRational represents negative infinity.\n\t *\n\t * @return true iff this BigRational represents negative infinity\n\t */\n\tpublic boolean isMInf()\n\t{\n\t\treturn num.equals(BMONE) && den.equals(BigInteger.ZERO);\n\t}\n\n\t/**\n\t * Returns true iff this BigRational represents a finite value\n\t * (i.e., not positive or negative infinity), nor NaN.\n\t *\n\t * @return true iff this BigRational represents a finite value\n\t */\n\tpublic boolean isFinite()\n\t{\n\t\treturn !(isInf() || isMInf() || isNaN());\n\t}\n\n\t/**\n\t * Returns true iff this object represents a true rational number.\n\t * This excludes the values for not-a-number as well as positive\n\t * and negative infinity.\n\t *\n\t * @return true iff this object represents a true rational number\n\t */\n\tpublic boolean isRational()\n\t{\n\t\treturn !isNaN() && !isInf() && !isMInf();\n\t}\n\n\t/**\n\t * Returns true iff this object represents an integer, i.e.,\n\t * is not not-a-number, positive, or negative infinity and\n\t * the denominator is 1.\n\t *\n\t * @return true iff this object represents an integer\n\t */\n\tpublic boolean isInteger()\n\t{\n\t\treturn isRational() && getDen().equals(BigInteger.ONE);\n\t}\n\n\t/**\n\t * Returns true iff this value represents a special number.\n\t * This is the case if this is either not-a-number, positive or\n\t * negative infinity.\n\t *\n\t * @return true iff this object represents a special number\n\t */\n\tpublic boolean isSpecial()\n\t{\n\t\treturn isNaN() || isInf() || isMInf();\n\t}\n\n\t/**\n\t * Returns true if this value equals 1 or false if this value\n\t * equals 0. In all other cases, a PrismLangException is thrown.\n\t */\n\tpublic boolean toBoolean() throws PrismLangException\n\t{\n\t\tif (isOne())\n\t\t\treturn true;\n\t\tif (isZero())\n\t\t\treturn false;\n\t\tthrow new PrismLangException(\"Conversion from BigRational to Boolean not possible, invalid value: \" + this);\n\t}\n\n\t/**\n\t * Return an approximate String representation (via conversion to double).\n\t * If the conversion is imprecise, the result string is prefixed by '~'.\n\t */\n\tpublic String toApproximateString()\n\t{\n\t\tString result = Double.toString(doubleValue());\n\t\tif (new BigRational(result).equals(this)) {\n\t\t\t// round-trip did not lose precision\n\t\t\treturn result;\n\t\t}\n\t\t// only approximate\n\t\treturn \"~\" + result;\n\n\t}\n\n\t/**\n\t * Returns the int representation of this value,\n\t * if this value is an integer and if the integer can\n\t * be represented by an int variable.\n\t * In all other cases, a PrismLangException is thrown.\n\t */\n\tpublic int toInt() throws PrismLangException\n\t{\n\t\tif (!isInteger()) {\n\t\t\tthrow new PrismLangException(\"Can not convert fractional number to int\");\n\t\t}\n\t\tint value = getNum().intValue();\n\t\tif (!getNum().equals(BigInteger.valueOf(value))) {\n\t\t\tthrow new PrismLangException(\"Can not convert BigInteger to int, value out of range\");\n\t\t}\n\t\treturn value;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/BoxRegion.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.math.BigInteger;\nimport java.util.ArrayList;\nimport java.util.Random;\n\n/**\n * Implements a region representation by a box (hyper-rectangle).\n * This means that for each parameter we have a lower and upper bound, and\n * the region contains all points so that the corresponding dimensions are\n * (not strictly) between these lower and upper bounds.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see BoxRegionFactory\n */\nfinal class BoxRegion extends Region {\n\t/** used to produce random inner points of box regions */\n\tstatic Random random = new Random();\n\t\n\t/** regions are only to be split at longest side */\n\tstatic final int SPLIT_LONGEST = 1;\n\t/** regions are to be split at all sides on each split */\n\tstatic final int SPLIT_ALL = 2;\n\t\n\t/** lower bound for each parameter */\n\tprivate BigRational[] lower;\n\t/** upper bound for each parameter */\n\tprivate BigRational[] upper;\n\t\n\t// constructors\n\t\n\t/**\n\t * Constructs a new box region.\n\t * Does not assign lower and upper bounds, that is the regions is\n\t * not direcly usable after construction.\n\t *  \n\t * @param factory factory this box region belongs to\n\t */\n\tprivate BoxRegion(BoxRegionFactory factory)\n\t{\n\t\tthis.factory = factory;\n\t\tlower = new BigRational[factory.numVariables()];\n\t\tupper = new BigRational[factory.numVariables()];\n\t}\n\t\n\t/**\n\t * Constructs a new box region.\n\t * \n\t * @param factory factory this box region belongs to\n\t * @param lower lower bounds for each parameter\n\t * @param upper upper bounds for each parameter\n\t */\n\tBoxRegion(BoxRegionFactory factory, BigRational[] lower, BigRational[] upper)\n\t{\n\t\tthis.factory = factory;\n\t\tthis.lower = new BigRational[lower.length];\n\t\tthis.upper = new BigRational[upper.length];\n\t\tSystem.arraycopy(lower, 0, this.lower, 0, lower.length);\n\t\tSystem.arraycopy(upper, 0, this.upper, 0, upper.length);\n\t}\n\t\n\t/**\n\t * Copy constructor for box regions.\n\t * For internal use, because regions are generally immutable, so that\n\t * there is no need to have external copy constructors.\n\t * \n\t * @param other region to copy from\n\t */\n\tprivate BoxRegion(BoxRegion other)\n\t{\n\t\tthis.factory = other.factory;\n\t\tthis.lower = new BigRational[other.lower.length];\n\t\tthis.upper = new BigRational[other.upper.length];\n\t\tSystem.arraycopy(other.lower, 0, this.lower, 0, other.lower.length);\n\t\tSystem.arraycopy(other.upper, 0, this.upper, 0, other.upper.length);\t\t\n\t}\n\t\n\t/**\n\t * Sets lower and upper bound of given parameter.\n\t * \n\t * @param dim parameter to set bounds of\n\t * @param lower new lower bound of parameter\n\t * @param upper new upper bound of parameter\n\t */\n\tprivate void setDimension(int dim, BigRational lower, BigRational upper)\n\t{\n\t\tthis.lower[dim] = lower;\n\t\tthis.upper[dim] = upper;\n\t}\n\t\n\t@Override\n\tint getDimensions()\n\t{\n\t\treturn lower.length;\n\t}\n\t\n\t/**\n\t * Get lower bound of given parameter in region.\n\t * \n\t * @param dim parameter to get lower bound of\n\t * @return lower bound of given parameter in region\n\t */\n\tBigRational getDimensionLower(int dim)\n\t{\n\t\treturn lower[dim];\n\t}\n\n\t/**\n\t * Get upper bound of given parameter in region.\n\t * \n\t * @param dim parameter to get lower bound of\n\t * @return upper bound of given parameter in region\n\t */\t\n\tBigRational getDimensionUpper(int dim)\n\t{\n\t\treturn upper[dim];\n\t}\n\n\t@Override\n\tpublic boolean equals(Object object) {\n\t\tif (!(object instanceof BoxRegion)) {\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\tBoxRegion other = (BoxRegion) object;\n\t\t\n\t\tif (this.getDimensions() != other.getDimensions()) {\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\tfor (int i = 0; i < getDimensions(); i++) {\n\t\t\tif (!this.lower[i].equals(other.lower[i])) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (!this.upper[i].equals(other.upper[i])) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tint hash = 0;\n\t\t\n\t\tfor (int i = 0; i < getDimensions(); i++) {\n\t\t\thash = lower[i].hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t\thash = upper[i].hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t}\n\t\t\n\t\treturn hash;\n\t}\n\t\n\t/**\n\t * Gets the central points of the region.\n\t *\n\t * @return point in the centre of the region\n\t */\n\tPoint getMidPoint()\n\t{\n\t\tBigRational[] point = new BigRational[lower.length];\n\t\tfor (int dim = 0; dim < lower.length; dim++) {\n\t\t\tBigRational mid = lower[dim].add(upper[dim]).divide(2);\n\t\t\tpoint[dim] = mid;\n\t\t}\n\t\treturn new Point(point);\n\t}\n\t\n\t/**\n\t * Get volume of the region.\n\t * The volumes of disjoint region which cover the whole parameter\n\t * space sum up to 1. This implies that the volumes are normalised\n\t * according to the upper and lower bounds of the parameters.\n\t * \n\t * @return volume of this region\n\t */\n\t@Override\n\tBigRational volume()\n\t{\n\t\tBigRational volume = BigRational.ONE;\n\t\tfor (int dim = 0; dim < lower.length; dim++) {\n\t\t\tvolume = volume.multiply(upper[dim].subtract(lower[dim]));\n\t\t\tvolume = volume.divide(factory.sideWidth(dim));\n\t\t}\n\t\treturn volume;\n\t}\n\t\n\t@Override\n\tboolean contains(Point point)\n\t{\n\t\tfor (int dim = 0; dim < getDimensions(); dim++) {\n\t\t\tif (point.getDimension(dim).compareTo(lower[dim]) < 0) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (point.getDimension(dim).compareTo(upper[dim]) > 0) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tboolean contains(Region region)\n\t{\n\t\tBoxRegion other = (BoxRegion) region;\n\t\tfor (int dim = 0; dim < getDimensions(); dim++) {\n\t\t\tif (other.lower[dim].compareTo(this.lower[dim]) == -1) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (other.upper[dim].compareTo(this.upper[dim]) == +1) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic String toString() {\n\t\tStringBuilder builder = new StringBuilder();\n\t\tbuilder.append(\"(\");\n\t\tfor (int dim = 0; dim < getDimensions(); dim++) {\n\t\t\tbuilder.append(\"[\");\n\t\t\tbuilder.append(lower[dim].doubleValue());\n\t\t\tbuilder.append(\",\");\n\t\t\tbuilder.append(upper[dim].doubleValue());\n\t\t\tbuilder.append(\"]\");\n\t\t\tif (dim < getDimensions() - 1) {\n\t\t\t\tbuilder.append(\",\");\n\t\t\t}\n\t\t}\n\t\tbuilder.append(\")\");\n\t\treturn builder.toString();\n\t}\n\n\t@Override\n\tRegionValues binaryOp(int op, StateValues values1, StateValues values2) {\n\t\tRegionValues result;\n\t\tif ((op == Region.EQ || op == Region.NE || op == Region.GT || op == Region.GE || op ==  Region.LT || op == Region.LE)) {\n\t\t\tresult = cmpOp(op, values1, values2);\n\t\t} else {\n\t\t\tresult = new RegionValues(factory);\n\t\t\tint numStates = values1.getNumStates();\n\t\t\tStateValues values = new StateValues(numStates, factory.getInitialState());\n\t\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\t\tif (op == Region.IMPLIES || op == Region.IFF || op == Region.OR || op == Region.AND) {\n\t\t\t\t\tboolean stateVal = booleanOp(op, values1.getStateValueAsBoolean(state), values2.getStateValueAsBoolean(state));\n\t\t\t\t\tvalues.setStateValue(state, stateVal);\n\t\t\t\t} else if (op == Region.PLUS || op == Region.MINUS || op == Region.TIMES || op == Region.DIVIDE) {\n\t\t\t\t\tFunction stateVal = arithOp(op, values1.getStateValueAsFunction(state), values2.getStateValueAsFunction(state));\n\t\t\t\t\tvalues.setStateValue(state, stateVal);\n\t\t\t\t} else if (op == Region.POW) {\n\t\t\t\t\tFunction stateVal = powOp(values1.getStateValueAsFunction(state), values2.getStateValueAsFunction(state));\n\t\t\t\t\tvalues.setStateValue(state, stateVal);\n\t\t\t\t} else {\n\t\t\t\t\tthrow new UnsupportedOperationException(\"operator not yet implemented for parametric analyses\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.add(this, values);\n\t\t}\n\t\treturn result;\n\t}\n\n\tprivate RegionValues cmpOp(int op, StateValues op1, StateValues op2) {\n\t\tConstraintChecker checker = factory.getConstraintChecker();\n\t\tRegionsTODO remaining = new RegionsTODO();\n\t\tremaining.add(this);\n\t\tBigRational requiredVolume = this.volume().multiply(BigRational.ONE.subtract(factory.getPrecision()));\n\t\tBigRational doneVolume = BigRational.ZERO;\n\t\tRegionValues result = new RegionValues(factory);\n\t\tFunction lastFunction = null;\n\t\twhile (doneVolume.compareTo(requiredVolume) == -1) {\n\t\t\tBoxRegion region = (BoxRegion) remaining.poll();\n\t\t\tStateValues newValues = new StateValues(op1.getNumStates(), factory.getInitialState());\n\t\t\tboolean allDecided = true;\n\t\t\tfor (int state = 0; state < op1.getNumStates(); state++) {\n\t\t\t\tStateValue op1Val = op1.getStateValue(state);\n\t\t\t\tStateValue op2Val = op2.getStateValue(state);\n\t\t\t\tFunction op1ValFn = op1Val instanceof Function ? (Function) op1Val : null;\n\t\t\t\tFunction op2ValFn = op2Val instanceof Function ? (Function) op2Val : null;\n\t\t\t\tif (op == Region.EQ) {\n\t\t\t\t\tif (op1Val instanceof StateBoolean) {\n\t\t\t\t\t\tnewValues.setStateValue(state, op1Val.equals(op2Val));\t\t\t\t\t\t\n\t\t\t\t\t}\n\t\t\t\t\telse if (op1Val.equals(op2Val)) {\n\t\t\t\t\t\tnewValues.setStateValue(state, true);\t\t\t\n\t\t\t\t\t} else if (checker.check(region, op1ValFn.subtract(op2ValFn), true)) {\n\t\t\t\t\t\tnewValues.setStateValue(state, false);\t\n\t\t\t\t\t} else if (checker.check(region, op2ValFn.subtract(op1ValFn), true)) {\n\t\t\t\t\t\tnewValues.setStateValue(state, false);\t\n\t\t\t\t\t} else {\n\t\t\t\t\t\tallDecided = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t} else if (op == Region.NE) {\n\t\t\t\t\tif (op1Val instanceof StateBoolean) {\n\t\t\t\t\t\tnewValues.setStateValue(state, !op1Val.equals(op2Val));\n\t\t\t\t\t} else if (op1Val.equals(op2Val)) {\n\t\t\t\t\t\tnewValues.setStateValue(state, false);\n\t\t\t\t\t} else if (checker.check(region, op1ValFn.subtract(op2ValFn), true)) {\n\t\t\t\t\t\tnewValues.setStateValue(state, true);\n\t\t\t\t\t} else if (checker.check(region, op2ValFn.subtract(op1ValFn), true)) {\n\t\t\t\t\t\tnewValues.setStateValue(state, true);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tallDecided = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tboolean strict = op == Region.GT || op == Region.LT;\n\t\t\t\t\tFunction cmpTrue = (op == Region.LT || op == Region.LE) ? op2ValFn.subtract(op1ValFn) : op1ValFn.subtract(op2ValFn);\n\t\t\t\t\tif (checker.check(region, cmpTrue, strict)) {\n\t\t\t\t\t\tnewValues.setStateValue(state, true);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tFunction cmpFalse = (op == Region.LT || op == Region.LE) ? op1ValFn.subtract(op2ValFn) : op2ValFn.subtract(op1ValFn);\n\t\t\t\t\t\tif (checker.check(region, cmpFalse, !strict)) {\n\t\t\t\t\t\t\tnewValues.setStateValue(state, false);\t\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tallDecided = false;\n\t\t\t\t\t\t\tlastFunction = op2ValFn.subtract(op1ValFn);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (allDecided) {\n\t\t\t\tresult.add(region, newValues);\n\t\t\t\tdoneVolume = doneVolume.add(region.volume());\n\t\t\t} else {\n\t\t\t\tremaining.addAll(region.split(lastFunction));\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn result;\n\t}\n\t\n\t/**\n\t * Performs given operation on two rational functions.\n\t * \n\t * @param op operation to perform, see values in {@code Region}\n\t * @param op1 first operand\n\t * @param op2  second operand\n\t * @return value of operation\n\t */\n\tprivate Function arithOp(int op, Function op1, Function op2) {\n\t\tFunction result = null;\n\t\tswitch (op) {\n\t\tcase Region.PLUS:\n\t\t\tresult = op1.add(op2);\n\t\t\tbreak;\n\t\tcase Region.MINUS:\n\t\t\tresult = op1.subtract(op2);\n\t\t\tbreak;\n\t\tcase Region.TIMES:\n\t\t\tresult = op1.multiply(op2);\n\t\t\tbreak;\n\t\tcase Region.DIVIDE:\n\t\t\tresult = op1.divide(op2);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new IllegalArgumentException(\"unsupported arithmetic operator number \" + op);\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Performs a power operation on two rational functions.\n\t *\n\t * @param op1 first operand\n\t * @param op2  second operand\n\t * @return value of operation\n\t */\n\tprivate Function powOp(Function op1, Function op2)\n\t{\n\t\tif (!op2.isConstant()) {\n\t\t\tthrow new IllegalArgumentException(\"unsupported pow operation\");\n\t\t}\n\t\tBigRational exp = op2.asBigRational();\n\t\tif (!exp.isInteger()) {\n\t\t\tthrow new IllegalArgumentException(\"unsupported pow operation\");\n\t\t}\n\t\tint expInt = exp.getNum().intValue();\n\t\treturn op1.pow(expInt);\n\t}\n\n\t/**\n\t * Performs given operation on two booleans.\n\t * \n\t * @param op operation to perform, see values in {@code Region}\n\t * @param op1 first operand\n\t * @param op2  second operand\n\t * @return value of operation\n\t */\n\tprivate boolean booleanOp(int op, boolean op1, boolean op2) {\n\t\tboolean result = false;\n\t\t\n\t\tswitch (op) {\n\t\tcase Region.IMPLIES:\n\t\t\tresult = !op1 || op2;\n\t\t\tbreak;\n\t\tcase Region.IFF:\n\t\t\tresult = op1 == op2;\n\t\t\tbreak;\n\t\tcase Region.OR:\n\t\t\tresult = op1 || op2;\n\t\t\tbreak;\n\t\tcase Region.AND:\n\t\t\tresult = op1 && op2;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new IllegalArgumentException(\"unsupported boolean operator number \" + op);\n\t\t}\n\t\treturn result;\n\t}\n\t\n\t@Override\n\tRegionValues ITE(StateValues valuesI, StateValues valuesT, StateValues valuesE)\n\t{\n\t\tRegionValues result = new RegionValues(factory);\n\t\tint numStates = valuesI.getNumStates();\n\t\tStateValues values = new StateValues(numStates, factory.getInitialState());\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tif (valuesI.getStateValueAsBoolean(state)) {\n\t\t\t\tvalues.setStateValue(state, valuesT.getStateValue(state));\n\t\t\t} else {\n\t\t\t\tvalues.setStateValue(state, valuesE.getStateValue(state));\n\t\t\t}\n\t\t}\n\t\tresult.add(this, values);\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Split region in longest dimension.\n\t * \n\t * @return set of new regions covering same area\n\t */\n\tprivate ArrayList<Region> splitLongest()\n\t{\n\t\tint longestSide = -1;\n\t\tBigRational longestLength = BigRational.ZERO;\n\t\tfor (int side = 0; side < lower.length; side++) {\n\t\t\tBigRational sideLength = upper[side].subtract(lower[side]);\n\t\t\tif (sideLength.compareTo(longestLength) == 1) {\n\t\t\t\tlongestSide = side;\n\t\t\t\tlongestLength = sideLength;\n\t\t\t}\n\t\t}\n\t\t\n\t\tArrayList<Region> result = new ArrayList<Region>();\n\t\tBoxRegion region1 = new BoxRegion(this);\n\t\tBoxRegion region2 = new BoxRegion(this);\n\t\tBigRational mid = (lower[longestSide].add(upper[longestSide])).divide(2);\n\t\tregion1.upper[longestSide] = mid;\n\t\tregion2.lower[longestSide] = mid;\n\t\tresult.add(region1);\n\t\tresult.add(region2);\n\t\t\t\t\n\t\treturn result;\n\t}\n\t\n\t/**\n\t * Split region in all dimensions.\n\t * \n\t * @return set of new regions covering same area\n\t */\n\tprivate ArrayList<Region> splitAll()\n\t{\n\t\tArrayList<Region> result = new ArrayList<Region>();\n\t\tfinal int numParts = 2;\n\t\tfinal int numNewRegions = (int) Math.pow(numParts, lower.length);\n\t\tBigRational[] newLower = new BigRational[lower.length];\n\t\tBigRational[] newUpper = new BigRational[upper.length];\n\t\tfor (int newRegionNr = 0; newRegionNr < numNewRegions; newRegionNr++) {\n\t\t\tint regionRest = newRegionNr;\n\t\t\tfor (int var = 0; var < lower.length; var++) {\n\t\t\t\tint lowerPart = regionRest % numParts;\n\t\t\t\tregionRest /= numParts;\n\t\t\t\tBigRational partLength = upper[var].subtract(lower[var]).divide(numParts);\n\t\t\t\tnewLower[var] = lower[var].add(partLength.multiply(lowerPart));\n\t\t\t\tnewUpper[var] = lower[var].add(partLength.multiply(lowerPart + 1));\n\t\t\t}\n\t\t\tresult.add(new BoxRegion((BoxRegionFactory) factory, newLower, newUpper));\n\t\t}\n\t\treturn result;\n\t}\n\n\t@Override\n\tArrayList<Region> split(Function constraint)\n\t{\n\t\t// TODO could implement more clever splitting using constraints\n\t\treturn split();\n\t}\n\n\t@Override\n\tArrayList<Region> split()\n\t{\n\t\tif (((BoxRegionFactory) factory).getSplitMethod() == SPLIT_LONGEST) {\n\t\t\treturn splitLongest();\n\t\t} else if (((BoxRegionFactory) factory).getSplitMethod() == SPLIT_ALL) {\n\t\t\treturn splitAll();\n\t\t} else {\n\t\t\tthrow new RuntimeException();\n\t\t}\n\t}\t\n\t\n\t@Override\n\tArrayList<Point> specialPoints()\n\t{\n\t\tArrayList<Point> result = new ArrayList<Point>();\n\t\tint numEdges = (int) Math.pow(2, lower.length);\n\t\tfor (int edgeNr = 0; edgeNr < numEdges; edgeNr++) {\n\t\t\tint regionRest = edgeNr;\n\t\t\tBigRational[] point = new BigRational[lower.length];\n\t\t\tfor (int dim = 0; dim < lower.length; dim++) {\n\t\t\t\tboolean useLower = ( 0 == (regionRest % 2));\n\t\t\t\tregionRest /= 2;\n\t\t\t\tif (useLower) {\n\t\t\t\t\tpoint[dim] = lower[dim];\n\t\t\t\t} else {\n\t\t\t\t\tpoint[dim] = upper[dim];\t\t\t\t\t\n\t\t\t\t}\n\t\t\t}\n\t\t\tresult.add(new Point(point));\n\t\t}\n\t\treturn result;\n\t}\n\t\n\t@Override\n\tPoint randomPoint()\n\t{\n\t\tBigRational[] point = new BigRational[lower.length];\n\t\tBigInteger maxInt = new BigInteger(Long.toString((long) Math.pow(2, 60))); \n\t\tfor (int dim = 0; dim < lower.length; dim++) {\n\t\t\tBigInteger rndInt = new BigInteger(60, random);\n\t\t\tBigRational rndRat = new BigRational(rndInt, maxInt);\n\t\t\trndRat = lower[dim].add(upper[dim].subtract(lower[dim]).multiply(rndRat));\n\t\t\tpoint[dim] = rndRat;\n\t\t}\n\t\t\n\t\treturn new Point(point);\n\t}\n\n\t@Override\n\tBoxRegion conjunct(Region region) {\n\t\tBoxRegion other = (BoxRegion) region;\n\t\t\n\t\tBoxRegion result = new BoxRegion((BoxRegionFactory) factory);\n\t\tfor (int dim = 0; dim < lower.length; dim++) {\n\t\t\tif (this.upper[dim].compareTo(other.lower[dim]) <= 0) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\tif (this.lower[dim].compareTo(other.upper[dim]) >= 0) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\tBigRational newLower = this.lower[dim].max(other.lower[dim]);\n\t\t\tBigRational newUpper = this.upper[dim].min(other.upper[dim]);\n\t\t\tif (newLower.equals(newUpper)) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\tresult.setDimension(dim, newLower, newUpper);\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Checks whether this region is adjacent to another region in given dimension.\n\t * In this case, both can be glued by @{code glue}.\n\t * \n\t * @param other region to check whether adjacent in given dimension\n\t * @param adjDim dimension where to check adjacency\n\t * @return true iff regions are adjacent in given dimension\n\t */\n\tprivate boolean adjacent(Region region, int adjDim)\n\t{\n\t\tBoxRegion other = (BoxRegion) region;\n\t\tfor (int dim = 0; dim < this.getDimensions(); dim++) {\n\t\t\tif (dim != adjDim) {\n\t\t\t\tif (!this.getDimensionLower(dim).equals(other.getDimensionLower(dim))) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t\tif (!this.getDimensionUpper(dim).equals(other.getDimensionUpper(dim))) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn this.getDimensionUpper(adjDim).equals(other.getDimensionLower(adjDim));\n\t}\n\n\t@Override\n\tboolean adjacent(Region region)\n\t{\n\t\tBoxRegion other = (BoxRegion) region;\n\t\tfor (int dim = 0; dim < getDimensions(); dim++) {\n\t\t\tif (adjacent(other, dim)) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tRegion glue(Region region) {\n\t\tBoxRegion other = (BoxRegion) region;\n\t\tBoxRegion result = new BoxRegion((BoxRegionFactory) this.getFactory());\n\t\t\n\t\tfor (int dim = 0; dim < result.getDimensions(); dim++) {\n\t\t\tresult.setDimension(dim, this.getDimensionLower(dim), other.getDimensionUpper(dim));\n\t\t}\n\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/BoxRegionFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\n/**\n * Implements a {@code RegionFactory} producing {@code BoxRegion}s.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see RegionFactory\n * @see BoxRegion\n */\nfinal class BoxRegionFactory extends RegionFactory {\n\t/** method to use to split boxes produces with this factory.\n\t * split either at all or only at the longest side. */\n\tprivate int splitMethod;\n\t\n\t/**\n\t * Constructs a new box region factory.\n\t * \n\t * @param functionFactory function factory to use\n\t * @param constraintChecker constraint checker to use\n\t * @param precision remaining undecided area to allow\n\t * @param numStates number of model states\n\t * @param initialState initial states of model\n\t * @param subsumeRegions whether to subsume regions if possible\n\t * @param splitMethod method to split regions\n\t */\n\tBoxRegionFactory(FunctionFactory functionFactory, ConstraintChecker constraintChecker, BigRational precision,\n\t\t\tint numStates, int initialState, boolean subsumeRegions, int splitMethod)\n\t{\n\t\tthis.functionFactory = functionFactory;\n\t\tthis.constraintChecker = constraintChecker;\n\t\tthis.precision = precision;\n\t\tthis.numStates = numStates;\n\t\tthis.initialState = initialState;\n\t\tthis.subsumeRegions = subsumeRegions;\n\t\tthis.splitMethod = splitMethod;\n\t}\n\t\n\t@Override\n\tRegionValues completeCover(StateValues values)\n\t{\n\t\tRegionValues result = new RegionValues(this);\n\t\tBigRational[] lower = new BigRational[functionFactory.getNumVariables()];\n\t\tBigRational[] upper = new BigRational[functionFactory.getNumVariables()];\n\t\tfor (int var = 0; var < functionFactory.getNumVariables(); var++) {\n\t\t\tlower[var] = functionFactory.getLowerBound(var);\n\t\t\tupper[var] = functionFactory.getUpperBound(var);\n\t\t}\n\t\tBoxRegion region = new BoxRegion(this, lower, upper);\n\t\tresult.add(region, values);\n\t\treturn result;\n\t}\n\n\t/**\n\t * Returns the method used to split regions.\n\t * See values specified in {@code Region}.\n\t * \n\t * @return method used to split regions\n\t */\n\tint getSplitMethod()\n\t{\n\t\treturn splitMethod;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/CachedFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport parser.ast.Expression;\nimport prism.PrismException;\n\n/**\n * Function representation using cached functions.\n *\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see CachedFunctionFactory\n */\nfinal class CachedFunction extends Function {\n\t/** unique number of cached function this function represents */\n\tprivate int number;\n\t/** factory this function belongs to */\n\tprivate CachedFunctionFactory factory;\n\t\n\t/**\n\t * Constructs a new cached function.\n\t * \n\t * @param factory function factory this function belongs to\n\t * @param number unique number of cached function this function represents\n\t */\n\tCachedFunction(CachedFunctionFactory factory, int number)\n\t{\n\t\tsuper(factory);\n\t\tthis.factory = factory;\n\t\tthis.number = number;\n\t}\n\t\n\t/**\n\t * Returns the unique number of the cached function this function represents. \n\t * \n\t * @return unique number\n\t */\n\tint getNumber()\n\t{\n\t\treturn number;\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn factory.getFunction(number).toString();\n\t}\n\t\n\t@Override\n\tpublic boolean equals(Object obj) {\n\t\tif (!(obj instanceof CachedFunction)) {\n\t\t\treturn false;\n\t\t}\n\t\tCachedFunction function = (CachedFunction) obj;\n\t\treturn number == function.number;\n\t}\n\t\n\t@Override\n\tpublic int hashCode() {\n\t\treturn number;\n\t}\n\t\n\t@Override\n\tpublic Function add(Function other) {\n\t\treturn factory.add(this,  other);\n\t}\n\n\t@Override\n\tpublic Function negate() {\n\t\treturn factory.negate(this);\n\t}\n\n\t@Override\n\tpublic Function multiply(Function other) {\n\t\treturn factory.multiply(this, other);\n\t}\n\n\t@Override\n\tpublic Function divide(Function other) {\n\t\treturn factory.divide(this, other);\n\t}\n\n\t@Override\n\tpublic Function pow(int exp) {\n\t\treturn factory.pow(this, exp);\n\t}\n\n\t@Override\n\tpublic Function star() {\n\t\treturn factory.star(this);\n\t}\n\n\t@Override\n\tpublic Function toConstraint() {\n\t\treturn factory.toConstraint(this);\n\t}\n\n\t@Override\n\tpublic BigRational evaluate(Point point, boolean cancel) {\n\t\treturn factory.evaluate(this, point, cancel);\n\t}\n\n\t@Override\n\tpublic BigRational evaluate(Point point) {\n\t\treturn factory.evaluate(this, point);\n\t}\n\n\t@Override\n\tpublic boolean check(Point point, boolean strict) {\n\t\treturn factory.check(this, point, strict);\n\t}\n\n\t@Override\n\tpublic BigRational asBigRational() {\n\t\treturn factory.asBigRational(this);\n\t}\n\n\t@Override\n\tpublic Expression asExpression() throws PrismException {\n\t\treturn factory.asExpression(this);\n\t}\n\n\t@Override\n\tpublic boolean isNaN() {\n\t\treturn factory.isNaN(this);\n\t}\n\n\t@Override\n\tpublic boolean isInf() {\n\t\treturn factory.isInf(this);\n\t}\n\n\t@Override\n\tpublic boolean isMInf() {\n\t\treturn factory.isMInf(this);\n\t}\n\n\t@Override\n\tpublic boolean isOne() {\n\t\treturn factory.isOne(this);\n\t}\n\n\t@Override\n\tpublic boolean isZero() {\n\t\treturn factory.isZero(this);\n\t}\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn factory.isConstant(this);\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/CachedFunctionFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport parser.ast.Expression;\nimport prism.PrismException;\n\nimport java.util.ArrayList;\nimport java.util.HashMap;\n\n/**\n * Function factory implementing a cache for functions from other factories.\n * This way, each function is only stored in memory once, so as to reduce\n * memory usage and improve speed. This function factory can also use a\n * cache for operations on functions, so that if an operation on the same\n * two functions has already been performed before, the result will be\n * looked up instead of being performed again.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see FunctionFactory\n * @see CachedFunction\n */\nfinal class CachedFunctionFactory extends FunctionFactory {\n\t/**\n\t * Represents an entry of the operation cache.\n\t *\n\t * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n\t */\n\tprivate class OpCacheKey\n\t{\n\t\t/** first operand */\n\t\tCachedFunction first;\n\t\t/** second operand */\n\t\tCachedFunction second;\n\t\t\n\t\t/**\n\t\t * Construct a new operation cache entry.\n\t\t * \n\t\t * @param first first operand\n\t\t * @param second second operand\n\t\t */\n\t\tpublic OpCacheKey(CachedFunction first, CachedFunction second)\n\t\t{\n\t\t\tif (second.getNumber() > first.getNumber()) {\n\t\t\t\tCachedFunction swap = first;\n\t\t\t\tfirst = second;\n\t\t\t\tsecond = swap;\n\t\t\t}\n\t\t\tthis.first = first;\n\t\t\tthis.second = second;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean equals(Object obj) {\n\t\t\tOpCacheKey key = (OpCacheKey) obj;\n\t\t\treturn first == key.first && second == key.second;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic int hashCode() {\n\t\t\tint hash = first.getNumber();\n\t\t\thash = second.getNumber() + (hash << 6) + (hash << 16) - hash;\n\t\t\treturn hash;\n\t\t}\n\t}\n\t\n\t/** function factory of which we cache functions */\n\tprivate FunctionFactory context;\n\t/** maps each function from {@code context} to a unique integer */\n\tprivate HashMap<Function, Integer> functionToNumber;\n\t/** maps each integer to function from {@code context}, cf. also {@code functionToNumber} */\n\tprivate ArrayList<Function> functions;\n\t/** list of all function of this function factory */ \n\tprivate ArrayList<CachedFunction> cachedFunctions;\n\t/** next new function will be assigned this number */\n\tprivate int nextFunctionNumber;\n\t/** function representing one (1) */\n\tprivate CachedFunction one;\n\t/** function representing zero (0) */\n\tprivate CachedFunction zero;\n\t/** true iff operation cache is to be used */\n\tprivate boolean useOpCache;\n\t/** cache for additions (and indirectly subtractions) */\t\t\n\tprivate HashMap<OpCacheKey, CachedFunction> addCache;\n\t/** cache for multiplications (and indirectly divisions) */\t\n\tprivate HashMap<OpCacheKey, CachedFunction> multCache;\n\t/** cache for star operation */\n\tprivate HashMap<CachedFunction, CachedFunction> starCache;\n\t\n\t/**\n\t * Constructs a new cached function factory.\n\t * Will cache functions of the given {@code context}.\n\t * \n\t * @param context function factory to cache functions of\n\t */\n\tpublic CachedFunctionFactory(FunctionFactory context) {\n\t\tsuper(context.parameterNames, context.lowerBounds, context.upperBounds);\n\t\tthis.context = context;\n\t\tfunctionToNumber = new HashMap<Function, Integer>();\n\t\tcachedFunctions = new ArrayList<CachedFunction>();\n\t\tfunctions = new ArrayList<Function>();\n\t\tnextFunctionNumber = 0;\n\t\tone = makeUnique(context.getOne());\n\t\tzero = makeUnique(context.getZero());\n\t\taddCache = new HashMap<OpCacheKey, CachedFunction>();\n\t\tmultCache = new HashMap<OpCacheKey, CachedFunction>();\n\t\tstarCache = new HashMap<CachedFunction, CachedFunction>();\n\t\tuseOpCache = true;\n\t}\n\t\n\t/**\n\t * Returns whether operations cache is used.\n\t * \n\t * @return true iff operation cache is used\n\t */\n\tboolean isUseOpCache()\n\t{\n\t\treturn useOpCache;\n\t}\n\t\n\t/**\n\t * Returns the unique integer representing the given function.\n\t * In case the function already exists in the function cache, returns\n\t * the assigned integer. Otherwise, inserts function in the cache and\n\t * returns the newly assigned integer.\n\t * \n\t * @param function function to return unique integer of\n\t * @return unique integer representing function\n\t */\n\tprivate CachedFunction makeUnique(Function function)\n\t{\n\t\tInteger number = functionToNumber.get(function);\n\t\tif (number != null) {\n\t\t\treturn cachedFunctions.get(number);\n\t\t} else {\n\t\t\tCachedFunction cachedFunction = new CachedFunction(this, nextFunctionNumber);\n\t\t\tfunctionToNumber.put(function, nextFunctionNumber);\n\t\t\tcachedFunctions.add(cachedFunction);\n\t\t\tfunctions.add(function);\n\t\t\tnextFunctionNumber++;\n\t\t\treturn cachedFunction;\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns integer with the given unique number.\n\t * \n\t * @param number number of function to return\n\t * @return function with the given number\n\t */\n\tFunction getFunction(int number)\n\t{\n\t\treturn functions.get(number);\n\t}\n\t\n\t@Override\n\tpublic Function getOne()\n\t{\n\t\treturn one;\n\t}\n\n\t@Override\n\tpublic Function getZero()\n\t{\n\t\treturn zero;\n\t}\n\n\tprivate Function getFunctionFromCache(Function cached)\n\t{\n\t\treturn functions.get(((CachedFunction) cached).getNumber());\n\t}\n\t\n\tFunction add(Function cached1, Function cached2)\n\t{\n\t\tFunction result;\n\t\tOpCacheKey opCacheKey = null;\n\t\tif (useOpCache) {\n\t\t\topCacheKey = new OpCacheKey((CachedFunction) cached1, (CachedFunction) cached2);\n\t\t\tresult = addCache.get(opCacheKey);\n\t\t\tif (result != null) {\n\t\t\t\treturn result;\n\t\t\t}\n\t\t}\n\t\tFunction function1 = getFunctionFromCache(cached1);\n\t\tFunction function2 = getFunctionFromCache(cached2);\n\t\tresult = makeUnique(function1.add(function2));\n\t\tif (useOpCache) {\n\t\t\taddCache.put(opCacheKey, (CachedFunction) result);\n\t\t}\n\t\treturn result;\n\t}\n\n\tFunction negate(Function cached)\n\t{\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn makeUnique(function.negate());\n\t}\n\n\tFunction multiply(Function cached1, Function cached2)\n\t{\n\t\tFunction result;\n\t\tOpCacheKey opCacheKey = null;\n\t\tif (useOpCache) {\n\t\t\topCacheKey = new OpCacheKey((CachedFunction) cached1, (CachedFunction) cached2);\n\t\t\tresult = multCache.get(opCacheKey);\n\t\t\tif (result != null) {\n\t\t\t\treturn result;\n\t\t\t}\n\t\t}\n\t\tFunction function1 = getFunctionFromCache(cached1);\n\t\tFunction function2 = getFunctionFromCache(cached2);\n\t\tresult = makeUnique(function1.multiply(function2));\n\t\tif (useOpCache) {\n\t\t\tmultCache.put(opCacheKey, (CachedFunction) result);\n\t\t}\n\t\treturn result;\n\t}\n\n\tFunction divide(Function cached1, Function cached2)\n\t{\n\t\tFunction function1 = getFunctionFromCache(cached1);\n\t\tFunction function2 = getFunctionFromCache(cached2);\n\t\treturn makeUnique(function1.divide(function2));\n\t}\n\n\tFunction pow(Function cached1, int exp)\n\t{\n\t\tFunction function1 = getFunctionFromCache(cached1);\n\t\treturn makeUnique(function1.pow(exp));\n\t}\n\n\tFunction star(Function cached) {\n\t\tFunction result;\n\t\tif (useOpCache) {\n\t\t\tresult = starCache.get(cached);\n\t\t\tif (result != null) {\n\t\t\t\treturn result;\n\t\t\t}\n\t\t}\n\t\tFunction function = getFunctionFromCache(cached);\n\t\tresult = makeUnique(function.star());\n\t\tif (useOpCache) {\n\t\t\tstarCache.put((CachedFunction) cached, (CachedFunction) result);\n\t\t}\n\t\treturn result;\n\t}\n\n\tFunction toConstraint(CachedFunction cachedFunction)\n\t{\n\t\treturn getFunctionFromCache(cachedFunction).toConstraint();\n\t}\n\n\tpublic BigRational evaluate(CachedFunction cached, Point point, boolean cancel)\n\t{\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.evaluate(point, cancel);\n\t}\n\t\n\tpublic BigRational evaluate(CachedFunction cached, Point point)\n\t{\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.evaluate(point);\n\t}\n\n\t@Override\n\tpublic Function fromBigRational(BigRational from)\n\t{\n\t\tFunction fn = context.fromBigRational(from);\n\t\treturn makeUnique(fn);\n\t}\n\n\tpublic BigRational asBigRational(CachedFunction cached) {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.asBigRational();\n\t}\n\n\tpublic Expression asExpression(CachedFunction cached) throws PrismException {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.asExpression();\n\t}\n\n\tpublic boolean check(CachedFunction cached, Point point,\n\t\t\tboolean strict) {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.check(point, strict);\n\t}\n\n\tpublic boolean isNaN(CachedFunction cached) {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.isNaN();\n\t}\n\n\tpublic boolean isInf(CachedFunction cached) {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.isInf();\n\t}\n\n\tpublic boolean isMInf(CachedFunction cached) {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.isMInf();\n\t}\n\n\tpublic boolean isOne(CachedFunction cached) {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.isOne();\n\t}\n\n\tpublic boolean isZero(CachedFunction cached) {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.isZero();\n\t}\n\n\tpublic boolean isConstant(CachedFunction cached) {\n\t\tFunction function = getFunctionFromCache(cached);\n\t\treturn function.isConstant();\n\t}\n\n\t@Override\n\tpublic Function getNaN() {\n\t\treturn makeUnique(context.getNaN());\n\t}\n\n\t@Override\n\tpublic Function getInf() {\n\t\treturn makeUnique(context.getInf());\n\t}\n\n\t@Override\n\tpublic Function getMInf() {\n\t\treturn makeUnique(context.getMInf());\n\t}\n\n\t@Override\n\tpublic Function getVar(int var) {\n\t\treturn makeUnique(context.getVar(var));\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/ConstraintChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.HashMap;\n\n/**\n * Checks if functions are (strictly) larger than zero in whole region.\n * This class implements only an approximate check. This means, that\n * functions are only evaluated in a finite number of points, so that it\n * is unlikely but not impossible that there are other points in the\n * region which are below (or equal) to zero. Derived classes might\n * use a constraint solver to guarantee validity of this check.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nclass ConstraintChecker {\n\tprivate boolean usedUnsoundCheck = false;\n\n\t/**\n\t * Class to store keys for the cache of the decision procedure.\n\t */\n\tclass DecisionEntryKey {\n\t\t/** constraint to be stored (representing \"constraint >=/> 0\") */\n\t\tFunction constraint;\n\t\t/** whether constraint should be strictly larger than zero */\n\t\tboolean strict;\n\t\t\n\t\t@Override\n\t\tpublic boolean equals(Object obj) {\n\t\t\tif (!(obj instanceof DecisionEntryKey)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tDecisionEntryKey other = (DecisionEntryKey) obj;\n\t\t\treturn this.constraint.equals(other.constraint) && (this.strict == other.strict);\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic int hashCode() {\n\t\t\tint hash = 0;\n\t\t\thash = constraint.hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t\thash = (strict ? 13 : 17) + (hash << 6) + (hash << 16) - hash;\n\n\t\t\treturn hash;\n\t\t}\n\t}\n\t\n\t/**\n\t * Class to store keys for the cache of the decision procedure.\n\t */\n\tclass DecisionEntryValue {\n\t\t/** region this result is valid for */\n\t\tRegion region;\n\t\t/** result, that is whether corresponding constraint holds in region */\n\t\tboolean result;\n\t\t\n\t\t@Override\n\t\tpublic boolean equals(Object obj) {\n\t\t\tif (!(obj instanceof DecisionEntryValue)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tDecisionEntryValue other = (DecisionEntryValue) obj;\n\t\t\treturn this.region.equals(other.region) && (this.result == other.result);\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic int hashCode() {\n\t\t\tint hash = 0;\n\t\t\thash = region.hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t\thash = (result ? 13 : 17) + (hash << 6) + (hash << 16) - hash;\n\n\t\t\treturn hash;\n\t\t}\n\t}\n\n\t/** number of random points to evaluate in decision procedure */\n\tprivate int numRandomPoints;\n\t/** decision cache */\n\tprotected HashMap<DecisionEntryKey,ArrayList<DecisionEntryValue>> decisions;\n\t\n\t/**\n\t * Constructs a new constraint checker.\n\t * \n\t * @param numRandomPoints number of inner points to evaluate in addition to border points\n\t */\n\tConstraintChecker(int numRandomPoints) {\n\t\tthis.numRandomPoints = numRandomPoints;\n\t\tdecisions = new HashMap<DecisionEntryKey,ArrayList<DecisionEntryValue>>();\n\t}\n\n\t/**\n\t * Main decision check.\n\t * In this class, does nothing. Derived class could override this method\n\t * for instance by calling an external decision procedure, use a library\n\t * to decide validity in a given region, etc.\n\t * \n\t * @param region region for which to check validity of constraint\n\t * @param constraint constraint to check (whether >=/> 0)\n\t * @param strict true iff \">\" shold be checked rathern than \">=\"\n\t * @return true\n\t */\n\tboolean mainCheck(Region region, Function constraint, boolean strict)\n\t{\n\t\tusedUnsoundCheck = true;\n\t\treturn true;\n\t}\n\n\t/**\n\t * Does a quick pre-check by evaluating constraint at random points.\n\t * \n\t * @param region region for which to check validity of constraint\n\t * @param constraint constraint to check (whether >=/> 0)\n\t * @param strict true iff \">\" shold be checked rathern than \">=\"\n\t * @return true if no counterexamples to validity found\n\t */\n\tboolean preCheck(Region region, Function constraint, boolean strict)\n\t{\n\t\tArrayList<Point> points = region.specialPoints();\n\t\tfor (Point point : points) {\n\t\t\tif (!constraint.check(point, strict)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\tfor (int pointNr = 0; pointNr < numRandomPoints; pointNr++) {\n\t\t\tif (!constraint.check(region.randomPoint(), strict)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn true;\n\t}\n\t\n\t/**\n\t * Checks whether constraint holds in given region.\n\t * \n\t * @param region region for which to check validity of constraint\n\t * @param constraint constraint to check (whether >=/> 0)\n\t * @param strict true iff \">\" shold be checked rathern than \">=\"\n\t * @return true iff function values are (strictly) larger than zero in whole region \n\t */\n\tboolean check(Region region, Function constraint, boolean strict)\n\t{\n\t\t// handle case where the constraint is a constant number\n\t\tif (constraint.isConstant()) {\n\t\t\tBigRational value = constraint.asBigRational();\n\n\t\t\tif (value.isNaN())\n\t\t\t\treturn false;\n\n\t\t\tif (strict) {\n\t\t\t\treturn value.signum() == 1;\n\t\t\t} else {\n\t\t\t\treturn value.signum() >= 0;\n\t\t\t}\n\t\t}\n\n\t\tFunction constr = constraint.toConstraint();\n\t\tDecisionEntryKey key = new DecisionEntryKey();\n\t\tkey.constraint = constr;\n\t\tkey.strict = strict;\n\t\tArrayList<DecisionEntryValue> entries = decisions.get(key);\n\t\tif (entries != null) {\n\t\t\tfor (DecisionEntryValue entry : entries) {\n\t\t\t\tif (entry.region.contains(region)) {\n\t\t\t\t\tif (entry.result) {\n\t\t\t\t\t\treturn true;\n\t\t\t\t\t} else if (entry.region.equals(region)) {\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tboolean result = preCheck(region, constr, strict);\n\t\tif (result) {\n\t\t\tresult = mainCheck(region, constr, strict);\n\t\t}\n\n\t\tentries = decisions.get(key);\n\t\tif (entries == null) {\n\t\t\tentries = new ArrayList<DecisionEntryValue>();\n\t\t\tdecisions.put(key, entries);\n\t\t}\n\t\tDecisionEntryValue entry = new DecisionEntryValue();\n\t\tentry.region = region;\n\t\tentry.result = result;\n\t\tentries.add(entry);\n\n\t\treturn result;\n\t}\n\n\tpublic boolean unsoundCheckWasUsed()\n\t{\n\t\treturn usedUnsoundCheck;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/param/DagFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport parser.ast.Expression;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\n/**\n * TODO implement completely\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\npublic class DagFunction extends Function {\n\tprivate DagFunctionFactory dagFactory;\n\tprivate DagOperator num;\n\tprivate DagOperator den;\n\tint type;\n\tfinal static int NORMAL = 0;\n\tfinal static int INF = 1;\n\tfinal static int MINF = 2;\n\tfinal static int NAN = 3;\n\t\n\tpublic DagFunction(FunctionFactory factory, DagOperator num, DagOperator den) {\n\t\tsuper(factory);\n\t\tdagFactory = (DagFunctionFactory) factory;\n\t\tthis.num = num;\n\t\tthis.den = den;\n\t\tthis.type = NORMAL;\n\t}\n\t\n\tpublic DagFunction(FunctionFactory factory, int type) {\n\t\tsuper(factory);\n\t\tthis.type = type;\n\t\tnum = null;\n\t\tden = null;\n\t}\t\n\n\tpublic DagOperator getNum() {\n\t\treturn num;\n\t}\n\t\n\tpublic DagOperator getDen() {\n\t\treturn den;\n\t}\n\t\n\t@Override\n\tpublic boolean equals(Object obj) {\n\t\tif (!(obj instanceof DagFunction)) {\n\t\t\treturn false;\n\t\t}\n\t\tDagFunction other = (DagFunction) obj;\n\t\tif (this.type != NORMAL) {\n\t\t\treturn this.type == other.type;\n\t\t}\n\t\tif (other.type != NORMAL) {\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\tBigRational thisRat = new BigRational(this.num.getCValue(), this.den.getCValue());\n\t\tBigRational otherRat = new BigRational(other.num.getCValue(), other.den.getCValue());\n\t\treturn thisRat.equals(otherRat);\n\t}\n\t\n\t@Override\n\tpublic int hashCode() {\n\t\tif (type != NORMAL) {\n\t\t\treturn type;\n\t\t}\n\t\tBigRational thisRat = new BigRational(num.getCValue(), den.getCValue());\n\t\treturn thisRat.hashCode();\n\t}\n\n\t\n\t@Override\n\tpublic Function add(Function other) {\n\t\treturn dagFactory.add(this, (DagFunction) other);\n\t}\n\n\t@Override\n\tpublic Function negate() {\n\t\treturn dagFactory.negate(this);\n\t}\n\t\n\t@Override\n\tpublic Function subtract(Function other) {\n\t\treturn dagFactory.subtract(this, (DagFunction) other);\n\t}\n\n\t@Override\n\tpublic Function multiply(Function other) {\n\t\treturn dagFactory.multiply(this, (DagFunction) other);\n\t}\n\n\t@Override\n\tpublic Function divide(Function other) {\n\t\treturn dagFactory.divide(this, (DagFunction) other);\n\t}\n\n\t@Override\n\tpublic Function pow(int exp) {\n\t\tthrow new RuntimeException(\"DagFunction does not support powers\");\n\t}\n\n\t@Override\n\tpublic Function star() {\n\t\treturn dagFactory.star(this);\n\t}\n\n\t@Override\n\tpublic Function toConstraint() {\n\t\treturn dagFactory.toConstraint(this);\n\t}\n\n\t@Override\n\tpublic BigRational evaluate(Point point, boolean cancel) {\n\t\tBigRational result = dagFactory.evaluate(this, point, cancel);\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic BigRational asBigRational() {\n\t\tswitch (type) {\n\t\tcase NORMAL:\n\t\t\treturn dagFactory.asBigRational(this);\n\t\tcase NAN:\n\t\t\treturn BigRational.NAN;\n\t\tcase INF:\n\t\t\treturn BigRational.INF;\n\t\tcase MINF:\n\t\t\treturn BigRational.MINF;\n\t\t}\n\t\tthrow new RuntimeException(\"Illegal type\");\n\t}\n\n\t@Override\n\tpublic Expression asExpression() throws PrismException {\n\t\tthrow new PrismNotSupportedException(\"DagFunction does not yet generate Expressions\");\n\t}\n\n\t@Override\n\tpublic boolean isNaN() {\n\t\treturn type == NAN;\n\t}\n\n\t@Override\n\tpublic boolean isInf() {\n\t\treturn type == INF;\n\t}\n\n\t@Override\n\tpublic boolean isMInf() {\n\t\treturn type == MINF;\n\t}\n\n\t@Override\n\tpublic boolean isOne() {\n\t\treturn dagFactory.isOne(this);\n\t}\n\n\t@Override\n\tpublic boolean isZero() {\n\t\treturn dagFactory.isZero(this);\n\t}\n\t\n\t@Override\n\tpublic String toString() {\n\t\treturn dagFactory.toString(this);\n\t}\n\n\tpublic int getType() {\n\t\treturn type;\n\t}\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\tif (type != NORMAL)\n\t\t\treturn true;\n\n\t\treturn dagFactory.isConstant(num) && dagFactory.isConstant(den);\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/DagFunctionFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.math.BigInteger;\nimport java.util.HashMap;\nimport java.util.Random;\n\n/**\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * TODO complete once needed\n */\nclass DagFunctionFactory extends FunctionFactory {\n\tprivate class Number extends DagOperator {\n\t\tprivate BigInteger number;\n\t\tNumber(BigInteger number) {\n\t\t\tsuper(number);\n\t\t\tthis.number = number;\n\t\t}\n\t\tBigInteger getNumber() {\n\t\t\treturn number;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic String toString() {\n\t\t\treturn number.toString();\n\t\t}\n\t}\n\t\n\tprivate class Variable extends DagOperator {\n\t\tprivate int variable;\n\t\tVariable(int variable) {\n\t\t\tsuper(randomPosition.getDimension(variable).getNum());\n\t\t\tthis.variable = variable;\n\t\t}\n\t\tint getVariable() {\n\t\t\treturn variable;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic String toString() {\n\t\t\treturn parameterNames[variable];\n\t\t}\n\t}\n\n\tprivate class Negate extends DagOperator {\n\t\tprivate DagOperator what;\n\t\tNegate(DagOperator what) {\n\t\t\tsuper(what.getCValue().negate());\n\t\t\tthis.what = what;\n\t\t}\n\t\tDagOperator getWhat() {\n\t\t\treturn what;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic String toString() {\n\t\t\treturn \"-(\" + what.toString() + \")\";\n\t\t}\n\t}\n\n\tprivate class Add extends DagOperator {\n\t\tprivate DagOperator op1;\n\t\tprivate DagOperator op2;\n\t\tAdd(DagOperator op1, DagOperator op2) {\n\t\t\tsuper(op1.getCValue().add(op2.getCValue()));\n\t\t\tthis.op1 = op1;\n\t\t\tthis.op2 = op2;\n\t\t}\n\t\tDagOperator getOp1() {\n\t\t\treturn op1;\n\t\t}\n\t\tDagOperator getOp2() {\n\t\t\treturn op2;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic String toString() {\n\t\t\treturn \"(\" + op1.toString() + \"+\" + op2.toString() + \")\";\n\t\t}\n\t}\n\t\n\tprivate class Multiply extends DagOperator {\n\t\tprivate DagOperator op1;\n\t\tprivate DagOperator op2;\n\t\tMultiply(DagOperator op1, DagOperator op2) {\n\t\t\tsuper(op1.getCValue().multiply(op2.getCValue()));\n\n\t\t\tthis.op1 = op1;\n\t\t\tthis.op2 = op2;\n\t\t}\n\t\tDagOperator getOp1() {\n\t\t\treturn op1;\n\t\t}\n\t\tDagOperator getOp2() {\n\t\t\treturn op2;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic String toString() {\n\t\t\treturn \"(\" + op1.toString() + \"*\" + op2.toString() + \")\";\n\t\t}\n\t}\n\t\n\tprivate Point randomPosition;\n\tprivate HashMap<DagOperator,DagOperator> polynomials;\n\tprivate DagOperator zeroOp;\n\tprivate DagOperator oneOp;\n\tprivate DagFunction[] parameters;\n\tprivate DagFunction zero;\n\tprivate DagFunction one;\n\tprivate DagFunction nan;\n\tprivate DagFunction inf;\n\tprivate DagFunction minf;\n\tprivate HashMap<DagFunction,DagFunction> functions;\n//\tprivate boolean negateToInner;\n\t\n\tpublic DagFunctionFactory(String[] parameterNames, BigRational[] lowerBounds, BigRational[] upperBounds, double maxProbWrong, boolean negateToInner) {\n\t\tsuper(parameterNames, lowerBounds, upperBounds);\n\t\tRandom random = new Random();\n\t\tBigRational[] randomPosArr = new BigRational[parameterNames.length];\n\t\tint numRandomBits = (int) Math.ceil(Math.log(parameterNames.length / maxProbWrong) / Math.log(2));\n\t\tfor (int dim = 0; dim < parameterNames.length; dim++) {\n\t\t\tBigInteger num = new BigInteger(numRandomBits, random);\n\t\t\trandomPosArr[dim] = new BigRational(num, BigInteger.ONE);\n\t\t}\n\t\trandomPosition = new Point(randomPosArr);\n\n\t\tpolynomials = new HashMap<DagOperator,DagOperator>();\n\t\tfunctions = new HashMap<DagFunction,DagFunction>();\n\t\tzeroOp = new Number(BigInteger.ZERO);\n\t\tpolynomials.put(zeroOp,zeroOp);\n\t\toneOp = new Number(BigInteger.ONE);\n\t\tpolynomials.put(oneOp,oneOp);\n\t\tzero = new DagFunction(this, zeroOp, oneOp);\n\t\tfunctions.put(zero,zero);\n\t\tone = new DagFunction(this, oneOp, oneOp);\n\t\tfunctions.put(one,one);\n\t\tnan = new DagFunction(this, DagFunction.NAN);\n\t\tfunctions.put(nan,nan);\n\t\tinf = new DagFunction(this, DagFunction.INF);\n\t\tfunctions.put(inf,inf);\n\t\tminf = new DagFunction(this, DagFunction.MINF);\n\t\tfunctions.put(minf,minf);\n\t\tparameters = new DagFunction[parameterNames.length];\n\t\tfor (int varNr = 0; varNr < parameterNames.length; varNr++) {\n\t\t\tDagOperator paramOp = new Variable(varNr);\n\t\t\tpolynomials.put(paramOp,paramOp);\n\t\t\tparameters[varNr] = new DagFunction(this, paramOp, oneOp);\n\t\t\tfunctions.put(parameters[varNr],parameters[varNr]);\n\t\t}\n//\t\tthis.negateToInner = negateToInner;\n\t}\n\t\n\t@Override\n\tpublic Function getZero() {\n\t\treturn zero;\n\t}\n\t\n\t@Override\n\tpublic Function getOne() {\n\t\treturn one;\n\t}\n\n\t@Override\n\tpublic Function getNaN() {\n\t\treturn nan;\n\t}\n\n\t@Override\n\tpublic Function getInf() {\n\t\treturn inf;\n\t}\n\n\t@Override\n\tpublic Function getMInf() {\n\t\treturn minf;\n\t}\n\t\n\tprivate DagOperator makeUnique(DagOperator op) {\n\t\tDagOperator foundOp = polynomials.get(op);\n\t\tif (foundOp == null) {\n\t\t\tfoundOp = op;\n\t\t\tpolynomials.put(foundOp, foundOp);\n\t\t}\n\t\treturn foundOp;\n\t}\n\t\n\tprivate DagFunction makeUnique(DagFunction fn) {\n\t\tDagFunction foundFn = functions.get(fn);\n\t\tif (foundFn == null) {\n\t\t\tfoundFn = fn;\n\t\t\tfunctions.put(foundFn, foundFn);\n\t\t}\n\t\treturn foundFn;\n\t}\n\t\n\t@Override\n\tpublic Function fromBigRational(BigRational bigRat) {\n\t\tif (bigRat.isSpecial()) {\n\t\t\tif (bigRat.isNaN()) {\n\t\t\t\treturn getNaN();\n\t\t\t} else if (bigRat.isInf()) {\n\t\t\t\treturn getInf();\n\t\t\t} else if (bigRat.isMInf()) {\n\t\t\t\treturn getMInf();\n\t\t\t} else {\n\t\t\t\tthrow new RuntimeException(\"Unknown special value\");\n\t\t\t}\n\t\t}\n\t\t// normal:\n\t\tbigRat = bigRat.cancel();\n\t\tDagOperator num = new Number(bigRat.getNum());\n\t\tnum = makeUnique(num);\n\t\tDagOperator den = new Number(bigRat.getDen());\n\t\tden = makeUnique(den);\n\t\tDagFunction result = new DagFunction(this,  num, den);\n\t\treturn makeUnique(result);\n\t}\n\n\t@Override\n\tpublic Function getVar(int var) {\n\t\treturn parameters[var];\n\t}\n\n\tprivate DagOperator opMultiply(DagOperator op1, DagOperator op2) {\n\t\treturn makeUnique(new Multiply(op1, op2));\n\t}\n\t\n\tprivate DagOperator opAdd(DagOperator op1, DagOperator op2) {\n\t\treturn makeUnique(new Add(op1, op2));\n\t}\n\t\n\tprivate DagOperator opNegate(DagOperator op) {\n\t\treturn makeUnique(new Negate(op));\n\t}\n\t\n\tpublic Function add(DagFunction op1, DagFunction op2) {\n\t\tDagOperator num = opAdd(opMultiply(op1.getNum(), op2.getDen()),\n\t\t\t\topMultiply(op1.getDen(), op2.getNum()));\n\t\tDagOperator den = opMultiply(op1.getDen(), op2.getDen());\n\t\treturn makeUnique(new DagFunction(this, num,  den));\n\t}\n\n\tpublic DagFunction negate(DagFunction dagFunction) {\n\t\tDagOperator neg = opNegate(dagFunction.getNum());\n\t\treturn makeUnique(new DagFunction(this, neg, dagFunction.getDen()));\n\t}\n\t\n\tpublic Function subtract(DagFunction op1, DagFunction op2) {\n\t\tDagFunction negOther = negate(op2);\n\t\treturn add(op1, negOther);\n\t}\n\n\tpublic Function multiply(DagFunction op1, DagFunction op2) {\n\t\tDagOperator num = opMultiply(op1.getNum(), op2.getNum());\n\t\tDagOperator den = opMultiply(op1.getDen(), op2.getDen());\n\t\treturn makeUnique(new DagFunction(this, num, den));\n\t}\n\n\tpublic Function divide(DagFunction op1, DagFunction op2) {\n\t\tDagOperator num = opMultiply(op1.getNum(), op2.getDen());\n\t\tDagOperator den = opMultiply(op1.getDen(), op2.getNum());\n\t\treturn makeUnique(new DagFunction(this, num, den));\n\t}\n\n\tpublic Function star(DagFunction op) {\n\t\tDagOperator num = op.getDen();\n\t\tDagOperator den = opAdd(op.getDen(), opNegate(op.getNum()));\n\t\treturn makeUnique(new DagFunction(this, num, den));\n\t}\n\n\t// TODO fix following\n\tpublic Function toConstraint(DagFunction op) {\n\t\tDagOperator num = op.getNum();\n\t\tDagOperator den = oneOp;\n\t\treturn makeUnique(new DagFunction(this, num, den));\n\t}\n\n\t// TODO use cache for faster evaluation\n\tprivate BigRational evaluate(DagOperator op, Point point) {\n\t\tif (op instanceof Number) {\n\t\t\tNumber opNum = (Number) op;\n\t\t\treturn new BigRational(opNum.getNumber());\n\t\t} else if (op instanceof Variable) {\n\t\t\tVariable opVar = (Variable) op;\n\t\t\treturn point.getDimension(opVar.getVariable());\n\t\t} else if (op instanceof Negate) {\n\t\t\tNegate opNegate = (Negate) op;\n\t\t\treturn evaluate(opNegate.getWhat(), point).negate();\n\t\t} else if (op instanceof Add) {\n\t\t\tAdd opAdd = (Add) op;\n\t\t\treturn evaluate(opAdd.getOp1(), point).add(evaluate(opAdd.getOp2(), point));\n\t\t} else if (op instanceof Multiply) {\n\t\t\tMultiply opMultiply = (Multiply) op;\n\t\t\treturn evaluate(opMultiply.getOp1(), point).multiply(evaluate(opMultiply.getOp2(), point));\n\t\t} else {\n\t\t\tthrow new RuntimeException(\"invalid operator\");\n\t\t}\n\t}\n\t\n\tpublic BigRational evaluate(DagFunction op, Point point, boolean cancel) {\n\t\tif (op.getType() == DagFunction.NAN) {\n\t\t\treturn BigRational.NAN;\n\t\t}\n\t\treturn evaluate(op.getNum(), point).divide(evaluate(op.getDen(), point));\n\t}\n\n\tpublic BigRational asBigRational(DagFunction op) {\n\t\tBigRational[] point = new BigRational[parameterNames.length];\n\t\tfor (int i = 0; i < parameterNames.length; i++) {\n\t\t\tpoint[i] = BigRational.ZERO;\n\t\t}\n\t\treturn evaluate(op, new Point(point), true);\n\t}\n\n\tpublic boolean isOne(DagFunction op) {\n\t\treturn op == one;\n\t}\n\n\tpublic boolean isZero(DagFunction op) {\n\t\treturn op == zero;\n\t}\n\n\t/**\n\t * Returns true if the tree rooted in {@code op}\n\t * is guaranteed to represent a constant value.\n\t */\n\tpublic boolean isConstant(DagOperator op) {\n\t\tif (op instanceof Number) {\n\t\t\treturn true;\n\t\t} else if (op instanceof Variable) {\n\t\t\treturn false;\n\t\t} else if (op instanceof Negate) {\n\t\t\tNegate opNegate = (Negate) op;\n\t\t\treturn isConstant(opNegate.getWhat());\n\t\t} else if (op instanceof Add) {\n\t\t\tAdd opAdd = (Add) op;\n\t\t\treturn isConstant(opAdd.getOp1()) && isConstant(opAdd.getOp2());\n\t\t} else if (op instanceof Multiply) {\n\t\t\tMultiply opMultiply = (Multiply) op;\n\t\t\treturn isConstant(opMultiply.getOp1()) && isConstant(opMultiply.getOp2());\n\t\t} else {\n\t\t\tthrow new RuntimeException(\"invalid operator\");\n\t\t}\n\t}\n\n\tpublic String toString(DagFunction op) {\n\t\treturn \"(\" + op.getNum().toString() + \")/(\" + op.getDen().toString() + \")\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/DagOperator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.math.BigInteger;\n\n/**\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nabstract class DagOperator {\n\tprivate BigInteger cValue;\n\tDagOperator(BigInteger cValue) {\n\t\tthis.cValue = cValue;\n\t}\n\tBigInteger getCValue() {\n\t\treturn cValue;\n\t}\n\t\n\t@Override\n\tpublic int hashCode() {\n\t\treturn cValue.hashCode();\n\t}\n\t\n\t@Override\n\tpublic boolean equals(Object obj) {\n\t\tif (!(obj instanceof DagOperator)) {\n\t\t\treturn false;\n\t\t}\n\t\tDagOperator other = (DagOperator) obj;\n\t\treturn this.cValue.equals(other.cValue);\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/Function.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport parser.ast.Expression;\nimport prism.PrismException;\n\n/**\n * Represents a rational function.\n * Allows for the usual operations (addition, multiplication, etc.) which\n * can be applied to rational functions, resulting in another rational\n * function. It also implements the special operator {@code star}, which\n * represents to value 1/(1-fn). Although this operation could be implemented\n * by standard operations, implementations of this class might choose a more\n * efficient solution, as this operation will be used quite often. Each\n * {@code Function} has a link to a corresponding {@code FunctionFactory},\n * which maintains objects shared by all rational functions with which it\n * can be combined by mathematical operations.\n * \n * Functions shall be created using either the corresponding\n * {@code FunctionFactory} or by mathematical operations. They are immutable\n * objects, and cannot be changed after their creation.\n * \n * In addition to rational functions, an object of this type can also represent\n * the special value not-a-number, negative and positive infinity.\n * \n * It is assumed that the signums of the denominators of the rational function\n * the objects of this class represent do not change within the parameter\n * range specified in the corresponding {@code FunctionFactory}.\n * \n * @see FunctionFactory\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\npublic abstract class Function extends StateValue\n{\n\t/** function factory for this function */\n\tprotected FunctionFactory factory;\n\n\t/**\n\t * Creates a new function.\n\t * For internal use.\n\t * \n\t * @param factory factory used for this function\n\t */\n\tprotected Function(FunctionFactory factory)\n\t{\n\t\tthis.factory = factory;\n\t}\n\n\t/**\n\t * Adds {@code other} to this function.\n\t * \n\t * @param other function to add to this function\n\t * @return sum of {@code} this and {@other}\n\t */\n\tpublic abstract Function add(Function other);\n\n\t/**\n\t * Negates this rational function.\n\t * \n\t * @return negated rational function.\n\t */\n\tpublic abstract Function negate();\n\n\t/**\n\t * Multiplies {@code other} with this function.\n\t * \n\t * @param other function to multiply with this function\n\t * @return product of {@code} this and {@other}\n\t */\n\tpublic abstract Function multiply(Function other);\n\n\t/**\n\t * Divides this function by {@code other}.\n\t * \n\t * @param other function to divide this function by\n\t * @return {@code this} divided by {@other}\n\t */\n\tpublic abstract Function divide(Function other);\n\n\t/**\n\t * Raises this function to the power {@code exp}.\n\t *\n\t * @param exp integer exponent\n\t * @return {@code this} to the power {@code exp}\n\t */\n\tpublic abstract Function pow(int exp);\n\n\t/**\n\t * Performs the {@code star} operation with this function.\n\t * The value of the result is equal to 1/(1-{@code this}).\n\t * It might however be represented in a different way than the\n\t * function which would be obtained if this result were to be computed\n\t * using subtraction and division.\n\t * \n\t * @return result of star operation\n\t */\n\tpublic abstract Function star();\n\n\t/**\n\t * Returns a simplified version for constraint checking.\n\t * The function returned shall be a polynomial which is above/equal to\n\t * zero for the same parameter valuations as the original function.\n\t * It might evaluate to different values otherwise. This function is\n\t * intended to prepare input to constraint solvers, which sometimes\n\t * cannot handle division and also otherwise perform better when applied\n\t * to less complex functions. \n\t * \n\t * @return simplified form for constraint checking\n\t */\n\tpublic abstract Function toConstraint();\n\n\t/**\n\t * Evaluate this function at a given point.\n\t * The {@code point} represents an evaluation of the parameters, with\n\t * values assigned to parameters according to their order as given in the\n\t * {@code FunctionFactory}.\n\t * \n\t * @param point parameter evaluation to evaluate\n\t * @param cancel whether result shall be enforced to be coprime\n\t * @return value at the given parameter evaluation\n\t */\n\tpublic abstract BigRational evaluate(Point point, boolean cancel);\n\n\t/**\n\t * Returns a BigRational representing the same number as this object.\n\t * Only works of this function is actually a rational number. Otherwise,\n\t * a numeric runtime exception might result.\n\t * \n\t * @return BigRational representation of this function\n\t */\n\tpublic abstract BigRational asBigRational();\n\n\t/**\n\t * Returns an Expression representing this object.\n\t *\n\t * @return Expression representation of this function\n\t */\n\tpublic abstract Expression asExpression() throws PrismException;\n\n\t/**\n\t * Returns true iff this function represents not-a-number.\n\t * @return true iff this function represents not-a-number\n\t */\n\tpublic abstract boolean isNaN();\n\n\t/**\n\t * Returns true iff this function represents positive infinity.\n\t * @return true iff this function represents positive infinity\n\t */\n\tpublic abstract boolean isInf();\n\n\t/**\n\t * Returns true iff this function represents negative infinity.\n\t * @return true iff this function represents negative infinity\n\t */\n\tpublic abstract boolean isMInf();\n\n\t/**\n\t * Returns true iff this function represents the number one.\n\t * @return true iff this function represents the number one \n\t */\n\tpublic abstract boolean isOne();\n\n\t/**\n\t * Returns true iff this function represents the number zero.\n\t * @return true iff this function represents the number zero\n\t */\n\tpublic abstract boolean isZero();\n\n\t/**\n\t * Returns true iff this function is guaranteed to return a constant value.\n\t * @return true iff this function is guaranteed to return a constant value\n\t */\n\tpublic abstract boolean isConstant();\n\n\t/**\n\t * Multiplies {@code byNumber} with this function.\n\t * \n\t * @param number to multiply with this function\n\t * @return product of {@code} this and {@byNumber}\n\t */\n\tpublic Function multiply(int byNumber)\n\t{\n\t\tFunction byFunction = factory.fromLong(byNumber);\n\t\treturn multiply(byFunction);\n\t}\n\n\t/**\n\t * Divides this function by {@code byNumber}.\n\t * \n\t * @param number to divide this function by\n\t * @return this function divided by {@code byNumber}\n\t */\n\tpublic Function divide(int byNumber)\n\t{\n\t\tFunction byFunction = factory.fromLong(byNumber);\n\t\treturn divide(byFunction);\n\t}\n\n\t/**\n\t * Returns the {@code FunctionFactory} of this function.\n\t * \n\t * @return {@code FunctionFactory} of this function\n\t */\n\tpublic FunctionFactory getFactory()\n\t{\n\t\treturn factory;\n\t}\n\n\t/**\n\t * Aubtracts {@code other} from this function.\n\t * \n\t * @param other function to subtract from this function\n\t * @return this function minus {@coce other}\n\t */\n\tpublic Function subtract(Function other)\n\t{\n\t\treturn add(other.negate());\n\t}\n\n\t/**\n\t * Evaluate this function at a given point.\n\t * The {@code point} represents an evaluation of the parameters, with\n\t * values assigned to parameters according to their order as given in the\n\t * {@code FunctionFactory}. The result will be a coprime representation\n\t * of a rational number.\n\t * \n\t * @param point parameter evaluation to evaluate\n\t * @return value at the given parameter evaluation\n\t */\n\tpublic BigRational evaluate(Point point)\n\t{\n\t\treturn evaluate(point, true);\n\t}\n\n\t/**\n\t * Checks whether this function is {@code >= 0} / {@code >0} at the given point.\n\t * \n\t * @param point point to check function at\n\t * @param strict true for strictly larger to zero, false for larger or equal\n\t * @return true iff value at {@code point} is (strictly) larger than zero\n\t */\n\tboolean check(Point point, boolean strict)\n\t{\n\t\tBigRational value = evaluate(point, false);\n\t\tint compare = value.signum();\n\t\treturn strict ? (compare > 0) : (compare >= 0);\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/FunctionFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport parser.EvaluateContext;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.ExpressionFunc;\nimport parser.ast.ExpressionITE;\nimport parser.ast.ExpressionLiteral;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.type.TypeInt;\nimport parser.visitor.ASTTraverse;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismSettings;\n\nimport java.util.HashMap;\n\n/**\n * Generates new functions, stores valid ranges of parameters, etc.\n */\npublic abstract class FunctionFactory\n{\n\t/** names of parameters */\n\tprotected String[] parameterNames;\n\t/** lower bounds of parameters */\n\tprotected BigRational[] lowerBounds;\n\t/** upper bounds of parameters */\n\tprotected BigRational[] upperBounds;\n\t/** maps variable name to index in {@code parameterNames}, @code lowerBounds} and {@code upperBounds} */\n\tprotected HashMap<String, Integer> varnameToInt;\n\t/** for expression evaluation (no constants need, just a convenient way to force exact evaluation */\n\tprotected EvaluateContext ec = EvaluateContext.create(EvaluateContext.EvalMode.EXACT);\n\n\t/**\n\t * Create a FunctionFactory based on PRISM settings and parameter details.\n\t * @param paramNames names of parameters\n\t * @param lowerStr lower bounds of parameters as strings\n\t * @param upperStr upper bounds of parameters as strings\n\t * @param settings PRISM settings\n\t */\n\tpublic static FunctionFactory create(String[] paramNames, String[] lowerStr, String[] upperStr, PrismSettings settings) throws PrismException\n\t{\n\t\t// Convert parameter info from strings to numbers\n\t\tBigRational[] lower = new BigRational[lowerStr.length];\n\t\tBigRational[] upper = new BigRational[upperStr.length];\n\t\tfor (int param = 0; param < lowerStr.length; param++) {\n\t\t\tlower[param] = new BigRational(lowerStr[param]);\n\t\t\tupper[param] = new BigRational(upperStr[param]);\n\t\t}\n\n\t\t// Create function factory\n\t\tString functionType = settings.getString(PrismSettings.PRISM_PARAM_FUNCTION);\n\t\tif (functionType.equals(\"JAS\")) {\n\t\t\treturn new JasFunctionFactory(paramNames, lower, upper);\n\t\t} else if (functionType.equals(\"JAS-cached\")) {\n\t\t\treturn new CachedFunctionFactory(new JasFunctionFactory(paramNames, lower, upper));\n\t\t} else if (functionType.equals(\"DAG\")) {\n\t\t\tdouble dagMaxError = settings.getDouble(PrismSettings.PRISM_PARAM_DAG_MAX_ERROR);\n\t\t\treturn new DagFunctionFactory(paramNames, lower, upper, dagMaxError, false);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Unknown function factory type \\\"\" + functionType + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Create a FunctionFactory based on PRISM settings and by creating a dummy\n\t * parameter that is not used.\n\t * @param settings PRISM settings\n\t */\n\tpublic static FunctionFactory createDummy(PrismSettings settings) throws PrismException\n\t{\n\t\tString[] paramNames = new String[] { \"dummy\" };\n\t\tString[] lowerStr = new String[] { \"0\" };\n\t\tString[] upperStr = new String[] { \"1\" };\n\t\treturn create(paramNames, lowerStr, upperStr, settings);\n\t}\n\n\t/**\n\t * Creates a new function factory.\n\t * {@code parameterNames}, {@code lowerBounds}, {@code upperBounds} all\n\t * must have the same length. Each index into these arrays represents\n\t * respectively the name, lower and upper bound of a given variable.\n\t * After this function factory has been created, the number of variables,\n\t * their names and bounds are fixed and cannot be changed anymore.\n\t * \n\t * @param parameterNames names of parameters\n\t * @param lowerBounds lower bounds of parameters\n\t * @param upperBounds upper bounds of parameters\n\t */\n\tpublic FunctionFactory(String[] parameterNames, BigRational[] lowerBounds, BigRational[] upperBounds) {\n\t\tthis.parameterNames = parameterNames;\n\t\tthis.lowerBounds = lowerBounds;\n\t\tthis.upperBounds = upperBounds;\n\t\tthis.varnameToInt = new HashMap<String, Integer>();\n\t\tfor (int var = 0; var < parameterNames.length; var++) {\n\t\t\tvarnameToInt.put(parameterNames[var], var);\n\t\t}\n\t}\n\n\t/**\n\t * Returns a function representing the number one.\n\t * @return function representing the number one\n\t */\n\tpublic abstract Function getOne();\n\t\n\t/**\n\t * Returns a function representing the number zero.\n\t * @return function representing the number zero\n\t */\n\tpublic abstract Function getZero();\n\n\t/**\n\t * Returns a function representing not-a-number.\n\t * @return function representing not-a-number\n\t */\n\tpublic abstract Function getNaN();\n\t\n\t/**\n\t * Returns a function representing positive infinity.\n\t * @return function representing the positive infinity\n\t */\n\tpublic abstract Function getInf();\n\t\n\t/**\n\t * Returns a function representing negative infinity.\n\t * @return function representing the negative infinity\n\t */\n\tpublic abstract Function getMInf();\n\t\n\t/**\n\t * Returns a new function which represents the same value as the\n\t * {@code BigRational} {@code bigRat}.\n\t * \n\t * @param bigRat value to create a function of\n\t * @return function representing the same value as {@code bigRat}\n\t */\n\tpublic abstract Function fromBigRational(BigRational bigRat);\n\t\n\t/**\n\t * Returns a function representing a single variable. \n\t * \n\t * @param var the variable to create a function of\n\t * @return function consisting only in one variable\n\t */\n\tpublic abstract Function getVar(int var);\n\n\n\t/**\n\t * Returns a function representing a single variable. \n\t * \n\t * @param var name of the variable to create a function of\n\t * @return function consisting only in one variable\n\t */\n\tpublic Function getVar(String var) {\n\t\treturn getVar(varnameToInt.get(var));\n\t}\n\t\n\t/**\n\t * Returns name of variable with the given index.\n\t * \n\t * @param var index of the variable to obtain name of\n\t * @return name of {@code var}\n\t */\n\tpublic String getParameterName(int var) {\n\t\treturn parameterNames[var];\n\t}\n\n\t/**\n\t * Returns lower bound of variable with the given index.\n\t * \n\t * @param var index of the variable to obtain lower bound of\n\t * @return lower bound of {@code var}\n\t */\n\tpublic BigRational getLowerBound(int var) {\n\t\treturn lowerBounds[var];\n\t}\n\t\n\t/**\n\t * Returns upper bound of variable with the given index.\n\t * \n\t * @param var index of the variable to obtain upper bound of\n\t * @return upper bound of {@code var}\n\t */\n\tpublic BigRational getUpperBound(int var) {\n\t\treturn upperBounds[var];\n\t}\n\t\n\t/**\n\t * Returns number of variables used in this function factory.\n\t * @return\n\t */\n\tpublic int getNumVariables() {\n\t\treturn parameterNames.length;\n\t}\n\t\n\t/**\n\t * Returns a function representing the value of the given number.\n\t * \n\t * @param from number to create function of\n\t * @return function representing the number {@code from}\n\t */\n\tpublic Function fromLong(long from) {\n\t\treturn fromBigRational(new BigRational(from));\n\t}\n\t\n\t/**\n\t * Transform PRISM expression to rational function.\n\t * If successful, a function representing the given expression will be\n\t * constructed. This is however not always possible, as not each PRISM\n\t * expression can be represented as a rational function. In this case\n\t * a {@code PrismException} will be thrown.\n\t * \n\t * @param expr PRISM expression to transform to rational function\n\t * @return rational function representing the given PRISM expression\n\t * @throws PrismException thrown if {@code expr} cannot be represented as rational function\n\t */\n\tpublic Function expr2function(Expression expr) throws PrismLangException\n\t{\n\t\treturn expr2function(expr, null);\n\t}\n\t\n\t/**\n\t * Transform PRISM expression to rational function.\n\t * If successful, a function representing the given expression will be\n\t * constructed. This is however not always possible, as not each PRISM\n\t * expression can be represented as a rational function. In this case\n\t * a {@code PrismException} will be thrown.\n\t * \n\t * @param expr PRISM expression to transform to rational function\n\t * @return rational function representing the given PRISM expression\n\t * @throws PrismException thrown if {@code expr} cannot be represented as rational function\n\t */\n\tpublic Function expr2function(Expression expr, Values constantValues) throws PrismLangException\n\t{\n\t\tif (expr instanceof ExpressionLiteral) {\n\t\t\tString exprString = ((ExpressionLiteral) expr).getString();\n\t\t\tif (exprString == null || exprString.equals(\"\")) {\n\t\t\t\tthrow new PrismLangException(\"Cannot create rational function from literal for which no string is set\", expr);\n\t\t\t}\n\t\t\treturn fromBigRational(new BigRational(exprString));\n\t\t} else if (expr instanceof ExpressionConstant) {\n\t\t\tString exprString = ((ExpressionConstant) expr).getName();\n\t\t\tif (constantValues != null && constantValues.contains(exprString)) {\n\t\t\t\tObject val = constantValues.getValueOf(exprString);\n\t\t\t\treturn fromBigRational(new BigRational(val.toString()));\n\t\t\t} else {\n\t\t\t\treturn getVar(exprString);\n\t\t\t}\n\t\t} else if (expr instanceof ExpressionBinaryOp) {\n\t\t\tExpressionBinaryOp binExpr = ((ExpressionBinaryOp) expr);\n\t\t\t// power is handled differently due to some constraints\n\t\t\tif (binExpr.getOperator() ==  ExpressionBinaryOp.POW) {\n\t\t\t\t// power is supported if the exponent is an integer and doesn't refer parametric constants\n\t\t\t\tif (!containsParameter(binExpr.getOperand2(), constantValues) && binExpr.getOperand2().getType() instanceof TypeInt) {\n\t\t\t\t\tint exp = binExpr.getOperand2().evaluateInt(ec);\n\t\t\t\t\tFunction f1 = expr2function(binExpr.getOperand1());\n\t\t\t\t\treturn f1.pow(exp);\n\t\t\t\t} else {\n\t\t\t\t\tthrow new PrismLangException(\"Cannot create rational function for expression \" + expr, expr);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// other arithmetic binary operators:\n\t\t\tFunction f1 = expr2function(binExpr.getOperand1());\n\t\t\tFunction f2 = expr2function(binExpr.getOperand2());\n\t\t\tswitch (binExpr.getOperator()) {\n\t\t\tcase ExpressionBinaryOp.PLUS:\n\t\t\t\treturn f1.add(f2);\n\t\t\tcase ExpressionBinaryOp.MINUS:\n\t\t\t\treturn f1.subtract(f2);\n\t\t\tcase ExpressionBinaryOp.TIMES:\n\t\t\t\treturn f1.multiply(f2);\n\t\t\tcase ExpressionBinaryOp.DIVIDE:\n\t\t\t\treturn f1.divide(f2);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Cannot create rational function for this operator: \" + expr, expr);\n\t\t\t}\n\t\t} else if (expr instanceof ExpressionUnaryOp) {\n\t\t\tExpressionUnaryOp unExpr = ((ExpressionUnaryOp) expr);\n\t\t\tFunction f = expr2function(unExpr.getOperand());\n\t\t\tswitch (unExpr.getOperator()) {\n\t\t\tcase ExpressionUnaryOp.MINUS:\n\t\t\t\treturn f.negate();\n\t\t\tcase ExpressionUnaryOp.PARENTH:\n\t\t\t\treturn f;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Cannot create rational function for this operator: \" + expr, expr);\n\t\t\t}\n\t\t} else if (expr instanceof ExpressionITE){\n\t\t\tExpressionITE iteExpr = (ExpressionITE) expr;\n\t\t\t// ITE expressions where the if-expression does not\n\t\t\t// depend on a parametric constant are supported\n\t\t\tif (!containsParameter(iteExpr.getOperand1(), constantValues)) {\n\t\t\t\tboolean ifValue = iteExpr.getOperand1().evaluateBoolean(ec);\n\t\t\t\tif (ifValue) {\n\t\t\t\t\treturn expr2function(iteExpr.getOperand2());\n\t\t\t\t} else {\n\t\t\t\t\treturn expr2function(iteExpr.getOperand3());\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismLangException(\"Cannot create rational function for expression \" + expr, expr);\n\t\t\t\t}\n\t\t} else if (expr instanceof ExpressionFunc) {\n\t\t\t// functions (min, max, floor, ...) are supported if\n\t\t\t// they don't refer to parametric constants in their arguments\n\t\t\t// and can be exactly evaluated\n\t\t\tif (!containsParameter(expr, constantValues)) {\n\t\t\t\tBigRational value = expr.evaluateBigRational(ec);\n\t\t\t\treturn fromBigRational(value);\n\t\t\t} else {\n\t\t\t\tthrow new PrismLangException(\"Cannot create rational function for this function: \" + expr, expr);\n\t\t\t}\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Cannot create rational function for expression \" + expr, expr);\n\t\t}\n\t}\n\n\t/**\n\t * Returns true if the expression contains a reference to a parameter,\n\t * i.e., an ExpressionConstant not in the provided constantValues list.\n\t */\n\tprivate static boolean containsParameter(Expression expr, Values constantValues)\n\t{\n\t\ttry {\n\t\t\t// check for time bounds, don't recurse into P/R/SS subformulas\n\t\t\texpr.accept(new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPre(ExpressionConstant e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tString exprString = ((ExpressionConstant) e).getName();\n\t\t\t\t\tif (constantValues == null || !constantValues.contains(exprString)) {\n\t\t\t\t\t\tthrow new PrismLangException(\"Found one\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (PrismLangException e) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/JasFunction.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\n\nimport edu.jas.arith.BigInteger;\nimport edu.jas.poly.ExpVector;\nimport edu.jas.poly.GenPolynomial;\nimport edu.jas.poly.Monomial;\nimport edu.jas.ufd.Quotient;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.ExpressionLiteral;\nimport parser.type.TypeDouble;\nimport prism.PrismException;\n\n/**\n * Rational function representation using the Java Algebra System (JAS).\n * Functions are stored in the form {@code num / den}. JAS takes care that\n * {@code num} and {@code den} stay coprime. This decreases the memory\n * needed to represent a function, allows for easier comparism, etc. On the\n * other hand, the cancellation algorithm is expensive. The function factory\n * class used with these functions is {@code JasFunctionFactory}.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see <a href=\"http://krum.rz.uni-mannheim.de/jas/\">http://krum.rz.uni-mannheim.de/jas/</a>\n * @see Function\n * @see JasFunctionFactory\n */\nfinal class JasFunction extends Function {\n\t/** JAS object the function is wrapping */\n\tprivate Quotient<BigInteger> jas;\n\t/** numerator of function (stored if needed) */\n\tPolynomial num;\n\t/** denominator of function (stored if needed) */\n\tPolynomial den;\n\t/** type of function (rational function, infinity, etc.) */\n\tint type;\n\tfinal static int NORMAL = 0;\n\tfinal static int INF = 1;\n\tfinal static int MINF = 2;\n\tfinal static int NAN = 3;\n\n\t// constructors\n\n\t/**\n\t * Creates a new JAS function.\n\t *\n\t * @param functionContext function context of this function\n\t * @param jas JAS object this function object is wrapping\n\t * @param type type of function represented\n\t */\n\tJasFunction(JasFunctionFactory functionContext, Quotient<BigInteger> jas, int type) {\n\t\tsuper(functionContext);\n\t\tthis.jas = jas;\n\t\tthis.num = null;\n\t\tthis.den = null;\n\t\tthis.type = type;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn toStringExpression();\n\t}\n\n\t/**\n\t * Convert to string formatted as Expression.\n\t */\n\tpublic String toStringExpression() {\n\t\ttry {\n\t\t\treturn asExpression().toString();\n\t\t} catch (PrismException e) {\n\t\t\treturn \"?\";\n\t\t}\n\t}\n\n\t/**\n\t * Convert to string formatted using JAS methods.\n\t */\n\tpublic String toStringJas()\n\t{\n\t\tif (isNaN()) {\n\t\t\treturn \"NaN\";\n\t\t} else if (isInf()) {\n\t\t\treturn \"Infinity\";\n\t\t} else if (isMInf()) {\n\t\t\treturn \"-Infinity\";\n\t\t}\n\n\t\treturn jas.toString();\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj) {\n\t\tif (!(obj instanceof JasFunction)) {\n\t\t\treturn false;\n\t\t}\n\t\tJasFunction function = (JasFunction) obj;\n\t\tif (isNaN()) {\n\t\t\treturn function.isNaN();\n\t\t}\n\t\tif (isInf()) {\n\t\t\treturn function.isInf();\n\t\t}\n\t\tif (isMInf()) {\n\t\t\treturn function.isMInf();\n\t\t}\n\t\treturn jas.equals(function.jas);\n\t}\n\t\n\t@Override\n\tpublic int hashCode() {\n\t\treturn jas.hashCode();\n\t}\n\t\n\t/**\n\t * Returns JAS object this function is wrapping.\n\t * \n\t * @return JAS object this function is wrapping\n\t */\n\tQuotient<BigInteger> getJas()\n\t{\n\t\treturn jas;\n\t}\n\t\n\t@Override\n\tpublic Function add(Function other)\n\t{\n\t\tif (this.isNaN() || other.isNaN()) {\n\t\t\treturn factory.getNaN();\n\t\t}\n\t\tif (this.isInf() || other.isInf()) {\n\t\t\tif (this.isMInf() || other.isMInf()) {\n\t\t\t\treturn factory.getZero();\n\t\t\t}\n\t\t\treturn factory.getInf();\n\t\t}\n\t\tif (this.isMInf() || other.isMInf()) {\n\t\t\treturn factory.getMInf();\n\t\t}\n\t\treturn new JasFunction((JasFunctionFactory) factory, jas.sum(((JasFunction)other).jas), NORMAL);\n\t}\n\n\t@Override\n\tpublic Function negate()\n\t{\n\t\tif (this.isNaN()) {\n\t\t\treturn factory.getNaN();\t\t\t\n\t\t}\n\t\tif (this.isInf()) {\n\t\t\treturn factory.getMInf();\n\t\t}\n\t\tif (this.isMInf()) {\n\t\t\treturn factory.getMInf();\t\t\t\n\t\t}\n\t\treturn new JasFunction((JasFunctionFactory) factory, jas.negate(), NORMAL);\n\t}\n\t\n\t@Override\n\tpublic Function multiply(Function other)\n\t{\n\t\tif (this.isNaN() || other.isNaN()) {\n\t\t\treturn factory.getNaN();\n\t\t}\n\t\tif (this.isZero() || other.isZero()) {\n\t\t\treturn factory.getZero();\n\t\t}\n\t\tif (this.isInf() || other.isInf()) {\n\t\t\tif (this.isMInf() || other.isMInf()) {\n\t\t\t\treturn factory.getMInf();\n\t\t\t} else {\n\t\t\t\treturn factory.getInf();\n\t\t\t}\n\t\t}\n\t\treturn new JasFunction((JasFunctionFactory) factory, jas.multiply(((JasFunction) other).jas), NORMAL);\t\t\n\t}\n\t\n\t@Override\n\tpublic Function divide(Function other)\n\t{\n\t\tif (this.isNaN() || other.isNaN()) {\n\t\t\treturn factory.getNaN();\n\t\t}\n\t\tif (other.isInf() || other.isMInf()) {\n\t\t\treturn factory.getNaN();\n\t\t}\n\t\tif (other.isZero()) {\n\t\t\tif (this.isConstant()) {\n\t\t\t\t// evaluate constant to return either NaN, Inf or -Inf, using BigRational division\n\t\t\t\treturn factory.fromBigRational(this.asBigRational().divide(BigRational.ZERO));\n\t\t\t} else {\n\t\t\t\t// non-constant\n\t\t\t\t// TODO: Fix, should be 'this / 0', but that can't be represented by JAS...\n\t\t\t\treturn factory.getInf();\n\t\t\t}\n\t\t}\n\t\tif (this.isZero()) {\n\t\t\treturn factory.getZero();\n\t\t}\n\t\treturn new JasFunction((JasFunctionFactory) factory, jas.divide(((JasFunction) other).jas), NORMAL);\n\t}\n\n\t@Override\n\tpublic Function pow(int exp)\n\t{\n\t\tif (this.isNaN()) {\n\t\t\treturn factory.getNaN();\n\t\t}\n\t\tif (this.isInf()) {\n\t\t\treturn factory.getMInf();\n\t\t}\n\t\tif (this.isMInf()) {\n\t\t\treturn factory.getMInf();\n\t\t}\n\t\treturn new JasFunction((JasFunctionFactory) factory, jas.power(exp), NORMAL);\n\t}\n\n\t@Override\n\tpublic Function star()\n\t{\n\t\tif (this.isNaN()) {\n\t\t\treturn factory.getNaN();\n\t\t}\n\t\tQuotient<BigInteger> one =  ((JasFunctionFactory) factory).getJasQuotRing().getONE();\n\t\tQuotient<BigInteger> result = one.subtract(jas);\n\t\tresult = one.divide(result);\n\t\treturn new JasFunction((JasFunctionFactory) factory, result, NORMAL);\n\t}\n\n\t/**\n\t * Transforms a JAS polynomial to a Polynomial object.\n\t * \n\t * @param j JAS polynomial\n\t * @return polynomial of Polynomial class\n\t */\n\tprivate Polynomial jasToPoly(GenPolynomial<BigInteger> j)\n\t{\n\t\tint numVariables = j.numberOfVariables();\n\t\tPolynomial result = new Polynomial(numVariables, j.length());\n\t\tfor (Monomial<BigInteger> jasMono : j) {\n\t\t\tjava.math.BigInteger coeff = (jasMono.coefficient()).getVal();\n\t\t\tExpVector jasExpo = jasMono.exponent();\n\t\t\tArrayList<Integer> expo = new ArrayList<Integer>();\n\t\t\tfor (int var = 0; var < numVariables; var++) {\n\t\t\t\texpo.add((int)jasExpo.getVal(var));\n\t\t\t}\n\t\t\tresult.addTerm(coeff, expo);\n\t\t}\n\t\t\n\t\treturn result;\n\t}\n\t\n\t@Override\n\tpublic Function toConstraint() {\n\t\tif (isNaN() || isInf() || isMInf()) {\n\t\t\treturn this;\n\t\t}\n\t\tif (num == null) {\n\t\t\tnum = jasToPoly(jas.num);\n\t\t}\n\t\tif (den == null) {\n\t\t\tden = jasToPoly(jas.den);\n\t\t}\n\t\tBigRational[] offset = new BigRational[factory.getNumVariables()]; \n\t\tfor (int dim = 0; dim < factory.getNumVariables(); dim++) {\n\t\t\toffset[dim] = factory.getUpperBound(dim).subtract(factory.getLowerBound(dim));\n\t\t}\n\t\tBigRational evaluated = BigRational.ZERO;\n\t\twhile (evaluated.isZero() || evaluated.isSpecial()) {\n\t\t\tfor (int dim = 0; dim < factory.getNumVariables(); dim++) {\n\t\t\t\toffset[dim] = offset[dim].divide(2);\n\t\t\t}\n\t\t\tBigRational[] point = new BigRational[factory.getNumVariables()];\n\t\t\tfor (int dim = 0; dim < factory.getNumVariables(); dim++) {\n\t\t\t\tpoint[dim] = factory.getLowerBound(dim).add(offset[dim]);\n\t\t\t}\n\t\t\tevaluated = den.evaluate(new Point(point), false);\n\t\t}\n\t\tif (evaluated.signum() == -1) {\n\t\t\treturn new JasFunction((JasFunctionFactory) factory, jas.multiply(jas.den).negate(), NORMAL);\n\t\t} else {\n\t\t\treturn new JasFunction((JasFunctionFactory) factory, jas.multiply(jas.den), NORMAL);\n\t\t}\n\t}\n\n\t@Override\n\tpublic BigRational evaluate(Point point, boolean cancel) {\n\t\tif (isNaN()) {\n\t\t\treturn BigRational.NAN;\n\t\t} else if (isInf()) {\n\t\t\treturn BigRational.INF;\n\t\t} else if (isMInf()) {\n\t\t\treturn BigRational.MINF;\n\t\t}\n\t\tif (num == null) {\n\t\t\tnum = jasToPoly(jas.num);\n\t\t}\n\t\tif (den == null) {\n\t\t\tden = jasToPoly(jas.den);\n\t\t}\n\t\tif (isNaN()) {\n\t\t\treturn BigRational.NAN;\n\t\t}\n\t\treturn num.evaluate(point, cancel).divide(den.evaluate(point, cancel), cancel);\n\t}\n\n\t@Override\n\tpublic BigRational evaluate(Point point) {\n\t\treturn evaluate(point, true);\n\t}\n\t\n\t@Override\n\tpublic boolean check(Point point, boolean strict)\n\t{\n\t\tBigRational value = evaluate(point, false);\n\t\tint compare = value.signum();\n\t\treturn strict ? (compare > 0) : (compare >= 0);\n\t}\n\n\t@Override\n\tpublic Expression asExpression() throws PrismException\n\t{\n\t\tif (isNaN()) {\n\t\t\treturn new ExpressionLiteral(TypeDouble.getInstance(), BigRational.NAN, BigRational.NAN.toString());\n\t\t} else if (isInf()) {\n\t\t\treturn new ExpressionLiteral(TypeDouble.getInstance(), BigRational.INF, BigRational.INF.toString());\n\t\t} else if (isMInf()) {\n\t\t\treturn new ExpressionLiteral(TypeDouble.getInstance(), BigRational.MINF, BigRational.MINF.toString());\n\t\t}\n\t\tExpression expr =  jasPoly2expr(jas.num);\n\t\tif (!jas.den.isONE()) {\n\t\t\texpr = Expression.Divide(expr, jasPoly2expr(jas.den));\n\t\t}\n\t\treturn expr;\n\t}\n\n\t/**\n\t * Transform a JAS polynomial to an Expression object.\n\t */\n\tprivate Expression jasPoly2expr(GenPolynomial<BigInteger> jasPoly) throws PrismException\n\t{\n\t\t// Special case: 0\n\t\tif (jasPoly.isZERO()) {\n\t\t\treturn new ExpressionLiteral(TypeDouble.getInstance(), BigInteger.ZERO, \"0\");\n\t\t}\n\n\t\t// Extract info about coefficients and (expressions for) variable powers\n\t\tint numVariables = jasPoly.numberOfVariables();\n\t\tArrayList<java.math.BigInteger> coeffsAbs = new ArrayList<>();\n\t\tBitSet coeffsNeg = new BitSet();\n\t\tBitSet coeffsOne = new BitSet();\n\t\tArrayList<Expression> exprPows = new ArrayList<>();\n\t\tint numCoeffs = 0;\n\t\tint firstPosCoeff = -1;\n\t\t// Iterate through monomials\n\t\tfor (Monomial<BigInteger> jasMono : jasPoly) {\n\t\t\tjava.math.BigInteger coeff = jasMono.coefficient().getVal();\n\t\t\tif (coeff.signum() != 0) {\n\t\t\t\t// Store (absolute) coefficient and sign/unity info\n\t\t\t\tjava.math.BigInteger coeffAbs = coeff.signum() > 0 ? coeff : coeff.negate();\n\t\t\t\tcoeffsAbs.add(coeffAbs);\n\t\t\t\tcoeffsNeg.set(numCoeffs, coeff.signum() < 0);\n\t\t\t\tcoeffsOne.set(numCoeffs, coeffAbs.equals(java.math.BigInteger.ONE));\n\t\t\t\tif (firstPosCoeff == -1 && coeff.signum() > 0 ) {\n\t\t\t\t\tfirstPosCoeff = numCoeffs;\n\t\t\t\t}\n\t\t\t\t// Convert variable powers to Expression (or null if none)\n\t\t\t\tExpVector jasExpo = jasMono.exponent();\n\t\t\t\tExpression exprPow = null;\n\t\t\t\tfor (int var = 0; var < numVariables; var++) {\n\t\t\t\t\tint power = (int) jasExpo.getVal(var);\n\t\t\t\t\tif (power < 0) {\n\t\t\t\t\t\tthrow new PrismException(\"Polynomials with negative powers not supported\");\n\t\t\t\t\t}\n\t\t\t\t\tif (power > 0) {\n\t\t\t\t\t\tExpression exprVar = new ExpressionConstant(factory.getParameterName(var), TypeDouble.getInstance());\n\t\t\t\t\t\tif (power > 1) {\n\t\t\t\t\t\t\texprVar = Expression.Pow(exprVar, Expression.Int(power));\n\t\t\t\t\t\t}\n\t\t\t\t\t\texprPow = (exprPow == null) ? exprVar : Expression.Times(exprPow, exprVar);\n\t\t\t\t\t}\n\t\t\t\t\t/*for (; power > 0; power--) {\n\t\t\t\t\t\t// Build x^power as x*x*...*x\n\t\t\t\t\t\tExpression exprConst = new ExpressionConstant(factory.getParameterName(var), TypeDouble.getInstance());\n\t\t\t\t\t\texprPow = (exprPow == null) ? exprConst : Expression.Times(exprPow, exprConst);\n\t\t\t\t\t}*/\n\t\t\t\t}\n\t\t\t\texprPows.add(exprPow);\n\t\t\t\tnumCoeffs++;\n\t\t\t}\n\t\t}\n\n\t\t// Convert to Expression\n\t\tExpression exprPoly = null, exprMono = null;\n\t\t// If possible, put a positive coefficient first\n\t\tint first = firstPosCoeff != -1 ? firstPosCoeff : 0;\n\t\t// First monomial (negation handled by negating coefficient)\n\t\tif (exprPows.get(first) == null) {\n\t\t\t// No variable powers - just use coefficient\n\t\t\tjava.math.BigInteger coeff = coeffsNeg.get(first) ? coeffsAbs.get(first).negate() : coeffsAbs.get(first);\n\t\t\texprMono = new ExpressionLiteral(TypeDouble.getInstance(), coeff, coeff.toString());\n\t\t} else {\n\t\t\tif (coeffsOne.get(first)) {\n\t\t\t\t// Coefficient = 1 (or -1)\n\t\t\t\texprMono = coeffsNeg.get(first) ? Expression.Minus(exprPows.get(first)) : exprPows.get(first);\n\t\t\t} else {\n\t\t\t\t// Pre-multiply by non-1 coefficient\n\t\t\t\tjava.math.BigInteger coeff = coeffsNeg.get(first) ? coeffsAbs.get(first).negate() : coeffsAbs.get(first);\n\t\t\t\texprMono = Expression.Times(new ExpressionLiteral(TypeDouble.getInstance(), coeff, coeff.toString()), exprPows.get(first));\n\t\t\t}\n\t\t}\n\t\texprPoly = exprMono;\n\t\t// Remaining monomials (negation handled by joining with minus)\n\t\tfor (int i = 0; i < numCoeffs; i++) {\n\t\t\tif (i != first) {\n\t\t\t\tif (exprPows.get(i) == null) {\n\t\t\t\t\t// No variable powers - just use (absolute) coefficient\n\t\t\t\t\texprMono = new ExpressionLiteral(TypeDouble.getInstance(), coeffsAbs.get(i), coeffsAbs.get(i).toString());\n\t\t\t\t} else {\n\t\t\t\t\t// Pre-multiply by (absolute) coefficient if non-1\n\t\t\t\t\texprMono = coeffsOne.get(i) ? exprPows.get(i) : Expression.Times(new ExpressionLiteral(TypeDouble.getInstance(), coeffsAbs.get(i), coeffsAbs.get(i).toString()), exprPows.get(i));\n\t\t\t\t}\n\t\t\t\texprPoly = coeffsNeg.get(i) ? Expression.Minus(exprPoly, exprMono) : Expression.Plus(exprPoly, exprMono);\n\t\t\t}\n\t\t}\n\n\t\treturn exprPoly;\n\t}\n\n\t@Override\n\tpublic BigRational asBigRational() {\n\t\tif (isNaN()) {\n\t\t\treturn BigRational.NAN;\n\t\t} else if (isInf()) {\n\t\t\treturn BigRational.INF;\n\t\t} else if (isMInf()) {\n\t\t\treturn BigRational.MINF;\n\t\t}\n\t\tBigRational[] point = new BigRational[factory.getNumVariables()];\n\t\tfor (int dim = 0; dim < factory.getNumVariables(); dim++) {\n\t\t\tpoint[dim] = new BigRational(0);\n\t\t}\n\t\treturn evaluate(new Point(point));\n\t}\n\n\t@Override\n\tpublic boolean isNaN() {\n\t\treturn type == NAN;\n\t}\n\n\t@Override\n\tpublic boolean isInf() {\n\t\treturn type == INF;\n\t}\n\n\t@Override\n\tpublic boolean isMInf() {\n\t\treturn type == MINF;\n\t}\n\n\t@Override\n\tpublic boolean isOne() {\n\t\tif (type != NORMAL) {\n\t\t\treturn false;\n\t\t}\n\t\treturn jas.isONE();\n\t}\n\n\t@Override\n\tpublic boolean isZero() {\n\t\tif (type != NORMAL) {\n\t\t\treturn false;\n\t\t}\n\t\treturn jas.isZERO();\n\t}\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\t// inf, NaN are constant\n\t\tif (type != NORMAL)\n\t\t\treturn true;\n\n\t\t// special handling for ZERO, as jas.isConstant() returns false\n\t\t// for zero...\n\t\tif (jas.isZERO()) {\n\t\t\treturn true;\n\t\t}\n\n\t\treturn jas.isConstant();\n\t}\n\n\n}\n"
  },
  {
    "path": "prism/src/param/JasFunctionFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.Arrays;\nimport java.util.Collections;\nimport edu.jas.arith.BigInteger;\nimport edu.jas.poly.GenPolynomialRing;\nimport edu.jas.ufd.Quotient;\nimport edu.jas.ufd.QuotientRing;\n\n/**\n * Function factory class for use with {@code JasFunction}.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see FunctionFactory\n * @see JasFunction\n */\nfinal class JasFunctionFactory extends FunctionFactory {\n\tprivate GenPolynomialRing<BigInteger> jasPolyRing;\n\tprivate QuotientRing<BigInteger> jasQuotRing;\n\tprivate JasFunction zero;\n\tprivate JasFunction one;\n\tprivate JasFunction nan;\n\tprivate JasFunction inf;\n\tprivate JasFunction minf;\n\tprivate JasFunction[] parameters;\n\n\t/**\n\t * Creates a new function factory.\n\t * \n\t * @param parameterNames names of parameters\n\t * @param lowerBounds lower bounds of parameters\n\t * @param upperBounds upper bounds of parameters\n\t */\n\tJasFunctionFactory(String[] parameterNames, BigRational[] lowerBounds, BigRational[] upperBounds)\n\t{\n\t\tsuper(parameterNames, lowerBounds, upperBounds);\n\t\tString[] pNameReversed = new String[parameterNames.length];\n\t\tSystem.arraycopy(parameterNames, 0, pNameReversed, 0, parameterNames.length);\n\t\tCollections.reverse(Arrays.asList(pNameReversed));\n\t\tthis.parameterNames = parameterNames;\n\t\t\n\t\tBigInteger fac = new BigInteger();\n\t\tjasPolyRing = new GenPolynomialRing<BigInteger>(fac,pNameReversed.length,pNameReversed);\n\t\tjasQuotRing = new QuotientRing<BigInteger>(jasPolyRing);\n\t\tone = new JasFunction(this, jasQuotRing.getONE(), JasFunction.NORMAL);\n\t\tzero = new JasFunction(this, jasQuotRing.getZERO(), JasFunction.NORMAL);\n\t\tnan = new JasFunction(this, jasQuotRing.getZERO(), JasFunction.NAN);\n\t\tinf = new JasFunction(this, jasQuotRing.getZERO(), JasFunction.INF);\n\t\tminf = new JasFunction(this, jasQuotRing.getZERO(), JasFunction.MINF);\n\t\tparameters = new JasFunction[parameterNames.length];\n\t\tfor (int param = 0; param < parameterNames.length; param++) {\n\t\t\tparameters[param] = new JasFunction(this, jasQuotRing.parse(parameterNames[param]), JasFunction.NORMAL);\n\t\t}\n\t}\t\n\n\t@Override\n\tpublic Function getOne()\n\t{\n\t\treturn one;\n\t}\n\t\n\t@Override\n\tpublic Function getZero()\n\t{\n\t\treturn zero;\n\t}\n\n\t@Override\n\tpublic Function getNaN()\n\t{\n\t\treturn nan;\n\t}\n\n\t@Override\n\tpublic Function getInf()\n\t{\n\t\treturn inf;\n\t}\n\t\n\t@Override\n\tpublic Function getMInf()\n\t{\n\t\treturn minf;\n\t}\n\n\t/**\n\t * Get JAS ring for rational functions used by this factory.\n\t * \n\t * @return JAS ring for rational functions used by this factory\n\t */\n\tQuotientRing<BigInteger> getJasQuotRing()\n\t{\n\t\treturn jasQuotRing;\n\t}\n\t\n\t/**\n\t * Get JAS ring for polynomials used by this factory.\n\t * In JAS, rational functions are built on polynomial rings, and this\n\t * function returns this corresponding ring.\n\t * \n\t * @return JAS ring for polynomials used by this factory\n\t */\n\tGenPolynomialRing<BigInteger> getJasPolyRing()\n\t{\n\t\treturn jasPolyRing;\n\t}\n\n\t@Override\n\tpublic Function fromBigRational(BigRational from) {\n\t\tif (from.isSpecial()) {\n\t\t\tif (from.isInf())\n\t\t\t\treturn getInf();\n\t\t\telse if (from.isMInf())\n\t\t\t\treturn getMInf();\n\t\t\telse if (from.isNaN())\n\t\t\t\treturn getNaN();\n\t\t\telse\n\t\t\t\tthrow new RuntimeException(\"Implementation error\");\n\t\t}\n\n\t\tQuotient<BigInteger> result = jasQuotRing.fromInteger(from.getNum());\n\t\tQuotient<BigInteger> den = jasQuotRing.fromInteger(from.getDen());\n\t\tresult = result.divide(den);\n\t\t\n\t\treturn new JasFunction(this, result, JasFunction.NORMAL);\n\t}\n\n\t@Override\n\tpublic Function getVar(int var) {\n\t\treturn parameters[var];\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/Lumper.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.HashMap;\nimport java.util.HashSet;\n\n/**\n * Base class for signature-based bisimulation lumping.\n * Derived classes could implement specific types of bisimulation,\n * e.g. weak, strong, etc.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see NullLumper\n * @see StrongLumper\n * @see WeakLumper\n */\nabstract class Lumper {\n\t/**\n\t * Kind of lumping to be used.\n\t */\n\tenum BisimType {\n\t\tNULL,\n\t\tSTRONG,\n\t\tWEAK\n\t}\n\t\n\t/** stores the original model to be lumped */\n\tprotected MutablePMC origPmc;\n\t/** stores the lumped model */\n\tprotected MutablePMC optPmc;\n\t/** stores the state partitioning */\n\tprotected Partition partition;\n\t/** maintains a mapping from blocks to block numbers */\n\tprotected HashMap<HashSet<Integer>, Integer> blockToNumber;\n\t/** list of all blocks */\n\tprotected ArrayList<HashSet<Integer>> blocks;\n\t/** maps states from original to containing states in lumped model */\n\tprotected int[] originalToOptimised;\n\n\t/**\n\t * Creates new lumper for given parametric Markov chain.\n\t * \n\t * @param origPmc Markov chain to build lumper for\n\t */\n\tLumper(MutablePMC origPmc)\n\t{\n\t\tthis.origPmc = origPmc;\n\t\tpartition = new Partition(origPmc);\n\t\tcreateInitialPartition();\n\t\tlump();\n\t\tmapBlocksToNumber();\n\t\tbuildQuotient();\n\t}\n\n\t/**\n\t * Creates a new lumper.\n\t * This constructor needs to be present for technical reasons.\n\t */\n\tprotected Lumper()\n\t{\n\t\t\n\t}\n\n\t/**\n\t * Stores combination of state reward and state time.\n\t * This class is used subsume states with the same reward and time.\n\t * If the time entry is irrelevant, it can be set to null.\n\t *  \n\t * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n\t */\n\tclass RewardEntry\n\t{\n\t\t/** reward for this entry */\n\t\tfinal Function reward;\n\t\t/** time for this entry */\n\t\tfinal Function time;\n\t\t\n\t\t/**\n\t\t * Creates a new reward entry.\n\t\t * \n\t\t * @param reward reward for this entry\n\t\t * @param time time for this entry.\n\t\t */\n\t\tRewardEntry(Function reward, Function time) {\n\t\t\tthis.reward = reward;\n\t\t\tthis.time = time;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic int hashCode()\n\t\t{\n\t\t\tint hash = reward.hashCode() << 13;\n\t\t\tif (time != null) {\n\t\t\t\thash |= time.hashCode();\n\t\t\t}\n\t\t\treturn hash;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean equals(Object obj)\n\t\t{\n\t\t\tif (!(obj instanceof RewardEntry)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\t\n\t\t\tRewardEntry other = (RewardEntry) obj;\n\t\t\tif (!this.reward.equals(other.reward)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif ((this.time == null) != (other.time == null)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (this.time != null && !this.time.equals(other.time)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\treturn true;\n\t\t}\n\t}\n\t\n\t/**\n\t * Creates an initial partitioning appropriate for analysis to perform.\n\t * For reachability, takes care that only target-states / non-target\n\t * are stored in one initial block, for reward analyses takes care\n\t * that only states with same reward are subsumed, etc. For certain types\n\t * of bisimulations, this is not enough, and the initial partition must be\n\t * refined further before starting the main refinement process. This is\n\t * the case for instance for weak bisimulation.\n\t */\n\tprotected void createInitialPartition()\n\t{\n\t\tHashSet<Integer> oldBlock = partition.nextChangeableBlock();\n\t\tif (!origPmc.isUseRewards()) {\n\t\t\tHashSet<Integer> safeStates = new HashSet<Integer>();\n\t\t\tHashSet<Integer> unsafeStates = new HashSet<Integer>();\n\t\t\tfor (int state : oldBlock) {\n\t\t\t\tif (origPmc.isTargetState(state)) {\n\t\t\t\t\tunsafeStates.add(state);\n\t\t\t\t} else {\n\t\t\t\t\tsafeStates.add(state);\n\t\t\t\t}\n\t\t\t}\n\t\t\tArrayList<HashSet<Integer>> newBlocks = new ArrayList<HashSet<Integer>>(); \n\t\t\tif (safeStates.size() != 0) {\n\t\t\t\tnewBlocks.add(safeStates);\n\t\t\t}\n\t\t\tif (unsafeStates.size() != 0) {\n\t\t\t\tnewBlocks.add(unsafeStates);\n\t\t\t}\n\t\t\tpartition.addBlocks(newBlocks);\n\t\t} else {\n\t\t\tHashMap<RewardEntry, HashSet<Integer>> rewardToStateMap = new HashMap<RewardEntry, HashSet<Integer>>();\n\t\t\tfor (int state : oldBlock) {\n\t\t\t\tFunction reward = origPmc.getReward(state);\n\t\t\t\tFunction time = null;\n\t\t\t\tif (origPmc.isUseTime()) {\n\t\t\t\t\ttime = origPmc.getTime(state);\n\t\t\t\t}\n\t\t\t\tRewardEntry entry = new RewardEntry(reward, time);\n\t\t\t\tHashSet<Integer> block = rewardToStateMap.get(entry);\n\t\t\t\tif (block == null) {\n\t\t\t\t\tblock = new HashSet<Integer>();\n\t\t\t\t\trewardToStateMap.put(entry, block);\n\t\t\t\t}\n\t\t\t\tblock.add(state);\n\t\t\t}\n\t\t\tArrayList<HashSet<Integer>> newBlocks = new ArrayList<HashSet<Integer>>(); \n\t\t\tfor (HashSet<Integer> block : rewardToStateMap.values()) {\n\t\t\t\tif (block.size() != 0) {\n\t\t\t\t\tnewBlocks.add(block);\n\t\t\t\t}\n\t\t\t}\n\t\t\tpartition.addBlocks(newBlocks);\n\t\t}\n\t\tpartition.markAllBlocksAsNew();\n\t}\n\t\n\t/**\n\t * Return the quotient of the original model.\n\t * Before calling this method, {@code lump()} must have been called.\n\t * \n\t * @return quotient of original model\n\t */\n\tMutablePMC getQuotient()\n\t{\n\t\treturn optPmc;\n\t}\n\t\n\t/**\n\t * Enumerates the blocks after refinement is finished.\n\t * This is done as a preparation to create the quotient and the\n\t * mapping from original to quotient states.\n\t */\n\tprotected void mapBlocksToNumber()\n\t{\n\t\tblocks = partition.getAllBlocks();\n\t\tblockToNumber = new HashMap<HashSet<Integer>, Integer>();\n\t\toriginalToOptimised = new int[origPmc.getNumStates()];\n\t\tint nextBlockNumber = 0;\n\t\tfor (HashSet<Integer> block : blocks) {\n\t\t\tblockToNumber.put(block, nextBlockNumber);\n\t\t\tfor (int state : block) {\n\t\t\t\toriginalToOptimised[state] = nextBlockNumber;\n\t\t\t}\n\t\t\tnextBlockNumber++;\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns a mapping from original model states to quotient states.\n\t * Thus, {@result[state]} is the state of the quotient to which\n\t * {@code state} belongs.\n\t * \n\t * @return mapping from original model states to quotient states\n\t */\n\tint[] getOriginalToOptimised()\n\t{\n\t\treturn originalToOptimised;\n\t}\n\t\n\t/**\n\t * Perform the lumping process.\n\t * Refines blocks from the list of blocks to refine, it is clear that\n\t * further tries to refine blocks will not lead to the creation of any\n\t * new blocks.\n\t */\n\tprotected void lump()\n\t{\n\t\tArrayList<HashSet<Integer>> newBlocks = new ArrayList<HashSet<Integer>>();\n\t\twhile (partition.mayChange()) {\n\t\t\tnewBlocks.clear();\n\t\t\tHashSet<Integer> oldBlock = partition.nextChangeableBlock();\n\t\t\trefineBlock(oldBlock, newBlocks);\n\t\t\tpartition.addBlocks(newBlocks);\n\t\t}\n\t}\n\t\n\t/**\n\t * Refine a given block.\n\t * The exact way of how this is done depends on the type of bisimulation used.\n\t * \n\t * @param oldBlock block to refine\n\t * @param newBlocks list of new blocks generated\n\t */\n\tabstract protected void refineBlock(HashSet<Integer> oldBlock, ArrayList<HashSet<Integer>> newBlocks);\n\t\n\t/**\n\t * Build the quotients after refinement has finished.\n\t * Each state of the quotient will be a block of states from the original\n\t * model. The exact way of how transitions between states are computed\n\t * depends on the type of bisimulation used.\n\t */\n\tabstract protected void buildQuotient();\n}\n"
  },
  {
    "path": "prism/src/param/MutablePMC.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.LinkedList;\nimport java.util.ListIterator;\n\n/**\n * Representation of mutable parametric Markov chain.\n * This class is intended to be used in combination with the\n * {@code StateEliminator}, which uses this class to compute values of\n * parametric Markov models.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see StateEliminator\n */\nfinal class MutablePMC {\n\t/** function factory to which functions in this object belong */\n\tprivate FunctionFactory functionFactory;\n\t/** assignment of rewards to each state */\n\tprivate Function[] rewards;\n\t/** assignment of time to each state */\n\tprivate Function[] times;\n\t/** for each state, provides list of leaving transition probabilities */\n\tArrayList<LinkedList<Function>> transitionProbs;\n\t/** for each state, provides list of leaving transition targets */\n\tArrayList<LinkedList<Integer>> transitionTargets;\n\t/** for each state, provides list of states which have transitions to this state */\n\tArrayList<LinkedList<Integer>> incoming;\n\t/** true iff uses a reward structure */\n\tprivate boolean useRewards;\n\t/** true iff uses time reward structure */\n\tprivate boolean useTime;\n\t/** initial states */\n\tprivate BitSet initStates;\n\t/** target states */\n\tprivate BitSet targetStates;\n\t/** total number of states */\n\tprivate int numStates;\n\n\t/**\n\t * Constructs a new mutable parametric Markov chain.\n\t * \n\t * @param functionFactory function factory used to maintain rational functions\n\t * @param numStates total number of states this parametric Markov chain shall have\n\t * @param useRewards true iff parametric Markov chain constructed shall use rewards\n\t * @param useTime true iff parametric Markov chain constructed needs time entry\n\t */\n\tMutablePMC(FunctionFactory functionFactory, int numStates, boolean useRewards, boolean useTime) {\n\t\tthis.numStates = numStates;\n\t\tthis.functionFactory = functionFactory;\n\t\ttransitionProbs = new ArrayList<LinkedList<Function>>(numStates);\n\t\ttransitionTargets = new ArrayList<LinkedList<Integer>>(numStates);\n\t\tincoming = new ArrayList<LinkedList<Integer>>(numStates);\t\t\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\ttransitionTargets.add(new LinkedList<Integer>());\n\t\t\ttransitionProbs.add(new LinkedList<Function>());\n\t\t\tincoming.add(new LinkedList<Integer>());\n\t\t}\n\t\tthis.useRewards = useRewards;\n\t\tthis.useTime = useTime;\n\t\tinitStates = new BitSet(numStates);\n\t\ttargetStates = new BitSet(numStates);\n\t\tif (useRewards) {\n\t\t\trewards = new Function[numStates];\n\t\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t\trewards[i] = functionFactory.getZero();\n\t\t\t}\n\t\t}\n\t\tif (useTime) {\n\t\t\ttimes = new Function[numStates];\n\t\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\t\ttimes[i] = functionFactory.getOne();\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns function factory maintaining functions used in this object.\n\t * \n\t * @return function factory maintaining functions\n\t */\n\tFunctionFactory getFunctionFactory()\n\t{\n\t\treturn functionFactory;\n\t}\n\t\n\t/**\n\t * Adds a probabilistic transition.\n\t * \n\t * @param from state transition starts from\n\t * @param to state transition leads to\n\t * @param prob probability of transition\n\t */\n\tvoid addTransition(int from, int to, Function prob)\n\t{\n\t\tListIterator<Integer> toIter = transitionTargets.get(from).listIterator();\n\t\tListIterator<Function> valIter = transitionProbs.get(from).listIterator();\n\t\tboolean alreadyThere = false;\n\t\twhile (toIter.hasNext() && !alreadyThere) {\n\t\t\tint succ = toIter.next();\n\t\t\tFunction succProb = valIter.next();\n\t\t\tif (succ == to) {\n\t\t\t\tvalIter.set(succProb.add(prob));\n\t\t\t\talreadyThere = true;\n\t\t\t}\n\t\t}\n\t\tif (!alreadyThere) {\n\t\t\ttransitionTargets.get(from).add(to);\n\t\t\ttransitionProbs.get(from).add(prob);\n\t\t\tincoming.get(to).add(from);\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns the probability of a given transition\n\t * \n\t * @param from source state of transition\n\t * @param to target state of transition\n\t * @return probability to move from given state to given state\n\t */\n\tFunction getTransProb(int from, int to)\n\t{\n\t\tFunction prob = null;\n\t\tListIterator<Integer> toIter = transitionTargets.get(from).listIterator();\n\t\tListIterator<Function> valIter = transitionProbs.get(from).listIterator();\t\t\n\t\twhile (toIter.hasNext()) {\n\t\t\tint succ = toIter.next();\n\t\t\tFunction succProb = valIter.next();\n\t\t\tif (succ == to) {\n\t\t\t\tprob = succProb;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif (prob == null) {\n\t\t\tprob = functionFactory.getZero();\n\t\t}\n\t\t\n\t\treturn prob;\n\t}\n\t\n\t/**\n\t * Returns probability of the self-loop in a given state.\n\t * \n\t * @param state state to return self-loop probability of\n\t * @return self-loop probability of given state\n\t */\n\tFunction getSelfLoopProb(int state)\n\t{\n\t\tFunction loopProb = null;\n\t\t\n\t\tListIterator<Integer> toIter = transitionTargets.get(state).listIterator();\n\t\tListIterator<Function> valIter = transitionProbs.get(state).listIterator();\t\t\n\t\twhile (toIter.hasNext()) {\n\t\t\tint to = toIter.next();\n\t\t\tFunction val = valIter.next();\n\t\t\tif (to == state) {\n\t\t\t\tloopProb = val;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\tif (loopProb == null) {\n\t\t\tloopProb = functionFactory.getZero();\n\t\t}\n\t\t\n\t\treturn loopProb;\n\t}\n\t\n\t/**\n\t * Makes a given state absorbing.\n\t * This means removing all leaving transitions and adding a self-loop\n\t * with probability one.\n\t * \n\t * @param state state to make absorbing\n\t */\n\tvoid makeAbsorbing(int state)\n\t{\n\t\tLinkedList<Integer> loop = new LinkedList<Integer>();\n\t\tloop.add(state);\n\t\tLinkedList<Function> one = new LinkedList<Function>();\n\t\tone.add(functionFactory.getOne());\n\t\ttransitionTargets.set(state, loop);\n\t\ttransitionProbs.set(state, one);\n\t}\n\n\t/**\n\t * Sets whether given state shall be an initial state\n\t * \n\t * @param state state which shall or shall not be an initial state\n\t * @param targetState true iff given state shall be an initial state\n\t */\n\tvoid setInitState(int state, boolean targetState)\n\t{\n\t\tinitStates.set(state, targetState);\n\t}\n\n\t/**\n\t * Sets whether given state shall be a target state\n\t * \n\t * @param state state which shall or shall not be a target state\n\t * @param targetState true iff given state shall be a target state\n\t */\n\tvoid setTargetState(int state, boolean targetState)\n\t{\n\t\ttargetStates.set(state, targetState);\n\t}\n\t\n\t/**\n\t * Set reward of a given state.\n\t * \n\t * @param state state to set reward of\n\t * @param reward reward to set for given state\n\t */\n\tvoid setReward(int state, Function reward)\n\t{\n\t\trewards[state] = reward;\n\t}\n\n\t/**\n\t * Set time of a given state.\n\t * \n\t * @param state state to set reward of\n\t * @param time time to set for given state\n\t */\n\tvoid setTime(int state, Function time)\n\t{\n\t\ttimes[state] = time;\n\t}\n\n\t/**\n\t * Get time of a given state.\n\t * \n\t * @param state state to get time of\n\t * @return time of given state\n\t */\n\tFunction getTime(int state)\n\t{\n\t\treturn times[state];\n\t}\n\t\n\t/**\n\t * Checks whether given state is a target state.\n\t * \n\t * @param state state to check whether it is a target state\n\t * @return true iff given state is a target state\n\t */\n\tboolean isTargetState(int state)\n\t{\n\t\treturn targetStates.get(state);\n\t}\n\n\t/**\n\t * Checks whether there are some target states\n\t * \n\t * @return true iff there are some target states\n\t */\n\tboolean hasTargetStates()\n\t{\n\t\treturn targetStates.cardinality() != 0;\n\t}\n\t\n\t/**\n\t * Checks whether given state is an initial state.\n\t * \n\t * @param state state to check whether it is an initial state\n\t * @return true iff given state is an initial state\n\t */\n\tboolean isInitState(int state)\n\t{\n\t\treturn initStates.get(state);\n\t}\n\n\t/**\n\t * Gets the reward of a given state.\n\t * \n\t * @param state state to get reward of\n\t * @return reward of given state\n\t */\n\tFunction getReward(int state)\n\t{\n\t\treturn rewards[state];\n\t}\n\t\n\t/**\n\t * Returns number of states.\n\t * \n\t * @return number of states\n\t */\n\tint getNumStates()\n\t{\n\t\treturn numStates;\n\t}\n\t\n\t/**\n\t * Returns whether pmc uses rewards.\n\t * \n\t * @return true iff rewards are used\n\t */\n\tboolean isUseRewards()\n\t{\n\t\treturn useRewards;\n\t}\n\t\n\t/**\n\t * Returns whether pmc uses time.\n\t * \n\t * @return true iff uses time\n\t */\n\tboolean isUseTime()\n\t{\n\t\treturn useTime;\n\t}\n\t\n\t/*\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuilder result = new StringBuilder();\n\t\t\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tresult.append(\"state \" + state);\n\t\t\tif (useRewards) {\n\t\t\t\tresult.append(\" \" + rewards[state]);\n\t\t\t}\n\t\t\tif (useTime) {\n\t\t\t\tresult.append(\" \" + times[state]);\n\t\t\t}\n\t\t\tresult.append(\"\\n\");\n\t\t}\n\t\t\n\t\treturn result.toString();\n\t}\n\t*/\n}\n"
  },
  {
    "path": "prism/src/param/NullLumper.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.HashSet;\n\n/**\n * Lumper for identity bisimulation.\n * That is, this class does basically nothing and is there for convenience\n * when choosing between different types of bisimulations. So, for\n * disabling bisimulation, one can use an object of this class.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class NullLumper extends Lumper {\n\n\t/**\n\t * Creates a new identity bisimulation lumper for given Markov chain.\n\t * @param origPmc parametric Markov chain to create lumper for\n\t */\n\tNullLumper(MutablePMC origPmc) {\n\t\tthis.origPmc = origPmc;\n\t\tthis.optPmc = origPmc;\n\t}\n\n\t/**\n\t * Does not have to do anything.\n\t */\n\t@Override\n\tprotected void refineBlock(HashSet<Integer> oldBlock,\n\t\t\tArrayList<HashSet<Integer>> newBlocks) {\n\t}\n\n\t/**\n\t * Does not have to do anything.\n\t */\n\t@Override\n\tprotected void buildQuotient() {\n\t}\n\n\t/**\n\t * Build identity mapping.\n\t * \n\t * @return identity mapping\n\t */\n\t@Override\n\tint[] getOriginalToOptimised() {\n\t\tint[] result = new int[origPmc.getNumStates()];\n\t\tfor (int state = 0; state < result.length; state++) {\n\t\t\tresult[state] = state;\n\t\t}\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/Optimiser.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\n\n/**\n * Searches for bounds of minimal/maximal values.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class Optimiser {\n\tRegionValues values;\n\tRegionValues filter;\n\tboolean min;\n\n\tpublic Optimiser(RegionValues values, RegionValues filter, boolean min) {\n\t\tthis.values = values;\n\t\tthis.filter = filter;\n\t\tthis.min = min;\n\t}\n\n\tpublic String optimise() {\n\t\tint numStates = values.getResult(0).getNumStates();\n\t\tBigRational[] bounds = new BigRational[numStates];\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tbounds[state] = min ? BigRational.INF : BigRational.MINF;\n\t\t}\n\t\tPoint[] optPoints = new Point[numStates];\n\t\t\n\t\tRegionValuesIntersections co = new RegionValuesIntersections(values, filter);\n\t\tfor (RegionIntersection inter : co) {\n\t\t\tRegion region = inter.getRegion();\n\t\t\tStateValues value1 = inter.getStateValues1();\n\t\t\tStateValues value2 = inter.getStateValues2();\n\t\t\tfor (int state = 0; state < value1.getNumStates(); state++) {\n\t\t\t\tArrayList<Point> edges = region.specialPoints();\n\t\t\t\tfor (Point edge : edges) {\n\t\t\t\t\tBigRational currentValue = value1.getStateValueAsFunction(state).evaluate(edge);\n\t\t\t\t\tif (value2.getStateValueAsBoolean(state)) {\n\t\t\t\t\t\tif (currentValue.compareTo(bounds[state]) == (min ? -1 : 1)) {\n\t\t\t\t\t\t\tbounds[state] = currentValue;\n\t\t\t\t\t\t\toptPoints[state] = edge;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tBigRational initBound = bounds[values.getInitState()];\n\t\t\n\t\treturn (min ? \"at most \" : \"at least \") + initBound.doubleValue() + \" at \" + optPoints[values.getInitState()];\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/param/ParamMode.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2017-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage param;\n\n/** Mode (parametric / exact) */\npublic enum ParamMode {\n\t/** Parametric analysis mode for the parametric engine */\n\tPARAMETRIC(\"parametric\"),\n\t/** Exact analysis mode (i.e., using constant functions) for the parametric engine */\n\tEXACT(\"exact\");\n\n\t/** The mode name */\n\tprivate final String name;\n\n\t/** Private constructor */\n\tprivate ParamMode(String name)\n\t{\n\t\tthis.name = name;\n\t}\n\n\t/** Get either \"parametric\" or \"exact\", depending on mode. */\n\tpublic String toString()\n\t{\n\t\treturn name;\n\t}\n\n\t/** Get \"parametric engine\" or \"exact engine\", depending on mode. */\n\tpublic String engine()\n\t{\n\t\treturn name + \" engine\";\n\t}\n\n\t/** Get \"Parametric engine\" or \"Exact engine\", depending on mode. */\n\tpublic String Engine()\n\t{\n\t\treturn name.substring(0,1).toUpperCase() + name.substring(1) + \" engine\";\n\t}\n}"
  },
  {
    "path": "prism/src/param/ParamModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n/*\n * TODO\n * - lumpers should start convert directly from ParamModel plus scheduler and rewards\n *   rather than from AlterablePMC as is done currently\n * - could print to log for which parameter values results will be valid\n * - could implement steady-state properties for models w.o.\n *   nondeterminism but not needed at least not for next paper\n * - could implement DAG-like functions + probabilistic equality\n *   - for each function num and den would each be pointers into DAG\n *   - then either exact equality (expensive)\n *   - or probabilistic equality (Schwartz-Zippel)\n * - also, DAG-like regexp representation possible\n * - for comparism with previous work, use \n * - could implement other types of regions apart from boxes\n * - could later improve support for optimisation over parameters\n *   - using apache math commons\n *   - or ipopt (zip file with java support for linux, windows, mac os x exists)\n * - libraries used should be loaded by classloader to make easier to use in\n *   projects where we cannot use GPLed code (just delete library and that's it)\n * - could later add support for abstraction of functions\n * - could integrate in GUI (student project?)\n * - if time left, add JUnit tests at least for BigRational and maybe functions and regions\n *   basically for all classes where interface is more or less fixed\n * - could try to bind to Ginac for comparability, but probably not much difference\n * - should integrate binding to solvers (RAHD and the like) at some point\n */\n\npackage param;\n\nimport java.util.BitSet;\nimport java.util.List;\n\nimport explicit.DTMC;\nimport explicit.DTMCSimple;\nimport explicit.ModelSimple;\nimport explicit.rewards.ConstructRewards;\nimport explicit.rewards.Rewards;\nimport explicit.rewards.RewardsSimple;\nimport param.Lumper.BisimType;\nimport param.StateEliminator.EliminationOrder;\nimport parser.EvaluateContext;\nimport parser.State;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.ExpressionExists;\nimport parser.ast.ExpressionFilter;\nimport parser.ast.ExpressionFilter.FilterOperator;\nimport parser.ast.ExpressionForAll;\nimport parser.ast.ExpressionFormula;\nimport parser.ast.ExpressionFunc;\nimport parser.ast.ExpressionITE;\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionLiteral;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionProp;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionSS;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.ast.LabelList;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport parser.ast.RelOp;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.type.TypePathBool;\nimport parser.type.TypePathDouble;\nimport prism.Accuracy;\nimport prism.Evaluator;\nimport prism.ModelInfo;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismSettings;\nimport prism.PrismNotSupportedException;\nimport prism.Result;\nimport edu.jas.kern.ComputerThreads;\nimport explicit.Model;\nimport prism.RewardGenerator;\n\n/**\n * Model checker for parametric Markov models.\n */\nfinal public class ParamModelChecker extends PrismComponent\n{\n\t// Model info (for reward structures, etc.)\n\tprivate ModelInfo modelInfo = null;\n\tprivate RewardGenerator<?> rewardGen = null;\n\n\t// Cached version of the model passed in for model checking, before any conversion\n\tprivate Model<?> modelOrig = null;\n\n\t// Properties file (for labels, constants, etc.)\n\tprivate PropertiesFile propertiesFile = null;\n\n\t// Constants (extracted from model/properties)\n\tprivate Values constantValues;\n\n\t// The result of model checking will be stored here\n\tprivate Result result;\n\t\n\t// Flags/settings\n\n\t/** The mode (parametric or exact)? */\n\tprivate ParamMode mode;\n\n\t// Verbosity level\n\tprivate int verbosity = 0;\n\t\n\tprivate BigRational[] paramLower;\n\tprivate BigRational[] paramUpper;\n\n\tprivate FunctionFactory functionFactory;\n\tprivate RegionFactory regionFactory;\n\tprivate ConstraintChecker constraintChecker;\n\tprivate ValueComputer valueComputer;\n\t\n\tprivate BigRational precision;\n\tprivate int splitMethod;\n\tprivate EliminationOrder eliminationOrder;\n\tprivate int numRandomPoints;\n\tprivate Lumper.BisimType bisimType;\n\tprivate boolean simplifyRegions;\n\n\t/**\n\t * Constructor\n\t */\n\tpublic ParamModelChecker(PrismComponent parent, ParamMode mode) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tthis.mode = mode;\n\n\t\t// If present, initialise settings from PrismSettings\n\t\tif (settings != null) {\n\t\tverbosity = settings.getBoolean(PrismSettings.PRISM_VERBOSE) ? 10 : 1;\n\t\tprecision = new BigRational(settings.getString(PrismSettings.PRISM_PARAM_PRECISION));\n\t\tString splitMethodString = settings.getString(PrismSettings.PRISM_PARAM_SPLIT);\n\t\tif (splitMethodString.equals(\"Longest\")) {\n\t\t\tsplitMethod = BoxRegion.SPLIT_LONGEST;\n\t\t} else if (splitMethodString.equals(\"All\")) {\n\t\t\tsplitMethod = BoxRegion.SPLIT_ALL;\n\t\t} else {\n\t\t\tthrow new PrismException(\"unknown region splitting method \" + splitMethodString);\t\t\t\t\n\t\t}\n\t\tString eliminationOrderString = settings.getString(PrismSettings.PRISM_PARAM_ELIM_ORDER);\n\t\tif (eliminationOrderString.equals(\"Arbitrary\")) {\n\t\t\teliminationOrder = EliminationOrder.ARBITRARY;\n\t\t} else if (eliminationOrderString.equals(\"Forward\")) {\n\t\t\teliminationOrder = EliminationOrder.FORWARD;\n\t\t} else if (eliminationOrderString.equals(\"Forward-reversed\")) {\n\t\t\teliminationOrder = EliminationOrder.FORWARD_REVERSED;\n\t\t} else if (eliminationOrderString.equals(\"Backward\")) {\n\t\t\teliminationOrder = EliminationOrder.BACKWARD;\n\t\t} else if (eliminationOrderString.equals(\"Backward-reversed\")) {\n\t\t\teliminationOrder = EliminationOrder.BACKWARD_REVERSED;\n\t\t} else if (eliminationOrderString.equals(\"Random\")) {\n\t\t\teliminationOrder = EliminationOrder.RANDOM;\n\t\t} else {\n\t\t\tthrow new PrismException(\"unknown state elimination order \" + eliminationOrderString);\t\t\t\t\n\t\t}\n\t\tnumRandomPoints = settings.getInteger(PrismSettings.PRISM_PARAM_RANDOM_POINTS);\n\t\tString bisimTypeString = settings.getString(PrismSettings.PRISM_PARAM_BISIM);\n\t\tif (bisimTypeString.equals(\"Weak\")) {\n\t\t\tbisimType = BisimType.WEAK;\n\t\t} else if (bisimTypeString.equals(\"Strong\")) {\n\t\t\tbisimType = BisimType.STRONG;\n\t\t} else if (bisimTypeString.equals(\"None\")) {\n\t\t\tbisimType = BisimType.NULL;\n\t\t} else {\n\t\t\tthrow new PrismException(\"unknown bisimulation type \" + bisimTypeString);\t\t\t\t\t\t\t\n\t\t}\n\t\tsimplifyRegions = settings.getBoolean(PrismSettings.PRISM_PARAM_SUBSUME_REGIONS);\n\t\t}\n\t}\n\t\n\t// Setters/getters\n\n\t/**\n\t * Set the attached model file (for e.g. reward structures when model checking)\n\t * and the attached properties file (for e.g. constants/labels when model checking)\n\t */\n\tpublic void setModelCheckingInfo(ModelInfo modelInfo, PropertiesFile propertiesFile, RewardGenerator<?> rewardGen)\n\t{\n\t\tthis.modelInfo = modelInfo;\n\t\tthis.propertiesFile = propertiesFile;\n\t\tthis.rewardGen = rewardGen;\n\t\t// Get combined constant values from model/properties\n\t\tconstantValues = new Values();\n\t\tconstantValues.addValues(modelInfo.getConstantValues());\n\t\tif (propertiesFile != null)\n\t\t\tconstantValues.addValues(propertiesFile.getConstantValues());\n\t}\n\n\tpublic ParamMode getMode()\n\t{\n\t\treturn mode;\n\t}\n\n\t// Model checking functions\n\n\t/**\n\t * Model check an expression, process and return the result.\n\t * Information about states and model constants should be attached to the model.\n\t * For other required info (labels, reward structures, etc.),\n\t * use the method {@link #setModelCheckingInfo(ModelInfo, PropertiesFile, RewardGenerator)}.\n\t */\n\tpublic Result check(Model<?> model, Expression expr) throws PrismException\n\t{\n\t\t// In \"exact\" mode, we first need to convert the rational probabilities to functions\n\t\t// Also store the original model for later use\n\t\tmodelOrig = model;\n\t\tif (mode == ParamMode.EXACT) {\n\t\t\tFunctionFactory functionFactory = FunctionFactory.createDummy(getSettings());\n\t\t\tEvaluator<Function> eval = Evaluator.forRationalFunction(functionFactory);\n\t\t\tmodel = ModelSimple.copy((Model<BigRational>) model, functionFactory::fromBigRational, eval);\n\t\t}\n\n\t\tfunctionFactory = ((Evaluator.EvaluatorFunction) model.getEvaluator()).getFunctionFactory();\n\t\tconstraintChecker = new ConstraintChecker(numRandomPoints);\n\t\tregionFactory = new BoxRegionFactory(functionFactory, constraintChecker, precision,\n\t\t\t\tmodel.getNumStates(), model.getFirstInitialState(), simplifyRegions, splitMethod);\n\t\tvalueComputer = new ValueComputer(this, mode, regionFactory, precision, eliminationOrder, bisimType);\n\t\t\n\t\tlong timer = 0;\n\t\t\n\t\t// Remove labels from property, using combined label list (on a copy of the expression)\n\t\t// This is done now so that we can handle labels nested below operators that are not\n\t\t// handled natively by the model checker yet (just evaluate()ed in a loop).\n\t\texpr = (Expression) expr.deepCopy().expandLabels(propertiesFile.getCombinedLabelList());\n\n\t\t// Also evaluate/replace any constants\n\t\t//expr = (Expression) expr.replaceConstants(constantValues);\n\n\t\t// Create storage for result\n\t\tresult = new Result();\n\n\t\t// Wrap a filter round the property, if needed\n\t\t// (in order to extract the final result of model checking) \n\t\texpr = ExpressionFilter.addDefaultFilterIfNeeded(expr, model.getNumInitialStates() == 1);\n\n\t\t// Do model checking and store result vector\n\t\ttimer = System.currentTimeMillis();\n\t\tBitSet needStates = new BitSet(model.getNumStates());\n\t\tneedStates.set(0, model.getNumStates());\n\t\tRegionValues vals = checkExpression(model, expr, needStates);\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"\\nTime for model checking: \" + timer / 1000.0 + \" seconds.\");\n\n\t\tif (constraintChecker.unsoundCheckWasUsed()) {\n\t\t\tmainLog.printWarning(\"Computation of Boolean values / parameter regions used heuristic sampling, results are potentially inaccurate.\");\n\t\t}\n\n\t\t/* // Output plot to tex file\n\t\tif (paramLower.length == 2) {\n\t\t\ttry {\n\t\t\t\tFileOutputStream file = new FileOutputStream(\"out.tex\");\n\t\t\t\tResultExporter printer = new ResultExporter();\n\t\t\t\tprinter.setOutputStream(file);\n\t\t\t\tprinter.setRegionValues(vals);\n\t\t\t\tprinter.setPointsPerDimension(19);\n\t\t\t\tprinter.print();\n\t\t\t\tfile.close();\n\t\t\t} catch (Exception e) {\n\t\t\t\tthrow new PrismException(\"file could not be written\");\n\t\t\t}\n\t\t}*/\n\n\t\t// Print result to log\n\t\tString resultString = \"Result\";\n\t\tif (!(\"Result\".equals(expr.getResultName())))\n\t\t\tresultString += \" (\" + expr.getResultName().toLowerCase() + \")\";\n\t\tresultString += \": \" + result.getResultAndAccuracy();\n\t\tmainLog.println(\"\\n\" + resultString);\n\n\t\t// Return result\n\t\treturn result;\n\t}\n\t\n\tprivate int parserBinaryOpToRegionOp(int parserOp) throws PrismException\n\t{\n\t\tint regionOp;\n\t\tswitch (parserOp) {\n\t\tcase ExpressionBinaryOp.IMPLIES:\n\t\t\tregionOp = Region.IMPLIES;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.IFF:\n\t\t\tregionOp = Region.IMPLIES;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.OR:\n\t\t\tregionOp = Region.OR;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.AND:\n\t\t\tregionOp = Region.AND;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.EQ:\n\t\t\tregionOp = Region.EQ;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.NE:\n\t\t\tregionOp = Region.NE;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.GT:\n\t\t\tregionOp = Region.GT;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.GE:\n\t\t\tregionOp = Region.GE;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.LT:\n\t\t\tregionOp = Region.LT;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.LE:\n\t\t\tregionOp = Region.LE;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.PLUS:\n\t\t\tregionOp = Region.PLUS;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.MINUS:\n\t\t\tregionOp = Region.MINUS;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.TIMES:\n\t\t\tregionOp = Region.TIMES;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.DIVIDE:\n\t\t\tregionOp = Region.DIVIDE;\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.POW:\n\t\t\tregionOp = Region.POW;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"operator \\\"\" + ExpressionBinaryOp.opSymbols[parserOp]\n\t\t\t\t\t+ \"\\\" not currently supported for \" + mode + \" analyses\");\n\t\t}\n\t\treturn regionOp;\n\t}\n\n\tprivate int parserUnaryOpToRegionOp(int parserOp) throws PrismException\n\t{\n\t\tint regionOp;\n\t\tswitch (parserOp) {\n\t\tcase ExpressionUnaryOp.MINUS:\n\t\t\tregionOp = Region.UMINUS;\n\t\t\tbreak;\n\t\tcase ExpressionUnaryOp.NOT:\n\t\t\tregionOp = Region.NOT;\n\t\t\tbreak;\n\t\tcase ExpressionUnaryOp.PARENTH:\n\t\t\tregionOp = Region.PARENTH;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"operator \\\"\" + ExpressionBinaryOp.opSymbols[parserOp]\n\t\t\t\t\t+ \"\\\" not currently supported for \" + mode + \" analyses\");\n\t\t}\n\t\treturn regionOp;\n\t}\n\n\t/**\n\t * Model check an expression and return a vector result values over all states.\n\t * Information about states and model constants should be attached to the model.\n\t * For other required info (labels, reward structures, etc.),\n\t * use the method {@link #setModelCheckingInfo(ModelInfo, PropertiesFile, RewardGenerator)}.\n\t */\n\tRegionValues checkExpression(Model<?> model, Expression expr, BitSet needStates) throws PrismException\n\t{\n\t\tRegionValues res;\n\t\tif (expr instanceof ExpressionUnaryOp) {\n\t\t\tres = checkExpressionUnaryOp(model, (ExpressionUnaryOp) expr, needStates);\n\t\t} else if (expr instanceof ExpressionBinaryOp) {\n\t\t\tres = checkExpressionBinaryOp(model, (ExpressionBinaryOp) expr, needStates);\n\t\t} else if (expr instanceof ExpressionITE) {\n\t\t\tres = checkExpressionITE(model, (ExpressionITE) expr, needStates);\n\t\t} else if (expr instanceof ExpressionLabel) {\n\t\t\tres = checkExpressionLabel(model, (ExpressionLabel) expr, needStates);\n\t\t} else if (expr instanceof ExpressionFormula) {\n\t\t\t// This should have been defined or expanded by now.\n\t\t\tif (((ExpressionFormula) expr).getDefinition() != null)\n\t\t\t\tres = checkExpression(model, ((ExpressionFormula) expr).getDefinition(), needStates);\n\t\t\telse\n\t\t\t\tthrow new PrismException(\"Unexpanded formula \\\"\" + ((ExpressionFormula) expr).getName() + \"\\\"\");\n\t\t} else if (expr instanceof ExpressionProp) {\n\t\t\tres = checkExpressionProp(model, (ExpressionProp) expr, needStates);\n\t\t} else if (expr instanceof ExpressionFilter) {\n\t\t\tif (((ExpressionFilter) expr).isParam()) {\n\t\t\t\tres = checkExpressionFilterParam(model, (ExpressionFilter) expr, needStates);\n\t\t\t} else {\n\t\t\t\tres = checkExpressionFilter(model, (ExpressionFilter) expr, needStates);\n\t\t\t}\n\t\t} else if (expr instanceof ExpressionProb) {\n\t\t\tres = checkExpressionProb(model, (ExpressionProb) expr, needStates);\n\t\t} else if (expr instanceof ExpressionReward) {\n\t\t\tres = checkExpressionReward(model, (ExpressionReward) expr, needStates);\n\t\t} else if (expr instanceof ExpressionSS) {\n\t\t\tres = checkExpressionSteadyState(model, (ExpressionSS) expr, needStates);\n\t\t} else if (expr instanceof ExpressionForAll || expr instanceof ExpressionExists) {\n\t\t\tthrow new PrismNotSupportedException(\"Non-probabilistic CTL model checking is currently not supported in the \" + mode.engine());\n\t\t} else if (expr instanceof ExpressionFunc && ((ExpressionFunc)expr).getNameCode() == ExpressionFunc.MULTI) {\n\t\t\tthrow new PrismNotSupportedException(\"Multi-objective model checking is not supported in the \" + mode.engine());\n\t\t} else {\n\t\t\tres = checkExpressionAtomic(model, expr, needStates);\n\t\t}\n\t\treturn res;\n\t}\n\n\tprivate RegionValues checkExpressionAtomic(Model<?> model, Expression expr, BitSet needStates) throws PrismException\n\t{\n\t\texpr = (Expression) expr.deepCopy().replaceConstants(constantValues);\n\t\t\n\t\tint numStates = model.getNumStates();\n\t\tList<State> statesList = model.getStatesList();\n\t\tStateValues stateValues = new StateValues(numStates, model.getFirstInitialState());\n\t\tint[] varMap = new int[statesList.get(0).varValues.length];\n\t\tfor (int var = 0; var < varMap.length; var++) {\n\t\t\tvarMap[var] = var;\n\t\t}\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tExpression exprVar = (Expression) expr.deepCopy().evaluatePartially(statesList.get(state), varMap);\n\t\t\tif (needStates.get(state)) {\n\t\t\t\tif (exprVar instanceof ExpressionLiteral) {\n\t\t\t\t\tExpressionLiteral exprLit = (ExpressionLiteral) exprVar;\n\t\t\t\t\tif (exprLit.getType() instanceof TypeBool) {\n\t\t\t\t\t\tstateValues.setStateValue(state, exprLit.evaluateBoolean());\n\t\t\t\t\t} else if (exprLit.getType() instanceof TypeInt || exprLit.getType() instanceof TypeDouble) {\n\t\t\t\t\t\tString exprStr = exprLit.getString();\n\t\t\t\t\t\tBigRational exprRat = new BigRational(exprStr);\n\t\t\t\t\t\tstateValues.setStateValue(state, functionFactory.fromBigRational(exprRat));\n\t\t\t\t\t} else {\n\t\t\t\t\t\tthrow new PrismNotSupportedException(\"model checking expresssion \" + expr + \" not supported for \" + mode + \" models\");\n\t\t\t\t\t}\n\t\t\t\t} else if (exprVar instanceof ExpressionConstant) {\n\t\t\t\t\tExpressionConstant exprConst = (ExpressionConstant) exprVar;\n\t\t\t\t\tstateValues.setStateValue(state, functionFactory.getVar(exprConst.getName()));\n\t\t\t\t} else {\n\t\t\t\t\tthrow new PrismNotSupportedException(\"cannot handle expression \" + expr + \" in \" + mode + \" analysis\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (exprVar.getType() instanceof TypeBool) {\n\t\t\t\t\tstateValues.setStateValue(state, false);\n\t\t\t\t} else {\n\t\t\t\t\tstateValues.setStateValue(state, functionFactory.getZero());\t\t\t\t\t\t\n\t\t\t\t}\n\t\t\t}\n\t\t}\t\n\t\treturn regionFactory.completeCover(stateValues);\n\t}\n\n\tprotected RegionValues checkExpressionUnaryOp(Model<?> model, ExpressionUnaryOp expr, BitSet needStates) throws PrismException\n\t{\n\t\tRegionValues resInner = checkExpression(model, expr.getOperand(), needStates);\n\t\tresInner.clearNotNeeded(needStates);\n\n\t\treturn resInner.unaryOp(parserUnaryOpToRegionOp(expr.getOperator()));\n\t}\n\n\t/**\n\t * Model check a binary operator.\n\t */\n\tprotected RegionValues checkExpressionBinaryOp(Model<?> model, ExpressionBinaryOp expr, BitSet needStates) throws PrismException\n\t{\n\t\tRegionValues res1 = checkExpression(model, expr.getOperand1(), needStates);\n\t\tRegionValues res2 = checkExpression(model, expr.getOperand2(), needStates);\n\t\tres1.clearNotNeeded(needStates);\n\t\tres2.clearNotNeeded(needStates);\n\n\t\treturn res1.binaryOp(parserBinaryOpToRegionOp(expr.getOperator()), res2);\n\t}\n\n\t/**\n\t * Model check an If-Then-Else operator.\n\t */\n\tprotected RegionValues checkExpressionITE(Model<?> model, ExpressionITE expr, BitSet needStates) throws PrismException\n\t{\n\t\tRegionValues resI = checkExpression(model, expr.getOperand1(), needStates);\n\t\tRegionValues resT = checkExpression(model, expr.getOperand2(), needStates);\n\t\tRegionValues resE = checkExpression(model, expr.getOperand3(), needStates);\n\t\tresI.clearNotNeeded(needStates);\n\t\tresT.clearNotNeeded(needStates);\n\t\tresE.clearNotNeeded(needStates);\n\n\t\treturn resI.ITE(resT, resE);\n\t}\n\n\t/**\n\t * Model check a label.\n\t */\n\tprotected RegionValues checkExpressionLabel(Model<?> model, ExpressionLabel expr, BitSet needStates) throws PrismException\n\t{\n\t\tLabelList ll;\n\t\tint i;\n\t\t\n\t\t// treat special cases\n\t\tif (expr.isDeadlockLabel()) {\n\t\t\tint numStates = model.getNumStates();\n\t\t\tStateValues stateValues = new StateValues(numStates, model.getFirstInitialState());\n\t\t\tfor (i = 0; i < numStates; i++) {\n\t\t\t\tstateValues.setStateValue(i, model.isDeadlockState(i));\n\t\t\t}\n\t\t\treturn regionFactory.completeCover(stateValues);\n\t\t} else if (expr.isInitLabel()) {\n\t\t\tint numStates = model.getNumStates();\n\t\t\tStateValues stateValues = new StateValues(numStates, model.getFirstInitialState());\n\t\t\tfor (i = 0; i < numStates; i++) {\n\t\t\t\tstateValues.setStateValue(i, model.isInitialState(i));\n\t\t\t}\n\t\t\treturn regionFactory.completeCover(stateValues);\n\t\t} else {\n\t\t\tll = propertiesFile.getCombinedLabelList();\n\t\t\ti = ll.getLabelIndex(expr.getName());\n\t\t\tif (i == -1)\n\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + expr.getName() + \"\\\" in property\");\n\t\t\t// check recursively\n\t\t\treturn checkExpression(model, ll.getLabel(i), needStates);\n\t\t}\n\t}\n\n\t// Check property ref\n\n\tprotected RegionValues checkExpressionProp(Model<?> model, ExpressionProp expr, BitSet needStates) throws PrismException\n\t{\n\t\t// Look up property and check recursively\n\t\tProperty prop = propertiesFile.lookUpPropertyObjectByName(expr.getName());\n\t\tif (prop != null) {\n\t\t\tmainLog.println(\"\\nModel checking : \" + prop);\n\t\t\treturn checkExpression(model, prop.getExpression(), needStates);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Unknown property reference \" + expr);\n\t\t}\n\t}\n\n\t// Check filter\n\n\tprotected RegionValues checkExpressionFilter(Model<?> model, ExpressionFilter expr, BitSet needStates) throws PrismException\n\t{\n\t\tExpression filter = expr.getFilter();\n\t\tif (filter == null) {\n\t\t\tfilter = Expression.True();\n\t\t}\n\t\tboolean filterTrue = Expression.isTrue(filter);\n\t\t\n\t\tBitSet needStatesInner = new BitSet(needStates.size());\n\t\tneedStatesInner.set(0, needStates.size());\n\t\tRegionValues rvFilter = checkExpression(model, filter, needStatesInner);\n\t\tif (!rvFilter.parameterIndependent()) {\n\t\t\tthrow new PrismException(\"currently, parameter-dependent filters are not supported\");\n\t\t}\n\t\tBitSet bsFilter = rvFilter.getStateValues().toBitSet();\n\t\t// Check filter satisfied by exactly one state\n\t\tFilterOperator op = expr.getOperatorType();\n\t\tif (op == FilterOperator.STATE && bsFilter.cardinality() != 1) {\n\t\t\tString s = \"Filter should be satisfied in exactly 1 state\";\n\t\t\ts += \" (but \\\"\" + filter + \"\\\" is true in \" + bsFilter.cardinality() + \" states)\";\n\t\t\tthrow new PrismException(s);\n\t\t}\n\t\tif (op == FilterOperator.FIRST) {\n\t\t\t// only first state is of interest\n\t\t\tbsFilter.clear(bsFilter.nextSetBit(0) + 1, bsFilter.length());\n\t\t}\n\t\tRegionValues vals = checkExpression(model, expr.getOperand(), bsFilter);\n\n\t\t// Check if filter state set is empty; we treat this as an error\n\t\tif (bsFilter.isEmpty()) {\n\t\t\tthrow new PrismException(\"Filter satisfies no states\");\n\t\t}\n\t\t\n\t\t// Remember whether filter is for the initial state and, if so, whether there's just one\n\t\tboolean filterInit = (filter instanceof ExpressionLabel && ((ExpressionLabel) filter).isInitLabel());\n\t\t// Print out number of states satisfying filter\n\t\tif (!filterInit) {\n\t\t\tmainLog.println(\"\\nStates satisfying filter \" + filter + \": \" + bsFilter.cardinality());\n\t\t}\n\t\t\t\n\t\t// Compute result according to filter type\n\t\tRegionValues resVals = null;\n\t\tswitch (op) {\n\t\tcase PRINT:\n\t\tcase PRINTALL:\n\t\t\t// Format of print-out depends on type\n\t\t\tif (expr.getType() instanceof TypeBool) {\n\t\t\t\t// NB: 'usual' case for filter(print,...) on Booleans is to use no filter\n\t\t\t\tmainLog.print(\"\\nSatisfying states\");\n\t\t\t\tmainLog.println(filterTrue ? \":\" : \" that are also in filter \" + filter + \":\");\n\t\t\t} else {\n\t\t\t\tmainLog.println(\"\\nResults (non-zero only) for filter \" + filter + \":\");\n\t\t\t}\n\n\t\t\tvals.printFiltered(mainLog, mode, expr.getType(), bsFilter,\n\t\t\t\t               model.getStatesList(),\n\t\t\t\t               op == FilterOperator.PRINT, // printSparse if PRINT\n\t\t\t\t               true,  // print state values\n\t\t\t\t               true); // print state index\n\n\t\t\tresVals = vals;\n\t\t\tbreak;\n\t\tcase MIN:\n\t\tcase MAX:\n\t\tcase ARGMIN:\n\t\tcase ARGMAX:\n\t\t\tthrow new PrismNotSupportedException(\"operation not implemented for \" + mode + \" models\");\n\t\tcase COUNT:\n\t\t\tresVals = vals.op(Region.COUNT, bsFilter);\n\t\t\tbreak;\n\t\tcase SUM:\n\t\t\tresVals = vals.op(Region.PLUS, bsFilter);\n\t\t\tbreak;\n\t\tcase AVG:\n\t\t\tresVals = vals.op(Region.AVG, bsFilter);\n\t\t\tbreak;\n\t\tcase FIRST:\n\t\t\tif (bsFilter.cardinality() < 1) {\n\t\t\t\tthrow new PrismException(\"Filter should be satisfied in at least 1 state.\");\n\t\t\t}\n\t\t\tresVals = vals.op(Region.FIRST, bsFilter);\n\t\t\tbreak;\n\t\tcase RANGE:\n\t\t\tthrow new PrismNotSupportedException(\"operation not implemented for \" + mode + \" models\");\n\t\tcase FORALL:\n\t\t\tresVals = vals.op(Region.FORALL, bsFilter);\n\t\t\tbreak;\n\t\tcase EXISTS:\n\t\t\tresVals = vals.op(Region.EXISTS, bsFilter);\n\t\t\tbreak;\n\t\tcase STATE:\n\t\t\tresVals = vals.op(Region.FIRST, bsFilter);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unrecognised filter type \\\"\" + expr.getOperatorName() + \"\\\"\");\n\t\t}\n\n\t\t// Store result\n\t\tvals.clearExceptInit();\n\t\tParamResult paramResult = new ParamResult(mode, resVals, functionFactory);\n\t\tif (mode == ParamMode.EXACT) {\n\t\t\t// Convert result of parametric model checking to a single value,\n\t\t\t// either boolean for boolean properties or a rational for numeric properties\n\t\t\t// There should be just one region since no parameters are used\n\t\t\tresult.setResult(paramResult.getSimpleResult(expr.getType()));\n\t\t} else {\n\t\t\tresult.setResult(paramResult);\n\t\t}\n\t\tresult.setAccuracy(new Accuracy(Accuracy.AccuracyLevel.EXACT));\n\t\tresult.setExplanation(null);\n\n\t\treturn resVals;\n\t}\n\n\t// check filter over parameters\n\t\n\tprotected RegionValues checkExpressionFilterParam(Model<?> model, ExpressionFilter expr, BitSet needStates) throws PrismException\n\t{\n\t\t// Filter info\n\t\tExpression filter = expr.getFilter();\n\t\t// Create default filter (true) if none given\n\t\tif (filter == null) {\n\t\t\tfilter = Expression.True();\n\t\t}\n\t\tRegionValues rvFilter = checkExpression(model, filter, needStates);\n\t\tRegionValues vals = checkExpression(model, expr.getOperand(), needStates);\n\n\t\tOptimiser opt = new Optimiser(vals, rvFilter, expr.getOperatorType() == FilterOperator.MIN);\n\t\tSystem.out.println(\"\\n\" + opt.optimise());\n\t\t\n\t\treturn null;\n\n\t\t/*\n\t\t// Remember whether filter is for the initial state and, if so, whether there's just one\n\t\tfilterInit = (filter instanceof ExpressionLabel && ((ExpressionLabel) filter).isInitLabel());\n\t\tfilterInitSingle = filterInit & model.getNumInitialStates() == 1;\n\t\t// Print out number of states satisfying filter\n\t\tif (!filterInit)\n\t\t\tmainLog.println(\"\\nStates satisfying filter \" + filter + \": \" + bsFilter.cardinality());\n\n\t\t// Compute result according to filter type\n\t\top = expr.getOperatorType();\n\t\tswitch (op) {\n\t\tcase PRINT:\n\t\t\t// Format of print-out depends on type\n\t\t\tif (expr.getType() instanceof TypeBool) {\n\t\t\t\t// NB: 'usual' case for filter(print,...) on Booleans is to use no filter\n\t\t\t\tmainLog.print(\"\\nSatisfying states\");\n\t\t\t\tmainLog.println(filterTrue ? \":\" : \" that are also in filter \" + filter + \":\");\n\t\t\t\tvals.printFiltered(mainLog, bsFilter);\n\t\t\t} else {\n\t\t\t\tmainLog.println(\"\\nResults (non-zero only) for filter \" + filter + \":\");\n\t\t\t\tvals.printFiltered(mainLog, bsFilter);\n\t\t\t}\n\t\t\t// Result vector is unchanged; for ARGMIN, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = vals;\n\t\t\t// Set vals to null to stop it being cleared below\n\t\t\tvals = null;\n\t\t\tbreak;\n\t\tcase MIN:\n\t\t\t// Compute min\n\t\t\t// Store as object/vector\n\t\t\tresObj = vals.minOverBitSet(bsFilter);\n\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Minimum value over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\t// Also find states that (are close to) selected value for display to log\n\t\t\t// TODO: un-hard-code precision once RegionValues knows hoe precise it is\n\t\t\tbsMatch = vals.getBitSetFromCloseValue(resObj, 1e-5, false);\n\t\t\tbsMatch.and(bsFilter);\n\t\t\tbreak;\n\t\tcase MAX:\n\t\t\t// Compute max\n\t\t\t// Store as object/vector\n\t\t\tresObj = vals.maxOverBitSet(bsFilter);\n\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Maximum value over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\t// Also find states that (are close to) selected value for display to log\n\t\t\t// TODO: un-hard-code precision once RegionValues knows hoe precise it is\n\t\t\tbsMatch = vals.getBitSetFromCloseValue(resObj, 1e-5, false);\n\t\t\tbsMatch.and(bsFilter);\n\t\t\tbreak;\n\t\tcase ARGMIN:\n\t\t\t// Compute/display min\n\t\t\tresObj = vals.minOverBitSet(bsFilter);\n\t\t\tmainLog.print(\"\\nMinimum value over \" + filterStatesString + \": \" + resObj);\n\t\t\t// Find states that (are close to) selected value\n\t\t\t// TODO: un-hard-code precision once RegionValues knows hoe precise it is\n\t\t\tbsMatch = vals.getBitSetFromCloseValue(resObj, 1e-5, false);\n\t\t\tbsMatch.and(bsFilter);\n\t\t\t// Store states in vector; for ARGMIN, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = RegionValues.createFromBitSet(bsMatch, model);\n\t\t\t// Print out number of matching states, but not the actual states\n\t\t\tmainLog.println(\"\\nNumber of states with minimum value: \" + bsMatch.cardinality());\n\t\t\tbsMatch = null;\n\t\t\tbreak;\n\t\tcase ARGMAX:\n\t\t\t// Compute/display max\n\t\t\tresObj = vals.maxOverBitSet(bsFilter);\n\t\t\tmainLog.print(\"\\nMaximum value over \" + filterStatesString + \": \" + resObj);\n\t\t\t// Find states that (are close to) selected value\n\t\t\tbsMatch = vals.getBitSetFromCloseValue(resObj, precision, false);\n\t\t\tbsMatch.and(bsFilter);\n\t\t\t// Store states in vector; for ARGMAX, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = RegionValues.createFromBitSet(bsMatch, model);\n\t\t\t// Print out number of matching states, but not the actual states\n\t\t\tmainLog.println(\"\\nNumber of states with maximum value: \" + bsMatch.cardinality());\n\t\t\tbsMatch = null;\n\t\t\tbreak;\n\t\tcase COUNT:\n\t\t\t// Compute count\n\t\t\tint count = vals.countOverBitSet(bsFilter);\n\t\t\t// Store as object/vector\n\t\t\tresObj = Integer.valueOf(count);\n\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = filterTrue ? \"Count of satisfying states\" : \"Count of satisfying states also in filter\";\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase SUM:\n\t\t\t// Compute sum\n\t\t\t// Store as object/vector\n\t\t\tresObj = vals.sumOverBitSet(bsFilter);\n\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Sum over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase AVG:\n\t\t\t// Compute average\n\t\t\t// Store as object/vector\n\t\t\tresObj = vals.averageOverBitSet(bsFilter);\n\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Average over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase FIRST:\n\t\t\t// Find first value\n\t\t\tresObj = vals.firstFromBitSet(bsFilter);\n\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Value in \";\n\t\t\tif (filterInit) {\n\t\t\t\tresultExpl += filterInitSingle ? \"the initial state\" : \"first initial state\";\n\t\t\t} else {\n\t\t\t\tresultExpl += filterTrue ? \"the first state\" : \"first state satisfying filter\";\n\t\t\t}\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase RANGE:\n\t\t\t// Find range of values\n\t\t\tresObj = new prism.Interval(vals.minOverBitSet(bsFilter), vals.maxOverBitSet(bsFilter));\n\t\t\t// Leave result vector unchanged: for a range, result is only available from Result object\n\t\t\tresVals = vals;\n\t\t\t// Set vals to null to stop it being cleared below\n\t\t\tvals = null;\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Range of values over \";\n\t\t\tresultExpl += filterInit ? \"initial states\" : filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase FORALL:\n\t\t\t// Get access to BitSet for this\n\t\t\tif(paras == null) {\n\t\t\t\tbs = vals.getBitSet();\n\t\t\t\t// Print some info to log\n\t\t\t\tmainLog.print(\"\\nNumber of states satisfying \" + expr.getOperand() + \": \");\n\t\t\t\tmainLog.print(bs.cardinality());\n\t\t\t\tmainLog.println(bs.cardinality() == model.getNumStates() ? \" (all in model)\" : \"\");\n\t\t\t\t// Check \"for all\" over filter\n\t\t\t\tb = vals.forallOverBitSet(bsFilter);\n\t\t\t\t// Store as object/vector\n\t\t\t\tresObj = Boolean.valueOf(b);\n\t\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t\t// Create explanation of result and print some details to log\n\t\t\t\tresultExpl = \"Property \" + (b ? \"\" : \"not \") + \"satisfied in \";\n\t\t\t\tmainLog.print(\"\\nProperty satisfied in \" + vals.countOverBitSet(bsFilter));\n\t\t\t\tif (filterInit) {\n\t\t\t\t\tif (filterInitSingle) {\n\t\t\t\t\t\tresultExpl += \"the initial state\";\n\t\t\t\t\t} else {\n\t\t\t\t\t\tresultExpl += \"all initial states\";\n\t\t\t\t\t}\n\t\t\t\t\tmainLog.println(\" of \" + model.getNumInitialStates() + \" initial states.\");\n\t\t\t\t} else {\n\t\t\t\t\tif (filterTrue) {\n\t\t\t\t\t\tresultExpl += \"all states\";\n\t\t\t\t\t\tmainLog.println(\" of all \" + model.getNumStates() + \" states.\");\n\t\t\t\t\t} else {\n\t\t\t\t\t\tresultExpl += \"all filter states\";\n\t\t\t\t\t\tmainLog.println(\" of \" + bsFilter.cardinality() + \" filter states.\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\t\tcase EXISTS:\n\t\t\t// Get access to BitSet for this\n\t\t\tbs = vals.getBitSet();\n\t\t\t// Check \"there exists\" over filter\n\t\t\tb = vals.existsOverBitSet(bsFilter);\n\t\t\t// Store as object/vector\n\t\t\tresObj = Boolean.valueOf(b);\n\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Property satisfied in \";\n\t\t\tif (filterTrue) {\n\t\t\t\tresultExpl += b ? \"at least one state\" : \"no states\";\n\t\t\t} else {\n\t\t\t\tresultExpl += b ? \"at least one filter state\" : \"no filter states\";\n\t\t\t}\n\t\t\tmainLog.println(\"\\n\" + resultExpl);\n\t\t\tbreak;\n\t\tcase STATE:\n\t\t\tif(paras == null) {\n\t\t\t\t// Check filter satisfied by exactly one state\n\t\t\t\tif (bsFilter.cardinality() != 1) {\n\t\t\t\t\tString s = \"Filter should be satisfied in exactly 1 state\";\n\t\t\t\t\ts += \" (but \\\"\" + filter + \"\\\" is true in \" + bsFilter.cardinality() + \" states)\";\n\t\t\t\t\tthrow new PrismException(s);\n\t\t\t\t}\n\t\t\t\t// Find first (only) value\n\t\t\t\t// Store as object/vector\n\t\t\t\tresObj = vals.firstFromBitSet(bsFilter);\n\t\t\t\tresVals = new RegionValues(expr.getType(), resObj, model); \n\t\t\t\t// Create explanation of result and print some details to log\n\t\t\t\tresultExpl = \"Value in \";\n\t\t\t\tif (filterInit) {\n\t\t\t\t\tresultExpl += \"the initial state\";\n\t\t\t\t} else {\n\t\t\t\t\tresultExpl += \"the filter state\";\n\t\t\t\t}\n\t\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unrecognised filter type \\\"\" + expr.getOperatorName() + \"\\\"\");\n\t\t}\n\n\t\t// For some operators, print out some matching states\n\t\tif (bsMatch != null) {\n\t\t\tstates = RegionValues.createFromBitSet(bsMatch, model);\n\t\t\tmainLog.print(\"\\nThere are \" + bsMatch.cardinality() + \" states with \");\n\t\t\tmainLog.print(expr.getType() instanceof TypeDouble ? \"(approximately) \" : \"\" + \"this value\");\n\t\t\tboolean verbose = verbosity > 0; // TODO\n\t\t\tif (!verbose && bsMatch.cardinality() > 10) {\n\t\t\t\tmainLog.print(\".\\nThe first 10 states are displayed below. To view them all, enable verbose mode or use a print filter.\\n\");\n\t\t\t\tstates.print(mainLog, 10);\n\t\t\t} else {\n\t\t\t\tmainLog.print(\":\\n\");\n\t\t\t\tstates.print(mainLog);\n\t\t\t}\n\t\t\t\n\t\t}\n\n\t\t// Store result\n\t\tresult.setResult(resObj);\n\t\t// Set result explanation (if none or disabled, clear)\n\t\tif (expr.getExplanationEnabled() && resultExpl != null) {\n\t\t\tresult.setExplanation(resultExpl.toLowerCase());\n\t\t} else {\n\t\t\tresult.setExplanation(null);\n\t\t}\n\n\t\t// Clear up\n\t\tif (vals != null)\n\t\t\tvals.clear();\n\n\t\treturn resVals;\n\t\t*/\n\t}\n\t\n\t/**\n\t * Model check a P operator expression and return the values for all states.\n\t */\n\tprotected RegionValues checkExpressionProb(Model<?> model, ExpressionProb expr, BitSet needStates) throws PrismException\n\t{\n\t\tExpression pb; // Probability bound (expression)\n\t\tBigRational p = null; // Probability bound (actual value)\n\t\t//String relOp; // Relational operator\n\t\t//boolean min = false; // For nondeterministic models, are we finding min (true) or max (false) probs\n\t\tModelType modelType = model.getModelType();\n\t\tRelOp relOp;\n\t\tboolean min = false;\n\n\t\tRegionValues probs = null;\n\n\t\t// Get info from prob operator\n\t\trelOp = expr.getRelOp();\n\t\tpb = expr.getProb();\n\t\tif (pb != null) {\n\t\t\tp = pb.evaluateBigRational(EvaluateContext.create(constantValues, EvaluateContext.EvalMode.EXACT));\n\t\t\tif (p.compareTo(0) == -1 || p.compareTo(1) == 1)\n\t\t\t\tthrow new PrismException(\"Invalid probability bound \" + p + \" in P operator\");\n\t\t}\n\t\tmin = relOp.isLowerBound() || relOp.isMin();\n\n\t\t// Compute probabilities\n\t\tif (!expr.getExpression().isSimplePathFormula()) {\n\t\t\tthrow new PrismNotSupportedException(mode.Engine() + \" does not yet handle LTL-style path formulas\");\n\t\t}\n\t\tprobs = checkProbPathFormulaSimple(model, expr.getExpression(), min, needStates);\n\t\tprobs.clearNotNeeded(needStates);\n\n\t\tif (verbosity > 5) {\n\t\t\tmainLog.print(\"\\nProbabilities (non-zero only) for all states:\\n\");\n\t\t\tmainLog.print(probs);\n\t\t}\n\t\t// For =? properties, just return values\n\t\tif (pb == null) {\n\t\t\treturn probs;\n\t\t}\n\t\t// Otherwise, compare against bound to get set of satisfying states\n\t\telse {\n\t\t\treturn probs.binaryOp(Region.getOp(relOp.toString()), p);\n\t\t}\n\t}\n\t\n\tprivate RegionValues checkProbPathFormulaSimple(Model<?> model, Expression expr, boolean min, BitSet needStates) throws PrismException\n\t{\n\t\tboolean negated = false;\n\t\tRegionValues probs = null;\n\t\t\n\t\texpr = Expression.convertSimplePathFormulaToCanonicalForm(expr);\n\t\t\n\t\t// Negation\n\t\tif (expr instanceof ExpressionUnaryOp &&\n\t\t    ((ExpressionUnaryOp)expr).getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\tnegated = true;\n\t\t\tmin = !min;\n\t\t\texpr = ((ExpressionUnaryOp)expr).getOperand();\n\t\t}\n\t\t\t\n\t\tif (expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\t\n\t\t\t// Next\n\t\t\tif (exprTemp.getOperator() == ExpressionTemporal.P_X) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Next operator not supported by \" + mode + \" engine\");\n\t\t\t}\n\t\t\t// Until\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\tBitSet needStatesInner = new BitSet(model.getNumStates());\n\t\t\t\tneedStatesInner.set(0, model.getNumStates());\n\t\t\t\tRegionValues b1 = checkExpression(model, exprTemp.getOperand1(), needStatesInner);\n\t\t\t\tRegionValues b2 = checkExpression(model, exprTemp.getOperand2(), needStatesInner);\n\t\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\t\tprobs = checkProbBoundedUntil(model, b1, b2, min);\n\t\t\t\t} else {\n\t\t\t\t\tprobs = checkProbUntil(model, b1, b2, min, needStates);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tif (probs == null)\n\t\t\tthrow new PrismException(\"Unrecognised path operator in P operator\");\n\n\t\tif (negated) {\n\t\t\t// Subtract from 1 for negation\n\t\t\tprobs = probs.binaryOp(new BigRational(1, 1), parserBinaryOpToRegionOp(ExpressionBinaryOp.MINUS));\n\t\t}\n\t\t\n\t\treturn probs;\n\t}\n\n\tprivate RegionValues checkProbUntil(Model<?> model, RegionValues b1, RegionValues b2, boolean min, BitSet needStates) throws PrismException\n\t{\n\t\tif (model.getModelType() == ModelType.MDP && settings.getBoolean(PrismSettings.PRISM_FAIRNESS)) {\n\t\t\tthrow new PrismNotSupportedException(\"Model checking MDPs under fairness not supported by \" + mode + \" engine\\\"\");\n\t\t}\n\t\treturn valueComputer.computeUnbounded(model, b1, b2, min, null);\n\t}\n\t\t\n\tprivate RegionValues checkProbBoundedUntil(Model<?> model, RegionValues b1, RegionValues b2, boolean min) throws PrismException {\n\t\tModelType modelType = model.getModelType();\n\t\t//RegionValues probs;\n\t\tswitch (modelType) {\n\t\tcase CTMC:\n\t\t\tthrow new PrismNotSupportedException(\"Bounded until operator not supported by \" + mode + \" engine\");\n\t\tcase DTMC:\n\t\t\tthrow new PrismNotSupportedException(\"Bounded until operator not supported by \" + mode + \" engine\");\n\t\tcase MDP:\n\t\t\tthrow new PrismNotSupportedException(\"Bounded until operator not supported by \" + mode + \" engine\");\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Cannot model check for a \" + modelType);\n\t\t}\n\n\t\t//return probs;\n\t}\n\n\t/**\n\t * Model check an R operator expression and return the values for all states.\n\t */\n\tprotected RegionValues checkExpressionReward(Model<?> model, ExpressionReward expr, BitSet needStates) throws PrismException\n\t{\n\t\tExpression rb; // Reward bound (expression)\n\t\tBigRational r = null; // Reward bound (actual value)\n\t\tRegionValues rews = null;\n\t\tboolean min = false;\n\n\t\t// Get info from reward operator\n\t\t\n\t\tRelOp relOp = expr.getRelOp();\n\t\trb = expr.getReward();\n\t\tif (rb != null) {\n\t\t\tr = rb.evaluateBigRational(EvaluateContext.create(constantValues, EvaluateContext.EvalMode.EXACT));\n\t\t\tif (r.compareTo(0) == -1)\n\t\t\t\tthrow new PrismException(\"Invalid reward bound \" + r + \" in R[] formula\");\n\t\t}\n\t\tmin = relOp.isLowerBound() || relOp.isMin();\n\n\t\t// Build rewards\n\t\tint r2 = expr.getRewardStructIndexByIndexObject(rewardGen, constantValues);\n\t\tmainLog.println(\"Building reward structure...\");\n\t\tRewards<?> rew = constructExpectedRewards(modelOrig, r2);\n\n\t\t// In \"exact\" mode, we first need to convert the rational rewards to functions\n\t\tif (mode == ParamMode.EXACT) {\n\t\t\trew = new RewardsSimple<>((Rewards<BigRational>) rew, model, functionFactory::fromBigRational, (Evaluator<Function>) model.getEvaluator());\n\t\t}\n\n\t\t// Compute rewards\n\t\trews = checkRewardFormula(model, rew, expr.getExpression(), min, needStates);\n\n\t\t// Print out rewards\n\t\tif (verbosity > 5) {\n\t\t\tmainLog.print(\"\\nProbabilities (non-zero only) for all states:\\n\");\n\t\t\tmainLog.print(rews);\n\t\t}\n\n\t\trews.clearNotNeeded(needStates);\n\t\t// For =? properties, just return values\n\t\tif (rb == null) {\n\t\t\treturn rews;\n\t\t}\n\t\t// Otherwise, compare against bound to get set of satisfying states\n\t\telse {\n\t\t\treturn rews.binaryOp(Region.getOp(relOp.toString()), r);\n\t\t}\n\t}\n\n\t/**\n\t * Construct rewards for the reward structure with index r of the reward generator and a model.\n\t * Ensures non-negative rewards.\n\t * <br>\n\t * Note: Relies on the stored RewardGenerator for constructing the reward structure.\n\t */\n\tprotected <Value> Rewards<Value> constructRewards(Model<Value> model, int r) throws PrismException\n\t{\n\t\tConstructRewards constructRewards = new ConstructRewards(this);\n\t\treturn constructRewards.buildRewardStructure(model, (RewardGenerator<Value>) rewardGen, r);\n\t}\n\n\t/**\n\t * Construct expected rewards for the reward structure with index r of the reward generator and a model,\n\t * i.e., using probability-weighted sum for any rewards attached to transitions,\n\t * assigning them to states/choices.\n\t * Ensures non-negative rewards.\n\t * <br>\n\t * Note: Relies on the stored RewardGenerator for constructing the reward structure.\n\t */\n\tprotected <Value> Rewards<Value> constructExpectedRewards(Model<Value> model, int r) throws PrismException\n\t{\n\t\tConstructRewards constructRewards = new ConstructRewards(this);\n\t\tconstructRewards.setExpectedRewards(true);\n\t\treturn constructRewards.buildRewardStructure(model, (RewardGenerator<Value>) rewardGen, r);\n\t}\n\n\tprivate RegionValues checkRewardFormula(Model<?> model,\n\t\t\tRewards<?> rew, Expression expr, boolean min, BitSet needStates) throws PrismException {\n\t\tRegionValues rewards = null;\n\n\t\tif (expr.getType() instanceof TypePathDouble) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\tswitch (exprTemp.getOperator()) {\n\t\t\tcase ExpressionTemporal.R_S:\n\t\t\t\trewards = checkRewardSteady(model, rew, exprTemp, min, needStates);\t\t\t\t\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismNotSupportedException(mode.Engine() + \" does not yet handle the \" + exprTemp.getOperatorSymbol() + \" operator in the R operator\");\n\t\t\t}\n\t\t} else if (expr.getType() instanceof TypePathBool || expr.getType() instanceof TypeBool) {\n\t\t\trewards = checkRewardPathFormula(model, rew, expr, min, needStates);\n\t\t}\n\n\t\tif (rewards == null) {\n\t\t\tthrow new PrismException(\"Unrecognised operator in R operator\");\n\t\t}\n\t\t\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute rewards for a path formula in a reward operator.\n\t */\n\tprivate RegionValues checkRewardPathFormula(Model<?> model, Rewards<?> rew, Expression expr, boolean min, BitSet needStates) throws PrismException\n\t{\n\t\tif (Expression.isReach(expr)) {\n\t\t\treturn checkRewardReach(model, rew, (ExpressionTemporal) expr, min, needStates);\n\t\t} else if (Expression.isCoSafeLTLSyntactic(expr, true)) {\n\t\t\tthrow new PrismNotSupportedException(mode.Engine() + \" does not yet support co-safe reward computation\");\n\t\t} else {\n\t\t\tthrow new PrismException(\"R operator contains a path formula that is not syntactically co-safe: \" + expr);\n\t\t}\n\t}\n\n\tprivate RegionValues checkRewardReach(Model<?> model,\n\t\t\tRewards<?> rew, ExpressionTemporal expr, boolean min, BitSet needStates) throws PrismException {\n\t\tRegionValues allTrue = regionFactory.completeCover(true);\n\t\tBitSet needStatesInner = new BitSet(needStates.size());\n\t\tneedStatesInner.set(0, needStates.size());\n\t\tRegionValues reachSet = checkExpression(model, expr.getOperand2(), needStatesInner);\n\t\treturn valueComputer.computeUnbounded(model, allTrue, reachSet, min, rew);\n\t}\n\t\n\tprivate RegionValues checkRewardSteady(Model<?> model,\n\t\t\tRewards<?> rew, ExpressionTemporal expr, boolean min, BitSet needStates) throws PrismException {\n\t\tif (model.getModelType() != ModelType.DTMC && model.getModelType() != ModelType.CTMC) {\n\t\t\tthrow new PrismNotSupportedException(mode.Engine() + \" long-run average rewards are only supported for DTMCs and CTMCs\");\n\t\t}\n\t\tRegionValues allTrue = regionFactory.completeCover(true);\n\t\tBitSet needStatesInner = new BitSet(needStates.size());\n\t\tneedStatesInner.set(0, needStates.size());\n\t\treturn valueComputer.computeSteadyState(model, allTrue, min, rew);\n\t}\n\n\t/**\n\t * Model check an S operator expression and return the values for all states.\n\t */\n\tprotected RegionValues checkExpressionSteadyState(Model<?> model, ExpressionSS expr, BitSet needStates) throws PrismException\n\t{\n\t\tExpression pb; // Probability bound (expression)\n\t\tBigRational p = null; // Probability bound (actual value)\n\t\t//String relOp; // Relational operator\n\t\t//boolean min = false; // For nondeterministic models, are we finding min (true) or max (false) probs\n\t\tModelType modelType = model.getModelType();\n\t\tRelOp relOp;\n\t\tboolean min = false;\n\n\t\tRegionValues probs = null;\n\n\t\t// Get info from prob operator\n\t\trelOp = expr.getRelOp();\n\t\tpb = expr.getProb();\n\t\tif (pb != null) {\n\t\t\tp = pb.evaluateBigRational(EvaluateContext.create(constantValues, EvaluateContext.EvalMode.EXACT));\n\t\t\tif (p.compareTo(0) == -1 || p.compareTo(1) == 1)\n\t\t\t\tthrow new PrismException(\"Invalid probability bound \" + p + \" in P operator\");\n\t\t}\n\t\tmin = relOp.isLowerBound() || relOp.isMin();\n\n\t\t// Compute probabilities\n\t\tprobs = checkProbSteadyState(model, expr.getExpression(), min, needStates);\n\n\t\tif (verbosity > 5) {\n\t\t\tmainLog.print(\"\\nProbabilities (non-zero only) for all states:\\n\");\n\t\t\tmainLog.print(probs);\n\t\t}\n\t\tprobs.clearNotNeeded(needStates);\n\t\t// For =? properties, just return values\n\t\tif (pb == null) {\n\t\t\treturn probs;\n\t\t}\n\t\t// Otherwise, compare against bound to get set of satisfying states\n\t\telse {\n\t\t\treturn probs.binaryOp(Region.getOp(relOp.toString()), p);\n\t\t}\n\t}\n\n\tprivate RegionValues checkProbSteadyState(Model<?> model, Expression expr, boolean min, BitSet needStates)\n\tthrows PrismException\n\t{\n\t\tBitSet needStatesInner = new BitSet(model.getNumStates());\n\t\tneedStatesInner.set(0, model.getNumStates());\n\t\tRegionValues b = checkExpression(model,expr, needStatesInner);\n\t\tif (model.getModelType() != ModelType.DTMC\n\t\t\t\t&& model.getModelType() != ModelType.CTMC) {\n\t\t\tthrow new PrismNotSupportedException(mode.Engine() + \" currently only implements steady state for DTMCs and CTMCs.\");\n\t\t}\n\t\treturn valueComputer.computeSteadyState(model, b, min, null);\n\t}\n\n\tpublic static void closeDown() {\n\t\tComputerThreads.terminate();\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/ParamResult.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Birmingham/Oxford)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage param;\n\nimport java.util.Collections;\nimport java.util.List;\n\nimport parser.EvaluateContext;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionLiteral;\nimport parser.type.Type;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismNotSupportedException;\n\n/**\n * Stores the result of a ParamModelChecker run (a RegionValues object)\n * as well as additional information (ParamMode, FunctionFactory)\n * that is needed to test the actual result against an expected result\n * (test mode).\n */\npublic class ParamResult\n{\n\t/** The computation mode (parametric / exact) */\n\tprivate ParamMode mode;\n\t/** The actual result */\n\tprivate RegionValues regionValues;\n\t/** The function factory used for model checking */\n\tprivate FunctionFactory factory;\n\n\t/**\n\t * Constructor\n\t * @param mode exact or parametric?\n\t * @param regionValues the actual result\n\t * @param factory the function factory used during checking\n\t */\n\tpublic ParamResult(ParamMode mode, RegionValues regionValues, FunctionFactory factory)\n\t{\n\t\tthis.mode = mode;\n\t\tthis.regionValues = regionValues;\n\t\tthis.factory = factory;\n\t}\n\n\t/**\n\t * Get the region values result.\n\t */\n\tpublic RegionValues getRegionValues()\n\t{\n\t\treturn regionValues;\n\t}\n\n\t/**\n\t * Returns the result (region values) as a String.\n\t */\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn regionValues.toStringInitState();\n\t}\n\n\t/**\n\t * If ParamModelChecker ran in exact mode (no parametric constants),\n\t * the result will consist of a single region and a single value instead\n\t * of a function.\n\t * <br>\n\t * This method returns this single value (either a Boolean or a BigRational).\n\t * @param propertyType the type of the checked property\n\t * @return Boolean/BigRational result (for the initial state)\n\t * @throws PrismException if there are multiple regions or the value is a function\n\t */\n\tpublic Object getSimpleResult(Type propertyType) throws PrismException\n\t{\n\t\tif (regionValues.getNumRegions() != 1)\n\t\t\tthrow new PrismException(\"Unexpected result from \" + mode + \" model checker\");\n\n\t\tif (propertyType.equals(TypeBool.getInstance())) {\n\t\t\t// boolean result\n\t\t\tboolean boolResult = regionValues.getResult(0).getInitStateValueAsBoolean();\n\t\t\treturn boolResult;\n\t\t} else {\n\t\t\t// numeric result\n\t\t\tparam.Function func = regionValues.getResult(0).getInitStateValueAsFunction();\n\t\t\t// Evaluate the function at an arbitrary point (should not depend on parameter values)\n\t\t\tBigRational rat = func.evaluate(new param.Point(new BigRational[] { new BigRational(0) }));\n\t\t\treturn rat;\n\t\t}\n\t}\n\n\t/**\n\t * Test the result against the given expected result string.\n\t * <br>\n\t * Returns true if the test succeeds, throws a PrismException\n\t * with an explanation otherwise.\n\t * @param propertyType the type of the checked property\n\t * @param strExpected the expected result (as a String)\n\t * @param constValues the model/property constants used during the checking\n\t * @param params The names of any parameters, i.e., still undefined constants (null if none)\n\t * @return true if the test succeeds\n\t * @throws PrismException on test failure\n\t */\n\tpublic boolean test(Type propertyType, String strExpected, Values constValues, List<String> params) throws PrismException\n\t{\n\t\tExpression exprExpected = null;\n\t\ttry {\n\t\t\tif (strExpected.equals(\"Infinity\") || strExpected.equals(\"+Infinity\") || strExpected.equals(\"Inf\") || strExpected.equals(\"+Inf\")) {\n\t\t\t\texprExpected = new ExpressionLiteral(TypeDouble.getInstance(), BigRational.INF);\n\t\t\t} else if (strExpected.equals(\"-Infinity\") || strExpected.equals(\"-Inf\")) {\n\t\t\t\texprExpected = new ExpressionLiteral(TypeDouble.getInstance(), BigRational.MINF);\n\t\t\t} else if (strExpected.equals(\"NaN\")) {\n\t\t\t\texprExpected =  new ExpressionLiteral(TypeDouble.getInstance(), BigRational.NAN);\n\t\t\t} else {\n\t\t\t\t// Parse expression\n\t\t\t\texprExpected = Prism.parseSingleExpressionString(strExpected);\n\t\t\t\t// And find constants: either defined constants or parametric constants\n\t\t\t\texprExpected = (Expression) exprExpected.findAllConstants(constValues.getNames(), constValues.getTypes());\n\t\t\t\texprExpected = (Expression) exprExpected.findAllConstants(params, Collections.nCopies(params.size(), TypeDouble.getInstance()));\n\t\t\t\t// Type check and plug in values for constants that have them\n\t\t\t\texprExpected.typeCheck();\n\t\t\t\texprExpected = (Expression) exprExpected.evaluatePartially(constValues);\n\t\t\t}\n\t\t} catch (PrismLangException e) {\n\t\t\tthrow new PrismException(\"Invalid RESULT specification \\\"\" + strExpected + \"\\\" for property: \" + e.getMessage());\n\t\t}\n\t\treturn test(propertyType, exprExpected, strExpected);\n\t}\n\n\t/**\n\t * Test the result against the given expression.\n\t * <br>\n\t * Returns true if the test succeeds, throws a PrismException\n\t * with an explanation otherwise.\n\t * @param expected expression for the expected result\n\t * @param strExpected the expected result (as a String, for display in error messages)\n\t * @param propertyType the type of the checked property\n\t * @return true if the test succeeds\n\t * @throws PrismException on test failure\n\t */\n\tprivate boolean test(Type propertyType, Expression expected, String strExpected) throws PrismException\n\t{\n\t\tif (regionValues.getNumRegions() != 1) {\n\t\t\tthrow new PrismNotSupportedException(\"Testing \" + mode + \" results with multiple regions not supported\");\n\t\t}\n\n\t\tif (propertyType.equals(TypeBool.getInstance())) {\n\t\t\t// boolean result\n\t\t\tboolean boolResult = regionValues.getResult(0).getInitStateValueAsBoolean();\n\t\t\tboolean boolExpected = expected.evaluateBoolean(EvaluateContext.create(EvaluateContext.EvalMode.EXACT));\n\n\t\t\tif (boolResult != boolExpected) {\n\t\t\t\tthrow new PrismException(\"Wrong result (expected \" + strExpected + \", got \" + boolResult + \")\");\n\t\t\t}\n\t\t} else {\n\t\t\t// numeric result\n\t\t\tFunction funcExpected;\n\t\t\ttry {\n\t\t\t\tfuncExpected = factory.expr2function(expected);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow new PrismException(\"Invalid (or unsupported) RESULT specification \\\"\" + strExpected + \"\\\" for \" + mode + \" property\");\n\t\t\t}\n\t\t\tparam.Function func = regionValues.getResult(0).getInitStateValueAsFunction();\n\n\t\t\tif (!func.equals(funcExpected)) {\n\t\t\t\tthrow new PrismException(\"Wrong result (expected \" + strExpected + \" = \" + funcExpected + \", got \" + func + \")\");\n\t\t\t}\n\t\t}\n\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/Partition.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.Comparator;\nimport java.util.HashSet;\nimport java.util.PriorityQueue;\n\n/**\n * Stores a given partitioning of the states of a Markov model.\n * This class is intended to be used in combination with signature-based\n * partitioning refinement. In addition to storing the states, it can also\n * compute which blocks become subject to change due to changes in other\n * blocks.  \n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class Partition {\n\t/**\n\t * Comparator class comparing integer hash sets according to their size.\n\t *\n\t * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n\t */\n\tfinal class HashSetSizeComparator implements Comparator<HashSet<Integer>> {\n\t\t@Override\n\t\tpublic int compare(HashSet<Integer> o1, HashSet<Integer> o2) {\n\t\t\tint size1 = o1.size();\n\t\t\tint size2 = o2.size();\n\t\t\t// TODO should actually be other way round, but slower then... ??\n\t\t\tif (size1 < size2) {\n\t\t\t\treturn 1;\n\t\t\t} else if (size1 == size2) {\n\t\t\t\treturn 0;\n\t\t\t} else {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean equals(Object obj) {\n\t\t\treturn obj instanceof HashSetSizeComparator;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic int hashCode() {\n\t\t\treturn 0;\n\t\t}\n\t}\n\n\t/** parametric Markov chain this partition is for */\n\tprivate MutablePMC pmc;\n\t/** all blocks of this partitioning */\n\tprivate HashSet<HashSet<Integer>> blocks;\n\t/** maps states to the block they are contained in */\n\tprivate ArrayList<HashSet<Integer>> stateToBlock;\n\t/** list of blocks which might need to be refined */\n\tprivate PriorityQueue<HashSet<Integer>> mayChange;\n\t/** hash set of blocks which might need to be refined */\n\tprivate HashSet<HashSet<Integer>> mayChangeHash;\n\t/** next block to refine */\n\tprivate HashSet<Integer> nextBlock;\n\n\t/**\n\t * Creates new partitioning for given parametric Markov chain.\n\t * Initially, all states will be in the same block.\n\t * \n\t * @param pmc parametric Markov chain to create partitioning of\n\t */\n\tPartition(MutablePMC pmc)\n\t{\n\t\tthis.pmc = pmc;\n\t\tblocks = new HashSet<HashSet<Integer>>();\n\t\tstateToBlock = new ArrayList<HashSet<Integer>>(pmc.getNumStates());\n\t\tHashSet<Integer> initialBlock = new HashSet<Integer>(1);\n\t\tmayChange = new PriorityQueue<HashSet<Integer>>(11, new HashSetSizeComparator());\n\t\tmayChangeHash = new HashSet<HashSet<Integer>>();\n\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\tinitialBlock.add(state);\n\t\t\tstateToBlock.add(initialBlock);\n\t\t}\n\t\tblocks.add(initialBlock);\n\t\tmayChange.add(initialBlock);\n\t\tmayChangeHash.add(initialBlock);\n\t}\n\n\t/**\n\t * Obtain the next changeable block, according to their priority (size).\n\t * \n\t * @return next changeable block\n\t */\n\tHashSet<Integer> nextChangeableBlock()\n\t{\n\t\tnextBlock = mayChange.poll();\n\t\tmayChangeHash.remove(nextBlock);\n\t\tblocks.remove(nextBlock);\n\t\treturn nextBlock;\n\t}\n\n\t/**\n\t * Add a list of new blocks to list of blocks.\n\t * Also marks existing blocks as subject to change in case they have\n\t * transitions into these new blocks, and thus might have to be split. \n\t * \n\t * @param newBlocks list of blocks to add\n\t */\n\tvoid addBlocks(ArrayList<HashSet<Integer>> newBlocks)\n\t{\n\t\tblocks.addAll(newBlocks);\n\t\t\n\t\tfor (HashSet<Integer> block : newBlocks) {\n\t\t\tfor (int state : block) {\n\t\t\t\tstateToBlock.set(state, block);\n\t\t\t}\n\t\t\tif (block.equals(nextBlock)) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tmayChange.add(block);\n\t\t\tmayChangeHash.add(block);\n\t\t}\n\t\tfor (HashSet<Integer> block : newBlocks) {\n\t\t\tfor (int state : block) {\t\t\n\t\t\t\tfor (int predec : pmc.incoming.get(state)) {\n\t\t\t\t\tHashSet<Integer> predecBlock = stateToBlock.get(predec);\n\t\t\t\t\tif (!nextBlock.contains(predec) && !mayChangeHash.contains(predecBlock) && (predecBlock.size() > 1)) {\n\t\t\t\t\t\tmayChange.add(predecBlock);\n\t\t\t\t\t\tmayChangeHash.add(predecBlock);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Checks whether there are blocks remaining which might need refinement.\n\t * \n\t * @return true iff blocks are remaining which might need refinement\n\t */\n\tboolean mayChange()\n\t{\n\t\treturn !mayChange.isEmpty();\n\t}\n\t\n\t/**\n\t * Obtain a list of all blocks of the partition. \n\t * \n\t * @return list of all blocks of the partition\n\t */\n\tArrayList<HashSet<Integer>> getAllBlocks()\n\t{\n\t\tArrayList<HashSet<Integer>> allBlocks = new ArrayList<HashSet<Integer>>(blocks.size());\n\t\tfor (HashSet<Integer> block : blocks) {\n\t\t\tallBlocks.add(block);\n\t\t}\n\t\t\n\t\treturn allBlocks;\n\t}\n\t\n\t/**\n\t * Get the block in which a given state is contained.\n\t * \n\t * @param state state to search containing block of\n\t * @return block state is contained in\n\t */\n\tHashSet<Integer> getStateBlock(int state)\n\t{\n\t\treturn stateToBlock.get(state);\n\t}\n\t\n\t/**\n\t * Marks all blocks as being new.\n\t */\n\tvoid markAllBlocksAsNew()\n\t{\n\t\tmayChange.clear();\n\t\tmayChangeHash.clear();\n\t\tfor (HashSet<Integer> block : blocks) {\n\t\t\tmayChange.add(block);\n\t\t\tmayChangeHash.add(block);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/Point.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\n/**\n * Represents a given evaluation of parameters.\n * Objects of this class are immutable. Once it is created, no further changes\n * are possible. Objects of this class are mainly intended to be used with\n * {@code Region} objects, which represent sets of points, and check\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see Region\n */\npublic final class Point\n{\n\t/** coordinates of point */\n\tprivate BigRational[] dimensions;\n\n\t/**\n\t * Constructs a new point.\n\t * \n\t * @param dimensions coordinates of this point\n\t */\n\tpublic Point(BigRational[] dimensions)\n\t{\n\t\tthis.dimensions = new BigRational[dimensions.length];\n\t\tSystem.arraycopy(dimensions, 0, this.dimensions, 0, dimensions.length);\n\t}\n\n\t/**\n\t * Returns value of a given coordinate\n\t * @param dim coordinate to return value of\n\t * @return value of given coordinate\n\t */\n\tpublic BigRational getDimension(int dim)\n\t{\n\t\treturn dimensions[dim];\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\n\t\tbuilder.append(\"(\");\n\t\tfor (int dim = 0; dim < dimensions.length; dim++) {\n\t\t\tbuilder.append(dimensions[dim].doubleValue());\n\t\t\tif (dim != dimensions.length - 1) {\n\t\t\t\tbuilder.append(\",\");\n\t\t\t}\n\t\t}\n\t\tbuilder.append(\")\");\n\n\t\treturn builder.toString();\n\t}\n\n\t/**\n\t * Returns array representation of point.\n\t * \n\t * @return array representation of point\n\t */\n\tpublic BigRational[] toArray()\n\t{\n\t\tBigRational[] result = new BigRational[dimensions.length];\n\t\tSystem.arraycopy(this.dimensions, 0, result, 0, this.dimensions.length);\n\t\treturn result;\n\t}\n\n\t/**\n\t * Returns number of dimensions of point.\n\t * \n\t * @return number of dimensions of point\n\t */\n\tpublic int size()\n\t{\n\t\treturn dimensions.length;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (!(obj instanceof Point)) {\n\t\t\treturn false;\n\t\t}\n\n\t\tPoint other = (Point) obj;\n\t\tif (this.dimensions.length != other.dimensions.length) {\n\t\t\treturn false;\n\t\t}\n\t\tfor (int dim = 0; dim < dimensions.length; dim++) {\n\t\t\tif (!this.dimensions[dim].equals(other.dimensions[dim])) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tint hash = 0;\n\n\t\tfor (int i = 0; i < dimensions.length; i++) {\n\t\t\thash = dimensions[i].hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t}\n\n\t\treturn hash;\n\t}\n\n\t/**\n\t * Returns array of doubles approximating this point.\n\t * \n\t * @return array of doubles approximating this point\n\t */\n\tdouble[] doubleValues()\n\t{\n\t\tdouble[] result = new double[dimensions.length];\n\t\tfor (int dim = 0; dim < dimensions.length; dim++) {\n\t\t\tresult[dim] = dimensions[dim].doubleValue();\n\t\t}\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/Polynomial.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.math.BigInteger;\nimport java.util.ArrayList;\nimport java.util.HashMap;\n\n// TODO terms should be sorted. will become necessary if a Function is\n// implemented which directly uses objects of this class to store\n// rational functions\n\n/**\n * A polynomial exressed as a sum of terms.\n * Once a polynomial is fully constructed, it is immutable and cannot\n * be changed anymore. \n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class Polynomial {\n\t/** number of variables in this polynomial */ \n\tprivate int numVariables;\n\t/** coefficients of this polynomial. */\n\tprivate BigInteger[] coefficients;\n\t/** exponents of each term. for each term, there are {@code numVariables}\n\t * entries in exponents in this array, followed by the entries for\n\t * the next term (if any). */\n\tprivate int[] exponents;\n\tprivate HashMap<Point,BigRational> pointsSeen;\n\t/** current size of the polynomial. used during its construction. */\n\tprivate int size;\n\t\n\t/**\n\t * Constructs a new polynomial.\n\t * \n\t * @param numVariables number of variables the polynomial will have\n\t * @param numTerms final number of terms after construction\n\t */\n\tPolynomial(int numVariables, int numTerms)\n\t{\n\t\tcoefficients = new BigInteger[numTerms];\n\t\texponents = new int[numTerms * numVariables];\n\t\tthis.numVariables = numVariables;\n\t\tthis.pointsSeen = new HashMap<Point,BigRational>();\n\t\tthis.size = 0;\n\t}\n\t\n\t/**\n\t * Adds a term to a polynomial.\n\t * To be used during its construction.\n\t * \n\t * @param coefficient\n\t * @param monomial\n\t */\n\tvoid addTerm(BigInteger coefficient, ArrayList<Integer> monomial)\n\t{\n\t\tcoefficients[size] = coefficient;\n\t\tfor (int i = 0; i < monomial.size(); i++) {\n\t\t\texponents[numVariables * size + i] = monomial.get(i);\n\t\t}\n\t\tsize++;\n\t}\n\t\n\t/**\n\t * Checks whether this polynomial is equal to the given object.\n\t * For this to hold, {@code obj} must be a polynomial, and it\n\t * must be the same polynomial as this polynomial.\n\t * \n\t * @param obj object to compare against\n\t * @return true iff {@code obj} is a polynomial which equals this polynomial\n\t */\n\t@Override\n\tpublic boolean equals(Object obj) {\n\t\tif (!(obj instanceof Polynomial)) {\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\tPolynomial other = (Polynomial) obj;\n\t\tif (this.numVariables != other.numVariables) {\n\t\t\treturn false;\n\t\t}\n\t\tif (this.coefficients.length != other.coefficients.length) {\n\t\t\treturn false;\n\t\t}\n\t\tfor (int i = 0; i < this.coefficients.length; i++) {\n\t\t\tif (!this.coefficients[i].equals(other.coefficients[i])) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\tfor (int i = 0; i < this.exponents.length; i++) {\n\t\t\tif (this.exponents[i] != other.exponents[i]) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn true;\n\t}\n\t\n\t/**\n\t * Returns a hashcode for this polynomial.\n\t * \n\t * @return hash code for this polynomial\n\t */\n\t@Override\n\tpublic int hashCode() {\n\t\tint hash = numVariables;\n\t\t\n\t\tfor (int i = 0; i < exponents.length; i++) {\n\t\t\thash = exponents[i] + (hash << 6) + (hash << 16) - hash;\n\t\t}\n\t\t\n\t\tfor (int i = 0; i < coefficients.length; i++) {\n\t\t\thash = coefficients[i].hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t}\n\n\t\treturn hash;\n\t}\n\n\t/**\n\t * Returns a string representation of the polynomial.\n\t * \n\t * @return string representation of the polynomial\n\t */\n\t@Override\n\tpublic String toString() {\n\t\tStringBuilder builder = new StringBuilder();\n\t\tfor (int term = 0; term < coefficients.length; term++) {\n\t\t\tBigInteger coeff = coefficients[term];\n\t\t\t\n\t\t\tif (coeff.signum() > -1) {\n\t\t\t\tif (term != 0) {\n\t\t\t\t\tbuilder.append(\" + \");\n\t\t\t\t}\n\t\t\t\tbuilder.append(coeff);\n\t\t\t} else {\n\t\t\t\tif (term == 0) {\n\t\t\t\t\tbuilder.append(\"-\");\n\t\t\t\t} else {\n\t\t\t\t\tbuilder.append(\" - \");\n\t\t\t\t}\n\t\t\t\tbuilder.append(coeff.negate());\n\t\t\t}\n\n\t\t\tbuilder.append(\"*\");\n\t\t\tfor (int var = 0; var < numVariables; var++) {\n\t\t\t\tint power = exponents[numVariables * term + var];\n\t\t\t\tbuilder.append(\"x\");\n\t\t\t\tbuilder.append(var);\n\t\t\t\tbuilder.append(\"^\");\n\t\t\t\tbuilder.append(power);\n\t\t\t\tif (var < numVariables - 1) {\n\t\t\t\t\tbuilder.append(\"*\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn builder.toString();\n\t}\n\n\t/**\n\t * Evaluates a polynomial at a given point.\n\t * {@code point} must have the same dimension as the number of variables\n\t * for this to work correctly. {@code cancel} specifies whether the\n\t * result is to be brought into coprime form.\n\t * \n\t * @param point point to evaluate polynomial at\n\t * @param cancel whether to make result coprime\n\t * @return value of polynomial at given point\n\t */\n\tBigRational evaluate(Point point, boolean cancel)\n\t{\n\t\tlong time = System.currentTimeMillis();\n\t\tBigRational result = pointsSeen.get(point);\n\t\tif (result != null) {\n\t\t\tif (!cancel) {\n\t\t\t\ttime = System.currentTimeMillis() - time;\n\t\t\t\treturn result;\n\t\t\t} else {\n\t\t\t\ttime = System.currentTimeMillis() - time;\n\t\t\t\treturn result.cancel();\n\t\t\t}\n\t\t}\n\t\tresult = BigRational.ZERO;\n\t\t\n\t\tfor (int coeffNr = 0; coeffNr < coefficients.length; coeffNr++) {\n\t\t\tBigRational coeffVal = new BigRational(coefficients[coeffNr]);\n\t\t\tfor (int var = 0; var < numVariables; var++) {\n\t\t\t\tBigRational exp = point.getDimension(var).pow(exponents[coeffNr * numVariables + var]);\n\t\t\t\tcoeffVal = coeffVal.multiply(exp, cancel);\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\tresult = result.add(coeffVal, cancel);\n\t\t}\n\t\tpointsSeen.put(point, result);\n\t\ttime = System.currentTimeMillis() - time;\n\t\treturn result;\n\t}\n\t\n\t/**\n\t * Evaluates a polynomial at a given point.\n\t * {@code point} must have the same dimension as the number of variables\n\t * for this to work correctly. Result is brought into coprime form.\n\t * \n\t * @param point point to evaluate polynomial at\n\t * @return value of polynomial at given point\n\t */\n\tBigRational evaluate(Point point)\n\t{\n\t\treturn evaluate(point, true);\n\t}\n\n\t/**\n\t * Checks whether the value of this polynomial is (strictly) greater zero. \n\t * \n\t * @param point point to evaluate polynomial at\n\t * @param strict true for strictly greater zero, greater or equal else\n\t * @return true if value at given {@code point} is (strictly) greater zero\n\t */\n\tboolean check(Point point, boolean strict)\n\t{\n\t\tBigRational value = evaluate(point, false);\n\t\tint compare = value.signum();\n\t\treturn strict ? (compare > 0) : (compare >= 0);\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/RahdConstraintChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.io.BufferedReader;\nimport java.io.IOException;\nimport java.io.InputStreamReader;\n\n/**\n * TODO complete\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class RahdConstraintChecker extends ConstraintChecker {\n\t// TODO read from PrismSettings\n\tfinal static String rahdBin = \"/home/scratch/svn/pers-sb/rahd/rahd-bin\";\t\n\n\tpublic RahdConstraintChecker(int numRandomPoints) {\n\t\tsuper(numRandomPoints);\n\t}\n\t\n\tprivate boolean runRahd(Region region, String formula)\n\t{\n\t\tboolean ok = false;\n\t\tStringBuilder varBuilder = new StringBuilder();\n\t\tfor (int var = 0; var < region.getDimensions(); var++) {\n\t\t\tvarBuilder.append(\"x\");\n\t\t\tvarBuilder.append(var);\n\t\t\tvarBuilder.append(\" \");\n\t\t}\n\t\t\t\n\t\tString[] command = {\"timeout\", \"5m\", rahdBin, \"-v\", varBuilder.toString(), \"-f\", formula};\n\t\tProcess p = null;\n\t\ttry {\n\t\t\tp = Runtime.getRuntime().exec(command);\n\n\t\t\tBufferedReader bri = new BufferedReader(new InputStreamReader(p.getInputStream()));\n\t\t\tString line;\n\t\t\twhile ((line = bri.readLine()) != null) {\n\t\t\t\tif (line.equals(\" unsat\")) {\n\t\t\t\t\tok = true;\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\te.printStackTrace();\n\t\t}\n\t\treturn ok;\n\t}\n\t\n\tprivate String buildRegionString(Region region)\n\t{\n\t\tBoxRegion boxRegion = (BoxRegion) region;\n\t\tStringBuilder result = new StringBuilder();\n\t\tfor (int dim = 0; dim < region.getDimensions(); dim++) {\n\t\t\tresult.append(\"x\");\n\t\t\tresult.append(dim);\n\t\t\tresult.append(\">=\");\n\t\t\tresult.append(boxRegion.getDimensionLower(dim));\n\t\t\tresult.append(\" /\\\\ \");\n\t\t\tresult.append(\"x\");\n\t\t\tresult.append(dim);\n\t\t\tresult.append(\"<=\");\n\t\t\tresult.append(boxRegion.getDimensionUpper(dim));\n\t\t\tif (dim < region.getDimensions() - 1) {\n\t\t\t\tresult.append(\" /\\\\ \");\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn result.toString();\n\t}\n\t\n\t@Override\n\tboolean mainCheck(Region region, Function poly, boolean strict) {\n\t\tString regionString = buildRegionString(region);\n\n\t\treturn runRahd(region, regionString + \" /\\\\ \" + poly + (strict ? \" <= 0\" : \" < 0\"));\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/param/Region.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\n\n/**\n * A region represents a subset of the valid parameter values.\n * New regions can be produced using the corresponding {@code RegionFactory},\n * or by applying operations on existing ones.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see RegionFactory\n */\nabstract class Region {\n\tstatic final int IMPLIES = 1;\n\tstatic final int IFF = 2;\n\tstatic final int OR = 3;\n\tstatic final int AND = 4;\n\tstatic final int EQ = 5;\n\tstatic final int NE = 6;\n\tstatic final int GT = 7;\n\tstatic final int GE = 8;\n\tstatic final int LT = 9;\n\tstatic final int LE = 10;\n\tstatic final int PLUS = 11;\n\tstatic final int MINUS = 12;\n\tstatic final int TIMES = 13;\n\tstatic final int DIVIDE = 14;\n\tstatic final int FIRST = 15;\n\tstatic final int AVG = 16;\n\tstatic final int COUNT = 17;\n\tstatic final int UMINUS = 18;\n\tstatic final int NOT = 19;\n\tstatic final int PARENTH = 20;\n\tstatic final int FORALL = 21;\n\tstatic final int EXISTS = 22;\n\tstatic final int POW = 23;\n\tstatic final String opSymbols[] = { \"\", \"=>\", \"<=>\", \"|\", \"&\", \"=\", \"!=\", \">\", \">=\", \"<\", \"<=\", \"+\", \"-\", \"*\", \"/\", \"1st\", \"avg\", \"-\", \"!\", \"()\", \"forall\", \"exists\", \"^\" };\n\n\t/** region factory to which this region belongs */\n\tprotected RegionFactory factory;\n\t\n\tabstract int getDimensions();\n\t\n\t/**\n\t * Get lower bound of the volume of the region.\n\t * The volumes of disjoint region which cover the whole parameter\n\t * space sum up to 1. This implies that the volumes are normalised\n\t * according to the upper and lower bounds of the parameters.\n\t * \n\t * @return lower bound of the volume of this region\n\t */\n\tabstract BigRational volume();\n\t\n\t/**\n\t * Checks whether this region contains the point {@code point}.\n\t * \n\t * @param point point to check whether contained in this region\n\t * @return true if the point is contained in this region, false else\n\t */\n\tabstract boolean contains(Point point);\n\t\n\t/**\n\t * Checks whether region {@code other} is contained in this region.\n\t * \n\t * @param other check whether contained in this region\n\t * @return true iff {@code other} is contained in this region\n\t */\n\tabstract boolean contains(Region other);\n\t\n\tabstract RegionValues binaryOp(int op, StateValues values1, StateValues values2);\n\n\tabstract RegionValues ITE(StateValues valueI, StateValues valueT, StateValues valueE);\n\n\t/**\n\t * Splits this region into several parts.\n\t * How this is done exactly depends on the implementation in derived\n\t * classes. Can take constraint into account.\n\t * \n\t * @param constraint\n\t */\n\tabstract ArrayList<Region> split(Function constraint);\n\n\t/**\n\t * Splits this region into several parts.\n\t * How this is done exactly depends on the implementation in derived\n\t * classes.\n\t */\n\tabstract ArrayList<Region> split();\n\n\tabstract ArrayList<Point> specialPoints();\n\n\tabstract Point randomPoint();\n\n\t/**\n\t * Returns the region factory of this region.\n\t * \n\t * @return region factory of this region\n\t */\n\tRegionFactory getFactory() {\n\t\treturn factory;\n\t}\n\n\t/**\n\t * Returns the region operator by its string representation.\n\t * If the string is not a valid operator, a {@code RuntimeException}\n\t * will result.\n\t * \n\t * @param opString string to convert to operator\n\t * @return operator from string\n\t */\n\tstatic int getOp(String opString) {\n\t\tfor (int symNr = 0; symNr < Region.opSymbols.length; symNr++) {\n\t\t\tif (opString.equals(Region.opSymbols[symNr])) {\n\t\t\t\treturn symNr;\n\t\t\t}\n\t\t}\n\t\tthrow new RuntimeException(\"bad operator\");\n\t}\n\n\t/**\n\t * Returns the region which is the conjunction of this and {@code other} region.\n\t * \n\t * @param other region to build conjunction with\n\t * @return conjunction of this and the other region\n\t */\n\tabstract Region conjunct(Region other);\n\n\t/**\n\t * Checks whether this region is adjacent to another region.\n\t * In this case, both can be glued by @{code glue}.\n\t * \n\t * @param other region to check whether adjacent to\n\t * @return true iff regions are adjacent\n\t */\n\tabstract boolean adjacent(Region other);\n\n\t/**\n\t * Glues this region with the adjacent region other.\n\t * \n\t * @param other region to glue this region with\n\t * @return combined region\n\t */\n\tabstract Region glue(Region other);\n}\n"
  },
  {
    "path": "prism/src/param/RegionFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\n/**\n * Class to produce new regions of a given subclass of {@code Region}.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see RegionFactory\n */\nabstract class RegionFactory {\n\t/** function factory used to produce functions used as values of regions */\n\tprotected FunctionFactory functionFactory;\n\t/** constraint checker to check properties of regions */\n\tprotected ConstraintChecker constraintChecker;\n\t/** maximal amount of undecided area for region cover produced */\n\tprotected BigRational precision;\n\t/** initial state of the model the considered */\n\tprotected int initialState;\n\t/** number of states of the model used */\n\tprotected int numStates;\n\t/** decides whether regions should be subsumed if possible,\n\t * that is if they can be represented by a single larger region\n\t * and are assigned the same values */\n\tprotected boolean subsumeRegions;\n\n\t/**\n\t * Covers the whole parameter space with the values specified.\n\t * \n\t * @param values values to assign to each state for all valid valuations\n\t * @return cover of whole parameter region\n\t */\n\tabstract RegionValues completeCover(StateValues values);\n\t\n\t/**\n\t * Covers the whole parameter space with the values specified.\n\t * Assigns the same values to each state.\n\t * \n\t * @param value values to assign for all valid evaluations (same for each state)\n\t * @return cover of whole parameter region\n\t */\n\tRegionValues completeCover(StateValue value)\n\t{\n\t\tStateValues values = new StateValues(numStates, initialState, value);\n\t\treturn completeCover(values);\n\t}\n\n\t/**\n\t * Covers the whole parameter space with the values specified.\n\t * Assigns the same values to each state.\n\t * \n\t * @param value values to assign for all valid evaluations (same for each state)\n\t * @return cover of whole parameter region\n\t */\n\tRegionValues completeCover(boolean value)\n\t{\n\t\treturn completeCover(new StateBoolean(value));\n\t}\n\t\n\t/**\n\t * Get lower bound of given parameter.\n\t * \n\t * @param dim parameter to get lower bound of\n\t * @return lower bound of given parameter\n\t */\n\tBigRational getLowerBound(int dim)\n\t{\n\t\treturn functionFactory.getLowerBound(dim);\n\t}\n\t\n\t/**\n\t * Get upper bound of given parameter.\n\t * \n\t * @param dim parameter to get upper bound fo\n\t * @return upper bound of given parameter\n\t */\n\tBigRational getUpperBound(int dim)\n\t{\n\t\treturn functionFactory.getUpperBound(dim);\n\t}\n\t\n\t/**\n\t * Returns diameter of range of given variable {@code dim}.\n\t * \n\t * @param dim variable to return diameter of\n\t * @return diameter of range of variable {@code dim}\n\t */\n\tBigRational sideWidth(int dim)\n\t{\n\t\treturn functionFactory.getUpperBound(dim).subtract(functionFactory.getLowerBound(dim));\n\t}\n\t\n\t/**\n\t * Returns function factory used to produce functions used as values of regions.\n\t * @return function factory used to produce functions used as values of regions\n\t */\n\tFunctionFactory getFunctionFactory()\n\t{\n\t\treturn functionFactory;\n\t}\n\t\n\t/**\n\t * Returns constraint checker to check properties of regions.\n\t * \n\t * @return constraint checker to check properties of regions\n\t */\n\tConstraintChecker getConstraintChecker()\n\t{\n\t\treturn constraintChecker;\n\t}\n\t\n\t/**\n\t * Returns maximal amount of undecided area for region cover produced.\n\t * \n\t * @return maximal amount of undecided area for region cover produced\n\t */\n\tBigRational getPrecision()\n\t{\n\t\treturn precision;\n\t}\n\n\t/**\n\t * Returns number of parameters used.\n\t * \n\t * @return number of parameters\n\t */\n\tint numVariables() {\n\t\treturn functionFactory.getNumVariables();\n\t}\n\n\t/**\n\t * Returns number of states of the model this {@code RegionFactory} is used for.\n\t * \n\t * @return number of states\n\t */\n\tint getNumStates()\n\t{\n\t\treturn numStates;\n\t}\n\t\n\t/**\n\t * Returns the initial state of the model this {@code RegionFactory} is used for.\n\t * \n\t * @return initial state of model\n\t */\n\tint getInitialState()\n\t{\n\t\treturn initialState;\n\t}\n\t\n\t/**\n\t * Returns whether regions are to be subsumed if possible.\n\t * \n\t * @return true iff regions shall be subsumed if possible\n\t */\n\tboolean isSubsumeRegions()\n\t{\n\t\treturn subsumeRegions;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/RegionIntersection.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\n/**\n * Maintains the intersection of two regions.\n * This class is to be used in combination with\n * {@code RegionValuesIntersections} to iterate over the intersection\n * of two (or three) {@RegionValues}.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see RegionValuesIntersections\n */\nfinal class RegionIntersection {\n\tprivate Region region;\n\tprivate StateValues values1;\n\tprivate StateValues values2;\n\tprivate StateValues values3;\n\n\tpublic RegionIntersection(Region region, StateValues values1, StateValues values2)\n\t{\n\t\tthis(region, values1, values2, null);\n\t}\n\n\tpublic RegionIntersection(Region region, StateValues values1, StateValues values2, StateValues values3)\n\t{\n\t\tthis.region = region;\n\t\tthis.values1 = values1;\n\t\tthis.values2 = values2;\n\t\tthis.values3 = values3;\n\t}\n\n\tpublic Region getRegion()\n\t{\n\t\treturn region;\n\t}\n\n\tpublic StateValues getStateValues1()\n\t{\n\t\treturn values1;\n\t}\n\t\n\tpublic StateValues getStateValues2()\n\t{\n\t\treturn values2;\n\t}\n\n\tpublic StateValues getStateValues3()\n\t{\n\t\treturn values3;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/param/RegionValues.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.ArrayList;\nimport java.util.HashSet;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Map.Entry;\n\nimport parser.State;\nimport prism.PrismLog;\n\n/**\n * Assigns to the different regions different values over model states.\n * For each region for which values have been decided, an object of this\n * class contains a value for each state.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\npublic final class RegionValues implements Iterable<Entry<Region, StateValues>>\n{\n\t/** list of all regions */\n\tprivate ArrayList<Region> regions;\n\t/** assigning values to regions */\n\tprivate HashMap<Region, StateValues> values;\n\t/** region factory this object belongs to */\n\tprivate RegionFactory factory;\n\n\t// constructors\n\n\tpublic RegionValues(RegionFactory factory)\n\t{\n\t\tregions = new ArrayList<Region>();\n\t\tvalues = new HashMap<Region, StateValues>();\n\t\tthis.factory = factory;\n\t}\n\n\tpublic int getNumStates()\n\t{\n\t\treturn factory.getNumStates();\n\t}\n\n\tpublic int getInitState()\n\t{\n\t\treturn factory.getInitialState();\n\t}\n\n\tpublic void add(Region region, StateValues result)\n\t{\n\t\tregions.add(region);\n\t\tvalues.put(region, result);\n\t}\n\n\t/**\n\t * Helper function for simplify.\n\t * Subsumes some of the regions. If it contains true, must be called\n\t * again until it returns false.\n\t * \n\t * @return true iff regions were subsumed\n\t */\n\tprivate boolean simplifyIter()\n\t{\n\t\tboolean changed = false;\n\t\tArrayList<Region> newRegions = new ArrayList<Region>();\n\t\tHashMap<Region, StateValues> newValues = new HashMap<Region, StateValues>();\n\t\tHashSet<Region> done = new HashSet<Region>();\n\n\t\tfor (Region region1 : regions) {\n\t\t\tfor (Region region2 : regions) {\n\t\t\t\tif (values.get(region1).equals(values.get(region2)) && region1.adjacent(region2) && !done.contains(region1) && !done.contains(region2)) {\n\t\t\t\t\tdone.add(region1);\n\t\t\t\t\tdone.add(region2);\n\t\t\t\t\tRegion newRegion = region1.glue(region2);\n\t\t\t\t\tnewRegions.add(newRegion);\n\t\t\t\t\tnewValues.put(newRegion, values.get(region1));\n\t\t\t\t\tchanged = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tfor (Region region : regions) {\n\t\t\tif (!done.contains(region)) {\n\t\t\t\tnewRegions.add(region);\n\t\t\t\tnewValues.put(region, values.get(region));\n\t\t\t}\n\t\t}\n\n\t\tregions.clear();\n\t\tvalues.clear();\n\t\tregions.addAll(newRegions);\n\t\tvalues.putAll(newValues);\n\n\t\treturn changed;\n\t}\n\n\t/**\n\t * Simplify by subsuming adjacent regions with same value.\n\t */\n\tpublic void simplify()\n\t{\n\t\tif (factory.isSubsumeRegions()) {\n\t\t\twhile (simplifyIter())\n\t\t\t\t;\n\t\t}\n\t}\n\n\tpublic Region getRegion(int number)\n\t{\n\t\treturn regions.get(number);\n\t}\n\n\tpublic int getNumRegions()\n\t{\n\t\treturn regions.size();\n\t}\n\n\tpublic StateValues getResult(int number)\n\t{\n\t\treturn values.get(regions.get(number));\n\t}\n\n\tpublic StateValues getResult(Region region)\n\t{\n\t\treturn values.get(region);\n\t}\n\n\tpublic void cosplit(RegionValues other)\n\t{\n\t\tthis.simplify();\n\t\tother.simplify();\n\n\t\tArrayList<Region> newRegions = new ArrayList<Region>();\n\t\tHashMap<Region, StateValues> thisNewStateValues = new HashMap<Region, StateValues>();\n\t\tHashMap<Region, StateValues> otherNewStateValues = new HashMap<Region, StateValues>();\n\t\tfor (Region thisRegion : this.regions) {\n\t\t\tfor (Region otherRegion : other.regions) {\n\t\t\t\tRegion newRegion = thisRegion.conjunct(otherRegion);\n\t\t\t\tif (newRegion != null) {\n\t\t\t\t\tnewRegions.add(newRegion);\n\t\t\t\t\tthisNewStateValues.put(newRegion, this.values.get(thisRegion));\n\t\t\t\t\totherNewStateValues.put(newRegion, other.values.get(otherRegion));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tthis.regions = new ArrayList<Region>(newRegions);\n\t\tthis.values = thisNewStateValues;\n\t\tother.regions = new ArrayList<Region>(newRegions);\n\t\tother.values = otherNewStateValues;\n\t}\n\n\tpublic void cosplit(RegionValues other, RegionValues other2)\n\t{\n\t\tthis.simplify();\n\t\tother.simplify();\n\t\tother2.simplify();\n\n\t\tArrayList<Region> newRegions = new ArrayList<Region>();\n\t\tHashMap<Region, StateValues> thisNewStateValues = new HashMap<Region, StateValues>();\n\t\tHashMap<Region, StateValues> otherNewStateValues = new HashMap<Region, StateValues>();\n\t\tHashMap<Region, StateValues> other2NewStateValues = new HashMap<Region, StateValues>();\n\t\tfor (Region thisRegion : this.regions) {\n\t\t\tfor (Region otherRegion : other.regions) {\n\t\t\t\tfor (Region other2Region : other2.regions) {\n\t\t\t\t\tRegion newRegion = thisRegion.conjunct(otherRegion);\n\t\t\t\t\tif (newRegion != null)\n\t\t\t\t\t\tnewRegion = newRegion.conjunct(other2Region);\n\t\t\t\t\tif (newRegion != null) {\n\t\t\t\t\t\tnewRegions.add(newRegion);\n\t\t\t\t\t\tthisNewStateValues.put(newRegion, this.values.get(thisRegion));\n\t\t\t\t\t\totherNewStateValues.put(newRegion, other.values.get(otherRegion));\n\t\t\t\t\t\tother2NewStateValues.put(newRegion, other2.values.get(other2Region));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tthis.regions = new ArrayList<Region>(newRegions);\n\t\tthis.values = thisNewStateValues;\n\t\tother.regions = new ArrayList<Region>(newRegions);\n\t\tother.values = otherNewStateValues;\n\t\tother2.regions = new ArrayList<Region>(newRegions);\n\t\tother2.values = other2NewStateValues;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\t\tfor (int i = 0; i < regions.size(); i++) {\n\t\t\tif (i > 0) {\n\t\t\t\tbuilder.append(\", \");\n\t\t\t}\n\t\t\tRegion region = regions.get(i);\n\t\t\tbuilder.append(region);\n\t\t\tbuilder.append(\": \");\n\t\t\tbuilder.append(values.get(region));\n\t\t}\n\n\t\treturn builder.toString();\n\t}\n\n\tpublic String toStringInitState()\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\t\tfor (int i = 0; i < regions.size(); i++) {\n\t\t\tif (i > 0) {\n\t\t\t\tbuilder.append(\", \");\n\t\t\t}\n\t\t\tRegion region = regions.get(i);\n\t\t\tbuilder.append(region);\n\t\t\tbuilder.append(\": \");\n\t\t\tbuilder.append(values.get(region).getInitStateValue());\n\t\t}\n\n\t\treturn builder.toString();\n\t}\n\n\tpublic void addAll(RegionValues other)\n\t{\n\t\tint numOtherRegions = other.getNumRegions();\n\t\tfor (int i = 0; i < numOtherRegions; i++) {\n\t\t\tRegion region = other.getRegion(i);\n\t\t\tregions.add(region);\n\t\t\tvalues.put(region, other.getResult(region));\n\t\t}\n\t}\n\n\tpublic void clearExcept(BitSet except)\n\t{\n\t\tfor (Region region : regions) {\n\t\t\tStateValues vals = values.get(region);\n\t\t\tfor (int state = 0; state < vals.getNumStates(); state++) {\n\t\t\t\tif (!except.get(state)) {\n\t\t\t\t\tStateValue oldValue = vals.getStateValue(state);\n\t\t\t\t\tif (oldValue instanceof StateBoolean) {\n\t\t\t\t\t\tvals.setStateValue(state, false);\n\t\t\t\t\t} else if (oldValue instanceof Function) {\n\t\t\t\t\t\tvals.setStateValue(state, factory.getFunctionFactory().getZero());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tthrow new RuntimeException();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tsimplify();\n\t}\n\n\tpublic void clearExceptInit()\n\t{\n\t\tif (regions.isEmpty()) {\n\t\t\treturn;\n\t\t}\n\t\tint numStates = values.get(regions.get(0)).getNumStates();\n\t\tBitSet except = new BitSet(numStates);\n\t\texcept.set(factory.getInitialState(), true);\n\t\tclearExcept(except);\n\t}\n\n\t@Override\n\tpublic Iterator<Entry<Region, StateValues>> iterator()\n\t{\n\t\treturn values.entrySet().iterator();\n\t}\n\n\tpublic RegionFactory getRegionFactory()\n\t{\n\t\treturn factory;\n\t}\n\n\tpublic boolean booleanValues()\n\t{\n\t\tif (regions.isEmpty()) {\n\t\t\treturn true;\n\t\t}\n\t\treturn values.get(regions.get(0)).getStateValue(0) instanceof StateBoolean;\n\t}\n\n\tpublic RegionValues binaryOp(int op, RegionValues other)\n\t{\n\t\tRegionValues result = new RegionValues(factory);\n\t\tRegionValuesIntersections co = new RegionValuesIntersections(this, other);\n\t\tfor (RegionIntersection inter : co) {\n\t\t\tRegion region = inter.getRegion();\n\t\t\tStateValues value1 = inter.getStateValues1();\n\t\t\tStateValues value2 = inter.getStateValues2();\n\t\t\tRegionValues values = region.binaryOp(op, value1, value2);\n\t\t\tresult.addAll(values);\n\t\t}\n\t\treturn result;\n\t}\n\n\tpublic RegionValues binaryOp(int op, BigRational p)\n\t{\n\t\tRegionValues result = new RegionValues(factory);\n\t\tFunction pFn = factory.getFunctionFactory().fromBigRational(p);\n\t\tStateValues pValue = new StateValues(values.get(regions.get(0)).getNumStates(), factory.getInitialState(), pFn);\n\t\tfor (Region region : regions) {\n\t\t\tRegionValues vals = region.binaryOp(op, values.get(region), pValue);\n\t\t\tresult.addAll(vals);\n\t\t}\n\t\treturn result;\n\t}\n\n\tpublic RegionValues binaryOp(BigRational p, int op)\n\t{\n\t\tRegionValues result = new RegionValues(factory);\n\t\tFunction pFn = factory.getFunctionFactory().fromBigRational(p);\n\t\tStateValues pValue = new StateValues(values.get(regions.get(0)).getNumStates(), factory.getInitialState(), pFn);\n\t\tfor (Region region : regions) {\n\t\t\tRegionValues vals = region.binaryOp(op, pValue, values.get(region));\n\t\t\tresult.addAll(vals);\n\t\t}\n\t\treturn result;\n\t}\n\n\tpublic RegionValues op(int op, BitSet whichStates)\n\t{\n\t\tRegionValues result = new RegionValues(factory);\n\t\tif (op == Region.FIRST) {\n\t\t\tfor (Region region : regions) {\n\t\t\t\tStateValue firstValue;\n\t\t\t\tint firstState = whichStates.nextSetBit(0);\n\t\t\t\tfirstValue = values.get(region).getStateValue(firstState);\n\t\t\t\tStateValues resValues = new StateValues(getNumStates(), getInitState());\n\t\t\t\tfor (int state = 0; state < getNumStates(); state++) {\n\t\t\t\t\tresValues.setStateValue(state, firstValue);\n\t\t\t\t}\n\t\t\t\tresult.add(region, resValues);\n\t\t\t}\n\t\t} else if (op == Region.PLUS || op == Region.AVG) {\n\t\t\tfor (Region region : regions) {\n\t\t\t\tStateValues vals = values.get(region);\n\t\t\t\tFunction sum = factory.getFunctionFactory().getZero();\n\t\t\t\tfor (int state = 0; state < getNumStates(); state++) {\n\t\t\t\t\tif (whichStates.get(state)) {\n\t\t\t\t\t\tsum = sum.add(vals.getStateValueAsFunction(state));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (op == Region.AVG) {\n\t\t\t\t\tsum = sum.divide(whichStates.cardinality());\n\t\t\t\t}\n\t\t\t\tStateValues resValues = new StateValues(getNumStates(), getInitState(), sum);\n\t\t\t\tresult.add(region, resValues);\n\t\t\t}\n\t\t} else if (op == Region.COUNT) {\n\t\t\tfor (Region region : regions) {\n\t\t\t\tStateValues vals = values.get(region);\n\t\t\t\tint count = 0;\n\t\t\t\tfor (int state = 0; state < getNumStates(); state++) {\n\t\t\t\t\tif (whichStates.get(state)) {\n\t\t\t\t\t\tif (vals.getStateValueAsBoolean(state)) {\n\t\t\t\t\t\t\tcount++;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tFunction countFn = factory.getFunctionFactory().fromLong(count);\n\t\t\t\tStateValues resValues = new StateValues(getNumStates(), getInitState(), countFn);\n\t\t\t\tresult.add(region, resValues);\n\t\t\t}\n\t\t} else if (op == Region.FORALL) {\n\t\t\tfor (Region region : regions) {\n\t\t\t\tStateValues vals = values.get(region);\n\t\t\t\tboolean forall = true;\n\t\t\t\tfor (int state = 0; state < getNumStates(); state++) {\n\t\t\t\t\tif (whichStates.get(state)) {\n\t\t\t\t\t\tif (!vals.getStateValueAsBoolean(state)) {\n\t\t\t\t\t\t\tforall = false;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tStateValues resValues = new StateValues(getNumStates(), getInitState(), forall);\n\t\t\t\tresult.add(region, resValues);\n\t\t\t}\n\t\t} else if (op == Region.EXISTS) {\n\t\t\tfor (Region region : regions) {\n\t\t\t\tStateValues vals = values.get(region);\n\t\t\t\tboolean exists = false;\n\t\t\t\tfor (int state = 0; state < getNumStates(); state++) {\n\t\t\t\t\tif (whichStates.get(state)) {\n\t\t\t\t\t\tif (vals.getStateValueAsBoolean(state)) {\n\t\t\t\t\t\t\texists = true;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tStateValues resValues = new StateValues(getNumStates(), getInitState(), exists);\n\t\t\t\tresult.add(region, resValues);\n\t\t\t}\n\t\t} else {\n\t\t\tthrow new RuntimeException(\"unknown operator\");\n\t\t}\n\n\t\treturn result;\n\t}\n\n\tpublic boolean parameterIndependent()\n\t{\n\t\tsimplify();\n\t\tif (regions.size() > 1) {\n\t\t\treturn false;\n\t\t}\n\t\tif (!regions.get(0).volume().equals(factory.getFunctionFactory().getOne().asBigRational())) {\n\t\t\treturn false;\n\t\t}\n\n\t\treturn true;\n\t}\n\n\tpublic StateValues getStateValues()\n\t{\n\t\treturn values.get(regions.get(0));\n\t}\n\n\tpublic void clearNotNeeded(BitSet needStates)\n\t{\n\t\tfor (Region region : regions) {\n\t\t\tStateValues vals = values.get(region);\n\t\t\tfor (int state = 0; state < vals.getNumStates(); state++) {\n\t\t\t\tif (!needStates.get(state)) {\n\t\t\t\t\tif (vals.getStateValue(state) instanceof Function) {\n\t\t\t\t\t\tvals.setStateValue(state, factory.getFunctionFactory().getZero());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tvals.setStateValue(state, false);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tsimplify();\n\t}\n\n\tpublic String filteredString(BitSet filter)\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\n\t\tfor (Region region : regions) {\n\t\t\tbuilder.append(region);\n\t\t\tStateValues vals = values.get(region);\n\t\t\tfor (int stateNr = filter.nextSetBit(0); stateNr >= 0; stateNr = filter.nextSetBit(stateNr + 1)) {\n\t\t\t\tbuilder.append(stateNr);\n\t\t\t\tbuilder.append(\":\");\n\t\t\t\t//\t\t\t\tbuilder.append(statesList.get(stateNr).toString());\n\t\t\t\tbuilder.append(\"=\");\n\t\t\t\tbuilder.append(vals.getStateValue(stateNr));\n\t\t\t}\n\t\t}\n\n\t\treturn builder.toString();\n\t}\n\n\t/**\n\t * For each region, print part of vector to a log/file.\n\t * @param log The log\n\t * @param mode the mode\n\t * @param filter A BitSet specifying which states to print for (null if all).\n\t * @param printSparse Print non-zero/non-false elements only?\n\t * @param printStates Print states (variable values) for each element?\n\t * @param printIndices Print state indices for each element?\n\t */\n\tpublic void printFiltered(PrismLog log, ParamMode mode, parser.type.Type type, BitSet filter, List<State> statesList, boolean printSparse, boolean printStates, boolean printIndices)\n\t{\n\t\tif (mode == ParamMode.EXACT) {\n\t\t\tassert(parameterIndependent());\n\t\t\tgetStateValues().printFiltered(log, mode, type, filter, statesList, printSparse, printStates, printIndices);\n\t\t} else {\n\t\t\tfor (Region region : regions) {\n\t\t\t\tlog.println(region + \":\");\n\t\t\t\tStateValues vals = values.get(region);\n\t\t\t\tvals.printFiltered(log, mode, type, filter, statesList, printSparse, printStates, printIndices);\n\t\t\t\tlog.println();\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic RegionValues unaryOp(int parserUnaryOpToRegionOp)\n\t{\n\t\tRegionValues result = new RegionValues(factory);\n\t\tfor (Region region : regions) {\n\t\t\tStateValues value = unaryOp(parserUnaryOpToRegionOp, values.get(region));\n\t\t\tresult.add(region, value);\n\t\t}\n\t\treturn result;\n\t}\n\n\tprivate StateValues unaryOp(int op, StateValues stateValues)\n\t{\n\t\tStateValues result = new StateValues(getNumStates(), getInitState());\n\t\tfor (int state = 0; state < stateValues.getNumStates(); state++) {\n\t\t\tStateValue value = null;\n\t\t\tswitch (op) {\n\t\t\tcase Region.UMINUS:\n\t\t\t\tvalue = stateValues.getStateValueAsFunction(state).negate();\n\t\t\t\tbreak;\n\t\t\tcase Region.NOT:\n\t\t\t\tvalue = new StateBoolean(!stateValues.getStateValueAsBoolean(state));\n\t\t\t\tbreak;\n\t\t\tcase Region.PARENTH:\n\t\t\t\tvalue = stateValues.getStateValue(state);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tresult.setStateValue(state, value);\n\t\t}\n\t\treturn result;\n\t}\n\n\tpublic RegionValues ITE(RegionValues resT, RegionValues resE)\n\t{\n\t\tRegionValues result = new RegionValues(factory);\n\t\tRegionValuesIntersections co = new RegionValuesIntersections(this, resT, resE);\n\t\tfor (RegionIntersection inter : co) {\n\t\t\tRegion region = inter.getRegion();\n\t\t\tStateValues valueI = inter.getStateValues1();\n\t\t\tStateValues valueT = inter.getStateValues2();\n\t\t\tStateValues valueE = inter.getStateValues3();\n\t\t\tRegionValues values = region.ITE(valueI, valueT, valueE);\n\t\t\tresult.addAll(values);\n\t\t}\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/RegionValuesIntersections.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.Iterator;\nimport java.util.NoSuchElementException;\n\n/**\n * Computes the intersections of two (or three) regions.\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class RegionValuesIntersections implements Iterable<RegionIntersection> {\n\tfinal private class RegionIntersectionOperator implements Iterator<RegionIntersection> {\n\t\tprivate RegionValues regions1;\n\t\tprivate RegionValues regions2;\n\t\tprivate RegionValues regions3;\n\t\tprivate int numRegions1;\n\t\tprivate int regions1Index;\n\t\tprivate boolean hasNext;\n\t\tprivate Region region;\n\t\tprivate StateValues stateValues1;\n\t\tprivate StateValues stateValues2;\n\t\tprivate StateValues stateValues3;\n\n\t\tRegionIntersectionOperator(RegionValues regions1, RegionValues regions2, RegionValues regions3)\n\t\t{\n\t\t\tthis.regions1 = regions1;\n\t\t\tthis.regions2 = regions2;\n\t\t\tthis.regions3 = regions3;\n\t\t\tregions1Index = 0;\n\t\t\tnumRegions1 = regions1.getNumRegions();\n\t\t\tregion = null;\n\t\t\tstateValues1 = null;\n\t\t\tstateValues2 = null;\n\t\t\tstateValues3 = null;\n\t\t\tfindNext();\n\t\t}\n\t\t\n\t\tprivate void findNext() {\n\t\t\tboolean found = false;\n\t\t\twhile (regions1Index < numRegions1 && !found) {\n\t\t\t\tregion = regions1.getRegion(regions1Index);\n\t\t\t\tstateValues1 = regions1.getResult(region);\n\t\t\t\tstateValues2 = regions2.getResult(region);\n\t\t\t\tstateValues3 = regions3 != null ? regions3.getResult(region) : null;\n\t\t\t\tfound = (stateValues2 != null\n\t\t\t\t\t\t&& (regions3 == null || stateValues3 != null));\n\t\t\t\tregions1Index++;\n\t\t\t}\n\t\t\thasNext = found;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean hasNext() {\n\t\t\treturn hasNext;\n\t\t}\n\n\t\t@Override\n\t\tpublic RegionIntersection next() {\n\t\t\tif (hasNext) {\n\t\t\t\tRegionIntersection result = new RegionIntersection(region, stateValues1, stateValues2, stateValues3);\n\t\t\t\tfindNext();\n\t\t\t\treturn result;\n\t\t\t} else {\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic void remove() {\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\t}\n\n\tprivate RegionValues regions1;\n\tprivate RegionValues regions2;\n\tprivate RegionValues regions3;\n\n\tpublic RegionValuesIntersections(RegionValues regions1, RegionValues regions2) {\n\t\tregions1.cosplit(regions2);\n\t\tthis.regions1 = regions1;\n\t\tthis.regions2 = regions2;\n\t\tthis.regions3 = null;\n\t}\n\n\tpublic RegionValuesIntersections(RegionValues regions1, RegionValues regions2, RegionValues regions3) {\n\t\tregions1.cosplit(regions2, regions3);\n\t\tthis.regions1 = regions1;\n\t\tthis.regions2 = regions2;\n\t\tthis.regions3 = regions3;\n\t}\n\n\t@Override\n\tpublic Iterator<RegionIntersection> iterator() {\n\t\treturn new RegionIntersectionOperator(regions1, regions2, regions3);\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/param/RegionsTODO.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.Comparator;\nimport java.util.List;\nimport java.util.PriorityQueue;\n\n/**\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class RegionsTODO {\n\tclass RegionsByVolumeComparator implements Comparator<Region> {\n\n\t\t@Override\n\t\tpublic int compare(Region reg1, Region reg2) {\n\t\t\treturn reg1.volume().compareTo(reg2.volume()) * -1;\n\t\t}\n\t}\n\n\tprivate PriorityQueue<Region> regions;\n\n\tpublic RegionsTODO() {\n\t\tregions = new PriorityQueue<Region>(11, new RegionsByVolumeComparator());\n\t}\n\t\n\tint size() {\n\t\treturn regions.size();\n\t}\n\n\tboolean isEmpty()\n\t{\n\t\treturn regions.isEmpty();\n\t}\n\n\tvoid add(Region e)\n\t{\n\t\tregions.add(e);\n\t}\n\t\n\tvoid addAll(List<Region> newRegions)\n\t{\n\t\tregions.addAll(newRegions);\n\t}\n\n\tRegion poll()\n\t{\n\t\tRegion result = regions.poll();\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/ResultExporter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// TODO support to print scheduler instead of values\n// TODO stop printing if infinity occurs as value, as plot will be unusable\n\npackage param;\n\nimport java.io.OutputStream;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.Comparator;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.Map.Entry;\n\n/**\n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class ResultExporter {\n\tclass PointComparator implements Comparator<Point> {\n\t\t@Override\n\t\tpublic int compare(Point o1, Point o2) {\n\t\t\tint numDims = o1.size();\n\t\t\tfor (int dim = numDims - 2; dim > 0; dim--) {\n\t\t\t\tint cmp = o1.getDimension(dim).compareTo(o2.getDimension(dim));\n\t\t\t\tif (cmp != 0) {\n\t\t\t\t\treturn cmp;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn 0;\n\t\t}\n\t}\n\t\n\tprivate RegionValues values;\n\tprivate BoxRegionFactory regionFactory;\n\tprivate OutputStream output;\n\tprivate int pointsPerDim;\n\t\n\tResultExporter()\n\t{\n\t\t\n\t}\n\t\n\tvoid setRegionValues(RegionValues values)\n\t{\n\t\tthis.values = values;\n\t\tthis.regionFactory = (BoxRegionFactory) values.getRegionFactory();\n\t}\n\t\n\tvoid setOutputStream(OutputStream output)\n\t{\n\t\tthis.output = output;\n\t}\n\t\n\tvoid setPointsPerDimension(int pointsPerDim)\n\t{\n\t\tthis.pointsPerDim = pointsPerDim;\n\t}\n\n\tvoid print()\n\t{\n\t\tPrintStream print = new PrintStream(output);\n\t\tint numVariables = regionFactory.numVariables();\n\t\tboolean isBoolean = values.booleanValues();\n\t\t\n\t\tif (numVariables == 2 && isBoolean) {\n\t\t\tprintBooleanTwoVars(print);\n\t\t} else if (numVariables == 2 && !isBoolean) {\n\t\t\tprintFunctionTwoVars(print);\n\t\t} else {\n\t\t\tthrow new RuntimeException(\"not implemented\");\n\t\t}\n\t\t\t\t\n\t\tprint.flush();\n\t}\n\n\tprivate void printBooleanTwoVars(PrintStream print)\n\t{\n\t\tprint.println(\"\\\\begin{tikzpicture}[scale=5]\");\n\t\tprint.print(\"\\\\draw[rectangle,fill=gray] \");\n\t\tprint.print(\"(\" + regionFactory.getLowerBound(0).doubleValue());\n\t\tprint.print(\",\" + regionFactory.getLowerBound(1).doubleValue() + \")\");\n\t\tprint.print(\" rectangle \");\n\t\tprint.print(\"(\" + regionFactory.getUpperBound(0).doubleValue());\n\t\tprint.print(\",\" + regionFactory.getUpperBound(1).doubleValue() + \");\\n\");\n\t\tfor (Entry<Region,StateValues> entry : values) {\n\t\t\tboolean value = entry.getValue().getInitStateValueAsBoolean();\n\t\t\tBoxRegion region = (BoxRegion) entry.getKey();\n\t\t\tString fillColor = value ? \"white\" : \"black\";\n\t\t\tString drawColor = value ? \"black\" : \"white\";\n\t\t\tprint.print(\"\\\\draw[rectangle,\");\n\t\t\tprint.print(\"fill=\" + fillColor + \",\");\n\t\t\tprint.print(\"draw=\" + drawColor + \"] \");\t\t\t\n\t\t\tprint.print(\"(\" + region.getDimensionLower(0).doubleValue());\n\t\t\tprint.print(\",\" + region.getDimensionLower(1).doubleValue() + \")\");\n\t\t\tprint.print(\" rectangle \");\n\t\t\tprint.print(\"(\" + region.getDimensionUpper(0).doubleValue());\n\t\t\tprint.print(\",\" + region.getDimensionUpper(1).doubleValue() + \");\\n\");\t\t\t\t\t\n\t\t}\n\t\tprint.print(\"\\\\draw[rectangle,draw=black] \");\n\t\tprint.print(\"(\" + regionFactory.getLowerBound(0).doubleValue());\n\t\tprint.print(\",\" + regionFactory.getLowerBound(1).doubleValue() + \")\");\n\t\tprint.print(\" rectangle \");\n\t\tprint.print(\"(\" + regionFactory.getUpperBound(0).doubleValue());\n\t\tprint.print(\",\" + regionFactory.getUpperBound(1).doubleValue() + \");\\n\");\n\t\tprint.println(\"\\\\end{tikzpicture}\");\n\t}\n\t\n\tprivate ArrayList<Point> samplePoints()\n\t{\n\t\t// compute step width\n\t\tint numVariables = regionFactory.numVariables();\n\t\tBigRational[] stepWidth = new BigRational[numVariables];\n\t\tfor (int var = 0; var < numVariables; var++) {\n\t\t\tstepWidth[var] = regionFactory.sideWidth(var).divide(pointsPerDim - 1);\n\t\t}\n\n\t\t// compute point grid\n\t\tArrayList<Point> points = new ArrayList<Point>();\n\t\tint numTotalPoints = (int) Math.pow(pointsPerDim, numVariables);\n\t\tfor (int pointNr = 0; pointNr < numTotalPoints; pointNr++) {\n\t\t\tint pointRest = pointNr;\n\t\t\tBigRational[] point = new BigRational[numVariables];\n\t\t\tfor (int dim = 0; dim < numVariables; dim++) {\n\t\t\t\tint dimPosNr = pointRest % pointsPerDim;\n\t\t\t\tpointRest /= pointsPerDim;\n\t\t\t\tBigRational vl = regionFactory.getLowerBound(dim).add(stepWidth[dim].multiply(dimPosNr));\n\t\t\t\tpoint[dim] = vl;\n\t\t\t}\n\t\t\tpoints.add(new Point(point));\n\t\t}\n\t\t\n\t\t// compute values of points contained in a region\n\t\tHashMap<Point,BigRational> pointValues = new HashMap<Point,BigRational>();\n\t\tfor (Point point : points) {\n\t\t\tfor (Entry<Region,StateValues> entry : values) {\n\t\t\t\tRegion region = entry.getKey();\n\t\t\t\tFunction value = entry.getValue().getInitStateValueAsFunction();\n\t\t\t\tif (region.contains(point)) {\n\t\t\t\t\tpointValues.put(point, value.evaluate(point));\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\t\t\n\t\t// interpolate values of points not in a region\n\t\tHashSet<Function> allFunctions = new HashSet<Function>();\n\t\tfor (Entry<Region,StateValues> entry : values) {\n\t\t\tallFunctions.add(entry.getValue().getInitStateValueAsFunction());\n\t\t}\n\t\tfor (Point point : points) {\n\t\t\tif (!pointValues.containsKey(point)) {\n\t\t\t\tboolean finish = false;\n\t\t\t\tBigRational average = BigRational.ZERO;\n\t\t\t\tfor (int distNr = 0; (distNr < pointsPerDim) && !finish; distNr++) {\n\t\t\t\t\tBigRational sum = BigRational.ZERO;\n\t\t\t\t\tint numFound = 0;\n\t\t\t\t\tfor (int dim = 0; (dim < numVariables); dim++) {\n\t\t\t\t\t\tfor (int direction = -1; direction <= 1; direction += 2) {\n\t\t\t\t\t\t\tBigRational offset = stepWidth[dim].multiply(dim).multiply(direction);\n\t\t\t\t\t\t\tBigRational[] dimensions = point.toArray();\n\t\t\t\t\t\t\tdimensions[dim] = dimensions[dim].add(offset);\n\t\t\t\t\t\t\tPoint distPoint = new Point(dimensions);\n\t\t\t\t\t\t\tBigRational value = pointValues.get(distPoint);\n\t\t\t\t\t\t\tif (value != null) {\n\t\t\t\t\t\t\t\tfinish = true;\n\t\t\t\t\t\t\t\tsum = sum.add(value);\n\t\t\t\t\t\t\t\tnumFound++;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (finish) {\n\t\t\t\t\t\taverage = sum.divide(numFound);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tBigRational minDiff = new BigRational(1000);\n\t\t\t\tBigRational bestValue = new BigRational(1000);\n\t\t\t\tfor (Function function : allFunctions) {\n\t\t\t\t\tBigRational newValue = function.evaluate(point);\n\t\t\t\t\tBigRational newDiff = average.subtract(newValue).abs();\n\t\t\t\t\tif (newDiff.compareTo(minDiff) == -1) {\n\t\t\t\t\t\tbestValue = newValue;\n\t\t\t\t\t\tminDiff = newDiff;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tpointValues.put(point, bestValue);\n\t\t\t}\n\t\t}\t\t\n\t\t\n\t\t// combine points and their values in result list and sort\n\t\tArrayList<Point> result = new ArrayList<Point>();\n\t\tfor (Point point : points) {\n\t\t\tBigRational[] entry = new BigRational[numVariables + 1];\n\t\t\tfor (int var = 0; var < numVariables; var++) {\n\t\t\t\tentry[var] = point.getDimension(var);\n\t\t\t}\n\t\t\tentry[numVariables] = pointValues.get(point);\n\t\t\tresult.add(new Point(entry));\n\t\t}\t\t\n\t\tPointComparator comparator = new PointComparator();\n\t\tCollections.sort(result, comparator);\n\n\t\treturn result;\n\t}\n\t\n\tprivate void printFunctionTwoVars(PrintStream print)\n\t{\n\t\tprint.println(\"\\\\begin{tikzpicture}\");\n\t\tprint.println(\"\\\\begin{axis}[\");\n\t\tprint.println(\"  view={30}{30}\");\n//\t\tprint.println(\"  x tick label style={right=1pt},\");\n//\t\tprint.println(\"  xtick={0,0.2,0.4,0.6,0.8,1.0},\");\n//\t\tprint.println(\"  ytick={0.2}\");\n\t\tprint.println(\"  ]\");\n\t\tprint.println(\"  \\\\addplot3[mesh,color=black] coordinates {\");\n\t\tArrayList<Point> points =  samplePoints();\n\t\tBigRational lastY = points.get(0).getDimension(1);\n\t\tfor (Point point : points) {\n\t\t\tif (!lastY.equals(point.getDimension(1))) {\n\t\t\t\tprint.print(\"\\n\\n\");\n\t\t\t\tlastY = point.getDimension(1);\n\t\t\t}\n\t\t\tprint.print(\" (\");\n\t\t\tfor (int dim = 0; dim < point.size(); dim++) {\n\t\t\t\tprint.print(point.getDimension(dim).doubleValue());\n\t\t\t\tif (dim < point.size() - 1) {\n\t\t\t\t\tprint.print(\",\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tprint.print(\")\");\n\t\t}\n\t\tprint.println();\n\t\tprint.println(\"  };\");\n\t\tprint.println(\"\\\\end{axis}\");\n\t\tprint.println(\"\\\\end{tikzpicture}\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/Scheduler.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport explicit.NondetModel;\n\n/**\n * Simple scheduler for a parametric model.\n * Assigns a single nonrandomised decision to each state of the model.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class Scheduler {\n\t/** represents the choice taken for each state */\n\tpublic int[] choices; // TODO\n\t\n\t/**\n\t * Constructs a new scheduler for {@code model}.\n\t * The scheduler is legal, but not necessarily optimal in any sense.\n\t * \n\t * @param model model to generate scheduler for\n\t */\n\tScheduler(NondetModel<Function> model)\n\t{\n\t\tchoices = new int[model.getNumStates()];\n\t\tfor (int state = 0; state < model.getNumStates(); state++) {\n\t\t\tchoices[state] = model.getNumChoices(state) - 1;\n\t\t}\n\t}\n\n\t/** Copy constructor */\n\tScheduler(Scheduler other)\n\t{\n\t\tchoices = other.choices.clone();\n\t}\n\n\t@Override\n\tpublic Scheduler clone()\n\t{\n\t\treturn new Scheduler(this);\n\t}\n\n\t/**\n\t * Set choice for given state.\n\t * \n\t * @param state state to set choice for\n\t * @param choice choice to set for given state \n\t */\n\tvoid setChoice(int state, int choice) {\n\t\tchoices[state] = choice;\n\t}\n\t\n\t/**\n\t * Get choice for given state.\n\t * \n\t * @param state state to get choice of\n\t * @return choice for given state\n\t */\n\tint getChoice(int state) {\n\t\treturn choices[state];\n\t}\n\t\n\t@Override\n\tpublic boolean equals(Object obj) {\n\t\tif (!(obj instanceof Scheduler)) {\n\t\t\treturn false;\n\t\t}\n\t\tScheduler other = (Scheduler) obj;\n\t\tfor (int state = 0; state < choices.length; state++) {\n\t\t\tif (this.choices[state] != other.choices[state]) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic int hashCode() {\n\t\tint hash = 0;\n\t\t\n\t\tfor (int state = 0; state < choices.length; state++) {\n\t\t\thash = choices[state] + (hash << 6) + (hash << 16) - hash;\n\t\t}\n\t\t\n\t\treturn hash;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/StateBoolean.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\n/**\n * A state value which can be represented as a truth value.\n * The truth value the object represents cannot be changed once this object\n * is created.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class StateBoolean extends StateValue {\n\tprivate boolean value;\n\n\tpublic StateBoolean()\n\t{\n\t\tvalue = Boolean.valueOf(false);\n\t}\n\t\n\tpublic StateBoolean(boolean value)\n\t{\n\t\tthis.value = value;\n\t}\n\t\n\tboolean getValue()\n\t{\n\t\treturn value;\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn value ? \"true\" : \"false\";\n\t}\n\t\n\t@Override\n\tpublic boolean equals(Object obj) {\n\t\tif (!(obj instanceof StateBoolean)) {\n\t\t\treturn false;\n\t\t}\n\t\treturn this.value == ((StateBoolean) obj).value;\n\t}\n\t\n\t@Override\n\tpublic int hashCode() {\n\t\treturn value ? 17 : 13;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/StateEliminator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.Collections;\nimport java.util.HashSet;\nimport java.util.List;\nimport java.util.ListIterator;\n\n/**\n * Performs computation of reachability probabilities and rewards.\n * This class handles the computation of unbounded reachability\n * probabilities, expected accumulated rewards and expected long-run\n * average rewards for Markov chains. To handle this computation, the\n * different states of the model are \"eliminated\", that is of the model are\n * modified in such a way that the value of concern (probability or reward)\n * is maintained, but the state no longer has any incoming transitions,\n * except in some cases self loops. This way, after all states have been\n * treated, the value of concern can be obtained by a simple computation.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class StateEliminator {\n\t/**\n\t * The order in which states shall be eliminated.\n\t */\n\tenum EliminationOrder {\n\t\t/** arbitrary */\n\t\tARBITRARY,\n\t\t/** states close to initial states first */\n\t\tFORWARD,\n\t\t/** states close to initial states last */\n\t\tFORWARD_REVERSED,\n\t\t/** states close to target states first */\n\t\tBACKWARD,\n\t\t/** states close to target states last */\n\t\tBACKWARD_REVERSED,\n\t\t/** random */\n\t\tRANDOM;\t\n\t}\n\t\n\t/** the mutable parametric Markov chain to compute values of */\n\tprivate MutablePMC pmc;\n\t/** order in which states are eliminated */\n\tprivate EliminationOrder eliminationOrder;\n\t\n\t/**\n\t * Create a new state eliminator object.\n\t * \n\t * @param pmc parametric Markov chain to compute values of\n\t * @param eliminationOrder order in which states shall be eliminated\n\t */\n\tStateEliminator(MutablePMC pmc, EliminationOrder eliminationOrder)\n\t{\n\t\tthis.pmc = pmc;\n\t\tthis.eliminationOrder = eliminationOrder;\n\t}\n\t\n\t/**\n\t * Orders states so that states near initial states are eliminated first.\n\t * \n\t * @return list of states in requested order\n\t */\n\tprivate int[] collectStatesForward()\n\t{\n\t\tint[] states = new int[pmc.getNumStates()];\n\t\tBitSet seen = new BitSet(pmc.getNumStates());\n\t\tHashSet<Integer> current = new HashSet<Integer>();\n\t\tint nextStateNr = 0;\n\t\t/* put initial states in queue */\n\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\tif (pmc.isInitState(state)) {\n\t\t\t\tstates[nextStateNr] = state;\n\t\t\t\tseen.set(state, true);\n\t\t\t\tcurrent.add(state);\n\t\t\t\tnextStateNr++;\n\t\t\t}\n\t\t}\n\t\t/* perform breadth-first search */\n\t\twhile (!current.isEmpty()) {\n\t\t\tHashSet<Integer> next = new HashSet<Integer>();\n\t\t\tfor (int state : current) {\n\t\t\t\tfor (int succState : pmc.transitionTargets.get(state)) {\n\t\t\t\t\tif (!seen.get(succState)) {\n\t\t\t\t\t\tseen.set(succState, true);\n\t\t\t\t\t\tnext.add(succState);\n\t\t\t\t\t\tstates[nextStateNr] = succState;\n\t\t\t\t\t\tnextStateNr++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tcurrent = next;\n\t\t}\n\t\treturn states;\n\t}\n\t\n\t/**\n\t * Orders states so that states near target states are eliminated first.\n\t * States which do not reach target states are eliminated last. In case\n\t * there are no target states, the order is arbitrary\n\t */\n\tprivate int[] collectStatesBackward()\n\t{\n\t\treturn collectStatesBackward(false);\n\t}\n\n\t/**\n\t * Orders states so that states near target states are eliminated first.\n\t * States which do not reach target states are eliminated last. In case\n\t * there are no target states, the order is arbitrary\n\t * <br>\n\t * If {@code onlyStatesReachingTarget} is true, only the states that\n\t * can reach the target states will be returned.\n\t * \n\t * @return list of states in requested order\n\t */\n\tprivate int[] collectStatesBackward(boolean onlyStatesReachingTarget)\n\t{\n\t\tint[] states = new int[pmc.getNumStates()];\n\t\tBitSet seen = new BitSet(pmc.getNumStates());\n\t\tHashSet<Integer> current = new HashSet<Integer>();\n\t\tint nextStateNr = 0;\n\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\tif (pmc.isTargetState(state)) {\n\t\t\t\tcurrent.add(state);\n\t\t\t\tstates[nextStateNr] = state;\n\t\t\t\tseen.set(state, true);\n\t\t\t\tnextStateNr++;\n\t\t\t}\n\t\t}\n\t\twhile (!current.isEmpty()) {\n\t\t\tHashSet<Integer> next = new HashSet<Integer>();\n\t\t\tfor (int state : current) {\n\t\t\t\tfor (int succState : pmc.incoming.get(state)) {\n\t\t\t\t\tif (!seen.get(succState)) {\n\t\t\t\t\t\tseen.set(succState, true);\n\t\t\t\t\t\tnext.add(succState);\n\t\t\t\t\t\tstates[nextStateNr] = succState;\n\t\t\t\t\t\tnextStateNr++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tcurrent = next;\n\t\t}\n\n\t\tif (onlyStatesReachingTarget) {\n\t\t\treturn states;\n\t\t}\n\n\t\t/* might not find all states when doing as above,\n\t\t * so add missing ones */\n\t\tHashSet<Integer> allStates = new HashSet<Integer>();\n\t\tfor (int stateNr = 0; stateNr < states.length; stateNr++) {\n\t\t\tint state = states[stateNr];\n\t\t\tallStates.add(state);\n\t\t}\n\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\tif (!allStates.contains(state)) {\n\t\t\t\tstates[nextStateNr] = state;\n\t\t\t\tnextStateNr++;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn states;\n\t}\n\t\n\t/**\n\t * Performs precomputation before actual state elimination.\n\t * This handles cases in which all or some states can or have to\n\t * be treated differently, e.g. because there are no target states\n\t * at all, or some states do never reach a target state.\n\t * \n\t * @return true iff state elimination is necessary to obtain a result\n\t */\n\tprivate boolean precompute()\n\t{\n\t\t/* if there are no target states, the result is zero everywhere\n\t\t * for a reachability probability analysis, so all states can be\n\t\t * made absorbing. If we are performing analysis of accumulated\n\t\t * rewards, the value will be infinity everywhere. */\n\t\tif (!pmc.isUseTime() && !pmc.hasTargetStates()) {\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tpmc.makeAbsorbing(state);\n\t\t\t\tif (pmc.isUseRewards()) {\n\t\t\t\t\tpmc.setReward(state, pmc.getFunctionFactory().getInf());\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\t/* search for states which might never reach a target state and thus\n\t\t * have to be assigned a reward of infinity. */\n\t\tif (pmc.isUseRewards()) {\n\t\t\tint[] backStatesArr = collectStatesBackward(true);\n\t\t\tHashSet<Integer> reaching = new HashSet<Integer>();\n\t\t\tfor (int stateNr = 0; stateNr < backStatesArr.length; stateNr++) {\n\t\t\t\treaching.add(backStatesArr[stateNr]);\n\t\t\t}\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tif (!pmc.isUseTime() && !reaching.contains(state)) {\n\t\t\t\t\tpmc.setReward(state, pmc.getFunctionFactory().getInf());\n\t\t\t\t} \n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t/**\n\t * Eliminate all states of the model.\n\t * The order of elimination is given by {@code eliminationOrder}.\n\t */\n\tvoid eliminate()\n\t{\n\t\tif (!precompute()) {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tint[] states = new int[pmc.getNumStates()];\n\t\tList<Integer> statesList = new ArrayList<Integer>();\n\t\tswitch (eliminationOrder) {\n\t\tcase ARBITRARY:\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tstates[state] = state;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase FORWARD:\n\t\t\tstates = collectStatesForward();\n\t\t\tbreak;\n\t\tcase FORWARD_REVERSED:\n\t\t\tstates = collectStatesForward();\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tstatesList.add(states[state]);\n\t\t\t}\n\t\t\tCollections.reverse(statesList);\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tstates[state] = statesList.get(state);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase BACKWARD:\n\t\t\tstates = collectStatesBackward();\n\t\t\tbreak;\n\t\tcase BACKWARD_REVERSED:\n\t\t\tstates = collectStatesBackward();\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tstatesList.add(states[state]);\n\t\t\t}\n\t\t\tCollections.reverse(statesList);\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tstates[state] = statesList.get(state);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase RANDOM:\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tstatesList.add(state);\n\t\t\t}\n\t\t\tCollections.shuffle(statesList);\n\t\t\tfor (int state = 0; state < pmc.getNumStates(); state++) {\n\t\t\t\tstates[state] = statesList.get(state);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new RuntimeException(\"unknown state elimination order\");\n\t\t}\n\t\t\n\t\tfor (int stateNr = 0; stateNr < pmc.getNumStates(); stateNr++) {\n\t\t\teliminate(states[stateNr]);\n\t\t}\n\t}\n\n\t/**\n\t * Stores a transition which shall be added to the model later.\n\t */\n\tclass NewTransition {\n\t\t/** source state of transition */\n\t\tfinal int fromState;\n\t\t/** target state of transition */\n\t\tfinal int toState;\n\t\t/** probability of transition */\n\t\tfinal Function prob;\n\n\t\t/**\n\t\t * Creates a new transition to be added later on.\n\t\t * \n\t\t * @param fromState source state of transition\n\t\t * @param toState target state of transition\n\t\t * @param prob probability of transition\n\t\t */\n\t\tpublic NewTransition(int fromState, int toState, Function prob)\n\t\t{\n\t\t\tthis.fromState = fromState;\n\t\t\tthis.toState = toState;\n\t\t\tthis.prob = prob;\n\t\t}\n\t\t\n\t}\n\n\t/**\n\t * Eliminates a given state\n\t * \n\t * @param midState state to eliminate\n\t */\n\tprivate void eliminate(int midState)\n\t{\n\t\tFunction loopProb = pmc.getSelfLoopProb(midState);\n\t\t/* states with only a self-loop require no further treatment */\n\t\tif (loopProb.equals(pmc.getFunctionFactory().getOne())) {\n\t\t\treturn;\n\t\t}\n\t\t/* slStar = 1/(1-x), where x is the self-loop probability */\n\t\tFunction slStar = loopProb.star(); \n\t\t\n\t\t/* adapt rewards and time spent in state accordingly. The new\n\t\t * values correspond to adding the expected reward/time obtained\n\t\t * from moving to the midState from one of its predecessors, times\n\t\t * the probability of moving. */\n\t\tif (pmc.isUseRewards()) {\n\t\t\tpmc.setReward(midState, pmc.getReward(midState).multiply(slStar));\n\t\t\tfor (int from : pmc.incoming.get(midState)) {\n\t\t\t\tif (from != midState) {\n\t\t\t\t\tpmc.setReward(from, pmc.getReward(from).add(pmc.getTransProb(from, midState).multiply(pmc.getReward(midState))));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (pmc.isUseTime()) {\n\t\t\tpmc.setTime(midState, pmc.getTime(midState).multiply(slStar));\n\t\t\tfor (int from : pmc.incoming.get(midState)) {\n\t\t\t\tif (from != midState) {\n\t\t\t\t\tpmc.setTime(from, pmc.getTime(from).add(pmc.getTransProb(from, midState).multiply(pmc.getTime(midState))));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t/* redirect transitions of predecessors of midState. Redirection is\n\t\t * done such that some state fromState will have a probability of\n\t\t * moving to a successor state toState of midState with probability\n\t\t * (<fromState-to-midState-prob> * <midState-to-toState-prob)\n\t\t * / (1-<self-loop-prob>). (If there already was a transition from fromState\n\t\t * to toState, probabilities will be added up.). All transitions to\n\t\t * midState will be removed. */\n\t\tArrayList<NewTransition> newTransitions = new ArrayList<NewTransition>(); \n\t\tfor (int fromState : pmc.incoming.get(midState)) {\n\t\t\tif (fromState != midState) {\n\t\t\t\tFunction fromToMid = pmc.getTransProb(fromState, midState);\n\t\t\t\tListIterator<Integer> toStateIter = pmc.transitionTargets.get(midState).listIterator();\n\t\t\t\tListIterator<Function> toProbIter = pmc.transitionProbs.get(midState).listIterator();\n\t\t\t\twhile (toStateIter.hasNext()) {\n\t\t\t\t\tint toState = toStateIter.next();\n\t\t\t\t\tFunction midToTo = toProbIter.next();\n\t\t\t\t\tif (toState != midState) {\n\t\t\t\t\t\tFunction fromToToAdd = fromToMid.multiply(slStar.multiply(midToTo));\n\t\t\t\t\t\tnewTransitions.add(new NewTransition(fromState, toState, fromToToAdd));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tfor (int fromState : pmc.incoming.get(midState)) {\n\t\t\tListIterator<Integer> toStateIter = pmc.transitionTargets.get(fromState).listIterator();\n\t\t\tListIterator<Function> toProbIter = pmc.transitionProbs.get(fromState).listIterator();\n\t\t\twhile (toStateIter.hasNext()) {\n\t\t\t\tint state = toStateIter.next();\n\t\t\t\ttoProbIter.next();\n\t\t\t\tif (state == midState) {\n\t\t\t\t\ttoStateIter.remove();\n\t\t\t\t\ttoProbIter.remove();\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tfor (NewTransition newTransition : newTransitions) {\n\t\t\tpmc.addTransition(newTransition.fromState, newTransition.toState, newTransition.prob);\n\t\t}\n\n\t\t/* remove self loop from state and set outgoing probabilities to\n\t\t * <out-prob> / (1-<self-loop-prob>). This corresponds to the\n\t\t * probability to eventually leaving midState to a specific successor\n\t\t * state, after executing any number of self loops. */\n\t\tListIterator<Integer> toStateIter = pmc.transitionTargets.get(midState).listIterator();\n\t\tListIterator<Function> toProbIter = pmc.transitionProbs.get(midState).listIterator();\n\t\twhile (toStateIter.hasNext()) {\n\t\t\tint toState = toStateIter.next();\n\t\t\tFunction toProb = toProbIter.next();\n\t\t\tif (midState != toState) {\n\t\t\t\ttoProbIter.set(slStar.multiply(toProb));\n\t\t\t}\n\t\t}\n\t\ttoStateIter = pmc.transitionTargets.get(midState).listIterator();\n\t\ttoProbIter = pmc.transitionProbs.get(midState).listIterator();\n\t\twhile (toStateIter.hasNext()) {\n\t\t\tint toState = toStateIter.next();\n\t\t\ttoProbIter.next();\n\t\t\tif (midState == toState) {\n\t\t\t\ttoStateIter.remove();\n\t\t\t\ttoProbIter.remove();\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\tpmc.incoming.get(midState).clear();\n\t}\n\t\n\t/**\n\t * Obtain result for a given state.\n\t * Before calling this method, all states must have been eliminated.\n\t * \n\t * @param state state to obtain result for\n\t * @return result for given state\n\t */\n\tFunction getResult(int state)\n\t{\n\t\t/* due to state elimination, at this point each state:\n\t\t * A) either has only a self-loop, or\n\t\t * B) has no self loop and only transitions to one or more states\n\t\t *    of the form A. */\n\t\t\n\t\tif (pmc.isUseRewards() && !pmc.isUseTime()) {\n\t\t\t/* states which do not reach target states with probability one\n\t\t\t * are assigned a reward of infinity. Target states have a reward\n\t\t\t * of zero and only self-loops. Because of this, and from the state\n\t\t\t * elimination (see above), we can read the reward directly from\n\t\t\t * the according reward structure. */\n\t\t\t\n\t\t\treturn pmc.getReward(state);\n\t\t} else if (pmc.isUseRewards() && pmc.isUseTime()) {\n\t\t\t/* due to state elimination, each state either: A) has a self loop\n\t\t\t * and or: B) does not have a self-loop and only transitions to\n\t\t\t * states of the form A. The long-run average probability for states\n\t\t\t * of the form A is then just reward(state) / time(state). For all\n\t\t\t * states of both the form A and B, the long-run average is the\n\t\t\t * probability to move to a state of form A times the long-run\n\t\t\t * average value of that A state. */\n\t\t\tListIterator<Integer> toStateIter = pmc.transitionTargets.get(state).listIterator();\n\t\t\tListIterator<Function> toProbIter = pmc.transitionProbs.get(state).listIterator();\n\t\t\tFunction result = pmc.getFunctionFactory().getZero();\n\t\t\twhile (toStateIter.hasNext()) {\n\t\t\t\tint toState = toStateIter.next();\n\t\t\t\tFunction toProb = toProbIter.next();\n\t\t\t\tresult = result.add(toProb.multiply(pmc.getReward(toState)).divide(pmc.getTime(toState)));\n\t\t\t}\n\t\t\treturn result;\t\t\t\n\t\t} else {\n\t\t\t/* due to state elimination, each state either: A) has a self loop\n\t\t\t * and then is a target state or cannot reach a target state at all,\n\t\t\t * or: B) is not a target state or a state which cannot reach\n\t\t\t * target states, and then does not have a self-loop and only\n\t\t\t * transitions to states of the form A. Because of this, to obtain\n\t\t\t * reachability probabilities, we just have to add up the one-step\n\t\t\t * probabilities to target states. */\n\t\t\tListIterator<Integer> toStateIter = pmc.transitionTargets.get(state).listIterator();\n\t\t\tListIterator<Function> toProbIter = pmc.transitionProbs.get(state).listIterator();\n\t\t\tFunction result = pmc.getFunctionFactory().getZero();\n\t\t\twhile (toStateIter.hasNext()) {\n\t\t\t\tint toState = toStateIter.next();\n\t\t\t\tFunction toProb = toProbIter.next();\n\t\t\t\tif (pmc.isTargetState(toState)) {\n\t\t\t\t\tresult = result.add(toProb);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn result;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/StateValue.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\n/**\n * Represents a value which might be assigned to a state during analysis.\n * Objects of this class shall be immutable, that is they are never changed\n * once they are created.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nabstract class StateValue {\n\n}\n"
  },
  {
    "path": "prism/src/param/StateValues.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// TODO allow null values in entries\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.function.IntPredicate;\n\nimport common.IterableStateSet;\nimport parser.State;\nimport parser.type.TypeBool;\nimport prism.PrismLog;\n\n/**\n * Class to assign a value to each state of a model.\n * Used by {@code RegionValues}.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n * @see RegionValues\n */\npublic final class StateValues\n{\n\t/** assigns values to each state of the model */\n\tprivate ArrayList<StateValue> values;\n\t/** initial state of the model */\n\tprivate int initState;\n\n\t/**\n\t * Constructs new set of state values.\n\t * Each state is mapped to {@code null}.\n\t * \n\t * @param numStates number of states of model\n\t * @param initState initial state of the model\n\t */\n\tpublic StateValues(int numStates, int initState)\n\t{\n\t\tvalues = new ArrayList<StateValue>(numStates);\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tvalues.add(state, null);\n\t\t}\n\t\tthis.initState = initState;\n\t}\n\n\t/**\n\t * Constructs new set of state values.\n\t * Each state is mapped to the given value.\n\t * \n\t * @param numStates number of states of the model\n\t * @param initState initial state of the model\n\t * @param value value to map all states to\n\t */\n\tpublic StateValues(int numStates, int initState, StateValue value)\n\t{\n\t\tthis(numStates, initState);\n\t\tfor (int state = 0; state < numStates; state++) {\n\t\t\tvalues.set(state, value);\n\t\t}\n\t}\n\n\t/**\n\t * Constructs new set of state values.\n\t * Each state is mapped to the given value.\n\t * \n\t * @param numStates number of states of the model\n\t * @param initState initial state of the model\n\t * @param value value to map all states to\n\t */\n\tpublic StateValues(int numStates, int initState, boolean value)\n\t{\n\t\tthis(numStates, initState, new StateBoolean(value));\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn values.toString();\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (!(obj instanceof StateValues)) {\n\t\t\treturn false;\n\t\t}\n\n\t\tStateValues result = (StateValues) obj;\n\n\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\tif (!values.get(i).equals(result.values.get(i))) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tint hash = 0;\n\n\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\thash = values.get(i).hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t}\n\n\t\treturn hash;\n\t}\n\n\t/**\n\t * Get value of given state.\n\t * \n\t * @param state state to get value of\n\t * @return value of given state\n\t */\n\tpublic StateValue getStateValue(int state)\n\t{\n\t\treturn values.get(state);\n\t}\n\n\t/**\n\t * Set value of given state.\n\t * \n\t * @param state state to set value of\n\t * @param value value to set for state\n\t */\n\tpublic void setStateValue(int state, StateValue value)\n\t{\n\t\tvalues.set(state, value);\n\t}\n\n\t/**\n\t * Set value of given state.\n\t * \n\t * @param state state to set value of\n\t * @param value value to set for state\n\t */\n\tpublic void setStateValue(int state, boolean value)\n\t{\n\t\tvalues.set(state, new StateBoolean(value));\n\t}\n\n\t/**\n\t * Get value of given state as rational function.\n\t * If the value of the state is not a function, this will lead to an error.\n\t * \n\t * @param state state to get value of\n\t * @return value of the state as a function\n\t */\n\tpublic Function getStateValueAsFunction(int state)\n\t{\n\t\treturn (Function) values.get(state);\n\t}\n\n\t/**\n\t * Get value of given state as boolean.\n\t * If the value of the state is not a boolean, this will lead to an error.\n\t * \n\t * @param state state to get value of\n\t * @return value of the state as a boolean\n\t */\n\tpublic boolean getStateValueAsBoolean(int state)\n\t{\n\t\treturn ((StateBoolean) values.get(state)).getValue();\n\t}\n\n\t/**\n\t * Get value of initial state as rational function.\n\t * If the value of the initial state is not a function, this will lead to an error.\n\t * \n\t * @return value of the initial state as a function\n\t */\n\tpublic Function getInitStateValueAsFunction()\n\t{\n\t\treturn (Function) values.get(initState);\n\t}\n\n\t/**\n\t * Get value of initial state as boolean.\n\t * If the value of the initial state is not a boolean, this will lead to an error.\n\t * \n\t * @return value of the initial state as a boolean\n\t */\n\tpublic boolean getInitStateValueAsBoolean()\n\t{\n\t\treturn ((StateBoolean) values.get(initState)).getValue();\n\t}\n\n\t/**\n\t * Get value of initial state.\n\t */\n\tpublic StateValue getInitStateValue()\n\t{\n\t\treturn values.get(initState);\n\t}\n\n\t/**\n\t * Returns number of states of the model.\n\t * \n\t * @return number of states of the model\n\t */\n\tpublic int getNumStates()\n\t{\n\t\treturn values.size();\n\t}\n\n\t/**\n\t * Converts this state value assignment to a bitset.\n\t * For this to work, all states must be mapped to booleans.\n\t * \n\t * @return bitset representing this state value assignment\n\t */\n\tpublic BitSet toBitSet()\n\t{\n\t\tBitSet result = new BitSet(values.size());\n\t\tfor (int state = 0; state < values.size(); state++) {\n\t\t\tresult.set(state, getStateValueAsBoolean(state));\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Instantiates the value to which each state is mapped at the given point.\n\t * For this to work, all states must be mapped to rational functions.\n\t * \n\t * @param point point to instantiate state values\n\t * @return array of {@code BigRational}s mapping each state to evaluated value\n\t */\n\tpublic BigRational[] instantiate(Point point)\n\t{\n\t\tBigRational[] result = new BigRational[values.size()];\n\t\tfor (int state = 0; state < values.size(); state++) {\n\t\t\tresult[state] = this.getStateValueAsFunction(state).evaluate(point);\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * Print part of vector to a log/file.\n\t * @param log The log\n\t * @param mode the mode\n\t * @param filter A BitSet specifying which states to print for (null if all).\n\t * @param printSparse Print non-zero/non-false elements only?\n\t * @param printStates Print states (variable values) for each element?\n\t * @param printIndices Print state indices for each element?\n\t */\n\tpublic void printFiltered(PrismLog log, ParamMode mode, parser.type.Type type, BitSet filter, List<State> statesList, boolean printSparse, boolean printStates, boolean printIndices)\n\t{\n\t\tint count = 0;\n\n\t\tIntPredicate nonZero =\n\t\t\t\t(type instanceof TypeBool)\n\t\t\t\t? (int n) -> {return getStateValueAsBoolean(n);}\n\t\t\t\t: (int n) -> {return !getStateValueAsFunction(n).isZero();};\n\n\t\t// Print vector\n\t\tfor (int n : new IterableStateSet(filter, getNumStates())) {\n\t\t\tif (!printSparse || nonZero.test(n)) {\n\t\t\t\tif (printIndices) {\n\t\t\t\t\tlog.print(n);\n\t\t\t\t\tlog.print(\":\");\n\t\t\t\t}\n\n\t\t\t\tif (printStates && statesList != null)\n\t\t\t\t\tlog.print(statesList.get(n).toString());\n\t\t\t\tif (printSparse && type instanceof TypeBool) {\n\t\t\t\t\tlog.println();\n\t\t\t\t} else {\n\t\t\t\t\tif (printIndices || printStates)\n\t\t\t\t\t\tlog.print(\"=\");\n\n\t\t\t\t\tif (type instanceof TypeBool) {\n\t\t\t\t\t\tlog.println(getStateValueAsBoolean(n));\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (mode == ParamMode.EXACT) {\n\t\t\t\t\t\t\tBigRational value = getStateValueAsFunction(n).asBigRational();\n\t\t\t\t\t\t\tlog.println(value + \"   (\" + value.toApproximateString() + \")\");\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlog.println(getStateValueAsFunction(n));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tcount++;\n\t\t\t}\n\t\t}\n\n\t\t// Check if all zero\n\t\tif (printSparse && count == 0) {\n\t\t\tlog.println(\"(all zero)\");\n\t\t\treturn;\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/param/StrongLumper.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayList;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.ListIterator;\nimport java.util.Map.Entry;\n\n/**\n * Strong bisimulation lumper.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class StrongLumper extends Lumper {\n\n\t/**\n\t * Construct a new strong bisimulation lumper.\n\t * \n\t * @param origPmc Markov chain to construct lumper for\n\t */\n\tStrongLumper(MutablePMC origPmc) {\n\t\tsuper(origPmc);\n\t}\n\n\t/**\n\t * Construct the strong bisimulation signature of given block.\n\t * The signature is a mapping of blocks to the probability to move\n\t * from the given state to any state of the block.\n\t * \n\t * @param state state to compute signature of\n\t * @return signature of this state\n\t */\n\tprivate HashMap<HashSet<Integer>, Function> stateSignature(int state)\n\t{\n\t\tHashMap<HashSet<Integer>, Function> signature = new HashMap<HashSet<Integer>, Function>();\n\t\tListIterator<Integer> toStateIter = origPmc.transitionTargets.get(state).listIterator();\n\t\tListIterator<Function> toProbIter = origPmc.transitionProbs.get(state).listIterator();\n\t\twhile (toStateIter.hasNext()) {\n\t\t\tint toState = toStateIter.next();\n\t\t\tFunction toStateProb = toProbIter.next();\n\t\t\tHashSet<Integer> toBlock = partition.getStateBlock(toState);\n\t\t\tFunction toBlockProb = signature.get(toBlock);\n\t\t\tif (toBlockProb == null) {\n\t\t\t\ttoBlockProb = origPmc.getFunctionFactory().getZero();\n\t\t\t}\n\t\t\ttoBlockProb = toBlockProb.add(toStateProb);\n\t\t\tsignature.put(toBlock, toBlockProb);\n\t\t}\n\t\treturn signature;\n\t}\n\t\n\t/**\n\t * Refines a given block to a list of new blocks for strong bisimulation.\n\t * Each block will consist of the states with the same signature.\n\t * \n\t * @param oldBlock block to refine\n\t * @param newBlocks list of new blocks generated\n\t */\n\t@Override\n\tprotected void refineBlock(HashSet<Integer> oldBlock, ArrayList<HashSet<Integer>> newBlocks) {\n\t\tHashMap<HashMap<HashSet<Integer>, Function>, HashSet<Integer>> signatures = new HashMap<HashMap<HashSet<Integer>, Function>, HashSet<Integer>>();\n\t\tfor (int state : oldBlock) {\n\t\t\tHashMap<HashSet<Integer>, Function> signature = stateSignature(state);\n\t\t\tHashSet<Integer> newBlock = signatures.get(signature);\n\t\t\tif (newBlock == null) {\n\t\t\t\tnewBlock = new HashSet<Integer>();\n\t\t\t\tsignatures.put(signature, newBlock);\n\t\t\t}\n\t\t\tnewBlock.add(state);\n\t\t}\n\t\tfor (HashSet<Integer> block : signatures.values()) {\n\t\t\tnewBlocks.add(block);\n\t\t}\n\t}\n\n\t/**\n\t * Build the strong bisimulation quotient from the blocks computed.\n\t * Transition probabilities are simply derived from the signature\n\t * of an arbitrary state for each block.\n\t */\n\t@Override\n\tprotected void buildQuotient() {\n\t\toptPmc = new MutablePMC(origPmc.getFunctionFactory(), blocks.size(), origPmc.isUseRewards(), origPmc.isUseTime());\n\t\tfor (int newState = 0; newState < blocks.size(); newState++) {\n\t\t\tHashSet<Integer> fromBlock = blocks.get(newState);\n\t\t\tint someOriginalState = fromBlock.iterator().next();\n\t\t\tHashMap<HashSet<Integer>, Function> signature = stateSignature(someOriginalState);\n\t\t\tfor (Entry<HashSet<Integer>, Function> entry : signature.entrySet()) {\n\t\t\t\toptPmc.addTransition(newState, blockToNumber.get(entry.getKey()), entry.getValue());\n\t\t\t}\n\t\t\tif (origPmc.isUseRewards()) {\n\t\t\t\toptPmc.setReward(newState, origPmc.getReward(someOriginalState));\n\t\t\t\tif (optPmc.getReward(newState).equals(origPmc.getFunctionFactory().getZero())) {\n\t\t\t\t\toptPmc.setTargetState(newState, true);\t\t\t\t\t\n\t\t\t\t}\n\t\t\t\tif (origPmc.isUseTime()) {\n\t\t\t\t\toptPmc.setTime(newState, origPmc.getTime(someOriginalState));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\toptPmc.setTargetState(newState, origPmc.isTargetState(someOriginalState));\n\t\t\t}\n\t\t\tfor (int oldState : fromBlock) {\n\t\t\t\tif (origPmc.isInitState(oldState)) {\n\t\t\t\t\toptPmc.setInitState(newState, true);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/param/ValueComputer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport common.IterableBitSet;\nimport common.IterableStateSet;\nimport explicit.CTMC;\nimport explicit.DTMC;\nimport explicit.DTMCFromMDPMemorylessAdversary;\nimport explicit.MDP;\nimport explicit.MDPSimple;\nimport explicit.Model;\nimport explicit.rewards.MCRewards;\nimport explicit.rewards.MCRewardsFromMDPRewards;\nimport explicit.rewards.MDPRewards;\nimport explicit.rewards.MDPRewardsSimple;\nimport explicit.rewards.Rewards;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.Iterator;\nimport java.util.Map.Entry;\n\n/**\n * Computes values for properties of a parametric Markov model. \n */\nfinal class ValueComputer extends PrismComponent\n{\n\tprivate enum PropType {\n\t\tREACH,\n\t\tSTEADY\n\t};\n\n\tclass SchedulerCacheKey\n\t{\t\t\n\t\tfinal private PropType propType;\n\t\tfinal private BitSet b1;\n\t\tfinal private BitSet b2;\n\t\tfinal private boolean min;\n\t\tfinal private Rewards<?> rew;\n\t\t\n\t\tSchedulerCacheKey(PropType propType, StateValues b1, StateValues b2, boolean min, Rewards<?> rew, Region region)\n\t\t{\n\t\t\tthis.propType = propType;\n\t\t\tthis.b1 = b1.toBitSet();\n\t\t\tif (b2 == null) {\n\t\t\t\tthis.b2 = null;\n\t\t\t} else {\n\t\t\t\tthis.b2 = b2.toBitSet();\n\t\t\t}\n\t\t\tthis.min = min;\n\t\t\tthis.rew = rew;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean equals(Object obj) {\n\t\t\tif (!(obj instanceof SchedulerCacheKey)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tSchedulerCacheKey other = (SchedulerCacheKey) obj;\n\t\t\tif (!this.propType.equals(other.propType)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (!this.b1.equals(other.b1)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif ((this.b2 == null) != (other.b2 == null)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (this.b2 != null && !this.b2.equals(other.b2)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif ((this.rew == null) != (other.rew == null)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif ((rew != null) && !this.rew.equals(other.rew)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (this.min != other.min){\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic int hashCode() {\n\t\t\tint hash = 0;\n\t\t\t\n\t\t\tswitch (propType) {\n\t\t\tcase REACH:\n\t\t\t\thash = 13;\n\t\t\t\tbreak;\n\t\t\tcase STEADY:\n\t\t\t\thash = 17;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\thash = ((b1 == null) ? 0 : b1.hashCode()) + (hash << 6) + (hash << 16) - hash;\n\t\t\tif (this.b2 != null) {\n\t\t\t\thash = ((b2 == null) ? 0 : b2.hashCode()) + (hash << 6) + (hash << 16) - hash;\n\t\t\t}\n\t\t\thash = ((min) ? 13 : 17) + (hash << 6) + (hash << 16) - hash;\n\t\t\thash = ((rew == null) ? 0 : rew.hashCode()) + (hash << 6) + (hash << 16) - hash;\n\t\t\t\n\t\t\treturn hash;\n\t\t}\n\t}\n\n\tclass ResultCacheKey\n\t{\n\t\tfinal private PropType propType;\n\t\tfinal private BitSet b1;\n\t\tfinal private BitSet b2;\n\t\tfinal private Rewards<?> rew;\n\t\tfinal private Scheduler sched;\n\t\tfinal private boolean min;\n\t\t\n\t\tResultCacheKey(PropType propType, StateValues b1, StateValues b2, Rewards<?> rew, Scheduler sched, boolean min)\n\t\t{\n\t\t\tthis.propType = propType;\n\t\t\tthis.b1 = b1.toBitSet();\n\t\t\tif (b2 == null) {\n\t\t\t\tthis.b2 = null;\n\t\t\t} else {\n\t\t\t\tthis.b2 = b2.toBitSet();\n\t\t\t}\n\t\t\tthis.rew = rew;\n\t\t\tthis.sched = sched;\n\t\t\tthis.min = min;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean equals(Object obj) {\n\t\t\tif (!(obj instanceof ResultCacheKey)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tResultCacheKey other = (ResultCacheKey) obj;\n\t\t\tif (!this.propType.equals(other.propType)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (!this.b1.equals(other.b1)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif ((this.b2 == null) != (other.b2 == null)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (this.b2 != null && !this.b2.equals(other.b2)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif ((this.rew == null) != (other.rew == null)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif ((rew != null) && !this.rew.equals(other.rew)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif ((this.sched == null) != (other.sched == null)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (!this.sched.equals(other.sched)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (this.min != other.min){\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic int hashCode() {\n\t\t\tint hash = 0;\n\t\t\t\n\t\t\tswitch (propType) {\n\t\t\tcase REACH:\n\t\t\t\thash = 13;\n\t\t\t\tbreak;\n\t\t\tcase STEADY:\n\t\t\t\thash = 17;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\thash = b1.hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t\tif (this.b2 != null) {\n\t\t\t\thash = b2.hashCode() + (hash << 6) + (hash << 16) - hash;\n\t\t\t}\n\t\t\thash = (rew == null ? 0 : rew.hashCode()) + (hash << 6) + (hash << 16) - hash;\n\t\t\thash = (sched == null ? 0 : sched.hashCode()) + (hash << 6) + (hash << 16) - hash;\n\t\t\thash = (min ? 13 : 17) + (hash << 6) + (hash << 16) - hash;\n\t\t\t\n\t\t\treturn hash;\n\t\t}\n\t}\n\t\n\tclass ResultCacheEntry\n\t{\n\t\tfinal private StateValues values;\n\t\tfinal private Function[] compare;\n\t\t\n\t\tResultCacheEntry(StateValues values, Function[] compare)\n\t\t{\n\t\t\tthis.values = values;\n\t\t\tthis.compare = compare;\n\t\t}\n\t\t\n\t\tStateValues getValues()\n\t\t{\n\t\t\treturn values;\n\t\t}\n\t\t\n\t\tFunction[] getCompare()\n\t\t{\n\t\t\treturn compare;\n\t\t}\n\t}\n\n\tprivate ParamMode mode;\n\tprivate RegionFactory regionFactory;\n\tprivate FunctionFactory functionFactory;\n\tprivate ConstraintChecker constraintChecker;\n\tprivate BigRational precision;\n\tprivate HashMap<SchedulerCacheKey,ArrayList<Scheduler>> schedCache;\n\tprivate HashMap<ResultCacheKey,ResultCacheEntry> resultCache;\n\tprivate StateEliminator.EliminationOrder eliminationOrder;\n\tprivate Lumper.BisimType bisimType;\n\n\tValueComputer(PrismComponent parent, ParamMode mode, RegionFactory regionFactory, BigRational precision, StateEliminator.EliminationOrder eliminationOrder, Lumper.BisimType bisimType) {\n\t\tsuper(parent);\n\t\tthis.mode = mode;\n\t\tthis.regionFactory = regionFactory;\n\t\tthis.functionFactory = regionFactory.getFunctionFactory();\n\t\tthis.constraintChecker = regionFactory.getConstraintChecker();\n\t\tthis.precision = precision;\n\t\tthis.schedCache = new HashMap<SchedulerCacheKey,ArrayList<Scheduler>>();\n\t\tthis.resultCache = new HashMap<ResultCacheKey,ResultCacheEntry>();\n\t\tthis.eliminationOrder = eliminationOrder;\n\t\tthis.bisimType = bisimType;\n\t}\n\n\tRegionValues computeUnbounded(Model<?> model, RegionValues b1, RegionValues b2, boolean min, Rewards<?> rew) throws PrismException {\n\t\tRegionValues result = new RegionValues(regionFactory);\n\t\tRegionValuesIntersections co = new RegionValuesIntersections(b1, b2);\n\t\tfor (RegionIntersection inter : co) {\n\t\t\tRegion region = inter.getRegion();\n\t\t\tStateValues value1 = inter.getStateValues1();\n\t\t\tStateValues value2 = inter.getStateValues2();\n\t\t\tRegionValues val = computeUnbounded(model, region, value1, value2, min, rew);\n\t\t\tresult.addAll(val);\n\t\t}\n\t\treturn result;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\tprivate RegionValues computeUnbounded(Model<?> model, Region region, StateValues b1, StateValues b2, boolean min, Rewards<?> rew) throws PrismException\n\t{\n\t\tswitch (model.getModelType()) {\n\t\tcase CTMC:\n\t\tcase DTMC:\n\t\t\treturn computeUnboundedMC((DTMC<Function>) model, region, b1, b2, (MCRewards<Function>) rew);\n\t\tcase MDP:\n\t\t\treturn computeUnboundedMDP((MDP<Function>) model, region, b1, b2, min, (MDPRewards<Function>) rew);\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Parametric unbounded reachability computation not supported for \" + model.getModelType());\n\t\t}\n\t}\n\n\tprivate RegionValues computeUnboundedMC(DTMC<Function> dtmc, Region region, StateValues b1, StateValues b2, MCRewards<Function> mcRewards) throws PrismException\n\t{\n\t\tBitSet inf = null;\n\t\tif (mcRewards != null) {\n\t\t\t// determine infinity states\n\t\t\texplicit.DTMCModelChecker mcExplicit = new explicit.DTMCModelChecker(this);\n\t\t\tmcExplicit.setSilentPrecomputations(true);\n\t\t\tinf = mcExplicit.prob1(dtmc, b1.toBitSet(), b2.toBitSet());\n\t\t\tinf.flip(0, dtmc.getNumStates());\n\t\t\tfor (int i : new IterableStateSet(inf, dtmc.getNumStates())) {\n\t\t\t\t// clear states with infinite value from b1 so they will get Infinity value in the DTMC\n\t\t\t\tb1.setStateValue(i, false);\n\t\t\t}\n\t\t}\n\n\t\tMutablePMC pmc = buildAlterablePMCForReach(dtmc, b1, b2, mcRewards);\n\t\t// TODO\n//\t\tif (rew != null && mode == ParamMode.EXACT) {\n//\t\t\trew.checkForNonNormalRewards();\n//\t\t}\n\n\t\tStateValues values = computeValues(pmc, dtmc.getFirstInitialState());\n\n\t\t// Set value of infinity states\n\t\tif (mcRewards != null) {\n\t\t\tfor (int i : new IterableStateSet(inf, dtmc.getNumStates())) {\n\t\t\t\tvalues.setStateValue(i, functionFactory.getInf());\n\t\t\t}\n\t\t}\n\n\t\treturn regionFactory.completeCover(values);\n\t}\n\n\tprivate RegionValues computeUnboundedMDP(MDP<Function> mdp, Region region, StateValues b1, StateValues b2, boolean min, MDPRewards<Function> mdpRewards) throws PrismException\n\t{\n\t\tBigRational precisionForThisRegion = region.volume().multiply(precision);\n\t\tBigRational requiredVolume = region.volume().subtract(precisionForThisRegion);\n\t\tRegionValues result = new RegionValues(regionFactory);\n\t\tRegionsTODO todo = new RegionsTODO();\n\t\ttodo.add(region);\n\t\tBigRational volume = BigRational.ZERO;\n\n\t\tif (mdpRewards != null) {\n\t\t\t// determine infinity states\n\t\t\texplicit.MDPModelChecker mcExplicit = new explicit.MDPModelChecker(this);\n\t\t\tmcExplicit.setSilentPrecomputations(true);\n\t\t\tBitSet inf = mcExplicit.prob1(mdp, b1.toBitSet(), b2.toBitSet(), !min, null);\n\t\t\tinf.flip(0, mdp.getNumStates());\n\n\t\t\tfor (int i : new IterableStateSet(inf, mdp.getNumStates())) {\n\t\t\t\t// clear states with infinite value from b1 so they will get Infinity value\n\t\t\t\t// in the DTMC\n\t\t\t\tb1.setStateValue(i, false);\n\t\t\t}\n\t\t}\n\n\t\tScheduler initialScheduler = new Scheduler(mdp);\n\t\tprecomputeScheduler(mdp, initialScheduler, b1, b2, mdpRewards, min);\n\n\t\twhile (volume.compareTo(requiredVolume) == -1) {\n\t\t\tRegion currentRegion = todo.poll();\n\t\t\tPoint midPoint = ((BoxRegion)currentRegion).getMidPoint();\n\t\t\tScheduler scheduler = computeOptConcreteReachScheduler(midPoint, mdp, b1, b2, min, mdpRewards, initialScheduler);\n\t\t\tif (scheduler == null) {\n\t\t\t\t// midpoint leads to non-well-defined model\n\t\t\t\tif (currentRegion.volume().compareTo(precisionForThisRegion) <= 0) {\n\t\t\t\t\t// region is below precision threshold, treat as undefined\n\t\t\t\t\t// and adjust required volume\n\t\t\t\t\trequiredVolume = requiredVolume.subtract(currentRegion.volume());\n\t\t\t\t} else {\n\t\t\t\t\t// we split the current region\n\t\t\t\t\t// TODO: Would be nice to try and analyse the well-definedness constraints\n\t\t\t\t\ttodo.addAll(currentRegion.split());\n\t\t\t\t}\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tResultCacheEntry resultCacheEntry = lookupValues(PropType.REACH, b1, b2, mdpRewards, scheduler, min);\n\t\t\tFunction[] compare;\n\t\t\tStateValues values;\n\t\t\tif (resultCacheEntry == null) {\n\t\t\t\tDTMC<Function> dtmc = new DTMCFromMDPMemorylessAdversary<>(mdp, scheduler.choices);\n\t\t\t\tMCRewards<Function> mcRewards = mdpRewards == null ? null : new MCRewardsFromMDPRewards<>(mdpRewards, scheduler.choices);\n\t\t\t\tMutablePMC pmc = buildAlterablePMCForReach(dtmc, b1, b2, mcRewards);\n\t\t\t\tvalues = computeValues(pmc, mdp.getFirstInitialState());\n\t\t\t\tcompare = computeCompare(mdp, b1, b2, mdpRewards, scheduler, min, values);\n\t\t\t\tstoreValues(PropType.REACH, b1, b2, mdpRewards, scheduler, min, values, compare);\n\t\t\t} else {\n\t\t\t\tvalues = resultCacheEntry.getValues();\n\t\t\t\tcompare = resultCacheEntry.getCompare();\n\t\t\t}\n\t\t\tboolean ok = true;\n\t\t\tFunction choiceValue = null;\n\t\t\tfor (Function entry : compare) {\n\t\t\t\tchoiceValue = entry;\n\t\t\t\tif (!constraintChecker.check(currentRegion, entry, false)) {\n\t\t\t\t\tok = false;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (ok) {\n\t\t\t\tvolume = volume.add(currentRegion.volume());\n\t\t\t\tresult.add(currentRegion, values);\n\t\t\t} else {\n\t\t\t\ttodo.addAll(currentRegion.split(choiceValue));\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\t\n\tprivate Function[] computeCompare(MDP<Function> model, StateValues b1, StateValues b2,\n\t\t\tMDPRewards<Function> mdpRewards, Scheduler scheduler, boolean min,\n\t\t\tStateValues values) {\n\t\tHashSet<Function> allValues = new HashSet<Function>();\n\t\t\n\t\tfor (int state = 0; state < model.getNumStates(); state++) {\n\t\t\tif (!b1.getStateValueAsBoolean(state) || b2.getStateValueAsBoolean(state)) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\tFunction stateValue = values.getStateValueAsFunction(state);\n\t\t\tfor (int altChoice = 0; altChoice < model.getNumChoices(state); altChoice++) {\n\t\t\t\tFunction choiceValue = functionFactory.getZero();\n\t\t\t\tif (mdpRewards != null) {\n\t\t\t\t\tchoiceValue = choiceValue.add(mdpRewards.getStateReward(state));\n\t\t\t\t\tchoiceValue = choiceValue.add(mdpRewards.getTransitionReward(state, altChoice));\n\t\t\t\t}\n\t\t\t\tIterator<Entry<Integer, Function>> iter = model.getTransitionsIterator(state, altChoice);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tEntry<Integer, Function> e = iter.next();\n\t\t\t\t\tint succState = e.getKey();\n\t\t\t\t\tFunction weighted = e.getValue().multiply(values.getStateValueAsFunction(succState));\n\t\t\t\t\tchoiceValue = choiceValue.add(weighted);\n\t\t\t\t}\n\t\t\t\tchoiceValue = min ? choiceValue.subtract(stateValue) : stateValue.subtract(choiceValue);\n\t\t\t\tallValues.add(choiceValue);\n\t\t\t}\n\t\t}\n\n\t\treturn allValues.toArray(new Function[0]);\n\t}\n\n\tprivate void storeValues(PropType propType, StateValues b1, StateValues b2,\n\t\t\tRewards<?> rew, Scheduler scheduler, boolean min, StateValues values, Function[] compare) {\n\t\tResultCacheKey cacheKey = new ResultCacheKey(propType, b1, b2, rew, scheduler, min);\n\t\tResultCacheEntry resultCacheEntry = new ResultCacheEntry(values, compare);\n\t\tresultCache.put(cacheKey, resultCacheEntry);\n\t}\n\n\tprivate ResultCacheEntry lookupValues(PropType propType, StateValues b1, StateValues b2,\n\t\t\tRewards<?> rew, Scheduler scheduler, boolean min) {\n\t\tResultCacheKey cacheKey = new ResultCacheKey(propType, b1, b2, rew, scheduler, min);\n\t\tResultCacheEntry resultCacheEntry = resultCache.get(cacheKey);\n\t\treturn resultCacheEntry;\n\t}\n\n\t/**\n\t * Compute an optimal scheduler for Pmin/Pmax[ b1 U b2 ] or Rmin/Rmax[ b1 U b2 ]\n\t * at the given parameter instantiation (point).\n\t * <br>\n\t * In parametric mode, returns {@code null} if the given point leads to a model\n\t * that is not well-formed, i.e., where transition probabilities are not actually\n\t * probabilities or graph-preserving, or the rewards are negative (not supported for MDPs).\n\t * <br>\n\t * In exact mode, throws an exception if there are negative rewards (not supported for MDPs).\n\t * <br>\n\t * This method expects an initial scheduler that ensures that policy iteration\n\t * will converge.\n\t *\n\t * @param point The point (parameter valuation) where the model should be instantiated\n\t * @param mdp the model\n\t * @param b1 the set of 'safe' states\n\t * @param b2 the set of 'target' states\n\t * @param min compute min or max? true = min\n\t * @param mdpRewards if non-null, compute reachability reward\n\t * @param initialScheduler an initial scheduler\n\t * @return an optimal scheduler\n\t */\n\tScheduler computeOptConcreteReachScheduler(Point point, MDP<Function> mdp, StateValues b1, StateValues b2, boolean min, MDPRewards<Function> mdpRewards, Scheduler initialScheduler) throws PrismException\n\t{\n\t\t// Instantiate MDP/reward with parameter values\n\t\tMDP<Function> mdpConcrete = new MDPSimple<Function>(mdp, r -> functionFactory.fromBigRational(r.evaluate(point)));\n\t\tMDPRewards<Function> mdpRewardsConcrete = null;\n\t\tif (mdpRewards != null) {\n\t\t\tmdpRewardsConcrete = new MDPRewardsSimple<>(mdpRewards, mdp, r -> functionFactory.fromBigRational(r.evaluate(point)));\n\t\t}\n\n\t\t// Check that instantiated MDP is well defined (underlying graph is preserved)\n\t\tfor (int state = 0; state < mdpConcrete.getNumStates(); state++) {\n\t\t\tfor (int altChoice = 0; altChoice < mdpConcrete.getNumChoices(state); altChoice++) {\n\t\t\t\tIterator<Entry<Integer, Function>> iter = mdpConcrete.getTransitionsIterator(state, altChoice);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tEntry<Integer, Function> e = iter.next();\n\t\t\t\t\tBigRational p = e.getValue().asBigRational();\n\t\t\t\t\tif (p.isSpecial() || p.compareTo(BigRational.ONE) == 1 || p.signum() <= 0) {\n\t\t\t\t\t\tthrow new PrismException(\"Parametric MDP is not well defined: probability in state \" + state + \" is \" + p);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tScheduler scheduler = lookupScheduler(point, mdpConcrete, PropType.REACH, b1, b2, min, mdpRewardsConcrete);\n\t\tif (scheduler != null) {\n\t\t\treturn scheduler;\n\t\t}\n\t\tscheduler = initialScheduler.clone();\n\t\tboolean changed = true;\n\t\twhile (changed) {\n\t\t\tDTMC<Function> dtmcConcrete = new DTMCFromMDPMemorylessAdversary<>(mdpConcrete, scheduler.choices);\n\t\t\tMCRewards<Function> mcRewardsConcrete = mdpRewardsConcrete == null ? null : new MCRewardsFromMDPRewards<>(mdpRewardsConcrete, scheduler.choices);\n\t\t\tMutablePMC pmc = buildAlterablePMCForReach(dtmcConcrete, b1, b2, mcRewardsConcrete);\n\t\t\tStateValues fnValues = computeValues(pmc, mdpConcrete.getFirstInitialState());\n\t\t\tBigRational[] values = new BigRational[fnValues.getNumStates()];\n\t\t\tfor (int state = 0; state < mdpConcrete.getNumStates(); state++) {\n\t\t\t\tvalues[state] = fnValues.getStateValueAsFunction(state).asBigRational();\n\t\t\t}\n\t\t\t\t\t\n\t\t\tchanged = false;\n\t\t\tfor (int state = 0; state < mdpConcrete.getNumStates(); state++) {\n\t\t\t\tif (!b1.getStateValueAsBoolean(state) || b2.getStateValueAsBoolean(state)) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tBigRational bestVal = values[state];\n\t\t\t\tfor (int altChoice = 0; altChoice < mdpConcrete.getNumChoices(state); altChoice++) {\n\t\t\t\t\tBigRational choiceValue = BigRational.ZERO;\n\t\t\t\t\tIterator<Entry<Integer, Function>> iter = mdpConcrete.getTransitionsIterator(state, altChoice);\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tEntry<Integer, Function> e = iter.next();\n\t\t\t\t\t\tint succState = e.getKey();\n\t\t\t\t\t\tBigRational succProb = e.getValue().asBigRational();\n\t\t\t\t\t\tBigRational succVal = values[succState];\n\t\t\t\t\t\tBigRational weighted = succProb.multiply(succVal);\n\t\t\t\t\t\tchoiceValue = choiceValue.add(weighted);\n\t\t\t\t\t}\n\t\t\t\t\tif (mdpRewards != null) {\n\t\t\t\t\t\tchoiceValue = choiceValue.add(mdpRewards.getStateReward(state).asBigRational());\n\t\t\t\t\t\tchoiceValue = choiceValue.add(mdpRewards.getTransitionReward(state, altChoice).asBigRational());\n\t\t\t\t\t}\n\t\t\t\t\tif (bestVal.compareTo(choiceValue) == (min ? 1 : -1)) {\n\t\t\t\t\t\tscheduler.setChoice(state, altChoice);\n\t\t\t\t\t\tbestVal = choiceValue;\n\t\t\t\t\t\tchanged = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tstoreScheduler(PropType.REACH, b1, b2, min, mdpRewards, scheduler);\n\n\t\treturn scheduler;\n\t}\n\t\n\tprivate void storeScheduler(PropType propType, StateValues b1, StateValues b2, boolean min,\n\t\t\tRewards<?> rew, Scheduler scheduler) {\n\t\tSchedulerCacheKey cacheKey = new SchedulerCacheKey(propType, b1, b2, min, rew, null);\n\t\tArrayList<Scheduler> schedulers = schedCache.get(cacheKey);\n\t\tif (schedulers == null) {\n\t\t\tschedulers = new ArrayList<Scheduler>();\n\t\t\tschedCache.put(cacheKey, schedulers);\n\t\t}\n\t\tschedulers.add(scheduler);\t\t\n\t}\n\n\tprivate Scheduler lookupScheduler(Point point, MDP<Function> mdp, PropType propType, StateValues b1, StateValues b2,\n\t\t\tboolean min, Rewards<?> rew)\n\t{\n\t\tSchedulerCacheKey cacheKey = new SchedulerCacheKey(propType, b1, b2, min, rew, null);\n\t\tArrayList<Scheduler> schedulers = schedCache.get(cacheKey);\n\t\tif (schedulers == null) {\n\t\t\treturn null;\n\t\t}\n\n\t\tfor (Scheduler scheduler : schedulers) {\n\t\t\tif (checkScheduler(point, propType, b1, b2, min, rew, scheduler)) {\n\t\t\t\treturn scheduler;\n\t\t\t}\n\t\t}\n\n\t\treturn null;\n\t}\n\n\tprivate boolean checkScheduler(final Point point, final PropType propType, final StateValues b1, final StateValues b2,\n\t\t\tfinal boolean min, final Rewards<?> rew, final Scheduler scheduler)\n\t{\n\t\tResultCacheKey resultKey = new ResultCacheKey(propType, b1, b2, rew, scheduler, min);\n\t\tResultCacheEntry resultCacheEntry = resultCache.get(resultKey);\n\t\t\n\t\tFunction compare[] = resultCacheEntry.getCompare();\t\t\n\t\tfor (Function entry : compare) {\n\t\t\tif (entry.evaluate(point, false).signum() == -1) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Perform precomputation for policy iteration.\n\t * <br>\n\t * For Pmin, if possible, for states with Pmin[ b1 U b2 ] = 0, generate zero scheduler.\n\t * <br>\n\t * For Rmin, generate a proper scheduler, i.e., with P^sched[ b1 U b2 ] = 1\n\t * to get proper convergence in policy iteration.\n\t * Assumes that states with Pmax[ b1 U b2 ] &lt; 1 have been filtered beforehand\n\t * and are not contained in b1 or b2.\n\t * <br>\n\t * In case of maximal accumulated reward or probabilities, currently does\n\t * nothing.\n\t * <br>\n\t * If {@code rew == null}, performs reachability, otherwise\n\t * performs accumulated reward computation. {@code b2} is the target set\n\t * for reachability probabilities or accumulated rewards. {@code b1} is\n\t * either constantly {@code true} or describes the left side of an until\n\t * property.\n\t */\n\tprivate void precomputeScheduler(MDP<Function> mdp, Scheduler sched, StateValues b1, StateValues b2, MDPRewards<Function> rew, boolean min) throws PrismException\n\t{\n\t\tif (rew == null) {\n\t\t\t// probability case\n\t\t\tif (min) {\n\t\t\t\tprecomputePmin(mdp, sched, b1, b2);\n\t\t\t}\n\t\t} else {\n\t\t\tif (min)\n\t\t\t\tprecomputeRminProperScheduler(mdp, sched, b1, b2);\n\t\t\t// TODO: Would be nice to generate proper zero scheduler in the situations\n\t\t\t// where that is possible\n\t\t}\n\t}\n\n\t/**\n\t * Precomputation for policy iteration, Rmin.\n\t * For Rmin, generate a proper scheduler, i.e., with P^sched[ b1 U b2 ] = 1\n\t * to get proper convergence in policy iteration.\n\t * Assumes that states with Pmax[ b1 U b2 ] &lt; 1 have been filtered beforehand\n\t * and are not contained in b1 or b2.\n\t */\n\tprivate void precomputeRminProperScheduler(MDP<Function> mdp, Scheduler sched, StateValues b1, StateValues b2) throws PrismException\n\t{\n\t\texplicit.MDPModelChecker mcExplicit = new explicit.MDPModelChecker(this);\n\t\tmcExplicit.setSilentPrecomputations(true);\n\t\tint[] strat = new int[mdp.getNumStates()];\n\t\tBitSet b1bs = b1.toBitSet();\n\t\t// use prob1e strategy generation from explicit model checker\n\t\tmcExplicit.prob1(mdp, b1bs, b2.toBitSet(), false, strat);\n\n\t\tfor (int s : IterableBitSet.getSetBits(b1bs)) {\n\t\t\tassert(strat[s] >= 0);\n\t\t\tsched.setChoice(s, strat[s]);\n\t\t}\n\t}\n\n\t/**\n\t * Precomputation for policy iteration, Pmin.\n\t * Sets decisions of {@code sched} such that states which have a minimal\n\t * reachability probability of zero do already have a minimal value of zero\n\t * if using this schedulers. For states with minimal value larger than zero,\n\t * this scheduler needs not be minimising.\n\t * {@code b2} is the target set for reachability probabilities. {@code b1} is\n\t * either constantly {@code true} or describes the left side of an until\n\t * property.\n\t * \n\t * @param mdp Markov model to precompute for\n\t * @param sched scheduler to precompute\n\t * @param b1 left side of U property, or constant true\n\t * @param b2 right side of U property, or of reachability reward\n\t */\n\tprivate void precomputePmin(MDP<Function> mdp, Scheduler sched, StateValues b1, StateValues b2)\n\t{\n\t\tBitSet ones = new BitSet(mdp.getNumStates());\n\t\tfor (int state = 0; state < mdp.getNumStates(); state++) {\n\t\t\tones.set(state, b2.getStateValueAsBoolean(state));\n\t\t}\n\t\tboolean changed = true;\n\t\twhile (changed) {\n\t\t\tchanged = false;\n\t\t\tfor (int state = 0; state < mdp.getNumStates(); state++) {\n\t\t\t\tif (!b1.getStateValueAsBoolean(state) || ones.get(state)) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tboolean allChoicesSeenOnes = true;\n\t\t\t\tfor (int choice = 0; choice < mdp.getNumChoices(state); choice++) {\n\t\t\t\t\tboolean seenOnes = false;\n\t\t\t\t\tIterator<Entry<Integer, Function>> iter = mdp.getTransitionsIterator(state, choice);\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tEntry<Integer, Function> e = iter.next();\n\t\t\t\t\t\tif (ones.get(e.getKey())) {\n\t\t\t\t\t\t\tseenOnes = true;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (!seenOnes) {\n\t\t\t\t\t\tsched.setChoice(state, choice);\n\t\t\t\t\t\tallChoicesSeenOnes = false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allChoicesSeenOnes) {\n\t\t\t\t\tones.set(state, true);\n\t\t\t\t\tchanged = true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Build a MutablePMC object for a probabilistic/reward reach problem.\n\t */\n\tprivate MutablePMC buildAlterablePMCForReach(DTMC<Function> dtmc, StateValues b1, StateValues b2, MCRewards<Function> mcRewards) throws PrismException\n\t{\n\t\tMutablePMC pmc = buildAlterablePMC(dtmc, b2.toBitSet(), b1.toBitSet(), mcRewards != null, false);\n\t\tif (mcRewards != null) {\n\t\t\tsetPMCReward(pmc, s -> b2.toBitSet().get(s) ? functionFactory.getZero() : b1.toBitSet().get(s) ? mcRewards.getStateReward(s) : functionFactory.getInf());\n\t\t}\n\t\tif (dtmc.getModelType() == ModelType.CTMC && mcRewards != null) {\n\t\t\tnormalisePMCRewards(pmc, (CTMC<Function>) dtmc);\n\t\t}\n\t\treturn pmc;\n\t}\n\n\t/**\n\t * Build a MutablePMC object, copying transitions from a DTMC/CTMC\n\t * @param dtmc D/CTMC to extract transitions an dinitial states from\n\t * @param target States to note as target in MutablePMC\n\t * @param nonSink Only copy transitions for (non-target) states from here (null = all)\n\t * @param useRewards Flag to set in MutablePMC\n\t * @param useTime Flag to set in MutablePMC\n\t */\n\tprivate MutablePMC buildAlterablePMC(DTMC<Function> dtmc, BitSet target, BitSet nonSink, boolean useRewards, boolean useTime) throws PrismException\n\t{\n\t\t// Switch to embedded DTMC for a CTMC\n\t\tif (dtmc.getModelType() == ModelType.CTMC) {\n\t\t\tdtmc = ((CTMC<Function>) dtmc).getImplicitEmbeddedDTMC();\n\t\t}\n\t\tMutablePMC pmc = new MutablePMC(functionFactory, dtmc.getNumStates(), useRewards, useTime);\n\t\tfor (int s = 0; s < dtmc.getNumStates(); s++) {\n\t\t\t// Set initial/target state info\n\t\t\tpmc.setTargetState(s, target.get(s));\n\t\t\tpmc.setInitState(s, dtmc.isInitialState(s));\n\t\t\t// Copy transitions or add loop for a sink state\n\t\t\tif ((nonSink == null || nonSink.get(s)) && !target.get(s)) {\n\t\t\t\tIterator<Entry<Integer, Function>> iter = dtmc.getTransitionsIterator(s);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tEntry<Integer, Function> e = iter.next();\n\t\t\t\t\tpmc.addTransition(s, e.getKey(), e.getValue());\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tpmc.addTransition(s, s, functionFactory.getOne());\n\t\t\t}\n\t\t}\n\t\treturn pmc;\n\t}\n\n\t/**\n\t * Set the reward for each state s in a MutablePMC to f(s).\n\t */\n\tprivate void setPMCReward(MutablePMC pmc, java.util.function.Function<Integer,Function> f)\n\t{\n\t\tint numStates = pmc.getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tpmc.setReward(s, f.apply(s));\n\t\t}\n\t}\n\n\t/**\n\t * Divide the rewards in a MutablePMC by the exit rates of a CTMC.\n\t */\n\tprivate void normalisePMCRewards(MutablePMC pmc, CTMC<Function> ctmc)\n\t{\n\t\tint numStates = pmc.getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tpmc.setReward(s, pmc.getReward(s).divide(ctmc.getExitRate(s)));\n\t\t}\n\t}\n\n\t/**\n\t * Divide the rewards in a MutablePMC by the exit rates of a CTMC.\n\t */\n\tprivate void normalisePMCTimes(MutablePMC pmc, CTMC<Function> ctmc)\n\t{\n\t\tint numStates = pmc.getNumStates();\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tpmc.setTime(s, pmc.getTime(s).divide(ctmc.getExitRate(s)));\n\t\t}\n\t}\n\n\tprivate StateValues computeValues(MutablePMC pmc, int initState)\n\t{\n\t\tLumper lumper;\n\t\tswitch (bisimType) {\n\t\tcase NULL:\n\t\t\tlumper = new NullLumper(pmc);\n\t\t\tbreak;\n\t\tcase STRONG:\n\t\t\tlumper = new StrongLumper(pmc);\n\t\t\tbreak;\n\t\tcase WEAK:\n\t\t\tif (pmc.isUseRewards()) {\n\t\t\t\tlumper = new StrongLumper(pmc);\n\t\t\t} else{\n\t\t\t\tlumper = new WeakLumper(pmc);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new RuntimeException(\"invalid bisimulation method\"); \n\t\t}\n\t\tif (lumper instanceof WeakLumper && pmc.isUseTime()) {\n\t\t\tlumper = new StrongLumper(pmc);\n\t\t}\n\t\t\n\t\tMutablePMC quot = lumper.getQuotient();\n\t\tStateEliminator eliminator = new StateEliminator(quot, eliminationOrder);\n\t\teliminator.eliminate();\n\t\tint[] origToCopy = lumper.getOriginalToOptimised();\n\t\tStateValues result = new StateValues(pmc.getNumStates(), initState);\n\t\tfor (int state = 0; state < origToCopy.length; state++) {\n\t\t\tresult.setStateValue(state, eliminator.getResult(origToCopy[state]));\n\t\t}\n\t\treturn result;\n\t}\n\n\tprivate RegionValues computeSteadyState(Model<?> model, Region region, StateValues b1, boolean min, Rewards<?> rew) throws PrismException\n\t{\n\t\tif (!(model.getModelType() == ModelType.DTMC || model.getModelType() == ModelType.CTMC)) {\n\t\t\tthrow new PrismNotSupportedException(\"Parametric steady state computation not supported for \" + model.getModelType());\n\t\t}\n\n\t\tMCRewards<Function> mcRewards = (MCRewards<Function>) rew;\n\t\tRegionValues result = new RegionValues(regionFactory);\n\t\tResultCacheEntry resultCacheEntry = lookupValues(PropType.STEADY, b1, null, rew, null, min);\n\t\tStateValues values;\n\t\tif (resultCacheEntry == null) {\n\t\t\tMutablePMC pmc = buildAlterablePMC((DTMC<Function>) model, new BitSet(), null, true, true);\n\t\t\tif (rew != null) {\n\t\t\t\tsetPMCReward(pmc, s -> ((MCRewards<Function>) rew).getStateReward(s));\n\t\t\t} else {\n\t\t\t\tsetPMCReward(pmc, s -> b1.getStateValueAsBoolean(s) ? functionFactory.getOne() : functionFactory.getZero());\n\t\t\t}\n\t\t\tif (model.getModelType() == ModelType.CTMC) {\n\t\t\t\tnormalisePMCRewards(pmc, (CTMC<Function>) model);\n\t\t\t\tnormalisePMCTimes(pmc, (CTMC<Function>) model);\n\t\t\t}\n\t\t\tvalues = computeValues(pmc, model.getFirstInitialState());\n\t\t\tstoreValues(PropType.STEADY, b1, null, rew, null, min, values, null);\n\t\t} else {\n\t\t\tvalues = resultCacheEntry.getValues();\n\t\t}\n\t\tresult.add(region, values);\n\n\t\treturn result;\n\t}\n\n\t\n\tpublic RegionValues computeSteadyState(Model<?> model, RegionValues b, boolean min, Rewards<?> rew) throws PrismException\n\t{\n\t\tRegionValues result = new RegionValues(regionFactory);\n\t\tfor (Entry<Region, StateValues> entry : b) {\n\t\t\tRegion region = entry.getKey();\n\t\t\tStateValues value = entry.getValue();\n\t\t\tRegionValues val = computeSteadyState(model, region, value, min, rew);\n\t\t\tresult.addAll(val);\t\t\t\n\t\t}\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/WeakLumper.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2013-\n//\tAuthors:\n//\t* Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage param;\n\nimport java.util.ArrayDeque;\nimport java.util.ArrayList;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.Iterator;\nimport java.util.ListIterator;\nimport java.util.Map.Entry;\n\n/**\n * Weak bisimulation lumper.\n * Notice that weak bisimulation is only valid for unbounded reachability,\n * but must not be used for expected accumulated rewards or long-run\n * average rewards.\n * \n * @author Ernst Moritz Hahn <emhahn@cs.ox.ac.uk> (University of Oxford)\n */\nfinal class WeakLumper extends Lumper {\n\n\t/**\n\t * Construct a new weak bisimulation lumper.\n\t * \n\t * @param origPmc Markov chain to construct lumper for\n\t */\n\tWeakLumper(MutablePMC origPmc) {\n\t\tsuper(origPmc);\n\t}\n\t\n\t/**\n\t * Construct the weak bisimulation signature of given block.\n\t * The signature is a mapping of blocks to the probability to move\n\t * from the given state to any state of the block under the condition\n\t * that the block is left. Thus, it is only defined for states which have\n\t * a non-zero probability of leaving the block in one step. The function\n\t * returns {@code null} for states (\"silent\" states) for which this is\n\t * not the case.\n\t * \n\t * @param state state to compute signature of\n\t * @return signature of this state\n\t */\n\tprivate HashMap<HashSet<Integer>, Function> stateSignature(int state, HashSet<Integer> ownClass)\n\t{\n\t\tHashMap<HashSet<Integer>, Function> signature = new HashMap<HashSet<Integer>, Function>();\n\t\tListIterator<Integer> toStateIter = origPmc.transitionTargets.get(state).listIterator();\n\t\tListIterator<Function> toProbIter = origPmc.transitionProbs.get(state).listIterator();\n\n\t\t/* compute probability to remain in block in one step */\n\t\tFunction slProb = origPmc.getFunctionFactory().getZero();\n\t\twhile (toStateIter.hasNext()) {\n\t\t\tint toState = toStateIter.next();\n\t\t\tFunction toStateProb = toProbIter.next();\n\t\t\tif (ownClass.contains(toState)) {\n\t\t\t\tslProb = slProb.add(toStateProb);\n\t\t\t}\n\t\t}\n\t\t/* for states which cannot leave their block directly, return {@code null} */\n\t\tif (slProb.equals(origPmc.getFunctionFactory().getOne())) {\n\t\t\treturn null;\n\t\t}\n\t\t/* 1 / (1 - slProb) */\n\t\tFunction star = slProb.star();\n\n\t\ttoStateIter = origPmc.transitionTargets.get(state).listIterator();\n\t\ttoProbIter = origPmc.transitionProbs.get(state).listIterator();\n\t\twhile (toStateIter.hasNext()) {\n\t\t\tint toState = toStateIter.next();\n\t\t\tFunction toStateProb = toProbIter.next();\n\t\t\tHashSet<Integer> toBlock = partition.getStateBlock(toState);\n\t\t\tif (ownClass != toBlock) {\n\t\t\t\ttoStateProb = star.multiply(toStateProb);\n\t\t\t\tFunction toBlockProb = signature.get(toBlock);\n\t\t\t\tif (toBlockProb == null) {\n\t\t\t\t\ttoBlockProb = origPmc.getFunctionFactory().getZero();\n\t\t\t\t}\n\t\t\t\ttoBlockProb = toBlockProb.add(toStateProb);\n\t\t\t\tsignature.put(toBlock, toBlockProb);\n\t\t\t}\n\t\t}\n\t\treturn signature;\n\t}\n\t\n\t/**\n\t * Refines a given block to a list of new blocks for weak bisimulation.\n\t * New blocks are as follows: some of the new blocks consist of the\n\t * states which can leave their block (\"non-silent\" states) and which\n\t * have the same signature. In addition, such a block contains the states\n\t * which cannot leave their block in one step (\"silent\" states) and which\n\t * can only reach states of this particular new block. Other blocks\n\t * consist of silent states which can reach more than one particular\n\t * signature block. For these kind of blocks, we have a new block for\n\t * each combination of new blocks they might reach. For instance, if\n\t * there are new blocks (based on a signature) A,B,C, we add blocks\n\t * {A,B},{B,C} and {A,B,C}, containing silent states which can reach\n\t * A and B / B and C / A, B and C. \n\t * \n\t * @param oldBlock block to refine\n\t * @param newBlocks list of new blocks generated\n\t */\n\t@Override\n\tprotected void refineBlock(HashSet<Integer> oldBlock,\n\t\t\tArrayList<HashSet<Integer>> newBlocks) {\n\t\tArrayList<Integer> nonSilent = new ArrayList<Integer>(oldBlock.size());\n\t\tHashSet<Integer> silent = new HashSet<Integer>();\n\t\tHashMap<HashMap<HashSet<Integer>, Function>, HashSet<Integer>> signatures = new HashMap<HashMap<HashSet<Integer>, Function>, HashSet<Integer>>();\n\t\tHashMap<Integer, HashSet<Integer>> stateToBlock = new HashMap<Integer, HashSet<Integer>>();\n\t\t/* compute signatures of states of old block and divide into silent/\n\t\t * nonsilent states. Silent states are states which cannot leave the\n\t\t * block in one step. */\n\t\tfor (int state : oldBlock) {\n\t\t\tHashMap<HashSet<Integer>, Function> signature = stateSignature(state, oldBlock);\n\t\t\tif (signature != null) {\n\t\t\t\tnonSilent.add(state);\n\t\t\t\tHashSet<Integer> newBlock = signatures.get(signature);\n\t\t\t\tif (newBlock == null) {\n\t\t\t\t\tnewBlock = new HashSet<Integer>();\n\t\t\t\t\tsignatures.put(signature, newBlock);\n\t\t\t\t}\n\t\t\t\tnewBlock.add(state);\n\t\t\t\tstateToBlock.put(state, newBlock);\n\t\t\t} else {\n\t\t\t\tsilent.add(state);\n\t\t\t}\n\t\t}\n\t\t\n\t\t/* non-silent states reach only the new block they are contained in */\n\t\tHashMap<Integer, HashSet<HashSet<Integer>>> reachWhichBlocks = new HashMap<Integer, HashSet<HashSet<Integer>>>();\n\t\tfor (int state : oldBlock) {\n\t\t\tHashSet<HashSet<Integer>> predReachBlocks = new HashSet<HashSet<Integer>>();\n\t\t\tif (!silent.contains(state)) {\n\t\t\t\tpredReachBlocks.add(stateToBlock.get(state));\n\t\t\t}\n\t\t\treachWhichBlocks.put(state, predReachBlocks);\n\t\t}\n\t\t\n\t\t/* collect all silent states which can reach a particular\n\t\t * non-silent state by performing a backwards depth-first search.\n\t\t * Mark silent states one comes across with the block of the\n\t\t * non-silent state. We can already stop the search if we know\n\t\t * that the state has previously been visited from another\n\t\t * state from the same block. */\n\t\tfor (int state : nonSilent) {\n\t\t\tHashSet<Integer> block = stateToBlock.get(state);\n\t\t\tArrayDeque<Integer> stack = new ArrayDeque<Integer>();\n\t\t\tstack.push(state);\n\t\t\twhile (!stack.isEmpty()) {\n\t\t\t\tint stackState = stack.pop();\n\t\t\t\tfor (int predState : origPmc.incoming.get(stackState)) {\n\t\t\t\t\tHashSet<HashSet<Integer>> predReachBlocks = reachWhichBlocks.get(predState);\n\t\t\t\t\tif (oldBlock.contains(predState) && silent.contains(predState) && !predReachBlocks.contains(block)) {\n\t\t\t\t\t\tpredReachBlocks.add(block);\n\t\t\t\t\t\tstack.push(predState);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t/* compute new blocks, add the nonempty ones to list of new blocks */\n\t\tHashMap<HashSet<HashSet<Integer>>, HashSet<Integer>> remap = new HashMap<HashSet<HashSet<Integer>>, HashSet<Integer>>();\n\t\tfor (Entry<Integer, HashSet<HashSet<Integer>>> entry : reachWhichBlocks.entrySet()) {\n\t\t\tHashSet<Integer> sigStates = remap.get(entry.getValue());\n\t\t\tif (sigStates == null) {\n\t\t\t\tsigStates = new HashSet<Integer>();\n\t\t\t\tremap.put(entry.getValue(), sigStates);\n\t\t\t}\n\t\t\tsigStates.add(entry.getKey());\n\t\t}\n\t\tfor (HashSet<Integer> block : remap.values()) {\n\t\t\tif (!block.isEmpty()) {\n\t\t\t\tnewBlocks.add(block);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Build the weak bisimulation quotient from the blocks computed.\n\t * Transition probabilities are basically based on the weak bisimulation\n\t * signature. However, we must take care that we use a non-silent state\n\t * to compute transition probabilties from. Also, states which can never\n\t * leave their block after an arbitrary number of steps (\"divergent\"\n\t * states) must lead to adding a self loop in their containing block.\n\t */\n\t@Override\n\tprotected void buildQuotient() {\n\t\toptPmc = new MutablePMC(origPmc.getFunctionFactory(), blocks.size(), origPmc.isUseRewards(), false);\n\t\tfor (int newState = 0; newState < blocks.size(); newState++) {\n\t\t\tHashMap<HashSet<Integer>, Function> signature = null;\n\t\t\tint oldState = -1;\n\t\t\tHashSet<Integer> fromBlock = blocks.get(newState);\n\t\t\tIterator<Integer> iter = fromBlock.iterator();\n\t\t\twhile (iter.hasNext()) {\n\t\t\t\toldState = iter.next();\n\t\t\t\tsignature = stateSignature(oldState, fromBlock);\n\t\t\t\tif (signature != null) {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (signature == null) {\n\t\t\t\toptPmc.addTransition(newState, newState, origPmc.getFunctionFactory().getOne());\t\t\t\t\n\t\t\t} else {\n\t\t\t\tfor (Entry<HashSet<Integer>, Function> entry : signature.entrySet()) {\n\t\t\t\t\toptPmc.addTransition(newState, blockToNumber.get(entry.getKey()), entry.getValue());\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (origPmc.isUseRewards()) {\n\t\t\t\toptPmc.setReward(newState, origPmc.getReward(oldState));\n\t\t\t} else {\n\t\t\t\toptPmc.setTargetState(newState, origPmc.isTargetState(oldState));\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Creates an initial partitioning.\n\t * This function is based on the of the {@code Lumper} class. However,\n\t * for the weak bisimulation lumping to work correctly, for each block\n\t * of the initial partitioning, we have to split off \"divergent\" states.\n\t * Divergent states are states which can never leave their block, after\n\t * any number of steps.\n\t */\n\t@Override\n\tprotected void createInitialPartition() {\n\t\tsuper.createInitialPartition();\n\t\tArrayList<HashSet<Integer>> newBlocks = new ArrayList<HashSet<Integer>>();\n\t\twhile (partition.mayChange()) {\n\t\t\tHashSet<Integer> oldBlock = partition.nextChangeableBlock();\n\t\t\tHashSet<Integer> leaveSet = new HashSet<Integer>();\n\t\t\tArrayList<Integer> directLeaving = new ArrayList<Integer>();\n\t\t\tfor (int state : oldBlock) {\n\t\t\t\tfor (int toState : origPmc.transitionTargets.get(state)) {\n\t\t\t\t\tif (!oldBlock.contains(toState)) {\n\t\t\t\t\t\tleaveSet.add(state);\n\t\t\t\t\t\tdirectLeaving.add(state);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (int state : directLeaving) {\n\t\t\t\tArrayDeque<Integer> stack = new ArrayDeque<Integer>();\n\t\t\t\tstack.push(state);\n\t\t\t\twhile (!stack.isEmpty()) {\n\t\t\t\t\tint leaving = stack.pop();\n\t\t\t\t\tfor (int inState : origPmc.incoming.get(leaving)) {\n\t\t\t\t\t\tif (oldBlock.contains(inState) && !leaveSet.contains(inState)) {\n\t\t\t\t\t\t\tleaveSet.add(inState);\n\t\t\t\t\t\t\tstack.push(inState);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!leaveSet.isEmpty()) {\n\t\t\t\tnewBlocks.add(leaveSet);\n\t\t\t}\n\t\t\tHashSet<Integer> staying = new HashSet<Integer>(oldBlock);\n\t\t\tstaying.removeAll(leaveSet);\n\t\t\tif (!staying.isEmpty()) {\n\t\t\t\tnewBlocks.add(staying);\n\t\t\t}\n\t\t}\n\t\tpartition.addBlocks(newBlocks);\n\t\tpartition.markAllBlocksAsNew();\n\t}\n}\n"
  },
  {
    "path": "prism/src/param/package-info.java",
    "content": "/**\n * Classes for parametric model checking.\n */\npackage param;\n"
  },
  {
    "path": "prism/src/parser/BooleanUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\nimport java.io.ByteArrayInputStream;\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionLiteral;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.type.TypeBool;\nimport parser.visitor.ASTTraverseModify;\nimport prism.PrismException;\nimport prism.PrismLangException;\n\npublic class BooleanUtils\n{\n\t/**\n\t * Extract the conjuncts from a conjunction in the form of zero or more nested\n\t * binary conjunctions represented by ExpressionBinaryOp objects.\n\t * \n\t * @param expr The conjunction to extract from \n\t * @param conjuncts The list to insert conjuncts into\n\t */\n\tpublic static void extractConjuncts(Expression expr, List<Expression> conjuncts)\n\t{\n\t\t// Traverse depth-first, and add any non-ands to the list\n\t\tif (Expression.isAnd(expr)) {\n\t\t\textractConjuncts(((ExpressionBinaryOp) expr).getOperand1(), conjuncts);\n\t\t\textractConjuncts(((ExpressionBinaryOp) expr).getOperand2(), conjuncts);\n\t\t} else {\n\t\t\tconjuncts.add(expr);\n\t\t}\n\t}\n\n\t/**\n\t * Extract the disjuncts from a disjunction in the form of zero or more nested\n\t * binary disjunctions represented by ExpressionBinaryOp objects.\n\t * \n\t * @param expr The disjunction to extract from \n\t * @param disjuncts The list to insert disjuncts into\n\t */\n\tpublic static void extractDisjuncts(Expression expr, List<Expression> disjuncts)\n\t{\n\t\t// Traverse depth-first, and add any non-ors to the list\n\t\tif (Expression.isAnd(expr)) {\n\t\t\textractDisjuncts(((ExpressionBinaryOp) expr).getOperand1(), disjuncts);\n\t\t\textractDisjuncts(((ExpressionBinaryOp) expr).getOperand2(), disjuncts);\n\t\t} else {\n\t\t\tdisjuncts.add(expr);\n\t\t}\n\t}\n\n\t/**\n\t * Convert a Boolean expression to positive normal form,\n\t * i.e., remove any instances of =>, <=> or () and then push\n\t * all negation inwards so that it only occurs on \"propositions\".\n\t * A \"proposition\" is any Expression object that\n\t * is not an operator used to define a Boolean expression (!, &, |, =>, <=>, ()).\n\t * The passed in expression is modified, and the result is returned. \n\t */\n\tpublic static Expression convertToPositiveNormalForm(Expression expr)\n\t{\n\t\t// First expand implies/iff/parentheses\n\t\t// Then do conversion to +ve normal form\n\t\treturn doConversionToPositiveNormalForm(removeImpliesIffAndParentheses(expr), false);\n\t}\n\t\n\t/**\n\t * Convert an LTL formula to positive normal form,\n\t * i.e., remove any instances of =>, <=> or () and then push\n\t * all negation inwards so that it only occurs on \"propositions\".\n\t * A \"proposition\" is any Expression object that\n\t * is not an operator used to define a Boolean expression (!, &, |, =>, <=>, ())\n\t * or a temporal operator (X, U, F, G, R, W).\n\t * The passed in expression is modified, and the result is returned. \n\t */\n\tpublic static Expression convertLTLToPositiveNormalForm(Expression expr)\n\t{\n\t\t// First expand implies/iff/parentheses\n\t\t// Then do conversion to +ve normal form\n\t\treturn doConversionToPositiveNormalForm(removeImpliesIffAndParentheses(expr), true);\n\t}\n\t\n\t/**\n\t * Remove any instances of =>, <=> or () by expanding/deleting as appropriate.\n\t */\n\tprivate static Expression removeImpliesIffAndParentheses(Expression expr)\n\t{\n\t\tExpression exprMod = null;\n\t\ttry {\n\t\t\texprMod = (Expression) expr.accept(new ASTTraverseModify()\n\t\t\t{\n\t\t\t\tpublic Object visit(ExpressionUnaryOp e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\t// Remove parentheses: (a)\n\t\t\t\t\tif (Expression.isParenth(e)) {\n\t\t\t\t\t\tExpression a = (Expression) (e.getOperand().accept(this));\n\t\t\t\t\t\t// (a)  ==  a \n\t\t\t\t\t\treturn a;\n\t\t\t\t\t}\n\t\t\t\t\treturn super.visit(e);\n\t\t\t\t}\n\n\t\t\t\tpublic Object visit(ExpressionBinaryOp e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\t// Remove implication: a => b\n\t\t\t\t\tif (Expression.isImplies(e)) {\n\t\t\t\t\t\tExpression a = (Expression) (e.getOperand1().accept(this));\n\t\t\t\t\t\tExpression b = (Expression) (e.getOperand2().accept(this));\n\t\t\t\t\t\t// a => b  ==  !a | b \n\t\t\t\t\t\treturn Expression.Or(Expression.Not(a), b);\n\t\t\t\t\t}\n\t\t\t\t\t// Remove iff: a <=> b\n\t\t\t\t\tif (Expression.isIff(e)) {\n\t\t\t\t\t\tExpression a = (Expression) (e.getOperand1().accept(this));\n\t\t\t\t\t\tExpression b = (Expression) (e.getOperand2().accept(this));\n\t\t\t\t\t\t// a <=> b  ==  (a | !b) & (!a | b) \n\t\t\t\t\t\treturn Expression.And(Expression.Or(a, Expression.Not(b)), Expression.Or(Expression.Not(a.deepCopy()), b.deepCopy()));\n\t\t\t\t\t}\n\t\t\t\t\treturn super.visit(e);\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (PrismLangException e) {\n\t\t\t// Shouldn't happen since we do not throw PrismLangException above\n\t\t}\n\t\treturn exprMod;\n\t}\n\t\n\t/**\n\t * Do the main part of the conversion of a Boolean expression to positive normal form,\n\t * i.e., push all negation inwards to the propositions. If {@code ltl} is false, it is assumed\n\t * that the Boolean expression comprises only the Boolean operators !, & and |.\n\t * If {@code ltl} is true, the expression can also contain temporal operators (X, U, F, G, R, W). \n\t * Anything else is treated as a proposition.\n\t * The passed in expression is modified, and the result is returned. \n\t */\n\tprivate static Expression doConversionToPositiveNormalForm(Expression expr, boolean ltl)\n\t{\n\t\t// Remove negation\n\t\tif (Expression.isNot(expr)) {\n\t\t\tExpression neg = ((ExpressionUnaryOp) expr).getOperand();\n\t\t\t// Boolean operators\n\t\t\tif (Expression.isTrue(neg)) {\n\t\t\t\t// ! true  ==  false\n\t\t\t\treturn new ExpressionLiteral(TypeBool.getInstance(), false);\n\t\t\t} else if (Expression.isFalse(neg)) {\n\t\t\t\t// ! false  ==  true\n\t\t\t\treturn new ExpressionLiteral(TypeBool.getInstance(), true);\n\t\t\t} else if (Expression.isNot(neg)) {\n\t\t\t\tExpression a = ((ExpressionUnaryOp) neg).getOperand();\n\t\t\t\t// !(!a)  ==  a \n\t\t\t\treturn doConversionToPositiveNormalForm(a, ltl);\n\t\t\t} else if (Expression.isOr(neg)) {\n\t\t\t\tExpression a = ((ExpressionBinaryOp) neg).getOperand1();\n\t\t\t\tExpression b = ((ExpressionBinaryOp) neg).getOperand2();\n\t\t\t\tExpression aNeg = doConversionToPositiveNormalForm(Expression.Not(a), ltl);\n\t\t\t\tExpression bNeg = doConversionToPositiveNormalForm(Expression.Not(b), ltl);\n\t\t\t\t// !(a | b)  ==  !a & !b \n\t\t\t\treturn Expression.And(aNeg, bNeg);\n\t\t\t} else if (Expression.isAnd(neg)) {\n\t\t\t\tExpression a = ((ExpressionBinaryOp) neg).getOperand1();\n\t\t\t\tExpression b = ((ExpressionBinaryOp) neg).getOperand2();\n\t\t\t\tExpression aNeg = doConversionToPositiveNormalForm(Expression.Not(a), ltl);\n\t\t\t\tExpression bNeg = doConversionToPositiveNormalForm(Expression.Not(b), ltl);\n\t\t\t\t// !(a & b)  ==  !a | !b \n\t\t\t\treturn Expression.Or(aNeg, bNeg);\n\t\t\t}\n\t\t\t// Temporal operators (if required)\n\t\t\telse if (ltl) {\n\t\t\t\tif (neg instanceof ExpressionTemporal) {\n\t\t\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) neg;\n\t\t\t\t\tExpression a = exprTemp.getOperand1();\n\t\t\t\t\tExpression b = exprTemp.getOperand2();\n\t\t\t\t\tExpression aNeg = null, bNeg = null, aCopy = null, bNegCopy = null;\n\t\t\t\t\tExpressionTemporal result = null;\n\t\t\t\t\tswitch (exprTemp.getOperator()) {\n\t\t\t\t\tcase ExpressionTemporal.P_X:\n\t\t\t\t\t\tbNeg = doConversionToPositiveNormalForm(Expression.Not(b), ltl);\n\t\t\t\t\t\t// !(X b)  ==  X !b\n\t\t\t\t\t\treturn new ExpressionTemporal(ExpressionTemporal.P_X, null, bNeg);\n\t\t\t\t\tcase ExpressionTemporal.P_U:\n\t\t\t\t\t\taNeg = doConversionToPositiveNormalForm(Expression.Not(a), ltl);\n\t\t\t\t\t\tbNeg = doConversionToPositiveNormalForm(Expression.Not(b), ltl);\n\t\t\t\t\t\t// !(a U b)  ==  !a R !b\n\t\t\t\t\t\tresult = new ExpressionTemporal(ExpressionTemporal.P_R, aNeg, bNeg);\n\t\t\t\t\t\tresult.setBoundsFrom(exprTemp);\n\t\t\t\t\t\treturn result;\n\t\t\t\t\tcase ExpressionTemporal.P_F:\n\t\t\t\t\t\t bNeg = doConversionToPositiveNormalForm(Expression.Not(b), ltl);\n\t\t\t\t\t\t// !(F b)  ==  G !b\n\t\t\t\t\t\tresult = new ExpressionTemporal(ExpressionTemporal.P_G, null, bNeg);\n\t\t\t\t\t\tresult.setBoundsFrom(exprTemp);\n\t\t\t\t\t\treturn result;\n\t\t\t\t\tcase ExpressionTemporal.P_G:\n\t\t\t\t\t\t bNeg = doConversionToPositiveNormalForm(Expression.Not(b), ltl);\n\t\t\t\t\t\t// !(G b)  ==  F !b\n\t\t\t\t\t\tresult = new ExpressionTemporal(ExpressionTemporal.P_F, null, bNeg);\n\t\t\t\t\t\tresult.setBoundsFrom(exprTemp);\n\t\t\t\t\t\treturn result;\n\t\t\t\t\tcase ExpressionTemporal.P_W:\n\t\t\t\t\t\taCopy = doConversionToPositiveNormalForm(a.deepCopy(), ltl);\n\t\t\t\t\t\tbNeg = doConversionToPositiveNormalForm(Expression.Not(b), ltl);\n\t\t\t\t\t\taNeg = doConversionToPositiveNormalForm(Expression.Not(a), ltl);\n\t\t\t\t\t\tbNegCopy = doConversionToPositiveNormalForm(Expression.Not(b.deepCopy()), ltl);\n\t\t\t\t\t\t// !(a W b) == a&!b U !a&!b\n\t\t\t\t\t\tresult = new ExpressionTemporal(ExpressionTemporal.P_R, Expression.And(aCopy, bNeg), Expression.And(aNeg, bNegCopy));\n\t\t\t\t\t\tresult.setBoundsFrom(exprTemp);\n\t\t\t\t\t\treturn result;\n\t\t\t\t\tcase ExpressionTemporal.P_R:\n\t\t\t\t\t\taNeg = doConversionToPositiveNormalForm(Expression.Not(a), ltl);\n\t\t\t\t\t\tbNeg = doConversionToPositiveNormalForm(Expression.Not(b), ltl);\n\t\t\t\t\t\t// !(a R b)  ==  !a U !b\n\t\t\t\t\t\tresult = new ExpressionTemporal(ExpressionTemporal.P_U, aNeg, bNeg);\n\t\t\t\t\t\tresult.setBoundsFrom(exprTemp);\n\t\t\t\t\t\treturn result;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\t// Don't change (shouldn't happen)\n\t\t\t\t\t\treturn expr;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\t// Proposition (negated)\n\t\t\t\treturn expr;\n\t\t\t}\n\t\t}\n\t\t// Preserve and\n\t\tif (Expression.isAnd(expr)) {\n\t\t\tExpression a = doConversionToPositiveNormalForm(((ExpressionBinaryOp) expr).getOperand1(), ltl);\n\t\t\tExpression b = doConversionToPositiveNormalForm(((ExpressionBinaryOp) expr).getOperand2(), ltl);\n\t\t\treturn Expression.And(a, b);\n\t\t}\n\t\t// Preserve or\n\t\tif (Expression.isOr(expr)) {\n\t\t\tExpression a = doConversionToPositiveNormalForm(((ExpressionBinaryOp) expr).getOperand1(), ltl);\n\t\t\tExpression b = doConversionToPositiveNormalForm(((ExpressionBinaryOp) expr).getOperand2(), ltl);\n\t\t\treturn Expression.Or(a, b);\n\t\t}\n\t\t// Preserve temporal operators\n\t\tif (ltl && expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal)expr;\n\t\t\tExpression a = exprTemp.getOperand1();\n\t\t\tExpression b = exprTemp.getOperand2();\n\t\t\tExpression aConv = (a == null) ? null : doConversionToPositiveNormalForm(a, ltl);\n\t\t\tExpression bConv = (b == null) ? null : doConversionToPositiveNormalForm(b, ltl);\n\t\t\tExpressionTemporal result = new ExpressionTemporal(exprTemp.getOperator(), aConv, bConv);\n\t\t\tresult.setBoundsFrom(exprTemp);\n\t\t\treturn result;\n\t\t}\n\t\t// Proposition\n\t\treturn expr;\n\t}\n\n\t/**\n\t * Convert an expression to disjunctive normal form (DNF).\n\t * The passed in expression is modified, and the result is returned. \n\t */\n\tpublic static Expression convertToDNF(Expression expr)\n\t{\n\t\treturn convertDNFListsToExpression(doConversionToDNF(convertToPositiveNormalForm(expr)));\n\t}\n\n\t/**\n\t * Convert an expression to disjunctive normal form (DNF).\n\t * The passed in expression is modified, and the result is returned as a list of lists of Expression;\n\t */\n\tpublic static List<List<Expression>> convertToDNFLists(Expression expr)\n\t{\n\t\treturn doConversionToDNF(convertToPositiveNormalForm(expr));\n\t}\n\n\tprivate static List<List<Expression>> doConversionToDNF(Expression expr)\n\t{\n\t\t// And\n\t\tif (Expression.isAnd(expr)) {\n\t\t\tExpression a = ((ExpressionBinaryOp) expr).getOperand1();\n\t\t\tExpression b = ((ExpressionBinaryOp) expr).getOperand2();\n\t\t\tList<List<Expression>> aDnf = doConversionToDNF(a);\n\t\t\tList<List<Expression>> bDnf = doConversionToDNF(b);\n\t\t\t// a1|a2|... & b1|b2|...  ==  a1&b1 | a1&b2 | ...\n\t\t\tList<List<Expression>> dnf = new ArrayList<List<Expression>>();\n\t\t\tfor (List<Expression> ai : aDnf) {\n\t\t\t\tfor (List<Expression> bj : bDnf) {\n\t\t\t\t\tList<Expression> aibj = new ArrayList<Expression>();\n\t\t\t\t\taibj.addAll(ai);\n\t\t\t\t\taibj.addAll(bj);\n\t\t\t\t\tdnf.add(aibj);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn dnf;\n\t\t}\n\t\t// Or\n\t\tif (Expression.isOr(expr)) {\n\t\t\tExpression a = ((ExpressionBinaryOp) expr).getOperand1();\n\t\t\tExpression b = ((ExpressionBinaryOp) expr).getOperand2();\n\t\t\tList<List<Expression>> aDnf = doConversionToDNF(a);\n\t\t\tList<List<Expression>> bDnf = doConversionToDNF(b);\n\t\t\t// (a1|a2|...) | (b1|b2|...)  ==  a1|a2|...|b1|b2|...\n\t\t\taDnf.addAll(bDnf);\n\t\t\treturn aDnf;\n\t\t}\n\t\t// Convert proposition to trivial DNF\n\t\tList<List<Expression>> dnf = new ArrayList<List<Expression>>(1);\n\t\tList<Expression> disjunct = new ArrayList<Expression>(1);\n\t\tdisjunct.add(expr);\n\t\tdnf.add(disjunct);\n\t\treturn dnf;\n\t}\n\n\t/**\n\t * Convert an expression to conjunctive normal form (CNF).\n\t * The passed in expression is modified, and the result is returned. \n\t */\n\tpublic static Expression convertToCNF(Expression expr)\n\t{\n\t\treturn convertCNFListsToExpression(doConversionToCNF(convertToPositiveNormalForm(expr)));\n\t}\n\n\t/**\n\t * Convert an expression to conjunctive normal form (CNF).\n\t * The passed in expression is modified, and the result is returned as a list of lists of Expression;\n\t */\n\tpublic static List<List<Expression>> convertToCNFLists(Expression expr)\n\t{\n\t\treturn doConversionToCNF(convertToPositiveNormalForm(expr));\n\t}\n\n\tprivate static List<List<Expression>> doConversionToCNF(Expression expr)\n\t{\n\t\t// Remove parentheses\n\t\tif (Expression.isParenth(expr)) {\n\t\t\treturn doConversionToCNF(((ExpressionUnaryOp) expr).getOperand());\n\t\t}\n\t\t// Or\n\t\tif (Expression.isOr(expr)) {\n\t\t\tExpression a = ((ExpressionBinaryOp) expr).getOperand1();\n\t\t\tExpression b = ((ExpressionBinaryOp) expr).getOperand2();\n\t\t\tList<List<Expression>> aCnf = doConversionToCNF(a);\n\t\t\tList<List<Expression>> bCnf = doConversionToCNF(b);\n\t\t\t// a1&a2&... | b1&b2&...  ==  a1|b1 & a1|b2 & ...\n\t\t\tList<List<Expression>> cnf = new ArrayList<List<Expression>>();\n\t\t\tfor (List<Expression> ai : aCnf) {\n\t\t\t\tfor (List<Expression> bj : bCnf) {\n\t\t\t\t\tList<Expression> aibj = new ArrayList<Expression>();\n\t\t\t\t\taibj.addAll(ai);\n\t\t\t\t\taibj.addAll(bj);\n\t\t\t\t\tcnf.add(aibj);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn cnf;\n\t\t}\n\t\t// And\n\t\tif (Expression.isAnd(expr)) {\n\t\t\tExpression a = ((ExpressionBinaryOp) expr).getOperand1();\n\t\t\tExpression b = ((ExpressionBinaryOp) expr).getOperand2();\n\t\t\tList<List<Expression>> aCnf = doConversionToCNF(a);\n\t\t\tList<List<Expression>> bCnf = doConversionToCNF(b);\n\t\t\t// (a1|a2|...) | (b1|b2|...)  ==  a1|a2|...|b1|b2|...\n\t\t\taCnf.addAll(bCnf);\n\t\t\treturn aCnf;\n\t\t}\n\t\t// Convert proposition to trivial CNF\n\t\tList<List<Expression>> cnf = new ArrayList<List<Expression>>(1);\n\t\tList<Expression> conjunct = new ArrayList<Expression>(1);\n\t\tconjunct.add(expr);\n\t\tcnf.add(conjunct);\n\t\treturn cnf;\n\t}\n\n\t// Methods to convert And/Or classes to Expressions\n\t\n\tpublic static Expression convertDNFListsToExpression(List<List<Expression>> dnf)\n\t{\n\t\tExpression ret = convertConjunctionListToExpression(dnf.get(0));\n\t\tfor (int i = 1; i < dnf.size(); i++) {\n\t\t\tret = Expression.Or(ret, convertConjunctionListToExpression(dnf.get(i)));\n\t\t}\n\t\treturn ret;\n\t}\n\n\tpublic static Expression convertCNFListsToExpression(List<List<Expression>> cnf)\n\t{\n\t\tExpression ret = convertDisjunctionListToExpression(cnf.get(0));\n\t\tfor (int i = 1; i < cnf.size(); i++) {\n\t\t\tret = Expression.And(ret, convertDisjunctionListToExpression(cnf.get(i)));\n\t\t}\n\t\treturn ret;\n\t}\n\n\tpublic static Expression convertDisjunctionListToExpression(List<Expression> disjunction)\n\t{\n\t\tExpression ret = disjunction.get(0);\n\t\tfor (int i = 1; i < disjunction.size(); i++) {\n\t\t\tret = Expression.Or(ret, disjunction.get(i));\n\t\t}\n\t\treturn ret;\n\t}\n\n\tpublic static Expression convertConjunctionListToExpression(List<Expression> conjunction)\n\t{\n\t\tExpression ret = conjunction.get(0);\n\t\tfor (int i = 1; i < conjunction.size(); i++) {\n\t\t\tret = Expression.And(ret, conjunction.get(i));\n\t\t}\n\t\treturn ret;\n\t}\n\n\t// Test code\n\t\n\tpublic static void main(String args[])\n\t{\n\t\tPrismParser parser = new PrismParser();\n\t\tString ss[] = new String[] { \"a&!(b=>c)\", \"(a|b)&(c|d|e)\" };\n\t\tfor (String s : ss) {\n\t\t\ttry {\n\t\t\t\tExpression expr = parser.parseSingleExpression(new ByteArrayInputStream(s.getBytes()));\n\t\t\t\tSystem.out.println(expr + \" in CNF is \" + convertToCNF(expr.deepCopy()));\n\t\t\t\tSystem.out.println(expr + \" in DNF is \" + convertToDNF(expr.deepCopy()));\n\t\t\t} catch (PrismException e) {\n\t\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/EvaluateContext.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\n/**\n * Classes providing the information required to evaluate an expression.\n * Primarily, this means providing values for variables.\n * Optionally, values for constants can also be supplied.\n */\npublic abstract class EvaluateContext\n{\n\t// Core information stored in an EvaluateContext\n\t\n\t/**\n\t * Evaluation mode (floating point? exact?)\n\t */\n\tpublic enum EvalMode { FP, EXACT }\n\tprotected EvalMode evalMode = EvalMode.FP;\n\t\n\t/**\n\t * Constant values (optional)\n\t */\n\tprotected Values constantValues = null;\n\t\n\t// Setters and getters for core information\n\t\n\t/**\n\t * Set the evaluation mode (floating point? exact?)\n\t * Returns a copy of this EvaluateContext to allow chaining of method calls.\n\t */\n\tpublic EvaluateContext setEvaluationMode(EvalMode evalMode)\n\t{\n\t\tthis.evalMode = evalMode;\n\t\treturn this;\n\t}\n\n\t/**\n\t * Get the evaluation mode (floating point? exact?)\n\t */\n\tpublic EvalMode getEvaluationMode()\n\t{\n\t\treturn evalMode;\n\t}\n\n\t/**\n\t * Set the constant values. The Values object is stored, not copied.\n\t * Returns a copy of this EvaluateContext to allow chaining of method calls.\n\t */\n\tpublic EvaluateContext setConstantValues(Values constantValues)\n\t{\n\t\tthis.constantValues = constantValues;\n\t\treturn this;\n\t}\n\t\n\t/**\n\t * Add some constant values. The Values object is copied, not stored.\n\t * There is no checking for duplicates.\n\t * Returns a copy of this EvaluateContext to allow chaining of method calls.\n\t */\n\tpublic EvaluateContext addConstantValues(Values moreConstantValues)\n\t{\n\t\tthis.constantValues = new Values(this.constantValues, moreConstantValues);\n\t\treturn this;\n\t}\n\t\n\t/**\n\t * Get the constant values.\n\t */\n\tpublic Values getConstantValues()\n\t{\n\t\treturn constantValues;\n\t}\n\t\n\t/**\n\t * Copy core information (constants, evaluation mode, etc.) from another EvaluateContext.\n\t * Return a copy of this EvaluateContext (to allow method chaining).\n\t */\n\tpublic EvaluateContext copyFrom(EvaluateContext ec)\n\t{\n\t\tthis.evalMode = ec.evalMode;\n\t\tthis.constantValues = ec.constantValues == null ? null : new Values(ec.constantValues);\n\t\treturn this;\n\t}\n\t\n\t// Main interface for EvaluateContext classes\n\t\n\t/**\n\t * Return the value for a constant (by name); null if unknown.\n\t */\n\tpublic Object getConstantValue(String name)\n\t{\n\t\tif (constantValues == null) {\n\t\t\treturn null;\n\t\t}\n\t\tint i = constantValues.getIndexOf(name);\n\t\tif (i == -1) {\n\t\t\treturn null;\n\t\t}\n\t\treturn constantValues.getValue(i);\n\t}\n\n\t/**\n\t * Return the value for a variable (by name or index); null if unknown.\n\t */\n\tpublic abstract Object getVarValue(String name, int index);\n\n\t/**\n\t * Return the value for an observable (by name or index); null if unknown.\n\t */\n\tpublic Object getObservableValue(String name, int index)\n\t{\n\t\t// No observables defined by default\n\t\treturn null;\n\t}\n\t\n\t// Utility methods\n\t\n\t/**\n\t * Create an EvaluateContext with no constants and default (floating point) evaluation mode.\n\t */\n\tpublic static EvaluateContext create()\n\t{\n\t\treturn new EvaluateContextConstants(null);\n\t}\n\t\n\t/**\n\t * Create an EvaluateContext with no constants and the specified evaluation mode.\n\t */\n\tpublic static EvaluateContext create(EvalMode evalMode)\n\t{\n\t\treturn new EvaluateContextConstants(null).setEvaluationMode(evalMode);\n\t}\n\t\n\t/**\n\t * Create an EvaluateContext with the specified constants and default (floating point) evaluation mode.\n\t */\n\tpublic static EvaluateContext create(Values constantValues)\n\t{\n\t\treturn new EvaluateContextConstants(constantValues);\n\t}\n\t\n\t/**\n\t * Create an EvaluateContext with the specified constants and evaluation mode.\n\t */\n\tpublic static EvaluateContext create(Values constantValues, EvalMode evalMode)\n\t{\n\t\treturn new EvaluateContextConstants(constantValues).setEvaluationMode(evalMode);\n\t}\n\t\n\t/**\n\t * Create an EvaluateContext with the specified constants and evaluation mode (exact or not).\n\t */\n\tpublic static EvaluateContext create(Values constantValues, boolean exact)\n\t{\n\t\treturn new EvaluateContextConstants(constantValues).setEvaluationMode(exact ? EvalMode.EXACT : EvalMode.FP);\n\t}\n\t\n\t/**\n\t * Create an EvaluateContext by copying core information\n\t * (constants, evaluation mode, etc.) from another EvaluateContext.\n\t */\n\tpublic static EvaluateContext create(EvaluateContext ec)\n\t{\n\t\treturn create().copyFrom(ec);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/EvaluateContextConstants.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2018-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\n/**\n * Information required to evaluate an expression, where no variable value info is available.\n * Constant values (if needed/present) are stored in a Values object.\n */\npublic class EvaluateContextConstants extends EvaluateContext\n{\n\tpublic EvaluateContextConstants(Values constantValues)\n\t{\n\t\tsetConstantValues(constantValues);\n\t}\n\n\t@Override\n\tpublic Object getVarValue(String name, int index)\n\t{\n\t\t// No variable info available\n\t\treturn null;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/EvaluateContextFull.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ox.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\n/**\n * Information required to evaluate an expression,\n * supporting all aspects defined in {@link EvaluateContext}.\n */\npublic class EvaluateContextFull extends EvaluateContextState\n{\n\t/**\n\t * Observable values\n\t */\n\tprivate Object[] obsValues;\n\n\t/**\n\t * Constructor\n\t */\n\tpublic EvaluateContextFull(State state, State obs)\n\t{\n\t\tsuper(state);\n\t\tif (obs != null) {\n\t\t\tsetObservation(obs);\n\t\t}\n\t}\n\n\t/**\n\t * Set the observable values. The array of observable values is extracted and stored, not copied.\n\t * Returns a copy of this EvaluateContext to allow chaining of method calls.\n\t */\n\tpublic EvaluateContext setObservation(State obs)\n\t{\n\t\tthis.obsValues = obs.varValues;\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic Object getObservableValue(String name, int index)\n\t{\n\t\t// There is no observable name info available,\n\t\t// so use index if provided; otherwise unknown\n\t\treturn (index == -1 || obsValues == null) ? null : obsValues[index];\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/EvaluateContextState.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\n/**\n * Information required to evaluate an expression,\n * where the values for variables are stored in a State object.\n * A State is basically just an array of Objects, with no variable name info,\n * so variable indices (i.e., offsets into the State array) need to be provided.\n * Optionally, values for constants can also be stored and used.\n */\npublic class EvaluateContextState extends EvaluateContext\n{\n\t/**\n\t * Variable values for state\n\t */\n\tprivate Object[] varValues;\n\n\tpublic EvaluateContextState(State state)\n\t{\n\t\tsetState(state);\n\t}\n\n\tpublic EvaluateContextState(Values constantValues, State state)\n\t{\n\t\tsetConstantValues(constantValues);\n\t\tsetState(state);\n\t}\n\n\t/**\n\t * Set the state variable values. The array of state values is extracted and stored, not copied.\n\t * Returns a copy of this EvaluateContext to allow chaining of method calls.\n\t */\n\tpublic EvaluateContext setState(State state)\n\t{\n\t\tthis.varValues = state.varValues;\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic Object getVarValue(String name, int index)\n\t{\n\t\t// There is no variable name info available,\n\t\t// so use index if provided; otherwise unknown\n\t\treturn index == -1 ? null : varValues[index];\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/EvaluateContextSubstate.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\n/**\n * Information required to evaluate an expression: a subset of a State object.\n * More precisely: a State object, indexed over a subset of all variables,\n * and a mapping from indices (over all variables) to this subset (-1 if not in subset). \n * Optionally values for constants can also be supplied.\n */\npublic class EvaluateContextSubstate extends EvaluateContext\n{\n\tprivate Object[] varValues;\n\tprivate int[] varMap;\n\n\tpublic EvaluateContextSubstate(State substate, int[] varMap)\n\t{\n\t\tthis.varValues = substate.varValues;\n\t\tthis.varMap = varMap;\n\t}\n\n\tpublic EvaluateContextSubstate(Values constantValues, State substate, int[] varMap)\n\t{\n\t\tsetConstantValues(constantValues);\n\t\tthis.varValues = substate.varValues;\n\t\tthis.varMap = varMap;\n\t}\n\n\t@Override\n\tpublic Object getVarValue(String name, int index)\n\t{\n\t\t// There is no variable name info available,\n\t\t// so use index if provided; otherwise unknown\n\t\tint newIndex;\n\t\tif (index == -1 || (newIndex = varMap[index]) == -1)\n\t\t\treturn null;\n\t\treturn varValues[newIndex];\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/EvaluateContextValues.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\n/**\n * Information required to evaluate an expression,\n * where the values for variables are stored in a Values object.\n * Optionally, values for constants can also be stored and used.\n */\npublic class EvaluateContextValues extends EvaluateContext\n{\n\tprivate Values varValues;\n\n\tpublic EvaluateContextValues(Values constantValues, Values varValues)\n\t{\n\t\tsetConstantValues(constantValues);\n\t\tthis.varValues = varValues;\n\t}\n\n\t@Override\n\tpublic Object getVarValue(String name, int index)\n\t{\n\t\tif (varValues == null)\n\t\t\treturn null;\n\t\tint i = varValues.getIndexOf(name);\n\t\tif (i == -1)\n\t\t\treturn null;\n\t\treturn varValues.getValue(i);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/IdentUsage.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\nimport java.util.HashMap;\n\nimport parser.ast.ASTElement;\nimport prism.PrismLangException;\n\n/**\n * Helper class to keep track of a set of identifiers that have been used.\n */\npublic class IdentUsage implements Cloneable\n{\n\t// Are these identifiers used in (double) quotes?\n\tprivate boolean quoted = false;\n\t\n\t// Where identifiers were declared (AST element)\n\tprivate HashMap<String, ASTElement> identDecls;\n\t// Uses of identifiers (e.g. \"constant\")\n\tprivate HashMap<String, String> identUses;\n\t// Location of identifiers (e.g. \"the model\")\n\tprivate HashMap<String, String> identLocs;\n\n\tpublic IdentUsage()\n\t{\n\t\tthis(false);\n\t}\n\t\n\t/**\n\t * @param quoted Are these identifiers used in (double) quotes?\n\t */\n\tpublic IdentUsage(boolean quoted)\n\t{\n\t\tthis.quoted = quoted;\n\t\tidentDecls = new HashMap<>();\n\t\tidentUses = new HashMap<>();\n\t\tidentLocs = new HashMap<>();\n\t}\n\t\n\tpublic void clear()\n\t{\n\t\tidentDecls.clear();\n\t\tidentUses.clear();\n\t\tidentLocs.clear();\n\t}\n\t\n\t/**\n\t * Check if an identifier is already used somewhere\n\t * and throw an exception if it is. Otherwise, add it to the list.\n\t * @param ident The name of the (new) identifier\n\t * @param decl Where the identifier is declared in the model\n\t * @param use Optionally, the identifier's usage (e.g. \"constant\")\n\t * @param loc Optionally, the identifier's location (e.g. \"the model\")\n\t */\n\tpublic void checkAndAddIdentifier(String ident, ASTElement decl, String use, String loc) throws PrismLangException\n\t{\n\t\tcheckIdent(ident, decl, use);\n\t\tidentDecls.put(ident, decl);\n\t\tidentUses.put(ident, use);\n\t\tidentLocs.put(ident, loc);\n\t}\n\t\n\t/**\n\t * Check if an identifier is already used somewhere\n\t * @param ident The name of the identifier to check\n\t */\n\tpublic boolean isIdentUsed(String ident)\n\t{\n\t\treturn identDecls.containsKey(ident);\n\t}\n\n\t/**\n\t * Check if an identifier is already used somewhere\n\t * and throw an exception if it is.\n\t * @param ident The name of the identifier to check\n\t * @param decl Where the identifier is declared in the model (for the error message)\n\t * @param use Optionally, the identifier's usage (e.g. \"constant\")\n\t */\n\tpublic void checkIdent(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\tASTElement existing = identDecls.get(ident);\n\t\tif (existing != null) {\n\t\t\t// Construct error message if identifier exists already\n\t\t\tString identStr = use != null ? (\"Name of \" + use) : \"Identifier\";\n\t\t\tString qu = quoted ? \"\\\"\" : \"\";\n\t\t\tidentStr += \" \" + qu + ident + qu;\n\t\t\tString existingUse = identUses.get(ident);\n\t\t\tif (existingUse == null) {\n\t\t\t\texistingUse = \"\";\n\t\t\t} else {\n\t\t\t\tif (existingUse.length() > 0 && \"aeiou\".contains(\"\" + existingUse.charAt(0))) {\n\t\t\t\t\texistingUse = \" for an \" + existingUse;\n\t\t\t\t} else {\n\t\t\t\t\texistingUse = \" for a \" + existingUse;\n\t\t\t\t}\n\t\t\t}\n\t\t\tString existingLoc = identLocs.get(ident);\n\t\t\texistingLoc = (existingLoc == null) ? \"\" : \" in \" + existingLoc;\n\t\t\tthrow new PrismLangException(identStr + \" is already used\" + existingUse + existingLoc, decl);\n\t\t}\n\t}\n\n\tpublic IdentUsage deepCopy()\n\t{\n\t\treturn clone();\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic IdentUsage clone()\n\t{\n\t\ttry {\n\t\t\tIdentUsage clone = (IdentUsage) super.clone();\n\t\t\tclone.identDecls = (HashMap<String, ASTElement>) identDecls.clone();\n\t\t\tclone.identUses = (HashMap<String, String>) identUses.clone();\n\t\t\tclone.identLocs = (HashMap<String, String>) identLocs.clone();\n\t\t\treturn clone;\n\t\t} catch (CloneNotSupportedException e) {\n\t\t\tthrow new InternalError(\"Object#clone is expected to work for Cloneable objects.\", e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ParseException.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. ParseException.java Version 7.0 */\n/* JavaCCOptions:KEEP_LINE_COLUMN=true */\npackage parser;\n\n/**\n * This exception is thrown when parse errors are encountered.\n * You can explicitly create objects of this exception type by\n * calling the method generateParseException in the generated\n * parser.\n *\n * You can modify this class to customize your error reporting\n * mechanisms so long as you retain the public fields.\n */\npublic class ParseException extends Exception {\n\n  /**\n   * The version identifier for this Serializable class.\n   * Increment only if the <i>serialized</i> form of the\n   * class changes.\n   */\n  private static final long serialVersionUID = 1L;\n\n  /**\n   * The end of line string for this machine.\n   */\n  protected static String EOL = System.getProperty(\"line.separator\", \"\\n\");\n\n  /**\n   * This constructor is used by the method \"generateParseException\"\n   * in the generated parser.  Calling this constructor generates\n   * a new object of this type with the fields \"currentToken\",\n   * \"expectedTokenSequences\", and \"tokenImage\" set.\n   */\n  public ParseException(Token currentTokenVal,\n                        int[][] expectedTokenSequencesVal,\n                        String[] tokenImageVal\n                       )\n  {\n    super(initialise(currentTokenVal, expectedTokenSequencesVal, tokenImageVal));\n    currentToken = currentTokenVal;\n    expectedTokenSequences = expectedTokenSequencesVal;\n    tokenImage = tokenImageVal;\n  }\n\n  /**\n   * The following constructors are for use by you for whatever\n   * purpose you can think of.  Constructing the exception in this\n   * manner makes the exception behave in the normal way - i.e., as\n   * documented in the class \"Throwable\".  The fields \"errorToken\",\n   * \"expectedTokenSequences\", and \"tokenImage\" do not contain\n   * relevant information.  The JavaCC generated code does not use\n   * these constructors.\n   */\n\n  public ParseException() {\n    super();\n  }\n\n  /** Constructor with message. */\n  public ParseException(String message) {\n    super(message);\n  }\n\n\n  /**\n   * This is the last token that has been consumed successfully.  If\n   * this object has been created due to a parse error, the token\n   * following this token will (therefore) be the first error token.\n   */\n  public Token currentToken;\n\n  /**\n   * Each entry in this array is an array of integers.  Each array\n   * of integers represents a sequence of tokens (by their ordinal\n   * values) that is expected at this point of the parse.\n   */\n  public int[][] expectedTokenSequences;\n\n  /**\n   * This is a reference to the \"tokenImage\" array of the generated\n   * parser within which the parse error occurred.  This array is\n   * defined in the generated ...Constants interface.\n   */\n  public String[] tokenImage;\n\n  /**\n   * It uses \"currentToken\" and \"expectedTokenSequences\" to generate a parse\n   * error message and returns it.  If this object has been created\n   * due to a parse error, and you do not catch it (it gets thrown\n   * from the parser) the correct error message\n   * gets displayed.\n   */\n  private static String initialise(Token currentToken,\n                           int[][] expectedTokenSequences,\n                           String[] tokenImage) {\n\n    StringBuilder expected = new StringBuilder();\n    int maxSize = 0;\n    for (int i = 0; i < expectedTokenSequences.length; i++) {\n      if (maxSize < expectedTokenSequences[i].length) {\n        maxSize = expectedTokenSequences[i].length;\n      }\n      for (int j = 0; j < expectedTokenSequences[i].length; j++) {\n        expected.append(tokenImage[expectedTokenSequences[i][j]]).append(' ');\n      }\n      if (expectedTokenSequences[i][expectedTokenSequences[i].length - 1] != 0) {\n        expected.append(\"...\");\n      }\n      expected.append(EOL).append(\"    \");\n    }\n    String retval = \"Encountered \\\"\";\n    Token tok = currentToken.next;\n    for (int i = 0; i < maxSize; i++) {\n      if (i != 0) retval += \" \";\n      if (tok.kind == 0) {\n        retval += tokenImage[0];\n        break;\n      }\n      retval += \" \" + tokenImage[tok.kind];\n      retval += \" \\\"\";\n      retval += add_escapes(tok.image);\n      retval += \" \\\"\";\n      tok = tok.next;\n    }\n    if (currentToken.next != null) {\n      retval += \"\\\" at line \" + currentToken.next.beginLine + \", column \" + currentToken.next.beginColumn;\n    }\n    retval += \".\" + EOL;\n    \n    \n    if (expectedTokenSequences.length == 0) {\n        // Nothing to add here\n    } else {\n\t    if (expectedTokenSequences.length == 1) {\n\t      retval += \"Was expecting:\" + EOL + \"    \";\n\t    } else {\n\t      retval += \"Was expecting one of:\" + EOL + \"    \";\n\t    }\n\t    retval += expected.toString();\n    }\n    \n    return retval;\n  }\n\n\n  /**\n   * Used to convert raw characters to their escaped version\n   * when these raw version cannot be used as part of an ASCII\n   * string literal.\n   */\n  static String add_escapes(String str) {\n      StringBuilder retval = new StringBuilder();\n      char ch;\n      for (int i = 0; i < str.length(); i++) {\n        switch (str.charAt(i))\n        {\n           case '\\b':\n              retval.append(\"\\\\b\");\n              continue;\n           case '\\t':\n              retval.append(\"\\\\t\");\n              continue;\n           case '\\n':\n              retval.append(\"\\\\n\");\n              continue;\n           case '\\f':\n              retval.append(\"\\\\f\");\n              continue;\n           case '\\r':\n              retval.append(\"\\\\r\");\n              continue;\n           case '\\\"':\n              retval.append(\"\\\\\\\"\");\n              continue;\n           case '\\'':\n              retval.append(\"\\\\\\'\");\n              continue;\n           case '\\\\':\n              retval.append(\"\\\\\\\\\");\n              continue;\n           default:\n              if ((ch = str.charAt(i)) < 0x20 || ch > 0x7e) {\n                 String s = \"0000\" + Integer.toString(ch, 16);\n                 retval.append(\"\\\\u\" + s.substring(s.length() - 4, s.length()));\n              } else {\n                 retval.append(ch);\n              }\n              continue;\n        }\n      }\n      return retval.toString();\n   }\n\n}\n/* JavaCC - OriginalChecksum=8dbcceed9d408427f9932dcf43e59aaa (do not edit this line) */\n"
  },
  {
    "path": "prism/src/parser/ParserUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\nimport java.util.*;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\npublic class ParserUtils\n{\n\t/**\n\t * Split a conjunction into a list of its component expressions, removing any parentheses.\n\t * Note: this is purely syntactic, e.g. both \"true\" and \"false\" just result in a singleton list.  \n\t * @param expr Expression to split.\n\t */\n\tpublic static List<Expression> splitConjunction(Expression expr)\n\t{\n\t\tArrayList<Expression> list = new ArrayList<Expression>();\n\t\tsplitOnBinaryOp(expr, ExpressionBinaryOp.AND, list);\n\t\treturn list;\n\t}\n\t\n\t/**\n\t * Split a disjunction into a list of its component expressions, removing any parentheses.\n\t * Note: this is purely syntactic, e.g. both \"true\" and \"false\" just result in a singleton list.  \n\t * @param expr Expression to split.\n\t */\n\tpublic static List<Expression> splitDisjunction(Expression expr)\n\t{\n\t\tArrayList<Expression> list = new ArrayList<Expression>();\n\t\tsplitOnBinaryOp(expr, ExpressionBinaryOp.OR, list);\n\t\treturn list;\n\t}\n\t\n\t/**\n\t * Split an expression into a list of its component expressions, based on a binary operator.\n\t * Also remove any parentheses.\n\t * @param expr Expression to split.\n\t * @param op Code of operator to split on (from ExpressionBinaryOp).\n\t * @param list Expression list in which to append resulting expressions.\n\t */\n\tpublic static void splitOnBinaryOp(Expression expr, int op, List<Expression> list)\n\t{\n\t\t// Recursive case 1: brackets\n\t\tif (Expression.isParenth(expr)) {\n\t\t\tsplitOnBinaryOp(((ExpressionUnaryOp)expr).getOperand(), op, list);\t\t\t\t\n\t\t\treturn;\n\t\t}\n\t\t// Recursive case 2: binary operator\n\t\tif (expr instanceof ExpressionBinaryOp) {\n\t\t\tif (((ExpressionBinaryOp)expr).getOperator() == op) {\n\t\t\t\tsplitOnBinaryOp(((ExpressionBinaryOp)expr).getOperand1(), op, list);\t\t\t\t\n\t\t\t\tsplitOnBinaryOp(((ExpressionBinaryOp)expr).getOperand2(), op, list);\t\t\t\t\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\t// Base case: anything else\n\t\tlist.add(expr);\n\t}\n\t\n\t/**\n\t * Find the minimum value of an integer valued-expression\n\t * with respect to a variable list and some values for constants.\n\t */\n\tpublic static int findMinForIntExpression(Expression expr, VarList varList, Values constantValues) throws PrismLangException\n\t{\n\t\tList<String> vars;\n\t\tList<Values> allValues;\n\t\tint i, min;\n\t\t\n\t\t// For constant expressions, this is easy\n\t\tif (expr.isConstant())\n\t\t\treturn expr.evaluateInt(constantValues);\n\t\t\n\t\t// Get all variables appearing in the expression and all values of them\n\t\tvars = expr.getAllVars();\n\t\tallValues = varList.getAllValues(vars);\n\t\t\n\t\t// Compute min over all values\n\t\tmin = Integer.MAX_VALUE;\n\t\tfor (Values varValues : allValues) {\n\t\t\ti = expr.evaluateInt(constantValues, varValues);\n\t\t\tif (i < min)\n\t\t\t\tmin = i;\n\t\t}\n\t\t\n\t\treturn min;\n\t}\n\t\n\t/**\n\t * Find the maximum value of an integer valued-expression\n\t * with respect to a variable list and some values for constants.\n\t */\n\tpublic static int findMaxForIntExpression(Expression expr, VarList varList, Values constantValues) throws PrismLangException\n\t{\n\t\tList<String> vars;\n\t\tList<Values> allValues;\n\t\tint i, max;\n\t\t\n\t\t// For constant expressions, this is easy\n\t\tif (expr.isConstant())\n\t\t\treturn expr.evaluateInt(constantValues);\n\t\t\n\t\t// Get all variables appearing in the expression and all values of them\n\t\tvars = expr.getAllVars();\n\t\tallValues = varList.getAllValues(vars);\n\t\t\n\t\t// Compute max over all values\n\t\tmax = Integer.MIN_VALUE;\n\t\tfor (Values varValues : allValues) {\n\t\t\ti = expr.evaluateInt(constantValues, varValues);\n\t\t\tif (i > max)\n\t\t\t\tmax = i;\n\t\t}\n\t\t\n\t\treturn max;\n\t}\n\t\n\t/**\n\t * Find all possible values of an integer valued-expression\n\t * with respect to a variable list and some values for constants.\n\t */\n\tpublic static Collection<Integer> findAllValsForIntExpression(Expression expr, VarList varList, Values constantValues) throws PrismLangException\n\t{\n\t\tList<String> vars;\n\t\tList<Values> allValues;\n\t\tHashSet<Integer> res;\n\t\t\n\t\t// For constant expressions, this is easy\n\t\tif (expr.isConstant()) {\n\t\t\tres = new HashSet<Integer>();\n\t\t\tres.add(expr.evaluateInt(constantValues));\n\t\t\treturn res;\n\t\t}\n\t\t\n\t\t// Get all variables appearing in the expression and all values of them\n\t\tvars = expr.getAllVars();\n\t\tallValues = varList.getAllValues(vars);\n\t\t\n\t\t// Compute set of all values\n\t\tres = new HashSet<Integer>();\n\t\tfor (Values varValues : allValues) {\n\t\t\tres.add(expr.evaluateInt(constantValues, varValues));\n\t\t}\n\t\t\n\t\treturn res;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/Prism3To4.java",
    "content": "/* Prism3To4.java */\n/* Generated By:JavaCC: Do not edit this line. Prism3To4.java */\npackage parser;\n\nimport java.io.*;\n\n@SuppressWarnings({\"unused\", \"static-access\", \"serial\"})\npublic class Prism3To4 implements Prism3To4Constants {\n        public static void main(String[] args) throws ParseException\n        {\n                try {\n                        Prism3To4 p;\n                        if (args.length > 0) { p = new Prism3To4(new FileInputStream(args[0])); }\n                        else { p = new Prism3To4(System.in); }\n                        p.ModulesFileOrPropertiesFile();\n                }\n                catch (TokenMgrError e) {\n                        System.err.println(\"Syntax error\"+(args.length > 0?\" in \"+args[0]:\"\")+\": \" + e.getMessage()); System.exit(1);\n                }\n                catch (ParseException e) {\n                        System.err.println(\"Error\"+(args.length > 0?\" in \"+args[0]:\"\")+\": \" + e.getMessage()); System.exit(1);\n                }\n                catch (FileNotFoundException e) {\n                        System.err.println(e); System.exit(1);\n                }\n        }\n\n        private static void insertTokenBeforeNext(Token t, String s)\n        {\n                Token tNew=new Token(); tNew.image=s; tNew.specialToken=t.next.specialToken; t.next.specialToken=null; tNew.next=t.next; t.next=tNew;\n        }\n\n//-----------------------------------------------------------------------------------\n// top-level stuff\n//-----------------------------------------------------------------------------------\n  static final public \nvoid ModulesFileOrPropertiesFile() throws ParseException {Token t = null, ptr, ptr2;\nt = getToken(1);\n    if (jj_2_1(2147483647)) {\n      ModulesFile();\n    } else if (jj_2_2(2147483647)) {\n      PropertiesFile();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\nptr = t;\n                while (ptr != null) {\n                        if (ptr.specialToken != null) {\n                                ptr2 = ptr;\n                                while (ptr2.specialToken != null) ptr2 = ptr2.specialToken;\n                                while (ptr2 != null) { System.out.print(ptr2.image); ptr2 = ptr2.next; }\n                        }\n                        System.out.print(ptr.image);\n                        ptr = ptr.next;\n                }\n  }\n\n// modules file\n  static final public \nvoid ModulesFile() throws ParseException {\n    label_1:\n    while (true) {\n      if (jj_2_3(2147483647)) {\n        ;\n      } else {\n        break label_1;\n      }\n      if (jj_2_4(2147483647)) {\n        ModulesFileType();\n      } else if (jj_2_5(2147483647)) {\n        FormulaDef();\n      } else if (jj_2_6(2147483647)) {\n        LabelDef();\n      } else if (jj_2_7(2147483647)) {\n        ConstantDef();\n      } else if (jj_2_8(2147483647)) {\n        GlobalDecl();\n      } else if (jj_2_9(2147483647)) {\n        Module();\n      } else if (jj_2_10(2147483647)) {\n        RenamedModule();\n      } else if (jj_2_11(2147483647)) {\n        SystemComp();\n      } else if (jj_2_12(2147483647)) {\n        RewardStruct();\n      } else if (jj_2_13(2147483647)) {\n        Init();\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n    }\n    jj_consume_token(0);\n  }\n\n// properties file\n  static final public \nvoid PropertiesFile() throws ParseException {\n    label_2:\n    while (true) {\n      if (jj_2_14(2147483647)) {\n        ;\n      } else {\n        break label_2;\n      }\n      if (jj_2_15(2147483647)) {\n        LabelDef();\n      } else if (jj_2_16(2147483647)) {\n        ConstantDef();\n      } else if (jj_2_17(2147483647)) {\n        PCTLFormula();\ngetToken(0).image += \";\";\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n    }\n    jj_consume_token(0);\n  }\n\n// a single expression\n  static final public \nvoid SingleExpression() throws ParseException {\n    Expression();\n    jj_consume_token(0);\n  }\n\n//-----------------------------------------------------------------------------------\n// modules file stuff\n//-----------------------------------------------------------------------------------\n\n// keyword denoting module type (nondeterministic, probabilistic, ...)\n  static final public \nvoid ModulesFileType() throws ParseException {\n    if (jj_2_18(2147483647)) {\n      jj_consume_token(PROBABILISTIC);\n    } else if (jj_2_19(2147483647)) {\n      jj_consume_token(NONDETERMINISTIC);\n    } else if (jj_2_20(2147483647)) {\n      jj_consume_token(STOCHASTIC);\n    } else if (jj_2_21(2147483647)) {\n      jj_consume_token(DTMC);\n    } else if (jj_2_22(2147483647)) {\n      jj_consume_token(MDP);\n    } else if (jj_2_23(2147483647)) {\n      jj_consume_token(CTMC);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// formula definition\n  static final public \nvoid FormulaDef() throws ParseException {\n    jj_consume_token(FORMULA);\n    Identifier();\n    jj_consume_token(EQ);\n    Expression();\n    jj_consume_token(SEMICOLON);\n  }\n\n// label definition\n  static final public \nvoid LabelDef() throws ParseException {\n    jj_consume_token(LABEL);\n    jj_consume_token(DQUOTE);\n    Identifier();\n    jj_consume_token(DQUOTE);\n    jj_consume_token(EQ);\n    Expression();\n    jj_consume_token(SEMICOLON);\n  }\n\n// constant definition\n  static final public \nvoid ConstantDef() throws ParseException {\n    if (jj_2_31(2147483647)) {\n      jj_consume_token(CONST);\n      jj_consume_token(INT);\n      Identifier();\n      if (jj_2_24(2147483647)) {\n        jj_consume_token(EQ);\n        Expression();\n      } else {\n        ;\n      }\n      jj_consume_token(SEMICOLON);\n    } else if (jj_2_32(2147483647)) {\n      jj_consume_token(CONST);\n      jj_consume_token(DOUBLE);\n      Identifier();\n      if (jj_2_25(2147483647)) {\n        jj_consume_token(EQ);\n        Expression();\n      } else {\n        ;\n      }\n      jj_consume_token(SEMICOLON);\n    } else if (jj_2_33(2147483647)) {\n      jj_consume_token(CONST);\n      jj_consume_token(BOOL);\n      Identifier();\n      if (jj_2_26(2147483647)) {\n        jj_consume_token(EQ);\n        Expression();\n      } else {\n        ;\n      }\n      jj_consume_token(SEMICOLON);\n    } else if (jj_2_34(2147483647)) {\n      jj_consume_token(CONST);\n      Identifier();\n      if (jj_2_27(2147483647)) {\n        jj_consume_token(EQ);\n        Expression();\n      } else {\n        ;\n      }\n      jj_consume_token(SEMICOLON);\n    } else if (jj_2_35(2147483647)) {\n      if (jj_2_28(2147483647)) {\n        jj_consume_token(RATE);\n      } else if (jj_2_29(2147483647)) {\n        jj_consume_token(PROB);\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      Identifier();\n      if (jj_2_30(2147483647)) {\n        jj_consume_token(EQ);\n        Expression();\n      } else {\n        ;\n      }\n      jj_consume_token(SEMICOLON);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// global variable declaration\n  static final public \nvoid GlobalDecl() throws ParseException {\n    jj_consume_token(GLOBAL);\n    Declaration();\n  }\n\n// module definition\n  static final public \nvoid Module() throws ParseException {\n    jj_consume_token(MODULE);\n    Identifier();\n    label_3:\n    while (true) {\n      if (jj_2_36(2147483647)) {\n        ;\n      } else {\n        break label_3;\n      }\n      Declaration();\n    }\n    label_4:\n    while (true) {\n      if (jj_2_37(2147483647)) {\n        ;\n      } else {\n        break label_4;\n      }\n      Command();\n    }\n    jj_consume_token(ENDMODULE);\n  }\n\n// variable declaration\n  static final public \nvoid Declaration() throws ParseException {\n    if (jj_2_40(2147483647)) {\n      Identifier();\n      jj_consume_token(COLON);\n      jj_consume_token(LBRACKET);\n      Expression();\n      jj_consume_token(DOTS);\n      Expression();\n      jj_consume_token(RBRACKET);\n      if (jj_2_38(2147483647)) {\n        jj_consume_token(INIT);\n        Expression();\n      } else {\n        ;\n      }\n      jj_consume_token(SEMICOLON);\n    } else if (jj_2_41(2147483647)) {\n      Identifier();\n      jj_consume_token(COLON);\n      jj_consume_token(BOOL);\n      if (jj_2_39(2147483647)) {\n        jj_consume_token(INIT);\n        Expression();\n      } else {\n        ;\n      }\n      jj_consume_token(SEMICOLON);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// command definition\n  static final public \nvoid Command() throws ParseException {\n    jj_consume_token(LBRACKET);\n    if (jj_2_42(2147483647)) {\n      Identifier();\n    } else {\n      ;\n    }\n    jj_consume_token(RBRACKET);\n    Expression();\n    jj_consume_token(RARROW);\n    Updates();\n    jj_consume_token(SEMICOLON);\n  }\n\n  static final public void Updates() throws ParseException {\n    if (jj_2_44(2147483647)) {\n      Update();\n    } else if (jj_2_45(2147483647)) {\n      ProbUpdate();\n      label_5:\n      while (true) {\n        if (jj_2_43(2147483647)) {\n          ;\n        } else {\n          break label_5;\n        }\n        jj_consume_token(PLUS);\n        ProbUpdate();\n      }\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n  static final public void ProbUpdate() throws ParseException {\n    Expression();\n    jj_consume_token(COLON);\n    Update();\n  }\n\n  static final public void Update() throws ParseException {\n    if (jj_2_47(2147483647)) {\n      UpdateElement();\n      label_6:\n      while (true) {\n        if (jj_2_46(2147483647)) {\n          ;\n        } else {\n          break label_6;\n        }\n        jj_consume_token(AND);\n        UpdateElement();\n      }\n    } else if (jj_2_48(2147483647)) {\n      jj_consume_token(TRUE);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n  static final public void UpdateElement() throws ParseException {Token t1, t2;\n    if (jj_2_49(2147483647)) {\n      jj_consume_token(LPARENTH);\n      IdentifierPrime();\n      jj_consume_token(EQ);\n      Expression();\n      jj_consume_token(RPARENTH);\n    } else if (jj_2_50(2147483647)) {\nt1=getToken(0);\n      IdentifierPrime();\n      jj_consume_token(EQ);\n      Expression();\nt2=getToken(0);\ninsertTokenBeforeNext(t1, \"(\"); t2.image += \")\";\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// module definition (by renaming)\n  static final public \nvoid RenamedModule() throws ParseException {\n    jj_consume_token(MODULE);\n    Identifier();\n    jj_consume_token(EQ);\n    Identifier();\n    jj_consume_token(LBRACKET);\n    Renames();\n    jj_consume_token(RBRACKET);\n    jj_consume_token(ENDMODULE);\n  }\n\n  static final public void Renames() throws ParseException {\n    Rename();\n    label_7:\n    while (true) {\n      if (jj_2_51(2147483647)) {\n        ;\n      } else {\n        break label_7;\n      }\n      jj_consume_token(COMMA);\n      Rename();\n    }\n  }\n\n  static final public void Rename() throws ParseException {\n    if (jj_2_52(2147483647)) {\n      Identifier();\n    } else if (jj_2_53(2147483647)) {\n      jj_consume_token(MIN);\n    } else if (jj_2_54(2147483647)) {\n      jj_consume_token(MAX);\n    } else if (jj_2_55(2147483647)) {\n      jj_consume_token(FLOOR);\n    } else if (jj_2_56(2147483647)) {\n      jj_consume_token(CEIL);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    jj_consume_token(EQ);\n    if (jj_2_57(2147483647)) {\n      Identifier();\n    } else if (jj_2_58(2147483647)) {\n      jj_consume_token(MIN);\n    } else if (jj_2_59(2147483647)) {\n      jj_consume_token(MAX);\n    } else if (jj_2_60(2147483647)) {\n      jj_consume_token(FLOOR);\n    } else if (jj_2_61(2147483647)) {\n      jj_consume_token(CEIL);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// system composition definition\n  static final public \nvoid SystemComp() throws ParseException {\n    jj_consume_token(SYSTEM);\n    SystemParallels();\n    jj_consume_token(ENDSYSTEM);\n  }\n\n// system definition component\n  static final public \nvoid SystemParallels() throws ParseException {\n    if (jj_2_62(2147483647)) {\n      SystemFullParallel();\n    } else if (jj_2_63(2147483647)) {\n      SystemInterleaved();\n    } else if (jj_2_64(2147483647)) {\n      SystemParallel();\n    } else if (jj_2_65(2147483647)) {\n      SystemHideRename();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// system definition component (full parallel)\n  static final public \nvoid SystemFullParallel() throws ParseException {\n    SystemHideRename();\n    label_8:\n    while (true) {\n      jj_consume_token(OR);\n      jj_consume_token(OR);\n      SystemHideRename();\n      if (jj_2_66(2147483647)) {\n        ;\n      } else {\n        break label_8;\n      }\n    }\n  }\n\n// system definition component (interleaved parallel)\n  static final public \nvoid SystemInterleaved() throws ParseException {\n    SystemHideRename();\n    label_9:\n    while (true) {\n      jj_consume_token(OR);\n      jj_consume_token(OR);\n      jj_consume_token(OR);\n      SystemHideRename();\n      if (jj_2_67(2147483647)) {\n        ;\n      } else {\n        break label_9;\n      }\n    }\n  }\n\n// system definition component (parallel over set of actions)\n  static final public \nvoid SystemParallel() throws ParseException {\n    SystemHideRename();\n    jj_consume_token(OR);\n    jj_consume_token(LBRACKET);\n    SystemAction();\n    label_10:\n    while (true) {\n      if (jj_2_68(2147483647)) {\n        ;\n      } else {\n        break label_10;\n      }\n      jj_consume_token(COMMA);\n      SystemAction();\n    }\n    jj_consume_token(RBRACKET);\n    jj_consume_token(OR);\n    SystemHideRename();\n  }\n\n// system definition component (hiding and renaming)\n  static final public \nvoid SystemHideRename() throws ParseException {\n    SystemAtomic();\n    label_11:\n    while (true) {\n      if (jj_2_69(2147483647)) {\n        ;\n      } else {\n        break label_11;\n      }\n      if (jj_2_72(2147483647)) {\n        jj_consume_token(DIVIDE);\n        jj_consume_token(LBRACE);\n        SystemAction();\n        label_12:\n        while (true) {\n          if (jj_2_70(2147483647)) {\n            ;\n          } else {\n            break label_12;\n          }\n          jj_consume_token(COMMA);\n          SystemAction();\n        }\n        jj_consume_token(RBRACE);\n      } else if (jj_2_73(2147483647)) {\n        jj_consume_token(LBRACE);\n        SystemAction();\n        jj_consume_token(RENAME);\n        SystemAction();\n        label_13:\n        while (true) {\n          if (jj_2_71(2147483647)) {\n            ;\n          } else {\n            break label_13;\n          }\n          jj_consume_token(COMMA);\n          SystemAction();\n          jj_consume_token(RENAME);\n          SystemAction();\n        }\n        jj_consume_token(RBRACE);\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n    }\n  }\n\n// system definition component (bottom level)\n  static final public \nvoid SystemAtomic() throws ParseException {\n    if (jj_2_74(2147483647)) {\n      SystemModule();\n    } else if (jj_2_75(2147483647)) {\n      SystemBrackets();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// system definition component (action identifier)\n  static final public \nvoid SystemAction() throws ParseException {\n    Identifier();\n  }\n\n// system definition component (module identifier)\n  static final public \nvoid SystemModule() throws ParseException {\n    Identifier();\n  }\n\n// system definition component (brackets)\n  static final public \nvoid SystemBrackets() throws ParseException {\n    jj_consume_token(LPARENTH);\n    SystemParallels();\n    jj_consume_token(RPARENTH);\n  }\n\n// reward structure\n  static final public \nvoid RewardStruct() throws ParseException {\n    jj_consume_token(REWARDS);\n    if (jj_2_76(2147483647)) {\n      jj_consume_token(DQUOTE);\n      Identifier();\n      jj_consume_token(DQUOTE);\n    } else {\n      ;\n    }\n    label_14:\n    while (true) {\n      if (jj_2_77(2147483647)) {\n        ;\n      } else {\n        break label_14;\n      }\n      RewardStructItem();\n    }\n    jj_consume_token(ENDREWARDS);\n  }\n\n// single line (item) of state-based rewards structure\n  static final public \nvoid RewardStructItem() throws ParseException {\n    if (jj_2_79(2147483647)) {\n      jj_consume_token(LBRACKET);\n      if (jj_2_78(2147483647)) {\n        Identifier();\n      } else {\n        ;\n      }\n      jj_consume_token(RBRACKET);\n    } else {\n      ;\n    }\n    Expression();\n    jj_consume_token(COLON);\n    Expression();\n    jj_consume_token(SEMICOLON);\n  }\n\n// multiple initial states\n  static final public \nvoid Init() throws ParseException {\n    jj_consume_token(INIT);\n    Expression();\n    jj_consume_token(ENDINIT);\n  }\n\n//-----------------------------------------------------------------------------------\n// properties file stuff\n//-----------------------------------------------------------------------------------\n\n// pctl formula\n  static final public \nvoid PCTLFormula() throws ParseException {\n    PCTLImplies();\n  }\n\n  static final public void PCTLImplies() throws ParseException {\n    PCTLOr();\n    if (jj_2_80(2147483647)) {\n      jj_consume_token(IMPLIES);\n      PCTLOr();\n    } else {\n      ;\n    }\n  }\n\n  static final public void PCTLOr() throws ParseException {\n    PCTLAnd();\n    label_15:\n    while (true) {\n      if (jj_2_81(2147483647)) {\n        ;\n      } else {\n        break label_15;\n      }\n      jj_consume_token(OR);\n      PCTLAnd();\n    }\n  }\n\n  static final public void PCTLAnd() throws ParseException {\n    PCTLNot();\n    label_16:\n    while (true) {\n      if (jj_2_82(2147483647)) {\n        ;\n      } else {\n        break label_16;\n      }\n      jj_consume_token(AND);\n      PCTLNot();\n    }\n  }\n\n  static final public void PCTLNot() throws ParseException {\n    if (jj_2_83(2147483647)) {\n      jj_consume_token(NOT);\n    } else {\n      ;\n    }\n    PCTLProb();\n  }\n\n// pctl prob operator\n  static final public \nvoid PCTLProb() throws ParseException {\n    if (jj_2_99(2147483647)) {\n      if (jj_2_84(2147483647)) {\n        jj_consume_token(P);\n        LtGt();\n        Expression();\n      } else if (jj_2_85(2147483647)) {\n        jj_consume_token(P);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\n      } else if (jj_2_86(2147483647)) {\n        jj_consume_token(P);\n        jj_consume_token(MIN);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\n      } else if (jj_2_87(2147483647)) {\n        jj_consume_token(P);\n        jj_consume_token(MAX);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\n      } else if (jj_2_88(2147483647)) {\n        jj_consume_token(PMIN);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\n      } else if (jj_2_89(2147483647)) {\n        jj_consume_token(PMAX);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      jj_consume_token(LBRACKET);\n      if (jj_2_90(2147483647)) {\n        PCTLProbNext();\n      } else if (jj_2_91(2147483647)) {\n        PCTLProbBoundedUntil();\n      } else if (jj_2_92(2147483647)) {\n        PCTLProbUntil();\n      } else if (jj_2_93(2147483647)) {\n        PCTLProbBoundedFutureGlobal();\n      } else if (jj_2_94(2147483647)) {\n        PCTLProbFutureGlobal();\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      if (jj_2_98(2147483647)) {\n        jj_consume_token(LBRACE);\n        PCTLFormula();\n        jj_consume_token(RBRACE);\n        label_17:\n        while (true) {\n          if (jj_2_95(2147483647)) {\n            ;\n          } else {\n            break label_17;\n          }\n          if (jj_2_96(2147483647)) {\n            jj_consume_token(LBRACE);\n            jj_consume_token(MIN);\n            jj_consume_token(RBRACE);\n          } else if (jj_2_97(2147483647)) {\n            jj_consume_token(LBRACE);\n            jj_consume_token(MAX);\n            jj_consume_token(RBRACE);\n          } else {\n            jj_consume_token(-1);\n            throw new ParseException();\n          }\n        }\n      } else {\n        ;\n      }\n      jj_consume_token(RBRACKET);\n    } else if (jj_2_100(2147483647)) {\n      PCTLSS();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// pctl next\n  static final public \nvoid PCTLProbNext() throws ParseException {\n    jj_consume_token(NEXT);\n    PCTLFormula();\n  }\n\n// pctl bounded until\n  static final public \nvoid PCTLProbBoundedUntil() throws ParseException {\n    PCTLFormula();\n    jj_consume_token(UNTIL);\n    if (jj_2_101(2147483647)) {\n      jj_consume_token(LE);\n      Expression();\n    } else if (jj_2_102(2147483647)) {\n      jj_consume_token(GE);\n      Expression();\n    } else if (jj_2_103(2147483647)) {\n      jj_consume_token(LBRACKET);\n      Expression();\n      jj_consume_token(COMMA);\n      Expression();\n      jj_consume_token(RBRACKET);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    PCTLFormula();\n  }\n\n// pctl until (unbounded)\n  static final public \nvoid PCTLProbUntil() throws ParseException {\n    PCTLFormula();\n    jj_consume_token(UNTIL);\n    PCTLFormula();\n  }\n\n// pctl bounded future (eventually) or global\n  static final public \nvoid PCTLProbBoundedFutureGlobal() throws ParseException {\n    if (jj_2_104(2147483647)) {\n      jj_consume_token(FUTURE);\n    } else if (jj_2_105(2147483647)) {\n      jj_consume_token(GLOB);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    if (jj_2_106(2147483647)) {\n      jj_consume_token(LE);\n      Expression();\n    } else if (jj_2_107(2147483647)) {\n      jj_consume_token(GE);\n      Expression();\n    } else if (jj_2_108(2147483647)) {\n      jj_consume_token(LBRACKET);\n      Expression();\n      jj_consume_token(COMMA);\n      Expression();\n      jj_consume_token(RBRACKET);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    PCTLFormula();\n  }\n\n// pctl future (eventually) or globally\n  static final public \nvoid PCTLProbFutureGlobal() throws ParseException {\n    if (jj_2_109(2147483647)) {\n      jj_consume_token(FUTURE);\n    } else if (jj_2_110(2147483647)) {\n      jj_consume_token(GLOB);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    PCTLFormula();\n  }\n\n// pctl steady state (actually only csl - not pctl at all)\n  static final public \nvoid PCTLSS() throws ParseException {\n    if (jj_2_114(2147483647)) {\n      if (jj_2_111(2147483647)) {\n        jj_consume_token(S);\n        LtGt();\n        Expression();\n      } else if (jj_2_112(2147483647)) {\n        jj_consume_token(S);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      jj_consume_token(LBRACKET);\n      PCTLFormula();\n      if (jj_2_113(2147483647)) {\n        jj_consume_token(LBRACE);\n        PCTLFormula();\n        jj_consume_token(RBRACE);\n      } else {\n        ;\n      }\n      jj_consume_token(RBRACKET);\n    } else if (jj_2_115(2147483647)) {\n      PCTLReward();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// pctl reward operator\n  static final public \nvoid PCTLReward() throws ParseException {\n    if (jj_2_134(2147483647)) {\n      if (jj_2_123(2147483647)) {\n        jj_consume_token(R);\n        if (jj_2_118(2147483647)) {\n          jj_consume_token(LBRACE);\n          if (jj_2_116(2147483647)) {\n            jj_consume_token(DQUOTE);\n            Identifier();\n            jj_consume_token(DQUOTE);\n          } else if (jj_2_117(2147483647)) {\n            Expression();\n          } else {\n            jj_consume_token(-1);\n            throw new ParseException();\n          }\n          jj_consume_token(RBRACE);\n        } else {\n          ;\n        }\n        if (jj_2_119(2147483647)) {\n          LtGt();\n          Expression();\n        } else if (jj_2_120(2147483647)) {\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\n        } else if (jj_2_121(2147483647)) {\n          jj_consume_token(MIN);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\n        } else if (jj_2_122(2147483647)) {\n          jj_consume_token(MAX);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\n        } else {\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n      } else if (jj_2_124(2147483647)) {\n        jj_consume_token(RMIN);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\n      } else if (jj_2_125(2147483647)) {\n        jj_consume_token(RMAX);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      jj_consume_token(LBRACKET);\n      if (jj_2_126(2147483647)) {\n        PCTLRewardCumul();\n      } else if (jj_2_127(2147483647)) {\n        PCTLRewardInst();\n      } else if (jj_2_128(2147483647)) {\n        PCTLRewardReach();\n      } else if (jj_2_129(2147483647)) {\n        PCTLRewardSS();\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      if (jj_2_133(2147483647)) {\n        jj_consume_token(LBRACE);\n        PCTLFormula();\n        jj_consume_token(RBRACE);\n        label_18:\n        while (true) {\n          if (jj_2_130(2147483647)) {\n            ;\n          } else {\n            break label_18;\n          }\n          if (jj_2_131(2147483647)) {\n            jj_consume_token(LBRACE);\n            jj_consume_token(MIN);\n            jj_consume_token(RBRACE);\n          } else if (jj_2_132(2147483647)) {\n            jj_consume_token(LBRACE);\n            jj_consume_token(MAX);\n            jj_consume_token(RBRACE);\n          } else {\n            jj_consume_token(-1);\n            throw new ParseException();\n          }\n        }\n      } else {\n        ;\n      }\n      jj_consume_token(RBRACKET);\n    } else if (jj_2_135(2147483647)) {\n      PCTLInit();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// cumulative reward\n  static final public \nvoid PCTLRewardCumul() throws ParseException {\n    jj_consume_token(CUMUL);\n    jj_consume_token(LE);\n    Expression();\n  }\n\n// instantaneous reward\n  static final public \nvoid PCTLRewardInst() throws ParseException {\n    jj_consume_token(INST);\n    jj_consume_token(EQ);\n    Expression();\n  }\n\n// reach reward\n  static final public \nvoid PCTLRewardReach() throws ParseException {\n    jj_consume_token(FUTURE);\n    PCTLFormula();\n  }\n\n// steady-state reward\n  static final public \nvoid PCTLRewardSS() throws ParseException {\n    jj_consume_token(S);\n  }\n\n// init\n  static final public \nvoid PCTLInit() throws ParseException {\n    if (jj_2_136(2147483647)) {\n      jj_consume_token(DQUOTE);\n      jj_consume_token(INIT);\n      jj_consume_token(DQUOTE);\n    } else if (jj_2_137(2147483647)) {\n      PCTLLabel();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// label\n  static final public \nvoid PCTLLabel() throws ParseException {\n    if (jj_2_138(2147483647)) {\n      jj_consume_token(DQUOTE);\n      Identifier();\n      jj_consume_token(DQUOTE);\n    } else if (jj_2_139(2147483647)) {\n      PCTLBrackets();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// brackets\n  static final public \nvoid PCTLBrackets() throws ParseException {\n    if (jj_2_140(2147483647)) {\n      jj_consume_token(LPARENTH);\n      PCTLFormula();\n      jj_consume_token(RPARENTH);\n    } else if (jj_2_141(2147483647)) {\n      PCTLExpression();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// pctl expression\n  static final public \nvoid PCTLExpression() throws ParseException {\n    ExpressionRelOpRange();\n  }\n\n//-----------------------------------------------------------------------------------\n// expression stuff\n//-----------------------------------------------------------------------------------\n\n// expression\n  static final public \nvoid Expression() throws ParseException {\n    ExpressionITE();\n  }\n\n// expression (if-then-else)\n  static final public \nvoid ExpressionITE() throws ParseException {\n    if (jj_2_142(2147483647)) {\n      ExpressionOr();\n      jj_consume_token(QMARK);\n      ExpressionOr();\n      jj_consume_token(COLON);\n      ExpressionITE();\n    } else if (jj_2_143(2147483647)) {\n      ExpressionOr();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// expression (or)\n  static final public \nvoid ExpressionOr() throws ParseException {\n    ExpressionAnd();\n    if (jj_2_144(2147483647)) {\n      jj_consume_token(OR);\n      ExpressionOr();\n    } else {\n      ;\n    }\n  }\n\n// expression (and)\n  static final public \nvoid ExpressionAnd() throws ParseException {\n    ExpressionNot();\n    label_19:\n    while (true) {\n      if (jj_2_145(2147483647)) {\n        ;\n      } else {\n        break label_19;\n      }\n      jj_consume_token(AND);\n      ExpressionNot();\n    }\n  }\n\n// expression (not)\n  static final public \nvoid ExpressionNot() throws ParseException {\n    if (jj_2_146(2147483647)) {\n      jj_consume_token(NOT);\n    } else {\n      ;\n    }\n    ExpressionRelOpRange();\n  }\n\n// expression: relational operators/ranges\n  static final public \nvoid ExpressionRelOpRange() throws ParseException {Token t0, t1, t2, ptr;\n        String relOp = null;\n        boolean up, thisIsARange = false;\n        String lhs = null, s1 = null, s2 = null, newExpr = \"\";\n    if (jj_2_150(2147483647)) {\n      ExpressionPlusMinus();\n      relOp = LtGt();\n      ExpressionPlusMinus();\n    } else if (jj_2_151(2147483647)) {\nt0=getToken(0); t1=getToken(1);\n      ExpressionPlusMinus();\nt2=getToken(1); ptr = t1; lhs = \"\"; while (ptr != t2) { lhs += ptr.image; ptr = ptr.next; }\n      relOp = EqNeq();\nnewExpr = (relOp.equals(\"!=\"))?\"!(\":\"(\";\nt1=getToken(1);\n      ExpressionPlusMinus();\nt2=getToken(1); ptr = t1; s1 = \"\"; while (ptr != t2) { s1 += ptr.image; ptr = ptr.next; } up = false;\n      if (jj_2_147(2147483647)) {\n        jj_consume_token(DOTS);\nthisIsARange = true; t1=getToken(1);\n        ExpressionPlusMinus();\nt2=getToken(1); ptr = t1; s2 = \"\"; while (ptr != t2) { s2 += ptr.image; ptr = ptr.next; } up = true;\n      } else {\n        ;\n      }\nif (up) newExpr += \"(\"+lhs+\")>=(\"+s1+\")&(\"+lhs+\")<=(\"+s2+\")\"; else newExpr += \"(\"+lhs+\")=(\"+s1+\")\";\n      label_20:\n      while (true) {\n        if (jj_2_148(2147483647)) {\n          ;\n        } else {\n          break label_20;\n        }\n        jj_consume_token(COMMA);\nthisIsARange = true; t1=getToken(1);\n        ExpressionPlusMinus();\nt2=getToken(1); ptr = t1; s1 = \"\"; while (ptr != t2) { s1 += ptr.image; ptr = ptr.next; } up = false;\n        if (jj_2_149(2147483647)) {\n          jj_consume_token(DOTS);\nt1=getToken(1);\n          ExpressionPlusMinus();\nt2=getToken(1); ptr = t1; s2 = \"\"; while (ptr != t2) { s2 += ptr.image; ptr = ptr.next; } up = true;\n        } else {\n          ;\n        }\nif (up) newExpr += \"|(\"+lhs+\")>=(\"+s1+\")&(\"+lhs+\")<=(\"+s2+\")\"; else newExpr += \"|(\"+lhs+\")=(\"+s1+\")\";\n      }\nnewExpr += \")\"; if (thisIsARange) { t0.next = getToken(1); insertTokenBeforeNext(t0, newExpr); }\n    } else if (jj_2_152(2147483647)) {\n      ExpressionPlusMinus();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// expression: plus/minus - binary, left associative\n  static final public \nvoid ExpressionPlusMinus() throws ParseException {\n    ExpressionTimesDivide();\n    label_21:\n    while (true) {\n      if (jj_2_153(2147483647)) {\n        ;\n      } else {\n        break label_21;\n      }\n      if (jj_2_154(2147483647)) {\n        jj_consume_token(PLUS);\n      } else if (jj_2_155(2147483647)) {\n        jj_consume_token(MINUS);\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      ExpressionTimesDivide();\n    }\n  }\n\n// expression: times/divide - binary, left associative\n  static final public \nvoid ExpressionTimesDivide() throws ParseException {\n    ExpressionUnaryMinus();\n    label_22:\n    while (true) {\n      if (jj_2_156(2147483647)) {\n        ;\n      } else {\n        break label_22;\n      }\n      if (jj_2_157(2147483647)) {\n        jj_consume_token(TIMES);\n      } else if (jj_2_158(2147483647)) {\n        jj_consume_token(DIVIDE);\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      ExpressionUnaryMinus();\n    }\n  }\n\n// expression: unary minus (right associative)\n  static final public \nvoid ExpressionUnaryMinus() throws ParseException {\n    if (jj_2_159(2147483647)) {\n      jj_consume_token(MINUS);\n      ExpressionFunc();\n    } else if (jj_2_160(2147483647)) {\n      ExpressionFunc();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// expression (function)\n  static final public \nvoid ExpressionFunc() throws ParseException {\n    if (jj_2_173(2147483647)) {\n      if (jj_2_170(2147483647)) {\n        if (jj_2_161(2147483647)) {\n          jj_consume_token(MIN);\n        } else if (jj_2_162(2147483647)) {\n          jj_consume_token(MAX);\n        } else if (jj_2_163(2147483647)) {\n          jj_consume_token(FLOOR);\n        } else if (jj_2_164(2147483647)) {\n          jj_consume_token(CEIL);\n        } else {\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n        jj_consume_token(LPARENTH);\n      } else if (jj_2_171(2147483647)) {\n        jj_consume_token(FUNC);\n        jj_consume_token(LPARENTH);\n        if (jj_2_165(2147483647)) {\n          Identifier();\n        } else if (jj_2_166(2147483647)) {\n          jj_consume_token(MIN);\n        } else if (jj_2_167(2147483647)) {\n          jj_consume_token(MAX);\n        } else if (jj_2_168(2147483647)) {\n          jj_consume_token(FLOOR);\n        } else if (jj_2_169(2147483647)) {\n          jj_consume_token(CEIL);\n        } else {\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n        jj_consume_token(COMMA);\n      } else {\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      Expression();\n      label_23:\n      while (true) {\n        if (jj_2_172(2147483647)) {\n          ;\n        } else {\n          break label_23;\n        }\n        jj_consume_token(COMMA);\n        Expression();\n      }\n      jj_consume_token(RPARENTH);\n    } else if (jj_2_174(2147483647)) {\n      ExpressionIdent();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// expression (identifier)\n  static final public \nvoid ExpressionIdent() throws ParseException {\n    if (jj_2_175(2147483647)) {\n      Identifier();\n    } else if (jj_2_176(2147483647)) {\n      ExpressionLiteral();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// expression (literal)\n  static final public \nvoid ExpressionLiteral() throws ParseException {\n    if (jj_2_177(2147483647)) {\n      Int();\n    } else if (jj_2_178(2147483647)) {\n      Double();\n    } else if (jj_2_179(2147483647)) {\n      jj_consume_token(TRUE);\n    } else if (jj_2_180(2147483647)) {\n      jj_consume_token(FALSE);\n    } else if (jj_2_181(2147483647)) {\n      ExpressionBrackets();\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n// expression (brackets)\n  static final public \nvoid ExpressionBrackets() throws ParseException {\n    jj_consume_token(LPARENTH);\n    Expression();\n    jj_consume_token(RPARENTH);\n  }\n\n//-----------------------------------------------------------------------------------\n// miscellaneous stuff\n//-----------------------------------------------------------------------------------\n\n// identifier\n  static final public \nString Identifier() throws ParseException {\n    jj_consume_token(REG_IDENT);\n{if (\"\" != null) return token.image;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n// identifier with a prime\n  static final public \nString IdentifierPrime() throws ParseException {\n    jj_consume_token(REG_IDENTPRIME);\n// remove prime and return\n                String s = token.image;\n                s = s.substring(0, s.length()-1);\n                {if (\"\" != null) return s;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n// one of the relational operators: =, !=\n  static final public \nString EqNeq() throws ParseException {\n    if (jj_2_182(2147483647)) {\n      jj_consume_token(EQ);\n    } else if (jj_2_183(2147483647)) {\n      jj_consume_token(NE);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return token.image;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n// one of the relational operators: >, <, >=, <=\n  static final public \nString LtGt() throws ParseException {\n    if (jj_2_184(2147483647)) {\n      jj_consume_token(GT);\n    } else if (jj_2_185(2147483647)) {\n      jj_consume_token(LT);\n    } else if (jj_2_186(2147483647)) {\n      jj_consume_token(GE);\n    } else if (jj_2_187(2147483647)) {\n      jj_consume_token(LE);\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return token.image;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n// integer\n  static final public \nint Int() throws ParseException {int i;\n    jj_consume_token(REG_INT);\ni = Integer.parseInt(token.image);\n                {if (\"\" != null) return i;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n// double\n  static final public \nString Double() throws ParseException {\n    jj_consume_token(REG_DOUBLE);\n//return Double.valueOf(token.image).doubleValue();\n                {if (\"\" != null) return token.image;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n  static private boolean jj_2_1(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_1(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(0, xla); }\n  }\n\n  static private boolean jj_2_2(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_2(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(1, xla); }\n  }\n\n  static private boolean jj_2_3(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_3(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(2, xla); }\n  }\n\n  static private boolean jj_2_4(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_4(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(3, xla); }\n  }\n\n  static private boolean jj_2_5(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_5(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(4, xla); }\n  }\n\n  static private boolean jj_2_6(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_6(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(5, xla); }\n  }\n\n  static private boolean jj_2_7(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_7(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(6, xla); }\n  }\n\n  static private boolean jj_2_8(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_8(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(7, xla); }\n  }\n\n  static private boolean jj_2_9(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_9(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(8, xla); }\n  }\n\n  static private boolean jj_2_10(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_10(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(9, xla); }\n  }\n\n  static private boolean jj_2_11(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_11(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(10, xla); }\n  }\n\n  static private boolean jj_2_12(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_12(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(11, xla); }\n  }\n\n  static private boolean jj_2_13(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_13(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(12, xla); }\n  }\n\n  static private boolean jj_2_14(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_14(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(13, xla); }\n  }\n\n  static private boolean jj_2_15(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_15(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(14, xla); }\n  }\n\n  static private boolean jj_2_16(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_16(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(15, xla); }\n  }\n\n  static private boolean jj_2_17(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_17(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(16, xla); }\n  }\n\n  static private boolean jj_2_18(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_18(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(17, xla); }\n  }\n\n  static private boolean jj_2_19(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_19(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(18, xla); }\n  }\n\n  static private boolean jj_2_20(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_20(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(19, xla); }\n  }\n\n  static private boolean jj_2_21(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_21(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(20, xla); }\n  }\n\n  static private boolean jj_2_22(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_22(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(21, xla); }\n  }\n\n  static private boolean jj_2_23(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_23(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(22, xla); }\n  }\n\n  static private boolean jj_2_24(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_24(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(23, xla); }\n  }\n\n  static private boolean jj_2_25(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_25(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(24, xla); }\n  }\n\n  static private boolean jj_2_26(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_26(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(25, xla); }\n  }\n\n  static private boolean jj_2_27(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_27(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(26, xla); }\n  }\n\n  static private boolean jj_2_28(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_28(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(27, xla); }\n  }\n\n  static private boolean jj_2_29(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_29(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(28, xla); }\n  }\n\n  static private boolean jj_2_30(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_30(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(29, xla); }\n  }\n\n  static private boolean jj_2_31(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_31(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(30, xla); }\n  }\n\n  static private boolean jj_2_32(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_32(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(31, xla); }\n  }\n\n  static private boolean jj_2_33(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_33(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(32, xla); }\n  }\n\n  static private boolean jj_2_34(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_34(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(33, xla); }\n  }\n\n  static private boolean jj_2_35(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_35(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(34, xla); }\n  }\n\n  static private boolean jj_2_36(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_36(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(35, xla); }\n  }\n\n  static private boolean jj_2_37(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_37(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(36, xla); }\n  }\n\n  static private boolean jj_2_38(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_38(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(37, xla); }\n  }\n\n  static private boolean jj_2_39(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_39(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(38, xla); }\n  }\n\n  static private boolean jj_2_40(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_40(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(39, xla); }\n  }\n\n  static private boolean jj_2_41(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_41(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(40, xla); }\n  }\n\n  static private boolean jj_2_42(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_42(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(41, xla); }\n  }\n\n  static private boolean jj_2_43(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_43(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(42, xla); }\n  }\n\n  static private boolean jj_2_44(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_44(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(43, xla); }\n  }\n\n  static private boolean jj_2_45(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_45(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(44, xla); }\n  }\n\n  static private boolean jj_2_46(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_46(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(45, xla); }\n  }\n\n  static private boolean jj_2_47(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_47(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(46, xla); }\n  }\n\n  static private boolean jj_2_48(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_48(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(47, xla); }\n  }\n\n  static private boolean jj_2_49(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_49(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(48, xla); }\n  }\n\n  static private boolean jj_2_50(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_50(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(49, xla); }\n  }\n\n  static private boolean jj_2_51(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_51(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(50, xla); }\n  }\n\n  static private boolean jj_2_52(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_52(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(51, xla); }\n  }\n\n  static private boolean jj_2_53(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_53(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(52, xla); }\n  }\n\n  static private boolean jj_2_54(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_54(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(53, xla); }\n  }\n\n  static private boolean jj_2_55(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_55(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(54, xla); }\n  }\n\n  static private boolean jj_2_56(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_56(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(55, xla); }\n  }\n\n  static private boolean jj_2_57(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_57(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(56, xla); }\n  }\n\n  static private boolean jj_2_58(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_58(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(57, xla); }\n  }\n\n  static private boolean jj_2_59(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_59(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(58, xla); }\n  }\n\n  static private boolean jj_2_60(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_60(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(59, xla); }\n  }\n\n  static private boolean jj_2_61(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_61(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(60, xla); }\n  }\n\n  static private boolean jj_2_62(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_62(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(61, xla); }\n  }\n\n  static private boolean jj_2_63(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_63(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(62, xla); }\n  }\n\n  static private boolean jj_2_64(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_64(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(63, xla); }\n  }\n\n  static private boolean jj_2_65(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_65(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(64, xla); }\n  }\n\n  static private boolean jj_2_66(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_66(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(65, xla); }\n  }\n\n  static private boolean jj_2_67(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_67(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(66, xla); }\n  }\n\n  static private boolean jj_2_68(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_68(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(67, xla); }\n  }\n\n  static private boolean jj_2_69(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_69(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(68, xla); }\n  }\n\n  static private boolean jj_2_70(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_70(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(69, xla); }\n  }\n\n  static private boolean jj_2_71(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_71(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(70, xla); }\n  }\n\n  static private boolean jj_2_72(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_72(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(71, xla); }\n  }\n\n  static private boolean jj_2_73(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_73(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(72, xla); }\n  }\n\n  static private boolean jj_2_74(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_74(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(73, xla); }\n  }\n\n  static private boolean jj_2_75(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_75(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(74, xla); }\n  }\n\n  static private boolean jj_2_76(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_76(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(75, xla); }\n  }\n\n  static private boolean jj_2_77(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_77(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(76, xla); }\n  }\n\n  static private boolean jj_2_78(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_78(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(77, xla); }\n  }\n\n  static private boolean jj_2_79(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_79(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(78, xla); }\n  }\n\n  static private boolean jj_2_80(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_80(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(79, xla); }\n  }\n\n  static private boolean jj_2_81(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_81(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(80, xla); }\n  }\n\n  static private boolean jj_2_82(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_82(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(81, xla); }\n  }\n\n  static private boolean jj_2_83(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_83(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(82, xla); }\n  }\n\n  static private boolean jj_2_84(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_84(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(83, xla); }\n  }\n\n  static private boolean jj_2_85(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_85(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(84, xla); }\n  }\n\n  static private boolean jj_2_86(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_86(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(85, xla); }\n  }\n\n  static private boolean jj_2_87(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_87(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(86, xla); }\n  }\n\n  static private boolean jj_2_88(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_88(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(87, xla); }\n  }\n\n  static private boolean jj_2_89(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_89(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(88, xla); }\n  }\n\n  static private boolean jj_2_90(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_90(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(89, xla); }\n  }\n\n  static private boolean jj_2_91(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_91(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(90, xla); }\n  }\n\n  static private boolean jj_2_92(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_92(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(91, xla); }\n  }\n\n  static private boolean jj_2_93(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_93(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(92, xla); }\n  }\n\n  static private boolean jj_2_94(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_94(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(93, xla); }\n  }\n\n  static private boolean jj_2_95(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_95(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(94, xla); }\n  }\n\n  static private boolean jj_2_96(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_96(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(95, xla); }\n  }\n\n  static private boolean jj_2_97(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_97(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(96, xla); }\n  }\n\n  static private boolean jj_2_98(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_98(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(97, xla); }\n  }\n\n  static private boolean jj_2_99(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_99(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(98, xla); }\n  }\n\n  static private boolean jj_2_100(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_100(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(99, xla); }\n  }\n\n  static private boolean jj_2_101(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_101(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(100, xla); }\n  }\n\n  static private boolean jj_2_102(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_102(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(101, xla); }\n  }\n\n  static private boolean jj_2_103(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_103(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(102, xla); }\n  }\n\n  static private boolean jj_2_104(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_104(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(103, xla); }\n  }\n\n  static private boolean jj_2_105(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_105(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(104, xla); }\n  }\n\n  static private boolean jj_2_106(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_106(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(105, xla); }\n  }\n\n  static private boolean jj_2_107(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_107(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(106, xla); }\n  }\n\n  static private boolean jj_2_108(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_108(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(107, xla); }\n  }\n\n  static private boolean jj_2_109(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_109(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(108, xla); }\n  }\n\n  static private boolean jj_2_110(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_110(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(109, xla); }\n  }\n\n  static private boolean jj_2_111(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_111(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(110, xla); }\n  }\n\n  static private boolean jj_2_112(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_112(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(111, xla); }\n  }\n\n  static private boolean jj_2_113(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_113(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(112, xla); }\n  }\n\n  static private boolean jj_2_114(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_114(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(113, xla); }\n  }\n\n  static private boolean jj_2_115(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_115(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(114, xla); }\n  }\n\n  static private boolean jj_2_116(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_116(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(115, xla); }\n  }\n\n  static private boolean jj_2_117(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_117(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(116, xla); }\n  }\n\n  static private boolean jj_2_118(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_118(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(117, xla); }\n  }\n\n  static private boolean jj_2_119(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_119(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(118, xla); }\n  }\n\n  static private boolean jj_2_120(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_120(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(119, xla); }\n  }\n\n  static private boolean jj_2_121(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_121(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(120, xla); }\n  }\n\n  static private boolean jj_2_122(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_122(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(121, xla); }\n  }\n\n  static private boolean jj_2_123(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_123(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(122, xla); }\n  }\n\n  static private boolean jj_2_124(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_124(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(123, xla); }\n  }\n\n  static private boolean jj_2_125(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_125(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(124, xla); }\n  }\n\n  static private boolean jj_2_126(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_126(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(125, xla); }\n  }\n\n  static private boolean jj_2_127(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_127(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(126, xla); }\n  }\n\n  static private boolean jj_2_128(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_128(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(127, xla); }\n  }\n\n  static private boolean jj_2_129(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_129(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(128, xla); }\n  }\n\n  static private boolean jj_2_130(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_130(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(129, xla); }\n  }\n\n  static private boolean jj_2_131(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_131(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(130, xla); }\n  }\n\n  static private boolean jj_2_132(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_132(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(131, xla); }\n  }\n\n  static private boolean jj_2_133(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_133(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(132, xla); }\n  }\n\n  static private boolean jj_2_134(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_134(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(133, xla); }\n  }\n\n  static private boolean jj_2_135(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_135(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(134, xla); }\n  }\n\n  static private boolean jj_2_136(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_136(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(135, xla); }\n  }\n\n  static private boolean jj_2_137(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_137(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(136, xla); }\n  }\n\n  static private boolean jj_2_138(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_138(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(137, xla); }\n  }\n\n  static private boolean jj_2_139(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_139(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(138, xla); }\n  }\n\n  static private boolean jj_2_140(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_140(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(139, xla); }\n  }\n\n  static private boolean jj_2_141(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_141(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(140, xla); }\n  }\n\n  static private boolean jj_2_142(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_142(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(141, xla); }\n  }\n\n  static private boolean jj_2_143(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_143(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(142, xla); }\n  }\n\n  static private boolean jj_2_144(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_144(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(143, xla); }\n  }\n\n  static private boolean jj_2_145(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_145(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(144, xla); }\n  }\n\n  static private boolean jj_2_146(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_146(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(145, xla); }\n  }\n\n  static private boolean jj_2_147(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_147(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(146, xla); }\n  }\n\n  static private boolean jj_2_148(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_148(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(147, xla); }\n  }\n\n  static private boolean jj_2_149(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_149(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(148, xla); }\n  }\n\n  static private boolean jj_2_150(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_150(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(149, xla); }\n  }\n\n  static private boolean jj_2_151(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_151(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(150, xla); }\n  }\n\n  static private boolean jj_2_152(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_152(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(151, xla); }\n  }\n\n  static private boolean jj_2_153(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_153(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(152, xla); }\n  }\n\n  static private boolean jj_2_154(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_154(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(153, xla); }\n  }\n\n  static private boolean jj_2_155(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_155(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(154, xla); }\n  }\n\n  static private boolean jj_2_156(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_156(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(155, xla); }\n  }\n\n  static private boolean jj_2_157(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_157(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(156, xla); }\n  }\n\n  static private boolean jj_2_158(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_158(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(157, xla); }\n  }\n\n  static private boolean jj_2_159(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_159(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(158, xla); }\n  }\n\n  static private boolean jj_2_160(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_160(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(159, xla); }\n  }\n\n  static private boolean jj_2_161(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_161(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(160, xla); }\n  }\n\n  static private boolean jj_2_162(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_162(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(161, xla); }\n  }\n\n  static private boolean jj_2_163(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_163(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(162, xla); }\n  }\n\n  static private boolean jj_2_164(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_164(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(163, xla); }\n  }\n\n  static private boolean jj_2_165(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_165(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(164, xla); }\n  }\n\n  static private boolean jj_2_166(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_166(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(165, xla); }\n  }\n\n  static private boolean jj_2_167(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_167(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(166, xla); }\n  }\n\n  static private boolean jj_2_168(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_168(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(167, xla); }\n  }\n\n  static private boolean jj_2_169(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_169(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(168, xla); }\n  }\n\n  static private boolean jj_2_170(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_170(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(169, xla); }\n  }\n\n  static private boolean jj_2_171(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_171(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(170, xla); }\n  }\n\n  static private boolean jj_2_172(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_172(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(171, xla); }\n  }\n\n  static private boolean jj_2_173(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_173(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(172, xla); }\n  }\n\n  static private boolean jj_2_174(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_174(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(173, xla); }\n  }\n\n  static private boolean jj_2_175(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_175(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(174, xla); }\n  }\n\n  static private boolean jj_2_176(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_176(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(175, xla); }\n  }\n\n  static private boolean jj_2_177(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_177(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(176, xla); }\n  }\n\n  static private boolean jj_2_178(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_178(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(177, xla); }\n  }\n\n  static private boolean jj_2_179(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_179(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(178, xla); }\n  }\n\n  static private boolean jj_2_180(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_180(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(179, xla); }\n  }\n\n  static private boolean jj_2_181(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_181(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(180, xla); }\n  }\n\n  static private boolean jj_2_182(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_182(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(181, xla); }\n  }\n\n  static private boolean jj_2_183(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_183(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(182, xla); }\n  }\n\n  static private boolean jj_2_184(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_184(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(183, xla); }\n  }\n\n  static private boolean jj_2_185(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_185(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(184, xla); }\n  }\n\n  static private boolean jj_2_186(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_186(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(185, xla); }\n  }\n\n  static private boolean jj_2_187(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return !jj_3_187(); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(186, xla); }\n  }\n\n  static private boolean jj_3_63()\n {\n    if (jj_3R_47()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_180()\n {\n    if (jj_scan_token(FALSE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_48()\n {\n    if (jj_3R_49()) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_50()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_68()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(RBRACKET)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_49()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_59()\n {\n    if (jj_scan_token(MAX)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_54()\n {\n    if (jj_scan_token(MAX)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_44()\n {\n    if (jj_scan_token(REG_IDENTPRIME)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_47()\n {\n    if (jj_3R_49()) return true;\n    Token xsp;\n    if (jj_3_67()) return true;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_67()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_164()\n {\n    if (jj_scan_token(CEIL)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_179()\n {\n    if (jj_scan_token(TRUE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_13()\n {\n    if (jj_3R_35()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_39()\n {\n    if (jj_scan_token(INIT)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_46()\n {\n    if (jj_3R_49()) return true;\n    Token xsp;\n    if (jj_3_66()) return true;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_66()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_48()\n {\n    if (jj_scan_token(TRUE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_58()\n {\n    if (jj_scan_token(MIN)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_53()\n {\n    if (jj_scan_token(MIN)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_38()\n {\n    if (jj_scan_token(REG_IDENT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_86()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_62()) {\n    jj_scanpos = xsp;\n    if (jj_3_63()) {\n    jj_scanpos = xsp;\n    if (jj_3_64()) {\n    jj_scanpos = xsp;\n    if (jj_3_65()) return true;\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_62()\n {\n    if (jj_3R_46()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_163()\n {\n    if (jj_scan_token(FLOOR)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_178()\n {\n    if (jj_3R_83()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_176()\n {\n    if (jj_3R_81()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_158()\n {\n    if (jj_scan_token(DIVIDE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_160()\n {\n    if (jj_3R_79()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_12()\n {\n    if (jj_3R_34()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_33()\n {\n    if (jj_scan_token(SYSTEM)) return true;\n    if (jj_3R_86()) return true;\n    if (jj_scan_token(ENDSYSTEM)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_51()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_45()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_84()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_155()\n {\n    if (jj_scan_token(MINUS)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_57()\n {\n    if (jj_3R_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_162()\n {\n    if (jj_scan_token(MAX)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_52()\n {\n    if (jj_3R_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_157()\n {\n    if (jj_scan_token(TIMES)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_81()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_177()) {\n    jj_scanpos = xsp;\n    if (jj_3_178()) {\n    jj_scanpos = xsp;\n    if (jj_3_179()) {\n    jj_scanpos = xsp;\n    if (jj_3_180()) {\n    jj_scanpos = xsp;\n    if (jj_3_181()) return true;\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_45()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_52()) {\n    jj_scanpos = xsp;\n    if (jj_3_53()) {\n    jj_scanpos = xsp;\n    if (jj_3_54()) {\n    jj_scanpos = xsp;\n    if (jj_3_55()) {\n    jj_scanpos = xsp;\n    if (jj_3_56()) return true;\n    }\n    }\n    }\n    }\n    if (jj_scan_token(EQ)) return true;\n    xsp = jj_scanpos;\n    if (jj_3_57()) {\n    jj_scanpos = xsp;\n    if (jj_3_58()) {\n    jj_scanpos = xsp;\n    if (jj_3_59()) {\n    jj_scanpos = xsp;\n    if (jj_3_60()) {\n    jj_scanpos = xsp;\n    if (jj_3_61()) return true;\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_177()\n {\n    if (jj_3R_82()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_156()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_157()) {\n    jj_scanpos = xsp;\n    if (jj_3_158()) return true;\n    }\n    if (jj_3R_78()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_43()\n {\n    if (jj_scan_token(PLUS)) return true;\n    if (jj_3R_41()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_85()\n {\n    if (jj_3R_45()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_51()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_154()\n {\n    if (jj_scan_token(PLUS)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_11()\n {\n    if (jj_3R_33()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_151()\n {\n    if (jj_3R_75()) return true;\n    if (jj_3R_76()) return true;\n    if (jj_3R_75()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_147()) jj_scanpos = xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_148()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_46()\n {\n    if (jj_scan_token(AND)) return true;\n    if (jj_3R_43()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_80()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_175()) {\n    jj_scanpos = xsp;\n    if (jj_3_176()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_175()\n {\n    if (jj_3R_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_153()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_154()) {\n    jj_scanpos = xsp;\n    if (jj_3_155()) return true;\n    }\n    if (jj_3R_77()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_41()\n {\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(COLON)) return true;\n    if (jj_scan_token(BOOL)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_39()) jj_scanpos = xsp;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_32()\n {\n    if (jj_scan_token(MODULE)) return true;\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_85()) return true;\n    if (jj_scan_token(RBRACKET)) return true;\n    if (jj_scan_token(ENDMODULE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_161()\n {\n    if (jj_scan_token(MIN)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_37()\n {\n    if (jj_3R_40()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_170()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_161()) {\n    jj_scanpos = xsp;\n    if (jj_3_162()) {\n    jj_scanpos = xsp;\n    if (jj_3_163()) {\n    jj_scanpos = xsp;\n    if (jj_3_164()) return true;\n    }\n    }\n    }\n    if (jj_scan_token(LPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_79()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_173()) {\n    jj_scanpos = xsp;\n    if (jj_3_174()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_173()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_170()) {\n    jj_scanpos = xsp;\n    if (jj_3_171()) return true;\n    }\n    if (jj_3R_37()) return true;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_172()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_43()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_49()) {\n    jj_scanpos = xsp;\n    if (jj_3_50()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_49()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_44()) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_78()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_159()) {\n    jj_scanpos = xsp;\n    if (jj_3_160()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_159()\n {\n    if (jj_scan_token(MINUS)) return true;\n    if (jj_3R_79()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_45()\n {\n    if (jj_3R_41()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_43()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_23()\n {\n    if (jj_scan_token(CTMC)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_10()\n {\n    if (jj_3R_32()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_42()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_47()) {\n    jj_scanpos = xsp;\n    if (jj_3_48()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_47()\n {\n    if (jj_3R_43()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_46()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_42()\n {\n    if (jj_3R_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_77()\n {\n    if (jj_3R_78()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_156()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_36()\n {\n    if (jj_3R_39()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_22()\n {\n    if (jj_scan_token(MDP)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_41()\n {\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(COLON)) return true;\n    if (jj_3R_42()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_30()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_9()\n {\n    if (jj_3R_31()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_75()\n {\n    if (jj_3R_77()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_153()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_143()\n {\n    if (jj_3R_72()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_88()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_44()) {\n    jj_scanpos = xsp;\n    if (jj_3_45()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_44()\n {\n    if (jj_3R_42()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_152()\n {\n    if (jj_3R_75()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_25()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_21()\n {\n    if (jj_scan_token(DTMC)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_26()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_40()\n {\n    if (jj_scan_token(LBRACKET)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_42()) jj_scanpos = xsp;\n    if (jj_scan_token(RBRACKET)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(RARROW)) return true;\n    if (jj_3R_88()) return true;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_24()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_27()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_38()\n {\n    if (jj_scan_token(INIT)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_149()\n {\n    if (jj_scan_token(DOTS)) return true;\n    if (jj_3R_75()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_39()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_40()) {\n    jj_scanpos = xsp;\n    if (jj_3_41()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_40()\n {\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(COLON)) return true;\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(DOTS)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(RBRACKET)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_38()) jj_scanpos = xsp;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_8()\n {\n    if (jj_3R_30()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_148()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_75()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_149()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3_20()\n {\n    if (jj_scan_token(STOCHASTIC)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_29()\n {\n    if (jj_scan_token(PROB)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_31()\n {\n    if (jj_scan_token(MODULE)) return true;\n    if (jj_3R_38()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_36()) { jj_scanpos = xsp; break; }\n    }\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_37()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(ENDMODULE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_147()\n {\n    if (jj_scan_token(DOTS)) return true;\n    if (jj_3R_75()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_115()\n {\n    if (jj_3R_64()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_17()\n {\n    if (jj_3R_36()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_30()\n {\n    if (jj_scan_token(GLOBAL)) return true;\n    if (jj_3R_39()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_28()\n {\n    if (jj_scan_token(RATE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_7()\n {\n    if (jj_3R_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_35()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_28()) {\n    jj_scanpos = xsp;\n    if (jj_3_29()) return true;\n    }\n    if (jj_3R_38()) return true;\n    xsp = jj_scanpos;\n    if (jj_3_30()) jj_scanpos = xsp;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_91()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_150()) {\n    jj_scanpos = xsp;\n    if (jj_3_151()) {\n    jj_scanpos = xsp;\n    if (jj_3_152()) return true;\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_150()\n {\n    if (jj_3R_75()) return true;\n    if (jj_3R_57()) return true;\n    if (jj_3R_75()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_145()\n {\n    if (jj_scan_token(AND)) return true;\n    if (jj_3R_74()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_34()\n {\n    if (jj_scan_token(CONST)) return true;\n    if (jj_3R_38()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_27()) jj_scanpos = xsp;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_33()\n {\n    if (jj_scan_token(CONST)) return true;\n    if (jj_scan_token(BOOL)) return true;\n    if (jj_3R_38()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_26()) jj_scanpos = xsp;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_32()\n {\n    if (jj_scan_token(CONST)) return true;\n    if (jj_scan_token(DOUBLE)) return true;\n    if (jj_3R_38()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_25()) jj_scanpos = xsp;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_29()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_31()) {\n    jj_scanpos = xsp;\n    if (jj_3_32()) {\n    jj_scanpos = xsp;\n    if (jj_3_33()) {\n    jj_scanpos = xsp;\n    if (jj_3_34()) {\n    jj_scanpos = xsp;\n    if (jj_3_35()) return true;\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_31()\n {\n    if (jj_scan_token(CONST)) return true;\n    if (jj_scan_token(INT)) return true;\n    if (jj_3R_38()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_24()) jj_scanpos = xsp;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_19()\n {\n    if (jj_scan_token(NONDETERMINISTIC)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_144()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_72()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_16()\n {\n    if (jj_3R_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_6()\n {\n    if (jj_3R_28()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_146()\n {\n    if (jj_scan_token(NOT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_28()\n {\n    if (jj_scan_token(LABEL)) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_74()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_146()) jj_scanpos = xsp;\n    if (jj_3R_91()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_141()\n {\n    if (jj_3R_71()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_27()\n {\n    if (jj_scan_token(FORMULA)) return true;\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_92()\n {\n    if (jj_3R_74()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_145()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_15()\n {\n    if (jj_3R_28()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_14()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_15()) {\n    jj_scanpos = xsp;\n    if (jj_3_16()) {\n    jj_scanpos = xsp;\n    if (jj_3_17()) return true;\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_5()\n {\n    if (jj_3R_27()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_18()\n {\n    if (jj_scan_token(PROBABILISTIC)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_26()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_18()) {\n    jj_scanpos = xsp;\n    if (jj_3_19()) {\n    jj_scanpos = xsp;\n    if (jj_3_20()) {\n    jj_scanpos = xsp;\n    if (jj_3_21()) {\n    jj_scanpos = xsp;\n    if (jj_3_22()) {\n    jj_scanpos = xsp;\n    if (jj_3_23()) return true;\n    }\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_72()\n {\n    if (jj_3R_92()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_144()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3_139()\n {\n    if (jj_3R_70()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_73()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_142()) {\n    jj_scanpos = xsp;\n    if (jj_3_143()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_142()\n {\n    if (jj_3R_72()) return true;\n    if (jj_scan_token(QMARK)) return true;\n    if (jj_3R_72()) return true;\n    if (jj_scan_token(COLON)) return true;\n    if (jj_3R_73()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_37()\n {\n    if (jj_3R_73()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_113()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_3R_36()) return true;\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_137()\n {\n    if (jj_3R_69()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_25()\n {\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_14()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(0)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_3()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_4()) {\n    jj_scanpos = xsp;\n    if (jj_3_5()) {\n    jj_scanpos = xsp;\n    if (jj_3_6()) {\n    jj_scanpos = xsp;\n    if (jj_3_7()) {\n    jj_scanpos = xsp;\n    if (jj_3_8()) {\n    jj_scanpos = xsp;\n    if (jj_3_9()) {\n    jj_scanpos = xsp;\n    if (jj_3_10()) {\n    jj_scanpos = xsp;\n    if (jj_3_11()) {\n    jj_scanpos = xsp;\n    if (jj_3_12()) {\n    jj_scanpos = xsp;\n    if (jj_3_13()) return true;\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_4()\n {\n    if (jj_3R_26()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_129()\n {\n    if (jj_scan_token(41)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_71()\n {\n    if (jj_3R_91()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_24()\n {\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_3()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(0)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_2()\n {\n    if (jj_3R_25()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_70()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_140()) {\n    jj_scanpos = xsp;\n    if (jj_3_141()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_140()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_36()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_69()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_138()) {\n    jj_scanpos = xsp;\n    if (jj_3_139()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_138()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_1()\n {\n    if (jj_3R_24()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_128()\n {\n    if (jj_3R_67()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_68()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_136()) {\n    jj_scanpos = xsp;\n    if (jj_3_137()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_117()\n {\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_136()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_scan_token(INIT)) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_108()\n {\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_132()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_scan_token(MAX)) return true;\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_94()\n {\n    if (jj_3R_62()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_67()\n {\n    if (jj_scan_token(FUTURE)) return true;\n    if (jj_3R_36()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_103()\n {\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_127()\n {\n    if (jj_3R_66()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_112()\n {\n    if (jj_scan_token(S)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_66()\n {\n    if (jj_scan_token(INST)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_107()\n {\n    if (jj_scan_token(GE)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_65()\n {\n    if (jj_scan_token(CUMUL)) return true;\n    if (jj_scan_token(LE)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_174()\n {\n    if (jj_3R_80()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_135()\n {\n    if (jj_3R_68()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_116()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_102()\n {\n    if (jj_scan_token(GE)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_130()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_131()) {\n    jj_scanpos = xsp;\n    if (jj_3_132()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_131()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_scan_token(MIN)) return true;\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_133()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_3R_36()) return true;\n    if (jj_scan_token(RBRACE)) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_130()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_126()\n {\n    if (jj_3R_65()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_93()\n {\n    if (jj_3R_61()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_125()\n {\n    if (jj_scan_token(RMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_124()\n {\n    if (jj_scan_token(RMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_122()\n {\n    if (jj_scan_token(MAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_121()\n {\n    if (jj_scan_token(MIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_123()\n {\n    if (jj_scan_token(R)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_118()) jj_scanpos = xsp;\n    xsp = jj_scanpos;\n    if (jj_3_119()) {\n    jj_scanpos = xsp;\n    if (jj_3_120()) {\n    jj_scanpos = xsp;\n    if (jj_3_121()) {\n    jj_scanpos = xsp;\n    if (jj_3_122()) return true;\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_118()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_116()) {\n    jj_scanpos = xsp;\n    if (jj_3_117()) return true;\n    }\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_119()\n {\n    if (jj_3R_57()) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_120()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_64()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_134()) {\n    jj_scanpos = xsp;\n    if (jj_3_135()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_106()\n {\n    if (jj_scan_token(LE)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_134()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_123()) {\n    jj_scanpos = xsp;\n    if (jj_3_124()) {\n    jj_scanpos = xsp;\n    if (jj_3_125()) return true;\n    }\n    }\n    if (jj_scan_token(LBRACKET)) return true;\n    xsp = jj_scanpos;\n    if (jj_3_126()) {\n    jj_scanpos = xsp;\n    if (jj_3_127()) {\n    jj_scanpos = xsp;\n    if (jj_3_128()) {\n    jj_scanpos = xsp;\n    if (jj_3_129()) return true;\n    }\n    }\n    }\n    xsp = jj_scanpos;\n    if (jj_3_133()) jj_scanpos = xsp;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_111()\n {\n    if (jj_scan_token(S)) return true;\n    if (jj_3R_57()) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_110()\n {\n    if (jj_scan_token(GLOB)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_63()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_114()) {\n    jj_scanpos = xsp;\n    if (jj_3_115()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_114()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_111()) {\n    jj_scanpos = xsp;\n    if (jj_3_112()) return true;\n    }\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_36()) return true;\n    xsp = jj_scanpos;\n    if (jj_3_113()) jj_scanpos = xsp;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_92()\n {\n    if (jj_3R_60()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_105()\n {\n    if (jj_scan_token(GLOB)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_101()\n {\n    if (jj_scan_token(LE)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_109()\n {\n    if (jj_scan_token(FUTURE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_62()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_109()) {\n    jj_scanpos = xsp;\n    if (jj_3_110()) return true;\n    }\n    if (jj_3R_36()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_104()\n {\n    if (jj_scan_token(FUTURE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_97()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_scan_token(MAX)) return true;\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_61()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_104()) {\n    jj_scanpos = xsp;\n    if (jj_3_105()) return true;\n    }\n    xsp = jj_scanpos;\n    if (jj_3_106()) {\n    jj_scanpos = xsp;\n    if (jj_3_107()) {\n    jj_scanpos = xsp;\n    if (jj_3_108()) return true;\n    }\n    }\n    if (jj_3R_36()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_172()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_60()\n {\n    if (jj_3R_36()) return true;\n    if (jj_scan_token(UNTIL)) return true;\n    if (jj_3R_36()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_91()\n {\n    if (jj_3R_59()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_59()\n {\n    if (jj_3R_36()) return true;\n    if (jj_scan_token(UNTIL)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_101()) {\n    jj_scanpos = xsp;\n    if (jj_3_102()) {\n    jj_scanpos = xsp;\n    if (jj_3_103()) return true;\n    }\n    }\n    if (jj_3R_36()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_58()\n {\n    if (jj_scan_token(NEXT)) return true;\n    if (jj_3R_36()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_100()\n {\n    if (jj_3R_63()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_95()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_96()) {\n    jj_scanpos = xsp;\n    if (jj_3_97()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_96()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_scan_token(MIN)) return true;\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_98()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_3R_36()) return true;\n    if (jj_scan_token(RBRACE)) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_95()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_90()\n {\n    if (jj_3R_58()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_89()\n {\n    if (jj_scan_token(PMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_88()\n {\n    if (jj_scan_token(PMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_87()\n {\n    if (jj_scan_token(P)) return true;\n    if (jj_scan_token(MAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_86()\n {\n    if (jj_scan_token(P)) return true;\n    if (jj_scan_token(MIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_82()\n {\n    if (jj_scan_token(AND)) return true;\n    if (jj_3R_56()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_85()\n {\n    if (jj_scan_token(P)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_169()\n {\n    if (jj_scan_token(CEIL)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_84()\n {\n    if (jj_scan_token(P)) return true;\n    if (jj_3R_57()) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_90()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_99()) {\n    jj_scanpos = xsp;\n    if (jj_3_100()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_99()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_84()) {\n    jj_scanpos = xsp;\n    if (jj_3_85()) {\n    jj_scanpos = xsp;\n    if (jj_3_86()) {\n    jj_scanpos = xsp;\n    if (jj_3_87()) {\n    jj_scanpos = xsp;\n    if (jj_3_88()) {\n    jj_scanpos = xsp;\n    if (jj_3_89()) return true;\n    }\n    }\n    }\n    }\n    }\n    if (jj_scan_token(LBRACKET)) return true;\n    xsp = jj_scanpos;\n    if (jj_3_90()) {\n    jj_scanpos = xsp;\n    if (jj_3_91()) {\n    jj_scanpos = xsp;\n    if (jj_3_92()) {\n    jj_scanpos = xsp;\n    if (jj_3_93()) {\n    jj_scanpos = xsp;\n    if (jj_3_94()) return true;\n    }\n    }\n    }\n    }\n    xsp = jj_scanpos;\n    if (jj_3_98()) jj_scanpos = xsp;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_77()\n {\n    if (jj_3R_53()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_81()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_55()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_83()\n {\n    if (jj_scan_token(NOT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_56()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_83()) jj_scanpos = xsp;\n    if (jj_3R_90()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_80()\n {\n    if (jj_scan_token(IMPLIES)) return true;\n    if (jj_3R_54()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_55()\n {\n    if (jj_3R_56()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_82()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_168()\n {\n    if (jj_scan_token(FLOOR)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_54()\n {\n    if (jj_3R_55()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_81()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_87()\n {\n    if (jj_3R_54()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_80()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3_167()\n {\n    if (jj_scan_token(MAX)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_36()\n {\n    if (jj_3R_87()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_70()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_50()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_78()\n {\n    if (jj_3R_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_71()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_50()) return true;\n    if (jj_scan_token(RENAME)) return true;\n    if (jj_3R_50()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_166()\n {\n    if (jj_scan_token(MIN)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_76()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_38()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_35()\n {\n    if (jj_scan_token(INIT)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(ENDINIT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_68()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_50()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_65()\n {\n    if (jj_3R_49()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_79()\n {\n    if (jj_scan_token(LBRACKET)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_78()) jj_scanpos = xsp;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_53()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_79()) jj_scanpos = xsp;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(COLON)) return true;\n    if (jj_3R_37()) return true;\n    if (jj_scan_token(SEMICOLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_83()\n {\n    if (jj_scan_token(REG_DOUBLE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_187()\n {\n    if (jj_scan_token(LE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_34()\n {\n    if (jj_scan_token(REWARDS)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_76()) jj_scanpos = xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_77()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(ENDREWARDS)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_165()\n {\n    if (jj_3R_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_186()\n {\n    if (jj_scan_token(GE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_82()\n {\n    if (jj_scan_token(REG_INT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_52()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_86()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_75()\n {\n    if (jj_3R_52()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_64()\n {\n    if (jj_3R_48()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_185()\n {\n    if (jj_scan_token(LT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_51()\n {\n    if (jj_3R_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_72()\n {\n    if (jj_scan_token(DIVIDE)) return true;\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_3R_50()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_70()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_69()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_72()) {\n    jj_scanpos = xsp;\n    if (jj_3_73()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_184()\n {\n    if (jj_scan_token(GT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_61()\n {\n    if (jj_scan_token(CEIL)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_57()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_184()) {\n    jj_scanpos = xsp;\n    if (jj_3_185()) {\n    jj_scanpos = xsp;\n    if (jj_3_186()) {\n    jj_scanpos = xsp;\n    if (jj_3_187()) return true;\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_50()\n {\n    if (jj_3R_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_56()\n {\n    if (jj_scan_token(CEIL)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_183()\n {\n    if (jj_scan_token(NE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_171()\n {\n    if (jj_scan_token(FUNC)) return true;\n    if (jj_scan_token(LPARENTH)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_165()) {\n    jj_scanpos = xsp;\n    if (jj_3_166()) {\n    jj_scanpos = xsp;\n    if (jj_3_167()) {\n    jj_scanpos = xsp;\n    if (jj_3_168()) {\n    jj_scanpos = xsp;\n    if (jj_3_169()) return true;\n    }\n    }\n    }\n    }\n    if (jj_scan_token(COMMA)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_181()\n {\n    if (jj_3R_84()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_67()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_49()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_89()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_74()) {\n    jj_scanpos = xsp;\n    if (jj_3_75()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_74()\n {\n    if (jj_3R_51()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_182()\n {\n    if (jj_scan_token(EQ)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_76()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3_182()) {\n    jj_scanpos = xsp;\n    if (jj_3_183()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3_66()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_49()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_60()\n {\n    if (jj_scan_token(FLOOR)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_50()\n {\n    if (jj_3R_44()) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_37()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_55()\n {\n    if (jj_scan_token(FLOOR)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_73()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_3R_50()) return true;\n    if (jj_scan_token(RENAME)) return true;\n    if (jj_3R_50()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_71()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_49()\n {\n    if (jj_3R_89()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3_69()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_initialized_once = false;\n  /** Generated Token Manager. */\n  static public Prism3To4TokenManager token_source;\n  static SimpleCharStream jj_input_stream;\n  /** Current token. */\n  static public Token token;\n  /** Next token. */\n  static public Token jj_nt;\n  static private int jj_ntk;\n  static private Token jj_scanpos, jj_lastpos;\n  static private int jj_la;\n  static private int jj_gen;\n  static final private int[] jj_la1 = new int[0];\n  static private int[] jj_la1_0;\n  static private int[] jj_la1_1;\n  static private int[] jj_la1_2;\n  static {\n      jj_la1_init_0();\n      jj_la1_init_1();\n      jj_la1_init_2();\n   }\n   private static void jj_la1_init_0() {\n      jj_la1_0 = new int[] {};\n   }\n   private static void jj_la1_init_1() {\n      jj_la1_1 = new int[] {};\n   }\n   private static void jj_la1_init_2() {\n      jj_la1_2 = new int[] {};\n   }\n  static final private JJCalls[] jj_2_rtns = new JJCalls[187];\n  static private boolean jj_rescan = false;\n  static private int jj_gc = 0;\n\n  /** Constructor with InputStream. */\n  public Prism3To4(java.io.InputStream stream) {\n     this(stream, null);\n  }\n  /** Constructor with InputStream and supplied encoding */\n  public Prism3To4(java.io.InputStream stream, String encoding) {\n    if (jj_initialized_once) {\n      System.out.println(\"ERROR: Second call to constructor of static parser.  \");\n      System.out.println(\"       You must either use ReInit() or set the JavaCC option STATIC to false\");\n      System.out.println(\"       during parser generation.\");\n      throw new Error();\n    }\n    jj_initialized_once = true;\n    try { jj_input_stream = new SimpleCharStream(stream, encoding, 1, 1); } catch(java.io.UnsupportedEncodingException e) { throw new RuntimeException(e); }\n    token_source = new Prism3To4TokenManager(jj_input_stream);\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Reinitialise. */\n  static public void ReInit(java.io.InputStream stream) {\n     ReInit(stream, null);\n  }\n  /** Reinitialise. */\n  static public void ReInit(java.io.InputStream stream, String encoding) {\n    try { jj_input_stream.ReInit(stream, encoding, 1, 1); } catch(java.io.UnsupportedEncodingException e) { throw new RuntimeException(e); }\n    token_source.ReInit(jj_input_stream);\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < 0; i++) jj_la1[i] = -1;\n    for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Constructor. */\n  public Prism3To4(java.io.Reader stream) {\n    if (jj_initialized_once) {\n      System.out.println(\"ERROR: Second call to constructor of static parser. \");\n      System.out.println(\"       You must either use ReInit() or set the JavaCC option STATIC to false\");\n      System.out.println(\"       during parser generation.\");\n      throw new Error();\n    }\n    jj_initialized_once = true;\n    jj_input_stream = new SimpleCharStream(stream, 1, 1);\n    token_source = new Prism3To4TokenManager(jj_input_stream);\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Reinitialise. */\n  static public void ReInit(java.io.Reader stream) {\n    jj_input_stream.ReInit(stream, 1, 1);\n    token_source.ReInit(jj_input_stream);\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Constructor with generated Token Manager. */\n  public Prism3To4(Prism3To4TokenManager tm) {\n    if (jj_initialized_once) {\n      System.out.println(\"ERROR: Second call to constructor of static parser. \");\n      System.out.println(\"       You must either use ReInit() or set the JavaCC option STATIC to false\");\n      System.out.println(\"       during parser generation.\");\n      throw new Error();\n    }\n    jj_initialized_once = true;\n    token_source = tm;\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Reinitialise. */\n  public void ReInit(Prism3To4TokenManager tm) {\n    token_source = tm;\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  static private Token jj_consume_token(int kind) throws ParseException {\n    Token oldToken;\n    if ((oldToken = token).next != null) token = token.next;\n    else token = token.next = token_source.getNextToken();\n    jj_ntk = -1;\n    if (token.kind == kind) {\n      jj_gen++;\n      if (++jj_gc > 100) {\n        jj_gc = 0;\n        for (int i = 0; i < jj_2_rtns.length; i++) {\n          JJCalls c = jj_2_rtns[i];\n          while (c != null) {\n            if (c.gen < jj_gen) c.first = null;\n            c = c.next;\n          }\n        }\n      }\n      return token;\n    }\n    token = oldToken;\n    jj_kind = kind;\n    throw generateParseException();\n  }\n\n  @SuppressWarnings(\"serial\")\n  static private final class LookaheadSuccess extends java.lang.Error { }\n  static final private LookaheadSuccess jj_ls = new LookaheadSuccess();\n  static private boolean jj_scan_token(int kind) {\n    if (jj_scanpos == jj_lastpos) {\n      jj_la--;\n      if (jj_scanpos.next == null) {\n        jj_lastpos = jj_scanpos = jj_scanpos.next = token_source.getNextToken();\n      } else {\n        jj_lastpos = jj_scanpos = jj_scanpos.next;\n      }\n    } else {\n      jj_scanpos = jj_scanpos.next;\n    }\n    if (jj_rescan) {\n      int i = 0; Token tok = token;\n      while (tok != null && tok != jj_scanpos) { i++; tok = tok.next; }\n      if (tok != null) jj_add_error_token(kind, i);\n    }\n    if (jj_scanpos.kind != kind) return true;\n    if (jj_la == 0 && jj_scanpos == jj_lastpos) throw jj_ls;\n    return false;\n  }\n\n\n/** Get the next Token. */\n  static final public Token getNextToken() {\n    if (token.next != null) token = token.next;\n    else token = token.next = token_source.getNextToken();\n    jj_ntk = -1;\n    jj_gen++;\n    return token;\n  }\n\n/** Get the specific Token. */\n  static final public Token getToken(int index) {\n    Token t = token;\n    for (int i = 0; i < index; i++) {\n      if (t.next != null) t = t.next;\n      else t = t.next = token_source.getNextToken();\n    }\n    return t;\n  }\n\n  static private int jj_ntk_f() {\n    if ((jj_nt=token.next) == null)\n      return (jj_ntk = (token.next=token_source.getNextToken()).kind);\n    else\n      return (jj_ntk = jj_nt.kind);\n  }\n\n  static private java.util.List<int[]> jj_expentries = new java.util.ArrayList<int[]>();\n  static private int[] jj_expentry;\n  static private int jj_kind = -1;\n  static private int[] jj_lasttokens = new int[100];\n  static private int jj_endpos;\n\n  static private void jj_add_error_token(int kind, int pos) {\n    if (pos >= 100) return;\n    if (pos == jj_endpos + 1) {\n      jj_lasttokens[jj_endpos++] = kind;\n    } else if (jj_endpos != 0) {\n      jj_expentry = new int[jj_endpos];\n      for (int i = 0; i < jj_endpos; i++) {\n        jj_expentry[i] = jj_lasttokens[i];\n      }\n      jj_entries_loop: for (java.util.Iterator<?> it = jj_expentries.iterator(); it.hasNext();) {\n        int[] oldentry = (int[])(it.next());\n        if (oldentry.length == jj_expentry.length) {\n          for (int i = 0; i < jj_expentry.length; i++) {\n            if (oldentry[i] != jj_expentry[i]) {\n              continue jj_entries_loop;\n            }\n          }\n          jj_expentries.add(jj_expentry);\n          break jj_entries_loop;\n        }\n      }\n      if (pos != 0) jj_lasttokens[(jj_endpos = pos) - 1] = kind;\n    }\n  }\n\n  /** Generate ParseException. */\n  static public ParseException generateParseException() {\n    jj_expentries.clear();\n    boolean[] la1tokens = new boolean[80];\n    if (jj_kind >= 0) {\n      la1tokens[jj_kind] = true;\n      jj_kind = -1;\n    }\n    for (int i = 0; i < 0; i++) {\n      if (jj_la1[i] == jj_gen) {\n        for (int j = 0; j < 32; j++) {\n          if ((jj_la1_0[i] & (1<<j)) != 0) {\n            la1tokens[j] = true;\n          }\n          if ((jj_la1_1[i] & (1<<j)) != 0) {\n            la1tokens[32+j] = true;\n          }\n          if ((jj_la1_2[i] & (1<<j)) != 0) {\n            la1tokens[64+j] = true;\n          }\n        }\n      }\n    }\n    for (int i = 0; i < 80; i++) {\n      if (la1tokens[i]) {\n        jj_expentry = new int[1];\n        jj_expentry[0] = i;\n        jj_expentries.add(jj_expentry);\n      }\n    }\n    jj_endpos = 0;\n    jj_rescan_token();\n    jj_add_error_token(0, 0);\n    int[][] exptokseq = new int[jj_expentries.size()][];\n    for (int i = 0; i < jj_expentries.size(); i++) {\n      exptokseq[i] = jj_expentries.get(i);\n    }\n    return new ParseException(token, exptokseq, tokenImage);\n  }\n\n  /** Enable tracing. */\n  static final public void enable_tracing() {\n  }\n\n  /** Disable tracing. */\n  static final public void disable_tracing() {\n  }\n\n  static private void jj_rescan_token() {\n    jj_rescan = true;\n    for (int i = 0; i < 187; i++) {\n    try {\n      JJCalls p = jj_2_rtns[i];\n      do {\n        if (p.gen > jj_gen) {\n          jj_la = p.arg; jj_lastpos = jj_scanpos = p.first;\n          switch (i) {\n            case 0: jj_3_1(); break;\n            case 1: jj_3_2(); break;\n            case 2: jj_3_3(); break;\n            case 3: jj_3_4(); break;\n            case 4: jj_3_5(); break;\n            case 5: jj_3_6(); break;\n            case 6: jj_3_7(); break;\n            case 7: jj_3_8(); break;\n            case 8: jj_3_9(); break;\n            case 9: jj_3_10(); break;\n            case 10: jj_3_11(); break;\n            case 11: jj_3_12(); break;\n            case 12: jj_3_13(); break;\n            case 13: jj_3_14(); break;\n            case 14: jj_3_15(); break;\n            case 15: jj_3_16(); break;\n            case 16: jj_3_17(); break;\n            case 17: jj_3_18(); break;\n            case 18: jj_3_19(); break;\n            case 19: jj_3_20(); break;\n            case 20: jj_3_21(); break;\n            case 21: jj_3_22(); break;\n            case 22: jj_3_23(); break;\n            case 23: jj_3_24(); break;\n            case 24: jj_3_25(); break;\n            case 25: jj_3_26(); break;\n            case 26: jj_3_27(); break;\n            case 27: jj_3_28(); break;\n            case 28: jj_3_29(); break;\n            case 29: jj_3_30(); break;\n            case 30: jj_3_31(); break;\n            case 31: jj_3_32(); break;\n            case 32: jj_3_33(); break;\n            case 33: jj_3_34(); break;\n            case 34: jj_3_35(); break;\n            case 35: jj_3_36(); break;\n            case 36: jj_3_37(); break;\n            case 37: jj_3_38(); break;\n            case 38: jj_3_39(); break;\n            case 39: jj_3_40(); break;\n            case 40: jj_3_41(); break;\n            case 41: jj_3_42(); break;\n            case 42: jj_3_43(); break;\n            case 43: jj_3_44(); break;\n            case 44: jj_3_45(); break;\n            case 45: jj_3_46(); break;\n            case 46: jj_3_47(); break;\n            case 47: jj_3_48(); break;\n            case 48: jj_3_49(); break;\n            case 49: jj_3_50(); break;\n            case 50: jj_3_51(); break;\n            case 51: jj_3_52(); break;\n            case 52: jj_3_53(); break;\n            case 53: jj_3_54(); break;\n            case 54: jj_3_55(); break;\n            case 55: jj_3_56(); break;\n            case 56: jj_3_57(); break;\n            case 57: jj_3_58(); break;\n            case 58: jj_3_59(); break;\n            case 59: jj_3_60(); break;\n            case 60: jj_3_61(); break;\n            case 61: jj_3_62(); break;\n            case 62: jj_3_63(); break;\n            case 63: jj_3_64(); break;\n            case 64: jj_3_65(); break;\n            case 65: jj_3_66(); break;\n            case 66: jj_3_67(); break;\n            case 67: jj_3_68(); break;\n            case 68: jj_3_69(); break;\n            case 69: jj_3_70(); break;\n            case 70: jj_3_71(); break;\n            case 71: jj_3_72(); break;\n            case 72: jj_3_73(); break;\n            case 73: jj_3_74(); break;\n            case 74: jj_3_75(); break;\n            case 75: jj_3_76(); break;\n            case 76: jj_3_77(); break;\n            case 77: jj_3_78(); break;\n            case 78: jj_3_79(); break;\n            case 79: jj_3_80(); break;\n            case 80: jj_3_81(); break;\n            case 81: jj_3_82(); break;\n            case 82: jj_3_83(); break;\n            case 83: jj_3_84(); break;\n            case 84: jj_3_85(); break;\n            case 85: jj_3_86(); break;\n            case 86: jj_3_87(); break;\n            case 87: jj_3_88(); break;\n            case 88: jj_3_89(); break;\n            case 89: jj_3_90(); break;\n            case 90: jj_3_91(); break;\n            case 91: jj_3_92(); break;\n            case 92: jj_3_93(); break;\n            case 93: jj_3_94(); break;\n            case 94: jj_3_95(); break;\n            case 95: jj_3_96(); break;\n            case 96: jj_3_97(); break;\n            case 97: jj_3_98(); break;\n            case 98: jj_3_99(); break;\n            case 99: jj_3_100(); break;\n            case 100: jj_3_101(); break;\n            case 101: jj_3_102(); break;\n            case 102: jj_3_103(); break;\n            case 103: jj_3_104(); break;\n            case 104: jj_3_105(); break;\n            case 105: jj_3_106(); break;\n            case 106: jj_3_107(); break;\n            case 107: jj_3_108(); break;\n            case 108: jj_3_109(); break;\n            case 109: jj_3_110(); break;\n            case 110: jj_3_111(); break;\n            case 111: jj_3_112(); break;\n            case 112: jj_3_113(); break;\n            case 113: jj_3_114(); break;\n            case 114: jj_3_115(); break;\n            case 115: jj_3_116(); break;\n            case 116: jj_3_117(); break;\n            case 117: jj_3_118(); break;\n            case 118: jj_3_119(); break;\n            case 119: jj_3_120(); break;\n            case 120: jj_3_121(); break;\n            case 121: jj_3_122(); break;\n            case 122: jj_3_123(); break;\n            case 123: jj_3_124(); break;\n            case 124: jj_3_125(); break;\n            case 125: jj_3_126(); break;\n            case 126: jj_3_127(); break;\n            case 127: jj_3_128(); break;\n            case 128: jj_3_129(); break;\n            case 129: jj_3_130(); break;\n            case 130: jj_3_131(); break;\n            case 131: jj_3_132(); break;\n            case 132: jj_3_133(); break;\n            case 133: jj_3_134(); break;\n            case 134: jj_3_135(); break;\n            case 135: jj_3_136(); break;\n            case 136: jj_3_137(); break;\n            case 137: jj_3_138(); break;\n            case 138: jj_3_139(); break;\n            case 139: jj_3_140(); break;\n            case 140: jj_3_141(); break;\n            case 141: jj_3_142(); break;\n            case 142: jj_3_143(); break;\n            case 143: jj_3_144(); break;\n            case 144: jj_3_145(); break;\n            case 145: jj_3_146(); break;\n            case 146: jj_3_147(); break;\n            case 147: jj_3_148(); break;\n            case 148: jj_3_149(); break;\n            case 149: jj_3_150(); break;\n            case 150: jj_3_151(); break;\n            case 151: jj_3_152(); break;\n            case 152: jj_3_153(); break;\n            case 153: jj_3_154(); break;\n            case 154: jj_3_155(); break;\n            case 155: jj_3_156(); break;\n            case 156: jj_3_157(); break;\n            case 157: jj_3_158(); break;\n            case 158: jj_3_159(); break;\n            case 159: jj_3_160(); break;\n            case 160: jj_3_161(); break;\n            case 161: jj_3_162(); break;\n            case 162: jj_3_163(); break;\n            case 163: jj_3_164(); break;\n            case 164: jj_3_165(); break;\n            case 165: jj_3_166(); break;\n            case 166: jj_3_167(); break;\n            case 167: jj_3_168(); break;\n            case 168: jj_3_169(); break;\n            case 169: jj_3_170(); break;\n            case 170: jj_3_171(); break;\n            case 171: jj_3_172(); break;\n            case 172: jj_3_173(); break;\n            case 173: jj_3_174(); break;\n            case 174: jj_3_175(); break;\n            case 175: jj_3_176(); break;\n            case 176: jj_3_177(); break;\n            case 177: jj_3_178(); break;\n            case 178: jj_3_179(); break;\n            case 179: jj_3_180(); break;\n            case 180: jj_3_181(); break;\n            case 181: jj_3_182(); break;\n            case 182: jj_3_183(); break;\n            case 183: jj_3_184(); break;\n            case 184: jj_3_185(); break;\n            case 185: jj_3_186(); break;\n            case 186: jj_3_187(); break;\n          }\n        }\n        p = p.next;\n      } while (p != null);\n      } catch(LookaheadSuccess ls) { }\n    }\n    jj_rescan = false;\n  }\n\n  static private void jj_save(int index, int xla) {\n    JJCalls p = jj_2_rtns[index];\n    while (p.gen > jj_gen) {\n      if (p.next == null) { p = p.next = new JJCalls(); break; }\n      p = p.next;\n    }\n    p.gen = jj_gen + xla - jj_la; p.first = token; p.arg = xla;\n  }\n\n  static final class JJCalls {\n    int gen;\n    Token first;\n    int arg;\n    JJCalls next;\n  }\n\n}\n\n//-----------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/parser/Prism3To4.jj",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// This is a very stripped down version of the PRISM version 3.x parser\n// used to generate valid code for post-3.x versions of PRISM.\n\n// It fixes 3 things:\n// * appends semicolons to properties in properties files\n// * ensures that updates are parenthesised\n// * replaces the defunct range operator with an equivalent expression\n\noptions {\n\tLOOKAHEAD = 2147483647; // max possible lookahead\n}\n\nPARSER_BEGIN(Prism3To4)\n\npackage parser;\n\nimport java.io.*;\n\n@SuppressWarnings({\"unused\", \"static-access\", \"serial\"})\npublic class Prism3To4\n{\n\tpublic static void main(String[] args) throws ParseException\n\t{\n\t\ttry {\n\t\t\tPrism3To4 p;\n\t\t\tif (args.length > 0) { p = new Prism3To4(new FileInputStream(args[0])); }\n\t\t\telse { p = new Prism3To4(System.in); }\n\t\t\tp.ModulesFileOrPropertiesFile();\n\t\t}\n\t\tcatch (TokenMgrError e) {\n\t\t\tSystem.err.println(\"Syntax error\"+(args.length > 0?\" in \"+args[0]:\"\")+\": \" + e.getMessage()); System.exit(1);\n\t\t}\n\t\tcatch (ParseException e) {\n\t\t\tSystem.err.println(\"Error\"+(args.length > 0?\" in \"+args[0]:\"\")+\": \" + e.getMessage()); System.exit(1);\n\t\t}\n\t\tcatch (FileNotFoundException e) {\n\t\t\tSystem.err.println(e); System.exit(1);\n\t\t}\n\t}\n\t\n\tprivate static void insertTokenBeforeNext(Token t, String s)\n\t{\n\t\tToken tNew=new Token(); tNew.image=s; tNew.specialToken=t.next.specialToken; t.next.specialToken=null; tNew.next=t.next; t.next=tNew;\n\t} \n}\n\n//-----------------------------------------------------------------------------------\n\nPARSER_END(Prism3To4)\n\n// skip (but store) all other white space\n\nSPECIAL_TOKEN :\n{\n\t<WHITESPACE: (\" \"|\"\\t\"|\"\\n\"|\"\\r\")>\n}\n\n// skip (but store) comments\n\nSPECIAL_TOKEN :\n{\n\t<COMMENT: \"//\" (~[\"\\n\",\"\\r\"])* (\"\\n\"|\"\\r\"|\"\\r\\n\")>\n}\n\n// tokens\n\nTOKEN :\n{\n\t// keywords\n\t< BOOL:\t\t\t\t\"bool\" >\n|\t< CONST:\t\t\t\"const\" >\n|\t< CEIL:\t\t\t\t\"ceil\" >\n|\t< CTMC:\t\t\t\t\"ctmc\" >\n|\t< CUMUL:\t\t\t\"C\" >\n|\t< DOUBLE:\t\t\t\"double\" >\n|\t< DTMC:\t\t\t\t\"dtmc\" >\n|\t< ENDINIT:\t\t\t\"endinit\" >\n|\t< ENDMODULE:\t\t\"endmodule\" >\n|\t< ENDREWARDS:\t\t\"endrewards\" >\n|\t< ENDSYSTEM:\t\t\"endsystem\" >\n|\t< FALSE:\t\t\t\"false\" >\n|\t< FLOOR:\t\t\t\"floor\" >\n|\t< FORMULA:\t\t\t\"formula\" >\n|\t< FUNC:\t\t\t\t\"func\" >\n|\t< FUTURE:\t\t\t\"F\" >\n|\t< GLOBAL:\t\t\t\"global\" >\n|\t< GLOB:\t\t\t\t\"G\" >\n|\t< INIT:\t\t\t\t\"init\" >\n|\t< INST:\t\t\t\t\"I\" >\n|\t< INT:\t\t\t\t\"int\" >\n|\t< LABEL:\t\t\t\"label\" >\n|\t< MAX:\t\t\t\t\"max\" >\n|\t< MDP:\t\t\t\t\"mdp\" >\n|\t< MIN:\t\t\t\t\"min\" >\n|\t< MODULE:\t\t\t\"module\" >\n|\t< NEXT:\t\t\t\t\"X\" >\n|\t< NONDETERMINISTIC:\t\"nondeterministic\" >\n|\t< PMAX:\t\t\t\t\"Pmax\" >\n|\t< PMIN:\t\t\t\t\"Pmin\" >\n|\t< P:\t\t\t\t\"P\" >\n|\t< PROBABILISTIC:\t\"probabilistic\" >\n|\t< PROB:\t\t\t\t\"prob\" >\n|\t< RATE:\t\t\t\t\"rate\" >\n|\t< REWARDS:\t\t\t\"rewards\" >\n|\t< RMAX:\t\t\t\t\"Rmax\" >\n|\t< RMIN:\t\t\t\t\"Rmin\" >\n|\t< R:\t\t\t\t\"R\" >\n|\t< S:\t\t\t\t\"S\" >\n|\t< STOCHASTIC:\t\t\"stochastic\" >\n|\t< SYSTEM:\t\t\t\"system\" >\n|\t< TRUE:\t\t\t\t\"true\" >\n|\t< UNTIL:\t\t\t\"U\" >\n\t// punctuation, etc.\n\t// note that \"NOT\" must be the first item of punctuation in this list\n\t// (PrismSyntaxHighlighter relies on this fact)\n|\t< NOT:\t\t\t\"!\" >\n|\t< AND:\t\t\t\"&\" >\n|\t< OR:\t\t\t\"|\" >\n|\t< IMPLIES:\t\t\"=>\" >\n|\t< RARROW:\t\t\"->\" >\n|\t< COLON:\t\t\":\" >\n|\t< SEMICOLON:\t\";\" >\n|\t< COMMA:\t\t\",\" >\n|\t< DOTS:\t\t\t\"..\" >\n|\t< LPARENTH:\t\t\"(\" >\n|\t< RPARENTH:\t\t\")\" >\n|\t< LBRACKET: \t\"[\" >\n|\t< RBRACKET:\t\t\"]\" >\n|\t< LBRACE:\t\t\"{\" >\n|\t< RBRACE:\t\t\"}\" >\n|\t< EQ:\t\t\t\"=\" >\n|\t< NE:\t\t\t\"!=\" >\n|\t< LT:\t\t\t\"<\" >\n|\t< GT:\t\t\t\">\" >\n|\t< LE:\t\t\t\"<=\" >\n|\t< GE:\t\t\t\">=\" >\n|\t< PLUS:\t\t\t\"+\" >\n|\t< MINUS:\t\t\"-\" >\n|\t< TIMES:\t\t\"*\" >\n|\t< DIVIDE:\t\t\"/\" >\n|\t< PRIME:\t\t\"'\" >\n|\t< RENAME:\t\t\"<-\" >\n|\t< QMARK:\t\t\"?\" >\n|\t< DQUOTE:\t\t\"\\\"\" >\n\t// regular expressions\n|\t< REG_INT:\t\t\t([\"1\"-\"9\"]([\"0\"-\"9\"])*)|(\"0\") >\n//|\t< REG_DOUBLE:\t\t<REG_INT>\".\"([\"0\"-\"9\"])+ >\n|\t< REG_DOUBLE:\t\t([\"0\"-\"9\"])*(\".\")?([\"0\"-\"9\"])+([\"e\",\"E\"]([\"-\",\"+\"])?([\"0\"-\"9\"])+)? >\n|\t< REG_IDENTPRIME:\t[\"_\",\"a\"-\"z\",\"A\"-\"Z\"]([\"_\",\"a\"-\"z\",\"A\"-\"Z\",\"0\"-\"9\"])*\"'\" >\n|\t< REG_IDENT:\t\t[\"_\",\"a\"-\"z\",\"A\"-\"Z\"]([\"_\",\"a\"-\"z\",\"A\"-\"Z\",\"0\"-\"9\"])* >\n|\t< PREPROC:\t\t\t\"#\"(~[\"#\"])*\"#\" >\n}\n\n//-----------------------------------------------------------------------------------\n// top-level stuff\n//-----------------------------------------------------------------------------------\n\nvoid ModulesFileOrPropertiesFile() :\n{\n\tToken t = null, ptr, ptr2;\n}\n{\n\t{ t = getToken(1); }\n\t( ModulesFile() | PropertiesFile() )\n\t{\n\t\tptr = t;\n\t\twhile (ptr != null) {\n\t\t\tif (ptr.specialToken != null) {\n\t\t\t\tptr2 = ptr;\n\t\t\t\twhile (ptr2.specialToken != null) ptr2 = ptr2.specialToken;\n\t\t\t\twhile (ptr2 != null) { System.out.print(ptr2.image); ptr2 = ptr2.next; }\n\t\t\t}\n\t\t\tSystem.out.print(ptr.image);\n\t\t\tptr = ptr.next;\n\t\t}\n\t}\n}\n\n// modules file\n\nvoid ModulesFile() : {}\n{\n\t( ( ( ModulesFileType() ) | FormulaDef() | LabelDef() | ConstantDef() | GlobalDecl() | Module() | RenamedModule() | SystemComp() | RewardStruct() | Init() )* <EOF> )\n}\n\n// properties file\n\nvoid PropertiesFile() : {}\n{\n\t( ( /*FormulaDef() |*/ LabelDef() | ConstantDef() | PCTLFormula() { getToken(0).image += \";\"; } \n )* <EOF> )\n}\n\n// a single expression\n\nvoid SingleExpression() : {}\n{\n\t( Expression() <EOF> )\n}\n\n//-----------------------------------------------------------------------------------\n// modules file stuff\n//-----------------------------------------------------------------------------------\n\n// keyword denoting module type (nondeterministic, probabilistic, ...)\n\nvoid ModulesFileType() : {}\n{\n\t( <PROBABILISTIC> | <NONDETERMINISTIC> | <STOCHASTIC> | <DTMC> | <MDP> | <CTMC> )\n}\n\n// formula definition\n\nvoid FormulaDef() : {}\n{\n\t( <FORMULA> Identifier() <EQ> Expression() <SEMICOLON> )\n}\n\n// label definition\n\nvoid LabelDef() : {}\n{\n\t( <LABEL> <DQUOTE> Identifier() <DQUOTE> <EQ> Expression() <SEMICOLON> )\n}\n\n// constant definition\n\nvoid ConstantDef() : {}\n{\n\t( <CONST> <INT> Identifier() (<EQ> Expression())? <SEMICOLON> )\n\t| ( <CONST> <DOUBLE> Identifier() (<EQ> Expression())? <SEMICOLON> )\n\t| ( <CONST> <BOOL> Identifier() (<EQ> Expression())? <SEMICOLON> )\n\t| ( <CONST> Identifier() (<EQ> Expression())? <SEMICOLON> )\n\t| ( ( <RATE> | <PROB> ) Identifier() (<EQ> Expression())? <SEMICOLON> )\n}\n\n// global variable declaration\n\nvoid GlobalDecl() : {}\n{\n\t( <GLOBAL> Declaration() )\n}\n\n// module definition\n\nvoid Module() : {}\n{\n\t( <MODULE> Identifier() ( Declaration() )* ( Command() )* <ENDMODULE> )\n}\n\n// variable declaration\n\nvoid Declaration() : {}\n{\n\t( Identifier() <COLON> <LBRACKET> Expression() <DOTS> Expression() <RBRACKET>\n\t( <INIT> Expression() )? <SEMICOLON> ) | ( Identifier() <COLON> <BOOL> ( <INIT> Expression() )? <SEMICOLON> )\n}\n\n// command definition\n\nvoid Command() : {}\n{\n\t( <LBRACKET> ( Identifier() )? <RBRACKET> Expression() <RARROW> Updates() <SEMICOLON> )\n}\n\nvoid Updates() : {}\n{\n\t( Update() ) | ( ProbUpdate() ( <PLUS> ProbUpdate() )* )\n}\n\nvoid ProbUpdate() : {}\n{\n\t( Expression() <COLON> Update() )\n}\n\nvoid Update() : {}\n{\n\t( UpdateElement() ( <AND> UpdateElement() )* ) | ( <TRUE> )\n}\n\nvoid UpdateElement() :\n{\n\tToken t1, t2;\n}\n{\n\t( <LPARENTH> IdentifierPrime() <EQ> Expression() <RPARENTH> ) | ( { t1=getToken(0); } IdentifierPrime() <EQ> Expression() { t2=getToken(0); } )\n\t{ insertTokenBeforeNext(t1, \"(\"); t2.image += \")\"; } \n}\n\n// module definition (by renaming)\n\nvoid RenamedModule() : {}\n{\n\t( <MODULE> Identifier() <EQ> Identifier() <LBRACKET> Renames() <RBRACKET> <ENDMODULE> )\n}\n\nvoid Renames() : {}\n{\n\t( Rename() ( <COMMA> Rename() )* )\n}\n\nvoid Rename() : {}\n{\n\t((( Identifier() ) | ( <MIN> ) | ( <MAX> ) | ( <FLOOR> ) | ( <CEIL> ))\n\t<EQ>\n\t(( Identifier() ) | ( <MIN> ) | ( <MAX> ) | ( <FLOOR> ) | ( <CEIL> )))\n}\n\n// system composition definition\n\nvoid SystemComp() : {}\n{\n\t( <SYSTEM> SystemParallels() <ENDSYSTEM> )\n}\n\n// system definition component\n\nvoid SystemParallels() : {}\n{\n\t( SystemFullParallel() ) | ( SystemInterleaved() ) | ( SystemParallel() ) | ( SystemHideRename() )\n}\n\n// system definition component (full parallel)\n\nvoid SystemFullParallel() : {}\n{\n\t( SystemHideRename() ( <OR> <OR> SystemHideRename() )+ )\n}\n\n// system definition component (interleaved parallel)\n\nvoid SystemInterleaved() : {}\n{\n\t( SystemHideRename() ( <OR> <OR> <OR> SystemHideRename() )+ )\n}\n\n// system definition component (parallel over set of actions)\n\nvoid SystemParallel() : {}\n{\n\t( SystemHideRename() <OR> <LBRACKET> ( SystemAction() ( <COMMA> SystemAction() )* ) <RBRACKET> <OR> SystemHideRename() )\n}\n\n// system definition component (hiding and renaming)\n\nvoid SystemHideRename() : {}\n{\n\t( SystemAtomic() ( ( ( <DIVIDE> <LBRACE> ( SystemAction() ( <COMMA> SystemAction() )* ) <RBRACE> ) |\n\t( <LBRACE> SystemAction() <RENAME> SystemAction() ( <COMMA> SystemAction() <RENAME> SystemAction() )* <RBRACE> ) ) )* )\n}\n\n// system definition component (bottom level)\n\nvoid SystemAtomic() : {}\n{\n\t( SystemModule() ) | ( SystemBrackets() )\n}\n\n// system definition component (action identifier)\n\nvoid SystemAction() : {}\n{\n\t( Identifier() )\n}\n\n// system definition component (module identifier)\n\nvoid SystemModule() : {}\n{\n\t( Identifier() )\n}\n\n// system definition component (brackets)\n\nvoid SystemBrackets() : {}\n{\n\t( <LPARENTH> SystemParallels() <RPARENTH> )\n}\n\n// reward structure\n\nvoid RewardStruct() : {}\n{\n\t( ( <REWARDS> (<DQUOTE> Identifier() <DQUOTE>)? ( RewardStructItem() )* <ENDREWARDS> ) )\n}\n\n// single line (item) of state-based rewards structure\n\nvoid RewardStructItem() : {}\n{\n\t( ( <LBRACKET> ( Identifier() )? <RBRACKET> )? Expression() <COLON> Expression() <SEMICOLON> )\n}\n\n// multiple initial states\n\nvoid Init() : {}\n{\n\t( ( <INIT> Expression() <ENDINIT> ) )\n}\n\n//-----------------------------------------------------------------------------------\n// properties file stuff\n//-----------------------------------------------------------------------------------\n\n// pctl formula\n\nvoid PCTLFormula() : {}\n{\n\t( PCTLImplies() )\n}\n\nvoid PCTLImplies() : {}\n{\n\t( PCTLOr() ( <IMPLIES> PCTLOr() )? )\n}\n\nvoid PCTLOr() : {}\n{\n\t( PCTLAnd() ( <OR> PCTLAnd() )* )\n}\n\nvoid PCTLAnd() : {}\n{\n\t( PCTLNot() ( <AND> PCTLNot() )* )\n}\n\nvoid PCTLNot() : {}\n{\n\t( (<NOT>)? PCTLProb() )\n}\n\n// pctl prob operator\n\nvoid PCTLProb() : {}\n{\n\t( (\n\t( <P> LtGt() Expression() ) |\n\t( <P> <EQ> <QMARK> ) |\n\t( <P> <MIN> <EQ> <QMARK> ) |\n\t( <P> <MAX> <EQ> <QMARK> ) |\n\t( <PMIN> <EQ> <QMARK> ) |\n\t( <PMAX> <EQ> <QMARK> ) )\n\t<LBRACKET>\n\t( PCTLProbNext() | PCTLProbBoundedUntil() | PCTLProbUntil() | PCTLProbBoundedFutureGlobal() | PCTLProbFutureGlobal() )\n\t( <LBRACE> PCTLFormula() <RBRACE>\n\t(( <LBRACE> <MIN> <RBRACE> ) | ( <LBRACE> <MAX> <RBRACE> ))*\n\t)? <RBRACKET> )\n\t| ( PCTLSS() )\n}\n\n// pctl next\n\nvoid PCTLProbNext() : {}\n{\n\t( <NEXT> PCTLFormula() )\n}\n\n// pctl bounded until\n\nvoid PCTLProbBoundedUntil() : {}\n{\n\t( PCTLFormula() <UNTIL> ((<LE> Expression()) | (<GE> Expression()) | (<LBRACKET> Expression() <COMMA> Expression() <RBRACKET>)) PCTLFormula() )\n}\n\n// pctl until (unbounded)\n\nvoid PCTLProbUntil() : {}\n{\n\t( PCTLFormula() <UNTIL> PCTLFormula() )\n}\n\n// pctl bounded future (eventually) or global\n\nvoid PCTLProbBoundedFutureGlobal() : {}\n{\n\t( (<FUTURE>|<GLOB>) ((<LE> Expression()) | (<GE> Expression()) | (<LBRACKET> Expression() <COMMA> Expression() <RBRACKET>)) PCTLFormula() )\n}\n\n// pctl future (eventually) or globally\n\nvoid PCTLProbFutureGlobal() : {}\n{\n\t( (<FUTURE>|<GLOB>) PCTLFormula() )\n}\n\n// pctl steady state (actually only csl - not pctl at all)\n\nvoid PCTLSS() : {}\n{\n\t( ( ( ( <S> LtGt() Expression() ) | ( <S> <EQ> <QMARK> ) ) <LBRACKET> PCTLFormula() ( <LBRACE> PCTLFormula() <RBRACE> )? <RBRACKET> ) ) | ( PCTLReward() )\n}\n\n// pctl reward operator\n\nvoid PCTLReward() : {}\n{\n\t( ( ( <R>\n\t( <LBRACE> ((<DQUOTE> Identifier() <DQUOTE>) | (Expression())) <RBRACE> )?\n\t(( LtGt() Expression() ) |\n\t( <EQ> <QMARK> ) |\n\t( <MIN> <EQ> <QMARK> ) |\n\t( <MAX> <EQ> <QMARK> ))) |\n\t( <RMIN> <EQ> <QMARK> ) |\n\t( <RMAX> <EQ> <QMARK> ) )\n\t<LBRACKET>\n\t( PCTLRewardCumul() | PCTLRewardInst() | PCTLRewardReach() | PCTLRewardSS() )\n\t( <LBRACE> PCTLFormula() <RBRACE>\n\t(( <LBRACE> <MIN> <RBRACE> ) | ( <LBRACE> <MAX> <RBRACE> ))*\n\t)? <RBRACKET> )\n\t| ( PCTLInit() )\n}\n\n// cumulative reward\n\nvoid PCTLRewardCumul() : {}\n{\n\t( <CUMUL> <LE> Expression() )\n}\n\n// instantaneous reward\n\nvoid PCTLRewardInst() : {}\n{\n\t( <INST> <EQ> Expression() )\n}\n\n// reach reward\n\nvoid PCTLRewardReach() : {}\n{\n\t( <FUTURE> PCTLFormula() )\n}\n\n// steady-state reward\n\nvoid PCTLRewardSS() : {}\n{\n\t( <S> )\n}\n\n// init\n\nvoid PCTLInit() : {}\n{\n\t( <DQUOTE> <INIT> <DQUOTE> ) | ( PCTLLabel() )\n}\n\n// label\n\nvoid PCTLLabel() : {}\n{\n\t( <DQUOTE> Identifier() <DQUOTE> ) | ( PCTLBrackets() )\n}\n\n// brackets\n\nvoid PCTLBrackets() : {}\n{\n\t( <LPARENTH> PCTLFormula() <RPARENTH> ) | ( PCTLExpression() )\n}\n\n// pctl expression\n\nvoid PCTLExpression() : {}\n{\n\t( ExpressionRelOpRange() )\n}\n\n//-----------------------------------------------------------------------------------\n// expression stuff\n//-----------------------------------------------------------------------------------\n\n// expression\n\nvoid Expression() : {}\n{\n\t( ExpressionITE() )\n}\n\n// expression (if-then-else)\n\nvoid ExpressionITE() : {}\n{\n\t( ExpressionOr() <QMARK> ExpressionOr() <COLON> ExpressionITE() ) | ( ExpressionOr() )\n}\n\n// expression (or)\n\nvoid ExpressionOr() : {}\n{\n\t( ExpressionAnd() ( <OR> ExpressionOr() )? )\n}\n\n// expression (and)\n\nvoid ExpressionAnd() : {}\n{\n\t( ExpressionNot() ( <AND> ExpressionNot() )* )\n}\n\n// expression (not)\n\nvoid ExpressionNot() : {}\n{\n\t( (<NOT>)? ExpressionRelOpRange() )\n}\n\n// expression: relational operators/ranges\n\nvoid ExpressionRelOpRange() :\n{\n\tToken t0, t1, t2, ptr;\n\tString relOp = null;\n\tboolean up, thisIsARange = false;\n\tString lhs = null, s1 = null, s2 = null, newExpr = \"\";\n}\n{\n\t( ExpressionPlusMinus() relOp=LtGt() ExpressionPlusMinus() ) | (\n\t{ t0=getToken(0); t1=getToken(1); }\n\tExpressionPlusMinus()\n\t{ t2=getToken(1); ptr = t1; lhs = \"\"; while (ptr != t2) { lhs += ptr.image; ptr = ptr.next; } }\n\trelOp=EqNeq() (\n\t{ newExpr = (relOp.equals(\"!=\"))?\"!(\":\"(\"; }\n\t{ t1=getToken(1); }\n\tExpressionPlusMinus()\n\t{ t2=getToken(1); ptr = t1; s1 = \"\"; while (ptr != t2) { s1 += ptr.image; ptr = ptr.next; } up = false; }\n\t( <DOTS>\n\t{ thisIsARange = true; t1=getToken(1); }\n\tExpressionPlusMinus()\n\t{ t2=getToken(1); ptr = t1; s2 = \"\"; while (ptr != t2) { s2 += ptr.image; ptr = ptr.next; } up = true; }\n\t)?\n\t{ if (up) newExpr += \"(\"+lhs+\")>=(\"+s1+\")&(\"+lhs+\")<=(\"+s2+\")\"; else newExpr += \"(\"+lhs+\")=(\"+s1+\")\"; }\n\t) ( ( <COMMA>\n\t{ thisIsARange = true; t1=getToken(1); }\n\tExpressionPlusMinus()\n\t{ t2=getToken(1); ptr = t1; s1 = \"\"; while (ptr != t2) { s1 += ptr.image; ptr = ptr.next; } up = false; }\n\t( <DOTS>\n\t{ t1=getToken(1); }\n\tExpressionPlusMinus()\n\t{ t2=getToken(1); ptr = t1; s2 = \"\"; while (ptr != t2) { s2 += ptr.image; ptr = ptr.next; } up = true; }\n\t)?\n\t{ if (up) newExpr += \"|(\"+lhs+\")>=(\"+s1+\")&(\"+lhs+\")<=(\"+s2+\")\"; else newExpr += \"|(\"+lhs+\")=(\"+s1+\")\"; }\n\t) )*\n\t{ newExpr += \")\"; if (thisIsARange) { t0.next = getToken(1); insertTokenBeforeNext(t0, newExpr); } }\n\t) | ( ExpressionPlusMinus() )\n}\n\n// expression: plus/minus - binary, left associative\n\nvoid ExpressionPlusMinus() : {}\n{\n\t( ExpressionTimesDivide() ( ( <PLUS> | <MINUS> ) ExpressionTimesDivide() )* )\n}\n\n// expression: times/divide - binary, left associative\n\nvoid ExpressionTimesDivide() : {}\n{\n\t( ExpressionUnaryMinus() ( ( <TIMES> | <DIVIDE> ) ExpressionUnaryMinus() )* )\n}\n\n// expression: unary minus (right associative)\n\nvoid ExpressionUnaryMinus() : {}\n{\n\t( <MINUS> ExpressionFunc() ) | ( ExpressionFunc() )\n}\n\n// expression (function)\n\nvoid ExpressionFunc() : {}\n{\n\t((((( <MIN> ) | ( <MAX> ) | ( <FLOOR> ) | ( <CEIL> )) <LPARENTH> ) | ( <FUNC> <LPARENTH> (( Identifier() ) | ( <MIN> ) | ( <MAX> ) | ( <FLOOR> ) | ( <CEIL> )) <COMMA> )) Expression() ( <COMMA> Expression() )* <RPARENTH> ) | ( ExpressionIdent() )\n}\n\n// expression (identifier)\n\nvoid ExpressionIdent() : {}\n{\n\t( Identifier() ) | ( ExpressionLiteral() )\n}\n\n// expression (literal)\n\nvoid ExpressionLiteral() : {}\n{\n\t( Int() ) | ( Double() ) | ( <TRUE> ) | ( <FALSE> ) | ( ExpressionBrackets() )\n}\n\n// expression (brackets)\n\nvoid ExpressionBrackets() : {}\n{\n\t( <LPARENTH> Expression() <RPARENTH> )\n}\n\n//-----------------------------------------------------------------------------------\n// miscellaneous stuff\n//-----------------------------------------------------------------------------------\n\n// identifier\n\nString Identifier() :\n{\n}\n{\n\t<REG_IDENT>\n\t{\n\t\treturn token.image;\n\t}\n}\n\n// identifier with a prime\n\nString IdentifierPrime() :\n{\n}\n{\n\t<REG_IDENTPRIME>\n\t{\n\t\t// remove prime and return\n\t\tString s = token.image;\n\t\ts = s.substring(0, s.length()-1);\n\t\treturn s;\n\t}\n}\n\n// one of the relational operators: =, !=\n\nString EqNeq() :\n{\n}\n{\n\t( <EQ> | <NE> )\n\t{\n\t\treturn token.image;\n\t}\n}\n\n// one of the relational operators: >, <, >=, <=\n\nString LtGt() :\n{\n}\n{\n\t( <GT> | <LT> | <GE> | <LE> )\n\t{\n\t\treturn token.image;\n\t}\n}\n\n// integer\n\nint Int() :\n{\n\tint i;\n}\n{\n\t// basic int\n\t<REG_INT>\n\t{\n\t\ti = Integer.parseInt(token.image);\n\t\treturn i;\n\t}\n}\n\n// double\n\nString Double() :\n{\n}\n{\n\t<REG_DOUBLE>\n\t{\n\t\t//return Double.valueOf(token.image).doubleValue();\n\t\treturn token.image;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/Prism3To4Constants.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. Prism3To4Constants.java */\npackage parser;\n\n\n/**\n * Token literal values and constants.\n * Generated by org.javacc.parser.OtherFilesGen#start()\n */\npublic interface Prism3To4Constants {\n\n  /** End of File. */\n  int EOF = 0;\n  /** RegularExpression Id. */\n  int WHITESPACE = 1;\n  /** RegularExpression Id. */\n  int COMMENT = 2;\n  /** RegularExpression Id. */\n  int BOOL = 3;\n  /** RegularExpression Id. */\n  int CONST = 4;\n  /** RegularExpression Id. */\n  int CEIL = 5;\n  /** RegularExpression Id. */\n  int CTMC = 6;\n  /** RegularExpression Id. */\n  int CUMUL = 7;\n  /** RegularExpression Id. */\n  int DOUBLE = 8;\n  /** RegularExpression Id. */\n  int DTMC = 9;\n  /** RegularExpression Id. */\n  int ENDINIT = 10;\n  /** RegularExpression Id. */\n  int ENDMODULE = 11;\n  /** RegularExpression Id. */\n  int ENDREWARDS = 12;\n  /** RegularExpression Id. */\n  int ENDSYSTEM = 13;\n  /** RegularExpression Id. */\n  int FALSE = 14;\n  /** RegularExpression Id. */\n  int FLOOR = 15;\n  /** RegularExpression Id. */\n  int FORMULA = 16;\n  /** RegularExpression Id. */\n  int FUNC = 17;\n  /** RegularExpression Id. */\n  int FUTURE = 18;\n  /** RegularExpression Id. */\n  int GLOBAL = 19;\n  /** RegularExpression Id. */\n  int GLOB = 20;\n  /** RegularExpression Id. */\n  int INIT = 21;\n  /** RegularExpression Id. */\n  int INST = 22;\n  /** RegularExpression Id. */\n  int INT = 23;\n  /** RegularExpression Id. */\n  int LABEL = 24;\n  /** RegularExpression Id. */\n  int MAX = 25;\n  /** RegularExpression Id. */\n  int MDP = 26;\n  /** RegularExpression Id. */\n  int MIN = 27;\n  /** RegularExpression Id. */\n  int MODULE = 28;\n  /** RegularExpression Id. */\n  int NEXT = 29;\n  /** RegularExpression Id. */\n  int NONDETERMINISTIC = 30;\n  /** RegularExpression Id. */\n  int PMAX = 31;\n  /** RegularExpression Id. */\n  int PMIN = 32;\n  /** RegularExpression Id. */\n  int P = 33;\n  /** RegularExpression Id. */\n  int PROBABILISTIC = 34;\n  /** RegularExpression Id. */\n  int PROB = 35;\n  /** RegularExpression Id. */\n  int RATE = 36;\n  /** RegularExpression Id. */\n  int REWARDS = 37;\n  /** RegularExpression Id. */\n  int RMAX = 38;\n  /** RegularExpression Id. */\n  int RMIN = 39;\n  /** RegularExpression Id. */\n  int R = 40;\n  /** RegularExpression Id. */\n  int S = 41;\n  /** RegularExpression Id. */\n  int STOCHASTIC = 42;\n  /** RegularExpression Id. */\n  int SYSTEM = 43;\n  /** RegularExpression Id. */\n  int TRUE = 44;\n  /** RegularExpression Id. */\n  int UNTIL = 45;\n  /** RegularExpression Id. */\n  int NOT = 46;\n  /** RegularExpression Id. */\n  int AND = 47;\n  /** RegularExpression Id. */\n  int OR = 48;\n  /** RegularExpression Id. */\n  int IMPLIES = 49;\n  /** RegularExpression Id. */\n  int RARROW = 50;\n  /** RegularExpression Id. */\n  int COLON = 51;\n  /** RegularExpression Id. */\n  int SEMICOLON = 52;\n  /** RegularExpression Id. */\n  int COMMA = 53;\n  /** RegularExpression Id. */\n  int DOTS = 54;\n  /** RegularExpression Id. */\n  int LPARENTH = 55;\n  /** RegularExpression Id. */\n  int RPARENTH = 56;\n  /** RegularExpression Id. */\n  int LBRACKET = 57;\n  /** RegularExpression Id. */\n  int RBRACKET = 58;\n  /** RegularExpression Id. */\n  int LBRACE = 59;\n  /** RegularExpression Id. */\n  int RBRACE = 60;\n  /** RegularExpression Id. */\n  int EQ = 61;\n  /** RegularExpression Id. */\n  int NE = 62;\n  /** RegularExpression Id. */\n  int LT = 63;\n  /** RegularExpression Id. */\n  int GT = 64;\n  /** RegularExpression Id. */\n  int LE = 65;\n  /** RegularExpression Id. */\n  int GE = 66;\n  /** RegularExpression Id. */\n  int PLUS = 67;\n  /** RegularExpression Id. */\n  int MINUS = 68;\n  /** RegularExpression Id. */\n  int TIMES = 69;\n  /** RegularExpression Id. */\n  int DIVIDE = 70;\n  /** RegularExpression Id. */\n  int PRIME = 71;\n  /** RegularExpression Id. */\n  int RENAME = 72;\n  /** RegularExpression Id. */\n  int QMARK = 73;\n  /** RegularExpression Id. */\n  int DQUOTE = 74;\n  /** RegularExpression Id. */\n  int REG_INT = 75;\n  /** RegularExpression Id. */\n  int REG_DOUBLE = 76;\n  /** RegularExpression Id. */\n  int REG_IDENTPRIME = 77;\n  /** RegularExpression Id. */\n  int REG_IDENT = 78;\n  /** RegularExpression Id. */\n  int PREPROC = 79;\n\n  /** Lexical state. */\n  int DEFAULT = 0;\n\n  /** Literal token values. */\n  String[] tokenImage = {\n    \"<EOF>\",\n    \"<WHITESPACE>\",\n    \"<COMMENT>\",\n    \"\\\"bool\\\"\",\n    \"\\\"const\\\"\",\n    \"\\\"ceil\\\"\",\n    \"\\\"ctmc\\\"\",\n    \"\\\"C\\\"\",\n    \"\\\"double\\\"\",\n    \"\\\"dtmc\\\"\",\n    \"\\\"endinit\\\"\",\n    \"\\\"endmodule\\\"\",\n    \"\\\"endrewards\\\"\",\n    \"\\\"endsystem\\\"\",\n    \"\\\"false\\\"\",\n    \"\\\"floor\\\"\",\n    \"\\\"formula\\\"\",\n    \"\\\"func\\\"\",\n    \"\\\"F\\\"\",\n    \"\\\"global\\\"\",\n    \"\\\"G\\\"\",\n    \"\\\"init\\\"\",\n    \"\\\"I\\\"\",\n    \"\\\"int\\\"\",\n    \"\\\"label\\\"\",\n    \"\\\"max\\\"\",\n    \"\\\"mdp\\\"\",\n    \"\\\"min\\\"\",\n    \"\\\"module\\\"\",\n    \"\\\"X\\\"\",\n    \"\\\"nondeterministic\\\"\",\n    \"\\\"Pmax\\\"\",\n    \"\\\"Pmin\\\"\",\n    \"\\\"P\\\"\",\n    \"\\\"probabilistic\\\"\",\n    \"\\\"prob\\\"\",\n    \"\\\"rate\\\"\",\n    \"\\\"rewards\\\"\",\n    \"\\\"Rmax\\\"\",\n    \"\\\"Rmin\\\"\",\n    \"\\\"R\\\"\",\n    \"\\\"S\\\"\",\n    \"\\\"stochastic\\\"\",\n    \"\\\"system\\\"\",\n    \"\\\"true\\\"\",\n    \"\\\"U\\\"\",\n    \"\\\"!\\\"\",\n    \"\\\"&\\\"\",\n    \"\\\"|\\\"\",\n    \"\\\"=>\\\"\",\n    \"\\\"->\\\"\",\n    \"\\\":\\\"\",\n    \"\\\";\\\"\",\n    \"\\\",\\\"\",\n    \"\\\"..\\\"\",\n    \"\\\"(\\\"\",\n    \"\\\")\\\"\",\n    \"\\\"[\\\"\",\n    \"\\\"]\\\"\",\n    \"\\\"{\\\"\",\n    \"\\\"}\\\"\",\n    \"\\\"=\\\"\",\n    \"\\\"!=\\\"\",\n    \"\\\"<\\\"\",\n    \"\\\">\\\"\",\n    \"\\\"<=\\\"\",\n    \"\\\">=\\\"\",\n    \"\\\"+\\\"\",\n    \"\\\"-\\\"\",\n    \"\\\"*\\\"\",\n    \"\\\"/\\\"\",\n    \"\\\"\\\\\\'\\\"\",\n    \"\\\"<-\\\"\",\n    \"\\\"?\\\"\",\n    \"\\\"\\\\\\\"\\\"\",\n    \"<REG_INT>\",\n    \"<REG_DOUBLE>\",\n    \"<REG_IDENTPRIME>\",\n    \"<REG_IDENT>\",\n    \"<PREPROC>\",\n  };\n\n}\n"
  },
  {
    "path": "prism/src/parser/Prism3To4TokenManager.java",
    "content": "/* Prism3To4TokenManager.java */\n/* Generated By:JavaCC: Do not edit this line. Prism3To4TokenManager.java */\npackage parser;\nimport java.io.*;\n\n/** Token Manager. */\n@SuppressWarnings(\"unused\")public class Prism3To4TokenManager implements Prism3To4Constants {\n\n  /** Debug output. */\n  public static  java.io.PrintStream debugStream = System.out;\n  /** Set debug output. */\n  public static  void setDebugStream(java.io.PrintStream ds) { debugStream = ds; }\nprivate static final int jjStopStringLiteralDfa_0(int pos, long active0, long active1){\n   switch (pos)\n   {\n      case 0:\n         if ((active0 & 0x1c3c5fabff78L) != 0L)\n         {\n            jjmatchedKind = 78;\n            return 23;\n         }\n         if ((active0 & 0x23c3a0540080L) != 0L)\n            return 23;\n         if ((active1 & 0x40L) != 0L)\n            return 1;\n         if ((active0 & 0x40000000000000L) != 0L)\n            return 11;\n         return -1;\n      case 1:\n         if ((active0 & 0x1cfddfabff78L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 1;\n            return 23;\n         }\n         return -1;\n      case 2:\n         if ((active0 & 0x1cfdd12bff78L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 2;\n            return 23;\n         }\n         if ((active0 & 0xe800000L) != 0L)\n            return 23;\n         return -1;\n      case 3:\n         if ((active0 & 0xc205109fd10L) != 0L)\n         {\n            if (jjmatchedPos != 3)\n            {\n               jjmatchedKind = 78;\n               jjmatchedPos = 3;\n            }\n            return 23;\n         }\n         if ((active0 & 0x10dd80220268L) != 0L)\n            return 23;\n         return -1;\n      case 4:\n         if ((active0 & 0xc2450093d00L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 4;\n            return 23;\n         }\n         if ((active0 & 0x100c010L) != 0L)\n            return 23;\n         return -1;\n      case 5:\n         if ((active0 & 0x42440013c00L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 5;\n            return 23;\n         }\n         if ((active0 & 0x80010080100L) != 0L)\n            return 23;\n         return -1;\n      case 6:\n         if ((active0 & 0x2000010400L) != 0L)\n            return 23;\n         if ((active0 & 0x40440003800L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 6;\n            return 23;\n         }\n         return -1;\n      case 7:\n         if ((active0 & 0x40440003800L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 7;\n            return 23;\n         }\n         return -1;\n      case 8:\n         if ((active0 & 0x2800L) != 0L)\n            return 23;\n         if ((active0 & 0x40440001000L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 8;\n            return 23;\n         }\n         return -1;\n      case 9:\n         if ((active0 & 0x440000000L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 9;\n            return 23;\n         }\n         if ((active0 & 0x40000001000L) != 0L)\n            return 23;\n         return -1;\n      case 10:\n         if ((active0 & 0x440000000L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 10;\n            return 23;\n         }\n         return -1;\n      case 11:\n         if ((active0 & 0x440000000L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 11;\n            return 23;\n         }\n         return -1;\n      case 12:\n         if ((active0 & 0x400000000L) != 0L)\n            return 23;\n         if ((active0 & 0x40000000L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 12;\n            return 23;\n         }\n         return -1;\n      case 13:\n         if ((active0 & 0x40000000L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 13;\n            return 23;\n         }\n         return -1;\n      case 14:\n         if ((active0 & 0x40000000L) != 0L)\n         {\n            jjmatchedKind = 78;\n            jjmatchedPos = 14;\n            return 23;\n         }\n         return -1;\n      default :\n         return -1;\n   }\n}\nprivate static final int jjStartNfa_0(int pos, long active0, long active1){\n   return jjMoveNfa_0(jjStopStringLiteralDfa_0(pos, active0, active1), pos + 1);\n}\nstatic private int jjStopAtPos(int pos, int kind)\n{\n   jjmatchedKind = kind;\n   jjmatchedPos = pos;\n   return pos + 1;\n}\nstatic private int jjMoveStringLiteralDfa0_0(){\n   switch(curChar)\n   {\n      case 33:\n         jjmatchedKind = 46;\n         return jjMoveStringLiteralDfa1_0(0x4000000000000000L, 0x0L);\n      case 34:\n         return jjStopAtPos(0, 74);\n      case 38:\n         return jjStopAtPos(0, 47);\n      case 39:\n         return jjStopAtPos(0, 71);\n      case 40:\n         return jjStopAtPos(0, 55);\n      case 41:\n         return jjStopAtPos(0, 56);\n      case 42:\n         return jjStopAtPos(0, 69);\n      case 43:\n         return jjStopAtPos(0, 67);\n      case 44:\n         return jjStopAtPos(0, 53);\n      case 45:\n         jjmatchedKind = 68;\n         return jjMoveStringLiteralDfa1_0(0x4000000000000L, 0x0L);\n      case 46:\n         return jjMoveStringLiteralDfa1_0(0x40000000000000L, 0x0L);\n      case 47:\n         return jjStartNfaWithStates_0(0, 70, 1);\n      case 58:\n         return jjStopAtPos(0, 51);\n      case 59:\n         return jjStopAtPos(0, 52);\n      case 60:\n         jjmatchedKind = 63;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x102L);\n      case 61:\n         jjmatchedKind = 61;\n         return jjMoveStringLiteralDfa1_0(0x2000000000000L, 0x0L);\n      case 62:\n         jjmatchedKind = 64;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x4L);\n      case 63:\n         return jjStopAtPos(0, 73);\n      case 67:\n         return jjStartNfaWithStates_0(0, 7, 23);\n      case 70:\n         return jjStartNfaWithStates_0(0, 18, 23);\n      case 71:\n         return jjStartNfaWithStates_0(0, 20, 23);\n      case 73:\n         return jjStartNfaWithStates_0(0, 22, 23);\n      case 80:\n         jjmatchedKind = 33;\n         return jjMoveStringLiteralDfa1_0(0x180000000L, 0x0L);\n      case 82:\n         jjmatchedKind = 40;\n         return jjMoveStringLiteralDfa1_0(0xc000000000L, 0x0L);\n      case 83:\n         return jjStartNfaWithStates_0(0, 41, 23);\n      case 85:\n         return jjStartNfaWithStates_0(0, 45, 23);\n      case 88:\n         return jjStartNfaWithStates_0(0, 29, 23);\n      case 91:\n         return jjStopAtPos(0, 57);\n      case 93:\n         return jjStopAtPos(0, 58);\n      case 98:\n         return jjMoveStringLiteralDfa1_0(0x8L, 0x0L);\n      case 99:\n         return jjMoveStringLiteralDfa1_0(0x70L, 0x0L);\n      case 100:\n         return jjMoveStringLiteralDfa1_0(0x300L, 0x0L);\n      case 101:\n         return jjMoveStringLiteralDfa1_0(0x3c00L, 0x0L);\n      case 102:\n         return jjMoveStringLiteralDfa1_0(0x3c000L, 0x0L);\n      case 103:\n         return jjMoveStringLiteralDfa1_0(0x80000L, 0x0L);\n      case 105:\n         return jjMoveStringLiteralDfa1_0(0xa00000L, 0x0L);\n      case 108:\n         return jjMoveStringLiteralDfa1_0(0x1000000L, 0x0L);\n      case 109:\n         return jjMoveStringLiteralDfa1_0(0x1e000000L, 0x0L);\n      case 110:\n         return jjMoveStringLiteralDfa1_0(0x40000000L, 0x0L);\n      case 112:\n         return jjMoveStringLiteralDfa1_0(0xc00000000L, 0x0L);\n      case 114:\n         return jjMoveStringLiteralDfa1_0(0x3000000000L, 0x0L);\n      case 115:\n         return jjMoveStringLiteralDfa1_0(0xc0000000000L, 0x0L);\n      case 116:\n         return jjMoveStringLiteralDfa1_0(0x100000000000L, 0x0L);\n      case 123:\n         return jjStopAtPos(0, 59);\n      case 124:\n         return jjStopAtPos(0, 48);\n      case 125:\n         return jjStopAtPos(0, 60);\n      default :\n         return jjMoveNfa_0(0, 0);\n   }\n}\nstatic private int jjMoveStringLiteralDfa1_0(long active0, long active1){\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(0, active0, active1);\n      return 1;\n   }\n   switch(curChar)\n   {\n      case 45:\n         if ((active1 & 0x100L) != 0L)\n            return jjStopAtPos(1, 72);\n         break;\n      case 46:\n         if ((active0 & 0x40000000000000L) != 0L)\n            return jjStopAtPos(1, 54);\n         break;\n      case 61:\n         if ((active0 & 0x4000000000000000L) != 0L)\n            return jjStopAtPos(1, 62);\n         else if ((active1 & 0x2L) != 0L)\n            return jjStopAtPos(1, 65);\n         else if ((active1 & 0x4L) != 0L)\n            return jjStopAtPos(1, 66);\n         break;\n      case 62:\n         if ((active0 & 0x2000000000000L) != 0L)\n            return jjStopAtPos(1, 49);\n         else if ((active0 & 0x4000000000000L) != 0L)\n            return jjStopAtPos(1, 50);\n         break;\n      case 97:\n         return jjMoveStringLiteralDfa2_0(active0, 0x1003004000L, active1, 0L);\n      case 100:\n         return jjMoveStringLiteralDfa2_0(active0, 0x4000000L, active1, 0L);\n      case 101:\n         return jjMoveStringLiteralDfa2_0(active0, 0x2000000020L, active1, 0L);\n      case 105:\n         return jjMoveStringLiteralDfa2_0(active0, 0x8000000L, active1, 0L);\n      case 108:\n         return jjMoveStringLiteralDfa2_0(active0, 0x88000L, active1, 0L);\n      case 109:\n         return jjMoveStringLiteralDfa2_0(active0, 0xc180000000L, active1, 0L);\n      case 110:\n         return jjMoveStringLiteralDfa2_0(active0, 0xa03c00L, active1, 0L);\n      case 111:\n         return jjMoveStringLiteralDfa2_0(active0, 0x50010118L, active1, 0L);\n      case 114:\n         return jjMoveStringLiteralDfa2_0(active0, 0x100c00000000L, active1, 0L);\n      case 116:\n         return jjMoveStringLiteralDfa2_0(active0, 0x40000000240L, active1, 0L);\n      case 117:\n         return jjMoveStringLiteralDfa2_0(active0, 0x20000L, active1, 0L);\n      case 121:\n         return jjMoveStringLiteralDfa2_0(active0, 0x80000000000L, active1, 0L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(0, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa2_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(0, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(1, active0, 0L);\n      return 2;\n   }\n   switch(curChar)\n   {\n      case 97:\n         return jjMoveStringLiteralDfa3_0(active0, 0x4080000000L);\n      case 98:\n         return jjMoveStringLiteralDfa3_0(active0, 0x1000000L);\n      case 100:\n         return jjMoveStringLiteralDfa3_0(active0, 0x10003c00L);\n      case 105:\n         return jjMoveStringLiteralDfa3_0(active0, 0x8100200020L);\n      case 108:\n         return jjMoveStringLiteralDfa3_0(active0, 0x4000L);\n      case 109:\n         return jjMoveStringLiteralDfa3_0(active0, 0x240L);\n      case 110:\n         if ((active0 & 0x8000000L) != 0L)\n            return jjStartNfaWithStates_0(2, 27, 23);\n         return jjMoveStringLiteralDfa3_0(active0, 0x40020010L);\n      case 111:\n         return jjMoveStringLiteralDfa3_0(active0, 0x40c00088008L);\n      case 112:\n         if ((active0 & 0x4000000L) != 0L)\n            return jjStartNfaWithStates_0(2, 26, 23);\n         break;\n      case 114:\n         return jjMoveStringLiteralDfa3_0(active0, 0x10000L);\n      case 115:\n         return jjMoveStringLiteralDfa3_0(active0, 0x80000000000L);\n      case 116:\n         if ((active0 & 0x800000L) != 0L)\n            return jjStartNfaWithStates_0(2, 23, 23);\n         return jjMoveStringLiteralDfa3_0(active0, 0x1000000000L);\n      case 117:\n         return jjMoveStringLiteralDfa3_0(active0, 0x100000000100L);\n      case 119:\n         return jjMoveStringLiteralDfa3_0(active0, 0x2000000000L);\n      case 120:\n         if ((active0 & 0x2000000L) != 0L)\n            return jjStartNfaWithStates_0(2, 25, 23);\n         break;\n      default :\n         break;\n   }\n   return jjStartNfa_0(1, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa3_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(1, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(2, active0, 0L);\n      return 3;\n   }\n   switch(curChar)\n   {\n      case 97:\n         return jjMoveStringLiteralDfa4_0(active0, 0x2000000000L);\n      case 98:\n         if ((active0 & 0x800000000L) != 0L)\n         {\n            jjmatchedKind = 35;\n            jjmatchedPos = 3;\n         }\n         return jjMoveStringLiteralDfa4_0(active0, 0x400080100L);\n      case 99:\n         if ((active0 & 0x40L) != 0L)\n            return jjStartNfaWithStates_0(3, 6, 23);\n         else if ((active0 & 0x200L) != 0L)\n            return jjStartNfaWithStates_0(3, 9, 23);\n         else if ((active0 & 0x20000L) != 0L)\n            return jjStartNfaWithStates_0(3, 17, 23);\n         return jjMoveStringLiteralDfa4_0(active0, 0x40000000000L);\n      case 100:\n         return jjMoveStringLiteralDfa4_0(active0, 0x40000000L);\n      case 101:\n         if ((active0 & 0x1000000000L) != 0L)\n            return jjStartNfaWithStates_0(3, 36, 23);\n         else if ((active0 & 0x100000000000L) != 0L)\n            return jjStartNfaWithStates_0(3, 44, 23);\n         return jjMoveStringLiteralDfa4_0(active0, 0x1000000L);\n      case 105:\n         return jjMoveStringLiteralDfa4_0(active0, 0x400L);\n      case 108:\n         if ((active0 & 0x8L) != 0L)\n            return jjStartNfaWithStates_0(3, 3, 23);\n         else if ((active0 & 0x20L) != 0L)\n            return jjStartNfaWithStates_0(3, 5, 23);\n         break;\n      case 109:\n         return jjMoveStringLiteralDfa4_0(active0, 0x10800L);\n      case 110:\n         if ((active0 & 0x100000000L) != 0L)\n            return jjStartNfaWithStates_0(3, 32, 23);\n         else if ((active0 & 0x8000000000L) != 0L)\n            return jjStartNfaWithStates_0(3, 39, 23);\n         break;\n      case 111:\n         return jjMoveStringLiteralDfa4_0(active0, 0x8000L);\n      case 114:\n         return jjMoveStringLiteralDfa4_0(active0, 0x1000L);\n      case 115:\n         return jjMoveStringLiteralDfa4_0(active0, 0x6010L);\n      case 116:\n         if ((active0 & 0x200000L) != 0L)\n            return jjStartNfaWithStates_0(3, 21, 23);\n         return jjMoveStringLiteralDfa4_0(active0, 0x80000000000L);\n      case 117:\n         return jjMoveStringLiteralDfa4_0(active0, 0x10000000L);\n      case 120:\n         if ((active0 & 0x80000000L) != 0L)\n            return jjStartNfaWithStates_0(3, 31, 23);\n         else if ((active0 & 0x4000000000L) != 0L)\n            return jjStartNfaWithStates_0(3, 38, 23);\n         break;\n      default :\n         break;\n   }\n   return jjStartNfa_0(2, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa4_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(2, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(3, active0, 0L);\n      return 4;\n   }\n   switch(curChar)\n   {\n      case 97:\n         return jjMoveStringLiteralDfa5_0(active0, 0x400080000L);\n      case 101:\n         if ((active0 & 0x4000L) != 0L)\n            return jjStartNfaWithStates_0(4, 14, 23);\n         return jjMoveStringLiteralDfa5_0(active0, 0x80040001000L);\n      case 104:\n         return jjMoveStringLiteralDfa5_0(active0, 0x40000000000L);\n      case 108:\n         if ((active0 & 0x1000000L) != 0L)\n            return jjStartNfaWithStates_0(4, 24, 23);\n         return jjMoveStringLiteralDfa5_0(active0, 0x10000100L);\n      case 110:\n         return jjMoveStringLiteralDfa5_0(active0, 0x400L);\n      case 111:\n         return jjMoveStringLiteralDfa5_0(active0, 0x800L);\n      case 114:\n         if ((active0 & 0x8000L) != 0L)\n            return jjStartNfaWithStates_0(4, 15, 23);\n         return jjMoveStringLiteralDfa5_0(active0, 0x2000000000L);\n      case 116:\n         if ((active0 & 0x10L) != 0L)\n            return jjStartNfaWithStates_0(4, 4, 23);\n         break;\n      case 117:\n         return jjMoveStringLiteralDfa5_0(active0, 0x10000L);\n      case 121:\n         return jjMoveStringLiteralDfa5_0(active0, 0x2000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(3, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa5_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(3, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(4, active0, 0L);\n      return 5;\n   }\n   switch(curChar)\n   {\n      case 97:\n         return jjMoveStringLiteralDfa6_0(active0, 0x40000000000L);\n      case 98:\n         return jjMoveStringLiteralDfa6_0(active0, 0x400000000L);\n      case 100:\n         return jjMoveStringLiteralDfa6_0(active0, 0x2000000800L);\n      case 101:\n         if ((active0 & 0x100L) != 0L)\n            return jjStartNfaWithStates_0(5, 8, 23);\n         else if ((active0 & 0x10000000L) != 0L)\n            return jjStartNfaWithStates_0(5, 28, 23);\n         break;\n      case 105:\n         return jjMoveStringLiteralDfa6_0(active0, 0x400L);\n      case 108:\n         if ((active0 & 0x80000L) != 0L)\n            return jjStartNfaWithStates_0(5, 19, 23);\n         return jjMoveStringLiteralDfa6_0(active0, 0x10000L);\n      case 109:\n         if ((active0 & 0x80000000000L) != 0L)\n            return jjStartNfaWithStates_0(5, 43, 23);\n         break;\n      case 115:\n         return jjMoveStringLiteralDfa6_0(active0, 0x2000L);\n      case 116:\n         return jjMoveStringLiteralDfa6_0(active0, 0x40000000L);\n      case 119:\n         return jjMoveStringLiteralDfa6_0(active0, 0x1000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(4, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa6_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(4, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(5, active0, 0L);\n      return 6;\n   }\n   switch(curChar)\n   {\n      case 97:\n         if ((active0 & 0x10000L) != 0L)\n            return jjStartNfaWithStates_0(6, 16, 23);\n         return jjMoveStringLiteralDfa7_0(active0, 0x1000L);\n      case 101:\n         return jjMoveStringLiteralDfa7_0(active0, 0x40000000L);\n      case 105:\n         return jjMoveStringLiteralDfa7_0(active0, 0x400000000L);\n      case 115:\n         if ((active0 & 0x2000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 37, 23);\n         return jjMoveStringLiteralDfa7_0(active0, 0x40000000000L);\n      case 116:\n         if ((active0 & 0x400L) != 0L)\n            return jjStartNfaWithStates_0(6, 10, 23);\n         return jjMoveStringLiteralDfa7_0(active0, 0x2000L);\n      case 117:\n         return jjMoveStringLiteralDfa7_0(active0, 0x800L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(5, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa7_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(5, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(6, active0, 0L);\n      return 7;\n   }\n   switch(curChar)\n   {\n      case 101:\n         return jjMoveStringLiteralDfa8_0(active0, 0x2000L);\n      case 108:\n         return jjMoveStringLiteralDfa8_0(active0, 0x400000800L);\n      case 114:\n         return jjMoveStringLiteralDfa8_0(active0, 0x40001000L);\n      case 116:\n         return jjMoveStringLiteralDfa8_0(active0, 0x40000000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(6, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa8_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(6, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(7, active0, 0L);\n      return 8;\n   }\n   switch(curChar)\n   {\n      case 100:\n         return jjMoveStringLiteralDfa9_0(active0, 0x1000L);\n      case 101:\n         if ((active0 & 0x800L) != 0L)\n            return jjStartNfaWithStates_0(8, 11, 23);\n         break;\n      case 105:\n         return jjMoveStringLiteralDfa9_0(active0, 0x40400000000L);\n      case 109:\n         if ((active0 & 0x2000L) != 0L)\n            return jjStartNfaWithStates_0(8, 13, 23);\n         return jjMoveStringLiteralDfa9_0(active0, 0x40000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(7, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa9_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(7, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(8, active0, 0L);\n      return 9;\n   }\n   switch(curChar)\n   {\n      case 99:\n         if ((active0 & 0x40000000000L) != 0L)\n            return jjStartNfaWithStates_0(9, 42, 23);\n         break;\n      case 105:\n         return jjMoveStringLiteralDfa10_0(active0, 0x40000000L);\n      case 115:\n         if ((active0 & 0x1000L) != 0L)\n            return jjStartNfaWithStates_0(9, 12, 23);\n         return jjMoveStringLiteralDfa10_0(active0, 0x400000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(8, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa10_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(8, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(9, active0, 0L);\n      return 10;\n   }\n   switch(curChar)\n   {\n      case 110:\n         return jjMoveStringLiteralDfa11_0(active0, 0x40000000L);\n      case 116:\n         return jjMoveStringLiteralDfa11_0(active0, 0x400000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(9, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa11_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(9, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(10, active0, 0L);\n      return 11;\n   }\n   switch(curChar)\n   {\n      case 105:\n         return jjMoveStringLiteralDfa12_0(active0, 0x440000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(10, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa12_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(10, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(11, active0, 0L);\n      return 12;\n   }\n   switch(curChar)\n   {\n      case 99:\n         if ((active0 & 0x400000000L) != 0L)\n            return jjStartNfaWithStates_0(12, 34, 23);\n         break;\n      case 115:\n         return jjMoveStringLiteralDfa13_0(active0, 0x40000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(11, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa13_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(11, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(12, active0, 0L);\n      return 13;\n   }\n   switch(curChar)\n   {\n      case 116:\n         return jjMoveStringLiteralDfa14_0(active0, 0x40000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(12, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa14_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(12, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(13, active0, 0L);\n      return 14;\n   }\n   switch(curChar)\n   {\n      case 105:\n         return jjMoveStringLiteralDfa15_0(active0, 0x40000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(13, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa15_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(13, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(14, active0, 0L);\n      return 15;\n   }\n   switch(curChar)\n   {\n      case 99:\n         if ((active0 & 0x40000000L) != 0L)\n            return jjStartNfaWithStates_0(15, 30, 23);\n         break;\n      default :\n         break;\n   }\n   return jjStartNfa_0(14, active0, 0L);\n}\nstatic private int jjStartNfaWithStates_0(int pos, int kind, int state)\n{\n   jjmatchedKind = kind;\n   jjmatchedPos = pos;\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) { return pos + 1; }\n   return jjMoveNfa_0(state, pos + 1);\n}\nstatic final long[] jjbitVec0 = {\n   0x0L, 0x0L, 0xffffffffffffffffL, 0xffffffffffffffffL\n};\nstatic private int jjMoveNfa_0(int startState, int curPos)\n{\n   int startsAt = 0;\n   jjnewStateCnt = 23;\n   int i = 1;\n   jjstateSet[0] = startState;\n   int kind = 0x7fffffff;\n   for (;;)\n   {\n      if (++jjround == 0x7fffffff)\n         ReInitRounds();\n      if (curChar < 64)\n      {\n         long l = 1L << curChar;\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 23:\n                  if ((0x3ff000000000000L & l) != 0L)\n                  {\n                     if (kind > 78)\n                        kind = 78;\n                     { jjCheckNAdd(22); }\n                  }\n                  else if (curChar == 39)\n                  {\n                     if (kind > 77)\n                        kind = 77;\n                  }\n                  if ((0x3ff000000000000L & l) != 0L)\n                     { jjCheckNAddTwoStates(20, 21); }\n                  break;\n               case 0:\n                  if ((0x3ff000000000000L & l) != 0L)\n                  {\n                     if (kind > 76)\n                        kind = 76;\n                     { jjCheckNAddStates(0, 3); }\n                  }\n                  else if ((0x100002600L & l) != 0L)\n                  {\n                     if (kind > 1)\n                        kind = 1;\n                  }\n                  else if (curChar == 35)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  else if (curChar == 46)\n                     { jjCheckNAdd(11); }\n                  else if (curChar == 47)\n                     jjstateSet[jjnewStateCnt++] = 1;\n                  if ((0x3fe000000000000L & l) != 0L)\n                  {\n                     if (kind > 75)\n                        kind = 75;\n                     { jjCheckNAdd(8); }\n                  }\n                  else if (curChar == 48)\n                  {\n                     if (kind > 75)\n                        kind = 75;\n                  }\n                  break;\n               case 1:\n                  if (curChar == 47)\n                     { jjCheckNAddStates(4, 6); }\n                  break;\n               case 2:\n                  if ((0xffffffffffffdbffL & l) != 0L)\n                     { jjCheckNAddStates(4, 6); }\n                  break;\n               case 3:\n                  if ((0x2400L & l) != 0L && kind > 2)\n                     kind = 2;\n                  break;\n               case 4:\n                  if (curChar == 10 && kind > 2)\n                     kind = 2;\n                  break;\n               case 5:\n                  if (curChar == 13)\n                     jjstateSet[jjnewStateCnt++] = 4;\n                  break;\n               case 6:\n                  if (curChar == 47)\n                     jjstateSet[jjnewStateCnt++] = 1;\n                  break;\n               case 7:\n                  if ((0x3fe000000000000L & l) == 0L)\n                     break;\n                  if (kind > 75)\n                     kind = 75;\n                  { jjCheckNAdd(8); }\n                  break;\n               case 8:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 75)\n                     kind = 75;\n                  { jjCheckNAdd(8); }\n                  break;\n               case 9:\n                  if (curChar == 48 && kind > 75)\n                     kind = 75;\n                  break;\n               case 10:\n                  if (curChar == 46)\n                     { jjCheckNAdd(11); }\n                  break;\n               case 11:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 76)\n                     kind = 76;\n                  { jjCheckNAddTwoStates(11, 12); }\n                  break;\n               case 13:\n                  if ((0x280000000000L & l) != 0L)\n                     { jjCheckNAdd(14); }\n                  break;\n               case 14:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 76)\n                     kind = 76;\n                  { jjCheckNAdd(14); }\n                  break;\n               case 15:\n                  if (curChar == 35)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  break;\n               case 16:\n                  if ((0xfffffff7ffffffffL & l) != 0L)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  break;\n               case 17:\n                  if (curChar == 35 && kind > 79)\n                     kind = 79;\n                  break;\n               case 18:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 76)\n                     kind = 76;\n                  { jjCheckNAddStates(0, 3); }\n                  break;\n               case 20:\n                  if ((0x3ff000000000000L & l) != 0L)\n                     { jjCheckNAddTwoStates(20, 21); }\n                  break;\n               case 21:\n                  if (curChar == 39 && kind > 77)\n                     kind = 77;\n                  break;\n               case 22:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 78)\n                     kind = 78;\n                  { jjCheckNAdd(22); }\n                  break;\n               default : break;\n            }\n         } while(i != startsAt);\n      }\n      else if (curChar < 128)\n      {\n         long l = 1L << (curChar & 077);\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 23:\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                  {\n                     if (kind > 78)\n                        kind = 78;\n                     { jjCheckNAdd(22); }\n                  }\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                     { jjCheckNAddTwoStates(20, 21); }\n                  break;\n               case 0:\n                  if ((0x7fffffe87fffffeL & l) == 0L)\n                     break;\n                  if (kind > 78)\n                     kind = 78;\n                  { jjCheckNAddStates(7, 9); }\n                  break;\n               case 2:\n                  { jjAddStates(4, 6); }\n                  break;\n               case 12:\n                  if ((0x2000000020L & l) != 0L)\n                     { jjAddStates(10, 11); }\n                  break;\n               case 16:\n                  { jjAddStates(12, 13); }\n                  break;\n               case 20:\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                     { jjCheckNAddTwoStates(20, 21); }\n                  break;\n               case 22:\n                  if ((0x7fffffe87fffffeL & l) == 0L)\n                     break;\n                  if (kind > 78)\n                     kind = 78;\n                  { jjCheckNAdd(22); }\n                  break;\n               default : break;\n            }\n         } while(i != startsAt);\n      }\n      else\n      {\n         int i2 = (curChar & 0xff) >> 6;\n         long l2 = 1L << (curChar & 077);\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 2:\n                  if ((jjbitVec0[i2] & l2) != 0L)\n                     { jjAddStates(4, 6); }\n                  break;\n               case 16:\n                  if ((jjbitVec0[i2] & l2) != 0L)\n                     { jjAddStates(12, 13); }\n                  break;\n               default : break;\n            }\n         } while(i != startsAt);\n      }\n      if (kind != 0x7fffffff)\n      {\n         jjmatchedKind = kind;\n         jjmatchedPos = curPos;\n         kind = 0x7fffffff;\n      }\n      ++curPos;\n      if ((i = jjnewStateCnt) == (startsAt = 23 - (jjnewStateCnt = startsAt)))\n         return curPos;\n      try { curChar = input_stream.readChar(); }\n      catch(java.io.IOException e) { return curPos; }\n   }\n}\nstatic final int[] jjnextStates = {\n   10, 11, 12, 18, 2, 3, 5, 20, 21, 22, 13, 14, 16, 17, \n};\n\n/** Token literal values. */\npublic static final String[] jjstrLiteralImages = {\n\"\", null, null, \"\\142\\157\\157\\154\", \"\\143\\157\\156\\163\\164\", \n\"\\143\\145\\151\\154\", \"\\143\\164\\155\\143\", \"\\103\", \"\\144\\157\\165\\142\\154\\145\", \"\\144\\164\\155\\143\", \n\"\\145\\156\\144\\151\\156\\151\\164\", \"\\145\\156\\144\\155\\157\\144\\165\\154\\145\", \n\"\\145\\156\\144\\162\\145\\167\\141\\162\\144\\163\", \"\\145\\156\\144\\163\\171\\163\\164\\145\\155\", \"\\146\\141\\154\\163\\145\", \n\"\\146\\154\\157\\157\\162\", \"\\146\\157\\162\\155\\165\\154\\141\", \"\\146\\165\\156\\143\", \"\\106\", \n\"\\147\\154\\157\\142\\141\\154\", \"\\107\", \"\\151\\156\\151\\164\", \"\\111\", \"\\151\\156\\164\", \"\\154\\141\\142\\145\\154\", \n\"\\155\\141\\170\", \"\\155\\144\\160\", \"\\155\\151\\156\", \"\\155\\157\\144\\165\\154\\145\", \"\\130\", \n\"\\156\\157\\156\\144\\145\\164\\145\\162\\155\\151\\156\\151\\163\\164\\151\\143\", \"\\120\\155\\141\\170\", \"\\120\\155\\151\\156\", \"\\120\", \n\"\\160\\162\\157\\142\\141\\142\\151\\154\\151\\163\\164\\151\\143\", \"\\160\\162\\157\\142\", \"\\162\\141\\164\\145\", \"\\162\\145\\167\\141\\162\\144\\163\", \n\"\\122\\155\\141\\170\", \"\\122\\155\\151\\156\", \"\\122\", \"\\123\", \n\"\\163\\164\\157\\143\\150\\141\\163\\164\\151\\143\", \"\\163\\171\\163\\164\\145\\155\", \"\\164\\162\\165\\145\", \"\\125\", \"\\41\", \"\\46\", \"\\174\", \n\"\\75\\76\", \"\\55\\76\", \"\\72\", \"\\73\", \"\\54\", \"\\56\\56\", \"\\50\", \"\\51\", \"\\133\", \"\\135\", \"\\173\", \n\"\\175\", \"\\75\", \"\\41\\75\", \"\\74\", \"\\76\", \"\\74\\75\", \"\\76\\75\", \"\\53\", \"\\55\", \"\\52\", \"\\57\", \n\"\\47\", \"\\74\\55\", \"\\77\", \"\\42\", null, null, null, null, null, };\nstatic protected Token jjFillToken()\n{\n   final Token t;\n   final String curTokenImage;\n   final int beginLine;\n   final int endLine;\n   final int beginColumn;\n   final int endColumn;\n   String im = jjstrLiteralImages[jjmatchedKind];\n   curTokenImage = (im == null) ? input_stream.GetImage() : im;\n   beginLine = input_stream.getBeginLine();\n   beginColumn = input_stream.getBeginColumn();\n   endLine = input_stream.getEndLine();\n   endColumn = input_stream.getEndColumn();\n   t = Token.newToken(jjmatchedKind, curTokenImage);\n\n   t.beginLine = beginLine;\n   t.endLine = endLine;\n   t.beginColumn = beginColumn;\n   t.endColumn = endColumn;\n\n   return t;\n}\n\nstatic int curLexState = 0;\nstatic int defaultLexState = 0;\nstatic int jjnewStateCnt;\nstatic int jjround;\nstatic int jjmatchedPos;\nstatic int jjmatchedKind;\n\n/** Get the next Token. */\npublic static Token getNextToken() \n{\n  Token specialToken = null;\n  Token matchedToken;\n  int curPos = 0;\n\n  EOFLoop :\n  for (;;)\n  {\n   try\n   {\n      curChar = input_stream.BeginToken();\n   }\n   catch(java.io.IOException e)\n   {\n      jjmatchedKind = 0;\n      jjmatchedPos = -1;\n      matchedToken = jjFillToken();\n      matchedToken.specialToken = specialToken;\n      return matchedToken;\n   }\n\n   jjmatchedKind = 0x7fffffff;\n   jjmatchedPos = 0;\n   curPos = jjMoveStringLiteralDfa0_0();\n   if (jjmatchedKind != 0x7fffffff)\n   {\n      if (jjmatchedPos + 1 < curPos)\n         input_stream.backup(curPos - jjmatchedPos - 1);\n      if ((jjtoToken[jjmatchedKind >> 6] & (1L << (jjmatchedKind & 077))) != 0L)\n      {\n         matchedToken = jjFillToken();\n         matchedToken.specialToken = specialToken;\n         return matchedToken;\n      }\n      else\n      {\n         if ((jjtoSpecial[jjmatchedKind >> 6] & (1L << (jjmatchedKind & 077))) != 0L)\n         {\n            matchedToken = jjFillToken();\n            if (specialToken == null)\n               specialToken = matchedToken;\n            else\n            {\n               matchedToken.specialToken = specialToken;\n               specialToken = (specialToken.next = matchedToken);\n            }\n         }\n         continue EOFLoop;\n      }\n   }\n   int error_line = input_stream.getEndLine();\n   int error_column = input_stream.getEndColumn();\n   String error_after = null;\n   boolean EOFSeen = false;\n   try { input_stream.readChar(); input_stream.backup(1); }\n   catch (java.io.IOException e1) {\n      EOFSeen = true;\n      error_after = curPos <= 1 ? \"\" : input_stream.GetImage();\n      if (curChar == '\\n' || curChar == '\\r') {\n         error_line++;\n         error_column = 0;\n      }\n      else\n         error_column++;\n   }\n   if (!EOFSeen) {\n      input_stream.backup(1);\n      error_after = curPos <= 1 ? \"\" : input_stream.GetImage();\n   }\n   throw new TokenMgrError(EOFSeen, curLexState, error_line, error_column, error_after, curChar, TokenMgrError.LEXICAL_ERROR);\n  }\n}\n\nstatic private void jjCheckNAdd(int state)\n{\n   if (jjrounds[state] != jjround)\n   {\n      jjstateSet[jjnewStateCnt++] = state;\n      jjrounds[state] = jjround;\n   }\n}\nstatic private void jjAddStates(int start, int end)\n{\n   do {\n      jjstateSet[jjnewStateCnt++] = jjnextStates[start];\n   } while (start++ != end);\n}\nstatic private void jjCheckNAddTwoStates(int state1, int state2)\n{\n   jjCheckNAdd(state1);\n   jjCheckNAdd(state2);\n}\n\nstatic private void jjCheckNAddStates(int start, int end)\n{\n   do {\n      jjCheckNAdd(jjnextStates[start]);\n   } while (start++ != end);\n}\n\n    /** Constructor. */\n    public Prism3To4TokenManager(SimpleCharStream stream){\n\n      if (input_stream != null)\n        throw new TokenMgrError(\"ERROR: Second call to constructor of static lexer. You must use ReInit() to initialize the static variables.\", TokenMgrError.STATIC_LEXER_ERROR);\n\n    input_stream = stream;\n  }\n\n  /** Constructor. */\n  public Prism3To4TokenManager (SimpleCharStream stream, int lexState){\n    ReInit(stream);\n    SwitchTo(lexState);\n  }\n\n  /** Reinitialise parser. */\n  static public void ReInit(SimpleCharStream stream)\n  {\n    jjmatchedPos = jjnewStateCnt = 0;\n    curLexState = defaultLexState;\n    input_stream = stream;\n    ReInitRounds();\n  }\n\n  static private void ReInitRounds()\n  {\n    int i;\n    jjround = 0x80000001;\n    for (i = 23; i-- > 0;)\n      jjrounds[i] = 0x80000000;\n  }\n\n  /** Reinitialise parser. */\n  static public void ReInit(SimpleCharStream stream, int lexState)\n  {\n    ReInit(stream);\n    SwitchTo(lexState);\n  }\n\n  /** Switch to specified lex state. */\n  static public void SwitchTo(int lexState)\n  {\n    if (lexState >= 1 || lexState < 0)\n      throw new TokenMgrError(\"Error: Ignoring invalid lexical state : \" + lexState + \". State unchanged.\", TokenMgrError.INVALID_LEXICAL_STATE);\n    else\n      curLexState = lexState;\n  }\n\n/** Lexer state names. */\npublic static final String[] lexStateNames = {\n   \"DEFAULT\",\n};\nstatic final long[] jjtoToken = {\n   0xfffffffffffffff9L, 0xffffL, \n};\nstatic final long[] jjtoSkip = {\n   0x6L, 0x0L, \n};\nstatic final long[] jjtoSpecial = {\n   0x6L, 0x0L, \n};\n    static protected SimpleCharStream  input_stream;\n\n    static private final int[] jjrounds = new int[23];\n    static private final int[] jjstateSet = new int[2 * 23];\n\n    \n    static protected char curChar;\n}\n"
  },
  {
    "path": "prism/src/parser/PrismParser.java",
    "content": "/* PrismParser.java */\n/* Generated By:JavaCC: Do not edit this line. PrismParser.java */\npackage parser;\n\nimport java.io.*;\nimport java.util.List;\nimport java.util.ArrayList;\nimport java.util.HashSet;\n\nimport jltl2ba.SimpleLTL;\nimport parser.BooleanUtils;\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.ModelInfo;\nimport parser.visitor.*;\nimport prism.ModelType;\nimport prism.PrismLangException;\n\n@SuppressWarnings({\"unused\", \"static-access\", \"serial\"})\npublic class PrismParser implements PrismParserConstants {\n        // The model associated with the properties file being parsed\n        private static ModelInfo modelInfo;\n\n        // List of keyword strings\n        private static ArrayList<String> keywordList = new ArrayList<>();\n        static {\n                keywordList.clear();\n                for (int i = PrismParserConstants.COMMENT+1; i < PrismParserConstants.NOT; i++) {\n                        keywordList.add(PrismParserConstants.tokenImage[i].replaceAll(\"\\\"\", \"\"));\n                }\n        }\n        private static HashSet<String> keywordSet = new HashSet<>(keywordList);\n\n        //-----------------------------------------------------------------------------------\n        // Main method for testing purposes\n        //-----------------------------------------------------------------------------------\n\n        public static void main(String[] args)\n        {\n                PrismParser p = null;\n                InputStream str = null;\n                String src = null;\n\n                try {\n                        if (args.length == 0) {\n                                System.out.println(\"Usage: java parser.PrismParser <switch> [<file>]\");\n                                System.out.println(\"Where: <switch> = -modulesfile or -mf\");\n                                System.out.println(\"                  -propertiesfile or -pf\");\n                                System.out.println(\"                  -expression or -e\");\n                                System.out.println(\"                  -ltl or -l\");\n                                System.exit(1);\n                        }\n\n                        p = new PrismParser();\n                        str = (args.length > 1) ? new FileInputStream(args[1]) : System.in;\n                        src = (args.length > 1) ? \"file \"+args[1] : \"stdin\";\n                        System.out.println(\"Reading from \"+src+\"...\\n\");\n\n                        if (args[0].equals(\"-modulesfile\") || args[0].equals(\"-mf\")) {\n                                ModulesFile mf = p.parseModulesFile(str);\n                                System.out.print(\"Modules file:\\n=============\\n\\n\" + mf);\n                                System.out.print(\"\\nTree:\\n=====\\n\" + mf.toTreeString());\n                                mf.tidyUp();\n                                System.out.print(\"\\nAnd after expansion:\\n====================\\n\\n\" +mf);\n                        }\n                        else if (args[0].equals(\"-propertiesfile\") || args[0].equals(\"-pf\")) {\n                                PropertiesFile pf = p.parsePropertiesFile(new ModulesFile(), str);\n                                System.out.print(\"Properties file:\\n================\\n\\n\" + pf);\n                                System.out.print(\"\\nTree:\\n=====\\n\" + pf.toTreeString());\n                                pf.tidyUp();\n                                System.out.print(\"\\nAnd after expansion:\\n====================\\n\\n\" + pf);\n                        }\n                        else if (args[0].equals(\"-expression\") || args[0].equals(\"-e\")) {\n                                Expression expr = p.parseSingleExpression(str);\n                                System.out.println(\"Expression: \" + expr.toString());\n                                System.out.print(\"Tree:\\n=====\\n\" + expr.toTreeString());\n                                expr.typeCheck();\n                                expr.semanticCheck();\n                                System.out.println(\"Type: \" + expr.getType().getTypeString());\n                                System.out.println(\"Eval: \" + expr.evaluate());\n                        }\n                        else if (args[0].equals(\"-ltl\") || args[0].equals(\"-l\")) {\n                                Expression expr = p.parseSingleLTLFormula(str);\n                                expr = (Expression) expr.accept(new ASTTraverseModify() {\n                                        public Object visit(ExpressionIdent e) throws PrismLangException\n                                        {\n                                                return new parser.ast.ExpressionVar(e.getName(), TypeBool.getInstance());\n                                        }\n                                });\n                                System.out.println(\"LTL formula: \" + expr.toString());\n                                System.out.print(\"Tree:\\n=====\\n\" + expr.toTreeString());\n                                expr.typeCheck();\n                                //expr.semanticCheck();\n                                System.out.println(\"Type: \" + expr.getType().getTypeString());\n                                boolean pnf = Expression.isPositiveNormalFormLTL(expr);\n                                System.out.println(\"Positive normal form: \" + pnf);\n                                System.out.println(\"Syntactically co-safe: \" + Expression.isCoSafeLTLSyntactic(expr));\n                                if (!pnf) {\n                                        Expression exprPnf = BooleanUtils.convertLTLToPositiveNormalForm(expr.deepCopy());\n                                        System.out.println(\"Positive normal form conversion: \" + exprPnf);\n                                        System.out.println(\"Syntactically co-safe: \" + Expression.isCoSafeLTLSyntactic(exprPnf));\n                                }\n                                Expression expr2 = (Expression) expr.deepCopy().accept(new ASTTraverseModify() {\n                                        public Object visit(ExpressionVar e) throws PrismLangException\n                                        {\n                                                        return new parser.ast.ExpressionLabel(e.getName());\n                                        }\n                                });\n                                SimpleLTL sltl = expr2.convertForJltl2ba();\n                                System.out.println(\"LBT: \" + sltl.toStringLBT());\n                                System.out.println(\"Spot: \" + sltl.toStringSpot());\n                                System.out.println(\"Spin: \" + sltl.toStringSpin());\n                        } else {\n                                System.out.println(\"Unknown switch\"); System.exit(1);\n                        }\n                }\n                catch (PrismLangException e) {\n                        System.out.println(\"Error in \"+src+\": \" + e.getMessage()+\".\"); System.exit(1);\n                }\n                catch (FileNotFoundException e) {\n                        System.out.println(e); System.exit(1);\n                }\n        }\n\n        //-----------------------------------------------------------------------------------\n        // Methods called by Prism\n        //-----------------------------------------------------------------------------------\n\n        // Constructor\n\n        public PrismParser()\n        {\n                // Call default constructor\n                this(System.in);\n                setTabSize(8);\n        }\n\n        // Parse modules file\n\n        public ModulesFile parseModulesFile(InputStream str) throws PrismLangException { return parseModulesFile(str, null); }\n\n        public ModulesFile parseModulesFile(InputStream str, ModelType typeOverride) throws PrismLangException\n        {\n                ModulesFile mf = null;\n\n                // (Re)start parser\n                ReInit(str);\n                // Parse\n                try {\n                        mf = ModulesFile();\n                }\n                catch (ParseException e) {\n                        throw generateSyntaxError(e);\n                }\n                // Override type of model if requested\n                if (typeOverride != null) {\n                        mf.setModelTypeInFile(typeOverride);\n                }\n\n                return mf;\n        }\n\n        // Parse properties file (pass ModulesFile in to get at its constants)\n\n        public PropertiesFile parsePropertiesFile(ModelInfo modelInfo, InputStream str) throws PrismLangException\n        { return parsePropertiesFile(modelInfo, str, false); }\n\n        public PropertiesFile parsePropertiesFile(ModelInfo modelInfo, InputStream str, boolean strict) throws PrismLangException\n        {\n                PropertiesFile pf = null;\n\n                // (Re)start parser\n                ReInit(str);\n                this.modelInfo = modelInfo;\n                // Parse\n                try {\n                        pf = strict ? PropertiesFile() : PropertiesFileSemicolonless();\n                }\n                catch (ParseException e) {\n                        throw generateSyntaxError(e);\n                }\n\n                return pf;\n        }\n\n        // Parse a single expression\n\n        public Expression parseSingleExpression(InputStream str) throws PrismLangException\n        {\n                Expression expr = null;\n\n                // (Re)start parser\n                ReInit(str);\n                // Parse\n                try {\n                        expr = SingleExpression();\n                }\n                catch (ParseException e) {\n                        throw generateSyntaxError(e);\n                }\n                return expr;\n        }\n\n        // Parse a single LTL formula\n\n        public Expression parseSingleLTLFormula(InputStream str) throws PrismLangException\n        {\n                Expression expr = null;\n\n                // (Re)start parser\n                ReInit(str);\n                // Parse\n                try {\n                        expr = SingleLTLFormula();\n                }\n                catch (ParseException e) {\n                        throw generateSyntaxError(e);\n                }\n                return expr;\n        }\n\n        // Parse a for loop\n\n        public ForLoop parseForLoop(InputStream str) throws PrismLangException\n        {\n                ForLoop fl = null;\n\n                // (Re)start parser\n                ReInit(str);\n                // Parse\n                try {\n                        fl = ForLoop();\n                }\n                catch (ParseException e) {\n                        throw generateSyntaxError(e);\n                }\n                return fl;\n        }\n\n        //-----------------------------------------------------------------------------------\n        // Some utility methods\n        //-----------------------------------------------------------------------------------\n\n        /**\n\t * Get comment block directly preceding a token and remove \"//\" characters\n\t */\n        public static String getPrecedingCommentBlock(Token firstToken)\n        {\n                String comment = \"\", s;\n                Token t = firstToken;\n\n                // extract any comment from the previous lines of the file\n                if (t.specialToken != null && !(t.specialToken.kind == PrismParserConstants.WHITESPACE && t.specialToken.image.matches(\"[\\\\n\\\\r]*\"))) {\n                        // trace back thru special tokens that are comments\n                        t = t.specialToken;\n                        while (t.specialToken != null && !(t.specialToken.kind == PrismParserConstants.WHITESPACE && t.specialToken.image.matches(\"[\\\\n\\\\r]*\")))\n                                t = t.specialToken;\n                        // concatenate comment special tokens\n                        while (t != null) {\n                                s = t.image;\n                                // strip any nasty carriage returns\n                                s = s.replaceAll(\"\\r\", \"\");\n                                // remove \"//\" and preceding/subsequent spaces/tabs from comments\n                                if (t.kind == PrismParserConstants.COMMENT) {\n                                        while (comment.length() > 0 && (\"\"+comment.charAt(comment.length()-1)).matches(\"[ \\t]\"))\n                                                comment = comment.substring(0,comment.length()-1);\n                                        s = s.substring(2);\n                                        s = s.replaceFirst(\"[ \\t]*\", \"\");\n                                }\n                                comment += s;\n                                t = t.next;\n                        }\n                }\n                // remove final new line (if present)\n                if (comment.length() > 0 && (comment.charAt(comment.length()-1) == '\\n'))\n                        comment = comment.substring(0,comment.length()-1);\n\n                return comment;\n        }\n\n        // Add \"//\"s into comment block\n\n        public static String slashCommentBlock(String comment)\n        {\n                int i;\n                String s, res = \"\";\n                // break into lines\n                while ((i = comment.indexOf(\"\\n\")) != -1) {\n                        s = comment.substring(0, i);\n                        comment = comment.substring(i+1);\n                        // add \"//\" to non-empty lines\n                        if (s.trim().length()>0) res += \"// \" + s;\n                        res += \"\\n\";\n                }\n                // deal with any trailing characters (with no new line ending them)\n                if (comment.trim().length()>0) res += \"// \" + comment + \"\\n\";\n                return res;\n        }\n\n        /**\n\t * Test a string to see if it is a PRISM language keyword.\n\t */\n        public static boolean isKeyword(String s)\n        {\n                return keywordSet.contains(s);\n        }\n\n        /**\n\t * Get access to the list of all PRISM language keywords.\n\t */\n        public static List<String> getListOfKeywords()\n        {\n                return keywordList;\n        }\n\n        /**\n\t * Set the tab size used by the lexer/parser.\n\t */\n        public void setTabSize(int size)\n        {\n                SimpleCharStream.setTabSize(size);\n        }\n\n        /**\n\t * Get the tab size used by the lexer/parser.\n\t */\n        public int getTabSize()\n        {\n                return SimpleCharStream.getTabSize();\n        }\n\n        /**\n\t * Generate a syntax error (PrismLangException) from a ParseException.\n\t */\n        protected PrismLangException generateSyntaxError(ParseException e)\n        {\n                if (e == null) return new PrismLangException(\"Syntax error\");\n                // No token: was prob created manually so use message if present\n                if (e.currentToken == null) {\n                        String msg = e.getMessage();\n                        String exMsg = \"Syntax error\";\n                        if (msg != null && msg.length() > 0)\n                                exMsg += \": \" + msg;\n                        return new PrismLangException(exMsg);\n                }\n                // Use current/next token to find location of error\n                // But don't use error message if too long (esp if generated by JavaCC)\n                else {\n                        ExpressionIdent tmp;\n                        if (e.currentToken.next == null) {\n                                tmp = new ExpressionIdent(e.currentToken.image);\n                                tmp.setPosition(e.currentToken);\n                        } else {\n                                tmp = new ExpressionIdent(e.currentToken.next.image);\n                                tmp.setPosition(e.currentToken.next);\n                        }\n                        String msg = e.getMessage();\n                        String exMsg = \"Syntax error\";\n                        if (msg != null && msg.length() > 0 && msg.length() < 20)\n                                exMsg += \": \" + msg;\n                        return new PrismLangException(exMsg, tmp);\n                }\n        }\n\n        //-----------------------------------------------------------------------------------\n        // A few classes for temporary storage of bits of the AST\n        //-----------------------------------------------------------------------------------\n\n        static class ExpressionPair { public Expression expr1 = null; public Expression expr2 = null; }\n\n//-----------------------------------------------------------------------------------\n// Top-level productions\n//-----------------------------------------------------------------------------------\n\n// Modules file\n  static final public \nModulesFile ModulesFile() throws ParseException, PrismLangException {ModelType type = null;\n        int typeCount = 0;\n        Token typeDupe = null;\n        Declaration global;\n        parser.ast.Module m = null;\n        RenamedModule rm = null;\n        RewardStruct rs = null;\n        Expression init = null;\n        ObservableVars obsVars = null;\n        Observable obs = null;\n        int initCount = 0;\n        Expression initDupe = null;\n        ModulesFile mf = new ModulesFile();\n        Token begin = null;\n    label_1:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case CONST:\n      case CTMC:\n      case DTMC:\n      case FORMULA:\n      case GLOBAL:\n      case INIT:\n      case LABEL:\n      case MDP:\n      case MODULE:\n      case NONDETERMINISTIC:\n      case OBSERVABLE:\n      case OBSERVABLES:\n      case POMDP:\n      case POPTA:\n      case PROBABILISTIC:\n      case PROB:\n      case PTA:\n      case RATE:\n      case REWARDS:\n      case STOCHASTIC:\n      case SYSTEM:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[0] = jj_gen;\n        break label_1;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case CTMC:\n      case DTMC:\n      case MDP:\n      case NONDETERMINISTIC:\n      case POMDP:\n      case POPTA:\n      case PROBABILISTIC:\n      case PTA:\n      case STOCHASTIC:{\nbegin = getToken(1);\n        type = ModulesFileType();\ntypeCount++; if (typeCount == 2) typeDupe = getToken(0);\n        break;\n        }\n      case FORMULA:{\n        FormulaDef(mf.getFormulaList());\n        break;\n        }\n      case LABEL:{\n        LabelDef(mf.getLabelList());\n        break;\n        }\n      case CONST:\n      case PROB:\n      case RATE:{\n        ConstantDef(mf.getConstantList());\n        break;\n        }\n      case GLOBAL:{\n        // Global variable\n                global = GlobalDecl();\nmf.addGlobal(global);\n        break;\n        }\n      default:\n        jj_la1[1] = jj_gen;\n        if (jj_2_1(2147483647)) {\n          rm = RenamedModule();\nmf.addRenamedModule(rm);\n        } else {\n          switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n          case MODULE:{\n            // Module\n                    m = Module();\nmf.addModule(m);\n            break;\n            }\n          case REWARDS:{\n            // Reward structure\n                    rs = RewardStruct();\nmf.addRewardStruct(rs);\n            break;\n            }\n          case INIT:{\n            // Initial states (\"init...endinit\" construct)\n                    init = Init();\nmf.setInitialStates(init); initCount++; if (initCount == 2) initDupe = init;\n            break;\n            }\n          case OBSERVABLES:{\n            // Observables\n                    obsVars = ObservableVars();\nmf.addObservableVarList(obsVars);\n            break;\n            }\n          case OBSERVABLE:{\n            obs = Observable();\nmf.addObservableDefinition(obs);\n            break;\n            }\n          case SYSTEM:{\n            SystemEndsystem(mf);\n            break;\n            }\n          default:\n            jj_la1[2] = jj_gen;\n            jj_consume_token(-1);\n            throw new ParseException();\n          }\n        }\n      }\n    }\n    jj_consume_token(0);\n// Check for multiple instances of some items\n                if (typeDupe != null) {\n                        ExpressionIdent tmp = new ExpressionIdent(typeDupe.image);\n                        tmp.setPosition(typeDupe);\n                        {if (true) throw new PrismLangException(\"There were multiple model type declarations\", tmp);}\n                }\n                if (initDupe != null) {\n                        {if (true) throw new PrismLangException(\"There were multiple init...endinit constructs\", initDupe);}\n                }\n\n                // Set model type (might be null, i.e., unspecified)\n                mf.setModelTypeInFile(type);\n\n                // Return completed ModulesFile object\n                mf.setPosition(begin != null? begin: getToken(0), getToken(0));\n                {if (\"\" != null) return mf;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Properties file\n  static final public \nPropertiesFile PropertiesFile() throws ParseException, PrismLangException {PropertiesFile pf = new PropertiesFile(modelInfo);\n        Property prop;\n        Token begin = null;\nbegin = getToken(1);\n    label_2:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case A:\n      case CONST:\n      case E:\n      case FALSE:\n      case FILTER:\n      case FUNC:\n      case LABEL:\n      case MAX:\n      case MIN:\n      case PMAXMAX:\n      case PMAXMIN:\n      case PMAX:\n      case PMINMAX:\n      case PMINMIN:\n      case PMIN:\n      case P:\n      case PROB:\n      case RATE:\n      case RMAXMAX:\n      case RMAXMIN:\n      case RMAX:\n      case RMINMAX:\n      case RMINMIN:\n      case RMIN:\n      case R:\n      case S:\n      case TRUE:\n      case NOT:\n      case LPARENTH:\n      case DLBRACKET:\n      case DLT:\n      case MINUS:\n      case DQUOTE:\n      case REG_INT:\n      case REG_DOUBLE:\n      case REG_IDENT:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[3] = jj_gen;\n        break label_2;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case A:\n      case E:\n      case FALSE:\n      case FILTER:\n      case FUNC:\n      case MAX:\n      case MIN:\n      case PMAXMAX:\n      case PMAXMIN:\n      case PMAX:\n      case PMINMAX:\n      case PMINMIN:\n      case PMIN:\n      case P:\n      case RMAXMAX:\n      case RMAXMIN:\n      case RMAX:\n      case RMINMAX:\n      case RMINMIN:\n      case RMIN:\n      case R:\n      case S:\n      case TRUE:\n      case NOT:\n      case LPARENTH:\n      case DLBRACKET:\n      case DLT:\n      case MINUS:\n      case DQUOTE:\n      case REG_INT:\n      case REG_DOUBLE:\n      case REG_IDENT:{\n        prop = Property();\npf.addProperty(prop);\n        label_3:\n        while (true) {\n          jj_consume_token(SEMICOLON);\n          switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n          case SEMICOLON:{\n            ;\n            break;\n            }\n          default:\n            jj_la1[4] = jj_gen;\n            break label_3;\n          }\n        }\n        break;\n        }\n      case LABEL:{\n        LabelDef(pf.getLabelList());\n        break;\n        }\n      case CONST:\n      case PROB:\n      case RATE:{\n        ConstantDef(pf.getConstantList());\n        break;\n        }\n      default:\n        jj_la1[5] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n    }\n    jj_consume_token(0);\npf.setPosition(begin, getToken(0)); {if (\"\" != null) return pf;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Properties file with optional semicolons - beware of potential ambiguities\n  static final public \nPropertiesFile PropertiesFileSemicolonless() throws ParseException, PrismLangException {PropertiesFile pf = new PropertiesFile(modelInfo);\n        Property prop;\n        Token begin = null;\nbegin = getToken(1);\n    label_4:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case A:\n      case CONST:\n      case E:\n      case FALSE:\n      case FILTER:\n      case FUNC:\n      case LABEL:\n      case MAX:\n      case MIN:\n      case PMAXMAX:\n      case PMAXMIN:\n      case PMAX:\n      case PMINMAX:\n      case PMINMIN:\n      case PMIN:\n      case P:\n      case PROB:\n      case RATE:\n      case RMAXMAX:\n      case RMAXMIN:\n      case RMAX:\n      case RMINMAX:\n      case RMINMIN:\n      case RMIN:\n      case R:\n      case S:\n      case TRUE:\n      case NOT:\n      case LPARENTH:\n      case DLBRACKET:\n      case DLT:\n      case MINUS:\n      case DQUOTE:\n      case REG_INT:\n      case REG_DOUBLE:\n      case REG_IDENT:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[6] = jj_gen;\n        break label_4;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case A:\n      case E:\n      case FALSE:\n      case FILTER:\n      case FUNC:\n      case MAX:\n      case MIN:\n      case PMAXMAX:\n      case PMAXMIN:\n      case PMAX:\n      case PMINMAX:\n      case PMINMIN:\n      case PMIN:\n      case P:\n      case RMAXMAX:\n      case RMAXMIN:\n      case RMAX:\n      case RMINMAX:\n      case RMINMIN:\n      case RMIN:\n      case R:\n      case S:\n      case TRUE:\n      case NOT:\n      case LPARENTH:\n      case DLBRACKET:\n      case DLT:\n      case MINUS:\n      case DQUOTE:\n      case REG_INT:\n      case REG_DOUBLE:\n      case REG_IDENT:{\n        prop = Property();\n        label_5:\n        while (true) {\n          switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n          case SEMICOLON:{\n            ;\n            break;\n            }\n          default:\n            jj_la1[7] = jj_gen;\n            break label_5;\n          }\n          jj_consume_token(SEMICOLON);\n        }\npf.addProperty(prop);\n        break;\n        }\n      case LABEL:{\n        LabelDef(pf.getLabelList());\n        break;\n        }\n      case CONST:\n      case PROB:\n      case RATE:{\n        ConstantDef(pf.getConstantList());\n        break;\n        }\n      default:\n        jj_la1[8] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n    }\n    jj_consume_token(0);\npf.setPosition(begin, getToken(0)); {if (\"\" != null) return pf;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Property - expression, with optional name/comment\n  static final public \nProperty Property() throws ParseException {String name = null;\n        Expression expr;\n        Property prop;\n        Token begin = null;\nbegin = getToken(1);\n    if (jj_2_2(2147483647)) {\n      jj_consume_token(DQUOTE);\n      name = Identifier();\n      jj_consume_token(DQUOTE);\n      jj_consume_token(COLON);\n    } else {\n      ;\n    }\n    expr = ExpressionITE(true, false);\nprop = new Property(expr, name, getPrecedingCommentBlock(begin));\nprop.setPosition(begin, getToken(0)); {if (\"\" != null) return prop;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// A single expression\n  static final public \nExpression SingleExpression() throws ParseException {Expression ret;\n    ret = Expression(false, false);\n    jj_consume_token(0);\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// A single LTL formula\n  static final public \nExpression SingleLTLFormula() throws ParseException {Expression ret;\n    ret = Expression(true, true);\n    jj_consume_token(0);\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n//-----------------------------------------------------------------------------------\n// Modules file stuff (a few bits of which are reused for property files)\n//-----------------------------------------------------------------------------------\n\n// Keyword denoting model type\n  static final public \nModelType ModulesFileType() throws ParseException {ModelType modelType = null;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case DTMC:\n    case PROBABILISTIC:{\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case DTMC:{\n        jj_consume_token(DTMC);\n        break;\n        }\n      case PROBABILISTIC:{\n        jj_consume_token(PROBABILISTIC);\n        break;\n        }\n      default:\n        jj_la1[9] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\nmodelType=ModelType.DTMC;\n      break;\n      }\n    case MDP:\n    case NONDETERMINISTIC:{\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case MDP:{\n        jj_consume_token(MDP);\n        break;\n        }\n      case NONDETERMINISTIC:{\n        jj_consume_token(NONDETERMINISTIC);\n        break;\n        }\n      default:\n        jj_la1[10] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\nmodelType=ModelType.MDP;\n      break;\n      }\n    case CTMC:\n    case STOCHASTIC:{\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case CTMC:{\n        jj_consume_token(CTMC);\n        break;\n        }\n      case STOCHASTIC:{\n        jj_consume_token(STOCHASTIC);\n        break;\n        }\n      default:\n        jj_la1[11] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\nmodelType=ModelType.CTMC;\n      break;\n      }\n    case PTA:{\n      jj_consume_token(PTA);\nmodelType=ModelType.PTA;\n      break;\n      }\n    case POMDP:{\n      jj_consume_token(POMDP);\nmodelType=ModelType.POMDP;\n      break;\n      }\n    case POPTA:{\n      jj_consume_token(POPTA);\nmodelType=ModelType.POPTA;\n      break;\n      }\n    default:\n      jj_la1[12] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return modelType;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Formula definition\n  static final public \nvoid FormulaDef(FormulaList formulaList) throws ParseException {ExpressionIdent name = null;\n        Expression expr = null;\n    jj_consume_token(FORMULA);\n    name = IdentifierExpression();\n    jj_consume_token(EQ);\n    expr = Expression(false, false);\n    jj_consume_token(SEMICOLON);\nformulaList.addFormula(name, expr);\n}\n\n// Label definition\n  static final public \nvoid LabelDef(LabelList labelList) throws ParseException, PrismLangException {ExpressionIdent name = null;\n        Expression expr = null;\n    if (jj_2_3(2147483647)) {\n      jj_consume_token(LABEL);\n      jj_consume_token(DQUOTE);\n      name = IdentifierExpression();\n      jj_consume_token(DQUOTE);\n      jj_consume_token(EQ);\n      expr = Expression(false, false);\n      jj_consume_token(SEMICOLON);\nlabelList.addLabel(name, expr);\n    } else if (jj_2_4(2147483647)) {\n      jj_consume_token(LABEL);\n      name = IdentifierExpression();\n{if (true) throw new PrismLangException(\"Label names must be enclosed in double-quotes\", name);}\n    } else {\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n}\n\n// Constant definition\n  static final public \nvoid ConstantDef(ConstantList constantList) throws ParseException {Type type = TypeInt.getInstance();\n        ExpressionIdent name = null;\n        Expression expr = null;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case CONST:{\n      jj_consume_token(CONST);\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case BOOL:\n      case DOUBLE:\n      case INT:{\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case INT:{\n          jj_consume_token(INT);\ntype=TypeInt.getInstance();\n          break;\n          }\n        case DOUBLE:{\n          jj_consume_token(DOUBLE);\ntype=TypeDouble.getInstance();\n          break;\n          }\n        case BOOL:{\n          jj_consume_token(BOOL);\ntype=TypeBool.getInstance();\n          break;\n          }\n        default:\n          jj_la1[13] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n        break;\n        }\n      default:\n        jj_la1[14] = jj_gen;\n        ;\n      }\n      break;\n      }\n    case PROB:\n    case RATE:{\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case RATE:{\n        jj_consume_token(RATE);\n        break;\n        }\n      case PROB:{\n        jj_consume_token(PROB);\n        break;\n        }\n      default:\n        jj_la1[15] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\ntype=TypeDouble.getInstance();\n      break;\n      }\n    default:\n      jj_la1[16] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    // Name and (optional) initial value\n            name = IdentifierExpression();\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case EQ:{\n      jj_consume_token(EQ);\n      expr = Expression(false, false);\n      break;\n      }\n    default:\n      jj_la1[17] = jj_gen;\n      ;\n    }\n    jj_consume_token(SEMICOLON);\nconstantList.addConstant(name, expr, type);\n}\n\n// Global variable declaration\n  static final public \nDeclaration GlobalDecl() throws ParseException {Declaration decl = null;\n    jj_consume_token(GLOBAL);\n    decl = Declaration();\n{if (\"\" != null) return decl;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Variable declaration\n  static final public \nDeclaration Declaration() throws ParseException {Declaration decl;\n        String name = null;\n        DeclarationType declType;\n        Expression init = null;\n        Token begin = null;\nbegin = getToken(1);\n    name = Identifier();\n    jj_consume_token(COLON);\n    declType = DeclarationVarType();\ndecl = new Declaration(name, declType);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case INIT:{\n      jj_consume_token(INIT);\n      init = Expression(false, false);\ndecl.setStart(init);\n      break;\n      }\n    default:\n      jj_la1[18] = jj_gen;\n      ;\n    }\n    jj_consume_token(SEMICOLON);\ndecl.setPosition(begin, getToken(0)); {if (\"\" != null) return decl;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Type part of a declaration\n  static final public \nDeclarationType DeclarationVarType() throws ParseException {Expression low = null, high = null;\n        DeclarationType declType, subtype;\n        Token begin = null;\nbegin = getToken(1);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LBRACKET:{\n      jj_consume_token(LBRACKET);\n      low = Expression(false, false);\n      jj_consume_token(DOTS);\n      high = Expression(false, false);\n      jj_consume_token(RBRACKET);\ndeclType = new DeclarationInt(low, high);\n      break;\n      }\n    case INT:{\n      jj_consume_token(INT);\ndeclType = new DeclarationIntUnbounded();\n      break;\n      }\n    case BOOL:{\n      jj_consume_token(BOOL);\ndeclType = new DeclarationBool();\n      break;\n      }\n    case CLOCK:{\n      jj_consume_token(CLOCK);\ndeclType = new DeclarationClock();\n      break;\n      }\n    default:\n      jj_la1[19] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\ndeclType.setPosition(begin, getToken(0)); {if (\"\" != null) return declType;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Module\n  static final public \nparser.ast.Module Module() throws ParseException {ExpressionIdent name = null;\n        Declaration var = null;\n        Expression invar;\n        Command comm = null;\n        parser.ast.Module module = null;\n        Token begin = null;\n    begin = jj_consume_token(MODULE);\n    name = IdentifierExpression();\nmodule = new parser.ast.Module(name.getName());\n    label_6:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case REG_IDENT:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[20] = jj_gen;\n        break label_6;\n      }\n      var = Declaration();\nmodule.addDeclaration(var);\n    }\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case INVARIANT:{\n      jj_consume_token(INVARIANT);\n      invar = Expression(false, false);\n      jj_consume_token(ENDINVARIANT);\nmodule.setInvariant(invar);\n      break;\n      }\n    default:\n      jj_la1[21] = jj_gen;\n      ;\n    }\n    label_7:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACKET:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[22] = jj_gen;\n        break label_7;\n      }\n      comm = Command();\nmodule.addCommand(comm);\n    }\n    jj_consume_token(ENDMODULE);\nmodule.setPosition(begin, getToken(0)); module.setNameASTElement(name); {if (\"\" != null) return module;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Command\n  static final public \nCommand Command() throws ParseException {String synch = null;\n        Expression guard = null;\n        Updates updates = null;\n        Command comm = new Command();\n        Token begin = null;\n    // Synchronisation action-label\n            begin = jj_consume_token(LBRACKET);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_IDENT:{\n      synch = Identifier();\ncomm.setSynch(synch);\n      break;\n      }\n    default:\n      jj_la1[23] = jj_gen;\n      ;\n    }\n    jj_consume_token(RBRACKET);\n    // Guard/updates\n            guard = Expression(false, false);\ncomm.setGuard(guard);\n    jj_consume_token(RARROW);\n    updates = Updates();\ncomm.setUpdates(updates);\n    jj_consume_token(SEMICOLON);\ncomm.setPosition(begin, getToken(0)); {if (\"\" != null) return comm;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Updates\n  static final public \nUpdates Updates() throws ParseException {Expression prob;\n        Update update;\n        Updates updates = new Updates();\n        Token begin = null;\nbegin = getToken(1);\n    if (jj_2_5(2147483647)) {\n      update = Update();\nupdates.addUpdate(null, update);\n    } else {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case A:\n      case E:\n      case FALSE:\n      case FILTER:\n      case FUNC:\n      case F:\n      case G:\n      case MAX:\n      case MIN:\n      case X:\n      case PMAXMAX:\n      case PMAXMIN:\n      case PMAX:\n      case PMINMAX:\n      case PMINMIN:\n      case PMIN:\n      case P:\n      case RMAXMAX:\n      case RMAXMIN:\n      case RMAX:\n      case RMINMAX:\n      case RMINMIN:\n      case RMIN:\n      case R:\n      case S:\n      case TRUE:\n      case NOT:\n      case LPARENTH:\n      case LBRACKET:\n      case DLBRACKET:\n      case DLT:\n      case MINUS:\n      case DQUOTE:\n      case REG_INT:\n      case REG_DOUBLE:\n      case REG_IDENT:{\n        prob = ProbOrRateOrInterval();\n        jj_consume_token(COLON);\n        update = Update();\nupdates.addUpdate(prob, update);\n        label_8:\n        while (true) {\n          switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n          case PLUS:{\n            ;\n            break;\n            }\n          default:\n            jj_la1[24] = jj_gen;\n            break label_8;\n          }\n          jj_consume_token(PLUS);\n          prob = ProbOrRateOrInterval();\n          jj_consume_token(COLON);\n          update = Update();\nupdates.addUpdate(prob, update);\n        }\n        break;\n        }\n      default:\n        jj_la1[25] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n    }\nupdates.setPosition(begin, getToken(0)); {if (\"\" != null) return updates;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n  static final public Expression ProbOrRateOrInterval() throws ParseException {Expression prob;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case A:\n    case E:\n    case FALSE:\n    case FILTER:\n    case FUNC:\n    case F:\n    case G:\n    case MAX:\n    case MIN:\n    case X:\n    case PMAXMAX:\n    case PMAXMIN:\n    case PMAX:\n    case PMINMAX:\n    case PMINMIN:\n    case PMIN:\n    case P:\n    case RMAXMAX:\n    case RMAXMIN:\n    case RMAX:\n    case RMINMAX:\n    case RMINMIN:\n    case RMIN:\n    case R:\n    case S:\n    case TRUE:\n    case NOT:\n    case LPARENTH:\n    case DLBRACKET:\n    case DLT:\n    case MINUS:\n    case DQUOTE:\n    case REG_INT:\n    case REG_DOUBLE:\n    case REG_IDENT:{\n      prob = Expression(false, false);\n      break;\n      }\n    case LBRACKET:{\n      prob = ExpressionInterval(false, false);\n      break;\n      }\n    default:\n      jj_la1[26] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return prob;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n  static final public Update Update() throws ParseException {Update update = new Update();\n        Token begin = null;\nbegin = getToken(1);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LPARENTH:{\n      UpdateElement(update);\n      label_9:\n      while (true) {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case AND:{\n          ;\n          break;\n          }\n        default:\n          jj_la1[27] = jj_gen;\n          break label_9;\n        }\n        jj_consume_token(AND);\n        UpdateElement(update);\n      }\n      break;\n      }\n    case TRUE:{\n      jj_consume_token(TRUE);\n      break;\n      }\n    default:\n      jj_la1[28] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\nupdate.setPosition(begin, getToken(0)); {if (\"\" != null) return update;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n  static final public void UpdateElement(Update update) throws ParseException {ExpressionIdent var = null;\n        Expression expr = null;\n        Token begin = null;\n    begin = jj_consume_token(LPARENTH);\n    var = IdentifierPrime();\n    jj_consume_token(EQ);\n    expr = Expression(false, false);\n    jj_consume_token(RPARENTH);\nUpdateElement ue = new UpdateElement(var, expr); ue.setPosition(begin, getToken(0)); update.addElement(ue);\n}\n\n// Module renaming\n  static final public \nRenamedModule RenamedModule() throws ParseException {ExpressionIdent name = null, base = null;\n        RenamedModule rm = null;\n        Token begin = null;\n    begin = jj_consume_token(MODULE);\n    name = IdentifierExpression();\n    jj_consume_token(EQ);\n    base = IdentifierExpression();\nrm = new RenamedModule(name.getName(), base.getName());\n    jj_consume_token(LBRACKET);\n    Rename(rm);\n    label_10:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case COMMA:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[29] = jj_gen;\n        break label_10;\n      }\n      jj_consume_token(COMMA);\n      Rename(rm);\n    }\n    jj_consume_token(RBRACKET);\n    jj_consume_token(ENDMODULE);\nrm.setPosition(begin, getToken(0)); rm.setNameASTElement(name); rm.setBaseModuleASTElement(base); {if (\"\" != null) return rm;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n  static final public void Rename(RenamedModule rm) throws ParseException {ExpressionIdent id1 = null, id2 = null;\n    // NB: have to explicitly include keywords for functions because they can be renamed\n            id1 = IdentifierExpressionMinMax();\n    jj_consume_token(EQ);\n    id2 = IdentifierExpressionMinMax();\nrm.addRename(id1.getName(), id2.getName(), id1, id2);\n}\n\n// Reward structure\n  static final public \nRewardStruct RewardStruct() throws ParseException {String name = null, s = null;\n        Expression guard = null, value = null;\n        RewardStruct rs = new RewardStruct();\n        RewardStructItem rsi;\n        Token begin = null, begin2 = null;\n    begin = jj_consume_token(REWARDS);\n    if (jj_2_6(2147483647)) {\n      jj_consume_token(DQUOTE);\n      name = Identifier();\n      jj_consume_token(DQUOTE);\nrs.setName(name);\n    } else {\n      ;\n    }\n    label_11:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case A:\n      case E:\n      case FALSE:\n      case FILTER:\n      case FUNC:\n      case F:\n      case G:\n      case MAX:\n      case MIN:\n      case X:\n      case PMAXMAX:\n      case PMAXMIN:\n      case PMAX:\n      case PMINMAX:\n      case PMINMIN:\n      case PMIN:\n      case P:\n      case RMAXMAX:\n      case RMAXMIN:\n      case RMAX:\n      case RMINMAX:\n      case RMINMIN:\n      case RMIN:\n      case R:\n      case S:\n      case TRUE:\n      case NOT:\n      case LPARENTH:\n      case LBRACKET:\n      case DLBRACKET:\n      case DLT:\n      case MINUS:\n      case DQUOTE:\n      case REG_INT:\n      case REG_DOUBLE:\n      case REG_IDENT:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[30] = jj_gen;\n        break label_11;\n      }\nbegin2 = getToken(1); s = null;\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACKET:{\n        jj_consume_token(LBRACKET);\ns = \"\";\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case REG_IDENT:{\n          s = Identifier();\n          break;\n          }\n        default:\n          jj_la1[31] = jj_gen;\n          ;\n        }\n        jj_consume_token(RBRACKET);\n        break;\n        }\n      default:\n        jj_la1[32] = jj_gen;\n        ;\n      }\n      guard = Expression(false, false);\n      jj_consume_token(COLON);\n      value = Expression(false, false);\n      jj_consume_token(SEMICOLON);\nrsi = new RewardStructItem(s, guard, value); rsi.setPosition(begin2, getToken(0)); rs.addItem(rsi);\n    }\n    jj_consume_token(ENDREWARDS);\nrs.setPosition(begin, getToken(0)); {if (\"\" != null) return rs;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Initial states (\"init...endinit\" construct)\n  static final public \nExpression Init() throws ParseException {Expression expr = null;\n    jj_consume_token(INIT);\n    expr = Expression(false, false);\n    jj_consume_token(ENDINIT);\n{if (\"\" != null) return expr;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Observable variables list (for partially observable models)\n  static final public \nObservableVars ObservableVars() throws ParseException {Token begin = null;\n        ObservableVars obsVars = null;\n        Expression exprVar = null;\nbegin = getToken(1);\n    jj_consume_token(OBSERVABLES);\nobsVars = new ObservableVars();\n    exprVar = IdentifierExpression();\nobsVars.addVar(exprVar);\n    label_12:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case COMMA:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[33] = jj_gen;\n        break label_12;\n      }\n      jj_consume_token(COMMA);\n      exprVar = IdentifierExpression();\nobsVars.addVar(exprVar);\n    }\n    jj_consume_token(ENDOBSERVABLES);\nobsVars.setPosition(begin, getToken(0)); {if (\"\" != null) return obsVars;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Individual observable (for partially observable models)\n  static final public \nObservable Observable() throws ParseException {Token begin = null;\n        String name = null;\n        Expression defn = null;\nbegin = getToken(1);\n    jj_consume_token(OBSERVABLE);\n    jj_consume_token(DQUOTE);\n    name = Identifier();\n    jj_consume_token(DQUOTE);\n    jj_consume_token(EQ);\n    defn = Expression(false, false);\n    jj_consume_token(SEMICOLON);\nObservable obs = new Observable(name, defn); obs.setPosition(begin, getToken(0)); {if (\"\" != null) return obs;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// System definition (\"system...endsystem\" construct)\n  static final public \nvoid SystemEndsystem(ModulesFile mf) throws ParseException {String name = null;\n        SystemDefn sysdef;\n    jj_consume_token(SYSTEM);\n    if (jj_2_7(2147483647)) {\n      jj_consume_token(DQUOTE);\n      name = Identifier();\n      jj_consume_token(DQUOTE);\n    } else {\n      ;\n    }\n    sysdef = SystemDefn();\n    jj_consume_token(ENDSYSTEM);\nmf.addSystemDefn(sysdef, name);\n}\n\n// System definition component\n  static final public \nSystemDefn SystemDefn() throws ParseException {SystemDefn ret;\n    ret = SystemFullParallel();\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// System definition component (full parallel)\n  static final public \nSystemDefn SystemFullParallel() throws ParseException {SystemDefn sys1 = null, sys2 = null;\n        SystemFullParallel par = null;\n        Token begin;\nbegin = getToken(1);\n    sys1 = SystemInterleaved();\npar = new SystemFullParallel(); par.addOperand(sys1);\n    label_13:\n    while (true) {\n      if (jj_2_8(2147483647)) {\n        ;\n      } else {\n        break label_13;\n      }\n      jj_consume_token(OR);\n      jj_consume_token(OR);\n      sys2 = SystemParallel();\npar.addOperand(sys2);\n    }\nif (par==null || par.getNumOperands() == 1) {\n                        {if (\"\" != null) return sys1;}\n                }\n                else {\n                        par.setPosition(begin, getToken(0));\n                        {if (\"\" != null) return par;}\n                }\n    throw new Error(\"Missing return statement in function\");\n}\n\n// System definition component (interleaved parallel)\n  static final public \nSystemDefn SystemInterleaved() throws ParseException {SystemDefn sys1 = null, sys2 = null;\n        SystemInterleaved par = null;\n        Token begin;\nbegin = getToken(1);\n    sys1 = SystemParallel();\npar = new SystemInterleaved(); par.addOperand(sys1);\n    label_14:\n    while (true) {\n      if (jj_2_9(2147483647)) {\n        ;\n      } else {\n        break label_14;\n      }\n      jj_consume_token(OR);\n      jj_consume_token(OR);\n      jj_consume_token(OR);\n      sys2 = SystemFullParallel();\npar.addOperand(sys2);\n    }\nif (par==null || par.getNumOperands() == 1) {\n                        {if (\"\" != null) return sys1;}\n                }\n                else {\n                        par.setPosition(begin, getToken(0));\n                        {if (\"\" != null) return par;}\n                }\n    throw new Error(\"Missing return statement in function\");\n}\n\n// System definition component (parallel over set of actions)\n  static final public \nSystemDefn SystemParallel() throws ParseException {SystemDefn sys1 = null, sys2 = null;\n        SystemParallel par = null;\n        String s;\n        Token begin;\nbegin = getToken(1);\n    sys1 = SystemHideRename();\n    if (jj_2_10(2147483647)) {\npar = new SystemParallel(); par.setOperand1(sys1);\n      jj_consume_token(OR);\n      jj_consume_token(LBRACKET);\n      s = Identifier();\npar.addAction(s);\n      label_15:\n      while (true) {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case COMMA:{\n          ;\n          break;\n          }\n        default:\n          jj_la1[34] = jj_gen;\n          break label_15;\n        }\n        jj_consume_token(COMMA);\n        s = Identifier();\npar.addAction(s);\n      }\n      jj_consume_token(RBRACKET);\n      jj_consume_token(OR);\n      sys2 = SystemHideRename();\npar.setOperand2(sys2);\n    } else {\n      ;\n    }\nif (par==null) {\n                        {if (\"\" != null) return sys1;}\n                }\n                else {\n                        par.setPosition(begin, getToken(0));\n                        {if (\"\" != null) return par;}\n                }\n    throw new Error(\"Missing return statement in function\");\n}\n\n// System definition component (hiding and renaming)\n  static final public \nSystemDefn SystemHideRename() throws ParseException {SystemDefn sys = null;\n        SystemHide hide = null;\n        SystemRename rename = null;\n        String s1 = null, s2 = null;\n        Token begin;\nbegin = getToken(1);\n    sys = SystemAtomic();\n    label_16:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACE:\n      case DIVIDE:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[35] = jj_gen;\n        break label_16;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case DIVIDE:{\nhide = new SystemHide(sys);\n        jj_consume_token(DIVIDE);\n        jj_consume_token(LBRACE);\n        s1 = Identifier();\nhide.addAction(s1);\n        label_17:\n        while (true) {\n          switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n          case COMMA:{\n            ;\n            break;\n            }\n          default:\n            jj_la1[36] = jj_gen;\n            break label_17;\n          }\n          jj_consume_token(COMMA);\n          s1 = Identifier();\nhide.addAction(s1);\n        }\n        jj_consume_token(RBRACE);\nsys = hide;\n        break;\n        }\n      case LBRACE:{\nrename = new SystemRename(sys);\n        jj_consume_token(LBRACE);\n        s1 = Identifier();\n        jj_consume_token(RENAME);\n        s2 = Identifier();\nrename.addRename(s1, s2);\n        label_18:\n        while (true) {\n          switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n          case COMMA:{\n            ;\n            break;\n            }\n          default:\n            jj_la1[37] = jj_gen;\n            break label_18;\n          }\n          jj_consume_token(COMMA);\n          s1 = Identifier();\n          jj_consume_token(RENAME);\n          s2 = Identifier();\nrename.addRename(s1, s2);\n        }\n        jj_consume_token(RBRACE);\nsys = rename;\n        break;\n        }\n      default:\n        jj_la1[38] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n    }\nsys.setPosition(begin, getToken(0)); {if (\"\" != null) return sys;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// System definition component (bottom level)\n  static final public \nSystemDefn SystemAtomic() throws ParseException {String name = null;\n        SystemDefn sys = null;\n        Token begin;\nbegin = getToken(1);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_IDENT:{\n      name = Identifier();\nsys = new SystemModule(name);\n      break;\n      }\n    case DQUOTE:{\n      jj_consume_token(DQUOTE);\n      name = Identifier();\n      jj_consume_token(DQUOTE);\nsys = new SystemReference(name);\n      break;\n      }\n    case LPARENTH:{\n      jj_consume_token(LPARENTH);\n      sys = SystemDefn();\n      jj_consume_token(RPARENTH);\nsys = new SystemBrackets(sys);\n      break;\n      }\n    default:\n      jj_la1[39] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\nsys.setPosition(begin, getToken(0)); {if (\"\" != null) return sys;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n//-----------------------------------------------------------------------------------\n// Expressions.\n// This includes PRISM properties (if the \"prop\" parameter is true)\n// and (within this) path formulas (if the \"pathprop\" parameter is true).\n// Which allows us to use the same productions for the grammars for\n// all three cases (they are very similar).\n//-----------------------------------------------------------------------------------\n\n// Expression\n  static final public \nExpression Expression(boolean prop, boolean pathprop) throws ParseException {Expression ret;\n    ret = ExpressionTemporalBinary(prop, pathprop);\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: temporal operators, binary (U, W, R) and unary (X, F, G)\n\n// Note: the potential occurrence of two successive (unseparated) expressions\n// (e.g. \"a\" and \"b\" in \"F<=a b\") is a grammar flaw because the function and\n// minus operators can cause ambiguities, for example:\n// \"F<=a(b)+c(d)\" = \"F<=a\" \"(b)+c(d)\" = \"F<=a(b)+c\" \"(d)\" ?\n// \"F<=-a-b-c\" = \"F<=-a\" \"-b-c\" = \"F<=-a-b\" \"-c\" ?\n// In many cases, these could be distinguished by type checking but\n// that does not really help since this is done post-parsing.\n// To prevent (very common) cases such as \"F<=t (b)\", \"F<=t (b)&(c)\", etc.\n// being mis-parsed (\"t(b)\" would always be taken over \"t\"), we catch this case\n// separately (see TimeBound() production below for details).\n// This means that more complex time-bounds, especially those that\n// start/end with an identifier should be parenthesised, e.g. \"F<=(t1+t2)\".\n\n// In fact, JavaCC also warns about lookahead for this function.\n// This is because (like unary minus), R can appear on the left of a unary\n// operator (reward R operator) or in the middle of a binary operator (release).\n  static final public \nExpression ExpressionTemporalBinary(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        ExpressionTemporal exprTemp;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionTemporalUnary(prop, pathprop);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case R:\n    case U:\n    case W:{\nif (!pathprop) {if (true) throw generateParseException();}\nexprTemp = new ExpressionTemporal(); exprTemp.setOperand1(ret);\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case U:{\n        jj_consume_token(U);\nexprTemp.setOperator(ExpressionTemporal.P_U);\n        break;\n        }\n      case W:{\n        jj_consume_token(W);\nexprTemp.setOperator(ExpressionTemporal.P_W);\n        break;\n        }\n      case R:{\n        jj_consume_token(R);\nexprTemp.setOperator(ExpressionTemporal.P_R);\n        break;\n        }\n      default:\n        jj_la1[40] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACKET:\n      case EQ:\n      case LT:\n      case GT:\n      case LE:\n      case GE:{\n        TimeBound(exprTemp);\n        break;\n        }\n      default:\n        jj_la1[41] = jj_gen;\n        ;\n      }\n      expr = ExpressionTemporalUnary(prop, pathprop);\nexprTemp.setOperand2(expr); exprTemp.setPosition(begin, getToken(0)); ret = exprTemp;\n      break;\n      }\n    default:\n      jj_la1[42] = jj_gen;\n      ;\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n  static final public Expression ExpressionTemporalUnary(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        ExpressionTemporal exprTemp;\n        Token begin = null;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case F:\n    case G:\n    case X:{\nif (!pathprop) {if (true) throw generateParseException();}\nbegin = getToken(1); exprTemp = new ExpressionTemporal();\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case X:{\n        jj_consume_token(X);\nexprTemp.setOperator(ExpressionTemporal.P_X);\n        break;\n        }\n      case F:{\n        jj_consume_token(F);\nexprTemp.setOperator(ExpressionTemporal.P_F);\n        break;\n        }\n      case G:{\n        jj_consume_token(G);\nexprTemp.setOperator(ExpressionTemporal.P_G);\n        break;\n        }\n      default:\n        jj_la1[43] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACKET:\n      case EQ:\n      case LT:\n      case GT:\n      case LE:\n      case GE:{\n        TimeBound(exprTemp);\n        break;\n        }\n      default:\n        jj_la1[44] = jj_gen;\n        ;\n      }\n      expr = ExpressionTemporalUnary(prop, pathprop);\nexprTemp.setOperand2(expr); exprTemp.setPosition(begin, getToken(0)); ret = exprTemp;\n      break;\n      }\n    case A:\n    case E:\n    case FALSE:\n    case FILTER:\n    case FUNC:\n    case MAX:\n    case MIN:\n    case PMAXMAX:\n    case PMAXMIN:\n    case PMAX:\n    case PMINMAX:\n    case PMINMIN:\n    case PMIN:\n    case P:\n    case RMAXMAX:\n    case RMAXMIN:\n    case RMAX:\n    case RMINMAX:\n    case RMINMIN:\n    case RMIN:\n    case R:\n    case S:\n    case TRUE:\n    case NOT:\n    case LPARENTH:\n    case DLBRACKET:\n    case DLT:\n    case MINUS:\n    case DQUOTE:\n    case REG_INT:\n    case REG_DOUBLE:\n    case REG_IDENT:{\n      ret = ExpressionITE(prop, pathprop);\n      break;\n      }\n    default:\n      jj_la1[45] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Time bound for temporal operators\n// (see ExpressionTemporal production for lookahead explanation)\n  static final public \nvoid TimeBound(ExpressionTemporal exprTemp) throws ParseException {Expression lBound, uBound;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LE:{\n      jj_consume_token(LE);\n      if (jj_2_11(2147483647)) {\n        uBound = IdentifierExpression();\n      } else {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case A:\n        case E:\n        case FALSE:\n        case FILTER:\n        case FUNC:\n        case F:\n        case G:\n        case MAX:\n        case MIN:\n        case X:\n        case PMAXMAX:\n        case PMAXMIN:\n        case PMAX:\n        case PMINMAX:\n        case PMINMIN:\n        case PMIN:\n        case P:\n        case RMAXMAX:\n        case RMAXMIN:\n        case RMAX:\n        case RMINMAX:\n        case RMINMIN:\n        case RMIN:\n        case R:\n        case S:\n        case TRUE:\n        case NOT:\n        case LPARENTH:\n        case DLBRACKET:\n        case DLT:\n        case MINUS:\n        case DQUOTE:\n        case REG_INT:\n        case REG_DOUBLE:\n        case REG_IDENT:{\n          uBound = Expression(false, false);\n          break;\n          }\n        default:\n          jj_la1[46] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n      }\nexprTemp.setUpperBound(uBound, false);\n      break;\n      }\n    case LT:{\n      jj_consume_token(LT);\n      if (jj_2_12(2147483647)) {\n        uBound = IdentifierExpression();\n      } else {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case A:\n        case E:\n        case FALSE:\n        case FILTER:\n        case FUNC:\n        case F:\n        case G:\n        case MAX:\n        case MIN:\n        case X:\n        case PMAXMAX:\n        case PMAXMIN:\n        case PMAX:\n        case PMINMAX:\n        case PMINMIN:\n        case PMIN:\n        case P:\n        case RMAXMAX:\n        case RMAXMIN:\n        case RMAX:\n        case RMINMAX:\n        case RMINMIN:\n        case RMIN:\n        case R:\n        case S:\n        case TRUE:\n        case NOT:\n        case LPARENTH:\n        case DLBRACKET:\n        case DLT:\n        case MINUS:\n        case DQUOTE:\n        case REG_INT:\n        case REG_DOUBLE:\n        case REG_IDENT:{\n          uBound = Expression(false, false);\n          break;\n          }\n        default:\n          jj_la1[47] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n      }\nexprTemp.setUpperBound(uBound, true);\n      break;\n      }\n    case GE:{\n      jj_consume_token(GE);\n      if (jj_2_13(2147483647)) {\n        lBound = IdentifierExpression();\n      } else {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case A:\n        case E:\n        case FALSE:\n        case FILTER:\n        case FUNC:\n        case F:\n        case G:\n        case MAX:\n        case MIN:\n        case X:\n        case PMAXMAX:\n        case PMAXMIN:\n        case PMAX:\n        case PMINMAX:\n        case PMINMIN:\n        case PMIN:\n        case P:\n        case RMAXMAX:\n        case RMAXMIN:\n        case RMAX:\n        case RMINMAX:\n        case RMINMIN:\n        case RMIN:\n        case R:\n        case S:\n        case TRUE:\n        case NOT:\n        case LPARENTH:\n        case DLBRACKET:\n        case DLT:\n        case MINUS:\n        case DQUOTE:\n        case REG_INT:\n        case REG_DOUBLE:\n        case REG_IDENT:{\n          lBound = Expression(false, false);\n          break;\n          }\n        default:\n          jj_la1[48] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n      }\nexprTemp.setLowerBound(lBound, false);\n      break;\n      }\n    case GT:{\n      jj_consume_token(GT);\n      if (jj_2_14(2147483647)) {\n        lBound = IdentifierExpression();\n      } else {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case A:\n        case E:\n        case FALSE:\n        case FILTER:\n        case FUNC:\n        case F:\n        case G:\n        case MAX:\n        case MIN:\n        case X:\n        case PMAXMAX:\n        case PMAXMIN:\n        case PMAX:\n        case PMINMAX:\n        case PMINMIN:\n        case PMIN:\n        case P:\n        case RMAXMAX:\n        case RMAXMIN:\n        case RMAX:\n        case RMINMAX:\n        case RMINMIN:\n        case RMIN:\n        case R:\n        case S:\n        case TRUE:\n        case NOT:\n        case LPARENTH:\n        case DLBRACKET:\n        case DLT:\n        case MINUS:\n        case DQUOTE:\n        case REG_INT:\n        case REG_DOUBLE:\n        case REG_IDENT:{\n          lBound = Expression(false, false);\n          break;\n          }\n        default:\n          jj_la1[49] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n      }\nexprTemp.setLowerBound(lBound, true);\n      break;\n      }\n    case LBRACKET:{\n      jj_consume_token(LBRACKET);\n      lBound = Expression(false, false);\n      jj_consume_token(COMMA);\n      uBound = Expression(false, false);\n      jj_consume_token(RBRACKET);\nexprTemp.setLowerBound(lBound, false); exprTemp.setUpperBound(uBound, false);\n      break;\n      }\n    case EQ:{\n      jj_consume_token(EQ);\n      lBound = Expression(false, false);\nexprTemp.setEqualBounds(lBound);\n      break;\n      }\n    default:\n      jj_la1[50] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n}\n\n// Expression: if-then-else, i.e. \"cond ? then : else\"\n  static final public \nExpression ExpressionITE(boolean prop, boolean pathprop) throws ParseException {Expression ret, left, right;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionImplies(prop, pathprop);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case QMARK:{\n      jj_consume_token(QMARK);\n      left = ExpressionImplies(prop, pathprop);\n      jj_consume_token(COLON);\n      right = ExpressionITE(prop, pathprop);\nret = new ExpressionITE(ret, left, right); ret.setPosition(begin, getToken(0));\n      break;\n      }\n    default:\n      jj_la1[51] = jj_gen;\n      ;\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: implies\n  static final public \nExpression ExpressionImplies(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionIff(prop, pathprop);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case IMPLIES:{\n      jj_consume_token(IMPLIES);\n      expr = ExpressionImplies(prop, pathprop);\nret = new ExpressionBinaryOp(ExpressionBinaryOp.IMPLIES, ret, expr); ret.setPosition(begin, getToken(0));\n      break;\n      }\n    default:\n      jj_la1[52] = jj_gen;\n      ;\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: if-and-only-iff\n  static final public \nExpression ExpressionIff(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionOr(prop, pathprop);\n    label_19:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case IFF:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[53] = jj_gen;\n        break label_19;\n      }\n      jj_consume_token(IFF);\n      expr = ExpressionOr(prop, pathprop);\nret = new ExpressionBinaryOp(ExpressionBinaryOp.IFF, ret, expr); ret.setPosition(begin, getToken(0));\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: or\n  static final public \nExpression ExpressionOr(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionAnd(prop, pathprop);\n    label_20:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case OR:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[54] = jj_gen;\n        break label_20;\n      }\n      jj_consume_token(OR);\n      expr = ExpressionAnd(prop, pathprop);\nret = new ExpressionBinaryOp(ExpressionBinaryOp.OR, ret, expr); ret.setPosition(begin, getToken(0));\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: and\n  static final public \nExpression ExpressionAnd(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionNot(prop, pathprop);\n    label_21:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case AND:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[55] = jj_gen;\n        break label_21;\n      }\n      jj_consume_token(AND);\n      expr = ExpressionNot(prop, pathprop);\nret = new ExpressionBinaryOp(ExpressionBinaryOp.AND, ret, expr); ret.setPosition(begin, getToken(0));\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: not\n  static final public \nExpression ExpressionNot(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        Token begin = null;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case NOT:{\n      begin = jj_consume_token(NOT);\n      expr = ExpressionNot(prop, pathprop);\nret = new ExpressionUnaryOp(ExpressionUnaryOp.NOT, expr); ret.setPosition(begin, getToken(0));\n      break;\n      }\n    case A:\n    case E:\n    case FALSE:\n    case FILTER:\n    case FUNC:\n    case MAX:\n    case MIN:\n    case PMAXMAX:\n    case PMAXMIN:\n    case PMAX:\n    case PMINMAX:\n    case PMINMIN:\n    case PMIN:\n    case P:\n    case RMAXMAX:\n    case RMAXMIN:\n    case RMAX:\n    case RMINMAX:\n    case RMINMIN:\n    case RMIN:\n    case R:\n    case S:\n    case TRUE:\n    case LPARENTH:\n    case DLBRACKET:\n    case DLT:\n    case MINUS:\n    case DQUOTE:\n    case REG_INT:\n    case REG_DOUBLE:\n    case REG_IDENT:{\n      ret = ExpressionEquality(prop, pathprop);\n      break;\n      }\n    default:\n      jj_la1[56] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: equality operators: =, !=\n  static final public \nExpression ExpressionEquality(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        int op;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionRelop(prop, pathprop);\n    label_22:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case EQ:\n      case NE:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[57] = jj_gen;\n        break label_22;\n      }\n      op = EqNeq();\n      expr = ExpressionRelop(prop, pathprop);\nret = new ExpressionBinaryOp(op, ret, expr); ret.setPosition(begin, getToken(0));\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: relational operators: >, <, >=, <=\n  static final public \nExpression ExpressionRelop(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        int op;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionPlusMinus(prop, pathprop);\n    label_23:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LT:\n      case GT:\n      case LE:\n      case GE:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[58] = jj_gen;\n        break label_23;\n      }\n      op = LtGt();\n      expr = ExpressionPlusMinus(prop, pathprop);\nret = new ExpressionBinaryOp(op, ret, expr); ret.setPosition(begin, getToken(0));\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: plus/minus\n\n// JavaCC warns about lookahead for this function. This is because in a few places\n// (bounded temporal operators and semicolon-less properties files)\n// (see the relevant productions for details)\n// we allow two or more successive expressions resulting in potential ambiguities\n// e.g. \"-a-b\" = \"(-a)-b\" = \"-a\" \"-b\"\n// Ignoring the warning results in the largest match being taken.\n  static final public \nExpression ExpressionPlusMinus(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        int op;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionTimesDivide(prop, pathprop);\n    label_24:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case PLUS:\n      case MINUS:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[59] = jj_gen;\n        break label_24;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case PLUS:{\n        jj_consume_token(PLUS);\nop = ExpressionBinaryOp.PLUS;\n        break;\n        }\n      case MINUS:{\n        jj_consume_token(MINUS);\nop = ExpressionBinaryOp.MINUS;\n        break;\n        }\n      default:\n        jj_la1[60] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      expr = ExpressionTimesDivide(prop, pathprop);\nret = new ExpressionBinaryOp(op, ret, expr); ret.setPosition(begin, getToken(0));\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: times/divide\n  static final public \nExpression ExpressionTimesDivide(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        int op;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionPower(prop, pathprop);\n    label_25:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case TIMES:\n      case DIVIDE:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[61] = jj_gen;\n        break label_25;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case TIMES:{\n        jj_consume_token(TIMES);\nop = ExpressionBinaryOp.TIMES;\n        break;\n        }\n      case DIVIDE:{\n        jj_consume_token(DIVIDE);\nop = ExpressionBinaryOp.DIVIDE;\n        break;\n        }\n      default:\n        jj_la1[62] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      expr = ExpressionPower(prop, pathprop);\nret = new ExpressionBinaryOp(op, ret, expr); ret.setPosition(begin, getToken(0));\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: power (^)\n  static final public \nExpression ExpressionPower(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        int op;\n        Token begin = null;\nbegin = getToken(1);\n    ret = ExpressionUnaryMinus(prop, pathprop);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case POWER:{\n      jj_consume_token(POWER);\n      expr = ExpressionPower(prop, pathprop);\nret = new ExpressionBinaryOp(ExpressionBinaryOp.POW, ret, expr); ret.setPosition(begin, getToken(0));\n      break;\n      }\n    default:\n      jj_la1[63] = jj_gen;\n      ;\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: unary minus\n  static final public \nExpression ExpressionUnaryMinus(boolean prop, boolean pathprop) throws ParseException {Expression ret, expr;\n        Token begin = null;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case MINUS:{\n      begin = jj_consume_token(MINUS);\n      expr = ExpressionUnaryMinus(prop, pathprop);\nret = new ExpressionUnaryOp(ExpressionUnaryOp.MINUS, expr); ret.setPosition(begin, getToken(0));\n      break;\n      }\n    case A:\n    case E:\n    case FALSE:\n    case FILTER:\n    case FUNC:\n    case MAX:\n    case MIN:\n    case PMAXMAX:\n    case PMAXMIN:\n    case PMAX:\n    case PMINMAX:\n    case PMINMIN:\n    case PMIN:\n    case P:\n    case RMAXMAX:\n    case RMAXMIN:\n    case RMAX:\n    case RMINMAX:\n    case RMINMIN:\n    case RMIN:\n    case R:\n    case S:\n    case TRUE:\n    case LPARENTH:\n    case DLBRACKET:\n    case DLT:\n    case DQUOTE:\n    case REG_INT:\n    case REG_DOUBLE:\n    case REG_IDENT:{\n      ret = ExpressionBasic(prop, pathprop);\n      break;\n      }\n    default:\n      jj_la1[64] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Basic expression (top of operator precedence ordering)\n  static final public \nExpression ExpressionBasic(boolean prop, boolean pathprop) throws ParseException {Expression ret;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case FALSE:\n    case TRUE:\n    case REG_INT:\n    case REG_DOUBLE:{\n      ret = ExpressionLiteral(prop, pathprop);\n      break;\n      }\n    case REG_IDENT:{\n      ret = ExpressionFuncOrIdent(prop, pathprop);\n      break;\n      }\n    case MAX:\n    case MIN:{\n      ret = ExpressionFuncMinMax(prop, pathprop);\n      break;\n      }\n    case FUNC:{\n      ret = ExpressionFuncOldStyle(prop, pathprop);\n      break;\n      }\n    case LPARENTH:{\n      ret = ExpressionParenth(prop, pathprop);\n      break;\n      }\n    case PMAXMAX:\n    case PMAXMIN:\n    case PMAX:\n    case PMINMAX:\n    case PMINMIN:\n    case PMIN:\n    case P:{\n      // Remaining options are only applicable for properties\n                      ret = ExpressionProb(prop, pathprop);\n      break;\n      }\n    case S:{\n      ret = ExpressionSS(prop, pathprop);\n      break;\n      }\n    case RMAXMAX:\n    case RMAXMIN:\n    case RMAX:\n    case RMINMAX:\n    case RMINMIN:\n    case RMIN:\n    case R:{\n      ret = ExpressionReward(prop, pathprop);\n      break;\n      }\n    case E:{\n      ret = ExpressionExists(prop, pathprop);\n      break;\n      }\n    case A:{\n      ret = ExpressionForAll(prop, pathprop);\n      break;\n      }\n    case DLBRACKET:\n    case DLT:{\n      ret = ExpressionStrategy(prop, pathprop);\n      break;\n      }\n    case DQUOTE:{\n      ret = ExpressionLabel(prop, pathprop);\n      break;\n      }\n    case FILTER:{\n      ret = ExpressionFilter(prop, pathprop);\n      break;\n      }\n    default:\n      jj_la1[65] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: function or identifier\n\n// JavaCC warns about lookahead for this function. This is because in a few places\n// (bounded temporal operators and semicolon-less properties files)\n// (see the relevant productions for details)\n// we allow two or more successive expressions resulting in potential ambiguities\n// e.g. \"a(b)\" = \"a\" \"(b)\"\n// Ignoring the warning results in the largest match being taken.\n  static final public \nExpression ExpressionFuncOrIdent(boolean prop, boolean pathprop) throws ParseException {String s = null;\n        Expression ret = null;\n        Token begin = null;\n    // If there is no \"(...)\", this is an identifier\n            s = Identifier();\nret = new ExpressionIdent(s); begin = getToken(0);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LPARENTH:{\n      jj_consume_token(LPARENTH);\nret = new ExpressionFunc(s);\n      ExpressionFuncArgs(prop, pathprop, (ExpressionFunc)ret);\n      jj_consume_token(RPARENTH);\n      break;\n      }\n    default:\n      jj_la1[66] = jj_gen;\n      ;\n    }\nret.setPosition(begin, getToken(0)); {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: min/max function (treated differently because min/max are keywords)\n  static final public \nExpression ExpressionFuncMinMax(boolean prop, boolean pathprop) throws ParseException {String s = null;\n        ExpressionFunc func = null;\n        Token begin = null;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case MIN:{\n      begin = jj_consume_token(MIN);\ns = \"min\";\n      break;\n      }\n    case MAX:{\n      begin = jj_consume_token(MAX);\ns = \"max\";\n      break;\n      }\n    default:\n      jj_la1[67] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\nfunc = new ExpressionFunc(s);\n    jj_consume_token(LPARENTH);\n    ExpressionFuncArgs(prop, pathprop, func);\n    jj_consume_token(RPARENTH);\nfunc.setPosition(begin, getToken(0)); {if (\"\" != null) return func;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: old-style function, i.e. \"func(name, ...)\"\n  static final public \nExpression ExpressionFuncOldStyle(boolean prop, boolean pathprop) throws ParseException {String s = null;\n        ExpressionFunc func = null;\n        Token begin = null;\n    begin = jj_consume_token(FUNC);\n    jj_consume_token(LPARENTH);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case MIN:{\n      jj_consume_token(MIN);\ns = \"min\";\n      break;\n      }\n    case MAX:{\n      jj_consume_token(MAX);\ns = \"max\";\n      break;\n      }\n    case REG_IDENT:{\n      s = Identifier();\n      break;\n      }\n    default:\n      jj_la1[68] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    jj_consume_token(COMMA);\nfunc = new ExpressionFunc(s); func.setOldStyle(true);\n    ExpressionFuncArgs(prop, pathprop, func);\n    jj_consume_token(RPARENTH);\nfunc.setPosition(begin, getToken(0)); {if (\"\" != null) return func;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Arguments for a function in an expression\n  static final public \nvoid ExpressionFuncArgs(boolean prop, boolean pathprop, ExpressionFunc func) throws ParseException {Expression expr;\n    expr = Expression(prop, pathprop);\nfunc.addOperand(expr);\n    label_26:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case COMMA:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[69] = jj_gen;\n        break label_26;\n      }\n      jj_consume_token(COMMA);\n      expr = Expression(prop, pathprop);\nfunc.addOperand(expr);\n    }\n}\n\n// Expression: literal\n  static final public \nExpression ExpressionLiteral(boolean prop, boolean pathprop) throws ParseException {Expression ret = null;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_INT:{\n      jj_consume_token(REG_INT);\ntry {\n                        int i = Integer.parseInt(getToken(0).image);\n                        ret = new ExpressionLiteral(TypeInt.getInstance(), Integer.valueOf(i));\n                } catch (NumberFormatException e) {\n                        // Need to catch this because some matches for regexp REG_INT\n                        // are not valid integers (e.g. too big).\n                        ParseException ex = new ParseException(\"Invalid integer literal\");\n                        ex.currentToken = getToken(0);\n                        {if (true) throw ex;}\n                        // NB: can't call generateParseException() here; it crashes\n                }\n      break;\n      }\n    case REG_DOUBLE:{\n      jj_consume_token(REG_DOUBLE);\ntry {\n                        double d = Double.parseDouble(getToken(0).image);\n                        ret = new ExpressionLiteral(TypeDouble.getInstance(), Double.valueOf(d), getToken(0).image);\n                } catch (NumberFormatException e) {\n                        // Need to catch this because some matches for regexp REG_DOUBLE\n                        // may not be valid doubles.\n                        ParseException ex = new ParseException(\"Invalid double literal\");\n                        // NB: can't call generateParseException() here; it crashes\n                }\n      break;\n      }\n    case TRUE:{\n      jj_consume_token(TRUE);\nret = new ExpressionLiteral(TypeBool.getInstance(), Boolean.valueOf(true));\n      break;\n      }\n    case FALSE:{\n      jj_consume_token(FALSE);\nret = new ExpressionLiteral(TypeBool.getInstance(), Boolean.valueOf(false));\n      break;\n      }\n    default:\n      jj_la1[70] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\nret.setPosition(getToken(0)); {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: parentheses\n  static final public \nExpression ExpressionParenth(boolean prop, boolean pathprop) throws ParseException {Expression expr, ret;\n        Token begin = null;\n    begin = jj_consume_token(LPARENTH);\n    expr = Expression(prop, pathprop);\n    jj_consume_token(RPARENTH);\nret = new ExpressionUnaryOp(ExpressionUnaryOp.PARENTH, expr); ret.setPosition(begin, getToken(0)); {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Expression: interval\n  static final public \nExpression ExpressionInterval(boolean prop, boolean pathprop) throws ParseException {ExpressionInterval expr = null;\n        Expression expr1 = null, expr2 = null;\n        Token begin = null;\n    begin = jj_consume_token(LBRACKET);\n    expr1 = Expression(prop, pathprop);\n    jj_consume_token(COMMA);\n    expr2 = Expression(prop, pathprop);\n    jj_consume_token(RBRACKET);\nexpr = new ExpressionInterval(expr1, expr2); expr.setPosition(begin, getToken(0)); {if (\"\" != null) return expr;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n//-----------------------------------------------------------------------------------\n// Property stuff\n//-----------------------------------------------------------------------------------\n\n// (Property) expression: probabilistic operator P\n  static final public \nExpression ExpressionProb(boolean prop, boolean pathprop) throws ParseException {ExpressionIdent modifier = null;\n        int r;\n        String relOp = null;\n        Expression prob = null;\n        Expression expr;\n        Filter filter = null;\n        ExpressionProb ret = new ExpressionProb();\n        Token begin = null;\n        boolean isBool;\nif (!prop) {if (true) throw generateParseException();}\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case P:{\n      begin = jj_consume_token(P);\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LPARENTH:{\n        jj_consume_token(LPARENTH);\n        modifier = IdentifierExpression();\n        jj_consume_token(RPARENTH);\n        break;\n        }\n      default:\n        jj_la1[71] = jj_gen;\n        ;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LT:\n      case GT:\n      case LE:\n      case GE:{\n        r = LtGt();\n        prob = Expression(false, false);\nrelOp = ExpressionBinaryOp.opSymbols[r]; isBool = true;\n        break;\n        }\n      case EQ:{\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"=\"; isBool = false;\n        break;\n        }\n      case MIN:{\n        jj_consume_token(MIN);\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case EQ:{\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"min=\"; isBool = false;\n          break;\n          }\n        case MIN:{\n          jj_consume_token(MIN);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"minmin=\"; isBool = false;\n          break;\n          }\n        case MAX:{\n          jj_consume_token(MAX);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"minmax=\"; isBool = false;\n          break;\n          }\n        default:\n          jj_la1[72] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n        break;\n        }\n      case MAX:{\n        jj_consume_token(MAX);\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case EQ:{\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"max=\"; isBool = false;\n          break;\n          }\n        case MIN:{\n          jj_consume_token(MIN);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"maxmin=\"; isBool = false;\n          break;\n          }\n        case MAX:{\n          jj_consume_token(MAX);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"maxmax=\"; isBool = false;\n          break;\n          }\n        default:\n          jj_la1[73] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n        break;\n        }\n      case MINMIN:{\n        jj_consume_token(MINMIN);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"minmin=\"; isBool = false;\n        break;\n        }\n      case MINMAX:{\n        jj_consume_token(MINMAX);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"minmax=\"; isBool = false;\n        break;\n        }\n      case MAXMIN:{\n        jj_consume_token(MAXMIN);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"maxmin=\"; isBool = false;\n        break;\n        }\n      case MAXMAX:{\n        jj_consume_token(MAXMAX);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"maxmax=\"; isBool = false;\n        break;\n        }\n      default:\n        jj_la1[74] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      break;\n      }\n    case PMIN:{\n      begin = jj_consume_token(PMIN);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"min=\"; isBool = false;\n      break;\n      }\n    case PMAX:{\n      begin = jj_consume_token(PMAX);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"max=\"; isBool = false;\n      break;\n      }\n    case PMINMIN:{\n      begin = jj_consume_token(PMINMIN);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"minmin=\"; isBool = false;\n      break;\n      }\n    case PMINMAX:{\n      begin = jj_consume_token(PMINMAX);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"minmax=\"; isBool = false;\n      break;\n      }\n    case PMAXMIN:{\n      begin = jj_consume_token(PMAXMIN);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"maxmin=\"; isBool = false;\n      break;\n      }\n    case PMAXMAX:{\n      begin = jj_consume_token(PMAXMAX);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"maxmax=\"; isBool = false;\n      break;\n      }\n    default:\n      jj_la1[75] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    jj_consume_token(LBRACKET);\n    expr = Expression(prop, true);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LBRACE:{\n      filter = Filter();\n      break;\n      }\n    default:\n      jj_la1[76] = jj_gen;\n      ;\n    }\n    jj_consume_token(RBRACKET);\nret.setModifier(modifier == null ? null : modifier.getName());\n                ret.setRelOp(relOp);\n                ret.setProb(prob);\n                ret.setExpression(expr);\n                ret.setFilter(filter);\n                ret.setPosition(begin, getToken(0));\n                // Filter is actually dealt with by wrapping this expression in\n                // an (invisible) ExpressionFilter expression\n                if (filter != null) {\n                        String filterOp = isBool ? \"&\" : filter.getFilterOpString();\n                        ExpressionFilter ef = new ExpressionFilter(filterOp, ret, filter.getExpression());\n                        ef.setInvisible(true);\n                        {if (\"\" != null) return ef;}\n                }\n                else {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Filter for a P/S/R operator\n  static final public \nFilter Filter() throws ParseException {Filter filter;\n        Expression expr;\n        Token begin = null;\n    begin = jj_consume_token(LBRACE);\n    expr = Expression(true, false);\nfilter = new Filter(expr);\n    jj_consume_token(RBRACE);\n    label_27:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACE:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[77] = jj_gen;\n        break label_27;\n      }\n      jj_consume_token(LBRACE);\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case MIN:{\n        jj_consume_token(MIN);\nfilter.setMinRequested(true);\n        break;\n        }\n      case MAX:{\n        jj_consume_token(MAX);\nfilter.setMaxRequested(true);\n        break;\n        }\n      default:\n        jj_la1[78] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      jj_consume_token(RBRACE);\n    }\nfilter.setPosition(begin, getToken(0)); {if (\"\" != null) return filter;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// (Property) expression: steady-state operator S\n  static final public \nExpression ExpressionSS(boolean prop, boolean pathprop) throws ParseException {ExpressionIdent modifier = null;\n        int r;\n        String relOp = null;\n        Expression prob = null;\n        Expression expr;\n        Filter filter = null;\n        ExpressionSS ret = new ExpressionSS();\n        Token begin;\n        boolean isBool;\nif (!prop) {if (true) throw generateParseException();}\n    // Various options for \"S\" keyword and attached symbols\n            begin = jj_consume_token(S);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LPARENTH:\n    case LT:\n    case GT:\n    case LE:\n    case GE:{\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LPARENTH:{\n        jj_consume_token(LPARENTH);\n        modifier = IdentifierExpression();\n        jj_consume_token(RPARENTH);\n        break;\n        }\n      default:\n        jj_la1[79] = jj_gen;\n        ;\n      }\n      r = LtGt();\n      prob = Expression(false, false);\nrelOp = ExpressionBinaryOp.opSymbols[r]; isBool = true;\n      break;\n      }\n    case EQ:{\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"=\"; isBool = false;\n      break;\n      }\n    default:\n      jj_la1[80] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    jj_consume_token(LBRACKET);\n    expr = Expression(prop, pathprop);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LBRACE:{\n      filter = Filter();\n      break;\n      }\n    default:\n      jj_la1[81] = jj_gen;\n      ;\n    }\n    jj_consume_token(RBRACKET);\nret.setModifier(modifier == null ? null : modifier.getName());\n                ret.setRelOp(relOp);\n                ret.setProb(prob);\n                ret.setExpression(expr);\n                ret.setFilter(filter);\n                ret.setPosition(begin, getToken(0));\n                // Filter is actually dealt with by wrapping this expression in\n                // an (invisible) ExpressionFilter expression\n                if (filter != null) {\n                        String filterOp = isBool ? \"&\" : filter.getFilterOpString();\n                        ExpressionFilter ef = new ExpressionFilter(filterOp, ret, filter.getExpression());\n                        ef.setInvisible(true);\n                        {if (\"\" != null) return ef;}\n                }\n                else {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// (Property) expression: expected reward operator R\n  static final public \nExpression ExpressionReward(boolean prop, boolean pathprop) throws ParseException {ExpressionIdent modifier = null;\n        int r;\n        String relOp = null;\n        Expression rew = null;\n        Expression expr;\n        Filter filter = null;\n        ExpressionReward ret = new ExpressionReward();\n        Token begin;\n        boolean isBool;\nif (!prop) {if (true) throw generateParseException();}\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case R:{\n      begin = jj_consume_token(R);\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LPARENTH:{\n        jj_consume_token(LPARENTH);\n        modifier = IdentifierExpression();\n        jj_consume_token(RPARENTH);\n        break;\n        }\n      default:\n        jj_la1[82] = jj_gen;\n        ;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACE:{\n        RewardIndex(ret);\n        break;\n        }\n      default:\n        jj_la1[83] = jj_gen;\n        ;\n      }\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LT:\n      case GT:\n      case LE:\n      case GE:{\n        r = LtGt();\n        rew = Expression(false, false);\nrelOp = ExpressionBinaryOp.opSymbols[r]; isBool = true;\n        break;\n        }\n      case EQ:{\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"=\"; isBool = false;\n        break;\n        }\n      case MIN:{\n        jj_consume_token(MIN);\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case EQ:{\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"min=\"; isBool = false;\n          break;\n          }\n        case MIN:{\n          jj_consume_token(MIN);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"minmin=\"; isBool = false;\n          break;\n          }\n        case MAX:{\n          jj_consume_token(MAX);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"minmax=\"; isBool = false;\n          break;\n          }\n        default:\n          jj_la1[84] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n        break;\n        }\n      case MAX:{\n        jj_consume_token(MAX);\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case EQ:{\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"max=\"; isBool = false;\n          break;\n          }\n        case MIN:{\n          jj_consume_token(MIN);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"maxmin=\"; isBool = false;\n          break;\n          }\n        case MAX:{\n          jj_consume_token(MAX);\n          jj_consume_token(EQ);\n          jj_consume_token(QMARK);\nrelOp = \"maxmax=\"; isBool = false;\n          break;\n          }\n        default:\n          jj_la1[85] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n        break;\n        }\n      case MINMIN:{\n        jj_consume_token(MINMIN);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"minmin=\"; isBool = false;\n        break;\n        }\n      case MINMAX:{\n        jj_consume_token(MINMAX);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"minmax=\"; isBool = false;\n        break;\n        }\n      case MAXMIN:{\n        jj_consume_token(MAXMIN);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"maxmin=\"; isBool = false;\n        break;\n        }\n      case MAXMAX:{\n        jj_consume_token(MAXMAX);\n        jj_consume_token(EQ);\n        jj_consume_token(QMARK);\nrelOp = \"maxmax=\"; isBool = false;\n        break;\n        }\n      default:\n        jj_la1[86] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n      break;\n      }\n    case RMIN:{\n      begin = jj_consume_token(RMIN);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"min=\"; isBool = false;\n      break;\n      }\n    case RMAX:{\n      begin = jj_consume_token(RMAX);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"max=\"; isBool = false;\n      break;\n      }\n    case RMINMIN:{\n      begin = jj_consume_token(RMINMIN);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"minmin=\"; isBool = false;\n      break;\n      }\n    case RMINMAX:{\n      begin = jj_consume_token(RMINMAX);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"minmax=\"; isBool = false;\n      break;\n      }\n    case RMAXMIN:{\n      begin = jj_consume_token(RMAXMIN);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"maxmin=\"; isBool = false;\n      break;\n      }\n    case RMAXMAX:{\n      begin = jj_consume_token(RMAXMAX);\n      jj_consume_token(EQ);\n      jj_consume_token(QMARK);\nrelOp = \"maxmax=\"; isBool = false;\n      break;\n      }\n    default:\n      jj_la1[87] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    jj_consume_token(LBRACKET);\n    expr = ExpressionRewardContents(prop, pathprop);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LBRACE:{\n      filter = Filter();\n      break;\n      }\n    default:\n      jj_la1[88] = jj_gen;\n      ;\n    }\n    jj_consume_token(RBRACKET);\nret.setModifier(modifier == null ? null : modifier.getName());\n                ret.setRelOp(relOp);\n                ret.setReward(rew);\n                ret.setExpression(expr);\n                ret.setFilter(filter);\n                ret.setPosition(begin, getToken(0));\n                // Filter is actually dealt with by wrapping this expression in\n                // an (invisible) ExpressionFilter expression\n                if (filter != null) {\n                        String filterOp = isBool ? \"&\" : filter.getFilterOpString();\n                        ExpressionFilter ef = new ExpressionFilter(filterOp, ret, filter.getExpression());\n                        ef.setInvisible(true);\n                        {if (\"\" != null) return ef;}\n                }\n                else {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Reward struct index for R operator\n  static final public \nvoid RewardIndex(ExpressionReward exprRew) throws ParseException {Object index = null;\n        Object indexDiv = null;\n    jj_consume_token(LBRACE);\n    if (jj_2_15(2147483647)) {\n      jj_consume_token(DQUOTE);\n      index = Identifier();\n      jj_consume_token(DQUOTE);\n    } else {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case A:\n      case E:\n      case FALSE:\n      case FILTER:\n      case FUNC:\n      case F:\n      case G:\n      case MAX:\n      case MIN:\n      case X:\n      case PMAXMAX:\n      case PMAXMIN:\n      case PMAX:\n      case PMINMAX:\n      case PMINMIN:\n      case PMIN:\n      case P:\n      case RMAXMAX:\n      case RMAXMIN:\n      case RMAX:\n      case RMINMAX:\n      case RMINMIN:\n      case RMIN:\n      case R:\n      case S:\n      case TRUE:\n      case NOT:\n      case LPARENTH:\n      case DLBRACKET:\n      case DLT:\n      case MINUS:\n      case DQUOTE:\n      case REG_INT:\n      case REG_DOUBLE:\n      case REG_IDENT:{\n        index = Expression(false, false);\n        break;\n        }\n      default:\n        jj_la1[89] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\n    }\n    jj_consume_token(RBRACE);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case DIVIDE:{\n      jj_consume_token(DIVIDE);\n      jj_consume_token(LBRACE);\n      if (jj_2_16(2147483647)) {\n        jj_consume_token(DQUOTE);\n        indexDiv = Identifier();\n        jj_consume_token(DQUOTE);\n      } else {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case A:\n        case E:\n        case FALSE:\n        case FILTER:\n        case FUNC:\n        case F:\n        case G:\n        case MAX:\n        case MIN:\n        case X:\n        case PMAXMAX:\n        case PMAXMIN:\n        case PMAX:\n        case PMINMAX:\n        case PMINMIN:\n        case PMIN:\n        case P:\n        case RMAXMAX:\n        case RMAXMIN:\n        case RMAX:\n        case RMINMAX:\n        case RMINMIN:\n        case RMIN:\n        case R:\n        case S:\n        case TRUE:\n        case NOT:\n        case LPARENTH:\n        case DLBRACKET:\n        case DLT:\n        case MINUS:\n        case DQUOTE:\n        case REG_INT:\n        case REG_DOUBLE:\n        case REG_IDENT:{\n          indexDiv = Expression(false, false);\n          break;\n          }\n        default:\n          jj_la1[90] = jj_gen;\n          jj_consume_token(-1);\n          throw new ParseException();\n        }\n      }\n      jj_consume_token(RBRACE);\n      break;\n      }\n    default:\n      jj_la1[91] = jj_gen;\n      ;\n    }\nexprRew.setRewardStructIndex(index);\n                if (indexDiv != null) {\n                        exprRew.setRewardStructIndexDiv(indexDiv);\n                }\n}\n\n// Contents of an R operator\n\n// JavaCC warns about lookahead for this function. This is because there is a possible conflict between\n// R [ S ], where \"S\" is the long-run reward operator, and R [ S [ ] ], where \"S [ ]\" is an LTL formula\n// comprising a single atomic proposition. We use lookahead to resolve the ambiguity.\n  static final public \nExpression ExpressionRewardContents(boolean prop, boolean pathprop) throws ParseException {Expression expr = null;\n        ExpressionTemporal exprTemp = null;\n        Expression ret = null;\n        Token begin;\nbegin = getToken(1);\n    if (jj_2_17(2147483647)) {\n      expr = ExpressionSS(prop, true);\nret = expr;\n    } else {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case S:{\n        jj_consume_token(S);\nret = new ExpressionTemporal(ExpressionTemporal.R_S, null, null);\n        break;\n        }\n      default:\n        jj_la1[92] = jj_gen;\n        if (jj_2_18(2147483647)) {\n          begin = jj_consume_token(C);\n          jj_consume_token(LE);\n          expr = Expression(false, false);\nexprTemp = new ExpressionTemporal(ExpressionTemporal.R_C, null, null); exprTemp.setUpperBound(expr); ret = exprTemp;\n        } else {\n          switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n          case C:{\n            jj_consume_token(C);\nret = new ExpressionTemporal(ExpressionTemporal.R_C, null, null);\n            break;\n            }\n          case I:{\n            jj_consume_token(I);\n            jj_consume_token(EQ);\n            expr = Expression(false, false);\nexprTemp = new ExpressionTemporal(ExpressionTemporal.R_I, null, null); exprTemp.setUpperBound(expr); ret = exprTemp;\n            break;\n            }\n          case A:\n          case E:\n          case FALSE:\n          case FILTER:\n          case FUNC:\n          case F:\n          case G:\n          case MAX:\n          case MIN:\n          case X:\n          case PMAXMAX:\n          case PMAXMIN:\n          case PMAX:\n          case PMINMAX:\n          case PMINMIN:\n          case PMIN:\n          case P:\n          case RMAXMAX:\n          case RMAXMIN:\n          case RMAX:\n          case RMINMAX:\n          case RMINMIN:\n          case RMIN:\n          case R:\n          case S:\n          case TRUE:\n          case NOT:\n          case LPARENTH:\n          case DLBRACKET:\n          case DLT:\n          case MINUS:\n          case DQUOTE:\n          case REG_INT:\n          case REG_DOUBLE:\n          case REG_IDENT:{\n            expr = Expression(prop, true);\nret = expr;\n            break;\n            }\n          default:\n            jj_la1[93] = jj_gen;\n            jj_consume_token(-1);\n            throw new ParseException();\n          }\n        }\n      }\n    }\nret.setPosition(begin, getToken(0)); {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// (Property) expression: CTL existential operator E\n  static final public \nExpression ExpressionExists(boolean prop, boolean pathprop) throws ParseException {ExpressionExists ret = new ExpressionExists();\n        Expression expr;\n        Token begin = null;\nif (!prop) {if (true) throw generateParseException();}\n    begin = jj_consume_token(E);\n    jj_consume_token(LBRACKET);\n    expr = Expression(prop, true);\n    jj_consume_token(RBRACKET);\nret.setExpression(expr);\n                ret.setPosition(begin, getToken(0));\n                {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// (Property) expression: CTL universal operator A\n  static final public \nExpression ExpressionForAll(boolean prop, boolean pathprop) throws ParseException {ExpressionForAll ret = new ExpressionForAll();\n        Expression expr;\n        Token begin = null;\nif (!prop) {if (true) throw generateParseException();}\n    begin = jj_consume_token(A);\n    jj_consume_token(LBRACKET);\n    expr = Expression(prop, true);\n    jj_consume_token(RBRACKET);\nret.setExpression(expr);\n                ret.setPosition(begin, getToken(0));\n                {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// (Property) expression: ATL strategy operators <<>> and [[]]\n  static final public \nExpression ExpressionStrategy(boolean prop, boolean pathprop) throws ParseException {ExpressionStrategy ret;\n        Expression expr;\n        Token begin = null;\nif (!prop) {if (true) throw generateParseException();}\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case DLT:{\n      begin = jj_consume_token(DLT);\nret = new ExpressionStrategy(true);\n      ExpressionStrategyCoalition(ret);\n      jj_consume_token(DGT);\n      break;\n      }\n    case DLBRACKET:{\n      begin = jj_consume_token(DLBRACKET);\nret = new ExpressionStrategy(false);\n      ExpressionStrategyCoalition(ret);\n      jj_consume_token(DRBRACKET);\n      break;\n      }\n    default:\n      jj_la1[94] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case PMAXMAX:\n    case PMAXMIN:\n    case PMAX:\n    case PMINMAX:\n    case PMINMIN:\n    case PMIN:\n    case P:\n    case RMAXMAX:\n    case RMAXMIN:\n    case RMAX:\n    case RMINMAX:\n    case RMINMIN:\n    case RMIN:\n    case R:{\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case PMAXMAX:\n      case PMAXMIN:\n      case PMAX:\n      case PMINMAX:\n      case PMINMIN:\n      case PMIN:\n      case P:{\n        expr = ExpressionProb(prop, pathprop);\n        break;\n        }\n      case RMAXMAX:\n      case RMAXMIN:\n      case RMAX:\n      case RMINMAX:\n      case RMINMIN:\n      case RMIN:\n      case R:{\n        expr = ExpressionReward(prop, pathprop);\n        break;\n        }\n      default:\n        jj_la1[95] = jj_gen;\n        jj_consume_token(-1);\n        throw new ParseException();\n      }\nret.setSingleOperand(expr);\n      break;\n      }\n    case LPARENTH:{\n      expr = ExpressionParenth(prop, pathprop);\nret.addOperand(expr);\n      break;\n      }\n    default:\n      jj_la1[96] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\nret.setPosition(begin, getToken(0));\n                {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Coalition (player list) for a strategy (<<>> or [[]]) operator\n  static final public \nvoid ExpressionStrategyCoalition(ExpressionStrategy exprStrat) throws ParseException {List<String> coalition = new ArrayList<String>();\n        String s;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case TIMES:{\n      jj_consume_token(TIMES);\nexprStrat.setCoalitionAllPlayers();\n      break;\n      }\n    default:\n      jj_la1[99] = jj_gen;\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case REG_INT:\n      case REG_IDENT:{\n        s = ExpressionStrategyCoalitionPlayer();\ncoalition.add(s);\n        label_28:\n        while (true) {\n          switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n          case COMMA:{\n            ;\n            break;\n            }\n          default:\n            jj_la1[97] = jj_gen;\n            break label_28;\n          }\n          jj_consume_token(COMMA);\n          s = ExpressionStrategyCoalitionPlayer();\ncoalition.add(s);\n        }\n        break;\n        }\n      default:\n        jj_la1[98] = jj_gen;\n        ;\n      }\nexprStrat.setCoalition(coalition);\n    }\n}\n\n// Single player in a coalition for a strategy (<<>> or [[]]) operator\n  static final public \nString ExpressionStrategyCoalitionPlayer() throws ParseException {String s;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_INT:{\n      jj_consume_token(REG_INT);\n      break;\n      }\n    case REG_IDENT:{\n      jj_consume_token(REG_IDENT);\n      break;\n      }\n    default:\n      jj_la1[100] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\ns = getToken(0).image;\n{if (\"\" != null) return s;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// (Property) expression: label (including \"init\")\n  static final public \nExpression ExpressionLabel(boolean prop, boolean pathprop) throws ParseException {String s;\n        ExpressionLabel ret = null;\n        Token begin;\nif (!prop) {if (true) throw generateParseException();}\n    begin = jj_consume_token(DQUOTE);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_IDENT:{\n      s = Identifier();\n      break;\n      }\n    case INIT:{\n      jj_consume_token(INIT);\ns = \"init\";\n      break;\n      }\n    default:\n      jj_la1[101] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    jj_consume_token(DQUOTE);\nret = new ExpressionLabel(s); ret.setPosition(begin, getToken(0)); {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// (Property) expression: filter (using \"filter\" keyword)\n  static final public \nExpression ExpressionFilter(boolean prop, boolean pathprop) throws ParseException {ExpressionFilter expr = null;\n        String op = null;\n        Expression filter = null;\n        Expression expr2 = null;\n        Token begin = null;\nif (!prop) {if (true) throw generateParseException();}\n    // filter(\n            begin = jj_consume_token(FILTER);\n    jj_consume_token(LPARENTH);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case MIN:{\n      jj_consume_token(MIN);\nop = \"min\";\n      break;\n      }\n    case MAX:{\n      jj_consume_token(MAX);\nop = \"max\";\n      break;\n      }\n    case PLUS:{\n      jj_consume_token(PLUS);\nop = \"+\";\n      break;\n      }\n    case AND:{\n      jj_consume_token(AND);\nop = \"&\";\n      break;\n      }\n    case OR:{\n      jj_consume_token(OR);\nop = \"|\";\n      break;\n      }\n    case REG_IDENT:{\n      op = Identifier();\n      break;\n      }\n    default:\n      jj_la1[102] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    jj_consume_token(COMMA);\n    expr2 = Expression(prop, pathprop);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case COMMA:{\n      jj_consume_token(COMMA);\n      filter = Expression(prop, pathprop);\n      break;\n      }\n    default:\n      jj_la1[103] = jj_gen;\n      ;\n    }\n    jj_consume_token(RPARENTH);\nexpr = new ExpressionFilter(op, expr2, filter); expr.setPosition(begin, getToken(0)); {if (\"\" != null) return expr;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n//-----------------------------------------------------------------------------------\n// Miscellaneous stuff\n//-----------------------------------------------------------------------------------\n\n// Identifier (returns String)\n  static final public \nString Identifier() throws ParseException {\n    jj_consume_token(REG_IDENT);\n{if (\"\" != null) return getToken(0).image;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Identifier (returns ExpressionIdent, storing position info)\n  static final public \nExpressionIdent IdentifierExpression() throws ParseException {String ident;\n        ExpressionIdent ret;\n    ident = Identifier();\nret = new ExpressionIdent(ident); ret.setPosition(getToken(0)); {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Identifier or min/max keyword (returns ExpressionIdent, storing position info)\n  static final public \nExpressionIdent IdentifierExpressionMinMax() throws ParseException {String ident;\n        ExpressionIdent ret;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_IDENT:{\n      ident = Identifier();\n      break;\n      }\n    case MIN:{\n      jj_consume_token(MIN);\nident=\"min\";\n      break;\n      }\n    case MAX:{\n      jj_consume_token(MAX);\nident=\"max\";\n      break;\n      }\n    default:\n      jj_la1[104] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\nret = new ExpressionIdent(ident); ret.setPosition(getToken(0)); {if (\"\" != null) return ret;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Primed identifier\n  static final public \nExpressionIdent IdentifierPrime() throws ParseException {\n    jj_consume_token(REG_IDENTPRIME);\n// Remove prime, create new ident and return\n                String s = getToken(0).image;\n                s = s.substring(0, s.length()-1);\n                ExpressionIdent expr = new ExpressionIdent(s);\n                expr.setPosition(token);\n                expr.setEndColumn(expr.getEndColumn() - 1);\n                {if (\"\" != null) return expr;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Equality operators: =, !=\n  static final public \nint EqNeq() throws ParseException {\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case EQ:{\n      jj_consume_token(EQ);\n{if (\"\" != null) return ExpressionBinaryOp.EQ;}\n      break;\n      }\n    case NE:{\n      jj_consume_token(NE);\n{if (\"\" != null) return ExpressionBinaryOp.NE;}\n      break;\n      }\n    default:\n      jj_la1[105] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    throw new Error(\"Missing return statement in function\");\n}\n\n// Relational operators: >, <, >=, <=\n  static final public \nint LtGt() throws ParseException {\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case GT:{\n      jj_consume_token(GT);\n{if (\"\" != null) return ExpressionBinaryOp.GT;}\n      break;\n      }\n    case LT:{\n      jj_consume_token(LT);\n{if (\"\" != null) return ExpressionBinaryOp.LT;}\n      break;\n      }\n    case GE:{\n      jj_consume_token(GE);\n{if (\"\" != null) return ExpressionBinaryOp.GE;}\n      break;\n      }\n    case LE:{\n      jj_consume_token(LE);\n{if (\"\" != null) return ExpressionBinaryOp.LE;}\n      break;\n      }\n    default:\n      jj_la1[106] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    throw new Error(\"Missing return statement in function\");\n}\n\n// For loop\n  static final public \nForLoop ForLoop() throws ParseException {String s;\n        Expression from = null, to = null, step = null;\n        ForLoop fl = new ForLoop();\n        Token begin;\nbegin = getToken(1);\n    s = Identifier();\n    jj_consume_token(EQ);\n    from = Expression(false, false);\n    jj_consume_token(COLON);\n    to = Expression(false, false);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case COLON:{\n      jj_consume_token(COLON);\n      step = Expression(false, false);\n      break;\n      }\n    default:\n      jj_la1[107] = jj_gen;\n      ;\n    }\n    jj_consume_token(0);\nfl.setLHS(s);\n                fl.setFrom(from);\n                fl.setTo(to);\n                if (step != null) fl.setStep(step);\n                fl.setPosition(begin, getToken(0));\n                {if (\"\" != null) return fl;}\n    throw new Error(\"Missing return statement in function\");\n}\n\n  static private boolean jj_2_1(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_1()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(0, xla); }\n  }\n\n  static private boolean jj_2_2(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_2()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(1, xla); }\n  }\n\n  static private boolean jj_2_3(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_3()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(2, xla); }\n  }\n\n  static private boolean jj_2_4(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_4()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(3, xla); }\n  }\n\n  static private boolean jj_2_5(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_5()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(4, xla); }\n  }\n\n  static private boolean jj_2_6(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_6()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(5, xla); }\n  }\n\n  static private boolean jj_2_7(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_7()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(6, xla); }\n  }\n\n  static private boolean jj_2_8(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_8()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(7, xla); }\n  }\n\n  static private boolean jj_2_9(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_9()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(8, xla); }\n  }\n\n  static private boolean jj_2_10(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_10()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(9, xla); }\n  }\n\n  static private boolean jj_2_11(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_11()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(10, xla); }\n  }\n\n  static private boolean jj_2_12(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_12()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(11, xla); }\n  }\n\n  static private boolean jj_2_13(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_13()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(12, xla); }\n  }\n\n  static private boolean jj_2_14(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_14()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(13, xla); }\n  }\n\n  static private boolean jj_2_15(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_15()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(14, xla); }\n  }\n\n  static private boolean jj_2_16(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_16()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(15, xla); }\n  }\n\n  static private boolean jj_2_17(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_17()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(16, xla); }\n  }\n\n  static private boolean jj_2_18(int xla)\n {\n    jj_la = xla; jj_lastpos = jj_scanpos = token;\n    try { return (!jj_3_18()); }\n    catch(LookaheadSuccess ls) { return true; }\n    finally { jj_save(17, xla); }\n  }\n\n  static private boolean jj_3R_ExpressionFuncMinMax_1520_11_161()\n {\n    if (jj_scan_token(MIN)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncMinMax_1520_9_146()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionFuncMinMax_1520_11_161()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionFuncMinMax_1520_42_162()) return true;\n    }\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_ExpressionFuncArgs_1546_9_163()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemHideRename_1133_11_81()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    if (jj_scan_token(RENAME)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_SystemHideRename_1136_19_91()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemInterleaved_1074_70_50()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_SystemFullParallel_1049_9_35()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_4()\n {\n    if (jj_scan_token(LABEL)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_RewardIndex_1817_87_242()\n {\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_3()\n {\n    if (jj_scan_token(LABEL)) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemHideRename_1127_9_80()\n {\n    if (jj_scan_token(DIVIDE)) return true;\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_SystemHideRename_1129_81_90()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemHideRename_1127_9_69()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_SystemHideRename_1127_9_80()) {\n    jj_scanpos = xsp;\n    if (jj_3R_SystemHideRename_1133_11_81()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncOrIdent_1507_11_160()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_ExpressionFuncArgs_1546_9_163()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemHideRename_1124_9_58()\n {\n    if (jj_3R_SystemAtomic_1152_9_68()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_SystemHideRename_1127_9_69()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_8()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncOrIdent_1505_9_145()\n {\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionFuncOrIdent_1507_11_160()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionForAll_1888_9_152()\n {\n    if (jj_scan_token(A)) return true;\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemFullParallel_1051_71_43()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_SystemParallel_1096_9_49()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_10()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(LBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1483_17_143()\n {\n    if (jj_3R_ExpressionFilter_1979_9_155()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1481_17_142()\n {\n    if (jj_3R_ExpressionLabel_1961_9_154()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1479_17_141()\n {\n    if (jj_3R_ExpressionStrategy_1907_9_153()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionExists_1869_9_151()\n {\n    if (jj_scan_token(E)) return true;\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1477_17_140()\n {\n    if (jj_3R_ExpressionForAll_1888_9_152()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemParallel_1098_11_59()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_SystemParallel_1099_65_70()) { jj_scanpos = xsp; break; }\n    }\n    if (jj_scan_token(RBRACKET)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_SystemHideRename_1124_9_58()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1475_17_139()\n {\n    if (jj_3R_ExpressionExists_1869_9_151()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1473_17_138()\n {\n    if (jj_3R_ExpressionReward_1760_9_150()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemParallel_1096_9_49()\n {\n    if (jj_3R_SystemHideRename_1124_9_58()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_SystemParallel_1098_11_59()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1471_17_137()\n {\n    if (jj_3R_ExpressionSS_1716_9_33()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_18()\n {\n    if (jj_scan_token(C)) return true;\n    if (jj_scan_token(LE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1469_17_136()\n {\n    if (jj_3R_ExpressionProb_1637_9_149()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1466_17_135()\n {\n    if (jj_3R_ExpressionParenth_1596_9_148()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRewardContents_1854_11_222()\n {\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1464_17_134()\n {\n    if (jj_3R_ExpressionFuncOldStyle_1534_9_147()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_17()\n {\n    if (jj_3R_ExpressionSS_1716_9_33()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRewardContents_1851_11_221()\n {\n    if (jj_scan_token(I)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1462_17_133()\n {\n    if (jj_3R_ExpressionFuncMinMax_1520_9_146()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_16()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRewardContents_1850_11_220()\n {\n    if (jj_scan_token(C)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRewardContents_1849_11_219()\n {\n    if (jj_scan_token(C)) return true;\n    if (jj_scan_token(LE)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1460_17_132()\n {\n    if (jj_3R_ExpressionFuncOrIdent_1505_9_145()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTimesDivide_1411_64_127()\n {\n    if (jj_scan_token(DIVIDE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1458_17_131()\n {\n    if (jj_3R_ExpressionLiteral_1556_9_144()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRewardContents_1846_11_218()\n {\n    if (jj_scan_token(S)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1788_69_183()\n {\n    if (jj_3R_Filter_1692_9_47()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRewardContents_1845_9_217()\n {\n    if (jj_3R_ExpressionSS_1716_9_33()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_RewardIndex_1819_33_245()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRewardContents_1842_9_182()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionRewardContents_1845_9_217()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionRewardContents_1846_11_218()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionRewardContents_1849_11_219()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionRewardContents_1850_11_220()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionRewardContents_1851_11_221()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionRewardContents_1854_11_222()) return true;\n    }\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionBasic_1457_9_130()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionBasic_1458_17_131()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1460_17_132()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1462_17_133()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1464_17_134()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1466_17_135()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1469_17_136()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1471_17_137()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1473_17_138()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1475_17_139()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1477_17_140()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1479_17_141()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1481_17_142()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionBasic_1483_17_143()) return true;\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_15()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemInterleaved_1072_9_42()\n {\n    if (jj_3R_SystemParallel_1096_9_49()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_SystemInterleaved_1074_70_50()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionUnaryMinus_1445_17_129()\n {\n    if (jj_3R_ExpressionBasic_1457_9_130()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionUnaryMinus_1442_17_128()\n {\n    if (jj_scan_token(MINUS)) return true;\n    if (jj_3R_ExpressionUnaryMinus_1441_9_124()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_RewardIndex_1817_22_241()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionPlusMinus_1394_62_123()\n {\n    if (jj_scan_token(MINUS)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_2()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_scan_token(COLON)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionUnaryMinus_1441_9_124()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionUnaryMinus_1442_17_128()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionUnaryMinus_1445_17_129()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_RewardIndex_1819_11_243()\n {\n    if (jj_scan_token(DIVIDE)) return true;\n    if (jj_scan_token(LBRACE)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_RewardIndex_1819_33_245()) {\n    jj_scanpos = xsp;\n    if (jj_3R_RewardIndex_1819_101_246()) return true;\n    }\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionPower_1428_17_125()\n {\n    if (jj_scan_token(POWER)) return true;\n    if (jj_3R_ExpressionPower_1426_9_120()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_RewardIndex_1817_9_232()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_RewardIndex_1817_22_241()) {\n    jj_scanpos = xsp;\n    if (jj_3R_RewardIndex_1817_87_242()) return true;\n    }\n    if (jj_scan_token(RBRACE)) return true;\n    xsp = jj_scanpos;\n    if (jj_3R_RewardIndex_1819_11_243()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemFullParallel_1049_9_35()\n {\n    if (jj_3R_SystemInterleaved_1072_9_42()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_SystemFullParallel_1051_71_43()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionPower_1426_9_120()\n {\n    if (jj_3R_ExpressionUnaryMinus_1441_9_124()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionPower_1428_17_125()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTimesDivide_1411_19_126()\n {\n    if (jj_scan_token(TIMES)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemDefn_1036_9_31()\n {\n    if (jj_3R_SystemFullParallel_1049_9_35()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTimesDivide_1411_17_121()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionTimesDivide_1411_19_126()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionTimesDivide_1411_64_127()) return true;\n    }\n    if (jj_3R_ExpressionPower_1426_9_120()) return true;\n    return false;\n  }\n\n  static private boolean jj_3_7()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_SystemDefn_1036_9_31()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTimesDivide_1409_9_116()\n {\n    if (jj_3R_ExpressionPower_1426_9_120()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionTimesDivide_1411_17_121()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1773_26_238()\n {\n    if (jj_scan_token(MAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1772_26_237()\n {\n    if (jj_scan_token(MIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1771_26_236()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1786_10_181()\n {\n    if (jj_scan_token(RMAXMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionPlusMinus_1394_19_122()\n {\n    if (jj_scan_token(PLUS)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1769_26_235()\n {\n    if (jj_scan_token(MAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1778_17_216()\n {\n    if (jj_scan_token(MAXMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1785_10_180()\n {\n    if (jj_scan_token(RMAXMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1768_26_234()\n {\n    if (jj_scan_token(MIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1777_17_215()\n {\n    if (jj_scan_token(MAXMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1784_10_179()\n {\n    if (jj_scan_token(RMINMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionPlusMinus_1394_17_117()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionPlusMinus_1394_19_122()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionPlusMinus_1394_62_123()) return true;\n    }\n    if (jj_3R_ExpressionTimesDivide_1409_9_116()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1767_26_233()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1776_17_214()\n {\n    if (jj_scan_token(MINMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1783_10_178()\n {\n    if (jj_scan_token(RMINMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1775_17_213()\n {\n    if (jj_scan_token(MINMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1782_10_177()\n {\n    if (jj_scan_token(RMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1781_10_176()\n {\n    if (jj_scan_token(RMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1771_17_212()\n {\n    if (jj_scan_token(MAX)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionReward_1771_26_236()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1772_26_237()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1773_26_238()) return true;\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1767_17_211()\n {\n    if (jj_scan_token(MIN)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionReward_1767_26_233()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1768_26_234()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1769_26_235()) return true;\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionPlusMinus_1392_9_113()\n {\n    if (jj_3R_ExpressionTimesDivide_1409_9_116()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionPlusMinus_1394_17_117()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1766_17_210()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1765_18_209()\n {\n    if (jj_3R_LtGt_2067_9_45()) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1764_18_208()\n {\n    if (jj_3R_RewardIndex_1817_9_232()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1763_19_207()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionSS_1724_55_39()\n {\n    if (jj_3R_Filter_1692_9_47()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1762_10_175()\n {\n    if (jj_scan_token(R)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionReward_1763_19_207()) jj_scanpos = xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionReward_1764_18_208()) jj_scanpos = xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionReward_1765_18_209()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1766_17_210()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1767_17_211()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1771_17_212()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1775_17_213()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1776_17_214()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1777_17_215()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1778_17_216()) return true;\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionReward_1760_9_150()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionReward_1762_10_175()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1781_10_176()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1782_10_177()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1783_10_178()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1784_10_179()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1785_10_180()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionReward_1786_10_181()) return true;\n    }\n    }\n    }\n    }\n    }\n    }\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_ExpressionRewardContents_1842_9_182()) return true;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionReward_1788_69_183()) jj_scanpos = xsp;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRelop_1372_11_114()\n {\n    if (jj_3R_LtGt_2067_9_45()) return true;\n    if (jj_3R_ExpressionPlusMinus_1392_9_113()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionRelop_1371_9_111()\n {\n    if (jj_3R_ExpressionPlusMinus_1392_9_113()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionRelop_1372_11_114()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionEquality_1358_11_112()\n {\n    if (jj_3R_EqNeq_2057_9_115()) return true;\n    if (jj_3R_ExpressionRelop_1371_9_111()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionEquality_1357_9_110()\n {\n    if (jj_3R_ExpressionRelop_1371_9_111()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionEquality_1358_11_112()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3_1()\n {\n    if (jj_scan_token(MODULE)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    if (jj_scan_token(EQ)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_6()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionNot_1343_17_109()\n {\n    if (jj_3R_ExpressionEquality_1357_9_110()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionNot_1341_17_108()\n {\n    if (jj_scan_token(NOT)) return true;\n    if (jj_3R_ExpressionNot_1340_9_106()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1258_99_101()\n {\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1257_99_99()\n {\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1256_99_97()\n {\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionSS_1721_17_37()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionSS_1719_19_44()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1255_99_95()\n {\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionSS_1719_17_36()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionSS_1719_19_44()) jj_scanpos = xsp;\n    if (jj_3R_LtGt_2067_9_45()) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionNot_1340_9_106()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionNot_1341_17_108()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionNot_1343_17_109()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionSS_1716_9_33()\n {\n    if (jj_scan_token(S)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionSS_1719_17_36()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionSS_1721_17_37()) return true;\n    }\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionSS_1724_55_39()) jj_scanpos = xsp;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionAnd_1328_11_107()\n {\n    if (jj_scan_token(AND)) return true;\n    if (jj_3R_ExpressionNot_1340_9_106()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionAnd_1327_9_104()\n {\n    if (jj_3R_ExpressionNot_1340_9_106()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionAnd_1328_11_107()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1663_51_174()\n {\n    if (jj_3R_Filter_1692_9_47()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_Filter_1695_19_67()\n {\n    if (jj_scan_token(MAX)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_Filter_1694_19_66()\n {\n    if (jj_scan_token(MIN)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionOr_1315_11_105()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_3R_ExpressionAnd_1327_9_104()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionOr_1314_9_102()\n {\n    if (jj_3R_ExpressionAnd_1327_9_104()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionOr_1315_11_105()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_Filter_1693_11_57()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_Filter_1694_19_66()) {\n    jj_scanpos = xsp;\n    if (jj_3R_Filter_1695_19_67()) return true;\n    }\n    if (jj_scan_token(RBRACE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_Update_899_36_41()\n {\n    if (jj_scan_token(AND)) return true;\n    if (jj_3R_UpdateElement_912_9_40()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_Filter_1692_9_47()\n {\n    if (jj_scan_token(LBRACE)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    if (jj_scan_token(RBRACE)) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_Filter_1693_11_57()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionIff_1302_11_103()\n {\n    if (jj_scan_token(IFF)) return true;\n    if (jj_3R_ExpressionOr_1314_9_102()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_LtGt_2070_9_54()\n {\n    if (jj_scan_token(LE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_LtGt_2069_9_53()\n {\n    if (jj_scan_token(GE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_LtGt_2068_9_52()\n {\n    if (jj_scan_token(LT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionIff_1301_9_92()\n {\n    if (jj_3R_ExpressionOr_1314_9_102()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionIff_1302_11_103()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_LtGt_2067_9_51()\n {\n    if (jj_scan_token(GT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_LtGt_2067_9_45()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_LtGt_2067_9_51()) {\n    jj_scanpos = xsp;\n    if (jj_3R_LtGt_2068_9_52()) {\n    jj_scanpos = xsp;\n    if (jj_3R_LtGt_2069_9_53()) {\n    jj_scanpos = xsp;\n    if (jj_3R_LtGt_2070_9_54()) return true;\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_UpdateElement_912_9_40()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_IdentifierPrime_2039_9_48()) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_EqNeq_2058_9_119()\n {\n    if (jj_scan_token(NE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionImplies_1289_11_93()\n {\n    if (jj_scan_token(IMPLIES)) return true;\n    if (jj_3R_ExpressionImplies_1288_9_82()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_EqNeq_2057_9_115()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_EqNeq_2057_9_118()) {\n    jj_scanpos = xsp;\n    if (jj_3R_EqNeq_2058_9_119()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_EqNeq_2057_9_118()\n {\n    if (jj_scan_token(EQ)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionImplies_1288_9_82()\n {\n    if (jj_3R_ExpressionIff_1301_9_92()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionImplies_1289_11_93()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3R_Update_899_10_34()\n {\n    if (jj_3R_UpdateElement_912_9_40()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_Update_899_36_41()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1648_26_231()\n {\n    if (jj_scan_token(MAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionITE_1274_17_83()\n {\n    if (jj_scan_token(QMARK)) return true;\n    if (jj_3R_ExpressionImplies_1288_9_82()) return true;\n    if (jj_scan_token(COLON)) return true;\n    if (jj_3R_ExpressionITE_1272_9_75()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1647_26_230()\n {\n    if (jj_scan_token(MIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1646_26_229()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_Update_897_9_30()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_Update_899_10_34()) {\n    jj_scanpos = xsp;\n    if (jj_scan_token(66)) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1661_10_173()\n {\n    if (jj_scan_token(PMAXMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_14()\n {\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    if (jj_scan_token(LPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1644_26_228()\n {\n    if (jj_scan_token(MAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1653_17_206()\n {\n    if (jj_scan_token(MAXMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1660_10_172()\n {\n    if (jj_scan_token(PMAXMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_13()\n {\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    if (jj_scan_token(LPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1643_26_227()\n {\n    if (jj_scan_token(MIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1652_17_205()\n {\n    if (jj_scan_token(MAXMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1659_10_171()\n {\n    if (jj_scan_token(PMINMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_12()\n {\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    if (jj_scan_token(LPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1642_26_226()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1651_17_204()\n {\n    if (jj_scan_token(MINMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1658_10_170()\n {\n    if (jj_scan_token(PMINMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_11()\n {\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    if (jj_scan_token(LPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1650_17_203()\n {\n    if (jj_scan_token(MINMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1657_10_169()\n {\n    if (jj_scan_token(PMAX)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1656_10_168()\n {\n    if (jj_scan_token(PMIN)) return true;\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1640_25_199()\n {\n    if (jj_3R_LtGt_2067_9_45()) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1639_26_198()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_5()\n {\n    if (jj_3R_Update_897_9_30()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_IdentifierPrime_2039_9_48()\n {\n    if (jj_scan_token(REG_IDENTPRIME)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionITE_1272_9_75()\n {\n    if (jj_3R_ExpressionImplies_1288_9_82()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionITE_1274_17_83()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1646_17_202()\n {\n    if (jj_scan_token(MAX)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionProb_1646_26_229()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1647_26_230()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1648_26_231()) return true;\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1258_20_100()\n {\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1257_20_98()\n {\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1642_17_201()\n {\n    if (jj_scan_token(MIN)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionProb_1642_26_226()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1643_26_227()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1644_26_228()) return true;\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1256_20_96()\n {\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1641_17_200()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_scan_token(QMARK)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFilter_1985_56_194()\n {\n    if (jj_scan_token(OR)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1255_20_94()\n {\n    if (jj_3R_IdentifierExpression_2017_9_32()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1260_11_89()\n {\n    if (jj_scan_token(EQ)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1259_11_88()\n {\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1258_11_87()\n {\n    if (jj_scan_token(GT)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_TimeBound_1258_20_100()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1258_99_101()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1257_11_86()\n {\n    if (jj_scan_token(GE)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_TimeBound_1257_20_98()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1257_99_99()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1256_11_85()\n {\n    if (jj_scan_token(LT)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_TimeBound_1256_20_96()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1256_99_97()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1639_10_167()\n {\n    if (jj_scan_token(P)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionProb_1639_26_198()) jj_scanpos = xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionProb_1640_25_199()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1641_17_200()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1642_17_201()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1646_17_202()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1650_17_203()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1651_17_204()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1652_17_205()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1653_17_206()) return true;\n    }\n    }\n    }\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1255_11_84()\n {\n    if (jj_scan_token(LE)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_TimeBound_1255_20_94()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1255_99_95()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_TimeBound_1255_9_76()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_TimeBound_1255_11_84()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1256_11_85()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1257_11_86()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1258_11_87()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1259_11_88()) {\n    jj_scanpos = xsp;\n    if (jj_3R_TimeBound_1260_11_89()) return true;\n    }\n    }\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionProb_1637_9_149()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionProb_1639_10_167()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1656_10_168()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1657_10_169()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1658_10_170()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1659_10_171()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1660_10_172()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionProb_1661_10_173()) return true;\n    }\n    }\n    }\n    }\n    }\n    }\n    if (jj_scan_token(LBRACKET)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionProb_1663_51_174()) jj_scanpos = xsp;\n    if (jj_scan_token(RBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_IdentifierExpression_2017_9_32()\n {\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalUnary_1242_17_61()\n {\n    if (jj_3R_ExpressionITE_1272_9_75()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalUnary_1238_19_74()\n {\n    if (jj_3R_TimeBound_1255_9_76()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalUnary_1237_19_73()\n {\n    if (jj_scan_token(G)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalUnary_1236_19_72()\n {\n    if (jj_scan_token(F)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalUnary_1235_19_71()\n {\n    if (jj_scan_token(X)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFilter_1985_34_193()\n {\n    if (jj_scan_token(AND)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFilter_1984_35_191()\n {\n    if (jj_scan_token(MAX)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalUnary_1233_17_60()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionTemporalUnary_1235_19_71()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionTemporalUnary_1236_19_72()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionTemporalUnary_1237_19_73()) return true;\n    }\n    }\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionTemporalUnary_1238_19_74()) jj_scanpos = xsp;\n    if (jj_3R_ExpressionTemporalUnary_1231_9_55()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_Identifier_2006_9_29()\n {\n    if (jj_scan_token(REG_IDENT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionLabel_1963_47_189()\n {\n    if (jj_scan_token(INIT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalUnary_1231_9_55()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionTemporalUnary_1233_17_60()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionTemporalUnary_1242_17_61()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalBinary_1217_19_65()\n {\n    if (jj_3R_TimeBound_1255_9_76()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncArgs_1546_72_197()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFilter_1990_11_196()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalBinary_1216_19_64()\n {\n    if (jj_scan_token(R)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncOldStyle_1534_83_166()\n {\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalBinary_1215_19_63()\n {\n    if (jj_scan_token(W)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalBinary_1214_19_62()\n {\n    if (jj_scan_token(U)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFilter_1986_11_195()\n {\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFilter_1985_11_192()\n {\n    if (jj_scan_token(PLUS)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFilter_1984_11_190()\n {\n    if (jj_scan_token(MIN)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalBinary_1212_17_56()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionTemporalBinary_1214_19_62()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionTemporalBinary_1215_19_63()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionTemporalBinary_1216_19_64()) return true;\n    }\n    }\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionTemporalBinary_1217_19_65()) jj_scanpos = xsp;\n    if (jj_3R_ExpressionTemporalUnary_1231_9_55()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionLabel_1963_30_188()\n {\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFilter_1979_9_155()\n {\n    if (jj_scan_token(FILTER)) return true;\n    if (jj_scan_token(LPARENTH)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionFilter_1984_11_190()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionFilter_1984_35_191()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionFilter_1985_11_192()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionFilter_1985_34_193()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionFilter_1985_56_194()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionFilter_1986_11_195()) return true;\n    }\n    }\n    }\n    }\n    }\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionFilter_1990_11_196()) jj_scanpos = xsp;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionParenth_1596_9_148()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_Expression_1179_9_38()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionTemporalBinary_1209_9_46()\n {\n    if (jj_3R_ExpressionTemporalUnary_1231_9_55()) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionTemporalBinary_1212_17_56()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncOldStyle_1534_60_165()\n {\n    if (jj_scan_token(MAX)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemHideRename_1129_81_90()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionLiteral_1583_9_159()\n {\n    if (jj_scan_token(FALSE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionLiteral_1581_9_158()\n {\n    if (jj_scan_token(TRUE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionLabel_1961_9_154()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionLabel_1963_30_188()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionLabel_1963_47_189()) return true;\n    }\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategy_1914_51_225()\n {\n    if (jj_3R_ExpressionReward_1760_9_150()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionLiteral_1570_9_157()\n {\n    if (jj_scan_token(REG_DOUBLE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategyCoalitionPlayer_1947_9_247()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_scan_token(104)) {\n    jj_scanpos = xsp;\n    if (jj_scan_token(107)) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncOldStyle_1534_37_164()\n {\n    if (jj_scan_token(MIN)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_Expression_1179_9_38()\n {\n    if (jj_3R_ExpressionTemporalBinary_1209_9_46()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionLiteral_1557_9_156()\n {\n    if (jj_scan_token(REG_INT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionLiteral_1556_9_144()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionLiteral_1557_9_156()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionLiteral_1570_9_157()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionLiteral_1581_9_158()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionLiteral_1583_9_159()) return true;\n    }\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategyCoalition_1936_11_248()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_ExpressionStrategyCoalitionPlayer_1947_9_247()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategyCoalition_1935_11_244()\n {\n    if (jj_3R_ExpressionStrategyCoalitionPlayer_1947_9_247()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionStrategyCoalition_1936_11_248()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncMinMax_1520_42_162()\n {\n    if (jj_scan_token(MAX)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategyCoalition_1935_9_240()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionStrategyCoalition_1935_11_244()) jj_scanpos = xsp;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategyCoalition_1933_9_239()\n {\n    if (jj_scan_token(TIMES)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategyCoalition_1933_9_223()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionStrategyCoalition_1933_9_239()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionStrategyCoalition_1935_9_240()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncArgs_1546_9_163()\n {\n    if (jj_3R_Expression_1179_9_38()) return true;\n    Token xsp;\n    while (true) {\n      xsp = jj_scanpos;\n      if (jj_3R_ExpressionFuncArgs_1546_72_197()) { jj_scanpos = xsp; break; }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_SystemAtomic_1159_10_79()\n {\n    if (jj_scan_token(LPARENTH)) return true;\n    if (jj_3R_SystemDefn_1036_9_31()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemAtomic_1157_10_78()\n {\n    if (jj_scan_token(DQUOTE)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    if (jj_scan_token(DQUOTE)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemAtomic_1155_9_77()\n {\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemParallel_1099_65_70()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategy_1916_11_187()\n {\n    if (jj_3R_ExpressionParenth_1596_9_148()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemAtomic_1152_9_68()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_SystemAtomic_1155_9_77()) {\n    jj_scanpos = xsp;\n    if (jj_3R_SystemAtomic_1157_10_78()) {\n    jj_scanpos = xsp;\n    if (jj_3R_SystemAtomic_1159_10_79()) return true;\n    }\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionFuncOldStyle_1534_9_147()\n {\n    if (jj_scan_token(FUNC)) return true;\n    if (jj_scan_token(LPARENTH)) return true;\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionFuncOldStyle_1534_37_164()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionFuncOldStyle_1534_60_165()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionFuncOldStyle_1534_83_166()) return true;\n    }\n    }\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_ExpressionFuncArgs_1546_9_163()) return true;\n    if (jj_scan_token(RPARENTH)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategy_1914_11_224()\n {\n    if (jj_3R_ExpressionProb_1637_9_149()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategy_1914_9_186()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionStrategy_1914_11_224()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionStrategy_1914_51_225()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategy_1911_11_185()\n {\n    if (jj_scan_token(DLBRACKET)) return true;\n    if (jj_3R_ExpressionStrategyCoalition_1933_9_223()) return true;\n    if (jj_scan_token(DRBRACKET)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_SystemHideRename_1136_19_91()\n {\n    if (jj_scan_token(COMMA)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    if (jj_scan_token(RENAME)) return true;\n    if (jj_3R_Identifier_2006_9_29()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_RewardIndex_1819_101_246()\n {\n    if (jj_3R_Expression_1179_9_38()) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategy_1910_10_184()\n {\n    if (jj_scan_token(DLT)) return true;\n    if (jj_3R_ExpressionStrategyCoalition_1933_9_223()) return true;\n    if (jj_scan_token(DGT)) return true;\n    return false;\n  }\n\n  static private boolean jj_3_9()\n {\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    if (jj_scan_token(OR)) return true;\n    return false;\n  }\n\n  static private boolean jj_3R_ExpressionStrategy_1907_9_153()\n {\n    Token xsp;\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionStrategy_1910_10_184()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionStrategy_1911_11_185()) return true;\n    }\n    xsp = jj_scanpos;\n    if (jj_3R_ExpressionStrategy_1914_9_186()) {\n    jj_scanpos = xsp;\n    if (jj_3R_ExpressionStrategy_1916_11_187()) return true;\n    }\n    return false;\n  }\n\n  static private boolean jj_initialized_once = false;\n  /** Generated Token Manager. */\n  static public PrismParserTokenManager token_source;\n  static SimpleCharStream jj_input_stream;\n  /** Current token. */\n  static public Token token;\n  /** Next token. */\n  static public Token jj_nt;\n  static private int jj_ntk;\n  static private Token jj_scanpos, jj_lastpos;\n  static private int jj_la;\n  static private int jj_gen;\n  static final private int[] jj_la1 = new int[108];\n  static private int[] jj_la1_0;\n  static private int[] jj_la1_1;\n  static private int[] jj_la1_2;\n  static private int[] jj_la1_3;\n  static {\n\t   jj_la1_init_0();\n\t   jj_la1_init_1();\n\t   jj_la1_init_2();\n\t   jj_la1_init_3();\n\t}\n\tprivate static void jj_la1_init_0() {\n\t   jj_la1_0 = new int[] {0x228804c0,0x208804c0,0x2000000,0x20340848,0x0,0x20340848,0x20340848,0x0,0x20340848,0x400,0x0,0x80,0x480,0x10000210,0x10000210,0x0,0x40,0x0,0x2000000,0x10000030,0x0,0x4000000,0x0,0x0,0x0,0x1740808,0x1740808,0x0,0x0,0x0,0x1740808,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x1400000,0x0,0x1740808,0x1740808,0x1740808,0x1740808,0x1740808,0x0,0x0,0x0,0x0,0x0,0x0,0x340808,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x340808,0x340808,0x0,0x0,0x0,0x0,0x40000,0x0,0x0,0x0,0xc0000000,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0xc0000000,0x0,0x0,0x1740808,0x1740808,0x0,0x0,0x9740908,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x2000000,0x0,0x0,0x0,0x0,0x0,0x0,};\n\t}\n\tprivate static void jj_la1_init_1() {\n\t   jj_la1_1 = new int[] {0xfe03a2,0x7e0082,0x800320,0xff51fc11,0x0,0xff51fc11,0xff51fc11,0x0,0xff51fc11,0x80000,0x82,0x0,0x2e0082,0x0,0x0,0x500000,0x500000,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0xff01fc51,0xff01fc51,0x0,0x0,0x0,0xff01fc51,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x40000000,0x0,0x40000000,0x40,0x0,0xff01fc51,0xff01fc51,0xff01fc51,0xff01fc51,0xff01fc51,0x0,0x0,0x0,0x0,0x0,0x0,0xff01fc11,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0xff01fc11,0xff01fc11,0x0,0x11,0x11,0x0,0x0,0x0,0x11,0x11,0x1d,0x1fc00,0x0,0x0,0x11,0x0,0x0,0x0,0x0,0x0,0x11,0x11,0x1d,0x7f000000,0x0,0xff01fc51,0xff01fc51,0x0,0x80000000,0xff01fc51,0x0,0x7f01fc00,0x7f01fc00,0x0,0x0,0x0,0x0,0x0,0x11,0x0,0x11,0x0,0x0,0x0,};\n\t}\n\tprivate static void jj_la1_init_2() {\n\t   jj_la1_2 = new int[] {0x3,0x1,0x2,0x8088024,0x1000,0x8088024,0x8088024,0x1000,0x8088024,0x0,0x0,0x1,0x1,0x0,0x0,0x0,0x0,0x800000,0x0,0x20000,0x0,0x0,0x20000,0x0,0x80000000,0x80a8024,0x80a8024,0x40,0x8004,0x2000,0x80a8024,0x0,0x20000,0x2000,0x2000,0x200000,0x2000,0x2000,0x200000,0x8000,0x18,0x66820000,0x18,0x0,0x66820000,0x8088024,0x8088024,0x8088024,0x8088024,0x8088024,0x66820000,0x0,0x100,0x200,0x80,0x40,0x8088024,0x1800000,0x66000000,0x80000000,0x80000000,0x0,0x0,0x0,0x8088004,0x8088004,0x8000,0x0,0x0,0x2000,0x4,0x8000,0x800000,0x800000,0x66800000,0x0,0x200000,0x200000,0x0,0x8000,0x66808000,0x200000,0x8000,0x200000,0x800000,0x800000,0x66800000,0x0,0x200000,0x8088024,0x8088024,0x0,0x0,0x8088024,0x8080000,0x0,0x8000,0x2000,0x0,0x0,0x0,0x0,0x800000c0,0x2000,0x0,0x1800000,0x66000000,0x800,};\n\t}\n\tprivate static void jj_la1_init_3() {\n\t   jj_la1_3 = new int[] {0x0,0x0,0x0,0xb81,0x0,0xb81,0xb81,0x0,0xb81,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x800,0x0,0x0,0x800,0x0,0xb81,0xb81,0x0,0x0,0x0,0xb81,0x800,0x0,0x0,0x0,0x4,0x0,0x0,0x4,0x880,0x0,0x0,0x0,0x0,0x0,0xb81,0xb81,0xb81,0xb81,0xb81,0x0,0x40,0x0,0x0,0x0,0x0,0xb81,0x0,0x0,0x1,0x1,0x6,0x6,0x8,0xb81,0xb80,0x0,0x0,0x800,0x0,0x300,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0x0,0xb81,0xb81,0x4,0x0,0xb81,0x0,0x0,0x0,0x0,0x900,0x2,0x900,0x800,0x800,0x0,0x800,0x0,0x0,0x0,};\n\t}\n  static final private JJCalls[] jj_2_rtns = new JJCalls[18];\n  static private boolean jj_rescan = false;\n  static private int jj_gc = 0;\n\n  /** Constructor with InputStream. */\n  public PrismParser(java.io.InputStream stream) {\n\t  this(stream, null);\n  }\n  /** Constructor with InputStream and supplied encoding */\n  public PrismParser(java.io.InputStream stream, String encoding) {\n\t if (jj_initialized_once) {\n\t   System.out.println(\"ERROR: Second call to constructor of static parser.  \");\n\t   System.out.println(\"\t   You must either use ReInit() or set the JavaCC option STATIC to false\");\n\t   System.out.println(\"\t   during parser generation.\");\n\t   throw new Error();\n\t }\n\t jj_initialized_once = true;\n\t try { jj_input_stream = new SimpleCharStream(stream, encoding, 1, 1); } catch(java.io.UnsupportedEncodingException e) { throw new RuntimeException(e); }\n\t token_source = new PrismParserTokenManager(jj_input_stream);\n\t token = new Token();\n\t jj_ntk = -1;\n\t jj_gen = 0;\n\t for (int i = 0; i < 108; i++) jj_la1[i] = -1;\n\t for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Reinitialise. */\n  static public void ReInit(java.io.InputStream stream) {\n\t  ReInit(stream, null);\n  }\n  /** Reinitialise. */\n  static public void ReInit(java.io.InputStream stream, String encoding) {\n\t try { jj_input_stream.ReInit(stream, encoding, 1, 1); } catch(java.io.UnsupportedEncodingException e) { throw new RuntimeException(e); }\n\t token_source.ReInit(jj_input_stream);\n\t token = new Token();\n\t jj_ntk = -1;\n\t jj_gen = 0;\n\t for (int i = 0; i < 108; i++) jj_la1[i] = -1;\n\t for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Constructor. */\n  public PrismParser(java.io.Reader stream) {\n\t if (jj_initialized_once) {\n\t   System.out.println(\"ERROR: Second call to constructor of static parser. \");\n\t   System.out.println(\"\t   You must either use ReInit() or set the JavaCC option STATIC to false\");\n\t   System.out.println(\"\t   during parser generation.\");\n\t   throw new Error();\n\t }\n\t jj_initialized_once = true;\n\t jj_input_stream = new SimpleCharStream(stream, 1, 1);\n\t token_source = new PrismParserTokenManager(jj_input_stream);\n\t token = new Token();\n\t jj_ntk = -1;\n\t jj_gen = 0;\n\t for (int i = 0; i < 108; i++) jj_la1[i] = -1;\n\t for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Reinitialise. */\n  static public void ReInit(java.io.Reader stream) {\n\tif (jj_input_stream == null) {\n\t   jj_input_stream = new SimpleCharStream(stream, 1, 1);\n\t} else {\n\t   jj_input_stream.ReInit(stream, 1, 1);\n\t}\n\tif (token_source == null) {\n token_source = new PrismParserTokenManager(jj_input_stream);\n\t}\n\n\t token_source.ReInit(jj_input_stream);\n\t token = new Token();\n\t jj_ntk = -1;\n\t jj_gen = 0;\n\t for (int i = 0; i < 108; i++) jj_la1[i] = -1;\n\t for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Constructor with generated Token Manager. */\n  public PrismParser(PrismParserTokenManager tm) {\n\t if (jj_initialized_once) {\n\t   System.out.println(\"ERROR: Second call to constructor of static parser. \");\n\t   System.out.println(\"\t   You must either use ReInit() or set the JavaCC option STATIC to false\");\n\t   System.out.println(\"\t   during parser generation.\");\n\t   throw new Error();\n\t }\n\t jj_initialized_once = true;\n\t token_source = tm;\n\t token = new Token();\n\t jj_ntk = -1;\n\t jj_gen = 0;\n\t for (int i = 0; i < 108; i++) jj_la1[i] = -1;\n\t for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  /** Reinitialise. */\n  public void ReInit(PrismParserTokenManager tm) {\n\t token_source = tm;\n\t token = new Token();\n\t jj_ntk = -1;\n\t jj_gen = 0;\n\t for (int i = 0; i < 108; i++) jj_la1[i] = -1;\n\t for (int i = 0; i < jj_2_rtns.length; i++) jj_2_rtns[i] = new JJCalls();\n  }\n\n  static private Token jj_consume_token(int kind) throws ParseException {\n\t Token oldToken;\n\t if ((oldToken = token).next != null) token = token.next;\n\t else token = token.next = token_source.getNextToken();\n\t jj_ntk = -1;\n\t if (token.kind == kind) {\n\t   jj_gen++;\n\t   if (++jj_gc > 100) {\n\t\t jj_gc = 0;\n\t\t for (int i = 0; i < jj_2_rtns.length; i++) {\n\t\t   JJCalls c = jj_2_rtns[i];\n\t\t   while (c != null) {\n\t\t\t if (c.gen < jj_gen) c.first = null;\n\t\t\t c = c.next;\n\t\t   }\n\t\t }\n\t   }\n\t   return token;\n\t }\n\t token = oldToken;\n\t jj_kind = kind;\n\t throw generateParseException();\n  }\n\n  @SuppressWarnings(\"serial\")\n  static private final class LookaheadSuccess extends java.lang.Error {\n    @Override\n    public Throwable fillInStackTrace() {\n      return this;\n    }\n  }\n  static private final LookaheadSuccess jj_ls = new LookaheadSuccess();\n  static private boolean jj_scan_token(int kind) {\n\t if (jj_scanpos == jj_lastpos) {\n\t   jj_la--;\n\t   if (jj_scanpos.next == null) {\n\t\t jj_lastpos = jj_scanpos = jj_scanpos.next = token_source.getNextToken();\n\t   } else {\n\t\t jj_lastpos = jj_scanpos = jj_scanpos.next;\n\t   }\n\t } else {\n\t   jj_scanpos = jj_scanpos.next;\n\t }\n\t if (jj_rescan) {\n\t   int i = 0; Token tok = token;\n\t   while (tok != null && tok != jj_scanpos) { i++; tok = tok.next; }\n\t   if (tok != null) jj_add_error_token(kind, i);\n\t }\n\t if (jj_scanpos.kind != kind) return true;\n\t if (jj_la == 0 && jj_scanpos == jj_lastpos) throw jj_ls;\n\t return false;\n  }\n\n\n/** Get the next Token. */\n  static final public Token getNextToken() {\n\t if (token.next != null) token = token.next;\n\t else token = token.next = token_source.getNextToken();\n\t jj_ntk = -1;\n\t jj_gen++;\n\t return token;\n  }\n\n/** Get the specific Token. */\n  static final public Token getToken(int index) {\n\t Token t = token;\n\t for (int i = 0; i < index; i++) {\n\t   if (t.next != null) t = t.next;\n\t   else t = t.next = token_source.getNextToken();\n\t }\n\t return t;\n  }\n\n  static private int jj_ntk_f() {\n\t if ((jj_nt=token.next) == null)\n\t   return (jj_ntk = (token.next=token_source.getNextToken()).kind);\n\t else\n\t   return (jj_ntk = jj_nt.kind);\n  }\n\n  static private java.util.List<int[]> jj_expentries = new java.util.ArrayList<int[]>();\n  static private int[] jj_expentry;\n  static private int jj_kind = -1;\n  static private int[] jj_lasttokens = new int[100];\n  static private int jj_endpos;\n\n  static private void jj_add_error_token(int kind, int pos) {\n\t if (pos >= 100) {\n\t\treturn;\n\t }\n\n\t if (pos == jj_endpos + 1) {\n\t   jj_lasttokens[jj_endpos++] = kind;\n\t } else if (jj_endpos != 0) {\n\t   jj_expentry = new int[jj_endpos];\n\n\t   for (int i = 0; i < jj_endpos; i++) {\n\t\t jj_expentry[i] = jj_lasttokens[i];\n\t   }\n\n\t   for (int[] oldentry : jj_expentries) {\n\t\t if (oldentry.length == jj_expentry.length) {\n\t\t   boolean isMatched = true;\n\n\t\t   for (int i = 0; i < jj_expentry.length; i++) {\n\t\t\t if (oldentry[i] != jj_expentry[i]) {\n\t\t\t   isMatched = false;\n\t\t\t   break;\n\t\t\t }\n\n\t\t   }\n\t\t   if (isMatched) {\n\t\t\t jj_expentries.add(jj_expentry);\n\t\t\t break;\n\t\t   }\n\t\t }\n\t   }\n\n\t   if (pos != 0) {\n\t\t jj_lasttokens[(jj_endpos = pos) - 1] = kind;\n\t   }\n\t }\n  }\n\n  /** Generate ParseException. */\n  static public ParseException generateParseException() {\n\t jj_expentries.clear();\n\t boolean[] la1tokens = new boolean[110];\n\t if (jj_kind >= 0) {\n\t   la1tokens[jj_kind] = true;\n\t   jj_kind = -1;\n\t }\n\t for (int i = 0; i < 108; i++) {\n\t   if (jj_la1[i] == jj_gen) {\n\t\t for (int j = 0; j < 32; j++) {\n\t\t   if ((jj_la1_0[i] & (1<<j)) != 0) {\n\t\t\t la1tokens[j] = true;\n\t\t   }\n\t\t   if ((jj_la1_1[i] & (1<<j)) != 0) {\n\t\t\t la1tokens[32+j] = true;\n\t\t   }\n\t\t   if ((jj_la1_2[i] & (1<<j)) != 0) {\n\t\t\t la1tokens[64+j] = true;\n\t\t   }\n\t\t   if ((jj_la1_3[i] & (1<<j)) != 0) {\n\t\t\t la1tokens[96+j] = true;\n\t\t   }\n\t\t }\n\t   }\n\t }\n\t for (int i = 0; i < 110; i++) {\n\t   if (la1tokens[i]) {\n\t\t jj_expentry = new int[1];\n\t\t jj_expentry[0] = i;\n\t\t jj_expentries.add(jj_expentry);\n\t   }\n\t }\n\t jj_endpos = 0;\n\t jj_rescan_token();\n\t jj_add_error_token(0, 0);\n\t int[][] exptokseq = new int[jj_expentries.size()][];\n\t for (int i = 0; i < jj_expentries.size(); i++) {\n\t   exptokseq[i] = jj_expentries.get(i);\n\t }\n\t return new ParseException(token, exptokseq, tokenImage);\n  }\n\n  static private boolean trace_enabled;\n\n/** Trace enabled. */\n  static final public boolean trace_enabled() {\n\t return trace_enabled;\n  }\n\n  /** Enable tracing. */\n  static final public void enable_tracing() {\n  }\n\n  /** Disable tracing. */\n  static final public void disable_tracing() {\n  }\n\n  static private void jj_rescan_token() {\n\t jj_rescan = true;\n\t for (int i = 0; i < 18; i++) {\n\t   try {\n\t\t JJCalls p = jj_2_rtns[i];\n\n\t\t do {\n\t\t   if (p.gen > jj_gen) {\n\t\t\t jj_la = p.arg; jj_lastpos = jj_scanpos = p.first;\n\t\t\t switch (i) {\n\t\t\t   case 0: jj_3_1(); break;\n\t\t\t   case 1: jj_3_2(); break;\n\t\t\t   case 2: jj_3_3(); break;\n\t\t\t   case 3: jj_3_4(); break;\n\t\t\t   case 4: jj_3_5(); break;\n\t\t\t   case 5: jj_3_6(); break;\n\t\t\t   case 6: jj_3_7(); break;\n\t\t\t   case 7: jj_3_8(); break;\n\t\t\t   case 8: jj_3_9(); break;\n\t\t\t   case 9: jj_3_10(); break;\n\t\t\t   case 10: jj_3_11(); break;\n\t\t\t   case 11: jj_3_12(); break;\n\t\t\t   case 12: jj_3_13(); break;\n\t\t\t   case 13: jj_3_14(); break;\n\t\t\t   case 14: jj_3_15(); break;\n\t\t\t   case 15: jj_3_16(); break;\n\t\t\t   case 16: jj_3_17(); break;\n\t\t\t   case 17: jj_3_18(); break;\n\t\t\t }\n\t\t   }\n\t\t   p = p.next;\n\t\t } while (p != null);\n\n\t\t } catch(LookaheadSuccess ls) { }\n\t }\n\t jj_rescan = false;\n  }\n\n  static private void jj_save(int index, int xla) {\n\t JJCalls p = jj_2_rtns[index];\n\t while (p.gen > jj_gen) {\n\t   if (p.next == null) { p = p.next = new JJCalls(); break; }\n\t   p = p.next;\n\t }\n\n\t p.gen = jj_gen + xla - jj_la; \n\t p.first = token;\n\t p.arg = xla;\n  }\n\n  static final class JJCalls {\n\t int gen;\n\t Token first;\n\t int arg;\n\t JJCalls next;\n  }\n\n}\n\n//-----------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/parser/PrismParser.jj",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\noptions {\n\tLOOKAHEAD = 1;\n\tUNICODE_INPUT = true;\n}\n\nPARSER_BEGIN(PrismParser)\n\npackage parser;\n\nimport java.io.*;\nimport java.util.List;\nimport java.util.ArrayList;\nimport java.util.HashSet;\n\nimport jltl2ba.SimpleLTL;\nimport parser.BooleanUtils;\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.ModelInfo;\nimport parser.visitor.*;\nimport prism.ModelType;\nimport prism.PrismLangException;\n\n@SuppressWarnings({\"unused\", \"static-access\", \"serial\"})\npublic class PrismParser\n{\n\t// The model associated with the properties file being parsed\n\tprivate static ModelInfo modelInfo;\n\t\n\t// List of keyword strings\n\tprivate static ArrayList<String> keywordList = new ArrayList<>();\n\tstatic {\n\t\tkeywordList.clear();\n\t\tfor (int i = PrismParserConstants.COMMENT+1; i < PrismParserConstants.NOT; i++) {\n\t\t\tkeywordList.add(PrismParserConstants.tokenImage[i].replaceAll(\"\\\"\", \"\"));\n\t\t}\n\t}\n\tprivate static HashSet<String> keywordSet = new HashSet<>(keywordList);\n\t\n\t//-----------------------------------------------------------------------------------\n\t// Main method for testing purposes\n\t//-----------------------------------------------------------------------------------\n\n\tpublic static void main(String[] args)\n\t{\n\t\tPrismParser p = null;\n\t\tInputStream str = null;\n\t\tString src = null;\n\t\t\n\t\ttry {\n\t\t\tif (args.length == 0) {\n\t\t\t\tSystem.out.println(\"Usage: java parser.PrismParser <switch> [<file>]\");\n\t\t\t\tSystem.out.println(\"Where: <switch> = -modulesfile or -mf\");\n\t\t\t\tSystem.out.println(\"                  -propertiesfile or -pf\");\n\t\t\t\tSystem.out.println(\"                  -expression or -e\");\n\t\t\t\tSystem.out.println(\"                  -ltl or -l\");\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t\t\n\t\t\tp = new PrismParser();\n\t\t\tstr = (args.length > 1) ? new FileInputStream(args[1]) : System.in;\n\t\t\tsrc = (args.length > 1) ? \"file \"+args[1] : \"stdin\";\n\t\t\tSystem.out.println(\"Reading from \"+src+\"...\\n\");\n\t\t\t\n\t\t\tif (args[0].equals(\"-modulesfile\") || args[0].equals(\"-mf\")) {\n\t\t\t\tModulesFile mf = p.parseModulesFile(str);\n\t\t\t\tSystem.out.print(\"Modules file:\\n=============\\n\\n\" + mf);\n\t\t\t\tSystem.out.print(\"\\nTree:\\n=====\\n\" + mf.toTreeString());\n\t\t\t\tmf.tidyUp();\n\t\t\t\tSystem.out.print(\"\\nAnd after expansion:\\n====================\\n\\n\" +mf);\n\t\t\t}\n\t\t\telse if (args[0].equals(\"-propertiesfile\") || args[0].equals(\"-pf\")) {\n\t\t\t\tPropertiesFile pf = p.parsePropertiesFile(new ModulesFile(), str);\n\t\t\t\tSystem.out.print(\"Properties file:\\n================\\n\\n\" + pf);\n\t\t\t\tSystem.out.print(\"\\nTree:\\n=====\\n\" + pf.toTreeString());\n\t\t\t\tpf.tidyUp();\n\t\t\t\tSystem.out.print(\"\\nAnd after expansion:\\n====================\\n\\n\" + pf);\n\t\t\t}\n\t\t\telse if (args[0].equals(\"-expression\") || args[0].equals(\"-e\")) {\n\t\t\t\tExpression expr = p.parseSingleExpression(str);\n\t\t\t\tSystem.out.println(\"Expression: \" + expr.toString());\n\t\t\t\tSystem.out.print(\"Tree:\\n=====\\n\" + expr.toTreeString());\n\t\t\t\texpr.typeCheck();\n\t\t\t\texpr.semanticCheck();\n\t\t\t\tSystem.out.println(\"Type: \" + expr.getType().getTypeString());\n\t\t\t\tSystem.out.println(\"Eval: \" + expr.evaluate());\n\t\t\t}\n\t\t\telse if (args[0].equals(\"-ltl\") || args[0].equals(\"-l\")) {\n\t\t\t\tExpression expr = p.parseSingleLTLFormula(str);\n\t\t\t\texpr = (Expression) expr.accept(new ASTTraverseModify() {\n\t\t\t\t\tpublic Object visit(ExpressionIdent e) throws PrismLangException\n\t\t\t\t\t{\n\t\t\t\t\t\treturn new parser.ast.ExpressionVar(e.getName(), TypeBool.getInstance());\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\tSystem.out.println(\"LTL formula: \" + expr.toString());\n\t\t\t\tSystem.out.print(\"Tree:\\n=====\\n\" + expr.toTreeString());\n\t\t\t\texpr.typeCheck();\n\t\t\t\t//expr.semanticCheck();\n\t\t\t\tSystem.out.println(\"Type: \" + expr.getType().getTypeString());\n\t\t\t\tboolean pnf = Expression.isPositiveNormalFormLTL(expr);\n\t\t\t\tSystem.out.println(\"Positive normal form: \" + pnf);\n\t\t\t\tSystem.out.println(\"Syntactically co-safe: \" + Expression.isCoSafeLTLSyntactic(expr));\n\t\t\t\tif (!pnf) {\n\t\t\t\t\tExpression exprPnf = BooleanUtils.convertLTLToPositiveNormalForm(expr.deepCopy());\n\t\t\t\t\tSystem.out.println(\"Positive normal form conversion: \" + exprPnf);\n\t\t\t\t\tSystem.out.println(\"Syntactically co-safe: \" + Expression.isCoSafeLTLSyntactic(exprPnf));\n\t\t\t\t}\n\t\t\t\tExpression expr2 = (Expression) expr.deepCopy().accept(new ASTTraverseModify() {\n\t\t\t\t\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t\t\t\t\t{\n\t\t\t\t\t\t\treturn new parser.ast.ExpressionLabel(e.getName());\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\tSimpleLTL sltl = expr2.convertForJltl2ba();\n\t\t\t\tSystem.out.println(\"LBT: \" + sltl.toStringLBT());\n\t\t\t\tSystem.out.println(\"Spot: \" + sltl.toStringSpot());\n\t\t\t\tSystem.out.println(\"Spin: \" + sltl.toStringSpin());\n\t\t\t} else {\n\t\t\t\tSystem.out.println(\"Unknown switch\"); System.exit(1);\n\t\t\t}\n\t\t}\n\t\tcatch (PrismLangException e) {\n\t\t\tSystem.out.println(\"Error in \"+src+\": \" + e.getMessage()+\".\"); System.exit(1);\n\t\t}\n\t\tcatch (FileNotFoundException e) {\n\t\t\tSystem.out.println(e); System.exit(1);\n\t\t}\n\t}\n\n\t//-----------------------------------------------------------------------------------\n\t// Methods called by Prism\n\t//-----------------------------------------------------------------------------------\n\n\t// Constructor\n\n\tpublic PrismParser()\n\t{\n\t\t// Call default constructor\n\t\tthis(System.in);\n\t\tsetTabSize(8);\n\t}\n\t\n\t// Parse modules file\n\t\n\tpublic ModulesFile parseModulesFile(InputStream str) throws PrismLangException { return parseModulesFile(str, null); }\n\t\n\tpublic ModulesFile parseModulesFile(InputStream str, ModelType typeOverride) throws PrismLangException\n\t{\n\t\tModulesFile mf = null;\n\t\t\n\t\t// (Re)start parser\n\t\tReInit(str);\n\t\t// Parse\n\t\ttry {\n\t\t\tmf = ModulesFile();\n\t\t}\n\t\tcatch (ParseException e) {\n\t\t\tthrow generateSyntaxError(e);\n\t\t}\n\t\t// Override type of model if requested\n\t\tif (typeOverride != null) {\n\t\t\tmf.setModelTypeInFile(typeOverride);\n\t\t}\n\t\t\n\t\treturn mf;\n\t}\n\t\n\t// Parse properties file (pass ModulesFile in to get at its constants)\n\t\n\tpublic PropertiesFile parsePropertiesFile(ModelInfo modelInfo, InputStream str) throws PrismLangException\n\t{ return parsePropertiesFile(modelInfo, str, false); }\n\t\n\tpublic PropertiesFile parsePropertiesFile(ModelInfo modelInfo, InputStream str, boolean strict) throws PrismLangException\n\t{\n\t\tPropertiesFile pf = null;\n\t\t\n\t\t// (Re)start parser\n\t\tReInit(str);\n\t\tthis.modelInfo = modelInfo;\n\t\t// Parse\n\t\ttry {\n\t\t\tpf = strict ? PropertiesFile() : PropertiesFileSemicolonless();\n\t\t}\n\t\tcatch (ParseException e) {\n\t\t\tthrow generateSyntaxError(e);\n\t\t}\n\n\t\treturn pf;\n\t}\n\t\n\t// Parse a single expression\n\t\n\tpublic Expression parseSingleExpression(InputStream str) throws PrismLangException\n\t{\n\t\tExpression expr = null;\n\t\t\n\t\t// (Re)start parser\n\t\tReInit(str);\n\t\t// Parse\n\t\ttry {\n\t\t\texpr = SingleExpression();\n\t\t}\n\t\tcatch (ParseException e) {\n\t\t\tthrow generateSyntaxError(e);\n\t\t}\n\t\treturn expr;\n\t}\n\t\n\t// Parse a single LTL formula\n\t\n\tpublic Expression parseSingleLTLFormula(InputStream str) throws PrismLangException\n\t{\n\t\tExpression expr = null;\n\t\t\n\t\t// (Re)start parser\n\t\tReInit(str);\n\t\t// Parse\n\t\ttry {\n\t\t\texpr = SingleLTLFormula();\n\t\t}\n\t\tcatch (ParseException e) {\n\t\t\tthrow generateSyntaxError(e);\n\t\t}\n\t\treturn expr;\n\t}\n\t\n\t// Parse a for loop\n\t\n\tpublic ForLoop parseForLoop(InputStream str) throws PrismLangException\n\t{\n\t\tForLoop fl = null;\n\t\t\n\t\t// (Re)start parser\n\t\tReInit(str);\n\t\t// Parse\n\t\ttry {\n\t\t\tfl = ForLoop();\n\t\t}\n\t\tcatch (ParseException e) {\n\t\t\tthrow generateSyntaxError(e);\n\t\t}\n\t\treturn fl;\n\t}\n\t\n\t//-----------------------------------------------------------------------------------\n\t// Some utility methods\n\t//-----------------------------------------------------------------------------------\n\t\n\t/**\n\t * Get comment block directly preceding a token and remove \"//\" characters\n\t */\n\tpublic static String getPrecedingCommentBlock(Token firstToken)\n\t{\n\t\tString comment = \"\", s;\n\t\tToken t = firstToken;\n\t\t\n\t\t// extract any comment from the previous lines of the file\n\t\tif (t.specialToken != null && !(t.specialToken.kind == PrismParserConstants.WHITESPACE && t.specialToken.image.matches(\"[\\\\n\\\\r]*\"))) {\n\t\t\t// trace back thru special tokens that are comments\n\t\t\tt = t.specialToken;\n\t\t\twhile (t.specialToken != null && !(t.specialToken.kind == PrismParserConstants.WHITESPACE && t.specialToken.image.matches(\"[\\\\n\\\\r]*\")))\n\t\t\t\tt = t.specialToken;\n\t\t\t// concatenate comment special tokens\n\t\t\twhile (t != null) {\n\t\t\t\ts = t.image;\n\t\t\t\t// strip any nasty carriage returns\n\t\t\t\ts = s.replaceAll(\"\\r\", \"\");\n\t\t\t\t// remove \"//\" and preceding/subsequent spaces/tabs from comments\n\t\t\t\tif (t.kind == PrismParserConstants.COMMENT) {\n\t\t\t\t\twhile (comment.length() > 0 && (\"\"+comment.charAt(comment.length()-1)).matches(\"[ \\t]\"))\n\t\t\t\t\t\tcomment = comment.substring(0,comment.length()-1);\n\t\t\t\t\ts = s.substring(2);\n\t\t\t\t\ts = s.replaceFirst(\"[ \\t]*\", \"\");\n\t\t\t\t}\n\t\t\t\tcomment += s;\n\t\t\t\tt = t.next;\n\t\t\t}\n\t\t}\n\t\t// remove final new line (if present)\n\t\tif (comment.length() > 0 && (comment.charAt(comment.length()-1) == '\\n'))\n\t\t\tcomment = comment.substring(0,comment.length()-1);\n\t\t\n\t\treturn comment;\n\t}\n\t\n\t// Add \"//\"s into comment block\n\t\n\tpublic static String slashCommentBlock(String comment)\n\t{\n\t\tint i;\n\t\tString s, res = \"\";\n\t\t// break into lines\n\t\twhile ((i = comment.indexOf(\"\\n\")) != -1) {\n\t\t\ts = comment.substring(0, i);\n\t\t\tcomment = comment.substring(i+1);\n\t\t\t// add \"//\" to non-empty lines\n\t\t\tif (s.trim().length()>0) res += \"// \" + s;\n\t\t\tres += \"\\n\";\n\t\t}\n\t\t// deal with any trailing characters (with no new line ending them)\n\t\tif (comment.trim().length()>0) res += \"// \" + comment + \"\\n\";\n\t\treturn res;\n\t}\n\t\n\t/**\n\t * Test a string to see if it is a PRISM language keyword.\n\t */\n\tpublic static boolean isKeyword(String s)\n\t{\n\t\treturn keywordSet.contains(s);\n\t}\n\t\n\t/**\n\t * Get access to the list of all PRISM language keywords.\n\t */\n\tpublic static List<String> getListOfKeywords()\n\t{\n\t\treturn keywordList;\n\t}\n\t\n\t/**\n\t * Set the tab size used by the lexer/parser.\n\t */\n\tpublic void setTabSize(int size) \n\t{\n\t\tSimpleCharStream.setTabSize(size);   \n\t}\n\t\n\t/**\n\t * Get the tab size used by the lexer/parser.\n\t */\n\tpublic int getTabSize()\n\t{\n\t\treturn SimpleCharStream.getTabSize();\n\t}\n\t\n\t/**\n\t * Generate a syntax error (PrismLangException) from a ParseException.\n\t */\n\tprotected PrismLangException generateSyntaxError(ParseException e)\n\t{\n\t\tif (e == null) return new PrismLangException(\"Syntax error\");\n\t\t// No token: was prob created manually so use message if present\n\t\tif (e.currentToken == null) {\n\t\t\tString msg = e.getMessage();\n\t\t\tString exMsg = \"Syntax error\";\n\t\t\tif (msg != null && msg.length() > 0)\n\t\t\t\texMsg += \": \" + msg;\n\t\t\treturn new PrismLangException(exMsg);\n\t\t}\n\t\t// Use current/next token to find location of error\n\t\t// But don't use error message if too long (esp if generated by JavaCC)\n\t\telse {\n\t\t\tExpressionIdent tmp;\n\t\t\tif (e.currentToken.next == null) {\n\t\t\t\ttmp = new ExpressionIdent(e.currentToken.image);\n\t\t\t\ttmp.setPosition(e.currentToken);\n\t\t\t} else {\n\t\t\t\ttmp = new ExpressionIdent(e.currentToken.next.image);\n\t\t\t\ttmp.setPosition(e.currentToken.next);\n\t\t\t}\n\t\t\tString msg = e.getMessage();\n\t\t\tString exMsg = \"Syntax error\";\n\t\t\tif (msg != null && msg.length() > 0 && msg.length() < 20)\n\t\t\t\texMsg += \": \" + msg;\n\t\t\treturn new PrismLangException(exMsg, tmp);\n\t\t}\n\t}\n\t\n\t//-----------------------------------------------------------------------------------\n\t// A few classes for temporary storage of bits of the AST\n\t//-----------------------------------------------------------------------------------\n\t\n\tstatic class ExpressionPair { public Expression expr1 = null; public Expression expr2 = null; }\n}\n\n//-----------------------------------------------------------------------------------\n\nPARSER_END(PrismParser)\n\n// Token definitions follow\n// Note that PrismSyntaxHighlighter makes assumptions about the ordering of these\n\n// Skip (but store) all other white space\n\nSPECIAL_TOKEN :\n{\n\t<WHITESPACE: (\" \"|\"\\t\"|\"\\n\"|\"\\r\")>\n}\n\n// Skip (but store) comments\n\nSPECIAL_TOKEN :\n{\n\t<COMMENT: \"//\" (~[\"\\n\",\"\\r\"])* (\"\\n\"|\"\\r\"|\"\\r\\n\")?>\n}\n\n// Tokens\n\nTOKEN :\n{\n\t// Keywords\n\t< A:\t\t\t\t\"A\" >\n//|\t< ARRAY:\t\t\t\"array\" >\n|\t< BOOL:\t\t\t\t\"bool\" >\n|\t< CLOCK:\t\t\t\"clock\" >\n|\t< CONST:\t\t\t\"const\" >\n|\t< CTMC:\t\t\t\t\"ctmc\" >\n|\t< C:\t\t\t\t\"C\" >\n|\t< DOUBLE:\t\t\t\"double\" >\n|\t< DTMC:\t\t\t\t\"dtmc\" >\n|\t< E:\t\t\t\t\"E\" >\n|\t< ENDINIT:\t\t\t\"endinit\" >\n|\t< ENDINVARIANT:\t\t\"endinvariant\" >\n|\t< ENDMODULE:\t\t\"endmodule\" >\n|\t< ENDOBSERVABLES:\t\"endobservables\" >\n|\t< ENDREWARDS:\t\t\"endrewards\" >\n|\t< ENDSYSTEM:\t\t\"endsystem\" >\n|\t< FALSE:\t\t\t\"false\" >\n|\t< FORMULA:\t\t\t\"formula\" >\n|\t< FILTER:\t\t\t\"filter\" >\n|\t< FUNC:\t\t\t\t\"func\" >\n|\t< F:\t\t\t\t\"F\" >\n|\t< GLOBAL:\t\t\t\"global\" >\n|\t< G:\t\t\t\t\"G\" >\n|\t< INIT:\t\t\t\t\"init\" >\n|\t< INVARIANT:\t\t\"invariant\" >\n|\t< I:\t\t\t\t\"I\" >\n|\t< INT:\t\t\t\t\"int\" >\n|\t< LABEL:\t\t\t\"label\" >\n|\t< MAXMAX:\t\t\t\"maxmax\" >\n|\t< MAXMIN:\t\t\t\"maxmin\" >\n|\t< MAX:\t\t\t\t\"max\" >\n|\t< MDP:\t\t\t\t\"mdp\" >\n|\t< MINMAX:\t\t\t\"minmax\" >\n|\t< MINMIN:\t\t\t\"minmin\" >\n|\t< MIN:\t\t\t\t\"min\" >\n|\t< MODULE:\t\t\t\"module\" >\n|\t< X:\t\t\t\t\"X\" >\n|\t< NONDETERMINISTIC:\t\"nondeterministic\" >\n|\t< OBSERVABLE:\t\t\"observable\" >\n|\t< OBSERVABLES:\t\t\"observables\" >\n//|\t< OF:\t\t\t\t\"of\" >\n|\t< PMAXMAX:\t\t\t\"Pmaxmax\" >\n|\t< PMAXMIN:\t\t\t\"Pmaxmin\" >\n|\t< PMAX:\t\t\t\t\"Pmax\" >\n|\t< PMINMAX:\t\t\t\"Pminmax\" >\n|\t< PMINMIN:\t\t\t\"Pminmin\" >\n|\t< PMIN:\t\t\t\t\"Pmin\" >\n|\t< P:\t\t\t\t\"P\" >\n|\t< POMDP:\t\t\t\"pomdp\" >\n|\t< POPTA:\t\t\t\"popta\" >\n|\t< PROBABILISTIC:\t\"probabilistic\" >\n|\t< PROB:\t\t\t\t\"prob\" >\n|\t< PTA:\t\t\t\t\"pta\" >\n|\t< RATE:\t\t\t\t\"rate\" >\n|\t< REWARDS:\t\t\t\"rewards\" >\n|\t< RMAXMAX:\t\t\t\"Rmaxmax\" >\n|\t< RMAXMIN:\t\t\t\"Rmaxmin\" >\n|\t< RMAX:\t\t\t\t\"Rmax\" >\n|\t< RMINMAX:\t\t\t\"Rminmax\" >\n|\t< RMINMIN:\t\t\t\"Rminmin\" >\n|\t< RMIN:\t\t\t\t\"Rmin\" >\n|\t< R:\t\t\t\t\"R\" >\n|\t< S:\t\t\t\t\"S\" >\n|\t< STOCHASTIC:\t\t\"stochastic\" >\n|\t< SYSTEM:\t\t\t\"system\" >\n|\t< TRUE:\t\t\t\t\"true\" >\n|\t< U:\t\t\t\t\"U\" >\n|\t< W:\t\t\t\t\"W\" >\n\t// Punctuation, etc.\n\t// Note that \"NOT\" must be the first item of punctuation in this list\n\t// (PrismSyntaxHighlighter relies on this fact)\n|\t< NOT:\t\t\t\"!\" >\n|\t< AND:\t\t\t\"&\" >\n|\t< OR:\t\t\t\"|\" >\n|\t< IMPLIES:\t\t\"=>\" >\n|\t< IFF:\t\t\t\"<=>\" >\n|\t< RARROW:\t\t\"->\" >\n|\t< COLON:\t\t\":\" >\n|\t< SEMICOLON:\t\";\" >\n|\t< COMMA:\t\t\",\" >\n|\t< DOTS:\t\t\t\"..\" >\n|\t< LPARENTH:\t\t\"(\" >\n|\t< RPARENTH:\t\t\")\" >\n|\t< LBRACKET: \t\"[\" >\n|\t< RBRACKET:\t\t\"]\" >\n|\t< DLBRACKET: \t\"[[\" >\n|\t< DRBRACKET:\t\"]]\" >\n|\t< LBRACE:\t\t\"{\" >\n|\t< RBRACE:\t\t\"}\" >\n|\t< EQ:\t\t\t\"=\" >\n|\t< NE:\t\t\t\"!=\" >\n|\t< LT:\t\t\t\"<\" >\n|\t< GT:\t\t\t\">\" >\n|\t< DLT:\t\t\t\"<<\" >\n|\t< DGT:\t\t\t\">>\" >\n|\t< LE:\t\t\t\"<=\" >\n|\t< GE:\t\t\t\">=\" >\n|\t< PLUS:\t\t\t\"+\" >\n|\t< MINUS:\t\t\"-\" >\n|\t< TIMES:\t\t\"*\" >\n|\t< DIVIDE:\t\t\"/\" >\n|\t< POWER:\t\t\"^\" >\n|\t< PRIME:\t\t\"'\" >\n|\t< RENAME:\t\t\"<-\" >\n|\t< QMARK:\t\t\"?\" >\n|\t< DQUOTE:\t\t\"\\\"\" >\n\t// Regular expressions\n|\t< REG_INT:\t\t\t([\"1\"-\"9\"]([\"0\"-\"9\"])*)|(\"0\") >\n|\t< REG_DOUBLE:\t\t([\"0\"-\"9\"])*(\".\")?([\"0\"-\"9\"])+([\"e\",\"E\"]([\"-\",\"+\"])?([\"0\"-\"9\"])+)? >\n|\t< REG_IDENTPRIME:\t[\"_\",\"a\"-\"z\",\"A\"-\"Z\"]([\"_\",\"a\"-\"z\",\"A\"-\"Z\",\"0\"-\"9\"])*\"'\" >\n|\t< REG_IDENT:\t\t[\"_\",\"a\"-\"z\",\"A\"-\"Z\"]([\"_\",\"a\"-\"z\",\"A\"-\"Z\",\"0\"-\"9\"])* >\n|\t< PREPROC:\t\t\t\"#\"(~[\"#\"])*\"#\" >\n\t// Special catch-all token for lexical errors\n\t// (this allows us to throw our usual exceptions in this case)\n|\t< LEXICAL_ERROR: ~[] >\n}\n\n//-----------------------------------------------------------------------------------\n// Top-level productions\n//-----------------------------------------------------------------------------------\n\n// Modules file\n\nModulesFile ModulesFile() throws PrismLangException :\n{\n\tModelType type = null;\n\tint typeCount = 0;\n\tToken typeDupe = null;\n\tDeclaration global;\n\tparser.ast.Module m = null;\n\tRenamedModule rm = null;\n\tRewardStruct rs = null;\n\tExpression init = null;\n\tObservableVars obsVars = null;\n\tObservable obs = null;\n\tint initCount = 0;\n\tExpression initDupe = null;\n\tModulesFile mf = new ModulesFile();\n\tToken begin = null;\n}\n{\n\t( { begin = getToken(1); }\n\t// Model type\n\t( type=ModulesFileType() { typeCount++; if (typeCount == 2) typeDupe = getToken(0); } ) |\n\t// Formula/label/constant definition\n\tFormulaDef(mf.getFormulaList()) | LabelDef(mf.getLabelList()) | ConstantDef(mf.getConstantList()) |\n\t// Global variable\n\tglobal = GlobalDecl() { mf.addGlobal(global); } |\n\t// Renamed module (lookahead to distinguish from normal module)\n\tLOOKAHEAD(<MODULE> Identifier() <EQ>) rm = RenamedModule() { mf.addRenamedModule(rm); } |\n\t// Module\n\tm = Module() { mf.addModule(m); } | \n\t// Reward structure\n\trs = RewardStruct() { mf.addRewardStruct(rs); } |\n\t// Initial states (\"init...endinit\" construct)\n\tinit = Init() { mf.setInitialStates(init); initCount++; if (initCount == 2) initDupe = init; } |\n\t// Observables\n\tobsVars = ObservableVars() { mf.addObservableVarList(obsVars); } |\n\tobs = Observable() {mf.addObservableDefinition(obs); } |\n\t// System definition (\"system...endsystem\" construct)\n\tSystemEndsystem(mf)\n\t)* <EOF>\n\t{\n\t\t// Check for multiple instances of some items\n\t\tif (typeDupe != null) {\n\t\t\tExpressionIdent tmp = new ExpressionIdent(typeDupe.image);\n\t\t\ttmp.setPosition(typeDupe);\n\t\t\tthrow new PrismLangException(\"There were multiple model type declarations\", tmp);\n\t\t}\n\t\tif (initDupe != null) {\n\t\t\tthrow new PrismLangException(\"There were multiple init...endinit constructs\", initDupe);\n\t\t}\n\t\t\n\t\t// Set model type (might be null, i.e., unspecified)\n\t\tmf.setModelTypeInFile(type);\n\t\t\n\t\t// Return completed ModulesFile object\n\t\tmf.setPosition(begin != null? begin: getToken(0), getToken(0));\n\t\treturn mf;\n\t}\n}\n\n// Properties file\n\nPropertiesFile PropertiesFile() throws PrismLangException :\n{\n\tPropertiesFile pf = new PropertiesFile(modelInfo);\n\tProperty prop;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); }\n\t(\n\t\t// Semi-colon terminated property\n\t\t( prop = Property() { pf.addProperty(prop); } (<SEMICOLON>)+ )\n\t|\n\t\t// Label/constant definition\n\t\t( LabelDef(pf.getLabelList()) ) | ( ConstantDef(pf.getConstantList()) )\n\t)* <EOF>\n\t{ pf.setPosition(begin, getToken(0)); return pf; }\n}\n\n// Properties file with optional semicolons - beware of potential ambiguities\n\nPropertiesFile PropertiesFileSemicolonless() throws PrismLangException :\n{\n\tPropertiesFile pf = new PropertiesFile(modelInfo);\n\tProperty prop;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); }\n\t(\n\t\t// Semi-colon terminated property\n\t\t( prop = Property() (<SEMICOLON>)* { pf.addProperty(prop); } )\n\t|\n\t\t// Label/constant definition\n\t\t( LabelDef(pf.getLabelList()) ) | ( ConstantDef(pf.getConstantList()) )\n\t)* <EOF>\n\t{ pf.setPosition(begin, getToken(0)); return pf; }\n}\n\n// Property - expression, with optional name/comment\n\nProperty Property() :\n{\n\tString name = null;\n\tExpression expr;\n\tProperty prop;\n\tToken begin = null;\n}\n{\n\t// Note that we jump in a few levels down in the Expression hierarchy\n\t// (more precisely, we skip the temporal operators, which can't occur at the top-level)\n\t// (this avoids some common parsing errors for semicolon-less files)\n\t// Note also use of lookahead (to colon) to distinguish (optional) name from label reference\n\t( { begin = getToken(1); }\n\t( LOOKAHEAD(<DQUOTE> Identifier() <DQUOTE> <COLON>) <DQUOTE> name = Identifier() <DQUOTE> <COLON> )?\n\texpr = ExpressionITE(true, false)\n\t{ prop = new Property(expr, name, getPrecedingCommentBlock(begin)); }\n\t)\n\t{ prop.setPosition(begin, getToken(0)); return prop; }\n}\n\n// A single expression\n\nExpression SingleExpression() :\n{\n\tExpression ret;\n}\n{\n\t( ret = Expression(false, false) <EOF> ) { return ret; }\n}\n\n// A single LTL formula\n\nExpression SingleLTLFormula() :\n{\n\tExpression ret;\n}\n{\n\t( ret = Expression(true, true) <EOF> ) { return ret; }\n}\n\n//-----------------------------------------------------------------------------------\n// Modules file stuff (a few bits of which are reused for property files)\n//-----------------------------------------------------------------------------------\n\n// Keyword denoting model type\n\nModelType ModulesFileType() :\n{\n\tModelType modelType = null;\n}\n{\n\t( (<DTMC>|<PROBABILISTIC>) { modelType=ModelType.DTMC; }\n\t| (<MDP>|<NONDETERMINISTIC>) { modelType=ModelType.MDP; }\n\t| (<CTMC>|<STOCHASTIC>) { modelType=ModelType.CTMC; }\n\t| <PTA> { modelType=ModelType.PTA; }\n\t| <POMDP> { modelType=ModelType.POMDP; }\n\t| <POPTA> { modelType=ModelType.POPTA; }\n\t)\n\t{ return modelType; }\n}\n\n// Formula definition\n\nvoid FormulaDef(FormulaList formulaList) :\n{\n\tExpressionIdent name = null;\n\tExpression expr = null;\n}\n{\n\t( <FORMULA> name = IdentifierExpression() <EQ> expr = Expression(false, false) <SEMICOLON> )\n\t{ formulaList.addFormula(name, expr); }\n}\n\n// Label definition\n\nvoid LabelDef(LabelList labelList) throws PrismLangException :\n{\n\tExpressionIdent name = null;\n\tExpression expr = null;\n}\n{\n\t// Lookahead required because of the error handling clause below\n\tLOOKAHEAD(<LABEL> <DQUOTE>) <LABEL> ( <DQUOTE> name = IdentifierExpression() <DQUOTE> <EQ> expr = Expression(false, false) <SEMICOLON> )\n\t{ labelList.addLabel(name, expr); }\n\t// Error handling\n\t| LOOKAHEAD(<LABEL>) ( <LABEL> name = IdentifierExpression() ) { throw new PrismLangException(\"Label names must be enclosed in double-quotes\", name); }\n}\n\n// Constant definition\n\nvoid ConstantDef(ConstantList constantList) :\n{\n\tType type = TypeInt.getInstance();\n\tExpressionIdent name = null;\n\tExpression expr = null;\n}\n{\n\t// Constant (allow omission of \"int\" and use of \"rate\"/\"prob\" for backwards compatability)\n\t(( <CONST> ( <INT> { type=TypeInt.getInstance(); } | <DOUBLE> { type=TypeDouble.getInstance(); } | <BOOL> { type=TypeBool.getInstance(); } )? )\n\t| (<RATE> | <PROB> ) { type=TypeDouble.getInstance(); } )\n\t// Name and (optional) initial value\n\tname = IdentifierExpression()\n\t( <EQ> expr = Expression(false, false) )? <SEMICOLON>\n\t{ constantList.addConstant(name, expr, type); }\n}\n\n// Global variable declaration\n\nDeclaration GlobalDecl() :\n{\n\tDeclaration decl = null;\n}\n{\n\t( <GLOBAL> decl = Declaration() )\n\t{ return decl; }\n}\n\n// Variable declaration\n\nDeclaration Declaration() :\n{\n\tDeclaration decl;\n\tString name = null;\n\tDeclarationType declType;\n\tExpression init = null;\n\tToken begin = null;\n}\n{\n\t// Name, colon, type\n\t( { begin = getToken(1); } name = Identifier() <COLON> declType = DeclarationVarType()\n\t\t{ decl = new Declaration(name, declType); }\n\t// Optional inital value\n\t( <INIT> init = Expression(false, false)\n\t{ decl.setStart(init); } )?\n\t// Terminating ;\n\t<SEMICOLON> )\n\t{ decl.setPosition(begin, getToken(0)); return decl; }\n}\n\n// Type part of a declaration\n\nDeclarationType DeclarationVarType() :\n{\n\tExpression low = null, high = null;\n\tDeclarationType declType, subtype;\n\tToken begin = null;\n}\n{\n\t( { begin = getToken(1); } (\n\t// Integer-range declaration\n\t( <LBRACKET> low = Expression(false, false) <DOTS> high = Expression(false, false) <RBRACKET>\n\t\t{ declType = new DeclarationInt(low, high); } )\n\t// Integer (unbounded) declaration\n\t| ( <INT> { declType = new DeclarationIntUnbounded(); } )\n\t// Boolean variable declaration\n\t| ( <BOOL> { declType = new DeclarationBool(); } )\n\t// Array variable declaration\n\t/* | ( <ARRAY> <LBRACKET> low = Expression(false, false) <DOTS> high = Expression(false, false) <RBRACKET> \n\t\t<OF> subtype = DeclarationVarType()\n\t\t{ declType = new DeclarationArray(low, high, subtype); } )\n\t\t// TODO: sort initial values */\n\t| ( <CLOCK> { declType = new DeclarationClock(); } )\n\t))\n\t{ declType.setPosition(begin, getToken(0)); return declType; }\n}\n\n// Module\n\nparser.ast.Module Module() :\n{\n\tExpressionIdent name = null;\n\tDeclaration var = null;\n\tExpression invar;\n\tCommand comm = null;\n\tparser.ast.Module module = null;\n\tToken begin = null;\n}\n{\n\tbegin = <MODULE> name = IdentifierExpression() { module = new parser.ast.Module(name.getName()); }\n\t( var = Declaration() { module.addDeclaration(var); } )*\n\t( <INVARIANT> invar = Expression(false, false) <ENDINVARIANT> { module.setInvariant(invar); } )?\n\t( comm = Command() { module.addCommand(comm); } )*\n\t<ENDMODULE>\n\t{ module.setPosition(begin, getToken(0)); module.setNameASTElement(name); return module; }\n}\n\n// Command\n\nCommand Command() :\n{\n\tString synch = null;\n\tExpression guard = null;\n\tUpdates updates = null;\n\tCommand comm = new Command();\n\tToken begin = null;\n}\n{\n\t// Synchronisation action-label\n\tbegin = <LBRACKET> ( synch = Identifier() { comm.setSynch(synch); } )? <RBRACKET>\n\t// Guard/updates\n\tguard = Expression(false, false) { comm.setGuard(guard); } <RARROW> updates = Updates() { comm.setUpdates(updates); } <SEMICOLON>\n\t{ comm.setPosition(begin, getToken(0)); return comm; }\n}\n\n// Updates\n\nUpdates Updates() :\n{\n\tExpression prob;\n\tUpdate update;\n\tUpdates updates = new Updates();\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); }\n\t(\n\t\t// Single update with probability 1\n\t\t// (lookahead required because update and probability can both start with \"(\")\n\t\tLOOKAHEAD(Update()) update = Update()\n\t\t{ updates.addUpdate(null, update); }\n\t|\n\t\t// Several probabilistic updates\n\t\t( prob = ProbOrRateOrInterval() <COLON> update = Update() { updates.addUpdate(prob, update); }\n\t\t( <PLUS> prob = ProbOrRateOrInterval() <COLON> update = Update() { updates.addUpdate(prob, update); } )* )\n\t)\n\t{ updates.setPosition(begin, getToken(0)); return updates; }\n}\n\nExpression ProbOrRateOrInterval() :\n{\n\tExpression prob;\n}\n{\n\t( prob = Expression(false, false) | prob = ExpressionInterval(false, false) )\n\t{ return prob; }\n}\n\nUpdate Update() :\n{\n\tUpdate update = new Update();\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); }\n\t// Conjunction of update elements\n\t(( UpdateElement(update) ( <AND> UpdateElement(update) )* )\n\t// Empty conjunction: true\n\t| <TRUE> )\n\t{ update.setPosition(begin, getToken(0)); return update; }\n}\n\nvoid UpdateElement(Update update) :\n{\n\tExpressionIdent var = null;\n\tExpression expr = null;\n\tToken begin = null;\n}\n{\n\tbegin = <LPARENTH> var = IdentifierPrime() <EQ> expr = Expression(false, false) <RPARENTH>\n\t{ UpdateElement ue = new UpdateElement(var, expr); ue.setPosition(begin, getToken(0)); update.addElement(ue); }\n}\n\n// Module renaming\n\nRenamedModule RenamedModule() :\n{\n\tExpressionIdent name = null, base = null;\n\tRenamedModule rm = null;\n\tToken begin = null;\n}\n{\n\tbegin = <MODULE> name = IdentifierExpression() <EQ> base = IdentifierExpression() { rm = new RenamedModule(name.getName(), base.getName()); }\n\t<LBRACKET> Rename(rm) ( <COMMA> Rename(rm) )* <RBRACKET> <ENDMODULE>\n\t{ rm.setPosition(begin, getToken(0)); rm.setNameASTElement(name); rm.setBaseModuleASTElement(base); return rm; }\n}\n\nvoid Rename(RenamedModule rm) :\n{\n\tExpressionIdent id1 = null, id2 = null;\n}\n{\n\t// NB: have to explicitly include keywords for functions because they can be renamed\n\tid1=IdentifierExpressionMinMax()\n\t<EQ>\n\tid2=IdentifierExpressionMinMax()\n\t{\n\t\trm.addRename(id1.getName(), id2.getName(), id1, id2);\n\t}\n}\n\n// Reward structure\n\nRewardStruct RewardStruct() :\n{\n\tString name = null, s = null;\n\tExpression guard = null, value = null;\n\tRewardStruct rs = new RewardStruct();\n\tRewardStructItem rsi;\n\tToken begin = null, begin2 = null;\n}\n{\n\tbegin = <REWARDS>\n\t// Optional name\n\t// (lookahead required so not misdetected as an ExpressionLabel)\n\t// (which would not be allowed to appear here anyway)\n\t( LOOKAHEAD(<DQUOTE>) <DQUOTE> name = Identifier() <DQUOTE> { rs.setName(name); } )?\n\t// Reward structure items\n\t( { begin2 = getToken(1); s = null; } ( <LBRACKET> { s = \"\"; } ( s=Identifier() )? <RBRACKET> )?\n\tguard = Expression(false, false) <COLON> value = Expression(false, false) <SEMICOLON>\n\t{ rsi = new RewardStructItem(s, guard, value); rsi.setPosition(begin2, getToken(0)); rs.addItem(rsi); } )*\n\t<ENDREWARDS>\n\t{ rs.setPosition(begin, getToken(0)); return rs; }\n}\n\t\n// Initial states (\"init...endinit\" construct)\n\nExpression Init() :\n{\n\tExpression expr = null;\n}\n{\n\t<INIT> expr = Expression(false, false) <ENDINIT> { return expr; }\n}\n\n// Observable variables list (for partially observable models)\n\nObservableVars ObservableVars() :\n{\n\tToken begin = null;\n\tObservableVars obsVars = null;\n\tExpression exprVar = null;\n}\n{\n\t{ begin = getToken(1); }\n\t<OBSERVABLES> { obsVars = new ObservableVars(); }\n\texprVar = IdentifierExpression() { obsVars.addVar(exprVar); }\n\t( <COMMA> exprVar = IdentifierExpression() { obsVars.addVar(exprVar); } )*\n\t<ENDOBSERVABLES>\n\t{ obsVars.setPosition(begin, getToken(0)); return obsVars; }\t\n}\n\n// Individual observable (for partially observable models)\n\nObservable Observable() :\n{\n\tToken begin = null;\n\tString name = null;\n\tExpression defn = null;\n}\n{\n\t{ begin = getToken(1); }\n\t( <OBSERVABLE> <DQUOTE> name = Identifier() <DQUOTE> <EQ> defn = Expression(false, false) <SEMICOLON> )\n\t{ Observable obs = new Observable(name, defn); obs.setPosition(begin, getToken(0)); return obs; }\n}\n\n// System definition (\"system...endsystem\" construct)\n\nvoid SystemEndsystem(ModulesFile mf) :\n{\n\tString name = null;\n\tSystemDefn sysdef;\n}\n{\n\t<SYSTEM>\n\t// Optional name\n\t// (need lookahead because names look like references)\n\t( LOOKAHEAD(<DQUOTE> name = Identifier() <DQUOTE> SystemDefn()) <DQUOTE> name = Identifier() <DQUOTE> )?\n\t// The rest\n\t( sysdef = SystemDefn() )\n\t<ENDSYSTEM>\n\t{\n\t\tmf.addSystemDefn(sysdef, name);\n\t}\n}\n\n// System definition component\n\nSystemDefn SystemDefn() :\n{\n\tSystemDefn ret;\n}\n{\n\tret = SystemFullParallel()\n\t{ return ret; }\n}\n\n// System definition component (full parallel)\n\nSystemDefn SystemFullParallel() :\n{\n\tSystemDefn sys1 = null, sys2 = null;\n\tSystemFullParallel par = null;\n\tToken begin;\n}\n{\n\t{ begin = getToken(1); }\n\tsys1 = SystemInterleaved()\n\t( { par = new SystemFullParallel(); par.addOperand(sys1); } ( LOOKAHEAD(<OR> <OR>) <OR> <OR> sys2 = SystemParallel() { par.addOperand(sys2); } )* )\n\t{\n\t\tif (par==null || par.getNumOperands() == 1) {\n\t\t\treturn sys1;\n\t\t}\n\t\telse {\n\t\t\tpar.setPosition(begin, getToken(0));\n\t\t\treturn par;\n\t\t}\n\t}\n}\n\n// System definition component (interleaved parallel)\n\nSystemDefn SystemInterleaved() :\n{\n\tSystemDefn sys1 = null, sys2 = null;\n\tSystemInterleaved par = null;\n\tToken begin;\n}\n{\n\t{ begin = getToken(1); }\n\tsys1 = SystemParallel()\n\t( { par = new SystemInterleaved(); par.addOperand(sys1); } ( LOOKAHEAD(<OR> <OR> <OR>) <OR> <OR> <OR>  sys2 = SystemFullParallel() { par.addOperand(sys2); } )* )\n\t{\n\t\tif (par==null || par.getNumOperands() == 1) {\n\t\t\treturn sys1;\n\t\t}\n\t\telse {\n\t\t\tpar.setPosition(begin, getToken(0));\n\t\t\treturn par;\n\t\t}\n\t}\n}\n\n// System definition component (parallel over set of actions)\n\nSystemDefn SystemParallel() :\n{\n\tSystemDefn sys1 = null, sys2 = null;\n\tSystemParallel par = null;\n\tString s;\n\tToken begin;\n}\n{\n\t{ begin = getToken(1); }\n\tsys1 = SystemHideRename()\n\t( LOOKAHEAD(<OR> <LBRACKET>) { par = new SystemParallel(); par.setOperand1(sys1); } <OR> \n\t  <LBRACKET> ( s = Identifier() { par.addAction(s); } ( <COMMA> s = Identifier() { par.addAction(s); } )* ) <RBRACKET>\n\t  <OR> sys2 = SystemHideRename() { par.setOperand2(sys2); }\n\t)?\n\t{\n\t\tif (par==null) {\n\t\t\treturn sys1;\n\t\t}\n\t\telse {\n\t\t\tpar.setPosition(begin, getToken(0));\n\t\t\treturn par;\n\t\t}\n\t}\n}\n\n// System definition component (hiding and renaming)\n\nSystemDefn SystemHideRename() :\n{\n\tSystemDefn sys = null;\n\tSystemHide hide = null;\n\tSystemRename rename = null;\n\tString s1 = null, s2 = null;\n\tToken begin;\n}\n{\n\t{ begin = getToken(1); }\n\t( sys = SystemAtomic() (\n\t// Hiding\n\t(\n\t\t{ hide = new SystemHide(sys); }\n\t\t<DIVIDE> <LBRACE> ( s1 = Identifier() { hide.addAction(s1); } ( <COMMA> s1 = Identifier() { hide.addAction(s1); } )* ) <RBRACE>\n\t\t{ sys = hide; }\n\t)\n\t// Renaming\n\t| (\n\t\t{ rename = new SystemRename(sys); }\n\t\t<LBRACE> s1 = Identifier() <RENAME> s2 = Identifier() { rename.addRename(s1, s2); }\n\t\t( <COMMA> s1 = Identifier() <RENAME> s2 = Identifier() { rename.addRename(s1, s2); } )* <RBRACE>\n\t\t{ sys = rename; }\n\t)\n\t)* )\n\t{ sys.setPosition(begin, getToken(0)); return sys; }\n}\n\n// System definition component (bottom level)\n\nSystemDefn SystemAtomic() :\n{\n\tString name = null;\n\tSystemDefn sys = null;\n\tToken begin;\n}\n{\n\t{ begin = getToken(1); }\n\t(\n\t// Module name\n\t( name = Identifier() { sys = new SystemModule(name); } )\n\t// SystemDefn reference\n\t|( <DQUOTE> name = Identifier() <DQUOTE> { sys = new SystemReference(name); } )\n\t// Parentheses\n\t|( <LPARENTH> sys = SystemDefn() <RPARENTH> { sys = new SystemBrackets(sys); } )\n\t)\n\t{ sys.setPosition(begin, getToken(0)); return sys; }\n}\n\n//-----------------------------------------------------------------------------------\n// Expressions.\n// This includes PRISM properties (if the \"prop\" parameter is true)\n// and (within this) path formulas (if the \"pathprop\" parameter is true).\n// Which allows us to use the same productions for the grammars for\n// all three cases (they are very similar).\n//-----------------------------------------------------------------------------------\n\n// Expression\n\nExpression Expression(boolean prop, boolean pathprop) :\n{\n\tExpression ret;\n}\n{\n\tret = ExpressionTemporalBinary(prop, pathprop)\n\t{ return ret; }\n}\n\n// Expression: temporal operators, binary (U, W, R) and unary (X, F, G)\n\n// Note: the potential occurrence of two successive (unseparated) expressions\n// (e.g. \"a\" and \"b\" in \"F<=a b\") is a grammar flaw because the function and\n// minus operators can cause ambiguities, for example:\n// \"F<=a(b)+c(d)\" = \"F<=a\" \"(b)+c(d)\" = \"F<=a(b)+c\" \"(d)\" ?\n// \"F<=-a-b-c\" = \"F<=-a\" \"-b-c\" = \"F<=-a-b\" \"-c\" ?\n// In many cases, these could be distinguished by type checking but\n// that does not really help since this is done post-parsing.\n// To prevent (very common) cases such as \"F<=t (b)\", \"F<=t (b)&(c)\", etc.\n// being mis-parsed (\"t(b)\" would always be taken over \"t\"), we catch this case\n// separately (see TimeBound() production below for details).\n// This means that more complex time-bounds, especially those that\n// start/end with an identifier should be parenthesised, e.g. \"F<=(t1+t2)\".\n\n// In fact, JavaCC also warns about lookahead for this function.\n// This is because (like unary minus), R can appear on the left of a unary\n// operator (reward R operator) or in the middle of a binary operator (release).\n\nExpression ExpressionTemporalBinary(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tExpressionTemporal exprTemp;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionTemporalUnary(prop, pathprop)\n\t[\n\t\t// This production is only allowed in expressions if the \"pathprop\" parameter is true\n\t\t{ if (!pathprop) throw generateParseException(); }\n\t\t{ exprTemp = new ExpressionTemporal(); exprTemp.setOperand1(ret); }\n\t\t( <U> { exprTemp.setOperator(ExpressionTemporal.P_U); }\n\t\t| <W> { exprTemp.setOperator(ExpressionTemporal.P_W); }\n\t\t| <R> { exprTemp.setOperator(ExpressionTemporal.P_R); } )\n\t\t( TimeBound(exprTemp) )?\n\t\texpr = ExpressionTemporalUnary(prop, pathprop)\n\t\t{ exprTemp.setOperand2(expr); exprTemp.setPosition(begin, getToken(0)); ret = exprTemp; }\n\t]\n\t{ return ret; }\n}\n\nExpression ExpressionTemporalUnary(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tExpressionTemporal exprTemp;\n\tToken begin = null;\n}\n{\n\t(\n\t\t// This production is only allowed in expressions if the \"pathprop\" parameter is true\n\t\t{ if (!pathprop) throw generateParseException(); }\n\t\t{ begin = getToken(1); exprTemp = new ExpressionTemporal(); }\n\t\t( <X> { exprTemp.setOperator(ExpressionTemporal.P_X); }\n\t\t| <F> { exprTemp.setOperator(ExpressionTemporal.P_F); }\n\t\t| <G> { exprTemp.setOperator(ExpressionTemporal.P_G); } )\n\t\t( TimeBound(exprTemp) )?\n\t\texpr = ExpressionTemporalUnary(prop, pathprop)\n\t\t{ exprTemp.setOperand2(expr); exprTemp.setPosition(begin, getToken(0)); ret = exprTemp; }\n\t|\n\t\tret = ExpressionITE(prop, pathprop)\n\t)\n\t{ return ret; }\n}\n\n// Time bound for temporal operators\n// (see ExpressionTemporal production for lookahead explanation)\n\nvoid TimeBound(ExpressionTemporal exprTemp) :\n{\n\tExpression lBound, uBound;\n}\n{\n\t( ( <LE> ( LOOKAHEAD(IdentifierExpression() <LPARENTH>) uBound = IdentifierExpression() | uBound = Expression(false, false) ) { exprTemp.setUpperBound(uBound, false); } )\n\t| ( <LT> ( LOOKAHEAD(IdentifierExpression() <LPARENTH>) uBound = IdentifierExpression() | uBound = Expression(false, false) ) { exprTemp.setUpperBound(uBound, true); } )\n\t| ( <GE> ( LOOKAHEAD(IdentifierExpression() <LPARENTH>) lBound = IdentifierExpression() | lBound = Expression(false, false) ) { exprTemp.setLowerBound(lBound, false); } )\n\t| ( <GT> ( LOOKAHEAD(IdentifierExpression() <LPARENTH>) lBound = IdentifierExpression() | lBound = Expression(false, false) ) { exprTemp.setLowerBound(lBound, true); } )\n\t| ( <LBRACKET> lBound = Expression(false, false) <COMMA> uBound = Expression(false, false) <RBRACKET> { exprTemp.setLowerBound(lBound, false); exprTemp.setUpperBound(uBound, false); } )\n\t| ( <EQ> lBound = Expression(false, false) { exprTemp.setEqualBounds(lBound); } )\n\t)\n}\n\n// Expression: if-then-else, i.e. \"cond ? then : else\"\n\nExpression ExpressionITE(boolean prop, boolean pathprop) :\n{\n\tExpression ret, left, right;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionImplies(prop, pathprop) \n\t[\n\t\t<QMARK> left = ExpressionImplies(prop, pathprop) <COLON> right = ExpressionITE(prop, pathprop)\n\t\t{ ret = new ExpressionITE(ret, left, right); ret.setPosition(begin, getToken(0)); }\n\t]\n\t{ return ret; }\n}\n\n// Expression: implies\n\nExpression ExpressionImplies(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionIff(prop, pathprop)\n\t( <IMPLIES> expr = ExpressionImplies(prop, pathprop) { ret = new ExpressionBinaryOp(ExpressionBinaryOp.IMPLIES, ret, expr); ret.setPosition(begin, getToken(0)); } )?\n\t{ return ret; }\n}\n\n// Expression: if-and-only-iff\n\nExpression ExpressionIff(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionOr(prop, pathprop)\n\t( <IFF> expr = ExpressionOr(prop, pathprop) { ret = new ExpressionBinaryOp(ExpressionBinaryOp.IFF, ret, expr); ret.setPosition(begin, getToken(0)); } )*\n\t{ return ret; }\n}\n\n// Expression: or\n\nExpression ExpressionOr(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionAnd(prop, pathprop)\n\t( <OR> expr = ExpressionAnd(prop, pathprop) { ret = new ExpressionBinaryOp(ExpressionBinaryOp.OR, ret, expr); ret.setPosition(begin, getToken(0)); } )*\n\t{ return ret; }\n}\n\n// Expression: and\n\nExpression ExpressionAnd(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionNot(prop, pathprop)\n\t( <AND> expr = ExpressionNot(prop, pathprop) { ret = new ExpressionBinaryOp(ExpressionBinaryOp.AND, ret, expr); ret.setPosition(begin, getToken(0)); } )*\n\t{ return ret; }\n}\n\n// Expression: not\n\nExpression ExpressionNot(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tToken begin = null;\n}\n{\n\t(\n\t\tbegin = <NOT> expr = ExpressionNot(prop, pathprop) { ret = new ExpressionUnaryOp(ExpressionUnaryOp.NOT, expr); ret.setPosition(begin, getToken(0)); }\n\t|\n\t\tret = ExpressionEquality(prop, pathprop)\n\t)\n\t{ return ret; }\n}\n\n// Expression: equality operators: =, !=\n\nExpression ExpressionEquality(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tint op;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionRelop(prop, pathprop)\n\t( op = EqNeq() expr = ExpressionRelop(prop, pathprop) { ret = new ExpressionBinaryOp(op, ret, expr); ret.setPosition(begin, getToken(0)); } )*\n\t{ return ret; }\n}\n\n// Expression: relational operators: >, <, >=, <=\n\nExpression ExpressionRelop(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tint op;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionPlusMinus(prop, pathprop)\n\t( op = LtGt() expr = ExpressionPlusMinus(prop, pathprop) { ret = new ExpressionBinaryOp(op, ret, expr); ret.setPosition(begin, getToken(0)); } )*\n\t{ return ret; }\n}\n\n// Expression: plus/minus\n\n// JavaCC warns about lookahead for this function. This is because in a few places\n// (bounded temporal operators and semicolon-less properties files)\n// (see the relevant productions for details)\n// we allow two or more successive expressions resulting in potential ambiguities\n// e.g. \"-a-b\" = \"(-a)-b\" = \"-a\" \"-b\"\n// Ignoring the warning results in the largest match being taken.\n\nExpression ExpressionPlusMinus(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tint op;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionTimesDivide(prop, pathprop) \n\t(\n\t\t( <PLUS> { op = ExpressionBinaryOp.PLUS; } | <MINUS> { op = ExpressionBinaryOp.MINUS; } )\n\t\texpr = ExpressionTimesDivide(prop, pathprop) { ret = new ExpressionBinaryOp(op, ret, expr); ret.setPosition(begin, getToken(0)); }\n\t)*\n\t{ return ret; }\n}\n\n// Expression: times/divide\n\nExpression ExpressionTimesDivide(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tint op;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionPower(prop, pathprop)\n\t(\n\t\t( <TIMES> { op = ExpressionBinaryOp.TIMES; } | <DIVIDE> { op = ExpressionBinaryOp.DIVIDE; } )\n\t\texpr = ExpressionPower(prop, pathprop) { ret = new ExpressionBinaryOp(op, ret, expr); ret.setPosition(begin, getToken(0)); }\n\t)*\n\t{ return ret; }\n}\n\n// Expression: power (^)\n\nExpression ExpressionPower(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tint op;\n\tToken begin = null;\n}\n{\n\t{ begin = getToken(1); } ret = ExpressionUnaryMinus(prop, pathprop)\n\t(\n\t\t<POWER> expr = ExpressionPower(prop, pathprop) { ret = new ExpressionBinaryOp(ExpressionBinaryOp.POW, ret, expr); ret.setPosition(begin, getToken(0)); }\n\t)?\n\t{ return ret; }\n}\n\n// Expression: unary minus\n\nExpression ExpressionUnaryMinus(boolean prop, boolean pathprop) :\n{\n\tExpression ret, expr;\n\tToken begin = null;\n}\n{\n\t(\n\t\tbegin = <MINUS> expr = ExpressionUnaryMinus(prop, pathprop)\n\t\t{ ret = new ExpressionUnaryOp(ExpressionUnaryOp.MINUS, expr); ret.setPosition(begin, getToken(0)); }\n\t|\n\t\tret = ExpressionBasic(prop, pathprop)\n\t)\n\t{ return ret; }\n}\n\n// Basic expression (top of operator precedence ordering)\n\nExpression ExpressionBasic(boolean prop, boolean pathprop) :\n{\n\tExpression ret;\n}\n{\n\t(\n\t\tret = ExpressionLiteral(prop, pathprop)\n\t|\n\t\tret = ExpressionFuncOrIdent(prop, pathprop)\n\t|\n\t\tret = ExpressionFuncMinMax(prop, pathprop)\n\t|\n\t\tret = ExpressionFuncOldStyle(prop, pathprop)\n\t|\n\t\tret = ExpressionParenth(prop, pathprop)\n\t|\n\t\t// Remaining options are only applicable for properties\n\t\tret = ExpressionProb(prop, pathprop)\n\t|\n\t\tret = ExpressionSS(prop, pathprop)\n\t|\n\t\tret = ExpressionReward(prop, pathprop)\n\t|\n\t\tret = ExpressionExists(prop, pathprop)\n\t|\n\t\tret = ExpressionForAll(prop, pathprop)\n\t|\n\t\tret = ExpressionStrategy(prop, pathprop)\n\t|\n\t\tret = ExpressionLabel(prop, pathprop)\n\t|\n\t\tret = ExpressionFilter(prop, pathprop)\n\t)\n\t{ return ret; }\n}\n\n// Expression: function or identifier\n\n// JavaCC warns about lookahead for this function. This is because in a few places\n// (bounded temporal operators and semicolon-less properties files)\n// (see the relevant productions for details)\n// we allow two or more successive expressions resulting in potential ambiguities\n// e.g. \"a(b)\" = \"a\" \"(b)\"\n// Ignoring the warning results in the largest match being taken.\n\nExpression ExpressionFuncOrIdent(boolean prop, boolean pathprop) :\n{\n\tString s = null;\n\tExpression ret = null;\n\tToken begin = null;\n}\n{\n\t// If there is no \"(...)\", this is an identifier\n\ts = Identifier() { ret = new ExpressionIdent(s); begin = getToken(0); }\n\t// If there is, it's a function\n\t( <LPARENTH> { ret = new ExpressionFunc(s); } ExpressionFuncArgs(prop, pathprop, (ExpressionFunc)ret) <RPARENTH> )?\n\t{ ret.setPosition(begin, getToken(0)); return ret; }\n}\n\n// Expression: min/max function (treated differently because min/max are keywords)\n\nExpression ExpressionFuncMinMax(boolean prop, boolean pathprop) :\n{\n\tString s = null;\n\tExpressionFunc func = null;\n\tToken begin = null;\n}\n{\n\t( begin = <MIN> { s = \"min\"; } | begin = <MAX> { s = \"max\"; } ) \n\t{ func = new ExpressionFunc(s); } <LPARENTH>  ExpressionFuncArgs(prop, pathprop, func) <RPARENTH>\n\t{ func.setPosition(begin, getToken(0)); return func; }\n}\n\n// Expression: old-style function, i.e. \"func(name, ...)\"\n\nExpression ExpressionFuncOldStyle(boolean prop, boolean pathprop) :\n{\n\tString s = null;\n\tExpressionFunc func = null;\n\tToken begin = null;\n}\n{\n\tbegin = <FUNC> <LPARENTH> ( <MIN> { s = \"min\"; } | <MAX> { s = \"max\"; } | s = Identifier() )\n\t<COMMA> { func = new ExpressionFunc(s); func.setOldStyle(true); } ExpressionFuncArgs(prop, pathprop, func) <RPARENTH>\n\t{ func.setPosition(begin, getToken(0)); return func; }\n}\n\n// Arguments for a function in an expression\n\nvoid ExpressionFuncArgs(boolean prop, boolean pathprop, ExpressionFunc func) :\n{\n\tExpression expr;\n}\n{\n\texpr = Expression(prop, pathprop) { func.addOperand(expr); } ( <COMMA> expr = Expression(prop, pathprop) { func.addOperand(expr); })*\n}\n\n// Expression: literal\n\nExpression ExpressionLiteral(boolean prop, boolean pathprop) :\n{\n\tExpression ret = null;\n}\n{\n\t(\n\t<REG_INT> {\n\t\ttry {\n\t\t\tint i = Integer.parseInt(getToken(0).image);\n\t\t\tret = new ExpressionLiteral(TypeInt.getInstance(), Integer.valueOf(i));\n\t\t} catch (NumberFormatException e) {\n\t\t\t// Need to catch this because some matches for regexp REG_INT\n\t\t\t// are not valid integers (e.g. too big).\n\t\t\tParseException ex = new ParseException(\"Invalid integer literal\");\n\t\t\tex.currentToken = getToken(0);\n\t\t\tthrow ex;\n\t\t\t// NB: can't call generateParseException() here; it crashes\n\t\t}}\n\t|\n\t<REG_DOUBLE> {\n\t\ttry {\n\t\t\tdouble d = Double.parseDouble(getToken(0).image);\n\t\t\tret = new ExpressionLiteral(TypeDouble.getInstance(), Double.valueOf(d), getToken(0).image);\n\t\t} catch (NumberFormatException e) {\n\t\t\t// Need to catch this because some matches for regexp REG_DOUBLE\n\t\t\t// may not be valid doubles.\n\t\t\tParseException ex = new ParseException(\"Invalid double literal\");\n\t\t\t// NB: can't call generateParseException() here; it crashes\n\t\t}}\n\t|\n\t<TRUE> { ret = new ExpressionLiteral(TypeBool.getInstance(), Boolean.valueOf(true)); }\n\t|\n\t<FALSE> { ret = new ExpressionLiteral(TypeBool.getInstance(), Boolean.valueOf(false)); }\n\t)\n\t{ ret.setPosition(getToken(0)); return ret; }\n}\n\n// Expression: parentheses\n\nExpression ExpressionParenth(boolean prop, boolean pathprop) : \n{\n\tExpression expr, ret;\n\tToken begin = null;\n}\n{\n\tbegin = <LPARENTH> expr = Expression(prop, pathprop) <RPARENTH>\n\t{ ret = new ExpressionUnaryOp(ExpressionUnaryOp.PARENTH, expr); ret.setPosition(begin, getToken(0)); return ret;}\n}\n\n// Expression: interval\n\nExpression ExpressionInterval(boolean prop, boolean pathprop) :\n{\n\tExpressionInterval expr = null;\n\tExpression expr1 = null, expr2 = null;\n\tToken begin = null;\n}\n{\n\tbegin = <LBRACKET>\n\texpr1 = Expression(prop, pathprop)\n \t<COMMA>\n \texpr2 = Expression(prop, pathprop)\n\t<RBRACKET>\n\t{ expr = new ExpressionInterval(expr1, expr2); expr.setPosition(begin, getToken(0)); return expr; }\n}\n\n//-----------------------------------------------------------------------------------\n// Property stuff\n//-----------------------------------------------------------------------------------\n\n// (Property) expression: probabilistic operator P\n\nExpression ExpressionProb(boolean prop, boolean pathprop) :\n{\n\tExpressionIdent modifier = null;\n\tint r;\n\tString relOp = null;\n\tExpression prob = null;\n\tExpression expr;\n\tFilter filter = null;\n\tExpressionProb ret = new ExpressionProb();\n\tToken begin = null;\n\tboolean isBool;\n}\n{\n\t// This production is only allowed in expressions if the \"prop\" parameter is true\n\t{ if (!prop) throw generateParseException(); }\n\t// Various options for \"P\" keyword and attached symbols\n\t(( begin = <P> ( <LPARENTH> modifier = IdentifierExpression() <RPARENTH> )? (\n\t\t\t( r = LtGt() prob = Expression(false, false) { relOp = ExpressionBinaryOp.opSymbols[r]; isBool = true; } )\n\t       |( <EQ> <QMARK> { relOp = \"=\"; isBool = false; } )\n\t       |( <MIN> (( <EQ> <QMARK> { relOp = \"min=\"; isBool = false; } )\n\t                |( <MIN> <EQ> <QMARK> { relOp = \"minmin=\"; isBool = false; } )\n\t                |( <MAX> <EQ> <QMARK> { relOp = \"minmax=\"; isBool = false; } )\n\t       ))\n\t       |( <MAX> (( <EQ> <QMARK> { relOp = \"max=\"; isBool = false; } )\n\t                |( <MIN> <EQ> <QMARK> { relOp = \"maxmin=\"; isBool = false; } )\n\t                |( <MAX> <EQ> <QMARK> { relOp = \"maxmax=\"; isBool = false; } )\n\t       ))\n\t       |( <MINMIN> <EQ> <QMARK> { relOp = \"minmin=\"; isBool = false; } )\n\t       |( <MINMAX> <EQ> <QMARK> { relOp = \"minmax=\"; isBool = false; } )\n\t       |( <MAXMIN> <EQ> <QMARK> { relOp = \"maxmin=\"; isBool = false; } )\n\t       |( <MAXMAX> <EQ> <QMARK> { relOp = \"maxmax=\"; isBool = false; } )\n\t))\n\t// These two are dupes of above but allow space to be omitted\n\t|( begin = <PMIN> <EQ> <QMARK> { relOp = \"min=\"; isBool = false; } )\n\t|( begin = <PMAX> <EQ> <QMARK> { relOp = \"max=\"; isBool = false; } )\n\t|( begin = <PMINMIN> <EQ> <QMARK> { relOp = \"minmin=\"; isBool = false; } )\n\t|( begin = <PMINMAX> <EQ> <QMARK> { relOp = \"minmax=\"; isBool = false; } )\n\t|( begin = <PMAXMIN> <EQ> <QMARK> { relOp = \"maxmin=\"; isBool = false; } )\n\t|( begin = <PMAXMAX> <EQ> <QMARK> { relOp = \"maxmax=\"; isBool = false; } ))\n\t// Path formula, optional filter\n\t<LBRACKET> expr = Expression(prop, true) (filter = Filter())? <RBRACKET>\n\t{\n\t\tret.setModifier(modifier == null ? null : modifier.getName());\n\t\tret.setRelOp(relOp);\n\t\tret.setProb(prob);\n\t\tret.setExpression(expr);\n\t\tret.setFilter(filter);\n\t\tret.setPosition(begin, getToken(0));\n\t\t// Filter is actually dealt with by wrapping this expression in\n\t\t// an (invisible) ExpressionFilter expression\n\t\tif (filter != null) {\n\t\t\tString filterOp = isBool ? \"&\" : filter.getFilterOpString();\n\t\t\tExpressionFilter ef = new ExpressionFilter(filterOp, ret, filter.getExpression());\n\t\t\tef.setInvisible(true);\n\t\t\treturn ef;\n\t\t}\n\t\telse return ret;\n\t}\n}\n\n// Filter for a P/S/R operator\n\nFilter Filter() :\n{\n\tFilter filter;\n\tExpression expr;\n\tToken begin = null;\n}\n{\n\tbegin = <LBRACE> expr = Expression(true, false) { filter = new Filter(expr); } <RBRACE>\n\t( <LBRACE>\n\t\t( <MIN> { filter.setMinRequested(true); }\n\t\t| <MAX> { filter.setMaxRequested(true); } )\n\t<RBRACE> )*\n\t{ filter.setPosition(begin, getToken(0)); return filter; }\n}\n\n// (Property) expression: steady-state operator S\n\nExpression ExpressionSS(boolean prop, boolean pathprop) :\n{\n\tExpressionIdent modifier = null;\n\tint r;\n\tString relOp = null;\n\tExpression prob = null;\n\tExpression expr;\n\tFilter filter = null;\n\tExpressionSS ret = new ExpressionSS();\n\tToken begin;\n\tboolean isBool;\n}\n{\n\t// This production is only allowed in expressions if the \"prop\" parameter is true\n\t{ if (!prop) throw generateParseException(); }\n\t// Various options for \"S\" keyword and attached symbols\n\tbegin = <S> (\n\t\t( <LPARENTH> modifier = IdentifierExpression() <RPARENTH> )?\n\t\t( r = LtGt() prob = Expression(false, false) { relOp = ExpressionBinaryOp.opSymbols[r]; isBool = true; } ) |\n\t\t( <EQ> <QMARK> { relOp = \"=\"; isBool = false; } )\n\t)\n\t// Expression, optional filter\n\t<LBRACKET> expr = Expression(prop, pathprop) (filter = Filter())? <RBRACKET>\n\t{\n\t\tret.setModifier(modifier == null ? null : modifier.getName());\n\t\tret.setRelOp(relOp);\n\t\tret.setProb(prob);\n\t\tret.setExpression(expr);\n\t\tret.setFilter(filter);\n\t\tret.setPosition(begin, getToken(0));\n\t\t// Filter is actually dealt with by wrapping this expression in\n\t\t// an (invisible) ExpressionFilter expression\n\t\tif (filter != null) {\n\t\t\tString filterOp = isBool ? \"&\" : filter.getFilterOpString();\n\t\t\tExpressionFilter ef = new ExpressionFilter(filterOp, ret, filter.getExpression());\n\t\t\tef.setInvisible(true);\n\t\t\treturn ef;\n\t\t}\n\t\telse return ret;\n\t}\n}\n\n// (Property) expression: expected reward operator R\n\nExpression ExpressionReward(boolean prop, boolean pathprop) :\n{\n\tExpressionIdent modifier = null;\n\tint r;\n\tString relOp = null;\n\tExpression rew = null;\n\tExpression expr;\n\tFilter filter = null;\n\tExpressionReward ret = new ExpressionReward();\n\tToken begin;\n\tboolean isBool;\n}\n{\n\t// This production is only allowed in expressions if the \"prop\" parameter is true\n\t{ if (!prop) throw generateParseException(); }\n\t// Various options for \"R\" keyword and attached symbols\n\t(( begin = <R>\n\t\t( <LPARENTH> modifier = IdentifierExpression() <RPARENTH> )?\n\t\t(RewardIndex(ret))?\n\t\t(( r = LtGt() rew = Expression(false, false) { relOp = ExpressionBinaryOp.opSymbols[r]; isBool = true; } )\n\t       |( <EQ> <QMARK> { relOp = \"=\"; isBool = false; } )\n\t       |( <MIN> (( <EQ> <QMARK> { relOp = \"min=\"; isBool = false; } )\n\t                |( <MIN> <EQ> <QMARK> { relOp = \"minmin=\"; isBool = false; } )\n\t                |( <MAX> <EQ> <QMARK> { relOp = \"minmax=\"; isBool = false; } )\n\t       ))\n\t       |( <MAX> (( <EQ> <QMARK> { relOp = \"max=\"; isBool = false; } )\n\t                |( <MIN> <EQ> <QMARK> { relOp = \"maxmin=\"; isBool = false; } )\n\t                |( <MAX> <EQ> <QMARK> { relOp = \"maxmax=\"; isBool = false; } )\n\t       ))\n\t       |( <MINMIN> <EQ> <QMARK> { relOp = \"minmin=\"; isBool = false; } )\n\t       |( <MINMAX> <EQ> <QMARK> { relOp = \"minmax=\"; isBool = false; } )\n\t       |( <MAXMIN> <EQ> <QMARK> { relOp = \"maxmin=\"; isBool = false; } )\n\t       |( <MAXMAX> <EQ> <QMARK> { relOp = \"maxmax=\"; isBool = false; } )\n\t))\n\t// These two are dupes of above but allow space to be omitted\n\t|( begin = <RMIN> <EQ> <QMARK> { relOp = \"min=\"; isBool = false; } )\n\t|( begin = <RMAX> <EQ> <QMARK> { relOp = \"max=\"; isBool = false; } )\n\t|( begin = <RMINMIN> <EQ> <QMARK> { relOp = \"minmin=\"; isBool = false; } )\n\t|( begin = <RMINMAX> <EQ> <QMARK> { relOp = \"minmax=\"; isBool = false; } )\n\t|( begin = <RMAXMIN> <EQ> <QMARK> { relOp = \"maxmin=\"; isBool = false; } )\n\t|( begin = <RMAXMAX> <EQ> <QMARK> { relOp = \"maxmax=\"; isBool = false; } ))\n\t// Path formula, optional filter\n\t<LBRACKET> expr = ExpressionRewardContents(prop, pathprop) (filter = Filter())? <RBRACKET>\n\t{\n\t\tret.setModifier(modifier == null ? null : modifier.getName());\n\t\tret.setRelOp(relOp);\n\t\tret.setReward(rew);\n\t\tret.setExpression(expr);\n\t\tret.setFilter(filter);\n\t\tret.setPosition(begin, getToken(0));\n\t\t// Filter is actually dealt with by wrapping this expression in\n\t\t// an (invisible) ExpressionFilter expression\n\t\tif (filter != null) {\n\t\t\tString filterOp = isBool ? \"&\" : filter.getFilterOpString();\n\t\t\tExpressionFilter ef = new ExpressionFilter(filterOp, ret, filter.getExpression());\n\t\t\tef.setInvisible(true);\n\t\t\treturn ef;\n\t\t}\n\t\telse return ret;\n\t}\n}\n\n// Reward struct index for R operator\n\nvoid RewardIndex(ExpressionReward exprRew) :\n{\n\tObject index = null;\n\tObject indexDiv = null;\n}\n{\n\t// Lookahead here is to ensure that \"id\" is not misdetected as an ExpressionLabel\n\t( <LBRACE> ( LOOKAHEAD(<DQUOTE>) ( <DQUOTE> index = Identifier() <DQUOTE> ) | index = Expression(false, false) ) <RBRACE> )\n\t// Optional second reward structure index (for ratio objectives)\n\t( <DIVIDE> ( <LBRACE> ( LOOKAHEAD(<DQUOTE>) ( <DQUOTE> indexDiv = Identifier() <DQUOTE> ) | indexDiv = Expression(false, false) ) <RBRACE> ))?\n\t{\n\t\texprRew.setRewardStructIndex(index);\n\t\tif (indexDiv != null) {\n\t\t\texprRew.setRewardStructIndexDiv(indexDiv);\n\t\t}\n\t}\n}\n\n// Contents of an R operator\n\n// JavaCC warns about lookahead for this function. This is because there is a possible conflict between\n// R [ S ], where \"S\" is the long-run reward operator, and R [ S [ ] ], where \"S [ ]\" is an LTL formula\n// comprising a single atomic proposition. We use lookahead to resolve the ambiguity.\n\nExpression ExpressionRewardContents(boolean prop, boolean pathprop) :\n{\n\tExpression expr = null;\n\tExpressionTemporal exprTemp = null;\n\tExpression ret = null;\n\tToken begin;\n}\n{\n\t{ begin = getToken(1); }\n\t(\n\t// First look for cases where it starts with \"S\" (see above)\n\tLOOKAHEAD(ExpressionSS(prop, pathprop)) expr = ExpressionSS(prop, true) { ret = expr; }\n\t| <S> { ret = new ExpressionTemporal(ExpressionTemporal.R_S, null, null); }\n\t\n\t// Normal reward operators (excluding S; see above)\n\t| LOOKAHEAD(<C> <LE>) begin = <C> <LE> expr = Expression(false, false) { exprTemp = new ExpressionTemporal(ExpressionTemporal.R_C, null, null); exprTemp.setUpperBound(expr); ret = exprTemp; }\n\t| <C> { ret = new ExpressionTemporal(ExpressionTemporal.R_C, null, null); }\n\t| <I> <EQ> expr = Expression(false, false) { exprTemp = new ExpressionTemporal(ExpressionTemporal.R_I, null, null); exprTemp.setUpperBound(expr); ret = exprTemp; }\n\t\n\t// Path formula (including F \"target\")\n\t| expr = Expression(prop, true) { ret = expr; }\n\t)\n\t{ ret.setPosition(begin, getToken(0)); return ret; }\n}\n\n// (Property) expression: CTL existential operator E\n\nExpression ExpressionExists(boolean prop, boolean pathprop) :\n{\n\tExpressionExists ret = new ExpressionExists();\n\tExpression expr;\n\tToken begin = null;\n}\n{\n\t// This production is only allowed in expressions if the \"prop\" parameter is true\n\t{ if (!prop) throw generateParseException(); }\n\t( begin = <E> <LBRACKET> expr = Expression(prop, true) <RBRACKET> )\n\t{\n\t\tret.setExpression(expr);\n\t\tret.setPosition(begin, getToken(0));\n\t\treturn ret;\n\t}\n}\n\n// (Property) expression: CTL universal operator A\n\nExpression ExpressionForAll(boolean prop, boolean pathprop) :\n{\n\tExpressionForAll ret = new ExpressionForAll();\n\tExpression expr;\n\tToken begin = null;\n}\n{\n\t// This production is only allowed in expressions if the \"prop\" parameter is true\n\t{ if (!prop) throw generateParseException(); }\n\t( begin = <A> <LBRACKET> expr = Expression(prop, true) <RBRACKET> )\n\t{\n\t\tret.setExpression(expr);\n\t\tret.setPosition(begin, getToken(0));\n\t\treturn ret;\n\t}\n}\n\n// (Property) expression: ATL strategy operators <<>> and [[]]\n\nExpression ExpressionStrategy(boolean prop, boolean pathprop) :\n{\n\tExpressionStrategy ret;\n\tExpression expr;\n\tToken begin = null;\n}\n{\n\t// This production is only allowed in expressions if the \"prop\" parameter is true\n\t{ if (!prop) throw generateParseException(); }\n\t(\n\t// <<...>> or [[...]]\n\t(( begin = <DLT> { ret = new ExpressionStrategy(true); } ExpressionStrategyCoalition(ret) <DGT> )\n\t| (begin = <DLBRACKET> { ret = new ExpressionStrategy(false); } ExpressionStrategyCoalition(ret) <DRBRACKET> ))\n\t// Child expression\n\t(\n\t( expr = ExpressionProb(prop, pathprop) | expr = ExpressionReward(prop, pathprop) )\n\t{ ret.setSingleOperand(expr); }\n\t| expr = ExpressionParenth(prop, pathprop)\n\t{ ret.addOperand(expr); }\n\t))\n\t{\n\t\tret.setPosition(begin, getToken(0));\n\t\treturn ret;\n\t}\n}\n\n// Coalition (player list) for a strategy (<<>> or [[]]) operator\n\nvoid ExpressionStrategyCoalition(ExpressionStrategy exprStrat) :\n{\n\tList<String> coalition = new ArrayList<String>();\n\tString s;\n}\n{\n\t( <TIMES> ) { exprStrat.setCoalitionAllPlayers();}\n\t|\n\t( s = ExpressionStrategyCoalitionPlayer() { coalition.add(s); }\n\t( <COMMA> s = ExpressionStrategyCoalitionPlayer()  { coalition.add(s); } )* )?\n\t{ exprStrat.setCoalition(coalition); }\n}\n\n// Single player in a coalition for a strategy (<<>> or [[]]) operator\n\nString ExpressionStrategyCoalitionPlayer() :\n{\n\tString s;\n}\n{\n\t( <REG_INT> | <REG_IDENT> ) { s = getToken(0).image; }\n\t{ return s; }\n}\n\n// (Property) expression: label (including \"init\")\n\nExpression ExpressionLabel(boolean prop, boolean pathprop) :\n{\n\tString s;\n\tExpressionLabel ret = null;\n\tToken begin;\n}\n{\n\t// This production is only allowed in expressions if the \"prop\" parameter is true\n\t{ if (!prop) throw generateParseException(); }\n\t// Label can be arbitary string or the \"init\" keyword\n\t( begin = <DQUOTE> ( s=Identifier() | <INIT> { s = \"init\"; } ) <DQUOTE> )\n\t{ ret = new ExpressionLabel(s); ret.setPosition(begin, getToken(0)); return ret; }\n}\n\n// (Property) expression: filter (using \"filter\" keyword)\n\nExpression ExpressionFilter(boolean prop, boolean pathprop) :\n{\n\tExpressionFilter expr = null;\n\tString op = null;\n\tExpression filter = null;\n\tExpression expr2 = null;\n\tToken begin = null;\n}\n{\n\t// This production is only allowed in expressions if the \"prop\" parameter is true\n\t{ if (!prop) throw generateParseException(); }\n\t\n\t// filter(\n\tbegin = <FILTER> <LPARENTH>\n\t// filter type\n\t( <MIN> { op = \"min\"; } | <MAX> { op = \"max\"; }\n\t| <PLUS> { op = \"+\"; } | <AND> { op = \"&\"; } | <OR> { op = \"|\"; }\n\t| op = Identifier() )\n\t// operand\n\t<COMMA> expr2 = Expression(prop, pathprop)\n\t// (optional filter expression)\n\t[ <COMMA> filter = Expression(prop, pathprop) ]\n\t// )\n\t<RPARENTH>\n\t{ expr = new ExpressionFilter(op, expr2, filter); expr.setPosition(begin, getToken(0)); return expr; }\n}\n\n//-----------------------------------------------------------------------------------\n// Miscellaneous stuff\n//-----------------------------------------------------------------------------------\n\n// Identifier (returns String)\n\nString Identifier() :\n{\n}\n{\n\t<REG_IDENT> { return getToken(0).image; }\n}\n\n// Identifier (returns ExpressionIdent, storing position info)\n\nExpressionIdent IdentifierExpression() :\n{\n\tString ident;\n\tExpressionIdent ret;\n}\n{\n\tident = Identifier()\n\t{ ret = new ExpressionIdent(ident); ret.setPosition(getToken(0)); return ret; }\n}\n\n// Identifier or min/max keyword (returns ExpressionIdent, storing position info)\n\nExpressionIdent IdentifierExpressionMinMax() :\n{\n\tString ident;\n\tExpressionIdent ret;\n}\n{\n\t( ident = Identifier() | <MIN> { ident=\"min\"; } | <MAX> { ident=\"max\"; } )\n\t{ ret = new ExpressionIdent(ident); ret.setPosition(getToken(0)); return ret; }\n}\n\n// Primed identifier\n\nExpressionIdent IdentifierPrime() :\n{\n}\n{\n\t<REG_IDENTPRIME>\n\t{\n\t\t// Remove prime, create new ident and return\n\t\tString s = getToken(0).image;\n\t\ts = s.substring(0, s.length()-1);\n\t\tExpressionIdent expr = new ExpressionIdent(s);\n\t\texpr.setPosition(token);\n\t\texpr.setEndColumn(expr.getEndColumn() - 1);\n\t\treturn expr;\n\t}\n}\n\n// Equality operators: =, !=\n\nint EqNeq() :\n{\n}\n{\n\t<EQ> {return ExpressionBinaryOp.EQ; } |\n\t<NE> {return ExpressionBinaryOp.NE; }\n}\n\n// Relational operators: >, <, >=, <=\n\nint LtGt() :\n{\n}\n{\n\t<GT> {return ExpressionBinaryOp.GT; } |\n\t<LT> {return ExpressionBinaryOp.LT; } |\n\t<GE>  {return ExpressionBinaryOp.GE; }|\n\t<LE> {return ExpressionBinaryOp.LE; }\n}\n\n// For loop\n\nForLoop ForLoop() :\n{\n\tString s;\n\tExpression from = null, to = null, step = null;\n\tForLoop fl = new ForLoop();\n\tToken begin;\n}\n{\n\t( { begin = getToken(1); } s=Identifier() <EQ> from = Expression(false, false) <COLON> to = Expression(false, false)\n\t( <COLON> step = Expression(false, false) )? <EOF> )\n\t{\n\t\tfl.setLHS(s);\n\t\tfl.setFrom(from);\n\t\tfl.setTo(to);\n\t\tif (step != null) fl.setStep(step);\n\t\tfl.setPosition(begin, getToken(0));\n\t\treturn fl;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/PrismParserConstants.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. PrismParserConstants.java */\npackage parser;\n\n\n/**\n * Token literal values and constants.\n * Generated by org.javacc.parser.OtherFilesGen#start()\n */\npublic interface PrismParserConstants {\n\n  /** End of File. */\n  int EOF = 0;\n  /** RegularExpression Id. */\n  int WHITESPACE = 1;\n  /** RegularExpression Id. */\n  int COMMENT = 2;\n  /** RegularExpression Id. */\n  int A = 3;\n  /** RegularExpression Id. */\n  int BOOL = 4;\n  /** RegularExpression Id. */\n  int CLOCK = 5;\n  /** RegularExpression Id. */\n  int CONST = 6;\n  /** RegularExpression Id. */\n  int CTMC = 7;\n  /** RegularExpression Id. */\n  int C = 8;\n  /** RegularExpression Id. */\n  int DOUBLE = 9;\n  /** RegularExpression Id. */\n  int DTMC = 10;\n  /** RegularExpression Id. */\n  int E = 11;\n  /** RegularExpression Id. */\n  int ENDINIT = 12;\n  /** RegularExpression Id. */\n  int ENDINVARIANT = 13;\n  /** RegularExpression Id. */\n  int ENDMODULE = 14;\n  /** RegularExpression Id. */\n  int ENDOBSERVABLES = 15;\n  /** RegularExpression Id. */\n  int ENDREWARDS = 16;\n  /** RegularExpression Id. */\n  int ENDSYSTEM = 17;\n  /** RegularExpression Id. */\n  int FALSE = 18;\n  /** RegularExpression Id. */\n  int FORMULA = 19;\n  /** RegularExpression Id. */\n  int FILTER = 20;\n  /** RegularExpression Id. */\n  int FUNC = 21;\n  /** RegularExpression Id. */\n  int F = 22;\n  /** RegularExpression Id. */\n  int GLOBAL = 23;\n  /** RegularExpression Id. */\n  int G = 24;\n  /** RegularExpression Id. */\n  int INIT = 25;\n  /** RegularExpression Id. */\n  int INVARIANT = 26;\n  /** RegularExpression Id. */\n  int I = 27;\n  /** RegularExpression Id. */\n  int INT = 28;\n  /** RegularExpression Id. */\n  int LABEL = 29;\n  /** RegularExpression Id. */\n  int MAXMAX = 30;\n  /** RegularExpression Id. */\n  int MAXMIN = 31;\n  /** RegularExpression Id. */\n  int MAX = 32;\n  /** RegularExpression Id. */\n  int MDP = 33;\n  /** RegularExpression Id. */\n  int MINMAX = 34;\n  /** RegularExpression Id. */\n  int MINMIN = 35;\n  /** RegularExpression Id. */\n  int MIN = 36;\n  /** RegularExpression Id. */\n  int MODULE = 37;\n  /** RegularExpression Id. */\n  int X = 38;\n  /** RegularExpression Id. */\n  int NONDETERMINISTIC = 39;\n  /** RegularExpression Id. */\n  int OBSERVABLE = 40;\n  /** RegularExpression Id. */\n  int OBSERVABLES = 41;\n  /** RegularExpression Id. */\n  int PMAXMAX = 42;\n  /** RegularExpression Id. */\n  int PMAXMIN = 43;\n  /** RegularExpression Id. */\n  int PMAX = 44;\n  /** RegularExpression Id. */\n  int PMINMAX = 45;\n  /** RegularExpression Id. */\n  int PMINMIN = 46;\n  /** RegularExpression Id. */\n  int PMIN = 47;\n  /** RegularExpression Id. */\n  int P = 48;\n  /** RegularExpression Id. */\n  int POMDP = 49;\n  /** RegularExpression Id. */\n  int POPTA = 50;\n  /** RegularExpression Id. */\n  int PROBABILISTIC = 51;\n  /** RegularExpression Id. */\n  int PROB = 52;\n  /** RegularExpression Id. */\n  int PTA = 53;\n  /** RegularExpression Id. */\n  int RATE = 54;\n  /** RegularExpression Id. */\n  int REWARDS = 55;\n  /** RegularExpression Id. */\n  int RMAXMAX = 56;\n  /** RegularExpression Id. */\n  int RMAXMIN = 57;\n  /** RegularExpression Id. */\n  int RMAX = 58;\n  /** RegularExpression Id. */\n  int RMINMAX = 59;\n  /** RegularExpression Id. */\n  int RMINMIN = 60;\n  /** RegularExpression Id. */\n  int RMIN = 61;\n  /** RegularExpression Id. */\n  int R = 62;\n  /** RegularExpression Id. */\n  int S = 63;\n  /** RegularExpression Id. */\n  int STOCHASTIC = 64;\n  /** RegularExpression Id. */\n  int SYSTEM = 65;\n  /** RegularExpression Id. */\n  int TRUE = 66;\n  /** RegularExpression Id. */\n  int U = 67;\n  /** RegularExpression Id. */\n  int W = 68;\n  /** RegularExpression Id. */\n  int NOT = 69;\n  /** RegularExpression Id. */\n  int AND = 70;\n  /** RegularExpression Id. */\n  int OR = 71;\n  /** RegularExpression Id. */\n  int IMPLIES = 72;\n  /** RegularExpression Id. */\n  int IFF = 73;\n  /** RegularExpression Id. */\n  int RARROW = 74;\n  /** RegularExpression Id. */\n  int COLON = 75;\n  /** RegularExpression Id. */\n  int SEMICOLON = 76;\n  /** RegularExpression Id. */\n  int COMMA = 77;\n  /** RegularExpression Id. */\n  int DOTS = 78;\n  /** RegularExpression Id. */\n  int LPARENTH = 79;\n  /** RegularExpression Id. */\n  int RPARENTH = 80;\n  /** RegularExpression Id. */\n  int LBRACKET = 81;\n  /** RegularExpression Id. */\n  int RBRACKET = 82;\n  /** RegularExpression Id. */\n  int DLBRACKET = 83;\n  /** RegularExpression Id. */\n  int DRBRACKET = 84;\n  /** RegularExpression Id. */\n  int LBRACE = 85;\n  /** RegularExpression Id. */\n  int RBRACE = 86;\n  /** RegularExpression Id. */\n  int EQ = 87;\n  /** RegularExpression Id. */\n  int NE = 88;\n  /** RegularExpression Id. */\n  int LT = 89;\n  /** RegularExpression Id. */\n  int GT = 90;\n  /** RegularExpression Id. */\n  int DLT = 91;\n  /** RegularExpression Id. */\n  int DGT = 92;\n  /** RegularExpression Id. */\n  int LE = 93;\n  /** RegularExpression Id. */\n  int GE = 94;\n  /** RegularExpression Id. */\n  int PLUS = 95;\n  /** RegularExpression Id. */\n  int MINUS = 96;\n  /** RegularExpression Id. */\n  int TIMES = 97;\n  /** RegularExpression Id. */\n  int DIVIDE = 98;\n  /** RegularExpression Id. */\n  int POWER = 99;\n  /** RegularExpression Id. */\n  int PRIME = 100;\n  /** RegularExpression Id. */\n  int RENAME = 101;\n  /** RegularExpression Id. */\n  int QMARK = 102;\n  /** RegularExpression Id. */\n  int DQUOTE = 103;\n  /** RegularExpression Id. */\n  int REG_INT = 104;\n  /** RegularExpression Id. */\n  int REG_DOUBLE = 105;\n  /** RegularExpression Id. */\n  int REG_IDENTPRIME = 106;\n  /** RegularExpression Id. */\n  int REG_IDENT = 107;\n  /** RegularExpression Id. */\n  int PREPROC = 108;\n  /** RegularExpression Id. */\n  int LEXICAL_ERROR = 109;\n\n  /** Lexical state. */\n  int DEFAULT = 0;\n\n  /** Literal token values. */\n  String[] tokenImage = {\n    \"<EOF>\",\n    \"<WHITESPACE>\",\n    \"<COMMENT>\",\n    \"\\\"A\\\"\",\n    \"\\\"bool\\\"\",\n    \"\\\"clock\\\"\",\n    \"\\\"const\\\"\",\n    \"\\\"ctmc\\\"\",\n    \"\\\"C\\\"\",\n    \"\\\"double\\\"\",\n    \"\\\"dtmc\\\"\",\n    \"\\\"E\\\"\",\n    \"\\\"endinit\\\"\",\n    \"\\\"endinvariant\\\"\",\n    \"\\\"endmodule\\\"\",\n    \"\\\"endobservables\\\"\",\n    \"\\\"endrewards\\\"\",\n    \"\\\"endsystem\\\"\",\n    \"\\\"false\\\"\",\n    \"\\\"formula\\\"\",\n    \"\\\"filter\\\"\",\n    \"\\\"func\\\"\",\n    \"\\\"F\\\"\",\n    \"\\\"global\\\"\",\n    \"\\\"G\\\"\",\n    \"\\\"init\\\"\",\n    \"\\\"invariant\\\"\",\n    \"\\\"I\\\"\",\n    \"\\\"int\\\"\",\n    \"\\\"label\\\"\",\n    \"\\\"maxmax\\\"\",\n    \"\\\"maxmin\\\"\",\n    \"\\\"max\\\"\",\n    \"\\\"mdp\\\"\",\n    \"\\\"minmax\\\"\",\n    \"\\\"minmin\\\"\",\n    \"\\\"min\\\"\",\n    \"\\\"module\\\"\",\n    \"\\\"X\\\"\",\n    \"\\\"nondeterministic\\\"\",\n    \"\\\"observable\\\"\",\n    \"\\\"observables\\\"\",\n    \"\\\"Pmaxmax\\\"\",\n    \"\\\"Pmaxmin\\\"\",\n    \"\\\"Pmax\\\"\",\n    \"\\\"Pminmax\\\"\",\n    \"\\\"Pminmin\\\"\",\n    \"\\\"Pmin\\\"\",\n    \"\\\"P\\\"\",\n    \"\\\"pomdp\\\"\",\n    \"\\\"popta\\\"\",\n    \"\\\"probabilistic\\\"\",\n    \"\\\"prob\\\"\",\n    \"\\\"pta\\\"\",\n    \"\\\"rate\\\"\",\n    \"\\\"rewards\\\"\",\n    \"\\\"Rmaxmax\\\"\",\n    \"\\\"Rmaxmin\\\"\",\n    \"\\\"Rmax\\\"\",\n    \"\\\"Rminmax\\\"\",\n    \"\\\"Rminmin\\\"\",\n    \"\\\"Rmin\\\"\",\n    \"\\\"R\\\"\",\n    \"\\\"S\\\"\",\n    \"\\\"stochastic\\\"\",\n    \"\\\"system\\\"\",\n    \"\\\"true\\\"\",\n    \"\\\"U\\\"\",\n    \"\\\"W\\\"\",\n    \"\\\"!\\\"\",\n    \"\\\"&\\\"\",\n    \"\\\"|\\\"\",\n    \"\\\"=>\\\"\",\n    \"\\\"<=>\\\"\",\n    \"\\\"->\\\"\",\n    \"\\\":\\\"\",\n    \"\\\";\\\"\",\n    \"\\\",\\\"\",\n    \"\\\"..\\\"\",\n    \"\\\"(\\\"\",\n    \"\\\")\\\"\",\n    \"\\\"[\\\"\",\n    \"\\\"]\\\"\",\n    \"\\\"[[\\\"\",\n    \"\\\"]]\\\"\",\n    \"\\\"{\\\"\",\n    \"\\\"}\\\"\",\n    \"\\\"=\\\"\",\n    \"\\\"!=\\\"\",\n    \"\\\"<\\\"\",\n    \"\\\">\\\"\",\n    \"\\\"<<\\\"\",\n    \"\\\">>\\\"\",\n    \"\\\"<=\\\"\",\n    \"\\\">=\\\"\",\n    \"\\\"+\\\"\",\n    \"\\\"-\\\"\",\n    \"\\\"*\\\"\",\n    \"\\\"/\\\"\",\n    \"\\\"^\\\"\",\n    \"\\\"\\\\\\'\\\"\",\n    \"\\\"<-\\\"\",\n    \"\\\"?\\\"\",\n    \"\\\"\\\\\\\"\\\"\",\n    \"<REG_INT>\",\n    \"<REG_DOUBLE>\",\n    \"<REG_IDENTPRIME>\",\n    \"<REG_IDENT>\",\n    \"<PREPROC>\",\n    \"<LEXICAL_ERROR>\",\n  };\n\n}\n"
  },
  {
    "path": "prism/src/parser/PrismParserTokenManager.java",
    "content": "/* PrismParserTokenManager.java */\n/* Generated By:JavaCC: Do not edit this line. PrismParserTokenManager.java */\npackage parser;\nimport java.io.*;\nimport java.util.List;\nimport java.util.ArrayList;\nimport java.util.HashSet;\nimport jltl2ba.SimpleLTL;\nimport parser.BooleanUtils;\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.ModelInfo;\nimport parser.visitor.*;\nimport prism.ModelType;\nimport prism.PrismLangException;\n\n/** Token Manager. */\n@SuppressWarnings (\"unused\")\npublic class PrismParserTokenManager implements PrismParserConstants {\n\n  /** Debug output. */\n  public static  java.io.PrintStream debugStream = System.out;\n  /** Set debug output. */\n  public static  void setDebugStream(java.io.PrintStream ds) { debugStream = ds; }\nprivate static final int jjStopStringLiteralDfa_0(int pos, long active0, long active1){\n   switch (pos)\n   {\n      case 0:\n         if ((active0 & 0xff01fc4009400908L) != 0L || (active1 & 0x18L) != 0L)\n            return 23;\n         if ((active0 & 0xfe03bff6bff6f0L) != 0L || (active1 & 0x7L) != 0L)\n         {\n            jjmatchedKind = 107;\n            return 23;\n         }\n         if ((active1 & 0x400000000L) != 0L)\n            return 1;\n         if ((active1 & 0x4000L) != 0L)\n            return 11;\n         return -1;\n      case 1:\n         if ((active0 & 0x3ffeffbff6bff6f0L) != 0L || (active1 & 0x7L) != 0L)\n         {\n            if (jjmatchedPos != 1)\n            {\n               jjmatchedKind = 107;\n               jjmatchedPos = 1;\n            }\n            return 23;\n         }\n         return -1;\n      case 2:\n         if ((active0 & 0x20001fd0000000L) != 0L)\n            return 23;\n         if ((active0 & 0x3fdeffa026bff6f0L) != 0L || (active1 & 0x7L) != 0L)\n         {\n            if (jjmatchedPos != 2)\n            {\n               jjmatchedKind = 107;\n               jjmatchedPos = 2;\n            }\n            return 23;\n         }\n         return -1;\n      case 3:\n         if ((active0 & 0x3f58fc0002200490L) != 0L || (active1 & 0x4L) != 0L)\n            return 23;\n         if ((active0 & 0x8603ace49ff260L) != 0L || (active1 & 0x3L) != 0L)\n         {\n            if (jjmatchedPos != 3)\n            {\n               jjmatchedKind = 107;\n               jjmatchedPos = 3;\n            }\n            return 23;\n         }\n         return -1;\n      case 4:\n         if ((active0 & 0x6000020040060L) != 0L)\n            return 23;\n         if ((active0 & 0x1b886facc49bf200L) != 0L || (active1 & 0x3L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 4;\n            return 23;\n         }\n         return -1;\n      case 5:\n         if ((active0 & 0x2cc0900200L) != 0L || (active1 & 0x2L) != 0L)\n            return 23;\n         if ((active0 & 0x1b886f80040bf000L) != 0L || (active1 & 0x1L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 5;\n            return 23;\n         }\n         return -1;\n      case 6:\n         if ((active0 & 0x1b806c0000081000L) != 0L)\n            return 23;\n         if ((active0 & 0x803800403e000L) != 0L || (active1 & 0x1L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 6;\n            return 23;\n         }\n         return -1;\n      case 7:\n         if ((active0 & 0x803800403e000L) != 0L || (active1 & 0x1L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 7;\n            return 23;\n         }\n         return -1;\n      case 8:\n         if ((active0 & 0x4024000L) != 0L)\n            return 23;\n         if ((active0 & 0x803800001a000L) != 0L || (active1 & 0x1L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 8;\n            return 23;\n         }\n         return -1;\n      case 9:\n         if ((active0 & 0x30000010000L) != 0L || (active1 & 0x1L) != 0L)\n            return 23;\n         if ((active0 & 0x800800000a000L) != 0L)\n         {\n            if (jjmatchedPos != 9)\n            {\n               jjmatchedKind = 107;\n               jjmatchedPos = 9;\n            }\n            return 23;\n         }\n         return -1;\n      case 10:\n         if ((active0 & 0x20000000000L) != 0L)\n            return 23;\n         if ((active0 & 0x800800000a000L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 10;\n            return 23;\n         }\n         return -1;\n      case 11:\n         if ((active0 & 0x2000L) != 0L)\n            return 23;\n         if ((active0 & 0x8008000008000L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 11;\n            return 23;\n         }\n         return -1;\n      case 12:\n         if ((active0 & 0x8000000000000L) != 0L)\n            return 23;\n         if ((active0 & 0x8000008000L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 12;\n            return 23;\n         }\n         return -1;\n      case 13:\n         if ((active0 & 0x8000L) != 0L)\n            return 23;\n         if ((active0 & 0x8000000000L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 13;\n            return 23;\n         }\n         return -1;\n      case 14:\n         if ((active0 & 0x8000000000L) != 0L)\n         {\n            jjmatchedKind = 107;\n            jjmatchedPos = 14;\n            return 23;\n         }\n         return -1;\n      default :\n         return -1;\n   }\n}\nprivate static final int jjStartNfa_0(int pos, long active0, long active1){\n   return jjMoveNfa_0(jjStopStringLiteralDfa_0(pos, active0, active1), pos + 1);\n}\nstatic private int jjStopAtPos(int pos, int kind)\n{\n   jjmatchedKind = kind;\n   jjmatchedPos = pos;\n   return pos + 1;\n}\nstatic private int jjMoveStringLiteralDfa0_0(){\n   switch(curChar)\n   {\n      case 33:\n         jjmatchedKind = 69;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x1000000L);\n      case 34:\n         return jjStopAtPos(0, 103);\n      case 38:\n         return jjStopAtPos(0, 70);\n      case 39:\n         return jjStopAtPos(0, 100);\n      case 40:\n         return jjStopAtPos(0, 79);\n      case 41:\n         return jjStopAtPos(0, 80);\n      case 42:\n         return jjStopAtPos(0, 97);\n      case 43:\n         return jjStopAtPos(0, 95);\n      case 44:\n         return jjStopAtPos(0, 77);\n      case 45:\n         jjmatchedKind = 96;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x400L);\n      case 46:\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x4000L);\n      case 47:\n         return jjStartNfaWithStates_0(0, 98, 1);\n      case 58:\n         return jjStopAtPos(0, 75);\n      case 59:\n         return jjStopAtPos(0, 76);\n      case 60:\n         jjmatchedKind = 89;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x2028000200L);\n      case 61:\n         jjmatchedKind = 87;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x100L);\n      case 62:\n         jjmatchedKind = 90;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x50000000L);\n      case 63:\n         return jjStopAtPos(0, 102);\n      case 65:\n         return jjStartNfaWithStates_0(0, 3, 23);\n      case 67:\n         return jjStartNfaWithStates_0(0, 8, 23);\n      case 69:\n         return jjStartNfaWithStates_0(0, 11, 23);\n      case 70:\n         return jjStartNfaWithStates_0(0, 22, 23);\n      case 71:\n         return jjStartNfaWithStates_0(0, 24, 23);\n      case 73:\n         return jjStartNfaWithStates_0(0, 27, 23);\n      case 80:\n         jjmatchedKind = 48;\n         return jjMoveStringLiteralDfa1_0(0xfc0000000000L, 0x0L);\n      case 82:\n         jjmatchedKind = 62;\n         return jjMoveStringLiteralDfa1_0(0x3f00000000000000L, 0x0L);\n      case 83:\n         return jjStartNfaWithStates_0(0, 63, 23);\n      case 85:\n         return jjStartNfaWithStates_0(0, 67, 23);\n      case 87:\n         return jjStartNfaWithStates_0(0, 68, 23);\n      case 88:\n         return jjStartNfaWithStates_0(0, 38, 23);\n      case 91:\n         jjmatchedKind = 81;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x80000L);\n      case 93:\n         jjmatchedKind = 82;\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x100000L);\n      case 94:\n         return jjStopAtPos(0, 99);\n      case 98:\n         return jjMoveStringLiteralDfa1_0(0x10L, 0x0L);\n      case 99:\n         return jjMoveStringLiteralDfa1_0(0xe0L, 0x0L);\n      case 100:\n         return jjMoveStringLiteralDfa1_0(0x600L, 0x0L);\n      case 101:\n         return jjMoveStringLiteralDfa1_0(0x3f000L, 0x0L);\n      case 102:\n         return jjMoveStringLiteralDfa1_0(0x3c0000L, 0x0L);\n      case 103:\n         return jjMoveStringLiteralDfa1_0(0x800000L, 0x0L);\n      case 105:\n         return jjMoveStringLiteralDfa1_0(0x16000000L, 0x0L);\n      case 108:\n         return jjMoveStringLiteralDfa1_0(0x20000000L, 0x0L);\n      case 109:\n         return jjMoveStringLiteralDfa1_0(0x3fc0000000L, 0x0L);\n      case 110:\n         return jjMoveStringLiteralDfa1_0(0x8000000000L, 0x0L);\n      case 111:\n         return jjMoveStringLiteralDfa1_0(0x30000000000L, 0x0L);\n      case 112:\n         return jjMoveStringLiteralDfa1_0(0x3e000000000000L, 0x0L);\n      case 114:\n         return jjMoveStringLiteralDfa1_0(0xc0000000000000L, 0x0L);\n      case 115:\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x3L);\n      case 116:\n         return jjMoveStringLiteralDfa1_0(0x0L, 0x4L);\n      case 123:\n         return jjStopAtPos(0, 85);\n      case 124:\n         return jjStopAtPos(0, 71);\n      case 125:\n         return jjStopAtPos(0, 86);\n      default :\n         return jjMoveNfa_0(0, 0);\n   }\n}\nstatic private int jjMoveStringLiteralDfa1_0(long active0, long active1){\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(0, active0, active1);\n      return 1;\n   }\n   switch(curChar)\n   {\n      case 45:\n         if ((active1 & 0x2000000000L) != 0L)\n            return jjStopAtPos(1, 101);\n         break;\n      case 46:\n         if ((active1 & 0x4000L) != 0L)\n            return jjStopAtPos(1, 78);\n         break;\n      case 60:\n         if ((active1 & 0x8000000L) != 0L)\n            return jjStopAtPos(1, 91);\n         break;\n      case 61:\n         if ((active1 & 0x1000000L) != 0L)\n            return jjStopAtPos(1, 88);\n         else if ((active1 & 0x20000000L) != 0L)\n         {\n            jjmatchedKind = 93;\n            jjmatchedPos = 1;\n         }\n         else if ((active1 & 0x40000000L) != 0L)\n            return jjStopAtPos(1, 94);\n         return jjMoveStringLiteralDfa2_0(active0, 0L, active1, 0x200L);\n      case 62:\n         if ((active1 & 0x100L) != 0L)\n            return jjStopAtPos(1, 72);\n         else if ((active1 & 0x400L) != 0L)\n            return jjStopAtPos(1, 74);\n         else if ((active1 & 0x10000000L) != 0L)\n            return jjStopAtPos(1, 92);\n         break;\n      case 91:\n         if ((active1 & 0x80000L) != 0L)\n            return jjStopAtPos(1, 83);\n         break;\n      case 93:\n         if ((active1 & 0x100000L) != 0L)\n            return jjStopAtPos(1, 84);\n         break;\n      case 97:\n         return jjMoveStringLiteralDfa2_0(active0, 0x400001e0040000L, active1, 0L);\n      case 98:\n         return jjMoveStringLiteralDfa2_0(active0, 0x30000000000L, active1, 0L);\n      case 100:\n         return jjMoveStringLiteralDfa2_0(active0, 0x200000000L, active1, 0L);\n      case 101:\n         return jjMoveStringLiteralDfa2_0(active0, 0x80000000000000L, active1, 0L);\n      case 105:\n         return jjMoveStringLiteralDfa2_0(active0, 0x1c00100000L, active1, 0L);\n      case 108:\n         return jjMoveStringLiteralDfa2_0(active0, 0x800020L, active1, 0L);\n      case 109:\n         return jjMoveStringLiteralDfa2_0(active0, 0x3f00fc0000000000L, active1, 0L);\n      case 110:\n         return jjMoveStringLiteralDfa2_0(active0, 0x1603f000L, active1, 0L);\n      case 111:\n         return jjMoveStringLiteralDfa2_0(active0, 0x600a000080250L, active1, 0L);\n      case 114:\n         return jjMoveStringLiteralDfa2_0(active0, 0x18000000000000L, active1, 0x4L);\n      case 116:\n         return jjMoveStringLiteralDfa2_0(active0, 0x20000000000480L, active1, 0x1L);\n      case 117:\n         return jjMoveStringLiteralDfa2_0(active0, 0x200000L, active1, 0L);\n      case 121:\n         return jjMoveStringLiteralDfa2_0(active0, 0L, active1, 0x2L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(0, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa2_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(0, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(1, active0, active1);\n      return 2;\n   }\n   switch(curChar)\n   {\n      case 62:\n         if ((active1 & 0x200L) != 0L)\n            return jjStopAtPos(2, 73);\n         break;\n      case 97:\n         if ((active0 & 0x20000000000000L) != 0L)\n            return jjStartNfaWithStates_0(2, 53, 23);\n         return jjMoveStringLiteralDfa3_0(active0, 0x7001c0000000000L, active1, 0L);\n      case 98:\n         return jjMoveStringLiteralDfa3_0(active0, 0x20000000L, active1, 0L);\n      case 100:\n         return jjMoveStringLiteralDfa3_0(active0, 0x200003f000L, active1, 0L);\n      case 105:\n         return jjMoveStringLiteralDfa3_0(active0, 0x3800e00002000000L, active1, 0L);\n      case 108:\n         return jjMoveStringLiteralDfa3_0(active0, 0x140000L, active1, 0L);\n      case 109:\n         return jjMoveStringLiteralDfa3_0(active0, 0x2000000000480L, active1, 0L);\n      case 110:\n         if ((active0 & 0x1000000000L) != 0L)\n         {\n            jjmatchedKind = 36;\n            jjmatchedPos = 2;\n         }\n         return jjMoveStringLiteralDfa3_0(active0, 0x8c00200040L, active1, 0L);\n      case 111:\n         return jjMoveStringLiteralDfa3_0(active0, 0x18000000800030L, active1, 0x1L);\n      case 112:\n         if ((active0 & 0x200000000L) != 0L)\n            return jjStartNfaWithStates_0(2, 33, 23);\n         return jjMoveStringLiteralDfa3_0(active0, 0x4000000000000L, active1, 0L);\n      case 114:\n         return jjMoveStringLiteralDfa3_0(active0, 0x80000L, active1, 0L);\n      case 115:\n         return jjMoveStringLiteralDfa3_0(active0, 0x30000000000L, active1, 0x2L);\n      case 116:\n         if ((active0 & 0x10000000L) != 0L)\n            return jjStartNfaWithStates_0(2, 28, 23);\n         return jjMoveStringLiteralDfa3_0(active0, 0x40000000000000L, active1, 0L);\n      case 117:\n         return jjMoveStringLiteralDfa3_0(active0, 0x200L, active1, 0x4L);\n      case 118:\n         return jjMoveStringLiteralDfa3_0(active0, 0x4000000L, active1, 0L);\n      case 119:\n         return jjMoveStringLiteralDfa3_0(active0, 0x80000000000000L, active1, 0L);\n      case 120:\n         if ((active0 & 0x100000000L) != 0L)\n         {\n            jjmatchedKind = 32;\n            jjmatchedPos = 2;\n         }\n         return jjMoveStringLiteralDfa3_0(active0, 0xc0000000L, active1, 0L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(1, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa3_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(1, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(2, active0, active1);\n      return 3;\n   }\n   switch(curChar)\n   {\n      case 97:\n         return jjMoveStringLiteralDfa4_0(active0, 0x80000004000000L, active1, 0L);\n      case 98:\n         if ((active0 & 0x10000000000000L) != 0L)\n         {\n            jjmatchedKind = 52;\n            jjmatchedPos = 3;\n         }\n         return jjMoveStringLiteralDfa4_0(active0, 0x8000000800200L, active1, 0L);\n      case 99:\n         if ((active0 & 0x80L) != 0L)\n            return jjStartNfaWithStates_0(3, 7, 23);\n         else if ((active0 & 0x400L) != 0L)\n            return jjStartNfaWithStates_0(3, 10, 23);\n         else if ((active0 & 0x200000L) != 0L)\n            return jjStartNfaWithStates_0(3, 21, 23);\n         return jjMoveStringLiteralDfa4_0(active0, 0x20L, active1, 0x1L);\n      case 100:\n         return jjMoveStringLiteralDfa4_0(active0, 0x2008000000000L, active1, 0L);\n      case 101:\n         if ((active0 & 0x40000000000000L) != 0L)\n            return jjStartNfaWithStates_0(3, 54, 23);\n         else if ((active1 & 0x4L) != 0L)\n            return jjStartNfaWithStates_0(3, 66, 23);\n         return jjMoveStringLiteralDfa4_0(active0, 0x30020000000L, active1, 0L);\n      case 105:\n         return jjMoveStringLiteralDfa4_0(active0, 0x3000L, active1, 0L);\n      case 108:\n         if ((active0 & 0x10L) != 0L)\n            return jjStartNfaWithStates_0(3, 4, 23);\n         break;\n      case 109:\n         return jjMoveStringLiteralDfa4_0(active0, 0xcc0084000L, active1, 0L);\n      case 110:\n         if ((active0 & 0x800000000000L) != 0L)\n         {\n            jjmatchedKind = 47;\n            jjmatchedPos = 3;\n         }\n         else if ((active0 & 0x2000000000000000L) != 0L)\n         {\n            jjmatchedKind = 61;\n            jjmatchedPos = 3;\n         }\n         return jjMoveStringLiteralDfa4_0(active0, 0x1800600000000000L, active1, 0L);\n      case 111:\n         return jjMoveStringLiteralDfa4_0(active0, 0x8000L, active1, 0L);\n      case 114:\n         return jjMoveStringLiteralDfa4_0(active0, 0x10000L, active1, 0L);\n      case 115:\n         return jjMoveStringLiteralDfa4_0(active0, 0x60040L, active1, 0L);\n      case 116:\n         if ((active0 & 0x2000000L) != 0L)\n            return jjStartNfaWithStates_0(3, 25, 23);\n         return jjMoveStringLiteralDfa4_0(active0, 0x4000000100000L, active1, 0x2L);\n      case 117:\n         return jjMoveStringLiteralDfa4_0(active0, 0x2000000000L, active1, 0L);\n      case 120:\n         if ((active0 & 0x100000000000L) != 0L)\n         {\n            jjmatchedKind = 44;\n            jjmatchedPos = 3;\n         }\n         else if ((active0 & 0x400000000000000L) != 0L)\n         {\n            jjmatchedKind = 58;\n            jjmatchedPos = 3;\n         }\n         return jjMoveStringLiteralDfa4_0(active0, 0x3000c0000000000L, active1, 0L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(2, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa4_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(2, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(3, active0, active1);\n      return 4;\n   }\n   switch(curChar)\n   {\n      case 97:\n         if ((active0 & 0x4000000000000L) != 0L)\n            return jjStartNfaWithStates_0(4, 50, 23);\n         return jjMoveStringLiteralDfa5_0(active0, 0x8000440800000L, active1, 0L);\n      case 98:\n         return jjMoveStringLiteralDfa5_0(active0, 0x8000L, active1, 0L);\n      case 101:\n         if ((active0 & 0x40000L) != 0L)\n            return jjStartNfaWithStates_0(4, 18, 23);\n         return jjMoveStringLiteralDfa5_0(active0, 0x8000110000L, active1, 0x2L);\n      case 104:\n         return jjMoveStringLiteralDfa5_0(active0, 0L, active1, 0x1L);\n      case 105:\n         return jjMoveStringLiteralDfa5_0(active0, 0x880000000L, active1, 0L);\n      case 107:\n         if ((active0 & 0x20L) != 0L)\n            return jjStartNfaWithStates_0(4, 5, 23);\n         break;\n      case 108:\n         if ((active0 & 0x20000000L) != 0L)\n            return jjStartNfaWithStates_0(4, 29, 23);\n         return jjMoveStringLiteralDfa5_0(active0, 0x2000000200L, active1, 0L);\n      case 109:\n         return jjMoveStringLiteralDfa5_0(active0, 0x1b006c0000000000L, active1, 0L);\n      case 110:\n         return jjMoveStringLiteralDfa5_0(active0, 0x3000L, active1, 0L);\n      case 111:\n         return jjMoveStringLiteralDfa5_0(active0, 0x4000L, active1, 0L);\n      case 112:\n         if ((active0 & 0x2000000000000L) != 0L)\n            return jjStartNfaWithStates_0(4, 49, 23);\n         break;\n      case 114:\n         return jjMoveStringLiteralDfa5_0(active0, 0x80030004000000L, active1, 0L);\n      case 116:\n         if ((active0 & 0x40L) != 0L)\n            return jjStartNfaWithStates_0(4, 6, 23);\n         break;\n      case 117:\n         return jjMoveStringLiteralDfa5_0(active0, 0x80000L, active1, 0L);\n      case 121:\n         return jjMoveStringLiteralDfa5_0(active0, 0x20000L, active1, 0L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(3, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa5_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(3, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(4, active0, active1);\n      return 5;\n   }\n   switch(curChar)\n   {\n      case 97:\n         return jjMoveStringLiteralDfa6_0(active0, 0x900240000000000L, active1, 0x1L);\n      case 98:\n         return jjMoveStringLiteralDfa6_0(active0, 0x8000000000000L, active1, 0L);\n      case 100:\n         return jjMoveStringLiteralDfa6_0(active0, 0x80000000004000L, active1, 0L);\n      case 101:\n         if ((active0 & 0x200L) != 0L)\n            return jjStartNfaWithStates_0(5, 9, 23);\n         else if ((active0 & 0x2000000000L) != 0L)\n            return jjStartNfaWithStates_0(5, 37, 23);\n         break;\n      case 105:\n         return jjMoveStringLiteralDfa6_0(active0, 0x1200480004001000L, active1, 0L);\n      case 108:\n         if ((active0 & 0x800000L) != 0L)\n            return jjStartNfaWithStates_0(5, 23, 23);\n         return jjMoveStringLiteralDfa6_0(active0, 0x80000L, active1, 0L);\n      case 109:\n         if ((active1 & 0x2L) != 0L)\n            return jjStartNfaWithStates_0(5, 65, 23);\n         break;\n      case 110:\n         if ((active0 & 0x80000000L) != 0L)\n            return jjStartNfaWithStates_0(5, 31, 23);\n         else if ((active0 & 0x800000000L) != 0L)\n            return jjStartNfaWithStates_0(5, 35, 23);\n         break;\n      case 114:\n         if ((active0 & 0x100000L) != 0L)\n            return jjStartNfaWithStates_0(5, 20, 23);\n         break;\n      case 115:\n         return jjMoveStringLiteralDfa6_0(active0, 0x28000L, active1, 0L);\n      case 116:\n         return jjMoveStringLiteralDfa6_0(active0, 0x8000000000L, active1, 0L);\n      case 118:\n         return jjMoveStringLiteralDfa6_0(active0, 0x30000002000L, active1, 0L);\n      case 119:\n         return jjMoveStringLiteralDfa6_0(active0, 0x10000L, active1, 0L);\n      case 120:\n         if ((active0 & 0x40000000L) != 0L)\n            return jjStartNfaWithStates_0(5, 30, 23);\n         else if ((active0 & 0x400000000L) != 0L)\n            return jjStartNfaWithStates_0(5, 34, 23);\n         break;\n      default :\n         break;\n   }\n   return jjStartNfa_0(4, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa6_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(4, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(5, active0, active1);\n      return 6;\n   }\n   switch(curChar)\n   {\n      case 97:\n         if ((active0 & 0x80000L) != 0L)\n            return jjStartNfaWithStates_0(6, 19, 23);\n         return jjMoveStringLiteralDfa7_0(active0, 0x30004012000L, active1, 0L);\n      case 101:\n         return jjMoveStringLiteralDfa7_0(active0, 0x8000008000L, active1, 0L);\n      case 105:\n         return jjMoveStringLiteralDfa7_0(active0, 0x8000000000000L, active1, 0L);\n      case 110:\n         if ((active0 & 0x80000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 43, 23);\n         else if ((active0 & 0x400000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 46, 23);\n         else if ((active0 & 0x200000000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 57, 23);\n         else if ((active0 & 0x1000000000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 60, 23);\n         break;\n      case 115:\n         if ((active0 & 0x80000000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 55, 23);\n         return jjMoveStringLiteralDfa7_0(active0, 0L, active1, 0x1L);\n      case 116:\n         if ((active0 & 0x1000L) != 0L)\n            return jjStartNfaWithStates_0(6, 12, 23);\n         return jjMoveStringLiteralDfa7_0(active0, 0x20000L, active1, 0L);\n      case 117:\n         return jjMoveStringLiteralDfa7_0(active0, 0x4000L, active1, 0L);\n      case 120:\n         if ((active0 & 0x40000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 42, 23);\n         else if ((active0 & 0x200000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 45, 23);\n         else if ((active0 & 0x100000000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 56, 23);\n         else if ((active0 & 0x800000000000000L) != 0L)\n            return jjStartNfaWithStates_0(6, 59, 23);\n         break;\n      default :\n         break;\n   }\n   return jjStartNfa_0(5, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa7_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(5, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(6, active0, active1);\n      return 7;\n   }\n   switch(curChar)\n   {\n      case 98:\n         return jjMoveStringLiteralDfa8_0(active0, 0x30000000000L, active1, 0L);\n      case 101:\n         return jjMoveStringLiteralDfa8_0(active0, 0x20000L, active1, 0L);\n      case 108:\n         return jjMoveStringLiteralDfa8_0(active0, 0x8000000004000L, active1, 0L);\n      case 110:\n         return jjMoveStringLiteralDfa8_0(active0, 0x4000000L, active1, 0L);\n      case 114:\n         return jjMoveStringLiteralDfa8_0(active0, 0x800001a000L, active1, 0L);\n      case 116:\n         return jjMoveStringLiteralDfa8_0(active0, 0L, active1, 0x1L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(6, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa8_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(6, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(7, active0, active1);\n      return 8;\n   }\n   switch(curChar)\n   {\n      case 100:\n         return jjMoveStringLiteralDfa9_0(active0, 0x10000L, active1, 0L);\n      case 101:\n         if ((active0 & 0x4000L) != 0L)\n            return jjStartNfaWithStates_0(8, 14, 23);\n         break;\n      case 105:\n         return jjMoveStringLiteralDfa9_0(active0, 0x8000000002000L, active1, 0x1L);\n      case 108:\n         return jjMoveStringLiteralDfa9_0(active0, 0x30000000000L, active1, 0L);\n      case 109:\n         if ((active0 & 0x20000L) != 0L)\n            return jjStartNfaWithStates_0(8, 17, 23);\n         return jjMoveStringLiteralDfa9_0(active0, 0x8000000000L, active1, 0L);\n      case 116:\n         if ((active0 & 0x4000000L) != 0L)\n            return jjStartNfaWithStates_0(8, 26, 23);\n         break;\n      case 118:\n         return jjMoveStringLiteralDfa9_0(active0, 0x8000L, active1, 0L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(7, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa9_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(7, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(8, active0, active1);\n      return 9;\n   }\n   switch(curChar)\n   {\n      case 97:\n         return jjMoveStringLiteralDfa10_0(active0, 0xa000L, active1, 0L);\n      case 99:\n         if ((active1 & 0x1L) != 0L)\n            return jjStartNfaWithStates_0(9, 64, 23);\n         break;\n      case 101:\n         if ((active0 & 0x10000000000L) != 0L)\n         {\n            jjmatchedKind = 40;\n            jjmatchedPos = 9;\n         }\n         return jjMoveStringLiteralDfa10_0(active0, 0x20000000000L, active1, 0L);\n      case 105:\n         return jjMoveStringLiteralDfa10_0(active0, 0x8000000000L, active1, 0L);\n      case 115:\n         if ((active0 & 0x10000L) != 0L)\n            return jjStartNfaWithStates_0(9, 16, 23);\n         return jjMoveStringLiteralDfa10_0(active0, 0x8000000000000L, active1, 0L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(8, active0, active1);\n}\nstatic private int jjMoveStringLiteralDfa10_0(long old0, long active0, long old1, long active1){\n   if (((active0 &= old0) | (active1 &= old1)) == 0L)\n      return jjStartNfa_0(8, old0, old1);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(9, active0, 0L);\n      return 10;\n   }\n   switch(curChar)\n   {\n      case 98:\n         return jjMoveStringLiteralDfa11_0(active0, 0x8000L);\n      case 110:\n         return jjMoveStringLiteralDfa11_0(active0, 0x8000002000L);\n      case 115:\n         if ((active0 & 0x20000000000L) != 0L)\n            return jjStartNfaWithStates_0(10, 41, 23);\n         break;\n      case 116:\n         return jjMoveStringLiteralDfa11_0(active0, 0x8000000000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(9, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa11_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(9, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(10, active0, 0L);\n      return 11;\n   }\n   switch(curChar)\n   {\n      case 105:\n         return jjMoveStringLiteralDfa12_0(active0, 0x8008000000000L);\n      case 108:\n         return jjMoveStringLiteralDfa12_0(active0, 0x8000L);\n      case 116:\n         if ((active0 & 0x2000L) != 0L)\n            return jjStartNfaWithStates_0(11, 13, 23);\n         break;\n      default :\n         break;\n   }\n   return jjStartNfa_0(10, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa12_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(10, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(11, active0, 0L);\n      return 12;\n   }\n   switch(curChar)\n   {\n      case 99:\n         if ((active0 & 0x8000000000000L) != 0L)\n            return jjStartNfaWithStates_0(12, 51, 23);\n         break;\n      case 101:\n         return jjMoveStringLiteralDfa13_0(active0, 0x8000L);\n      case 115:\n         return jjMoveStringLiteralDfa13_0(active0, 0x8000000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(11, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa13_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(11, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(12, active0, 0L);\n      return 13;\n   }\n   switch(curChar)\n   {\n      case 115:\n         if ((active0 & 0x8000L) != 0L)\n            return jjStartNfaWithStates_0(13, 15, 23);\n         break;\n      case 116:\n         return jjMoveStringLiteralDfa14_0(active0, 0x8000000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(12, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa14_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(12, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(13, active0, 0L);\n      return 14;\n   }\n   switch(curChar)\n   {\n      case 105:\n         return jjMoveStringLiteralDfa15_0(active0, 0x8000000000L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(13, active0, 0L);\n}\nstatic private int jjMoveStringLiteralDfa15_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(13, old0, 0L);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(14, active0, 0L);\n      return 15;\n   }\n   switch(curChar)\n   {\n      case 99:\n         if ((active0 & 0x8000000000L) != 0L)\n            return jjStartNfaWithStates_0(15, 39, 23);\n         break;\n      default :\n         break;\n   }\n   return jjStartNfa_0(14, active0, 0L);\n}\nstatic private int jjStartNfaWithStates_0(int pos, int kind, int state)\n{\n   jjmatchedKind = kind;\n   jjmatchedPos = pos;\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) { return pos + 1; }\n   return jjMoveNfa_0(state, pos + 1);\n}\nstatic final long[] jjbitVec0 = {\n   0xfffffffffffffffeL, 0xffffffffffffffffL, 0xffffffffffffffffL, 0xffffffffffffffffL\n};\nstatic final long[] jjbitVec2 = {\n   0x0L, 0x0L, 0xffffffffffffffffL, 0xffffffffffffffffL\n};\nstatic private int jjMoveNfa_0(int startState, int curPos)\n{\n   int startsAt = 0;\n   jjnewStateCnt = 23;\n   int i = 1;\n   jjstateSet[0] = startState;\n   int kind = 0x7fffffff;\n   for (;;)\n   {\n      if (++jjround == 0x7fffffff)\n         ReInitRounds();\n      if (curChar < 64)\n      {\n         long l = 1L << curChar;\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 23:\n                  if ((0x3ff000000000000L & l) != 0L)\n                  {\n                     if (kind > 107)\n                        kind = 107;\n                     { jjCheckNAdd(22); }\n                  }\n                  else if (curChar == 39)\n                  {\n                     if (kind > 106)\n                        kind = 106;\n                  }\n                  if ((0x3ff000000000000L & l) != 0L)\n                     { jjCheckNAddTwoStates(20, 21); }\n                  break;\n               case 0:\n                  if ((0x3ff000000000000L & l) != 0L)\n                  {\n                     if (kind > 105)\n                        kind = 105;\n                     { jjCheckNAddStates(0, 3); }\n                  }\n                  else if ((0x100002600L & l) != 0L)\n                  {\n                     if (kind > 1)\n                        kind = 1;\n                  }\n                  else if (curChar == 35)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  else if (curChar == 46)\n                     { jjCheckNAdd(11); }\n                  else if (curChar == 47)\n                     jjstateSet[jjnewStateCnt++] = 1;\n                  if ((0x3fe000000000000L & l) != 0L)\n                  {\n                     if (kind > 104)\n                        kind = 104;\n                     { jjCheckNAdd(8); }\n                  }\n                  else if (curChar == 48)\n                  {\n                     if (kind > 104)\n                        kind = 104;\n                  }\n                  break;\n               case 1:\n                  if (curChar != 47)\n                     break;\n                  if (kind > 2)\n                     kind = 2;\n                  { jjCheckNAddStates(4, 6); }\n                  break;\n               case 2:\n                  if ((0xffffffffffffdbffL & l) == 0L)\n                     break;\n                  if (kind > 2)\n                     kind = 2;\n                  { jjCheckNAddStates(4, 6); }\n                  break;\n               case 3:\n                  if ((0x2400L & l) != 0L && kind > 2)\n                     kind = 2;\n                  break;\n               case 4:\n                  if (curChar == 10 && kind > 2)\n                     kind = 2;\n                  break;\n               case 5:\n                  if (curChar == 13)\n                     jjstateSet[jjnewStateCnt++] = 4;\n                  break;\n               case 6:\n                  if (curChar == 47)\n                     jjstateSet[jjnewStateCnt++] = 1;\n                  break;\n               case 7:\n                  if ((0x3fe000000000000L & l) == 0L)\n                     break;\n                  if (kind > 104)\n                     kind = 104;\n                  { jjCheckNAdd(8); }\n                  break;\n               case 8:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 104)\n                     kind = 104;\n                  { jjCheckNAdd(8); }\n                  break;\n               case 9:\n                  if (curChar == 48 && kind > 104)\n                     kind = 104;\n                  break;\n               case 10:\n                  if (curChar == 46)\n                     { jjCheckNAdd(11); }\n                  break;\n               case 11:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 105)\n                     kind = 105;\n                  { jjCheckNAddTwoStates(11, 12); }\n                  break;\n               case 13:\n                  if ((0x280000000000L & l) != 0L)\n                     { jjCheckNAdd(14); }\n                  break;\n               case 14:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 105)\n                     kind = 105;\n                  { jjCheckNAdd(14); }\n                  break;\n               case 15:\n                  if (curChar == 35)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  break;\n               case 16:\n                  if ((0xfffffff7ffffffffL & l) != 0L)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  break;\n               case 17:\n                  if (curChar == 35 && kind > 108)\n                     kind = 108;\n                  break;\n               case 18:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 105)\n                     kind = 105;\n                  { jjCheckNAddStates(0, 3); }\n                  break;\n               case 20:\n                  if ((0x3ff000000000000L & l) != 0L)\n                     { jjCheckNAddTwoStates(20, 21); }\n                  break;\n               case 21:\n                  if (curChar == 39 && kind > 106)\n                     kind = 106;\n                  break;\n               case 22:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 107)\n                     kind = 107;\n                  { jjCheckNAdd(22); }\n                  break;\n               default : break;\n            }\n         } while(i != startsAt);\n      }\n      else if (curChar < 128)\n      {\n         long l = 1L << (curChar & 077);\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 23:\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                  {\n                     if (kind > 107)\n                        kind = 107;\n                     { jjCheckNAdd(22); }\n                  }\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                     { jjCheckNAddTwoStates(20, 21); }\n                  break;\n               case 0:\n                  if ((0x7fffffe87fffffeL & l) == 0L)\n                     break;\n                  if (kind > 107)\n                     kind = 107;\n                  { jjCheckNAddStates(7, 9); }\n                  break;\n               case 2:\n                  if (kind > 2)\n                     kind = 2;\n                  { jjAddStates(4, 6); }\n                  break;\n               case 12:\n                  if ((0x2000000020L & l) != 0L)\n                     { jjAddStates(10, 11); }\n                  break;\n               case 16:\n                  { jjAddStates(12, 13); }\n                  break;\n               case 20:\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                     { jjCheckNAddTwoStates(20, 21); }\n                  break;\n               case 22:\n                  if ((0x7fffffe87fffffeL & l) == 0L)\n                     break;\n                  if (kind > 107)\n                     kind = 107;\n                  { jjCheckNAdd(22); }\n                  break;\n               default : break;\n            }\n         } while(i != startsAt);\n      }\n      else\n      {\n         int hiByte = (curChar >> 8);\n         int i1 = hiByte >> 6;\n         long l1 = 1L << (hiByte & 077);\n         int i2 = (curChar & 0xff) >> 6;\n         long l2 = 1L << (curChar & 077);\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 2:\n                  if (!jjCanMove_0(hiByte, i1, i2, l1, l2))\n                     break;\n                  if (kind > 2)\n                     kind = 2;\n                  { jjAddStates(4, 6); }\n                  break;\n               case 16:\n                  if (jjCanMove_0(hiByte, i1, i2, l1, l2))\n                     { jjAddStates(12, 13); }\n                  break;\n               default : if (i1 == 0 || l1 == 0 || i2 == 0 ||  l2 == 0) break; else break;\n            }\n         } while(i != startsAt);\n      }\n      if (kind != 0x7fffffff)\n      {\n         jjmatchedKind = kind;\n         jjmatchedPos = curPos;\n         kind = 0x7fffffff;\n      }\n      ++curPos;\n      if ((i = jjnewStateCnt) == (startsAt = 23 - (jjnewStateCnt = startsAt)))\n         return curPos;\n      try { curChar = input_stream.readChar(); }\n      catch(java.io.IOException e) { return curPos; }\n   }\n}\n\n/** Token literal values. */\npublic static final String[] jjstrLiteralImages = {\n\"\", null, null, \"\\101\", \"\\142\\157\\157\\154\", \"\\143\\154\\157\\143\\153\", \n\"\\143\\157\\156\\163\\164\", \"\\143\\164\\155\\143\", \"\\103\", \"\\144\\157\\165\\142\\154\\145\", \"\\144\\164\\155\\143\", \n\"\\105\", \"\\145\\156\\144\\151\\156\\151\\164\", \n\"\\145\\156\\144\\151\\156\\166\\141\\162\\151\\141\\156\\164\", \"\\145\\156\\144\\155\\157\\144\\165\\154\\145\", \n\"\\145\\156\\144\\157\\142\\163\\145\\162\\166\\141\\142\\154\\145\\163\", \"\\145\\156\\144\\162\\145\\167\\141\\162\\144\\163\", \n\"\\145\\156\\144\\163\\171\\163\\164\\145\\155\", \"\\146\\141\\154\\163\\145\", \"\\146\\157\\162\\155\\165\\154\\141\", \n\"\\146\\151\\154\\164\\145\\162\", \"\\146\\165\\156\\143\", \"\\106\", \"\\147\\154\\157\\142\\141\\154\", \"\\107\", \n\"\\151\\156\\151\\164\", \"\\151\\156\\166\\141\\162\\151\\141\\156\\164\", \"\\111\", \"\\151\\156\\164\", \n\"\\154\\141\\142\\145\\154\", \"\\155\\141\\170\\155\\141\\170\", \"\\155\\141\\170\\155\\151\\156\", \"\\155\\141\\170\", \n\"\\155\\144\\160\", \"\\155\\151\\156\\155\\141\\170\", \"\\155\\151\\156\\155\\151\\156\", \"\\155\\151\\156\", \n\"\\155\\157\\144\\165\\154\\145\", \"\\130\", \"\\156\\157\\156\\144\\145\\164\\145\\162\\155\\151\\156\\151\\163\\164\\151\\143\", \n\"\\157\\142\\163\\145\\162\\166\\141\\142\\154\\145\", \"\\157\\142\\163\\145\\162\\166\\141\\142\\154\\145\\163\", \n\"\\120\\155\\141\\170\\155\\141\\170\", \"\\120\\155\\141\\170\\155\\151\\156\", \"\\120\\155\\141\\170\", \n\"\\120\\155\\151\\156\\155\\141\\170\", \"\\120\\155\\151\\156\\155\\151\\156\", \"\\120\\155\\151\\156\", \"\\120\", \n\"\\160\\157\\155\\144\\160\", \"\\160\\157\\160\\164\\141\", \n\"\\160\\162\\157\\142\\141\\142\\151\\154\\151\\163\\164\\151\\143\", \"\\160\\162\\157\\142\", \"\\160\\164\\141\", \"\\162\\141\\164\\145\", \n\"\\162\\145\\167\\141\\162\\144\\163\", \"\\122\\155\\141\\170\\155\\141\\170\", \"\\122\\155\\141\\170\\155\\151\\156\", \n\"\\122\\155\\141\\170\", \"\\122\\155\\151\\156\\155\\141\\170\", \"\\122\\155\\151\\156\\155\\151\\156\", \n\"\\122\\155\\151\\156\", \"\\122\", \"\\123\", \"\\163\\164\\157\\143\\150\\141\\163\\164\\151\\143\", \n\"\\163\\171\\163\\164\\145\\155\", \"\\164\\162\\165\\145\", \"\\125\", \"\\127\", \"\\41\", \"\\46\", \"\\174\", \"\\75\\76\", \n\"\\74\\75\\76\", \"\\55\\76\", \"\\72\", \"\\73\", \"\\54\", \"\\56\\56\", \"\\50\", \"\\51\", \"\\133\", \"\\135\", \n\"\\133\\133\", \"\\135\\135\", \"\\173\", \"\\175\", \"\\75\", \"\\41\\75\", \"\\74\", \"\\76\", \"\\74\\74\", \"\\76\\76\", \n\"\\74\\75\", \"\\76\\75\", \"\\53\", \"\\55\", \"\\52\", \"\\57\", \"\\136\", \"\\47\", \"\\74\\55\", \"\\77\", \"\\42\", \nnull, null, null, null, null, null, };\nstatic protected Token jjFillToken()\n{\n   final Token t;\n   final String curTokenImage;\n   final int beginLine;\n   final int endLine;\n   final int beginColumn;\n   final int endColumn;\n   String im = jjstrLiteralImages[jjmatchedKind];\n   curTokenImage = (im == null) ? input_stream.GetImage() : im;\n   beginLine = input_stream.getBeginLine();\n   beginColumn = input_stream.getBeginColumn();\n   endLine = input_stream.getEndLine();\n   endColumn = input_stream.getEndColumn();\n   t = Token.newToken(jjmatchedKind, curTokenImage);\n\n   t.beginLine = beginLine;\n   t.endLine = endLine;\n   t.beginColumn = beginColumn;\n   t.endColumn = endColumn;\n\n   return t;\n}\nstatic final int[] jjnextStates = {\n   10, 11, 12, 18, 2, 3, 5, 20, 21, 22, 13, 14, 16, 17, \n};\nprivate static final boolean jjCanMove_0(int hiByte, int i1, int i2, long l1, long l2)\n{\n   switch(hiByte)\n   {\n      case 0:\n         return ((jjbitVec2[i2] & l2) != 0L);\n      default :\n         if ((jjbitVec0[i1] & l1) != 0L)\n            return true;\n         return false;\n   }\n}\n\nstatic int curLexState = 0;\nstatic int defaultLexState = 0;\nstatic int jjnewStateCnt;\nstatic int jjround;\nstatic int jjmatchedPos;\nstatic int jjmatchedKind;\n\n/** Get the next Token. */\npublic static Token getNextToken() \n{\n  Token specialToken = null;\n  Token matchedToken;\n  int curPos = 0;\n\n  EOFLoop :\n  for (;;)\n  {\n   try\n   {\n      curChar = input_stream.BeginToken();\n   }\n   catch(Exception e)\n   {\n      jjmatchedKind = 0;\n      jjmatchedPos = -1;\n      matchedToken = jjFillToken();\n      matchedToken.specialToken = specialToken;\n      return matchedToken;\n   }\n\n   jjmatchedKind = 0x7fffffff;\n   jjmatchedPos = 0;\n   curPos = jjMoveStringLiteralDfa0_0();\n   if (jjmatchedPos == 0 && jjmatchedKind > 109)\n   {\n      jjmatchedKind = 109;\n   }\n   if (jjmatchedKind != 0x7fffffff)\n   {\n      if (jjmatchedPos + 1 < curPos)\n         input_stream.backup(curPos - jjmatchedPos - 1);\n      if ((jjtoToken[jjmatchedKind >> 6] & (1L << (jjmatchedKind & 077))) != 0L)\n      {\n         matchedToken = jjFillToken();\n         matchedToken.specialToken = specialToken;\n         return matchedToken;\n      }\n      else\n      {\n         if ((jjtoSpecial[jjmatchedKind >> 6] & (1L << (jjmatchedKind & 077))) != 0L)\n         {\n            matchedToken = jjFillToken();\n            if (specialToken == null)\n               specialToken = matchedToken;\n            else\n            {\n               matchedToken.specialToken = specialToken;\n               specialToken = (specialToken.next = matchedToken);\n            }\n         }\n         continue EOFLoop;\n      }\n   }\n   int error_line = input_stream.getEndLine();\n   int error_column = input_stream.getEndColumn();\n   String error_after = null;\n   boolean EOFSeen = false;\n   try { input_stream.readChar(); input_stream.backup(1); }\n   catch (java.io.IOException e1) {\n      EOFSeen = true;\n      error_after = curPos <= 1 ? \"\" : input_stream.GetImage();\n      if (curChar == '\\n' || curChar == '\\r') {\n         error_line++;\n         error_column = 0;\n      }\n      else\n         error_column++;\n   }\n   if (!EOFSeen) {\n      input_stream.backup(1);\n      error_after = curPos <= 1 ? \"\" : input_stream.GetImage();\n   }\n   throw new TokenMgrError(EOFSeen, curLexState, error_line, error_column, error_after, curChar, TokenMgrError.LEXICAL_ERROR);\n  }\n}\n\nstatic void SkipLexicalActions(Token matchedToken)\n{\n   switch(jjmatchedKind)\n   {\n      default :\n         break;\n   }\n}\nstatic void MoreLexicalActions()\n{\n   jjimageLen += (lengthOfMatch = jjmatchedPos + 1);\n   switch(jjmatchedKind)\n   {\n      default :\n         break;\n   }\n}\nstatic void TokenLexicalActions(Token matchedToken)\n{\n   switch(jjmatchedKind)\n   {\n      default :\n         break;\n   }\n}\nstatic private void jjCheckNAdd(int state)\n{\n   if (jjrounds[state] != jjround)\n   {\n      jjstateSet[jjnewStateCnt++] = state;\n      jjrounds[state] = jjround;\n   }\n}\nstatic private void jjAddStates(int start, int end)\n{\n   do {\n      jjstateSet[jjnewStateCnt++] = jjnextStates[start];\n   } while (start++ != end);\n}\nstatic private void jjCheckNAddTwoStates(int state1, int state2)\n{\n   jjCheckNAdd(state1);\n   jjCheckNAdd(state2);\n}\n\nstatic private void jjCheckNAddStates(int start, int end)\n{\n   do {\n      jjCheckNAdd(jjnextStates[start]);\n   } while (start++ != end);\n}\n\n    /** Constructor. */\n    public PrismParserTokenManager(SimpleCharStream stream){\n\n      if (input_stream != null)\n        throw new TokenMgrError(\"ERROR: Second call to constructor of static lexer. You must use ReInit() to initialize the static variables.\", TokenMgrError.STATIC_LEXER_ERROR);\n\n    input_stream = stream;\n  }\n\n  /** Constructor. */\n  public PrismParserTokenManager (SimpleCharStream stream, int lexState){\n    ReInit(stream);\n    SwitchTo(lexState);\n  }\n\n  /** Reinitialise parser. */\n  \n  static public void ReInit(SimpleCharStream stream)\n  {\n\n\n    jjmatchedPos =\n    jjnewStateCnt =\n    0;\n    curLexState = defaultLexState;\n    input_stream = stream;\n    ReInitRounds();\n  }\n\n  static private void ReInitRounds()\n  {\n    int i;\n    jjround = 0x80000001;\n    for (i = 23; i-- > 0;)\n      jjrounds[i] = 0x80000000;\n  }\n\n  /** Reinitialise parser. */\n  static public void ReInit(SimpleCharStream stream, int lexState)\n  \n  {\n    ReInit(stream);\n    SwitchTo(lexState);\n  }\n\n  /** Switch to specified lex state. */\n  public static void SwitchTo(int lexState)\n  {\n    if (lexState >= 1 || lexState < 0)\n      throw new TokenMgrError(\"Error: Ignoring invalid lexical state : \" + lexState + \". State unchanged.\", TokenMgrError.INVALID_LEXICAL_STATE);\n    else\n      curLexState = lexState;\n  }\n\n\n/** Lexer state names. */\npublic static final String[] lexStateNames = {\n   \"DEFAULT\",\n};\n\n/** Lex State array. */\npublic static final int[] jjnewLexState = {\n   -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, \n   -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, \n   -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, \n   -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, \n   -1, -1, -1, -1, -1, -1, -1, -1, -1, -1, \n};\nstatic final long[] jjtoToken = {\n   0xfffffffffffffff9L, 0x3fffffffffffL, \n};\nstatic final long[] jjtoSkip = {\n   0x6L, 0x0L, \n};\nstatic final long[] jjtoSpecial = {\n   0x6L, 0x0L, \n};\nstatic final long[] jjtoMore = {\n   0x0L, 0x0L, \n};\n    static protected SimpleCharStream  input_stream;\n\n    static private final int[] jjrounds = new int[23];\n    static private final int[] jjstateSet = new int[2 * 23];\n    private static final StringBuilder jjimage = new StringBuilder();\n    private static StringBuilder image = jjimage;\n    private static int jjimageLen;\n    private static int lengthOfMatch;\n    static protected int curChar;\n}\n"
  },
  {
    "path": "prism/src/parser/PrismSyntaxHighlighter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\nimport java.util.ArrayList;\nimport java.io.*;\n\nimport prism.Prism;\nimport prism.PrismLangException;\n\npublic class PrismSyntaxHighlighter\n{\n\t// token types\n\tpublic static final int PUNCTUATION = 0;\n\tpublic static final int COMMENT = 1;\n\tpublic static final int WHITESPACE = 2;\n\tpublic static final int KEYWORD = 3;\n\tpublic static final int NUMERIC = 4;\n\tpublic static final int IDENTIFIER = 5;\n\tpublic static final int PREPROC = 6;\n\tpublic static final int EOF = 100;\n\t\n\t// output types\n\tprivate static final int ECHO = 0; // for testing mainly\n\tprivate static final int HTML = 1;\n\tprivate static final int LATEX = 2;\n\tprivate static final int PRISMGUI = 3;\n\t\n\t// punctation replacements\n\tprivate static final ArrayList<String> puncReplaceTo_ECHO , puncReplaceFrom_ECHO;\n\tprivate static final ArrayList<String> puncReplaceTo_HTML, puncReplaceFrom_HTML;\n\tprivate static final ArrayList<String> puncReplaceTo_LATEX, puncReplaceFrom_LATEX;\n\tprivate static final ArrayList<String> puncReplaceTo_LATEXMATHS, puncReplaceFrom_LATEXMATHS;\n\tprivate static final ArrayList<String> puncReplaceTo_PRISMGUI, puncReplaceFrom_PRISMGUI;\n\tprivate static int quoteAlternator = 1;\n\t\n\tstatic {\n\t\tpuncReplaceFrom_ECHO = new ArrayList<String>(); puncReplaceTo_ECHO = new ArrayList<String>();\n\t\tpuncReplaceFrom_HTML = new ArrayList<String>(); puncReplaceTo_HTML = new ArrayList<String>();\n\t\tpuncReplaceFrom_HTML.add(\"&\"); puncReplaceTo_HTML.add(\"&amp;\");\n\t\tpuncReplaceFrom_HTML.add(\"<\"); puncReplaceTo_HTML.add(\"&lt;\");\n\t\tpuncReplaceFrom_HTML.add(\">\"); puncReplaceTo_HTML.add(\"&gt;\");\n\t\tpuncReplaceFrom_LATEX = new ArrayList<String>(); puncReplaceTo_LATEX = new ArrayList<String>();\n\t\tpuncReplaceFrom_LATEX.add(\"\\\\{\"); puncReplaceTo_LATEX.add(\"\\\\\\\\{\");\n\t\tpuncReplaceFrom_LATEX.add(\"\\\\}\"); puncReplaceTo_LATEX.add(\"\\\\\\\\}\");\n\t\tpuncReplaceFrom_LATEX.add(\"&\"); puncReplaceTo_LATEX.add(\"\\\\\\\\&\");\n\t\tpuncReplaceFrom_LATEX.add(\"_\"); puncReplaceTo_LATEX.add(\"\\\\\\\\_\");\n\t\tpuncReplaceFrom_LATEX.add(\"%\"); puncReplaceTo_LATEX.add(\"\\\\\\\\%\");\n\t\tpuncReplaceFrom_LATEX.add(\">=\"); puncReplaceTo_LATEX.add(\"\\\\${\\\\\\\\geq}\\\\$\");\n\t\tpuncReplaceFrom_LATEX.add(\"<=\"); puncReplaceTo_LATEX.add(\"\\\\${\\\\\\\\leq}\\\\$\");\n\t\tpuncReplaceFrom_LATEX.add(\"->\"); puncReplaceTo_LATEX.add(\"\\\\$\\\\\\\\rightarrow\\\\$\");\n\t\tpuncReplaceFrom_LATEX.add(\"=>\"); puncReplaceTo_LATEX.add(\"\\\\$\\\\\\\\Rightarrow\\\\$\");\n\t\tpuncReplaceFrom_LATEX.add(\"=\"); puncReplaceTo_LATEX.add(\"\\\\${=}\\\\$\");\n\t\tpuncReplaceFrom_LATEX.add(\">\"); puncReplaceTo_LATEX.add(\"\\\\${>}\\\\$\");\n\t\tpuncReplaceFrom_LATEX.add(\"<\"); puncReplaceTo_LATEX.add(\"\\\\${<}\\\\$\");\n\t\tpuncReplaceFrom_LATEX.add(\"#\"); puncReplaceTo_LATEX.add(\"\\\\\\\\#\");\n\t\tpuncReplaceFrom_LATEXMATHS = new ArrayList<String>(); puncReplaceTo_LATEXMATHS = new ArrayList<String>();\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"\\\\{\"); puncReplaceTo_LATEXMATHS.add(\"\\\\\\\\{\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"\\\\}\"); puncReplaceTo_LATEXMATHS.add(\"\\\\\\\\}\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"&\"); puncReplaceTo_LATEXMATHS.add(\"\\\\\\\\&\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"_\"); puncReplaceTo_LATEXMATHS.add(\"\\\\\\\\_\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"%\"); puncReplaceTo_LATEXMATHS.add(\"\\\\\\\\%\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\">=\"); puncReplaceTo_LATEXMATHS.add(\"{\\\\\\\\geq}\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"<=\"); puncReplaceTo_LATEXMATHS.add(\"{\\\\\\\\leq}\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"->\"); puncReplaceTo_LATEXMATHS.add(\"\\\\\\\\rightarrow\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"=>\"); puncReplaceTo_LATEXMATHS.add(\"\\\\\\\\Rightarrow\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"=\"); puncReplaceTo_LATEXMATHS.add(\"{=}\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\">\"); puncReplaceTo_LATEXMATHS.add(\"{>}\");\n\t\tpuncReplaceFrom_LATEXMATHS.add(\"<\"); puncReplaceTo_LATEXMATHS.add(\"{<}\");\n\t\tpuncReplaceFrom_PRISMGUI = new ArrayList<String>(); puncReplaceTo_PRISMGUI = new ArrayList<String>();\n\t}\n\t\n\t// resulting output\n\tprivate static StringBuffer resStringBuffer;;\n\tprivate static int resNewLine;\n\tprivate static boolean resStart;\n\tprivate static int resTypeArray[];\n\tprivate static int resCharCount;\n\t\n\t// public methods\n\t\n\tpublic static String echoFile(File file) throws FileNotFoundException, PrismLangException\n\t{\n\t\tresStringBuffer = new StringBuffer();\n\t\thighlight(new FileInputStream(file), ECHO);\n\t\treturn resStringBuffer.toString();\n\t}\n\t\n\tpublic static String echoFile(InputStream stream) throws PrismLangException\n\t{\n\t\tresStringBuffer = new StringBuffer();\n\t\thighlight(stream, ECHO);\n\t\treturn resStringBuffer.toString();\n\t}\n\t\n\tpublic static String lineToHtml(String line) throws PrismLangException\n\t{\n\t\tresStringBuffer = new StringBuffer();\n\t\thighlight(new ByteArrayInputStream(line.getBytes()), HTML);\n\t\treturn resStringBuffer.toString();\n\t}\n\t\n\tpublic static String fileToHtml(File file, boolean hf, String cssLoc) throws FileNotFoundException, PrismLangException\n\t{\n\t\tresStringBuffer = new StringBuffer();\n\t\tif (hf) resStringBuffer.append(htmlFileHeader(file.getName(), cssLoc));\n\t\thighlight(new FileInputStream(file), HTML);\n\t\tif (hf) resStringBuffer.append(htmlFileFooter()); \n\t\treturn resStringBuffer.toString();\n\t}\n\t\n\tpublic static String fileToHtml(InputStream stream, boolean hf, String cssLoc) throws PrismLangException\n\t{\n\t\tresStringBuffer = new StringBuffer();\n\t\tif (hf) resStringBuffer.append(htmlFileHeader(\"PRISM Code\", cssLoc)); \n\t\thighlight(stream, HTML);\n\t\tif (hf) resStringBuffer.append(htmlFileFooter()); \n\t\treturn resStringBuffer.toString();\n\t}\n\n\tpublic static String fileToLatex(File file, boolean hf) throws FileNotFoundException, PrismLangException\n\t{\n\t\tresStringBuffer = new StringBuffer();\n\t\tresNewLine = 1;\n\t\tresStart = true;\n\t\tif (hf) resStringBuffer.append(latexFileHeader(file.getName()));\n\t\thighlight(new FileInputStream(file), LATEX);\n\t\tif (hf) resStringBuffer.append(latexFileFooter()); \n\t\treturn resStringBuffer.toString();\n\t}\n\t\n\tpublic static String fileToLatex(InputStream stream, boolean hf) throws PrismLangException\n\t{\n\t\tresStringBuffer = new StringBuffer();\n\t\tresNewLine = 1;\n\t\tresStart = true;\n\t\tif (hf) resStringBuffer.append(latexFileHeader(\"PRISM Code\")); \n\t\thighlight(stream, LATEX);\n\t\tif (hf) resStringBuffer.append(latexFileFooter()); \n\t\treturn resStringBuffer.toString();\n\t}\n\t\n\tpublic static int[] lineForPrismGUI(String line) throws PrismLangException\n\t{\n\t\tresTypeArray = new int[line.length()];\n\t\tresCharCount = 0;\n\t\thighlight(new ByteArrayInputStream(line.getBytes()), PRISMGUI);\n\t\treturn resTypeArray;\n\t}\n\n\t// generate file headers/footers\n\t\n\tprivate static String htmlFileHeader(String title, String cssLoc)\n\t{\n\t\tString s = \"\";\n\t\ts += \"<!DOCTYPE HTML PUBLIC \\\"-//W3C//DTD HTML 4.01 Transitional//EN\\\"\\n\";\n\t\ts += \"\\\"http://www.w3.org/TR/html4/loose.dtd\\\">\\n\";\n\t\t\n\t\ts += \"<html>\" + \"\\n\";\n\t\ts += \"<head>\" + \"\\n\";\n\t\ts += \"<title>\" + \"\\n\";\n\t\ts += title + \"\\n\";\n\t\ts += \"</title>\" + \"\\n\";\n\t\ts += \"<meta http-equiv=\\\"Content-Type\\\" content=\\\"text/html; charset=iso-8859-1\\\">\" + \"\\n\";\n\t\ts += \"<!-- Style sheet \\\"prism.css\\\" can be found in the \\\"etc\\\" directory of the PRISM distribution -->\" + \"\\n\";\n\t\ts += \"<link type=\\\"text/css\\\" rel=\\\"stylesheet\\\" href=\\\"\" + cssLoc + \"\\\">\" + \"\\n\";\n\t\ts += \"</head>\" + \"\\n\";\n\t\ts += \"<body text=\\\"#000000\\\" bgcolor=\\\"#ffffff\\\">\" + \"\\n\";\n\t\ts += \"<pre>\" + \"\\n\";\n\t\t\n\t\treturn s;\n\t}\n\t\n\tprivate static String htmlFileFooter()\n\t{\n\t\tString s = \"\";\n\t\t\n\t\ts += \"</pre>\" + \"\\n\";\n\t\ts += \"</body>\" + \"\\n\";\n\t\ts += \"</html>\" + \"\\n\";\n\t\t\n\t\treturn s;\n\t}\n\n\tprivate static String latexFileHeader(String title)\n\t{\n\t\tString s = \"\";\n\t\t\n\t\ts += \"\\\\centering\" + \"\\n\";\n\t\ts += \"{\\\\scriptsize\" + \"\\n\";\n\t\ts += \"\\\\fbox{\\\\begin{minipage}{6in}\" + \"\\n\";\n\t\ts += \"\\\\begin{tabbing}\" + \"\\n\";\n\t\t//s += \"\\\\quad \\\\=\\\\quad \\\\=\\\\quad \\\\=\\\\quad \\\\=\\\\quad \\\\=\\\\quad \\\\=\\\\quad \\\\=\\\\quad \\\\=\\\\quad\\\\=\\\\quad \\\\=\\\\quad \\\\=\\\\quad \\\\kill\" + \"\\n\";\n\t\t\n\t\treturn s;\n\t}\n\t\n\tprivate static String latexFileFooter()\n\t{\n\t\tString s = \"\";\n\t\t\n\t\ts += \"\\\\end{tabbing}\" + \"\\n\";\n\t\ts += \"\\\\end{minipage}}}\" + \"\\n\";\n\t\t\n\t\treturn s;\n\t}\n\n\t// multi-purpose highlighting code\n\t\n\tpublic static void highlight(InputStream stream, int oType) throws PrismLangException\n\t{\n\t\tPrismParser prismParser;\n\t\tPrismParserTokenManager tokenManager;\n\t\tToken first, t, st;\n\t\tboolean done = false;\n\t\t\n\t\ttry {\n\t\t\t// obtain exclusive acces to the prism parser\n\t\t\t// (don't forget to release it afterwards)\n\t\t\tprismParser = Prism.getPrismParser();\n\t\t\ttry {\n\t\t\t\t// restart parser and get its token manager\n\t\t\t\tPrismParser.ReInit(stream);\n\t\t\t\ttokenManager = prismParser.token_source;\n\t\t\t\t\n\t\t\t\t// get stream of tokens from token manager and put in a linked list\n\t\t\t\tfirst = t = tokenManager.getNextToken();\n\t\t\t\twhile (t != null && t.kind != PrismParserConstants.EOF) {\n\t\t\t\t\tt.next = tokenManager.getNextToken();\n\t\t\t\t\tt = t.next;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// go through tokens to do syntax highlighting\n\t\t\t\tt = first;\n\t\t\t\twhile (!done) {\n\t\t\t\t\t// see if we're at the end\n\t\t\t\t\tif (t == null) { done = true; continue; }\n\t\t\t\t\tif (t.kind == PrismParserConstants.EOF) { done = true; }\n\t\t\t\t\t// see if there was a lexical error\n\t\t\t\t\tif (t.kind == PrismParserConstants.LEXICAL_ERROR) {\n\t\t\t\t\t\tString s = \"Lexical error (\\\"\"+t.image+\"\\\", line \"+t.beginLine+\", column \"+t.beginColumn+\")\";\n\t\t\t\t\t\tthrow new PrismLangException(s);\n\t\t\t\t\t}\n\t\t\t\t\t// if there are preceding special tokens\n\t\t\t\t\tif (t.specialToken != null) {\n\t\t\t\t\t\t// go back to start of special tokens\n\t\t\t\t\t\tst = t.specialToken;\n\t\t\t\t\t\twhile (st.specialToken != null) st = st.specialToken;\n\t\t\t\t\t\t// go through special tokens\n\t\t\t\t\t\twhile (st != null) {\n\t\t\t\t\t\t\t// output\n\t\t\t\t\t\t\tif (st.kind == PrismParserConstants.COMMENT) {\n\t\t\t\t\t\t\t\toutput(st.image, COMMENT, oType);\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\toutput(st.image, WHITESPACE, oType);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// next special token\n\t\t\t\t\t\t\tst = st.next;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// output\n\t\t\t\t\tif (t.kind == PrismParserConstants.EOF) {\n\t\t\t\t\t\toutput(t.image, EOF, oType);\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\telse if (t.kind > PrismParserConstants.COMMENT && t.kind < PrismParserConstants.NOT)\n\t\t\t\t\t\toutput(t.image, KEYWORD, oType);\n\t\t\t\t\telse if (t.kind == PrismParserConstants.REG_INT || t.kind == PrismParserConstants.REG_DOUBLE)\n\t\t\t\t\t\toutput(t.image, NUMERIC, oType);\n\t\t\t\t\telse if (t.kind == PrismParserConstants.REG_IDENT || t.kind == PrismParserConstants.REG_IDENTPRIME)\n\t\t\t\t\t\toutput(t.image, IDENTIFIER, oType);\n\t\t\t\t\telse if (t.kind == PrismParserConstants.PREPROC)\n\t\t\t\t\t\toutput(t.image, PREPROC, oType);\n\t\t\t\t\telse\n\t\t\t\t\t\toutput(t.image, PUNCTUATION, oType);\n\t\t\t\t\t// next token\n\t\t\t\t\tt = t.next;\n\t\t\t\t}\n\t\t\t}\n\t\t\tfinally {\n\t\t\t\t// release prism parser\n\t\t\t\tPrism.releasePrismParser();\n\t\t\t}\n\t\t}\n\t\tcatch (InterruptedException e) {\n\t\t\tthrow new PrismLangException(\"Concurrency error in parser\");\n\t\t}\n\t}\n\n\tprivate static void output(String s, int tType, int oType)\n\t{\n\t\tint i, n;\n\t\t\n\t\t// deal with new lines for latex\n\t\t// (beacuse we have to precede each new line with \"\\mbox{\")\n\t\tif (oType == LATEX) if (resNewLine > 0) {\n\t\t\t// if this next token is another new line, don't output anything yet\n\t\t\tif (!(tType == WHITESPACE && (\"\\r\".equals(s) || \"\\n\".equals(s)))) {\n\t\t\t\t// trim trailing new lines\n\t\t\t\tif (tType == EOF) resNewLine = 1;\n\t\t\t\t// output code for new line(s)\n\t\t\t\tfor (i = 0; i < resNewLine; i++) {\n\t\t\t\t\tif (!resStart) {\n\t\t\t\t\t\tresStringBuffer.append(\"$}\");\n\t\t\t\t\t\tif (tType != EOF) resStringBuffer.append(\" \\\\\\\\\");\n\t\t\t\t\t\tresStringBuffer.append(\"\\n\");\n\t\t\t\t\t}\n\t\t\t\t\tif (tType != EOF) resStringBuffer.append(\"\\\\mbox{$\");\n\t\t\t\t\tresStart = false;\n\t\t\t\t}\n\t\t\t\tresNewLine = 0;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// substitute any punctuation with special code as necessary\n\t\ts = replacePunc(s, tType, oType);\n\t\t\n\t\tswitch (tType) {\n\t\t\n\t\tcase PUNCTUATION:\n\t\t\tswitch(oType) {\n\t\t\tcase ECHO: resStringBuffer.append(s); break;\n\t\t\tcase HTML: resStringBuffer.append(s); break;\n\t\t\tcase LATEX: resStringBuffer.append(s); break;\n\t\t\tcase PRISMGUI: n = s.length(); for (i=0;i<n;i++) resTypeArray[resCharCount++]=PUNCTUATION; break;\n\t\t\t}\n\t\t\tbreak;\n\t\t\n\t\tcase COMMENT:\n\t\t\t// strip any nasty carriage returns\n\t\t\ts = s.replaceAll(\"\\r\", \"\");\n\t\t\tswitch (oType) {\n\t\t\tcase ECHO: resStringBuffer.append(s); break;\n\t\t\tcase HTML: resStringBuffer.append(\"<span class=\\\"prismcomment\\\">\"+s.substring(0,s.length()-1)+\"</span>\"+\"\\n\"); break;\n\t\t\tcase LATEX: resStringBuffer.append(\"\\\\prismcomment{\"+s.substring(0,s.length()-1)+\"}\"); resNewLine++; break;\n\t\t\tcase PRISMGUI: n = s.length(); for (i=0;i<n;i++) resTypeArray[resCharCount++]=COMMENT; break;\n\t\t\t}\n\t\t\tbreak;\n\t\t\n\t\tcase WHITESPACE:\n\t\t\t// ignore carriage returns\n\t\t\tif (\"\\r\".equals(s)) break;\n\t\t\tswitch(oType) {\n\t\t\tcase ECHO: resStringBuffer.append(s); break;\n\t\t\tcase HTML: resStringBuffer.append(s); break;\n\t\t\tcase LATEX: if (\"\\n\".equals(s)) resNewLine++;\n\t\t\t            else if (\" \".equals(s)) resStringBuffer.append(\" \\\\; \");\n\t\t\t            else if (\"\\t\".equals(s)) resStringBuffer.append(\"\\\\prismtab\");\n\t\t\t            else resStringBuffer.append(s);\n\t\t\t            break;\n\t\t\tcase PRISMGUI: n = s.length(); for (i=0;i<n;i++) resTypeArray[resCharCount++]=WHITESPACE; break;\n\t\t\t}\n\t\t\tbreak;\n\t\t\n\t\tcase KEYWORD:\n\t\t\tswitch (oType) {\n\t\t\tcase ECHO: resStringBuffer.append(s); break;\n\t\t\tcase HTML: resStringBuffer.append(\"<span class=\\\"prismkeyword\\\">\"+s+\"</span>\"); break;\n\t\t\tcase LATEX: resStringBuffer.append(\"\\\\prismkeyword{\"+s+\"}\"); break;\n\t\t\tcase PRISMGUI: n = s.length(); for (i=0;i<n;i++) resTypeArray[resCharCount++]=KEYWORD; break;\n\t\t\t}\n\t\t\tbreak;\n\t\t\n\t\t\n\t\tcase NUMERIC:\n\t\t\tswitch (oType) {\n\t\t\tcase ECHO: resStringBuffer.append(s); break;\n\t\t\tcase HTML: resStringBuffer.append(\"<span class=\\\"prismnum\\\">\"+s+\"</span>\"); break;\n\t\t\tcase LATEX: resStringBuffer.append(s); break;\n\t\t\tcase PRISMGUI: n = s.length(); for (i=0;i<n;i++) resTypeArray[resCharCount++]=NUMERIC; break;\n\t\t\t}\n\t\t\tbreak;\n\t\t\n\t\tcase IDENTIFIER:\n\t\t\tswitch (oType) {\n\t\t\tcase ECHO: resStringBuffer.append(s); break;\n\t\t\tcase HTML: resStringBuffer.append(\"<span class=\\\"prismident\\\">\"+s+\"</span>\"); break;\n\t\t\tcase LATEX: resStringBuffer.append(\"\\\\prismident{\"+s+\"}\"); break;\n\t\t\tcase PRISMGUI: n = s.length(); for (i=0;i<n;i++) resTypeArray[resCharCount++]=IDENTIFIER; break;\n\t\t\t}\n\t\t\tbreak;\n\t\t\n\t\tcase PREPROC:\n\t\t\tswitch (oType) {\n\t\t\tcase ECHO: resStringBuffer.append(s); break;\n\t\t\tcase HTML: resStringBuffer.append(\"<span class=\\\"prismpreproc\\\">\"+s+\"</span>\"); break;\n\t\t\tcase LATEX: resStringBuffer.append(\"\\\\prismpreproc{\"+s+\"}\"); break;\n\t\t\tcase PRISMGUI: n = s.length(); for (i=0;i<n;i++) resTypeArray[resCharCount++]=PREPROC; break;\n\t\t\t}\n\t\t\tbreak;\n\t\t\n\t\tcase EOF:\n\t\t\tswitch (oType) {\n\t\t\tcase ECHO: break;\n\t\t\tcase HTML: break;\n\t\t\tcase LATEX:\n\t\t\t\t// close \\mbox if there was no trailing new line\n\t\t\t\tif (resStringBuffer.length() > 0)\n\t\t\t\t\tif (resStringBuffer.charAt(resStringBuffer.length()-1)  != '\\n')\n\t\t\t\t\t\tresStringBuffer.append(\"$}\");\n\t\t\t\tbreak;\n\t\t\tcase PRISMGUI: break;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t}\n\t\n\t// substitute any punctuation with special code as necessary\n\t\n\tpublic static String replacePunc(String s, int tType, int oType)\n\t{\n\t\tint i, n;\n\t\tString s1, s2, snew;\n\t\tArrayList<String> to, from;\n\t\t\n\t\tswitch (oType) {\n\t\t\tcase ECHO: to = puncReplaceTo_ECHO; from = puncReplaceFrom_ECHO; break;\n\t\t\tcase HTML: to = puncReplaceTo_HTML; from = puncReplaceFrom_HTML; break;\n\t\t\tcase LATEX: if (tType == COMMENT) {\n\t\t\t              to = puncReplaceTo_LATEX; from = puncReplaceFrom_LATEX;\n\t\t\t            } else {\n\t\t\t              to = puncReplaceTo_LATEXMATHS; from = puncReplaceFrom_LATEXMATHS;\n\t\t\t            } break;\n\t\t\tcase PRISMGUI: to = puncReplaceTo_PRISMGUI; from = puncReplaceFrom_PRISMGUI; break;\n\t\t\tdefault: to = puncReplaceTo_ECHO; from = puncReplaceFrom_ECHO; break;\n\t\t}\n\t\t\n\t\tsnew = s;\n\t\tn = from.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts1 = from.get(i);\n\t\t\ts2 = to.get(i);\n\t\t\tsnew = snew.replaceAll(s1, s2);\n\t\t}\n\t\t\n\t\tif (oType == LATEX && s.contains(\"\\\"\")) {\n\t\t\tsnew = snew.replaceAll(\"\\\"\", (quoteAlternator==1)?\"\\\\\\\\mbox{``}\":\"\\\\\\\\mbox{''}\");\n\t\t\tquoteAlternator = 3 - quoteAlternator;\n\t\t}\n\t\t\n\t\treturn snew;\n\t}\n\t\n\t// old version - worked on buffer not string; also: no regexes\n\t/*public static void replacePunc(StringBuffer sb, int oType)\n\t{\n\t\tint i, j, n;\n\t\tString s1, s2;\n\t\t\n\t\tn = puncReplaceFrom[oType].size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts1 = puncReplaceFrom[oType].get(i);\n\t\t\tj = 0;\n\t\t\twhile (j != -1) {\n\t\t\t\tj = sb.indexOf(s1, j);\n\t\t\t\tif (j != -1) {\n\t\t\t\t\ts2 = puncReplaceTo[oType].get(i);\n\t\t\t\t\tsb.replace(j, j+s1.length(), s2);\n\t\t\t\t\tj = j+s2.length();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}*/\n\n\t// main method - for command-line execution\n\t// arguments:\n\t// 0 = output type\n\t//     echo, html\n\t// 1 = filename\n\t//     if provided, argument is name of file to use, header/footer added\n\t//     if not, read from stdin, no header/footer added\n\t\n\tpublic static void main(String args[])\n\t{\n\t\t// Default setting\n\t\tString cssLoc = \"prism.css\";\n\t\t\n\t\t// Put arguments into a list, parsing any switches as we go\n\t\tArrayList<String> argsList = new ArrayList<String>();\n\t\tint i = 0;\n\t\twhile (i < args.length) {\n\t\t\tif (args[i].matches(\"-.*\")) {\n\t\t\t\tString sw = args[i].substring(1);\n\t\t\t\tif (sw.equals(\"css\")) {\n\t\t\t\t\tif (args.length < i + 2)  {\n\t\t\t\t\t\tSystem.out.print(\"Error: Missing argument for switch \" + args[i]);\n\t\t\t\t\t\tSystem.exit(1);\n\t\t\t\t\t}\n\t\t\t\t\tcssLoc = args[i+1];\n\t\t\t\t\ti += 2;\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tSystem.out.print(\"Error: Unknown switch \" + args[i]);\n\t\t\t\t\tSystem.exit(1);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\targsList.add(args[i]);\n\t\t\t\ti++;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Process non-switch arguments\n\t\tif (argsList.size() == 0) {\n\t\t\tSystem.out.println(\"Error: First argument must be output type\");\n\t\t\tSystem.exit(1);\n\t\t}\n\t\ttry {\n\t\t\tif (argsList.get(0).equals(\"echo\")) {\n\t\t\t\tif (argsList.size() > 1) {\n\t\t\t\t\tSystem.out.print(echoFile(new File(argsList.get(1))));\n\t\t\t\t} else {\n\t\t\t\t\tSystem.out.print(echoFile(System.in));\n\t\t\t\t}\n\t\t\t} else if (argsList.get(0).equals(\"html\")) {\n\t\t\t\tif (argsList.size() > 1) {\n\t\t\t\t\tSystem.out.print(fileToHtml(new File(argsList.get(1)), true, cssLoc));\n\t\t\t\t} else {\n\t\t\t\t\tSystem.out.print(fileToHtml(System.in, false, cssLoc));\n\t\t\t\t}\n\t\t\t} else if (argsList.get(0).equals(\"latex\")) {\n\t\t\t\tif (argsList.size() > 1) {\n\t\t\t\t\tSystem.out.print(fileToLatex(new File(argsList.get(1)), true));\n\t\t\t\t} else {\n\t\t\t\t\tSystem.out.print(fileToLatex(System.in, false));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tSystem.out.println(\"Error: Type must be \\\"echo\\\", \\\"html\\\" or \\\"latex\\\"\");\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t}\n\t\tcatch (FileNotFoundException e) {\n\t\t\tSystem.out.println(\"Error: Could not load file \\\"\"+ argsList.get(1) + \"\\\"\");\n\t\t\tSystem.exit(1);\n\t\t}\n\t\tcatch (PrismLangException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/README",
    "content": "parser\n======\n\nTo compile .jj file into .java parser\n-------------------------------------\n\n(cd parser; javacc PrismParser.jj); javac parser/PrismParser.java\n"
  },
  {
    "path": "prism/src/parser/SimpleCharStream.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. SimpleCharStream.java Version 7.0 */\n/* JavaCCOptions:STATIC=true,SUPPORT_CLASS_VISIBILITY_PUBLIC=true */\npackage parser;\n\n/**\n * An implementation of interface CharStream, where the stream is assumed to\n * contain only ASCII characters (without unicode processing).\n */\n\npublic class SimpleCharStream\n{\n/** Whether parser is static. */\n  public static final boolean staticFlag = true;\n  static int bufsize;\n  static int available;\n  static int tokenBegin;\n/** Position in buffer. */\n  static public int bufpos = -1;\n  static protected int bufline[];\n  static protected int bufcolumn[];\n\n  static protected int column = 0;\n  static protected int line = 1;\n\n  static protected boolean prevCharIsCR = false;\n  static protected boolean prevCharIsLF = false;\n\n  static protected java.io.Reader inputStream;\n\n  static protected char[] buffer;\n  static protected int maxNextCharInd = 0;\n  static protected int inBuf = 0;\n  static protected int tabSize = 1;\n  static protected boolean trackLineColumn = true;\n\n  static public void setTabSize(int i) { tabSize = i; }\n  static public int getTabSize() { return tabSize; }\n\n\n\n  static protected void ExpandBuff(boolean wrapAround)\n  {\n    char[] newbuffer = new char[bufsize + 2048];\n    int newbufline[] = new int[bufsize + 2048];\n    int newbufcolumn[] = new int[bufsize + 2048];\n\n    try\n    {\n      if (wrapAround)\n      {\n        System.arraycopy(buffer, tokenBegin, newbuffer, 0, bufsize - tokenBegin);\n        System.arraycopy(buffer, 0, newbuffer, bufsize - tokenBegin, bufpos);\n        buffer = newbuffer;\n\n        System.arraycopy(bufline, tokenBegin, newbufline, 0, bufsize - tokenBegin);\n        System.arraycopy(bufline, 0, newbufline, bufsize - tokenBegin, bufpos);\n        bufline = newbufline;\n\n        System.arraycopy(bufcolumn, tokenBegin, newbufcolumn, 0, bufsize - tokenBegin);\n        System.arraycopy(bufcolumn, 0, newbufcolumn, bufsize - tokenBegin, bufpos);\n        bufcolumn = newbufcolumn;\n\n        maxNextCharInd = (bufpos += (bufsize - tokenBegin));\n      }\n      else\n      {\n        System.arraycopy(buffer, tokenBegin, newbuffer, 0, bufsize - tokenBegin);\n        buffer = newbuffer;\n\n        System.arraycopy(bufline, tokenBegin, newbufline, 0, bufsize - tokenBegin);\n        bufline = newbufline;\n\n        System.arraycopy(bufcolumn, tokenBegin, newbufcolumn, 0, bufsize - tokenBegin);\n        bufcolumn = newbufcolumn;\n\n        maxNextCharInd = (bufpos -= tokenBegin);\n      }\n    }\n    catch (Throwable t)\n    {\n      throw new Error(t.getMessage());\n    }\n\n\n    bufsize += 2048;\n    available = bufsize;\n    tokenBegin = 0;\n  }\n\n  static protected void FillBuff() throws java.io.IOException\n  {\n    if (maxNextCharInd == available)\n    {\n      if (available == bufsize)\n      {\n        if (tokenBegin > 2048)\n        {\n          bufpos = maxNextCharInd = 0;\n          available = tokenBegin;\n        }\n        else if (tokenBegin < 0)\n          bufpos = maxNextCharInd = 0;\n        else\n          ExpandBuff(false);\n      }\n      else if (available > tokenBegin)\n        available = bufsize;\n      else if ((tokenBegin - available) < 2048)\n        ExpandBuff(true);\n      else\n        available = tokenBegin;\n    }\n\n    int i;\n    try {\n      if ((i = inputStream.read(buffer, maxNextCharInd, available - maxNextCharInd)) == -1)\n      {\n        inputStream.close();\n        throw new java.io.IOException();\n      }\n      else\n        maxNextCharInd += i;\n      return;\n    }\n    catch(java.io.IOException e) {\n      --bufpos;\n      backup(0);\n      if (tokenBegin == -1)\n        tokenBegin = bufpos;\n      throw e;\n    }\n  }\n\n/** Start. */\n  static public char BeginToken() throws java.io.IOException\n  {\n    tokenBegin = -1;\n    char c = readChar();\n    tokenBegin = bufpos;\n\n    return c;\n  }\n\n  static protected void UpdateLineColumn(char c)\n  {\n    column++;\n\n    if (prevCharIsLF)\n    {\n      prevCharIsLF = false;\n      line += (column = 1);\n    }\n    else if (prevCharIsCR)\n    {\n      prevCharIsCR = false;\n      if (c == '\\n')\n      {\n        prevCharIsLF = true;\n      }\n      else\n        line += (column = 1);\n    }\n\n    switch (c)\n    {\n      case '\\r' :\n        prevCharIsCR = true;\n        break;\n      case '\\n' :\n        prevCharIsLF = true;\n        break;\n      case '\\t' :\n        column--;\n        column += (tabSize - (column % tabSize));\n        break;\n      default :\n        break;\n    }\n\n    bufline[bufpos] = line;\n    bufcolumn[bufpos] = column;\n  }\n\n/** Read a character. */\n  static public char readChar() throws java.io.IOException\n  {\n    if (inBuf > 0)\n    {\n      --inBuf;\n\n      if (++bufpos == bufsize)\n        bufpos = 0;\n\n      return buffer[bufpos];\n    }\n\n    if (++bufpos >= maxNextCharInd)\n      FillBuff();\n\n    char c = buffer[bufpos];\n\n    UpdateLineColumn(c);\n    return c;\n  }\n\n  /**\n   * @deprecated\n   * @see #getEndColumn\n   */\n  @Deprecated\n  static public int getColumn() {\n    return bufcolumn[bufpos];\n  }\n\n  /**\n   * @deprecated\n   * @see #getEndLine\n   */\n  @Deprecated\n  static public int getLine() {\n    return bufline[bufpos];\n  }\n\n  /** Get token end column number. */\n  static public int getEndColumn() {\n    return bufcolumn[bufpos];\n  }\n\n  /** Get token end line number. */\n  static public int getEndLine() {\n     return bufline[bufpos];\n  }\n\n  /** Get token beginning column number. */\n  static public int getBeginColumn() {\n    return bufcolumn[tokenBegin];\n  }\n\n  /** Get token beginning line number. */\n  static public int getBeginLine() {\n    return bufline[tokenBegin];\n  }\n\n/** Backup a number of characters. */\n  static public void backup(int amount) {\n\n    inBuf += amount;\n    if ((bufpos -= amount) < 0)\n      bufpos += bufsize;\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.Reader dstream, int startline,\n  int startcolumn, int buffersize)\n  {\n    if (inputStream != null)\n      throw new Error(\"\\n   ERROR: Second call to the constructor of a static SimpleCharStream.\\n\" +\n      \"       You must either use ReInit() or set the JavaCC option STATIC to false\\n\" +\n      \"       during the generation of this class.\");\n    inputStream = dstream;\n    line = startline;\n    column = startcolumn - 1;\n\n    available = bufsize = buffersize;\n    buffer = new char[buffersize];\n    bufline = new int[buffersize];\n    bufcolumn = new int[buffersize];\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.Reader dstream, int startline,\n                          int startcolumn)\n  {\n    this(dstream, startline, startcolumn, 4096);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.Reader dstream)\n  {\n    this(dstream, 1, 1, 4096);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.Reader dstream, int startline,\n  int startcolumn, int buffersize)\n  {\n    inputStream = dstream;\n    line = startline;\n    column = startcolumn - 1;\n\n    if (buffer == null || buffersize != buffer.length)\n    {\n      available = bufsize = buffersize;\n      buffer = new char[buffersize];\n      bufline = new int[buffersize];\n      bufcolumn = new int[buffersize];\n    }\n    prevCharIsLF = prevCharIsCR = false;\n    tokenBegin = inBuf = maxNextCharInd = 0;\n    bufpos = -1;\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.Reader dstream, int startline,\n                     int startcolumn)\n  {\n    ReInit(dstream, startline, startcolumn, 4096);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.Reader dstream)\n  {\n    ReInit(dstream, 1, 1, 4096);\n  }\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, String encoding, int startline,\n  int startcolumn, int buffersize) throws java.io.UnsupportedEncodingException\n  {\n    this(encoding == null ? new java.io.InputStreamReader(dstream) : new java.io.InputStreamReader(dstream, encoding), startline, startcolumn, buffersize);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, int startline,\n  int startcolumn, int buffersize)\n  {\n    this(new java.io.InputStreamReader(dstream), startline, startcolumn, buffersize);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, String encoding, int startline,\n                          int startcolumn) throws java.io.UnsupportedEncodingException\n  {\n    this(dstream, encoding, startline, startcolumn, 4096);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, int startline,\n                          int startcolumn)\n  {\n    this(dstream, startline, startcolumn, 4096);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, String encoding) throws java.io.UnsupportedEncodingException\n  {\n    this(dstream, encoding, 1, 1, 4096);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream)\n  {\n    this(dstream, 1, 1, 4096);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, String encoding, int startline,\n                          int startcolumn, int buffersize) throws java.io.UnsupportedEncodingException\n  {\n    ReInit(encoding == null ? new java.io.InputStreamReader(dstream) : new java.io.InputStreamReader(dstream, encoding), startline, startcolumn, buffersize);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, int startline,\n                          int startcolumn, int buffersize)\n  {\n    ReInit(new java.io.InputStreamReader(dstream), startline, startcolumn, buffersize);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, String encoding) throws java.io.UnsupportedEncodingException\n  {\n    ReInit(dstream, encoding, 1, 1, 4096);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream)\n  {\n    ReInit(dstream, 1, 1, 4096);\n  }\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, String encoding, int startline,\n                     int startcolumn) throws java.io.UnsupportedEncodingException\n  {\n    ReInit(dstream, encoding, startline, startcolumn, 4096);\n  }\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, int startline,\n                     int startcolumn)\n  {\n    ReInit(dstream, startline, startcolumn, 4096);\n  }\n  /** Get token literal value. */\n  static public String GetImage()\n  {\n    if (bufpos >= tokenBegin)\n      return new String(buffer, tokenBegin, bufpos - tokenBegin + 1);\n    else\n      return new String(buffer, tokenBegin, bufsize - tokenBegin) +\n                            new String(buffer, 0, bufpos + 1);\n  }\n\n  /** Get the suffix. */\n  static public char[] GetSuffix(int len)\n  {\n    char[] ret = new char[len];\n\n    if ((bufpos + 1) >= len)\n      System.arraycopy(buffer, bufpos - len + 1, ret, 0, len);\n    else\n    {\n      System.arraycopy(buffer, bufsize - (len - bufpos - 1), ret, 0,\n                                                        len - bufpos - 1);\n      System.arraycopy(buffer, 0, ret, len - bufpos - 1, bufpos + 1);\n    }\n\n    return ret;\n  }\n\n  /** Reset buffer when finished. */\n  static public void Done()\n  {\n    buffer = null;\n    bufline = null;\n    bufcolumn = null;\n  }\n\n  /**\n   * Method to adjust line and column numbers for the start of a token.\n   */\n  static public void adjustBeginLineColumn(int newLine, int newCol)\n  {\n    int start = tokenBegin;\n    int len;\n\n    if (bufpos >= tokenBegin)\n    {\n      len = bufpos - tokenBegin + inBuf + 1;\n    }\n    else\n    {\n      len = bufsize - tokenBegin + bufpos + 1 + inBuf;\n    }\n\n    int i = 0, j = 0, k = 0;\n    int nextColDiff = 0, columnDiff = 0;\n\n    while (i < len && bufline[j = start % bufsize] == bufline[k = ++start % bufsize])\n    {\n      bufline[j] = newLine;\n      nextColDiff = columnDiff + bufcolumn[k] - bufcolumn[j];\n      bufcolumn[j] = newCol + columnDiff;\n      columnDiff = nextColDiff;\n      i++;\n    }\n\n    if (i < len)\n    {\n      bufline[j] = newLine++;\n      bufcolumn[j] = newCol + columnDiff;\n\n      while (i++ < len)\n      {\n        if (bufline[j = start % bufsize] != bufline[++start % bufsize])\n          bufline[j] = newLine++;\n        else\n          bufline[j] = newLine;\n      }\n    }\n\n    line = bufline[j];\n    column = bufcolumn[j];\n  }\n  static boolean getTrackLineColumn() { return trackLineColumn; }\n  static void setTrackLineColumn(boolean tlc) { trackLineColumn = tlc; }\n}\n/* JavaCC - OriginalChecksum=248d3736771a20ebabfe2c19ce2acc79 (do not edit this line) */\n"
  },
  {
    "path": "prism/src/parser/State.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\nimport java.util.Arrays;\nimport java.util.List;\nimport java.util.stream.Collectors;\n\nimport prism.ModelInfo;\nimport prism.PrismLangException;\n\n/**\n * Class to store a model state, i.e. a mapping from variables to values.\n * Stores as an array of Objects, where indexing is defined by a model. \n */\npublic class State implements Comparable<State>\n{\n\tpublic Object varValues[];\n\n\t/**\n\t * Construct empty (uninitialised) state.\n\t * @param n Number of variables.\n\t */\n\tpublic State(int n)\n\t{\n\t\tvarValues = new Object[n];\n\t}\n\n\t/**\n\t * Construct by copying existing State object.\n\t * @param s State to copy.\n\t */\n\tpublic State(State s)\n\t{\n\t\tthis(s.varValues.length);\n\t\tcopy(s);\n\t}\n\n\t/**\n\t * Construct by concatenating two existing State objects.\n\t */\n\tpublic State(State s1, State s2)\n\t{\n\t\tObject[] arr1 = (Object[]) s1.varValues;\n\t\tObject[] arr2 = (Object[]) s2.varValues;\n\t\tvarValues = new Object[arr1.length + arr2.length];\n\t\tint i;\n\t\tfor (i = 0; i < arr1.length; i++)\n\t\t\tvarValues[i] = arr1[i];\n\t\tfor (i = 0; i < arr2.length; i++)\n\t\t\tvarValues[arr1.length + i] = arr2[i];\n\t}\n\n\t/**\n\t * Construct by copying existing Values object.\n\t * Need access to model info in case variables are not ordered correctly.\n\t * Throws an exception if any variables are undefined. \n\t * @param v Values object to copy.\n\t * @param modelInfo Model info (for variable info/ordering)\n\t */\n\tpublic State(Values v, ModelInfo modelInfo) throws PrismLangException\n\t{\n\t\tthis(v, modelInfo, true);\n\t}\n\n\t/**\n\t * Construct by copying existing Values object.\n\t * Need access to model info in case variables are not ordered correctly.\n\t * If requested, throws an exception if any variables are undefined. \n\t * @param v Values object to copy.\n\t * @param modelInfo Model info (for variable info/ordering)\n\t * @param checkAllDef If true, check all variables are present\n\t */\n\tpublic State(Values v, ModelInfo modelInfo, boolean checkAllDef) throws PrismLangException\n\t{\n\t\tint i, j, n;\n\t\tn = v.getNumValues();\n\t\tif (checkAllDef && n != modelInfo.getNumVars()) {\n\t\t\tthrow new PrismLangException(\"Wrong number of variables in state\");\n\t\t}\n\t\tvarValues = new Object[n];\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tvarValues[i] = null;\n\t\t}\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tj = modelInfo.getVarIndex(v.getName(i));\n\t\t\tif (j == -1) {\n\t\t\t\tthrow new PrismLangException(\"Unknown variable \" + v.getName(i) + \" in state\");\n\t\t\t}\n\t\t\tif (varValues[i] != null) {\n\t\t\t\tthrow new PrismLangException(\"Duplicated variable \" + v.getName(i) + \" in state\");\n\t\t\t}\n\t\t\tvarValues[i] = v.getValue(i);\n\t\t}\n\t}\n\n\t/**\n\t * Clear: set all values to null\n\t */\n\tpublic void clear()\n\t{\n\t\tint i, n;\n\t\tn = varValues.length;\n\t\tfor (i = 0; i < n; i++)\n\t\t\tvarValues[i] = null;\n\t}\n\n\t/**\n\t * Set the {@code i}th value to {@code val}.\n\t */\n\tpublic State setValue(int i, Object val)\n\t{\n\t\tvarValues[i] = val;\n\t\treturn this;\n\t}\n\n\t/**\n\t * Copy contents of an existing state.\n\t * @param s State to copy.\n\t */\n\tpublic void copy(State s)\n\t{\n\t\tint i, n;\n\t\tn = varValues.length;\n\t\tfor (i = 0; i < n; i++)\n\t\t\tvarValues[i] = s.varValues[i];\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\treturn Arrays.hashCode(varValues);\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == this)\n\t\t\treturn true;\n\t\tif (!(o instanceof State))\n\t\t\treturn false;\n\n\t\tint i, n;\n\t\tState s = (State) o;\n\t\tn = varValues.length;\n\t\tif (n != s.varValues.length)\n\t\t\treturn false;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (!(varValues[i]).equals(s.varValues[i]))\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic int compareTo(State s)\n\t{\n\t\treturn compareTo(s, 0);\n\t}\n\t\n\t/**\n\t * Compare this state to another state {@code s} (in the style of {@link #compareTo(State)},\n\t * first comparing variables with index greater than or equal to {@code j},\n\t * and then comparing variables with index less than {@code j}.\n\t */\n\tpublic int compareTo(State s, int j)\n\t{\n\t\tint i, c, n;\n\t\tObject svv[];\n\t\t\n\t\t// Can't compare to null\n\t\tif (s == null)\n\t\t\tthrow new NullPointerException();\n\t\t\n\t\t// States of different size are incomparable \n\t\tsvv = s.varValues;\n\t\tn = varValues.length;\n\t\tif (n != svv.length)\n\t\t\tthrow new ClassCastException(\"States are different sizes\");\n\t\t\n\t\tif (j > n-1)\n\t\t\tthrow new ClassCastException(\"Variable index is incorrect\");\n\t\t\n\t\t// Go through variables j...n-1\n\t\tfor (i = j; i < n; i++) {\n\t\t\tc = compareObjects(varValues[i], svv[i]);\n\t\t\tif (c != 0)\n\t\t\t\treturn c;\n\t\t\telse\n\t\t\t\tcontinue;\n\t\t}\n\t\t\n\t\t// Go through variables 0...j\n\t\tfor (i = 0; i < j; i++) {\n\t\t\tc = compareObjects(varValues[i], svv[i]);\n\t\t\tif (c != 0)\n\t\t\t\treturn c;\n\t\t\telse\n\t\t\t\tcontinue;\n\t\t}\n\t\t\n\t\treturn 0;\n\t}\n\n\t/**\n\t * Get string representation, e.g. \"(0,true,5)\". \n\t */\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tString s = \"(\";\n\t\tn = varValues.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (i > 0)\n\t\t\t\ts += \",\";\n\t\t\ts += valueToString(varValues[i]);\n\t\t}\n\t\ts += \")\";\n\t\treturn s;\n\t}\n\n\t/**\n\t * Get string representation, without outer parentheses, e.g. \"0,true,5\". \n\t */\n\tpublic String toStringNoParentheses()\n\t{\n\t\tint i, n;\n\t\tString s = \"\";\n\t\tn = varValues.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (i > 0)\n\t\t\t\ts += \",\";\n\t\t\ts += valueToString(varValues[i]);\n\t\t}\n\t\treturn s;\n\t}\n\n\t/**\n\t * Get string representation, e.g. \"(a=0,b=true,c=5)\", \n\t * with variables names (taken from a String list). \n\t */\n\tpublic String toString(List<String> varNames)\n\t{\n\t\tint i, n;\n\t\tString s = \"(\";\n\t\tn = varValues.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (i > 0)\n\t\t\t\ts += \",\";\n\t\t\ts += varNames.get(i) + \"=\" + valueToString(varValues[i]);\n\t\t}\n\t\ts += \")\";\n\t\treturn s;\n\t}\n\n\t/**\n\t * Get string representation, e.g. \"(a=0,b=true,c=5)\", \n\t * with variables names (taken from model info). \n\t */\n\tpublic String toString(ModelInfo modelInfo)\n\t{\n\t\tint i, n;\n\t\tString s = \"(\";\n\t\tn = varValues.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (i > 0)\n\t\t\t\ts += \",\";\n\t\t\ts += modelInfo.getVarName(i) + \"=\" + valueToString(varValues[i]);\n\t\t}\n\t\ts += \")\";\n\t\treturn s;\n\t}\n\n\t/**\n\t * Convert a value, represented as an Object, to a string for display.\n\t * Like {@code Object.toString}, except that null is presented as \"?\"\n\t * and we remove spaces separating list elements.\n\t */\n\tpublic static String valueToString(Object value)\n\t{\n\t\tif (value == null) {\n\t\t\treturn \"?\";\n\t\t} else if (value instanceof List) {\n\t\t\treturn \"[\" + ((List<?>) value).stream().map(State::valueToString).collect(Collectors.joining(\",\")) + \"]\";\n\t\t} else {\n\t\t\treturn value.toString();\n\t\t}\n\t}\n\n\t/**\n\t * Utility method for comparing values stored as Objects.\n\t * Return values are as for the standard Comparable.compareTo method.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic static int compareObjects(Object o1, Object o2)\n\t{\n\t\t// Deal with nulls\n\t\tif (o1 == null) {\n\t\t\treturn (o2 == null) ? 0 : -1;\n\t\t} else if (o2 == null) {\n\t\t\treturn 1; // (we know o1 is non-null here)\n\t\t}\n\t\t// Things that already implement Comparable (Integer, Double)\n\t\tif (o1 instanceof Comparable && o2 instanceof Comparable && o1.getClass().equals(o2.getClass())) {\n\t\t\treturn ((Comparable<Object>) o1).compareTo((Comparable<Object>) o2);\n\t\t}\n\t\t// Two lists of comparable objects\n\t\telse if (o1 instanceof List && o2 instanceof List) {\n\t\t\tList<?> l1 = (List<?>) o1;\n\t\t\tList<?> l2 = (List<?>) o2;\n\t\t\tint size = l1.size();\n\t\t\tif (l2.size() != size) {\n\t\t\t\tthrow new ClassCastException(\"Can't compare \" + o1 + \" and \" + o2 + \" since their sizes differ\");\n\t\t\t}\n\t\t\tfor (int i = 0; i < size; i++) {\n\t\t\t\tint c = compareObjects(l1.get(i), l2.get(i));\n\t\t\t\tif (c != 0)\n\t\t\t\t\treturn c;\n\t\t\t\telse\n\t\t\t\t\tcontinue;\n\t\t\t}\n\t\t\treturn 0;\n\t\t} else {\n\t\t\tthrow new ClassCastException(\"Can't compare \" + o1.getClass() + \" and \" + o2.getClass());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/Token.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. Token.java Version 7.0 */\n/* JavaCCOptions:TOKEN_EXTENDS=,KEEP_LINE_COLUMN=true,SUPPORT_CLASS_VISIBILITY_PUBLIC=true */\npackage parser;\n\n/**\n * Describes the input token stream.\n */\n\npublic class Token implements java.io.Serializable {\n\n  /**\n   * The version identifier for this Serializable class.\n   * Increment only if the <i>serialized</i> form of the\n   * class changes.\n   */\n  private static final long serialVersionUID = 1L;\n\n  /**\n   * An integer that describes the kind of this token.  This numbering\n   * system is determined by JavaCCParser, and a table of these numbers is\n   * stored in the file ...Constants.java.\n   */\n  public int kind;\n\n  /** The line number of the first character of this Token. */\n  public int beginLine;\n  /** The column number of the first character of this Token. */\n  public int beginColumn;\n  /** The line number of the last character of this Token. */\n  public int endLine;\n  /** The column number of the last character of this Token. */\n  public int endColumn;\n\n  /**\n   * The string image of the token.\n   */\n  public String image;\n\n  /**\n   * A reference to the next regular (non-special) token from the input\n   * stream.  If this is the last token from the input stream, or if the\n   * token manager has not read tokens beyond this one, this field is\n   * set to null.  This is true only if this token is also a regular\n   * token.  Otherwise, see below for a description of the contents of\n   * this field.\n   */\n  public Token next;\n\n  /**\n   * This field is used to access special tokens that occur prior to this\n   * token, but after the immediately preceding regular (non-special) token.\n   * If there are no such special tokens, this field is set to null.\n   * When there are more than one such special token, this field refers\n   * to the last of these special tokens, which in turn refers to the next\n   * previous special token through its specialToken field, and so on\n   * until the first special token (whose specialToken field is null).\n   * The next fields of special tokens refer to other special tokens that\n   * immediately follow it (without an intervening regular token).  If there\n   * is no such token, this field is null.\n   */\n  public Token specialToken;\n\n  /**\n   * An optional attribute value of the Token.\n   * Tokens which are not used as syntactic sugar will often contain\n   * meaningful values that will be used later on by the compiler or\n   * interpreter. This attribute value is often different from the image.\n   * Any subclass of Token that actually wants to return a non-null value can\n   * override this method as appropriate.\n   */\n  public Object getValue() {\n    return null;\n  }\n\n  /**\n   * No-argument constructor\n   */\n  public Token() {}\n\n  /**\n   * Constructs a new token for the specified Image.\n   */\n  public Token(int kind)\n  {\n    this(kind, null);\n  }\n\n  /**\n   * Constructs a new token for the specified Image and Kind.\n   */\n  public Token(int kind, String image)\n  {\n    this.kind = kind;\n    this.image = image;\n  }\n\n  /**\n   * Returns the image.\n   */\n  @Override\n  public String toString()\n  {\n    return image;\n  }\n\n  /**\n   * Returns a new Token object, by default. However, if you want, you\n   * can create and return subclass objects based on the value of ofKind.\n   * Simply add the cases to the switch for all those special cases.\n   * For example, if you have a subclass of Token called IDToken that\n   * you want to create if ofKind is ID, simply add something like :\n   *\n   *    case MyParserConstants.ID : return new IDToken(ofKind, image);\n   *\n   * to the following switch statement. Then you can cast matchedToken\n   * variable to the appropriate type and use sit in your lexical actions.\n   */\n  public static Token newToken(int ofKind, String image)\n  {\n    switch(ofKind)\n    {\n      default : return new Token(ofKind, image);\n    }\n  }\n\n  public static Token newToken(int ofKind)\n  {\n    return newToken(ofKind, null);\n  }\n\n}\n/* JavaCC - OriginalChecksum=a6e99fa366f40513e8823da999781b1f (do not edit this line) */\n"
  },
  {
    "path": "prism/src/parser/TokenMgrError.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. TokenMgrError.java Version 7.0 */\n/* JavaCCOptions: */\npackage parser;\n\n/** Token Manager Error. */\n@SuppressWarnings(\"all\") \npublic class TokenMgrError extends Error\n{\n\n  /**\n   * The version identifier for this Serializable class.\n   * Increment only if the <i>serialized</i> form of the\n   * class changes.\n   */\n  private static final long serialVersionUID = 1L;\n\n  /*\n   * Ordinals for various reasons why an Error of this type can be thrown.\n   */\n\n  /**\n   * Lexical error occurred.\n   */\n  public static final int LEXICAL_ERROR = 0;\n\n  /**\n   * An attempt was made to create a second instance of a static token manager.\n   */\n  public static final int STATIC_LEXER_ERROR = 1;\n\n  /**\n   * Tried to change to an invalid lexical state.\n   */\n  public static final int INVALID_LEXICAL_STATE = 2;\n\n  /**\n   * Detected (and bailed out of) an infinite loop in the token manager.\n   */\n  public static final int LOOP_DETECTED = 3;\n\n  /**\n   * Indicates the reason why the exception is thrown. It will have\n   * one of the above 4 values.\n   */\n  int errorCode;\n\n  /**\n   * Replaces unprintable characters by their escaped (or unicode escaped)\n   * equivalents in the given string\n   */\n  protected static final String addEscapes(String str) {\n    StringBuilder retval = new StringBuilder();\n    char ch;\n    for (int i = 0; i < str.length(); i++) {\n      switch (str.charAt(i))\n      {\n        case '\\b':\n          retval.append(\"\\\\b\");\n          continue;\n        case '\\t':\n          retval.append(\"\\\\t\");\n          continue;\n        case '\\n':\n          retval.append(\"\\\\n\");\n          continue;\n        case '\\f':\n          retval.append(\"\\\\f\");\n          continue;\n        case '\\r':\n          retval.append(\"\\\\r\");\n          continue;\n        case '\\\"':\n          retval.append(\"\\\\\\\"\");\n          continue;\n        case '\\'':\n          retval.append(\"\\\\\\'\");\n          continue;\n        case '\\\\':\n          retval.append(\"\\\\\\\\\");\n          continue;\n        default:\n          if ((ch = str.charAt(i)) < 0x20 || ch > 0x7e) {\n            String s = \"0000\" + Integer.toString(ch, 16);\n            retval.append(\"\\\\u\" + s.substring(s.length() - 4, s.length()));\n          } else {\n            retval.append(ch);\n          }\n          continue;\n      }\n    }\n    return retval.toString();\n  }\n\n  /**\n   * Returns a detailed message for the Error when it is thrown by the\n   * token manager to indicate a lexical error.\n   * Parameters :\n   *    EOFSeen     : indicates if EOF caused the lexical error\n   *    lexState    : lexical state in which this error occurred\n   *    errorLine   : line number when the error occurred\n   *    errorColumn : column number when the error occurred\n   *    errorAfter  : prefix that was seen before this error occurred\n   *    curchar     : the offending character\n   * Note: You can customize the lexical error message by modifying this method.\n   */\n  protected static String LexicalErr(boolean EOFSeen, int lexState, int errorLine, int errorColumn, String errorAfter, int curChar) {\n    return(\"Lexical error at line \" + //\n          errorLine + \", column \" + //\n          errorColumn + \".  Encountered: \" + //\n          (EOFSeen ? \"<EOF>\" : (\"'\" + addEscapes(String.valueOf((char) curChar)) + \"' (\" + curChar + \"),\")) + //\n          (errorAfter == null || errorAfter.length() == 0 ? \"\" : \" after prefix \\\"\" + addEscapes(errorAfter) + \"\\\"\")) + //\n          (lexState == 0 ? \"\" : \" (in lexical state \" + lexState + \")\");\n  }\n\n  /**\n   * You can also modify the body of this method to customize your error messages.\n   * For example, cases like LOOP_DETECTED and INVALID_LEXICAL_STATE are not\n   * of end-users concern, so you can return something like :\n   *\n   *     \"Internal Error : Please file a bug report .... \"\n   *\n   * from this method for such cases in the release version of your parser.\n   */\n  @Override\n  public String getMessage() {\n    return super.getMessage();\n  }\n\n  /*\n   * Constructors of various flavors follow.\n   */\n\n  /** No arg constructor. */\n  public TokenMgrError() {\n  }\n\n  /** Constructor with message and reason. */\n  public TokenMgrError(String message, int reason) {\n    super(message);\n    errorCode = reason;\n  }\n\n  /** Full Constructor. */\n  public TokenMgrError(boolean EOFSeen, int lexState, int errorLine, int errorColumn, String errorAfter, int curChar, int reason) {\n    this(LexicalErr(EOFSeen, lexState, errorLine, errorColumn, errorAfter, curChar), reason);\n  }\n}\n/* JavaCC - OriginalChecksum=e91e0e66d4dd0cdd0c9358f11a60962a (do not edit this line) */\n"
  },
  {
    "path": "prism/src/parser/Values.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.type.Type;\nimport parser.type.TypeUtils;\nimport prism.ModelInfo;\nimport prism.PrismLangException;\nimport prism.PrismUtils;\n\n/**\n * Class to store a list of typed constant/variable values.\n * (Basically, just a mapping from String to Object)\n */\npublic class Values implements Cloneable //implements Comparable\n{\n\tprotected ArrayList<String> names;\n\tprotected ArrayList<Object> values;\n\t\n\t// Constructors\n\t\n\t/**\n\t * Construct a new, empty Values object\n\t */\n\tpublic Values()\n\t{\n\t\tnames = new ArrayList<String>();\n\t\tvalues = new ArrayList<Object>();\n\t}\n\t\n\t/**\n\t * Construct a new Values object by copying an existing one.\n\t * If the existing one is null, it is treated as empty. \n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic Values(Values v)\n\t{\n\t\tif (v == null) {\n\t\t\tnames = new ArrayList<String>();\n\t\t\tvalues = new ArrayList<Object>();\n\t\t} else {\n\t\t\tnames = (ArrayList<String>) v.names.clone();\n\t\t\tvalues = (ArrayList<Object>) v.values.clone();\n\t\t}\n\t}\n\t\n\t/**\n\t * Construct a new Values object by merging two existing ones.\n\t * There is no checking for duplicates.\n\t * Either can be null and, if so, is treated as empty. \n\t */\n\tpublic Values(Values v1, Values v2)\n\t{\n\t\tthis(v1);\n\t\taddValues(v2);\n\t}\n\t\n\t/**\n\t * Construct a new Values object by copying existing State object.\n\t * If it is null, it is treated as empty. \n\t * Need access to model info for variable names.\n\t * @param s State object to copy.\n\t * @param modelInfo Corresponding modelInfo (for variable info/ordering)\n\t */\n\tpublic Values(State s, ModelInfo modelInfo)\n\t{\n\t\tthis();\n\t\tif (s == null) return;\n\t\tint n = s.varValues.length;\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\taddValue(modelInfo.getVarName(i), s.varValues[i]);\n\t\t}\n\t}\n\t\n\t/**\n\t * Add a value (type of value determined by type of Object).\n\t * (Note: there is no checking for duplication/inconsistencies/etc.)\n\t * @param name Constant/variable name\n\t * @param value Value\n\t */\n\tpublic void addValue(String name, Object value)\n\t{\n\t\tnames.add(name);\n\t\tvalues.add(value);\n\t}\n\t\n\t/**\n\t * Add multiple values, specified as a {@link Values} object {@code v}.\n\t * If {@code v} is null, it is treated as empty. \n\t * (Note: there is no checking for duplication/inconsistencies/etc.)\n\t */\n\tpublic void addValues(Values v)\n\t{\n\t\tint i, n;\n\t\t\n\t\tif (v == null) return;\n\t\tn = v.getNumValues();\n\t\tfor (i = 0; i < n; i ++) {\n\t\t\taddValue(v.getName(i), v.getValue(i));\n\t\t}\n\t}\n\t\n\t/**\n\t * Set a value (overwrite if already present)\n\t * Returns 0 if added, -1 if overwritten\n\t * @param name Constant/variable name\n\t * @param value Value\n\t */\n\tpublic int setValue(String name, Object value)\n\t{\n\t\tint i = getIndexOf(name);\n\t\tif (i == -1) {\n\t\t\taddValue(name, value);\n\t\t\treturn 0;\n\t\t}\n\t\telse {\n\t\t\tvalues.set(i, value);\n\t\t\treturn -1;\n\t\t}\n\t}\n\t\n\t/**\n\t * Set multiple values (overwrite if already present)\n\t * Returns number of values overwritten.\n\t */\n\tpublic int setValues(Values v)\n\t{\n\t\tint i, n, c = 0;\n\t\t\n\t\tif (v == null) return c;\n\t\tn = v.getNumValues();\n\t\tfor (i = 0; i < n; i ++) {\n\t\t\tif (setValue(v.getName(i), v.getValue(i)) == 0) c++;\n\t\t}\n\t\t\n\t\treturn c;\n\t}\n\t\n\t/**\n\t * Remove the {@code i}th value added (if present)\n\t */\n\tpublic void removeValue(int i)\n\t{\n\t\tif (i >= 0 && i < getNumValues()) {\n\t\t\tnames.remove(i);\n\t\t\tvalues.remove(i);\n\t\t}\n\t}\n\t\n\t/**\n\t * Remove the value for constant/variable {@code name} (if present)\n\t */\n\tpublic void removeValue(String name)\n\t{\n\t\tint i = getIndexOf(name);\n\t\tif (i != -1) {\n\t\t\tremoveValue(i);\n\t\t}\n\t}\n\t\n\t// Get methods\n\t\n\t/**\n\t * Get the number of values.\n\t */\n\tpublic int getNumValues()\n\t{\n\t\treturn names.size();\n\t}\n\t\n\t/**\n\t * Get the variable/constant name for the {@code i}th value.\n\t */\n\tpublic String getName(int i)\n\t{\n\t\treturn names.get(i);\n\t}\n\n\t/**\n\t * Get a list of all names for values stored.\n\t */\n\tpublic List<String> getNames()\n\t{\n\t\treturn names;\n\t}\n\n\t/**\n\t * Get the index of the value for variable/constant {@code name} (-1 if not present).\n\t */\n\tpublic int getIndexOf(String name)\n\t{\n\t\treturn names.indexOf(name);\n\t}\n\t\n\t/**\n\t * Is there a value for variable/constant {@code name}?\n\t */\n\tpublic boolean contains(String name)\n\t{\n\t\treturn names.contains(name);\n\t}\n\t\n\t/**\n\t * Get the {@code i}th value.\n\t */\n\tpublic Object getValue(int i)\n\t{\n\t\treturn values.get(i);\n\t}\n\t\n\t/**\n\t * Get the value for variable/constant {@code name}.\n\t * @throws PrismLangException if no value is present.\n\t */\n\tpublic Object getValueOf(String name) throws PrismLangException\n\t{\n\t\tint i;\n\t\t\n\t\ti = getIndexOf(name);\n\t\tif (i == -1) throw new PrismLangException(\"Couldn't get value for \\\"\" + name + \"\\\"\");\n\t\treturn getValue(i);\n\t}\n\n\t/**\n\t * Get a list of all values stored.\n\t */\n\tpublic List<Object> getValues()\n\t{\n\t\treturn values;\n\t}\n\n\t/**\n\t * Get a type for the {@code i}th value.\n\t * This is not stored explicitly here, so an appropriate type\n\t * is guessed based on the type of the Object storing the value.\n\t */\n\tpublic Type getType(int i) throws PrismLangException\n\t{\n\t\treturn TypeUtils.guessTypeForValue(values.get(i));\n\t}\n\n\t/**\n\t * Get a list of types for all values stored.\n\t * These are not stored explicitly here, so appropriate types\n\t * are guessed based on the types of the Objects storing the values.\n\t */\n\tpublic List<Type> getTypes() throws PrismLangException\n\t{\n\t\treturn TypeUtils.guessTypesForValues(values);\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tint i, j, n;\n\t\tValues v;\n\t\tString s;\n\t\t\n\t\t// trivial case: null arg\n\t\tif (o == null) return false;\n\t\t// another trivial case: wrong type\n\t\ttry { v = (Values)o; } catch (ClassCastException e) { return false; }\n\t\t// check sizes are equal\n\t\tn = getNumValues();\n\t\tif (v.getNumValues() != n) return false;\n\t\t// check each value\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = getName(i);\n\t\t\tj = v.getIndexOf(s);\n\t\t\tif (j == -1) return false;\n\t\t\to = v.getValue(j);\n\t\t\tif (!getValue(i).equals(o)) return false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t// compare\n\t\n// \tpublic int compareTo(Object o)\n// \t{\n// \t\tint i, j, n, c;\n// \t\tValues v;\n// \t\tString s;\n// \t\tObject c1, c2;\n// \t\t\n// \t\t// trivial case: null arg\n// \t\tif (o == null) throw new NullPointerException();\n// \t\t// cast\n// \t\tv = (Values)o;\n// \t\t// check sizes are equal\n// \t\tn = getNumValues();\n// \t\tif (v.getNumValues() != n) throw new ClassCastException();\n// \t\t// check each value\n// \t\tfor (i = 0; i < n; i++) {\n// \t\t\ts = getName(i);\n// \t\t\tj = v.getIndexOf(s);\n// \t\t\tif (j == -1) throw new ClassCastException();\n// \t\t\tc1 = getValue(i);\n// \t\t\tc2 = v.getValue(j);\n// \t\t\tif (c1 instanceof Double) c = ((Double)c1).compareTo(c2);\n// \t\t\telse if (c1 instanceof Integer) c = ((Integer)c1).compareTo(c2);\n// \t\t\telse {\n// \t\t\t\tboolean b1 = ((Boolean)c1).booleanValue();\n// \t\t\t\tboolean b2 = ((Boolean)c2).booleanValue();\n// \t\t\t\tif (b1 == b2) c = 0; else if (b1 == false) c = -1; else c = 1;\n// \t\t\t}\n// \t\t\tif (c != 0) return c;\n// \t\t}\n// \t\treturn 0;\n// \t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic Values clone()\n\t{\n\t\tValues clone;\n\t\ttry {\n\t\t\tclone = (Values) super.clone();\n\t\t} catch (CloneNotSupportedException e) {\n\t\t\tthrow new InternalError(\"Object#clone is expected to work for Cloneable objects.\", e);\n\t\t}\n\t\tclone.names = (ArrayList<String>) names.clone();\n\t\tclone.values = (ArrayList<Object>) values.clone();\n\t\treturn clone;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn toString(true, \",\");\n\t}\n\t\n\t/**\n\t * Return a string representation of this Values object, e.g. \"x=1,y=2\".\n\t * If {@code printNames} is false, the \"x=\"s are omitted.\n\t * The separator (\",\" above) can be specified in {@code separator}.\n\t * @param printNames Print variable/constant names?\n\t * @param separator String used to separate values in the list \n\t */\n\tpublic String toString(boolean printNames, String separator)\n\t{\n\t\t// Build string of form \"x=1,y=2\"\n\t\tint n = getNumValues();\n\t\tString s = \"\";\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (printNames) {\n\t\t\t\ts += getName(i) + \"=\";\n\t\t\t}\n\t\t\ts += valToString(getValue(i));\n\t\t\tif (i < n-1) {\n\t\t\t\ts += separator;\n\t\t\t}\n\t\t}\n\t\treturn s;\n\t}\n\t\n\t/**\n\t * Build a string for two Values objects, combined.\n\t * Either can be null, meaning an empty object\n\t * If both are empty the resulting string is \"\".\n\t */\n\tpublic static String toStringConcatenated(Values v1, Values v2)\n\t{\n\t\tString s = \"\", s2;\n\t\tif (v1 != null) {\n\t\t\ts += v1.toString();\n\t\t}\n\t\tif (v2 != null) {\n\t\t\ts2 = v2.toString();\n\t\t\tif (s2.length() > 0) {\n\t\t\t\tif (s.length() > 0)\n\t\t\t\t\ts += \",\";\n\t\t\t\ts += s2;\n\t\t\t}\n\t\t}\n\t\treturn s;\n\t}\n\t\n\t/**\n\t * Format a value (as an Object) as a string.\n\t */\n\tpublic static String valToString(Object o)\n\t{\n\t\tString s;\n\t\t\n\t\tif (o instanceof Double) {\n\t\t\ts = PrismUtils.formatDouble(12, (double) o);\n\t\t} else {\n\t\t\ts = String.valueOf(o);\n\t\t}\n\t\t\n\t\treturn s;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/VarList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser;\n\nimport java.util.*;\n\nimport prism.*;\nimport parser.ast.*;\nimport parser.type.*;\n\n/**\n * Class to store information about the set of variables in a PRISM model.\n * Assumes that any constants in the model have been given fixed values.\n * Thus, min/max values for all variables are known.\n * VarList also takes care of how each variable will be encoded to an integer\n * (e.g. for (MT)BDD representation).\n */\npublic class VarList\n{\n\t// List of variables\n\tprivate List<Var> vars;\n\t// Mapping from names to indices\n\tprivate Map<String, Integer> nameMap;\n\t// Total number of bits needed  to encode\n\tprivate int totalNumBits;\n\t\n\t// Evaluation context (constant values + evaluation mode)\n\tprivate EvaluateContext ec;\n\n\t/**\n\t * Construct empty variable list.\n\t */\n\tpublic VarList()\n\t{\n\t\tsetEvaluateContext(EvaluateContext.create());\n\t\tvars = new ArrayList<Var>();\n\t\tnameMap = new HashMap<String, Integer>();\n\t\ttotalNumBits = 0;\n\t}\n\n\t/**\n\t* Construct variable list for a ModelInfo object.\n\t*/\n\tpublic VarList(ModelInfo modelInfo) throws PrismException\n\t{\n\t\tthis();\n\t\tsetEvaluateContext(modelInfo.getEvaluateContext());\n\t\tint numVars = modelInfo.getNumVars();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tDeclarationType declType = modelInfo.getVarDeclarationType(i);\n\t\t\tint module = modelInfo.getVarModuleIndex(i);\n\t\t\taddVar(modelInfo.getVarName(i), declType, module);\n\t\t}\n\t}\n\n\t/**\n\t * Set the evaluation context used to evaluate any expressions,\n\t * e.g. for variable range bounds. This supplies constant values\n\t * and determines the evaluation mode used.\n\t */\n\tpublic void setEvaluateContext(EvaluateContext ec)\n\t{\n\t\tthis.ec = ec;\n\t}\n\n\t/**\n\t * Add a new variable to the end of the VarList.\n\t * @param decl Declaration defining the variable\n\t * @param module Index of module containing variable\n\t */\n\tpublic void addVar(Declaration decl, int module) throws PrismLangException\n\t{\n\t\taddVar(decl.getName(), decl.getDeclType(), module);\n\t}\n\n\t/**\n\t * Add a new variable to the start of the VarList.\n\t * @param decl Declaration defining the variable\n\t * @param module Index of module containing variable\n\t */\n\tpublic void addVarAtStart(Declaration decl, int module) throws PrismLangException\n\t{\n\t\taddVar(0, decl, module);\n\t}\n\t\n\t/**\n\t * Add a new variable at position i in the VarList.\n\t * @param decl Declaration defining the variable\n\t * @param module Index of module containing variable\n\t */\n\tpublic void addVar(int i, Declaration decl, int module) throws PrismLangException\n\t{\n\t\tVar var = createVar(decl.getName(), decl.getDeclType(), module);\n\t\tvars.add(i, var);\n\t\ttotalNumBits += getRangeLogTwo(i);\n\t\t// Recompute name map\n\t\tint j, n;\n\t\tn = getNumVars();\n\t\tnameMap = new HashMap<String, Integer>(n);\n\t\tfor (j = 0; j < n; j++) {\n\t\t\tnameMap.put(getName(j), j);\n\t\t}\n\t}\n\n\t/**\n\t * Add a new variable to the end of the VarList.\n\t * @param name Variable name\n\t * @param declType Type declaration defining the variable\n\t * @param module Index of module containing variable\n\t */\n\tpublic void addVar(String name, DeclarationType declType, int module) throws PrismLangException\n\t{\n\t\tVar var = createVar(name, declType, module);\n\t\tvars.add(var);\n\t\ttotalNumBits += getRangeLogTwo(vars.size() - 1);\n\t\tnameMap.put(name, vars.size() - 1);\n\t}\n\n\t/**\n\t * Create a new variable object to the store in the list.\n\t * @param name Variable name\n\t * @param declType Type declaration defining the variable\n\t * @param module Index of module containing variable\n\t */\n\tprivate Var createVar(String name, DeclarationType declType, int module) throws PrismLangException\n\t{\n\t\tVar var;\n\t\tint low, high;\n\n\t\t// Create new Var object\n\t\tvar = new Var(name, declType.getType());\n\t\tvar.declType = declType;\n\t\tvar.module = module;\n\t\t\n\t\t// Variable is a bounded integer\n\t\tif (declType instanceof DeclarationInt) {\n\t\t\tDeclarationInt intdecl = (DeclarationInt) declType;\n\t\t\tlow = intdecl.getLow().evaluateInt(ec);\n\t\t\thigh = intdecl.getHigh().evaluateInt(ec);\n\t\t\t// Check range is valid\n\t\t\tif (high - low <= 0) {\n\t\t\t\tString s = \"Invalid range (\" + low + \"-\" + high + \") for variable \\\"\" + name + \"\\\"\";\n\t\t\t\tthrow new PrismLangException(s, declType);\n\t\t\t}\n\t\t\tif ((long) high - (long) low >= Integer.MAX_VALUE) {\n\t\t\t\tString s = \"Range for variable \\\"\" + name + \"\\\" (\" + low + \"-\" + high + \") is too big\";\n\t\t\t\tthrow new PrismLangException(s, declType);\n\t\t\t}\n\t\t}\n\t\t// Variable is a Boolean\n\t\telse if (declType instanceof DeclarationBool) {\n\t\t\tlow = 0;\n\t\t\thigh = 1;\n\t\t}\n\t\t// Variable is a clock\n\t\telse if (declType instanceof DeclarationClock) {\n\t\t\t// Create dummy info\n\t\t\tlow = 0;\n\t\t\thigh = 1;\n\t\t}\n\t\t// Variable is an (unbounded) integer\n\t\telse if (declType instanceof DeclarationIntUnbounded) {\n\t\t\t// Create dummy range info\n\t\t\tlow = 0;\n\t\t\thigh = 1;\n\t\t}\n\t\t// Variable is an (unbounded) double\n\t\telse if (declType instanceof DeclarationDoubleUnbounded) {\n\t\t\t// Create dummy range info\n\t\t\tlow = 0;\n\t\t\thigh = 1;\n\t\t}\n\t\telse {\n\t\t\tthrow new PrismLangException(\"Unknown variable type \\\"\" + declType + \"\\\" in declaration\", declType);\n\t\t}\n\n\t\t// Store low/high and return\n\t\tvar.low = low;\n\t\tvar.high = high;\n\n\t\treturn var;\n\t}\n\n\t/**\n\t * Get the number of variables stored in this list.  \n\t */\n\tpublic int getNumVars()\n\t{\n\t\treturn vars.size();\n\t}\n\n\t/**\n\t * Look up the index of a variable, as stored in this list, by name.\n\t * Returns -1 if there is no such variable. \n\t */\n\tpublic int getIndex(String name)\n\t{\n\t\tInteger i = nameMap.get(name);\n\t\treturn (i == null) ? -1 : i;\n\t}\n\n\t/**\n\t * Check if there is a variable of a given name in this list.\n\t */\n\tpublic boolean exists(String name)\n\t{\n\t\treturn getIndex(name) != -1;\n\t}\n\n\t/**\n\t * Get the declaration type of the ith variable in this list.\n\t */\n\tpublic DeclarationType getDeclarationType(int i)\n\t{\n\t\treturn vars.get(i).declType;\n\t}\n\n\t/**\n\t * Get the name of the ith variable in this list.\n\t */\n\tpublic String getName(int i)\n\t{\n\t\treturn vars.get(i).name;\n\t}\n\n\t/**\n\t * Get the type of the ith variable in this list.\n\t */\n\tpublic Type getType(int i)\n\t{\n\t\treturn vars.get(i).type;\n\t}\n\n\t/**\n\t * Get the index of the module of the ith variable in this list (-1 denotes global variable).\n\t */\n\tpublic int getModule(int i)\n\t{\n\t\treturn vars.get(i).module;\n\t}\n\n\t/**\n\t * Get the low value of the ith variable in this list (when encoded as an integer).\n\t */\n\tpublic int getLow(int i)\n\t{\n\t\treturn vars.get(i).low;\n\t}\n\n\t/**\n\t * Get the high value of the ith variable in this list (when encoded as an integer).\n\t */\n\tpublic int getHigh(int i)\n\t{\n\t\treturn vars.get(i).high;\n\t}\n\n\t/**\n\t * Get the range of the ith variable in this list (when encoded as an integer).\n\t */\n\tpublic int getRange(int i)\n\t{\n\t\treturn vars.get(i).high - vars.get(i).low + 1;\n\t}\n\n\t/**\n\t * Get the number of bits required to store the ith variable in this list (when encoded as an integer).\n\t */\n\tpublic int getRangeLogTwo(int i)\n\t{\n\t\treturn (int) Math.ceil(PrismUtils.log2(getRange(i)));\n\t}\n\n\t/**\n\t * Get the total number of bits required to store all variables in this list (when encoded as integers).\n\t */\n\tpublic int getTotalNumBits()\n\t{\n\t\treturn totalNumBits;\n\t}\n\n\t/**\n\t * Get the value (as an Object) for the ith variable, from its encoding as an integer.\n\t * In case of any problems, this will return null.\n\t */\n\tpublic Object decodeFromInt(int i, int val)\n\t{\n\t\ttry {\n\t\t\tType type = getType(i);\n\t\t\t// Integer type\n\t\t\tif (type instanceof TypeInt) {\n\t\t\t\treturn type.castValueTo(val + getLow(i), ec.getEvaluationMode());\n\t\t\t}\n\t\t\t// Boolean type\n\t\t\telse if (type instanceof TypeBool) {\n\t\t\t\treturn val != 0;\n\t\t\t}\n\t\t\t// Unknown\n\t\t\treturn null;\n\t\t} catch (PrismLangException e) {\n\t\t\t// In case of any error return null\n\t\t\treturn null;\n\t\t}\n\t}\n\n\t/**\n\t * Get the integer encoding of a value for the ith variable, specified as an Object.\n\t * The Object is assumed to be of correct type (e.g. Integer, Boolean).\n\t * Throws an exception if Object is of the wrong type.\n\t * Also throws an exception if the value is out of range.\n\t */\n\tpublic int encodeToInt(int i, Object val) throws PrismLangException\n\t{\n\t\tType type = getType(i);\n\t\ttry {\n\t\t\t// Integer type\n\t\t\tif (type instanceof TypeInt) {\n\t\t\t\tint intVal = ((TypeInt) type).castValueTo(val).intValue();\n\t\t\t\tif (intVal < getLow(i) || intVal > getHigh(i)) {\n\t\t\t\t\tthrow new PrismLangException(\"Value \" + val + \" out of range for variable \" + getName(i));\n\t\t\t\t}\n\t\t\t\treturn intVal - getLow(i);\n\t\t\t}\n\t\t\t// Boolean type\n\t\t\telse if (type instanceof TypeBool) {\n\t\t\t\treturn ((TypeBool) type).castValueTo(val).booleanValue() ? 1 : 0;\n\t\t\t}\n\t\t\t// Anything else\n\t\t\telse {\n\t\t\t\tthrow new PrismLangException(\"Unsupported type \" + type + \" for variable \" + getName(i));\n\t\t\t}\n\t\t} catch (ClassCastException e) {\n\t\t\tthrow new PrismLangException(\"Value \" + val + \" is wrong type for variable \" + getName(i));\n\t\t}\n\t}\n\n\t/**\n\t * Get the integer encoding of a value for the ith variable, specified as a string.\n\t */\n\tpublic int encodeToIntFromString(int i, String s) throws PrismLangException\n\t{\n\t\tType type = getType(i);\n\t\t// Integer type\n\t\tif (type instanceof TypeInt) {\n\t\t\ttry {\n\t\t\t\tint iVal = Integer.parseInt(s);\n\t\t\t\tif (iVal < getLow(i) || iVal > getHigh(i)) {\n\t\t\t\t\tthrow new PrismLangException(\"Value \" + iVal + \" out of range for variable \" + getName(i));\n\t\t\t\t}\n\t\t\t\treturn iVal - getLow(i);\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismLangException(\"\\\"\" + s + \"\\\" is not a valid integer value\");\n\t\t\t}\n\t\t}\n\t\t// Boolean type\n\t\telse if (type instanceof TypeBool) {\n\t\t\tif (s.equals(\"true\"))\n\t\t\t\treturn 1;\n\t\t\telse if (s.equals(\"false\"))\n\t\t\t\treturn 0;\n\t\t\telse\n\t\t\t\tthrow new PrismLangException(\"\\\"\" + s + \"\\\" is not a valid Boolean value\");\n\n\t\t}\n\t\t// Anything else\n\t\telse {\n\t\t\tthrow new PrismLangException(\"Unsupported type \" + type + \" for variable \" + getName(i));\n\t\t}\n\t}\n\n\t/**\n\t * Get a list of all possible values for a subset of the variables in this list.\n\t * @param vars The subset of variables\n\t */\n\tpublic List<Values> getAllValues(List<String> vars) throws PrismLangException\n\t{\n\t\tint i, j, k, n, lo, hi;\n\t\tVector<Values> allValues;\n\t\tValues vals, valsNew;\n\n\t\tallValues = new Vector<Values>();\n\t\tallValues.add(new Values());\n\t\tfor (String var : vars) {\n\t\t\ti = getIndex(var);\n\t\t\tif (getType(i) instanceof TypeBool) {\n\t\t\t\tn = allValues.size();\n\t\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\t\tvals = allValues.get(j);\n\t\t\t\t\tvalsNew = new Values(vals);\n\t\t\t\t\tvalsNew.setValue(var, true);\n\t\t\t\t\tallValues.add(valsNew);\n\t\t\t\t\tvals.addValue(var, false);\n\t\t\t\t}\n\t\t\t} else if (getType(i) instanceof TypeInt) {\n\t\t\t\tlo = getLow(i);\n\t\t\t\thi = getHigh(i);\n\t\t\t\tn = allValues.size();\n\t\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\t\tvals = allValues.get(j);\n\t\t\t\t\tfor (k = lo + 1; k < hi + 1; k++) {\n\t\t\t\t\t\tvalsNew = new Values(vals);\n\t\t\t\t\t\tvalsNew.setValue(var, getType(i).castValueTo(k, ec.getEvaluationMode()));\n\t\t\t\t\t\tallValues.add(valsNew);\n\t\t\t\t\t}\n\t\t\t\t\tvals.addValue(var, getType(i).castValueTo(lo, ec.getEvaluationMode()));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismLangException(\"Cannot determine all values for a variable of type \" + getType(i));\n\t\t\t}\n\t\t}\n\n\t\treturn allValues;\n\t}\n\n\t/**\n\t * Get a list of all possible states over the variables in this list. Use with care!\n\t */\n\tpublic List<State> getAllStates() throws PrismLangException\n\t{\n\t\tList<State> allStates;\n\t\tState state, stateNew;\n\n\t\tint numVars = getNumVars();\n\t\tallStates = new ArrayList<State>();\n\t\tallStates.add(new State(numVars));\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tif (getType(i) instanceof TypeBool) {\n\t\t\t\tint n = allStates.size();\n\t\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\t\tstate = allStates.get(j);\n\t\t\t\t\tstateNew = new State(state);\n\t\t\t\t\tstateNew.setValue(i, true);\n\t\t\t\t\tstate.setValue(i, false);\n\t\t\t\t\tallStates.add(stateNew);\n\t\t\t\t}\n\t\t\t} else if (getType(i) instanceof TypeInt) {\n\t\t\t\tint lo = getLow(i);\n\t\t\t\tint hi = getHigh(i);\n\t\t\t\tint n = allStates.size();\n\t\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\t\tstate = allStates.get(j);\n\t\t\t\t\tfor (int k = lo + 1; k < hi + 1; k++) {\n\t\t\t\t\t\tstateNew = new State(state);\n\t\t\t\t\t\tstateNew.setValue(i, getType(i).castValueTo(k, ec.getEvaluationMode()));\n\t\t\t\t\t\tallStates.add(stateNew);\n\t\t\t\t\t}\n\t\t\t\t\tstate.setValue(i, getType(i).castValueTo(lo, ec.getEvaluationMode()));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismLangException(\"Cannot determine all values for a variable of type \" + getType(i));\n\t\t\t}\n\t\t}\n\n\t\treturn allStates;\n\t}\n\n\t/**\n\t * Convert a bit vector representing a single state to a State object. \n\t */\n\tpublic State convertBitSetToState(BitSet bits)\n\t{\n\t\tint i, n, j, var, val;\n\t\tState state;\n\t\tstate = new State(getNumVars());\n\t\tvar = val = j = 0;\n\t\tn = totalNumBits;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (bits.get(i))\n\t\t\t\tval += (1 << (getRangeLogTwo(var) - j - 1));\n\t\t\tif (j >= getRangeLogTwo(var) - 1) {\n\t\t\t\tstate.setValue(var, decodeFromInt(var, val));\n\t\t\t\tvar++;\n\t\t\t\tval = 0;\n\t\t\t\tj = 0;\n\t\t\t} else {\n\t\t\t\tj++;\n\t\t\t}\n\t\t}\n\t\treturn state;\n\t}\n\n\t/**\n\t * Clone this list.\n\t */\n\tpublic Object clone()\n\t{\n\t\tint i, n;\n\t\tn = getNumVars();\n\t\tVarList rv = new VarList();\n\t\trv.setEvaluateContext(ec);\n\t\trv.vars = new ArrayList<Var>(n);\n\t\trv.nameMap = new HashMap<String, Integer>(n);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\trv.vars.add(new Var(vars.get(i)));\n\t\t\trv.nameMap.put(getName(i), i);\n\t\t}\n\t\treturn rv;\n\t}\n\n\t/**\n\t * Class to store information about a single variable.\n\t */\n\tclass Var\n\t{\n\t\t// Name\n\t\tpublic String name;\n\t\t// Type\n\t\tpublic Type type;\n\t\t// Further type info from variable declaration\n\t\tpublic DeclarationType declType;\n\t\t// Index of containing module (-1 for a global)\n\t\tpublic int module;\n\t\t// Info about how variable is encoded as an integer\n\t\tpublic int low;\n\t\tpublic int high;\n\n\t\t/** Default constructor */\n\t\tpublic Var(String name, Type type)\n\t\t{\n\t\t\tthis.name = name;\n\t\t\tthis.type = type;\n\t\t}\n\n\t\t/** Copy constructor */\n\t\tpublic Var(Var var)\n\t\t{\n\t\t\tname = var.name;\n\t\t\ttype = var.type;\n\t\t\tdeclType = (DeclarationType) var.declType.deepCopy();\n\t\t\tmodule = var.module;\n\t\t\tlow = var.low;\n\t\t\thigh = var.high;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/ASTElement.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.EvaluateContext;\nimport parser.EvaluateContextConstants;\nimport parser.EvaluateContextState;\nimport parser.EvaluateContextSubstate;\nimport parser.EvaluateContextValues;\nimport parser.State;\nimport parser.Token;\nimport parser.Values;\nimport parser.type.Type;\nimport parser.visitor.ASTTraverse;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.ComputeProbNesting;\nimport parser.visitor.DeepCopy;\nimport parser.visitor.EvaluatePartially;\nimport parser.visitor.ExpandConstants;\nimport parser.visitor.ExpandFormulas;\nimport parser.visitor.ExpandLabels;\nimport parser.visitor.ExpandPropRefsAndLabels;\nimport parser.visitor.FindAllActions;\nimport parser.visitor.FindAllConstants;\nimport parser.visitor.FindAllFormulas;\nimport parser.visitor.FindAllObsRefs;\nimport parser.visitor.FindAllPropRefs;\nimport parser.visitor.FindAllVars;\nimport parser.visitor.GetAllConstants;\nimport parser.visitor.GetAllFormulas;\nimport parser.visitor.GetAllLabels;\nimport parser.visitor.GetAllPropRefs;\nimport parser.visitor.GetAllPropRefsRecursively;\nimport parser.visitor.GetAllUndefinedConstantsRecursively;\nimport parser.visitor.GetAllVars;\nimport parser.visitor.Rename;\nimport parser.visitor.SemanticCheck;\nimport parser.visitor.Simplify;\nimport parser.visitor.ToTreeString;\nimport parser.visitor.TypeCheck;\nimport prism.PrismLangException;\n\n// Abstract class for PRISM language AST elements\n\npublic abstract class ASTElement implements Cloneable\n{\n\t// Type - default to null (unknown)\n\tprotected Type type = null;\n\t// Position in the file - default to -1s (unknown)\n\tprotected int beginLine = -1;\n\tprotected int beginColumn = -1;\n\tprotected int endLine = -1;\n\tprotected int endColumn = -1;\n\n\t// Set methods\n\n\tpublic void setType(Type t)\n\t{\n\t\ttype = t;\n\t}\n\n\tpublic void setBeginColumn(int beginColumn)\n\t{\n\t\tthis.beginColumn = beginColumn;\n\t}\n\n\tpublic void setBeginLine(int beginLine)\n\t{\n\t\tthis.beginLine = beginLine;\n\t}\n\n\tpublic void setEndColumn(int endColumn)\n\t{\n\t\tthis.endColumn = endColumn;\n\t}\n\n\tpublic void setEndLine(int endLine)\n\t{\n\t\tthis.endLine = endLine;\n\t}\n\n\tpublic void setPosition(int beginLine, int beginColumn, int endLine, int endColumn)\n\t{\n\t\tthis.beginLine = beginLine;\n\t\tthis.beginColumn = beginColumn;\n\t\tthis.endLine = endLine;\n\t\tthis.endColumn = endColumn;\n\t}\n\n\tpublic void setPosition(Token begin, Token end)\n\t{\n\t\tthis.beginLine = begin.beginLine;\n\t\tthis.beginColumn = begin.beginColumn;\n\t\tthis.endLine = end.endLine;\n\t\tthis.endColumn = end.endColumn;\n\t}\n\n\tpublic void setPosition(Token token)\n\t{\n\t\tsetPosition(token, token);\n\t}\n\n\tpublic void setPosition(ASTElement begin, ASTElement end)\n\t{\n\t\tthis.beginLine = begin.getBeginLine();\n\t\tthis.beginColumn = begin.getBeginColumn();\n\t\tthis.endLine = end.getEndLine();\n\t\tthis.endColumn = end.getEndColumn();\n\t}\n\n\tpublic void setPosition(ASTElement e)\n\t{\n\t\tsetPosition(e, e);\n\t}\n\n\t/**\n\t * Remove any positional info, i.e., set begin/end line/column numbers to -1\n\t */\n\tpublic void clearPosition()\n\t{\n\t\tsetPosition(-1, -1, -1, -1);\n\t}\n\n\t/**\n\t * Remove any positional info, i.e., set begin/end line/column numbers to -1,\n\t * in this ASTElement and all of its children.\n\t */\n\tpublic void clearPositionRecursively()\n\t{\n\t\ttry {\n\t\t\t// NB: Don't need ASTTraverse since the structure is never changed\n\t\t\taccept(new ASTTraverse()\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic void defaultVisitPost(ASTElement e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tclearPosition();\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (PrismLangException e) {\n\t\t\t// Ignore any errors during traversal\n\t\t}\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the type for this element. It should have already been computed\n\t * by calling typeCheck(). If not, it will be computed first but, in\n\t * the case of error, you will get \"unknown\" (null) type, not the error.\n\t */\n\tpublic Type getType()\n\t{\n\t\tif (type != null)\n\t\t\treturn type;\n\t\ttry {\n\t\t\ttypeCheck();\n\t\t} catch (PrismLangException e) {\n\t\t\t// Returns null (unknown) in case of error.\n\t\t\t// If you want to check for errors, use typeCheck().\n\t\t\treturn null;\n\t\t}\n\t\treturn type;\n\t}\n\n\t/**\n\t * Get the type for this element but, unlike getType(), don't call typeCheck()\n\t * if it has not been computed yet - just return null instead.\n\t */\n\tpublic Type getTypeIfDefined()\n\t{\n\t\treturn type;\n\t}\n\n\tpublic boolean hasPosition()\n\t{\n\t\treturn beginLine != -1;\n\t}\n\n\tpublic int getBeginLine()\n\t{\n\t\treturn beginLine;\n\t}\n\n\tpublic int getBeginColumn()\n\t{\n\t\treturn beginColumn;\n\t}\n\n\tpublic String getBeginString()\n\t{\n\t\treturn \"line \" + beginLine + \", column \" + beginColumn;\n\t}\n\n\tpublic int getEndLine()\n\t{\n\t\treturn endLine;\n\t}\n\n\tpublic int getEndColumn()\n\t{\n\t\treturn endColumn;\n\t}\n\n\tpublic String getEndString()\n\t{\n\t\treturn \"line \" + endLine + \", column \" + endColumn;\n\t}\n\n\t// Methods required for ASTElement (all subclasses should implement):\n\n\t/**\n\t * Visitor method.\n\t */\n\tpublic abstract Object accept(ASTVisitor v) throws PrismLangException;\n\n\t/**\n\t * Convert to string.\n\t */\n\tpublic abstract String toString();\n\n\t/**\n\t * Perform a deep copy.\n\t */\n\tpublic ASTElement deepCopy()\n\t{\n\t\ttry {\n\t\t\treturn new DeepCopy().copy(this);\n\t\t} catch (PrismLangException e) {\n\t\t\tthrow new Error(e);\n\t\t}\n\t}\n\n\t/**\n\t * Perform a deep copy of all internal ASTElements using a deep copy visitor.\n\t * This method is usually called after {@code clone()} and must return the receiver.\n\t *\n\t * @param copier the copy visitor\n\t * @return the receiver with deep-copied subcomponents\n\t * @throws PrismLangException\n\t * @see #clone()\n\t */\n\tpublic abstract ASTElement deepCopy(DeepCopy copier) throws PrismLangException;\n\n\t/**\n\t * Perform a shallow copy of the receiver and\n\t * clone all internal containers, e.g., lists and vectors, too.\n\t */\n\t@Override\n\tpublic ASTElement clone()\n\t{\n\t\ttry {\n\t\t\treturn (ASTElement) super.clone();\n\t\t} catch (CloneNotSupportedException e) {\n\t\t\tthrow new InternalError(\"Object#clone is expected to work for Cloneable objects\", e);\n\t\t}\n\t}\n\n\t// Various methods based on AST traversals (implemented using the visitor\n\t// pattern):\n\n\t/**\n\t * Find all idents which are formulas, replace with ExpressionFormula,\n\t * return result.\n\t */\n\tpublic ASTElement findAllFormulas(FormulaList formulaList) throws PrismLangException\n\t{\n\t\tFindAllFormulas visitor = new FindAllFormulas(formulaList);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Expand all formulas, return result.\n\t * @param formulaList The FormulaList for formula definitions\n\t */\n\tpublic ASTElement expandFormulas(FormulaList formulaList) throws PrismLangException\n\t{\n\t\treturn expandFormulas(formulaList, true);\n\t}\n\n\t/**\n\t * Expand all formulas, return result.\n\t * @param formulaList The FormulaList for formula definitions\n\t * @param replace Whether to replace formulas outright with their definition\n\t * (true for use in models since they may be subjected to renaming afterwards;\n\t * false for properties since it is cleaner just to have the name there when displayed)\n\t */\n\tpublic ASTElement expandFormulas(FormulaList formulaList, boolean replace) throws PrismLangException\n\t{\n\t\tExpandFormulas visitor = new ExpandFormulas(formulaList, replace);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Get all formulas (i.e. ExpressionFormula objects), store names in set.\n\t */\n\tpublic List<String> getAllFormulas() throws PrismLangException\n\t{\n\t\tList<String> v = new ArrayList<>();\n\t\tGetAllFormulas visitor = new GetAllFormulas(v);\n\t\taccept(visitor);\n\t\treturn v;\n\t}\n\n\t/**\n\t * Rename (according to RenamedModule definition), return result.\n\t */\n\tpublic ASTElement rename(RenamedModule rm) throws PrismLangException\n\t{\n\t\tRename visitor = new Rename(rm);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Find all idents which are constants, replace with ExpressionConstant, return result.\n\t */\n\tpublic ASTElement findAllConstants(ConstantList constantList) throws PrismLangException\n\t{\n\t\tFindAllConstants visitor = new FindAllConstants(constantList);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Find all idents which are constants, replace with ExpressionConstant, return result.\n\t */\n\tpublic ASTElement findAllConstants(List<String> constIdents, List<Type> constTypes) throws PrismLangException\n\t{\n\t\tFindAllConstants visitor = new FindAllConstants(constIdents, constTypes);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Get all constants (i.e. ExpressionConstant objects), store names in set.\n\t */\n\tpublic List<String> getAllConstants()\n\t{\n\t\tList<String> v = new ArrayList<>();\n\t\tGetAllConstants visitor = new GetAllConstants(v);\n\t\ttry {\n\t\t\taccept(visitor);\n\t\t} catch (PrismLangException e) {\n\t\t\t// GetAllConstants never throws an exception\n\t\t\t// (but base traversal class is defined so that it can)\n\t\t}\n\t\treturn v;\n\t}\n\n\t/**\n\t* Get all undefined constants used (i.e. in ExpressionConstant objects) recursively and return as a list.\n\t* Recursive descent means that we also find constants that are used within other constants, labels, properties.\n\t* We only recurse into constants/labels/properties in the passed in lists.\n\t* Any others discovered are ignored (and not descended into).\n\t* ConstantList must be non-null so that we can determine which constants are undefined;\n\t* LabelList and PropertiesFile passed in as null are ignored.\n\t */\n\tpublic List<String> getAllUndefinedConstantsRecursively(ConstantList constantList, LabelList labelList, PropertiesFile propertiesFile)\n\t{\n\t\tList<String> v = new ArrayList<>();\n\t\tGetAllUndefinedConstantsRecursively visitor = new GetAllUndefinedConstantsRecursively(v, constantList, labelList, propertiesFile);\n\t\ttry {\n\t\t\taccept(visitor);\n\t\t} catch (PrismLangException e) {\n\t\t\t// Should not happen; ignore. \n\t\t}\n\t\treturn v;\n\t}\n\n\t/**\n\t * Expand constants whose definitions are contained in the supplied ConstantList.\n\t * Throw an exception if constants are found with no definitions.\n\t * @param constantList The ConstantList containing definitions\n\t */\n\tpublic ASTElement expandConstants(ConstantList constantList) throws PrismLangException\n\t{\n\t\treturn expandConstants(constantList, true);\n\t}\n\n\t/**\n\t * Expand constants whose definitions are contained in the supplied ConstantList.\n\t * @param constantList The ConstantList containing definitions\n\t * @param all If true, an exception is thrown if any constants are undefined\n\t */\n\tpublic ASTElement expandConstants(ConstantList constantList, boolean all) throws PrismLangException\n\t{\n\t\tExpandConstants visitor = new ExpandConstants(constantList, all);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Replace some constants with values.\n\t * Note: This is the same as evaluatePartially(constantValues, null).\n\t */\n\tpublic ASTElement replaceConstants(Values constantValues) throws PrismLangException\n\t{\n\t\treturn evaluatePartially(new EvaluateContextConstants(constantValues));\n\t}\n\n\t/**\n\t * Find all references to variables, replace any identifier objects with variable objects,\n\t * check variables exist and store their index (as defined by the containing ModuleFile).\n\t */\n\tpublic ASTElement findAllVars(List<String> varIdents, List<Type> varTypes) throws PrismLangException\n\t{\n\t\tFindAllVars visitor = new FindAllVars(varIdents, varTypes);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Get all variables (i.e. ExpressionVar objects), store names in set.\n\t */\n\tpublic List<String> getAllVars() throws PrismLangException\n\t{\n\t\tList<String> v = new ArrayList<>();\n\t\tGetAllVars visitor = new GetAllVars(v);\n\t\taccept(visitor);\n\t\treturn v;\n\t}\n\n\t/**\n\t * Replace some variables with values.\n\t * Note: This is the same as evaluatePartially(null, varValues).\n\t */\n\tpublic ASTElement replaceVars(Values varValues) throws PrismLangException\n\t{\n\t\treturn evaluatePartially(new EvaluateContextValues(null, varValues));\n\t}\n\n\t/**\n\t * Get all labels (i.e. ExpressionLabel objects), store names in set.\n\t * Special labels \"deadlock\", \"init\" *are* included in the list.\n\t */\n\tpublic List<String> getAllLabels() throws PrismLangException\n\t{\n\t\tList<String> v = new ArrayList<>();\n\t\tGetAllLabels visitor = new GetAllLabels(v);\n\t\taccept(visitor);\n\t\treturn v;\n\t}\n\n\t/**\n\t * Expand labels, return result.\n\t * Special labels \"deadlock\", \"init\" and any not in list are left.\n\t * @param labelList The LabelList for label definitions\n\t */\n\tpublic ASTElement expandLabels(LabelList labelList) throws PrismLangException\n\t{\n\t\tExpandLabels visitor = new ExpandLabels(labelList);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Find all references to properties (by name), replace the ExpressionLabels with ExpressionProp objects.\n\t */\n\tpublic ASTElement findAllPropRefs(ModulesFile mf, PropertiesFile pf) throws PrismLangException\n\t{\n\t\tFindAllPropRefs visitor = new FindAllPropRefs(mf, pf);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Get all references to properties (by name) (i.e. ExpressionProp objects), store names in set.\n\t */\n\tpublic List<String> getAllPropRefs() throws PrismLangException\n\t{\n\t\tList<String> v = new ArrayList<>();\n\t\tGetAllPropRefs visitor = new GetAllPropRefs(v);\n\t\taccept(visitor);\n\t\treturn v;\n\t}\n\n\t/**\n\t * Get all references to properties (by name) (i.e. ExpressionProp objects) recursively, store names in set.\n\t */\n\tpublic List<String> getAllPropRefsRecursively(PropertiesFile propertiesFile) throws PrismLangException\n\t{\n\t\tList<String> v = new ArrayList<>();\n\t\tGetAllPropRefsRecursively visitor = new GetAllPropRefsRecursively(v, propertiesFile);\n\t\taccept(visitor);\n\t\treturn v;\n\t}\n\n\t/**\n\t * Find all references to observables (by name), replace the ExpressionLabels with ExpressionObs objects.\n\t */\n\tpublic ASTElement findAllObsRefs(List<String> observableNames, List<Type> observableTypes) throws PrismLangException\n\t{\n\t\tFindAllObsRefs visitor = new FindAllObsRefs(observableNames, observableTypes);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Expand property references and labels, return result.\n\t * Property expansion is done recursively.\n\t * Special labels \"deadlock\", \"init\" and any not in label list are left.\n\t * @param propertiesFile The PropertiesFile for property lookup\n\t * @param labelList The LabelList for label definitions\n\t */\n\tpublic ASTElement expandPropRefsAndLabels(PropertiesFile propertiesFile, LabelList labelList) throws PrismLangException\n\t{\n\t\tExpandPropRefsAndLabels visitor = new ExpandPropRefsAndLabels(propertiesFile, labelList);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Find all references to action labels, check they exist and, if required,\n\t * store their index locally (as defined by the containing ModuleFile).\n\t */\n\tpublic ASTElement findAllActions(List<String> synchs) throws PrismLangException\n\t{\n\t\tFindAllActions visitor = new FindAllActions(synchs);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Check for type-correctness and compute type.\n\t * Passed in PropertiesFile might be needed to find types for property references.\n\t */\n\tpublic void typeCheck(PropertiesFile propertiesFile) throws PrismLangException\n\t{\n\t\tTypeCheck visitor = new TypeCheck(propertiesFile);\n\t\taccept(visitor);\n\t}\n\n\t/**\n\t * Check for type-correctness and compute type.\n\t * If you are checking a property that might contain references to other properties, use {@link #typeCheck(PropertiesFile)}.\n\t */\n\tpublic void typeCheck() throws PrismLangException\n\t{\n\t\tTypeCheck visitor = new TypeCheck();\n\t\taccept(visitor);\n\t}\n\n\t/**\n\t * Perform any required semantic checks. These are just simple checks on expressions, mostly.\n\t * For semantic checks on models and properties, specifically, see:\n\t * {@link parser.visitor.ModulesFileSemanticCheck} and {@link parser.visitor.PropertiesSemanticCheck}. \n\t * These checks are done *before* any undefined constants have been defined.\n\t */\n\tpublic void semanticCheck() throws PrismLangException\n\t{\n\t\tSemanticCheck visitor = new SemanticCheck();\n\t\taccept(visitor);\n\t}\n\n\t/**\n\t * Evaluate partially: replace some constants and variables with actual values.\n\t * Warning: Unlike evaluate(), evaluatePartially() methods modify (and return) the expression. \n\t */\n\tpublic ASTElement evaluatePartially(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tEvaluatePartially visitor = new EvaluatePartially(ec);\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Evaluate partially: replace some constants with actual values. \n\t * Constants are specified as a Values object.\n\t * Warning: Unlike evaluate(), evaluatePartially() methods modify (and return) the expression. \n\t */\n\tpublic ASTElement evaluatePartially(Values constantValues) throws PrismLangException\n\t{\n\t\treturn evaluatePartially(new EvaluateContextValues(constantValues, null));\n\t}\n\n\t/**\n\t * Evaluate partially: replace some constants and variables with actual values. \n\t * Constants/variables are specified as Values objects; either can be left null.\n\t * Warning: Unlike evaluate(), evaluatePartially() methods modify (and return) the expression. \n\t */\n\tpublic ASTElement evaluatePartially(Values constantValues, Values varValues) throws PrismLangException\n\t{\n\t\treturn evaluatePartially(new EvaluateContextValues(constantValues, varValues));\n\t}\n\n\t/**\n\t * Evaluate partially: replace variables with actual values, specified as a State object.\n\t * Warning: Unlike evaluate(), evaluatePartially() methods modify (and return) the expression. \n\t */\n\tpublic ASTElement evaluatePartially(State state) throws PrismLangException\n\t{\n\t\treturn evaluatePartially(new EvaluateContextState(state));\n\t}\n\n\t/**\n\t * Evaluate partially: replace variables with actual values, specified as a State object.\n\t * Constant values are supplied as a Values object. \n\t * Warning: Unlike evaluate(), evaluatePartially() methods modify (and return) the expression. \n\t */\n\tpublic ASTElement evaluatePartially(Values constantValues, State state) throws PrismLangException\n\t{\n\t\treturn evaluatePartially(new EvaluateContextState(constantValues, state));\n\t}\n\n\t/**\n\t * Evaluate partially: replace some variables with actual values. \n\t * Variables are specified as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset). \n\t * Warning: Unlike evaluate(), evaluatePartially() methods modify (and return) the expression. \n\t */\n\tpublic ASTElement evaluatePartially(State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluatePartially(new EvaluateContextSubstate(substate, varMap));\n\t}\n\n\t/**\n\t * Simplify expressions (constant propagation, ...)\n\t */\n\tpublic ASTElement simplify() throws PrismLangException\n\t{\n\t\tSimplify visitor = new Simplify();\n\t\treturn (ASTElement) accept(visitor);\n\t}\n\n\t/**\n\t * Compute (maximum) number of nested probabilistic operators (P, S, R).\n\t */\n\tpublic int computeProbNesting() throws PrismLangException\n\t{\n\t\tComputeProbNesting visitor = new ComputeProbNesting();\n\t\taccept(visitor);\n\t\treturn visitor.getMaxNesting();\n\t}\n\n\t/**\n\t * Compute (maximum) number of nested probabilistic operators (P, S, R).\n\t * Optionally, pass a properties file for looking up property references.\n\t */\n\tpublic int computeProbNesting(PropertiesFile propertiesFile) throws PrismLangException\n\t{\n\t\tComputeProbNesting visitor = new ComputeProbNesting(propertiesFile);\n\t\taccept(visitor);\n\t\treturn visitor.getMaxNesting();\n\t}\n\n\t/**\n\t * Convert to string showing tree representation.\n\t */\n\tpublic String toTreeString()\n\t{\n\t\tToTreeString visitor = new ToTreeString();\n\t\ttry {\n\t\t\taccept(visitor);\n\t\t} catch (PrismLangException e) {\n\t\t\treturn e.toString();\n\t\t}\n\t\treturn visitor.getString();\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/Coalition.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.Map;\n\nimport prism.PrismUtils;\n\n/**\n * Class to represent coalition info, e.g., in an ExpressionStrategy object.\n * Stored as a list of strings which are either player names (e.g. \"controller\")\n * or player indices (e.g. \"2\"). Alternatively, \"*\" denotes all players.\n */\npublic class Coalition\n{\n\t/** Is coalition all players? (denoted by *) */\n\tprotected boolean allPlayers;\n\t\n\t/** Coalition: list of player names/indices */\n\tprotected List<String> players; \n\t\n\t// Constructors\n\n\t/**\n\t * Default constructor: empty player list\n\t */\n\tpublic Coalition()\n\t{\n\t\t// Empty list of players\n\t\tallPlayers = false;\n\t\tplayers = new ArrayList<String>();\n\t}\n\n\t/**\n\t * Copy constructor\n\t */\n\tpublic Coalition(Coalition c)\n\t{\n\t\t// Copy all info (though, strictly speaking, \"players\" is irrelevant if allPlayers==true\n\t\t// (note that we access c.players directly since getPlayers() can return null)\n\t\tallPlayers = c.isAllPlayers();\n\t\tplayers = new ArrayList<String>(c.players);\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Make this coalition comprise all players (denoted \"*\")\n\t */\n\tpublic void setAllPlayers()\n\t{\n\t\tallPlayers = true;\n\t\tplayers.clear();;\n\t}\n\n\t/**\n\t * Make this coalition comprise these players\n\t * (each string can be a player name or an integer player index)\n\t */\n\tpublic void setPlayers(List<String> players)\n\t{\n\t\tallPlayers = false;\n\t\tthis.players.clear();\n\t\tthis.players.addAll(players);\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Does this coalition comprise all players? (denoted \"*\")\n\t */\n\tpublic boolean isAllPlayers()\n\t{\n\t\treturn allPlayers;\n\t}\n\t\n\t/**\n\t * Is this coalition empty?\n\t */\n\tpublic boolean isEmpty()\n\t{\n\t\treturn !allPlayers && players.isEmpty();\n\t}\n\t\n\t/**\n\t * Get a list of strings describing the coalition\n\t * (each string can be a player name or an integer player index).\n\t * This will be null is the coalition is \"*\" (all players).\n\t */\n\tpublic List<String> getPlayers()\n\t{\n\t\treturn allPlayers ? null : players;\n\t}\n\t\n\t/**\n\t * Check if a given player (specified by its index) is in the coalition,\n\t * i.e., if the index or the name of the player with this index is in the list.\n\t * The mapping from player indices to player names is passed in.\n\t */\n\tpublic boolean isPlayerIndexInCoalition(int index, Map<Integer, String> playerNames)\n\t{\n\t\tif (allPlayers) {\n\t\t\treturn true;\n\t\t}\n\t\tif (players.contains(\"\" + index)) {\n\t\t\treturn true;\n\t\t}\n\t\tString playerName = playerNames.get(index);\n\t\tif (playerName != null && !\"\".equals(playerName) && players.contains(playerName)) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn allPlayers ? \"*\" : PrismUtils.joinString(players, \",\");\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + (allPlayers ? 1231 : 1237);\n\t\tresult = prime * result + ((players == null) ? 0 : players.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tCoalition other = (Coalition) obj;\n\t\tif (allPlayers != other.allPlayers)\n\t\t\treturn false;\n\t\tif (players == null) {\n\t\t\tif (other.players != null)\n\t\t\t\treturn false;\n\t\t} else if (!players.equals(other.players))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/Command.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class Command extends ASTElement\n{\n\t// Action label\n\tprivate String synch;\n\t// Index of action label in model's list of all actions (\"synchs\")\n\t// This is 1-indexed, with 0 denoting an independent (\"tau\"-labelled) command.\n\t// -1 denotes not (yet) known.\n\tprivate int synchIndex;\n\t// Guard\n\tprivate Expression guard;\n\t// List of updates\n\tprivate Updates updates;\n\t// Parent module\n\tprivate Module parent;\n\t\n\t// Constructor\n\t\n\tpublic Command()\n\t{\n\t\tsynch = \"\";\n\t\tsynchIndex = -1;\n\t\tguard = null;\n\t\tupdates = null;\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void setSynch(String s)\n\t{\n\t\tsynch = s;\n\t}\n\t\n\tpublic void setSynchIndex(int i)\n\t{\n\t\tsynchIndex = i;\n\t}\n\t\n\tpublic void setGuard(Expression g)\n\t{\n\t\tguard = g;\n\t}\n\t\n\tpublic void setUpdates(Updates u)\n\t{\n\t\tupdates = u;\n\t\tu.setParent(this);\n\t}\n\t\n\tpublic void setParent(Module m)\n\t{\n\t\tparent = m;\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the action label for this command. For independent (\"tau\"-labelled) commands,\n\t * this is the empty string \"\" (it should never be null).\n\t */\n\tpublic String getSynch()\n\t{\n\t\treturn synch;\n\t}\n\t\n\t/**\n\t * Get the index of the action label for this command (in the model's list of actions).\n\t * This is 1-indexed, with 0 denoting an independent (\"tau\"-labelled) command.\n\t// -1 denotes not (yet) known.\n\t */\n\tpublic int getSynchIndex()\n\t{\n\t\treturn synchIndex;\n\t}\n\n\t/**\n\t * Returns true if this is an unlabelled command (\"[] ...\"),\n\t * i.e., if there is no synchronous action label attached to it.\n\t */\n\tpublic boolean isUnlabelled()\n\t{\n\t\treturn \"\".equals(getSynch());\n\t}\n\n\tpublic Expression getGuard()\n\t{\n\t\treturn guard;\n\t}\n\t\n\tpublic Updates getUpdates()\n\t{\n\t\treturn updates;\n\t}\n\t\n\tpublic Module getParent()\n\t{\n\t\treturn parent;\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"[\" + synch;\n\t\ts += \"] \" + guard + \" -> \" + updates;\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic Command deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tguard = copier.copy(guard);\n\t\tsetUpdates(copier.copy(updates));\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic Command clone()\n\t{\n\t\treturn (Command) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ConstantList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.EvaluateContext;\nimport parser.Values;\nimport parser.type.Type;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\nimport prism.PrismUtils;\n\n/**\n * Class to store list of (defined and undefined) constants\n */\npublic class ConstantList extends ASTElement\n{\n\t// Name/expression/type triples to define constants\n\tprivate ArrayList<String> names = new ArrayList<>();\n\tprivate ArrayList<Expression> constants = new ArrayList<>(); // these can be null, i.e. undefined\n\tprivate ArrayList<Type> types = new ArrayList<>();\n\t// We also store an ExpressionIdent to match each name.\n\t// This is to just to provide positional info.\n\tprivate ArrayList<ExpressionIdent> nameIdents = new ArrayList<>();\n\n\t/**\n\t * Construct an empty constants list.\n\t */\n\tpublic ConstantList()\n\t{\n\t}\n\n\t/**\n\t * Construct a constants list from a Values object, i.e., a list of name=value pairs.\n\t * This is just for convenience and only works for constants of primitive type.\n\t * In general, it is preferred to construct an empty list and then repeatedly call\n\t * {@link #addConstant(ExpressionIdent, Expression, Type)}\n\t * so that the type of each constant can be reliably determined.\n\t */\n\tpublic ConstantList(Values constValues) throws PrismLangException\n\t{\n\t\tint numConsts = constValues.getNumValues();\n\t\tfor (int i = 0; i < numConsts; i++) {\n\t\t\tExpressionIdent nameIdent = new ExpressionIdent(constValues.getName(i));\n\t\t\tExpression constDefn = new ExpressionLiteral(type, constValues.getValue(i));\n\t\t\taddConstant(nameIdent, constDefn, constValues.getType(i));\n\t\t}\n\t}\n\n\t// Set methods\n\t\n\tpublic void addConstant(ExpressionIdent n, Expression c, Type t)\n\t{\n\t\tnames.add(n.getName());\n\t\tconstants.add(c);\n\t\ttypes.add(t);\n\t\tnameIdents.add(n);\n\t}\n\t\n\tpublic void setConstant(int i, Expression c)\n\t{\n\t\tconstants.set(i, c);\n\t}\n\t\n\t// Get methods\n\n\tpublic int size()\n\t{\n\t\treturn constants.size();\n\t}\n\n\tpublic String getConstantName(int i)\n\t{\n\t\treturn names.get(i);\n\t}\n\t\n\tpublic Expression getConstant(int i)\n\t{\n\t\treturn constants.get(i);\n\t}\n\t\n\tpublic Type getConstantType(int i)\n\t{\n\t\treturn types.get(i);\n\t}\n\t\n\tpublic ExpressionIdent getConstantNameIdent(int i)\n\t{\n\t\treturn nameIdents.get(i);\n\t}\n\n\t/**\n\t * Get the index of a constant by its name (returns -1 if it does not exist).\n\t */\n\tpublic int getConstantIndex(String s)\n\t{\n\t\treturn names.indexOf(s);\n\t}\n\n\t/**\n\t * Remove the constant with the given name.\n\t * @param name the name of the constant\n\t * @param ignoreNonexistent if true, don't throw an exception if the constant does not exist\n\t * @throws PrismLangException if the constant does not exist (if not ignoreNonexistent)\n\t */\n\tpublic void removeConstant(String name, boolean ignoreNonexistent) throws PrismLangException\n\t{\n\t\tint constantIndex = getConstantIndex(name);\n\t\tif (constantIndex == -1) {\n\t\t\tif (ignoreNonexistent) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tthrow new PrismLangException(\"Can not remove nonexistent constant: \" + name);\n\t\t}\n\t\tremoveConstant(constantIndex);\n\t}\n\n\t/**\n\t * Remove the constant with the given index.\n\t * @param i the index\n\t */\n\tpublic void removeConstant(int i)\n\t{\n\t\tnames.remove(i);\n\t\tconstants.remove(i);\n\t\ttypes.remove(i);\n\t\tnameIdents.remove(i);\n\t}\n\n\t/**\n\t * Find cyclic dependencies.\n\t */\n\tpublic void findCycles() throws PrismLangException\n\t{\n\t\t// Create boolean matrix of dependencies\n\t\t// (matrix[i][j] is true if constant i contains constant j)\n\t\tint n = constants.size();\n\t\tboolean matrix[][] = new boolean[n][n];\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tExpression e = getConstant(i);\n\t\t\tif (e != null) {\n\t\t\t\tList<String> v = e.getAllConstants();\n\t\t\t\tfor (int j = 0; j < v.size(); j++) {\n\t\t\t\t\tint k = getConstantIndex(v.get(j));\n\t\t\t\t\tif (k != -1) {\n\t\t\t\t\t\tmatrix[i][k] = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Check for and report dependencies\n\t\tint firstCycle = PrismUtils.findCycle(matrix);\n\t\tif (firstCycle != -1) {\n\t\t\tString s = \"Cyclic dependency in definition of constant \\\"\" + getConstantName(firstCycle) + \"\\\"\";\n\t\t\tthrow new PrismLangException(s, getConstant(firstCycle));\n\t\t}\n\t}\n\t\n\t/**\n\t * Get the number of undefined constants in the list.\n\t */\n\tpublic int getNumUndefined()\n\t{\n\t\tint i, n, res;\n\t\tExpression e;\n\t\t\n\t\tres = 0;\n\t\tn = constants.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\te = getConstant(i);\n\t\t\tif (e == null) {\n\t\t\t\tres++;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn res;\n\t}\n\t\n\t/**\n\t * Get a list of the undefined constants in the list.\n\t */\n\tpublic List<String> getUndefinedConstants()\n\t{\n\t\tint i, n;\n\t\tExpression e;\n\t\tList<String> v = new ArrayList<>();\n\n\t\tn = constants.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\te = getConstant(i);\n\t\t\tif (e == null) {\n\t\t\t\tv.add(getConstantName(i));\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn v;\n\t}\n\t\n\t/**\n\t * Check if {@code name} is a *defined* constants in the list,\n\t * i.e. a constant whose value was *not* left unspecified in the model/property.\n\t */\n\tpublic boolean isDefinedConstant(String name)\n\t{\n\t\tint i = getConstantIndex(name);\n\t\tif (i == -1)\n\t\t\treturn false;\n\t\treturn (getConstant(i) != null);\n\t}\n\n\t/**\n\t * Set values for *all* undefined constants, evaluate values for *all* constants\n\t * and return a Values object with values for *all* constants.\n\t * The values being provided for these constants, as well as any other constants needed,\n\t * are provided in an EvaluateContext object. This also determines the evaluation mode.\n\t */\n\tpublic Values evaluateConstants(EvaluateContext ec) throws PrismLangException\n\t{\n\t\treturn evaluateSomeOrAllConstants(ec, true);\n\t}\n\n\t/**\n\t * Set values for *some* undefined constants, evaluate values for constants where possible\n\t * and return a Values object with values for all constants that could be evaluated.\n\t * The values being provided for these constants, as well as any other constants needed,\n\t * are provided in an EvaluateContext object. This also determines the evaluation mode.\n\t */\n\tpublic Values evaluateSomeConstants(EvaluateContext ec) throws PrismLangException\n\t{\n\t\treturn evaluateSomeOrAllConstants(ec, false);\n\t}\n\n\t/**\n\t * Set values for *some* or *all* undefined constants, evaluate values for constants where possible\n\t * and return a Values object with values for all constants that could be evaluated.\n\t * The values being provided for these constants, as well as any other constants needed,\n\t * are provided in an EvaluateContext object. This also determines the evaluation mode.\n\t * If argument 'all' is true, an exception is thrown if any undefined constant is not defined.\n\t */\n\tprivate Values evaluateSomeOrAllConstants(EvaluateContext ec, boolean all) throws PrismLangException\n\t{\n\t\t// Take a copy of this constant list,\n\t\t// and replace all (defined) constant references with their definitions)\n\t\tConstantList cl = (ConstantList) deepCopy();\n\t\tint n = size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tExpression constant = cl.getConstant(i);\n\t\t\tcl.setConstant(i, constant == null ? null : (Expression) constant.expandConstants(cl, false));\n\t\t}\n\t\t\n\t\t// Evaluate all constants and store in a new Values object\n\t\tValues allValues = new Values();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tExpression constant = cl.getConstant(i);\n\t\t\tif (constant == null) {\n\t\t\t\tconstant = new ExpressionConstant(cl.getConstantName(i), cl.getConstantType(i));\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tObject val = constant.evaluate(ec);\n\t\t\t\tval = cl.getConstantType(i).castValueTo(val, ec.getEvaluationMode());\n\t\t\t\tallValues.addValue(cl.getConstantName(i), val);\n\t\t\t} catch (PrismLangException ex) {\n\t\t\t\tif (all) {\n\t\t\t\t\tthrow ex;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn allValues;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tint i, n;\n\t\tExpression e;\n\t\t\n\t\tn = constants.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts += \"const \";\n\t\t\ts += getConstantType(i).getTypeString() + \" \";\n\t\t\ts += getConstantName(i);\n\t\t\te = getConstant(i);\n\t\t\tif (e != null) {\n\t\t\t\ts += \" = \" + e;\n\t\t\t}\n\t\t\ts += \";\\n\";\n\t\t}\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic ConstantList deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(constants);\n\t\tcopier.copyAll(nameIdents);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic ConstantList clone()\n\t{\n\t\tConstantList clone = (ConstantList) super.clone();\n\n\t\tclone.names      = (ArrayList<String>)          names.clone();\n\t\tclone.constants  = (ArrayList<Expression>)      constants.clone();\n\t\tclone.types      = (ArrayList<Type>)            types.clone();\n\t\tclone.nameIdents = (ArrayList<ExpressionIdent>) nameIdents.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/Declaration.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n/**\n * Variable declaration details\n */\npublic class Declaration extends ASTElement\n{\n\t// Name\n\tprotected String name;\n\t// Type of declaration\n\tprotected DeclarationType declType;\n\t// Initial value - null if none specified\n\tprotected Expression start;\n\t\t\n\tpublic Declaration(String name, DeclarationType declType)\n\t{\n\t\tsetName(name);\n\t\tsetDeclType(declType);\n\t\tsetStart(null);\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void setName(String name)\n\t{\n\t\tthis.name = name;\n\t}\t\n\n\tpublic void setDeclType(DeclarationType declType)\n\t{\n\t\tthis.declType = declType;\n\t\t// The type stored for a Declaration/DeclarationType object\n\t\t// is static - it is not computed during type checking.\n\t\t// (But we re-use the existing \"type\" field for this purpose)\n\t\tsetType(declType.getType());\n\t}\t\n\n\tpublic void setStart(Expression start)\n\t{\n\t\tthis.start = start;\n\t}\n\n\t// Get methods\n\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\n\tpublic DeclarationType getDeclType()\n\t{\n\t\treturn declType;\n\t}\t\n\n\t/**\n\t * Get the specified initial value of this variable (null if it was not specified).\n\t * To get the actual value (defaults to lower bound if appropriate),\n\t * use {@link #getStartOrDefault()}.\n\t */\n\tpublic Expression getStart()\n\t{\n\t\treturn start;\n\t}\n\t\n\t/**\n\t * Get the specified initial value of this variable,\n\t * using the default value for its type if not specified.\n\t */\n\tpublic Expression getStartOrDefault()\n\t{\n\t\treturn isStartSpecified() ? start : declType.getDefaultStart();\n\t}\n\t\n\t/**\n\t * Get the initial value of this variable, within a ModulesFile.\n\t * Will be null if parent ModulesFile passed in has an init...endinit.\n\t * Otherwise defaults to lower bound.\n\t * Can force lower bound to returned by passing in null. \n\t */\n\t\n\t/** TODO public abstract Expression getStart(ModulesFile parent); */\n\n\tpublic boolean isStartSpecified()\n\t{\n\t\treturn start != null;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t/**\n\t * Convert to string.\n\t */\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s  = \"\";\n\t\ts += name + \" : \";\n\t\ts += declType;\n\t\tif (start != null) s += \" init \" + start;\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic Declaration deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tdeclType = copier.copy(declType);\n\t\tstart = copier.copy(start);\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic Declaration clone()\n\t{\n\t\treturn (Declaration) super.clone();\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/DeclarationArray.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.type.TypeArray;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class DeclarationArray extends DeclarationType\n{\n\t// Min array index\n\tprotected Expression low;\n\t// Max array index\n\tprotected Expression high;\n\t// Type of object contained in this array\n\tprotected DeclarationType subtype;\n\n\tpublic DeclarationArray(Expression low, Expression high, DeclarationType subtype)\n\t{\n\t\tthis.low = low;\n\t\tthis.high = high;\n\t\tthis.subtype = subtype;\n\t\t// The type stored for a Declaration/DeclarationType object\n\t\t// is static - it is not computed during type checking.\n\t\t// (But we re-use the existing \"type\" field for this purpose)\n\t\t// And we copy the info from DeclarationType across to Declaration for convenience.\n\t\tsetType(new TypeArray(subtype.getType()));\n\t}\n\n\tpublic void setLow(Expression l)\n\t{\n\t\tlow = l;\n\t}\n\n\tpublic void setHigh(Expression h)\n\t{\n\t\thigh = h;\n\t}\n\n\tpublic void setSubtype(DeclarationType subtype)\n\t{\n\t\tthis.subtype = subtype;\n\t}\n\n\tpublic Expression getLow()\n\t{\n\t\treturn low;\n\t}\n\n\tpublic Expression getHigh()\n\t{\n\t\treturn high;\n\t}\n\n\tpublic DeclarationType getSubtype()\n\t{\n\t\treturn subtype;\n\t}\n\n\t/**\n\t * Return the default start value for a variable of this type.\n\t */\n\tpublic Expression getDefaultStart()\n\t{\n\t\t// TODO: what should be the default?\n\t\treturn null;\n\t}\n\t\n\t/* TODO\n\t@Override\n\tpublic Expression getStart(ModulesFile parent)\n\t{\n\t\tif (parent != null && parent.getInitialStates() != null)\n\t\t\treturn null;\n\n\t\t// TODO: what should be the default?\n\t\treturn start != null ? start : null;\n\t}*/\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t/**\n\t * Convert to string.\n\t */\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"array [\" + low + \"..\" + high + \"] of \" + subtype;\n\t}\n\n\t@Override\n\tpublic DeclarationArray deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tlow = copier.copy(low);\n\t\thigh = copier.copy(high);\n\t\tsubtype = copier.copy(subtype);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic DeclarationArray clone()\n\t{\n\t\treturn (DeclarationArray) super.clone();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/DeclarationBool.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.type.TypeBool;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class DeclarationBool extends DeclarationType\n{\n\tpublic DeclarationBool()\n\t{\n\t\t// The type stored for a Declaration/DeclarationType object\n\t\t// is static - it is not computed during type checking.\n\t\t// (But we re-use the existing \"type\" field for this purpose)\n\t\tsetType(TypeBool.getInstance());\n\t}\n\t\n\t@Override\n\tpublic Expression getDefaultStart()\n\t{\n\t\treturn Expression.False();\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"bool\";\n\t}\n\n\t@Override\n\tpublic DeclarationBool deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic DeclarationBool clone()\n\t{\n\t\treturn (DeclarationBool) super.clone();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/DeclarationClock.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.type.TypeClock;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class DeclarationClock extends DeclarationType\n{\n\tpublic DeclarationClock()\n\t{\n\t\t// The type stored for a Declaration/DeclarationType object\n\t\t// is static - it is not computed during type checking.\n\t\t// (But we re-use the existing \"type\" field for this purpose)\n\t\tsetType(TypeClock.getInstance());\n\t}\n\n\t@Override\n\tpublic Expression getDefaultStart()\n\t{\n\t\treturn Expression.Double(0);\n\t}\n\n\t@Override\n\tpublic boolean isUnbounded()\n\t{\n\t\treturn true;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"clock\";\n\t}\n\n\t@Override\n\tpublic DeclarationClock deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic DeclarationClock clone()\n\t{\n\t\treturn (DeclarationClock) super.clone();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/DeclarationDoubleUnbounded.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.type.*;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class DeclarationDoubleUnbounded extends DeclarationType\n{\n\tpublic DeclarationDoubleUnbounded()\n\t{\n\t\t// The type stored for a Declaration/DeclarationType object\n\t\t// is static - it is not computed during type checking.\n\t\t// (But we re-use the existing \"type\" field for this purpose)\n\t\tsetType(TypeDouble.getInstance());\n\t}\n\n\t@Override\n\tpublic Expression getDefaultStart()\n\t{\n\t\treturn Expression.Double(0);\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"double\";\n\t}\n\n\t@Override\n\tpublic DeclarationDoubleUnbounded deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic DeclarationDoubleUnbounded clone()\n\t{\n\t\treturn (DeclarationDoubleUnbounded) super.clone();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/DeclarationInt.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.type.TypeInt;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class DeclarationInt extends DeclarationType\n{\n\t// Min value\n\tprotected Expression low;\n\t// Max value\n\tprotected Expression high;\n\n\tpublic DeclarationInt(Expression low, Expression high)\n\t{\n\t\tthis.low = low;\n\t\tthis.high = high;\n\t\t// The type stored for a Declaration/DeclarationType object\n\t\t// is static - it is not computed during type checking.\n\t\t// (But we re-use the existing \"type\" field for this purpose)\n\t\tsetType(TypeInt.getInstance());\n\t}\n\n\tpublic void setLow(Expression l)\n\t{\n\t\tlow = l;\n\t}\n\n\tpublic void setHigh(Expression h)\n\t{\n\t\thigh = h;\n\t}\n\n\tpublic Expression getLow()\n\t{\n\t\treturn low;\n\t}\n\n\tpublic Expression getHigh()\n\t{\n\t\treturn high;\n\t}\n\t\n\t@Override\n\tpublic Expression getDefaultStart()\n\t{\n\t\treturn low;\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + low + \"..\" + high + \"]\";\n\t}\n\n\t@Override\n\tpublic DeclarationInt deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tlow = copier.copy(low);\n\t\thigh = copier.copy(high);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic DeclarationInt clone()\n\t{\n\t\treturn (DeclarationInt) super.clone();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/DeclarationIntUnbounded.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.type.*;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class DeclarationIntUnbounded extends DeclarationType\n{\n\tpublic DeclarationIntUnbounded()\n\t{\n\t\t// The type stored for a Declaration/DeclarationType object\n\t\t// is static - it is not computed during type checking.\n\t\t// (But we re-use the existing \"type\" field for this purpose)\n\t\tsetType(TypeInt.getInstance());\n\t}\n\n\t@Override\n\tpublic Expression getDefaultStart()\n\t{\n\t\treturn Expression.Int(0);\n\t}\n\n\t@Override\n\tpublic boolean isUnbounded()\n\t{\n\t\treturn true;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"int\";\n\t}\n\n\t@Override\n\tpublic DeclarationIntUnbounded deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic DeclarationIntUnbounded clone()\n\t{\n\t\treturn (DeclarationIntUnbounded) super.clone();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/DeclarationType.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic abstract class DeclarationType extends ASTElement\n{\n\t/**\n\t * Return the default start value for a variable of this type, as an Expression.\n\t */\n\tpublic abstract Expression getDefaultStart();\n\n\t/**\n\t * Is this variable type \"unbounded\"?\n\t */\n\tpublic boolean isUnbounded()\n\t{\n\t\t// Usually not\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic abstract DeclarationType deepCopy(DeepCopy copier) throws PrismLangException;\n\n\t@Override\n\tpublic DeclarationType clone()\n\t{\n\t\treturn (DeclarationType) super.clone();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/Expression.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport jltl2ba.SimpleLTL;\nimport param.BigRational;\nimport parser.BooleanUtils;\nimport parser.EvaluateContext;\nimport parser.EvaluateContext.EvalMode;\nimport parser.EvaluateContextConstants;\nimport parser.EvaluateContextState;\nimport parser.EvaluateContextSubstate;\nimport parser.EvaluateContextValues;\nimport parser.State;\nimport parser.Values;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.type.TypePathBool;\nimport parser.visitor.ASTTraverse;\nimport parser.visitor.CheckValid;\nimport parser.visitor.ConvertForJltl2ba;\nimport parser.visitor.DeepCopy;\nimport parser.visitor.ExpressionTraverseNonNested;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLangException;\n\n// Abstract class for PRISM language expressions\n\npublic abstract class Expression extends ASTElement\n{\n\t/**\n\t * Is this expression constant?\n\t */\n\tpublic abstract boolean isConstant();\n\n\t/**\n\t * Is this expression a proposition?\n\t * (i.e. something that can be evaluated on a single state in isolation)\n\t */\n\tpublic abstract boolean isProposition();\n\n\t/**\n\t * Evaluate this expression and return the result as an Object\n\t * of the appropriate type for the type of this expression and the\n\t * evaluation mode of the {@link EvaluateContext} object.\n\t * E.g. a \"double\" is returned as a Double for floating point mode (EvalMode.FP)\n\t * but as a BigRational for exact mode (EvalMode.EXACT).\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic abstract Object evaluate(EvaluateContext ec) throws PrismLangException;\n\n\t/**\n\t * Evaluate this expression exactly and return the result as a BigRational.\n\t * This is regardless of the type (e.g. ints, booleans are also converted).\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic BigRational evaluateExact(EvaluateContext ec) throws PrismLangException\n\t{\n\t\t// Evaluate using a copy of the EvaluateContext\n\t\t// where the evaluation mode is set to EXACT.\n\t\t// Then convert the result to BigRational, regardless of type.\n\t\treturn BigRational.from(evaluate(new EvaluateContext()\n\t\t{\n\t\t\tpublic EvalMode getEvaluationMode()\n\t\t\t{\n\t\t\t\treturn EvalMode.EXACT;\n\t\t\t}\n\t\t\t\n\t\t\t@Override\n\t\t\tpublic Object getVarValue(String name, int index)\n\t\t\t{\n\t\t\t\treturn ec.getVarValue(name, index);\n\t\t\t}\n\t\t\t\n\t\t\t@Override\n\t\t\tpublic Object getConstantValue(String name)\n\t\t\t{\n\t\t\t\treturn ec.getConstantValue(name);\n\t\t\t}\n\t\t}));\n\t}\n\n\t/**\n\t  * Get \"name\" of the result of this expression (used for y-axis of any graphs plotted)\n\t  */\n\tpublic String getResultName()\n\t{\n\t\treturn \"Result\";\n\t}\n\n\t/**\n\t * Does this expression equate to a single value, rather than a different value for all states,\n\t * when evaluated during model checking?\n\t */\n\tpublic abstract boolean returnsSingleValue();\n\n\t/**\n\t * Ordered list defining precedence of operators in the PRISM expression grammar.\n\t * Earlier in the list means lower precedence (binds less tightly).\n\t */\n\tenum Precedence {\n\t\tTEMPORAL_BINARY,\n\t\tTEMPORAL_UNARY,\n\t\tITE,\n\t\tIMPLIES,\n\t\tIFF,\n\t\tOR,\n\t\tAND,\n\t\tNOT,\n\t\tEQUALITY,\n\t\tRELOP,\n\t\tPLUS_MINUS,\n\t\tTIMES_DIVIDE,\n\t\tPOW,\n\t\tUNARY_MINUS,\n\t\tBASIC\n\t}\n\n\t/**\n\t * Get the relative precedence ordering of this expression in the PRISM expression grammar,\n\t * primarily for the purposes of making sure toString() is parseable.\n\t */\n\tpublic Precedence getPrecedence()\n\t{\n\t\t// Default to \"basic\" (atomic, highest precedence)\n\t\treturn Precedence.BASIC;\n\t}\n\n\t/**\n\t * Returns true if {@code expr1} has (strictly) lower operator precedence than {@code expr2},\n\t * i.e., if {@code expr1} needs parenthesising when a child of {@code expr2}.\n\t */\n\tpublic static boolean hasPrecedenceLessThan(Expression expr1, Expression expr2)\n\t{\n\t\treturn expr2.getPrecedence() != Precedence.BASIC && expr1.getPrecedence().ordinal() < expr2.getPrecedence().ordinal();\n\t}\n\n\t/**\n\t * Returns true if {@code expr1} has lower or equal operator precedence than {@code expr2},\n\t * i.e., if {@code expr1} needs parenthesising when a child of {@code expr2}.\n\t */\n\tpublic static boolean hasPrecedenceLessThanOrEquals(Expression expr1, Expression expr2)\n\t{\n\t\treturn expr2.getPrecedence() != Precedence.BASIC && expr1.getPrecedence().ordinal() <= expr2.getPrecedence().ordinal();\n\t}\n\n\t// Overwritten version of deepCopy() and deepCopy(DeepCopy copier) from superclass ASTElement (to reduce casting).\n\n\t@Override\n\tpublic abstract Expression deepCopy(DeepCopy copier) throws PrismLangException;\n\n\t@Override\n\tpublic Expression deepCopy()\n\t{\n\t\treturn (Expression) super.deepCopy();\n\t}\n\n\t// Overwritten version of clone() from superclass ASTElement (to reduce casting).\n\t\n\t@Override\n\tpublic Expression clone()\n\t{\n\t\treturn (Expression) super.clone();\n\t}\n\n\t// Utility methods:\n\n\t/**\n\t * Check expression (property) for validity with respect to a particular model type\n\t * (i.e. whether not it is a property that can be model checked for that model type).\n\t */\n\tpublic void checkValid(ModelType modelType) throws PrismLangException\n\t{\n\t\tCheckValid visitor = new CheckValid(modelType);\n\t\taccept(visitor);\n\t}\n\n\t/**\n\t * Determine whether expression is a valid \"simple\" path formula , i.e. a formula\n\t * that could occur in the P operator of a PCTL/CSL formula (not LTL, PCTL*).\n\t * This is defined as a single instance of a temporal operator (X, U, F, etc.),\n\t * possibly negated. Strictly speaking, negations are not allowed in PCTL/CSL\n\t * but they can always be converted to a dual formula which is.   \n\t */\n\tpublic boolean isSimplePathFormula() throws PrismLangException\n\t{\n\t\t// One (or more) top-level negations is allowed.\n\t\t// Top-level parentheses also OK.\n\t\tif (this instanceof ExpressionUnaryOp) {\n\t\t\tExpressionUnaryOp expr = (ExpressionUnaryOp) this;\n\t\t\tint op = expr.getOperator();\n\t\t\tif (op == ExpressionUnaryOp.NOT || op == ExpressionUnaryOp.PARENTH) {\n\t\t\t\treturn expr.getOperand().isSimplePathFormula();\n\t\t\t} else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\t// Otherwise, must be a temporal operator.\n\t\telse if (this instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal expr = (ExpressionTemporal) this;\n\t\t\t// And children, if present, must be state (not path) formulas\n\t\t\tif (expr.getOperand1() != null && !(expr.getOperand1().getType() instanceof TypeBool)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (expr.getOperand2() != null && !(expr.getOperand2().getType() instanceof TypeBool)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\treturn true;\n\t\t}\n\t\t// Default: false.\n\t\treturn false;\n\t}\n\n\t/**\n\t * Returns {@code true} if this expression is a path formula.\n\t * If {@code allowNestedOperators==false} then we don't allow\n\t * nested P, R, ... operators.\n\t * @param allowNestedOperators allow nested P, R, ... operators?\n\t */\n\tpublic boolean isPathFormula(boolean allowNestedOperators)\n\t{\n\t\ttry {\n\t\t\tif (getType() == null) {\n\t\t\t\tthis.typeCheck();\n\t\t\t}\n\t\t\tif (getType() == TypePathBool.getInstance() ||\n\t\t\t    getType() == TypeBool.getInstance()) {\n\t\t\t\tif (!allowNestedOperators) {\n\t\t\t\t\tif (this.computeProbNesting() >= 1) {\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\treturn true;\n\t\t\t}\n\n\t\t\treturn false;\n\t\t} catch (PrismLangException e) {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\t/**\n\t * Convert a property expression (an LTL formula) into the classes used by\n\t * the jltl2ba (and jltl2dstar) libraries.\n\t */\n\tpublic jltl2ba.SimpleLTL convertForJltl2ba() throws PrismLangException\n\t{\n\t\tConvertForJltl2ba converter = new ConvertForJltl2ba();\n\t\treturn converter.convert(this);\n\t}\n\n\t/**\n\t * Evaluate this expression, using no constant or variable values.\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic Object evaluate() throws PrismLangException\n\t{\n\t\treturn evaluate(new EvaluateContextConstants(null));\n\t}\n\n\t/**\n\t * Evaluate this expression, based on values for constants (but not variables).\n\t * Constant values are supplied as a Values object. \n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic Object evaluate(Values constantValues) throws PrismLangException\n\t{\n\t\treturn evaluate(new EvaluateContextConstants(constantValues));\n\t}\n\n\t/**\n\t * Evaluate this expression, based on values for constants/variables.\n\t * Each set of values is supplied as a Values object. \n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic Object evaluate(Values constantValues, Values varValues) throws PrismLangException\n\t{\n\t\treturn evaluate(new EvaluateContextValues(constantValues, varValues));\n\t}\n\n\t/**\n\t * Evaluate this expression, based on values for variables (but not constants).\n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic Object evaluate(State state) throws PrismLangException\n\t{\n\t\treturn evaluate(new EvaluateContextState(state));\n\t}\n\n\t/**\n\t * Evaluate this expression, based on values for constants/variables.\n\t * Constant values are supplied as a Values object. \n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic Object evaluate(Values constantValues, State state) throws PrismLangException\n\t{\n\t\treturn evaluate(new EvaluateContextState(constantValues, state));\n\t}\n\n\t/**\n\t * Evaluate this expression, based on values for some variables (but not constants).\n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic Object evaluate(State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluate(new EvaluateContextSubstate(substate, varMap));\n\t}\n\n\t/**\n\t * Evaluate this expression, based on values for constants and some variables.\n\t * Constant values are supplied as a Values object. \n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic Object evaluate(Values constantValues, State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluate(new EvaluateContextSubstate(constantValues, substate, varMap));\n\t}\n\n\t/**\n\t * Evaluate this expression as an integer.\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors,\n\t * and converts to evaluation mode FP (e.g. from EXACT) if needed.\n\t */\n\tpublic int evaluateInt(EvaluateContext ec) throws PrismLangException\n\t{\n\t\treturn (Integer) TypeInt.getInstance().castValueTo(evaluate(ec), EvalMode.FP);\n\t}\n\n\t/**\n\t * Evaluate this expression as an integer, using no constant or variable values.\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors.\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic int evaluateInt() throws PrismLangException\n\t{\n\t\treturn evaluateInt(new EvaluateContextConstants(null));\n\t}\n\n\t/**\n\t * Evaluate this expression as an integer, based on values for constants (but not variables).\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic int evaluateInt(Values constantValues) throws PrismLangException\n\t{\n\t\treturn evaluateInt(new EvaluateContextConstants(constantValues));\n\t}\n\n\t/**\n\t * Evaluate this expression as an integer, based on values for constants/variables.\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors.\n\t * Each set of values is supplied as a Values object. \n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic int evaluateInt(Values constantValues, Values varValues) throws PrismLangException\n\t{\n\t\treturn evaluateInt(new EvaluateContextValues(constantValues, varValues));\n\t}\n\n\t/**\n\t * Evaluate this expression as an integer, based on values for variables (but not constants).\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors.\n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic int evaluateInt(State state) throws PrismLangException\n\t{\n\t\treturn evaluateInt(new EvaluateContextState(state));\n\t}\n\n\t/**\n\t * Evaluate this expression as an integer, based on values for constants/variables.\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic int evaluateInt(Values constantValues, State state) throws PrismLangException\n\t{\n\t\treturn evaluateInt(new EvaluateContextState(constantValues, state));\n\t}\n\n\t/**\n\t * Evaluate this expression as an integer, based on values for some variables (but not constants).\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors.\n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic int evaluateInt(State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluateInt(new EvaluateContextSubstate(substate, varMap));\n\t}\n\n\t/**\n\t * Evaluate this expression as an integer, based on values for constants and some variables.\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic int evaluateInt(Values constantValues, State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluateInt(new EvaluateContextSubstate(constantValues, substate, varMap));\n\t}\n\n\t/**\n\t * Evaluate this object as an integer.\n\t * This assumes that the type of the expression is int.\n\t * Basically casts the result to an int, checking for any type errors.\n\t */\n\tpublic static int evaluateObjectAsInt(Object o) throws PrismLangException\n\t{\n\t\treturn (Integer) TypeInt.getInstance().castValueTo(o, EvalMode.FP);\n\t}\n\n\t/**\n\t * Evaluate this expression as a double.\n\t * This assumes that the type of the expression is (or can be cast to) double.\n\t * Basically casts the result to a double, checking for any type errors,\n\t * and converts to evaluation mode FP (e.g. from EXACT) if needed.\n\t * Any typing issues cause an exception (but: we do allow conversion of boolean to 0.0/1.0).\n\t */\n\tpublic double evaluateDouble(EvaluateContext ec) throws PrismLangException\n\t{\n\t\treturn (Double) TypeDouble.getInstance().castValueTo(evaluate(ec), EvalMode.FP);\n\t}\n\n\t/**\n\t * Evaluate this expression as a double, using no constant or variable values.\n\t * This assumes that the type of the expression is (or can be cast to) double.\n\t * Basically casts the result to a double, checking for any type errors.\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic double evaluateDouble() throws PrismLangException\n\t{\n\t\treturn evaluateDouble(new EvaluateContextConstants(null));\n\t}\n\n\t/**\n\t * Evaluate this expression as a double, based on values for constants (but not variables).\n\t * This assumes that the type of the expression is (or can be cast to) double.\n\t * Basically casts the result to a double, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic double evaluateDouble(Values constantValues) throws PrismLangException\n\t{\n\t\treturn evaluateDouble(new EvaluateContextConstants(constantValues));\n\t}\n\n\t/**\n\t * Evaluate this expression as a double, based on values for constants/variables.\n\t * This assumes that the type of the expression is (or can be cast to) double.\n\t * Basically casts the result to a double, checking for any type errors.\n\t * Each set of values is supplied as a Values object. \n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic double evaluateDouble(Values constantValues, Values varValues) throws PrismLangException\n\t{\n\t\treturn evaluateDouble(new EvaluateContextValues(constantValues, varValues));\n\t}\n\n\t/**\n\t * Evaluate this expression as a double, based on values for variables (but not constants).\n\t * This assumes that the type of the expression is (or can be cast to) double.\n\t * Basically casts the result to a double, checking for any type errors.\n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic double evaluateDouble(State state) throws PrismLangException\n\t{\n\t\treturn evaluateDouble(new EvaluateContextState(state));\n\t}\n\n\t/**\n\t * Evaluate this expression as a double, based on values for constants/variables.\n\t * This assumes that the type of the expression is (or can be cast to) double.\n\t * Basically casts the result to a double, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic double evaluateDouble(Values constantValues, State state) throws PrismLangException\n\t{\n\t\treturn evaluateDouble(new EvaluateContextState(constantValues, state));\n\t}\n\n\t/**\n\t * Evaluate this expression as a double, based on values for some variables (but not constants).\n\t * This assumes that the type of the expression is (or can be cast to) double.\n\t * Basically casts the result to a double, checking for any type errors.\n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic double evaluateDouble(State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluateDouble(new EvaluateContextSubstate(substate, varMap));\n\t}\n\n\t/**\n\t * Evaluate this expression as a double, based on values for constants and some variables.\n\t * This assumes that the type of the expression is (or can be cast to) double.\n\t * Basically casts the result to a double, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic double evaluateDouble(Values constantValues, State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluateDouble(new EvaluateContextSubstate(constantValues, substate, varMap));\n\t}\n\n\t/**\n\t * Evaluate this expression as a BigRational.\n\t * This assumes that the type of the expression is (or can be cast to) double..\n\t * Basically casts the result to a BigRational, checking for any type errors.\n\t */\n\tpublic BigRational evaluateBigRational(EvaluateContext ec) throws PrismLangException\n\t{\n\t\treturn (BigRational) TypeDouble.getInstance().castValueTo(evaluate(ec), EvalMode.EXACT);\n\t}\n\n\t/**\n\t * Evaluate this expression as a boolean.\n\t * This assumes that the type of the expression is bool.\n\t * Basically casts the result to a boolean, checking for any type errors.\n\t */\n\tpublic boolean evaluateBoolean(EvaluateContext ec) throws PrismLangException\n\t{\n\t\treturn TypeBool.getInstance().castValueTo(evaluate(ec), EvalMode.FP);\n\t}\n\n\t/**\n\t * Evaluate this expression as a boolean, using no constant or variable values.\n\t * Basically casts the result to a boolean, checking for any type errors.\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic boolean evaluateBoolean() throws PrismLangException\n\t{\n\t\treturn evaluateBoolean(new EvaluateContextConstants(null));\n\t}\n\n\t/**\n\t * Evaluate this expression as a boolean, based on values for constants (but not variables).\n\t * Basically casts the result to a boolean, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic boolean evaluateBoolean(Values constantValues) throws PrismLangException\n\t{\n\t\treturn evaluateBoolean(new EvaluateContextConstants(constantValues));\n\t}\n\n\t/**\n\t * Evaluate this expression as a boolean, based on values for constants/variables.\n\t * Basically casts the result to a boolean, checking for any type errors.\n\t * Each set of values is supplied as a Values object. \n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic boolean evaluateBoolean(Values constantValues, Values varValues) throws PrismLangException\n\t{\n\t\treturn evaluateBoolean(new EvaluateContextValues(constantValues, varValues));\n\t}\n\n\t/**\n\t * Evaluate this expression as a boolean, based on values for variables (but not constants).\n\t * Basically casts the result to a boolean, checking for any type errors.\n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic boolean evaluateBoolean(State state) throws PrismLangException\n\t{\n\t\treturn evaluateBoolean(new EvaluateContextState(state));\n\t}\n\n\t/**\n\t * Evaluate this expression as a boolean, based on values for constants/variables.\n\t * Basically casts the result to a boolean, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic boolean evaluateBoolean(Values constantValues, State state) throws PrismLangException\n\t{\n\t\treturn evaluateBoolean(new EvaluateContextState(constantValues, state));\n\t}\n\n\t/**\n\t * Evaluate this expression as a boolean, based on values for some variables (but not constants).\n\t * Basically casts the result to a boolean, checking for any type errors.\n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic boolean evaluateBoolean(State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluateBoolean(new EvaluateContextSubstate(substate, varMap));\n\t}\n\n\t/**\n\t * Evaluate this expression as a boolean, based on values for constants and some variables.\n\t * Basically casts the result to a boolean, checking for any type errors.\n\t * Constant values are supplied as a Values object. \n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic boolean evaluateBoolean(Values constantValues, State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluateBoolean(new EvaluateContextSubstate(constantValues, substate, varMap));\n\t}\n\n\t\n\t/**\n\t * Evaluate this expression exactly to a BigRational, using no constant or variable values.\n\t * This is regardless of the type (e.g. ints, booleans are also converted).\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic BigRational evaluateExact() throws PrismLangException\n\t{\n\t\treturn evaluateExact(new EvaluateContextConstants(null));\n\t}\n\n\t/**\n\t * Evaluate this expression exactly to a BigRational, based on values for constants (but not variables).\n\t * This is regardless of the type (e.g. ints, booleans are also converted).\n\t * Constant values are supplied as a Values object.\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic BigRational evaluateExact(Values constantValues) throws PrismLangException\n\t{\n\t\treturn evaluateExact(new EvaluateContextConstants(constantValues));\n\t}\n\n\t/**\n\t * Evaluate this expression exactly to a BigRational, based on values for constants/variables.\n\t * This is regardless of the type (e.g. ints, booleans are also converted).\n\t * Each set of values is supplied as a Values object.\n\t * Note: assumes that type checking has been done already.\n\t */\n\tpublic BigRational evaluateExact(Values constantValues, Values varValues) throws PrismLangException\n\t{\n\t\treturn evaluateExact(new EvaluateContextValues(constantValues, varValues));\n\t}\n\n\t/**\n\t * Evaluate this expression exactly to a BigRational, based on values for variables (but not constants).\n\t * This is regardless of the type (e.g. ints, booleans are also converted).\n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic BigRational evaluateExact(State state) throws PrismLangException\n\t{\n\t\treturn evaluateExact(new EvaluateContextState(state));\n\t}\n\n\t/**\n\t * Evaluate this expression exactly to a BigRational, based on values for constants/variables.\n\t * This is regardless of the type (e.g. ints, booleans are also converted).\n\t * Constant values are supplied as a Values object.\n\t * Variable values are supplied as a State object, i.e. array of variable values.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic BigRational evaluateExact(Values constantValues, State state) throws PrismLangException\n\t{\n\t\treturn evaluateExact(new EvaluateContextState(constantValues, state));\n\t}\n\n\t/**\n\t * Evaluate this expression exactly to a BigRational, based on values for some variables (but not constants).\n\t * This is regardless of the type (e.g. ints, booleans are also converted).\n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that constants have been evaluated and type checking has been done.\n\t */\n\tpublic BigRational evaluateExact(State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluateExact(new EvaluateContextSubstate(substate, varMap));\n\t}\n\n\t/**\n\t * Evaluate this expression exactly to a BigRational, based on values for constants and some variables.\n\t * This is regardless of the type (e.g. ints, booleans are also converted).\n\t * Constant values are supplied as a Values object.\n\t * Variable values are supplied as a State object, indexed over a subset of all variables,\n\t * and a mapping from indices (over all variables) to this subset (-1 if not in subset).\n\t * If any variables required for evaluation are missing, this will fail with an exception.\n\t * Note: assumes that type checking has been done.\n\t */\n\tpublic BigRational evaluateExact(Values constantValues, State substate, int[] varMap) throws PrismLangException\n\t{\n\t\treturn evaluateExact(new EvaluateContextSubstate(constantValues, substate, varMap));\n\t}\n\n\t// Static constructors for convenience\n\n\tpublic static ExpressionLiteral True()\n\t{\n\t\treturn new ExpressionLiteral(TypeBool.getInstance(), true);\n\t}\n\n\tpublic static ExpressionLiteral False()\n\t{\n\t\treturn new ExpressionLiteral(TypeBool.getInstance(), false);\n\t}\n\n\tpublic static ExpressionLiteral Int(int i)\n\t{\n\t\treturn new ExpressionLiteral(TypeInt.getInstance(), i);\n\t}\n\n\tpublic static ExpressionLiteral Double(double d)\n\t{\n\t\treturn new ExpressionLiteral(TypeDouble.getInstance(), d);\n\t}\n\n\tpublic static ExpressionLiteral Literal(Object o) throws PrismLangException\n\t{\n\t\tif (o instanceof Integer) {\n\t\t\treturn Int(((Integer) o).intValue());\n\t\t} else if (o instanceof Double) {\n\t\t\treturn Double(((Double) o).doubleValue());\n\t\t} else if (o instanceof Boolean) {\n\t\t\treturn (((Boolean) o).booleanValue() ? True() : False());\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Unknown object type \" + o.getClass());\n\t\t}\n\t}\n\n\tpublic static ExpressionUnaryOp Not(Expression expr)\n\t{\n\t\treturn new ExpressionUnaryOp(ExpressionUnaryOp.NOT, expr);\n\t}\n\n\tpublic static ExpressionBinaryOp And(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.AND, expr1, expr2);\n\t}\n\n\tpublic static ExpressionBinaryOp Or(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.OR, expr1, expr2);\n\t}\n\n\tpublic static ExpressionBinaryOp Iff(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.IFF, expr1, expr2);\n\t}\n\n\tpublic static ExpressionBinaryOp Implies(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.IMPLIES, expr1, expr2);\n\t}\n\n\tpublic static ExpressionBinaryOp Plus(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.PLUS, expr1, expr2);\n\t}\n\n\tpublic static ExpressionUnaryOp Minus(Expression expr)\n\t{\n\t\treturn new ExpressionUnaryOp(ExpressionUnaryOp.MINUS, expr);\n\t}\n\n\tpublic static ExpressionBinaryOp Minus(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.MINUS, expr1, expr2);\n\t}\n\n\tpublic static ExpressionBinaryOp Times(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.TIMES, expr1, expr2);\n\t}\n\n\tpublic static ExpressionBinaryOp Divide(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.DIVIDE, expr1, expr2);\n\t}\n\n\tpublic static ExpressionBinaryOp Pow(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionBinaryOp(ExpressionBinaryOp.POW, expr1, expr2);\n\t}\n\n\tpublic static ExpressionUnaryOp Parenth(Expression expr)\n\t{\n\t\treturn new ExpressionUnaryOp(ExpressionUnaryOp.PARENTH, expr);\n\t}\n\n\tpublic static ExpressionTemporal Next(Expression expr) {\n\t\treturn new ExpressionTemporal(ExpressionTemporal.P_X, null, expr);\n\t}\n\n\t// Static testers for convenience\n\n\tpublic static boolean isTrue(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionLiteral && ((ExpressionLiteral) expr).getValue().equals(true);\n\t}\n\n\tpublic static boolean isFalse(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionLiteral && ((ExpressionLiteral) expr).getValue().equals(false);\n\t}\n\n\tpublic static boolean isInt(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionLiteral && expr.getType() instanceof TypeInt;\n\t}\n\n\tpublic static boolean isDouble(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionLiteral && expr.getType() instanceof TypeDouble;\n\t}\n\n\tpublic static boolean isNot(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionUnaryOp && ((ExpressionUnaryOp) expr).getOperator() == ExpressionUnaryOp.NOT;\n\t}\n\n\tpublic static boolean isAnd(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionBinaryOp\n\t\t\t\t&& ((ExpressionBinaryOp) expr).getOperator() == ExpressionBinaryOp.AND;\n\t}\n\n\tpublic static boolean isOr(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionBinaryOp && ((ExpressionBinaryOp) expr).getOperator() == ExpressionBinaryOp.OR;\n\t}\n\n\tpublic static boolean isIff(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionBinaryOp\n\t\t\t\t&& ((ExpressionBinaryOp) expr).getOperator() == ExpressionBinaryOp.IFF;\n\t}\n\n\tpublic static boolean isImplies(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionBinaryOp\n\t\t\t\t&& ((ExpressionBinaryOp) expr).getOperator() == ExpressionBinaryOp.IMPLIES;\n\t}\n\n\tpublic static boolean isParenth(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionUnaryOp\n\t\t\t\t&& ((ExpressionUnaryOp) expr).getOperator() == ExpressionUnaryOp.PARENTH;\n\t}\n\n\tpublic static boolean isRelOp(Expression expr)\n\t{\n\t\treturn expr instanceof ExpressionBinaryOp\n\t\t\t\t&& ExpressionBinaryOp.isRelOp(((ExpressionBinaryOp) expr).getOperator());\n\t}\n\n\tpublic static boolean isFilter(Expression expr, ExpressionFilter.FilterOperator opType)\n\t{\n\t\treturn expr instanceof ExpressionFilter && ((ExpressionFilter) expr).getOperatorType() == opType;\n\t}\n\t\n\t/**\n\t * Test if an expression is a function of type {@code nameCode}.\n\t */\n\tpublic static boolean isFunc(Expression expr, int nameCode)\n\t{\n\t\treturn expr instanceof ExpressionFunc && ((ExpressionFunc) expr).getNameCode() == nameCode;\n\t}\n\n\t/**\n\t * Test if an expression is a quantitative property (P=?, R=? or S=?) \n\t */\n\tpublic static boolean isQuantitative(Expression expr)\n\t{\n\t\tif (expr instanceof ExpressionProb) {\n\t\t\treturn ((ExpressionProb) expr).getProb() == null;\n\t\t}\n\t\telse if (expr instanceof ExpressionReward) {\n\t\t\treturn ((ExpressionReward) expr).getReward() == null;\n\t\t}\n\t\telse if (expr instanceof ExpressionSS) {\n\t\t\treturn ((ExpressionSS) expr).getProb() == null;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Test if an expression is a reachability path formula (F phi), possibly with a time bound.\n\t */\n\tpublic static boolean isReach(Expression expr)\n\t{\n\t\tif (expr instanceof ExpressionTemporal) {\n\t\t\tif (((ExpressionTemporal) expr).getOperator() == ExpressionTemporal.P_F) {\n\t\t\t\treturn ((ExpressionTemporal) expr).getOperand2().getType() instanceof TypeBool;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Test if an expression contains time bounds on temporal operators \n\t */\n\tpublic static boolean containsTemporalTimeBounds(Expression expr)\n\t{\n\t\ttry {\n\t\t\t// check for time bounds, don't recurse into P/R/SS subformulas\n\t\t\texpr.accept(new ExpressionTraverseNonNested()\n\t\t\t{\n\t\t\t\tpublic void visitPre(ExpressionTemporal e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.hasBounds())\n\t\t\t\t\t\tthrow new PrismLangException(\"\");\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (PrismLangException e) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Test if an expression is a reward operator using instantaneous rewards only.\n\t */\n\tpublic static boolean usesInstantaneousReward(Expression expr)\n\t{\n\t\tif (expr instanceof ExpressionTemporal) {\n\t\t\tif (((ExpressionTemporal) expr).getOperator() == ExpressionTemporal.R_I) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Test if an expression contains a minimum expected reward operator. \n\t * Actually, this returns true if there is an R operator with \"min=?\" or a lower bound attached to it,\n\t * so this is just an approximation. (For example, an R operator might be embedded within\n\t * an \"exists\" strategy operator)\n\t */\n\tpublic static boolean containsMinReward(Expression expr)\n\t{\n\t\ttry {\n\t\t\tASTTraverse astt = new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPost(ExpressionReward e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.isMin()) {\n\t\t\t\t\t\tthrow new PrismLangException(\"Found one\", e);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t};\n\t\t\texpr.accept(astt);\n\t\t} catch (PrismLangException e) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Test if an expression contains a non-probabilistic LTL formula (i.e., a non-simple path formula). \n\t */\n\tpublic static boolean containsNonProbLTLFormula(Expression expr)\n\t{\n\t\ttry {\n\t\t\tASTTraverse astt = new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPost(ExpressionForAll e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (!e.getExpression().isSimplePathFormula())\n\t\t\t\t\t\tthrow new PrismLangException(\"Found one\", e);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tpublic void visitPost(ExpressionExists e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (!e.getExpression().isSimplePathFormula())\n\t\t\t\t\t\tthrow new PrismLangException(\"Found one\", e);\n\t\t\t\t}\n\t\t\t};\n\t\t\texpr.accept(astt);\n\t\t} catch (PrismLangException e) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Test if an expression contains a multi(...) property within \n\t */\n\tpublic static boolean containsMultiObjective(Expression expr)\n\t{\n\t\ttry {\n\t\t\tASTTraverse astt = new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPost(ExpressionFunc e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.getNameCode() == ExpressionFunc.MULTI)\n\t\t\t\t\t\tthrow new PrismLangException(\"Found one\", e);\n\t\t\t\t}\n\t\t\t};\n\t\t\texpr.accept(astt);\n\t\t} catch (PrismLangException e) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Test if an expression is an LTL formula and is in positive normal form,\n\t * i.e. where negation only occurs at the level of state formulae.\n\t * This means that the operators => and <=> are also disallowed. \n\t */\n\tpublic static boolean isPositiveNormalFormLTL(Expression expr)\n\t{\n\t\t// State formulae (negated or otherwise) are OK\n\t\tif (expr.getType() instanceof TypeBool)\n\t\t\treturn true;\n\t\t// Otherwise recurse, looking for negations...\n\t\telse if (expr instanceof ExpressionUnaryOp) {\n\t\t\tExpressionUnaryOp exprUnOp = (ExpressionUnaryOp) expr;\n\t\t\tint op = exprUnOp.getOperator();\n\t\t\tswitch (op) {\n\t\t\t// Negation is not allowed\n\t\t\t// (since we already checked for state formulae that include negation)\n\t\t\tcase ExpressionUnaryOp.NOT:\n\t\t\t\treturn false;\n\t\t\tdefault:\n\t\t\t\treturn isPositiveNormalFormLTL(exprUnOp.getOperand());\n\t\t\t}\n\t\t}\n\t\telse if (expr instanceof ExpressionBinaryOp) {\n\t\t\tExpressionBinaryOp exprBinOp = (ExpressionBinaryOp) expr;\n\t\t\tint op = exprBinOp.getOperator();\n\t\t\tswitch (op) {\n\t\t\t// => and <=> are not allowed\n\t\t\tcase ExpressionBinaryOp.IMPLIES:\n\t\t\tcase ExpressionBinaryOp.IFF:\n\t\t\t\treturn false;\n\t\t\tdefault:\n\t\t\t\treturn isPositiveNormalFormLTL(exprBinOp.getOperand1()) && isPositiveNormalFormLTL(exprBinOp.getOperand2());\n\t\t\t}\n\t\t}\n\t\telse if (expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\tif (exprTemp.getOperand1() != null && !isPositiveNormalFormLTL(exprTemp.getOperand1())) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (exprTemp.getOperand2() != null && !isPositiveNormalFormLTL(exprTemp.getOperand2())) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\treturn true;\n\t\t}\n\t\t// If we get here, it is probably not even LTL\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Test if an expression is a co-safe LTL formula, detected syntactically\n\t * (i.e. if it is in positive normal form and only uses X, F and U).\n\t */\n\tpublic static boolean isCoSafeLTLSyntactic(Expression expr)\n\t{\n\t\treturn isCoSafeLTLSyntactic(expr, false);\n\t}\n\n\t/**\n\t * Test if an expression is a co-safe LTL formula, detected syntactically\n\t * (i.e. if it is in positive normal form and only uses X, F and U).\n\t * If {@code convert} is true, the expression is first converted into positive normal form,\n\t * and then it is checked whether it only uses X, F and U.\n\t * For example, a => ! (G b) would return true if (and only if) {@code convert} was true.\n\t */\n\tpublic static boolean isCoSafeLTLSyntactic(Expression expr, boolean convert)\n\t{\n\t\t// Convert to or check for positive normal form\n\t\tif (convert) {\n\t\t\texpr = BooleanUtils.convertLTLToPositiveNormalForm(expr.deepCopy());\n\t\t} else {\n\t\t\tif (!isPositiveNormalFormLTL(expr))\n\t\t\t\treturn false;\n\t\t}\n\t\t// Check temporal operators (don't recurse into P/R/S subformulas)\n\t\ttry {\n\t\t\tASTTraverse astt = new ExpressionTraverseNonNested()\n\t\t\t{\n\t\t\t\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.getOperator() == ExpressionTemporal.P_X)\n\t\t\t\t\t\treturn;\n\t\t\t\t\tif (e.getOperator() == ExpressionTemporal.P_F)\n\t\t\t\t\t\treturn;\n\t\t\t\t\tif (e.getOperator() == ExpressionTemporal.P_U)\n\t\t\t\t\t\treturn;\n\t\t\t\t\tthrow new PrismLangException(\"Found non-X/F/U\", e);\n\t\t\t\t}\n\t\t\t};\n\t\t\texpr.accept(astt);\n\t\t} catch (PrismLangException e) {\n\t\t\treturn false;\n\t\t}\n\t\t// All good\n\t\treturn true;\n\t}\n\n\t/**\n\t * Converts an Expression that is a simple path formula to a canonical form:\n\t * Either a single non-negated next-step operator\n\t * or a single until-operator, optionally preceded by a single negation.\n\t * Parentheses are removed.\n\t * @param expr the simple path formula\n\t * @return the canonical expression\n\t */\n\tpublic static Expression convertSimplePathFormulaToCanonicalForm(Expression expr) throws PrismLangException\n\t{\n\t\tboolean negated = false;\n\n\t\tif (!expr.isSimplePathFormula()) {\n\t\t\tthrow new PrismLangException(\"Expression is not a simple path formula.\");\n\t\t}\n\n\t\t// Negation/parentheses\n\t\twhile (expr instanceof ExpressionUnaryOp) {\n\t\t\tExpressionUnaryOp exprUnary = (ExpressionUnaryOp) expr;\n\t\t\t// remove parentheses\n\t\t\tif (exprUnary.getOperator() == ExpressionUnaryOp.PARENTH) {\n\t\t\t\texpr = exprUnary.getOperand();\n\t\t\t}\n\t\t\t// deal with negation\n\t\t\telse if (exprUnary.getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\t\tnegated = !negated;\n\t\t\t\texpr = exprUnary.getOperand();\n\t\t\t} else {\n\t\t\t\tthrow new PrismLangException(\"Expression is not a simple path formula: Unexpected unary operator \"+exprUnary.getOperatorSymbol());\n\t\t\t}\n\t\t}\n\n\t\t// Temporal operator\n\t\tif (expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\t// Next\n\t\t\tif (exprTemp.getOperator() == ExpressionTemporal.P_X) {\n\t\t\t\tif (negated) {\n\t\t\t\t\tif (exprTemp.hasBounds()) throw new PrismLangException(\"Next-Step operator should not have bounds!\");\n\n\t\t\t\t\t// ! X expr  <=> X ! expr\n\t\t\t\t\treturn new ExpressionTemporal(ExpressionTemporal.P_X, null,\n\t\t\t\t\t                              Expression.Not(Expression.Parenth(exprTemp.getOperand2())));\n\t\t\t\t} else {\n\t\t\t\t\t// X expr\n\t\t\t\t\treturn exprTemp;\n\t\t\t\t}\n\t\t\t} else if (exprTemp.getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\t// Until\n\t\t\t\texpr = exprTemp;\n\t\t\t} else {\n\t\t\t\t// other operators: convert\n\t\t\t\texpr = exprTemp.convertToUntilForm();\n\t\t\t}\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Expression is not a simple path formula: Unsupported expression \"+expr.toString());\n\t\t}\n\n\t\tif (negated) {\n\t\t\tif (expr instanceof ExpressionUnaryOp &&\n\t\t\t    ((ExpressionUnaryOp)expr).getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\t\t// remove the outer negation\n\t\t\t\treturn ((ExpressionUnaryOp)expr).getOperand();\n\t\t\t} else {\n\t\t\t\t// negate\n\t\t\t\treturn Expression.Not(expr);\n\t\t\t}\n\t\t}\n\n\t\treturn expr;\n\t}\n\n\t/**\n\t * Create a property expression (an LTL formula) from the classes used by the jltl2ba (and jltl2dstar) libraries.\n\t */\n\tpublic static Expression createFromJltl2ba(SimpleLTL ltl) throws PrismException\n\t{\n\t\tswitch (ltl.kind) {\n\t\tcase AND:\n\t\t\treturn Expression.And(createFromJltl2ba(ltl.left), createFromJltl2ba(ltl.right));\n\t\tcase AP:\n\t\t\treturn new ExpressionLabel(ltl.ap);\n\t\tcase EQUIV:\n\t\t\treturn Expression.Iff(createFromJltl2ba(ltl.left), createFromJltl2ba(ltl.right));\n\t\tcase FALSE:\n\t\t\treturn Expression.False();\n\t\tcase FINALLY:\n\t\t\treturn new ExpressionTemporal(ExpressionTemporal.P_F, null, createFromJltl2ba(ltl.left));\n\t\tcase GLOBALLY:\n\t\t\treturn new ExpressionTemporal(ExpressionTemporal.P_G, null, createFromJltl2ba(ltl.left));\n\t\tcase IMPLIES:\n\t\t\treturn Expression.Implies(createFromJltl2ba(ltl.left), createFromJltl2ba(ltl.right));\n\t\tcase NEXT:\n\t\t\treturn new ExpressionTemporal(ExpressionTemporal.P_X, null, createFromJltl2ba(ltl.left));\n\t\tcase NOT:\n\t\t\treturn Expression.Not(createFromJltl2ba(ltl.left));\n\t\tcase OR:\n\t\t\treturn Expression.Or(createFromJltl2ba(ltl.left), createFromJltl2ba(ltl.right));\n\t\tcase RELEASE:\n\t\t\treturn new ExpressionTemporal(ExpressionTemporal.P_R, createFromJltl2ba(ltl.left), createFromJltl2ba(ltl.right));\n\t\tcase TRUE:\n\t\t\treturn Expression.True();\n\t\tcase UNTIL:\n\t\t\treturn new ExpressionTemporal(ExpressionTemporal.P_U, createFromJltl2ba(ltl.left), createFromJltl2ba(ltl.right));\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Cannot convert jltl2ba formula \" + ltl);\n\t\t}\n\t}\n\n\t/**\n\t * Convert {@code expr} to a string, enclosing in () if its precedence is (strictly) less than {@code parent}.\n\t * @param expr Expression to convert to string\n\t * @param parent Parent expression directly containing {@code expr}\n\t */\n\tpublic static String toStringPrecLt(Expression expr, Expression parent)\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\t\tbuilder.append(expr.toString());\n\t\tif (hasPrecedenceLessThan(expr, parent)) {\n\t\t\tbuilder.insert(0, \"(\");\n\t\t\tbuilder.append(\")\");\n\t\t}\n\t\treturn builder.toString();\n\t}\n\n\t/**\n\t * Convert {@code expr} to a string, enclosing in () if its precedence is less than or equal to its {@code parent}.\n\t * @param expr Expression to convert to string\n\t * @param parent Parent expression directly containing {@code expr}\n\t */\n\tpublic static String toStringPrecLeq(Expression expr, Expression parent)\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\t\tbuilder.append(expr.toString());\n\t\tif (hasPrecedenceLessThanOrEquals(expr, parent)) {\n\t\t\tbuilder.insert(0, \"(\");\n\t\t\tbuilder.append(\")\");\n\t\t}\n\t\treturn builder.toString();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionBinaryOp.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.math.BigInteger;\n\nimport param.BigRational;\nimport parser.EvaluateContext;\nimport parser.EvaluateContext.EvalMode;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionBinaryOp extends Expression\n{\n\t// Operator constants\n\tpublic static final int IMPLIES = 1;\n\tpublic static final int IFF = 2;\n\tpublic static final int OR = 3;\n\tpublic static final int AND = 4;\n\tpublic static final int EQ = 5;\n\tpublic static final int NE = 6;\n\tpublic static final int GT = 7;\n\tpublic static final int GE = 8;\n\tpublic static final int LT = 9;\n\tpublic static final int LE = 10;\n\tpublic static final int PLUS = 11;\n\tpublic static final int MINUS = 12;\n\tpublic static final int TIMES = 13;\n\tpublic static final int DIVIDE = 14;\n\tpublic static final int POW = 15;\n\t// Operator symbols\n\tpublic static final String opSymbols[] = { \"\", \"=>\", \"<=>\", \"|\", \"&\", \"=\", \"!=\", \">\", \">=\", \"<\", \"<=\", \"+\", \"-\", \"*\", \"/\", \"^\" };\n\t// Operator type testers\n\tpublic static boolean isLogical(int op) { return op==IMPLIES || op==IFF || op==OR || op==AND; }\n\tpublic static boolean isRelOp(int op) { return op==EQ || op==NE || op==GT ||  op==GE || op==LT || op==LE; }\n\tpublic static boolean isArithmetic(int op) { return op==PLUS || op==MINUS || op==TIMES || op==DIVIDE || op== POW; }\n\t\n\t// Operator\n\tprotected int op = 0;\n\t// Pair of operands\n\tprotected Expression operand1 = null;\n\tprotected Expression operand2 = null;\n\n\t// Constructors\n\n\tpublic ExpressionBinaryOp()\n\t{\n\t}\n\n\tpublic ExpressionBinaryOp(int op, Expression operand1, Expression operand2)\n\t{\n\t\tthis.operand1 = operand1;\n\t\tthis.operand2 = operand2;\n\t\tthis.op = op;\n\t}\n\n\t// Set methods\n\n\tpublic void setOperator(int i)\n\t{\n\t\top = i;\n\t}\n\n\t/**\n\t * Set the operator from the operator symbol.\n\t */\n\tpublic void setOperator(String s) throws PrismLangException\n\t{\n\t\tfor (int i = 1; i < opSymbols.length; i++) {\n\t\t\tif (opSymbols[i].equals(s)) {\n\t\t\t\tsetOperator(i);\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\tthrow new PrismLangException(\"Unknown binary operator '\" + s + \"'\");\n\t}\n\n\tpublic void setOperand1(Expression e1)\n\t{\n\t\toperand1 = e1;\n\t}\n\n\tpublic void setOperand2(Expression e2)\n\t{\n\t\toperand2 = e2;\n\t}\n\n\t// Get methods\n\n\tpublic int getOperator()\n\t{\n\t\treturn op;\n\t}\n\n\tpublic String getOperatorSymbol()\n\t{\n\t\treturn opSymbols[op];\n\t}\n\n\tpublic Expression getOperand1()\n\t{\n\t\treturn operand1;\n\t}\n\n\tpublic Expression getOperand2()\n\t{\n\t\treturn operand2;\n\t}\n\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn operand1.isConstant() && operand2.isConstant();\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn operand1.isProposition() && operand2.isProposition();\n\t}\n\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tObject eval1 = operand1.evaluate(ec);\n\t\tswitch (op) {\n\t\t\t// Short-circuit evaluation\n\t\t\tcase IMPLIES:\n\t\t\t\treturn !((boolean) eval1) || ((boolean) operand2.evaluate(ec));\n\t\t\tcase OR:\n\t\t\t\treturn ((boolean) eval1) || ((boolean) operand2.evaluate(ec));\n\t\t\tcase AND:\n\t\t\t\treturn ((boolean) eval1) && ((boolean) operand2.evaluate(ec));\n\t\t\t// No short-circuit evaluation\n\t\t\tdefault:\n\t\t\t\tObject eval2 = operand2.evaluate(ec);\n\t\t\t\treturn apply(eval1, eval2, ec.getEvaluationMode());\n\t\t}\n\t}\n\t\n\t/**\n\t * Apply this binary operator instance to the arguments provided\n\t */\n\tpublic Object apply(Object eval1, Object eval2, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tswitch (op) {\n\n\t\t// Boolean operators (any eval mode)\n\t\tcase IMPLIES:\n\t\t\treturn !((boolean) eval1) || ((boolean) eval2);\n\t\tcase IFF:\n\t\t\treturn ((boolean) eval1) == ((boolean) eval2);\n\t\tcase OR:\n\t\t\treturn ((boolean) eval1) || ((boolean) eval2);\n\t\tcase AND:\n\t\t\treturn ((boolean) eval1) && ((boolean) eval2);\n\n\t\t// (In)equality (any eval mode)\n\t\tcase EQ:\n\t\tcase NE:\n\t\t\t// Cast arguments to the same type if needed,\n\t\t\t// before testing using equals() on the resulting Objects\n\t\t\tif (!operand1.getType().equals(operand2.getType())) {\n\t\t\t\tif (operand1.getType().canCastTypeTo(operand2.getType())) {\n\t\t\t\t\teval1 = operand1.getType().castValueTo(eval1);\n\t\t\t\t\teval2 = operand1.getType().castValueTo(eval2);\n\t\t\t\t} else if (operand2.getType().canCastTypeTo(operand1.getType())) {\n\t\t\t\t\teval1 = operand2.getType().castValueTo(eval1);\n\t\t\t\t\teval2 = operand2.getType().castValueTo(eval2);\n\t\t\t\t} else {\n\t\t\t\t\tthrow new PrismLangException(\"Cannot apply \" + getOperatorSymbol() + \" to \" + operand1.getType() + \" and \" + operand2.getType(), this);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn op == EQ ? eval1.equals(eval2) : !eval1.equals(eval2);\n\n\t\t// Division (always evaluates to a double)\n\t\tcase DIVIDE:\n\t\t\t// Type will always be double; so cast both to doubles\n\t\t\tObject eval1D = TypeDouble.getInstance().castValueTo(eval1, evalMode);\n\t\t\tObject eval2D = TypeDouble.getInstance().castValueTo(eval2, evalMode);\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn ((double) eval1D) / ((double) eval2D);\n\t\t\tcase EXACT:\n\t\t\t\treturn ((BigRational) eval1D).divide(((BigRational) eval2D));\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\n\t\t// Division (reuse code for pow())\n\t\tcase POW:\n\t\t\treturn ExpressionFunc.applyPow(getType(), eval1, eval2, evalMode);\n\n\t\t// Other numerical (relations/arithmetic) - mix of doubles/ints\n\t\tdefault:\n\t\t\ttry {\n\t\t\t\t// Two ints\n\t\t\t\tif (operand1.getType() == TypeInt.getInstance() && operand2.getType() == TypeInt.getInstance()) {\n\t\t\t\t\tswitch (evalMode) {\n\t\t\t\t\tcase FP:\n\t\t\t\t\t\tint i1 = (int) eval1;\n\t\t\t\t\t\tint i2 = (int) eval2;\n\t\t\t\t\t\tswitch (op) {\n\t\t\t\t\t\tcase GT:\n\t\t\t\t\t\t\treturn i1 > i2;\n\t\t\t\t\t\tcase GE:\n\t\t\t\t\t\t\treturn i1 >= i2;\n\t\t\t\t\t\tcase LT:\n\t\t\t\t\t\t\treturn i1 < i2;\n\t\t\t\t\t\tcase LE:\n\t\t\t\t\t\t\treturn i1 <= i2;\n\t\t\t\t\t\tcase PLUS:\n\t\t\t\t\t\t\treturn Math.addExact(i1, i2);\n\t\t\t\t\t\tcase MINUS:\n\t\t\t\t\t\t\treturn Math.subtractExact(i1, i2);\n\t\t\t\t\t\tcase TIMES:\n\t\t\t\t\t\t\treturn Math.multiplyExact(i1, i2);\n\t\t\t\t\t\t}\n\t\t\t\t\tcase EXACT:\n\t\t\t\t\t\tBigInteger bi1 = (BigInteger) eval1;\n\t\t\t\t\t\tBigInteger bi2 = (BigInteger) eval2;\n\t\t\t\t\t\tswitch (op) {\n\t\t\t\t\t\tcase GT:\n\t\t\t\t\t\t\treturn bi1.compareTo(bi2) > 0;\n\t\t\t\t\t\tcase GE:\n\t\t\t\t\t\t\treturn bi1.compareTo(bi2) >= 0;\n\t\t\t\t\t\tcase LT:\n\t\t\t\t\t\t\treturn bi1.compareTo(bi2) < 0;\n\t\t\t\t\t\tcase LE:\n\t\t\t\t\t\t\treturn bi1.compareTo(bi2) <= 0;\n\t\t\t\t\t\tcase PLUS:\n\t\t\t\t\t\t\treturn bi1.add(bi2);\n\t\t\t\t\t\tcase MINUS:\n\t\t\t\t\t\t\treturn bi1.subtract(bi2);\n\t\t\t\t\t\tcase TIMES:\n\t\t\t\t\t\t\treturn bi1.multiply(bi2);\n\t\t\t\t\t\t}\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// One or more arguments doubles - convert all to doubles\n\t\t\t\telse {\n\t\t\t\t\teval1D = TypeDouble.getInstance().castValueTo(eval1, evalMode);\n\t\t\t\t\teval2D = TypeDouble.getInstance().castValueTo(eval2, evalMode);\n\t\t\t\t\tswitch (evalMode) {\n\t\t\t\t\tcase FP:\n\t\t\t\t\t\tdouble d1 = (double) TypeDouble.getInstance().castValueTo(eval1, EvalMode.FP);\n\t\t\t\t\t\tdouble d2 = (double) TypeDouble.getInstance().castValueTo(eval2, EvalMode.FP);\n\t\t\t\t\t\tswitch (op) {\n\t\t\t\t\t\tcase GT:\n\t\t\t\t\t\t\treturn d1 > d2;\n\t\t\t\t\t\tcase GE:\n\t\t\t\t\t\t\treturn d1 >= d2;\n\t\t\t\t\t\tcase LT:\n\t\t\t\t\t\t\treturn d1 < d2;\n\t\t\t\t\t\tcase LE:\n\t\t\t\t\t\t\treturn d1 <= d2;\n\t\t\t\t\t\tcase PLUS:\n\t\t\t\t\t\t\treturn d1 + d2;\n\t\t\t\t\t\tcase MINUS:\n\t\t\t\t\t\t\treturn d1 - d2;\n\t\t\t\t\t\tcase TIMES:\n\t\t\t\t\t\t\treturn d1 * d2;\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Unknown binary operator\", this);\n\t\t\t\t\t\t}\n\t\t\t\t\tcase EXACT:\n\t\t\t\t\t\tBigRational br1 = (BigRational) TypeDouble.getInstance().castValueTo(eval1, EvalMode.EXACT);\n\t\t\t\t\t\tBigRational br2 = (BigRational) TypeDouble.getInstance().castValueTo(eval2, EvalMode.EXACT);\n\t\t\t\t\t\tswitch (op) {\n\t\t\t\t\t\tcase GT:\n\t\t\t\t\t\t\treturn br1.compareTo(br2) > 0;\n\t\t\t\t\t\tcase GE:\n\t\t\t\t\t\t\treturn br1.compareTo(br2) >= 0;\n\t\t\t\t\t\tcase LT:\n\t\t\t\t\t\t\treturn br1.compareTo(br2) < 0;\n\t\t\t\t\t\tcase LE:\n\t\t\t\t\t\t\treturn br1.compareTo(br2) <= 0;\n\t\t\t\t\t\tcase PLUS:\n\t\t\t\t\t\t\treturn br1.add(br2);\n\t\t\t\t\t\tcase MINUS:\n\t\t\t\t\t\t\treturn br1.subtract(br2);\n\t\t\t\t\t\tcase TIMES:\n\t\t\t\t\t\t\treturn br1.multiply(br2);\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Unknown binary operator\", this);\n\t\t\t\t\t\t}\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} catch (ArithmeticException e) {\n\t\t\t\tthrow new PrismLangException(e.getMessage(), this);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn operand1.returnsSingleValue() && operand2.returnsSingleValue();\n\t}\n\n\t@Override\n\tpublic Precedence getPrecedence()\n\t{\n\t\tswitch (op) {\n\t\t\tcase IMPLIES:\n\t\t\t\treturn Precedence.IMPLIES;\n\t\t\tcase IFF:\n\t\t\t\treturn Precedence.IFF;\n\t\t\tcase OR:\n\t\t\t\treturn Precedence.OR;\n\t\t\tcase AND:\n\t\t\t\treturn Precedence.AND;\n\t\t\tcase EQ:\n\t\t\tcase NE:\n\t\t\t\treturn Precedence.EQUALITY;\n\t\t\tcase GT:\n\t\t\tcase GE:\n\t\t\tcase LT:\n\t\t\tcase LE:\n\t\t\t\treturn Precedence.RELOP;\n\t\t\tcase PLUS:\n\t\t\tcase MINUS:\n\t\t\t\treturn Precedence.PLUS_MINUS;\n\t\t\tcase TIMES:\n\t\t\tcase DIVIDE:\n\t\t\t\treturn Precedence.TIMES_DIVIDE;\n\t\t\tcase POW:\n\t\t\t\treturn Precedence.POW;\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t}\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionBinaryOp deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand1 = copier.copy(operand1);\n\t\toperand2 = copier.copy(operand2);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionBinaryOp clone()\n\t{\n\t\treturn (ExpressionBinaryOp) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\t\tif (op == IMPLIES || op == EQ || op == NE) {\n\t\t\t// => is a (right-associative) non-commutative binary operator\n\t\t\t// Don't treat = and != as associative since types may vary\n\t\t\tbuilder.append(Expression.toStringPrecLeq(operand1, this));\n\t\t} else {\n\t\t\t// Others are commutative (or left-associative)\n\t\t\tbuilder.append(Expression.toStringPrecLt(operand1, this));\n\t\t}\n\t\tbuilder.append(opSymbols[op]);\n\t\tif (op == MINUS || op == DIVIDE || op == EQ || op == NE) {\n\t\t\t// - and / are (left-associative) non-commutative binary operators\n\t\t\t// Don't treat = and != as associative since types may vary\n\t\t\tbuilder.append(Expression.toStringPrecLeq(operand2, this));\n\t\t} else {\n\t\t\t// Others are commutative (or right-associative)\n\t\t\tbuilder.append(Expression.toStringPrecLt(operand2, this));\n\t\t}\n\t\treturn builder.toString();\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + op;\n\t\tresult = prime * result + ((operand1 == null) ? 0 : operand1.hashCode());\n\t\tresult = prime * result + ((operand2 == null) ? 0 : operand2.hashCode());\n\t\treturn result;\n\t}\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionBinaryOp other = (ExpressionBinaryOp) obj;\n\t\tif (op != other.op)\n\t\t\treturn false;\n\t\tif (operand1 == null) {\n\t\t\tif (other.operand1 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand1.equals(other.operand1))\n\t\t\treturn false;\n\t\tif (operand2 == null) {\n\t\t\tif (other.operand2 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand2.equals(other.operand2))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionConstant.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.type.Type;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionConstant extends Expression\n{\n\tprotected String name;\n\t\n\t// Constructors\n\t\n\tpublic ExpressionConstant()\n\t{\n\t}\n\t\n\tpublic ExpressionConstant(String n, Type t)\n\t{\n\t\tsetType(t);\n\t\tname = n;\n\t}\n\t\t\t\n\t// Set method\n\t\n\tpublic void setName(String n) \n\t{\n\t\tname = n;\n\t}\n\t\n\t// Get method\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\t// Extract constant value from the evaluation context\n\t\tObject res = ec.getConstantValue(name);\n\t\tif (res == null) {\n\t\t\tthrow new PrismLangException(\"Could not evaluate constant\", this);\n\t\t}\n\t\t// And cast it to the right type/mode if needed\n\t\treturn getType().castValueTo(res, ec.getEvaluationMode());\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn true;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic ExpressionConstant deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionConstant clone()\n\t{\n\t\treturn (ExpressionConstant) super.clone();\n\t}\n\t\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn name;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((name == null) ? 0 : name.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionConstant other = (ExpressionConstant) obj;\n\t\tif (name == null) {\n\t\t\tif (other.name != null)\n\t\t\t\treturn false;\n\t\t} else if (!name.equals(other.name))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionExists.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionExists extends Expression\n{\n\tprotected Expression expression = null;\n\t\n\t// Constructors\n\t\n\tpublic ExpressionExists()\n\t{\n\t}\n\t\n\tpublic ExpressionExists(Expression e)\n\t{\n\t\texpression = e;\n\t}\n\n\t// Set methods\n\t\n\tpublic void setExpression(Expression e)\n\t{\n\t\texpression = e;\n\t}\n\n\t// Get methods\n\t\n\tpublic Expression getExpression()\n\t{\n\t\treturn expression;\n\t}\n\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate an E operator without a model\");\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic ExpressionExists deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\texpression = copier.copy(expression);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionExists clone()\n\t{\n\t\treturn (ExpressionExists) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\t\n\t\ts += \"E [ \" + expression + \" ]\";\n\t\t\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((expression == null) ? 0 : expression.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionExists other = (ExpressionExists) obj;\n\t\tif (expression == null) {\n\t\t\tif (other.expression != null)\n\t\t\t\treturn false;\n\t\t} else if (!expression.equals(other.expression))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionFilter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.type.Type;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.Accuracy;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismUtils;\n\npublic class ExpressionFilter extends Expression\n{\n\t/**\n\t * Types of filter, for expressions of the form \"filter(op, prop, states)\",\n\t * with filter states \"states\" being optional (denoting \"true\").\n\t */ \n\tpublic enum FilterOperator {\n\t\t/** Minimum value of prop over all filter states */\n\t\tMIN (\"min\"),\n\t\t/** Maximum value of prop over all filter states */\n\t\tMAX (\"max\"),\n\t\t/** True for the filter states that yield the minimum value of prop */\n\t\tARGMIN (\"argmin\"),\n\t\t/** True for the filter states that yield the maximum value of prop */\n\t\tARGMAX (\"argmax\"),\n\t\t/** Number of filter states for which prop is true */\n\t\tCOUNT (\"count\"),\n\t\t/** Sum of the value of prop for all filter states */\n\t\tSUM (\"sum\"),\n\t\t/** Average of the value of prop over all filter states */\n\t\tAVG (\"avg\"),\n\t\t/** Value of prop for the first (lowest-indexed) filter state */\n\t\tFIRST (\"first\"),\n\t\t/** Range (interval) of values of prop over all filter states */\n\t\tRANGE (\"range\"),\n\t\t/** True iff prop is true for all filter states */\n\t\tFORALL (\"forall\"),\n\t\t/** True iff prop is true for some filter states */\n\t\tEXISTS (\"exists\"),\n\t\t/** Print the (non-zero) values to the log */\n\t\tPRINT (\"print\"),\n\t\t/** Print all (including zero) values to the log */\n\t\tPRINTALL (\"printall\"),\n\t\t/** Value for the single filter state (if there is more than one, this is an error) */\n\t\tSTATE (\"state\"),\n\t\t/** Store the results vector (used internally) */\n\t\tSTORE (\"store\");\n\t\tpublic final String keyword;\n\t\tFilterOperator(final String keyword) {\n\t\t\tthis.keyword = keyword;\n\t\t}\n\t};\n\n\t// Operator used in filter\n\t// (and string representation of)\n\tprivate FilterOperator opType;\n\tprivate String opName;\n\t// Expression that filter is applied to\n\tprivate Expression operand;\n\t// Expression defining states that filter is over\n\t// (optional; can be null, denoting \"true\")\n\tprivate Expression filter;\n\t\n\t// Filter can be invisible, meaning it is not actually displayed\n\t// by toString(). This is used to add filters to P/R/S operators that\n\t// were created with old-style filter syntax. \n\tprivate boolean invisible = false;\n\t// Whether or not an explanation should be displayed when model checking\n\tprivate boolean explanationEnabled = true;\n\t// whether this is a filter over parameters\n\tprivate boolean param = false;\n\t\n\n\t// Constructors\n\n\tpublic ExpressionFilter(String opName, Expression operand)\n\t{\n\t\tthis(opName, operand, null);\n\t}\n\n\tpublic ExpressionFilter(String opName, Expression operand, Expression filter)\n\t{\n\t\tsetOperator(opName);\n\t\tsetOperand(operand);\n\t\tsetFilter(filter);\n\t}\n\n\t// Set methods\n\n\tpublic void setOperator(String opName)\n\t{\n\t\tthis.opName = opName;\n\t\tfor (FilterOperator op : FilterOperator.values()) {\n\t\t\tif (op.keyword.equals(opName)) {\n\t\t\t\topType = op;\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\t// handle shorthands\n\t\tif (\"+\".equals(opName)) {\n\t\t\topType = FilterOperator.SUM;\n\t\t} else if (\"&\".equals(opName)) {\n\t\t\topType = FilterOperator.FORALL;\n\t\t} else if (\"|\".equals(opName)) {\n\t\t\topType = FilterOperator.EXISTS;\n\t\t} else {\n\t\t\topType = null;\n\t\t}\n\t}\n\n\tpublic void setOperand(Expression operand)\n\t{\n\t\tthis.operand = operand;\n\t}\n\t\n\tpublic void setFilter(Expression filter)\n\t{\n\t\tthis.filter = filter;\n\t}\n\t\n\tpublic void setInvisible(boolean invisible)\n\t{\n\t\tthis.invisible = invisible;\n\t}\n\t\n\tpublic void setExplanationEnabled(boolean explanationEnabled)\n\t{\n\t\tthis.explanationEnabled = explanationEnabled;\n\t}\n\t\n\tpublic void setParam()\n\t{\n\t\tparam = true;\n\t}\n\n\t// Get methods\n\n\tpublic FilterOperator getOperatorType()\n\t{\n\t\treturn opType;\n\t}\n\n\tpublic String getOperatorName()\n\t{\n\t\treturn opName;\n\t}\n\n\tpublic Expression getOperand()\n\t{\n\t\treturn operand;\n\t}\n\n\tpublic Expression getFilter()\n\t{\n\t\treturn filter;\n\t}\n\n\tpublic boolean isInvisible()\n\t{\n\t\treturn invisible;\n\t}\n\n\tpublic boolean getExplanationEnabled()\n\t{\n\t\treturn explanationEnabled;\n\t}\n\t\n\tpublic boolean isParam()\n\t{\n\t\treturn param;\n\t}\n\t\n\t// Definitions of filter operators\n\t\n\t/**\n\t * Apply this filter instance to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the type of this filter's operand.\n\t */\n\tpublic Object apply(Iterable<Object> values) throws PrismException\n\t{\n\t\tswitch (opType) {\n\t\tcase MIN:\n\t\t\treturn applyMin(values, operand.getType());\n\t\tcase MAX:\n\t\t\treturn applyMax(values, operand.getType());\n\t\tcase COUNT:\n\t\t\treturn applyCount(values, operand.getType());\n\t\tcase SUM:\n\t\t\treturn applySum(values, operand.getType());\n\t\tcase AVG:\n\t\t\treturn applyAvg(values, operand.getType());\n\t\tcase RANGE:\n\t\t\treturn applyRange(values, operand.getType());\n\t\tcase FORALL:\n\t\t\treturn applyForAll(values, operand.getType());\n\t\tcase EXISTS:\n\t\t\treturn applyExists(values, operand.getType());\n\t\tdefault:\n\t\t\tthrow new PrismException(\"No apply operator for filter \\\"\" + opName + \"\\\"\");\n\t\t}\n\t}\n\t\n\t/**\n\t * Apply a min filter to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the provided type.\n\t */\n\tpublic static Object applyMin(Iterable<Object> values, Type type) throws PrismException\n\t{\n\t\tif (type instanceof TypeInt) {\n\t\t\tint min = Integer.MAX_VALUE;\n\t\t\tfor (Object value : values) {\n\t\t\t\tmin = Math.min(min, (int) value);\n\t\t\t}\n\t\t\treturn min;\n\t\t} else if (type instanceof TypeDouble) {\n\t\t\tdouble min = Double.POSITIVE_INFINITY;\n\t\t\tfor (Object value : values) {\n\t\t\t\tmin = Math.min(min, (double) value);\n\t\t\t}\n\t\t\treturn min;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't apply min over elements of type \" + type);\n\t\t}\n\t}\n\n\t/**\n\t * Apply a max filter to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the provided type.\n\t */\n\tpublic static Object applyMax(Iterable<Object> values, Type type) throws PrismException\n\t{\n\t\tif (type instanceof TypeInt) {\n\t\t\tint max = Integer.MIN_VALUE;\n\t\t\tfor (Object value : values) {\n\t\t\t\tmax = Math.max(max, (int) value);\n\t\t\t}\n\t\t\treturn max;\n\t\t} else if (type instanceof TypeDouble) {\n\t\t\tdouble max = Double.NEGATIVE_INFINITY;\n\t\t\tfor (Object value : values) {\n\t\t\t\tmax = Math.max(max, (double) value);\n\t\t\t}\n\t\t\treturn max;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't apply max over elements of type \" + type);\n\t\t}\n\t}\n\n\t/**\n\t * Apply a count filter to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the provided type.\n\t */\n\tpublic static Object applyCount(Iterable<Object> values, Type type) throws PrismException\n\t{\n\t\tif (type instanceof TypeBool) {\n\t\t\tint count = 0;\n\t\t\tfor (Object value : values) {\n\t\t\t\tif ((boolean) value) {\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn count;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't apply count over elements of type \" + type);\n\t\t}\n\t}\n\t\n\t/**\n\t * Apply a sum filter to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the provided type.\n\t */\n\tpublic static Object applySum(Iterable<Object> values, Type type) throws PrismException\n\t{\n\t\tif (type instanceof TypeInt) {\n\t\t\tint sum = 0;\n\t\t\tfor (Object value : values) {\n\t\t\t\tsum += (int) value;\n\t\t\t}\n\t\t\treturn sum;\n\t\t} else if (type instanceof TypeDouble) {\n\t\t\tdouble sum = 0.0;\n\t\t\tfor (Object value : values) {\n\t\t\t\tsum += (double) value;\n\t\t\t}\n\t\t\treturn sum;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't apply sum over elements of type \" + type);\n\t\t}\n\t}\n\t\n\t/**\n\t * Apply an average filter to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the provided type.\n\t */\n\tpublic static Object applyAvg(Iterable<Object> values, Type type) throws PrismException\n\t{\n\t\tif (type instanceof TypeInt) {\n\t\t\tint count = 0;\n\t\t\tdouble sum = 0.0;\n\t\t\tfor (Object value : values) {\n\t\t\t\tcount++;\n\t\t\t\tsum += (int) value;\n\t\t\t}\n\t\t\treturn sum / count;\n\t\t} else if (type instanceof TypeDouble) {\n\t\t\tint count = 0;\n\t\t\tdouble sum = 0.0;\n\t\t\tfor (Object value : values) {\n\t\t\t\tcount++;\n\t\t\t\tsum += (double) value;\n\t\t\t}\n\t\t\treturn sum / count;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't apply avg over elements of type \" + type);\n\t\t}\n\t}\n\t\n\t/**\n\t * Apply a range filter to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the provided type.\n\t */\n\tpublic static Object applyRange(Iterable<Object> values, Type type) throws PrismException\n\t{\n\t\tif (type instanceof TypeInt) {\n\t\t\tint min = Integer.MAX_VALUE;\n\t\t\tint max = Integer.MIN_VALUE;\n\t\t\tfor (Object value : values) {\n\t\t\t\tmin = Math.min(min, (int) value);\n\t\t\t\tmax = Math.max(max, (int) value);\n\t\t\t}\n\t\t\treturn new prism.Interval(min, max);\n\t\t} else if (type instanceof TypeDouble) {\n\t\t\tdouble min = Double.POSITIVE_INFINITY;\n\t\t\tdouble max = Double.NEGATIVE_INFINITY;\n\t\t\tfor (Object value : values) {\n\t\t\t\tmin = Math.min(min, (double) value);\n\t\t\t\tmax = Math.max(max, (double) value);\n\t\t\t}\n\t\t\treturn new prism.Interval(min, max);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't apply min over elements of type \" + type);\n\t\t}\n\t}\n\n\t/**\n\t * Apply a for all filter to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the provided type.\n\t */\n\tpublic static Object applyForAll(Iterable<Object> values, Type type) throws PrismException\n\t{\n\t\tif (type instanceof TypeBool) {\n\t\t\tfor (Object value : values) {\n\t\t\t\tif (!((boolean) value)) {\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn true;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't apply for all over elements of type \" + type);\n\t\t}\n\t}\n\t\n\t/**\n\t * Apply an exists filter to the list of values provided.\n\t * The values should all be the same type of Object, which should\n\t * be the expected one for the provided type.\n\t */\n\tpublic static Object applyExists(Iterable<Object> values, Type type) throws PrismException\n\t{\n\t\tif (type instanceof TypeBool) {\n\t\t\tfor (Object value : values) {\n\t\t\t\tif ((boolean) value) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Can't apply there exists over elements of type \" + type);\n\t\t}\n\t}\n\t\n\t/**\n\t * Convenience method: check two values, {@code value} and {@code match}\n\t * for (approximate) equality. If the value is a double, stored imprecisely\n\t * (i.e., floating point), and the passed in accuracy is non-null, then this\n\t * returns true iff {@code match} falls within the range of possible values\n\t * for {@code value}, given it's accuracy. Otherwise, exactly equality is checked.\n\t * The type of Object for the values should be the expected one for the provided type.\n\t * @param value The value to check\n\t * @param match The value to check against {@code value}\n\t * @param type The type corresponding to both {@code value} and {@code match}\n\t * @param accuracy Optionally, the accuracy of {@code value}\n\t */\n\tpublic static boolean isClose(Object value, Object match, Type type, Accuracy accuracy) throws PrismException\n\t{\n\t\tif (value instanceof Double && accuracy != null) {\n\t\t\tdouble valueD = (double) value;\n\t\t\tdouble matchD = (double) match;\n\t\t\treturn PrismUtils.measureSupNormAbs(valueD, matchD) <= accuracy.getAbsoluteErrorBound(valueD);\n\t\t} else {\n\t\t\treturn value.equals(match);\n\t\t}\n\t}\n\t\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\t// Note: In some sense, ExpressionFilters are (often) constant since they return the same\n\t\t// value for every state. But the actual value is model dependent, so they are not\n\t\t// considered to be constants.\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate a filter without a model\");\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\t// Most filters return a single value, but there are some exceptions...\n\t\tif (opType == FilterOperator.PRINT) return false;\n\t\telse if (opType == FilterOperator.PRINTALL) return false;\n\t\telse if (opType == FilterOperator.ARGMIN) return false;\n\t\telse if (opType == FilterOperator.ARGMAX) return false;\n\t\telse if (opType == FilterOperator.STORE) return false;\n\t\telse if (param) return false;\n\t\telse return true;\n\t}\n\t\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionFilter deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand = copier.copy(operand);\n\t\tfilter = copier.copy(filter);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionFilter clone()\n\t{\n\t\treturn (ExpressionFilter) super.clone();\n\t}\n\t\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tif (invisible)\n\t\t\treturn operand.toString();\n\t\ts += (param ? \"paramfilter(\" : \"filter(\") + opName + \", \" + operand;\n\t\tif (filter != null)\n\t\t\ts += \", \" + filter;\n\t\ts += \")\";\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + (explanationEnabled ? 1231 : 1237);\n\t\tresult = prime * result + ((filter == null) ? 0 : filter.hashCode());\n\t\tresult = prime * result + (invisible ? 1231 : 1237);\n\t\tresult = prime * result + ((opName == null) ? 0 : opName.hashCode());\n\t\tresult = prime * result + ((opType == null) ? 0 : opType.hashCode());\n\t\tresult = prime * result + ((operand == null) ? 0 : operand.hashCode());\n\t\tresult = prime * result + (param ? 1231 : 1237);\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionFilter other = (ExpressionFilter) obj;\n\t\tif (explanationEnabled != other.explanationEnabled)\n\t\t\treturn false;\n\t\tif (filter == null) {\n\t\t\tif (other.filter != null)\n\t\t\t\treturn false;\n\t\t} else if (!filter.equals(other.filter))\n\t\t\treturn false;\n\t\tif (invisible != other.invisible)\n\t\t\treturn false;\n\t\tif (opName == null) {\n\t\t\tif (other.opName != null)\n\t\t\t\treturn false;\n\t\t} else if (!opName.equals(other.opName))\n\t\t\treturn false;\n\t\tif (opType != other.opType)\n\t\t\treturn false;\n\t\tif (operand == null) {\n\t\t\tif (other.operand != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand.equals(other.operand))\n\t\t\treturn false;\n\t\tif (param != other.param)\n\t\t\treturn false;\n\t\treturn true;\n\t}\n\t\n\t/**\n\t * Wrap a \"default\" ExpressionFilter around an Expression representing a property to be model checked,\n\t * in order to pick out a single value (the final result of model checking) from a vector of values for all states.\n\t * See the PRISM manual (or check the code below) to see the definition of the \"default\" filter.\n\t * If the expression is already an ExpressionFilter (of the right kind), nothing is done.\n\t * Note that we need to know whether the model has multiple initial states, because this affects the default filter.  \n\t * @param expr Expression to be model checked\n\t * @param singleInit Does the model on which it is being checked have a single initial states? \n\t */\n\tpublic static ExpressionFilter addDefaultFilterIfNeeded(Expression expr, boolean singleInit) throws PrismLangException\n\t{\n\t\tExpressionFilter exprFilter = null;\n\t\t\n\t\t// The final result of model checking will be a single value. If the expression to be checked does not\n\t\t// already yield a single value (e.g. because a filter has not been explicitly included), we need to wrap\n\t\t// a new (invisible) filter around it. Note that some filters (e.g. print/argmin/argmax) also do not\n\t\t// return single values and have to be treated in this way.\n\t\tif (!expr.returnsSingleValue()) {\n\t\t\t// New filter depends on expression type and number of initial states.\n\t\t\t// Boolean expressions...\n\t\t\tif (expr.getType() instanceof TypeBool) {\n\t\t\t\t// Result is true iff true for all initial states\n\t\t\t\texprFilter = new ExpressionFilter(\"forall\", expr, new ExpressionLabel(\"init\"));\n\t\t\t}\n\t\t\t// Non-Boolean (double or integer) expressions...\n\t\t\telse {\n\t\t\t\t// Result is for the initial state, if there is just one,\n\t\t\t\t// or the range over all initial states, if multiple\n\t\t\t\tif (singleInit) {\n\t\t\t\t\texprFilter = new ExpressionFilter(\"state\", expr, new ExpressionLabel(\"init\"));\n\t\t\t\t} else {\n\t\t\t\t\texprFilter = new ExpressionFilter(\"range\", expr, new ExpressionLabel(\"init\"));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Even, when the expression does already return a single value, if the the outermost operator\n\t\t// of the expression is not a filter, we still need to wrap a new filter around it.\n\t\t// e.g. 2*filter(...) or 1-P=?[...{...}]\n\t\t// This because the final result of model checking is only stored when we process a filter.\n\t\telse if (!(expr instanceof ExpressionFilter)) {\n\t\t\t// We just pick the first value (they are all the same)\n\t\t\texprFilter = new ExpressionFilter(\"first\", expr, new ExpressionLabel(\"init\"));\n\t\t\t// We stop any additional explanation being displayed to avoid confusion.\n\t\t\texprFilter.setExplanationEnabled(false);\n\t\t}\n\t\t// Finalise filter (if created) and return\n\t\tif (exprFilter != null) {\n\t\t\t// Make it invisible (not that it will be displayed)\n\t\t\texprFilter.setInvisible(true);\n\t\t\t// Compute type of new filter expression (will be same as child)\n\t\t\texprFilter.typeCheck();\n\t\t\treturn exprFilter;\n\t\t} else {\n\t\t\t// If no new filter was created, we no expr is an ExpressionFilter\n\t\t\treturn (ExpressionFilter) expr;\n\t\t}\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionForAll.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionForAll extends Expression\n{\n\tprotected Expression expression = null;\n\t\n\t// Constructors\n\t\n\tpublic ExpressionForAll()\n\t{\n\t}\n\t\n\tpublic ExpressionForAll(Expression e)\n\t{\n\t\texpression = e;\n\t}\n\n\t// Set methods\n\t\n\tpublic void setExpression(Expression e)\n\t{\n\t\texpression = e;\n\t}\n\n\t// Get methods\n\t\n\tpublic Expression getExpression()\n\t{\n\t\treturn expression;\n\t}\n\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate an E operator without a model\");\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic ExpressionForAll deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\texpression = copier.copy(expression);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionForAll clone()\n\t{\n\t\treturn (ExpressionForAll) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\t\n\t\ts += \"A [ \" + expression + \" ]\";\n\t\t\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((expression == null) ? 0 : expression.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionForAll other = (ExpressionForAll) obj;\n\t\tif (expression == null) {\n\t\t\tif (other.expression != null)\n\t\t\t\treturn false;\n\t\t} else if (!expression.equals(other.expression))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionFormula.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionFormula extends Expression\n{\n\tprotected String name;\n\tprotected Expression definition;\n\t\n\t// Constructors\n\t\n\tpublic ExpressionFormula()\n\t{\n\t}\n\t\n\tpublic ExpressionFormula(String n)\n\t{\n\t\tname = n;\n\t\tdefinition = null;\n\t}\n\t\t\t\n\t// Set method\n\t\n\tpublic void setName(String n) \n\t{\n\t\tname = n;\n\t}\n\t\n\tpublic void setDefinition(Expression definition) \n\t{\n\t\tthis.definition = definition;\n\t}\n\t\n\t// Get method\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\tpublic Expression getDefinition()\n\t{\n\t\treturn definition;\n\t}\n\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\t// Unless defined, don't know so err on the side of caution\n\t\treturn definition == null ? false : definition.isConstant();\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\t// Unless defined, don't know so err on the side of caution\n\t\treturn definition == null ? false : definition.isProposition();\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\t// Should only be called (if at all) after definition has been set\n\t\tif (definition == null)\n\t\t\tthrow new PrismLangException(\"Could not evaluate formula\", this);\n\t\telse\n\t\t\treturn definition.evaluate(ec);\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\t// Unless defined, don't know so err on the side of caution\n\t\treturn definition == null ? false : definition.returnsSingleValue();\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\t\n\t@Override\n\tpublic ExpressionFormula deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tdefinition = copier.copy(definition);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionFormula clone()\n\t{\n\t\treturn (ExpressionFormula) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn name;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((definition == null) ? 0 : definition.hashCode());\n\t\tresult = prime * result + ((name == null) ? 0 : name.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionFormula other = (ExpressionFormula) obj;\n\t\tif (definition == null) {\n\t\t\tif (other.definition != null)\n\t\t\t\treturn false;\n\t\t} else if (!definition.equals(other.definition))\n\t\t\treturn false;\n\t\tif (name == null) {\n\t\t\tif (other.name != null)\n\t\t\t\treturn false;\n\t\t} else if (!name.equals(other.name))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionFunc.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport common.SafeCast;\nimport param.BigRational;\nimport parser.EvaluateContext;\nimport parser.EvaluateContext.EvalMode;\nimport parser.type.Type;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\nimport prism.PrismUtils;\n\nimport java.math.BigInteger;\nimport java.util.ArrayList;\n\npublic class ExpressionFunc extends Expression\n{\n\t// Built-in function name constants\n\tpublic static final int MIN = 0;\n\tpublic static final int MAX = 1;\n\tpublic static final int FLOOR = 2;\n\tpublic static final int CEIL = 3;\n\tpublic static final int ROUND = 4;\n\tpublic static final int POW = 5;\n\tpublic static final int MOD = 6;\n\tpublic static final int LOG = 7;\n\tpublic static final int MULTI = 8;\n\t// Built-in function names\n\tpublic static final String names[] = { \"min\", \"max\", \"floor\", \"ceil\", \"round\", \"pow\", \"mod\", \"log\", \"multi\"};\n\t// Min/max function arities\n\tpublic static final int minArities[] = { 1, 1, 1, 1, 1, 2, 2, 2, 1 };\n\tpublic static final int maxArities[] = { -1, -1, 1, 1, 1, 2, 2, 2, -1 };\n\n\t// Function name\n\tprivate String name = \"\";\n\tprivate int code = -1;\n\t// Operands\n\tprivate ArrayList<Expression> operands;\n\t// Was function written in old style notation (using \"func\" keyword)?\n\tprivate boolean oldStyle = false;\n\n\t// Constructors\n\n\tpublic ExpressionFunc()\n\t{\n\t\toperands = new ArrayList<Expression>();\n\t}\n\n\tpublic ExpressionFunc(String name)\n\t{\n\t\tsetName(name);\n\t\toperands = new ArrayList<Expression>();\n\t}\n\n\t// Set methods\n\n\tpublic void setName(String s)\n\t{\n\t\tint i, n;\n\t\t// Set string\n\t\tname = s;\n\t\t// Determine and set code\n\t\tn = names.length;\n\t\tcode = -1;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (s.equals(names[i])) {\n\t\t\t\tcode = i;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void addOperand(Expression e)\n\t{\n\t\toperands.add(e);\n\t}\n\n\tpublic void setOperand(int i, Expression e)\n\t{\n\t\toperands.set(i, e);\n\t}\n\n\tpublic void setOldStyle(boolean b)\n\t{\n\t\toldStyle = b;\n\t}\n\n\t// Get methods\n\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\n\tpublic int getNameCode()\n\t{\n\t\treturn code;\n\t}\n\n\tpublic int getNumOperands()\n\t{\n\t\treturn operands.size();\n\t}\n\n\tpublic Expression getOperand(int i)\n\t{\n\t\treturn operands.get(i);\n\t}\n\n\tpublic boolean getOldStyle()\n\t{\n\t\treturn oldStyle;\n\t}\n\n\tpublic int getMinArity()\n\t{\n\t\treturn code == -1 ? Integer.MAX_VALUE : minArities[code];\n\t}\n\n\tpublic int getMaxArity()\n\t{\n\t\treturn code == -1 ? -1 : maxArities[code];\n\t}\n\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\tint i, n;\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (!getOperand(i).isConstant())\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\tint i, n;\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (!getOperand(i).isProposition())\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\ttry {\n\t\t\tint n = getNumOperands();\n\t\t\tObject[] eval = new Object[n];\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\teval[i] = getOperand(i).evaluate(ec);\n\t\t\t}\n\t\t\treturn apply(eval, ec.getEvaluationMode());\n\t\t} catch (PrismLangException e) {\n\t\t\te.setASTElement(this);\n\t\t\tthrow e;\n\t\t}\n\t}\n\n\t/**\n\t * Apply this function instance to the arguments provided.\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tpublic Object apply(Object[] eval, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tswitch (code) {\n\t\tcase MIN:\n\t\t\treturn applyMin(eval, evalMode);\n\t\tcase MAX:\n\t\t\treturn applyMax(eval, evalMode);\n\t\tcase FLOOR:\n\t\t\treturn applyFloor(eval[0], evalMode);\n\t\tcase CEIL:\n\t\t\treturn applyCeil(eval[0], evalMode);\n\t\tcase ROUND:\n\t\t\treturn applyRound(eval[0], evalMode);\n\t\tcase POW:\n\t\t\treturn applyPow(eval[0], eval[1], evalMode);\n\t\tcase MOD:\n\t\t\treturn applyMod(eval[0], eval[1], evalMode);\n\t\tcase LOG:\n\t\t\treturn applyLog(eval[0], eval[1], evalMode);\n\t\t}\n\t\tthrow new PrismLangException(\"Unknown function \\\"\" + name + \"\\\"\", this);\n\t}\n\t\n\t/**\n\t * Apply this (unary) function instance to the argument provided.\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tpublic Object applyUnary(Object eval, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tswitch (code) {\n\t\tcase FLOOR:\n\t\t\treturn applyFloor(eval, evalMode);\n\t\tcase CEIL:\n\t\t\treturn applyCeil(eval, evalMode);\n\t\tcase ROUND:\n\t\t\treturn applyRound(eval, evalMode);\n\t\t}\n\t\tthrow new PrismLangException(\"Unknown unary function \\\"\" + name + \"\\\"\", this);\n\t}\n\t\n\t/**\n\t * Apply this (binary, or n-ary) function instance to the argument provided.\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tpublic Object applyBinary(Object eval1, Object eval2, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tswitch (code) {\n\t\tcase MIN:\n\t\t\treturn applyMinBinary(eval1, eval2, evalMode);\n\t\tcase MAX:\n\t\t\treturn applyMaxBinary(eval1, eval2, evalMode);\n\t\tcase POW:\n\t\t\treturn applyPow(eval1, eval2, evalMode);\n\t\tcase MOD:\n\t\t\treturn applyMod(eval1, eval2, evalMode);\n\t\tcase LOG:\n\t\t\treturn applyLog(eval1, eval2, evalMode);\n\t\t}\n\t\tthrow new PrismLangException(\"Unknown binary function \\\"\" + name + \"\\\"\", this);\n\t}\n\t\n\t/**\n\t * Apply this (min) function instance to the arguments provided.\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyMin(Object[] eval, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tint n = eval.length;\n\t\t// All arguments ints\n\t\tif (getType() instanceof TypeInt) {\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\tint iMin = (int) eval[0];\n\t\t\t\tfor (int i = 1; i < n; i++) {\n\t\t\t\t\tiMin = Math.min(iMin, (int) eval[i]);\n\t\t\t\t}\n\t\t\t\treturn iMin;\n\t\t\tcase EXACT:\n\t\t\t\tBigInteger biMin = (BigInteger) eval[0];\n\t\t\t\tfor (int i = 1; i < n; i++) {\n\t\t\t\t\tbiMin = biMin.min((BigInteger) eval[i]);\n\t\t\t\t}\n\t\t\t\treturn biMin;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t\t// One or more arguments doubles - convert all to doubles\n\t\telse {\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\tdouble dMin = (double) TypeDouble.getInstance().castValueTo(eval[0], evalMode);\n\t\t\t\tfor (int i = 1; i < n; i++) {\n\t\t\t\t\tdMin = Math.min(dMin, (double) TypeDouble.getInstance().castValueTo(eval[i], evalMode));\n\t\t\t\t}\n\t\t\t\treturn dMin;\n\t\t\tcase EXACT:\n\t\t\t\tBigRational brMin = (BigRational) TypeDouble.getInstance().castValueTo(eval[0], evalMode);\n\t\t\t\tfor (int i = 1; i < n; i++) {\n\t\t\t\t\tbrMin = brMin.min((BigRational) TypeDouble.getInstance().castValueTo(eval[i], evalMode));\n\t\t\t\t}\n\t\t\t\treturn brMin;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (min) function instance to the argument provided.\n\t * The argument is assumed to be the correct kind of Object for its type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyMinBinary(Object eval1, Object eval2, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// All arguments ints\n\t\tif (getType() instanceof TypeInt) {\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn Math.min((int) eval1, (int) eval2);\n\t\t\tcase EXACT:\n\t\t\t\treturn ((BigInteger) eval1).min((BigInteger) eval2);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t\t// One or more arguments doubles - convert all to doubles\n\t\telse {\n\t\t\tObject eval1D = TypeDouble.getInstance().castValueTo(eval1, evalMode);\n\t\t\tObject eval2D = TypeDouble.getInstance().castValueTo(eval2, evalMode);\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn Math.min((double) eval1D, (double) eval2D);\n\t\t\tcase EXACT:\n\t\t\t\treturn ((BigRational) eval1D).min((BigRational) eval2D);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (max) function instance to the arguments provided.\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyMax(Object[] eval, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tint n = eval.length;\n\t\t// All arguments ints\n\t\tif (getType() instanceof TypeInt) {\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\tint iMax = (int) eval[0];\n\t\t\t\tfor (int i = 1; i < n; i++) {\n\t\t\t\t\tiMax = Math.max(iMax, (int) eval[i]);\n\t\t\t\t}\n\t\t\t\treturn iMax;\n\t\t\tcase EXACT:\n\t\t\t\tBigInteger biMax = (BigInteger) eval[0];\n\t\t\t\tfor (int i = 1; i < n; i++) {\n\t\t\t\t\tbiMax = biMax.max((BigInteger) eval[i]);\n\t\t\t\t}\n\t\t\t\treturn biMax;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t\t// One or more arguments doubles - convert all to doubles\n\t\telse {\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\tdouble dMax = (double) TypeDouble.getInstance().castValueTo(eval[0], evalMode);\n\t\t\t\tfor (int i = 1; i < n; i++) {\n\t\t\t\t\tdMax = Math.max(dMax, (double) TypeDouble.getInstance().castValueTo(eval[i], evalMode));\n\t\t\t\t}\n\t\t\t\treturn dMax;\n\t\t\tcase EXACT:\n\t\t\t\tBigRational brMax = (BigRational) TypeDouble.getInstance().castValueTo(eval[0], evalMode);\n\t\t\t\tfor (int i = 1; i < n; i++) {\n\t\t\t\t\tbrMax = brMax.max((BigRational) TypeDouble.getInstance().castValueTo(eval[i], evalMode));\n\t\t\t\t}\n\t\t\t\treturn brMax;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (max) function instance to the argument provided.\n\t * The argument is assumed to be the correct kind of Object for its type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyMaxBinary(Object eval1, Object eval2, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// All arguments ints\n\t\tif (getType() instanceof TypeInt) {\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn Math.max((int) eval1, (int) eval2);\n\t\t\tcase EXACT:\n\t\t\t\treturn ((BigInteger) eval1).max((BigInteger) eval2);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t\t// One or more arguments doubles - convert all to doubles\n\t\telse {\n\t\t\tObject eval1D = TypeDouble.getInstance().castValueTo(eval1, evalMode);\n\t\t\tObject eval2D = TypeDouble.getInstance().castValueTo(eval2, evalMode);\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn Math.max((double) eval1D, (double) eval2D);\n\t\t\tcase EXACT:\n\t\t\t\treturn ((BigRational) eval1D).max((BigRational) eval2D);\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (floor) function instance to the argument provided.\n\t * The argument is assumed to be the correct kind of Object for its type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyFloor(Object eval, EvalMode evalMode) throws PrismLangException\n\t{\n\t\ttry {\n\t\t\t// Double argument so may need to cast to double first\n\t\t\tObject evalD = TypeDouble.getInstance().castValueTo(eval, evalMode);\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn SafeCast.toIntExact(Math.floor((double) evalD));\n\t\t\tcase EXACT:\n\t\t\t\treturn ((BigRational) evalD).floor().bigIntegerValue();\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t} catch (ArithmeticException e) {\n\t\t\tthrow new PrismLangException(\"Error evaluating \" + getName() + \":\" + e.getMessage(), this);\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (ceil) function instance to the argument provided.\n\t * The argument is assumed to be the correct kind of Object for its type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyCeil(Object eval, EvalMode evalMode) throws PrismLangException\n\t{\n\t\ttry {\n\t\t\t// Double argument so may need to cast to double first\n\t\t\tObject evalD = TypeDouble.getInstance().castValueTo(eval, evalMode);\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn SafeCast.toIntExact(Math.ceil((double) evalD));\n\t\t\tcase EXACT:\n\t\t\t\treturn ((BigRational) evalD).ceil().bigIntegerValue();\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t} catch (ArithmeticException e) {\n\t\t\tthrow new PrismLangException(\"Error evaluating \" + getName() + \":\" + e.getMessage(), this);\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (round) function instance to the argument provided.\n\t * The argument is assumed to be the correct kind of Object for its type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyRound(Object eval, EvalMode evalMode) throws PrismLangException\n\t{\n\t\ttry {\n\t\t\t// Double argument so may need to cast to double first\n\t\t\tObject evalD = TypeDouble.getInstance().castValueTo(eval, evalMode);\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn SafeCast.toIntExact(Math.round((double) evalD));\n\t\t\tcase EXACT:\n\t\t\t\treturn ((BigRational) evalD).round().bigIntegerValue();\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t} catch (ArithmeticException e) {\n\t\t\tthrow new PrismLangException(\"Error evaluating \" + getName() + \":\" + e.getMessage(), this);\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (pow) function instance to the arguments provided\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyPow(Object eval1, Object eval2, EvalMode evalMode) throws PrismLangException\n\t{\n\t\ttry {\n\t\t\t// The apply code is in a separate static method for re-use elsewhere\n\t\t\treturn applyPow(getType(), eval1, eval2, evalMode);\n\t\t} catch (PrismLangException e) {\n\t\t\tthrow new PrismLangException(e.getMessage(), this);\n\t\t}\n\t}\n\n\t/**\n\t * Apply a (pow) function instance of the specified type to the arguments provided\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tpublic static Object applyPow(Type type, Object eval1, Object eval2, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// All arguments ints\n\t\tif (type instanceof TypeInt) {\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\tint iBase = (int) eval1;\n\t\t\t\tint iExp = (int) eval2;\n\t\t\t\t// Not allowed to do e.g. pow(2,-2) because of typing (should be pow(2.0,-2) instead)\n\t\t\t\tif (iExp < 0)\n\t\t\t\t\tthrow new PrismLangException(\"Negative exponent not allowed for integer power\");\n\t\t\t\ttry {\n\t\t\t\t\treturn SafeCast.toIntExact(Math.pow(iBase, iExp));\n\t\t\t\t} catch (ArithmeticException e) {\n\t\t\t\t\tthrow new PrismLangException(\"Overflow evaluating integer power: \" + e.getMessage());\n\t\t\t\t}\n\t\t\tcase EXACT:\n\t\t\t\tBigInteger biBase = (BigInteger) eval1;\n\t\t\t\tBigInteger biExp = (BigInteger) eval2;\n\t\t\t\t// Not allowed to do e.g. pow(2,-2) because of typing (should be pow(2.0,-2) instead)\n\t\t\t\tif (biExp.compareTo(BigInteger.ZERO) < 0)\n\t\t\t\t\tthrow new PrismLangException(\"Negative exponent not allowed for integer power\");\n\t\t\t\ttry {\n\t\t\t\t\treturn biBase.pow(biExp.intValue());\n\t\t\t\t} catch (ArithmeticException e) {\n\t\t\t\t\tthrow new PrismLangException(\"Cannot compute pow exactly, as there is a problem with the exponent: \" + e.getMessage());\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t\t// One or more arguments doubles - convert all to doubles\n\t\telse {\n\t\t\tObject base = TypeDouble.getInstance().castValueTo(eval1);\n\t\t\tObject exp = TypeDouble.getInstance().castValueTo(eval2);\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\treturn Math.pow((double) base, (double) exp);\n\t\t\tcase EXACT:\n\t\t\t\tif (((BigRational) exp).isInteger()) {\n\t\t\t\t\treturn ((BigRational) base).pow(((BigRational) exp).toInt());\n\t\t\t\t} else {\n\t\t\t\t\tthrow new PrismLangException(\"Cannot compute fractional powers exactly\");\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (mod) function instance to the arguments provided.\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyMod(Object eval1, Object eval2, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// Both arguments are integers\n\t\tswitch (evalMode) {\n\t\tcase FP:\n\t\t\tint i1 = (int) eval1;\n\t\t\tint i2 = (int) eval2;\n\t\t\t// Non-positive divisor not allowed \n\t\t\tif (i2 <= 0) {\n\t\t\t\tthrow new PrismLangException(\"Attempt to compute modulo with non-positive divisor\", this);\n\t\t\t}\n\t\t\t// Take care of negative case (% is remainder, not modulo)\n\t\t\tint rem = i1 % i2;\n\t\t\treturn (rem < 0) ? rem + i2 : rem;\n\t\tcase EXACT:\n\t\t\tBigInteger bi1 = (BigInteger) eval1;\n\t\t\tBigInteger bi2 = (BigInteger) eval2;\n\t\t\t// Non-positive divisor not allowed \n\t\t\tif (bi2.compareTo(BigInteger.ZERO) <= 0) {\n\t\t\t\tthrow new PrismLangException(\"Attempt to compute modulo with non-positive divisor\");\n\t\t\t}\n\t\t\treturn bi1.mod(bi2);\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t}\n\t}\n\n\t/**\n\t * Apply this (log) function instance to the arguments provided.\n\t * The arguments are assumed to be the correct kinds of Objects for their type\n\t * (as returned by {@link Type#castValueTo(Object, EvalMode)}).\n\t */\n\tprivate Object applyLog(Object eval1, Object eval2, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// Double arguments so may need to cast to double first\n\t\tObject x = TypeDouble.getInstance().castValueTo(eval1, evalMode);\n\t\tObject b = TypeDouble.getInstance().castValueTo(eval2, evalMode);\n\t\tswitch (evalMode) {\n\t\tcase FP:\n\t\t\t// Type will be double; so evaluate both operands and cast to doubles\n\t\t\treturn PrismUtils.log((double) x, (double) b);\n\t\tcase EXACT:\n\t\t\tthrow new PrismLangException(\"Currently, cannot compute log exactly\", this);\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\tint i, n;\n\t\t// Otherwise, true iff all operands true\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (!getOperand(i).returnsSingleValue())\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionFunc deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(operands);\n\n\t\treturn this;\n\t}\n\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic ExpressionFunc clone()\n\t{\n\t\tExpressionFunc clone = (ExpressionFunc) super.clone();\n\n\t\tclone.operands = (ArrayList<Expression>) operands.clone();\n\n\t\treturn clone;\n\t}\n\t\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tString s = \"\";\n\t\tboolean first = true;\n\n\t\tif (!oldStyle)\n\t\t\ts += name + \"(\";\n\t\telse\n\t\t\ts += \"func(\" + name + \", \";\n\t\tn = operands.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (!first)\n\t\t\t\ts += \", \";\n\t\t\telse\n\t\t\t\tfirst = false;\n\t\t\ts = s + getOperand(i);\n\t\t}\n\t\ts += \")\";\n\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + code;\n\t\tresult = prime * result + ((name == null) ? 0 : name.hashCode());\n\t\tresult = prime * result + (oldStyle ? 1231 : 1237);\n\t\tresult = prime * result + ((operands == null) ? 0 : operands.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionFunc other = (ExpressionFunc) obj;\n\t\tif (code != other.code)\n\t\t\treturn false;\n\t\tif (name == null) {\n\t\t\tif (other.name != null)\n\t\t\t\treturn false;\n\t\t} else if (!name.equals(other.name))\n\t\t\treturn false;\n\t\tif (oldStyle != other.oldStyle)\n\t\t\treturn false;\n\t\tif (operands == null) {\n\t\t\tif (other.operands != null)\n\t\t\t\treturn false;\n\t\t} else if (!operands.equals(other.operands))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionITE.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.EvaluateContext.EvalMode;\nimport parser.type.TypeBool;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionITE extends Expression\n{\n\t// Operands\n\tprotected Expression operand1 = null; // condition\n\tprotected Expression operand2 = null; // then\n\tprotected Expression operand3 = null; // else\n\n\t// Constructor\n\n\tpublic ExpressionITE(Expression c, Expression t, Expression e)\n\t{\n\t\toperand1 = c;\n\t\toperand2 = t;\n\t\toperand3 = e;\n\t}\n\n\t// Set methods\n\n\tpublic void setOperand1(Expression e)\n\t{\n\t\toperand1 = e;\n\t}\n\n\tpublic void setOperand2(Expression e)\n\t{\n\t\toperand2 = e;\n\t}\n\n\tpublic void setOperand3(Expression e)\n\t{\n\t\toperand3 = e;\n\t}\n\n\t// Get methods\n\n\tpublic Expression getOperand1()\n\t{\n\t\treturn operand1;\n\t}\n\n\tpublic Expression getOperand2()\n\t{\n\t\treturn operand2;\n\t}\n\n\tpublic Expression getOperand3()\n\t{\n\t\treturn operand3;\n\t}\n\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn operand1.isConstant() && operand2.isConstant() && operand3.isConstant();\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn operand1.isProposition() && operand2.isProposition() && operand3.isProposition();\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\t// Note that we don't use apply(...) because we want short-circuiting\n\t\tObject eval1 = operand1.evaluate(ec);\n\t\tboolean b = TypeBool.getInstance().castValueTo(eval1);\n\t\treturn getType().castValueTo(b ? operand2.evaluate(ec) : operand3.evaluate(ec), ec.getEvaluationMode());\n\t}\n\n\t/**\n\t * Apply this ITE operator instance to the arguments provided\n\t */\n\tpublic Object apply(Object eval1, Object eval2, Object eval3, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tboolean b = TypeBool.getInstance().castValueTo(eval1);\n\t\treturn getType().castValueTo(b ? eval2 : eval3, evalMode);\n\t}\n\t\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn operand1.returnsSingleValue() && operand2.returnsSingleValue() && operand3.returnsSingleValue();\n\t}\n\n\t@Override\n\tpublic Precedence getPrecedence()\n\t{\n\t\treturn Precedence.ITE;\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionITE deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand1 = copier.copy(operand1);\n\t\toperand2 = copier.copy(operand2);\n\t\toperand3 = copier.copy(operand3);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionITE clone()\n\t{\n\t\treturn (ExpressionITE) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\t\t// ? is a (right-associative) non-commutative operator\n\t\tbuilder.append(Expression.toStringPrecLeq(operand1, this));\n\t\tbuilder.append(\"?\");\n\t\tbuilder.append(Expression.toStringPrecLeq(operand2, this));\n\t\tbuilder.append(\":\");\n\t\tbuilder.append(Expression.toStringPrecLt(operand3, this));\n\t\treturn builder.toString();\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((operand1 == null) ? 0 : operand1.hashCode());\n\t\tresult = prime * result + ((operand2 == null) ? 0 : operand2.hashCode());\n\t\tresult = prime * result + ((operand3 == null) ? 0 : operand3.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionITE other = (ExpressionITE) obj;\n\t\tif (operand1 == null) {\n\t\t\tif (other.operand1 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand1.equals(other.operand1))\n\t\t\treturn false;\n\t\tif (operand2 == null) {\n\t\t\tif (other.operand2 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand2.equals(other.operand2))\n\t\t\treturn false;\n\t\tif (operand3 == null) {\n\t\t\tif (other.operand3 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand3.equals(other.operand3))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionIdent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionIdent extends Expression\n{\n\tprotected String name;\n\t\n\t// Constructors\n\t\n\tpublic ExpressionIdent()\n\t{\n\t}\n\t\n\tpublic ExpressionIdent(String n)\n\t{\n\t\tname = n;\n\t}\n\t\n\t// Set method\n\t\n\tpublic void setName(String n)\n\t{\n\t\tname = n;\n\t}\n\t\n\t// Get method\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\t// Don't know - err on the side of caution\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\t// Don't know - err on the side of caution\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\t// This should never be called.\n\t\t// The ExpressionIdent should have been converted to an ExpressionVar/ExpressionConstant/...\n\t\tthrow new PrismLangException(\"Could not evaluate identifier\", this);\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\t// Don't know - err on the side of caution\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic ExpressionIdent deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionIdent clone()\n\t{\n\t\treturn (ExpressionIdent) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn name;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((name == null) ? 0 : name.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionIdent other = (ExpressionIdent) obj;\n\t\tif (name == null) {\n\t\t\tif (other.name != null)\n\t\t\t\treturn false;\n\t\t} else if (!name.equals(other.name))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n\t\n\t// Static utility methods\n\t\n\tpublic static boolean isLegalIdentifierName(String name)\n\t{\n\t\treturn name.matches(\"[_a-zA-z][_a-zA-z0-9]*\");\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionInterval.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport common.Interval;\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionInterval extends Expression\n{\n\t// Pair of operands\n\tprotected Expression operand1 = null;\n\tprotected Expression operand2 = null;\n\n\t// Constructors\n\n\tpublic ExpressionInterval(Expression operand1, Expression operand2)\n\t{\n\t\tthis.operand1 = operand1;\n\t\tthis.operand2 = operand2;\n\t}\n\n\t// Set methods\n\n\tpublic void setOperand1(Expression e1)\n\t{\n\t\toperand1 = e1;\n\t}\n\n\tpublic void setOperand2(Expression e2)\n\t{\n\t\toperand2 = e2;\n\t}\n\n\t// Get methods\n\n\tpublic Expression getOperand1()\n\t{\n\t\treturn operand1;\n\t}\n\n\tpublic Expression getOperand2()\n\t{\n\t\treturn operand2;\n\t}\n\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn operand1.isConstant() && operand2.isConstant();\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn operand1.isProposition() && operand2.isProposition();\n\t}\n\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tdouble lo = operand1.evaluateDouble(ec);\n\t\tdouble hi = operand2.evaluateDouble(ec);\n\t\tif (lo > hi) {\n\t\t\tthrow new PrismLangException(\"Invalid interval bounds \" + lo + \",\" + hi, this);\n\t\t}\n\t\treturn new Interval<Double>(lo, hi);\n\t}\n\t\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn operand1.returnsSingleValue() && operand2.returnsSingleValue();\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionInterval deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand1 = copier.copy(operand1);\n\t\toperand2 = copier.copy(operand2);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionInterval clone()\n\t{\n\t\treturn (ExpressionInterval) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + operand1 + \",\" + operand2 + \"]\";\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((operand1 == null) ? 0 : operand1.hashCode());\n\t\tresult = prime * result + ((operand2 == null) ? 0 : operand2.hashCode());\n\t\treturn result;\n\t}\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionBinaryOp other = (ExpressionBinaryOp) obj;\n\t\tif (operand1 == null) {\n\t\t\tif (other.operand1 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand1.equals(other.operand1))\n\t\t\treturn false;\n\t\tif (operand2 == null) {\n\t\t\tif (other.operand2 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand2.equals(other.operand2))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionLabel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionLabel extends Expression\n{\n\tString name;\n\n\t// Constructor\n\t\n\tpublic ExpressionLabel(String s)\n\t{\n\t\tname = s;\n\t}\n\n\t// Get Method\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\n\t/**\n\t * Is this the special \"init\" label?\n\t */\n\tpublic boolean isInitLabel()\n\t{\n\t\treturn getName().equals(\"init\");\n\t}\n\n\t/**\n\t * Is this the special \"deadlock\" label?\n\t */\n\tpublic boolean isDeadlockLabel()\n\t{\n\t\treturn getName().equals(\"deadlock\");\n\t}\n\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\t// Don't know - err on the side of caution\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate labels\", this);\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic ExpressionLabel deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionLabel clone()\n\t{\n\t\treturn (ExpressionLabel) super.clone();\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"\\\"\" + name + \"\\\"\";\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((name == null) ? 0 : name.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionLabel other = (ExpressionLabel) obj;\n\t\tif (name == null) {\n\t\t\tif (other.name != null)\n\t\t\t\treturn false;\n\t\t} else if (!name.equals(other.name))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionLiteral.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.math.BigInteger;\n\nimport param.BigRational;\nimport parser.EvaluateContext;\nimport parser.EvaluateContext.EvalMode;\nimport parser.type.Type;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\npublic class ExpressionLiteral extends Expression\n{\n\tObject value; // Value\n\tString string; // Optionally, keep original string to preserve user formatting and allow exact evaluation\n\n\t// Constructor\n\t\n\tpublic ExpressionLiteral(Type type, Object value)\n\t{\n\t\tthis(type, value, \"\"+value);\n\t}\n\n\tpublic ExpressionLiteral(Type type, Object value, String string)\n\t{\n\t\tthis.type = type;\n\t\tthis.value = value;\n\t\tthis.string = string;\n\t}\n\n\t// Set Methods\n\t\n\tpublic void setValue(Object value)\n\t{\n\t\tthis.value = value;\n\t\tthis.string = \"\"+value;\n\t}\n\n\tpublic void setString(String string)\n\t{\n\t\tthis.string = string;\n\t}\n\n\t// Get Methods\n\t\n\tpublic Object getValue()\n\t{\n\t\treturn value;\n\t}\n\n\tpublic String getString()\n\t{\n\t\treturn string;\n\t}\n\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\t// For exact mode and numerical types, the value may have been\n\t\t// stored non-exactly, so we regenerate it from the string\n\t\tif (ec.getEvaluationMode() == EvalMode.EXACT) {\n\t\t\tif (type instanceof TypeDouble) {\n\t\t\t\tif (value instanceof BigRational) {\n\t\t\t\t\treturn value;\n\t\t\t\t} else {\n\t\t\t\t\treturn new BigRational(string);\n\t\t\t\t}\n\t\t\t} else if (type instanceof TypeInt) {\n\t\t\t\tif (value instanceof BigInteger) {\n\t\t\t\t\treturn value;\n\t\t\t\t} else {\n\t\t\t\t\treturn new BigInteger(string);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Otherwise, cast to the right Object for type/mode\n\t\treturn getType().castValueTo(value, ec.getEvaluationMode());\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn true;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionLiteral deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionLiteral clone()\n\t{\n\t\treturn (ExpressionLiteral) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn string;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((string == null) ? 0 : string.hashCode());\n\t\tresult = prime * result + ((value == null) ? 0 : value.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionLiteral other = (ExpressionLiteral) obj;\n\t\tif (string == null) {\n\t\t\tif (other.string != null)\n\t\t\t\treturn false;\n\t\t} else if (!string.equals(other.string))\n\t\t\treturn false;\n\t\tif (value == null) {\n\t\t\tif (other.value != null)\n\t\t\t\treturn false;\n\t\t} else if (!value.equals(other.value))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionObs.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n/*\n * A reference to an observable.\n */\npublic class ExpressionObs extends Expression\n{\n\t// Observable name\n\tprivate String name;\n\t// The index of the observable in the model to which it belongs\n\tprivate int index;\n\t\n\t// Constructors\n\t\n\tpublic ExpressionObs(String name)\n\t{\n\t\tthis.name = name;\n\t\tindex = -1;\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void setName(String name)\n\t{\n\t\tthis.name = name;\n\t}\n\t\n\tpublic void setIndex(int i)\n\t{\n\t\tindex = i;\n\t}\n\t\n\t// Get methods\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\tpublic int getIndex()\n\t{\n\t\treturn index;\n\t}\n\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\t// Extract observable value from the evaluation context\n\t\tObject res = ec.getObservableValue(name, index);\n\t\tif (res == null) {\n\t\t\tthrow new PrismLangException(\"Could not evaluate observable\", this);\n\t\t}\n\t\t// And cast it to the right type/mode if needed\n\t\treturn getType().castValueTo(res, ec.getEvaluationMode());\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionObs deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionObs clone()\n\t{\n\t\treturn (ExpressionObs) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"\\\"\" + name + \"\\\"\";\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + index;\n\t\tresult = prime * result + ((name == null) ? 0 : name.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionObs other = (ExpressionObs) obj;\n\t\tif (index != other.index)\n\t\t\treturn false;\n\t\tif (name == null) {\n\t\t\tif (other.name != null)\n\t\t\t\treturn false;\n\t\t} else if (!name.equals(other.name))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionProb.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.Values;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.OpRelOpBound;\nimport prism.PrismLangException;\n\npublic class ExpressionProb extends ExpressionQuant\n{\n\t// Constructors\n\n\tpublic ExpressionProb()\n\t{\n\t}\n\n\tpublic ExpressionProb(Expression expression, String relOpString, Expression p)\n\t{\n\t\tsetExpression(expression);\n\t\tsetRelOp(relOpString);\n\t\tsetBound(p);\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Set the probability bound. Equivalent to {@code setBound(p)}.\n\t */\n\tpublic void setProb(Expression p)\n\t{\n\t\tsetBound(p);\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the probability bound. Equivalent to {@code getBound()}.\n\t */\n\tpublic Expression getProb()\n\t{\n\t\treturn getBound();\n\t}\n\n\t/**\n\t * Get a string describing the type of P operator, e.g. \"P=?\" or \"P&lt;p\".\n\t */\n\tpublic String getTypeOfPOperator()\n\t{\n\t\tString s = \"\";\n\t\ts += \"P\" + getRelOp();\n\t\ts += (getBound() == null) ? \"?\" : \"p\";\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic OpRelOpBound getRelopBoundInfo(Values constantValues) throws PrismLangException\n\t{\n\t\tif (getBound() != null) {\n\t\t\tdouble boundVal = getBound().evaluateDouble(constantValues);\n\t\t\tif (boundVal < 0 || boundVal > 1)\n\t\t\t\tthrow new PrismLangException(\"Invalid probability bound \" + boundVal + \" in P operator\");\n\t\t\treturn new OpRelOpBound(\"P\", getRelOp(), boundVal);\n\t\t} else {\n\t\t\treturn new OpRelOpBound(\"P\", getRelOp(), null);\n\t\t}\n\t}\n\t\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate a P operator without a model\");\n\t}\n\n\t@Override\n\tpublic String getResultName()\n\t{\n\t\tif (getBound() != null)\n\t\t\treturn \"Result\";\n\t\telse if (getRelOp() == RelOp.MIN)\n\t\t\treturn \"Minimum probability\";\n\t\telse if (getRelOp() == RelOp.MAX)\n\t\t\treturn \"Maximum probability\";\n\t\telse\n\t\t\treturn \"Probability\";\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionProb deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tsuper.deepCopy(copier);\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionProb clone()\n\t{\n\t\treturn (ExpressionProb) super.clone();\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\n\t\ts += \"P\" + getModifierString() + getRelOp();\n\t\ts += (getBound() == null) ? \"?\" : getBound().toString();\n\t\ts += \" [ \" + getExpression();\n\t\tif (getFilter() != null)\n\t\t\ts += \" \" + getFilter();\n\t\ts += \" ]\";\n\n\t\treturn s;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionProp.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n/**\n * An expression \"prop\", representing a reference to another property.\n */\npublic class ExpressionProp extends Expression\n{\n\tprivate String name;\n\n\t// Constructor\n\t\n\tpublic ExpressionProp(String s)\n\t{\n\t\tname = s;\n\t}\n\n\t// Get Method\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\t// Don't know - err on the side of caution\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\t// Don't know - err on the side of caution\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate property references\", this);\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionProp deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionProp clone()\n\t{\n\t\treturn (ExpressionProp) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"\\\"\" + name + \"\\\"\";\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((name == null) ? 0 : name.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionProp other = (ExpressionProp) obj;\n\t\tif (name == null) {\n\t\t\tif (other.name != null)\n\t\t\t\treturn false;\n\t\t} else if (!name.equals(other.name))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionQuant.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.Values;\nimport parser.visitor.DeepCopy;\nimport prism.OpRelOpBound;\nimport prism.PrismException;\nimport prism.PrismLangException;\n\n/**\n * Abstract class for representing \"quantitative\" operators (P,R,S),\n * i.e., a superclass of ExpressionProb, ExpressionReward, ExpressionSS.\n */\npublic abstract class ExpressionQuant extends Expression\n{\n\t/** Optional \"modifier\" to specify variants of the P/R/S operator */\n\tprotected String modifier = null;\n\t/** The attached relational operator (e.g. \"&lt;\" in \"P&lt;0.1\"). */\n\tprotected RelOp relOp = null;\n\t/** The attached (probability/reward) bound, as an expression (e.g. \"p\" in \"P&lt;p\"). Null if absent (e.g. \"P=?\"). */\n\tprotected Expression bound = null;\n\t/** The main operand of the operator (e.g. \"F target=true\" in \"P&lt;0.1[F target=true]. */\n\tprotected Expression expression = null;\n\t/** Optional \"old-style\" filter. This is just for display purposes since\n\t  *  the parser creates an (invisible) new-style filter around this expression. */\n\tprotected Filter filter = null;\n\n\t// Set methods\n\n\t/**\n\t * Set the (optional) \"modifier\" for this operator.\n\t */\n\tpublic void setModifier(String modifier)\n\t{\n\t\tthis.modifier = modifier;\n\t}\n\n\t/**\n\t * Set the attached relational operator (e.g. \"&lt;\" in \"P&lt;0.1\").\n\t * Uses the enum {@link RelOp}. For example: {@code setRelOp(RelOp.GT);}\n\t */\n\tpublic void setRelOp(RelOp relOp)\n\t{\n\t\tthis.relOp = relOp;\n\t}\n\n\t/**\n\t * Set the attached relational operator (e.g. \"&lt;\" in \"P&lt;0.1\").\n\t * The operator is passed as a string, e.g. \"&lt;\" or \"&gt;=\".\n\t */\n\tpublic void setRelOp(String relOpString)\n\t{\n\t\trelOp = RelOp.parseSymbol(relOpString);\n\t}\n\n\t/**\n\t * Set the attached bound, as an expression (e.g. \"p\" in \"P&lt;p\"). Should be null if absent (e.g. \"P=?\").\n\t */\n\tpublic void setBound(Expression bound)\n\t{\n\t\tthis.bound = bound;\n\t}\n\n\t/**\n\t * Set the main operand of the operator (e.g. \"F target=true\" in \"P&lt;0.1[F target=true].\n\t */\n\tpublic void setExpression(Expression expression)\n\t{\n\t\tthis.expression = expression;\n\t}\n\n\t/**\n\t * Set the optional \"old-style\" filter. This is just for display purposes since\n\t * the parser creates an (invisible) new-style filter around this expression.\n\t */\n\tpublic void setFilter(Filter f)\n\t{\n\t\tfilter = f;\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the (optional) \"modifier\" for this operator.\n\t */\n\tpublic String getModifier()\n\t{\n\t\treturn modifier;\n\t}\n\n\t/**\n\t * Get a string representing the modifier as a suffix for the operator.\n\t */\n\tpublic String getModifierString()\n\t{\n\t\treturn modifier == null ? \"\" : \"(\" + modifier + \")\";\n\t}\n\n\t/**\n\t * Get the attached relational operator (e.g. \"&lt;\" in \"P&lt;0.1\"), as a {@link RelOp}.\n\t */\n\tpublic RelOp getRelOp()\n\t{\n\t\treturn relOp;\n\t}\n\n\t/**\n\t * Get the attached bound, as an expression (e.g. \"p\" in \"P&lt;p\"). Should be null if absent (e.g. \"P=?\").\n\t */\n\tpublic Expression getBound()\n\t{\n\t\treturn bound;\n\t}\n\n\t/**\n\t * Get the main operand of the operator (e.g. \"F target=true\" in \"P&lt;0.1[F target=true].\n\t */\n\tpublic Expression getExpression()\n\t{\n\t\treturn expression;\n\t}\n\n\t/**\n\t * Get an object storing info about the attached relational operator and bound, after evaluating the bound to a double.\n\t * For example \"&lt;0.1\" in \"P&lt;p\" where p=0.5 in {@code constantValues}.\n\t * Does some checks, e.g., throws an exception if a probability is not in the range [0,1]\n\t * \n\t * @param constantValues Values for constants in order to evaluate any bound\n\t */\n\tpublic abstract OpRelOpBound getRelopBoundInfo(Values constantValues) throws PrismException;\n\n\t/**\n\t * Get the optional \"old-style\" filter. This is just for display purposes since\n\t * the parser creates an (invisible) new-style filter around this expression.\n\t */\n\tpublic Filter getFilter()\n\t{\n\t\treturn filter;\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic ExpressionQuant clone()\n\t{\n\t\treturn (ExpressionQuant) super.clone();\n\t}\n\t\n\t@Override\n\tpublic ExpressionQuant deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tbound = copier.copy(bound);\n\t\tfilter = copier.copy(filter);\n\t\texpression = copier.copy(expression);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((bound == null) ? 0 : bound.hashCode());\n\t\tresult = prime * result + ((expression == null) ? 0 : expression.hashCode());\n\t\tresult = prime * result + ((filter == null) ? 0 : filter.hashCode());\n\t\tresult = prime * result + ((modifier == null) ? 0 : modifier.hashCode());\n\t\tresult = prime * result + ((relOp == null) ? 0 : relOp.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionQuant other = (ExpressionQuant) obj;\n\t\tif (bound == null) {\n\t\t\tif (other.bound != null)\n\t\t\t\treturn false;\n\t\t} else if (!bound.equals(other.bound))\n\t\t\treturn false;\n\t\tif (expression == null) {\n\t\t\tif (other.expression != null)\n\t\t\t\treturn false;\n\t\t} else if (!expression.equals(other.expression))\n\t\t\treturn false;\n\t\tif (filter == null) {\n\t\t\tif (other.filter != null)\n\t\t\t\treturn false;\n\t\t} else if (!filter.equals(other.filter))\n\t\t\treturn false;\n\t\tif (modifier == null) {\n\t\t\tif (other.modifier != null)\n\t\t\t\treturn false;\n\t\t} else if (!modifier.equals(other.modifier))\n\t\t\treturn false;\n\t\tif (relOp != other.relOp)\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionReward.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.Values;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.OpRelOpBound;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.RewardGenerator;\n\nimport java.util.List;\n\npublic class ExpressionReward extends ExpressionQuant\n{\n\tprotected Object rewardStructIndex = null;\n\tprotected Object rewardStructIndexDiv = null;\n\t\n\t// Constructors\n\t\n\tpublic ExpressionReward()\n\t{\n\t}\n\t\n\tpublic ExpressionReward(Expression expression, String relOpString, Expression r)\n\t{\n\t\tsetExpression(expression);\n\t\tsetRelOp(relOpString);\n\t\tsetBound(r);\n\t}\n\n\t// Set methods\n\t\n\tpublic void setRewardStructIndex(Object o)\n\t{\n\t\trewardStructIndex = o;\n\t}\n\n\tpublic void setRewardStructIndexDiv(Object o)\n\t{\n\t\trewardStructIndexDiv = o;\n\t}\n\n\t/**\n\t * Set the reward bound. Equivalent to {@code setBound(r)}.\n\t */\n\tpublic void setReward(Expression r)\n\t{\n\t\tsetBound(r);\n\t}\n\n\t// Get methods\n\t\n\tpublic Object getRewardStructIndex()\n\t{\n\t\treturn rewardStructIndex;\n\t}\n\n\tpublic Object getRewardStructIndexDiv()\n\t{\n\t\treturn rewardStructIndexDiv;\n\t}\n\n\t/**\n\t * Get the reward bound. Equivalent to {@code getBound()}.\n\t */\n\tpublic Expression getReward()\n\t{\n\t\treturn getBound();\n\t}\n\n\t// Other methods\n\t\n\t/**\n\t * Get a string describing the type of R operator, e.g. \"R=?\" or \"R&lt;r\".\n\t */\n\tpublic String getTypeOfROperator()\n\t{\n\t\tString s = \"\";\n\t\ts += \"R\" + getRelOp();\n\t\ts += (getBound() == null) ? \"?\" : \"r\";\n\t\treturn s;\n\t}\n\n\t/**\n\t * Get the index of a reward structure (within a model) corresponding to the index of this R operator.\n\t * This is 0-indexed (as used e.g. in ModulesFile), not 1-indexed (as seen by user)\n\t * Throws an exception (with explanatory message) if it cannot be found.\n\t * This means that, the method always returns a valid index if it finishes.\n\t * @param rewardGen RewardGenerator object to be used for looking up reward struct names\n\t * @param constantValues Values of constants which may be needed to evaluate the index\n\t */\n\tpublic int getRewardStructIndexByIndexObject(RewardGenerator rewardGen, Values constantValues) throws PrismException\n\t{\n\t\treturn getRewardStructIndexByIndexObject(rewardStructIndex, rewardGen, constantValues);\n\t}\n\n\t/**\n\t * Get the index of a reward structure (within a model) corresponding to the index of this R operator.\n\t * This is 0-indexed (as used e.g. in ModulesFile), not 1-indexed (as seen by user)\n\t * Throws an exception (with explanatory message) if it cannot be found.\n\t * This means that, the method always returns a valid index if it finishes.\n\t * @param rewardStructNames List of reward struct names\n\t * @param constantValues Values of constants which may be needed to evaluate the index\n\t */\n\tpublic int getRewardStructIndexByIndexObject(List<String> rewardStructNames, Values constantValues) throws PrismException\n\t{\n\t\treturn getRewardStructIndexByIndexObject(rewardStructIndex, rewardStructNames, constantValues);\n\t}\n\n\t/**\n\t * Get the index of a reward structure (within a model) corresponding to the rsi reward structure index object.\n\t * This is 0-indexed (as used e.g. in ModulesFile), not 1-indexed (as seen by user)\n\t * Throws an exception (with explanatory message) if it cannot be found.\n\t * This means that, the method always returns a valid index if it finishes.\n\t * @param rsi The reward structure index: Expression (evaluating to index, starting from 1) or String (name)\n\t * @param rewardGen RewardGenerator object to be used for looking up reward struct names\n\t * @param constantValues Values of constants which may be needed to evaluate the index\n\t */\n\tpublic static int getRewardStructIndexByIndexObject(Object rsi, RewardGenerator rewardGen, Values constantValues) throws PrismException\n\t{\n\t\tif (rewardGen == null) {\n\t\t\tthrow new PrismException(\"No reward info to obtain reward structures\");\n\t\t}\n\t\treturn getRewardStructIndexByIndexObject(rsi, rewardGen.getRewardStructNames(), constantValues);\n\t}\n\n\t/**\n\t * Get the index of a reward structure (within a model) corresponding to the rsi reward structure index object.\n\t * This is 0-indexed (as used e.g. in ModulesFile), not 1-indexed (as seen by user)\n\t * Throws an exception (with explanatory message) if it cannot be found.\n\t * This means that, the method always returns a valid index if it finishes.\n\t * @param rsi The reward structure index: Expression (evaluating to index, starting from 1) or String (name)\n\t * @param rewardStructNames List of reward struct names\n\t * @param constantValues Values of constants which may be needed to evaluate the index\n\t */\n\tpublic static int getRewardStructIndexByIndexObject(Object rsi, List<String> rewardStructNames, Values constantValues) throws PrismException\n\t{\n\t\tif (rewardStructNames.size() == 0) {\n\t\t\tthrow new PrismException(\"Model has no rewards specified\");\n\t\t}\n\t\t// Recall: the index is an Object which is either an Integer, denoting the index (starting from 0) directly,\n\t\t// or an expression, which can be evaluated (possibly using the passed in constants) to an index. \n\t\tint rewStruct = -1;\n\t\t// No index specified - use the first one\n\t\tif (rsi == null) {\n\t\t\trewStruct = 0;\n\t\t}\n\t\t// Expression - evaluate to an index\n\t\telse if (rsi instanceof Expression) {\n\t\t\tint i = ((Expression) rsi).evaluateInt(constantValues);\n\t\t\trsi = i; // (for better error reporting below)\n\t\t\t// Check in range (set to -1 if not) and convert to zero-indexed\n\t\t\trewStruct = (i < 1 || i > rewardStructNames.size()) ? -1 : i - 1;\n\t\t}\n\t\t// String - name of reward structure\n\t\telse if (rsi instanceof String) {\n\t\t\trewStruct = rewardStructNames.indexOf((String) rsi);\n\t\t}\n\t\tif (rewStruct == -1) {\n\t\t\tthrow new PrismException(\"Invalid reward structure index \\\"\" + rsi + \"\\\"\");\n\t\t}\n\t\treturn rewStruct;\n\t}\n\n\t/**\n\t * Get info about the operator and bound.\n\t * @param constantValues Values for constants in order to evaluate any bound\n\t */\n\tpublic OpRelOpBound getRelopBoundInfo(Values constantValues) throws PrismException\n\t{\n\t\tif (getBound() != null) {\n\t\t\tdouble boundValue = getBound().evaluateDouble(constantValues);\n\t\t\treturn new OpRelOpBound(\"R\", getRelOp(), boundValue);\n\t\t} else {\n\t\t\treturn new OpRelOpBound(\"R\", getRelOp(), null);\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns true is this is a minimum rewards operator.\n\t * Actually, this returns true if the operator has \"min=?\" or a lower bound attached to it,\n\t * so this is just an approximation. (For example, this R operator might be embedded within\n\t * an \"exists\" strategy operator)\n\t */\n\tpublic boolean isMin()\n\t{\n\t\treturn getRelOp().isMin() || getRelOp().isLowerBound();\n\t}\n\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate an R operator without a model\");\n\t}\n\n\t@Override\n\tpublic String getResultName()\n\t{\n\t\t// For R=? properties, use name of reward structure where applicable\n\t\tif (getBound() == null) {\n\t\t\tString s = \"E\";\n\t\t\tif (getRelOp() == RelOp.MIN) s = \"Minimum e\";\n\t\t\telse if (getRelOp() == RelOp.MAX) s = \"Maximum e\";\n\t\t\telse s = \"E\";\n\t\t\tif (rewardStructIndex instanceof String) {\n\t\t\t\tif (rewardStructIndexDiv instanceof String)\n\t\t\t\t\ts += \"xpected \"+rewardStructIndex + \"/\" + rewardStructIndexDiv;\n\t\t\t\telse if (rewardStructIndexDiv == null)\n\t\t\t\t\ts += \"xpected \"+rewardStructIndex;\n\t\t\t\telse\n\t\t\t\t\ts += \"xpected reward\";\n\t\t\t}\n\t\t\t// Or just call it \"Expected reward\"\n\t\t\telse s += \"xpected reward\";\n\t\t\treturn s;\n\t\t}\n\t\t// For R>r etc., just use \"Result\"\n\t\telse {\n\t\t\treturn \"Result\";\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionReward deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tsuper.deepCopy(copier);\n\n\t\tif (rewardStructIndex != null && rewardStructIndex instanceof Expression) {\n\t\t\trewardStructIndex = copier.copy((Expression) rewardStructIndex);\n\t\t}\n\t\tif (rewardStructIndexDiv != null && rewardStructIndexDiv instanceof Expression) {\n\t\t\trewardStructIndexDiv = copier.copy((Expression) rewardStructIndexDiv);\n\t\t}\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionReward clone()\n\t{\n\t\treturn (ExpressionReward) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\t\n\t\ts += \"R\" + getModifierString();\n\t\tif (rewardStructIndex != null) {\n\t\t\tif (rewardStructIndex instanceof Expression) s += \"{\"+rewardStructIndex+\"}\";\n\t\t\telse if (rewardStructIndex instanceof String) s += \"{\\\"\"+rewardStructIndex+\"\\\"}\";\n\t\t\tif (rewardStructIndexDiv != null) {\n\t\t\t\ts += \"/\";\n\t\t\t\tif (rewardStructIndexDiv instanceof Expression) s += \"{\"+rewardStructIndexDiv+\"}\";\n\t\t\t\telse if (rewardStructIndexDiv instanceof String) s += \"{\\\"\"+rewardStructIndexDiv+\"\\\"}\";\n\t\t\t}\n\t\t}\n\t\ts += getRelOp();\n\t\ts += (getBound()==null) ? \"?\" : getBound().toString();\n\t\ts += \" [ \" + getExpression();\n\t\tif (getFilter() != null) s += \" \"+getFilter();\n\t\ts += \" ]\";\n\t\t\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = super.hashCode();\n\t\tresult = prime * result + ((rewardStructIndex == null) ? 0 : rewardStructIndex.hashCode());\n\t\tresult = prime * result + ((rewardStructIndexDiv == null) ? 0 : rewardStructIndexDiv.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (!super.equals(obj))\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionReward other = (ExpressionReward) obj;\n\t\tif (rewardStructIndex == null) {\n\t\t\tif (other.rewardStructIndex != null)\n\t\t\t\treturn false;\n\t\t} else if (!rewardStructIndex.equals(other.rewardStructIndex))\n\t\t\treturn false;\n\t\tif (rewardStructIndexDiv == null) {\n\t\t\tif (other.rewardStructIndexDiv != null)\n\t\t\t\treturn false;\n\t\t} else if (!rewardStructIndexDiv.equals(other.rewardStructIndexDiv))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionSS.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.Values;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.OpRelOpBound;\nimport prism.PrismException;\nimport prism.PrismLangException;\n\npublic class ExpressionSS extends ExpressionQuant\n{\n\t// Constructors\n\t\n\tpublic ExpressionSS()\n\t{\n\t}\n\t\n\tpublic ExpressionSS(Expression expression, String relOpString, Expression p)\n\t{\n\t\tsetExpression(expression);\n\t\tsetRelOp(relOpString);\n\t\tsetBound(p);\n\t}\n\n\t// Set methods\n\t\n\t/**\n\t * Set the probability bound. Equivalent to {@code setBound(p)}.\n\t */\n\tpublic void setProb(Expression p)\n\t{\n\t\tsetBound(p);\n\t}\n\n\t// Get methods\n\t\n\t/**\n\t * Get the probability bound. Equivalent to {@code getBound()}.\n\t */\n\tpublic Expression getProb()\n\t{\n\t\treturn getBound();\n\t}\n\n\t/**\n\t * Get info about the operator and bound.\n\t * Does some checks, e.g., throws an exception if probability is out of range.\n\t * @param constantValues Values for constants in order to evaluate any bound\n\t */\n\tpublic OpRelOpBound getRelopBoundInfo(Values constantValues) throws PrismException\n\t{\n\t\tif (getBound() != null) {\n\t\t\tdouble boundValue = getBound().evaluateDouble(constantValues);\n\t\t\tif (boundValue < 0 || boundValue > 1)\n\t\t\t\tthrow new PrismException(\"Invalid probability bound \" + boundValue + \" in P operator\");\n\t\t\treturn new OpRelOpBound(\"S\", getRelOp(), boundValue);\n\t\t} else {\n\t\t\treturn new OpRelOpBound(\"S\", getRelOp(), null);\n\t\t}\n\t}\n\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate an S operator without a model\");\n\t}\n\n\t@Override\n\tpublic String getResultName()\n\t{\n\t\treturn (getBound() == null) ? \"Probability\" : \"Result\";\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionSS deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\treturn (ExpressionSS) super.deepCopy(copier);\n\t}\n\n\t@Override\n\tpublic ExpressionSS clone()\n\t{\n\t\treturn (ExpressionSS) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\t\n\t\ts += \"S\" + getModifierString() + getRelOp();\n\t\ts += (getBound()==null) ? \"?\" : getBound().toString();\n\t\ts += \" [ \" + getExpression();\n\t\tif (getFilter() != null) s += \" \"+getFilter();\n\t\ts += \" ]\";\n\t\t\n\t\treturn s;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionStrategy.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n/**\n * Class to represent ATL &lt;&lt;.&gt;&gt; and [[.]] operators, i.e. quantification over strategies\n * (\"there exists a strategy\" or \"for all strategies\").\n */\npublic class ExpressionStrategy extends Expression\n{\n\t/** \"There exists a strategy\" (true) or \"for all strategies\" (false) */\n\tprotected boolean thereExists = false;\n\t\n\t/** Coalition info (for game models) */\n\tprotected Coalition coalition = new Coalition(); \n\t\n\t/** Child expression(s) */\n\tprotected ArrayList<Expression> operands = new ArrayList<Expression>();\n\t\n\t/** Is there just a single operand (P/R operator)? If not, the operand list will be parenthesised. **/\n\tprotected boolean singleOperand = false;\n\t\n\t// Constructors\n\n\tpublic ExpressionStrategy()\n\t{\n\t}\n\n\tpublic ExpressionStrategy(boolean thereExists)\n\t{\n\t\tthis.thereExists = thereExists;\n\t}\n\n\tpublic ExpressionStrategy(boolean thereExists, Expression expression)\n\t{\n\t\tthis.thereExists = thereExists;\n\t\toperands.add(expression);\n\t\tsingleOperand = true;\n\t}\n\n\t// Set methods\n\n\tpublic void setThereExists(boolean thereExists)\n\t{\n\t\tthis.thereExists = thereExists;\n\t}\n\t\n\tpublic void setCoalitionAllPlayers()\n\t{\n\t\tthis.coalition.setAllPlayers();\n\t}\n\n\tpublic void setCoalition(List<String> coalition)\n\t{\n\t\tthis.coalition.setPlayers(coalition);\n\t}\n\n\tpublic void setSingleOperand(Expression expression)\n\t{\n\t\toperands.clear();\n\t\toperands.add(expression);\n\t\tsingleOperand = true;\n\t}\n\n\tpublic void addOperand(Expression e)\n\t{\n\t\toperands.add(e);\n\t}\n\n\tpublic void setOperand(int i, Expression e)\n\t{\n\t\toperands.set(i, e);\n\t}\n\n\t// Get methods\n\n\tpublic boolean isThereExists()\n\t{\n\t\treturn thereExists;\n\t}\n\n\t/**\n\t * Get a string \"\"&lt;&lt;&gt;&gt;\"\" or \"[[]]\" indicating type of quantification.\n\t */\n\tpublic String getOperatorString()\n\t{\n\t\treturn thereExists ? \"<<>>\" : \"[[]]\";\n\t}\n\n\tpublic Coalition getCoalition()\n\t{\n\t\treturn coalition;\n\t}\n\t\n\tpublic boolean coalitionIsAllPlayers()\n\t{\n\t\treturn coalition.isAllPlayers();\n\t}\n\t\n\tpublic List<String> getCoalitionPlayers()\n\t{\n\t\treturn coalition.getPlayers();\n\t}\n\t\n\tpublic boolean hasSingleOperand()\n\t{\n\t\treturn singleOperand;\n\t}\n\t\n\tpublic int getNumOperands()\n\t{\n\t\treturn operands.size();\n\t}\n\n\tpublic Expression getOperand(int i)\n\t{\n\t\treturn operands.get(i);\n\t}\n\n\tpublic List<Expression> getOperands()\n\t{\n\t\treturn operands;\n\t}\n\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate a \" + getOperatorString() + \" operator without a model\");\n\t}\n\n\t/*@Override\n\tpublic String getResultName()\n\t{\n\t\treturn expression.getResultName();\n\t}*/\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionStrategy deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(operands);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic ExpressionStrategy clone()\n\t{\n\t\tExpressionStrategy clone = (ExpressionStrategy) super.clone();\n\n\t\tclone.coalition = new Coalition(coalition);\n\t\tclone.operands  = (ArrayList<Expression>) operands.clone();\n\n\t\treturn clone;\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\ts += (thereExists ? \"<<\" : \"[[\");\n\t\ts += coalition;\n\t\ts += (thereExists ? \">> \" : \"]] \");\n\t\tif (singleOperand) {\n\t\t\ts += operands.get(0);\n\t\t} else {\n\t\t\ts += \"(\";\n\t\t\tboolean first = true;\n\t\t\tfor (Expression operand : operands) {\n\t\t\t\tif (!first)\n\t\t\t\t\ts += \", \";\n\t\t\t\telse\n\t\t\t\t\tfirst = false;\n\t\t\t\ts = s + operand;\n\t\t\t}\n\t\t\ts += \")\";\n\t\t}\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((coalition == null) ? 0 : coalition.hashCode());\n\t\tresult = prime * result + ((operands == null) ? 0 : operands.hashCode());\n\t\tresult = prime * result + (singleOperand ? 1231 : 1237);\n\t\tresult = prime * result + (thereExists ? 1231 : 1237);\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionStrategy other = (ExpressionStrategy) obj;\n\t\tif (coalition == null) {\n\t\t\tif (other.coalition != null)\n\t\t\t\treturn false;\n\t\t} else if (!coalition.equals(other.coalition))\n\t\t\treturn false;\n\t\tif (operands == null) {\n\t\t\tif (other.operands != null)\n\t\t\t\treturn false;\n\t\t} else if (!operands.equals(other.operands))\n\t\t\treturn false;\n\t\tif (singleOperand != other.singleOperand)\n\t\t\treturn false;\n\t\tif (thereExists != other.thereExists)\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionTemporal.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionTemporal extends Expression\n{\n\t// Operator constants\n\tpublic static final int P_X = 1; // Next (for P operator)\n\tpublic static final int P_U = 2; // Until (for P operator)\n\tpublic static final int P_F = 3; // Future (for P operator)\n\tpublic static final int P_G = 4; // Globally (for P operator)\n\tpublic static final int P_W = 5; // Weak until (for P operator)\n\tpublic static final int P_R = 6; // Release (for P operator)\n\tpublic static final int R_C = 11; // Cumulative (for R operator)\n\tpublic static final int R_I = 12; // Instantaneous (for R operator)\n\tpublic static final int R_F = 13; // Reachability (for R operator) // DEPRECATED: Use P_F\n\tpublic static final int R_S = 14; // Steady-state (for R operator)\n\t// Operator symbols\n\tpublic static final String opSymbols[] = { \"\", \"X\", \"U\", \"F\", \"G\", \"W\", \"R\", \"\", \"\", \"\", \"\", \"C\", \"I\", \"F\", \"S\" };\n\n\t/** Operator, one of the operator constants above */\n\tprotected int op = 0;\n\n\t// Up to two operands (either may be null)\n\t/** LHS of operator, null for unary operators */\n\tprotected Expression operand1 = null;\n\t/** RHS of operator, null for nullary operators (e.g., S) */\n\tprotected Expression operand2 = null;\n\n\t// Optional (time) bounds\n\tprotected Expression lBound = null; // None if null, i.e. zero\n\tprotected Expression uBound = null; // None if null, i.e. infinity\n\t// Strictness of (time) bounds\n\tprotected boolean lBoundStrict = false; // true: >, false: >= \n\tprotected boolean uBoundStrict = false; // true: <, false: <=\n\t// Display as =T rather than [T,T] ?\n\tprotected boolean equals = false;\n\n\t// Constructors\n\n\t/** Constructor */\n\tpublic ExpressionTemporal()\n\t{\n\t}\n\n\t/**\n\t * Constructor.\n\t * @param op the temporal operator (see constants at ExpressionTemporal)\n\t * @param operand1 the LHS operand ({@code null} for unary operators)\n\t * @param operand2 the RHS operand\n\t */\n\tpublic ExpressionTemporal(int op, Expression operand1, Expression operand2)\n\t{\n\t\tthis.op = op;\n\t\tthis.operand1 = operand1;\n\t\tthis.operand2 = operand2;\n\t}\n\n\t// Set methods\n\n\t/** Set the operator to i */\n\tpublic void setOperator(int i)\n\t{\n\t\top = i;\n\t}\n\n\t/** Set the LHS operand to e1 */\n\tpublic void setOperand1(Expression e1)\n\t{\n\t\toperand1 = e1;\n\t}\n\n\t/** Set the RHS operand to e2 */\n\tpublic void setOperand2(Expression e2)\n\t{\n\t\toperand2 = e2;\n\t}\n\n\t/**\n\t * Set lower time bound to be of form &gt;= e\n\t * (null denotes no lower bound, i.e. zero)\n\t */\n\tpublic void setLowerBound(Expression e)\n\t{\n\t\tsetLowerBound(e, false);\n\t}\n\n\t/**\n\t * Set lower time bound to be of form &gt;= e or &gt; e\n\t * (null denotes no lower bound, i.e. zero)\n\t */\n\tpublic void setLowerBound(Expression e, boolean strict)\n\t{\n\t\tlBound = e;\n\t\tlBoundStrict = strict;\n\t}\n\n\t/**\n\t * Set upper time bound to be of form &lt;= e\n\t * (null denotes no upper bound, i.e. infinity)\n\t */\n\tpublic void setUpperBound(Expression e)\n\t{\n\t\tsetUpperBound(e, false);\n\t}\n\n\t/**\n\t * Set upper time bound to be of form &lt;= e or &lt; e\n\t * (null denotes no upper bound, i.e. infinity)\n\t */\n\tpublic void setUpperBound(Expression e, boolean strict)\n\t{\n\t\tuBound = e;\n\t\tuBoundStrict = strict;\n\t}\n\n\t/**\n\t * Set both lower/upper time bound to e, i.e. \"=e\".\n\t */\n\tpublic void setEqualBounds(Expression e)\n\t{\n\t\tlBound = e;\n\t\tlBoundStrict = false;\n\t\tuBound = e;\n\t\tuBoundStrict = false;\n\t\tequals = true;\n\t}\n\n\t/**\n\t * Take the bounds information from the other ExpressionTemporal\n\t * and store them in this ExpressionTemporal (no deep copy).\n\t */\n\tpublic void setBoundsFrom(ExpressionTemporal exprTemp)\n\t{\n\t\tsetLowerBound(exprTemp.getLowerBound(), exprTemp.lowerBoundIsStrict());\n\t\tsetUpperBound(exprTemp.getUpperBound(), exprTemp.upperBoundIsStrict());\n\t\tequals = exprTemp.equals;\n\t}\n\n\t// Get methods\n\n\t/** Set the operator */\n\tpublic int getOperator()\n\t{\n\t\treturn op;\n\t}\n\n\tpublic String getOperatorSymbol()\n\t{\n\t\treturn opSymbols[op];\n\t}\n\n\t/** Get the LHS operand (should be {@code null} for unary operators) */\n\tpublic Expression getOperand1()\n\t{\n\t\treturn operand1;\n\t}\n\n\t/** Get the RHS operand */\n\tpublic Expression getOperand2()\n\t{\n\t\treturn operand2;\n\t}\n\n\t/* Get the number of stored operands */\n\tpublic int getNumOperands()\n\t{\n\t\tif (operand2 == null)\n\t\t\treturn 0;\n\t\telse\n\t\t\treturn (operand1 == null) ? 1 : 2;\n\t}\n\n\tpublic boolean hasBounds()\n\t{\n\t\treturn lBound != null || uBound != null;\n\t}\n\n\tpublic Expression getLowerBound()\n\t{\n\t\treturn lBound;\n\t}\n\n\tpublic boolean lowerBoundIsStrict()\n\t{\n\t\treturn lBoundStrict;\n\t}\n\n\tpublic Expression getUpperBound()\n\t{\n\t\treturn uBound;\n\t}\n\n\tpublic boolean upperBoundIsStrict()\n\t{\n\t\treturn uBoundStrict;\n\t}\n\n\t/**\n\t * Returns true if lower/upper bound are equal and should be displayed as =T \n\t */\n\tpublic boolean getEquals()\n\t{\n\t\treturn equals;\n\t}\n\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Cannot evaluate a temporal operator without a path\");\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic Precedence getPrecedence()\n\t{\n\t\tswitch (op) {\n\t\t\tcase P_X:\n\t\t\tcase P_F:\n\t\t\tcase P_G:\n\t\t\tcase R_C:\n\t\t\tcase R_I:\n\t\t\tcase R_F:\n\t\t\tcase R_S:\n\t\t\t\treturn Precedence.TEMPORAL_UNARY;\n\t\t\tcase P_U:\n\t\t\tcase P_W:\n\t\t\tcase P_R:\n\t\t\t\treturn Precedence.TEMPORAL_BINARY;\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t}\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionTemporal deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand1 = copier.copy(operand1);\n\t\toperand2 = copier.copy(operand2);\n\t\tlBound = copier.copy(lBound);\n\t\tuBound = copier.copy(uBound);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionTemporal clone()\n\t{\n\t\treturn (ExpressionTemporal) super.clone();\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\t\tif (operand1 != null) {\n\t\t\t// Binary temporal operators are generally not assumed to be commutative\n\t\t\tbuilder.append(Expression.toStringPrecLeq(operand1, this));\n\t\t\tbuilder.append(\" \");\n\t\t}\n\t\tbuilder.append(opSymbols[op]);\n\t\tif (lBound == null) {\n\t\t\tif (uBound != null) {\n\t\t\t\tif (op != R_I) {\n\t\t\t\t\tbuilder.append(\"<\");\n\t\t\t\t\tbuilder.append(uBoundStrict ? \"\" : \"=\");\n\t\t\t\t} else {\n\t\t\t\t\tbuilder.append(\"=\");\n\t\t\t\t}\n\t\t\t\tbuilder.append(uBound);\n\t\t\t}\n\t\t} else {\n\t\t\tif (uBound == null) {\n\t\t\t\tbuilder.append(\">\");\n\t\t\t\tbuilder.append(lBoundStrict ? \"\" : \"=\");\n\t\t\t\tbuilder.append(lBound);\n\t\t\t} else {\n\t\t\t\tif (equals) {\n\t\t\t\t\tbuilder.append(\"=\");\n\t\t\t\t\tbuilder.append(lBound);\n\t\t\t\t} else {\n\t\t\t\t\tbuilder.append(\"[\");\n\t\t\t\t\tbuilder.append(lBound);\n\t\t\t\t\tbuilder.append(\",\");\n\t\t\t\t\tbuilder.append(uBound);\n\t\t\t\t\tbuilder.append(\"]\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (operand2 != null) {\n\t\t\tbuilder.append(\" \");\n\t\t\tif (operand1 != null) {\n\t\t\t\t// Binary temporal operators are generally not assumed to be commutative\n\t\t\t\tbuilder.append(Expression.toStringPrecLeq(operand2, this));\n\t\t\t} else {\n\t\t\t\t// Unary temporal operators can be nested without parenthesising\n\t\t\t\tbuilder.append(Expression.toStringPrecLt(operand2, this));\n\t\t\t}\n\t\t}\n\t\treturn builder.toString();\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + (equals ? 1231 : 1237);\n\t\tresult = prime * result + ((lBound == null) ? 0 : lBound.hashCode());\n\t\tresult = prime * result + (lBoundStrict ? 1231 : 1237);\n\t\tresult = prime * result + op;\n\t\tresult = prime * result + ((operand1 == null) ? 0 : operand1.hashCode());\n\t\tresult = prime * result + ((operand2 == null) ? 0 : operand2.hashCode());\n\t\tresult = prime * result + ((uBound == null) ? 0 : uBound.hashCode());\n\t\tresult = prime * result + (uBoundStrict ? 1231 : 1237);\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionTemporal other = (ExpressionTemporal) obj;\n\t\tif (equals != other.equals)\n\t\t\treturn false;\n\t\tif (lBound == null) {\n\t\t\tif (other.lBound != null)\n\t\t\t\treturn false;\n\t\t} else if (!lBound.equals(other.lBound))\n\t\t\treturn false;\n\t\tif (lBoundStrict != other.lBoundStrict)\n\t\t\treturn false;\n\t\tif (op != other.op)\n\t\t\treturn false;\n\t\tif (operand1 == null) {\n\t\t\tif (other.operand1 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand1.equals(other.operand1))\n\t\t\treturn false;\n\t\tif (operand2 == null) {\n\t\t\tif (other.operand2 != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand2.equals(other.operand2))\n\t\t\treturn false;\n\t\tif (uBound == null) {\n\t\t\tif (other.uBound != null)\n\t\t\t\treturn false;\n\t\t} else if (!uBound.equals(other.uBound))\n\t\t\treturn false;\n\t\tif (uBoundStrict != other.uBoundStrict)\n\t\t\treturn false;\n\t\treturn true;\n\t}\n\n\t// Other useful methods\n\n\t/**\n\t * Convert (P operator) path formula to untils, using standard equivalences.\n\t */\n\tpublic Expression convertToUntilForm() throws PrismLangException\n\t{\n\t\tExpression op1, op2;\n\t\tExpressionTemporal exprTemp = null;\n\t\tswitch (op) {\n\t\tcase P_U:\n\t\t\treturn this;\n\t\tcase P_F:\n\t\t\t// F a == true U a\n\t\t\top1 = Expression.True();\n\t\t\texprTemp = new ExpressionTemporal(P_U, op1, operand2);\n\t\t\texprTemp.setBoundsFrom(this);\n\t\t\treturn exprTemp;\n\t\tcase P_G:\n\t\t\t// G a == !(true U !a)\n\t\t\top1 = Expression.True();\n\t\t\top2 = Expression.Not(operand2);\n\t\t\texprTemp = new ExpressionTemporal(P_U, op1, op2);\n\t\t\texprTemp.setBoundsFrom(this);\n\t\t\treturn Expression.Not(exprTemp);\n\t\tcase P_W:\n\t\t\t// a W b == !(a&!b U !a&!b)\n\t\t\top1 = Expression.And(operand1, Expression.Not(operand2));\n\t\t\top2 = Expression.And(Expression.Not(operand1), Expression.Not(operand2));\n\t\t\texprTemp = new ExpressionTemporal(P_U, op1, op2);\n\t\t\texprTemp.setBoundsFrom(this);\n\t\t\treturn Expression.Not(exprTemp);\n\t\tcase P_R:\n\t\t\t// a R b == !(!a U !b)\n\t\t\top1 = Expression.Not(operand1);\n\t\t\top2 = Expression.Not(operand2);\n\t\t\texprTemp = new ExpressionTemporal(P_U, op1, op2);\n\t\t\texprTemp.setBoundsFrom(this);\n\t\t\treturn Expression.Not(exprTemp);\n\t\t}\n\t\tthrow new PrismLangException(\"Cannot convert \" + getOperatorSymbol() + \" to until form\");\n\t}\n\n\t// ---- convenience methods for distinguishing top-level temporal operators -----------------\n\n\t/**\n\t * Returns true if the given expression is an ExpressionTemporal with the next step (X) top-level operator.\n\t */\n\tpublic static boolean isNext(Expression e)\n\t{\n\t\treturn (e instanceof ExpressionTemporal) && ((ExpressionTemporal) e).getOperator() == P_X;\n\t}\n\n\t/**\n\t * Returns true if the given expression is an ExpressionTemporal with the Until (U) top-level operator.\n\t */\n\tpublic static boolean isUntil(Expression e)\n\t{\n\t\treturn (e instanceof ExpressionTemporal) && ((ExpressionTemporal) e).getOperator() == P_U;\n\t}\n\n\t/**\n\t * Returns true if the given expression is an ExpressionTemporal with the Weak Until (W) top-level operator.\n\t */\n\tpublic static boolean isWeakUntil(Expression e)\n\t{\n\t\treturn (e instanceof ExpressionTemporal) && ((ExpressionTemporal) e).getOperator() == P_W;\n\t}\n\n\t/**\n\t * Returns true if the given expression is an ExpressionTemporal with the Release (R) top-level operator.\n\t */\n\tpublic static boolean isRelease(Expression e)\n\t{\n\t\treturn (e instanceof ExpressionTemporal) && ((ExpressionTemporal) e).getOperator() == P_R;\n\t}\n\n\t/**\n\t * Returns true if the given expression is an ExpressionTemporal with the finally / eventually (F) top-level operator.\n\t */\n\tpublic static boolean isFinally(Expression e)\n\t{\n\t\treturn (e instanceof ExpressionTemporal) && ((ExpressionTemporal) e).getOperator() == P_F;\n\t}\n\n\t/**\n\t * Returns true if the given expression is an ExpressionTemporal with the globally / always (G) top-level operator.\n\t */\n\tpublic static boolean isGlobally(Expression e)\n\t{\n\t\treturn (e instanceof ExpressionTemporal) && ((ExpressionTemporal) e).getOperator() == P_G;\n\t}\n\n\t/**\n\t * Returns true if the given expression is an ExpressionTemporal\n\t * with a globally finally / always eventually (G followed by F) top-level operator pair.\n\t */\n\tpublic static boolean isGloballyFinally(Expression e)\n\t{\n\t\treturn isGlobally(e) && isFinally(((ExpressionTemporal) e).getOperand2());\n\t}\n\n\t/**\n\t * Returns true if the given expression is an ExpressionTemporal\n\t * with a finally globally / eventually always (F followed by G) top-level operator pair.\n\t */\n\tpublic static boolean isFinallyGlobally(Expression e)\n\t{\n\t\treturn isFinally(e) && isGlobally(((ExpressionTemporal) e).getOperand2());\n\t}\n\n\n\t// ---- static constructors for building temporal expressions -----------------\n\n\t/** Construct a ExpressionTemporal for \"X expr\" */\n\tpublic static ExpressionTemporal Next(Expression expr)\n\t{\n\t\treturn new ExpressionTemporal(P_X, null, expr);\n\t}\n\n\t/** Construct a ExpressionTemporal for \"F expr\" */\n\tpublic static ExpressionTemporal Finally(Expression expr)\n\t{\n\t\treturn new ExpressionTemporal(P_F, null, expr);\n\t}\n\n\t/** Construct a ExpressionTemporal for \"G expr\" */\n\tpublic static ExpressionTemporal Globally(Expression expr)\n\t{\n\t\treturn new ExpressionTemporal(P_G, null, expr);\n\t}\n\n\t/** Construct a ExpressionTemporal for \"expr1 U expr2\" */\n\tpublic static ExpressionTemporal Globally(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionTemporal(P_U, expr1, expr2);\n\t}\n\n\t/** Construct a ExpressionTemporal for \"expr1 W expr2\" */\n\tpublic static ExpressionTemporal WeakUntil(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionTemporal(P_W, expr1, expr2);\n\t}\n\n\t/** Construct a ExpressionTemporal for \"expr1 R expr2\" */\n\tpublic static ExpressionTemporal Release(Expression expr1, Expression expr2)\n\t{\n\t\treturn new ExpressionTemporal(P_R, expr1, expr2);\n\t}\n\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionUnaryOp.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.math.BigInteger;\n\nimport param.BigRational;\nimport parser.*;\nimport parser.EvaluateContext.EvalMode;\nimport parser.visitor.*;\nimport prism.PrismLangException;\nimport parser.type.*;\n\npublic class ExpressionUnaryOp extends Expression\n{\n\t// Operator constants\n\tpublic static final int NOT = 1;\n\tpublic static final int MINUS = 2;\n\tpublic static final int PARENTH = 3;\n\t// Operator symbols\n\tpublic static final String opSymbols[] = { \"\", \"!\", \"-\", \"()\" };\n\n\t// Operator\n\tprotected int op = 0;\n\t// Operand\n\tprotected Expression operand = null;\n\n\t// Constructors\n\n\tpublic ExpressionUnaryOp()\n\t{\n\t}\n\n\tpublic ExpressionUnaryOp(int op, Expression operand)\n\t{\n\t\tthis.operand = operand;\n\t\tthis.op = op;\n\t}\n\n\t// Set methods\n\n\tpublic void setOperator(int i)\n\t{\n\t\top = i;\n\t}\n\n\t/**\n\t * Set the operator from the operator symbol.\n\t */\n\tpublic void setOperator(String s) throws PrismLangException\n\t{\n\t\tfor (int i = 1; i < opSymbols.length; i++) {\n\t\t\tif (opSymbols[i].equals(s)) {\n\t\t\t\tsetOperator(i);\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\tthrow new PrismLangException(\"Unknown unary operator '\" + s + \"'\");\n\t}\n\n\tpublic void setOperand(Expression e)\n\t{\n\t\toperand = e;\n\t}\n\n\t// Get methods\n\n\tpublic int getOperator()\n\t{\n\t\treturn op;\n\t}\n\n\tpublic String getOperatorSymbol()\n\t{\n\t\treturn opSymbols[op];\n\t}\n\n\tpublic Expression getOperand()\n\t{\n\t\treturn operand;\n\t}\n\n\t// Methods required for Expression:\n\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn operand.isConstant();\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn operand.isProposition();\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\tObject eval = operand.evaluate(ec);\n\t\treturn apply(eval, ec.getEvaluationMode());\n\t}\n\n\t/**\n\t * Apply this unary operator instance to the argument provided\n\t */\n\tpublic Object apply(Object eval, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tswitch (op) {\n\t\tcase NOT:\n\t\t\treturn !((Boolean) getType().castValueTo(eval));\n\t\tcase MINUS:\n\t\t\tswitch (evalMode) {\n\t\t\tcase FP:\n\t\t\t\ttry {\n\t\t\t\t\tif (getType() instanceof TypeInt) {\n\t\t\t\t\t\tint i = (int) TypeInt.getInstance().castValueTo(eval);\n\t\t\t\t\t\treturn Math.negateExact(i);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tdouble d = (double) TypeDouble.getInstance().castValueTo(eval);\n\t\t\t\t\t\treturn -d;\n\t\t\t\t\t}\n\t\t\t\t} catch (ArithmeticException e) {\n\t\t\t\t\tthrow new PrismLangException(e.getMessage(), this);\n\t\t\t\t}\n\t\t\tcase EXACT:\n\t\t\t\tif (getType() instanceof TypeInt) {\n\t\t\t\t\tBigInteger i = (BigInteger) TypeInt.getInstance().castValueTo(eval);\n\t\t\t\t\treturn i.negate();\n\t\t\t\t} else {\n\t\t\t\t\tBigRational d = (BigRational) TypeDouble.getInstance().castValueTo(eval);\n\t\t\t\t\treturn d.negate();\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t\t}\n\t\tcase PARENTH:\n\t\t\treturn eval;\n\t\t}\n\t\tthrow new PrismLangException(\"Unknown unary operator\", this);\n\t}\n\t\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn operand.returnsSingleValue();\n\t}\n\n\t@Override\n\tpublic Precedence getPrecedence()\n\t{\n\t\tswitch (op) {\n\t\t\tcase NOT:\n\t\t\t\treturn Precedence.NOT;\n\t\t\tcase MINUS:\n\t\t\t\treturn Precedence.UNARY_MINUS;\n\t\t\tcase PARENTH:\n\t\t\t\treturn Precedence.BASIC;\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t}\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionUnaryOp deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand = copier.copy(operand);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionUnaryOp clone()\n\t{\n\t\treturn (ExpressionUnaryOp) super.clone();\n\t}\n\n\t// Standard methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuilder builder = new StringBuilder();\n\t\tif (op == PARENTH) {\n\t\t\tbuilder.append(\"(\");\n\t\t} else {\n\t\t\tbuilder.append(opSymbols[op]);\n\t\t}\n\t\tbuilder.append(Expression.toStringPrecLt(operand, this));\n\t\tif (op == PARENTH) {\n\t\t\tbuilder.append(\")\");\n\t\t}\n\t\treturn builder.toString();\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + op;\n\t\tresult = prime * result + ((operand == null) ? 0 : operand.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionUnaryOp other = (ExpressionUnaryOp) obj;\n\t\tif (op != other.op)\n\t\t\treturn false;\n\t\tif (operand == null) {\n\t\t\tif (other.operand != null)\n\t\t\t\treturn false;\n\t\t} else if (!operand.equals(other.operand))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ExpressionVar.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.type.Type;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class ExpressionVar extends Expression\n{\n\t// Variable name\n\tprivate String name;\n\t// The index of the variable in the model to which it belongs\n\tprivate int index;\n\t\n\t// Constructors\n\t\n\tpublic ExpressionVar(String n, Type t)\n\t{\n\t\tsetType(t);\n\t\tname = n;\n\t\tindex = -1;\n\t}\n\t\t\t\n\t// Set method\n\t\n\tpublic void setName(String n) \n\t{\n\t\tname = n;\n\t}\n\t\n\tpublic void setIndex(int i) \n\t{\n\t\tindex = i;\n\t}\n\t\n\t// Get method\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\tpublic int getIndex()\n\t{\n\t\treturn index;\n\t}\n\t\n\t// Methods required for Expression:\n\t\n\t@Override\n\tpublic boolean isConstant()\n\t{\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean isProposition()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t{\n\t\t// Extract variable value from the evaluation context\n\t\tObject res = ec.getVarValue(name, index);\n\t\tif (res == null) {\n\t\t\tthrow new PrismLangException(\"Could not evaluate variable\", this);\n\t\t}\n\t\t// And cast it to the right type/mode if needed\n\t\treturn getType().castValueTo(res, ec.getEvaluationMode());\n\t}\n\n\t@Override\n\tpublic boolean returnsSingleValue()\n\t{\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic ExpressionVar deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ExpressionVar clone()\n\t{\n\t\treturn (ExpressionVar) super.clone();\n\t}\n\n\t// Standard methods\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn name;\n\t}\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + index;\n\t\tresult = prime * result + ((name == null) ? 0 : name.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tExpressionVar other = (ExpressionVar) obj;\n\t\tif (index != other.index)\n\t\t\treturn false;\n\t\tif (name == null) {\n\t\t\tif (other.name != null)\n\t\t\t\treturn false;\n\t\t} else if (!name.equals(other.name))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/Filter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n/**\n * Old-style filter, as embedded in P/R/S operator.\n */\npublic class Filter extends ASTElement\n{\n\tprivate Expression expr = null;\n\t// Either \"min\" or \"max\", or neither or both.\n\t// In the latter two cases, this means \"state\" or \"range\"\n\tprivate boolean minReq = false;\n\tprivate boolean maxReq = false;\n\n\t// Constructor\n\t\n\tpublic Filter(Expression expr)\n\t{\n\t\tthis.expr = expr;\n\t}\n\n\t// Set methods\n\t\n\tpublic void setExpression(Expression expr)\n\t{\n\t\tthis.expr = expr;\n\t}\n\n\tpublic void setMinRequested(boolean b)\n\t{\n\t\tminReq = b;\n\t}\n\n\tpublic void setMaxRequested(boolean b)\n\t{\n\t\tmaxReq = b;\n\t}\n\t\n\t// Get methods\n\t\n\tpublic Expression getExpression()\n\t{\n\t\treturn expr;\n\t}\n\n\tpublic boolean minRequested()\n\t{\n\t\treturn minReq;\n\t}\n\n\tpublic boolean maxRequested()\n\t{\n\t\treturn maxReq;\n\t}\n\n\t/**\n\t * Get (as a string) the operator for this filter\n\t * (as need to construct an ExpressionFilter object)\n\t */\n\tpublic String getFilterOpString()\n\t{\n\t\tif (minReq) {\n\t\t\treturn maxReq ? \"range\" : \"min\";\n\t\t} else {\n\t\t\treturn maxReq ? \"max\" : \"state\";\n\t\t}\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\ts += \"{\" + expr + \"}\";\n\t\tif (minReq) s += \"{min}\";\n\t\tif (maxReq) s += \"{max}\";\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic Filter deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\texpr = copier.copy(expr);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic Filter clone()\n\t{\n\t\treturn (Filter) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ForLoop.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.type.TypeInt;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\npublic class ForLoop extends ASTElement\n{\n\t// For loop info\n\tprivate String lhs;\n\tprivate Expression from;\n\tprivate Expression to;\n\tprivate Expression step;\n\t// Optional storage...\n\tprivate int pc;\n\tprivate String between;\n\t\n\t// Constructor\n\t\n\tpublic ForLoop()\n\t{\n\t\t// for loop info\n\t\tlhs = null;\n\t\tfrom = null;\n\t\tto = null;\n\t\tstep = null;\n\t\t// optional stuff\n\t\tpc = 0;\n\t\tbetween = \"\";\n\t}\n\n\t// Set methods\n\t\n\tpublic void setLHS(String s)\n\t{\n\t\tlhs = s;\n\t}\n\t\n\tpublic void setFrom(Expression e)\n\t{\n\t\tfrom = e;\n\t}\n\t\n\tpublic void setTo(Expression e)\n\t{\n\t\tto = e;\n\t}\n\t\n\tpublic void setStep(Expression e)\n\t{\n\t\tstep = e;\n\t}\n\t\n\tpublic void setPC(int i)\n\t{\n\t\tpc = i;\n\t}\n\t\n\tpublic void setBetween(String s)\n\t{\n\t\tbetween = s;\n\t}\n\n\t// Get methods\n\t\n\tpublic String getLHS()\n\t{\n\t\treturn lhs;\n\t}\n\t\n\tpublic Expression getFrom()\n\t{\n\t\treturn from;\n\t}\n\t\n\tpublic Expression getTo()\n\t{\n\t\treturn to;\n\t}\n\t\n\tpublic Expression getStep()\n\t{\n\t\treturn (step != null) ? step : new ExpressionLiteral(TypeInt.getInstance(), 1);\n\t}\n\t\n\tpublic int getPC()\n\t{\n\t\treturn pc;\n\t}\n\t\n\tpublic String getBetween()\n\t{\n\t\treturn between;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = lhs + \"=\" + from;\n\t\tif (step != null) s += \":\" + step;\n\t\ts += \":\" + to;\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic ForLoop deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tto = copier.copy(to);\n\t\tfrom = copier.copy(from);\n\t\tstep = copier.copy(step);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic ForLoop clone()\n\t{\n\t\treturn (ForLoop) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/FormulaList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\nimport prism.PrismUtils;\n\n// class to store list of formulas\n\npublic class FormulaList extends ASTElement\n{\n\t// Name/expression pairs to define formulas\n\tprivate ArrayList<String> names;\n\tprivate ArrayList<Expression> formulas;\n\t// We also store an ExpressionIdent to match each name.\n\t// This is to just to provide positional info.\n\tprivate ArrayList<ExpressionIdent> nameIdents;\n\n\t// Constructor\n\n\tpublic FormulaList()\n\t{\n\t\tnames = new ArrayList<>();\n\t\tformulas = new ArrayList<>();\n\t\tnameIdents = new ArrayList<>();\n\t}\n\n\t// Set methods\n\n\tpublic void addFormula(ExpressionIdent n, Expression f)\n\t{\n\t\tnames.add(n.getName());\n\t\tformulas.add(f);\n\t\tnameIdents.add(n);\n\t}\n\n\tpublic void setFormulaName(int i, ExpressionIdent n)\n\t{\n\t\tnames.set(i, n.getName());\n\t\tnameIdents.set(i, n);\n\t}\n\n\tpublic void setFormula(int i, Expression f)\n\t{\n\t\tformulas.set(i, f);\n\t}\n\n\t// Get methods\n\n\tpublic int size()\n\t{\n\t\treturn formulas.size();\n\t}\n\n\tpublic String getFormulaName(int i)\n\t{\n\t\treturn names.get(i);\n\t}\n\n\tpublic Expression getFormula(int i)\n\t{\n\t\treturn formulas.get(i);\n\t}\n\n\tpublic ExpressionIdent getFormulaNameIdent(int i)\n\t{\n\t\treturn nameIdents.get(i);\n\t}\n\n\t/**\n\t * Get the index of a formula by its name (returns -1 if it does not exist).\n\t */\n\tpublic int getFormulaIndex(String s)\n\t{\n\t\treturn names.indexOf(s);\n\t}\n\n\t/**\n\t * Find cyclic dependencies.\n\t */\n\tpublic void findCycles() throws PrismLangException\n\t{\n\t\t// Create boolean matrix of dependencies\n\t\t// (matrix[i][j] is true if formula i contains formula j)\n\t\tint n = size();\n\t\tboolean matrix[][] = new boolean[n][n];\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tList<String> v = getFormula(i).getAllFormulas();\n\t\t\tfor (int j = 0; j < v.size(); j++) {\n\t\t\t\tint k = getFormulaIndex(v.get(j));\n\t\t\t\tif (k != -1) {\n\t\t\t\t\tmatrix[i][k] = true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Check for and report dependencies\n\t\tint firstCycle = PrismUtils.findCycle(matrix);\n\t\tif (firstCycle != -1) {\n\t\t\tString s = \"Cyclic dependency in definition of formula \\\"\" + getFormulaName(firstCycle) + \"\\\"\";\n\t\t\tthrow new PrismLangException(s, getFormula(firstCycle));\n\t\t}\n\t}\n\n\t// Methods required for ASTElement:\n\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tint i, n;\n\n\t\tn = size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts += \"formula \" + getFormulaName(i);\n\t\t\ts += \" = \" + getFormula(i) + \";\\n\";\n\t\t}\n\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic FormulaList deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(formulas);\n\t\tcopier.copyAll(nameIdents);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic FormulaList clone()\n\t{\n\t\tFormulaList clone = (FormulaList) super.clone();\n\n\t\tclone.names      = (ArrayList<String>)          names.clone();\n\t\tclone.formulas   = (ArrayList<Expression>)      formulas.clone();\n\t\tclone.nameIdents = (ArrayList<ExpressionIdent>) nameIdents.clone();\n\n\t\treturn clone;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/LabelList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n// class to store list of labels\n\npublic class LabelList extends ASTElement\n{\n\t// Name/expression pairs to define labels\n\tprivate ArrayList<String> names;\n\tprivate ArrayList<Expression> labels;\n\t// We also store an ExpressionIdent to match each name.\n\t// This is to just to provide positional info.\n\tprivate ArrayList<ExpressionIdent> nameIdents;\n\t\n\t// Constructor\n\t\n\tpublic LabelList()\n\t{\n\t\tnames = new ArrayList<>();\n\t\tlabels = new ArrayList<>();\n\t\tnameIdents = new ArrayList<>();\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void addLabel(ExpressionIdent n, Expression l)\n\t{\n\t\tnames.add(n.getName());\n\t\tlabels.add(l);\n\t\tnameIdents.add(n);\n\t}\n\t\n\tpublic void setLabelName(int i , ExpressionIdent n)\n\t{\n\t\tnames.set(i, n.getName());\n\t\tnameIdents.set(i, n);\n\t}\n\t\n\tpublic void setLabel(int i , Expression l)\n\t{\n\t\tlabels.set(i, l);\n\t}\n\t\n\t// Get methods\n\n\tpublic int size()\n\t{\n\t\treturn labels.size();\n\t}\n\n\tpublic String getLabelName(int i)\n\t{\n\t\treturn names.get(i);\n\t}\n\t\n\tpublic List<String> getLabelNames()\n\t{\n\t\treturn names;\n\t}\n\t\n\tpublic Expression getLabel(int i)\n\t{\n\t\treturn labels.get(i);\n\t}\n\t\n\tpublic ExpressionIdent getLabelNameIdent(int i)\n\t{\n\t\treturn nameIdents.get(i);\n\t}\n\n\t/**\n\t * Get the index of a label by its name (returns -1 if it does not exist).\n\t */\n\tpublic int getLabelIndex(String s)\n\t{\n\t\treturn names.indexOf(s);\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tint i, n;\n\t\t\n\t\tn = size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts += \"label \\\"\" + getLabelName(i);\n\t\t\ts += \"\\\" = \" + getLabel(i) + \";\\n\";\n\t\t}\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic LabelList deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(labels);\n\t\tcopier.copyAll(nameIdents);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic LabelList clone()\n\t{\n\t\tLabelList clone = (LabelList) super.clone();\n\n\t\tclone.names      = (ArrayList<String>)       \tnames.clone();\n\t\tclone.labels     = (ArrayList<Expression>)      labels.clone();\n\t\tclone.nameIdents = (ArrayList<ExpressionIdent>) nameIdents.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/Module.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class Module extends ASTElement\n{\n\t// Module name\n\tprivate String name;\n\tprivate ExpressionIdent nameASTElement;\n\t// Local variables\n\tprivate ArrayList<Declaration> decls;\n\t// Commands\n\tprivate ArrayList<Command> commands;\n\t// Invariant (PTA models only; optional)\n\tprivate Expression invariant;\n\t// Parent ModulesFile\n\tprivate ModulesFile parent;\n\t// Base module (if was constructed through renaming; null if not)\n\tprivate String baseModule;\n\t// Alphabet (if defined explicitly rather than deduced from syntax)\n\tprivate ArrayList<String> alphabet;\n\n\t// Constructor\n\t\n\tpublic Module(String n)\n\t{\n\t\tname = n;\n\t\tdecls = new ArrayList<>();\n\t\tcommands = new ArrayList<>();\n\t\tinvariant = null;\n\t\tparent = null;\n\t\tbaseModule = null;\n\t}\n\n\t// Set methods\n\t\n\tpublic void setName(String n)\n\t{\n\t\tname = n;\n\t}\n\t\n\tpublic void setNameASTElement(ExpressionIdent e)\n\t{\n\t\tnameASTElement = e;\n\t}\n\t\n\tpublic void addDeclaration(Declaration d)\n\t{\n\t\tdecls.add(d);\n\t}\n\t\n\tpublic void setDeclaration(int i, Declaration d)\n\t{\n\t\tdecls.set(i, d);\n\t}\n\t\n\tpublic void addCommand(Command c)\n\t{\n\t\tcommands.add(c);\n\t\tc.setParent(this);\n\t}\n\t\n\tpublic void removeCommand(Command c)\n\t{\n\t\tcommands.remove(c);\n\t}\n\t\n\tpublic void setCommand(int i, Command c)\n\t{\n\t\tcommands.set(i, c);\n\t\tc.setParent(this);\n\t}\n\t\n\tpublic void setInvariant(Expression e)\n\t{\n\t\tinvariant = e;\n\t}\n\t\n\tpublic void setParent(ModulesFile mf)\n\t{\n\t\tparent = mf;\n\t}\n\n\tpublic void setBaseModule(String b)\n\t{\n\t\tbaseModule = b;\n\t}\n\t\n\t/**\n\t * Optionally, define the alphabet (of actions that can label transitions) for this module.\n\t * Normally, this is deduced syntactically (as the set of actions appearing in commands)\n\t * but you can override this if you want. Pass null to un-override;\n\t */\n\tpublic void setAlphabet(List<String> alphabet)\n\t{\n\t\tthis.alphabet = (alphabet == null) ? null : new ArrayList<>(alphabet);\n\t}\n\t\n\t// Get methods\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\tpublic ExpressionIdent getNameASTElement()\n\t{\n\t\treturn nameASTElement;\n\t}\n\t\n\t/**\n\t * Get the number of local variable declarations. \n\t */\n\tpublic int getNumDeclarations()\n\t{\n\t\treturn decls.size();\n\t}\n\t\n\t/**\n\t * Get the ith local variable declaration. \n\t */\n\tpublic Declaration getDeclaration(int i)\n\t{\n\t\treturn decls.get(i);\n\t}\n\t\n\t/**\n\t * Get the list of all local variable declarations. \n\t */\n\tpublic List<Declaration> getDeclarations()\n\t{\n\t\treturn decls;\n\t}\n\t\n\t/**\n\t * Check for the existence of a local variable (declaration).\n\t */\n\tpublic boolean isVariableName(String var)\n\t{\n\t\tfor (Declaration decl: decls) {\n\t\t\tif (decl.getName().equals(var))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\t\n\tpublic int getNumCommands()\n\t{\n\t\treturn commands.size();\n\t}\n\t\n\tpublic Command getCommand(int i)\n\t{\n\t\treturn commands.get(i);\n\t}\n\t\n\tpublic List<Command> getCommands()\n\t{\n\t\treturn commands;\n\t}\n\t\n\tpublic Expression getInvariant()\n\t{\n\t\treturn invariant;\n\t}\n\t\n\tpublic ModulesFile getParent()\n\t{\n\t\treturn parent;\n\t}\n\t\n\tpublic String getBaseModule()\n\t{\n\t\treturn baseModule;\n\t}\n\n\t/**\n\t * Get the set of synchronising actions of this module, i.e. its alphabet.\n\t * Note that the definition of alphabet is syntactic: existence of an a-labelled command in this\n\t * module ensures that a is in the alphabet, regardless of whether the guard is true.\n\t * The alphabet for a module can also be overridden using {@link #setAlphabet(List)}\n\t */\n\tpublic List<String> getAllSynchs()\n\t{\n\t\t// If overridden, use this\n\t\tif (alphabet != null) {\n\t\t\treturn alphabet;\n\t\t}\n\t\t// Otherwise, deduce syntactically\n\t\tList<String> allSynchs = new ArrayList<>();\n\t\tint numCommands = getNumCommands();\n\t\tfor (int i = 0; i < numCommands; i++) {\n\t\t\tString s = getCommand(i).getSynch();\n\t\t\tif (!s.equals(\"\") && !allSynchs.contains(s)) {\n\t\t\t\tallSynchs.add(s);\n\t\t\t}\n\t\t}\n\t\treturn allSynchs;\n\t}\n\n\t/**\n\t * Returns true iff this module contains at least one command\n\t * with no synchronous action label (\"[] ...\").\n\t */\n\tpublic boolean containsUnlabelledCommand()\n\t{\n\t\tint numCommands = getNumCommands();\n\t\tfor (int i = 0; i < numCommands; i++) {\n\t\t\tif (getCommand(i).isUnlabelled()) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Check if action label 's' is in the alphabet of this module.\n\t */\n\tpublic boolean usesSynch(String s)\n\t{\n\t\treturn getAllSynchs().contains(s);\n\t}\n\t\n\tpublic boolean isLocalVariable(String s)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumDeclarations();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (getDeclaration(i).getName().equals(s)) return true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tint i, n;\n\t\t\n\t\ts = s + \"module \" + name + \"\\n\\n\";\n\t\tn = getNumDeclarations();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = s + \"\\t\" + getDeclaration(i) + \";\\n\";\n\t\t}\n\t\tif (n > 0) s = s + \"\\n\";\n\t\tif (invariant != null) {\n\t\t\ts += \"\\tinvariant \" + invariant + \" endinvariant\\n\\n\";\n\t\t}\n\t\tn = getNumCommands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = s + \"\\t\" + getCommand(i) + \";\\n\";\n\t\t}\n\t\ts = s + \"\\nendmodule\";\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic Module deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tinvariant = copier.copy(invariant);\n\t\tnameASTElement = copier.copy(nameASTElement);\n\n\t\tcopier.copyAll(decls);\n\t\tcopier.copyAll(commands);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic Module clone()\n\t{\n\t\tModule clone = (Module) super.clone();\n\n\t\tclone.decls    = (ArrayList<Declaration>) decls.clone();\n\t\tclone.commands = (ArrayList<Command>) commands.clone();\n\t\tclone.alphabet = (alphabet == null) ? null : (ArrayList<String>) alphabet.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ModulesFile.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.HashSet;\nimport java.util.List;\nimport java.util.Objects;\n\nimport parser.EvaluateContext;\nimport parser.IdentUsage;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport parser.type.Type;\nimport parser.type.TypeInterval;\nimport parser.visitor.ASTTraverse;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport parser.visitor.ModulesFileSemanticCheck;\nimport parser.visitor.ModulesFileSemanticCheckAfterConstants;\nimport prism.ModelInfo;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismUtils;\nimport prism.RewardGenerator;\n\n// Class representing parsed model file\n\npublic class ModulesFile extends ASTElement implements ModelInfo, RewardGenerator\n{\n\t// Model type, as specified in the model file\n\tprivate ModelType modelTypeInFile;\n\t// Model type (actual, may differ)\n\tprivate ModelType modelType;\n\n\t// Model components\n\tprivate FormulaList formulaList;\n\tprivate LabelList labelList;\n\tprivate ConstantList constantList;\n\tprivate ArrayList<Declaration> globals; // Global variables\n\tprivate ArrayList<Object> modules; // Modules (includes renamed modules)\n\tprivate ArrayList<SystemDefn> systemDefns; // System definitions (system...endsystem constructs)\n\tprivate ArrayList<String> systemDefnNames; // System definition names (system...endsystem constructs)\n\tprivate ArrayList<RewardStruct> rewardStructs; // Rewards structures\n\tprivate ArrayList<String> rewardStructNames; // Names of reward structures\n\tprivate Expression initStates; // Initial states specification\n\tprivate ArrayList<ObservableVars> observableVarLists; // Observable variables lists\n\tprivate ArrayList<Observable> observableDefns; // Standalone observable definitions\n\t\n\t// Info about all identifiers used\n\tprivate IdentUsage identUsage;\n\tprivate IdentUsage quotedIdentUsage;\n\t// List of all module names\n\tprivate String[] moduleNames;\n\t// List of synchronising actions (strings appearing as [a] in commands)\n\tprivate ArrayList<String> synchs;\n\t// List of choice/transition action labels (includes null when some are unlabelled)\n\tprivate ArrayList<Object> actions;\n\t// Lists of variable info (declaration, name, type, module index)\n\tprivate ArrayList<Declaration> varDecls;\n\tprivate ArrayList<String> varNames;\n\tprivate ArrayList<Type> varTypes;\n\tprivate ArrayList<Integer> varModules;\n\t// Lists of observable info\n\tprivate ArrayList<Observable> observables;\n\tprivate ArrayList<String> observableNames;\n\tprivate ArrayList<Type> observableTypes;\n\tprivate ArrayList<String> observableVars;\n\n\t// Copy of the evaluation context used to defined undefined constants (null if none)\n\tprivate EvaluateContext ecUndefined;\n\t\n\t// Actual values of (some or all) constants\n\tprivate Values constantValues;\n\t// Evaluation context (all constant values + evaluation mode)\n\tprivate EvaluateContext ec;\n\n\t// Constructor\n\n\tpublic ModulesFile()\n\t{\n\t\tformulaList = new FormulaList();\n\t\tlabelList = new LabelList();\n\t\tconstantList = new ConstantList();\n\t\tmodelTypeInFile = modelType = null; // Unspecified\n\t\tglobals = new ArrayList<>();\n\t\tmodules = new ArrayList<>();\n\t\tsystemDefns = new ArrayList<SystemDefn>();\n\t\tsystemDefnNames = new ArrayList<String>();\n\t\trewardStructs = new ArrayList<RewardStruct>();\n\t\trewardStructNames = new ArrayList<String>();\n\t\tinitStates = null;\n\t\tobservableVarLists = new ArrayList<>();\n\t\tobservableDefns = new ArrayList<>();\n\t\tidentUsage = new IdentUsage();\n\t\tquotedIdentUsage = new IdentUsage(true);\n\t\tvarDecls = new ArrayList<>();\n\t\tvarNames = new ArrayList<>();\n\t\tvarTypes = new ArrayList<>();\n\t\tvarModules = new ArrayList<>();\n\t\tobservables = new ArrayList<>();\n\t\tobservableNames = new ArrayList<>();\n\t\tobservableTypes = new ArrayList<>();\n\t\tobservableVars = new ArrayList<>();\n\t\tecUndefined = null;\n\t\tconstantValues = null;\n\t\tec = EvaluateContext.create();\n\t}\n\n\t// Set methods\n\n\tpublic void setFormulaList(FormulaList fl)\n\t{\n\t\tformulaList = fl;\n\t}\n\n\tpublic void setLabelList(LabelList ll)\n\t{\n\t\tlabelList = ll;\n\t}\n\n\tpublic void setConstantList(ConstantList cl)\n\t{\n\t\tconstantList = cl;\n\t}\n\n\t/**\n\t * Set the model type that is specified in the model file.\n\t * Can be null, denoting that it is unspecified.\n\t */\n\tpublic void setModelTypeInFile(ModelType t)\n\t{\n\t\tmodelTypeInFile = t;\n\t\t// As a default, set the actual type to be the same\n\t\tmodelType = modelTypeInFile;\n\t}\n\n\t/**\n\t * Set the actual model type,\n\t * which may differ from the type specified in the model file.\n\t * Note: if {@link #tidyUp()} is called, this may be overwritten.\n\t */\n\tpublic void setModelType(ModelType t)\n\t{\n\t\tmodelType = t;\n\t}\n\n\tpublic void addGlobal(Declaration d)\n\t{\n\t\tglobals.add(d);\n\t}\n\n\tpublic void setGlobal(int i, Declaration d)\n\t{\n\t\tglobals.set(i, d);\n\t}\n\n\tpublic void addModule(Module m)\n\t{\n\t\tmodules.add(m);\n\t\tm.setParent(this);\n\t}\n\n\tpublic void setModule(int i, Module m)\n\t{\n\t\tmodules.set(i, m);\n\t\tm.setParent(this);\n\t}\n\n\tpublic void addRenamedModule(RenamedModule m)\n\t{\n\t\tmodules.add(m);\n\t}\n\n\t/**\n\t * Set a (single, un-named) \"system...endsystem\" construct for this model.\n\t * @param systemDefn SystemDefn object for the \"system...endsystem\" construct \n\t */\n\tpublic void setSystemDefn(SystemDefn systemDefn)\n\t{\n\t\tclearSystemDefns();\n\t\taddSystemDefn(systemDefn);\n\t}\n\n\t/**\n\t * Remove any \"system...endsystem\" constructs for this model.\n\t */\n\tpublic void clearSystemDefns()\n\t{\n\t\tsystemDefns.clear();\n\t\tsystemDefnNames.clear();\n\t}\n\n\t/**\n\t * Add an (un-named) \"system...endsystem\" construct to this model.\n\t * @param systemDefn SystemDefn object for the \"system...endsystem\" construct \n\t */\n\tpublic void addSystemDefn(SystemDefn systemDefn)\n\t{\n\t\taddSystemDefn(systemDefn, null);\n\t}\n\n\t/**\n\t * Add a \"system...endsystem\" construct to this model.\n\t * @param systemDefn SystemDefn object for the \"system...endsystem\" construct \n\t * @param name Optional name for the construct (null if un-named) \n\t */\n\tpublic void addSystemDefn(SystemDefn systemDefn, String name)\n\t{\n\t\tsystemDefns.add(systemDefn);\n\t\tsystemDefnNames.add(name);\n\t}\n\n\t/**\n\t * Set the {@code i}th  \"system...endsystem\" construct for this model.\n\t * @param i Index (starting from 0) \n\t * @param systemDefn SystemDefn object for the \"system...endsystem\" construct \n\t * @param name Optional name for the construct (null if un-named) \n\t */\n\tpublic void setSystemDefn(int i, SystemDefn systemDefn, String name)\n\t{\n\t\tsystemDefns.set(i, systemDefn);\n\t\tsystemDefnNames.set(i, name);\n\t}\n\n\tpublic void clearRewardStructs()\n\t{\n\t\trewardStructs.clear();\n\t\trewardStructNames.clear();\n\t}\n\n\tpublic void addRewardStruct(RewardStruct r)\n\t{\n\t\trewardStructs.add(r);\n\t\trewardStructNames.add(r.getName());\n\t}\n\n\tpublic void setRewardStruct(int i, RewardStruct r)\n\t{\n\t\trewardStructs.set(i, r);\n\t\trewardStructNames.set(i, r.getName());\n\t}\n\n\t// this method is included for backwards compatibility only\n\tpublic void setRewardStruct(RewardStruct r)\n\t{\n\t\tclearRewardStructs();\n\t\taddRewardStruct(r);\n\t}\n\n\tpublic void setInitialStates(Expression e)\n\t{\n\t\tinitStates = e;\n\t}\n\n\t/**\n\t * Add an observable variables list\n\t */\n\tpublic void addObservableVarList(ObservableVars obsVars)\n\t{\n\t\tobservableVarLists.add(obsVars);\n\t}\n\t\n\t/**\n\t * Set the ith observable variables list\n\t */\n\tpublic void setObservableVarList(int i, ObservableVars obsVars)\n\t{\n\t\tobservableVarLists.set(i, obsVars);\n\t}\n\t\n\t/**\n\t * Add a (standalone) observable definition\n\t */\n\tpublic void addObservableDefinition(Observable obs)\n\t{\n\t\tobservableDefns.add(obs);\n\t}\n\t\n\t/**\n\t * Set the ith (standalone) observable definition\n\t */\n\tpublic void setObservableDefinition(int i, Observable obs)\n\t{\n\t\tobservableDefns.set(i, obs);\n\t}\n\t\n\t// Get methods\n\n\tpublic FormulaList getFormulaList()\n\t{\n\t\treturn formulaList;\n\t}\n\n\t@Override\n\tpublic int getNumLabels()\n\t{\n\t\treturn labelList.size();\n\t}\n\n\t@Override\n\tpublic List<String> getLabelNames()\n\t{\n\t\treturn labelList.getLabelNames();\n\t}\n\n\t@Override\n\tpublic String getLabelName(int i) throws PrismException\n\t{\n\t\treturn labelList.getLabelName(i);\n\t}\n\n\t@Override\n\tpublic int getLabelIndex(String label)\n\t{\n\t\treturn labelList.getLabelIndex(label);\n\t}\n\t\n\tpublic LabelList getLabelList()\n\t{\n\t\treturn labelList;\n\t}\n\n\tpublic ConstantList getConstantList()\n\t{\n\t\treturn constantList;\n\t}\n\n\tpublic ModelType getModelTypeInFile()\n\t{\n\t\treturn modelTypeInFile;\n\t}\n\t\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn modelType;\n\t}\n\n\tpublic String getTypeString()\n\t{\n\t\treturn \"\" + modelType;\n\t}\n\n\tpublic String getTypeFullString()\n\t{\n\t\treturn modelType.fullName();\n\t}\n\n\tpublic int getNumGlobals()\n\t{\n\t\treturn globals.size();\n\t}\n\n\tpublic Declaration getGlobal(int i)\n\t{\n\t\treturn globals.get(i);\n\t}\n\t\n\tpublic int getNumModules()\n\t{\n\t\treturn modules.size();\n\t}\n\n\t// get module by index\n\t// returns null if it is a RenamedModule\n\t// these will have been replaced with Modules after tidyUp()\n\tpublic Module getModule(int i)\n\t{\n\t\tObject o = modules.get(i);\n\t\treturn (o instanceof Module) ? (Module) o : null;\n\t}\n\n\t// get the index of a module by its name\n\t// (returns -1 if it does not exist)\n\t// (or is a RenamedModule and hasn't been turned into a normal Module yet)\n\tpublic int getModuleIndex(String s)\n\t{\n\t\tint i;\n\t\tModule m;\n\n\t\tfor (i = 0; i < modules.size(); i++) {\n\t\t\tm = getModule(i);\n\t\t\tif (m != null)\n\t\t\t\tif (s.equals(m.getName())) {\n\t\t\t\t\treturn i;\n\t\t\t\t}\n\t\t}\n\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Get the default \"system...endsystem\" construct for this model, if it exists.\n\t * If there is an un-named \"system...endsystem\" (there can be at most one),\n\t * this is the default. If not, the first (named) one is taken as the default.\n\t * If there are no  \"system...endsystem\" constructs, this method returns null.\n\t */\n\tpublic SystemDefn getSystemDefn()\n\t{\n\t\tint n = systemDefns.size();\n\t\tif (n == 0)\n\t\t\treturn null;\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (systemDefnNames.get(i) == null)\n\t\t\t\treturn systemDefns.get(i);\n\t\t}\n\t\treturn systemDefns.get(0);\n\t}\n\t\n\t/**\n\t * Get the number of \"system...endsystem\" constructs for this model.\n\t */\n\tpublic int getNumSystemDefns()\n\t{\n\t\treturn systemDefns.size();\n\t}\n\n\t/**\n\t * Get the {@code i}th \"system...endsystem\" construct for this model (0-indexed).\n\t */\n\tpublic SystemDefn getSystemDefn(int i)\n\t{\n\t\treturn systemDefns.get(i);\n\t}\n\n\t/**\n\t * Get the name of the {@code i}th \"system...endsystem\" construct for this model (0-indexed).\n\t * Returns null if that construct is un-named.\n\t */\n\tpublic String getSystemDefnName(int i)\n\t{\n\t\treturn systemDefnNames.get(i);\n\t}\n\n\t/**\n\t * Get the index of a \"system...endsystem\" construct by its name (indexed from 0).\n\t * Passing null for the name looks up an un-named construct. \n\t * Returns null if the requested construct does not exist.\n\t */\n\tpublic int getSystemDefnIndex(String name)\n\t{\n\t\tint n = systemDefns.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = systemDefnNames.get(i); \n\t\t\tif ((s == null && name == null) || (s != null && s.equals(name)))\n\t\t\t\treturn i;\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Get a \"system...endsystem\" construct by its name.\n\t * Passing null for the name looks up an un-named construct. \n\t * Returns null if the requested construct does not exist.\n\t */\n\tpublic SystemDefn getSystemDefnByName(String name)\n\t{\n\t\tint i = getSystemDefnIndex(name);\n\t\treturn i == -1 ? null : getSystemDefn(i);\n\t}\n\n\t/**\n\t * Get the number of reward structures in the model.\n\t */\n\tpublic int getNumRewardStructs()\n\t{\n\t\treturn rewardStructs.size();\n\t}\n\n\t/**\n\t * Get a list of the names of the reward structures in the model.\n\t */\n\tpublic List<String> getRewardStructNames()\n\t{\n\t\treturn rewardStructNames;\n\t}\n\t\n\t/**\n\t * Get the index of a module by its name\n\t * (indexed from 0, not from 1 like at the user (property language) level).\n\t * Returns -1 if name does not exist.\n\t */\n\tpublic int getRewardStructIndex(String name)\n\t{\n\t\tint i, n;\n\t\tn = rewardStructs.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif ((rewardStructs.get(i)).getName().equals(name))\n\t\t\t\treturn i;\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Returns true if the {@code r}th reward structure defines state rewards.\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t */\n\tpublic boolean rewardStructHasStateRewards(int r)\n\t{\n\t\tRewardStruct rewStr = getRewardStruct(r);\n\t\treturn rewStr.getNumStateItems() > 0;\n\t}\n\n\t/**\n\t * Returns true if the {@code r}th reward structure defines transition rewards.\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t */\n\tpublic boolean rewardStructHasTransitionRewards(int r)\n\t{\n\t\tRewardStruct rewStr = getRewardStruct(r);\n\t\treturn rewStr.getNumTransItems() > 0;\n\t}\n\n\t/**\n\t * Get a reward structure by its index\n\t * (indexed from 0, not from 1 like at the user (property language) level).\n\t * Returns null if index is out of range.\n\t */\n\tpublic RewardStruct getRewardStruct(int i)\n\t{\n\t\treturn (i < rewardStructs.size()) ? rewardStructs.get(i) : null;\n\t}\n\n\t/**\n\t * Get access to the list of reward structures\n\t */\n\tpublic List<RewardStruct> getRewardStructs()\n\t{\n\t\treturn rewardStructs;\n\t}\n\n\t/**\n\t * Get a reward structure by its name\n\t * Returns null if name does not exist.\n\t */\n\tpublic RewardStruct getRewardStructByName(String name)\n\t{\n\t\tint i = getRewardStructIndex(name);\n\t\treturn i == -1 ? null : getRewardStruct(i);\n\t}\n\n\t/**\n\t * Get the first reward structure (exists for backwards compatibility only).\n\t */\n\tpublic RewardStruct getRewardStruct()\n\t{\n\t\treturn getRewardStruct(0);\n\t}\n\n\t@Override\n\tpublic boolean isRewardLookupSupported(RewardLookup lookup)\n\t{\n\t\treturn lookup == RewardLookup.BY_REWARD_STRUCT;\n\t}\n\t\n\t/**\n\t * Get the expression used in init...endinit to define the initial states of the model.\n\t * This is null if absent, i.e. the model has a single initial state defined by the\n\t * initial values for each individual variable.  \n\t * If non-null, we have to assume that there may be multiple initial states. \n\t */\n\tpublic Expression getInitialStates()\n\t{\n\t\treturn initStates;\n\t}\n\n\t/**\n\t * Does this model define observables?\n\t * (i.e., is it a partially observable model?)\n\t */\n\tpublic boolean hasObservables()\n\t{\n\t\treturn observableVarLists.size() > 0 || observableDefns.size() > 0;\n\t}\n\t\n\t/**\n\t * Get the number of lists of observable variables\n\t */\n\tpublic int getNumObservableVarLists()\n\t{\n\t\treturn observableVarLists.size();\n\t}\n\t\n\t/**\n\t * Get the ith list of observable variables\n\t */\n\tpublic ObservableVars getObservableVarList(int i)\n\t{\n\t\treturn observableVarLists.get(i);\n\t}\n\t\n\t/**\n\t * Get the number of (standalone) observable definitions\n\t */\n\tpublic int getNumObservableDefinitions()\n\t{\n\t\treturn observableDefns.size();\n\t}\n\t\n\t/**\n\t * Get the ith (standalone) observable definition\n\t */\n\tpublic Observable getObservableDefinition(int i)\n\t{\n\t return observableDefns.get(i);\n\t}\n\n\t/**\n\t * Look up a property by name.\n\t * Returns null if not found.\n\t * Currently only exists for forwards compatibility.\n\t */\n\tpublic Property getPropertyByName(String name)\n\t{\n\t\treturn null;\n\t}\n\t\n\t/**\n\t * Check if an identifier is already used somewhere in the model\n\t * (as a formula, constant or variable)\n\t * and throw an exception if it is. Otherwise, add it to the list.\n\t * @param ident The name of the (new) identifier\n\t * @param decl Where the identifier is declared in the model\n\t * @param use Optionally, the identifier's usage (e.g. \"constant\")\n\t */\n\tprivate void checkAndAddIdentifier(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\tidentUsage.checkAndAddIdentifier(ident, decl, use, \"the model\");\n\t}\n\t\n\t@Override\n\tpublic boolean isIdentUsed(String ident)\n\t{\n\t\t// Goes beyond default implementation in ModelInfo:\n\t\t// also looks at formulas\n\t\treturn identUsage.isIdentUsed(ident);\n\t}\n\n\t@Override\n\tpublic void checkIdent(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\t// Goes beyond default implementation in ModelInfo:\n\t\t// also looks at formulas, and produces better error messages\n\t\tidentUsage.checkIdent(ident, decl, use);\n\t}\n\n\t/**\n\t * Check if a quoted identifier is already used somewhere in the model\n\t * (as a label)\n\t * and throw an exception if it is. Otherwise, add it to the list.\n\t * @param ident The name of the (new) identifier, without quotes\n\t * @param decl Where the identifier is declared in the model\n\t * @param use Optionally, the identifier's usage (e.g. \"label\")\n\t */\n\tprivate void checkAndAddQuotedIdentifier(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\tquotedIdentUsage.checkAndAddIdentifier(ident, decl, use, \"the model\");\n\t}\n\t\n\t@Override\n\tpublic boolean isQuotedIdentUsed(String ident)\n\t{\n\t\treturn quotedIdentUsage.isIdentUsed(ident);\n\t}\n\n\t@Override\n\tpublic void checkQuotedIdent(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\t// Goes beyond default implementation in ModelInfo:\n\t\t// produces better error messages\n\t\tquotedIdentUsage.checkIdent(ident, decl, use);\n\t}\n\n\t// get individual module name\n\tpublic String getModuleName(int i)\n\t{\n\t\treturn moduleNames[i];\n\t}\n\n\t// get array of all module names\n\tpublic String[] getModuleNames()\n\t{\n\t\treturn moduleNames;\n\t}\n\n\t/**\n\t * Get the list of synchronising action names\n\t * (strings appearing as [a] in commands).\n\t */\n\tpublic List<String> getSynchs()\n\t{\n\t\treturn synchs;\n\t}\n\n\t/**\n\t * Get the {@code i}th (0-indexed) synchronising action name\n\t * (strings appearing as [a] in commands).\n\t */\n\tpublic String getSynch(int i)\n\t{\n\t\treturn synchs.get(i);\n\t}\n\n\t/**\n\t * Is {@code a} a synchronising action name\n\t * (a strings appearing as [a] in a command)?\n\t */\n\tpublic boolean isSynch(String a)\n\t{\n\t\treturn synchs != null && synchs.contains(a);\n\t}\n\n\t/**\n\t * Get the list of actions that can label choices/transitions\n\t * (includes null when some are unlabelled).\n\t */\n\tpublic List<Object> getActions()\n\t{\n\t\treturn actions;\n\t}\n\n\t// Variable query methods\n\n\t/**\n\t * Get the total number of variables (global and local).\n\t */\n\tpublic int getNumVars()\n\t{\n\t\treturn varNames.size();\n\t}\n\n\t/**\n\t * Look up the index of a variable in the model by name.\n\t * Returns -1 if there is no such variable. \n\t */\n\tpublic int getVarIndex(String name)\n\t{\n\t\treturn varNames.indexOf(name);\n\t}\n\n\t/**\n\t * Get the declaration of the ith variable.\n\t */\n\tpublic Declaration getVarDeclaration(int i)\n\t{\n\t\treturn varDecls.get(i);\n\t}\n\n\t/**\n\t * Get the name of the ith variable.\n\t */\n\tpublic String getVarName(int i)\n\t{\n\t\treturn varNames.get(i);\n\t}\n\n\t/**\n\t * Get the type of the ith variable.\n\t */\n\tpublic Type getVarType(int i)\n\t{\n\t\treturn varTypes.get(i);\n\t}\n\n\tpublic List<String> getVarNames()\n\t{\n\t\treturn varNames;\n\t}\n\n\tpublic List<Type> getVarTypes()\n\t{\n\t\treturn varTypes;\n\t}\n\n\t@Override\n\tpublic DeclarationType getVarDeclarationType(int i)\n\t{\n\t\treturn varDecls.get(i).getDeclType();\n\t}\n\n\t@Override\n\tpublic int getVarModuleIndex(int i)\n\t{\n\t\treturn varModules.get(i);\n\t}\n\n\tpublic boolean isGlobalVariable(String s)\n\t{\n\t\tint i, n;\n\n\t\tn = getNumGlobals();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (getGlobal(i).getName().equals(s))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic boolean containsUnboundedVariables()\n\t{\n\t\tint n = getNumVars();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tDeclarationType declType = getVarDeclaration(i).getDeclType();\n\t\t\tif (declType.isUnbounded()) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\t\n\tpublic boolean containsClockVariables()\n\t{\n\t\tint n = getNumVars();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (getVarDeclaration(i).getDeclType() instanceof DeclarationClock) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\t\n\tpublic Observable getObservable(int i)\n\t{\n\t\treturn observables.get(i);\n\t}\n\t\n\t@Override\n\tpublic boolean isVarObservable(int i)\n\t{\n\t\treturn observableVars.contains(getVarName(i));\n\t}\n\t\n\tpublic boolean isVarObservable(String varName)\n\t{\n\t\treturn observableVars.contains(varName);\n\t}\n\t\n\t@Override\n\tpublic List<String> getObservableNames()\n\t{\n\t\treturn observableNames;\n\t}\n\t\n\t@Override\n\tpublic List<Type> getObservableTypes()\n\t{\n\t\treturn observableTypes;\n\t}\n\t\n\t/**\n\t * Method to \"tidy up\" after parsing (must be called)\n\t * (do some checks and extract some information)\n\t */\n\tpublic void tidyUp() throws PrismLangException\n\t{\n\t\t// Clear data that will be generated by this method \n\t\t// (in case it has already been called previously).\n\t\tidentUsage.clear();\n\t\tquotedIdentUsage.clear();\n\t\tvarDecls.clear();\n\t\tvarNames.clear();\n\t\tvarTypes.clear();\n\t\tvarModules.clear();\n\t\t\n\t\t// Expansion of formulas and renaming\n\n\t\t// Check formula identifiers\n\t\tcheckFormulaIdents();\n\t\t// Find all formulas (i.e. locate identifiers which are formulas).\n\t\t// Note: This should all be done before replacing any other identifiers\n\t\t// (e.g. with variables) because this relies on module renaming which in turn\n\t\t// must be done after formula expansion. Then, check for any cyclic\n\t\t// dependencies in the formula list and then expand all formulas.\n\t\tfindAllFormulas(formulaList);\n\t\tformulaList.findCycles();\n\t\texpandFormulas(formulaList);\n\t\t// Perform module renaming\n\t\tsortRenamings();\n\n\t\t// Check label identifiers\n\t\tcheckLabelIdents();\n\n\t\t// Check module names\n\t\tcheckModuleNames();\n\n\t\t// Check constant identifiers\n\t\tcheckConstantIdents();\n\t\t// Find all instances of constants\n\t\t// (i.e. locate identifiers which are constants)\n\t\tfindAllConstants(constantList);\n\t\t// Check constants for cyclic dependencies\n\t\tconstantList.findCycles();\n\n\t\t// Check variable names, etc.\n\t\tcheckVarNames();\n\t\t// Find all instances of variables, replace identifiers with variables.\n\t\t// Also check variables valid, store indices, etc.\n\t\tfindAllVars(varNames, varTypes);\n\n\t\t// Find all instances of property refs\n\t\tfindAllPropRefs(this, null);\n\t\t\n\t\t// Check reward structure names\n\t\tcheckRewardStructNames();\n\n\t\t// Check \"system...endsystem\" constructs\n\t\tcheckSystemDefns();\n\t\t\n\t\t// Get synchronising action names\n\t\t// (NB: Do this *after* checking for cycles in system defns above)\n\t\tgetSynchAndActionNames();\n\t\t// Then identify/check any references to action names\n\t\tfindAllActions(synchs);\n\n\t\t// Determine actual model type\n\t\t// (checks/processing below this point can assume that modelType\n\t\t//  is non-null; methods before this point cannot)\n\t\tfinaliseModelType();\n\t\t\n\t\t// Various semantic checks \n\t\tdoSemanticChecks();\n\t\t// Type checking\n\t\ttypeCheck();\n\t\t// Check observables\n\t\tcheckObservables();\n\t\t\n\t\t// If there are no undefined constants, set up values for constants\n\t\t// (to avoid need for a later call to setSomeUndefinedConstants).\n\t\t// NB: Can't call setSomeUndefinedConstants now if there are undefined constants\n\t\t// because semanticCheckAfterConstants may fail. \n\t\tif (getUndefinedConstants().isEmpty()) {\n\t\t\t// NB: we use non-exact constant evaluation by default,\n\t\t\t// for exact mode constants will be reevaluated later on\n\t\t\tsetSomeUndefinedConstants(EvaluateContext.create());\n\t\t}\n\t}\n\n\t// Check formula identifiers\n\n\tprivate void checkFormulaIdents() throws PrismLangException\n\t{\n\t\tint n = formulaList.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = formulaList.getFormulaName(i);\n\t\t\tcheckAndAddIdentifier(s, formulaList.getFormulaNameIdent(i), \"formula\");\n\t\t}\n\t}\n\n\t// sort out modules defined by renaming\n\n\tprivate void sortRenamings() throws PrismLangException\n\t{\n\t\tint i, j, n, i2, n2;\n\t\tRenamedModule module;\n\t\tModule newModule;\n\t\tString s;\n\t\tObject o;\n\t\tHashSet<String> renamedSoFar;\n\n\t\t// Go through modules and find ones which are defined by renaming\n\t\tn = modules.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\to = modules.get(i);\n\t\t\tif (o instanceof Module)\n\t\t\t\tcontinue;\n\t\t\tmodule = (RenamedModule) o;\n\t\t\t// Check base module exists\n\t\t\tj = getModuleIndex(module.getBaseModule());\n\t\t\tif (j == -1) {\n\t\t\t\ts = \"No such module \" + module.getBaseModule();\n\t\t\t\ts += \" in renamed module \\\"\" + module.getName() + \"\\\"\";\n\t\t\t\tthrow new PrismLangException(s, module.getBaseModuleASTElement());\n\t\t\t}\n\t\t\t// Check for invalid renames\n\t\t\tn2 = module.getNumRenames();\n\t\t\trenamedSoFar = new HashSet<String>();\n\t\t\tfor (i2 = 0; i2 < n2; i2++) {\n\t\t\t\ts = module.getOldName(i2);\n\t\t\t\tif (!renamedSoFar.add(s)) {\n\t\t\t\t\tthrow new PrismLangException(\"Identifier \\\"\" + s + \"\\\" is renamed more than once in module \\\"\"\n\t\t\t\t\t\t\t+ module.getName() + \"\\\"\", module.getOldNameASTElement(i2));\n\t\t\t\t}\n\t\t\t\tif (formulaList.getFormulaIndex(s) != -1) {\n\t\t\t\t\tthrow new PrismLangException(\"Formula \\\"\" + s\n\t\t\t\t\t\t\t+ \"\\\" cannot be renamed since formulas are expanded before module renaming\", module\n\t\t\t\t\t\t\t.getOldNameASTElement(i2));\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Then rename (a copy of) base module and replace\n\t\t\t// (note: also store name of base module for later reference)\n\t\t\tnewModule = (Module) getModule(j).deepCopy().rename(module);\n\t\t\tnewModule.setNameASTElement(module.getNameASTElement());\n\t\t\tnewModule.setBaseModule(module.getBaseModule());\n\t\t\tsetModule(i, newModule);\n\t\t}\n\t}\n\n\t// check label identifiers\n\n\tprivate void checkLabelIdents() throws PrismLangException\n\t{\n\t\tint n = labelList.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = labelList.getLabelName(i);\n\t\t\tcheckAndAddQuotedIdentifier(s, labelList.getLabelNameIdent(i), \"label\");\n\t\t}\n\t}\n\n\t// check module names\n\n\tprivate void checkModuleNames() throws PrismLangException\n\t{\n\t\tint i, j, n;\n\t\tString s;\n\n\t\t// check we have at least one module\n\t\tn = modules.size();\n\t\tif (n == 0) {\n\t\t\tthrow new PrismLangException(\"There must be at least one module\");\n\t\t}\n\n\t\t// compile list of all module names\n\t\t// and check as we go through\n\t\tmoduleNames = new String[n];\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = getModule(i).getName();\n\t\t\tfor (j = 0; j < i; j++) {\n\t\t\t\tif (s.equals(moduleNames[j])) {\n\t\t\t\t\tthrow new PrismLangException(\"Duplicated module name \\\"\" + s + \"\\\"\", getModule(i)\n\t\t\t\t\t\t\t.getNameASTElement());\n\t\t\t\t}\n\t\t\t}\n\t\t\tmoduleNames[i] = s;\n\t\t}\n\t}\n\n\t/**\n\t * Construct the list of synchronising action names\n\t * and also all action names (including null for unlabelled commands).\n\t */\n\tprivate void getSynchAndActionNames() throws PrismLangException\n\t{\n\t\t// Go thru modules and extract action names which appear in their commands\n\t\t// Also check for presence of unlabelled commands\n\t\tsynchs = new ArrayList<>();\n\t\tboolean unlabelled = false;\n\t\tint numModules = modules.size();\n\t\tfor (int i = 0; i < numModules; i++) {\n\t\t\tModule module = getModule(i);\n\t\t\tfor (String s : module.getAllSynchs()) {\n\t\t\t\tif (!synchs.contains(s)) {\n\t\t\t\t\tsynchs.add(s);\n\t\t\t\t}\n\t\t\t}\n\t\t\tunlabelled |= module.containsUnlabelledCommand();\n\t\t}\n\n\t\t// Then extract any which are introduced in the (default) system construct (by renaming)\n\t\tSystemDefn defaultSystemDefn = getSystemDefn();\n\t\tif (defaultSystemDefn != null) {\n\t\t\tdefaultSystemDefn.getSynchs(synchs, this);\n\t\t\tunlabelled |= defaultSystemDefn.containsSystemHide();\n\t\t}\n\n\t\t// Put all synchronising actions in the action list\n\t\t// If there are unlabelled commands, add null too\n\t\tactions = new ArrayList<>();\n\t\tif (unlabelled) {\n\t\t\tactions.add(null);\n\t\t}\n\t\tactions.addAll(synchs);\n\t}\n\n\t@Override\n\tpublic String getActionStringDescription()\n\t{\n\t\treturn \"Module/[action]\";\n\t}\n\t\n\t// check constant identifiers\n\n\tprivate void checkConstantIdents() throws PrismLangException\n\t{\n\t\tint n = constantList.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = constantList.getConstantName(i);\n\t\t\tcheckAndAddIdentifier(s, constantList.getConstantNameIdent(i), \"constant\");\n\t\t}\n\t}\n\n\t// check variable names\n\n\tprivate void checkVarNames() throws PrismLangException\n\t{\n\t\t// compile list of all var names\n\t\t// and check as we go through\n\n\t\t// globals\n\t\tint n = getNumGlobals();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = getGlobal(i).getName();\n\t\t\tcheckAndAddIdentifier(s, getGlobal(i), \"variable\");\n\t\t\tvarDecls.add(getGlobal(i));\n\t\t\tvarNames.add(s);\n\t\t\tvarTypes.add(getGlobal(i).getType());\n\t\t\tvarModules.add(-1);\n\t\t}\n\n\t\t// locals\n\t\tint numModules = modules.size();\n\t\tfor (int i = 0; i < numModules; i++) {\n\t\t\tModule module = getModule(i);\n\t\t\tint numLocals = module.getNumDeclarations();\n\t\t\tfor (int j = 0; j < numLocals; j++) {\n\t\t\t\tString s = module.getDeclaration(j).getName();\n\t\t\t\tcheckAndAddIdentifier(s, module.getDeclaration(j), \"variable\");\n\t\t\t\tvarDecls.add(module.getDeclaration(j));\n\t\t\t\tvarNames.add(s);\n\t\t\t\tvarTypes.add(module.getDeclaration(j).getType());\n\t\t\t\tvarModules.add(i);\n\t\t\t}\n\t\t}\n\n\t\t// check there is at least one variable\n\t\tif (varNames.size() == 0) {\n\t\t\tthrow new PrismLangException(\"There must be at least one variable\");\n\t\t}\n\t}\n\n\t// Check there are no duplicate names labelling reward structs\n\n\tprivate void checkRewardStructNames() throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\tHashSet<String> names = new HashSet<String>();\n\t\tn = getNumRewardStructs();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = getRewardStruct(i).getName();\n\t\t\tif (s != null && !\"\".equals(s))\n\t\t\t\tif (!names.add(s))\n\t\t\t\t\tthrow new PrismLangException(\"Duplicated reward structure name \\\"\" + s + \"\\\"\", getRewardStruct(i));\n\t\t}\n\t}\n\n\t/**\n\t * Check \"system...endsystem\" constructs, if present.\n\t */\n\tprivate void checkSystemDefns() throws PrismLangException\n\t{\n\t\tint n = systemDefns.size();\n\t\t\n\t\t// Check there is a most one un-named system...endsystem...\n\t\t\n\t\t// None is ok\n\t\tif (n == 0)\n\t\t\treturn;\n\t\t// If there are any, at most one should be un-named\n\t\t// and names should be unique \n\t\tint numUnnamed = 0;\n\t\tHashSet<String> names = new HashSet<String>();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = systemDefnNames.get(i); \n\t\t\tif (s == null) {\n\t\t\t\tnumUnnamed++;\n\t\t\t} else {\n\t\t\t\tif (!names.add(s))\n\t\t\t\t\tthrow new PrismLangException(\"Duplicated system...endystem name \\\"\" + s + \"\\\"\", getSystemDefn(i));\n\t\t\t}\n\t\t\tif (numUnnamed > 1)\n\t\t\t\tthrow new PrismLangException(\"There can be at most one un-named system...endsystem construct\", getSystemDefn(i));\n\t\t}\n\n\t\t// Check for cyclic dependencies...\n\t\t\n\t\t// Create boolean matrix of dependencies\n\t\t// (matrix[i][j] is true if prop i contains a ref to prop j)\n\t\tboolean matrix[][] = new boolean[n][n];\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tSystemDefn sys = systemDefns.get(i);\n\t\t\tList<String> v = new ArrayList<>();\n\t\t\tsys.getReferences(v);\n\t\t\tfor (int j = 0; j < v.size(); j++) {\n\t\t\t\tint k = getSystemDefnIndex(v.get(j));\n\t\t\t\tif (k != -1) {\n\t\t\t\t\tmatrix[i][k] = true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Check for and report dependencies\n\t\tint firstCycle = PrismUtils.findCycle(matrix);\n\t\tif (firstCycle != -1) {\n\t\t\tString s = \"Cyclic dependency from references in system...endsystem definition \\\"\" + getSystemDefnName(firstCycle) + \"\\\"\";\n\t\t\tthrow new PrismLangException(s, getSystemDefn(firstCycle));\n\t\t}\n\t}\n\t\n\t/**\n\t * Check definitions of observables,\n\t * and extract/store information about them.\n\t */\n\tprivate void checkObservables() throws PrismLangException\n\t{\n\t\t// Check observable definitions are present/absent, as required\n\t\tif (getModelType().partiallyObservable() && !hasObservables()) {\n\t\t\tthrow new PrismLangException(getModelType() + \"s must specify observables\");\n\t\t}\n\t\tif (hasObservables() && !getModelType().partiallyObservable()) {\n\t\t\tthrow new PrismLangException(getModelType() + \"s cannot specify observables\");\n\t\t}\n\t\t// Extract info about observables from\n\t\t// observable variable lists and/or observable definitions\n\t\tfor (ObservableVars obsVars : observableVarLists) {\n\t\t\tint n = obsVars.getNumVars();\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tif (!(obsVars.getVar(i) instanceof ExpressionVar)) {\n\t\t\t\t\tthrow new PrismLangException(\"Observable variables list can only contain variables\", obsVars.getVar(i));\n\t\t\t\t}\n\t\t\t\tExpressionVar exprVar = (ExpressionVar) obsVars.getVar(i);\n\t\t\t\tString name = exprVar.getName();\n\t\t\t\taddObservable(name, obsVars.getVar(i), exprVar, exprVar);\n\t\t\t}\n\t\t}\n\t\tfor (Observable obs : observableDefns) {\n\t\t\tString name = obs.getName();\n\t\t\tExpressionVar exprVar = null;\n\t\t\tif (obs.getDefinition() instanceof ExpressionVar) {\n\t\t\t\texprVar = (ExpressionVar) obs.getDefinition();\n\t\t\t}\n\t\t\taddObservable(name, obs, obs.getDefinition(), exprVar);\n\t\t}\n\t\t// For real-time models with partial observability (i.e. POPTAs), check that all clocks are observable\n\t\tif (getModelType().partiallyObservable() && getModelType().realTime()) {\n\t\t\tint n = getNumVars();\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tif (getVarDeclaration(i).getDeclType() instanceof DeclarationClock) {\n\t\t\t\t\tif (!observableVars.contains(getVarName(i))) {\n\t\t\t\t\t\tthrow new PrismLangException(\"All clocks in \" + modelType + \"s must be observable\" , getVarDeclaration(i));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Add info about an observable, from an\n\t * observable variable list or observable definition\n\t * @param name Observable name\n\t * @param decl Where the observable is declared\n\t * @param defn Observable definition expression\n\t * @param exprVar If observable is a variable, the variable reference\n\t */\n\tprivate void addObservable(String name, ASTElement decl, Expression defn, ExpressionVar exprVar) throws PrismLangException\n\t{\n\t\tcheckAndAddQuotedIdentifier(name, decl, \"observable\");\n\t\tobservables.add(new Observable(name, defn));\n\t\tobservableNames.add(name);\n\t\tobservableTypes.add(defn.getType());\n\t\tif (exprVar != null) {\n\t\t\tobservableVars.add(exprVar.getName());\n\t\t}\n\t}\n\t\n\t/**\n\t  * Perform any required semantic checks.\n\t  * These checks are done *before* any undefined constants have been defined.\n\t */\n\tprivate void doSemanticChecks() throws PrismLangException\n\t{\n\t\tModulesFileSemanticCheck visitor = new ModulesFileSemanticCheck(this);\n\t\taccept(visitor);\n\t\t\n\t}\n\t\n\t/**\n\t * Perform further semantic checks that can only be done once values\n\t * for any undefined constants have been defined.\n\t */\n\tpublic void doSemanticChecksAfterConstants() throws PrismLangException\n\t{\n\t\tModulesFileSemanticCheckAfterConstants visitor = new ModulesFileSemanticCheckAfterConstants(this);\n\t\taccept(visitor);\n\t}\n\n\t/**\n\t * Get  a list of constants in the model that are undefined\n\t * (\"const int x;\" rather than \"const int x = 1;\") \n\t */\n\tpublic List<String> getUndefinedConstants()\n\t{\n\t\treturn constantList.getUndefinedConstants();\n\t}\n\n\t@Override\n\tpublic void setSomeUndefinedConstants(EvaluateContext ecUndefined) throws PrismLangException\n\t{\n\t\tthis.ecUndefined = ecUndefined == null ? EvaluateContext.create() : EvaluateContext.create(ecUndefined);\n\t\tconstantValues = constantList.evaluateSomeConstants(ecUndefined);\n\t\tec = EvaluateContext.create(constantValues, ecUndefined.getEvaluationMode());\n\t\tdoSemanticChecksAfterConstants();\n\t}\n\n\t/**\n\t * Same as {@link #setSomeUndefinedConstants(Values)}.\n\t * Note: This method no longer throws an exception if some constants are undefined.\n\t * Deprecated: Just use {@link #setSomeUndefinedConstants(Values)}.\n\t * @deprecated\n\t */\n\t@Deprecated\n\tpublic void setUndefinedConstants(Values someValues) throws PrismException\n\t{\n\t\tsetSomeUndefinedConstants(someValues);\n\t}\n\n\t/**\n\t * Check if {@code name} is a *defined* constant in the model,\n\t * i.e. a constant whose value was *not* left unspecified.\n\t */\n\tpublic boolean isDefinedConstant(String name)\n\t{\n\t\treturn constantList.isDefinedConstant(name);\n\t}\n\t\n\t/**\n\t * Get the evaluation context that was used to provide values for undefined constants in the model\n\t * (e.g. via the method {@link #setSomeUndefinedConstants(EvaluateContext)}).\n\t */\n\tpublic EvaluateContext getUndefinedEvaluateContext()\n\t{\n\t\treturn ecUndefined;\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn constantValues;\n\t}\n\n\t@Override\n\tpublic EvaluateContext getEvaluateContext()\n\t{\n\t\treturn ec;\n\t}\n\n\t/**\n\t * Create a State object representing the default initial state of this model.\n\t * If there are potentially multiple initial states (because the model has an\n\t * init...endinit specification), this method returns null.\n\t * Assumes that values for constants (and evaluation mode) have been set for the model.\n\t */\n\tpublic State getDefaultInitialState() throws PrismLangException\n\t{\n\t\tif (initStates != null) {\n\t\t\treturn null;\n\t\t}\n\n\t\t// Create State object\n\t\tState initialState = new State(getNumVars());\n\t\t// Then add values for all globals and all locals, in that order\n\t\tint count = 0;\n\t\tint n = getNumGlobals();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tDeclaration decl = getGlobal(i);\n\t\t\tObject initialValue = decl.getType().castValueTo(decl.getStartOrDefault().evaluate(ec));\n\t\t\tinitialState.setValue(count++, initialValue);\n\t\t}\n\t\tn = getNumModules();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tModule module = getModule(i);\n\t\t\tint n2 = module.getNumDeclarations();\n\t\t\tfor (int j = 0; j < n2; j++) {\n\t\t\t\tDeclaration decl = module.getDeclaration(j);\n\t\t\t\tObject initialValue = decl.getType().castValueTo(decl.getStartOrDefault().evaluate(ec));\n\t\t\t\tinitialState.setValue(count++, initialValue);\n\t\t\t}\n\t\t}\n\n\t\treturn initialState;\n\t}\n\n\t/**\n\t * Create a Values object representing the default initial state of this model.\n\t * Deprecated: Use getDefaultInitialState() instead\n\t * (or new Values(getDefaultInitialState(), modulesFile)).\n\t */\n\t@Deprecated\n\tpublic Values getInitialValues() throws PrismLangException\n\t{\n\t\tState stateInit = getDefaultInitialState();\n\t\treturn (stateInit == null) ? null : new Values(stateInit, this);\n\t}\n\n\t/**\n\t * Recompute all information about variables.\n\t * More precisely... TODO\n\t * Note: This does not re-compute the list of all identifiers used. \n\t */\n\tpublic void recomputeVariableinformation() throws PrismLangException\n\t{\n\t\tint i, n;\n\n\t\t// Recompute lists of all variables and types\n\t\tvarDecls = new ArrayList<>();\n\t\tvarNames = new ArrayList<>();\n\t\tvarTypes = new ArrayList<>();\n\t\tvarModules = new ArrayList<>();\n\t\t// Globals\n\t\tfor (Declaration decl : globals) {\n\t\t\tvarDecls.add(decl);\n\t\t\tvarNames.add(decl.getName());\n\t\t\tvarTypes.add(decl.getType());\n\t\t\tvarModules.add(-1);\n\t\t}\n\t\t// Locals\n\t\tn = modules.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tfor (Declaration decl : getModule(i).getDeclarations()) {\n\t\t\t\tvarDecls.add(decl);\n\t\t\t\tvarNames.add(decl.getName());\n\t\t\t\tvarTypes.add(decl.getType());\n\t\t\t\tvarModules.add(i);\n\t\t\t}\n\t\t}\n\t\t// Find all instances of variables, replace identifiers with variables.\n\t\t// Also check variables valid, store indices, etc.\n\t\tfindAllVars(varNames, varTypes);\n\t}\n\n\t/**\n\t * Create a VarList object storing information about all variables in this model.\n\t * Assumes that values for constants have been provided for the model.\n\t * Also performs various syntactic checks on the variables.   \n\t */\n\tpublic VarList createVarList() throws PrismException\n\t{\n\t\treturn new VarList(this);\n\t}\n\n\t/**\n\t * Determine the actual model type\n\t */\n\tprivate void finaliseModelType() throws PrismLangException\n\t{\n\t\t// First, fix a \"base\" model type\n\t\t// If unspecified, auto-detect\n\t\tif (modelTypeInFile == null) {\n\t\t\tboolean isNonProb = isNonProbabilistic();\n\t\t\tmodelType = isNonProb ? ModelType.LTS : ModelType.MDP;\n\t\t}\n\t\t// Otherwise, it's just whatever was specified\n\t\telse {\n\t\t\tmodelType = modelTypeInFile;\n\t\t}\n\t\t// Then, even if already specified, update the model type\n\t\t// based on the existence of certain features\n\t\tboolean isRealTime = containsClockVariables();\n\t\tboolean isPartObs = hasObservables();\n\t\tboolean isInterval = probabilitiesContainIntervals();\n\t\tif (isRealTime) {\n\t\t\tif (modelType == ModelType.MDP || modelType == ModelType.LTS) {\n\t\t\t\tmodelType = ModelType.PTA;\n\t\t\t}\n\t\t}\n\t\tif (isPartObs) {\n\t\t\tif (modelType == ModelType.MDP || modelType == ModelType.LTS) {\n\t\t\t\tmodelType = ModelType.POMDP;\n\t\t\t} else if (modelType == ModelType.PTA) {\n\t\t\t\tmodelType = ModelType.POPTA;\n\t\t\t}\n\t\t}\n\t\tif (isInterval) {\n\t\t\tif (modelType == ModelType.DTMC) {\n\t\t\t\tmodelType = ModelType.IDTMC;\n\t\t\t} else if (modelType == ModelType.MDP) {\n\t\t\t\tmodelType = ModelType.IMDP;\n\t\t\t} else if (modelType == ModelType.POMDP) {\n\t\t\t\tmodelType = ModelType.IPOMDP;\n\t\t\t} else {\n\t\t\t\tthrow new PrismLangException(\"Intervals only allowed in DTMCs and MDPs currently\");\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns true if one or more of the probabilities in a guarded command contains an interval.\n\t */\n\tpublic boolean probabilitiesContainIntervals()\n\t{\n\t\treturn findIntervalInProbabilities() != null;\n\t}\n\t\n\t/**\n\t * If one or more of the probabilities in a guarded command contains an interval,\n\t * return it; otherwise return null.\n\t */\n\tpublic ASTElement findIntervalInProbabilities()\n\t{\n\t\ttry {\n\t\t\tASTTraverse astt = new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPost(Updates e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tint n = e.getNumUpdates();\n\t\t\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\t\t\tif (e.getProbability(i) != null && e.getProbability(i).getType() instanceof TypeInterval) {\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Found one\", e);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t};\n\t\t\taccept(astt);\n\t\t} catch (PrismLangException e) {\n\t\t\treturn e.getASTElement();\n\t\t}\n\t\treturn null;\n\t}\n\t\n\t/**\n\t * Check whether this model is non-probabilistic,\n\t * i.e., whether none of the commands are probabilistic. \n\t */\n\tprivate boolean isNonProbabilistic()\n\t{\n\t\ttry {\n\t\t\t// Search through commands, checking for probabilities\n\t\t\taccept(new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic Object visit(Updates e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tint n = e.getNumUpdates();\n\t\t\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\t\t\tif (e.getProbability(i) != null) {\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Found one\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tvisitPost(e);\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (PrismLangException e) {\n\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t// Methods required for ASTElement:\n\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\", tmp;\n\t\tint i, n;\n\n\t\tif (modelTypeInFile != null) {\n\t\t\ts += modelTypeInFile.toString().toLowerCase() + \"\\n\\n\";\n\t\t}\n\n\t\ttmp = \"\" + formulaList;\n\t\tif (tmp.length() > 0)\n\t\t\ttmp += \"\\n\";\n\t\ts += tmp;\n\n\t\ttmp = \"\" + labelList;\n\t\tif (tmp.length() > 0)\n\t\t\ttmp += \"\\n\";\n\t\ts += tmp;\n\n\t\ttmp = \"\" + constantList;\n\t\tif (tmp.length() > 0)\n\t\t\ttmp += \"\\n\";\n\t\ts += tmp;\n\n\t\tfor (ObservableVars obsVars : observableVarLists) {\n\t\t\ts += obsVars + \"\\n\\n\";\n\t\t}\n\t\tfor (Observable obs : observableDefns) {\n\t\t\ts += obs + \"\\n\";\n\t\t}\n\t\tif (!observableDefns.isEmpty()) {\n\t\t\ts += \"\\n\";\n\t\t}\n\t\t\n\t\tn = getNumGlobals();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts += \"global \" + getGlobal(i) + \";\\n\";\n\t\t}\n\t\tif (n > 0) {\n\t\t\ts += \"\\n\";\n\t\t}\n\n\t\tfor (i = 0; i < modules.size() - 1; i++) {\n\t\t\ts += modules.get(i) + \"\\n\\n\";\n\t\t}\n\t\ts += modules.get(modules.size() - 1) + \"\\n\";\n\n\t\tfor (i = 0; i < systemDefns.size(); i++) {\n\t\t\ts += \"\\nsystem \";\n\t\t\tif (systemDefnNames.get(i) != null)\n\t\t\t\ts += \"\\\"\" + systemDefnNames.get(i) + \"\\\" \";\n\t\t\ts += systemDefns.get(i) + \" endsystem\\n\";\n\t\t}\n\n\t\tn = getNumRewardStructs();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts += \"\\n\" + getRewardStruct(i);\n\t\t}\n\n\t\tif (initStates != null) {\n\t\t\ts += \"\\n\" + \"init \" + initStates + \" endinit\\n\";\n\t\t}\n\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic ModulesFile deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\t// Deep copy main components\n\t\tlabelList = copier.copy(labelList);\n\t\tformulaList = copier.copy(formulaList);\n\t\tconstantList = copier.copy(constantList);\n\t\tinitStates = copier.copy(initStates);\n\t\tidentUsage = identUsage.deepCopy();\n\t\tquotedIdentUsage = quotedIdentUsage.deepCopy();\n\n\t\tcopier.copyAll(globals);\n\t\tcopier.copyAll(varDecls);\n\t\tcopier.copyAll(systemDefns);\n\t\tcopier.copyAll(observables);\n\t\tcopier.copyAll(rewardStructs);\n\t\tcopier.copyAll(observableDefns);\n\t\tcopier.copyAll(observableVarLists);\n\n\t\tfor (int i = 0, n = getNumModules(); i < n; i++) {\n\t\t\tModule mod = Objects.requireNonNull(getModule(i));\n\t\t\tsetModule(i, copier.copy(mod));\n\t\t}\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic ModulesFile clone()\n\t{\n\t\tModulesFile clone = (ModulesFile) super.clone();\n\n\t\t// clone main components\n\t\tclone.globals            = (ArrayList<Declaration>) globals.clone();\n\t\tclone.modules            = (ArrayList<Object>) modules.clone();\n\t\tclone.systemDefns        = (ArrayList<SystemDefn>) systemDefns.clone();\n\t\tclone.systemDefnNames    = (ArrayList<String>) systemDefnNames.clone();\n\t\tclone.rewardStructs      = (ArrayList<RewardStruct>) rewardStructs.clone();\n\t\tclone.rewardStructNames  = (ArrayList<String>) rewardStructNames.clone();\n\t\tclone.observableVarLists = (ArrayList<ObservableVars>) observableVarLists.clone();\n\t\tclone.observableDefns    = (ArrayList<Observable>) observableDefns.clone();\n\t\tclone.varDecls           = (ArrayList<Declaration>) varDecls.clone();\n\t\tclone.varNames           = (ArrayList<String>) varNames.clone();\n\t\tclone.varTypes           = (ArrayList<Type>) varTypes.clone();\n\t\tclone.varModules         = (ArrayList<Integer>) varModules.clone();\n\t\tclone.observables        = (ArrayList<Observable>) observables.clone();\n\t\tclone.observableNames    = (ArrayList<String>) observableNames.clone();\n\t\tclone.observableTypes    = (ArrayList<Type>) observableTypes.clone();\n\t\tclone.observableVars     = (ArrayList<String>) observableVars.clone();\n\n\t\t// clone other (generated) info\n\t\tif (constantValues != null)\n\t\t\tclone.constantValues = constantValues.clone();\n\t\tif (moduleNames != null)\n\t\t\tclone.moduleNames = moduleNames.clone();\n\t\tif (synchs != null)\n\t\t\tclone.synchs =  (ArrayList<String>) synchs.clone();\n\t\tif (ecUndefined != null)\n\t\t\tecUndefined = EvaluateContext.create(ecUndefined);\n\t\tif (ec != null)\n\t\t\tec = EvaluateContext.create(ec);\n\n\t\treturn clone;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/Observable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class Observable extends ASTElement\n{\n\t/**\n\t * Name of the observable\n\t */\n\tprivate String name;\n\t/**\n\t * Expression defining the observable.\n\t */\n\tprivate Expression definition;\n\t\n\t// Constructor\n\t\n\t/**\n\t * Create a new observable with a given name and definition.\n\t * @param name Name of the observable\n\t * @param expr Expression defining the observable\n\t */\n\tpublic Observable(String name, Expression definition)\n\t{\n\t\tsetName(name);\n\t\tsetDefinition(definition);\n\t}\n\n\t// Set methods\n\t\n\tpublic void setName(String name)\n\t{\n\t\tthis.name = name;\n\t}\n\n\tpublic void setDefinition(Expression definition)\n\t{\n\t\tthis.definition = definition;\n\t}\n\n\t// Get methods\n\t\n\t/**\n\t * Get the name of the observable.\n\t */\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\t/**\n\t * Get the expression defining the observable.\n\t */\n\tpublic Expression getDefinition()\n\t{\n\t\treturn definition;\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\treturn \"observable \\\"\" + name + \"\\\" = \" + definition + \";\";\n\t}\n\t\n\t@Override\n\tpublic Observable deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tdefinition = copier.copy(definition);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic Observable clone()\n\t{\n\t\treturn (Observable) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/ObservableVars.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.stream.Collectors;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n/**\n * A list of variables that are observable\n */\npublic class ObservableVars extends ASTElement\n{\n\t/**\n\t * List of variables (stored as AST elements referencing them)\n\t */\n\tprivate ArrayList<Expression> vars;\n\t\n\t// Constructor\n\t\n\t/**\n\t * Create a new (empty) observable variables list.\n\t */\n\tpublic ObservableVars()\n\t{\n\t\tvars = new ArrayList<>();\n\t}\n\n\t// Mutators\n\t\n\t/**\n\t * Add a variable to the list.\n\t * It is specified via the AST element from the model description,\n\t * e.g. an ExpressionIdent, for improved error reporting.\n\t */\n\tpublic void addVar(Expression exprVar)\n\t{\n\t\tvars.add(exprVar);\n\t}\n\t\n\t/**\n\t * Add a variable to the list, specified by its name.\n\t */\n\tpublic void addVar(String varName)\n\t{\n\t\taddVar(new ExpressionIdent(varName));\n\t}\n\t\n\t/**\n\t * Set the {@code i}th variable in the list.\n\t * It is specified via the AST element from the model description,\n\t * e.g. an ExpressionIdent, for improved error reporting.\n\t */\n\tpublic void setVar(int i, Expression exprVar)\n\t{\n\t\tvars.set(i, exprVar);\n\t}\n\t\n\t// Accessors\n\t\n\t/**\n\t * Get the number of variables in the list.\n\t */\n\tpublic int getNumVars()\n\t{\n\t\treturn vars.size();\n\t}\n\t\n\t/**\n\t * Get the {@code i}th variable in the list.\n\t * Returned as an AST element referring to it.\n\t */\n\tpublic Expression getVar(int i)\n\t{\n\t\treturn vars.get(i);\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"observables\";\n\t\tif (!vars.isEmpty()) {\n\t\t\ts += vars.stream().map(e -> e.toString()).collect(Collectors.joining(\", \", \" \", \"\")) + \"\";\n\t\t}\n\t\ts += \" endobservables\";\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic ObservableVars deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(vars);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic ObservableVars clone()\n\t{\n\t\tObservableVars clone = (ObservableVars) super.clone();\n\t\tclone.vars = (ArrayList<Expression>) vars.clone();\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/PropertiesFile.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.EvaluateContext;\nimport parser.IdentUsage;\nimport parser.Values;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport parser.visitor.PropertiesSemanticCheck;\nimport prism.ModelInfo;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismUtils;\n\n// Class representing parsed properties file/list\n\npublic class PropertiesFile extends ASTElement\n{\n\t// Associated ModulesFile (for constants, ...)\n\tprivate ModulesFile modulesFile;\n\tprivate ModelInfo modelInfo;\n\n\t// Components\n\tprivate FormulaList formulaList;\n\tprivate LabelList labelList;\n\tprivate LabelList combinedLabelList; // Labels from both model/here\n\tprivate ConstantList constantList;\n\tprivate ArrayList<Property> properties; // Properties\n\n\t// Info about all identifiers used\n\tprivate IdentUsage identUsage;\n\tprivate IdentUsage quotedIdentUsage;\n\n\t// Copy of the evaluation context used to defined undefined constants (null if none)\n\tprivate EvaluateContext ecUndefined;\n\t\n\t// Actual values of (some or all) constants\n\tprivate Values constantValues;\n\n\t// Constructor\n\n\tpublic PropertiesFile(ModelInfo modelInfo)\n\t{\n\t\tsetModelInfo(modelInfo);\n\t\tformulaList = new FormulaList();\n\t\tlabelList = new LabelList();\n\t\tcombinedLabelList = new LabelList();\n\t\tconstantList = new ConstantList();\n\t\tproperties = new ArrayList<>();\n\t\tidentUsage = new IdentUsage();\n\t\tquotedIdentUsage = new IdentUsage(true);\n\t\tecUndefined = null;\n\t\tconstantValues = null;\n\t}\n\n\t// Set methods\n\n\t/** Attach model information (so can access labels/constants etc.) */\n\tpublic void setModelInfo(ModelInfo modelInfo)\n\t{\n\t\t// Store ModelInfo. Need a ModulesFile too for now. Create a dummy one if needed.\n\t\tif (modelInfo  == null) {\n\t\t\tthis.modelInfo = this.modulesFile = new ModulesFile();\n\t\t\tthis.modulesFile.setFormulaList(new FormulaList());\n\t\t\tthis.modulesFile.setConstantList(new ConstantList());\n\t\t} else if (modelInfo instanceof ModulesFile) {\n\t\t\tthis.modelInfo = this.modulesFile = (ModulesFile) modelInfo;\n\t\t} else {\n\t\t\tthis.modelInfo = modelInfo;\n\t\t\tthis.modulesFile = new ModulesFile();\n\t\t\tthis.modulesFile.setFormulaList(new FormulaList());\n\t\t\tthis.modulesFile.setConstantList(new ConstantList());\n\t\t}\n\t}\n\n\tpublic void setFormulaList(FormulaList fl)\n\t{\n\t\tformulaList = fl;\n\t}\n\n\tpublic void setLabelList(LabelList ll)\n\t{\n\t\tlabelList = ll;\n\t}\n\n\tpublic void setConstantList(ConstantList cl)\n\t{\n\t\tconstantList = cl;\n\t}\n\n\tpublic void addProperty(Property prop)\n\t{\n\t\tproperties.add(prop);\n\t}\n\n\tpublic void addProperty(Expression p, String c)\n\t{\n\t\tproperties.add(new Property(p, null, c));\n\t}\n\n\tpublic void setPropertyObject(int i, Property prop)\n\t{\n\t\tproperties.set(i, prop);\n\t}\n\n\tpublic void setPropertyExpression(int i, Expression p)\n\t{\n\t\tproperties.get(i).setExpression(p);\n\t}\n\n\t/**\n\t * Insert the contents of another PropertiesFile (just a shallow copy).\n\t */\n\tpublic void insertPropertiesFile(PropertiesFile pf) throws PrismLangException\n\t{\n\t\tFormulaList fl;\n\t\tLabelList ll;\n\t\tConstantList cl;\n\t\tint i, n;\n\t\tfl = pf.formulaList;\n\t\tn = fl.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tformulaList.addFormula(fl.getFormulaNameIdent(i), fl.getFormula(i));\n\t\t}\n\t\tll = pf.labelList;\n\t\tn = ll.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tlabelList.addLabel(ll.getLabelNameIdent(i), ll.getLabel(i));\n\t\t}\n\t\tcl = pf.constantList;\n\t\tn = cl.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tconstantList.addConstant(cl.getConstantNameIdent(i), cl.getConstant(i), cl.getConstantType(i));\n\t\t}\n\t\tn = pf.properties.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tproperties.add(pf.properties.get(i));\n\t\t}\n\t\t// Need to re-tidy (some checks should be re-done, some new info created)\n\t\ttidyUp();\n\t}\n\n\t// Get methods\n\n\tpublic FormulaList getFormulaList()\n\t{\n\t\treturn formulaList;\n\t}\n\n\tpublic LabelList getLabelList()\n\t{\n\t\treturn labelList;\n\t}\n\n\tpublic LabelList getCombinedLabelList()\n\t{\n\t\treturn combinedLabelList;\n\t}\n\n\tpublic ConstantList getConstantList()\n\t{\n\t\treturn constantList;\n\t}\n\n\tpublic int getNumProperties()\n\t{\n\t\treturn properties.size();\n\t}\n\n\tpublic Property getPropertyObject(int i)\n\t{\n\t\treturn properties.get(i);\n\t}\n\n\tpublic Expression getProperty(int i)\n\t{\n\t\treturn properties.get(i).getExpression();\n\t}\n\n\tpublic String getPropertyName(int i)\n\t{\n\t\treturn properties.get(i).getName();\n\t}\n\n\tpublic String getPropertyComment(int i)\n\t{\n\t\treturn properties.get(i).getComment();\n\t}\n\n\t/**\n\t * Look up a property by name from those listed in this properties file.\n\t * (Use {@link #lookUpPropertyObjectByName} to search model file too)\n\t * Returns null if not found.\n\t */\n\tpublic Property getPropertyObjectByName(String name)\n\t{\n\t\tint i, n;\n\t\tn = getNumProperties();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (name.equals(getPropertyName(i))) {\n\t\t\t\treturn getPropertyObject(i);\n\t\t\t}\n\t\t}\n\t\treturn null;\n\t}\n\n\t/**\n\t * Look up the index of a property by name from those listed in this properties file.\n\t * Returns -1 if not found.\n\t */\n\tpublic int getPropertyIndexByName(String name)\n\t{\n\t\tint i, n;\n\t\tn = getNumProperties();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (name.equals(getPropertyName(i))) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Look up a property by name, currently just locally like {@link #getPropertyObjectByName}.\n\t * Returns null if not found.\n\t */\n\tpublic Property lookUpPropertyObjectByName(String name)\n\t{\n\t\treturn getPropertyObjectByName(name);\n\t}\n\n\t/**\n\t * Check if an identifier is already used somewhere here or in the model\n\t * (as a formula, constant or variable)\n\t * and throw an exception if it is. Otherwise, add it to the list.\n\t * @param ident The name of the (new) identifier\n\t * @param decl Where the identifier is declared\n\t * @param use Optionally, the identifier's usage (e.g. \"constant\")\n\t */\n\tprivate void checkAndAddIdentifier(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\t// Check model first\n\t\tmodelInfo.checkIdent(ident, decl, use);\n\t\t// Then check/add here in the properties file\n\t\tidentUsage.checkAndAddIdentifier(ident, decl, use, \"the properties\");\n\t}\n\t\n\t/**\n\t * Check if an identifier is used by this properties file \n\t * (as a formula or constant)\n\t */\n\tpublic boolean isIdentUsed(String ident)\n\t{\n\t\treturn identUsage.isIdentUsed(ident);\n\t}\n\n\t/**\n\t * Check if a quoted identifier is already used somewhere here or in the model\n\t * (as a label or property name)\n\t * and throw an exception if it is. Otherwise, add it to the list.\n\t * @param ident The name of the (new) identifier\n\t * @param decl Where the identifier is declared\n\t * @param use Optionally, the identifier's usage (e.g. \"constant\")\n\t */\n\tprivate void checkAndAddQuotedIdentifier(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\t// Check model first\n\t\tmodelInfo.checkQuotedIdent(ident, decl, use);\n\t\t// Then check/add here in the properties file\n\t\tquotedIdentUsage.checkAndAddIdentifier(ident, decl, use, \"the properties\");\n\t}\n\t\n\t// method to tidy up (called after parsing)\n\n\tpublic void tidyUp() throws PrismLangException\n\t{\n\t\t// Clear data that will generated by this method \n\t\t// (in case it has already been called previously).\n\t\tidentUsage.clear();\n\n\t\t// Check formula identifiers\n\t\tcheckFormulaIdents();\n\t\t// Find all instances of formulas (i.e. locate idents which are formulas),\n\t\t// check for any cyclic dependencies in the formula list and then expand all formulas.\n\t\t// Note: We have to look for formulas defined both here and in the model.\n\t\t// Note also that we opt not to do actual replacement of formulas in calls to exandFormulas\n\t\t// (to improve legibility of properties)\n\t\tfindAllFormulas(modulesFile.getFormulaList());\n\t\tfindAllFormulas(formulaList);\n\t\tformulaList.findCycles();\n\t\texpandFormulas(modulesFile.getFormulaList(), false);\n\t\texpandFormulas(formulaList, false);\n\n\t\t// Check label identifiers\n\t\tcheckLabelIdents();\n\n\t\t// Check constant identifiers\n\t\tcheckConstantIdents();\n\t\t// Find all instances of constants (i.e. locate idents which are constants).\n\t\t// Note: We have to look in both constant lists\n\t\tfindAllConstants(modulesFile.getConstantList());\n\t\tfindAllConstants(constantList);\n\t\t// check constants for cyclic dependencies\n\t\tconstantList.findCycles();\n\n\t\t// Check property names\n\t\tcheckPropertyNames();\n\n\t\t// Find all instances of variables (i.e. locate idents which are variables).\n\t\tfindAllVars(modelInfo.getVarNames(), modelInfo.getVarTypes());\n\n\t\t// Find all references to observables (i.e. locate \"labels\" which are observables).\n\t\tfindAllObsRefs(modelInfo.getObservableNames(), modelInfo.getObservableTypes());\n\t\t\n\t\t// Find all instances of property refs\n\t\tfindAllPropRefs(null, this);\n\t\t// Check property references for cyclic dependencies\n\t\tfindCyclesInPropertyReferences();\n\n\t\t// Various semantic checks \n\t\tdoSemanticChecks();\n\t\t// Type checking\n\t\ttypeCheck(this);\n\n\t\t// Set up some values for constants\n\t\t// (without assuming any info about undefined constants)\n\t\t// NB: we use non-exact constant evaluation by default,\n\t\t// for exact mode constants will be reevaluated later on\n\t\tsetSomeUndefinedConstants(EvaluateContext.create());\n\t}\n\n\t// check formula identifiers\n\n\tprivate void checkFormulaIdents() throws PrismLangException\n\t{\n\t\tint n = formulaList.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = formulaList.getFormulaName(i);\n\t\t\tcheckAndAddIdentifier(s, formulaList.getFormulaNameIdent(i), \"formula\");\n\t\t}\n\t}\n\n\t// check label identifiers\n\t// also check reference to these identifiers in properties\n\n\tprivate void checkLabelIdents() throws PrismLangException\n\t{\n\t\t// check for identifier clashes\n\t\tint n = labelList.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = labelList.getLabelName(i);\n\t\t\tcheckAndAddQuotedIdentifier(s, labelList.getLabelNameIdent(i), \"label\");\n\t\t}\n\t\t\n\t\t// build combined label list\n\t\tcombinedLabelList = new LabelList();\n\t\t// first add model file labels to combined label list (cloning them just for good measure)\n\t\tLabelList mfLabels = modulesFile.getLabelList();\n\t\tn = mfLabels.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tcombinedLabelList.addLabel(mfLabels.getLabelNameIdent(i), mfLabels.getLabel(i).deepCopy());\n\t\t}\n\t\t// then add labels from here\n\t\tn = labelList.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tcombinedLabelList.addLabel(labelList.getLabelNameIdent(i), labelList.getLabel(i));\n\t\t}\n\t}\n\n\t// check constant identifiers\n\n\tprivate void checkConstantIdents() throws PrismLangException\n\t{\n\t\t// go thru constants\n\t\tint n = constantList.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = constantList.getConstantName(i);\n\t\t\tcheckAndAddIdentifier(s, constantList.getConstantNameIdent(i), \"constant\");\n\t\t}\n\t}\n\n\t/**\n\t * Check for any duplicate property names (or clashes with labels).\n\t */\n\tprivate void checkPropertyNames() throws PrismLangException\n\t{\n\t\tint n = properties.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tString s = properties.get(i).getName();\n\t\t\tif (s != null) {\n\t\t\t\tcheckAndAddQuotedIdentifier(s, getPropertyObject(i), \"property\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Find cyclic dependencies in property references.\n\t */\n\tpublic void findCyclesInPropertyReferences() throws PrismLangException\n\t{\n\t\t// Create boolean matrix of dependencies\n\t\t// (matrix[i][j] is true if prop i contains a ref to prop j)\n\t\tint n = properties.size();\n\t\tboolean matrix[][] = new boolean[n][n];\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tExpression e = properties.get(i).getExpression();\n\t\t\tList<String> v = e.getAllPropRefs();\n\t\t\tfor (int j = 0; j < v.size(); j++) {\n\t\t\t\tint k = getPropertyIndexByName(v.get(j));\n\t\t\t\tif (k != -1) {\n\t\t\t\t\tmatrix[i][k] = true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Check for and report dependencies\n\t\tint firstCycle = PrismUtils.findCycle(matrix);\n\t\tif (firstCycle != -1) {\n\t\t\tString s = \"Cyclic dependency in property references from property \\\"\" + getPropertyName(firstCycle) + \"\\\"\";\n\t\t\tthrow new PrismLangException(s, getPropertyObject(firstCycle));\n\t\t}\n\t}\n\n\t/**\n\t  * Perform any required semantic checks.\n\t  * These checks are done *before* any undefined constants have been defined.\n\t */\n\tprivate void doSemanticChecks() throws PrismLangException\n\t{\n\t\tPropertiesSemanticCheck visitor = new PropertiesSemanticCheck(this, modelInfo);\n\t\taccept(visitor);\n\t}\n\n\t/**\n\t * Get a list of all undefined constants in the properties files\n\t * (\"const int x;\" rather than \"const int x = 1;\") \n\t */\n\tpublic List<String> getUndefinedConstants()\n\t{\n\t\treturn constantList.getUndefinedConstants();\n\t}\n\n\t/**\n\t * Get a list of undefined (properties file) constants appearing in labels of the properties file\n\t * (including those that appear in definitions of other needed constants)\n\t * (undefined constants are those of form \"const int x;\" rather than \"const int x = 1;\")\n\t */\n\tpublic List<String> getUndefinedConstantsUsedInLabels()\n\t{\n\t\tint i, n;\n\t\tExpression expr;\n\t\tList<String> consts, tmp;\n\t\tconsts = new ArrayList<>();\n\t\tn = labelList.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\texpr = labelList.getLabel(i);\n\t\t\ttmp = expr.getAllUndefinedConstantsRecursively(constantList, combinedLabelList, null);\n\t\t\tfor (String s : tmp) {\n\t\t\t\tif (!consts.contains(s)) {\n\t\t\t\t\tconsts.add(s);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn consts;\n\t}\n\n\t/**\n\t * Get a list of undefined (properties file) constants used in a property\n\t * (including those that appear in definitions of other needed constants and labels/properties)\n\t * (undefined constants are those of form \"const int x;\" rather than \"const int x = 1;\") \n\t */\n\tpublic List<String> getUndefinedConstantsUsedInProperty(Property prop)\n\t{\n\t\treturn prop.getExpression().getAllUndefinedConstantsRecursively(constantList, combinedLabelList, this);\n\t}\n\n\t/**\n\t * Get a list of undefined (properties file) constants used in a list of properties\n\t * (including those that appear in definitions of other needed constants and labels/properties)\n\t * (undefined constants are those of form \"const int x;\" rather than \"const int x = 1;\") \n\t */\n\tpublic List<String> getUndefinedConstantsUsedInProperties(List<Property> props)\n\t{\n\t\tList<String> consts, tmp;\n\t\tconsts = new ArrayList<>();\n\t\tfor (Property prop : props) {\n\t\t\ttmp = prop.getExpression().getAllUndefinedConstantsRecursively(constantList, combinedLabelList, this);\n\t\t\tfor (String s : tmp) {\n\t\t\t\tif (!consts.contains(s)) {\n\t\t\t\t\tconsts.add(s);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn consts;\n\t}\n\n\t/**\n\t * Set values for some undefined constants.\n\t * The values being provided for these constants, as well as any other constants needed,\n\t * are provided in an EvaluateContext object. This also determines the evaluation mode.\n\t * If there are no undefined constants, {@code ecUndefined} can be null.\n\t * Undefined constants can be subsequently redefined to different values with the same method.\n\t * This may result in the values for other model constants now being known;\n\t * the values for all current constant values (if set) are available via {@link #getConstantValues()}.\n\t */\n\tpublic void setSomeUndefinedConstants(EvaluateContext ecUndefined) throws PrismLangException\n\t{\n\t\tthis.ecUndefined = ecUndefined == null ? EvaluateContext.create() : EvaluateContext.create(ecUndefined);\n\t\t// Might need values for ModulesFile constants too\n\t\tEvaluateContext ecUndefinedPlusMF = EvaluateContext.create(this.ecUndefined).addConstantValues(modulesFile.getConstantValues());\n\t\tconstantValues = constantList.evaluateSomeConstants(ecUndefinedPlusMF);\n\t\t// Note: unlike ModulesFile, we don't trigger any semantic checks at this point\n\t\t// This will usually be done on a per-property basis later\n\t}\n\n\t/**\n\t * Set values for some undefined constants.\n\t * It is preferable to use {@link #setSomeUndefinedConstants(EvaluateContext)} instead.\n\t * By default, this method creates an {@link EvaluateContext} via {@link EvaluateContext#create(someValues)}.\n\t * If this will be called frequently, it is better to maintain your own {@link EvaluateContext}.\n\t * Also, this method can only handle the default (floating point) evaluation mode.\n\t */\n\tpublic void setSomeUndefinedConstants(Values someValues) throws PrismException\n\t{\n\t\tsetSomeUndefinedConstants(EvaluateContext.create(someValues));\n\t}\n\n\t/**\n\t * Set values for some undefined constants.\n\t * Deprecated. Better to use {@link #setSomeUndefinedConstants(EvaluateContext)}.\n\t * @deprecated\n\t */\n\t@Deprecated\n\tpublic void setSomeUndefinedConstants(Values someValues, boolean exact) throws PrismException\n\t{\n\t\tsetSomeUndefinedConstants(EvaluateContext.create(someValues, exact));\n\t}\n\n\t/**\n\t * Same as {@link #setSomeUndefinedConstants(Values)}.\n\t * Note: This method no longer throws an exception if some constants are undefined.\n\t * Deprecated: Just use {@link #setSomeUndefinedConstants(Values)}.\n\t * @deprecated\n\t */\n\t@Deprecated\n\tpublic void setUndefinedConstants(Values someValues) throws PrismException\n\t{\n\t\tsetSomeUndefinedConstants(someValues);\n\t}\n\n\t/**\n\t * Check if {@code name} is a *defined* constant in the properties file,\n\t * i.e. a constant whose value was *not* left unspecified.\n\t */\n\tpublic boolean isDefinedConstant(String name)\n\t{\n\t\treturn constantList.isDefinedConstant(name);\n\t}\n\n\t/**\n\t * Get the evaluation context that was used to provide values for undefined constants in the model\n\t * (e.g. via the method {@link #setSomeUndefinedConstants(EvaluateContext)}).\n\t */\n\tpublic EvaluateContext getUndefinedEvaluateContext()\n\t{\n\t\treturn ecUndefined;\n\t}\n\n\t/**\n\t * Get access to the values for all constants in the properties file, including the\n\t * undefined constants set previously via the method {@link #setSomeUndefinedConstants(Values)}\n\t * If this has been called, constant values will have been evaluated assuming that there are no undefined constants.\n\t */\n\tpublic Values getConstantValues()\n\t{\n\t\treturn constantValues;\n\t}\n\n\t// Methods required for ASTElement:\n\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\", tmp;\n\t\tint i, n;\n\n\t\ttmp = \"\" + formulaList;\n\t\tif (tmp.length() > 0)\n\t\t\ttmp += \"\\n\";\n\t\ts += tmp;\n\n\t\ttmp = \"\" + labelList;\n\t\tif (tmp.length() > 0)\n\t\t\ttmp += \"\\n\";\n\t\ts += tmp;\n\n\t\ttmp = \"\" + constantList;\n\t\tif (tmp.length() > 0)\n\t\t\ttmp += \"\\n\";\n\t\ts += tmp;\n\n\t\tn = getNumProperties();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts += getPropertyObject(i) + \";\\n\";\n\t\t\tif (i < n - 1)\n\t\t\t\ts += \"\\n\";\n\t\t}\n\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic PropertiesFile deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tquotedIdentUsage = new IdentUsage(true);\n\t\tlabelList = copier.copy(labelList);\n\t\tformulaList = copier.copy(formulaList);\n\t\tconstantList = copier.copy(constantList);\n\t\tcombinedLabelList = copier.copy(combinedLabelList);\n\t\tidentUsage = identUsage.deepCopy();\n\n\t\tcopier.copyAll(properties);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic PropertiesFile clone()\n\t{\n\t\tPropertiesFile clone = (PropertiesFile) super.clone();\n\n\t\t// clone main components\n\t\tclone.properties = (ArrayList<Property>) properties.clone();\n\n\t\t// clone other (generated) info\n\t\tif (constantValues != null)\n\t\t\tclone.constantValues = constantValues.clone();\n\t\tif (ecUndefined != null)\n\t\t\tecUndefined = EvaluateContext.create(ecUndefined);\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/Property.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.regex.Matcher;\nimport java.util.regex.Pattern;\n\nimport param.BigRational;\nimport parser.Values;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.DefinedConstant;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismUtils;\nimport prism.Result;\nimport prism.ResultTesting;\n\n/**\n * PRISM property, i.e. a PRISM expression plus other (optional info) such as name, comment, etc.\n */\npublic class Property extends ASTElement\n{\n\t/** PRISM expression representing property */\n\tprivate Expression expr;\n\t/** Optional name for property (null if absent); */\n\tprivate String name;\n\t/** Optional comment for property (null if absent); */\n\tprivate String comment;\n\n\t// Constructors\n\n\tpublic Property(Expression expr)\n\t{\n\t\tthis(expr, null, null);\n\t}\n\n\tpublic Property(Expression expr, String name)\n\t{\n\t\tthis(expr, name, null);\n\t}\n\n\tpublic Property(Expression expr, String name, String comment)\n\t{\n\t\tthis.expr = expr;\n\t\tthis.name = name;\n\t\tthis.comment = comment;\n\t}\n\n\t// Mutators\n\n\tpublic void setExpression(Expression expr)\n\t{\n\t\tthis.expr = expr;\n\t}\n\n\tpublic void setName(String name)\n\t{\n\t\tthis.name = name;\n\t}\n\n\tpublic void setComment(String comment)\n\t{\n\t\tthis.comment = comment;\n\t}\n\n\t// Accessors\n\n\tpublic Expression getExpression()\n\t{\n\t\treturn expr;\n\t}\n\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\n\tpublic String getComment()\n\t{\n\t\treturn comment;\n\t}\n\n\t/**\n\t * Tests a result against the expected result for this Property, specified by an embedded \"RESULT: xxx\"\n\t * string in the accompanying comment (immediately preceding it in the property specification).\n\t * Different results for different constant values are specified by e.g. \"RESULT (x=1): xxx\".\n\t * The result should ideally be passed in as a {@link prism.Result} object, but can also\n\t * be given directly as an object of the appropriate type: Boolean, Double, etc.)\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * Otherwise, the method successfully exits, returning a boolean value that indicates\n\t * whether or not a check was actually applied (i.e. if the result specification is of the\n\t * form \"RESULT: ?\") then false is returned; otherwise true.\n\t * @param result The actual result\n\t * @return Whether or not the check was performed\n\t */\n\tpublic boolean checkAgainstExpectedResult(Object result) throws PrismException\n\t{\n\t\treturn checkAgainstExpectedResult(result, null);\n\t}\n\n\t/**\n\t * Tests a result against the expected result for this Property, specified by an embedded \"RESULT: xxx\"\n\t * string in the accompanying comment (immediately preceding it in the property specification).\n\t * Different results for different constant values are specified by e.g. \"RESULT (x=1): xxx\".\n\t * The result should ideally be passed in as a {@link prism.Result} object, but can also\n\t * be given directly as an object of the appropriate type: Boolean, Double, etc.)\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * Otherwise, the method successfully exits, returning a boolean value that indicates\n\t * whether or not a check was actually applied (i.e. if the result specification is of the\n\t * form \"RESULT: ?\") then false is returned; otherwise true.\n\t * @param result The actual result\n\t * @param constValues The values of any constants (null if none)\n\t * @return Whether or not the check was performed\n\t */\n\tpublic boolean checkAgainstExpectedResult(Object result, Values constValues) throws PrismException\n\t{\n\t\treturn checkAgainstExpectedResult(result, constValues, null);\n\t}\n\n\t/**\n\t * Tests a result against the expected result for this Property, specified by an embedded \"RESULT: xxx\"\n\t * string in the accompanying comment (immediately preceding it in the property specification).\n\t * Different results for different constant values are specified by e.g. \"RESULT (x=1): xxx\".\n\t * The result should ideally be passed in as a {@link prism.Result} object, but can also\n\t * be given directly as an object of the appropriate type: Boolean, Double, etc.)\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * Otherwise, the method successfully exits, returning a boolean value that indicates\n\t * whether or not a check was actually applied (i.e. if the result specification is of the\n\t * form \"RESULT: ?\") then false is returned; otherwise true.\n\t * @param result The actual result\n\t * @param constValues The values of any constants (null if none)\n\t * @param params The names of any parameters, for \"symbolic\" results (null if none)\n\t * @return Whether or not the check was performed\n\t */\n\tpublic boolean checkAgainstExpectedResult(Object result, Values constValues, List<String> params) throws PrismException\n\t{\n\t\tResult resultObj = (result instanceof Result) ? ((Result) result) : new Result(result);\n\t\tString strExpected = getExpectedResultString(constValues);\n\t\treturn ResultTesting.checkAgainstExpectedResultString(strExpected, constValues, params, expr.getType(), resultObj);\n\t}\n\n\t/**\n\t * Get the expected result by extracting from the appropriate RESULT annotation.\n\t * This is done by finding the first RESULT whose constant values (if any) all match those\n\t * provided in {@code constValues}. A PrismException is thrown if no matching RESULT is found.\n\t * @param constValues The values of any constants (null if none)\n\t */\n\tprivate String getExpectedResultString(Values constValues) throws PrismException\n\t{\n\t\tString strExpected = null;\n\n\t\t// Extract expected result(s) from comment\n\t\tif (comment != null) {\n\t\t\t// Look for \"RESULT: val\" or \"RESULT (x=1,y=2): val\"\n\t\t\tPattern p = Pattern.compile(\"RESULT[ \\t]*(\\\\(([^\\\\)]+)\\\\))?[ \\t]*:[ \\t]*([^ \\t\\n\\r]+)\");\n\t\t\tMatcher matcher = p.matcher(comment);\n\t\t\t// Look at each RESULT specification found\n\t\t\twhile (matcher.find()) {\n\t\t\t\tString constValsSubstring = matcher.group(2) == null ? \"\" : matcher.group(2);\n\t\t\t\tboolean allMatch = true;\n\t\t\t\t// Look at each constant in the list\n\t\t\t\tString ss[] = constValsSubstring.split(\",\");\n\t\t\t\tfor (String s : ss) {\n\t\t\t\t\tboolean match = true;\n\t\t\t\t\ts = s.trim();\n\t\t\t\t\tif (s.length() == 0)\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\tString pair[] = s.split(\"=\");\n\t\t\t\t\tif (pair.length != 2)\n\t\t\t\t\t\tthrow new PrismException(\"Badly formed RESULT specification \\\"\" + matcher.group() + \"\\\"\");\n\t\t\t\t\t// Make sure constant/value is in constValues list and matches\n\t\t\t\t\tString constName = pair[0].trim();\n\t\t\t\t\tString constVal = pair[1].trim();\n\n\t\t\t\t\tObject constValToMatch;\n\t\t\t\t\tif (constValues.getIndexOf(constName) == -1) {\n\t\t\t\t\t\t// there is no constant of that name, might be a parametric constant\n\t\t\t\t\t\tconstValToMatch = null;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tconstValToMatch = constValues.getValueOf(constName);\n\t\t\t\t\t}\n\t\t\t\t\tif (constValToMatch == null)\n\t\t\t\t\t\tmatch = false;\n\t\t\t\t\t// Check doubles numerically\n\t\t\t\t\telse if (constValToMatch instanceof Double)\n\t\t\t\t\t\tmatch = PrismUtils.doublesAreEqual(((Double) constValToMatch).doubleValue(), DefinedConstant.parseDouble(constVal));\n\t\t\t\t\t// if constant is exact rational number, compare exactly\n\t\t\t\t\telse if (constValToMatch instanceof BigRational)\n\t\t\t\t\t\tmatch = BigRational.from(constVal).equals(constValToMatch);\n\t\t\t\t\t// Otherwise just check for exact string match for now\n\t\t\t\t\telse\n\t\t\t\t\t\tmatch = constValToMatch.toString().equals(constVal);\n\n\t\t\t\t\t// We need all constants to match\n\t\t\t\t\tallMatch &= match;\n\t\t\t\t}\n\t\t\t\t// Found it...\n\t\t\t\tif (allMatch) {\n\t\t\t\t\tstrExpected = matcher.group(3);\n\t\t\t\t\t// we return the expected answer for the first RESULT that matches\n\t\t\t\t\t// the constants\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (strExpected == null) {\n\t\t\tthrow new PrismException(\"Did not find a RESULT specification (for \" + constValues + \") to test against\");\n\t\t}\n\n\t\treturn strExpected;\n\t}\n\n\t/**\n\t * Get the expected result by extracting from the appropriate RESULT annotation.\n\t * This is done by an exact string match against the provided string of constant values.\n\t * A PrismException is thrown if no matching RESULT is found.\n\t * This method actually looks at all RESULTs and complains if there multiple matches. \n\t * @param constValues The values of any constants (null or \"\" if none)\n\t */\n\t@SuppressWarnings(\"unused\")\n\tprivate String getExpectedResultString(String constValues) throws PrismException\n\t{\n\t\tHashMap<String, String> strExpectedMap = new HashMap<String, String>();\n\t\tString strExpected = null;\n\n\t\t// Extract expected result(s) from comment\n\t\tif (comment != null) {\n\t\t\t// Look for \"RESULT: val\" or \"RESULT (x=1,y=2): val\"\n\t\t\tPattern p = Pattern.compile(\"RESULT[ \\t]*(\\\\(([^\\\\)]+)\\\\))?[ \\t]*:[ \\t]*([^ \\t\\n\\r]+)\");\n\t\t\tMatcher matcher = p.matcher(comment);\n\t\t\t// Store RESULT specifications found\n\t\t\twhile (matcher.find()) {\n\t\t\t\tString constValsSubstring = matcher.group(2) == null ? \"\" : matcher.group(2);\n\t\t\t\tString expResultSubstring = matcher.group(3);\n\t\t\t\t// Error if there are dupes \n\t\t\t\tif (strExpectedMap.put(constValsSubstring, expResultSubstring) != null) {\n\t\t\t\t\tif (constValsSubstring.length() == 0)\n\t\t\t\t\t\tthrow new PrismException(\"Multiple RESULT specificiations for test\");\n\t\t\t\t\telse\n\t\t\t\t\t\tthrow new PrismException(\"Multiple RESULT (\" + constValsSubstring + \") specificiations for test\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (strExpectedMap.size() == 0) {\n\t\t\tthrow new PrismException(\"Did not find any RESULT specifications to test against\");\n\t\t}\n\t\t// Look up result for the constant values provided\n\t\tstrExpected = strExpectedMap.get(constValues);\n\t\tif (strExpected == null) {\n\t\t\tthrow new PrismException(\"Did not find a RESULT specification (for \" + constValues + \") to test against\");\n\t\t}\n\n\t\treturn strExpected;\n\t}\n\n\t// Methods required for ASTElement:\n\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\t// Note: don't print comment\n\t\tString s = \"\";\n\t\t//if (comment != null)\n\t\t//s += PrismParser.slashCommentBlock(comment);\n\t\tif (name != null)\n\t\t\ts += \"\\\"\" + name + \"\\\": \";\n\t\ts += expr;\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic Property deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\texpr = copier.copy(expr);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic Property clone()\n\t{\n\t\treturn (Property) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/RelOp.java",
    "content": "package parser.ast;\n\nimport prism.PrismLangException;\n\n/**\n * Class to represent a relational operator (or similar) found in a P/R/S operator.\n */\npublic enum RelOp\n{\n\tGT(\">\") {\n\t\t@Override\n\t\tpublic boolean isLowerBound()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isStrict()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn (keepStrictness ? LT : LEQ);\n\t\t}\n\t},\n\tGEQ(\">=\") {\n\t\t@Override\n\t\tpublic boolean isLowerBound()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn (keepStrictness ? LEQ : LT);\n\t\t}\n\t},\n\tMIN(\"min=\") {\n\t\t@Override\n\t\tpublic boolean isMin()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn MAX;\n\t\t}\n\t},\n\tMINMAX(\"minmax=\") {\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn MAXMIN;\n\t\t}\n\t},\n\tMINMIN(\"minmin=\") {\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn MAXMAX;\n\t\t}\n\t},\n\tLT(\"<\") {\n\t\t@Override\n\t\tpublic boolean isUpperBound()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isStrict()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn (keepStrictness ? GT : GEQ);\n\t\t}\n\t},\n\tLEQ(\"<=\") {\n\t\t@Override\n\t\tpublic boolean isUpperBound()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn (keepStrictness ? GEQ : GT);\n\t\t}\n\t},\n\tMAX(\"max=\") {\n\t\t@Override\n\t\tpublic boolean isMax()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn MIN;\n\t\t}\n\t},\n\tMAXMAX(\"maxmax=\") {\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn MINMIN;\n\t\t}\n\t},\n\tMAXMIN(\"maxmin=\") {\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\treturn MINMAX;\n\t\t}\n\t},\n\tEQ(\"=\") {\n\t\t@Override\n\t\tpublic RelOp negate(boolean keepStrictness) throws PrismLangException\n\t\t{\n\t\t\tthrow new PrismLangException(\"Cannot negate \" + this);\n\t\t}\n\t};\n\n\tprivate final String symbol;\n\n\tprivate RelOp(String symbol)\n\t{\n\t\tthis.symbol = symbol;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn symbol;\n\t}\n\n\t/**\n\t * Returns true if this corresponds to a lower bound (i.e. &gt;, &gt;=).\n\t * NB: \"min=?\" does not return true for this.\n\t */\n\tpublic boolean isLowerBound()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Returns true if this corresponds to an upper bound (i.e. &lt;, &lt;=).\n\t * NB: \"max=?\" does not return true for this.\n\t */\n\tpublic boolean isUpperBound()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Returns true if this is a strict bound (i.e. &lt; or &gt;).\n\t */\n\tpublic boolean isStrict()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Returns true if this corresponds to minimum (min=?).\n\t */\n\tpublic boolean isMin()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Returns true if this corresponds to maximum (max=?).\n\t */\n\tpublic boolean isMax()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Returns the negated form of this operator.\n\t * <br>\n\t * Equivalent to {@code negate(false)}.\n\t */\n\tpublic RelOp negate() throws PrismLangException\n\t{\n\t\treturn negate(false);\n\t}\n\n\t/**\n\t * Returns the negated form of this operator.\n\t * Depending on the flag {@code keepStrictness},\n\t * the strictness is preserved. E.g., with\n\t * {@code keepStrictness == true} the operator \"&lt;\"\n\t * is turned into \"&gt;\", with {@code keepStrictness == false}\n\t * the operator \"&lt;\" is turned into \"&gt=;\"\n\t */\n\tpublic abstract RelOp negate(boolean keepStrictness) throws PrismLangException;\n\n\t/**\n\t * Returns the RelOp object corresponding to a (string) symbol,\n\t * e.g. parseSymbol(\"&lt;=\") returns RelOp.LEQ. Returns null if invalid.\n\t * @param symbol The symbol to look up\n\t * @return\n\t */\n\tpublic static RelOp parseSymbol(String symbol)\n\t{\n\t\tfor (RelOp relop : RelOp.values()) {\n\t\t\tif (relop.toString().equals(symbol)) {\n\t\t\t\treturn relop;\n\t\t\t}\n\t\t}\n\t\treturn null;\n\t}\n}"
  },
  {
    "path": "prism/src/parser/ast/RenamedModule.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\nimport java.util.ArrayList;\n\npublic class RenamedModule extends ASTElement\n{\n\t// Rename info\n\tprivate String name;\n\tprivate String baseModule;\n\tprivate ArrayList<String> oldNames;\n\tprivate ArrayList<String> newNames;\n\t// AST elements (for positional info)\n\tprivate ExpressionIdent nameASTElement;\n\tprivate ExpressionIdent baseModuleASTElement;\n\tprivate ArrayList<ExpressionIdent> oldNameASTElements;\n\tprivate ArrayList<ExpressionIdent> newNameASTElements;\n\t\n\t// Constructor\n\t\n\tpublic RenamedModule(String n, String b)\n\t{\n\t\tname = n;\n\t\tbaseModule = b;\n\t\toldNames = new ArrayList<String>();\n\t\tnewNames = new ArrayList<String>();\n\t\toldNameASTElements = new ArrayList<ExpressionIdent>();\n\t\tnewNameASTElements = new ArrayList<ExpressionIdent>();\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void setName(String n)\n\t{\n\t\tname = n;\n\t}\n\n\tpublic void setBaseModule(String b)\n\t{\n\t\tbaseModule = b;\n\t}\n\t\n\tpublic void setNameASTElement(ExpressionIdent e)\n\t{\n\t\tnameASTElement = e;\n\t}\n\t\n\tpublic void setBaseModuleASTElement(ExpressionIdent e)\n\t{\n\t\tbaseModuleASTElement = e;\n\t}\n\t\n\tpublic void addRename(String s1, String s2)\n\t{\n\t\taddRename(s1, s2, null, null);\n\t}\n\t\t\n\tpublic void addRename(String s1, String s2, ExpressionIdent e1, ExpressionIdent e2)\n\t{\n\t\toldNames.add(s1);\n\t\tnewNames.add(s2);\n\t\toldNameASTElements.add(e1);\n\t\tnewNameASTElements.add(e2);\n\t}\n\t\t\n\t// Get methods\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\tpublic String getBaseModule()\n\t{\n\t\treturn baseModule;\n\t}\n\n\tpublic String getNewName(String s)\n\t{\n\t\tint i = oldNames.indexOf(s);\n\t\tif (i == -1) {\n\t\t\treturn null;\n\t\t}\n\t\treturn newNames.get(i);\n\t}\n\t\t\n\tpublic String getOldName(String s)\n\t{\n\t\tint i = newNames.indexOf(s);\n\t\tif (i == -1) {\n\t\t\treturn null;\n\t\t}\n\t\treturn oldNames.get(i);\n\t}\n\t\n\tpublic int getNumRenames()\n\t{\n\t\treturn oldNames.size();\n\t}\n\t\n\tpublic String getOldName(int i)\n\t{\n\t\treturn oldNames.get(i); \n\t}\n\t\n\tpublic String getNewName(int i)\n\t{\n\t\treturn newNames.get(i); \n\t}\n\t\n\tpublic ExpressionIdent getNameASTElement()\n\t{\n\t\treturn nameASTElement;\n\t}\n\t\n\tpublic ExpressionIdent getBaseModuleASTElement()\n\t{\n\t\treturn baseModuleASTElement;\n\t}\n\t\n\tpublic ExpressionIdent getOldNameASTElement(int i)\n\t{\n\t\treturn oldNameASTElements.get(i);\n\t}\n\t\n\tpublic ExpressionIdent getNewNameASTElement(int i)\n\t{\n\t\treturn newNameASTElements.get(i);\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tint i;\n\t\t\n\t\ts = s + \"module \" + name + \" = \" + baseModule + \" [\";\n\t\tfor (i = 0; i < oldNames.size() - 1; i++) {\n\t\t\ts = s + oldNames.get(i) + \" = \" + newNames.get(i) + \", \";\n\t\t}\n\t\ti = oldNames.size() - 1;\n\t\ts = s + oldNames.get(i) + \" = \" + newNames.get(i) + \"] endmodule\";\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic RenamedModule deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic RenamedModule clone()\n\t{\n\t\tRenamedModule clone = (RenamedModule) super.clone();\n\n\t\tclone.newNameASTElements = (ArrayList<ExpressionIdent>) newNameASTElements.clone();\n\t\tclone.newNames           = (ArrayList<String>) newNames.clone();\n\t\tclone.oldNameASTElements = (ArrayList<ExpressionIdent>) oldNameASTElements.clone();\n\t\tclone.oldNames           = (ArrayList<String>) oldNames.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/RewardStruct.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class RewardStruct extends ASTElement\n{\n\tprivate String name;\t\t// name (optional)\n\tprivate ArrayList<RewardStructItem> items;\t\t// list of items\n\tprivate int numStateItems;\t// how may of the items are state rewards\n\tprivate int numTransItems;\t// how may of the items are transition rewards\n\t\n\t// Constructor\n\t\n\tpublic RewardStruct()\n\t{\n\t\tname = \"\";\n\t\titems = new ArrayList<>();\n\t\tnumStateItems = 0;\n\t\tnumTransItems = 0;\n\t}\n\n\tpublic void setName(String n)\n\t{\n\t\tname = n;\n\t}\n\n\t// Set methods\n\t\n\tpublic void addItem(String synch, Expression states, Expression reward)\n\t{\n\t\taddItem(new RewardStructItem(synch, states, reward));\n\t}\n\t\n\tpublic void addItem(RewardStructItem rsi)\n\t{\n\t\titems.add(rsi);\n\t\tif (rsi.isTransitionReward()) numTransItems++; else numStateItems++;\n\t}\n\n\tpublic void setRewardStructItem(int i, RewardStructItem rsi)\n\t{\n\t\tif (getRewardStructItem(i).isTransitionReward()) numTransItems--; else numStateItems--;\n\t\titems.set(i, rsi);\n\t\tif (rsi.isTransitionReward()) numTransItems++; else numStateItems++;\n\t}\n\n\t// Get methods\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\tpublic int getNumItems()\n\t{\n\t\treturn items.size();\n\t}\n\t\n\tpublic int getNumStateItems()\n\t{\n\t\treturn numStateItems;\n\t}\n\t\n\tpublic int getNumTransItems()\n\t{\n\t\treturn numTransItems;\n\t}\n\t\n\tpublic RewardStructItem getRewardStructItem(int i)\n\t{\n\t\treturn items.get(i);\n\t}\n\t\n\tpublic String getSynch(int i)\n\t{\n\t\treturn getRewardStructItem(i).getSynch();\n\t}\n\t\n\tpublic Expression getStates(int i)\n\t{\n\t\treturn getRewardStructItem(i).getStates();\n\t}\n\t\n\tpublic Expression getReward(int i)\n\t{\n\t\treturn getRewardStructItem(i).getReward();\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tString s = \"\";\n\t\t\n\t\ts += \"rewards\";\n\t\tif (name != null && name.length() > 0) s += \" \\\"\"+name+\"\\\"\";\n\t\ts += \" \\n\\n\";\n\t\tn = getNumItems();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts += \"\\t\" + getRewardStructItem(i) + \"\\n\";\n\t\t}\n\t\ts += \"\\nendrewards\\n\";\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic RewardStruct deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(items);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic RewardStruct clone()\n\t{\n\t\tRewardStruct clone = (RewardStruct) super.clone();\n\n\t\tclone.items = (ArrayList<RewardStructItem>) items.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/RewardStructItem.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class RewardStructItem extends ASTElement\n{\n\t// Synchronising action:\n\t// * null = none (i.e. state reward)\n\t// * \"\" = empty/tau/asynchronous action (i.e. transition reward)\n\t// * \"act\" = \"act\"-labelled action (i.e. transition reward)\n\tprivate String synch;\n\t// Index of action label in model's list of all actions (\"synchs\")\n\t// This is 1-indexed, with 0 denoting an independent (\"tau\"-labelled) command.\n\t// -1 denotes either none (i.e. state reward, synch==null) or not (yet) known.\n\tprivate int synchIndex;\n\t// Guard expression\n\tprivate Expression states;\n\t// Reward expression\n\tprivate Expression reward;\n\t\n\t// constructor\n\t\n\tpublic RewardStructItem(String a, Expression s, Expression r)\n\t{\n\t\tsynch = a;\n\t\tsynchIndex = -1;\n\t\tstates = s;\n\t\treward = r;\n\t}\n\n\t// Set methods\n\t\n\tpublic void setSynch(String s)\n\t{\n\t\tsynch = s;\n\t}\n\t\n\tpublic void setSynchIndex(int i)\n\t{\n\t\tsynchIndex = i;\n\t}\n\t\n\tpublic void setStates(Expression e)\n\t{\n\t\tstates = e;\n\t}\n\t\n\tpublic void setReward(Expression e)\n\t{\n\t\treward = e;\n\t}\n\t\n\t// Get methods\n\t\n\t/**\n\t * Get the action label for this command. For independent (\"tau\"-labelled) commands,\n\t * this is the empty string \"\" (it should never be null).\n\t */\n\tpublic String getSynch()\n\t{\n\t\treturn synch;\n\t}\n\t\n\t/**\n\t * Get the index of the action label for this command (in the model's list of actions).\n\t * This is 1-indexed, with 0 denoting an independent (\"tau\"-labelled) command.\n\t * -1 denotes either none (i.e. state reward, synch==null) or not (yet) known.\n\t */\n\tpublic int getSynchIndex()\n\t{\n\t\treturn synchIndex;\n\t}\n\t\n\tpublic Expression getStates()\n\t{\n\t\treturn states;\n\t}\n\t\n\tpublic Expression getReward()\n\t{\n\t\treturn reward;\n\t}\n\t\n\t/**\n\t *\tReturns whether this reward is a state (false) or transition (true) reward\n\t */\n\tpublic boolean isTransitionReward()\n\t{\n\t\treturn (synch!=null);\n\t}\n\n\t// Methods required for ASTElement:\n\t\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\t\n\t\tif (synch != null) s += \"[\" + synch + \"] \";\n\t\ts += states + \" : \" + reward + \";\";\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic RewardStructItem deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tstates = copier.copy(states);\n\t\treward = copier.copy(reward);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic RewardStructItem clone()\n\t{\n\t\treturn (RewardStructItem) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemBrackets.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n// note: although this makes no difference to the meaning\n// of the expression, it means we can keep the user's\n// original bracketting for display purposes\n\npublic class SystemBrackets extends SystemDefn\n{\n\t// Operand\n\tprivate SystemDefn operand;\n\n\t// Constructors\n\t\n\tpublic SystemBrackets()\n\t{\n\t}\n\n\tpublic SystemBrackets(SystemDefn s)\n\t{\n\t\toperand = s;\n\t}\n\n\t// Set method\n\t\n\tpublic void setOperand(SystemDefn s)\n\t{\n\t\toperand = s;\n\t}\n\t\n\t// Get method\n\t\n\tpublic SystemDefn getOperand()\n\t{\n\t\treturn operand;\n\t}\n\t\n\t// Methods required for SystemDefn (all subclasses should implement):\n\t\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getModules(List<String> v)\n\t{\n\t\toperand.getModules(v);\n\t}\n\n\t@Override\n\tpublic void getModules(List<String> v, ModulesFile modulesFile)\n\t{\n\t\toperand.getModules(v, modulesFile);\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getSynchs(List<String> v)\n\t{\n\t\toperand.getSynchs(v);\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v, ModulesFile modulesFile)\n\t{\n\t\toperand.getSynchs(v, modulesFile);\n\t}\n\t\n\t@Override\n\tpublic void getReferences(List<String> v)\n\t{\n\t\toperand.getReferences(v);\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"(\" + operand + \")\";\n\t}\n\t\n\t@Override\n\tpublic SystemBrackets deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand = copier.copy(operand);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic SystemBrackets clone()\n\t{\n\t\treturn (SystemBrackets) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemDefn.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.List;\n\nimport parser.visitor.ASTTraverse;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic abstract class SystemDefn extends ASTElement\n{\n\t// Overwritten version of deepCopy() and deepCopy(DeepCopy copier) from superclass ASTElement (to reduce casting).\n\n\t@Override\n\tpublic abstract SystemDefn deepCopy(DeepCopy copier) throws PrismLangException;\n\n\t@Override\n\tpublic SystemDefn deepCopy()\n\t{\n\t\treturn (SystemDefn) super.deepCopy();\n\t}\n\n\t@Override\n\tpublic SystemDefn clone()\n\t{\n\t\treturn (SystemDefn) super.clone();\n\t}\n\n\t// Methods required for SystemDefn (all subclasses should implement):\n\n\t/**\n\t * Get list of all modules appearing (recursively).\n\t * Duplicates are not removed and will appear multiple times in the list.\n\t * @deprecated Use {@link SystemDefn#getModules(List, ModulesFile)} instead.\n\t */\n\t@Deprecated\n\tpublic abstract void getModules(List<String> v);\n\n\t/**\n\t * Get list of all modules appearing (recursively, including descent into references).\n\t * Duplicates are not removed and will appear multiple times in the list.\n\t */\n\tpublic abstract void getModules(List<String> v, ModulesFile modulesFile);\n\n\t/**\n\t * Get list of all synchronising actions _introduced_ (recursively).\n\t * @deprecated Use {@link SystemDefn#getSynchs(List, ModulesFile)} instead.\n\t */\n\t@Deprecated\n\tpublic abstract void getSynchs(List<String> v);\n\n\t/**\n\t * Get list of all synchronising actions _introduced_ (recursively, including descent into references).\n\t */\n\tpublic abstract void getSynchs(List<String> v, ModulesFile modulesFile);\n\n\t/**\n\t * Returns true if this SystemDefn contains a SystemHide.\n\t */\n\tpublic boolean containsSystemHide()\n\t{\n\t\ttry {\n\t\t\tthis.accept(new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPre(SystemHide e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tthrow new PrismLangException(\"Found one\");\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (PrismLangException e) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get list of all references to other SystemDefns (recursively, but not following references).\n\t */\n\tpublic abstract void getReferences(List<String> v);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemFullParallel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class SystemFullParallel extends SystemDefn\n{\n\t// List of operands\n\tprivate ArrayList<SystemDefn> operands;\n\t\n\t// Constructor\n\t\n\tpublic SystemFullParallel()\n\t{\n\t\toperands = new ArrayList<>();\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void addOperand(SystemDefn s)\n\t{\n\t\toperands.add(s);\n\t}\n\t\t\n\tpublic void setOperand(int i, SystemDefn s)\n\t{\n\t\toperands.set(i, s);\n\t}\n\t\t\t\n\t// Get methods\n\t\n\tpublic int getNumOperands()\n\t{\n\t\treturn operands.size();\n\t}\n\t\n\tpublic SystemDefn getOperand(int i)\n\t{\n\t\treturn operands.get(i);\n\t}\n\t\t\n\t// Methods required for SystemDefn (all subclasses should implement):\n\t\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getModules(List<String> v)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getModules(v);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void getModules(List<String> v, ModulesFile modulesFile)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getModules(v, modulesFile);\n\t\t}\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getSynchs(List<String> v)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getSynchs(v);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v, ModulesFile modulesFile)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getSynchs(v, modulesFile);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void getReferences(List<String> v)\n\t{\n\t\tint n = getNumOperands();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getReferences(v);\n\t\t}\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tString s = \"\";\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n-1; i++) {\n\t\t\ts = s + getOperand(i) + \" || \";\n\t\t}\n\t\tif (n > 0) {\n\t\t\ts = s + getOperand(n-1);\n\t\t}\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic SystemFullParallel deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(operands);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic SystemFullParallel clone()\n\t{\n\t\tSystemFullParallel clone = (SystemFullParallel) super.clone();\n\n\t\tclone.operands = (ArrayList<SystemDefn>) operands.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemHide.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class SystemHide extends SystemDefn\n{\n\t// Operand\n\tprivate SystemDefn operand;\n\t// Actions to be hidden\n\tprivate ArrayList<String> actions;\n\t\n\t// Constructors\n\t\n\tpublic SystemHide()\n\t{\n\t\tactions = new ArrayList<>();\n\t}\n\t\n\tpublic SystemHide(SystemDefn s)\n\t{\n\t\tthis();\n\t\toperand = s;\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void setOperand(SystemDefn s)\n\t{\n\t\toperand = s;\n\t}\n\t\n\tpublic void addAction(String s)\n\t{\n\t\tactions.add(s);\n\t}\n\t\t\n\tpublic void setAction(int i, String s)\n\t{\n\t\tactions.set(i, s);\n\t}\n\t\n\t// Get methods\n\t\n\tpublic SystemDefn getOperand()\n\t{\n\t\treturn operand;\n\t}\n\t\n\tpublic int getNumActions()\n\t{\n\t\treturn actions.size();\n\t}\n\t\n\tpublic String getAction(int i)\n\t{\n\t\treturn actions.get(i);\n\t}\n\t\t\n\tpublic boolean containsAction(String s)\n\t{\n\t\treturn actions.contains(s);\n\t}\n\t\n\t// Methods required for SystemDefn (all subclasses should implement):\n\t\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getModules(List<String> v)\n\t{\n\t\toperand.getModules(v);\n\t}\n\t\n\t@Override\n\tpublic void getModules(List<String> v, ModulesFile modulesFile)\n\t{\n\t\toperand.getModules(v, modulesFile);\n\t}\n\t\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getSynchs(List<String> v)\n\t{\n\t\t// recurse\n\t\toperand.getSynchs(v);\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v, ModulesFile modulesFile)\n\t{\n\t\t// recurse\n\t\toperand.getSynchs(v, modulesFile);\n\t}\n\t\n\t@Override\n\tpublic void getReferences(List<String> v)\n\t{\n\t\toperand.getReferences(v);\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tString s = \"\";\n\t\t\n\t\ts = s + operand + \"/{\";\n\t\tn = getNumActions();\n\t\tfor (i = 0; i < n-1; i++) {\n\t\t\ts = s + getAction(i) + \",\";\n\t\t}\n\t\tif (n > 0) {\n\t\t\ts = s + getAction(n-1);\n\t\t}\n\t\ts = s + \"}\";\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic SystemHide deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand = copier.copy(operand);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic SystemHide clone()\n\t{\n\t\tSystemHide clone = (SystemHide) super.clone();\n\n\t\tclone.actions = (ArrayList<String>) actions.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemInterleaved.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class SystemInterleaved extends SystemDefn\n{\n\t// List of operands\n\tprivate ArrayList<SystemDefn> operands;\n\t\n\t// Constructor\n\t\n\tpublic SystemInterleaved()\n\t{\n\t\toperands = new ArrayList<>();\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void addOperand(SystemDefn s)\n\t{\n\t\toperands.add(s);\n\t}\n\t\t\n\tpublic void setOperand(int i, SystemDefn s)\n\t{\n\t\toperands.set(i, s);\n\t}\n\t\t\t\n\t// Get methods\n\t\n\tpublic int getNumOperands()\n\t{\n\t\treturn operands.size();\n\t}\n\t\n\tpublic SystemDefn getOperand(int i)\n\t{\n\t\treturn operands.get(i);\n\t}\n\t\t\n\t// Methods required for SystemDefn (all subclasses should implement):\n\t\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getModules(List<String> v)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getModules(v);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void getModules(List<String> v, ModulesFile modulesFile)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getModules(v, modulesFile);\n\t\t}\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getSynchs(List<String> v)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getSynchs(v);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v, ModulesFile modulesFile)\n\t{\n\t\tint i, n;\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getSynchs(v, modulesFile);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void getReferences(List<String> v)\n\t{\n\t\tint n = getNumOperands();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tgetOperand(i).getReferences(v);\n\t\t}\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tString s = \"\";\n\t\t\n\t\tn = getNumOperands();\n\t\tfor (i = 0; i < n-1; i++) {\n\t\t\ts = s + getOperand(i) + \" ||| \";\n\t\t}\n\t\tif (n > 0) {\n\t\t\ts = s + getOperand(n-1);\n\t\t}\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic SystemInterleaved deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(operands);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic SystemInterleaved clone()\n\t{\n\t\tSystemInterleaved clone = (SystemInterleaved) super.clone();\n\n\t\tclone.operands = (ArrayList<SystemDefn>) operands.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemModule.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class SystemModule extends SystemDefn\n{\n\t// Module name\n\tString name;\n\t\n\t// Constructors\n\t\n\tpublic SystemModule()\n\t{\n\t}\n\t\n\tpublic SystemModule(String n)\n\t{\n\t\tname = n;\n\t}\n\t\n\t// Set method\n\t\n\tpublic void setName(String n)\n\t{\n\t\tname = n;\n\t}\n\t\n\t// Get method\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\t// Methods required for SystemDefn (all subclasses should implement):\n\t\n\t@Override\n\tpublic void getModules(List<String> v)\n\t{\n\t\tv.add(name);\n\t}\n\t\n\t@Override\n\tpublic void getModules(List<String> v, ModulesFile modulesFile)\n\t{\n\t\tv.add(name);\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v)\n\t{\n\t\t// do nothing\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v, ModulesFile modulesFile)\n\t{\n\t\t// do nothing\n\t}\n\t\n\t@Override\n\tpublic void getReferences(List<String> v)\n\t{\n\t\t// do nothing\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn name;\n\t}\n\t\n\t@Override\n\tpublic SystemModule deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic SystemModule clone()\n\t{\n\t\treturn (SystemModule) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemParallel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class SystemParallel extends SystemDefn\n{\n\t// Pair of operands\n\tprivate SystemDefn operand1;\n\tprivate SystemDefn operand2;\n\t// List of synchronising actions\n\tprivate ArrayList<String> actions;\n\t\n\t// Constructors\n\t\n\tpublic SystemParallel()\n\t{\n\t\tactions = new ArrayList<>();\n\t}\n\t\n\tpublic SystemParallel(SystemDefn s1, SystemDefn s2)\n\t{\n\t\tthis();\n\t\toperand1 = s1;\n\t\toperand2 = s2;\n\t}\n\t\n\t// Set methods\n\t\n\tpublic void setOperand1(SystemDefn s1)\n\t{\n\t\toperand1 = s1;\n\t}\n\t\n\tpublic void setOperand2(SystemDefn s2)\n\t{\n\t\toperand2 = s2;\n\t}\n\t\n\tpublic void addAction(String s)\n\t{\n\t\tactions.add(s);\n\t}\n\t\t\n\tpublic void setAction(int i, String s)\n\t{\n\t\tactions.set(i, s);\n\t}\n\t\t\t\n\t// Get methods\n\t\n\tpublic SystemDefn getOperand1()\n\t{\n\t\treturn operand1;\n\t}\n\t\n\tpublic SystemDefn getOperand2()\n\t{\n\t\treturn operand2;\n\t}\n\n\tpublic int getNumActions()\n\t{\n\t\treturn actions.size();\n\t}\n\t\n\tpublic String getAction(int i)\n\t{\n\t\treturn actions.get(i);\n\t}\n\t\t\n\tpublic boolean containsAction(String s)\n\t{\n\t\treturn actions.contains(s);\n\t}\n\t\t\n\t// Methods required for SystemDefn (all subclasses should implement):\n\t\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getModules(List<String> v)\n\t{\n\t\toperand1.getModules(v);\n\t\toperand2.getModules(v);\n\t}\n\n\t@Override\n\tpublic void getModules(List<String> v, ModulesFile modulesFile)\n\t{\n\t\toperand1.getModules(v, modulesFile);\n\t\toperand2.getModules(v, modulesFile);\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getSynchs(List<String> v)\n\t{\n\t\toperand1.getSynchs(v);\n\t\toperand2.getSynchs(v);\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v, ModulesFile modulesFile)\n\t{\n\t\toperand1.getSynchs(v, modulesFile);\n\t\toperand2.getSynchs(v, modulesFile);\n\t}\n\t\n\t@Override\n\tpublic void getReferences(List<String> v)\n\t{\n\t\toperand1.getReferences(v);\n\t\toperand2.getReferences(v);\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tString s = \"\";\n\t\t\n\t\ts = s + operand1 + \" |[\";\n\t\tn = getNumActions();\n\t\tfor (i = 0; i < n-1; i++) {\n\t\t\ts = s + getAction(i) + \",\";\n\t\t}\n\t\tif (n > 0) {\n\t\t\ts = s + getAction(n-1);\n\t\t}\n\t\ts = s + \"]| \" + operand2;\n\t\t\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic SystemParallel deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand1 = copier.copy(operand1);\n\t\toperand2 = copier.copy(operand2);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic SystemParallel clone()\n\t{\n\t\tSystemParallel clone = (SystemParallel) super.clone();\n\n\t\tclone.actions = (ArrayList<String>) actions.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemReference.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class SystemReference extends SystemDefn\n{\n\t// Name of SystemDefn referenced\n\tprivate String name;\n\t\n\t// Constructors\n\t\n\tpublic SystemReference(String name)\n\t{\n\t\tthis.name = name;\n\t}\n\t\n\t// Set method\n\t\n\tpublic void setName(String name)\n\t{\n\t\tthis.name = name;\n\t}\n\t\n\t// Get method\n\t\n\tpublic String getName()\n\t{\n\t\treturn name;\n\t}\n\t\n\t// Methods required for SystemDefn (all subclasses should implement):\n\t\n\t@Override\n\tpublic void getModules(List<String> v)\n\t{\n\t\tv.add(name);\n\t}\n\t\n\t@Override\n\tpublic void getModules(List<String> v, ModulesFile modulesFile)\n\t{\n\t\t// Recurse into referenced SystemDefn\n\t\tSystemDefn ref = modulesFile.getSystemDefnByName(name);\n\t\tif (ref != null) {\n\t\t\tref.getModules(v, modulesFile);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v)\n\t{\n\t\t// do nothing\n\t}\n\t\n\t@Override\n\tpublic void getSynchs(List<String> v, ModulesFile modulesFile)\n\t{\n\t\t// Recurse into referenced SystemDefn\n\t\tSystemDefn ref = modulesFile.getSystemDefnByName(name);\n\t\tif (ref != null) {\n\t\t\tref.getSynchs(v, modulesFile);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void getReferences(List<String> v)\n\t{\n\t\tif (!v.contains(name))\n\t\t\tv.add(name);\n\t}\n\t\n\t// Methods required for ASTElement:\n\t\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"\\\"\" + name + \"\\\"\";\n\t}\n\t\n\t@Override\n\tpublic SystemReference deepCopy(DeepCopy copier)\n\t{\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic SystemReference clone()\n\t{\n\t\treturn (SystemReference) super.clone();\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/SystemRename.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\npublic class SystemRename extends SystemDefn\n{\n\t// Operand\n\tprivate SystemDefn operand;\n\t// lists for pairs of actions to be renamed\n\tprivate ArrayList<String> from;\n\tprivate ArrayList<String> to;\n\n\t// Constructors\n\n\tpublic SystemRename()\n\t{\n\t\tfrom = new ArrayList<>();\n\t\tto = new ArrayList<>();\n\t}\n\n\tpublic SystemRename(SystemDefn s)\n\t{\n\t\tthis();\n\t\toperand = s;\n\t}\n\n\t// Set methods\n\n\tpublic void setOperand(SystemDefn s)\n\t{\n\t\toperand = s;\n\t}\n\n\tpublic void addRename(String s1, String s2)\n\t{\n\t\tfrom.add(s1);\n\t\tto.add(s2);\n\t}\n\n\tpublic void setRename(int i, String s1, String s2)\n\t{\n\t\tfrom.set(i, s1);\n\t\tto.set(i, s2);\n\t}\n\n\t// Get methods\n\n\tpublic SystemDefn getOperand()\n\t{\n\t\treturn operand;\n\t}\n\n\tpublic int getNumRenames()\n\t{\n\t\treturn from.size();\n\t}\n\n\tpublic String getFrom(int i)\n\t{\n\t\treturn from.get(i);\n\t}\n\n\tpublic String getTo(int i)\n\t{\n\t\treturn to.get(i);\n\t}\n\n\tpublic String getNewName(String s)\n\t{\n\t\tint i;\n\n\t\ti = from.indexOf(s);\n\t\tif (i == -1) {\n\t\t\treturn s;\n\t\t} else {\n\t\t\treturn to.get(i);\n\t\t}\n\t}\n\n\t// Methods required for SystemDefn (all subclasses should implement):\n\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getModules(List<String> v)\n\t{\n\t\toperand.getModules(v);\n\t}\n\n\t@Override\n\tpublic void getModules(List<String> v, ModulesFile modulesFile)\n\t{\n\t\toperand.getModules(v, modulesFile);\n\t}\n\n\t@Override\n\t@SuppressWarnings(\"deprecation\")\n\tpublic void getSynchs(List<String> v)\n\t{\n\t\tint i, n;\n\t\tString s;\n\n\t\t// add action names in renames\n\t\t// (only look in 'to' list because we're only\n\t\t//  interested in actions _introduced_)\n\t\tn = getNumRenames();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = getTo(i);\n\t\t\tif (!(v.contains(s)))\n\t\t\t\tv.add(s);\n\t\t}\n\n\t\t// recurse\n\t\toperand.getSynchs(v);\n\t}\n\n\t@Override\n\tpublic void getSynchs(List<String> v, ModulesFile modulesFile)\n\t{\n\t\tint i, n;\n\t\tString s;\n\n\t\t// add action names in renames\n\t\t// (only look in 'to' list because we're only\n\t\t//  interested in actions _introduced_)\n\t\tn = getNumRenames();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = getTo(i);\n\t\t\tif (!(v.contains(s)))\n\t\t\t\tv.add(s);\n\t\t}\n\n\t\t// recurse\n\t\toperand.getSynchs(v, modulesFile);\n\t}\n\n\t@Override\n\tpublic void getReferences(List<String> v)\n\t{\n\t\toperand.getReferences(v);\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tString s = \"\";\n\n\t\ts = s + operand + \"{\";\n\t\tn = getNumRenames();\n\t\tfor (i = 0; i < n - 1; i++) {\n\t\t\ts = s + getFrom(i) + \"<-\" + getTo(i) + \",\";\n\t\t}\n\t\tif (n > 0) {\n\t\t\ts = s + getFrom(n - 1) + \"<-\" + getTo(n - 1);\n\t\t}\n\t\ts = s + \"}\";\n\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic SystemRename deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\toperand = copier.copy(operand);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic SystemRename clone()\n\t{\n\t\tSystemRename clone = (SystemRename) super.clone();\n\n\t\tclone.from = (ArrayList<String>) from.clone();\n\t\tclone.to   = (ArrayList<String>) to.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/Update.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport java.util.ArrayList;\nimport java.util.Iterator;\nimport java.util.stream.Collectors;\n\nimport parser.EvaluateContext;\nimport parser.EvaluateContext.EvalMode;\nimport parser.EvaluateContextState;\nimport parser.EvaluateContextSubstate;\nimport parser.State;\nimport parser.VarList;\nimport parser.type.Type;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n/**\n * Class to store a single update, i.e. a list of assignments of variables to expressions, e.g. (s'=1)&amp;(x'=x+1)\n */\npublic class Update extends ASTElement implements Iterable<UpdateElement>\n{\n\t// Individual elements of update\n\tprivate ArrayList<UpdateElement> elements;\n\n\t// Parent Updates object\n\tprivate Updates parent;\n\n\t/**\n\t * Create an empty update.\n\t */\n\tpublic Update()\n\t{\n\t\telements = new ArrayList<>();\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Add a variable assignment ({@code v}'={@code e}) to this update.\n\t * @param v The AST element corresponding to the variable being updated\n\t * @param e The expression which will be assigned to the variable\n\t */\n\tpublic void addElement(ExpressionIdent v, Expression e)\n\t{\n\t\telements.add(new UpdateElement(v, e));\n\t}\n\n\t/**\n\t * Add a variable assignment (encoded as an UpdateElement) to this update.\n\t */\n\tpublic void addElement(UpdateElement e)\n\t{\n\t\telements.add(e);\n\t}\n\n\t/**\n\t * Set the ith variable assignment (encoded as an UpdateElement) to this update.\n\t */\n\tpublic void setElement(int i, UpdateElement e)\n\t{\n\t\telements.set(i, e);\n\t}\n\n\t/**\n\t * Set the variable {@code v} for the {@code i}th variable assignment of this update.\n\t * @param i The index of the variable assignment within the update\n\t * @param v The AST element corresponding to the variable being updated\n\t */\n\tpublic void setVar(int i, ExpressionIdent v)\n\t{\n\t\telements.get(i).setVarIdent(v);\n\t}\n\n\t/**\n\t * Set the expression {@code e} for the {@code i}th variable assignment of this update.\n\t * @param i The index of the variable assignment within the update\n\t * @param e The expression which will be assigned to the variable\n\t */\n\tpublic void setExpression(int i, Expression e)\n\t{\n\t\telements.get(i).setExpression(e);\n\t}\n\n\t/**\n\t * Set the type of the {@code i}th variable assigned to by this update.\n\t * @param i The index of the variable assignment within the update\n\t * @param t The variable's type\n\t */\n\tpublic void setType(int i, Type t)\n\t{\n\t\telements.get(i).setType(t);\n\t}\n\n\t/**\n\t * Set the index (wrt the model) of the {@code i}th variable assigned to by this update.\n\t * @param i The index of the variable assignment within the update\n\t * @param t The index of the variable within the model to which it belongs\n\t */\n\tpublic void setVarIndex(int i, int index)\n\t{\n\t\telements.get(i).setVarIndex(index);\n\t}\n\n\t/**\n\t * Set the {@link parser.ast.Updates} object containing this update.\n\t */\n\tpublic void setParent(Updates u)\n\t{\n\t\tparent = u;\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the number of variables assigned values by this update.\n\t */\n\tpublic int getNumElements()\n\t{\n\t\treturn elements.size();\n\t}\n\n\t/** Get the update element (individual assignment) with the given index. */\n\tpublic UpdateElement getElement(int index)\n\t{\n\t\treturn elements.get(index);\n\t}\n\t\n\t/**\n\t * Get the name of the {@code i}th variable in this update.\n\t */\n\tpublic String getVar(int i)\n\t{\n\t\treturn elements.get(i).getVar();\n\t}\n\n\t/**\n\t * Get the expression used to update the {@code i}th variable in this update.\n\t */\n\tpublic Expression getExpression(int i)\n\t{\n\t\treturn elements.get(i).getExpression();\n\t}\n\n\t/**\n\t * Get the type of the {@code i}th variable in this update.\n\t */\n\tpublic Type getType(int i)\n\t{\n\t\treturn elements.get(i).getType();\n\t}\n\n\t/**\n\t * Get the ASTElement corresponding to the {@code i}th variable in this update.\n\t */\n\tpublic ExpressionIdent getVarIdent(int i)\n\t{\n\t\treturn elements.get(i).getVarIdent();\n\t}\n\n\t/**\n\t * Get the index (wrt the model) of the {@code i}th variable in this update.\n\t */\n\tpublic int getVarIndex(int i)\n\t{\n\t\treturn elements.get(i).getVarIndex();\n\t}\n\n\t/**\n\t * Get the {@link parser.ast.Updates} object containing this update.\n\t */\n\tpublic Updates getParent()\n\t{\n\t\treturn parent;\n\t}\n\n\t/**\n\t * Execute this update, based on variable values specified as a State object.\n\t * Apply changes in variables to a provided copy of the State object.\n\t * (i.e. oldState and newState should be equal when passed in)\n\t * It is assumed that any constants have already been defined.\n\t * @param oldState Variable values in current state\n\t * @param newState State object to apply changes to\n\t * @param exact evaluate arithmetic expressions exactly?\n\t * @param varList VarList for info about state variables\n\t */\n\tpublic void update(State oldState, State newState, boolean exact, VarList varList) throws PrismLangException\n\t{\n\t\tEvaluateContext ec = new EvaluateContextState(oldState);\n\t\tec.setEvaluationMode(exact ? EvalMode.EXACT : EvalMode.FP);\n\t\tfor (UpdateElement e : this) {\n\t\t\te.update(ec, newState, varList);\n\t\t}\n\t}\n\n\t/**\n\t * Execute this update, based on variable values specified as a State object.\n\t * Apply changes in variables to a provided copy of the State object.\n\t * (i.e. oldState and newState should be equal when passed in.) \n\t * Both State objects represent only a subset of the total set of variables,\n\t * with this subset being defined by the mapping varMap.\n\t * Only variables in this subset are updated.\n\t * But if doing so requires old values for variables outside the subset, this will cause an exception. \n\t * It is assumed that any constants have already been defined.\n\t * @param oldState Variable values in current state\n\t * @param newState State object to apply changes to\n\t * @param varMap A mapping from indices (over all variables) to the subset (-1 if not in subset). \n\t */\n\tpublic void updatePartially(State oldState, State newState, int[] varMap) throws PrismLangException\n\t{\n\t\tint i, j, n;\n\t\tn = elements.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tj = varMap[getVarIndex(i)];\n\t\t\tif (j != -1) {\n\t\t\t\tnewState.setValue(j, getExpression(i).evaluate(new EvaluateContextSubstate(oldState, varMap)));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Check whether this update (from a particular state) would cause any errors, mainly variable overflows.\n\t * Variable ranges are specified in the passed in VarList.\n\t * Throws an exception if such an error occurs.\n\t */\n\tpublic State checkUpdate(State oldState, VarList varList) throws PrismLangException\n\t{\n\t\tState res;\n\t\tres = new State(oldState);\n\t\tfor (UpdateElement e : this) {\n\t\t\te.checkUpdate(oldState, varList);\n\t\t}\n\t\treturn res;\n\t}\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic Update deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(elements);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic Update clone()\n\t{\n\t\tUpdate clone = (Update) super.clone();\n\n\t\tclone.elements = (ArrayList<UpdateElement>) elements.clone();\n\n\t\treturn clone;\n\t}\n\t\n\t// Other methods:\n\t\n\t@Override\n\tpublic Iterator<UpdateElement> iterator()\n\t{\n\t\treturn elements.iterator();\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\t// Normal case\n\t\tif (elements.size() > 0) {\n\t\t\treturn elements.stream().map(UpdateElement::toString).collect(Collectors.joining(\" & \"));\n\t\t}\n\t\t// Special (empty) case\n\t\telse {\n\t\t\treturn \"true\";\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/UpdateElement.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2018\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.EvaluateContext;\nimport parser.State;\nimport parser.VarList;\nimport parser.type.Type;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\n/**\n * Class to store a single element of an Update, i.e. a single assignment (e.g. s'=1)\n */\npublic class UpdateElement extends ASTElement\n{\n\t/** The variable that is assigned to */\n\tprivate String var;\n\t/** The expression for the assignment value */\n\tprivate Expression expr;\n\t/** The type of the assignment (initially empty / unknown) */\n\tprivate Type type;\n\t/** The identifier expression for the variable (for position information, etc) */\n\tprivate ExpressionIdent ident;\n\t/** The variable index (initially unknown, i.e., -1) */\n\tprivate int index;\n\n\t/** Constructor */\n\tpublic UpdateElement(ExpressionIdent v, Expression e)\n\t{\n\t\tvar = v.getName();\n\t\texpr = e;\n\t\ttype = null; // Type currently unknown\n\t\tident = v;\n\t\tindex = -1; // Index currently unknown\n\t}\n\n\t/** Shallow copy constructor */\n\tpublic UpdateElement(UpdateElement other)\n\t{\n\t\tvar = other.var;\n\t\texpr = other.expr;\n\t\ttype = other.type;\n\t\tident = other.ident;\n\t\tindex = other.index;\n\t}\n\n\t// Getters\n\n\t/** Get the name of the variable that is the assignment target */\n\tpublic String getVar()\n\t{\n\t\treturn var;\n\t}\n\n\t/** Get the update expression */\n\tpublic Expression getExpression()\n\t{\n\t\treturn expr;\n\t}\n\n\t/** Get the type of the update */\n\tpublic Type getType()\n\t{\n\t\treturn type;\n\t}\n\n\t/** Get the ExpressionIdent corresponding to the variable name (for position information) */\n\tpublic ExpressionIdent getVarIdent()\n\t{\n\t\treturn ident;\n\t}\n\n\t/** Set the name of the variable that is the assignment target */\n\tpublic void setVar(String var)\n\t{\n\t\tthis.var = var;\n\t}\n\n\t/** Get the variable index for the variable that is the assignment target */\n\tpublic int getVarIndex()\n\t{\n\t\treturn index;\n\t}\n\n\t// Setters\n\t\n\t/** Set the update expression */\n\tpublic void setExpression(Expression expr)\n\t{\n\t\tthis.expr = expr;\n\t}\n\n\t/** Set the type of the update */\n\tpublic void setType(Type type)\n\t{\n\t\tthis.type = type;\n\t}\n\n\t/** Set the ExpressionIdent corresponding to the variable name (for position information) */\n\tpublic void setVarIdent(ExpressionIdent ident)\n\t{\n\t\tthis.ident = ident;\n\t\tthis.var = ident.getName();\n\t}\n\n\t/** Set the variable index for the variable that is the assignment target */\n\tpublic void setVarIndex(int index)\n\t{\n\t\tthis.index = index;\n\t}\n\n\t/**\n\t * Execute this update element, applying variable changes to a State object.\n\t * Current variable/constant values are specified as an EvaluateContext object.\n\t * The evaluation mode and values for any undefined constants are also taken from this object.\n\t * @param ec Context for evaluation of variables values etc.\n\t * @param newState State object to apply changes to\n\t * @param varList VarList for info about state variables\n\t */\n\tpublic void update(EvaluateContext ec, State newState, VarList varList) throws PrismLangException\n\t{\n\t\tObject newValue = getType().castValueTo(expr.evaluate(ec));\n\t\tnewState.setValue(index, newValue);\n\t}\n\t\n\t/**\n\t * Check whether this update (from a particular state) would cause any errors, mainly variable overflows.\n\t * Variable ranges are specified in the passed in VarList.\n\t * Throws an exception if such an error occurs.\n\t */\n\tpublic void checkUpdate(State oldState, VarList varList) throws PrismLangException\n\t{\n\t\tint valNew;\n\t\tvalNew = varList.encodeToInt(index, expr.evaluate(oldState));\n\t\tif (valNew < varList.getLow(index) || valNew > varList.getHigh(index))\n\t\t\tthrow new PrismLangException(\"Value of variable \" + var + \" overflows\", expr);\n\t}\n\n\n\t// Methods required for ASTElement:\n\n\t@Override\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t@Override\n\tpublic UpdateElement deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tident = copier.copy(ident);\n\t\texpr = copier.copy(expr);\n\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic UpdateElement clone()\n\t{\n\t\treturn (UpdateElement) super.clone();\n\t}\n\t\n\t// Other methods:\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"(\" + getVar() + \"'=\" + getExpression() + \")\";\t\t\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/ast/Updates.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.ast;\n\nimport parser.State;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.Objects;\n\n/**\n * Class to store a list of updates with associated probabilities (or rates).\n * e.g. 0.5:(s'=1)&amp;(x'=x+1) + 0.5:(s'=2)&amp;(x'=x-1)\n */\npublic class Updates extends ASTElement\n{\n\t// Pairs of probabilities/updates\n\tprivate ArrayList<Expression> probs;\n\tprivate ArrayList<Update> updates;\n\t// Parent command\n\tprivate Command parent;\n\n\t/**\n\t * Construct an empty Updates object.\n\t */\n\tpublic Updates()\n\t{\n\t\tprobs = new ArrayList<Expression>();\n\t\tupdates = new ArrayList<Update>();\n\t\tparent = null;\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Add a probability (or rate) and update pair (probability/rate can be null, which equates to 1.0).\n\t */\n\tpublic void addUpdate(Expression p, Update u)\n\t{\n\t\tprobs.add(p);\n\t\tupdates.add(u);\n\t\tu.setParent(this);\n\t}\n\n\t/**\n\t * Set the ith update.\n\t */\n\tpublic void setUpdate(int i, Update u)\n\t{\n\t\tupdates.set(i, u);\n\t\tu.setParent(this);\n\t}\n\n\t/**\n\t * Set the probability (or rate) of the ith update (can be null; denotes default of 1.0)\n\t */\n\tpublic void setProbability(int i, Expression p)\n\t{\n\t\t// Note: probability can be null, which equates to 1.0\n\t\tprobs.set(i, p);\n\t}\n\n\t/**\n\t * Set the parent Command.\n\t */\n\tpublic void setParent(Command c)\n\t{\n\t\tparent = c;\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the number of updates.\n\t */\n\tpublic int getNumUpdates()\n\t{\n\t\treturn updates.size();\n\t}\n\n\t/**\n\t * Get the ith update.\n\t */\n\tpublic Update getUpdate(int i)\n\t{\n\t\treturn updates.get(i);\n\t}\n\n\t/**\n\t * Get access to the whole list of the updates\n\t */\n\tpublic List<Update> getUpdates()\n\t{\n\t\treturn updates;\n\t}\n\n\t/**\n\t *  Get the probability (or rate) of the ith update (may be null, which should be interpreted as constant 1.0)\n\t */\n\tpublic Expression getProbability(int i)\n\t{\n\t\treturn probs.get(i);\n\t}\n\n\t/**\n\t * Evaluate the probability (or rate) of the ith update, in the context of a state\n\t */\n\tpublic double getProbabilityInState(int i, State state) throws PrismLangException\n\t{\n\t\tExpression p = probs.get(i);\n\t\treturn (p == null) ? 1.0 : p.evaluateDouble(state);\n\t}\n\t\t\t\n\t/**\n\t * Get the Command to which this Updates object belongs.\n\t */\n\tpublic Command getParent()\n\t{\n\t\treturn parent;\n\t}\n\n\t// Methods required for ASTElement:\n\n\t/**\n\t * Visitor method.\n\t */\n\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t{\n\t\treturn v.visit(this);\n\t}\n\n\t/**\n\t * Convert to string.\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tint i, n;\n\n\t\tn = getNumUpdates();\n\t\tfor (i = 0; i < n - 1; i++) {\n\t\t\tif (getProbability(i) != null)\n\t\t\t\ts += getProbability(i) + \" : \";\n\t\t\ts += getUpdate(i) + \" + \";\n\t\t}\n\t\tif (getProbability(n - 1) != null)\n\t\t\ts += getProbability(n - 1) + \" : \";\n\t\ts += getUpdate(n - 1);\n\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic Updates deepCopy(DeepCopy copier) throws PrismLangException\n\t{\n\t\tcopier.copyAll(probs);\n\t\tfor (int i = 0, n = getNumUpdates(); i < n; i++) {\n\t\t\tUpdate upd = Objects.requireNonNull(getUpdate(i));\n\t\t\tsetUpdate(i, copier.copy(upd));\n\t\t}\n\t\tcopier.copyAll(updates);\n\n\t\treturn this;\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\t@Override\n\tpublic Updates clone()\n\t{\n\t\tUpdates clone = (Updates) super.clone();\n\n\t\tclone.probs   = (ArrayList<Expression>) probs.clone();\n\t\tclone.updates = (ArrayList<Update>) updates.clone();\n\n\t\treturn clone;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/parser/ast/package-info.java",
    "content": "/**\n * Abstract syntax tree data structures for the PRISM model/properties parser.\n */\npackage parser.ast;\n"
  },
  {
    "path": "prism/src/parser/package-info.java",
    "content": "/**\n * The PRISM model/properties parser, accompanying abstract syntax tree data structures and tools (including JavaCC-generated code).\n */\npackage parser;\n"
  },
  {
    "path": "prism/src/parser/type/Type.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport parser.EvaluateContext.EvalMode;\nimport parser.ast.DeclarationType;\nimport prism.PrismLangException;\n\npublic abstract class Type \n{\n\t/**\n\t * Returns the string denoting this type, e.g. \"int\", \"bool\".\n\t */\n\tpublic abstract String getTypeString();\n\t\n\t/**\n\t * Is this a primitive type (bool, int, etc.)?\n\t */\n\tpublic boolean isPrimitive()\n\t{\n\t\t// Assume true by default; override if not\n\t\treturn true;\n\t}\n\t\n\t/**\n\t * Returns the default value for this type, assuming no initialisation specified.\n\t */\n\tpublic Object defaultValue()\n\t{\n\t\t// Play safe: assume null\n\t\treturn null;\n\t}\n\t\n\t/**\n\t * Returns an appropriate DeclarationType object for this type, assuming no info about bounds, etc.\n\t */\n\tpublic DeclarationType defaultDeclarationType() throws PrismLangException\n\t{\n\t\t// Not implemented by default\n\t\tthrow new PrismLangException(\"Cannot create a DeclarationType for type \" + getTypeString());\n\t}\n\t\n\t/**\n\t * Returns true iff a value of type {@code type} can be cast to a value of this type.\n\t */\n\tpublic boolean canCastTypeTo(Type type)\n\t{\n\t\t// Play safe: assume not possible, unless explicitly overridden.\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Make sure that a value, stored as an Object (Integer, Boolean, etc.)\n\t * is the correct kind of Object for this type.\n\t * Basically, implement some implicit casts (e.g. from type int to double).\n\t * The evaluation mode is not changed (e.g. when casting  int to double,\n\t * the conversion could be either Integer -> Double or BigInteger -> BigRational).\n\t * This should only only work for combinations of types that satisfy {@code #canAssign(Type)}.\n\t * If not, an exception is thrown (but such problems should have been caught earlier by type checking)\n\t */\n\tpublic Object castValueTo(Object value) throws PrismLangException\n\t{\n\t\t// Play safe: assume error unless explicitly overridden.\n\t\tthrow new PrismLangException(\"Cannot cast a value to type \" + getTypeString());\n\t}\n\n\t/**\n\t * Make sure that a value, stored as an Object (Integer, Boolean, etc.),\n\t * is the correct kind of Object for this type, and a given evaluation mode.\n\t * E.g. a \"double\" is stored as a Double for floating point mode (EvalMode.FP)\n\t * but a BigRational for exact mode (EvalMode.EXACT).\n\t * Basically, implement some implicit casts (e.g. from type int to double)\n\t * and some conversions between evaluation modes (e.g. BigRational to Double).\n\t * This should only only work for combinations of types that satisfy {@code #canAssign(Type)}.\n\t * If not, an exception is thrown (but such problems should have been caught earlier by type checking)\n\t */\n\tpublic Object castValueTo(Object value, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// Play safe: assume error unless explicitly overridden.\n\t\tthrow new PrismLangException(\"Cannot cast a value to type \" + getTypeString());\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn getTypeString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypeArray.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport java.util.*;\n\npublic class TypeArray extends Type \n{\n\tprivate static Map<Type, TypeArray> singletons;\n\t\n\tstatic\n\t{\n\t\tsingletons = new HashMap<Type, TypeArray>();\n\t}\n\t\n\tprivate Type subType;\n\t\n\tpublic TypeArray(Type subType)\n\t{\n\t\tthis.subType = subType;\n\t}\n\n\tpublic Type getSubType() \n\t{\n\t\treturn subType;\n\t}\n\n\tpublic void setSubType(Type subType) \n\t{\n\t\tthis.subType = subType;\n\t}\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o instanceof TypeArray)\n\t\t{\n\t\t\tTypeArray oa = (TypeArray)o;\n\t\t\treturn (subType.equals(oa.getSubType()));\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tpublic String getTypeString()\n\t{\n\t\treturn \"array of \" + subType.getTypeString();\n\t}\n\t\n\tpublic static TypeArray getInstance(Type subType)\n\t{\n\t\tif (!singletons.containsKey(subType))\n\t\t\tsingletons.put(subType, new TypeArray(subType));\n\t\t\t\n\t\treturn singletons.get(subType);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypeBool.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport parser.EvaluateContext.EvalMode;\nimport parser.ast.DeclarationBool;\nimport parser.ast.DeclarationType;\nimport prism.PrismLangException;\n\npublic class TypeBool extends Type \n{\n\tprivate static TypeBool singleton;\n\t\n\tstatic\n\t{\n\t\tsingleton = new TypeBool();\n\t}\t\n\t\n\tprivate TypeBool()\n\t{\t\t\n\t}\n\t\n\tpublic static TypeBool getInstance()\n\t{\n\t\treturn singleton;\n\t}\n\t\n\t// Methods required for Type:\n\t\n\t@Override\n\tpublic String getTypeString()\n\t{\n\t\treturn \"bool\";\n\t}\n\t\n\t@Override\n\tpublic boolean isPrimitive()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object defaultValue()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean canCastTypeTo(Type type)\n\t{\n\t\treturn (type instanceof TypeBool);\n\t}\n\t\n\t@Override\n\tpublic DeclarationType defaultDeclarationType()\n\t{\n\t\treturn new DeclarationBool();\n\t}\n\t\n\t@Override\n\tpublic Boolean castValueTo(Object value) throws PrismLangException\n\t{\n\t\tif (value instanceof Boolean) {\n\t\t\treturn (Boolean) value;\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Can't convert \" + value.getClass() + \" to type \" + getTypeString());\n\t\t}\n\t}\n\n\t@Override\n\tpublic Boolean castValueTo(Object value, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// Always a Boolean, regardless of evaluation mode\n\t\tif (value instanceof Boolean) {\n\t\t\treturn (Boolean) value;\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Can't convert \" + value.getClass() + \" to type \" + getTypeString());\n\t\t}\n\t}\n\t\n\t// Standard methods:\n\t\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof TypeBool);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypeClock.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport parser.EvaluateContext.EvalMode;\nimport prism.PrismLangException;\n\npublic class TypeClock extends Type \n{\n\tprivate static TypeClock singleton;\n\t\n\tstatic\n\t{\n\t\tsingleton = new TypeClock();\n\t}\n\t\n\tprivate TypeClock()\n\t{\t\t\n\t}\t\n\t\n\tpublic static TypeClock getInstance()\n\t{\n\t\treturn singleton;\n\t}\n\t\n\t// Methods required for Type:\n\t\n\t@Override\n\tpublic String getTypeString()\n\t{\n\t\treturn \"clock\";\n\t}\n\t\n\t@Override\n\tpublic boolean isPrimitive()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object defaultValue()\n\t{\n\t\treturn 0;\n\t}\n\t\n\t@Override\n\tpublic boolean canCastTypeTo(Type type)\n\t{\n\t\treturn (type instanceof TypeClock || TypeDouble.getInstance().canCastTypeTo(type));\n\t}\n\t\n\t@Override\n\tpublic Number castValueTo(Object value) throws PrismLangException\n\t{\n\t\t// Same as double so reuse code\n\t\t// (probably not used too often so performance not so relevant)\n\t\treturn TypeDouble.getInstance().castValueTo(value);\n\t}\n\t\n\t@Override\n\tpublic Number castValueTo(Object value, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// Same as double so reuse code\n\t\t// (probably not used too often so performance not so relevant)\n\t\treturn TypeDouble.getInstance().castValueTo(value, evalMode);\n\t}\n\n\t// Standard methods:\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof TypeClock);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypeDouble.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport java.math.BigInteger;\n\nimport param.BigRational;\nimport parser.EvaluateContext.EvalMode;\nimport parser.ast.DeclarationDoubleUnbounded;\nimport parser.ast.DeclarationType;\nimport prism.PrismLangException;\n\npublic class TypeDouble extends Type \n{\n\tprivate static TypeDouble singleton;\n\t\n\tstatic\n\t{\n\t\tsingleton = new TypeDouble();\n\t}\n\t\n\tprivate TypeDouble()\n\t{\t\t\n\t}\t\n\t\n\tpublic static TypeDouble getInstance()\n\t{\n\t\treturn singleton;\n\t}\n\t\n\t// Methods required for Type:\n\t\n\t@Override\n\tpublic String getTypeString()\n\t{\n\t\treturn \"double\";\n\t}\n\t\n\t@Override\n\tpublic boolean isPrimitive()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object defaultValue()\n\t{\n\t\treturn 0.0;\n\t}\n\t\n\t@Override\n\tpublic DeclarationType defaultDeclarationType()\n\t{\n\t\treturn new DeclarationDoubleUnbounded();\n\t}\n\t\n\t@Override\n\tpublic boolean canCastTypeTo(Type type)\n\t{\n\t\treturn (type instanceof TypeDouble || type instanceof TypeInt);\n\t}\n\t\n\t@Override\n\tpublic Number castValueTo(Object value) throws PrismLangException\n\t{\n\t\t// Convert from int to double if needed, ignore eval mode\n\t\tif (value instanceof Double) {\n\t\t\treturn (Double) value;\n\t\t}\n\t\tif (value instanceof BigRational) {\n\t\t\treturn (BigRational) value;\n\t\t}\n\t\tif (value instanceof Integer) {\n\t\t\treturn Double.valueOf(((Integer) value).intValue());\n\t\t}\n\t\tif (value instanceof BigInteger) {\n\t\t\treturn new BigRational((BigInteger) value);\n\t\t}\n\t\telse {\n\t\t\tthrow new PrismLangException(\"Can't convert \" + value.getClass() + \" to type \" + getTypeString());\n\t\t}\n\t}\n\n\t@Override\n\tpublic Number castValueTo(Object value, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tswitch (evalMode) {\n\t\t// For floating point mode, should be a Double\n\t\tcase FP:\n\t\t\t// Already a Double - nothing to do\n\t\t\tif (value instanceof Double) {\n\t\t\t\treturn (Double) value;\n\t\t\t}\n\t\t\t// Other possibilities (Integer/BigRational/BigInteger) are all Numbers\n\t\t\tif (value instanceof Number) {\n\t\t\t\treturn ((Number) value).doubleValue();\n\t\t\t}\n\t\t\tthrow new PrismLangException(\"Cannot cast \" + value.getClass() + \" to \" + getTypeString());\n\t\t// For exact mode, should be a BigRational\n\t\tcase EXACT:\n\t\t\t// Already a BigRational - nothing to do\n\t\t\tif (value instanceof BigRational) {\n\t\t\t\treturn (BigRational) value;\n\t\t\t}\n\t\t\t// Other possibilities (Integer/BigRational/BigInteger) need conversion\n\t\t\tif (value instanceof BigInteger) {\n\t\t\t\treturn new BigRational((BigInteger) value);\n\t\t\t}\n\t\t\tif (value instanceof Double) {\n\t\t\t\treturn new BigRational(value.toString());\n\t\t\t}\n\t\t\tif (value instanceof Integer) {\n\t\t\t\treturn new BigRational((Integer) value);\n\t\t\t}\n\t\t\tthrow new PrismLangException(\"Cannot cast \" + value.getClass() + \" to \" + getTypeString());\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t}\n\t}\n\n\t// Standard methods:\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof TypeDouble);\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypeInt.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport java.math.BigInteger;\n\nimport parser.EvaluateContext.EvalMode;\nimport parser.ast.DeclarationIntUnbounded;\nimport parser.ast.DeclarationType;\nimport prism.PrismLangException;\n\npublic class TypeInt extends Type \n{\n\tprivate static TypeInt singleton;\n\t\n\tstatic\n\t{\n\t\tsingleton = new TypeInt();\n\t}\n\t\n\tprivate TypeInt()\n\t{\t\t\n\t}\n\t\n\tpublic static TypeInt getInstance()\n\t{\n\t\treturn singleton;\n\t}\n\t\n\t// Methods required for Type:\n\t\n\t@Override\n\tpublic String getTypeString()\n\t{\n\t\treturn \"int\";\n\t}\n\t\n\t@Override\n\tpublic boolean isPrimitive()\n\t{\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic Object defaultValue()\n\t{\n\t\treturn 0;\n\t}\n\t\n\t@Override\n\tpublic DeclarationType defaultDeclarationType()\n\t{\n\t\treturn new DeclarationIntUnbounded();\n\t}\n\t\n\t@Override\n\tpublic boolean canCastTypeTo(Type type)\n\t{\n\t\treturn (type instanceof TypeInt);\n\t}\n\t\n\t@Override\n\tpublic Number castValueTo(Object value) throws PrismLangException\n\t{\n\t\tif (value instanceof Integer) {\n\t\t\treturn (Integer) value;\n\t\t} else if (value instanceof BigInteger) {\n\t\t\treturn (BigInteger) value;\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Can't convert \" + value.getClass() + \" to type \" + getTypeString());\n\t\t}\n\t}\n\n\t@Override\n\tpublic Number castValueTo(Object value, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tswitch (evalMode) {\n\t\t// For floating point mode, should be an Integer\n\t\tcase FP:\n\t\t\tif (value instanceof Integer) {\n\t\t\t\treturn (Integer) value;\n\t\t\t} else if (value instanceof BigInteger) {\n\t\t\t\treturn ((BigInteger) value).intValue();\n\t\t\t}\n\t\t\tthrow new PrismLangException(\"Cannot convert \" + value.getClass() + \" to \" + getTypeString());\n\t\t// For exact mode, should be a BigInteger\n\t\tcase EXACT:\n\t\t\tif (value instanceof BigInteger) {\n\t\t\t\treturn (BigInteger) value;\n\t\t\t} else if (value instanceof Integer) {\n\t\t\t\treturn BigInteger.valueOf((Integer) value);\n\t\t\t}\n\t\t\tthrow new PrismLangException(\"Cannot convert \" + value.getClass() + \" to \" + getTypeString());\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Unknown evaluation mode \" + evalMode);\n\t\t}\n\t}\n\n\t// Standard methods:\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof TypeInt);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypeInterval.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport java.math.BigInteger;\nimport java.util.HashMap;\nimport java.util.Map;\n\nimport common.Interval;\nimport param.BigRational;\nimport parser.EvaluateContext.EvalMode;\nimport prism.PrismLangException;\n\npublic class TypeInterval extends Type\n{\n\tprivate static Map<Type, TypeInterval> singletons;\n\t\n\tstatic\n\t{\n\t\tsingletons = new HashMap<Type, TypeInterval>();\n\t}\n\t\n\tprivate Type subType;\n\t\n\tprivate TypeInterval(Type subType)\n\t{\n\t\tthis.subType = subType;\n\t}\n\n\tpublic static TypeInterval getInstance(Type subType)\n\t{\n\t\treturn singletons.computeIfAbsent(subType, TypeInterval::new);\n\t}\n\n\tpublic Type getSubType()\n\t{\n\t\treturn subType;\n\t}\n\n\tpublic void setSubType(Type subType)\n\t{\n\t\tthis.subType = subType;\n\t}\n\n\t// Methods required for Type:\n\t\n\t@Override\n\tpublic String getTypeString()\n\t{\n\t\treturn \"interval of \" + subType.getTypeString();\n\t}\n\t\n\t@Override\n\tpublic boolean isPrimitive()\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object defaultValue()\n\t{\n\t\treturn new Interval<Object>(subType.defaultValue(), subType.defaultValue());\n\t}\n\t\n\t@Override\n\tpublic boolean canCastTypeTo(Type type)\n\t{\n\t\treturn type instanceof TypeDouble || type instanceof TypeInt || (type instanceof TypeInterval && getSubType().canCastTypeTo(((TypeInterval) type).getSubType()));\n\t}\n\t\n\t@Override\n\tpublic Interval<?> castValueTo(Object value) throws PrismLangException\n\t{\n\t\t// Scalar converts to singleton interval\n\t\tif (value instanceof Double || value instanceof Integer) {\n\t\t\tObject subValue = getSubType().castValueTo(value);\n\t\t\treturn new Interval<>(subValue, subValue);\n\t\t}\n\t\t// For interval, cast low/high\n\t\telse if (value instanceof Interval) {\n\t\t\tObject lower = getSubType().castValueTo(((Interval<?>) value).getLower());\n\t\t\tObject upper = getSubType().castValueTo(((Interval<?>) value).getUpper());\n\t\t\treturn new Interval<>(lower, upper);\n\t\t}\n\t\telse {\n\t\t\tthrow new PrismLangException(\"Can't convert \" + value.getClass() + \" to type \" + getTypeString());\n\t\t}\n\t}\n\n\t@Override\n\tpublic Interval<?> castValueTo(Object value, EvalMode evalMode) throws PrismLangException\n\t{\n\t\t// Scalar converts to singleton interval\n\t\tif (value instanceof Double || value instanceof Integer || value instanceof BigRational || value instanceof BigInteger) {\n\t\t\tObject subValue = getSubType().castValueTo(value, evalMode);\n\t\t\treturn new Interval<Object>(subValue, subValue);\n\t\t}\n\t\t// For interval, cast low/high\n\t\telse if (value instanceof Interval) {\n\t\t\tObject lower = getSubType().castValueTo(((Interval<?>) value).getLower(), evalMode);\n\t\t\tObject upper = getSubType().castValueTo(((Interval<?>) value).getUpper(), evalMode);\n\t\t\treturn new Interval<Object>(lower, upper);\n\t\t}\n\t\telse {\n\t\t\tthrow new PrismLangException(\"Can't convert \" + value.getClass() + \" to type \" + getTypeString());\n\t\t}\n\t}\n\n\t// Standard methods:\n\t\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o instanceof TypeInterval)\n\t\t{\n\t\t\tTypeInterval oi = (TypeInterval)o;\n\t\t\treturn (subType.equals(oi.getSubType()));\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypePathBool.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\npublic class TypePathBool extends Type \n{\n\tprivate static TypePathBool singleton;\n\t\n\tstatic\n\t{\n\t\tsingleton = new TypePathBool();\n\t}\n\t\n\tprivate TypePathBool()\n\t{\t\t\n\t}\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof TypePathBool);\n\t}\n\t\n\tpublic String getTypeString()\n\t{\n\t\treturn \"path-bool\";\n\t}\n\t\n\tpublic static TypePathBool getInstance()\n\t{\n\t\treturn singleton;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypePathDouble.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\npublic class TypePathDouble extends Type \n{\n\tprivate static TypePathDouble singleton;\n\t\n\tstatic\n\t{\n\t\tsingleton = new TypePathDouble();\n\t}\n\t\n\tprivate TypePathDouble()\n\t{\t\t\n\t}\t\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof TypePathDouble);\n\t}\n\t\n\tpublic String getTypeString()\n\t{\n\t\treturn \"path-double\";\n\t}\n\t\n\tpublic static TypePathDouble getInstance()\n\t{\n\t\treturn singleton;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypePathInt.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\npublic class TypePathInt extends Type \n{\n\tprivate static TypePathInt singleton;\n\t\n\tstatic\n\t{\n\t\tsingleton = new TypePathInt();\n\t}\n\n\tprivate TypePathInt()\n\t{\t\t\n\t}\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof TypePathInt);\n\t}\n\t\n\tpublic String getTypeString()\n\t{\n\t\treturn \"path-int\";\n\t}\n\t\n\tpublic static TypePathInt getInstance()\n\t{\n\t\treturn singleton;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/type/TypeUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport java.math.BigInteger;\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport param.BigRational;\nimport prism.PrismLangException;\n\n/**\n * Utility methods relating to types\n */\npublic class TypeUtils\n{\n\t/**\n\t * Guess the type for a value stored as an Object,\n\t * i.e., return a type which returns value of the same type of Object when evaluated. \n\t * Throws an exception if no type can be guessed. \n\t */\n\tpublic static Type guessTypeForValue(Object value) throws PrismLangException\n\t{\n\t\tif (value instanceof Boolean) {\n\t\t\treturn TypeBool.getInstance();\n\t\t}\n\t\tif (value instanceof Integer || value instanceof BigInteger) {\n\t\t\treturn TypeInt.getInstance();\n\t\t}\n\t\tif (value instanceof Double || value instanceof BigRational) {\n\t\t\treturn TypeDouble.getInstance();\n\t\t}\n\t\tthrow new PrismLangException(\"Cannot guess type for value \" + value);\n\t}\n\t\n\t/**\n\t * Guess the types for a list of values stored as Objects,\n\t * by applying {@link #guessTypeForValue(Object)} to each one.\n\t * Throws an exception if any type cannot be guessed. \n\t */\n\tpublic static List<Type> guessTypesForValues(List<Object> values) throws PrismLangException\n\t{\n\t\tList<Type> types = new ArrayList<>();\n\t\tfor (Object value : values) {\n\t\t\ttypes.add(guessTypeForValue(value));\n\t\t}\n\t\treturn types;\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/type/TypeVoid.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.type;\n\nimport parser.EvaluateContext.EvalMode;\nimport prism.PrismLangException;\n\npublic class TypeVoid extends Type \n{\n\tprivate static TypeVoid singleton;\n\t\n\tstatic\n\t{\n\t\tsingleton = new TypeVoid();\n\t}\n\t\n\tprivate TypeVoid()\n\t{\t\t\n\t}\t\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\treturn (o instanceof TypeVoid);\n\t}\n\t\n\t@Override\n\tpublic String getTypeString()\n\t{\n\t\treturn \"void\";\n\t}\n\t\n\t@Override\n\tpublic Object defaultValue()\n\t{\n\t\treturn null;\n\t}\n\t\n\tpublic static TypeVoid getInstance()\n\t{\n\t\treturn singleton;\n\t}\n\t\n\t@Override\n\tpublic boolean canCastTypeTo(Type type)\n\t{\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic Object castValueTo(Object value) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Can't convert \" + value.getClass() + \" to type \" + getTypeString());\n\t}\n\t\n\t@Override\n\tpublic Object castValueTo(Object value, EvalMode evalMode) throws PrismLangException\n\t{\n\t\tthrow new PrismLangException(\"Can't convert \" + value.getClass() + \" to type \" + getTypeString());\n\t}\n}"
  },
  {
    "path": "prism/src/parser/type/package-info.java",
    "content": "/**\n * Type system for the PRISM model/properties parser.\n */\npackage parser.type;\n"
  },
  {
    "path": "prism/src/parser/visitor/ASTTraverse.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n// Performs a depth-first traversal of an asbtract syntax tree (AST).\n// Many traversal-based tasks can be implemented by extending and either:\n// (a) overriding defaultVisitPre or defaultVisitPost\n// (b) overiding visit for leaf (or other selected) nodes\n// See also ASTTraverseModify.\n\npublic class ASTTraverse implements ASTVisitor\n{\n\tpublic void defaultVisitPre(ASTElement e) throws PrismLangException {}\n\tpublic void defaultVisitPost(ASTElement e) throws PrismLangException {}\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ModulesFile e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ModulesFile e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tif (e.getFormulaList() != null) e.getFormulaList().accept(this);\n\t\tif (e.getLabelList() != null) e.getLabelList().accept(this);\n\t\tif (e.getConstantList() != null) e.getConstantList().accept(this);\n\t\tn = e.getNumGlobals();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getGlobal(i) != null) e.getGlobal(i).accept(this);\n\t\t}\n\t\tn = e.getNumModules();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getModule(i) != null) e.getModule(i).accept(this);\n\t\t}\n\t\tif (e.getSystemDefn() != null) e.getSystemDefn().accept(this);\n\t\tn = e.getNumRewardStructs();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getRewardStruct(i) != null) e.getRewardStruct(i).accept(this);\n\t\t}\n\t\tif (e.getInitialStates() != null) e.getInitialStates().accept(this);\n\t\tn = e.getNumObservableVarLists();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getObservableVarList(i) != null) e.getObservableVarList(i).accept(this);\n\t\t}\n\t\tn = e.getNumObservableDefinitions();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getObservableDefinition(i) != null) e.getObservableDefinition(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ModulesFile e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(PropertiesFile e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(PropertiesFile e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tif (e.getLabelList() != null) e.getLabelList().accept(this);\n\t\tif (e.getConstantList() != null) e.getConstantList().accept(this);\n\t\tn = e.getNumProperties();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getPropertyObject(i) != null) e.getPropertyObject(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(PropertiesFile e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Property e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Property e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.getExpression().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(Property e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(FormulaList e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(FormulaList e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getFormula(i) != null) e.getFormula(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(FormulaList e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(LabelList e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(LabelList e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getLabel(i) != null) e.getLabel(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(LabelList e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ConstantList e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ConstantList e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getConstant(i) != null) e.getConstant(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ConstantList e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Declaration e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Declaration e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getDeclType() != null) e.getDeclType().accept(this);\n\t\tif (e.getStart() != null) e.getStart().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(Declaration e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationInt e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationInt e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getLow() != null) e.getLow().accept(this);\n\t\tif (e.getHigh() != null) e.getHigh().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(DeclarationInt e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationBool e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationBool e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(DeclarationBool e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationArray e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationArray e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getLow() != null) e.getLow().accept(this);\n\t\tif (e.getHigh() != null) e.getHigh().accept(this);\n\t\tif (e.getSubtype() != null) e.getSubtype().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(DeclarationArray e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationClock e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationClock e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(DeclarationClock e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationIntUnbounded e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationIntUnbounded e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(DeclarationIntUnbounded e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationDoubleUnbounded e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationDoubleUnbounded e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(DeclarationDoubleUnbounded e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(parser.ast.Module e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(parser.ast.Module e) throws PrismLangException\n\t{\n\t\t// Note: a few classes override this method (e.g. SemanticCheck)\n\t\t// so take care to update those versions if changing this method\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumDeclarations();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getDeclaration(i) != null) e.getDeclaration(i).accept(this);\n\t\t}\n\t\tif (e.getInvariant() != null)\n\t\t\te.getInvariant().accept(this);\n\t\tn = e.getNumCommands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getCommand(i) != null) e.getCommand(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(parser.ast.Module e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Command e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Command e) throws PrismLangException\n\t{\n\t\t// Note: a few classes override this method (e.g. SemanticCheck)\n\t\t// so take care to update those versions if changing this method\n\t\tvisitPre(e);\n\t\te.getGuard().accept(this);\n\t\te.getUpdates().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(Command e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Updates e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Updates e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumUpdates();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getProbability(i) != null) e.getProbability(i).accept(this);\n\t\t\tif (e.getUpdate(i) != null) e.getUpdate(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(Updates e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Update e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Update e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumElements();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getElement(i) != null) e.getElement(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(Update e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(UpdateElement e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(UpdateElement e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.getExpression().accept(this);\n\t\treturn null;\n\t}\n\tpublic void visitPost(UpdateElement e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(RenamedModule e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(RenamedModule e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(RenamedModule e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(RewardStruct e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(RewardStruct e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumItems();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getRewardStructItem(i) != null) e.getRewardStructItem(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(RewardStruct e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(RewardStructItem e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(RewardStructItem e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.getStates().accept(this);\n\t\te.getReward().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(RewardStructItem e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ObservableVars e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ObservableVars e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumVars();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getVar(i) != null) e.getVar(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ObservableVars e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Observable e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Observable e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getDefinition() != null) e.getDefinition().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(Observable e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemInterleaved e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemInterleaved e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.getOperand(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(SystemInterleaved e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemFullParallel e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemFullParallel e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.getOperand(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(SystemFullParallel e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemParallel e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemParallel e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.getOperand1().accept(this);\n\t\te.getOperand2().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(SystemParallel e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemHide e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemHide e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.getOperand().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(SystemHide e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemRename e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemRename e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.getOperand().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(SystemRename e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemModule e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemModule e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(SystemModule e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemBrackets e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemBrackets e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.getOperand().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(SystemBrackets e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemReference e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemReference e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(SystemReference e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionTemporal e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionTemporal e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getOperand1() != null) e.getOperand1().accept(this);\n\t\tif (e.getOperand2() != null) e.getOperand2().accept(this);\n\t\tif (e.getLowerBound() != null) e.getLowerBound().accept(this);\n\t\tif (e.getUpperBound() != null) e.getUpperBound().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionITE e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionITE e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.getOperand1().accept(this);\n\t\te.getOperand2().accept(this);\n\t\te.getOperand3().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionITE e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionBinaryOp e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionBinaryOp e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.getOperand1().accept(this);\n\t\te.getOperand2().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionBinaryOp e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionUnaryOp e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionUnaryOp e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.getOperand().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionUnaryOp e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionFunc e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionFunc e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.getOperand(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionFunc e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionIdent e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionIdent e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionIdent e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionLiteral e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionLiteral e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionLiteral e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionConstant e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionConstant e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionConstant e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionFormula e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionFormula e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getDefinition() != null) e.getDefinition().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionFormula e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionVar e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionVar e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionInterval e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionInterval e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getOperand1() != null) e.getOperand1().accept(this);\n\t\tif (e.getOperand2() != null) e.getOperand2().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionInterval e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionProb e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionProb e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getProb() != null) e.getProb().accept(this);\n\t\tif (e.getExpression() != null) e.getExpression().accept(this);\n\t\tif (e.getFilter() != null) e.getFilter().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionProb e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionReward e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionReward e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getRewardStructIndex() != null && e.getRewardStructIndex() instanceof Expression) ((Expression)e.getRewardStructIndex()).accept(this);\n\t\tif (e.getRewardStructIndexDiv() != null && e.getRewardStructIndexDiv() instanceof Expression) ((Expression)e.getRewardStructIndexDiv()).accept(this);\n\t\tif (e.getReward() != null) e.getReward().accept(this);\n\t\tif (e.getExpression() != null) e.getExpression().accept(this);\n\t\tif (e.getFilter() != null) e.getFilter().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionReward e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionSS e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionSS e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getProb() != null) e.getProb().accept(this);\n\t\tif (e.getExpression() != null) e.getExpression().accept(this);\n\t\tif (e.getFilter() != null) e.getFilter().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionSS e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionExists e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionExists e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.getExpression().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionExists e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionForAll e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionForAll e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.getExpression().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionForAll e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionStrategy e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionStrategy e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.getOperand(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionStrategy e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionLabel e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionLabel e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionObs e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionObs e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionObs e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionProp e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionProp e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionProp e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionFilter e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionFilter e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getFilter() != null) e.getFilter().accept(this);\n\t\tif (e.getOperand() != null) e.getOperand().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ExpressionFilter e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Filter e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Filter e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.getExpression().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(Filter e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ForLoop e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ForLoop e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getFrom() != null) e.getFrom().accept(this);\n\t\tif (e.getTo() != null) e.getTo().accept(this);\n\t\tif (e.getStep() != null) e.getStep().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\tpublic void visitPost(ForLoop e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/ASTTraverseModify.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n// Variant of ASTTraverse.\n// Performs a depth-first traversal of an asbtract syntax tree (AST),\n// replacing each child node with the object returned by the recursive visit call.\n// Like ASTTraverse, many traversal-based tasks can be implemented by extending and either:\n// (a) overriding defaultVisitPre or defaultVisitPost\n// (b) overiding visit for leaf (or other selected) nodes\n\npublic class ASTTraverseModify implements ASTVisitor\n{\n\tpublic void defaultVisitPre(ASTElement e) throws PrismLangException {}\n\tpublic void defaultVisitPost(ASTElement e) throws PrismLangException {}\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ModulesFile e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ModulesFile e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tif (e.getFormulaList() != null) e.setFormulaList((FormulaList)(e.getFormulaList().accept(this)));\n\t\tif (e.getLabelList() != null) e.setLabelList((LabelList)(e.getLabelList().accept(this)));\n\t\tif (e.getConstantList() != null) e.setConstantList((ConstantList)(e.getConstantList().accept(this)));\n\t\tn = e.getNumGlobals();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getGlobal(i) != null) e.setGlobal(i, (Declaration)(e.getGlobal(i).accept(this)));\n\t\t}\n\t\tn = e.getNumModules();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getModule(i) != null) e.setModule(i, (parser.ast.Module)(e.getModule(i).accept(this)));\n\t\t}\n\t\tn = e.getNumSystemDefns();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getSystemDefn(i) != null) e.setSystemDefn(i, (SystemDefn)(e.getSystemDefn(i).accept(this)), e.getSystemDefnName(i));\n\t\t}\n\t\tn = e.getNumRewardStructs();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getRewardStruct(i) != null) e.setRewardStruct(i, (RewardStruct)(e.getRewardStruct(i).accept(this)));\n\t\t}\n\t\tif (e.getInitialStates() != null) e.setInitialStates((Expression)(e.getInitialStates().accept(this)));\n\t\tn = e.getNumObservableVarLists();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getObservableVarList(i) != null) e.setObservableVarList(i, (ObservableVars) e.getObservableVarList(i).accept(this));\n\t\t}\n\t\tn = e.getNumObservableDefinitions();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getObservableDefinition(i) != null) e.setObservableDefinition(i, (Observable) e.getObservableDefinition(i).accept(this));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ModulesFile e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(PropertiesFile e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(PropertiesFile e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tif (e.getLabelList() != null) e.setLabelList((LabelList)(e.getLabelList().accept(this)));\n\t\tif (e.getConstantList() != null) e.setConstantList((ConstantList)(e.getConstantList().accept(this)));\n\t\tn = e.getNumProperties();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getPropertyObject(i) != null) e.setPropertyObject(i, (Property)(e.getPropertyObject(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(PropertiesFile e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\n\tpublic void visitPre(Property e) throws PrismLangException\n\t{\n\t\tdefaultVisitPre(e);\n\t}\n\n\tpublic Object visit(Property e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null)\n\t\t\te.setExpression((Expression) e.getExpression().accept(this));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\n\tpublic void visitPost(Property e) throws PrismLangException\n\t{\n\t\tdefaultVisitPost(e);\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(FormulaList e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(FormulaList e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getFormula(i) != null) e.setFormula(i, (Expression)(e.getFormula(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(FormulaList e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(LabelList e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(LabelList e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getLabel(i) != null) e.setLabel(i, (Expression)(e.getLabel(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(LabelList e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ConstantList e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ConstantList e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getConstant(i) != null) e.setConstant(i, (Expression)(e.getConstant(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ConstantList e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Declaration e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Declaration e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getDeclType() != null) e.setDeclType((DeclarationType)e.getDeclType().accept(this));\n\t\tif (e.getStart() != null) e.setStart((Expression)e.getStart().accept(this));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(Declaration e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationInt e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationInt e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getLow() != null) e.setLow((Expression)e.getLow().accept(this));\n\t\tif (e.getHigh() != null) e.setHigh((Expression)e.getHigh().accept(this));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(DeclarationInt e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationBool e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationBool e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(DeclarationBool e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationArray e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationArray e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getLow() != null) e.setLow((Expression)e.getLow().accept(this));\n\t\tif (e.getHigh() != null) e.setHigh((Expression)e.getHigh().accept(this));\n\t\tif (e.getSubtype() != null) e.setSubtype((DeclarationType)e.getSubtype().accept(this));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(DeclarationArray e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationClock e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationClock e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(DeclarationClock e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationIntUnbounded e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationIntUnbounded e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(DeclarationIntUnbounded e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(DeclarationDoubleUnbounded e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(DeclarationDoubleUnbounded e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(DeclarationDoubleUnbounded e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(parser.ast.Module e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(parser.ast.Module e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumDeclarations();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getDeclaration(i) != null) e.setDeclaration(i, (Declaration)(e.getDeclaration(i).accept(this)));\n\t\t}\n\t\tif (e.getInvariant() != null)\n\t\t\te.setInvariant((Expression)(e.getInvariant().accept(this)));\n\t\tn = e.getNumCommands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getCommand(i) != null) e.setCommand(i, (Command)(e.getCommand(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(parser.ast.Module e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Command e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Command e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setGuard((Expression)(e.getGuard().accept(this)));\n\t\te.setUpdates((Updates)(e.getUpdates().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(Command e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Updates e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Updates e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumUpdates();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getProbability(i) != null) e.setProbability(i, (Expression)(e.getProbability(i).accept(this)));\n\t\t\tif (e.getUpdate(i) != null) e.setUpdate(i, (Update)(e.getUpdate(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(Updates e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Update e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Update e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumElements();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getElement(i) != null) e.setElement(i, (UpdateElement)(e.getElement(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(Update e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(UpdateElement e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(UpdateElement e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.setExpression((Expression)(e.getExpression().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(UpdateElement e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(RenamedModule e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(RenamedModule e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(RenamedModule e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(RewardStruct e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(RewardStruct e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumItems();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getRewardStructItem(i) != null) e.setRewardStructItem(i, (RewardStructItem)(e.getRewardStructItem(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(RewardStruct e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(RewardStructItem e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(RewardStructItem e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setStates((Expression)(e.getStates().accept(this)));\n\t\te.setReward((Expression)(e.getReward().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(RewardStructItem e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ObservableVars e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ObservableVars e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumVars();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getVar(i) != null) e.setVar(i, (Expression)(e.getVar(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ObservableVars e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Observable e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Observable e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getDefinition() != null) e.setDefinition((Expression)(e.getDefinition().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(Observable e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemInterleaved e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemInterleaved e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.setOperand(i, (SystemDefn)(e.getOperand(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(SystemInterleaved e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemFullParallel e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemFullParallel e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.setOperand(i, (SystemDefn)(e.getOperand(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(SystemFullParallel e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemParallel e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemParallel e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setOperand1((SystemDefn)(e.getOperand1().accept(this)));\n\t\te.setOperand2((SystemDefn)(e.getOperand2().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(SystemParallel e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemHide e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemHide e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setOperand((SystemDefn)(e.getOperand().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(SystemHide e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemRename e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemRename e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setOperand((SystemDefn)(e.getOperand().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(SystemRename e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemModule e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemModule e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(SystemModule e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemBrackets e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemBrackets e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setOperand((SystemDefn)(e.getOperand().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(SystemBrackets e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(SystemReference e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(SystemReference e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(SystemReference e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionTemporal e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionTemporal e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getOperand1() != null) e.setOperand1((Expression)(e.getOperand1().accept(this)));\n\t\tif (e.getOperand2() != null) e.setOperand2((Expression)(e.getOperand2().accept(this)));\n\t\tif (e.getLowerBound() != null) e.setLowerBound((Expression)(e.getLowerBound().accept(this)), e.lowerBoundIsStrict());\n\t\tif (e.getUpperBound() != null) e.setUpperBound((Expression)(e.getUpperBound().accept(this)), e.upperBoundIsStrict());\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionITE e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionITE e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setOperand1((Expression)(e.getOperand1().accept(this)));\n\t\te.setOperand2((Expression)(e.getOperand2().accept(this)));\n\t\te.setOperand3((Expression)(e.getOperand3().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionITE e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionBinaryOp e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionBinaryOp e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setOperand1((Expression)(e.getOperand1().accept(this)));\n\t\te.setOperand2((Expression)(e.getOperand2().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionBinaryOp e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionUnaryOp e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionUnaryOp e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\te.setOperand((Expression)(e.getOperand().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionUnaryOp e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionFunc e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionFunc e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.setOperand(i, (Expression)(e.getOperand(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionFunc e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionIdent e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionIdent e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionIdent e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionLiteral e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionLiteral e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionLiteral e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionConstant e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionConstant e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionConstant e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionFormula e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionFormula e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getDefinition() != null) e.setDefinition((Expression)(e.getDefinition().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionFormula e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionVar e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionVar e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionInterval e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionInterval e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getOperand1() != null) e.setOperand1((Expression)(e.getOperand1().accept(this)));\n\t\tif (e.getOperand2() != null) e.setOperand2((Expression)(e.getOperand2().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionInterval e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionProb e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionProb e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getProb() != null) e.setProb((Expression)(e.getProb().accept(this)));\n\t\tif (e.getExpression() != null) e.setExpression((Expression)(e.getExpression().accept(this)));\n\t\tif (e.getFilter() != null) e.setFilter((Filter)(e.getFilter().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionProb e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionReward e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionReward e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getRewardStructIndex() != null && e.getRewardStructIndex() instanceof Expression)\n\t\t\te.setRewardStructIndex((Expression)(((Expression)e.getRewardStructIndex()).accept(this)));\n\t\tif (e.getRewardStructIndexDiv() != null && e.getRewardStructIndexDiv() instanceof Expression)\n\t\t\te.setRewardStructIndexDiv((Expression)(((Expression)e.getRewardStructIndexDiv()).accept(this)));\n\t\tif (e.getReward() != null) e.setReward((Expression)(e.getReward().accept(this)));\n\t\tif (e.getExpression() != null) e.setExpression((Expression)(e.getExpression().accept(this)));\n\t\tif (e.getFilter() != null) e.setFilter((Filter)(e.getFilter().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionReward e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionSS e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionSS e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getProb() != null) e.setProb((Expression)(e.getProb().accept(this)));\n\t\tif (e.getExpression() != null) e.setExpression((Expression)(e.getExpression().accept(this)));\n\t\tif (e.getFilter() != null) e.setFilter((Filter)(e.getFilter().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionSS e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionExists e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionExists e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.setExpression((Expression)(e.getExpression().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionExists e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionForAll e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionForAll e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.setExpression((Expression)(e.getExpression().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionForAll e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionStrategy e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionStrategy e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tint i, n = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.setOperand(i, (Expression)(e.getOperand(i).accept(this)));\n\t\t}\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionStrategy e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionLabel e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionLabel e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionObs e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionObs e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionObs e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionProp e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionProp e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionProp e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ExpressionFilter e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ExpressionFilter e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getFilter() != null) e.setFilter((Expression)(e.getFilter().accept(this)));\n\t\tif (e.getOperand() != null) e.setOperand((Expression)(e.getOperand().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ExpressionFilter e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(ForLoop e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(ForLoop e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getFrom() != null) e.setFrom((Expression)(e.getFrom().accept(this)));\n\t\tif (e.getTo() != null) e.setTo((Expression)(e.getTo().accept(this)));\n\t\tif (e.getStep() != null) e.setStep((Expression)(e.getStep().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(ForLoop e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n\tpublic void visitPre(Filter e) throws PrismLangException { defaultVisitPre(e); }\n\tpublic Object visit(Filter e) throws PrismLangException\n\t{\n\t\tvisitPre(e);\n\t\tif (e.getExpression() != null) e.setExpression((Expression)(e.getExpression().accept(this)));\n\t\tvisitPost(e);\n\t\treturn e;\n\t}\n\tpublic void visitPost(Filter e) throws PrismLangException { defaultVisitPost(e); }\n\t// -----------------------------------------------------------------------------------\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/ASTVisitor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\npublic interface ASTVisitor\n{\n\t// ASTElement classes (model/properties file)\n\tpublic Object visit(ModulesFile e) throws PrismLangException;\n\tpublic Object visit(PropertiesFile e) throws PrismLangException;\n\tpublic Object visit(Property e) throws PrismLangException;\n\tpublic Object visit(FormulaList e) throws PrismLangException;\n\tpublic Object visit(LabelList e) throws PrismLangException;\n\tpublic Object visit(ConstantList e) throws PrismLangException;\n\tpublic Object visit(Declaration e) throws PrismLangException;\n\tpublic Object visit(DeclarationInt e) throws PrismLangException;\n\tpublic Object visit(DeclarationBool e) throws PrismLangException;\n\tpublic Object visit(DeclarationArray e) throws PrismLangException;\n\tpublic Object visit(DeclarationClock e) throws PrismLangException;\n\tpublic Object visit(DeclarationIntUnbounded e) throws PrismLangException;\n\tpublic Object visit(DeclarationDoubleUnbounded e) throws PrismLangException;\n\tpublic Object visit(parser.ast.Module e) throws PrismLangException;\n\tpublic Object visit(Command e) throws PrismLangException;\n\tpublic Object visit(Updates e) throws PrismLangException;\n\tpublic Object visit(Update e) throws PrismLangException;\n\tpublic Object visit(UpdateElement e) throws PrismLangException;\n\tpublic Object visit(RenamedModule e) throws PrismLangException;\n\tpublic Object visit(RewardStruct e) throws PrismLangException;\n\tpublic Object visit(RewardStructItem e) throws PrismLangException;\n\tpublic Object visit(ObservableVars e) throws PrismLangException;\n\tpublic Object visit(Observable e) throws PrismLangException;\n\t// ASTElement/SystemDefn classes\n\tpublic Object visit(SystemInterleaved e) throws PrismLangException;\n\tpublic Object visit(SystemFullParallel e) throws PrismLangException;\n\tpublic Object visit(SystemParallel e) throws PrismLangException;\n\tpublic Object visit(SystemHide e) throws PrismLangException;\n\tpublic Object visit(SystemRename e) throws PrismLangException;\n\tpublic Object visit(SystemModule e) throws PrismLangException;\n\tpublic Object visit(SystemBrackets e) throws PrismLangException;\n\tpublic Object visit(SystemReference e) throws PrismLangException;\n\t// ASTElement/Expression classes\n\tpublic Object visit(ExpressionTemporal e) throws PrismLangException;\n\tpublic Object visit(ExpressionITE e) throws PrismLangException;\n\tpublic Object visit(ExpressionBinaryOp e) throws PrismLangException;\n\tpublic Object visit(ExpressionUnaryOp e) throws PrismLangException;\n\tpublic Object visit(ExpressionFunc e) throws PrismLangException;\n\tpublic Object visit(ExpressionIdent e) throws PrismLangException;\n\tpublic Object visit(ExpressionLiteral e) throws PrismLangException;\n\tpublic Object visit(ExpressionConstant e) throws PrismLangException;\n\tpublic Object visit(ExpressionFormula e) throws PrismLangException;\n\tpublic Object visit(ExpressionVar e) throws PrismLangException;\n\tpublic Object visit(ExpressionInterval e) throws PrismLangException;\n\tpublic Object visit(ExpressionProb e) throws PrismLangException;\n\tpublic Object visit(ExpressionReward e) throws PrismLangException;\n\tpublic Object visit(ExpressionSS e) throws PrismLangException;\n\tpublic Object visit(ExpressionExists e) throws PrismLangException;\n\tpublic Object visit(ExpressionForAll e) throws PrismLangException;\n\tpublic Object visit(ExpressionStrategy e) throws PrismLangException;\n\tpublic Object visit(ExpressionLabel e) throws PrismLangException;\n\tpublic Object visit(ExpressionObs e) throws PrismLangException;\n\tpublic Object visit(ExpressionProp e) throws PrismLangException;\n\tpublic Object visit(ExpressionFilter e) throws PrismLangException;\n\t// ASTElement classes (misc.)\n\tpublic Object visit(Filter e) throws PrismLangException;\n\tpublic Object visit(ForLoop e) throws PrismLangException;\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/CheckValid.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.ModelType;\n\n/**\n * Check expression (property) for validity with respect to a particular model type\n * (i.e. whether not it is a property that can be model checked for that model type).\n */\npublic class CheckValid extends ASTTraverse\n{\n\tprivate ModelType modelType = null;\n\n\tpublic CheckValid(ModelType modelType)\n\t{\n\t\tthis.modelType = modelType;\n\t}\n\n\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException\n\t{\n\t\t// R operator types restricted for some models\n\t\tif (modelType == ModelType.MDP) {\n\t\t\tif (e.getOperator() == ExpressionTemporal.R_S) {\n\t\t\t\tthrow new PrismLangException(\"Steady-state reward properties cannot be used for MDPs\");\n\t\t\t}\n\t\t}\n\t\telse if (modelType.realTime()) {\n\t\t\tif (e.getOperator() == ExpressionTemporal.R_C || e.getOperator() == ExpressionTemporal.R_I || e.getOperator() == ExpressionTemporal.R_S) {\n\t\t\t\tthrow new PrismLangException(\"Only reachability (F) reward properties can be used for \" + modelType + \"s\");\n\t\t\t}\n\t\t}\n\t\t// Real-time models only support upper time bounds\n\t\tif (e.getLowerBound() != null) {\n\t\t\tif (modelType.realTime()) {\n\t\t\t\tthrow new PrismLangException(\"Only upper time bounds are allowed on the \" + e.getOperatorSymbol()\n\t\t\t\t\t\t+ \" operator for \" + modelType + \"s\");\n\t\t\t}\n\t\t}\n\t\t// Apart from CTMCs, we only support integer time bounds\n\t\tif ((e.getUpperBound() != null && !(e.getUpperBound().getType() instanceof TypeInt)) ||\n\t\t    (e.getLowerBound() != null && !(e.getLowerBound().getType() instanceof TypeInt))) {\n\t\t\tif (modelType != ModelType.CTMC) {\n\t\t\t\tthrow new PrismLangException(\"Time bounds on the \" + e.getOperatorSymbol()\n\t\t\t\t\t\t+ \" operator must be integers for \" + modelType + \"s\");\n\t\t\t}\n\t\t}\n\t\t// Don't allow lower bounds on weak until - does not have intuitive semantics\n\t\tif (e.getOperator() == ExpressionTemporal.P_W && e.getLowerBound() != null) {\n\t\t\tthrow new PrismLangException(\"The weak until operator (W) with lower bounds is not yet supported\");\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionProb e) throws PrismLangException\n\t{\n\t\tif (modelType.nondeterministic() && e.getRelOp() == RelOp.EQ)\n\t\t\tthrow new PrismLangException(\"Can't use \\\"P=?\\\" for nondeterministic models; use \\\"Pmin=?\\\" or \\\"Pmax=?\\\"\");\n\t}\n\t\n\tpublic void visitPost(ExpressionReward e) throws PrismLangException\n\t{\n\t\tif (modelType.nondeterministic() && e.getRelOp() == RelOp.EQ)\n\t\t\tthrow new PrismLangException(\"Can't use \\\"R=?\\\" for nondeterministic models; use \\\"Rmin=?\\\" or \\\"Rmax=?\\\"\");\n\t\tif (e.getRewardStructIndexDiv() != null)\n\t\t\tthrow new PrismLangException(\"No support for ratio reward objectives yet\");\n\t}\n\t\n\tpublic void visitPost(ExpressionSS e) throws PrismLangException\n\t{\n\t\t// S operator only works for some models\n\t\tif (modelType == ModelType.MDP || modelType.realTime()) {\n\t\t\tthrow new PrismLangException(\"The S operator cannot be used for \" + modelType + \"s\");\n\t\t}\n\t\t/*if (modelType.nondeterministic() && e.getRelOp() == RelOp.EQ)\n\t\t\tthrow new PrismLangException(\"Can't use \\\"S=?\\\" for nondeterministic models; use \\\"Smin=?\\\" or \\\"Smax=?\\\"\");*/\n\t}\n\n\tpublic void visitPost(ExpressionStrategy e) throws PrismLangException\n\t{\n\t\tif (!modelType.nondeterministic())\n\t\t\tthrow new PrismLangException(\"The \" + e.getOperatorString() + \" operator is only meaningful for models with nondeterminism\");\n\t\t// Currently (for non-games), <<>> or [[]] can only contain \"*\" or \"\" \n\t\tCoalition coalition = e.getCoalition();\n\t\tif (!(coalition.isAllPlayers() || coalition.isEmpty())) {\n\t\t\tthrow new PrismLangException(\"The \" + e.getOperatorString() + \" operator must contain either \\\"*\\\" or be empty for an \" + modelType);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/ComputeProbNesting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n/**\n * Compute (maximum) number of nested probabilistic operators (P, S, R).\n */\npublic class ComputeProbNesting extends ASTTraverse\n{\n\t// Optional properties file to look up property references;\n\tPropertiesFile propertiesFile = null;\n\t\n\tprivate int currentNesting;\n\tprivate int maxNesting;\n\t\n\tpublic ComputeProbNesting()\n\t{\n\t\tthis(null);\n\t}\n\n\tpublic ComputeProbNesting(PropertiesFile propertiesFile)\n\t{\n\t\tthis.propertiesFile = propertiesFile;\n\t\tcurrentNesting = 0;\n\t\tmaxNesting = 0;\n\t}\n\n\tpublic int getMaxNesting()\n\t{\n\t\treturn maxNesting;\n\t}\n\t\n\tpublic void visitPre(ExpressionProb e) throws PrismLangException\n\t{\n\t\tcurrentNesting++;\n\t\tmaxNesting = Math.max(maxNesting, currentNesting);\n\t}\n\n\tpublic void visitPost(ExpressionProb e) throws PrismLangException\n\t{\n\t\tcurrentNesting--;\n\t}\n\n\tpublic void visitPre(ExpressionReward e) throws PrismLangException\n\t{\n\t\tcurrentNesting++;\n\t\tmaxNesting = Math.max(maxNesting, currentNesting);\n\t}\n\n\tpublic void visitPost(ExpressionReward e) throws PrismLangException\n\t{\n\t\tcurrentNesting--;\n\t}\n\n\tpublic void visitPre(ExpressionSS e) throws PrismLangException\n\t{\n\t\tcurrentNesting++;\n\t\tmaxNesting = Math.max(maxNesting, currentNesting);\n\t}\n\t\n\tpublic void visitPost(ExpressionSS e) throws PrismLangException\n\t{\n\t\tcurrentNesting--;\n\t}\n\t\n\tpublic void visitPost(ExpressionProp e) throws PrismLangException\n\t{\n\t\t// If possible, look up property and recurse\n\t\tif (propertiesFile != null) {\n\t\t\tProperty prop = propertiesFile.lookUpPropertyObjectByName(e.getName());\n\t\t\tif (prop != null) {\n\t\t\t\tprop.accept(this);\n\t\t\t} else {\n\t\t\t\tthrow new PrismLangException(\"Unknown property reference \" + e, e);\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/ConvertForJltl2ba.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Carlos S. Bederián (Universidad Nacional de Córdoba)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport java.util.HashMap;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\nimport jltl2ba.*;\nimport parser.type.*;\n\n/*\n * Convert a property expression (an LTL formula) into the classes used by\n * the jltl2ba (and jltl2dstar) libraries.\n *\n * Optionally, during this conversion, identical subtrees are shared, i.e.,\n * the resulting SimpleLTL structure is a directed acyclic graph (DAG)\n * instead of a tree. This is controlled via the {@code allowSharing} flag.\n *\n * Note that, currently, the jltl2ba LTL to NBA translator requires that the\n * SimpleLTL formula does not share subtrees.\n */\npublic class ConvertForJltl2ba\n{\n\t/** Flag: allow sharing (produce DAG instead of tree) */\n\tprivate boolean allowSharing = true;\n\t/** Hash map to lookup already translated subformulas (if sharing is allowed) */\n\tprivate HashMap<ASTElement, SimpleLTL> formulas = null;\n\n\t/** Default constructor (don't allow sharing) */\n\tpublic ConvertForJltl2ba()\n\t{\n\t\tthis(false);\n\t}\n\n\t/**\n\t * Constructor\n\t * @param allowSharing Flag: allow sharing (produce DAG instead of tree)\n\t */\n\tpublic ConvertForJltl2ba(boolean allowSharing)\n\t{\n\t\tthis.allowSharing = allowSharing;\n\t\tif (allowSharing) {\n\t\t\tformulas = new HashMap<ASTElement, SimpleLTL>();\n\t\t}\n\t}\n\n\t/** Convert expression to a SimpleLTL formula */\n\tpublic SimpleLTL convert(Expression e) throws PrismLangException\n\t{\n\t\tSimpleLTL res = null;\n\n\t\tif (allowSharing) {\n\t\t\t// if sharing is allowed, lookup the expression and return\n\t\t\t// a previously converted SimpleLTL if available\n\t\t\tres = getFormula(e);\n\t\t\tif (res != null) {\n\t\t\t\treturn res;\n\t\t\t}\n\t\t}\n\n\t\t// do the actual conversion\n\t\tif (e instanceof ExpressionTemporal) {\n\t\t\tres = convertTemporal((ExpressionTemporal)e);\n\t\t} else if (e instanceof ExpressionBinaryOp) {\n\t\t\tres = convertBinaryOp((ExpressionBinaryOp)e);\n\t\t} else if (e instanceof ExpressionUnaryOp) {\n\t\t\tres = convertUnaryOp((ExpressionUnaryOp)e);\n\t\t} else if (e instanceof ExpressionLiteral) {\n\t\t\tres = convertLiteral((ExpressionLiteral)e);\n\t\t} else if (e instanceof ExpressionLabel) {\n\t\t\tres = convertLabel((ExpressionLabel)e);\n\t\t}\n\n\t\tif (allowSharing) {\n\t\t\t// store converted formula if sharing is allowed\n\t\t\tsetFormula(e, res);\n\t\t}\n\t\treturn res;\n\t}\n\n\t/** Helper: store converted formula in hash map */\n\tprivate Object setFormula(ASTElement e, SimpleLTL formula)\n\t{\n\t\treturn formulas.put(e, formula);\n\t}\n\n\t/** Helper: lookup formula in hash map */\n\tprivate SimpleLTL getFormula(ASTElement e)\n\t{\n\t\treturn formulas.get(e);\n\t}\n\n\t/** Convert ExpressionTemporal to a SimpleLTL formula */\n\tprivate SimpleLTL convertTemporal(ExpressionTemporal e) throws PrismLangException\n\t{\n\t\tSimpleLTL ltl1 = null, ltl2 = null, res = null;\n\t\tExpression until;\n\t\tif (e.getOperand1() != null) ltl1 = convert(e.getOperand1());\n\t\tif (e.getOperand2() != null) ltl2 = convert(e.getOperand2());\n\t\tif (e.hasBounds()) {\n\t\t\tthrow new PrismLangException(\"Can not convert expression with temporal bounds to SimpleLTL: \" + e);\n\t\t}\n\t\tswitch (e.getOperator()) {\n\t\tcase ExpressionTemporal.P_X:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.NEXT, ltl2);\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.P_U:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.UNTIL, ltl1, ltl2);\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.P_F:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.FINALLY, ltl2);\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.P_G:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.GLOBALLY, ltl2);\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.P_W:\n\t\tcase ExpressionTemporal.P_R:\n\t\t\tuntil = e.convertToUntilForm();\n\t\t\tif (allowSharing) {\n\t\t\t\tres = getFormula(until);\n\t\t\t}\n\t\t\tif (res == null) {\n\t\t\t\t// convert normally\n\t\t\t\tres = convert(until);\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Cannot convert expression to jltl2ba form\", e);\n\t\t}\n\t\treturn res;\n\t}\n\n\t/** Convert ExpressionBinaryOp to a SimpleLTL formula */\n\tprivate SimpleLTL convertBinaryOp(ExpressionBinaryOp e) throws PrismLangException\n\t{\n\t\tSimpleLTL ltl1 = null, ltl2 = null, res = null;\n\t\tif (e.getOperand1() != null) ltl1 = convert(e.getOperand1());\n\t\tif (e.getOperand2() != null) ltl2 = convert(e.getOperand2());\n\t\tswitch (e.getOperator()) {\n\t\tcase ExpressionBinaryOp.IMPLIES:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.IMPLIES, ltl1, ltl2);\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.IFF:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.EQUIV, ltl1, ltl2);\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.OR:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.OR, ltl1, ltl2);\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.AND:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.AND, ltl1, ltl2);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Cannot convert expression to jltl2ba form\", e);\n\t\t}\n\t\treturn res;\n\t}\n\n\t/** Convert ExpressionUnaryOp to a SimpleLTL formula */\n\tprivate SimpleLTL convertUnaryOp(ExpressionUnaryOp e) throws PrismLangException\n\t{\n\t\tSimpleLTL ltl1 = null, res = null;\n\t\tif (e.getOperand() != null) ltl1 = convert(e.getOperand());\n\t\tswitch (e.getOperator()) {\n\t\tcase ExpressionUnaryOp.NOT:\n\t\t\tres = new SimpleLTL(SimpleLTL.LTLType.NOT, ltl1);\n\t\t\tbreak;\n\t\tcase ExpressionUnaryOp.PARENTH:\n\t\t\tres = ltl1;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Cannot convert expression to jltl2ba form\", e);\n\t\t}\n\t\treturn res;\n\t}\n\n\t/** Convert ExpressionLiteral to a SimpleLTL formula */\n\tprivate SimpleLTL convertLiteral(ExpressionLiteral e) throws PrismLangException\n\t{\n\t\tif (!(e.getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Cannot convert expression to jltl2ba form\", e);\n\t\t}\n\t\treturn new SimpleLTL(e.evaluateBoolean());\n\t}\n\n\t/** Convert ExpressionLabel to a SimpleLTL formula */\n\tprivate SimpleLTL convertLabel(ExpressionLabel e) throws PrismLangException\n\t{\n\t\treturn new SimpleLTL(e.getName());\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/DeepCopy.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Max Kurze <Max.Kurze@mailbox.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\n\nimport java.util.List;\nimport java.util.ListIterator;\n\nimport parser.ast.ASTElement;\nimport parser.ast.Command;\nimport parser.ast.ConstantList;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationArray;\nimport parser.ast.DeclarationBool;\nimport parser.ast.DeclarationClock;\nimport parser.ast.DeclarationDoubleUnbounded;\nimport parser.ast.DeclarationInt;\nimport parser.ast.DeclarationIntUnbounded;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.ExpressionExists;\nimport parser.ast.ExpressionFilter;\nimport parser.ast.ExpressionForAll;\nimport parser.ast.ExpressionFormula;\nimport parser.ast.ExpressionFunc;\nimport parser.ast.ExpressionITE;\nimport parser.ast.ExpressionIdent;\nimport parser.ast.ExpressionInterval;\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionLiteral;\nimport parser.ast.ExpressionObs;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionProp;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionSS;\nimport parser.ast.ExpressionStrategy;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.ast.ExpressionVar;\nimport parser.ast.Filter;\nimport parser.ast.ForLoop;\nimport parser.ast.FormulaList;\nimport parser.ast.LabelList;\nimport parser.ast.Module;\nimport parser.ast.ModulesFile;\nimport parser.ast.Observable;\nimport parser.ast.ObservableVars;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport parser.ast.RenamedModule;\nimport parser.ast.RewardStruct;\nimport parser.ast.RewardStructItem;\nimport parser.ast.SystemBrackets;\nimport parser.ast.SystemFullParallel;\nimport parser.ast.SystemHide;\nimport parser.ast.SystemInterleaved;\nimport parser.ast.SystemModule;\nimport parser.ast.SystemParallel;\nimport parser.ast.SystemReference;\nimport parser.ast.SystemRename;\nimport parser.ast.Update;\nimport parser.ast.UpdateElement;\nimport parser.ast.Updates;\nimport prism.PrismLangException;\n\n/**\n * DeepCopy is a visitor that copies an AST.\n * <p>\n * For copying it provides the methods {@link DeepCopy#copy} and {@link DeepCopy#copyAll} and relies\n * on {@link ASTElement#deepCopy(DeepCopy)}.\n * </p>\n *\n * @see ASTElement#deepCopy(DeepCopy)\n */\npublic class DeepCopy implements ASTVisitor\n{\n\t/**\n\t * Copy an ASTElement or null.\n\t *\n\t * @param element the element to be copied or null\n\t * @return copy of the element or null\n\t * @throws PrismLangException\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic <T extends ASTElement> T copy(T element) throws PrismLangException\n\t{\n\t\treturn (element == null) ? null : (T) element.accept(this);\n\t}\n\n\t/**\n\t * Copy all ASTElements (or null) in the collection.\n\t *\n\t * @param list list of elements to be copied\n\t * @return the argument list with all elements copied\n\t * @throws PrismLangException\n\t */\n\tpublic <T extends ASTElement> List<T> copyAll(List<T> list) throws PrismLangException\n\t{\n\t\tif (list == null)\n\t\t\treturn null;\n\n\t\tListIterator<T> iter = list.listIterator();\n\t\twhile (iter.hasNext()) {\n\t\t\titer.set(copy(iter.next()));\n\t\t}\n\t\treturn list;\n\t}\n\n\t@Override\n\tpublic Object visit(ModulesFile e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(PropertiesFile e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(Property e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(FormulaList e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(LabelList e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ConstantList e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(Declaration e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(DeclarationInt e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(DeclarationBool e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(DeclarationArray e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(DeclarationClock e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(DeclarationIntUnbounded e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(DeclarationDoubleUnbounded e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(Module e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(Command e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(Updates e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(Update e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(UpdateElement e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(RenamedModule e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(RewardStruct e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(RewardStructItem e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ObservableVars e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(Observable e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(SystemInterleaved e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(SystemFullParallel e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(SystemParallel e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(SystemHide e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(SystemRename e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(SystemModule e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(SystemBrackets e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(SystemReference e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionTemporal e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionITE e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionBinaryOp e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionUnaryOp e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionFunc e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionIdent e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionLiteral e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionConstant e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionFormula e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionInterval e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionProb e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionReward e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionSS e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionExists e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionForAll e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionStrategy e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionObs e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionProp e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionFilter e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(Filter e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n\n\t@Override\n\tpublic Object visit(ForLoop e) throws PrismLangException\n\t{\n\t\treturn e.clone().deepCopy(this);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/EvaluatePartially.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.*;\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n/**\n * Evaluate partially: replace some constants and variables with actual values. \n */\npublic class EvaluatePartially extends ASTTraverseModify\n{\n\tprivate EvaluateContext ec;\n\t\n\tpublic EvaluatePartially(EvaluateContext ec)\n\t{\n\t\tthis.ec = ec;\n\t}\n\t\n\tpublic Object visit(ExpressionConstant e) throws PrismLangException\n\t{\n\t\tObject val = ec.getConstantValue(e.getName());\n\t\tif (val == null) {\n\t\t\treturn e;\n\t\t} else {\n\t\t\treturn new ExpressionLiteral(e.getType(), val);\n\t\t}\n\t}\n\t\n\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t{\n\t\tObject val = ec.getVarValue(e.getName(), e.getIndex());\n\t\tif (val == null) {\n\t\t\treturn e;\n\t\t} else {\n\t\t\treturn new ExpressionLiteral(e.getType(), val);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/ExpandConstants.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.PrismLangException;\n\n/**\n * Expand constants whose definitions are contained in the supplied ConstantList.\n */\npublic class ExpandConstants extends ASTTraverseModify\n{\n\tprivate ConstantList constantList;\n\tprivate boolean all;\n\t\n\t/**\n\t * @param constantList The ConstantList containing definitions\n\t */\n\tpublic ExpandConstants(ConstantList constantList)\n\t{\n\t\tthis(constantList, true);\n\t}\n\t\n\t/**\n\t * @param constantList The ConstantList containing definitions\n\t * @param all If true, an exception is thrown if any constants are undefined\n\t */\n\tpublic ExpandConstants(ConstantList constantList, boolean all)\n\t{\n\t\tthis.constantList = constantList;\n\t\tthis.all = all;\n\t}\n\t\n\t@Override\n\tpublic Object visit(ExpressionConstant e) throws PrismLangException\n\t{\n\t\t// See if identifier corresponds to a constant defined in the list\n\t\tint i = constantList.getConstantIndex(e.getName());\n\t\tif (i != -1 && constantList.getConstant(i) != null) {\n\t\t\t// If so, replace it with the corresponding expression\n\t\t\tExpression expr = constantList.getConstant(i).deepCopy();\n\t\t\t// But also recursively expand that\n\t\t\texpr = (Expression) expr.expandConstants(constantList, all);\n\t\t\t// Put in brackets so precedence is preserved\n\t\t\t// (for display purposes only; in case of re-parse)\n\t\t\t// This is being done after type-checking so also set type\n\t\t\tType t = expr.getType();\n\t\t\texpr = Expression.Parenth(expr);\n\t\t\texpr.setType(t);\n\t\t\t// Return replacement expression\n\t\t\treturn expr;\n\t\t}\n\t\t// Otherwise, either return unchanged or complain (depending on 'all')\n\t\tif (all) {\n\t\t\tthrow new PrismLangException(\"Undefined constant\", e);\n\t\t} else {\n\t\t\treturn e;\n\t\t}\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/ExpandFormulas.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.PrismLangException;\n\n/**\n * Expand all formulas, return result.\n */\npublic class ExpandFormulas extends ASTTraverseModify\n{\n\t// The FormulaList for formula definitions\n\tprivate FormulaList formulaList;\n\t // Whether to replace formulas outright with their definition\n\t // (true for use in models since they may be subjected to renaming afterwards;\n\t // false for properties since it is cleaner just to have the name there when displayed)\n\tprivate boolean replace;\n\t\n\tpublic ExpandFormulas(FormulaList formulaList, boolean replace)\n\t{\n\t\tthis.formulaList = formulaList;\n\t\tthis.replace = replace;\n\t}\n\t\n\tpublic Object visit(ExpressionFormula e) throws PrismLangException\n\t{\n\t\tint i;\n\t\tType t;\n\t\tExpression expr;\n\t\t\n\t\t// See if identifier corresponds to a formula\n\t\ti = formulaList.getFormulaIndex(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, replace it with the corresponding expression\n\t\t\texpr = formulaList.getFormula(i);\n\t\t\t// But also recursively expand that\n\t\t\t// (don't clone it to avoid duplication of work)\n\t\t\texpr = (Expression)expr.expandFormulas(formulaList, replace);\n\t\t\t// Put in brackets so precedence is preserved\n\t\t\t// (for display purposes only; in case of re-parse)\n\t\t\texpr = Expression.Parenth(expr);\n\t\t\t// This is probably being done before type-checking so\n\t\t\t// don't really need to preserve type, but do so just in case\n\t\t\tt = expr.getTypeIfDefined();\n\t\t\texpr = Expression.Parenth(expr);\n\t\t\texpr.setType(t);\n\t\t\t// Return replacement expression\n\t\t\t// (or just set definition and return)\n\t\t\tif (replace) {\n\t\t\t\treturn expr;\n\t\t\t} else {\n\t\t\t\te.setDefinition(expr);\n\t\t\t\treturn e;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Couldn't find definition - leave unchanged.\n\t\treturn e;\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/ExpandLabels.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.PrismLangException;\n\n/**\n * Expand labels, return result.\n * Special labels \"deadlock\", \"init\" and any not in list are left.\n */\npublic class ExpandLabels extends ASTTraverseModify\n{\n\t// The LabelList for label definitions\n\tprivate LabelList labelList;\n\t\n\tpublic ExpandLabels(LabelList labelList)\n\t{\n\t\tthis.labelList = labelList;\n\t}\n\t\n\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tint i;\n\t\tType t;\n\t\tExpression expr;\n\t\t\n\t\t// See if identifier corresponds to a label\n\t\ti = labelList.getLabelIndex(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, replace it with (a copy of) the corresponding expression\n\t\t\texpr = labelList.getLabel(i).deepCopy();\n\t\t\t// But also recursively expand that\n\t\t\t// (nested labels not currently supported but may be one day)\n\t\t\t// (don't clone it to avoid duplication of work)\n\t\t\texpr = (Expression) expr.accept(this);\n\t\t\t// Put in brackets so precedence is preserved\n\t\t\t// (for display purposes only; in case of re-parse)\n\t\t\t// Also, preserve type (this is probably being done before\n\t\t\t// type-checking so unnecessary, but do so just in case)\n\t\t\tt = expr.getType();\n\t\t\texpr = Expression.Parenth(expr);\n\t\t\texpr.setType(t);\n\t\t\t// Return replacement expression\n\t\t\treturn expr;\n\t\t}\n\t\t\n\t\t// Couldn't find definition - leave unchanged.\n\t\treturn e;\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/ExpandPropRefsAndLabels.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.PrismLangException;\n\n/**\n * Expand property references and labels, return result.\n * Property expansion is done recursively.\n * Either properties file or label list can be omitted (set to null)\n * Special labels \"deadlock\", \"init\" and any not in label list are left.\n */\npublic class ExpandPropRefsAndLabels extends ASTTraverseModify\n{\n\t// The PropertiesFile for property lookup\n\tprivate PropertiesFile propertiesFile;\n\t// The LabelList for label definitions\n\tprivate LabelList labelList;\n\t\n\tpublic ExpandPropRefsAndLabels(PropertiesFile propertiesFile, LabelList labelList)\n\t{\n\t\tthis.propertiesFile = propertiesFile;\n\t\tthis.labelList = labelList;\n\t}\n\t\n\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tint i;\n\t\tType t;\n\t\tExpression expr;\n\t\t\n\t\t// Skip this if label list is missing\n\t\tif (labelList == null) {\n\t\t\treturn e;\n\t\t}\n\t\t\n\t\t// See if identifier corresponds to a label\n\t\ti = labelList.getLabelIndex(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, replace it with (a copy of) the corresponding expression\n\t\t\texpr = labelList.getLabel(i).deepCopy();\n\t\t\t// But also recursively expand that\n\t\t\t// (nested labels not currently supported but may be one day)\n\t\t\t// (don't clone it to avoid duplication of work)\n\t\t\texpr = (Expression) expr.accept(this);\n\t\t\t// Put in brackets so precedence is preserved\n\t\t\t// (for display purposes only; in case of re-parse)\n\t\t\t// Also, preserve type (this is probably being done before\n\t\t\t// type-checking so unnecessary, but do so just in case)\n\t\t\tt = expr.getType();\n\t\t\texpr = Expression.Parenth(expr);\n\t\t\texpr.setType(t);\n\t\t\t// Return replacement expression\n\t\t\treturn expr;\n\t\t}\n\t\t\n\t\t// Couldn't find definition - leave unchanged.\n\t\treturn e;\n\t}\n\n\tpublic Object visit(ExpressionProp e) throws PrismLangException\n\t{\n\t\tProperty prop;\n\t\tType t;\n\t\tExpression expr;\n\t\t\n\t\t// Skip this if label list is missing\n\t\tif (propertiesFile == null) {\n\t\t\treturn e;\n\t\t}\n\t\t\n\t\t// See if name corresponds to a property\n\t\tprop = propertiesFile.lookUpPropertyObjectByName(e.getName());\n\t\tif (prop != null) {\n\t\t\t// If so, replace it with (a copy of) the corresponding expression\n\t\t\texpr = prop.getExpression().deepCopy();\n\t\t\t// But also recursively expand that\n\t\t\t// (don't clone it to avoid duplication of work)\n\t\t\texpr = (Expression) expr.accept(this);\n\t\t\t// Put in brackets so precedence is preserved\n\t\t\t// (for display purposes only; in case of re-parse)\n\t\t\t// Also, preserve type (this is probably being done before\n\t\t\t// type-checking so unnecessary, but do so just in case)\n\t\t\tt = expr.getType();\n\t\t\texpr = Expression.Parenth(expr);\n\t\t\texpr.setType(t);\n\t\t\t// Return replacement expression\n\t\t\treturn expr;\n\t\t}\n\t\t\n\t\t// Couldn't find definition - leave unchanged.\n\t\treturn e;\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/ExpressionTraverseNonNested.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionSS;\nimport prism.PrismLangException;\n\n/**\n * Base class for recursively traversing an Expression, but not\n * entering nested P/R/SS subexpressions.\n *\n * By default, will not recurse into the P/R/SS elements, but\n * can be configured to allow a certain amount of nested P/R/SS\n * elements before stopping.\n *\n * <br/>\n * Subclasses should not override<br/>\n * <ul>\n *  <li>{@code visit(ExpressionProb)}</li>\n *  <li>{@code visit(ExpressionReward)}</li>\n *  <li>{@code visit(ExpressionSS)}</li>\n * </ul>\n */\npublic class ExpressionTraverseNonNested extends ASTTraverse\n{\n\t/** the current nesting level */\n\tprivate int currentNesting;\n\t/** the maximal nesting level that still allows recursion */\n\tprivate int nestingLimit;\n\n\t/** Constructor, defaulting to \"no nesting\" */\n\tpublic ExpressionTraverseNonNested()\n\t{\n\t\tthis(0);\n\t}\n\n\t/** Constructor, with \"stop recursion after {@code nestingLimit} nestings\" */\n\tpublic ExpressionTraverseNonNested(int nestingLimit)\n\t{\n\t\tcurrentNesting = 0;\n\t\tthis.nestingLimit = 0;\n\t}\n\n\t/** Are we still allowed to recurse? */\n\tprivate boolean inLimit()\n\t{\n\t\treturn currentNesting <= nestingLimit;\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionProb e) throws PrismLangException\n\t{\n\t\tcurrentNesting++;\n\t\t// only visit if we are still in limit\n\t\tif (!inLimit()) {\n\t\t\tcurrentNesting--;\n\t\t\treturn null;\n\t\t}\n\t\tObject rv = super.visit(e);\n\t\tcurrentNesting--;\n\t\treturn rv;\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionReward e) throws PrismLangException\n\t{\n\t\tcurrentNesting++;\n\t\t// only visit if we are still in limit\n\t\tif (!inLimit()) {\n\t\t\tcurrentNesting--;\n\t\t\treturn null;\n\t\t}\n\t\tObject rv = super.visit(e);\n\t\tcurrentNesting--;\n\t\treturn rv;\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionSS e) throws PrismLangException\n\t{\n\t\tcurrentNesting++;\n\t\t// only visit if we are still in limit\n\t\tif (!inLimit()) {\n\t\t\tcurrentNesting--;\n\t\t\treturn null;\n\t\t}\n\t\tObject rv = super.visit(e);\n\t\tcurrentNesting--;\n\t\treturn rv;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/FindAllActions.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport java.util.*;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n/**\n * Find all references to action labels, check they exist and, if required,\n * store their index locally (as defined by the containing ModuleFile).\n */\npublic class FindAllActions extends ASTTraverseModify\n{\n\tprivate List<String> synchs;\n\t\n\tpublic FindAllActions(List<String> synchs)\n\t{\n\t\tthis.synchs = synchs;\n\t}\n\t\n\t// Note that this is done with VisitPost, i.e. after recursively visiting children.\n\t// This is ok because we can modify rather than create a new object so don't need to return it.\n\tpublic void visitPost(Command e) throws PrismLangException\n\t{\n\t\tint i;\n\t\t// For independent actions, the index is 0\n\t\tif (e.getSynch().equals(\"\")) {\n\t\t\te.setSynchIndex(0);\n\t\t\treturn;\n\t\t}\n\t\t// Otherwise, see if action name exists\n\t\ti = synchs.indexOf(e.getSynch());\n\t\tif (i != -1) {\n\t\t\t// If so, set the index (starts from 1)\n\t\t\te.setSynchIndex(i + 1);\n\t\t\treturn;\n\t\t}\n\t\t// Otherwise, there is a problem.\n\t\t// In theory, this can never occur since the set of action names is defined by existence in commands\n\t\tthrow new PrismLangException(\"Unknown action name \" + e.getSynch() + \" in command\", e);\n\t}\n\t\n\t// Note that this is done with VisitPost, i.e. after recursively visiting children.\n\t// This is ok because we can modify rather than create a new Command so don't need to return it.\n\tpublic void visitPost(RewardStructItem e) throws PrismLangException\n\t{\n\t\tint i;\n\t\t// Ignore state rewards\n\t\t// (Note: This guarantees getSynch() is non-null)\n\t\tif (!e.isTransitionReward())\n\t\t\treturn;\n\t\t// For independent actions, the index is 0\n\t\tif (e.getSynch().equals(\"\")) {\n\t\t\te.setSynchIndex(0);\n\t\t\treturn;\n\t\t}\n\t\t// Otherwise, see if action name exists\n\t\ti = synchs.indexOf(e.getSynch());\n\t\tif (i != -1) {\n\t\t\t// If so, set the index (starts from 1)\n\t\t\te.setSynchIndex(i + 1);\n\t\t\treturn;\n\t\t}\n\t\t// Otherwise, there is a problem.\n\t\tthrow new PrismLangException(\"Unknown action name \" + e.getSynch() + \" in reward structure item\", e);\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/FindAllConstants.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport java.util.List;\n\nimport parser.ast.*;\nimport parser.type.Type;\nimport prism.PrismLangException;\n\n/**\n * Find all idents which are constants, replace with ExpressionConstant, return result.\n */\npublic class FindAllConstants extends ASTTraverseModify\n{\n\t// Either:\n\tprivate ConstantList constantList;\n\t// Or:\n\tprivate List<String> constIdents;\n\tprivate List<Type> constTypes;\n\t\n\tpublic FindAllConstants(ConstantList constantList)\n\t{\n\t\tthis.constantList = constantList;\n\t}\n\t\n\tpublic FindAllConstants(List<String> constIdents, List<Type> constTypes)\n\t{\n\t\tthis.constIdents = constIdents;\n\t\tthis.constTypes = constTypes;\n\t}\n\t\n\tprivate int getConstantIndex(String name)\n\t{\n\t\tif (constantList != null) {\n\t\t\treturn constantList.getConstantIndex(name);\n\t\t} else {\n\t\t\treturn constIdents.indexOf(name);\n\t\t}\n\t}\n\t\n\tprivate Type getConstantType(int i)\n\t{\n\t\tif (constantList != null) {\n\t\t\treturn constantList.getConstantType(i);\n\t\t} else {\n\t\t\treturn constTypes.get(i);\n\t\t}\n\t}\n\t\n\tpublic Object visit(ExpressionIdent e) throws PrismLangException\n\t{\n\t\t// See if identifier corresponds to a constant\n\t\tint i = getConstantIndex(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, replace it with an ExpressionConstant object\n\t\t\tExpressionConstant expr = new ExpressionConstant(e.getName(), getConstantType(i));\n\t\t\texpr.setPosition(e);\n\t\t\treturn expr;\n\t\t}\n\t\t// Otherwise, leave it unchanged\n\t\treturn e;\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/FindAllFormulas.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n/**\n * Find all idents which are formulas, replace with ExpressionFormula, return result.\n */\npublic class FindAllFormulas extends ASTTraverseModify\n{\n\tprivate FormulaList formulaList;\n\t\n\tpublic FindAllFormulas(FormulaList formulaList)\n\t{\n\t\tthis.formulaList = formulaList;\n\t}\n\t\n\tpublic Object visit(ExpressionIdent e) throws PrismLangException\n\t{\n\t\tint i;\n\t\t// See if identifier corresponds to a formula\n\t\ti = formulaList.getFormulaIndex(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, replace it with an ExpressionFormula object\n\t\t\tExpressionFormula expr = new ExpressionFormula(e.getName());\n\t\t\texpr.setPosition(e);\n\t\t\treturn expr;\n\t\t}\n\t\t// Otherwise, leave it unchanged\n\t\treturn e;\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/FindAllObsRefs.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport java.util.List;\n\nimport parser.ast.*;\nimport parser.type.Type;\nimport prism.PrismLangException;\n\n/**\n * Find all references to observables (by name), replace the ExpressionLabels with ExpressionObs objects.\n * Also cache the index of the observable.\n */\npublic class FindAllObsRefs extends ASTTraverseModify\n{\n\t// A list of pairs of observable names/types\n\tprivate List<String> observableNames = null;\n\tprivate List<Type> observableTypes = null;\n\t\n\tpublic FindAllObsRefs(List<String> observableNames, List<Type> observableTypes)\n\t{\n\t\tthis.observableNames = observableNames;\n\t\tthis.observableTypes = observableTypes;\n\t}\n\t\n\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t{\n\t\t// See if identifier corresponds to an observable\n\t\tint i = observableNames.indexOf(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, replace it with an ExpressionObs object\n\t\t\t// (storing type explicitly)\n\t\t\tExpressionObs expr = new ExpressionObs(e.getName());\n\t\t\texpr.setType(observableTypes.get(i));\n\t\t\texpr.setPosition(e);\n\t\t\t// Also store the observable index\n\t\t\texpr.setIndex(i);\n\t\t\treturn expr;\n\t\t}\n\t\t// Otherwise, leave it unchanged\n\t\treturn e;\n\t}\n\t\n\t// Also re-compute info for ExpressionObs objects in case observable indices have changed\n\tpublic Object visit(ExpressionObs e) throws PrismLangException\n\t{\n\t\t// See if identifier corresponds to an observable\n\t\tint i = observableNames.indexOf(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, set the index\n\t\t\te.setIndex(i);\n\t\t\treturn e;\n\t\t}\n\t\t// Otherwise, there is a problem\n\t\tthrow new PrismLangException(\"Unknown observable \" + e.getName() + \" in ExpressionObs object\", e);\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/FindAllPropRefs.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n/**\n * Find all references to properties (by name), replace the ExpressionLabels with ExpressionProp objects.\n */\npublic class FindAllPropRefs extends ASTTraverseModify\n{\n\tprivate ModulesFile mf;\n\tprivate PropertiesFile pf;\n\t\n\tpublic FindAllPropRefs(ModulesFile mf, PropertiesFile pf)\n\t{\n\t\tthis.mf = mf;\n\t\tthis.pf = pf;\n\t}\n\t\n\tpublic Object visit(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tString name;\n\t\tProperty prop = null;\n\t\t// See if identifier corresponds to a property\n\t\tname = e.getName();\n\t\tif (mf != null) {\n\t\t\tprop = mf.getPropertyByName(name);\n\t\t}\n\t\tif (prop == null && pf != null) {\n\t\t\tprop = pf.getPropertyObjectByName(name);\n\t\t}\n\t\tif (prop != null) {\n\t\t\t// If so, replace it with an ExpressionProp object\n\t\t\tExpressionProp expr = new ExpressionProp(e.getName());\n\t\t\texpr.setPosition(e);\n\t\t\treturn expr;\n\t\t}\n\t\t// Otherwise, leave it unchanged\n\t\treturn e;\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/FindAllVars.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport java.util.List;\n\nimport parser.ast.ExpressionIdent;\nimport parser.ast.ExpressionVar;\nimport parser.ast.Update;\nimport parser.type.Type;\nimport prism.PrismLangException;\n\n/**\n * Find all references to variables, replace any identifier objects with variable objects,\n * check variables exist and store their index (as defined by the containing ModuleFile).\n */\npublic class FindAllVars extends ASTTraverseModify\n{\n\tprivate List<String> varIdents;\n\tprivate List<Type> varTypes;\n\t\n\tpublic FindAllVars(List<String> varIdents, List<Type> varTypes)\n\t{\n\t\tthis.varIdents = varIdents;\n\t\tthis.varTypes = varTypes;\n\t}\n\t\n\t// Note that this is done with VisitPost, i.e. after recursively visiting children.\n\t// This is ok because we can modify rather than create a new object so don't need to return it.\n\tpublic void visitPost(Update e) throws PrismLangException\n\t{\n\t\tint i, j, n;\n\t\tString s;\n\t\t// For each element of update\n\t\tn = e.getNumElements();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t// Check variable exists\n\t\t\tj = varIdents.indexOf(e.getVar(i));\n\t\t\tif (j == -1) {\n\t\t\t\ts = \"Unknown variable \\\"\" + e.getVar(i) + \"\\\" in update\";\n\t\t\t\tthrow new PrismLangException(s, e.getVarIdent(i));\n\t\t\t}\n\t\t\t// Store the type\n\t\t\te.setType(i, varTypes.get(j));\n\t\t\t// And store the variable index\n\t\t\te.setVarIndex(i, j);\n\t\t}\n\t}\n\t\n\tpublic Object visit(ExpressionIdent e) throws PrismLangException\n\t{\n\t\tint i;\n\t\t// See if identifier corresponds to a variable\n\t\ti = varIdents.indexOf(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, replace it with an ExpressionVar object\n\t\t\tExpressionVar expr = new ExpressionVar(e.getName(), varTypes.get(i));\n\t\t\texpr.setPosition(e);\n\t\t\t// Store variable index\n\t\t\texpr.setIndex(i);\n\t\t\treturn expr;\n\t\t}\n\t\t// Otherwise, leave it unchanged\n\t\treturn e;\n\t}\n\t\n\t// Also re-compute info for ExpressionVar objects in case variable indices have changed\n\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t{\n\t\tint i;\n\t\t// See if identifier corresponds to a variable\n\t\ti = varIdents.indexOf(e.getName());\n\t\tif (i != -1) {\n\t\t\t// If so, set the index\n\t\t\te.setIndex(i);\n\t\t\treturn e;\n\t\t}\n\t\t// Otherwise, there is a problem\n\t\tthrow new PrismLangException(\"Unknown variable \" + e.getName() + \" in ExpressionVar object\", e);\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/GetAllConstants.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ExpressionConstant;\nimport prism.PrismLangException;\n\nimport java.util.List;\n\n/**\n * Get all constants (i.e. ExpressionConstant objects), store names in set.\n */\npublic class GetAllConstants extends ASTTraverse\n{\n\tprivate List<String> v;\n\t\n\tpublic GetAllConstants(List<String> v)\n\t{\n\t\tthis.v = v;\n\t}\n\t\n\tpublic void visitPost(ExpressionConstant e) throws PrismLangException\n\t{\n\t\tif (!v.contains(e.getName())) {\n\t\t\tv.add(e.getName());\n\t\t}\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/GetAllFormulas.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ExpressionFormula;\nimport prism.PrismLangException;\n\nimport java.util.List;\n\n/**\n * Get all formulas (i.e. ExpressionFormula objects), store names in set.\n */\npublic class GetAllFormulas extends ASTTraverse\n{\n\tprivate List<String> v;\n\t\n\tpublic GetAllFormulas(List<String> v)\n\t{\n\t\tthis.v = v;\n\t}\n\t\n\tpublic void visitPost(ExpressionFormula e) throws PrismLangException\n\t{\n\t\tif (!v.contains(e.getName())) {\n\t\t\tv.add(e.getName());\n\t\t}\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/GetAllLabels.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ExpressionLabel;\nimport prism.PrismLangException;\n\nimport java.util.List;\n\n/**\n * Get all variables (i.e. ExpressionVar objects), store names in set.\n */\npublic class GetAllLabels extends ASTTraverse\n{\n\tprivate List<String> v;\n\t\n\tpublic GetAllLabels(List<String> v)\n\t{\n\t\tthis.v = v;\n\t}\n\t\n\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tif (!v.contains(e.getName())) {\n\t\t\tv.add(e.getName());\n\t\t}\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/GetAllPropRefs.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ExpressionProp;\nimport prism.PrismLangException;\n\nimport java.util.List;\n\n/**\n * Get all references to properties (by name) (i.e. ExpressionProp objects), store names in set.\n */\npublic class GetAllPropRefs extends ASTTraverse\n{\n\tprivate List<String> v;\n\t\n\tpublic GetAllPropRefs(List<String> v)\n\t{\n\t\tthis.v = v;\n\t}\n\t\n\tpublic void visitPost(ExpressionProp e) throws PrismLangException\n\t{\n\t\tif (!v.contains(e.getName())) {\n\t\t\tv.add(e.getName());\n\t\t}\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/GetAllPropRefsRecursively.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport java.util.List;\nimport java.util.Vector;\n\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionProp;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport prism.PrismLangException;\n\n/**\n * Get all references to properties (by name) (i.e. ExpressionProp objects) recursively, store names in set.\n */\npublic class GetAllPropRefsRecursively extends ASTTraverse\n{\n\tprivate List<String> v;\n\tprivate PropertiesFile pf;\n\n\tpublic GetAllPropRefsRecursively(List<String> v, PropertiesFile pf)\n\t{\n\t\tthis.v = v;\n\t\tthis.pf = pf;\n\t}\n\n\tpublic void visitPost(ExpressionProp e) throws PrismLangException\n\t{\n\t\tif (!v.contains(e.getName())) {\n\t\t\tv.add(e.getName());\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tString name;\n\t\tProperty prop = null;\n\t\t// See if identifier corresponds to a property\n\t\tname = e.getName();\n\t\tif (prop == null && pf != null) {\n\t\t\tprop = pf.lookUpPropertyObjectByName(name);\n\t\t}\n\t\tif (prop != null) {\n\t\t\t// If so, add the name\n\t\t\tv.add(e.getName());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/GetAllUndefinedConstantsRecursively.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ConstantList;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionProp;\nimport parser.ast.LabelList;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport prism.PrismLangException;\n\nimport java.util.List;\n\n/**\n * Get all undefined constants used (i.e. in ExpressionConstant objects) recursively and return as a list.\n * Recursive descent means that we also find constants that are used within other constants, labels, properties.\n * We only recurse into constants/labels/properties in the passed in lists.\n * Any others discovered are ignored (and not descended into).\n * ConstantList must be non-null so that we can determine which constants are undefined;\n * LabelList and PropertiesFile passed in as null are ignored.\n */\npublic class GetAllUndefinedConstantsRecursively extends ASTTraverse\n{\n\tprivate List<String> v;\n\tprivate ConstantList constantList;\n\tprivate LabelList labelList;\n\tprivate PropertiesFile propertiesFile;\n\n\tpublic GetAllUndefinedConstantsRecursively(List<String> v, ConstantList constantList, LabelList labelList, PropertiesFile propertiesFile)\n\t{\n\t\tthis.v = v;\n\t\tthis.constantList = constantList;\n\t\tthis.labelList = labelList;\n\t\tthis.propertiesFile = propertiesFile;\n\t}\n\n\tpublic void visitPost(ExpressionConstant e) throws PrismLangException\n\t{\n\t\t// Look up this constant in the constant list\n\t\tint i = constantList.getConstantIndex(e.getName());\n\t\t// Ignore constants not in the list \n\t\tif (i == -1)\n\t\t\treturn;\n\t\tExpression expr = constantList.getConstant(i);\n\t\t// If constant is undefined, add to the list\n\t\tif (expr == null) {\n\t\t\tif (!v.contains(e.getName())) {\n\t\t\t\tv.add(e.getName());\n\t\t\t}\n\t\t}\n\t\t// If not, check constant definition recursively for more undefined constants\n\t\telse {\n\t\t\texpr.accept(this);\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t{\n\t\t// Ignore special cases of labels (no constants there)\n\t\tif (e.isDeadlockLabel() || e.isInitLabel()) {\n\t\t\treturn;\n\t\t}\n\t\t// Look up this label in the label list, if possible\n\t\tif (labelList == null)\n\t\t\treturn;\n\t\tint i = labelList.getLabelIndex(e.getName());\n\t\tif (i == -1)\n\t\t\treturn;\n\t\tExpression expr = labelList.getLabel(i);\n\t\t// Check label definition recursively for more undefined constants\n\t\texpr.accept(this);\n\t}\n\n\tpublic void visitPost(ExpressionProp e) throws PrismLangException\n\t{\n\t\t// Look up this property in the properties files, if possible\n\t\tif (propertiesFile == null)\n\t\t\treturn;\n\t\tProperty prop = propertiesFile.lookUpPropertyObjectByName(e.getName());\n\t\tif (prop == null)\n\t\t\treturn;\n\t\t// Check property recursively for more undefined constants\n\t\tprop.getExpression().accept(this);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/GetAllVars.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ExpressionVar;\nimport prism.PrismLangException;\n\nimport java.util.List;\n\n/**\n * Get all variables (i.e. ExpressionVar objects), store names in set.\n */\npublic class GetAllVars extends ASTTraverse\n{\n\tprivate List<String> v;\n\t\n\tpublic GetAllVars(List<String> v)\n\t{\n\t\tthis.v = v;\n\t}\n\t\n\tpublic void visitPost(ExpressionVar e) throws PrismLangException\n\t{\n\t\tif (!v.contains(e.getName())) {\n\t\t\tv.add(e.getName());\n\t\t}\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/ModulesFileSemanticCheck.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport java.util.Vector;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.ModelType;\nimport prism.PrismLangException;\n\n/**\n * Perform any required semantic checks on a ModulesFile (or parts of it).\n * These checks are done *before* any undefined constants have been defined.\n */\npublic class ModulesFileSemanticCheck extends SemanticCheck\n{\n\tprivate ModulesFile modulesFile;\n\t// Sometimes we need to keep track of parent (ancestor) objects\n\t//private Module inModule = null;\n\tprivate Expression inInvariant = null;\n\tprivate Expression inGuard = null;\n\tprivate ASTElement inObservable = null;\n\t//private Update inUpdate = null;\n\n\tpublic ModulesFileSemanticCheck(ModulesFile modulesFile)\n\t{\n\t\tthis.modulesFile = modulesFile;\n\t}\n\n\tpublic void visitPost(ModulesFile e) throws PrismLangException\n\t{\n\t\tint i, j, n, n2;\n\t\tparser.ast.Module m;\n\t\tVector<String> v;\n\n\t\t// Check for use of init...endinit _and_ var initial values\n\t\tif (e.getInitialStates() != null) {\n\t\t\tn = e.getNumGlobals();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (e.getGlobal(i).isStartSpecified())\n\t\t\t\t\tthrow new PrismLangException(\"Cannot use both \\\"init...endinit\\\" and initial values for variables\", e.getGlobal(i).getStart());\n\t\t\t}\n\t\t\tn = e.getNumModules();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tm = e.getModule(i);\n\t\t\t\tn2 = m.getNumDeclarations();\n\t\t\t\tfor (j = 0; j < n2; j++) {\n\t\t\t\t\tif (m.getDeclaration(j).isStartSpecified())\n\t\t\t\t\t\tthrow new PrismLangException(\"Cannot use both \\\"init...endinit\\\" and initial values for variables\", m.getDeclaration(j).getStart());\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Check system...endsystem construct (if present)\n\t\t// Each module should appear exactly once\n\t\tif (e.getSystemDefn() != null) {\n\t\t\te.getSystemDefn().getModules(v = new Vector<String>(), modulesFile);\n\t\t\tn = e.getNumModules();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tint k = v.indexOf(e.getModuleName(i));\n\t\t\t\tif (k == -1) {\n\t\t\t\t\tthrow new PrismLangException(\"Module \" + e.getModuleName(i) + \" does not appear in the \\\"system\\\" construct\", e.getSystemDefn());\n\t\t\t\t}\n\t\t\t\tif (v.indexOf(e.getModuleName(i), k + 1) != -1) {\n\t\t\t\t\tthrow new PrismLangException(\"Module \" + e.getModuleName(i) + \" appears more than once in the \\\"system\\\" construct\", e.getSystemDefn());\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic Object visit(SystemReference e) throws PrismLangException\n\t{\n\t\t// Make sure referenced system exists\n\t\tif (modulesFile.getSystemDefnByName(e.getName()) == null)\n\t\t\tthrow new PrismLangException(\"Reference to system \" + e.getName() + \" which does not exist\", e);\n\t\treturn null;\n\t}\n\t\n\tpublic Object visit(FormulaList e) throws PrismLangException\n\t{\n\t\t// Override - don't need to do any semantic checks on formulas\n\t\t// (they will have been expanded in place, where needed)\n\t\t// (and we shouldn't check them - e.g. clock vars appearing in errors would show as an error)\n\t\treturn null;\n\t}\n\t\n\tpublic void visitPost(LabelList e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = e.getLabelName(i);\n\t\t\tif (\"deadlock\".equals(s))\n\t\t\t\tthrow new PrismLangException(\"Cannot define a label called \\\"deadlock\\\" - this is a built-in label\", e.getLabel(i));\n\t\t\tif (\"init\".equals(s))\n\t\t\t\tthrow new PrismLangException(\"Cannot define a label called \\\"init\\\" - this is a built-in label\", e.getLabel(i));\n\t\t}\n\t}\n\n\tpublic void visitPost(ConstantList e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getConstant(i) != null && !e.getConstant(i).isConstant()) {\n\t\t\t\tthrow new PrismLangException(\"Definition of constant \\\"\" + e.getConstantName(i) + \"\\\" is not constant\", e.getConstant(i));\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(Declaration e) throws PrismLangException\n\t{\n\t\tif (e.getStart() != null && !e.getStart().isConstant()) {\n\t\t\tthrow new PrismLangException(\"Initial variable value of variable \\\"\" + e.getName() + \"\\\" is not constant\", e.getStart());\n\t\t}\n\t\t// Clocks cannot be given initial variables\n\t\t// (Note: it is safe to use getType() here because the type of a Declaration\n\t\t// is set on construction, not during type checking).\n\t\tif (e.getStart() != null && e.getType() instanceof TypeClock) {\n\t\t\tthrow new PrismLangException(\"Cannot specify initial value for a clock\", e);\n\t\t}\n\t}\n\n\tpublic void visitPost(DeclarationInt e) throws PrismLangException\n\t{\n\t\tif (e.getLow() != null && !e.getLow().isConstant()) {\n\t\t\tthrow new PrismLangException(\"Integer range lower bound \\\"\" + e.getLow() + \"\\\" is not constant\", e.getLow());\n\t\t}\n\t\tif (e.getHigh() != null && !e.getHigh().isConstant()) {\n\t\t\tthrow new PrismLangException(\"Integer range upper bound \\\"\" + e.getLow() + \"\\\" is not constant\", e.getLow());\n\t\t}\n\t}\n\n\tpublic void visitPost(DeclarationArray e) throws PrismLangException\n\t{\n\t\tif (e.getLow() != null && !e.getLow().isConstant()) {\n\t\t\tthrow new PrismLangException(\"Array lower bound \\\"\" + e.getLow() + \"\\\" is not constant\", e.getLow());\n\t\t}\n\t\tif (e.getHigh() != null && !e.getHigh().isConstant()) {\n\t\t\tthrow new PrismLangException(\"Array upper bound \\\"\" + e.getLow() + \"\\\" is not constant\", e.getLow());\n\t\t}\n\t}\n\n\tpublic void visitPost(DeclarationClock e) throws PrismLangException\n\t{\n\t\t// Clocks are only allowed in real-time models\n\t\tif (!(modulesFile.getModelType().realTime())) {\n\t\t\tthrow new PrismLangException(\"Clock variables are not allowed in \" + modulesFile.getModelType() + \" models\", e);\n\t\t}\n\t}\n\n\tpublic void visitPre(parser.ast.Module e) throws PrismLangException\n\t{\n\t\t// Register the fact we are entering a module\n\t\t//inModule = e;\n\t}\n\n\tpublic Object visit(parser.ast.Module e) throws PrismLangException\n\t{\n\t\t// Override this so we can keep track of when we are in an invariant\n\t\tvisitPre(e);\n\t\tint i, n;\n\t\tn = e.getNumDeclarations();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getDeclaration(i) != null) e.getDeclaration(i).accept(this);\n\t\t}\n\t\tinInvariant = e.getInvariant();\n\t\tif (e.getInvariant() != null)\n\t\t\te.getInvariant().accept(this);\n\t\tinInvariant = null;\n\t\tn = e.getNumCommands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getCommand(i) != null) e.getCommand(i).accept(this);\n\t\t}\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\n\tpublic void visitPost(parser.ast.Module e) throws PrismLangException\n\t{\n\t\t// Register the fact we are leaving a module\n\t\t//inModule = null;\n\t}\n\n\tpublic Object visit(Command e) throws PrismLangException\n\t{\n\t\t// Override this so we can keep track of when we are in a command\n\t\tvisitPre(e);\n\t\tinGuard = e.getGuard();\n\t\te.getGuard().accept(this);\n\t\tinGuard = null;\n\t\te.getUpdates().accept(this);\n\t\tvisitPost(e);\n\t\treturn null;\n\t}\n\t\n\tpublic void visitPre(Update e) throws PrismLangException\n\t{\n\t\t// Register the fact we are entering an update\n\t\t//inUpdate = e;\n\t}\n\n\tpublic void visitPost(Update e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString s, var;\n\t\tCommand c;\n\t\tparser.ast.Module m;\n\t\tboolean isLocal, isGlobal;\n\n\t\t// Register the fact we are leaving an update\n\t\t//inUpdate = null;\n\n\t\t// Determine containing command/module/model\n\t\t// (mf should coincide with the stored modulesFile)\n\t\tc = e.getParent().getParent();\n\t\tm = c.getParent();\n\t\tn = e.getNumElements();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t// Check that the update is allowed to modify this variable\n\t\t\tvar = e.getVar(i);\n\t\t\tisLocal = m.isLocalVariable(var);\n\t\t\tisGlobal = isLocal ? false : modulesFile.isGlobalVariable(var);\n\t\t\tif (!isLocal && !isGlobal) {\n\t\t\t\ts = \"Module \\\"\" + m.getName() + \"\\\" is not allowed to modify variable \\\"\" + var + \"\\\"\";\n\t\t\t\tthrow new PrismLangException(s, e.getVarIdent(i));\n\t\t\t}\n\t\t\tif (isGlobal && !c.getSynch().equals(\"\")) {\n\t\t\t\ts = \"Synchronous command cannot modify global variable\";\n\t\t\t\tthrow new PrismLangException(s, e.getVarIdent(i));\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPre(ObservableVars e) throws PrismLangException\n\t{\n\t\tdefaultVisitPre(e);\n\t\tinObservable = e;\n\t}\n\n\tpublic void visitPost(ObservableVars e) throws PrismLangException\n\t{\n\t\tinObservable = null;\n\t\tdefaultVisitPost(e);\n\t}\n\t\n\tpublic void visitPre(Observable e) throws PrismLangException\n\t{\n\t\tdefaultVisitPre(e);\n\t\tinObservable = e;\n\t}\n\n\tpublic void visitPost(Observable e) throws PrismLangException\n\t{\n\t\tinObservable = null;\n\t\tdefaultVisitPost(e);\n\t}\n\t\n\tpublic void visitPost(SystemRename e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\tVector<String> v;\n\n\t\t// Check all actions are valid and ensure no duplicates\n\t\t// (only check \"from\": OK to introduce new actions and to map to same\n\t\t// action)\n\t\tv = new Vector<String>();\n\t\tn = e.getNumRenames();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = e.getFrom(i);\n\t\t\tif (!modulesFile.isSynch(s)) {\n\t\t\t\tthrow new PrismLangException(\"Invalid action \\\"\" + s + \"\\\" in \\\"system\\\" construct\", e);\n\t\t\t}\n\t\t\tif (v.contains(s)) {\n\t\t\t\tthrow new PrismLangException(\"Duplicated action \\\"\" + s + \"\\\" in parallel composition in \\\"system\\\" construct\", e);\n\t\t\t} else {\n\t\t\t\tv.addElement(s);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(SystemHide e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\tVector<String> v;\n\n\t\t// Check all actions are valid and ensure no duplicates\n\t\tv = new Vector<String>();\n\t\tn = e.getNumActions();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = e.getAction(i);\n\t\t\tif (!modulesFile.isSynch(s)) {\n\t\t\t\tthrow new PrismLangException(\"Invalid action \\\"\" + s + \"\\\" in \\\"system\\\" construct\", e);\n\t\t\t}\n\t\t\tif (v.contains(s)) {\n\t\t\t\tthrow new PrismLangException(\"Duplicated action \\\"\" + s + \"\\\" in parallel composition in \\\"system\\\" construct\", e);\n\t\t\t} else {\n\t\t\t\tv.addElement(s);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(SystemParallel e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\tVector<String> v;\n\n\t\t// Check all actions are valid and ensure no duplicates\n\t\tv = new Vector<String>();\n\t\tn = e.getNumActions();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = e.getAction(i);\n\t\t\tif (!modulesFile.isSynch(s)) {\n\t\t\t\tthrow new PrismLangException(\"Invalid action \\\"\" + s + \"\\\" in \\\"system\\\" construct\", e);\n\t\t\t}\n\t\t\tif (v.contains(s)) {\n\t\t\t\tthrow new PrismLangException(\"Duplicated action \\\"\" + s + \"\\\" in parallel composition in \\\"system\\\" construct\", e);\n\t\t\t} else {\n\t\t\t\tv.addElement(s);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionVar e) throws PrismLangException\n\t{\n\t\t// For PTAs, references to variables in modules have to be local\n\t\t// (no longer checked here, e.g. because allowed for digital clocks)\n\t\t/*if (modulesFile != null && modulesFile.getModelType() == ModelType.PTA && inModule != null) {\n\t\t\tif (!inModule.isLocalVariable(e.getName())) {\n\t\t\t\tthrow new PrismLangException(\"Modules in a PTA cannot access non-local variables\", e);\n\t\t\t}\n\t\t}*/\n\t\t// Clock references, in models, can only appear in certain places\n\t\t// (Note: type checking has not been done, but we know types for ExpressionVars)\n\t\tif (e.getType() instanceof TypeClock) {\n\t\t\tif (inInvariant == null && inGuard == null && inObservable == null) {\n\t\t\t\tthrow new PrismLangException(\"Reference to a clock variable cannot appear here\", e);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tLabelList labelList;\n\t\tif (modulesFile != null)\n\t\t\tlabelList = modulesFile.getLabelList();\n\t\telse\n\t\t\tthrow new PrismLangException(\"Undeclared label\", e);\n\t\tString name = e.getName();\n\t\t// Allow special cases\n\t\tif (\"deadlock\".equals(name) || \"init\".equals(name))\n\t\t\treturn;\n\t\t// Otherwise check list\n\t\tif (labelList == null || labelList.getLabelIndex(name) == -1) {\n\t\t\tthrow new PrismLangException(\"Undeclared label\", e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/ModulesFileSemanticCheckAfterConstants.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport java.util.Vector;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n/**\n * Perform further  semantic checks on a ModulesFile (or parts of it)\n * that can only be done once values for (at least some) undefined constants have been defined.\n */\npublic class ModulesFileSemanticCheckAfterConstants extends ASTTraverse\n{\n\t@SuppressWarnings(\"unused\")\n\tprivate ModulesFile modulesFile;\n\n\tpublic ModulesFileSemanticCheckAfterConstants(ModulesFile modulesFile)\n\t{\n\t\tsetModulesFile(modulesFile);\n\t}\n\n\tpublic void setModulesFile(ModulesFile modulesFile)\n\t{\n\t\tthis.modulesFile = modulesFile;\n\t}\n\n\tpublic void visitPost(Update e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString var;\n\t\tVector<String> varsUsed = new Vector<String>();\n\n\t\t// Check that no variables are set twice in the same update\n\t\t// Currently, could do this *before* constants are defined,\n\t\t// but one day we might need to worry about e.g. array indices...\n\t\tn = e.getNumElements();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tvar = e.getVar(i);\n\t\t\tif (varsUsed.contains(var)) {\n\t\t\t\tthrow new PrismLangException(\"Variable \\\"\" + var + \"\\\" is set twice in the same update\", e.getVarIdent(i));\n\t\t\t}\n\t\t\tvarsUsed.add(var);\n\t\t}\n\t\tvarsUsed.clear();\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/PropertiesSemanticCheck.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ConstantList;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionFilter;\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionSS;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.FormulaList;\nimport parser.ast.LabelList;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport prism.ModelInfo;\nimport prism.PrismLangException;\n\n/**\n * Perform any required semantic checks on a PropertiesFile (or parts of it).\n * These checks are done *before* any undefined constants have been defined.\n * Optionally pass in parent ModulesFile (or leave null);\n */\npublic class PropertiesSemanticCheck extends SemanticCheck\n{\n\tprivate PropertiesFile propertiesFile;\n\tprivate ModelInfo modelInfo;\n\tprivate ModulesFile modulesFile;\n\n\tpublic PropertiesSemanticCheck(PropertiesFile propertiesFile)\n\t{\n\t\tthis(propertiesFile, null);\n\t}\n\n\tpublic PropertiesSemanticCheck(PropertiesFile propertiesFile, ModelInfo modelInfo)\n\t{\n\t\tsetPropertiesFile(propertiesFile);\n\t\tsetModelInfo(modelInfo);\n\t}\n\n\tpublic void setPropertiesFile(PropertiesFile propertiesFile)\n\t{\n\t\tthis.propertiesFile = propertiesFile;\n\t}\n\n\tpublic void setModelInfo(ModelInfo modelInfo)\n\t{\n\t\tthis.modelInfo = modelInfo;\n\t\tif (modelInfo instanceof ModulesFile) {\n\t\t\tthis.modulesFile = (ModulesFile) modelInfo;\n\t\t} else {\n\t\t\tthis.modulesFile = null;\n\t\t}\n\t}\n\n\tpublic Object visit(FormulaList e) throws PrismLangException\n\t{\n\t\t// Override - don't need to do any semantic checks on formulas\n\t\t// (they will have been expanded in place, where needed)\n\t\t// (and we shouldn't check them - e.g. clock vars appearing in errors would show as an error)\n\t\treturn null;\n\t}\n\t\n\tpublic void visitPost(LabelList e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = e.getLabelName(i);\n\t\t\tif (\"deadlock\".equals(s))\n\t\t\t\tthrow new PrismLangException(\"Cannot define a label called \\\"deadlock\\\" - this is a built-in label\", e.getLabel(i));\n\t\t\tif (\"init\".equals(s))\n\t\t\t\tthrow new PrismLangException(\"Cannot define a label called \\\"init\\\" - this is a built-in label\", e.getLabel(i));\n\t\t}\n\t}\n\n\tpublic void visitPost(ConstantList e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getConstant(i) != null && !e.getConstant(i).isConstant()) {\n\t\t\t\tthrow new PrismLangException(\"Definition of constant \\\"\" + e.getConstantName(i) + \"\\\" is not constant\", e.getConstant(i));\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException\n\t{\n\t\tint op = e.getOperator();\n\t\tExpression operand1 = e.getOperand1();\n\t\tExpression operand2 = e.getOperand2();\n\t\tExpression lBound = e.getLowerBound();\n\t\tExpression uBound = e.getUpperBound();\n\t\tif (lBound != null && !lBound.isConstant()) {\n\t\t\tthrow new PrismLangException(\"Lower bound in \" + e.getOperatorSymbol() + \" operator is not constant\", lBound);\n\t\t}\n\t\tif (uBound != null && !uBound.isConstant()) {\n\t\t\tthrow new PrismLangException(\"Upper bound in \" + e.getOperatorSymbol() + \" operator is not constant\", uBound);\n\t\t}\n\t\t// Other checks (which parser should never allow to occur anyway)\n\t\tif (op == ExpressionTemporal.P_X && (operand1 != null || operand2 == null || lBound != null || uBound != null)) {\n\t\t\tthrow new PrismLangException(\"Cannot attach bounds to \" + e.getOperatorSymbol() + \" operator\", e);\n\t\t}\n\t\tif (op == ExpressionTemporal.R_C && (operand1 != null || operand2 != null || lBound != null)) {\n\t\t\t// NB: upper bound is optional (e.g. multi-objective allows R...[C] operator)\n\t\t\tthrow new PrismLangException(\"Badly formed \" + e.getOperatorSymbol() + \" operator\", e);\n\t\t}\n\t\tif (op == ExpressionTemporal.R_I && (operand1 != null || operand2 != null || lBound != null || uBound == null)) {\n\t\t\tthrow new PrismLangException(\"Badly formed \" + e.getOperatorSymbol() + \" operator\", e);\n\t\t}\n\t\tif (op == ExpressionTemporal.R_S && (operand1 != null || operand2 != null || lBound != null || uBound != null)) {\n\t\t\tthrow new PrismLangException(\"Badly formed \" + e.getOperatorSymbol() + \" operator\", e);\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionProb e) throws PrismLangException\n\t{\n\t\tif (e.getModifier() != null) {\n\t\t\tthrow new PrismLangException(\"Modifier \\\"\" + e.getModifier() + \"\\\" not supported for P operator\");\n\t\t}\n\t\tif (e.getProb() != null && !e.getProb().isConstant()) {\n\t\t\tthrow new PrismLangException(\"P operator probability bound is not constant\", e.getProb());\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionReward e) throws PrismLangException\n\t{\n\t\tif (e.getModifier() != null) {\n\t\t\tthrow new PrismLangException(\"Modifier \\\"\" + e.getModifier() + \"\\\" not supported for R operator\");\n\t\t}\n\t\tif (e.getRewardStructIndex() != null) {\n\t\t\tif (e.getRewardStructIndex() instanceof Expression) {\n\t\t\t\tExpression rsi = (Expression) e.getRewardStructIndex();\n\t\t\t\tif (!(rsi.isConstant())) {\n\t\t\t\t\tthrow new PrismLangException(\"R operator reward struct index is not constant\", rsi);\n\t\t\t\t}\n\t\t\t} else if (e.getRewardStructIndex() instanceof String) {\n\t\t\t\tString s = (String) e.getRewardStructIndex();\n\t\t\t\tif (modulesFile != null && modulesFile.getRewardStructIndex(s) == -1) {\n\t\t\t\t\tthrow new PrismLangException(\"R operator reward struct index \\\"\" + s + \"\\\" does not exist\", e);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (e.getRewardStructIndexDiv() != null) {\n\t\t\tif (e.getRewardStructIndexDiv() instanceof Expression) {\n\t\t\t\tExpression rsi = (Expression) e.getRewardStructIndexDiv();\n\t\t\t\tif (!(rsi.isConstant())) {\n\t\t\t\t\tthrow new PrismLangException(\"R operator reward struct index is not constant\", rsi);\n\t\t\t\t}\n\t\t\t} else if (e.getRewardStructIndexDiv() instanceof String) {\n\t\t\t\tString s = (String) e.getRewardStructIndexDiv();\n\t\t\t\tif (modulesFile != null && modulesFile.getRewardStructIndex(s) == -1) {\n\t\t\t\t\tthrow new PrismLangException(\"R operator reward struct index \\\"\" + s + \"\\\" does not exist\", e);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (e.getReward() != null && !e.getReward().isConstant()) {\n\t\t\tthrow new PrismLangException(\"R operator reward bound is not constant\", e.getReward());\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionSS e) throws PrismLangException\n\t{\n\t\tif (e.getModifier() != null) {\n\t\t\tthrow new PrismLangException(\"Modifier \\\"\" + e.getModifier() + \"\\\" not supported for S operator\");\n\t\t}\n\t\tif (e.getProb() != null && !e.getProb().isConstant()) {\n\t\t\tthrow new PrismLangException(\"S operator probability bound is not constant\", e.getProb());\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t{\n\t\tString name = e.getName();\n\t\t// Allow special cases\n\t\tif (\"deadlock\".equals(name) || \"init\".equals(name))\n\t\t\treturn;\n\t\t// Otherwise check if it exists\n\t\tif (modelInfo != null && modelInfo.getLabelIndex(name) != -1) { \n\t\t\treturn;\n\t\t} else if (propertiesFile != null) {\n\t\t\tLabelList labelList = propertiesFile.getCombinedLabelList();\n\t\t\tif (labelList != null && labelList.getLabelIndex(name) != -1) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\tthrow new PrismLangException(\"Undeclared label\", e);\n\t}\n\n\tpublic void visitPost(ExpressionFilter e) throws PrismLangException\n\t{\n\t\t// Check filter type is valid\n\t\tif (e.getOperatorType() == null) {\n\t\t\tthrow new PrismLangException(\"Unknown filter type \\\"\" + e.getOperatorName() + \"\\\"\", e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/Rename.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\n/**\n * Rename (according to RenamedModule definition), return result.\n */\npublic class Rename extends ASTTraverseModify\n{\n\tprivate RenamedModule rm;\n\t\n\tpublic Rename(RenamedModule rm)\n\t{\n\t\tthis.rm = rm;\n\t}\n\t\n\tpublic void visitPost(ModulesFile e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(\"ModulesFile should never be renamed\");\n\t}\n\t\n\tpublic void visitPost(PropertiesFile e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(\"PropertiesFile should never be renamed\");\n\t}\n\t\n\tpublic void visitPost(Declaration e) throws PrismLangException\n\t{\n\t\t// Get new name for variable\n\t\tString s = rm.getNewName(e.getName());\n\t\t// No new name is an error\n\t\tif (s != null) {\n\t\t\te.setName(s);\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Definition of module \\\"\" + rm.getName() + \"\\\" must rename variable \\\"\" + e.getName() + \"\\\"\", rm);\n\t\t}\n\t}\n\t\n\tpublic void visitPost(parser.ast.Module e) throws PrismLangException\n\t{\n\t\t// New name for module is specied in RenamedModule\n\t\te.setName(rm.getName());\n\t}\n\t\n\tpublic void visitPost(Command e) throws PrismLangException\n\t{\n\t\t// Rename synchronising action of command\n\t\tString s = rm.getNewName(e.getSynch());\n\t\tif (s != null) e.setSynch(s);\n\t}\n\t\n\tpublic void visitPost(Update e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\t// Rename variables in update\n\t\tn = e.getNumElements();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts = rm.getNewName(e.getVar(i));\n\t\t\tif (s != null) e.setVar(i, new ExpressionIdent(s));\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(\"Temporal operators should never be renamed\");\n\t}\n\n\tpublic void visitPost(ExpressionFunc e) throws PrismLangException\n\t{\n\t\t// Rename function name (if necessary)\n\t\tString s = rm.getNewName(e.getName());\n\t\tif (s != null) e.setName(s);\n\t}\n\n\tpublic void visitPost(ExpressionIdent e) throws PrismLangException\n\t{\n\t\t// Rename identifier (if necessary)\n\t\tString s = rm.getNewName(e.getName());\n\t\tif (s != null) e.setName(s);\n\t}\n\n\tpublic void visitPost(ExpressionProb e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(\"P operator should never be renamed\");\n\t}\n\n\tpublic void visitPost(ExpressionReward e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(\"R operator should never be renamed\");\n\t}\n\n\tpublic void visitPost(ExpressionSS e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(\"S operator should never be renamed\");\n\t}\n\n\tpublic void visitPost(ExpressionExists e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(\"E operator should never be renamed\");\n\t}\n\n\tpublic void visitPost(ExpressionForAll e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(\"A operator should never be renamed\");\n\t}\n\n\tpublic void visitPost(ExpressionStrategy e) throws PrismLangException\n\t{\n\t\t// This renaming is only designed to be applied\n\t\t// at the level of an individual module (and below)\n\t\tthrow new PrismLangException(e.getOperatorString() + \" operator should never be renamed\");\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/ReplaceLabels.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage parser.visitor;\n\nimport java.util.HashMap;\nimport java.util.Map;\n\nimport parser.ast.ExpressionLabel;\n\n/** Visitor for replacing some labels in an expression by other labels */\npublic class ReplaceLabels extends ASTTraverseModify\n{\n\t/** The replacement map */\n\tprivate Map<String, String> replacements;\n\n\t/** Constructor for multiple replacements (from -> to) */\n\tpublic ReplaceLabels(Map<String, String> replacements)\n\t{\n\t\tthis.replacements = replacements;\n\t}\n\n\t/** Constructor for a single replacement */\n\tpublic ReplaceLabels(String labelFrom, String labelTo)\n\t{\n\t\treplacements = new HashMap<String,String>();\n\t\treplacements.put(labelFrom, labelTo);\n\t}\n\n\t@Override\n\tpublic Object visit(ExpressionLabel e)\n\t{\n\t\tif (e.getName() == null)\n\t\t\treturn e;\n\n\t\tString replacement = replacements.get(e.getName());\n\t\tif (replacement != null)\n\t\t\treturn new ExpressionLabel(replacement);\n\n\t\treturn e;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/SemanticCheck.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.ExpressionFormula;\nimport parser.ast.ExpressionFunc;\nimport parser.ast.ExpressionIdent;\nimport prism.PrismLangException;\n\n/**\n * Perform any required semantic checks. These are just simple checks on expressions, mostly.\n * For semantic checks on models and properties, specifically, see:\n * {@link parser.visitor.ModulesFileSemanticCheck} and {@link parser.visitor.PropertiesSemanticCheck}. \n * These checks are done *before* any undefined constants have been defined.\n */\npublic class SemanticCheck extends ASTTraverse\n{\n\tpublic SemanticCheck()\n\t{\n\t}\n\n\tpublic void visitPost(ExpressionFunc e) throws PrismLangException\n\t{\n\t\t// Check function name is valid\n\t\tif (e.getNameCode() == -1) {\n\t\t\tthrow new PrismLangException(\"Unknown function \\\"\" + e.getName() + \"\\\"\", e);\n\t\t}\n\t\t// Check num arguments\n\t\tif (e.getNumOperands() < e.getMinArity()) {\n\t\t\tthrow new PrismLangException(\"Not enough arguments to \\\"\" + e.getName() + \"\\\" function\", e);\n\t\t}\n\t\tif (e.getMaxArity() != -1 && e.getNumOperands() > e.getMaxArity()) {\n\t\t\tthrow new PrismLangException(\"Too many arguments to \\\"\" + e.getName() + \"\\\" function\", e);\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionIdent e) throws PrismLangException\n\t{\n\t\t// By the time the expression is checked, this should\n\t\t// have been converted to an ExpressionVar/ExpressionConstant/...\n\t\tthrow new PrismLangException(\"Undeclared identifier\", e);\n\t}\n\n\tpublic void visitPost(ExpressionFormula e) throws PrismLangException\n\t{\n\t\t// This should have been defined or expanded by now\n\t\tif (e.getDefinition() == null)\n\t\t\tthrow new PrismLangException(\"Unexpanded formula\", e);\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/Simplify.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport parser.type.TypeDouble;\nimport prism.PrismLangException;\n\n/**\n * Simplify expressions (constant propagation, ...)\n */\npublic class Simplify extends ASTTraverseModify\n{\n\tpublic Object visit(ExpressionBinaryOp e) throws PrismLangException\n\t{\n\t\t// Apply recursively\n\t\te.setOperand1((Expression) (e.getOperand1().accept(this)));\n\t\te.setOperand2((Expression) (e.getOperand2().accept(this)));\n\t\t// If all operands are literals, replace with literal\n\t\tif (e.getOperand1() instanceof ExpressionLiteral && e.getOperand2() instanceof ExpressionLiteral) {\n\t\t\treturn replace(e, new ExpressionLiteral(e.getType(), e.evaluate()));\n\t\t}\n\t\t// Other special cases\n\t\tswitch (e.getOperator()) {\n\t\tcase ExpressionBinaryOp.IMPLIES:\n\t\t\tif (Expression.isFalse(e.getOperand1()) || Expression.isTrue(e.getOperand2()))\n\t\t\t\treturn replace(e, Expression.True());\n\t\t\tif (Expression.isFalse(e.getOperand2()))\n\t\t\t\treturn replace(e, Expression.Not(e.getOperand1()));\n\t\t\tif (Expression.isTrue(e.getOperand1()))\n\t\t\t\treturn replace(e, e.getOperand2());\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.IFF:\n\t\t\tif (Expression.isFalse(e.getOperand1())) {\n\t\t\t\tif (Expression.isFalse(e.getOperand2())) {\n\t\t\t\t\treturn replace(e, Expression.True());\n\t\t\t\t} else if (Expression.isTrue(e.getOperand2())) {\n\t\t\t\t\treturn replace(e, Expression.False());\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (Expression.isTrue(e.getOperand1())) {\n\t\t\t\tif (Expression.isFalse(e.getOperand2())) {\n\t\t\t\t\treturn replace(e, Expression.False());\n\t\t\t\t} else if (Expression.isTrue(e.getOperand2())) {\n\t\t\t\t\treturn replace(e, Expression.True());\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.OR:\n\t\t\tif (Expression.isTrue(e.getOperand1()) || Expression.isTrue(e.getOperand2()))\n\t\t\t\treturn replace(e, Expression.True());\n\t\t\tif (Expression.isFalse(e.getOperand2()))\n\t\t\t\treturn replace(e, e.getOperand1());\n\t\t\tif (Expression.isFalse(e.getOperand1()))\n\t\t\t\treturn replace(e, e.getOperand2());\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.AND:\n\t\t\tif (Expression.isFalse(e.getOperand1()) || Expression.isFalse(e.getOperand2()))\n\t\t\t\treturn replace(e, Expression.False());\n\t\t\tif (Expression.isTrue(e.getOperand2()))\n\t\t\t\treturn replace(e, e.getOperand1());\n\t\t\tif (Expression.isTrue(e.getOperand1()))\n\t\t\t\treturn replace(e, e.getOperand2());\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.PLUS:\n\t\t\tif (Expression.isInt(e.getOperand2()) && e.getOperand2().evaluateInt() == 0)\n\t\t\t\treturn replace(e, e.getOperand1());\n\t\t\tif (Expression.isInt(e.getOperand1()) && e.getOperand1().evaluateInt() == 0)\n\t\t\t\treturn replace(e, e.getOperand2());\n\t\t\tif (Expression.isDouble(e.getOperand2()) && e.getOperand2().evaluateDouble() == 0.0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\te.getOperand1().setType(e.getType());\n\t\t\t\treturn replace(e, e.getOperand1());\n\t\t\t}\n\t\t\tif (Expression.isDouble(e.getOperand1()) && e.getOperand1().evaluateDouble() == 0.0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\te.getOperand2().setType(e.getType());\n\t\t\t\treturn replace(e, e.getOperand2());\n\t\t\t}\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.MINUS:\n\t\t\tif (Expression.isInt(e.getOperand2()) && e.getOperand2().evaluateInt() == 0)\n\t\t\t\treturn replace(e, e.getOperand1());\n\t\t\tif (Expression.isInt(e.getOperand1()) && e.getOperand1().evaluateInt() == 0) {\n\t\t\t\tExpressionUnaryOp simplified = new ExpressionUnaryOp(ExpressionUnaryOp.MINUS, e.getOperand2());\n\t\t\t\t// preserve type\n\t\t\t\tsimplified.setType(e.getType());\n\t\t\t\treturn replace(e, simplified);\n\t\t\t}\n\t\t\tif (Expression.isDouble(e.getOperand2()) && e.getOperand2().evaluateDouble() == 0.0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\te.getOperand1().setType(e.getType());\n\t\t\t\treturn replace(e, e.getOperand1());\n\t\t\t}\n\t\t\tif (Expression.isDouble(e.getOperand1()) && e.getOperand1().evaluateDouble() == 0.0) {\n\t\t\t\tExpressionUnaryOp simplified = new ExpressionUnaryOp(ExpressionUnaryOp.MINUS, e.getOperand2());\n\t\t\t\t// preserve type\n\t\t\t\tsimplified.setType(e.getType());\n\t\t\t\treturn replace(e, simplified);\n\t\t\t}\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.TIMES:\n\t\t\tif (Expression.isInt(e.getOperand2()) && e.getOperand2().evaluateInt() == 1)\n\t\t\t\treturn replace(e, e.getOperand1());\n\t\t\tif (Expression.isInt(e.getOperand1()) && e.getOperand1().evaluateInt() == 1)\n\t\t\t\treturn replace(e, e.getOperand2());\n\t\t\tif (Expression.isDouble(e.getOperand2()) && e.getOperand2().evaluateDouble() == 1.0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\te.getOperand1().setType(e.getType());\n\t\t\t\treturn replace(e, e.getOperand1());\n\t\t\t}\n\t\t\tif (Expression.isDouble(e.getOperand1()) && e.getOperand1().evaluateDouble() == 1.0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\te.getOperand2().setType(e.getType());\n\t\t\t\treturn replace(e, e.getOperand2());\n\t\t\t}\n\t\t\tif (Expression.isInt(e.getOperand2()) && e.getOperand2().evaluateInt() == 0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\treturn replace(e, (e.getType() instanceof TypeDouble) ? Expression.Double(0.0) : Expression.Int(0));\n\t\t\t}\n\t\t\tif (Expression.isInt(e.getOperand1()) && e.getOperand1().evaluateInt() == 0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\treturn replace(e, (e.getType() instanceof TypeDouble) ? Expression.Double(0.0) : Expression.Int(0));\n\t\t\t}\n\t\t\tif (Expression.isDouble(e.getOperand2()) && e.getOperand2().evaluateDouble() == 0.0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\treturn replace(e, (e.getType() instanceof TypeDouble) ? Expression.Double(0.0) : Expression.Int(0));\n\t\t\t}\n\t\t\tif (Expression.isDouble(e.getOperand1()) && e.getOperand1().evaluateDouble() == 0.0) {\n\t\t\t\t// Need to be careful that type is preserved\n\t\t\t\treturn replace(e, (e.getType() instanceof TypeDouble) ? Expression.Double(0.0) : Expression.Int(0));\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\treturn e;\n\t}\n\n\tpublic Object visit(ExpressionUnaryOp e) throws PrismLangException\n\t{\n\t\t// Apply recursively\n\t\te.setOperand((Expression) (e.getOperand().accept(this)));\n\t\t// If operand is a literal, replace with literal\n\t\tif (e.getOperand() instanceof ExpressionLiteral) {\n\t\t\treturn replace(e, new ExpressionLiteral(e.getType(), e.evaluate()));\n\t\t}\n\t\t// Even if not a literal, remove any parentheses\n\t\tif (e.getOperator() == ExpressionUnaryOp.PARENTH) {\n\t\t\treturn replace(e, e.getOperand());\n\t\t}\n\t\treturn e;\n\t}\n\n\tpublic Object visit(ExpressionITE e) throws PrismLangException\n\t{\n\t\t// Apply recursively\n\t\te.setOperand1((Expression) (e.getOperand1().accept(this)));\n\t\te.setOperand2((Expression) (e.getOperand2().accept(this)));\n\t\te.setOperand3((Expression) (e.getOperand3().accept(this)));\n\n\t\t// If 'if' operand is true, replace with 'then' part\n\t\tif (Expression.isTrue(e.getOperand1())) {\n\t\t\treturn replace(e, e.getOperand2());\n\t\t}\n\n\t\t// If 'if' operand is false, replace with 'else' part\n\t\tif (Expression.isFalse(e.getOperand1())) {\n\t\t\treturn replace(e, e.getOperand3());\n\t\t}\n\n\t\treturn e;\n\t}\n\n\tpublic Object visit(ExpressionFunc e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tboolean literal;\n\t\t// Apply recursively\n\t\tn = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getOperand(i) != null) e.setOperand(i, (Expression)(e.getOperand(i).accept(this)));\n\t\t}\n\t\t// If all operands are literals, replace with literal\n\t\tliteral = true;\n\t\tn = e.getNumOperands();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (!(e.getOperand(i) instanceof ExpressionLiteral)) {\n\t\t\t\tliteral = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\tif (literal) {\n\t\t\treturn replace(e, new ExpressionLiteral(e.getType(), e.evaluate()));\n\t\t}\n\t\treturn e;\n\t}\n\t\n\tpublic Object visit(ExpressionFormula e) throws PrismLangException\n\t{\n\t\t// If formula has an attached definition, just replace it with that\n\t\treturn replace(e, e.getDefinition() != null ? e.getDefinition() : e);\n\t}\n\t\n\tprivate Expression replace(Expression eOld, Expression eNew)\n\t{\n\t\teNew.setPosition(eOld);\n\t\treturn eNew;\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/ToTreeString.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport prism.PrismLangException;\n\npublic class ToTreeString extends ASTTraverse\n{\n\tprivate int depth = 0;\n\tprivate StringBuffer buf = new StringBuffer();\n\t\n\t/**\n\t * Get the created string representing the tree.\n\t */\n\tpublic String getString()\n\t{\n\t\treturn buf.toString();\n\t}\n\t\n\tpublic void defaultVisitPre(ASTElement node) throws PrismLangException\n\t{\n\t\t// Don't print full toString() for multi-line objects\n\t\tString s = node.toString();\n\t\tif (s.indexOf('\\n') != -1) s = \"\";\n\t\tprint(node.getClass().getName() + \" : \" + s);\n\t\tdepth++;\n\t}\n\t\n\tpublic void defaultVisitPost(ASTElement node) throws PrismLangException\n\t{\n\t\tdepth--;\n\t}\n\n\t/**\n\t * Utility function to add an indented string to the string buffer\n\t */\n\tprivate void print(String s)\n\t{\n\t\tfor (int i = 0; i < depth; i++) buf.append(\" \");\n\t\tbuf.append(s + \"\\n\");\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/parser/visitor/TypeCheck.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage parser.visitor;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.PrismLangException;\n\n/**\n * Check for type-correctness and compute type.\n * Optionally pass in a PropertiesFile in order to find types of referenced properties.\n */\npublic class TypeCheck extends ASTTraverse\n{\n\tprivate PropertiesFile propertiesFile = null;\n\n\tpublic TypeCheck()\n\t{\n\t\tthis.propertiesFile = null;\n\t}\n\n\tpublic TypeCheck(PropertiesFile propertiesFile)\n\t{\n\t\tthis.propertiesFile = propertiesFile;\n\t}\n\n\tpublic void visitPost(ModulesFile e) throws PrismLangException\n\t{\n\t\tif (e.getInitialStates() != null && !(e.getInitialStates().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: Initial states definition must be Boolean\", e.getInitialStates());\n\t\t}\n\t}\n\n\tpublic void visitPost(Property e) throws PrismLangException\n\t{\n\t\te.setType(e.getExpression().getType());\n\t}\n\n\tpublic void visitPost(FormulaList e) throws PrismLangException\n\t{\n\t\t// Formulas are defined at the text level and are type checked after\n\t\t// substitutions have been applied\n\t}\n\n\tpublic void visitPost(LabelList e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (!(e.getLabel(i).getType() instanceof TypeBool)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Label \\\"\" + e.getLabelName(i) + \"\\\" is not Boolean\", e.getLabel(i));\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(ConstantList e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tn = e.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getConstant(i) != null && !e.getConstantType(i).canCastTypeTo(e.getConstant(i).getType())) {\n\t\t\t\tthrow new PrismLangException(\"Type mismatch in definition of constant \\\"\" + e.getConstantName(i) + \"\\\"\", e.getConstant(i));\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(Declaration e) throws PrismLangException\n\t{\n\t\tif (e.getStart() != null && !e.getType().canCastTypeTo(e.getStart().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: Initial value of variable \\\"\" + e.getName() + \"\\\" does not match\", e.getStart());\n\t\t}\n\t}\n\n\tpublic void visitPost(DeclarationInt e) throws PrismLangException\n\t{\n\t\tif (e.getLow() != null && !TypeInt.getInstance().canCastTypeTo(e.getLow().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: Integer range lower bound \\\"\" + e.getLow() + \"\\\" is not an integer\", e.getLow());\n\t\t}\n\t\tif (e.getHigh() != null && !TypeInt.getInstance().canCastTypeTo(e.getHigh().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: Integer range upper bound \\\"\" + e.getHigh() + \"\\\" is not an integer\", e.getHigh());\n\t\t}\n\t}\n\n\tpublic void visitPost(DeclarationArray e) throws PrismLangException\n\t{\n\t\tif (e.getLow() != null && !TypeInt.getInstance().canCastTypeTo(e.getLow().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: Array lower bound \\\"\" + e.getLow() + \"\\\" is not an integer\", e.getLow());\n\t\t}\n\t\tif (e.getHigh() != null && !TypeInt.getInstance().canCastTypeTo(e.getHigh().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: Array upper bound \\\"\" + e.getHigh() + \"\\\" is not an integer\", e.getHigh());\n\t\t}\n\t}\n\n\tpublic void visitPost(Command e) throws PrismLangException\n\t{\n\t\tif (!(e.getGuard().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: Guard is not Boolean\", e.getGuard());\n\t\t}\n\t}\n\n\tpublic void visitPost(Updates e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tn = e.getNumUpdates();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (e.getProbability(i) != null) {\n\t\t\t\tType typeProb = e.getProbability(i).getType();\n\t\t\t\tboolean typeOK = TypeDouble.getInstance().canCastTypeTo(typeProb);\n\t\t\t\ttypeOK |= typeProb instanceof TypeInterval && TypeDouble.getInstance().canCastTypeTo(((TypeInterval) typeProb).getSubType());\n\t\t\t\tif (!typeOK) {\n\t\t\t\t\tthrow new PrismLangException(\"Type error: Update probability/rate cannot have type \" + typeProb, e.getProbability(i));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(Update e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tn = e.getNumElements();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t// Updates to non-clocks\n\t\t\tif (!(e.getType(i) instanceof TypeClock)) {\n\t\t\t\tif (!e.getType(i).canCastTypeTo(e.getExpression(i).getType())) {\n\t\t\t\t\tthrow new PrismLangException(\"Type error in update to variable \\\"\" + e.getVar(i) + \"\\\"\", e.getExpression(i));\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Updates to clocks\n\t\t\telse {\n\t\t\t\tif (!(e.getExpression(i).getType().equals(TypeInt.getInstance())))\n\t\t\t\t\tthrow new PrismLangException(\"Clocks can only be reset to constant integer values\", e);\n\t\t\t\tif (!(e.getExpression(i).isConstant()))\n\t\t\t\t\tthrow new PrismLangException(\"Clocks can only be reset to constant integer values\", e);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void visitPost(RewardStructItem e) throws PrismLangException\n\t{\n\t\tif (!(e.getStates().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error in reward struct item: guard must be Boolean\", e.getStates());\n\t\t}\n\t\tif (!TypeDouble.getInstance().canCastTypeTo(e.getReward().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error in reward struct item: value must be an int or double\", e.getReward());\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException\n\t{\n\t\tType type;\n\t\tif (e.getLowerBound() != null && !TypeDouble.getInstance().canCastTypeTo(e.getLowerBound().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: Lower bound in \" + e.getOperatorSymbol() + \" operator must be an int or double\", e.getLowerBound());\n\t\t}\n\t\tif (e.getUpperBound() != null && !TypeDouble.getInstance().canCastTypeTo(e.getUpperBound().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: Upper bound in \" + e.getOperatorSymbol() + \" operator must be an int or double\", e.getUpperBound());\n\t\t}\n\t\tswitch (e.getOperator()) {\n\t\tcase ExpressionTemporal.P_X:\n\t\tcase ExpressionTemporal.P_U:\n\t\tcase ExpressionTemporal.P_F:\n\t\tcase ExpressionTemporal.P_G:\n\t\tcase ExpressionTemporal.P_W:\n\t\tcase ExpressionTemporal.P_R:\n\t\t\tif (e.getOperand1() != null) {\n\t\t\t\ttype = e.getOperand1().getType();\n\t\t\t\tif (!(type instanceof TypeBool) && !(type instanceof TypePathBool))\n\t\t\t\t\tthrow new PrismLangException(\"Type error: Argument of \" + e.getOperatorSymbol() + \" operator is not Boolean\", e.getOperand1());\n\t\t\t}\n\t\t\tif (e.getOperand2() != null) {\n\t\t\t\ttype = e.getOperand2().getType();\n\t\t\t\tif (!(type instanceof TypeBool) && !(type instanceof TypePathBool))\n\t\t\t\t\tthrow new PrismLangException(\"Type error: Argument of \" + e.getOperatorSymbol() + \" operator is not Boolean\", e.getOperand2());\n\t\t\t}\n\t\t\te.setType(TypePathBool.getInstance());\n\t\t\tbreak;\n\t\tcase ExpressionTemporal.R_C:\n\t\tcase ExpressionTemporal.R_I:\n\t\tcase ExpressionTemporal.R_S:\n\t\t\te.setType(TypePathDouble.getInstance());\n\t\t\tbreak;\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionITE e) throws PrismLangException\n\t{\n\t\tType t1 = e.getOperand1().getType();\n\t\tType t2 = e.getOperand2().getType();\n\t\tType t3 = e.getOperand3().getType();\n\n\t\tif (!(t1 instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: condition of ? operator is not Boolean\", e.getOperand1());\n\t\t}\n\t\tif (!(t2.canCastTypeTo(t3) || t3.canCastTypeTo(t2))) {\n\t\t\tthrow new PrismLangException(\"Type error: types for then/else operands of ? operator must match\", e);\n\t\t}\n\n\t\tif (t2 instanceof TypeBool)\n\t\t\te.setType(TypeBool.getInstance());\n\t\telse if (t2 instanceof TypeInt && t3 instanceof TypeInt)\n\t\t\te.setType(TypeInt.getInstance());\n\t\telse\n\t\t\te.setType(TypeDouble.getInstance());\n\t}\n\n\tpublic void visitPost(ExpressionBinaryOp e) throws PrismLangException\n\t{\n\t\tType t1 = e.getOperand1().getType();\n\t\tif (t1 == null)\n\t\t\te.getOperand1().getType();\n\t\tType t2 = e.getOperand2().getType();\n\t\tboolean ok;\n\n\t\tswitch (e.getOperator()) {\n\t\tcase ExpressionBinaryOp.IMPLIES:\n\t\tcase ExpressionBinaryOp.IFF:\n\t\tcase ExpressionBinaryOp.OR:\n\t\tcase ExpressionBinaryOp.AND:\n\t\t\tif (!(t1 instanceof TypeBool) && !(t1 instanceof TypePathBool)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" applied to non-Boolean expression\", e.getOperand1());\n\t\t\t}\n\t\t\tif (!(t2 instanceof TypeBool) && !(t2 instanceof TypePathBool)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" applied to non-Boolean expression\", e.getOperand2());\n\t\t\t}\n\t\t\te.setType(t1 instanceof TypePathBool || t2 instanceof TypePathBool ? TypePathBool.getInstance() : TypeBool.getInstance());\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.EQ:\n\t\tcase ExpressionBinaryOp.NE:\n\t\t\tok = false;\n\t\t\t// equality of booleans\n\t\t\tif (t1 instanceof TypeBool && t2 instanceof TypeBool) {\n\t\t\t\tok = true;\n\t\t\t}\n\t\t\t// equality of ints/doubles\n\t\t\telse if ((t1 instanceof TypeInt || t1 instanceof TypeDouble) && (t2 instanceof TypeInt || t2 instanceof TypeDouble)) {\n\t\t\t\tok = true;\n\t\t\t}\n\t\t\t// equality of clocks against clocks/integers\n\t\t\t// (and int/int - but this is already covered above)\n\t\t\telse if ((t1 instanceof TypeInt || t1 instanceof TypeClock) && (t2 instanceof TypeInt || t2 instanceof TypeClock)) {\n\t\t\t\tok = true;\n\t\t\t}\n\t\t\tif (!ok) {\n\t\t\t\tif (t1.equals(t2))\n\t\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" cannot compare \" + t1 + \"s\", e);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" cannot compare \" + t1 + \" and \" + t2, e);\n\t\t\t}\n\t\t\te.setType(TypeBool.getInstance());\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.GT:\n\t\tcase ExpressionBinaryOp.GE:\n\t\tcase ExpressionBinaryOp.LT:\n\t\tcase ExpressionBinaryOp.LE:\n\t\t\tok = false;\n\t\t\t// comparison of ints/doubles\n\t\t\tif ((t1 instanceof TypeInt || t1 instanceof TypeDouble) && (t2 instanceof TypeInt || t2 instanceof TypeDouble)) {\n\t\t\t\tok = true;\n\t\t\t}\n\t\t\t// equality of clocks against clocks/integers\n\t\t\t// (and int/int - but this is already covered above)\n\t\t\telse if ((t1 instanceof TypeInt || t1 instanceof TypeClock) && (t2 instanceof TypeInt || t2 instanceof TypeClock)) {\n\t\t\t\tok = true;\n\t\t\t}\n\t\t\tif (!ok) {\n\t\t\t\tif (t1.equals(t2))\n\t\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" cannot compare \" + t1 + \"s\", e);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" cannot compare \" + t1 + \" and \" + t2, e);\n\t\t\t}\n\t\t\te.setType(TypeBool.getInstance());\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.PLUS:\n\t\tcase ExpressionBinaryOp.MINUS:\n\t\tcase ExpressionBinaryOp.TIMES:\n\t\tcase ExpressionBinaryOp.POW:\n\t\t\tif (!(t1 instanceof TypeInt || t1 instanceof TypeDouble)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" can only be applied to ints or doubles\", e.getOperand1());\n\t\t\t}\n\t\t\tif (!(t2 instanceof TypeInt || t2 instanceof TypeDouble)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" can only be applied to ints or doubles\", e.getOperand2());\n\t\t\t}\n\t\t\te.setType(t1 instanceof TypeDouble || t2 instanceof TypeDouble ? TypeDouble.getInstance() : TypeInt.getInstance());\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.DIVIDE:\n\t\t\tif (!(t1 instanceof TypeInt || t1 instanceof TypeDouble)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" can only be applied to ints or doubles\", e.getOperand1());\n\t\t\t}\n\t\t\tif (!(t2 instanceof TypeInt || t2 instanceof TypeDouble)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" can only be applied to ints or doubles\", e.getOperand2());\n\t\t\t}\n\t\t\te.setType(TypeDouble.getInstance());\n\t\t\tbreak;\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionUnaryOp e) throws PrismLangException\n\t{\n\t\tType t = e.getOperand().getType();\n\n\t\tswitch (e.getOperator()) {\n\t\tcase ExpressionUnaryOp.NOT:\n\t\t\tif (!(t instanceof TypeBool) && !(t instanceof TypePathBool)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" applied to non-Boolean expression\", e.getOperand());\n\t\t\t}\n\t\t\te.setType(t);\n\t\t\tbreak;\n\t\tcase ExpressionUnaryOp.MINUS:\n\t\t\tif (!(t instanceof TypeInt || t instanceof TypeDouble)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: \" + e.getOperatorSymbol() + \" can only be applied to ints or doubles\", e.getOperand());\n\t\t\t}\n\t\t\te.setType(t);\n\t\t\tbreak;\n\t\tcase ExpressionUnaryOp.PARENTH:\n\t\t\te.setType(t);\n\t\t\tbreak;\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionFunc e) throws PrismLangException\n\t{\n\t\tint i, n;\n\t\tType types[];\n\n\t\t// Get types of operands\n\t\tn = e.getNumOperands();\n\t\ttypes = new Type[n];\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ttypes[i] = e.getOperand(i).getType();\n\t\t}\n\n\t\t// Check types of operands are ok\n\t\tswitch (e.getNameCode()) {\n\t\tcase ExpressionFunc.MIN:\n\t\tcase ExpressionFunc.MAX:\n\t\tcase ExpressionFunc.FLOOR:\n\t\tcase ExpressionFunc.CEIL:\n\t\tcase ExpressionFunc.ROUND:\n\t\tcase ExpressionFunc.POW:\n\t\tcase ExpressionFunc.LOG:\n\t\t\t// All operands must be ints or doubles\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (types[i] instanceof TypeBool) {\n\t\t\t\t\tthrow new PrismLangException(\"Type error: Boolean argument not allowed as argument to function \\\"\" + e.getName() + \"\\\"\", e.getOperand(i));\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\t\tcase ExpressionFunc.MOD:\n\t\t\t// All operands must be ints\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (!(types[i] instanceof TypeInt)) {\n\t\t\t\t\tthrow new PrismLangException(\"Type error: non-integer argument to  function \\\"\" + e.getName() + \"\\\"\", e.getOperand(i));\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\t\tcase ExpressionFunc.MULTI:\n\t\t\t// All operands must be booleans or doubles, and doubles must come first.\n\t\t\tboolean seenBoolean = false;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (!(types[i] instanceof TypeBool || types[i] instanceof TypeDouble)) {\n\t\t\t\t\tthrow new PrismLangException(\"Type error: non-Boolean/Double argument to  function \\\"\" + e.getName()\n\t\t\t\t\t\t\t+ \"\\\"\", e.getOperand(i));\n\t\t\t\t}\n\t\t\t\tif (seenBoolean && types[i] instanceof TypeDouble) {\n\t\t\t\t\tthrow new PrismLangException(\"Type error: in the function \\\"\" + e.getName() + \"\\\", any Double arguments must come before any Boolean arguments.\");\n\t\t\t\t}\n\t\t\t\tif (types[i] instanceof TypeBool) {\n\t\t\t\t\tseenBoolean = true;\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Cannot type check unknown function\", e);\n\t\t}\n\n\t\t// Determine type of this function\n\t\tswitch (e.getNameCode()) {\n\t\tcase ExpressionFunc.MIN:\n\t\tcase ExpressionFunc.MAX:\n\t\t\t// int if all ints, double otherwise\n\t\t\te.setType(TypeInt.getInstance());\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (types[i] instanceof TypeDouble) {\n\t\t\t\t\te.setType(TypeDouble.getInstance());\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tbreak;\n\t\tcase ExpressionFunc.FLOOR:\n\t\tcase ExpressionFunc.CEIL:\n\t\tcase ExpressionFunc.ROUND:\n\t\tcase ExpressionFunc.MOD:\n\t\t\t// Resulting type is always int\n\t\t\te.setType(TypeInt.getInstance());\n\t\t\tbreak;\n\t\tcase ExpressionFunc.POW:\n\t\t\t// int if both ints, double otherwise\n\t\t\te.setType(types[0] instanceof TypeDouble || types[1] instanceof TypeDouble ? TypeDouble.getInstance() : TypeInt.getInstance());\n\t\t\tbreak;\n\t\tcase ExpressionFunc.LOG:\n\t\t\t// Resulting type is always double\n\t\t\te.setType(TypeDouble.getInstance());\n\t\t\tbreak;\n\t\tcase ExpressionFunc.MULTI:\n\t\t\t// Resulting type is always same as first arg\n\t\t\tif (types[0] instanceof TypeBool)\n\t\t\t\te.setType(TypeBool.getInstance());\n\t\t\telse if (types.length == 1 || types[1] instanceof TypeBool) //in this case type[0] is TypeDouble\n\t\t\t\te.setType(TypeDouble.getInstance());\n\t\t\telse\n\t\t\t\te.setType(TypeVoid.getInstance());\n\t\t\tbreak;\n\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionIdent e) throws PrismLangException\n\t{\n\t\t// Should never happpen\n\t\tthrow new PrismLangException(\"Cannot determine type of unknown identifier\", e);\n\t}\n\n\tpublic void visitPost(ExpressionLiteral e) throws PrismLangException\n\t{\n\t\t// Type already known\n\t}\n\n\tpublic void visitPost(ExpressionConstant e) throws PrismLangException\n\t{\n\t\t// Type already known\n\t}\n\n\tpublic void visitPost(ExpressionFormula e) throws PrismLangException\n\t{\n\t\t// This should have been defined or expanded by now.\n\t\t// If so, just set type to that of the definition; otherwise error\n\t\tif (e.getDefinition() != null)\n\t\t\te.setType(e.getDefinition().getType());\n\t\telse\n\t\t\tthrow new PrismLangException(\"Cannot determine type of formula\", e);\n\t}\n\n\tpublic void visitPost(ExpressionVar e) throws PrismLangException\n\t{\n\t\t// Type already known\n\t}\n\n\tpublic void visitPost(ExpressionInterval e) throws PrismLangException\n\t{\n\t\tType t1 = e.getOperand1().getType();\n\t\tType t2 = e.getOperand2().getType();\n\t\t// Only intervals of intervals or doubles allowed\n\t\tif (!(t1 instanceof TypeInt || t1 instanceof TypeDouble)) {\n\t\t\tthrow new PrismLangException(\"Type error: intervals can only of ints or doubles\", e.getOperand1());\n\t\t}\n\t\tif (!(t2 instanceof TypeInt || t2 instanceof TypeDouble)) {\n\t\t\tthrow new PrismLangException(\"Type error: intervals can only of ints or doubles\", e.getOperand1());\n\t\t}\n\t\t// Interval of int only if both ints\n\t\tType subType = t1 instanceof TypeDouble || t2 instanceof TypeDouble ? TypeDouble.getInstance() : TypeInt.getInstance();\n\t\te.setType(TypeInterval.getInstance(subType));\n\t}\n\n\tpublic void visitPost(ExpressionProb e) throws PrismLangException\n\t{\n\t\t// Check prob bound\n\t\tif (e.getProb() != null && !TypeDouble.getInstance().canCastTypeTo(e.getProb().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: P operator probability bound is not a double\", e.getProb());\n\t\t}\n\t\t// Check filter\n\t\tif (e.getFilter() != null && !(e.getFilter().getExpression().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: P operator filter is not a Boolean\", e.getFilter().getExpression());\n\t\t}\n\t\t// Need to to do this type check here because some info has been lost when converted to ExpressionFilter\n\t\tif (e.getProb() != null && e.getFilter() != null) {\n\t\t\tif (e.getFilter().minRequested() || e.getFilter().maxRequested()) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Cannot use min/max filters in Boolean-valued properties\");\n\t\t\t}\n\t\t}\n\t\t// Check path operator\n\t\t// Note: need to allow (non-path) Boolean types too, since propositional formulae are also LTL\n\t\tif (!(e.getExpression().getType() instanceof TypePathBool || e.getExpression().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: Contents of P operator is not a path formula\", e.getExpression());\n\t\t}\n\t\t// Set type\n\t\te.setType(e.getProb() == null ? TypeDouble.getInstance() : TypeBool.getInstance());\n\t}\n\n\tpublic void visitPost(ExpressionReward e) throws PrismLangException\n\t{\n\t\t// Check reward struct ref(s)\n\t\tif (e.getRewardStructIndex() != null && e.getRewardStructIndex() instanceof Expression) {\n\t\t\tExpression rsi = (Expression) e.getRewardStructIndex();\n\t\t\tif (!(rsi.getType() instanceof TypeInt)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Reward structure index must be string or integer\", rsi);\n\t\t\t}\n\t\t}\n\t\tif (e.getRewardStructIndexDiv() != null && e.getRewardStructIndexDiv() instanceof Expression) {\n\t\t\tExpression rsi = (Expression) e.getRewardStructIndexDiv();\n\t\t\tif (!(rsi.getType() instanceof TypeInt)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Reward structure index must be string or integer\", rsi);\n\t\t\t}\n\t\t}\n\t\t// Check reward bound\n\t\tif (e.getReward() != null && !TypeDouble.getInstance().canCastTypeTo(e.getReward().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: R operator reward bound is not a double\", e.getReward());\n\t\t}\n\t\t// Check filter\n\t\tif (e.getFilter() != null && !(e.getFilter().getExpression().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: R operator filter is not a Boolean\", e.getFilter().getExpression());\n\t\t}\n\t\t// Need to to do this type check here because some info has been lost when converted to ExpressionFilter\n\t\tif (e.getReward() != null && e.getFilter() != null) {\n\t\t\tif (e.getFilter().minRequested() || e.getFilter().maxRequested()) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Cannot use min/max filters in Boolean-valued properties\");\n\t\t\t}\n\t\t}\n\t\t// Check argument\n\t\tType typeArg = e.getExpression().getType();\n\t\tif (!(typeArg instanceof TypePathDouble || typeArg instanceof TypePathBool || typeArg instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: Contents of R operator is invalid\", e.getExpression());\n\t\t}\n\t\t// Set type\n\t\te.setType(e.getReward() == null ? TypeDouble.getInstance() : TypeBool.getInstance());\n\t}\n\n\tpublic void visitPost(ExpressionSS e) throws PrismLangException\n\t{\n\t\t// Check probability bound\n\t\tif (e.getProb() != null && !TypeDouble.getInstance().canCastTypeTo(e.getProb().getType())) {\n\t\t\tthrow new PrismLangException(\"Type error: S operator probability bound is not a double\", e.getProb());\n\t\t}\n\t\t// Check filter\n\t\tif (e.getFilter() != null && !(e.getFilter().getExpression().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: S operator filter is not a Boolean\", e.getFilter().getExpression());\n\t\t}\n\t\t// Need to to do this type check here because some info has been lost when converted to ExpressionFilter\n\t\tif (e.getProb() != null && e.getFilter() != null) {\n\t\t\tif (e.getFilter().minRequested() || e.getFilter().maxRequested()) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Cannot use min/max filters in Boolean-valued properties\");\n\t\t\t}\n\t\t}\n\t\t// Check argument\n\t\tif (!(e.getExpression().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: Contents of S operator is not a Boolean-valued expression\", e.getExpression());\n\t\t}\n\t\t// Set type\n\t\te.setType(e.getProb() == null ? TypeDouble.getInstance() : TypeBool.getInstance());\n\t}\n\n\tpublic void visitPost(ExpressionExists e) throws PrismLangException\n\t{\n\t\te.setType(TypeBool.getInstance());\n\t}\n\n\tpublic void visitPost(ExpressionForAll e) throws PrismLangException\n\t{\n\t\te.setType(TypeBool.getInstance());\n\t}\n\n\tpublic void visitPost(ExpressionStrategy e) throws PrismLangException\n\t{\n\t\t// Get types of operands\n\t\tint n = e.getNumOperands();\n\t\tType types[] = new Type[n];\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\ttypes[i] = e.getOperand(i).getType();\n\t\t}\n\n\t\t// Currently, resulting type is always same as first arg\n\t\tif (types[0] instanceof TypeBool)\n\t\t\te.setType(TypeBool.getInstance());\n\t\telse if (types.length == 1 || types[1] instanceof TypeBool) //in this case type[0] is TypeDouble\n\t\t\te.setType(TypeDouble.getInstance());\n\t\telse\n\t\t\te.setType(TypeVoid.getInstance());\n\t}\n\n\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t{\n\t\te.setType(TypeBool.getInstance());\n\t}\n\n\tpublic void visitPost(ExpressionObs e) throws PrismLangException\n\t{\n\t\t// Type should be already known\n\t\tif (e.getTypeIfDefined() == null) {\n\t\t\tthrow new PrismLangException(\"Cannot determine type of observable\", e);\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionProp e) throws PrismLangException\n\t{\n\t\t// Recursively type check referenced property\n\t\t// (may not have been done yet, e.g. because that property appears later than the current one in a PropertiesFile)\n\t\t// (NB: recursive check not triggered in visit() method because PropertiesFile not available there)\n\t\t// However, if a PropertiesFile is not available *and* we have a type stored already, don't recompute\n\t\t// (in case typeCheck() is called by getType() later without passing a PropertieFile)\n\t\tif (propertiesFile == null) {\n\t\t\tif (e.getTypeIfDefined() == null)\n\t\t\t\tthrow new PrismLangException(\"No properties file to look up type of property reference \" + e);\n\t\t} else {\n\t\t\tProperty prop = propertiesFile.lookUpPropertyObjectByName(e.getName());\n\t\t\tif (prop == null)\n\t\t\t\tthrow new PrismLangException(\"Could not look up type of property reference \" + e);\n\t\t\t// Notice we explicitly start a type check using the current TypeCheck class, rather than let\n\t\t\t// it be triggered by the subsequent call to getType() becase need to keep ref to PropertiesFile\n\t\t\tprop.accept(this);\n\t\t\te.setType(prop.getType());\n\t\t}\n\t}\n\n\tpublic void visitPost(ExpressionFilter e) throws PrismLangException\n\t{\n\t\t// Get type of operand\n\t\tType t = e.getOperand().getType();\n\n\t\t// Check filter is ok\n\t\tif (e.getFilter() != null && !(e.getFilter().getType() instanceof TypeBool)) {\n\t\t\tthrow new PrismLangException(\"Type error: Second argument of filter is not a Boolean\", e.getFilter());\n\t\t}\n\n\t\t// Check type of operands is ok\n\t\tswitch (e.getOperatorType()) {\n\t\tcase MIN:\n\t\tcase MAX:\n\t\tcase ARGMIN:\n\t\tcase ARGMAX:\n\t\tcase SUM:\n\t\tcase AVG:\n\t\tcase RANGE:\n\t\t\tif (t instanceof TypeBool) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Boolean argument not allowed as operand for filter of type \\\"\" + e.getOperatorName() + \"\\\"\",\n\t\t\t\t\t\te.getOperand());\n\t\t\t}\n\t\t\tif (t instanceof TypeVoid) {\n\t\t\t\t// e.g., complex results from multi-objective checking\n\t\t\t\tthrow new PrismLangException(\"Type error: Void/complex arguments not allowed as operand for filter of type \\\"\" + e.getOperatorName() + \"\\\"\",\n\t\t\t\t\t\te.getOperand());\n\t\t\t}\n\t\t\tbreak;\n\t\tcase COUNT:\n\t\tcase FORALL:\n\t\tcase EXISTS:\n\t\t\tif (!(t instanceof TypeBool)) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Operand for filter of type \\\"\" + e.getOperatorName() + \"\\\" must be Boolean\", e.getOperand());\n\t\t\t}\n\t\t\tbreak;\n\t\tcase FIRST:\n\t\tcase PRINT:\n\t\tcase PRINTALL:\n\t\tcase STORE:\n\t\t\tif (t instanceof TypeVoid) {\n\t\t\t\tthrow new PrismLangException(\"Type error: Void/complex arguments not allowed as operand for filter of type \\\"\" + e.getOperatorName() + \"\\\"\",\n\t\t\t\t\t\te.getOperand());\n\t\t\t}\n\t\t\tbreak;\n\t\tcase STATE:\n\t\t\t// Anything goes, has special handling for TypeVoid (e.g., some multi-objective results)\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismLangException(\"Cannot type check filter of unknown type\", e);\n\t\t}\n\n\t\t// Determine type of this filter\n\t\tswitch (e.getOperatorType()) {\n\t\tcase MIN:\n\t\tcase MAX:\n\t\tcase SUM:\n\t\tcase FIRST:\n\t\tcase PRINT:\n\t\tcase PRINTALL:\n\t\tcase STORE:\n\t\tcase STATE:\n\t\t\te.setType(t);\n\t\t\tbreak;\n\t\tcase RANGE:\n\t\t\te.setType(TypeInterval.getInstance(t));\n\t\t\tbreak;\n\t\tcase COUNT:\n\t\t\te.setType(TypeInt.getInstance());\n\t\t\tbreak;\n\t\tcase AVG:\n\t\t\te.setType(TypeDouble.getInstance());\n\t\t\tbreak;\n\t\tcase ARGMIN:\n\t\tcase ARGMAX:\n\t\tcase FORALL:\n\t\tcase EXISTS:\n\t\t\te.setType(TypeBool.getInstance());\n\t\t\tbreak;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/parser/visitor/package-info.java",
    "content": "/**\n * Syntax tree traversal operations for the PRISM model/properties parser (implemented with the \"visitor\" pattern).\n */\npackage parser.visitor;\n"
  },
  {
    "path": "prism/src/pepa/compiler/InternalError.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Stephen Gilmore <stephen.gilmore@ed.ac.uk> (University of Edinburgh)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pepa.compiler;\n\npublic class InternalError extends Exception {\n    private static final String flag = \"\\n[><]  ----------->   \";\n\n    protected InternalError(String s) {\n\tsuper(flag + flag + s + flag);\n    }\n\n}\n"
  },
  {
    "path": "prism/src/pepa/compiler/Main.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Stephen Gilmore <stephen.gilmore@ed.ac.uk> (University of Edinburgh)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pepa.compiler;\n\nimport java.lang.reflect.*;\npublic class Main {\n\n    public static String compile(String fileName) throws InternalError {\n\ttry {\n\t    Class c = Class.forName(\"pepa\");\n\t    Method[] m = c.getMethods();\n\t    // Terminate here if no methods found\n\t    if (m.length == 0)\n\t\tthrow new InternalError(\"Could not locate the methods for the PEPA compiler\");\n\n\t    // Locate the entry point for the class\n\t    Method entryPoint = null;\n\t    for (int i = 0; i < m.length; i++) {\n\t\tif (m[i].getName().equals(\"compile\")) {\n\t\t    entryPoint = m[i];\n\t\t}\n\t    }\n\t    // Terminate here if the entry point was not found\n\t    if (entryPoint == null)\n\t\tthrow new InternalError(\"Could not locate the entry point for the PEPA compiler\");\n\n\t    // Build the arguments for the method\n\t    Object[] oa = { fileName };\n\t    Object o = entryPoint.invoke(null, oa);\n            if (!(o instanceof String))\n\t\tthrow new InternalError(\"Non-string returned by PEPA compile method \");\n\n\t    String PRISM_result = (String)o;\n\n            return PRISM_result;\n\t} catch (ClassNotFoundException cnfe) {\n\t    throw new InternalError(\"Could not load the PEPA compiler class from pepa.zip\");\n\t} catch (SecurityException se) {\n\t    throw new InternalError(\"Could not secure the PEPA compiler class\");\n\t} catch (IllegalAccessException iae) {\n\t    throw new InternalError(\"Could not access the PEPA compiler instance\");\n\t} catch (IllegalArgumentException iarge) {\n\t    throw new InternalError(\"Attempted to start the PEPA compiler with the wrong arguments\");\n\t} catch (InvocationTargetException ite) {\n\t    Throwable t = ite.getTargetException();\t    \n\t    throw new InternalError(t.toString());\n\t}\n    }\n\n    public static void main(String[] args) throws InternalError {\n\tif (args == null)\n\t    throw new InternalError(\"Cannot invoke the PEPA compiler on a null filename\");\n\n\tif (args.length == 0)\n\t    throw new InternalError(\"Must supply a file name to invoke the PEPA compiler\");\n\n\tif (args.length != 1)\n\t    throw new InternalError(\"Cannot invoke the PEPA compiler on more than one file\");\n\n\tSystem.out.println(compile(args[0]));\n    }\n}\n"
  },
  {
    "path": "prism/src/pepa/compiler/package-info.java",
    "content": "/**\n * Access to PEPA-to-PRISM model translation.\n */\npackage pepa.compiler;\n"
  },
  {
    "path": "prism/src/prism/Accuracy.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * Class to store information about the accuracy of a model checking result.\n */\npublic class Accuracy\n{\n\t/**\n\t * The possible levels of accuracy. \n\t */\n\tpublic enum AccuracyLevel { EXACT, EXACT_FLOATING_POINT, BOUNDED, ESTIMATED_BOUNDED, PROBABLY_BOUNDED }\n\t\n\t/**\n\t * The level of accuracy provided. \n\t */\n\tprivate AccuracyLevel level;\n\n\t/**\n\t * The error bound between the result and the correct answer.\n\t */\n\tprivate double errorBound;\n\t\n\t/**\n\t * The default value for an error bound, if unspecified.\n\t */\n\tpublic final static double DEFAULT_ERROR_BOUND = 1e-5;\n\t\n\t/**\n\t * Error bound (absolute) assumed resulting from storage of values using floating point arithmetic.\n\t */\n\tpublic final static double FLOATING_POINT_ERROR = 1e-12;\n\t\n\t/**\n\t * The possible types of accuracy: absolute or relative. \n\t */\n\tpublic enum AccuracyType { ABSOLUTE, RELATIVE }\n\t\n\t/**\n\t * The type of accuracy: absolute or relative. \n\t */\n\tprivate AccuracyType type;\n\t\n\t/**\n\t * If appropriate, the probability with which the accuracy is guaranteed\n\t */\n\tprivate double probability = 1.0;\n\t\n\t/**\n\t * Create an accuracy of the specified level.\n\t * For \"bounded\" accuracies, {@link Accuracy#DEFAULT_ERROR_BOUND} is assumed.\n\t * The error bound is also assumed to be absolute.\n\t */\n\tpublic Accuracy(AccuracyLevel level)\n\t{\n\t\tthis(level, DEFAULT_ERROR_BOUND);\n\t}\n\t\n\t/**\n\t * Create an accuracy of the specified level and with the specified error bound.\n\t * The error bound is assumed to be absolute. It is ignored for \"exact\" accuracy levels.   \n\t */\n\tpublic Accuracy(AccuracyLevel level, double errorBound)\n\t{\n\t\tthis(level, errorBound, AccuracyType.ABSOLUTE);\n\t}\n\t\n\t/**\n\t * Create an accuracy specification of the specified level, the specified error bound\n\t * and the specified accuracy type: absolute (true) or relative (false).\n\t * The latter two are ignored for \"exact\" accuracy levels.   \n\t */\n\tpublic Accuracy(AccuracyLevel level, double errorBound, boolean absolute)\n\t{\n\t\tthis(level, errorBound, absolute ? AccuracyType.ABSOLUTE : AccuracyType.RELATIVE);\n\t}\n\t\n\t/**\n\t * Create an accuracy specification of the specified level, the specified error bound\n\t * and the specified type: absolute or relative bound.\n\t * The latter two are ignored for \"exact\" accuracy levels.   \n\t */\n\tpublic Accuracy(AccuracyLevel level, double errorBound, AccuracyType type)\n\t{\n\t\tsetLevel(level);\n\t\tswitch (level) {\n\t\tcase EXACT:\n\t\tcase EXACT_FLOATING_POINT:\n\t\t\tsetErrorBound(0.0);\n\t\t\tsetType(AccuracyType.ABSOLUTE);\n\t\t\tbreak;\n\t\tcase BOUNDED:\n\t\tcase ESTIMATED_BOUNDED:\n\t\tcase PROBABLY_BOUNDED:\n\t\t\tsetErrorBound(errorBound);\n\t\t\tsetType(type);\n\t\t\tbreak;\n\t\t}\n\t}\n\t\n\t/**\n\t * Set the accuracy level.\n\t */\n\tpublic void setLevel(AccuracyLevel level)\n\t{\n\t\tthis.level = level;\n\t}\n\t\n\t/**\n\t * Set the error bound (for non-exact accuracies)\n\t * between the result and the correct answer. \n\t */\n\tpublic void setErrorBound(double errorBound)\n\t{\n\t\tthis.errorBound = errorBound;\n\t}\n\t\n\t/**\n\t * Set the probability with which the accuracy is guaranteed\n\t * (for the case where the level is {@link AccuracyLevel#PROBABLY_BOUNDED}).\n\t */\n\tpublic void setProbability(double probability)\n\t{\n\t\tthis.probability = probability;\n\t}\n\t\n\t/**\n\t * Set the accuracy type (absolute or relative).\n\t */\n\tpublic void setType(AccuracyType type)\n\t{\n\t\tthis.type = type;\n\t}\n\t\n\t/**\n\t * Get the accuracy level.\n\t */\n\tpublic AccuracyLevel getLevel()\n\t{\n\t\treturn level;\n\t}\n\t\n\t/**\n\t * Get the error bound between the result and the correct answer.\n\t * Will return 0.0 for both {@code EXACT} and {@code EXACT_FLOATING_POINT},\n\t * i.e., error due to floating point representation is ignored here. \n\t */\n\tpublic double getErrorBound()\n\t{\n\t\tswitch (level) {\n\t\tcase EXACT:\n\t\tcase EXACT_FLOATING_POINT:\n\t\t\treturn 0.0;\n\t\tcase BOUNDED:\n\t\tcase ESTIMATED_BOUNDED:\n\t\tcase PROBABLY_BOUNDED:\n\t\tdefault:\n\t\t\treturn errorBound;\n\t\t}\n\t}\n\t\n\t/**\n\t * Get the accuracy type (absolute or relative).\n\t */\n\tpublic AccuracyType getType()\n\t{\n\t\treturn type;\n\t}\n\t\n\t/**\n\t * Get a string representation of the accuracy type (absolute or relative).\n\t */\n\tpublic String getTypeString()\n\t{\n\t\treturn type == AccuracyType.RELATIVE ? \"relative\" : \"absolute\";\n\t}\n\t\n\t/**\n\t * Get the absolute error bound between the (specified) result and the correct answer.\n\t */\n\tpublic double getAbsoluteErrorBound(double result)\n\t{\n\t\tif (type == AccuracyType.ABSOLUTE) {\n\t\t\treturn errorBound;\n\t\t} else {\n\t\t\treturn Double.isFinite(result) ? (errorBound * Math.abs(result)) : 0.0;\n\t\t}\n\t}\n\t\n\t/**\n\t * Get the relative error bound between the (specified) result and the correct answer.\n\t */\n\tpublic double getRelativeErrorBound(double result)\n\t{\n\t\tif (type == AccuracyType.RELATIVE) {\n\t\t\treturn errorBound;\n\t\t} else {\n\t\t\treturn (errorBound == 0.0 || Double.isInfinite(result)) ? 0.0 : errorBound / Math.abs(result);\n\t\t}\n\t}\n\t\n\t/**\n\t * Get the lower bound for a (specified) result,\n\t * factoring in the error bound (and ignoring possible floating point error).\n\t */\n\tpublic double getResultLowerBound(double result)\n\t{\n\t\treturn result - getAbsoluteErrorBound(result);\n\t}\n\t\n\t/**\n\t * Get the upper bound for a (specified) result,\n\t * factoring in the error bound (and ignoring possible floating point error).\n\t */\n\tpublic double getResultUpperBound(double result)\n\t{\n\t\treturn result + getAbsoluteErrorBound(result);\n\t}\n\t\n\t/**\n\t * Get the lower bound for a (specified) result,\n\t * factoring in the error bound and, optionally, possible floating point error.\n\t */\n\tpublic double getResultLowerBound(double result, boolean fpError)\n\t{\n\t\tdouble fpErrorBound = fpError ? FLOATING_POINT_ERROR : 0.0;\n\t\treturn result - getAbsoluteErrorBound(result) - fpErrorBound;\n\t}\n\t\n\t/**\n\t * Get the upper bound for a (specified) result,\n\t * factoring in the error bound and, optionally, possible floating point error.\n\t */\n\tpublic double getResultUpperBound(double result, boolean fpError)\n\t{\n\t\tdouble fpErrorBound = fpError ? FLOATING_POINT_ERROR : 0.0;\n\t\treturn result + getAbsoluteErrorBound(result) + fpErrorBound;\n\t}\n\t\n\t/**\n\t * Get the probability with which the accuracy is guaranteed\n\t * (for the case where the level is {@link AccuracyLevel#PROBABLY_BOUNDED}; otherwise 1.0).\n\t */\n\tpublic double getProbability()\n\t{\n\t\treturn level == AccuracyLevel.PROBABLY_BOUNDED ? probability : 1.0;\n\t}\n\t\n\t/**\n\t * Get a string representation of the accuracy.\n\t * The actual result needs to be passed in, in order to\n\t * show both absolute and relative accuracy.\n\t */\n\tpublic String toString(Object result)\n\t{\n\t\tswitch (getLevel()) {\n\t\tcase EXACT:\n\t\t\treturn \"exact\";\n\t\tcase EXACT_FLOATING_POINT:\n\t\t\treturn \"exact floating point\";\n\t\tcase BOUNDED:\n\t\tcase ESTIMATED_BOUNDED:\n\t\tcase PROBABLY_BOUNDED:\n\t\tdefault:\n\t\t\t// Numerical results \n\t\t\tif (result instanceof Double) {\n\t\t\t\tdouble d = (Double) result;\n\t\t\t\tString s = \"+/- \" + getAbsoluteErrorBound(d);\n\t\t\t\tif (level == AccuracyLevel.ESTIMATED_BOUNDED) {\n\t\t\t\t\ts += \" estimated\";\n\t\t\t\t} else if (level == AccuracyLevel.PROBABLY_BOUNDED) {\n\t\t\t\t\ts += \" with probability \" + getProbability();\n\t\t\t\t}\n\t\t\t\treturn s + \"; rel err \" + getRelativeErrorBound(d);\n\t\t\t}\n\t\t\t// Non-numerical: only really makes sense for \"probably\"\n\t\t\telse if (level == AccuracyLevel.PROBABLY_BOUNDED) {\n\t\t\t\treturn \"with probability \" + getProbability();\n\t\t\t}\n\t\t}\n\t\t// Default to empty: will be ignored\n\t\treturn \"\";\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tswitch (getLevel()) {\n\t\tcase EXACT:\n\t\t\treturn \"exact\";\n\t\tcase EXACT_FLOATING_POINT:\n\t\t\treturn \"exact floating point\";\n\t\tcase BOUNDED:\n\t\tcase ESTIMATED_BOUNDED:\n\t\tcase PROBABLY_BOUNDED:\n\t\tdefault:\n\t\t\tString s = \"+/- \" + getErrorBound() + \" \" + getTypeString();\n\t\t\tif (level == AccuracyLevel.ESTIMATED_BOUNDED) {\n\t\t\t\ts += \" estimated\";\n\t\t\t} else if (level == AccuracyLevel.PROBABLY_BOUNDED) {\n\t\t\t\ts += \" with probability \" + getProbability();\n\t\t\t}\n\t\t\treturn s;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/AccuracyFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport prism.Accuracy.AccuracyLevel;\n\n/**\n * Class to create {@link Accuracy} objects in a consistent way\n * for various types of numerical computation. \n */\npublic class AccuracyFactory\n{\n\t/**\n\t * Create an {@link Accuracy} object for value iteration like numerical methods\n\t * where there is information about convergence but no guaranteed error bound.\n\t * @param convEps Value of epsilon used to check convergence\n\t * @param maxDiff Final max difference between successive solution vectors\n\t * @param absolute Whether the epsilon/difference are absolute (rather than relative)\n\t */\n\tpublic static Accuracy valueIteration(double convEps, double maxDiff, boolean absolute)\n\t{\n\t\t// If the difference is actual zero (can happen e.g. in acyclic models), it's precise\n\t\tif (maxDiff == 0.0) {\n\t\t\treturn new Accuracy(AccuracyLevel.EXACT_FLOATING_POINT);\n\t\t}\n\t\t// Otherwise, for now, we simply use 10 x the maximum difference\n\t\t// as an (unreliable) estimate of the error bound. \n\t\telse {\n\t\t\tdouble errorBoundEstim = 10 * maxDiff;\n\t\t\treturn new Accuracy(AccuracyLevel.ESTIMATED_BOUNDED, errorBoundEstim, absolute);\n\t\t}\n\t}\n\t\n\t/**\n\t * Create an {@link Accuracy} object for iterative numerical methods which provide\n\t * guaranteed error bounds on the results., e.g. interval iteration.\n\t * @param errorBound Error bound\n\t * @param absolute Whether the error bound is absolute (rather than relative)\n\t */\n\tpublic static Accuracy guaranteedNumericalIterative(double errorBound, boolean absolute)\n\t{\n\t\t// If the difference is actual zero (can happen e.g. in acyclic models), it's precise\n\t\tif (errorBound == 0.0) {\n\t\t\treturn new Accuracy(AccuracyLevel.EXACT_FLOATING_POINT);\n\t\t}\n\t\t// Otherwise use the provided error bound\n\t\telse {\n\t\t\treturn new Accuracy(AccuracyLevel.BOUNDED, errorBound, absolute);\n\t\t}\n\t}\n\t\n\t/**\n\t * Create an {@link Accuracy} object for iterative numerical methods which use\n\t * a fixed number of iterations (e.g., finite-horizon variants).\n\t * We assume this gives \"exact\" results, ignoring floating point issues.\n\t */\n\tpublic static Accuracy boundedNumericalIterations()\n\t{\n\t\treturn new Accuracy(AccuracyLevel.EXACT_FLOATING_POINT);\n\t}\n\t\n\t/**\n\t * Create an {@link Accuracy} object for the case where floating-point results\n\t * are returned but have been derived from exact qualitative results, e.g., from\n\t * graph-based precomputation methods that determine 0/1-probability cases.\n\t */\n\tpublic static Accuracy doublesFromQualitative()\n\t{\n\t\treturn new Accuracy(AccuracyLevel.EXACT_FLOATING_POINT);\n\t}\n\t\n\t/**\n\t * Create a pair of a (double) value and an associated {@link Accuracy} object\n\t * representing an interval of values, specified by its lower and upper bounds.\n\t * Optionally, the accuracy of each bound can be specified. \n\t * @param loVal Lower bound\n\t * @param loAcc Lower bound accuracy\n\t * @param hiVal Upper bound\n\t * @param hiAcc Upper bound accuracy\n\t */\n\tpublic static Pair<Double,Accuracy> valueAndAccuracyFromInterval(double loVal, Accuracy loAcc, double hiVal, Accuracy hiAcc) throws PrismException \n\t{\n\t\t// Don't support probabilistic accuracy bounds\n\t\tif (loAcc != null && loAcc.getLevel() == AccuracyLevel.PROBABLY_BOUNDED) {\n\t\t\tthrow new PrismException(\"Cannot create interval accuracy from probabilistic bounds\");\n\t\t}\n\t\tif (hiAcc != null && hiAcc.getLevel() == AccuracyLevel.PROBABLY_BOUNDED) {\n\t\t\tthrow new PrismException(\"Cannot create interval accuracy from probabilistic bounds\");\n\t\t}\n\t\t// Extract lower/upper bounds (taking into account accuracy if present)\n\t\tdouble lo = loAcc == null ? loVal : loAcc.getResultLowerBound(loVal);\n\t\tdouble hi = hiAcc == null ? hiVal : hiAcc.getResultLowerBound(hiVal);\n\t\t// Compute new mid point value and error bound\n\t\tdouble mid, err;\n\t\tif (Double.isFinite(lo) && Double.isFinite(hi)) {\n\t\t\tmid = (lo + hi) / 2.0;\n\t\t\terr = (hi - lo) / 2.0;\n\t\t} else if (Double.isInfinite(lo) && Double.isInfinite(hi)) {\n\t\t\tmid = lo == hi ? lo : 0.0;\n\t\t\terr = lo == hi ? 0.0 : Double.POSITIVE_INFINITY;\n\t\t} else {\n\t\t\tmid = err = Double.NaN;\n\t\t}\n\t\t// Compute accuracy of new result value:\n\t\t// \"bounded\" if lower/upper bounds were provided with bounded accuracy;\n\t\t// \"estimated bounded\" if either bound was estimated or missing;\n\t\t// \"exactfp\" if \"bounded\" with error 0\n\t\tAccuracyLevel accLev;\n\t\tif (loAcc == null || loAcc.getLevel() == AccuracyLevel.ESTIMATED_BOUNDED) {\n\t\t\taccLev = AccuracyLevel.ESTIMATED_BOUNDED;\n\t\t} else if (hiAcc == null || hiAcc.getLevel() == AccuracyLevel.ESTIMATED_BOUNDED) {\n\t\t\taccLev = AccuracyLevel.ESTIMATED_BOUNDED;\n\t\t} else if (err == 0.0) {\n\t\t\taccLev = AccuracyLevel.EXACT_FLOATING_POINT;\n\t\t} else {\n\t\t\taccLev = AccuracyLevel.BOUNDED;\n\t\t}\n\t\t// Return pair\n\t\tAccuracy acc = new Accuracy(accLev, err, true);\n\t\treturn new Pair<>(mid, acc);\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ActionList.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.function.Supplier;\n\n/**\n * Class to manage the (ordered) list of action labels associated with a model.\n * The list can be obtained via {@link #getActions()} and the index of a given\n * action in the list can be found with {@link #actionIndex(Object)}.\n * <br><br>\n * A list of actions can be provided at the time of creation or, if not,\n * the list is created lazily from the {@code newActionSource} provided on creation.\n * Call {@link #markNeedsRecomputing()} to indicate that actions in the model\n * may have changed and the list therefore needs recomputing.\n * Actions can be added manually with {@link #addAction(Object)}\n * or {@link #addActions(List)}, which does not change whether\n * the list needs recomputing. The full list can be set by calling\n * {@link #setActions(List)}, after which it is assumed recomputation is _not_ needed.\n * In general, actions are not removed (unless {@link #clear()} is called)\n * in order to preserve the order/indexing of actions.\n */\npublic class ActionList\n{\n\t/** Where to get new actions when the list needs recomputing */\n\tprotected Supplier<List<Object>> newActionSource;\n\n\t/** The list of actions */\n\tprotected List<Object> actionList;\n\n\t/** Map from actions to indices */\n\tprotected Map<Object,Integer> actionLookup;\n\n\t/** Does the list need recomputing? */\n\tprotected boolean needsRecomputing;\n\n\t/** Never recompute list? */\n\tprotected boolean neverRecompute;\n\n\t/**\n\t * Construct a (for now empty) new {@link ActionList}\n\t * with a supplier of new actions for when the list needs (re)computing.\n\t * Since the list is empty, it is assumed that it needs recomputing.\n\t */\n\tpublic ActionList(Supplier<List<Object>> newActionSource)\n\t{\n\t\tthis.newActionSource = newActionSource;\n\t\tactionList = new ArrayList<>();\n\t\tactionLookup = new HashMap<>();\n\t\t// Initially empty and therefore almost certainly incomplete\n\t\tneedsRecomputing = true;\n\t\tneverRecompute = false;\n\t}\n\n\t/**\n\t * Construct a new {@link ActionList} from a list of (Object) actions.\n\t * plus a supplier of new actions for when the list needs recomputing.\n\t * For now, it is assumed that the list does _not_ need recomputing.\n\t */\n\tpublic ActionList(List<Object> actions, Supplier<List<Object>> newActionSource)\n\t{\n\t\tthis(newActionSource);\n\t\tsetActions(actions);\n\t}\n\n\t/**\n\t * Copy action info from another ActionList\n\t * (but not the source of new actions)\n\t */\n\tpublic void copyFrom(ActionList other)\n\t{\n\t\tactionList = new ArrayList<>(other.actionList);\n\t\tactionLookup = new HashMap<>(other.actionLookup);\n\t\tneedsRecomputing = other.needsRecomputing;\n\t\tneverRecompute = other.neverRecompute;\n\t}\n\n\t/**\n\t * Set the full list of actions.\n\t * After this, it is assumed that the list does _not_ need recomputing,\n\t * even if {@link #markNeedsRecomputing()} is called.\n\t */\n\tpublic void setActions(List<Object> actions)\n\t{\n\t\tactionList.clear();\n\t\tactionLookup.clear();\n\t\taddActions(actions);\n\t\tneedsRecomputing = false;\n\t\tneverRecompute = true;\n\t}\n\n\t/**\n\t * Clear the action info.\n\t * Since the list is now empty, it is assumed that it needs recomputing.\n\t */\n\tpublic void clear()\n\t{\n\t\tactionList.clear();\n\t\tactionLookup.clear();\n\t\t// Empty and therefore almost certainly incomplete\n\t\tneedsRecomputing = true;\n\t\tneverRecompute = false;\n\t}\n\n\t/**\n\t * Add an action to the list (if it is not already present)\n\t * and return its index in the list.\n\t */\n\tpublic int addAction(Object action)\n\t{\n\t\tInteger index = actionLookup.get(action);\n\t\tif (index == null) {\n\t\t\tindex = actionList.size();\n\t\t\tactionLookup.put(action, index);\n\t\t\tactionList.add(action);\n\t\t}\n\t\treturn index;\n\t}\n\n\t/**\n\t * Add actions to the list (any that are not already present).\n\t */\n\tpublic void addActions(List<Object> actionList)\n\t{\n\t\tactionList.forEach(this::addAction);\n\t}\n\n\t/**\n\t * Mark the action list as needing recomputing.\n\t */\n\tpublic void markNeedsRecomputing()\n\t{\n\t\tneedsRecomputing = true;\n\t}\n\n\t/**\n\t * Recompute the list of actions, from the new action source.\n\t * Existing actions and indices are kept.\n\t */\n\tprivate void recompute()\n\t{\n\t\tnewActionSource.get().forEach(this::addAction);\n\t\tneedsRecomputing = false;\n\t}\n\n\t/**\n\t * Get the list of actions, recomputing and caching if needed.\n\t */\n\tpublic List<Object> getActions()\n\t{\n\t\tif (needsRecomputing && !neverRecompute) {\n\t\t\trecompute();\n\t\t}\n\t\treturn actionList;\n\t}\n\n\t/**\n\t * Get the index (in this list) of an action label.\n\t * Returns -1 if the list is not found.\n\t */\n\tpublic int actionIndex(Object action)\n\t{\n\t\tif (needsRecomputing && !neverRecompute) {\n\t\t\trecompute();\n\t\t}\n\t\tInteger index = actionLookup.get(action);\n\t\treturn index == null ? -1 : index;\n\t}\n\n\t/**\n\t * Default conversion of an action label to a string\n\t * ({@code toString()} or {@code \"\"} for {@code null}).\n\t */\n\tpublic static String actionString(Object action)\n\t{\n\t\treturn action == null ? \"\" : action.toString();\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn actionList.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ActionListOwner.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\n/**\n * Interface for model classes that store action label info as a {@link ActionList}.\n */\npublic interface ActionListOwner\n{\n\t/**\n\t * Get the {@link ActionList} object storing info about actions\n\t */\n\tActionList getActionList();\n}\n"
  },
  {
    "path": "prism/src/prism/BasicModelInfo.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\nimport parser.EvaluateContext;\nimport parser.VarList;\nimport parser.ast.DeclarationType;\nimport parser.type.Type;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.stream.Collectors;\nimport java.util.stream.IntStream;\n\n/**\n * Simple storage of basic model info, implementing {@link ModelInfo}.\n * Stores and provides access to mutable info about\n * model type, variables, labels, etc.\n */\npublic class BasicModelInfo implements ModelInfo\n{\n\t/** Constants, optionally */\n\tprivate EvaluateContext ecConstants;\n\t/** Model type */\n\tprivate ModelType modelType;\n\t/** Action list (optional) */\n\tprivate List<Object> actionList;\n\t/** Variable list */\n\tprivate VarList varList;\n\t/** Observable name list */\n\tprivate List<String> observableNameList;\n\t/** Observable type list */\n\tprivate List<Type> observableTypeList;\n\t/** Label names */\n\tprivate List<String> labelNameList;\n\n\t// Constructors\n\n\t/**\n\t * Construct a blank {@link BasicModelInfo}.\n\t */\n\tpublic BasicModelInfo()\n\t{\n\t\tecConstants = EvaluateContext.create();\n\t\tactionList = null;\n\t\tvarList = new VarList();\n\t\tobservableNameList = new ArrayList<>();\n\t\tobservableTypeList = new ArrayList<>();\n\t\tlabelNameList = new ArrayList<>();\n\t}\n\n\t/**\n\t * Construct a {@link BasicModelInfo} with the specified model type.\n\t */\n\tpublic BasicModelInfo(ModelType modelType)\n\t{\n\t\tthis();\n\t\tsetModelType(modelType);\n\t}\n\n\t// Setters/getters for basic model info storage\n\n\t/**\n\t * Set the model type.\n\t */\n\tpublic void setModelType(ModelType modelType)\n\t{\n\t\tthis.modelType = modelType;\n\t}\n\n\t/**\n\t * Set the list used to store actions.\n\t */\n\tpublic void setActionList(List<Object> actionList)\n\t{\n\t\tthis.actionList = actionList;\n\t}\n\n\t/**\n\t * Set the {@link VarList} used to store variable info.\n\t */\n\tpublic void setVarList(VarList varList)\n\t{\n\t\tthis.varList = varList;\n\t}\n\n\t/**\n\t * Set the list used to store observable names.\n\t */\n\tpublic void setObservableNameList(List<String> observableNameList)\n\t{\n\t\tthis.observableNameList = observableNameList;\n\t}\n\n\t/**\n\t * Set the list used to store observable types.\n\t */\n\tpublic void setObservableTypeList(List<Type> observableTypeList)\n\t{\n\t\tthis.observableTypeList = observableTypeList;\n\t}\n\n\t/**\n\t * Set the list used to store label names.\n\t */\n\tpublic void setLabelNameList(List<String> labelNameList)\n\t{\n\t\tthis.labelNameList = labelNameList;\n\t}\n\n\t/**\n\t * Get the list used to store actions (may be null).\n\t */\n\tpublic List<Object> getActionList()\n\t{\n\t\treturn actionList;\n\t}\n\n\t/**\n\t * Get the {@link VarList} used to store variable info.\n\t */\n\tpublic VarList getVarList()\n\t{\n\t\treturn varList;\n\t}\n\n\t/**\n\t * Get the list used to store observable names.\n\t */\n\tpublic List<String> getObservableNameList()\n\t{\n\t\treturn observableNameList;\n\t}\n\n\t/**\n\t * Get the list used to store observable types.\n\t */\n\tpublic List<Type> getObservableTypeList()\n\t{\n\t\treturn observableTypeList;\n\t}\n\n\t/**\n\t * Get the list used to store label names.\n\t */\n\tpublic List<String> getLabelNameList()\n\t{\n\t\treturn labelNameList;\n\t}\n\n\t// Methods to implement ModelInfo\n\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn modelType;\n\t}\n\n\t@Override\n\tpublic void setSomeUndefinedConstants(EvaluateContext ecUndefined) throws PrismException\n\t{\n\t\tthis.ecConstants = ecUndefined == null ? EvaluateContext.create() : EvaluateContext.create(ecUndefined);\n\t}\n\n\t@Override\n\tpublic EvaluateContext getEvaluateContext()\n\t{\n\t\treturn ecConstants;\n\t}\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\treturn actionList;\n\t}\n\n\t@Override\n\tpublic int getNumVars()\n\t{\n\t\t// Override default implementation that calls (slow) getVarNames()\n\t\treturn varList.getNumVars();\n\t}\n\n\t@Override\n\tpublic List<String> getVarNames()\n\t{\n\t\tint numVars = varList.getNumVars();\n\t\tList<String> varNames = new ArrayList<>(numVars);\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tvarNames.add(varList.getName(i));\n\t\t}\n\t\treturn varNames;\n\t\t/*return IntStream.range(0, varList.getNumVars())\n\t\t\t\t.mapToObj(varList::getName)\n\t\t\t\t.collect(Collectors.toCollection(ArrayList::new));*/\n\t}\n\n\t@Override\n\tpublic int getVarIndex(String name)\n\t{\n\t\t// Override default implementation that calls (slow) getVarNames()\n\t\treturn varList.getIndex(name);\n\t}\n\n\t@Override\n\tpublic String getVarName(int i)\n\t{\n\t\t// Override default implementation that calls (slow) getVarNames()\n\t\treturn varList.getName(i);\n\t}\n\n\t@Override\n\tpublic List<Type> getVarTypes()\n\t{\n\t\tint numVars = varList.getNumVars();\n\t\tList<Type> varTypes = new ArrayList<>(numVars);\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tvarTypes.add(varList.getType(i));\n\t\t}\n\t\treturn varTypes;\n\t\t/*return IntStream.range(0, varList.getNumVars())\n\t\t\t\t.mapToObj(varList::getType)\n\t\t\t\t.collect(Collectors.toCollection(ArrayList::new));*/\n\t}\n\n\t@Override\n\tpublic Type getVarType(int i) throws PrismException\n\t{\n\t\t// Override default implementation that calls (slow) getVarNames()\n\t\treturn varList.getType(i);\n\t}\n\n\t@Override\n\tpublic DeclarationType getVarDeclarationType(int i)\n\t{\n\t\treturn varList.getDeclarationType(i);\n\t}\n\n\t@Override\n\tpublic List<String> getObservableNames()\n\t{\n\t\treturn observableNameList;\n\t}\n\n\t@Override\n\tpublic List<Type> getObservableTypes()\n\t{\n\t\treturn  observableTypeList;\n\t}\n\n\t@Override\n\tpublic List<String> getLabelNames()\n\t{\n\t\treturn labelNameList;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/BasicRewardInfo.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\n/**\n * Simple mutable storage of basic info about rewards of a model.\n * Implements {@link RewardInfo}, but only provides info, not actual rewards.\n */\npublic class BasicRewardInfo implements RewardInfo\n{\n\t/** Reward names */\n\tprivate final List<String> rewardNameList = new ArrayList<>();\n\t/** Which rewards have state rewards */\n\tprivate final BitSet hasStateRewards = new BitSet();\n\t/** Which rewards have transition rewards */\n\tprivate final BitSet hasTransitionRewards = new BitSet();\n\n\t/**\n\t * Add a reward structure to the list.\n\t * Use \"\" for {@code name} if it is unnamed.\n\t * Assumes that it has state/transition rewards for now.\n\t */\n\tpublic void addReward(String name)\n\t{\n\t\trewardNameList.add(name);\n\t\thasStateRewards.set(rewardNameList.size() - 1);\n\t\thasTransitionRewards.set(rewardNameList.size() - 1);\n\t}\n\n\t/**\n\t * Specify whether reward structure r has state rewards.\n\t * @param r Index of reward structure (indexed from 0).\n\t * @param b Whether or not it has state rewards\n\t */\n\tpublic void setHasStateRewards(int r, boolean b)\n\t{\n\t\thasStateRewards.set(r, b);\n\t}\n\n\t/**\n\t * Specify whether reward structure r has transition rewards.\n\t * @param r Index of reward structure (indexed from 0).\n\t * @param b Whether or not it has transition rewards\n\t */\n\tpublic void setHasTransitionRewards(int r, boolean b)\n\t{\n\t\thasTransitionRewards.set(r, b);\n\t}\n\n\t// Methods to implement RewardGenerator\n\n\t@Override\n\tpublic List<String> getRewardStructNames()\n\t{\n\t\treturn rewardNameList;\n\t}\n\n\t@Override\n\tpublic int getNumRewardStructs()\n\t{\n\t\treturn rewardNameList.size();\n\t}\n\n\t@Override\n\tpublic boolean rewardStructHasStateRewards(int r)\n\t{\n\t\treturn hasStateRewards.get(r);\n\t}\n\n\t@Override\n\tpublic boolean rewardStructHasTransitionRewards(int r)\n\t{\n\t\treturn hasTransitionRewards.get(r);\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/DefaultModelGenerator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Nishan Kamaleson <nxk249@bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * Default implementation of the {@link ModelGenerator} and {@link RewardGenerator} interfaces.\n * Basically redundant since these interfaces now have default method implementations.\n * Retained just for backwards compatibility.\n */\npublic abstract class DefaultModelGenerator implements ModelGenerator<Double>, RewardGenerator<Double>\n{\n}\n"
  },
  {
    "path": "prism/src/prism/DefinedConstant.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.Arrays;\nimport java.util.Collection;\nimport java.util.HashSet;\nimport java.util.Objects;\nimport java.util.Set;\n\nimport param.BigRational;\nimport parser.type.*;\n\n/**\n * Class to manage values for a an undefined constant.\n */\npublic abstract class DefinedConstant<T>\n{\n\t/* When iterating over doubles it is not unlikely that the value\n\t * of the iterators are slightly different to the expected value.\n\t * If this difference is within DOUBLE_PRECISION_CORRECTION * ds then\n\t * we presume that this is caused by the inprecision of doubles.\n\t */\n\tpublic static final double DOUBLE_PRECISION_CORRECTION = 0.001;\n\n\t/* Basic info about constant. */\n\tprotected final String name;\n\tprotected final Type type;\n\t/* Definition for constant. */\n\tprotected final T low;\n\tprotected final T high;\n\tprotected final T step;\n\tprotected final int numSteps;\n\t/* Storage for a (temporary) value of the constant. */\n\tprotected T value;\n\n\t/** Creates a new instance of DefinedConstant\n\t(which is initially undefined, bar a name and type). */\n\t\n\tprivate DefinedConstant(String name, Type type, T low, T high, T step, int numSteps)\n\t{\n\t\tthis.name = name;\n\t\tthis.type = type;\n\t\tthis.low = low;\n\t\tthis.high = high;\n\t\tthis.step = step;\n\t\tthis.numSteps = numSteps;\n\t}\n\n\t/** Check whether the constant is defined. */\n\tpublic boolean isDefined()\n\t{\n\t\treturn (low != null);\n\t}\n\n\t/**\n\t * Clear the defined value (and low/high/start) for this constant.\n\t * The cleared version is returned as a new DefinedConstant object.\n\t */\n\tpublic Undefined clear()\n\t{\n\t\treturn new Undefined(name, type);\n\t}\n\n\n\t/**\n\t * Define the constant (by passing in strings).\n\t * The defined version is returned as a new DefinedConstant object.\n\t * <br>\n\t * If {@code exact} is true, BigRationals are used for real values,\n\t * otherwise double arithmetic is used.\n\t */\n\tpublic DefinedConstant<?> define(String sl, String sh, String ss, boolean exact) throws PrismException\n\t{\n\t\tif (type instanceof TypeInt) {\n\t\t\treturn defineInt(name, sl, sh, ss);\n\t\t}\n\t\tif (type instanceof TypeDouble) {\n\t\t\treturn exact ? defineBigRational(name, sl, sh, ss) : defineDouble(name, sl, sh, ss);\n\t\t}\n\t\tif (type instanceof TypeBool) { \n\t\t\treturn defineBoolean(name, sl, sh, ss);\n\t\t}\n\t\tthrow new PrismException(\"Unknown type for undefined constant \" + name + \"\");\n\t}\n\n\tpublic static DefinedInteger defineInt(String name, String sl, String sh, String ss) throws PrismException\n\t{\n\t\tint i, il, ih, is, ihNew;\n\n\t\t// parse low value\n\t\ttry {\n\t\t\til = Integer.parseInt(sl);\n\t\t}\n\t\tcatch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Value \" + sl + \" for constant \" + name + \" is not a valid integer\");\n\t\t}\n\t\t// if no high value given, use low value, default step is 1\n\t\tif (sh == null) {\n\t\t\tih = il;\n\t\t\tis = 1;\n\t\t} else {\n\t\t\t// parse high value\n\t\t\ttry {\n\t\t\t\tih = Integer.parseInt(sh);\n\t\t\t}\n\t\t\tcatch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Value \" + sh + \" for constant \" + name + \" is not a valid integer\");\n\t\t\t}\n\t\t\tif (ih < il) throw new PrismException(\"Low value \"+il+\" for constant \" + name + \" is higher than the high value \"+ih);\n\t\t\tif (ss == null) {\n\t\t\t\t// default step is 1\n\t\t\t\tis = 1;\n\t\t\t} else {\n\t\t\t\t// parse step\n\t\t\t\ttry {\n\t\t\t\t\tis = Integer.parseInt(ss);\n\t\t\t\t}\n\t\t\t\tcatch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Value \" + ss + \" for constant \" + name + \" is not a valid integer\");\n\t\t\t\t}\n\t\t\t\tif (is == 0) throw new PrismException(\"Step value for constant \" + name + \" cannot be zero\");\n\t\t\t\tif (is < 0) throw new PrismException(\"Step value for constant \" + name + \" must be positive\");\n\t\t\t\tif (is > ih-il) throw new PrismException(\"Step value \"+is+\" for constant \" + name + \" is bigger than the difference between \"+il+\" and \"+ih);\n\t\t\t}\n\t\t}\n\t\t// compute num steps\n\t\tint numSteps = 0;\n\t\tihNew = ih;\n\t\t\n\t\tfor (i = il; i <= ih; i = il + numSteps * is) {\n\t\t\tnumSteps++; \n\t\t\tihNew = i; \n\t\t}\n\t\t// store 'actual' value for high\n\t\treturn new DefinedInteger(name, il, ihNew, is, numSteps);\n\t}\n\n\tpublic static DefinedDouble defineDouble(String name, String sl, String sh, String ss) throws PrismException\n\t{\n\t\tdouble d, dl, dh, ds, dhNew;\n\n\t\t// parse low value\n\t\ttry {\n\t\t\tdl = parseDouble(sl);\n\t\t\tif (!Double.isFinite(dl)) {\n\t\t\t\tthrow new NumberFormatException(\"Value is not finite\");\n\t\t\t}\n\t\t}\n\t\tcatch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Value \" + sl + \" for constant \" + name + \" is not a valid double\");\n\t\t}\n\t\t// if no high value given, use low value, default step is 1.0\n\t\tif (sh == null) {\n\t\t\tdh = dl;\n\t\t\tds = 1.0;\n\t\t} else {\n\t\t\t// parse high value\n\t\t\ttry {\n\t\t\t\tdh = parseDouble(sh);\n\t\t\t\tif (!Double.isFinite(dh)) {\n\t\t\t\t\tthrow new NumberFormatException(\"Value is not finite\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tcatch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Value \" + sh + \" for constant \" + name + \" is not a valid double\");\n\t\t\t}\n\t\t\tif (dh < dl) throw new PrismException(\"Low value \"+dl+\" for constant \" + name + \" is higher than the high value \"+dh);\n\t\t\tif (ss == null) {\n\t\t\t\t// default step is 1.0\n\t\t\t\tds = 1.0;\n\t\t\t} else {\n\t\t\t\t// parse step\n\t\t\t\ttry {\n\t\t\t\t\tds = parseDouble(ss);\n\t\t\t\t\tif (!Double.isFinite(ds)) {\n\t\t\t\t\t\tthrow new NumberFormatException(\"Value is not finite\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tcatch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Value \" + ss + \" for constant \" + name + \" is not a valid double\");\n\t\t\t\t}\n\t\t\t\tif (ds == 0) throw new PrismException(\"Step value for constant \" + name + \" cannot be zero\");\n\t\t\t\tif (ds < 0) throw new PrismException(\"Step value for constant \" + name + \" must be positive\");\n\t\t\t\tif (ds > dh-dl) throw new PrismException(\"Step value \"+ds+\" for constant \" + name + \" is bigger than the difference between \"+dl+\" and \"+dh);\n\t\t\t}\n\t\t}\n\t\t// compute num steps\n\t\tint numSteps = 0;\n\t\tdhNew = dh;\n\t\tfor (d = dl; d <= dh + DOUBLE_PRECISION_CORRECTION * ds; d = dl + numSteps * ds) {\n\t\t\tnumSteps++; \n\t\t\tdhNew = d; \n\t\t}\n\t\t// store 'actual' value for high\n\t\treturn new DefinedDouble(name, dl, dhNew, ds, numSteps);\n\t}\n\n\tpublic static DefinedBigRational defineBigRational(String name, String sl, String sh, String ss) throws PrismException\n\t{\n\t\tBigRational r, rl, rh, rs;\n\n\t\t// parse low value\n\t\ttry {\n\t\t\trl = BigRational.from(sl);\n\t\t\tif (rl.isSpecial()) {\n\t\t\t\tthrow new NumberFormatException(\"Value is not finite\");\n\t\t\t}\n\t\t}\n\t\tcatch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Value \" + sl + \" for constant \" + name + \" is not a valid rational number\");\n\t\t}\n\t\t// if no high value given, use low value, default step is 1.0\n\t\tif (sh == null) {\n\t\t\trh = rl;\n\t\t\trs = BigRational.from(1);\n\t\t} else {\n\t\t\t// parse high value\n\t\t\ttry {\n\t\t\t\trh = BigRational.from(sh);\n\t\t\t\tif (rh.isSpecial()) {\n\t\t\t\t\tthrow new NumberFormatException(\"Value is not finite\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tcatch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Value \" + sh + \" for constant \" + name + \" is not a valid rational number\");\n\t\t\t}\n\t\t\tif (rh.lessThan(rl)) throw new PrismException(\"Low value \"+rl+\" for constant \" + name + \" is higher than the high value \"+rh);\n\t\t\tif (ss == null) {\n\t\t\t\t// default step is 1.0\n\t\t\t\trs = BigRational.from(1);\n\t\t\t} else {\n\t\t\t\t// parse step\n\t\t\t\ttry {\n\t\t\t\t\trs = BigRational.from(ss);\n\t\t\t\t\tif (rs.isSpecial()) {\n\t\t\t\t\t\tthrow new NumberFormatException(\"Value is not finite\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tcatch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Value \" + ss + \" for constant \" + name + \" is not a valid double\");\n\t\t\t\t}\n\t\t\t\tif (rs.isZero()) throw new PrismException(\"Step value for constant \" + name + \" cannot be zero\");\n\t\t\t\tif (rs.lessThan(BigRational.ZERO)) throw new PrismException(\"Step value for constant \" + name + \" must be positive\");\n\t\t\t\tif (rs.greaterThan(rh.subtract(rl))) throw new PrismException(\"Step value \"+rs+\" for constant \" + name + \" is bigger than the difference between \"+rl+\" and \"+rh);\n\t\t\t}\n\t\t}\n\t\t// compute num steps\n\t\tint numSteps = 0;\n\t\tBigRational rhNew = rh;\n\t\tfor (r = rl; r.lessThanEquals(rh); r = rl.add(rs.multiply(numSteps))) {\n\t\t\tnumSteps++;\n\t\t\trhNew = r;\n\t\t}\n\t\t// store 'actual' value for high\n\t\treturn new DefinedBigRational(name, rl, rhNew, rs, numSteps);\n\t}\n\n\tpublic static DefinedBoolean defineBoolean(String name, String sl, String sh, String ss) throws PrismException\n\t{\n\t\t// no high or step allowed for booleans\n\t\tif (sh != null) {\n\t\t\tthrow new PrismException(\"Cannot define ranges for Boolean constants\");\n\t\t}\n\t\tif (ss != null) {\n\t\t\tthrow new PrismException(\"Cannot define ranges for Boolean constants\");\n\t\t}\n\t\t// parse value (low)\n\t\tif (sl.equals(\"true\")) {\n\t\t\treturn new DefinedBoolean(name, true);\n\t\t} else if (sl.equals(\"false\")) {\n\t\t\treturn new DefinedBoolean(name, false);\n\t\t}\n\t\tthrow new PrismException(\"Value \" + sl + \" for constant \" + name + \" is not a valid Boolean\");\n\t}\n\n\t/** Set the current value.\n\t(note that \"value\" is distinct from \"definition\") */\n\t\n\tpublic void setValue(T val)\n\t{\n\t\tvalue = val;\n\t}\n\n\t/* Get the current value for the object.\n\t(note that \"value\" is distinct from \"definition\") */\n\t\n\tpublic Object getValue()\n\t{\n\t\treturn value;\n\t}\n\n\t/**\n\t * Increment the value, return status of overflow.\n\t * \n\t * @return Did an overflow occur?\n\t */\n\tpublic abstract boolean incr();\n\n\t/**\n\t * Get the jth value for the constant,\n\t * eg. if the constant definition is 3:2:9, the values would be \n\t * [3, 5, 7, 9] and so getValue(1) would return 5.\n\t * \n\t * @return the j-th value of the constant\n\t */\n\tpublic abstract T getValue(int j);\n\n\t/**\n\t * Get the index of a value of the constant,\n\t * eg. if the constant definition is 3:2:9, the values would be \n\t * [3, 5, 7, 9] and so getValueIndex(7) would return 2.\n\t * \n\t * @return the index of the value of the constant\n\t */\n\tpublic abstract int getValueIndex(T v);\n\n\t// ACCESS METHODS\n\t\n\tpublic String getName() {  return name; }\n\t\n\tpublic Type getType() { return type; }\n\t\n\tpublic T getLow() { return low; }\n\t\n\tpublic T getHigh() { return high; }\n\t\n\tpublic T getStep() { return step; }\n\t\n\tpublic int getNumSteps() { return numSteps; }\n\n\t/**\n\t * Convert to string.\n\t * Note that the (temporary) value is not included here\n\t */\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\t\n\t\ts += name + \"=\";\n\t\ts += low;\n\t\tif (numSteps > 1) s += \":\" + step + \":\" + high;\n\t\t\n\t\treturn s;\n\t}\n\n\t/**\n\t * Parse a double value (supports a/b fraction syntax)\n\t */\n\tpublic static double parseDouble(String s)\n\t{\n\t\tint slashIdx = s.lastIndexOf('/');\n\t\tif (slashIdx < 0) {\n\t\t\treturn Double.parseDouble(s);\n\t\t} else {\n\t\t\t// fraction\n\t\t\t// because we use lastIndexOf, we obtain left-associativity,\n\t\t\t// i.e. a/b/c is interpreted as (a/b)/c\n\t\t\tif (slashIdx == 0 || slashIdx == s.length()-1) {\n\t\t\t\tthrow new NumberFormatException(\"Illegal fraction syntax\");\n\t\t\t}\n\t\t\tdouble num = parseDouble(s.substring(0, slashIdx));\n\t\t\tdouble den = parseDouble(s.substring(slashIdx+1));\n\t\t\treturn num / den;\n\t\t}\n\t}\n\n\t/**\n\t * Check that the string can be parsed as a double value\n\t * (double, or fraction).\n\t */\n\tpublic static boolean isValidDouble(String s)\n\t{\n\t\ttry {\n\t\t\tparseDouble(s);\n\t\t\treturn true;\n\t\t} catch (NumberFormatException e) {\n\t\t\treturn false;\n\t\t}\n\t}\n\n\n\n\tpublic static class Undefined extends DefinedConstant<Object>\n\t{\n\t\tpublic Undefined(String name, Type type)\n\t\t{\n\t\t\tsuper(name, type, null, null, null, -1);\n\t\t}\n\n\t\tpublic boolean incr()\n\t\t{\n\t\t\tthrow new NullPointerException(\"Constant is not defined\");\n\t\t}\n\n\t\tpublic Object getValue(int j)\n\t\t{\n\t\t\tthrow new NullPointerException(\"Constant is not defined\");\n\t\t}\n\n\t\tpublic int getValueIndex(Object v)\n\t\t{\n\t\t\tthrow new NullPointerException(\"Constant is not defined\");\n\t\t}\n\t}\n\n\n\n\tpublic static class DefinedBigRational extends DefinedConstant<BigRational>\n\t{\n\t\tpublic DefinedBigRational(String name, BigRational low, BigRational high, BigRational step, int numSteps)\n\t\t{\n\t\t\tsuper(name,\n\t\t\t           TypeDouble.getInstance(),\n\t\t\t           Objects.requireNonNull(low),\n\t\t\t           Objects.requireNonNull(high),\n\t\t\t           Objects.requireNonNull(step),\n\t\t\t           numSteps);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean incr()\n\t\t{\n\t\t\tBigRational rl = (BigRational) low;\n\t\t\tBigRational rh = (BigRational) high;\n\t\t\tBigRational rs = (BigRational) step;\n\t\t\tBigRational rv = (BigRational) value;\n\t\t\t// if possible, increment\n\t\t\tint index = getValueIndex((BigRational) value) + 1;\n\t\t\trv = rl.add(rs.multiply(index));\n\t\t\tif (rv.lessThanEquals(rh)) {\n\t\t\t\tvalue = rv;\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\t// otherwise, reset to low value, note overflow\n\t\t\tvalue = low;\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic BigRational getValue(int j)\n\t\t{\n\t\t\tBigRational rl = (BigRational)low;\n\t\t\tBigRational rs = (BigRational)low;\n\t\t\tBigRational rv;\n\t\t\t// rv = rl + j*rs\n\t\t\trv = rl.add(rs.multiply(j));\n\t\t\treturn rv;\n\t\t}\n\n\t\t@Override\n\t\tpublic int getValueIndex(BigRational v)\n\t\t{\n\t\t\tBigRational rl = (BigRational) low;\n\t\t\tBigRational rs = (BigRational) step;\n\t\t\tBigRational rv = (BigRational) v;\n\t\t\tBigRational index = (rv.subtract(rl)).divide(rs);\n\t\t\ttry {\n\t\t\t\treturn index.toInt();\n\t\t\t} catch (PrismLangException e) {\n\t\t\t\tthrow new IllegalArgumentException(\"Can not compute value index, out of range: \" + e);\n\t\t\t}\n\t\t}\n\t}\n\n\n\tpublic static class DefinedBoolean extends DefinedConstant<Boolean>\n\t{\n\t\tpublic DefinedBoolean(String name, boolean low)\n\t\t{\n\t\t\tsuper(name, TypeBool.getInstance(), low, null, null, 1);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean incr()\n\t\t{\n\t\t\t// booleans can't be incremented\n\t\t\tvalue = low;\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic Boolean getValue(int j)\n\t\t{\n\t\t\t// Fail if j is neither 0 nor 1\n\t\t\tswitch (j) {\n\t\t\tcase 0:\n\t\t\t\treturn false;\n\t\t\tcase 1:\n\t\t\t\treturn true;\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic int getValueIndex(Boolean v)\n\t\t{\n\t\t\t// Fail if Object is not a Boolean\n\t\t\treturn (Boolean) v ? 1 : 0;\n\t\t}\n\t}\n\n\n\n\tpublic static class DefinedDouble extends DefinedConstant<Double>\n\t{\n\t\tpublic DefinedDouble(String name, double low, double high, double step, int numSteps)\n\t\t{\n\t\t\tsuper(name, TypeDouble.getInstance(), low, high, step, numSteps);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean incr()\n\t\t{\n\t\t\t// double arithmetic\n\t\t\tdouble dl = ((Double)low).doubleValue();\n\t\t\tdouble dh = ((Double)high).doubleValue();\n\t\t\tdouble ds = ((Double)step).doubleValue();\n\t\t\tdouble dv = ((Double)value).doubleValue();\n\t\t\t// if possible, increment\n\t\t\tint index = getValueIndex((Double) value) + 1;\n\t\t\tdv = dl + index * ds;\n\t\t\tif (dv <= dh + DOUBLE_PRECISION_CORRECTION * ds) {\n\t\t\t\tvalue = Double.valueOf(dv);\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\t// otherwise, reset to low value, note overflow\n\t\t\tvalue = low;\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic Double getValue(int j)\n\t\t{\n\t\t\tdouble dl = ((Double)low).doubleValue();\n\t\t\tdouble ds = ((Double)step).doubleValue();\n\t\t\t//for (i = 0; i < j; i++) dv += ds;\n\t\t\tdouble dv = dl + j * ds;\n\t\t\treturn Double.valueOf(dv);\n\t\t}\n\n\t\t@Override\n\t\tpublic int getValueIndex(Double v)\n\t\t{\n\t\t\tdouble dl  = ((Double)low).doubleValue();\n\t\t\tdouble ds = ((Double)step).doubleValue();\n\t\t\tdouble dv = ((Double)v).doubleValue();\n\t\t\treturn (int)Math.round((dv-dl)/ds);\n\t\t}\n\t}\n\n\n\n\tpublic static class DefinedInteger extends DefinedConstant<Integer>\n\t{\n\t\tpublic DefinedInteger(String name, int low, int high, int step, int numSteps)\n\t\t{\n\t\t\tsuper(name, TypeInt.getInstance(), low, high, step, numSteps);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean incr()\n\t\t{\n\t\t\tint ih = ((Integer)high).intValue();\n\t\t\tint is = ((Integer)step).intValue();\n\t\t\tint iv = ((Integer)value).intValue();\n\t\t\t// if possible, increment\n\t\t\tif (iv + is <= ih) {\n\t\t\t\tvalue = Integer.valueOf(iv + is);\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\t// otherwise, reset to low value, note overflow\n\t\t\tvalue = low;\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic Integer getValue(int j)\n\t\t{\n\t\t\tint il = ((Integer)low).intValue();\n\t\t\tint is = ((Integer)step).intValue();\n\t\t\tint iv = il;\n\t\t\tfor (int i = 0; i < j; i++) {\n\t\t\t\tiv += is;\n\t\t\t}\n\t\t\treturn Integer.valueOf(iv);\n\t\t}\n\n\t\t@Override\n\t\tpublic int getValueIndex(Integer v)\n\t\t{\n\t\t\tint il = ((Integer)low).intValue();\n\t\t\tint is = ((Integer)step).intValue();\n\t\t\tint iv = ((Integer)v).intValue();\n\t\t\treturn (iv-il)/is;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * Class for a constant that is defined over a set of possible values, the domain.\n\t * \n\t * @param <T> the Java type of the values in the domain\n\t */\n\tpublic static class DefinedDomain<T extends Number> extends DefinedConstant<T>\n\t{\n\t\tprivate final T[] domain;\n\n\t\t/**\n\t\t * Define a constant from a collection of possible values.\n\t\t * \n\t\t * @param <T> the Java type of the values in the domain\n\t\t * @param name the name of the constant\n\t\t * @param type the Prism type of the values\n\t\t * @param values the values of the domain\n\t\t * @param a an empty array as blueprint to store the domain in an array of the correct type\n\t\t * @return The constant defined over the given domain\n\t\t */\n\t\tpublic static <T extends Number> DefinedDomain<T> fromValues(String name, Type type, Collection<T> values, T[] a)\n\t\t{\n\t\t\tif (values.size() < 1) {\n\t\t\t\tthrow new IllegalArgumentException(\"expected at least one element in domain\");\n\t\t\t}\n\t\t\tif (!(values instanceof Set)) {\n\t\t\t\tvalues =  new HashSet<T>(values);\n\t\t\t}\n\t\t\tT[] domain = values.toArray(a);\n\t\t\tArrays.sort(domain);\n\t\t\treturn new DefinedDomain<>(name, type, domain);\n\t\t}\n\n\t\t/**\n\t\t * Define a constant over a set of possible values, the domain.\n\t\t * \n\t\t * @param name the name of the constant\n\t\t * @param type the Prism type of the values\n\t\t * @param domain the domain of distinct values\n\t\t */\n\t\tprotected DefinedDomain(String name, Type type, T[] domain)\n\t\t{\n\t\t\tsuper(name, type, domain[0], domain[domain.length-1], null, domain.length);\n\t\t\tthis.domain = domain;\n\t\t\tcheckType();\n\t\t}\n\n\t\t/**\n\t\t * Check that the Java type and the Prism type match.\n\t\t * \n\t\t * @throws IllegalArgumentException If the types do not match\n\t\t */\n\t\tprotected void checkType()\n\t\t{\n\t\t\tClass<?> sampleClass = domain[0].getClass();\n\t\t\tif (sampleClass == Integer.class && ! (type instanceof TypeInt)) {\n\t\t\t\tthrow new IllegalArgumentException(\"expected TypeInt but got\" + type);\n\t\t\t} else if (sampleClass == Double.class && ! (type instanceof TypeDouble)) {\n\t\t\t\tthrow new IllegalArgumentException(\"expected TypeDouble but got\" + type);\n\t\t\t} else if (sampleClass == BigRational.class && ! (type instanceof TypeDouble)) {\n\t\t\t\tthrow new IllegalArgumentException(\"expected TypeDouble but got\" + type);\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean incr()\n\t\t{\n\t\t\tint i = getValueIndex(value);\n\t\t\tif (i == numSteps - 1) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t\tvalue = domain[i+1];\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic T getValue(int j)\n\t\t{\n\t\t\treturn domain[j];\n\t\t}\n\n\t\t@Override\n\t\tpublic void setValue(T value)\n\t\t{\n\t\t\tif (getValueIndex(value) < 0) {\n\t\t\t\tthrow new IllegalArgumentException(\"expected value from domain\");\n\t\t\t}\n\t\t\tsuper.setValue((T) value);\n\t\t}\n\n\t\t@Override\n\t\tpublic int getValueIndex(T v)\n\t\t{\n\t\t\treturn Arrays.binarySearch(domain, v);\n\t\t}\n\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn name + \"=\" + Arrays.toString(domain);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Evaluator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport common.Interval;\nimport param.BigRational;\nimport param.Function;\nimport param.FunctionFactory;\nimport parser.EvaluateContext.EvalMode;\nimport parser.EvaluateContextState;\nimport parser.State;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInterval;\n\n/**\n * Interface specifying operations that need to be supported for classes used to\n * store values for probabilities/rewards/etc. in generic storage classes,\n * e.g., subclasses of {@link explicit.Model}{@code <Value>}. Such classes\n * store values as an arbitrary type {@code Value} but also need to provide\n * an {@link Evaluator} object to manipulate them. This approach is intended to\n * allow existing types (e.g. Double, BigRational, Function) to be used for for\n * generic models without the need for creating additional wrappers.\n * \n * For evaluators where values are non-scalar and represent a set of different\n * values (e.g., intervals or symbolic functions), the methods should return a\n * result that holds for all possible values. If this cannot be done, an\n * UnsupportedOperationException can be thrown.\n */\npublic interface Evaluator<Value>\n{\n\t// Static methods to create Evaluator instances for common types\n\t\n\tpublic static Evaluator<Double> forDouble()\n\t{\n\t\treturn EvaluatorDouble.EVALUATOR_DOUBLE;\n\t}\n\n\tpublic static Evaluator<BigRational> forBigRational()\n\t{\n\t\treturn EvaluatorBigRational.EVALUATOR_BIG_RATIONAL;\n\t}\n\n\tpublic static Evaluator<Function> forRationalFunction(FunctionFactory functionFactory)\n\t{\n\t\treturn new EvaluatorFunction(functionFactory);\n\t}\n\t\n\tpublic static Evaluator<Interval<Double>> forDoubleInterval()\n\t{\n\t\treturn EvaluatorDoubleInterval.EVALUATOR_DOUBLE_INTERVAL;\n\t}\n\n\t// Methods in the Evaluator interface\n\t\n\t/**\n\t * Get the value zero.\n\t */\n\tpublic Value zero();\n\n\t/**\n\t * Get the value one.\n\t */\n\tpublic Value one();\n\n\t/**\n\t * Check if a value {@code x} is equal to zero.\n\t */\n\tpublic boolean isZero(Value x);\n\n\t/**\n\t * Check if a value {@code x} is equal to one.\n\t */\n\tpublic boolean isOne(Value x);\n\n\t/**\n\t * Check if a value {@code x} is finite (not +/- infinite or NaN).\n\t */\n\tpublic boolean isFinite(Value x);\n\t\n\t/**\n\t * Compute the sum of {@code x} and {@code y}.\n\t */\n\tpublic Value add(Value x, Value y);\n\n\t/**\n\t * Compute {@code x} minus {@code y}.\n\t */\n\tpublic Value subtract(Value x, Value y);\n\n\t/**\n\t * Compute {@code x} multiplied by {@code y}.\n\t */\n\tpublic Value multiply(Value x, Value y);\n\n\t/**\n\t * Compute {@code x} divided by {@code y}.\n\t */\n\tpublic Value divide(Value x, Value y);\n\n\t/**\n\t * Is {@code x} greater than {@code y}?\n\t */\n\tpublic boolean gt(Value x, Value y);\n\n\t/**\n\t * Is {@code x} greater than or equal to {@code y}?\n\t */\n\tpublic boolean geq(Value x, Value y);\n\n\t/**\n\t * Is {@code x} \"equal\" to {@code y}?\n\t * Note: this is typically a weaker check than Value.equals(), e.g.,\n\t * a floating-point implementation might incorporate a round-off tolerance.\n\t */\n\tpublic boolean equals(Value x, Value y);\n\n\t/**\n\t * Check that the sum of probabilities in a distribution is legal.\n\t * Throws an explanation exception if not.\n\t * By default, this amounts to checking that it is equal to 1.\n\t * A floating-point implementation might incorporate a round-off tolerance.\n\t */\n\tpublic Value checkProbabilitySum(Value sum) throws PrismException;\n\t\n\t/**\n\t * Evaluate an expression in a state to type {@code Value},\n\t * and with values for any constants (optionally) provided.\n\t * Values for constants need to be of appropriate type, e.g.,\n\t * using exact arithmetic if the Evaluator is doing likewise.\n\t */\n\tpublic Value evaluate(Expression expr, Values constantValues, State state) throws PrismLangException;\n\n\t/**\n\t * Evaluate an expression in a state to type {@code Value}\n\t */\n\tpublic default Value evaluate(Expression expr, State state) throws PrismLangException\n\t{\n\t\treturn evaluate(expr, null, state);\n\t}\n\n\t/**\n\t * Parse a value from a string.\n\t * Throws NumberFormatException in case of a parsing error.\n\t */\n\tpublic Value fromString(String s) throws NumberFormatException;\n\t\n\t/**\n\t * Convert value {@code x} to a double (if possible).\n\t */\n\tpublic double toDouble(Value x);\n\n\t/**\n\t * Convert value {@code x} to a string for use in an exported file,\n\t * such as a transitions (.tra) file or similar. For example,\n\t * PRISM exports doubles in a consistent fashion (different from\n\t * Java's Double.toString) to be compatible with export code in C++.\n\t */\n\tpublic default String toStringExport(Value x)\n\t{\n\t\treturn x.toString();\n\t}\n\t\n\t/**\n\t * Convert value {@code x} to a string for use in an exported file,\n\t * such as a transitions (.tra) file or similar. For example,\n\t * PRISM exports doubles in a consistent fashion (different from\n\t * Java's Double.toString) to be compatible with export code in C++.\n\t * If relevant/possible, this is shown to {@code precision} significant places.\n\t */\n\tpublic default String toStringExport(Value x, int precision)\n\t{\n\t\t// By default, just ignore precision\n\t\treturn toStringExport(x);\n\t}\n\t\n\t/**\n\t * Convert value {@code x} to a string for use in a PRISM model/property.\n\t */\n\tpublic default String toStringPrism(Value x)\n\t{\n\t\t// Just do the same as toStringExport, by default\n\t\treturn toStringExport(x);\n\t}\n\t\n\t/**\n\t * Convert value {@code x} to a string for use in a PRISM model/property.\n\t * If relevant/possible, this is shown to {@code precision} significant places.\n\t */\n\tpublic default String toStringPrism(Value x, int precision)\n\t{\n\t\t// Just do the same as toStringExport, by default\n\t\treturn toStringExport(x, precision);\n\t}\n\t\n\t/**\n\t * Does this Evaluator work with exact values?\n\t */\n\tpublic boolean exact();\n\n\t/**\n\t * Does this Evaluator work with symbolic expressions, rather than scalar values?\n\t */\n\tpublic boolean isSymbolic();\n\t\n\t/**\n\t * Get the evaluation model used by this Evaluator.\n\t */\n\tpublic EvalMode evalMode();\n\t\n\t/**\n\t * Create an evaluator for intervals of the {@code Value} object.\n\t */\n\tpublic default Evaluator<Interval<Value>> createIntervalEvaluator() throws PrismException\n\t{\n\t\t// Not supported by default\n\t\tthrow new PrismException(\"Intervals not supported for \" + evalMode());\n\t}\n\n\t// Utility functions\n\n\t/**\n\t * Compute the sum of a list of values.\n\t * By default, this is done using {@link #zero()} and {@link #add(Object, Object)}.\n\t */\n\tpublic default Value sum(Iterable<Value> values)\n\t{\n\t\tValue sum = zero();\n\t\tfor (Value value : values) {\n\t\t\tsum = add(sum, value);\n\t\t}\n\t\treturn sum;\n\t}\n\n\t/**\n\t * Compute the product of a list of values.\n\t * By default, this is done using {@link #one()} and {@link #multiply(Object, Object)}.\n\t */\n\tpublic default Value product(Iterable<Value> values)\n\t{\n\t\tValue prod = one();\n\t\tfor (Value value : values) {\n\t\t\tprod = multiply(prod, value);\n\t\t}\n\t\treturn prod;\n\t}\n\n\t// Evaluator for doubles\n\n\tclass EvaluatorDouble implements Evaluator<Double>\n\t{\n\t\tprivate static final Evaluator<Double> EVALUATOR_DOUBLE = new EvaluatorDouble();\n\t\tprivate static final Double ZERO = Double.valueOf(0.0);\n\t\tprivate static final Double ONE = Double.valueOf(1.0);\n\n\t\t@Override\n\t\tpublic Double zero()\n\t\t{\n\t\t\treturn ZERO;\n\t\t}\n\n\t\t@Override\n\t\tpublic Double one()\n\t\t{\n\t\t\treturn ONE;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isZero(Double x)\n\t\t{\n\t\t\treturn x == 0.0;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isOne(Double x)\n\t\t{\n\t\t\t// We allow round-off error here\n\t\t\treturn PrismUtils.doublesAreEqual(x, 1.0);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isFinite(Double x)\n\t\t{\n\t\t\treturn Double.isFinite(x);\n\t\t}\n\n\t\t@Override\n\t\tpublic Double add(Double x, Double y)\n\t\t{\n\t\t\treturn x + y;\n\t\t}\n\n\t\t@Override\n\t\tpublic Double subtract(Double x, Double y)\n\t\t{\n\t\t\treturn x - y;\n\t\t}\n\n\t\t@Override\n\t\tpublic Double multiply(Double x, Double y)\n\t\t{\n\t\t\treturn x * y;\n\t\t}\n\n\t\t@Override\n\t\tpublic Double divide(Double x, Double y)\n\t\t{\n\t\t\treturn x / y;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean gt(Double x, Double y)\n\t\t{\n\t\t\treturn x > y;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean geq(Double x, Double y)\n\t\t{\n\t\t\treturn x >= y;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(Double x, Double y)\n\t\t{\n\t\t\t// We allow round-off error here\n\t\t\treturn PrismUtils.doublesAreEqual(x, y);\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic Double checkProbabilitySum(Double sum) throws PrismException\n\t\t{\n\t\t\t// We allow round-off error here\n\t\t\tif (!PrismUtils.doublesAreEqual(sum, 1.0)) {\n\t\t\t\tthrow new PrismException(\"Probabilities sum to \" + sum);\n\t\t\t}\n\t\t\treturn sum;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic Double evaluate(Expression expr, Values constantValues, State state) throws PrismLangException\n\t\t{\n\t\t\treturn expr.evaluateDouble(constantValues, state);\n\t\t}\n\n\t\t@Override\n\t\tpublic double toDouble(Double x)\n\t\t{\n\t\t\treturn x;\n\t\t}\n\n\t\t@Override\n\t\tpublic String toStringExport(Double x)\n\t\t{\n\t\t\treturn PrismUtils.formatDouble(x);\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic String toStringExport(Double x, int precision)\n\t\t{\n\t\t\treturn PrismUtils.formatDouble(precision, x);\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic Double fromString(String s) throws NumberFormatException\n\t\t{\n\t\t\treturn Double.parseDouble(s);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean exact()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean isSymbolic()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic EvalMode evalMode()\n\t\t{\n\t\t\treturn EvalMode.FP;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic Evaluator<Interval<Double>> createIntervalEvaluator()\n\t\t{\n\t\t\treturn EvaluatorDoubleInterval.EVALUATOR_DOUBLE_INTERVAL;\n\t\t}\n\t};\n\n\t// Evaluator for rationals (using param.BigRational)\n\n\tclass EvaluatorBigRational implements Evaluator<BigRational>\n\t{\n\t\tprivate static final Evaluator<BigRational> EVALUATOR_BIG_RATIONAL = new EvaluatorBigRational();\n\n\t\t@Override\n\t\tpublic BigRational zero()\n\t\t{\n\t\t\treturn BigRational.ZERO;\n\t\t}\n\n\t\t@Override\n\t\tpublic BigRational one()\n\t\t{\n\t\t\treturn BigRational.ONE;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isZero(BigRational x)\n\t\t{\n\t\t\treturn x.equals(BigRational.ZERO);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isOne(BigRational x)\n\t\t{\n\t\t\treturn x.equals(BigRational.ONE);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isFinite(BigRational x)\n\t\t{\n\t\t\treturn x.isFinite();\n\t\t}\n\n\t\t@Override\n\t\tpublic BigRational add(BigRational x, BigRational y)\n\t\t{\n\t\t\treturn x.add(y);\n\t\t}\n\n\t\t@Override\n\t\tpublic BigRational subtract(BigRational x, BigRational y)\n\t\t{\n\t\t\treturn x.subtract(y);\n\t\t}\n\n\t\t@Override\n\t\tpublic BigRational multiply(BigRational x, BigRational y)\n\t\t{\n\t\t\treturn x.multiply(y);\n\t\t}\n\n\t\t@Override\n\t\tpublic BigRational divide(BigRational x, BigRational y)\n\t\t{\n\t\t\treturn x.divide(y);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean gt(BigRational x, BigRational y)\n\t\t{\n\t\t\treturn x.compareTo(y) > 0;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean geq(BigRational x, BigRational y)\n\t\t{\n\t\t\treturn x.compareTo(y) >= 0;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(BigRational x, BigRational y)\n\t\t{\n\t\t\treturn x.equals(y);\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic BigRational checkProbabilitySum(BigRational sum) throws PrismException\n\t\t{\n\t\t\tif (!isOne(sum)) {\n\t\t\t\tthrow new PrismException(\"Probabilities sum to \" + sum);\n\t\t\t}\n\t\t\treturn sum;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic BigRational evaluate(Expression expr, Values constantValues, State state) throws PrismLangException\n\t\t{\n\t\t\tObject value = expr.evaluate(new EvaluateContextState(constantValues, state).setEvaluationMode(EvalMode.EXACT));\n\t\t\treturn (BigRational) TypeDouble.getInstance().castValueTo(value, EvalMode.EXACT);\n\t\t}\n\n\t\t@Override\n\t\tpublic double toDouble(BigRational x)\n\t\t{\n\t\t\treturn x.doubleValue();\n\t\t}\n\n\t\t@Override\n\t\tpublic BigRational fromString(String s) throws NumberFormatException\n\t\t{\n\t\t\treturn new BigRational(s);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean exact()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean isSymbolic()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic EvalMode evalMode()\n\t\t{\n\t\t\treturn EvalMode.EXACT;\n\t\t}\n\n\t\t@Override\n\t\tpublic Evaluator<Interval<BigRational>> createIntervalEvaluator()\n\t\t{\n\t\t\treturn EvaluatorBigRationalInterval.EVALUATOR_BIG_RATIONAL_INTERVAL;\n\t\t}\n\t};\n\t\n\t// Evaluator for rational functions (using param.Function)\n\t\n\tclass EvaluatorFunction implements Evaluator<Function>\n\t{\n\t\tprotected FunctionFactory functionFactory;\n\n\t\tpublic EvaluatorFunction(FunctionFactory functionFactory)\n\t\t{\n\t\t\tthis.functionFactory = functionFactory;\n\t\t}\n\n\t\t/**\n\t\t * Get the FunctionFactory used for manipulating Function objects.\n\t\t */\n\t\tpublic FunctionFactory getFunctionFactory()\n\t\t{\n\t\t\treturn functionFactory;\n\t\t}\n\n\t\t@Override\n\t\tpublic Function zero()\n\t\t{\n\t\t\treturn functionFactory.getZero();\n\t\t}\n\n\t\t@Override\n\t\tpublic Function one()\n\t\t{\n\t\t\treturn functionFactory.getOne();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isZero(Function x)\n\t\t{\n\t\t\t// Technically, not quite right since it could miss some cases\n\t\t\t// where the function is globally zero. But, if this returns true,\n\t\t\t// then it _is_ zero for all values, so still useful to have\n\t\t\treturn x.isZero();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isOne(Function x)\n\t\t{\n\t\t\t// Technically, not quite right since it could miss some cases\n\t\t\t// where the function is globally one. But, if this returns true,\n\t\t\t// then it _is_ one for all values, so still useful to have\n\t\t\treturn x.isOne();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isFinite(Function x)\n\t\t{\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic Function add(Function x, Function y)\n\t\t{\n\t\t\treturn x.add(y);\n\t\t}\n\n\t\t@Override\n\t\tpublic Function subtract(Function x, Function y)\n\t\t{\n\t\t\treturn x.subtract(y);\n\t\t}\n\n\t\t@Override\n\t\tpublic Function multiply(Function x, Function y)\n\t\t{\n\t\t\treturn x.multiply(y);\n\t\t}\n\n\t\t@Override\n\t\tpublic Function divide(Function x, Function y)\n\t\t{\n\t\t\treturn x.divide(y);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean gt(Function x, Function y)\n\t\t{\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean geq(Function x, Function y)\n\t\t{\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(Function x, Function y)\n\t\t{\n\t\t\treturn x.equals(y);\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic Function checkProbabilitySum(Function sum) throws PrismException\n\t\t{\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic Function evaluate(Expression expr, Values constantValues, State state) throws PrismLangException\n\t\t{\n\t\t\t//return expr.getType().castFromBigRational(expr.evaluateExact(state);\n\t\t\treturn functionFactory.expr2function((Expression) expr.deepCopy().evaluatePartially(constantValues, state));\n\t\t}\n\n\t\t@Override\n\t\tpublic double toDouble(Function x)\n\t\t{\n\t\t\t// Cannot do this, in general\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic Function fromString(String s) throws NumberFormatException\n\t\t{\n\t\t\t// TODO\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean exact()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isSymbolic()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic EvalMode evalMode()\n\t\t{\n\t\t\t// Return EXACT for now since exact computation uses this\n\t\t\treturn EvalMode.EXACT;\n\t\t}\n\t}\n\t\n\t// Evaluator for intervals (of doubles)\n\n\tclass EvaluatorDoubleInterval implements Evaluator<Interval<Double>>\n\t{\n\t\tprivate static final Evaluator<Interval<Double>> EVALUATOR_DOUBLE_INTERVAL = new EvaluatorDoubleInterval();\n\t\tprivate static final Interval<Double> ZERO = new Interval<Double>(0.0, 0.0);\n\t\tprivate static final Interval<Double> ONE = new Interval<Double>(1.0, 1.0);\n\n\t\t@Override\n\t\tpublic Interval<Double> zero()\n\t\t{\n\t\t\treturn ZERO;\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<Double> one()\n\t\t{\n\t\t\treturn ONE;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isZero(Interval<Double> x)\n\t\t{\n\t\t\treturn x.getLower() == 0.0 && x.getUpper() == 0.0;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isOne(Interval<Double> x)\n\t\t{\n\t\t\t// We allow round-off error here\n\t\t\treturn PrismUtils.doublesAreEqual(x.getLower(), 1.0) && PrismUtils.doublesAreEqual(x.getUpper(), 1.0);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isFinite(Interval<Double> x)\n\t\t{\n\t\t\treturn Double.isFinite(x.getLower()) && Double.isFinite(x.getUpper());\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<Double> add(Interval<Double> x, Interval<Double> y)\n\t\t{\n\t\t\tdouble lo = x.getLower() + y.getLower();\n\t\t\tdouble up = x.getUpper() + y.getUpper();\n\t\t\treturn new Interval<Double>(lo, up);\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<Double> subtract(Interval<Double> x, Interval<Double> y)\n\t\t{\n\t\t\tdouble lo = x.getLower() - y.getLower();\n\t\t\tdouble up = x.getUpper() - y.getUpper();\n\t\t\treturn new Interval<Double>(lo, up);\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<Double> multiply(Interval<Double> x, Interval<Double> y)\n\t\t{\n\t\t\tdouble x1y1 = x.getLower() * y.getLower();\n\t\t\tdouble x1y2 = x.getLower() * y.getUpper();\n\t\t\tdouble x2y1 = x.getUpper() * y.getLower();\n\t\t\tdouble x2y2 = x.getUpper() * y.getUpper();\n\t\t\tdouble lo = Math.min(x1y1, Math.min(x1y2, Math.min(x2y1, x2y2)));\n\t\t\tdouble up = Math.max(x1y1, Math.max(x1y2, Math.max(x2y1, x2y2)));\n\t\t\treturn new Interval<Double>(lo, up);\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<Double> divide(Interval<Double> x, Interval<Double> y)\n\t\t{\n\t\t\t// TODO\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean gt(Interval<Double> x, Interval<Double> y)\n\t\t{\n\t\t\treturn x.getLower() > y.getUpper();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean geq(Interval<Double> x, Interval<Double> y)\n\t\t{\n\t\t\treturn x.getLower() >= y.getUpper();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(Interval<Double> x, Interval<Double> y)\n\t\t{\n\t\t\t// We allow round-off error here\n\t\t\tboolean loClose = PrismUtils.doublesAreEqual(x.getLower(), y.getLower());\n\t\t\tboolean upClose = PrismUtils.doublesAreEqual(x.getUpper(), y.getUpper());\n\t\t\treturn loClose && upClose;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic Interval<Double> checkProbabilitySum(Interval<Double> sum) throws PrismException\n\t\t{\n\t\t\t// For intervals, we need the sum of lower bounds to be <=1\n\t\t\t// and the sum of upper bounds to be >=1\n\t\t\t// We allow round-off error here (as for the normal case of doubles)\n\t\t\tif (sum.getLower() > 1.0 + PrismUtils.epsilonDouble) {\n\t\t\t\tthrow new PrismException(\"Probability lower bounds sum to \" + sum.getLower() + \" which is greater than 1\");\n\t\t\t}\n\t\t\tif (sum.getUpper() < 1.0 - PrismUtils.epsilonDouble) {\n\t\t\t\tthrow new PrismException(\"Probability upper bounds sum to \" + sum.getUpper() + \" which is less than 1\");\n\t\t\t}\n\t\t\treturn sum;\n\t\t}\n\t\t\n\t\t@Override\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tpublic Interval<Double> evaluate(Expression expr, Values constantValues, State state) throws PrismLangException\n\t\t{\n\t\t\tObject value = expr.evaluate(constantValues, state);\n\t\t\treturn (Interval<Double>) TypeInterval.getInstance(TypeDouble.getInstance()).castValueTo(value);\n\t\t}\n\n\t\t@Override\n\t\tpublic double toDouble(Interval<Double> x)\n\t\t{\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic String toStringExport(Interval<Double> x)\n\t\t{\n\t\t\tString l = PrismUtils.formatDouble(x.getLower()); \n\t\t\tString u = PrismUtils.formatDouble(x.getUpper()); \n\t\t\treturn \"[\" + l + \",\" + u + \"]\";\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic String toStringExport(Interval<Double> x, int precision)\n\t\t{\n\t\t\tString l = PrismUtils.formatDouble(precision, x.getLower()); \n\t\t\tString u = PrismUtils.formatDouble(precision, x.getUpper()); \n\t\t\treturn \"[\" + l + \",\" + u + \"]\";\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic Interval<Double> fromString(String s) throws NumberFormatException\n\t\t{\n\t\t\tif (!(s.charAt(0) == '[' && s.charAt(s.length() - 1) == ']')) {\n\t\t\t\tthrow new NumberFormatException(\"Illegal interval \" + s);\n\t\t\t}\n\t\t\ts = s.substring(1, s.length() - 1);\n\t\t\tString ss[] = s.split(\",\");\n\t\t\tif (ss.length != 2) {\n\t\t\t\tthrow new NumberFormatException(\"Illegal interval \" + s);\n\t\t\t}\n\t\t\treturn new Interval<Double>(Double.parseDouble(ss[0]), Double.parseDouble(ss[1]));\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean exact()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean isSymbolic()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic EvalMode evalMode()\n\t\t{\n\t\t\treturn EvalMode.FP;\n\t\t}\n\t}\n\n\t// Evaluator for intervals (of doubles)\n\n\tclass EvaluatorBigRationalInterval implements Evaluator<Interval<BigRational>>\n\t{\n\t\tprivate static final Evaluator<Interval<BigRational>> EVALUATOR_BIG_RATIONAL_INTERVAL = new EvaluatorBigRationalInterval();\n\t\tprivate static final Interval<BigRational> ZERO = new Interval<BigRational>(BigRational.ZERO, BigRational.ZERO);\n\t\tprivate static final Interval<BigRational> ONE = new Interval<BigRational>(BigRational.ONE, BigRational.ONE);\n\n\t\t@Override\n\t\tpublic Interval<BigRational> zero()\n\t\t{\n\t\t\treturn ZERO;\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<BigRational> one()\n\t\t{\n\t\t\treturn ONE;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isZero(Interval<BigRational> x)\n\t\t{\n\t\t\treturn x.getLower().equals(BigRational.ZERO) && x.getUpper().equals(BigRational.ZERO);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isOne(Interval<BigRational> x)\n\t\t{\n\t\t\treturn x.getLower().equals(BigRational.ONE) && x.getUpper().equals(BigRational.ONE);\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isFinite(Interval<BigRational> x)\n\t\t{\n\t\t\treturn x.getLower().isFinite() && x.getUpper().isFinite();\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<BigRational> add(Interval<BigRational> x, Interval<BigRational> y)\n\t\t{\n\t\t\tBigRational lo = x.getLower().add(y.getLower());\n\t\t\tBigRational up = x.getUpper().add(y.getUpper());\n\t\t\treturn new Interval<BigRational>(lo, up);\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<BigRational> subtract(Interval<BigRational> x, Interval<BigRational> y)\n\t\t{\n\t\t\tBigRational lo = x.getLower().subtract(y.getLower());\n\t\t\tBigRational up = x.getUpper().subtract(y.getUpper());\n\t\t\treturn new Interval<>(lo, up);\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<BigRational> multiply(Interval<BigRational> x, Interval<BigRational> y)\n\t\t{\n\t\t\tBigRational x1y1 = x.getLower().multiply(y.getLower());\n\t\t\tBigRational x1y2 = x.getLower().multiply(y.getUpper());\n\t\t\tBigRational x2y1 = x.getUpper().multiply(y.getLower());\n\t\t\tBigRational x2y2 = x.getUpper().multiply(y.getUpper());\n\t\t\tBigRational lo = x1y1.min(x1y2).min(x2y1).min(x2y2);\n\t\t\tBigRational up = x1y1.max(x1y2).max(x2y1).max(x2y2);\n\t\t\treturn new Interval<>(lo, up);\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<BigRational> divide(Interval<BigRational> x, Interval<BigRational> y)\n\t\t{\n\t\t\t// TODO\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean gt(Interval<BigRational> x, Interval<BigRational> y)\n\t\t{\n\t\t\treturn x.getLower().greaterThan(y.getUpper());\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean geq(Interval<BigRational> x, Interval<BigRational> y)\n\t\t{\n\t\t\treturn x.getLower().greaterThanEquals(y.getUpper());\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(Interval<BigRational> x, Interval<BigRational> y)\n\t\t{\n\t\t\treturn x.getLower().equals(y.getLower()) && x.getUpper().equals(y.getUpper());\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<BigRational> checkProbabilitySum(Interval<BigRational> sum) throws PrismException\n\t\t{\n\t\t\t// For intervals, we need the sum of lower bounds to be <=1\n\t\t\t// and the sum of upper bounds to be >=1\n\t\t\tif (sum.getLower().greaterThan(BigRational.ONE)) {\n\t\t\t\tthrow new PrismException(\"Probability lower bounds sum to \" + sum.getLower() + \" which is greater than 1\");\n\t\t\t}\n\t\t\tif (sum.getUpper() .lessThan(BigRational.ONE)) {\n\t\t\t\tthrow new PrismException(\"Probability upper bounds sum to \" + sum.getUpper() + \" which is less than 1\");\n\t\t\t}\n\t\t\treturn sum;\n\t\t}\n\n\t\t@Override\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tpublic Interval<BigRational> evaluate(Expression expr, Values constantValues, State state) throws PrismLangException\n\t\t{\n\t\t\tObject value = expr.evaluate(new EvaluateContextState(constantValues, state).setEvaluationMode(EvalMode.EXACT));\n\t\t\treturn (Interval<BigRational>) TypeInterval.getInstance(TypeDouble.getInstance()).castValueTo(value, EvalMode.EXACT);\n\t\t}\n\n\t\t@Override\n\t\tpublic double toDouble(Interval<BigRational> x)\n\t\t{\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\t@Override\n\t\tpublic Interval<BigRational> fromString(String s) throws NumberFormatException\n\t\t{\n\t\t\tif (!(s.charAt(0) == '[' && s.charAt(s.length() - 1) == ']')) {\n\t\t\t\tthrow new NumberFormatException(\"Illegal interval \" + s);\n\t\t\t}\n\t\t\ts = s.substring(1, s.length() - 1);\n\t\t\tString ss[] = s.split(\",\");\n\t\t\tif (ss.length != 2) {\n\t\t\t\tthrow new NumberFormatException(\"Illegal interval \" + s);\n\t\t\t}\n\t\t\treturn new Interval<>(new BigRational(ss[0]), new BigRational(ss[1]));\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean exact()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isSymbolic()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic EvalMode evalMode()\n\t\t{\n\t\t\treturn EvalMode.EXACT;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Filter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * Class to store basic information about how results of model checking will be filtered.\n */\npublic class Filter\n{\n\t// Enums for types of filter\n\tpublic enum FilterOperator {\n\t\tSTATE;\n\t};\n\t// Filter operator\n\tprivate FilterOperator op = null;\n\t// State of interest\n\tprivate int stateIndex = -1; \n\n\t// Constructors\n\t\n\tpublic Filter(FilterOperator op, int stateIndex)\n\t{\n\t\tsetOperator(op);\n\t\tsetStateIndex(stateIndex);\n\t}\n\t\n\t// Getters/setters\n\t\n\tpublic FilterOperator getOperator()\n\t{\n\t\treturn op;\n\t}\n\t\n\tpublic int getStateIndex()\n\t{\n\t\treturn stateIndex;\n\t}\n\t\n\tpublic void setOperator(FilterOperator op)\n\t{\n\t\tthis.op = op;\n\t}\n\t\n\tpublic void setStateIndex(int stateIndex)\n\t{\n\t\tthis.stateIndex = stateIndex;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/IntegerBound.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport parser.Values;\nimport parser.ast.ExpressionTemporal;\n\n/**\n * Canonical representation of an integer bound, with strict/non-strict lower and upper bound.\n */\npublic class IntegerBound\n{\n\t/** The lowest integer that is included in the bound. {@code null} for \"no bound\". */\n\tprivate Integer lowest;\n\t/** The highest integer that is included in the bound. {@code null} for \"no bound\". */\n\tprivate Integer highest;\n\n\t/** Create new bounds.\n\t * @param lower: The lower bound, {@code null} represents \"no lower bound\"\n\t * @param lower_strict: Is the lower bound strict (&gt; lower) or non-strict (&gt;= lower)\n\t * @param upper: The upper bound, {@code null} represents \"no upper bound\"\n\t * @param upper_strict: Is the upper bound strict (&lt; upper) or non-strict (&lt;= upper)\n\t */\n\tpublic IntegerBound(Integer lower, boolean lower_strict, Integer upper, boolean upper_strict)\n\t{\n\t\t// normalize\n\t\tif (lower_strict && lower != null) {\n\t\t\tlowest = Integer.valueOf(lower+1);\n\t\t} else {\n\t\t\tlowest = lower;\n\t\t}\n\t\tif (upper_strict && upper != null) {\n\t\t\thighest = Integer.valueOf(upper-1);\n\t\t} else {\n\t\t\thighest = upper;\n\t\t}\n\t}\n\n\t/**\n\t * Extract the bounds from an {@code ExpressionTemporal} expression\n\t * and create the corresponding {@code IntegerBound}.\n\t *\n\t * Expects that constants for the upper and lower bounds have already been resolved.\n\t *\n\t * If {@code check} is {@code true}, throws an exception for negative or empty bounds.\n\t *\n\t * @param expression the expression\n\t * @param check check for non-negative bounds / non-emptiness?\n\t * @return the {@code IntegerBound} for the expression\n\t * @throws PrismException\n\t */\n\tpublic static IntegerBound fromExpressionTemporal(ExpressionTemporal expression, boolean check) throws PrismException\n\t{\n\t\treturn fromExpressionTemporal(expression, null, check);\n\t}\n\n\t/**\n\t * Extract the bounds from an {@code ExpressionTemporal} expression\n\t * and create the corresponding {@code IntegerBound}, resolving constants\n\t * via {@code constantValues}.\n\t *\n\t * If {@code check} is {@code true}, throws an exception for negative or empty bounds.\n\t *\n\t * @param expression the expression\n\t * @param constantValues the values for constants (may be {@code null})\n\t * @param check check for non-negative bounds / non-emptiness?\n\t * @return the {@code IntegerBound} for the expression\n\t * @throws PrismException\n\t */\n\tpublic static IntegerBound fromExpressionTemporal(ExpressionTemporal expression, Values constantValues, boolean check) throws PrismException\n\t{\n\t\tIntegerBound bounds =  new IntegerBound(expression.getLowerBound() == null ? null : expression.getLowerBound().evaluateInt(constantValues),\n\t\t                                          expression.lowerBoundIsStrict(),\n\t\t                                          expression.getUpperBound() == null ? null : expression.getUpperBound().evaluateInt(constantValues),\n\t\t                                          expression.upperBoundIsStrict());\n\n\t\tif (check) {\n\t\t\tif (bounds.hasNegativeBound()) {\n\t\t\t\tthrow new PrismException(\"Negative bound in \"+expression.toString());\n\t\t\t}\n\t\t\tif (bounds.isEmpty()) {\n\t\t\t\tthrow new PrismException(\"Empty bound in \"+expression.toString());\n\t\t\t}\n\t\t}\n\n\t\treturn bounds;\n\t}\n\n\t/** Returns {@code true} if there exists some lower bound. */\n\tpublic boolean hasLowerBound()\n\t{\n\t\treturn lowest != null;\n\t}\n\n\t/** Returns {@code true} if there exists some upper bound. */\n\tpublic boolean hasUpperBound()\n\t{\n\t\treturn highest != null;\n\t}\n\n\t/**\n\t * Returns the lowest integer included in the bounds. {@code null} = \"no bound\".\n\t * Assumes that {@code isEmpty()} is {@code false}.\n\t **/\n\tpublic Integer getLowestInteger()\n\t{\n\t\treturn lowest;\n\t}\n\n\t/**\n\t * Returns the highest integer included in the bounds. {@code null} = \"no bound\".\n\t * Assumes that {@code isEmpty} is {@code false}.\n\t **/\n\tpublic Integer getHighestInteger()\n\t{\n\t\treturn highest;\n\t}\n\n\t/** Returns {@code true} if the lower or upper bound is negative. */\n\tpublic boolean hasNegativeBound()\n\t{\n\t\tif (lowest != null && lowest < 0 ||\n\t\t    highest != null && highest < 0) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** Returns {@code true} if the lower bound is higher than the upper bound. */\n\tpublic boolean isEmpty()\n\t{\n\t\tif (hasLowerBound() && hasUpperBound()) return getLowestInteger()>getHighestInteger();\n\t\treturn false;\n\t}\n\n\t/** Returns true if {@code value} is in the bounds. */\n\tpublic boolean isInBounds(int value)\n\t{\n\t\tif (lowest!=null) {\n\t\t\tif (value >= lowest) {\n\t\t\t\t// continue\n\t\t\t} else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\tif (highest!=null) {\n\t\t\tif (value <= highest) {\n\t\t\t\treturn true;\n\t\t\t} else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\t// no bound (upper=lower=null)\n\t\treturn true;\n\t}\n\n\t/** Get the maximal interesting value, i.e., the value v such that\n\t *  for _all_ i&gt;=v either isInBound(i)=true or isInBound(i)=false */\n\tpublic int getMaximalInterestingValue()\n\t{\n\t\tint max = 0;\n\n\t\tif (isEmpty()) return 0;\n\n\t\tif (lowest != null) {\n\t\t\tmax = lowest;\n\t\t}\n\n\t\tif (highest != null) {\n\t\t\tmax = highest + 1;\n\t\t}\n\n\t\treturn max;\n\t}\n\n\t/** String representation */\n\tpublic String toString()\n\t{\n\t\tif (hasLowerBound()) {\n\t\t\tif (hasUpperBound()) {\n\t\t\t\tif (getLowestInteger().equals(getHighestInteger())) {\n\t\t\t\t\treturn \"=\"+getLowestInteger();\n\t\t\t\t}\n\t\t\t\treturn \"[\"+getLowestInteger()+\",\"+getHighestInteger()+\"]\";\n\t\t\t} else {\n\t\t\t\treturn \">=\"+getLowestInteger();\n\t\t\t}\n\t\t} else {\n\t\t\tif (hasUpperBound()) {\n\t\t\t\treturn \"<=\"+getHighestInteger();\n\t\t\t} else {\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\t}\n\t\n\tpublic static void main(String args[])\n\t{\n\t\tSystem.out.println(new IntegerBound(1, true, 3, false));\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Interval.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * This class stores an interval of numerical values.\n */\npublic class Interval\n{\n\t// Lower/upper value\n\tpublic Object lower;\n\tpublic Object upper;\n\t\n\t/**\n\t * Construct an Interval.\n\t * (lower and upper should be of the same type: Integer or Double)\n\t */\n\tpublic Interval(Object lower, Object upper)\n\t{\n\t\tthis.lower = lower;\n\t\tthis.upper = upper;\n\t}\n\t\n\t/**\n\t * Construct an integer Interval.\n\t */\n\tpublic Interval(Integer lower, Integer upper)\n\t{\n\t\tthis.lower = lower;\n\t\tthis.upper = upper;\n\t}\n\t\n\t/**\n\t * Construct a double Interval.\n\t */\n\tpublic Interval(Double lower, Double upper)\n\t{\n\t\tthis.lower = lower;\n\t\tthis.upper = upper;\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + lower + \",\" + upper + \"]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/MathML2Prism.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.*;\nimport java.util.*;\nimport javax.xml.parsers.*;\nimport org.w3c.dom.Document;\nimport org.w3c.dom.Node;\nimport org.w3c.dom.NodeList;\nimport org.xml.sax.*;\n\npublic class MathML2Prism\n{\n\t// Converts a MathML object to the corresponding PRISM expression (as a string)\n\t// (optionally with a list of renames for identifiers)\n\t\n\tpublic static String convert(Node node) throws PrismException { return convert(node, null, null); }\n\t\n\tpublic static String convert(Node node, ArrayList<String> renameFrom, ArrayList<String> renameTo) throws PrismException\n\t{\n\t\tString s, nodeName, apply;\n\t\tint nodeType, i, n;\n\t\tNodeList allChildren;\n\t\tArrayList<Node> children;\n\t\tArrayList<String> translatedChildren;\n\t\t\n\t\tnodeType = node.getNodeType();\n\t\tswitch (nodeType) {\n\t\t\n\t\t// MathML node\n\t\tcase Node.ELEMENT_NODE:\n\t\t\tnodeName = node.getNodeName();\n\t\t\t\n\t\t\t// Top-level element\n\t\t\tif (nodeName.equals(\"math\")) {\n\t\t\t\t// return string for first non-text element\n\t\t\t\tallChildren = node.getChildNodes();\n\t\t\t\tn = allChildren.getLength();\n\t\t\t\tchildren = new ArrayList<Node>();\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\tif (allChildren.item(i).getNodeType() != Node.TEXT_NODE) children.add(allChildren.item(i));\n\t\t\t\t}\n\t\t\t\tif (children.size() == 0) throw new PrismException(\"Empty MathML expression\");\n\t\t\t\tif (children.size() > 1) throw new PrismException(\"Too many top-level nodes in MathML expression\");\n\t\t\t\treturn convert(children.get(0), renameFrom, renameTo);\n\t\t\t}\n\t\t\t\n\t\t\t// Literal\n\t\t\tif (nodeName.equals(\"cn\")) {\n\t\t\t\ts = node.getFirstChild().getNodeValue().trim();\n\t\t\t\treturn s;\n\t\t\t}\n\t\t\t\n\t\t\t// Identifier\n\t\t\telse if (nodeName.equals(\"ci\")) {\n\t\t\t\ts = node.getFirstChild().getNodeValue().trim();\n\t\t\t\tif (renameFrom != null) if (renameFrom.contains(s)) s = renameTo.get(renameFrom.indexOf(s));\n\t\t\t\treturn s;\n\t\t\t}\n\t\t\t\n\t\t\t// Apply operator\n\t\t\telse if (nodeName.equals(\"apply\")) {\n\t\t\t\t// Get list of non-text nodes\n\t\t\t\tallChildren = node.getChildNodes();\n\t\t\t\tn = allChildren.getLength();\n\t\t\t\tchildren = new ArrayList<Node>();\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\tif (allChildren.item(i).getNodeType() != Node.TEXT_NODE) children.add(allChildren.item(i));\n\t\t\t\t}\n\t\t\t\tn = children.size();\n\t\t\t\tif (n == 0) throw new PrismException(\"Empty apply node in MathML expression\");\n\t\t\t\t// Find operator and translate children\n\t\t\t\tapply = children.get(0).getNodeName();\n\t\t\t\ttranslatedChildren = new ArrayList<String>();\n\t\t\t\tn = children.size() - 1;\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\ttranslatedChildren.add(convert(children.get(i+1), renameFrom, renameTo));\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Apply \"plus\"\n\t\t\t\tif (apply.equals(\"plus\")) {\n\t\t\t\t\ts = \"(\";\n\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\tif (i > 0) s += \"+\";\n\t\t\t\t\t\ts += translatedChildren.get(i);\n\t\t\t\t\t}\n\t\t\t\t\ts += \")\";\n\t\t\t\t\treturn s;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Apply \"minus\"\n\t\t\t\tif (apply.equals(\"minus\")) {\n\t\t\t\t\tif (n != 2) throw new PrismException(\"MathML apply minus operations has \"+n+\" operands\");\n\t\t\t\t\ts = \"(\"+translatedChildren.get(0)+\"-\"+translatedChildren.get(1)+\")\";\n\t\t\t\t\treturn s;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Apply \"times\"\n\t\t\t\tif (apply.equals(\"times\")) {\n\t\t\t\t\ts = \"(\";\n\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\tif (i > 0) s += \"*\";\n\t\t\t\t\t\ts += translatedChildren.get(i);\n\t\t\t\t\t}\n\t\t\t\t\ts += \")\";\n\t\t\t\t\treturn s;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Apply \"divide\"\n\t\t\t\tif (apply.equals(\"divide\")) {\n\t\t\t\t\tif (n != 2) throw new PrismException(\"MathML apply divide operations has \"+n+\" operands\");\n\t\t\t\t\ts = \"(\"+translatedChildren.get(0)+\"/\"+translatedChildren.get(1)+\")\";\n\t\t\t\t\treturn s;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Apply \"power\"\n\t\t\t\tif (apply.equals(\"power\")) {\n\t\t\t\t\tif (n != 2) throw new PrismException(\"MathML apply power operations has \"+n+\" operands\");\n\t\t\t\t\ts = \"(func(pow,\"+translatedChildren.get(0)+\",\"+translatedChildren.get(1)+\"))\";\n\t\t\t\t\treturn s;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tthrow new PrismException(\"Unknown MathML apply operator \\\"\"+apply+\"\\\"\");\n\t\t\t}\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Unknown MathML element \\\"\"+nodeName+\"\\\"\");\n\t\t\t}\n\t\t\n\t\t// Ignore CDATA sections + entity references\n\t\tcase Node.CDATA_SECTION_NODE:\n\t\tcase Node.ENTITY_REFERENCE_NODE:\n\t\t\treturn \"\";\n\t\t\n\t\t// Ignore text. For cases where we need it, e.g. \"<ci> k4prime </ci>\",\n\t\t// this is processed by the parent node, e.g. <ci>\n\t\tcase Node.TEXT_NODE:\n\t\t\treturn \"\";\n\t\t\n\t\t// Ignore processing instructions\n\t\tcase Node.PROCESSING_INSTRUCTION_NODE:\n\t\t\treturn \"\";\n\t\t}\n\t\t\n\t\t// Default: return empty string\n\t\treturn \"\";\n\t}\n\t\n\t// Additional utility method (currently unused except for testing)\n\t// which parses a MathML expression from an InputStream before calling the conversion method above\n\t\n\tpublic static String parseAndConvert(InputStream in) throws PrismException\n\t{\n\t\tDocumentBuilderFactory factory;\n\t\tDocumentBuilder builder;\n\t\tDocument doc = null;\n\t\t\n\t\t// Create XML parser\n\t\tfactory = DocumentBuilderFactory.newInstance();\n\t\tfactory.setValidating(false);\n\t\tfactory.setIgnoringElementContentWhitespace(true);\n\t\ttry {\n\t\t\tbuilder = factory.newDocumentBuilder();\n\t\t\t//builder.setEntityResolver(this);\n\t\t\tbuilder.setErrorHandler(new ErrorHandler() {\n\t\t\t\tpublic void fatalError(SAXParseException e) throws SAXException { throw e; }\n\t\t\t\tpublic void error(SAXParseException e) throws SAXException { throw e; }\n\t\t\t\tpublic void warning(SAXParseException e) {}\n\t\t\t});\n\t\t}\n\t\tcatch (ParserConfigurationException e) {\n\t\t\tthrow new PrismException(\"Couldn't create XML parser\");\n\t\t}\n\t\t\n\t\t// Parse\n\t\ttry {\n\t\t\tdoc = builder.parse(in);\n\t\t\t\n\t\t\treturn convert(doc.getDocumentElement());\n\t\t}\n\t\tcatch (IOException e) {\n\t\t\tthrow new PrismException(\"I/O error: \"+e.getMessage());\n\t\t}\n\t\tcatch (SAXException e) {\n\t\t\tthrow new PrismException(\"Invalid XML file:\\n\"+ e.getMessage());\n\t\t}\n\t}\n\n\t// Test call function - read MathML expression from stdin, convert, send to stdout\n\t\n\tpublic static void main(String args[])\n\t{\n\t\ttry {\n\t\t\tString s = parseAndConvert(System.in);\n\t\t\tSystem.out.println(s);\n\t\t}\n\t\tcatch (PrismException e) {\n\t\t\tSystem.err.println(\"Error: \"+e.getMessage());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Model.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2023-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.stream.Collectors;\n\n/**\n * Interface for classes that store models.\n * This is generic, where probabilities/rates/etc. are of type {@code Value}.\n */\npublic interface Model<Value>\n{\n\t// Accessors\n\n\t/**\n\t * Get the type of this model.\n\t */\n\tModelType getModelType();\n\n\t/**\n\t * Get a list of the action labels attached to choices/transitions.\n\t * This can be a superset of the action labels that are actually used in the model.\n\t * Action labels can be any Object, but will often be treated as a string,\n\t * so should at least have a meaningful toString() method implemented.\n\t * Absence of an action label is denoted by null,\n\t * and null is also included in this list if there are unlabelled choices/transitions.\n\t */\n\tdefault List<Object> getActions()\n\t{\n\t\t// Default implementation: find unique actions used across the model.\n\t\t// This should be cached/optimised if action indices are looked up frequently.\n\t\treturn findActionsUsed();\n\t}\n\n\t/**\n\t * Get a list of the string representations of the action labels attached\n\t * to choices/transitions, i.e., {@link #getActions()} converted to strings.\n\t * This can be a superset of the action labels that are actually used in the model.\n\t * If there are unlabelled choices/transitions, the empty string \"\" is included in this list.\n\t */\n\tdefault List<String> getActionStrings()\n\t{\n\t\t// By default, just convert list from getActions() to strings\n\t\treturn getActions().stream().map(ActionList::actionString).collect(Collectors.toList());\n\t}\n\n\t/**\n\t * Produce a list of the action labels attached to choices/transitions.\n\t * Absence of an action label is denoted by null,\n\t * and null is also included in this list if there are unlabelled choices/transitions.\n\t */\n\tList<Object> findActionsUsed();\n\n\t/**\n\t * Do all choices/transitions have empty (null) action labels?\n\t */\n\tdefault boolean onlyNullActionUsed()\n\t{\n\t\t// Can't assume this is true\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get the index of an action label.\n\t * Indices are into the list given by {@link #getActions()},\n\t * which includes null if there are unlabelled choices,\n\t * so this method should always return a value >= 0 for a valid action.\n\t */\n\tdefault int actionIndex(Object action)\n\t{\n\t\t// Default (inefficient) implementation: just look up in getActions()\n\t\treturn getActions().indexOf(action);\n\t}\n\n\t/**\n\t * Get the number of states.\n\t */\n\tint getNumStates();\n\n\t/**\n\t * Get the number of players.\n\t */\n\tdefault int getNumPlayers()\n\t{\n\t\tModelType modelType = getModelType();\n\t\treturn modelType.nondeterministic() ? (modelType == ModelType.STPG ? 2 : 1) : 0;\n\t}\n\n\t/**\n\t * Get the number of initial states.\n\t */\n\tint getNumInitialStates();\n\n\t/**\n\t * Get the total number of transitions.\n\t */\n\tint getNumTransitions();\n\n\t/**\n\t * Does the number of states exceed {@code Integer.MAX_VALUE}?\n\t */\n\tdefault boolean numStatesExceedsInt()\n\t{\n\t\t// Usually not\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get the number of states, as a string.\n\t */\n\tdefault String getNumStatesString()\n\t{\n\t\treturn Integer.toString(getNumStates());\n\t}\n\n\t/**\n\t * Get the number of initial states, as a string.\n\t */\n\tdefault String getNumInitialStatesString()\n\t{\n\t\treturn Integer.toString(getNumStates());\n\t}\n\n\t/**\n\t * Get the total number of transitions, as a string.\n\t */\n\tdefault String getNumTransitionsString()\n\t{\n\t\treturn Integer.toString(getNumStates());\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ModelGenerator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Nishan Kamaleson <nxk249@bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.Collections;\nimport java.util.List;\n\nimport common.Interval;\nimport parser.State;\nimport parser.ast.Expression;\n\n/**\n * Interface for classes that generate a probabilistic model:\n * given a particular model state (represented as a State object),\n * they provide information about the outgoing transitions from that state.\n * This is a generic class where transition probabilities or rates are of type Value.\n */\npublic interface ModelGenerator<Value> extends ModelInfo\n{\n\t/**\n\t * Get an Evaluator for the values generated by this ModelGenerator for probabilities etc.\n\t * This is needed, for example, to compute probability sums, check for equality to 0/1, etc.\n\t * A default implementation provides an evaluator for the (usual) case when Value is Double.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic default Evaluator<Value> getEvaluator()\n\t{\n\t\treturn (Evaluator<Value>) Evaluator.forDouble();\n\t}\n\t\n\t/**\n\t * Get an Evaluator for intervals of Value (needed for models with interval probabilities)\n\t * A default implementation provides an evaluator for the (usual) case when Value is Double.\n\t */\n\tpublic default Evaluator<Interval<Value>> getIntervalEvaluator() throws PrismException\n\t{\n\t\treturn getEvaluator().createIntervalEvaluator();\n\t\t//return (Evaluator<Interval<Value>>) (Evaluator<? extends Interval<?>>) Evaluator.createForDoubleIntervals();\n\t}\n\n\t/**\n\t * Does the model have a single initial state?\n\t */\n\tpublic default boolean hasSingleInitialState() throws PrismException\n\t{\n\t\t// Default to the case of a single initial state\n\t\treturn true;\n\t}\n\t\n\t/**\n\t * Get the initial states of the model.\n\t * The returned list should contain fresh State objects that can be kept/modified. \n\t */\n\tpublic default List<State> getInitialStates() throws PrismException\n\t{\n\t\t// Default to the case of a single initial state\n\t\treturn Collections.singletonList(getInitialState());\n\t}\n\t\n\t/**\n\t * Get the initial state of the model, if there is just one,\n\t * or the first of the initial states if there are more than one.\n\t * The returned State object should be fresh, i.e. can be kept/modified. \n\t */\n\tpublic State getInitialState() throws PrismException;\n\t\n\t/**\n\t * Explore a given state of the model. After a call to this method,\n\t * the class should be able to respond to the various methods that are\n\t * available to query the outgoing transitions from the current state.\n\t * @param exploreState State to explore (generate transition information for)\n\t */\n\tpublic void exploreState(State exploreState) throws PrismException;\n\n\t/**\n\t * Get the number of nondeterministic choices in the current state.\n\t */\n\tpublic int getNumChoices() throws PrismException;\n\n\t/**\n\t * Get the total number of transitions in the current state.\n\t */\n\tpublic default int getNumTransitions() throws PrismException\n\t{\n\t\t// Default implementation just extracts from getNumChoices() and getNumTransitions(i) \n\t\tint tot = 0;\n\t\tint n = getNumChoices();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\ttot += getNumTransitions(i);\n\t\t}\n\t\treturn tot;\n\t}\n\n\t/**\n\t * Get the number of transitions in the {@code i}th nondeterministic choice.\n\t * @param i Index of the nondeterministic choice\n\t */\n\tpublic int getNumTransitions(int i) throws PrismException;\n\n\t/**\n\t * Get the index of the choice containing a transition of a given index.\n\t * @param index Index of the transition amongst all transitions\n\t */\n\tpublic default int getChoiceIndexOfTransition(int index) throws PrismException\n\t{\n\t\t// Default implementation just extracts from getNumChoices() and getNumTransitions(i) \n\t\tint tot = 0;\n\t\tint n = getNumChoices();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\ttot += getNumTransitions(i);\n\t\t\tif (index < tot) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\t// Won't happen if index is valid:\n\t\treturn -1;\n\t}\n\t\n\t/**\n\t * Get the offset of a transition within its containing choice.\n\t * @param index Index of the transition amongst all transitions\n\t */\n\tpublic default int getChoiceOffsetOfTransition(int index) throws PrismException\n\t{\n\t\t// Default implementation just extracts from getNumChoices() and getNumTransitions(i) \n\t\tint tot = 0;\n\t\tint n = getNumChoices();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\ttot += getNumTransitions(i);\n\t\t\tif (index < tot) {\n\t\t\t\treturn index - (tot - getNumTransitions(i));\n\t\t\t}\n\t\t}\n\t\t// Won't happen if index is valid:\n\t\treturn -1;\n\t}\n\t\n\t/**\n\t * Get the (total) index of a transition from the index of its containing choice and its offset within it.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic default int getTotalIndexOfTransition(int i, int offset) throws PrismException\n\t{\n\t\t// Default implementation just extracts from getNumChoices() and getNumTransitions(i) \n\t\tint tot = 0;\n\t\tfor (int j = 0; j < i; j++) {\n\t\t\ttot += getNumTransitions(j);\n\t\t}\n\t\treturn tot + offset;\n\t}\n\t\n\t/**\n\t * Is there a deadlock (i.e. no available transitions)?\n\t */\n\tpublic default boolean isDeadlock() throws PrismException\n\t{\n\t\treturn getNumChoices() == 0;\n\t}\n\n\t/**\n\t * Get the action label of a transition within a choice, specified by its index/offset.\n\t * The label can be any Object, but will often be treated as a string, so it should at least\n\t * have a meaningful toString() method implemented. Absence of an action label is denoted by null.\n\t * Note: For most types of models, the action label will be the same for all transitions within\n\t * the same nondeterministic choice (i.e. for each different value of {@code offset}),\n\t * but for Markov chains this may not necessarily be the case.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic Object getTransitionAction(int i, int offset) throws PrismException;\n\n\t/**\n\t * Get a string representation of the action label of a transition within a choice, specified by its index/offset.\n\t * The string is \"\" for an unlabelled choice.\n\t * Note: For most types of models, the action label will be the same for all transitions within\n\t * the same nondeterministic choice (i.e. for each different value of {@code offset}),\n\t * but for Markov chains this may not necessarily be the case.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic default String getTransitionActionString(int i, int offset) throws PrismException\n\t{\n\t\treturn ActionList.actionString(getTransitionAction(i, offset));\n\t}\n\n\t/**\n\t * Get a description for the action label of a choice, specified by its index/offset.\n\t * This might be displayed in a representation of a path, e.g. in the simulator UI.\n\t * By default this, will be {@code toString()} for {@link #getTransitionAction(int, int)},\n\t * but can be customised, e.g. a PRISM model shows \"[a]\" for a synchronous action a\n\t * and \"M\" for an unlabelled action belonging to a module M.\n\t * For unlabelled transitions, this should return \"\", not null. \n\t * Note: For most types of models, the action label will be the same for all transitions within\n\t * the same nondeterministic choice (i.e. for each different value of {@code offset}),\n\t * but for Markov chains this may not necessarily be the case.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic default String getTransitionActionDescription(int i, int offset) throws PrismException\n\t{\n\t\t// Default implementation: use getTransitionActionString\n\t\treturn getTransitionActionString(i, offset);\n\t}\n\n\t/**\n\t * Get the action label of a choice, specified by its index.\n\t * The label can be any Object, but will often be treated as a string, so it should at least\n\t * have a meaningful toString() method implemented. Absence of an action label is denoted by null.\n\t * Note: If the model has different actions for different transitions within a choice\n\t * (as can be the case for Markov chains), this method returns the action for the first transition.\n\t * So, this method is essentially equivalent to {@code getTransitionAction(i, 0)}. \n\t * @param i Index of the nondeterministic choice\n\t */\n\tpublic default Object getChoiceAction(int i) throws PrismException\n\t{\n\t\t// Default implementation \n\t\treturn getTransitionAction(i, 0);\n\t}\n\n\t/**\n\t * Get a string representation of the action label of a choice within a choice, specified by its index.\n\t * The string is \"\" for an unlabelled choice.\n\t * Note: If the model has different actions for different transitions within a choice\n\t * (as can be the case for Markov chains), this method returns the action for the first transition.\n\t * So, this method is essentially equivalent to {@code getTransitionActionString(i, 0)}.\n\t * @param i Index of the nondeterministic choice\n\t */\n\tpublic default String getChoiceActionString(int i) throws PrismException\n\t{\n\t\treturn ActionList.actionString(getChoiceAction(i));\n\t}\n\n\t/**\n\t * Get a description for the action label of a choice, specified by its index.\n\t * This might be displayed in a representation of a path, e.g. in the simulator UI.\n\t * By default this, will be {@code toString()} for {@link #getChoiceAction(int)},\n\t * but can be customised, e.g. a PRISM model shows \"[a]\" for a synchronous action a\n\t * and \"M\" for an unlabelled action belonging to a module M. \n\t * For unlabelled choices, this should return \"\", not null. \n\t * Note: If the model has different actions for different transitions within a choice\n\t * (as can be the case for Markov chains), this method returns the action for the first transition.\n\t * So, this method is essentially equivalent to {@code getTransitionActionDescription(i, 0)}.\n\t * @param i Index of the nondeterministic choice\n\t */\n\tpublic default String getChoiceActionDescription(int i) throws PrismException\n\t{\n\t\t// Default implementation: use getChoiceActionString\n\t\treturn getChoiceActionString(i);\n\t}\n\n\t/**\n\t * Get the index of the (first) choice with a given action label.\n\t * Returns -1 if none exists.\n\t */\n\tpublic default int getChoiceIndexByAction(Object action) throws PrismException\n\t{\n\t\t// Default implementation just searches via getChoiceAction(i)\n\t\tint n = getNumChoices();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tObject a = getChoiceAction(i);\n\t\t\tif (a == null) {\n\t\t\t\tif (action == null) {\n\t\t\t\t\treturn i;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (a.equals(action)) {\n\t\t\t\t\treturn i;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\t\n\t/**\n\t * For real-time models, get the clock guard of a choice,\n\t * i.e., an expression over clock variables denoting when it can be taken.\n\t * If there is no guard, this returns null;\n\t * @param i Index of the nondeterministic choice\n\t */\n\tpublic default Expression getChoiceClockGuard(int i) throws PrismException\n\t{\n\t\t// Absent by default\n\t\treturn null;\n\t}\n\t\n\t/**\n\t * Get the probability/rate of a transition within a choice, specified by its index/offset.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic Value getTransitionProbability(int i, int offset) throws PrismException;\n\n\t/**\n\t * Get the sum of probabilities/rates of transitions within a choice, specified by its index.\n\t * @param i Index of the nondeterministic choice\n\t */\n\tpublic default Value getChoiceProbabilitySum(int i) throws PrismException\n\t{\n\t\tEvaluator<Value> eval = getEvaluator();\n\t\tint numTransitions = getNumTransitions(i);\n\t\tValue probSum = eval.zero();\n\t\tfor (int offset = 0; offset < numTransitions; offset++) {\n\t\t\tprobSum = eval.add(probSum, getTransitionProbability(i, offset));\n\t\t}\n\t\treturn probSum;\n\t}\n\n\t/**\n\t * Get the sum of all probabilities/rates of transitions across choices.\n\t */\n\tpublic default Value getProbabilitySum() throws PrismException\n\t{\n\t\tEvaluator<Value> eval = getEvaluator();\n\t\tint numChoices = getNumChoices();\n\t\tValue probSum = eval.zero();\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tprobSum = eval.add(probSum, getChoiceProbabilitySum(i));\n\t\t}\n\t\treturn probSum;\n\t}\n\t\n\t/**\n\t * Get the interval of probability/rates for a transition within a choice,\n\t * specified by its index/offset, for an interval model.\n\t * Returns null for non-interval models.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic default Interval<Value> getTransitionProbabilityInterval(int i, int offset) throws PrismException\n\t{\n\t\t// Not supported by default (but must be for interval models)\n\t\treturn null;\n\t}\n\n\t/**\n\t * Get the probability/rate of a transition within a choice, specified by its index/offset,\n\t * as an Object (which may be either a {@code Value} or an {@code Interval<Value>}, depending on the model type.\n\t * This method works regardless of whether transition probabilities are intervals.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic default Object getTransitionProbabilityObject(int i, int offset) throws PrismException\n\t{\n\t\tif (!getModelType().uncertain()) {\n\t\t\treturn getTransitionProbability(i, offset);\n\t\t} else {\n\t\t\treturn getTransitionProbabilityInterval(i, offset);\n\t\t}\n\t}\n\n\t/**\n\t * Get a string for the probability/rate of a transition within a choice, specified by its index/offset.\n\t * This method works regardless of whether transition probabilities are intervals.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic default String getTransitionProbabilityString(int i, int offset) throws PrismException\n\t{\n\t\tif (!getModelType().uncertain()) {\n\t\t\treturn getTransitionProbability(i, offset).toString();\n\t\t} else {\n\t\t\treturn getTransitionProbabilityInterval(i, offset).toString();\n\t\t}\n\t}\n\n\t/**\n\t * Are the choices deterministic? (i.e. a single probability 1.0 transition)\n\t * (will also return true for a continuous-time model matching this\n\t * definition, since TransitionList does not know about model type)\n\t */\n\tpublic default boolean isDeterministic() throws PrismException\n\t{\n\t\tif (getNumChoices() == 1 && getNumTransitions(0) == 1) {\n\t\t\tif (!getModelType().uncertain()) {\n\t\t\t\treturn getEvaluator().isOne(getTransitionProbability(0, 0));\n\t\t\t} else {\n\t\t\t\treturn getIntervalEvaluator().isOne(getTransitionProbabilityInterval(0, 0));\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get a string describing the update comprising a transition, specified by its index/offset.\n\t * The default implementation is of the form \"x'=1, y'=0\",\n\t * including all variables in the state. An implementation might choose,\n\t * for example, to only include variables that are actually updated. \n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic default String getTransitionUpdateString(int i, int offset) throws PrismException\n\t{\n\t\t// By default, just build a string showing new values of all\n\t\t// variables, regardless of whether they changed or not \n\t\tState nextState = computeTransitionTarget(i, offset);\n\t\tString update = \"\";\n\t\tint numVars = getNumVars();\n\t\tfor (int j = 0; j < numVars; j++) {\n\t\t\tupdate += ((j > 0) ? \", \" : \"\") + getVarName(j) + \"'=\" + nextState.varValues[j]; \n\t\t}\n\t\treturn update;\n\t}\n\n\t/**\n\t * Optionally, a more verbose version of {@link #getTransitionUpdateString(int, int)}.\n\t * The default implementation just returns the same string.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic default String getTransitionUpdateStringFull(int i, int offset) throws PrismException\n\t{\n\t\treturn getTransitionUpdateString(i, offset);\n\t}\n\n\t/**\n\t * Get the target (as a new State object) of a transition within a choice, specified by its index/offset.\n\t * @param i Index of the nondeterministic choice\n\t * @param offset Index of the transition within the choice\n\t */\n\tpublic State computeTransitionTarget(int i, int offset) throws PrismException;\n\t\n\t/**\n\t * Is label {@code label} true in the state currently being explored?\n\t * @param label The name of the label to check \n\t */\n\tpublic default boolean isLabelTrue(String label) throws PrismException\n\t{\n\t\t// Default implementation: Look up label and then check by index\n\t\tint i = getLabelIndex(label);\n\t\tif (i == -1) {\n\t\t\tthrow new PrismException(\"Label \\\"\" + label + \"\\\" not defined\");\n\t\t} else {\n\t\t\treturn isLabelTrue(i);\n\t\t}\n\t}\n\t\n\t/**\n\t * For real-time models, get the clock invariant for the current state,\n\t * i.e., an expression over clock variables which must remain true.\n\t * If there is no invariant, this returns null;\n\t */\n\tpublic default Expression getClockInvariant() throws PrismException\n\t{\n\t\t// Absent by default\n\t\treturn null;\n\t}\n\t\n\t/**\n\t * Is the {@code i}th label of the model true in the state currently being explored?\n\t * @param i The index of the label to check \n\t */\n\tpublic default boolean isLabelTrue(int i) throws PrismException\n\t{\n\t\t// No labels by default\n\t\tthrow new PrismException(\"Label number \\\"\" + i + \"\\\" not defined\");\n\t}\n\t\n\t/**\n\t * Get the observation when entering state {@code state}.\n\t * This is represented as a {@link parser.State} object, with one value per observable.\n\t * For models that are not partially observable, null can be returned.\n\t * (for partially observable models only)\n\t * @param state The state\n\t */\n\tpublic default State getObservation(State state) throws PrismException\n\t{\n\t\tif (!getModelType().partiallyObservable()) {\n\t\t\treturn null;\n\t\t}\n\t\t// Undefined by default\n\t\tthrow new PrismException(\"Observation not defined\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ModelInfo.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Nishan Kamaleson <nxk249@bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.List;\nimport java.util.stream.Collectors;\n\nimport parser.EvaluateContext;\nimport parser.EvaluateContext.EvalMode;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.ASTElement;\nimport parser.ast.DeclarationType;\nimport parser.type.Type;\n\n/**\n * Interface for classes that provide some basic (syntactic) information about a probabilistic model.\n */\npublic interface ModelInfo\n{\n\t/**\n\t * Get the type of probabilistic model.\n\t */\n\tpublic ModelType getModelType();\n\n\t/**\n\t * Set values for some undefined constants.\n\t * The values being provided for these constants, as well as any other constants needed,\n\t * are provided in an EvaluateContext object. This also determines the evaluation mode.\n\t * If there are no undefined constants, {@code ecUndefined} can be null.\n\t * Undefined constants can be subsequently redefined to different values with the same method.\n\t * This may result in the values for other model constants now being known;\n\t * the values for all current constant values (if set) are available via {@link #getConstantValues()}.\n\t */\n\tpublic default void setSomeUndefinedConstants(EvaluateContext ecUndefined) throws PrismException\n\t{\n\t\t// Default implementation: assume no constants and do nothing.\n\t\t// So if constants are actually being provided, this is a problem.\n\t\tif (ecUndefined != null && ecUndefined.getConstantValues() != null && ecUndefined.getConstantValues().getNumValues() > 0) {\n\t\t\tthrow new PrismLangException(\"This model has no constants to set\");\n\t\t}\n\t\t// Also assume no support for exact evaluation by default\n\t\tif (ecUndefined != null && ecUndefined.getEvaluationMode() != EvalMode.FP) {\n\t\t\tthrow new PrismLangException(\"Evaluation mode \" + ecUndefined.getEvaluationMode() + \" not supported\");\n\t\t}\n\t}\n\n\t/**\n\t * Set values for some undefined constants.\n\t * It is preferable to use {@link #setSomeUndefinedConstants(EvaluateContext)} instead.\n\t * By default, this method creates an {@link EvaluateContext} via {@link EvaluateContext#create(Values)}.\n\t * If this will be called frequently, it is better to maintain your own {@link EvaluateContext}.\n\t * Also, this method can only handle the default (floating point) evaluation mode.\n\t */\n\tpublic default void setSomeUndefinedConstants(Values someValues) throws PrismException\n\t{\n\t\tsetSomeUndefinedConstants(EvaluateContext.create(someValues));\n\t}\n\n\t/**\n\t * Set values for some undefined constants.\n\t * Deprecated. Better to use {@link #setSomeUndefinedConstants(EvaluateContext)}.\n\t * @deprecated\n\t */\n\t@Deprecated\n\tpublic default void setSomeUndefinedConstants(Values someValues, boolean exact) throws PrismException\n\t{\n\t\tsetSomeUndefinedConstants(EvaluateContext.create(someValues, exact));\n\t}\n\n\t/**\n\t * Get access to the values for all constants in the model, including the \n\t * undefined constants set previously via the method {@link #setSomeUndefinedConstants(EvaluateContext)}.\n\t * Until they are set for the first time, this method may return null.\n\t */\n\tpublic default Values getConstantValues()\n\t{\n\t\t// Default, get via getEvaluateContext()\n\t\treturn getEvaluateContext().getConstantValues();\n\t}\n\n\t/**\n\t * Get access to an EvaluateContext object defining the values\n\t * for all constants in the model, including the undefined constants\n\t * set previously via the method {@link #setSomeUndefinedConstants(EvaluateContext)}.\n\t * This also specified the evaluation mode being used.\n\t */\n\tpublic default EvaluateContext getEvaluateContext()\n\t{\n\t\t// By default, assume there are no constants to define (and FP)\n\t\treturn EvaluateContext.create(new Values());\n\t}\n\n\t/**\n\t * Get a list of the action labels attached to choices/transitions.\n\t * This can be a superset of the action labels that are actually used in the model.\n\t * Action labels can be any Object, but will often be treated as a string,\n\t * so should at least have a meaningful toString() method implemented.\n\t * Absence of an action label is denoted by null,\n\t * and null is also included in this list if there are unlabelled choices/transitions.\n\t * <br><br>\n\t * This is optional - the default implementation just returns null,\n\t * which means that this info is not being provided by this class.\n\t * But it can help for more efficient mapping of actions to indices.\n\t */\n\tpublic default List<Object> getActions()\n\t{\n\t\t// Default implementation just says that info is unavailable\n\t\treturn null;\n\t}\n\n\t/**\n\t * Get a list of the string representations of the action labels attached\n\t * to choices/transitions, i.e., {@link #getActions()} converted to strings.\n\t * This can be a superset of the action labels that are actually used in the model.\n\t * If there are unlabelled choices/transitions, the empty string \"\" is included in this list.\n\t * <br><br>\n\t * This is optional - the default implementation just returns null,\n\t * which means that this info is not being provided by this class.\n\t */\n\tpublic default List<String> getActionStrings()\n\t{\n\t\treturn getActions() == null ? null : getActions().stream()\n\t\t\t\t.map(ActionList::actionString)\n\t\t\t\t.collect(Collectors.toList());\n\t}\n\n\t/**\n\t * Get a list of the string representations of the action labels attached\n\t * to choices/transitions, like {@link #getActionStrings()}), but with\n\t * actions formatted as [a], for easier display of empty (\"\") actions.\n\t * <br><br>\n\t * This is optional - the default implementation just returns null,\n\t * which means that this info is not being provided by this class.\n\t */\n\tpublic default List<String> getBracketedActionStrings()\n\t{\n\t\treturn getActions() == null ? null : getActions().stream()\n\t\t\t\t.map(a -> \"[\" + ActionList.actionString(a) + \"]\")\n\t\t\t\t.collect(Collectors.toList());\n\t}\n\n\t/**\n\t * Does the model contain unbounded variables?\n\t */\n\tpublic default boolean containsUnboundedVariables()\n\t{\n\t\t// By default, assume all variables are finite-ranging\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get the number of variables in the model. \n\t */\n\tpublic default int getNumVars()\n\t{\n\t\t// Default implementation just extracts from getVarNames() \n\t\treturn getVarNames().size();\n\t}\n\t\n\t/**\n\t * Get the names of all the variables in the model.\n\t */\n\tpublic List<String> getVarNames();\n\t\n\t/**\n\t * Look up the index of a variable in the model by name.\n\t * Returns -1 if there is no such variable.\n\t */\n\tpublic default int getVarIndex(String name)\n\t{\n\t\t// Default implementation just extracts from getVarNames() \n\t\treturn getVarNames().indexOf(name);\n\t}\n\n\t/**\n\t * Get the name of the {@code i}th variable in the model.\n\t * {@code i} should always be between 0 and getNumVars() - 1. \n\t */\n\tpublic default String getVarName(int i)\n\t{\n\t\t// Default implementation just extracts from getVarNames() \n\t\treturn getVarNames().get(i);\n\t}\n\n\t/**\n\t * Get the types of all the variables in the model.\n\t */\n\tpublic List<Type> getVarTypes();\n\n\t/**\n\t * Get the type of the {@code i}th variable in the model.\n\t * {@code i} should always be between 0 and getNumVars() - 1. \n\t */\n\tpublic default Type getVarType(int i) throws PrismException\n\t{\n\t\t// Default implementation just extracts from getVarTypes() \n\t\treturn getVarTypes().get(i);\n\t}\n\n\t/**\n\t * Get a declaration providing more information about\n\t * the type of the {@code i}th variable in the model.\n\t * For example, for integer variables, this can define\n\t * the lower and upper bounds of the range of the variable.\n\t * This is specified using a subclass of {@link DeclarationType},\n\t * which specifies info such as bounds using {@link parser.ast.Expression} objects.\n\t * These can use constants which will later be supplied,\n\t * e.g., via the {@link #setSomeUndefinedConstants(Values)} method.\n\t * If this method is not provided, a default implementation supplies sensible\n\t * declarations, but these are _unbounded_ for integers.\n\t * {@code i} should always be between 0 and getNumVars() - 1.\n\t */\n\tpublic default DeclarationType getVarDeclarationType(int i) throws PrismException\n\t{\n\t\ttry {\n\t\t\treturn getVarType(i).defaultDeclarationType();\n\t\t} catch (PrismLangException e) {\n\t\t\tthrow new PrismException(\"No default declaration available for type \" + getVarType(i));\n\t\t}\n\t}\n\t\n\t/**\n\t * Get the (optionally specified) \"module\" that the {@code i}th variable in\n\t * the model belongs to (e.g., the PRISM language divides models into such modules).\n\t * This method returns the index of module; use {@link #getModuleName(int)}\n\t * to obtain the name of the corresponding module.\n\t * If there is no module info, or the variable is \"global\" and does not belong\n\t * to a specific model, this returns -1. A default implementation always returns -1.\n\t * {@code i} should always be between 0 and getNumVars() - 1.\n\t */\n\tpublic default int getVarModuleIndex(int i)\n\t{\n\t\t// Default is -1 (unspecified or \"global\")\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Get the name of the {@code i}th \"module\"; these are optionally used to\n\t * organise variables within the model, e.g., in the PRISM modelling language.\n\t * The module containing a variable is available via {@link #getVarModuleIndex(int)}.\n\t * This method should return a valid module name for any (non -1)\n\t * value returned by {@link #getVarModuleIndex(int)}.\n\t */\n\tpublic default String getModuleName(int i)\n\t{\n\t\t// No names needed by default\n\t\treturn null;\n\t}\n\n\t/**\n\t * Create a {@link VarList} object, collating information about all the variables\n\t * in the model. This provides various helper functions to work with variables.\n\t * This list is created once all undefined constant values have been provided.\n\t * A default implementation of this method creates a {@link VarList} object\n\t * automatically from the variable info supplied by {@link ModelInfo}.\n\t * Generally, this requires {@link #getVarDeclarationType(int)} to\n\t * be properly implemented (beyond the default implementation) so that\n\t * variable ranges can be determined.\n\t */\n\tpublic default VarList createVarList() throws PrismException\n\t{\n\t\treturn new VarList(this); \n\t}\n\t\n\t/**\n\t * Is the {@code i}th variable declared as observable?\n\t * (for partially observable models)\n\t * Technically, the only info needed to verify partially observable\n\t * models is {@link #getObservableNames()} and {@link #getObservableTypes()}\n\t * but in practice this is needed too to construct belief states efficiently.\n\t */\n\tpublic default boolean isVarObservable(int i)\n\t{\n\t\t// Assume false (inefficient but safe)\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Get the number of variables declared as observable\n\t * (for partially observable models)\n\t * (derived from {@link #isVarObservable(int)} by default)\n\t */\n\tpublic default int getNumObservableVars()\n\t{\n\t\tint count = 0;\n\t\tint numVars = getNumVars();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tif (isVarObservable(i)) {\n\t\t\t\tcount++;\n\t\t\t}\n\t\t}\n\t\treturn count;\n\t}\n\t\n\t/**\n\t * Get the number of variables _not_ declared as observable\n\t * (for partially observable models)\n\t * (derived from {@link #isVarObservable(int)} by default)\n\t */\n\tpublic default int getNumUnobservableVars()\n\t{\n\t\treturn getNumVars() - getNumObservableVars();\n\t}\n\t\n\t/**\n\t * Get the names of the variables declared as observable\n\t * (for partially observable models)\n\t * (derived from {@link #isVarObservable(int)} by default)\n\t */\n\tpublic default List<String> getObservableVars()\n\t{\n\t\tList<String> list = new ArrayList<>();\n\t\tint numVars = getNumVars();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tif (isVarObservable(i)) {\n\t\t\t\tlist.add(getVarName(i));\n\t\t\t}\n\t\t}\n\t\treturn list;\n\t}\n\t\n\t/**\n\t * Get the names of the variables _not_ declared as observable\n\t * (for partially observable models)\n\t * (derived from {@link #isVarObservable(int)} by default)\n\t */\n\tpublic default List<String> getUnobservableVars()\n\t{\n\t\tList<String> list = new ArrayList<>();\n\t\tint numVars = getNumVars();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tif (!isVarObservable(i)) {\n\t\t\t\tlist.add(getVarName(i));\n\t\t\t}\n\t\t}\n\t\treturn list;\n\t}\n\t\n\t/**\n\t * Get a short description of the action strings associated with transitions/choices.\n\t * For example, for a PRISM model, this is \"Module/[action]\".\n\t * The default implementation just returns \"Action\".\n  \t */\n\tpublic default String getActionStringDescription()\n\t{\n\t\treturn \"Action\";\n\t}\n\t\n\t/**\n\t * Get the number of labels (atomic propositions) defined for the model. \n\t */\n\tpublic default int getNumLabels()\n\t{\n\t\t// Default implementation just extracts from getLabelNames() \n\t\treturn getLabelNames().size();\n\t}\n\t\n\t/**\n\t * Get the names of all the labels in the model.\n\t */\n\tpublic default List<String> getLabelNames()\n\t{\n\t\t// No labels by default\n\t\treturn Collections.emptyList();\n\t}\n\t\n\t/**\n\t * Get the name of the {@code i}th label of the model.\n\t * {@code i} should always be between 0 and getNumLabels() - 1. \n\t */\n\tpublic default String getLabelName(int i) throws PrismException\n\t{\n\t\t// Default implementation just extracts from getLabelNames() \n\t\ttry {\n\t\t\treturn getLabelNames().get(i);\n\t\t} catch (IndexOutOfBoundsException e) {\n\t\t\tthrow new PrismException(\"Label number \" + i + \" not defined\");\n\t\t}\n\t}\n\t\n\t/**\n\t * Get the index of the label with name {@code name}.\n\t * Indexed from 0. Returns -1 if label of that name does not exist.\n\t */\n\tpublic default int getLabelIndex(String name)\n\t{\n\t\t// Default implementation just extracts from getLabelNames() \n\t\treturn getLabelNames().indexOf(name);\n\t}\n\t\n\t/**\n\t * Get the number of observables defined for the model\n\t * (for partially observable models only)\n\t */\n\tpublic default int getNumObservables()\n\t{\n\t\t// Default implementation just extracts from getObservableNames()\n\t\treturn getObservableNames().size();\n\t}\n\t\n\t/**\n\t * Get the names of all the observables in the model\n\t * (for partially observable models only)\n\t */\n\tpublic default List<String> getObservableNames()\n\t{\n\t\t// No observables by default\n\t\treturn Collections.emptyList();\n\t}\n\t\n\t/**\n\t * Get the name of the {@code i}th observable of the model\n\t * (for partially observable models only)\n\t * {@code i} should always be between 0 and getNumObservables() - 1.\n\t */\n\tpublic default String getObservableName(int i) throws PrismException\n\t{\n\t\t// Default implementation just extracts from getObservableNames()\n\t\ttry {\n\t\t\treturn getObservableNames().get(i);\n\t\t} catch (IndexOutOfBoundsException e) {\n\t\t\tthrow new PrismException(\"Observable number \" + i + \" not defined\");\n\t\t}\n\t}\n\t\n\t/**\n\t * Get the index of the observable with name {@code name}\n\t * (for partially observable models only)\n\t * Indexed from 0. Returns -1 if observable of that name does not exist.\n\t */\n\tpublic default int getObservableIndex(String name)\n\t{\n\t\t// Default implementation just extracts from getObservableNames()\n\t\treturn getObservableNames().indexOf(name);\n\t}\n\t\n\t/**\n\t * Get the types of all the observables in the model.\n\t * (for partially observable models only)\n\t */\n\tpublic default List<Type> getObservableTypes()\n\t{\n\t\t// No observables by default\n\t\treturn Collections.emptyList();\n\t}\n\n\t/**\n\t * Get the type of the {@code i}th observable in the model.\n\t * (for partially observable models only)\n\t * {@code i} should always be between 0 and getNumObservables() - 1.\n\t */\n\tpublic default Type getObservableType(int i)\n\t{\n\t\t// Default implementation just extracts from getObservableTypes()\n\t\treturn getObservableTypes().get(i);\n\t}\n\t\n\t/**\n\t * Check if an identifier is used in the model\n\t * (e.g., as a constant or variable)\n\t */\n\tpublic default boolean isIdentUsed(String ident)\n\t{\n\t\t// Default implementation looks up any vars/consts\n\t\tif (getVarIndex(ident) != -1) {\n\t\t\treturn true;\n\t\t}\n\t\tValues v = getConstantValues();\n\t\tif (v != null & v.contains(ident)) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Check if an identifier is already used in the model\n\t * (e.g., as a constant or variable) and throw an exception if it is.\n\t * @param ident The name of the identifier to check\n\t * @param decl Where the identifier is declared in the model (for the error message)\n\t * @param use Optionally, the identifier's usage (e.g. \"constant\")\n\t */\n\tpublic default void checkIdent(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\t// Default implementation via isIdentUsed\n\t\tif (isIdentUsed(ident)) {\n\t\t\tthrow new PrismLangException(\"Identifier \" + ident + \" is already used in the model\", decl);\n\t\t}\n\t}\n\t\n\t/**\n\t * Check if an identifier (in double quotes) is used in the model\n\t * (e.g., as a label)\n\t */\n\tpublic default boolean isQuotedIdentUsed(String ident)\n\t{\n\t\t// Default implementation looks up any labels\n\t\tif (getLabelIndex(ident) != -1) {\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Check if an identifier (in double quotes) is already used in the model\n\t * (e.g., as a label) and throw an exception if it is.\n\t * @param ident The name of the identifier to check\n\t * @param decl Where the identifier is declared in the model (for the error message)\n\t * @param use Optionally, the identifier's usage (e.g. \"constant\")\n\t */\n\tpublic default void checkQuotedIdent(String ident, ASTElement decl, String use) throws PrismLangException\n\t{\n\t\t// Default implementation via isQuotedIdentUsed\n\t\tif (isQuotedIdentUsed(ident)) {\n\t\t\tthrow new PrismLangException(\"Identifier \\\"\" + ident + \"\\\" is already used in the model\", decl);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ModelType.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\npublic enum ModelType\n{\n\t// List of model types (ordered alphabetically)\n\tCTMC(\"continuous-time Markov chain\") {\n\t\t@Override\n\t\tpublic boolean choicesSumToOne()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean continuousTime()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean nondeterministic()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic String probabilityOrRate()\n\t\t{\n\t\t\treturn RATE;\n\t\t}\n\t},\n\tCTMDP(\"continuous-time Markov decision process\") {\n\t\t@Override\n\t\tpublic boolean choicesSumToOne()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean continuousTime()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic String probabilityOrRate()\n\t\t{\n\t\t\treturn RATE;\n\t\t}\n\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn CTMC;\n\t\t}\n\t},\n\tDTMC(\"discrete-time Markov chain\") {\n\t\t@Override\n\t\tpublic boolean nondeterministic()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\t},\n\tLTS(\"labelled transition system\") {\n\t\t@Override\n\t\tpublic boolean isProbabilistic()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic String probabilityOrRate()\n\t\t{\n\t\t\treturn NEITHER;\n\t\t}\n\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\t},\n\tMDP(\"Markov decision process\") {\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\t},\n\tPOMDP(\"partially observable Markov decision process\") {\n\t\t@Override\n\t\tpublic boolean partiallyObservable()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\t},\n\tPOPTA(\"partially observable probabilistic timed automaton\") {\n\t\t@Override\n\t\tpublic boolean continuousTime()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean realTime()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean partiallyObservable()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\t},\n\tPTA(\"probabilistic timed automaton\") {\n\t\t@Override\n\t\tpublic boolean continuousTime()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t@Override\n\t\tpublic boolean realTime()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t},\n\tSTPG(\"stochastic two-player game\") {\n\t\t@Override\n\t\tpublic boolean multiplePlayers()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\t},\n\tSMG(\"stochastic multi-player game\") {\n\t\t@Override\n\t\tpublic boolean multiplePlayers()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\t},\n\tIDTMC(\"interval discrete-time Markov chain\") {\n\t\t@Override\n\t\tpublic boolean nondeterministic()\n\t\t{\n\t\t\t// NB: we distinguish between nondeterminism and uncertainty\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean uncertain()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean intervals()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t},\n\tUDTMC(\"uncertain discrete-time Markov chain\") {\n\t\t@Override\n\t\tpublic boolean nondeterministic()\n\t\t{\n\t\t\t// NB: we distinguish between nondeterminism and uncertainty\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean uncertain()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t},\n\tIMDP(\"interval Markov decision process\") {\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean uncertain()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean intervals()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t},\n\tUMDP(\"uncertain Markov decision process\") {\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean uncertain()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t},\n\tIPOMDP(\"interval partially observable Markov decision process\") {\n\t\t@Override\n\t\tpublic boolean partiallyObservable()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean uncertain()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean intervals()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t},\n\tUPOMDP(\"uncertain partially observable Markov decision process\") {\n\t\t@Override\n\t\tpublic boolean partiallyObservable()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic ModelType removeNondeterminism()\n\t\t{\n\t\t\treturn DTMC;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean uncertain()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t};\n\n\tprivate static final String PROBABILITY = \"Probability\";\n\tprivate static final String RATE = \"Rate\";\n\tprivate static final String NEITHER = \"\";\n\n\tprivate final String fullName;\n\n\tModelType(final String fullName) {\n\t\tthis.fullName = fullName;\n\t}\n\n\t/**\n\t * Get the full name, in words, of the this model type.\n\t */\n\tpublic String fullName()\n\t{\n\t\treturn fullName;\n\t}\n\n\t/**\n\t * Get the PRISM keyword for this model type.\n\t */\n\tpublic String keyword()\n\t{\n\t\treturn this.name().toLowerCase();\n\t}\n\n\t/**\n\t * Do the transitions in a choice sum to 1 for this model type?\n\t * Can also use this to test whether models uses rates or probabilities.\n\t */\n\tpublic boolean choicesSumToOne()\n\t{\n\t\treturn true;\n\t}\n\n\t/**\n\t * Are time delays continuous for this model type?\n\t */\n\tpublic boolean continuousTime()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Is this a \"real time\" (timed automata like) model type?\n\t */\n\tpublic boolean realTime()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Does this model allow nondeterministic choices?\n\t */\n\tpublic boolean nondeterministic()\n\t{\n\t\treturn true;\n\t}\n\n\t/**\n\t * Does this model have more than 1 player?\n\t */\n\tpublic boolean multiplePlayers()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Is this model probabilistic?\n\t */\n\tpublic boolean isProbabilistic()\n\t{\n\t\treturn true;\n\t}\n\n\t/**\n\t * Does this model have probabilities or rates?\n\t * Returns \"Probability\" or \"Rate\", accordingly (or \"\" if there are neither)\n\t */\n\tpublic String probabilityOrRate()\n\t{\n\t\treturn PROBABILITY;\n\t}\n\n\t/**\n\t * Does the model feature partial observability? \n\t */\n\tpublic boolean partiallyObservable()\n\t{\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Does this model have uncertainty (e.g., intervals)?\n\t */\n\tpublic boolean uncertain()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Does this model define probabilities using intervals?\n\t */\n\tpublic boolean intervals()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Return the model type that results from removing the nondeterminism\n\t * in this model type.\n\t * <br>\n\t * If there is no nondeterminism (or the removal of nondeterminism is not supported),\n\t * returns the same model type.\n\t */\n\tpublic ModelType removeNondeterminism()\n\t{\n\t\t// default: same model type\n\t\treturn this;\n\t}\n\n\tpublic static ModelType parseName(String name)\n\t{\n\t\ttry {\n\t\t\treturn valueOf(name.toUpperCase());\n\t\t} catch (IllegalArgumentException e) {\n\t\t\treturn null;\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/prism/MultiObjUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.File;\nimport java.io.FileWriter;\nimport java.io.IOException;\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.Collections;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.Map;\n\n/**\n * This class contains auxiliary static methods used in multi-objective verification.\n */\npublic class MultiObjUtils\n{\n\t/**\n\t * Returns a point that represents a hyperplane that separates {@code point}\n\t * from {@code computedPoints}. An LP solver is used to get the hyperplane, but it\n\t * is expected that the number of points  in {@code computedPoints} is relatively small\n\t * and so this approach should be efficient\n\t * \n\t * @param point A point which should be at one direction from the separating hyperplane.\n\t * @param computedPoints Set of points which should be at the other direction from the separating hyperplane.\n\t * @return A vector orthogonal to the computed separating hyperplane.\n\t * @throws PrismException When the LP solver throws an exception or returns an unexpected result, an exception with a related message is thrown.\n\t */\n\tpublic static Point getWeights(Point point, List<Point> computedPoints) throws PrismException {\n\t\tint dim = point.getDimension();\n\t\tif (computedPoints == null || computedPoints.size() == 0) {\n\t\t\tboolean nonZero = false;\n\t\t\tfor(int i = 0; i < dim; i++) {\n\t\t\t\tif (point.getCoord(i) != 0) {\n\t\t\t\t\tnonZero = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\t\t\t\n\t\t\t\n\t\t\tPoint resPoint;\n\t\t\tif (nonZero) {\n\t\t\t\tresPoint = point.normalize();\n\t\t\t} else {\n\t\t\t\tdouble[] result = new double[dim];\n\t\t\t\tfor(int i = 0; i < dim; i++) {\n\t\t\t\t\tresult[i] = 1.0;\n\t\t\t\t}\n\t\t\t\tresPoint = (new Point(result)).normalize();\n\t\t\t}\n\t\t\treturn resPoint;\n\t\t}\n\t\t\n\t\tint epsilonCoord = dim + 1;\n\t\t//int numVars = dim + 1;\n\t\tdouble[] d;\n\t\ttry {\n\t\t\tlpsolve.LpSolve solver = lpsolve.LpSolve.makeLp(0,dim + 2);\n\t\t\tsolver.setVerbose(lpsolve.LpSolve.CRITICAL);\n\t\t\t\n\t\t\t//for some strange reason the 0th element of an array is ignored by addConstraint\n\t\t\td = new double[dim + 3];\n\t\t\tfor (int i = 0; i< dim; i++) {\n\t\t\t\td[i + 1] = point.getCoord(i);\n\t\t\t}\n\t\t\t\n\t\t\td[dim + 2] = -1.0;\n\t\t\t\n\t\t\t//System.out.println(Arrays.toString(d));\n\t\t\tsolver.addConstraint(d, lpsolve.LpSolve.GE, 0.0);\n\t\t\t\n\t\t\tfor (Point p : computedPoints)\n\t\t\t{\n\t\t\t\td = new double[dim + 3];\n\t\t\t\tfor (int i = 0; i< dim; i++) {\n\t\t\t\t\td[i + 1] = p.getCoord(i);\n\t\t\t\t}\n\t\t\t\td[epsilonCoord] = 1;\n\t\t\t\t\n\t\t\t\td[dim + 2] = -1.0;\n\t\t\t\t\n\t\t\t\tsolver.addConstraint(d, lpsolve.LpSolve.LE, 0.0);\n\t\t\t}\n\t\t\t\n\t\t\tfor(int i = 0; i < dim; i++) {\n\t\t\t\td = new double[dim + 3];\n\t\t\t\td[i + 1] = 1;\n\t\t\t\t\n\t\t\t\tsolver.addConstraint(d, lpsolve.LpSolve.GE, 0.0);\n\t\t\t}\n\t\t\t\n\t\t\td = new double[dim + 3];\n\t\t\t\n\t\t\tfor(int i = 0; i < dim; i++) {\n\t\t\t\td[i + 1] = 1;\n\t\t\t}\n\n\t\t\tsolver.addConstraint(d, lpsolve.LpSolve.LE, 1.0);\n\n\t\t\td = new double[dim + 3];\n\t\t\td[epsilonCoord] = 1;\n\t\t\t\t\n\t\t\tsolver.setBounds(dim + 2, Double.NEGATIVE_INFINITY, Double.POSITIVE_INFINITY);\n\t\t\t\n\t\t\tsolver.setObjFn(d);\n\t\t\tsolver.setMaxim();\n\t\t\t\n\t\t\tint r = solver.solve();\n\t\t\t\t\t\n\t\t\tif (r == lpsolve.LpSolve.INFEASIBLE) {\n\t\t\t\tSystem.out.println(\"The solution is infeasible\");\n\t\t\t\treturn null;\n\t\t\t} else if (r == lpsolve.LpSolve.UNBOUNDED) {\n\t\t\t\t//this should never happen\n\t\t\t\tthrow new PrismException(\"The solution of a linear program is unbounded.\");\n\t\t\t} if (r != lpsolve.LpSolve.OPTIMAL)\n\t\t\t\t//this should also never happen\n\t\t\t\tthrow new PrismException(\"LpSolve returns an unexpected value: \" + r);\n\n\t\t\tdouble[] resultSolver = solver.getPtrVariables();\n\t\t\t//solver.printLp();\n\t\t\tif (resultSolver[epsilonCoord-1] == 0.0) {\n\t\t\t\t//there is no _strictly_ separating hyperplane (i.e. one that doesn't touch any of the points)\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\t\n\t\t\t//solver.printLp();\n\t\t    //System.out.println(\"solver says:\" + r);\n\t\t    //System.out.println(\"solver results:\" + Arrays.toString(resultSolver));\n\t\t\t\t\n\t\t\tdouble[] result = new double[dim];\n\t\t\t//copy all coordinates and ignore auxiliary variables\n\t\t\tfor(int i = 0; i < dim; i++)\n\t\t\t\tresult[i] = resultSolver[i];\n\t\t\t\n\t\t\tPoint resPoint = new Point(result).normalize();\n\t\t\t\n\t\t\treturn resPoint;\n\t\t} catch (lpsolve.LpSolveException ex) {\n\t\t\tPrismException ex2 = new PrismException(\"lpsolve threw an exception: \" + ex.getMessage());\n\t\t\tthrow ex2;\n\t\t}\n\t}\n\n\t/**\n\t * Prints an auxiliary graph file in gnuplot format. Points must be 2D.\n\t * \n\t * NOTE: not very nice now, should be enhanced in the future...\n\t * \n\t * @param target Current target\n\t * @param points Corner points of the pareto curve\n\t * @param directions Directions associated with the corner points.\n\t * @param directory The directory where to store the file.\n\t * @param index Counter that should be incremented with every call of this method, determines a suffix of the name of the file.\n\t * @throws PrismException\n\t */\n\tpublic static void printGraphFileDebug(Point target, List<Point> points, List<Point> directions, String directory, int index) throws PrismException {\n\t\t//System.out.println(\"Plotting \" + index + \": \" + points + \", \" + directions);\n\t\t\n\t\tdouble padding = 1.2;\n\t\tdouble maxX = target.getCoord(0) * padding;\n\t\tdouble maxY = target.getCoord(1) * padding;\n\t\tfor (Point p : points) {\n\t\t\tdouble x = p.getCoord(0) * padding;\n\t\t\tdouble y = p.getCoord(1) * padding;\n\t\t\tmaxX = (maxX >= x) ? maxX : x;\n\t\t\tmaxY = (maxY >= y) ? maxY : y;\n\t\t}\n\t\t\n\t\ttry {\n\t\t\tFileWriter fw;\n\t\t\tif (target != null) {\n\t\t\t\tfw = new FileWriter(new File(directory, \"dataT\" + index + \".dat\"));\n\t\t\t\tfw.write(target.getCoord(0) + \" \" + target.getCoord(1));\n\t\t\t\tfw.close();\n\t\t\t}\n\t\t\t\n\t\t\tfw = new FileWriter(new File(directory,\"dataP\" + index + \".dat\"));\n\t\t\tfor (Point p : points) {\n\t\t\t\tfw.write(p.getCoord(0) + \" \" + p.getCoord(1) + \"\\n\");\n\t\t\t}\n\t\t\tfw.close();\n\t\t\t\n\t\t\tfw = new FileWriter(new File(directory, \"plot\" + index + \".plot\"));\n\t\t\tfw.write(\"set parametric\\n\");\n\t\t\tfw.write(\"set trange [0:\" + maxX + \"]\\n\");\n\t\t\tfw.write(\"set xrange [0:\" + maxX + \"]\\n\");\n\t\t\tfw.write(\"set yrange [0:\" + maxY + \"]\\n\");\n\t\t\tfw.write(\"set term aqua\\n\");\n\t\t\t//fw.write(\"set output \\\"output\" + index + \".ps\\\"\\n\");\n\t\t\tfw.write(\"plot \");\n\t\t\tif (target != null)\n\t\t\t\tfw.write(\"\\\"dataT\" + index + \".dat\\\" with points pt 9, \");\n\t\t\tfw.write(\"\\\"< sort dataP\" + index + \".dat\\\"  with linespoints pt 9 lw 3\");\n\t\t\tfor (int i = 0; i < points.size(); i++) {\n\t\t\t\tPoint p = points.get(i);\n\t\t\t\tPoint d = directions.get(i);\n\t\t\t\tdouble k = (p.getCoord(0)*d.getCoord(0)) + (p.getCoord(1)*d.getCoord(1));\n\t\t\t\tif (d.getCoord(1) > 0)\n\t\t\t\t\tfw.write(\", t,(-\" + d.getCoord(0) + \"*t + \" + k + \")/\" + d.getCoord(1) + \" with lines lc 3\");\n\t\t\t\telse\n\t\t\t\t\tfw.write(\", \" + p.getCoord(0) + \",t with lines lc 3\");\n\t\t\t}\n\t\t\tfw.close();\n\t\t} catch (IOException ex) {\n\t\t\tthrow new PrismException(\"An IOException error occured when writing graph files (exception message: \" + ex.getMessage() + \").\");\n\t\t}\n\t}\n\n\tpublic static void exportPareto(TileList tl, String filename) throws PrismException {\n\t\t//System.out.println(\"Plotting \" + index + \": \" + points + \", \" + directions);\n\t\ttry {\n\t\t\tFileWriter fw;\n\t\t\tfw = new FileWriter(filename);\n\t\t\tfw.write(tl.toString());\n\t\t\tfw.close();\n\t\t\t\t} catch (IOException ex) {\n\t\t\tthrow new PrismException(\"An IOException error occured when writing graph files (exception message: \" + ex.getMessage() + \").\");\n\t\t}\n\t}\n\t\n\t/**\n\t * This method takes a list of computed points together with their associated directions, where points are possibly\n\t * repeated, and returns a map in which to each point from {@code computedPoints} corresponds the associated direction\n\t * from {@code directions} which has the most extreme slope. Which extreme is taken depends on the {@code horiz} parameter.\n\t * <br>\n\t * Note that this method considers two points as \"equal\" if the method {@code isCloseTo(Point)} returns {@code true}.\n\t * So the returned map will not contain two keys which are too close to each other, which should be fine w.r.t. roundoff\n\t * errors, but might theoretically cause trouble if the corner points of the Pareto curve are very close to each other.\n\t * <br>\n\t * It is guaranteed that if there are two points {@code p1} and {@code p2} in {@code computedPoints} such that\n\t * {@code p1.isCloseTo{p2}} is {@code true} and {@code p1} occurs in {@code computedPoints} before\n\t * {@code p2}, then {@code p1} will be given precedence when picking a representative for the key in the map. This is crucial\n\t * when using this method together with {@link MultiObjUtils#removeDuplicities(List)}.\n\t * \n\t * @param computedPoints The computed points of the Pareto curve\n\t * @param directions The directions associated with the computed points.\n\t * @param horiz If true, gets the one which is closest to horizontal, if false then the one which is closest to vertical.\n\t * @return A map in which to each point from {@code computedPoints} is associated the most extreme direction from {@code directions}.\n\t */\n\tprotected static java.util.Map<Point, Point> fillDirections(List<Point> computedPoints, List<Point> directions, boolean horiz) {\n\t\tHashMap<Point, Point> map = new HashMap<Point, Point>();\n\t\tfor(int i = 0; i < computedPoints.size(); i++) {\n\t\t\tPoint p = computedPoints.get(i);\n\t\t\tPoint dir = directions.get(i);\n\t\t\tboolean added = false;\n\t\t\tfor (Point key : map.keySet()) {\n\t\t\t\tif (key.isCloseTo(p)) {\n\t\t\t\t\tdouble slopeNew = (dir.getCoord(1) == 0) ? Double.POSITIVE_INFINITY :  dir.getCoord(0)/dir.getCoord(1);\n\t\t\t\t\tdouble slopeOrig = (map.get(key).getCoord(1) == 0) ? Double.POSITIVE_INFINITY : map.get(key).getCoord(0)/map.get(key).getCoord(1);\n\t\t\t\t\tif ((horiz && slopeNew < slopeOrig) || (!horiz && slopeNew > slopeOrig)) {\n\t\t\t\t\t\tmap.put(key, dir);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t\t\n\t\t\tif (!added) {\n\t\t\t\tmap.put(p, dir);\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn map;\n\t}\n\n\t/**\n\t * This method takes a list of points and returns a sub-list in which points that are very close to\n\t * each other (where {@code isCloseTo(Point)} is used to determine what is \"very close\") are removed.\n\t * The order of elements is preserved.\n\t * \n\t * It is guaranteed that if there are two points {@code p1} and {@code p2} in {@code list} such that\n\t * {@code p1.isCloseTo{p2}} is {@code true} and {@code p1} occurs in {@code list} before\n\t * {@code p2}, then {@code p1} will be given precedence when picking the point to keep. This is crucial\n\t * when using this method together with {@link fillDirections}.\n\t * @param list\n\t * @return\n\t */\n\tprotected static List<Point> removeDuplicities(List<Point> list) {\n\t\t//TODO implement faster alg if we can be bothered.\n\t\tArrayList<Point> ret = new ArrayList<Point>();\n\t\tif (list.size() == 0)\n\t\t\treturn ret;\n\t\t\n\t\tret.add(list.get(0));\n\t\tfor (int i = 1; i < list.size(); i++) {\n\t\t\tPoint p = list.get(i);\n\t\t\t\n\t\t\t//check if contains\n\t\t\tboolean contains = false;\n\t\t\tfor(Point p2 : ret) {\n\t\t\t\tif (p2.isCloseTo(p)) {\n\t\t\t\t\tcontains = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif (!contains)\n\t\t\t\tret.add(p);\n\t\t}\n\t\treturn ret;\n\t}\n\n\t/**\n\t * This method takes the set of some corner points of a pareto curve {@code computedPoints} together\n\t * with associated orthogonal lines {@code directions} that determine current over-approximation,\n\t * and returns the points which determine the over-approximation. (These points are in fact the intersecting\n\t * points of the directions which are not covered by other points.)\n\t * @param computedPoints Corner points of the Pareto curve\n\t * @param directions Directions (orthogonal lines) associated with the corner points\n\t * @return The list of points that together with {@code computedPoints} determine the over-approximation of the pareto curve\n\t */\n\tprotected static List<Point> upperBoundPoints(List<Point> computedPoints, List<Point> directions)\n\t{\n\t\tjava.util.Map<Point, Point> directionMapHoriz = fillDirections(computedPoints, directions, true);\n\t\tjava.util.Map<Point, Point> directionMapVert = fillDirections(computedPoints, directions, false);\n\t\t\n\t\tPermutedLexicographicComparator plc = new PermutedLexicographicComparator(new int[] {0,1}, new boolean[] {true, false});\n\t\tList<Point> sortedLP = removeDuplicities(computedPoints);\n\t\tCollections.sort(sortedLP, plc);\n\t\t\n\t\t//System.out.println(\"LP: \" + sortedLP);\n\t\t\n\t\tArrayList<Point> ret = new ArrayList<Point>();\n\t\tfor (int i =0; i < sortedLP.size() - 1; i++) {\t\t\t\n\t\t\tPoint p1 = sortedLP.get(i);\n\t\t\tPoint p2 = sortedLP.get(i+1);\n\t\t\tPoint d1 = directionMapVert.get(p1);\n\t\t\tPoint d2 = directionMapHoriz.get(p2);\n\t\t\t\n\t\t\t//System.out.println(\"p1: \" + p1 + \", p2: \" + p2);\n\t\t\tPoint p;\n\t\t\tif (d2.getCoord(1) > Point.SMALL_NUMBER) {\t\t\n\t\t\t\tdouble k1 = p1.getCoord(0)*d1.getCoord(0) + p1.getCoord(1)* d1.getCoord(1);\n\t\t\t\tdouble k2 = p2.getCoord(0)*d2.getCoord(0) + p2.getCoord(1)* d2.getCoord(1);\n\t\t\t\t\n\t\t\t\tdouble[][] eqns = {{d1.getCoord(0), d1.getCoord(1)}, {d2.getCoord(0), d2.getCoord(1)}};\n\t\t\t\tdouble[] coords =MultiObjUtils.solveEqns(eqns, new double[] {k1,k2});\n\t\t\t\t\n\t\t\t\tif (coords == null) //HACK this is if two numbers are too close\n\t\t\t\t\tcontinue;\n\t\t\t\t\n\t\t\t\t//System.out.println(\"returned: \" + Arrays.toString(coords));\n\t\t\t\t\n\t\t\t\tp = new Point(coords);\n\t\t\t} else if (d1.getCoord(0) < Point.SMALL_NUMBER && d2.getCoord(1) < Point.SMALL_NUMBER) {\n\t\t\t\tp = new Point(new double [] {p2.getCoord(0), p1.getCoord(1)});\n\t\t\t\t//System.out.println(\"returned': \" + p);\n\t\t\t} else {\n\t\t\t\tdouble x = p2.getCoord(0);\n\t\t\t\tdouble k1 = p1.getCoord(0)*d1.getCoord(0) + p1.getCoord(1)* d1.getCoord(1);\n\t\t\t\t//System.out.println(\"x: \" + x + \", k1: \" + k1 + \", d1[0]: \" + d1.getCoord(0) + \", d1[1]: \" + d1.getCoord(1));\n\t\t\t\tdouble y = (k1 - d1.getCoord(0)*x)/d1.getCoord(1);\n\t\t\t\tp = new Point(new double[] {x,y});\n\t\t\t\t//System.out.println(\"returned'': \" + p.toString());\n\t\t\t}\n\t\t\t\n\t\t\t//check if this point is in computedPoints\n\t\t\tboolean isCornerPoint = false;\n\t\t\tfor (Point pc : computedPoints)\n\t\t\t\tif (pc.isCloseTo(p)) {\n\t\t\t\t\tisCornerPoint = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\t\t\n\t\t\tif (!isCornerPoint)\n\t\t\t\tret.add(p);\n\t\t}\n\t\treturn ret;\n\t}\n\n\t/**\n\t * Returns new point for computation of two dimensional pareto curve. More formally,\n\t * this method takes the points on the pareto curve computed so far, together with\n\t * the directions (i.e. orthogonal hyperplanes) corresponding to the points, and\n\t * returns a point which can still be in a pareto curve, and which is most distant\n\t * from the points which are already known to be on the pareto curve. Here, most distant\n\t * means that a point (x,y) is taken such that for every point (a,b) from the pareto\n\t * curve the number max{x-a,y-b) is maximized.  \n\t * \n\t * @param computedPoints The list of already computed corner points of the pareto curve.\n\t * @param directions The list of directions associated with the computed corner points.\n\t * @param errorTolerance The required precision of the pareto curve being approximated\n\t * @return The point, or {@code null} if no point has a distance greater than {@code errorTolerance}\n\t */\n\tprotected static Point getNewTarget(List<Point> computedPoints, List<Point> directions, double errorTolerance, double[] maxValues)\n\t{\n\t\t//if we have less than 2 computed points, we take the most extreme directions\n\t\tif (computedPoints.size() == 0)\n\t\t\treturn new Point(new double[] {maxValues[0], 0});\n\t\tif (computedPoints.size() == 1)\n\t\t\treturn new Point(new double[] {0, maxValues[1]});\n\t\t\t//return new Point(new double[] {0, computedPoints.get(0).getCoord(1) + 1.0});\n\t\t\n\t\t//sortedLP is the set of computed corner points (i.e. their convex closure is an under-approx. of solution)\n\t\t//sortedUP is the set of points that toget (i.e. together with sortedLP, their convex closure is an over-approx. of solution)\n\t\t\n\t\tPermutedLexicographicComparator plc = new PermutedLexicographicComparator(new int[] {0,1}, new boolean[] {true, false});\n\t\tList<Point> sortedLP = removeDuplicities(computedPoints);\n\t\tCollections.sort(sortedLP, plc);\n\t\tSystem.out.println(\"sortedLP\" + sortedLP);\n\t\t\n\t\tList<Point> sortedUP = upperBoundPoints(computedPoints, directions);\n\t\tCollections.sort(sortedUP, plc);\n\t\tSystem.out.println(\"sortedUP: \" + sortedUP);\n\t\t\n\t\t//if (sortedUP.size() == 0)\n\t\t//\treturn null;\n\t\tint iLP = 0, iUP = 0;\n\t\tdouble maxVal = 0.0;\n\t\tint maxUP = -1;\n\t\twhile (iLP < sortedLP.size() - 1 && iUP < sortedUP.size()) {\n\t\t\tif(sortedUP.get(iUP).getCoord(0) > sortedLP.get(iLP + 1).getCoord(0)) {\n\t\t\t\tiLP++;\n\t\t\t} else if(sortedUP.get(iUP).getCoord(0) <= sortedLP.get(iLP + 1).getCoord(0)) {\n\t\t\t\tdouble a1  = sortedLP.get(iLP).getCoord(0);\n\t\t\t\tdouble a2  = sortedLP.get(iLP).getCoord(1);\n\t\t\t\tdouble b1  = sortedLP.get(iLP + 1).getCoord(0);\n\t\t\t\tdouble b2  = sortedLP.get(iLP + 1).getCoord(1);\n\t\t\t\t\n\t\t\t\t//distance on the x axis\n\t\t\t\tdouble x2  = sortedUP.get(iUP).getCoord(1);\n\t\t\t\tdouble x1 = ((a1-b1)*(x2-b2))/(a2-b2) + b1;\n\t\t\t\tdouble d = Math.abs((sortedUP.get(iUP).getCoord(0)-x1)/x1);\n\t\t\t\t//double d = (sortedUP.get(iUP).getCoord(0)-x1);\n\t\t\t\t//System.out.println(\"a1: \" + a1 + \"  a2: \" + a2 + \"  b1: \" + b1 + \"  b2: \" + b2 + \"  x1: \" + x1 + \"  x2: \" + x2 + \"  d:\" + d);\n\t\t\t\tif (maxVal < d) {\n\t\t\t\t\tmaxVal = d;\n\t\t\t\t\tmaxUP = iUP;\n\t\t\t\t\t//System.out.println(\"val: \" + maxVal + \", point: \" + sortedUP.get(iUP));\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t//distance on the y axis\n\t\t\t\tx1 = sortedUP.get(iUP).getCoord(0);\n\t\t\t\tx2 = ((a2-b2)*(x1-b1))/(a1-b1) + b2;\n\t\t\t\td = Math.abs((sortedUP.get(iUP).getCoord(1)-x2)/x2);\n\t\t\t\t//d = (sortedUP.get(iUP).getCoord(1)-x2);\n\t\t\t\tif (maxVal < d) {\n\t\t\t\t\tmaxVal = d;\n\t\t\t\t\tmaxUP = iUP;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t//distance along the y axis\n\t\t\t\t\n\t\t\t\tiUP++;\n\t\t\t} else {\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif (maxUP != -1 && maxVal > errorTolerance) {\n\t\t\t//System.out.println(\"distance:\" + maxVal);\n\t\t\treturn sortedUP.get(maxUP);\n\t\t} else {\n\t\t\treturn null;\n\t\t}\n\t}\n\n\t/**\n\t * Uses Gaussian elimination to solve equations given by {@code eqns} and {@code b}.\n\t * The equations are given by eqns.x=b, where eqns is a matrix, and b is a column vector.\n\t * \n\t * @return Array containing values for each variable.\n\t */\n\tprotected static double[] solveEqns(double[][] eqns, double[] b)\n\t{\n\t\t//System.out.println(\"Solving eqns\");\n\t\t//using Gaussian elimination\n\t\n\t\t//System.out.println(\"y \" + Arrays.deepToString(eqns) + \" \" + Arrays.toString(b));\n\t\t\n\t\tint numVars = eqns[0].length;\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t//find pivot (the greatest number) for i-th column\n\t\t\tint index = i;\n\t\t\tfor (int j = i + 1; j < numVars; j++) {\n\t\t\t\tif (eqns[j][i] > eqns[index][i])\n\t\t\t\t\tindex = j;\n\t\t\t}\n\t\t\t\n\t\t\tdouble[] row = eqns[i];\n\t\t\teqns[i] = eqns[index];\n\t\t\teqns[index] = row;\n\t\t\tdouble right = b[i];\n\t\t\tb[i] = b[index];\n\t\t\tb[index] = right;\n\t\t\t\n\t\t\t\n\t\t\tif (Math.abs(eqns[i][i]) > Point.SMALL_NUMBER)\n\t\t\t{\n\t\t\t\tfor (int j = i+1; j < eqns.length; j++)\n\t\t\t\t{\n\t\t\t\t\tdouble factor = eqns[j][i] / eqns[i][i];\n\t\t\t\t\tfor (int k = i; k < numVars; k++) {\n\t\t\t\t\t\teqns[j][k] -= factor * eqns[i][k];\n\t\t\t\t\t}\n\t\t\t\t\tb[j] -= factor * b[i];\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t//System.out.println(\"z \" + Arrays.deepToString(eqns) + \" \" + Arrays.toString(b));\n\t\t}\t\t\n\t\t\n\t\t//System.out.println(\"x \" + Arrays.deepToString(eqns) + \" \" + Arrays.toString(b));\n\t\t\n\t\tfor(int i = numVars; i < eqns.length; i++)\n\t\t{\n\t\t\tif (Math.abs(eqns[i][numVars-1]) > Point.SMALL_NUMBER || Math.abs(b[i]) > Point.SMALL_NUMBER) {\n\t\t\t\tSystem.out.println(\"m \" + Arrays.deepToString(eqns) + \" \" + Arrays.toString(b));\n\t\t\t\treturn null;\n\t\t\t}\n\t\t}\n\t\t\n\t\tdouble[] res = new double[eqns[0].length];\n\t\tfor (int i = eqns[0].length - 1; i >= 0; i--)\n\t\t{\n\t\t\tdouble sum = 0.0;\n\t\t\tfor (int j = i + 1; j < eqns[0].length; j++) {\n\t\t\t\tsum += eqns[i][j]*res[j];\n\t\t\t}\n\t\t\t\n\t\t\tif (eqns[i][i] < Point.SMALL_NUMBER && Math.abs(b[i] - sum) < Point.SMALL_NUMBER)\n\t\t\t{\n\t\t\t\tres[i] = 0.0;\n\t\t\t}\n\t\t\t/*\n\t\t\telse if (eqns[i][i] < Point.SMALL_NUMBER && Math.abs(b[i] - sum) > Point.SMALL_NUMBER)\n\t\t\t{\n\t\t\t\tSystem.out.println(\"n \" + Arrays.deepToString(eqns) + \" \" + Arrays.toString(b));\n\t\t\t\treturn null;\n\t\t\t}*/\n\t\t\telse \n\t\t\t{\n\t\t\t\tres[i] = (b[i] - sum ) / eqns[i][i];\n\t\t\t}\n\t\t}\n\t\treturn res;\n\t}\n\n/*\tprotected static double[] solveEqnsUsingLP(double[][] eqns, double[] b)\n\t{\n\t\tint dim = eqns[0].length;\n\t\t//lpsolve.LpSolve solver = lpsolve.LpSolve.makeLp(0,dim + 1);\n\t\tsolver.setVerbose(lpsolve.LpSolve.CRITICAL);\n\t\t\n\t\t//for some strange reason the 0th element of an array is ignored by addConstraint\n\t\t\n\t\tfor (int i = 0; i < eqns.length; i++) {\n\t\t\tdouble[] d = new double[dim + 1];\n\t\t\tfor (int j = 0; j< dim; j++) {\n\t\t\t\td[j + 1] = eqns[i][j];\n\t\t\t}\n\t\t\t//solver.addConstraint(d, lpsolve.LpSolve.EQ, b[i]);\n\t\t}\n\t\treturn null;\n\t}*/\n}\n"
  },
  {
    "path": "prism/src/prism/NativeIntArray.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"NativeIntArray.h\"\n#include \"jnipointer.h\"\n\nJNIEXPORT jlong JNICALL Java_prism_NativeIntArray_NIA_1CreateArray\n(JNIEnv * env, jclass cls, jint size)\n{\n    int* a = new int[size];\n    return ptr_to_jlong(a);\n}\n\nJNIEXPORT void JNICALL Java_prism_NativeIntArray_NIA_1DeleteArray\n(JNIEnv * env, jclass cls, jlong ptr)\n{\n    delete ((int *) jlong_to_ptr(ptr));\n}\n\nJNIEXPORT jint JNICALL Java_prism_NativeIntArray_NIA_1Get\n(JNIEnv * env, jclass cls, jlong ptr, jint index)\n{\n    return  ((int *) jlong_to_ptr(ptr))[index];\n}\n\nJNIEXPORT void JNICALL Java_prism_NativeIntArray_NIA_1Set\n(JNIEnv * env, jclass cls, jlong ptr, jint index, jint value)\n{\n    ((int *) jlong_to_ptr(ptr))[index] = value;\n}\n\nJNIEXPORT void JNICALL Java_prism_NativeIntArray_NIA_1SetAll\n(JNIEnv * env, jclass cls, jlong ptr, jint index, jint count, jint value)\n{\n    int* a = (int *) jlong_to_ptr(ptr);\n    for(int i = 0; i < count; i++)\n        a[i+index] = value;\n}\n"
  },
  {
    "path": "prism/src/prism/NativeIntArray.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * Class to store {@code int} elements in an array.\n */\npublic class NativeIntArray \n{\n\tprivate static native long NIA_CreateArray(int size);\n\tprivate static native void NIA_DeleteArray(long ptr);\n\tprivate static native int NIA_Get(long ptr, int index);\n\tprivate static native void NIA_Set(long ptr, int index, int value);\n\tprivate static native void NIA_SetAll(long ptr, int indexFrom, int count, int value);\n\t\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\t\n\tprivate long ptr;\n\tprivate int size;\n\t\n\t/**\n\t * Creates a new native array of size s, and keeps it wrapped in this object.\n\t * Note that the elements of the array may not be initialised to 0. Use\n\t * {@link #setAllTo(int)} to initialise the array.\n\t * @param size The size of the array to be created.\n\t */\n\tpublic NativeIntArray(int size)\n\t{\n\t\tthis.size = size;\n\t\tthis.ptr = NIA_CreateArray(size);\n\t}\n\t\n\t/**\n\t * Returns the pointer to the wrapped native array.\n\t * @return Pointer\n\t */\n\tpublic long getPtr()\n\t{\n\t\treturn ptr;\n\t}\n\t\n\t/**\n\t * Deletes the native array and frees the memory.\n\t */\n\tpublic void clear()\n\t{\n\t\tNIA_DeleteArray(ptr);\n\t}\n\t\n\t/**\n\t * Returns the {@code index}-th element of the aray\n\t * @param index\n\t * @throws IndexOutOfBoundsException If the index is outside of the bounds of the array\n\t */\n\tpublic int get(int index) throws IndexOutOfBoundsException\n\t{\n\t\tif (index < 0 || index >= size)\n\t\t\tthrow new IndexOutOfBoundsException();\n\t\treturn NIA_Get(ptr, index);\n\t}\n\t\n\t/**\n\t * Sets the {@code index}-th element of the array to {@code val}.\n\t * @param index\n\t * @param value\n\t * @throws IndexOutOfBoundsException If the index is outside of the bounds of the array\n\t */\n\tpublic void set(int index, int value) throws IndexOutOfBoundsException\n\t{\n\t\tif (index < 0 || index >= size)\n\t\t\tthrow new IndexOutOfBoundsException();\n\t\tNIA_Set(ptr, index, value);\n\t}\n\n\t/**\n\t * Sets all elements of the array to {@code value}.\n\t * @param value Value to be set\n\t */\n\tpublic void setAllTo(int value) {\n\t\tNIA_SetAll(ptr, 0, size, value);\n\t}\n\t\n\t/**\n\t * Returns the size of the wrapped array.\n\t */\n\tpublic int size()\n\t{\n\t\treturn this.size;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/OpRelOpBound.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2014-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport explicit.MinMax;\nimport parser.ast.RelOp;\n\n/**\n * Class to represent info (operator, relational operator, bound, etc.) found in a P/R/S operator.\n */\npublic class OpRelOpBound\n{\n\tprotected String op;\n\tprotected RelOp relOp;\n\tprotected boolean numeric;\n\tprotected double bound;\n\n\tpublic OpRelOpBound(String op, RelOp relOp, Double boundObject)\n\t{\n\t\tthis.op = op;\n\t\tthis.relOp = relOp;\n\t\tnumeric = (boundObject == null);\n\t\tif (boundObject != null)\n\t\t\tbound = boundObject.doubleValue();\n\t}\n\n\tpublic boolean isProbabilistic()\n\t{\n\t\treturn \"P\".equals(op);\n\t}\n\n\tpublic boolean isReward()\n\t{\n\t\treturn \"R\".equals(op);\n\t}\n\n\tpublic RelOp getRelOp()\n\t{\n\t\treturn relOp;\n\t}\n\n\tpublic boolean isNumeric()\n\t{\n\t\treturn numeric;\n\t}\n\n\tpublic double getBound()\n\t{\n\t\treturn bound;\n\t}\n\n\tpublic boolean isQualitative()\n\t{\n\t\treturn !isNumeric() && op.equals(\"P\") && (bound == 0 || bound == 1);\n\t}\n\n\tpublic boolean isTriviallyTrue()\n\t{\n\t\tif (!isNumeric() && op.equals(\"P\")) {\n\t\t\t// >=0\n\t\t\tif (bound == 0 && relOp == RelOp.GEQ)\n\t\t\t\treturn true;\n\t\t\t// <=1\n\t\t\tif (bound == 1 && relOp == RelOp.LEQ)\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\tpublic boolean isTriviallyFalse()\n\t{\n\t\tif (!isNumeric() && op.equals(\"P\")) {\n\t\t\t// <0\n\t\t\tif (bound == 0 && relOp == RelOp.LT)\n\t\t\t\treturn true;\n\t\t\t// >1\n\t\t\tif (bound == 1 && relOp == RelOp.GT)\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\tpublic MinMax getMinMax(ModelType modelType) throws PrismLangException\n\t{\n\t\treturn getMinMax(modelType, true);\n\t}\n\n\tpublic MinMax getMinMax(ModelType modelType, boolean forAll) throws PrismLangException\n\t{\n\t\tMinMax minMax = MinMax.blank();\n\t\tint nondetSources = modelType.nondeterministic() ? 1 : 0;\n\t\tnondetSources += modelType.uncertain() ? 1 : 0;\n\t\tif (nondetSources > 0) {\n\t\t\tif (isNumeric()) {\n\t\t\t\tif (relOp == RelOp.EQ) {\n\t\t\t\t\tthrow new PrismLangException(\"Can't use \\\"\" + op + \"=?\\\" for nondeterministic models; use e.g. \\\"\" + op + \"min=?\\\" or \\\"\" + op + \"max=?\\\"\");\n\t\t\t\t}\n\t\t\t\tif (nondetSources == 1) {\n\t\t\t\t\tif (relOp == RelOp.MINMIN || relOp == RelOp.MINMAX || relOp == RelOp.MAXMIN || relOp == RelOp.MAXMAX) {\n\t\t\t\t\t\tthrow new PrismLangException(\"Can't use \\\"\" + toString() + \" for \" + modelType + \"s\");\n\t\t\t\t\t}\n\t\t\t\t\tif (modelType.uncertain()) {\n\t\t\t\t\t\t// IDTMC\n\t\t\t\t\t\tminMax = MinMax.blank().setMinUnc(relOp.isMin());\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// MDP etc.\n\t\t\t\t\t\tminMax = relOp.isMin() ? MinMax.min() : MinMax.max();\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// IMDP\n\t\t\t\t\tif (relOp == RelOp.MIN || relOp == RelOp.MINMIN || relOp == RelOp.MINMAX) {\n\t\t\t\t\t\tminMax = MinMax.min();\n\t\t\t\t\t} else {\n\t\t\t\t\t\tminMax = MinMax.max();\n\t\t\t\t\t}\n\t\t\t\t\tminMax.setMinUnc(relOp == RelOp.MIN || relOp == RelOp.MINMIN || relOp == RelOp.MAXMIN);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tboolean min = forAll ? relOp.isLowerBound() : relOp.isUpperBound();\n\t\t\t\tif (!modelType.nondeterministic()) {\n\t\t\t\t\tminMax = MinMax.blank();\n\t\t\t\t} else {\n\t\t\t\t\tminMax = min ? MinMax.min() : MinMax.max();\n\t\t\t\t}\n\t\t\t\tif (modelType.uncertain()) {\n\t\t\t\t\tminMax.setMinUnc(min);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn minMax;\n\t}\n\n\tpublic String getTypeOfOperator()\n\t{\n\t\tString s = \"\";\n\t\ts += op + relOp;\n\t\ts += isNumeric() ? \"?\" : \"p\"; // TODO: always \"p\"?\n\t\treturn s;\n\t}\n\n\tpublic String relOpBoundString()\n\t{\n\t\treturn relOp.toString() + bound;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn op + relOp.toString() + (isNumeric() ? \"?\" : bound);\n\t}\n\n\t/**\n\t * Apply this relational operator and bound instance to a value.\n\t */\n\tpublic boolean apply(double value) throws PrismException\n\t{\n\t\tswitch (relOp) {\n\t\tcase GEQ:\n\t\t\treturn (double) value >= bound;\n\t\tcase GT:\n\t\t\treturn (double) value > bound;\n\t\tcase LEQ:\n\t\t\treturn (double) value <= bound;\n\t\tcase LT:\n\t\t\treturn (double) value < bound;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Cannot apply relational operator \" + relOp);\n\t\t}\n\t}\n\t\n\t/**\n\t * Apply this relational operator and bound instance to a value.\n\t * If the value is stored imprecisely (i.e., floating point),\n\t * the specified accuracy (if non-null) is taken into account, and an\n\t * exception is thrown if the value is not accurate enough to check the bound.\n\t */\n\tpublic boolean apply(double value, Accuracy accuracy) throws PrismException\n\t{\n\t\tif (accuracy != null) {\n\t\t\tboolean valueLow = apply(accuracy.getResultLowerBound(value));\n\t\t\tboolean valueHigh = apply(accuracy.getResultUpperBound(value));\n\t\t\tif (valueLow != valueHigh) {\n\t\t\t\tthrow new PrismException(\"Accuracy of value \" + value  + \" is not enough to compare to bound \" + bound);\n\t\t\t}\n\t\t}\n\t\treturn apply(value);\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Operator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * Enumeration that represents one of the operators used in multi-objective\n * verification. Note that strict inequalities are missing as these are not\n * allowed in current implementation of multi-objective.\n */\npublic enum Operator {\n\tP_MAX(0), R_MAX(3), P_MIN(5), R_MIN(8), P_GE(2), R_GE(4), P_LE(7), R_LE(9);\n\t   \n\tprivate int intValue = -1;\n\t\n\tprivate Operator(int i)\n\t{\n\t\tthis.intValue = i;\n\t}\n\t\n   \t/**\n   \t * Returns {@code true} if op is one {@code Operator.P_MIN},\n   \t * {@code Operator.R_MIN}, {@code Operator.P_LE}, or {@code Operator.R_LE}.\n   \t */\n\tpublic static boolean isMinOrLe(Operator op)\n\t{\n\t\tswitch (op)\n\t\t{\n\t\t\tcase P_MIN:\n\t\t\tcase R_MIN:\n\t\t\tcase P_LE:\n\t\t\tcase R_LE:\n\t\t\t\treturn true;\n\t\t\tdefault:\n\t\t\t\treturn false;\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns a number representing the current operator. These numbers\n\t * are used in the C code.\n\t */\n\tpublic int toNumber()\n\t{\n\t\treturn this.intValue;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/OpsAndBoundsList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\n/**\n * This class keeps lists of operators and bounds used in multi-objective verification. \n *\n * The instance keeps an ordered instance of (operator,bound) values.\n * These are currently held in two separate lists internally. A tuple\n * is added using {@link add(OpRelOpBound, Operator,double,int)} method, and retrieved using\n * {@link getOperator(int)} and {@link getBound(int)} methods.\n * \n * The class also provides methods for accessing i-th elements in the\n * subsequence containing only the tuples in which operator is a probabilistic\n * operator, and in the subsequence containing only the tuples in which operator\n * is a reward operator.\n */\npublic class OpsAndBoundsList\n{\n \n\t/**\n\t * Used when printing info to user.\n\t */\n\tprivate BitSet probNegated;\n\t\n\tprotected List<OpRelOpBound> opInfos;\n\tprotected List<Operator> relOps, relOpsProb, relOpsReward;\n\tprotected List<Double> bounds,  boundsProb, boundsReward;\n\tprotected List<Integer> stepBounds,  stepBoundsProb, stepBoundsReward, origPositionsReward, origPositionsProb;\n\t\n\t/**\n\t * The default constructor which allocates the lists with size 1.\n\t */\n\tpublic OpsAndBoundsList()\n\t{\n\t\tthis(1);\n\t}\n\t\n\t/**\n\t * Creates an instance of the class in which the \"big\" lists\n\t * are allocated with size numTargets.\n\t * @param numObjectives The expected number of elements that would be added to the list. \n\t */\n\tpublic OpsAndBoundsList(int numObjectives)\n\t{\n\t\tprobNegated = new BitSet();\n\t\topInfos = new ArrayList<OpRelOpBound>(numObjectives);\n\t\trelOps = new ArrayList<Operator>(numObjectives);\n\t\tbounds = new ArrayList<Double>(numObjectives);\n\t\tstepBounds = new ArrayList<Integer>(numObjectives);\n\t\trelOpsProb = new ArrayList<Operator>();\n\t\tboundsProb = new ArrayList<Double>();\n\t\tstepBoundsProb = new ArrayList<Integer>(numObjectives);\n\t\trelOpsReward = new ArrayList<Operator>();\n\t\tboundsReward = new ArrayList<Double>();\n\t\tstepBoundsReward = new ArrayList<Integer>(numObjectives);\n\t\torigPositionsReward = new ArrayList<Integer>(numObjectives);\n\t\torigPositionsProb = new ArrayList<Integer>(numObjectives);\n\t}\n\t\n\t/**\n\t * Adds a new tuple (op, bound) to the list. \n\t * @param op\n\t * @param quantityBound\n\t * @param stepBound\n\t * @param origPosition What was the position of this operator in the user's call to the multi(...) function.\n\t */\n\tpublic void add(OpRelOpBound opInfo, Operator op, double quantityBound, int stepBound, int origPosition)\n\t{\n\t\topInfos.add(opInfo);\n\t\trelOps.add(op);\n\t\tbounds.add(quantityBound);\n\t\tstepBounds.add(stepBound);\n\n\t\tswitch (op)\n\t\t{\n\t\t\tcase P_MAX:\n\t\t\tcase P_MIN:\n\t\t\tcase P_GE:\n\t\t\tcase P_LE:\n\t\t\t\trelOpsProb.add(op);\n\t\t\t\tboundsProb.add(quantityBound);\n\t\t\t\tstepBoundsProb.add(stepBound);\n\t\t\t\torigPositionsProb.add(origPosition);\n\t\t\t\tbreak;\n\t\t\tcase R_MAX:\n\t\t\tcase R_MIN:\n\t\t\tcase R_GE:\n\t\t\tcase R_LE:\n\t\t\t\trelOpsReward.add(op);\n\t\t\t\tboundsReward.add(quantityBound);\n\t\t\t\tstepBoundsReward.add(stepBound);\n\t\t\t\torigPositionsReward.add(origPosition);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new UnsupportedOperationException(\"Don't know how to add\" +\n\t\t\t\t\t\t\" operator \" + op + \", the handling code does not exist.\");\n\t\t}\n\t}\n\n\t/**\n\t * Returns the original position (starting from 0) of the operator that is now at i-th position among the reward properties.\n\t */\n\tpublic int getOrigPositionReward(int i)\n\t{\n\t\treturn origPositionsReward.get(i);\n\t}\n\n\t/**\n\t * Returns the original position (starting from 0) of the operator that is now at i-th position among the probabilistic properties.\n\t */\n\tpublic int getOrigPositionProb(int i)\n\t{\n\t\treturn origPositionsProb.get(i);\n\t}\n\t\n\t/**\n\t * Returns the operator at i-th position.\n\t */\n\tpublic Operator getOperator(int i)\n\t{\n\t\treturn relOps.get(i);\n\t}\n\t\n\t/**\n\t * Returns the bound on quantity at i-th position.\n\t */\n\tpublic double getBound(int i)\n\t{\n\t\treturn bounds.get(i);\n\t}\n\t\n\t/**\n\t * Returns the number-of-steps step bound at i-th position.\n\t */\n\tpublic int getStepBound(int i)\n\t{\n\t\treturn stepBounds.get(i);\n\t}\n\t\n\t/**\n\t * Returns the operator/relop info at i-th position.\n\t */\n\tpublic OpRelOpBound getOpRelOpBound(int i)\n\t{\n\t\treturn opInfos.get(i);\n\t}\n\n\t/**\n\t * Returns the operator at i-th position in the subsequence containing only probabilistic\n\t * operators.\n\t */\n\tpublic Operator getProbOperator(int i)\n\t{\n\t\treturn relOpsProb.get(i);\n\t}\n\n\t/**\n\t * Returns the probability bound at i-th position in the subsequence containing only probabilistic\n\t * operators.\n\t */\n\tpublic double getProbBound(int i)\n\t{\n\t\treturn boundsProb.get(i);\n\t}\n\n\t/**\n\t * Returns the number-of-steps bound at i-th position in the subsequence containing only probabilistic\n\t * operators.\n\t */\n\tpublic int getProbStepBound(int i)\n\t{\n\t\treturn stepBoundsProb.get(i);\n\t}\n\t\n\t/**\n\t * Returns the operator at i-th position in the subsequence containing only reward\n\t * operators.\n\t */\n\tpublic Operator getRewardOperator(int i)\n\t{\n\t\treturn relOpsReward.get(i);\n\t}\n\t\n\t/**\n\t * Returns the bound on reward at i-th position in the subsequence containing only reward\n\t * operators.\n\t */\n\tpublic double getRewardBound(int i)\n\t{\n\t\treturn boundsReward.get(i);\n\t}\n\t\n\t/**\n\t * Returns the number-of-steps bound at i-th position in the subsequence containing only reward\n\t * operators.\n\t */\n\tpublic int getRewardStepBound(int i)\n\t{\n\t\treturn stepBoundsReward.get(i);\n\t}\n\t\n\t/**\n\t * Returns true iff the i-th objective is probability objective.\n\t */\n\tpublic boolean isProbabilityObjective(int i)\n\t{\n\t\tswitch (relOps.get(i))\n\t\t{\n\t\t\tcase P_MAX:\n\t\t\tcase P_MIN:\n\t\t\tcase P_GE:\n\t\t\tcase P_LE:\n\t\t\t\treturn true;\n\t\t\tdefault:\n\t\t\t\treturn false;\n\t\t}\n\t}\n\n\t/**\n\t * True if the ith probabilistic objective is negation of what the user required\n\t * (i.e. formula is negated and we use &gt;= instead &lt;= or max instead of min).\n\t * Used to determine what values to display to the user.\n\t * @param i\n\t * @return\n\t */\n\tpublic boolean isProbNegated(int i)\n\t{\n\t\treturn this.probNegated.get(i);\n\t}\n\t\n\t/**\n\t *  Replace min by max and &lt;= by &gt;= in prob.\n\t */\n\t//TODO: why not do prob also in main list?\n\tpublic void makeAllProbUp()\n\t{\n\t\tfor (int i = 0; i < relOpsProb.size(); i++) {\n\t\t\tif (relOpsProb.get(i) == Operator.P_MIN) {\n\t\t\t\trelOpsProb.remove(i);\n\t\t\t\trelOpsProb.add(i, Operator.P_MAX);\n\t\t\t    probNegated.set(i);\n\t\t\t} else if (relOpsProb.get(i) == Operator.P_LE) {\n\t\t\t\trelOpsProb.remove(i);\n\t\t\t\trelOpsProb.add(i, Operator.P_GE);\n\t\t\t    probNegated.set(i);\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns the number of reward (R) operators added so far.\n\t */\n\tpublic int rewardSize()\n\t{\n\t\treturn this.relOpsReward.size();\n\t}\n\t\n\t/**\n\t * Returns the number of probabilistic (P) operators added so far.\n\t */\n\tpublic int probSize()\n\t{\n\t\treturn this.relOpsProb.size();\n\t}\n\t\n\t/**\n\t * Returns true if the list contains the operator op.\n\t */\n\tpublic boolean contains(Operator op)\n\t{\n\t\treturn relOps.contains(op);\n\t}\n\t\n\t/**\n\t * Returns the number of numerical (=?) operators.\n\t */\n\tpublic int numberOfNumerical()\n\t{\n\t\tint num = 0;\n\t\tfor (OpRelOpBound opInfo : opInfos)\n\t\t\tif (opInfo.isNumeric())\n\t\t\t\tnum++;\n\t\treturn num;\n\t}\n\t\n\t/**\n\t * Returns the number of step-bounded (<=k) objectives.\n\t */\n\tpublic int numberOfStepBounded()\n\t{\n\t\tint num = 0;\n\t\tfor (int k : stepBounds) {\n\t\t\tif (k != -1) {\n\t\t\t\tnum++;\n\t\t\t}\n\t\t}\n\t\treturn num;\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString ret = \"\";\n\t\tfor (int i = 0; i < opInfos.size(); i++) {\n\t\t\tif (i > 0)\n\t\t\t\tret += \",\";\n\t\t\tret += opInfos.get(i);\n\t\t\tret += stepBounds.get(i);\n\t\t}\n\t\treturn ret;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/OptionsIntervalIteration.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2017-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.Map.Entry;\n\n/** Option handling for interval iteration */\npublic class OptionsIntervalIteration\n{\n\t/**\n\t * The different methods for computing upper bounds for reward computations,\n\t * and DEFAULT to choose the default method.\n\t */\n\tpublic enum BoundMethod {\n\t\tDEFAULT,\n\t\tVARIANT_1_COARSE,\n\t\tVARIANT_1_FINE,\n\t\tVARIANT_2,\n\t\tDSMPI,\n\t};\n\n\t/** The method for computing upper bounds for reward computations */\n\tprivate BoundMethod boundMethod = BoundMethod.DEFAULT;\n\n\t/** Verbose upper bound computations? (default false) */\n\tprivate boolean boundComputationVerbose = false;\n\n\t/** Select midpoint in results? (default true) */\n\tprivate boolean resultSelectMidpoint = true;\n\n\t/** Check for monotonicity in iterations? (default false) */\n\tprivate boolean checkMonotonicity = false;\n\n\t/** Enforce monotonicity in iteration from below? (default true) */\n\tprivate boolean enforceMonotonicityBelow = true;\n\n\t/** Enforce monotonicity in iteration from above? (default true) */\n\tprivate boolean enforceMonotonicityAbove = true;\n\n\t/** Manual lower bound (default none) */\n\tprivate Double manualLowerBound = null;\n\n\t/** Manual upper bound (default none) */\n\tprivate Double manualUpperBound = null;\n\n\t/* List of valid bound methods, for helper texts */\n\tfinal private static String boundMethodsList = \"default, variant-1-coarse, variant-1-fine, variant-2, dsmpi\";\n\n\t/** Constructor from options String, throws PrismException on errors */\n\tpublic OptionsIntervalIteration(String options) throws PrismException\n\t{\n\t\tfromOptionsString(options);\n\t}\n\n\t/** Static constructor from PrismComponent settings, throws PrismException on errors */\n\tpublic static OptionsIntervalIteration from(PrismComponent parent) throws PrismException\n\t{\n\t\treturn from(parent.getSettings());\n\t}\n\n\t/** Static constructor from PrismSettings, throws PrismException on errors */\n\tpublic static OptionsIntervalIteration from(PrismSettings settings) throws PrismException\n\t{\n\t\treturn new OptionsIntervalIteration(settings.getString(PrismSettings.PRISM_INTERVAL_ITER_OPTIONS));\n\t}\n\n\t/** Validate an options String, throws PrismException on errors */\n\tpublic static void validate(String optionsString) throws PrismException\n\t{\n\t\tnew OptionsIntervalIteration(optionsString);\n\t}\n\n\t/** The method for computing upper bounds for reward computations */\n\tpublic BoundMethod getBoundMethod()\n\t{\n\t\treturn boundMethod;\n\t}\n\n\t/** Verbose upper bound computations? */\n\tpublic boolean isBoundComputationVerbose()\n\t{\n\t\treturn boundComputationVerbose;\n\t}\n\n\t/** Select midpoint in results? */\n\tpublic boolean isSelectMidpointForResult()\n\t{\n\t\treturn resultSelectMidpoint;\n\t}\n\n\t/** Check for monotonicity in iterations? */\n\tpublic boolean isCheckMonotonicity()\n\t{\n\t\treturn checkMonotonicity;\n\t}\n\n\t/** Enforce monotonicity in iteration from below? */\n\tpublic boolean isEnforceMonotonicityFromBelow()\n\t{\n\t\treturn enforceMonotonicityBelow;\n\t}\n\n\t/** Enforce monotonicity in iteration from above? */\n\tpublic boolean isEnforceMonotonicityFromAbove()\n\t{\n\t\treturn enforceMonotonicityAbove;\n\t}\n\n\t/** Is there a manual lower bound? */\n\tpublic boolean hasManualLowerBound()\n\t{\n\t\treturn manualLowerBound != null;\n\t}\n\n\t/** Get manual lower bound (or null) */\n\tpublic Double getManualLowerBound()\n\t{\n\t\treturn manualLowerBound;\n\t}\n\n\t/** Is there a manual upper bound? */\n\tpublic boolean hasManualUpperBound()\n\t{\n\t\treturn manualUpperBound != null;\n\t}\n\n\t/** Get manual upper bound (or null) */\n\tpublic Double getManualUpperBound()\n\t{\n\t\treturn manualUpperBound;\n\t}\n\n\t/** Get helper text for the options */\n\tpublic static String getOptionsDescription()\n\t{\n\t\tStringBuffer sb = new StringBuffer();\n\t\tsb.append(\" boundmethod=<x>     Select upper bound heuristic for reward computations\\n\");\n\t\tsb.append(\"   <x> is one of \" + boundMethodsList + \"\\n\");\n\t\tsb.append(\" lower=<d>           Manually specify lower bound for reward computations (double value)\\n\");\n\t\tsb.append(\" upper=<d>           Manually specify upper bound for reward computations (double value)\\n\");\n\t\tsb.append(\" [no]boundverbose    Verbose output for upper bound computations (default = no)\\n\");\n\t\tsb.append(\" [no]selectmidpoint  Select midpoint between upper and lower as the result (default = yes)\\n\");\n\t\tsb.append(\" [no]monotonicbelow  Enforce monotonicity in iteration from below (default = yes)\\n\");\n\t\tsb.append(\" [no]monotonicabove  Enforce monotonicity in iteration from above (default = yes)\\n\");\n\t\tsb.append(\" [no]checkmonotonic  Check monotonicity, for testing (default = no)\\n\");\n\t\tsb.append(\"\\nExample: boundmethod=default,upper=3.0,noselectmidpoint,checkmonotonic\\n\");\n\n\t\treturn sb.toString();\n\t}\n\n\t/** Parse options string, throw on error */\n\tprivate void fromOptionsString(String options) throws PrismException\n\t{\n\t\tfor (Entry<String, String> entry : splitOptionsString(options)){\n\t\t\tString option = entry.getKey();\n\t\t\tString extra = entry.getValue();\n\n\t\t\tboolean isBooleanOption = true;\n\t\t\tswitch (option) {\n\t\t\tcase   \"boundverbose\":\n\t\t\tcase \"noboundverbose\":\n\t\t\t\tboundComputationVerbose = !option.startsWith(\"no\");\n\t\t\t\tbreak;\n\t\t\tcase   \"selectmidpoint\":\n\t\t\tcase \"noselectmidpoint\":\n\t\t\t\tresultSelectMidpoint = !option.startsWith(\"no\");\n\t\t\t\tbreak;\n\t\t\tcase   \"checkmonotonic\":\n\t\t\tcase \"nocheckmonotonic\":\n\t\t\t\tcheckMonotonicity = !option.startsWith(\"no\");\n\t\t\t\tbreak;\n\t\t\tcase   \"monotonicbelow\":\n\t\t\tcase \"nomonotonicbelow\":\n\t\t\t\tenforceMonotonicityBelow = !option.startsWith(\"no\");\n\t\t\t\tbreak;\n\t\t\tcase   \"monotonicabove\":\n\t\t\tcase \"nomonotonicabove\":\n\t\t\t\tenforceMonotonicityAbove = !option.startsWith(\"no\");\n\t\t\t\tbreak;\n\t\t\tcase \"lower\":\n\t\t\tcase \"upper\": {\n\t\t\t\tif (extra == null)\n\t\t\t\t\tthrow new PrismException(\"Missing argument to interval iteration option '\" + option + \"'\");\n\t\t\t\ttry {\n\t\t\t\t\tDouble value = Double.parseDouble(extra);\n\t\t\t\t\tif (option.equals(\"lower\")) {\n\t\t\t\t\t\tmanualLowerBound = value;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tmanualUpperBound = value;\n\t\t\t\t\t}\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Illegal argument to interval iteration option '\" + option + \"': \" + e.getMessage());\n\t\t\t\t}\n\t\t\t\tisBooleanOption = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tcase \"boundmethod\": {\n\t\t\t\tif (extra == null)\n\t\t\t\t\tthrow new PrismException(\"Missing argument to interval iteration option '\" + option + \"'\");\n\t\t\t\tswitch (extra) {\n\t\t\t\tcase \"default\":\n\t\t\t\t\tboundMethod = BoundMethod.DEFAULT;\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"variant-1-coarse\":\n\t\t\t\t\tboundMethod = BoundMethod.VARIANT_1_COARSE;\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"variant-1-fine\":\n\t\t\t\t\tboundMethod = BoundMethod.VARIANT_1_FINE;\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"variant-2\":\n\t\t\t\t\tboundMethod = BoundMethod.VARIANT_2;\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"dsmpi\":\n\t\t\t\t\tboundMethod = BoundMethod.DSMPI;\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown argument to interval iteration option '\" + option + \"', expected one of \"\n\t\t\t\t\t\t\t+ boundMethodsList);\n\t\t\t\t}\n\t\t\t\tisBooleanOption = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown interval iteration option '\" + option + \"'\");\n\t\t\t}\n\n\t\t\tif (isBooleanOption) {\n\t\t\t\tif (extra != null) {\n\t\t\t\t\tthrow new PrismException(\"Interval iteration option '\" + option + \"' has additional argument (\" + extra + \"), but is boolean option\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Split options string into list of pairs */\n\tprivate static List<Pair<String,String>> splitOptionsString(String options)\n\t{\n\t\tList<Pair<String,String>> list = new ArrayList<>();\n\t\tif (\"\".equals(options))\n\t\t\treturn list;\n\n\t\tfor (String option : options.split(\",\")) {\n\t\t\tint j = option.indexOf(\"=\");\n\t\t\tif (j == -1) {\n\t\t\t\tlist.add(new Pair<>(option.trim(), null));\n\t\t\t} else {\n\t\t\t\tlist.add(new Pair<>(option.substring(0,j).trim(), option.substring(j+1).trim()));\n\t\t\t}\n\t\t}\n\t\treturn list;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PEPA2Prism.java",
    "content": "package prism;\n\nimport java.io.File;\nimport java.io.FileWriter;\nimport java.io.IOException;\nimport java.io.InputStream;\nimport java.io.PrintStream;\n\npublic class PEPA2Prism extends PrismLanguageTranslator\n{\n\tprivate File modelFile;\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"pepa\";\n\t}\n\n\t@Override\n\tpublic void load(File file) throws PrismException\n\t{\n\t\tmodelFile = file;\n\t}\n\n\t@Override\n\tpublic void load(String s) throws PrismException\n\t{\n\t\ttry {\n\t\t\t// Create temporary file containing pepa model\n\t\t\tmodelFile = File.createTempFile(\"tempPepa\" + System.currentTimeMillis(), \".pepa\");\n\t\t\tFileWriter write = new FileWriter(modelFile);\n\t\t\twrite.write(s);\n\t\t\twrite.close();\n\t\t} catch (IOException e) {\n\t\t\tif (modelFile != null) {\n\t\t\t\tmodelFile.delete();\n\t\t\t\tmodelFile = null;\n\t\t\t}\n\t\t\tthrow new PrismException(\"Couldn't create temporary file for PEPA conversion\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void load(InputStream in) throws PrismException\n\t{\n\t\ttry {\n\t\t\t// Create temporary file containing pepa model\n\t\t\tmodelFile = File.createTempFile(\"tempPepa\" + System.currentTimeMillis(), \".pepa\");\n\t\t\tFileWriter write = new FileWriter(modelFile);\n\t\t\tint byteIn = in.read();\n\t\t\twhile (byteIn != -1) {\n\t\t\t\twrite.write(byteIn);\n\t\t\t\tbyteIn = in.read();\n\t\t\t}\n\t\t\twrite.close();\n\t\t} catch (IOException e) {\n\t\t\tif (modelFile != null) {\n\t\t\t\tmodelFile.delete();\n\t\t\t\tmodelFile = null;\n\t\t\t}\n\t\t\tthrow new PrismException(\"Couldn't create temporary file for PEPA conversion\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic String translateToString() throws PrismException\n\t{\n\t\t// Translate PEPA model to PRISM model string\n\t\tString prismModelString = null;\n\t\ttry {\n\t\t\tprismModelString = pepa.compiler.Main.compile(\"\" + modelFile);\n\t\t} catch (pepa.compiler.InternalError e) {\n\t\t\tthrow new PrismException(\"Could not import PEPA model:\\n\" + e.getMessage());\n\t\t}\n\t\treturn prismModelString;\n\t}\n\n\t@Override\n\tpublic void translate(PrintStream out) throws PrismException\n\t{\n\t\tout.print(translateToString());\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Pair.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.Map.Entry;\n\n/**\n * Simple class to store a pair of values.\n */\npublic class Pair<X,Y> implements Entry<X, Y>\n{\n\tpublic X first;\n\tpublic Y second;\n\t\n\tpublic Pair(X first, Y second)\n\t{\n\t\tthis.first = first;\n\t\tthis.second = second;\n\t}\n\n\t@Override\n\tpublic X getKey() {\n\t\treturn first;\n\t}\n\n\t@Override\n\tpublic Y getValue() {\n\t\treturn second;\n\t}\n\n\t@Override\n\tpublic Y setValue(Y value) {\n\t\tsecond = value;\n\t\treturn second;\n\t}\n\t\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tfinal int prime = 31;\n\t\tint result = 1;\n\t\tresult = prime * result + ((first == null) ? 0 : first.hashCode());\n\t\tresult = prime * result + ((second == null) ? 0 : second.hashCode());\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (this == obj)\n\t\t\treturn true;\n\t\tif (obj == null)\n\t\t\treturn false;\n\t\tif (getClass() != obj.getClass())\n\t\t\treturn false;\n\t\tPair<?, ?> other = (Pair<?, ?>) obj;\n\t\tif (first == null) {\n\t\t\tif (other.first != null)\n\t\t\t\treturn false;\n\t\t} else if (!first.equals(other.first))\n\t\t\treturn false;\n\t\tif (second == null) {\n\t\t\tif (other.second != null)\n\t\t\t\treturn false;\n\t\t} else if (!second.equals(other.second))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"(\" + first + \",\" + second + \")\"; \n\t}\n\n\t// Utility functions\n\n\t/**\n\t * Static method to compare two pairs containing the same Comparable objects.\n\t */\n\tpublic static <A extends Comparable,B extends Comparable> int compare(Pair<A,B> c, Pair<A,B> d)\n\t{\n\t\tint comp = c.first.compareTo(d.first);\n\t\treturn (comp != 0) ? comp : c.second.compareTo(d.second);\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PermutedLexicographicComparator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.Arrays;\nimport java.util.Comparator;\n\n/**\n * A class that allows to compare points w.r.g. a lexicographic order.\n * The order of elements is given by the array {@code dimensionPermutation}\n * passed in the constructor {@link #PermutedLexicographicComparator(int[],boolean[])}.\n * <br>\n * Note that the comparator is only capable of comparing points with equal\n * dimension. This probably violates the specification of the {@link Comparator}\n * class, but it shouldn't be any problem as comparing points of different dimensions\n * makes no sense in our case.\n */\npublic class PermutedLexicographicComparator implements Comparator<Point>\n{\n\tprivate int[] permutation;\n\tprivate boolean[] increasing;\n\t\n\t/**\n\t * Creates a new instance of the comparator.\n\t * @param dimensionPermutation The order of coordinates, the length of\n\t * the array must be equal to the dimension of points to be compared. For example,\n\t * supposing the dimension of points to compare is 3, the array [2,0,1] says\n\t * that the lexicographic order should be used in which the last coordinate\n\t * has the highest priority, and then the first two follow.\n\t * @param increasing if increasing[i] is true, then the ith dimension\n\t * will be used such that the points with the smaller values go first, otherwise they go last\n\t */\n\tpublic PermutedLexicographicComparator(int[] dimensionPermutation, boolean[] increasing) {\n\t\t//check that the array is a valid permutation\n\t\tint[] clone = dimensionPermutation.clone();\n\t\t//TODO check size etc.\n\t\tthis.increasing = increasing;\n\t\tArrays.sort(clone);\n\t\tfor(int i = 0; i < clone.length; i++)\n\t\t\tif (clone[i] != i)\n\t\t\t\tthrow new IllegalArgumentException(\"The array is not a valid permutation\");\n\t\tthis.permutation = dimensionPermutation;\n\t}\n\n\t@Override\n\tpublic int compare(Point o1, Point o2)\n\t{\n\t\t//check if the input is allowed;\n\t\tif (o1.getDimension() > permutation.length\n\t\t\t\t|| o2.getDimension() > permutation.length)\n\t\t\tthrow new ClassCastException(\"The dimension of the point is greater that comparator's dimension\");\n\t\t\n\t\tif(o1.isCloseTo(o2))\n\t\t\treturn 0;\n\t\t\n\t\treturn compare(o1,o2,0);\n\t}\n\t\n\t/**\n\t * Compares two points, starting with the coordinate with the\n\t * {@code i}-th highest priority. \n\t * @param o1\n\t * @param o2\n\t * @param i\n\t * @return\n\t */\n\tprotected int compare(Point o1, Point o2, int i)\n\t{\n\t\tint dim = this.permutation[i];\n\t\tif ( o1.getCoord(dim) < o2.getCoord(dim))\n\t\t\treturn (increasing[dim]) ? -1 : 1;\n\t\telse if (o1.getCoord(dim) > o2.getCoord(dim))\n\t\t\treturn (increasing[dim]) ? 1 : -1;\n\t\telse return compare(o1, o2, i+1);\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Point.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\n\n\npublic class Point\n{\t\n\t/**\n\t * A number used as a basis when neglecting roundoff errors in tests\n\t * for equality.\n\t */\n\tprotected static final double SMALL_NUMBER = 10e-6;\n\t\n\t/**\n\t * Internal storage for the coordinates\n\t */\n\tprivate double[] coords;\n\n\t/**\n\t * Creates a point of dimension {@code dimensions} in which all\n\t * coordinates are initially set to 0.\n\t * @param dimensions\n\t */\n\tpublic Point(int dimensions)\n\t{\n\t\tthis.coords = new double[dimensions];\n\t}\n\n\t/**\n\t * Creates a point whose dimension is equal to the length of the\n\t * array provided and whose values are taken from the array.\n\t * @param coords The initial values.\n\t */\n\tpublic Point(double[] coords)\n\t{\n\t\tthis.coords = coords;\n\t}\n\n\t/**\n\t * gets the calue of the {@code dim}-th coordinate.\n\t * @param dim\n\t * @return\n\t */\n\tpublic double getCoord(int dim)\n\t{\n\t\treturn coords[dim];\n\t}\n\n\t/**\n\t * sets the value of the {@code dim}-th coordinate to {@code val}\n\t * @param dim Which coordinate to set.\n\t * @param val What value to set.\n\t */\n\tpublic void setCoord(int dim, double val)\n\t{\n\t\tthis.coords[dim] = val;\n\t}\n\n\t/**\n\t * Gets the number of dimension this point has.\n\t * @return\n\t */\n\tpublic int getDimension()\n\t{\n\t\treturn coords.length;\n\t}\n\n\t/**\n\t * Determines if two points are equals. Two points are equal if they have\n\t * the same dimension and all their coordinates are precisely equal. Use\n\t * {@link #isCloseTo(Point)} if a numerical error could have been introduced\n\t * when computing the point and so a tolerance is needed.\n\t */\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (obj == null || !(obj instanceof Point))\n\t\t\treturn false;\n\t\telse {\n\t\t\tPoint second = (Point) obj;\n\n\t\t\tif (second.getDimension() != this.getDimension())\n\t\t\t\treturn false;\n\n\t\t\tfor (int i = 0; i < this.getDimension(); i++) {\n\t\t\t\tif (second.getCoord(i) != this.getCoord(i))\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t\t//System.err.println(\"comparing \" + this + \" and \" + second + \" with the result \" + (x == second.getX() && y == second.getY()));\n\t\t\treturn true;\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\treturn (int) (this.coords[0] * 100);\n\t}\n\t\n\n\t/**\n\t * Determines if this point is very close to the point {@code p}, where\n\t * two points are very close if all of their coordinated differ at most by\n\t * {@link #SMALL_NUMBER}. When a point is computed using a numerical method\n\t * and thus can be rounded off, this method is a good replacement for {@link #equals(Object)}\n\t * \n\t * @param p\n\t * @return\n\t */\n\tpublic boolean isCloseTo(Point p)\n\t{\n\t\tif (p.getDimension() != this.getDimension())\n\t\t\treturn false;\n\n\t\tfor (int i = 0; i < this.getDimension(); i++) {\n\t\t\tif (Math.abs(p.getCoord(i) - this.getCoord(i)) >= SMALL_NUMBER)\n\t\t\t\treturn false;\n\t\t}\n\t\t//System.err.println(\"comparing \" + this + \" and \" + second + \" with the result \" + (x == second.getX() && y == second.getY()));\n\t\treturn true;\n\t}\n\n\t/**\n \t * Determines if this point is pointwise smaller than {@code p+SMALL_NUMBER}.\n \t * \n \t */\n\tpublic boolean isCoveredBy(Point p)\n\t{\n\t\tif (p.getDimension() != this.getDimension())\n\t\t\treturn false;\n\n\t\tfor (int i = 0; i < this.getDimension(); i++) {\n\t\t\tif (p.getCoord(i) + SMALL_NUMBER - this.getCoord(i) < 0)\n\t\t\t\treturn false;\n\t\t}\n\t\t//System.err.println(\"comparing \" + this + \" and \" + second + \" with the result \" + (x == second.getX() && y == second.getY()));\n\t\treturn true;\n\t}\n\n\t\n\n\t/**\n\t * Returns the point in which the coordinates are reweighted so that the\n\t * norm of the point is equal to 1.\n\t * @return\n\t */\n\tpublic Point normalize()\n\t{\n\t\tdouble[] ret = new double[this.coords.length];\n\n\t\tdouble sum = 0;\n\t\tfor (Double d : this.coords)\n\t\t\tsum += Math.abs(d);\n\t\t\n\t\t//TODO throw exception when sum is 0?\n\t\tfor (int i = 0; i < ret.length; i++) {\n\t\t\tret[i] = Math.abs(this.coords[i]) / sum;\n\t\t\tif (ret[i] < 1e-10)\n\t\t\t\tret[i] = 0;\n\t\t}\n\n\t\treturn new Point(ret);\n\t}\n\n\t/**\n\t * Returns the Euclidean distance from this point to {@code p}\n\t * @param p The point to compute the distance from.\n\t * @return The Euclidean distance.\n\t * @throws IllegalArgumentException Thrown when the points have different dimensions\n\t */\n\tpublic double distanceTo(Point p) throws IllegalArgumentException\n\t{\n\t\tif (p.getDimension() != this.getDimension())\n\t\t\tthrow new IllegalArgumentException(\"The method Point.distanceTo(Point) can be only applied to points of equal dimensions\");\n\n\t\tdouble result = 0.0;\n\t\tfor (int i = 0; i < this.getDimension(); i++) {\n\t\t\tresult += Math.pow((this.getCoord(i) - p.getCoord(i)), 2.0);\n\t\t}\n\t\treturn Math.sqrt(result);\n\t}\n\t\n\t/**\n\t * Returns the euclidean norm of this point.\n\t */\n\tpublic double euclideanNorm()\n\t{\n\t\treturn this.distanceTo(new Point(this.getDimension()));\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn Arrays.toString(coords).replace('[', '(').replace(']', ')');\n\t}\n\t\n\t/**\n\t * Returns a point with the same coordinates as this point.\n\t */\n\tpublic Point clone() {\n\t\treturn new Point(this.coords.clone());\n\t}\n\t\n\t/**\n\t * Returns the vector representing the coordinates of this point. It is\n\t * a copy of the vector stored internally, so it can be modified without\n\t * any problem.\n\t * \n\t * @return\n\t */\n\tpublic double[] getCoords()\n\t{\n\t\treturn this.coords.clone();\n\t}\n\n\t/**\n\t * Returns the point obtained from the current one by projecting it to the\n\t * dimensions specified by {@code b}.\n\t * @param b A bitset with the size same as the dimension equal to the one of this point.\n\t * @return Projected point\n\t */\n\tpublic Point project(BitSet b)\n\t{\n\t\tArrayList<Double> al = new ArrayList<Double>();\n\t\tfor (int i = 0; i < this.getDimension(); i++)\n\t\t\tif (b.get(i))\n\t\t\t\tal.add(this.getCoord(i));\n\t\t\n\t\tdouble[] ar = new double[al.size()];\n\t\tfor (int i = 0; i < ar.length; i++)\n\t\t\tar[i] = al.get(i);\n\t\t\n\t\treturn new Point(ar);\n\t}\n\n\t/**\n\t *  This methods ensures that the point's values corresponds to the properties\n\t *  the user did input. Namely, (i) the order of properties is restored, and\n\t *  (ii) when the rewards were minimizing, the value\n\t *  is multiplied by -1, and when the probabilities were minimizing,\n\t *  a new value is obtained by 1-value.\n\t * @return\n\t */\n\tpublic Point toRealProperties(OpsAndBoundsList obl)\n\t{\n\t\tdouble[] oldCoords = coords.clone();\n\t\tdouble[] newCoords = new double[oldCoords.length];\n\n\t\tfor (int i = 0; i < obl.probSize(); i++) {\n\t\t\tint newIndex = obl.getOrigPositionProb(i);\n\t\t\tif (obl.isProbNegated(i))\n\t\t\t\tnewCoords[newIndex] = 1-oldCoords[i];\n\t\t\telse\n\t\t\t\tnewCoords[newIndex] = oldCoords[i];\n\n\t\t}\n\n\t\tfor (int i = 0; i < obl.rewardSize(); i++) {\n\t\t\tint newIndex = obl.getOrigPositionReward(i);\n\t\t\tif (obl.getRewardOperator(i) == Operator.R_MIN\n\t\t\t\t\t|| obl.getRewardOperator(i) == Operator.R_LE)\n\t\t\t\tnewCoords[newIndex] = -oldCoords[i + obl.probSize()];\t\t\t\n\t\t\telse\n\t\t\t\tnewCoords[newIndex] = oldCoords[i + obl.probSize()];\t\t\t\n\n\t\t}\n\t\t\n\t\treturn new Point(newCoords);\n\t}\n\t\n\t/**\n\t * True if all coordinates are exactly 0.\n\t * @return\n\t */\n\tpublic boolean isZero() {\n\t\tfor (int i = 0; i < this.getDimension(); i++)\n\t\t\tif (this.getCoord(i) != 0)\n\t\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Preprocessor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.BufferedReader;\nimport java.io.File;\nimport java.io.FileReader;\nimport java.io.IOException;\nimport java.util.Stack;\nimport java.util.Vector;\n\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ForLoop;\nimport parser.type.Type;\nimport parser.type.TypeInt;\n\npublic class Preprocessor\n{\n\tprivate final static char DELIMITER = '#';\n\tprivate final static boolean IGNORE_COMMENTS = true;\n\n\t// prism\n\tprivate Prism prism;\n\n\t// files\n\tprivate File modelFile;\n\n\t// preprocessing (PP) stuff\n\tprivate int numPPExprs;\n\tprivate String ppExprStrings[];\n\tprivate String ppExprs[];\n\tprivate int ppExprLines[];\n\tprivate String lastString;\n\n\t// interpreter stuff\n\tprivate int pc; // program counter\n\tprivate Stack<Object> stack; // control flow stack\n\tprivate String output; // output string\n\tprivate boolean outputEnabled; // output enabling flag\n\tprivate Vector<String> varNames; // variable names\n\tprivate Vector<Type> varTypes; // variable types\n\tprivate Vector<Integer> varScopes; // variable scopes\n\tprivate Values values; // variable values\n\tprivate int paramCounter; // how many paramaters found so far\n\n\tprivate String params[];\n\n\t// constructor\n\n\tpublic Preprocessor(Prism p, File mf)\n\t{\n\t\tprism = p;\n\t\tmodelFile = mf;\n\t}\n\n\tpublic void setParameters(String args[])\n\t{\n\t\tparams = args;\n\t}\n\n\t// main method: do preprocessing\n\n\tpublic String preprocess() throws PrismException\n\t{\n\t\t// see how many preprocessing expressions there are\n\t\tcountPPExprs();\n\t\t// and bail out if none\n\t\tif (numPPExprs == 0)\n\t\t\treturn null;\n\n\t\t// do preprocessing\n\t\tstorePPExprs();\n\t\tinterpret();\n\n\t\treturn output;\n\t}\n\n\t// count the number of preprocessing expressions\n\n\tprivate void countPPExprs() throws PrismException\n\t{\n\t\tString s, s2;\n\t\tint i, count, lineNum = 0;\n\n\t\tnumPPExprs = 0;\n\t\ttry (BufferedReader in = new BufferedReader(new FileReader(modelFile))) {\n\t\t\t// read lines one by one\n\t\t\ts = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\t// strip any comments\n\t\t\t\ti = (IGNORE_COMMENTS) ? s.indexOf(\"//\") : -1;\n\t\t\t\ts2 = (i != -1) ? s.substring(0, i) : s;\n\t\t\t\t// count delimiters\n\t\t\t\tcount = 0;\n\t\t\t\ti = -1;\n\t\t\t\twhile ((i = s2.indexOf(DELIMITER, i + 1)) != -1)\n\t\t\t\t\tcount++;\n\t\t\t\tif (count % 2 != 0)\n\t\t\t\t\tthrow new PrismException(\"Unterminated preprocessing expression at line \" + lineNum);\n\t\t\t\tnumPPExprs += (count / 2);\n\t\t\t\t// read next line\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + modelFile + \"\\\"\");\n\t\t}\n\t}\n\n\t// store the preprocessing expressions and related info\n\n\tprivate void storePPExprs() throws PrismException\n\t{\n\t\tBufferedReader in;\n\t\tString s, s1, s2, s3, text, ss[];\n\t\tint i, j, n, count, lineNum = 0;\n\n\t\t// allocate arrays\n\t\tppExprStrings = new String[numPPExprs];\n\t\tppExprs = new String[numPPExprs];\n\t\tppExprLines = new int[numPPExprs];\n\n\t\ttry {\n\t\t\tcount = 0;\n\t\t\ttext = \"\";\n\t\t\t// open file for reading\n\t\t\tin = new BufferedReader(new FileReader(modelFile));\n\t\t\t// read lines one by one\n\t\t\ts = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\t// split into non-comment(s1)/comment(s2)\n\t\t\t\ti = (IGNORE_COMMENTS) ? s.indexOf(\"//\") : -1;\n\t\t\t\ts1 = (i != -1) ? s.substring(0, i) : s;\n\t\t\t\ts2 = (i != -1) ? s.substring(i) : \"\";\n\t\t\t\t// if there are delimiters no delimiters, move on\n\t\t\t\ti = s1.indexOf(DELIMITER);\n\t\t\t\tif (i == -1) {\n\t\t\t\t\ttext += s1;\n\t\t\t\t\ttext += s2;\n\t\t\t\t\ttext += \"\\n\";\n\t\t\t\t} else {\n\t\t\t\t\t// strip off stuff before first and after last delimiter\n\t\t\t\t\tj = s1.lastIndexOf(DELIMITER);\n\t\t\t\t\ts3 = s1.substring(i, j + 1);\n\t\t\t\t\ts2 = s1.substring(j + 1) + s2;\n\t\t\t\t\ts1 = s1.substring(0, i);\n\t\t\t\t\t// add trailing space so that split() catches any trailing empty pairs of delimiters\n\t\t\t\t\ts3 += \" \";\n\t\t\t\t\t// go through delimiters\n\t\t\t\t\tss = s3.split(\"\" + DELIMITER);\n\t\t\t\t\tn = (ss.length - 1) / 2;\n\t\t\t\t\t// add first part of line to text\n\t\t\t\t\t// (unless this line contains just one pp expr and white space)\n\t\t\t\t\tif (!(n == 1 && s1.trim().length() == 0 && s2.trim().length() == 0))\n\t\t\t\t\t\ttext += s1;\n\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\ttext += ss[2 * i];\n\t\t\t\t\t\tppExprStrings[count] = text;\n\t\t\t\t\t\tppExprs[count] = ss[2 * i + 1];\n\t\t\t\t\t\tppExprLines[count] = lineNum;\n\t\t\t\t\t\tcount++;\n\t\t\t\t\t\ttext = \"\";\n\t\t\t\t\t}\n\t\t\t\t\t// add last part of line to text\n\t\t\t\t\t// (unless this line contains just one pp expr and white space)\n\t\t\t\t\tif (!(n == 1 && s1.trim().length() == 0 && s2.trim().length() == 0))\n\t\t\t\t\t\ttext += s2 + \"\\n\";\n\t\t\t\t}\n\t\t\t\t// read next line\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t\tlastString = text;\n\t\t\t// close file\n\t\t\tin.close();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + modelFile + \"\\\"\");\n\t\t}\n\t}\n\n\t// go through the preprocessing expressions, interpreting them\n\n\tprivate void interpret() throws PrismException\n\t{\n\t\tString s;\n\n\t\t// initialise interpreter\n\t\toutput = \"\";\n\t\toutputEnabled = true;\n\t\tpc = 0;\n\t\tstack = new Stack<Object>();\n\t\tvarNames = new Vector<String>();\n\t\tvarTypes = new Vector<Type>();\n\t\tvarScopes = new Vector<Integer>();\n\t\tvalues = new Values();\n\t\tparamCounter = 0;\n\n\t\t// main control flow loop\n\t\ttry {\n\t\t\twhile (pc < numPPExprs) {\n\n\t\t\t\t// add text preceding this preprocessing expression to output\n\t\t\t\tif (outputEnabled)\n\t\t\t\t\toutput += ppExprStrings[pc];\n\n\t\t\t\t// process current preprocessing expression\n\t\t\t\ts = ppExprs[pc].trim();\n\n\t\t\t\t// parameter\n\t\t\t\tif (s.indexOf(\"param int \") == 0) {\n\t\t\t\t\ts = s.substring(10).trim();\n\t\t\t\t\tinterpretConstant(s);\n\t\t\t\t} else if (s.indexOf(\"const \") == 0) {\n\t\t\t\t\t// old notation - backwards compatability\n\t\t\t\t\ts = s.substring(6).trim();\n\t\t\t\t\tinterpretConstant(s);\n\t\t\t\t}\n\t\t\t\t// for loops\n\t\t\t\telse if (s.indexOf(\"for \") == 0) {\n\t\t\t\t\ts = s.substring(4).trim();\n\t\t\t\t\tinterpretForLoop(s, \"\");\n\t\t\t\t} else if (s.indexOf(\"& \") == 0) {\n\t\t\t\t\ts = s.substring(2).trim();\n\t\t\t\t\tinterpretForLoop(s, \"&\");\n\t\t\t\t} else if (s.indexOf(\"| \") == 0) {\n\t\t\t\t\ts = s.substring(2).trim();\n\t\t\t\t\tinterpretForLoop(s, \"|\");\n\t\t\t\t} else if (s.indexOf(\"* \") == 0) {\n\t\t\t\t\ts = s.substring(2).trim();\n\t\t\t\t\tinterpretForLoop(s, \"*\");\n\t\t\t\t} else if (s.indexOf(\"+ \") == 0) {\n\t\t\t\t\ts = s.substring(2).trim();\n\t\t\t\t\tinterpretForLoop(s, \"+\");\n\t\t\t\t} else if (s.indexOf(\", \") == 0) {\n\t\t\t\t\ts = s.substring(2).trim();\n\t\t\t\t\tinterpretForLoop(s, \",\");\n\t\t\t\t} else if (s.indexOf(\"; \") == 0) {\n\t\t\t\t\ts = s.substring(2).trim();\n\t\t\t\t\tinterpretForLoop(s, \";\");\n\t\t\t\t}\n\t\t\t\t// end\n\t\t\t\telse if (s.equals(\"end\")) {\n\t\t\t\t\tinterpretEnd();\n\t\t\t\t}\n\t\t\t\t// empty expression\n\t\t\t\telse if (s.length() == 0) {\n\t\t\t\t\t// move to next statement\n\t\t\t\t\tpc++;\n\t\t\t\t}\n\t\t\t\t// anything else, i.e. arbitrary expression\n\t\t\t\telse {\n\t\t\t\t\tinterpretExpression(s);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add final piece of text to output\n\t\t\tif (outputEnabled)\n\t\t\t\toutput += lastString;\n\t\t} catch (PrismException e) {\n\t\t\tthrow new PrismException(e.getMessage() + \" (preprocessing expression \\\"\" + ppExprs[pc] + \"\\\" at line \" + ppExprLines[pc] + \")\");\n\t\t}\n\t}\n\n\tprivate void interpretConstant(String s) throws PrismException\n\t{\n\t\tint i;\n\t\tString name;\n\t\tExpression expr;\n\n\t\t// if not currently outputting, just skip this\n\t\tif (!outputEnabled) {\n\t\t\tpc++;\n\t\t\treturn;\n\t\t}\n\n\t\t// get constant name - terminated by \"=\", white space or end of expression\n\t\ti = s.indexOf('=');\n\t\tif (i == -1)\n\t\t\ti = s.indexOf(' ');\n\t\tif (i == -1)\n\t\t\ti = s.indexOf('\\t');\n\t\tif (i == -1)\n\t\t\ti = s.length();\n\t\tname = s.substring(0, i).trim();\n\t\t// check name is valid identifier\n\t\tif (!name.matches(\"[_a-zA-Z]([_a-zA-Z0-9])*\"))\n\t\t\tthrow new PrismException(\"Invalid constant name \\\"\" + name + \"\\\"\");\n\t\t// and that it doesn't already exist\n\t\tif (varNames.contains(name))\n\t\t\tthrow new PrismException(\"Duplicated variable/constant \\\"\" + name + \"\\\"\");\n\t\t// see if a value if defined for it\n\t\texpr = null;\n\t\ts = s.substring(i).trim();\n\t\tif (s.length() > 0) {\n\t\t\tif (s.charAt(0) != '=') {\n\t\t\t\tthrow new PrismException(\"Syntax error in constant definition\");\n\t\t\t}\n\t\t\t// if so, get expression for value definition\n\t\t\ts = s.substring(1).trim();\n\t\t\t// parse expression, do some checks\n\t\t\texpr = Prism.parseSingleExpressionString(s);\n\t\t\texpr = (Expression) expr.findAllVars(varNames, varTypes);\n\t\t\texpr.typeCheck();\n\t\t\texpr.semanticCheck();\n\t\t}\n\t\t// set up new variable in interpreter\n\t\tvarNames.add(name);\n\t\tvarTypes.add(TypeInt.getInstance());\n\t\tvarScopes.add(stack.size());\n\t\tif (expr != null) {\n\t\t\tvalues.addValue(name, Integer.valueOf(expr.evaluateInt(null, values)));\n\t\t} else {\n\t\t\tif (params.length <= paramCounter + 1)\n\t\t\t\tthrow new PrismException(\"No value provided for undefined preprocessor constant \\\"\" + name + \"\\\"\");\n\t\t\tvalues.addValue(name, Integer.valueOf(Integer.parseInt(params[++paramCounter])));\n\t\t}\n\t\t// move to next statement\n\t\tpc++;\n\t}\n\n\tprivate void interpretForLoop(String s, String between) throws PrismException\n\t{\n\t\tForLoop fl;\n\n\t\t// if not currently outputting, just stick a dummy for loop on the stack and move on\n\t\tif (!outputEnabled) {\n\t\t\tstack.push(\"Dummy for loop\");\n\t\t\tpc++;\n\t\t\treturn;\n\t\t}\n\n\t\t// parse for loop, do some checks\n\t\tfl = prism.parseForLoopString(s);\n\t\tif (varNames.contains(fl.getLHS()))\n\t\t\tthrow new PrismException(\"Duplicated variable/constant \\\"\" + fl.getLHS() + \"\\\"\");\n\t\tfl = (ForLoop) fl.findAllVars(varNames, varTypes);\n\t\tfl.typeCheck();\n\t\tfl.semanticCheck();\n\t\t// set up more info and then put on stack\n\t\tfl.setPC(pc + 1);\n\t\tfl.setBetween(between);\n\t\tstack.push(fl);\n\t\t// set up new variable in interpreter\n\t\tvarNames.add(fl.getLHS());\n\t\tvarTypes.add(TypeInt.getInstance());\n\t\tvarScopes.add(stack.size());\n\t\tvalues.addValue(fl.getLHS(), Integer.valueOf(fl.getFrom().evaluateInt(null, values)));\n\t\t// if for loop trivially not satisfied, set output flag to false\n\t\tif (fl.getFrom().evaluateInt(null, values) > fl.getTo().evaluateInt(null, values)) {\n\t\t\toutputEnabled = false;\n\t\t}\n\n\t\t// move to next statement\n\t\tpc++;\n\t}\n\n\tprivate void interpretEnd() throws PrismException\n\t{\n\t\tint i, j;\n\t\tForLoop fl;\n\n\t\t// make sure there is something to end\n\t\tif (stack.empty())\n\t\t\tthrow new PrismException(\"Surplus \\\"end\\\" statement\");\n\n\t\t// end of for loop\n\t\tif (stack.peek() instanceof ForLoop) {\n\t\t\tfl = (ForLoop) stack.peek();\n\t\t\t// remove variables that will become out of scope (except loop counter)\n\t\t\ti = stack.size();\n\t\t\tj = 0;\n\t\t\twhile (j < varNames.size()) {\n\t\t\t\tif (varScopes.get(j) >= i && !varNames.get(j).equals(fl.getLHS())) {\n\t\t\t\t\tvarNames.removeElementAt(j);\n\t\t\t\t\tvarTypes.removeElementAt(j);\n\t\t\t\t\tvarScopes.removeElementAt(j);\n\t\t\t\t\tvalues.removeValue(j);\n\t\t\t\t} else {\n\t\t\t\t\tj++;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// if not outputting (which means that the condition for the for loop was initially false)\n\t\t\t// the end for loop\n\t\t\tif (!outputEnabled) {\n\t\t\t\t// reset flag\n\t\t\t\toutputEnabled = true;\n\t\t\t\t// remove loop counter variable\n\t\t\t\tj = varNames.indexOf(fl.getLHS());\n\t\t\t\tvarNames.removeElementAt(j);\n\t\t\t\tvarTypes.removeElementAt(j);\n\t\t\t\tvarScopes.removeElementAt(j);\n\t\t\t\tvalues.removeValue(j);\n\t\t\t\t// remove for loop from stack\n\t\t\t\tstack.pop();\n\t\t\t\t// move to next statement\n\t\t\t\tpc++;\n\t\t\t}\n\t\t\t// otherwise increment to see if we have finished yet\n\t\t\telse {\n\t\t\t\t// increment for loop\n\t\t\t\ti = (int) values.getValueOf(fl.getLHS());\n\t\t\t\ti += fl.getStep().evaluateInt(null, values);\n\t\t\t\t// if loop is not finished...\n\t\t\t\tif (i <= fl.getTo().evaluateInt(null, values)) {\n\t\t\t\t\t// update value of loop counter\n\t\t\t\t\tvalues.setValue(fl.getLHS(), Integer.valueOf(i));\n\t\t\t\t\t// add \"between\" character to text\n\t\t\t\t\toutput += fl.getBetween();\n\t\t\t\t\t// go back to start of loop\n\t\t\t\t\tpc = fl.getPC();\n\t\t\t\t}\n\t\t\t\t// if loop is finished...\n\t\t\t\telse {\n\t\t\t\t\t// remove loop counter variable\n\t\t\t\t\tj = varNames.indexOf(fl.getLHS());\n\t\t\t\t\tvarNames.removeElementAt(j);\n\t\t\t\t\tvarTypes.removeElementAt(j);\n\t\t\t\t\tvarScopes.removeElementAt(j);\n\t\t\t\t\tvalues.removeValue(j);\n\t\t\t\t\t// remove for loop from stack\n\t\t\t\t\tstack.pop();\n\t\t\t\t\t// move to next statement\n\t\t\t\t\tpc++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// if not currently outputting, just pop the stack and move on\n\t\telse if (stack.peek() instanceof String && !outputEnabled) {\n\t\t\tstack.pop();\n\t\t\tpc++;\n\t\t}\n\n\t\telse {\n\t\t\tthrow new PrismException(\"Preprocessor stack error\");\n\t\t}\n\t}\n\n\tprivate void interpretExpression(String s) throws PrismException\n\t{\n\t\tExpression expr;\n\n\t\t// if not currently outputting, just skip this\n\t\tif (!outputEnabled) {\n\t\t\tpc++;\n\t\t\treturn;\n\t\t}\n\n\t\t// parse expression, do some checks\n\t\texpr = Prism.parseSingleExpressionString(s);\n\t\texpr = (Expression) expr.findAllVars(varNames, varTypes);\n\t\texpr.typeCheck();\n\t\texpr.semanticCheck();\n\t\t// add \n\t\toutput += \"\" + expr.evaluate(null, values);\n\t\t// move to next statement\n\t\tpc++;\n\t}\n\n\tpublic static void main(String[] args)\n\t{\n\t\tif (args.length < 1)\n\t\t\treturn;\n\t\ttry {\n\t\t\tPrism p = new Prism(new PrismFileLog(\"stdout\"));\n\t\t\tPreprocessor pp = new Preprocessor(p, new File(args[0]));\n\t\t\tpp.setParameters(args);\n\t\t\tString s = pp.preprocess();\n\t\t\tif (s == null) {\n\t\t\t\tSystem.out.println(\"Error: No preprocessing information.\");\n\t\t\t} else {\n\t\t\t\tSystem.out.print(s);\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tSystem.err.println(\"Error: \" + e.getMessage());\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/Prism.java",
    "content": "//==============================================================================\n//\t\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.ByteArrayInputStream;\nimport java.io.File;\nimport java.io.FileInputStream;\nimport java.io.FileNotFoundException;\nimport java.nio.file.Files;\nimport java.nio.file.Path;\nimport java.nio.file.Paths;\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.regex.Pattern;\n\nimport common.iterable.Range;\nimport explicit.CTMC;\nimport explicit.CTMCModelChecker;\nimport explicit.ConstructModel;\nimport explicit.DTMC;\nimport explicit.DTMCModelChecker;\nimport explicit.ExplicitFiles2Model;\nimport explicit.ExplicitFiles2Rewards;\nimport explicit.FastAdaptiveUniformisation;\nimport explicit.FastAdaptiveUniformisationModelChecker;\nimport explicit.ModelModelGenerator;\nimport io.UMBImporter;\nimport io.ExplicitModelImporter;\nimport io.ModelExportOptions;\nimport io.ModelExportTask;\nimport io.ModelExportFormat;\nimport jdd.JDD;\nimport jdd.JDDLibrary;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport param.ParamMode;\nimport param.ParamModelChecker;\nimport parser.PrismParser;\nimport parser.State;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ForLoop;\nimport parser.ast.LabelList;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport pta.DigitalClocks;\nimport pta.PTAModelChecker;\nimport simulator.GenerateSimulationPath;\nimport simulator.ModulesFileModelGenerator;\nimport simulator.SimulatorEngine;\nimport simulator.method.SimulationMethod;\nimport strat.Strategy;\nimport strat.StrategyExportOptions;\nimport strat.StrategyExportOptions.StrategyExportType;\nimport strat.StrategyGenerator;\nimport symbolic.build.ExplicitFiles2MTBDD;\nimport io.PrismExplicitImporter;\nimport symbolic.build.ExplicitModel2MTBDD;\nimport symbolic.build.MTBDD2ExplicitModel;\nimport symbolic.build.ModelGenerator2MTBDD;\nimport symbolic.build.Modules2MTBDD;\nimport symbolic.comp.ECComputer;\nimport symbolic.comp.ModelChecker;\nimport symbolic.comp.ProbModelChecker;\nimport symbolic.comp.SCCComputer;\nimport symbolic.comp.StateModelChecker;\nimport symbolic.comp.StochModelChecker;\nimport symbolic.model.Model;\nimport symbolic.model.ModelSymbolic;\nimport symbolic.model.NondetModel;\nimport symbolic.states.StateList;\nimport symbolic.states.StateListMTBDD;\nimport symbolic.states.StateValues;\n\n/**\n * Main class for all PRISM's core functionality.\n * This is independent of the user interface (command line or gui).\n */\npublic class Prism extends PrismComponent implements PrismSettingsListener\n{\n\t/** PRISM version (e.g. \"4.0.3\"). Read from prism.Version. */\n\tprivate static String version = prism.Version.versionString;\n\n\t/** Optional PRISM version suffix (e.g. \"dev\", \"beta\"). Read from prism.Version. */\n\tprivate static String versionSuffix = prism.Version.versionSuffixString;\n\n\t//------------------------------------------------------------------------------\n\t// Constants\n\t//------------------------------------------------------------------------------\n\n\t// underlying computation engine\n\tpublic static final int MTBDD = 1;\n\tpublic static final int SPARSE = 2;\n\tpublic static final int HYBRID = 3;\n\tpublic static final int EXPLICIT = 4;\n\tprivate static String[] engineStrings = { \"?\", \"MTBDD\", \"Sparse\", \"Hybrid\", \"Explicit\" };\n\n\t// methods for solving linear equation systems\n\tpublic static final int POWER = 1;\n\tpublic static final int JACOBI = 2;\n\tpublic static final int GAUSSSEIDEL = 3;\n\tpublic static final int BGAUSSSEIDEL = 4;\n\tpublic static final int PGAUSSSEIDEL = 5;\n\tpublic static final int BPGAUSSSEIDEL = 6;\n\tpublic static final int JOR = 7;\n\tpublic static final int SOR = 8;\n\tpublic static final int BSOR = 9;\n\tpublic static final int PSOR = 10;\n\tpublic static final int BPSOR = 11;\n\n\t// methods for solving MDPs\n\tpublic static final int MDP_VALITER = 1;\n\tpublic static final int MDP_GAUSSSEIDEL = 2;\n\tpublic static final int MDP_POLITER = 3;\n\tpublic static final int MDP_MODPOLITER = 4;\n\tpublic static final int MDP_LP = 5;\n\n\t// methods for solving multi-objective queries on MDPs\n\tpublic static final int MDP_MULTI_VALITER = 1;\n\tpublic static final int MDP_MULTI_GAUSSSEIDEL = 2;\n\tpublic static final int MDP_MULTI_LP = 3;\n\n\t// termination criterion for iterative methods\n\tpublic static final int ABSOLUTE = 1;\n\tpublic static final int RELATIVE = 2;\n\n\t// options for model matrix export\n\tpublic static final int EXPORT_PLAIN = 1;\n\tpublic static final int EXPORT_MATLAB = 2;\n\tpublic static final int EXPORT_DOT = 3;\n\tpublic static final int EXPORT_ROWS = 5;\n\tpublic static final int EXPORT_DOT_STATES = 6;\n\n\t// options for adversary export\n\tpublic static final int EXPORT_ADV_NONE = 1;\n\tpublic static final int EXPORT_ADV_DTMC = 2;\n\tpublic static final int EXPORT_ADV_MDP = 3;\n\n\t// methods for SCC decomposition\n\tpublic static final int XIEBEEREL = 1;\n\tpublic static final int LOCKSTEP = 2;\n\tpublic static final int SCCFIND = 3;\n\n\t// state space cut-off to trigger MTBDD engine\n\tprotected static final int MTBDD_STATES_THRESHOLD = 100000000;\n\t\n\t//------------------------------------------------------------------------------\n\t// Settings / flags / options\n\t//------------------------------------------------------------------------------\n\n\t// Export digital clocks translation PRISM model?\n\tprotected boolean exportDigital = false;\n\tprotected File exportDigitalFile = null;\n\t// Export target state info?\n\tprotected boolean exportTarget = false;\n\tprotected String exportTargetFilename = null;\n\t// Export product model info?\n\tprotected boolean exportProductTrans = false;\n\tprotected String exportProductTransFilename = null;\n\tprotected boolean exportProductStates = false;\n\tprotected String exportProductStatesFilename = null;\n\tprotected boolean exportProductVector = false;\n\tprotected String exportProductVectorFilename = null;\n\t// Store the final results vector after model checking?\n\tprotected boolean storeVector = false;\n\t// Generate/store a strategy during model checking?\n\tprotected boolean genStrat = false;\n\t// Should any generated strategies should be restricted to the states reachable under them?\n\tprotected boolean restrictStratToReach = true;\n\t// Do bisimulation minimisation before model checking?\n\tprotected boolean doBisim = false;\n\n\t// A few miscellaneous options (i.e. defunct/hidden/undocumented/etc.)\n\t// See constructor below for default values\n\n\tprivate boolean doReach = true; // do reachability? (sometimes might want to skip it)\n\tprivate boolean bsccComp = true; // do bscc computation before steady-state?\n\tprivate boolean checkZeroLoops = false;\n\n\t// MTBDD construction method (NOW DEFUNCT)\n\t//  1 - use with ordering 1: nondet vars form a tree at the top\n\t//  3 - use with ordering 2: zero for nonexistant bits\n\t// nb: option 2 removed because it was stupid\n\tprivate int construction = 3;\n\n\t// MTBDD variable ordering\n\t//  1 - (s ... s) (l ... l) (r c ... r c)\n\t//  2 - (s l ... l r c ... r c) (s l ... l r c ... r c) ...\n\tprivate int ordering = 1;\n\n\t// Method to use for (symbolic) state-space reachability\n\tprivate int reachMethod = REACH_BFS;\n\n\t// Test mode(s)\n\tprivate boolean testUMB = false;\n\n\t//------------------------------------------------------------------------------\n\t// Parsers/translators/model checkers/simulators/etc.\n\t//------------------------------------------------------------------------------\n\n\tprivate final List<PrismLibrary> libraries = new ArrayList<>();\n\tprivate static PrismParser thePrismParser = null;\n\tprivate static boolean prismParserInUse = false;\n\tprivate SimulatorEngine theSimulator = null;\n\n\t/** Regexp for PRISM language identifiers */\n\tprivate static final Pattern IDENTIFIER_PATTERN = Pattern.compile(\"[_a-zA-Z][_a-zA-Z0-9]*\");\n\n\t//------------------------------------------------------------------------------\n\t// Event listeners\n\t//------------------------------------------------------------------------------\n\n\tprivate List<PrismModelListener> modelListeners;\n\n\t//------------------------------------------------------------------------------\n\t// State\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Working directory for resolving files (null = current working directory).\n\t * Since this is used by native shared libraries, and to ease access from other code, it is static.\n\t */\n\tprivate static Path workingDirectory = null;\n\n\tpublic enum ModelSource {\n\t\tPRISM_MODEL, MODEL_GENERATOR, EXPLICIT_FILES, BUILT_MODEL;\n\t\tpublic String description()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase PRISM_MODEL:\n\t\t\t\t\treturn \"PRISM model\";\n\t\t\t\tcase MODEL_GENERATOR:\n\t\t\t\t\treturn \"model generator\";\n\t\t\t\tcase EXPLICIT_FILES:\n\t\t\t\t\treturn \"explicit files\";\n\t\t\t\tcase BUILT_MODEL:\n\t\t\t\t\treturn \"built model\";\n\t\t\t\tdefault:\n\t\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic enum ModelBuildType {\n\t\tSYMBOLIC, EXPLICIT, EXACT, PARAM;\n\t\tpublic String description()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase SYMBOLIC:\n\t\t\t\t\treturn \"symbolic\";\n\t\t\t\tcase EXPLICIT:\n\t\t\t\t\treturn \"explicit\";\n\t\t\t\tcase EXACT:\n\t\t\t\t\treturn \"exact\";\n\t\t\t\tcase PARAM:\n\t\t\t\t\treturn \"parametric\";\n\t\t\t\tdefault:\n\t\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t}\n\t\n\tpublic enum PrismEngine {\n\t\tSYMBOLIC, EXPLICIT, EXACT, PARAM;\n\t\tpublic String description()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase SYMBOLIC:\n\t\t\t\t\treturn \"symbolic\";\n\t\t\t\tcase EXPLICIT:\n\t\t\t\t\treturn \"explicit\";\n\t\t\t\tcase EXACT:\n\t\t\t\t\treturn \"exact\";\n\t\t\t\tcase PARAM:\n\t\t\t\t\treturn \"parametric\";\n\t\t\t\tdefault:\n\t\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Class to store details about a loaded model */\n\tpublic class ModelDetails\n\t{\n\t\t// Model source (null if none/unknown)\n\t\tModelSource modelSource = null;\n\t\t// Model type (null if none/unknown)\n\t\tModelType modelType = null;\n\t\t// Model info (null if none/unknown)\n\t\tModelInfo modelInfo = null;\n\t\t// PRISM model (null if none loaded)\n\t\tModulesFile modulesFile = null;\n\t\t// Model generator (null if none loaded)\n\t\tModelGenerator<?> modelGenerator = null;\n\t\t// Reward info (null if none loaded)\n\t\tRewardInfo rewardInfo = null;\n\t\t// Reward generator (null if none loaded)\n\t\tRewardGenerator<?> rewardGenerator = null;\n\t\t// Constants to be defined for PRISM model (null if none/undefined)\n\t\tValues definedMFConstants = null;\n\t\t// Was definedMFConstants evaluated exactly?\n\t\tboolean definedMFConstantsAreExact = false;\n\t\t// Built model storage - symbolic or explicit - at most one is non-null\n\t\tprism.Model<?> model = null;\n\t\tsymbolic.model.Model modelSymb = null;\n\t\texplicit.Model<?> modelExpl = null;\n\t\t// Type of built model storage\n\t\tModelBuildType modelBuildType = null;\n\t\t// Are we doing digital clocks translation for PTAs?\n\t\tboolean modelDigitalClocks = false;\n\n\t\t/** Default constructor */\n\t\tModelDetails()\n\t\t{\n\t\t\t// Fields take default values as listed above\n\t\t}\n\n\t\t/** Copy constructor */\n\t\tModelDetails(ModelDetails other)\n\t\t{\n\t\t\tmodelSource = other.modelSource;\n\t\t\tmodelType = other.modelType;\n\t\t\tmodelInfo = other.modelInfo;\n\t\t\tmodulesFile = other.modulesFile;\n\t\t\tmodelGenerator = other.modelGenerator;\n\t\t\trewardInfo = other.rewardInfo;\n\t\t\trewardGenerator = other.rewardGenerator;\n\t\t\tdefinedMFConstants = other.definedMFConstants;\n\t\t\tdefinedMFConstantsAreExact = other.definedMFConstantsAreExact;\n\t\t\tmodel = other.model;\n\t\t\tmodelSymb = other.modelSymb;\n\t\t\tmodelExpl = other.modelExpl;\n\t\t\tmodelBuildType = other.modelBuildType;\n\t\t\tmodelDigitalClocks = other.modelDigitalClocks;\n\t\t}\n\t}\n\n\t/** Info about currently loaded model, if any */\n\tprivate ModelDetails currentModelDetails = new ModelDetails();\n\n\t// The last strategy that was generated\n\tprivate Strategy<?> strategy = null;\n\t\n\t// Info for explicit files load\n\tprivate ExplicitModelImporter modelImporter;\n\n\t// Info about parametric mode\n\tprivate boolean param = false;\n\tprivate String[] paramNames;\n\tprivate String[] paramLowerBounds;\n\tprivate String[] paramUpperBounds;\n\n\t// Info about automatic engine switching\n\tprivate int engineOld = -1;\n\tprivate boolean engineSwitched = false;\n\n\t//------------------------------------------------------------------------------\n\t// Constructors + options methods\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Construct a new Prism object.\n\t * Output will be sent to stdout.\n\t */\n\tpublic Prism() throws PrismException\n\t{\n\t\tthis(new PrismFileLog(\"stdout\"));\n\t}\n\n\t/**\n\t * Construct a new Prism object.\n\t * @param mainLog PrismLog where all output will be sent.\n\t */\n\tpublic Prism(PrismLog mainLog)\n\t{\n\t\t// set up log\n\t\tthis.mainLog = mainLog;\n\t\t// set up some default options\n\t\tsettings = new PrismSettings();\n\t\t// add this Prism object as a results listener\n\t\tsettings.addSettingsListener(this);\n\t\t// create list of model listeners\n\t\tmodelListeners = new ArrayList<PrismModelListener>();\n\t}\n\n\t/**\n\t * Read in PRISM settings from the default file (see PrismSettings.getLocationForSettingsFile()).\n\t * If no file exists, attempt to create a new one with default settings.\n\t */\n\tpublic void loadUserSettingsFile()\n\t{\n\t\tloadUserSettingsFile(null);\n\t}\n\n\t/**\n\t * Read in PRISM settings from a specified file.\n\t * If the file is null, use the default (see PrismSettings.getLocationForSettingsFile()).\n\t * If no file exists, attempt to create a new one with default settings.\n\t */\n\tpublic void loadUserSettingsFile(File settingsFile)\n\t{\n\t\t// load user's default settings\n\t\ttry {\n\t\t\tif (settingsFile == null)\n\t\t\t\tsettings.loadSettingsFile();\n\t\t\telse\n\t\t\t\tsettings.loadSettingsFile(settingsFile);\n\t\t} catch (PrismException e) {\n\t\t\t// if there were no user defaults to load, create them\n\t\t\ttry {\n\t\t\t\tif (settingsFile == null)\n\t\t\t\t\tsettings.saveSettingsFile();\n\t\t\t\telse\n\t\t\t\t\tsettings.saveSettingsFile(settingsFile);\n\t\t\t} catch (PrismException ex) {\n\t\t\t\tmainLog.printWarning(\"Failed to create new PRISM settings file.\");\n\t\t\t}\n\t\t}\n\t}\n\n\t// Working directory\n\n\t/**\n\t * Set the working directory, with respect to which filenames for reading/writing\n\t * will be resolved. If set to null, the existing current working directory is used.\n\t * If set, this should be called before {@link #initialise()} so that it is\n\t * passed to any other libraries that are initialised.\n\t *\n\t * @param dirname Name of working directory (null = current working directory)\n\t */\n\tpublic static void setWorkingDirectory(String dirname) throws PrismException\n\t{\n\t\tif (dirname == null) {\n\t\t\tworkingDirectory = null;\n\t\t\treturn;\n\t\t}\n\t\tPath wd = Paths.get(dirname);\n\t\tif (!Files.isDirectory(wd)) {\n\t\t\tthrow new PrismException(\"Working directory \\\"\" + dirname + \"\\\" is not a directory\");\n\t\t}\n\t\tif (!Files.isReadable(wd)) {\n\t\t\tthrow new PrismException(\"Working directory \\\"\" + dirname + \"\\\" is not readable\");\n\t\t}\n\t\tif (!Files.isWritable(wd)) {\n\t\t\tthrow new PrismException(\"Working directory \\\"\" + dirname + \"\\\" is not writeable\");\n\t\t}\n\t\tworkingDirectory = wd;\n\t}\n\n\t/**\n\t * Get the working directory, with respect to which filenames for reading/writing\n\t * will be resolved. If set to null, the existing current working directory is used.\n\t */\n\tpublic static Path getWorkingDirectory()\n\t{\n\t\treturn  workingDirectory;\n\t}\n\n\t/**\n\t * Resolve a filename. If relative, it will be resolved with respect to\n\t * {@link #getWorkingDirectory()} (or the current working directory if that is null).\n\t */\n\tpublic static File resolveFile(String filename)\n\t{\n\t\treturn resolveFile(new File(filename));\n\t}\n\n\t/**\n\t * Resolve a filename. If relative, it will be resolved with respect to\n\t * {@link #getWorkingDirectory()} (or the current working directory if that is null).\n\t */\n\tpublic static File resolveFile(File file)\n\t{\n\t\treturn workingDirectory == null ? file : workingDirectory.resolve(file.toPath()).toFile();\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Set the PrismLog where messages and model checking output will be sent.\n\t */\n\tpublic void setMainLog(PrismLog mainLog) throws PrismException\n\t{\n\t\tsuper.setLog(mainLog);\n\t\tfor (PrismLibrary lib : libraries) {\n\t\t\tlib.setMainLog(mainLog);\n\t\t}\n\t}\n\n\t// Set methods for main prism settings\n\t// (provided for convenience and for compatibility with old code)\n\n\tpublic void setEngine(int e) throws PrismException\n\t{\n\t\tsettings.setChoice(PrismSettings.PRISM_ENGINE, e);\n\t}\n\n\tpublic void setVerbose(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_VERBOSE, b);\n\t}\n\n\tpublic void setFairness(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_FAIRNESS, b);\n\t}\n\n\tpublic void setPrecomp(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_PRECOMPUTATION, b);\n\t}\n\n\tpublic void setProb0(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_PROB0, b);\n\t}\n\n\tpublic void setProb1(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_PROB1, b);\n\t}\n\n\tpublic void setFixDeadlocks(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_FIX_DEADLOCKS, b);\n\t}\n\n\tpublic void setDoProbChecks(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_DO_PROB_CHECKS, b);\n\t}\n\n\tpublic void setSumRoundOff(double d) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_SUM_ROUND_OFF, d);\n\t}\n\n\tpublic void setCompact(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_COMPACT, b);\n\t}\n\n\tpublic void setLinEqMethod(int i) throws PrismException\n\t{\n\t\tsettings.setChoice(PrismSettings.PRISM_LIN_EQ_METHOD, i);\n\t}\n\n\tpublic void setLinEqMethodParam(double d) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_LIN_EQ_METHOD_PARAM, d);\n\t}\n\n\tpublic void setMDPSolnMethod(int i) throws PrismException\n\t{\n\t\tsettings.setChoice(PrismSettings.PRISM_MDP_SOLN_METHOD, i);\n\t}\n\n\tpublic void setMDPMultiSolnMethod(int i) throws PrismException\n\t{\n\t\tsettings.setChoice(PrismSettings.PRISM_MDP_MULTI_SOLN_METHOD, i);\n\t}\n\n\tpublic void setTermCrit(int i) throws PrismException\n\t{\n\t\tsettings.setChoice(PrismSettings.PRISM_TERM_CRIT, i);\n\t}\n\n\tpublic void setTermCritParam(double d) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_TERM_CRIT_PARAM, d);\n\t}\n\n\tpublic void setMaxIters(int i) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_MAX_ITERS, i);\n\t}\n\n\tpublic void setGridResolution(int i) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_GRID_RESOLUTION, i);\n\t}\n\n\tpublic void setCUDDMaxMem(String s) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_CUDD_MAX_MEM, s);\n\t}\n\n\tpublic void setCUDDEpsilon(double d) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_CUDD_EPSILON, d);\n\t}\n\n\tpublic void setNumSBLevels(int i) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_NUM_SB_LEVELS, i);\n\t}\n\n\tpublic void setSBMaxMem(int i) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_SB_MAX_MEM, i);\n\t}\n\n\tpublic void setNumSORLevels(int i) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_NUM_SOR_LEVELS, i);\n\t}\n\n\tpublic void setSORMaxMem(int i) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_SOR_MAX_MEM, i);\n\t}\n\n\tpublic void setDoSSDetect(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_DO_SS_DETECTION, b);\n\t}\n\n\tpublic void setExtraDDInfo(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_EXTRA_DD_INFO, b);\n\t}\n\n\tpublic void setExtraReachInfo(boolean b) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_EXTRA_REACH_INFO, b);\n\t}\n\n\tpublic void setSCCMethod(int i) throws PrismException\n\t{\n\t\tsettings.setChoice(PrismSettings.PRISM_SCC_METHOD, i);\n\t}\n\n\tpublic void setExportAdv(int i) throws PrismException\n\t{\n\t\tsettings.setChoice(PrismSettings.PRISM_EXPORT_ADV, i);\n\t}\n\n\tpublic void setExportAdvFilename(String s) throws PrismException\n\t{\n\t\tsettings.set(PrismSettings.PRISM_EXPORT_ADV_FILENAME, s);\n\t}\n\n\t// Set methods for miscellaneous options\n\n\tpublic void setParametric(String[] paramNames, String[] paramLowerBounds, String[] paramUpperBounds)\n\t{\n\t\tparam = true;\n\t\tthis.paramNames = paramNames;\n\t\tthis.paramLowerBounds = paramLowerBounds;\n\t\tthis.paramUpperBounds = paramUpperBounds;\n\t}\n\n\tpublic void setParametricOff()\n\t{\n\t\tparam = false;\n\t}\n\n\tpublic void setExportDigital(boolean b) throws PrismException\n\t{\n\t\texportDigital = b;\n\t}\n\n\t/**\n\t * Set file to export digital clocks translation PRISM file to (null = stdout).\n\t */\n\tpublic void setExportDigitalFile(File f) throws PrismException\n\t{\n\t\texportDigitalFile = f;\n\t}\n\n\tpublic void setExportTarget(boolean b) throws PrismException\n\t{\n\t\texportTarget = b;\n\t}\n\n\tpublic void setExportTargetFilename(String s) throws PrismException\n\t{\n\t\texportTargetFilename = s;\n\t}\n\n\tpublic void setExportProductTrans(boolean b) throws PrismException\n\t{\n\t\texportProductTrans = b;\n\t}\n\n\tpublic void setExportProductTransFilename(String s) throws PrismException\n\t{\n\t\texportProductTransFilename = s;\n\t}\n\n\tpublic void setExportProductStates(boolean b) throws PrismException\n\t{\n\t\texportProductStates = b;\n\t}\n\n\tpublic void setExportProductStatesFilename(String s) throws PrismException\n\t{\n\t\texportProductStatesFilename = s;\n\t}\n\n\tpublic void setExportProductVector(boolean b) throws PrismException\n\t{\n\t\texportProductVector = b;\n\t}\n\n\tpublic void setExportProductVectorFilename(String s) throws PrismException\n\t{\n\t\texportProductVectorFilename = s;\n\t}\n\n\t/**\n\t * Specify whether or not to store the final results vector after model checking.\n\t */\n\tpublic void setStoreVector(boolean storeVector)\n\t{\n\t\tthis.storeVector = storeVector;\n\t}\n\n\t/**\n\t * Specify whether or not a strategy should be generated during model checking.\n\t */\n\tpublic void setGenStrat(boolean genStrat)\n\t{\n\t\tthis.genStrat = genStrat;\n\t}\n\n\t/**\n\t * Specify whether or not any generated strategies should be restricted to the states reachable under them.\n\t */\n\tpublic void setRestrictStratToReach(boolean restrictStratToReach)\n\t{\n\t\tthis.restrictStratToReach = restrictStratToReach;\n\t}\n\n\t/**\n\t * Specify whether or not to do bisimulation minimisation before model checking.\n\t */\n\tpublic void setDoBisim(boolean doBisim)\n\t{\n\t\tthis.doBisim = doBisim;\n\t}\n\n\tpublic void setDoReach(boolean b) throws PrismException\n\t{\n\t\tdoReach = b;\n\t}\n\n\tpublic void setBSCCComp(boolean b) throws PrismException\n\t{\n\t\tbsccComp = b;\n\t}\n\n\tpublic void setCheckZeroLoops(boolean checkZeroLoops)\n\t{\n\t\tthis.checkZeroLoops = checkZeroLoops;\n\t}\n\n\tpublic void setConstruction(int i) throws PrismException\n\t{\n\t\tconstruction = i;\n\t}\n\n\tpublic void setOrdering(int i) throws PrismException\n\t{\n\t\tordering = i;\n\t}\n\n\tpublic static int REACH_BFS = 1;\n\tpublic static int REACH_FRONTIER = 2;\n\n\tpublic void setReachMethod(int reachMethod)\n\t{\n\t\tthis.reachMethod = reachMethod;\n\t}\n\n\tpublic void setTestUMB(boolean testUMB)\n\t{\n\t\tthis.testUMB = testUMB;\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the name of this tool.\n\t * (\"PRISM\" by default, extensions might override) \n\t */\n\tpublic static String getToolName()\n\t{\n\t\treturn \"PRISM\";\n\t}\n\n\t/**\n\t * Get the name of the command-line version of this tool.\n\t * (\"prism\" by default, extensions might override) \n\t */\n\tpublic static String getCommandLineName()\n\t{\n\t\treturn \"prism\";\n\t}\n\n\t/**\n\t * Get current version number, as a string. \n\t */\n\tpublic static String getVersion()\n\t{\n\t\tString v = version;\n\t\t// Append version suffix (e.g. \"dev\", \"beta\") if non-empty\n\t\tif (versionSuffix.length() > 0) {\n\t\t\tv += \"-\" + versionSuffix;\n\t\t}\n\t\treturn v;\n\t}\n\n\tpublic PrismLog getMainLog()\n\t{\n\t\treturn mainLog;\n\t}\n\n\tpublic PrismSettings getSettings()\n\t{\n\t\treturn settings;\n\t}\n\n\t// Get methods for main prism settings\n\t// (as above, provided for convenience and for compatibility with old code)\n\n\tpublic int getEngine()\n\t{\n\t\treturn settings.getChoice(PrismSettings.PRISM_ENGINE);\n\t}\n\n\t/**\n\t * Is the current engine \"Explicit\"?\n\t */\n\tpublic boolean getExplicit()\n\t{\n\t\treturn getEngine() == Prism.EXPLICIT;\n\t}\n\n\tpublic boolean getFixDeadlocks()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_FIX_DEADLOCKS);\n\t}\n\n\tpublic boolean getDoProbChecks()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_DO_PROB_CHECKS);\n\t}\n\n\tpublic double getSumRoundOff()\n\t{\n\t\treturn settings.getDouble(PrismSettings.PRISM_SUM_ROUND_OFF);\n\t}\n\n\tpublic int getLinEqMethod()\n\t{\n\t\treturn settings.getChoice(PrismSettings.PRISM_LIN_EQ_METHOD);\n\t}\n\n\tpublic double getLinEqMethodParam()\n\t{\n\t\treturn settings.getDouble(PrismSettings.PRISM_LIN_EQ_METHOD_PARAM);\n\t}\n\n\tpublic int getMDPSolnMethod()\n\t{\n\t\treturn settings.getChoice(PrismSettings.PRISM_MDP_SOLN_METHOD);\n\t}\n\n\tpublic int getMDPMultiSolnMethod()\n\t{\n\t\treturn settings.getChoice(PrismSettings.PRISM_MDP_MULTI_SOLN_METHOD);\n\t}\n\n\tpublic int getTermCrit()\n\t{\n\t\treturn settings.getChoice(PrismSettings.PRISM_TERM_CRIT);\n\t}\n\n\tpublic double getTermCritParam()\n\t{\n\t\treturn settings.getDouble(PrismSettings.PRISM_TERM_CRIT_PARAM);\n\t}\n\n\tpublic int getMaxIters()\n\t{\n\t\treturn settings.getInteger(PrismSettings.PRISM_MAX_ITERS);\n\t}\n\n\tpublic int getGridResolution()\n\t{\n\t\treturn settings.getInteger(PrismSettings.PRISM_GRID_RESOLUTION);\n\t}\n\n\tpublic boolean getVerbose()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_VERBOSE);\n\t}\n\n\tpublic boolean getPrecomp()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_PRECOMPUTATION);\n\t}\n\n\tpublic boolean getProb0()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_PROB0);\n\t}\n\n\tpublic boolean getProb1()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_PROB1);\n\t}\n\n\tpublic boolean getPreRel()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_PRE_REL);\n\t}\n\n\tpublic boolean getFairness()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_FAIRNESS);\n\t}\n\n\tpublic int getSBMaxMem()\n\t{\n\t\treturn settings.getInteger(PrismSettings.PRISM_SB_MAX_MEM);\n\t}\n\n\tpublic int getNumSBLevels()\n\t{\n\t\treturn settings.getInteger(PrismSettings.PRISM_NUM_SB_LEVELS);\n\t}\n\n\tpublic int getSORMaxMem()\n\t{\n\t\treturn settings.getInteger(PrismSettings.PRISM_SOR_MAX_MEM);\n\t}\n\n\tpublic boolean getDoSSDetect()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_DO_SS_DETECTION);\n\t}\n\n\tpublic boolean getExtraDDInfo()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_EXTRA_DD_INFO);\n\t}\n\n\tpublic boolean getExtraReachInfo()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_EXTRA_REACH_INFO);\n\t}\n\n\tpublic int getNumSORLevels()\n\t{\n\t\treturn settings.getInteger(PrismSettings.PRISM_NUM_SOR_LEVELS);\n\t}\n\n\tpublic boolean getCompact()\n\t{\n\t\treturn settings.getBoolean(PrismSettings.PRISM_COMPACT);\n\t}\n\n\tpublic String getCUDDMaxMem()\n\t{\n\t\treturn settings.getString(PrismSettings.PRISM_CUDD_MAX_MEM);\n\t}\n\n\tpublic double getCUDDEpsilon()\n\t{\n\t\treturn settings.getDouble(PrismSettings.PRISM_CUDD_EPSILON);\n\t}\n\n\tpublic int getSCCMethod()\n\t{\n\t\treturn settings.getChoice(PrismSettings.PRISM_SCC_METHOD);\n\t}\n\n\tpublic int getExportAdv()\n\t{\n\t\treturn settings.getChoice(PrismSettings.PRISM_EXPORT_ADV);\n\t}\n\n\tpublic String getExportAdvFilename()\n\t{\n\t\treturn settings.getString(PrismSettings.PRISM_EXPORT_ADV_FILENAME);\n\t}\n\n\t// Get methods for miscellaneous options\n\n\tpublic boolean getExportTarget()\n\t{\n\t\treturn exportTarget;\n\t}\n\n\tpublic String getExportTargetFilename()\n\t{\n\t\treturn exportTargetFilename;\n\t}\n\n\tpublic boolean getExportProductTrans()\n\t{\n\t\treturn exportProductTrans;\n\t}\n\n\tpublic String getExportProductTransFilename()\n\t{\n\t\treturn exportProductTransFilename;\n\t}\n\n\tpublic boolean getExportProductStates()\n\t{\n\t\treturn exportProductStates;\n\t}\n\n\tpublic String getExportProductStatesFilename()\n\t{\n\t\treturn exportProductStatesFilename;\n\t}\n\n\tpublic boolean getExportProductVector()\n\t{\n\t\treturn exportProductVector;\n\t}\n\n\tpublic String getExportProductVectorFilename()\n\t{\n\t\treturn exportProductVectorFilename;\n\t}\n\n\t/**\n\t * Whether or not to store the final results vector after model checking.\n\t */\n\tpublic boolean getStoreVector()\n\t{\n\t\treturn storeVector;\n\t}\n\n\t/**\n\t * Whether or not a strategy should be generated during model checking.\n\t */\n\tpublic boolean getGenStrat()\n\t{\n\t\treturn genStrat;\n\t}\n\n\t/**\n\t * Whether or not any generated strategies should be restricted to the states reachable under them.\n\t */\n\tpublic boolean getRestrictStratToReach()\n\t{\n\t\treturn restrictStratToReach;\n\t}\n\n\t/**\n\t * Whether or not to do bisimulation minimisation before model checking.\n\t */\n\tpublic boolean getDoBisim()\n\t{\n\t\treturn doBisim;\n\t}\n\n\tpublic boolean getDoReach()\n\t{\n\t\treturn doReach;\n\t}\n\n\tpublic boolean getBSCCComp()\n\t{\n\t\treturn bsccComp;\n\t}\n\n\tpublic boolean getCheckZeroLoops()\n\t{\n\t\treturn this.checkZeroLoops;\n\t}\n\n\tpublic int getConstruction()\n\t{\n\t\treturn construction;\n\t}\n\n\tpublic int getOrdering()\n\t{\n\t\treturn ordering;\n\t}\n\n\tpublic int getReachMethod()\n\t{\n\t\treturn reachMethod;\n\t}\n\n\t/**\n\t * Returns an integer containing flags for the C++ implementation of interval iteration,\n\t * derived from the current settings object.\n\t */\n\tpublic int getIntervalIterationFlags() throws PrismException\n\t{\n\t\tint flags = 0;\n\n\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(settings);\n\n\t\tif (iiOptions.isEnforceMonotonicityFromBelow())\n\t\t\tflags += 1;\n\n\t\tif (iiOptions.isEnforceMonotonicityFromAbove())\n\t\t\tflags += 2;\n\n\t\tif (iiOptions.isSelectMidpointForResult())\n\t\t\tflags += 4;  // select midpoint for result\n\n\t\treturn flags;\n\t}\n\n\n\n\tpublic void addModelListener(PrismModelListener listener)\n\t{\n\t\tmodelListeners.add(listener);\n\t}\n\n\t// String methods for options\n\n\tpublic static String getEngineString(int engine)\n\t{\n\t\treturn engineStrings[engine];\n\t}\n\n\t/**\n\t * Let PrismSettings object notify us things have changed\n\t */\n\tpublic void notifySettings(PrismSettings settings)\n\t{\n\t\tfor (PrismLibrary lib : libraries) {\n\t\t\tlib.notifySettings(settings);\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// Access to parser, simulator, etc.\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Get (exclusive) access to the PRISM parser.\n\t * Not usually used externally - use the ready-made model/property parse methods instead.\n\t */\n\tpublic static PrismParser getPrismParser() throws InterruptedException\n\t{\n\t\t// Note: this mutex mechanism is based on public domain code by Doug Lea\n\t\tif (Thread.interrupted())\n\t\t\tthrow new InterruptedException();\n\t\t// this code is synchronized on the whole Prism class\n\t\t// (because this is a static method)\n\t\tsynchronized (Prism.class) {\n\t\t\ttry {\n\t\t\t\t// wait until parser is free\n\t\t\t\twhile (prismParserInUse) {\n\t\t\t\t\tPrism.class.wait();\n\t\t\t\t}\n\t\t\t\t// lock parser\n\t\t\t\tprismParserInUse = true;\n\t\t\t\t// return parser, creating anew if necessary\n\t\t\t\tif (thePrismParser == null)\n\t\t\t\t\tthePrismParser = new PrismParser();\n\t\t\t\treturn thePrismParser;\n\t\t\t} catch (InterruptedException e) {\n\t\t\t\tPrism.class.notify();\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Release (exclusive) access to the PRISM parser.\n\t */\n\tpublic static synchronized void releasePrismParser()\n\t{\n\t\tprismParserInUse = false;\n\t\tPrism.class.notify();\n\t}\n\n\t/**\n\t * Get the SimulatorEngine object for PRISM, creating if necessary.\n\t */\n\tpublic SimulatorEngine getSimulator()\n\t{\n\t\tif (theSimulator == null) {\n\t\t\ttheSimulator = new SimulatorEngine(this);\n\t\t}\n\t\treturn theSimulator;\n\t}\n\n\t/**\n\t * Get an SCCComputer object.\n\t * Type (i.e. algorithm) depends on SCCMethod PRISM option.\n\t */\n\tpublic SCCComputer getSCCComputer(Model model) throws PrismException\n\t{\n\t\treturn SCCComputer.createSCCComputer(this, model);\n\t}\n\n\t/**\n\t * Get an SCCComputer object.\n\t * Type (i.e. algorithm) depends on SCCMethod PRISM option.\n\t */\n\tpublic SCCComputer getSCCComputer(JDDNode reach, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars) throws PrismException\n\t{\n\t\treturn SCCComputer.createSCCComputer(this, reach, trans01, allDDRowVars, allDDColVars);\n\t}\n\n\t/**\n\t * Get an SCCComputer object for the explicit engine.\n\t * @param consumer the SCCConsumer\n\t */\n\tpublic explicit.SCCComputer getExplicitSCCComputer(explicit.Model<?> model, explicit.SCCConsumer consumer) throws PrismException\n\t{\n\t\treturn explicit.SCCComputer.createSCCComputer(this, model, consumer);\n\t}\n\n\t/**\n\t * Get an ECComputer object.\n\t */\n\tpublic ECComputer getECComputer(NondetModel model) throws PrismException\n\t{\n\t\treturn ECComputer.createECComputer(this, model);\n\t}\n\n\t/**\n\t * Get an ECComputer object.\n\t */\n\tpublic ECComputer getECComputer(JDDNode reach, JDDNode trans, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars, JDDVars allDDNondetVars)\n\t\t\tthrows PrismException\n\t{\n\t\treturn ECComputer.createECComputer(this, reach, trans, trans01, allDDRowVars, allDDColVars, allDDNondetVars);\n\t}\n\n\t/**\n\t * Get an ECComputer object for the explicit engine.\n\t */\n\tpublic explicit.ECComputer getExplicitECComputer(explicit.NondetModel<?> model) throws PrismException\n\t{\n\t\treturn explicit.ECComputer.createECComputer(this, model);\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// Utility methods\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Get access to the list of all PRISM language keywords.\n\t */\n\tpublic static List<String> getListOfKeywords()\n\t{\n\t\treturn PrismParser.getListOfKeywords();\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// Main API methods\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Initialise PRISM.\n\t */\n\tpublic void initialise() throws PrismException\n\t{\n\t\tboolean verbose = this.getSettings().getBoolean(\"PRISM_VERBOSE\");\n\t\tmainLog.setVerbosityLevel(verbose ? PrismLog.VL_ALL : PrismLog.VL_DEFAULT);\n\t\tmainLog.print(getToolName() + \"\\n\");\n\t\tmainLog.print(new String(new char[getToolName().length()]).replace(\"\\0\", \"=\") + \"\\n\");\n\t\tmainLog.print(\"\\nVersion: \" + getVersion() + \"\\n\");\n\t\tmainLog.print(\"Date: \" + new java.util.Date() + \"\\n\");\n\t\ttry {\n\t\t\tString h = java.net.InetAddress.getLocalHost().getHostName();\n\t\t\tmainLog.print(\"Hostname: \" + h + \"\\n\");\n\t\t} catch (java.net.UnknownHostException e) {\n\t\t}\n\t\tmainLog.print(\"Memory limits: cudd=\" + getCUDDMaxMem());\n\t\tmainLog.println(\", java(heap)=\" + PrismUtils.convertBytesToMemoryString(Runtime.getRuntime().maxMemory()));\n\t}\n\n\t/**\n\t * Ensure that the native libraries are loaded and initialised,\n\t * and that any relevant settings are passed to them.\n\t */\n\tpublic void useNative() throws PrismException\n\t{\n\t\t// Add/initialise libraries for native code, if not already done\n\t\tif (libraries.stream().noneMatch(JDDLibrary.class::isInstance)) {\n\t\t\taddLibrary(new JDDLibrary());\n\t\t}\n\t\tif (libraries.stream().noneMatch(PrismNativeLibrary.class::isInstance)) {\n\t\t\taddLibrary(new PrismNativeLibrary());\n\t\t}\n\t}\n\n\t/**\n\t * Initialise a freshy created {@link PrismLibrary} and add to the list of libraries.\n\t */\n\tprivate void addLibrary(PrismLibrary lib) throws PrismException\n\t{\n\t\tlib.initialise(this);\n\t\tlib.setMainLog(mainLog);\n\t\tlibraries.add(lib);\n\t}\n\n\t/**\n\t * Set the random seed for the simulator.\n\t */\n\tpublic void setSimulatorSeed(int seed) throws PrismException\n\t{\n\t\tgetSimulator().setRandomNumberGeneratorSeed(seed);\n\t}\n\n\t/**\n\t * Parse a PRISM model from a file.\n\t * @param file File to read in\n\t */\n\tpublic ModulesFile parseModelFile(File file) throws FileNotFoundException, PrismLangException\n\t{\n\t\treturn parseModelFile(file, null);\n\t}\n\n\t/**\n\t * Parse a PRISM model from a file.\n\t * @param file File to read in\n\t * @param typeOverride Optionally, override model type here (null if unused)\n\t */\n\tpublic ModulesFile parseModelFile(File file, ModelType typeOverride) throws FileNotFoundException, PrismLangException\n\t{\n\t\tFileInputStream strModel;\n\t\tPrismParser prismParser;\n\t\tModulesFile modulesFile = null;\n\n\t\t// open file\n\t\tmainLog.print(\"\\nParsing PRISM model file \\\"\" + file + \"\\\"...\\n\");\n\t\tstrModel = new FileInputStream(file);\n\n\t\ttry {\n\t\t\t// obtain exclusive access to the prism parser\n\t\t\t// (don't forget to release it afterwards)\n\t\t\tprismParser = getPrismParser();\n\t\t\ttry {\n\t\t\t\t// parse file\n\t\t\t\tmodulesFile = prismParser.parseModulesFile(strModel, typeOverride);\n\t\t\t} finally {\n\t\t\t\t// release prism parser\n\t\t\t\treleasePrismParser();\n\t\t\t}\n\t\t} catch (InterruptedException ie) {\n\t\t\tthrow new PrismLangException(\"Concurrency error in parser\");\n\t\t}\n\n\t\tmodulesFile.tidyUp();\n\n\t\treturn modulesFile;\n\t}\n\n\t/**\n\t * Parse a PRISM model from a string.\n\t * @param s String containing model\n\t */\n\tpublic ModulesFile parseModelString(String s) throws PrismLangException\n\t{\n\t\treturn parseModelString(s, null);\n\t}\n\n\t/**\n\t * Parse a PRISM model from a string.\n\t * @param s String containing model\n\t * @param typeOverride Optionally, override model type here (null if unused)\n\t */\n\tpublic ModulesFile parseModelString(String s, ModelType typeOverride) throws PrismLangException\n\t{\n\t\tPrismParser prismParser;\n\t\tModulesFile modulesFile = null;\n\n\t\ttry {\n\t\t\t// obtain exclusive access to the prism parser\n\t\t\t// (don't forget to release it afterwards)\n\t\t\tprismParser = getPrismParser();\n\t\t\ttry {\n\t\t\t\t// parse string\n\t\t\t\tmodulesFile = prismParser.parseModulesFile(new ByteArrayInputStream(s.getBytes()), typeOverride);\n\t\t\t} finally {\n\t\t\t\t// release prism parser\n\t\t\t\treleasePrismParser();\n\t\t\t}\n\t\t} catch (InterruptedException ie) {\n\t\t\tthrow new PrismLangException(\"Concurrency error in parser\");\n\t\t}\n\n\t\tmodulesFile.tidyUp();\n\n\t\treturn modulesFile;\n\t}\n\n\t/**\n\t * Import a PRISM model from a PEPA model in a file\n\t * @param file File to read in\n\t */\n\tpublic ModulesFile importPepaFile(File file) throws PrismException, PrismLangException\n\t{\n\t\treturn importModelFile(\"pepa\", file);\n\t}\n\n\t/**\n\t * Import a PRISM model from a PEPA model in a string\n\t * @param s String containing model\n\t */\n\tpublic ModulesFile importPepaString(String s) throws PrismException, PrismLangException\n\t{\n\t\treturn importModelString(\"pepa\", s);\n\t}\n\n\t/**\n\t * Import a PRISM model from an SBML model in a file\n\t * @param file File to read in\n\t */\n\tpublic ModulesFile importSBMLFile(File file) throws PrismException, PrismLangException\n\t{\n\t\treturn importModelFile(\"sbml\", file);\n\t}\n\n\t/**\n\t * Import a PRISM model from an SBML model in a string\n\t * @param s String containing model\n\t */\n\tpublic ModulesFile importSBMLString(String s) throws PrismException, PrismLangException\n\t{\n\t\treturn importModelString(\"sbml\", s);\n\t}\n\n\t/**\n\t * Import a PRISM model by translating from another language\n\t */\n\tpublic ModulesFile importModelFile(String lang, File file) throws PrismException, PrismLangException\n\t{\n\t\tmainLog.print(\"\\nImporting \" + lang.toUpperCase() + \" file \\\"\" + file + \"\\\"...\\n\");\n\t\tPrismLanguageTranslator importer = createPrismLanguageTranslator(lang);\n\t\timporter.load(file);\n\t\tString prismModelString = importer.translateToString();\n\t\treturn parseModelString(prismModelString);\n\t}\n\n\t/**\n\t * Import a PRISM model by translating from another language\n\t */\n\tpublic ModulesFile importModelString(String lang, String s) throws PrismException, PrismLangException\n\t{\n\t\tmainLog.print(\"\\nImporting \" + lang.toUpperCase() + \" model...\\n\");\n\t\tPrismLanguageTranslator importer = createPrismLanguageTranslator(lang);\n\t\timporter.load(s);\n\t\tString prismModelString = importer.translateToString();\n\t\treturn parseModelString(prismModelString);\n\t}\n\n\t/**\n\t * Create a translator to the PRISM language.\n\t */\n\tprivate PrismLanguageTranslator createPrismLanguageTranslator(String lang) throws PrismException\n\t{\n\t\tPrismLanguageTranslator importer = null;\n\t\tswitch (lang) {\n\t\tcase \"pepa\":\n\t\t\timporter = new PEPA2Prism();\n\t\t\tbreak;\n\t\tcase \"sbml\":\n\t\t\timporter = new SBML2Prism();\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown import language \\\"\" + lang + \"\\\"\");\n\t\t}\n\t\treturn importer;\n\t}\n\n\t/**\n\t * Import a PRISM model from a PRISM preprocessor file\n\t * @param file File to read in\n\t * @param params List of values for preprocessor parameters\n\t */\n\tpublic ModulesFile importPrismPreprocFile(File file, String params[]) throws PrismException\n\t{\n\t\tString modelString;\n\n\t\t// Compile preprocessor file to a string\n\t\tmainLog.print(\"\\nImporting PRISM preprocessor file \\\"\" + file + \"\\\"...\\n\");\n\t\tPreprocessor pp = new Preprocessor(this, file);\n\t\tpp.setParameters(params);\n\t\tmodelString = pp.preprocess();\n\t\tif (modelString == null) {\n\t\t\tthrow new PrismException(\"No preprocessing information\");\n\t\t}\n\n\t\t// Parse string as PRISM model and return\n\t\treturn parseModelString(modelString);\n\t}\n\n\t/**\n\t * Parse a PRISM properties file, using the currently loaded model\n\t * for context (i.e. definitions of variables, constants, labels, etc.). \n\t * @param file File to read in\n\t */\n\tpublic PropertiesFile parsePropertiesFile(File file) throws FileNotFoundException, PrismLangException\n\t{\n\t\treturn parsePropertiesFile(getModelInfo(), file, true);\n\t}\n\n\t/**\n\t * Parse a PRISM properties file, using a specific ModelInfo object (e.g. ModulesFile)\n\t * for context (i.e. definitions of variables, constants, labels, etc.).\n\t * Usually, just use {@link #parsePropertiesFile(File)}, which uses the currently loaded model. \n\t * @param modelInfo Accompanying model info (null if not needed)\n\t * @param file File to read in\n\t */\n\tpublic PropertiesFile parsePropertiesFile(ModelInfo modelInfo, File file) throws FileNotFoundException, PrismLangException\n\t{\n\t\treturn parsePropertiesFile(modelInfo, file, true);\n\t}\n\n\t/**\n\t * Parse a PRISM properties file, using the currently loaded model\n\t * for context (i.e. definitions of variables, constants, labels, etc.). \n\t * You can also choose whether to do \"tidy\", i.e. post-parse checks and processing\n\t * (this must be done at some point but may want to postpone to allow parsing of files with errors). \n\t * @param file File to read in\n\t * @param tidy Whether or not to do \"tidy\" (post-parse checks and processing)\n\t */\n\tpublic PropertiesFile parsePropertiesFile(File file, boolean tidy) throws FileNotFoundException, PrismLangException\n\t{\n\t\treturn parsePropertiesFile(getModelInfo(), file, tidy);\n\t}\n\n\t/**\n\t * Parse a PRISM properties file, using a specific ModelInfo object (e.g. ModulesFile)\n\t * for context (i.e. definitions of variables, constants, labels, etc.).\n\t * You can also choose whether to do \"tidy\", i.e. post-parse checks and processing\n\t * (this must be done at some point but may want to postpone to allow parsing of files with errors). \n\t * Usually, just use {@link #parsePropertiesFile(File, boolean)}, which uses the currently loaded model. \n\t * @param modelInfo Accompanying model info (null if not needed)\n\t * @param file File to read in\n\t * @param tidy Whether or not to do \"tidy\" (post-parse checks and processing)\n\t */\n\tpublic PropertiesFile parsePropertiesFile(ModelInfo modelInfo, File file, boolean tidy) throws FileNotFoundException, PrismLangException\n\t{\n\t\tFileInputStream strProperties;\n\t\tPrismParser prismParser;\n\t\tPropertiesFile propertiesFile = null;\n\n\t\t// open file\n\t\tstrProperties = new FileInputStream(file);\n\n\t\ttry {\n\t\t\t// obtain exclusive access to the prism parser\n\t\t\t// (don't forget to release it afterwards)\n\t\t\tprismParser = getPrismParser();\n\t\t\ttry {\n\t\t\t\t// parse file\n\t\t\t\tpropertiesFile = prismParser.parsePropertiesFile(modelInfo, strProperties);\n\t\t\t} finally {\n\t\t\t\t// release prism parser\n\t\t\t\treleasePrismParser();\n\t\t\t}\n\t\t} catch (InterruptedException ie) {\n\t\t\tthrow new PrismLangException(\"Concurrency error in parser\");\n\t\t}\n\n\t\tif (tidy)\n\t\t\tpropertiesFile.tidyUp();\n\n\t\treturn propertiesFile;\n\t}\n\n\t/**\n\t * Parse a PRISM properties file from a string, using the currently loaded model\n\t * for context (i.e. definitions of variables, constants, labels, etc.). \n\t * @param s String to parse\n\t */\n\tpublic PropertiesFile parsePropertiesString(String s) throws PrismLangException\n\t{\n\t\treturn parsePropertiesString(getModelInfo(), s);\n\t}\n\n\t/**\n\t * Parse a PRISM properties file from a string, using a specific ModelInfo object (e.g. ModulesFile)\n\t * for context (i.e. definitions of variables, constants, labels, etc.).\n\t * Usually, just use {@link #parsePropertiesString(String)}, which uses the currently loaded model. \n\t * @param modelInfo Accompanying model info (null if not needed)\n\t * @param s String to parse\n\t */\n\tpublic PropertiesFile parsePropertiesString(ModelInfo modelInfo, String s) throws PrismLangException\n\t{\n\t\tPrismParser prismParser;\n\t\tPropertiesFile propertiesFile = null;\n\n\t\ttry {\n\t\t\t// obtain exclusive access to the prism parser\n\t\t\t// (don't forget to release it afterwards)\n\t\t\tprismParser = getPrismParser();\n\t\t\ttry {\n\t\t\t\t// parse string\n\t\t\t\tpropertiesFile = prismParser.parsePropertiesFile(modelInfo, new ByteArrayInputStream(s.getBytes()));\n\t\t\t} finally {\n\t\t\t\t// release prism parser\n\t\t\t\treleasePrismParser();\n\t\t\t}\n\t\t} catch (InterruptedException ie) {\n\t\t\tthrow new PrismLangException(\"Concurrency error in parser\");\n\t\t}\n\n\t\tpropertiesFile.tidyUp();\n\n\t\treturn propertiesFile;\n\t}\n\n\t/**\n\t * Parse a single PRISM expression from a string.\n\t * @param s String to parse\n\t */\n\tpublic static Expression parseSingleExpressionString(String s) throws PrismLangException\n\t{\n\t\tPrismParser prismParser;\n\t\tExpression expr;\n\n\t\ttry {\n\t\t\t// obtain exclusive access to the prism parser\n\t\t\t// (don't forget to release it afterwards)\n\t\t\tprismParser = getPrismParser();\n\t\t\ttry {\n\t\t\t\t// parse expression\n\t\t\t\texpr = prismParser.parseSingleExpression(new ByteArrayInputStream(s.getBytes()));\n\t\t\t} finally {\n\t\t\t\t// release prism parser\n\t\t\t\treleasePrismParser();\n\t\t\t}\n\t\t} catch (InterruptedException ie) {\n\t\t\tthrow new PrismLangException(\"Concurrency error in parser\");\n\t\t}\n\n\t\treturn expr;\n\t}\n\n\t/**\n\t * Parse a for-loop (as used e.g. in preprocessor) from a string.\n\t * @param s String to parse\n\t */\n\tpublic ForLoop parseForLoopString(String s) throws PrismLangException\n\t{\n\t\tPrismParser prismParser;\n\t\tForLoop fl;\n\n\t\ttry {\n\t\t\t// obtain exclusive access to the prism parser\n\t\t\t// (don't forget to release it afterwards)\n\t\t\tprismParser = getPrismParser();\n\t\t\ttry {\n\t\t\t\t// parse for loop\n\t\t\t\tfl = prismParser.parseForLoop(new ByteArrayInputStream(s.getBytes()));\n\t\t\t} finally {\n\t\t\t\t// release prism parser\n\t\t\t\treleasePrismParser();\n\t\t\t}\n\t\t} catch (InterruptedException ie) {\n\t\t\tthrow new PrismLangException(\"Concurrency error in parser\");\n\t\t}\n\n\t\treturn fl;\n\t}\n\n\t/**\n\t * Check if a string is a keyword in the PRISM language.\n\t */\n\tpublic static boolean isKeyword(String s)\n\t{\n\t\treturn PrismParser.isKeyword(s);\n\t}\n\n\t/**\n\t * Check if a string is a valid identifier in the PRISM language.\n\t */\n\tpublic static boolean isValidIdentifier(String s)\n\t{\n\t\tif (s == null || s.isEmpty()) {\n\t\t\treturn false;\n\t\t}\n\t\tchar first = s.charAt(0);\n\t\tif (!(first == '_' || Character.isLetter(first))) {\n\t\t\treturn false;\n\t\t}\n\t\tif (!IDENTIFIER_PATTERN.matcher(s).matches()) {\n\t\t\treturn false;\n\t\t}\n\t\treturn !PrismParser.isKeyword(s);\n\t}\n\n\t/**\n\t * Convert an object into a valid identifier in the PRISM language.\n\t */\n\tpublic static String toIdentifier(Object o)\n\t{\n\t\tString s = o.toString().replaceAll(\"[^_a-zA-Z0-9]+\", \"_\");\n\t\treturn isValidIdentifier(s) ? s : \"_\" + s;\n\t}\n\n\t/**\n\t * Clear storage of the current model, if any.\n\t */\n\tpublic void clearModel() throws PrismException\n\t{\n\t\tsetModelSource(null);\n\t\tsetModelType(null);\n\t\tsetModelInfo(null);\n\t\tsetPRISMModel(null);\n\t\tsetModelGenerator(null);\n\t\tsetRewardInfo(null);\n\t\tsetRewardGenerator(null);\n\t\tsetDefinedMFConstants(null);\n\t\t// Clear built model storage too\n\t\tclearBuiltModel();\n\t}\n\t\n\t/**\n\t * Load a (parsed) PRISM model, which will be stored and used for subsequent model checking etc.\n\t * Some model constants can still be undefined at this stage.\n\t * Pass in null to clear storage of the current model.\n\t * @param modulesFile The PRISM model\n\t */\n\tpublic void loadPRISMModel(ModulesFile modulesFile) throws PrismException\n\t{\n\t\tif (modulesFile == null) {\n\t\t\tclearModel();\n\t\t}\n\t\t// Update model info\n\t\tsetModelSource(ModelSource.PRISM_MODEL);\n\t\tsetModelType(modulesFile.getModelType());\n\t\tsetModelInfo(modulesFile);\n\t\tsetPRISMModel(modulesFile);\n\t\tsetRewardInfo(modulesFile);\n\t\t// Reset model/reward generator (will be created properly when needed)\n\t\tresetGenerators();\n\t\t// No constant definitions yet\n\t\tsetDefinedMFConstants(null);\n\t\t// Clear any existing built model(s)\n\t\tclearBuiltModel();\n\t\t// Print basic model info\n\t\tprintModelInfo();\n\t}\n\n\t/**\n\t * Load a model generator, which will be stored and used for subsequent model checking etc.\n\t * Some model constants can still be undefined at this stage.\n\t * Pass in null to clear storage of the current model.\n\t * @param modelGen The model generator\n\t */\n\tpublic void loadModelGenerator(ModelGenerator<?> modelGen) throws PrismException\n\t{\n\t\tif (modelGen == null) {\n\t\t\tclearModel();\n\t\t}\n\t\tmainLog.println(\"Loading model generator \" +  modelGen.getClass().getName() + \"...\");\n\t\t// Update model info\n\t\tsetModelSource(ModelSource.MODEL_GENERATOR);\n\t\tsetModelType(modelGen.getModelType());\n\t\tsetModelInfo(modelGen);\n\t\tsetPRISMModel(null);\n\t\tsetModelGenerator(modelGen);\n\t\t// Create a blank reward generator if not provided by the model generator\n\t\tRewardGenerator<?> newRewardGen = (modelGen instanceof RewardGenerator) ? (RewardGenerator<?>) modelGen : new RewardGenerator<>() {};\n\t\tsetRewardInfo(newRewardGen);\n\t\tsetRewardGenerator(newRewardGen);\n\t\tsetDefinedMFConstants(null);\n\t\t// Clear any existing built model(s)\n\t\tclearBuiltModel();\n\t\t// Print basic model info\n\t\tprintModelInfo();\n\t\tmainLog.println();\n\t}\n\n\t/**\n\t * For model sources where model/reward generators are created automatically,\n\t * reset these to default settings, so will be recreated when neeeded.\n\t */\n\tprivate void resetGenerators() throws PrismException\n\t{\n\t\tif (getModelSource() == ModelSource.PRISM_MODEL) {\n\t\t\t// Don't create ModelGenerator yet; do it on demand\n\t\t\tsetModelGenerator(null);\n\t\t\t// For now, use ModulesFile as a RewardGenerator (via reward struct objects)\n\t\t\t// If we build a ModelGenerator too, that can be used for rewards too\n\t\t\tsetRewardGenerator(getPRISMModel());\n\t\t}\n\t}\n\n\t/**\n\t * Set (some or all) undefined constants for the currently loaded PRISM model\n\t * (assuming they have changed since the last time this was called).\n\t * <br>\n\t * Constants are evaluated using standard (integer, floating-point) arithmetic.\n\t * @param definedMFConstants The constant values\n\t */\n\tpublic void setPRISMModelConstants(Values definedMFConstants) throws PrismException\n\t{\n\t\tsetPRISMModelConstants(definedMFConstants, false);\n\t}\n\n\t/**\n\t * Set (some or all) undefined constants for the currently loaded PRISM model\n\t * (assuming they have changed since the last time this was called).\n\t * @param definedMFConstants The constant values\n\t * @param exact if true, do exact evaluation of constants (using BigRational)\n\t */\n\tpublic void setPRISMModelConstants(Values definedMFConstants, boolean exact) throws PrismException\n\t{\n\t\t// If there is no change in constants, there is nothing to do\n\t\tboolean currentMFNone = getUndefinedModelValues() == null || getUndefinedModelValues().getNumValues() == 0;\n\t\tboolean newMFNone = definedMFConstants == null || definedMFConstants.getNumValues() == 0;\n\t\tboolean exactSame = areUndefinedModelValuesExact() == exact;\n\t\tif (currentMFNone && newMFNone && exactSame) {\n\t\t\treturn;\n\t\t}\n\t\tif (getUndefinedModelValues() != null &&\n\t\t\t\tgetUndefinedModelValues().equals(definedMFConstants) && exactSame) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Clear any existing built model(s)\n\t\tclearBuiltModel();\n\t\t// Store constants here and in ModulesFile\n\t\tsetDefinedMFConstants(definedMFConstants, exact);\n\t\tif (getPRISMModel() != null) {\n\t\t\tgetPRISMModel().setSomeUndefinedConstants(definedMFConstants, exact);\n\t\t}\n\t\t// Reset/update model generator\n\t\tif (!exactSame) {\n\t\t\tresetGenerators();\n\t\t} else if (getModelGenerator(false) != null) {\n\t\t\tgetModelGenerator(false).setSomeUndefinedConstants(definedMFConstants, exact);\n\t\t}\n\t}\n\n\t/**\n\t * Load a (built) model, with an accompanying (parsed) PRISM model.\n\t * These will be stored and used for subsequent model checking etc.\n\t * Pass in nulls to clear storage of the current model.\n\t * @param modulesFile The PRISM model\n\t */\n\tpublic void loadPRISMModelAndBuiltModel(ModulesFile modulesFile, Model model) throws PrismException\n\t{\n\t\tsetModelSource(ModelSource.PRISM_MODEL);\n\t\t// Clear any existing built model(s)\n\t\tclearBuiltModel();\n\t\t// Store model info\n\t\tsetPRISMModel(modulesFile);\n\t\t// Reset dependent info\n\t\tsetModelType(modulesFile == null ? null : modulesFile.getModelType());\n\t\tsetModelInfo(modulesFile);\n\t\tsetRewardInfo(modulesFile);\n\t\tsetDefinedMFConstants(null);\n\t\t// Store built model info\n\t\tsetBuiltModel(ModelBuildType.SYMBOLIC, model);\n\t}\n\n\t/**\n\t * Load a (built) model, without an accompanying (parsed) PRISM model.\n\t * The model will be stored and used for subsequent model checking etc.\n\t * Pass in null to clear storage of the current model.\n\t * @param model The built model\n\t */\n\tpublic void loadBuiltModel(Model model) throws PrismException\n\t{\n\t\tsetModelSource(ModelSource.BUILT_MODEL);\n\t\t// Clear any existing built model(s)\n\t\tclearBuiltModel();\n\t\t// Store model info\n\t\tsetPRISMModel(null);\n\t\t// Reset dependent info\n\t\tsetModelType(model == null ? null : model.getModelType());\n\t\tsetDefinedMFConstants(null);\n\t\t// Store built model info\n\t\tsetBuiltModel(ModelBuildType.SYMBOLIC, model);\n\t}\n\n\t/**\n\t * Load files containing an explicit list of transitions/etc. for subsequent model building.\n\t * @param statesFile File containing a list of states (optional, can be null)\n\t * @param transFile File containing the list of transitions (required)\n\t * @param labelsFile File containing label definitions (optional, can be null)\n\t * @param stateRewardsFiles Files containing state reward definitions (optional, can be null)\n\t * @param typeOverride Model type (auto-detected if {@code null})\n\t */\n\tpublic void loadModelFromExplicitFiles(File statesFile, File transFile, File labelsFile, List<File> stateRewardsFiles, ModelType typeOverride) throws PrismException\n\t{\n\t\tloadModelFromExplicitFiles(statesFile, transFile, labelsFile, stateRewardsFiles, null, typeOverride);\n\t}\n\n\t/**\n\t * Load files containing an explicit list of transitions/etc. for subsequent model building.\n\t * @param statesFile File containing a list of states (optional, can be null)\n\t * @param transFile File containing the list of transitions (required)\n\t * @param labelsFile File containing label definitions (optional, can be null)\n\t * @param stateRewardsFiles Files containing state reward definitions (optional, can be null)\n\t * @param transRewardsFiles Files containing state reward definitions (optional, can be null)\n\t * @param typeOverride Model type (auto-detected if {@code null})\n\t */\n\tpublic void loadModelFromExplicitFiles(File statesFile, File transFile, File labelsFile, List<File> stateRewardsFiles, List<File> transRewardsFiles, ModelType typeOverride) throws PrismException\n\t{\n\t\tExplicitModelImporter importer = new PrismExplicitImporter(statesFile, transFile, labelsFile, stateRewardsFiles, transRewardsFiles, typeOverride);\n\t\tloadModelFromExplicitFiles(importer);\n\t}\n\n\t/**\n\t * Load a UMB file for subsequent model building.\n\t * @param umbFile The UMB file\n\t */\n\tpublic void loadModelFromUMBFile(File umbFile) throws PrismException\n\t{\n\t\tUMBImporter importer = new UMBImporter(umbFile);\n\t\tloadModelFromExplicitFiles(importer);\n\t}\n\n\t/**\n\t * Load an explicit file model importer for subsequent model building.\n\t */\n\tpublic void loadModelFromExplicitFiles(ExplicitModelImporter importer) throws PrismException\n\t{\n\t\tmainLog.println(\"\\nImporting model from \" + importer.sourceString() + \"...\");\n\t\t// Update model source info\n\t\tsetModelSource(ModelSource.EXPLICIT_FILES);\n\t\tsetPRISMModel(null);\n\t\tmodelImporter = importer;\n\t\t// Clear any existing built model(s)\n\t\tclearBuiltModel();\n\t\t// Get/store model/reward info from importer\n\t\tsetModelInfo(importer.getModelInfo());\n\t\tsetModelType(getModelInfo().getModelType());\n\t\tsetRewardInfo(importer.getRewardInfo());\n\t\tsetDefinedMFConstants(null);\n\t\t// Print basic model info\n\t\tprintModelInfo();\n\t}\n\n\t/**\n\t * Print basic info about the (unbuilt) current model: type, variables, etc.\n\t */\n\tprivate void printModelInfo() throws PrismException\n\t{\n\t\tprintModelInfo(getModelInfo(), getRewardInfo());\n\t}\n\n\t/**\n\t * Print basic info about an (unbuilt) model: type, variables, etc.\n\t * @param modelInfo The model info\n\t * @param rewardInfo The reward info (optional, can be null)\n\t */\n\tprivate void printModelInfo(ModelInfo modelInfo, RewardInfo rewardInfo) throws PrismException\n\t{\n\t\tmainLog.println();\n\t\tif (getModelSource() == ModelSource.EXPLICIT_FILES && modelImporter != null) {\n\t\t\tmainLog.println(\"Type:        \" + modelImporter.getModelTypeString());\n\t\t} else {\n\t\t\tmainLog.println(\"Type:        \" + modelInfo.getModelType());\n\t\t}\n\t\tif (modelInfo instanceof ModulesFile) {\n\t\t\tmainLog.println(\"Modules:     \" + String.join(\" \", ((ModulesFile) modelInfo).getModuleNames()));\n\t\t}\n\t\tif (modelInfo.getActions() != null) {\n\t\t\tmainLog.println(\"Actions:     \" + String.join(\" \", modelInfo.getBracketedActionStrings()));\n\t\t}\n\t\tmainLog.println(\"Variables:   \" + String.join(\" \", modelInfo.getVarNames()));\n\t\tif (modelInfo.getModelType().partiallyObservable()) {\n\t\t\tmainLog.println(\"Observables: \" + \"\\\"\" + String.join(\"\\\" \\\"\", modelInfo.getObservableNames()) + \"\\\"\");\n\t\t}\n\t\tif (modelInfo.getNumLabels() > 0) {\n\t\t\tmainLog.println(\"Labels:      \" + \"\\\"\" + String.join(\"\\\" \\\"\", modelInfo.getLabelNames()) + \"\\\"\");\n\t\t}\n\t\tif (rewardInfo != null && rewardInfo.getNumRewardStructs() > 0) {\n\t\t\tmainLog.println(\"Rewards:     \" + String.join(\" \", rewardInfo.getRewardStructReferences()));\n\t\t}\n\t}\n\n\t/**\n\t * Get the source of the currently loaded model (null if none/unknown).\n\t */\n\tpublic ModelSource getModelSource()\n\t{\n\t\treturn currentModelDetails.modelSource;\n\t}\n\n\t/**\n\t * Is the source of the currently loaded model digital clocks?\n\t */\n\tpublic boolean isModelSourceDigitalClocks()\n\t{\n\t\treturn currentModelDetails.modelDigitalClocks;\n\t}\n\n\t/**\n\t * Get the type of the currently loaded model (null if none/unknown).\n\t */\n\tpublic ModelType getModelType()\n\t{\n\t\treturn currentModelDetails.modelType;\n\t}\n\n\t/**\n\t * Get info about the currently loaded model (null if none/unknown).\n\t */\n\tpublic ModelInfo getModelInfo()\n\t{\n\t\treturn currentModelDetails.modelInfo;\n\t}\n\n\t/**\n\t * Get the currently stored (parsed) PRISM model.\n\t */\n\tpublic ModulesFile getPRISMModel()\n\t{\n\t\treturn currentModelDetails.modulesFile;\n\t}\n\n\t/**\n\t * Get the currently selected model checking engine.\n\t */\n\tpublic PrismEngine getCurrentEngine()\n\t{\n\t\tif (param) {\n\t\t\treturn PrismEngine.PARAM;\n\t\t} else if (settings.getBoolean(PrismSettings.PRISM_EXACT_ENABLED)) {\n\t\t\treturn PrismEngine.EXACT;\n\t\t} else if (getEngine() == Prism.EXPLICIT) {\n\t\t\treturn PrismEngine.EXPLICIT;\n\t\t} else {\n\t\t\treturn PrismEngine.SYMBOLIC;\n\t\t}\n\t}\n\t\n\t/**\n\t * Get the ModelGenerator for the currently loaded model.\n\t * This will have either have been loaded directly\n\t * using {@link #loadModelGenerator(ModelGenerator)}\n\t * or is created automatically, e.g., for a PRISM model that has been loaded\n\t * using {@link #loadPRISMModel(ModulesFile)}.\n\t * If it needs to be created, it will be stored as well as returned.\n\t * An accompanying reward generator may also be created.\n\t * Throw an explanatory exception if not possible.\n\t */\n\tpublic ModelGenerator<?> getModelGenerator() throws PrismException\n\t{\n\t\treturn getModelGenerator(true);\n\t}\n\n\t/**\n\t * Get access to the current model generator (optionally creating if missing).\n\t */\n\tprivate ModelGenerator<?> getModelGenerator(boolean buildIfMissing) throws PrismException\n\t{\n\t\t// Only rebuild if not already present\n\t\tif (currentModelDetails.modelGenerator == null && buildIfMissing) {\n\t\t\tswitch (getModelSource()) {\n\t\t\tcase PRISM_MODEL:\n\t\t\t\tif (getPRISMModel() != null) {\n\t\t\t\t\t// Create a model generator via ModulesFileModelGenerator\n\t\t\t\t\tModulesFileModelGenerator<?> mfmg = null;\n\t\t\t\t\tif (getCurrentEngine() == PrismEngine.PARAM) {\n\t\t\t\t\t\t// Parametric model checking uses functions\n\t\t\t\t\t\tmfmg = ModulesFileModelGenerator.createForRationalFunctions(getPRISMModel(), paramNames, paramLowerBounds, paramUpperBounds, this);\n\t\t\t\t\t} else if (getCurrentEngine() == PrismEngine.EXACT) {\n\t\t\t\t\t\t// Exact model checking uses rationals\n\t\t\t\t\t\tmfmg = ModulesFileModelGenerator.createForRationals(getPRISMModel(), this);\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// Anything else (explicit engine, simulation, etc.) uses doubles\n\t\t\t\t\t\tmfmg = ModulesFileModelGenerator.createForDoubles(getPRISMModel(), this);\n\t\t\t\t\t}\n\t\t\t\t\tsetModelGenerator(mfmg);\n\t\t\t\t\tsetRewardGenerator(mfmg);\n\t\t\t\t} else {\n\t\t\t\t\tthrow new PrismException(\"There is no currently loaded PRISM model\");\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase MODEL_GENERATOR:\n\t\t\t\t// Not present - must be an error\n\t\t\t\tthrow new PrismException(\"There is no currently loaded model generator\");\n\t\t\tcase BUILT_MODEL:\n\t\t\tcase EXPLICIT_FILES:\n\t\t\t\t// If possible, model building from files creates a ModelGenerator too \n\t\t\t\tbuildModelIfRequired();\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown model source\");\n\t\t\t}\n\t\t}\n\t\t// Default error message if we failed to create a ModelGenerator\n\t\tif (currentModelDetails.modelGenerator == null && buildIfMissing) {\n\t\t\tthrow new PrismException(\"Could not create a model generator\");\n\t\t}\n\t\treturn currentModelDetails.modelGenerator;\n\t}\n\n\t/**\n\t * Get the reward info for the currently loaded model.\n\t */\n\tpublic RewardInfo getRewardInfo() throws PrismException\n\t{\n\t\treturn currentModelDetails.rewardInfo;\n\t}\n\n\t/**\n\t * Get the RewardGenerator for the currently loaded model.\n\t */\n\tpublic RewardGenerator<?> getRewardGenerator() throws PrismException\n\t{\n\t\treturn currentModelDetails.rewardGenerator;\n\t}\n\n\t/**\n\t * Get the values that have been provided for undefined constants in the current model.\n\t */\n\tpublic Values getUndefinedModelValues()\n\t{\n\t\treturn currentModelDetails.definedMFConstants;\n\t}\n\n\t/**\n\t * Get the values that have been provided for undefined constants in the current model.\n\t */\n\tpublic boolean areUndefinedModelValuesExact()\n\t{\n\t\treturn currentModelDetails.definedMFConstantsAreExact;\n\t}\n\n\t/**\n\t * Get the currently stored built model.\n\t */\n\tpublic prism.Model<?> getBuiltModel()\n\t{\n\t\treturn currentModelDetails.model;\n\t}\n\n\t/**\n\t * Get the currently stored built symbolic model.\n\t */\n\tprivate symbolic.model.Model getBuiltModelSymbolic()\n\t{\n\t\treturn currentModelDetails.modelSymb;\n\t}\n\n\t/**\n\t * Get the currently stored built explicit model.\n\t */\n\tpublic explicit.Model<?> getBuiltModelExplicit()\n\t{\n\t\treturn currentModelDetails.modelExpl;\n\t}\n\n\t/**\n\t * Get the type of currently built model (null if not built).\n\t */\n\tpublic ModelBuildType getBuiltModelType()\n\t{\n\t\treturn currentModelDetails.modelBuildType;\n\t}\n\n\t/**\n\t * Returns true if the current model is of a type that can be built (e.g. not a PTA).\n\t */\n\tpublic boolean modelCanBeBuilt()\n\t{\n\t\tif (getModelType().realTime()) {\n\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get the model build type used/needed by a given model checking engine.\n\t * Returns null if model is not needed (or unknown).\n\t */\n\tpublic ModelBuildType getModelBuildTypeForEngine(PrismEngine engine)\n\t{\n\t\tswitch (engine) {\n\t\tcase EXPLICIT:\n\t\t\treturn ModelBuildType.EXPLICIT;\n\t\tcase SYMBOLIC:\n\t\t\treturn ModelBuildType.SYMBOLIC;\n\t\tcase EXACT:\n\t\t\treturn ModelBuildType.EXACT;\n\t\tcase PARAM:\n\t\t\treturn ModelBuildType.PARAM;\n\t\tdefault:\n\t\t\treturn null;\n\t\t}\n\t}\n\t\n\t/**\n\t * Returns true if the current model has been built (for the currently selected engine).\n\t */\n\tpublic boolean modelIsBuilt()\n\t{\n\t\tModelBuildType modelBuildTypeForEngine = getModelBuildTypeForEngine(getCurrentEngine());\n\t\treturn modelBuildTypeForEngine != null && getBuiltModelType() == modelBuildTypeForEngine;\n\t}\n\n\t/**\n\t * Returns true if the current model has been built (for any engine).\n\t */\n\tpublic boolean someModelIsBuilt()\n\t{\n\t\treturn getBuiltModelType() != null;\n\t}\n\n\t/**\n\t * Get the currently stored strategy (null if none)\n\t */\n\tpublic Strategy<?> getStrategy()\n\t{\n\t\treturn strategy;\n\t}\n\n\t/**\n\t * Build the currently loaded PRISM model and store for later use.\n\t * The built model can be accessed subsequently via either\n\t * {@link #getBuiltModel()} or {@link #getBuiltModelExplicit()},\n\t * depending on the engine currently selected.\n\t * Only call this to explicitly force a built; normally it is done automatically.\n\t */\n\tpublic void buildModel() throws PrismException\n\t{\n\t\tmainLog.printSeparator();\n\t\tchooseEngineForModelBuild();\n\t\tdoBuildModel();\n\t}\n\n\t/**\n\t * Build the currently loaded PRISM model, if it needs to be done,\n\t * i.e. if it has not been constructed yet for the current engine.\n\t */\n\tpublic void buildModelIfRequired() throws PrismException\n\t{\n\t\tchooseEngineForModelBuild();\n\t\tif (!modelIsBuilt())\n\t\t\tdoBuildModel();\n\t}\n\n\t/**\n\t * If required (based on model type), switch engine to enable building.\n\t */\n\tprivate void chooseEngineForModelBuild()\n\t{\n\t\t// For some models, automatically switch engine\n\t\tswitch (getModelType()) {\n\t\t\tcase IDTMC:\n\t\t\tcase IMDP:\n\t\t\tcase LTS:\n\t\t\tcase POMDP:\n\t\t\tcase IPOMDP:\n\t\t\t\tif (getCurrentEngine() == PrismEngine.SYMBOLIC) {\n\t\t\t\t\tmainLog.println(\"\\nSwitching to explicit engine, which supports \" + getModelType() + \"s...\");\n\t\t\t\t\tengineOld = getEngine();\n\t\t\t\t\tengineSwitched = true;\n\t\t\t\t\ttry {\n\t\t\t\t\t\tsetEngine(Prism.EXPLICIT);\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t// Won't happen\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t// For other models, switch engine back if changed earlier\n\t\t\tdefault:\n\t\t\t\tif (engineSwitched) {\n\t\t\t\t\ttry {\n\t\t\t\t\t\tsetEngine(engineOld);\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t// Won't happen\n\t\t\t\t\t}\n\t\t\t\t\tengineSwitched = false;\n\t\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Build the currently loaded PRISM model and store for later use.\n\t * The built model can be accessed subsequently via either\n\t * {@link #getBuiltModel()} or {@link #getBuiltModelExplicit()},\n\t * depending on the engine currently selected.\n\t */\n\tprivate void doBuildModel() throws PrismException\n\t{\n\t\tlong l; // timer\n\n\t\t// Clear any existing built model(s)\n\t\tclearBuiltModel();\n\n\t\ttry {\n\t\t\tif (getModelType().realTime()) {\n\t\t\t\tthrow new PrismException(\"You cannot build a \" + getModelType() + \" model explicitly, only perform model checking\");\n\t\t\t}\n\n\t\t\tmainLog.print(\"\\nBuilding model (engine:\" + getCurrentEngine().toString().toLowerCase() + \")...\\n\");\n\t\t\tif (getUndefinedModelValues() != null && getUndefinedModelValues().getNumValues() > 0)\n\t\t\t\tmainLog.println(\"Model constants: \" + getUndefinedModelValues());\n\n\t\t\t// Build model\n\t\t\tl = System.currentTimeMillis();\n\n\t\t\tswitch (getCurrentEngine()) {\n\t\t\tcase SYMBOLIC:\n\t\t\t\tsymbolic.model.Model newModelSymb;\n\t\t\t\tswitch (getModelSource()) {\n\t\t\t\tcase PRISM_MODEL:\n\t\t\t\t\tModules2MTBDD mod2mtbdd = new Modules2MTBDD(this, getPRISMModel());\n\t\t\t\t\tnewModelSymb = mod2mtbdd.translate();\n\t\t\t\t\tsetBuiltModel(ModelBuildType.SYMBOLIC, newModelSymb);\n\t\t\t\t\tbreak;\n\t\t\t\tcase MODEL_GENERATOR:\n\t\t\t\t\tModelGenerator2MTBDD modelGen2mtbdd = new ModelGenerator2MTBDD(this);\n\t\t\t\t\tModelGenerator<Double> modelGenDbl = (ModelGenerator<Double>) getModelGenerator();\n\t\t\t\t\tnewModelSymb = modelGen2mtbdd.build(modelGenDbl, (RewardGenerator<Double>) getRewardGenerator());\n\t\t\t\t\tsetBuiltModel(ModelBuildType.SYMBOLIC, newModelSymb);\n\t\t\t\t\tbreak;\n\t\t\t\tcase EXPLICIT_FILES:\n\t\t\t\t\tExplicitFiles2MTBDD expf2mtbdd = new ExplicitFiles2MTBDD(this);\n\t\t\t\t\tnewModelSymb = expf2mtbdd.build(modelImporter);\n\t\t\t\t\tsetBuiltModel(ModelBuildType.SYMBOLIC, newModelSymb);\n\t\t\t\t\t// No current support for building a ModelGenerator\n\t\t\t\t\t// (e.g. for simulation)\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Cannot do symbolic model construction for model source \" + getModelSource());\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase EXPLICIT:\n\t\t\tcase EXACT:\n\t\t\tcase PARAM:\n\t\t\t\texplicit.Model<?> newModelExpl;\n\t\t\t\tswitch (getModelSource()) {\n\t\t\t\tcase PRISM_MODEL:\n\t\t\t\tcase MODEL_GENERATOR:\n\t\t\t\t\ttry {\n\t\t\t\t\t\tgetModelGenerator();\n\t\t\t\t\t} catch (PrismException e){\n\t\t\t\t\t\tthrow e.prepend(\"Explicit engine: \");\n\t\t\t\t\t}\n\t\t\t\t\tConstructModel constructModel = new ConstructModel(this);\n\t\t\t\t\tconstructModel.setFixDeadlocks(getFixDeadlocks());\n\t\t\t\t\tnewModelExpl = constructModel.constructModel(getModelGenerator());\n\t\t\t\t\tsetBuiltModel(getModelBuildTypeForEngine(getCurrentEngine()), newModelExpl);\n\t\t\t\t\tbreak;\n\t\t\t\tcase EXPLICIT_FILES:\n\t\t\t\t\tExplicitFiles2Model expf2model = new ExplicitFiles2Model(this);\n\t\t\t\t\tEvaluator<?> eval = (getCurrentEngine() == PrismEngine.EXACT) ? Evaluator.forBigRational() : Evaluator.forDouble();\n\t\t\t\t\tnewModelExpl = expf2model.build(modelImporter, eval);\n\t\t\t\t\tsetBuiltModel(getModelBuildTypeForEngine(getCurrentEngine()), newModelExpl);\n\t\t\t\t\t// Also build a Model/RewardGenerator\n\t\t\t\t\t// (the latter since rewards are built later, the former e.g. for simulation)\n\t\t\t\t\tsetModelGenerator(new ModelModelGenerator<>(getBuiltModelExplicit(), getModelInfo()));\n\t\t\t\t\tExplicitFiles2Rewards<?> expf2rews = new ExplicitFiles2Rewards<>(this, modelImporter, getBuiltModelExplicit(), eval);\n\t\t\t\t\tsetRewardGenerator(expf2rews.getRewardGenerator());\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Cannot do explicit model construction for model source \" + getModelSource());\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown engine \" + getCurrentEngine());\n\t\t\t}\n\n\t\t\tl = System.currentTimeMillis() - l;\n\t\t\tmainLog.println(\"\\nTime for model construction: \" + l / 1000.0 + \" seconds.\");\n\n\t\t\t// In UMB test mode, to an export/import roundtrip\n\t\t\tif (testUMB && !(getModelSource() == ModelSource.EXPLICIT_FILES)) {\n\t\t\t\tFile umbTestFile;\n\t\t\t\ttry {\n\t\t\t\t\tumbTestFile = File.createTempFile(\"built\", \".umb\");\n\t\t\t\t\texportBuiltModel(umbTestFile, ModelExportFormat.UMB);\n\t\t\t\t} catch(java.io.IOException | PrismNotSupportedException e){\n\t\t\t\t\tumbTestFile = null;\n\t\t\t\t\tmainLog.printWarning(\"UMB export failed; skipping testing\");\n\t\t\t\t}\n\t\t\t\tif (umbTestFile != null) {\n\t\t\t\t\tValues constantsCached = getModelInfo().getConstantValues();\n\t\t\t\t\tclearBuiltModel();\n\t\t\t\t\tloadModelFromUMBFile(umbTestFile);\n\t\t\t\t\tbuildModel();\n\t\t\t\t\tgetModelInfo().setSomeUndefinedConstants(constantsCached);\n\t\t\t\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t\t\t\t((ModelSymbolic) getBuiltModelSymbolic()).setConstantValues(constantsCached);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// For digital clocks, do some extra checks on the built model\n\t\t\tif (isModelSourceDigitalClocks()) {\n\t\t\t\tdoBuildModelDigitalClocksChecks();\n\t\t\t}\n\n\t\t\t// Deal with deadlocks\n\t\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t\tStateList deadlocks = getBuiltModelSymbolic().getDeadlockStates();\n\t\t\t\tint numDeadlocks = deadlocks.size();\n\t\t\t\tif (numDeadlocks > 0) {\n\t\t\t\t\tif (getFixDeadlocks()) {\n\t\t\t\t\t\tmainLog.printWarning(\"Deadlocks detected and fixed in \" + numDeadlocks + \" states\");\n\t\t\t\t\t} else {\n\t\t\t\t\t\tgetBuiltModelSymbolic().printTransInfo(mainLog, getExtraDDInfo());\n\t\t\t\t\t\tmainLog.print(\"\\n\" + numDeadlocks + \" deadlock states found\");\n\t\t\t\t\t\tif (!getVerbose() && numDeadlocks > 10) {\n\t\t\t\t\t\t\tmainLog.print(\". The first 10 are below. Use verbose mode to view them all.\\n\");\n\t\t\t\t\t\t\tdeadlocks.print(mainLog, 10);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tmainLog.print(\":\\n\");\n\t\t\t\t\t\t\tdeadlocks.print(mainLog);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tmainLog.print(\"\\nTip: Use the \\\"fix deadlocks\\\" option to automatically add self-loops in deadlock states.\\n\");\n\t\t\t\t\t\tthrow new PrismException(\"Model contains \" + numDeadlocks + \" deadlock states\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\texplicit.StateValues deadlocks = getBuiltModelExplicit().getDeadlockStatesList();\n\t\t\t\tint numDeadlocks = getBuiltModelExplicit().getNumDeadlockStates();\n\t\t\t\tif (numDeadlocks > 0) {\n\t\t\t\t\tif (getFixDeadlocks()) {\n\t\t\t\t\t\tmainLog.printWarning(\"Deadlocks detected and fixed in \" + numDeadlocks + \" states\");\n\t\t\t\t\t} else {\n\t\t\t\t\t\tmainLog.print(getBuiltModelExplicit().infoStringTable());\n\t\t\t\t\t\tmainLog.print(\"\\n\" + numDeadlocks + \" deadlock states found\");\n\t\t\t\t\t\tif (!getVerbose() && numDeadlocks > 10) {\n\t\t\t\t\t\t\tmainLog.print(\". The first 10 are below. Use verbose mode to view them all.\\n\");\n\t\t\t\t\t\t\tdeadlocks.print(mainLog, 10);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tmainLog.print(\":\\n\");\n\t\t\t\t\t\t\tdeadlocks.print(mainLog);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tmainLog.print(\"\\nTip: Use the \\\"fix deadlocks\\\" option to automatically add self-loops in deadlock states.\\n\");\n\t\t\t\t\t\tthrow new PrismException(\"Model contains \" + numDeadlocks + \" deadlock states\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Print model stats\n\t\t\tmainLog.println();\n\t\t\tmainLog.println(\"Type:        \" + getBuiltModel().getModelType());\n\t\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t\tgetBuiltModelSymbolic().printTransInfo(mainLog, getExtraDDInfo());\n\t\t\t} else {\n\t\t\t\tmainLog.print(getBuiltModelExplicit().infoStringTable());\n\t\t\t}\n\n\t\t\t// Notify model listeners of build success\n\t\t\tfor (PrismModelListener listener : modelListeners) {\n\t\t\t\tif (listener != null)\n\t\t\t\t\tlistener.notifyModelBuildSuccessful();\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\t// Notify model listeners of build failure\n\t\t\tfor (PrismModelListener listener : modelListeners) {\n\t\t\t\tif (listener != null)\n\t\t\t\t\tlistener.notifyModelBuildFailed(e);\n\t\t\t}\n\t\t\t// Throw exception anyway\n\t\t\tthrow e;\n\t\t}\n\t}\n\n\tprivate void doBuildModelDigitalClocksChecks() throws PrismException\n\t{\n\t\t// For digital clocks, by construction, deadlocks can only occur from timelocks (and are not allowed)\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tStateList deadlocks = getBuiltModelSymbolic().getDeadlockStates();\n\t\t\tif (deadlocks.size() > 0) {\n\t\t\t\tthrow new PrismException(\"Timelock in PTA, e.g. in state (\" + deadlocks.getFirstAsValues() + \")\");\n\t\t\t}\n\t\t} else {\n\t\t\tif (getBuiltModelExplicit().getNumDeadlockStates() > 0) {\n\t\t\t\tint dl = getBuiltModelExplicit().getFirstDeadlockState();\n\t\t\t\tString dls = getBuiltModelExplicit().getStatesList().get(dl).toString(getModelInfo());\n\t\t\t\tthrow new PrismException(\"Timelock in PTA, e.g. in state \" + dls);\n\t\t\t}\n\t\t}\n\n\t\t/*// Create new model checker object and do model checking\n\t\tPropertiesFile pf = parsePropertiesString(\"filter(exists,!\\\"invariants\\\"); E[F!\\\"invariants\\\"]\");\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tModelChecker mc = new NondetModelChecker(this, currentModel, pf);\n\t\t\tif (((Boolean) mc.check(pf.getProperty(0)).getResult()).booleanValue()) {\n\t\t\t\tmainLog.println(mc.check(pf.getProperty(1)).getCounterexample());\n\t\t\t}\n\t\t\t//sv.pr\n\t\t\t//mainLog.println(\"XX\" + res.getResult());\n\t\t} else {\n\t\t\texplicit.StateModelChecker mc = new MDPModelChecker();\n\t\t\tmc.setLog(mainLog);\n\t\t\tmc.setSettings(settings);\n\t\t\tmc.setModulesFileAndPropertiesFile(currentModulesFile, pf);\n\t\t\texplicit.StateValues sv = mc.checkExpression(getBuiltModelExplicit(), pf.getProperty(0));\n\t\t\tsv.print(mainLog, 1);\n\t\t}*/\n\t}\n\n\t/**\n\t * Build a model from a PRISM modelling language description, storing it symbolically,\n\t * as MTBDDs) via explicit-state reachability and model construction.\n\t * It is assumed that all constants in the model file have been defined by now.  \n\t * @param modulesFile Model to build\n\t */\n\tpublic Model buildModelExplicit(ModulesFile modulesFile) throws PrismException\n\t{\n\t\tlong l; // timer\n\t\tConstructModel constructModel;\n\t\texplicit.Model<?> modelExpl;\n\t\tModel model;\n\t\tList<State> statesList;\n\n\t\tif (modulesFile.getModelType().realTime()) {\n\t\t\tthrow new PrismException(\"You cannot build a \" + modulesFile.getModelType() + \" model explicitly, only perform model checking\");\n\t\t}\n\n\t\tmainLog.print(\"\\nBuilding model...\\n\");\n\t\tif (getUndefinedModelValues() != null && getUndefinedModelValues().getNumValues() > 0)\n\t\t\tmainLog.println(\"Model constants: \" + getUndefinedModelValues());\n\n\t\tconstructModel = new ConstructModel(this);\n\t\tModelGenerator<Double> modelGen = ModulesFileModelGenerator.createForDoubles(modulesFile, this);\n\t\tmodelExpl = constructModel.constructModel(modelGen);\n\t\tstatesList = constructModel.getStatesList();\n\n\t\t// create Explicit2MTBDD object\n\t\tExplicitModel2MTBDD expm2mtbdd = new ExplicitModel2MTBDD(this);\n\n\t\t// build model\n\t\tl = System.currentTimeMillis();\n\t\tmodel = expm2mtbdd.buildModel((explicit.Model<Double>) modelExpl, statesList, modulesFile, false);\n\t\tl = System.currentTimeMillis() - l;\n\n\t\tmainLog.println(\"\\nTime for model construction: \" + l / 1000.0 + \" seconds.\");\n\n\t\treturn model;\n\t}\n\n\t/**\n\t * Export the currently loaded and parsed PRISM model to a file.\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\tpublic void exportPRISMModel(File file) throws FileNotFoundException, PrismException\n\t{\n\t\tmainLog.print(\"\\nExporting parsed PRISM file \");\n\t\tmainLog.println(getDestinationStringForFile(file));\n\t\tPrismLog tmpLog = getPrismLogForFile(file);\n\t\ttmpLog.print(getPRISMModel().toString());\n\t\t// tidy up\n\t\tif (file != null)\n\t\t\ttmpLog.close();\n\t}\n\n\t/**\n\t * Export the currently loaded and parsed PRISM model to a file,\n\t * after expanding all constants to their actual, defined values.\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\tpublic void exportPRISMModelWithExpandedConstants(File file) throws FileNotFoundException, PrismException\n\t{\n\t\tmainLog.print(\"\\nExporting parsed PRISM file (with constant expansion) \");\n\t\tmainLog.println(getDestinationStringForFile(file));\n\t\tPrismLog tmpLog = getPrismLogForFile(file);\n\t\tModulesFile mfTmp = (ModulesFile) getPRISMModel().deepCopy();\n\t\tmfTmp = (ModulesFile) mfTmp.replaceConstants(getPRISMModel().getConstantValues());\n\t\t// NB: Don't use simplify() here because doesn't work for the purposes of printing out\n\t\t// (e.g. loss of parentheses causes precedence problems)\n\t\ttmpLog.print(mfTmp.toString());\n\t\t// tidy up\n\t\tif (file != null)\n\t\t\ttmpLog.close();\n\t}\n\n\t/**\n\t * Export the current model, building it first if needed.\n\t * To configure which model parts are exported, use {@link #exportBuiltModelTask(ModelExportTask)}.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportBuiltModel(File file, ModelExportFormat exportFormat) throws PrismException\n\t{\n\t\texportBuiltModelTask(ModelExportTask.fromFormat(file, exportFormat));\n\t}\n\n\t/**\n\t * Export the current model, building it first if needed.\n\t * The format to use is specified within {@code exportOptions}.\n\t * To configure which model parts are exported, use {@link #exportBuiltModelTask(ModelExportTask)}\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModel(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\texportBuiltModelTask(ModelExportTask.fromOptions(file, exportOptions));\n\t}\n\n\t/**\n\t * Export the transition matrix/function for the current model, building it first if needed.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportBuiltModelTransitions(File file, ModelExportFormat exportFormat) throws PrismException\n\t{\n\t\t// This is equivalent to exportBuiltModel\n\t\texportBuiltModel(file, exportFormat);\n\t}\n\n\t/**\n\t * Export the transition matrix/function for the current model, building it first if needed.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModelTransitions(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\t// This is equivalent to exportBuiltModel\n\t\texportBuiltModel(file, exportOptions);\n\t}\n\n\t/**\n\t * Export the state rewards for the current model, building it first if needed.\n\t * If there is more than 1 reward structure, then multiple files are generated\n\t * (e.g. \"rew.sta\" becomes \"rew1.sta\", \"rew2.sta\", ...)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportBuiltModelStateRewards(File file, ModelExportFormat exportFormat) throws PrismException\n\t{\n\t\texportBuiltModelStateRewards(file, new ModelExportOptions(exportFormat));\n\t}\n\n\t/**\n\t * Export the state rewards for the current model, building it first if needed.\n\t * If there is more than 1 reward structure, then multiple files are generated\n\t * (e.g. \"rew.sta\" becomes \"rew1.sta\", \"rew2.sta\", ...)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModelStateRewards(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\tif (getRewardInfo().getNumRewardStructs() == 0) {\n\t\t\tmainLog.println(\"\\nOmitting state reward export as there are no reward structures\");\n\t\t\treturn;\n\t\t}\n\t\texportBuiltModelTask(new ModelExportTask(ModelExportTask.ModelExportEntity.STATE_REWARDS, file, exportOptions));\n\t}\n\n\t/**\n\t * Export the transition rewards for the current model, building it first if needed.\n\t * If there is more than 1 reward structure, then multiple files are generated\n\t * (e.g. \"rew.sta\" becomes \"rew1.sta\", \"rew2.sta\", ...)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportBuiltModelTransRewards(File file, ModelExportFormat exportFormat) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelTransRewards(file, new ModelExportOptions(exportFormat));\n\t}\n\n\t/**\n\t * Export the transition rewards for the current model, building it first if needed.\n\t * If there is more than 1 reward structure, then multiple files are generated\n\t * (e.g. \"rew.sta\" becomes \"rew1.sta\", \"rew2.sta\", ...)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModelTransRewards(File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\tif (getRewardInfo().getNumRewardStructs() == 0) {\n\t\t\tmainLog.println(\"\\nOmitting transition reward export as there are no reward structures\");\n\t\t\treturn;\n\t\t}\n\t\texportBuiltModelTask(new ModelExportTask(ModelExportTask.ModelExportEntity.TRANSITION_REWARDS, file, exportOptions));\n\t}\n\n\t/**\n\t * Export the states of the currently loaded model, building it first if needed.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportBuiltModelStates(File file, ModelExportFormat exportFormat) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelStates(file, new ModelExportOptions(exportFormat));\n\t}\n\n\t/**\n\t * Export the states of the currently loaded model, building it first if needed.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModelStates(File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelTask(new ModelExportTask(ModelExportTask.ModelExportEntity.STATES, file, exportOptions));\n\t}\n\n\t/**\n\t * Export the observations of the currently loaded (partially observable) loaded model, building it first if needed.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportBuiltModelObservations(File file, ModelExportFormat exportFormat) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelObservations(file, new ModelExportOptions(exportFormat));\n\t}\n\n\t/**\n\t * Export the observations of the currently loaded (partially observable) loaded model, building it first if needed.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModelObservations(File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\tif (!getModelType().partiallyObservable()) {\n\t\t\tmainLog.println(\"\\nOmitting observations export as the model is not partially observable\");\n\t\t\treturn;\n\t\t}\n\t\texportBuiltModelTask(new ModelExportTask(ModelExportTask.ModelExportEntity.OBSERVATIONS, file, exportOptions));\n\t}\n\n\t/**\n\t * Export the labels and satisfying states of the currently loaded model, building it first if needed.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportBuiltModelLabels(File file, ModelExportFormat exportFormat) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelLabels(file, new ModelExportOptions(exportFormat));\n\t}\n\n\t/**\n\t * Export the labels and satisfying states of the currently loaded model, building it first if needed.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModelLabels(File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelLabels(null, file, exportOptions);\n\t}\n\n\t/**\n\t * Export model, and optionally property file, labels and the satisfying states\n\t * of the currently loaded model, building it first if needed.\n\t * The PropertiesFile (if non-null) should correspond to the currently loaded model.\n\t * @param propertiesFile The properties file, for further labels (ignored if null)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModelLabels(PropertiesFile propertiesFile, File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\tModelExportTask exportTask = new ModelExportTask(ModelExportTask.ModelExportEntity.LABELS, file, exportOptions);\n\t\tif (propertiesFile != null) {\n\t\t\texportTask.setLabelExportSet(ModelExportTask.LabelExportSet.ALL);\n\t\t\texportTask.setExtraLabelsSource(propertiesFile);\n\t\t}\n\t\texportBuiltModelTask(exportTask);\n\t}\n\n\t/**\n\t * Export labels from a properties file and the satisfying states\n\t * of the currently loaded model, building it first if needed.\n\t * The PropertiesFile should correspond to the currently loaded model.\n\t * @param propertiesFile The properties file (for further labels)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportBuiltModelPropLabels(PropertiesFile propertiesFile, File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\tModelExportTask exportTask = new ModelExportTask(ModelExportTask.ModelExportEntity.LABELS, file, exportOptions);\n\t\texportTask.setLabelExportSet(ModelExportTask.LabelExportSet.EXTRA);\n\t\texportTask.setExtraLabelsSource(propertiesFile);\n\t\texportBuiltModelTask(exportTask);\n\t}\n\n\t/**\n\t * Export multiple model export tasks, building the model first if needed.\n\t * @param modelExportTasks List of export tasks\n\t */\n\tpublic void exportBuiltModelTasks(List<ModelExportTask> modelExportTasks) throws PrismException\n\t{\n\t\t// Build model, if necessary\n\t\t// (allows us to more easily compute the time for all exports)\n\t\tbuildModelIfRequired();\n\n\t\t// Then do export tasks\n\t\tmainLog.println();\n\t\tlong timer = System.currentTimeMillis();\n\t\tfor (ModelExportTask exportTask : modelExportTasks) {\n\t\t\texportBuiltModelTask(exportTask);\n\t\t}\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Time for exporting: \" + timer / 1000.0 + \" seconds.\");\n\t}\n\n\t/**\n\t * Perform an export task for the current model, building it first if needed.\n\t * @param exportTask Export task\n\t */\n\tpublic void exportBuiltModelTask(ModelExportTask exportTask) throws PrismException\n\t{\n\t\t// Skip non-applicable tasks\n\t\tif (!exportTask.isApplicable(getModelInfo())) {\n\t\t\treturn;\n\t\t}\n\t\t// NB: currently no engine auto-switch needed\n\t\t// Build model, if necessary\n\t\tbuildModelIfRequired();\n\t\t// Merge export options with PRISM settings and do export\n\t\tmainLog.println( exportTask.getMessage());\n\t\tModelExportOptions exportOptions = newMergedModelExportOptions(exportTask.getExportOptions());\n\t\tswitch (exportTask.getEntity()) {\n\t\t\tcase MODEL:\n\t\t\t\tdoExportBuiltModel(new ModelExportTask(exportTask, exportOptions));\n\t\t\t\tbreak;\n\t\t\tcase STATE_REWARDS:\n\t\t\t\tdoExportBuiltModelStateRewards(exportTask.getFile(), exportOptions);\n\t\t\t\tbreak;\n\t\t\tcase TRANSITION_REWARDS:\n\t\t\t\tdoExportBuiltModelTransRewards(exportTask.getFile(), exportOptions);\n\t\t\t\tbreak;\n\t\t\tcase STATES:\n\t\t\t\tdoExportBuiltModelStates(exportTask.getFile(), exportOptions);\n\t\t\t\tbreak;\n\t\t\tcase OBSERVATIONS:\n\t\t\t\tdoExportBuiltModelObservations(exportTask.getFile(), exportOptions);\n\t\t\t\tbreak;\n\t\t\tcase LABELS:\n\t\t\t\tdoExportBuiltModelLabels(new ModelExportTask(exportTask, exportOptions));\n\t\t\t\tbreak;\n\t\t}\n\t}\n\n\t/**\n\t * Export the transition matrix/function for the current built model.\n\t * This assumes that the model has already been built.\n\t * Various other parts/annotations of the model may also be exported,\n\t * as specified by the {@code exportTask} object.\n\t * @param exportTask Export task (destination, which parts of the model to export, options)\n\t */\n\tprivate void doExportBuiltModel(ModelExportTask exportTask) throws PrismException\n\t{\n\t\t// Export via either symbolic/explicit model checker\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t// In some cases, we need to convert to an explicit model first\n\t\t\tif (exportTask.getExportOptions().getFormat() == ModelExportFormat.DRN || exportTask.getExportOptions().getFormat() == ModelExportFormat.UMB) {\n\t\t\t\tMTBDD2ExplicitModel m2m = new MTBDD2ExplicitModel(this);\n\t\t\t\texplicit.Model<Double> modelExpl = m2m.convertModel(getBuiltModelSymbolic());\n\t\t\t\texplicit.StateModelChecker mcExpl = explicit.StateModelChecker.createModelChecker(getModelType(), this);\n\t\t\t\tRewardGenerator<Double> rewardGen = m2m.getRewardConverter(getBuiltModelSymbolic(), modelExpl, getRewardInfo());\n\t\t\t\tmcExpl.setModelCheckingInfo(getModelInfo(), null, rewardGen);\n\t\t\t\tmcExpl.exportModel(modelExpl, exportTask);\n\t\t\t} else {\n\t\t\t\tsymbolic.comp.StateModelChecker mcSymb = createModelChecker(null);\n\t\t\t\tmcSymb.exportModel(exportTask);\n\t\t\t}\n\t\t} else {\n\t\t\texplicit.StateModelChecker mcExpl = createModelCheckerExplicit(null);\n\t\t\tmcExpl.exportModel(getBuiltModelExplicit(), exportTask);\n\t\t}\n\t}\n\n\t/**\n\t * Export the state rewards for the current built model.\n\t * This assumes that the model has already been built.\n\t * If there is more than 1 reward structure, then multiple files are generated\n\t * (e.g. \"rew.sta\" becomes \"rew1.sta\", \"rew2.sta\", ...)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tprivate void doExportBuiltModelStateRewards(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\t// Export to multiple files if necessary\n\t\tList <String> files = new ArrayList<>();\n\t\tint numRewardStructs = getRewardInfo().getNumRewardStructs();\n\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\tString filename = (file != null) ? file.getPath() : null;\n\t\t\tif (filename != null && numRewardStructs > 1) {\n\t\t\t\tfilename = PrismUtils.addCounterSuffixToFilename(filename, r + 1);\n\t\t\t\tfiles.add(filename);\n\t\t\t}\n\t\t\tFile fileToUse = (filename == null) ? null : new File(filename);\n\t\t\t// Export via either symbolic/explicit model checker\n\t\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t\tsymbolic.comp.StateModelChecker mcSymb = createModelChecker(null);\n\t\t\t\tmcSymb.exportStateRewards(r, fileToUse, exportOptions);\n\t\t\t} else {\n\t\t\t\texplicit.StateModelChecker mcExpl = createModelCheckerExplicit(null);\n\t\t\t\tmcExpl.exportStateRewards(getBuiltModelExplicit(), r, fileToUse, exportOptions);\n\t\t\t}\n\t\t}\n\t\tif (files.size() > 1) {\n\t\t\tmainLog.println(\"Rewards were exported to multiple files: \" + PrismUtils.joinString(files, \",\"));\n\t\t}\n\t}\n\n\t/**\n\t * Export the transition rewards for the current built model.\n\t * This assumes that the model has already been built.\n\t * If there is more than 1 reward structure, then multiple files are generated\n\t * (e.g. \"rew.sta\" becomes \"rew1.sta\", \"rew2.sta\", ...)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tprivate void doExportBuiltModelTransRewards(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\t// Export to multiple files if necessary\n\t\tList <String> files = new ArrayList<>();\n\t\tint numRewardStructs = getRewardInfo().getNumRewardStructs();\n\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\tString filename = (file != null) ? file.getPath() : null;\n\t\t\tif (filename != null && numRewardStructs > 1) {\n\t\t\t\tfilename = PrismUtils.addCounterSuffixToFilename(filename, r + 1);\n\t\t\t\tfiles.add(filename);\n\t\t\t}\n\t\t\tFile fileToUse = (filename == null) ? null : new File(filename);\n\t\t\t// Export via either symbolic/explicit model checker\n\t\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t\tsymbolic.comp.StateModelChecker mcSymb = createModelChecker(null);\n\t\t\t\tmcSymb.exportTransRewards(r, fileToUse, exportOptions);\n\t\t\t} else {\n\t\t\t\texplicit.StateModelChecker mcExpl = createModelCheckerExplicit(null);\n\t\t\t\tmcExpl.exportTransRewards(getBuiltModelExplicit(), r, fileToUse, exportOptions);\n\t\t\t}\n\t\t}\n\t\tif (files.size() > 1) {\n\t\t\tmainLog.println(\"Rewards were exported to multiple files: \" + PrismUtils.joinString(files, \",\"));\n\t\t}\n\t}\n\n\t/**\n\t * Export the states of the currently built model.\n\t * This assumes that the model has already been built.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tprivate void doExportBuiltModelStates(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\t// Export via either symbolic/explicit model checker\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tsymbolic.comp.StateModelChecker mcSymb = createModelChecker(null);\n\t\t\tmcSymb.exportStates(file, exportOptions);\n\t\t} else {\n\t\t\texplicit.StateModelChecker mcExpl = createModelCheckerExplicit(null);\n\t\t\tmcExpl.exportStates(getBuiltModelExplicit(), file, exportOptions);\n\t\t}\n\t}\n\n\t/**\n\t * Export the observations of the current built (partially observable) model.\n\t * This assumes that the model has already been built.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tprivate void doExportBuiltModelObservations(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\t// Export (explicit engine only)\n\t\texplicit.StateModelChecker mcExpl = createModelCheckerExplicit(null);\n\t\tmcExpl.exportObservations(getBuiltModelExplicit(), file, exportOptions);\n\t}\n\n\t/**\n\t * Export the states satisfying a set of labels, as specified in a ModelExportTask.\n\t * @param exportTask Export task (destination, which labels to export, options)\n\t */\n\tprivate void doExportBuiltModelLabels(ModelExportTask exportTask) throws PrismException\n\t{\n\t\t// Collect names of labels to export from model and/or properties file\n\t\tList<String> labelNames = new ArrayList<>();\n\t\tif (exportTask.getLabelExportSet() == ModelExportTask.LabelExportSet.MODEL || exportTask.getLabelExportSet() == ModelExportTask.LabelExportSet.ALL) {\n\t\t\tif (exportTask.initLabelIncluded()) {\n\t\t\t\tlabelNames.add(\"init\");\n\t\t\t}\n\t\t\tif (exportTask.deadlockLabelIncluded()) {\n\t\t\t\tlabelNames.add(\"deadlock\");\n\t\t\t}\n\t\t\tlabelNames.addAll(getModelInfo().getLabelNames());\n\t\t}\n\t\tif (exportTask.getLabelExportSet() == ModelExportTask.LabelExportSet.EXTRA || exportTask.getLabelExportSet() == ModelExportTask.LabelExportSet.ALL) {\n\t\t\tLabelList ll = exportTask.getExtraLabelsSource().getLabelList();\n\t\t\tnew Range(ll.size()).map((int i) -> ll.getLabelName(i)).collect(labelNames);\n\t\t}\n\t\t// Export via either symbolic/explicit model checker\n\t\tPropertiesFile propertiesFile = exportTask.getExtraLabelsSource();\n\t\tFile file = exportTask.getFile();\n\t\tModelExportOptions exportOptions = exportTask.getExportOptions();\n\t\tif (getBuiltModelType() != ModelBuildType.SYMBOLIC) {\n\t\t\texplicit.StateModelChecker mcExpl = createModelCheckerExplicit(propertiesFile);\n\t\t\tmcExpl.exportLabels(getBuiltModelExplicit(), labelNames, file, exportOptions);\n\t\t} else {\n\t\t\tsymbolic.comp.StateModelChecker mcSymb = createModelChecker(propertiesFile);\n\t\t\tmcSymb.exportLabels(labelNames, file, exportOptions);\n\t\t}\n\t}\n\n\t/**\n\t * Export the currently loaded model's bottom strongly connected components (BSCCs) to a file\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN} \n\t * <li> {@link #EXPORT_MATLAB}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\tpublic void exportBSCCsToFile(int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\tint i, n;\n\t\tlong l; // timer\n\t\tPrismLog tmpLog;\n\t\tSCCComputer sccComputer = null;\n\t\texplicit.SCCConsumerStore sccConsumerExpl = null;\n\t\t//Vector<JDDNode> bsccs;\n\t\t//JDDNode not, bscc;\n\n\t\t// rows format does not apply to states output\n\t\tif (exportType == EXPORT_ROWS)\n\t\t\texportType = EXPORT_PLAIN;\n\n\t\t// Build model, if necessary\n\t\tbuildModelIfRequired();\n\n\t\t// Compute BSCCs\n\t\tmainLog.println(\"\\nComputing BSCCs...\");\n\t\tl = System.currentTimeMillis();\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tsccComputer = getSCCComputer(getBuiltModelSymbolic());\n\t\t\tsccComputer.computeBSCCs();\n\t\t} else {\n\t\t\tsccConsumerExpl = new explicit.SCCConsumerStore();\n\t\t\tgetExplicitSCCComputer(getBuiltModelExplicit(), sccConsumerExpl).computeSCCs();\n\t\t}\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"\\nTime for BSCC computation: \" + l / 1000.0 + \" seconds.\");\n\n\t\t// print message\n\t\tmainLog.print(\"\\nExporting BSCCs \");\n\t\tmainLog.print(getStringForExportType(exportType) + \" \");\n\t\tmainLog.println(getDestinationStringForFile(file));\n\n\t\t// create new file log or use main log\n\t\ttmpLog = getPrismLogForFile(file);\n\n\t\t// print header: list of model vars\n\t\tif (exportType == EXPORT_MATLAB)\n\t\t\ttmpLog.print(\"% \");\n\t\ttmpLog.print(\"Variables: (\");\n\t\tfor (i = 0; i < getModelInfo().getNumVars(); i++) {\n\t\t\ttmpLog.print(getModelInfo().getVarName(i));\n\t\t\tif (i < getModelInfo().getNumVars() - 1)\n\t\t\t\ttmpLog.print(\",\");\n\t\t}\n\t\ttmpLog.println(\")\");\n\n\t\t// print states for each bscc\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tn = sccComputer.getBSCCs().size();\n\t\t} else {\n\t\t\tn = sccConsumerExpl.getBSCCs().size();\n\t\t}\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ttmpLog.println();\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.print(\"% \");\n\t\t\ttmpLog.println(\"BSCC \" + (i + 1) + \"/\" + n + \":\");\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.println(\"bscc\" + (i + 1) + \"=[\");\n\t\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t\tif (exportType != EXPORT_MATLAB)\n\t\t\t\t\tnew StateListMTBDD(sccComputer.getBSCCs().get(i), getBuiltModelSymbolic()).print(tmpLog);\n\t\t\t\telse\n\t\t\t\t\tnew StateListMTBDD(sccComputer.getBSCCs().get(i), getBuiltModelSymbolic()).printMatlab(tmpLog);\n\t\t\t\tJDD.Deref(sccComputer.getBSCCs().get(i));\n\t\t\t} else {\n\t\t\t\texplicit.StateValues.createFromBitSet(sccConsumerExpl.getBSCCs().get(i), getBuiltModelExplicit()).print(tmpLog, true, exportType == EXPORT_MATLAB, true, true);\n\t\t\t}\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.println(\"];\");\n\t\t}\n\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tJDD.Deref(sccComputer.getNotInBSCCs());\n\t\t}\n\n\t\t// tidy up\n\t\tif (file != null)\n\t\t\ttmpLog.close();\n\t}\n\n\t/**\n\t * Export the (states of the) currently loaded model's maximal end components (MECs) to a file\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN} \n\t * <li> {@link #EXPORT_MATLAB}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\tpublic void exportMECsToFile(int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\tint i, n;\n\t\tlong l; // timer\n\t\tPrismLog tmpLog;\n\t\tECComputer ecComputer = null;\n\t\texplicit.ECComputer ecComputerExpl = null;\n\n\t\t// rows format does not apply to states output\n\t\tif (exportType == EXPORT_ROWS)\n\t\t\texportType = EXPORT_PLAIN;\n\n\t\t// Build model, if necessary\n\t\tbuildModelIfRequired();\n\n\t\t// Compute MECs\n\t\tmainLog.println(\"\\nComputing MECs...\");\n\t\tl = System.currentTimeMillis();\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tecComputer = getECComputer((NondetModel) getBuiltModelSymbolic());\n\t\t\tecComputer.computeMECStates();\n\t\t} else {\n\t\t\tecComputerExpl = getExplicitECComputer((explicit.NondetModel<?>) getBuiltModelExplicit());\n\t\t\tecComputerExpl.computeMECStates();\n\t\t}\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"\\nTime for MEC computation: \" + l / 1000.0 + \" seconds.\");\n\n\t\t// print message\n\t\tmainLog.print(\"\\nExporting MECs \");\n\t\tmainLog.print(getStringForExportType(exportType) + \" \");\n\t\tmainLog.println(getDestinationStringForFile(file));\n\n\t\t// create new file log or use main log\n\t\ttmpLog = getPrismLogForFile(file);\n\n\t\t// print header: list of model vars\n\t\tif (exportType == EXPORT_MATLAB)\n\t\t\ttmpLog.print(\"% \");\n\t\ttmpLog.print(\"Variables: (\");\n\t\tfor (i = 0; i < getModelInfo().getNumVars(); i++) {\n\t\t\ttmpLog.print(getModelInfo().getVarName(i));\n\t\t\tif (i < getModelInfo().getNumVars() - 1)\n\t\t\t\ttmpLog.print(\",\");\n\t\t}\n\t\ttmpLog.println(\")\");\n\n\t\t// print states for each mec\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tn = ecComputer.getMECStates().size();\n\t\t} else {\n\t\t\tn = ecComputerExpl.getMECStates().size();\n\t\t}\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ttmpLog.println();\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.print(\"% \");\n\t\t\ttmpLog.println(\"MEC \" + (i + 1) + \"/\" + n + \":\");\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.println(\"mec\" + (i + 1) + \"=[\");\n\t\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t\tif (exportType != EXPORT_MATLAB)\n\t\t\t\t\tnew StateListMTBDD(ecComputer.getMECStates().get(i), getBuiltModelSymbolic()).print(tmpLog);\n\t\t\t\telse\n\t\t\t\t\tnew StateListMTBDD(ecComputer.getMECStates().get(i), getBuiltModelSymbolic()).printMatlab(tmpLog);\n\t\t\t\tJDD.Deref(ecComputer.getMECStates().get(i));\n\t\t\t} else {\n\t\t\t\texplicit.StateValues.createFromBitSet(ecComputerExpl.getMECStates().get(i), getBuiltModelExplicit()).print(tmpLog, true, exportType == EXPORT_MATLAB,\n\t\t\t\t\t\ttrue, true);\n\t\t\t}\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.println(\"];\");\n\t\t}\n\n\t\t// tidy up\n\t\tif (file != null)\n\t\t\ttmpLog.close();\n\t}\n\n\t/**\n\t * Export the (states of the) currently loaded model's strongly connected components (SCCs) to a file\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN} \n\t * <li> {@link #EXPORT_MATLAB}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\tpublic void exportSCCsToFile(int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\tint i, n;\n\t\tlong l; // timer\n\t\tPrismLog tmpLog;\n\t\tSCCComputer sccComputer = null;\n\t\texplicit.SCCConsumerStore sccConsumerExpl = null;\n\n\t\t// rows format does not apply to states output\n\t\tif (exportType == EXPORT_ROWS)\n\t\t\texportType = EXPORT_PLAIN;\n\n\t\t// Build model, if necessary\n\t\tbuildModelIfRequired();\n\n\t\t// Compute SCCs\n\t\tmainLog.println(\"\\nComputing SCCs...\");\n\t\tl = System.currentTimeMillis();\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tsccComputer = getSCCComputer(getBuiltModelSymbolic());\n\t\t\tsccComputer.computeSCCs();\n\t\t} else {\n\t\t\tsccConsumerExpl = new explicit.SCCConsumerStore();\n\t\t\tgetExplicitSCCComputer(getBuiltModelExplicit(), sccConsumerExpl).computeSCCs();\n\t\t}\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"\\nTime for SCC computation: \" + l / 1000.0 + \" seconds.\");\n\n\t\t// print message\n\t\tmainLog.print(\"\\nExporting SCCs \");\n\t\tmainLog.print(getStringForExportType(exportType) + \" \");\n\t\tmainLog.println(getDestinationStringForFile(file));\n\n\t\t// create new file log or use main log\n\t\ttmpLog = getPrismLogForFile(file);\n\n\t\t// print header: list of model vars\n\t\tif (exportType == EXPORT_MATLAB)\n\t\t\ttmpLog.print(\"% \");\n\t\ttmpLog.print(\"Variables: (\");\n\t\tfor (i = 0; i < getModelInfo().getNumVars(); i++) {\n\t\t\ttmpLog.print(getModelInfo().getVarName(i));\n\t\t\tif (i < getModelInfo().getNumVars() - 1)\n\t\t\t\ttmpLog.print(\",\");\n\t\t}\n\t\ttmpLog.println(\")\");\n\n\t\t// print states for each scc\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tn = sccComputer.getSCCs().size();\n\t\t} else {\n\t\t\tn = sccConsumerExpl.getSCCs().size();\n\t\t}\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ttmpLog.println();\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.print(\"% \");\n\t\t\ttmpLog.println(\"SCC \" + (i + 1) + \"/\" + n + \":\");\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.println(\"scc\" + (i + 1) + \"=[\");\n\t\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\t\tif (exportType != EXPORT_MATLAB)\n\t\t\t\t\tnew StateListMTBDD(sccComputer.getSCCs().get(i), getBuiltModelSymbolic()).print(tmpLog);\n\t\t\t\telse\n\t\t\t\t\tnew StateListMTBDD(sccComputer.getSCCs().get(i), getBuiltModelSymbolic()).printMatlab(tmpLog);\n\t\t\t\tJDD.Deref(sccComputer.getSCCs().get(i));\n\t\t\t} else {\n\t\t\t\texplicit.StateValues.createFromBitSet(sccConsumerExpl.getSCCs().get(i), getBuiltModelExplicit()).print(tmpLog, true, exportType == EXPORT_MATLAB, true, true);\n\t\t\t}\n\t\t\tif (exportType == EXPORT_MATLAB)\n\t\t\t\ttmpLog.println(\"];\");\n\t\t}\n\n\t\tif (getBuiltModelType() == ModelBuildType.SYMBOLIC) {\n\t\t\tJDD.Deref(sccComputer.getNotInSCCs());\n\t\t}\n\n\t\t// tidy up\n\t\tif (file != null)\n\t\t\ttmpLog.close();\n\t}\n\n\t/**\n\t * Return a new {@code ModelExportOptions} object with any relevant PRISM settings applied,\n\t * then merged with the passed export options (which take precedence).\n\t */\n\tprivate ModelExportOptions newMergedModelExportOptions(ModelExportOptions exportOptions)\n\t{\n\t\tModelExportOptions newExportOptions = new ModelExportOptions();\n\t\tnewExportOptions.setModelPrecision(settings.getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION));\n\t\tnewExportOptions.setPrintHeaders(settings.getBoolean(PrismSettings.PRISM_EXPORT_MODEL_HEADERS));\n\t\tnewExportOptions.apply(exportOptions);\n\t\treturn newExportOptions;\n\t}\n\n\t/**\n\t * Perform model checking of a property on the currently loaded model and return result.\n\t * Here, the property is passed as a string and parsed first. Usually, you would use the other\n\t * model checking methods which assume you have already parsed the property separately.\n\t * This is just a simplified method for convenience. The property string can in fact be a whole\n\t * properties file, e.g. you can define labels/constants/etc. too, but an exception will be\n\t * thrown if there is more than one property present.    \n\t * @param propertyString The property (in fact properties file) to check as a string\n\t */\n\tpublic Result modelCheck(String propertyString) throws PrismException\n\t{\n\t\tPropertiesFile propertiesFile = parsePropertiesString(propertyString);\n\t\tif (propertiesFile.getNumProperties() != 1) {\n\t\t\tthrow new PrismException(\"There should be exactly one property to check (there are \" + propertiesFile.getNumProperties() + \")\");\n\t\t}\n\t\treturn modelCheck(propertiesFile, propertiesFile.getPropertyObject(0));\n\t}\n\n\t/**\n\t * Perform model checking of a property on the currently loaded model and return result.\n\t * @param propertiesFile Parent property file of property (for labels/constants/...)\n\t * @param expr The property to check\n\t */\n\tpublic Result modelCheck(PropertiesFile propertiesFile, Expression expr) throws PrismException, PrismLangException\n\t{\n\t\treturn modelCheck(propertiesFile, new Property(expr));\n\t}\n\n\t/**\n\t * Perform model checking of a property on the currently loaded model and return result.\n\t * @param propertiesFile Parent property file of property (for labels/constants/...)\n\t * @param prop The property to check\n\t */\n\tpublic Result modelCheck(PropertiesFile propertiesFile, Property prop) throws PrismException, PrismLangException\n\t{\n\t\tResult res = null;\n\t\tValues definedPFConstants = propertiesFile.getConstantValues();\n\t\tboolean engineSwitch = false, switchToMTBDDEngine = false, switchedToExplicitEngine = false;\n\t\tint lastEngine = -1;\n\n\t\tif (!isModelSourceDigitalClocks())\n\t\t\tmainLog.printSeparator();\n\t\tmainLog.println(\"\\nModel checking: \" + prop);\n\t\tif (getUndefinedModelValues() != null && getUndefinedModelValues().getNumValues() > 0)\n\t\t\tmainLog.println(\"Model constants: \" + getUndefinedModelValues());\n\t\tif (definedPFConstants != null && definedPFConstants.getNumValues() > 0)\n\t\t\tmainLog.println(\"Property constants: \" + definedPFConstants);\n\n\t\t// Check that property is valid for the current model type\n\t\tprop.getExpression().checkValid(getModelType());\n\n\t\t// Remove old strategy if present\n\t\tclearStrategy();\n\n\t\t// Exact model checking only support for some models\n\t\tif (getCurrentEngine() == PrismEngine.EXACT) {\n\t\t\tif (!(getModelType() == ModelType.DTMC || getModelType() == ModelType.CTMC || getModelType() == ModelType.MDP || !getModelType().isProbabilistic())) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Exact model checking not supported for \" + getModelType() + \"s\");\n\t\t\t}\n\t\t}\n\t\t// Parametric model checking only support for some models/settings\n\t\tif (getCurrentEngine() == PrismEngine.PARAM) {\n\t\t\tif (!(getModelType() == ModelType.DTMC || getModelType() == ModelType.CTMC || getModelType() == ModelType.MDP || !getModelType().isProbabilistic())) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Parametric model checking not supported for \" + getModelType() + \"s\");\n\t\t\t}\n\t\t\tif (getModelType() == ModelType.MDP && getFairness()) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Parametric model checking does not support checking MDPs under fairness\");\n\t\t\t}\n\t\t}\n\t\t// PTA (and similar) model checking is handled separately\n\t\tif (getModelType().realTime()) {\n\t\t\treturn modelCheckPTA(propertiesFile, prop.getExpression(), definedPFConstants);\n\t\t}\n\t\t// For fast adaptive uniformisation\n\t\tif (getModelType() == ModelType.CTMC && settings.getString(PrismSettings.PRISM_TRANSIENT_METHOD).equals(\"Fast adaptive uniformisation\")) {\n\t\t\tFastAdaptiveUniformisationModelChecker fauMC;\n\t\t\tfauMC = new FastAdaptiveUniformisationModelChecker(this, getPRISMModel(), propertiesFile);\n\t\t\treturn fauMC.check(prop.getExpression());\n\t\t}\n\t\t// Heuristic choices of engine/method\n\t\tif (settings.getString(PrismSettings.PRISM_HEURISTIC).equals(\"Speed\")) {\n\t\t\tmainLog.printWarning(\"Switching to sparse engine and (backwards) Gauss Seidel (default for heuristic=speed).\");\n\t\t\tengineSwitch = true;\n\t\t\tlastEngine = getEngine();\n\t\t\tsetEngine(Prism.SPARSE);\n\t\t\tsettings.set(PrismSettings.PRISM_LIN_EQ_METHOD, \"Backwards Gauss-Seidel\");\n\n\t\t}\n\t\t// Auto-switch to explicit engine if required\n\t\tif (getModelType() == ModelType.MDP && !Expression.containsMultiObjective(prop.getExpression())) {\n\t\t\tif (getMDPSolnMethod() != Prism.MDP_VALITER && getCurrentEngine() == PrismEngine.SYMBOLIC) {\n\t\t\t\tmainLog.printWarning(\"Switching to explicit engine to allow use of chosen MDP solution method.\");\n\t\t\t\tengineSwitch = true;\n\t\t\t\tlastEngine = getEngine();\n\t\t\t\tswitchedToExplicitEngine = true;\n\t\t\t\tsetEngine(Prism.EXPLICIT);\n\t\t\t}\n\t\t}\n\t\tif (Expression.containsNonProbLTLFormula(prop.getExpression()) && getCurrentEngine() == PrismEngine.SYMBOLIC) {\n\t\t\tmainLog.printWarning(\"Switching to explicit engine to allow non-probabilistic LTL model checking.\");\n\t\t\tengineSwitch = true;\n\t\t\tlastEngine = getEngine();\n\t\t\tswitchedToExplicitEngine = true;\n\t\t\tsetEngine(Prism.EXPLICIT);\n\t\t}\n\t\tif (settings.getBoolean(PrismSettings.PRISM_INTERVAL_ITER) && getCurrentEngine() == PrismEngine.SYMBOLIC) {\n\t\t\tif (getModelType() == ModelType.MDP && Expression.containsMinReward(prop.getExpression())) {\n\t\t\t\tmainLog.printWarning(\"Switching to explicit engine to allow interval iteration on Rmin operator.\");\n\t\t\t\tengineSwitch = true;\n\t\t\t\tlastEngine = getEngine();\n\t\t\t\tswitchedToExplicitEngine = true;\n\t\t\t\tsetEngine(Prism.EXPLICIT);\n\t\t\t}\n\t\t}\n\t\tif ((getModelType() == ModelType.IDTMC || getModelType() == ModelType.IMDP) && getCurrentEngine() == PrismEngine.SYMBOLIC) {\n\t\t\tmainLog.printWarning(\"Switching to explicit engine to allow model checking of interval model.\");\n\t\t\tengineSwitch = true;\n\t\t\tlastEngine = getEngine();\n\t\t\tswitchedToExplicitEngine = true;\n\t\t\tsetEngine(Prism.EXPLICIT);\n\t\t}\n\t\tif (genStrat && getCurrentEngine() == PrismEngine.SYMBOLIC) {\n\t\t\tmainLog.printWarning(\"Switching to explicit engine to allow strategy generation.\");\n\t\t\tengineSwitch = true;\n\t\t\tlastEngine = getEngine();\n\t\t\tswitchedToExplicitEngine = true;\n\t\t\tsetEngine(Prism.EXPLICIT);\n\t\t}\n\t\ttry {\n\t\t\t// Build model, if necessary\n\t\t\tbuildModelIfRequired();\n\n\t\t\t// Compatibility check\n\t\t\tif (genStrat && getModelType().nondeterministic() && getCurrentEngine() == PrismEngine.SYMBOLIC) {\n\t\t\t\tif (!((NondetModel) getBuiltModelSymbolic()).areAllChoiceActionsUnique())\n\t\t\t\t\tthrow new PrismException(\"Cannot generate strategies with the current engine \"\n\t\t\t\t\t\t\t+ \"because some state of the model do not have unique action labels for each choice. \"\n\t\t\t\t\t\t\t+ \"Either switch to the explicit engine or add more action labels to the model\");\n\t\t\t}\n\n\t\t\t// Check if we need to switch to MTBDD engine\n\t\t\tif (getCurrentEngine() == PrismEngine.SYMBOLIC && getEngine() != MTBDD && !switchedToExplicitEngine) {\n\t\t\t\t// Either because number of states is two big for double-valued solution vectors\n\t\t\t\tif (getBuiltModelSymbolic().numStatesExceedsInt()) {\n\t\t\t\t\tmainLog.printWarning(\"Switching to MTBDD engine, as number of states is too large for \" + engineStrings[getEngine()] + \" engine.\");\n\t\t\t\t\tswitchToMTBDDEngine = true;\n\t\t\t\t}\n\t\t\t\t// Or based on heuristic choices of engine/method\n\t\t\t\t// (sparse/hybrid typically v slow if need to work with huge state spaces)\n\t\t\t\telse if (settings.getString(PrismSettings.PRISM_HEURISTIC).equals(\"Speed\") && getBuiltModelSymbolic().getNumStates() > MTBDD_STATES_THRESHOLD) {\n\t\t\t\t\tmainLog.printWarning(\"Switching to MTBDD engine (default for heuristic=speed and this state space size).\");\n\t\t\t\t\tswitchToMTBDDEngine = true;\n\t\t\t\t}\n\t\t\t\t// NB: Need to make sure solution methods supported for MTBDDs are used\n\t\t\t\tif (switchToMTBDDEngine) {\n\t\t\t\t\tengineSwitch = true;\n\t\t\t\t\tlastEngine = getEngine();\n\t\t\t\t\tsetEngine(Prism.MTBDD);\n\t\t\t\t\tsettings.set(PrismSettings.PRISM_LIN_EQ_METHOD, \"Jacobi\");\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Create new model checker object and do model checking\n\t\t\tif (getCurrentEngine() == PrismEngine.SYMBOLIC) {\n\t\t\t\tModelChecker mc = createModelChecker(propertiesFile);\n\t\t\t\tres = mc.check(prop.getExpression());\n\t\t\t} else if (getCurrentEngine() == PrismEngine.EXPLICIT) {\n\t\t\t\texplicit.StateModelChecker mc = createModelCheckerExplicit(propertiesFile);\n\t\t\t\tres = mc.check(getBuiltModelExplicit(), prop.getExpression());\n\t\t\t} else if (getCurrentEngine() == PrismEngine.EXACT) {\n\t\t\t\tParamModelChecker mc = new ParamModelChecker(this, ParamMode.EXACT);\n\t\t\t\tmc.setModelCheckingInfo(getModelInfo(), propertiesFile, getRewardGenerator());\n\t\t\t\tres = mc.check(getBuiltModelExplicit(), prop.getExpression());\n\t\t\t} else if (getCurrentEngine() == PrismEngine.PARAM) {\n\t\t\t\tParamModelChecker mc = new ParamModelChecker(this, ParamMode.PARAMETRIC);\n\t\t\t\tmc.setModelCheckingInfo(getModelInfo(), propertiesFile, getRewardGenerator());\n\t\t\t\tres = mc.check(getBuiltModelExplicit(), prop.getExpression());\n\t\t\t}\n\t\t\t\n\t\t\t// If model checking generated a strategy, store it\n\t\t\tif (res.getStrategy() != null) {\n\t\t\t\tstrategy = res.getStrategy();\n\t\t\t}\n\t\t} finally {\n\t\t\t// Undo auto-switch (if any)\n\t\t\tif (engineSwitch) {\n\t\t\t\tsetEngine(lastEngine);\n\t\t\t}\n\t\t}\n\n\t\t// Return result\n\t\treturn res;\n\t}\n\n\t/**\n\t * Perform model checking of a property on the currently loaded PTA PRISM model and return result.\n\t * @param propertiesFile Parent property file of property (for labels/constants/...)\n\t * @param expr The property to check\n\t * @param definedPFConstants Optional values info for properties file (to display in log) \n\t */\n\tpublic Result modelCheckPTA(PropertiesFile propertiesFile, Expression expr, Values definedPFConstants) throws PrismException, PrismLangException\n\t{\n\t\t// Check that property is valid for this model type\n\t\t// and create new model checker object\n\t\texpr.checkValid(getModelType());\n\n\t\t// Remove old strategy if present\n\t\tclearStrategy();\n\t\t\n\t\t// Digital clocks translation\n\t\tif (settings.getString(PrismSettings.PRISM_PTA_METHOD).equals(\"Digital clocks\") || getModelType() == ModelType.POPTA) {\n\t\t\tsetModelSourceIsDigitalClocks(true);\n\t\t\tModulesFile oldModulesFile = getPRISMModel();\n\t\t\ttry {\n\t\t\t\tDigitalClocks dc = new DigitalClocks(this);\n\t\t\t\tdc.translate(oldModulesFile, propertiesFile, expr);\n\t\t\t\tloadPRISMModel(dc.getNewModulesFile());\n\t\t\t\t// If required, export generated PRISM model\n\t\t\t\tif (exportDigital) {\n\t\t\t\t\ttry {\n\t\t\t\t\t\texportPRISMModel(exportDigitalFile);\n\t\t\t\t\t}\n\t\t\t\t\t// In case of error, just print a warning\n\t\t\t\t\tcatch (FileNotFoundException e) {\n\t\t\t\t\t\tmainLog.printWarning(\"PRISM code export failed: Couldn't open file \\\"\" + exportDigitalFile + \"\\\" for output\");\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\tmainLog.printWarning(\"PRISM code export failed: \" + e.getMessage());\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\treturn modelCheck(dc.getNewPropertiesFile(), dc.getNewPropertyToCheck());\n\t\t\t} finally {\n\t\t\t\tsetModelSourceIsDigitalClocks(false);\n\t\t\t\t// Preserve strategy (setting to null stops it being cleared with model)\n\t\t\t\tStrategy strategyDigital = strategy;\n\t\t\t\tstrategy = null;\n\t\t\t\t// Restore/clear model info\n\t\t\t\tsetPRISMModel(oldModulesFile);\n\t\t\t\tsetModelType(oldModulesFile.getModelType());\n\t\t\t\tclearBuiltModel();\n\t\t\t\t// Restore strategy\n\t\t\t\tstrategy = strategyDigital;\n\t\t\t}\n\t\t}\n\t\t// Other methods\n\t\telse {\n\t\t\tPTAModelChecker mcPta;\n\t\t\tmcPta = new PTAModelChecker(this, getPRISMModel(), propertiesFile);\n\t\t\treturn mcPta.check(expr);\n\t\t}\n\t}\n\n\t/**\n\t * Check if the currently loaded model is suitable for analysis with the simulator.\n\t * If not, an explanatory exception is thrown.\n\t */\n\tpublic void checkModelForSimulation() throws PrismException\n\t{\n\t\t// Get (but ignore) the ModelGenerator.\n\t\t// If creation failed before, this tries again, throwing an explanatory exception.\n\t\ttry {\n\t\t\tgetModelGenerator();\n\t\t\t// No support for real-time models yet\n\t\t\tif (getModelType().realTime()) {\n\t\t\t\tthrow new PrismException(getModelType() + \"s are not currently supported\");\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tthrow e.prepend(\"Simulation not possible: \");\n\t\t}\n\t}\n\n\t/**\n\t * Load the current model into the simulator.\n\t */\n\tpublic void loadModelIntoSimulator() throws PrismException\n\t{\n\t\t// Get the ModelGenerator.\n\t\t// If creation failed before, this tries again, throwing an explanatory exception.\n\t\tModelGenerator<?> modelGenForSim = null;\n\t\ttry {\n\t\t\tmodelGenForSim = getModelGenerator();\n\t\t} catch (PrismException e) {\n\t\t\tthrow e.prepend(\"Simulation not possible: \");\n\t\t}\n\t\t// Load into simulator\n\t\tgetSimulator().loadModel((ModelGenerator<Double>) modelGenForSim, (RewardGenerator<Double>) getRewardGenerator());\n\t}\n\n\t/**\n\t * Load the current strategy (if any) into the simulator.\n\t * Does nothing if there is no strategy to load, or is not able to be simulated.\n\t */\n\tpublic void loadStrategyIntoSimulator() throws PrismException\n\t{\n\t\tif (getStrategy() != null && getStrategy() instanceof StrategyGenerator) {\n\t\t\tgetSimulator().loadStrategy((StrategyGenerator) getStrategy());\n\t\t}\n\t}\n\n\t/**\n\t * Check whether a property is suitable for approximate model checking using the simulator.\n\t * @param expr The property to check.\n\t */\n\tpublic boolean isPropertyOKForSimulation(Expression expr)\n\t{\n\t\treturn getSimulator().isPropertyOKForSimulation(expr);\n\t}\n\n\t/**\n\t * Check if a property is suitable for analysis with the simulator.\n\t * If not, an explanatory exception is thrown.\n\t * @param expr The property to check.\n\t */\n\tpublic void checkPropertyForSimulation(Expression expr) throws PrismException\n\t{\n\t\tgetSimulator().checkPropertyForSimulation(expr);\n\t}\n\n\t/**\n\t * Perform approximate model checking of a property on the currently loaded model, using the simulator.\n\t * Sampling starts from the initial state provided or, if null, the default\n\t * initial state is used, selecting randomly (each time) if there are more than one.\n\t * Returns a Result object, except in case of error, where an Exception is thrown.\n\t * Note: All constants in the model/property files must have already been defined.\n\t * @param propertiesFile Parent property file of property (for labels/constants/...)\n\t * @param expr The property to check\n\t * @param definedPFConstants Optional values info for properties file (to display in log) \n\t * @param initialState Initial state (if null, use default, selecting randomly if needed)\n\t * @param maxPathLength The maximum path length for sampling\n\t * @param simMethod Object specifying details of method to use for simulation\n\t */\n\tpublic Result modelCheckSimulator(PropertiesFile propertiesFile, Expression expr, Values definedPFConstants, State initialState, long maxPathLength,\n\t\t\tSimulationMethod simMethod) throws PrismException\n\t{\n\t\tif (getCurrentEngine() == PrismEngine.EXACT) {\n\t\t\tthrow new PrismNotSupportedException(\"Simulation does not support exact computation\");\n\t\t}\n\n\t\t// Print info\n\t\tmainLog.printSeparator();\n\t\tmainLog.println(\"\\nSimulating: \" + expr);\n\t\tif (getUndefinedModelValues() != null && getUndefinedModelValues().getNumValues() > 0)\n\t\t\tmainLog.println(\"Model constants: \" + getUndefinedModelValues());\n\t\tif (definedPFConstants != null && definedPFConstants.getNumValues() > 0)\n\t\t\tmainLog.println(\"Property constants: \" + definedPFConstants);\n\n\t\tif (getModelType().nondeterministic() && getModelType().removeNondeterminism() != getModelType()) {\n\t\t\tmainLog.printWarning(\"For simulation, nondeterminism in \" + getModelType() + \" is resolved uniformly (resulting in \" + getModelType().removeNondeterminism() + \").\");\n\t\t}\n\n\t\t// Check that property is valid for this model type\n\t\texpr.checkValid(getModelType().removeNondeterminism());\n\n\t\t// Remove old strategy if present\n\t\tclearStrategy();\n\t\t\n\t\t// Do simulation\n\t\tloadModelIntoSimulator();\n\t\tResult res = getSimulator().modelCheckSingleProperty(propertiesFile, expr, initialState, maxPathLength, simMethod);\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Perform approximate model checking of several properties (simultaneously) on the currently loaded model, using the simulator.\n\t * Sampling starts from the initial state provided or, if null, the default\n\t * initial state is used, selecting randomly (each time) if there are more than one.\n\t * Returns an array of results, some of which may be Exception objects if there were errors.\n\t * In the case of an error which affects all properties, an exception is thrown.\n\t * Note: All constants in the model/property files must have already been defined.\n\t * @param propertiesFile Parent property file of property (for labels/constants/...)\n\t * @param exprs The properties to check\n\t * @param definedPFConstants Optional values info for properties file (to display in log) \n\t * @param initialState Initial state (if null, use default, selecting randomly if needed)\n\t * @param maxPathLength The maximum path length for sampling\n\t * @param simMethod Object specifying details of method to use for simulation\n\t */\n\tpublic Result[] modelCheckSimulatorSimultaneously(PropertiesFile propertiesFile, List<Expression> exprs, Values definedPFConstants, State initialState,\n\t\t\tlong maxPathLength, SimulationMethod simMethod) throws PrismException\n\t{\n\t\tif (getCurrentEngine() == PrismEngine.EXACT) {\n\t\t\tthrow new PrismNotSupportedException(\"Simulation does not support exact computation\");\n\t\t}\n\n\t\t// Print info\n\t\tmainLog.printSeparator();\n\t\tmainLog.print(\"\\nSimulating\");\n\t\tif (exprs.size() == 1) {\n\t\t\tmainLog.println(\": \" + exprs.get(0));\n\t\t} else {\n\t\t\tmainLog.println(\" \" + exprs.size() + \" properties:\");\n\t\t\tfor (int i = 0; i < exprs.size(); i++) {\n\t\t\t\tmainLog.println(\" \" + exprs.get(i));\n\t\t\t}\n\t\t}\n\t\tif (getUndefinedModelValues() != null && getUndefinedModelValues().getNumValues() > 0)\n\t\t\tmainLog.println(\"Model constants: \" + getUndefinedModelValues());\n\t\tif (definedPFConstants != null && definedPFConstants.getNumValues() > 0)\n\t\t\tmainLog.println(\"Property constants: \" + definedPFConstants);\n\n\t\tif (getModelType().nondeterministic() && getModelType().removeNondeterminism() != getModelType()) {\n\t\t\tmainLog.printWarning(\"For simulation, nondeterminism in \" + getModelType() + \" is resolved uniformly (resulting in \" + getModelType().removeNondeterminism() + \").\");\n\t\t}\n\n\t\t// Check that properties are valid for this model type\n\t\tfor (Expression expr : exprs)\n\t\t\texpr.checkValid(getModelType().removeNondeterminism());\n\n\t\t// Remove old strategy if present\n\t\tclearStrategy();\n\t\t\n\t\t// Do simulation\n\t\tloadModelIntoSimulator();\n\t\tResult[] resArray = getSimulator().modelCheckMultipleProperties(propertiesFile, exprs, initialState, maxPathLength, simMethod);\n\n\t\treturn resArray;\n\t}\n\n\t/**\n\t * Perform an approximate model checking experiment on the currently loaded model, using the simulator.\n\t * (specified by values for undefined constants from the property only).\n\t * Sampling starts from the initial state provided or, if null, the default\n\t * initial state is used, selecting randomly (each time) if there are more than one.\n\t * Results are stored in the ResultsCollection object passed in,\n\t * some of which may be Exception objects if there were errors.\n\t * In the case of an error which affects all properties, an exception is thrown.\n\t * Note: All constants in the model file must have already been defined.\n\t * @param propertiesFile Properties file containing property to check, constants defined\n\t * @param undefinedConstants Details of constant ranges defining the experiment\n\t * @param results Where to store the results\n\t * @param expr The property to check\n\t * @param initialState Initial state (if null, is selected randomly)\n\t * @param maxPathLength The maximum path length for sampling\n\t * @param simMethod Object specifying details of method to use for simulation\n\t * @throws PrismException if something goes wrong with the sampling algorithm\n\t * @throws InterruptedException if the thread is interrupted\n\t */\n\tpublic void modelCheckSimulatorExperiment(PropertiesFile propertiesFile, UndefinedConstants undefinedConstants, ResultsCollection results, Expression expr,\n\t\t\tState initialState, long maxPathLength, SimulationMethod simMethod) throws PrismException, InterruptedException\n\t{\n\t\tif (getCurrentEngine() == PrismEngine.EXACT) {\n\t\t\tthrow new PrismNotSupportedException(\"Simulation does not support exact computation\");\n\t\t}\n\n\t\t// Print info\n\t\tmainLog.printSeparator();\n\t\tmainLog.println(\"\\nSimulating: \" + expr);\n\t\tif (getUndefinedModelValues() != null && getUndefinedModelValues().getNumValues() > 0)\n\t\t\tmainLog.println(\"Model constants: \" + getUndefinedModelValues());\n\t\tmainLog.println(\"Property constants: \" + undefinedConstants.getPFDefinedConstantsString());\n\n\t\t// Remove old strategy if present\n\t\tclearStrategy();\n\t\t\n\t\t// Do simulation\n\t\tloadModelIntoSimulator();\n\t\tgetSimulator().modelCheckExperiment(propertiesFile, undefinedConstants, results, expr, initialState, maxPathLength, simMethod);\n\t}\n\n\t/**\n\t * Export the current strategy. The associated model should be attached to the strategy.\n\t * Strictly, speaking that does not need to be the currently loaded model,\n\t * but it would probably have been discarded if that was not the case.\n\t * @param exportOptions The options for export\n\t * @param file File to output the path to (stdout if null)\n\t */\n\tpublic void exportStrategy(StrategyExportOptions exportOptions, File file) throws FileNotFoundException, PrismException\n\t{\n\t\tif (getStrategy() != null) {\n\t\t\texportStrategy(getStrategy(), exportOptions, file);\n\t\t} else {\n\t\t\tthrow new PrismException(\"There is no current strategy to export\");\n\t\t}\n\t}\n\n\t/**\n\t * Export the current strategy. The associated model should be attached to the strategy.\n\t * Strictly, speaking that does not need to be the currently loaded model,\n\t * but it would probably have been discarded if that was not the case.\n\t * @param exportType The type of export\n\t * @param file File to output the path to (stdout if null)\n\t */\n\tpublic void exportStrategy(StrategyExportType exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportStrategy(new StrategyExportOptions(exportType), file);\n\t}\n\n\t/**\n\t * Export a strategy. The associated model should be attached to the strategy.\n\t * Strictly, speaking that does not need to be the currently loaded model,\n\t * but it would probably have been discarded if that was not the case.\n\t * @param strat The strategy\n\t * @param exportOptions The options for export\n\t * @param file File to output the path to (stdout if null)\n\t */\n\tpublic void exportStrategy(Strategy<?> strat, StrategyExportOptions exportOptions, File file) throws FileNotFoundException, PrismException\n\t{\n\t\t// Print message\n\t\tmainLog.print(\"\\nExporting strategy \" + exportOptions.description() + \" \");\n\t\tmainLog.println(getDestinationStringForFile(file));\n\n\t\t// Export to file (or use main log)\n\t\tPrismLog tmpLog = getPrismLogForFile(file);\n\t\texportOptions = exportOptions.clone();\n\t\texportOptions.setModelPrecision(settings.getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION));\n\t\tstrat.export(tmpLog, exportOptions);\n\t\tif (file != null) {\n\t\t\ttmpLog.close();\n\t\t}\n\t}\n\n\t/**\n\t * Export a strategy. The associated model should be attached to the strategy.\n\t * Strictly, speaking that does not need to be the currently loaded model,\n\t * but it would probably have been discarded if that was not the case.\n\t * @param strat The strategy\n\t * @param exportType The type of export\n\t * @param file File to output the path to (stdout if null)\n\t */\n\tpublic void exportStrategy(Strategy<?> strat, StrategyExportType exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportStrategy(strat, new StrategyExportOptions(exportType), file);\n\t}\n\n\t/**\n\t * Generate a random path through the currently loaded model using the simulator.\n\t * @param details Information about the path to be generated\n\t * @param maxPathLength The maximum length of path to generate\n\t * @param file File to output the path to (stdout if null)\n\t */\n\tpublic void generateSimulationPath(String details, long maxPathLength, File file) throws PrismException, PrismLangException\n\t{\n\t\tloadModelIntoSimulator();\n\t\tGenerateSimulationPath genPath = new GenerateSimulationPath(getSimulator(), mainLog);\n\t\tgenPath.generateSimulationPath(null, details, maxPathLength, file);\n\t}\n\n\t/**\n\t * Compute/export steady-state probabilities for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportSteadyStateProbabilities(File file, ModelExportFormat exportFormat) throws PrismException\n\t{\n\t\texportSteadyStateProbabilities(file, new ModelExportOptions(exportFormat), null);\n\t}\n\n\t/**\n\t * Compute/export steady-state probabilities for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t * @param initDistFile Initial distribution (ignored if null)\n\t */\n\tpublic void exportSteadyStateProbabilities(File file, ModelExportFormat exportFormat, File initDistFile) throws PrismException\n\t{\n\t\texportSteadyStateProbabilities(file, new ModelExportOptions(exportFormat), initDistFile);\n\t}\n\n\t/**\n\t * Compute/export steady-state probabilities for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t * @param initDistFile Initial distribution (ignored if null)\n\t */\n\tpublic void exportSteadyStateProbabilities(File file, ModelExportOptions exportOptions, File initDistFile) throws PrismException\n\t{\n\t\tprism.StateVector probs = computeSteadyStateProbabilities(initDistFile);\n\t\tmainLog.print(\"\\nExporting steady-state probabilities \");\n\t\tmainLog.println(exportOptions.getFormat().description() + \" \" + getDestinationStringForFile(file));\n\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\tprobs.print(out, file == null, exportOptions.getFormat() == ModelExportFormat.MATLAB, file == null, file == null);\n\t\t}\n\t\tprobs.clear();\n\t}\n\n\t/**\n\t * Compute steady-state probabilities for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @param initDistFile Initial distribution (ignored if null)\n\t */\n\tpublic prism.StateVector computeSteadyStateProbabilities(File initDistFile) throws PrismException\n\t{\n\t\tif (!(getModelType() == ModelType.CTMC || getModelType() == ModelType.DTMC)) {\n\t\t\tthrow new PrismException(\"Steady-state probabilities only computed for DTMCs/CTMCs\");\n\t\t}\n\t\tif (getCurrentEngine() == PrismEngine.EXACT || getCurrentEngine() == PrismEngine.PARAM) {\n\t\t\tthrow new PrismException(\"Steady-state probabilities cannot be computed with \" + getCurrentEngine().description() + \" engine\");\n\t\t}\n\t\tmainLog.printSeparator();\n\t\tmainLog.println(\"\\nComputing steady-state probabilities...\");\n\t\t// Build model, if necessary\n\t\tbuildModelIfRequired();\n\t\t// Do computation\n\t\tlong l = System.currentTimeMillis();\n\t\tprism.StateVector probs;\n\t\tswitch (getBuiltModelType()) {\n\t\t\tcase SYMBOLIC:\n\t\t\t\tprobs = computeSteadyStateProbabilities(getBuiltModelSymbolic(), initDistFile);\n\t\t\t\tbreak;\n\t\t\tcase EXPLICIT:\n\t\t\t\tprobs = computeSteadyStateProbabilitiesExplicit(getBuiltModelExplicit(), initDistFile);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Steady-state probability computation not supported for \" + getBuiltModelType().description() + \" models\");\n\t\t}\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"\\nTime for steady-state probability computation: \" + l / 1000.0 + \" seconds.\");\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute steady-state probabilities (for a DTMC or CTMC) using symbolic engines.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tprotected StateValues computeSteadyStateProbabilities(Model model, File fileIn) throws PrismException\n\t{\n\t\tProbModelChecker mc;\n\t\tif (model.getModelType() == ModelType.DTMC) {\n\t\t\tmc = new ProbModelChecker(this, model, null);\n\t\t} else if (model.getModelType() == ModelType.CTMC) {\n\t\t\tmc = new StochModelChecker(this, model, null);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Steady-state probabilities only computed for DTMCs/CTMCs\");\n\t\t}\n\t\treturn mc.doSteadyState(fileIn);\n\t}\n\n\t/**\n\t * Compute steady-state probabilities (for a DTMC or CTMC) using the explicit engine.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tprotected explicit.StateValues computeSteadyStateProbabilitiesExplicit(explicit.Model<?> model, File fileIn) throws PrismException\n\t{\n\t\texplicit.StateValues probs;\n\t\tswitch (model.getModelType()) {\n\t\tcase DTMC: {\n\t\t\tDTMCModelChecker mcDTMC = new DTMCModelChecker(this);\n\t\t\tprobs = mcDTMC.doSteadyState((DTMC<Double>) model, fileIn);\n\t\t\tbreak;\n\t\t}\n\t\tcase CTMC: {\n\t\t\tCTMCModelChecker mcCTMC = new CTMCModelChecker(this);\n\t\t\tprobs = mcCTMC.doSteadyState((CTMC<Double>) model, fileIn);\n\t\t\tbreak;\n\t\t}\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Steady-state probabilities only computed for DTMCs/CTMCs\");\n\t\t}\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute/export transient probabilities (forwards) for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only. For a DTMC, {@code time} will be cast to an integer.\n\t * @param time Time instant for transient probabilities\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t */\n\tpublic void exportTransientProbabilities(double time, File file, ModelExportFormat exportFormat) throws PrismException\n\t{\n\t\texportTransientProbabilities(time, file, new ModelExportOptions(exportFormat), null);\n\t}\n\n\t/**\n\t * Compute/export transient probabilities (forwards) for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only. For a DTMC, {@code time} will be cast to an integer.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @param time Time instant for transient probabilities\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportFormat The format to use for export\n\t * @param initDistFile Initial distribution (ignored if null)\n\t */\n\tpublic void exportTransientProbabilities(double time, File file, ModelExportFormat exportFormat, File initDistFile) throws PrismException\n\t{\n\t\texportTransientProbabilities(time, file, new ModelExportOptions(exportFormat), initDistFile);\n\t}\n\n\t/**\n\t * Compute/export transient probabilities (forwards) for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only. The time (or times) for which transient probabilities are to be computed\n\t * are specified as a string, which should give an integer/double for discrete/continuous time models.\n\t * Multiple times can also be given in \"experiment\" notation (\"1:10\", \"0.1:0.1:1.0\").\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @param timeSpec Time instant(s) for transient probabilities\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t * @param initDistFile Initial distribution (ignored if null)\n\t */\n\tpublic void exportTransientProbabilities(String timeSpec, File file, ModelExportOptions exportOptions, File initDistFile) throws PrismException\n\t{\n\t\t// Parse time specification, store as UndefinedConstant for constant T\n\t\t// (NB: use \"null\" for model to avoid a potential name clash with T)\n\t\tString timeType = getModelType().continuousTime() ? \"double\" : \"int\";\n\t\tUndefinedConstants ucTransient = new UndefinedConstants(null, parsePropertiesString(null, \"const \" + timeType + \" T; T;\"));\n\t\ttry {\n\t\t\tucTransient.defineUsingConstSwitch(\"T=\" + timeSpec);\n\t\t} catch (PrismException e) {\n\t\t\tif (timeSpec.contains(\":\")) {\n\t\t\t\tthrow new PrismException(\"\\\"\" + timeSpec + \"\\\" is not a valid time range for a \" + getModelType());\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"\\\"\" + timeSpec + \"\\\" is not a valid time for a \" + getModelType());\n\t\t\t}\n\t\t}\n\t\texportTransientProbabilities(ucTransient, file, exportOptions, initDistFile);\n\t}\n\n\t/**\n\t * Compute/export transient probabilities (forwards) for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only. For a DTMC, {@code time} will be cast to an integer.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @param time Time instant for transient probabilities\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t * @param initDistFile Initial distribution (ignored if null)\n\t */\n\tpublic void exportTransientProbabilities(double time, File file, ModelExportOptions exportOptions, File initDistFile) throws PrismException\n\t{\n\t\tprism.StateVector probs = computeTransientProbabilities(time, initDistFile);\n\t\tmainLog.print(\"\\nExporting transient probabilities \");\n\t\tmainLog.println(exportOptions.getFormat().description() + \" \" + getDestinationStringForFile(file));\n\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\tprobs.print(out, file == null, exportOptions.getFormat() == ModelExportFormat.MATLAB, file == null, file == null);\n\t\t}\n\t\tprobs.clear();\n\t}\n\n\t/**\n\t * Compute transient probabilities (forwards) for the current model, building it first if needed.\n\t * For a discrete-time model, {@code time} will be cast to an integer.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @param time Time instant for transient probabilities\n\t * @param initDistFile Initial distribution (ignored if null)\n\t */\n\tpublic prism.StateVector computeTransientProbabilities(double time, File initDistFile) throws PrismException\n\t{\n\t\tif (!(getModelType() == ModelType.CTMC || getModelType() == ModelType.DTMC)) {\n\t\t\tthrow new PrismException(\"Transient probabilities only computed for DTMCs/CTMCs\");\n\t\t}\n\t\tif (getCurrentEngine() == PrismEngine.EXACT || getCurrentEngine() == PrismEngine.PARAM) {\n\t\t\tthrow new PrismException(\"Transient probabilities cannot be computed with \" + getCurrentEngine().description() + \" engine\");\n\t\t}\n\t\tif (time < 0) {\n\t\t\tthrow new PrismException(\"Cannot compute transient probabilities for negative time value\");\n\t\t}\n\t\tmainLog.printSeparator();\n\t\tString strTime = getModelType().continuousTime() ? Double.toString(time) : Integer.toString((int) time);\n\t\tmainLog.println(\"\\nComputing transient probabilities (time = \" + strTime + \")...\");\n\t\t// Do computation\n\t\tlong l = System.currentTimeMillis();\n\t\tprism.StateVector probs;\n\t\t// FAU\n\t\tif (getModelType() == ModelType.CTMC && settings.getString(PrismSettings.PRISM_TRANSIENT_METHOD).equals(\"Fast adaptive uniformisation\")) {\n\t\t\tif (initDistFile != null) {\n\t\t\t\tthrow new PrismException(\"Fast adaptive uniformisation cannot read an initial distribution from a file\");\n\t\t\t}\n\t\t\tModulesFileModelGenerator<Double> prismModelGen = ModulesFileModelGenerator.createForDoubles(getPRISMModel(), this);\n\t\t\tFastAdaptiveUniformisation fau = new FastAdaptiveUniformisation(this, prismModelGen);\n\t\t\tfau.setConstantValues(getPRISMModel().getConstantValues());\n\t\t\tprobs = fau.doTransient(time);\n\t\t}\n\t\t// Non-FAU\n\t\telse {\n\t\t\t// Build model, if necessary\n\t\t\tbuildModelIfRequired();\n\t\t\t// Then solve\n\t\t\tswitch (getBuiltModelType()) {\n\t\t\t\tcase SYMBOLIC:\n\t\t\t\t\tif (getModelType() == ModelType.DTMC) {\n\t\t\t\t\t\tModelChecker mcDTMC = new ProbModelChecker(this, getBuiltModelSymbolic(), null);\n\t\t\t\t\t\tprobs = ((ProbModelChecker) mcDTMC).doTransient((int) time, initDistFile);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tModelChecker mcCTMC = new StochModelChecker(this, getBuiltModelSymbolic(), null);\n\t\t\t\t\t\tprobs = ((StochModelChecker) mcCTMC).doTransient(time, initDistFile);\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\tcase EXPLICIT:\n\t\t\t\t\tif (getModelType() == ModelType.DTMC) {\n\t\t\t\t\t\tDTMCModelChecker mcDTMC = new DTMCModelChecker(this);\n\t\t\t\t\t\tprobs = mcDTMC.doTransient((DTMC<Double>) getBuiltModelExplicit(), (int) time, initDistFile);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tCTMCModelChecker mcCTMC = new CTMCModelChecker(this);\n\t\t\t\t\t\tprobs = mcCTMC.doTransient((CTMC<Double>) getBuiltModelExplicit(), time, initDistFile);\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Transient probability computation not supported for \" + getBuiltModelType().description() + \" models\");\n\t\t\t}\n\t\t}\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"\\nTime for transient probability computation: \" + l / 1000.0 + \" seconds.\");\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute/export transient probabilities (forwards) for the current model, building it first if needed.\n\t * Applicable for DTMCs/CTMCs only. For a DTMC, {@code time} will be cast to an integer.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @param times Time instants for transient probabilities\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t * @param initDistFile Initial distribution (ignored if null)\n\t */\n\tpublic void exportTransientProbabilities(UndefinedConstants times, File file, ModelExportOptions exportOptions, File initDistFile) throws PrismException\n\t{\n\t\tif (!(getModelType() == ModelType.CTMC || getModelType() == ModelType.DTMC)) {\n\t\t\tthrow new PrismException(\"Transient probabilities only computed for DTMCs/CTMCs\");\n\t\t}\n\t\tif (getCurrentEngine() == PrismEngine.EXACT || getCurrentEngine() == PrismEngine.PARAM) {\n\t\t\tthrow new PrismException(\"Transient probabilities cannot be computed with \" + getCurrentEngine().description() + \" engine\");\n\t\t}\n\t\t// Step through required time points\n\t\tprism.StateVector probs = null;\n\t\tsymbolic.states.StateValues probsSym = null, initDistSym = null;\n\t\texplicit.StateValues probsExpl = null, initDistExpl = null;\n\t\tint timeInt = 0, initTimeInt = 0;\n\t\tdouble timeDouble = 0, initTimeDouble = 0;\n\t\tfor (int i = 0; i < times.getNumPropertyIterations(); i++) {\n\n\t\t\t// Get time, check non-negative\n\t\t\tObject time = times.getPFConstantValues().getValue(0);\n\t\t\tif (getModelType().continuousTime()) {\n\t\t\t\ttimeDouble = ((Double) time).doubleValue();\n\t\t\t} else {\n\t\t\t\ttimeInt = ((Integer) time).intValue();\n\t\t\t}\n\t\t\tif (getModelType().continuousTime() ? (((Double) time).doubleValue() < 0) : (((Integer) time).intValue() < 0)) {\n\t\t\t\tthrow new PrismException(\"Cannot compute transient probabilities for negative time value\");\n\t\t\t}\n\t\t\tmainLog.printSeparator();\n\t\t\tmainLog.println(\"\\nComputing transient probabilities (time = \" + time + \")...\");\n\t\t\t// Do computation\n\t\t\tlong l = System.currentTimeMillis();\n\t\t\t// FAU\n\t\t\tif (getModelType() == ModelType.CTMC && settings.getString(PrismSettings.PRISM_TRANSIENT_METHOD).equals(\"Fast adaptive uniformisation\")) {\n\t\t\t\tif (initDistFile != null) {\n\t\t\t\t\tthrow new PrismException(\"Fast adaptive uniformisation cannot read an initial distribution from a file\");\n\t\t\t\t}\n\t\t\t\tModulesFileModelGenerator<Double> prismModelGen = ModulesFileModelGenerator.createForDoubles(getPRISMModel(), this);\n\t\t\t\tFastAdaptiveUniformisation fau = new FastAdaptiveUniformisation(this, prismModelGen);\n\t\t\t\tfau.setConstantValues(getPRISMModel().getConstantValues());\n\t\t\t\tif (i == 0) {\n\t\t\t\t\tprobs = probsExpl = fau.doTransient(timeDouble);\n\t\t\t\t\tinitTimeDouble = 0.0;\n\t\t\t\t} else {\n\t\t\t\t\tprobs = probsExpl = fau.doTransient(timeDouble - initTimeDouble, probsExpl);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Non-FAU\n\t\t\telse {\n\t\t\t\t// Build model, if necessary\n\t\t\t\tbuildModelIfRequired();\n\t\t\t\t// Then solve\n\t\t\t\tswitch (getBuiltModelType()) {\n\t\t\t\t\tcase SYMBOLIC:\n\t\t\t\t\t\tif (getModelType().continuousTime()) {\n\t\t\t\t\t\t\tStochModelChecker mc = new StochModelChecker(this, getBuiltModelSymbolic(), null);\n\t\t\t\t\t\t\tif (i == 0) {\n\t\t\t\t\t\t\t\tinitDistSym = mc.readDistributionFromFile(initDistFile);\n\t\t\t\t\t\t\t\tinitTimeDouble = 0;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tprobs = probsSym = ((StochModelChecker) mc).doTransient(timeDouble - initTimeDouble, initDistSym);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tProbModelChecker mc = new ProbModelChecker(this, getBuiltModelSymbolic(), null);\n\t\t\t\t\t\t\tif (i == 0) {\n\t\t\t\t\t\t\t\tinitDistSym = mc.readDistributionFromFile(initDistFile);\n\t\t\t\t\t\t\t\tinitTimeInt = 0;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tprobs = probsSym = ((ProbModelChecker) mc).doTransient(timeInt - initTimeInt, initDistSym);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (initDistSym != null) {\n\t\t\t\t\t\t\tinitDistSym.clear();\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase EXPLICIT:\n\t\t\t\t\t\tif (getModelType().continuousTime()) {\n\t\t\t\t\t\t\tCTMCModelChecker mc = new CTMCModelChecker(this);\n\t\t\t\t\t\t\tif (i == 0) {\n\t\t\t\t\t\t\t\tinitDistExpl = mc.readDistributionFromFile(initDistFile, getBuiltModelExplicit());\n\t\t\t\t\t\t\t\tinitTimeDouble = 0;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tprobs = probsExpl = mc.doTransient((CTMC<Double>) getBuiltModelExplicit(), timeDouble - initTimeDouble, initDistExpl);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tDTMCModelChecker mc = new DTMCModelChecker(this);\n\t\t\t\t\t\t\tif (i == 0) {\n\t\t\t\t\t\t\t\tinitDistExpl = mc.readDistributionFromFile(initDistFile, getBuiltModelExplicit());\n\t\t\t\t\t\t\t\tinitTimeInt = 0;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tprobs = probsExpl = mc.doTransient((DTMC<Double>) getBuiltModelExplicit(), timeInt - initTimeInt, initDistExpl);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (initDistExpl != null) {\n\t\t\t\t\t\t\tinitDistExpl.clear();\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tthrow new PrismException(\"Transient probability computation not supported for \" + getBuiltModelType().description() + \" models\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tl = System.currentTimeMillis() - l;\n\t\t\tmainLog.println(\"\\nTime for transient probability computation: \" + l / 1000.0 + \" seconds.\");\n\n\t\t\t// If output is to a file and there are multiple points, change filename\n\t\t\tFile fileOutActual;\n\t\t\tif (file != null && times.getNumPropertyIterations() > 1) {\n\t\t\t\tfileOutActual = new File(PrismUtils.addSuffixToFilename(file.getPath(), time.toString()));\n\t\t\t} else {\n\t\t\t\tfileOutActual = file;\n\t\t\t}\n\t\t\t// Print/export probabilities\n\t\t\tmainLog.print(\"\\nExporting transient probabilities \");\n\t\t\tmainLog.println(exportOptions.getFormat().description() + \" \" + getDestinationStringForFile(fileOutActual));\n\t\t\ttry (PrismLog out = getPrismLogForFile(fileOutActual)) {\n\t\t\t\tif (!settings.getString(PrismSettings.PRISM_TRANSIENT_METHOD).equals(\"Fast adaptive uniformisation\")) {\n\t\t\t\t\tprobs.print(out, file == null, exportOptions.getFormat() == ModelExportFormat.MATLAB, file == null, true);\n\t\t\t\t} else {\n\t\t\t\t\t// If full state space not computed, don't print vectors and always show states\n\t\t\t\t\tprobs.print(out, file == null, exportOptions.getFormat() == ModelExportFormat.MATLAB, true, false);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Prepare for next iteration\n\t\t\tinitDistSym = probsSym;\n\t\t\tinitDistExpl = probsExpl;\n\t\t\tinitTimeInt = timeInt;\n\t\t\tinitTimeDouble = timeDouble;\n\t\t\ttimes.iterateProperty();\n\t\t}\n\t\tprobs.clear();\n\t}\n\n\tpublic void explicitBuildTest() throws PrismException\n\t{\n\t\t/* old code...\n\t\tString tmpFile = \"\";\n\t\ttry {\n\t\t\texplicit.ConstructModel constructModel = new explicit.ConstructModel(getSimulator(), mainLog);\n\t\t\tmainLog.println(\"\\nConstructing model explicitly...\");\n\t\t\texplicit.Model modelExplicit = constructModel.constructModel(currentModulesFile);\n\t\t\ttmpFile = File.createTempFile(\"explicitbuildtest\", \".tra\").getAbsolutePath();\n\t\t\ttmpFile = \"explicitbuildtest.tra\";\n\t\t\tmainLog.println(\"\\nExporting (explicit) model to \\\"\" + tmpFile + \"1\\\"...\");\n\t\t\tmodelExplicit.exportToPrismExplicitTra(tmpFile + \"1\");\n\t\t\tmainLog.println(\"\\nExporting (normal) model to \\\"\" + tmpFile + \"2\\\"...\");\n\t\t\texportTransToFile(true, Prism.EXPORT_PLAIN, new File(tmpFile + \"2\"));\n\t\t\texplicit.ModelSimple modelExplicit2 = null;\n\t\t\tswitch (getModelType()) {\n\t\t\tcase DTMC:\n\t\t\t\tmodelExplicit2 = new explicit.DTMCSimple();\n\t\t\t\tbreak;\n\t\t\tcase CTMC:\n\t\t\t\tmodelExplicit2 = new explicit.CTMCSimple();\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\t\tmodelExplicit2 = new explicit.MDPSimple();\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tmodelExplicit2.buildFromPrismExplicit(tmpFile + \"2\");\n\t\t\tif (!modelExplicit.equals(modelExplicit2)) {\n\t\t\t\tthrow new PrismException(\"Explicit models differ\");\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"Could not create temporary file \\\"\" + tmpFile + \"\\\"\");\n\t\t}*/\n\t}\n\n\t/**\n\t * Clear up and close down.\n\t */\n\tpublic void closeDown()\n\t{\n\t\tcloseDown(true);\n\t}\n\n\t/**\n\t * Clear up and close down.\n\t * @param check Whether to perform checks on CUDD status when shutting it down. \n\t */\n\tpublic void closeDown(boolean check)\n\t{\n\t\t// Clear any built model(s)\n\t\tclearBuiltModel();\n\t\t// Close down libraries/engines\n\t\tParamModelChecker.closeDown();\n\t\tint numLibs = libraries.size();\n\t\tfor (int i = numLibs - 1; i >= 0; i--) {\n\t\t\tlibraries.get(i).closeDown(check);\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// Private methods for dealing with model state\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Set the source type for the currently loaded model.\n\t */\n\tprivate void setModelSource(ModelSource modelSource) throws PrismException\n\t{\n\t\tcurrentModelDetails.modelSource = modelSource;\n\t}\n\n\t/**\n\t * Specify whether the source of the currently loaded model is digital clocks.\n\t */\n\tprivate void setModelSourceIsDigitalClocks(boolean digital) throws PrismException\n\t{\n\t\tthis.currentModelDetails.modelDigitalClocks = digital;\n\t}\n\n\t/**\n\t * Set the type for the currently loaded model.\n\t */\n\tprivate void setModelType(ModelType modelType) throws PrismException\n\t{\n\t\tcurrentModelDetails.modelType = modelType;\n\t}\n\n\t/**\n\t * Set the model info for the currently loaded model.\n\t */\n\tprivate void setModelInfo(ModelInfo modelInfo) throws PrismException\n\t{\n\t\tcurrentModelDetails.modelInfo = modelInfo;\n\t}\n\n\t/**\n\t * Set the PRISM model source (if appropriate) for the currently loaded model.\n\t */\n\tprivate void setPRISMModel(ModulesFile modulesFile) throws PrismException\n\t{\n\t\tcurrentModelDetails.modulesFile = modulesFile;\n\t}\n\n\t/**\n\t * Set the model generator for the currently loaded model.\n\t */\n\tprivate void setModelGenerator(ModelGenerator modelGenerator) throws PrismException\n\t{\n\t\tcurrentModelDetails.modelGenerator = modelGenerator;\n\t}\n\n\t/**\n\t * Set the reward info for the currently loaded model.\n\t */\n\tprivate void setRewardInfo(RewardInfo rewardInfo) throws PrismException\n\t{\n\t\tcurrentModelDetails.rewardInfo = rewardInfo;\n\t}\n\n\t/**\n\t * Set the reward generator for the currently loaded model.\n\t */\n\tprivate void setRewardGenerator(RewardGenerator rewardGenerator) throws PrismException\n\t{\n\t\tcurrentModelDetails.rewardGenerator = rewardGenerator;\n\t}\n\n\t/**\n\t * Set the defined constants for the currently loaded model.\n\t */\n\tprivate void setDefinedMFConstants(Values definedMFConstants) throws PrismException\n\t{\n\t\tsetDefinedMFConstants(definedMFConstants, false);\n\t}\n\n\t/**\n\t * Set the defined constants for the currently loaded model.\n\t */\n\tprivate void setDefinedMFConstants(Values definedMFConstants, boolean exact) throws PrismException\n\t{\n\t\tcurrentModelDetails.definedMFConstants = definedMFConstants;\n\t\tcurrentModelDetails.definedMFConstantsAreExact = exact;\n\t}\n\n\t/**\n\t * Store the built model.\n\t */\n\tprivate void setBuiltModel(ModelBuildType buildType, prism.Model<?> newModel) throws PrismException\n\t{\n\t\tswitch (buildType) {\n\t\t\tcase SYMBOLIC:\n\t\t\t\tif (!(newModel instanceof symbolic.model.Model)) {\n\t\t\t\t\tthrow new PrismException(\"Attempt to store model of incorrect type\");\n\t\t\t\t}\n\t\t\t\tcurrentModelDetails.model = newModel;\n\t\t\t\tcurrentModelDetails.modelSymb = (symbolic.model.Model) newModel;\n\t\t\t\tcurrentModelDetails.modelExpl = null;\n\t\t\t\tbreak;\n\t\t\tcase EXPLICIT:\n\t\t\tcase EXACT:\n\t\t\tcase PARAM:\n\t\t\t\tif (!(newModel instanceof explicit.Model)) {\n\t\t\t\t\tthrow new PrismException(\"Attempt to store model of incorrect type\");\n\t\t\t\t}\n\t\t\t\tcurrentModelDetails.model = newModel;\n\t\t\t\tcurrentModelDetails.modelSymb = null;\n\t\t\t\tcurrentModelDetails.modelExpl = (explicit.Model) newModel;;\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown built model type\");\n\t\t}\n\t\tthis.currentModelDetails.modelBuildType = buildType;\n\t}\n\n\t/**\n\t * Clear the built model if needed (free/deallocate memory etc).\n\t * This resets {@code currentModelSymb} and {@code currentModelExpl} to {@code null}.\n\t * Also clear objects that connect to a build model, notably strategies.\n\t */\n\tprivate void clearBuiltModel()\n\t{\n\t\tcurrentModelDetails.model = null;\n\t\tif (currentModelDetails.modelSymb != null) {\n\t\t\tcurrentModelDetails.modelSymb.clear();\n\t\t\tcurrentModelDetails.modelSymb = null;\n\t\t}\n\t\tcurrentModelDetails.modelExpl = null;\n\t\tcurrentModelDetails.modelBuildType = null;\n\t\tclearStrategy();\n\t}\n\n\t/**\n\t * Clear the currently stored strategy if present (free/deallocate memory etc).\n\t * This resets {@code strategy} to {@code null}.\n\t */\n\tprivate void clearStrategy()\n\t{\n\t\tif (strategy != null) {\n\t\t\tstrategy.clear();\n\t\t\tstrategy = null;\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// Private utility methods\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * Utility method to create and initialise a (symbolic) model checker based on the current model.\n\t * @param propertiesFile Optional properties file for extra info needed during model checking (can be null)\n\t */\n\tprivate StateModelChecker createModelChecker(PropertiesFile propertiesFile) throws PrismException\n\t{\n\t\t// Create a dummy properties file if none exist\n\t\t// (the symbolic model checkers rely on this to store e.g. model labels)\n\t\tif (propertiesFile == null) {\n\t\t\tpropertiesFile = parsePropertiesString(\"\");\n\t\t}\n\t\t// Create model checker\n\t\tStateModelChecker mc = StateModelChecker.createModelChecker(getModelType(), this, getBuiltModelSymbolic(), propertiesFile);\n\t\t// Pass any additional local settings\n\t\t// TODO\n\n\t\treturn mc;\n\t}\n\n\t/**\n\t * Utility method to create and initialise an (explicit) model checker based on the current model.\n\t * @param propertiesFile Optional properties file for extra info needed during model checking (can be null)\n\t */\n\tprivate explicit.StateModelChecker createModelCheckerExplicit(PropertiesFile propertiesFile) throws PrismException\n\t{\n\t\t// Create model checker\n\t\texplicit.StateModelChecker mc = explicit.StateModelChecker.createModelChecker(getModelType(), this);\n\t\tmc.setModelCheckingInfo(getModelInfo(), propertiesFile, getRewardGenerator());\n\t\t// Pass any additional local settings\n\t\tmc.setExportTarget(exportTarget);\n\t\tmc.setExportTargetFilename(exportTargetFilename);\n\t\tmc.setExportProductTrans(exportProductTrans);\n\t\tmc.setExportProductTransFilename(exportProductTransFilename);\n\t\tmc.setExportProductStates(exportProductStates);\n\t\tmc.setExportProductStatesFilename(exportProductStatesFilename);\n\t\tmc.setExportProductVector(exportProductVector);\n\t\tmc.setExportProductVectorFilename(exportProductVectorFilename);\n\t\tmc.setStoreVector(storeVector);\n\t\tmc.setGenStrat(genStrat);\n\t\tmc.setRestrictStratToReach(restrictStratToReach);\n\t\tmc.setDoBisim(doBisim);\n\n\t\treturn mc;\n\t}\n\n\t/**\n\t * Get a string describing an output format, e.g. \"in plain text format\" for EXPORT_PLAIN.\n\t */\n\tprivate static String getStringForExportType(int exportType)\n\t{\n\t\tswitch (exportType) {\n\t\tcase EXPORT_PLAIN:\n\t\t\treturn \"in plain text format\";\n\t\tcase EXPORT_MATLAB:\n\t\t\treturn \"in Matlab format\";\n\t\tcase EXPORT_DOT:\n\t\t\treturn \"in Dot format\";\n\t\tcase EXPORT_ROWS:\n\t\t\treturn \"in rows format\";\n\t\tcase EXPORT_DOT_STATES:\n\t\t\treturn \"in Dot format (with states)\";\n\t\tdefault:\n\t\t\treturn \"in ? format\";\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// Old API methods, supported via new one\n\t//------------------------------------------------------------------------------\n\n\t/**\n\t * @deprecated\n\t * Export the currently loaded model's transition matrix to a file (or to the log)\n\t * @param ordered Ignored (assumed to be true)\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN}\n\t * <li> {@link #EXPORT_MATLAB}\n\t * <li> {@link #EXPORT_DOT}\n\t * <li> {@link #EXPORT_ROWS}\n\t * <li> {@link #EXPORT_DOT_STATES}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\t@Deprecated\n\tpublic void exportTransToFile(boolean ordered, int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelTransitions(file, convertExportType(exportType));\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export the currently loaded model's state rewards to a file (or files, or stdout).\n\t * If there is more than 1 reward structure, then multiple files are generated\n\t * (e.g. \"rew.sta\" becomes \"rew1.sta\", \"rew2.sta\", ...)\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN}\n\t * <li> {@link #EXPORT_MATLAB}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\t@Deprecated\n\tpublic void exportStateRewardsToFile(int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelStateRewards(file, convertExportType(exportType));\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export the currently loaded model's transition rewards to a file\n\t * @param ordered Ignored (assumed to be true)\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN}\n\t * <li> {@link #EXPORT_MATLAB}\n\t * <li> {@link #EXPORT_ROWS}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\t@Deprecated\n\tpublic void exportTransRewardsToFile(boolean ordered, int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelTransRewards(file, convertExportType(exportType));\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export the currently loaded model's states to a file\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN}\n\t * <li> {@link #EXPORT_MATLAB}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\t@Deprecated\n\tpublic void exportStatesToFile(int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelStates(file, convertExportType(exportType));\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export the observations for the currently loaded model to a file\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN}\n\t * <li> {@link #EXPORT_MATLAB}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\t@Deprecated\n\tpublic void exportObservationsToFile(int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelObservations(file, convertExportType(exportType));\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export the states satisfying labels from the currently loaded model and (optionally) a properties file to a file.\n\t * The PropertiesFile should correspond to the currently loaded model.\n\t * @param propertiesFile The properties file, for further labels (ignored if null)\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN}\n\t * <li> {@link #EXPORT_MATLAB}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\t@Deprecated\n\tpublic void exportLabelsToFile(PropertiesFile propertiesFile, int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelLabels(propertiesFile, file, convertExportType(exportType));\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export the states satisfying labels from the properties file to a file.\n\t * The PropertiesFile should correspond to the currently loaded model.\n\t * @param propertiesFile The properties file (for further labels)\n\t * @param exportType Type of export; one of: <ul>\n\t * <li> {@link #EXPORT_PLAIN}\n\t * <li> {@link #EXPORT_MATLAB}\n\t * </ul>\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\t@Deprecated\n\tpublic void exportPropLabelsToFile(PropertiesFile propertiesFile, int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelPropLabels(propertiesFile, file, convertExportType(exportType));\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export the MTBDD for the currently loaded model's transition matrix to a Dot file.\n\t * @param file File to export to\n\t */\n\t@Deprecated\n\tpublic void exportToDotFile(File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportBuiltModelTransitions(file, new ModelExportOptions(ModelExportFormat.DD_DOT));\n\t}\n\n\t/**\n\t * @deprecated\n\t * Export various aspects of the current built model together.\n\t * @param file File to export to\n\t * @param exportOptions The options for export\n\t */\n\t@Deprecated\n\tpublic void exportBuiltModelCombined(File file, ModelExportOptions exportOptions) throws PrismException, FileNotFoundException\n\t{\n\t\texportBuiltModel(file, exportOptions);\n\t}\n\n\t/**\n\t * Compute steady-state probabilities for the current model (DTMCs/CTMCs only).\n\t * Output probability distribution to log.\n\t * @deprecated Use {@link #exportSteadyStateProbabilities(File, ModelExportFormat)}\n\t */\n\t@Deprecated\n\tpublic void doSteadyState() throws PrismException\n\t{\n\t\texportSteadyStateProbabilities(null, ModelExportFormat.EXPLICIT, null);\n\t}\n\n\t/**\n\t * Compute steady-state probabilities for the current model (DTMCs/CTMCs only).\n\t * Output probability distribution to a file (or, if {@code fileOut} is null, to log).\n\t * The exportType should be EXPORT_PLAIN or EXPORT_MATLAB.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @deprecated Use {@link #exportSteadyStateProbabilities(File, ModelExportFormat, File)}\n\t */\n\t@Deprecated\n\tpublic void doSteadyState(int exportType, File fileOut, File fileIn) throws PrismException\n\t{\n\t\texportSteadyStateProbabilities(fileOut, convertExportType(exportType), fileIn);\n\t}\n\n\t/**\n\t * Compute transient probabilities (forwards) for the current model (DTMCs/CTMCs only).\n\t * Output probability distribution to log.\n\t * For a discrete-time model, {@code time} will be cast to an integer.\n\t * @deprecated Use {@link #exportTransientProbabilities(double, File, ModelExportFormat)}\n\t */\n\t@Deprecated\n\tpublic void doTransient(double time) throws PrismException\n\t{\n\t\texportTransientProbabilities(time, null, ModelExportFormat.EXPLICIT, null);\n\t}\n\n\t/**\n\t * Compute transient probabilities (forwards) for the current model (DTMCs/CTMCs only).\n\t * Output probability distribution to a file (or, if {@code fileOut} is null, to log).\n\t * For a discrete-time model, {@code time} will be cast to an integer.\n\t * The exportType should be EXPORT_PLAIN or EXPORT_MATLAB.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @deprecated Use {@link #exportTransientProbabilities(double, File, ModelExportFormat, File)}\n\t */\n\t@Deprecated\n\tpublic void doTransient(double time, int exportType, File fileOut, File fileIn) throws PrismException\n\t{\n\t\texportTransientProbabilities(time, fileOut, convertExportType(exportType), fileIn);\n\t}\n\n\t/**\n\t * Compute transient probabilities (forwards) for the current model (DTMCs/CTMCs only)\n\t * for a range of time points. Each distribution is computed incrementally.\n\t * Output probability distribution to a file (or, if file is null, to log).\n\t * Time points are specified using an UndefinedConstants with a single ranging variable\n\t * (of the appropriate type (int/double) and with arbitrary name).\n\t * The exportType should be EXPORT_PLAIN or EXPORT_MATLAB.\n\t * Optionally (if non-null), read in the initial probability distribution from a file.\n\t * @deprecated Use {@link #exportTransientProbabilities(UndefinedConstants, File, ModelExportOptions, File)}.\n\t */\n\t@Deprecated\n\tpublic void doTransient(UndefinedConstants times, int exportType, File fileOut, File fileIn) throws PrismException\n\t{\n\t\texportTransientProbabilities(times, fileOut, convertExportType(exportType), fileIn);\n\t}\n\n\t/**\n\t * Convert a {@code ModelExportOptions} object to an {@code exportType} value.\n\t */\n\tpublic static int convertExportType(ModelExportOptions exportOptions)\n\t{\n\t\tswitch (exportOptions.getFormat()) {\n\t\t\tcase EXPLICIT:\n\t\t\t\treturn Prism.EXPORT_PLAIN;\n\t\t\tcase MATLAB:\n\t\t\t\treturn Prism.EXPORT_MATLAB;\n\t\t\tcase DOT:\n\t\t\t\treturn Prism.EXPORT_DOT;\n\t\t}\n\t\treturn Prism.EXPORT_PLAIN;\n\t}\n\n\t/**\n\t * Convert a {@code ModelExportOptions} object to an {@code exportType} value for a transition matrix.\n\t */\n\tpublic static int convertExportTypeTrans(ModelExportOptions exportOptions)\n\t{\n\t\tswitch (exportOptions.getFormat()) {\n\t\t\tcase EXPLICIT:\n\t\t\t\treturn exportOptions.getExplicitRows() ? Prism.EXPORT_ROWS : Prism.EXPORT_PLAIN;\n\t\t\tcase MATLAB:\n\t\t\t\treturn Prism.EXPORT_MATLAB;\n\t\t\tcase DOT:\n\t\t\t\treturn exportOptions.getShowStates() ? Prism.EXPORT_DOT_STATES : Prism.EXPORT_DOT;\n\t\t}\n\t\treturn Prism.EXPORT_PLAIN;\n\t}\n\n\t/**\n\t * Convert an {@code exportType} value to a {@code ModelExportOptions} object.\n\t */\n\tpublic static ModelExportOptions convertExportType(int exportType)\n\t{\n\t\tModelExportOptions exportOptions = new ModelExportOptions();\n\t\tswitch (exportType) {\n\t\t\tcase Prism.EXPORT_PLAIN:\n\t\t\t\texportOptions.setFormat(ModelExportFormat.EXPLICIT);\n\t\t\t\tbreak;\n\t\t\tcase Prism.EXPORT_MATLAB:\n\t\t\t\texportOptions.setFormat(ModelExportFormat.MATLAB);\n\t\t\t\tbreak;\n\t\t\tcase Prism.EXPORT_DOT:\n\t\t\t\texportOptions.setFormat(ModelExportFormat.DOT);\n\t\t\t\texportOptions.setShowStates(false);\n\t\t\t\texportOptions.setShowObservations(false);\n\t\t\t\tbreak;\n\t\t\tcase Prism.EXPORT_DOT_STATES:\n\t\t\t\texportOptions.setFormat(ModelExportFormat.DOT);\n\t\t\t\texportOptions.setShowStates(true);\n\t\t\t\texportOptions.setShowObservations(true);\n\t\t\t\tbreak;\n\t\t\tcase Prism.EXPORT_ROWS:\n\t\t\t\texportOptions.setFormat(ModelExportFormat.EXPLICIT);\n\t\t\t\texportOptions.setExplicitRows(true);\n\t\t\t\tbreak;\n\t\t}\n\t\treturn exportOptions;\n\t}\n\n\t/**\n\t * Perform model checking on the currently loaded model using exact methods\n\t * (currently, this is done via the parametric model checking functionality)\n\t * @param propertiesFile parent properties file\n\t * @param prop property to model check\n\t * @deprecated Better to use {@link #modelCheck(PropertiesFile, Property)} now.\n\t */\n\t@Deprecated\n\tpublic Result modelCheckExact(PropertiesFile propertiesFile, Property prop) throws PrismException\n\t{\n\t\tboolean exactOld = settings.getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\t\tsettings.set(PrismSettings.PRISM_EXACT_ENABLED, Boolean.TRUE);\n\t\tResult result = modelCheck(propertiesFile, prop);\n\t\tsettings.set(PrismSettings.PRISM_EXACT_ENABLED, exactOld);\n\t\treturn result;\n\t}\n\n\t/**\n\t * Perform parametric model checking on the currently loaded model.\n\t * @param propertiesFile parent properties file\n\t * @param prop property to model check\n\t * @param paramNames parameter names\n\t * @param paramLowerBounds lower bounds of parameters\n\t * @param paramUpperBounds upper bounds of parameters\n\t * @deprecated Better to use {@link #modelCheck(PropertiesFile, Property)} now.\n\t */\n\t@Deprecated\n\tpublic Result modelCheckParametric(PropertiesFile propertiesFile, Property prop, String[] paramNames, String[] paramLowerBounds, String[] paramUpperBounds)\n\t\t\tthrows PrismException\n\t{\n\t\tboolean paramOld = param;\n\t\tString[] paramNamesOld = this.paramNames;\n\t\tString[] paramLowerBoundsOld = this.paramLowerBounds;\n\t\tString[] paramUpperBoundsOld = this.paramUpperBounds;\n\t\tsetParametric(paramNames, paramLowerBounds, paramUpperBounds);\n\t\tResult result = modelCheck(propertiesFile, prop);\n\t\tif (paramOld) {\n\t\t\tsetParametric(paramNamesOld, paramLowerBoundsOld, paramUpperBoundsOld);\n\t\t} else {\n\t\t\tsetParametricOff();\n\t\t}\n\t\treturn result;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/PrismCL.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.BufferedReader;\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.io.FileReader;\nimport java.io.IOException;\nimport java.io.PrintWriter;\nimport java.net.UnknownHostException;\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.Collections;\nimport java.util.List;\nimport java.util.Map.Entry;\n\nimport common.StackTraceHelper;\nimport csv.CsvFormatException;\nimport io.ModelExportOptions;\nimport io.ModelExportFormat;\nimport io.ModelExportTask;\nimport io.PrismExplicitImporter;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport strat.StrategyExportOptions;\nimport prism.ResultsExporter.ResultsExportShape;\nimport prism.ResultsImporter.RawResultsCollection;\nimport simulator.GenerateSimulationPath;\nimport simulator.method.ACIconfidence;\nimport simulator.method.ACIiterations;\nimport simulator.method.ACIwidth;\nimport simulator.method.APMCapproximation;\nimport simulator.method.APMCconfidence;\nimport simulator.method.APMCiterations;\nimport simulator.method.CIconfidence;\nimport simulator.method.CIiterations;\nimport simulator.method.CIwidth;\nimport simulator.method.SPRTMethod;\nimport simulator.method.SimulationMethod;\n\nimport static prism.PrismSettings.RANGE_EXPORT_DOUBLE_PRECISION;\n\n// prism - command line version\n\npublic class PrismCL implements PrismModelListener\n{\n\t// flags\n\tprivate boolean importpepa = false;\n\tprivate boolean importprismpp = false;\n\tprivate boolean importinitdist = false;\n\tprivate boolean importresults = false;\n\tprivate boolean steadystate = false;\n\tprivate boolean dotransient = false;\n\tprivate boolean exportprism = false;\n\tprivate boolean exportprismconst = false;\n\tprivate boolean exportmodeldotview = false;\n\tprivate boolean exportsccs = false;\n\tprivate boolean exportbsccs = false;\n\tprivate boolean exportmecs = false;\n\tprivate boolean exportresults = false;\n\tprivate ResultsExportShape exportShape = ResultsExportShape.LIST_PLAIN;\n\tprivate boolean exportvector = false;\n\tprivate int exportType = Prism.EXPORT_PLAIN;\n\tprivate boolean exportstrat = false;\n\tprivate boolean simulate = false;\n\tprivate boolean simpath = false;\n\tprivate boolean param = false;\n\tprivate ModelType typeOverride = null;\n\tprivate boolean orderingOverride = false;\n\tprivate boolean explicitbuild = false;\n\tprivate boolean explicitbuildtest = false;\n\tprivate boolean nobuild = false;\n\tprivate boolean test = false;\n\tprivate boolean testExitsOnFail = true;\n\n\t// export info\n\tprivate List<ModelExportTask> modelExportTasks = new ArrayList<>();\n\tprivate ModelExportOptions modelExportOptionsGlobal = new ModelExportOptions();\n\n\t// import info\n\tprivate List<ModelImportSource> modelImportSources = new ArrayList<>();\n\n\t// property info\n\tprivate List<Object> propertyIndices = null;\n\tprivate String propertyString = \"\";\n\n\t// argument to -const switch\n\tprivate String constSwitch = null;\n\n\t// argument to -simpath switch\n\tprivate String simpathDetails = null;\n\n\t// argument to -importprismpp switch\n\tprivate String prismppParams = null;\n\n\t// argument to -param switch\n\tprivate String paramSwitch = null;\n\n\t// files/filenames\n\tprivate String mainLogFilename = \"stdout\";\n\tprivate String settingsFilename = null;\n\tprivate String modelFilename = null;\n\tprivate String importInitDistFilename = null;\n\tprivate String importResultsFilename = null;\n\tprivate String importModelWarning = null;\n\tprivate String propertiesFilename = null;\n\tprivate String exportPrismFilename = null;\n\tprivate String exportPrismConstFilename = null;\n\tprivate String exportSCCsFilename = null;\n\tprivate String exportBSCCsFilename = null;\n\tprivate String exportMECsFilename = null;\n\tprivate String exportResultsFilename = null;\n\tprivate String exportVectorFilename = null;\n\tprivate String exportSteadyStateFilename = null;\n\tprivate String exportTransientFilename = null;\n\tprivate String exportStratFilename = null;\n\tprivate String simpathFilename = null;\n\n\t// logs\n\tprivate PrismLog mainLog = null;\n\n\t// prism object\n\tprivate Prism prism = null;\n\n\t// storage for parsed model/properties files\n\tprivate ModulesFile modulesFile = null;\n\tprivate PropertiesFile propertiesFile = null;\n\n\t// model failure info\n\tboolean modelBuildFail = false;\n\tException modelBuildException = null;\n\n\t// info about which properties to model check\n\tprivate int numPropertiesToCheck = 0;\n\tprivate List<Property> propertiesToCheck = null;\n\n\t// info about undefined constants\n\tprivate UndefinedConstants undefinedConstants[];\n\tprivate UndefinedConstants undefinedMFConstants;\n\tprivate Values definedMFConstants;\n\tprivate Values definedPFConstants;\n\n\t// results\n\tprivate ResultsCollection results[] = null;\n\n\t// time for transient computation\n\tprivate String transientTime;\n\n\t// simulation info\n\tprivate String simMethodName = null;\n\tprivate double simApprox;\n\tprivate double simConfidence;\n\tprivate int simNumSamples;\n\tprivate double simWidth;\n\tprivate int reqIterToConclude;\n\tprivate double simMaxReward;\n\tprivate long simMaxPath;\n\tprivate boolean simApproxGiven = false;\n\tprivate boolean simConfidenceGiven = false;\n\tprivate boolean simNumSamplesGiven = false;\n\tprivate boolean simWidthGiven = false;\n\tprivate boolean reqIterToConcludeGiven = false;\n\tprivate boolean simMaxRewardGiven = false;\n\tprivate boolean simMaxPathGiven = false;\n\tprivate boolean simManual = false;\n\tprivate SimulationMethod simMethod = null;\n\n\t// strategy export info\n\tprivate StrategyExportOptions exportStratOptions = null;\n\t\n\t// parametric analysis info\n\tprivate String[] paramLowerBounds = null;\n\tprivate String[] paramUpperBounds = null;\n\tprivate String[] paramNames = null;\n\n\tprivate boolean exactConstants = false;\n\n\t/** Specification of a single file for model import. */\n\tprivate class ModelImportSource\n\t{\n\t\tprivate ModelExportTask.ModelExportEntity entity;\n\t\tprivate ModelExportFormat format;\n\t\tprivate File file;\n\n\t\tpublic ModelImportSource(ModelExportTask.ModelExportEntity entity, ModelExportFormat format, File file)\n\t\t{\n\t\t\tthis.entity = entity;\n\t\t\tthis.format = format;\n\t\t\tthis.file = file;\n\t\t}\n\t}\n\n\t/**\n\t * Entry point: call run method, catch CuddOutOfMemoryException\n\t */\n\tpublic void go(String[] args) {\n\t\ttry {\n\t\t\trun(args);\n\t\t} catch (jdd.JDD.CuddOutOfMemoryException e) {\n\t\t\tmainLog.println(\"\\nCUDD internal error detected, from the following stack trace:\");\n\t\t\tfor (StackTraceElement st : e.getStackTrace()) {\n\t\t\t\tmainLog.print(\"  \");\n\t\t\t\tmainLog.println(st);\n\t\t\t}\n\t\t\terrorAndExit(e.getMessage() + \".\\nTip: Try using the -cuddmaxmem switch to increase the memory available to CUDD\");\n\t\t} catch (com.martiansoftware.nailgun.NGExitException e) {\n\t\t\t// we don't want to catch the nailgun exception below,\n\t\t\t// so we catch it and rethrow\n\t\t\tthrow e;\n\t\t} catch (Exception|StackOverflowError e) {\n\t\t\t// We catch Exceptions/stack overflows here ourself to ensure that we actually exit\n\t\t\t// In the presence of thread pools (e.g., in the JAS library when using -exact),\n\t\t\t// the main thread dying does not necessarily quit the program...\n\t\t\tmainLog.println();\n\t\t\tif (e instanceof StackOverflowError) {\n\t\t\t\t// print exception + limited stack trace for stack overflows\n\t\t\t\tmainLog.println(e.toString());\n\t\t\t\tmainLog.println(StackTraceHelper.asString(e, StackTraceHelper.DEFAULT_STACK_TRACE_LIMIT));\n\t\t\t\tmainLog.println(\"Try increasing the value of the Java stack size (via the -javastack argument).\");\n\t\t\t} else {\n\t\t\t\t// print exception + full stack trace for generic exceptions\n\t\t\t\tmainLog.print(e.toString() + \"\\n\" + StackTraceHelper.asString(e, 0));\n\t\t\t}\n\t\t\terrorAndExit(\"Caught unhandled exception, aborting...\");\n\t\t}\n\t}\n\n\t/**\n\t * Run PRISM.\n\t */\n\tpublic void run(String[] args)\n\t{\n\t\tint i, j, k;\n\t\tResult res;\n\n\t\t// Initialise\n\t\tinitialise(args);\n\n\t\t// Import (and optionally re-export) results\n\t\tif (importresults) {\n\t\t\timportResults();\n\t\t\tif (exportresults) {\n\t\t\t\texportResults();\n\t\t\t}\n\t\t\tcloseDown();\n\t\t\treturn;\n\t\t}\n\n\t\t// Parse/load model/properties\n\t\tdoParsing();\n\n\t\t// Sort out properties to check\n\t\tsortProperties();\n\n\t\t// evaluate constants exactly if we are in param or exact computation mode\n\t\texactConstants = param || prism.getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\n\t\t// process info about undefined constants\n\t\ttry {\n\t\t\t// first, see which constants are undefined\n\t\t\t// (one set of info for model, and one set of info for each property)\n\t\t\tif (modelExportTasks.stream().anyMatch(ModelExportTask::extraLabelsUsed)) {\n\t\t\t\tundefinedMFConstants = new UndefinedConstants(modulesFile, propertiesFile, true);\n\t\t\t} else {\n\t\t\t\tundefinedMFConstants = new UndefinedConstants(modulesFile, null);\n\t\t\t}\n\t\t\tundefinedMFConstants.setExactMode(exactConstants);\n\t\t\tundefinedConstants = new UndefinedConstants[numPropertiesToCheck];\n\t\t\tfor (i = 0; i < numPropertiesToCheck; i++) {\n\t\t\t\tundefinedConstants[i] = new UndefinedConstants(modulesFile, propertiesFile, propertiesToCheck.get(i));\n\t\t\t\tundefinedConstants[i].setExactMode(exactConstants);\n\t\t\t}\n\t\t\t// may need to remove some constants if they are used for parametric methods\n\t\t\tif (param) {\n\t\t\t\tundefinedMFConstants.removeConstants(paramNames);\n\t\t\t\tfor (i = 0; i < numPropertiesToCheck; i++) {\n\t\t\t\t\tundefinedConstants[i].removeConstants(paramNames);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// then set up value using const switch definitions\n\t\t\tundefinedMFConstants.defineUsingConstSwitch(constSwitch);\n\t\t\tfor (i = 0; i < numPropertiesToCheck; i++) {\n\t\t\t\tundefinedConstants[i].defineUsingConstSwitch(constSwitch);\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\terrorAndExit(e.getMessage());\n\t\t}\n\t\tif (param) {\n\t\t\tprism.setParametric(paramNames, paramLowerBounds, paramUpperBounds);\n\t\t}\n\n\t\t// If -exportadv was used and the explicit engine has been requested for MDPs,\n\t\t// or the model type is only supported by the explicit engine, stop with an error message\n\t\tif (prism.getSettings().getChoice(PrismSettings.PRISM_EXPORT_ADV) != Prism.EXPORT_ADV_NONE) {\n\t\t\tif (prism.getModelType() == ModelType.MDP && prism.getCurrentEngine() == Prism.PrismEngine.EXPLICIT) {\n\t\t\t\terrorAndExit(\"The -exportadv functionality does not work for the explicit engine; use -exportstrat instead\");\n\t\t\t}\n\t\t\tif (prism.getModelType().partiallyObservable() || prism.getModelType().uncertain()) {\n\t\t\t\terrorAndExit(\"The -exportadv functionality does not work for the explicit engine; use -exportstrat instead\");\n\t\t\t}\n\t\t}\n\n\t\t// initialise storage for results\n\t\tresults = new ResultsCollection[numPropertiesToCheck];\n\t\tfor (i = 0; i < numPropertiesToCheck; i++) {\n\t\t\tresults[i] = new ResultsCollection(undefinedConstants[i], propertiesToCheck.get(i).getExpression().getResultName());\n\t\t}\n\n\t\t// iterate through as many models as necessary\n\t\tfor (i = 0; i < undefinedMFConstants.getNumModelIterations(); i++) {\n\n\t\t\t// set values for ModulesFile constants\n\t\t\ttry {\n\t\t\t\tdefinedMFConstants = undefinedMFConstants.getMFConstantValues();\n\t\t\t\tprism.setPRISMModelConstants(definedMFConstants, exactConstants);\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// in case of error, report it, store as result for any properties, and go on to the next model\n\t\t\t\t// (might happen for example if overflow or another numerical problem is detected at this stage)\n\t\t\t\terror(e.getMessage());\n\t\t\t\tfor (j = 0; j < numPropertiesToCheck; j++) {\n\t\t\t\t\tresults[j].setMultipleErrors(definedMFConstants, null, e);\n\t\t\t\t}\n\t\t\t\t// iterate to next model\n\t\t\t\tundefinedMFConstants.iterateModel();\n\t\t\t\tfor (j = 0; j < numPropertiesToCheck; j++) {\n\t\t\t\t\tundefinedConstants[j].iterateModel();\n\t\t\t\t}\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tmodelBuildFail = false;\n\n\t\t\t// if requested, generate a random path with the simulator\n\t\t\tif (simpath) {\n\t\t\t\ttry {\n\t\t\t\t\tif (!simMaxPathGiven)\n\t\t\t\t\t\tsimMaxPath = prism.getSettings().getLong(PrismSettings.SIMULATOR_DEFAULT_MAX_PATH);\n\t\t\t\t\tFile f = (simpathFilename.equals(\"stdout\")) ? null : new File(simpathFilename);\n\t\t\t\t\tprism.generateSimulationPath(simpathDetails, simMaxPath, f);\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\terror(e.getMessage());\n\t\t\t\t}\n\t\t\t\t// iterate to next model\n\t\t\t\tundefinedMFConstants.iterateModel();\n\t\t\t\tfor (j = 0; j < numPropertiesToCheck; j++) {\n\t\t\t\t\tundefinedConstants[j].iterateModel();\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Do any model exports\n\t\t\ttry {\n\t\t\t\tdoExports();\n\t\t\t} catch (PrismException e) {\n\t\t\t\terror(e);\n\t\t\t}\n\t\t\tif (modelBuildFail)\n\t\t\t\tcontinue;\n\n\t\t\t// Do steady-state/transient probability computation, if required\n\t\t\tdoSteadyState();\n\t\t\tif (modelBuildFail)\n\t\t\t\tcontinue;\n\t\t\tdoTransient();\n\t\t\tif (modelBuildFail)\n\t\t\t\tcontinue;\n\n\t\t\t// Work through list of properties to be checked\n\t\t\tfor (j = 0; j < numPropertiesToCheck; j++) {\n\n\t\t\t\t// for simulation we can do multiple values of property constants simultaneously\n\t\t\t\tif (simulate && undefinedConstants[j].getNumPropertyIterations() > 1) {\n\t\t\t\t\ttry {\n\t\t\t\t\t\tsimMethod = processSimulationOptions(propertiesToCheck.get(j).getExpression());\n\t\t\t\t\t\tprism.modelCheckSimulatorExperiment(propertiesFile, undefinedConstants[j], results[j], propertiesToCheck.get(j).getExpression(), null,\n\t\t\t\t\t\t\t\tsimMaxPath, simMethod);\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t// in case of (overall) error, report it, store as result for property, and proceed\n\t\t\t\t\t\terror(e.getMessage());\n\t\t\t\t\t\tresults[j].setMultipleErrors(definedMFConstants, null, e);\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t} catch (InterruptedException e) {\n\t\t\t\t\t\t// ignore - won't get interrupted\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// otherwise, treat each case individually\n\t\t\t\telse {\n\t\t\t\t\tfor (k = 0; k < undefinedConstants[j].getNumPropertyIterations(); k++) {\n\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t// Set values for PropertiesFile constants\n\t\t\t\t\t\t\tif (propertiesFile != null) {\n\t\t\t\t\t\t\t\tdefinedPFConstants = undefinedConstants[j].getPFConstantValues();\n\t\t\t\t\t\t\t\tpropertiesFile.setSomeUndefinedConstants(definedPFConstants, exactConstants);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// Normal model checking\n\t\t\t\t\t\t\tif (!simulate) {\n\t\t\t\t\t\t\t\tres = prism.modelCheck(propertiesFile, propertiesToCheck.get(j));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// Approximate (simulation-based) model checking\n\t\t\t\t\t\t\telse {\n\t\t\t\t\t\t\t\tsimMethod = processSimulationOptions(propertiesToCheck.get(j).getExpression());\n\t\t\t\t\t\t\t\tres = prism.modelCheckSimulator(propertiesFile, propertiesToCheck.get(j).getExpression(), definedPFConstants, null, simMaxPath,\n\t\t\t\t\t\t\t\t\t\tsimMethod);\n\t\t\t\t\t\t\t\tsimMethod.reset();\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t\t// in case of error, report it, store exception as the result and proceed\n\t\t\t\t\t\t\terror(e.getMessage(), true);\n\t\t\t\t\t\t\tres = new Result(e);\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// in case of build failure during model checking, store as result for any const values and continue\n\t\t\t\t\t\tif (modelBuildFail) {\n\t\t\t\t\t\t\tresults[j].setMultipleErrors(definedMFConstants, null, modelBuildException);\n\t\t\t\t\t\t\tif (test) {\n\t\t\t\t\t\t\t\tdoResultTest(propertiesToCheck.get(j), new Result(modelBuildException), prism.getModelInfo().getConstantValues(), propertiesFile.getConstantValues());\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// store result of model checking\n\t\t\t\t\t\tresults[j].setResult(definedMFConstants, definedPFConstants, res.getResult());\n\n\t\t\t\t\t\t// if a counterexample was generated, display it\n\t\t\t\t\t\tObject cex = res.getCounterexample();\n\t\t\t\t\t\tif (cex != null) {\n\t\t\t\t\t\t\tmainLog.println(\"\\nCounterexample/witness:\");\n\t\t\t\t\t\t\tmainLog.println(cex);\n\t\t\t\t\t\t\t/*SimulatorEngine engine = prism.getSimulator();\n\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\tengine.loadPath(modulesFile, (CexPathStates) cex);\n\t\t\t\t\t\t\t\tengine.exportPath(null, true, \",\", null);\n\t\t\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t\t\terror(e.getMessage());\n\t\t\t\t\t\t\t}*/\n\t\t\t\t\t\t\tif (cex instanceof cex.CexPathAsBDDs) {\n\t\t\t\t\t\t\t\t((cex.CexPathAsBDDs) cex).clear();\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// if a strategy was generated, and we need to export it, do so\n\t\t\t\t\t\tif (exportstrat && res.getStrategy() != null) {\n\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\tprism.exportStrategy(res.getStrategy(), exportStratOptions, exportStratFilename.equals(\"stdout\") ? null : new File(exportStratFilename));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// in case of error, report it and proceed\n\t\t\t\t\t\t\tcatch (FileNotFoundException e) {\n\t\t\t\t\t\t\t\terror(\"Couldn't open file \\\"\" + exportStratFilename + \"\\\" for output\");\n\t\t\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t\t\terror(e.getMessage());\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// if a results vector was stored, and we need to export it, do so\n\t\t\t\t\t\tif (exportvector && res.getVector() != null) {\n\t\t\t\t\t\t\tmainLog.print(\"\\nExporting vector of results for all states \");\n\t\t\t\t\t\t\tmainLog.println(exportVectorFilename.equals(\"stdout\") ? \"below:\" : \"to file \\\"\" + exportVectorFilename + \"\\\"...\");\n\t\t\t\t\t\t\tboolean toStdout = exportVectorFilename.equals(\"stdout\");\n\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\tPrismLog tmpLog = toStdout ? prism.getMainLog() : new PrismFileLog(exportVectorFilename);\n\t\t\t\t\t\t\t\tres.getVector().print(tmpLog, false, false, toStdout, toStdout);\n\t\t\t\t\t\t\t\tres.getVector().clear();\n\t\t\t\t\t\t\t\tif (!toStdout) {\n\t\t\t\t\t\t\t\t\ttmpLog.close();\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t\t\terror(e.getMessage());\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\t// if required, check result against expected value\n\t\t\t\t\t\tif (test) {\n\t\t\t\t\t\t\tdoResultTest(propertiesToCheck.get(j), res, prism.getModelInfo().getConstantValues(), propertiesFile.getConstantValues());\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// iterate to next property\n\t\t\t\t\t\tundefinedConstants[j].iterateProperty();\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// in case of build failure during model checking, store as result for any further properties and continue\n\t\t\t\tif (modelBuildFail) {\n\t\t\t\t\tfor (j++; j < numPropertiesToCheck; j++) {\n\t\t\t\t\t\tresults[j].setMultipleErrors(definedMFConstants, null, modelBuildException);\n\t\t\t\t\t\tif (test) {\n\t\t\t\t\t\t\tdoResultTest(propertiesToCheck.get(j), new Result(modelBuildException), prism.getModelInfo().getConstantValues(), propertiesFile.getConstantValues());\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Explicitly request a build if necessary\n\t\t\tif (propertiesToCheck.size() == 0 && !steadystate && !dotransient && !simpath && !nobuild && prism.modelCanBeBuilt() && !prism.someModelIsBuilt()) {\n\t\t\t\ttry {\n\t\t\t\t\tprism.buildModel();\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\terror(e.getMessage());\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// iterate to next model\n\t\t\tundefinedMFConstants.iterateModel();\n\t\t\tfor (j = 0; j < numPropertiesToCheck; j++) {\n\t\t\t\tundefinedConstants[j].iterateModel();\n\t\t\t}\n\t\t}\n\n\t\t// export results (if required)\n\t\tif (exportresults) {\n\t\t\texportResults();\n\t\t}\n\t\t// close down\n\t\tcloseDown();\n\n\t}\n\n\t/**\n\t * Import results from a data frame in a CSV file.\n\t */\n\tprotected void importResults()\n\t{\n\t\tmainLog.print(\"\\nImporting results from dataframe in \" + importResultsFilename + \"\\\"...\");\n\t\ttry {\n\t\t\tpropertiesToCheck = new ArrayList<Property>();\n\t\t\tList<ResultsCollection> importedResults = new ArrayList<ResultsCollection>();\n\t\t\tFileReader reader = new FileReader(new File(importResultsFilename));\n\t\t\tResultsImporter importer = new ResultsImporter(new BufferedReader(reader));\n\t\t\tfor (Entry<Property, RawResultsCollection> result : importer) {\n\t\t\t\tpropertiesToCheck.add(result.getKey());\n\t\t\t\timportedResults.add(result.getValue().toResultsCollection());\n\t\t\t}\n\t\t\tresults = importedResults.toArray(new ResultsCollection[0]);\n\t\t} catch (FileNotFoundException e) {\n\t\t\terrorAndExit(\"Could not import results: \" + e.getMessage());\n\t\t} catch (IOException e) {\n\t\t\terrorAndExit(\"Could not read results file: \" + e.getMessage());\n\t\t} catch (CsvFormatException e) {\n\t\t\terrorAndExit(\"Malformatted CSV results file: \" + e.getMessage());\n\t\t} catch (PrismLangException e) {\n\t\t\terrorAndExit(\"Syntax error in results file: \" + e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Export results to a file according to the export options.\n\t */\n\tprotected void exportResults()\n\t{\n\t\tmainLog.print(\"\\nExporting results as \" + exportShape.fullName);\n\t\tmainLog.println(exportResultsFilename.equals(\"stdout\") ? \" below:\\n\" : \" to file \\\"\" + exportResultsFilename + \"\\\"...\");\n\n\t\ttry {\n\t\t\tPrintWriter out;\n\t\t\tif (exportResultsFilename.equals(\"stdout\")) {\n\t\t\t\tout = new PrintWriter(System.out);\n\t\t\t\texportShape.getExporter().printResults(Arrays.asList(results), propertiesToCheck, out);\n\t\t\t\t// Do not close System.out !\n\t\t\t} else {\n\t\t\t\tout = new PrintWriter(exportResultsFilename);\n\t\t\t\texportShape.getExporter().printResults(Arrays.asList(results), propertiesToCheck, out);\n\t\t\t\tout.close();\n\t\t\t}\n\t\t\tif (out.checkError()) {\n\t\t\t\t// PrintWriter hides exceptions in print methods and close()\n\t\t\t\terrorAndExit(\"Could not export results: unknown IO exception\");\n\t\t\t}\n\t\t} catch (FileNotFoundException e) {\n\t\t\terrorAndExit(\"Could not export results: \" + e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Initialise.\n\t */\n\tprivate void initialise(String[] args)\n\t{\n\t\ttry {\n\t\t\t// default to log going to stdout\n\t\t\t// this means all errors etc. can be safely sent to the log\n\t\t\t// even if a new log is created shortly\n\t\t\tmainLog = new PrismFileLog(\"stdout\");\n\n\t\t\t// create prism object(s)\n\t\t\tprism = new Prism(mainLog);\n\t\t\tprism.addModelListener(this);\n\n\t\t\t// parse command line arguments\n\t\t\tparseArguments(args);\n\n\t\t\t// load setting file if requested\n\t\t\tif (settingsFilename != null)\n\t\t\t\tprism.loadUserSettingsFile(new File(settingsFilename));\n\n\t\t\t// initialise\n\t\t\tprism.initialise();\n\n\t\t\t// print command line for reference\n\t\t\tprintArguments(args);\n\n\t\t\t// do some processing of the options\n\t\t\tprocessOptions();\n\t\t} catch (PrismException e) {\n\t\t\terrorAndExit(e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Parse model and properties, load model into PRISM. \n\t */\n\tprivate void doParsing()\n\t{\n\t\tint i;\n\t\tFile sf = null, lf = null;\n\t\tList<File> srf = new ArrayList<>();\n\t\tList<File> trf = new ArrayList<>();\n\n\t\t// parse model\n\n\t\ttry {\n\t\t\tif (importModelWarning != null) {\n\t\t\t\tmainLog.printWarning(importModelWarning);\n\t\t\t}\n\t\t\tif (importpepa) {\n\t\t\t\tmodulesFile = prism.importPepaFile(new File(modelFilename));\n\t\t\t\tprism.loadPRISMModel(modulesFile);\n\t\t\t} else if (importprismpp) {\n\t\t\t\tString prismppParamsList[] = (\"? \" + prismppParams).split(\" \");\n\t\t\t\tmodulesFile = prism.importPrismPreprocFile(new File(modelFilename), prismppParamsList);\n\t\t\t\tprism.loadPRISMModel(modulesFile);\n\t\t\t} else if (!modelImportSources.isEmpty()) {\n\t\t\t\tsortModelImports();\n\t\t\t} else {\n\t\t\t\tmodulesFile = prism.parseModelFile(new File(modelFilename), typeOverride);\n\t\t\t\tprism.loadPRISMModel(modulesFile);\n\t\t\t}\n\t\t} catch (FileNotFoundException e) {\n\t\t\terrorAndExit(\"File \\\"\" + modelFilename + \"\\\" not found\");\n\t\t} catch (PrismException e) {\n\t\t\terrorAndExit(e.getMessage());\n\t\t}\n\n\t\t// export prism model, if requested\n\t\tif (exportprism) {\n\t\t\ttry {\n\t\t\t\tFile f = (exportPrismFilename.equals(\"stdout\")) ? null : new File(exportPrismFilename);\n\t\t\t\tprism.exportPRISMModel(f);\n\t\t\t}\n\t\t\t// in case of error, report it and proceed\n\t\t\tcatch (FileNotFoundException e) {\n\t\t\t\terror(\"Couldn't open file \\\"\" + exportPrismFilename + \"\\\" for output\");\n\t\t\t} catch (PrismException e) {\n\t\t\t\terror(e);\n\t\t\t}\n\t\t}\n\n\t\t// parse properties\n\n\t\ttry {\n\t\t\t// if properties file specified...\n\t\t\tif (propertiesFilename != null) {\n\t\t\t\tmainLog.print(\"\\nParsing properties file \\\"\" + propertiesFilename + \"\\\"...\\n\");\n\t\t\t\tpropertiesFile = prism.parsePropertiesFile(new File(propertiesFilename));\n\t\t\t}\n\t\t\t// if properties were given on command line...\n\t\t\telse if (!propertyString.equals(\"\")) {\n\t\t\t\tpropertiesFile = prism.parsePropertiesString(propertyString);\n\t\t\t} else {\n\t\t\t\tpropertiesFile = null;\n\t\t\t}\n\t\t} catch (FileNotFoundException e) {\n\t\t\terrorAndExit(\"File \\\"\" + propertiesFilename + \"\\\" not found\");\n\t\t} catch (PrismException e) {\n\t\t\terrorAndExit(e.getMessage());\n\t\t}\n\n\t\t// print out properties (if any)\n\n\t\tif (propertiesFile != null) {\n\t\t\tmainLog.print(\"\\n\" + propertiesFile.getNumProperties());\n\t\t\tmainLog.print(\" propert\" + ((propertiesFile.getNumProperties() == 1) ? \"y\" : \"ies\") + \":\\n\");\n\t\t\tfor (i = 0; i < propertiesFile.getNumProperties(); i++) {\n\t\t\t\tmainLog.println(\"(\" + (i + 1) + \") \" + propertiesFile.getPropertyObject(i));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * If importing a model, process the specification and import.\n\t */\n\tprivate void sortModelImports() throws PrismException\n\t{\n\t\t// Exactly one model/transitions source should be provided\n\t\tint numModelSources = (int) modelImportSources.stream().filter(s -> s.entity == ModelExportTask.ModelExportEntity.MODEL).count();\n\t\tif (numModelSources < 1) {\n\t\t\tthrow new PrismException(\"No transitions specified for model import\");\n\t\t}\n\t\tif (numModelSources > 1) {\n\t\t\tthrow new PrismException(\"Multiple model imports provided\");\n\t\t}\n\t\t// Create an importer and add the requested files\n\t\tModelImportSource modelSource = modelImportSources.stream().filter(s -> s.entity == ModelExportTask.ModelExportEntity.MODEL).findFirst().get();\n\t\tswitch (modelSource.format) {\n\t\t\t// Import from PRISM explicit files\n\t\t\tcase EXPLICIT:\n\t\t\t\tif (!modelImportSources.stream().allMatch(s -> s.format == ModelExportFormat.EXPLICIT)) {\n\t\t\t\t\tthrow new PrismException(\"Mixed formats for model import\");\n\t\t\t\t}\n\t\t\t\tPrismExplicitImporter importer = new PrismExplicitImporter(modelSource.file, typeOverride);\n\t\t\t\tfor (ModelImportSource modelImportSource : modelImportSources) {\n\t\t\t\t\tswitch (modelImportSource.entity) {\n\t\t\t\t\t\tcase MODEL:\n\t\t\t\t\t\t\t// Skip; already handled\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase STATES:\n\t\t\t\t\t\t\tif (importer.getStatesFile() != null) {\n\t\t\t\t\t\t\t\tthrow new PrismException(\"Multiple state files provided for model import\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\timporter.setStatesFile(modelImportSource.file);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase OBSERVATIONS:\n\t\t\t\t\t\t\tif (importer.getObservationsFile() != null) {\n\t\t\t\t\t\t\t\tthrow new PrismException(\"Multiple observation files provided for model import\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\timporter.setObservationsFile(modelImportSource.file);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase LABELS:\n\t\t\t\t\t\t\tif (importer.getLabelsFile() != null) {\n\t\t\t\t\t\t\t\tthrow new PrismException(\"Multiple label files provided for model import\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\timporter.setLabelsFile(modelImportSource.file);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase STATE_REWARDS:\n\t\t\t\t\t\t\timporter.addStateRewardsFile(modelImportSource.file);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase TRANSITION_REWARDS:\n\t\t\t\t\t\t\timporter.addTransitionRewardsFile(modelImportSource.file);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\tthrow new PrismException(\"Unknown model import entity\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tprism.loadModelFromExplicitFiles(importer);\n\t\t\t\tbreak;\n\n\t\t\t// Import from a UMB file\n\t\t\tcase UMB:\n\t\t\t\tif (modelImportSources.size() > 1) {\n\t\t\t\t\tthrow new PrismException(\"Conflicting files provided for model import\");\n\t\t\t\t}\n\t\t\t\tprism.loadModelFromUMBFile(modelSource.file);\n\t\t\t\tbreak;\n\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown model import format \" + modelSource.format);\n\t\t}\n\n\t}\n\n\t/**\n\t * Sort out which properties need checking. \n\t */\n\tprivate void sortProperties()\n\t{\n\t\tint i;\n\n\t\tpropertiesToCheck = new ArrayList<Property>();\n\n\t\t// no properties to check\n\t\tif (propertiesFile == null) {\n\t\t\tif (propertyIndices != null && !propertyIndices.isEmpty()) {\n\t\t\t\terrorAndExit(\"There is not a property \\\"\" + propertyIndices.get(0) + \"\\\" to check\");\n\t\t\t}\n\t\t\tnumPropertiesToCheck = 0;\n\t\t}\n\t\t// unless specified, verify all properties\n\t\telse if (propertyIndices == null) {\n\t\t\tnumPropertiesToCheck = propertiesFile.getNumProperties();\n\t\t\tfor (i = 0; i < numPropertiesToCheck; i++) {\n\t\t\t\tpropertiesToCheck.add(propertiesFile.getPropertyObject(i));\n\t\t\t}\n\t\t}\n\t\t// otherwise just verify the specified properties\n\t\telse {\n\t\t\tfor (Object o : propertyIndices) {\n\t\t\t\tif (o instanceof Integer) {\n\t\t\t\t\tint propIndex = (Integer) o;\n\t\t\t\t\tif (propIndex <= 0 || propIndex > propertiesFile.getNumProperties())\n\t\t\t\t\t\terrorAndExit(\"There is not a property \" + propIndex + \" to verify\");\n\t\t\t\t\tnumPropertiesToCheck += 1;\n\t\t\t\t\tpropertiesToCheck.add(propertiesFile.getPropertyObject(propIndex - 1));\n\t\t\t\t} else if (o instanceof String) {\n\t\t\t\t\tProperty p = propertiesFile.getPropertyObjectByName((String) o);\n\t\t\t\t\tif (p == null)\n\t\t\t\t\t\terrorAndExit(\"There is not a property \\\"\" + o + \"\\\" to check\");\n\t\t\t\t\tnumPropertiesToCheck += 1;\n\t\t\t\t\tpropertiesToCheck.add(p);\n\t\t\t\t} else {\n\t\t\t\t\terrorAndExit(\"There is not a property \" + o + \" to check\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// do any exporting requested\n\n\tprivate void doExports() throws PrismException\n\t{\n\t\t// export prism model (with constants), if requested\n\t\tif (exportprismconst) {\n\t\t\ttry {\n\t\t\t\tFile f = (exportPrismConstFilename.equals(\"stdout\")) ? null : new File(exportPrismConstFilename);\n\t\t\t\tprism.exportPRISMModelWithExpandedConstants(f);\n\t\t\t}\n\t\t\t// in case of error, report it and proceed\n\t\t\tcatch (FileNotFoundException e) {\n\t\t\t\terror(\"Couldn't open file \\\"\" + exportPrismConstFilename + \"\\\" for output\");\n\t\t\t} catch (PrismException e) {\n\t\t\t\terror(e);\n\t\t\t}\n\t\t}\n\n\t\t// Exceptions from the remaining exports are thrown\n\t\t// since they usually indicate a model build problem, affecting all\n\n\t\t// Do export tasks\n\t\tfor (ModelExportTask exportTask : modelExportTasks) {\n\t\t\texportTask.getExportOptions().apply(modelExportOptionsGlobal);\n\t\t\tif (exportTask.extraLabelsUsed()) {\n\t\t\t\tdefinedPFConstants = undefinedMFConstants.getPFConstantValues();\n\t\t\t\tpropertiesFile.setSomeUndefinedConstants(definedPFConstants, exactConstants);\n\t\t\t\texportTask.setExtraLabelsSource(propertiesFile);\n\t\t\t}\n\t\t}\n\t\tif (!modelExportTasks.isEmpty()) {\n\t\t\tprism.exportBuiltModelTasks(modelExportTasks);\n\t\t}\n\n\t\t// export transition matrix graph to dot file and view it\n\t\tif (exportmodeldotview) {\n\t\t\ttry {\n\t\t\t\tFile dotFile = File.createTempFile(\"prism-dot-\", \".dot\", null);\n\t\t\t\tFile dotPdfFile = File.createTempFile(\"prism-dot-\", \".dot.pdf\", null);\n\t\t\t\tprism.exportBuiltModelTransitions(dotFile, new ModelExportOptions().setFormat(ModelExportFormat.DOT).setShowStates(true).setShowObservations(true));\n\t\t\t\t(new ProcessBuilder(new String[]{ \"dot\", \"-Tpdf\", \"-o\", dotPdfFile.getPath(), dotFile.getPath()})).start().waitFor();\n\t\t\t\t(new ProcessBuilder(new String[]{ \"open\",dotPdfFile.getPath()})).start();\n\t\t\t}\n\t\t\t// in case of error, report it and proceed\n\t\t\tcatch (IOException | InterruptedException e) {\n\t\t\t\terror(\"Problem generating dot file: \" + e.getMessage());\n\t\t\t}\n\t\t}\n\n\t\t// export SCCs to a file\n\t\tif (exportsccs) {\n\t\t\ttry {\n\t\t\t\tFile f = (exportSCCsFilename.equals(\"stdout\")) ? null : new File(exportSCCsFilename);\n\t\t\t\tprism.exportSCCsToFile(exportType, f);\n\t\t\t}\n\t\t\t// in case of error, report it and proceed\n\t\t\tcatch (FileNotFoundException e) {\n\t\t\t\terror(\"Couldn't open file \\\"\" + exportSCCsFilename + \"\\\" for output\");\n\t\t\t}\n\t\t}\n\n\t\t// export BSCCs to a file\n\t\tif (exportbsccs) {\n\t\t\ttry {\n\t\t\t\tFile f = (exportBSCCsFilename.equals(\"stdout\")) ? null : new File(exportBSCCsFilename);\n\t\t\t\tprism.exportBSCCsToFile(exportType, f);\n\t\t\t}\n\t\t\t// in case of error, report it and proceed\n\t\t\tcatch (FileNotFoundException e) {\n\t\t\t\terror(\"Couldn't open file \\\"\" + exportBSCCsFilename + \"\\\" for output\");\n\t\t\t}\n\t\t}\n\n\t\t// export MECs to a file\n\t\tif (exportmecs) {\n\t\t\ttry {\n\t\t\t\tFile f = (exportMECsFilename.equals(\"stdout\")) ? null : new File(exportMECsFilename);\n\t\t\t\tprism.exportMECsToFile(exportType, f);\n\t\t\t}\n\t\t\t// in case of error, report it and proceed\n\t\t\tcatch (FileNotFoundException e) {\n\t\t\t\terror(\"Couldn't open file \\\"\" + exportMECsFilename + \"\\\" for output\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Do steady-state probability computation (if required).\n\t */\n\tprivate void doSteadyState()\n\t{\n\t\tFile exportSteadyStateFile = null;\n\n\t\tif (steadystate) {\n\t\t\ttry {\n\t\t\t\t// Choose destination for output (file or log)\n\t\t\t\tif (exportSteadyStateFilename == null || exportSteadyStateFilename.equals(\"stdout\"))\n\t\t\t\t\texportSteadyStateFile = null;\n\t\t\t\telse\n\t\t\t\t\texportSteadyStateFile = new File(exportSteadyStateFilename);\n\t\t\t\t// Compute steady-state probabilities\n\t\t\t\tprism.exportSteadyStateProbabilities(exportSteadyStateFile, Prism.convertExportType(exportType), importinitdist ? new File(importInitDistFilename) : null);\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// In case of error, report it and proceed\n\t\t\t\terror(e);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Do transient probability computation (if required).\n\t */\n\tprivate void doTransient()\n\t{\n\t\tModelType modelType;\n\t\tFile exportTransientFile = null;\n\n\t\tif (dotransient) {\n\t\t\ttry {\n\t\t\t\t// Choose destination for output (file or log)\n\t\t\t\tif (exportTransientFilename == null || exportTransientFilename.equals(\"stdout\"))\n\t\t\t\t\texportTransientFile = null;\n\t\t\t\telse\n\t\t\t\t\texportTransientFile = new File(exportTransientFilename);\n\t\t\t\t// Compute transient probabilities\n\t\t\t\tprism.exportTransientProbabilities(transientTime, exportTransientFile, Prism.convertExportType(exportType), importinitdist ? new File(importInitDistFilename) : null);\n\t\t\t}\n\t\t\t// In case of error, report it and proceed\n\t\t\tcatch (PrismException e) {\n\t\t\t\terror(e);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Test a model checking result against the RESULT specifications attached\n\t * to the property (test mode). Test results are output to the log.\n\t * If a test fails and {@code testExitsOnFail} is {@code true} then {@code errorAndExit} is called.\n\t * Model/properties file constant values should be provided in case they are used\n\t * in the RESULT specification (but either can be left null if not needed).\n\t * @param prop the property\n\t * @param res the result\n\t * @param mfConstants values for model constants\n\t * @param pfConstants values for properties file constants\n\t */\n\tprivate void doResultTest(Property prop, Result res, Values mfConstants, Values pfConstants)\n\t{\n\t\ttry {\n\t\t\tValues allConsts = new Values(mfConstants, pfConstants);\n\t\t\tList<String> allParams = param ? Arrays.asList(paramNames) : Collections.emptyList(); \n\t\t\tif (prop.checkAgainstExpectedResult(res, allConsts, allParams)) {\n\t\t\t\tmainLog.println(\"Testing result: PASS\");\n\t\t\t} else {\n\t\t\t\tmainLog.println(\"Testing result: NOT TESTED\");\n\t\t\t}\n\t\t} catch (PrismNotSupportedException e) {\n\t\t\tmainLog.println(\"Testing result: UNSUPPORTED: \" + e.getMessage());\n\t\t} catch (PrismException e) {\n\t\t\tmainLog.println(\"Testing result: FAIL: \" + e.getMessage());\n\t\t\tif (testExitsOnFail)\n\t\t\t\terrorAndExit(\"Testing failed\");\n\t\t}\n\t}\n\n\t/**\n\t * Close down.\n\t */\n\tprivate void closeDown()\n\t{\n\t\t// clear up and close down\n\t\tprism.closeDown(true);\n\t\t// notify about any warnings\n\t\tint numWarnings = mainLog.getNumberOfWarnings();\n\t\tif (numWarnings > 0) {\n\t\t\tmainLog.printSeparator();\n\t\t\tmainLog.print(\"\\nNote: There \");\n\t\t\tif (numWarnings == 1)\n\t\t\t\tmainLog.print(\"was 1 warning\");\n\t\t\telse\n\t\t\t\tmainLog.print(\"were \" + numWarnings + \" warnings\");\n\t\t\tmainLog.println(\" during computation.\");\n\t\t}\n\t\tmainLog.println();\n\t\t// Close logs (in case they are files)\n\t\tmainLog.close();\n\t}\n\n\t/** Set a timeout, exit program if timeout is reached */\n\tprivate void setTimeout(final int timeout)\n\t{\n\t\tcommon.Timeout.setTimeout(timeout, new Runnable() {\n\t\t\t@Override\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tmainLog.println(\"\\nError: Timeout (after \" + timeout + \" seconds).\");\n\t\t\t\tmainLog.flush();\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t});\n\t}\n\n\t// PrismModelListener methods\n\n\t@Override\n\tpublic void notifyModelBuildSuccessful()\n\t{\n\t}\n\n\t@Override\n\tpublic void notifyModelBuildFailed(PrismException e)\n\t{\n\t\tmodelBuildFail = true;\n\t\tmodelBuildException = e;\n\t}\n\n\t/**\n\t * Process command-line arguments/switches.\n\t */\n\tprivate void parseArguments(String[] args) throws PrismException\n\t{\n\t\tint i, j;\n\t\tString sw, s;\n\t\tPrismLog log;\n\n\t\tconstSwitch = \"\";\n\t\tparamSwitch = \"\";\n\t\tList<String> filenameArgs = new ArrayList<>();\n\n\t\tfor (i = 0; i < args.length; i++) {\n\n\t\t\t// if is a switch...\n\t\t\tif (args[i].length() > 0 && args[i].charAt(0) == '-') {\n\n\t\t\t\t// Remove \"-\"\n\t\t\t\tsw = args[i].substring(1);\n\t\t\t\tif (sw.length() == 0) {\n\t\t\t\t\terrorAndExit(\"Invalid empty switch\");\n\t\t\t\t}\n\t\t\t\t// Remove optional second \"-\" (i.e. we allow switches of the form --sw too)\n\t\t\t\tif (sw.charAt(0) == '-')\n\t\t\t\t\tsw = sw.substring(1);\n\n\t\t\t\t// Note: the order of these switches should match the -help output (just to help keep track of things).\n\t\t\t\t// But: processing of \"PRISM\" options is done elsewhere in PrismSettings\n\t\t\t\t// Any \"hidden\" options, i.e. not in -help text/manual, are indicated as such.\n\n\t\t\t\t// print help\n\t\t\t\tif (sw.equals(\"help\") || sw.equals(\"?\")) {\n\t\t\t\t\t// see if user requested help for a specific switch, e.g. -help simpath\n\t\t\t\t\t// note: this is one of the few places where a second argument is optional,\n\t\t\t\t\t// which is possible here because -help should usually be the only switch provided\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprintHelpSwitch(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tprintHelp();\n\t\t\t\t\t}\n\t\t\t\t\texit();\n\t\t\t\t}\n\t\t\t\t// java max mem & java stack size & java parameters\n\t\t\t\telse if (sw.equals(\"javamaxmem\") || sw.equals(\"javastack\") || sw.equals(\"javaparams\")) {\n\t\t\t\t\t// ignore argument and subsequent value, this is dealt with before java is launched\n\t\t\t\t\ti++;\n\t\t\t\t}\n\t\t\t\t// timeout\n\t\t\t\telse if (sw.equals(\"timeout\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tint timeout = PrismUtils.convertTimeStringtoSeconds(args[++i]);\n\t\t\t\t\t\tif (timeout < 0) {\n\t\t\t\t\t\t\terrorAndExit(\"Negative timeout value \\\"\" + timeout + \"\\\" for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (timeout > 0) {\n\t\t\t\t\t\t\tsetTimeout(timeout);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// timeout == 0 -> no timeout\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"Missing timeout value for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// print version\n\t\t\t\telse if (sw.equals(\"version\")) {\n\t\t\t\t\tprintVersion();\n\t\t\t\t\texit();\n\t\t\t\t}\n\t\t\t\t// set working directory\n\t\t\t\telse if (sw.equals(\"dir\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tPrism.setWorkingDirectory(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No property specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// load settings\n\t\t\t\telse if (sw.equals(\"settings\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tsettingsFilename = args[++i].trim();\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"Incomplete -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// print a list of all keywords (hidden option)\n\t\t\t\telse if (sw.equals(\"keywords\")) {\n\t\t\t\t\tprintListOfKeywords();\n\t\t\t\t\texit();\n\t\t\t\t}\n\n\t\t\t\t// property/properties given in command line\n\t\t\t\telse if (sw.equals(\"pf\") || sw.equals(\"pctl\") || sw.equals(\"csl\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tpropertyString = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No property specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// which property to check (int index or string name)\n\t\t\t\telse if (sw.equals(\"prop\") || sw.equals(\"property\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tString[] props = args[++i].trim().split(\",\");\n\t\t\t\t\t\tpropertyIndices = new ArrayList<Object>();\n\t\t\t\t\t\tfor (String p : props) {\n\t\t\t\t\t\t\tif (!p.isEmpty()) {\n\t\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\t\tpropertyIndices.add(Integer.parseInt(p));\n\t\t\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\t\t\tpropertyIndices.add(p);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// definition of undefined constants\n\t\t\t\telse if (sw.equals(\"const\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\t// store argument for later use (append if already partially specified)\n\t\t\t\t\t\tif (\"\".equals(constSwitch))\n\t\t\t\t\t\t\tconstSwitch = args[++i].trim();\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\tconstSwitch += \",\" + args[++i].trim();\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"Incomplete -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// defining a parameter\n\t\t\t\telse if (sw.equals(\"param\")) {\n\t\t\t\t\tparam = true;\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\t// store argument for later use (append if already partially specified)\n\t\t\t\t\t\tif (\"\".equals(paramSwitch)) {\n\t\t\t\t\t\t\tparamSwitch = args[++i].trim();\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tparamSwitch += \",\" + args[++i].trim();\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"Incomplete -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// do steady-state probability computation\n\t\t\t\telse if (sw.equals(\"steadystate\") || sw.equals(\"ss\")) {\n\t\t\t\t\tsteadystate = true;\n\t\t\t\t}\n\t\t\t\t// do transient probability computation\n\t\t\t\telse if (sw.equals(\"transient\") || sw.equals(\"tr\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tdotransient = true;\n\t\t\t\t\t\ttransientTime = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// generate random path with simulator\n\t\t\t\telse if (sw.equals(\"simpath\")) {\n\t\t\t\t\tif (i < args.length - 2) {\n\t\t\t\t\t\tsimpath = true;\n\t\t\t\t\t\tsimpathDetails = args[++i];\n\t\t\t\t\t\tsimpathFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"The -\" + sw + \" switch requires two arguments (path details, filename)\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// disable model construction\n\t\t\t\telse if (sw.equals(\"nobuild\")) {\n\t\t\t\t\tnobuild = true;\n\t\t\t\t}\n\t\t\t\t// enable \"testing\" mode\n\t\t\t\telse if (sw.equals(\"test\")) {\n\t\t\t\t\ttest = true;\n\t\t\t\t}\n\t\t\t\t// enable \"test all\" mode (don't stop on errors)\n\t\t\t\t// (overrides -test switch)\n\t\t\t\telse if (sw.equals(\"testall\")) {\n\t\t\t\t\ttest = true;\n\t\t\t\t\ttestExitsOnFail = false;\n\t\t\t\t}\n\t\t\t\t// enable UMB test mode\n\t\t\t\telse if (sw.equals(\"test:umb\")) {\n\t\t\t\t\tprism.setTestUMB(true);\n\t\t\t\t}\n\n\t\t\t\t// DD Debugging options\n\t\t\t\telse if (sw.equals(\"dddebug\")) {\n\t\t\t\t\tjdd.DebugJDD.enable();\n\t\t\t\t}\n\t\t\t\telse if (sw.equals(\"ddtraceall\")) {\n\t\t\t\t\tjdd.DebugJDD.traceAll = true;\n\t\t\t\t}\n\t\t\t\telse if (sw.equals(\"ddtracefollowcopies\")) {\n\t\t\t\t\tjdd.DebugJDD.traceFollowCopies = true;\n\t\t\t\t}\n\t\t\t\telse if (sw.equals(\"dddebugwarnfatal\")) {\n\t\t\t\t\tjdd.DebugJDD.warningsAreFatal = true;\n\t\t\t\t}\n\t\t\t\telse if (sw.equals(\"dddebugwarnoff\")) {\n\t\t\t\t\tjdd.DebugJDD.warningsOff = true;\n\t\t\t\t}\n\t\t\t\telse if (sw.equals(\"ddtrace\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tString idString = args[++i];\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tint id = Integer.parseInt(idString);\n\t\t\t\t\t\t\tjdd.DebugJDD.enableTracingForID(id);\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"The -\" + sw + \" switch requires an integer argument (JDDNode ID)\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"The -\" + sw + \" switch requires an additional argument (JDDNode ID)\");\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// IMPORT OPTIONS:\n\n\t\t\t\t// change model type to pepa\n\t\t\t\telse if (sw.equals(\"importpepa\")) {\n\t\t\t\t\timportpepa = true;\n\t\t\t\t}\n\t\t\t\t// Import model from PRISM preprocessor (hidden option)\n\t\t\t\telse if (sw.equals(\"importprismpp\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\timportprismpp = true;\n\t\t\t\t\t\tprismppParams = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No parameters specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import model from explicit file(s)\n\t\t\t\telse if (sw.equals(\"importmodel\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprocessImportModelSwitch(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file/options specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import transition matrix from explicit format\n\t\t\t\telse if (sw.equals(\"importtrans\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\t// Recall model name in case needed as basename for model exprts\n\t\t\t\t\t\tmodelFilename = args[++i];\n\t\t\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.MODEL, ModelExportFormat.EXPLICIT, new File(modelFilename)));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import states for explicit model import\n\t\t\t\telse if (sw.equals(\"importstates\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.STATES, ModelExportFormat.EXPLICIT, new File(args[++i])));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import observations for explicit model import\n\t\t\t\telse if (sw.equals(\"importobs\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.OBSERVATIONS, ModelExportFormat.EXPLICIT, new File(args[++i])));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import labels for explicit model import\n\t\t\t\telse if (sw.equals(\"importlabels\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.LABELS, ModelExportFormat.EXPLICIT, new File(args[++i])));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import state rewards for explicit model import\n\t\t\t\telse if (sw.equals(\"importstaterewards\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.STATE_REWARDS, ModelExportFormat.EXPLICIT, new File(args[++i])));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import trans rewards for explicit model import\n\t\t\t\telse if (sw.equals(\"importtransrewards\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.TRANSITION_REWARDS, ModelExportFormat.EXPLICIT, new File(args[++i])));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import initial distribution e.g. for transient probability distribution\n\t\t\t\telse if (sw.equals(\"importinitdist\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\timportinitdist = true;\n\t\t\t\t\t\timportInitDistFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// import results\n\t\t\t\telse if (sw.equals(\"importresults\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\timportresults = true;\n\t\t\t\t\t\tmodelFilename = \"no-model-file.prism\";\n\t\t\t\t\t\timportResultsFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// override model type to dtmc\n\t\t\t\telse if (sw.equals(\"dtmc\")) {\n\t\t\t\t\ttypeOverride = ModelType.DTMC;\n\t\t\t\t}\n\t\t\t\t// override model type to mdp\n\t\t\t\telse if (sw.equals(\"mdp\")) {\n\t\t\t\t\ttypeOverride = ModelType.MDP;\n\t\t\t\t}\n\t\t\t\t// override model type to ctmc\n\t\t\t\telse if (sw.equals(\"ctmc\")) {\n\t\t\t\t\ttypeOverride = ModelType.CTMC;\n\t\t\t\t}\n\n\t\t\t\t// EXPORT OPTIONS:\n\n\t\t\t\t// export prism model to file\n\t\t\t\telse if (sw.equals(\"exportprism\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportprism = true;\n\t\t\t\t\t\texportPrismFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export prism model to file (with consts expanded)\n\t\t\t\telse if (sw.equals(\"exportprismconst\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportprismconst = true;\n\t\t\t\t\t\texportPrismConstFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export results\n\t\t\t\telse if (sw.equals(\"exportresults\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportresults = true;\n\t\t\t\t\t\t// Parse filename/options\n\t\t\t\t\t\ts = args[++i];\n\t\t\t\t\t\t// Assume use of : to split filename/options but check for , if : not found\n\t\t\t\t\t\t// (this was the old notation)\n\t\t\t\t\t\tString halves[] = splitFilesAndOptions(s);\n\t\t\t\t\t\tif (halves[1].length() == 0 && halves[0].indexOf(',') > -1) {\n\t\t\t\t\t\t\tint comma = halves[0].indexOf(',');\n\t\t\t\t\t\t\thalves[1] = halves[0].substring(comma + 1);\n\t\t\t\t\t\t\thalves[0] = halves[0].substring(0, comma);\n\t\t\t\t\t\t}\n\t\t\t\t\t\texportResultsFilename = halves[0];\n\t\t\t\t\t\tString ss[] = halves[1].split(\",\");\n\t\t\t\t\t\texportShape = ResultsExportShape.LIST_PLAIN;\n\t\t\t\t\t\tfor (j = 0; j < ss.length; j++) {\n\t\t\t\t\t\t\tif (ss[j].equals(\"\")) {\n\t\t\t\t\t\t\t} else if (ss[j].equals(\"csv\"))\n\t\t\t\t\t\t\t\texportShape = exportShape.isMatrix ? ResultsExportShape.MATRIX_CSV : ResultsExportShape.LIST_CSV;\n\t\t\t\t\t\t\telse if (ss[j].equals(\"matrix\"))\n\t\t\t\t\t\t\t\tswitch (exportShape) {\n\t\t\t\t\t\t\t\tcase LIST_PLAIN:\n\t\t\t\t\t\t\t\t\texportShape = ResultsExportShape.MATRIX_PLAIN;\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\tcase LIST_CSV:\n\t\t\t\t\t\t\t\t\texportShape = ResultsExportShape.MATRIX_CSV;\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t\t\t\t// switch does not apply\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\telse if (ss[j].equals(\"dataframe\"))\n\t\t\t\t\t\t\t\texportShape = ResultsExportShape.DATA_FRAME;\n\t\t\t\t\t\t\telse if (ss[j].equals(\"comment\"))\n\t\t\t\t\t\t\t\texportShape = ResultsExportShape.COMMENT;\n\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\terrorAndExit(\"Unknown option \\\"\" + ss[j] + \"\\\" for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file/options specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export vector of results\n\t\t\t\telse if (sw.equals(\"exportvector\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportvector = true;\n\t\t\t\t\t\texportVectorFilename = args[++i];\n\t\t\t\t\t\tprism.setStoreVector(true);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export model to explicit file(s)\n\t\t\t\telse if (sw.equals(\"exportmodel\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprocessExportModelSwitch(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file/options specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// process -exportmodelprecision in PrismSettings\n\t\t\t\t// export transition matrix to file\n\t\t\t\telse if (sw.equals(\"exporttrans\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.MODEL, args[++i]));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export state rewards to file\n\t\t\t\telse if (sw.equals(\"exportstaterewards\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.STATE_REWARDS, args[++i]));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export transition rewards to file\n\t\t\t\telse if (sw.equals(\"exporttransrewards\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.TRANSITION_REWARDS, args[++i]));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export both state/transition rewards to file\n\t\t\t\telse if (sw.equals(\"exportrewards\")) {\n\t\t\t\t\tif (i < args.length - 2) {\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.STATE_REWARDS, args[++i]));\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.TRANSITION_REWARDS, args[++i]));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"Two files must be specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export states\n\t\t\t\telse if (sw.equals(\"exportstates\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.STATES, args[++i]));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export observations\n\t\t\t\telse if (sw.equals(\"exportobs\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.OBSERVATIONS, args[++i]));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export labels/states\n\t\t\t\telse if (sw.equals(\"exportlabels\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprocessExportLabelsSwitch(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export labels/states from properties file\n\t\t\t\telse if (sw.equals(\"exportproplabels\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprocessExportPropLabelsSwitch(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// switch export mode to \"matlab\"\n\t\t\t\telse if (sw.equals(\"exportmatlab\")) {\n\t\t\t\t\texportType = Prism.EXPORT_MATLAB;\n\t\t\t\t\tmodelExportOptionsGlobal.setFormat(ModelExportFormat.MATLAB);\n\t\t\t\t}\n\t\t\t\t// switch export mode to \"mrmc\"\n\t\t\t\telse if (sw.equals(\"exportmrmc\")) {\n\t\t\t\t\terrorAndExit(\"Export to MRMC format no longer supported\");\n\t\t\t\t}\n\t\t\t\t// switch export mode to \"rows\"\n\t\t\t\telse if (sw.equals(\"exportrows\")) {\n\t\t\t\t\texportType = Prism.EXPORT_ROWS;\n\t\t\t\t\tmodelExportOptionsGlobal.setExplicitRows(true);\n\t\t\t\t}\n\t\t\t\t// exported matrix entries are ordered\n\t\t\t\telse if (sw.equals(\"exportordered\") || sw.equals(\"ordered\")) {\n\t\t\t\t\t// this is always done now, so ignore\n\t\t\t\t}\n\t\t\t\t// exported matrix entries are unordered\n\t\t\t\telse if (sw.equals(\"exportunordered\") || sw.equals(\"unordered\")) {\n\t\t\t\t\terrorAndExit(\"Switch -\" + sw + \" is no longer supported\");\n\t\t\t\t}\n\t\t\t\t// export transition matrix graph to dot file\n\t\t\t\telse if (sw.equals(\"exporttransdot\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions().setFormat(ModelExportFormat.DOT).setShowStates(false).setShowObservations(false);\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.MODEL, args[++i], exportOptions));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export transition matrix graph to dot file (with states)\n\t\t\t\telse if (sw.equals(\"exporttransdotstates\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions().setFormat(ModelExportFormat.DOT).setShowStates(true).setShowObservations(true);\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.MODEL, args[++i], exportOptions));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export transition matrix MTBDD to dot file\n\t\t\t\telse if (sw.equals(\"exportdot\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions().setFormat(ModelExportFormat.DD_DOT);\n\t\t\t\t\t\tmodelExportTasks.add(new ModelExportTask(ModelExportTask.ModelExportEntity.MODEL, args[++i], exportOptions));\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export sccs to file\n\t\t\t\telse if (sw.equals(\"exportsccs\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportsccs = true;\n\t\t\t\t\t\texportSCCsFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export bsccs to file\n\t\t\t\telse if (sw.equals(\"exportbsccs\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportbsccs = true;\n\t\t\t\t\t\texportBSCCsFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export mecs to file\n\t\t\t\telse if (sw.equals(\"exportmecs\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportmecs = true;\n\t\t\t\t\t\texportMECsFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export steady-state probs (as opposed to displaying on screen) \n\t\t\t\telse if (sw.equals(\"exportsteadystate\") || sw.equals(\"exportss\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportSteadyStateFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t\t// if we are asked to export the steady-state probs, we should compute them\n\t\t\t\t\tsteadystate = true;\n\t\t\t\t}\n\t\t\t\t// export transient probs (as opposed to displaying on screen) \n\t\t\t\telse if (sw.equals(\"exporttransient\") || sw.equals(\"exporttr\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\texportTransientFilename = args[++i];\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export strategy\n\t\t\t\telse if (sw.equals(\"exportstrat\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprocessExportStratSwitch(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file/options specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export digital clocks translation prism model to file\n\t\t\t\telse if (sw.equals(\"exportdigital\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tString filename = args[++i];\n\t\t\t\t\t\tFile f = (filename.equals(\"stdout\")) ? null : new File(filename);\n\t\t\t\t\t\tprism.setExportDigital(true);\n\t\t\t\t\t\tprism.setExportDigitalFile(f);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export reachability target info to file (hidden option)\n\t\t\t\telse if (sw.equals(\"exporttarget\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprism.setExportTarget(true);\n\t\t\t\t\t\tprism.setExportTargetFilename(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export product transition matrix to file (hidden option)\n\t\t\t\telse if (sw.equals(\"exportprodtrans\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprism.setExportProductTrans(true);\n\t\t\t\t\t\tprism.setExportProductTransFilename(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export product states to file (hidden option)\n\t\t\t\telse if (sw.equals(\"exportprodstates\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprism.setExportProductStates(true);\n\t\t\t\t\t\tprism.setExportProductStatesFilename(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export product vector to file (hidden option)\n\t\t\t\telse if (sw.equals(\"exportprodvector\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tprism.setExportProductVector(true);\n\t\t\t\t\t\tprism.setExportProductVectorFilename(args[++i]);\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// NB: Following the ordering of the -help text, more options go here,\n\t\t\t\t// but these are processed in the PrismSettings class; see below \n\n\t\t\t\t// SIMULATION OPTIONS:\n\n\t\t\t\t// use simulator for approximate/statistical model checking\n\t\t\t\telse if (sw.equals(\"sim\")) {\n\t\t\t\t\tsimulate = true;\n\t\t\t\t}\n\t\t\t\t// simulation-based model checking methods\n\t\t\t\telse if (sw.equals(\"simmethod\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\ts = args[++i];\n\t\t\t\t\t\tif (s.equals(\"ci\") || s.equals(\"aci\") || s.equals(\"apmc\") || s.equals(\"sprt\"))\n\t\t\t\t\t\t\tsimMethodName = s;\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\terrorAndExit(\"Unrecognised option for -\" + sw + \" switch (options are: ci, aci, apmc, sprt)\");\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No parameter specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// simulation number of samples\n\t\t\t\telse if (sw.equals(\"simsamples\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tsimNumSamples = Integer.parseInt(args[++i]);\n\t\t\t\t\t\t\tif (simNumSamples <= 0)\n\t\t\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\t\t\tsimNumSamplesGiven = true;\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// simulation confidence parameter\n\t\t\t\telse if (sw.equals(\"simconf\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tsimConfidence = Double.parseDouble(args[++i]);\n\t\t\t\t\t\t\tif (simConfidence <= 0 || simConfidence >= 1)\n\t\t\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\t\t\tsimConfidenceGiven = true;\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// simulation confidence interval width\n\t\t\t\telse if (sw.equals(\"simwidth\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tsimWidth = Double.parseDouble(args[++i]);\n\t\t\t\t\t\t\tif (simWidth <= 0)\n\t\t\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\t\t\tsimWidthGiven = true;\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// simulation approximation parameter\n\t\t\t\telse if (sw.equals(\"simapprox\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tsimApprox = Double.parseDouble(args[++i]);\n\t\t\t\t\t\t\tif (simApprox <= 0)\n\t\t\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\t\t\tsimApproxGiven = true;\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// use the number of iterations given instead of automatically deciding whether the variance is null ot not\n\t\t\t\telse if (sw.equals(\"simmanual\")) {\n\t\t\t\t\tsimManual = true;\n\t\t\t\t}\n\t\t\t\t// simulation number of samples to conclude S^2=0 or not\n\t\t\t\telse if (sw.equals(\"simvar\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\treqIterToConclude = Integer.parseInt(args[++i]);\n\t\t\t\t\t\t\tif (reqIterToConclude <= 0)\n\t\t\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\t\t\treqIterToConcludeGiven = true;\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// maximum value of reward\n\t\t\t\telse if (sw.equals(\"simmaxrwd\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tsimMaxReward = Double.parseDouble(args[++i]);\n\t\t\t\t\t\t\tif (simMaxReward <= 0.0)\n\t\t\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\t\t\tsimMaxRewardGiven = true;\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// simulation max path length\n\t\t\t\telse if (sw.equals(\"simpathlen\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tsimMaxPath = Long.parseLong(args[++i]);\n\t\t\t\t\t\t\tif (simMaxPath <= 0)\n\t\t\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\t\t\tsimMaxPathGiven = true;\n\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\terrorAndExit(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// FURTHER OPTIONS - NEED TIDYING/FIXING\n\n\t\t\t\t// zero-reward loops check on\n\t\t\t\telse if (sw.equals(\"zerorewardcheck\")) {\n\t\t\t\t\tprism.setCheckZeroLoops(true);\n\t\t\t\t}\n\t\t\t\t// explicit-state model construction\n\t\t\t\telse if (sw.equals(\"explicitbuild\")) {\n\t\t\t\t\texplicitbuild = true;\n\t\t\t\t}\n\t\t\t\t// (hidden) option for testing of prototypical explicit-state model construction\n\t\t\t\telse if (sw.equals(\"explicitbuildtest\")) {\n\t\t\t\t\texplicitbuildtest = true;\n\t\t\t\t}\n\n\t\t\t\t// MISCELLANEOUS UNDOCUMENTED/UNUSED OPTIONS:\n\n\t\t\t\t// specify main log (hidden option)\n\t\t\t\telse if (sw.equals(\"mainlog\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tmainLogFilename = args[++i];\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t// use temporary storage because an error would go to the old log\n\t\t\t\t\t\t\tlog = new PrismFileLog(mainLogFilename);\n\t\t\t\t\t\t\tmainLog = log;\n\t\t\t\t\t\t\tprism.setMainLog(mainLog);\n\t\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t\terrorAndExit(\"Couldn't open log file \\\"\" + mainLogFilename + \"\\\"\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\terrorAndExit(\"No file specified for -\" + sw + \" switch\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// export transition matrix graph to dot file and view it (hidden option, for now)\n\t\t\t\telse if (sw.equals(\"exportmodeldotview\")) {\n\t\t\t\t\texportmodeldotview = true;\n\t\t\t\t}\n\t\t\t\t// mtbdd construction method (hidden option)\n\t\t\t\telse if (sw.equals(\"c1\")) {\n\t\t\t\t\tprism.setConstruction(1);\n\t\t\t\t} else if (sw.equals(\"c2\")) {\n\t\t\t\t\tprism.setConstruction(2);\n\t\t\t\t} else if (sw.equals(\"c3\")) {\n\t\t\t\t\tprism.setConstruction(3);\n\t\t\t\t}\n\t\t\t\t// mtbdd variable ordering (hidden option)\n\t\t\t\telse if (sw.equals(\"o1\")) {\n\t\t\t\t\tprism.setOrdering(1);\n\t\t\t\t\torderingOverride = true;\n\t\t\t\t} else if (sw.equals(\"o2\")) {\n\t\t\t\t} else if (sw.equals(\"o2\")) {\n\t\t\t\t\tprism.setOrdering(2);\n\t\t\t\t\torderingOverride = true;\n\t\t\t\t} else if (sw.equals(\"o2\")) {\n\t\t\t\t}\n\t\t\t\t// reachability off (hidden option)\n\t\t\t\telse if (sw.equals(\"noreach\")) {\n\t\t\t\t\tprism.setDoReach(false);\n\t\t\t\t}\n\t\t\t\t// no bscc computation (hidden option)\n\t\t\t\telse if (sw.equals(\"nobscc\")) {\n\t\t\t\t\tprism.setBSCCComp(false);\n\t\t\t\t}\n\t\t\t\t// reachability options (hidden options)\n\t\t\t\telse if (sw.equals(\"frontier\")) {\n\t\t\t\t\tprism.setReachMethod(Prism.REACH_FRONTIER);\n\t\t\t\t} else if (sw.equals(\"bfs\")) {\n\t\t\t\t\tprism.setReachMethod(Prism.REACH_BFS);\n\t\t\t\t}\n\t\t\t\t// enable bisimulation minimisation before model checking (hidden option)\n\t\t\t\telse if (sw.equals(\"bisim\")) {\n\t\t\t\t\tprism.setDoBisim(true);\n\t\t\t\t}\n\n\t\t\t\t// Other switches - pass to PrismSettings\n\n\t\t\t\telse {\n\t\t\t\t\ti = prism.getSettings().setFromCommandLineSwitch(args, i) - 1;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// otherwise argument is assumed to be a (model/properties) filename\n\t\t\telse {\n\t\t\t\tfilenameArgs.add(args[i]);\n\t\t\t}\n\t\t}\n\n\t\tprocessFileNames(filenameArgs);\n\t}\n\n\t/**\n\t * Process the non-switch command-line arguments,\n\t * which should be (model/properties) file names.\n\t */\n\tprivate void processFileNames(List<String> filenameArgs) throws PrismException\n\t{\n\t\tif (filenameArgs.size() > 2) {\n\t\t\terrorAndExit(\"Invalid argument syntax\");\n\t\t}\n\t\tif (!modelImportSources.isEmpty()) {\n\t\t\tif (filenameArgs.size() > 1) {\n\t\t\t\terrorAndExit(\"Two models provided (\" + filenameArgs.get(0) + \", \" + modelFilename + \")\");\n\t\t\t} else if (filenameArgs.size() == 1) {\n\t\t\t\tpropertiesFilename = filenameArgs.get(0);\n\t\t\t}\n\t\t} else {\n\t\t\tif (filenameArgs.size() > 0) {\n\t\t\t\tmodelFilename = filenameArgs.get(0);\n\t\t\t\tif (modelFilename.endsWith(\".all\")) {\n\t\t\t\t\tprocessImportModelSwitch(modelFilename);\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (filenameArgs.size() > 1) {\n\t\t\t\tpropertiesFilename = filenameArgs.get(1);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Process the arguments (files, options) to the -importmodel switch\n\t * NB: This is done at the time of parsing switches (not later)\n\t * because other individual switches (e.g. -importXXX) can later override\n\t * parts of the configurations set up here.\n\t */\n\tprivate void processImportModelSwitch(String filesOptionsString) throws PrismException\n\t{\n\t\t// Split into files/options (on :)\n\t\tString halves[] = splitFilesAndOptions(filesOptionsString);\n\t\tString filesString = halves[0];\n\t\tString optionsString = halves[1];\n\t\t// Split files into basename/extensions\n\t\tint i = filesString.lastIndexOf('.');\n\t\tString basename = i == -1 ? filesString : filesString.substring(0, i);\n\t\tString extList = i == -1 ? \"\" : filesString.substring(i + 1);\n\t\tString exts[] = extList.split(\",\");\n\t\t// Process file extensions\n\t\timportModelWarning = null;\n\t\tfor (String ext : exts) {\n\t\t\t// Items to import\n\t\t\tif (ext.equals(\"all\")) {\n\t\t\t\tmodelFilename = basename + \".tra\";\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.MODEL,basename + \".tra\", false);\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.STATES,basename + \".sta\", false);\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.OBSERVATIONS,basename + \".obs\", false);\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.LABELS,basename + \".lab\", false);\n\t\t\t\taddStateRewardImports(basename, false);\n\t\t\t\taddTransitionRewardImports(basename, false);\n\t\t\t} else if (ext.equals(\"tra\")) {\n\t\t\t\tmodelFilename = basename + \".tra\";\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.MODEL,basename + \".tra\", true);\n\t\t\t} else if (ext.equals(\"sta\")) {\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.STATES,basename + \".sta\", true);\n\t\t\t} else if (ext.equals(\"obs\")) {\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.OBSERVATIONS,basename + \".obs\", true);\n\t\t\t} else if (ext.equals(\"lab\")) {\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.LABELS,basename + \".lab\", true);\n\t\t\t} else if (ext.equals(\"srew\")) {\n\t\t\t\taddStateRewardImports(basename, true);\n\t\t\t} else if (ext.equals(\"trew\")) {\n\t\t\t\taddTransitionRewardImports(basename, true);\n\t\t\t} else if (ext.equals(\"umb\")) {\n\t\t\t\tmodelFilename = basename + \".umb\";;\n\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.MODEL, ModelExportFormat.UMB, new File(basename + \".umb\")));\n\t\t\t}\n\t\t\t// For any other extension (including none/unknown), default to explicit (.tra)\n\t\t\telse {\n\t\t\t\tmodelFilename = basename + (ext.isEmpty() ? \"\" : \".\" + ext);\n\t\t\t\taddModelImport(ModelExportTask.ModelExportEntity.MODEL,modelFilename, true);\n\t\t\t}\n\t\t}\n\t\t// Process options\n\t\tString options[] = optionsString.split(\",\");\n\t\tfor (String opt : options) {\n\t\t\t// Ignore \"\"\n\t\t\tif (opt.equals(\"\")) {\n\t\t\t}\n\t\t\t// Import format\n\t\t\telse if (opt.startsWith(\"format\")) {\n\t\t\t\tif (!opt.startsWith(\"format=\")) {\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"format\\\" option of -importmodel\");\n\t\t\t\t}\n\t\t\t\tString optVal = opt.substring(7);\n\t\t\t\tModelExportFormat importFormat = null;\n\t\t\t\tswitch (optVal) {\n\t\t\t\t\tcase \"explicit\":\n\t\t\t\t\t\timportFormat = ModelExportFormat.EXPLICIT;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase \"umb\":\n\t\t\t\t\t\timportFormat = ModelExportFormat.UMB;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"format\\\" option of -importmodel\");\n\t\t\t\t}\n\t\t\t\t// Apply format to the import sources\n\t\t\t\tfor (ModelImportSource source : modelImportSources) {\n\t\t\t\t\tsource.format = importFormat;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Unknown option\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Unknown option \\\"\" + opt + \"\\\" for -importmodel switch\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Add a model import file to {@code modelImportSources}.\n\t * @param entity Model entity\n\t * @param filename Model import filename\n\t * @param assumeExists If true, we add the file even if it does not exist\n\t */\n\tprivate void addModelImport(ModelExportTask.ModelExportEntity entity, String filename, boolean assumeExists)\n\t{\n\t\tif (assumeExists || new File(filename).exists()) {\n\t\t\tmodelImportSources.add(new ModelImportSource(entity, ModelExportFormat.EXPLICIT, new File(filename)));\n\t\t}\n\t}\n\n\t/**\n\t * Given a file basename, find corresponding .srew files\n\t * and add them to {@code modelImportSources}.\n\t * \"corresponding\" means basename.srew, or a set basename1.srew, ...\n\t * If any are present, {@code importstaterewards} is set to true.\n\t * \n\t * If {@code assumeExists} is true, then we add basename.srew regardless,\n\t * typically because the user has told us it should be there.\n\t */\n\tprivate void addStateRewardImports(String basename, boolean assumeExists)\n\t{\n\t\tboolean found = false;\n\t\tif (new File(basename + \".srew\").exists()) {\n\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.STATE_REWARDS, ModelExportFormat.EXPLICIT, new File(basename + \".srew\")));\n\t\t\tfound = true;\n\t\t} else {\n\t\t\tint index = 1;\n\t\t\twhile (true) {\n\t\t\t\tif (new File(basename + String.valueOf(index) + \".srew\").exists()) {\n\t\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.STATE_REWARDS, ModelExportFormat.EXPLICIT, new File(basename + String.valueOf(index) + \".srew\")));\n\t\t\t\t\tfound = true;\n\t\t\t\t\tindex++;\n\t\t\t\t} else {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (assumeExists && !found) {\n\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.STATE_REWARDS, ModelExportFormat.EXPLICIT, new File(basename + \".srew\")));\n\t\t}\n\t}\n\n\t/**\n\t * Given a file basename, find corresponding .trew files\n\t * and add them to {@code modelImportSources}.\n\t * \"corresponding\" means basename.srew, or a set basename1.srew, ...\n\t * If any are present, {@code importtransrewards} is set to true.\n\t *\n\t * If {@code assumeExists} is true, then we add basename.srew regardless,\n\t * typically because the user has told us it should be there.\n\t */\n\tprivate void addTransitionRewardImports(String basename, boolean assumeExists)\n\t{\n\t\tboolean found = false;\n\t\tif (new File(basename + \".trew\").exists()) {\n\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.TRANSITION_REWARDS, ModelExportFormat.EXPLICIT, new File(basename + \".trew\")));\n\t\t\tfound = true;\n\t\t} else {\n\t\t\tint index = 1;\n\t\t\twhile (true) {\n\t\t\t\tif (new File(basename + String.valueOf(index) + \".trew\").exists()) {\n\t\t\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.TRANSITION_REWARDS, ModelExportFormat.EXPLICIT, new File(basename + String.valueOf(index) + \".trew\")));\n\t\t\t\t\tfound = true;\n\t\t\t\t\tindex++;\n\t\t\t\t} else {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (assumeExists && !found) {\n\t\t\tmodelImportSources.add(new ModelImportSource(ModelExportTask.ModelExportEntity.TRANSITION_REWARDS, ModelExportFormat.EXPLICIT, new File(basename + \".trew\")));\n\t\t}\n\t}\n\n\t/**\n\t * Process the arguments (file, options) to the -exportlabels switch.\n\t */\n\tprivate void processExportLabelsSwitch(String filesOptionsString) throws PrismException\n\t{\n\t\t// Split into files/options (on :)\n\t\tString pair[] = splitFilesAndOptions(filesOptionsString);\n\t\tModelExportTask newExportTask = new ModelExportTask(ModelExportTask.ModelExportEntity.LABELS, pair[0]);\n\t\tString options[] = pair[1].split(\",\");\n\t\tfor (String opt : options) {\n\t\t\t// Ignore \"\"\n\t\t\tif (opt.equals(\"\")) {\n\t\t\t}\n\t\t\t// Export type\n\t\t\telse if (opt.equals(\"matlab\")) {\n\t\t\t\tnewExportTask.getExportOptions().setFormat(ModelExportFormat.MATLAB);\n\t\t\t} else if (opt.equals(\"proplabels\")) {\n\t\t\t\tnewExportTask.setLabelExportSet(ModelExportTask.LabelExportSet.ALL);\n\t\t\t}\n\t\t\t// Unknown option\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Unknown option \\\"\" + opt + \"\\\" for -exportlabels switch\");\n\t\t\t}\n\t\t}\n\t\tmodelExportTasks.add(newExportTask);\n\t}\n\n\t/**\n\t * Process the arguments (file, options) to the -exportproplabels switch.\n\t */\n\tprivate void processExportPropLabelsSwitch(String filesOptionsString) throws PrismException\n\t{\n\t\t// Split into files/options (on :)\n\t\tString pair[] = splitFilesAndOptions(filesOptionsString);\n\t\tModelExportTask newExportTask = new ModelExportTask(ModelExportTask.ModelExportEntity.LABELS, pair[0]);\n\t\tnewExportTask.setLabelExportSet(ModelExportTask.LabelExportSet.EXTRA);\n\t\tString options[] = pair[1].split(\",\");\n\t\tfor (String opt : options) {\n\t\t\t// Ignore \"\"\n\t\t\tif (opt.equals(\"\")) {\n\t\t\t}\n\t\t\t// Export type\n\t\t\telse if (opt.equals(\"matlab\")) {\n\t\t\t\tnewExportTask.getExportOptions().setFormat(ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t\t// Unknown option\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Unknown option \\\"\" + opt + \"\\\" for -exportproplabels switch\");\n\t\t\t}\n\t\t}\n\t\tmodelExportTasks.add(newExportTask);\n\t}\n\n\t/**\n\t * Process the arguments (files, options) to the -exportmodel switch\n\t * NB: This is done at the time of parsing switches (not later)\n\t * because other individual switches (e.g. -exportmatlab) can later override\n\t * parts of the configurations set up here.\n\t */\n\tprivate void processExportModelSwitch(String filesOptionsString) throws PrismException\n\t{\n\t\t// Split into files/options (on :)\n\t\tString halves[] = splitFilesAndOptions(filesOptionsString);\n\t\tString filesString = halves[0];\n\t\tString optionsString = halves[1];\n\t\t// Split files into basename/extensions\n\t\tint i = filesString.lastIndexOf('.');\n\t\tString basename = i == -1 ? filesString : filesString.substring(0, i);\n\t\tString extList = i == -1 ? \"\" : filesString.substring(i + 1);\n\t\tString exts[] = extList.split(\",\");\n\t\t// Process file extensions\n\t\tList<ModelExportTask> newModelExportTasks = new ArrayList<>();\n\t\tfor (String ext : exts) {\n\t\t\t// Some extensions get expanded to multiple exports\n\t\t\tif (ext.equals(\"all\")) {\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, \"tra\"));\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, \"srew\"));\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, \"trew\"));\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, \"sta\"));\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, \"obs\"));\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, \"lab\"));\n\t\t\t} else if (ext.equals(\"rew\")) {\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, \"srew\"));\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, \"trew\"));\n\t\t\t}\n\t\t\t// For any other extension (including none/unknown), deduce export\n\t\t\telse {\n\t\t\t\tnewModelExportTasks.add(ModelExportTask.fromFilename(basename, ext));\n\t\t\t}\n\t\t}\n\t\t// Process options\n\t\tModelExportOptions exportOptions = new ModelExportOptions();\n\t\tString options[] = optionsString.split(\",\");\n\t\tfor (String opt : options) {\n\t\t\tString sOpt;\n\t\t\t// Ignore \"\"\n\t\t\tif (opt.equals(\"\")) {\n\t\t\t}\n\t\t\t// Export format\n\t\t\telse if (opt.startsWith(\"format\")) {\n\t\t\t\tif (!opt.startsWith(\"format=\")) {\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"format\\\" option of -exportmodel\");\n\t\t\t\t}\n\t\t\t\tString optVal = opt.substring(7);\n\t\t\t\tswitch (optVal) {\n\t\t\t\t\tcase \"explicit\":\n\t\t\t\t\t\texportOptions.setFormat(ModelExportFormat.EXPLICIT);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase \"matlab\":\n\t\t\t\t\t\texportOptions.setFormat(ModelExportFormat.MATLAB);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase \"dot\":\n\t\t\t\t\t\texportOptions.setFormat(ModelExportFormat.DOT);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase \"drn\":\n\t\t\t\t\t\texportOptions.setFormat(ModelExportFormat.DRN);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase \"umb\":\n\t\t\t\t\t\texportOptions.setFormat(ModelExportFormat.UMB);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"format\\\" option of -exportmodel\");\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Export type\n\t\t\telse if (opt.equals(\"matlab\")) {\n\t\t\t\texportOptions.setFormat(ModelExportFormat.MATLAB);\n\t\t\t\texportType = Prism.EXPORT_MATLAB;\n\t\t\t} else if (opt.equals(\"rows\")) {\n\t\t\t\texportOptions.setExplicitRows(true);\n\t\t\t\texportType = Prism.EXPORT_ROWS;\n\t\t\t} else if (opt.equals(\"text\")) {\n\t\t\t\texportOptions.setBinaryAsText(true);\n\t\t\t}\n\t\t\telse if (opt.equals(\"proplabels\")) {\n\t\t\t\tfor (ModelExportTask exportTask : newModelExportTasks) {\n\t\t\t\t\tif (exportTask.getEntity() == ModelExportTask.ModelExportEntity.LABELS) {\n\t\t\t\t\t\texportTask.setLabelExportSet(ModelExportTask.LabelExportSet.ALL);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\telse if (opt.startsWith(sOpt = \"labels\")) {\n\t\t\t\tif (!opt.startsWith(sOpt + \"=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\tString optVal = opt.substring(sOpt.length() + 1);\n\t\t\t\tif (optVal.equals(\"true\"))\n\t\t\t\t\texportOptions.setShowLabels(true);\n\t\t\t\telse if (optVal.equals(\"false\"))\n\t\t\t\t\texportOptions.setShowLabels(false);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t}\n\t\t\telse if (opt.startsWith(sOpt = \"rewards\")) {\n\t\t\t\tif (!opt.startsWith(sOpt + \"=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\tString optVal = opt.substring(sOpt.length() + 1);\n\t\t\t\tif (optVal.equals(\"true\"))\n\t\t\t\t\texportOptions.setShowRewards(true);\n\t\t\t\telse if (optVal.equals(\"false\"))\n\t\t\t\t\texportOptions.setShowRewards(false);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t}\n\t\t\telse if (opt.startsWith(sOpt = \"states\")) {\n\t\t\t\tif (!opt.startsWith(sOpt + \"=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\tString optVal = opt.substring(sOpt.length() + 1);\n\t\t\t\tif (optVal.equals(\"true\"))\n\t\t\t\t\texportOptions.setShowStates(true);\n\t\t\t\telse if (optVal.equals(\"false\"))\n\t\t\t\t\texportOptions.setShowStates(false);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t}\n\t\t\telse if (opt.startsWith(sOpt = \"obs\")) {\n\t\t\t\tif (!opt.startsWith(sOpt + \"=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\tString optVal = opt.substring(sOpt.length() + 1);\n\t\t\t\tif (optVal.equals(\"true\"))\n\t\t\t\t\texportOptions.setShowObservations(true);\n\t\t\t\telse if (optVal.equals(\"false\"))\n\t\t\t\t\texportOptions.setShowObservations(false);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t}\n\t\t\telse if (opt.startsWith(sOpt = \"actions\")) {\n\t\t\t\tif (!opt.startsWith(sOpt + \"=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\tString optVal = opt.substring(sOpt.length() + 1);\n\t\t\t\tif (optVal.equals(\"true\")) {\n\t\t\t\t\texportOptions.setShowActions(true);\n\t\t\t\t} else if (optVal.equals(\"false\")) {\n\t\t\t\t\texportOptions.setShowActions(false);\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\t}\n\t\t\t}\n\t\t\telse if (opt.startsWith(sOpt = \"headers\")) {\n\t\t\t\tif (!opt.startsWith(sOpt + \"=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\tString optVal = opt.substring(sOpt.length() + 1);\n\t\t\t\tif (optVal.equals(\"true\")) {\n\t\t\t\t\texportOptions.setPrintHeaders(true);\n\t\t\t\t} else if (optVal.equals(\"false\")) {\n\t\t\t\t\texportOptions.setPrintHeaders(false);\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\t}\n\t\t\t}\n\t\t\telse if (opt.startsWith(sOpt = \"precision\")) {\n\t\t\t\tif (!opt.startsWith(sOpt + \"=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\tString optVal = opt.substring(sOpt.length() + 1);\n\t\t\t\ttry {\n\t\t\t\t\tint precision = Integer.parseInt(optVal);\n\t\t\t\t\tif (!RANGE_EXPORT_DOUBLE_PRECISION.contains(precision)) {\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\t}\n\t\t\t\t\texportOptions.setModelPrecision(precision);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value \\\"\" + optVal + \"\\\" provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\t}\n\t\t\t}\n\t\t\telse if (opt.startsWith(sOpt = \"zip\")) {\n\t\t\t\tif (!opt.startsWith(sOpt + \"=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\tString optVal = opt.substring(sOpt.length() + 1);\n\t\t\t\tif (optVal.equals(\"true\")) {\n\t\t\t\t\texportOptions.setZipped(true);\n\t\t\t\t} else if (optVal.equals(\"false\")) {\n\t\t\t\t\texportOptions.setZipped(false);\n\t\t\t\t} else if (optVal.equals(\"gzip\") || optVal.equals(\"gz\")) {\n\t\t\t\t\texportOptions.setZipped(true).setCompressionFormat(ModelExportOptions.CompressionFormat.GZIP);\n\t\t\t\t} else if (optVal.equals(\"xz\")) {\n\t\t\t\t\texportOptions.setZipped(true).setCompressionFormat(ModelExportOptions.CompressionFormat.XZ);\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"\" + sOpt + \"\\\" option of -exportmodel\");\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Unknown option\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Unknown option \\\"\" + opt + \"\\\" for -exportmodel switch\");\n\t\t\t}\n\t\t}\n\t\t// Apply options from this switch to each export task\n\t\tfor (ModelExportTask exportTask : newModelExportTasks) {\n\t\t\texportTask.getExportOptions().apply(exportOptions);\n\t\t}\n\t\t// Add export tasks to the main list\n\t\tmodelExportTasks.addAll(newModelExportTasks);\n\t}\n\n\t/**\n\t * Process the arguments (files, options) to the -exportstrat switch\n\t */\n\tprivate void processExportStratSwitch(String filesOptionsString) throws PrismException\n\t{\n\t\t// Split into files/options (on :)\n\t\tString halves[] = splitFilesAndOptions(filesOptionsString);\n\t\tString fileString = halves[0];\n\t\tString optionsString = halves[1];\n\t\t// Split file into basename/extension\n\t\tint i = fileString.lastIndexOf('.');\n\t\tString basename = i == -1 ? fileString : fileString.substring(0, i);\n\t\tString ext = i == -1 ? \"\" : fileString.substring(i + 1);\n\t\t// Store some settings (here and in PRISM)\n\t\texportstrat = true;\n\t\texportStratFilename = basename.equals(\"stdout\") ? \"stdout\" : fileString;\n\t\texportStratOptions = new StrategyExportOptions();\n\t\tprism.setGenStrat(true);\n\t\t// Default strategy export type is based on filename extension\n\t\tif (ext.equals(\"tra\")) {\n\t\t\texportStratOptions.setType(StrategyExportOptions.StrategyExportType.INDUCED_MODEL);\n\t\t} else if (ext.equals(\"dot\")) {\n\t\t\texportStratOptions.setType(StrategyExportOptions.StrategyExportType.DOT_FILE);\n\t\t} else {\n\t\t\texportStratOptions.setType(StrategyExportOptions.StrategyExportType.ACTIONS);\n\t\t}\n\t\t// Process options\n\t\tString options[] = optionsString.split(\",\");\n\t\tfor (String opt : options) {\n\t\t\t// Ignore \"\"\n\t\t\tif (opt.equals(\"\")) {\n\t\t\t}\n\t\t\telse if (opt.startsWith(\"type\")) {\n\t\t\t\tif (!opt.startsWith(\"type=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"type\\\" option of -exportstrat\");\n\t\t\t\tString optVal = opt.substring(5);\n\t\t\t\tif (optVal.equals(\"actions\"))\n\t\t\t\t\texportStratOptions.setType(StrategyExportOptions.StrategyExportType.ACTIONS);\n\t\t\t\telse if (optVal.equals(\"indices\"))\n\t\t\t\t\texportStratOptions.setType(StrategyExportOptions.StrategyExportType.INDICES);\n\t\t\t\telse if (optVal.equals(\"model\") || optVal.equals(\"induced\"))\n\t\t\t\t\texportStratOptions.setType(StrategyExportOptions.StrategyExportType.INDUCED_MODEL);\n\t\t\t\telse if (optVal.equals(\"dot\"))\n\t\t\t\t\texportStratOptions.setType(StrategyExportOptions.StrategyExportType.DOT_FILE);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"type\\\" option of -exportstrat\");\n\t\t\t}\n\t\t\telse if (opt.startsWith(\"mode\")) {\n\t\t\t\tif (!opt.startsWith(\"mode=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"mode\\\" option of -exportstrat\");\n\t\t\t\tString optVal = opt.substring(5);\n\t\t\t\tif (optVal.equals(\"restrict\"))\n\t\t\t\t\texportStratOptions.setMode(StrategyExportOptions.InducedModelMode.RESTRICT);\n\t\t\t\telse if (optVal.equals(\"reduce\"))\n\t\t\t\t\texportStratOptions.setMode(StrategyExportOptions.InducedModelMode.REDUCE);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"mode\\\" option of -exportstrat\");\n\t\t\t}\n\t\t\telse if (opt.startsWith(\"reach\")) {\n\t\t\t\tif (!opt.startsWith(\"reach=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"reach\\\" option of -exportstrat\");\n\t\t\t\tString optVal = opt.substring(6);\n\t\t\t\tif (optVal.equals(\"true\"))\n\t\t\t\t\texportStratOptions.setReachOnly(true);\n\t\t\t\telse if (optVal.equals(\"false\"))\n\t\t\t\t\texportStratOptions.setReachOnly(false);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"reach\\\" option of -exportstrat\");\n\t\t\t}\n\t\t\telse if (opt.startsWith(\"states\")) {\n\t\t\t\tif (!opt.startsWith(\"states=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"states\\\" option of -exportstrat\");\n\t\t\t\tString optVal = opt.substring(7);\n\t\t\t\tif (optVal.equals(\"true\"))\n\t\t\t\t\texportStratOptions.setShowStates(true);\n\t\t\t\telse if (optVal.equals(\"false\"))\n\t\t\t\t\texportStratOptions.setShowStates(false);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"reach\\\" option of -exportstrat\");\n\t\t\t}\n\t\t\telse if (opt.startsWith(\"obs\")) {\n\t\t\t\tif (!opt.startsWith(\"obs=\"))\n\t\t\t\t\tthrow new PrismException(\"No value provided for \\\"obs\\\" option of -exportstrat\");\n\t\t\t\tString optVal = opt.substring(4);\n\t\t\t\tif (optVal.equals(\"true\"))\n\t\t\t\t\texportStratOptions.setMergeObservations(true);\n\t\t\t\telse if (optVal.equals(\"false\"))\n\t\t\t\t\texportStratOptions.setMergeObservations(false);\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unknown value \\\"\" + optVal + \"\\\" provided for \\\"reach\\\" option of -exportstrat\");\n\t\t\t}\n\t\t\t// Unknown option\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Unknown option \\\"\" + opt + \"\\\" for -exportstrat switch\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Split a string of the form <files>:<options> into its two parts.\n\t * The latter can be empty, in which case the : is optional.\n\t * Instances of :\\ are ignored (not treated as :) in case there is a Windows filename.\n\t * @return the two parts as an array of two strings.\n\t */\n\tprivate static String[] splitFilesAndOptions(String filesOptionsString)\n\t{\n\t\tString res[] = new String[2];\n\t\t// Split into files/options (on :)\n\t\tint i = filesOptionsString.indexOf(':');\n\t\twhile (filesOptionsString.length() > i + 1 && filesOptionsString.charAt(i + 1) == '\\\\') {\n\t\t\ti = filesOptionsString.indexOf(':', i + 1);\n\t\t}\n\t\tif (i != -1) {\n\t\t\tres[0] = filesOptionsString.substring(0, i);\n\t\t\tres[1] = filesOptionsString.substring(i + 1);\n\t\t} else {\n\t\t\tres[0] = filesOptionsString;\n\t\t\tres[1] = \"\";\n\t\t}\n\t\treturn res;\n\t}\n\n\t// print command line arguments\n\n\tpublic void printArguments(String[] args)\n\t{\n\t\tString s;\n\t\tint i;\n\t\tmainLog.print(\"Command line: prism\");\n\t\t// Print out the command-line arguments\n\t\tfor (i = 0; i < args.length; i++) {\n\t\t\ts = args[i];\n\t\t\t// If necessary add quotes so can be pasted back into a shell\n\t\t\ts = shellQuoteSingleIfNecessary(s);\n\t\t\tmainLog.print(\" \" + s);\n\t\t}\n\t\tmainLog.println();\n\t}\n\n\t/**\n\t * For a command-line argument, returns a quoted version\n\t * with single quotes if it contains unsafe characters.\n\t * Otherwise, just returns the unquoted argument.\n\t */\n\tpublic static String shellQuoteSingleIfNecessary(String arg)\n\t{\n\t\tif (arg.isEmpty()) {\n\t\t\t// empty argument needs to be quoted\n\t\t\treturn \"''\";\n\t\t}\n\n\t\t// If necessary add quotes so can be pasted back into a shell\n\t\t// (where \"necessary\" means contains any non-safe characters)\n\t\tif (arg.matches(\".*[^_a-zA-Z0-9\\\\./\\\\-=].*\")) {\n\t\t\t// argument needs quoting, so we surround with single quotes,\n\t\t\t// which neutralises all characters except '\n\t\t\t// for that we have to have special handling, replacing ' by '\\''\n\t\t\t// (close quote, escaped-', open quote again)\n\t\t\targ = arg.replace(\"'\", \"'\\\\''\");\n\t\t\targ = \"'\" + arg + \"'\";\n\t\t}\n\t\treturn arg;\n\t}\n\n\t// do some processing of the options\n\n\tprivate void processOptions() throws PrismException\n\t{\n\t\tint j;\n\n\t\t// make sure a model file is specified\n\t\tif (modelFilename == null) {\n\t\t\tmainLog.println(\"Usage: \" + Prism.getCommandLineName() + \" [options] <model-file> [<properties-file>] [more-options]\");\n\t\t\tmainLog.println(\"\\nFor more information, type: prism -help\");\n\t\t\texit();\n\t\t}\n\n\t\t// default to alternative ordering for MTBDD engine\n\t\tif (prism.getEngine() == Prism.MTBDD && !orderingOverride) {\n\t\t\ttry {\n\t\t\t\tprism.setOrdering(2);\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// Can't go wrong\n\t\t\t}\n\t\t}\n\n\t\t// explicit overrides explicit build\n\t\tif (prism.getExplicit()) {\n\t\t\texplicitbuild = false;\n\t\t}\n\n\t\t// check not trying to do gauss-seidel with mtbdd engine\n\t\t// (if we are in test mode, we ignore here; will lead to appropriate 'not supported' error handling during testing)\n\t\tif (prism.getEngine() == Prism.MTBDD && !test) {\n\t\t\tj = prism.getLinEqMethod();\n\t\t\tif (j == Prism.GAUSSSEIDEL || j == Prism.BGAUSSSEIDEL || j == Prism.PGAUSSSEIDEL || j == Prism.BPGAUSSSEIDEL) {\n\t\t\t\terrorAndExit(\"Gauss-Seidel and its variants are currently not supported by the MTBDD engine\");\n\t\t\t}\n\t\t\tif (j == Prism.SOR || j == Prism.BSOR || j == Prism.PSOR || j == Prism.BPSOR) {\n\t\t\t\terrorAndExit(\"SOR and its variants are currently not supported by the MTBDD engine\");\n\t\t\t}\n\t\t}\n\n\t\t// or pseudo methods with sparse engine\n\t\t// (if we are in test mode, we ignore here; will lead to appropriate 'not supported' error handling during testing)\n\t\telse if (prism.getEngine() == Prism.SPARSE && !test) {\n\t\t\tj = prism.getLinEqMethod();\n\t\t\tif (j == Prism.PGAUSSSEIDEL || j == Prism.BPGAUSSSEIDEL || j == Prism.PSOR || j == Prism.BPSOR) {\n\t\t\t\terrorAndExit(\"Pseudo Gauss-Seidel/SOR methods are currently not supported by the sparse engine\");\n\t\t\t}\n\t\t}\n\n\t\t// process info about parametric constants\n\t\tif (param) {\n\t\t\tString[] paramDefs = paramSwitch.split(\",\");\n\t\t\tparamNames = new String[paramDefs.length];\n\t\t\tparamLowerBounds = new String[paramDefs.length];\n\t\t\tparamUpperBounds = new String[paramDefs.length];\n\t\t\tfor (int pdNr = 0; pdNr < paramDefs.length; pdNr++) {\n\t\t\t\tif (!paramDefs[pdNr].contains(\"=\")) {\n\t\t\t\t\tparamNames[pdNr] = paramDefs[pdNr];\n\t\t\t\t\tparamLowerBounds[pdNr] = \"0\";\n\t\t\t\t\tparamUpperBounds[pdNr] = \"1\";\n\t\t\t\t} else {\n\t\t\t\t\tString[] paramDefSplit = paramDefs[pdNr].split(\"=\");\n\t\t\t\t\tparamNames[pdNr] = paramDefSplit[0];\n\t\t\t\t\tparamDefSplit[1] = paramDefSplit[1].trim();\n\t\t\t\t\tString[] upperLower = paramDefSplit[1].split(\":\");\n\t\t\t\t\tif (upperLower.length != 2)\n\t\t\t\t\t\tthrow new PrismException(\"Invalid range \\\"\" + paramDefSplit[1] + \"\\\" for parameter \" + paramNames[pdNr]);\n\t\t\t\t\tparamLowerBounds[pdNr] = upperLower[0].trim();\n\t\t\t\t\tparamUpperBounds[pdNr] = upperLower[1].trim();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Plug in model basename for model exports where needed\n\t\tif (!modelExportTasks.isEmpty()) {\n\t\t\tString modelFileBasename = modelFilename;\n\t\t\tif (modelFileBasename.lastIndexOf('.') > -1) {\n\t\t\t\tmodelFileBasename = modelFilename.substring(0, modelFileBasename.lastIndexOf('.'));\n\t\t\t}\n\t\t\tfor (ModelExportTask exportTask : modelExportTasks) {\n\t\t\t\texportTask.replaceEmptyFileBasename(modelFileBasename);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Process the simulation-related command-line options and generate\n\t * a SimulationMethod object to be used for approximate model checking.\n\t * @param expr The property to be checked (note: constants may not be defined)\n\t * @throws PrismException if there are problems with the specified options\n\t */\n\tprivate SimulationMethod processSimulationOptions(Expression expr) throws PrismException\n\t{\n\t\tSimulationMethod aSimMethod = null;\n\n\t\t// See if property to be checked is a reward (R) operator\n\t\tboolean isReward = (expr instanceof ExpressionReward);\n\n\t\t// See if property to be checked is quantitative (=?)\n\t\tboolean isQuant = Expression.isQuantitative(expr);\n\n\t\t// Pick defaults for simulation settings not set from command-line\n\t\tif (!simApproxGiven)\n\t\t\tsimApprox = prism.getSettings().getDouble(PrismSettings.SIMULATOR_DEFAULT_APPROX);\n\t\tif (!simConfidenceGiven)\n\t\t\tsimConfidence = prism.getSettings().getDouble(PrismSettings.SIMULATOR_DEFAULT_CONFIDENCE);\n\t\tif (!simNumSamplesGiven)\n\t\t\tsimNumSamples = prism.getSettings().getInteger(PrismSettings.SIMULATOR_DEFAULT_NUM_SAMPLES);\n\t\tif (!simWidthGiven)\n\t\t\tsimWidth = prism.getSettings().getDouble(PrismSettings.SIMULATOR_DEFAULT_WIDTH);\n\n\t\tif (!reqIterToConcludeGiven)\n\t\t\treqIterToConclude = prism.getSettings().getInteger(PrismSettings.SIMULATOR_DECIDE);\n\t\tif (!simMaxRewardGiven)\n\t\t\tsimMaxReward = prism.getSettings().getDouble(PrismSettings.SIMULATOR_MAX_REWARD);\n\t\tif (!simMaxPathGiven)\n\t\t\tsimMaxPath = prism.getSettings().getLong(PrismSettings.SIMULATOR_DEFAULT_MAX_PATH);\n\n\t\t// Pick a default method, if not specified\n\t\t// (CI for quantitative, SPRT for bounded)\n\t\tif (simMethodName == null) {\n\t\t\tsimMethodName = isQuant ? \"ci\" : \"sprt\";\n\t\t}\n\n\t\t// CI\n\t\tif (simMethodName.equals(\"ci\")) {\n\t\t\tif (simWidthGiven && simConfidenceGiven && simNumSamplesGiven) {\n\t\t\t\tthrow new PrismException(\"Cannot specify all three parameters (width/confidence/samples) for CI method\");\n\t\t\t}\n\t\t\tif (!simWidthGiven) {\n\t\t\t\t// Default (unless width specified) is to leave width unknown\n\t\t\t\taSimMethod = new CIwidth(simConfidence, simNumSamples);\n\t\t\t} else if (!simNumSamplesGiven) {\n\t\t\t\t// Next preferred option (unless specified) is unknown samples\n\t\t\t\tif (simManual)\n\t\t\t\t\taSimMethod = new CIiterations(simConfidence, simWidth, reqIterToConclude);\n\t\t\t\telse\n\t\t\t\t\taSimMethod = (isReward ? new CIiterations(simConfidence, simWidth, simMaxReward) : new CIiterations(simConfidence, simWidth));\n\t\t\t} else {\n\t\t\t\t// Otherwise confidence unknown\n\t\t\t\taSimMethod = new CIconfidence(simWidth, simNumSamples);\n\t\t\t}\n\t\t\tif (simApproxGiven) {\n\t\t\t\tmainLog.printWarning(\"Option -simapprox is not used for the CI method and is being ignored\");\n\t\t\t}\n\t\t}\n\t\t// ACI\n\t\telse if (simMethodName.equals(\"aci\")) {\n\t\t\tif (simWidthGiven && simConfidenceGiven && simNumSamplesGiven) {\n\t\t\t\tthrow new PrismException(\"Cannot specify all three parameters (width/confidence/samples) for ACI method\");\n\t\t\t}\n\t\t\tif (!simWidthGiven) {\n\t\t\t\t// Default (unless width specified) is to leave width unknown\n\t\t\t\taSimMethod = new ACIwidth(simConfidence, simNumSamples);\n\t\t\t} else if (!simNumSamplesGiven) {\n\t\t\t\t// Next preferred option (unless specified) is unknown samples\n\t\t\t\tif (simManual)\n\t\t\t\t\taSimMethod = new ACIiterations(simConfidence, simWidth, reqIterToConclude);\n\t\t\t\telse\n\t\t\t\t\taSimMethod = (isReward ? new ACIiterations(simConfidence, simWidth, simMaxReward) : new CIiterations(simConfidence, simWidth));\n\t\t\t} else {\n\t\t\t\t// Otherwise confidence unknown\n\t\t\t\taSimMethod = new ACIconfidence(simWidth, simNumSamples);\n\t\t\t}\n\t\t\tif (simApproxGiven) {\n\t\t\t\tmainLog.printWarning(\"Option -simapprox is not used for the ACI method and is being ignored\");\n\t\t\t}\n\t\t}\n\t\t// APMC\n\t\telse if (simMethodName.equals(\"apmc\")) {\n\t\t\tif (isReward) {\n\t\t\t\tthrow new PrismException(\"Cannot use the APMC method on reward properties; try CI (switch -simci) instead\");\n\t\t\t}\n\t\t\tif (simApproxGiven && simConfidenceGiven && simNumSamplesGiven) {\n\t\t\t\tthrow new PrismException(\"Cannot specify all three parameters (approximation/confidence/samples) for APMC method\");\n\t\t\t}\n\t\t\tif (!simApproxGiven) {\n\t\t\t\t// Default (unless width specified) is to leave approximation unknown\n\t\t\t\taSimMethod = new APMCapproximation(simConfidence, simNumSamples);\n\t\t\t} else if (!simNumSamplesGiven) {\n\t\t\t\t// Next preferred option (unless specified) is unknown samples\n\t\t\t\taSimMethod = new APMCiterations(simConfidence, simApprox);\n\t\t\t} else {\n\t\t\t\t// Otherwise confidence unknown\n\t\t\t\taSimMethod = new APMCconfidence(simApprox, simNumSamples);\n\t\t\t}\n\t\t\tif (simWidthGiven) {\n\t\t\t\tmainLog.printWarning(\"Option -simwidth is not used for the APMC method and is being ignored\");\n\t\t\t}\n\t\t}\n\t\t// SPRT\n\t\telse if (simMethodName.equals(\"sprt\")) {\n\t\t\tif (isQuant) {\n\t\t\t\tthrow new PrismException(\"Cannot use SPRT on a quantitative (=?) property\");\n\t\t\t}\n\t\t\taSimMethod = new SPRTMethod(simConfidence, simConfidence, simWidth);\n\t\t\tif (simApproxGiven) {\n\t\t\t\tmainLog.printWarning(\"Option -simapprox is not used for the SPRT method and is being ignored\");\n\t\t\t}\n\t\t\tif (simNumSamplesGiven) {\n\t\t\t\tmainLog.printWarning(\"Option -simsamples is not used for the SPRT method and is being ignored\");\n\t\t\t}\n\t\t} else\n\t\t\tthrow new PrismException(\"Unknown simulation method \\\"\" + simMethodName + \"\\\"\");\n\n\t\treturn aSimMethod;\n\t}\n\n\t/**\n\t * Print a -help message, i.e. a list of the command-line switches.\n\t */\n\tprivate void printHelp()\n\t{\n\t\tmainLog.println(\"Usage: \" + Prism.getCommandLineName() + \" [options] <model-file> [<properties-file>] [more-options]\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"Options:\");\n\t\tmainLog.println(\"========\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"-help .......................... Display this help message\");\n\t\tmainLog.println(\"-version ....................... Display PRISM version info\");\n\t\tmainLog.println(\"-javaversion ................... Display Java version info\");\n\t\tmainLog.println(\"-dir <dir> ..................... Set current working directory\");\n\t\tmainLog.println(\"-settings <file>................ Load settings from <file>\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"-pf <props> (or -pctl or -csl) . Model check properties <props>\");\n\t\tmainLog.println(\"-property <refs> (or -prop) .... Only model check properties included in list <refs> of indices/names\");\n\t\tmainLog.println(\"-const <vals> .................. Define constant values as <vals> (e.g. for experiments)\");\n\t\tmainLog.println(\"-steadystate (or -ss) .......... Compute steady-state probabilities (D/CTMCs only)\");\n\t\tmainLog.println(\"-transient <x> (or -tr <x>) .... Compute transient probabilities for time (or time range) <x> (D/CTMCs only)\");\n\t\tmainLog.println(\"-simpath <options> <file>....... Generate a random path with the simulator\");\n\t\tmainLog.println(\"-nobuild ....................... Skip model construction (just do parse/export)\");\n\t\tmainLog.println(\"-test .......................... Enable \\\"test\\\" mode\");\n\t\tmainLog.println(\"-testall ....................... Enable \\\"test\\\" mode, but don't exit on error\");\n\t\tmainLog.println(\"-javamaxmem <x>................. Set the maximum heap size for Java, e.g. 500m, 4g [default: 1g]\");\n\t\tmainLog.println(\"-javastack <x> ................. Set the Java stack size [default: 4m]\");\n\t\tmainLog.println(\"-javaparams <x>................. Pass additional command-line arguments to Java\");\n\t\tmainLog.println(\"-timeout <n> ................... Exit after a time-out of <n> seconds if not already terminated\");\n\t\tmainLog.println(\"-ng ............................ Run PRISM in Nailgun server mode; subsequent calls are then made via \\\"ngprism\\\"\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"IMPORTS:\");\n\t\tmainLog.println(\"-importpepa .................... Model description is in PEPA, not the PRISM language\");\n\t\tmainLog.println(\"-importmodel <files> ........... Import the model directly from text file(s)\");\n\t\tmainLog.println(\"-importtrans <file> ............ Import the transition matrix directly from a text file\");\n\t\tmainLog.println(\"-importstates <file>............ Import the list of states directly from a text file\");\n\t\tmainLog.println(\"-importobs <file>............... Import the list of observations directly from a text file\");\n\t\tmainLog.println(\"-importlabels <file>............ Import the list of labels directly from a text file\");\n\t\tmainLog.println(\"-importstaterewards <file>...... Import the state rewards directly from a text file\");\n\t\tmainLog.println(\"-importtransrewards <file>...... Import the transition rewards directly from a text file\");\n\t\tmainLog.println(\"-importinitdist <file>.......... Specify initial probability distribution for transient/steady-state analysis\");\n\t\tmainLog.println(\"-dtmc .......................... Force imported/built model to be a DTMC\");\n\t\tmainLog.println(\"-ctmc .......................... Force imported/built model to be a CTMC\");\n\t\tmainLog.println(\"-mdp ........................... Force imported/built model to be an MDP\");\n\t\tmainLog.println(\"-importresults <file> .......... Import results from a data frame stored in CSV file\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"EXPORTS:\");\n\t\tmainLog.println(\"-exportresults <file[:options]>  Export the results of model checking to a file\");\n\t\tmainLog.println(\"-exportvector <file>  .......... Export results of model checking for all states to a file\");\n\t\tmainLog.println(\"-exportmodel <files[:options]> . Export the built model to file(s)\");\n\t\tmainLog.println(\"-exporttrans <file> ............ Export the transition matrix to a file\");\n\t\tmainLog.println(\"-exportstaterewards <file> ..... Export the state rewards vector to a file\");\n\t\tmainLog.println(\"-exporttransrewards <file> ..... Export the transition rewards matrix to a file\");\n\t\tmainLog.println(\"-exportrewards <file1> <file2>.. Export state/transition rewards to files 1/2\");\n\t\tmainLog.println(\"-exportstates <file> ........... Export the list of reachable states to a file\");\n\t\tmainLog.println(\"-exportobs <file> .............. Export the list of observations to a file\");\n\t\tmainLog.println(\"-exportlabels <file[:options]> . Export the list of labels and satisfying states to a file\");\n\t\tmainLog.println(\"-exportproplabels <file[:opt]> . Export the list of labels and satisfying states from the properties file to a file\");\n\t\tmainLog.println(\"-exportstrat <file[:options]> .. Generate and export a strategy to a file\");\n\t\tmainLog.println(\"-exportmatlab .................. When exporting matrices/vectors/labels/etc., use Matlab format\");\n\t\tmainLog.println(\"-exportrows .................... When exporting matrices, put a whole row on one line\");\n\t\tmainLog.println(\"-exporttransdot <file> ......... Export the transition matrix graph to a dot file\");\n\t\tmainLog.println(\"-exporttransdotstates <file> ... Export the transition matrix graph to a dot file, with state info\");\n\t\tmainLog.println(\"-exportdot <file> .............. Export the transition matrix MTBDD to a dot file\");\n\t\tmainLog.println(\"-exportsccs <file> ............. Compute and export all SCCs of the model\");\n\t\tmainLog.println(\"-exportbsccs <file> ............ Compute and export all BSCCs of the model\");\n\t\tmainLog.println(\"-exportmecs <file> ............. Compute and export all maximal end components (MDPs only)\");\n\t\tmainLog.println(\"-exportsteadystate <file> ...... Export steady-state probabilities to a file\");\n\t\tmainLog.println(\"-exporttransient <file> ........ Export transient probabilities to a file\");\n\t\tmainLog.println(\"-exportprism <file> ............ Export final PRISM model to a file\");\n\t\tmainLog.println(\"-exportprismconst <file> ....... Export final PRISM model with expanded constants to a file\");\n\n\t\tPrismSettings.printHelp(mainLog);\n\n\t\tmainLog.println();\n\t\tmainLog.println(\"SIMULATION OPTIONS:\");\n\t\tmainLog.println(\"-sim ........................... Use the PRISM simulator to approximate results of model checking\");\n\t\tmainLog.println(\"-simmethod <name> .............. Specify the method for approximate model checking (ci, aci, apmc, sprt)\");\n\t\tmainLog.println(\"-simsamples <n> ................ Set the number of samples for the simulator (CI/ACI/APMC methods)\");\n\t\tmainLog.println(\"-simconf <x> ................... Set the confidence parameter for the simulator (CI/ACI/APMC methods)\");\n\t\tmainLog.println(\"-simwidth <x> .................. Set the interval width for the simulator (CI/ACI methods)\");\n\t\tmainLog.println(\"-simapprox <x> ................. Set the approximation parameter for the simulator (APMC method)\");\n\t\tmainLog.println(\"-simmanual ..................... Do not use the automated way of deciding whether the variance is null or not\");\n\t\tmainLog.println(\"-simvar <n> .................... Set the minimum number of samples to know the variance is null or not\");\n\t\tmainLog.println(\"-simmaxrwd <x> ................. Set the maximum reward -- useful to display the CI/ACI methods progress\");\n\t\tmainLog.println(\"-simpathlen <n> ................ Set the maximum path length for the simulator\");\n\n\t\tmainLog.println();\n\t\tmainLog.println(\"You can also use \\\"prism -help xxx\\\" for help on some switches -xxx with non-obvious syntax.\");\n\t}\n\n\t/**\n\t * Print a -help xxx message, i.e. display help on a specific switch\n\t */\n\tprivate void printHelpSwitch(String sw)\n\t{\n\t\t// Remove \"-\" from start of switch, in case present (it shouldn't be really)\n\t\tif (sw.charAt(0) == '-')\n\t\t\tsw = sw.substring(1);\n\n\t\t// -const\n\t\tif (sw.equals(\"const\")) {\n\t\t\tmainLog.println(\"Switch: -const <vals>\\n\");\n\t\t\tmainLog.println(\"<vals> is a comma-separated list of values or value ranges for undefined constants\");\n\t\t\tmainLog.println(\"in the model or properties (i.e. those declared without values, such as \\\"const int a;\\\").\");\n\t\t\tmainLog.println(\"You can either specify a single value (a=1), a range (a=1:10) or a range with a step (a=1:2:50).\");\n\t\t\tmainLog.println(\"For convenience, constant definutions can also be split across multiple -const switches.\");\n\t\t\tmainLog.println(\"\\nExamples:\");\n\t\t\tmainLog.println(\" -const a=1,b=5.6,c=true\");\n\t\t\tmainLog.println(\" -const a=1:10,b=5.6\");\n\t\t\tmainLog.println(\" -const a=1:2:50,b=5.6\");\n\t\t\tmainLog.println(\" -const a=1:2:50 -const b=5.6\");\n\t\t}\n\t\t// -simpath\n\t\telse if (sw.equals(\"simpath\")) {\n\t\t\tmainLog.println(\"Switch: -simpath <options> <file>\\n\");\n\t\t\tmainLog.println(\"Generate a random path with the simulator and export it to <file> (or to the screen if <file>=\\\"stdout\\\").\");\n\t\t\tmainLog.println(\"<options> is a comma-separated list of options taken from:\");\n\t\t\tGenerateSimulationPath.printOptions(mainLog);\n\t\t}\n\t\t// -importmodel\n\t\telse if (sw.equals(\"importmodel\")) {\n\t\t\tmainLog.println(\"Switch: -importmodel <files>[:options]\\n\");\n\t\t\tmainLog.println(\"Import the model directly from one or more file(s).\");\n\t\t\tmainLog.println(\"Use a list of file extensions to indicate which files should be read, e.g.:\");\n\t\t\tmainLog.println(\"\\n -importmodel in.tra,sta\\n\");\n\t\t\tmainLog.println(\"Possible extensions are: .tra, .sta, .obs, .lab, .srew, .trew, .umb\");\n\t\t\tmainLog.println(\"Use extension .all to import all explicit files (.tra/sta/obs/lab/srew/trew), e.g.:\");\n\t\t\tmainLog.println(\"\\n -importmodel in.all\\n\");\n\t\t\tmainLog.println(\"If provided, <options> is a comma-separated list of options taken from:\");\n\t\t\tmainLog.println(\" * format (=explicit/umb) - model import format\");\n\t\t}\n\t\t// -importresults\n\t\telse if (sw.equals(\"importresults\")) {\n\t\t\tmainLog.println(\"Switch: -importresults <file>\\n\");\n\t\t\tmainLog.println(\"Import results from a data frame stored as comma-separated values in <file>.\");\n\t\t}\t\t\t\n\t\t// -exportresults\n\t\telse if (sw.equals(\"exportresults\")) {\n\t\t\tmainLog.println(\"Switch: -exportresults <file[:options]>\\n\");\n\t\t\tmainLog.println(\"Exports the results of model checking to <file> (or to the screen if <file>=\\\"stdout\\\").\");\n\t\t\tmainLog.println(\"The default behaviour is to export a list of results in text form, using tabs to separate items.\");\n\t\t\tmainLog.println(\"If provided, <options> is a comma-separated list of options taken from:\");\n\t\t\tmainLog.println(\" * csv - Export results as comma-separated values\");\n\t\t\tmainLog.println(\" * matrix - Export results as one or more 2D matrices (e.g. for surface plots)\");\n\t\t\tmainLog.println(\" * dataframe - Export results as dataframe in comma-separated values)\");\n\t\t\tmainLog.println(\" * comment - Export results in comment format for regression testing)\");\n\t\t}\n\t\t// -exportlabels\n\t\telse if (sw.equals(\"exportlabels\")) {\n\t\t\tmainLog.println(\"Switch: -exportlabels <files[:options]>\\n\");\n\t\t\tmainLog.println(\"Export the list of labels and satisfying states to a file (or to the screen if <file>=\\\"stdout\\\").\");\n\t\t\tmainLog.println();\n\t\t\tmainLog.println(\"If provided, <options> is a comma-separated list of options taken from:\");\n\t\t\tmainLog.println(\" * matlab - export data in Matlab format\");\n\t\t\tmainLog.println(\" * proplabels - export labels from a properties file into the same file, too\");\n\t\t}\n\t\t// -exportproplabels\n\t\telse if (sw.equals(\"exportproplabels\")) {\n\t\t\tmainLog.println(\"Switch: -exportproplabels <files[:options]>\\n\");\n\t\t\tmainLog.println(\"Export the list of labels and satisfying states from the properties file to a file (or to the screen if <file>=\\\"stdout\\\").\");\n\t\t\tmainLog.println();\n\t\t\tmainLog.println(\"If provided, <options> is a comma-separated list of options taken from:\");\n\t\t\tmainLog.println(\" * matlab - export data in Matlab format\");\n\t\t}\n\t\t// -exportmodel\n\t\telse if (sw.equals(\"exportmodel\")) {\n\t\t\tmainLog.println(\"Switch: -exportmodel <files[:options]>\\n\");\n\t\t\tmainLog.println(\"Export the built model to file(s) (or to the screen if <file>=\\\"stdout\\\").\");\n\t\t\tmainLog.println(\"Use a list of file extensions to indicate which files should be generated, e.g.:\");\n\t\t\tmainLog.println(\"\\n -exportmodel out.tra,sta\\n\");\n\t\t\tmainLog.println(\"\\n -exportmodel out.umb\\n\");\n\t\t\tmainLog.println(\"Possible extensions are: .tra, .srew, .trew, .lab, .sta, .obs, .dot, .umb, .drn\");\n\t\t\tmainLog.println(\"Use extension .all to export all explicit files (.tra/srew/trew/lab/sta/obs), e.g.:\");\n\t\t\tmainLog.println(\"\\n -exportmodel out.all\\n\");\n\t\t\tmainLog.println(\"Omit the file basename to use the basename of the model file, e.g.:\");\n\t\t\tmainLog.println(\"\\n -exportmodel .all\\n\");\n\t\t\tmainLog.println(\"Use extension .rew to export both .srew/.trew files\");\n\t\t\tmainLog.println();\n\t\t\tmainLog.println(\"If provided, <options> is a comma-separated list of options taken from:\");\n\t\t\tmainLog.println(\" * format (=explicit/matlab/dot/drn/umb) - model export format\");\n\t\t\tmainLog.println(\" * rewards (=true/false) - whether to include rewards\");\n\t\t\tmainLog.println(\" * labels (=true/false) - whether to include labels\");\n\t\t\tmainLog.println(\" * states (=true/false) - whether to include state definitions\");\n\t\t\tmainLog.println(\" * obs (=true/false) - whether to include observation definitions\");\n\t\t\tmainLog.println(\" * actions (=true/false) - whether to include actions on choices/transitions\");\n\t\t\tmainLog.println(\" * precision (=<n>) - use <n> significant figures for floating point values (in text)\");\n\t\t\tmainLog.println(\" * zip (=true/false) - whether to zip UMB files\");\n\t\t\tmainLog.println(\" * text - show binary formats in textual form \");\n\t\t\tmainLog.println(\" * matlab - same as format=matlab\");\n\t\t\tmainLog.println(\"For the explicit files format:\");\n\t\t\tmainLog.println(\" * rows - export matrices with one row/distribution on each line\");\n\t\t\tmainLog.println(\" * proplabels - also export labels from a properties file into the same file, too\");\n\t\t\tmainLog.println(\" * headers (=true/false) - include headers in explicit (reward) files\");\n\t\t}\n\t\t// -exportstrat\n\t\telse if (sw.equals(\"exportstrat\")) {\n\t\t\tmainLog.println(\"Switch: -exportstrat <file[:options]>\\n\");\n\t\t\tmainLog.println(\"Generate and export a strategy to a file (or to the screen if <file>=\\\"stdout\\\").\");\n\t\t\tmainLog.println(\"Use file extension .tra or .dot to export as an induced model or Dot file, respectively.\");\n\t\t\tmainLog.println(\"If provided, <options> is a comma-separated list of options taken from:\");\n\t\t\tmainLog.println(\" * type (=actions/induced/dot) - type of strategy export\");\n\t\t\tmainLog.println(\" * mode (=restrict/reduce) - mode to use for building induced model (or Dot file)\");\n\t\t\tmainLog.println(\" * reach (=true/false) - whether to restrict the strategy to its reachable states\");\n\t\t\tmainLog.println(\" * states (=true/false) - whether to show states, rather than state indices, for actions lists or Dot files\");\n\t\t\tmainLog.println(\" * obs (=true/false) - for partially observable models, whether to merge observationally equivalent states\");\n\t\t}\n\t\t// Try PrismSettings\n\t\telse if (PrismSettings.printHelpSwitch(mainLog, sw)) {\n\t\t\treturn;\n\t\t}\n\t\t// Unknown\n\t\telse {\n\t\t\tmainLog.println(\"Sorry - no help available for switch -\" + sw);\n\t\t}\n\t}\n\n\t// print version\n\n\tprivate void printVersion()\n\t{\n\t\tmainLog.println(Prism.getToolName() + \" version \" + Prism.getVersion());\n\t}\n\n\t/**\n\t * Print out a list of all PRISM language keywords.\n\t */\n\tprivate void printListOfKeywords()\n\t{\n\t\tList<String> list = Prism.getListOfKeywords();\n\t\tmainLog.print(\"PRISM keywords:\");\n\t\tfor (String s : list) {\n\t\t\tmainLog.print(\" \" + s);\n\t\t}\n\t\tmainLog.println();\n\t}\n\n\t/**\n\t * Report a (non-fatal) error to the log.\n\t * In test mode, this _will_ result in an exit,\n\t * unless we are in test-all mode or the passed in error\n\t * is a PrismNotSupportedException, which is not\n\t * treated as a normal error (e.g., by prism-auto/prism-test)\n\t */\n\tprivate void error(PrismException e)\n\t{\n\t\terror(e.getMessage(), e instanceof PrismNotSupportedException);\n\t}\n\n\t/**\n\t * Report a (non-fatal) error to the log.\n\t * In test (but not test-all) mode, this _will_ result in an exit.\n\t */\n\tprivate void error(String s)\n\t{\n\t\terror(s, false);\n\t}\n\n\t/**\n\t * Report a (non-fatal) error to the log.\n\t * In test (but not test-all) mode, this _will_ result in an exit.\n\t * The latter can be overridden by setting dontExit to true.\n\t */\n\tprivate void error(String s, boolean dontExit)\n\t{\n\t\t// If (and only if) we are in \"test\" (and not \"testall\") mode, treat any error as fatal\n\t\tif (test && testExitsOnFail && !dontExit) {\n\t\t\terrorAndExit(s);\n\t\t}\n\t\t// Normal case: just display error message, but don't exit\n\t\tmainLog.println(\"\\nError: \" + s + \".\");\n\t\tmainLog.flush();\n\t}\n\n\t/**\n\t * Report a (fatal) error and exit cleanly (with exit code 1).\n\t */\n\tprivate void errorAndExit(String s)\n\t{\n\t\tprism.closeDown(false);\n\t\tmainLog.println(\"\\nError: \" + s + \".\");\n\t\tmainLog.flush();\n\t\tSystem.exit(1);\n\t}\n\n\t/**\n\t * Exit cleanly (with exit code 0).\n\t */\n\tprivate void exit()\n\t{\n\t\tprism.closeDown(true);\n\t\tSystem.exit(0);\n\t}\n\n\t/**\n\t * Exit cleanly (with exit code i).\n\t */\n\tprivate void exit(int i)\n\t{\n\t\tprism.closeDown(true);\n\t\tSystem.exit(i);\n\t}\n\n\t// main method\n\n\tpublic static void main(String[] args)\n\t{\n\t\t// Normal operation: just run PrismCL\n\t\tif (!(args.length > 0 && \"-ng\".equals(args[0]))) {\n\t\t\tnew PrismCL().go(args);\n\t\t}\n\t\t// Nailgun server mode (-ng switch)\n\t\telse {\n\t\t\ttry {\n\t\t\t\tSystem.out.println(\"Starting PRISM-Nailgun server...\");\n\t\t\t\tcom.martiansoftware.nailgun.NGServer.main(new String[0]);\n\t\t\t} catch (NumberFormatException | UnknownHostException e) {\n\t\t\t\tSystem.out.println(\"Failed to launch Nailgun server: \" + e);\n\t\t\t}\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/PrismComponent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.File;\n\n/**\n * Base class for \"components\" of PRISM, i.e. classes that implement\n * a particular piece of functionality required for model checking.\n * \n * Stores:\n * <ul>\n * <li> A PrismLog ({@code mainLog}) for output \n * <li> A PrismSettings object ({@code settings})\n * </ul>\n * \n * Depending on the (sub)class, the {@code settings} object may either be read\n * from each time that a setting is required (thus respecting any changes that\n * are made to it over time), or read from initially and then ignored.\n * Mostly, these classes are freshly created to perform some task and then discarded,\n * so there is no point making changes to {@code settings} after creation.\n */\npublic class PrismComponent\n{\n\t/**\n\t * Log for output.\n\t * Defaults to System.out, so that is always available.\n\t */\n\tprotected PrismLog mainLog = new PrismPrintStreamLog(System.out);\n\n\t/**\n\t * PRISM settings object.\n\t * Defaults to null to avoid delays when it will be copied from a parent object.\n\t */\n\tprotected PrismSettings settings = null;\n\n\t// Constructors\n\t\n\t/**\n\t * Default constructor.\n\t */\n\tpublic PrismComponent()\n\t{\n\t\t// Create a fresh PrismSettings() object containing PRISM defaults.\n\t\tsettings = new PrismSettings();\n\t}\n\n\t/**\n\t * Create a PrismComponent object, inheriting state from another (\"parent\") PrismComponent.\n\t */\n\tpublic PrismComponent(PrismComponent parent)\n\t{\n\t\tif (parent == null)\n\t\t\treturn;\n\t\tsetLog(parent.getLog());\n\t\tsetSettings(parent.getSettings());\n\t}\n\t\n\t// Setters (declared as final since they are called from the constructor)\n\t\n\t/**\n\t * Set log (\"mainLog\") for output.\n\t */\n\tpublic final void setLog(PrismLog mainLog)\n\t{\n\t\tthis.mainLog = mainLog;\n\t}\n\n\t/**\n\t * Set PRISMSettings object.\n\t */\n\tpublic final void setSettings(PrismSettings settings)\n\t{\n\t\tthis.settings = settings;\n\t}\n\t\n\t// Getters\n\t\n\t/**\n\t * Get log (\"mainLog\") for output.\n\t */\n\tpublic PrismLog getLog()\n\t{\n\t\treturn mainLog;\n\t}\n\t\n\t/**\n\t * Get the locally stored PRISMSettings object.\n\t */\n\tpublic PrismSettings getSettings()\n\t{\n\t\treturn settings;\n\t}\n\n\t/**\n\t * Either create a new PrismFileLog for {@code file} or,\n\t * if {@code file} is null, return the log.\n\t * Throws a {@code PrismException} if there is a problem opening the file.\n\t */\n\tpublic PrismLog getPrismLogForFile(File file) throws PrismException\n\t{\n\t\treturn getPrismLogForFile(file, false);\n\t}\n\n\t/**\n\t * Either create a new PrismFileLog for {@code file} or,\n\t * if {@code file} is null, return the log.\n\t * In the former case, if {@code append} is true,\n\t * the file should be opened in \"append\" mode.\n\t * In the latter case, a wrapper around the log is returned,\n\t * which can be {@code close()}ed without closing the underlying log.\n\t * The {@code append} parameter is ignored if {@code file} is null.\n\t * Throws a {@code PrismException} if there is a problem opening the file.\n\t */\n\tpublic PrismLog getPrismLogForFile(File file, boolean append) throws PrismException\n\t{\n\t\t// create new file log or use main log\n\t\tPrismLog tmpLog;\n\t\tif (file != null) {\n\t\t\ttmpLog = PrismFileLog.create(file.getPath(), append);\n\t\t} else {\n\t\t\ttmpLog = new PrismLogWrapper(mainLog);\n\t\t}\n\t\treturn tmpLog;\n\t}\n\n\t/**\n\t * Get a string describing the output destination specified by a File:\n\t * \"to file \\\"filename\\\"...\" if non-null; \"below:\" if null.\n\t * See {@link #getPrismLogForFile(File)}.\n\t */\n\tpublic static String getDestinationStringForFile(File file)\n\t{\n\t\treturn (file == null) ? \"below:\" : \"to file \\\"\" + file + \"\\\"...\";\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/prism/PrismDevNullLog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * A {@link PrismLog} that discards all output.\n */\npublic class PrismDevNullLog extends PrismLog\n{\n\tpublic PrismDevNullLog()\n\t{\n\t}\n\n\t// Methods to implement PrismLog\n\n\t@Override\n\tpublic boolean ready()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic void flush()\n\t{\n\t}\n\n\t@Override\n\tpublic void close()\n\t{\n\t\tflush();\n\t}\n\n\t@Override\n\tpublic void print(boolean b)\n\t{\n\t}\n\n\t@Override\n\tpublic void print(char c)\n\t{\n\t}\n\n\t@Override\n\tpublic void print(double d)\n\t{\n\t}\n\n\t@Override\n\tpublic void print(float f)\n\t{\n\t}\n\n\t@Override\n\tpublic void print(int i)\n\t{\n\t}\n\n\t@Override\n\tpublic void print(long l)\n\t{\n\t}\n\n\t@Override\n\tpublic void print(Object obj)\n\t{\n\t}\n\n\t@Override\n\tpublic void print(String s)\n\t{\n\t}\n\n\t@Override\n\tpublic void println()\n\t{\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PrismException.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\npublic class PrismException extends Exception\n{\n\tpublic PrismException(String s)\n\t{\n\t\tsuper(s);\n\t}\n\t\n\t/**\n\t * Return a new exception of the same type with {@code prefix} prepended to the message.\n\t */\n\tpublic PrismException prepend(String prefix)\n\t{\n\t\treturn new PrismException(prefix + getMessage());\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"Error: \" + getMessage() + \".\";\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/PrismFileLog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.BufferedOutputStream;\nimport java.io.FileNotFoundException;\nimport java.io.FileOutputStream;\nimport java.io.PrintStream;\n\n/**\n * A {@link PrismLog} that will write to a file (or stdout).\n */\npublic class PrismFileLog extends PrismPrintStreamLog\n{\n\t/** Filename (or \"stdout\") */\n\tprotected String filename;\n\t/** Are we writing to stdout? */\n\tprotected boolean stdout;\n\t/** Are we using native code to write to the file? */\n\tprotected boolean nativeCode;\n\n\t/**\n\t * Create a {@link PrismLog} which will write to {@code filename}, overwriting any previous contents.\n\t * If {@code filename} is \"stdout\", then output will be written to standard output.\n\t * Throw a PRISM exception if there is a problem opening the file for writing.\n\t * @param filename Filename of log file\n\t */\n\tpublic PrismFileLog(String filename) throws PrismException\n\t{\n\t\tthis(filename, false);\n\t}\n\n\t/**\n\t * Create a {@link PrismLog} which will write to {@code filename}, appending to an existing file if requested.\n\t * If {@code filename} is \"stdout\", then output will be written to standard output.\n\t * Throw a PRISM exception if there is a problem opening the file for writing.\n\t * @param filename Filename of log file\n\t * @param append Append to the existing file?\n\t */\n\tpublic PrismFileLog(String filename, boolean append) throws PrismException\n\t{\n\t\tthis(filename, append, false);\n\t}\n\n\t/**\n\t * Create a {@link PrismLog} which will write to {@code filename}, appending to an existing file if requested.\n\t * If {@code filename} is \"stdout\", then output will be written to standard output.\n\t * Throw a PRISM exception if there is a problem opening the file for writing.\n\t * @param filename Filename of log file\n\t * @param append Append to the existing file?\n\t * @param nativeCode Use native code to write to the file?\n\t */\n\tpublic PrismFileLog(String filename, boolean append, boolean nativeCode) throws PrismException\n\t{\n\t\tcreateLogStream(filename, append, nativeCode);\n\t}\n\n\t/**\n\t * Set up the PrintStream that will be used to write to the log\n\t * @param filename Filename of log file\n\t * @param append Append to the existing file?\n\t * @param nativeCode Use native code to write to the file?\n\t */\n\tprivate void createLogStream(String filename, boolean append, boolean nativeCode) throws PrismException\n\t{\n\t\tthis.filename = filename;\n\t\tthis.stdout = \"stdout\".equals(filename);\n\t\tthis.nativeCode = nativeCode;\n\t\ttry {\n\t\t\tif (nativeCode) {\n\t\t\t\tsetPrintStream(new PrismFileLogNative(filename, append));\n\t\t\t} else {\n\t\t\t\tif (stdout) {\n\t\t\t\t\tsetPrintStream(System.out);\n\t\t\t\t} else {\n\t\t\t\t\tsetPrintStream(new PrintStream(new BufferedOutputStream(new FileOutputStream(filename, append))));\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (FileNotFoundException e) {\n\t\t\tthrow new PrismException(\"Could not open file \\\"\" + filename + \"\\\" for output\");\n\t\t}\n\t}\n\n\t/**\n\t * Ensure the log is using native code to write to the file.\n\t * If this is currently not the case, this method will {@code close()}\n\t * the current log and open a new equivalent one using native code.\n\t * Throw a PRISM exception if there is a problem opening the file for writing.\n\t */\n\tpublic void useNative() throws PrismException\n\t{\n\t\tif (!nativeCode) {\n\t\t\tclose();\n\t\t\tcreateLogStream(filename, true, true);\n\t\t}\n\t}\n\n\t/**\n\t * Get the filename (or \"stdout\" if writing to standard output)\n\t **/\n\tpublic String getFileName()\n\t{\n\t\treturn stdout ? \"stdout\" : filename;\n\t}\n\n\t/**\n\t * Is this log using native code to write to the file?\n\t */\n\tpublic boolean isNative()\n\t{\n\t\treturn nativeCode;\n\t}\n\n\t// Methods for PrismLog\n\t\n\t@Override\n\tpublic boolean ready()\n\t{\n\t\tif (logStream == null) {\n\t\t\treturn false;\n\t\t}\n\t\tif (logStream instanceof PrismFileLogNative) {\n\t\t\treturn ((PrismFileLogNative) logStream).ready();\n\t\t} else {\n\t\t\treturn !logStream.checkError();\n\t\t}\n\t}\n\n\t@Override\n\tpublic long getFilePointer()\n\t{\n\t\tif (logStream instanceof PrismFileLogNative) {\n\t\t\treturn ((PrismFileLogNative) logStream).getFilePointer();\n\t\t} else {\n\t\t\treturn -1;\n\t\t}\n\t}\n\n\t// Static methods for creating logs\n\n\t/**\n\t /**\n\t * Create a {@link PrismLog} which will write to {@code filename}, overwriting any previous contents.\n\t * If {@code filename} is \"stdout\", then output will be written to standard output.\n\t * Throw a PRISM exception if there is a problem opening the file for writing.\n\t * @param filename Filename of log file\n\t */\n\tpublic static PrismFileLog create(String filename) throws PrismException\n\t{\n\t\treturn new PrismFileLog(filename);\n\t}\n\n\t/**\n\t * Create a {@link PrismLog} which will write to {@code filename}, appending to an existing file if requested.\n\t * If {@code filename} is \"stdout\", then output will be written to standard output.\n\t * Throw a PRISM exception if there is a problem opening the file for writing.\n\t * @param filename Filename of log file\n\t * @param append Append to the existing file?\n\t */\n\tpublic static PrismFileLog create(String filename, boolean append) throws PrismException\n\t{\n\t\treturn new PrismFileLog(filename, append);\n\t}\n\n\t/**\n\t * Create a {@link PrismLog} which will write to {@code filename}, appending to an existing file if requested.\n\t * If {@code filename} is \"stdout\", then output will be written to standard output.\n\t * Throw a PRISM exception if there is a problem opening the file for writing.\n\t * @param filename Filename of log file\n\t * @param append Append to the existing file?\n\t * @param nativeCode Use native code to write to the file?\n\t */\n\tpublic static PrismFileLog create(String filename, boolean append, boolean nativeCode) throws PrismException\n\t{\n\t\treturn new PrismFileLog(filename, append, nativeCode);\n\t}\n\n\t/**\n\t * Create a {@link PrismLog} which will write to standard output.\n\t */\n\tpublic static PrismFileLog createStdout() throws PrismException\n\t{\n\t\treturn create(\"stdout\");\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/PrismFileLogNative.java",
    "content": "package prism;\n\nimport java.io.ByteArrayOutputStream;\nimport java.io.FileNotFoundException;\nimport java.io.OutputStream;\nimport java.io.PrintStream;\nimport java.nio.charset.StandardCharsets;\n\n/**\n * A PrintStream that will write to a file (or stdout) using native code,\n */\npublic class PrismFileLogNative extends PrintStream\n{\n    /** Native file pointer, cast to a long */\n    protected long fp;\n    /** Are we writing to stdout? */\n    protected boolean stdout;\n\n    /** Line buffer to accumulate bytes until a newline */\n    private final ByteArrayOutputStream lineBuffer = new ByteArrayOutputStream(128);\n\n    /**\n     * Create a stream that will write to {@code filename}, overwriting any previous contents.\n     * If {@code filename} is \"stdout\", then output will be written to standard output.\n     * In both cases, native code will be used to do the writing.\n     * @param filename Filename of log file\n     */\n    public PrismFileLogNative(String filename) throws FileNotFoundException\n    {\n        this(filename, false);\n    }\n\n    /**\n     * Create a stream that will write to {@code filename}, appending to an existing file if requested.\n     * If {@code filename} is \"stdout\", then output will be written to standard output.\n     * In both cases, native code will be used to do the writing.\n     * @param filename Filename of log file\n     * @param append Append to the existing file?\n     */\n    public PrismFileLogNative(String filename, boolean append) throws FileNotFoundException\n    {\n        super(OutputStream.nullOutputStream());\n        this.stdout = \"stdout\".equals(filename);\n        if (stdout) {\n            fp = PrismNative.PN_GetStdout();\n        } else {\n            fp = append ? PrismNative.PN_OpenFileAppend(filename) : PrismNative.PN_OpenFile(filename);\n        }\n    }\n\n    /**\n     * Is this stream ready to be written to? (i.e. is the file pointer valid?)\n     */\n    public boolean ready()\n    {\n        return fp != 0;\n    }\n\n    /**\n     * Get the native file pointer (cast to a long) that this stream is writing to.\n     */\n    public long getFilePointer()\n    {\n        return fp;\n    }\n\n    // Methods to overwrite the PrintStream implementation\n\n    @Override\n    public synchronized void write(byte[] buf, int off, int len)\n    {\n        int start = off;\n        for (int i = off; i < off + len; i++) {\n            if (buf[i] == '\\n') {\n                // Print up to (but not including) a newline\n                lineBuffer.write(buf, start, (i - start));\n                if (fp == 0) {\n                    throw new IllegalStateException(\"Trying to write to an invalid file handle (already closed?)\");\n                }\n                String line = lineBuffer.toString(StandardCharsets.UTF_8);\n                // On Windows, lines probably end with \\r\\n, so remove a trailing \\r if it exists\n                if (line.endsWith(\"\\r\")) {\n                    line = line.substring(0, line.length() - 1);\n                }\n                PrismNative.PN_PrintToFile(fp, line + \"\\n\");\n                lineBuffer.reset();\n                start = i + 1;\n            }\n        }\n        // Buffer any remaining bytes after the last newline\n        if (start < off + len) {\n            lineBuffer.write(buf, start, (off + len) - start);\n        }\n    }\n\n    @Override\n    public synchronized void write(int b)\n    {\n        lineBuffer.write(b);\n        if (b == '\\n') {\n            if (fp == 0) {\n                throw new IllegalStateException(\"Trying to write to an invalid file handle (already closed?)\");\n            }\n            PrismNative.PN_PrintToFile(fp, lineBuffer.toString(StandardCharsets.UTF_8));\n            lineBuffer.reset();\n        }\n    }\n\n    @Override\n    public synchronized void flush()\n    {\n        if (fp == 0) {\n            throw new IllegalStateException(\"Trying to flush an invalid file handle (already closed?)\");\n        }\n        if (lineBuffer.size() > 0) {\n            PrismNative.PN_PrintToFile(fp, lineBuffer.toString(StandardCharsets.UTF_8));\n            lineBuffer.reset();\n        }\n        PrismNative.PN_FlushFile(fp);\n    }\n\n    @Override\n    public void close()\n    {\n        // Ignore if already closed (as specified by Closable contract)\n        if (fp == 0) {\n            return;\n        }\n        flush();\n        // We never close stdout\n        if (stdout) {\n            return;\n        }\n        PrismNative.PN_CloseFile(fp);\n        // Set pointer to zero to indicate that the file handle is not valid anymore\n        fp = 0;\n    }\n}\n"
  },
  {
    "path": "prism/src/prism/PrismLangException.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport parser.ast.ASTElement;\n\npublic class PrismLangException extends PrismException\n{\n\tpublic static final int MAX_ERR_STR = 20;\n\t\n\tprotected ASTElement e = null;\n\t\n\tpublic PrismLangException(String s)\n\t{\n\t\tsuper(s);\n\t}\n\t\n\tpublic PrismLangException(String s, ASTElement e)\n\t{\n\t\tsuper(s);\n\t\tthis.e =e ;\n\t}\n\t\n\tpublic void setASTElement(ASTElement e)\n\t{\n\t\tthis.e =e ;\n\t}\n\t\n\t@Override\n\tpublic PrismLangException prepend(String prefix)\n\t{\n\t\treturn new PrismLangException(prefix + getMessage(), e);\n\t}\n\t\n\tpublic boolean hasASTElement()\n\t{\n\t\treturn e != null ;\n\t}\n\t\n\tpublic ASTElement getASTElement()\n\t{\n\t\treturn e ;\n\t}\n\t\n\tpublic String getMessage()\n\t{\n\t\tString msg = super.getMessage();\n\t\tif (e == null) return msg;\n\t\tString s = null;\n\t\ttry {\n\t\t\ts = e.toString();\n\t\t} catch (Exception ex) {\n\t\t\t// in case there is a problem converting the AST element to a string\n\t\t\t// we ignore it\n\t\t}\n\t\tif (s != null && s.length() < MAX_ERR_STR) {\n\t\t\tif (e.hasPosition()) msg += \" (\\\"\" + s + \"\\\", \" + e.getBeginString() +\")\";\n\t\t\telse msg += \" (\\\"\" + s + \"\\\")\";\n\t\t}\n\t\telse {\n\t\t\tif (e.hasPosition()) msg += \" (\" + e.getBeginString() +\")\";\n\t\t}\n\t\treturn msg;\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"Error: \" + getMessage() + \".\";\n\t}\n\t\n\tpublic boolean hasLineNumbers()\n\t{\n\t\tif (hasASTElement())\n\t\t{\n\t\t\tif (e.getBeginColumn() != -1\n\t\t\t && e.getBeginLine() != -1\n\t\t\t && e.getEndLine() != -1\n\t\t\t && e.getEndColumn() != -1)\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\treturn false;\n\t}\n\t\n\tpublic int getBeginColumn()\n\t{\n\t\tif (hasLineNumbers())\n\t\t\treturn e.getBeginColumn();\n\t\telse\n\t\t\treturn -1;\n\t}\n\t\n\tpublic int getEndColumn()\n\t{\n\t\tif (hasLineNumbers())\n\t\t\treturn e.getEndColumn();\n\t\telse\n\t\t\treturn -1;\n\t}\n\t\n\tpublic int getBeginLine()\n\t{\n\t\tif (hasLineNumbers())\n\t\t\treturn e.getBeginLine();\n\t\telse\n\t\t\treturn -1;\n\t}\n\t\n\tpublic int getEndLine()\n\t{\n\t\tif (hasLineNumbers())\n\t\t\treturn e.getEndLine();\n\t\telse\n\t\t\treturn -1;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/PrismLanguageTranslator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.ByteArrayInputStream;\nimport java.io.ByteArrayOutputStream;\nimport java.io.File;\nimport java.io.FileInputStream;\nimport java.io.FileNotFoundException;\nimport java.io.InputStream;\nimport java.io.PrintStream;\nimport java.io.UnsupportedEncodingException;\n\n/**\n * Base class for classes that convert to PRISM language models from other languages.\n */\npublic abstract class PrismLanguageTranslator\n{\n\t/**\n\t * Get a name associated with the language to be translated from.\n\t */\n\tpublic abstract String getName();\n\t\n\t/**\n\t * Load a model to be translated from an input stream.\n\t */\n\tpublic abstract void load(InputStream in) throws PrismException;\n\t\n\t/**\n\t * Load a model to be translated from a string.\n\t */\n\tpublic void load(String modelString) throws PrismException\n\t{\n\t\tload(new ByteArrayInputStream(modelString.getBytes()));\n\t}\n\t\n\t/**\n\t * Load a model to be translated from a file.\n\t */\n\tpublic void load(File file) throws PrismException\n\t{\n\t\tFileInputStream in;\n\t\ttry {\n\t\t\tin = new FileInputStream(file);\n\t\t} catch (FileNotFoundException e) {\n\t\t\tthrow new PrismException(\"File \\\"\" + file.getPath() + \"\\\" not found\");\n\t\t}\n\t\tload(in);\n\t}\n\t\n\t/**\n\t * Translate the loaded model to a PRISM language model and write it to an output stream.\n\t */\n\tpublic abstract void translate(PrintStream out) throws PrismException;\n\t\n\t/**\n\t * Translate the loaded model to a PRISM language model and return it as a string.\n\t */\n\tpublic String translateToString() throws PrismException\n\t{\n\t\tByteArrayOutputStream os = new ByteArrayOutputStream();\n\t\tPrintStream out = new PrintStream(os);\n\t\ttranslate(out);\n\t\ttry {\n\t\t\treturn os.toString(\"UTF-8\");\n\t\t} catch (UnsupportedEncodingException e) {\n\t\t\tthrow new PrismException(\"Error translating output stream to string: \" + e.getMessage());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PrismLibrary.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2026-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\n/**\n * Interface for libraries that can be loaded and used by PRISM.\n * Currently, this is mainly used to provide a clean way for\n * native code to be detached from the main Prism class.\n */\npublic interface PrismLibrary\n{\n    /**\n     * Initialise the library.\n     * @param prism The main Prism object\n     */\n    void initialise(Prism prism) throws PrismException;\n\n    /**\n     * Set the main log for the library to use.\n     * @param mainLog The log\n     */\n    void setMainLog(PrismLog mainLog) throws PrismException;\n\n    /**\n     * Notify the library of changes to PRISM settings.\n     * @param settings The new settings\n     */\n    void notifySettings(PrismSettings settings);\n\n    /**\n     * Close down the library, tidying up any resources.\n     * @param check Do additional checks to make sure close down was clean?\n     */\n    void closeDown(boolean check);\n}\n"
  },
  {
    "path": "prism/src/prism/PrismLog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.Closeable;\n\n/**\n * Base class for PRISM logs: PrintStream-like objects which can write messages, warnings, etc.\n *\n * . A log is an output stream to which PRISM can write messages, warnings, etc.\n * <br>\n * The log also has a verbosity level, which determines what messages will be printed. The verbosity level can be changed at any time.\n * <br>\n * The log also keeps track of the number of warnings that have been printed, so that this can be queried at the end of computation and the user informed if there were any warnings.\n */\npublic abstract class PrismLog implements Closeable, AutoCloseable\n{\n\t// Verbosity settings + log state\n\n\t/** Specifies that only more important messages should be printed */\n\tpublic static final int VL_DEFAULT = 0;\n\t/** Specifies that the output should be more verbose */\n\tpublic static final int VL_HIGH = 1;\n\t/** Specifies that all messages should be printed */\n\tpublic static final int VL_ALL = 2;\n\n\t/** Verbosity level of this log */\n\tprotected int verbosityLevel = VL_DEFAULT;\n\n\t/** Number of warnings printed so far */\n\tprotected int numberOfWarnings = 0;\n\n\t// Setters\n\n\t/**\n\t * Changes the verbosity level of this log. The verbosity level determines what messages will be printed.\n\t * @param verbosityLevel Should be one of {@link #VL_DEFAULT}, {@link #VL_HIGH} or {@link #VL_ALL}.\n\t */\n\tpublic void setVerbosityLevel(int verbosityLevel)\n\t{\n\t\tthis.verbosityLevel = verbosityLevel;\n\t}\n\n\t/**\n\t * Sets the counter of warnings printed to 0.\n\t */\n\tpublic void resetNumberOfWarnings()\n\t{\n\t\tthis.numberOfWarnings = 0;\n\t}\n\n\t// Getters\n\n\t/**\n\t * Returns the verbosity level of this log. The verbosity level determines what messages will be printed.\n\t */\n\tpublic int getVerbosityLevel()\n\t{\n\t\treturn verbosityLevel;\n\t}\n\n\t/**\n\t * Returns the number of warnings that have been printed since the beginning\n\t * or since the last reset of the number of warnings.\n\t */\n\tpublic int getNumberOfWarnings()\n\t{\n\t\treturn this.numberOfWarnings;\n\t}\n\n\t// Core log methods to be implemented by subclasses\n\n\t/**\n\t * Returns true if this log is ready to be written to, and false otherwise.\n\t */\n\tpublic abstract boolean ready();\n\n\t/**\n\t * For a log with a native implementation, returns the underlying file pointer,\n\t * cast to a long (or 0 if the log is not ready). Returns -1 for non-native logs.\n\t */\n\tpublic long getFilePointer()\n\t{\n\t\t// Default implementation assumes non-native log\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Flushes this log, ensuring that all buffered output is output.\n\t */\n\tpublic abstract void flush();\n\n\t@Override\n\tpublic abstract void close();\n\n\t/**\n\t * Prints a Boolean value.\n\t */\n\tpublic abstract void print(boolean b);\n\t/**\n\t * Prints a character.\n\t */\n\tpublic abstract void print(char c);\n\n\t/**\n\t * Prints a double-precision floating point number.\n\t */\n\tpublic abstract void print(double d);\n\n\t/**\n\t * Prints a single-precision floating point number.\n\t */\n\tpublic abstract void print(float f);\n\n\t/**\n\t * Prints an integer.\n\t */\n\tpublic abstract void print(int i);\n\n\t/**\n\t * Prints a long integer.\n\t */\n\tpublic abstract void print(long l);\n\n\t/**\n\t * Prints an object.\n\t */\n\tpublic abstract void print(Object obj);\n\n\t/**\n\t * Prints a string.\n\t */\n\tpublic abstract void print(String s);\n\n\t/**\n\t * Prints a newline character.\n\t */\n\tpublic abstract void println();\n\n\t// Additional print methods (other objects)\n\n\t/**\n\t * Prints a double array in a human-readable format, e.g. \"[1.0, 2.0, 3.0]\".\n\t */\n\tpublic void print(double arr[])\n\t{\n\t\tint i, n = arr.length;\n\t\tprint(\"[\");\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tprint(i > 0 ? \", \" : \"\");\n\t\t\tprint(arr[i]);\n\t\t}\n\t\tprint(\"]\");\n\t}\n\n\t/**\n\t * Prints an integer array in a human-readable format, e.g. \"[1, 2, 3]\".\n\t */\n\tpublic void print(int arr[])\n\t{\n\t\tint i, n = arr.length;\n\t\tprint(\"[\");\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tprint(i > 0 ? \", \" : \"\");\n\t\t\tprint(arr[i]);\n\t\t}\n\t\tprint(\"]\");\n\t}\n\n\t// Additional print methods (checking verbosity level)\n\n\t/**\n\t * Prints out the value of {@code b} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(boolean b, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(b);\n\t}\n\n\t/**\n\t * Prints out the value of {@code c} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(char c, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(c);\n\t}\n\n\t/**\n\t * Prints out the value of {@code d} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(double d, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(d);\n\t}\n\n\t/**\n\t * Prints out the value of {@code f} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(float f, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(f);\n\t}\n\n\t/**\n\t * Prints out the value of {@code i} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(int i, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(i);\n\t}\n\n\t/**\n\t * Prints out the value of {@code l} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(long l, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(l);\n\t}\n\n\t/**\n\t * Prints out the value of {@code obj} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(Object obj, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(obj);\n\t}\n\n\t/**\n\t * Prints out {@code s} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(String s, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(s);\n\t}\n\n\t/**\n\t * Prints out the content  of {@code arr} if the log's verbosity level is at least {@code level}\n\t */\n\tpublic void print(double[] arr, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprint(arr);\n\t}\n\n\t// Additional print methods (println)\n\n\t/**\n\t * Prints a Boolean value followed by a newline character.\n\t */\n\tpublic void println(boolean b)\n\t{\n\t\tprint(b);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints a character followed by a newline character.\n\t */\n\tpublic void println(char c)\n\t{\n\t\tprint(c);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints a double-precision floating point number followed by a newline character.\n\t */\n\tpublic void println(double d)\n\t{\n\t\tprint(d);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints a single-precision floating point number followed by a newline character.\n\t */\n\tpublic void println(float f)\n\t{\n\t\tprint(f);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints an integer followed by a newline character.\n\t */\n\tpublic void println(int i)\n\t{\n\t\tprint(i);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints a long integer followed by a newline character.\n\t */\n\tpublic void println(long l)\n\t{\n\t\tprint(l);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints an object followed by a newline character.\n\t */\n\tpublic void println(Object o)\n\t{\n\t\tprint(o);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints a string followed by a newline character.\n\t */\n\tpublic void println(String s)\n\t{\n\t\tprint(s);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints a double array followed by a newline character.\n\t */\n\tpublic void println(double arr[])\n\t{\n\t\tprint(arr);\n\t\tprintln();\n\t}\n\n\t/**\n\t * Prints an integer array followed by a newline character.\n\t */\n\tpublic void println(int arr[])\n\t{\n\t\tprint(arr);\n\t\tprintln();\n\t}\n\n\t// Additional print methods (println, checking verbosity level)\n\n\t/**\n\t * Prints out the value of {@code b} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(boolean b, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(b);\n\t}\n\n\t/**\n\t * Prints out the value of {@code c} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(char c, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(c);\n\t}\n\n\t/**\n\t * Prints out the value of {@code d} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(double d, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(d);\n\t}\n\n\t/**\n\t * Prints out the value of {@code f} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(float f, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(f);\n\t}\n\n\t/**\n\t * Prints out the value of {@code i} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(int i, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(i);\n\t}\n\n\t/**\n\t * Prints out the value of {@code l} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(long l, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(l);\n\t}\n\n\t/**\n\t * Prints out the value of {@code o} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(Object o, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(o);\n\t}\n\n\t/**\n\t * Prints out {@code s} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(String s, int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(s);\n\t}\n\n\t/**\n\t * Prints out the content of {@code arr} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(double arr[], int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(arr);\n\t}\n\n\t/**\n\t * Prints out the content of {@code arr} followed by a newline character, provided that the log's verbosity level is at least {@code level}\n\t */\n\tpublic void println(int arr[], int level)\n\t{\n\t\tif (level <= this.verbosityLevel)\n\t\t\tprintln(arr);\n\t}\n\n\t// Other print methods\n\n\t/**\n\t * Prints a separator between sections of log output.\n\t */\n\tpublic void printSeparator()\n\t{\n\t\tprintln(\"\\n---------------------------------------------------------------------\");\n\t}\n\t\n\t/**\n\t * Prints a warning message {@code s}, preceded by \"\\nWarning: \" and followed by a newline character.\n\t * <br>\n\t * Also increases {@link #numberOfWarnings} by one. This variable can then be\n\t * queried using {@link #getNumberOfWarnings()} at the end of computation\n\t * and the user can be appropriately informed that there were warnings generated.\n\t * @param s The warning message.\n\t */\n\tpublic void printWarning(String s)\n\t{\n\t\tprintln(\"\\nWarning: \" + s);\n\t\tthis.numberOfWarnings++;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/PrismLogWrapper.java",
    "content": "package prism;\n\n/**\n * Class providing a wrapper around an existing PrismLog object.\n * All method calls are passed through to the wrapped log,\n * except for {@link #close()}, so that this log can safely be closed\n * without affecting the wrapped log. This makes it easy to\n * provide temporary, close-able access to a log.\n */\npublic class PrismLogWrapper extends PrismLog\n{\n    /** The log being \"wrappepd\" */\n    protected PrismLog log;\n\n    /**\n     * Create a new PrismLogWrapper object, wrapping the provided log.\n     * @param log The log to wrap\n     */\n    public PrismLogWrapper(PrismLog log)\n    {\n        this.log = log;\n    }\n\n    // Methods to implement PrismLog\n\n    @Override\n    public boolean ready()\n    {\n        return log.ready();\n    }\n\n    @Override\n    public long getFilePointer()\n    {\n        return log.getFilePointer();\n    }\n\n    @Override\n    public void flush()\n    {\n        log.flush();\n    }\n\n    @Override\n    public void close()\n    {\n        // Flush the wrapped log but do not close it\n        flush();\n    }\n\n    @Override\n    public void print(boolean b)\n    {\n        log.print(b);\n    }\n\n    @Override\n    public void print(char c)\n    {\n        log.print(c);\n    }\n\n    @Override\n    public void print(double d)\n    {\n        log.print(d);\n    }\n\n    @Override\n    public void print(float f)\n    {\n        log.print(f);\n    }\n\n    @Override\n    public void print(int i)\n    {\n        log.print(i);\n    }\n\n    @Override\n    public void print(long l)\n    {\n        log.print(l);\n    }\n\n    @Override\n    public void print(Object obj)\n    {\n        log.print(obj);\n    }\n\n    @Override\n    public void print(String s)\n    {\n        log.print(s);\n    }\n\n    @Override\n    public void println()\n    {\n        log.println();\n    }\n}\n"
  },
  {
    "path": "prism/src/prism/PrismModelListener.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\npublic interface PrismModelListener\n{\n\tpublic void notifyModelBuildSuccessful();\n\tpublic void notifyModelBuildFailed(PrismException e);\n}\n"
  },
  {
    "path": "prism/src/prism/PrismNG.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de (TU Dresden)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.lang.reflect.InvocationTargetException;\nimport java.lang.reflect.Method;\nimport java.util.Map;\nimport java.util.Map.Entry;\n\nimport com.martiansoftware.nailgun.NGContext;\n\n/**\n * Entry point for Nailgun.\n */\npublic class PrismNG\n{\n\t/** The current NailGun context */\n\tprivate static NGContext currentNailGunContext = null;\n\n\t/**\n\t * The name of the environment variable that can be used\n\t * to override the default main class (PrismCL).\n\t */\n\tprivate final static String envNameNGMainClass = \"NG_MAINCLASS\";\n\n\t/**\n\t * This method is called on the Nailgun server to start a new PRISM\n\t * command-line instance to serve as the counterpart for a client invocation.\n\t * <br/>\n\t * This method is synchronized to ensure that there can only be a single\n\t * running instance of PRISM in the Nailgun server VM.\n\t * <br/>\n\t * Sets the working directory to that of the client.\n\t * <br/>\n\t * If the environment variable NG_MAINCLASS is defined,\n\t * the {@code main} method of that class is used instead of\n\t * the default {@code PrismCL.main()}.\n\t */\n\tpublic synchronized static void nailMain(NGContext context) throws InterruptedException\n\t{\n\t\tcurrentNailGunContext = context;\n\t\ttry {\n\t\t\tPrism.setWorkingDirectory(context.getWorkingDirectory());\n\t\t} catch (PrismException ex) {\n\t\t\tSystem.err.println(\"Nailgun: \" + ex.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\n\t\tString ngMainClass = null;\n\t\ttry {\n\t\t\tngMainClass = System.getenv(envNameNGMainClass);\n\t\t} catch (SecurityException e) {\n\t\t\t// ignore environment variable, proceed with default PRISM invocation\n\t\t}\n\n\t\tif (ngMainClass == null) {\n\t\t\t// default: start a PRISM command-line instance\n\t\t\tPrismCL.main(context.getArgs());\n\t\t} else {\n\t\t\tClass<?> clazz = null;\n\t\t\ttry {\n\t\t\t\tclazz = context.getClass().getClassLoader().loadClass(ngMainClass);\n\t\t\t} catch (ClassNotFoundException e) {\n\t\t\t\tSystem.err.println(\"PrismNG: Can not find class '\" + ngMainClass + \"' (from environment variable \" + envNameNGMainClass + \")\");\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\n\t\t\tString[] args = context.getArgs();\n\t\t\tMethod m = null;\n\t\t\ttry {\n\t\t\t\tm = clazz.getMethod(\"main\", args.getClass());\n\t\t\t} catch (NoSuchMethodException e) {\n\t\t\t\tSystem.err.println(\"PrismNG: Class '\" + ngMainClass + \"' (from environment variable \" + envNameNGMainClass + \") does not have a suitable main method\");\n\t\t\t\tSystem.exit(1);\n\t\t\t} catch (SecurityException e) {\n\t\t\t\tSystem.err.println(\"PrismNG: Security exception trying to load main method of class '\" + ngMainClass + \"' (from environment variable \" + envNameNGMainClass + \"): \" + e.getMessage());\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tm.invoke(null, new Object[]{args});\n\t\t\t} catch (IllegalAccessException | IllegalArgumentException | InvocationTargetException e) {\n\t\t\t\tSystem.err.println(\"PrismNG: Exception trying to invoke main method of class '\" + ngMainClass + \"' (from environment variable \" + envNameNGMainClass + \"): \" + e.getMessage());\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Modifies the environment of the ProcessBuilder by adding the environment\n\t * variables passed by the Nailgun client.\n\t * <br/>\n\t * If we are not running in a Nailgun context, this is a no-op.\n\t * */\n\tpublic static void setupChildProcessEnvironment(ProcessBuilder builder)\n\t{\n\t\tif (currentNailGunContext == null)\n\t\t\treturn;\n\n\t\tMap<String, String> env = builder.environment();\n\t\tfor (Entry<Object, Object> entry : currentNailGunContext.getEnv().entrySet()) {\n\t\t\tif (entry.getKey() instanceof String && entry.getValue() instanceof String) {\n\t\t\t\tenv.put((String) entry.getKey(), (String) entry.getValue());\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PrismNative.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"PrismNative.h\"\n#include <cstdio>\n#include <cstring>\n#include <limits>\n#include <locale.h>\n#include <unistd.h>\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n// Global ref to prism class/object\nEXPORT jclass prism_cls = NULL;\nEXPORT jobject prism_obj = NULL;\n\n// CUDD manager: stored so that it doesn't have to be passed to every CUDD/dd call.\n// Set via (JNI) PN_SetCUDDManager, cached here and accessible across all native code.\nDdManager *ddman;\n\n// error messages\nstatic char error_message[MAX_ERR_STRING_LEN];\n\n// logs\n// global refs to log classes\nstatic jclass main_log_cls = NULL;\n// global refs to log objects\nstatic jobject main_log_obj = NULL;\n// method ids for print method in logs\nstatic jmethodID main_log_mid = NULL;\nstatic jmethodID main_log_warn = NULL;\n\n// Export stuff:\n\nEXPORT int export_type;\nEXPORT FILE *export_file;\nEXPORT JNIEnv *export_env;\nstatic bool exportIterations = false;\n// adversary export mode\nEXPORT int export_adv;\n// adversary export filename\nEXPORT const char *export_adv_filename;\n// export iterations filename\nEXPORT const char *export_iterations_filename = \"iterations.html\";\n\n// Options:\n// numerical method stuff\nEXPORT int lin_eq_method;\nEXPORT double lin_eq_method_param;\nEXPORT int term_crit;\nEXPORT double term_crit_param;\nEXPORT int max_iters;\nEXPORT int export_model_precision;\n// use \"compact modified\" sparse matrix storage?\nEXPORT bool compact;\n// sparse bits info\nEXPORT int sb_max_mem;\nEXPORT int num_sb_levels;\n// hybrid sor info\nEXPORT int sor_max_mem;\nEXPORT int num_sor_levels;\n// use steady-state detection for transient computation?\nEXPORT bool do_ss_detect;\n\n// details from numerical computation which may be queried\nEXPORT double last_error_bound;\n\n//------------------------------------------------------------------------------\n// Prism object\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetPrism(JNIEnv *env, jclass cls, jobject prism)\n{\n\t// if prism has been set previously, we need to delete existing global refs first\n\tif (prism_obj != NULL) {\n\t\tenv->DeleteGlobalRef(prism_cls);\n\t\tprism_cls = NULL;\n\t\tenv->DeleteGlobalRef(prism_obj);\n\t\tprism_obj = NULL;\n\t}\n\t\n\t// make a global reference to the object\n\tprism_obj = env->NewGlobalRef(prism);\n\t// get the class and make a global reference to it\n\tprism_cls = (jclass)env->NewGlobalRef(env->GetObjectClass(prism_obj));\n\t\n\t// We should also set the locale, to ensure consistent display of numerical values\n\t// (e.g. 0.5 not 0,5). This seems as good a place as any to do it.\n\tsetlocale(LC_NUMERIC, \"C\");\n}\n\n//------------------------------------------------------------------------------\n// cudd manager\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetCUDDManager(JNIEnv *env, jclass cls, jlong __jlongpointer ddm)\n{\n\tddman = jlong_to_DdManager(ddm);\n}\n\n//------------------------------------------------------------------------------\n// logs\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetMainLog(JNIEnv *env, jclass cls, jobject log)\n{\n\t// if main log has been set previously, we need to delete existing global refs first\n\tif (main_log_obj != NULL) {\n\t\tenv->DeleteGlobalRef(main_log_cls);\n\t\tmain_log_cls = NULL;\n\t\tenv->DeleteGlobalRef(main_log_obj);\n\t\tmain_log_obj = NULL;\n\t}\n\t\n\t// make a global reference to the log object\n\tmain_log_obj = env->NewGlobalRef(log);\n\t// get the log class and make a global reference to it\n\tmain_log_cls = (jclass)env->NewGlobalRef(env->GetObjectClass(main_log_obj));\n\t// get the method id for the print method\n\tmain_log_mid = env->GetMethodID(main_log_cls, \"print\", \"(Ljava/lang/String;)V\");\n    main_log_warn = env->GetMethodID(main_log_cls, \"printWarning\", \"(Ljava/lang/String;)V\");\n}\n\n//------------------------------------------------------------------------------\n\nvoid PN_PrintToMainLog(JNIEnv *env, const char *str, ...)\n{\n\tva_list argptr;\n\tchar full_string[MAX_LOG_STRING_LEN];\n\t\n\tva_start(argptr, str);\n\tvsnprintf(full_string, MAX_LOG_STRING_LEN, str, argptr);\n\tva_end(argptr);\n\t\n\tif (env)\n\t\tenv->CallVoidMethod(main_log_obj, main_log_mid, env->NewStringUTF(full_string));\n\telse\n\t\tprintf(\"%s\", full_string);\n}\n\n//------------------------------------------------------------------------------\n\nvoid PN_PrintWarningToMainLog(JNIEnv *env, const char *str, ...)\n{\n\tva_list argptr;\n\tchar full_string[MAX_LOG_STRING_LEN];\n\t\n\tva_start(argptr, str);\n\tvsnprintf(full_string, MAX_LOG_STRING_LEN, str, argptr);\n\tva_end(argptr);\n\t\n\tif (env)\n\t\tenv->CallVoidMethod(main_log_obj, main_log_warn, env->NewStringUTF(full_string));\n\telse\n\t\tprintf(\"\\nWarning: %s\\n\", full_string);\n}\n\n//------------------------------------------------------------------------------\n\n// Print formatted memory info to main log\n\nvoid PN_PrintMemoryToMainLog(JNIEnv *env, const char *before, double mem, const char *after)\n{\n\tchar full_string[MAX_LOG_STRING_LEN];\n\t\n\tif (mem > 1048576)\n\t\tsnprintf(full_string, MAX_LOG_STRING_LEN, \"%s%.1f GB%s\", before, mem/1048576.0, after);\n\telse if (mem > 1024)\n\t\tsnprintf(full_string, MAX_LOG_STRING_LEN, \"%s%.1f MB%s\", before, mem/1024.0, after);\n\telse\n\t\tsnprintf(full_string, MAX_LOG_STRING_LEN, \"%s%.1f KB%s\", before, mem, after);\n\t\n\tif (env) {\n\t\tenv->CallVoidMethod(main_log_obj, main_log_mid, env->NewStringUTF(full_string));\n\t}\n\telse {\n\t\tprintf(\"%s\", full_string);\n\t}\n}\n\n//------------------------------------------------------------------------------\n// error message handling\n//------------------------------------------------------------------------------\n\nvoid PN_SetErrorMessage(const char *str, ...)\n{\n\tva_list argptr;\n\n\tva_start(argptr, str);\n\tvsnprintf(error_message, MAX_ERR_STRING_LEN, str, argptr);\n\tva_end(argptr);\n}\n\nchar *PN_GetErrorMessage()\n{\n\treturn error_message;\n}\n\nJNIEXPORT jstring JNICALL Java_prism_PrismNative_PN_1GetErrorMessage(JNIEnv *env, jclass cls)\n{\n\treturn env->NewStringUTF(error_message);\n}\n\n//------------------------------------------------------------------------------\n// Export stuff\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetExportIterations(JNIEnv *env, jclass cls, jboolean value)\n{\n\texportIterations = value;\n}\n\nbool PN_GetFlagExportIterations()\n{\n\treturn exportIterations;\n}\n\n//------------------------------------------------------------------------------\n// Set methods for options in native code\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetCompact(JNIEnv *env, jclass cls, jboolean b)\n{\n\tcompact = b;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetLinEqMethod(JNIEnv *env, jclass cls, jint i)\n{\n\tlin_eq_method = i;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetLinEqMethodParam(JNIEnv *env, jclass cls, jdouble d)\n{\n\tlin_eq_method_param = d;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetTermCrit(JNIEnv *env, jclass cls, jint i)\n{\n\tterm_crit = i;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetTermCritParam(JNIEnv *env, jclass cls, jdouble d)\n{\n\tterm_crit_param = d;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetMaxIters(JNIEnv *env, jclass cls, jint i)\n{\n\tmax_iters = i;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetExportModelPrecision(JNIEnv *env, jclass cls, jint prec)\n{\n\texport_model_precision = prec;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetSBMaxMem(JNIEnv *env, jclass cls, jint sbmm)\n{\n\tsb_max_mem = sbmm;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetNumSBLevels(JNIEnv *env, jclass cls, jint nsbl)\n{\n\tnum_sb_levels = nsbl;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetSORMaxMem(JNIEnv *env, jclass cls, jint smm)\n{\n\tsor_max_mem = smm;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetNumSORLevels(JNIEnv *env, jclass cls, jint nsl)\n{\n\tnum_sor_levels = nsl;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetDoSSDetect(JNIEnv *env, jclass cls, jboolean b)\n{\n\tdo_ss_detect = b;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetExportAdv(JNIEnv *env, jclass cls, jint i)\n{\n\texport_adv = i;\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetExportAdvFilename(JNIEnv *env, jclass cls, jstring fn)\n{\n\tif (fn) {\n\t\texport_adv_filename = env->GetStringUTFChars(fn, 0);\n\t\t// This never gets released. Oops.\n\t} else {\n\t\texport_adv_filename = NULL;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetDefaultExportIterationsFilename(JNIEnv *env, jclass cls, jstring fn)\n{\n\tif (fn) {\n\t\texport_iterations_filename = env->GetStringUTFChars(fn, 0);\n\t\t// This never gets released. Oops.\n\t} else {\n\t\texport_iterations_filename = NULL;\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_prism_PrismNative_PN_1SetWorkingDirectory(JNIEnv *env, jclass cls, jstring dn) {\n\tint rv;\n\tconst char* dirname = env->GetStringUTFChars(dn, 0);\n\trv = chdir(dirname);\n\tenv->ReleaseStringUTFChars(dn, dirname);\n\treturn rv;\n}\n\n//------------------------------------------------------------------------------\n// export stuff\n//------------------------------------------------------------------------------\n\n// store export info globally\n// returns 0 on failure, 1 otherwise\n\nint store_export_info(int type, jstring fn, JNIEnv *env)\n{\n\texport_type = type;\n\tif (fn) {\n\t\tconst char *filename = env->GetStringUTFChars(fn, 0);\n\t\texport_file = fopen(filename, \"w\");\n\t\tif (!export_file) {\n\t\t\tenv->ReleaseStringUTFChars(fn, filename);\n\t\t\treturn 0;\n\t\t}\n\t\tenv->ReleaseStringUTFChars(fn, filename);\n\t} else {\n\t\texport_file = NULL;\n\t}\n\texport_env = env;\n\treturn 1;\n}\n\n//------------------------------------------------------------------------------\n\n// export string (either to file or main log)\n\nvoid export_string(const char *str, ...)\n{\n\tva_list argptr;\n\tchar full_string[MAX_LOG_STRING_LEN];\n\t\n\tva_start(argptr, str);\n\tvsnprintf(full_string, MAX_LOG_STRING_LEN, str, argptr);\n\tva_end(argptr);\n\t\n\tif (export_file) {\n\t\tfprintf(export_file, \"%s\", full_string);\n\t} else {\n\t\tPN_PrintToMainLog(export_env, \"%s\", full_string);\n\t}\n}\n\n//------------------------------------------------------------------------------\n// Some miscellaneous native methods\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_prism_PrismNative_PN_1GetStdout(JNIEnv *env, jclass cls)\n{\n#ifdef _WIN32\n\tsetvbuf(stdout, NULL, _IONBF, 0);\n#else\n\tsetvbuf(stdout, NULL, _IOLBF, 1024);\n#endif\n\treturn ptr_to_jlong(stdout);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_prism_PrismNative_PN_1OpenFile(JNIEnv *env, jclass cls, jstring filename)\n{\n\tconst char *str = env->GetStringUTFChars(filename, 0);\n\tFILE *fp = fopen(str, \"w\");\n\tenv->ReleaseStringUTFChars(filename, str);\n\treturn ptr_to_jlong(fp);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_prism_PrismNative_PN_1OpenFileAppend(JNIEnv *env, jclass cls, jstring filename)\n{\n\tconst char *str = env->GetStringUTFChars(filename, 0);\n\tFILE *fp = fopen(str, \"a\");\n\tenv->ReleaseStringUTFChars(filename, str);\n\treturn ptr_to_jlong(fp);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1PrintToFile(JNIEnv *env, jclass cls, jlong __jlongpointer fp, jstring s)\n{\n\tconst char *str = env->GetStringUTFChars(s, 0);\n\t// note: use fwrite not fprintf here because there is no formatting to do\n\t// (and in fact formatting has probably already been done so mustn't do it again,\n\t//  especially if we want to print % characters reliably)\n\tfwrite(str, sizeof(char), strlen(str), jlong_to_FILE(fp));\n\t//fprintf(jlong_to_FILE(fp), str);\n\tenv->ReleaseStringUTFChars(s, str);\n}\n\n//------------------------------------------------------------------------------\n\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1FlushFile(JNIEnv *env, jclass cls, jlong __jlongpointer fp)\n{\n\tfflush(jlong_to_FILE(fp));\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1CloseFile(JNIEnv *env, jclass cls, jlong __jlongpointer fp)\n{\n\tfclose(jlong_to_FILE(fp));\n}\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1SetLastErrorBound(JNIEnv *env, jclass cls,jdouble d)\n{\n\tlast_error_bound = d;\n}\n\nJNIEXPORT jdouble JNICALL Java_prism_PrismNative_PN_1GetLastErrorBound(JNIEnv *env, jclass cls)\n{\n\treturn last_error_bound;\n}\n\n//------------------------------------------------------------------------------\n// tidy up\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_prism_PrismNative_PN_1FreeGlobalRefs(JNIEnv *env, jclass cls)\n{\n\t// delete all global references\n\tenv->DeleteGlobalRef(prism_cls);\n\tprism_cls = NULL;\n\tenv->DeleteGlobalRef(prism_obj);\n\tprism_obj = NULL;\n\tenv->DeleteGlobalRef(main_log_cls);\n\tmain_log_cls = NULL;\n\tenv->DeleteGlobalRef(main_log_obj);\n\tmain_log_obj = NULL;\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/prism/PrismNative.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport jdd.JDD;\n\n/**\n * Set methods to pass options to native code.\n * And a few utility methods, relying on native methods in the \"prism\" shared library.\n */ \npublic class PrismNative\n{\n\t// Load \"prism\" shared library\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t// Initialise/close down methods\n\t\n\tpublic static void initialise(Prism prism)\n\t{\n\t\tsetPrism(prism);\n\t\tsetCUDDManager();\n\t}\n\t\n\tpublic static void closeDown()\n\t{\n\t\t// Tidy up any JNI stuff\n\t\tPN_FreeGlobalRefs();\n\t}\n\n\t// tidy up in jni (free global references)\n\tprivate static native void PN_FreeGlobalRefs();\n\n\t// Prism object\n\t\n\t// Place to store Prism object for Java code\n\tprivate static Prism prism;\n\t// JNI method to set Prism object for native code\n\tprivate static native void PN_SetPrism(Prism prism);\n\t// Method to set Prism object both in Java and C++\n\tpublic static void setPrism(Prism prism)\n\t{\n\t\tPrismNative.prism = prism;\n\t\tPN_SetPrism(prism);\n\t}\n\n\t// cudd manager\n\n\t// jni method to set cudd manager for native code\n\tprivate static native void PN_SetCUDDManager(long ddm);\n\tpublic static void setCUDDManager()\n\t{\n\t\tPN_SetCUDDManager(JDD.GetCUDDManager());\n\t}\n\n\t// main log\n\n\t// place to store main log for java code\n\tprivate static PrismLog mainLog;\n\t// jni method to set main log for native code\n\tprivate static native void PN_SetMainLog(PrismLog log);\n\t// method to set main log both in java and c++\n\tpublic static void setMainLog(PrismLog log)\n\t{\n\t\tmainLog = log;\n\t\tPN_SetMainLog(log);\n\t}\n\n\t// Error message handling\n\tpublic static native String PN_GetErrorMessage();\n\n\tprivate static native void PN_SetExportIterations(boolean value);\n\tpublic static void SetExportIterations(boolean value)\n\t{\n\t\tPN_SetExportIterations(value);\n\t}\n\n\t// Options passing\n\t\n\tprivate static native void PN_SetCompact(boolean b);\n\tpublic static void setCompact(boolean b)\n\t{\n\t\tPN_SetCompact(b);\n\t}\n\n\tprivate static native void PN_SetLinEqMethod(int i);\n\tpublic static void setLinEqMethod(int i)\n\t{\n\t\tPN_SetLinEqMethod(i);\n\t}\n\t\n\tprivate static native void PN_SetLinEqMethodParam(double d);\n\tpublic static void setLinEqMethodParam(double d)\n\t{\n\t\tPN_SetLinEqMethodParam(d);\n\t}\n\t\n\tprivate static int termCrit;\n\tprivate static native void PN_SetTermCrit(int i);\n\tpublic static void setTermCrit(int i)\n\t{\n\t\tPN_SetTermCrit(i);\n\t\t// Cache locally too\n\t\ttermCrit = i;\n\t}\n\tpublic static int getTermCrit()\n\t{\n\t\treturn termCrit;\n\t}\n\t\n\tprivate static double termCritParam;\n\tprivate static native void PN_SetTermCritParam(double d);\n\tpublic static void setTermCritParam(double d)\n\t{\n\t\tPN_SetTermCritParam(d);\n\t\t// Cache locally too\n\t\ttermCritParam = d;\n\t}\n\tpublic static double getTermCritParam()\n\t{\n\t\treturn termCritParam;\n\t}\n\t\n\tprivate static native void PN_SetMaxIters(int i);\n\tpublic static void setMaxIters(int i)\n\t{\n\t\tPN_SetMaxIters(i);\n\t}\n\n\tprivate static native void PN_SetExportModelPrecision(int prec);\n\tpublic static void setExportModelPrecision(int prec)\n\t{\n\t\tif (prec < 1)\n\t\t\tthrow new IllegalArgumentException(\"Precision has to be >= 1; got \" + prec);\n\t\tPN_SetExportModelPrecision(prec);\n\t}\n\n\tprivate static native void PN_SetSBMaxMem(int i);\n\tpublic static void setSBMaxMem(int i)\n\t{\n\t\tPN_SetSBMaxMem(i);\n\t}\n\t\n\tprivate static native void PN_SetNumSBLevels(int i);\n\tpublic static void setNumSBLevels(int i)\n\t{\n\t\tPN_SetNumSBLevels(i);\n\t}\n\t\n\tprivate static native void PN_SetSORMaxMem(int i);\n\tpublic static void setSORMaxMem(int i)\n\t{\n\t\tPN_SetSORMaxMem(i);\n\t}\n\t\n\tprivate static native void PN_SetNumSORLevels(int i);\n\tpublic static void setNumSORLevels(int i)\n\t{\n\t\tPN_SetNumSORLevels(i);\n\t}\n\t\n\tprivate static native void PN_SetDoSSDetect(boolean b);\n\tpublic static void setDoSSDetect(boolean b)\n\t{\n\t\tPN_SetDoSSDetect(b);\n\t}\n\n\tprivate static native void PN_SetExportAdv(int i);\n\tpublic static void setExportAdv(int i)\n\t{\n\t\tPN_SetExportAdv(i);\n\t}\n\t\n\tprivate static native void PN_SetExportAdvFilename(String filename);\n\tpublic static void setExportAdvFilename(String filename)\n\t{\n\t\tPN_SetExportAdvFilename(filename);\n\t}\n\n\tprivate static native void PN_SetDefaultExportIterationsFilename(String filename);\n\tpublic static void setDefaultExportIterationsFilename(String filename)\n\t{\n\t\tPN_SetDefaultExportIterationsFilename(filename);\n\t}\n\n\tprivate static native int PN_SetWorkingDirectory(String dirname);\n\t/** Changes the current working directory. Returns 0 on success. */\n\tpublic static int setWorkingDirectory(String dirname) {\n\t\treturn PN_SetWorkingDirectory(dirname);\n\t}\n\t\n\t// Getting (or resetting) information about model checking\n\t\n\tpublic static void resetModelCheckingInfo()\n\t{\n\t\tPN_SetLastErrorBound(Double.POSITIVE_INFINITY);\n\t}\n\t\n\tprivate static native void PN_SetLastErrorBound(double d);\n\tprivate static native double PN_GetLastErrorBound();\n\tpublic static double getLastErrorBound()\n\t{\n\t\treturn PN_GetLastErrorBound();\n\t}\n\n\t// Some miscellaneous native methods\n\tpublic static native long PN_GetStdout();\n\tpublic static native long PN_OpenFile(String filename);\n\tpublic static native long PN_OpenFileAppend(String filename);\n\tpublic static native void PN_PrintToFile(long fp, String s);\n\tpublic static native void PN_FlushFile(long fp);\n\tpublic static native void PN_CloseFile(long fp);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/PrismNativeComponent.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2026-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\n/**\n * Base class for {@link PrismComponent}s that use native code.\n */\npublic class PrismNativeComponent extends PrismComponent\n{\n    /* Reference to the parent Prism instance. */\n    protected Prism prism;\n\n    public PrismNativeComponent(Prism prism) throws PrismException\n    {\n        super(prism);\n        this.prism = prism;\n        // Make sure PRISM is set up to use native code.\n        prism.useNative();\n    }\n}\n"
  },
  {
    "path": "prism/src/prism/PrismNativeLibrary.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2026-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\nimport java.nio.file.Path;\n\n/**\n * A {@code PrismLibrary} wrapper around native code in the \"prism\" shared library.\n */\npublic class PrismNativeLibrary implements PrismLibrary\n{\n    @Override\n    public void initialise(Prism prism) throws PrismException\n    {\n        Path workingDirectory = Prism.getWorkingDirectory();\n        if (workingDirectory != null) {\n            PrismNative.setWorkingDirectory(workingDirectory.toString());\n        }\n        PrismNative.initialise(prism);\n    }\n\n    @Override\n    public void setMainLog(PrismLog mainLog) throws PrismException\n    {\n        PrismNative.setMainLog(mainLog);\n    }\n\n    @Override\n    public void notifySettings(PrismSettings settings)\n    {\n        PrismNative.SetExportIterations(settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS));\n    }\n\n    @Override\n    public void closeDown(boolean check)\n    {\n        PrismNative.closeDown();\n    }\n}\n"
  },
  {
    "path": "prism/src/prism/PrismNotSupportedException.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * An exception indicating that a given feature is (currently) not supported,\n * e.g., a given combination of model type, engine and property.\n */\npublic class PrismNotSupportedException extends PrismException\n{\n\tpublic PrismNotSupportedException(String s)\n\t{\n\t\tsuper(s);\n\t}\n\t\n\t@Override\n\tpublic PrismNotSupportedException prepend(String prefix)\n\t{\n\t\treturn new PrismNotSupportedException(prefix + getMessage());\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PrismPrintStreamLog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.PrintStream;\n\n/**\n * A {@link PrismFileLog} that passes all output to a PrintStream object.\n */\npublic class PrismPrintStreamLog extends PrismLog\n{\n\t/** PrintStream used for the log writing */\n\tprotected PrintStream logStream = null;\n\n\t/**\n\t * Create an as-yet unconfigured {@link PrismPrintStreamLog}. Mainly for subclasses.\n\t */\n\tpublic PrismPrintStreamLog()\n\t{\n\t}\n\n\t/**\n\t * Create a {@link PrismPrintStreamLog} which will write to the given PrintStream.\n\t */\n\tpublic PrismPrintStreamLog(PrintStream out)\n\t{\n\t\tsetPrintStream(out);\n\t}\n\n\t/**\n\t * Set the underlying PrintStream.\n\t */\n\tpublic void setPrintStream(PrintStream out)\n\t{\n\t\tthis.logStream = out;\n\t}\n\n\t/**\n\t * Get the underlying PrintStream.\n\t */\n\tpublic PrintStream getPrintStream()\n\t{\n\t\treturn logStream;\n\t}\n\n\t// Methods to implement PrismLog\n\n\t@Override\n\tpublic boolean ready()\n\t{\n\t\treturn logStream != null;\n\t}\n\n\t@Override\n\tpublic void flush()\n\t{\n\t\tlogStream.flush();\n\t}\n\n\t@Override\n\tpublic void close()\n\t{\n\t\tif (logStream != null) {\n\t\t\tflush();\n\t\t\tif (logStream != System.out && logStream != System.err) {\n\t\t\t\tlogStream.close();\n\t\t\t}\n\t\t\tlogStream = null;\n\t\t}\n\t}\n\n\t@Override\n\tpublic void print(boolean b)\n\t{\n\t\tlogStream.print(b);\n\t}\n\n\t@Override\n\tpublic void print(char c)\n\t{\n\t\tlogStream.print(c);\n\t}\n\n\t@Override\n\tpublic void print(double d)\n\t{\n\t\tlogStream.print(d);\n\t}\n\n\t@Override\n\tpublic void print(float f)\n\t{\n\t\tlogStream.print(f);\n\t}\n\n\t@Override\n\tpublic void print(int i)\n\t{\n\t\tlogStream.print(i);\n\t}\n\n\t@Override\n\tpublic void print(long l)\n\t{\n\t\tlogStream.print(l);\n\t}\n\n\t@Override\n\tpublic void print(Object obj)\n\t{\n\t\tlogStream.print(obj);\n\t}\n\n\t@Override\n\tpublic void print(String s)\n\t{\n\t\tlogStream.print(s);\n\t}\n\n\t@Override\n\tpublic void println()\n\t{\n\t\tlogStream.println();\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PrismSettings.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.*;\nimport java.io.*;\nimport java.awt.*;\n\nimport javax.swing.*;\n\nimport common.iterable.Range;\nimport explicit.QuantAbstractRefine;\n\nimport java.util.regex.*;\n\nimport settings.*;\n\npublic class PrismSettings implements Observer\n{\n\t//Default Constants\n\tpublic static final String DEFAULT_STRING = \"\";\n\tpublic static final int DEFAULT_INT = 0;\n\tpublic static final double DEFAULT_DOUBLE = 0.0;\n\tpublic static final float DEFAULT_FLOAT = 0.0f;\n\tpublic static final long DEFAULT_LONG = 0l;\n\tpublic static final boolean DEFAULT_BOOLEAN = false;\n\tpublic static final Color DEFAULT_COLOUR = Color.white;\n\tpublic static final Font DEFAULT_FONT = new Font(\"monospaced\", Font.PLAIN, 12);\n\tpublic static final FontColorPair DEFAULT_FONT_COLOUR = new FontColorPair(new Font(\"monospaced\", Font.PLAIN, 12), Color.black);\n\tpublic static final File DEFAULT_FILE = null;\n\n\t//Type Constants\n\tpublic static final String STRING_TYPE = \"s\";\n\tpublic static final String INTEGER_TYPE = \"i\";\n\tpublic static final String FLOAT_TYPE = \"f\";\n\tpublic static final String DOUBLE_TYPE = \"d\";\n\tpublic static final String LONG_TYPE = \"l\";\n\tpublic static final String BOOLEAN_TYPE = \"b\";\n\tpublic static final String COLOUR_TYPE = \"c\";\n\t//public static final String FONT_TYPE = \"fo\";\t  //remove for now cos we don't have a setting for this yet\n\tpublic static final String CHOICE_TYPE = \"ch\";\n\tpublic static final String FONT_COLOUR_TYPE = \"fct\";\n\tpublic static final String FILE_TYPE = \"fi\";\n\n\t// Constraint constants\n\tpublic static final Range RANGE_EXPORT_DOUBLE_PRECISION = Range.closed(1, 17);\n\tpublic static final int DEFAULT_EXPORT_MODEL_PRECISION = 16;\n\n\t//Property Constant Keys\n\t//======================\n\t\n\t//PRISM\n\tpublic static final\tString PRISM_ENGINE\t\t\t\t\t\t\t= \"prism.engine\";\n\tpublic static final\tString PRISM_HEURISTIC\t\t\t\t\t\t= \"prism.heuristic\";\n\tpublic static final\tString PRISM_VERBOSE\t\t\t\t\t\t= \"prism.verbose\";\n\tpublic static final\tString PRISM_FAIRNESS\t\t\t\t\t\t= \"prism.fairness\";\n\tpublic static final\tString PRISM_PRECOMPUTATION\t\t\t\t\t= \"prism.precomputation\";\n\tpublic static final\tString PRISM_PROB0\t\t\t\t\t\t\t= \"prism.prob0\";\n\tpublic static final\tString PRISM_PROB1\t\t\t\t\t\t\t= \"prism.prob1\";\n\tpublic static final\tString PRISM_PRE_REL\t\t\t\t\t= \"prism.preRel\";\n\tpublic static final\tString PRISM_FIX_DEADLOCKS\t\t\t\t\t= \"prism.fixDeadlocks\";\n\tpublic static final\tString PRISM_DO_PROB_CHECKS\t\t\t\t\t= \"prism.doProbChecks\";\n\tpublic static final\tString PRISM_SUM_ROUND_OFF\t\t\t\t\t= \"prism.sumRoundOff\";\n\tpublic static final\tString PRISM_COMPACT\t\t\t\t\t\t= \"prism.compact\";\n\tpublic static final\tString PRISM_LIN_EQ_METHOD\t\t\t\t\t= \"prism.linEqMethod\";//\"prism.iterativeMethod\";\n\tpublic static final\tString PRISM_LIN_EQ_METHOD_PARAM\t\t\t= \"prism.linEqMethodParam\";//\"prism.overRelaxation\";\n\tpublic static final String PRISM_TOPOLOGICAL_VI\t\t\t\t\t= \"prism.topologicalVI\";\n\tpublic static final\tString PRISM_PMAX_QUOTIENT\t\t\t\t\t= \"prism.pmaxQuotient\";\n\tpublic static final\tString PRISM_INTERVAL_ITER\t\t\t\t\t= \"prism.intervalIter\";\n\tpublic static final\tString PRISM_INTERVAL_ITER_OPTIONS\t\t\t= \"prism.intervalIterOptions\";\n\tpublic static final\tString PRISM_MDP_SOLN_METHOD\t\t\t\t= \"prism.mdpSolnMethod\";\n\tpublic static final\tString PRISM_MDP_MULTI_SOLN_METHOD\t\t\t= \"prism.mdpMultiSolnMethod\";\n\tpublic static final\tString PRISM_IMDP_SOLN_METHOD\t\t\t\t= \"prism.imdpSolnMethod\";\n\tpublic static final\tString PRISM_TERM_CRIT\t\t\t\t\t\t= \"prism.termCrit\";//\"prism.termination\";\n\tpublic static final\tString PRISM_TERM_CRIT_PARAM\t\t\t\t= \"prism.termCritParam\";//\"prism.terminationEpsilon\";\n\tpublic static final\tString PRISM_MAX_ITERS\t\t\t\t\t\t= \"prism.maxIters\";//\"prism.maxIterations\";\n\tpublic static final String PRISM_EXPORT_ITERATIONS\t\t\t\t= \"prism.exportIterations\";\n\tpublic static final\tString PRISM_GRID_RESOLUTION\t\t\t\t= \"prism.gridResolution\";\n\tpublic static final String PRISM_EXPORT_MODEL_PRECISION         = \"prism.exportModelPrecision\";\n\tpublic static final String PRISM_EXPORT_MODEL_HEADERS           = \"prism.exportModelHeaders\";\n\n\tpublic static final\tString PRISM_CUDD_MAX_MEM\t\t\t\t\t= \"prism.cuddMaxMem\";\n\tpublic static final\tString PRISM_CUDD_EPSILON\t\t\t\t\t= \"prism.cuddEpsilon\";\n\tpublic static final\tString PRISM_DD_EXTRA_STATE_VARS\t\t\t\t= \"prism.ddExtraStateVars\";\n\tpublic static final\tString PRISM_DD_EXTRA_ACTION_VARS\t\t\t\t= \"prism.ddExtraActionVars\";\n\tpublic static final\tString PRISM_NUM_SB_LEVELS\t\t\t\t\t= \"prism.numSBLevels\";//\"prism.hybridNumLevels\";\n\tpublic static final\tString PRISM_SB_MAX_MEM\t\t\t\t\t\t= \"prism.SBMaxMem\";//\"prism.hybridMaxMemory\";\n\tpublic static final\tString PRISM_NUM_SOR_LEVELS\t\t\t\t\t= \"prism.numSORLevels\";//\"prism.hybridSORLevels\";\n\tpublic static final\tString PRISM_SOR_MAX_MEM\t\t\t\t\t= \"prism.SORMaxMem\";//\"prism.hybridSORMaxMemory\";\n\tpublic static final\tString PRISM_DO_SS_DETECTION\t\t\t\t= \"prism.doSSDetect\";\n\tpublic static final\tString PRISM_EXTRA_DD_INFO\t\t\t\t\t= \"prism.extraDDInfo\";\n\tpublic static final\tString PRISM_EXTRA_REACH_INFO\t\t\t\t= \"prism.extraReachInfo\";\n\tpublic static final String PRISM_SCC_METHOD\t\t\t\t\t\t= \"prism.sccMethod\";\n\tpublic static final String PRISM_SYMM_RED_PARAMS\t\t\t\t\t= \"prism.symmRedParams\";\n\tpublic static final\tString PRISM_EXACT_ENABLED\t\t\t\t\t= \"prism.exact.enabled\";\n\tpublic static final String PRISM_PTA_METHOD\t\t\t\t\t= \"prism.ptaMethod\";\n\tpublic static final String PRISM_TRANSIENT_METHOD\t\t\t\t= \"prism.transientMethod\";\n\tpublic static final String PRISM_AR_OPTIONS\t\t\t\t\t= \"prism.arOptions\";\n\tpublic static final String PRISM_PATH_VIA_AUTOMATA\t\t\t\t= \"prism.pathViaAutomata\";\n\tpublic static final String PRISM_NO_DA_SIMPLIFY\t\t\t\t= \"prism.noDaSimplify\";\n\tpublic static final String PRISM_EXPORT_ADV\t\t\t\t\t= \"prism.exportAdv\";\n\tpublic static final String PRISM_EXPORT_ADV_FILENAME\t\t\t= \"prism.exportAdvFilename\";\n\t\n\tpublic static final\tString PRISM_MULTI_MAX_POINTS\t\t\t\t= \"prism.multiMaxIters\";\n\tpublic static final\tString PRISM_PARETO_EPSILON\t\t\t\t\t= \"prism.paretoEpsilon\";\n\tpublic static final\tString PRISM_EXPORT_PARETO_FILENAME\t\t\t= \"prism.exportParetoFileName\";\n\t\n\tpublic static final String PRISM_LTL2DA_TOOL\t\t\t\t\t= \"prism.ltl2daTool\";\n\tpublic static final String PRISM_LTL2DA_SYNTAX\t\t\t\t\t= \"prism.ltl2daSyntax\";\n\n\tpublic static final\tString PRISM_JDD_SANITY_CHECKS\t\t\t\t\t= \"prism.ddsanity\";\n\n\tpublic static final\tString PRISM_PARAM_ENABLED\t\t\t\t\t= \"prism.param.enabled\";\n\tpublic static final\tString PRISM_PARAM_PRECISION\t\t\t\t= \"prism.param.precision\";\n\tpublic static final\tString PRISM_PARAM_SPLIT\t\t\t\t\t= \"prism.param.split\";\n\tpublic static final\tString PRISM_PARAM_BISIM\t\t\t\t\t= \"prism.param.bisim\";\n\tpublic static final\tString PRISM_PARAM_FUNCTION\t\t\t\t\t= \"prism.param.function\";\n\tpublic static final\tString PRISM_PARAM_ELIM_ORDER\t\t\t\t= \"prism.param.elimOrder\";\n\tpublic static final\tString PRISM_PARAM_RANDOM_POINTS\t\t\t= \"prism.param.randomPoints\";\n\tpublic static final\tString PRISM_PARAM_SUBSUME_REGIONS\t\t\t= \"prism.param.subsumeRegions\";\n\tpublic static final String PRISM_PARAM_DAG_MAX_ERROR\t\t\t= \"prism.param.functionDagMaxError\";\n\n\tpublic static final String PRISM_FAU_EPSILON\t\t\t\t\t= \"prism.fau.epsilon\";\n\tpublic static final String PRISM_FAU_DELTA\t\t\t\t\t\t= \"prism.fau.delta\";\n\tpublic static final String PRISM_FAU_INTERVALS\t\t\t\t\t= \"prism.fau.intervals\";\n\tpublic static final String PRISM_FAU_INITIVAL\t\t\t\t\t= \"prism.fau.initival\";\n\tpublic static final String PRISM_FAU_ARRAYTHRESHOLD\t\t\t\t= \"prism.fau.arraythreshold\";\n\n\t//Simulator\n\tpublic static final String SIMULATOR_DEFAULT_NUM_SAMPLES\t\t= \"simulator.defaultNumSamples\";\n\tpublic static final String SIMULATOR_DEFAULT_CONFIDENCE\t\t\t= \"simulator.defaultConfidence\";\n\tpublic static final String SIMULATOR_DEFAULT_WIDTH\t\t\t\t= \"simulator.defaultWidth\";\n\tpublic static final String SIMULATOR_DEFAULT_APPROX\t\t\t\t= \"simulator.defaultApprox\";\n\tpublic static final String SIMULATOR_DEFAULT_MAX_PATH\t\t\t= \"simulator.defaultMaxPath\";\n\tpublic static final String SIMULATOR_DECIDE \t\t\t\t\t= \"simulator.decide\";\n\tpublic static final String SIMULATOR_ITERATIONS_TO_DECIDE\t\t= \"simulator.iterationsToDecide\";\n\tpublic static final String SIMULATOR_MAX_REWARD\t\t\t\t\t= \"simulator.maxReward\";\n\tpublic static final\tString SIMULATOR_SIMULTANEOUS\t\t\t\t= \"simulator.simultaneous\";\n\tpublic static final String SIMULATOR_FIELD_CHOICE\t\t\t\t= \"simulator.fieldChoice\";\n\tpublic static final\tString SIMULATOR_NEW_PATH_ASK_VIEW\t\t\t= \"simulator.newPathAskView\";\n\tpublic static final\tString SIMULATOR_RENDER_ALL_VALUES\t\t\t= \"simulator.renderAllValues\";\n\tpublic static final String SIMULATOR_NETWORK_FILE\t\t\t\t= \"simulator.networkFile\";\n\t\n\t//GUI Model\n\tpublic static final\tString MODEL_AUTO_PARSE\t\t\t\t\t\t= \"model.autoParse\";\n\tpublic static final\tString MODEL_AUTO_MANUAL\t\t\t\t\t= \"model.autoManual\";\n\tpublic static final\tString MODEL_PARSE_DELAY\t\t\t\t\t= \"model.parseDelay\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_FONT\t\t\t\t= \"model.prismEditor.font\";\n\tpublic static final\tString MODEL_SHOW_LINE_NUMBERS\t\t\t\t= \"model.prismEditor.lineNumbers\";\n\t\n\t//public static final\tString MODEL_PRISM_EDITOR_FONT_COLOUR\t\t= \"model.prismEditor.fontColour\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_BG_COLOUR\t\t\t= \"model.prismEditor.bgColour\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_NUMERIC_COLOUR\t= \"model.prismEditor.numericColour\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_NUMERIC_STYLE\t\t= \"model.prismEditor.numericStyle\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_IDENTIFIER_COLOUR\t  =\t\"model.prismEditor.identifierColour\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_IDENTIFIER_STYLE\t  =\t\"model.prismEditor.identifierStyle\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_KEYWORD_COLOUR\t= \"model.prismEditor.keywordColour\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_KEYWORD_STYLE\t\t= \"model.prismEditor.keywordStyle\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_COMMENT_COLOUR\t= \"model.prismEditor.commentColour\";\n\tpublic static final\tString MODEL_PRISM_EDITOR_COMMENT_STYLE\t\t= \"model.prismEditor.commentStyle\";\n\tpublic static final\tString MODEL_PEPA_EDITOR_FONT\t\t\t\t= \"model.pepaEditor.font\";\n\t//public static final\tString MODEL_PEPA_EDITOR_FONT_COLOUR\t\t= \"model.pepaEditor.fontColour\";\n\tpublic static final\tString MODEL_PEPA_EDITOR_BG_COLOUR\t\t\t= \"model.pepaEditor.bgColour\";\n\tpublic static final\tString MODEL_PEPA_EDITOR_COMMENT_COLOUR\t\t= \"model.pepaEditor.commentColour\";\n\tpublic static final\tString MODEL_PEPA_EDITOR_COMMENT_STYLE\t\t= \"model.pepaEditor.commentStyle\";\n\t\n\t//GUI Properties\n\tpublic static final\tString PROPERTIES_FONT\t\t\t\t\t\t= \"properties.font\";\n\tpublic static final\tString PROPERTIES_SELECTION_COLOUR\t\t\t= \"properties.selectionColour\";\n\tpublic static final\tString PROPERTIES_WARNING_COLOUR\t\t\t= \"properties.warningColour\";\n\tpublic static final\tString PROPERTIES_ADDITION_STRATEGY\t\t\t= \"properties.additionStategy\";\n\tpublic static final\tString PROPERTIES_CLEAR_LIST_ON_LOAD\t\t= \"properties.clearListOnLoad\";\n\t\n\t//GUI Log\n\tpublic static final\tString LOG_FONT\t\t\t\t\t\t\t\t= \"log.font\";\n\tpublic static final\tString LOG_SELECTION_COLOUR\t\t\t\t\t= \"log.selectionColour\";\n\tpublic static final\tString LOG_BG_COLOUR\t\t\t\t\t\t= \"log.bgColour\";\n\tpublic static final\tString LOG_BUFFER_LENGTH\t\t\t\t\t= \"log.bufferLength\";\n\t\n\t\n\t//Defaults, types and constaints\n\t\n\tpublic static final String[] propertyOwnerNames =\n\t{\n\t\t\"PRISM\",\n\t\t\"Simulator\",\n\t\t\"Model\",\n\t\t\"Properties\",\n\t\t\"Log\"\n\t};\n\tpublic static final int[] propertyOwnerIDs =\n\t{\n\t\tPropertyConstants.PRISM,\n\t\tPropertyConstants.SIMULATOR,\n\t\tPropertyConstants.MODEL,\n\t\tPropertyConstants.PROPERTIES,\n\t\tPropertyConstants.LOG\t\t\n\t};\n\t\n\t\n\t// Property table:\n\t// * Datatype = type of choice (see type constants at top of this file)\n\t// * Key = internal key, used programmatically; need to add this to key list above\n\t// * Display name = display name; used e.g. in GUI options dialog\n\t// * Version = last public version of PRISM in which this setting did *not* appear\n\t//   (the main use for this is to allow a new default setting to be provided in a new version of PRISM)\n\t//   (if the version of the user settings file is older, a new default value will be set in the file)\n\t// * Default = default value \n\t// * Constraints = limitations on possible values \n\t// * Comments = explanatory comments; used e.g. in GUI options dialog \n\t\n\tpublic static final Object[][][] propertyData =\n\t{\n\t\t{\t//Datatype:\t\t\tKey:\t\t\t\t\t\t\t\t\tDisplay name:\t\t\t\t\t\t\tVersion:\t\tDefault:\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\tConstraints:\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\tComment:\n\t\t\t//====================================================================================================================================================================================================================================================================================================================================\n\t\t\t\n\t\t\t// ENGINES/METHODS:\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_ENGINE,\t\t\t\t\t\t\t\"Engine\",\t\t\t\t\t\t\t\t\"2.1\",\t\t\t\"Hybrid\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"MTBDD,Sparse,Hybrid,Explicit\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which engine (hybrid, sparse, MTBDD, explicit) should be used for model checking.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_HEURISTIC,\t\t\t\t\t\t\"Heuristic mode\",\t\t\t\t\t\t\t\"4.5\",\t\t\t\"None\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"None,Speed,Memory\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which heuristic mode to use for picking engines/settings (none, speed, memory).\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_EXACT_ENABLED,\t\t\t\t\t\"Do exact model checking\",\t\t\t\"4.2.1\",\t\t\tBoolean.valueOf(false),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Perform exact model checking.\" },\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_PTA_METHOD,\t\t\t\t\t\t\"PTA model checking method\",\t\t\t\"3.3\",\t\t\t\"Stochastic games\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Digital clocks,Stochastic games,Backwards reachability\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which method to use for model checking of PTAs.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_TRANSIENT_METHOD,\t\t\t\t\t\"Transient probability computation method\",\t\"3.3\",\t\t\"Uniformisation\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Uniformisation,Fast adaptive uniformisation\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which method to use for computing transient probabilities in CTMCs.\" },\n\t\t\t// NUMERICAL SOLUTION OPTIONS:\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_LIN_EQ_METHOD,\t\t\t\t\t\"Linear equations method\",\t\t\t\t\"2.1\",\t\t\t\"Jacobi\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Power,Jacobi,Gauss-Seidel,Backwards Gauss-Seidel,Pseudo-Gauss-Seidel,Backwards Pseudo-Gauss-Seidel,JOR,SOR,Backwards SOR,Pseudo-SOR,Backwards Pseudo-SOR\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which iterative method to use when solving linear equation systems.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tPRISM_LIN_EQ_METHOD_PARAM,\t\t\t\t\"Over-relaxation parameter\",\t\t\t\"2.1\",\t\t\tDouble.valueOf(0.9),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Over-relaxation parameter for iterative numerical methods such as JOR/SOR.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_TOPOLOGICAL_VI,\t\t\t\t\"Use topological value iteration\",\t\t\t\t\"4.3.1\",\t\tfalse,\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Use topological value iteration in iterative numerical methods.\"},\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_PMAX_QUOTIENT,\t\t\t\t\"For Pmax computations, compute in the MEC quotient\",\t\t\t\t\"4.3.1\",\t\tfalse,\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"For Pmax computations, compute in the MEC quotient.\"},\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_INTERVAL_ITER,\t\t\t\t\"Use interval iteration\",\t\t\t\t\"4.3.1\",\t\tfalse,\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Use interval iteration (from above and below) in iterative numerical methods.\"},\n\t\t\t{ STRING_TYPE,\t\tPRISM_INTERVAL_ITER_OPTIONS,\t\t\t\t\"Interval iteration options\",\t\t\t\t\"4.3.1\",\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Interval iteration options, a comma-separated list of the following:\\n\" + OptionsIntervalIteration.getOptionsDescription() },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_MDP_SOLN_METHOD,\t\t\t\t\t\"MDP solution method\",\t\t\t\t\"4.0\",\t\t\t\"Value iteration\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Value iteration,Gauss-Seidel,Policy iteration,Modified policy iteration,Linear programming\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which method to use when solving Markov decision processes.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_MDP_MULTI_SOLN_METHOD,\t\t\t\"MDP multi-objective solution method\",\t\t\t\t\"4.0.3\",\t\t\t\"Value iteration\",\t\t\t\t\t\t\t\t\t\t\t\"Value iteration,Gauss-Seidel,Linear programming\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which method to use when solving multi-objective queries on Markov decision processes.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_IMDP_SOLN_METHOD,\t\t\t\t\t\"IMDP/DTMC solution method\",\t\t\t\t\"4.7\",\t\t\t\"Gauss-Seidel\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Value iteration,Gauss-Seidel\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which method to use when solving interval Markov decision processes and Markov chains.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_TERM_CRIT,\t\t\t\t\t\t\"Termination criteria\",\t\t\t\t\t\"2.1\",\t\t\t\"Relative\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Absolute,Relative\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Criteria to use for checking termination of iterative numerical methods.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tPRISM_TERM_CRIT_PARAM,\t\t\t\t\t\"Termination epsilon\",\t\t\t\t\t\"2.1\",\t\t\tDouble.valueOf(1.0E-6),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0.0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Epsilon value to use for checking termination of iterative numerical methods.\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_MAX_ITERS,\t\t\t\t\t\t\"Termination max. iterations\",\t\t\t\"2.1\",\t\t\tInteger.valueOf(10000),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Maximum number of iterations to perform if iterative methods do not converge.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_EXPORT_ITERATIONS,\t\t\t\t\"Export iterations (debug/visualisation)\",\t\t\t\"4.3.1\",\t\t\tfalse,\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Export solution vectors for iteration algorithms to iterations.html\"},\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_GRID_RESOLUTION,\t\t\t\t\t\"Fixed grid resolution\",\t\t\t    \"4.5\",\t\t\tInteger.valueOf(10),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"1,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"The resolution for the fixed grid approximation algorithm for POMDPs.\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_EXPORT_MODEL_PRECISION,\t\t\t\"Precision of model export\",\t\t\t\"4.7\",\t\t\t16,\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\tRANGE_EXPORT_DOUBLE_PRECISION.min() + \"-\" + RANGE_EXPORT_DOUBLE_PRECISION.max(),\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Export model probabilities/rewards to n significant decimal places.\"},\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_EXPORT_MODEL_HEADERS,\t\t\t\t\"Include headers in model exports\",\t\t\"4.7\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Whether to include #-commented header lines when exporting model data to explicit files.\"},\n\t\t\t// MODEL CHECKING OPTIONS:\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_PRECOMPUTATION,\t\t\t\t\t\"Use precomputation\",\t\t\t\t\t\"2.1\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Whether to use model checking precomputation algorithms (Prob0, Prob1, etc.), where optional.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_PROB0,\t\t\t\t\t\t\t\"Use Prob0 precomputation\",\t\t\t\t\"4.0.2\",\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Whether to use model checking precomputation algorithm Prob0 (if precomputation enabled).\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_PROB1,\t\t\t\t\t\t\t\"Use Prob1 precomputation\",\t\t\t\t\"4.0.2\",\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Whether to use model checking precomputation algorithm Prob1 (if precomputation enabled).\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_PRE_REL,\t\t\t\t\t\t\t\"Use predecessor relation\",\t\t\"4.2.1\",\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Whether to use a pre-computed predecessor relation in several algorithms.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_FAIRNESS,\t\t\t\t\t\t\t\"Use fairness\",\t\t\t\t\t\t\t\"2.1\",\t\t\tBoolean.valueOf(false),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Constrain to fair adversaries when model checking MDPs.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_FIX_DEADLOCKS,\t\t\t\t\t\"Automatically fix deadlocks\",\t\t\t\"4.0.3\",\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Automatically fix deadlocks, where necessary, when constructing probabilistic models.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_DO_PROB_CHECKS,\t\t\t\t\t\"Do probability/rate checks\",\t\t\t\"2.1\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Perform sanity checks on model probabilities/rates when constructing probabilistic models.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tPRISM_SUM_ROUND_OFF,\t\t\t\t\t\"Probability sum threshold\",\t\t\t\t\t\"2.1\",\t\t\tDouble.valueOf(1.0E-5),\t\t\t\t\t\t\t\t\t\t\t\t\t\"0.0,\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Round-off threshold for places where doubles are summed and compared to integers (e.g. checking that probabilities sum to 1 in an update).\" },\t\t\t\t\t\t\t\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_DO_SS_DETECTION,\t\t\t\t\t\"Use steady-state detection\",\t\t\t\"2.1\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Use steady-state detection during CTMC transient probability computation.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_SCC_METHOD,\t\t\t\t\t\t\"SCC decomposition method\",\t\t\t\t\"3.2\",\t\t\t\"Lockstep\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Xie-Beerel,Lockstep,SCC-Find\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Which algorithm to use for (symbolic) decomposition of a graph into strongly connected components (SCCs).\" },\n\t\t\t{ STRING_TYPE,\t\tPRISM_SYMM_RED_PARAMS,\t\t\t\t\t\"Symmetry reduction parameters\",\t\t\"3.2\",\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Parameters for symmetry reduction (format: \\\"i j\\\" where i and j are the number of modules before and after the symmetric ones; empty string means symmetry reduction disabled).\" },\n\t\t\t{ STRING_TYPE,\t\tPRISM_AR_OPTIONS,\t\t\t\t\t\t\"Abstraction refinement options\",\t\t\"3.3\",\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Various options passed to the asbtraction-refinement engine (e.g. for PTA model checking).\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_PATH_VIA_AUTOMATA,\t\t\t\t\"All path formulas via automata\",\t\t\t\"4.2.1\",\t\t\tBoolean.valueOf(false),\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Handle all path formulas via automata constructions.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_NO_DA_SIMPLIFY,\t\t\t\t\"Do not simplify deterministic automata\",\t\t\t\"4.3\",\t\t\tBoolean.valueOf(false),\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Do not attempt to simplify deterministic automata, acceptance conditions (for debugging).\" },\n\n\t\t\t// MULTI-OBJECTIVE MODEL CHECKING OPTIONS:\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_MULTI_MAX_POINTS,\t\t\t\t\t\"Max. multi-objective corner points\",\t\t\t\"4.0.3\",\t\t\tInteger.valueOf(50),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Maximum number of corner points to explore if (value iteration based) multi-objective model checking does not converge.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tPRISM_PARETO_EPSILON,\t\t\t\t\t\"Pareto approximation threshold\",\t\t\t\"4.0.3\",\t\t\tDouble.valueOf(1.0E-2),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0.0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Determines to what precision the Pareto curve will be approximated.\" },\n\t\t\t{ STRING_TYPE,\t\tPRISM_EXPORT_PARETO_FILENAME,\t\t\t\"Pareto curve export filename\",\t\t\t\"4.0.3\",\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"If non-empty, any Pareto curve generated will be exported to this file.\" },\n\t\t\t// OUTPUT OPTIONS:\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_VERBOSE,\t\t\t\t\t\t\t\"Verbose output\",\t\t\t\t\t\t\"2.1\",\t\tBoolean.valueOf(false),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Display verbose output to log.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_EXTRA_DD_INFO,\t\t\t\t\t\"Extra MTBDD information\",\t\t\t\t\"3.1.1\",\t\tBoolean.valueOf(false),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Display extra information about (MT)BDDs used during and after model construction.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_EXTRA_REACH_INFO,\t\t\t\t\t\"Extra reachability information\",\t\t\"3.1.1\",\t\tBoolean.valueOf(false),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Display extra information about progress of reachability during model construction.\" },\n\t\t\t// SPARSE/HYBRID/MTBDD OPTIONS:\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_COMPACT,\t\t\t\t\t\t\t\"Use compact schemes\",\t\t\t\t\t\"2.1\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Use additional optimisations for compressing sparse matrices and vectors with repeated values.\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_NUM_SB_LEVELS,\t\t\t\t\t\"Hybrid sparse levels\",\t\t\t\t\t\"2.1\",\t\t\tInteger.valueOf(-1),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"-1,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Number of MTBDD levels ascended when adding sparse matrices to hybrid engine data structures (-1 means use default).\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_SB_MAX_MEM,\t\t\t\t\t\t\"Hybrid sparse memory (KB)\",\t\t\t\"2.1\",\t\t\tInteger.valueOf(1024),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Maximum memory usage when adding sparse matrices to hybrid engine data structures (KB).\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_NUM_SOR_LEVELS,\t\t\t\t\t\"Hybrid GS levels\",\t\t\t\t\t\t\"2.1\",\t\t\tInteger.valueOf(-1),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"-1,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Number of MTBDD levels descended for hybrid engine data structures block division with GS/SOR.\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_SOR_MAX_MEM,\t\t\t\t\t\t\"Hybrid GS memory (KB)\",\t\t\t\t\"2.1\",\t\t\tInteger.valueOf(1024),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Maximum memory usage for hybrid engine data structures block division with GS/SOR (KB).\" },\n\t\t\t{ STRING_TYPE,\t\tPRISM_CUDD_MAX_MEM,\t\t\t\t\t\t\"CUDD max. memory\",\t\t\t\t\"4.2.1\",\t\t\tnew String(\"1g\"),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Maximum memory available to CUDD (underlying BDD/MTBDD library), e.g. 125k, 50m, 4g. Note: Restart PRISM after changing this.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tPRISM_CUDD_EPSILON,\t\t\t\t\t\t\"CUDD epsilon\",\t\t\t\t\t\t\t\"2.1\",\t\t\tDouble.valueOf(1.0E-15),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0.0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Epsilon value used by CUDD (underlying BDD/MTBDD library) for terminal cache comparisons.\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_DD_EXTRA_STATE_VARS,\t\t\t\t\"Extra DD state var allocation\",\t\t\"4.3.1\",\t\t\tInteger.valueOf(20),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Number of extra DD state variables preallocated for use in model transformation.\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_DD_EXTRA_ACTION_VARS,\t\t\t\t\"Extra DD action var allocation\",\t\t\"4.3.1\",\t\t\tInteger.valueOf(20),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Number of extra DD action variables preallocated for use in model transformation.\" },\n\n\n\t\t\t// ADVERSARIES/COUNTEREXAMPLES:\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_EXPORT_ADV,\t\t\t\t\t\t\"Adversary export\",\t\t\t\t\t\t\"3.3\",\t\t\t\"None\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"None,DTMC,MDP\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Type of adversary to generate and export during MDP model checking\" },\n\t\t\t{ STRING_TYPE,\t\tPRISM_EXPORT_ADV_FILENAME,\t\t\t\t\"Adversary export filename\",\t\t\t\"3.3\",\t\t\t\"adv.tra\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Name of file for MDP adversary export (if enabled)\" },\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t// LTL2DA TOOLS\n\t\t\t{ STRING_TYPE,\t\tPRISM_LTL2DA_TOOL,\t\t\t\t\t\t\"Use external LTL->DA tool\",\t\t\"4.2.1\",\t\t\t\"\",\t\tnull,\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"If non-empty, the path to the executable for the external LTL->DA tool.\"},\n\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_LTL2DA_SYNTAX,\t\t\t\t\t\"LTL syntax for external LTL->DA tool\",\t\t\"4.2.1\",\t\t\t\"LBT\",\t\t\"LBT,Spin,Spot,Rabinizer\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"The syntax for LTL formulas passed to the external LTL->DA tool.\"},\n\n\t\t\t// DEBUG / SANITY CHECK OPTIONS:\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_JDD_SANITY_CHECKS,\t\t\t\t\t\"Do BDD sanity checks\",\t\t\t\"4.3.1\",\t\t\tBoolean.valueOf(false),\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Perform internal sanity checks during computations (can cause significant slow-down).\" },\n\n\t\t\t// PARAMETRIC MODEL CHECKING\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_PARAM_ENABLED,\t\t\t\t\t\"Do parametric model checking\",\t\t\t\"4.1\",\t\t\tBoolean.valueOf(false),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Perform parametric model checking.\" },\n\t\t\t{ STRING_TYPE,\t\tPRISM_PARAM_PRECISION,\t\t\t\t\t\"Parametric model checking precision\",\t\"4.1\",\t\t\t\"5/100\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Maximal volume of area to remain undecided in each step when performing parametric model checking.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_PARAM_SPLIT,\t\t\t\t\t\t\"Parametric model checking split method\",\t\t\t\t\t\t\t\"4.1\",\t\t\t\"Longest\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Longest,All\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Strategy to use when splitting a region during parametric model checking. Either split on longest side, or split on all sides.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_PARAM_BISIM,\t\t\t\t\t\t\"Parametric model checking bisimulation method\",\t\t\t\t\t\"4.1\",\t\t\t\"Weak\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Weak,Strong,None\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Type of bisimulation used to reduce model size during paramteric model checking. For reward-based properties, weak bisimulation cannot be used.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_PARAM_FUNCTION,\t\t\t\t\t\"Parametric model checking function representation\",\t\t\t\t\"4.1\",\t\t\t\"JAS-cached\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"JAS-cached,JAS,DAG\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Type of representation for functions used during parametric model checking.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPRISM_PARAM_ELIM_ORDER,\t\t\t\t\t\"Parametric model checking state elimination order\",\t\t\t\"4.1\",\t\t\t\"Backward\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Arbitrary,Forward,Forward-reversed,Backward,Backward-reversed,Random\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Order in which states are eliminated during unbounded parametric model checking analysis.\" },\n\t\t\t{ INTEGER_TYPE,\t\tPRISM_PARAM_RANDOM_POINTS,\t\t\t\t\"Parametric model checking random evaluations\",\t\t\"4.1\",\t\t\tInteger.valueOf(5),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Number of random points to evaluate per region to increase chance of correctness during parametric model checking.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPRISM_PARAM_SUBSUME_REGIONS,\t\t\t\"Parametric model checking region subsumption\",\t\t\t\t\"4.1\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Subsume adjacent regions during parametric model checking.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tPRISM_PARAM_DAG_MAX_ERROR,\t\t\t\t\"Parametric model checking max. DAG error\",\t\"4.1\",\t\t\tDouble.valueOf(1E-100),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Maximal error probability (i.e. maximum probability of of a wrong result) in DAG function representation used for parametric model checking.\" },\n\t\t\t\n\t\t\t// FAST ADAPTIVE UNIFORMISATION\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t{ DOUBLE_TYPE,      PRISM_FAU_EPSILON,\t\t\t\t\t\t\"FAU epsilon\",\t\t \t\t\t\t\t\"4.1\",   \t \tDouble.valueOf(1E-6),     \t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"For fast adaptive uniformisation (FAU), decides how much probability may be lost due to truncation of birth process.\" },\n\t\t\t{ DOUBLE_TYPE,      PRISM_FAU_DELTA,\t\t\t\t\t\t\"FAU cut off delta\", \t\t\t\t\t\"4.1\",   \t \tDouble.valueOf(1E-12),     \t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"For fast adaptive uniformisation (FAU), states whose probability is below this value will be removed.\" },\n\t\t\t{ INTEGER_TYPE,     PRISM_FAU_ARRAYTHRESHOLD,\t\t\t\t\"FAU array threshold\", \t\t\t\t\t\"4.1\",   \t \tInteger.valueOf(100),    \t \t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"For fast adaptive uniformisation (FAU), after this number of iterations without changes to the state space, storage is switched to a faster, fixed-size data structure.\" },\n\t\t\t{ INTEGER_TYPE,     PRISM_FAU_INTERVALS,\t\t\t\t\t\"FAU time intervals\",\t\t\t\t\t\"4.1\",   \t \tInteger.valueOf(1),     \t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"For fast adaptive uniformisation (FAU), the time period is split into this number of of intervals.\" },\n\t\t\t{ DOUBLE_TYPE,      PRISM_FAU_INITIVAL,\t\t\t\t\t\t\"FAU initial time interval\",\t\t\t\"4.1\",   \t \tDouble.valueOf(1.0),     \t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"For fast adaptive uniformisation (FAU), the length of initial time interval to analyse.\" },\n\t\t},\n\t\t{\n\t\t\t{ INTEGER_TYPE,\t\tSIMULATOR_DEFAULT_NUM_SAMPLES,\t\t\t\"Default number of samples\",\t\t\t\"4.0\",\t\tInteger.valueOf(1000),\t\t\t\"1,\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Default number of samples when using approximate (simulation-based) model checking (CI/ACI/APMC methods).\" },\n\t\t\t{ DOUBLE_TYPE,\t\tSIMULATOR_DEFAULT_CONFIDENCE,\t\t\t\"Default confidence parameter\",\t\t\t\"4.0\",\t\tDouble.valueOf(0.01),\t\t\t\"0,1\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Default value for the 'confidence' parameter when using approximate (simulation-based) model checking (CI/ACI/APMC/SPRT methods). For CI/ACI, this means that the corresponding 'confidence level' is 100 x (1 - confidence)%; for APMC, this is the probability of the 'approximation' being exceeded; for SPRT, this is the acceptable probability for type I/II errors.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tSIMULATOR_DEFAULT_WIDTH,\t\t\t\t\"Default width of confidence interval\",\t\"4.0\",\t\tDouble.valueOf(0.05),\t\t\t\"0,\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Default (half-)width of the confidence interval when using approximate (simulation-based) model checking (CI/ACI/SPRT methods). For SPRT, this refers to the 'indifference' parameter.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tSIMULATOR_DEFAULT_APPROX,\t\t\t\t\"Default approximation parameter\",\t\t\"4.0\",\t\tDouble.valueOf(0.05),\t\t\t\"0,\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Default value for the 'approximation' parameter when using approximate (simulation-based) model checking (APMC method).\" },\n\t\t\t{ LONG_TYPE,\t\tSIMULATOR_DEFAULT_MAX_PATH,\t\t\t\t\"Default maximum path length\",\t\t\t\"2.1\",\t\tLong.valueOf(10000),\t\t\t\"1,\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Default maximum path length when using approximate (simulation-based) model checking.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tSIMULATOR_DECIDE,\t\t\t\t\t\t\"Decide S^2=0 or not automatically\",\t\"4.0\",\t\tBoolean.valueOf(true),\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Let PRISM choose whether, after a certain number of iterations, the standard error is null or not.\" },\n\t\t\t{ INTEGER_TYPE,\t\tSIMULATOR_ITERATIONS_TO_DECIDE,\t\t\t\"Number of iterations to decide\",\t\t\"4.0\",\t\tInteger.valueOf(10000),\t\t\t\"1,\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Number of iterations to decide whether the standard error is null or not.\" },\n\t\t\t{ DOUBLE_TYPE,\t\tSIMULATOR_MAX_REWARD,\t\t\t\t\t\"Maximum reward\",\t\t\t\t\t\t\"4.0\",\t\tDouble.valueOf(1000.0),\t\t\t\"1,\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Maximum reward for CI/ACI methods. It helps these methods in displaying the progress in case of rewards computation.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tSIMULATOR_SIMULTANEOUS,\t\t\t\t\t\"Check properties simultaneously\",\t\t\"2.1\",\t\tBoolean.valueOf(true),\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Check multiple properties simultaneously over the same set of execution paths (simulator only).\" },\n\t\t\t{ CHOICE_TYPE,\t\tSIMULATOR_FIELD_CHOICE,\t\t\t\t\t\"Values used in dialog\",\t\t\t\t\"2.1\",\t\t\"Last used values\",\t\t\t\"Last used values,Always use defaults\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"How to choose values for the simulation dialog: remember previously used values or revert to the defaults each time.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tSIMULATOR_NEW_PATH_ASK_VIEW,\t\t\t\"Ask for view configuration\",\t\t\t\"2.1\",\t\tBoolean.valueOf(false),\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Display dialog with display options when creating a new simulation path.\" },\n\t\t\t{ CHOICE_TYPE,\t\tSIMULATOR_RENDER_ALL_VALUES,\t\t\t\"Path render style\",\t\t\t\t\t\"3.2\",\t\t\"Render all values\",\t\t\"Render changes,Render all values\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Display style for paths in the simulator user interface: only show variable values when they change, or show all values regardless.\" },\n\t\t\t{ FILE_TYPE,\t\tSIMULATOR_NETWORK_FILE,\t\t\t\t\t\"Network profile\",\t\t\t\t\t\t\"2.1\",\t\tnew File(\"\"),\t\t\t\t\"\",\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"File specifying the network profile used by the distributed PRISM simulator.\" }\n\t\t},\n\t\t{\n\t\t\t{ BOOLEAN_TYPE,\t\tMODEL_AUTO_PARSE,\t\t\t\t\t\t\"Auto parse\",\t\t\t\t\t\t\t\"2.1\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Parse PRISM models automatically as they are loaded/edited in the text editor.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tMODEL_AUTO_MANUAL,\t\t\t\t\t\t\"Manual parse for large models\",\t\t\"2.1\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Disable automatic model parsing when loading large PRISM models.\" },\n\t\t\t{ INTEGER_TYPE,\t\tMODEL_PARSE_DELAY,\t\t\t\t\t\t\"Parse delay (ms)\",\t\t\t\t\t\t\"2.1\",\t\t\tInteger.valueOf(1000),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"0,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Time delay (after typing has finished) before an automatic re-parse of the model is performed.\" },\n\t\t\t{ FONT_COLOUR_TYPE,\tMODEL_PRISM_EDITOR_FONT,\t\t\t\t\"PRISM editor font\",\t\t\t\t\t\"2.1\",\t\t\tnew FontColorPair(new Font(\"monospaced\", Font.PLAIN, 12), Color.black),\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Font used in the PRISM model text editor.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tMODEL_SHOW_LINE_NUMBERS,\t\t\t\t\"PRISM editor line numbers\",            \"3.2\",    Boolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Enable or disable line numbers in the PRISM model text editor\" },\n\t\t\t{ COLOUR_TYPE,\t\tMODEL_PRISM_EDITOR_BG_COLOUR,\t\t\t\"PRISM editor background\",\t\t\t\t\"2.1\",\t\t\tnew Color(255,255,255),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Background colour for the PRISM model text editor.\" },\n\t\t\t{ COLOUR_TYPE,\t\tMODEL_PRISM_EDITOR_NUMERIC_COLOUR,\t\t\"PRISM editor numeric colour\",\t\t\t\"2.1\",\t\t\tnew Color(0,0,255),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting colour for numerical values in the PRISM model text editor.\" },\n\t\t\t{ CHOICE_TYPE,\t\tMODEL_PRISM_EDITOR_NUMERIC_STYLE,\t\t\"PRISM editor numeric style\",\t\t\t\"2.1\",\t\t\t\"Plain\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Plain,Italic,Bold,Bold Italic\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting style for numerical values in the PRISM model text editor.\" },\n\t\t\t{ COLOUR_TYPE,\t\tMODEL_PRISM_EDITOR_IDENTIFIER_COLOUR,\t\"PRISM editor identifier colour\",\t\t\"2.1\",\t\t\tnew Color(255,0,0),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting colour for identifiers values in the PRISM model text editor\" },\n\t\t\t{ CHOICE_TYPE,\t\tMODEL_PRISM_EDITOR_IDENTIFIER_STYLE,\t\"PRISM editor identifier style\",\t\t\"2.1\",\t\t\t\"Plain\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Plain,Italic,Bold,Bold Italic\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting style for identifiers in the PRISM model text editor.\" },\n\t\t\t{ COLOUR_TYPE,\t\tMODEL_PRISM_EDITOR_KEYWORD_COLOUR,\t\t\"PRISM editor keyword colour\",\t\t\t\"2.1\",\t\t\tnew Color(0,0,0),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting colour for keywords in the PRISM model text editor\" },\n\t\t\t{ CHOICE_TYPE,\t\tMODEL_PRISM_EDITOR_KEYWORD_STYLE,\t\t\"PRISM editor keyword style\",\t\t\t\"2.1\",\t\t\t\"Bold\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Plain,Italic,Bold,Bold Italic\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting style for keywords in the PRISM model text editor.\" },\n\t\t\t{ COLOUR_TYPE,\t\tMODEL_PRISM_EDITOR_COMMENT_COLOUR,\t\t\"PRISM editor comment colour\",\t\t\t\"2.1\",\t\t\tnew Color(0,99,0),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting colour for comments in the PRISM model text editor.\" },\n\t\t\t{ CHOICE_TYPE,\t\tMODEL_PRISM_EDITOR_COMMENT_STYLE,\t\t\"PRISM editor comment style\",\t\t\t\"2.1\",\t\t\t\"Italic\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Plain,Italic,Bold,Bold Italic\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting style for comments in the PRISM model text editor.\" },\n\t\t\t{ FONT_COLOUR_TYPE,\tMODEL_PEPA_EDITOR_FONT,\t\t\t\t\t\"PEPA editor font\",\t\t\t\t\t\t\"2.1\",\t\t\tnew FontColorPair(new Font(\"monospaced\", Font.PLAIN, 12), Color.black),\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Font used in the PEPA model text editor.\" },\n\t\t\t{ COLOUR_TYPE,\t\tMODEL_PEPA_EDITOR_BG_COLOUR,\t\t\t\"PEPA editor background\",\t\t\t\t\"2.1\",\t\t\tnew Color(255,250,240),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Background colour for the PEPA model text editor.\" },\n\t\t\t{ COLOUR_TYPE,\t\tMODEL_PEPA_EDITOR_COMMENT_COLOUR,\t\t\"PEPA editor comment colour\",\t\t\t\"2.1\",\t\t\tnew Color(0,99,0),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting colour for comments in the PEPA model text editor.\" },\n\t\t\t{ CHOICE_TYPE,\t\tMODEL_PEPA_EDITOR_COMMENT_STYLE,\t\t\"PEPA editor comment style\",\t\t\t\"2.1\",\t\t\t\"Italic\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Plain,Italic,Bold,Bold Italic\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Syntax highlighting style for comments in the PEPA model text editor.\" }\n\t\t},\n\t\t{\n\t\t\t{ FONT_COLOUR_TYPE,\tPROPERTIES_FONT,\t\t\t\t\t\t\"Display font\",\t\t\t\t\t\t\t\"2.1\",\t\t\tnew FontColorPair(new Font(\"monospaced\", Font.PLAIN, 12), Color.black),\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Font used for the properties list.\" },\n\t\t\t{ COLOUR_TYPE,\t\tPROPERTIES_WARNING_COLOUR,\t\t\t\t\"Warning colour\",\t\t\t\t\t\t\"2.1\",\t\t\tnew Color(255,130,130),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Colour used to indicate that a property is invalid.\" },\n\t\t\t{ CHOICE_TYPE,\t\tPROPERTIES_ADDITION_STRATEGY,\t\t\t\"Property addition strategy\",\t\t\t\"2.1\",\t\t\t\"Warn when invalid\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Warn when invalid,Do not allow invalid\",\t\t\t\t\t\t\t\t\t\t\t\t\t\"How to deal with properties that are invalid.\" },\n\t\t\t{ BOOLEAN_TYPE,\t\tPROPERTIES_CLEAR_LIST_ON_LOAD,\t\t\t\"Clear list when load model\",\t\t\t\"2.1\",\t\t\tBoolean.valueOf(true),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Clear the properties list whenever a new model is loaded.\" }\n\t\t},\n\t\t{\n\t\t\t{ FONT_COLOUR_TYPE,\tLOG_FONT,\t\t\t\t\t\t\t\t\"Display font\",\t\t\t\t\t\t\t\"2.1\",\t\t\tnew FontColorPair(new Font(\"monospaced\", Font.PLAIN, 12), Color.black),\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Font used for the log display.\" },\n\t\t\t{ COLOUR_TYPE,\t\tLOG_BG_COLOUR,\t\t\t\t\t\t\t\"Background colour\",\t\t\t\t\t\"2.1\",\t\t\tnew Color(255,255,255),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Background colour for the log display.\" },\n\t\t\t{ INTEGER_TYPE,\t\tLOG_BUFFER_LENGTH,\t\t\t\t\t\t\"Buffer length\",\t\t\t\t\t\t\"2.1\",\t\t\tInteger.valueOf(10000),\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"1,\",\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\"Length of the buffer for the log display.\" }\n\t\t}\n\t};\n\t\n\tpublic static final String[] oldPropertyNames =  {\"simulator.apmcStrategy\", \"simulator.engine\", \"simulator.newPathAskDefault\"};\n\t\n\tpublic DefaultSettingOwner[] optionOwners;\n\tprivate Hashtable<String,Setting> data;\n\tprivate boolean modified;\n\t\n\tprivate ArrayList<PrismSettingsListener> settingsListeners;\n\t\n\t/**\n\t * Default constructor: set all options to default values. \n\t */\n\tpublic PrismSettings()\n\t{\n\t\toptionOwners = new DefaultSettingOwner[propertyOwnerIDs.length];\n\t\t\n\t\tint counter = 0;\n\t\t\n\t\tfor(int i = 0; i < propertyOwnerIDs.length; i++)\n\t\t{\n\t\t\toptionOwners[i] = new DefaultSettingOwner(propertyOwnerNames[i], propertyOwnerIDs[i]);\n\t\t\tfor(int j = 0; j < propertyData[i].length; j++)\n\t\t\t{\n\t\t\t\tcounter++;\n\t\t\t\tObject[] setting = propertyData[i][j];\n\t\t\t\tString key = (String)setting[1];\n\t\t\t\tString display = (String)setting[2];\n\t\t\t\tString version = (String)setting[3];\n\t\t\t\tObject value = setting[4];\n\t\t\t\tString constraint = (String)setting[5];\n\t\t\t\tString comment = (String)setting[6];\n\t\t\t\t\n\t\t\t\tSetting set;\n\t\t\t\t\n\t\t\t\tif(setting[0].equals(STRING_TYPE))\n\t\t\t\t{\n\t\t\t\t\tset = new SingleLineStringSetting(display, (String)value, comment, optionOwners[i], false);\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse if(setting[0].equals(INTEGER_TYPE))\n\t\t\t\t{\n\t\t\t\t\tif(constraint.equals(\"\"))\n\t\t\t\t\t\tset = new IntegerSetting(display, (Integer)value, comment, optionOwners[i], false);\n\t\t\t\t\telse\n\t\t\t\t\t\tset = new IntegerSetting(display, (Integer)value, comment, optionOwners[i], false, new RangeConstraint(constraint));\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse if(setting[0].equals(DOUBLE_TYPE))\n\t\t\t\t{\n\t\t\t\t\t//DO constraints for this double\n\t\t\t\t\tif(constraint.equals(\"\"))\n\t\t\t\t\t\tset = new DoubleSetting(display, (Double)value, comment, optionOwners[i], false);\n\t\t\t\t\telse\n\t\t\t\t\t\tset = new DoubleSetting(display, (Double)value, comment, optionOwners[i], false, new RangeConstraint(constraint));\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse if(setting[0].equals(BOOLEAN_TYPE))\n\t\t\t\t{\n\t\t\t\t\t//DO constraints for this boolean\n\t\t\t\t\tset = new BooleanSetting(display, (Boolean)value, comment, optionOwners[i], false);\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse if(setting[0].equals(LONG_TYPE))\n\t\t\t\t{\n\t\t\t\t\tif(constraint.equals(\"\"))\n\t\t\t\t\t\tset = new LongSetting(display, (Long)value, comment, optionOwners[i], false);\n\t\t\t\t\telse\n\t\t\t\t\t\tset = new LongSetting(display, (Long)value, comment, optionOwners[i], false, new RangeConstraint(constraint));\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse if(setting[0].equals(COLOUR_TYPE))\n\t\t\t\t{\n\t\t\t\t\t//DO constraints for this Color\n\t\t\t\t\tset = new ColorSetting(display, (Color)value, comment, optionOwners[i], false);\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse if(setting[0].equals(CHOICE_TYPE))\n\t\t\t\t{\n\t\t\t\t\t//DO constraints for this choice\n\t\t\t\t\tStringTokenizer tokens = new StringTokenizer(constraint, \",\");\n\t\t\t\t\tString[] choices = new String[tokens.countTokens()];\n\t\t\t\t\tint k = 0;\n\t\t\t\t\twhile(tokens.hasMoreTokens())\n\t\t\t\t\t{\n\t\t\t\t\t\tchoices[k++] = tokens.nextToken();\n\t\t\t\t\t}\n\t\t\t\t\tset = new ChoiceSetting(display, choices, (String)value, comment, optionOwners[i], false);\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse if(setting[0].equals(FONT_COLOUR_TYPE))\n\t\t\t\t{\n\t\t\t\t\t//DO constraints for this FontColorPair\n\t\t\t\t\tset = new FontColorSetting(display, (FontColorPair)value, comment, optionOwners[i], false);\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse if(setting[0].equals(FILE_TYPE))\n\t\t\t\t{\n\t\t\t\t\tset = new FileSetting(display, (File)value, comment, optionOwners[i], false);\n\t\t\t\t\tset.setKey(key);\n\t\t\t\t\tset.setVersion(version);\n\t\t\t\t\toptionOwners[i].addSetting(set);\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\tSystem.err.println(\"Fatal error when loading properties: unknown setting type \"+setting[0]);\n\t\t\t\t}\n\t\t\t}\n\t\t\toptionOwners[i].addObserver(this);\n\t\t}\n\t\t\n\t\tmodified = false;\n\t\t\n\t\t//populate a hash table with the keys\n\t\tpopulateHashTable(counter);\n\t\tsettingsListeners = new ArrayList<PrismSettingsListener>();\n\t}\n\t\n\t/**\n\t * Copy constructor. \n\t */\n\tpublic PrismSettings(PrismSettings settings)\n\t{\n\t\t// Create anew with default values\n\t\t// (that way, we get a fresh set of Setting objects)\n\t\tthis();\n\t\t// Then, copy across options\n\t\tfor (Map.Entry<String,Setting> e : settings.data.entrySet()) {\n\t\t\ttry {\n\t\t\t\tset(e.getKey(), e.getValue().getValue());\n\t\t\t} catch (PrismException ex) {\n\t\t\t\t// Should never happen\n\t\t\t\tSystem.err.println(ex);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tprivate void populateHashTable(int size)\n\t{\n\t\tdata = new Hashtable<String,Setting>(size);\n\t\t\n\t\tfor(int i = 0; i < optionOwners.length; i++)\n\t\t{\n\t\t\tfor(int j = 0; j < optionOwners[i].getNumSettings(); j++)\n\t\t\t{\n\t\t\t\tdata.put(optionOwners[i].getSetting(j).getKey(), optionOwners[i].getSetting(j));\n\t\t\t}\n\t\t}\n\t}\n\t\n\tprivate Setting settingFromHash(String key)\n\t{\n\t\treturn data.get(key);\n\t}\n\t\n\tpublic void addSettingsListener(PrismSettingsListener listener)\n\t{\n\t\tsettingsListeners.add(listener);\n\t}\n\t\n\tpublic void removeSettingsListener(PrismSettingsListener listener)\n\t{\n\t\tsettingsListeners.remove(listener);\n\t}\n\t\n\tpublic void notifySettingsListeners()\n\t{\n\t\tfor(int i = 0; i < settingsListeners.size(); i++)\n\t\t{\n\t\t\tPrismSettingsListener listener = settingsListeners.get(i);\n\t\t\tlistener.notifySettings(this);\n\t\t}\n\t}\n\n\t/**\n\t * Get the default location of the settings file.\n\t * <br>\n\t * There is a legacy location (filename '.prism' in the user's\n\t * home directory), and a modern location, which depends on the\n\t * operating system:\n\t * <ul>\n\t * <li>For macOS, the location is $HOME/Library/Preferences/prism.settings</li>\n\t * <li>For Linux, the location depends on the environment variable $XDG_CONFIG_HOME;\n\t * if set, the location is $XDG_CONFIG_HOME/prism.settings;\n\t * if not, it's $HOME/.config/prism.settings</li>\n\t * <li>On Windows, only the legacy location is supported</li>\n\t * </ul>\n\t * <br>\n\t * If the legacy settings file exists, this method returns that location.\n\t * Otherwise, the modern location is returned.\n\t * <br>\n\t * To support different settings files in derived tools (e.g. prism-games),\n\t * the filename is derived from the tool name (see Prism.getToolName()).\n\t */\n\tpublic File getLocationForSettingsFile()\n\t{\n\t\tString toolName = Prism.getToolName().toLowerCase();\n\t\tFile legacyConfigFile = new File(System.getProperty(\"user.home\") +\n\t\t\t\tFile.separator + \".\" + toolName);\n\t\tif (legacyConfigFile.exists() && !legacyConfigFile.isDirectory()) {\n\t\t\treturn legacyConfigFile;\n\t\t}\n\t\t\n\t\t// Check for operating system, try XDG base directory specification if\n\t\t// UNIX-like system (except for MacOS) is found\n\t\tString os = System.getProperty(\"os.name\").toLowerCase();\n\t\tFile config;\n\t\tif (os.indexOf(\"win\") >= 0) { // Windows\n\t\t\t// use \"$HOME\\.prism\"\n\t\t\tconfig = new File(System.getProperty(\"user.home\") +\n\t\t\t\t\tFile.separator + \".\" + toolName);\n\t\t} else if (os.indexOf(\"mac\") >= 0) { // MacOS\n\t\t\t// use \"$HOME/Library/Preferences/prism/prism.settings\"\n\t\t\tconfig = new File(System.getProperty(\"user.home\") +\n\t\t\t\t\t\"/Library/Preferences/\" + toolName + \".settings\");\n\t\t} else if (os.indexOf(\"nix\") >= 0 || os.indexOf(\"nux\") >= 0 ||\n\t\t\t\tos.indexOf(\"aix\") >= 0 || os.indexOf(\"sunos\") >= 0 ||\n\t\t\t\tos.indexOf(\"bsd\") >= 0) { // Linux, AIX, Solaris, *BSD\n\t\t\t// check for $XDG_CONFIG_HOME\n\t\t\tString configBase = System.getenv(\"XDG_CONFIG_HOME\");\n\t\t\tif (configBase == null) {\n\t\t\t\tconfigBase = System.getProperty(\"user.home\") + \"/.config\";\n\t\t\t}\n\t\t\tif (configBase.endsWith(\"/\")) {\n\t\t\t\tconfigBase = configBase.substring(0, configBase.length() - 1);\n\t\t\t}\n\t\t\tconfig = new File(configBase + \"/\" + toolName + \".settings\");\n\t\t} else { // unknown operating system\n\t\t\t// use \"$HOME\\.prism\"\n\t\t\tconfig = new File(System.getProperty(\"user.home\") +\n\t\t\t\t\tFile.separator + \".\" + toolName);\n\t\t}\n\t\treturn config;\n\t}\n\t\n\tpublic synchronized void saveSettingsFile() throws PrismException\n\t{\n\t\tsaveSettingsFile(getLocationForSettingsFile());\n\t}\n\t\n\tpublic synchronized void saveSettingsFile(File file) throws PrismException\n\t{\n\t\t// first, we ensure the directories for the file that don't exist yet\n\t\t// are created\n\t\tFile parent = null;\n\t\ttry {\n\t\t\tparent = file.getAbsoluteFile().getParentFile();\n\t\t\tif (parent != null && !parent.exists()) {\n\t\t\t\tparent.mkdirs();\n\t\t\t}\n\t\t} catch (Exception e) {\n\t\t\tif (parent != null) {\n\t\t\t\tthrow new PrismException(\"Error creating required directories (\" + parent + \") for file \" + file + \": \" +e.getMessage());\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"Error creating required directories for file \" + file + \": \" +e.getMessage());\n\t\t\t}\n\t\t}\n\n\t\t// and now, we write the settings to file\n\t\ttry (FileWriter out = new FileWriter(file)) {\n\t\t\t\n\t\t\tout.write(\"# \" + Prism.getToolName() + \" settings file\\n\");\n\t\t\tout.write(\"# (created by version \"+Prism.getVersion()+\")\\n\");\n\t\t\t\n\t\t\tfor(int i = 0; i < optionOwners.length; i++)\n\t\t\t{\n\t\t\t\tout.write(\"\\n\");\n\t\t\t\tfor(int j = 0; j < optionOwners[i].getNumSettings(); j++)\n\t\t\t\t{\n\t\t\t\t\tSetting set = optionOwners[i].getSetting(j);\n\t\t\t\t\t//write the key\n\t\t\t\t\tout.write(set.getKey()+\"=\");\n\t\t\t\t\tString value = set.toString();\n\t\t\t\t\twhile(value.indexOf('\\n') != -1) //is multiline string\n\t\t\t\t\t{\n\t\t\t\t\t\tout.write(value.substring(0,value.indexOf('\\n')) + \"\\\\\");\n\t\t\t\t\t\tif(value.substring(value.indexOf('\\n')).length() > 0)\n\t\t\t\t\t\t\tvalue = value.substring(value.indexOf('\\n')+1);\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\tvalue = \"\";\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tout.write(value+\"\\n\");\n\t\t\t\t\t\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tout.close();\n\t\t\t\n\t\t}\n\t\tcatch(IOException e)\n\t\t{\n\t\t\tthrow new PrismException(\"Error exporting properties file: \"+e.getMessage());\n\t\t}\n\t\t\n\t\tmodified = false;\n\t}\n\t\n\tpublic synchronized void loadSettingsFile() throws PrismException\n\t{\n\t\tloadSettingsFile(getLocationForSettingsFile());\n\t}\n\t\n\tpublic synchronized void loadSettingsFile(File file) throws PrismException\n\t{\n\t\tBufferedReader reader;\n\t\tString line = null;\n\t\tString key = \"\";\n\t\tString value;\n\t\tint equalsIndex;\n\t\tStringBuffer multiline = new StringBuffer();\n\t\tboolean inMulti = false;\n\t\tString version;\n\t\tboolean resaveNeeded = false;\n\t\t\n\t\ttry\n\t\t{\n\t\t\t// Read first two lines to extract version\n\t\t\tversion = null;\n\t\t\treader = new BufferedReader(new FileReader(file));\n\t\t\tif (reader.ready()) line = reader.readLine();\n\t\t\tif (reader.ready()) line = reader.readLine();\n\t\t\tMatcher matcher =  Pattern.compile(\"# \\\\(created by version (.+)\\\\)\").matcher(line);\n\t\t\tif (matcher.find()) version = matcher.group(1);\n\t\t\treader.close();\n\t\t\t\n\t\t\t// Do we need to resave the file?\n\t\t\t// (i.e. is the version of the saved settings (a) old? (b) unparseable?)\n\t\t\tif (version == null) version = \"0\";\n\t\t\tif (PrismUtils.compareVersions(version, Prism.getVersion()) == -1) resaveNeeded = true;\n\t\t\t\n\t\t\t// Read whole file\n\t\t\treader = new BufferedReader(new FileReader(file));\n\t\t\twhile(reader.ready())\n\t\t\t{\n\t\t\t\tline = reader.readLine();\n\t\t\t\tif(!inMulti)\n\t\t\t\t{\n\t\t\t\t\tif(line.startsWith(\"#\")) continue; //ignore comments\n\t\t\t\t\tequalsIndex = line.indexOf('=');\n\t\t\t\t\tif(equalsIndex == -1) continue; //is not a valid property line\n\t\t\t\t\telse\n\t\t\t\t\t{\n\t\t\t\t\t\tkey = line.substring(0, equalsIndex);\n\t\t\t\t\t\tvalue = (equalsIndex==line.length()-1)?\"\":line.substring(equalsIndex+1);\n\t\t\t\t\t\tif(value.endsWith(\"\\\\\"))\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tinMulti = true;\n\t\t\t\t\t\t\tmultiline = new StringBuffer(value.substring(0, value.length()-1)); // trim the \\ off\n\t\t\t\t\t\t}\n\t\t\t\t\t\telse\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tSetting set = settingFromHash(key);\n\t\t\t\t\t\t\tif(set != null)\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t// If the version of the settings file is not newer than the \"version\" of the setting,\n\t\t\t\t\t\t\t\t// and we are re-saving the file, overwrite the setting with the default value \n\t\t\t\t\t\t\t\tif (resaveNeeded && PrismUtils.compareVersions(version, set.getVersion()) <= 0) continue;\n\t\t\t\t\t\t\t\ttry\n\t\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t\tObject valObj = set.parseStringValue(value);\n\t\t\t\t\t\t\t\t\tset.setValue(valObj);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tcatch(SettingException ee)\n\t\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t\tSystem.err.println(\"Warning: PRISM setting \\\"\"+key+\"\\\" has invalid value \\\"\" + value + \"\\\"\");\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t// Warning for unused options disabled for now\n\t\t\t\t\t\t\t\t// (it's a pain when you have lots of branches with lots of new options)\n\t\t\t\t\t\t\t\tif (false) {\n\t\t\t\t\t\t\t\t\t// Make sure this is not an old PRISM setting and if not print a warning\n\t\t\t\t\t\t\t\t\tboolean isOld = false;\n\t\t\t\t\t\t\t\t\tfor (int i = 0; i < oldPropertyNames.length; i++) {\n\t\t\t\t\t\t\t\t\t\tif (oldPropertyNames[i].equals(key)) {\n\t\t\t\t\t\t\t\t\t\t\tisOld = true;\n\t\t\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\tif (!isOld)\n\t\t\t\t\t\t\t\t\t\tSystem.err.println(\"Warning: PRISM setting \\\"\" + key + \"\\\" is unknown.\");\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\t//In multiline\n\t\t\t\t\tif(line.endsWith(\"\\\\\"))\n\t\t\t\t\t{\n\t\t\t\t\t\tmultiline.append(line.substring(0, line.length()-1));\n\t\t\t\t\t}\n\t\t\t\t\telse\n\t\t\t\t\t{\n\t\t\t\t\t\tSetting set = settingFromHash(key);\n\t\t\t\t\t\tif(set != null)\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\t// If the version of the settings file is not newer than the \"version\" of the setting,\n\t\t\t\t\t\t\t// and we are re-saving the file, overwrite the setting with the default value \n\t\t\t\t\t\t\tif (resaveNeeded && PrismUtils.compareVersions(version, set.getVersion()) <= 0) continue;\n\t\t\t\t\t\t\ttry\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tObject valObj = set.parseStringValue(multiline.toString() + line);\n\t\t\t\t\t\t\t\tset.setValue(valObj);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tcatch(SettingException ee)\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tSystem.err.println(\"Warning: PRISM setting \\\"\"+key+\"\\\" has invalid value \\\"\" + multiline.toString() + line + \"\\\"\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\telse\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tSystem.err.println(\"Warning: PRISM setting \\\"\"+key+\"\\\" is unknown.\");\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\tinMulti = false;\n\t\t\t\t\t\tmultiline = null;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tcatch(IOException e)\n\t\t{\n\t\t\tthrow new PrismException(\"Error importing properties file: \"+e.getMessage());\n\t\t}\n\t\t\n\t\tmodified = false;\n\t\t\n\t\t// If necessary, resave the preferences file\n\t\tif (resaveNeeded) {\n\t\t\ttry {\n\t\t\t\tsaveSettingsFile(file);\n\t\t\t}\n\t\t\tcatch (PrismException e) {\n\t\t\t}\n\t\t}\n\t\t\n\t\tnotifySettingsListeners();\n\t}\n\t\n\tpublic synchronized void loadDefaults()\n\t{\n\t\tfor(int i = 0; i < propertyOwnerIDs.length; i++)\n\t\t{\n\t\t\t\n\t\t\tfor(int j = 0; j < propertyData[i].length; j++)\n\t\t\t{\n\t\t\t\tSetting set = settingFromHash(propertyData[i][j][1].toString());\n\t\t\t\n\t\t\t\tif(set != null)\n\t\t\t\t{\n\t\t\t\t\ttry\n\t\t\t\t\t{\n\t\t\t\t\t\tset.setValue(propertyData[i][j][4]);\n\t\t\t\t\t}\n\t\t\t\t\tcatch(SettingException e)\n\t\t\t\t\t{\n\t\t\t\t\t\tSystem.err.println(\"Warning: Error with default value for PRISM setting \\\"\"+set.getName()+\"\\\"\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tnotifySettingsListeners();\n\t}\n\n\t// HIDDEN OPTIONS\n\t\n\t// Export property automaton info?\n\tprotected boolean exportPropAut = false;\n\tprotected String exportPropAutType = \"txt\";\n\tprotected String exportPropAutFilename = \"da.txt\";\n\t\n\tpublic void setExportPropAut(boolean b) throws PrismException\n\t{\n\t\texportPropAut = b;\n\t}\n\n\tpublic void setExportPropAutType(String s) throws PrismException\n\t{\n\t\texportPropAutType = s;\n\t}\n\n\tpublic void setExportPropAutFilename(String s) throws PrismException\n\t{\n\t\texportPropAutFilename = s;\n\t}\n\n\tpublic boolean getExportPropAut()\n\t{\n\t\treturn exportPropAut;\n\t}\n\n\tpublic String getExportPropAutType()\n\t{\n\t\treturn exportPropAutType;\n\t}\n\n\tpublic String getExportPropAutFilename()\n\t{\n\t\treturn exportPropAutFilename;\n\t}\n\n\t/**\n\t * Set an option by parsing one or more command-line arguments.\n\t * Reads the ith argument (assumed to be in the form \"-switch\")\n\t * and also any subsequent arguments required as parameters.\n\t * Return the index of the next argument to be read.\n\t * @param args Full list of arguments\n\t * @param i Index of first argument to read\n\t */\n\tpublic synchronized int setFromCommandLineSwitch(String args[], int i) throws PrismException\n\t{\n\t\tString s;\n\t\tint j;\n\t\tdouble d;\n\t\t\n\t\t// Process string (remove - and extract any options) \n\t\tPair<String, String> pair = splitSwitch(args[i]);\n\t\tString sw = pair.first;\n\t\tString optionsString = pair.second;\n\t\tMap<String, String> options = splitOptionsString(optionsString);\n\t\t\n\t\t// Note: the order of these switches should match the -help output (just to help keep track of things).\n\t\t\n\t\t// ENGINES/METHODS:\n\t\t\n\t\t// Main model checking engine\n\t\tif (sw.equals(\"mtbdd\") || sw.equals(\"m\")) {\n\t\t\tset(PRISM_ENGINE, \"MTBDD\");\n\t\t}\n\t\telse if (sw.equals(\"sparse\") || sw.equals(\"s\")) {\n\t\t\tset(PRISM_ENGINE, \"Sparse\");\n\t\t}\n\t\telse if (sw.equals(\"hybrid\") || sw.equals(\"h\")) {\n\t\t\tset(PRISM_ENGINE, \"Hybrid\");\n\t\t}\n\t\telse if (sw.equals(\"explicit\") || sw.equals(\"ex\")) {\n\t\t\tset(PRISM_ENGINE, \"Explicit\");\n\t\t}\n\t\t// Exact model checking\n\t\telse if (sw.equals(\"exact\")) {\n\t\t\tset(PRISM_EXACT_ENABLED, true);\n\t\t}\n\t\t// PTA model checking methods\n\t\telse if (sw.equals(\"ptamethod\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ts = args[++i];\n\t\t\t\tif (s.equals(\"digital\"))\n\t\t\t\t\tset(PRISM_PTA_METHOD, \"Digital clocks\");\n\t\t\t\telse if (s.equals(\"games\"))\n\t\t\t\t\tset(PRISM_PTA_METHOD, \"Stochastic games\");\n\t\t\t\telse if (s.equals(\"backwards\") || s.equals(\"bw\"))\n\t\t\t\t\tset(PRISM_PTA_METHOD, \"Backwards reachability\");\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: digital, games, backwards)\");\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No parameter specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Transient methods\n\t\telse if (sw.equals(\"transientmethod\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ts = args[++i];\n\t\t\t\tif (s.equals(\"unif\"))\n\t\t\t\t\tset(PRISM_TRANSIENT_METHOD, \"Uniformisation\");\n\t\t\t\telse if (s.equals(\"fau\"))\n\t\t\t\t\tset(PRISM_TRANSIENT_METHOD, \"Fast adaptive uniformisation\");\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: unif, fau)\");\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No parameter specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Heuristic modes\n\t\telse if (sw.equals(\"heuristic\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ts = args[++i];\n\t\t\t\tif (s.equals(\"none\"))\n\t\t\t\t\tset(PRISM_HEURISTIC, \"None\");\n\t\t\t\telse if (s.equals(\"speed\"))\n\t\t\t\t\tset(PRISM_HEURISTIC, \"Speed\");\n\t\t\t\telse if (s.equals(\"memory\"))\n\t\t\t\t\tset(PRISM_HEURISTIC, \"Memory\");\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: none, speed, memory)\");\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No parameter specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\n\t\t// NUMERICAL SOLUTION OPTIONS:\n\t\t\n\t\t// Linear equation solver + MDP soln method\n\t\telse if (sw.equals(\"power\") || sw.equals(\"pow\") || sw.equals(\"pwr\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Power\");\n\t\t} else if (sw.equals(\"jacobi\") || sw.equals(\"jac\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Jacobi\");\n\t\t} else if (sw.equals(\"gaussseidel\") || sw.equals(\"gs\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Gauss-Seidel\");\n\t\t\tset(PRISM_MDP_SOLN_METHOD, \"Gauss-Seidel\");\n\t\t\tset(PRISM_MDP_MULTI_SOLN_METHOD, \"Gauss-Seidel\");\n\t\t\tset(PRISM_IMDP_SOLN_METHOD, \"Gauss-Seidel\");\n\t\t} else if (sw.equals(\"bgaussseidel\") || sw.equals(\"bgs\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Backwards Gauss-Seidel\");\n\t\t} else if (sw.equals(\"pgaussseidel\") || sw.equals(\"pgs\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Pseudo-Gauss-Seidel\");\n\t\t} else if (sw.equals(\"bpgaussseidel\") || sw.equals(\"bpgs\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Backwards Pseudo-Gauss-Seidel\");\n\t\t} else if (sw.equals(\"jor\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"JOR\");\n\t\t} else if (sw.equals(\"sor\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"SOR\");\n\t\t} else if (sw.equals(\"bsor\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Backwards SOR\");\n\t\t} else if (sw.equals(\"psor\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Pseudo-SOR\");\n\t\t} else if (sw.equals(\"bpsor\")) {\n\t\t\tset(PRISM_LIN_EQ_METHOD, \"Backwards Pseudo-SOR\");\n\t\t} else if (sw.equals(\"valiter\")) {\n\t\t\tset(PRISM_MDP_SOLN_METHOD, \"Value iteration\");\n\t\t\tset(PRISM_MDP_MULTI_SOLN_METHOD, \"Value iteration\");\n\t\t\tset(PRISM_IMDP_SOLN_METHOD, \"Value iteration\");\n\t\t} else if (sw.equals(\"politer\")) {\n\t\t\tset(PRISM_MDP_SOLN_METHOD, \"Policy iteration\");\n\t\t} else if (sw.equals(\"modpoliter\")) {\n\t\t\tset(PRISM_MDP_SOLN_METHOD, \"Modified policy iteration\");\n\t\t} else if (sw.equals(\"linprog\") || sw.equals(\"lp\")) {\n\t\t\tset(PRISM_MDP_SOLN_METHOD, \"Linear programming\");\n\t\t\tset(PRISM_MDP_MULTI_SOLN_METHOD, \"Linear programming\");\n\t\t}\n\n\t\t// Interval iterations\n\t\telse if (sw.equals(\"intervaliter\") ||\n\t\t         sw.equals(\"ii\")) {\n\t\t\tset(PRISM_INTERVAL_ITER, true);\n\n\t\t\tif (optionsString != null) {\n\t\t\t\toptionsString = optionsString.trim();\n\t\t\t\ttry {\n\t\t\t\t\tOptionsIntervalIteration.validate(optionsString);\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\tthrow new PrismException(\"In options for -\" + sw + \" switch: \" + e.getMessage());\n\t\t\t\t}\n\n\t\t\t\t// append options to existing ones\n\t\t\t\tString iiOptions = getString(PRISM_INTERVAL_ITER_OPTIONS);\n\t\t\t\tif (\"\".equals(iiOptions))\n\t\t\t\t\tiiOptions = optionsString;\n\t\t\t\telse\n\t\t\t\t\tiiOptions += \",\" + optionsString;\n\t\t\t\tset(PRISM_INTERVAL_ITER_OPTIONS, iiOptions);\n\t\t\t}\n\t\t}\n\n\t\t// Pmax quotient\n\t\telse if (sw.equals(\"pmaxquotient\")) {\n\t\t\tset(PRISM_PMAX_QUOTIENT, true);\n\t\t}\n\n\t\t// Topological VI\n\t\telse if (sw.equals(\"topological\")) {\n\t\t\tset(PRISM_TOPOLOGICAL_VI, true);\n\t\t}\n\n\t\t// Linear equation solver over-relaxation parameter\n\t\telse if (sw.equals(\"omega\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\t\tset(PRISM_LIN_EQ_METHOD_PARAM, d);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Termination criterion (iterative methods)\n\t\telse if (sw.equals(\"relative\") || sw.equals(\"rel\")) {\n\t\t\tset(PRISM_TERM_CRIT, \"Relative\");\n\t\t}\n\t\telse if (sw.equals(\"absolute\") || sw.equals(\"abs\")) {\n\t\t\tset(PRISM_TERM_CRIT, \"Absolute\");\n\t\t}\n\t\t// Termination criterion parameter\n\t\telse if (sw.equals(\"epsilon\") || sw.equals(\"e\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\t\tif (d < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_TERM_CRIT_PARAM, d);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Max iters\n\t\telse if (sw.equals(\"maxiters\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_MAX_ITERS, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// export iterations\n\t\telse if (sw.equals(\"exportiterations\")) {\n\t\t\tset(PRISM_EXPORT_ITERATIONS, true);\n\t\t}\n\t\t// fixed grid resolution\n\t\telse if (sw.equals(\"gridresolution\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_GRID_RESOLUTION, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// export probabilities/rewards with up to n significant decimal places\n\t\telse if (sw.equals(\"exportmodelprecision\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tint precision = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (!RANGE_EXPORT_DOUBLE_PRECISION.contains(precision))\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_EXPORT_MODEL_PRECISION, precision);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// export headers off\n\t\telse if (sw.equals(\"noexportheaders\")) {\n\t\t\tset(PRISM_EXPORT_MODEL_HEADERS, false);\n\t\t}\n\n\t\t// MODEL CHECKING OPTIONS:\n\t\t\n\t\t// Precomputation algs off\n\t\telse if (sw.equals(\"nopre\")) {\n\t\t\tset(PRISM_PRECOMPUTATION, false);\n\t\t}\n\t\telse if (sw.equals(\"noprob0\")) {\n\t\t\tset(PRISM_PROB0, false);\n\t\t}\n\t\telse if (sw.equals(\"noprob1\")) {\n\t\t\tset(PRISM_PROB1, false);\n\t\t}\n\t\t// Use predecessor relation? (e.g. for precomputation)\n\t\telse if (sw.equals(\"noprerel\")) {\n\t\t\tset(PRISM_PRE_REL, false);\n\t\t}\n\t\t// Fix deadlocks on/off\n\t\telse if (sw.equals(\"fixdl\")) {\n\t\t\tset(PRISM_FIX_DEADLOCKS, true);\n\t\t}\n\t\telse if (sw.equals(\"nofixdl\")) {\n\t\t\tset(PRISM_FIX_DEADLOCKS, false);\n\t\t}\n\t\t// Fairness on/off\n\t\telse if (sw.equals(\"fair\")) {\n\t\t\tset(PRISM_FAIRNESS, true);\n\t\t}\n\t\telse if (sw.equals(\"nofair\")) {\n\t\t\tset(PRISM_FAIRNESS, false);\n\t\t}\n\t\t// Prob/rate checks off\n\t\telse if (sw.equals(\"noprobchecks\")) {\n\t\t\tset(PRISM_DO_PROB_CHECKS, false);\n\t\t}\n\t\t// Sum round-off threshold\n\t\telse if (sw.equals(\"sumroundoff\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\t\tif (d < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_SUM_ROUND_OFF, d);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// No steady-state detection\n\t\telse if (sw.equals(\"nossdetect\")) {\n\t\t\tset(PRISM_DO_SS_DETECTION, false);\n\t\t}\n\t\t// SCC computation algorithm\n\t\telse if (sw.equals(\"sccmethod\") || sw.equals(\"bsccmethod\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ts = args[++i];\n\t\t\t\tif (s.equals(\"xiebeerel\"))\n\t\t\t\t\tset(PRISM_SCC_METHOD, \"Xie-Beerel\");\n\t\t\t\telse if (s.equals(\"lockstep\"))\n\t\t\t\t\tset(PRISM_SCC_METHOD, \"Lockstep\");\n\t\t\t\telse if (s.equals(\"sccfind\"))\n\t\t\t\t\tset(PRISM_SCC_METHOD, \"SCC-Find\");\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: xiebeerel, lockstep, sccfind)\");\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No parameter specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Enable symmetry reduction\n\t\telse if (sw.equals(\"symm\")) {\n\t\t\tif (i < args.length - 2) {\n\t\t\t\tset(PRISM_SYMM_RED_PARAMS, args[++i] + \" \" + args[++i]);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"-symm switch requires two parameters (num. modules before/after symmetric ones)\");\n\t\t\t}\n\t\t}\n\t\t// Abstraction-refinement engine options string (append if already partially specified)\n\t\telse if (sw.equals(\"aroptions\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tString arOptions = getString(PRISM_AR_OPTIONS);\n\t\t\t\tif (\"\".equals(arOptions))\n\t\t\t\t\tarOptions = args[++i].trim();\n\t\t\t\telse\n\t\t\t\t\tarOptions += \",\" + args[++i].trim();\n\t\t\t\tset(PRISM_AR_OPTIONS, arOptions);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No parameter specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Handle all path formulas via automata constructions\n\t\telse if (sw.equals(\"pathviaautomata\")) {\n\t\t\tset(PRISM_PATH_VIA_AUTOMATA, true);\n\t\t}\n\t\t// Don't simplify deterministic automata\n\t\telse if (sw.equals(\"nodasimplify\")) {\n\t\t\tset(PRISM_NO_DA_SIMPLIFY, true);\n\t\t}\n\n\t\t\n\t\t// MULTI-OBJECTIVE MODEL CHECKING OPTIONS:\n\t\t\n\t\t// Max different corner points that will be generated when performing\n\t\t// target driven multi-obj verification.\n\t\telse if (sw.equals(\"multimaxpoints\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_MULTI_MAX_POINTS, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Threshold for approximate Pareto curve generation\n\t\telse if (sw.equals(\"paretoepsilon\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\t\tif (d < 0)\n\t\t\t\t\t\tthrow new PrismException(\"Value for -\" + sw + \" switch must be non-negative\");\n\t\t\t\t\tset(PRISM_PARETO_EPSILON, d);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"exportpareto\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tset(PRISM_EXPORT_PARETO_FILENAME, args[++i]);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No file specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t\n\t\t// OUTPUT OPTIONS:\n\t\t\n\t\t// Verbosity\n\t\telse if (sw.equals(\"verbose\") || sw.equals(\"v\")) {\n\t\t\tset(PRISM_VERBOSE, true);\n\t\t}\n\t\t// Extra dd info on\n\t\telse if (sw.equals(\"extraddinfo\")) {\n\t\t\tset(PRISM_EXTRA_DD_INFO, true);\n\t\t}\n\t\t// Extra reach info on\n\t\telse if (sw.equals(\"extrareachinfo\")) {\n\t\t\tset(PRISM_EXTRA_REACH_INFO, true);\n\t\t}\n\t\t\n\t\t// SPARSE/HYBRID/MTBDD OPTIONS:\n\t\t\n\t\t// Turn off compact option for sparse matrix storage\n\t\telse if (sw.equals(\"nocompact\")) {\n\t\t\tset(PRISM_COMPACT, false);\n\t\t}\n\t\t// Sparse bits info\n\t\telse if (sw.equals(\"sbl\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < -1)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\tset(PRISM_NUM_SB_LEVELS, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"sbmax\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < 0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\tset(PRISM_SB_MAX_MEM, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Hybrid SOR info\n\t\telse if (sw.equals(\"sorl\") || sw.equals(\"gsl\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < -1)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\tset(PRISM_NUM_SOR_LEVELS, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"sormax\") || sw.equals(\"gsmax\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < 0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\tset(PRISM_SOR_MAX_MEM, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// CUDD settings\n\t\telse if (sw.equals(\"cuddmaxmem\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tset(PRISM_CUDD_MAX_MEM, args[++i]);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"cuddepsilon\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\t\tif (d < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_CUDD_EPSILON, d);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t} else if (sw.equals(\"ddextrastatevars\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tint v = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (v < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_DD_EXTRA_STATE_VARS, v);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t} else if (sw.equals(\"ddextraactionvars\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tint v = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (v < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_DD_EXTRA_ACTION_VARS, v);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t\n\t\t// ADVERSARIES/COUNTEREXAMPLES:\n\t\t\n\t\t// Export adversary to file\n\t\telse if (sw.equals(\"exportadv\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tset(PRISM_EXPORT_ADV, \"DTMC\");\n\t\t\t\tset(PRISM_EXPORT_ADV_FILENAME, args[++i]);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No file specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Export adversary to file, as an MDP\n\t\telse if (sw.equals(\"exportadvmdp\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tset(PRISM_EXPORT_ADV, \"MDP\");\n\t\t\t\tset(PRISM_EXPORT_ADV_FILENAME, args[++i]);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No file specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t\n\t\t// LTL2DA TOOLS\n\t\t\n\t\telse if (sw.equals(\"ltl2datool\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tString filename = args[++i];\n\t\t\t\tset(PRISM_LTL2DA_TOOL, filename);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"The -\" + sw + \" switch requires one argument (path to the executable)\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"ltl2dasyntax\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tString syntax = args[++i];\n\t\t\t\tswitch (syntax) {\n\t\t\t\tcase \"lbt\":\n\t\t\t\t\tset(PRISM_LTL2DA_SYNTAX, \"LBT\");\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"spin\":\n\t\t\t\t\tset(PRISM_LTL2DA_SYNTAX, \"Spin\");\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"spot\":\n\t\t\t\t\tset(PRISM_LTL2DA_SYNTAX, \"Spot\");\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"rabinizer\":\n\t\t\t\t\tset(PRISM_LTL2DA_SYNTAX, \"Rabinizer\");\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: lbt, spin, spot, rabinizer)\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"The -\" + sw + \" switch requires one argument (options are: lbt, spin, spot, rabinizer)\");\n\t\t\t}\n\t\t}\n\n\t\t// DEBUGGING / SANITY CHECKS\n\t\telse if (sw.equals(\"ddsanity\")) {\n\t\t\tset(PRISM_JDD_SANITY_CHECKS, true);\n\t\t}\n\n\t\t// PARAMETRIC MODEL CHECKING:\n\t\t\n\t\telse if (sw.equals(\"param\")) {\n\t\t\tset(PRISM_PARAM_ENABLED, true);\n\t\t}\n\t\telse if (sw.equals(\"paramprecision\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tset(PRISM_PARAM_PRECISION, args[++i]);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"paramsplit\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ts = args[++i];\n\t\t\t\tif (s.equals(\"longest\"))\n\t\t\t\t\tset(PRISM_PARAM_SPLIT, \"Longest\");\n\t\t\t\telse if (s.equals(\"all\"))\n\t\t\t\t\tset(PRISM_PARAM_SPLIT, \"All\");\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: longest, all)\");\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"parambisim\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ts = args[++i];\n\t\t\t\tif (s.equals(\"strong\"))\n\t\t\t\t\tset(PRISM_PARAM_BISIM, \"Strong\");\n\t\t\t\telse if (s.equals(\"weak\"))\n\t\t\t\t\tset(PRISM_PARAM_BISIM, \"Weak\");\n\t\t\t\telse if (s.equals(\"none\"))\n\t\t\t\t\tset(PRISM_PARAM_BISIM, \"None\");\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: strong, weak, none)\");\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"paramfunction\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ts = args[++i];\n\t\t\t\tif (s.equals(\"jascached\"))\n\t\t\t\t\tset(PRISM_PARAM_FUNCTION, \"JAS-cached\");\n\t\t\t\telse if (s.equals(\"jas\"))\n\t\t\t\t\tset(PRISM_PARAM_FUNCTION, \"JAS\");\n\t\t\t\telse if (s.equals(\"dag\"))\n\t\t\t\t\tset(PRISM_PARAM_FUNCTION, \"DAG\");\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: jascached, jas, dag)\");\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"paramelimorder\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ts = args[++i];\n\t\t\t\tif (s.equals(\"arb\"))\n\t\t\t\t\tset(PRISM_PARAM_ELIM_ORDER, \"Arbitrary\");\n\t\t\t\telse if (s.equals(\"fw\"))\n\t\t\t\t\tset(PRISM_PARAM_ELIM_ORDER, \"Forward\");\n\t\t\t\telse if (s.equals(\"fwrev\"))\n\t\t\t\t\tset(PRISM_PARAM_ELIM_ORDER, \"Forward-reversed\");\n\t\t\t\telse if (s.equals(\"bw\"))\n\t\t\t\t\tset(PRISM_PARAM_ELIM_ORDER, \"Backward\");\n\t\t\t\telse if (s.equals(\"bwrev\"))\n\t\t\t\t\tset(PRISM_PARAM_ELIM_ORDER, \"Backward-reversed\");\n\t\t\t\telse if (s.equals(\"rand\"))\n\t\t\t\t\tset(PRISM_PARAM_ELIM_ORDER, \"Random\");\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Unrecognised option for -\" + sw + \" switch (options are: arb,fw,fwrev,bw,bwrev,rand)\");\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"paramrandompoints\")) {\n\t\t\ttry {\n\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\tif (j < 0)\n\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\tset(PRISM_PARAM_RANDOM_POINTS, j);\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"paramsubsumeregions\")) {\n\t\t\tboolean b = Boolean.parseBoolean(args[++i]);\n\t\t\tset(PRISM_PARAM_SUBSUME_REGIONS, b);\n\t\t}\n\t\telse if (sw.equals(\"paramdagmaxerror\")) {\n\t\t\ttry {\n\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\tif (d < 0)\n\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\tset(PRISM_PARAM_DAG_MAX_ERROR, d);\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t\n\t\t// FAST ADAPTIVE UNIFORMISATION\n\t\t\n\t\t// Epsilon for fast adaptive uniformisation\n\t\telse if (sw.equals(\"fauepsilon\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\t\tif (d < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_FAU_EPSILON, d);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Delta for fast adaptive uniformisation\n\t\telse if (sw.equals(\"faudelta\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\t\tif (d < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_FAU_DELTA, d);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t// Array threshold for fast adaptive uniformisation\n\t\telse if (sw.equals(\"fauarraythreshold\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_FAU_ARRAYTHRESHOLD, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\t\t\t\n\t\t}\n\t\t// Number of intervals for fast adaptive uniformisation\n\t\telse if (sw.equals(\"fauintervals\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\tj = Integer.parseInt(args[++i]);\n\t\t\t\t\tif (j < 0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_FAU_INTERVALS, j);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\telse if (sw.equals(\"fauinitival\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\ttry {\n\t\t\t\t\td = Double.parseDouble(args[++i]);\n\t\t\t\t\tif (d < 0.0)\n\t\t\t\t\t\tthrow new NumberFormatException(\"\");\n\t\t\t\t\tset(PRISM_FAU_INITIVAL, d);\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid value for -\" + sw + \" switch\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No value specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\n\t\t// HIDDEN OPTIONS\n\t\t\n\t\t// export property automaton to file (hidden option)\n\t\telse if (sw.equals(\"exportpropaut\")) {\n\t\t\tif (i < args.length - 1) {\n\t\t\t\tsetExportPropAut(true);\n\t\t\t\tsetExportPropAutFilename(args[++i]);\n\t\t\t\tsetExportPropAutType(\"txt\");  // default\n\t\t\t\tfor (Map.Entry<String, String> option : options.entrySet()) {\n\t\t\t\t    if (option.getKey().equals(\"txt\")) {\n\t\t\t\t\t\tsetExportPropAutType(\"txt\");\n\t\t\t\t    } else if (option.getKey().equals(\"dot\")) {\n\t\t\t\t\t\tsetExportPropAutType(\"dot\");\n\t\t\t\t    } else if (option.getKey().equals(\"hoa\")) {\n\t\t\t\t\t\tsetExportPropAutType(\"hoa\");\n\t\t\t\t    } else {\n\t\t\t\t    \t\tthrow new PrismException(\"Unknown option \\\"\" + option.getKey() + \"\\\" for -\" + sw + \" switch\"); \n\t\t\t\t    }\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"No file specified for -\" + sw + \" switch\");\n\t\t\t}\n\t\t}\n\t\t\n\t\t// unknown switch - error\n\t\telse {\n\t\t\tthrow new PrismException(\"Invalid switch -\" + sw + \" (type \\\"prism -help\\\" for full list)\");\n\t\t}\n\t\t\n\t\treturn i + 1;\n\t}\n\t\n\t/**\n\t * Split a switch of the form -switch:options into parts.\n\t * The latter can be empty, in which case the : is optional.\n\t * When present, the options is a comma-separated list of \"option\" or \"option=value\" items.\n\t * The switch itself can be prefixed with either 1 or 2 hyphens.\n\t * \n\t * @return a pair containing the switch name and the (optional, may be null) options part\n\t */\n\tprivate static Pair<String, String> splitSwitch(String sw)\n\t{\n\t\t// Remove \"-\"\n\t\tsw = sw.substring(1);\n\t\t// Remove optional second \"-\" (i.e. we allow switches of the form --sw too)\n\t\tif (sw.charAt(0) == '-')\n\t\t\tsw = sw.substring(1);\n\t\t// Extract options, if present\n\t\tint i = sw.indexOf(':');\n\n\t\tString optionsString = null;\n\t\tif (i != -1) {\n\t\t\toptionsString = sw.substring(i + 1);\n\t\t\tsw = sw.substring(0, i);\n\t\t}\n\n\t\treturn new Pair<String, String>(sw, optionsString);\n\t}\n\n\t/**\n\t * Split an options string (see splitSwitch)\n\t * into a map from options to values.\n\t * <br>\n\t * For \"option\" options, the value is {@code null}.\n\t * @return a mapping from options to values.\n\t */\n\tprivate static Map<String, String> splitOptionsString(String optionsString)\n\t{\n\t\tMap<String,String> map = new HashMap<String, String>();\n\t\tif (optionsString == null || \"\".equals(optionsString))\n\t\t\treturn map;\n\n\t\tString options[] = optionsString.split(\",\");\n\t\tfor (String option : options) {\n\t\t\tint j = option.indexOf(\"=\");\n\t\t\tif (j == -1) {\n\t\t\t\tmap.put(option, null);\n\t\t\t} else {\n\t\t\t\tmap.put(option.substring(0,j), option.substring(j+1));\n\t\t\t}\n\t\t}\n\n\t\treturn map;\n\t}\n\n\t/**\n\t * Print a fragment of the -help message,\n\t * i.e. a list of the command-line switches handled by this class.\n\t */\n\tpublic static void printHelp(PrismLog mainLog)\n\t{\n\t\tmainLog.println();\n\t\tmainLog.println(\"EXPORT OPTIONS:\");\n\t\tmainLog.println(\"-exportmodelprecision <n>....... Export probabilities/rewards with n significant decimal places\");\n\t\tmainLog.println(\"-noexportheaders ............... Don't include headers when exporting rewards\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"ENGINES/METHODS:\");\n\t\tmainLog.println(\"-mtbdd (or -m) ................. Use the MTBDD engine\");\n\t\tmainLog.println(\"-sparse (or -s) ................ Use the Sparse engine\");\n\t\tmainLog.println(\"-hybrid (or -h) ................ Use the Hybrid engine [default]\");\n\t\tmainLog.println(\"-explicit (or -ex) ............. Use the explicit engine\");\n\t\tmainLog.println(\"-exact ......................... Perform exact (arbitrary precision) model checking\");\n\t\tmainLog.println(\"-ptamethod <name> .............. Specify PTA engine (games, digital, backwards) [default: games]\");\n\t\tmainLog.println(\"-transientmethod <name> ........ CTMC transient analysis method (unif, fau) [default: unif]\");\n\t\tmainLog.println(\"-heuristic <mode> .............. Automatic choice of engines/settings (none, speed, memory) [default: none]\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"SOLUTION METHODS (LINEAR EQUATIONS):\");\n\t\tmainLog.println(\"-power (or -pow, -pwr) ......... Use the Power method for numerical computation\");\n\t\tmainLog.println(\"-jacobi (or -jac) .............. Use Jacobi for numerical computation [default]\");\n\t\tmainLog.println(\"-gaussseidel (or -gs) .......... Use Gauss-Seidel for numerical computation\");\n\t\tmainLog.println(\"-bgaussseidel (or -bgs) ........ Use Backwards Gauss-Seidel for numerical computation\");\n\t\tmainLog.println(\"-pgaussseidel (or -pgs) ........ Use Pseudo Gauss-Seidel for numerical computation\");\n\t\tmainLog.println(\"-bpgaussseidel (or -bpgs) ...... Use Backwards Pseudo Gauss-Seidel for numerical computation\");\n\t\tmainLog.println(\"-jor ........................... Use JOR for numerical computation\");\n\t\tmainLog.println(\"-sor ........................... Use SOR for numerical computation\");\n\t\tmainLog.println(\"-bsor .......................... Use Backwards SOR for numerical computation\");\n\t\tmainLog.println(\"-psor .......................... Use Pseudo SOR for numerical computation\");\n\t\tmainLog.println(\"-bpsor ......................... Use Backwards Pseudo SOR for numerical computation\");\n\t\tmainLog.println(\"-omega <x> ..................... Set over-relaxation parameter (for JOR/SOR/...) [default: 0.9]\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"SOLUTION METHODS (MDPS):\");\n\t\tmainLog.println(\"-valiter ....................... Use value iteration for solving MDPs [default]\");\n\t\tmainLog.println(\"-gaussseidel (or -gs) .......... Use Gauss-Seidel value iteration for solving MDPs\");\n\t\tmainLog.println(\"-politer ....................... Use policy iteration for solving MDPs\");\n\t\tmainLog.println(\"-modpoliter .................... Use modified policy iteration for solving MDPs\");\n\t\tmainLog.println(\"-intervaliter (or -ii) ......... Use interval iteration to solve MDPs/MCs (see -help -ii)\");\n\t\tmainLog.println(\"-topological ................... Use topological value iteration\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"SOLUTION METHOD SETTINGS\");\n\t\tmainLog.println(\"-relative (or -rel) ............ Use relative error for detecting convergence [default]\");\n\t\tmainLog.println(\"-absolute (or -abs) ............ Use absolute error for detecting convergence\");\n\t\tmainLog.println(\"-epsilon <x> (or -e <x>) ....... Set value of epsilon (for convergence check) [default: 1e-6]\");\n\t\tmainLog.println(\"-maxiters <n> .................. Set max number of iterations [default: 10000]\");\n\t\tmainLog.println(\"-gridresolution <n> .............Set resolution for fixed grid approximation (POMDP) [default: 10]\");\n\t\t\n\t\tmainLog.println();\n\t\tmainLog.println(\"MODEL CHECKING OPTIONS:\");\n\t\tmainLog.println(\"-nopre ......................... Skip precomputation algorithms (where optional)\");\n\t\tmainLog.println(\"-noprob0 ....................... Skip precomputation algorithm Prob0 (where optional)\");\n\t\tmainLog.println(\"-noprob1 ....................... Skip precomputation algorithm Prob1 (where optional)\");\n\t\tmainLog.println(\"-noprerel ...................... Do not pre-compute/use predecessor relation, e.g. for precomputation\");\n\t\tmainLog.println(\"-fair .......................... Use fairness (for model checking of MDPs)\");\n\t\tmainLog.println(\"-nofair ........................ Don't use fairness (for model checking of MDPs) [default]\");\n\t\tmainLog.println(\"-fixdl ......................... Automatically put self-loops in deadlock states [default]\");\n\t\tmainLog.println(\"-nofixdl ....................... Do not automatically put self-loops in deadlock states\");\n\t\tmainLog.println(\"-noprobchecks .................. Disable checks on model probabilities/rates\");\n\t\tmainLog.println(\"-sumroundoff <x> ............... Set probability sum threshold [default: 1-e5]\");\n\t\tmainLog.println(\"-zerorewardcheck ............... Check for absence of zero-reward loops\");\n\t\tmainLog.println(\"-nossdetect .................... Disable steady-state detection for CTMC transient computations\");\n\t\tmainLog.println(\"-sccmethod <name> .............. Specify (symbolic) SCC computation method (xiebeerel, lockstep, sccfind)\");\n\t\tmainLog.println(\"-symm <string> ................. Symmetry reduction options string\");\n\t\tmainLog.println(\"-aroptions <string> ............ Abstraction-refinement engine options string\");\n\t\tmainLog.println(\"-pathviaautomata ............... Handle all path formulas via automata constructions\");\n\t\tmainLog.println(\"-nodasimplify .................. Do not attempt to simplify deterministic automata, acceptance conditions\");\n\t\tmainLog.println(\"-exportadv <file> .............. Export an adversary from MDP model checking (as a DTMC)\");\n\t\tmainLog.println(\"-exportadvmdp <file> ........... Export an adversary from MDP model checking (as an MDP)\");\n\t\tmainLog.println(\"-ltl2datool <exec> ............. Run executable <exec> to convert LTL formulas to deterministic automata\");\n\t\tmainLog.println(\"-ltl2dasyntax <x> .............. Specify output format for -ltl2datool switch (lbt, spin, spot, rabinizer)\");\n\t\tmainLog.println(\"-exportiterations .............. Export vectors for iteration algorithms to file\");\n\t\tmainLog.println(\"-pmaxquotient .................. For Pmax computations in MDPs, compute in the MEC quotient\");\n\t\t\n\t\tmainLog.println();\n\t\tmainLog.println(\"MULTI-OBJECTIVE MODEL CHECKING:\");\n\t\tmainLog.println(\"-linprog (or -lp) .............. Use linear programming for multi-objective model checking\");\n\t\tmainLog.println(\"-multimaxpoints <n> ............ Maximal number of corner points for (valiter-based) multi-objective\");\n\t\tmainLog.println(\"-paretoepsilon <x> ............. Threshold for Pareto curve approximation\");\n\t\tmainLog.println(\"-exportpareto <file> ........... When computing Pareto curves, export points to a file\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"OUTPUT OPTIONS:\");\n\t\tmainLog.println(\"-verbose (or -v) ............... Verbose mode: print out state lists and probability vectors\");\n\t\tmainLog.println(\"-extraddinfo ................... Display extra info about some (MT)BDDs\");\n\t\tmainLog.println(\"-extrareachinfo ................ Display extra info about progress of reachability\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"SPARSE/HYBRID/MTBDD OPTIONS:\");\n\t\tmainLog.println(\"-nocompact ..................... Switch off \\\"compact\\\" sparse storage schemes\");\n\t\tmainLog.println(\"-sbl <n> ....................... Set number of levels (for hybrid engine) [default: -1]\");\n\t\tmainLog.println(\"-sbmax <n> ..................... Set memory limit (KB) (for hybrid engine) [default: 1024]\");\n\t\tmainLog.println(\"-gsl <n> (or sorl <n>) ......... Set number of levels for hybrid GS/SOR [default: -1]\");\n\t\tmainLog.println(\"-gsmax <n> (or sormax <n>) ..... Set memory limit (KB) for hybrid GS/SOR [default: 1024]\");\n\t\tmainLog.println(\"-cuddmaxmem <n> ................ Set max memory for CUDD package, e.g. 125k, 50m, 4g [default: 1g]\");\n\t\tmainLog.println(\"-cuddepsilon <x> ............... Set epsilon value for CUDD package [default: 1e-15]\");\n\t\tmainLog.println(\"-ddsanity ...................... Enable internal sanity checks (causes slow-down)\");\n\t\tmainLog.println(\"-ddextrastatevars <n> .......... Set the number of preallocated state vars [default: 20]\");\n\t\tmainLog.println(\"-ddextraactionvars <n> ......... Set the number of preallocated action vars [default: 20]\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"PARAMETRIC MODEL CHECKING OPTIONS:\");\n\t\tmainLog.println(\"-param <vals> .................. Do parametric model checking with parameters (and ranges) <vals>\");\n\t\tmainLog.println(\"-paramprecision <x> ............ Set max undecided region for parameter synthesis [default: 5/100]\");\n\t\tmainLog.println(\"-paramsplit <name> ............. Set method to split parameter regions (longest,all) [default: longest]\");\n\t\tmainLog.println(\"-parambisim <name> ............. Set bisimulation minimisation for parameter synthesis (weak,strong,none) [default: weak]\");\n\t\tmainLog.println(\"-paramfunction <name> .......... Set function representation for parameter synthesis (jascached,jas) [default: jascached]\");\n\t\tmainLog.println(\"-paramelimorder <name> ......... Set elimination order for parameter synthesis (arb,fw,fwrev,bw,bwrev,rand) [default: bw]\");\n\t\tmainLog.println(\"-paramrandompoints <n> ......... Set number of random points to evaluate per region [default: 5]\");\n\t\tmainLog.println(\"-paramsubsumeregions <b> ....... Subsume adjacent regions during analysis [default: true]\");\n\t\tmainLog.println(\"-paramdagmaxerror <b> .......... Maximal error probability allowed for DAG function representation [default: 1E-100]\");\n\t\tmainLog.println();\n\t\tmainLog.println(\"FAST ADAPTIVE UNIFORMISATION (FAU) OPTIONS:\");\n\t\tmainLog.println(\"-fauepsilon <x> ................ Set probability threshold of birth process in FAU [default: 1e-6]\");\n\t\tmainLog.println(\"-faudelta <x> .................. Set probability threshold for irrelevant states in FAU [default: 1e-12]\");\n\t\tmainLog.println(\"-fauarraythreshold <x> ......... Set threshold when to switch to sparse matrix in FAU [default: 100]\");\n\t\tmainLog.println(\"-fauintervals <x> .............. Set number of intervals to divide time intervals into for FAU [default: 1]\");\n\t\tmainLog.println(\"-fauinitival <x> ............... Set length of additional initial time interval for FAU [default: 1.0]\");\n\t}\n\n\t/**\n\t * Print a -help xxx message, i.e. display help on a specific switch {@code sw}.\n\t * Return true iff help was available for this switch.\n\t */\n\tpublic static boolean printHelpSwitch(PrismLog mainLog, String sw)\n\t{\n\t\t// -aroptions\n\t\tif (sw.equals(\"aroptions\")) {\n\t\t\tmainLog.println(\"Switch: -aroptions <string>\\n\");\n\t\t\tmainLog.println(\"<string> is a comma-separated list of options regarding abstraction-refinement:\");\n\t\t\tQuantAbstractRefine.printOptions(mainLog);\n\t\t\treturn true;\n\t\t}\n\t\telse if (sw.equals(\"ii\") || sw.equals(\"intervaliter\")) {\n\t\t\tmainLog.println(\"Switch: -intervaliter (or -ii) optionally takes a comma-separated list of options:\\n\");\n\t\t\tmainLog.println(\" -intervaliter:option1,option2,...\\n\");\n\t\t\tmainLog.println(\"where the options are one of the following:\\n\");\n\t\t\tmainLog.println(OptionsIntervalIteration.getOptionsDescription());\n\t\t\treturn true;\n\t\t}\n\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Set the value for an option, with the option key given as a String,\n\t * and the value as an Object of appropriate type or a String to be parsed.\n\t * For options of type ChoiceSetting, either a String or (0-indexed) Integer can be used.\n\t */\n\tpublic synchronized void set(String key, Object value) throws PrismException\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif (set == null)\n\t\t\tthrow new PrismException(\"Property \" + key + \" is not valid\");\n\t\ttry\n\t\t{\n\t\t\tString oldValueString = set.toString();\n\t\t\tif (value instanceof String) {\n\t\t\t\tset.setValue(set.parseStringValue((String) value));\n\t\t\t} else if (value instanceof Integer && set instanceof ChoiceSetting) {\n\t\t\t\tint iv = ((Integer)value).intValue();\n\t\t\t\t((ChoiceSetting) set).setSelectedIndex(iv);\n\t\t\t} else {\n\t\t\t\tset.setValue(value);\n\t\t\t}\n\t\t\tnotifySettingsListeners();\n\t\t\tif (!set.toString().equals(oldValueString))\n\t\t\t\tmodified = true;\n\t\t}\n\t\tcatch(SettingException e)\n\t\t{\n\t\t\tthrow new PrismException(e.getMessage());\n\t\t}\n\t}\n\t\n\t/**\n\t * Set the value for an option of type CHOICE_TYPE,\n\t * with the option key given as a String, and the value as an integer index.\n\t * This method exists to allow setting directly using 1-indexed values.\n\t */\n\tpublic synchronized void setChoice(String key, int value) throws PrismException\n\t{\n\t\t// Adjust by 1\n\t\tset(key, value - 1);\n\t}\n\t\n\tpublic synchronized void setFileSelector(String key, FileSelector select)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif (set instanceof FileSetting) {\n\t\t\tFileSetting fset = (FileSetting)set;\n\t\t\tfset.setFileSelector(select);\n\t\t}\n\t}\n\t\n\tpublic synchronized String getString(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof SingleLineStringSetting)\n\t\t{\n\t\t\treturn ((SingleLineStringSetting)set).getStringValue();\n\t\t}\n\t\telse if(set instanceof MultipleLineStringSetting)\n\t\t{\n\t\t\treturn ((MultipleLineStringSetting)set).getStringValue();\n\t\t}\n\t\telse if(set instanceof ChoiceSetting)\n\t\t{\n\t\t\treturn ((ChoiceSetting)set).getStringValue();\n\t\t}\n\t\telse return DEFAULT_STRING;\n\t}\n\t\n\tpublic synchronized int getInteger(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof IntegerSetting)\n\t\t{\n\t\t\treturn ((IntegerSetting)set).getIntegerValue();\n\t\t}\n\t\telse if(set instanceof ChoiceSetting)\n\t\t{\n\t\t\treturn ((ChoiceSetting)set).getCurrentIndex();\n\t\t}\n\t\telse return DEFAULT_INT;\n\t}\n\t\n\tpublic synchronized double getDouble(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof DoubleSetting)\n\t\t{\n\t\t\treturn ((DoubleSetting)set).getDoubleValue();\n\t\t}\n\t\telse return DEFAULT_DOUBLE;\n\t}\n\t\n\tpublic synchronized boolean getBoolean(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof BooleanSetting)\n\t\t{\n\t\t\treturn ((BooleanSetting)set).getBooleanValue();\n\t\t}\n\t\telse return DEFAULT_BOOLEAN;\n\t}\n\t\n\tpublic synchronized long getLong(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof LongSetting)\n\t\t{\n\t\t\treturn ((LongSetting)set).getLongValue();\n\t\t}\n\t\telse return DEFAULT_LONG;\n\t}\n\t\n\tpublic synchronized int getChoice(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof ChoiceSetting)\n\t\t{\n\t\t\t// Adjust by 1\n\t\t\treturn ((ChoiceSetting)set).getCurrentIndex() + 1;\n\t\t}\n\t\telse return DEFAULT_INT;\n\t}\n\t\n\tpublic synchronized Color getColor(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof ColorSetting)\n\t\t{\n\t\t\treturn ((ColorSetting)set).getColorValue();\n\t\t}\n\t\telse return DEFAULT_COLOUR;\n\t}\n\t\n\tpublic synchronized FontColorPair getFontColorPair(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof FontColorSetting)\n\t\t{\n\t\t\treturn ((FontColorSetting)set).getFontColorValue();\n\t\t}\n\t\telse return DEFAULT_FONT_COLOUR;\n\t}\n\t\n\tpublic synchronized File getFile(String key)\n\t{\n\t\tSetting set = settingFromHash(key);\n\t\tif(set instanceof FileSetting)\n\t\t{\n\t\t\treturn ((FileSetting)set).getFileValue();\n\t\t}\n\t\telse return DEFAULT_FILE;\n\t}\n\t\n\tpublic boolean isModified()\n\t{\n\t\treturn modified;\n\t}\n\t\n\tpublic void update(Observable obs, Object obj)\n\t{\n\t\tmodified = true;\n\t\tnotifySettingsListeners();\n\t}\n\t\n\tpublic static void main(String[]args)\n\t{\n\t\tPrismSettings set = new PrismSettings();\n\t\t\n\t\tJFrame jf = new JFrame(\"Prism Settings\");\n\t\tjf.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);\n\t\t\n\t\tArrayList<DefaultSettingOwner> owners = new ArrayList<DefaultSettingOwner>();\n\t\tfor(int i = 0; i < set.optionOwners.length; i++)\n\t\t{\n\t\t\towners.add(set.optionOwners[i]);\n\t\t}\n\t\t\n\t\tSettingTable pt = new SettingTable(jf);\n\t\tpt.setOwners(owners);\n\t\t\n\t\tfor(int i = 0; i < owners.size(); i++)\n\t\t{\n\t\t\tSettingOwner a = (SettingOwner)owners.get(i);\n\t\t\ta.setDisplay(pt);\n\t\t}\n\t\t\n\t\tjf.getContentPane().add(pt);\n\t\tjf.getContentPane().setSize(100, 300);\n\t\t\n\t\tjf.pack();\n\t\tjf.setVisible(true);\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PrismSettingsListener.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\npublic interface PrismSettingsListener\n{\n\tpublic void notifySettings(PrismSettings settings);\n}\n"
  },
  {
    "path": "prism/src/prism/PrismStaTra.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.*;\nimport java.util.ArrayList;\n\n// Small utility to merge PRISM states and transition files\n\npublic class PrismStaTra\n{\n\t// files to read in from\n\tprivate File statesFile;\n\tprivate File transFile;\n\n\t// states info\n\tprivate ArrayList<String> states;\n\n\tpublic PrismStaTra(File sf, File tf)\n\t{\n\t\tstatesFile = sf;\n\t\ttransFile = tf;\n\t}\n\n\t// Read info about reachable state space from file and store string\n\n\tpublic void readStatesFromFile() throws PrismException\n\t{\n\t\tBufferedReader in;\n\t\tString s, ss[];\n\t\tint lineNum = 0;\n\n\t\t// create arrays for explicit state storage\n\t\tstates = new ArrayList<String>();\n\t\ttry {\n\t\t\t// open file for reading\n\t\t\tin = new BufferedReader(new FileReader(statesFile));\n\t\t\t// skip first line\n\t\t\tin.readLine();\n\t\t\tlineNum = 1;\n\t\t\t// read remaining lines\n\t\t\ts = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\ts = s.trim();\n\t\t\t\tss = s.split(\":\");\n\t\t\t\t//i = Integer.parseInt(ss[0]);\n\t\t\t\tstates.add(ss[1]);\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t\t// close file\n\t\t\tin.close();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + statesFile + \"\\\"\");\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error detected at line \" + lineNum + \" of states file \\\"\" + statesFile + \"\\\"\");\n\t\t}\n\t}\n\n\t// Read info about transitions from file, insert state info and re-output\n\n\tprivate void readTransitionsFromFile() throws PrismException\n\t{\n\t\tBufferedReader in;\n\t\tString s, ss[];\n\t\tint i, r, c, lineNum = 0;\n\n\t\ttry {\n\t\t\t// open file for reading\n\t\t\tin = new BufferedReader(new FileReader(transFile));\n\t\t\t// skip first line\n\t\t\ts = in.readLine();\n\t\t\tSystem.out.println(s);\n\t\t\tlineNum = 1;\n\t\t\t// read remaining lines\n\t\t\ts = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\t// parse line, split into parts\n\t\t\t\ts = s.trim();\n\t\t\t\tss = s.split(\" \");\n\t\t\t\t// then replace any state indices with state description...\n\t\t\t\t// dtmc/ctmc with no action:\n\t\t\t\tif (ss.length == 3) {\n\t\t\t\t\tss[0] = \"\" + states.get(Integer.parseInt(ss[0]));\n\t\t\t\t\tss[1] = \"\" + states.get(Integer.parseInt(ss[1]));\n\t\t\t\t} else if (ss.length == 4) {\n\t\t\t\t\t// dtmc/ctmc with action:\n\t\t\t\t\tif (ss[3].matches(\"[_a-zA-Z][_a-zA-Z0-9]*\")) {\n\t\t\t\t\t\tss[0] = \"\" + states.get(Integer.parseInt(ss[0]));\n\t\t\t\t\t\tss[1] = \"\" + states.get(Integer.parseInt(ss[1]));\n\t\t\t\t\t}\n\t\t\t\t\t// mdp with no action:\n\t\t\t\t\telse {\n\t\t\t\t\t\tss[0] = \"\" + states.get(Integer.parseInt(ss[0]));\n\t\t\t\t\t\tss[2] = \"\" + states.get(Integer.parseInt(ss[2]));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// mdp with action:\n\t\t\t\telse {\n\t\t\t\t\tss[0] = \"\" + states.get(Integer.parseInt(ss[0]));\n\t\t\t\t\tss[2] = \"\" + states.get(Integer.parseInt(ss[2]));\n\t\t\t\t}\n\t\t\t\t// print out modified line\n\t\t\t\tfor (i = 0; i < ss.length; i++) {\n\t\t\t\t\tif (i > 0)\n\t\t\t\t\t\tSystem.out.print(\" \");\n\t\t\t\t\tSystem.out.print(ss[i]);\n\t\t\t\t}\n\t\t\t\tSystem.out.println();\n\t\t\t\t// read next line\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t\t// close file\n\t\t\tin.close();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + transFile + \"\\\"\");\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error detected at line \" + lineNum + \" of transition matrix file \\\"\" + transFile\n\t\t\t\t\t+ \"\\\"\");\n\t\t}\n\t}\n\n\tpublic static void main(String args[])\n\t{\n\t\tif (args.length < 2) {\n\t\t\tSystem.out.println(\"Error: Need two arguments (states and transitions file)\");\n\t\t\tSystem.exit(1);\n\t\t}\n\t\ttry {\n\t\t\tPrismStaTra pst = new PrismStaTra(new File(args[0]), new File(args[1]));\n\t\t\tpst.readStatesFromFile();\n\t\t\tpst.readTransitionsFromFile();\n\t\t} catch (PrismException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/PrismTest.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.*;\n\nimport parser.ast.*;\n\n/**\n * Example class demonstrating how to control PRISM programmatically,\n * i.e. through the \"API\" exposed by the class prism.Prism.\n * (this now uses the newer version of the API, released after PRISM 4.0.3)\n * Test like this:\n * PRISM_MAINCLASS=prism.PrismTest bin/prism ../prism-examples/polling/poll2.sm ../prism-examples/polling/poll3.sm\n */\npublic class PrismTest\n{\n\tpublic static void main(String args[])\n\t{\n\t\tnew PrismTest().go(args);\n\t}\n\t\n\tpublic void go(String args[])\n\t{\n\t\ttry {\n\t\t\tPrismLog mainLog;\n\t\t\tPrism prism;\n\t\t\tModulesFile modulesFile;\n\t\t\tPropertiesFile propertiesFile;\n\t\t\tResult result;\n\t\t\t\n\t\t\t// Init\n\t\t\tmainLog = new PrismFileLog(\"stdout\");\n\t\t\tprism = new Prism(mainLog);\n\t\t\tprism.initialise();\n\t\t\t\n\t\t\t// Parse/load model 1\n\t\t\t// NB: no need to build explicitly - it will be done if/when neeed\n\t\t\tmodulesFile = prism.parseModelFile(new File(args[0]));\n\t\t\tprism.loadPRISMModel(modulesFile);\n\t\t\t\n\t\t\t// Parse a prop, check on model 1\n\t\t\tpropertiesFile = prism.parsePropertiesString(\"P=?[F<=0.1 s1=1]\");\n\t\t\tresult = prism.modelCheck(propertiesFile, propertiesFile.getPropertyObject(0));\n\t\t\tSystem.out.println(result.getResult());\n\t\t\t\n\t\t\t// Parse another prop, check on model 1\n\t\t\tpropertiesFile = prism.parsePropertiesString(\"P=?[F<=0.1 s1=1]\");\n\t\t\tresult = prism.modelCheck(propertiesFile, propertiesFile.getPropertyObject(0));\n\t\t\tSystem.out.println(result.getResult());\n\t\t\t\n\t\t\t// Parse/load model 2\n\t\t\tmodulesFile = prism.parseModelFile(new File(args[1]));\n\t\t\tprism.loadPRISMModel(modulesFile);\n\t\t\t\n\t\t\t// Parse a prop, check on model 2\n\t\t\tpropertiesFile = prism.parsePropertiesString(\"P=?[F<=0.1 s1=1]\");\n\t\t\tresult = prism.modelCheck(propertiesFile, propertiesFile.getPropertyObject(0));\n\t\t\tSystem.out.println(result.getResult());\n\t\t\t\n\t\t\t// Close down\n\t\t\tprism.closeDown();\n\t\t}\n\t\tcatch (FileNotFoundException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\t\tcatch (PrismException e) {\n\t\t\tSystem.out.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PrismUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.FileNotFoundException;\nimport java.io.PrintStream;\nimport java.text.DecimalFormat;\nimport java.text.DecimalFormatSymbols;\nimport java.util.HashMap;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.Locale;\nimport java.util.PrimitiveIterator;\nimport java.util.Set;\nimport java.util.Map.Entry;\nimport java.util.regex.Matcher;\nimport java.util.regex.Pattern;\nimport java.util.stream.Stream;\nimport java.util.stream.StreamSupport;\n\nimport common.iterable.PrimitiveIterable;\nimport param.BigRational;\n\n/**\n * Various general-purpose utility methods in Java\n */\npublic class PrismUtils\n{\n\t// Threshold for comparison of doubles\n\tpublic static double epsilonDouble = 1e-12;\n\n\t/**\n\t * Compute logarithm of x to base b.\n\t */\n\tpublic static double log(double x, double b)\n\t{\n\t\t// If base is <=0 or ==1 (or +Inf/NaN), then result is NaN\n\t\tif (b <= 0 || b == 1 || (Double.isInfinite(b)) || Double.isNaN(b))\n\t\t\treturn Double.NaN;\n\n\t\t// Otherwise, log_b (x) is log(x) / log(b)\n\t\treturn Math.log(x) / Math.log(b);\n\t}\n\n\t/**\n\t * Compute logarithm of x to base 2.\n\t */\n\tpublic static double log2(double x)\n\t{\n\t\treturn Math.log(x) / Math.log(2);\n\t}\n\n\t/**\n\t * See if two doubles are within epsilon of each other (absolute error).\n\t */\n\tpublic static boolean doublesAreCloseAbs(double d1, double d2, double epsilon)\n\t{\n\t\t// Deal with infinite cases\n\t\tif (Double.isInfinite(d1)) {\n\t\t\treturn Double.isInfinite(d2) && (d1 > 0) == (d2 > 0);\n\t\t} else if (Double.isInfinite(d2)) {\n\t\t\treturn false;\n\t\t}\n\t\t// Compute/check error\n\t\treturn (Math.abs(d1 - d2) < epsilon);\n\t}\n\n\t/**\n\t * See if two doubles are within epsilon of each other (relative error).\n\t */\n\tpublic static boolean doublesAreCloseRel(double d1, double d2, double epsilon)\n\t{\n\t\t// Deal with infinite cases\n\t\tif (Double.isInfinite(d1)) {\n\t\t\treturn Double.isInfinite(d2) && (d1 > 0) == (d2 > 0);\n\t\t} else if (Double.isInfinite(d2)) {\n\t\t\treturn false;\n\t\t}\n\t\t// Compute/check error\n\t\tif (d2 == 0) {\n\t\t\t// If both are zero, error is 0; otherwise +inf\n\t\t\treturn d1 == 0;\n\t\t}\n\t\treturn Math.abs((d1 - d2) / d1) < epsilon;\n\t}\n\n\t/**\n\t * See if two doubles are within epsilon of each other (relative or absolute error).\n\t * @param abs Absolute if true, relative if false\n\t */\n\tpublic static boolean doublesAreClose(double d1, double d2, double epsilon, boolean abs)\n\t{\n\t\tif (abs) {\n\t\t\treturn doublesAreCloseAbs(d1, d2, epsilon);\n\t\t} else {\n\t\t\treturn doublesAreCloseRel(d1, d2, epsilon);\n\t\t}\n\t}\n\n\t/**\n\t * See if two arrays of doubles are all within epsilon of each other (relative or absolute error).\n\t */\n\tpublic static boolean doublesAreClose(double d1[], double d2[], double epsilon, boolean abs)\n\t{\n\t\tint n = Math.min(d1.length, d2.length);\n\t\tif (abs) {\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tif (!doublesAreCloseAbs(d1[i], d2[i], epsilon))\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tif (!doublesAreCloseRel(d1[i], d2[i], epsilon))\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * See if, for all the entries given by the {@code indizes}\n\t * iterator, two arrays of doubles are all within epsilon of each other (relative or absolute error).\n\t * <br>\n\t * Considers Inf == Inf and -Inf == -Inf.\n\t */\n\tpublic static boolean doublesAreClose(double d1[], double d2[], PrimitiveIterable.OfInt indizes, double epsilon, boolean abs)\n\t{\n\t\treturn doublesAreClose(d1, d2, indizes.iterator(), epsilon, abs);\n\t}\n\n\t/**\n\t * See if, for all the entries given by the {@code indizes}\n\t * iterator, two arrays of doubles are all within epsilon of each other (relative or absolute error).\n\t * <br>\n\t * Considers Inf == Inf and -Inf == -Inf.\n\t */\n\tpublic static boolean doublesAreClose(double d1[], double d2[], PrimitiveIterator.OfInt indizes, double epsilon, boolean abs)\n\t{\n\t\tif (abs) {\n\t\t\twhile (indizes.hasNext()) {\n\t\t\t\tint i = indizes.nextInt();\n\t\t\t\tif (!doublesAreCloseAbs(d1[i], d2[i], epsilon))\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t} else {\n\t\t\twhile (indizes.hasNext()) {\n\t\t\t\tint i = indizes.nextInt();\n\t\t\t\tif (!doublesAreCloseRel(d1[i], d2[i], epsilon))\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * See if two maps to doubles are all within epsilon of each other (relative or absolute error).\n\t */\n\tpublic static <X> boolean doublesAreClose(HashMap<X,Double> map1, HashMap<X,Double> map2, double epsilon, boolean abs)\n\t{\n\t\tSet<Entry<X,Double>> entries = map1.entrySet();\n\t\tfor (Entry<X,Double> entry : entries) {\n\t\t\tdouble d1 = (double) entry.getValue();\n\t\t\tif (map2.get(entry.getKey()) != null) {\n\t\t\t\tdouble d2 = (double) map2.get(entry.getKey());\n\t\t\t\tif (abs) {\n\t\t\t\t\tif (!PrismUtils.doublesAreCloseAbs(d1, d2, epsilon))\n\t\t\t\t\t\treturn false;\n\t\t\t\t} else {\n\t\t\t\t\tif (!PrismUtils.doublesAreCloseRel(d1, d2, epsilon))\n\t\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\t// Only check over common elements\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Measure supremum norm, either absolute or relative,\n\t * return the maximum difference.\n\t */\n\tpublic static <X> double measureSupNorm(HashMap<X,Double> map1, HashMap<X,Double> map2, boolean abs)\n\t{\n\t\tdouble value = 0;\n\t\tSet<Entry<X,Double>> entries = map1.entrySet();\n\t\tfor (Entry<X,Double> entry : entries) {\n\t\t\tdouble diff;\n\t\t\tdouble d1 = entry.getValue();\n\t\t\tif (map2.get(entry.getKey()) != null) {\n\t\t\t\tdouble d2 = map2.get(entry.getKey());\n\t\t\t\tif (abs) {\n\t\t\t\t\tdiff = measureSupNormAbs(d1, d2);\n\t\t\t\t} else {\n\t\t\t\t\tdiff = measureSupNormRel(d1, d2);\n\t\t\t\t}\n\t\t\t\tif (diff > value) {\n\t\t\t\t\tvalue = diff;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\t// Only check over common elements\n\t\t\t}\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Measure supremum norm, either absolute or relative,\n\t * return the maximum difference.\n\t */\n\tpublic static double measureSupNorm(double[] d1, double[] d2, boolean abs)\n\t{\n\t\tint n = Math.min(d1.length, d2.length);\n\t\tdouble value = 0;\n\t\tif (abs) {\n\t\t\tfor (int i=0; i < n; i++) {\n\t\t\t\tdouble diff = measureSupNormAbs(d1[i], d2[i]);\n\t\t\t\tif (diff > value)\n\t\t\t\t\tvalue = diff;\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int i=0; i < n; i++) {\n\t\t\t\tdouble diff = measureSupNormRel(d1[i], d2[i]);\n\t\t\t\tif (diff > value)\n\t\t\t\t\tvalue = diff;\n\t\t\t}\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Measure supremum norm for two values, absolute.\n\t */\n\tpublic static double measureSupNormAbs(double d1, double d2)\n\t{\n\t\tif (Double.isInfinite(d1) && d1==d2)\n\t\t\treturn 0;\n\t\treturn Math.abs(d1 - d2);\n\t}\n\n\t/**\n\t * Measure supremum norm for two values, relative,\n\t * with the first value used as the divisor.\n\t */\n\tpublic static double measureSupNormRel(double d1, double d2)\n\t{\n\t\tif (d1==d2)\n\t\t\treturn 0;\n\t\treturn (Math.abs(d1 - d2) / d1);\n\t}\n\n\t/**\n\t * Measure supremum norm, for all the entries given by the {@code indizes}\n\t * iterator, for an interval iteration.\n\t */\n\tpublic static double measureSupNormInterval(double[] lower, double[] upper, boolean abs, PrimitiveIterator.OfInt indizes)\n\t{\n\t\tdouble value = 0;\n\t\twhile (indizes.hasNext()) {\n\t\t\tint i = indizes.nextInt();\n\t\t\tdouble diff = measureSupNormInterval(lower[i], upper[i], abs);\n\t\t\tif (diff > value)\n\t\t\t\tvalue = diff;\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Measure supremum norm, either absolute or relative, for an interval iteration,\n\t * return the maximum difference.\n\t */\n\tpublic static double measureSupNormInterval(double[] lower, double[] upper, boolean abs)\n\t{\n\t\tint n = Math.min(lower.length, upper.length);\n\t\tdouble value = 0;\n\t\tfor (int i=0; i < n; i++) {\n\t\t\tdouble diff = measureSupNormInterval(lower[i], upper[i], abs);\n\t\t\tif (diff > value)\n\t\t\t\tvalue = diff;\n\t\t}\n\t\treturn value;\n\t}\n\n\t/**\n\t * Measure supremum norm for two values, for interval iteration.\n\t */\n\tpublic static double measureSupNormInterval(double lower, double upper, boolean abs)\n\t{\n\t\t// Deal with infinite cases\n\t\tif (Double.isInfinite(lower)) {\n\t\t\tif (Double.isInfinite(upper) && (lower > 0) == (upper > 0)) {\n\t\t\t\treturn 0;\n\t\t\t} else {\n\t\t\t\treturn Double.POSITIVE_INFINITY;\n\t\t\t}\n\t\t} else if (Double.isInfinite(upper)) {\n\t\t\treturn Double.POSITIVE_INFINITY;\n\t\t}\n\n\t\tif (lower == upper)\n\t\t\treturn 0.0;\n\n\t\t// Compute/check error\n\t\tlower = Math.abs(lower);\n\t\tupper = Math.abs(upper);\n\t\tdouble result = upper - lower;\n\t\tresult = Math.abs(result);\n\t\tif (!abs) {\n\t\t\tresult = result / lower;\n\t\t}\n\t\treturn result;\n\t}\n\n\t/**\n\t * See if two doubles are (nearly) equal.\n\t */\n\tpublic static boolean doublesAreEqual(double d1, double d2)\n\t{\n\t\treturn doublesAreCloseRel(d1, d2, epsilonDouble);\n\t}\n\n\t/**\n\t * Return the maximum finite value in a double array, looking at\n\t * those entries with indices given bit the integer iterator.\n\t */\n\tpublic static double findMaxFinite(double[] soln, PrimitiveIterator.OfInt indices)\n\t{\n\t\tdouble max_v = Double.NEGATIVE_INFINITY;\n\t\twhile (indices.hasNext()) {\n\t\t\tint i = indices.nextInt();\n\n\t\t\tdouble v = soln[i];\n\t\t\tif (v < Double.POSITIVE_INFINITY) {\n\t\t\t\tmax_v = Double.max(v, max_v);\n\t\t\t}\n\t\t}\n\t\treturn max_v;\n\t}\n\n\t/**\n\t * Ensure monotonicity from below for interval iteration solution vectors.\n\t * Compares the old and new values and overwrites the new value with the old\n\t * value if that is larger.\n\t * @param old_values old solution vector\n\t * @param new_values new solution vector\n\t */\n\tpublic static void ensureMonotonicityFromBelow(double[] old_values, double[] new_values)\n\t{\n\t\tassert(old_values.length == new_values.length);\n\n\t\tfor (int i = 0, n = old_values.length; i < n; i++) {\n\t\t\tdouble old_value = old_values[i];\n\t\t\tdouble new_value = new_values[i];\n\t\t\t// from below: do max\n\t\t\tif (old_value > new_value) {\n\t\t\t\tnew_values[i] = old_value;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Ensure monotonicity from above for interval iteration solution vectors.\n\t * Compares the old and new values and overwrites the new value with the old\n\t * value if that is smaller.\n\t * @param old_values old solution vector\n\t * @param new_values new solution vector\n\t */\n\tpublic static void ensureMonotonicityFromAbove(double[] old_values, double[] new_values)\n\t{\n\t\tassert(old_values.length == new_values.length);\n\n\t\tfor (int i = 0, n = old_values.length; i < n; i++) {\n\t\t\tdouble old_value = old_values[i];\n\t\t\tdouble new_value = new_values[i];\n\t\t\t// from above: do min\n\t\t\tif (old_value < new_value) {\n\t\t\t\tnew_values[i] = old_value;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Check for monotonicity: If the new_values are not element-wise less-than-equal the older values\n\t * (for from_above == true), then throws an exception. If from_above == false, the logic is reversed,\n\t * i.e., if the new_value is not greater-than-equal, an exception is thrown.\n\t * @param old_values the old values\n\t * @param new_values the new values\n\t * @param from_above the direction\n\t */\n\tpublic static void checkMonotonicity(double[] old_values, double[] new_values, boolean from_above) throws PrismException\n\t{\n\t\tassert(old_values.length == new_values.length);\n\n\t\tfor (int i = 0, n = old_values.length; i < n; i++) {\n\t\t\tdouble old_value = old_values[i];\n\t\t\tdouble new_value = new_values[i];\n\t\t\tif (from_above && old_value < new_value) {\n\t\t\t\tthrow new PrismException(\"Monotonicity violated (from above): old value \" + old_value + \" < new value \" + new_value);\n\t\t\t}\n\t\t\tif (!from_above && old_value > new_value) {\n\t\t\t\tthrow new PrismException(\"Monotonicity violated (from below): old value \" + old_value + \" > new value \" + new_value);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Select midpoint from two interval iteration solution vectors.\n\t * Stores the result in soln_below.\n\t * @param soln_below solution vector from below\n\t * @param soln_above solution vector from above\n\t */\n\tpublic static void selectMidpoint(double[] soln_below, double[] soln_above)\n\t{\n\t\tassert(soln_below.length == soln_above.length);\n\n\t\tfor (int i = 0, n = soln_below.length; i < n; i++) {\n\t\t\tdouble below = soln_below[i];\n\t\t\tdouble above = soln_above[i];\n\n\t\t\tif (below != above) {\n\t\t\t\t// use below + ( above - below ) / 2 instead of (below+above)/2 for better numerical\n\t\t\t\t// stability\n\t\t\t\tdouble d = below + (above - below)/2.0;\n\t\t\t\tif (d >= below && d <= above) {\n\t\t\t\t\t// only store result if between below and above\n\t\t\t\t\t// guard against rounding problems,\n\t\t\t\t\t// fallback is to simply return below as is\n\t\t\t\t\tsoln_below[i] = d;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Normalise the entries of a vector in-place such that that they sum to 1.\n\t * If {@code sum = 0.0}, all entries are set to {@code NaN} (assuming all entries are non-negative)\n\t * @param vector the vector\n\t * @return the altered vector (returned for convenience; it's the same one)\n\t */\n\tpublic static double[] normalise(double[] vector)\n\t{\n\t\tdouble sum = 0.0;\n\t\tint n = vector.length;\n\t\tfor (int state = 0; state < n; state++) {\n\t\t\tsum += vector[state];\n\t\t}\n\t\tfor (int state = 0; state < n; state++) {\n\t\t\tvector[state] /= sum;\n\t\t}\n\t\treturn vector;\n\t}\n\n\t/**\n\t * Normalise the given entries in the vector in-place such that that they sum to 1,\n\t * i.e., for all indices {@code s}, set {@code vector[s] = vector[s] / sum},\n\t * where {@code sum = sum_{s in entries} (vector[s]).<br>\n\t * If {@code sum = 0.0}, all entries are set to {@code NaN} (assuming all entries are non-negative)\n\t * @param vector the vector\n\t * @param entries Iterable over the entries (must not contain duplicates)\n\t * @return the altered vector (returned for convenience; it's the same one)\n\t */\n\tpublic static double[] normalise(double[] vector, PrimitiveIterable.OfInt entries)\n\t{\n\t\tdouble sum = 0.0;\n\t\tfor (PrimitiveIterator.OfInt iter = entries.iterator(); iter.hasNext();) {\n\t\t\tint state = iter.nextInt();\n\t\t\tsum += vector[state];\n\t\t}\n\t\tfor (PrimitiveIterator.OfInt iter = entries.iterator(); iter.hasNext();) {\n\t\t\tint state = iter.nextInt();\n\t\t\tvector[state] /= sum;\n\t\t}\n\t\treturn vector;\n\t}\n\n\t/**\n\t * Format a large integer, represented by a double, as a string. Un\n\t */\n\tpublic static String bigIntToString(double d)\n\t{\n\t\tif (d <= Long.MAX_VALUE) {\n\t\t\treturn \"\" + Math.round(d);\n\t\t} else {\n\t\t\treturn \"\" + d;\n\t\t}\n\t}\n\n\t/**\n\t * Modify a filename f, appending a counter i just before the filetype extension. \n\t */\n\tpublic static String addCounterSuffixToFilename(String f, int i)\n\t{\n\t\treturn addSuffixToFilename(f, \"\" + i);\n\t}\n\n\t/**\n\t * Modify a filename f, appending a string s just before the filetype extension. \n\t */\n\tpublic static String addSuffixToFilename(String f, String s)\n\t{\n\t\tint j = f.lastIndexOf(\".\");\n\t\tif (j != -1) {\n\t\t\treturn f.substring(0, j) + s + f.substring(j);\n\t\t} else {\n\t\t\treturn f + s;\n\t\t}\n\t}\n\n\t/**\n\t * Format a fraction as a percentage to 1 decimal place.\n\t */\n\tpublic static String formatPercent1dp(double frac)\n\t{\n\t\treturn formatterPercent1dp.format(frac);\n\t}\n\n\tprivate static DecimalFormat formatterPercent1dp = new DecimalFormat(\"#0.0%\", DecimalFormatSymbols.getInstance(Locale.UK));\n\n\t/**\n\t * Format a double to 2 decimal places.\n\t */\n\tpublic static String formatDouble2dp(double d)\n\t{\n\t\treturn formatterDouble2dp.format(d);\n\t}\n\n\tprivate static DecimalFormat formatterDouble2dp = new DecimalFormat(\"#0.00\", DecimalFormatSymbols.getInstance(Locale.UK));\n\n\t/**\n\t * Format a double, as would be done by printf's %.17g.\n\t * Preserving full double precision requires 17 = ceil(log(2^(52+1))) + 1 decimal places,\n\t * since the mantissa has 52+1 bits and one additional place is needed to tell close values apart.\n\t */\n\tpublic static String formatDouble(double d)\n\t{\n\t\treturn formatDouble(17, d);\n\t}\n\n\t/**\n\t * Format a double, as would be done by printf's %.(prec)g\n\t * @param prec precision (significant digits) >= 1\n\t */\n\tpublic static String formatDouble(int prec, double d)\n\t{\n\t\tif (prec < 1)\n\t\t\tthrow new IllegalArgumentException(\"Precision has to be >= 1; got \" + prec);\n\t\t// Use no locale to avoid . being changed to , in some countries.\n\t\t// To match C's printf, we have to tweak the Java version,\n\t\t// strip trailing zeros after the .\n\t\tString result = String.format((Locale)null, \"%.\" + prec + \"g\", d);\n\t\t// if there are only zeros after the . (e.g., .000000), strip them including the .\n\t\tresult = FORMAT_DOUBLE_TRAILING_ZEROS.matcher(result).replaceFirst(\"$1\");\n\t\t// handle .xxxx0000\n\t\t// we first match .xxx until there are only zeros before the end (or e)\n\t\t// as we match reluctantly (using the *?), all trailing zeros are captured\n\t\t// by the 0+ part\n\t\treturn FORMAT_DOUBLE_TRAILING_ZEROS2.matcher(result).replaceFirst(\"$1$2\");\n\t}\n\n\tprivate static final Pattern FORMAT_DOUBLE_TRAILING_ZEROS = Pattern.compile(\"\\\\.0+(e|$)\");\n\tprivate static final Pattern FORMAT_DOUBLE_TRAILING_ZEROS2 = Pattern.compile(\"(\\\\.[0-9]*?)0+(e|$)\");\n\n\t/**\n\t * Format a double (that is known to be an integer, but not necessarily in the int range)\n\t * to a string.<br>\n\t * Correctly handles values beyond INT_MIN/INT_MAX, as well as -Inf/Inf and NaN.\n\t */\n\tpublic static String formatIntFromDouble(double d)\n\t{\n\t\tBigRational v = BigRational.from(d);\n\t\treturn v.toString();\n\t}\n\n\t/**\n\t * Create a string for a list of objects, with a specified separator,\n\t * e.g. [\"a\",\"b\",\"c\"], \",\" -&gt; \"a,b,c\"\n\t */\n\tpublic static String joinString(List<?> objs, String separator)\n\t{\n\t\tString s = \"\";\n\t\tboolean first = true;\n\t\tfor (Object obj : objs) {\n\t\t\tif (first) {\n\t\t\t\tfirst = false;\n\t\t\t} else {\n\t\t\t\ts += separator; \n\t\t\t}\n\t\t\ts += obj.toString();\n\t\t}\n\t\treturn s;\n\t}\n\t\n\t/**\n\t * Create a string for an array of objects, with a specified separator,\n\t * e.g. [\"a\",\"b\",\"c\"], \",\" -&gt; \"a,b,c\"\n\t */\n\tpublic static String joinString(Object[] objs, String separator)\n\t{\n\t\tString s = \"\";\n\t\tboolean first = true;\n\t\tfor (Object obj : objs) {\n\t\t\tif (first) {\n\t\t\t\tfirst = false;\n\t\t\t} else {\n\t\t\t\ts += separator; \n\t\t\t}\n\t\t\ts += obj.toString();\n\t\t}\n\t\treturn s;\n\t}\n\t\n\t/**\n\t * Check for any cycles in an 2D boolean array representing a graph.\n\t * Useful for checking for cyclic dependencies in connected definitions.\n\t * Returns the lowest index of a node contained in a cycle, if there is one, -1 if not.  \n\t * @param matrix Square matrix of connections: {@code matr[i][j] == true} iff\n\t * there is a connection from {@code i} to {@code j}.\n\t */\n\tpublic static int findCycle(boolean matrix[][])\n\t{\n\t\tint n = matrix.length;\n\t\tint firstCycle = -1;\n\t\t// Go through nodes\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\t// See if there is a cycle yet\n\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\tif (matrix[j][j]) {\n\t\t\t\t\tfirstCycle = j;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// If so, stop\n\t\t\tif (firstCycle != -1)\n\t\t\t\tbreak;\n\t\t\t// Extend dependencies\n\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\tfor (int k = 0; k < n; k++) {\n\t\t\t\t\tif (matrix[j][k]) {\n\t\t\t\t\t\tfor (int l = 0; l < n; l++) {\n\t\t\t\t\t\t\tmatrix[j][l] |= matrix[k][l];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn firstCycle;\n\t}\n\n\t/**\n\t * Convert a string representing an amount of memory (e.g. 125k, 50m, 4g) to the value in KB.\n\t * If the letter prefix is omitted, we assume it is \"k\" (i.e. KB).\n\t */\n\tpublic static long convertMemoryStringtoKB(String mem) throws PrismException\n\t{\n\t\tPattern p = Pattern.compile(\"([0-9]+)([kmg]?)\");\n\t\tMatcher m = p.matcher(mem);\n\t\tif (!m.matches()) {\n\t\t\tthrow new PrismException(\"Invalid amount of memory \\\"\" + mem + \"\\\"\");\n\t\t}\n\t\tlong num;\n\t\ttry {\n\t\t\tnum = Long.parseLong(m.group(1));\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Invalid amount of memory \\\"\" + mem + \"\\\"\");\n\t\t}\n\t\tswitch (m.group(2)) {\n\t\tcase \"\":\n\t\tcase \"k\":\n\t\t\treturn num;\n\t\tcase \"m\":\n\t\t\treturn num * 1024;\n\t\tcase \"g\":\n\t\t\treturn num * (1024 * 1024);\n\t\tdefault:\n\t\t\t// Shouldn't happen\n\t\t\tthrow new PrismException(\"Invalid amount of memory \\\"\" + mem + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Convert a string representing an amount of time (e.g. 5s, 5m, 5h, 5d, 5w) to the value\n\t * in seconds.\n\t * If the unit is omitted, we assume it is seconds.\n\t */\n\tpublic static int convertTimeStringtoSeconds(String time) throws PrismException\n\t{\n\t\tPattern p = Pattern.compile(\"([0-9]+)([smhdw]?)\");\n\t\tMatcher m = p.matcher(time);\n\t\tif (!m.matches()) {\n\t\t\tthrow new PrismException(\"Invalid time value \\\"\" + time + \"\\\"\");\n\t\t}\n\t\tint value;\n\t\ttry {\n\t\t\tvalue = Integer.parseInt(m.group(1));\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Invalid time value \\\"\" + time + \"\\\"\");\n\t\t}\n\t\tswitch (m.group(2)) {\n\t\tcase \"\":\n\t\tcase \"s\":  // seconds\n\t\t\treturn value;\n\t\tcase \"m\":  // minutes\n\t\t\treturn value * 60;\n\t\tcase \"h\":  // hours\n\t\t\treturn value * (60 * 60);\n\t\tcase \"d\":  // days\n\t\t\treturn value * (24 * 60 * 60);\n\t\tcase \"w\":  // weeks\n\t\t\treturn value * (7 * 24 * 60 * 60);\n\t\tdefault:\n\t\t\t// Shouldn't happen\n\t\t\tthrow new PrismException(\"Invalid time value \\\"\" + time + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Convert a number of bytes to a string representing the amount of memory (e.g. 125k, 50m, 4g).\n\t */\n\tpublic static String convertBytesToMemoryString(long bytes) throws PrismException\n\t{\n\t\tString units[] = { \"b\", \"k\", \"m\", \"g\" };\n\t\tfor (int i = 3; i > 0; i--) {\n\t\t\tlong pow = 1 << (i * 10);\n\t\t\tif (bytes >= pow) {\n\t\t\t\treturn (bytes % pow == 0 ? (bytes / pow) : String.format(Locale.UK, \"%.1f\", ((double) bytes) / pow)) + units[i];\n\t\t\t}\n\t\t}\n\t\treturn bytes + units[0];\n\t\t\n\t\t/*for (String s : new String[] { \"1g\", \"1500m\", \"2g\", \"1000m\", \"1024m\", \"1\" }) {\n\t\t\tSystem.out.println(s + \" => \" + PrismUtils.convertMemoryStringtoKB(s) * 1024 + \" => \" + PrismUtils.convertBytesToMemoryString(PrismUtils.convertMemoryStringtoKB(s) * 1024));\n\t\t}*/\n\t}\n\t\n\t/**\n\t * Utility method to create a new PrintStream for a file, but any errors are converted to PrismExceptions\n\t */\n\tpublic static PrintStream newPrintStream(String filename) throws PrismException\n\t{\n\t\ttry {\n\t\t\treturn new PrintStream(filename);\n\t\t} catch (FileNotFoundException e) {\n\t\t\tthrow new PrismException(\"File \\\"\" + filename + \"\\\" could not opened for output\");\n\t\t}\n\t}\n\t\n\t/**\n\t * Compare two version numbers of PRISM (strings).\n\t * Supports standard semantic versioning, e.g., 2 < 2.1 < 2.1.1-dev < 2.1.1-alpha < 2.1.1-beta < 2.1.1.\n\t * But also respects legacy PRISM use of \".dev\" where 2.1.1 < 2.1.1.dev.\n\t * To achieve this, \".dev\" is interpreted as \".post\" and differently to \"-dev\".\n\t * Example ordering: { \"1\", \"2.0\", \"2.1-dev\", \"2.1.alpha\", \"2.1.beta\", \"2.1\", \"2.1.post\", \"2.1.2\", \"2.9\", \"3\", \"3.4\"};\n\t * Returns: 1 if v1&gt;v2, -1 if v1&lt;v2, 0 if v1=v2.\n\t */\n\tpublic static int compareVersions(String v1, String v2)\n\t{\n\t\treturn VersionUtils.compareVersions(v1, v2);\n\t}\n\n\t/**\n\t * Get access to a list's items in reverse order.\n\t * Similar to {@code List.reversed()}, which is only in Java 21.\n\t */\n\tpublic static <E> Iterable<E> listReversed(List<E> list)\n\t{\n\t\treturn () -> new Iterator<E>() {\n\t\t\tint i = list.size() - 1;\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn i >= 0;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic E next()\n\t\t\t{\n\t\t\t\treturn list.get(i--);\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Get access to a list's items in reverse order.\n\t * Similar to {@code List.reversed().stream()}, which is only in Java 21.\n\t */\n\tpublic static <E> Stream<E> listReversedStream(List<E> list)\n\t{\n\t\treturn StreamSupport.stream(listReversed(list).spliterator(), false);\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/prism/ProgressDisplay.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * Class to display progress meter to a log, either as percentages or just a counter.\n */\npublic class ProgressDisplay\n{\n\t/** Log to display progress to */\n\tprivate PrismLog mainLog;\n\t// Config\n\t/** Minimum delay between updates (milliseconds); */\n\tprivate int delay = 3000;\n\t/** Display progress as multiples of this number */\n\tprivate int percentMultiple = 2;\n\t// Current state\n\tprivate long totalCount;\n\tprivate long lastCount;\n\tprivate long lastPercentageDone;\n\tprivate long timerProgress;\n\tprivate boolean first;\n\n\tpublic ProgressDisplay(PrismLog mainLog)\n\t{\n\t\tthis.mainLog = mainLog;\n\t}\n\n\t/**\n\t * Initialise; start the timer.\n\t */\n\tpublic void start()\n\t{\n\t\ttotalCount = -1; // i.e. not used\n\t\tlastCount = 0;\n\t\tlastPercentageDone = 0;\n\t\ttimerProgress = System.currentTimeMillis();\n\t\tfirst = true;\n\t}\n\n\t/**\n\t * Set total count expected, thus triggering percentage mode.\n\t */\n\tpublic void setTotalCount(long totalCount)\n\t{\n\t\tthis.totalCount = totalCount;\n\t}\n\n\t/**\n\t * Is it time for the next update?\n\t */\n\tpublic boolean ready()\n\t{\n\t\treturn System.currentTimeMillis() - timerProgress > delay;\n\t}\n\n\t/**\n\t * Display an update, if it is ready and anything changed.\n\t */\n\tpublic void updateIfReady(long count)\n\t{\n\t\tif (ready())\n\t\t\tupdate(count);\n\t}\n\t\n\t/**\n\t * Display an update, if anything changed.\n\t */\n\tpublic void update(long count)\n\t{\n\t\t// Percentage mode\n\t\tif (totalCount != -1) {\n\t\t\t// Compute percentage, round down to nearest multiple of 'multiple'\n\t\t\tint percentageDoneRound;\n\t\t\tif (count >= totalCount) {\n\t\t\t\tpercentageDoneRound = 100;\n\t\t\t} else {\n\t\t\t\tpercentageDoneRound = (int) Math.floor((100.0 * count) / totalCount);\n\t\t\t\tpercentageDoneRound = (percentageDoneRound / percentMultiple) * percentMultiple;\n\t\t\t}\n\t\t\t// Print if new\n\t\t\tif (percentageDoneRound > lastPercentageDone) {\n\t\t\t\tif (first) {\n\t\t\t\t\tmainLog.print(\"[\");\n\t\t\t\t\tfirst = false;\n\t\t\t\t}\n\t\t\t\tlastPercentageDone = percentageDoneRound;\n\t\t\t\tmainLog.print(\" \" + percentageDoneRound + \"%\");\n\t\t\t\tmainLog.flush();\n\t\t\t\ttimerProgress = System.currentTimeMillis();\n\t\t\t}\n\t\t}\n\t\t// Counter mode\n\t\telse {\n\t\t\t// Print if new\n\t\t\tif (count > lastCount) {\n\t\t\t\tlastCount = count;\n\t\t\t\tmainLog.print(\" \" + count);\n\t\t\t\tmainLog.flush();\n\t\t\t\ttimerProgress = System.currentTimeMillis();\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Finish up.\n\t */\n\tpublic void end()\n\t{\n\t\tend(\"\");\n\t}\n\n\t/**\n\t * Finish up, displaying {@code text} first.\n\t */\n\tpublic void end(String text)\n\t{\n\t\tmainLog.print(text);\n\t\tif (totalCount != -1)\n\t\t\tmainLog.print(\" ]\");\n\t\tmainLog.println();\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/PropertyConstants.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\npublic final class PropertyConstants\n{\n\tpublic static final int STATE = 0;\n\tpublic static final int TRANSITION = 1;\n\tpublic static final int NAIL = 2;\n\tpublic static final int DECISION = 3;\n\tpublic static final int PROBTRANSITION = 4;\n\tpublic static final int BRANCHTRANSITION = 5;\n\tpublic static final int GRAPH = 6;\n\tpublic static final int AXIS = 7;\n\tpublic static final int SERIES = 8;\n\tpublic static final int PRISM = 9;\n\tpublic static final int MODEL = 10;\n\tpublic static final int PROPERTIES = 11;\n\tpublic static final int SIMULATOR = 12;\n\tpublic static final int LOG = 13;\n\tpublic static final int PARAM = 14;\n\tpublic static final int FAU = 15;\n\tpublic static final int SSHHOST = 16;\n\tpublic static final int FILESYSTEM = 17;\n\tpublic static final int NETWORK_PROFILE = 18;\n\tpublic static final int GRAPH_DISPLAY = 19;\n}\n"
  },
  {
    "path": "prism/src/prism/Reactions2Prism.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.BufferedOutputStream;\nimport java.io.BufferedWriter;\nimport java.io.File;\nimport java.io.FileWriter;\nimport java.io.IOException;\nimport java.io.OutputStreamWriter;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.HashSet;\n\nimport org.w3c.dom.Element;\n\nimport parser.PrismParser;\n\n/**\n * Base class for classes that build/store a set of biological reactions and then convert to PRISM.\n */\npublic abstract class Reactions2Prism extends PrismLanguageTranslator\n{\n\t// Log for output of warnings, messages\n\tprotected PrismLog mainLog = null;\n\n\t// Reactions set definition\n\tprotected String compartmentName, speciesId, initialAmountString;\n\tprotected double compartmentSize;\n\tprotected ArrayList<Species> speciesList;\n\tprotected ArrayList<Parameter> parameterList;\n\tprotected ArrayList<Reaction> reactionList;\n\n\t// Config\n\n\t/** Maximum amount of each species (unless some initial amount is higher). */\n\tprotected int maxAmount = 100;\n\n\t// Optional PRISM code header/footer\n\tprotected String prismCodeHeader;\n\tprotected String prismCodeFooter;\n\n\t// Constructors\n\n\tpublic Reactions2Prism() throws PrismException\n\t{\n\t\tthis(new PrismFileLog(\"stdout\"));\n\t}\n\n\tpublic Reactions2Prism(PrismLog mainLog)\n\t{\n\t\tthis.mainLog = mainLog;\n\t}\n\n\tpublic void setMaxAmount(int maxAmount)\n\t{\n\t\tthis.maxAmount = maxAmount;\n\t}\n\n\t/**\n\t * Print the currently loaded reaction set model (for testing purposes).\n\t */\n\tprotected void printModel(PrintStream out)\n\t{\n\t\tint i, n;\n\t\tReaction reaction;\n\n\t\tout.println(speciesList.size() + \" species: \" + speciesList);\n\t\tif (parameterList.size() > 0)\n\t\t\tout.println(parameterList.size() + \" parameters: \" + parameterList);\n\t\tn = reactionList.size();\n\t\tout.println(n + \" reactions:\");\n\t\tfor (i = 0; i < n; i++) {\n\t\t\treaction = reactionList.get(i);\n\t\t\tout.print(\" * \" + reaction);\n\t\t}\n\t}\n\n\t/**\n\t * Process the currently loaded reaction set model, convert to PRISM code, export to an OutputStream. \n\t */\n\tprotected void convertToPRISMCode(PrintStream out) throws PrismException\n\t{\n\t\tStringBuilder sb = convertToPRISMCode();\n\t\ttry {\n\t\t\tOutputStreamWriter writer = new OutputStreamWriter(new BufferedOutputStream(out), \"utf-8\");\n\t\t\twriter.append(sb);\n\t\t\twriter.flush();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"Error writing to output stream\");\n\t\t}\n\t}\n\n\t/**\n\t * Process the currently loaded reaction set model, convert to PRISM code, export as file. \n\t */\n\tprotected void convertToPRISMCode(File file) throws PrismException\n\t{\n\t\tStringBuilder sb = convertToPRISMCode();\n\t\t//OutputStreamWriter writer = new OutputStreamWriter(new BufferedOutputStream(outputStream), \"utf-8\");\n\t\ttry {\n\t\t\tBufferedWriter writer = new BufferedWriter(new FileWriter(file));\n\t\t\twriter.append(sb);\n\t\t\twriter.close();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"Error writing to file \\\"\" + file + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Process the currently loaded reaction set model, convert to PRISM code, return as StringBuilder. \n\t */\n\tprotected StringBuilder convertToPRISMCode() throws PrismException\n\t{\n\t\tprocessModel();\n\t\treturn generatePRISMCode();\n\t}\n\n\t/**\n\t * Do some processing of the reaction set model in preparation for conversion to PRISM code.\n\t */\n\tprivate void processModel() throws PrismException\n\t{\n\t\tint j, k, m;\n\t\tString s, s2;\n\t\tHashSet<String> modulesNames;\n\t\tHashSet<String> prismIdents;\n\n\t\t// Check species ids are unique\n\t\tArrayList<String> speciesIDs = new ArrayList<String>();\n\t\tfor (Species species : speciesList) {\n\t\t\tif (speciesIDs.contains(species.id))\n\t\t\t\tthrow new PrismException(\"Duplicate species id \\\"\" + species.id + \"\\\"\");\n\t\t\tspeciesIDs.add(species.id);\n\t\t}\n\t\t// Check parameter names are unique\n\t\tArrayList<String> paramNames = new ArrayList<String>();\n\t\tfor (Parameter parameter : parameterList) {\n\t\t\tif (paramNames.contains(parameter.name))\n\t\t\t\tthrow new PrismException(\"Duplicate parameter name \\\"\" + parameter.name + \"\\\"\");\n\t\t\tparamNames.add(parameter.name);\n\t\t}\n\t\t// Check reaction ids are unique\n\t\tArrayList<String> reactionIDs = new ArrayList<String>();\n\t\tfor (Reaction reaction : reactionList) {\n\t\t\tif (reactionIDs.contains(reaction.id))\n\t\t\t\tthrow new PrismException(\"Duplicate reaction id \\\"\" + reaction.id + \"\\\"\");\n\t\t\treactionIDs.add(reaction.id);\n\t\t}\n\t\t\n\t\t// Look at initial amounts for all species\n\t\t// If any exceed MAX_AMOUNT, increase it accordingly\n\t\tfor (Species species : speciesList) {\n\t\t\tif (species.init > maxAmount)\n\t\t\t\tmaxAmount = (int) species.init;\n\t\t}\n\n\t\t// Generate unique and valid PRISM identifier (module and variable name) for each species\n\t\tmodulesNames = new HashSet<String>();\n\t\tprismIdents = new HashSet<String>();\n\t\tfor (Species species : speciesList) {\n\t\t\ts = species.id;\n\t\t\ts2 = convertToValidPrismIdent(s);\n\t\t\tif (!s.equals(s2))\n\t\t\t\tmainLog.printWarning(\"Converted species id \\\"\" + s + \"\\\" to \\\"\" + s2 + \"\\\" (invalid PRISM identifier)\");\n\t\t\tif (!modulesNames.add(s2)) {\n\t\t\t\tj = 2;\n\t\t\t\twhile (!modulesNames.add(s2 + \"_\" + j))\n\t\t\t\t\tj++;\n\t\t\t\ts2 = s2 + \"_\" + j;\n\t\t\t\tmainLog.printWarning(\"Converted species id \\\"\" + s + \"\\\" to \\\"\" + s2 + \"\\\" (duplicate PRISM identifiers)\");\n\t\t\t}\n\t\t\tspecies.prismName = s2;\n\t\t\tprismIdents.add(s2);\n\t\t}\n\n\t\t// Generate unique and valid PRISM constant name for model parameter\n\t\tfor (Parameter parameter : parameterList) {\n\t\t\ts = parameter.name;\n\t\t\ts2 = convertToValidPrismIdent(s);\n\t\t\tif (!s.equals(s2))\n\t\t\t\tmainLog.printWarning(\"Converted parameter id \\\"\" + s + \"\\\" to \\\"\" + s2 + \"\\\" (invalid PRISM identifier)\");\n\t\t\tif (!modulesNames.add(s2)) {\n\t\t\t\tj = 2;\n\t\t\t\twhile (!prismIdents.add(s2 + \"_\" + j))\n\t\t\t\t\tj++;\n\t\t\t\ts2 = s2 + \"_\" + j;\n\t\t\t\tmainLog.printWarning(\"Converted parameter id \\\"\" + s + \"\\\" to \\\"\" + s2 + \"\\\" (duplicate PRISM identifiers)\");\n\t\t\t}\n\t\t\tparameter.prismName = s2;\n\t\t\tprismIdents.add(s2);\n\t\t}\n\n\t\t// Generate unique and valid PRISM constant name for each reaction parameter\n\t\tfor (Reaction reaction : reactionList) {\n\t\t\tm = reaction.parameters.size();\n\t\t\tfor (j = 0; j < m; j++) {\n\t\t\t\ts = reaction.parameters.get(j).name;\n\t\t\t\ts2 = convertToValidPrismIdent(s);\n\t\t\t\tif (!s.equals(s2))\n\t\t\t\t\tmainLog.printWarning(\"Converted parameter id \\\"\" + s + \"\\\" to \\\"\" + s2 + \"\\\" (invalid PRISM identifier)\");\n\t\t\t\tif (!prismIdents.add(s2)) {\n\t\t\t\t\tk = 2;\n\t\t\t\t\twhile (!prismIdents.add(s2 + \"_\" + k))\n\t\t\t\t\t\tk++;\n\t\t\t\t\ts2 = s2 + \"_\" + k;\n\t\t\t\t\tmainLog.printWarning(\"Converted parameter id \\\"\" + s + \"\\\" to \\\"\" + s2 + \"\\\" (duplicate PRISM identifiers)\");\n\t\t\t\t}\n\t\t\t\treaction.parameters.get(j).prismName = s2;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Generate PRISM code for the (already processed) reaction set model.\n\t */\n\tprivate StringBuilder generatePRISMCode() throws PrismException\n\t{\n\t\tint i, i2, n, n2, before, after;\n\t\tSpecies species;\n\t\tReaction reaction;\n\t\tParameter parameter;\n\t\tString s2;\n\t\tArrayList<String> renameFrom = new ArrayList<String>();\n\t\tArrayList<String> renameTo = new ArrayList<String>();\n\t\tStringBuilder sb = new StringBuilder();\n\n\t\t// Header\n\t\tif (prismCodeHeader != null)\n\t\t\tsb.append(prismCodeHeader);\n\t\tsb.append(\"ctmc\\n\");\n\t\tsb.append(\"\\nconst int MAX_AMOUNT = \" + maxAmount + \";\\n\");\n\n\t\t// If required, add a constant for compartment size\n\t\tif (compartmentName != null) {\n\t\t\tsb.append(\"\\n// Compartment size\\n\");\n\t\t\tsb.append(\"const double \" + compartmentName + \" = \" + compartmentSize + \";\\n\");\n\t\t}\n\n\t\t// Generate constant definition for each (model and reaction) parameter\n\t\tn = parameterList.size();\n\t\tif (n > 0)\n\t\t\tsb.append(\"\\n// Model parameters\\n\");\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tparameter = parameterList.get(i);\n\t\t\tsb.append(\"const double \" + parameter.prismName);\n\t\t\tif (parameter.value != null && parameter.value.length() > 0)\n\t\t\t\tsb.append(\" = \" + parameter.value);\n\t\t\tsb.append(\"; // \" + parameter.name + \"\\n\");\n\t\t}\n\t\tn = reactionList.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\treaction = reactionList.get(i);\n\t\t\tn2 = reaction.parameters.size();\n\t\t\tif (n2 > 0)\n\t\t\t\tsb.append(\"\\n// Parameters for reaction \" + reaction.id + \"\\n\");\n\t\t\tfor (i2 = 0; i2 < n2; i2++) {\n\t\t\t\tparameter = reaction.parameters.get(i2);\n\t\t\t\tsb.append(\"const double \" + parameter.prismName);\n\t\t\t\tif (parameter.value != null && parameter.value.length() > 0)\n\t\t\t\t\tsb.append(\" = \" + parameter.value);\n\t\t\t\tsb.append(\"; // \" + parameter.name + \"\\n\");\n\t\t\t}\n\t\t}\n\n\t\t// Generate module for each species (except those with boundaryCondition=true)\n\t\tn = speciesList.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tspecies = speciesList.get(i);\n\t\t\tif (species.boundaryCondition)\n\t\t\t\tcontinue;\n\t\t\tsb.append(\"\\n// Species \" + species + \"\\n\");\n\t\t\tsb.append(\"const int \" + species.prismName + \"_MAX = MAX_AMOUNT;\\n\");\n\t\t\tsb.append(\"module \" + species.prismName + \"\\n\");\n\n\t\t\t// Generate variable representing the amount of this species\n\t\t\tsb.append(\"\\t\\n\\t\" + species.prismName + \" : [0..\" + species.prismName + \"_MAX]\");\n\t\t\tsb.append(\" init \" + (int) species.init + \"; // Initial amount \" + (int) species.init + \"\\n\\t\\n\");\n\t\t\t//\t\t\tsb.append(\" init \" + (int)Math.round(scaleFactor*species.init) + \"; // Initial amount \" + species.init + \"\\n\\t\\n\");\n\n\t\t\t// Generate a command for each reaction that involves this species\n\t\t\tn2 = reactionList.size();\n\t\t\tfor (i2 = 0; i2 < n2; i2++) {\n\t\t\t\treaction = reactionList.get(i2);\n\t\t\t\tif (reaction.isSpeciesInvolved(species.id)) {\n\t\t\t\t\t// Forwards\n\t\t\t\t\tsb.append(\"\\t// \" + reaction.id);\n\t\t\t\t\tif (reaction.name.length() > 0)\n\t\t\t\t\t\tsb.append(\" (\" + reaction.name + \")\");\n\t\t\t\t\tsb.append(\"\\n\");\n\t\t\t\t\tsb.append(\"\\t[\" + reaction.id + \"] \");\n\t\t\t\t\tbefore = reaction.before(species.id);\n\t\t\t\t\tafter = reaction.after(species.id);\n\t\t\t\t\tif (before > 0)\n\t\t\t\t\t\tsb.append(species.prismName + \" > \" + (before - 1));\n\t\t\t\t\tif (after - before > 0) {\n\t\t\t\t\t\tif (before > 0)\n\t\t\t\t\t\t\tsb.append(\" &\");\n\t\t\t\t\t\tsb.append(\" \" + species.prismName + \" <= \" + species.prismName + \"_MAX-\" + (after - before));\n\t\t\t\t\t}\n\t\t\t\t\tsb.append(\" -> (\" + species.prismName + \"'=\" + species.prismName);\n\t\t\t\t\tif (after - before > 0)\n\t\t\t\t\t\tsb.append(\"+\" + (after - before));\n\t\t\t\t\tif (after - before < 0)\n\t\t\t\t\t\tsb.append((after - before));\n\t\t\t\t\tsb.append(\");\\n\");\n\t\t\t\t\t// Maybe also backwards\n\t\t\t\t\tif (reaction.reversible) {\n\t\t\t\t\t\tsb.append(\"\\t// \" + reaction.id);\n\t\t\t\t\t\tif (reaction.name.length() > 0)\n\t\t\t\t\t\t\tsb.append(\" (\" + reaction.name + \")\");\n\t\t\t\t\t\tsb.append(\" (reverse)\\n\");\n\t\t\t\t\t\tsb.append(\"\\t[\" + reaction.id + \"_rev] \");\n\t\t\t\t\t\tbefore = reaction.after(species.id);\n\t\t\t\t\t\tafter = reaction.before(species.id);\n\t\t\t\t\t\tif (before > 0)\n\t\t\t\t\t\t\tsb.append(species.prismName + \" > \" + (before - 1));\n\t\t\t\t\t\tif (after - before > 0) {\n\t\t\t\t\t\t\tif (before > 0)\n\t\t\t\t\t\t\t\tsb.append(\" &\");\n\t\t\t\t\t\t\tsb.append(\" \" + species.prismName + \" <= \" + species.prismName + \"_MAX-\" + (after - before));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tsb.append(\" -> (\" + species.prismName + \"'=\" + species.prismName);\n\t\t\t\t\t\tif (after - before > 0)\n\t\t\t\t\t\t\tsb.append(\"+\" + (after - before));\n\t\t\t\t\t\tif (after - before < 0)\n\t\t\t\t\t\t\tsb.append((after - before));\n\t\t\t\t\t\tsb.append(\");\\n\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Generate the end of this module definition\n\t\t\tsb.append(\"\\t\\nendmodule\\n\");\n\t\t}\n\n\t\t// Generate dummy module to store reaction rates\n\t\tsb.append(\"\\n// Reaction rates\\nmodule reaction_rates\\n\\n\");\n\t\tn = reactionList.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\treaction = reactionList.get(i);\n\t\t\t// Build info about renames (to unique PRISM idents)\n\t\t\trenameFrom.clear();\n\t\t\trenameTo.clear();\n\t\t\tn2 = speciesList.size();\n\t\t\tfor (i2 = 0; i2 < n2; i2++) {\n\t\t\t\tspecies = speciesList.get(i2);\n\t\t\t\tif (!species.id.equals(species.prismName)) {\n\t\t\t\t\trenameFrom.add(species.id);\n\t\t\t\t\trenameTo.add(species.prismName);\n\t\t\t\t}\n\t\t\t}\n\t\t\tn2 = reaction.parameters.size();\n\t\t\tfor (i2 = 0; i2 < n2; i2++) {\n\t\t\t\tparameter = reaction.parameters.get(i2);\n\t\t\t\tif (!parameter.name.equals(parameter.prismName)) {\n\t\t\t\t\trenameFrom.add(parameter.name);\n\t\t\t\t\trenameTo.add(parameter.prismName);\n\t\t\t\t}\n\t\t\t}\n\t\t\tn2 = parameterList.size();\n\t\t\tfor (i2 = 0; i2 < n2; i2++) {\n\t\t\t\tparameter = parameterList.get(i2);\n\t\t\t\tif (!parameter.name.equals(parameter.prismName)) {\n\t\t\t\t\trenameFrom.add(parameter.name);\n\t\t\t\t\trenameTo.add(parameter.prismName);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Generate code\n\t\t\t// Forwards\n\t\t\tsb.append(\"\\t// \" + reaction.id);\n\t\t\tif (reaction.name.length() > 0)\n\t\t\t\tsb.append(\" (\" + reaction.name + \")\");\n\t\t\tsb.append(\": \" + reaction.reactionString());\n\t\t\tsb.append(\"\\n\");\n\t\t\tif (reaction.kineticLawString != null)\n\t\t\t\ts2 = reaction.kineticLawString;\n\t\t\telse\n\t\t\t\ts2 = MathML2Prism.convert(reaction.kineticLaw, renameFrom, renameTo);\n\t\t\tsb.append(\"\\t[\" + reaction.id + \"] \" + s2 + \" > 0 -> \" + s2 + \" : true;\\n\");\n\t\t\t// Maybe also backwards\n\t\t\tif (reaction.reversible) {\n\t\t\t\tsb.append(\"\\t// \" + reaction.id);\n\t\t\t\tif (reaction.name.length() > 0)\n\t\t\t\t\tsb.append(\" (\" + reaction.name + \")\");\n\t\t\t\tsb.append(\": \" + reaction.reactionString());\n\t\t\t\tsb.append(\" (reverse)\\n\");\n\t\t\t\tif (reaction.kineticLawReverseString != null)\n\t\t\t\t\ts2 = reaction.kineticLawReverseString;\n\t\t\t\telse\n\t\t\t\t\ts2 = MathML2Prism.convert(reaction.kineticLawReverse, renameFrom, renameTo);\n\t\t\t\tsb.append(\"\\t[\" + reaction.id + \"_rev] \" + s2 + \" > 0 -> \" + s2 + \" : true;\\n\");\n\t\t\t}\n\t\t}\n\t\tsb.append(\"\\nendmodule\\n\");\n\n\t\t// Generate a reward structure for each species\n\t\tsb.append(\"\\n// Reward structures (one per species)\\n\\n\");\n\t\tn = speciesList.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tspecies = speciesList.get(i);\n\t\t\tif (species.boundaryCondition)\n\t\t\t\tcontinue;\n\t\t\tsb.append(\"// Reward \" + (i + 1) + \": \" + species + \"\\nrewards \\\"\" + species.prismName + \"\\\" true : \" + species.prismName + \"; endrewards\\n\");\n\t\t}\n\n\t\t// Footer\n\t\tif (prismCodeFooter != null)\n\t\t\tsb.append(prismCodeFooter);\n\n\t\treturn sb;\n\t}\n\n\t// Check whether a given string is a valid PRISM language identifier\n\n\tprotected static boolean isValidPrismIdent(String s)\n\t{\n\t\tif (!s.matches(\"[_a-zA-Z_][_a-zA-Z0-9]*\"))\n\t\t\treturn false;\n\t\tif (PrismParser.isKeyword(s))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n\n\t// Convert a string to a valid PRISM language identifier (by removing invalid characters)\n\n\tprotected static String convertToValidPrismIdent(String s)\n\t{\n\t\tString s2;\n\t\tif (!s.matches(\"[_a-zA-Z_][_a-zA-Z0-9]*\"))\n\t\t\ts2 = s.replaceAll(\"[^_a-zA-Z0-9]\", \"\");\n\t\telse\n\t\t\ts2 = s;\n\t\tif (PrismParser.isKeyword(s2))\n\t\t\ts2 = \"_\" + s2;\n\t\treturn s2;\n\t}\n\n\t// Classes to store info about a set of reactions\n\n\tclass Species\n\t{\n\t\tpublic String id;\n\t\tpublic String name;\n\t\tpublic double init;\n\t\tpublic String prismName;\n\t\tpublic boolean boundaryCondition;\n\n\t\tpublic Species(String id, String name, double init)\n\t\t{\n\t\t\tthis.id = id;\n\t\t\tthis.name = name;\n\t\t\tthis.init = init;\n\t\t\tthis.prismName = null;\n\t\t\tthis.boundaryCondition = false;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn id + (name != null && name.length() > 0 ? (\" (\" + name + \")\") : \"\");\n\t\t}\n\t}\n\n\tclass Parameter\n\t{\n\t\tpublic String name;\n\t\tpublic String value;\n\t\tpublic String prismName;\n\n\t\tpublic Parameter(String name, String value)\n\t\t{\n\t\t\tthis.name = name;\n\t\t\tthis.value = value;\n\t\t\tthis.prismName = null;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn name + \"=\" + value;\n\t\t}\n\t}\n\n\tclass Reaction\n\t{\n\t\tpublic String id;\n\t\tpublic String name;\n\t\tpublic ArrayList<String> reactants;\n\t\tpublic ArrayList<Integer> reactantStoichs;\n\t\tpublic ArrayList<String> products;\n\t\tpublic ArrayList<Integer> productStoichs;\n\t\tpublic boolean reversible;\n\t\tpublic Element kineticLaw;\n\t\tpublic String kineticLawString;\n\t\tpublic Element kineticLawReverse;\n\t\tpublic String kineticLawReverseString;\n\t\tpublic ArrayList<Parameter> parameters;\n\n\t\tpublic Reaction(String id, String name)\n\t\t{\n\t\t\tthis.id = id;\n\t\t\tthis.name = name;\n\t\t\treactants = new ArrayList<String>();\n\t\t\treactantStoichs = new ArrayList<Integer>();\n\t\t\tproducts = new ArrayList<String>();\n\t\t\tproductStoichs = new ArrayList<Integer>();\n\t\t\treversible = false;\n\t\t\tkineticLaw = null;\n\t\t\tkineticLawString = null;\n\t\t\tkineticLawReverse = null;\n\t\t\tkineticLawReverseString = null;\n\t\t\tparameters = new ArrayList<Parameter>();\n\t\t}\n\n\t\tpublic void addReactant(String reactant)\n\t\t{\n\t\t\taddReactant(reactant, 1);\n\t\t}\n\n\t\tpublic void addReactant(String reactant, int stoich)\n\t\t{\n\t\t\tint i = reactants.indexOf(reactant);\n\t\t\tif (i == -1) {\n\t\t\t\treactants.add(reactant);\n\t\t\t\treactantStoichs.add(stoich);\n\t\t\t} else {\n\t\t\t\treactantStoichs.set(i, reactantStoichs.get(i) + stoich);\n\t\t\t}\n\t\t}\n\n\t\tpublic void addProduct(String product)\n\t\t{\n\t\t\taddProduct(product, 1);\n\t\t}\n\n\t\tpublic void addProduct(String product, int stoich)\n\t\t{\n\t\t\tint i = products.indexOf(product);\n\t\t\tif (i == -1) {\n\t\t\t\tproducts.add(product);\n\t\t\t\tproductStoichs.add(stoich);\n\t\t\t} else {\n\t\t\t\tproductStoichs.set(i, productStoichs.get(i) + stoich);\n\t\t\t}\n\t\t}\n\n\t\tpublic void setReversible(boolean reversible)\n\t\t{\n\t\t\tthis.reversible = reversible;\n\t\t}\n\n\t\tpublic void setKineticLaw(Element kineticLaw)\n\t\t{\n\t\t\tthis.kineticLaw = kineticLaw;\n\t\t\tthis.kineticLawString = null;\n\t\t}\n\n\t\tpublic void setKineticLawString(String kineticLawString)\n\t\t{\n\t\t\tthis.kineticLawString = kineticLawString;\n\t\t\tthis.kineticLaw = null;\n\t\t}\n\n\t\tpublic void setKineticLawReverse(Element kineticLawReverse)\n\t\t{\n\t\t\tthis.kineticLawReverse = kineticLawReverse;\n\t\t\tthis.kineticLawReverseString = null;\n\t\t}\n\n\t\tpublic void setKineticLawReverseString(String kineticLawReverseString)\n\t\t{\n\t\t\tthis.kineticLawReverseString = kineticLawReverseString;\n\t\t\tthis.kineticLawReverse = null;\n\t\t}\n\n\t\tpublic void addParameter(String name, String value)\n\t\t{\n\t\t\tparameters.add(new Parameter(name, value));\n\t\t}\n\n\t\tpublic boolean isSpeciesInvolved(String species)\n\t\t{\n\t\t\treturn reactants.contains(species) || products.contains(species);\n\t\t}\n\n\t\tpublic int before(String species)\n\t\t{\n\t\t\tint i = reactants.indexOf(species);\n\t\t\tif (i == -1)\n\t\t\t\treturn 0;\n\t\t\treturn reactantStoichs.get(i);\n\t\t}\n\n\t\tpublic int after(String species)\n\t\t{\n\t\t\tint i = products.indexOf(species);\n\t\t\tif (i == -1)\n\t\t\t\treturn 0;\n\t\t\treturn productStoichs.get(i);\n\t\t}\n\n\t\tpublic String reactionString()\n\t\t{\n\t\t\tString s = PrismUtils.joinString(reactants, \"+\");\n\t\t\ts += \" -> \" + PrismUtils.joinString(products, \"+\");\n\t\t\treturn s;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\tString s = \"\";\n\t\t\ts += id;\n\t\t\tif (name.length() > 0)\n\t\t\t\ts += \" (\" + name + \")\";\n\t\t\ts += \":\\n\";\n\t\t\ts += \"    Reactants: \" + reactants + \"\\n\";\n\t\t\ts += \"    Reactants stoichiometry: \" + productStoichs + \"\\n\";\n\t\t\ts += \"    Products: \" + products + \"\\n\";\n\t\t\ts += \"    Products stoichiometry: \" + productStoichs + \"\\n\";\n\t\t\ts += \"    Kinetic law: \" + ((kineticLawString != null) ? kineticLawString : kineticLaw) + \"\\n\";\n\t\t\tif (reversible) {\n\t\t\t\ts += \"    Reverse kinetic law: \" + ((kineticLawReverseString != null) ? kineticLawReverseString : kineticLawReverse) + \"\\n\";\n\t\t\t}\n\t\t\ts += \"    Parameters: \" + parameters + \"\\n\";\n\t\t\treturn s;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ReactionsText2Prism.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.BufferedReader;\nimport java.io.File;\nimport java.io.IOException;\nimport java.io.InputStream;\nimport java.io.InputStreamReader;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\n\n/**\n * Class to convert a textual description of a set of reactions into PRISM code.\n */\npublic class ReactionsText2Prism extends Reactions2Prism\n{\n\t/** Name of the original file */\n\tprotected String parsedFileName;\n\t\n\t// Enums\n\n\tprivate enum SectionType {\n\t\tSPECIES, PARAMETERS, REACTIONS, RR, R\n\t};\n\n\t// Constructors\n\n\tpublic ReactionsText2Prism() throws PrismException\n\t{\n\t\tsuper();\n\t}\n\n\tpublic ReactionsText2Prism(PrismLog mainLog)\n\t{\n\t\tsuper(mainLog);\n\t}\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"reactions\";\n\t}\n\n\t@Override\n\tpublic void load(File file) throws PrismException\n\t{\n\t\t// Store filename for later use before parsing\n\t\tparsedFileName = file.getPath();\n\t\tsuper.load(file);\n\t}\n\n\t@Override\n\tpublic void load(InputStream in) throws PrismException\n\t{\n\t\tBufferedReader buf;\n\t\tSectionType secType = null;\n\t\tString s, s2, ss[], ss2[];\n\t\tint i, lineNum = 0;\n\t\tSpecies species;\n\t\tParameter parameter;\n\t\tReaction reaction;\n\t\tString reactionId = null, reactionName = null;\n\t\t\n\t\t// Initialise storage\n\t\tspeciesList = new ArrayList<Species>();\n\t\tparameterList = new ArrayList<Parameter>();\n\t\treactionList = new ArrayList<Reaction>();\n\n\t\ttry {\n\t\t\t// Open file for reading\n\t\t\tbuf = new BufferedReader(new InputStreamReader(in));\n\t\t\t// Read remaining lines\n\t\t\ts = buf.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\t// Strip comments\n\t\t\t\ts = s.replaceFirst(\" *#.*\", \"\");\n\t\t\t\t// Skip blank lines\n\t\t\t\ts = s.trim();\n\t\t\t\tif (s.length() > 0) {\n\n\t\t\t\t\t// Switch mode on section header\n\t\t\t\t\tif (s.charAt(0) == '@') {\n\t\t\t\t\t\ts2 = s.substring(1);\n\t\t\t\t\t\tif (s2.equals(\"species\")) {\n\t\t\t\t\t\t\tsecType = SectionType.SPECIES;\n\t\t\t\t\t\t} else if (s2.equals(\"parameters\")) {\n\t\t\t\t\t\t\tsecType = SectionType.PARAMETERS;\n\t\t\t\t\t\t} else if (s2.equals(\"reactions\")) {\n\t\t\t\t\t\t\tsecType = SectionType.REACTIONS;\n\t\t\t\t\t\t} else if (s2.startsWith(\"rr=\")) {\n\t\t\t\t\t\t\tsecType = SectionType.RR;\n\t\t\t\t\t\t\t// Extract reaction id/name \n\t\t\t\t\t\t\ts2 = s2.substring(3);\n\t\t\t\t\t\t\ti = s2.indexOf(' ');\n\t\t\t\t\t\t\treactionId = s2.substring(0, i > 0 ? i : s2.length());\n\t\t\t\t\t\t\treactionName = i > 0 ? s2.substring(i + 1).replaceAll(\"\\\"\", \"\") : \"\";\n\t\t\t\t\t\t} else if (s2.startsWith(\"r=\")) {\n\t\t\t\t\t\t\tsecType = SectionType.R;\n\t\t\t\t\t\t\t// Extract reaction id/name \n\t\t\t\t\t\t\ts2 = s2.substring(2);\n\t\t\t\t\t\t\ti = s2.indexOf(' ');\n\t\t\t\t\t\t\treactionId = s2.substring(0, i > 0 ? i : s2.length());\n\t\t\t\t\t\t\treactionName = i > 0 ? s2.substring(i + 1).replaceAll(\"\\\"\", \"\") : \"\";\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tthrow new PrismException(\"@\" + s2 + \" section not supported\");\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tswitch (secType) {\n\n\t\t\t\t\t\t// Species list\n\t\t\t\t\t\tcase SPECIES:\n\t\t\t\t\t\t\tss = s.split(\"=\");\n\t\t\t\t\t\t\tif (ss.length != 2)\n\t\t\t\t\t\t\t\tthrow new PrismException(\"invalid species definition \\\"\" + s + \"\\\"\");\n\t\t\t\t\t\t\t// Get id\n\t\t\t\t\t\t\tString speciesId = ss[0];\n\t\t\t\t\t\t\t// Get init amount/name\n\t\t\t\t\t\t\ts2 = ss[1].trim();\n\t\t\t\t\t\t\ti = s2.indexOf(' ');\n\t\t\t\t\t\t\tString sInit = s2.substring(0, i > 0 ? i : s2.length());\n\t\t\t\t\t\t\tString speciesName = i > 0 ? s2.substring(i + 1).replaceAll(\"\\\"\", \"\") : null;\n\t\t\t\t\t\t\tint initialAmount = Integer.parseInt(sInit);\n\t\t\t\t\t\t\tspecies = new Species(speciesId, speciesName, initialAmount);\n\t\t\t\t\t\t\tspeciesList.add(species);\n\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t// Parameter list\n\t\t\t\t\t\tcase PARAMETERS:\n\t\t\t\t\t\t\tss = s.split(\"=\");\n\t\t\t\t\t\t\tif (ss.length == 1) {\n\t\t\t\t\t\t\t\t// Get id (value undefined)\n\t\t\t\t\t\t\t\tString paramId = ss[0];\n\t\t\t\t\t\t\t\tparameter = new Parameter(paramId, null);\n\t\t\t\t\t\t\t} else if (ss.length == 2) {\n\t\t\t\t\t\t\t\t// Get id and value\n\t\t\t\t\t\t\t\tString paramId = ss[0];\n\t\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\t\tDouble.parseDouble(ss[1]);\n\t\t\t\t\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t\t\t\t\tthrow new PrismException(\"invalid value \\\"\" + ss[1] + \"\\\" for parameter \\\"\" + paramId + \"\\\"\");\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tparameter = new Parameter(paramId, ss[1]);\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tthrow new PrismException(\"invalid parameter definition \\\"\" + s + \"\\\"\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tparameterList.add(parameter);\n\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t// Reaction\n\t\t\t\t\t\tcase RR:\n\t\t\t\t\t\tcase R:\n\t\t\t\t\t\t\tss = s.split(\"->\");\n\t\t\t\t\t\t\tif (ss.length != 2)\n\t\t\t\t\t\t\t\tthrow new PrismException(\"invalid reaction definition \\\"\" + s + \"\\\"\");\n\t\t\t\t\t\t\t// Create reaction object with earlier info\n\t\t\t\t\t\t\treaction = new Reaction(reactionId, reactionName);\n\t\t\t\t\t\t\t// Get reactants\n\t\t\t\t\t\t\tss2 = ss[0].trim().split(\"\\\\+\");\n\t\t\t\t\t\t\tfor (String reactant : ss2) {\n\t\t\t\t\t\t\t\treaction.addReactant(reactant, 1);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// Get products\n\t\t\t\t\t\t\tss2 = ss[1].trim().split(\"\\\\+\");\n\t\t\t\t\t\t\tfor (String product : ss2) {\n\t\t\t\t\t\t\t\treaction.addProduct(product, 1);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// Next line\n\t\t\t\t\t\t\ts = buf.readLine();\n\t\t\t\t\t\t\tlineNum++;\n\t\t\t\t\t\t\tif (s == null)\n\t\t\t\t\t\t\t\tthrow new PrismException(\"missing line in reaction definition\");\n\t\t\t\t\t\t\t// Strip comments\n\t\t\t\t\t\t\ts = s.replaceFirst(\" *#.*\", \"\");\n\t\t\t\t\t\t\ts = s.trim();\n\t\t\t\t\t\t\t// Get kinetic law\n\t\t\t\t\t\t\t// Irreversible case\n\t\t\t\t\t\t\tif (secType == SectionType.R) {\n\t\t\t\t\t\t\t\treaction.setReversible(false);\n\t\t\t\t\t\t\t\treaction.setKineticLawString(s);\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// Irreversible case\n\t\t\t\t\t\t\telse {\n\t\t\t\t\t\t\t\treaction.setReversible(true);\n\t\t\t\t\t\t\t\tss = s.split(\"-\");\n\t\t\t\t\t\t\t\tif (ss.length != 2)\n\t\t\t\t\t\t\t\t\tthrow new PrismException(\"invalid kinetic law \\\"\" + s + \"\\\" for reversible reaction\");\n\t\t\t\t\t\t\t\treaction.setKineticLawString(ss[0].trim());\n\t\t\t\t\t\t\t\treaction.setKineticLawReverseString(ss[1].trim());\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\treactionList.add(reaction);\n\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t// Anything else: skip\n\t\t\t\t\t\tdefault:\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// read next line\n\t\t\t\ts = buf.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\n\t\t\t// close file\n\t\t\tbuf.close();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"I/O error reading reactions: \" + e.getMessage());\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error detected at line \" + lineNum + \" of reactions file\");\n\t\t} catch (PrismException e) {\n\t\t\tthrow new PrismException(\"Error detected (\" + e.getMessage() + \") at line \" + lineNum + \" of reactions file\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void translate(PrintStream out) throws PrismException\n\t{\n\t\t// Generate PRISM code\n\t\tprismCodeHeader = \"// File generated by reactions-to-PRISM conversion\\n\";\n\t\tif (parsedFileName != null) {\n\t\t\tprismCodeHeader += \"// Original file: \" + parsedFileName + \"\\n\\n\";\n\t\t}\n\t\tconvertToPRISMCode(out);\n\t\t// Reset filename storage\n\t\tparsedFileName = null;\n\t}\n\t\n\t/**\n\t * Calling point for command-line script:\n\t * e.g. java -cp classes prism.ReactionsText2Prism myfile.txt 100\n\t * (100 denotes (integer) maximum for species population sizes, default is 100)\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tPrismLog errLog = new PrismPrintStreamLog(System.err);\n\t\ttry {\n\t\t\tif (args.length < 1) {\n\t\t\t\tSystem.err.println(\"Usage: java -cp classes prism.ReactionsText2Prism <file> [max_amount]\");\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t\tReactionsText2Prism rt2prism = new ReactionsText2Prism(errLog);\n\t\t\ttry {\n\t\t\t\tif (args.length > 1)\n\t\t\t\t\trt2prism.setMaxAmount(Integer.parseInt(args[1]));\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Invalid max amount \\\"\" + args[1] + \"\\\"\");\n\t\t\t}\n\t\t\trt2prism.load(new File(args[0]));\n\t\t\trt2prism.translate(System.out);\n\t\t} catch (PrismException e) {\n\t\t\terrLog.println(\"Error: \" + e.getMessage() + \".\");\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Result.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport param.BigRational;\nimport strat.Strategy;\n\n/**\n * This class stores the result of a single verification/simulation.\n * It also stores other info/objects that may be passed back to the user,\n * e.g. an explanation of the result, counterexample, or optimal strategy.\n */\npublic class Result\n{\n\t// The result of model checking\n\tprivate Object result;\n\t// Accuracy of the result\n\tprivate Accuracy accuracy;\n\t// Explanatory text for result (optional)\n\tprivate String explanation;\n\t// Counterexample (optional)\n\tprivate Object cex;\n\t// Strategy (optional)\n\tprivate Strategy<?> strat;\n\t// Solution vector (optional)\n\tprivate StateVector vect;\n\t\n\t/**\n\t * Construct an empty Result object.\n\t */\n\tpublic Result()\n\t{\n\t\tthis.result = null;\n\t\tthis.explanation = null;\n\t\tthis.cex = null;\n\t\tthis.strat = null;\n\t\tthis.vect = null;\n\t}\n\t\n\t/**\n\t * Create a Result object based on a result.\n\t */\n\tpublic Result(Object result)\n\t{\n\t\tthis();\n\t\tsetResult(result);\n\t}\n\t\n\t/**\n\t * Set the accuracy.\n\t */\n\tpublic void setAccuracy(Accuracy accuracy)\n\t{\n\t\tthis.accuracy = accuracy;\n\t}\n\t\n\t/**\n\t * Set the result.\n\t */\n\tpublic void setResult(Object result)\n\t{\n\t\tthis.result = result;\n\t}\n\t\n\t/**\n\t * Set the string of explanatory text (null denotes absent).\n\t */\n\tpublic void setExplanation(String explanation)\n\t{\n\t\tthis.explanation = explanation;\n\t}\n\t\n\t/**\n\t * Set the counterexample (null denotes n/a).\n\t */\n\tpublic void setCounterexample(Object cex)\n\t{\n\t\tthis.cex = cex;\n\t}\n\t\n\t/**\n\t * Set the strategy (null denotes n/a).\n\t */\n\tpublic void setStrategy(Strategy<?> strat)\n\t{\n\t\tthis.strat = strat;\n\t}\n\t\n\t/**\n\t * Set the result vector (null denotes n/a).\n\t */\n\tpublic void setVector(StateVector vect)\n\t{\n\t\t// If we have a vector that was previously stored, clear it.\n\t\tif (this.vect != null) {\n\t\t\tthis.vect.clear();\n\t\t}\n\t\tthis.vect = vect;\n\t}\n\t\n\t/**\n\t * Get the result.\n\t */\n\tpublic Object getResult()\n\t{\n\t\treturn result;\n\t}\n\n\t/**\n\t * Get the accuracy.\n\t */\n\tpublic Accuracy getAccuracy()\n\t{\n\t\treturn accuracy;\n\t}\n\n\t/**\n\t * Get the explanatory text string (null denotes absent).\n\t */\n\tpublic String getExplanation()\n\t{\n\t\treturn explanation;\n\t}\n\n\t/**\n\t * Get the counterexample (null denotes n/a).\n\t */\n\tpublic Object getCounterexample()\n\t{\n\t\treturn cex;\n\t}\n\t\n\t/**\n\t * Get the strategy (null denotes n/a).\n\t */\n\tpublic Strategy<?> getStrategy()\n\t{\n\t\treturn strat;\n\t}\n\t\n\t/**\n\t * Get the result vector (null denotes n/a).\n\t */\n\tpublic StateVector getVector()\n\t{\n\t\treturn vect;\n\t}\n\t\n\t/**\n\t * Get a string of the result and (if present) explanatory text\n\t */\n\tpublic String getResultString()\n\t{\n\t\tString s = result.toString();\n\t\tif (explanation != null)\n\t\t\ts += \" (\" + explanation +\")\";\n\t\treturn s;\n\t}\n\t\n\t/**\n\t * Get a string of the result and its accuracy\n\t */\n\tpublic String getResultAndAccuracy()\n\t{\n\t\tString resultString = result.toString();\n\t\t// If accuracy is missing or blank, omit it\n\t\tif (accuracy != null) {\n\t\t\tString accuracyString = accuracy.toString(result);\n\t\t\tif (accuracyString != null && !\"\".equals(accuracyString)) {\n\t\t\t\tresultString += \" (\" + accuracy.toString(result) + \")\";\n\t\t\t}\n\t\t}\n\t\t// Append approximate value for exact results\n\t\tif (result instanceof BigRational) {\n\t\t\tresultString += \" (\" + ((BigRational) result).toApproximateString() + \")\";\n\t\t}\n\t\treturn resultString;\n\t}\n\t\n\t/**\n\t * Get the string representation of the actual result value.\n\t */\n\tpublic String toString()\n\t{\n\t\treturn result == null ? \"null\" : result.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ResultListener.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\r\npackage prism;\r\n\r\nimport parser.*;\r\n\r\n/**\r\n * This class is an interface between the chart package and ResultCollection.\r\n * From a design point of view it is nice if the ResultCollection is oblivious to the fact that\r\n * charts are generated from the results, and we allow the implementation of ResultListeners.\r\n * \r\n * See {@link  prism.ResultsCollection  ResultCollection}. \r\n */\r\npublic interface ResultListener \r\n{\r\n\t/**\r\n\t * This method is called whenever a ResultCollection discovers a new result. \r\n\t * @param resultsCollection The ResultsCollection from which this result is a member.\r\n\t * @param values The parameters of the experiment.\r\n\t * @param result The result of the experiment (any of Exception, Integer, Boolean, Double, null). Be aware that valid Double values include NaN, and plus and minus infinity.\r\n\t */\r\n\tpublic void notifyResult(ResultsCollection resultsCollection, Values values, Object result);\r\n}\r\n"
  },
  {
    "path": "prism/src/prism/ResultTesting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2020-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.regex.Matcher;\nimport java.util.regex.Pattern;\n\nimport param.BigRational;\nimport param.ParamResult;\nimport parser.EvaluateContext;\nimport parser.Values;\nimport parser.ast.ConstantList;\nimport parser.ast.Expression;\nimport parser.type.Type;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.type.TypeVoid;\nimport prism.Accuracy.AccuracyLevel;\nimport prism.Accuracy.AccuracyType;\n\npublic class ResultTesting\n{\n\t/**\n\t * Default level of accuracy for testing (1e-5; relative error)\n\t */\n\tpublic static final Accuracy DEFAULT_TESTING_ACCURACY = new Accuracy(AccuracyLevel.BOUNDED, 1e-5, AccuracyType.RELATIVE);\n\n\t/**\n\t * Get an Accuracy object for testing. If the one passed in is suitable,\n\t * then it is used. If it is missing (null) or just an estimate, then a\n\t * default level of testing accuracy (DEFAULT_TESTING_ACCURACY) is substituted.\n\t */\n\tpublic static Accuracy getTestingAccuracy(Accuracy accuracy)\n\t{\n\t\tif (accuracy == null || accuracy.getLevel() == AccuracyLevel.ESTIMATED_BOUNDED) {\n\t\t\treturn DEFAULT_TESTING_ACCURACY;\n\t\t} else {\n\t\t\treturn accuracy;\n\t\t}\n\t}\n\t\n\t/**\n\t * Tests a result (specified as a Result object) against the expected result,\n\t * given by a string extracted from a RESULT: specification.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * Otherwise, the method successfully exits, returning a boolean value that indicates\n\t * whether or not a check was actually applied (i.e. if the result specification is of the\n\t * form \"RESULT: ?\") then false is returned; otherwise true.   \n\t * @param strExpected Expected result\n\t * @param constValues The values of any constants (null if none)\n\t * @param params The names of any still undefined constants (null if none)\n\t * @param type The type of the property yielding this result\n\t * @param resultObj The result to check\n\t * @return Whether or not the check was performed\n\t */\n\tpublic static boolean checkAgainstExpectedResultString(String strExpected, Values constValues, List<String> params, Type type, Result resultObj) throws PrismException\n\t{\n\t\tObject result = resultObj.getResult();\n\t\t// Check for special \"don't care\" case\n\t\tif (strExpected.equals(\"?\")) {\n\t\t\treturn false;\n\t\t}\n\t\t// Check for errors/exceptions\n\t\tif (strExpected.startsWith(\"Error\") && !(result instanceof Exception)) {\n\t\t\tthrow new PrismException(\"Was expecting an error\");\n\t\t}\n\t\tif (result instanceof Exception) {\n\t\t\treturn checkExceptionAgainstExpectedResultString(strExpected, (Exception) result);\n\t\t}\n\t\t// Check result of parametric model checking\n\t\tif (result instanceof ParamResult) {\n\t\t\treturn ((ParamResult) result).test(type, strExpected, constValues, params);\n\t\t}\n\t\t// Otherwise, check depends on the type of the property  \n\t\t// Boolean-valued properties\n\t\tif (type instanceof TypeBool) {\n\t\t\tcheckBooleanAgainstExpectedResultString(strExpected, constValues, resultObj);\n\t\t}\n\t\t// Integer-valued properties (non-exact mode)\n\t\telse if (type instanceof TypeInt && !(result instanceof BigRational)) {\n\t\t\tcheckIntAgainstExpectedResultString(strExpected, constValues, resultObj);\n\t\t}\n\t\t// Double-valued properties (non-exact mode)\n\t\telse if (type instanceof TypeDouble && !(result instanceof BigRational)) {\n\t\t\tcheckDoubleAgainstExpectedResultString(strExpected, constValues, resultObj);\n\t\t}\n\t\t// Double-valued or integer-valued properties exact mode)\n\t\telse if ((type instanceof TypeDouble || type instanceof TypeInt) && result instanceof BigRational) {\n\t\t\tcheckExactAgainstExpectedResultString(strExpected, constValues, type, resultObj);\n\t\t}\n\t\telse if (type instanceof TypeVoid && result instanceof TileList) { //Pareto curve\n\t\t\tcheckParetoAgainstExpectedResultString(strExpected, constValues, resultObj);\n\t\t}\n\t\t// Unknown type\n\t\telse {\n\t\t\tthrow new PrismException(\"Don't know how to test properties of type \" + type);\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Tests a result specified as an Exception object against the expected result,\n\t * given by a string extracted from a RESULT: specification.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * Otherwise, the method successfully exits, returning a boolean value that indicates\n\t * whether or not a check was actually applied.   \n\t * @param strExpected Expected result\n\t * @param result The actual result\n\t * @return Whether or not the check was performed\n\t */\n\tprivate static boolean checkExceptionAgainstExpectedResultString(String strExpected, Exception result) throws PrismException\n\t{\n\t\tif (result instanceof PrismNotSupportedException) {\n\t\t\t// not supported -> handle in caller\n\t\t\tthrow (PrismNotSupportedException)result;\n\t\t}\n\t\tString errMsg = result.getMessage();\n\t\tif (strExpected.startsWith(\"Error\")) {\n\t\t\t// handle expected errors\n\t\t\tif (strExpected.startsWith(\"Error:\")) {\n\t\t\t\tString words[] = strExpected.substring(6).split(\",\");\n\t\t\t\tfor (String word : words) {\n\t\t\t\t\tif (word.length() == 0) {\n\t\t\t\t\t\tthrow new PrismException(\"Invalid RESULT specification: no expected words immediately following 'Error:'\");\n\t\t\t\t\t}\n\t\t\t\t\tif (!errMsg.toLowerCase().contains(word.toLowerCase())) {\n\t\t\t\t\t\tthrow new PrismException(\"Error message should contain \\\"\" + word + \"\\\"\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn true;\n\t\t}\n\t\tthrow new PrismException(\"Unexpected error: \" + errMsg);\n\t}\n\t\n\t/**\n\t * Tests a result of type boolean against the expected result,\n\t * given by a string extracted from a RESULT: specification.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * @param strExpected Expected result\n\t * @param constValues The values of any undefined constants (null or \"\" if none)\n\t * @param resultObj The actual result\n\t */\n\tprivate static void checkBooleanAgainstExpectedResultString(String strExpected, Values constValues, Result resultObj) throws PrismException\n\t{\n\t\t// Extract actual result\n\t\tObject result = resultObj.getResult();\n\t\tif (!(result instanceof Boolean)) {\n\t\t\tthrow new PrismException(\"Result is wrong type (\" + result.getClass() + \") for (boolean-valued) property\");\n\t\t}\n\t\tboolean boolRes = ((Boolean) result).booleanValue();\n\t\t// Parse expected result\n\t\tboolean boolExp;\n\t\tif (strExpected.toLowerCase().equals(\"true\")) {\n\t\t\tboolExp = true;\n\t\t} else if (strExpected.toLowerCase().equals(\"false\")) {\n\t\t\tboolExp = false;\n\t\t} else {\n\t\t\tboolExp = parseExpectedResultString(strExpected, constValues).evaluateBoolean(constValues);\n\t\t\tstrExpected += \" = \" + boolExp; \t\n\t\t}\n\t\t// Check result\n\t\tif (boolRes != boolExp) {\n\t\t\tthrow new PrismException(\"Wrong result (expected \" + strExpected + \", got \" + boolRes + \")\");\n\t\t}\n\t}\n\t\n\t/**\n\t * For the case where the expected result string is (or is suspected to be)\n\t * a PRISM expression, perhaps in terms of constants, parse and return it.\n\t * Throws an exception (invalid RESULT spec) if parsing fails.  \n\t * @param strExpected Expected result\n\t * @param constValues The values of any undefined constants (null or \"\" if none)\n\t */\n\tprivate static Expression parseExpectedResultString(String strExpected, Values constValues) throws PrismException\n\t{\n\t\ttry {\n\t\t\tExpression expectedExpr = Prism.parseSingleExpressionString(strExpected);\n\t\t\texpectedExpr = (Expression) expectedExpr.findAllConstants(constValues.getNames(), constValues.getTypes());\n\t\t\texpectedExpr.typeCheck();\n\t\t\treturn expectedExpr;\n\t\t} catch (PrismLangException e) {\n\t\t\tthrow new PrismException(\"Invalid RESULT specification \\\"\" + strExpected + \"\\\": \" + e.getMessage());\n\t\t}\n\t}\n\t\n\t/**\n\t * Tests a result of type int against the expected result,\n\t * given by a string extracted from a RESULT: specification.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * @param strExpected Expected result\n\t * @param constValues The values of any undefined constants (null or \"\" if none)\n\t * @param resultObj The actual result\n\t */\n\tprivate static void checkIntAgainstExpectedResultString(String strExpected, Values constValues, Result resultObj) throws PrismException\n\t{\n\t\t// Extract actual result\n\t\tObject result = resultObj.getResult();\n\t\tif (!(result instanceof Integer)) {\n\t\t\tthrow new PrismException(\"Result is wrong type (\" + result.getClass() + \") for (integer-valued) property\");\n\t\t}\n\t\tint intRes = ((Integer) result).intValue();\n\t\t// Parse expected result\n\t\tint intExp;\n\t\t// See if it's an int literal\n\t\ttry {\n\t\t\tintExp = Integer.parseInt(strExpected);\n\t\t}\n\t\t// If not, could be an expression\n\t\tcatch (NumberFormatException e) {\n\t\t\tintExp = parseExpectedResultString(strExpected, constValues).evaluateInt(constValues);\n\t\t\tstrExpected += \" = \" + intExp; \t\n\t\t}\n\t\t// Check result\n\t\tif (intRes != intExp) {\n\t\t\tthrow new PrismException(\"Wrong result (expected \" + strExpected + \", got \" + intRes + \")\");\n\t\t}\n\t}\n\t\n\t/**\n\t * Tests a result of type double against the expected result,\n\t * given by a string extracted from a RESULT: specification.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * @param strExpected Expected result\n\t * @param constValues The values of any undefined constants (null or \"\" if none)\n\t * @param resultObj The actual result\n\t */\n\tprivate static void checkDoubleAgainstExpectedResultString(String strExpected, Values constValues, Result resultObj) throws PrismException\n\t{\n\t\t// Parse expected result\n\t\tdouble doubleExp;\n\t\t// First, handle ~... expected results\n\t\t// In this case (non-exact mode) it does not really matter,\n\t\t// as we currently do an approximate comparison anyway\n\t\tif (strExpected.startsWith(\"~\")) {\n\t\t\tstrExpected = strExpected.substring(1);\n\t\t}\n\t\t// See if it's NaN\n\t\tif (strExpected.equals(\"NaN\")) {\n\t\t\tdoubleExp = Double.NaN;\n\t\t\tcheckDoubleAgainstExpectedResult(strExpected, doubleExp, resultObj);\n\t\t}\n\t\t// See if it's an interval\n\t\telse if (strExpected.matches(\"\\\\[[^,]+,[^,]+\\\\]\")) {\n\t\t\tString bounds[] = strExpected.substring(1, strExpected.length() - 1).split(\",\");\n\t\t\ttry {\n\t\t\t\tdouble expLow = Double.parseDouble(bounds[0]);\n\t\t\t\tdouble expHigh = Double.parseDouble(bounds[1]);\n\t\t\t\tcheckDoubleAgainstExpectedResultInterval(strExpected, expLow, expHigh, resultObj);\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Invalid RESULT specification \\\"\" + strExpected + \"\\\": \" + e.getMessage());\n\t\t\t}\n\t\t}\n\t\t// See if it's a fraction\n\t\telse if (strExpected.matches(\"-?[0-9]+/[0-9]+\")) {\n\t\t\tdoubleExp = new BigRational(strExpected).doubleValue();\n\t\t\tstrExpected += \" = \" + doubleExp; \t\n\t\t\tcheckDoubleAgainstExpectedResult(strExpected, doubleExp, resultObj);\n\t\t}\n\t\t// See if it's a double literal\n\t\telse try {\n\t\t\tdoubleExp = Double.parseDouble(strExpected);\n\t\t\tcheckDoubleAgainstExpectedResult(strExpected, doubleExp, resultObj);\n\t\t}\n\t\t// If not, could be an expression\n\t\tcatch (NumberFormatException e) {\n\t\t\tdoubleExp = parseExpectedResultString(strExpected, constValues).evaluateDouble(constValues);\n\t\t\tstrExpected += \" = \" + doubleExp; \t\n\t\t\tcheckDoubleAgainstExpectedResult(strExpected, doubleExp, resultObj);\n\t\t}\n\t}\n\t\n\t/**\n\t * Tests a result of type double against the expected result, given as a double.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * @param strExpected Expected result string (for error message)\n\t * @param doubleExp Expected result\n\t * @param resultObj The actual result\n\t */\n\tprivate static void checkDoubleAgainstExpectedResult(String strExpected, double doubleExp, Result resultObj) throws PrismException\n\t{\n\t\t// Extract actual result\n\t\tObject result = resultObj.getResult();\n\t\tif (!(result instanceof Double)) {\n\t\t\tthrow new PrismException(\"Result is wrong type (\" + result.getClass() + \") for (double-valued) property\");\n\t\t}\n\t\tdouble doubleRes = ((Double) result).doubleValue();\n\t\t// Case where one/both is NaN\n\t\tif (Double.isNaN(doubleRes) || Double.isNaN(doubleExp)) {\n\t\t\tif (Double.isNaN(doubleRes) != Double.isNaN(doubleExp)) {\n\t\t\t\tthrow new PrismException(\"Wrong result (expected \" + strExpected + \", got \" + doubleRes + \")\");\n\t\t\t}\n\t\t}\n\t\t// Case where one/both is infinite\n\t\telse if (Double.isInfinite(doubleRes) || Double.isInfinite(doubleExp)) {\n\t\t\tif (doubleRes != doubleExp) {\n\t\t\t\tthrow new PrismException(\"Wrong result (expected \" + strExpected + \", got \" + doubleRes + \")\");\n\t\t\t}\n\t\t}\n\t\t// Normal case: check result is in expected value overlap\n\t\telse {\n\t\t\t// Use accuracy info where possible\n\t\t\t// If it is missing, or only estimated, use default check instead\n\t\t\tAccuracy accuracy = getTestingAccuracy(resultObj.getAccuracy());\n\t\t\t// Check that value falls into ranges of error bounds\n\t\t\tdouble resLow = accuracy.getResultLowerBound(doubleRes, true);\n\t\t\tdouble resHigh = accuracy.getResultUpperBound(doubleRes, true);\n\t\t\tif (!(resLow <= doubleExp && doubleExp <= resHigh)) {\n\t\t\t\tthrow new PrismException(\"Wrong result (expected \" + strExpected + \", abs err = \" + Math.abs(doubleRes - doubleExp) + \" > \" + accuracy.getAbsoluteErrorBound(doubleRes) + \")\");\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Tests a result of type double against the expected result, given as a double.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * @param strExpected Expected result string (for error message)\n\t * @param doubleExp Expected result\n\t * @param resultObj The actual result\n\t */\n\tprivate static void checkDoubleAgainstExpectedResultInterval(String strExpected, double expLow, double expHigh, Result resultObj) throws PrismException\n\t{\n\t\t// Extract actual result\n\t\tObject result = resultObj.getResult();\n\t\tif (!(result instanceof Double)) {\n\t\t\tthrow new PrismException(\"Result is wrong type (\" + result.getClass() + \") for (double-valued) property\");\n\t\t}\n\t\tdouble doubleRes = ((Double) result).doubleValue();\n\t\t// Use accuracy info where possible\n\t\t// If it is missing, or only estimated, use default check instead\n\t\tAccuracy accuracy = getTestingAccuracy(resultObj.getAccuracy());\n\t\t// Check intervals for result and expected value overlap\n\t\tdouble resLow = accuracy.getResultLowerBound(doubleRes, true);\n\t\tdouble resHigh = accuracy.getResultUpperBound(doubleRes, true);\n\t\tif (!(resLow <= expHigh && expLow <= resHigh)) {\n\t\t\tthrow new PrismException(\"Wrong result (expected \" + strExpected + \", got \" + doubleRes + \")\");\n\t\t}\n\t}\n\t\n\t/**\n\t * Tests an exact result (of type int or double) against the expected result,\n\t * given by a string extracted from a RESULT: specification.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * @param strExpected Expected result\n\t * @param constValues The values of any undefined constants (null or \"\" if none)\n\t * @param resultObj The actual result\n\t */\n\tprivate static void checkExactAgainstExpectedResultString(String strExpected, Values constValues, Type type, Result resultObj) throws PrismException\n\t{\n\t\t// Extract actual result\n\t\tObject result = resultObj.getResult();\n\t\tif (!(result instanceof BigRational)) {\n\t\t\tthrow new PrismException(\"Result is wrong type (\" + result.getClass() + \") for exact property\");\n\t\t}\n\t\tBigRational rationalRes = (BigRational) result;\n\t\t// Parse expected result\n\t\tBigRational rationalExp = null;\n\t\t// Deal with NaN separately\n\t\tif (strExpected.equals(\"NaN\")) {\n\t\t\tif (rationalRes.isNaN()) {\n\t\t\t\treturn;\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"Wrong result (expected NaN, got \" + rationalRes + \")\");\n\t\t\t}\n\t\t}\n\t\t// Make a note if we only need to do an approximate comparison\n\t\t// (i.e., a floating point string starting with ~)\n\t\tboolean approx = false; \n\t\tif (strExpected.startsWith(\"~\")) {\n\t\t\tapprox = true;\n\t\t\tstrExpected = strExpected.substring(1);\n\t\t}\n\t\t// See if it's an int/double/rational literal - parse with BigRational\n\t\ttry {\n\t\t\trationalExp = new BigRational(strExpected);\n\t\t}\n\t\t// If not, could be an expression\n\t\tcatch (NumberFormatException e) {\n\t\t\trationalExp = parseExpectedResultString(strExpected, constValues).evaluateBigRational(EvaluateContext.create(constValues, EvaluateContext.EvalMode.EXACT));\n\t\t}\n\t\t// Check result\n\t\tif (!rationalRes.equals(rationalExp)) {\n\t\t\tboolean match = false;\n\t\t\tif (type instanceof TypeDouble) {\n\t\t\t\t// Try imprecise comparison\n\t\t\t\ttry {\n\t\t\t\t\tdouble doubleExp = Double.parseDouble(strExpected);\n\t\t\t\t\t// Use default accuracy since we have no epsilon available\n\t\t\t\t\tdouble resLow = DEFAULT_TESTING_ACCURACY.getResultLowerBound(rationalRes.doubleValue(), true);\n\t\t\t\t\tdouble resHigh = DEFAULT_TESTING_ACCURACY.getResultUpperBound(rationalRes.doubleValue(), true);\n\t\t\t\t\tboolean areClose = (resLow <= doubleExp && doubleExp <= resHigh);\n\t\t\t\t\tif (areClose) {\n\t\t\t\t\t\tif (approx) {\n\t\t\t\t\t\t\t// we only have an approximate value to compare to, so we are fine here\n\t\t\t\t\t\t\tmatch = true;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tthrow new PrismException(\"Inexact, but close result (expected '\" + strExpected + \"' = \" + rationalExp + \" (\"\n\t\t\t\t\t\t\t\t\t+ rationalExp.toApproximateString() + \"), got \" + rationalRes + \" (\" + rationalRes.toApproximateString() + \"))\");\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!match) {\n\t\t\t\tthrow new PrismException(\"Wrong result (expected '\" + strExpected + \"' = \" + rationalExp + \" (\" + rationalExp.toApproximateString() + \"), got \"\n\t\t\t\t\t\t+ rationalRes + \" (\" + rationalRes.toApproximateString() + \"))\");\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Tests a Pareto curve result against the expected result,\n\t * given by a string extracted from a RESULT: specification.\n\t * If the test fails or something else goes wrong, an explanatory PrismException is thrown.\n\t * @param strExpected Expected result\n\t * @param constValues The values of any undefined constants (null or \"\" if none)\n\t * @param resultObj The actual result\n\t */\n\tprivate static void checkParetoAgainstExpectedResultString(String strExpected, Values constValues, Result resultObj) throws PrismException\n\t{\n\t\t// Create the list of points from the expected results\n\t\tList<Point> liExpected = new ArrayList<Point>();\n\t\tPattern p = Pattern.compile(\"\\\\(([^,]*),([^)]*)\\\\)\");\n\t\tMatcher m = p.matcher(strExpected);\n\t\tif (!m.find()) {\n\t\t\tthrow new PrismException(\"The expected result does not contain any points, or does not have the required format.\");\n\t\t}\n\t\t\n\t\tdo {\n\t\t\tdouble x = Double.parseDouble(m.group(1));\n\t\t\tdouble y = Double.parseDouble(m.group(2));\n\t\t\tPoint point = new Point(new double[] {x,y});\n\t\t\tliExpected.add(point);\n\t\t} while(m.find());\n\n\t\tObject result = resultObj.getResult();\n\t\tList<Point> liResult = ((TileList) result).getRealPoints();\n\n\t\tif (liResult.size() != liExpected.size()) {\n\t\t\tthrow new PrismException(\"The expected Pareto curve and the computed Pareto curve have a different number of points.\");\n\t\t}\n\t\t// Check if we can find a matching point for every point on the expected Pareto curve\n\t\tfor(Point point : liExpected) {\n\t\t\tboolean foundClose = false;\n\t\t\tfor(Point point2 : liResult) {\n\t\t\t\tif (point2.isCloseTo(point)) {\n\t\t\t\t\tfoundClose = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!foundClose) {\n\t\t\t\tthrow new PrismException(\"The point \" + point + \" in the expected Pareto curve has no match among the points in the computed Pareto curve.\");\n\t\t\t}\n\t\t}\n\t\t// Check if we can find a matching point for every point on the computed Pareto curve\n\t\t// (we did check if both lists have the same number of points, but that does\n\t\t// not rule out the possibility of two very similar points contained in one list)\n\t\tfor (Point point : liResult) {\n\t\t\tboolean foundClose = false;\n\t\t\tfor (Point point2 : liExpected) {\n\t\t\t\tif (point2.isCloseTo(point)) {\n\t\t\t\t\tfoundClose = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!foundClose) {\n\t\t\t\tthrow new PrismException(\"The point \" + point + \" in the computed Pareto curve has no match among the points in the expected Pareto curve\");\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ResultsCollection.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.*;\n\nimport parser.*;\n\n/**\n * This class stores the results of experiments. It should be unaware what is being done with the results,\n * for instance the plotting of the results.\n */\npublic class ResultsCollection\n{\n\t// Info about the constants over which these results range\n\tprivate Vector<DefinedConstant> rangingConstants;\n\tprivate int numMFRangingConstants;\n\tprivate int numPFRangingConstants;\n\n\t// Info about other constants (over which these results do *not* range)\n\tprivate Values nonRangingConstantValues;\n\t\n\t// Storage of the actual results\n\tprivate TreeNode root;\n\tprivate int currentIteration = 0;\n\tprivate boolean anyErrors = false;\n\n\t// Listeners to results of this ResultCollection\n\tprivate Vector<ResultListener> resultListeners;\n\n\t// the \"name\" of the result (used for y-axis of any graphs plotted)\n\tprivate String resultName;\n\n\t/** Creates a new instance of ResultsCollection */\n\tpublic ResultsCollection(UndefinedConstants uCons)\n\t{\n\t\tthis(uCons, null);\n\t}\n\n\tpublic ResultsCollection(UndefinedConstants uCons, String resultName)\n\t{\n\t\tthis(uCons.getRangingConstants(), uCons.getNumModelRangingConstants(), uCons.getNumPropertyRangingConstants(), uCons.getNonRangingConstantValues(), resultName);\n\t}\n\n\t@SuppressWarnings(\"unchecked\")\n\tpublic ResultsCollection(Vector<DefinedConstant> rangingConstants, int numMFRangingConstants, int numPFRangingConstants, Values nonRangingConstants, String resultName)\n\t{\n\t\tthis.resultListeners = new Vector<ResultListener>();\n\t\tthis.rangingConstants = (Vector<DefinedConstant>) rangingConstants.clone();\n\t\tthis.numMFRangingConstants = numMFRangingConstants; \n\t\tthis.numPFRangingConstants = numPFRangingConstants;\n\t\tthis.nonRangingConstantValues = Objects.requireNonNull(nonRangingConstants);\n\n\t\tthis.root = (this.rangingConstants.size() > 0) ? new TreeNode(0) : new TreeLeaf();\n\t\tthis.resultName = (resultName == null) ? \"Result\" : resultName;\n\t}\n\n\tpublic Vector<DefinedConstant> getRangingConstants()\n\t{\n\t\treturn rangingConstants;\n\t}\n\n\tpublic int getNumRangingConstants()\n\t{\n\t\treturn rangingConstants.size();\n\t}\n\n\tpublic int getNumModelRangingConstants()\n\t{\n\t\treturn numMFRangingConstants;\n\t}\n\n\tpublic int getNumPropertyRangingConstants()\n\t{\n\t\treturn numPFRangingConstants;\n\t}\n\n\tpublic Values getNonRangingConstantValues()\n\t{\n\t\treturn nonRangingConstantValues;\n\t}\n\n\tpublic boolean addResultListener(ResultListener resultListener)\n\t{\n\t\treturn resultListeners.add(resultListener);\n\t}\n\n\tpublic boolean removeResultListener(ResultListener resultListener)\n\t{\n\t\treturn resultListeners.removeElement(resultListener);\n\t}\n\n\tpublic int getCurrentIteration()\n\t{\n\t\treturn currentIteration;\n\t}\n\n\tpublic String getResultName()\n\t{\n\t\treturn resultName;\n\t}\n\n\t/**\n\t * Sets the result for a particular set of values.\n\t */\n\tpublic int setResult(Values values, Object result)\n\t{\n\t\t// store result\n\t\tint ret = root.setResult(values, result);\n\n\t\t// notify listeners\n\t\tfor (int i = 0; i < resultListeners.size(); i++) {\n\t\t\tresultListeners.get(i).notifyResult(this, values, result);\n\t\t}\n\n\t\t// modify counters/flags as appropriate\n\t\tcurrentIteration += ret;\n\t\tif (result instanceof Exception)\n\t\t\tanyErrors = true;\n\n\t\treturn ret;\n\t}\n\n\t/**\n\t * Sets the result for a particular set of values.\n\t */\n\tpublic int setResult(Values mfValues, Values pfValues, Object result)\n\t{\n\t\t// merge mfValues and pfValues\n\t\tValues merged = new Values();\n\t\tif (mfValues != null)\n\t\t\tmerged.addValues(mfValues);\n\t\tif (pfValues != null)\n\t\t\tmerged.addValues(pfValues);\n\n\t\treturn setResult(merged, result);\n\t}\n\n\t/** Sets the result to an error for a particular set of values.\n\t  * If any constants are left undefined, the same error will be set for all values of each constant.\n\t  * Returns the total number of values which were set for the the first time.\n\t  * Note: individual errors can be set using setResult(). That method could easily be adapted to store\n\t  * multiple values but the DisplayableData aspect isn't sorted yet.\n\t  */\n\tpublic int setMultipleErrors(Values values, Exception error)\n\t{\n\t\t// store result\n\t\tint ret = root.setResult(values, error);\n\n\t\t// modify counters/flags as appropriate\n\t\tcurrentIteration += ret;\n\t\tanyErrors = true;\n\n\t\treturn ret;\n\t}\n\n\t/** Sets the result to an error for a particular set of values.\n\t  * If any constants are left undefined, the same error will be set for all values of each constant.\n\t  * Returns the total number of values which were set for the the first time.\n\t  * Note: individual errors can be set using setResult(). That method could easily be adapted to store\n\t  * multiple values but the DisplayableData aspect isn't sorted yet.\n\t  */\n\tpublic int setMultipleErrors(Values mfValues, Values pfValues, Exception error)\n\t{\n\t\t// merge mfValues and pfValues\n\t\tValues merged = new Values();\n\t\tif (mfValues != null)\n\t\t\tmerged.addValues(mfValues);\n\t\tif (pfValues != null)\n\t\t\tmerged.addValues(pfValues);\n\n\t\treturn setMultipleErrors(merged, error);\n\t}\n\n\t/**\n\t * Access a stored result\n\t */\n\tpublic Object getResult(Values val) throws PrismException\n\t{\n\t\treturn root.getResult(val);\n\t}\n\n\t/**\n\t * See if there were any errors\n\t */\n\tpublic boolean containsErrors()\n\t{\n\t\treturn anyErrors;\n\t}\n\n\t/**\n\t * Create array of headings\n\t */\n\tpublic String[] getHeadingsArray()\n\t{\n\t\tint i;\n\t\tString res[] = new String[rangingConstants.size() + 1];\n\n\t\t// create header\n\t\tfor (i = 0; i < rangingConstants.size(); i++) {\n\t\t\tres[i] = rangingConstants.elementAt(i).getName();\n\t\t}\n\t\tres[rangingConstants.size()] = \"Result\";\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Create ArrayList based representation of the data\n\t */\n\tpublic ArrayList<String[]> toArrayList()\n\t{\n\t\treturn root.toArrayList();\n\t}\n\n\t/**\n\t * Create string representation of the data\n\t */\n\tpublic String toString()\n\t{\n\t\treturn toString(false, \",\", \",\", true);\n\t}\n\n\t/**\n\t * Create string representation of the data\n\t */\n\tpublic String toString(boolean pv, String sep, String eq)\n\t{\n\t\treturn toString(pv, sep, eq, true);\n\t}\n\n\t/**\n\t * Create string representation of the data\n\t * @param pv Print the variables in each row?\n\t * @param sep String for separating values\n\t * @param eq String for separating values and result\n\t * @param header Add a header?\n\t */\n\tpublic String toString(boolean pv, String sep, String eq, boolean header)\n\t{\n\t\tString s = \"\";\n\n\t\t// if there are no variables, override eq separator\n\t\tif (rangingConstants.size() == 0)\n\t\t\teq = \"\";\n\t\t// create header\n\t\tif (header) {\n\t\t\tfor (int i = 0; i < rangingConstants.size(); i++) {\n\t\t\t\tif (i > 0)\n\t\t\t\t\ts += sep;\n\t\t\t\ts += rangingConstants.get(i).getName();\n\t\t\t}\n\t\t\ts += eq + \"Result\\n\";\n\t\t}\n\t\t// create table\n\t\ts += root.toString(pv, sep, eq);\n\n\t\treturn s;\n\t}\n\n\t/**\n\t * Pass the results to a ResultsExporter.\n\t * For convenience, returns a pointer to the same ResultsExporter passed in \n\t */\n\tpublic ResultsExporter export(ResultsExporter exporter)\n\t{\n\t\texporter.setRangingConstants(rangingConstants);\n\t\texporter.setNonRangingConstantValues(nonRangingConstantValues);\n\t\texporter.start();\n\t\troot.export(exporter);\n\t\texporter.end();\n\t\treturn exporter;\n\t}\n\t\n\t/**\n\t * Create string representation of the data for a partial evaluation\n\t * @param partial Values for a subset of the constants\n\t * @param pv Print the variables in each row?\n\t * @param sep String for separating values\n\t * @param eq String for separating values and result\n\t * @param header Add a header showing the constant names?\n\t */\n\tpublic String toStringPartial(Values partial, boolean pv, String sep, String eq, boolean header) throws PrismException\n\t{\n\t\tint i;\n\t\tString s = \"\", name;\n\t\tboolean first, noVars;\n\n\t\t// use an empty Values object if it is null\n\t\tif (partial == null)\n\t\t\tpartial = new Values();\n\t\t// if there are no variables, override eq separator\n\t\tnoVars = true;\n\t\tfor (i = 0; i < rangingConstants.size(); i++) {\n\t\t\tif (!partial.contains(rangingConstants.elementAt(i).getName())) {\n\t\t\t\tnoVars = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\tif (noVars)\n\t\t\teq = \"\";\n\t\t// create header\n\t\tif (header) {\n\t\t\tfirst = true;\n\t\t\tfor (i = 0; i < rangingConstants.size(); i++) {\n\t\t\t\tname = rangingConstants.elementAt(i).getName();\n\t\t\t\t// only print constants for which we haven't been given values\n\t\t\t\tif (!partial.contains(name)) {\n\t\t\t\t\tif (!first)\n\t\t\t\t\t\ts += sep;\n\t\t\t\t\ts += name;\n\t\t\t\t\tfirst = false;\n\t\t\t\t}\n\t\t\t}\n\t\t\ts += eq + \"Result\\n\";\n\t\t}\n\t\t// create table\n\t\ts += root.toStringPartial(partial, pv, sep, eq);\n\n\t\treturn s;\n\t}\n\n\t/**\n\t * Create string representation of the data as a 2D matrix\n\t * @param sep String for separating values\n\t */\n\tpublic String toStringMatrix(String sep)\n\t{\n\t\tString s = \"\";\n\n\t\t// create matrix\n\t\ts += root.toStringMatrix(sep);\n\n\t\treturn s;\n\t}\n\n\t// Data structure to store result collection (internal classes)\n\n\tprivate class TreeNode\n\t{\n\t\tprivate int level;\n\t\tprivate DefinedConstant constant;\n\t\tprivate TreeNode kids[];\n\n\t\t/**\n\t\t * Empty constructor\n\t\t * (required by subclass)\n\t\t */\n\t\tpublic TreeNode()\n\t\t{\n\t\t}\n\n\t\t/**\n\t\t * Actual constructor (recursive)\n\t\t */\n\t\tpublic TreeNode(int l)\n\t\t{\n\t\t\tint i, n;\n\n\t\t\t// store level and create children\n\t\t\tlevel = l;\n\t\t\tconstant = rangingConstants.get(level);\n\t\t\tn = constant.getNumSteps();\n\t\t\tkids = new TreeNode[n];\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tkids[i] = (level == rangingConstants.size() - 1) ? new TreeLeaf() : new TreeNode(l + 1);\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Sets the result for a particular set of values in the data structure.\n\t\t * If any constants are left undefined, the same result will be set for all values of each constant.\n\t\t * Returns the total number of values which were set for the the first time.\n\t\t */\n\t\tpublic int setResult(Values setThese, Object result)\n\t\t{\n\t\t\tObject val = null;\n\t\t\tint valIndex, ret, i, n;\n\n\t\t\t// if a value has been given for this node's constant, just store the result for this value\n\t\t\tif (setThese.contains(constant.getName())) {\n\t\t\t\t// get value of this node's constant\n\t\t\t\ttry {\n\t\t\t\t\tval = setThese.getValueOf(constant.getName());\n\t\t\t\t} catch (PrismLangException e) {\n\t\t\t\t\t// Ignore - already checked above\n\t\t\t\t}\n\t\t\t\t// and convert to index\n\t\t\t\tvalIndex = constant.getValueIndex(val);\n\t\t\t\t// store the value\n\t\t\t\treturn kids[valIndex].setResult(setThese, result);\n\t\t\t}\n\t\t\t// if not, iterate over all possible values for it and set them all\n\t\t\telse {\n\t\t\t\tn = constant.getNumSteps();\n\t\t\t\tret = 0;\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\tret += kids[i].setResult(setThese, result);\n\t\t\t\t}\n\t\t\t\treturn ret;\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Get a result from the data structure\n\t\t */\n\t\tpublic Object getResult(Values getThese) throws PrismException\n\t\t{\n\t\t\tObject val;\n\t\t\tint valIndex;\n\n\t\t\t// get value of this node's constant\n\t\t\tval = getThese.getValueOf(constant.getName());\n\t\t\t// and convert to index\n\t\t\tvalIndex = constant.getValueIndex(val);\n\t\t\t// return the value\n\t\t\treturn kids[valIndex].getResult(getThese);\n\t\t}\n\n\t\t/**\n\t\t * Create ArrayList representation of the data\n\t\t */\n\t\tpublic ArrayList<String[]> toArrayList()\n\t\t{\n\t\t\tArrayList<String[]> a = new ArrayList<String[]>();\n\t\t\tString line[] = new String[rangingConstants.size() + 1];\n\t\t\ttoArrayListRec(a, line);\n\t\t\treturn a;\n\t\t}\n\n\t\tpublic void toArrayListRec(ArrayList<String[]> a, String line[])\n\t\t{\n\t\t\tint i, n;\n\t\t\tn = constant.getNumSteps();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tline[level] = constant.getValue(i).toString();\n\t\t\t\tkids[i].toArrayListRec(a, line);\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Create string representation of the data\n\t\t */\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn toString(false, \",\", \",\");\n\t\t}\n\n\t\t/**\n\t\t * Create string representation of the data\n\t\t * @param pv Print the variables in each row?\n\t\t * @param sep String for separating values\n\t\t * @param eq String for separating values and result\n\t\t */\n\t\tpublic String toString(boolean pv, String sep, String eq)\n\t\t{\n\t\t\tString ret = toStringRec(pv, sep, eq, \"\");\n\t\t\t// Strip off last \\n before returning\n\t\t\tif (ret.charAt(ret.length() - 1) == '\\n')\n\t\t\t\tret = ret.substring(0, ret.length() - 1);\n\t\t\treturn ret;\n\t\t}\n\n\t\t/**\n\t\t * Pass the results to a ResultsExporter.\n\t\t */\n\t\tpublic void export(ResultsExporter export)\n\t\t{\n\t\t\texportRec(new Values(), export);\n\t\t}\n\n\t\tpublic String toStringRec(boolean pv, String sep, String eq, String head)\n\t\t{\n\t\t\tint i, n;\n\t\t\tString res, s;\n\n\t\t\tres = \"\";\n\t\t\tn = constant.getNumSteps();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\ts = \"\";\n\t\t\t\tif (level > 0)\n\t\t\t\t\ts += sep;\n\t\t\t\tif (pv)\n\t\t\t\t\ts += constant.getName() + \"=\";\n\t\t\t\ts += constant.getValue(i);\n\t\t\t\tres += kids[i].toStringRec(pv, sep, eq, head + s);\n\t\t\t}\n\n\t\t\treturn res;\n\t\t}\n\n\t\tpublic void exportRec(Values values, ResultsExporter export)\n\t\t{\n\t\t\tint n = constant.getNumSteps();\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tvalues.setValue(constant.getName(), constant.getValue(i));\n\t\t\t\tkids[i].exportRec(values, export);\n\t\t\t}\n\t\t}\n\t\t\n\t\t/**\n\t\t * Create string representation of the data for a partial evaluation\n\t\t * @param partial Values for a subset of the constants\n\t\t * @param pv Print the variables in each row?\n\t\t * @param sep String for separating values\n\t\t * @param eq String for separating values and result\n\t\t */\n\t\tpublic String toStringPartial(Values partial, boolean pv, String sep, String eq) throws PrismException\n\t\t{\n\t\t\treturn toStringPartialRec(partial, true, pv, sep, eq, \"\");\n\t\t}\n\n\t\tpublic String toStringPartialRec(Values partial, boolean first, boolean pv, String sep, String eq, String head) throws PrismException\n\t\t{\n\t\t\tint i, n, valIndex;\n\t\t\tString res, s;\n\t\t\tObject val;\n\n\t\t\tres = \"\";\n\t\t\t// if a value has been given for this node's constant, use it\n\t\t\tif (partial.contains(constant.getName())) {\n\t\t\t\t// get value of this node's constant\n\t\t\t\tval = partial.getValueOf(constant.getName());\n\t\t\t\t// and convert to index\n\t\t\t\tvalIndex = constant.getValueIndex(val);\n\t\t\t\t// return the value\n\t\t\t\tres += kids[valIndex].toStringPartialRec(partial, first, pv, sep, eq, head);\n\t\t\t}\n\t\t\t// if not, iterate over all possible values for it\n\t\t\telse {\n\t\t\t\tn = constant.getNumSteps();\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\ts = \"\";\n\t\t\t\t\tif (!first)\n\t\t\t\t\t\ts += sep;\n\t\t\t\t\tif (pv)\n\t\t\t\t\t\ts += constant.getName() + \"=\";\n\t\t\t\t\ts += constant.getValue(i);\n\t\t\t\t\tres += kids[i].toStringPartialRec(partial, false, pv, sep, eq, head + s);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\treturn res;\n\t\t}\n\n\t\t/**\n\t\t * Create string representation of the data as one or more 2D matrices\n\t\t * @param sep String for separating values\n\t\t */\n\t\tpublic String toStringMatrix(String sep)\n\t\t{\n\t\t\treturn toStringMatrixRec(sep, \"\");\n\t\t}\n\n\t\tpublic String toStringMatrixRec(String sep, String head)\n\t\t{\n\t\t\tint i, n;\n\t\t\tString res;\n\n\t\t\tres = \"\";\n\t\t\tn = constant.getNumSteps();\n\t\t\t\n\t\t\t// Print constants/indices for matrix\n\t\t\t// NB: need to enclose in quotes for CSV\n\t\t\tif (rangingConstants.size() == 1 || rangingConstants.size() - level == 2) {\n\t\t\t\tif (sep.equals(\",\"))\n\t\t\t\t\tres += \"\\\"\";\n\t\t\t\tif (rangingConstants.size() > 2)\n\t\t\t\t\tres += head+\", \";\n\t\t\t\tif (rangingConstants.size() == 1)\n\t\t\t\t\tres += constant.getName();\n\t\t\t\telse\n\t\t\t\t\tres += constant.getName() + \"\\\\\" + kids[0].constant.getName();\n\t\t\t\tif (!sep.equals(\",\"))\n\t\t\t\t\tres += \":\";\n\t\t\t\tif (sep.equals(\",\"))\n\t\t\t\t\tres += \"\\\"\";\n\t\t\t\tres += \"\\n\";\n\t\t\t}\n\t\t\t// Print top row of values\n\t\t\tif (rangingConstants.size() == 1 || rangingConstants.size() - level == 2) {\n\t\t\t\tTreeNode node = rangingConstants.size() == 1 ? this : kids[0];\n\t\t\t\tint nSteps = node.constant.getNumSteps();\n\t\t\t\tfor (i = 0; i < nSteps; i++) {\n\t\t\t\t\tif (rangingConstants.size() > 1 || i > 0)\n\t\t\t\t\t\tres += sep;\n\t\t\t\t\tres += node.constant.getValue(i);\n\t\t\t\t}\n\t\t\t\tres += \"\\n\";\n\t\t\t}\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t// Print first item of row: value\n\t\t\t\tif (rangingConstants.size() - level == 2)\n\t\t\t\t\tres += constant.getValue(i) + sep;\n\t\t\t\t// Print separator between row elements \n\t\t\t\tif (rangingConstants.size() - level == 1 && i > 0)\n\t\t\t\t\tres += sep;\n\t\t\t\t// Recurse\n\t\t\t\tif (rangingConstants.size() - level <= 2) {\n\t\t\t\t\tres += kids[i].toStringMatrixRec(sep, head);\n\t\t\t\t} else {\n\t\t\t\t\tString headNew = head;\n\t\t\t\t\tif (!(\"\".equals(head)))\n\t\t\t\t\t\theadNew += \",\";\n\t\t\t\t\theadNew += constant.getName() + \"=\" + constant.getValue(i);\n\t\t\t\t\tres += kids[i].toStringMatrixRec(sep, headNew);\n\t\t\t\t}\n\t\t\t\t// Print new line after row (except last one)\n\t\t\t\tif ((rangingConstants.size() - level == 2) && i < n - 1)\n\t\t\t\t\tres += \"\\n\";\n\t\t\t\t// Print gaps between matrices (except last one)\n\t\t\t\tif ((rangingConstants.size() - level > 2) && i < n - 1)\n\t\t\t\t\tres += \"\\n\\n\";\n\t\t\t}\n\n\t\t\treturn res;\n\t\t}\n\t}\n\n\tprivate class TreeLeaf extends TreeNode\n\t{\n\t\tprivate Object val = null;\n\n\t\tpublic int setResult(Values setThese, Object result)\n\t\t{\n\t\t\tint ret = (val == null) ? 1 : 0;\n\t\t\tval = result;\n\t\t\treturn ret;\n\t\t}\n\n\t\tpublic Object getResult(Values getThese) throws PrismException\n\t\t{\n\t\t\treturn val;\n\t\t}\n\n\t\tpublic String toStringMatrixRec(String sep, String head)\n\t\t{\n\t\t\treturn Values.valToString(val);\n\t\t}\n\n\t\tpublic String toStringRec(boolean pv, String sep, String eq, String head)\n\t\t{\n\t\t\treturn head + eq + val + \"\\n\";\n\t\t}\n\n\t\tpublic void exportRec(Values values, ResultsExporter export)\n\t\t{\n\t\t\texport.exportResult(values, val);\n\t\t}\n\t\t\n\t\tpublic String toStringPartialRec(Values partial, boolean first, boolean pv, String sep, String eq, String head)\n\t\t{\n\t\t\treturn head + eq + val + \"\\n\";\n\t\t}\n\n\t\tpublic void toArrayListRec(ArrayList<String[]> a, String line[])\n\t\t{\n\t\t\tline[rangingConstants.size()] = \"\" + val;\n\t\t\ta.add(line.clone());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ResultsExporter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.PrintWriter;\nimport java.util.ArrayList;\nimport java.util.Collection;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.LinkedHashSet;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\n\nimport parser.Values;\nimport parser.ast.Property;\n\n/**\n * Class to export the results of model checking in various shapes and formats.\n */\npublic abstract class ResultsExporter\n{\n\t/**\n\t * Legal combinations of export shapes and formats.\n\t * A shape defines how the data is arranged, e.g., as list or matrix.\n\t * Most shapes can be written to an output in different formats, e.g., as plain text or CSV.\n\t * Some shapes have an implicit format, e.g., comments.\n\t */\n\tpublic enum ResultsExportShape\n\t{\n\t\tLIST_PLAIN (\"list (plain text)\", false, false) {\n\t\t\tpublic ResultsExporter getExporter() {\n\t\t\t\treturn new ResultsExporterList(ExportFormat.PLAIN);\n\t\t\t}\n\t\t},\n\t\tLIST_CSV(\"list (CSV)\", false, true) {\n\t\t\tpublic ResultsExporter getExporter() {\n\t\t\t\treturn new ResultsExporterList(ExportFormat.CSV);\n\t\t\t}\n\t\t},\n\t\tMATRIX_PLAIN(\"matrix (plain text)\", true, false) {\n\t\t\tpublic ResultsExporter getExporter() {\n\t\t\t\treturn new ResultsExporterMatrix(ExportFormat.PLAIN);\n\t\t\t}\n\t\t},\n\t\tMATRIX_CSV(\"matrix (CSV)\", true, true) {\n\t\t\tpublic ResultsExporter getExporter() {\n\t\t\t\treturn new ResultsExporterMatrix(ExportFormat.CSV);\n\t\t\t}\n\t\t},\n\t\tDATA_FRAME(\"data frame (CSV)\", true, true) {\n\t\t\tpublic ResultsExporter getExporter() {\n\t\t\t\treturn new ResultsExporterDataFrame();\n\t\t\t}\n\t\t},\n\t\tCOMMENT(\"comment\", false, false) {\n\t\t\tpublic ResultsExporter getExporter() {\n\t\t\t\treturn new ResultsExporterComment();\n\t\t\t}\n\t\t};\n\n\t\tpublic final String fullName;\n\t\tpublic final boolean isMatrix;\n\t\tpublic final boolean isCSV;\n\n\t\tResultsExportShape(String fullName, boolean isMatrix, boolean isCSV)\n\t\t{\n\t\t\tthis.fullName = fullName;\n\t\t\tthis.isMatrix = isMatrix;\n\t\t\tthis.isCSV = isCSV;\n\t\t}\n\n\t\tpublic abstract ResultsExporter getExporter();\n\t}\n\n\t/**\n\t * An export format defines how data is written to an output.\n\t */\n\tpublic enum ExportFormat {\n\t\tPLAIN(\"\\t\")\n\t\t{\n\t\t\tpublic String quote(String s)\n\t\t\t{\n\t\t\t\t// Nothing to quote\n\t\t\t\treturn s;\n\t\t\t}\n\n\t\t\tpublic String printHeader(String s)\n\t\t\t{\n\t\t\t\treturn s + \":\";\n\t\t\t}\n\t\t},\n\t\tCSV(\",\")\n\t\t{\n\t\t\tpublic String quote(String s)\n\t\t\t{\n\t\t\t\t// Quote and escape double quotes (\").\n\t\t\t\treturn \"\\\"\" + s.replaceAll(\"\\\"\", \"\\\"\\\"\") + \"\\\"\";\n\t\t\t}\n\n\t\t\tpublic String printHeader(String s)\n\t\t\t{\n\t\t\t\treturn quote(s);\n\t\t\t}\n\t\t};\n\t\n\t\tpublic final String separator;\n\t\n\t\tExportFormat(String separator)\n\t\t{\n\t\t\tthis.separator = separator;\n\t\t}\n\t\n\t\tpublic abstract String quote(String s);\n\n\t\tpublic abstract String printHeader(String s);\n\t}\n\n\t@SuppressWarnings(\"rawtypes\")\n\tprotected List<DefinedConstant> rangingConstants;\n\tprotected Values nonRangingConstantValues;\n\tprotected PrintWriter target;\n\tprotected Property property;\n\tprotected boolean printProperty;\n\n\t// Methods to create and set up a ResultsExporter  \n\n\tpublic void setRangingConstants(@SuppressWarnings(\"rawtypes\") final List<DefinedConstant> rangingConstants)\n\t{\n\t\tthis.rangingConstants = rangingConstants;\n\t}\n\n\tpublic void setNonRangingConstantValues(final Values nonRangingConstantValues)\n\t{\n\t\tthis.nonRangingConstantValues = nonRangingConstantValues;\n\t}\n\n\t/**\n\t * Print multiple results to a text-output stream.\n\t * Results and properties are associated by their list indices.\n\t *  \n\t * @param results list of results to print\n\t * @param properties list of properties associated with the results\n\t * @param out target text-output stream\n\t */\n\tpublic void printResults(List<ResultsCollection> results, List<Property> properties, PrintWriter out)\n\t{\n\t\tint n = results.size();\n\t\t// print property before results\n\t\tprintProperty = n > 1;\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tproperty = properties.get(i);\n\t\t\tif (i > 0) {\n\t\t\t\tprintCollectionSeparator(out);\n\t\t\t}\n\t\t\texportResultsCollection(results.get(i), out);\n\t\t}\n\t\tout.flush();\n\t}\n\n\t/**\n\t * Print a separator between subsequent results collections\n\t * @param out\n\t */\n\tprotected void printCollectionSeparator(PrintWriter out)\n\t{\n\t\t// print separator\n\t\tout.println();\n\t}\n\n\tprotected abstract void printPropertyHeading();\n\n\t// Main interface for the actual export:\n\n\tpublic void exportResultsCollection(ResultsCollection collection, PrintWriter out)\n\t{\n\t\ttarget = out;\n\t\tcollection.export(this);\n\t\ttarget = null;\n\t}\n\n\t// methods to be called by the class that has the results\n\n\t/**\n\t * Start the export process.\n\t */\n\tpublic void start()\n\t{\n\t\t// Prepend property, if requested\n\t\tif (printProperty) {\n\t\t\tprintPropertyHeading();\n\t\t}\n\t}\n\n\t/**\n\t * Export a single result.\n\t */\n\tpublic abstract void exportResult(final Values values, final Object result);\n\n\t/**\n\t * Finish the export process.\n\t */\n\tpublic void end()\n\t{\n\t\t// None\n\t}\n\n\n\t/**\n\t * An exporter that arranges the results in a list.\n\t */\n\tpublic static class ResultsExporterList extends ResultsExporter\n\t{\n\t\tExportFormat style;\n\n\t\tpublic ResultsExporterList(ExportFormat style)\n\t\t{\n\t\t\tthis.style = style;\n\t\t}\n\n\t\t@Override\n\t\tprotected void printPropertyHeading()\n\t\t{\n\t\t\tif (property != null) {\n\t\t\t\ttarget.println(style.printHeader(property.toString()));\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic void start()\n\t\t{\n\t\t\tsuper.start();\n\t\t\t// Print table header, if needed\n\t\t\tif (rangingConstants != null) {\n\t\t\t\tfor (int i = 0; i < rangingConstants.size(); i++) {\n\t\t\t\t\tif (i > 0) {\n\t\t\t\t\t\ttarget.print(style.separator);\n\t\t\t\t\t}\n\t\t\t\t\ttarget.print(rangingConstants.get(i).getName());\n\t\t\t\t}\n\t\t\t\tif (rangingConstants.size() > 0) {\n\t\t\t\t\ttarget.print(style.separator);\n\t\t\t\t}\n\t\t\t\ttarget.println(\"Result\");\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic void exportResult(final Values values, final Object result)\n\t\t{\n\t\t\ttarget.print(values.toString(false, style.separator));\n\t\t\tif (values.getNumValues() > 0) {\n\t\t\t\ttarget.print(style.separator);\n\t\t\t}\n\t\t\ttarget.println(Values.valToString(result));\n\t\t}\n\t}\n\n\n\n\t/**\n\t * An exporter that arranges the results in a data frame.\n\t */\n\tpublic static class ResultsExporterDataFrame extends ResultsExporter\n\t{\n\t\tpublic static final String PROPERTY_COLUMN = \"Property\";\n\t\tpublic static final String RESULT_COLUMN = \"Result\";\n\n\t\tboolean multipleResultCollections = true;\n\t\tString propertyColumn = PROPERTY_COLUMN;\n\t\tString resultColumn = RESULT_COLUMN;\n\t\tSet<String>columns = new LinkedHashSet<>();\n\t\tMap<String, Integer> columnIndices = new HashMap<>();\n\n\n\t\t@Override\n\t\tpublic void printResults(List<ResultsCollection> results, List<Property> properties, PrintWriter out)\n\t\t{\n\t\t\tmultipleResultCollections = true;\n\t\t\tinitializeColumns(results);\n\t\t\tprintHeader(out);\n\t\t\tsuper.printResults(results, disambiguatePropertyNames(properties), out);\n\t\t\tresetColumns();\n\t\t\tmultipleResultCollections = false;\n\t\t}\n\n\t\t/**\n\t\t * Generate columns from the defined constants of all results collections.\n\t\t * \n\t\t * @param results the list of results collections to be included\n\t\t */\n\t\tprotected void initializeColumns(List<ResultsCollection> results)\n\t\t{\n\t\t\tresetColumns();\n\t\t\tSet<String> resultNames = new HashSet<>();\n\t\t\tfor (ResultsCollection col : results) {\n\t\t\t\t@SuppressWarnings(\"rawtypes\")\n\t\t\t\tList<DefinedConstant> constants = col.getRangingConstants();\n\t\t\t\taddConstantsToColumns(constants);\n\t\t\t\tresultNames.add(col.getResultName());\n\t\t\t}\n\t\t\tpropertyColumn = disambiguateName(PROPERTY_COLUMN, columns);\n\t\t\tresultColumn = disambiguateName((resultNames.size() == 1) ? resultNames.iterator().next() : RESULT_COLUMN, columns);\n\t\t}\n\n\t\t/**\n\t\t * If {@code names} contains {@code name}, append \"_(number)\" to make name unique.\n\t\t * @param name name to be made unique\n\t\t * @param names known names\n\t\t * @return unique name\n\t\t */\n\t\tprotected String disambiguateName(String name, Collection<String> names)\n\t\t{\n\t\t\tString unique = name;\n\t\t\tint i = 1;\n\t\t\twhile (names.contains(unique)) {\n\t\t\t\tunique = name + \"_\" + i++;\n\t\t\t}\n\t\t\treturn unique;\n\t\t}\n\n\t\t/**\n\t\t * Forget all generated columns.\n\t\t */\n\t\tprotected void resetColumns()\n\t\t{\n\t\t\tcolumns.clear();\n\t\t\tpropertyColumn = PROPERTY_COLUMN;\n\t\t\tresultColumn = RESULT_COLUMN;\n\t\t}\n\n\t\t@SuppressWarnings(\"rawtypes\")\n\t\tprotected void addConstantsToColumns(List<DefinedConstant> constants)\n\t\t{\n\t\t\tfor (DefinedConstant con : constants) {\n\t\t\t\tString name = con.getName();\n\t\t\t\tif (!columns.contains(name)) {\n\t\t\t\t\tcolumns.add(name);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Print the header:<br>\n\t\t * Property,Constant_1,...,Constant_n,Result\n\t\t * \n\t\t * @param out the writer to print the header\n\t\t */\n\t\tprotected void printHeader(PrintWriter out)\n\t\t{\n\t\t\tout.print(\"Property\");\n\t\t\tout.print(ExportFormat.CSV.separator);\n\t\t\tfor (String col : columns) {\n\t\t\t\tout.print(col);\n\t\t\t\tout.print(ExportFormat.CSV.separator);\n\t\t\t}\n\t\t\tout.println(resultColumn);\n\t\t}\n\n\t\t/**\n\t\t * First, copy each property and name properties with no name \"Property_(number)\".\n\t\t * Second, make property names unique by appending \"_(number)\" if necessary.\n\t\t * \n\t\t * @param properties\n\t\t * @return list of new properties with distinct names\n\t\t */\n\t\tprotected List<Property> disambiguatePropertyNames(List<Property> properties)\n\t\t{\n\t\t\tList<Property> namedProperties = new ArrayList<>(properties.size());\n\t\t\tMap<String, Integer> nameCounts = new HashMap<>();\n\t\t\t// 1. Ensure each property is given a name and count names\n\t\t\tfor (int i=0, size=properties.size(); i<size; i++) {\n\t\t\t\tProperty property = (Property) properties.get(i).deepCopy();\n\t\t\t\tString name = property.getName();\n\t\t\t\tif (name == null || name.isEmpty()) {\n\t\t\t\t\t// Create copy with new name\n\t\t\t\t\tname = \"Property_\" + (i+1);\n\t\t\t\t\tproperty.setName(name);\n\t\t\t\t}\n\t\t\t\tnamedProperties.add(property);\n\t\t\t\t// Count occurrences of name\n\t\t\t\tint count = nameCounts.getOrDefault(name, 0);\n\t\t\t\tnameCounts.put(name, count + 1);\n\t\t\t}\n\t\t\t// 2. Make names unique by appending \"_<number>\"\n\t\t\tfor (Property property: namedProperties) {\n\t\t\t\tString name = property.getName();\n\t\t\t\tint occurrences = nameCounts.get(name);\n\t\t\t\tif (occurrences > 1) {\n\t\t\t\t\tfor (int i=1; i<=occurrences; i++) {\n\t\t\t\t\t\tString newName = name + \"_\" + i;\n\t\t\t\t\t\tif(!nameCounts.containsKey(newName)) {\n\t\t\t\t\t\t\tproperty.setName(newName);\n\t\t\t\t\t\t\tnameCounts.put(newName, 1);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn namedProperties;\n\t\t}\n\n\t\t@Override\n\t\tprotected void printCollectionSeparator(PrintWriter out)\n\t\t{\n\t\t\t// None - results are not separated\n\t\t}\n\n\t\t@Override\n\t\tprotected void printPropertyHeading()\n\t\t{\n\t\t\t// None - property is printed as a field in each record\n\t\t}\n\n\t\t@Override\n\t\tpublic void start()\n\t\t{\n\t\t\tinitializeColumnIndices();\n\t\t\tif (! multipleResultCollections) {\n\t\t\t\t// Printing a single result collection: print table header\n\t\t\t\taddConstantsToColumns(rangingConstants);\n\t\t\t\tprintHeader(target);\n\t\t\t\tresetColumns();\n\t\t\t\t// Ensure property has a name\n\t\t\t\tString name = property.getName();\n\t\t\t\tif (name == null || name.isEmpty()) {\n\t\t\t\t\tproperty = (Property) property.deepCopy();\n\t\t\t\t\tproperty.setName(\"Property_1\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tsuper.start();\n\t\t}\n\n\t\t/**\n\t\t * Create a mapping from column name to its index in list of ranging constants.\n\t\t */\n\t\tprotected void initializeColumnIndices()\n\t\t{\n\t\t\tcolumnIndices.clear();\n\t\t\tint size=rangingConstants.size();\n\t\t\tfor (int i=0; i<size; i++) {\n\t\t\t\tcolumnIndices.put(rangingConstants.get(i).getName(), i);\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic void exportResult(Values values, Object result)\n\t\t{\n\t\t\t// Don't quote as property names contain neither commas nor double quotes\n\t\t\ttarget.print(property.getName().toString());\n\t\t\ttarget.print(ExportFormat.CSV.separator);\n\t\t\tfor (String col : columns) {\n\t\t\t\tif (columnIndices.containsKey(col)) {\n\t\t\t\t\tObject value = values.getValue(columnIndices.get(col));\n\t\t\t\t\ttarget.print(Values.valToString(value));\n\t\t\t\t} \n\t\t\t\ttarget.print(ExportFormat.CSV.separator);\n\t\t\t}\n\t\t\ttarget.println(Values.valToString(result));\n\t\t}\n\t}\n\n\n\n\t/**\n\t * An exporter that arranges the results in a matrix.\n\t */\n\tpublic static class ResultsExporterMatrix extends ResultsExporter\n\t{\n\t\tExportFormat style;\n\n\t\tpublic ResultsExporterMatrix(ExportFormat style)\n\t\t{\n\t\t\tthis.style = style;\n\t\t}\n\n\t\t@Override\n\t\tprotected void printPropertyHeading()\n\t\t{\n\t\t\tif (property != null) {\n\t\t\t\ttarget.println(style.printHeader(property.toString()));\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic void exportResultsCollection(ResultsCollection collection, PrintWriter out)\n\t\t{\n\t\t\tthis.target = out;\n\t\t\tstart();\n\t\t\ttarget.println(collection.toStringMatrix(style.separator));\n\t\t\tend();\n\t\t}\n\n\t\t@Override\n\t\tpublic void exportResult(final Values values, final Object result)\n\t\t{\n\t\t\t// Dummy method, we rely on legacy code for matrix export\n\t\t}\n\t}\n\n\n\n\t/**\n\t * An exporter that arranges the results in a comment.\n\t */\n\tpublic static class ResultsExporterComment extends ResultsExporter\n\t{\n\t\t@Override\n\t\tprotected void printPropertyHeading()\n\t\t{\n\t\t\t// None - property is printed at the the end for comment shape\n\t\t}\n\n\t\t@Override\n\t\tpublic void exportResult(final Values values, final Object result)\n\t\t{\n\t\t\tValues mergedValues = new Values(nonRangingConstantValues, values);\n\t\t\ttarget.print(\"// RESULT\");\n\t\t\tif (mergedValues.getNumValues() > 0) {\n\t\t\t\ttarget.print(\" (\");\n\t\t\t\ttarget.print(mergedValues.toString(true, \",\"));\n\t\t\t\ttarget.print(\")\");\n\t\t\t}\n\t\t\ttarget.print(\": \");\n\t\t\ttarget.println(Values.valToString(result));\n\t\t}\n\n\t\t@Override\n\t\tpublic void end()\n\t\t{\n\t\t\t// For \"comment\" shape, print the property at the end, if requested\n\t\t\tif (printProperty) {\n\t\t\t\ttarget.println(property.toString());\n\t\t\t}\n\t\t\tsuper.end();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ResultsImporter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.ByteArrayInputStream;\nimport java.io.IOException;\nimport java.io.Reader;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashSet;\nimport java.util.Iterator;\nimport java.util.LinkedHashMap;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.PrimitiveIterator.OfInt;\nimport java.util.Set;\nimport java.util.Vector;\n\nimport common.IterableBitSet;\nimport csv.BasicReader;\nimport csv.CsvFormatException;\nimport csv.CsvReader;\nimport param.BigRational;\nimport parser.ParseException;\nimport parser.PrismParser;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.Property;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport prism.DefinedConstant.DefinedDomain;\nimport prism.ResultsImporter.RawResultsCollection;\n\nimport static csv.BasicReader.CR;\nimport static csv.BasicReader.LF;\n\n/**\n * A class to import Prism results collections from a data frame in CSV format.\n * <ul>\n * <li>The header either contains a field \"Property\" or the first column is considered to contain the property name\n * <li>The header either contains a field \"Result\" or the last column is considered to contain the results\n * <li>The other fields are names of ranging constants and must Prism identifiers\n * <li>A result collection is formed by all records with the same property field value\n * <li>The fields of the property column must be Prism Identifiers\n * <li>The result column may contain either {@link Boolean} values or numeric values, i.e., {@link Integer}, {@link Double} or {@link BigRational}\n * <li>The columns for ranging constants may contain numeric values only\n * </ul>\n */\npublic class ResultsImporter implements Iterable<Pair<Property, RawResultsCollection>>\n{\n\tprivate static final int COMMA = CsvReader.COMMA;\n\n\tfinal Header header;\n\tfinal Map<String, RawResultsCollection> rawResults;\n\n\t/**\n\t * Import the results from a reader on a source for comma-separated values.\n\t * Use a {@link BufferedReader} for performant access to external sources such as files.\n\t * \n\t * @param input the reader on CSV input\n\t * @throws IOException If an I/O error occurs\n\t * @throws PrismLangException If the content of the CSV input does not conform to the supported data frame format\n\t * @throws CsvFormatException If the CSV input has a syntax error\n\t */\n\tpublic ResultsImporter(Reader input) throws PrismLangException, IOException, CsvFormatException\n\t{\n\t\t// Convert all line endings to LF for compatibility\n\t\ttry (BasicReader reader = BasicReader.wrap(input).normalizeLineEndings();\n\t\t\t\tCsvReader csv = new CsvReader(reader, COMMA, LF)) {\n\t\t\theader = new Header(csv.getHeader());\n\t\t\trawResults = new LinkedHashMap<>();\n\t\t\twhile (csv.hasNextRecord()) {\n\t\t\t\t// 1. Parse record\n\t\t\t\tString[] record = csv.nextRecord();\n\t\t\t\tRawResult result = new RawResult(record, header, csv.getLine());\n\t\t\t\tString propertyName = result.propertyName;\n\t\t\t\t// 2. Add to raw results\n\t\t\t\tif (rawResults.containsKey(result.propertyName)) {\n\t\t\t\t\trawResults.get(result.propertyName).add(result);\n\t\t\t\t} else {\n\t\t\t\t\trawResults.put(propertyName, new RawResultsCollection(header, result));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Create an iterator over properties and their associated intermediate results collections.\n\t * \n\t *@return The iterator over pairs {@code (property, results)}\n\t */\n\tpublic Iterator<Pair<Property, RawResultsCollection>> iterator()\n\t{\n\t\treturn new Iterator<Pair<Property, RawResultsCollection>>()\n\t\t{\n\t\t\tIterator<RawResultsCollection> collections = rawResults.values().iterator();\n\n\t\t\t@Override\n\t\t\tpublic boolean hasNext()\n\t\t\t{\n\t\t\t\treturn collections.hasNext();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic Pair<Property, RawResultsCollection> next()\n\t\t\t{\n\t\t\t\tRawResultsCollection collection = collections.next();\n\t\t\t\tString propertyName = collection.getPropertyName();\n\t\t\t\tExpression dummy;\n\t\t\t\tswitch (collection.getResultType()) {\n\t\t\t\tcase Boolean:\n\t\t\t\t\tdummy = new ExpressionConstant(propertyName, TypeBool.getInstance());\n\t\t\t\t\tbreak;\n\t\t\t\tcase Integer:\n\t\t\t\t\tdummy = new ExpressionConstant(propertyName, TypeInt.getInstance());\n\t\t\t\t\tbreak;\n\t\t\t\tcase Double:\n\t\t\t\tcase BigRational:\n\t\t\t\t\tdummy = new ExpressionConstant(propertyName, TypeDouble.getInstance());\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\t// It is a program error if this branch is taken. Types have to be checked before.\n\t\t\t\t\tthrow new RuntimeException(\"Result type not supported: \" + collection.getResultType());\n\t\t\t\t}\n\t\t\t\tProperty property = new Property(dummy, propertyName);\n\t\t\t\treturn new Pair<>(property, collection);\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Parse a string as Prism identifier.\n\t * \n\t * @param string the string to be parsed\n\t * @return The argument if it is a Prism identifier\n\t * @throws PrismLangException If the argument is not a Prism identifier\n\t */\n\tprotected static String parseIdentifier(String string) throws PrismLangException\n\t{\n\t\tByteArrayInputStream stream = new ByteArrayInputStream(string.getBytes());\n\t\ttry {\n\t\t\t// obtain exclusive access to the prism parser\n\t\t\t// (don't forget to release it afterwards)\n\t\t\tPrism.getPrismParser();\n\t\t\ttry {\n\t\t\t\t// (Re)start parser\n\t\t\t\tPrismParser.ReInit(stream);\n\t\t\t\t// Parse\n\t\t\t\tboolean success = true;\n\t\t\t\ttry {\n\t\t\t\t\tsuccess = string.equals(PrismParser.Identifier());\n\t\t\t\t} catch (ParseException e) {\n\t\t\t\t\tsuccess = false;\n\t\t\t\t}\n\t\t\t\tif (! success) {\n\t\t\t\t\tthrow new PrismLangException(\"Expected identifier but got: \" + string);\n\t\t\t\t}\n\t\t\t} finally {\n\t\t\t\t// release prism parser\n\t\t\t\tPrism.releasePrismParser();\n\t\t\t}\n\t\t} catch (InterruptedException ie) {\n\t\t\tthrow new PrismLangException(\"Concurrency error in parser\");\n\t\t}\n\t\treturn string;\n\t}\n\n\t/**\n\t * Parse a string as Java data type {@link Boolean}, {@link Integer}, {@link Double} or {@link BigRational}.\n\t * The special values {@code NaN}, {@code +Infinity} and {@code -Infinity} are parsed as Double.\n\t * \n\t * @param string the string to be parsed\n\t * @return A value corresponding to the argument or the argument itself if it represents no supported type\n\t */\n\tprotected static Object parseValue(String string)\n\t{\n\t\t// Boolean\n\t\tif (\"true\".equals(string)) {\n\t\t\treturn true;\n\t\t}\n\t\tif (\"false\".equals(string)) {\n\t\t\treturn false;\n\t\t}\n\t\t// Integer\n\t\ttry {\n\t\t\treturn Integer.parseInt(string);\n\t\t} catch (NumberFormatException e) {}\n\t\t// Double\n\t\ttry {\n\t\t\treturn Double.parseDouble(string);\n\t\t} catch (NumberFormatException e) {}\n\t\t// BigRational\n\t\ttry {\n\t\t\treturn new BigRational(string);\n\t\t} catch (NumberFormatException e) {}\n\t\treturn string;\n\t}\n\n\n\n\t/**\n\t * Enumeration to support type inference.\n\t */\n\tpublic enum TypeInfo\n\t{\n\t\tNil {\n\t\t\t@Override\n\t\t\tpublic Object convert(Object value)\n\t\t\t{\n\t\t\t\tif (value == null) {\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Nil type\");\n\t\t\t}\n\t\n\t\t\t@Override\n\t\t\tpublic TypeInfo infer(Object value)\n\t\t\t{\n\t\t\t\tif (value == null) {\n\t\t\t\t\treturn this;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected null but got: \" + value.getClass());\n\t\t\t}\n\t\t},\n\t\tString {\n\t\t\t@Override\n\t\t\tpublic String convert(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof String) {\n\t\t\t\t\treturn (String) value;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected String but got: \" + value.getClass());\n\t\t\t}\n\t\n\t\t\t@Override\n\t\t\tpublic TypeInfo infer(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof String) {\n\t\t\t\t\treturn this;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected String but got: \" + value.getClass());\n\t\t\t}\n\t\t},\n\t\tBoolean {\n\t\t\t@Override\n\t\t\tpublic Boolean convert(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof Boolean) {\n\t\t\t\t\treturn (Boolean) value;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected Boolean but got: \" + value.getClass());\n\t\t\t}\n\t\n\t\t\t@Override\n\t\t\tpublic TypeInfo infer(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof Boolean) {\n\t\t\t\t\treturn this;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected Boolean but got: \" + value.getClass());\n\t\t\t}\n\t\t},\n\t\tInteger {\n\t\t\t@Override\n\t\t\tpublic Integer convert(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof Integer) {\n\t\t\t\t\treturn (Integer) value;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected Integer but got: \" + value.getClass());\n\t\t\t}\n\t\n\t\t\t@Override\n\t\t\tpublic TypeInfo infer(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof Integer) {\n\t\t\t\t\treturn Integer;\n\t\t\t\t}\n\t\t\t\tif (value instanceof Double) {\n\t\t\t\t\treturn Double;\n\t\t\t\t}\n\t\t\t\tif (value instanceof BigRational) {\n\t\t\t\t\treturn BigRational;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected Integer, Double or BigRational but got: \" + value.getClass());\n\t\t\t}\n\t\t},\n\t\tDouble {\n\t\t\t@Override\n\t\t\tpublic Double convert(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof Double) {\n\t\t\t\t\treturn (Double) value;\n\t\t\t\t}\n\t\t\t\tif (value instanceof Integer) {\n\t\t\t\t\treturn ((Integer) value).doubleValue();\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected Integer but got: \" + value.getClass());\n\t\t\t}\n\t\n\t\t\t@Override\n\t\t\tpublic TypeInfo infer(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof Double || value instanceof Integer) {\n\t\t\t\t\treturn Double;\n\t\t\t\t}\n\t\t\t\tif (value instanceof BigRational) {\n\t\t\t\t\treturn BigRational;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected Double or BigRational but got: \" + value.getClass());\n\t\t\t}\n\t\t},\n\t\tBigRational {\n\t\t\t@Override\n\t\t\tpublic BigRational convert(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof BigRational) {\n\t\t\t\t\treturn (BigRational) value;\n\t\t\t\t}\n\t\t\t\tif (value instanceof Double) {\n\t\t\t\t\treturn param.BigRational.from(value);\n\t\t\t\t}\n\t\t\t\tif (value instanceof Integer) {\n\t\t\t\t\treturn new BigRational((Integer) value);\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected Integer but got: \" + value.getClass());\n\t\t\t}\n\t\n\t\t\t@Override\n\t\t\tpublic TypeInfo infer(Object value)\n\t\t\t{\n\t\t\t\tif (value instanceof BigRational || value instanceof Double || value instanceof Integer) {\n\t\t\t\t\treturn BigRational;\n\t\t\t\t}\n\t\t\t\tthrow new IllegalArgumentException(\"Expected BigRational but got: \" + value.getClass());\n\t\t\t}\n\t\t};\n\t\n\t\t/**\n\t\t * Convert an object into the receivers type.\n\t\t * \n\t\t * @param value the object to convert\n\t\t * @return the converted object\n\t\t * @throws IllegalArgumentException If the object's type is incompatible\n\t\t */\n\t\tpublic abstract Object convert(Object value);\n\t\n\t\t/**\n\t\t * Infer a super type of receiver that is compatible with an object.\n\t\t * \n\t\t * @param value the object to infer the common type from\n\t\t * @return The common type\n\t\t * @throws IllegalArgumentException If the object's type is incompatible\n\t\t */\n\t\tpublic abstract TypeInfo infer(Object value);\n\t\n\t\t/**\n\t\t * Get the type info from an object\n\t\t * \n\t\t * @param value the object\n\t\t * @return the type info of the object\n\t\t * @throws IllegalArgumentException If the object's type is not supported\n\t\t */\n\t\tpublic static TypeInfo from(Object value)\n\t\t{\n\t\t\tif (value == null) {\n\t\t\t\treturn Nil;\n\t\t\t}\n\t\t\tif (value instanceof String) {\n\t\t\t\treturn String;\n\t\t\t}\n\t\t\tif (value instanceof Boolean) {\n\t\t\t\treturn Boolean;\n\t\t\t}\n\t\t\tif (value instanceof Integer) {\n\t\t\t\treturn Integer;\n\t\t\t}\n\t\t\tif (value instanceof Double) {\n\t\t\t\treturn Double;\n\t\t\t}\n\t\t\tif (value instanceof BigRational) {\n\t\t\t\treturn BigRational;\n\t\t\t}\n\t\t\tthrow new IllegalArgumentException(\"Unsupported type \" + value.getClass());\n\t\t}\n\t}\n\n\n\n\t/**\n\t * The header of a data frame containing result collections.\n\t */\n\tpublic static class Header\n\t{\n\t\tfinal int numColumns;\n\t\tfinal String resultName;\n\t\tfinal String[] constantNames;\n\t\tint propertyIndex = -1;\n\t\tint resultIndex = -1;\n\n\t\t/**\n\t\t * Create a header from an array of at least two header fields.\n\t\t * \n\t\t * @param fields the header fields containing the column names\n\t\t * @throws PrismLangException If the property or the result is not found or if the constant names are not Prism identifiers\n\t\t */\n\t\tpublic Header(String[] fields) throws PrismLangException\n\t\t{\n\t\t\tnumColumns = fields.length;\n\t\t\tsetPropertyAndResultIndex(fields);\n\t\t\tresultName = fields[resultIndex];\n\t\t\tconstantNames = parseConstantNames(fields);\n\t\t}\n\n\t\t/**\n\t\t * Find and set the index of the property and the result column.\n\t\t * If no field is named \"Property\", assume the first column is the property column.\n\t\t * If no field is named \"Result\", assume the last column is the result column.\n\t\t * If the column indices conflict, throw an exception.\n\t\t * \n\t\t * @param fields the header fields containing the column names\n\t\t * @throws PrismLangException If the property or the result column is not found\n\t\t */\n\t\tprotected void setPropertyAndResultIndex(String[] fields) throws PrismLangException\n\t\t{\n\t\t\t// Try to find Property and Result field\n\t\t\tfor (int i = 0, length = fields.length; i < length; i++) {\n\t\t\t\tswitch (fields[i]) {\n\t\t\t\tcase \"Property\":\n\t\t\t\t\tpropertyIndex = i;\n\t\t\t\t\tbreak;\n\t\t\t\tcase \"Result\":\n\t\t\t\t\tresultIndex = i;\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\t// Skip field\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (propertyIndex < 0) {\n\t\t\t\t// If no field \"Property\" was found, assume the first column contains the properties\n\t\t\t\tif (resultIndex == 0) {\n\t\t\t\t\tthrow new PrismLangException(\"Cannot find the property column (either \\\"Property\\\" or the first column)\");\n\t\t\t\t}\n\t\t\t\tpropertyIndex = 0;\n\t\t\t}\n\t\t\tif (resultIndex < 0) {\n\t\t\t\t// If no field \"Result\" was found, assume the last column contains the results\n\t\t\t\tif (propertyIndex == fields.length - 1) {\n\t\t\t\t\tthrow new PrismLangException(\"Cannot find the result column (either \\\"Result\\\" or the last column)\");\n\t\t\t\t}\n\t\t\t\tresultIndex = fields.length - 1;\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Parse the names of the constant columns as Prism identifiers.\n\t\t * \n\t\t * @param fields the header fields containing the column names\n\t\t * @return An array of constant names\n\t\t * @throws PrismLangException If a constant name is not a Prism identifier\n\t\t */\n\t\tprotected String[] parseConstantNames(String[] fields) throws PrismLangException\n\t\t{\n\t\t\tString[] constants = new String[fields.length - 2];\n\t\t\tfor (int i = 0, c = 0, length = fields.length; i < length; i++) {\n\t\t\t\tif (i != propertyIndex && i != resultIndex)\n\t\t\t\t\ttry {\n\t\t\t\t\t\tconstants[c++] = parseIdentifier(fields[i]);\n\t\t\t\t\t} catch (PrismLangException e) {\n\t\t\t\t\t\tthrow new PrismLangException(\"Header fields for constants must be identifiers but got: \" + fields[i] + \"(field \" + i +\")\");\n\t\t\t\t\t}\n\t\t\t}\n\t\t\treturn constants;\n\t\t}\n\t}\n\n\n\n\t/**\n\t * A result obtained from a record of a data frame containing result collections.\n\t */\n\tpublic static class RawResult\n\t{\n\t\tfinal String propertyName;\n\t\tfinal Object resultValue;\n\t\tfinal Object[] constantValues;\n\n\t\t/**\n\t\t * Create a result from a record and a the header of the data frame.\n\t\t * \n\t\t * @param record the record\n\t\t * @param header the header of the data frame\n\t\t * @param line the line number of the record for error messages\n\t\t * @throws PrismLangException If the record has too few fields, if the property name is not a Prism identifier or if the fields are neither Boolean nor numeric\n\t\t */\n\t\tpublic RawResult(String[] record, Header header, int line) throws PrismLangException\n\t\t{\n\t\t\tcheckNumberOfFields(record, header);\n\t\t\tpropertyName = parsePropertyName(record, header, line);\n\t\t\tconstantValues = parseConstants(record, header, line);\n\t\t\tresultValue =  parseResult(record, header, line);\n\t\t}\n\n\t\t/**\n\t\t * Check that the record has the same number of fields as the header.\n\t\t * \n\t\t * @param record the record\n\t\t * @param header the header\n\t\t * @return The number of fields\n\t\t * @throws PrismLangException If the record has not the same number of fields as the header\n\t\t */\n\t\tprotected int checkNumberOfFields(String[] record, Header header) throws PrismLangException\n\t\t{\n\t\t\tif (record.length != header.numColumns) {\n\t\t\t\tthrow new PrismLangException(\"Record must have \" + header.numColumns + \" columns but got \" + record.length);\n\t\t\t}\n\t\t\treturn record.length;\n\t\t}\n\n\t\t/**\n\t\t * Parse the property name as a Prism identifier.\n\t\t * \n\t\t * @param record the record\n\t\t * @param header the header\n\t\t * @param line the line number of the record for error messages\n\t\t * @return The property name\n\t\t * @throws PrismLangException If the property name is not a Prism identifier\n\t\t */\n\t\tprotected String parsePropertyName(String[] record, Header header, int line) throws PrismLangException\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn parseIdentifier(record[header.propertyIndex]);\n\t\t\t} catch (PrismLangException e) {\n\t\t\t\tthrow new PrismLangException(\"Property must be an identifier (input line: \" + line + \", field: \" + (header.propertyIndex + 1) + \")\");\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Parse the constant fields as Booleans or numeric values.\n\t\t * \n\t\t * @param record the record\n\t\t * @param header the header\n\t\t * @param line the line number of the record for error messages\n\t\t * @return The constant values\n\t\t * @throws PrismLangException If the a constant field is neither Boolean nor numeric\n\t\t */\n\t\tprotected Object[] parseConstants(String[] record, Header header, int line) throws PrismLangException\n\t\t{\n\t\t\tObject[] constants = new Object[record.length - 2];\n\t\t\tfor (int i = 0, c = 0, length = record.length; i < length; i++ ) {\n\t\t\t\tif (i != header.propertyIndex && i != header.resultIndex) {\n\t\t\t\t\tconstants[c++] = parseConstant(record, line, i);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn constants;\n\t\t}\n\n\t\t/**\n\t\t * Parse a single constant field as Boolean or numeric value.\n\t\t * \n\t\t * @param record the record\n\t\t * @param line the line number of the record for error messages\n\t\t * @param field the field index\n\t\t * @return The constant value\n\t\t * @throws PrismLangException If the field is neither Boolean nor numeric\n\t\t */\n\t\tprotected Object parseConstant(String[] record, int line, int field) throws PrismLangException\n\t\t{\n\t\t\tString string = record[field];\n\t\t\tif (string.isEmpty()) {\n\t\t\t\treturn null;\n\t\t\t}\n\t\t\tObject value =  parseValue(record[field]);\n\t\t\tif (value instanceof Boolean || value instanceof Number) {\n\t\t\t\treturn value;\n\t\t\t}\n\t\t\tthrow new PrismLangException(\"Constant must be either Boolean or numeric (input line: \" + line + \", field: \" + (field + 1) + \") but got: \" + value);\n\t\t}\n\n\t\t/**\n\t\t * Parse the result field as Boolean or numeric value.\n\t\t * \n\t\t * @param record the record\n\t\t * @param header the header\n\t\t * @param line the line number of the record for error messages\n\t\t * @return The result value\n\t\t * @throws PrismLangException If the field is neither Boolean nor numeric\n\t\t */\n\t\tprotected Object parseResult(String[] record, Header header, int line) throws PrismLangException\n\t\t{\n\t\t\tObject value =  parseValue(record[header.resultIndex]);\n\t\t\tif (value instanceof Boolean || value instanceof Number) {\n\t\t\t\treturn value;\n\t\t\t}\n\t\t\tthrow new PrismLangException(\"Result must be either Boolean or numeric (input line: \" + line + \", field: \" + (header.resultIndex + 1) + \") but got: \" + value);\n\t\t}\n\t}\n\n\n\n\t/**\n\t * An intermediate collection of results for which the domains of the constants are not known yet.\n\t */\n\tpublic static class RawResultsCollection\n\t{\n\t\tfinal Header header;\n\t\tfinal String propertyName;\n\t\tfinal List<RawResult> results;\n\t\tBitSet typeConversions;\n\t\tTypeInfo constantTypes[];\n\t\tTypeInfo resultType;\n\n\t\t/**\n\t\t * Create an intermediate collection of results.\n\t\t * The non-empty constant fields of the first result determine the ranging constants.\n\t\t * \n\t\t * @param header the header containing the constant names and the result name\n\t\t * @param result the first result to initialize the collection\n\t\t */\n\t\tpublic RawResultsCollection(Header header, RawResult result)\n\t\t{\n\t\t\tthis.header = header;\n\t\t\tthis.propertyName = result.propertyName;\n\t\t\tthis.results = new ArrayList<RawResult>();\n\t\t\tinitializeTypes(result);\n\t\t\tinferTypes(result);\n\t\t\tresults.add(result);\n\t\t}\n\n\t\t/**\n\t\t * Add a result to the collection.\n\t\t * \n\t\t * @param result the result to be added\n\t\t * @throws PrismLangException If the property field is not the name of the collection\n\t\t */\n\t\tpublic void add(RawResult result) throws PrismLangException\n\t\t{\n\t\t\tif (! propertyName.equals(result.propertyName)) {\n\t\t\t\tthrow new PrismLangException(\"Property field expected to be \\\"\" + propertyName + \"\\\" but got: \" + result.propertyName);\n\t\t\t}\n\t\t\tinferTypes(result);\n\t\t\tresults.add(result);\n\t\t}\n\n\t\t/**\n\t\t * Define the constants and their domains and create a {@link ResultsCollection}.\n\t\t * \n\t\t * @return The receiver converted to a results collection\n\t\t * @throws PrismLangException \n\t\t */\n\t\tpublic ResultsCollection toResultsCollection() throws PrismLangException\n\t\t{\n\t\t\tconvertConstants();\n\t\t\t@SuppressWarnings(\"rawtypes\")\n\t\t\tVector<DefinedConstant> rangingConstants = getRangingConstants();\n\t\t\tResultsCollection collection = new ResultsCollection(rangingConstants, 0, rangingConstants.size(), new Values(), header.resultName);\n\t\t\tfor (RawResult result : results) {\n\t\t\t\tValues values = new Values();\n\t\t\t\tfor (int i = 0, length = constantTypes.length; i < length; i++) {\n\t\t\t\t\tif (constantTypes[i] != TypeInfo.Nil) {\n\t\t\t\t\t\tvalues.addValue(header.constantNames[i], result.constantValues[i]);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tint set = collection.setResult(values, result.resultValue);\n\t\t\t\tif (set < 1) {\n\t\t\t\t\tthrow new PrismLangException(\"Result overridden: \" + values + \" -> \" + result);\n\t\t\t\t}\n\t\t\t\tif (set > 1) {\n\t\t\t\t\tthrow new PrismLangException(\"Multiple results set: \" + values + \" -> \" + result);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn collection;\n\t\t}\n\n\t\t/**\n\t\t * Get the name.\n\t\t * \n\t\t * @return The name\n\t\t */\n\t\tpublic String getPropertyName()\n\t\t{\n\t\t\treturn propertyName;\n\t\t}\n\n\t\t/**\n\t\t * Get the type of the result fields.\n\t\t * \n\t\t * @return The type of the result fields\n\t\t */\n\t\tpublic TypeInfo getResultType()\n\t\t{\n\t\t\treturn resultType;\n\t\t}\n\n\t\t/**\n\t\t * Initialize the type information with the first result.\n\t\t *  \n\t\t * @param result the initial result\n\t\t */\n\t\tprotected void initializeTypes(RawResult result)\n\t\t{\n\t\t\tint numConstants = result.constantValues.length;\n\t\t\ttypeConversions = new BitSet(numConstants); \n\t\t\tconstantTypes = new TypeInfo[numConstants];\n\t\t\tfor (int i = 0; i < numConstants; i++) {\n\t\t\t\tconstantTypes[i] = TypeInfo.from(result.constantValues[i]);\n\t\t\t}\n\t\t\tresultType = TypeInfo.from(result.resultValue);\n\t\t}\n\n\t\t/**\n\t\t * Infer the types of the constant values and the type of the result value.\n\t\t * \n\t\t * @param result the raw result\n\t\t */\n\t\tprotected void inferTypes(RawResult result)\n\t\t{\n\t\t\tfor (int i = 0, length = constantTypes.length; i < length; i++) {\n\t\t\t\tObject value = result.constantValues[i];\n\t\t\t\tTypeInfo type = TypeInfo.from(value);\n\t\t\t\tTypeInfo current = constantTypes[i];\n\t\t\t\tTypeInfo inferred = current.infer(value);\n\t\t\t\tconstantTypes[i] = inferred;\n\t\t\t\tif (type != current || inferred != current) {\n\t\t\t\t\ttypeConversions.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\tresultType = resultType.infer(result.resultValue);\n\t\t}\n\n\t\t/**\n\t\t * Convert the field values such that all fields of each column have the same type.\n\t\t */\n\t\tprotected void convertConstants()\n\t\t{\n\t\t\tif (typeConversions.isEmpty()) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tfor (RawResult result : results) {\n\t\t\t\tfor (OfInt bits = IterableBitSet.getSetBits(typeConversions).iterator(); bits.hasNext();) {\n\t\t\t\t\tint i = bits.nextInt();\n\t\t\t\t\tresult.constantValues[i] = constantTypes[i].convert(result.constantValues[i]);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Define a constant for each value column with its entries as domain.\n\t\t * \n\t\t * @return A vector containing the defined constants\n\t\t * @throws PrismLangException If a type is not supported for constants\n\t\t */\n\t\t@SuppressWarnings({ \"rawtypes\"})\n\t\tprotected Vector<DefinedConstant> getRangingConstants() throws PrismLangException\n\t\t{\n\t\t\tSet<Object>[] domains = collectConstantDomains();\n\t\t\tVector<DefinedConstant> rangingConstants = new Vector<>();\n\t\t\tfor (int i = 0, length = domains.length; i < length; i++) {\n\t\t\t\tSet<?> domain = domains[i];\n\t\t\t\tif (! domain.isEmpty()) {\n\t\t\t\t\tDefinedDomain<?> constant = defineConstant(header.constantNames[i], domains[i], constantTypes[i]);\n\t\t\t\t\trangingConstants.add(constant);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn rangingConstants;\n\t\t}\n\n\t\t/**\n\t\t * Define a Prism constant over a domain.\n\t\t * \n\t\t * @param constantName the name of the constant\n\t\t * @param domain the domain of the constant\n\t\t * @param type the type of the constant\n\t\t * @return A constant defined over the domain of the given type\n\t\t * @throws PrismLangException If the type is not supported for a constant\n\t\t */\n\t\t@SuppressWarnings(\"unchecked\")\n\t\tprotected DefinedDomain<?> defineConstant(String constantName, Set<?> domain, TypeInfo type) throws PrismLangException\n\t\t{\n\t\t\tDefinedDomain<?> constant;\n\t\t\tswitch (type) {\n\t\t\tcase Integer:\n\t\t\t\tconstant = DefinedDomain.fromValues(constantName, TypeInt.getInstance(), (Set<Integer>) domain, new Integer[0]);\n\t\t\t\tbreak;\n\t\t\tcase Double:\n\t\t\t\tconstant = DefinedDomain.fromValues(constantName, TypeDouble.getInstance(), (Set<Double>) domain, new Double[0]);\n\t\t\t\tbreak;\n\t\t\tcase BigRational:\n\t\t\t\tconstant = DefinedDomain.fromValues(constantName, TypeDouble.getInstance(), (Set<BigRational>) domain, new BigRational[0]);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismLangException(\"Ranging constants must not be of type\" + type);\n\t\t\t}\n\t\t\treturn constant;\n\t\t}\n\n\t\t/**\n\t\t * Collect for each constant the non-null values in a set\n\t\t * \n\t\t * @return An array of sets of values for each constant\n\t\t */\n\t\tprotected Set<Object>[] collectConstantDomains()\n\t\t{\n\t\t\t@SuppressWarnings(\"unchecked\")\n\t\t\tSet<Object>[] domains = new Set[constantTypes.length];\n\t\t\tfor (int i = 0, length = domains.length; i < length; i++) {\n\t\t\t\tdomains[i] = new HashSet<>();\n\t\t\t}\n\t\t\tfor (RawResult result : results) {\n\t\t\t\tfor (int i = 0, length = domains.length; i < length; i++) {\n\t\t\t\t\tObject value = result.constantValues[i];\n\t\t\t\t\tif (value != null) {\n\t\t\t\t\t\tdomains[i].add(value);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn domains;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/RewardGenerator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport explicit.rewards.Rewards;\nimport parser.State;\nimport parser.ast.RewardStruct;\n\n/**\n * Interface for classes that generate rewards for a model.\n * This is a generic class where rewards are of type {@code Value}.\n * <br><br>\n * Firstly, this includes basic syntactic info (see {@link RewardInfo}).\n * In particular, this gives the number of reward structures and their names.\n * It is only necessary to implement {@link #getRewardStructNames()};\n * the others have default implementations that use this method as a basis.\n * <br><br>\n * Secondly it provides access to the rewards themselves.\n * Implementations of {@link RewardGenerator} can allow rewards to be queried in one or more ways:\n * by {@link State} object; by (integer) state index; syntactically by providing a {@link RewardStruct};\n * or by directly providing a (explicit engine) {@link Rewards} object.\n * The method {@link RewardGenerator#isRewardLookupSupported(RewardLookup)} should return true or false accordingly.\n * <br><br>\n * Default implementations of all methods are provided which assume that rewards are\n * looked up by {@link State} object and there are no rewards defined (zero reward structures).\n */\npublic interface RewardGenerator<Value> extends RewardInfo\n{\n\t/**\n\t * Mechanisms for querying rewards\n\t */\n\tpublic enum RewardLookup { BY_STATE, BY_STATE_INDEX, BY_REWARD_STRUCT, BY_REWARD_OBJECT };\n\t\n\t/**\n\t * Get an Evaluator for the values generated by this RewardGenerator for rewards.\n\t * This is needed, for example, to sum rewards or check if they are negative/NaN.\n\t * A default implementation provides an evaluator for the (usual) case when Value is Double.\n\t * The method name is distinct from {@link ModelGenerator#getEvaluator()} so that\n\t * classes implementing both interfaces do not need to disambiguate.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic default Evaluator<Value> getRewardEvaluator()\n\t{\n\t\treturn (Evaluator<Value>) Evaluator.forDouble();\n\t}\n\t\n\t/**\n\t * Check which mechanisms for looking up rewards are supported.\n\t */\n\tpublic default boolean isRewardLookupSupported(RewardLookup lookup)\n\t{\n\t\t// By default, rewards are queried via State objects (only)\n\t\treturn lookup == RewardLookup.BY_STATE;\n\t}\n\t\n\t/**\n\t * Get the state reward of the {@code r}th reward structure for state {@code state}\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_STATE)}.\n\t * If a reward structure has no state rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasStateRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support state rewards.\n\t * @param r The index of the reward structure to use\n\t * @param state The state in which to evaluate the rewards\n\t */\n\tpublic default Value getStateReward(int r, State state) throws PrismException\n\t{\n\t\treturn getStateReward(r, state, false);\n\t}\n\n\t/**\n\t * Get the state reward of the {@code r}th reward structure for state {@code state}\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_STATE)}.\n\t * If a reward structure has no state rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasStateRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support state rewards.\n\t * @param r The index of the reward structure to use\n\t * @param state The state in which to evaluate the rewards\n\t * @param allowNegative Whether to allow negative rewards\n\t */\n\tpublic default Value getStateReward(int r, State state, boolean allowNegative) throws PrismException\n\t{\n\t\t// Default implementation: error if not supported, or bad index\n\t\tif (!isRewardLookupSupported(RewardLookup.BY_STATE)) {\n\t\t\tthrow new PrismException(\"Reward lookup by State not supported\");\n\t\t}\n\t\tif (r < 0 || r >= getNumRewardStructs()) {\n\t\t\tthrow new PrismException(\"Invalid reward index \" + r);\n\t\t}\n\t\t// Otherwise, if reward is not defined, that's an error\n\t\tthrow new PrismException(\"Reward has not been defined\");\n\t}\n\n\t/**\n\t * Get the state-action reward of the {@code r}th reward structure for state {@code state} and action {@code action}\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_STATE)}.\n\t * If a reward structure has no transition rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasTransitionRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support transition rewards rewards.\n\t * @param r The index of the reward structure to use\n\t * @param state The state in which to evaluate the rewards\n\t * @param action The outgoing action label\n\t */\n\tpublic default Value getStateActionReward(int r, State state, Object action) throws PrismException\n\t{\n\t\treturn getStateActionReward(r, state, action, false);\n\t}\n\n\t/**\n\t * Get the state-action reward of the {@code r}th reward structure for state {@code state} and action {@code action}\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_STATE)}.\n\t * If a reward structure has no transition rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasTransitionRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support transition rewards.\n\t * @param r The index of the reward structure to use\n\t * @param state The state in which to evaluate the rewards\n\t * @param action The outgoing action label\n\t * @param allowNegative Whether to allow negative rewards\n\t */\n\tpublic default Value getStateActionReward(int r, State state, Object action, boolean allowNegative) throws PrismException\n\t{\n\t\t// Default implementation: error if not supported, or bad index\n\t\tif (!isRewardLookupSupported(RewardLookup.BY_STATE)) {\n\t\t\tthrow new PrismException(\"Reward lookup by State not supported\");\n\t\t}\n\t\tif (r < 0 || r >= getNumRewardStructs()) {\n\t\t\tthrow new PrismException(\"Invalid reward index \" + r);\n\t\t}\n\t\t// Otherwise, if reward is not defined, that's an error\n\t\tthrow new PrismException(\"Reward has not been defined\");\n\t}\n\n\t/**\n\t * Get the state reward of the {@code r}th reward structure for state {@code s}\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_STATE_INDEX)}.\n\t * If a reward structure has no state rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasStateRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support state rewards.\n\t * @param r The index of the reward structure to use\n\t * @param s The index of the state in which to evaluate the rewards\n\t */\n\tpublic default Value getStateReward(int r, int s) throws PrismException\n\t{\n\t\treturn getStateReward(r, s, false);\n\t}\n\n\t/**\n\t * Get the state reward of the {@code r}th reward structure for state {@code s}\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_STATE_INDEX)}.\n\t * If a reward structure has no state rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasStateRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support state rewards.\n\t * @param r The index of the reward structure to use\n\t * @param s The index of the state in which to evaluate the rewards\n\t * @param allowNegative Whether to allow negative rewards\n\t */\n\tpublic default Value getStateReward(int r, int s, boolean allowNegative) throws PrismException\n\t{\n\t\t// Default implementation: error if not supported, or bad index\n\t\tif (!isRewardLookupSupported(RewardLookup.BY_STATE_INDEX)) {\n\t\t\tthrow new PrismException(\"Reward lookup by state index not supported\");\n\t\t}\n\t\tif (r < 0 || r >= getNumRewardStructs()) {\n\t\t\tthrow new PrismException(\"Invalid reward index \" + r);\n\t\t}\n\t\t// Otherwise, if reward is not defined, that's an error\n\t\tthrow new PrismException(\"Reward has not been defined\");\n\t}\n\n\t/**\n\t * Get the state-action reward of the {@code r}th reward structure for state {@code s} and action {@code action}\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_STATE_INDEX)}.\n\t * If a reward structure has no transition rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasTransitionRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support transition rewards.\n\t * @param r The index of the reward structure to use\n\t * @param s The index of the state in which to evaluate the rewards\n\t * @param action The outgoing action label\n\t */\n\tpublic default Value getStateActionReward(int r, int s, Object action) throws PrismException\n\t{\n\t\treturn getStateActionReward(r, s, action, false);\n\t}\n\n\t/**\n\t * Get the state-action reward of the {@code r}th reward structure for state {@code s} and action {@code action}\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_STATE_INDEX)}.\n\t * If a reward structure has no transition rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasTransitionRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support transition rewards.\n\t * @param r The index of the reward structure to use\n\t * @param s The index of the state in which to evaluate the rewards\n\t * @param action The outgoing action label\n\t * @param allowNegative Whether to allow negative rewards\n\t */\n\tpublic default Value getStateActionReward(int r, int s, Object action, boolean allowNegative) throws PrismException\n\t{\n\t\t// Default implementation: error if not supported, or bad index\n\t\tif (!isRewardLookupSupported(RewardLookup.BY_STATE_INDEX)) {\n\t\t\tthrow new PrismException(\"Reward lookup by state index not supported\");\n\t\t}\n\t\tif (r < 0 || r >= getNumRewardStructs()) {\n\t\t\tthrow new PrismException(\"Invalid reward index \" + r);\n\t\t}\n\t\t// Otherwise, if reward is not defined, that's an error\n\t\tthrow new PrismException(\"Reward has not been defined\");\n\t}\n\n\t/**\n\t * Get a {@link RewardStruct} object representing the {@code r}th reward structure\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_REWARD_STRUCT)}.\n\t * Throws an exception if {@code r} is out of range or the information is not available.\n\t * If a reward structure has no transition rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasTransitionRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support transition rewards.\n\t */\n\tpublic default RewardStruct getRewardStruct(int r) throws PrismException\n\t{\n\t\t// Default implementation: error if not supported, or bad index\n\t\tif (!isRewardLookupSupported(RewardLookup.BY_REWARD_STRUCT)) {\n\t\t\tthrow new PrismException(\"Reward lookup by reward struct not supported\");\n\t\t}\n\t\tif (r < 0 || r >= getNumRewardStructs()) {\n\t\t\tthrow new PrismException(\"Invalid reward index \" + r);\n\t\t}\n\t\t// Otherwise, if reward is not defined, that's an error\n\t\tthrow new PrismException(\"Reward has not been defined\");\n\t}\n\n\t/**\n\t * Get a {@link Rewards} object representing the {@code r}th reward structure\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_REWARD_OBJECT)}.\n\t * Throws an exception if {@code r} is out of range or the information is not available.\n\t * If a reward structure has no transition rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasTransitionRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support transition rewards.\n\t */\n\tpublic default Rewards<Value> getRewardObject(int r) throws PrismException\n\t{\n\t\t// Default implementation: error if not supported, or bad index\n\t\tif (!isRewardLookupSupported(RewardLookup.BY_REWARD_OBJECT)) {\n\t\t\tthrow new PrismException(\"Reward lookup by reward object not supported\");\n\t\t}\n\t\tif (r < 0 || r >= getNumRewardStructs()) {\n\t\t\tthrow new PrismException(\"Invalid reward index \" + r);\n\t\t}\n\t\t// Otherwise, if reward is not defined, that's an error\n\t\tthrow new PrismException(\"Reward has not been defined\");\n\t}\n\n\t/**\n\t * Get the {@link Model} corresponding to the {@link Rewards} objects when rewards are provided in this way.\n\t * Only available if {@link #isRewardLookupSupported(RewardLookup)} returns true for {@code RewardLookup.BY_REWARD_OBJECT)}.\n\t * Throws an exception if the information is not available.\n\t * If a reward structure has no transition rewards, you can indicate this by implementing\n\t * the method {@link #rewardStructHasTransitionRewards(int)}, which may improve efficiency\n\t * and/or allow use of algorithms/implementations that do not support transition rewards.\n\t */\n\tpublic default explicit.Model<Value> getRewardObjectModel() throws PrismException\n\t{\n\t\t// Default implementation: error if not supported\n\t\tif (!isRewardLookupSupported(RewardLookup.BY_REWARD_OBJECT)) {\n\t\t\tthrow new PrismException(\"Reward lookup by reward object not supported\");\n\t\t}\n\t\t// Otherwise, if model is not defined, that's an error\n\t\tthrow new PrismException(\"Model for rewards has not been defined\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/RewardInfo.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2024-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.List;\n\n/**\n * Interface for classes that provide some basic (syntactic) information about rewards for a model.\n * In particular, this gives the number of reward structures and their names.\n * It is only necessary to implement {@link #getRewardStructNames()};\n * the others have default implementations that use this method as a basis.\n */\npublic interface RewardInfo\n{\n\t/**\n\t * Get a list of the names of the reward structures.\n\t * Unnamed reward structures are allowed and should use name \"\".\n\t * Reward names should be distinct (except if equal to \"\").\n\t */\n\tpublic default List<String> getRewardStructNames()\n\t{\n\t\t// No reward structures by default\n\t\treturn Collections.emptyList();\n\t}\n\n\t/**\n\t * Get a list of the strings needed to reference the reward structures,\n\t * i.e., \"r\" for named ones and k for unnamed ones.\n\t */\n\tpublic default List<String> getRewardStructReferences()\n\t{\n\t\tList<String> refs = new ArrayList<>();\n\t\tint numRewards = getNumRewardStructs();\n\t\tfor (int r = 0; r < numRewards; r++) {\n\t\t\tString name = getRewardStructName(r);\n\t\t\tif (\"\".equals(name) || name == null) {\n\t\t\t\trefs.add(Integer.toString(r + 1));\n\t\t\t} else {\n\t\t\t\trefs.add(\"\\\"\" + name + \"\\\"\");\n\t\t\t}\n\t\t}\n\t\treturn refs;\n\t}\n\n\t/**\n\t * Get the number of reward structures.\n\t */\n\tpublic default int getNumRewardStructs()\n\t{\n\t\t// Default implementation just extracts from getRewardStructNames()\n\t\treturn getRewardStructNames().size();\n\t}\n\n\t/**\n\t * Look up the index of a reward structure by name.\n\t * (indexed from 0, not from 1 like at the user (property language) level).\n\t * Returns -1 if there is no such reward structure.\n\t */\n\tpublic default int getRewardStructIndex(String name)\n\t{\n\t\t// Default implementation just extracts from getRewardStructNames()\n\t\treturn getRewardStructNames().indexOf(name);\n\t}\n\n\t/**\n\t * Get the name of the {@code i}th reward structure.\n\t * {@code i} should always be between 0 and getNumVars() - 1.\n\t */\n\tpublic default String getRewardStructName(int i)\n\t{\n\t\t// Default implementation just extracts from getRewardStructNames()\n\t\treturn getRewardStructNames().get(i);\n\t}\n\n\t/**\n\t * Returns true if the {@code r}th reward structure defines state rewards.\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * If this returns false, the model checker is allowed to ignore them (which may be more efficient).\n\t * If using an algorithm or implementation that does not support state rewards,\n\t * you may need to return false here (as well as not defining state rewards).\n\t */\n\tpublic default boolean rewardStructHasStateRewards(int r)\n\t{\n\t\t// By default, assume that any reward structures that do exist may have state rewards\n\t\treturn true;\n\t}\n\n\t/**\n\t * Returns true if the {@code r}th reward structure defines transition rewards.\n\t * ({@code r} is indexed from 0, not from 1 like at the user (property language) level).\n\t * If this returns false, the model checker is allowed to ignore them (which may be more efficient).\n\t * If using an algorithm or implementation that does not support transition rewards,\n\t * you may need to return false here (as well as not defining transition rewards).\n\t */\n\tpublic default boolean rewardStructHasTransitionRewards(int r)\n\t{\n\t\t// By default, assume that any reward structures that do exist may have transition rewards\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/SBML2Prism.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.File;\nimport java.io.IOException;\nimport java.io.InputStream;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\n\nimport javax.xml.parsers.DocumentBuilder;\nimport javax.xml.parsers.DocumentBuilderFactory;\nimport javax.xml.parsers.ParserConfigurationException;\n\nimport org.w3c.dom.Document;\nimport org.w3c.dom.Element;\nimport org.w3c.dom.Node;\nimport org.w3c.dom.NodeList;\nimport org.xml.sax.EntityResolver;\nimport org.xml.sax.ErrorHandler;\nimport org.xml.sax.InputSource;\nimport org.xml.sax.SAXException;\nimport org.xml.sax.SAXParseException;\n\npublic class SBML2Prism extends Reactions2Prism implements EntityResolver\n{\n\t/** Name of the original SBML file */\n\tprotected String parsedFileName;\n\t/** Temporary storage of the parsed XML */\n\tprotected Document parsedSBML;\n\n\t// Constructors\n\n\tpublic SBML2Prism() throws PrismException\n\t{\n\t\tsuper();\n\t}\n\n\tpublic SBML2Prism(PrismLog mainLog)\n\t{\n\t\tsuper(mainLog);\n\t}\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"sbml\";\n\t}\n\n\t@Override\n\tpublic void load(File file) throws PrismException\n\t{\n\t\t// Store filename for later use before parsing\n\t\tparsedFileName = file.getPath();\n\t\tsuper.load(file);\n\t}\n\n\t@Override\n\tpublic void load(InputStream in) throws PrismException\n\t{\n\t\tDocumentBuilderFactory factory;\n\t\tDocumentBuilder builder;\n\t\tparsedSBML = null;\n\n\t\t// Create XML parser\n\t\tfactory = DocumentBuilderFactory.newInstance();\n\t\tfactory.setValidating(false);\n\t\tfactory.setIgnoringElementContentWhitespace(true);\n\t\ttry {\n\t\t\tbuilder = factory.newDocumentBuilder();\n\t\t\tbuilder.setEntityResolver(this);\n\t\t\tbuilder.setErrorHandler(new ErrorHandler()\n\t\t\t{\n\t\t\t\tpublic void fatalError(SAXParseException e) throws SAXException\n\t\t\t\t{\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\n\t\t\t\tpublic void error(SAXParseException e) throws SAXException\n\t\t\t\t{\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\n\t\t\t\tpublic void warning(SAXParseException e)\n\t\t\t\t{\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (ParserConfigurationException e) {\n\t\t\tthrow new PrismException(\"Couldn't create XML parser\");\n\t\t}\n\n\t\t// Parse XML\n\t\ttry {\n\t\t\tparsedSBML = builder.parse(in);\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"Error reading SBML: \" + e.getMessage());\n\t\t} catch (SAXException e) {\n\t\t\tthrow new PrismException(\"Invalid XML file:\\n\" + e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Function used by parseSBML() above to find the SBML DTD\n\t * (this currently unused since we do not validate the SBML file when reading)\n\t * (and since the DTD specified in the SBML files is not local)\n\t * (if validation is enabled, put the DTD file \"sbml.dtd\" in PRISM's \"dtds\" directory)\n\t */\n\tpublic InputSource resolveEntity(String publicId, String systemId) throws SAXException, IOException\n\t{\n\t\tInputSource inputSource = null;\n\n\t\t// override the resolve method for the dtd\n\t\tif (systemId.endsWith(\"dtd\")) {\n\t\t\t// get appropriate dtd from classpath\n\t\t\tInputStream inputStream = this.getClass().getResourceAsStream(\"dtds/sbml.dtd\");\n\t\t\tif (inputStream != null)\n\t\t\t\tinputSource = new InputSource(inputStream);\n\t\t}\n\n\t\treturn inputSource;\n\t}\n\n\t@Override\n\tpublic void translate(PrintStream out) throws PrismException\n\t{\n\t\tcheckSBMLVersion(parsedSBML);\n\t\textractModelFromSBML(parsedSBML);\n\t\t// Generate PRISM code\n\t\tprismCodeHeader = \"// File generated by automatic SBML-to-PRISM conversion\\n\";\n\t\tif (parsedFileName != null) {\n\t\t\tprismCodeHeader += \"// Original SBML file: \" + parsedFileName + \"\\n\\n\";\n\t\t}\n\t\tconvertToPRISMCode(out);\n\t\t// Reset filename storage\n\t\tparsedFileName = null;\n\t}\n\n\t/**\n\t * Check that we can handle whatever level/version this file is.\n\t */\n\tprivate void checkSBMLVersion(Document doc) throws PrismException\n\t{\n\t\tString level, s;\n\n\t\tlevel = doc.getDocumentElement().getAttribute(\"level\");\n\t\tif (!(\"2\".equals(level))) {\n\t\t\ts = \"The translator only handles Level 2 SBML files - this is a Level \" + level + \" file\";\n\t\t\tthrow new PrismException(s);\n\t\t}\n\t}\n\n\t/**\n\t * Build the reaction set model from a parsed SBML file.\n\t */\n\tprivate void extractModelFromSBML(Document doc) throws PrismException\n\t{\n\t\tElement e, e_model, e_list;\n\t\tElement e_comp, e_species, e_parameter, e_reaction, e_kinetics, e_mathml;\n\t\tNodeList nodes, nodes2;\n\t\tNode node = null;\n\t\tSpecies species;\n\t\tParameter parameter;\n\t\tReaction reaction;\n\t\tint i, j, k, n, m;\n\t\tdouble d;\n\t\tString s, s2;\n\t\tboolean found;\n\n\t\t// Get \"model\" element of SBML file\n\t\tnodes = doc.getDocumentElement().getElementsByTagName(\"model\");\n\t\te_model = (Element) nodes.item(0);\n\n\t\t// Process compartment info (if present)\n\t\t// Just need to extract the size in case used\n\t\te_list = (Element) e_model.getElementsByTagName(\"listOfCompartments\").item(0);\n\t\tnodes = e_list.getElementsByTagName(\"compartment\");\n\t\tn = nodes.getLength();\n\t\t// Make sure there is at most one\n\t\tif (n > 1)\n\t\t\tthrow new PrismException(\"Only one compartment is permitted\");\n\t\t// And if present, store size info\n\t\tcompartmentName = null;\n\t\tif (n == 1) {\n\t\t\te_comp = (Element) nodes.item(0);\n\t\t\tif (!\"\".equals(e_comp.getAttribute(\"size\"))) {\n\t\t\t\tcompartmentName = e_comp.getAttribute(\"id\");\n\t\t\t\tif (\"\".equals(compartmentName))\n\t\t\t\t\tthrow new PrismException(\"Missing compartment name\");\n\t\t\t\tcompartmentSize = Double.parseDouble(e_comp.getAttribute(\"size\"));\n\t\t\t}\n\t\t}\n\n\t\t// Process list of species\n\t\tspeciesList = new ArrayList<Species>();\n\t\te_list = (Element) e_model.getElementsByTagName(\"listOfSpecies\").item(0);\n\t\tnodes = e_list.getElementsByTagName(\"species\");\n\t\tn = nodes.getLength();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\te_species = (Element) nodes.item(i);\n\t\t\tspeciesId = e_species.getAttribute(\"id\");\n\t\t\tinitialAmountString = e_species.getAttribute(\"initialAmount\");\n\t\t\tif (\"\".equals(initialAmountString))\n\t\t\t\tthrow new PrismException(\"Missing initial amount for species \" + speciesId);\n\t\t\ttry {\n\t\t\t\td = Double.parseDouble(initialAmountString);\n\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\tString msg = \"Badly formatted initialAmount \\\"\" + initialAmountString + \"\\\" for species \" + speciesId;\n\t\t\t\tthrow new PrismException(msg);\n\t\t\t}\n\t\t\tspecies = new Species(speciesId, e_species.getAttribute(\"name\"), d);\n\t\t\ts = e_species.getAttribute(\"boundaryCondition\");\n\t\t\tif (s.equals(\"true\"))\n\t\t\t\tspecies.boundaryCondition = true;\n\t\t\tspeciesList.add(species);\n\t\t}\n\n\t\t// Process list of parameters (if present)\n\t\tparameterList = new ArrayList<Parameter>();\n\t\t// Look at direct children only (there might be listOfParameters nodes lower in the tree)\n\t\tnodes = e_model.getChildNodes();\n\t\tn = nodes.getLength();\n\t\tfound = false;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tnode = nodes.item(i);\n\t\t\tif (\"listOfParameters\".equals(node.getNodeName())) {\n\t\t\t\tfound = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\tif (found) {\n\t\t\te_list = (Element) node;\n\t\t\tnodes = e_list.getElementsByTagName(\"parameter\");\n\t\t\tn = nodes.getLength();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\te_parameter = (Element) nodes.item(i);\n\t\t\t\tparameter = new Parameter(e_parameter.getAttribute(\"id\"), e_parameter.getAttribute(\"value\"));\n\t\t\t\tparameterList.add(parameter);\n\t\t\t}\n\t\t}\n\n\t\t// Process list of reactions\n\t\treactionList = new ArrayList<Reaction>();\n\t\te_list = (Element) e_model.getElementsByTagName(\"listOfReactions\").item(0);\n\t\tnodes = e_list.getElementsByTagName(\"reaction\");\n\t\tn = nodes.getLength();\n\t\tfor (i = 0; i < n; i++) {\n\n\t\t\t// Process a single reaction...\n\t\t\te_reaction = (Element) nodes.item(i);\n\t\t\treaction = new Reaction(e_reaction.getAttribute(\"id\"), e_reaction.getAttribute(\"name\"));\n\n\t\t\t// Reactant list\n\t\t\te_list = (Element) e_reaction.getElementsByTagName(\"listOfReactants\").item(0);\n\t\t\tif (e_list != null) {\n\t\t\t\tnodes2 = e_list.getElementsByTagName(\"speciesReference\");\n\t\t\t\tm = nodes2.getLength();\n\t\t\t\tfor (j = 0; j < m; j++) {\n\t\t\t\t\te = (Element) nodes2.item(j);\n\t\t\t\t\t// Get species name of product\n\t\t\t\t\ts = e.getAttribute(\"species\");\n\t\t\t\t\t// Get stoichiometry if present\n\t\t\t\t\ts2 = e.getAttribute(\"stoichiometry\");\n\t\t\t\t\tk = 1;\n\t\t\t\t\tif (s2.length() > 0)\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tk = Integer.parseInt(s2);\n\t\t\t\t\t\t} catch (NumberFormatException ex) {\n\t\t\t\t\t\t\tthrow new PrismException(\"Invalid stoichiometry value \\\"\" + s2 + \"\\\"\");\n\t\t\t\t\t\t}\n\t\t\t\t\t// Add reactant to reaction\n\t\t\t\t\treaction.addReactant(s, k);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Product list\n\t\t\te_list = (Element) e_reaction.getElementsByTagName(\"listOfProducts\").item(0);\n\t\t\tif (e_list != null) {\n\t\t\t\tnodes2 = e_list.getElementsByTagName(\"speciesReference\");\n\t\t\t\tm = nodes2.getLength();\n\t\t\t\tfor (j = 0; j < m; j++) {\n\t\t\t\t\te = (Element) nodes2.item(j);\n\t\t\t\t\t// Get species name of product\n\t\t\t\t\ts = e.getAttribute(\"species\");\n\t\t\t\t\t// Get stoichiometry if present\n\t\t\t\t\ts2 = e.getAttribute(\"stoichiometry\");\n\t\t\t\t\tk = 1;\n\t\t\t\t\tif (s2.length() > 0)\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tk = Integer.parseInt(s2);\n\t\t\t\t\t\t} catch (NumberFormatException ex) {\n\t\t\t\t\t\t\tthrow new PrismException(\"Invalid stoichiometry value \\\"\" + s2 + \"\\\"\");\n\t\t\t\t\t\t}\n\t\t\t\t\t// Add product to reaction\n\t\t\t\t\treaction.addProduct(s, k);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Kinetic law\n\t\t\te_kinetics = (Element) e_reaction.getElementsByTagName(\"kineticLaw\").item(0);\n\t\t\te_mathml = (Element) e_kinetics.getElementsByTagName(\"math\").item(0);\n\t\t\treaction.setKineticLaw(e_mathml);\n\t\t\te_list = (Element) e_kinetics.getElementsByTagName(\"listOfParameters\").item(0);\n\t\t\tif (e_list != null) {\n\t\t\t\tnodes2 = e_list.getElementsByTagName(\"parameter\");\n\t\t\t\tm = nodes2.getLength();\n\t\t\t\tfor (j = 0; j < m; j++) {\n\t\t\t\t\te = (Element) nodes2.item(j);\n\t\t\t\t\treaction.addParameter(e.getAttribute(\"id\"), e.getAttribute(\"value\"));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Add reaction to list\n\t\t\treactionList.add(reaction);\n\t\t}\n\t}\n\n\t/**\n\t * Calling point for command-line script:\n\t * This is probably the sbml2prism (found in etc/scripts)\n\t * But it can also be called as, e.g.: java -cp classes prism.SBML2Prism myfile.sbml 100\n\t * (100 denotes (integer) maximum for species population sizes, default is 100)\n\t * (also used to compute amounts from (real-valued) concentrations)\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tPrismLog errLog = new PrismPrintStreamLog(System.err);\n\t\ttry {\n\t\t\tif (args.length < 1) {\n\t\t\t\tSystem.err.println(\"Usage: sbml2prism <sbml_file> [max_amount]\");\n\t\t\t\tSystem.exit(1);\n\t\t\t}\n\t\t\tSBML2Prism sbml2prism = new SBML2Prism(errLog);\n\t\t\ttry {\n\t\t\t\tif (args.length > 1)\n\t\t\t\t\tsbml2prism.setMaxAmount(Integer.parseInt(args[1]));\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Invalid max amount \\\"\" + args[1] + \"\\\"\");\n\t\t\t}\n\t\t\tsbml2prism.load(new File(args[0]));\n\t\t\tsbml2prism.translate(System.out);\n\t\t} catch (PrismException e) {\n\t\t\terrLog.println(\"Error: \" + e.getMessage() + \".\");\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/StateAndValueConsumer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2018-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * Functional interface for a consumer of (state, value) pairs,\n * used in iteration over a StateValues vector, e.g., printing.\n */\n@FunctionalInterface\npublic interface StateAndValueConsumer\n{\n\n\t/**\n\t * Accept a state/value pair.\n\t * <br>\n\t * The values of the state variables are provided as integers,\n\t * with boolean values mapped to 0 and 1, respectively.\n\t * @param varValues an integer array with the state variable values\n\t * @param value the value for this state\n\t * @param stateIndex the state index (-1 indicates that no index information is available)\n\t */\n\tvoid accept(int[] varValues, double value, long stateIndex);\n\n}\n"
  },
  {
    "path": "prism/src/prism/StateAndValuePrinter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2018-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport parser.VarList;\nimport parser.type.TypeInt;\n\n/**\n * StateValueConsumer that formats the state/value pairs\n * and prints them to a PrismLog.\n */\npublic class StateAndValuePrinter implements StateAndValueConsumer\n{\n\t/** The log for output */\n\tprivate PrismLog outputLog;\n\t/** The VarList (for the type information on the variables) */\n\tprivate VarList varList;\n\n\t/** Flag: printSparse (only non-zero values) */\n\tboolean printSparse = true;\n\t/** Flag: printMatlab */\n\tboolean printMatlab = false;\n\t/** Flag: printStates (variable values on the model) */\n\tboolean printStates = true;\n\t/** Flag: printIndizes (indizes for the states) */\n\tboolean printIndices = true;\n\n\t/** Flag: Did we print at least one line? */\n\tprivate boolean hadOutput = false;\n\n\t/**\n\t * Constructor.\n\t * @param outputLog The log for output\n\t * @param varList The VarList (for the type information)\n\t * @param printSparse Print only non-zero values?\n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print the state variable values?\n\t * @param printIndices Print the state indices?\n\t */\n\tpublic StateAndValuePrinter(PrismLog outputLog, VarList varList, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices)\n\t{\n\t\tthis.outputLog = outputLog;\n\t\tthis.varList = varList;\n\n\t\tthis.printSparse = printSparse;\n\t\tthis.printMatlab = printMatlab;\n\t\tthis.printStates = printStates;\n\t\tthis.printIndices = printIndices;\n\t}\n\n\t@Override\n\tpublic void accept(int[] varValues, double value, long stateIndex)\n\t{\n\t\tif (printSparse && value == 0) {\n\t\t\t// skip zeroes\n\t\t\treturn;\n\t\t}\n\n\t\thadOutput = true;\n\n\t\t// Matlab\n\t\tif (printMatlab) {\n\t\t\tif (printSparse) {\n\t\t\t\toutputLog.println(\"v(\" + (stateIndex + 1) + \")=\" + value + \";\");\n\t\t\t} else {\n\t\t\t\toutputLog.println(value);\n\t\t\t}\n\t\t\treturn;\n\t\t}\n\n\t\t// PRISM format\n\t\tif (printIndices) {\n\t\t\toutputLog.print(stateIndex);\n\t\t}\n\t\tif (printStates) {\n\t\t\tif (printIndices) {\n\t\t\t\toutputLog.print(\":\");\n\t\t\t}\n\t\t\toutputLog.print(\"(\");\n\t\t\tint n = varList.getNumVars();\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tif (i > 0)\n\t\t\t\t\toutputLog.print(\",\");\n\t\t\t\toutputLog.print(varList.decodeFromInt(i, varValues[i]).toString());\n\t\t\t}\n\t\t\toutputLog.print(\")\");\n\t\t}\n\t\tif (printIndices || printStates) {\n\t\t\toutputLog.print(\"=\");\n\t\t}\n\t\toutputLog.println(value);\n\t}\n\n\t/** Return true if we printed at least one state/value pair. */\n\tpublic boolean hadOutput()\n\t{\n\t\treturn hadOutput;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/prism/StateVector.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\n/**\n * Interface for classes supporting read-access to state-indexed vectors of values. \n */\npublic interface StateVector\n{\n\t/**\n\t * Return the size of the vector (i.e. the number of elements).\n\t */\n\tpublic int getSize();\n\n\t/**\n\t * Get the value of the ith element of the vector, as an Object.\n\t */\n\tpublic Object getValue(int i) throws PrismNotSupportedException;\n\t\n\t/**\n\t * Clear the vector, i.e. free any used memory.\n\t */\n\tpublic void clear();\n\t\n\t/**\n\t * Print vector to a log/file (non-zero/non-false entries only).\n\t */\n\tpublic void print(PrismLog log, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices) throws PrismException;\n}\n"
  },
  {
    "path": "prism/src/prism/TestModelGenerator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.Arrays;\nimport java.util.Collections;\nimport java.util.List;\n\nimport explicit.ConstructModel;\nimport explicit.DTMCModelChecker;\nimport io.ModelExportFormat;\nimport io.ModelExportOptions;\nimport parser.State;\nimport parser.ast.DeclarationInt;\nimport parser.ast.DeclarationType;\nimport parser.ast.Expression;\nimport parser.ast.PropertiesFile;\nimport parser.type.Type;\nimport parser.type.TypeInt;\n\npublic class TestModelGenerator implements ModelGenerator<Double>\n{\n\tprotected State exploreState;\n\tprotected int x;\n\tprotected int n;\n\tprotected List<String> varNames = Arrays.asList(\"x\");\n\tprotected List<Type> varTypes = Arrays.asList((Type) TypeInt.getInstance());\n\n\tpublic TestModelGenerator(int n)\n\t{\n\t\tthis.n = n;\n\t}\n\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn ModelType.DTMC;\n\t}\n\n\t@Override\n\tpublic List<String> getVarNames()\n\t{\n\t\treturn varNames;\n\t}\n\n\t@Override\n\tpublic List<Type> getVarTypes()\n\t{\n\t\treturn varTypes;\n\t}\n\n\t@Override\n\tpublic DeclarationType getVarDeclarationType(int i) throws PrismException\n\t{\n\t\treturn new DeclarationInt(Expression.Int(0), Expression.Int(n));\n\t}\n\t\n\t@Override\n\tpublic List<String> getLabelNames()\n\t{\n\t\treturn Arrays.asList(\"goal\");\n\t}\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\treturn Collections.singletonList(null);\n\t}\n\n\t@Override\n\tpublic State getInitialState() throws PrismException\n\t{\n\t\tState s = new State(1);\n\t\ts.varValues[0] = n/2;\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic void exploreState(State exploreState) throws PrismException\n\t{\n\t\tthis.exploreState = exploreState;\n\t\tx = ((Integer) exploreState.varValues[0]).intValue();\n\t}\n\n\t@Override\n\tpublic int getNumChoices() throws PrismException\n\t{\n\t\treturn 1;\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int i) throws PrismException\n\t{\n\t\treturn x > 0 && x < n ? 2 : 1;\n\t}\n\n\t@Override\n\tpublic Object getTransitionAction(int i, int offset) throws PrismException\n\t{\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic Double getTransitionProbability(int i, int offset) throws PrismException\n\t{\n\t\treturn x > 0 && x < n ? 0.5 : 1.0;\n\t}\n\n\t@Override\n\tpublic State computeTransitionTarget(int i, int offset) throws PrismException\n\t{\n\t\tState s = new State(1);\n\t\tif (x == 0 || x == n) {\n\t\t\ts.varValues[i] = x;\n\t\t} else {\n\t\t\ts.varValues[i] = (offset == 0) ? x -1 : x + 1;\n\t\t}\n\t\treturn s;\n\t}\n\t\n\t@Override\n\tpublic boolean isLabelTrue(int i) throws PrismException\n\t{\n\t\tif (i == 0) {\n\t\t\treturn x == n;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Label number \\\"\" + i + \"\\\" not defined\");\n\t\t}\n\t}\n\n\tpublic static void main(String args[])\n\t{\n\t\ttry {\n\t\t\tPrism prism = new Prism(new PrismPrintStreamLog(System.out));\n\t\t\tprism.setMainLog(new PrismFileLog(\"stdout\"));\n\t\t\tprism.initialise();\n\n\t\t\tint test = 2;\n\n\t\t\tif (test == 1) {\n\t\t\t\t// Direct usage of model constructor/checker \n\t\t\t\tTestModelGenerator modelGen = new TestModelGenerator(10);\n\t\t\t\tConstructModel constructModel = new ConstructModel(prism);\n\t\t\t\tconstructModel.setSortStates(true);\n\t\t\t\texplicit.Model model = constructModel.constructModel(modelGen);\n\t\t\t\tmodel.exportToDotFile(new PrismFileLog(\"test.dot\"), null, true);\n\t\t\t\tDTMCModelChecker mc = new DTMCModelChecker(prism);\n\t\t\t\tPropertiesFile pf = prism.parsePropertiesString(modelGen, \"P=? [F \\\"goal\\\"]\");\n\t\t\t\tExpression expr = pf.getProperty(0);\n\t\t\t\tResult res = mc.check(model, expr);\n\t\t\t\tSystem.out.println(res);\n\t\t\t} else {\n\t\t\t\t// Perform model construction/checking via Prism\n\t\t\t\tTestModelGenerator modelGen2 = new TestModelGenerator(10);\n\t\t\t\tprism.loadModelGenerator(modelGen2);\n\t\t\t\tprism.exportBuiltModelTransitions(new File(\"test2.dot\"), new ModelExportOptions(ModelExportFormat.DOT));\n\t\t\t\tPropertiesFile pf = prism.parsePropertiesString(modelGen2, \"P=? [F x=10]\");\n\t\t\t\tExpression expr = pf.getProperty(0);\n\t\t\t\tResult res = prism.modelCheck(pf, expr);\n\t\t\t\tSystem.out.println(res);\n\t\t\t}\n\n\t\t\tprism.closeDown(true);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.err.println(\"Error: \" + e.getMessage());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/TestSim.java",
    "content": "package prism;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.Collections;\n\nimport javax.swing.event.ListSelectionEvent;\n\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport simulator.ModulesFileModelGenerator;\nimport simulator.SimulatorEngine;\nimport simulator.method.CIwidth;\nimport simulator.method.SimulationMethod;\n\npublic class TestSim\n{\n\tpublic static void main(String[] args)\n\t{\n\t\tnew TestSim().run();\n\t}\n\n\tpublic void run()\n\t{\n\t\ttry {\n\t\t\tPrismLog mainLog = new PrismFileLog(\"stdout\");\n\t\t\tPrism prism = new Prism(mainLog);\n\t\t\tprism.initialise();\n\t\t\t\n\t\t\tModulesFile modulesFile = prism.parseModelFile(new File(\"../prism-examples/simple/dice/dice.pm\"));\n\t\t\t\n\t\t\tPropertiesFile propertiesFile = prism.parsePropertiesFile(modulesFile, new File(\"../prism-examples/simple/dice/dice.pctl\"));\n\t\t\t\n\t\t\tSimulatorEngine simEngine = new SimulatorEngine(prism);\n\t\t\tModulesFileModelGenerator modelGen = new ModulesFileModelGenerator(modulesFile, prism);\n\t\t\tsimEngine.loadModel(modelGen, modelGen);\n\t\t\t\n\t\t\tSimulationMethod simMethod = new CIwidth(0.01, 1000);\n\t\t\tsimEngine.modelCheckMultipleProperties(propertiesFile, Collections.singletonList(propertiesFile.getProperty(1)), null, 10000, simMethod); \n\t\t\t\n\t\t\tsimEngine.createNewOnTheFlyPath();\n\t\t\tsimEngine.initialisePath(null);\n\t\t\tsimEngine.automaticTransitions(100, false);\n\n\t\t\t\n\t\t} catch (PrismException e) {\n\t\t\te.printStackTrace();\n\t\t} catch (FileNotFoundException e) {\n\t\t\te.printStackTrace();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Tile.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.List;\n\n/**\n * This class represents a face (or a part of face) of a Pareto curve or its\n * underapproximation, given\n * by it's corner points. The number of corner points must be equal to the dimension,\n * e.g. a line in a 2d, and a triangle in 3d. So for example a square face must\n * be represented as two triangle Tiles.\n */\npublic class Tile\n{\n\t/**\n\t * The corner points that determine this Tile\n\t */\n\tprotected ArrayList<Point> cornerPoints;\n\n\tprotected int dim;\n\t\n\t/**\n\t * Creates a new Tile with a given corner points\n\t * @param cornerPoints The number of corner points must be equal to the dimension.\n\t */\n\tpublic Tile(ArrayList<Point> cornerPoints)\n\t{\n\t\t//TODO check equal dimension\n\t\tthis.cornerPoints = cornerPoints;\n\t\tdim = this.cornerPoints.size();\n\t\tprojectionUpperBound = new boolean[dim];\n\t}\n\t\n\t/**\n\t * Returns a list containing the corner points representing this tile.\n\t */\n\tpublic ArrayList<Point> getCornerPoints()\n\t{\n\t\treturn this.cornerPoints;\n\t}\n\t\n\t/**\n\t * If true, this tile is already known to be part of a facet of a Pareto\n\t * curve, not just it's underapproximation.\n\t */\n\tprotected boolean upperBound;\n\tprotected boolean[] projectionUpperBound;\n\t\n\tprotected boolean hyperplaneSuggested;\n\n\t/**\n\t * Returns true if this tile is already known to be part of a facet of a Pareto\n\t * curve, not just its underapproximation.\n\t */\n\tpublic boolean isUpperBound(int index)\n\t{\n\t\tif (index == dim)\n\t\t\treturn this.upperBound;\n\t\telse\n\t\t\treturn this.projectionUpperBound[index];\n\t}\n\t\n\t/**\n\t * Returns true if {@code point} lies strictly above the hyperplane given\n\t * by this tile.\n\t */\n\tprotected boolean pointAboveHyperplane(Point point) throws PrismException\n\t{\n\t\t//System.out.println(\"t: \" + this);\n\t\tfor (Point cp : this.cornerPoints) {\n\t\t\tif (point.isCloseTo(cp))\n\t\t\t\treturn false;\n\t\t}\n\t\t\n\t\tPoint w = Tile.getWeightsForTile(this);\n\t\t\n\t\tdouble productTile = 0;\n\t\tfor (int j = 0; j < dim; j++)\n\t\t\tfor (int i = 0; i < point.getDimension(); i++)\n\t\t\t\tproductTile += w.getCoord(i) * this.cornerPoints.get(j).getCoord(i); \n\t\tproductTile = productTile/point.getDimension();\n\t\t\n\t\t\n\t\tdouble productPoint = 0;\n\t\tfor (int i = 0; i < point.getDimension(); i++)\n\t\t\tproductPoint += w.getCoord(i) * point.getCoord(i);\n\t\t//System.out.println(productPoint + \" \" + productTile + \" \" + (productPoint - productTile));\n\t\treturn productPoint >= productTile + Point.SMALL_NUMBER;\n\t}\n\t\n\t/**\n\t * Returns true if this tile will be changed when {@code point} is added\n\t * to a parent {@link TileList}. If {@code updateUpperBounds} is set, then also\n\t * the information about the tile lying on a pareto curve is updated\n\t *\n\t * @param updateUpperBounds If true, the new point does not split the tile, and\n\t * the tile's corresponding hyperplane was suggested, then the information\n\t * about the tile being an upper bound is updated. This can be either information\n\t * for the whole tile or its border lines, depending on {@code upperBoundsIndex} \n\t * @param upperBoundsIndex If equal to {@code dim}, when the information\n\t * about this tile being an upper bound is updated, the whole tile will be\n\t * marked as upper bound. If lower than {@code dim}, only the line having\n\t * zero value in {@code upperBoundsIndex}-th coordinate will be marked as upper\n\t * bound\n\t * \n\t * @throws PrismException\n\t * \n\t */\n\t\n\tpublic boolean processNewPoint(Point point, boolean updateUpperBounds, int upperBoundsIndex) throws PrismException\n\t{\n\t\tboolean ret = pointAboveHyperplane(point);\n\t\t\n\t\tif (ret) {\n\t\t\t//System.out.println(\"is affected: \" + this);\n\t\t\thyperplaneSuggested = false;\n\t\t\treturn true;\n\t\t} else {\n\t\t\tif (hyperplaneSuggested && updateUpperBounds) {\n\t\t\t\thyperplaneSuggested = false;\n\t\t\t\tif (upperBoundsIndex == this.cornerPoints.size()) {\n\t\t\t\t\tthis.upperBound = true;\n\t\t\t\t} else\n\t\t\t\t\tthis.projectionUpperBound[upperBoundsIndex] = true;\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\t\n\t}\n\t\n\t/**\n\t * Returns a list of tiles that should be added to the parent TileList\n\t * when {@code point} is added, replacing the current tile. For the computation\n\t * to be performed correctly, the list {@code otherPoints} must contain the\n\t * set of points from all affected tiles.\n\t * \n\t * @param tolerance When the newly created tiles will differ only in a point\n\t * which is {@code tolerance} far from the original tiles, the new tile will\n\t * be considered finished.\n\t */\n\tpublic List<Tile> splitByPoint(Point point, List<Point> otherPoints, double tolerance) throws PrismException\n\t{\n\t\tPoint weights = Tile.getWeightsForTile(this);\n\t\tdouble pointWeight = 0;\n\t\tfor (int i = 0; i< point.getDimension(); i++) {\n\t\t\tpointWeight += weights.getCoord(i) * point.getCoord(i);\n\t\t}\n\t\t\n\t\tdouble thisTileWeight = 0;\n\t\tfor (int i = 0; i< point.getDimension(); i++) {\n\t\t\tthisTileWeight += weights.getCoord(i) * this.getCornerPoints().get(0).getCoord(i);\n\t\t}\n\t\t\n\t\tboolean isClose = (pointWeight - thisTileWeight) < tolerance;\n\n\t\t//System.out.println(\"SPLITTING\");\n\t\tArrayList<Tile> tiles = new ArrayList<Tile>();\n\t\tfor (int i = 0; i < this.cornerPoints.size(); i++) {\n\t\t\tArrayList<Point> newPoints = (ArrayList<Point>) this.cornerPoints.clone();\n\t\t\tnewPoints.set(i, point);\n\t\t\tTile t = new Tile(newPoints);\n\t\t\t\n\t\t\tboolean onBorder=true;\n\t\t\tfor (int j = 0 ; j < t.cornerPoints.size(); j ++) {\n\t\t\t\tonBorder = true;\n\t\t\t\tfor (int k = 0 ; k < t.cornerPoints.size(); k ++)\n\t\t\t\t\tif (t.cornerPoints.get(k).getCoord(j) != 0.0) {\n\t\t\t\t\t\tonBorder =false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\tif (onBorder)\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\t//System.out.println(\"hyperplane:\" + t);\n\t\t\t\n\t\t\tboolean pointAboveExists = false;\n\t\t\tfor (Point p : otherPoints) {\n\t\t\t\t//System.out.println(\"point \" + p);\n\t\t\t\tif (t.pointAboveHyperplane(p)) {\n\t\t\t\t\tpointAboveExists = true;\n\t\t\t\t\t//System.out.println(\"is above\");\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\t//the tile is upper bound if the original was (this is not a contradiction,\n\t\t\t//due to the approx nature of computation even an upper bound tile could be\n\t\t\t//improved), or is upper bound if the change is rather small.\n\t\t\tif (isClose || this.isUpperBound(this.dim))\n\t\t\t\tt.upperBound = true;\n\t\t\t\n\t\t\tif (!onBorder && !pointAboveExists)\n\t\t\t\ttiles.add(t);\n\t\t}\n\t\t//System.out.println(\"RET: \" + tiles);\n\t\treturn tiles;\n\t}\n\t\n\t/**\n\t * Gets a weight vector representing the hyperplane given by the tile.\n\t * @param t The tile to compute the weight vector for.\n\t * @return\n\t */\n\tprotected static Point getWeightsForTile(Tile t)\n\t{\n\t\tint dim = t.cornerPoints.size();\n\t\t\n\t\t//First check if we have a nonzero point and remember one.\n\t\tint nonzeroIndex = -1;\n\t\tfor (int j = 0; j < dim; j++) {\n\t\t\tif (!t.cornerPoints.get(j).isZero()) {\n\t\t\t\tnonzeroIndex = j;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\t\n\t\t//If all are zero, we return anything meaningful\n\t\tif (nonzeroIndex == -1) {\n\t\t\tdouble[] pointCoords = new double[dim];\n\t\t\tpointCoords[0] = 1;\n\t\t\treturn new Point(pointCoords);\n\t\t}\n\t\t\n\t\t\n\t\tdouble[][] d = new double [dim][dim];\n\t\tdouble[] b = new double [dim];\n\t\t\n\t\tPoint pFixed = t.cornerPoints.get(dim-1);\n\t\tfor (int j = 0; j < dim-1; j++) {\n\t\t\tPoint p = t.cornerPoints.get(j);\n\t\t\tfor (int i = 0; i < dim; i++) {\n\t\t\t\td[j][i] = p.getCoord(i) - pFixed.getCoord(i);\n\t\t\t}\n\t\t\tb[j] = 0;\n\t\t}\n\n\t\tfor (int i = 0; i < dim; i++) {\n\t\t\td[dim-1][i] = 1;\n\t\t}\n\t\tb[dim-1] = 1;\n\t\t\n\t\tdouble[] ret = MultiObjUtils.solveEqns(d, b);\n\t\tdouble[] pointCoords = new double[dim];\n\t\tfor (int i = 0; i < dim; i++)\n\t\t\tpointCoords[i] = ret[i];\t\n\t\t//System.out.println(\"returned points: \" + Arrays.toString(pointCoords));\n\t\t\n\t\treturn new Point(pointCoords).normalize();\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tStringBuffer sb = new StringBuffer();\n\t\tsb.append('{');\n\t\tfor (int i = 0; i < this.cornerPoints.size() - 1; i++) {\n\t\t\tsb.append(this.cornerPoints.get(i).toString());\n\t\t\tsb.append(\"; \");\n\t\t}\n\t\tsb.append(this.cornerPoints.get(this.cornerPoints.size()-1).toString());\n\t\tsb.append('}');\n\t\treturn sb.toString();\n\t}\n\t\n\t\n\t/**\n\t * True if there is one of the boundaries of the Tile is\n\t * a line orthogonal to {@code index}'s axis\n\t */\n\tpublic boolean liesOnBoundary(int index) {\n\t\tint count = 0;\n\t\t\n\t\tfor (Point p : this.cornerPoints) {\n\t\t\tif (p.getCoord(index) == 0)\n\t\t\t\tcount++;\n\t\t}\n\t\t\n\t\t//System.out.println(count);\n\t\t\n\t\t/*//this can happen in fact in all zeros\n\t\t  if (count == 3) {\n\t\t\tthrow new Error(\"Error in design of Pareto curve algorithm. The whole Tile lies on a boundary.\");\n\t\t}*/\n\t\t\n\t\treturn (count >= 2);\n\t\t\t\t\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/TileList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.ast.Expression;\n\n/**\n * This class represent a list of tiles which have corners in Pareto points,\n * and which represent an under-approximation of the Pareto curve.\n */\npublic class TileList\n{\n\t/**\n\t * Threshold for approximation of the Pareto curve.\n\t */\n\tprivate double tolerance;\n\n\t/**\n\t * This is used when printing the tileList to the user. The information\n\t * we need are whether the reward is min (to multiply by -1) and\n\t * whether the probability is min (to do 1-value) \n\t */\n\tprivate OpsAndBoundsList opsAndBoundsList;\n\n\tpublic OpsAndBoundsList getOpsAndBoundsList()\n\t{\n\t\treturn this.opsAndBoundsList;\n\t}\n\n\t/**\n\t * This is where a TileLists are stored to be later retrieved in GUI.\n\t * It is a workaround for the fact that Pareto curve can't be \n\t * returned in any reasonable way.\n\t * \n\t * To ensure correct concurrent behaviour, object accessing any stored tile lists\n\t * or elements should synchronise on this object;\n\t */\n\tpublic static List<TileList> storedTileLists;\n\n\tpublic static List<TileList> getStoredTileLists()\n\t{\n\t\treturn storedTileLists;\n\t}\n\n\t/**\n\t * Formulas for X and Y axes (or multi-obj formulas) of the corresponding\n\t * elements of storedTileLists.\n\t */\n\tpublic static List<Expression> storedFormulasX;\n\tpublic static List<Expression> storedFormulasY;\n\tpublic static List<List<Expression>> storedFormulas;\n\n\tpublic static List<Expression> getStoredFormulasX()\n\t{\n\t\treturn storedFormulasX;\n\t}\n\n\tpublic static List<Expression> getStoredFormulasY()\n\t{\n\t\treturn storedFormulasY;\n\t}\n\n\tpublic static List<List<Expression>> getStoredFormulas()\n\t{\n\t\treturn storedFormulas;\n\t}\n\n\t/** Removes all stored tile list and associated formulas */\n\tpublic static void clearStoredTileLists()\n\t{\n\t\tTileList.storedFormulasX.clear();\n\t\tTileList.storedFormulasY.clear();\n\t\tTileList.storedFormulas.clear();\n\t\tTileList.storedTileLists.clear();\n\t}\n\n\tstatic {\n\t\tstoredFormulasX = new ArrayList<Expression>();\n\t\tstoredFormulasY = new ArrayList<Expression>();\n\t\tstoredFormulas = new ArrayList<List<Expression>>();\n\t\tstoredTileLists = new ArrayList<TileList>();\n\t}\n\n\tprotected int currentProjectionIndex = 0;\n\t/**\n\t * This list holds all tiles of this TileList.\n\t */\n\tprotected ArrayList<Tile> list;\n\t/**\n\t * Initial tile passed in constructor.\n\t * Currently only used for drawing nice tikz pics\n\t */\n\tprotected Tile initialTile;\n\t/**\n\t * Dimension of the space, determined from the initial tile.\n\t */\n\tprotected int dim;\n\n\t/**\n\t * Creates a new instance of the TileList, originally containing only one\n\t * tile, {@code initialTile}.\n\t * @param initialTile The first {@link Tile} to put in a list.\n\t */\n\tpublic TileList(Tile initialTile, OpsAndBoundsList opsAndBounds, double tolerance)\n\t{\n\t\tthis.dim = initialTile.cornerPoints.get(0).getDimension();\n\t\tthis.initialTile = initialTile;\n\t\tthis.list = new ArrayList<Tile>();\n\t\tthis.list.add(initialTile);\n\t\tthis.opsAndBoundsList = opsAndBounds;\n\t\tthis.tolerance = tolerance;\n\n\t\t//this is a HACK so that we don't try projections in 2 dimensions.\n\t\t//these are not needed since projections are extremes in 1 dim,\n\t\t//which were done for initial tile\n\t\tif (this.dim == 2) {\n\t\t\tthis.currentProjectionIndex = 2;\n\t\t}\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tList<Point> li = getRealPoints();\n\t\treturn li.toString();\n\t}\n\n\t/**\n\t * Returns a weight vector which could yield a new Pareto point when used.\n\t * {@code null} is returned if no candidate point exists.\n\t * \n\t * TODO: currently just calls another method.\n\t */\n\tpublic Point getCandidateHyperplane()\n\t{\n\t\treturn getFreshRealCandidateHyperplane();\n\t}\n\n\t/**\n\t * Queries the tiles of this TileList to get a new weight vector which \n\t * could yield a new pareto point when used. {@code null} is returned\n\t * if no candidate point exists. It gives absolute preference to\n\t * weight vectors having zero in one of the coordinates.\n\t */\n\tprivate Point getFreshRealCandidateHyperplane()\n\t{\n\t\t//we have to exhaust the boundaries first\n\t\twhile (this.currentProjectionIndex < this.dim) {\n\t\t\tfor (Tile t : list) {\n\t\t\t\tif (!t.isUpperBound(this.currentProjectionIndex) && t.liesOnBoundary(this.currentProjectionIndex)) {\n\t\t\t\t\tt.hyperplaneSuggested = true;\n\t\t\t\t\t//System.out.println(\"fresh candidate hyperplane:\" + t + \"with weight \" + Tile.getWeightsForTile(t));\n\t\t\t\t\tPoint ret = Tile.getWeightsForTile(t);\n\n\t\t\t\t\t//We want to make sure we optimize on the boundary,\n\t\t\t\t\t//so we make the point parallel to an axis. But at\n\t\t\t\t\t//the same time we need to make sure it's not zero weight.\n\t\t\t\t\tPoint vert = ret.clone();\n\t\t\t\t\tvert.setCoord(this.currentProjectionIndex, 0);\n\t\t\t\t\treturn (vert.isZero()) ? ret : vert.normalize();\n\t\t\t\t}\n\t\t\t\t/*else {\n\t\t\t\t\tSystem.out.println(\"does not lie on \" + this.currentProjectionIndex + \" boundary: \" + t);\n\t\t\t\t}*/\n\t\t\t}\n\n\t\t\tthis.currentProjectionIndex++;\n\t\t\t//System.out.println(\"Increasing projection index to \" + this.currentProjectionIndex);\n\t\t\t//System.out.println(this.toString());\n\t\t}\n\n\t\t//now the points inside the quadrant\n\t\tfor (Tile t : list) {\n\t\t\tif (!t.isUpperBound(dim)) {\n\t\t\t\tt.hyperplaneSuggested = true;\n\t\t\t\t//System.out.println(\"fresh candidate hyperplane:\" + t + \"with weight \" + Tile.getWeightsForTile(t));\n\t\t\t\treturn Tile.getWeightsForTile(t);\n\t\t\t}\n\t\t}\n\n\t\treturn null;\n\t}\n\n\t/**\n\t * Returns the number of different points that form the tiles of this\n\t * TileList. The implementation is rather inefficient and is intended\n\t * only for debugging purposes.\n\t */\n\tpublic int getNumberOfDifferentPoints()\n\t{\n\t\treturn this.getPoints().size();\n\t}\n\n\t/**\n\t * Returns the points that form the tiles of this\n\t * TileList. The implementation is rather inefficient and is intended\n\t * only for debugging purposes.\n\t */\n\tpublic List<Point> getPoints()\n\t{\n\t\tArrayList<Point> a = new ArrayList<Point>();\n\t\tfor (Tile t : this.list) {\n\t\t\tfor (Point p : t.cornerPoints)\n\t\t\t\tif (!a.contains(p))\n\t\t\t\t\ta.add(p);\n\t\t}\n\t\treturn a;\n\t}\n\n\t/**\n\t * Returns the points that form the tiles of this\n\t * TileList, omitting the points that are covered by other points.\n\t * The implementation is rather inefficient and is intended\n\t * only for debugging purposes.\n\t */\n\tpublic List<Point> getPointsWithoutCovered()\n\t{\n\t\tList<Point> a = getPoints();\n\n\t\tboolean changed;\n\t\tdo {\n\t\t\tchanged = false;\n\t\t\tfor (int i = 0; i < a.size(); i++) {\n\t\t\t\tboolean covered = false;\n\t\t\t\tfor (int j = 0; j < a.size(); j++) {\n\t\t\t\t\tif (i==j)\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\tif (a.get(i).isCoveredBy(a.get(j))) {\n\t\t\t\t\t\tcovered = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (covered) {\n\t\t\t\t\ta.remove(i);\n\t\t\t\t\tchanged = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\n\t\t} while(changed);\n\t\t\n\t\treturn a;\n\t}\n\n\t/**\n\t * Returns the points that form the actual Pareto curve (modifying the points from tiles\n\t * according to the operator bound changes).\n\t * The implementation is rather inefficient and is intended\n\t * only for debugging purposes.\n\t */\n\tpublic List<Point> getRealPoints()\n\t{\n\t\tList<Point> a = this.getPointsWithoutCovered();\n\t\tif (this.opsAndBoundsList != null) {\n\t\t\tfor (int i = 0; i < a.size(); i++) {\n\t\t\t\tPoint p = a.get(i).toRealProperties(this.opsAndBoundsList);\n\t\t\t\ta.set(i,p);\n\t\t\t}\n\t\t}\n\t\treturn a;\n\t}\n\n\t/**\n\t * Adds a newly discovered point to this TileList. This basically means that\n\t * some tiles will be split into smaller tiles. Also makes sure that the invariant\n\t * \"approximation is downward closed\" is maintained true.\n\t */\n\tpublic void addNewPoint(Point point) throws PrismException\n\t{\n\t\t//first create the projection to the boundary\n\t\tif (this.currentProjectionIndex < this.dim && point.getCoord(this.currentProjectionIndex) > 0.0) {\n\t\t\tPoint projectionPoint = point.clone();\n\t\t\tprojectionPoint.setCoord(this.currentProjectionIndex, 0.0);\n\t\t\tsplitTilesByPoint(projectionPoint, false);\n\t\t} else {\n\t\t\tsplitTilesByPoint(point, this.currentProjectionIndex == dim);\n\t\t}\n\t}\n\n\t/**\n\t * Splits the Tiles using the new point. This basically means that\n\t * some tiles will be replaced by smaller tiles. Note that this method\n\t * does <em>not</em> check whether the tiles form a downward closed\n\t * polyhedron, hence it shouldn't be called directly, but indirecly by\n\t * calling {@link #addNewPoint(Point)}.\n\t * \n\t * @param isRealyFoundPoint False if {@code point} is just a projection of a point found.\n\t */\n\tprotected void splitTilesByPoint(Point point, boolean isRealyFoundPoint) throws PrismException\n\t{\n\t\t//System.out.println(\"really processing point \" + point);\n\n\t\tArrayList<Tile> affectedTiles = new ArrayList<Tile>();\n\t\tfor (Tile t : this.list) {\n\t\t\tboolean affected = t.processNewPoint(point, true, this.currentProjectionIndex);\n\t\t\tif (affected)\n\t\t\t\taffectedTiles.add(t);\n\t\t}\n\n\t\tArrayList<Point> allPoints = new ArrayList<Point>();\n\t\tfor (Tile t : affectedTiles) {\n\t\t\tallPoints.addAll(t.cornerPoints);\n\t\t}\n\t\t//System.out.println(\"allpoints \" + allPoints);\n\n\t\tfor (Tile t : affectedTiles) {\n\t\t\tlist.remove(t);\n\t\t\t//System.out.println(\"removing \" + t);\n\t\t\tList<Tile> l = t.splitByPoint(point, allPoints, this.tolerance);\n\t\t\t//System.out.println(\"adding \" + l);\n\t\t\tthis.list.addAll(l);\n\t\t}\n\n\t\t//System.out.println(this.toString());\n\t}\n\n\t/**\n\t * returns the dimension of the points in this TileList\n\t */\n\tpublic int getDimension()\n\t{\n\t\treturn this.dim;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/UndefinedConstants.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.Collection;\nimport java.util.List;\nimport java.util.Vector;\n\nimport parser.*;\nimport parser.ast.*;\nimport parser.type.*;\n\n/**\n * Class to handle the undefined constants in model and/or properties file.\n * This may not be *all* of the constants in the file(s); it may be just\n * the ones that are required to execute model checking or some other task.\n * Really, the main purpose of this class is to manage an \"experiment\",\n * i.e. to iterate through several different values of one or more constants,\n * but this includes the special case where all undefined constants are given a single value.\n */\npublic class UndefinedConstants\n{\n\t// info used to construct this object\n\t// parsed model/properties files\n\tprivate ModulesFile modulesFile = null;\n\tprivate PropertiesFile propertiesFile = null;\n\t// optionally, specific properties to get constants from\n\tprivate List<Property> props = null;\n\t// just get constants from labels (in properties file)?\n\tprivate boolean justLabels = false;\n\t// computation / evaluation of constants via double or exact arithmetic?\n\tprivate boolean exact = false;\n\n\t// info about constants\n\tprivate int mfNumConsts = 0;\n\tprivate List<DefinedConstant> mfConsts = null;\n\tprivate int pfNumConsts = 0;\n\tprivate List<DefinedConstant> pfConsts = null;\n\n\t// stuff for iterating through constant values\n\tprivate Values mfValues = null;\n\tprivate Values pfValues = null;\n\n\t// class-wide storage for info from -const switch\n\tprivate Vector<String> constSwitchNames;\n\tprivate Vector<String> constSwitchLows;\n\tprivate Vector<String> constSwitchHighs;\n\tprivate Vector<String> constSwitchSteps;\n\n\t/**\n\t * Construct information about undefined constants from a model and/or properties file.\n\t * If either is not required, it can be left as null. All undefined constants,\n\t * whether used or not, are assumed to be required to be provided.\n\t */\n\tpublic UndefinedConstants(ModulesFile modulesFile, PropertiesFile propertiesFile)\n\t{\n\t\tthis(modulesFile, propertiesFile, false);\n\t}\n\n\t/**\n\t * Construct information about undefined constants from a model and/or properties file.\n\t * If either is not required, it can be left as null. If {@code justLabels} is false,\n\t * all constants, whether used or not, are assumed to be required to be provided.\n\t * If {@code justLabels} is true, only properties file constants that are needed for labels are.\n\t */\n\tpublic UndefinedConstants(ModulesFile modulesFile, PropertiesFile propertiesFile, boolean justLabels)\n\t{\n\t\tsetModulesFile(modulesFile);\n\t\tsetPropertiesFile(propertiesFile);\n\t\tsetJustLabels(justLabels);\n\t\tinitialise();\n\t}\n\n\t/**\n\t * Construct information about undefined constants for a specific property.\n\t * It is assumed that all undefined constants from the model file are needed,\n\t * plus any from the properties file that are use in the property {@code prop}.  \n\t */\n\tpublic UndefinedConstants(ModulesFile modulesFile, PropertiesFile propertiesFile, Property prop)\n\t{\n\t\tsetModulesFile(modulesFile);\n\t\tsetPropertiesFile(propertiesFile);\n\t\taddProperty(prop);\n\t\tinitialise();\n\t}\n\n\t/**\n\t * Construct information about undefined constants for specific properties.\n\t * It is assumed that all undefined constants from the model file are needed,\n\t * plus any from the properties file that are use in the properties {@code props}.  \n\t */\n\tpublic UndefinedConstants(ModulesFile modulesFile, PropertiesFile propertiesFile, List<Property> props)\n\t{\n\t\tsetModulesFile(modulesFile);\n\t\tsetPropertiesFile(propertiesFile);\n\t\tsetProperties(props);\n\t\tinitialise();\n\t}\n\n\t/**\n\t * Reconstruct information about undefined constants from a ResultCollection.\n\t * This information is necessarily incomplete.\n\t * Hence, consider the information a mockup and do not use the instance to run an experiment.\n\t * The provided property does not need to correspond to the data.\n\t * It has only a decorative function. \n\t * @param property a property to associate with the results\n\t * @param results the ResultsCollection from which the undefined constants are extracted\n\t */\n\t@SuppressWarnings(\"rawtypes\")\n\tpublic UndefinedConstants(Property property, ResultsCollection results)\n\t{\n\t\tsetModulesFile(null);\n\t\tsetPropertiesFile(null);\n\t\tsetProperties(List.of(property));\n\t\t// consider all constants pf constants as we do not know the model file\n\t\tVector<DefinedConstant> constants = results.getRangingConstants();\n\t\tmfNumConsts = 0;\n\t\tpfNumConsts = constants.size();\n\t\t// create storage for info about constant definitions\n\t\tmfConsts = new ArrayList<DefinedConstant>(mfNumConsts);\n\t\tpfConsts = new ArrayList<DefinedConstant>(pfNumConsts);\n\t\t// we can add constants safely as they are immutable except for the temporary value\n\t\tpfConsts.addAll(constants);\n\t}\n\n\t// Setters\n\n\tpublic void setModulesFile(ModulesFile modulesFile)\n\t{\n\t\tthis.modulesFile = modulesFile;\n\t}\n\n\tpublic void setPropertiesFile(PropertiesFile propertiesFile)\n\t{\n\t\tthis.propertiesFile = propertiesFile;\n\t}\n\n\tpublic void setProperties(List<Property> props)\n\t{\n\t\tthis.props = props;\n\t}\n\n\tpublic void addProperty(Property prop)\n\t{\n\t\tif (props == null)\n\t\t\tprops = new ArrayList<Property>();\n\t\tprops.add(prop);\n\t}\n\n\tpublic void setJustLabels(boolean justLabels)\n\t{\n\t\tthis.justLabels = justLabels;\n\t}\n\n\tpublic void setExactMode(boolean exact)\n\t{\n\t\tthis.exact = exact;\n\t}\n\n\t/**\n\t * Initialise this UndefinedConstants object:\n\t * determine which constants are undefined and then set up data structures.\n\t */\n\tpublic void initialise()\n\t{\n\t\tList<String> mfv, pfv;\n\t\t// determine which constants are undefined\n\t\tmfv = (modulesFile == null) ? new ArrayList<>() : modulesFile.getUndefinedConstants();\n\t\tif (propertiesFile == null) {\n\t\t\tpfv = new ArrayList<>();\n\t\t} else {\n\t\t\tif (props == null) {\n\t\t\t\tif (justLabels) {\n\t\t\t\t\tpfv = propertiesFile.getUndefinedConstantsUsedInLabels();\n\t\t\t\t\tpfv = orderConstantsByPropertiesFile(pfv, propertiesFile);\n\t\t\t\t} else {\n\t\t\t\t\tpfv = propertiesFile.getUndefinedConstants();\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tpfv = propertiesFile.getUndefinedConstantsUsedInProperties(props);\n\t\t\t\tpfv = orderConstantsByPropertiesFile(pfv, propertiesFile);\n\t\t\t}\n\t\t}\n\t\t// create data structures\n\t\tsetUpDataStructures(mfv, pfv);\n\t}\n\n\t/**\n\t * Create a new copy of a list of constant names, sorted by their occurrence in a PropertiesFile. \n\t */\n\tprivate List<String> orderConstantsByPropertiesFile(List<String> oldList, PropertiesFile propertiesFile)\n\t{\n\t\tList<String> newList = new ArrayList<>();\n\t\tList<String> pfList = propertiesFile.getUndefinedConstants();\n\t\tfor (String s : pfList) {\n\t\t\tif (oldList.contains(s))\n\t\t\t\tnewList.add(s);\n\t\t}\n\t\treturn newList;\n\t}\n\n\t/**\n\t * Set up data structures (as required by constructor methods)\n\t */\n\tprivate void setUpDataStructures(List<String> mfv, List<String> pfv)\n\t{\n\t\tint i;\n\t\tString s;\n\t\t// determine how many constants there are\n\t\tmfNumConsts = mfv.size();\n\t\tpfNumConsts = pfv.size();\n\t\t// create storage for info about constant definitions\n\t\tmfConsts = new ArrayList<DefinedConstant>(mfNumConsts);\n\t\tfor (i = 0; i < mfNumConsts; i++) {\n\t\t\ts = mfv.get(i);\n\t\t\tType type = modulesFile.getConstantList().getConstantType(modulesFile.getConstantList().getConstantIndex(s));\n\t\t\tmfConsts.add(new DefinedConstant.Undefined(s, type));\n\t\t}\n\t\tpfConsts = new ArrayList<DefinedConstant>(pfNumConsts);\n\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\ts = pfv.get(i);\n\t\t\tType type = propertiesFile.getConstantList().getConstantType(propertiesFile.getConstantList().getConstantIndex(s));\n\t\t\tpfConsts.add(new DefinedConstant.Undefined(s, type));\n\t\t}\n\t\t// initialise storage just created\n\t\tclearAllDefinitions();\n\t}\n\n\t/**\n\t * Remove a constant. This is used if you decide that you do not want to treat\n\t * some constant as undefined once you have created the UndefinedConstants object.\n\t * @return whether a constant was actually removed.  \n\t */\n\tpublic boolean removeConstant(String constName)\n\t{\n\t\tint i = getMFConstIndex(constName);\n\t\tif (i != -1) {\n\t\t\tmfNumConsts--;\n\t\t\tmfConsts.remove(i);\n\t\t\treturn true;\n\t\t} else {\n\t\t\ti = getPFConstIndex(constName);\n\t\t\tif (i != -1) {\n\t\t\t\tpfNumConsts--;\n\t\t\t\tpfConsts.remove(i);\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Remove some constants. This is used if you decide that you do not want to treat\n\t * some constants as undefined once you have created the UndefinedConstants object.\n\t * @return how many constants were actually removed.\n\t */\n\tpublic int removeConstants(String constNames[])\n\t{\n\t\treturn removeConstants(Arrays.asList(constNames));\n\t}\n\n\t/**\n\t * Remove some constants. This is used if you decide that you do not want to treat\n\t * some constants as undefined once you have created the UndefinedConstants object.\n\t * @return how many constants were actually removed.\n\t */\n\tpublic int removeConstants(Collection<String> constNames)\n\t{\n\t\tint removed = 0;\n\t\tfor (String name : constNames) {\n\t\t\tif (removeConstant(name))\n\t\t\t\tremoved++;\n\t\t}\n\t\treturn removed;\n\t}\n\n\t// Accessor methods for info about undefined constants\n\n\tpublic int getMFNumUndefined()\n\t{\n\t\treturn mfNumConsts;\n\t}\n\n\tpublic int getPFNumUndefined()\n\t{\n\t\treturn pfNumConsts;\n\t}\n\n\tpublic String getMFUndefinedName(int i)\n\t{\n\t\treturn mfConsts.get(i).getName();\n\t}\n\n\tpublic String getPFUndefinedName(int i)\n\t{\n\t\treturn pfConsts.get(i).getName();\n\t}\n\n\tpublic Type getMFUndefinedType(int i)\n\t{\n\t\treturn mfConsts.get(i).getType();\n\t}\n\n\tpublic Type getPFUndefinedType(int i)\n\t{\n\t\treturn pfConsts.get(i).getType();\n\t}\n\n\tpublic int getMFConstIndex(String s)\n\t{\n\t\tfor (int i = 0; i < mfNumConsts; i++) {\n\t\t\tif (mfConsts.get(i).getName().equals(s))\n\t\t\t\treturn i;\n\t\t}\n\t\treturn -1;\n\t}\n\n\tpublic int getPFConstIndex(String s)\n\t{\n\t\tfor (int i = 0; i < pfNumConsts; i++) {\n\t\t\tif (pfConsts.get(i).getName().equals(s))\n\t\t\t\treturn i;\n\t\t}\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Clear definitions of all undefined constants.\n\t */\n\tpublic void clearAllDefinitions()\n\t{\n\t\tint i;\n\n\t\t// constants from model file\n\t\tfor (i = 0; i < mfNumConsts; i++) {\n\t\t\tmfConsts.set(i, mfConsts.get(i).clear());\n\t\t\t;\n\t\t}\n\t\t// constants from properties file\n\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\tpfConsts.set(i, pfConsts.get(i).clear());\n\t\t}\n\t}\n\n\t/**\n\t * Define all undefined constants using the argument to the prism -const command line switch.\n\t * (i.e. format is \"x=1,y=1:100,z=1:10:100,b=true\")\n\t */\n\tpublic void defineUsingConstSwitch(String constSwitch) throws PrismException\n\t{\n\t\tint i;\n\t\tString name;\n\t\tboolean dupe;\n\t\tboolean useAll = false;\n\n\t\t// clear any previous definitions\n\t\tclearAllDefinitions();\n\n\t\t// parse and store info from switch argument\n\t\tparseConstSwitch(constSwitch);\n\n\t\t// if there are no undefined consts...\n\t\tif (useAll && (mfNumConsts + pfNumConsts == 0)) {\n\t\t\tif (constSwitchNames.size() > 0) {\n\t\t\t\tthrow new PrismException(\"There are no undefined constants to define\");\n\t\t\t}\n\t\t\treturn;\n\t\t}\n\n\t\t// go thru parts of -const switch one by one\n\t\tfor (i = 0; i < constSwitchNames.size(); i++) {\n\n\t\t\t// get name\n\t\t\tname = constSwitchNames.elementAt(i);\n\n\t\t\t// define constant using info from switch\n\t\t\tdupe = defineConstant(name, constSwitchLows.elementAt(i), constSwitchHighs.elementAt(i), constSwitchSteps.elementAt(i), useAll);\n\n\t\t\t// check for duplication\n\t\t\tif (dupe) {\n\t\t\t\tthrow new PrismException(\"Duplicate definitions for undefined constant \\\"\" + name + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t// check all undefined consts have now been defined\n\t\tcheckAllDefined();\n\n\t\t// initialise info for iterating\n\t\tinitialiseIterators();\n\t}\n\n\t/**\n\t * Parse -const switch string and store info.\n\t */\n\tprivate void parseConstSwitch(String constSwitch) throws PrismException\n\t{\n\t\tint i, j;\n\t\tString parts[], args[];\n\n\t\t// create storage for info\n\t\tconstSwitchNames = new Vector<String>();\n\t\tconstSwitchLows = new Vector<String>();\n\t\tconstSwitchHighs = new Vector<String>();\n\t\tconstSwitchSteps = new Vector<String>();\n\n\t\t// if string is null, nothing more to do\n\t\tif (constSwitch == null)\n\t\t\treturn;\n\n\t\t// split into comma separated parts...\n\t\tparts = constSwitch.split(\",\");\n\n\t\t// ...and treat each separately\n\t\tfor (i = 0; i < parts.length; i++) {\n\n\t\t\t// ignore blanks\n\t\t\tif (parts[i].length() == 0)\n\t\t\t\tcontinue;\n\n\t\t\t// split either size of \"=\", store lhs (name)\n\t\t\tj = parts[i].indexOf('=');\n\t\t\tif (j < 1 || j + 2 > parts[i].length())\n\t\t\t\tthrow new PrismException(\"Invalid format in definition of undefined constants\");\n\t\t\tconstSwitchNames.add(parts[i].substring(0, j));\n\n\t\t\t// check for trailing colon(s)\n\t\t\t// this is a formatting error not detected by split(\":\") below\n\t\t\tif (parts[i].charAt(parts[i].length() - 1) == ':')\n\t\t\t\tthrow new PrismException(\"Invalid format in definition of undefined constants\");\n\n\t\t\t// split into colon separated parts\n\t\t\targs = parts[i].substring(j + 1).split(\":\");\n\t\t\t// simple case - no colons, e.g. x=0\n\t\t\tif (args.length == 1) {\n\t\t\t\tconstSwitchLows.add(args[0]);\n\t\t\t\tconstSwitchHighs.add(null);\n\t\t\t\tconstSwitchSteps.add(null);\n\t\t\t}\n\t\t\t// range, e.g. x=0:10\n\t\t\telse if (args.length == 2) {\n\t\t\t\tconstSwitchLows.add(args[0]);\n\t\t\t\tconstSwitchHighs.add(args[1]);\n\t\t\t\tconstSwitchSteps.add(null);\n\t\t\t}\n\t\t\t// range with step, e.g. x=0:2:10\n\t\t\telse if (args.length == 3) {\n\t\t\t\tconstSwitchLows.add(args[0]);\n\t\t\t\tconstSwitchHighs.add(args[2]);\n\t\t\t\tconstSwitchSteps.add(args[1]);\n\t\t\t}\n\t\t\t// error\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Invalid format in definition of undefined constants\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Define value for a single undefined constant.\n\t *  Returns whether or not an existing definition was overwritten.\n\t *\tActually just helper method for more general method {@link #defineConstant(String, String, String, String) below}.\n\t *  \n\t *  The method {@link #initialiseIterators() initialiseIterators} must be called after all constants are defined.\n\t *\n\t *  @param name The name of the constant.\n\t *  @param val The value to be assigned.\n\t *  \n\t *  @return True if the constant was defined before.\n\t */\n\tpublic boolean defineConstant(String name, String val) throws PrismException\n\t{\n\t\treturn defineConstant(name, val, null, null, false);\n\t}\n\n\t/** Define value for a single undefined constant.\n\t *  Returns whether or not an existing definition was overwritten.\n\t *\n\t *  The method {@link #initialiseIterators() initialiseIterators} must be called after all constants are defined.\n\t *\t\n\t *  @param name The name of the constant.\n\t *  @param sl If sh are ss are null, this is the value to be assigned. Otherwise, it is the lower bound for the range.\n\t *  @param sh The upper bound for the range.\n\t *  @param ss The step for the values. Null means 1.\n\t *  \n\t *  @return True if the constant was defined before.\n\t */\n\tpublic boolean defineConstant(String name, String sl, String sh, String ss) throws PrismException\n\t{\n\t\treturn defineConstant(name, sl, sh, ss, false);\n\t}\n\n\t/** Define value for a single undefined constant.\n\t *  Returns whether or not an existing definition was overwritten.\n\t *\n\t *  The method {@link #initialiseIterators() initialiseIterators} must be called after all constants are defined.\n\t *\t\n\t *  @param name The name of the constant.\n\t *  @param sl If sh are ss are null, this is the value to be assigned. Otherwise, it is the lower bound for the range.\n\t *  @param sh The upper bound for the range.\n\t *  @param ss The step for the values. Null means 1.\n\t *  @param useAll If true, throw an exception if {@code name} does not need to be defined\n\t *  \n\t *  @return True if the constant was defined before.\n\t */\n\tpublic boolean defineConstant(String name, String sl, String sh, String ss, boolean useAll) throws PrismException\n\t{\n\t\tint index = 0;\n\t\tboolean overwrite = false; // did definition exist already?\n\n\t\t// find out if const is in model or properties file (or neither)\n\t\t// also check for overwriting\n\t\tindex = getMFConstIndex(name);\n\t\tif (index != -1) {\n\t\t\t// const is in modules file\n\t\t\toverwrite = (mfConsts.get(index).isDefined());\n\t\t\tmfConsts.set(index, mfConsts.get(index).define(sl, sh, ss, exact));\n\t\t} else {\n\t\t\tindex = getPFConstIndex(name);\n\t\t\tif (index != -1) {\n\t\t\t\t// const is in properties file\n\t\t\t\toverwrite = (pfConsts.get(index).isDefined());\n\t\t\t\tpfConsts.set(index, pfConsts.get(index).define(sl, sh, ss, exact));\n\t\t\t} else {\n\t\t\t\t// If we are required to use all supplied const values, check for this\n\t\t\t\t// (by default we don't care about un-needed or non-existent const values)\n\t\t\t\tif (useAll)\n\t\t\t\t\tthrow new PrismException(\"\\\"\" + name + \"\\\" is not an undefined constant\");\n\t\t\t\t// But if an unused supplied value clashes with a defined constant, we complain\n\t\t\t\tif (modulesFile != null && modulesFile.isDefinedConstant(name)) {\n\t\t\t\t\tthrow new PrismException(\"Constant \\\"\" + name + \"\\\" has already been defined in the model\");\n\t\t\t\t}\n\t\t\t\tif (propertiesFile != null && propertiesFile.isDefinedConstant(name)) {\n\t\t\t\t\tthrow new PrismException(\"Constant \\\"\" + name + \"\\\" has already been defined\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// return whether or not we overwrote an existing definition\n\t\treturn overwrite;\n\t}\n\n\t/**\n\t * Check that definitions have been provided for all constants.\n\t * Throw explanatory exception if not.\n\t */\n\tpublic void checkAllDefined() throws PrismException\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\tVector<String> v = new Vector<String>();\n\n\t\tfor (i = 0; i < mfNumConsts; i++) {\n\t\t\tif (mfConsts.get(i).getLow() == null) {\n\t\t\t\tv.add(mfConsts.get(i).getName());\n\t\t\t}\n\t\t}\n\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\tif (pfConsts.get(i).getLow() == null) {\n\t\t\t\tv.add(pfConsts.get(i).getName());\n\t\t\t}\n\t\t}\n\t\tn = v.size();\n\t\tif (n > 0) {\n\t\t\tif (n == 1) {\n\t\t\t\ts = \"Undefined constant \\\"\" + v.get(0) + \"\\\" must be defined\";\n\t\t\t} else {\n\t\t\t\ts = \"Undefined constants\";\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\tif (i > 0 && i < n - 1)\n\t\t\t\t\t\ts += \",\";\n\t\t\t\t\telse if (i == n - 1)\n\t\t\t\t\t\ts += \" and\";\n\t\t\t\t\ts += \" \\\"\" + v.get(i) + \"\\\"\";\n\t\t\t\t}\n\t\t\t\ts += \" must be defined\";\n\t\t\t}\n\t\t\tthrow new PrismException(s);\n\t\t}\n\t}\n\n\t/**\n\t * Initialise iterators for stepping through constant values.\n\t */\n\tpublic void initialiseIterators()\n\t{\n\t\tintialiseModelIterator();\n\t\tintialisePropertyIterator();\n\t}\n\n\t/**\n\t * Initialise iterator for stepping through model constant values.\n\t */\n\tprivate void intialiseModelIterator()\n\t{\n\t\tint i;\n\n\t\t// set all consts to lowest values\n\t\tfor (i = 0; i < mfNumConsts; i++) {\n\t\t\tmfConsts.get(i).setValue(mfConsts.get(i).getLow());\n\t\t}\n\t\t// create Values object\n\t\tmfValues = new Values();\n\t\tfor (i = 0; i < mfNumConsts; i++) {\n\t\t\tmfValues.addValue(mfConsts.get(i).getName(), mfConsts.get(i).getValue());\n\t\t}\n\t}\n\n\t/**\n\t * Initialise iterator for stepping through property constant values.\n\t */\n\tprivate void intialisePropertyIterator()\n\t{\n\t\tint i;\n\n\t\t// set all consts to lowest values\n\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\tpfConsts.get(i).setValue(pfConsts.get(i).getLow());\n\t\t}\n\t\t// create Values object\n\t\tpfValues = new Values();\n\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\tpfValues.addValue(pfConsts.get(i).getName(), pfConsts.get(i).getValue());\n\t\t}\n\t}\n\n\t// Accessor methods for info about values of defined constants, iterators, etc.\n\n\t/**\n\t * Get a string showing the values/ranges of all constants. \n\t * (e.g. \"x=1,y=1:100,z=1:10:100,b=true\")\n\t */\n\tpublic String getDefinedConstantsString()\n\t{\n\t\tint i;\n\t\tString s = \"\";\n\n\t\tfor (i = 0; i < mfNumConsts; i++) {\n\t\t\ts += mfConsts.get(i);\n\t\t\tif (i < mfNumConsts - 1)\n\t\t\t\ts += \",\";\n\t\t}\n\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\tif (i == 0 && mfNumConsts > 0)\n\t\t\t\ts += \",\";\n\t\t\ts += pfConsts.get(i);\n\t\t\tif (i < pfNumConsts - 1)\n\t\t\t\ts += \",\";\n\t\t}\n\n\t\treturn s;\n\t}\n\n\t/**\n\t * Get a string showing the values/ranges of all properties file constants. \n\t * (e.g. \"x=1,y=1:100,z=1:10:100,b=true\")\n\t */\n\tpublic String getPFDefinedConstantsString()\n\t{\n\t\tint i;\n\t\tString s = \"\";\n\n\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\ts += pfConsts.get(i);\n\t\t\tif (i < pfNumConsts - 1)\n\t\t\t\ts += \",\";\n\t\t}\n\n\t\treturn s;\n\t}\n\n\tpublic int getNumModelIterations()\n\t{\n\t\tint i, res;\n\n\t\tres = 1;\n\t\tfor (i = 0; i < mfNumConsts; i++)\n\t\t\tres *= mfConsts.get(i).getNumSteps();\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Get the number of ranging constants (constants with range greater than 1) from the model file.\n\t */\n\tpublic int getNumModelRangingConstants()\n\t{\n\t\tint i, res;\n\n\t\tres = 0;\n\t\tfor (i = 0; i < mfNumConsts; i++)\n\t\t\tif (mfConsts.get(i).getNumSteps() > 1)\n\t\t\t\tres++;\n\n\t\treturn res;\n\t}\n\n\tpublic int getNumPropertyIterations()\n\t{\n\t\tint i, res;\n\n\t\tres = 1;\n\t\tfor (i = 0; i < pfNumConsts; i++)\n\t\t\tres *= pfConsts.get(i).getNumSteps();\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Get the number of ranging constants (constants with range greater than 1) from the properties file.\n\t */\n\tpublic int getNumPropertyRangingConstants()\n\t{\n\t\tint i, res;\n\n\t\tres = 0;\n\t\tfor (i = 0; i < pfNumConsts; i++)\n\t\t\tif (pfConsts.get(i).getNumSteps() > 1)\n\t\t\t\tres++;\n\n\t\treturn res;\n\t}\n\n\tpublic int getNumIterations()\n\t{\n\t\treturn getNumModelIterations() * getNumPropertyIterations();\n\t}\n\n\t/**\n\t * Get a list of DefinedConstant objects: one for each ranging constant,\n\t * i.e. each constant that has range greater than 1.\n\t */\n\tpublic Vector<DefinedConstant> getRangingConstants()\n\t{\n\t\tVector<DefinedConstant> res = new Vector<DefinedConstant>();\n\t\tfor (int i = 0; i < mfNumConsts; i++)\n\t\t\tif (mfConsts.get(i).getNumSteps() > 1)\n\t\t\t\tres.addElement(mfConsts.get(i));\n\t\tfor (int i = 0; i < pfNumConsts; i++)\n\t\t\tif (pfConsts.get(i).getNumSteps() > 1)\n\t\t\t\tres.addElement(pfConsts.get(i));\n\n\t\treturn res;\n\t}\n\n\tpublic void iterateModel()\n\t{\n\t\tint i, ptr;\n\n\t\t// pointer to which constant we are looking at\n\t\tptr = mfNumConsts - 1;\n\t\t// cycle backwards through contants\n\t\twhile (ptr >= -1) {\n\t\t\t// general case\n\t\t\tif (ptr >= 0) {\n\t\t\t\tif (!mfConsts.get(ptr).incr()) {\n\t\t\t\t\tbreak;\n\t\t\t\t} else {\n\t\t\t\t\tptr--;\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// special case - have reached last iteration and need to restart\n\t\t\telse {\n\t\t\t\tfor (i = 0; i < mfNumConsts; i++) {\n\t\t\t\t\tmfConsts.get(i).setValue(mfConsts.get(i).getLow());\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\t// create Values objects\n\t\tmfValues = new Values();\n\t\tfor (i = 0; i < mfNumConsts; i++) {\n\t\t\tmfValues.addValue(mfConsts.get(i).getName(), mfConsts.get(i).getValue());\n\t\t}\n\t}\n\n\tpublic void iterateProperty()\n\t{\n\t\tint i, ptr;\n\n\t\t// pointer to which constant we are looking at\n\t\tptr = pfNumConsts - 1;\n\t\t// cycle backwards through contants\n\t\twhile (ptr >= -1) {\n\t\t\t// general case\n\t\t\tif (ptr >= 0) {\n\t\t\t\tif (!pfConsts.get(ptr).incr()) {\n\t\t\t\t\tbreak;\n\t\t\t\t} else {\n\t\t\t\t\tptr--;\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// special case - have reached last iteration and need to restart\n\t\t\telse {\n\t\t\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\t\t\tpfConsts.get(i).setValue(pfConsts.get(i).getLow());\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\t// create Values objects\n\t\tpfValues = new Values();\n\t\tfor (i = 0; i < pfNumConsts; i++) {\n\t\t\tpfValues.addValue(pfConsts.get(i).getName(), pfConsts.get(i).getValue());\n\t\t}\n\t}\n\n\tpublic Values getMFConstantValues()\n\t{\n\t\treturn mfValues;\n\t}\n\n\tpublic Values getPFConstantValues()\n\t{\n\t\treturn pfValues;\n\t}\n\n\t/**\n\t * Get the values for non-ranging model constants, i.e. each constant that has range 1.\n\t */\n\tpublic Values getNonRangingConstantValues()\n\t{\n\t\tValues vals = new Values();\n\t\tfor (int i = 0; i < mfNumConsts; i++)\n\t\t\tif (mfConsts.get(i).getNumSteps() == 1)\n\t\t\t\tvals.addValue(mfConsts.get(i).getName(), mfConsts.get(i).getValue());\n\t\tfor (int i = 0; i < pfNumConsts; i++)\n\t\t\tif (pfConsts.get(i).getNumSteps() == 1)\n\t\t\t\tvals.addValue(pfConsts.get(i).getName(), pfConsts.get(i).getValue());\n\t\treturn vals;\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/Version.java",
    "content": "package prism;\n\npublic class Version\n{\n\t/** PRISM version (e.g. \"4.0.3\"). Just a single string (will be extracted by scripts). */\n\tpublic static String versionString = \"4.10.2\";\n\t/** Optional PRISM version suffix (e.g. \"\", \"dev\", \"beta\"). Just a single string (will be extracted by scripts). */\n\tpublic static String versionSuffixString = \"dev\";\n}\n"
  },
  {
    "path": "prism/src/prism/VersionUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage prism;\n\nimport java.util.Locale;\nimport java.util.regex.Matcher;\nimport java.util.regex.Pattern;\n\n/**\n * Utility methods for parsing and comparing PRISM version strings.\n */\npublic final class VersionUtils\n{\n\tprivate static final Pattern VERSION_ALPHA_PATTERN = Pattern.compile(\"alpha(\\\\d*)\", Pattern.CASE_INSENSITIVE);\n\tprivate static final Pattern VERSION_BETA_PATTERN = Pattern.compile(\"beta(\\\\d*)\", Pattern.CASE_INSENSITIVE);\n\tprivate static final Pattern VERSION_DEV_PATTERN = Pattern.compile(\"dev(\\\\d*)\", Pattern.CASE_INSENSITIVE);\n\tprivate static final Pattern VERSION_POST_PATTERN = Pattern.compile(\"post(\\\\d*)\", Pattern.CASE_INSENSITIVE);\n\tprivate static final Pattern VERSION_LEGACY_DOT_DEV_PATTERN = Pattern.compile(\"\\\\.dev(\\\\d*)\", Pattern.CASE_INSENSITIVE);\n\tprivate static final Pattern VERSION_REVISION_PATTERN = Pattern.compile(\"r(\\\\d+)\", Pattern.CASE_INSENSITIVE);\n\tprivate static final Pattern VERSION_NUMERIC_PATTERN = Pattern.compile(\"\\\\d+\");\n\n\tprivate VersionUtils()\n\t{\n\t}\n\n\t/**\n\t * Compare two version numbers of PRISM (strings).\n\t * Supports standard semantic versioning, e.g., 2 < 2.1 < 2.1.1-dev < 2.1.1-alpha < 2.1.1-beta < 2.1.1.\n\t * But also respects legacy PRISM use of \".dev\" where 2.1.1 < 2.1.1.dev.\n\t * To achieve this, \".dev\" is interpreted as \".post\" and differently to \"-dev\".\n\t * Example ordering: { \"1\", \"2.0\", \"2.1-dev\", \"2.1.alpha\", \"2.1.beta\", \"2.1\", \"2.1.post\", \"2.1.2\", \"2.9\", \"3\", \"3.4\"};\n\t * Returns: 1 if v1&gt;v2, -1 if v1&lt;v2, 0 if v1=v2.\n\t */\n\tpublic static int compareVersions(String v1, String v2)\n\t{\n\t\tif (v1.equals(v2))\n\t\t\treturn 0;\n\n\t\tString n1 = normaliseLegacyDotDev(v1);\n\t\tString n2 = normaliseLegacyDotDev(v2);\n\t\tif (n1.equals(n2))\n\t\t\treturn 0;\n\n\t\tString[] ss1 = n1.split(\"[.-]\", -1);\n\t\tString[] ss2 = n2.split(\"[.-]\", -1);\n\t\tint n = Math.max(ss1.length, ss2.length);\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tVersionPart p1 = parseVersionPart(i < ss1.length ? ss1[i] : \"\");\n\t\t\tVersionPart p2 = parseVersionPart(i < ss2.length ? ss2[i] : \"\");\n\t\t\tint cmp = p1.compareTo(p2);\n\t\t\tif (cmp != 0) {\n\t\t\t\treturn Integer.signum(cmp);\n\t\t\t}\n\t\t}\n\n\t\treturn 0;\n\t}\n\n\tprivate static String normaliseLegacyDotDev(String version)\n\t{\n\t\treturn VERSION_LEGACY_DOT_DEV_PATTERN.matcher(version).replaceAll(\".post$1\");\n\t}\n\n\tprivate static VersionPart parseVersionPart(String raw)\n\t{\n\t\tString s = raw == null ? \"\" : raw.trim();\n\t\tif (s.isEmpty()) {\n\t\t\treturn new VersionPart(VersionPartType.NUMERIC, 0, \"\");\n\t\t}\n\n\t\tMatcher alpha = VERSION_ALPHA_PATTERN.matcher(s);\n\t\tif (alpha.matches()) {\n\t\t\treturn new VersionPart(VersionPartType.ALPHA, parseInt(alpha.group(1)), \"\");\n\t\t}\n\n\t\tMatcher beta = VERSION_BETA_PATTERN.matcher(s);\n\t\tif (beta.matches()) {\n\t\t\treturn new VersionPart(VersionPartType.BETA, parseInt(beta.group(1)), \"\");\n\t\t}\n\n\t\tMatcher dev = VERSION_DEV_PATTERN.matcher(s);\n\t\tif (dev.matches()) {\n\t\t\treturn new VersionPart(VersionPartType.DEV, parseInt(dev.group(1)), \"\");\n\t\t}\n\n\t\tMatcher post = VERSION_POST_PATTERN.matcher(s);\n\t\tif (post.matches()) {\n\t\t\treturn new VersionPart(VersionPartType.POST, parseInt(post.group(1)), \"\");\n\t\t}\n\n\t\tMatcher revision = VERSION_REVISION_PATTERN.matcher(s);\n\t\tif (revision.matches()) {\n\t\t\treturn new VersionPart(VersionPartType.NUMERIC, parseInt(revision.group(1)), \"\");\n\t\t}\n\n\t\tMatcher numeric = VERSION_NUMERIC_PATTERN.matcher(s);\n\t\tif (numeric.matches()) {\n\t\t\treturn new VersionPart(VersionPartType.NUMERIC, parseInt(s), \"\");\n\t\t}\n\n\t\treturn new VersionPart(VersionPartType.TEXT, 0, s.toLowerCase(Locale.ROOT));\n\t}\n\n\tprivate static int parseInt(String s)\n\t{\n\t\tif (s == null || s.isEmpty()) {\n\t\t\treturn 0;\n\t\t}\n\t\ttry {\n\t\t\treturn Integer.parseInt(s);\n\t\t} catch (NumberFormatException e) {\n\t\t\treturn Integer.MAX_VALUE;\n\t\t}\n\t}\n\n\tprivate static class VersionPart implements Comparable<VersionPart>\n\t{\n\t\tprivate final VersionPartType type;\n\t\tprivate final int numericValue;\n\t\tprivate final String textValue;\n\n\t\tprivate VersionPart(VersionPartType type, int numericValue, String textValue)\n\t\t{\n\t\t\tthis.type = type;\n\t\t\tthis.numericValue = numericValue;\n\t\t\tthis.textValue = textValue;\n\t\t}\n\n\t\t@Override\n\t\tpublic int compareTo(VersionPart other)\n\t\t{\n\t\t\t// Post-release tags are newer than release (0) but older than patch levels >= 1.\n\t\t\tif (type == VersionPartType.POST && other.type == VersionPartType.NUMERIC) {\n\t\t\t\treturn other.numericValue == 0 ? 1 : -1;\n\t\t\t}\n\t\t\tif (type == VersionPartType.NUMERIC && other.type == VersionPartType.POST) {\n\t\t\t\treturn numericValue == 0 ? -1 : 1;\n\t\t\t}\n\n\t\t\tint rankCmp = Integer.compare(type.rank, other.type.rank);\n\t\t\tif (rankCmp != 0) {\n\t\t\t\treturn rankCmp;\n\t\t\t}\n\t\t\tint numericCmp = Integer.compare(numericValue, other.numericValue);\n\t\t\tif (numericCmp != 0) {\n\t\t\t\treturn numericCmp;\n\t\t\t}\n\t\t\treturn textValue.compareTo(other.textValue);\n\t\t}\n\t}\n\n\tprivate static enum VersionPartType\n\t{\n\t\tDEV(0), ALPHA(1), BETA(2), TEXT(3), NUMERIC(4), POST(5);\n\n\t\tprivate final int rank;\n\n\t\tprivate VersionPartType(int rank)\n\t\t{\n\t\t\tthis.rank = rank;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/prism/ng.c.orig",
    "content": "/*   \n\n  Copyright 2004-2012, Martian Software, Inc.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n  http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  \n*/\n\n/**\n * @author <a href=\"http://www.martiansoftware.com/contact.html\">Marty Lamb</a>\n * @author Pete Kirkham (Win32 port)\n */\n\n#ifdef WIN32\n\t#include <direct.h>\n\t#include <winsock2.h>\n#else\n\t#include <arpa/inet.h>\n\t#include <netdb.h>\n\t#include <netinet/in.h>\n\t#include <sys/socket.h>\n\t#include <sys/time.h>\n\t#include <sys/types.h>\n#endif\n\n#include <stdio.h>\n#include <stdlib.h>\n#include <string.h>\n#include <unistd.h>\n#include <fcntl.h>\n#include <errno.h>\n\n#define NAILGUN_VERSION \"0.9.0\"\n\n#define BUFSIZE (2048)\n\n#ifdef WIN32\n\tHANDLE NG_STDIN_FILENO;\n\tHANDLE NG_STDOUT_FILENO;\n\tHANDLE NG_STDERR_FILENO;\n\t#define FILE_SEPARATOR '\\\\'\n\t#define MSG_WAITALL 0\n#else\n\t#define NG_STDIN_FILENO STDIN_FILENO\n\t#define NG_STDOUT_FILENO STDOUT_FILENO\n\t#define NG_STDERR_FILENO STDERR_FILENO\n\t#define FILE_SEPARATOR '/'\n\ttypedef int HANDLE;\n\ttypedef unsigned int SOCKET;\n#endif\n\n#ifdef __APPLE__\n  #define SEND_FLAGS 0\n#else\n  #define SEND_FLAGS MSG_NOSIGNAL\n#endif\n\n#ifndef MIN\n#define MIN(a,b) ((a<b)?(a):(b))\n#endif\n\n#ifdef WIN32\n\t#define NAILGUN_FILESEPARATOR \"NAILGUN_FILESEPARATOR=\\\\\"\n\t#define NAILGUN_PATHSEPARATOR \"NAILGUN_PATHSEPARATOR=;\"\n#else\n\t#define NAILGUN_FILESEPARATOR \"NAILGUN_FILESEPARATOR=/\"\n\t#define NAILGUN_PATHSEPARATOR \"NAILGUN_PATHSEPARATOR=:\"\n#endif\n\n#define NAILGUN_CLIENT_NAME_EXE \"ng.exe\"\n\n#define NAILGUN_PORT_DEFAULT \"2113\"\n#define NAILGUN_CLIENT_NAME \"ng\"\n#define CHUNK_HEADER_LEN (5)\n\n#define NAILGUN_SOCKET_FAILED (231)\n#define NAILGUN_CONNECT_FAILED (230)\n#define NAILGUN_UNEXPECTED_CHUNKTYPE (229)\n#define NAILGUN_EXCEPTION_ON_SERVER (228)\n#define NAILGUN_CONNECTION_BROKEN (227)\n#define NAILGUN_BAD_ARGUMENTS (226)\n\n#define CHUNKTYPE_STDIN '0'\n#define CHUNKTYPE_STDOUT '1'\n#define CHUNKTYPE_STDERR '2'\n#define CHUNKTYPE_STDIN_EOF '.'\n#define CHUNKTYPE_ARG 'A'\n#define CHUNKTYPE_LONGARG 'L'\n#define CHUNKTYPE_ENV 'E'\n#define CHUNKTYPE_DIR 'D'\n#define CHUNKTYPE_CMD 'C'\n#define CHUNKTYPE_EXIT 'X'\n#define CHUNKTYPE_SENDINPUT 'S'\n#define CHUNKTYPE_HEARTBEAT 'H'\n\n#define HEARTBEAT_TIMEOUT_MILLIS 500\n\n#define NAILGUN_TTY_FORMAT \"NAILGUN_TTY_%d=%d\"\n\n/*\n   the following is required to compile for hp-ux\n   originally posted at http://jira.codehaus.org/browse/JRUBY-2346\n*/\n#ifndef MSG_WAITALL\n#define MSG_WAITALL 0x40 /* wait for full request or error */\n#endif\n\n/* the socket connected to the nailgun server */\nint nailgunsocket = 0;\n\n/* buffer used for receiving and writing nail output chunks */\nchar buf[BUFSIZE];\n\n/* track whether server is ready to receive */\n#ifdef WIN32\n    HANDLE readyToSend = 0;\n    HANDLE sending = 0;\n#else\n    int readyToSend = 0;\n    struct timeval sendtime;\n#endif\n\n/**\n * Clean up the application.\n */\nvoid cleanUpAndExit (int exitCode) {\n\n\n  #ifdef WIN32\n    CancelIo(STDIN_FILENO);\n    WSACleanup();\n    if (nailgunsocket) {\n      closesocket(nailgunsocket);\n    }\n  #else\n    close(nailgunsocket);\n  #endif\n\n  exit(exitCode);\n}\n\n#ifdef WIN32\n/**\n * Handles an error.\n * Shows the message for the latest error then exits.\n */\nvoid handleError () {\n  LPVOID lpMsgBuf;\n  int error = GetLastError();\n\n  FormatMessage( \n    FORMAT_MESSAGE_ALLOCATE_BUFFER | \n    FORMAT_MESSAGE_FROM_SYSTEM | \n    FORMAT_MESSAGE_IGNORE_INSERTS,\n    NULL,\n    error,\n    MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), /* Default language */\n    (LPTSTR) &lpMsgBuf,\n    0,\n    NULL);\n\n  /* Display the string. */\n  MessageBox( NULL, (LPCTSTR)lpMsgBuf, \"Error\", MB_OK | MB_ICONERROR );\n\n  /* Free the buffer. */\n  LocalFree( lpMsgBuf );\n \n  cleanUpAndExit(error);\n}\n#endif\n\n/**\n * Exits the client if the nailgun server ungracefully shut down the connection.\n */\nvoid handleSocketClose() {\n  cleanUpAndExit(NAILGUN_CONNECTION_BROKEN);\n}\n\n/**\n * Writes everything in the specified buffer to the specified\n * socket handle.\n *\n * @param s the socket descriptor\n * @param buf the buffer containing the data to send\n * @param len the number of bytes to send.  Also used to\n *            return the number of bytes sent.\n * @return total bytes written or 0 if failure\n */\nint sendAll(SOCKET s, char *buf, int len) {\n  int total = 0;      \n  int bytesleft = len; \n  int n = 0;\n\n  while(total < len) {\n    n = send(s, buf+total, bytesleft, SEND_FLAGS);\n    \n    if (n == -1) { \n      break;\n    }\n    \n    total += n;\n    bytesleft -= n;\n  }\n\n  return n==-1 ? 0:total; \n}\n\n/**\n * Sends a chunk noting the specified payload size and chunk type.\n * Waits for sending mutex on Win32.\n * \n * @param size the payload size\n * @param chunkType the chunk type identifier\n */\nvoid sendChunk(unsigned int size, char chunkType, char* buf) {\n  /* buffer used for reading and writing chunk headers */\n  char header[CHUNK_HEADER_LEN];\n  int bytesSent;\n\n  header[0] = (size >> 24) & 0xff;\n  header[1] = (size >> 16) & 0xff;\n  header[2] = (size >> 8) & 0xff;\n  header[3] = size & 0xff;\n  header[4] = chunkType;\n\n#ifdef WIN32\n  if (WaitForSingleObject(sending, INFINITE) != WAIT_OBJECT_0) {\n    handleError();\n  }\n#else\n  gettimeofday(&sendtime, NULL);\n#endif\n\n  bytesSent = sendAll(nailgunsocket, header, CHUNK_HEADER_LEN);\n  if (bytesSent != 0 && size > 0) {\n    bytesSent = sendAll(nailgunsocket, buf, size);\n  } else if (bytesSent == 0 && (chunkType != CHUNKTYPE_HEARTBEAT || errno != EPIPE)) {\n    perror(\"send\");\n    handleSocketClose();\n  }\n\n#ifdef WIN32\n  ReleaseMutex(sending);\n#endif\n}\n\n/**\n * Sends the contents of the specified file as a long argument (--nailgun-filearg)\n * This is sent as one or more chunks of type CHUNK_LONGARG.  The end of the argument\n * is indicated by an empty chunk.\n *\n * @param filename the name of the file to send.\n * @return nonzero on failure\n */\nint sendFileArg(char *filename) {\n  int i, f;\n  \n  if ((f = open(filename, O_RDONLY)) < 0) {\n    perror(\"--nailgun-filearg\");\n    return 1;  \n  }\n\n  i = read(f, buf, BUFSIZE);\n  while (i > 0) {\n    sendChunk(i, CHUNKTYPE_LONGARG, buf);\n    i = read(f, buf, BUFSIZE);\n  }\n  if (i < 0) {\n    perror(\"--nailgun-filearg\");\n    return 1;\n  }\n  sendChunk(0, CHUNKTYPE_LONGARG, buf);\n  \n  close(f);\n  return 0;\n}\n\n/**\n * Sends a null-terminated string with the specified chunk type.\n *\n * @param chunkType the chunk type identifier\n * @param text the null-terminated string to send\n */\nvoid sendText(char chunkType, char *text) {\n  int len = text ? strlen(text) : 0;\n  sendChunk(len, chunkType, text);\n}\n\n/**\n * Receives len bytes from the nailgun socket and copies them to the specified file descriptor.\n * Used to route data to stdout or stderr on the client.\n *\n * @param destFD the destination file descriptor (stdout or stderr)\n * @param len the number of bytes to copy\n */\nvoid recvToFD(HANDLE destFD, char *buf, unsigned long len) {\n  unsigned long bytesRead = 0;\n  int bytesCopied;\n  \n  while (bytesRead < len) {\n    unsigned long bytesRemaining = len - bytesRead;\n    int bytesToRead = (BUFSIZE < bytesRemaining) ? BUFSIZE : bytesRemaining;\n    int thisPass = 0;\n    \n    thisPass = recv(nailgunsocket, buf, bytesToRead, MSG_WAITALL);\n    if (thisPass == 0 || thisPass == -1) {\n      perror(\"recv\");\n      handleSocketClose();\n    }\n    bytesRead += thisPass;\n\n    bytesCopied = 0;\n\n    while(bytesCopied < thisPass) {\n      #ifdef WIN32\n        DWORD thisWrite =  0;\n\n        WriteFile(destFD, buf + bytesCopied, thisPass - bytesCopied,\n          &thisWrite, NULL);\n\n        if (thisWrite < 0) {\n          break;\n        }\n\n        bytesCopied += thisWrite;\n      #else\n        int bytesWritten = write(destFD, buf + bytesCopied, thisPass - bytesCopied);\n        if (bytesWritten == -1) {\n          perror(\"write\");\n          handleSocketClose();\n        }\n        bytesCopied += bytesWritten;\n      #endif\n    }  \n  }\n}\n\nunsigned long recvToBuffer(unsigned long len) {\n  unsigned long bytesRead = 0;\n  while(bytesRead < len) {\n    int thisPass = recv(nailgunsocket, buf + bytesRead, len - bytesRead, MSG_WAITALL);\n    if (thisPass == 0 || thisPass == -1) {\n        perror(\"recv\");\n        handleSocketClose();\n    }\n    bytesRead += thisPass;\n  }\n  return bytesRead;\n}\n\n/**\n * Processes an exit chunk from the server.  This is just a string\n * containing the exit code in decimal format.  It should fit well\n * within our buffer, so assume that it does.\n *\n * @param len the current length of the buffer containing the exit code.\n */\nvoid processExit(char *buf, unsigned long len) {\n  int exitcode;\n  int bytesToRead = (BUFSIZE - 1 < len) ? BUFSIZE - 1 : len;\n  int bytesRead = recvToBuffer(bytesToRead);\n  \n  if (bytesRead < 0) {\n    handleSocketClose();\n  }\n  \n  buf[bytesRead] = 0;\n  \n  exitcode = atoi(buf);\n  \n  cleanUpAndExit(exitcode);\n}\n\n\n/**\n * Sends len bytes from buf to the nailgun server in a stdin chunk.\n *\n * @param buf the bytes to send\n * @param len the number of bytes to send\n */\nvoid sendStdin(char *buf, unsigned int len) {\n#ifndef WIN32\n  readyToSend = 0;\n#endif\n  sendChunk(len, CHUNKTYPE_STDIN, buf);\n}\n\n/**\n * Sends a stdin-eof chunk to the nailgun server\n */\nvoid processEof() {\n  sendChunk(0, CHUNKTYPE_STDIN_EOF, buf);\n}\n\n/**\n * Sends a heartbeat chunk to let the server know the client is still alive.\n */\nvoid sendHeartbeat() {\n  sendChunk(0, CHUNKTYPE_HEARTBEAT, buf);\n}\n\n#ifdef WIN32\n\nHANDLE createEvent(BOOL manualReset) {\n  return CreateEvent(NULL, /* default security */\n\t\t     manualReset,\n\t\t     FALSE, /* initial state unsignalled */\n\t\t     NULL /* unnamed event */);\n}\n\nDWORD WINAPI sendHeartbeats(LPVOID lpParameter) {\n\t\t\n\t/* this could be made more efficient by only sending heartbeats when stdin chunks aren't being sent */\n\tfor (;;) {\n\t\tSleep(HEARTBEAT_TIMEOUT_MILLIS);\n\t\tsendHeartbeat();\n\t}\n}\n\n/**\n * Thread main for reading from stdin and sending\n */\nDWORD WINAPI processStdin (LPVOID lpParameter) {\n  /* buffer used for reading and sending stdin chunks */\n  char wbuf[BUFSIZE];\n\n  /* number of bytes read */\n  DWORD numberOfBytes;\n\n  for (;;) {\n\n    /* wait for ready to send */\n    if(WaitForSingleObject(readyToSend, INFINITE) != WAIT_OBJECT_0) {\n      handleError();\n    }\n\n\t/* read data from stdin */\n\tif (! ReadFile(NG_STDIN_FILENO, wbuf, BUFSIZE, &numberOfBytes, NULL)) {\n\t\tif (numberOfBytes != 0) {\n\t\t\thandleError();\n\t\t}\n\t}\n\n    /* send data to server */\n    if (numberOfBytes > 0) {\n      sendStdin(wbuf, numberOfBytes);\n    } else {\n      processEof();\n      break;\n    }\n\n  }\n  return 0;\n}\n#else\n/**\n * Reads from stdin and transmits it to the nailgun server in a stdin chunk.\n * Sends a stdin-eof chunk if necessary.\n *\n * @return zero if eof has been reached.\n */\nint processStdin() {\n\tint bytesread = read(STDIN_FILENO, buf, BUFSIZE);\n\tif (bytesread > 0) {\n\t\tsendStdin(buf, bytesread);\n\t} else if (bytesread == 0) {\n\t\tprocessEof();\n\t}\n\treturn(bytesread);\n}\n#endif\n\n#ifdef WIN32\n/**\n * Initialise Windows sockets\n */\nvoid initSockets () {\n  WSADATA win_socket_data;     /* required to initialise winsock */\n  \n  WSAStartup(2, &win_socket_data);\n\n  /* create flow control event and mutex */\n  readyToSend = createEvent(FALSE);\n  sending = CreateMutex(NULL, FALSE, NULL);\n}\n#endif\n\n#ifdef WIN32\n/**\n * Initialise the asynchronous io.\n */\nvoid initIo () {\n  /* create non-blocking console io */\n  AllocConsole();\n  \n  NG_STDIN_FILENO = GetStdHandle(STD_INPUT_HANDLE);\n  NG_STDOUT_FILENO = GetStdHandle(STD_OUTPUT_HANDLE);\n  NG_STDERR_FILENO = GetStdHandle(STD_ERROR_HANDLE);\n}\n#endif\n\n#ifdef WIN32\n/**\n * Initialise the asynchronous io.\n */\nvoid winStartInput () {\n  SECURITY_ATTRIBUTES securityAttributes;\n  DWORD threadId = 0;\n\n  securityAttributes.bInheritHandle = TRUE;\n  securityAttributes.lpSecurityDescriptor = NULL;\n  securityAttributes.nLength = 0;\n  \n  if (!CreateThread(&securityAttributes, 0, &processStdin, NULL, 0, &threadId)) {\n    handleError();\n  }\n\n  if (!CreateThread(&securityAttributes, 0, &sendHeartbeats, NULL, 0, &threadId)) {\n    handleError();\n  }\n}\n#endif\n\n/**\n * Processes data from the nailgun server.\n */\nvoid processnailgunstream() {\n\n  /*for (;;) {*/\n    unsigned long len;\n    char chunkType;\n\n    recvToBuffer(CHUNK_HEADER_LEN);\n\n    len = ((buf[0] << 24) & 0xff000000)\n      | ((buf[1] << 16) & 0x00ff0000)\n      | ((buf[2] << 8) & 0x0000ff00)\n      | ((buf[3]) & 0x000000ff);\n  \n    chunkType = buf[4];\n  \n    switch(chunkType) {\n      case CHUNKTYPE_STDOUT: recvToFD(NG_STDOUT_FILENO, buf, len);\n            break;\n      case CHUNKTYPE_STDERR: recvToFD(NG_STDERR_FILENO, buf, len);\n            break;\n      case CHUNKTYPE_EXIT:   processExit(buf, len);\n            break;\n      case CHUNKTYPE_SENDINPUT:\n#ifdef WIN32\n            SetEvent(readyToSend);\n#else\n            readyToSend = 1;\n#endif\n            break;\n      default:  fprintf(stderr, \"Unexpected chunk type %d ('%c')\\n\", chunkType, chunkType);\n          cleanUpAndExit(NAILGUN_UNEXPECTED_CHUNKTYPE);\n    }\n  /*}*/\n}\n\n/**\n * Returns the time interval between start and end in milliseconds.\n * @param end the end time\n * @param start the start time\n */\nint intervalMillis(struct timeval end, struct timeval start) {\n\n  return ((end.tv_sec - start.tv_sec) * 1000) + \n    ((end.tv_usec - start.tv_usec) /1000);\n}\n\n/**\n * Trims any path info from the beginning of argv[0] to determine\n * the name used to launch the client.\n *\n * @param s argv[0]\n */\nchar *shortClientName(char *s) {\n  char *result = strrchr(s, FILE_SEPARATOR);\n  return ((result == NULL) ? s : result + 1);\n}\n\n/**\n * Returns true if the specified string is the name of the nailgun\n * client.  The comparison is made case-insensitively for windows.\n *\n * @param s the program name to check\n */\nint isNailgunClientName(char *s) {\n  /* VMS can't get the command name from argv[0] when defined\n     as a foreign command, as the symbol is expanded. Aliases\n     are supported by defining a foreign command that includes\n     the class alias argument, e.g.\n         ng==\"$path:[to]ng.exe\"\n         alias==ng+\" \"\"alias\"\"\"\n  */\n  #ifdef __VMS\n  return (1);\n  #else\n  #ifdef WIN32\n  return (!strcasecmp(s, NAILGUN_CLIENT_NAME) ||\n           !strcasecmp(s, NAILGUN_CLIENT_NAME_EXE));\n  #else\n  return(!(strcmp(s, NAILGUN_CLIENT_NAME)));\n  #endif\n  #endif\n}\n\n/**\n * Displays usage info and bails\n */\nvoid usage(int exitcode) {\n  fprintf(stderr, \"NailGun v%s\\n\\n\", NAILGUN_VERSION);\n  fprintf(stderr, \"Usage: ng class [--nailgun-options] [args]\\n\");\n  fprintf(stderr, \"          (to execute a class)\\n\");\n  fprintf(stderr, \"   or: ng alias [--nailgun-options] [args]\\n\");\n  fprintf(stderr, \"          (to execute an aliased class)\\n\");\n  fprintf(stderr, \"   or: alias [--nailgun-options] [args]\\n\");\n  fprintf(stderr, \"          (to execute an aliased class, where \\\"alias\\\"\\n\");\n  fprintf(stderr, \"           is both the alias for the class and a symbolic\\n\");\n  fprintf(stderr, \"           link to the ng client)\\n\\n\");\n  \n  fprintf(stderr, \"where options include:\\n\");\n  fprintf(stderr, \"   --nailgun-D<name>=<value>   set/override a client environment variable\\n\");\n  fprintf(stderr, \"   --nailgun-version           print product version and exit\\n\");\n  fprintf(stderr, \"   --nailgun-showversion       print product version and continue\\n\");\n  fprintf(stderr, \"   --nailgun-server            to specify the address of the nailgun server\\n\");\n  fprintf(stderr, \"                               (default is NAILGUN_SERVER environment variable\\n\");\n  fprintf(stderr, \"                               if set, otherwise localhost)\\n\");\n  fprintf(stderr, \"   --nailgun-port              to specify the port of the nailgun server\\n\");\n  fprintf(stderr, \"                               (default is NAILGUN_PORT environment variable\\n\");\n  fprintf(stderr, \"                               if set, otherwise 2113)\\n\");  \n  fprintf(stderr, \"   --nailgun-filearg FILE      places the entire contents of FILE into the\\n\");\n  fprintf(stderr, \"                               next argument, which is interpreted as a string\\n\");\n  fprintf(stderr, \"                               using the server's default character set.  May be\\n\");\n  fprintf(stderr, \"                               specified more than once.\\n\");\n  fprintf(stderr, \"   --nailgun-help              print this message and exit\\n\");\n\n  cleanUpAndExit(exitcode);\n}\n\nint main(int argc, char *argv[], char *env[]) {\n  int i;\n  struct sockaddr_in server_addr;\n  char *nailgun_server;        /* server as specified by user */\n  char *nailgun_port;          /* port as specified by user */\n  char *cwd;\n  u_short port;                /* port */\n  struct hostent *hostinfo;\n  char *cmd;\n  int firstArgIndex;           /* the first argument _to pass to the server_ */\n  char isattybuf[] = NAILGUN_TTY_FORMAT;\n\n  #ifndef WIN32\n    fd_set readfds;\n    int eof = 0;\n    struct timeval readtimeout;\n    struct timeval currenttime;\n    memset(&sendtime, '\\0', sizeof(sendtime));\n  #endif\n\n  #ifdef WIN32\n  initSockets();\n  #endif\n  \n  /* start with environment variable.  default to localhost if not defined. */\n  nailgun_server = getenv(\"NAILGUN_SERVER\");\n  if (nailgun_server == NULL) {\n    nailgun_server = \"127.0.0.1\";\n  }\n  \n  /* start with environment variable.  default to normal nailgun port if not defined */\n  nailgun_port = getenv(\"NAILGUN_PORT\");\n  if (nailgun_port == NULL) {\n    nailgun_port = NAILGUN_PORT_DEFAULT;\n  }\n  \n  /* look at the command used to launch this program.  if it was \"ng\", then the actual\n     command to issue to the server must be specified as another argument.  if it\n     wasn't ng, assume that the desired command name was symlinked to ng in the user's\n     filesystem, and use the symlink name (without path info) as the command for the server. */\n  cmd = shortClientName(argv[0]);\n\n  if (isNailgunClientName(cmd)) {\n    cmd = NULL;\n  }\n\n  /* if executing just the ng client with no arguments or -h|--help, then\n     display usage and exit.  Don't handle -h|--help if a command other than\n     ng or ng.exe was used, since the appropriate nail should then handle\n     --help. */\n  if (cmd == NULL && \n        (argc == 1 || \n\t  (argc == 2 && strcmp(\"--help\", argv[1]) == 0) ||\n\t  (argc == 2 && strcmp(\"-h\", argv[1]) == 0))) usage(0);\n     \n  firstArgIndex = 1;\n\n  /* quite possibly the lamest commandline parsing ever. \n     look for the two args we care about (--nailgun-server and\n     --nailgun-port) and NULL them and their parameters after\n     reading them if found.  later, when we send args to the\n     server, skip the null args. */\n  for (i = 1; i < argc; ++i) {\n    if (!strcmp(\"--nailgun-server\", argv[i])) {\n      if (i == argc - 1) usage(NAILGUN_BAD_ARGUMENTS);\n      nailgun_server = argv[i + 1];\n      argv[i] = argv[i + 1] = NULL;\n      ++i;\n    } else if(!strcmp(\"--nailgun-port\", argv[i])) {\n      if (i == argc - 1) usage(NAILGUN_BAD_ARGUMENTS);\n      nailgun_port = argv[i + 1];\n      argv[i] = argv[i + 1]= NULL;\n      ++i;\n    } else if (!strcmp(\"--nailgun-filearg\", argv[i])) {\n      /* just verify usage here.  do the rest when sending args. */\n      if (i == argc - 1) usage (NAILGUN_BAD_ARGUMENTS);\n    } else if (!strcmp(\"--nailgun-version\", argv[i])) {\n      printf(\"NailGun client version %s\\n\", NAILGUN_VERSION);\n      cleanUpAndExit(0);\n    } else if (!strcmp(\"--nailgun-showversion\", argv[i])) {\n      printf(\"NailGun client version %s\\n\", NAILGUN_VERSION);\n      argv[i] = NULL;\n    } else if (!strcmp(\"--nailgun-help\", argv[i])) {\n      usage(0);\n    } else if (cmd == NULL) {\n      cmd = argv[i];\n      firstArgIndex = i + 1;\n    }\n  }\n\n  /* if there's no command, we should only display usage info\n     if the version number was not displayed. */\n  if (cmd == NULL) {\n    usage(NAILGUN_BAD_ARGUMENTS);\n  }\n  \n  /* jump through a series of connection hoops */  \n  hostinfo = gethostbyname(nailgun_server);\n\n  if (hostinfo == NULL) {\n    fprintf(stderr, \"Unknown host: %s\\n\", nailgun_server);\n    cleanUpAndExit(NAILGUN_CONNECT_FAILED);\n  }\n \n  port = atoi(nailgun_port);\n\n  if ((nailgunsocket = socket(AF_INET, SOCK_STREAM, 0)) == -1) {\n    perror(\"socket\");\n    cleanUpAndExit(NAILGUN_SOCKET_FAILED);\n  }\n\n  server_addr.sin_family = AF_INET;    \n  server_addr.sin_port = htons(port);\n  server_addr.sin_addr = *(struct in_addr *) hostinfo->h_addr;\n  \n  memset(&(server_addr.sin_zero), '\\0', 8);\n\n  if (connect(nailgunsocket, (struct sockaddr *)&server_addr,\n    sizeof(struct sockaddr)) == -1) {\n    perror(\"connect\");\n    cleanUpAndExit(NAILGUN_CONNECT_FAILED);\n  } \n    \n  /* ok, now we're connected.  first send all of the command line\n     arguments for the server, if any.  remember that we may have\n     marked some arguments NULL if we read them to specify the\n     nailgun server and/or port */\n  for(i = firstArgIndex; i < argc; ++i) {\n    if (argv[i] != NULL) {\n      if (!strcmp(\"--nailgun-filearg\", argv[i])) {\n        int sendResult = sendFileArg(argv[++i]);\n        if (sendResult != 0) {\n          perror(\"send\");\n          handleSocketClose();\n        }\n      } else sendText(CHUNKTYPE_ARG, argv[i]);\n    }\n  }\n\n  /* now send environment */  \n  sendText(CHUNKTYPE_ENV, NAILGUN_FILESEPARATOR);\n  sendText(CHUNKTYPE_ENV, NAILGUN_PATHSEPARATOR);\n#ifndef WIN32\n  /* notify isatty for standard pipes */\n  for(i = 0; i < 3; i++) {\n    sprintf(isattybuf, NAILGUN_TTY_FORMAT, i, isatty(i));\n    sendText(CHUNKTYPE_ENV, isattybuf);\n  }\n#endif\n  /* forward the client process environment */\n  for(i = 0; env[i]; ++i) {\n    sendText(CHUNKTYPE_ENV, env[i]);\n  }\n  \n  /* now send the working directory */\n  cwd = getcwd(NULL, 0);\n  sendText(CHUNKTYPE_DIR, cwd);\n  free(cwd);\n  \n  /* and finally send the command.  this marks the point at which\n     streams are linked between client and server. */\n  sendText(CHUNKTYPE_CMD, cmd);\n\n  \n  /* initialise the std-* handles and the thread to send stdin to the server */ \n  #ifdef WIN32\n  initIo();\n  winStartInput();\n  #endif\n\n  /* stream forwarding loop */\t\n  while(1) {\n    #ifndef WIN32\n      FD_ZERO(&readfds);\n\n      /* don't select on stdin if we've already reached its end */\n      if (readyToSend && !eof) {\n\tFD_SET(NG_STDIN_FILENO, &readfds);\n      }\n\n      FD_SET(nailgunsocket, &readfds);\n\n      memset(&readtimeout, '\\0', sizeof(readtimeout));\n      readtimeout.tv_usec = HEARTBEAT_TIMEOUT_MILLIS * 1000;\n      if(select (nailgunsocket + 1, &readfds, NULL, NULL, &readtimeout) == -1) {\n\t  perror(\"select\");\n      }\n\t  \n      if (FD_ISSET(nailgunsocket, &readfds)) {\n    #endif\n\tprocessnailgunstream();\n    #ifndef WIN32\n      } else if (FD_ISSET(NG_STDIN_FILENO, &readfds)) {\n        int result = processStdin();\n        if (result == -1) {\n          perror(\"read\");\n          handleSocketClose();\n        } else if (result == 0) {\n          FD_CLR(NG_STDIN_FILENO, &readfds);\n          eof = 1;\n        }\n      }\n      gettimeofday(&currenttime, NULL);\n      if (intervalMillis(currenttime, sendtime) > HEARTBEAT_TIMEOUT_MILLIS) {\n\t  sendHeartbeat();\n      }\n    #endif\n  }  \n\n  /* normal termination is triggered by the server, and so occurs in processExit(), above */\n}\n"
  },
  {
    "path": "prism/src/prism/ngprism.c",
    "content": "/*   \n\n  Copyright 2004-2012, Martian Software, Inc.\n\n  Licensed under the Apache License, Version 2.0 (the \"License\");\n  you may not use this file except in compliance with the License.\n  You may obtain a copy of the License at\n\n  http://www.apache.org/licenses/LICENSE-2.0\n\n  Unless required by applicable law or agreed to in writing, software\n  distributed under the License is distributed on an \"AS IS\" BASIS,\n  WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.\n  See the License for the specific language governing permissions and\n  limitations under the License.\n  \n*/\n\n/**\n * @author <a href=\"http://www.martiansoftware.com/contact.html\">Marty Lamb</a>\n * @author Pete Kirkham (Win32 port)\n */\n\n/**\n * This file (ngprism.c) is a simple customisation of ng.c)\n * which fixes the command (to prism.PrismNG) by default.\n */\n\n#ifdef WIN32\n\t#include <direct.h>\n\t#include <winsock2.h>\n#else\n\t#include <arpa/inet.h>\n\t#include <netdb.h>\n\t#include <netinet/in.h>\n\t#include <sys/socket.h>\n\t#include <sys/time.h>\n\t#include <sys/types.h>\n#endif\n\n#include <stdio.h>\n#include <stdlib.h>\n#include <string.h>\n#include <unistd.h>\n#include <fcntl.h>\n#include <errno.h>\n\n#define NAILGUN_VERSION \"0.9.0\"\n\n#define BUFSIZE (2048)\n\n#ifdef WIN32\n\tHANDLE NG_STDIN_FILENO;\n\tHANDLE NG_STDOUT_FILENO;\n\tHANDLE NG_STDERR_FILENO;\n\t#define FILE_SEPARATOR '\\\\'\n#ifndef MSG_WAITALL\n\t#define MSG_WAITALL 0\n#endif\n#else\n\t#define NG_STDIN_FILENO STDIN_FILENO\n\t#define NG_STDOUT_FILENO STDOUT_FILENO\n\t#define NG_STDERR_FILENO STDERR_FILENO\n\t#define FILE_SEPARATOR '/'\n\ttypedef int HANDLE;\n\ttypedef unsigned int SOCKET;\n#endif\n\n#if defined(__APPLE__) || !defined(MSG_NOSIGNAL)\n  #define SEND_FLAGS 0\n#else\n  #define SEND_FLAGS MSG_NOSIGNAL\n#endif\n\n#ifndef MIN\n#define MIN(a,b) ((a<b)?(a):(b))\n#endif\n\n#ifdef WIN32\n\t#define NAILGUN_FILESEPARATOR \"NAILGUN_FILESEPARATOR=\\\\\"\n\t#define NAILGUN_PATHSEPARATOR \"NAILGUN_PATHSEPARATOR=;\"\n#else\n\t#define NAILGUN_FILESEPARATOR \"NAILGUN_FILESEPARATOR=/\"\n\t#define NAILGUN_PATHSEPARATOR \"NAILGUN_PATHSEPARATOR=:\"\n#endif\n\n#define NAILGUN_CLIENT_NAME_EXE \"ng.exe\"\n\n#define NAILGUN_PORT_DEFAULT \"2113\"\n#define NAILGUN_CLIENT_NAME \"ng\"\n#define CHUNK_HEADER_LEN (5)\n\n#define NAILGUN_SOCKET_FAILED (231)\n#define NAILGUN_CONNECT_FAILED (230)\n#define NAILGUN_UNEXPECTED_CHUNKTYPE (229)\n#define NAILGUN_EXCEPTION_ON_SERVER (228)\n#define NAILGUN_CONNECTION_BROKEN (227)\n#define NAILGUN_BAD_ARGUMENTS (226)\n\n#define CHUNKTYPE_STDIN '0'\n#define CHUNKTYPE_STDOUT '1'\n#define CHUNKTYPE_STDERR '2'\n#define CHUNKTYPE_STDIN_EOF '.'\n#define CHUNKTYPE_ARG 'A'\n#define CHUNKTYPE_LONGARG 'L'\n#define CHUNKTYPE_ENV 'E'\n#define CHUNKTYPE_DIR 'D'\n#define CHUNKTYPE_CMD 'C'\n#define CHUNKTYPE_EXIT 'X'\n#define CHUNKTYPE_SENDINPUT 'S'\n#define CHUNKTYPE_HEARTBEAT 'H'\n\n#define HEARTBEAT_TIMEOUT_MILLIS 500\n\n#define NAILGUN_TTY_FORMAT \"NAILGUN_TTY_%d=%d\"\n\n/*\n   the following is required to compile for hp-ux\n   originally posted at http://jira.codehaus.org/browse/JRUBY-2346\n*/\n#ifndef MSG_WAITALL\n#define MSG_WAITALL 0x40 /* wait for full request or error */\n#endif\n\n/* the socket connected to the nailgun server */\nint nailgunsocket = 0;\n\n/* buffer used for receiving and writing nail output chunks */\nchar buf[BUFSIZE];\n\n/* track whether server is ready to receive */\n#ifdef WIN32\n    HANDLE readyToSend = 0;\n    HANDLE sending = 0;\n#else\n    int readyToSend = 0;\n    struct timeval sendtime;\n#endif\n\n/**\n * Clean up the application.\n */\nvoid cleanUpAndExit (int exitCode) {\n\n\n  #ifdef WIN32\n    CancelIo(STDIN_FILENO);\n    WSACleanup();\n    if (nailgunsocket) {\n      closesocket(nailgunsocket);\n    }\n  #else\n    close(nailgunsocket);\n  #endif\n\n  exit(exitCode);\n}\n\n#ifdef WIN32\n/**\n * Handles an error.\n * Shows the message for the latest error then exits.\n */\nvoid handleError () {\n  LPVOID lpMsgBuf;\n  int error = GetLastError();\n\n  FormatMessage( \n    FORMAT_MESSAGE_ALLOCATE_BUFFER | \n    FORMAT_MESSAGE_FROM_SYSTEM | \n    FORMAT_MESSAGE_IGNORE_INSERTS,\n    NULL,\n    error,\n    MAKELANGID(LANG_NEUTRAL, SUBLANG_DEFAULT), /* Default language */\n    (LPTSTR) &lpMsgBuf,\n    0,\n    NULL);\n\n  /* Display the string. */\n  MessageBox( NULL, (LPCTSTR)lpMsgBuf, \"Error\", MB_OK | MB_ICONERROR );\n\n  /* Free the buffer. */\n  LocalFree( lpMsgBuf );\n \n  cleanUpAndExit(error);\n}\n#endif\n\n/**\n * Exits the client if the nailgun server ungracefully shut down the connection.\n */\nvoid handleSocketClose() {\n  cleanUpAndExit(NAILGUN_CONNECTION_BROKEN);\n}\n\n/**\n * Writes everything in the specified buffer to the specified\n * socket handle.\n *\n * @param s the socket descriptor\n * @param buf the buffer containing the data to send\n * @param len the number of bytes to send.  Also used to\n *            return the number of bytes sent.\n * @return total bytes written or 0 if failure\n */\nint sendAll(SOCKET s, char *buf, int len) {\n  int total = 0;      \n  int bytesleft = len; \n  int n = 0;\n\n  while(total < len) {\n    n = send(s, buf+total, bytesleft, SEND_FLAGS);\n    \n    if (n == -1) { \n      break;\n    }\n    \n    total += n;\n    bytesleft -= n;\n  }\n\n  return n==-1 ? 0:total; \n}\n\n/**\n * Sends a chunk noting the specified payload size and chunk type.\n * Waits for sending mutex on Win32.\n * \n * @param size the payload size\n * @param chunkType the chunk type identifier\n */\nvoid sendChunk(unsigned int size, char chunkType, char* buf) {\n  /* buffer used for reading and writing chunk headers */\n  char header[CHUNK_HEADER_LEN];\n  int bytesSent;\n\n  header[0] = (size >> 24) & 0xff;\n  header[1] = (size >> 16) & 0xff;\n  header[2] = (size >> 8) & 0xff;\n  header[3] = size & 0xff;\n  header[4] = chunkType;\n\n#ifdef WIN32\n  if (WaitForSingleObject(sending, INFINITE) != WAIT_OBJECT_0) {\n    handleError();\n  }\n#else\n  gettimeofday(&sendtime, NULL);\n#endif\n\n  bytesSent = sendAll(nailgunsocket, header, CHUNK_HEADER_LEN);\n  if (bytesSent != 0 && size > 0) {\n    bytesSent = sendAll(nailgunsocket, buf, size);\n  } else if (bytesSent == 0 && (chunkType != CHUNKTYPE_HEARTBEAT || errno != EPIPE)) {\n    perror(\"send\");\n    handleSocketClose();\n  }\n\n#ifdef WIN32\n  ReleaseMutex(sending);\n#endif\n}\n\n/**\n * Sends the contents of the specified file as a long argument (--nailgun-filearg)\n * This is sent as one or more chunks of type CHUNK_LONGARG.  The end of the argument\n * is indicated by an empty chunk.\n *\n * @param filename the name of the file to send.\n * @return nonzero on failure\n */\nint sendFileArg(char *filename) {\n  int i, f;\n  \n  if ((f = open(filename, O_RDONLY)) < 0) {\n    perror(\"--nailgun-filearg\");\n    return 1;  \n  }\n\n  i = read(f, buf, BUFSIZE);\n  while (i > 0) {\n    sendChunk(i, CHUNKTYPE_LONGARG, buf);\n    i = read(f, buf, BUFSIZE);\n  }\n  if (i < 0) {\n    perror(\"--nailgun-filearg\");\n    return 1;\n  }\n  sendChunk(0, CHUNKTYPE_LONGARG, buf);\n  \n  close(f);\n  return 0;\n}\n\n/**\n * Sends a null-terminated string with the specified chunk type.\n *\n * @param chunkType the chunk type identifier\n * @param text the null-terminated string to send\n */\nvoid sendText(char chunkType, char *text) {\n  int len = text ? strlen(text) : 0;\n  sendChunk(len, chunkType, text);\n}\n\n/**\n * Receives len bytes from the nailgun socket and copies them to the specified file descriptor.\n * Used to route data to stdout or stderr on the client.\n *\n * @param destFD the destination file descriptor (stdout or stderr)\n * @param len the number of bytes to copy\n */\nvoid recvToFD(HANDLE destFD, char *buf, unsigned long len) {\n  unsigned long bytesRead = 0;\n  int bytesCopied;\n  \n  while (bytesRead < len) {\n    unsigned long bytesRemaining = len - bytesRead;\n    int bytesToRead = (BUFSIZE < bytesRemaining) ? BUFSIZE : bytesRemaining;\n    int thisPass = 0;\n    \n    thisPass = recv(nailgunsocket, buf, bytesToRead, MSG_WAITALL);\n    if (thisPass == 0 || thisPass == -1) {\n      perror(\"recv\");\n      handleSocketClose();\n    }\n    bytesRead += thisPass;\n\n    bytesCopied = 0;\n\n    while(bytesCopied < thisPass) {\n      #ifdef WIN32\n        DWORD thisWrite =  0;\n\n        WriteFile(destFD, buf + bytesCopied, thisPass - bytesCopied,\n          &thisWrite, NULL);\n\n        if (thisWrite < 0) {\n          break;\n        }\n\n        bytesCopied += thisWrite;\n      #else\n        int bytesWritten = write(destFD, buf + bytesCopied, thisPass - bytesCopied);\n        if (bytesWritten == -1) {\n          perror(\"write\");\n          handleSocketClose();\n        }\n        bytesCopied += bytesWritten;\n      #endif\n    }  \n  }\n}\n\nunsigned long recvToBuffer(unsigned long len) {\n  unsigned long bytesRead = 0;\n  while(bytesRead < len) {\n    int thisPass = recv(nailgunsocket, buf + bytesRead, len - bytesRead, MSG_WAITALL);\n    if (thisPass == 0 || thisPass == -1) {\n        perror(\"recv\");\n        handleSocketClose();\n    }\n    bytesRead += thisPass;\n  }\n  return bytesRead;\n}\n\n/**\n * Processes an exit chunk from the server.  This is just a string\n * containing the exit code in decimal format.  It should fit well\n * within our buffer, so assume that it does.\n *\n * @param len the current length of the buffer containing the exit code.\n */\nvoid processExit(char *buf, unsigned long len) {\n  int exitcode;\n  int bytesToRead = (BUFSIZE - 1 < len) ? BUFSIZE - 1 : len;\n  int bytesRead = recvToBuffer(bytesToRead);\n  \n  if (bytesRead < 0) {\n    handleSocketClose();\n  }\n  \n  buf[bytesRead] = 0;\n  \n  exitcode = atoi(buf);\n  \n  cleanUpAndExit(exitcode);\n}\n\n\n/**\n * Sends len bytes from buf to the nailgun server in a stdin chunk.\n *\n * @param buf the bytes to send\n * @param len the number of bytes to send\n */\nvoid sendStdin(char *buf, unsigned int len) {\n#ifndef WIN32\n  readyToSend = 0;\n#endif\n  sendChunk(len, CHUNKTYPE_STDIN, buf);\n}\n\n/**\n * Sends a stdin-eof chunk to the nailgun server\n */\nvoid processEof() {\n  sendChunk(0, CHUNKTYPE_STDIN_EOF, buf);\n}\n\n/**\n * Sends a heartbeat chunk to let the server know the client is still alive.\n */\nvoid sendHeartbeat() {\n  sendChunk(0, CHUNKTYPE_HEARTBEAT, buf);\n}\n\n#ifdef WIN32\n\nHANDLE createEvent(BOOL manualReset) {\n  return CreateEvent(NULL, /* default security */\n\t\t     manualReset,\n\t\t     FALSE, /* initial state unsignalled */\n\t\t     NULL /* unnamed event */);\n}\n\nDWORD WINAPI sendHeartbeats(LPVOID lpParameter) {\n\t\t\n\t/* this could be made more efficient by only sending heartbeats when stdin chunks aren't being sent */\n\tfor (;;) {\n\t\tSleep(HEARTBEAT_TIMEOUT_MILLIS);\n\t\tsendHeartbeat();\n\t}\n}\n\n/**\n * Thread main for reading from stdin and sending\n */\nDWORD WINAPI processStdin (LPVOID lpParameter) {\n  /* buffer used for reading and sending stdin chunks */\n  char wbuf[BUFSIZE];\n\n  /* number of bytes read */\n  DWORD numberOfBytes;\n\n  for (;;) {\n\n    /* wait for ready to send */\n    if(WaitForSingleObject(readyToSend, INFINITE) != WAIT_OBJECT_0) {\n      handleError();\n    }\n\n\t/* read data from stdin */\n\tif (! ReadFile(NG_STDIN_FILENO, wbuf, BUFSIZE, &numberOfBytes, NULL)) {\n\t\tif (numberOfBytes != 0) {\n\t\t\thandleError();\n\t\t}\n\t}\n\n    /* send data to server */\n    if (numberOfBytes > 0) {\n      sendStdin(wbuf, numberOfBytes);\n    } else {\n      processEof();\n      break;\n    }\n\n  }\n  return 0;\n}\n#else\n/**\n * Reads from stdin and transmits it to the nailgun server in a stdin chunk.\n * Sends a stdin-eof chunk if necessary.\n *\n * @return zero if eof has been reached.\n */\nint processStdin() {\n\tint bytesread = read(STDIN_FILENO, buf, BUFSIZE);\n\tif (bytesread > 0) {\n\t\tsendStdin(buf, bytesread);\n\t} else if (bytesread == 0) {\n\t\tprocessEof();\n\t}\n\treturn(bytesread);\n}\n#endif\n\n#ifdef WIN32\n/**\n * Initialise Windows sockets\n */\nvoid initSockets () {\n  WSADATA win_socket_data;     /* required to initialise winsock */\n  \n  WSAStartup(2, &win_socket_data);\n\n  /* create flow control event and mutex */\n  readyToSend = createEvent(FALSE);\n  sending = CreateMutex(NULL, FALSE, NULL);\n}\n#endif\n\n#ifdef WIN32\n/**\n * Initialise the asynchronous io.\n */\nvoid initIo () {\n  /* create non-blocking console io */\n  AllocConsole();\n  \n  NG_STDIN_FILENO = GetStdHandle(STD_INPUT_HANDLE);\n  NG_STDOUT_FILENO = GetStdHandle(STD_OUTPUT_HANDLE);\n  NG_STDERR_FILENO = GetStdHandle(STD_ERROR_HANDLE);\n}\n#endif\n\n#ifdef WIN32\n/**\n * Initialise the asynchronous io.\n */\nvoid winStartInput () {\n  SECURITY_ATTRIBUTES securityAttributes;\n  DWORD threadId = 0;\n\n  securityAttributes.bInheritHandle = TRUE;\n  securityAttributes.lpSecurityDescriptor = NULL;\n  securityAttributes.nLength = 0;\n  \n  if (!CreateThread(&securityAttributes, 0, &processStdin, NULL, 0, &threadId)) {\n    handleError();\n  }\n\n  if (!CreateThread(&securityAttributes, 0, &sendHeartbeats, NULL, 0, &threadId)) {\n    handleError();\n  }\n}\n#endif\n\n/**\n * Processes data from the nailgun server.\n */\nvoid processnailgunstream() {\n\n  /*for (;;) {*/\n    unsigned long len;\n    char chunkType;\n\n    recvToBuffer(CHUNK_HEADER_LEN);\n\n    len = ((buf[0] << 24) & 0xff000000)\n      | ((buf[1] << 16) & 0x00ff0000)\n      | ((buf[2] << 8) & 0x0000ff00)\n      | ((buf[3]) & 0x000000ff);\n  \n    chunkType = buf[4];\n  \n    switch(chunkType) {\n      case CHUNKTYPE_STDOUT: recvToFD(NG_STDOUT_FILENO, buf, len);\n            break;\n      case CHUNKTYPE_STDERR: recvToFD(NG_STDERR_FILENO, buf, len);\n            break;\n      case CHUNKTYPE_EXIT:   processExit(buf, len);\n            break;\n      case CHUNKTYPE_SENDINPUT:\n#ifdef WIN32\n            SetEvent(readyToSend);\n#else\n            readyToSend = 1;\n#endif\n            break;\n      default:  fprintf(stderr, \"Unexpected chunk type %d ('%c')\\n\", chunkType, chunkType);\n          cleanUpAndExit(NAILGUN_UNEXPECTED_CHUNKTYPE);\n    }\n  /*}*/\n}\n\n/**\n * Returns the time interval between start and end in milliseconds.\n * @param end the end time\n * @param start the start time\n */\nint intervalMillis(struct timeval end, struct timeval start) {\n\n  return ((end.tv_sec - start.tv_sec) * 1000) + \n    ((end.tv_usec - start.tv_usec) /1000);\n}\n\n/**\n * Trims any path info from the beginning of argv[0] to determine\n * the name used to launch the client.\n *\n * @param s argv[0]\n */\nchar *shortClientName(char *s) {\n  char *result = strrchr(s, FILE_SEPARATOR);\n  return ((result == NULL) ? s : result + 1);\n}\n\n/**\n * Returns true if the specified string is the name of the nailgun\n * client.  The comparison is made case-insensitively for windows.\n *\n * @param s the program name to check\n */\nint isNailgunClientName(char *s) {\n  /* VMS can't get the command name from argv[0] when defined\n     as a foreign command, as the symbol is expanded. Aliases\n     are supported by defining a foreign command that includes\n     the class alias argument, e.g.\n         ng==\"$path:[to]ng.exe\"\n         alias==ng+\" \"\"alias\"\"\"\n  */\n  #ifdef __VMS\n  return (1);\n  #else\n  #ifdef WIN32\n  return (!strcasecmp(s, NAILGUN_CLIENT_NAME) ||\n           !strcasecmp(s, NAILGUN_CLIENT_NAME_EXE));\n  #else\n  return(!(strcmp(s, NAILGUN_CLIENT_NAME)));\n  #endif\n  #endif\n}\n\n/**\n * Displays usage info and bails\n */\nvoid usage(int exitcode) {\n  fprintf(stderr, \"NailGun v%s\\n\\n\", NAILGUN_VERSION);\n  fprintf(stderr, \"Usage: ng class [--nailgun-options] [args]\\n\");\n  fprintf(stderr, \"          (to execute a class)\\n\");\n  fprintf(stderr, \"   or: ng alias [--nailgun-options] [args]\\n\");\n  fprintf(stderr, \"          (to execute an aliased class)\\n\");\n  fprintf(stderr, \"   or: alias [--nailgun-options] [args]\\n\");\n  fprintf(stderr, \"          (to execute an aliased class, where \\\"alias\\\"\\n\");\n  fprintf(stderr, \"           is both the alias for the class and a symbolic\\n\");\n  fprintf(stderr, \"           link to the ng client)\\n\\n\");\n  \n  fprintf(stderr, \"where options include:\\n\");\n  fprintf(stderr, \"   --nailgun-D<name>=<value>   set/override a client environment variable\\n\");\n  fprintf(stderr, \"   --nailgun-version           print product version and exit\\n\");\n  fprintf(stderr, \"   --nailgun-showversion       print product version and continue\\n\");\n  fprintf(stderr, \"   --nailgun-server            to specify the address of the nailgun server\\n\");\n  fprintf(stderr, \"                               (default is NAILGUN_SERVER environment variable\\n\");\n  fprintf(stderr, \"                               if set, otherwise localhost)\\n\");\n  fprintf(stderr, \"   --nailgun-port              to specify the port of the nailgun server\\n\");\n  fprintf(stderr, \"                               (default is NAILGUN_PORT environment variable\\n\");\n  fprintf(stderr, \"                               if set, otherwise 2113)\\n\");  \n  fprintf(stderr, \"   --nailgun-filearg FILE      places the entire contents of FILE into the\\n\");\n  fprintf(stderr, \"                               next argument, which is interpreted as a string\\n\");\n  fprintf(stderr, \"                               using the server's default character set.  May be\\n\");\n  fprintf(stderr, \"                               specified more than once.\\n\");\n  fprintf(stderr, \"   --nailgun-help              print this message and exit\\n\");\n\n  cleanUpAndExit(exitcode);\n}\n\nint main(int argc, char *argv[], char *env[]) {\n  int i;\n  struct sockaddr_in server_addr;\n  char *nailgun_server;        /* server as specified by user */\n  char *nailgun_port;          /* port as specified by user */\n  char *cwd;\n  u_short port;                /* port */\n  struct hostent *hostinfo;\n  char *cmd = \"prism.PrismNG\";\n  int firstArgIndex;           /* the first argument _to pass to the server_ */\n  char isattybuf[] = NAILGUN_TTY_FORMAT;\n\n  #ifndef WIN32\n    fd_set readfds;\n    int eof = 0;\n    struct timeval readtimeout;\n    struct timeval currenttime;\n    memset(&sendtime, '\\0', sizeof(sendtime));\n  #endif\n\n  #ifdef WIN32\n  initSockets();\n  #endif\n  \n  /* start with environment variable.  default to localhost if not defined. */\n  nailgun_server = getenv(\"NAILGUN_SERVER\");\n  if (nailgun_server == NULL) {\n    nailgun_server = \"127.0.0.1\";\n  }\n  \n  /* start with environment variable.  default to normal nailgun port if not defined */\n  nailgun_port = getenv(\"NAILGUN_PORT\");\n  if (nailgun_port == NULL) {\n    nailgun_port = NAILGUN_PORT_DEFAULT;\n  }\n  \n  /* if executing just the ng client with no arguments or -h|--help, then\n     display usage and exit.  Don't handle -h|--help if a command other than\n     ng or ng.exe was used, since the appropriate nail should then handle\n     --help. */\n  if (argc > 1 && strcmp(\"stop\", argv[1]) == 0) {\n    cmd = \"ng-stop\";\n  }\n     \n  /* if executing just the ng client with no arguments or -h|--help, then\n     display usage and exit.  Don't handle -h|--help if a command other than\n     ng or ng.exe was used, since the appropriate nail should then handle\n     --help. */\n  if (((argc == 2 && strcmp(\"--help\", argv[1]) == 0) ||\n\t  (argc == 2 && strcmp(\"-h\", argv[1]) == 0))) usage(0);\n     \n  firstArgIndex = 1;\n\n  /* quite possibly the lamest commandline parsing ever. \n     look for the two args we care about (--nailgun-server and\n     --nailgun-port) and NULL them and their parameters after\n     reading them if found.  later, when we send args to the\n     server, skip the null args. */\n  for (i = 1; i < argc; ++i) {\n    if (!strcmp(\"--nailgun-server\", argv[i])) {\n      if (i == argc - 1) usage(NAILGUN_BAD_ARGUMENTS);\n      nailgun_server = argv[i + 1];\n      argv[i] = argv[i + 1] = NULL;\n      ++i;\n    } else if(!strcmp(\"--nailgun-port\", argv[i])) {\n      if (i == argc - 1) usage(NAILGUN_BAD_ARGUMENTS);\n      nailgun_port = argv[i + 1];\n      argv[i] = argv[i + 1]= NULL;\n      ++i;\n    } else if (!strcmp(\"--nailgun-filearg\", argv[i])) {\n      /* just verify usage here.  do the rest when sending args. */\n      if (i == argc - 1) usage (NAILGUN_BAD_ARGUMENTS);\n    } else if (!strcmp(\"--nailgun-version\", argv[i])) {\n      printf(\"NailGun client version %s\\n\", NAILGUN_VERSION);\n      cleanUpAndExit(0);\n    } else if (!strcmp(\"--nailgun-showversion\", argv[i])) {\n      printf(\"NailGun client version %s\\n\", NAILGUN_VERSION);\n      argv[i] = NULL;\n    } else if (!strcmp(\"--nailgun-help\", argv[i])) {\n      usage(0);\n    } else if (cmd == NULL) {\n      cmd = argv[i];\n      firstArgIndex = i + 1;\n    }\n  }\n\n  /* jump through a series of connection hoops */  \n  hostinfo = gethostbyname(nailgun_server);\n\n  if (hostinfo == NULL) {\n    fprintf(stderr, \"Unknown host: %s\\n\", nailgun_server);\n    cleanUpAndExit(NAILGUN_CONNECT_FAILED);\n  }\n \n  port = atoi(nailgun_port);\n\n  if ((nailgunsocket = socket(AF_INET, SOCK_STREAM, 0)) == -1) {\n    perror(\"socket\");\n    cleanUpAndExit(NAILGUN_SOCKET_FAILED);\n  }\n\n  server_addr.sin_family = AF_INET;    \n  server_addr.sin_port = htons(port);\n  server_addr.sin_addr = *(struct in_addr *) hostinfo->h_addr;\n  \n  memset(&(server_addr.sin_zero), '\\0', 8);\n\n  if (connect(nailgunsocket, (struct sockaddr *)&server_addr,\n    sizeof(struct sockaddr)) == -1) {\n    perror(\"connect\");\n    cleanUpAndExit(NAILGUN_CONNECT_FAILED);\n  } \n    \n  /* ok, now we're connected.  first send all of the command line\n     arguments for the server, if any.  remember that we may have\n     marked some arguments NULL if we read them to specify the\n     nailgun server and/or port */\n  for(i = firstArgIndex; i < argc; ++i) {\n    if (argv[i] != NULL) {\n      if (!strcmp(\"--nailgun-filearg\", argv[i])) {\n        int sendResult = sendFileArg(argv[++i]);\n        if (sendResult != 0) {\n          perror(\"send\");\n          handleSocketClose();\n        }\n      } else sendText(CHUNKTYPE_ARG, argv[i]);\n    }\n  }\n\n  /* now send environment */  \n  sendText(CHUNKTYPE_ENV, NAILGUN_FILESEPARATOR);\n  sendText(CHUNKTYPE_ENV, NAILGUN_PATHSEPARATOR);\n#ifndef WIN32\n  /* notify isatty for standard pipes */\n  for(i = 0; i < 3; i++) {\n    sprintf(isattybuf, NAILGUN_TTY_FORMAT, i, isatty(i));\n    sendText(CHUNKTYPE_ENV, isattybuf);\n  }\n#endif\n  /* forward the client process environment */\n  for(i = 0; env[i]; ++i) {\n    sendText(CHUNKTYPE_ENV, env[i]);\n  }\n  \n  /* now send the working directory */\n  cwd = getcwd(NULL, 0);\n  sendText(CHUNKTYPE_DIR, cwd);\n  free(cwd);\n  \n  /* and finally send the command.  this marks the point at which\n     streams are linked between client and server. */\n  sendText(CHUNKTYPE_CMD, cmd);\n\n  \n  /* initialise the std-* handles and the thread to send stdin to the server */ \n  #ifdef WIN32\n  initIo();\n  winStartInput();\n  #endif\n\n  /* stream forwarding loop */\t\n  while(1) {\n    #ifndef WIN32\n      FD_ZERO(&readfds);\n\n      /* don't select on stdin if we've already reached its end */\n      if (readyToSend && !eof) {\n\tFD_SET(NG_STDIN_FILENO, &readfds);\n      }\n\n      FD_SET(nailgunsocket, &readfds);\n\n      memset(&readtimeout, '\\0', sizeof(readtimeout));\n      readtimeout.tv_usec = HEARTBEAT_TIMEOUT_MILLIS * 1000;\n      if(select (nailgunsocket + 1, &readfds, NULL, NULL, &readtimeout) == -1) {\n\t  perror(\"select\");\n      }\n\t  \n      if (FD_ISSET(nailgunsocket, &readfds)) {\n    #endif\n\tprocessnailgunstream();\n    #ifndef WIN32\n      } else if (FD_ISSET(NG_STDIN_FILENO, &readfds)) {\n        int result = processStdin();\n        if (result == -1) {\n          perror(\"read\");\n          handleSocketClose();\n        } else if (result == 0) {\n          FD_CLR(NG_STDIN_FILENO, &readfds);\n          eof = 1;\n        }\n      }\n      gettimeofday(&currenttime, NULL);\n      if (intervalMillis(currenttime, sendtime) > HEARTBEAT_TIMEOUT_MILLIS) {\n\t  sendHeartbeat();\n      }\n    #endif\n  }  \n\n  /* normal termination is triggered by the server, and so occurs in processExit(), above */\n}\n"
  },
  {
    "path": "prism/src/prism/package-info.java",
    "content": "/**\n * The main Prism API, the command-line tool, and Java classes for symbolic data structures and algorithms.\n *\n * See {@link prism.Prism} for details.\n */\npackage prism;\n"
  },
  {
    "path": "prism/src/prism/prism.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <forejt@fi.muni.cz> (Masaryk University)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"prism.h\"\n#include <cstdio>\n#include <cmath>\n#include <new>\n#include <vector>\n#include \"jnipointer.h\"\n#include \"PrismNativeGlob.h\"\n\n//------------------------------------------------------------------------------\n\n// Get the current time in milliseconds (via Java).\n// Returns -1 in case of error obtaining the time.\n\nlong get_real_time(JNIEnv *env)\n{\n\tjlong ret = 0;\n\tif (env) {\n\t\tjclass cl = env->FindClass(\"java/lang/System\");\n\t\tjmethodID me = env->GetStaticMethodID(cl, \"currentTimeMillis\", \"()J\");\n\t\tret = env->CallLongMethod(cl, me);\n\t} else {\n\t\tret = -1;\n\t}\n\treturn ret;\n}\n\n//------------------------------------------------------------------------------\n\n// convert a list of strings (from java/jni) to an array of c strings.\n// actually stores arrays of both jstring objects and c strings, and also size\n// (because need these to free memory afterwards).\n\nvoid get_string_array_from_java(JNIEnv *env, jobject strings_list, jstring *&strings_jstrings, const char **&strings, int &size)\n{\n\tint i, j;\n\tjclass vn_cls;\n\tjmethodID vn_mid;\n\t// get size of vector of strings\n\tvn_cls = env->GetObjectClass(strings_list);\n\tvn_mid = env->GetMethodID(vn_cls, \"size\", \"()I\");\n\tif (vn_mid == 0) {\n\t\treturn;\n\t}\n\tsize = (int)env->CallIntMethod(strings_list,vn_mid);\n\t// put strings from vector into array\n\tstrings_jstrings = new jstring[size];\n\tstrings = new const char*[size];\n\tvn_mid = env->GetMethodID(vn_cls, \"get\", \"(I)Ljava/lang/Object;\");\n\tif (vn_mid == 0) {\n\t\treturn;\n\t}\n\tfor (i = 0; i < size; i++) {\n\t\tstrings_jstrings[i] = (jstring)env->CallObjectMethod(strings_list, vn_mid, i);\n\t\tstrings[i] = env->GetStringUTFChars(strings_jstrings[i], 0);\n\t}\n}\n\n//------------------------------------------------------------------------------\n\n// release the memory from a list of strings created by get_string_array_from_java\n\nvoid release_string_array_from_java(JNIEnv *env, jstring *strings_jstrings, const char **strings, jint size)\n{\n\t// release memory\n\tfor (int i = 0; i < size; i++) {\n\t\tenv->ReleaseStringUTFChars(strings_jstrings[i], strings[i]);\n\t}\n\tdelete[] strings_jstrings;\n\tdelete[] strings;\n}\n\n//------------------------------------------------------------------------------\n\n// Compute probabilities for the Poisson distribution efficiently and reliably,\n// truncating above and below for a provided error bound. Implements the algorithm from:\n// B. Fox and P. Glynn, Computing Poisson Probabilities,\n// Communications of the ACM 31(4):440-445, 1988.\n\n// Computes the probabilities for the Poisson distribution with rate q_tmax.\n// The ith probability is returned for L<=i<=R, where L and R\n// are determined according to the requested accuracy.\n// The sum of the probabilities will be greater than equal to 1-accuracy.\n// Furthermore, the sum of probabilities for i<L and i>R are both <=accuracy/2.\n// Thresholds for underflow and overflow should also be given.\n// Note that the Fox-Glynn method requires accuracy to be at least 1e-10.\n\n// The probabilities are given in an array in the form of weights;\n// these should be normalised by dividing by the sum of the weights.\n// These, and the left/right truncation points are all contained in\n// the returned FoxGlynnWeights struct.\n\n// On error, the member 'right' of the returned object is set to -1 and the\n// member array 'weights' is not allocated (does not need to be freed).\n\nEXPORT FoxGlynnWeights fox_glynn(double q_tmax, double underflow, double overflow, double accuracy)\n{\n\t// construct result struct and zero-initialise\n\t// this ensures that fgw.weights = nullptr in case we return early on error\n\tFoxGlynnWeights fgw{};\n\n\tif (q_tmax == 0.0) {\n\t\tprintf(\"Overflow: TA parameter qtmax = time * maxExitRate = 0.\");\n\t\tfgw.right = -1;\n\t\treturn fgw;\n\t}\n\n\tif (accuracy < 1e-10) {\n\t\tprintf(\"Overflow: Accuracy is smaller than Fox Glynn can handle (must be at least 1e-10).\");\n\t\tfgw.right = -1;\n\t\treturn fgw;\n\t}\n\n\tif (q_tmax < 400)\n\t{ //here naive approach should have better performance than Fox Glynn\n\t\tconst double expcoef = exp(-q_tmax); //the \"e^-lambda\" part of p.m.f. of Poisson dist.\n\t\tint k; //denotes that we work with event \"k steps occur\"\n\t\tdouble lastval; //(probability that exactly k events occur)/expcoef\n\t\tdouble accum; //(probability that 0 to k events occur)/expcoef\n\t\tdouble desval = (1-(accuracy/2.0)) / expcoef; //value that we want to accumulate in accum before we stop\n\t\tstd::vector<double> w; //stores weights computed so far.\n\t\t\n\t\t//k=0 is simple\n\t\tlastval = 1;\n\t\taccum = lastval;\n\t\tw.push_back(lastval * expcoef);\n\t\t\n\t\t//add further steps until you have accumulated enough\n\t\tk = 1;\n\t\tdo {\n\t\t\t// TODO: catch case where lastval gets so small that\n\t\t\t// accnum never reaches desval due to rounding/floating point precision errors (infinite loop)\n\n\t\t\tlastval *= q_tmax / k; // invariant: lastval = q_tmax^k / k!\n\t\t\taccum += lastval;\n\t\t\tw.push_back(lastval * expcoef);\n\t\t\tk++;\n\t\t} while (accum < desval);\n\n\t\t//store all data to fgw\n\t\tfgw.left=0;\n\t\tfgw.right=k-1;\n\t\tfgw.weights = new double[k];\n\n\t\tfor(int i = 0; i < w.size(); i++)\n\t\t{\n\t\t\tfgw.weights[i] = w[i];\t\t\t\n\t\t}\n\n\t\t//we return actual weights, so no reweighting should be done\n\t\tfgw.total_weight = 1.0;\n\t}\n\telse\n\t{ //use actual Fox Glynn for q_tmax>400\n\t\tconst double factor = 1e+10;\n\n\t\tconst long m = (long) q_tmax; //mode\n\t\t//run FINDER to get left, right and weight[m]\n\t\t{\n\t\t\tconst double sqrtpi = 1.7724538509055160; //square root of PI\n\t\t\tconst double sqrt2 = 1.4142135623730950; //square root of 2\n\t\t\tconst double sqrtq = sqrt(q_tmax);\n\t\t\tconst double aq = (1.0 + 1.0/q_tmax) * exp(0.0625) * sqrt2; //a_\\lambda from the paper\t\t\t\n\t\t\tconst double bq = (1.0 + 1.0/q_tmax) * exp(0.125/q_tmax); //b_\\lambda from the paper\n\n\t\t\t//use Corollary 1 to find right truncation point\n\t\t\tconst double lower_k_1 = 1.0 / (2.0*sqrt2*q_tmax); //lower bound on k from Corollary 1\n\t\t\tconst double upper_k_1 = sqrtq / (2.0*sqrt2); //upper bound on k from Corollary 1\n\t\t\tdouble k;\n\n\t\t\t//justification for increment is in the paper:\n\t\t\t//\"increase k through the positive integers greater than 3\"\n\t\t\tfor(k=lower_k_1; k <= upper_k_1;\n\t\t\t\tk=(k==lower_k_1)? k+4 : k+1 )\n\t\t\t{\n\t\t\t\tdouble dkl = 1.0/(1 - exp(-(2.0/9.0)*(k*sqrt2*sqrtq+1.5))); //d(k,\\lambda) from the paper\n\t\t\t\tdouble res = aq*dkl*exp(-k*k/2.0)/(k*sqrt2*sqrtpi); //right hand side of the equation in Corollary 1\n\t\t\t\tif (res <= accuracy/2.0)\n\t\t\t\t{\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (k>upper_k_1)\n\t\t\t\tk=upper_k_1;\n\n\t\t\tconst double right_d = ceil(m+k*sqrt2*sqrtq + 1.5);\n\t\t\tfgw.right = (long) right_d; \n\n\t\t\t//use Corollary 2 to find left truncation point\n\t\t\t//NOTE: the original implementation used some upper bound on k,\n\t\t\t//      however, I didn't find it in the paper and I think it is not needed\n\t\t\tconst double lower_k_2 = 1.0/(sqrt2*sqrtq); //lower bound on k from Corollary 2\n\n\t\t\tdouble res;\n\t\t\tk=lower_k_2;\n\t\t\tdo\n\t\t\t{\n\t\t\t\tres = bq*exp(-k*k/2.0)/(k*sqrt2*sqrtpi); //right hand side of the equation in Corollary 2\n\t\t\t\tk++;\t\t\t\n\t\t\t}\n\t\t\twhile (res > accuracy/2.0);\n\t\t\t\n\t\t\tfgw.left = (long) (m - k*sqrtq - 1.5);\n\t\t\t\n\t\t\t//According to the paper, we should check underflow of lower bound.\n\t\t\t//However, it seems that for no reasonable values this can happen.\n\t\t\t//And neither the original implementation checked it\n\t\t\t\n\t\t\tdouble wm = overflow / (factor*(fgw.right - fgw.left));\n\n\t\t\tfgw.weights = new double[fgw.right-fgw.left+1];\n\t\t\tfgw.weights[m-fgw.left] = wm;\n\t\t}\n\t\t//end of FINDER\n\n\t\t//compute weights\n\t\t//(at this point fgw.left, fgw.right and fgw.weight[m] is known)\n\t\t\n\t\t//Down from m\n\t\tfor(long j=m; j>fgw.left; j--)\n\t\t\tfgw.weights[j-1-fgw.left] = (j/q_tmax)*fgw.weights[j-fgw.left];\n\t\t//Up from m\n\t\tfor(long j=m; j<fgw.right; j++)\n\t\t\tfgw.weights[j+1-fgw.left] = (q_tmax/(j+1))*fgw.weights[j-fgw.left];\n\n\t\t//Compute total_weight (i.e. W in the paper)\n\t\t//instead of summing from left to right, start from smallest\n\t\t//and go to highest weights to prevent roundoff\n\t\tfgw.total_weight = 0.0;\n\t\tlong s = fgw.left;\n\t\tlong t = fgw.right;\n\t\twhile (s<t)\n\t\t{\n\t\t\tif(fgw.weights[s - fgw.left] <= fgw.weights[t - fgw.left])\n\t\t\t{\n\t\t\t\tfgw.total_weight += fgw.weights[s-fgw.left];\n\t\t\t\ts++;\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\tfgw.total_weight += fgw.weights[t-fgw.left];\n\t\t\t\tt--;\n\t\t\t}\n\t\t}\n\t\tfgw.total_weight += fgw.weights[s-fgw.left];\n\t}\n\treturn fgw;\n}\n\n//------------------------------------------------------------------------------\n\nconst char* get_export_iterations_filename() {\n\treturn export_iterations_filename;\n}\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/pta/BackwardsReach.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\nimport prism.*;\nimport explicit.*;\n\npublic class BackwardsReach extends PrismComponent\n{\n\t/**\n\t * Create a new MDPModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic BackwardsReach(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Compute the min/max probability of reaching a target in a PTA, from the initial state,\n\t * using the backwards reachability method.\n\t * @param pta The PTA\n\t * @param targetLocs Target locations\n\t * @param targetConstraint Target timing contraint\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tpublic double computeProbabilisticReachability(PTA pta, BitSet targetLocs, boolean min) throws PrismException\n\t{\n\t\tif (min)\n\t\t\tthrow new PrismException(\"Backwards reachability does not yet support minmum probabilities\");\n\n\t\t// Build backwards graph\n\t\tBackwardsReachabilityGraph graph = buildBackwardsGraph(pta, targetLocs);\n\n\t\t// Build corresponding MDP\n\t\tmainLog.print(\"Building MDP... \");\n\t\tmainLog.flush();\n\t\tMDP mdp = graph.buildMDP(pta);\n\t\tmainLog.println(mdp.infoString());\n\t\t//mdp.exportToDotFile(\"mdp.dot\", target);\n\n\t\t// Compute reachability probs on MDP\n\t\tMDPModelChecker mc = new MDPModelChecker(this);\n\t\tmc.setPrecomp(false);\n\t\tModelCheckerResult res = mc.computeReachProbs(mdp, graph.getTarget(), false);\n\n\t\t// Result is max prob over all initial states\n\t\treturn Math.max(0.0, Utils.minMaxOverArraySubset(res.soln, graph.getInitialStates(), false));\n\t}\n\n\t/**\n\t * Build a backwards reachability graph, from a PTA object.\n\t */\n\tpublic BackwardsReachabilityGraph buildBackwardsGraph(PTA pta, BitSet targetLocs) throws PrismException\n\t{\n\t\tLocZone lz;\n\t\tLinkedList<LocZone> explore; // (Waiting)\n\t\tIndexedSet<LocZone> found; // (Visited)\n\t\tList<LocZone> states;\n\t\tBackwardsReachabilityGraph graph;\n\t\tint src, dest, count;\n\t\tlong timer;\n\n\t\tmainLog.print(\"\\nBuilding backwards reachability graph...\");\n\t\tmainLog.flush();\n\t\tProgressDisplay progress = new ProgressDisplay(mainLog);\n\t\tprogress.start();\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Initialise data structures\n\t\tgraph = new BackwardsReachabilityGraph();\n\t\tfound = new IndexedSet<LocZone>();\n\t\texplore = new LinkedList<LocZone>();\n\t\tgraph.states = states = new ArrayList<LocZone>();\n\n\t\t// Add target states\n\t\tcount = 0;\n\t\tfor (int loc = targetLocs.nextSetBit(0); loc >= 0; loc = targetLocs.nextSetBit(loc + 1)) {\n\t\t\tZone zTarget = DBM.createTrue(pta);\n\t\t\tzTarget.addConstraints(pta.getInvariantConstraints(loc));\n\t\t\tLocZone lzTarget = new LocZone(loc, zTarget);\n\t\t\tfound.add(lzTarget);\n\t\t\texplore.add(lzTarget);\n\t\t\tstates.add(lzTarget);\n\t\t\tgraph.addState(pta.getTransitions(loc));\n\t\t\tgraph.addTargetState(count++);\n\t\t}\n\n\t\t// Reachability loop\n\t\tdest = -1;\n\t\t// While there are unexplored symbolic states...\n\t\twhile (!explore.isEmpty()) {\n\t\t\t// Pick next state to explore\n\t\t\t// NB: States are added in order found so we know index of lz is dest+1\n\t\t\tlz = explore.removeFirst();\n\t\t\tdest++;\n\t\t\t//mainLog.println(\"Exploring: \" + dest + \":\" + lz);\n\n\t\t\t// Time predecessor (same for all incoming edges)\n\t\t\tlz = lz.deepCopy();\n\t\t\tlz.tPre(pta);\n\n\t\t\t// For each incoming transition...\n\t\t\t// TODO: make more efficient\n\t\t\tfor (int ii = 0; ii < pta.getNumLocations(); ii++) {\n\t\t\t\tif (targetLocs.get(ii))\n\t\t\t\t\tcontinue;\n\t\t\t\tint iTrans = -1;\n\t\t\t\tfor (Transition tr : pta.getTransitions(ii)) {\n\t\t\t\t\tiTrans++;\n\t\t\t\t\tint numEdges = tr.getNumEdges();\n\t\t\t\t\tfor (int iEdge = 0; iEdge < numEdges; iEdge++) {\n\t\t\t\t\t\tEdge edge = tr.getEdges().get(iEdge);\n\t\t\t\t\t\t//mainLog.println(edge);\n\t\t\t\t\t\tif (edge.getDestination() != lz.loc)\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\tLocZone lzSrc = lz.deepCopy();\n\t\t\t\t\t\tlzSrc.dPre(edge);\n\t\t\t\t\t\t// If predecessor state is non-empty\n\t\t\t\t\t\tif (!lzSrc.zone.isEmpty()) {\n\t\t\t\t\t\t\t// add state\n\t\t\t\t\t\t\tif (found.add(lzSrc)) {\n\t\t\t\t\t\t\t\t//mainLog.println(\"Added \" + Yset.getIndexOfLastAdd() + \":\" + lzSrc);\n\t\t\t\t\t\t\t\texplore.add(lzSrc);\n\t\t\t\t\t\t\t\tstates.add(lzSrc);\n\t\t\t\t\t\t\t\tgraph.addState(pta.getTransitions(lzSrc.loc));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// end add state\n\t\t\t\t\t\t\tsrc = found.getIndexOfLastAdd();\n\t\t\t\t\t\t\t//mainLog.println(\"D += \" + src + \":\" + lz2 + \"->\" + dest + \":...\");\n\t\t\t\t\t\t\tgraph.addTransition(src, iTrans, iEdge, dest);\n\t\t\t\t\t\t\t//mainLog.println(src + \":\" + graph.getList(src));\n\n\t\t\t\t\t\t\t// For each state that lzTmp intersects lzSrc\n\t\t\t\t\t\t\tint numStatesSoFar = states.size();\n\t\t\t\t\t\t\tfor (int src2 = 0; src2 < numStatesSoFar; src2++) {\n\t\t\t\t\t\t\t\t// TODO: if any edges in graph...\n\t\t\t\t\t\t\t\tLocZone lzTmp = states.get(src2);\n\t\t\t\t\t\t\t\tif (src2 != src && lzTmp.loc == lzSrc.loc) {\n\t\t\t\t\t\t\t\t\tZone zTmp = lzTmp.zone.deepCopy();\n\t\t\t\t\t\t\t\t\tzTmp.intersect(lzSrc.zone);\n\t\t\t\t\t\t\t\t\t//mainLog.println(\"intersect with \" + st + \":\" + lzTmp + \": \" + zTmp);\n\t\t\t\t\t\t\t\t\tif (!zTmp.isEmpty()) {\n\t\t\t\t\t\t\t\t\t\t// For all reachability graph edges from lzTmp...\n\t\t\t\t\t\t\t\t\t\tint numTrans2 = graph.getList(src2).size();\n\t\t\t\t\t\t\t\t\t\tfor (int iTrans2 = 0; iTrans2 < numTrans2; iTrans2++) {\n\t\t\t\t\t\t\t\t\t\t\tList<List<Integer>> edges2 = graph.getList(src2).get(iTrans2);\n\t\t\t\t\t\t\t\t\t\t\tint numEdges2 = edges2.size();\n\t\t\t\t\t\t\t\t\t\t\tif (numEdges2 < 2) {\n\t\t\t\t\t\t\t\t\t\t\t\t//mainLog.println(\"SKIP\");\n\t\t\t\t\t\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\t\tfor (int iEdge2 = 0; iEdge2 < numEdges2; iEdge2++) {\n\t\t\t\t\t\t\t\t\t\t\t\tList<Integer> dests2 = edges2.get(iEdge2);\n\t\t\t\t\t\t\t\t\t\t\t\tint numDests2 = dests2.size();\n\t\t\t\t\t\t\t\t\t\t\t\tfor (int iDest2 = 0; iDest2 < numDests2; iDest2++) {\n\t\t\t\t\t\t\t\t\t\t\t\t\tint dest2 = dests2.get(iDest2);\n\t\t\t\t\t\t\t\t\t\t\t\t\t// Edge (src2, iTrans2, iEdge2, dest2)\n\n\t\t\t\t\t\t\t\t\t\t\t\t\t// add state\n\n\t\t\t\t\t\t\t\t\t\t\t\t\tLocZone lz3 = new LocZone(lzSrc.loc, zTmp);\n\t\t\t\t\t\t\t\t\t\t\t\t\tif (found.add(lz3)) {\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t//mainLog.println(\"Added2 \" + Yset.getIndexOfLastAdd() + \":\" + lz3);\n\t\t\t\t\t\t\t\t\t\t\t\t\t\texplore.add(lz3);\n\t\t\t\t\t\t\t\t\t\t\t\t\t\tstates.add(lz3);\n\t\t\t\t\t\t\t\t\t\t\t\t\t\tgraph.addState(pta.getTransitions(lz3.loc));\n\t\t\t\t\t\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t//mainLog.println(\"Reusing \" + Yset.getIndexOfLastAdd() + \":\" + lz3);\n\t\t\t\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\t\t\t\t// end add state\n\t\t\t\t\t\t\t\t\t\t\t\t\tint src3 = found.getIndexOfLastAdd();\n\t\t\t\t\t\t\t\t\t\t\t\t\t//mainLog.println(\"^D += \" + src3 + \":\" + lz3 + \"->\" + dest + \":...\");\n\t\t\t\t\t\t\t\t\t\t\t\t\tgraph.addTransition(src3, iTrans, iEdge, dest);\n\t\t\t\t\t\t\t\t\t\t\t\t\t//mainLog.println(src3 + \":\" + graph.getList(src3));\n\t\t\t\t\t\t\t\t\t\t\t\t\t//mainLog.println(\"^D += \" + src3 + \":\" + lz3 + \"->\" + dest2 + \":...\");\n\t\t\t\t\t\t\t\t\t\t\t\t\tgraph.addTransition(src3, iTrans2, iEdge2, dest2);\n\t\t\t\t\t\t\t\t\t\t\t\t\t//mainLog.println(src3 + \":\" + graph.getList(src3));\n\t\t\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Print some progress info occasionally\n\t\t\tif (progress.ready())\n\t\t\t\tprogress.update(found.size());\n\t\t}\n\n\t\t// Tidy up progress display\n\t\tprogress.update(found.size());\n\t\tprogress.end(\" states\");\n\n\t\t// Determine which are initial states\n\t\t// (NB: assume initial location = 0)\n\t\tint numStates = states.size();\n\t\tfor (int st = 0; st < numStates; st++) {\n\t\t\tif (states.get(st).loc == 0) {\n\t\t\t\tZone z = states.get(st).zone.deepCopy();\n\t\t\t\tz.down();\n\t\t\t\tif (z.includes(DBM.createZero(pta)))\n\t\t\t\t\tgraph.addInitialState(st);\n\t\t\t}\n\t\t}\n\n\t\t// Reachability complete\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Graph constructed in \" + (timer / 1000.0) + \" secs.\");\n\t\tmainLog.print(\"Graph: \" + graph.states.size() + \" symbolic states\");\n\t\tmainLog.println(\" (\" + graph.getInitialStates().size() + \" initial, \" + graph.getTarget().cardinality() + \" target)\");\n\n\t\treturn graph;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/BackwardsReachabilityGraph.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\nimport prism.PrismException;\nimport explicit.Distribution;\nimport explicit.MDP;\nimport explicit.MDPSimple;\n\npublic class BackwardsReachabilityGraph\n{\n\tpublic List<LocZone> states;\n\tprivate List<Integer> initialStates;\n\tprivate BitSet target;\n\tprivate List<List<List<List<Integer>>>> trans;\n\n\tpublic class Edge\n\t{\n\t\tint index; // Edge index in transition\n\t\tint dest; // Destination location\n\n\t\tpublic Edge(int index, int dest)\n\t\t{\n\t\t\tthis.index = index;\n\t\t\tthis.dest = dest;\n\t\t}\n\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn index + \"/\" + dest;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean equals(Object o)\n\t\t{\n\t\t\treturn o instanceof Edge && ((Edge) o).index == index && ((Edge) o).dest == dest;\n\t\t}\n\t}\n\n\tpublic BackwardsReachabilityGraph()\n\t{\n\t\tinitialStates = new ArrayList<Integer>();\n\t\ttarget = new BitSet();\n\t\ttrans = new ArrayList<List<List<List<Integer>>>>();\n\t}\n\n\tpublic void addState(List<Transition> trs)\n\t{\n\t\tint numTransitions = trs.size();\n\t\tList<List<List<Integer>>> list = new ArrayList<List<List<Integer>>>(numTransitions);\n\t\tfor (int i = 0; i < numTransitions; i++) {\n\t\t\tint numEdges = trs.get(i).getNumEdges();\n\t\t\tList<List<Integer>> list2 = new ArrayList<List<Integer>>(numEdges);\n\t\t\tfor (int j = 0; j < numEdges; j++) {\n\t\t\t\tlist2.add(new ArrayList<Integer>());\n\t\t\t}\n\t\t\tlist.add(list2);\n\t\t}\n\t\ttrans.add(list);\n\t}\n\n\tpublic void addInitialState(int s)\n\t{\n\t\tinitialStates.add(s);\n\t}\n\t\n\tpublic void addTargetState(int s)\n\t{\n\t\ttarget.set(s);\n\t}\n\t\n\tpublic List<Integer> getInitialStates()\n\t{\n\t\treturn initialStates; \n\t}\n\t\t\n\tpublic BitSet getTarget()\n\t{\n\t\treturn target;\n\t}\n\n\tpublic void addTransition(int src, int tr, int i, int dest)\n\t{\n\t\tList<Integer> list = trans.get(src).get(tr).get(i);\n\t\tif (!list.contains(dest))\n\t\t\tlist.add(dest);\n\t}\n\n\tpublic List<List<List<Integer>>> getList(int src)\n\t{\n\t\treturn trans.get(src);\n\t}\n\n\tpublic MDP buildMDP(PTA pta)\n\t{\n\t\tMDPSimple mdp = new MDPSimple(states.size() + 1); // + sink\n\t\tint src = -1;\n\t\tfor (List<List<List<Integer>>> list : trans) {\n\t\t\tsrc++;\n\t\t\tint tr = -1;\n\t\t\tfor (List<List<Integer>> list2 : list) {\n\t\t\t\ttr++;\n\t\t\t\tDistribution distr = Distribution.ofDouble();\n\t\t\t\tdouble prob, rest = 0;\n\t\t\t\tint j = -1;\n\t\t\t\tfor (List<Integer> dests : list2) {\n\t\t\t\t\tj++;\n\t\t\t\t\tprob = pta.getTransitions(states.get(src).loc).get(tr).getEdges().get(j).getProbability();\n\t\t\t\t\tif (dests.size() > 1) {\n\t\t\t\t\t\tint sNew = mdp.addState();\n\t\t\t\t\t\tdistr.add(sNew, prob);\n\t\t\t\t\t\tfor (int dest : dests) {\n\t\t\t\t\t\t\tDistribution distr2 = Distribution.ofDouble();\n\t\t\t\t\t\t\tdistr2.add(dest, 1.0);\n\t\t\t\t\t\t\tmdp.addChoice(sNew, distr2);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (dests.size() == 1) {\n\t\t\t\t\t\tdistr.add(dests.get(0), prob);\n\t\t\t\t\t} else {\n\t\t\t\t\t\trest += prob;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t//if (rest > 0)\n\t\t\t\t//\tdistr.add(mdp.getNumStates() - 1, rest);\n\t\t\t\tmdp.addChoice(src, distr);\n\t\t\t}\n\t\t}\n\t\t// Add initial states\n\t\tfor (int is : initialStates) {\n\t\t\tmdp.addInitialState(is);\n\t\t}\n\t\t// fix sink\n\t\ttry {\n\t\t\tmdp.findDeadlocks(true);\n\t\t} catch (PrismException e) {\n\t\t\t// Never happens for MDPSimple\n\t\t}\n\t\t//log.println(mdp);\n\t\treturn mdp;\n\t}\n\n\tpublic MDP buildMdpExpo(PTA pta)\n\t{\n\t\tMDPSimple mdp = new MDPSimple(states.size() + 1); // + sink\n\t\tint src = -1;\n\t\tfor (List<List<List<Integer>>> list : trans) {\n\t\t\tsrc++;\n\t\t\tint tr = -1;\n\t\t\tfor (List<List<Integer>> list2 : list) {\n\t\t\t\ttr++;\n\t\t\t\tint dests[] = new int[list2.size()];\n\t\t\t\tint size = 1;\n\t\t\t\tfor (int i = 0; i < list2.size(); i++) {\n\t\t\t\t\tif (list2.get(i).size() > 0)\n\t\t\t\t\t\tsize *= list2.get(i).size();\n\t\t\t\t}\n\t\t\t\tif (size > 6) {\n\t\t\t\t\tSystem.out.println(size + \"!\");\n\t\t\t\t\tSystem.out.println(list2);\n\t\t\t\t\tfor (List<Integer> list3 : list2) {\n\t\t\t\t\t\tfor (int x : list3) {\n\t\t\t\t\t\t\tSystem.out.println(x + \":\" + states.get(x));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t}\n\t\t\t\tbuildMdpExpo(mdp, pta, src, tr, list2, 0, dests);\n\t\t\t}\n\t\t}\n\t\t// Add initial states\n\t\tfor (int is : initialStates) {\n\t\t\tmdp.addInitialState(is);\n\t\t}\n\t\t// fix sink\n\t\ttry {\n\t\t\tmdp.findDeadlocks(true);\n\t\t} catch (PrismException e) {\n\t\t\t// Never happens for MDPSimple\n\t\t}\n\t\t//log.println(mdp);\n\t\treturn mdp;\n\t}\n\n\tpublic void buildMdpExpo(MDPSimple mdp, PTA pta, int src, int tr, List<List<Integer>> list2, int i, int dests[])\n\t{\n\t\tif (i == dests.length) {\n\t\t\t//log.print(src + \"/\" + tr);\n\t\t\tDistribution distr = Distribution.ofDouble();\n\t\t\tdouble prob, rest = 0;\n\t\t\tif (dests.length > 0) {\n\t\t\t\tfor (int j = 0; j < dests.length; j++) {\n\t\t\t\t\tprob = pta.getTransitions(states.get(src).loc).get(tr).getEdges().get(j).getProbability();\n\t\t\t\t\tif (list2.get(j).size() > 0) {\n\t\t\t\t\t\t//log.print(\" \" + prob + \":\" + dests[j]);\n\t\t\t\t\t\tdistr.add(dests[j], prob);\n\t\t\t\t\t} else {\n\t\t\t\t\t\trest += prob;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t//if (rest > 0)\n\t\t\t//\tdistr.add(mdp.getNumStates() - 1, rest);\n\t\t\tmdp.addChoice(src, distr);\n\t\t\t//log.println();\n\t\t} else {\n\t\t\tList<Integer> list3 = list2.get(i);\n\t\t\tif (list3.size() == 0) {\n\t\t\t\tbuildMdpExpo(mdp, pta, src, tr, list2, i + 1, dests);\n\t\t\t} else {\n\t\t\t\tfor (int j = 0; j < list3.size(); j++) {\n\t\t\t\t\tdests[i] = list3.get(j);\n\t\t\t\t\tbuildMdpExpo(mdp, pta, src, tr, list2, i + 1, dests);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn trans.toString();\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/Constraint.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\n/**\n * Single clock constraint.\n */\npublic class Constraint\n{\n\tprotected int x;\n\tprotected int y;\n\tprotected int db;\n\n\t/**\n\t * Create a constraint.\n\t * @param x Left clock\n\t * @param y Right clock\n\t * @param db Difference bound encoded as an integer\n\t */\n\tprivate Constraint(int x, int y, int db)\n\t{\n\t\tthis.x = x;\n\t\tthis.y = y;\n\t\tthis.db = db;\n\t}\n\n\t/**\n\t * Copy constructor. \n\t */\n\tpublic Constraint(Constraint c)\n\t{\n\t\tthis(c.x, c.y, c.db);\n\t}\n\t\n\tpublic int hashCode()\n\t{\n\t\treturn (((db * 7) + x) * 7) + y;\n\t}\n\n\tpublic boolean equals(Object o)\n\t{\n\t\tif (o == null || !(o instanceof Constraint))\n\t\t\treturn false;\n\t\tConstraint c = (Constraint) o;\n\t\treturn db == c.db && x == c.x && y == c.y;\n\t}\n\n\tpublic Constraint deepCopy()\n\t{\n\t\treturn new Constraint(x, y, db);\n\t}\n\n\t// Reindex clocks and return self\n\tpublic Constraint renameClocks(PTA oldPta, PTA newPta)\n\t{\n\t\tx = PTA.renameClock(oldPta, newPta, x);\n\t\ty = PTA.renameClock(oldPta, newPta, y);\n\t\treturn this;\n\t}\n\n\tpublic String toString(PTA pta)\n\t{\n\t\treturn DB.constraintToString(x, y, db, pta);\n\t}\n\n\tpublic static String toStringList(PTA pta, Iterable<Constraint> list)\n\t{\n\t\tString s = \"\";\n\t\tboolean first;\n\t\tif (list == null || !list.iterator().hasNext())\n\t\t\ts += \"true\";\n\t\telse {\n\t\t\tfirst = true;\n\t\t\tfor (Constraint c : list) {\n\t\t\t\tif (first)\n\t\t\t\t\tfirst = false;\n\t\t\t\telse\n\t\t\t\t\ts += \",\";\n\t\t\t\ts += c.toString(pta);\n\t\t\t}\n\t\t}\n\t\treturn s;\n\t}\n\n\t/**\n\t * Build constraint x <= v.\n\t */\n\tpublic static Constraint buildLeq(int x, int v)\n\t{\n\t\treturn new Constraint(x, 0, DB.createLeq(v));\n\t}\n\n\t/**\n\t * Build constraint x < v.\n\t */\n\tpublic static Constraint buildLt(int x, int v)\n\t{\n\t\treturn new Constraint(x, 0, DB.createLt(v));\n\t}\n\n\t/**\n\t * Build constraint x >= v.\n\t */\n\tpublic static Constraint buildGeq(int x, int v)\n\t{\n\t\treturn new Constraint(0, x, DB.createLeq(-v));\n\t}\n\n\t/**\n\t * Build constraint x > v.\n\t */\n\tpublic static Constraint buildGt(int x, int v)\n\t{\n\t\treturn new Constraint(0, x, DB.createLt(-v));\n\t}\n\n\t/**\n\t * Build constraint x <= y.\n\t */\n\tpublic static Constraint buildXLeqY(int x, int y)\n\t{\n\t\treturn new Constraint(x, y, DB.createLeq(0));\n\t}\n\n\t/**\n\t * Build constraint x < y.\n\t */\n\tpublic static Constraint buildXLtY(int x, int y)\n\t{\n\t\treturn new Constraint(x, y, DB.createLt(0));\n\t}\n\n\t/**\n\t * Build constraint x >= y.\n\t */\n\tpublic static Constraint buildXGeqY(int x, int y)\n\t{\n\t\treturn new Constraint(y, x, DB.createLeq(0));\n\t}\n\n\t/**\n\t * Build constraint x > y.\n\t */\n\tpublic static Constraint buildXGtY(int x, int y)\n\t{\n\t\treturn new Constraint(y, x, DB.createLt(0));\n\t}\n\t\n\t/**\n\t * Build constraint x - y <= v.\n\t */\n\tpublic static Constraint buildXYLeq(int x, int y, int v)\n\t{\n\t\treturn new Constraint(x, y, DB.createLeq(v));\n\t}\n\n\t/**\n\t * Build constraint x - y < v.\n\t */\n\tpublic static Constraint buildXYLt(int x, int y, int v)\n\t{\n\t\treturn new Constraint(x, y, DB.createLt(v));\n\t}\n\n\t/**\n\t * Build constraint x - y >= v.\n\t */\n\tpublic static Constraint buildXYGeq(int x, int y, int v)\n\t{\n\t\treturn new Constraint(y, x, DB.createLeq(-v));\n\t}\n\n\t/**\n\t * Build constraint x - y > v.\n\t */\n\tpublic static Constraint buildXYGt(int x, int y, int v)\n\t{\n\t\treturn new Constraint(y, x, DB.createLt(-v));\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/ConstructPTA.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.ArrayList;\nimport java.util.LinkedList;\nimport java.util.Vector;\n\nimport explicit.IndexedSet;\nimport explicit.StateStorage;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.Expression;\nimport parser.type.TypeClock;\nimport prism.ModelGenerator;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.ProgressDisplay;\n\n/**\n * Class to construct a PTA from a {@link prism.ModelGenerator} object.\n */\npublic class ConstructPTA extends PrismComponent\n{\n\t/**\n\t * Constructor.\n\t */\n\tpublic ConstructPTA(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Construct a PTA from a {@link prism.ModelGenerator} object.\n\t * This is done somewhat symbolically, in the sense that all reachable locations\n\t * are explored, ignoring possible clock values. Invariants, guards and resets\n\t * relating to clocks are extracted and stored in the PTA.\n\t */\n\tpublic PTA constructPTA(ModelGenerator<Double> modelGen) throws PrismException\n\t{\n\t\t// Do a few basic checks on the model\n\t\tif (modelGen.getModelType() != ModelType.PTA) {\n\t\t\tthrow new PrismLangException(\"Model is not a PTA\");\n\t\t}\n\t\t// We only support PTAs with a single initial state\n\t\tif (!modelGen.hasSingleInitialState()) {\n\t\t\tthrow new PrismLangException(\"Cannot construct PTA models with multiple initial states\");\n\t\t}\n\t\t\n\t\t// Extract some info from the model generator\n\t\tValues constantValues  = modelGen.getConstantValues();\n\t\tVarList varList = modelGen.createVarList();\n\t\t\n\t\t// Starting reachability...\n\t\tmainLog.print(\"\\nComputing reachable locations of \" + modelGen.getModelType() + \"...\");\n\t\tmainLog.flush();\n\t\tProgressDisplay progress = new ProgressDisplay(mainLog);\n\t\tprogress.start();\n\t\tlong timer = System.currentTimeMillis();\n\n\t\t// Get list of clock (and all) variables\n\t\tint numVars = varList.getNumVars();\n\t\tArrayList<String> clocks = new ArrayList<String>();\n\t\tArrayList<String> varNames = new ArrayList<String>();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tif (varList.getType(i) instanceof TypeClock) {\n\t\t\t\tclocks.add(varList.getName(i));\n\t\t\t}\n\t\t\tvarNames.add(varList.getName(i));\n\t\t}\n\t\t\n\t\t// Create new PTA and add a clock for each clock variable\n\t\t// (note we construct a single global PTA, so no need for action alphabet)\n\t\tPTA pta = new PTA(new ArrayList<String>(new Vector<>()));\n\t\tfor (String clockName : clocks) {\n\t\t\tpta.addClock(clockName);\n\t\t}\n\t\t\n\t\t// Initialise states storage\n\t\tStateStorage<State> states = new IndexedSet<State>(true);\n\t\tLinkedList<State> explore = new LinkedList<State>();\n\t\t// Add initial state(s) to 'explore', 'states' and to the model\n\t\tfor (State initState : modelGen.getInitialStates()) {\n\t\t\t// We set clock variable values to null\n\t\t\t// (so we can tell if they are reset in transitions)\n\t\t\tfor (String clock : clocks) {\n\t\t\t\tinitState.varValues[varList.getIndex(clock)] = null;\n\t\t\t}\n\t\t\texplore.add(initState);\n\t\t\tstates.add(initState);\n\t\t\tpta.addLocation(initState);\n\t\t}\n\t\t// Explore...\n\t\tint src = -1;\n\t\twhile (!explore.isEmpty()) {\n\t\t\t// Pick next state to explore\n\t\t\t// (they are stored in order found so know index is src+1)\n\t\t\tState state = explore.removeFirst();\n\t\t\tsrc++;\n\t\t\t// Explore all choices/transitions from this state\n\t\t\tmodelGen.exploreState(state);\n\t\t\t// Get/store invariant (should be syntactically convex, i.e., conjunction of\n\t\t\t// clock constraints, or true; complain if not)\n\t\t\tExpression invar = modelGen.getClockInvariant();\n\t\t\tif (invar != null) {\n\t\t\t\tfinal int srcFinal = src;\n\t\t\t\tPTAUtils.exprConjToConstraintConsumer(invar, constantValues, pta, c -> { pta.addInvariantCondition(srcFinal, c); });\n\t\t\t}\n\t\t\t// Look at each outgoing choice in turn\n\t\t\tint nc = modelGen.getNumChoices();\n\t\t\tfor (int i = 0; i < nc; i++) {\n\t\t\t\tfinal Transition tr = pta.addTransition(src, modelGen.getChoiceActionString(i));\n\t\t\t\t// Get/store guard (should be syntactically convex, i.e., conjunction of\n\t\t\t\t// clock constraints, or true; complain if not)\n\t\t\t\tPTAUtils.exprConjToConstraintConsumer(modelGen.getChoiceClockGuard(i), constantValues, pta, c -> { tr.addGuardConstraint(c); });\n\t\t\t\t// Look at each transition in the choice\n\t\t\t\tint nt = modelGen.getNumTransitions(i);\n\t\t\t\tfor (int j = 0; j < nt; j++) {\n\t\t\t\t\t// Create edge\n\t\t\t\t\tEdge edge = tr.addEdge(modelGen.getTransitionProbability(i, j), -1);\n\t\t\t\t\tState stateNew = modelGen.computeTransitionTarget(i, j);\n\t\t\t\t\t// See which clocks are reset on this edge, and store\n\t\t\t\t\tfor (String clock : clocks) {\n\t\t\t\t\t\tint index = varList.getIndex(clock);\n\t\t\t\t\t\tObject newClockVal = stateNew.varValues[index];\n\t\t\t\t\t\tif (newClockVal != null) {\n\t\t\t\t\t\t\t// (was reset to int, but stored as double) \n\t\t\t\t\t\t\tint newClockValInt = (int) Math.round((Double) newClockVal);\n\t\t\t\t\t\t\tedge.addReset(pta.getClockIndex(clock), newClockValInt);\n\t\t\t\t\t\t\t// Now set clock variable values to null\n\t\t\t\t\t\t\t// (so we can tell if they are reset in future transitions)\n\t\t\t\t\t\t\tstateNew.varValues[index] = null;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Is this a new state?\n\t\t\t\t\tif (states.add(stateNew)) {\n\t\t\t\t\t\t// If so, add to the explore list and model\n\t\t\t\t\t\texplore.add(stateNew);\n\t\t\t\t\t\tpta.addLocation(stateNew);\n\t\t\t\t\t}\n\t\t\t\t\t// Get index of state in state set (NB: should match return from pta.addLocation)\n\t\t\t\t\tint dest = states.getIndexOfLastAdd();\n\t\t\t\t\tedge.setDestination(dest);\n\t\t\t\t}\n\t\t\t}\n\t\t\t // Print some progress info occasionally\n\t\t\t progress.updateIfReady(src + 1);\n\t\t}\n\t\t\n\t\t// Finish progress display\n\t\tprogress.update(src + 1);\n\t\tprogress.end(\" locations\");\n\n\t\t// Reachability complete\n\t\tmainLog.print(\"Reachable locations exploration and model construction\");\n\t\tmainLog.println(\" done in \" + ((System.currentTimeMillis() - timer) / 1000.0) + \" secs.\");\n\n\t\t// Pass the list of variable names to the PTA\n\t\tpta.setLocationNameVars(varNames);\n\t\t\n\t\treturn pta;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/DB.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\n/**\n * Helper class for encapsulation of difference bound as an integer.\n * We use the least significant bit to encode strictness in the bound\n * (1 = non-strict, 0 = strict); the rest is for the (integer) bound.\n * Upper bound of infinity is encoded as Integer.MAX_VALUE.\n */\npublic class DB\n{\n\t// Bit masks, etc.\n\tprotected final static int NON_STRICT = 0x1;\n\tprotected final static int DIFF_MASK = ~0x1;\n\tprotected final static int INFTY = Integer.MAX_VALUE;\n\tprotected final static int LEQ_ZERO = 0x1;\n\tprotected final static int LT_ZERO = 0x0;\n\tprotected final static int LEQ_MINUS_ONE = (-1 << 1) | NON_STRICT;\n\n\t// Created bound <=v\n\tprotected static int createLeq(int v)\n\t{\n\t\treturn (v << 1) | NON_STRICT;\n\t}\n\n\t// Create bound <v\n\tprotected static int createLt(int v)\n\t{\n\t\treturn (v << 1);\n\t}\n\n\t// Get (signed) difference part of bound\n\tprotected static int getSignedDiff(int d)\n\t{\n\t\treturn (DIFF_MASK & d) >> 1;\n\t}\n\n\t// Is bound strict?\n\tprotected static boolean isStrict(int d)\n\t{\n\t\treturn (NON_STRICT & d) == 0;\n\t}\n\n\t// Is infinity\n\tprotected static boolean isInfty(int d)\n\t{\n\t\treturn (d == INFTY);\n\t}\n\n\t// Add two bounds\n\tprotected static int add(int d1, int d2)\n\t{\n\t\t// Anything + inf = inf\n\t\tif (d1 == INFTY || d2 == INFTY)\n\t\t\treturn INFTY;\n\t\t// Both leq: <=m + <=n = <=m+n; else: <m+n\n\t\treturn d1 + d2 - ((d1 & NON_STRICT) | (d2 & NON_STRICT));\n\t}\n\n\t// Compute dual bound: flip both strictness and sign\n\tprotected static int dual(int d)\n\t{\n\t\tif (d == INFTY)\n\t\t\treturn d;\n\t\t// TODO: probably a more efficient way to do this\n\t\treturn isStrict(d) ? createLeq(-getSignedDiff(d)) : createLt(-getSignedDiff(d)); \n\t}\n\n\t// Get bound as a string\n\tprotected static String toString(int d)\n\t{\n\t\tif (d == INFTY)\n\t\t\treturn \"<inf\";\n\t\treturn (isStrict(d) ? \"<\" : \"<=\") + getSignedDiff(d);\n\t}\n\n\t// Get bound as a string, multiplied by -1 and flipped, e.g. \"<v\" -> \"-v<\" \n\tprotected static String toStringFlipped(int d)\n\t{\n\t\tif (d == INFTY)\n\t\t\treturn \"-inf<\";\n\t\treturn (-getSignedDiff(d)) + (isStrict(d) ? \"<\" : \"<=\");\n\t}\n\n\t// Get constraint as a string\n\tprotected static String constraintToString(int i, int j, int d, PTA pta)\n\t{\n\t\tString s;\n\t\tif (i > 0) {\n\t\t\t// x-y < v\n\t\t\tif (j > 0) {\n\t\t\t\ts = pta.getClockName(i);\n\t\t\t\t// x-y < inf\n\t\t\t\tif (isInfty(d))\n\t\t\t\t\ts += \"-\" + pta.getClockName(j) + \"<inf\";\n\t\t\t\t// x-y < 0  ->  x < y\n\t\t\t\telse if (getSignedDiff(d) == 0)\n\t\t\t\t\ts += (isStrict(d) ? \"<\" : \"<=\") + pta.getClockName(j);\n\t\t\t\t// x-y < v\n\t\t\t\telse\n\t\t\t\t\ts += \"-\" + pta.getClockName(j) + (isStrict(d) ? \"<\" : \"<=\") + getSignedDiff(d);\n\t\t\t\t// x-0 < v\n\t\t\t} else {\n\t\t\t\ts = pta.getClockName(i);\n\t\t\t\tif (isInfty(d))\n\t\t\t\t\ts += \"<inf\";\n\t\t\t\telse\n\t\t\t\t\ts += (isStrict(d) ? \"<\" : \"<=\") + getSignedDiff(d);\n\t\t\t}\n\t\t}\n\t\t// 0-y < v  ->  y > -v\n\t\telse {\n\t\t\ts = pta.getClockName(j);\n\t\t\tif (isInfty(d))\n\t\t\t\ts += \">-inf\";\n\t\t\telse\n\t\t\t\ts += (isStrict(d) ? \">\" : \">=\") + (-getSignedDiff(d));\n\t\t}\n\t\treturn s;\n\t}\n\n\t// Get constraint pair as a string\n\t// (x - y < v2 and y - x < v1, i.e. -v1 < x - y < v2) where x,y are clocks i,j and vk is from dk \n\tprotected static String constraintPairToString(int i, int j, int d2, int d1, PTA pta)\n\t{\n\t\tString s;\n\t\tif (i > 0) {\n\t\t\t// -v1 < x-y < v2\n\t\t\tif (j > 0) {\n\t\t\t\tif (!isInfty(d2) && (-getSignedDiff(d1) == getSignedDiff(d2))) {\n\t\t\t\t\tif (getSignedDiff(d1) == 0)\n\t\t\t\t\t\ts = pta.getClockName(i) + \"=\" + pta.getClockName(j);\n\t\t\t\t\telse\n\t\t\t\t\t\ts = pta.getClockName(i) + \"-\" + pta.getClockName(j) + \"=\" + getSignedDiff(d2);\n\t\t\t\t} else {\n\t\t\t\t\ts = toStringFlipped(d1) + pta.getClockName(i) + \"-\" + pta.getClockName(j) + toString(d2);\n\t\t\t\t}\n\t\t\t\t// -v1 < x-0 < v2\n\t\t\t} else {\n\t\t\t\tif (!isInfty(d2) && (-getSignedDiff(d1) == getSignedDiff(d2)))\n\t\t\t\t\ts = pta.getClockName(i) + \"=\" + getSignedDiff(d2);\n\t\t\t\telse\n\t\t\t\t\ts = toStringFlipped(d1) + pta.getClockName(i) + toString(d2);\n\t\t\t}\n\t\t}\n\t\t// -v1 < 0-y < v2  ->  -v2 < y < v1\n\t\telse {\n\t\t\tif (!isInfty(d2) && (-getSignedDiff(d1) == getSignedDiff(d2)))\n\t\t\t\ts = pta.getClockName(j) + \"=\" + getSignedDiff(d1);\n\t\t\telse\n\t\t\t\ts = toStringFlipped(d2) + pta.getClockName(j) + toString(d1);\n\t\t}\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/DBM.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\n/**\n * Implementation of the difference-bound matrix (DBM) data structure.\n * \n * Data structures and algorithms are mostly based on those from: \n * Johan Bengtsson, Wang Yi: Timed Automata: Semantics, Algorithms and Tools.\n * Lectures on Concurrency and Petri Nets 2003, LNCS volume 3098, pages 87-124, Springer, 2004\n */\npublic class DBM extends Zone\n{\n\t/* Parent PTA */\n\tprotected PTA pta;\n\t/*\n\t * Canonical zone representation: DBM\n\t * (numClocks+1)^2 matrix d, indexed 1...numClocks for clocks in PTA and 0 for special zero clock.\n\t * Each entry d[i][j] gives the bound for clock difference xi-xj.\n\t * Difference bounds are encoded as a single integer; see help class DB for details.\n\t */\n\tprotected int d[][];\n\n\t/**\n\t * Construct an empty DBM (don't use this).\n\t */\n\tpublic DBM(PTA pta)\n\t{\n\t\tthis.pta = pta;\n\t\tthis.d = new int[pta.numClocks + 1][pta.numClocks + 1];\n\t}\n\n\t// Methods required for Zone interface\n\n\t/**\n\t * Get parent PTA\n\t */\n\tpublic PTA getPTA()\n\t{\n\t\treturn pta;\n\t}\n\n\t// Zone operations (modify the zone)\n\n\t/**\n\t * Conjunction: add constraint x-y db\n\t */\n\tpublic void addConstraint(int x, int y, int db)\n\t{\n\t\t// Check if this causes inconsistency (i.e. zone emptiness)\n\t\t// and, if so, flag this by setting d[0][0] to -1;\n\t\tif (DB.add(d[y][x], db) < DB.LEQ_ZERO)\n\t\t\td[0][0] = DB.LEQ_MINUS_ONE;\n\t\t// Now add the constraint (if it is tighter than existing one)\n\t\telse if (db < d[x][y]) {\n\t\t\tint i, j, n, dTmp;\n\t\t\t// Store new constraint\n\t\t\td[x][y] = db;\n\t\t\t// Partial re-canonicalisation\n\t\t\t// Note we do 2 (separate) outer iterations of Floyd-Warshall,\n\t\t\t// unlike the incorrect formulation in the DBM algorithm notes.\n\t\t\tn = pta.numClocks;\n\t\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\t\tdTmp = DB.add(d[i][x], d[x][j]);\n\t\t\t\t\tif (dTmp < d[i][j])\n\t\t\t\t\t\td[i][j] = dTmp;\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\t\tdTmp = DB.add(d[i][y], d[y][j]);\n\t\t\t\t\tif (dTmp < d[i][j])\n\t\t\t\t\t\td[i][j] = dTmp;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Conjunction: add constraint c\n\t */\n\tpublic void addConstraint(Constraint c)\n\t{\n\t\taddConstraint(c.x, c.y, c.db);\n\t}\n\n\t/**\n\t * Conjunction: add multiple constraints\n\t */\n\tpublic void addConstraints(Iterable<Constraint> constraints)\n\t{\n\t\tfor (Constraint c : constraints)\n\t\t\taddConstraint(c);\n\t}\n\n\t/**\n\t * Conjunction: with another zone\n\t */\n\tpublic void intersect(Zone z)\n\t{\n\t\tint i, j, n;\n\t\tDBM dbm = (DBM) z;\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tif (i != j && !DB.isInfty(dbm.d[i][j]))\n\t\t\t\t\taddConstraint(i, j, dbm.d[i][j]);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Up, i.e. let time elapse, subject to some constraints\n\t */\n\tpublic void up(Iterable<Constraint> constraints)\n\t{\n\t\tint i, n;\n\t\tn = pta.numClocks;\n\t\tfor (i = 1; i < n + 1; i++) {\n\t\t\td[i][0] = DB.INFTY;\n\t\t}\n\t\tif (constraints != null) {\n\t\t\tfor (Constraint c : constraints) {\n\t\t\t\taddConstraint(c);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Down, i.e. zone which can reach this one, subject to some constraints\n\t */\n\tpublic void down(Iterable<Constraint> constraints)\n\t{\n\t\tint i, j, n;\n\t\tn = pta.numClocks;\n\t\tfor (i = 1; i < n + 1; i++) {\n\t\t\td[0][i] = DB.LEQ_ZERO;\n\t\t\tfor (j = 1; j < n + 1; j++) {\n\t\t\t\tif (d[j][i] < d[0][i])\n\t\t\t\t\td[0][i] = d[j][i];\n\t\t\t}\n\t\t}\n\t\tif (constraints != null) {\n\t\t\tfor (Constraint c : constraints) {\n\t\t\t\taddConstraint(c);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Free, i.e. remove constraints on a clock\n\t */\n\tpublic void free(int x)\n\t{\n\t\tint i, n;\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tif (i != x) {\n\t\t\t\td[x][i] = DB.INFTY;\n\t\t\t\td[i][x] = d[i][0];\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Reset clock x\n\t */\n\tpublic void reset(int x, int v)\n\t{\n\t\tint i, n;\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\td[x][i] = DB.add(DB.createLeq(v), d[0][i]);\n\t\t\td[i][x] = DB.add(d[i][0], DB.createLeq(-v));\n\t\t}\n\t}\n\n\t/**\n\t * Backward reset of clock x\n\t */\n\tpublic void backReset(int x, int v)\n\t{\n\t\t// Conjunction with constraint x=v\n\t\t// (i.e. x-0 <= v && 0-x <= -v)\n\t\taddConstraint(x, 0, DB.createLeq(v));\n\t\taddConstraint(0, x, DB.createLeq(-v));\n\t\t// Then \"free\" clock x\n\t\tfree(x);\n\t}\n\n\t/**\n\t * c-Closure\n\t */\n\tpublic void cClosure(int c)\n\t{\n\t\tint i, j, n;\n\t\tif (isEmpty())\n\t\t\treturn;\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tif (!DB.isInfty(d[i][j]) && DB.createLeq(c) < d[i][j]) {\n\t\t\t\t\td[i][j] = DB.INFTY;\n\t\t\t\t} else if (!DB.isInfty(d[i][j]) && d[i][j] < DB.createLt(-c)) {\n\t\t\t\t\td[i][j] = DB.createLt(-c);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tcanonicalise();\n\t}\n\n\t// Zone operations (create new zone)\n\t\n\t/**\n\t * Complement this DBM; creates a new DBM list as result.\n\t */\n\tpublic DBMList createComplement()\n\t{\n\t\tDBMList list = new DBMList(pta);\n\t\tDBM dbmNew;\n\t\tint i, j, n;\n\t\t// Special case: complement of empty DBM is True\n\t\tif (isEmpty()) {\n\t\t\tlist.addDBM(createTrue(pta));\n\t\t\treturn list;\n\t\t}\n\t\tn = d.length - 1;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tif (i == j)\n\t\t\t\t\tcontinue;\n\t\t\t\tif (DB.isInfty(d[i][j]))\n\t\t\t\t\tcontinue;\n\t\t\t\tdbmNew = (DBM) new DBMFactory().createTrue(pta);\n\t\t\t\tdbmNew.addConstraint(j, i, DB.dual(d[i][j]));\n\t\t\t\tif (!dbmNew.isEmpty()) {\n\t\t\t\t\tlist.addDBM(dbmNew);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn list;\n\t}\n\n\t// Zone queries (do not modify the zone)\n\t\n\t/**\n\t * Is this zone empty (i.e. inconsistent)?\n\t */\n\tpublic boolean isEmpty()\n\t{\n\t\t// Internally, inconsistency is flagged by setting d[0][0] to -1.\n\t\t// (Note: strictly speaking \"<0\" checks that the difference bound is less than \"<0\".)\n\t\treturn d[0][0] < 0;\n\t}\n\n\t/**\n\t * Is constraint c satisfied by this zone (i.e does it overlap)?\n\t */\n\tpublic boolean isSatisfied(Constraint c)\n\t{\n\t\treturn DB.add(c.db, d[c.y][c.x]) > 0;\n\t}\n\n\t/**\n\t * Is a DBM (fully) included in this zone?\n\t */\n\tpublic boolean includes(DBM dbm)\n\t{\n\t\tint i, j, n;\n\t\tint[][] d2 = dbm.d;\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tif (d[i][j] < d2[i][j])\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get the minimum value of a clock. \n\t */\n\tpublic int getClockMin(int x)\n\t{\n\t\treturn -DB.getSignedDiff(d[0][x]);\n\t}\n\t\n\t/**\n\t * Get the maximum value of a clock. \n\t */\n\tpublic int getClockMax(int x)\n\t{\n\t\treturn DB.getSignedDiff(d[x][0]);\n\t}\n\t\n\t/**\n\t * Check if a clock is unbounded (can be infinite).\n\t */\n\tpublic boolean clockIsUnbounded(int x)\n\t{\n\t\treturn DB.isInfty(d[x][0]);\n\t}\n\t\n\t/**\n\t * Check if all clocks are unbounded (can be infinite).\n\t */\n\tpublic boolean allClocksAreUnbounded()\n\t{\n\t\tint i, n;\n\t\tn = pta.numClocks;\n\t\tfor (i = 1; i < n + 1; i++) {\n\t\t\tif (!DB.isInfty(d[i][0])) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t// Misc\n\t\n\t/**\n\t * Clone this zone\n\t */\n\tpublic DBM deepCopy()\n\t{\n\t\tint i, j, n;\n\t\tDBM copy = new DBM(pta);\n\t\tn = pta.numClocks;\n\t\tcopy.d = new int[n + 1][n + 1];\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tcopy.d[i][j] = d[i][j];\n\t\t\t}\n\t\t}\n\t\treturn copy;\n\t}\n\n\t/**\n\t * Get storage info string\n\t */\n\tpublic String storageInfo()\n\t{\n\t\treturn \"DBM with \" + pta.numClocks + \" clocks\";\n\t}\n\n\t// Standard Java methods\n\n\tpublic int hashCode()\n\t{\n\t\tint n = pta.numClocks + 1;\n\t\tint hash = 0;\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tfor (int j = 0; j < n; j++) {\n\t\t\t\thash = (hash * 7) + d[i][j];\n\t\t\t}\n\t\t}\n\t\treturn hash;\n\t}\n\n\tpublic boolean equals(Object o)\n\t{\n\t\tDBM dbm;\n\t\tint i, j, n;\n\t\tif (o == null)\n\t\t\treturn false;\n\t\ttry {\n\t\t\tdbm = (DBM) o;\n\t\t} catch (ClassCastException e) {\n\t\t\treturn false;\n\t\t}\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tif (d[i][j] != dbm.d[i][j])\n\t\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t// To string methods\n\n\tpublic String toString()\n\t{\n\t\treturn toStringTextual();\n\t}\n\n\t/**\n\t * Convert to string - textual representation\n\t */\n\tpublic String toStringTextual()\n\t{\n\t\tint i, j, n;\n\t\tboolean first = true;\n\t\tString s = \"\", s2;\n\t\tn = pta.numClocks;\n\t\t// Trivial case - empty\n\t\tif (isEmpty())\n\t\t\treturn \"empty\";\n\t\t// Generate textual description for each difference (pair)\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = i + 1; j < n + 1; j++) {\n\t\t\t\ts2 = null;\n\t\t\t\tif (!DB.isInfty(d[i][j])) {\n\t\t\t\t\tif (!DB.isInfty(d[j][i])) {\n\t\t\t\t\t\ts2 = DB.constraintPairToString(i, j, d[i][j], d[j][i], pta);\n\t\t\t\t\t} else {\n\t\t\t\t\t\ts2 = DB.constraintToString(i, j, d[i][j], pta);\n\t\t\t\t\t}\n\t\t\t\t} else if (!DB.isInfty(d[j][i])) {\n\t\t\t\t\ts2 = DB.constraintToString(j, i, d[j][i], pta);\n\t\t\t\t}\n\t\t\t\tif (s2 != null) {\n\t\t\t\t\tif (!first)\n\t\t\t\t\t\ts += \",\";\n\t\t\t\t\telse\n\t\t\t\t\t\tfirst = false;\n\t\t\t\t\ts += s2;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (\"\".equals(s))\n\t\t\treturn \"true\";\n\t\telse\n\t\t\treturn \"{\" + s + \"}\";\n\t}\n\n\t/**\n\t * Convert to string - DBM representation\n\t */\n\tpublic String toStringDBM()\n\t{\n\t\tint i, j, n;\n\t\tString s = \"[ \";\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tif (j > 0)\n\t\t\t\t\ts += \" \";\n\t\t\t\ts += DB.toString(d[i][j]);\n\t\t\t}\n\t\t\tif (i < n)\n\t\t\t\ts += \", \";\n\t\t}\n\t\ts += \" ]\";\n\t\treturn s;\n\t}\n\n\t/* Private utility methods */\n\n\t/**\n\t * Canonicalise, by applying Floyd-Warshall SPP algorithm \n\t */\n\tprivate void canonicalise()\n\t{\n\t\tint k, i, j, db, n;\n\t\tn = pta.numClocks;\n\t\tfor (k = 0; k < n + 1; k++) {\n\t\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\t\tdb = DB.add(d[i][k], d[k][j]);\n\t\t\t\t\tif (db < d[i][j])\n\t\t\t\t\t\td[i][j] = db;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/* Static zone creation methods */\n\n\t/**\n\t * All clocks = 0\n\t */\n\tpublic static DBM createZero(PTA pta)\n\t{\n\t\tint i, j, n;\n\t\tDBM dbm = new DBM(pta);\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tdbm.d[i][j] = DB.LEQ_ZERO;\n\t\t\t}\n\t\t}\n\t\treturn dbm;\n\t}\n\n\t/**\n\t * All clocks any (non-negative) value\n\t */\n\tpublic static DBM createTrue(PTA pta)\n\t{\n\t\tint i, j, n;\n\t\tDBM dbm = new DBM(pta);\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tif (i == j)\n\t\t\t\t\tdbm.d[i][j] = DB.LEQ_ZERO;\n\t\t\t\telse if (i == 0)\n\t\t\t\t\tdbm.d[i][j] = DB.LEQ_ZERO;\n\t\t\t\telse\n\t\t\t\t\tdbm.d[i][j] = DB.INFTY;\n\t\t\t}\n\t\t}\n\t\treturn dbm;\n\t}\n\n\t/**\n\t * Zone defined by set of constraints\n\t */\n\tpublic static DBM createFromConstraints(PTA pta, Iterable<Constraint> constrs)\n\t{\n\t\tDBM dbm = createTrue(pta);\n\t\tfor (Constraint c : constrs) {\n\t\t\tdbm.addConstraint(c);\n\t\t}\n\t\treturn dbm;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/DBMFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\npublic class DBMFactory implements ZoneFactory\n{\n\t/* Basic zone creation */\n\n\t/**\n\t * All clocks = 0\n\t */\n\tpublic DBM createZero(PTA pta)\n\t{\n\t\tint i, j, n;\n\t\tDBM dbm = new DBM(pta);\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tdbm.d[i][j] = DB.LEQ_ZERO;\n\t\t\t}\n\t\t}\n\t\treturn dbm;\n\t}\n\n\t/**\n\t * All clocks any (non-negative) value\n\t */\n\tpublic DBM createTrue(PTA pta)\n\t{\n\t\tint i, j, n;\n\t\tDBM dbm = new DBM(pta);\n\t\tn = pta.numClocks;\n\t\tfor (i = 0; i < n + 1; i++) {\n\t\t\tfor (j = 0; j < n + 1; j++) {\n\t\t\t\tif (i == j) dbm.d[i][j] = DB.LEQ_ZERO;\n\t\t\t\telse if (i == 0) dbm.d[i][j] = DB.LEQ_ZERO;\n\t\t\t\telse  dbm.d[i][j] = DB.INFTY;\n\t\t\t}\n\t\t}\n\t\treturn dbm;\n\t}\n\n\t/**\n\t * Zone defined by set of constraints\n\t */\n\tpublic DBM createFromConstraints(PTA pta, Iterable<Constraint> constrs)\n\t{\n\t\tDBM dbm = createTrue(pta);\n\t\tfor (Constraint c : constrs) {\n\t\t\tdbm.addConstraint(c);\n\t\t}\n\t\treturn dbm;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/DBMList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\n/**\n * List of DBMs representing a non-convex zone.\n * \n * See this reference for some useful algorithms:\n * S. Tripakis. The formal analysis of timed systems in practice. Joseph Fourier University, 1998.\n */\npublic class DBMList extends NCZone\n{\n\t/* Parent PTA */\n\tprotected PTA pta;\n\t/* List of DBMs */\n\tprotected ArrayList<DBM> list;\n\n\t/* Should we check for inclusion of DBMs as we go? */\n\tpublic static boolean checkInclusion = true;\n\n\t/**\n\t * Default constructor\n\t */\n\tpublic DBMList(PTA pta)\n\t{\n\t\tthis.pta = pta;\n\t\tlist = new ArrayList<DBM>();\n\t}\n\n\t/**\n\t * Copy constructor: create single list from existing DBM(List)\n\t */\n\tpublic DBMList(Zone z)\n\t{\n\t\t// From DBM \n\t\tif (z instanceof DBM) {\n\t\t\tDBM dbm = (DBM)z;\n\t\t\tthis.pta = dbm.pta;\n\t\t\tlist = new ArrayList<DBM>();\n\t\t\taddDBM(dbm);\n\t\t}\n\t\t// From DBM \n\t\telse { \n\t\t\tDBMList dbml = (DBMList)z;\n\t\t\tthis.pta = dbml.pta;\n\t\t\tlist = new ArrayList<DBM>();\n\t\t\tfor (DBM dbm : dbml.list) {\n\t\t\t\tlist.add((DBM) dbm.deepCopy());\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Add a DBM to the list\n\t */\n\tpublic void addDBM(DBM dbm)\n\t{\n\t\tint i, n;\n\t\tBitSet toRemove;\n\t\t// If we don't want to check inclusions, just add\n\t\tif (!checkInclusion) {\n\t\t\tlist.add(dbm);\n\t\t}\n\t\t// Otherwise look at existing DBMs\n\t\telse {\n\t\t\tn = list.size();\n\t\t\ttoRemove = new BitSet(n);\n\t\t\ti = 0;\n\t\t\tfor (DBM dbm2 : list) {\n\t\t\t\tif (dbm2.includes(dbm)) {\n\t\t\t\t\t// New DBM already included inside something - don't add \n\t\t\t\t\treturn;\n\t\t\t\t} else if (dbm.includes(dbm2)) {\n\t\t\t\t\t// This DBM is will be redundant when new DBM is added\n\t\t\t\t\ttoRemove.set(i);\n\t\t\t\t}\n\t\t\t\ti++;\n\t\t\t}\n\t\t\t// Remove (now) redundant ones\n\t\t\tfor (i = n - 1; i >= 0; i--) {\n\t\t\t\tif (toRemove.get(i))\n\t\t\t\t\tlist.remove(i);\n\t\t\t}\n\t\t\t// Add DBM\n\t\t\tlist.add(dbm);\n\t\t}\n\t}\n\n\t/**\n\t * Add a list of DBMs to the list\n\t */\n\tpublic void addDBMs(DBMList dbml)\n\t{\n\t\tfor (DBM dbm : dbml.list)\n\t\t\taddDBM(dbm);\n\t}\n\n\t/**\n\t * Get the {@code i}th DBM in the list.\n\t */\n\tpublic DBM getDBM(int i) \n\t{\n\t\treturn list.get(i);\n\t}\n\n\t// Methods required for Zone interface\n\n\t/**\n\t * Get parent PTA\n\t */\n\tpublic PTA getPTA()\n\t{\n\t\treturn pta;\n\t}\n\t\n\t// Zone operations (modify the zone)\n\n\t/**\n\t * Conjunction: add constraint x-y db\n\t */\n\tpublic void addConstraint(int x, int y, int db)\n\t{\n\t\tfor (DBM dbm : list) {\n\t\t\tdbm.addConstraint(x, y, db);\n\t\t}\n\t\tif (checkInclusion)\n\t\t\tremoveInclusions();\n\t}\n\n\t/**\n\t * Conjunction: add constraint c\n\t */\n\tpublic void addConstraint(Constraint c)\n\t{\n\t\taddConstraint(c.x, c.y, c.db);\n\t}\n\n\t/**\n\t * Conjunction: add multiple constraints\n\t */\n\tpublic void addConstraints(Iterable<Constraint> constraints)\n\t{\n\t\tfor (Constraint c : constraints)\n\t\t\taddConstraint(c);\n\t}\n\n\t/**\n\t * Conjunction: with another zone\n\t */\n\tpublic void intersect(Zone z)\n\t{\n\t\tint i, j, n1, n2;\n\t\tif (z instanceof DBM)\n\t\t\tz = new DBMList((DBM) z);\n\t\tDBMList dbml = (DBMList) z;\n\t\tDBMList listNew;\n\t\tDBM dbmNew;\n\t\tlistNew = new DBMList(pta);\n\t\tn1 = list.size();\n\t\tn2 = dbml.list.size();\n\t\tfor (i = 0; i < n1; i++) {\n\t\t\tfor (j = 0; j < n2; j++) {\n\t\t\t\tdbmNew = list.get(i).deepCopy();\n\t\t\t\tdbmNew.intersect(dbml.list.get(j));\n\t\t\t\tif (!dbmNew.isEmpty())\n\t\t\t\t\tlistNew.addDBM(dbmNew);\n\t\t\t}\n\t\t}\n\t\tlist = listNew.list;\n\t}\n\n\t/**\n\t * Up, i.e. let time elapse, subject to some constraints\n\t */\n\tpublic void up(Iterable<Constraint> constraints)\n\t{\n\t\tfor (DBM dbm : list) {\n\t\t\tdbm.up(constraints);\n\t\t}\n\t\tif (checkInclusion)\n\t\t\tremoveInclusions();\n\t}\n\n\t/**\n\t * Down, i.e. zone which can reach this one, subject to some constraints\n\t */\n\tpublic void down(Iterable<Constraint> constraints)\n\t{\n\t\tfor (DBM dbm : list) {\n\t\t\tdbm.down(constraints);\n\t\t}\n\t\tif (checkInclusion)\n\t\t\tremoveInclusions();\n\t}\n\n\t/**\n\t * Free, i.e. remove constraints on a clock\n\t */\n\tpublic void free(int x)\n\t{\n\t\t// Existential quantification distributes over union \n\t\tfor (DBM dbm : list) {\n\t\t\tdbm.free(x);\n\t\t}\n\t\tif (checkInclusion)\n\t\t\tremoveInclusions();\n\t}\n\n\t/**\n\t * Reset clock x\n\t */\n\tpublic void reset(int x, int v)\n\t{\n\t\t// NOT IMPLEMENTED\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t/**\n\t * Backward reset of clock x\n\t */\n\tpublic void backReset(int x, int v)\n\t{\n\t\t// Implemented as conjunction, then \"free\"\n\t\t// (see method in DBM class),\n\t\t// both of which distribute over union\n\t\tfor (DBM dbm : list) {\n\t\t\tdbm.addConstraint(x, 0, DB.createLeq(v));\n\t\t\tdbm.addConstraint(0, x, DB.createLeq(-v));\n\t\t}\n\t\tfor (DBM dbm : list) {\n\t\t\tdbm.free(x);\n\t\t}\n\t\tif (checkInclusion)\n\t\t\tremoveInclusions();\n\t}\n\n\t/**\n\t * c-Closure\n\t */\n\tpublic void cClosure(int c)\n\t{\n\t\t// NOT IMPLEMENTED\n\t\tthrow new RuntimeException(\"Not implemented yet\");\n\t}\n\n\t// Zone operations (create new zone)\n\t\n\t/**\n\t * Complement\n\t * Creates non-convex zone so creates new one,\n\t * and leaves this one unmodified\n\t */\n\tpublic DBMList createComplement()\n\t{\n\t\tDBMList dbml = deepCopy();\n\t\tdbml.complement();\n\t\treturn dbml;\n\t}\n\n\t// Zone queries (do not modify the zone)\n\t\n\t/**\n\t * Is this zone empty (i.e. inconsistent)?\n\t */\n\tpublic boolean isEmpty()\n\t{\n\t\tfor (DBM dbm : list) {\n\t\t\tif (!dbm.isEmpty())\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Is constraint c satisfied by this zone (i.e does it overlap)?\n\t */\n\tpublic boolean isSatisfied(Constraint c)\n\t{\n\t\tfor (DBM dbm : list) {\n\t\t\tif (!dbm.isSatisfied(c))\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Is a DBM (fully) included in this zone?\n\t */\n\tpublic boolean includes(DBM dbm)\n\t{\n\t\tfor (DBM dbm2 : list) {\n\t\t\tif (dbm2.includes(dbm))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get the minimum value of a clock. \n\t */\n\tpublic int getClockMin(int x)\n\t{\n\t\t// Take min across all DBMs\n\t\tint min = Integer.MAX_VALUE;\n\t\tfor (DBM dbm : list) {\n\t\t\tmin = Math.min(min, dbm.getClockMin(x));\n\t\t}\n\t\treturn min;\n\t}\n\t\n\t/**\n\t * Get the maximum value of a clock. \n\t */\n\tpublic int getClockMax(int x)\n\t{\n\t\t// Take max across all DBMs\n\t\tint max = Integer.MIN_VALUE;\n\t\tfor (DBM dbm : list) {\n\t\t\tmax = Math.max(max, dbm.getClockMax(x));\n\t\t}\n\t\treturn max;\n\t}\n\t\n\t/**\n\t * Check if a clock is unbounded (can be infinite).\n\t */\n\tpublic boolean clockIsUnbounded(int x)\n\t{\n\t\t// Clock is unbounded if is in any DBM\n\t\tfor (DBM dbm : list) {\n\t\t\tif (dbm.clockIsUnbounded(x))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Check if all clocks are unbounded (can be infinite).\n\t */\n\tpublic boolean allClocksAreUnbounded()\n\t{\n\t\tint i, n;\n\t\tn = pta.numClocks;\n\t\tfor (i = 1; i < n + 1; i++) {\n\t\t\tif (!clockIsUnbounded(i)) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t// Methods required for NCZone interface\n\t\n\t/**\n\t * Conjunction: with complement of another zone\n\t */\n\tpublic void intersectComplement(Zone z)\n\t{\n\t\tif (z instanceof DBM)\n\t\t\tz = new DBMList((DBM) z);\n\t\tDBMList dbml = (DBMList) z;\n\t\tfor (DBM dbm : dbml.list) {\n\t\t\tDBMList listTmp = dbm.createComplement();\n\t\t\tintersect(listTmp);\n\t\t}\n\t}\n\n\t/**\n\t * Complement\n\t */\n\tpublic void complement()\n\t{\n\t\tDBMList listNew, res;\n\t\tres = null;\n\t\t// Special case: complement of empty DBM list is True\n\t\tif (list.size() == 0)\n\t\t\taddDBM(DBM.createTrue(pta));\n\t\t// The complement of a list of DBMs is the intersection\n\t\t// of the complement of each DBM (and the complement of\n\t\t// of a DBM is a DBM list).\n\t\tfor (DBM dbm : list) {\n\t\t\tlistNew = dbm.createComplement();\n\t\t\tif (res == null)\n\t\t\t\tres = listNew;\n\t\t\telse {\n\t\t\t\tres.intersect(listNew);\n\t\t\t}\n\t\t\t// Stop early if res already empty\n\t\t\tif (res.list.size() == 0)\n\t\t\t\tbreak;\n\t\t}\n\t\tlist = res.list;\n\t}\n\n\t/**\n\t * Disjunction: with another zone\n\t */\n\tpublic void union(Zone z)\n\t{\n\t\tif (z instanceof DBM) {\n\t\t\taddDBM((DBM) z);\n\t\t}\n\t\telse {\n\t\t\taddDBMs((DBMList) z);\n\t\t}\n\t}\n\t\n\t/**\n\t * Get some (any) convex zone contained within this zone.\n\t * Returns null if this zone is empty.\n\t */\n\tpublic Zone getAZone()\n\t{\n\t\tif (list.size() > 0)\n\t\t\treturn list.get(0);\n\t\telse return null;\n\t}\n\t\n\t/**\n\t * Get the number of DBMs in this DBMList.\n\t */\n\tpublic int size()\n\t{\n\t\treturn list.size();\n\t}\n\n\t/**\n\t * Clone this zone\n\t */\n\tpublic DBMList deepCopy()\n\t{\n\t\tDBMList copy = new DBMList(pta);\n\t\tfor (DBM dbm : list) {\n\t\t\tcopy.list.add((DBM) dbm.deepCopy());\n\t\t}\n\t\treturn copy;\n\t}\n\n\t// Standard Java methods\n\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\tint hash = 0;\n\t\tfor (DBM dbm : list) {\n\t\t\thash = (hash * 7) + dbm.hashCode();\n\t\t}\n\t\treturn hash;\n\t}\n\n\t@Override\n\tpublic boolean equals(Object o)\n\t{\n\t\tDBMList dbml;\n\t\tint i, n;\n\t\tif (o == null)\n\t\t\treturn false;\n\t\ttry {\n\t\t\tdbml = (DBMList) o;\n\t\t} catch (ClassCastException e) {\n\t\t\treturn false;\n\t\t}\n\t\tn = list.size();\n\t\tif (n != dbml.list.size())\n\t\t\treturn false;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (!list.get(i).equals(dbml.list.get(i)))\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t// To string methods\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"\" + list;\n\t}\n\n\t/**\n\t * Get storage info string\n\t */\n\tpublic String storageInfo()\n\t{\n\t\treturn \"List of \" + list.size() + \" DBMs with \" + pta.numClocks + \" clocks\";\n\t}\n\n\t// Static zone creation methods\n\n\t/**\n\t * Create empty DBM list (i.e. false)\n\t */\n\tpublic static DBMList createFalse(PTA pta)\n\t{\n\t\tDBMList dbml = new DBMList(pta);\n\t\treturn dbml;\n\t}\n\n\t// Private utility methods\n\n\tprivate void removeInclusions()\n\t{\n\t\tint i, j, n;\n\t\tDBM dbm1, dbm2;\n\t\tBitSet toRemove;\n\t\tn = list.size();\n\t\ttoRemove = new BitSet(n);\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (toRemove.get(i))\n\t\t\t\tcontinue;\n\t\t\tdbm1 = list.get(i);\n\t\t\tfor (j = i + 1; j < n; j++) {\n\t\t\t\tif (toRemove.get(i) || toRemove.get(j))\n\t\t\t\t\tcontinue;\n\t\t\t\tdbm2 = list.get(j);\n\t\t\t\tif (dbm2.includes(dbm1))\n\t\t\t\t\ttoRemove.set(i);\n\t\t\t\telse if (dbm1.includes(dbm2))\n\t\t\t\t\ttoRemove.set(j);\n\t\t\t}\n\t\t}\n\t\tfor (i = n - 1; i >= 0; i--) {\n\t\t\tif (toRemove.get(i))\n\t\t\t\tlist.remove(i);\n\t\t}\n\t}\n\t\n\t// Test program for complementing big DBM lists\n\t\n\tpublic static void main(String args[])\n\t{\n\t\tint numClocks = 7;\n\t\tint i, j, x, y, db;\n\t\tRandom generator = new Random();\n\t\tPTA pta = new PTA(Collections.emptyList());\n\t\tfor (i = 0; i < numClocks; i++) {\n\t\t\tpta.addClock(\"\" + i);\n\t\t}\n\t\tDBMList dbml = new DBMList(pta);\n\t\tfor (i = 0; i < 5; i++) {\n\t\t\tDBM dbm = DBM.createTrue(pta);\n\t\t\tfor (j = 0; j < 10; j++) {\n\t\t\t\tx = generator.nextInt(numClocks);\n\t\t\t\ty = generator.nextInt(numClocks);\n\t\t\t\tdb = generator.nextInt();\n\t\t\t\tdbm.addConstraint(x, y, db);\n\t\t\t}\n\t\t\tdbml.addDBM(dbm);\n\t\t}\n\t\tSystem.out.println(dbml.storageInfo());\n\t\tdbml.complement();\n\t\tSystem.out.println(dbml.storageInfo());\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/DBMListFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.ArrayList;\n\npublic class DBMListFactory implements ZoneFactory\n{\n\t/* Basic zone creation */\n\n\tprivate DBMFactory dbmf = new DBMFactory();\n\t\n\t/**\n\t * All clocks = 0\n\t */\n\tpublic DBMList createZero(PTA pta)\n\t{\n\t\tDBMList list = new DBMList(pta);\n\t\tlist.addDBM((DBM)dbmf.createZero(pta));\n\t\treturn list;\n\t}\n\n\t/**\n\t * All clocks any value\n\t */\n\tpublic DBMList createTrue(PTA pta)\n\t{\n\t\tDBMList list = new DBMList(pta);\n\t\tlist.addDBM((DBM)dbmf.createTrue(pta));\n\t\treturn list;\n\t}\n\n\t/**\n\t * Zone defined by set of constraints\n\t */\n\tpublic DBMList createFromConstraints(PTA pta, Iterable<Constraint> constrs)\n\t{\n\t\tDBMList list = new DBMList(pta);\n\t\tlist.addDBM((DBM)dbmf.createFromConstraints(pta, constrs));\n\t\treturn list;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/DigitalClocks.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.ArrayList;\nimport java.util.Collection;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\n\nimport parser.ParserUtils;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.ASTElement;\nimport parser.ast.Command;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationClock;\nimport parser.ast.DeclarationInt;\nimport parser.ast.DeclarationType;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.ExpressionFunc;\nimport parser.ast.ExpressionIdent;\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionProp;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionVar;\nimport parser.ast.LabelList;\nimport parser.ast.Module;\nimport parser.ast.ModulesFile;\nimport parser.ast.Observable;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport parser.ast.RewardStruct;\nimport parser.ast.RewardStructItem;\nimport parser.ast.Update;\nimport parser.ast.Updates;\nimport parser.type.TypeClock;\nimport parser.type.TypeInt;\nimport parser.visitor.ASTTraverse;\nimport parser.visitor.ASTTraverseModify;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLangException;\n\n/**\n * Class that converts a PRISM modelling language description\n * of a PTA into a PRISM model of a PTA, through digital clocks\n */\npublic class DigitalClocks extends PrismComponent\n{\n\t// Constants from model\n\tprivate Values constantValues;\n\t// Variable list for model\n\tprivate VarList varList;\n\t// Time bound from property if present\n\tprivate int timeBound = -1;\n\n\t// Flags + settings\n\tprivate boolean doScaling = true;\n\n\t// Object for computing max clock constraints\n\tprivate ComputeClockInformation cci;\n\t// String to be used for time action \n\tprivate String timeAction;\n\t// Some invariant info\n\tprivate Expression allInVariants = null;\n\n\t// Translated model file\n\tprivate ModulesFile mf;\n\t// Translated properties file\n\tprivate PropertiesFile pf;\n\t// Translated property to check\n\tprivate Expression prop;\n\n\t/**\n\t * Create a new DigitalClocks, inherit basic state from parent (unless null).\n\t */\n\tpublic DigitalClocks(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tmf = null;\n\t\tpf = null;\n\t\tprop = null;\n\t}\n\n\t/**\n\t * Get translated model file.\n\t */\n\tpublic ModulesFile getNewModulesFile()\n\t{\n\t\treturn mf;\n\t}\n\n\t/**\n\t * Get translated properties file.\n\t */\n\tpublic PropertiesFile getNewPropertiesFile()\n\t{\n\t\treturn pf;\n\t}\n\n\t/**\n\t * Get translated property to check.\n\t */\n\tpublic Expression getNewPropertyToCheck()\n\t{\n\t\treturn prop;\n\t}\n\n\t/**\n\t * Main method - translate.\n\t */\n\tpublic void translate(ModulesFile modulesFile, PropertiesFile propertiesFile, Expression propertyToCheck) throws PrismException\n\t{\n\t\tmainLog.println(\"\\nPerforming digital clocks translation...\");\n\n\t\t// Store some info for global access\n\t\tconstantValues = modulesFile.getConstantValues();\n\t\tif (propertiesFile != null ) {\n\t\t\tconstantValues = new Values(constantValues, propertiesFile.getConstantValues());\n\t\t}\n\t\tvarList = modulesFile.createVarList();\n\n\t\t// Check that model does not contain any closed clock constraints\n\t\tASTElement ast = findAStrictClockConstraint(modulesFile, null);\n\t\tif (ast != null) {\n\t\t\tthrow new PrismLangException(\"Strict clock constraints are not allowed when using the digital clocks method\", ast);\n\t\t}\n\t\t// Check that model does not contain any diagonal clock constraints\n\t\t// (for now; should be able to relax this later)\n\t\tast = findADiagonalClockConstraint(modulesFile, null);\n\t\tif (ast != null) {\n\t\t\tthrow new PrismLangException(\"Diagonal clock constraints are not allowed when using the digital clocks method\", ast);\n\t\t}\n\t\t// Check for any references to clocks in rewards structures - not allowed.\n\t\tfor (RewardStruct rs : modulesFile.getRewardStructs()) {\n\t\t\trs.accept(new ASTTraverseModify()\n\t\t\t{\n\t\t\t\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.getType() instanceof TypeClock) {\n\t\t\t\t\t\tthrow new PrismLangException(\"Reward structures cannot contain references to clocks\", e);\n\t\t\t\t\t} else {\n\t\t\t\t\t\treturn e;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\t// Check for any global clocks\n\t\tfor (int v = 0; v < modulesFile.getNumGlobals(); v++) {\n\t\t\tmodulesFile.getGlobal(v).accept(new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPost(Declaration e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.getDeclType() instanceof DeclarationClock) {\n\t\t\t\t\t\tthrow new PrismLangException(\"Global clock variables are not allowed when using the digital clocks method\", e);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\t// Check that the property is suitable for checking with digital clocks\n\t\tif (propertyToCheck != null) {\n\t\t\tcheckProperty(propertyToCheck, propertiesFile);\n\t\t}\n\t\t\n\t\t// Choose a new action label to represent time\n\t\ttimeAction = \"time\";\n\t\twhile (modulesFile.getSynchs().contains(timeAction)) {\n\t\t\ttimeAction += \"_\";\n\t\t}\n\n\t\t// Extract information about clocks from the model\n\t\tcci = new ComputeClockInformation(modulesFile, propertiesFile, propertyToCheck);\n\t\tmainLog.println(\"Computed clock maximums: \" + cci.getClockMaxs());\n\t\tif (doScaling) {\n\t\t\tmainLog.println(\"Computed GCD: \" + cci.getScaleFactor());\n\t\t}\n\t\t\n\t\t// Take a copy of the whole model/properties file before translation\n\t\tmf = (ModulesFile) modulesFile.deepCopy();\n\t\tpf = (propertiesFile == null) ? null : (PropertiesFile) propertiesFile.deepCopy();\n\t\tprop = (Expression) propertyToCheck.deepCopy();\n\n\t\t// Change the model type\n\t\tmf.setModelTypeInFile(modulesFile.getModelType() == ModelType.PTA ? ModelType.MDP : ModelType.POMDP);\n\n\t\t// Change all clock variable declarations to bounded integers\n\t\tmf = (ModulesFile) mf.accept(new ASTTraverseModify()\n\t\t{\n\t\t\tpublic Object visit(Declaration e) throws PrismLangException\n\t\t\t{\n\t\t\t\tif (e.getDeclType() instanceof DeclarationClock) {\n\t\t\t\t\tint cMax = cci.getScaledClockMax(e.getName());\n\t\t\t\t\tif (cMax < 0) {\n\t\t\t\t\t\tthrow new PrismLangException(\"Clock \" + e.getName() + \" is unbounded since there are no references to it in the model\");\n\t\t\t\t\t}\n\t\t\t\t\tDeclarationType declType = new DeclarationInt(Expression.Int(0), Expression.Int(cMax + 1));\n\t\t\t\t\tDeclaration decl = new Declaration(e.getName(), declType);\n\t\t\t\t\treturn decl;\n\t\t\t\t} else {\n\t\t\t\t\treturn e;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\t// Add time command based on invariant for each module\n\t\t// Also build an \"invariants\" label, as we go\n\t\tallInVariants = null;\n\t\tmf = (ModulesFile) mf.accept(new ASTTraverseModify()\n\t\t{\n\t\t\tpublic Object visit(parser.ast.Module e) throws PrismLangException\n\t\t\t{\n\t\t\t\t// Get (clock) invariant for module; create default if none\n\t\t\t\tExpression invar = e.getInvariant();\n\t\t\t\tinvar = (invar == null) ? Expression.True() : invar.deepCopy();\n\t\t\t\t// Collect invariant for \"invariants\" label\n\t\t\t\tif (!Expression.isTrue(invar)) {\n\t\t\t\t\tallInVariants = (allInVariants == null) ? invar.deepCopy() : Expression.And(allInVariants, invar.deepCopy());\n\t\t\t\t}\n\t\t\t\t// Replace all clocks x with x+1 in invariant\n\t\t\t\tinvar = (Expression) invar.accept(new ASTTraverseModify()\n\t\t\t\t{\n\t\t\t\t\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t\t\t\t\t{\n\t\t\t\t\t\tif (e.getType() instanceof TypeClock) {\n\t\t\t\t\t\t\treturn Expression.Plus(e, Expression.Int(1));\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\treturn e;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\t// Construct command representing progression of time\n\t\t\t\tCommand timeCommand = new Command();\n\t\t\t\ttimeCommand.setSynch(timeAction);\n\t\t\t\t// Guard comes from invariant\n\t\t\t\ttimeCommand.setGuard(invar);\n\t\t\t\t// Update is constructed from clocks\n\t\t\t\tUpdate up = new Update();\n\t\t\t\tfor (String x : cci.getClocksForModule(e.getName())) {\n\t\t\t\t\t// Get clock max value\n\t\t\t\t\tint cMax = cci.getScaledClockMax(x);\n\t\t\t\t\t// Build expression min(x+1,cMax)\n\t\t\t\t\tExpressionFunc expr = new ExpressionFunc(\"min\");\n\t\t\t\t\texpr.addOperand(Expression.Plus(new ExpressionVar(x, TypeInt.getInstance()), Expression.Int(1)));\n\t\t\t\t\texpr.addOperand(Expression.Int(cMax + 1));\n\t\t\t\t\t// Add to update\n\t\t\t\t\tup.addElement(new ExpressionIdent(x), expr);\n\t\t\t\t}\n\t\t\t\tUpdates ups = new Updates();\n\t\t\t\tups.addUpdate(Expression.Double(1.0), up);\n\t\t\t\ttimeCommand.setUpdates(ups);\n\t\t\t\te.addCommand(timeCommand);\n\t\t\t\t// Finally, remove invariant info\n\t\t\t\te.setInvariant(null);\n\t\t\t\t// Return modified module\n\t\t\t\treturn e;\n\t\t\t}\n\t\t});\n\t\t// Add \"invariants\" label\n\t\tmf.getLabelList().addLabel(new ExpressionIdent(\"invariants\"), allInVariants == null ? Expression.True() : allInVariants);\n\n\t\t// Change the type of any clock variable references to int\n\t\t// and scale the variable appropriately, if required\n\t\t// (in both model and properties list)\n\t\tASTTraverseModify asttm = new ASTTraverseModify()\n\t\t{\n\t\t\t// Resets\n\t\t\tpublic Object visit(Update e) throws PrismLangException\n\t\t\t{\n\t\t\t\tint i, n;\n\t\t\t\tExpressionFunc exprFunc;\n\t\t\t\tn = e.getNumElements();\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\tif (e.getType(i) instanceof TypeClock) {\n\t\t\t\t\t\t// Don't actually need to set the type here since\n\t\t\t\t\t\t// will be done in subsequent call to tidyUp() but do it anyway.\n\t\t\t\t\t\te.setType(i, TypeInt.getInstance());\n\t\t\t\t\t\t// Scaling is done with division here, rather than multiplying clock like elsewhere\n\t\t\t\t\t\tif (cci.getScaleFactor() > 1) {\n\t\t\t\t\t\t\texprFunc = new ExpressionFunc(\"floor\");\n\t\t\t\t\t\t\texprFunc.addOperand(Expression.Divide(e.getExpression(i), Expression.Int(cci.getScaleFactor())));\n\t\t\t\t\t\t\te.setExpression(i, (Expression) exprFunc.simplify());\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\treturn e;\n\t\t\t}\n\n\t\t\t// Variable accesses\n\t\t\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t\t\t{\n\t\t\t\tif (e.getType() instanceof TypeClock) {\n\t\t\t\t\te.setType(TypeInt.getInstance());\n\t\t\t\t\tif (!doScaling || cci.getScaleFactor() == 1)\n\t\t\t\t\t\treturn e;\n\t\t\t\t\treturn Expression.Times(e, Expression.Int(cci.getScaleFactor()));\n\t\t\t\t}\n\t\t\t\treturn e;\n\t\t\t}\n\t\t};\n\t\tmf = (ModulesFile) mf.accept(asttm);\n\t\tif (pf != null) {\n\t\t\tpf = (PropertiesFile) pf.accept(asttm);\n\t\t}\n\t\tprop = (Expression) prop.accept(asttm);\n\n\t\t// Change state rewards in reward structures to use time action)\n\t\t// (transition rewards can be left unchanged)\n\t\t// Note: only cumulative (F) properties supported currently.\n\t\tfor (RewardStruct rs : mf.getRewardStructs()) {\n\t\t\tint n = rs.getNumItems();\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tRewardStructItem rsi = rs.getRewardStructItem(i);\n\t\t\t\t// Convert state rewards\n\t\t\t\tif (!rsi.isTransitionReward()) {\n\t\t\t\t\t// Scale reward by clock GCD\n\t\t\t\t\tExpression rew = rsi.getReward().deepCopy();\n\t\t\t\t\tif (cci.getScaleFactor() > 1) {\n\t\t\t\t\t\trew = Expression.Times(rew, Expression.Int(cci.getScaleFactor()));\n\t\t\t\t\t}\n\t\t\t\t\trsi = new RewardStructItem(timeAction, rsi.getStates().deepCopy(), rew);\n\t\t\t\t\trs.setRewardStructItem(i, rsi);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// If we are checking a time bounded property... \n\t\tif (timeBound != -1) {\n\t\t\t\n\t\t\tint scaledTimeBound = timeBound / cci.getScaleFactor();\n\t\t\t\n\t\t\t// First add a timer to the model\n\t\t\t\n\t\t\t// Create names for module/variable for timer\n\t\t\tString timerModuleName = \"timer\";\n\t\t\twhile (mf.getModuleIndex(timerModuleName) != -1) {\n\t\t\t\ttimerModuleName = \"_\" + timerModuleName;\n\t\t\t}\n\t\t\tString timerVarName = \"timer\";\n\t\t\twhile (mf.isIdentUsed(timerVarName) || (pf != null && pf.isIdentUsed(timerVarName))) {\n\t\t\t\ttimerVarName = \"_\" + timerVarName;\n\t\t\t}\n\t\t\t// Store time bound as a constant\n\t\t\tString timeboundName = \"T\";\n\t\t\twhile (mf.isIdentUsed(timeboundName) || (pf != null && pf.isIdentUsed(timeboundName))) {\n\t\t\t\ttimeboundName = \"_\" + timeboundName;\n\t\t\t}\n\t\t\tmf.getConstantList().addConstant(new ExpressionIdent(timeboundName), Expression.Int(scaledTimeBound), TypeInt.getInstance());\n\t\t\t// Create module/variable\n\t\t\tModule timerModule = new Module(timerModuleName);\n\t\t\tDeclarationType timerDeclType = new DeclarationInt(Expression.Int(0),\n\t\t\t\t\tExpression.Plus(new ExpressionConstant(timeboundName, TypeInt.getInstance()), Expression.Int(1)));\n\t\t\tDeclaration timerDecl = new Declaration(timerVarName, timerDeclType);\n\t\t\ttimerModule.addDeclaration(timerDecl);\n\t\t\t// Construct command representing progression of time\n\t\t\tCommand timeCommand = new Command();\n\t\t\ttimeCommand.setSynch(timeAction);\n\t\t\ttimeCommand.setGuard(Expression.True());\n\t\t\t// Construct update\n\t\t\tUpdate up = new Update();\n\t\t\t// Build expression min(timer+1,timerMax)\n\t\t\tExpressionFunc exprMin = new ExpressionFunc(\"min\");\n\t\t\texprMin.addOperand(Expression.Plus(new ExpressionVar(timerVarName, TypeInt.getInstance()), Expression.Int(1)));\n\t\t\texprMin.addOperand(Expression.Plus(new ExpressionConstant(timeboundName, TypeInt.getInstance()), Expression.Literal(1)));\n\t\t\t// Add to update\n\t\t\tup.addElement(new ExpressionIdent(timerVarName), exprMin);\n\t\t\tUpdates ups = new Updates();\n\t\t\tups.addUpdate(Expression.Double(1.0), up);\n\t\t\ttimeCommand.setUpdates(ups);\n\t\t\ttimerModule.addCommand(timeCommand);\n\t\t\t// Finally add module to model\n\t\t\tmf.addModule(timerModule);\n\t\t\t// For POPTAs, the variable needs to be observable\n\t\t\tif (modulesFile.getModelType().partiallyObservable()) {\n\t\t\t\tmf.addObservableDefinition(new Observable(timerVarName, new ExpressionVar(timerVarName, TypeInt.getInstance())));\n\t\t\t}\n\t\t\t\n\t\t\t// Then modify the property\n\t\t\t\n\t\t\t// Build time bound (timer <= T)\n\t\t\tExpression timerRef = new ExpressionVar(timerVarName, TypeInt.getInstance()); \n\t\t\tExpression boundNew = new ExpressionBinaryOp(ExpressionBinaryOp.LE, timerRef, new ExpressionConstant(timeboundName, TypeInt.getInstance()));\n\t\t\tprop.accept(new ASTTraverseModify()\n\t\t\t{\n\t\t\t\tpublic Object visit(ExpressionTemporal e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\t// Push (new) time bound into target\n\t\t\t\t\te.setUpperBound(null);\n\t\t\t\t\tExpression targetNew = Expression.And(e.getOperand2().deepCopy(), boundNew);\n\t\t\t\t\te.setOperand2(targetNew);\n\t\t\t\t\treturn e;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\t\t\t\t\t\t\n\t\t// Re-do type checking, indexing, etc. on the model/properties\n\t\tmf.tidyUp();\n\t\tif (pf != null) {\n\t\t\tpf.setModelInfo(mf);\n\t\t\tpf.tidyUp();\n\t\t}\n\t\tprop.findAllVars(mf.getVarNames(), mf.getVarTypes());\n\t\t// Copy across undefined constants since these get lost in the call to tidyUp()\n\t\tmf.setSomeUndefinedConstants(modulesFile.getUndefinedEvaluateContext());\n\t\tpf.setSomeUndefinedConstants(propertiesFile.getUndefinedEvaluateContext());\n\t}\n\n\t/**\n\t * Check that a property is checkable with the digital clocks method.\n\t * Throw an explanatory exception if not.\n\t * Optionally, an enclosing PropertiesFile is provided, to look up\n\t * property/label references. Can be null.\n\t */\n\tpublic void checkProperty(Expression propertyToCheck, PropertiesFile propertiesFile) throws PrismLangException\n\t{\n\t\tLabelList labelList = (propertiesFile == null) ? null : propertiesFile.getLabelList();\n\n\t\t// LTL not handled (look in any P operators)\n\t\ttry {\n\t\t\tpropertyToCheck.accept(new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPost(ExpressionProb e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (!e.getExpression().isSimplePathFormula()) {\n\t\t\t\t\t\tthrow new PrismLangException(\"The digital clocks method does not support LTL properties\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (PrismLangException e) {\n\t\t\te.setASTElement(propertyToCheck);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Bounded properties: check allowable, and store time bound if so\n\t\ttimeBound = -1;\n\t\ttry {\n\t\t\tpropertyToCheck.accept(new ASTTraverse()\n\t\t\t{\n\t\t\t\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.getLowerBound() != null) {\n\t\t\t\t\t\tthrow new PrismLangException(\"The digital clocks method does not yet support lower time bounds\");\n\t\t\t\t\t}\n\t\t\t\t\tif (e.getUpperBound() != null) {\n\t\t\t\t\t\tif (!ExpressionTemporal.isFinally(e)) {\n\t\t\t\t\t\t\tthrow new PrismLangException(\"The digital clocks method only ssupport time bounds on F\");\n\t\t\t\t\t\t}\n\t\t\t\t\t\ttimeBound = e.getUpperBound().evaluateInt(constantValues);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t} catch (PrismLangException e) {\n\t\t\te.setASTElement(propertyToCheck);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Check that there are no nested probabilistic operators\n\t\tif (propertyToCheck.computeProbNesting(propertiesFile) > 1) {\n\t\t\tthrow new PrismLangException(\"Nested P/R operators are not allowed when using the digital clocks method\", propertyToCheck);\n\t\t}\n\n\t\t// Check for presence of strict clock constraints\n\t\tASTElement ast = findAStrictClockConstraint(propertyToCheck, labelList);\n\t\tif (ast != null) {\n\t\t\tthrow new PrismLangException(\"Strict clock constraints are not allowed when using the digital clocks method\", ast);\n\t\t}\n\t\t// Check for presence of diagonal clock constraints\n\t\t// (for now; should be able to relax this later)\n\t\tast = findADiagonalClockConstraint(propertyToCheck, labelList);\n\t\tif (ast != null) {\n\t\t\tthrow new PrismLangException(\"Diagonal clock constraints are not allowed when using the digital clocks method\", ast);\n\t\t}\n\t}\n\n\t/**\n\t * Look for a strict clock constraint. If found return the offending element. Else, return null.\n\t * Optionally, pass in a LabelList to look up labels (can be null).\n\t */\n\tpublic ASTElement findAStrictClockConstraint(ASTElement ast, LabelList labelList) throws PrismLangException\n\t{\n\t\ttry {\n\t\t\tASTTraverse astt = new ASTTraverse()\n\t\t\t{\n\t\t\t\t// Clock constraints\n\t\t\t\tpublic void visitPost(ExpressionBinaryOp e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.getOperand1().getType() instanceof TypeClock) {\n\t\t\t\t\t\tif (e.getOperator() == ExpressionBinaryOp.GT || e.getOperator() == ExpressionBinaryOp.LT)\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Found one\", e);\n\t\t\t\t\t} else if (e.getOperand2().getType() instanceof TypeClock) {\n\t\t\t\t\t\tif (e.getOperator() == ExpressionBinaryOp.GT || e.getOperator() == ExpressionBinaryOp.LT)\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Found one\", e);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Recurse on labels\n\t\t\t\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (labelList != null) {\n\t\t\t\t\t\tint i = labelList.getLabelIndex(e.getName());\n\t\t\t\t\t\tif (i != -1) {\n\t\t\t\t\t\t\tlabelList.getLabel(i).accept(this);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t};\n\t\t\tast.accept(astt);\n\t\t} catch (PrismLangException e) {\n\t\t\treturn e.getASTElement();\n\t\t}\n\t\treturn null;\n\t}\n\n\t/**\n\t * Look for a diagonal clock constraint. If found return the offending element. Else, return null.\n\t * Optionally, pass in a LabelList to look up labels (can be null).\n\t */\n\tpublic ASTElement findADiagonalClockConstraint(ASTElement ast, LabelList labelList) throws PrismLangException\n\t{\n\t\ttry {\n\t\t\tASTTraverse astt = new ASTTraverse()\n\t\t\t{\n\t\t\t\t// Clock constraints\n\t\t\t\tpublic void visitPost(ExpressionBinaryOp e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (e.getOperand1().getType() instanceof TypeClock) {\n\t\t\t\t\t\tif (e.getOperand2().getType() instanceof TypeClock) {\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Found one\", e);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Recurse on labels\n\t\t\t\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t\t\t\t{\n\t\t\t\t\tif (labelList != null) {\n\t\t\t\t\t\tint i = labelList.getLabelIndex(e.getName());\n\t\t\t\t\t\tif (i != -1) {\n\t\t\t\t\t\t\tlabelList.getLabel(i).accept(this);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t};\n\t\t\tast.accept(astt);\n\t\t} catch (PrismLangException e) {\n\t\t\treturn e.getASTElement();\n\t\t}\n\t\treturn null;\n\t}\n\n\t/**\n\t * Class to extract information about clocks:\n\t * - list of clocks for each module;\n\t * - maximum value that each clock is compared against or set to;\n\t * - g.c.d. of all integers used in clock comparisons or assignments.\n\t */\n\tclass ComputeClockInformation extends ASTTraverse\n\t{\n\t\t// Model/property info\n\t\tPropertiesFile propertiesFile = null;\n\t\tLabelList labelList = null;\n\t\t// Clock info\n\t\tprivate Map<String, List<String>> clockLists;\n\t\tprivate List<String> currentClockList;\n\t\tprivate Map<String, Integer> clockMaxs;\n\t\tprivate Set<Integer> allClockVals;\n\t\tprivate int scaleFactor;\n\t\t\n\t\tpublic ComputeClockInformation(ModulesFile modulesFile, PropertiesFile propertiesFile, Expression propertyToCheck) throws PrismLangException\n\t\t{\n\t\t\t// Extract some info needed for traversal \n\t\t\tthis.propertiesFile = propertiesFile;\n\t\t\tlabelList = (propertiesFile == null) ? null : propertiesFile.getLabelList();\n\t\t\t// Set up storage\n\t\t\tclockLists = new HashMap<String, List<String>>();\n\t\t\tclockMaxs = new HashMap<String, Integer>();\n\t\t\tallClockVals = new HashSet<Integer>();\n\t\t\t// Traverse ModulesFile first (further storage created)\n\t\t\tmodulesFile.accept(this);\n\t\t\t// Then property (but not whole property file, to maximise possible scaling)\n\t\t\tpropertyToCheck.accept(this);\n\t\t\t// Finally, compute GCDs and scale factor\n\t\t\tscaleFactor = computeGCD(allClockVals);\n\t\t}\n\n\t\tprivate void updateMax(String clock, int val)\n\t\t{\n\t\t\tInteger i = clockMaxs.get(clock);\n\t\t\tif (i == null || val > i)\n\t\t\t\tclockMaxs.put(clock, val);\n\t\t}\n\n\t\tpublic List<String> getClocksForModule(String module)\n\t\t{\n\t\t\tList<String> list = clockLists.get(module);\n\t\t\treturn (list == null) ? new ArrayList<String>() : list;\n\t\t}\n\n\t\tpublic int getClockMax(String clock)\n\t\t{\n\t\t\tInteger i = clockMaxs.get(clock);\n\t\t\treturn (i == null) ? -1 : i;\n\t\t}\n\n\t\tpublic Map<String, Integer> getClockMaxs()\n\t\t{\n\t\t\treturn clockMaxs;\n\t\t}\n\n\t\t/**\n\t\t * Get the maximum value of a clock, scaled wrt. GCD (if required)\n\t\t * @param clock\n\t\t * @return\n\t\t */\n\t\tpublic int getScaledClockMax(String clock)\n\t\t{\n\t\t\tInteger i = clockMaxs.get(clock);\n\t\t\treturn (i == null) ? -1 : doScaling ? i / scaleFactor : i;\n\t\t}\n\n\t\tpublic int getScaleFactor()\n\t\t{\n\t\t\treturn scaleFactor;\n\t\t}\n\n\t\t/**\n\t\t * Compute greatest common divisor of several non-negative ints\n\t\t */\n\t\tprivate int computeGCD(Iterable<Integer> ints)\n\t\t{\n\t\t\tint gcd = 0;\n\t\t\tfor (int x : ints) {\n\t\t\t\tgcd = computeGCD(gcd, x);\n\t\t\t}\n\t\t\tif (gcd == 0) {\n\t\t\t\t// For the case where clock set is empty or all zeros\n\t\t\t\tgcd = 1;\n\t\t\t}\n\t\t\treturn gcd;\n\t\t}\n\n\t\t/**\n\t\t * Compute greatest common divisor of 2 non-negative ints\n\t\t */\n\t\tprivate int computeGCD(int x, int y)\n\t\t{\n\t\t\treturn (y == 0) ? x : computeGCD(y, x % y);\n\t\t}\n\n\t\t// AST traversal\n\t\t\n\t\tpublic void visitPre(parser.ast.Module e) throws PrismLangException\n\t\t{\n\t\t\t// Create new array to store clocks for this module\n\t\t\tcurrentClockList = new ArrayList<String>();\n\t\t\tclockLists.put(e.getName(), currentClockList);\n\t\t}\n\n\t\tpublic void visitPost(Declaration e) throws PrismLangException\n\t\t{\n\t\t\t// Detect clock variable and store info\n\t\t\tif (e.getDeclType() instanceof DeclarationClock) {\n\t\t\t\tcurrentClockList.add(e.getName());\n\t\t\t}\n\t\t}\n\n\t\t// Resets\n\t\tpublic Object visit(Update e) throws PrismLangException\n\t\t{\n\t\t\tCollection<Integer> allVals;\n\t\t\tint n = e.getNumElements();\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tif (e.getType(i) instanceof TypeClock) {\n\t\t\t\t\tString clock = e.getVar(i);\n\t\t\t\t\tint maxVal = ParserUtils.findMaxForIntExpression(e.getExpression(i), varList, constantValues);\n\t\t\t\t\tupdateMax(clock, maxVal);\n\t\t\t\t\tallVals = ParserUtils.findAllValsForIntExpression(e.getExpression(i), varList, constantValues);\n\t\t\t\t\tallClockVals.addAll(allVals);\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn e;\n\t\t}\n\n\t\t// Clock constraints\n\t\tpublic void visitPost(ExpressionBinaryOp e) throws PrismLangException\n\t\t{\n\t\t\t// If this is a clock constraint, get and store max value\n\t\t\t// (only look at x ~ c or c ~ x)\n\t\t\tString clock;\n\t\t\tint maxVal;\n\t\t\tCollection<Integer> allVals;\n\t\t\tif (e.getOperand1().getType() instanceof TypeClock) {\n\t\t\t\tif (!(e.getOperand2().getType() instanceof TypeClock)) {\n\t\t\t\t\tclock = ((ExpressionVar) e.getOperand1()).getName();\n\t\t\t\t\tmaxVal = ParserUtils.findMaxForIntExpression(e.getOperand2(), varList, constantValues);\n\t\t\t\t\tupdateMax(clock, maxVal);\n\t\t\t\t\tallVals = ParserUtils.findAllValsForIntExpression(e.getOperand2(), varList, constantValues);\n\t\t\t\t\tallClockVals.addAll(allVals);\n\t\t\t\t}\n\t\t\t} else if (e.getOperand2().getType() instanceof TypeClock) {\n\t\t\t\tclock = ((ExpressionVar) e.getOperand2()).getName();\n\t\t\t\tmaxVal = ParserUtils.findMaxForIntExpression(e.getOperand1(), varList, constantValues);\n\t\t\t\tupdateMax(clock, maxVal);\n\t\t\t\tallVals = ParserUtils.findAllValsForIntExpression(e.getOperand1(), varList, constantValues);\n\t\t\t\tallClockVals.addAll(allVals);\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Time bounds in properties\n\t\tpublic void visitPost(ExpressionTemporal e) throws PrismLangException\n\t\t{\n\t\t\t// This is easier than for clock constraints since they must be constant\n\t\t\t// (so just evaluate directly)\n\t\t\t// We also don't care about the max value - this is done elsewhere;\n\t\t\t// we just want to make sure that the values is used to compute the GCD\n\t\t\tif (e.getLowerBound() != null) {\n\t\t\t\tallClockVals.add(e.getLowerBound().evaluateInt(constantValues));\n\t\t\t}\n\t\t\tif (e.getUpperBound() != null) {\n\t\t\t\tallClockVals.add(e.getUpperBound().evaluateInt(constantValues));\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Recurse on labels\n\t\tpublic void visitPost(ExpressionLabel e) throws PrismLangException\n\t\t{\n\t\t\tif (labelList != null) {\n\t\t\t\tint i = labelList.getLabelIndex(e.getName());\n\t\t\t\tif (i != -1) {\n\t\t\t\t\tlabelList.getLabel(i).accept(this);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Recurse on property refs\n\t\tpublic void visitPost(ExpressionProp e) throws PrismLangException\n\t\t{\n\t\t\t// If possible, look up property and recurse\n\t\t\tif (propertiesFile != null) {\n\t\t\t\tProperty prop = propertiesFile.lookUpPropertyObjectByName(e.getName());\n\t\t\t\tif (prop != null) {\n\t\t\t\t\tprop.accept(this);\n\t\t\t\t} else {\n\t\t\t\t\tthrow new PrismLangException(\"Unknown property reference \" + e, e);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/Edge.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.io.IOException;\nimport java.io.Writer;\nimport java.util.*;\n\nimport prism.PrismException;\n\npublic class Edge\n{\n\t// Parent transition;\n\tprivate Transition parent;\n\t// Probability\n\tprivate double prob;\n\t// Destination location\n\tprivate int dest;\n\t// Resets\n\tprivate HashMap<Integer, Integer> resets;\n\n\t/**\n\t * Create an empty edge.\n\t * @param parent Parent transition\n\t * @param prob Probability\n\t * @param dest destination location\n\t */\n\tpublic Edge(Transition parent, double prob, int dest)\n\t{\n\t\tthis.parent = parent;\n\t\tthis.prob = prob;\n\t\tthis.dest = dest;\n\t\tresets = new HashMap<Integer, Integer>();\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic Edge(Edge edge)\n\t{\n\t\tthis(edge.parent, edge.prob, edge.dest);\n\t\tfor (Map.Entry<Integer, Integer> e : edge.resets.entrySet()) {\n\t\t\taddReset(e.getKey(), e.getValue());\n\t\t}\n\t}\n\t\n\tpublic void setProb(double prob)\n\t{\n\t\tthis.prob = prob;\n\t}\n\n\tpublic void setDestination(int dest)\n\t{\n\t\tthis.dest = dest;\n\t}\n\n\tpublic void setParent(Transition parent)\n\t{\n\t\tthis.parent = parent;\n\t}\n\n\tpublic void addReset(int clock)\n\t{\n\t\taddReset(clock, 0);\n\t}\n\n\tpublic void addReset(int clock, int val)\n\t{\n\t\tresets.put(clock, val);\n\t}\n\n\tpublic Transition getParent()\n\t{\n\t\treturn parent;\n\t}\n\n\tpublic int getDestination()\n\t{\n\t\treturn dest;\n\t}\n\n\tpublic double getProbability()\n\t{\n\t\treturn prob;\n\t}\n\n\tpublic Iterable<Map.Entry<Integer, Integer>> getResets()\n\t{\n\t\treturn resets.entrySet();\n\t}\n\n\t/**\n\t * Perform some basic syntactic checks.\n\t */\n\tpublic void check() throws PrismException\n\t{\n\t}\n\n\tpublic String toString()\n\t{\n\t\tboolean first = true;\n\t\tString s = \"\";\n\t\ts += prob + \" : {\";\n\t\tfor (Map.Entry<Integer, Integer> e : resets.entrySet()) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\ts += \",\";\n\t\t\ts += parent.getParent().getClockName(e.getKey());\n\t\t\ts += \"=\" + e.getValue();\n\t\t}\n\t\ts += \"}\" + parent.getParent().getLocationName(dest);\n\t\treturn s;\n\t}\n\n\tpublic void writeToDesFile(Writer out, String actionPrefix, Iterable<Constraint> guard) throws PrismException,\n\t\t\tIOException\n\t{\n\t\tboolean first;\n\t\tPTA pta = parent.getParent();\n\t\tout.write(\"\\t\" + actionPrefix + \"tran  \");\n\t\tout.write(pta.getLocationName(dest).toString().replace(':', '_') + \"; \");\n\t\tout.write(Constraint.toStringList(pta, guard));\n\t\tout.write(\"; \");\n\t\tfirst = true;\n\t\tfor (Map.Entry<Integer, Integer> e : resets.entrySet()) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\tout.write(\",\");\n\t\t\tout.write(pta.getClockName(e.getKey()) + \"=\" + e.getValue());\n\t\t}\n\t\tif (first)\n\t\t\tout.write(\"null\");\n\t\tout.write(\"; \" + prob + \"\\n\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/ForwardsReach.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\nimport prism.*;\nimport explicit.*;\n\npublic class ForwardsReach\n{\n\t// Log for output\n\tprotected PrismLog mainLog;\n\n\t// PTA target info\n\tprotected BitSet targetLocs;\n\tprotected Constraint targetConstraint;\n\n\t// Extra information associated with reachability graph\n\tprotected BitSet target; // Bit set specifying target states\n\tprotected List<Integer> initialStates; // Initial states\n\n\t// Constructors\n\n\tpublic ForwardsReach()\n\t{\n\t\tthis(new PrismPrintStreamLog(System.out));\n\t}\n\n\tpublic ForwardsReach(PrismLog log)\n\t{\n\t\tthis.mainLog = log;\n\t}\n\n\t// Accessors for other info generated during construction of reachability graph\n\n\tpublic BitSet getTarget()\n\t{\n\t\treturn target;\n\t}\n\n\tpublic List<Integer> getInitialStates()\n\t{\n\t\treturn initialStates;\n\t}\n\n\t/**\n\t * Build a reachability graph based on a forwards PTA traversal.\n\t * All zones in the symbolic states in the graph are guaranteed to be convex (i.e. DBMs).\n\t * The set of target states found and the (singleton) set of initial states are stored separately\n\t * and can be obtained subsequently using getTarget() and getInitialStates().\n\t */\n\tpublic ReachabilityGraph buildForwardsGraph(PTA pta, BitSet targetLocs, Constraint targetConstraint)\n\t\t\tthrows PrismException\n\t{\n\t\treturn buildForwardsGraphFormats10(pta, targetLocs, targetConstraint);\n\t\t//return buildForwardsGraphFormats09(pta, targetLocs, targetConstraint);\n\t}\n\t\n\t/**\n\t * Implementation of {@link #buildForwardsGraph} using FORMATS'10 definition.\n\t */\n\tprivate ReachabilityGraph buildForwardsGraphFormats10(PTA pta, BitSet targetLocs, Constraint targetConstraint)\n\tthrows PrismException\n\t{\n\t\tLocZone init, lz, lz2;\n\t\tLinkedList<LocZone> X;\n\t\tStateStorage<LocZone> Yset;\n\t\t//LocZoneSetOld Zset;\n\t\tReachabilityGraph graph;\n\t\tint src, dest, count, dests[];\n\t\tboolean canDiverge;\n\t\tlong timer;\n\n\t\t// Store target info\n\t\tthis.targetLocs = targetLocs;\n\t\tthis.targetConstraint = targetConstraint;\n\n\t\t// Starting reachability...\n\t\tmainLog.print(\"\\nBuilding forwards reachability graph...\");\n\t\tmainLog.flush();\n\t\tProgressDisplay progress = new ProgressDisplay(mainLog);\n\t\tprogress.start();\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Re-compute max clock constraint value if required\n\t\tif (targetConstraint != null)\n\t\t\tpta.recomputeMaxClockConstraint(targetConstraint);\n\t\t\n\t\t// Initialise data structures\n\t\tgraph = new ReachabilityGraph(pta);\n\t\tYset = new IndexedSet<LocZone>();\n\t\tX = new LinkedList<LocZone>();\n\t\ttarget = new BitSet();\n\n\t\t// Build initial symbolic state (NB: assume initial location = 0)\n\t\tinit = new LocZone(0, DBM.createZero(pta));\n\n\t\t// Reachability loop\n\t\tYset.add(init);\n\t\tX.add(init);\n\t\tsrc = -1;\n\t\t// While there are unexplored symbolic states (in X)...\n\t\twhile (!X.isEmpty()) {\n\t\t\t// Pick next state to explore\n\t\t\t// X is a list containing states in order found\n\t\t\t// (so we know index of lz is src+1)\n\t\t\tlz = X.removeFirst();\n\t\t\tsrc++;\n\t\t\t// Compute timed post for this zone (NB: do this before checking if target)\n\t\t\tlz = lz.deepCopy();\n\t\t\tlz.tPost(pta);\n\t\t\t// Is this a target state? (If so, don't explore)\n\t\t\tif (targetLocs.get(lz.loc) && (targetConstraint == null || lz.zone.isSatisfied(targetConstraint))) {\n\t\t\t\ttarget.set(src);\n\t\t\t\t// Add null for this state (no need to store info)\n\t\t\t\tgraph.addState();\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\t// Check if time can diverge in this state\n\t\t\t// (note we already did tPost above)\n\t\t\tcanDiverge = lz.zone.allClocksAreUnbounded();\n\t\t\t// Explore this symbolic state\n\t\t\t// First, check for one possible cause of timelock:\n\t\t\t// no PTA transitions and not possible for time to diverge\n\t\t\tif (!canDiverge && pta.getTransitions(lz.loc).size() == 0) {\n\t\t\t\tthrow new PrismException(\"Timelock (no transitions) in PTA at location \" + pta.getLocationNameString(lz.loc));\n\t\t\t}\n\t\t\t// Add current state to reachability graph\n\t\t\tgraph.addState();\n\t\t\t// For unbounded case, add a special self-loop transition to model divergence\n\t\t\tif (canDiverge) {\n\t\t\t\tdests = new int[1];\n\t\t\t\tdests[0] = src;\n\t\t\t\tTransition trNew = new Transition(pta, lz.loc, \"_diverge\");\n\t\t\t\ttrNew.addEdge(1.0, lz.loc);\n\t\t\t\tgraph.addTransition(src, trNew, dests, null);\n\t\t\t}\n\t\t\t// And for the non-unbounded case, need to do a check for time-locks\n\t\t\telse {\n\t\t\t\tZone zone;\n\t\t\t\tNCZone ncZone;\n\t\t\t\t// Build union of tPre of each guard\n\t\t\t\tncZone = DBMList.createFalse(pta);\n\t\t\t\tfor (Transition transition : pta.getTransitions(lz.loc)) {\n\t\t\t\t\tzone = DBM.createFromConstraints(pta, transition.getGuardConstraints());\n\t\t\t\t\tzone.down();\n\t\t\t\t\tncZone.union(zone);\n\t\t\t\t}\n\t\t\t\t// Make sure tPost of this zone is not bigger (tPost done above)\n\t\t\t\t// (i.e. intersection with complement of union is empty)\n\t\t\t\tncZone.complement();\n\t\t\t\tncZone.intersect(lz.zone);\n\t\t\t\tif (!ncZone.isEmpty()) {\n\t\t\t\t\tString s = \"Timelock in PTA at location \" + pta.getLocationNameString(lz.loc);\n\t\t\t\t\ts += \" when \" + ncZone.getAZone();\n\t\t\t\t\tthrow new PrismException(s);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// For each outgoing transition...\n\t\t\tfor (Transition transition : pta.getTransitions(lz.loc)) {\n\t\t\t\tdests = new int[transition.getNumEdges()];\n\t\t\t\tboolean enabled = false;\n\t\t\t\tboolean unenabled = false;\n\t\t\t\tEdge unenabledEdge = null;\n\t\t\t\tcount = 0;\n\t\t\t\tfor (Edge edge : transition.getEdges()) {\n\t\t\t\t\t// Do \"discrete post\" for this edge\n\t\t\t\t\t// (followed by c-closure)\n\t\t\t\t\tlz2 = lz.deepCopy();\n\t\t\t\t\tlz2.dPost(edge);\n\t\t\t\t\tlz2.cClosure(pta);\n\t\t\t\t\t// If non-empty, create edge, also adding state to X if new \n\t\t\t\t\tif (!lz2.zone.isEmpty()) {\n\t\t\t\t\t\tif (Yset.add(lz2)) {\n\t\t\t\t\t\t\tX.add(lz2);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tdest = Yset.getIndexOfLastAdd();\n\t\t\t\t\t\tenabled = true;\n\t\t\t\t\t\tdests[count] = dest;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tunenabled = true;\n\t\t\t\t\t\t// Store first unenabled edge\n\t\t\t\t\t\tunenabledEdge = (unenabledEdge == null) ? edge : unenabledEdge;\n\t\t\t\t\t\tdests[count] = -1;\n\t\t\t\t\t}\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t\tif (enabled) {\n\t\t\t\t\tif (unenabled) {\n\t\t\t\t\t\tString s = \"Badly formed PTA at location \" + pta.getLocationNameString(lz.loc) + \" when \" + lz.zone;\n\t\t\t\t\t\ts += \": \\\"\" + transition.getAction() + \"\\\"-labelled transition to \";\n\t\t\t\t\t\ts += pta.getLocationNameString(unenabledEdge.getDestination());\n\t\t\t\t\t\ts += \" leads to state where invariant is not satisfied\";\n\t\t\t\t\t\tthrow new PrismException(s);\n\t\t\t\t\t}\n\t\t\t\t\tgraph.addTransition(src, transition, dests, null);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Check for another possible cause of timelock:\n\t\t\t// no PTA transitions *enabled* and not possible for time to diverge\n\t\t\t// (NB: This should be defunct now because of earlier timelock check)\n\t\t\t// (NB2: Strictly speaking, don't need to check canDiverge - if it was\n\t\t\t// true, we would have added a loop transition that is definitely enabled)\n\t\t\tif (!canDiverge && graph.trans.get(src).size() == 0) {\n\t\t\t\tString s = \"Timelock in PTA (no enabled transitions) at location \" + pta.getLocationNameString(lz.loc);\n\t\t\t\ts += \" when \" + lz.zone;\n\t\t\t\tthrow new PrismException(s);\n\t\t\t}\n\t\t\t// Print some progress info occasionally\n\t\t\tif (progress.ready())\n\t\t\t\tprogress.update(Yset.size());\n\t\t}\n\n\t\t// Tidy up progress display\n\t\tprogress.update(Yset.size());\n\t\tprogress.end(\" states\");\n\n\t\t// Convert state set to ArrayList and store\n\t\tgraph.states = Yset.toArrayList();\n\n\t\t// Always have a single initial state 0 after this construction\n\t\tinitialStates = new ArrayList<Integer>();\n\t\tinitialStates.add(0);\n\n\t\t// Reachability complete\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Graph constructed in \" + (timer / 1000.0) + \" secs.\");\n\t\tmainLog.print(\"Graph: \" + graph.states.size() + \" symbolic states\");\n\t\tmainLog.println(\" (\" + initialStates.size() + \" initial, \" + target.cardinality() + \" target)\");\n\n\t\t// Print a warning if there are no target states\n\t\tif (target.cardinality() == 0)\n\t\t\tmainLog.printWarning(\"There are no target states.\");\n\n\t\treturn graph;\n\t}\n\t\n\t/**\n\t * Implementation of {@link #buildForwardsGraph} using FORMATS'09 definition.\n\t * This should not be used any more since changes/improvements to e.g. timelock detection\n\t * have been implemented under the assumption that the default (FORMATS'10) algorithm is used.\n\t */\n\t@SuppressWarnings(\"unused\")\n\tprivate ReachabilityGraph buildForwardsGraphFormats09(PTA pta, BitSet targetLocs, Constraint targetConstraint)\n\tthrows PrismException\n\t{\n\t\tZone z;\n\t\tLocZone init, lz, lz2;\n\t\tLinkedList<LocZone> Y;\n\t\tStateStorage<LocZone> Zset;\n\t\t//LocZoneSetOld Zset;\n\t\tReachabilityGraph graph;\n\t\tint cMax;\n\t\tint src, dest, count;\n\t\tlong timer, timerProgress;\n\t\tboolean progressDisplayed;\n\n\t\t// Store target info\n\t\tthis.targetLocs = targetLocs;\n\t\tthis.targetConstraint = targetConstraint;\n\n\t\t// Starting reachability...\n\t\tmainLog.println(\"\\nBuilding forwards reachability graph...\");\n\t\ttimer = timerProgress = System.currentTimeMillis();\n\t\tprogressDisplayed = false;\n\n\t\t// Compute max clock constraint value\n\t\tif (targetConstraint != null)\n\t\t\tpta.recomputeMaxClockConstraint(targetConstraint);\n\t\tcMax = pta.getMaxClockConstraint();\n\n\t\t// Initialise data structures\n\t\tgraph = new ReachabilityGraph(pta);\n\t\t//Zset = new LocZoneSetOld();\n\t\tZset = new IndexedSet<LocZone>();\n\t\tY = new LinkedList<LocZone>();\n\t\ttarget = new BitSet();\n\n\t\t// Build initial symbolic state (NB: assume initial location = 0)\n\t\tz = DBM.createZero(pta);\n\t\tinit = new LocZone(0, z);\n\t\t// And do tpost/c-closure\n\t\tinit.tPost(pta);\n\t\tinit.cClosure(pta);\n\n\t\t// Reachability loop\n\t\tZset.add(init);\n\t\tY.add(init);\n\t\tsrc = -1;\n\t\t// While there are unexplored symbolic states (in Y)...\n\t\twhile (!Y.isEmpty()) {\n\t\t\t// Pick next state to explore\n\t\t\t// Y is a list containing states in order found\n\t\t\t// (so we know index of lz is src)\n\t\t\tlz = Y.removeFirst();\n\t\t\tsrc++;\n\t\t\t// Is this a target state?\n\t\t\tif (targetLocs.get(lz.loc) && (targetConstraint == null || lz.zone.isSatisfied(targetConstraint))) {\n\t\t\t\ttarget.set(src);\n\t\t\t\t// Add null for this state (no need to store info)\n\t\t\t\tgraph.addState();\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\t// Otherwise, explore this symbolic state\n\t\t\t// First, check there is at least one transition\n\t\t\t// (don't want deadlocks in non-target states)\n\t\t\tif (pta.getTransitions(lz.loc).size() == 0) {\n\t\t\t\tthrow new PrismException(\"PTA deadlocks in location \" + pta.getLocationNameString(lz.loc));\n\t\t\t}\n\t\t\t// For each outgoing transition...\n\t\t\tgraph.addState();\n\t\t\tfor (Transition transition : pta.getTransitions(lz.loc)) {\n\t\t\t\tint[] dests = new int[transition.getNumEdges()];\n\t\t\t\tboolean enabled = false;\n\t\t\t\tboolean unenabled = false;\n\t\t\t\tcount = 0;\n\t\t\t\tfor (Edge edge : transition.getEdges()) {\n\t\t\t\t\t// Build \"post\" zone for this edge\n\t\t\t\t\t// (dpost, then tpost, then c-closure) \n\t\t\t\t\tlz2 = lz.deepCopy();\n\t\t\t\t\tlz2.dPost(edge);\n\t\t\t\t\tlz2.tPost(pta);\n\t\t\t\t\tlz2.cClosure(pta);\n\t\t\t\t\t// If non-empty, create edge, also adding state to Y if new \n\t\t\t\t\tif (!lz2.zone.isEmpty()) {\n\t\t\t\t\t\tif (Zset.add(lz2)) {\n\t\t\t\t\t\t\tY.add(lz2);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tdest = Zset.getIndexOfLastAdd();\n\t\t\t\t\t\tenabled = true;\n\t\t\t\t\t\tdests[count] = dest;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tunenabled = true;\n\t\t\t\t\t\tdests[count] = -1;\n\t\t\t\t\t}\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t\tif (enabled) {\n\t\t\t\t\tif (unenabled)\n\t\t\t\t\t\tthrow new PrismException(\"Badly formed PTA: state \" + src);\n\t\t\t\t\tgraph.addTransition(src, transition, dests, null);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Print some progress info occasionally\n\t\t\tif (System.currentTimeMillis() - timerProgress > 3000) {\n\t\t\t\tif (!progressDisplayed) {\n\t\t\t\t\tmainLog.print(\"Number of states so far:\");\n\t\t\t\t\tprogressDisplayed = true;\n\t\t\t\t}\n\t\t\t\tmainLog.print(\" \" + Zset.size());\n\t\t\t\tmainLog.flush();\n\t\t\t\ttimerProgress = System.currentTimeMillis();\n\t\t\t}\n\t\t}\n\n\t\t// Tidy up progress display\n\t\tif (progressDisplayed)\n\t\t\tmainLog.println(\" \" + Zset.size());\n\n\t\t// Convert state set to ArrayList and store\n\t\tgraph.states = Zset.toArrayList();\n\n\t\t// Always have a single initial state 0 after this construction\n\t\tinitialStates = new ArrayList<Integer>();\n\t\tinitialStates.add(0);\n\n\t\t// Reachability complete\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Graph constructed in \" + (timer / 1000.0) + \" secs.\");\n\t\tmainLog.print(\"Graph: \" + graph.states.size() + \" symbolic states\");\n\t\tmainLog.println(\"), \" + target.cardinality() + \" target states\");\n\n\t\t// Print a warning if there are no target states\n\t\tif (target.cardinality() == 0)\n\t\t\tmainLog.printWarning(\"There are no target states.\");\n\n\t\treturn graph;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/LocZone.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.Map;\n\npublic class LocZone\n{\n\tpublic int loc;\n\tpublic Zone zone;\n\n\tpublic LocZone(int loc, Zone zone)\n\t{\n\t\tthis.loc = loc;\n\t\tthis.zone = zone;\n\t}\n\n\t/**\n\t * Do time part of post operation (not including c-closure).\n\t * Note: pta is passed in just for efficiency, could find it if we wanted.\n\t */\n\tpublic void tPost(PTA pta)\n\t{\n\t\t// Time successor (up)\n\t\tzone.up(pta.getInvariantConstraints(loc));\n\t}\n\t\n\t/**\n\t * Do discrete part of post operation (wrt. an edge).\n\t */\n\tpublic void dPost(Edge edge)\n\t{\n\t\tTransition tr = edge.getParent();\n\t\t// Intersect this zone with guard of edge's transition's guard \n\t\tfor (Constraint c : tr.getGuardConstraints()) {\n\t\t\tzone.addConstraint(c);\n\t\t}\n\t\t// Apply clock resets in edge\n\t\tfor (Map.Entry<Integer,Integer>e : edge.getResets()) {\n\t\t\tzone.reset(e.getKey(), e.getValue());\n\t\t}\n\t\t// Intersect with invariant of target location \n\t\tzone.addConstraints(tr.getParent().getInvariantConstraints(edge.getDestination()));\n\t\t// Set location to target location\n\t\tloc = edge.getDestination();\n\t}\n\n\t/**\n\t * Do c-closure.\n\t * Note: pta is passed in just for efficiency, could find it if we wanted.\n\t */\n\tpublic void cClosure(PTA pta)\n\t{\n\t\t// c-Closure\n\t\tzone.cClosure(pta.getMaxClockConstraint());\n\t}\n\t\n\t/**\n\t * Do time part of predecessor operation (not including c-closure).\n\t * Note: pta is passed in just for efficiency, could find it if we wanted.\n\t */\n\tpublic void tPre(PTA pta)\n\t{\n\t\t// Time predecessor (down)\n\t\tzone.down(pta.getInvariantConstraints(loc));\n\t}\n\t\n\t/**\n\t * dPre: discrete predecessor\n\t */\n\tpublic void dPre(Edge edge)\n\t{\n\t\tTransition tr = edge.getParent();\n\t\t// Backwards reset of clocks from edge\n\t\tfor (Map.Entry<Integer,Integer>e : edge.getResets()) {\n\t\t\tzone.backReset(e.getKey(), e.getValue());\n\t\t}\n\t\t// Intersect with guard of edge's transition's guard \n\t\tfor (Constraint c : tr.getGuardConstraints()) {\n\t\t\tzone.addConstraint(c);\n\t\t}\n\t\t// Intersect with invariant of source location \n\t\tzone.addConstraints(tr.getParent().getInvariantConstraints(tr.getSource()));\n\t\t// Set location to source location\n\t\tloc = tr.getSource();\n\t}\n\n\t/**\n\t * Clone this location/zone pair\n\t */\n\tpublic LocZone deepCopy()\n\t{\n\t\treturn new LocZone(loc, zone.deepCopy());\n\t}\n\t\n\t// Standard Java methods\n\n\tpublic int hashCode()\n\t{\n\t\treturn loc + zone.hashCode();\n\t}\n\t\n\tpublic boolean equals(Object o)\n\t{\n\t\tLocZone lz;\n\t\tif (o == null) return false;\n\t\ttry {\n\t\t\tlz = (LocZone) o;\n\t\t} catch (ClassCastException e) {\n\t\t\treturn false;\n\t\t}\n\t\tif (loc != lz.loc)\n\t\t\treturn false;\n\t\treturn (zone.equals(lz.zone));\n\t}\n\n\tpublic String toString()\n\t{\n\t\treturn \"(\" + zone.getPTA().getLocationNameString(loc) + \",\" + zone + \")\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/LocZoneSet.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\npublic class LocZoneSet\n{\n\tprivate HashMap<LocZone, Integer> set;\n\tprivate int indexOfLastAdd;\n\n\tpublic LocZoneSet()\n\t{\n\t\tset = new HashMap<LocZone, Integer>();\n\t\tindexOfLastAdd = -1;\n\t}\n\n\tpublic boolean add(int loc, Zone z)\n\t{\n\t\treturn add(new LocZone(loc, z));\n\t}\n\n\tpublic boolean add(LocZone lz)\n\t{\n\t\tInteger i = set.get(lz);\n\t\tif (i != null) {\n\t\t\tindexOfLastAdd = i;\n\t\t\treturn false;\n\t\t} else {\n\t\t\tindexOfLastAdd = set.size();\n\t\t\tset.put(lz, set.size());\n\t\t\treturn true;\n\t\t}\n\t}\n\n\tpublic boolean contains(LocZone lz)\n\t{\n\t\t\treturn set.get(lz) != null;\n\t}\n\n\tpublic int getIndexOfLastAdd()\n\t{\n\t\treturn indexOfLastAdd;\n\t}\n\n\tpublic boolean isEmpty()\n\t{\n\t\treturn set.isEmpty();\n\t}\n\n\tpublic int size()\n\t{\n\t\treturn set.size();\n\t}\n\n\tpublic ArrayList<LocZone> toArrayList()\n\t{\n\t\tint i, n;\n\n\t\tn = set.size();\n\t\tArrayList<LocZone> list = new ArrayList<LocZone>(n);\n\t\tfor (i = 0; i < n ; i++)\n\t\t\tlist.add(null);\n\t\tfor (Map.Entry<LocZone, Integer> e : set.entrySet()) {\n\t\t\tlist.set(e.getValue(), e.getKey());\n\t\t}\n\t\treturn list;\n\t}\n\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\ts += set;\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/LocZoneSetOld.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\npublic class LocZoneSetOld extends ArrayList<LocZone>\n{\n\tprivate int indexOfLastAdd = -1;\n\n\tpublic int getIndexOfLastAdd()\n\t{\n\t\treturn indexOfLastAdd;\n\t}\n\n\tpublic boolean add(int loc, Zone z)\n\t{\n\t\treturn add(new LocZone(loc, z));\n\t}\n\n\t// Override add to store index\n\tpublic boolean add(LocZone lz)\n\t{\n\t\tint i = indexOf(lz);\n\t\tif (i == -1) {\n\t\t\tindexOfLastAdd = size();\n\t\t\tsuper.add(lz);\n\t\t\treturn true;\n\t\t} else {\n\t\t\tindexOfLastAdd = i;\n\t\t\treturn false;\n\t\t}\n\t}\n\t\n\tpublic ArrayList<LocZone> toArrayList()\n\t{\n\t\treturn this;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/NCZone.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\npublic abstract class NCZone extends Zone\n{\n\tpublic abstract void intersectComplement(Zone z);\n\tpublic abstract void complement();\n\tpublic abstract void union(Zone z);\n\tpublic abstract Zone getAZone();\n\tpublic abstract NCZone deepCopy();\n}\n"
  },
  {
    "path": "prism/src/pta/PTA.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.io.*;\nimport java.util.*;\n\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport parser.*;\nimport pta.parser.PTAParser;\n\npublic class PTA\n{\n\t// Info about clocks\n\t// Note: from an external point of view, clocks are indexed from 1\n\t// (to allow use of index 0 for the zero clock)\n\tprotected int numClocks;\n\tprotected ArrayList<String> clockNames;\n\t// Locations info\n\tprotected int numLocations;\n\tprotected ArrayList<Object> locationNames;\n\tprotected ArrayList<LinkedHashSet<Constraint>> invariants;\n\tprotected List<String> locationNameVars;\n\t// Transitions\n\tprotected int numTransitions;\n\tprotected ArrayList<ArrayList<Transition>> transitions;\n\t// Alphabet\n\tprotected List<String> alphabet;\n\t// Maximum clock constraint value\n\tprotected int cMax;\n\n\t/**\n\t * Constructor: build an empty PTA.\n\t * \n\t * @param alphabet The set of (non-tau) actions that can label transitions.\n\t * This is *syntactically* defined, e.g., in PRISM it's the list of all actions appearing in commands,\n\t * but may be a strict superset of the actions that actually label transitions.\n\t */\n\tpublic PTA(List<String> alphabet)\n\t{\n\t\tnumClocks = 0;\n\t\tclockNames = new ArrayList<>();\n\t\tnumLocations = 0;\n\t\tlocationNames = new ArrayList<>();\n\t\tinvariants = new ArrayList<>();\n\t\tlocationNameVars = null;\n\t\tnumTransitions = 0;\n\t\ttransitions = new ArrayList<>();\n\t\tthis.alphabet = alphabet;\n\t\tcMax = 0;\n\t}\n\n\t// Setters\n\n\tpublic int addClock(String name)\n\t{\n\t\tnumClocks++;\n\t\tclockNames.add(name);\n\t\t// Note: returned index starts from 1, not 0\n\t\treturn numClocks;\n\t}\n\n\tpublic int getOrAddClock(String name)\n\t{\n\t\tint i = clockNames.indexOf(name);\n\t\tif (i == -1) {\n\t\t\treturn addClock(name);\n\t\t} else\n\t\t\treturn i + 1;\n\t}\n\n\tpublic int addLocation()\n\t{\n\t\treturn addLocation(null);\n\t}\n\n\tpublic int addLocation(Object name)\n\t{\n\t\tnumLocations++;\n\t\tlocationNames.add(name == null ? \"L\" + (numLocations - 1) : name);\n\t\tinvariants.add(new LinkedHashSet<>());\n\t\ttransitions.add(new ArrayList<>());\n\t\treturn numLocations - 1;\n\t}\n\n\tpublic int getOrAddLocation(Object name)\n\t{\n\t\tint i = locationNames.indexOf(name);\n\t\tif (i == -1) {\n\t\t\treturn addLocation(name);\n\t\t} else\n\t\t\treturn i;\n\t}\n\n\tpublic void addInvariantCondition(int loc, Constraint c)\n\t{\n\t\tinvariants.get(loc).add(c);\n\t\trecomputeMaxClockConstraint(c);\n\t}\n\n\tpublic void setInvariantConditions(int loc, LinkedHashSet<Constraint> cs)\n\t{\n\t\tinvariants.set(loc, cs);\n\t\trecomputeMaxClockConstraint(cs);\n\t}\n\n\t/**\n\t * Add a new \"tau\" transition (no action label) to the PTA.\n\t * @param loc Source location of the new transition.  \n\t */\n\tpublic Transition addTransition(int loc)\n\t{\n\t\treturn addTransition(loc, null);\n\t}\n\n\t/**\n\t * Add a new transition to the PTA.\n\t * @param loc Source location of the new transition.  \n\t * @param action Action label for the transition  \n\t */\n\tpublic Transition addTransition(int loc, String action)\n\t{\n\t\tif (action == null)\n\t\t\taction = \"\";\n\t\tTransition transition = new Transition(this, loc, action);\n\t\tArrayList<Transition> list = transitions.get(loc);\n\t\tlist.add(transition);\n\t\tnumTransitions++;\n\t\treturn transition;\n\t}\n\n\t/**\n\t * Add a previously created transition to the PTA.\n\t */\n\tpublic void addTransition(Transition transition)\n\t{\n\t\ttransition.setParent(this);\n\t\tArrayList<Transition> list = transitions.get(transition.getSource());\n\t\tlist.add(transition);\n\t\tnumTransitions++;\n\t}\n\n\tpublic void removeTransition(int loc, Transition transition)\n\t{\n\t\tArrayList<Transition> list = transitions.get(loc);\n\t\tif (list.remove(transition))\n\t\t\tnumTransitions--;\n\t}\n\n\tpublic int recomputeMaxClockConstraint(Constraint c)\n\t{\n\t\tcMax = Math.max(cMax, Math.abs(DB.getSignedDiff(c.db)));\n\t\treturn cMax;\n\t}\n\n\tpublic int recomputeMaxClockConstraint(Iterable<Constraint> cs)\n\t{\n\t\tfor (Constraint c : cs)\n\t\t\trecomputeMaxClockConstraint(c);\n\t\treturn cMax;\n\t}\n\n\tpublic void setLocationNameVars(List<String> locationNameVars)\n\t{\n\t\tthis.locationNameVars = locationNameVars;\n\t}\n\t\n\t// Getters\n\n\tpublic int getNumClocks()\n\t{\n\t\treturn numClocks;\n\t}\n\n\tpublic String getClockName(int x)\n\t{\n\t\tif (x == 0)\n\t\t\treturn \"0\";\n\t\treturn clockNames.get(x - 1);\n\t}\n\n\t/**\n\t * Return index (starting from 1) of a clock, or -1 if non-existent \n\t */\n\tpublic int getClockIndex(String name)\n\t{\n\t\tint i = clockNames.indexOf(name);\n\t\treturn i == -1 ? -1 : i + 1;\n\t}\n\n\tpublic Object getLocationName(int loc)\n\t{\n\t\treturn locationNames.get(loc);\n\t}\n\n\tpublic Object getLocationNameString(int loc)\n\t{\n\t\tObject name = locationNames.get(loc);\n\t\tif (name instanceof State && locationNameVars != null)\n\t\t\treturn ((State)name).toString(locationNameVars);\n\t\telse\n\t\t\treturn name.toString();\n\t}\n\n\tpublic List<Object> getLocationNameList()\n\t{\n\t\treturn locationNames;\n\t}\n\n\tpublic int getLocationIndex(Object name)\n\t{\n\t\treturn locationNames.indexOf(name);\n\t}\n\n\tpublic int getNumLocations()\n\t{\n\t\treturn numLocations;\n\t}\n\n\tpublic Iterable<Constraint> getInvariantConstraints(int loc)\n\t{\n\t\treturn invariants.get(loc);\n\t}\n\n\tpublic List<Transition> getTransitions(int loc)\n\t{\n\t\treturn transitions.get(loc);\n\t}\n\n\tpublic Iterable<Transition> getTransitionsByAction(final int loc, final String action)\n\t{\n\t\treturn new Iterable<Transition>()\n\t\t{\n\t\t\tpublic Iterator<Transition> iterator()\n\t\t\t{\n\t\t\t\treturn new TransitionsByActionIterator(loc, action);\n\t\t\t}\n\t\t};\n\t}\n\n\tpublic int getMaxClockConstraint()\n\t{\n\t\treturn cMax;\n\t}\n\n\tpublic List<String> getAlphabet()\n\t{\n\t\treturn alphabet;\n\t}\n\n\tpublic boolean isActionInAlphabet(String action)\n\t{\n\t\treturn alphabet.contains(action);\n\t}\n\n\t/**\n\t * Perform some basic syntactic checks.\n\t */\n\tpublic void check() throws PrismException\n\t{\n\t\tfor (int i = 0; i < numLocations; i++) {\n\t\t\tfor (Transition t : getTransitions(i)) {\n\t\t\t\tt.check();\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic String infoString()\n\t{\n\t\treturn numClocks + \" clocks, \" + numLocations + \" locations, \" + numTransitions + \" transitions\";\n\t}\n\n\tpublic String toString()\n\t{\n\t\tint i;\n\t\tString s = \"\";\n\t\ts += \"PTA: \" + numLocations + \" locations, \" + numTransitions + \" transitions\\n\";\n\t\ts += \"  cMax = \" + cMax + \", clocks = \" + clockNames + \"\\n\";\n\t\ts += \"   alphabet = \" + alphabet + \"\\n\";\n\t\tfor (i = 0; i < numLocations; i++) {\n\t\t\ts += \"Location \" + i + \" (\" + locationNames.get(i) + \"):\\n\";\n\t\t\ts += \"  Invariant: \" + Constraint.toStringList(this, invariants.get(i)) + \"\\n\";\n\t\t\tfor (Transition t : getTransitions(i))\n\t\t\t\ts += \"  \" + t + \"\\n\";\n\t\t}\n\t\treturn s;\n\t}\n\n\tpublic void writeToDesFile(String filename) throws PrismException\n\t{\n\t\tint i;\n\t\ttry {\n\t\t\tFileWriter out = new FileWriter(filename);\n\t\t\tout.write(\"#no update for variables\\n\");\n\t\t\tfor (i = 0; i < numLocations; i++) {\n\t\t\t\tout.write(\"#\" + i + \"\\n{\\n\");\n\t\t\t\tif (i == 0)\n\t\t\t\t\tout.write(\"init\\n\");\n\t\t\t\tout.write(\"\\tnode \" + getLocationName(i).toString().replace(':', '_') + \"; \");\n\t\t\t\tout.write(Constraint.toStringList(this, invariants.get(i)) + \"\\n\");\n\t\t\t\tfor (Transition t : getTransitions(i))\n\t\t\t\t\tt.writeToDesFile(out);\n\t\t\t\tif (transitions.get(i).isEmpty())\n\t\t\t\t\tout.write(\"\\t[\\n\\t]\\n\");\n\t\t\t\tout.write(i == numLocations - 1 ? \"*\" : \"}\");\n\t\t\t\tout.write(\"\\n\");\n\t\t\t}\n\t\t\tout.close();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"Could not write PTA to file \\\"\" + filename + \"\\\"\");\n\t\t}\n\t}\n\n\t// Static utility methods\n\n\t/**\n\t * Combine the names of two PTA locations (e.g. to put in parallel).\n\t */\n\tpublic static Object combineLocationNames(Object name1, Object name2)\n\t{\n\t\t// Different strategies depending on the types of Object used for names\n\t\t// Strings: colon-delimited concatenation\n\t\tif (name1 instanceof String && name2 instanceof String) {\n\t\t\treturn name1 + \":\" + name2;\n\t\t}\n\t\t// Object arrays: concatenation\n\t\telse if (name1 instanceof Object[] && name2 instanceof Object[]) {\n\t\t\tObject[] arr1 = (Object[]) name1;\n\t\t\tObject[] arr2 = (Object[]) name2;\n\t\t\tObject[] arr = new Object[arr1.length + arr2.length];\n\t\t\tint i;\n\t\t\tfor (i = 0; i < arr1.length; i++)\n\t\t\t\tarr[i] = arr1[i];\n\t\t\tfor (i = 0; i < arr2.length; i++)\n\t\t\t\tarr[arr1.length + i] = arr2[i];\n\t\t\treturn arr;\n\t\t}\n\t\t// State objects: concatenation\n\t\telse if (name1 instanceof State && name2 instanceof State) {\n\t\t\treturn new State((State) name1, (State) name2);\n\t\t}\n\t\t// Values objects: union\n\t\telse if (name1 instanceof Values && name2 instanceof Values) {\n\t\t\tValues vals = new Values((Values) name1);\n\t\t\tvals.addValues((Values) name2);\n\t\t\treturn vals;\n\t\t}\n\t\t// Default: convert to strings, colon-delimited concatenation\n\t\treturn name1 + \":\" + name2;\n\t}\n\n\t/**\n\t * Compute the index (in newPta) of a clock name (from oldPta)\n\t */\n\tpublic static int renameClock(PTA oldPta, PTA newPta, int x)\n\t{\n\t\tint xNew = 0;\n\t\tif (x > 0) {\n\t\t\txNew = newPta.getClockIndex(oldPta.getClockName(x));\n\t\t\tif (xNew == -1)\n\t\t\t\tSystem.out.println(\"Warning: Error renaming clock index \" + x);\n\t\t}\n\t\treturn xNew;\n\t}\n\n\tprivate static PTAParser parser = null;\n\n\t/**\n\t * Construct a PTA by reading in a 'des' file\n\t */\n\tpublic static PTA buildPTAFromDesFile(String file)\n\t{\n\t\tPTA pta = null;\n\t\ttry {\n\t\t\tif (parser == null)\n\t\t\t\tparser = new PTAParser();\n\t\t\tpta = parser.parsePTA(new FileInputStream(file));\n\t\t} catch (PrismLangException e) {\n\t\t\tSystem.out.println(\"Error in \" + file + \": \" + e.getMessage() + \".\");\n\t\t\tSystem.exit(1);\n\t\t} catch (FileNotFoundException e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t\treturn pta;\n\t}\n\n\t/**\n\t * Build a simple test PTA.\n\t */\n\tpublic static PTA buildTestPTA()\n\t{\n\t\tPTA pta;\n\t\tTransition t;\n\t\tEdge e;\n\t\tpta = new PTA(Collections.emptyList());\n\t\tint x = pta.addClock(\"x\");\n\t\tint y = pta.addClock(\"y\");\n\t\tpta.addLocation(); // L0\n\t\tpta.addLocation(); // L1\n\t\tpta.addLocation(); // L2\n\t\tpta.addLocation(); // L3\n\t\tt = pta.addTransition(0);\n\t\te = t.addEdge(0.5, 1);\n\t\te.addReset(x);\n\t\te = t.addEdge(0.5, 2);\n\t\tt = pta.addTransition(1);\n\t\tt.addGuardConstraint(Constraint.buildLeq(x, 0));\n\t\tt.addGuardConstraint(Constraint.buildLeq(y, 1));\n\t\tt.addGuardConstraint(Constraint.buildGeq(y, 0));\n\t\te = t.addEdge(1.0, 3);\n\t\te.addReset(y);\n\t\tt = pta.addTransition(2);\n\t\tt.addGuardConstraint(Constraint.buildLeq(x, 0));\n\t\tt.addGuardConstraint(Constraint.buildLeq(y, 0));\n\t\te = t.addEdge(1.0, 3);\n\t\treturn pta;\n\t}\n\n\t// Inner class used by getTransitionsByAction\n\n\tprivate class TransitionsByActionIterator implements Iterator<Transition>\n\t{\n\t\tprivate Iterator<Transition> it;\n\t\tprivate String action;\n\t\tprivate Transition next;\n\n\t\tprivate TransitionsByActionIterator(int loc, String action)\n\t\t{\n\t\t\tit = transitions.get(loc).iterator();\n\t\t\tthis.action = action;\n\t\t\tcomputeNext();\n\t\t}\n\n\t\tpublic boolean hasNext()\n\t\t{\n\t\t\treturn next != null;\n\t\t}\n\n\t\tpublic Transition next()\n\t\t{\n\t\t\tif (next == null)\n\t\t\t\tthrow new NoSuchElementException();\n\t\t\tTransition tr = next;\n\t\t\tcomputeNext();\n\t\t\treturn tr;\n\t\t}\n\n\t\tpublic void remove()\n\t\t{\n\t\t\tthrow new UnsupportedOperationException();\n\t\t}\n\n\t\tprivate void computeNext()\n\t\t{\n\t\t\tnext = null;\n\t\t\twhile (it.hasNext()) {\n\t\t\t\tTransition tr = it.next();\n\t\t\t\tif (tr != null && tr.getAction().equals(action)) {\n\t\t\t\t\tnext = tr;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/PTAAbstractRefine.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport explicit.*;\n\n/**\n * Probabilistic reachability for PTAs, using abstraction/refinement of stochastic games.\n * See: \"Stochastic Games for Verification of Probabilistic Timed Automata\" (FORMATS'09).\n */\npublic class PTAAbstractRefine extends QuantAbstractRefine\n{\n\t// PTA, target info\n\tprotected PTA pta = null;\n\tprotected BitSet targetLocs;\n\tprotected Constraint targetConstraint;\n\t// Forwards reachability graph\n\tprotected ReachabilityGraph graph;\n\n\t// Flags + options\n\n\t// Do we cache zones representing validity of transition subsets\n\t// for reuse when splitting that zone later on? (definitely saves a little\n\t// bit of time, but at the expense of some space). \n\tboolean storeValidZones = true;\n\n\t/**\n\t * Default constructor.\n\t */\n\tpublic PTAAbstractRefine(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\t// Just do basic config for QuantAbstractRefine\n\t\tsetModelType(ModelType.MDP);\n\t\tsetPropertyType(QuantAbstractRefine.PropertyType.PROB_REACH);\n\t}\n\t\n\t/**\n\t * Compute min/max PTA reachability probabilities using STPG abstraction refinement. \n\t */\n\tpublic double forwardsReachAbstractRefine(PTA pta, BitSet targetLocs, Constraint targetConstraint, boolean min)\n\t\t\tthrows PrismException\n\t{\n\t\t// Store PTA/target info\n\t\tthis.pta = pta;\n\t\tthis.targetLocs = targetLocs;\n\t\tthis.targetConstraint = targetConstraint;\n\n\t\t// Execute abstraction-refinement loop\n\t\treturn abstractRefine(min);\n\t}\n\n\t// Implementation of initialise() for abstraction-refinement loop; see superclass for details \n\n\t@Override\n\tprotected void initialise() throws PrismException\n\t{\n\t\tForwardsReach forwardsReach;\n\t\tList<Integer> initialStates;\n\t\tint src, numStates;\n\n\t\t// Build forwards reachability graph\n\t\tforwardsReach = new ForwardsReach(mainLog);\n\t\tgraph = forwardsReach.buildForwardsGraph(pta, targetLocs, targetConstraint);\n\t\t// Store the set of target/initial states from forwards reachability\n\t\ttarget = forwardsReach.getTarget();\n\t\tinitialStates = forwardsReach.getInitialStates();\n\n\t\t// Compute validities for all symbolic transitions in the graph\n\t\tgraph.computeAllValidities();\n\n\t\t// Display states, graph, etc.\n\t\tif (verbosity >= 5) {\n\t\t\tmainLog.println(\"\\nStates: \");\n\t\t\tgraph.printStates(mainLog);\n\t\t\tmainLog.println(\"\\nGraph: \" + graph);\n\t\t\tmainLog.println(\"Target states: \" + target);\n\t\t}\n\n\t\t// Build empty game\n\t\tabstraction = new STPGAbstrSimple();\n\n\t\t// Add all states\n\t\tnumStates = graph.states.size();\n\t\tabstraction.addStates(numStates);\n\t\t// Set initial states\n\t\tfor (int i : initialStates) {\n\t\t\tabstraction.addInitialState(i);\n\t\t}\n\t\t// Build each state individually\n\t\tfor (src = 0; src < numStates; src++) {\n\t\t\tbuildSTPGState(src);\n\t\t}\n\t}\n\n\t// Implementation of rebuildAbstraction(...) for abstraction-refinement loop; see superclass for details \n\n\t@Override\n\tprotected void rebuildAbstraction(Set<Integer> rebuildStates) throws PrismException\n\t{\n\t\tfor (int src : rebuildStates) {\n\t\t\tabstraction.clearState(src);\n\t\t\tbuildSTPGState(src);\n\t\t}\n\t}\n\n\t/**\n\t * Build a single state of the STPG.\n\t */\n\tprotected void buildSTPGState(int src) throws PrismException\n\t{\n\t\tLocZone lz;\n\t\tNCZone z;\n\t\tArrayList<NCZone> valids;\n\t\tSymbolicTransition st;\n\t\tint i, numTransitions, numValids, map[];\n\n\t\t// Get state and num transitions\n\t\tlz = graph.states.get(src);\n\t\tnumTransitions = graph.trans.get(src).size();\n\n\t\t// Skip build of state if no transitions (should just be target states)\n\t\tif (numTransitions == 0) {\n\t\t\tif (!target.get(src))\n\t\t\t\tmainLog.printWarning(\"Building STPG state (\" + src + \") with no transitions\");\n\t\t\treturn;\n\t\t}\n\n\t\t// Compute validity of each outgoing transition from this state.\n\t\t// In fact, since guards for multiple transitions are often identical,\n\t\t// we only do this for distinct ones, and build a 'map' between them.\n\t\tvalids = new ArrayList<NCZone>(numTransitions);\n\t\tmap = new int[numTransitions];\n\t\tfor (i = 0; i < numTransitions; i++) {\n\t\t\tst = graph.trans.get(src).get(i);\n\t\t\tz = (NCZone) st.valid;\n\t\t\t// Check that validity constraint is non-empty\n\t\t\tif (z.isEmpty())\n\t\t\t\tthrow new PrismException(\"Found invalid symbolic transition\");\n\t\t\t// See if we already have a copy of this zone z\n\t\t\tmap[i] = valids.indexOf(z);\n\t\t\t// If not, add to list and store index in map\n\t\t\tif (map[i] == -1) {\n\t\t\t\tmap[i] = valids.size();\n\t\t\t\tvalids.add(z);\n\t\t\t}\n\t\t}\n\n\t\t// Recursive construction of this state\n\t\tnumValids = valids.size();\n\t\tbuildSTPGStateRec(src, new DBMList(lz.zone), new BitSet(numValids), valids, map, 0, numValids);\n\n\t\t// Check for deadlocks in the constructed STPG\n\t\t// (should never occur because of the restrictions we impose on PTAs)\n\t\tif (abstraction.getNumChoices(src) == 0) {\n\t\t\tthrow new PrismException(\"STPG has deadlock in state #\" + src + \":\" + graph.states.get(src));\n\t\t}\n\t}\n\n\t/**\n\t * Recursive construction of STPG state 'src'.\n\t * Consider each combination of outgoing transitions (combination stored in 'bitSet'),\n\t * and build validity constraint ('valid') for each combination.\n\t * (Note: actually only consider transitions with distinct validity - see above.)\n\t */\n\tprotected void buildSTPGStateRec(int src, NCZone valid, BitSet bitSet, ArrayList<NCZone> valids, int[] map,\n\t\t\tint level, int numValids) throws PrismException\n\t{\n\t\tSTPGAbstrSimple stpg;\n\t\tArrayList<SymbolicTransition> sts;\n\t\tDistributionSet distrSet;\n\t\tDistribution distr;\n\t\tBitSet actionBitSet = null;\n\t\tint count, i, dest;\n\n\t\t// Cast abstraction to STPG since we know the type\n\t\tstpg = (STPGAbstrSimple) abstraction;\n\n\t\t// Bottom of recursion: check if valid and, if so, add appropriate distribution set to game\n\t\tif (level == numValids) {\n\t\t\t// Check this combination of transitions is non-empty  \n\t\t\tif (!valid.isEmpty()) {\n\t\t\t\t// Ignore the case where no transitions are enabled\n\t\t\t\t// (has been dealt with earlier by adding explicit \"diverge\" transition)\n\t\t\t\tif (bitSet.cardinality() == 0)\n\t\t\t\t\treturn;\n\t\t\t\t// Create distribution set for this combination of transitions\n\t\t\t\tdistrSet = stpg.newDistributionSet(null);\n\t\t\t\t// If using BitSets for action labels (as opposed to storing the zones directly)\n\t\t\t\t// create a bit set that will represent the actual combination of transitions\n\t\t\t\t// (the bit set passed into this function is indexed over distinct validity transitions only)\n\t\t\t\tsts = graph.trans.get(src);\n\t\t\t\tif (!storeValidZones)\n\t\t\t\t\tactionBitSet = new BitSet(sts.size());\n\t\t\t\ti = 0;\n\t\t\t\tfor (SymbolicTransition st : sts) {\n\t\t\t\t\t// Add distribution corresponding to ith transition if\n\t\t\t\t\t// it is included in the set we are considering in this iteration\n\t\t\t\t\tif (bitSet.get(map[i])) {\n\t\t\t\t\t\tdistr = Distribution.ofDouble();\n\t\t\t\t\t\tcount = 0;\n\t\t\t\t\t\tfor (Edge edge : st.tr.getEdges()) {\n\t\t\t\t\t\t\tdest = st.dests[count];\n\t\t\t\t\t\t\tif (dest != -1)\n\t\t\t\t\t\t\t\tdistr.add(dest, edge.getProbability());\n\t\t\t\t\t\t\tcount++;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (!distr.isEmpty())\n\t\t\t\t\t\t\tdistrSet.add(distr);\n\t\t\t\t\t\t// If using BitSets for action labels, modify the bit set\n\t\t\t\t\t\t// (setting kth bit to denote that kth transition is included)\n\t\t\t\t\t\tif (!storeValidZones)\n\t\t\t\t\t\t\tactionBitSet.set(i);\n\t\t\t\t\t}\n\t\t\t\t\ti++;\n\t\t\t\t}\n\t\t\t\t// Set the (BitSet or Zone) action label for the distribution set and add it to the game\n\t\t\t\tif (storeValidZones)\n\t\t\t\t\tdistrSet.setAction(valid);\n\t\t\t\telse\n\t\t\t\t\tdistrSet.setAction(actionBitSet);\n\t\t\t\tstpg.addDistributionSet(src, distrSet);\n\t\t\t}\n\t\t} else {\n\t\t\t// Recursive step\n\t\t\t// Note that the construction of the validity constraint for\n\t\t\t// transition combinations is done recursively - this gives big gains in efficiency.\n\t\t\t// Note also that, the first thing added to the conjunction (i.e. the validity constraint)\n\t\t\t// before recursion starts is the symbolic state zone. We can only do this because at\n\t\t\t// least one transition is enabled in this combination, so its validity will need to include\n\t\t\t// the symbolic state zone. Generally, it is better to\n\t\t\t// add non-complemented zones, like this, early to avoid blowups\n\t\t\t// (in terms of conjunctions on complements, which are typically large DBM lists).\n\t\t\t// Finally, note that use of combined intersectComplement operation is, like\n\t\t\t// for the refinement state-split set, crucial for efficiency.\n\t\t\t// bitSet[level] = 0\n\t\t\tNCZone validNew;\n\t\t\tvalidNew = valid.deepCopy();\n\t\t\tvalidNew.intersectComplement(valids.get(level));\n\t\t\tbitSet.set(level, false);\n\t\t\tif (!validNew.isEmpty())\n\t\t\t\tbuildSTPGStateRec(src, validNew, bitSet, valids, map, level + 1, numValids);\n\t\t\t// bitSet[level] = 1\n\t\t\tvalidNew = valid.deepCopy();\n\t\t\tvalidNew.intersect(valids.get(level));\n\t\t\tbitSet.set(level, true);\n\t\t\tif (!validNew.isEmpty())\n\t\t\t\tbuildSTPGStateRec(src, validNew, bitSet, valids, map, level + 1, numValids);\n\t\t}\n\t}\n\n\t// Implementation of splitState(...) for abstraction-refinement loop; see superclass for details\n\n\t// Needs to update:\n\t//  - local storage about abstraction (i.e. states and symbolic transitions in reachability graph)\n\t//  - abstraction (new states, initial states and transitions)\n\t//  - target set \n\n\t@Override\n\tprotected int splitState(int splitState, List<List<Integer>> choiceLists, Set<Integer> rebuiltStates,\n\t\t\tSet<Integer> rebuildStates) throws PrismException\n\t{\n\t\tLocZone lzSplit;\n\t\tDBMList z, valid1;\n\t\tint[] newStateMap;\n\t\tint i, n, numStates, numNewStates, choiceCount;\n\t\tObject action;\n\t\tBitSet actionBitSet;\n\t\tArrayList<DBMList> partition;\n\t\tboolean rebuild;\n\n\t\t// Get abstract state to split \n\t\tlzSplit = graph.states.get(splitState);\n\t\tif (verbosity >= 1)\n\t\t\tmainLog.println(\"Splitting: #\" + splitState + \"=\" + lzSplit);\n\n\t\t// Compute zones that this state will be split into; store in 'partition'\n\t\tpartition = new ArrayList<DBMList>();\n\t\tchoiceCount = 0;\n\t\tfor (List<Integer> choiceList : choiceLists) {\n\t\t\tchoiceCount += choiceList.size();\n\t\t\tz = new DBMList(pta);\n\t\t\tfor (int in : choiceList) {\n\t\t\t\t// If using BitSets for action labels (i.e. have not cached zones for reuse)\n\t\t\t\t// need to build the corresponding zone\n\t\t\t\taction = ((STPGAbstrSimple) abstraction).getChoice(splitState, in).action;\n\t\t\t\tif (!storeValidZones) {\n\t\t\t\t\tactionBitSet = (BitSet) action;\n\t\t\t\t\tList<SymbolicTransition> sts = graph.trans.get(splitState);\n\t\t\t\t\tn = sts.size();\n\t\t\t\t\tSet<NCZone> valids = new LinkedHashSet<NCZone>();\n\t\t\t\t\tSet<NCZone> validCmpls = new LinkedHashSet<NCZone>();\n\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\tSymbolicTransition st = sts.get(i);\n\t\t\t\t\t\t// Store in appropriate set \n\t\t\t\t\t\t(actionBitSet.get(i) ? valids : validCmpls).add((DBMList) st.valid);\n\t\t\t\t\t}\n\t\t\t\t\t//log.println(\"valids: \" + valids);\n\t\t\t\t\t//log.println(\"validCmpls: \" + validCmpls);\n\t\t\t\t\t// Build zone\n\t\t\t\t\tvalid1 = new DBMList(DBM.createTrue(pta));\n\t\t\t\t\tfor (Zone z2 : valids) {\n\t\t\t\t\t\tvalid1.intersect(z2);\n\t\t\t\t\t}\n\t\t\t\t\tfor (NCZone z2 : validCmpls) {\n\t\t\t\t\t\tvalid1.intersectComplement(z2);\n\t\t\t\t\t}\n\t\t\t\t\tvalid1.intersect(lzSplit.zone);\n\t\t\t\t}\n\t\t\t\t// If using zones, then we just use the stored zone\n\t\t\t\telse {\n\t\t\t\t\tvalid1 = (DBMList) action;\n\t\t\t\t}\n\t\t\t\tz.addDBMs(valid1);\n\t\t\t}\n\t\t\tpartition.add(z);\n\t\t}\n\t\t// Compute zone for remainder of the partition\n\t\t// (NB: another way to do this is to build a union of remaining player 1 choices)\n\t\t// (but, empirically, this seems to be bad in terms of DBM list efficiency)\n\t\t// (Note, though, we can check whether we need to do this at all, which is good)\n\t\tif (choiceCount < abstraction.getNumChoices(splitState)) {\n\t\t\t// Compute union of all partition elements from above \n\t\t\tDBMList all = new DBMList(pta);\n\t\t\tfor (DBMList dbml : partition) {\n\t\t\t\tall.addDBMs(dbml.deepCopy());\n\t\t\t}\n\t\t\t// Subtract union from symbolic state zone \n\t\t\tDBMList rest = new DBMList(lzSplit.zone);\n\t\t\trest.intersectComplement(all);\n\t\t\tif (!rest.isEmpty())\n\t\t\t\tpartition.add(rest);\n\t\t}\n\t\t// Check we actually got a strict split of the partition\n\t\tif (partition.size() <= 1) {\n\t\t\tmainLog.printWarning(\"failed to split state #\" + splitState + \"=\" + lzSplit);\n\t\t\treturn 1;\n\t\t}\n\n\t\t// Update symbolic state set info (graph.states) and store info about indices of new states\n\t\tnumNewStates = partition.size();\n\t\tnewStateMap = new int[numNewStates];\n\t\tfor (i = 0; i < numNewStates; i++) {\n\t\t\t// First new state overwrites one that is being split\n\t\t\tif (i == 0) {\n\t\t\t\tgraph.states.set(splitState, new LocZone(lzSplit.loc, partition.get(i)));\n\t\t\t\tnewStateMap[i] = splitState;\n\t\t\t}\n\t\t\t// Other new states are appended to end of list\n\t\t\telse {\n\t\t\t\tgraph.states.add(new LocZone(lzSplit.loc, partition.get(i)));\n\t\t\t\tnewStateMap[i] = graph.states.size() - 1;\n\t\t\t\tgraph.copyState(splitState);\n\t\t\t}\n\t\t}\n\n\t\t// Display info\n\t\tif (verbosity >= 1) {\n\t\t\tmainLog.println(\"Splitting: #\" + splitState + \"=\" + lzSplit);\n\t\t\tmainLog.println(\"into \" + numNewStates + \":\");\n\t\t\tfor (i = 0; i < numNewStates; i++)\n\t\t\t\tmainLog.println(\"#\" + newStateMap[i] + \"=\" + partition.get(i));\n\t\t}\n\t\tif (verbosity >= 5)\n\t\t\tmainLog.println(\"New states: \" + graph.states);\n\n\t\t// Add new states to the abstraction\n\t\tabstraction.addStates(numNewStates - 1);\n\n\t\t// Add new states to initial state set if needed\n\t\t// Note: we assume any abstract state contains either all/no initial states\n\t\tif (abstraction.isInitialState(splitState)) {\n\t\t\tfor (i = 1; i < numNewStates; i++) {\n\t\t\t\tabstraction.addInitialState(newStateMap[i]);\n\t\t\t}\n\t\t}\n\n\t\t// Rebuild target states\n\t\tfor (i = 0; i < numNewStates; i++) {\n\t\t\tLocZone lz = graph.states.get(newStateMap[i]);\n\t\t\ttarget.set(newStateMap[i], isTarget(lz));\n\t\t}\n\n\t\t// Update symbolic transitions and abstraction\n\t\tSet<SymbolicTransition> oldSTs = new LinkedHashSet<SymbolicTransition>();\n\t\tSet<SymbolicTransition> newSTs = new LinkedHashSet<SymbolicTransition>();\n\t\t// Go through all abstract states\n\t\tnumStates = graph.states.size();\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\toldSTs.clear();\n\t\t\tnewSTs.clear();\n\t\t\t// Do we need to rebuild this state?\n\t\t\t// (i.e. is it a new state or a successor of the split state?)\n\t\t\trebuild = false;\n\t\t\t// For a new state...\n\t\t\tif (i == splitState || i > numStates - numNewStates) {\n\t\t\t\t// Split all symbolic transitions from this state\n\t\t\t\tfor (SymbolicTransition st : graph.trans.get(i)) {\n\t\t\t\t\toldSTs.add(st);\n\t\t\t\t\tsplitSymbolicTransition(i, st, splitState, newStateMap, newSTs);\n\t\t\t\t}\n\t\t\t\trebuild = true;\n\t\t\t}\n\t\t\t// For a successor state\n\t\t\telse {\n\t\t\t\t// Split symbolic transitions that go to the split state\n\t\t\t\tfor (SymbolicTransition st : graph.trans.get(i)) {\n\t\t\t\t\tif (st.hasSuccessor(splitState)) {\n\t\t\t\t\t\toldSTs.add(st);\n\t\t\t\t\t\tsplitSymbolicTransition(i, st, splitState, newStateMap, newSTs);\n\t\t\t\t\t\trebuild = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Bail out, if we didn't need to rebuild for this state\n\t\t\tif (!rebuild)\n\t\t\t\tcontinue;\n\t\t\t// Now, actually modify the graph\n\t\t\t// (didn't do this on the fly because don't went to change\n\t\t\t// the list that we are iterating over)\n\t\t\tfor (SymbolicTransition st : oldSTs)\n\t\t\t\tgraph.trans.get(i).remove(st);\n\t\t\tfor (SymbolicTransition st : newSTs)\n\t\t\t\tgraph.trans.get(i).add(st);\n\t\t\tif ((verbosity >= 1) && !oldSTs.isEmpty()) {\n\t\t\t\tmainLog.print(\"Replacing symbolic transitions: \" + i + \":\" + oldSTs);\n\t\t\t\tmainLog.println(\" with: \" + i + \":\" + newSTs);\n\t\t\t}\n\t\t\t// Rebuild this state of the abstraction\n\t\t\tabstraction.clearState(i);\n\t\t\tbuildSTPGState(i);\n\t\t\trebuiltStates.add(i);\n\t\t}\n\n\t\tif (verbosity >= 5) {\n\t\t\tmainLog.println(\"New graph: \" + graph);\n\t\t}\n\n\t\treturn numNewStates;\n\t}\n\n\t/**\n\t * Split a symbolic transition, based on the division of a symbolic state into several parts.\n\t * @param src: The source of the symbolic transition to be split \n\t * @param st: The symbolic transition to be split\n\t * @param splitState: The index of the symbolic state that is being split \n\t * @param newStateMap: The indices of the new states\n\t * @param newSTs: Where to put the new symbolic transitions\n\t */\n\tprivate void splitSymbolicTransition(int src, SymbolicTransition st, int splitState, int newStateMap[],\n\t\t\tSet<SymbolicTransition> newSTs)\n\t{\n\t\t// Take a copy of the transition, because we will modify it when analysing it\n\t\tSymbolicTransition stNew = new SymbolicTransition(st);\n\t\t// Recursively...\n\t\tsplitSymbolicTransition(src, stNew, splitState, newStateMap, newSTs, 0, st.dests.length);\n\t}\n\n\tprivate void splitSymbolicTransition(int src, SymbolicTransition st, int splitState, int newStateMap[],\n\t\t\tSet<SymbolicTransition> newSTs, int level, int n)\n\t{\n\t\tif (level == n) {\n\t\t\tZone valid = graph.computeValidity(src, st.tr, st.dests);\n\t\t\tif (!valid.isEmpty()) {\n\t\t\t\tSymbolicTransition stNew = new SymbolicTransition(st);\n\t\t\t\tstNew.valid = valid;\n\t\t\t\tnewSTs.add(stNew);\n\t\t\t}\n\t\t} else {\n\t\t\tif (st.dests[level] == splitState) {\n\t\t\t\tint m = newStateMap.length;\n\t\t\t\tfor (int i = 0; i < m; i++) {\n\t\t\t\t\tst.dests[level] = newStateMap[i];\n\t\t\t\t\tsplitSymbolicTransition(src, st, splitState, newStateMap, newSTs, level + 1, n);\n\t\t\t\t}\n\t\t\t\tst.dests[level] = splitState;\n\t\t\t} else {\n\t\t\t\tsplitSymbolicTransition(src, st, splitState, newStateMap, newSTs, level + 1, n);\n\t\t\t}\n\t\t}\n\t}\n\n\t// TODO: why does this not work?\n\tprivate Zone valid2new(LocZone lz, Transition tr, int[] dests)\n\t{\n\t\tint count;\n\t\tZone z, z2;\n\n\t\tz = new DBMList(DBM.createTrue(pta));\n\t\t// Conjunction over edges in transition\n\t\tcount = 0;\n\t\tfor (Edge edge : tr.getEdges()) {\n\t\t\t// Get (copy of) edge target\n\t\t\tz2 = graph.states.get(dests[count]).zone.deepCopy();\n\t\t\t// Backwards reset of clocks for edge\n\t\t\tfor (Map.Entry<Integer, Integer> e : edge.getResets()) {\n\t\t\t\tz2.backReset(e.getKey(), e.getValue());\n\t\t\t}\n\t\t\t// Intersect\n\t\t\tz.intersect(z2);\n\t\t\tcount++;\n\t\t}\n\t\t// Intersect with transition guard \n\t\tfor (Constraint c : tr.getGuardConstraints()) {\n\t\t\tz.addConstraint(c);\n\t\t}\n\t\t// Time pre\n\t\tz.down();\n\t\t// Intersect with symbolic state zone\n\t\tz.intersect(lz.zone);\n\n\t\treturn z;\n\t}\n\n\tprivate boolean isTarget(LocZone lz)\n\t{\n\t\treturn targetLocs.get(lz.loc) && (targetConstraint == null || lz.zone.isSatisfied(targetConstraint));\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/PTAModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\nimport parser.*;\nimport parser.ast.*;\nimport parser.type.*;\nimport parser.visitor.ASTTraverseModify;\nimport prism.*;\nimport simulator.ModulesFileModelGenerator;\n\n/**\n * Model checker for probabilistic timed automata (PTAs).\n */\npublic class PTAModelChecker extends PrismComponent\n{\n\t// Model file\n\tprivate ModulesFile modulesFile;\n\t// Properties file\n\tprivate PropertiesFile propertiesFile;\n\t// Constants from model\n\tprivate Values constantValues;\n\t// Label list (combined: model/properties file)\n\tprivate LabelList labelList;\n\t// PTA\n\tprivate PTA pta;\n\n\t/**\n\t * Constructor.\n\t */\n\tpublic PTAModelChecker(PrismComponent parent, ModulesFile modulesFile, PropertiesFile propertiesFile) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tthis.modulesFile = modulesFile;\n\t\tthis.propertiesFile = propertiesFile;\n\n\t\t// Get combined constant values from model/properties\n\t\tconstantValues = new Values();\n\t\tconstantValues.addValues(modulesFile.getConstantValues());\n\t\tif (propertiesFile != null)\n\t\t\tconstantValues.addValues(propertiesFile.getConstantValues());\n\n\t\t// Build a combined label list and expand any constants\n\t\t// (note labels in model are ignored (removed) during PTA translation so need to store here)\n\t\tlabelList = new LabelList();\n\t\tfor (int i = 0; i < modulesFile.getLabelList().size(); i++) {\n\t\t\tlabelList.addLabel(modulesFile.getLabelList().getLabelNameIdent(i), modulesFile.getLabelList().getLabel(i).deepCopy());\n\t\t}\n\t\tfor (int i = 0; i < propertiesFile.getLabelList().size(); i++) {\n\t\t\tlabelList.addLabel(propertiesFile.getLabelList().getLabelNameIdent(i), propertiesFile.getLabelList().getLabel(i).deepCopy());\n\t\t}\n\t\tlabelList = (LabelList) labelList.replaceConstants(constantValues);\n\t}\n\n\t/**\n\t * Model check a property.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic Result check(Expression expr) throws PrismException\n\t{\n\t\tResult res;\n\t\tString resultString;\n\t\tlong timer;\n\n\t\t// Starting model checking\n\t\ttimer = System.currentTimeMillis();\n\n\t\t// Build a model generator\n\t\tModelGenerator<Double> modelGen;\n\t\ttry {\n\t\t\tmodelGen = (ModelGenerator<Double>) ModulesFileModelGenerator.create(modulesFile, this);\n\t\t} catch (PrismException e) {\n\t\t\tthrow new PrismException(e.getMessage() + \". Try the digital clocks engine instead\");\n\t\t}\n\t\t\n\t\t// Translate ModulesFile object into a PTA object\n\t\t// Technically, this just requires a ModelGenerator,\n\t\t// but for now we assume a ModulesFile for the purposes of labels\n\t\tmainLog.println(\"\\nBuilding PTA...\");\n\t\tConstructPTA constructPTA = new ConstructPTA(this);\n\t\tpta = constructPTA.constructPTA(modelGen);\n\t\tmainLog.println(\"\\nPTA: \" + pta.infoString());\n\n\t\t// Check for references to clocks - not allowed (yet)\n\t\t// (do this before modifications below for better error reporting)\n\t\texpr.accept(new ASTTraverseModify()\n\t\t{\n\t\t\tpublic Object visit(ExpressionVar e) throws PrismLangException\n\t\t\t{\n\t\t\t\tif (e.getType() instanceof TypeClock) {\n\t\t\t\t\tthrow new PrismLangException(\"Properties cannot contain references to clocks (try the digital clocks engine instead)\", e);\n\t\t\t\t} else {\n\t\t\t\t\treturn e;\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\t\n\t\t// Take a copy of property, since will modify\n\t\texpr = expr.deepCopy();\n\t\t// Remove property refs ands labels from property \n\t\texpr = (Expression) expr.expandPropRefsAndLabels(propertiesFile, labelList);\n\t\t// Evaluate constants in property (easier to do now)\n\t\texpr = (Expression) expr.replaceConstants(constantValues);\n\t\t// Also simplify expression to optimise model checking\n\t\texpr = (Expression) expr.simplify();\n\n\t\t// Do model checking\n\t\tres = checkExpression(expr);\n\n\t\t// Model checking complete\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"\\nModel checking completed in \" + (timer / 1000.0) + \" secs.\");\n\n\t\t// Print result to log\n\t\tresultString = \"Result\";\n\t\tif (!(\"Result\".equals(expr.getResultName())))\n\t\t\tresultString += \" (\" + expr.getResultName().toLowerCase() + \")\";\n\t\tresultString += \": \" + res;\n\t\tmainLog.print(\"\\n\" + resultString + \"\\n\");\n\n\t\t// Return result\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check an expression (used recursively).\n\t */\n\tprivate Result checkExpression(Expression expr) throws PrismException\n\t{\n\t\tResult res;\n\n\t\t// Current range of supported properties is quite limited...\n\t\tif (expr instanceof ExpressionProb)\n\t\t\tres = checkExpressionProb((ExpressionProb) expr);\n\t\telse if (expr instanceof ExpressionReward)\n\t\t\tres = checkExpressionReward((ExpressionReward) expr);\n\t\telse if (expr instanceof ExpressionFilter)\n\t\t\tthrow new PrismException(\"PTA model checker does not handle filters since it only computes values for the initial state\");\n\t\telse\n\t\t\tthrow new PrismException(\"PTA model checking not yet supported for this operator (try the digital clocks engine)\");\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check a P operator.\n\t */\n\tprivate Result checkExpressionProb(ExpressionProb expr) throws PrismException\n\t{\n\t\tboolean min;\n\t\tExpressionTemporal exprTemp;\n\t\tExpression exprTarget;\n\t\tBitSet targetLocs;\n\t\tint timeBound;\n\t\tboolean timeBoundStrict;\n\t\tdouble prob;\n\n\t\t// Check whether Pmin=? or Pmax=? (only two cases allowed)\n\t\tRelOp relOp = expr.getRelOp();\n\t\tif (expr.getProb() != null) {\n\t\t\tthrow new PrismException(\"PTA model checking currently only supports Pmin=? and Pmax=? properties (try the digital clocks engine instead)\");\n\t\t}\n\t\tmin = relOp.isLowerBound() || relOp.isMin();\n\n\t\t// Check this is a F path property (only case allowed at the moment)\n\t\tif (!(expr.getExpression() instanceof ExpressionTemporal))\n\t\t\tthrow new PrismException(\"PTA model checking currently only supports the F path operator (try the digital clocks engine instead)\");\n\t\texprTemp = (ExpressionTemporal) expr.getExpression();\n\t\tif (exprTemp.getOperator() != ExpressionTemporal.P_F || !exprTemp.isSimplePathFormula())\n\t\t\tthrow new PrismException(\"PTA model checking currently only supports the F path operator (try the digital clocks engine instead)\");\n\t\t\n\t\t// Determine locations satisfying target\n\t\texprTarget = exprTemp.getOperand2();\n\t\ttargetLocs = checkLocationExpression(exprTarget);\n\t\tmainLog.println(\"Target (\" + exprTarget + \") satisfied by \" + targetLocs.cardinality() + \" locations.\");\n\t\t//mainLog.println(targetLocs);\n\n\t\t// If there is a time bound, add a clock and encode this into target\n\t\tif (exprTemp.hasBounds()) {\n\t\t\tmainLog.println(\"Modifying PTA to encode time bound from property...\");\n\t\t\t// Get time bound info (is always of form <=T or <T)\n\t\t\ttimeBound = exprTemp.getUpperBound().evaluateInt(constantValues);\n\t\t\ttimeBoundStrict = exprTemp.upperBoundIsStrict();\n\t\t\t// Check for non-allowed time bounds (negative)\n\t\t\tif (timeBound < (timeBoundStrict ? 1 : 0)) {\n\t\t\t\tthrow new PrismLangException(\"Negative bound in \" + exprTemp);\n\t\t\t}\n\t\t\t// Modify PTA to include time bound; get new target\n\t\t\ttargetLocs = buildTimeBoundIntoPta(pta, targetLocs, timeBound, timeBoundStrict);\n\t\t\tmainLog.println(\"New PTA: \" + pta.infoString());\n\t\t}\n\n\t\t// Compute probability of reaching the set of target locations\n\t\tprob = computeProbabilisticReachability(targetLocs, min);\n\n\t\t// Return result\n\t\treturn new Result(prob);\n\t}\n\n\t/**\n\t * Build a time bounded reachability query into a PTA; return the new target location set.  \n\t */\n\tprivate BitSet buildTimeBoundIntoPta(PTA pta, BitSet targetLocs, int timeBound, boolean timeBoundStrict)\n\t{\n\t\tString timerClock = null;\n\t\tint timerClockIndex, numLocs, newTargetLoc;\n\t\tString newTargetLocString;\n\t\tList<Transition> trNewList;\n\t\tTransition trNew;\n\t\tBitSet targetLocsNew;\n\t\tboolean toTarget;\n\t\tint i;\n\n\t\t// Add a timer clock\n\t\ttimerClock = \"time\";\n\t\twhile (pta.getClockIndex(timerClock) != -1)\n\t\t\ttimerClock += \"_\";\n\t\ttimerClockIndex = pta.addClock(timerClock);\n\t\t// Add a new target location\n\t\tnumLocs = pta.getNumLocations();\n\t\tnewTargetLocString = \"target\";\n\t\twhile (pta.getLocationIndex(newTargetLocString) != -1)\n\t\t\tnewTargetLocString += \"_\";\n\t\tnewTargetLoc = pta.addLocation(newTargetLocString);\n\t\t// Go through old (on-target) locations\n\t\tfor (i = 0; i < numLocs; i++) {\n\t\t\ttrNewList = new ArrayList<>();\n\t\t\tfor (Transition tr : pta.getTransitions(i)) {\n\t\t\t\t// See if the transition can go to a target location \n\t\t\t\ttoTarget = false;\n\t\t\t\tfor (Edge e : tr.getEdges()) {\n\t\t\t\t\tif (targetLocs.get(e.getDestination())) {\n\t\t\t\t\t\ttoTarget = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Copy transition, modify edges going to target and add guard \n\t\t\t\tif (toTarget) {\n\t\t\t\t\ttrNew = new Transition(tr);\n\t\t\t\t\tfor (Edge e : trNew.getEdges()) {\n\t\t\t\t\t\tif (targetLocs.get(e.getDestination())) {\n\t\t\t\t\t\t\te.setDestination(newTargetLoc);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (timeBoundStrict)\n\t\t\t\t\t\ttrNew.addGuardConstraint(Constraint.buildLt(timerClockIndex, timeBound));\n\t\t\t\t\telse\n\t\t\t\t\t\ttrNew.addGuardConstraint(Constraint.buildLeq(timerClockIndex, timeBound));\n\t\t\t\t\ttrNewList.add(trNew);\n\t\t\t\t\t// Modify guard of copied transition\n\t\t\t\t\tif (timeBoundStrict)\n\t\t\t\t\t\ttr.addGuardConstraint(Constraint.buildGeq(timerClockIndex, timeBound));\n\t\t\t\t\telse\n\t\t\t\t\t\ttr.addGuardConstraint(Constraint.buildGt(timerClockIndex, timeBound));\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Add new transitions to PTA\n\t\t\tfor (Transition tr : trNewList) {\n\t\t\t\tpta.addTransition(tr);\n\t\t\t}\n\t\t}\n\t\t// Re-generate set of target locations\n\t\t// (newly added target location, plus initial location (always 0) is this is a target)\n\t\ttargetLocsNew = new BitSet(pta.getNumLocations());\n\t\ttargetLocsNew.set(newTargetLoc);\n\t\tif (targetLocs.get(0)) {\n\t\t\ttargetLocsNew.set(0);\n\t\t}\n\n\t\treturn targetLocsNew;\n\t}\n\n\t/**\n\t * Compute the min/max probability, from the initial state, of reaching a set of target locations.\n\t */\n\tprivate double computeProbabilisticReachability(BitSet targetLocs, boolean min) throws PrismException\n\t{\n\t\t// Catch the special case where the initial state is already a target - just return 1.0 directly\n\t\tif (targetLocs.get(0)) {\n\t\t\tmainLog.println(\"Skipping numerical computation since initial state is a target...\");\n\t\t\treturn 1.0;\n\t\t}\n\t\t\n\t\t// Determine which method to use for computation\n\t\tString ptaMethod = settings.getString(PrismSettings.PRISM_PTA_METHOD);\n\n\t\t// Do probability computation through abstraction/refinement/stochastic games  \n\t\tif (ptaMethod.equals(\"Stochastic games\")) {\n\t\t\tPTAAbstractRefine ptaAR;\n\t\t\tptaAR = new PTAAbstractRefine(this);\n\t\t\tString arOptions = settings.getString(PrismSettings.PRISM_AR_OPTIONS);\n\t\t\tptaAR.parseOptions(arOptions.split(\",\"));\n\t\t\treturn ptaAR.forwardsReachAbstractRefine(pta, targetLocs, null, min);\n\t\t}\n\n\t\t// Do probability computation through backwards reachability  \n\t\telse if (ptaMethod.equals(\"Backwards reachability\")) {\n\t\t\tBackwardsReach ptaBw = new BackwardsReach(this);\n\t\t\treturn ptaBw.computeProbabilisticReachability(pta, targetLocs, min);\n\t\t}\n\n\t\telse\n\t\t\tthrow new PrismException(\"Unknown PTA solution method\");\n\t}\n\n\t/**\n\t * Model check an R operator.\n\t */\n\tprivate Result checkExpressionReward(ExpressionReward expr) throws PrismException\n\t{\n\t\tthrow new PrismException(\"Reward properties not yet supported for PTA model checking (try the digital clocks engine instead)\");\n\t}\n\n\t/**\n\t * Determine which locations in the PTA satisfy a (Boolean) expression.\n\t * Note: This is rather inefficiently at the moment.\n\t * TODO: potentially use explicit.StateMC on dummy model eventually\n\t */\n\tprivate BitSet checkLocationExpression(Expression expr) throws PrismException\n\t{\n\t\tint i, n;\n\t\tBitSet res;\n\n\t\t// Labels - expand and recurse\n\t\t// (note: currently not used - these are expanded earlier)\n\t\tif (expr instanceof ExpressionLabel) {\n\t\t\tExpressionLabel exprLabel = (ExpressionLabel) expr;\n\t\t\tif (exprLabel.isDeadlockLabel())\n\t\t\t\tthrow new PrismException(\"The \\\"deadlock\\\" label is not yet supported for PTAs\");\n\t\t\tif (exprLabel.isInitLabel())\n\t\t\t\tthrow new PrismException(\"The \\\"init\\\" label is not yet supported for PTAs\");\n\t\t\ti = labelList.getLabelIndex(exprLabel.getName());\n\t\t\tif (i == -1)\n\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + exprLabel.getName() + \"\\\" in property\");\n\t\t\t// Check recursively\n\t\t\treturn checkLocationExpression(labelList.getLabel(i));\n\n\t\t}\n\t\t// Other expressions...\n\t\telse {\n\t\t\tList<Object> states;\n\t\t\t//Object[] state;\n\t\t\tstates = pta.getLocationNameList();\n\t\t\tn = states.size();\n\t\t\tres = new BitSet(n);\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t//state = (Object[])states.get(i);\n\t\t\t\tState state = (State) states.get(i);\n\t\t\t\tif (expr.evaluateBoolean(state)) {\n\t\t\t\t\tres.set(i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn res;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/PTAModelCheckerCL.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.io.*;\nimport java.util.*;\n\nimport explicit.MDP;\nimport explicit.MDPModelChecker;\n\nimport prism.PrismException;\n\n/**\n * Command-line interface to PTA model checker.\n */\npublic class PTAModelCheckerCL\n{\n\t// Inputs\n\n\t// List of PTA files\n\tArrayList<String> ptaFiles;\n\t// Target info\n\tString targetLocString, targetConstraintString;\n\n\t// Flags, settings\n\n\t// Compute min probabilities? (as opposed to max)\n\tboolean min = false;\n\t// Export the parallel composition PTA after construction?\n\tboolean exportPTA = false;\n\t// Do MDP forward reach rather than abstraction-refinement?\n\tboolean mdpReach = false;\n\n\t// Processed target info\n\tString targetLocRegexp;\n\tConstraint targetConstraint;\n\tBitSet targetLocs;\n\t// PTAs\n\tPTA pta, pta2;\n\t// Abstraction refinement object\n\tPTAAbstractRefine abstractRefine;\n\n\t/**\n\t * Main method\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tnew PTAModelCheckerCL().go(args);\n\t}\n\n\t/**\n\t * Main method\n\t */\n\tpublic void go(String args[])\n\t{\n\t\tint i, n, z;\n\t\tboolean found;\n\n\t\ttry {\n\n\t\t\t// Build PTAAbstractRefine object\n\t\t\tabstractRefine = new PTAAbstractRefine(null);\n\n\t\t\t// Parse command-line arguments\n\t\t\tparseCommandLineArgs(args);\n\t\t\t\n\t\t\t// Process target info\n\t\t\t// Strip any accidental quotes\n\t\t\ttargetLocString = targetLocString.replaceAll(\"['\\\"]\", \"\");\n\t\t\ttargetConstraintString = targetConstraintString.replaceAll(\"['\\\"]\", \"\");\n\t\t\t// Build regexp for target location spec \n\t\t\tString targetLocStringSplit[] = targetLocString.split(\",\");\n\t\t\ttargetLocRegexp = \"\";\n\t\t\tfor (String targetLocStringBit : targetLocStringSplit) {\n\t\t\t\tif (!(\"\".equals(targetLocRegexp)))\n\t\t\t\t\ttargetLocRegexp += \"|\";\n\t\t\t\ttargetLocRegexp += \"(\" + targetLocStringBit.replaceAll(\"\\\\*\", \"[a-zA-Z0-9_]*\") + \")\";\n\n\t\t\t}\n\t\t\t//System.out.print(\"Target locations regexp: \" + targetLocRegexp);\n\n\t\t\t// Display command-line arguments and settings:\n\t\t\tSystem.out.print(\"Command:\");\n\t\t\tfor (i = 0; i < args.length; i++)\n\t\t\t\tSystem.out.print(\" \" + args[i]);\n\t\t\tSystem.out.println();\n\t\t\tabstractRefine.printSettings();\n\t\t\t\n\t\t\t// Expand any input files that are lists of PTAs\n\t\t\tprocessPTAFiles();\n\t\t\t\n\t\t\t// Build PTA\n\t\t\tSystem.out.println(\"\\nBuilding PTA from \\\"\" + ptaFiles.get(0) + \"\\\"\");\n\t\t\tpta = PTA.buildPTAFromDesFile(ptaFiles.get(0));\n\t\t\tSystem.out.println(pta.infoString());\n\t\t\t//System.out.println(pta);\n\t\t\tfor (i = 1; i < ptaFiles.size(); i++) {\n\t\t\t\tSystem.out.println(\"Building PTA from \\\"\" + ptaFiles.get(i) + \"\\\"\");\n\t\t\t\tpta2 = PTA.buildPTAFromDesFile(ptaFiles.get(i));\n\t\t\t\tSystem.out.println(pta2.infoString());\n\t\t\t\t//System.out.println(pta2);\n\t\t\t\tpta = new PTAParallel().compose(pta, pta2);\n\t\t\t\t//System.out.println(pta);\n\t\t\t}\n\t\t\tSystem.out.println(\"Final PTA: \" + pta.infoString());\n\t\t\t//System.out.println(pta);\n\t\t\t// Do some checks on PTA\n\t\t\tpta.check();\n\t\t\t// Export PTA if required\n\t\t\tif (exportPTA)\n\t\t\t\tpta.writeToDesFile(\"par.des\");\n\t\t\t\n\t\t\t// Parse target clock constraint\n\t\t\tif (targetConstraintString.equals(\"true\")) {\n\t\t\t\ttargetConstraint = null;\n\t\t\t} else {\n\t\t\t\tz = pta.getOrAddClock(targetConstraintString.substring(0, 1));\n\t\t\t\tif (targetConstraintString.indexOf(\">=\", 1) != -1)\n\t\t\t\t\ttargetConstraint = Constraint.buildGeq(z, Integer.parseInt(targetConstraintString.substring(3)));\n\t\t\t\telse if (targetConstraintString.indexOf(\"<=\", 1) != -1)\n\t\t\t\t\ttargetConstraint = Constraint.buildLeq(z, Integer.parseInt(targetConstraintString.substring(3)));\n\t\t\t\telse if (targetConstraintString.indexOf(\">\", 1) != -1)\n\t\t\t\t\ttargetConstraint = Constraint.buildGt(z, Integer.parseInt(targetConstraintString.substring(2)));\n\t\t\t\telse if (targetConstraintString.indexOf(\"<\", 1) != -1)\n\t\t\t\t\ttargetConstraint = Constraint.buildLt(z, Integer.parseInt(targetConstraintString.substring(2)));\n\t\t\t\telse\n\t\t\t\t\ttargetConstraint = null;\n\t\t\t}\n\t\t\t// Determine PTA locations satisfying target specification; check non-empty\n\t\t\tn = pta.getNumLocations();\n\t\t\ttargetLocs = new BitSet(n);\n\t\t\tfound = false;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t// Since we build from des files here, PTA names are strings\n\t\t\t\tif (((String) pta.getLocationName(i)).matches(targetLocRegexp)) {\n\t\t\t\t\ttargetLocs.set(i);\n\t\t\t\t\tfound |= true;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!found)\n\t\t\t\tthrow new PrismException(\"No matches for PTA target location specification \" + targetLocString);\n\n\t\t\t// Display final target info\n\t\t\tSystem.out.print(\"\\nTarget locations: \" + targetLocString);\n\t\t\tSystem.out.println(\" (\" + targetLocs.cardinality() + \" locations)\");\n\t\t\tSystem.out.println(\"Target constraint: \"\n\t\t\t\t\t+ (targetConstraint == null ? \"true\" : targetConstraint.toString(pta)));\n\n\t\t\t// Do forward reach\n\t\t\t// Default case: use game-based abstraction refinement\n\t\t\tif (!mdpReach) {\n\t\t\t\tabstractRefine.forwardsReachAbstractRefine(pta, targetLocs, targetConstraint, min);\n\t\t\t}\n\t\t\t// But we can also just do standard MDP-based forwards reachability\n\t\t\telse {\n\t\t\t\tForwardsReach forwardsReach = new ForwardsReach();\n\t\t\t\tReachabilityGraph graph = forwardsReach.buildForwardsGraph(pta, targetLocs, targetConstraint);\n\t\t\t\tMDP<Double> mdp = graph.buildMDP(forwardsReach.getInitialStates());\n\t\t\t\tnew MDPModelChecker(null).computeReachProbs(mdp, forwardsReach.getTarget(), min);\n\t\t\t}\n\n\t\t} catch (PrismException e) {\n\t\t\tSystem.err.println(\"\\nError: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t/**\n\t * Parse command-line arguments\n\t */\n\tprivate void parseCommandLineArgs(String args[]) throws PrismException\n\t{\n\t\tint i;\n\t\tString s;\n\n\t\tif (args.length < 3) {\n\t\t\tSystem.err.println(\"Usage: ptamc [options] <des files> <target loc> <target constraint>\");\n\t\t\tSystem.exit(1);\n\t\t}\n\n\t\tptaFiles = new ArrayList<>();\n\t\tfor (i = 0; i < args.length; i++) {\n\t\t\ts = args[i];\n\t\t\t// Process a switch\n\t\t\tif (s.charAt(0) == '-') {\n\t\t\t\ts = s.substring(1);\n\t\t\t\t\n\t\t\t\t// Local options\n\t\t\t\tif (s.equals(\"min\")) {\n\t\t\t\t\tmin = true;\n\t\t\t\t} else if (s.equals(\"max\")) {\n\t\t\t\t\tmin = false;\n\t\t\t\t} else if (s.equals(\"exportpta\")) {\n\t\t\t\t\texportPTA = true;\n\t\t\t\t} else if (s.equals(\"mdp\")) {\n\t\t\t\t\tmdpReach = true;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Otherwise, try passing to abstraction-refinement engine\n\t\t\t\telse {\n\t\t\t\t\tabstractRefine.parseOption(s);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// If not a switch, must be a PTA filename\n\t\t\telse {\n\t\t\t\tptaFiles.add(s);\n\t\t\t}\n\t\t}\n\t\t// Last two arguments are actually target info, not PTA files\n\t\ttargetLocString = ptaFiles.get(ptaFiles.size() - 2);\n\t\ttargetConstraintString = ptaFiles.get(ptaFiles.size() - 1);\n\t\tptaFiles.remove(ptaFiles.size() - 1);\n\t\tptaFiles.remove(ptaFiles.size() - 1);\n\t}\n\t\n\t/**\n\t * Expand any input files that are lists of PTAs. \n\t */\n\tprivate void processPTAFiles() throws PrismException\n\t{\n\t\tString s;\n\t\t\n\t\tArrayList<String> ptaFilesNew = new ArrayList<>();\n\t\tfor (String ptaFile : ptaFiles) {\n\t\t\tif (ptaFile.endsWith(\".deslist\")) {\n\t\t\t\ttry {\n\t\t\t\t\tBufferedReader in = new BufferedReader(new FileReader(new File(ptaFile)));\n\t\t\t\t\twhile ((s = in.readLine()) != null) {\n\t\t\t\t\t\ts = s.trim();\n\t\t\t\t\t\tif (s.equals(\"\"))\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t// Absolute filename\n\t\t\t\t\t\tif (new File(s).isAbsolute()) {\n\t\t\t\t\t\t\tptaFilesNew.add(s);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// Relative filename\n\t\t\t\t\t\telse if (new File(ptaFile).getParent() != null) {\n\t\t\t\t\t\t\tptaFilesNew.add(new File(ptaFile).getParent() + File.separator + s);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// Current directory\n\t\t\t\t\t\telse {\n\t\t\t\t\t\t\tptaFilesNew.add(s);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} catch (IOException e) {\n\t\t\t\t\tthrow new PrismException(\"Could not read from file \\\"\" + ptaFile + \"\\\"\");\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tptaFilesNew.add(ptaFile);\n\t\t\t}\n\t\t}\n\t\tptaFiles = ptaFilesNew;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/PTAParallel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\nimport prism.PrismException;\nimport explicit.IndexedSet;\nimport explicit.StateStorage;\n\n/**\n * Class to perform the parallel composition of PTAs.\n */\npublic class PTAParallel\n{\n\t// All states\n\tprivate StateStorage<IndexPair> states;\n\t// States to be explored\n\tprivate LinkedList<IndexPair> explore;\n\t// Component PTAs\n\tprivate PTA pta1;\n\tprivate PTA pta2;\n\t// Resulting PTA (parallel composition)\n\tprivate PTA par;\n\t\n\t/**\n\t * Construct the parallel composition of two PTAs.\n\t */\n\tpublic PTA compose(PTA pta1, PTA pta2)\n\t{\n\t\tTransition transition;\n\t\tEdge edge;\n\t\tdouble prob;\n\t\tIndexPair state;\n\t\tint src, dest;\n\n\t\t// Store PTAs locally\n\t\tthis.pta1 = pta1;\n\t\tthis.pta2 = pta2;\n\n\t\t// Get alphabets, compute intersection, union etc.\n\t\tList<String> alpha1 = pta1.getAlphabet();\n\t\tList<String> alpha2 = pta2.getAlphabet();\n\t\tLinkedHashSet<String> sync = new LinkedHashSet<String>();\n\t\tLinkedHashSet<String> alpha1only = new LinkedHashSet<String>();\n\t\tLinkedHashSet<String> alpha2only = new LinkedHashSet<String>();\n\t\tList<String> alphaUnion = new ArrayList<String>(pta1.getAlphabet());\n\t\tfor (String a : alpha1) {\n\t\t\tif (!(\"\".equals(a)) && alpha2.contains(a)) {\n\t\t\t\tsync.add(a);\n\t\t\t} else {\n\t\t\t\talpha1only.add(a);\n\t\t\t}\n\t\t}\n\t\tfor (String a : alpha2) {\n\t\t\tif (!alpha1.contains(a)) {\n\t\t\t\talpha2only.add(a);\n\t\t\t\talphaUnion.add(a);\n\t\t\t}\n\t\t}\n\t\t// Explicitly add tau to action lists\n\t\talpha1only.add(\"\");\n\t\talpha2only.add(\"\");\n\n\t\t// Create new PTA to store parallel composition\n\t\tpar = new PTA(alphaUnion);\n\n\t\t// New set of clocks is union of sets for two PTAs\n\t\tfor (String s : pta1.clockNames) {\n\t\t\tpar.getOrAddClock(s);\n\t\t}\n\t\tfor (String s : pta2.clockNames) {\n\t\t\tpar.getOrAddClock(s);\n\t\t}\n\n\t\t// Initialise states storage\n\t\tstates = new IndexedSet<IndexPair>();\n\t\texplore = new LinkedList<IndexPair>();\n\t\t// Add initial location\n\t\taddState(0, 0);\n\t\tsrc = -1;\n\t\twhile (!explore.isEmpty()) {\n\t\t\t// Pick next state to explore\n\t\t\t// (they are stored in order found so know index is src+1)\n\t\t\tstate = explore.removeFirst();\n\t\t\tsrc++;\n\t\t\t// Go through asynchronous transitions of PTA 1\n\t\t\tfor (String a : alpha1only) {\n\t\t\t\tfor (Transition transition1 : pta1.getTransitionsByAction(state.i1, a)) {\n\t\t\t\t\t// Create new transition\n\t\t\t\t\ttransition = par.addTransition(src, a);\n\t\t\t\t\t// Copy guard\n\t\t\t\t\tfor (Constraint c : transition1.getGuardConstraints())\n\t\t\t\t\t\ttransition.addGuardConstraint(c.deepCopy().renameClocks(pta1, par));\n\t\t\t\t\t// Combine edges\n\t\t\t\t\tfor (Edge edge1 : transition1.getEdges()) {\n\t\t\t\t\t\tprob = edge1.getProbability();\n\t\t\t\t\t\tdest = addState(edge1.getDestination(), state.i2);\n\t\t\t\t\t\tedge = transition.addEdge(prob, dest);\n\t\t\t\t\t\t// Copy resets\n\t\t\t\t\t\tfor (Map.Entry<Integer, Integer> e : edge1.getResets()) {\n\t\t\t\t\t\t\tedge.addReset(PTA.renameClock(pta1, par, e.getKey()), e.getValue());\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Go through asynchronous transitions of PTA 2\n\t\t\tfor (String a : alpha2only) {\n\t\t\t\tfor (Transition transition2 : pta2.getTransitionsByAction(state.i2, a)) {\n\t\t\t\t\t// Create new transition\n\t\t\t\t\ttransition = par.addTransition(src, a);\n\t\t\t\t\t// Copy guard\n\t\t\t\t\tfor (Constraint c : transition2.getGuardConstraints())\n\t\t\t\t\t\ttransition.addGuardConstraint(c.deepCopy().renameClocks(pta2, par));\n\t\t\t\t\t// Combine edges\n\t\t\t\t\tfor (Edge edge2 : transition2.getEdges()) {\n\t\t\t\t\t\tprob = edge2.getProbability();\n\t\t\t\t\t\tdest = addState(state.i1, edge2.getDestination());\n\t\t\t\t\t\tedge = transition.addEdge(prob, dest);\n\t\t\t\t\t\t// Copy resets\n\t\t\t\t\t\tfor (Map.Entry<Integer, Integer> e : edge2.getResets()) {\n\t\t\t\t\t\t\tedge.addReset(PTA.renameClock(pta2, par, e.getKey()), e.getValue());\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Go through synchronous transitions\n\t\t\tfor (String a : sync) {\n\t\t\t\tfor (Transition transition1 : pta1.getTransitionsByAction(state.i1, a)) {\n\t\t\t\t\tfor (Transition transition2 : pta2.getTransitionsByAction(state.i2, a)) {\n\t\t\t\t\t\t// Create new transition\n\t\t\t\t\t\ttransition = par.addTransition(src, a);\n\t\t\t\t\t\t// Guard is conjunction of guards\n\t\t\t\t\t\tfor (Constraint c : transition1.getGuardConstraints())\n\t\t\t\t\t\t\ttransition.addGuardConstraint(c.deepCopy().renameClocks(pta1, par));\n\t\t\t\t\t\tfor (Constraint c : transition2.getGuardConstraints())\n\t\t\t\t\t\t\ttransition.addGuardConstraint(c.deepCopy().renameClocks(pta2, par));\n\t\t\t\t\t\t// Combine edges\n\t\t\t\t\t\tfor (Edge edge1 : transition1.getEdges()) {\n\t\t\t\t\t\t\tfor (Edge edge2 : transition2.getEdges()) {\n\t\t\t\t\t\t\t\tprob = edge1.getProbability() * edge2.getProbability();\n\t\t\t\t\t\t\t\tdest = addState(edge1.getDestination(), edge2.getDestination());\n\t\t\t\t\t\t\t\tedge = transition.addEdge(prob, dest);\n\t\t\t\t\t\t\t\t// Reset set is union of reset sets\n\t\t\t\t\t\t\t\tfor (Map.Entry<Integer, Integer> e : edge1.getResets()) {\n\t\t\t\t\t\t\t\t\tedge.addReset(PTA.renameClock(pta1, par, e.getKey()), e.getValue());\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tfor (Map.Entry<Integer, Integer> e : edge2.getResets()) {\n\t\t\t\t\t\t\t\t\tedge.addReset(PTA.renameClock(pta2, par, e.getKey()), e.getValue());\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn par;\n\t}\n\n\t/**\n\t * Helper function. Add a new state, if it does not already exist, and returns its index.\n\t * @param loc1: Index of location of PTA 1\n\t * @param loc2: Index of location of PTA 2\n\t */\n\tprivate int addState(int loc1, int loc2)\n\t{\n\t\t// See if this is a new state\n\t\tIndexPair stateNew = new IndexPair(loc1, loc2);\n\t\tif (states.add(stateNew)) {\n\t\t\t// If so, add to the explore list\n\t\t\texplore.add(stateNew);\n\t\t\t// Get index of state in state set\n\t\t\tint locNew = states.getIndexOfLastAdd();\n\t\t\t// And add a location to the PTA\n\t\t\tpar.addLocation(PTA.combineLocationNames(pta1.getLocationName(loc1), pta2.getLocationName(loc2)));\n\t\t\t// Invariant is conjunction of two invariants\n\t\t\tfor (Constraint c : pta1.getInvariantConstraints(loc1))\n\t\t\t\tpar.addInvariantCondition(locNew, c.deepCopy().renameClocks(pta1, par));\n\t\t\tfor (Constraint c : pta2.getInvariantConstraints(loc2))\n\t\t\t\tpar.addInvariantCondition(locNew, c.deepCopy().renameClocks(pta2, par));\n\t\t}\n\t\t// Return index of state in state set \n\t\treturn states.getIndexOfLastAdd();\n\t}\n\t\n\t/**\n\t * Class to store a pair of indices.\n\t */\n\tclass IndexPair\n\t{\n\t\tint i1;\n\t\tint i2;\n\n\t\tpublic IndexPair(int i1, int i2)\n\t\t{\n\t\t\tthis.i1 = i1;\n\t\t\tthis.i2 = i2;\n\t\t}\n\t\t\n\t\tpublic int hashCode()\n\t\t{\n\t\t\t// Simple hash code\n\t\t\treturn i1;\n\t\t}\n\t\t\n\t\tpublic boolean equals(Object o)\n\t\t{\n\t\t\tIndexPair ip;\n\t\t\tif (o == null) return false;\n\t\t\ttry {\n\t\t\t\tip = (IndexPair) o;\n\t\t\t} catch (ClassCastException e) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\treturn i1 == ip.i1 && i2 == ip.i2;\n\t\t}\n\t\t\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn i1 +\",\" + i2; \n\t\t}\n\t}\n\n\t/**\n\t * Main method to test\n\t *  (read from multiple des files, output result to a des file)\n\t */ \n\tpublic static void main(String args[])\n\t{\n\t\tPTA pta, pta2;\n\t\tint i;\n\n\t\tif (args.length < 1) {\n\t\t\tSystem.err.println(\"Usage: java ... <des files>\");\n\t\t\tSystem.exit(1);\n\t\t}\n\t\ttry {\n\t\t\t// Build PTA\n\t\t\tSystem.out.println(\"Building PTA from \\\"\" + args[0] + \"\\\"\");\n\t\t\tpta = PTA.buildPTAFromDesFile(args[0]);\n\t\t\tSystem.out.println(pta.infoString());\n\t\t\t//System.out.println(pta);\n\t\t\tfor (i = 1; i < args.length; i++) {\n\t\t\t\tSystem.out.println(\"Building PTA from \\\"\" + args[i] + \"\\\"\");\n\t\t\t\tpta2 = PTA.buildPTAFromDesFile(args[i]);\n\t\t\t\tSystem.out.println(pta2.infoString());\n\t\t\t\t//System.out.println(pta2);\n\t\t\t\tpta = new PTAParallel().compose(pta, pta2);\n\t\t\t\t//System.out.println(pta);\n\t\t\t}\n\t\t\tSystem.out.println(\"Final PTA: \" + pta.infoString());\n\t\t\tSystem.out.println(pta);\n\t\t\tpta.check();\n\t\t\tpta.writeToDesFile(\"par.des\");\n\t\t\t// Parse target location\n\t\t} catch (PrismException e) {\n\t\t\tSystem.err.println(\"Error: \" + e.getMessage());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/PTAUtils.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.function.Consumer;\n\nimport parser.ParserUtils;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionVar;\nimport parser.type.TypeClock;\nimport parser.type.TypeInt;\nimport prism.PrismLangException;\n\npublic class PTAUtils\n{\n\t/**\n\t * Check whether a PRISM expression (over clock variables) is a \"simple\" clock constraint, i.e. of the form\n\t * x~c or x~y where x and y are clocks, c is an integer-valued expression and ~ is one of <, <=, >=, >, =.\n\t * Throws an explanatory exception if not.\n\t * @param expr: The expression to be checked.\n\t */\n\tpublic static void checkIsSimpleClockConstraint(Expression expr) throws PrismLangException\n\t{\n\t\tExpressionBinaryOp exprRelOp;\n\t\tExpression expr1, expr2;\n\t\tint op, clocks = 0;\n\n\t\t// Check is rel op\n\t\tif (!Expression.isRelOp(expr))\n\t\t\tthrow new PrismLangException(\"Invalid clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t// Split into parts\n\t\texprRelOp = (ExpressionBinaryOp) expr;\n\t\top = exprRelOp.getOperator();\n\t\texpr1 = exprRelOp.getOperand1();\n\t\texpr2 = exprRelOp.getOperand2();\n\t\t// Check operator is of allowed type\n\t\tif (!ExpressionBinaryOp.isRelOp(op))\n\t\t\tthrow new PrismLangException(\"Can't use operator \" + exprRelOp.getOperatorSymbol() + \" in clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\tif (op == ExpressionBinaryOp.NE)\n\t\t\tthrow new PrismLangException(\"Can't use negation in clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t// LHS\n\t\tif (expr1.getType() instanceof TypeClock) {\n\t\t\tif (!(expr1 instanceof ExpressionVar)) {\n\t\t\t\tthrow new PrismLangException(\"Invalid clock expression \\\"\" + expr1 + \"\\\"\", expr1);\n\t\t\t}\n\t\t\tclocks++;\n\t\t} else if (expr1.getType() instanceof TypeInt) {\n\t\t\tif (!expr1.isConstant()) {\n\t\t\t\tthrow new PrismLangException(\"Invalid clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t\t}\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Invalid clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t}\n\t\t// RHS\n\t\tif (expr2.getType() instanceof TypeClock) {\n\t\t\tif (!(expr2 instanceof ExpressionVar)) {\n\t\t\t\tthrow new PrismLangException(\"Invalid clock expression \\\"\" + expr2 + \"\\\"\", expr2);\n\t\t\t}\n\t\t\tclocks++;\n\t\t} else if (expr2.getType() instanceof TypeInt) {\n\t\t\tif (!expr2.isConstant()) {\n\t\t\t\tthrow new PrismLangException(\"Invalid clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t\t}\n\t\t} else {\n\t\t\tthrow new PrismLangException(\"Invalid clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t}\n\t\t// Should be at least one clock\n\t\tif (clocks == 0)\n\t\t\tthrow new PrismLangException(\"Invalid clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t}\n\n\t/**\n\t * Convert a PRISM expression representing a (simple) clock constraint into\n\t * the Constraint data structures used in the pta package.\n\t * Actually creates a list of constraints (since e.g. x=c maps to multiple constraints) \n\t * @param expr: The expression to be converted.\n\t * @param constantValues Values for constants appearing in the expression \n\t * @param pta: The PTA for which this constraint will be used. \n\t */\n\tpublic static List<Constraint> exprToConstraint(Expression expr, Values constantValues, PTA pta) throws PrismLangException\n\t{\n\t\tExpressionBinaryOp exprRelOp;\n\t\tExpression expr1, expr2;\n\t\tint x, y, v;\n\t\tList<Constraint> res = new ArrayList<Constraint>();\n\n\t\t// Check is rel op and split into parts\n\t\tif (!Expression.isRelOp(expr))\n\t\t\tthrow new PrismLangException(\"Invalid clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\texprRelOp = (ExpressionBinaryOp) expr;\n\t\texpr1 = exprRelOp.getOperand1();\n\t\texpr2 = exprRelOp.getOperand2();\n\t\t// 3 cases...\n\t\tif (expr1.getType() instanceof TypeClock) {\n\t\t\t// Comparison of two clocks (x ~ y)\n\t\t\tif (expr2.getType() instanceof TypeClock) {\n\t\t\t\tx = pta.getClockIndex(((ExpressionVar) expr1).getName());\n\t\t\t\tif (x < 0)\n\t\t\t\t\tthrow new PrismLangException(\"Unknown clock \\\"\" + ((ExpressionVar) expr1).getName() + \"\\\"\", expr);\n\t\t\t\ty = pta.getClockIndex(((ExpressionVar) expr2).getName());\n\t\t\t\tif (y < 0)\n\t\t\t\t\tthrow new PrismLangException(\"Unknown clock \\\"\" + ((ExpressionVar) expr2).getName() + \"\\\"\", expr);\n\t\t\t\tswitch (exprRelOp.getOperator()) {\n\t\t\t\tcase ExpressionBinaryOp.EQ:\n\t\t\t\t\tres.add(Constraint.buildXGeqY(x, y));\n\t\t\t\t\tres.add(Constraint.buildXLeqY(x, y));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionBinaryOp.NE:\n\t\t\t\t\tthrow new PrismLangException(\"Can't use negation in clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t\t\tcase ExpressionBinaryOp.GT:\n\t\t\t\t\tres.add(Constraint.buildXGtY(x, y));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionBinaryOp.GE:\n\t\t\t\t\tres.add(Constraint.buildXGeqY(x, y));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionBinaryOp.LT:\n\t\t\t\t\tres.add(Constraint.buildXLtY(x, y));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionBinaryOp.LE:\n\t\t\t\t\tres.add(Constraint.buildXLeqY(x, y));\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\treturn res;\n\t\t\t}\n\t\t\t// Comparison of clock and integer (x ~ v)\n\t\t\telse {\n\t\t\t\tx = pta.getClockIndex(((ExpressionVar) expr1).getName());\n\t\t\t\tif (x < 0)\n\t\t\t\t\tthrow new PrismLangException(\"Unknown clock \\\"\" + ((ExpressionVar) expr1).getName() + \"\\\"\", expr);\n\t\t\t\tv = expr2.evaluateInt(constantValues);\n\t\t\t\tswitch (exprRelOp.getOperator()) {\n\t\t\t\tcase ExpressionBinaryOp.EQ:\n\t\t\t\t\tres.add(Constraint.buildGeq(x, v));\n\t\t\t\t\tres.add(Constraint.buildLeq(x, v));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionBinaryOp.NE:\n\t\t\t\t\tthrow new PrismLangException(\"Can't use negation in clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t\t\tcase ExpressionBinaryOp.GT:\n\t\t\t\t\tres.add(Constraint.buildGt(x, v));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionBinaryOp.GE:\n\t\t\t\t\tres.add(Constraint.buildGeq(x, v));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionBinaryOp.LT:\n\t\t\t\t\tres.add(Constraint.buildLt(x, v));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionBinaryOp.LE:\n\t\t\t\t\tres.add(Constraint.buildLeq(x, v));\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\treturn res;\n\t\t\t}\n\t\t}\n\t\t// Comparison of integer and clock (v ~ x)\n\t\telse if (expr2.getType() instanceof TypeClock) {\n\t\t\tx = pta.getClockIndex(((ExpressionVar) expr2).getName());\n\t\t\tif (x < 0)\n\t\t\t\tthrow new PrismLangException(\"Unknown clock \\\"\" + ((ExpressionVar) expr2).getName() + \"\\\"\", expr);\n\t\t\tv = expr1.evaluateInt(constantValues);\n\t\t\tswitch (exprRelOp.getOperator()) {\n\t\t\tcase ExpressionBinaryOp.EQ:\n\t\t\t\tres.add(Constraint.buildGeq(x, v));\n\t\t\t\tres.add(Constraint.buildLeq(x, v));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.NE:\n\t\t\t\tthrow new PrismLangException(\"Can't use negation in clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t\t\tcase ExpressionBinaryOp.GT:\n\t\t\t\tres.add(Constraint.buildLt(x, v));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.GE:\n\t\t\t\tres.add(Constraint.buildLeq(x, v));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.LT:\n\t\t\t\tres.add(Constraint.buildGt(x, v));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.LE:\n\t\t\t\tres.add(Constraint.buildGeq(x, v));\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\treturn res;\n\t\t}\n\t\tthrow new PrismLangException(\"Invalid clock constraint \\\"\" + expr + \"\\\"\", expr);\n\t}\n\t\n\t/**\n\t * Convert a PRISM expression representing a conjunction of (simple) clock constraints\n\t * into Constraint data structures used in the pta package and pass to a consumer.\n\t * An exception is thrown if any conjunct is not a simple clock constraints (or true/false).\n\t * Since this is a conjunction, any \"true\" constraints are omitted. \n\t * @param expr: The expression to be converted.\n\t * @param constantValues Values for constants appearing in the expression \n\t * @param pta: The PTA for which this constraint will be used.\n\t * @param consumer: The consumer to pass the Constraints to \n\t */\n\tpublic static void exprConjToConstraintConsumer(Expression expr, Values constantValues, PTA pta, Consumer<Constraint> consumer) throws PrismLangException\n\t{\n\t\tList<Expression> exprs = ParserUtils.splitConjunction(expr);\n\t\tfor (Expression ex : exprs) {\n\t\t\tif (!(Expression.isTrue(ex) || Expression.isFalse(ex))) {\n\t\t\t\tcheckIsSimpleClockConstraint(ex);\n\t\t\t}\n\t\t}\n\t\tfor (Expression ex : exprs) {\n\t\t\tif (!Expression.isTrue(ex)) {\n\t\t\t\tfor (Constraint c : PTAUtils.exprToConstraint(ex, constantValues, pta)) {\n\t\t\t\t\tconsumer.accept(c);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Convert a PRISM expression representing a conjunction of (simple) clock constraints\n\t * into a list of Constraint data structures used in the pta package.\n\t * An exception is thrown if any conjunct is not a simple clock constraints (or true/false).\n\t * Since this is a conjunction, any \"true\" constraints are omitted. \n\t * @param expr: The expression to be converted.\n\t * @param constantValues Values for constants appearing in the expression \n\t * @param pta: The PTA for which this constraint will be used.\n\t */\n\tpublic static List<Constraint> exprConjToConstraintList(Expression expr, Values constantValues, PTA pta) throws PrismLangException\n\t{\n\t\tList<Constraint> cons = new ArrayList<>();\n\t\texprConjToConstraintConsumer(expr, constantValues, pta, c -> cons.add(c));\n\t\treturn cons;\n\t}\n\t\n\t/**\n\t * TODO\n\t * @param clockValues\n\t * @param pta\n\t * @return\n\t */\n\tpublic static Zone regionForPoint(double[] clockValues, PTA pta)\n\t{\n\t\tif (clockValues[0] >=2 && clockValues[0] <=2.2) {\n\t\t\tSystem.out.println(\"hmm\");\n\t\t}\n\t\tint numClocks = pta.getNumClocks();\n\t\tZone z = DBM.createTrue(pta);\n\t\tfor (int i = 1; i <= numClocks; i++) {\n\t\t\tdouble x = clockValues[i - 1];\n\t\t\tint xF = (int) Math.floor(x);\n\t\t\tint xC = (int) Math.ceil(x);\n\t\t\tif (x == xF) {\n\t\t\t\tz.addConstraint(Constraint.buildGeq(i, xF));\n\t\t\t} else {\n\t\t\t\tz.addConstraint(Constraint.buildGt(i, xF));\n\t\t\t}\n\t\t\tif (x == xC) {\n\t\t\t\tz.addConstraint(Constraint.buildLeq(i, xC));\n\t\t\t} else {\n\t\t\t\tz.addConstraint(Constraint.buildLt(i, xC));\n\t\t\t}\n\n\t\t\tfor (int j = 1; j <= numClocks; j++) {\n\t\t\t\tif (i != j) {\n\t\t\t\t\tdouble xy = x - clockValues[j - 1];\n\t\t\t\t\tint xyF = (int) Math.floor(xy);\n\t\t\t\t\tint xyC = (int) Math.ceil(xy);\n\t\t\t\t\t// doublesareclose?\n\t\t\t\t\tif (xy == xyF) {\n\t\t\t\t\t\tz.addConstraint(j, i, DB.createLeq(-xyF));\n\t\t\t\t\t} else {\n\t\t\t\t\t\tz.addConstraint(j, i, DB.createLt(-xyF));\n\t\t\t\t\t}\n\t\t\t\t\tif (xy == xyC) {\n\t\t\t\t\t\tz.addConstraint(i, j, DB.createLeq(xyC));\n\t\t\t\t\t} else {\n\t\t\t\t\t\tz.addConstraint(i, j, DB.createLt(xyC));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn z;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/ReachabilityGraph.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.util.*;\n\nimport explicit.*;\nimport prism.*;\n\n/**\n * Class to store a forwards reachability graph for a PTA.\n */\npublic class ReachabilityGraph\n{\n\t// PTA\n\tPTA pta;\n\t// List of symbolic states (Z)\n\tList<LocZone> states;\n\t// List of symbolic transitions (grouped by source location)\n\t// (thus source is not stored explicitly in the symbolic transition)\n\tArrayList<ArrayList<SymbolicTransition>> trans;\n\n\t/**\n\t * Construct empty reachability graph.\n\t * @param pta PTA associated with this graph.\n\t */\n\tpublic ReachabilityGraph(PTA pta)\n\t{\n\t\tthis.pta = pta;\n\t\tstates = null;\n\t\ttrans = new ArrayList<>();\n\t}\n\n\tpublic void addState()\n\t{\n\t\ttrans.add(new ArrayList<>());\n\t}\n\n\tpublic void copyState(int i)\n\t{\n\t\tArrayList<SymbolicTransition> listOld, listNew;\n\t\tlistOld = trans.get(i);\n\t\tlistNew = new ArrayList<>(listOld.size());\n\t\tfor (SymbolicTransition g : listOld)\n\t\t\tlistNew.add(new SymbolicTransition(g));\n\t\ttrans.add(listNew);\n\t}\n\n\t/**\n\t * Add a new symbolic transition to the graph.\n\t * @param src Source state index\n\t * @param tr Corresponding transition in the PTA\n\t * @param dests List of destinations\n\t * @param valid Validity condition (usually left null and computed later)\n\t */\n\tpublic void addTransition(int src, Transition tr, int dests[], Zone valid)\n\t{\n\t\ttrans.get(src).add(new SymbolicTransition(tr, dests, valid));\n\t}\n\n\t/**\n\t * Returns true if state s2 is a successor of state s1\n\t * (i.e. if there is a symbolic transition with s1 as source and s2 in destinations).\n\t */\n\tpublic boolean isSuccessor(int s1, int s2)\n\t{\n\t\tfor (SymbolicTransition st : trans.get(s1)) {\n\t\t\tif (st.hasSuccessor(s2))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Compute the validity conditions for all symbolic transitions in the graph.\n\t */\n\tpublic void computeAllValidities()\n\t{\n\t\tint i, n;\n\t\tArrayList<SymbolicTransition> list;\n\t\tn = trans.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tlist = trans.get(i);\n\t\t\tfor (SymbolicTransition st : list) {\n\t\t\t\tst.valid = computeValidity(i, st.tr, st.dests);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Print the list of symbolic states to a log.\n\t */\n\tpublic void printStates(PrismLog log)\n\t{\n\t\tint i = 0;\n\t\tfor (LocZone lz : states) {\n\t\t\tif (i > 0)\n\t\t\t\tlog.print(\" \");\n\t\t\tlog.print(\"#\" + (i++) + \":\" + lz);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tboolean first;\n\t\tString s = \"\";\n\t\tn = trans.size();\n\t\tfirst = true;\n\t\ts = \"[ \";\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\ts += \", \";\n\t\t\ts += i + \":\" + trans.get(i);\n\t\t}\n\t\ts += \" ]\";\n\t\treturn s;\n\t}\n\n\t/**\n\t * Compute the validity condition for a symbolic transition\n\t * @param src The index of the source state of the symbolic transition \n\t * @param tr The PTA transition corresponding to the symbolic transition\n\t * @param dests The list of destination state indices of the symbolic transition\n\t */\n\tpublic Zone computeValidity(int src, Transition tr, int[] dests)\n\t{\n\t\tZone z = new DBMList(DBM.createTrue(pta));\n\t\tint count = 0;\n\t\tfor (Edge edge : tr.getEdges()) {\n\t\t\tLocZone lz2 = states.get(dests[count]).deepCopy();\n\t\t\tlz2.dPre(edge);\n\t\t\tz.intersect(lz2.zone);\n\t\t\tcount++;\n\t\t}\n\t\tz.down();\n\t\tz.intersect(states.get(src).zone);\n\n\t\treturn z;\n\t}\n\t\n\t/**\n\t * Build an MDP from this forwards reachability graph.\n\t * The set of initial states should also be specified.\n\t */\n\tpublic MDP<Double> buildMDP(List<Integer> initialStates) throws PrismException\n\t{\n\t\tDistribution<Double> distr;\n\t\tint numStates, src, count, dest;\n\t\tMDPSimple<Double> mdp;\n\n\t\t// Building MDP...\n\t\tmdp = new MDPSimple<>();\n\n\t\t// Add all states\n\t\tmdp.addStates(states.size());\n\n\t\t// For each symbolic state...\n\t\tnumStates = states.size(); \n\t\tfor (src = 0; src < numStates; src++) {\n\t\t\t// And for each outgoing transition in PTA...\n\t\t\tfor (SymbolicTransition st : trans.get(src)) {\n\t\t\t\tdistr = Distribution.ofDouble();\n\t\t\t\tcount = -1;\n\t\t\t\tfor (Edge edge : st.tr.getEdges()) {\n\t\t\t\t\tcount++;\n\t\t\t\t\tdest = st.dests[count];\n\t\t\t\t\tdistr.add(dest, edge.getProbability());\n\t\t\t\t}\n\t\t\t\tif (!distr.isEmpty())\n\t\t\t\t\tmdp.addChoice(src, distr);\n\t\t\t}\n\t\t}\n\n\t\t// Set initial states\n\t\tfor (int i : initialStates) {\n\t\t\tmdp.addInitialState(i);\n\t\t}\n\n\t\treturn mdp;\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/SymbolicTransition.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\n/**\n * Class to store a \"symbolic transition\", i.e. an element of a forwards reachability graph\n */\nclass SymbolicTransition\n{\n\t// Pointer to a PTA transition\n\tpublic Transition tr;\n\t// List of target states\n\tpublic int[] dests;\n\t// Stored validity constraint \n\tpublic Zone valid;\n\n\t// Note: tr and valid are just references to other objects;\n\t// the objects themselves should never be modified here.\n\n\t/**\n\t * Usual constructor\n\t */\n\tpublic SymbolicTransition(Transition tr, int[] dests, Zone valid)\n\t{\n\t\tthis.tr = tr;\n\t\tthis.dests = dests;\n\t\tthis.valid = valid;\n\t}\n\n\t/**\n\t * Copy constructor\n\t */\n\tpublic SymbolicTransition(SymbolicTransition copy)\n\t{\n\t\tthis(copy.tr, copy.dests.clone(), copy.valid);\n\t}\n\n\t/**\n\t * Returns true if state s is a successor (a possible destination) of this symbolic transition.\n\t */\n\tpublic boolean hasSuccessor(int s)\n\t{\n\t\tint i, n;\n\t\tn = dests.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (dests[i] == s) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"[\";\n\t\tfor (int i = 0; i < dests.length; i++)\n\t\t\ts += \" \" + dests[i];\n\t\treturn s + \" ]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/Transition.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\nimport java.io.*;\nimport java.util.*;\n\nimport prism.PrismException;\n\npublic class Transition\n{\n\t// Parent PTA\n\tprivate PTA parent;\n\t// Source location\n\tprivate int src;\n\t// Action label (\"\" = tau)\n\tprivate String action;\n\t// Guard - currently a conjunction of constraints\n\tprivate Set<Constraint> guard;\n\t// Edges\n\tprivate int numEdges;\n\tprivate ArrayList<Edge> edges;\n\n\t/**\n\t * Create an empty transition.\n\t * @param parent Parent PTA\n\t * @param src Source location index\n\t * @param action Synchronising action (\"\" if none)\n\t */\n\tpublic Transition(PTA parent, int src, String action)\n\t{\n\t\tthis.parent = parent;\n\t\tthis.src = src;\n\t\tthis.action = action;\n\t\tguard = new LinkedHashSet<Constraint>();\n\t\tnumEdges = 0;\n\t\tedges = new ArrayList<Edge>();\n\t}\n\n\t/**\n\t * Copy constructor.\n\t */\n\tpublic Transition(Transition tr)\n\t{\n\t\tthis(tr.parent, tr.src, tr.action);\n\t\tfor (Constraint c : tr.guard) {\n\t\t\taddGuardConstraint(new Constraint(c));\n\t\t}\n\t\tfor (Edge e : tr.edges) {\n\t\t\taddEdge(new Edge(e));\n\t\t}\n\t}\n\t\n\tpublic void addGuardConstraint(Constraint c)\n\t{\n\t\tguard.add(c);\n\t\tparent.recomputeMaxClockConstraint(c);\n\t}\n\n\tpublic Edge addEdge(double prob, int dest)\n\t{\n\t\tEdge e = new Edge(this, prob, dest);\n\t\tedges.add(e);\n\t\tnumEdges++;\n\t\treturn e;\n\t}\n\n\tpublic void addEdge(Edge e)\n\t{\n\t\te.setParent(this);\n\t\tedges.add(e);\n\t\tnumEdges++;\n\t}\n\t\n\tpublic void setParent(PTA parent)\n\t{\n\t\tthis.parent = parent;\n\t}\n\n\tpublic PTA getParent()\n\t{\n\t\treturn parent;\n\t}\n\n\tpublic String getAction()\n\t{\n\t\treturn action;\n\t}\n\n\tpublic int getSource()\n\t{\n\t\treturn src;\n\t}\n\n\tpublic Iterable<Constraint> getGuardConstraints()\n\t{\n\t\treturn guard;\n\t}\n\n\tpublic int getNumEdges()\n\t{\n\t\treturn edges.size();\n\t}\n\n\tpublic List<Edge> getEdges()\n\t{\n\t\treturn edges;\n\t}\n\n\t/**\n\t * Perform some basic syntactic checks.\n\t */\n\tpublic void check() throws PrismException\n\t{\n\t\t// Check edges\n\t\t// Also check that  total probability is 1 (ish)\n\t\tdouble prob = 0.0;\n\t\tdouble err = 1e-10;\n\t\tfor (Edge e : edges) {\n\t\t\te.check();\n\t\t\tprob += e.getProbability();\n\t\t}\n\t\tif (prob < 1.0-err || prob > 1.0+err)\n\t\t\tthrow new PrismException(\"Non-1 probability (\"+prob+\") for PTA transition \\\"\"+this+\"\\\"\");\n\t}\n\n\tpublic String toString()\n\t{\n\t\tboolean first;\n\t\tString s = \"\";\n\t\ts += parent.getLocationName(src) + \" -\";\n\t\tif (action != null)\n\t\t\ts += action + \":\";\n\t\ts += Constraint.toStringList(parent, guard);\n\t\ts += \"-> \";\n\t\tfirst = true;\n\t\tfor (Edge e : edges) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\ts += \" + \";\n\t\t\ts += e;\n\t\t}\n\t\treturn s;\n\t}\n\n\tpublic void writeToDesFile(Writer out) throws PrismException, IOException\n\t{\n\t\tout.write(\"\\t[\\n\");\n\t\tfor (Edge e : edges) {\n\t\t\te.writeToDesFile(out, ((action == null || \"\".equals(action)) ? \"\" : action + \"||\"), guard);\n\t\t}\n\t\tout.write(\"\\t]\\n\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/pta/Zone.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\npublic abstract class Zone\n{\n\t/**\n\t * Get parent PTA\n\t */\n\n\tpublic abstract PTA getPTA();\n\n\t// Zone operations (modify the zone)\n\n\t/**\n\t * Conjunction: add constraint x-y db\n\t */\n\tpublic abstract void addConstraint(int x, int y, int db);\n\n\t/**\n\t * Conjunction: add constraint c\n\t */\n\tpublic abstract void addConstraint(Constraint c);\n\n\t/**\n\t * Conjunction: add multiple constraints\n\t */\n\tpublic abstract void addConstraints(Iterable<Constraint> constraints);\n\n\t/**\n\t * Conjunction: with another zone\n\t */\n\tpublic abstract void intersect(Zone z);\n\n\t/**\n\t * Up, i.e. let time elapse, subject to some constraints\n\t */\n\tpublic abstract void up(Iterable<Constraint> constraints);\n\n\t/**\n\t * Up, i.e. let time elapse\n\t */\n\tpublic void up()\n\t{\n\t\tup(null);\n\t}\n\n\t/**\n\t * Down, i.e. zone which can reach this one, subject to some constraints\n\t */\n\tpublic abstract void down(Iterable<Constraint> constraints);\n\n\t/**\n\t * Down, i.e. zone which can reach this one\n\t */\n\tpublic void down()\n\t{\n\t\tdown(null);\n\t}\n\t\n\t/**\n\t * Free, i.e. remove constraints on a clock\n\t */\n\tpublic abstract void free(int x);\n\n\t/**\n\t * Reset clock x\n\t */\n\tpublic abstract void reset(int x, int v);\n\n\t/**\n\t * Backward reset of clock x\n\t */\n\tpublic abstract void backReset(int x, int v);\n\n\t/**\n\t * c-Closure\n\t */\n\tpublic abstract void cClosure(int c);\n\n\t// Zone operations (create new zone)\n\t\n\t/**\n\t * Complement\n\t * Creates non-convex zone so creates new one,\n\t * and leaves this one unmodified\n\t */\n\tpublic abstract NCZone createComplement();\n\n\t// Zone queries (do not modify the zone)\n\t\n\t/**\n\t * Is this zone empty (i.e. inconsistent)?\n\t */\n\tpublic abstract boolean isEmpty();\n\n\t/**\n\t * Is constraint c satisfied by this zone (i.e does it overlap)?\n\t */\n\tpublic abstract boolean isSatisfied(Constraint c);\n\n\t/**\n\t * Is a DBM (fully) included in this zone?\n\t */\n\tpublic abstract boolean includes(DBM dbm);\n\t\n\t/**\n\t * Get the minimum value of a clock. \n\t */\n\tpublic abstract int getClockMin(int x);\n\t\n\t/**\n\t * Get the maximum value of a clock. \n\t */\n\tpublic abstract int getClockMax(int x);\n\t\n\t/**\n\t * Check if a clock is unbounded (can be infinite).\n\t */\n\tpublic abstract boolean clockIsUnbounded(int x);\n\t\n\t/**\n\t * Check if all clocks are unbounded (can be infinite).\n\t */\n\tpublic abstract boolean allClocksAreUnbounded();\n\t\n\t// Misc\n\t\n\t/**\n\t * Clone this zone\n\t */\n\tpublic abstract Zone deepCopy();\n\t\n\t/**\n\t * Get storage info string\n\t */\n\tpublic abstract String storageInfo();\n\t\n\t// Standard Java methods\n\n\tpublic abstract int hashCode();\n\n\tpublic abstract boolean equals(Object o);\n}\n"
  },
  {
    "path": "prism/src/pta/ZoneFactory.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage pta;\n\npublic interface ZoneFactory\n{\n\tpublic Zone createZero(PTA pta);\n\tpublic Zone createTrue(PTA pta);\n\tpublic Zone createFromConstraints(PTA pta, Iterable<Constraint> constrs);\n}\n"
  },
  {
    "path": "prism/src/pta/package-info.java",
    "content": "/**\n * Probabilistic timed automata (PTA) model checking, including DBM library.\n */\npackage pta;\n"
  },
  {
    "path": "prism/src/pta/parser/PTAParser.java",
    "content": "/* PTAParser.java */\n/* Generated By:JavaCC: Do not edit this line. PTAParser.java */\npackage pta.parser;\n\nimport java.io.*;\nimport java.util.*;\n\nimport pta.*;\nimport prism.PrismLangException;\n\npublic class PTAParser implements PTAParserConstants {\n        //-----------------------------------------------------------------------------------\n        // Main method for testing purposes\n        //-----------------------------------------------------------------------------------\n\n        public static void main(String[] args)\n        {\n                PTAParser p = null;\n                InputStream str = null;\n                String src = null;\n\n                try {\n                        p = new PTAParser();\n                        str = (args.length > 0) ? new FileInputStream(args[0]) : System.in;\n                        src = (args.length > 0) ? \"file \"+args[0] : \"stdin\";\n                        System.out.println(\"Reading from \"+src+\"...\\u005cn\");\n\n                        PTA pta = p.parsePTA(str);\n                        System.out.print(pta);\n                }\n                catch (PrismLangException e) {\n                        System.out.println(\"Error in \"+src+\": \" + e.getMessage()+\".\"); System.exit(1);\n                }\n                catch (FileNotFoundException e) {\n                        System.out.println(e); System.exit(1);\n                }\n        }\n\n        //-----------------------------------------------------------------------------------\n        // Methods called by Prism\n        //-----------------------------------------------------------------------------------\n\n        // Constructor\n\n        public PTAParser()\n        {\n                // Call default constructor\n                this(System.in);\n        }\n\n        // Parse PTA\n\n        public PTA parsePTA(InputStream str) throws PrismLangException\n        {\n                astPTA pta = null;\n\n                // (Re)start parser\n                ReInit(str);\n                // Parse\n                try {\n                        pta = PTA();\n                }\n                catch (ParseException e) {\n                        throw new PrismLangException(e.getMessage());\n                }\n\n                return pta.createDataStructures();\n        }\n\n        //------------------------------------------------------------------------------\n        // Abstract syntax tree classes\n        //------------------------------------------------------------------------------\n\n        // Classes used to build AST representing PTA.\n        // Note: locations are indexed by name here, not integer as in the normal PTA class\n        // (this is the main reason for needing separate AST classes here).\n        // For clocks, this approach is not needed: we just take the ordering of the clocks\n        // to be as they appear in the file (unlike locations, which have an explicit ordering\n        // combined with possible forward references).\n\n        static class astPTA\n        {\n                // Data\n                public ArrayList<String> clockNames;\n                public ArrayList<String> locationNames;\n                public HashMap<String,LinkedHashSet<Constraint>> invariants;\n                public HashMap<String,ArrayList<astTransition>> transitions;\n                // Methods\n        public astPTA() {\n                clockNames = new ArrayList<String>();\n                locationNames = new ArrayList<String>();\n                        invariants = new HashMap<String,LinkedHashSet<Constraint>>();\n                transitions = new HashMap<String,ArrayList<astTransition>>();\n        }\n                public int getOrAddClock(String name) {\n                        int i = clockNames.indexOf(name);\n                        if (i == -1) { clockNames.add(name); return clockNames.size(); }\n                        else return i+1;\n                }\n                public void addLocation(String name) {\n                        locationNames.add(name);\n                        invariants.put(name, new LinkedHashSet<Constraint>());\n                        transitions.put(name, new ArrayList<astTransition>());\n                }\n                public void addInvariantCondition(String locName, Constraint c) {\n                        invariants.get(locName).add(c);\n                }\n                public void setInvariantConditions(String locName, LinkedHashSet<Constraint> cs) {\n                        invariants.put(locName, cs);\n                }\n                public astTransition addTransition(String locName) {\n                        astTransition t = new astTransition();\n                        transitions.get(locName).add(t);\n                        return t;\n                }\n                public int getLocationIndex(String name) {\n                        return locationNames.indexOf(name);\n                }\n                // Conversion to pta classes\n                public PTA createDataStructures()\n                {\n                        int i, n;\n                        String name;\n                        PTA pta;\n                        Transition trans;\n                        LinkedHashSet <String> alphabet = new LinkedHashSet<String>();\n                        // Find alphabet\n                        n = locationNames.size();\n                        for (i = 0; i < n; i++) {\n                                ArrayList<astTransition> tt = transitions.get(locationNames.get(i));\n                                if (tt == null || tt.isEmpty()) continue;\n                                for (astTransition t : tt) {\n                                        if (t.action != null && !t.action.equals(\"\")) {\n                                                alphabet.add(t.action);\n                                        }\n                                }\n                        }\n                        // Create new PTA\n                        pta = new PTA(new ArrayList<String> (alphabet));\n                        // Add all clocks\n                        n = clockNames.size();\n                        for (i = 0; i < n; i++)\n                                pta.addClock(clockNames.get(i));\n                        // Add all locations\n                        n = locationNames.size();\n                        for (i = 0; i < n; i++)\n                                pta.addLocation(locationNames.get(i));\n                        // Add invariants/transitions to locations\n                        n = locationNames.size();\n                        for (i = 0; i < n; i++) {\n                                name = locationNames.get(i);\n                                pta.setInvariantConditions(i, invariants.get(name));\n                                ArrayList<astTransition> tt = transitions.get(name);\n                                if (tt == null || tt.isEmpty()) continue;\n                                for (astTransition t : tt) {\n                                        if (!(t.edges.isEmpty())) {\n                                                trans = pta.addTransition(i, t.action);\n                                                t.createDataStructures(this, trans);\n                                        }\n                                }\n                        }\n                        return pta;\n                }\n        }\n\n        static class astTransition\n        {\n                // Data\n                private String action = null;\n                private ArrayList<Constraint> guard;\n                public ArrayList<astEdge> edges;\n                // Methods\n                public astTransition() { guard = new ArrayList<Constraint>(); edges = new ArrayList<astEdge>(); }\n                public void setAction(String action) { this.action = action; }\n                public void addGuardConstraint(Constraint c) { guard.add(c); }\n                public astEdge addEdge(double prob, String dest) { astEdge e = new astEdge(prob, dest); edges.add(e); return e; }\n                // Conversion to pta classes\n                public void createDataStructures(astPTA pta, Transition trans)\n                {\n                        for (Constraint c : guard)\n                                trans.addGuardConstraint(c);\n                        for (astEdge e : edges)\n                                e.createDataStructures(pta, trans);\n                }\n        }\n\n        static class astEdge\n        {\n                // Data\n                public double prob;\n                public String dest;\n                public HashMap<Integer,Integer> resets;\n                // Methods\n                public astEdge(double prob, String dest) { this.prob = prob; this.dest = dest; resets = new HashMap<Integer,Integer>(); }\n                public void addReset(int clock, int val) { resets.put(clock, val); }\n                // Conversion to pta classes\n                public void createDataStructures(astPTA pta, Transition trans)\n                {\n                        int d = pta.getLocationIndex(dest);\n                        if (d == -1) { System.err.println(\"Error: Location \\u005c\"\"+dest+\"\\u005c\" does not exist\"); System.exit(1); }\n                        Edge edge = trans.addEdge(prob, d);\n                        for (Map.Entry<Integer,Integer> e : resets.entrySet()) edge.addReset(e.getKey(), e.getValue());\n                }\n        }\n\n//-----------------------------------------------------------------------------------\n// Top-level production\n//-----------------------------------------------------------------------------------\n\n// PTA\n  static final public \nastPTA PTA() throws ParseException {astPTA pta = new astPTA();\n    label_1:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACE:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[0] = jj_gen;\n        break label_1;\n      }\n      Location(pta);\n    }\n    jj_consume_token(0);\n{if (\"\" != null) return pta;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n  static final public void Location(astPTA pta) throws ParseException {String name;\n        LinkedHashSet<Constraint> constrs;\n    jj_consume_token(LBRACE);\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case INIT:{\n      jj_consume_token(INIT);\n      break;\n      }\n    default:\n      jj_la1[1] = jj_gen;\n      ;\n    }\n    jj_consume_token(NODE);\n    name = Identifier();\npta.addLocation(name);\n    jj_consume_token(SEMICOLON);\n    constrs = ConstraintList(pta);\npta.setInvariantConditions(name, constrs);\n    label_2:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case LBRACKET:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[2] = jj_gen;\n        break label_2;\n      }\n      Transition(pta, name);\n    }\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case RBRACE:{\n      jj_consume_token(RBRACE);\n      break;\n      }\n    case TIMES:{\n      jj_consume_token(TIMES);\n      break;\n      }\n    default:\n      jj_la1[3] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n  static final public void Transition(astPTA pta, String locName) throws ParseException {astTransition tr;\n    jj_consume_token(LBRACKET);\ntr = pta.addTransition(locName);\n    label_3:\n    while (true) {\n      switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n      case TRAN:\n      case REG_IDENT:{\n        ;\n        break;\n        }\n      default:\n        jj_la1[4] = jj_gen;\n        break label_3;\n      }\n      Edge(pta, tr);\n    }\n    jj_consume_token(RBRACKET);\n  }\n\n  static final public void Edge(astPTA pta, astTransition tr) throws ParseException {LinkedHashSet<Constraint> constrs;\n        String action = null, dest;\n        double p;\n        astEdge edge;\n        HashMap<Integer,Integer> resets;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_IDENT:{\n      action = Identifier();\n      jj_consume_token(OR);\n      jj_consume_token(OR);\n      break;\n      }\n    default:\n      jj_la1[5] = jj_gen;\n      ;\n    }\n    jj_consume_token(TRAN);\n    dest = Identifier();\n    jj_consume_token(SEMICOLON);\n    constrs = ConstraintList(pta);\n    jj_consume_token(SEMICOLON);\n    resets = Resets(pta);\n    jj_consume_token(SEMICOLON);\n    p = Probability();\ntr.setAction(action);\n                edge = tr.addEdge(p, dest);\n                for (Map.Entry<Integer,Integer> e : resets.entrySet()) edge.addReset(e.getKey(), e.getValue());\n                for (Constraint c : constrs) tr.addGuardConstraint(c);\n  }\n\n  static final public LinkedHashSet<Constraint> ConstraintList(astPTA pta) throws ParseException {LinkedHashSet<Constraint> constrs = new LinkedHashSet<Constraint>();\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_IDENT:{\n      Constraint(pta, constrs);\n      label_4:\n      while (true) {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case COMMA:{\n          ;\n          break;\n          }\n        default:\n          jj_la1[6] = jj_gen;\n          break label_4;\n        }\n        jj_consume_token(COMMA);\n        Constraint(pta, constrs);\n      }\n      break;\n      }\n    case TRUE:{\n      jj_consume_token(TRUE);\n      break;\n      }\n    default:\n      jj_la1[7] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return constrs;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n  static final public void Constraint(astPTA pta, LinkedHashSet<Constraint> constrs) throws ParseException {String clock1Name, clock2Name;\n        int clock1, clock2, val;\n        Token t;\n    clock1Name = Identifier();\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case LT:{\n      t = jj_consume_token(LT);\n      break;\n      }\n    case LE:{\n      t = jj_consume_token(LE);\n      break;\n      }\n    case GT:{\n      t = jj_consume_token(GT);\n      break;\n      }\n    case GE:{\n      t = jj_consume_token(GE);\n      break;\n      }\n    case EQ:{\n      t = jj_consume_token(EQ);\n      break;\n      }\n    default:\n      jj_la1[8] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_INT:{\n      val = Integer();\nclock1 = pta.getOrAddClock(clock1Name);\n                switch (t.kind) {\n                case PTAParserConstants.LT:\n                        constrs.add(Constraint.buildLt(clock1, val)); break;\n                case PTAParserConstants.LE:\n                        constrs.add(Constraint.buildLeq(clock1, val)); break;\n                case PTAParserConstants.GT:\n                        constrs.add(Constraint.buildGt(clock1, val)); break;\n                case PTAParserConstants.GE:\n                        constrs.add(Constraint.buildGeq(clock1, val)); break;\n                case PTAParserConstants.EQ:\n                        constrs.add(Constraint.buildLeq(clock1, val));\n                        constrs.add(Constraint.buildGeq(clock1, val)); break;\n                }\n      break;\n      }\n    case REG_IDENT:{\n      clock2Name = Identifier();\nclock1 = pta.getOrAddClock(clock1Name);\n                clock2 = pta.getOrAddClock(clock2Name);\n                switch (t.kind) {\n                case PTAParserConstants.LT:\n                        constrs.add(Constraint.buildLt(clock1, clock2)); break;\n                default:\n                        System.err.println(\"Error: Unsupported constraint type\"); System.exit(1);\n                }\n      break;\n      }\n    default:\n      jj_la1[9] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n  }\n\n  static final public HashMap<Integer,Integer> Resets(astPTA pta) throws ParseException {HashMap<Integer,Integer> resets = new HashMap<Integer,Integer>();\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_IDENT:{\n      Reset(pta, resets);\n      label_5:\n      while (true) {\n        switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n        case COMMA:{\n          ;\n          break;\n          }\n        default:\n          jj_la1[10] = jj_gen;\n          break label_5;\n        }\n        jj_consume_token(COMMA);\n        Reset(pta, resets);\n      }\n      break;\n      }\n    case NULL:{\n      jj_consume_token(NULL);\n      break;\n      }\n    default:\n      jj_la1[11] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return resets;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n  static final public void Reset(astPTA pta, HashMap<Integer,Integer> resets) throws ParseException {String clockName;\n        int clock;\n        int val;\n    clockName = Identifier();\n    jj_consume_token(EQ);\n    val = Integer();\nclock = pta.getOrAddClock(clockName);\n                resets.put(clock, val);\n  }\n\n  static final public double Probability() throws ParseException {Token t;\n        double d;\n    switch ((jj_ntk==-1)?jj_ntk_f():jj_ntk) {\n    case REG_DOUBLE:{\n      t = jj_consume_token(REG_DOUBLE);\n      break;\n      }\n    case REG_INT:{\n      t = jj_consume_token(REG_INT);\n      break;\n      }\n    default:\n      jj_la1[12] = jj_gen;\n      jj_consume_token(-1);\n      throw new ParseException();\n    }\n{if (\"\" != null) return Double.parseDouble(t.image);}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n//-----------------------------------------------------------------------------------\n// Miscellaneous stuff\n//-----------------------------------------------------------------------------------\n\n// Identifier (returns String)\n  static final public \nString Identifier() throws ParseException {\n    jj_consume_token(REG_IDENT);\n{if (\"\" != null) return getToken(0).image;}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n// Integer\n  static final public \nint Integer() throws ParseException {\n    jj_consume_token(REG_INT);\n{if (\"\" != null) return Integer.parseInt(getToken(0).image);}\n    throw new Error(\"Missing return statement in function\");\n  }\n\n  static private boolean jj_initialized_once = false;\n  /** Generated Token Manager. */\n  static public PTAParserTokenManager token_source;\n  static SimpleCharStream jj_input_stream;\n  /** Current token. */\n  static public Token token;\n  /** Next token. */\n  static public Token jj_nt;\n  static private int jj_ntk;\n  static private int jj_gen;\n  static final private int[] jj_la1 = new int[13];\n  static private int[] jj_la1_0;\n  static private int[] jj_la1_1;\n  static {\n      jj_la1_init_0();\n      jj_la1_init_1();\n   }\n   private static void jj_la1_init_0() {\n      jj_la1_0 = new int[] {0x200000,0x8,0x80000,0x80400000,0x40,0x0,0x8000,0x80,0x1e800000,0x0,0x8000,0x20,0x0,};\n   }\n   private static void jj_la1_init_1() {\n      jj_la1_1 = new int[] {0x0,0x0,0x0,0x0,0x100,0x100,0x0,0x100,0x0,0x120,0x0,0x100,0x60,};\n   }\n\n  /** Constructor with InputStream. */\n  public PTAParser(java.io.InputStream stream) {\n     this(stream, null);\n  }\n  /** Constructor with InputStream and supplied encoding */\n  public PTAParser(java.io.InputStream stream, String encoding) {\n    if (jj_initialized_once) {\n      System.out.println(\"ERROR: Second call to constructor of static parser.  \");\n      System.out.println(\"       You must either use ReInit() or set the JavaCC option STATIC to false\");\n      System.out.println(\"       during parser generation.\");\n      throw new Error();\n    }\n    jj_initialized_once = true;\n    try { jj_input_stream = new SimpleCharStream(stream, encoding, 1, 1); } catch(java.io.UnsupportedEncodingException e) { throw new RuntimeException(e); }\n    token_source = new PTAParserTokenManager(jj_input_stream);\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < 13; i++) jj_la1[i] = -1;\n  }\n\n  /** Reinitialise. */\n  static public void ReInit(java.io.InputStream stream) {\n     ReInit(stream, null);\n  }\n  /** Reinitialise. */\n  static public void ReInit(java.io.InputStream stream, String encoding) {\n    try { jj_input_stream.ReInit(stream, encoding, 1, 1); } catch(java.io.UnsupportedEncodingException e) { throw new RuntimeException(e); }\n    token_source.ReInit(jj_input_stream);\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < 13; i++) jj_la1[i] = -1;\n  }\n\n  /** Constructor. */\n  public PTAParser(java.io.Reader stream) {\n    if (jj_initialized_once) {\n      System.out.println(\"ERROR: Second call to constructor of static parser. \");\n      System.out.println(\"       You must either use ReInit() or set the JavaCC option STATIC to false\");\n      System.out.println(\"       during parser generation.\");\n      throw new Error();\n    }\n    jj_initialized_once = true;\n    jj_input_stream = new SimpleCharStream(stream, 1, 1);\n    token_source = new PTAParserTokenManager(jj_input_stream);\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < 13; i++) jj_la1[i] = -1;\n  }\n\n  /** Reinitialise. */\n  static public void ReInit(java.io.Reader stream) {\n    jj_input_stream.ReInit(stream, 1, 1);\n    token_source.ReInit(jj_input_stream);\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < 13; i++) jj_la1[i] = -1;\n  }\n\n  /** Constructor with generated Token Manager. */\n  public PTAParser(PTAParserTokenManager tm) {\n    if (jj_initialized_once) {\n      System.out.println(\"ERROR: Second call to constructor of static parser. \");\n      System.out.println(\"       You must either use ReInit() or set the JavaCC option STATIC to false\");\n      System.out.println(\"       during parser generation.\");\n      throw new Error();\n    }\n    jj_initialized_once = true;\n    token_source = tm;\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < 13; i++) jj_la1[i] = -1;\n  }\n\n  /** Reinitialise. */\n  public void ReInit(PTAParserTokenManager tm) {\n    token_source = tm;\n    token = new Token();\n    jj_ntk = -1;\n    jj_gen = 0;\n    for (int i = 0; i < 13; i++) jj_la1[i] = -1;\n  }\n\n  static private Token jj_consume_token(int kind) throws ParseException {\n    Token oldToken;\n    if ((oldToken = token).next != null) token = token.next;\n    else token = token.next = token_source.getNextToken();\n    jj_ntk = -1;\n    if (token.kind == kind) {\n      jj_gen++;\n      return token;\n    }\n    token = oldToken;\n    jj_kind = kind;\n    throw generateParseException();\n  }\n\n\n/** Get the next Token. */\n  static final public Token getNextToken() {\n    if (token.next != null) token = token.next;\n    else token = token.next = token_source.getNextToken();\n    jj_ntk = -1;\n    jj_gen++;\n    return token;\n  }\n\n/** Get the specific Token. */\n  static final public Token getToken(int index) {\n    Token t = token;\n    for (int i = 0; i < index; i++) {\n      if (t.next != null) t = t.next;\n      else t = t.next = token_source.getNextToken();\n    }\n    return t;\n  }\n\n  static private int jj_ntk_f() {\n    if ((jj_nt=token.next) == null)\n      return (jj_ntk = (token.next=token_source.getNextToken()).kind);\n    else\n      return (jj_ntk = jj_nt.kind);\n  }\n\n  static private java.util.List<int[]> jj_expentries = new java.util.ArrayList<int[]>();\n  static private int[] jj_expentry;\n  static private int jj_kind = -1;\n\n  /** Generate ParseException. */\n  static public ParseException generateParseException() {\n    jj_expentries.clear();\n    boolean[] la1tokens = new boolean[42];\n    if (jj_kind >= 0) {\n      la1tokens[jj_kind] = true;\n      jj_kind = -1;\n    }\n    for (int i = 0; i < 13; i++) {\n      if (jj_la1[i] == jj_gen) {\n        for (int j = 0; j < 32; j++) {\n          if ((jj_la1_0[i] & (1<<j)) != 0) {\n            la1tokens[j] = true;\n          }\n          if ((jj_la1_1[i] & (1<<j)) != 0) {\n            la1tokens[32+j] = true;\n          }\n        }\n      }\n    }\n    for (int i = 0; i < 42; i++) {\n      if (la1tokens[i]) {\n        jj_expentry = new int[1];\n        jj_expentry[0] = i;\n        jj_expentries.add(jj_expentry);\n      }\n    }\n    int[][] exptokseq = new int[jj_expentries.size()][];\n    for (int i = 0; i < jj_expentries.size(); i++) {\n      exptokseq[i] = jj_expentries.get(i);\n    }\n    return new ParseException(token, exptokseq, tokenImage);\n  }\n\n  /** Enable tracing. */\n  static final public void enable_tracing() {\n  }\n\n  /** Disable tracing. */\n  static final public void disable_tracing() {\n  }\n\n}\n\n//-----------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/pta/parser/PTAParser.jj",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\noptions {\n\tLOOKAHEAD = 1;\n}\n\nPARSER_BEGIN(PTAParser)\n\npackage pta.parser;\n\nimport java.io.*;\nimport java.util.*;\n\nimport pta.*;\nimport prism.PrismLangException;\n\npublic class PTAParser\n{\n\t//-----------------------------------------------------------------------------------\n\t// Main method for testing purposes\n\t//-----------------------------------------------------------------------------------\n\n\tpublic static void main(String[] args)\n\t{\n\t\tPTAParser p = null;\n\t\tInputStream str = null;\n\t\tString src = null;\n\t\t\n\t\ttry {\n\t\t\tp = new PTAParser();\n\t\t\tstr = (args.length > 0) ? new FileInputStream(args[0]) : System.in;\n\t\t\tsrc = (args.length > 0) ? \"file \"+args[0] : \"stdin\";\n\t\t\tSystem.out.println(\"Reading from \"+src+\"...\\n\");\n\t\t\t\n\t\t\tPTA pta = p.parsePTA(str);\n\t\t\tSystem.out.print(pta);\n\t\t}\n\t\tcatch (PrismLangException e) {\n\t\t\tSystem.out.println(\"Error in \"+src+\": \" + e.getMessage()+\".\"); System.exit(1);\n\t\t}\n\t\tcatch (FileNotFoundException e) {\n\t\t\tSystem.out.println(e); System.exit(1);\n\t\t}\n\t}\n\n\t//-----------------------------------------------------------------------------------\n\t// Methods called by Prism\n\t//-----------------------------------------------------------------------------------\n\n\t// Constructor\n\n\tpublic PTAParser()\n\t{\n\t\t// Call default constructor\n\t\tthis(System.in);\n\t}\n\t\n\t// Parse PTA\n\t\n\tpublic PTA parsePTA(InputStream str) throws PrismLangException\n\t{\n\t\tastPTA pta = null;\n\t\t\n\t\t// (Re)start parser\n\t\tReInit(str);\n\t\t// Parse\n\t\ttry {\n\t\t\tpta = PTA();\n\t\t}\n\t\tcatch (ParseException e) {\n\t\t\tthrow new PrismLangException(e.getMessage());\n\t\t}\n\t\t\n\t\treturn pta.createDataStructures();\n\t}\n\t\n\t//------------------------------------------------------------------------------\n\t// Abstract syntax tree classes\n\t//------------------------------------------------------------------------------\n\t\n\t// Classes used to build AST representing PTA.\n\t// Note: locations are indexed by name here, not integer as in the normal PTA class\n\t// (this is the main reason for needing separate AST classes here).\n\t// For clocks, this approach is not needed: we just take the ordering of the clocks\n\t// to be as they appear in the file (unlike locations, which have an explicit ordering\n\t// combined with possible forward references).\n\t\n\tstatic class astPTA\n\t{\n\t\t// Data\n\t\tpublic ArrayList<String> clockNames;\n\t\tpublic ArrayList<String> locationNames;\n\t\tpublic HashMap<String,LinkedHashSet<Constraint>> invariants;\n\t\tpublic HashMap<String,ArrayList<astTransition>> transitions;\n\t\t// Methods\n        public astPTA() {\n        \tclockNames = new ArrayList<String>();\n        \tlocationNames = new ArrayList<String>();\n\t\t\tinvariants = new HashMap<String,LinkedHashSet<Constraint>>();\n        \ttransitions = new HashMap<String,ArrayList<astTransition>>();\n        }\n\t\tpublic int getOrAddClock(String name) {\n\t\t\tint i = clockNames.indexOf(name);\n\t\t\tif (i == -1) { clockNames.add(name); return clockNames.size(); }\n\t\t\telse return i+1;\n\t\t}\n\t\tpublic void addLocation(String name) {\n\t\t\tlocationNames.add(name);\n\t\t\tinvariants.put(name, new LinkedHashSet<Constraint>());\n\t\t\ttransitions.put(name, new ArrayList<astTransition>());\n\t\t}\n\t\tpublic void addInvariantCondition(String locName, Constraint c) {\n\t\t\tinvariants.get(locName).add(c);\n\t\t}\n\t\tpublic void setInvariantConditions(String locName, LinkedHashSet<Constraint> cs) {\n\t\t\tinvariants.put(locName, cs);\n\t\t}\n\t\tpublic astTransition addTransition(String locName) {\n\t\t\tastTransition t = new astTransition();\n\t\t\ttransitions.get(locName).add(t);\n\t\t\treturn t;\n\t\t}\n\t\tpublic int getLocationIndex(String name) {\n\t\t\treturn locationNames.indexOf(name);\n\t\t}\n\t\t// Conversion to pta classes\n\t\tpublic PTA createDataStructures()\n\t\t{\n\t\t\tint i, n;\n\t\t\tString name;\n\t\t\tPTA pta;\n\t\t\tTransition trans;\n\t\t\tLinkedHashSet <String> alphabet = new LinkedHashSet<String>();\n\t\t\t// Find alphabet\n\t\t\tn = locationNames.size();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tArrayList<astTransition> tt = transitions.get(locationNames.get(i));\n\t\t\t\tif (tt == null || tt.isEmpty()) continue;\n\t\t\t\tfor (astTransition t : tt) {\n\t\t\t\t\tif (t.action != null && !t.action.equals(\"\")) {\n\t\t\t\t\t\talphabet.add(t.action);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Create new PTA\n\t\t\tpta = new PTA(new ArrayList<String> (alphabet));\n\t\t\t// Add all clocks\n\t\t\tn = clockNames.size();\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tpta.addClock(clockNames.get(i));\n\t\t\t// Add all locations\n\t\t\tn = locationNames.size();\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\tpta.addLocation(locationNames.get(i));\n\t\t\t// Add invariants/transitions to locations\n\t\t\tn = locationNames.size();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tname = locationNames.get(i);\n\t\t\t\tpta.setInvariantConditions(i, invariants.get(name));\n\t\t\t\tArrayList<astTransition> tt = transitions.get(name);\n\t\t\t\tif (tt == null || tt.isEmpty()) continue;\n\t\t\t\tfor (astTransition t : tt) {\n\t\t\t\t\tif (!(t.edges.isEmpty())) {\n\t\t\t\t\t\ttrans = pta.addTransition(i, t.action);\n\t\t\t\t\t\tt.createDataStructures(this, trans);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn pta;\n\t\t}\n\t}\n\n\tstatic class astTransition\n\t{\n\t\t// Data\n\t\tprivate String action = null;\n\t\tprivate ArrayList<Constraint> guard;\n\t\tpublic ArrayList<astEdge> edges;\n\t\t// Methods\n\t\tpublic astTransition() { guard = new ArrayList<Constraint>(); edges = new ArrayList<astEdge>(); }\n\t\tpublic void setAction(String action) { this.action = action; }\n\t\tpublic void addGuardConstraint(Constraint c) { guard.add(c); }\n\t\tpublic astEdge addEdge(double prob, String dest) { astEdge e = new astEdge(prob, dest); edges.add(e); return e; }\n\t\t// Conversion to pta classes\n\t\tpublic void createDataStructures(astPTA pta, Transition trans)\n\t\t{\n\t\t\tfor (Constraint c : guard)\n\t\t\t\ttrans.addGuardConstraint(c);\n\t\t\tfor (astEdge e : edges)\n\t\t\t\te.createDataStructures(pta, trans);\n\t\t}\n\t}\n\t\n\tstatic class astEdge\n\t{\n\t\t// Data\n\t\tpublic double prob;\n\t\tpublic String dest;\n\t\tpublic HashMap<Integer,Integer> resets;\n\t\t// Methods\n\t\tpublic astEdge(double prob, String dest) { this.prob = prob; this.dest = dest; resets = new HashMap<Integer,Integer>(); }\n\t\tpublic void addReset(int clock, int val) { resets.put(clock, val); }\n\t\t// Conversion to pta classes\n\t\tpublic void createDataStructures(astPTA pta, Transition trans)\n\t\t{\n\t\t\tint d = pta.getLocationIndex(dest);\n\t\t\tif (d == -1) { System.err.println(\"Error: Location \\\"\"+dest+\"\\\" does not exist\"); System.exit(1); }\n\t\t\tEdge edge = trans.addEdge(prob, d);\n\t\t\tfor (Map.Entry<Integer,Integer> e : resets.entrySet()) edge.addReset(e.getKey(), e.getValue());\n\t\t}\n\t}\n}\n\n//-----------------------------------------------------------------------------------\n\nPARSER_END(PTAParser)\n\n// Skip (but store) all other white space\n\nSPECIAL_TOKEN :\n{\n\t<WHITESPACE: (\" \"|\"\\t\"|\"\\n\"|\"\\r\")>\n}\n\n// Skip (but store) comments\n\nSPECIAL_TOKEN :\n{\n\t<COMMENT: \"#\" (~[\"\\n\",\"\\r\"])* (\"\\n\"|\"\\r\"|\"\\r\\n\")>\n}\n\n// Tokens\n\nTOKEN :\n{\n\t// Keywords\n\t< INIT:\t\t\t\t\"init\" >\n|\t< NODE:\t\t\t\t\"node\" >\n|\t< NULL:\t\t\t\t\"null\" >\n|\t< TRAN:\t\t\t\t\"tran\" >\n|\t< TRUE:\t\t\t\t\"true\" >\n\t// Punctuation, etc.\n|\t< NOT:\t\t\t\"!\" >\n|\t< AND:\t\t\t\"&\" >\n|\t< OR:\t\t\t\"|\" >\n|\t< IMPLIES:\t\t\"=>\" >\n|\t< RARROW:\t\t\"->\" >\n|\t< COLON:\t\t\":\" >\n|\t< SEMICOLON:\t\";\" >\n|\t< COMMA:\t\t\",\" >\n|\t< DOTS:\t\t\t\"..\" >\n|\t< LPARENTH:\t\t\"(\" >\n|\t< RPARENTH:\t\t\")\" >\n|\t< LBRACKET: \t\"[\" >\n|\t< RBRACKET:\t\t\"]\" >\n|\t< LBRACE:\t\t\"{\" >\n|\t< RBRACE:\t\t\"}\" >\n|\t< EQ:\t\t\t\"=\" >\n|\t< NE:\t\t\t\"!=\" >\n|\t< LT:\t\t\t\"<\" >\n|\t< GT:\t\t\t\">\" >\n|\t< LE:\t\t\t\"<=\" >\n|\t< GE:\t\t\t\">=\" >\n|\t< PLUS:\t\t\t\"+\" >\n|\t< MINUS:\t\t\"-\" >\n|\t< TIMES:\t\t\"*\" >\n|\t< DIVIDE:\t\t\"/\" >\n|\t< PRIME:\t\t\"'\" >\n|\t< RENAME:\t\t\"<-\" >\n|\t< QMARK:\t\t\"?\" >\n|\t< DQUOTE:\t\t\"\\\"\" >\n\t// Regular expressions\n|\t< REG_INT:\t\t\t([\"1\"-\"9\"]([\"0\"-\"9\"])*)|(\"0\") >\n|\t< REG_DOUBLE:\t\t([\"0\"-\"9\"])*(\".\")?([\"0\"-\"9\"])+([\"e\",\"E\"]([\"-\",\"+\"])?([\"0\"-\"9\"])+)? >\n|\t< REG_IDENTPRIME:\t[\"_\",\"a\"-\"z\",\"A\"-\"Z\"]([\"_\",\"a\"-\"z\",\"A\"-\"Z\",\"0\"-\"9\"])*\"'\" >\n|\t< REG_IDENT:\t\t[\"_\",\"a\"-\"z\",\"A\"-\"Z\"]([\"_\",\"a\"-\"z\",\"A\"-\"Z\",\"0\"-\"9\"])* >\n\t// Special catch-all token for lexical errors\n\t// (this allows us to throw our usual exceptions in this case)\n|\t< LEXICAL_ERROR: ~[] >\n}\n\n//-----------------------------------------------------------------------------------\n// Top-level production\n//-----------------------------------------------------------------------------------\n\n// PTA\n\nastPTA PTA() :\n{\n\tastPTA pta = new astPTA();\n}\n{\n\t( (Location(pta))* <EOF> )\n\t{\n\t\treturn pta;\n\t}\n}\n\nvoid Location(astPTA pta) :\n{\n\tString name;\n\tLinkedHashSet<Constraint> constrs;\n}\n{\n\t<LBRACE>\n\t(<INIT>)?\n\t<NODE> name=Identifier() { pta.addLocation(name); }\n\t<SEMICOLON> constrs=ConstraintList(pta) { pta.setInvariantConditions(name, constrs); }\n\t(Transition(pta, name))*\n\t(<RBRACE>|<TIMES>)\n}\n\nvoid Transition(astPTA pta, String locName) :\n{\n\tastTransition tr;\n}\n{\n\t<LBRACKET> { tr = pta.addTransition(locName); }\n\t(Edge(pta, tr))*\n\t<RBRACKET>\n}\n\nvoid Edge(astPTA pta, astTransition tr) :\n{\n\tLinkedHashSet<Constraint> constrs;\n\tString action = null, dest;\n\tdouble p;\n\tastEdge edge;\n\tHashMap<Integer,Integer> resets;\n}\n{\n\t(action=Identifier() <OR><OR>)? <TRAN> dest=Identifier() <SEMICOLON> constrs=ConstraintList(pta) <SEMICOLON> resets=Resets(pta) <SEMICOLON> p=Probability()\n\t{\n\t\ttr.setAction(action);\n\t\tedge = tr.addEdge(p, dest);\n\t\tfor (Map.Entry<Integer,Integer> e : resets.entrySet()) edge.addReset(e.getKey(), e.getValue());\n\t\tfor (Constraint c : constrs) tr.addGuardConstraint(c);\n\t}\n}\n\nLinkedHashSet<Constraint> ConstraintList(astPTA pta) :\n{\n\tLinkedHashSet<Constraint> constrs = new LinkedHashSet<Constraint>();\n}\n{\n\t((Constraint(pta, constrs) ( <COMMA> Constraint(pta, constrs) )* )\n\t|\n\t(<TRUE>))\n\t{ return constrs; }\n}\n\nvoid Constraint(astPTA pta, LinkedHashSet<Constraint> constrs) :\n{\n\tString clock1Name, clock2Name;\n\tint clock1, clock2, val;\n\tToken t;\n}\n{\n\t(clock1Name=Identifier() (t=<LT>|t=<LE>|t=<GT>|t=<GE>|t=<EQ>) (val=Integer()\n\t{\n\t\tclock1 = pta.getOrAddClock(clock1Name);\n\t\tswitch (t.kind) {\n\t\tcase PTAParserConstants.LT:\n\t\t\tconstrs.add(Constraint.buildLt(clock1, val)); break;\n\t\tcase PTAParserConstants.LE:\n\t\t\tconstrs.add(Constraint.buildLeq(clock1, val)); break;\n\t\tcase PTAParserConstants.GT:\n\t\t\tconstrs.add(Constraint.buildGt(clock1, val)); break;\n\t\tcase PTAParserConstants.GE:\n\t\t\tconstrs.add(Constraint.buildGeq(clock1, val)); break;\n\t\tcase PTAParserConstants.EQ:\n\t\t\tconstrs.add(Constraint.buildLeq(clock1, val));\n\t\t\tconstrs.add(Constraint.buildGeq(clock1, val)); break;\n\t\t}\n\t}\n\t| clock2Name=Identifier()\n\t{\n\t\tclock1 = pta.getOrAddClock(clock1Name);\n\t\tclock2 = pta.getOrAddClock(clock2Name);\n\t\tswitch (t.kind) {\n\t\tcase PTAParserConstants.LT:\n\t\t\tconstrs.add(Constraint.buildLt(clock1, clock2)); break;\n\t\tdefault:\n\t\t\tSystem.err.println(\"Error: Unsupported constraint type\"); System.exit(1);\n\t\t}\n\t}\n\t))\n}\n\nHashMap<Integer,Integer> Resets(astPTA pta) :\n{\n\tHashMap<Integer,Integer> resets = new HashMap<Integer,Integer>();\n}\n{\n\t((Reset(pta, resets) (<COMMA> Reset(pta, resets))*)\n\t|\n\t(<NULL>))\n\t{ return resets; }\n}\n\nvoid Reset(astPTA pta, HashMap<Integer,Integer> resets) :\n{\n\tString clockName;\n\tint clock;\n\tint val;\n}\n{\n\t(clockName=Identifier() <EQ> val=Integer())\n\t{\n\t\tclock = pta.getOrAddClock(clockName);\n\t\tresets.put(clock, val);\n\t}\n}\n\ndouble Probability() :\n{\n\tToken t;\n\tdouble d;\n}\n{\n\t(t=<REG_DOUBLE> | t=<REG_INT>)\n\t{ return Double.parseDouble(t.image); }\n}\n\n//-----------------------------------------------------------------------------------\n// Miscellaneous stuff\n//-----------------------------------------------------------------------------------\n\n// Identifier (returns String)\n\nString Identifier() :\n{\n}\n{\n\t<REG_IDENT> { return getToken(0).image; }\n}\n\n// Integer\n\nint Integer() :\n{\n}\n{\n\t<REG_INT> { return Integer.parseInt(getToken(0).image); }\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/pta/parser/PTAParserConstants.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. PTAParserConstants.java */\npackage pta.parser;\n\n\n/**\n * Token literal values and constants.\n * Generated by org.javacc.parser.OtherFilesGen#start()\n */\npublic interface PTAParserConstants {\n\n  /** End of File. */\n  int EOF = 0;\n  /** RegularExpression Id. */\n  int WHITESPACE = 1;\n  /** RegularExpression Id. */\n  int COMMENT = 2;\n  /** RegularExpression Id. */\n  int INIT = 3;\n  /** RegularExpression Id. */\n  int NODE = 4;\n  /** RegularExpression Id. */\n  int NULL = 5;\n  /** RegularExpression Id. */\n  int TRAN = 6;\n  /** RegularExpression Id. */\n  int TRUE = 7;\n  /** RegularExpression Id. */\n  int NOT = 8;\n  /** RegularExpression Id. */\n  int AND = 9;\n  /** RegularExpression Id. */\n  int OR = 10;\n  /** RegularExpression Id. */\n  int IMPLIES = 11;\n  /** RegularExpression Id. */\n  int RARROW = 12;\n  /** RegularExpression Id. */\n  int COLON = 13;\n  /** RegularExpression Id. */\n  int SEMICOLON = 14;\n  /** RegularExpression Id. */\n  int COMMA = 15;\n  /** RegularExpression Id. */\n  int DOTS = 16;\n  /** RegularExpression Id. */\n  int LPARENTH = 17;\n  /** RegularExpression Id. */\n  int RPARENTH = 18;\n  /** RegularExpression Id. */\n  int LBRACKET = 19;\n  /** RegularExpression Id. */\n  int RBRACKET = 20;\n  /** RegularExpression Id. */\n  int LBRACE = 21;\n  /** RegularExpression Id. */\n  int RBRACE = 22;\n  /** RegularExpression Id. */\n  int EQ = 23;\n  /** RegularExpression Id. */\n  int NE = 24;\n  /** RegularExpression Id. */\n  int LT = 25;\n  /** RegularExpression Id. */\n  int GT = 26;\n  /** RegularExpression Id. */\n  int LE = 27;\n  /** RegularExpression Id. */\n  int GE = 28;\n  /** RegularExpression Id. */\n  int PLUS = 29;\n  /** RegularExpression Id. */\n  int MINUS = 30;\n  /** RegularExpression Id. */\n  int TIMES = 31;\n  /** RegularExpression Id. */\n  int DIVIDE = 32;\n  /** RegularExpression Id. */\n  int PRIME = 33;\n  /** RegularExpression Id. */\n  int RENAME = 34;\n  /** RegularExpression Id. */\n  int QMARK = 35;\n  /** RegularExpression Id. */\n  int DQUOTE = 36;\n  /** RegularExpression Id. */\n  int REG_INT = 37;\n  /** RegularExpression Id. */\n  int REG_DOUBLE = 38;\n  /** RegularExpression Id. */\n  int REG_IDENTPRIME = 39;\n  /** RegularExpression Id. */\n  int REG_IDENT = 40;\n  /** RegularExpression Id. */\n  int LEXICAL_ERROR = 41;\n\n  /** Lexical state. */\n  int DEFAULT = 0;\n\n  /** Literal token values. */\n  String[] tokenImage = {\n    \"<EOF>\",\n    \"<WHITESPACE>\",\n    \"<COMMENT>\",\n    \"\\\"init\\\"\",\n    \"\\\"node\\\"\",\n    \"\\\"null\\\"\",\n    \"\\\"tran\\\"\",\n    \"\\\"true\\\"\",\n    \"\\\"!\\\"\",\n    \"\\\"&\\\"\",\n    \"\\\"|\\\"\",\n    \"\\\"=>\\\"\",\n    \"\\\"->\\\"\",\n    \"\\\":\\\"\",\n    \"\\\";\\\"\",\n    \"\\\",\\\"\",\n    \"\\\"..\\\"\",\n    \"\\\"(\\\"\",\n    \"\\\")\\\"\",\n    \"\\\"[\\\"\",\n    \"\\\"]\\\"\",\n    \"\\\"{\\\"\",\n    \"\\\"}\\\"\",\n    \"\\\"=\\\"\",\n    \"\\\"!=\\\"\",\n    \"\\\"<\\\"\",\n    \"\\\">\\\"\",\n    \"\\\"<=\\\"\",\n    \"\\\">=\\\"\",\n    \"\\\"+\\\"\",\n    \"\\\"-\\\"\",\n    \"\\\"*\\\"\",\n    \"\\\"/\\\"\",\n    \"\\\"\\\\\\'\\\"\",\n    \"\\\"<-\\\"\",\n    \"\\\"?\\\"\",\n    \"\\\"\\\\\\\"\\\"\",\n    \"<REG_INT>\",\n    \"<REG_DOUBLE>\",\n    \"<REG_IDENTPRIME>\",\n    \"<REG_IDENT>\",\n    \"<LEXICAL_ERROR>\",\n  };\n\n}\n"
  },
  {
    "path": "prism/src/pta/parser/PTAParserTokenManager.java",
    "content": "/* PTAParserTokenManager.java */\n/* Generated By:JavaCC: Do not edit this line. PTAParserTokenManager.java */\npackage pta.parser;\nimport java.io.*;\nimport java.util.*;\nimport pta.*;\nimport prism.PrismLangException;\n\n/** Token Manager. */\n@SuppressWarnings(\"unused\")public class PTAParserTokenManager implements PTAParserConstants {\n\n  /** Debug output. */\n  public static  java.io.PrintStream debugStream = System.out;\n  /** Set debug output. */\n  public static  void setDebugStream(java.io.PrintStream ds) { debugStream = ds; }\nprivate static final int jjStopStringLiteralDfa_0(int pos, long active0){\n   switch (pos)\n   {\n      case 0:\n         if ((active0 & 0x10000L) != 0L)\n            return 10;\n         if ((active0 & 0xf8L) != 0L)\n         {\n            jjmatchedKind = 40;\n            return 19;\n         }\n         return -1;\n      case 1:\n         if ((active0 & 0xf8L) != 0L)\n         {\n            jjmatchedKind = 40;\n            jjmatchedPos = 1;\n            return 19;\n         }\n         return -1;\n      case 2:\n         if ((active0 & 0xf8L) != 0L)\n         {\n            jjmatchedKind = 40;\n            jjmatchedPos = 2;\n            return 19;\n         }\n         return -1;\n      default :\n         return -1;\n   }\n}\nprivate static final int jjStartNfa_0(int pos, long active0){\n   return jjMoveNfa_0(jjStopStringLiteralDfa_0(pos, active0), pos + 1);\n}\nstatic private int jjStopAtPos(int pos, int kind)\n{\n   jjmatchedKind = kind;\n   jjmatchedPos = pos;\n   return pos + 1;\n}\nstatic private int jjMoveStringLiteralDfa0_0(){\n   switch(curChar)\n   {\n      case 33:\n         jjmatchedKind = 8;\n         return jjMoveStringLiteralDfa1_0(0x1000000L);\n      case 34:\n         return jjStopAtPos(0, 36);\n      case 38:\n         return jjStopAtPos(0, 9);\n      case 39:\n         return jjStopAtPos(0, 33);\n      case 40:\n         return jjStopAtPos(0, 17);\n      case 41:\n         return jjStopAtPos(0, 18);\n      case 42:\n         return jjStopAtPos(0, 31);\n      case 43:\n         return jjStopAtPos(0, 29);\n      case 44:\n         return jjStopAtPos(0, 15);\n      case 45:\n         jjmatchedKind = 30;\n         return jjMoveStringLiteralDfa1_0(0x1000L);\n      case 46:\n         return jjMoveStringLiteralDfa1_0(0x10000L);\n      case 47:\n         return jjStopAtPos(0, 32);\n      case 58:\n         return jjStopAtPos(0, 13);\n      case 59:\n         return jjStopAtPos(0, 14);\n      case 60:\n         jjmatchedKind = 25;\n         return jjMoveStringLiteralDfa1_0(0x408000000L);\n      case 61:\n         jjmatchedKind = 23;\n         return jjMoveStringLiteralDfa1_0(0x800L);\n      case 62:\n         jjmatchedKind = 26;\n         return jjMoveStringLiteralDfa1_0(0x10000000L);\n      case 63:\n         return jjStopAtPos(0, 35);\n      case 91:\n         return jjStopAtPos(0, 19);\n      case 93:\n         return jjStopAtPos(0, 20);\n      case 105:\n         return jjMoveStringLiteralDfa1_0(0x8L);\n      case 110:\n         return jjMoveStringLiteralDfa1_0(0x30L);\n      case 116:\n         return jjMoveStringLiteralDfa1_0(0xc0L);\n      case 123:\n         return jjStopAtPos(0, 21);\n      case 124:\n         return jjStopAtPos(0, 10);\n      case 125:\n         return jjStopAtPos(0, 22);\n      default :\n         return jjMoveNfa_0(0, 0);\n   }\n}\nstatic private int jjMoveStringLiteralDfa1_0(long active0){\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(0, active0);\n      return 1;\n   }\n   switch(curChar)\n   {\n      case 45:\n         if ((active0 & 0x400000000L) != 0L)\n            return jjStopAtPos(1, 34);\n         break;\n      case 46:\n         if ((active0 & 0x10000L) != 0L)\n            return jjStopAtPos(1, 16);\n         break;\n      case 61:\n         if ((active0 & 0x1000000L) != 0L)\n            return jjStopAtPos(1, 24);\n         else if ((active0 & 0x8000000L) != 0L)\n            return jjStopAtPos(1, 27);\n         else if ((active0 & 0x10000000L) != 0L)\n            return jjStopAtPos(1, 28);\n         break;\n      case 62:\n         if ((active0 & 0x800L) != 0L)\n            return jjStopAtPos(1, 11);\n         else if ((active0 & 0x1000L) != 0L)\n            return jjStopAtPos(1, 12);\n         break;\n      case 110:\n         return jjMoveStringLiteralDfa2_0(active0, 0x8L);\n      case 111:\n         return jjMoveStringLiteralDfa2_0(active0, 0x10L);\n      case 114:\n         return jjMoveStringLiteralDfa2_0(active0, 0xc0L);\n      case 117:\n         return jjMoveStringLiteralDfa2_0(active0, 0x20L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(0, active0);\n}\nstatic private int jjMoveStringLiteralDfa2_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(0, old0);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(1, active0);\n      return 2;\n   }\n   switch(curChar)\n   {\n      case 97:\n         return jjMoveStringLiteralDfa3_0(active0, 0x40L);\n      case 100:\n         return jjMoveStringLiteralDfa3_0(active0, 0x10L);\n      case 105:\n         return jjMoveStringLiteralDfa3_0(active0, 0x8L);\n      case 108:\n         return jjMoveStringLiteralDfa3_0(active0, 0x20L);\n      case 117:\n         return jjMoveStringLiteralDfa3_0(active0, 0x80L);\n      default :\n         break;\n   }\n   return jjStartNfa_0(1, active0);\n}\nstatic private int jjMoveStringLiteralDfa3_0(long old0, long active0){\n   if (((active0 &= old0)) == 0L)\n      return jjStartNfa_0(1, old0);\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) {\n      jjStopStringLiteralDfa_0(2, active0);\n      return 3;\n   }\n   switch(curChar)\n   {\n      case 101:\n         if ((active0 & 0x10L) != 0L)\n            return jjStartNfaWithStates_0(3, 4, 19);\n         else if ((active0 & 0x80L) != 0L)\n            return jjStartNfaWithStates_0(3, 7, 19);\n         break;\n      case 108:\n         if ((active0 & 0x20L) != 0L)\n            return jjStartNfaWithStates_0(3, 5, 19);\n         break;\n      case 110:\n         if ((active0 & 0x40L) != 0L)\n            return jjStartNfaWithStates_0(3, 6, 19);\n         break;\n      case 116:\n         if ((active0 & 0x8L) != 0L)\n            return jjStartNfaWithStates_0(3, 3, 19);\n         break;\n      default :\n         break;\n   }\n   return jjStartNfa_0(2, active0);\n}\nstatic private int jjStartNfaWithStates_0(int pos, int kind, int state)\n{\n   jjmatchedKind = kind;\n   jjmatchedPos = pos;\n   try { curChar = input_stream.readChar(); }\n   catch(java.io.IOException e) { return pos + 1; }\n   return jjMoveNfa_0(state, pos + 1);\n}\nstatic final long[] jjbitVec0 = {\n   0x0L, 0x0L, 0xffffffffffffffffL, 0xffffffffffffffffL\n};\nstatic private int jjMoveNfa_0(int startState, int curPos)\n{\n   int startsAt = 0;\n   jjnewStateCnt = 19;\n   int i = 1;\n   jjstateSet[0] = startState;\n   int kind = 0x7fffffff;\n   for (;;)\n   {\n      if (++jjround == 0x7fffffff)\n         ReInitRounds();\n      if (curChar < 64)\n      {\n         long l = 1L << curChar;\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 0:\n                  if ((0x3ff000000000000L & l) != 0L)\n                  {\n                     if (kind > 38)\n                        kind = 38;\n                     { jjCheckNAddStates(0, 3); }\n                  }\n                  else if ((0x100002600L & l) != 0L)\n                  {\n                     if (kind > 1)\n                        kind = 1;\n                  }\n                  else if (curChar == 46)\n                     { jjCheckNAdd(10); }\n                  else if (curChar == 35)\n                     { jjCheckNAddStates(4, 6); }\n                  if ((0x3fe000000000000L & l) != 0L)\n                  {\n                     if (kind > 37)\n                        kind = 37;\n                     { jjCheckNAdd(7); }\n                  }\n                  else if (curChar == 48)\n                  {\n                     if (kind > 37)\n                        kind = 37;\n                  }\n                  break;\n               case 19:\n                  if ((0x3ff000000000000L & l) != 0L)\n                  {\n                     if (kind > 40)\n                        kind = 40;\n                     { jjCheckNAdd(18); }\n                  }\n                  else if (curChar == 39)\n                  {\n                     if (kind > 39)\n                        kind = 39;\n                  }\n                  if ((0x3ff000000000000L & l) != 0L)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  break;\n               case 1:\n                  if (curChar == 35)\n                     { jjCheckNAddStates(4, 6); }\n                  break;\n               case 2:\n                  if ((0xffffffffffffdbffL & l) != 0L)\n                     { jjCheckNAddStates(4, 6); }\n                  break;\n               case 3:\n                  if ((0x2400L & l) != 0L && kind > 2)\n                     kind = 2;\n                  break;\n               case 4:\n                  if (curChar == 10 && kind > 2)\n                     kind = 2;\n                  break;\n               case 5:\n                  if (curChar == 13)\n                     jjstateSet[jjnewStateCnt++] = 4;\n                  break;\n               case 6:\n                  if ((0x3fe000000000000L & l) == 0L)\n                     break;\n                  if (kind > 37)\n                     kind = 37;\n                  { jjCheckNAdd(7); }\n                  break;\n               case 7:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 37)\n                     kind = 37;\n                  { jjCheckNAdd(7); }\n                  break;\n               case 8:\n                  if (curChar == 48 && kind > 37)\n                     kind = 37;\n                  break;\n               case 9:\n                  if (curChar == 46)\n                     { jjCheckNAdd(10); }\n                  break;\n               case 10:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 38)\n                     kind = 38;\n                  { jjCheckNAddTwoStates(10, 11); }\n                  break;\n               case 12:\n                  if ((0x280000000000L & l) != 0L)\n                     { jjCheckNAdd(13); }\n                  break;\n               case 13:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 38)\n                     kind = 38;\n                  { jjCheckNAdd(13); }\n                  break;\n               case 14:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 38)\n                     kind = 38;\n                  { jjCheckNAddStates(0, 3); }\n                  break;\n               case 16:\n                  if ((0x3ff000000000000L & l) != 0L)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  break;\n               case 17:\n                  if (curChar == 39 && kind > 39)\n                     kind = 39;\n                  break;\n               case 18:\n                  if ((0x3ff000000000000L & l) == 0L)\n                     break;\n                  if (kind > 40)\n                     kind = 40;\n                  { jjCheckNAdd(18); }\n                  break;\n               default : break;\n            }\n         } while(i != startsAt);\n      }\n      else if (curChar < 128)\n      {\n         long l = 1L << (curChar & 077);\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 0:\n                  if ((0x7fffffe87fffffeL & l) == 0L)\n                     break;\n                  if (kind > 40)\n                     kind = 40;\n                  { jjCheckNAddStates(7, 9); }\n                  break;\n               case 19:\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                  {\n                     if (kind > 40)\n                        kind = 40;\n                     { jjCheckNAdd(18); }\n                  }\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  break;\n               case 2:\n                  { jjAddStates(4, 6); }\n                  break;\n               case 11:\n                  if ((0x2000000020L & l) != 0L)\n                     { jjAddStates(10, 11); }\n                  break;\n               case 16:\n                  if ((0x7fffffe87fffffeL & l) != 0L)\n                     { jjCheckNAddTwoStates(16, 17); }\n                  break;\n               case 18:\n                  if ((0x7fffffe87fffffeL & l) == 0L)\n                     break;\n                  if (kind > 40)\n                     kind = 40;\n                  { jjCheckNAdd(18); }\n                  break;\n               default : break;\n            }\n         } while(i != startsAt);\n      }\n      else\n      {\n         int i2 = (curChar & 0xff) >> 6;\n         long l2 = 1L << (curChar & 077);\n         do\n         {\n            switch(jjstateSet[--i])\n            {\n               case 2:\n                  if ((jjbitVec0[i2] & l2) != 0L)\n                     { jjAddStates(4, 6); }\n                  break;\n               default : break;\n            }\n         } while(i != startsAt);\n      }\n      if (kind != 0x7fffffff)\n      {\n         jjmatchedKind = kind;\n         jjmatchedPos = curPos;\n         kind = 0x7fffffff;\n      }\n      ++curPos;\n      if ((i = jjnewStateCnt) == (startsAt = 19 - (jjnewStateCnt = startsAt)))\n         return curPos;\n      try { curChar = input_stream.readChar(); }\n      catch(java.io.IOException e) { return curPos; }\n   }\n}\nstatic final int[] jjnextStates = {\n   9, 10, 11, 14, 2, 3, 5, 16, 17, 18, 12, 13, \n};\n\n/** Token literal values. */\npublic static final String[] jjstrLiteralImages = {\n\"\", null, null, \"\\151\\156\\151\\164\", \"\\156\\157\\144\\145\", \"\\156\\165\\154\\154\", \n\"\\164\\162\\141\\156\", \"\\164\\162\\165\\145\", \"\\41\", \"\\46\", \"\\174\", \"\\75\\76\", \"\\55\\76\", \"\\72\", \"\\73\", \n\"\\54\", \"\\56\\56\", \"\\50\", \"\\51\", \"\\133\", \"\\135\", \"\\173\", \"\\175\", \"\\75\", \"\\41\\75\", \n\"\\74\", \"\\76\", \"\\74\\75\", \"\\76\\75\", \"\\53\", \"\\55\", \"\\52\", \"\\57\", \"\\47\", \"\\74\\55\", \"\\77\", \n\"\\42\", null, null, null, null, null, };\nstatic protected Token jjFillToken()\n{\n   final Token t;\n   final String curTokenImage;\n   final int beginLine;\n   final int endLine;\n   final int beginColumn;\n   final int endColumn;\n   String im = jjstrLiteralImages[jjmatchedKind];\n   curTokenImage = (im == null) ? input_stream.GetImage() : im;\n   beginLine = input_stream.getBeginLine();\n   beginColumn = input_stream.getBeginColumn();\n   endLine = input_stream.getEndLine();\n   endColumn = input_stream.getEndColumn();\n   t = Token.newToken(jjmatchedKind, curTokenImage);\n\n   t.beginLine = beginLine;\n   t.endLine = endLine;\n   t.beginColumn = beginColumn;\n   t.endColumn = endColumn;\n\n   return t;\n}\n\nstatic int curLexState = 0;\nstatic int defaultLexState = 0;\nstatic int jjnewStateCnt;\nstatic int jjround;\nstatic int jjmatchedPos;\nstatic int jjmatchedKind;\n\n/** Get the next Token. */\npublic static Token getNextToken() \n{\n  Token specialToken = null;\n  Token matchedToken;\n  int curPos = 0;\n\n  EOFLoop :\n  for (;;)\n  {\n   try\n   {\n      curChar = input_stream.BeginToken();\n   }\n   catch(java.io.IOException e)\n   {\n      jjmatchedKind = 0;\n      jjmatchedPos = -1;\n      matchedToken = jjFillToken();\n      matchedToken.specialToken = specialToken;\n      return matchedToken;\n   }\n\n   jjmatchedKind = 0x7fffffff;\n   jjmatchedPos = 0;\n   curPos = jjMoveStringLiteralDfa0_0();\n   if (jjmatchedPos == 0 && jjmatchedKind > 41)\n   {\n      jjmatchedKind = 41;\n   }\n   if (jjmatchedKind != 0x7fffffff)\n   {\n      if (jjmatchedPos + 1 < curPos)\n         input_stream.backup(curPos - jjmatchedPos - 1);\n      if ((jjtoToken[jjmatchedKind >> 6] & (1L << (jjmatchedKind & 077))) != 0L)\n      {\n         matchedToken = jjFillToken();\n         matchedToken.specialToken = specialToken;\n         return matchedToken;\n      }\n      else\n      {\n         if ((jjtoSpecial[jjmatchedKind >> 6] & (1L << (jjmatchedKind & 077))) != 0L)\n         {\n            matchedToken = jjFillToken();\n            if (specialToken == null)\n               specialToken = matchedToken;\n            else\n            {\n               matchedToken.specialToken = specialToken;\n               specialToken = (specialToken.next = matchedToken);\n            }\n         }\n         continue EOFLoop;\n      }\n   }\n   int error_line = input_stream.getEndLine();\n   int error_column = input_stream.getEndColumn();\n   String error_after = null;\n   boolean EOFSeen = false;\n   try { input_stream.readChar(); input_stream.backup(1); }\n   catch (java.io.IOException e1) {\n      EOFSeen = true;\n      error_after = curPos <= 1 ? \"\" : input_stream.GetImage();\n      if (curChar == '\\n' || curChar == '\\r') {\n         error_line++;\n         error_column = 0;\n      }\n      else\n         error_column++;\n   }\n   if (!EOFSeen) {\n      input_stream.backup(1);\n      error_after = curPos <= 1 ? \"\" : input_stream.GetImage();\n   }\n   throw new TokenMgrError(EOFSeen, curLexState, error_line, error_column, error_after, curChar, TokenMgrError.LEXICAL_ERROR);\n  }\n}\n\nstatic private void jjCheckNAdd(int state)\n{\n   if (jjrounds[state] != jjround)\n   {\n      jjstateSet[jjnewStateCnt++] = state;\n      jjrounds[state] = jjround;\n   }\n}\nstatic private void jjAddStates(int start, int end)\n{\n   do {\n      jjstateSet[jjnewStateCnt++] = jjnextStates[start];\n   } while (start++ != end);\n}\nstatic private void jjCheckNAddTwoStates(int state1, int state2)\n{\n   jjCheckNAdd(state1);\n   jjCheckNAdd(state2);\n}\n\nstatic private void jjCheckNAddStates(int start, int end)\n{\n   do {\n      jjCheckNAdd(jjnextStates[start]);\n   } while (start++ != end);\n}\n\n    /** Constructor. */\n    public PTAParserTokenManager(SimpleCharStream stream){\n\n      if (input_stream != null)\n        throw new TokenMgrError(\"ERROR: Second call to constructor of static lexer. You must use ReInit() to initialize the static variables.\", TokenMgrError.STATIC_LEXER_ERROR);\n\n    input_stream = stream;\n  }\n\n  /** Constructor. */\n  public PTAParserTokenManager (SimpleCharStream stream, int lexState){\n    ReInit(stream);\n    SwitchTo(lexState);\n  }\n\n  /** Reinitialise parser. */\n  static public void ReInit(SimpleCharStream stream)\n  {\n    jjmatchedPos = jjnewStateCnt = 0;\n    curLexState = defaultLexState;\n    input_stream = stream;\n    ReInitRounds();\n  }\n\n  static private void ReInitRounds()\n  {\n    int i;\n    jjround = 0x80000001;\n    for (i = 19; i-- > 0;)\n      jjrounds[i] = 0x80000000;\n  }\n\n  /** Reinitialise parser. */\n  static public void ReInit(SimpleCharStream stream, int lexState)\n  {\n    ReInit(stream);\n    SwitchTo(lexState);\n  }\n\n  /** Switch to specified lex state. */\n  static public void SwitchTo(int lexState)\n  {\n    if (lexState >= 1 || lexState < 0)\n      throw new TokenMgrError(\"Error: Ignoring invalid lexical state : \" + lexState + \". State unchanged.\", TokenMgrError.INVALID_LEXICAL_STATE);\n    else\n      curLexState = lexState;\n  }\n\n/** Lexer state names. */\npublic static final String[] lexStateNames = {\n   \"DEFAULT\",\n};\nstatic final long[] jjtoToken = {\n   0x3fffffffff9L, \n};\nstatic final long[] jjtoSkip = {\n   0x6L, \n};\nstatic final long[] jjtoSpecial = {\n   0x6L, \n};\n    static protected SimpleCharStream  input_stream;\n\n    static private final int[] jjrounds = new int[19];\n    static private final int[] jjstateSet = new int[2 * 19];\n\n    \n    static protected char curChar;\n}\n"
  },
  {
    "path": "prism/src/pta/parser/ParseException.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. ParseException.java Version 6.0 */\n/* JavaCCOptions:KEEP_LINE_COL=null */\npackage pta.parser;\n\n/**\n * This exception is thrown when parse errors are encountered.\n * You can explicitly create objects of this exception type by\n * calling the method generateParseException in the generated\n * parser.\n *\n * You can modify this class to customize your error reporting\n * mechanisms so long as you retain the public fields.\n */\npublic class ParseException extends Exception {\n\n  /**\n   * The version identifier for this Serializable class.\n   * Increment only if the <i>serialized</i> form of the\n   * class changes.\n   */\n  private static final long serialVersionUID = 1L;\n\n  /**\n   * This constructor is used by the method \"generateParseException\"\n   * in the generated parser.  Calling this constructor generates\n   * a new object of this type with the fields \"currentToken\",\n   * \"expectedTokenSequences\", and \"tokenImage\" set.\n   */\n  public ParseException(Token currentTokenVal,\n                        int[][] expectedTokenSequencesVal,\n                        String[] tokenImageVal\n                       )\n  {\n    super(initialise(currentTokenVal, expectedTokenSequencesVal, tokenImageVal));\n    currentToken = currentTokenVal;\n    expectedTokenSequences = expectedTokenSequencesVal;\n    tokenImage = tokenImageVal;\n  }\n\n  /**\n   * The following constructors are for use by you for whatever\n   * purpose you can think of.  Constructing the exception in this\n   * manner makes the exception behave in the normal way - i.e., as\n   * documented in the class \"Throwable\".  The fields \"errorToken\",\n   * \"expectedTokenSequences\", and \"tokenImage\" do not contain\n   * relevant information.  The JavaCC generated code does not use\n   * these constructors.\n   */\n\n  public ParseException() {\n    super();\n  }\n\n  /** Constructor with message. */\n  public ParseException(String message) {\n    super(message);\n  }\n\n\n  /**\n   * This is the last token that has been consumed successfully.  If\n   * this object has been created due to a parse error, the token\n   * followng this token will (therefore) be the first error token.\n   */\n  public Token currentToken;\n\n  /**\n   * Each entry in this array is an array of integers.  Each array\n   * of integers represents a sequence of tokens (by their ordinal\n   * values) that is expected at this point of the parse.\n   */\n  public int[][] expectedTokenSequences;\n\n  /**\n   * This is a reference to the \"tokenImage\" array of the generated\n   * parser within which the parse error occurred.  This array is\n   * defined in the generated ...Constants interface.\n   */\n  public String[] tokenImage;\n\n  /**\n   * It uses \"currentToken\" and \"expectedTokenSequences\" to generate a parse\n   * error message and returns it.  If this object has been created\n   * due to a parse error, and you do not catch it (it gets thrown\n   * from the parser) the correct error message\n   * gets displayed.\n   */\n  private static String initialise(Token currentToken,\n                           int[][] expectedTokenSequences,\n                           String[] tokenImage) {\n    String eol = System.getProperty(\"line.separator\", \"\\n\");\n    StringBuffer expected = new StringBuffer();\n    int maxSize = 0;\n    for (int i = 0; i < expectedTokenSequences.length; i++) {\n      if (maxSize < expectedTokenSequences[i].length) {\n        maxSize = expectedTokenSequences[i].length;\n      }\n      for (int j = 0; j < expectedTokenSequences[i].length; j++) {\n        expected.append(tokenImage[expectedTokenSequences[i][j]]).append(' ');\n      }\n      if (expectedTokenSequences[i][expectedTokenSequences[i].length - 1] != 0) {\n        expected.append(\"...\");\n      }\n      expected.append(eol).append(\"    \");\n    }\n    String retval = \"Encountered \\\"\";\n    Token tok = currentToken.next;\n    for (int i = 0; i < maxSize; i++) {\n      if (i != 0) retval += \" \";\n      if (tok.kind == 0) {\n        retval += tokenImage[0];\n        break;\n      }\n      retval += \" \" + tokenImage[tok.kind];\n      retval += \" \\\"\";\n      retval += add_escapes(tok.image);\n      retval += \" \\\"\";\n      tok = tok.next;\n    }\n    retval += \"\\\" at line \" + currentToken.next.beginLine + \", column \" + currentToken.next.beginColumn;\n    retval += \".\" + eol;\n    if (expectedTokenSequences.length == 1) {\n      retval += \"Was expecting:\" + eol + \"    \";\n    } else {\n      retval += \"Was expecting one of:\" + eol + \"    \";\n    }\n    retval += expected.toString();\n    return retval;\n  }\n\n  /**\n   * The end of line string for this machine.\n   */\n  protected String eol = System.getProperty(\"line.separator\", \"\\n\");\n\n  /**\n   * Used to convert raw characters to their escaped version\n   * when these raw version cannot be used as part of an ASCII\n   * string literal.\n   */\n  static String add_escapes(String str) {\n      StringBuffer retval = new StringBuffer();\n      char ch;\n      for (int i = 0; i < str.length(); i++) {\n        switch (str.charAt(i))\n        {\n           case 0 :\n              continue;\n           case '\\b':\n              retval.append(\"\\\\b\");\n              continue;\n           case '\\t':\n              retval.append(\"\\\\t\");\n              continue;\n           case '\\n':\n              retval.append(\"\\\\n\");\n              continue;\n           case '\\f':\n              retval.append(\"\\\\f\");\n              continue;\n           case '\\r':\n              retval.append(\"\\\\r\");\n              continue;\n           case '\\\"':\n              retval.append(\"\\\\\\\"\");\n              continue;\n           case '\\'':\n              retval.append(\"\\\\\\'\");\n              continue;\n           case '\\\\':\n              retval.append(\"\\\\\\\\\");\n              continue;\n           default:\n              if ((ch = str.charAt(i)) < 0x20 || ch > 0x7e) {\n                 String s = \"0000\" + Integer.toString(ch, 16);\n                 retval.append(\"\\\\u\" + s.substring(s.length() - 4, s.length()));\n              } else {\n                 retval.append(ch);\n              }\n              continue;\n        }\n      }\n      return retval.toString();\n   }\n\n}\n/* JavaCC - OriginalChecksum=7c64fc0ab38b25558450547c14c3b451 (do not edit this line) */\n"
  },
  {
    "path": "prism/src/pta/parser/SimpleCharStream.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. SimpleCharStream.java Version 6.0 */\n/* JavaCCOptions:STATIC=true,SUPPORT_CLASS_VISIBILITY_PUBLIC=true */\npackage pta.parser;\n\n/**\n * An implementation of interface CharStream, where the stream is assumed to\n * contain only ASCII characters (without unicode processing).\n */\n\npublic class SimpleCharStream\n{\n/** Whether parser is static. */\n  public static final boolean staticFlag = true;\n  static int bufsize;\n  static int available;\n  static int tokenBegin;\n/** Position in buffer. */\n  static public int bufpos = -1;\n  static protected int bufline[];\n  static protected int bufcolumn[];\n\n  static protected int column = 0;\n  static protected int line = 1;\n\n  static protected boolean prevCharIsCR = false;\n  static protected boolean prevCharIsLF = false;\n\n  static protected java.io.Reader inputStream;\n\n  static protected char[] buffer;\n  static protected int maxNextCharInd = 0;\n  static protected int inBuf = 0;\n  static protected int tabSize = 8;\n  static protected boolean trackLineColumn = true;\n\n  static public void setTabSize(int i) { tabSize = i; }\n  static public int getTabSize() { return tabSize; }\n\n\n  static protected void ExpandBuff(boolean wrapAround)\n  {\n    char[] newbuffer = new char[bufsize + 2048];\n    int newbufline[] = new int[bufsize + 2048];\n    int newbufcolumn[] = new int[bufsize + 2048];\n\n    try\n    {\n      if (wrapAround)\n      {\n        System.arraycopy(buffer, tokenBegin, newbuffer, 0, bufsize - tokenBegin);\n        System.arraycopy(buffer, 0, newbuffer, bufsize - tokenBegin, bufpos);\n        buffer = newbuffer;\n\n        System.arraycopy(bufline, tokenBegin, newbufline, 0, bufsize - tokenBegin);\n        System.arraycopy(bufline, 0, newbufline, bufsize - tokenBegin, bufpos);\n        bufline = newbufline;\n\n        System.arraycopy(bufcolumn, tokenBegin, newbufcolumn, 0, bufsize - tokenBegin);\n        System.arraycopy(bufcolumn, 0, newbufcolumn, bufsize - tokenBegin, bufpos);\n        bufcolumn = newbufcolumn;\n\n        maxNextCharInd = (bufpos += (bufsize - tokenBegin));\n      }\n      else\n      {\n        System.arraycopy(buffer, tokenBegin, newbuffer, 0, bufsize - tokenBegin);\n        buffer = newbuffer;\n\n        System.arraycopy(bufline, tokenBegin, newbufline, 0, bufsize - tokenBegin);\n        bufline = newbufline;\n\n        System.arraycopy(bufcolumn, tokenBegin, newbufcolumn, 0, bufsize - tokenBegin);\n        bufcolumn = newbufcolumn;\n\n        maxNextCharInd = (bufpos -= tokenBegin);\n      }\n    }\n    catch (Throwable t)\n    {\n      throw new Error(t.getMessage());\n    }\n\n\n    bufsize += 2048;\n    available = bufsize;\n    tokenBegin = 0;\n  }\n\n  static protected void FillBuff() throws java.io.IOException\n  {\n    if (maxNextCharInd == available)\n    {\n      if (available == bufsize)\n      {\n        if (tokenBegin > 2048)\n        {\n          bufpos = maxNextCharInd = 0;\n          available = tokenBegin;\n        }\n        else if (tokenBegin < 0)\n          bufpos = maxNextCharInd = 0;\n        else\n          ExpandBuff(false);\n      }\n      else if (available > tokenBegin)\n        available = bufsize;\n      else if ((tokenBegin - available) < 2048)\n        ExpandBuff(true);\n      else\n        available = tokenBegin;\n    }\n\n    int i;\n    try {\n      if ((i = inputStream.read(buffer, maxNextCharInd, available - maxNextCharInd)) == -1)\n      {\n        inputStream.close();\n        throw new java.io.IOException();\n      }\n      else\n        maxNextCharInd += i;\n      return;\n    }\n    catch(java.io.IOException e) {\n      --bufpos;\n      backup(0);\n      if (tokenBegin == -1)\n        tokenBegin = bufpos;\n      throw e;\n    }\n  }\n\n/** Start. */\n  static public char BeginToken() throws java.io.IOException\n  {\n    tokenBegin = -1;\n    char c = readChar();\n    tokenBegin = bufpos;\n\n    return c;\n  }\n\n  static protected void UpdateLineColumn(char c)\n  {\n    column++;\n\n    if (prevCharIsLF)\n    {\n      prevCharIsLF = false;\n      line += (column = 1);\n    }\n    else if (prevCharIsCR)\n    {\n      prevCharIsCR = false;\n      if (c == '\\n')\n      {\n        prevCharIsLF = true;\n      }\n      else\n        line += (column = 1);\n    }\n\n    switch (c)\n    {\n      case '\\r' :\n        prevCharIsCR = true;\n        break;\n      case '\\n' :\n        prevCharIsLF = true;\n        break;\n      case '\\t' :\n        column--;\n        column += (tabSize - (column % tabSize));\n        break;\n      default :\n        break;\n    }\n\n    bufline[bufpos] = line;\n    bufcolumn[bufpos] = column;\n  }\n\n/** Read a character. */\n  static public char readChar() throws java.io.IOException\n  {\n    if (inBuf > 0)\n    {\n      --inBuf;\n\n      if (++bufpos == bufsize)\n        bufpos = 0;\n\n      return buffer[bufpos];\n    }\n\n    if (++bufpos >= maxNextCharInd)\n      FillBuff();\n\n    char c = buffer[bufpos];\n\n    UpdateLineColumn(c);\n    return c;\n  }\n\n  @Deprecated\n  /**\n   * @deprecated\n   * @see #getEndColumn\n   */\n\n  static public int getColumn() {\n    return bufcolumn[bufpos];\n  }\n\n  @Deprecated\n  /**\n   * @deprecated\n   * @see #getEndLine\n   */\n\n  static public int getLine() {\n    return bufline[bufpos];\n  }\n\n  /** Get token end column number. */\n  static public int getEndColumn() {\n    return bufcolumn[bufpos];\n  }\n\n  /** Get token end line number. */\n  static public int getEndLine() {\n     return bufline[bufpos];\n  }\n\n  /** Get token beginning column number. */\n  static public int getBeginColumn() {\n    return bufcolumn[tokenBegin];\n  }\n\n  /** Get token beginning line number. */\n  static public int getBeginLine() {\n    return bufline[tokenBegin];\n  }\n\n/** Backup a number of characters. */\n  static public void backup(int amount) {\n\n    inBuf += amount;\n    if ((bufpos -= amount) < 0)\n      bufpos += bufsize;\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.Reader dstream, int startline,\n  int startcolumn, int buffersize)\n  {\n    if (inputStream != null)\n      throw new Error(\"\\n   ERROR: Second call to the constructor of a static SimpleCharStream.\\n\" +\n      \"       You must either use ReInit() or set the JavaCC option STATIC to false\\n\" +\n      \"       during the generation of this class.\");\n    inputStream = dstream;\n    line = startline;\n    column = startcolumn - 1;\n\n    available = bufsize = buffersize;\n    buffer = new char[buffersize];\n    bufline = new int[buffersize];\n    bufcolumn = new int[buffersize];\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.Reader dstream, int startline,\n                          int startcolumn)\n  {\n    this(dstream, startline, startcolumn, 4096);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.Reader dstream)\n  {\n    this(dstream, 1, 1, 4096);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.Reader dstream, int startline,\n  int startcolumn, int buffersize)\n  {\n    inputStream = dstream;\n    line = startline;\n    column = startcolumn - 1;\n\n    if (buffer == null || buffersize != buffer.length)\n    {\n      available = bufsize = buffersize;\n      buffer = new char[buffersize];\n      bufline = new int[buffersize];\n      bufcolumn = new int[buffersize];\n    }\n    prevCharIsLF = prevCharIsCR = false;\n    tokenBegin = inBuf = maxNextCharInd = 0;\n    bufpos = -1;\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.Reader dstream, int startline,\n                     int startcolumn)\n  {\n    ReInit(dstream, startline, startcolumn, 4096);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.Reader dstream)\n  {\n    ReInit(dstream, 1, 1, 4096);\n  }\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, String encoding, int startline,\n  int startcolumn, int buffersize) throws java.io.UnsupportedEncodingException\n  {\n    this(encoding == null ? new java.io.InputStreamReader(dstream) : new java.io.InputStreamReader(dstream, encoding), startline, startcolumn, buffersize);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, int startline,\n  int startcolumn, int buffersize)\n  {\n    this(new java.io.InputStreamReader(dstream), startline, startcolumn, buffersize);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, String encoding, int startline,\n                          int startcolumn) throws java.io.UnsupportedEncodingException\n  {\n    this(dstream, encoding, startline, startcolumn, 4096);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, int startline,\n                          int startcolumn)\n  {\n    this(dstream, startline, startcolumn, 4096);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream, String encoding) throws java.io.UnsupportedEncodingException\n  {\n    this(dstream, encoding, 1, 1, 4096);\n  }\n\n  /** Constructor. */\n  public SimpleCharStream(java.io.InputStream dstream)\n  {\n    this(dstream, 1, 1, 4096);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, String encoding, int startline,\n                          int startcolumn, int buffersize) throws java.io.UnsupportedEncodingException\n  {\n    ReInit(encoding == null ? new java.io.InputStreamReader(dstream) : new java.io.InputStreamReader(dstream, encoding), startline, startcolumn, buffersize);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, int startline,\n                          int startcolumn, int buffersize)\n  {\n    ReInit(new java.io.InputStreamReader(dstream), startline, startcolumn, buffersize);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, String encoding) throws java.io.UnsupportedEncodingException\n  {\n    ReInit(dstream, encoding, 1, 1, 4096);\n  }\n\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream)\n  {\n    ReInit(dstream, 1, 1, 4096);\n  }\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, String encoding, int startline,\n                     int startcolumn) throws java.io.UnsupportedEncodingException\n  {\n    ReInit(dstream, encoding, startline, startcolumn, 4096);\n  }\n  /** Reinitialise. */\n  public void ReInit(java.io.InputStream dstream, int startline,\n                     int startcolumn)\n  {\n    ReInit(dstream, startline, startcolumn, 4096);\n  }\n  /** Get token literal value. */\n  static public String GetImage()\n  {\n    if (bufpos >= tokenBegin)\n      return new String(buffer, tokenBegin, bufpos - tokenBegin + 1);\n    else\n      return new String(buffer, tokenBegin, bufsize - tokenBegin) +\n                            new String(buffer, 0, bufpos + 1);\n  }\n\n  /** Get the suffix. */\n  static public char[] GetSuffix(int len)\n  {\n    char[] ret = new char[len];\n\n    if ((bufpos + 1) >= len)\n      System.arraycopy(buffer, bufpos - len + 1, ret, 0, len);\n    else\n    {\n      System.arraycopy(buffer, bufsize - (len - bufpos - 1), ret, 0,\n                                                        len - bufpos - 1);\n      System.arraycopy(buffer, 0, ret, len - bufpos - 1, bufpos + 1);\n    }\n\n    return ret;\n  }\n\n  /** Reset buffer when finished. */\n  static public void Done()\n  {\n    buffer = null;\n    bufline = null;\n    bufcolumn = null;\n  }\n\n  /**\n   * Method to adjust line and column numbers for the start of a token.\n   */\n  static public void adjustBeginLineColumn(int newLine, int newCol)\n  {\n    int start = tokenBegin;\n    int len;\n\n    if (bufpos >= tokenBegin)\n    {\n      len = bufpos - tokenBegin + inBuf + 1;\n    }\n    else\n    {\n      len = bufsize - tokenBegin + bufpos + 1 + inBuf;\n    }\n\n    int i = 0, j = 0, k = 0;\n    int nextColDiff = 0, columnDiff = 0;\n\n    while (i < len && bufline[j = start % bufsize] == bufline[k = ++start % bufsize])\n    {\n      bufline[j] = newLine;\n      nextColDiff = columnDiff + bufcolumn[k] - bufcolumn[j];\n      bufcolumn[j] = newCol + columnDiff;\n      columnDiff = nextColDiff;\n      i++;\n    }\n\n    if (i < len)\n    {\n      bufline[j] = newLine++;\n      bufcolumn[j] = newCol + columnDiff;\n\n      while (i++ < len)\n      {\n        if (bufline[j = start % bufsize] != bufline[++start % bufsize])\n          bufline[j] = newLine++;\n        else\n          bufline[j] = newLine;\n      }\n    }\n\n    line = bufline[j];\n    column = bufcolumn[j];\n  }\n\n  static boolean getTrackLineColumn() { return trackLineColumn; }\n  static void setTrackLineColumn(boolean tlc) { trackLineColumn = tlc; }\n}\n/* JavaCC - OriginalChecksum=2c820e3833e159fe44638fac71ff5bb8 (do not edit this line) */\n"
  },
  {
    "path": "prism/src/pta/parser/Token.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. Token.java Version 6.0 */\n/* JavaCCOptions:TOKEN_EXTENDS=,KEEP_LINE_COL=null,SUPPORT_CLASS_VISIBILITY_PUBLIC=true */\npackage pta.parser;\n\n/**\n * Describes the input token stream.\n */\n\npublic class Token implements java.io.Serializable {\n\n  /**\n   * The version identifier for this Serializable class.\n   * Increment only if the <i>serialized</i> form of the\n   * class changes.\n   */\n  private static final long serialVersionUID = 1L;\n\n  /**\n   * An integer that describes the kind of this token.  This numbering\n   * system is determined by JavaCCParser, and a table of these numbers is\n   * stored in the file ...Constants.java.\n   */\n  public int kind;\n\n  /** The line number of the first character of this Token. */\n  public int beginLine;\n  /** The column number of the first character of this Token. */\n  public int beginColumn;\n  /** The line number of the last character of this Token. */\n  public int endLine;\n  /** The column number of the last character of this Token. */\n  public int endColumn;\n\n  /**\n   * The string image of the token.\n   */\n  public String image;\n\n  /**\n   * A reference to the next regular (non-special) token from the input\n   * stream.  If this is the last token from the input stream, or if the\n   * token manager has not read tokens beyond this one, this field is\n   * set to null.  This is true only if this token is also a regular\n   * token.  Otherwise, see below for a description of the contents of\n   * this field.\n   */\n  public Token next;\n\n  /**\n   * This field is used to access special tokens that occur prior to this\n   * token, but after the immediately preceding regular (non-special) token.\n   * If there are no such special tokens, this field is set to null.\n   * When there are more than one such special token, this field refers\n   * to the last of these special tokens, which in turn refers to the next\n   * previous special token through its specialToken field, and so on\n   * until the first special token (whose specialToken field is null).\n   * The next fields of special tokens refer to other special tokens that\n   * immediately follow it (without an intervening regular token).  If there\n   * is no such token, this field is null.\n   */\n  public Token specialToken;\n\n  /**\n   * An optional attribute value of the Token.\n   * Tokens which are not used as syntactic sugar will often contain\n   * meaningful values that will be used later on by the compiler or\n   * interpreter. This attribute value is often different from the image.\n   * Any subclass of Token that actually wants to return a non-null value can\n   * override this method as appropriate.\n   */\n  public Object getValue() {\n    return null;\n  }\n\n  /**\n   * No-argument constructor\n   */\n  public Token() {}\n\n  /**\n   * Constructs a new token for the specified Image.\n   */\n  public Token(int kind)\n  {\n    this(kind, null);\n  }\n\n  /**\n   * Constructs a new token for the specified Image and Kind.\n   */\n  public Token(int kind, String image)\n  {\n    this.kind = kind;\n    this.image = image;\n  }\n\n  /**\n   * Returns the image.\n   */\n  public String toString()\n  {\n    return image;\n  }\n\n  /**\n   * Returns a new Token object, by default. However, if you want, you\n   * can create and return subclass objects based on the value of ofKind.\n   * Simply add the cases to the switch for all those special cases.\n   * For example, if you have a subclass of Token called IDToken that\n   * you want to create if ofKind is ID, simply add something like :\n   *\n   *    case MyParserConstants.ID : return new IDToken(ofKind, image);\n   *\n   * to the following switch statement. Then you can cast matchedToken\n   * variable to the appropriate type and use sit in your lexical actions.\n   */\n  public static Token newToken(int ofKind, String image)\n  {\n    switch(ofKind)\n    {\n      default : return new Token(ofKind, image);\n    }\n  }\n\n  public static Token newToken(int ofKind)\n  {\n    return newToken(ofKind, null);\n  }\n\n}\n/* JavaCC - OriginalChecksum=7324b9615dc37b7f09c5841bfcbd980c (do not edit this line) */\n"
  },
  {
    "path": "prism/src/pta/parser/TokenMgrError.java",
    "content": "/* Generated By:JavaCC: Do not edit this line. TokenMgrError.java Version 6.0 */\n/* JavaCCOptions: */\npackage pta.parser;\n\n/** Token Manager Error. */\npublic class TokenMgrError extends Error\n{\n\n  /**\n   * The version identifier for this Serializable class.\n   * Increment only if the <i>serialized</i> form of the\n   * class changes.\n   */\n  private static final long serialVersionUID = 1L;\n\n  /*\n   * Ordinals for various reasons why an Error of this type can be thrown.\n   */\n\n  /**\n   * Lexical error occurred.\n   */\n  static final int LEXICAL_ERROR = 0;\n\n  /**\n   * An attempt was made to create a second instance of a static token manager.\n   */\n  static final int STATIC_LEXER_ERROR = 1;\n\n  /**\n   * Tried to change to an invalid lexical state.\n   */\n  static final int INVALID_LEXICAL_STATE = 2;\n\n  /**\n   * Detected (and bailed out of) an infinite loop in the token manager.\n   */\n  static final int LOOP_DETECTED = 3;\n\n  /**\n   * Indicates the reason why the exception is thrown. It will have\n   * one of the above 4 values.\n   */\n  int errorCode;\n\n  /**\n   * Replaces unprintable characters by their escaped (or unicode escaped)\n   * equivalents in the given string\n   */\n  protected static final String addEscapes(String str) {\n    StringBuffer retval = new StringBuffer();\n    char ch;\n    for (int i = 0; i < str.length(); i++) {\n      switch (str.charAt(i))\n      {\n        case 0 :\n          continue;\n        case '\\b':\n          retval.append(\"\\\\b\");\n          continue;\n        case '\\t':\n          retval.append(\"\\\\t\");\n          continue;\n        case '\\n':\n          retval.append(\"\\\\n\");\n          continue;\n        case '\\f':\n          retval.append(\"\\\\f\");\n          continue;\n        case '\\r':\n          retval.append(\"\\\\r\");\n          continue;\n        case '\\\"':\n          retval.append(\"\\\\\\\"\");\n          continue;\n        case '\\'':\n          retval.append(\"\\\\\\'\");\n          continue;\n        case '\\\\':\n          retval.append(\"\\\\\\\\\");\n          continue;\n        default:\n          if ((ch = str.charAt(i)) < 0x20 || ch > 0x7e) {\n            String s = \"0000\" + Integer.toString(ch, 16);\n            retval.append(\"\\\\u\" + s.substring(s.length() - 4, s.length()));\n          } else {\n            retval.append(ch);\n          }\n          continue;\n      }\n    }\n    return retval.toString();\n  }\n\n  /**\n   * Returns a detailed message for the Error when it is thrown by the\n   * token manager to indicate a lexical error.\n   * Parameters :\n   *    EOFSeen     : indicates if EOF caused the lexical error\n   *    curLexState : lexical state in which this error occurred\n   *    errorLine   : line number when the error occurred\n   *    errorColumn : column number when the error occurred\n   *    errorAfter  : prefix that was seen before this error occurred\n   *    curchar     : the offending character\n   * Note: You can customize the lexical error message by modifying this method.\n   */\n  protected static String LexicalError(boolean EOFSeen, int lexState, int errorLine, int errorColumn, String errorAfter, char curChar) {\n    return(\"Lexical error at line \" +\n          errorLine + \", column \" +\n          errorColumn + \".  Encountered: \" +\n          (EOFSeen ? \"<EOF> \" : (\"\\\"\" + addEscapes(String.valueOf(curChar)) + \"\\\"\") + \" (\" + (int)curChar + \"), \") +\n          \"after : \\\"\" + addEscapes(errorAfter) + \"\\\"\");\n  }\n\n  /**\n   * You can also modify the body of this method to customize your error messages.\n   * For example, cases like LOOP_DETECTED and INVALID_LEXICAL_STATE are not\n   * of end-users concern, so you can return something like :\n   *\n   *     \"Internal Error : Please file a bug report .... \"\n   *\n   * from this method for such cases in the release version of your parser.\n   */\n  public String getMessage() {\n    return super.getMessage();\n  }\n\n  /*\n   * Constructors of various flavors follow.\n   */\n\n  /** No arg constructor. */\n  public TokenMgrError() {\n  }\n\n  /** Constructor with message and reason. */\n  public TokenMgrError(String message, int reason) {\n    super(message);\n    errorCode = reason;\n  }\n\n  /** Full Constructor. */\n  public TokenMgrError(boolean EOFSeen, int lexState, int errorLine, int errorColumn, String errorAfter, char curChar, int reason) {\n    this(LexicalError(EOFSeen, lexState, errorLine, errorColumn, errorAfter, curChar), reason);\n  }\n}\n/* JavaCC - OriginalChecksum=baf3841bbc9582adae0bb96d10781ed7 (do not edit this line) */\n"
  },
  {
    "path": "prism/src/pta/parser/package-info.java",
    "content": "/**\n * A parser for a simple PTA input language - not used in PRISM.\n */\npackage pta.parser;\n"
  },
  {
    "path": "prism/src/scripts/bump_version.sh",
    "content": "#!/bin/bash\n\n# Usage: src/scripts/bump_version.sh 4.10.2 \"\" (for a clean release)\n# Usage: src/scripts/bump_version.sh 4.10.2 dev\n\nNEW_VERSION=$1\nNEW_SUFFIX=$2\nFILE=\"src/prism/Version.java\"\nVERSION_STRING=\"versionString\"\nSUFFIX_STRING=\"versionSuffixString\"\n\necho \"Current version info:\"\ngrep \"$VERSION_STRING\" \"$FILE\"\ngrep \"$SUFFIX_STRING\" \"$FILE\"\n\nif [ -z \"$NEW_VERSION\" ]; then\n    echo \"Usage: $0 <version-number> <suffix>\"\n    exit 1\nfi\n\necho \"Bumping $FILE to $NEW_VERSION (suffix: '$NEW_SUFFIX')...\"\n\nsed -i \"\" \"s/public static String $VERSION_STRING = \\\".*\\\";/public static String $VERSION_STRING = \\\"$NEW_VERSION\\\";/\" \"$FILE\"\n\nsed -i \"\" \"s/public static String $SUFFIX_STRING = \\\".*\\\";/public static String $SUFFIX_STRING = \\\"$NEW_SUFFIX\\\";/\" \"$FILE\"\n\ngit diff \"$FILE\"\n\n"
  },
  {
    "path": "prism/src/scripts/findjavac.sh",
    "content": "#!/bin/sh\n\n# The detection of javac below can handle cases:\n# - where javac is a symbolic link\n# - where there is actually a chain of symbolic links\n# - where there are relative symbolic links\n# - where some links/files are not called javac (e.g. ecj)\n# - where there are directory names including spaces\n# Note: The code would be simpler if we could rely on\n#       the existence of \"readlink -f\" but we can't.\n\nDETECT_JAVAC=`which javac`\nif [ -f \"$DETECT_JAVAC\" ]; then\n  DETECT_JAVAC_DIR=`dirname \"$DETECT_JAVAC\"`\n  DETECT_JAVAC_EXE=`basename \"$DETECT_JAVAC\"`\n  cd \"$DETECT_JAVAC_DIR\"\n  while [ -h ./\"$DETECT_JAVAC_EXE\" ]; do\n\tDETECT_JAVAC=`readlink ./javac`\n\tDETECT_JAVAC_DIR=`dirname \"$DETECT_JAVAC\"`\n\tDETECT_JAVAC_EXE=`basename \"$DETECT_JAVAC\"`\n\tcd \"$DETECT_JAVAC_DIR\"\n\tDETECT_JAVAC_DIR=`pwd`\n\t#pwd\n  done\n  echo \"$DETECT_JAVAC_DIR\"/\"$DETECT_JAVAC_EXE\"\nfi\n"
  },
  {
    "path": "prism/src/scripts/printversion.sh",
    "content": "#!/bin/sh\n\n# Print the version of PRISM in this directory,\n# based on extraction of the info from Java files.\n# Mirrors what is done (in Java) in prism.getVersion().\n\n# If given, the first argument to the script is assumed\n# to point to the \"src\" directory in a PRISM source\n# distribution. The default is just \"src\".\n\nPRISM_SRC_DIR=\"${1:-src}\"\n\nif [ -f \"$PRISM_SRC_DIR\"/prism/Version.java ]; then\n\tVERSION_NUM=`grep versionString \"$PRISM_SRC_DIR\"/prism/Version.java | sed -E 's/[^\"]+\"([^\"]+)\"[^\"]+/\\1/'`\n\tif [ \"$VERSION_NUM\" != \"\" ]; then\n\t\t/bin/echo -n $VERSION_NUM\n\n\t\tVERSION_SUFFIX=`grep versionSuffixString \"$PRISM_SRC_DIR\"/prism/Version.java | sed -E 's/[^\"]+\"([^\"]*)\"[^\"]+/\\1/'`\n\t\tif [ \"$VERSION_SUFFIX\" != \"\" ]; then\n\t\t\t/bin/echo -n \"-$VERSION_SUFFIX\"\n\t\n\t\tfi\n\t\t/bin/echo\n\telse\n\t\t/bin/echo unknown\n\tfi\nelse\n\t/bin/echo unknown\nfi\n"
  },
  {
    "path": "prism/src/settings/BooleanConstraint.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic abstract class BooleanConstraint implements SettingConstraint\n{\n\t\n\t/** Creates a new instance of BooleanConstraint */\n\tpublic BooleanConstraint()\n\t{\n\t}\n\t\n\tpublic void checkValue(Object value) throws SettingException\n\t{\n\t\tif(value instanceof Boolean)\n\t\t{\n\t\t\tcheckValueBoolean(((Boolean)value).booleanValue());\n\t\t}\n\t\telse\n\t\t{\n\t\t\tthrow new SettingException(\"Invalid type for property, should be a Boolean.\");\n\t\t}\n\t}\n\t\n\tpublic abstract void checkValueBoolean(boolean value) throws SettingException;\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/BooleanEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport java.awt.event.*;\nimport javax.swing.event.*;\nimport java.util.*;\n\npublic class BooleanEditor implements SettingEditor, ActionListener\n{\n\tprivate JCheckBox renderer;\n\tprivate JPanel panel;\n\n\tprivate JTable lastTable = null;\n\tprivate int tableCol = -1;\n\tprivate int tableRow = -1;\n\n\tprivate boolean modified = false;\n\n\tpublic BooleanEditor()\n\t{\n\t\tpanel = new JPanel();\n\t\t//FlowLayout flow = new FlowLayout(FlowLayout.CENTER);\n\t\t//flow.setHgap(0);\n\t\tpanel.setLayout(new BorderLayout());//new GridBagLayout());//flow);//new FlowLayout(FlowLayout.CENTER));\n\t\trenderer = new JCheckBox();\n\t\trenderer.setPreferredSize(new Dimension(17, 12));\n\t\tpanel.add(renderer);\n\t\trenderer.addActionListener(this);\n\t}\n\n\tpublic Object getEditorValue()\n\t{\n\t\tif (modified) {\n\t\t\tmodified = false;\n\t\t\treturn Boolean.valueOf(renderer.isSelected());\n\t\t} else\n\t\t\treturn NOT_CHANGED_VALUE;\n\t}\n\n\tpublic Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n\t{\n\t\tif (isSelected) {\n\t\t\tpanel.setBackground(table.getSelectionBackground());\n\t\t\trenderer.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\tpanel.setBackground(table.getBackground());\n\t\t\trenderer.setBackground(table.getBackground());\n\t\t}\n\n\t\tpanel.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\n\t\tif (value instanceof Boolean) {\n\t\t\tBoolean boo = (Boolean) value;\n\n\t\t\trenderer.setSelected(boo.booleanValue());\n\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tBoolean last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof Boolean) {\n\t\t\t\t\t\tBoolean str = (Boolean) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\trenderer.setSelected(last.booleanValue());\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setSelected(false);\n\t\t\t\t\trenderer.setBackground(Color.lightGray);\n\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\trenderer.setOpaque(true);\n\n\t\tlastTable = table;\n\t\ttableRow = row;\n\t\ttableCol = column;\n\n\t\treturn panel;\n\t}\n\n\tpublic void stopEditing()\n\t{\n\t}\n\n\tpublic void actionPerformed(ActionEvent e)\n\t{\n\t\tmodified = true;\n\t\tif (lastTable != null)\n\t\t\tlastTable.editingStopped(new ChangeEvent(this));\n\t\t//if(lastTable.getCellEditor() != null) lastTable.removeEditor();\n\t\t/*Object obj = getEditorValue();\n\t\t\n\t\tif(lastTable != null)\n\t\t{\n\t\t    lastTable.setValueAt(obj, tableRow, tableCol);\n\t\t}*/\n\t\tlastTable.getSelectionModel().setSelectionInterval(tableRow, tableRow);\n\t\tlastTable.getColumnModel().getSelectionModel().setSelectionInterval(tableCol, tableCol);\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/BooleanRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\npublic class BooleanRenderer implements SettingRenderer\n{\n\tprivate JCheckBox renderer;\n\tprivate JPanel panel;\n\n\tpublic BooleanRenderer()\n\t{\n\t\tpanel = new JPanel();\n\t\t//FlowLayout flow = new FlowLayout(FlowLayout.CENTER);\n\t\t//flow.setHgap(0);\n\t\tpanel.setLayout(new BorderLayout());//new GridBagLayout());//flow);//new FlowLayout(FlowLayout.CENTER));\n\t\trenderer = new JCheckBox();\n\t\trenderer.setPreferredSize(new Dimension(17, 12));\n\t\tpanel.add(renderer);\n\t}\n\n\tpublic Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row,\n\t\t\tint column)\n\t{\n\t\t//renderer.setMargin(new Insets(0, 2, 4, 2));\n\t\tif (isSelected) {\n\t\t\tpanel.setBackground(table.getSelectionBackground());\n\t\t\trenderer.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\tpanel.setBackground(table.getBackground());\n\t\t\trenderer.setBackground(table.getBackground());\n\t\t}\n\n\t\tif (hasFocus) {\n\t\t\tpanel.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t} else {\n\t\t\tpanel.setBorder(new EmptyBorder(1, 2, 2, 1));\n\t\t}\n\n\t\tif (value instanceof Boolean) {\n\t\t\tBoolean boo = (Boolean) value;\n\n\t\t\trenderer.setSelected(boo.booleanValue());\n\n\t\t\trenderer.setEnabled(isEnabled);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tBoolean last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof Boolean) {\n\t\t\t\t\t\tBoolean str = (Boolean) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\trenderer.setSelected(last.booleanValue());\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setSelected(false);\n\t\t\t\t\trenderer.setBackground(Color.lightGray);\n\t\t\t\t\tpanel.setBackground(Color.lightGray);\n\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\t\trenderer.setOpaque(true);\n\n\t\treturn panel;\n\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/BooleanSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic class BooleanSetting extends Setting \n{\n    private static BooleanRenderer renderer;\n    private static BooleanEditor editor;\n\n    /** Creates a new instance of BooleanSetting */\n    public BooleanSetting(String name, Boolean value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n    }\n\t\n\tpublic BooleanSetting(String name, Boolean value, String comment, SettingOwner owner, boolean editableWhenMultiple, BooleanConstraint constraint)\n\t{\n\t\tsuper(name, value, comment, owner, editableWhenMultiple, constraint);\n\t}\n\t\n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n            editor = new BooleanEditor();\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n            renderer = new BooleanRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return Boolean.class;\n    }\n    \n    public boolean getBooleanValue()\n    {\n        return ((Boolean)getValue()).booleanValue();\n    }\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\tif(string.equals(\"true\")) return Boolean.valueOf(true);\n\t\telse if(string.equals(\"false\")) return Boolean.valueOf(false);\n\t\telse throw new SettingException(\"Error when parsing: \"+string+\" as a Boolean value.\");\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\tif(getBooleanValue()) return \"true\";\n\t\telse return \"false\";\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/ChoiceEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.event.*;\nimport java.awt.event.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\npublic class ChoiceEditor implements SettingEditor, ActionListener, FocusListener\n{\n\tprivate Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n\tprivate String[] choices;\n\tprivate JComboBox combo;\n\tprivate JTable lastTable;\n\tprivate boolean modified = false;\n\n\t/** Creates a new instance of ChoiceEditor */\n\tpublic ChoiceEditor(String[] choices)\n\t{\n\t\tcombo = new JComboBox(choices);\n\t\tcombo.addActionListener(this);\n\t\tcombo.addFocusListener(this);\n\t\tthis.choices = choices;\n\t}\n\n\tpublic Object getEditorValue() throws SettingException\n\t{\n\t\tif (modified) {\n\t\t\tmodified = false;\n\t\t\tif (combo.getSelectedItem() != null)\n\t\t\t\treturn combo.getSelectedItem().toString();\n\t\t\telse\n\t\t\t\treturn NOT_CHANGED_VALUE;\n\t\t} else\n\t\t\treturn NOT_CHANGED_VALUE;\n\t}\n\n\tpublic Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n\t{\n\n\t\tif (isSelected) {\n\t\t\tcombo.setForeground(table.getSelectionForeground());\n\t\t\tcombo.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\tcombo.setForeground(table.getForeground());\n\t\t\tcombo.setBackground(table.getBackground());\n\t\t}\n\n\t\tcombo.setBorder(new EmptyBorder(0, 0, 0, 0));//UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n\t\tcombo.setFont(font);\n\t\tcombo.setFocusable(false);\n\n\t\tif (value instanceof String) {\n\t\t\tint index = -1;\n\t\t\tfor (int i = 0; i < choices.length; i++) {\n\t\t\t\tif (choices[i].equals(value.toString())) {\n\t\t\t\t\tindex = i;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tcombo.setSelectedIndex(index);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tString last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof String) {\n\t\t\t\t\t\tString str = (String) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\n\t\t\t\t\tint index = -1;\n\t\t\t\t\tfor (int i = 0; i < choices.length; i++) {\n\t\t\t\t\t\tif (choices[i].equals(last)) {\n\t\t\t\t\t\t\tindex = i;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tcombo.setSelectedIndex(index);\n\t\t\t\t} else {\n\t\t\t\t\tcombo.setSelectedIndex(-1);\n\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\tlastTable = table;\n\t\treturn combo;\n\t}\n\n\tpublic void stopEditing()\n\t{\n\t}\n\n\tpublic void actionPerformed(ActionEvent e)\n\t{\n\t\tmodified = true;\n\t\tif (lastTable != null)\n\t\t\tlastTable.editingStopped(new ChangeEvent(this));\n\t}\n\n\tpublic void focusGained(FocusEvent e)\n\t{\n\t}\n\n\tpublic void focusLost(FocusEvent e)\n\t{\n\t\tif (lastTable.getCellEditor() != null)\n\t\t\tlastTable.removeEditor();\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/ChoiceRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\npublic class ChoiceRenderer implements SettingRenderer\n{\n    private JPanel panel;\n    private JLabel renderer;\n    private Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n    private Font font2 = new Font(\"monospaced\", Font.ITALIC, 12);\n    \n    public ChoiceRenderer()\n    {\n        panel = new JPanel();\n        renderer = new JLabel();\n        \n        panel.setLayout(new BorderLayout());\n        panel.add(renderer, BorderLayout.CENTER);\n    }\n    \n    public Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row, int column)\n    {\n        //renderer.setMargin(new Insets(0, 2, 4, 2));\n        \n        if (isSelected)\n        {\n            renderer.setForeground(table.getSelectionForeground());\n            renderer.setBackground(table.getSelectionBackground());\n            panel.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            renderer.setForeground(table.getForeground());\n            renderer.setBackground(table.getBackground());\n            panel.setBackground(table.getBackground());\n        }\n        \n        if(hasFocus)\n        {\n            renderer.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        }\n        else\n        {\n            renderer.setBorder(new EmptyBorder(1, 2, 2, 1));\n        }\n        \n        if(value instanceof String)\n        {\n            String str = (String)value;\n            \n            renderer.setText(str);\n\n\t    renderer.setEnabled(isEnabled);\n            \n            renderer.setFont(font);\n            \n            \n        }\n        else if(value instanceof ArrayList)\n        {\n\t\t\tArrayList<?> values = (ArrayList<?>)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                String last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof String)\n                    {\n                        String str = (String)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    \n                    renderer.setText(last);\n\n                    renderer.setEnabled(isEnabled);\n            \n                    renderer.setFont(font);\n                }\n                else\n                {\n                    \n                    renderer.setText(\"(Different Values)\");\n\n                    renderer.setEnabled(isEnabled);\n            \n                    renderer.setFont(font2);\n                    \n                    panel.setBackground(Color.lightGray);\n                    \n                   \n                    \n                }\n                \n            }\n        }\n        \n        return panel;\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/settings/ChoiceSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic class ChoiceSetting extends Setting\n{\n    private static ChoiceRenderer renderer;\n\n    private String[]values;\n    /**\n     * Editor for these settings.\n     * It is not static, as we need one editor for each object.\n     * Delayed allocation on first use, so we don't allocate on headless use.\n     */\n    private ChoiceEditor editor;\n    \n    /** Creates a new instance of ChoiceSetting */\n    public ChoiceSetting(String name, String[]values, String value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n        this.values = values;\n    }\n\t\n\tpublic ChoiceSetting(String name, String[]values, String value, String comment, SettingOwner owner, boolean editableWhenMultiple, StringConstraint constraint)\n\t{\n\t\tsuper(name, value, comment, owner, editableWhenMultiple, constraint);\n\t\tthis.values = values;\n\t}\n    \n    public void checkObjectWithConstraints(Object obj) throws SettingException\n    {\n\t\tsuper.checkObjectWithConstraints(obj);\n        boolean valid = false;\n        for(int i = 0; i < values.length; i++)\n        {\n            if(obj.toString().equals(values[i]))\n            {\n                valid = true;\n                break;\n            }\n        }\n        if(!valid) throw new SettingException(\"Invalid Setting: \"+obj.toString()+ \" is not part of the enumeration.\");\n    }\n    \n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n            editor = new ChoiceEditor(values);\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n            renderer = new ChoiceRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return String.class;\n    }\n    \n    public String getStringValue()\n    {\n        return getValue().toString();\n    }\n    \n    public int getCurrentIndex()\n    {\n        for(int i = 0; i < values.length; i++)\n        {\n            if(getValue().toString().equals(values[i]))\n                return i;\n        }\n        return -1;\n    }\n    \n    public void setSelectedIndex(int i) throws SettingException\n    {\n        setValue(values[i]);\n    }\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\treturn string;\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn getStringValue();\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/ColorConstraint.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.awt.Color;\n\npublic abstract class ColorConstraint implements SettingConstraint\n{\n\t\n\t/** Creates a new instance of ColorConstraint */\n\tpublic ColorConstraint()\n\t{\n\t}\n\t\n\tpublic void checkValue(Object value) throws SettingException\n\t{\n\t\tif(value instanceof Color)\n\t\t{\n\t\t\tcheckValueColor((Color)value);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tthrow new SettingException(\"Invalid type for property, should be a Colour.\");\n\t\t}\n\t}\n\t\n\tpublic abstract void checkValueColor(Color col) throws SettingException;\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/ColorEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport java.awt.event.*;\nimport javax.swing.event.*;\nimport java.util.*;\n\npublic class ColorEditor implements SettingEditor, ActionListener, FocusListener\n{\n\tprivate JLabel renderer;\n\tprivate JPanel panel;\n\tprivate Font font = new Font(\"monospaced\", Font.ITALIC, 12);\n\tprivate JPanel colourPanel, blank1, blank2;\n\tprivate JButton button;\n\tprivate JTable lastTable = null;\n\tprivate int tableRow = -1;\n\tprivate int tableCol = -1;\n\n\tprivate boolean dialogFocus = false;\n\n\tprivate boolean modified = false;\n\n\tpublic ColorEditor()\n\t{\n\t\tpanel = new JPanel();\n\t\tpanel.setLayout(new BorderLayout());\n\t\trenderer = new JLabel();\n\n\t\tcolourPanel = new javax.swing.JPanel();\n\t\trenderer = new javax.swing.JLabel();\n\t\tblank2 = new javax.swing.JPanel();\n\t\tblank1 = new javax.swing.JPanel();\n\t\tbutton = new javax.swing.JButton(\"...\");\n\n\t\tbutton.setFont(new Font(\"serif\", Font.PLAIN, 7));\n\n\t\tpanel.add(renderer, BorderLayout.CENTER);\n\t\tblank2.setLayout(new FlowLayout(FlowLayout.CENTER, 0, 0));\n\t\tblank2.setPreferredSize(new Dimension(20, 2));\n\n\t\tcolourPanel.setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0), 1, false));\n\t\tcolourPanel.setPreferredSize(new Dimension(12, 12));\n\n\t\tblank2.add(colourPanel);\n\t\tpanel.add(blank2, BorderLayout.WEST);\n\n\t\tblank1.setLayout(new FlowLayout(FlowLayout.CENTER, 0, 0));\n\t\tblank1.setPreferredSize(new Dimension(18, 2));\n\n\t\tbutton.setPreferredSize(new Dimension(16, 12));\n\t\tblank1.add(button);\n\t\tpanel.add(blank1, BorderLayout.EAST);\n\n\t\tbutton.addActionListener(this);\n\n\t\tbutton.addFocusListener(this);\n\t}\n\n\tpublic Object getEditorValue()\n\t{\n\t\tif (modified) {\n\t\t\tmodified = false;\n\t\t\treturn colourPanel.getBackground();\n\t\t} else {\n\t\t\treturn NOT_CHANGED_VALUE;\n\t\t}\n\t}\n\n\tpublic Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n\t{\n\t\tif (isSelected) {\n\t\t\trenderer.setForeground(table.getSelectionForeground());\n\t\t\tpanel.setBackground(table.getSelectionBackground());\n\t\t\tblank1.setBackground(table.getSelectionBackground());\n\t\t\tblank2.setBackground(table.getSelectionBackground());\n\t\t\tbutton.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\trenderer.setForeground(table.getForeground());\n\t\t\tpanel.setBackground(table.getBackground());\n\t\t\tblank1.setBackground(table.getBackground());\n\t\t\tblank2.setBackground(table.getBackground());\n\t\t\tbutton.setBackground(table.getBackground());\n\t\t}\n\n\t\tpanel.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\n\t\tif (value instanceof Color) {\n\t\t\tColor col = (Color) value;\n\n\t\t\t//System.out.println(\"setting background to \"+col.toString());\n\n\t\t\trenderer.setText(\"[\" + col.getRed() + \",\" + col.getGreen() + \",\" + col.getBlue() + \"]\");\n\n\t\t\trenderer.setFont(font);\n\n\t\t\tcolourPanel.setBackground(col);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tColor last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof Color) {\n\t\t\t\t\t\tColor str = (Color) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\trenderer.setText(\"[\" + last.getRed() + \",\" + last.getGreen() + \",\" + last.getBlue() + \"]\");\n\n\t\t\t\t\trenderer.setFont(font);\n\n\t\t\t\t\tcolourPanel.setBackground(last);\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setText(\"(Different values)\");\n\n\t\t\t\t\trenderer.setFont(font);\n\n\t\t\t\t\tcolourPanel.setBackground(Color.lightGray);\n\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\t\tlastTable = table;\n\t\ttableRow = row;\n\t\ttableCol = column;\n\t\treturn panel;\n\t}\n\n\tpublic void stopEditing()\n\t{\n\t}\n\n\tpublic void actionPerformed(ActionEvent e)\n\t{\n\t\tdialogFocus = true;\n\t\tColor col = JColorChooser.showDialog(lastTable, \"Choose Colour\", colourPanel.getBackground());\n\t\tif (col != null) {\n\t\t\tcolourPanel.setBackground(col);\n\t\t\trenderer.setText(\"[\" + col.getRed() + \",\" + col.getGreen() + \",\" + col.getBlue() + \"]\");\n\n\t\t\tif (lastTable != null) {\n\t\t\t\tpanel.setBackground(lastTable.getBackground());\n\t\t\t\tblank1.setBackground(lastTable.getBackground());\n\t\t\t\tblank2.setBackground(lastTable.getBackground());\n\t\t\t}\n\n\t\t\tif (dialogFocus) {\n\t\t\t\tdialogFocus = false;\n\t\t\t\tif (lastTable != null)\n\t\t\t\t\tlastTable.editingStopped(new ChangeEvent(this));\n\t\t\t} else //must have lost the focus during editing\n\t\t\t{\n\t\t\t\tif (lastTable != null) {\n\t\t\t\t\tlastTable.setValueAt(getEditorValue(), tableRow, tableCol);\n\n\t\t\t\t}\n\t\t\t}\n\t\t\tmodified = true;\n\t\t}\n\t\tif (lastTable != null)\n\t\t\tlastTable.editingStopped(new ChangeEvent(this));\n\t\t//if(lastTable.getCellEditor() != null) lastTable.removeEditor();\n\t}\n\n\tpublic void focusGained(FocusEvent e)\n\t{\n\t}\n\n\tpublic void focusLost(FocusEvent e)\n\t{\n\t\tdialogFocus = false;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/ColorRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\npublic class ColorRenderer implements SettingRenderer\n{\n\tprivate JLabel renderer;\n\tprivate JPanel panel;\n\tprivate Font font = new Font(\"monospaced\", Font.ITALIC, 12);\n\tprivate JPanel colourPanel, blank1, blank2;\n\n\tpublic ColorRenderer()\n\t{\n\t\tpanel = new JPanel();\n\t\tpanel.setLayout(new BorderLayout());\n\t\trenderer = new JLabel();\n\n\t\tcolourPanel = new javax.swing.JPanel();\n\t\trenderer = new javax.swing.JLabel();\n\t\tblank2 = new javax.swing.JPanel();\n\t\tblank1 = new javax.swing.JPanel();\n\n\t\tpanel.add(renderer, BorderLayout.CENTER);\n\t\tblank2.setLayout(new FlowLayout(FlowLayout.CENTER, 0, 0));\n\t\tblank2.setPreferredSize(new Dimension(20, 2));\n\n\t\tcolourPanel.setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0), 1, false));\n\t\tcolourPanel.setPreferredSize(new Dimension(12, 12));\n\n\t\tblank2.add(colourPanel);\n\t\tpanel.add(blank2, BorderLayout.WEST);\n\t}\n\n\tpublic Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row,\n\t\t\tint column)\n\t{\n\t\t//renderer.setMargin(new Insets(0, 2, 4, 2));\n\n\t\tif (isSelected) {\n\t\t\trenderer.setForeground(table.getSelectionForeground());\n\t\t\tpanel.setBackground(table.getSelectionBackground());\n\t\t\tblank1.setBackground(table.getSelectionBackground());\n\t\t\tblank2.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\trenderer.setForeground(table.getForeground());\n\t\t\tpanel.setBackground(table.getBackground());\n\t\t\tblank1.setBackground(table.getBackground());\n\t\t\tblank2.setBackground(table.getBackground());\n\t\t}\n\n\t\tif (hasFocus) {\n\t\t\tpanel.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t} else {\n\t\t\tpanel.setBorder(new EmptyBorder(1, 2, 2, 1));\n\t\t}\n\n\t\tif (value instanceof Color) {\n\t\t\tColor col = (Color) value;\n\n\t\t\t//System.out.println(\"setting background to \"+col.toString());\n\n\t\t\trenderer.setText(\"[\" + col.getRed() + \",\" + col.getGreen() + \",\" + col.getBlue() + \"]\");\n\n\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\trenderer.setFont(font);\n\n\t\t\tcolourPanel.setBackground(col);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tColor last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof Color) {\n\t\t\t\t\t\tColor str = (Color) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\trenderer.setText(\"[\" + last.getRed() + \",\" + last.getGreen() + \",\" + last.getBlue() + \"]\");\n\n\t\t\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\t\t\trenderer.setFont(font);\n\n\t\t\t\t\tcolourPanel.setBackground(last);\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setText(\"(Different values)\");\n\n\t\t\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\t\t\trenderer.setFont(font);\n\n\t\t\t\t\tcolourPanel.setBackground(Color.lightGray);\n\t\t\t\t\tpanel.setBackground(Color.lightGray);\n\t\t\t\t\tblank1.setBackground(Color.lightGray);\n\t\t\t\t\tblank2.setBackground(Color.lightGray);\n\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\treturn panel;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/ColorSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.awt.*;\nimport java.util.*;\n\npublic class ColorSetting extends Setting\n{\n\tprivate static ColorRenderer renderer;\n\tprivate static ColorEditor editor;\n\n\t/** Creates a new instance of ColorSetting */\n\tpublic ColorSetting(String name, Color value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n\t{\n\t\tsuper(name, value, comment, owner, editableWhenMultiple);\n\t}\n\t\n\tpublic ColorSetting(String name, Color value, String comment, SettingOwner owner, boolean editableWhenMultiple, ColorConstraint constraint)\n\t{\n\t\tsuper(name, value, comment, owner, editableWhenMultiple, constraint);\n\t}\n\t\n\t\n\tpublic SettingEditor getSettingEditor()\n\t{\n\t\tif (editor == null) {\n\t\t\teditor = new ColorEditor();\n\t\t}\n\t\treturn editor;\n\t}\n\t\n\tpublic SettingRenderer getSettingRenderer()\n\t{\n\t\tif (renderer == null) {\n\t\t\trenderer = new ColorRenderer();\n\t\t}\n\t\treturn renderer;\n\t}\n\t\n\tpublic Class getValueClass()\n\t{\n\t\treturn Color.class;\n\t}\n\t\n\tpublic Color getColorValue()\n\t{\n\t\treturn (Color)getValue();\n\t}\n\t\n\t/**\n\t *\tParses strings of the form: \"r,g,b\" e.g. \"255,0,255\"\n\t */\n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\ttry\n\t\t{\n\t\t\tint r,g,b;\n\t\t\tStringTokenizer tokens = new StringTokenizer(string, \",\");\n\t\t\tr = Integer.parseInt(tokens.nextToken());\n\t\t\tg = Integer.parseInt(tokens.nextToken());\n\t\t\tb = Integer.parseInt(tokens.nextToken());\n\t\t\treturn new Color(r,g,b);\n\t\t}\n\t\tcatch(NumberFormatException e)\n\t\t{\n\t\t\tthrow new SettingException(\"Error when parsing: \"+string+\" as a Color value.\");\n\t\t}\n\t\tcatch(NoSuchElementException e)\n\t\t{\n\t\t\tthrow new SettingException(\"Error when parsing: \"+string+\" as a Color value.\");\n\t\t}\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\tColor c = getColorValue();\n\t\treturn c.getRed()+\",\"+c.getGreen()+\",\"+c.getBlue();\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/DefaultSettingOwner.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.util.*;\n\n/**\n * DefaultSettingOwners do not have a class and therefore can not be multiple\n */\npublic class DefaultSettingOwner extends Observable implements SettingOwner\n{\n\tprivate String name;\n\tprivate int id;\n\tprivate SettingDisplay display;\n\tprivate ArrayList<Setting> settings;\n\n\t/** Creates a new instance of DefaultSettingOwner */\n\tpublic DefaultSettingOwner(String name, int id)\n\t{\n\t\tthis.name = name;\n\t\tthis.id = id;\n\t\tdisplay = null;\n\t\tsettings = new ArrayList<Setting>();\n\t}\n\n\tpublic int compareTo(Object o)\n\t{\n\t\tif (o instanceof SettingOwner) {\n\t\t\tSettingOwner po = (SettingOwner) o;\n\t\t\tif (getSettingOwnerID() < po.getSettingOwnerID())\n\t\t\t\treturn -1;\n\t\t\telse if (getSettingOwnerID() > po.getSettingOwnerID())\n\t\t\t\treturn 1;\n\t\t\telse\n\t\t\t\treturn 0;\n\t\t} else\n\t\t\treturn 0;\n\t}\n\n\tpublic SettingDisplay getDisplay()\n\t{\n\t\treturn display;\n\t}\n\n\tpublic int getNumSettings()\n\t{\n\t\treturn settings.size();\n\t}\n\n\tpublic Setting getSetting(int index)\n\t{\n\t\treturn settings.get(index);\n\t}\n\n\tpublic String getSettingOwnerClassName()\n\t{\n\t\treturn \"\";\n\t}\n\n\tpublic int getSettingOwnerID()\n\t{\n\t\treturn id;\n\t}\n\n\tpublic String getSettingOwnerName()\n\t{\n\t\treturn name;\n\t}\n\n\tpublic void notifySettingChanged(Setting setting)\n\t{\n\t\tsetChanged();\n\t\tnotifyObservers(setting);\n\t}\n\n\tpublic void setDisplay(SettingDisplay display)\n\t{\n\t\tthis.display = display;\n\t}\n\n\tpublic void addSetting(Setting s)\n\t{\n\t\tsettings.add(s);\n\t}\n\n\tpublic Setting getFromKey(String key)\n\t{\n\t\tfor (int i = 0; i < getNumSettings(); i++) {\n\t\t\tif (getSetting(i).equals(key))\n\t\t\t\treturn getSetting(i);\n\t\t}\n\t\treturn null;\n\t}\n}\n"
  },
  {
    "path": "prism/src/settings/DoubleEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.event.*;\nimport java.awt.event.*;\nimport java.util.*;\n\npublic class DoubleEditor implements SettingEditor, CaretListener, FocusListener\n{\n\tprivate JTextField field;\n\tprivate Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n\tprivate Font font2 = new Font(\"monospaced\", Font.PLAIN, 12);\n\n\tprivate JTable lastTable = null;\n\tprivate int tableCol = -1;\n\tprivate int tableRow = -1;\n\n\tprivate boolean valueGot = true;\n\n\t/** Creates a new instance of SingleLineStringEditor */\n\tpublic DoubleEditor()\n\t{\n\t\tfield = new JTextField();\n\t\tfield.addCaretListener(this);\n\t\tfield.addFocusListener(this);\n\t}\n\n\tpublic Object getEditorValue() throws SettingException\n\t{\n\t\tif (field.getText().equals(\"\"))\n\t\t\treturn NOT_CHANGED_VALUE;\n\t\tvalueGot = true;\n\t\ttry {\n\t\t\treturn Double.valueOf(field.getText());\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new SettingException(\"The value entered is not a valid number.\");\n\t\t}\n\t}\n\n\tpublic Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n\t{\n\t\tfield.setMargin(new Insets(0, 2, 4, 2));\n\t\tif (isSelected) {\n\t\t\tfield.setForeground(table.getSelectionForeground());\n\t\t\tfield.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\tfield.setForeground(table.getForeground());\n\t\t\tfield.setBackground(table.getBackground());\n\t\t}\n\n\t\tfield.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\n\t\tif (value instanceof Double) {\n\t\t\tDouble str = (Double) value;\n\n\t\t\tfield.setText(str.toString());\n\n\t\t\tfield.setCaretColor(Color.black);\n\n\t\t\tfield.setFont(font);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tDouble last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof Double) {\n\t\t\t\t\t\tDouble str = (Double) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\tfield.setText(\"\" + last.doubleValue());\n\n\t\t\t\t\tfield.setFont(font);\n\t\t\t\t} else {\n\t\t\t\t\tfield.setText(\"\");\n\n\t\t\t\t\tfield.setFont(font2);\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\tlastTable = table;\n\t\ttableRow = row;\n\t\ttableCol = column;\n\t\tvalueGot = false;\n\n\t\treturn field;\n\t}\n\n\tpublic void stopEditing()\n\t{\n\t}\n\n\tpublic void caretUpdate(CaretEvent e)\n\t{\n\t\tfield.getCaret().setVisible(true);\n\t}\n\n\tpublic void focusGained(FocusEvent e)\n\t{\n\t}\n\n\tpublic void focusLost(FocusEvent e)\n\t{\n\t\tif (!valueGot && lastTable != null) {\n\t\t\tvalueGot = true;\n\t\t\tObject value;\n\t\t\tif (field.getText().equals(\"\"))\n\t\t\t\tvalue = NOT_CHANGED_VALUE;\n\t\t\telse {\n\t\t\t\ttry {\n\t\t\t\t\tvalue = Double.valueOf(field.getText());\n\t\t\t\t} catch (NumberFormatException ex) {\n\t\t\t\t\tvalue = new SettingException(\"The value entered is not a valid number.\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tlastTable.setValueAt(value, tableRow, tableCol);\n\t\t\tif (lastTable.getCellEditor() != null)\n\t\t\t\tlastTable.removeEditor();\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/DoubleRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\npublic class DoubleRenderer implements SettingRenderer\n{\n\tprivate JTextField renderer = new JTextField();\n\tprivate Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n\tprivate Font font2 = new Font(\"monospaced\", Font.ITALIC, 12);\n\n\tpublic Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row,\n\t\t\tint column)\n\t{\n\t\trenderer.setMargin(new Insets(0, 2, 4, 2));\n\t\tif (isSelected) {\n\t\t\trenderer.setForeground(table.getSelectionForeground());\n\t\t\trenderer.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\trenderer.setForeground(table.getForeground());\n\t\t\trenderer.setBackground(table.getBackground());\n\t\t}\n\n\t\tif (hasFocus) {\n\t\t\trenderer.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t} else {\n\t\t\trenderer.setBorder(new EmptyBorder(1, 2, 2, 1));\n\t\t}\n\n\t\tif (value instanceof Double) {\n\t\t\tDouble dob = (Double) value;\n\n\t\t\trenderer.setText(\"\" + dob.doubleValue());\n\n\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\trenderer.setFont(font);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tDouble last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof Double) {\n\t\t\t\t\t\tDouble str = (Double) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\trenderer.setText(\"\" + last.doubleValue());\n\n\t\t\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\t\t\trenderer.setFont(font);\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setText(\"(Different values)\");\n\n\t\t\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\t\t\trenderer.setFont(font2);\n\n\t\t\t\t\trenderer.setBackground(Color.lightGray);\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\treturn renderer;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/DoubleSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic class DoubleSetting extends Setting \n{\n    private static DoubleRenderer renderer;\n    private static DoubleEditor editor;\n\n    /** Creates a new instance of DoubleSetting */\n    public DoubleSetting(String name, Double value, String comment, SettingOwner owner, boolean editableWhenMultiple, NumericConstraint constraint)\n    {\n        super(name, value, comment, owner, editableWhenMultiple, constraint);\n    }\n    \n    public DoubleSetting(String name, Double value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n    }\n    \n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n            editor = new DoubleEditor();\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n            renderer = new DoubleRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return Double.class;\n    }\n    \n    public double getDoubleValue()\n    {\n        return ((Double)getValue()).doubleValue();\n    }\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\ttry\n\t\t{\n\t\t\treturn Double.valueOf(string);\n\t\t}\n\t\tcatch(NumberFormatException e)\n\t\t{\n\t\t\tthrow new SettingException(\"Error when parsing: \"+string+\" as a Double value.\");\n\t\t}\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"\"+getDoubleValue();\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/FileEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport java.awt.event.*;\nimport javax.swing.event.*;\nimport java.util.*;\nimport java.io.*;\n\nimport userinterface.GUIPrism;\n\npublic class FileEditor implements SettingEditor, ActionListener, FocusListener\n{\n\tprivate JLabel renderer;\n\tprivate JPanel panel;\n\tprivate ImageIcon warningIcon = GUIPrism.getIconFromImage(\"smallError.png\");\n\tprivate JButton button;\n\tprivate JTable lastTable = null;\n\tprivate int tableRow = -1;\n\tprivate int tableCol = -1;\n\tprivate JPanel blank1;\n\tprivate FileSetting lastSetting;\n\tprivate boolean dialogFocus = false;\n\tprivate boolean modified = false;\n\n\tpublic FileEditor()\n\t{\n\t\tpanel = new JPanel();\n\t\tpanel.setLayout(new BorderLayout());\n\t\trenderer = new JLabel();\n\t\trenderer = new javax.swing.JLabel();\n\t\tblank1 = new javax.swing.JPanel();\n\t\tbutton = new javax.swing.JButton(\"...\");\n\t\tbutton.setFont(new Font(\"serif\", Font.PLAIN, 7));\n\t\tpanel.add(renderer, BorderLayout.CENTER);\n\t\tblank1.setLayout(new FlowLayout(FlowLayout.CENTER, 0, 0));\n\t\tblank1.setPreferredSize(new Dimension(18, 2));\n\t\tbutton.setPreferredSize(new Dimension(16, 12));\n\t\tblank1.add(button);\n\t\tpanel.add(blank1, BorderLayout.EAST);\n\t\tbutton.addActionListener(this);\n\t\tbutton.addFocusListener(this);\n\t}\n\n\tpublic Object getEditorValue()\n\t{\n\t\tif (modified) {\n\t\t\tmodified = false;\n\t\t\treturn new File(renderer.getText());\n\t\t} else\n\t\t\treturn NOT_CHANGED_VALUE;\n\t}\n\n\tpublic Component getTableCellEditorComponent(JTable table, Setting setting, Object value, boolean isSelected, int row, int column)\n\t{\n\t\tif (isSelected) {\n\t\t\trenderer.setForeground(table.getSelectionForeground());\n\t\t\trenderer.setBackground(table.getSelectionBackground());\n\t\t\tpanel.setBackground(table.getSelectionBackground());\n\t\t\tblank1.setBackground(table.getSelectionBackground());\n\t\t\tbutton.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\trenderer.setForeground(table.getForeground());\n\t\t\trenderer.setBackground(table.getBackground());\n\t\t\tpanel.setBackground(table.getBackground());\n\t\t\tblank1.setBackground(table.getBackground());\n\t\t\tbutton.setBackground(table.getBackground());\n\t\t}\n\n\t\tpanel.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\n\t\tif (setting instanceof FileSetting) {\n\t\t\tlastSetting = (FileSetting) setting;\n\t\t\tif (!lastSetting.isValidFile()) {\n\t\t\t\trenderer.setIcon(warningIcon);\n\t\t\t} else {\n\t\t\t\trenderer.setIcon(null);\n\t\t\t}\n\t\t}\n\t\tif (value instanceof File) {\n\t\t\tFile file = (File) value;\n\t\t\trenderer.setText(file.toString());\n\t\t\t//renderer.setEnabled(isEnabled);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tFile last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof File) {\n\t\t\t\t\t\tFile str = (File) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\trenderer.setText(last.toString());\n\t\t\t\t\t;\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setText(\"(Different values)\");\n\t\t\t\t\trenderer.setFont(new Font(\"monospaced\", Font.ITALIC, 12));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (setting instanceof FileSetting) {\n\t\t\t\tlastSetting = (FileSetting) setting;\n\t\t\t\tif (!lastSetting.isValidFile()) {\n\t\t\t\t\trenderer.setIcon(warningIcon);\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setIcon(null);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tlastTable = table;\n\t\ttableRow = row;\n\t\ttableCol = column;\n\t\treturn panel;\n\t}\n\n\tpublic void stopEditing()\n\t{\n\t}\n\n\tpublic void actionPerformed(ActionEvent e)\n\t{\n\t\tdialogFocus = true;\n\n\t\tif (lastSetting == null) {\n\t\t\tSystem.out.println(\"lastSetting null\");\n\t\t\treturn;\n\t\t}\n\n\t\tFile newFile = lastSetting.getFileSelector().getFile(null, new File(renderer.getText()));\n\t\tif (newFile != null) {\n\t\t\trenderer.setText(newFile.toString());\n\t\t\tif (dialogFocus) {\n\t\t\t\tdialogFocus = false;\n\t\t\t\tif (lastTable != null)\n\t\t\t\t\tlastTable.editingStopped(new ChangeEvent(this));\n\t\t\t} else //must have lost the focus during editing\n\t\t\t{\n\t\t\t\tif (lastTable != null) {\n\t\t\t\t\tlastTable.setValueAt(getEditorValue(), tableRow, tableCol);\n\t\t\t\t}\n\t\t\t}\n\t\t\tmodified = true;\n\t\t}\n\t\tif (lastTable != null)\n\t\t\tlastTable.editingStopped(new ChangeEvent(this));\n\t}\n\n\tpublic void focusGained(FocusEvent e)\n\t{\n\t}\n\n\tpublic void focusLost(FocusEvent e)\n\t{\n\t\tdialogFocus = false;\n\t}\n}\n"
  },
  {
    "path": "prism/src/settings/FileRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.util.*;\nimport java.io.*;\n\nimport userinterface.GUIPrism;\n\npublic class FileRenderer implements SettingRenderer\n{\n\tprivate JLabel renderer;\n\tprivate JPanel panel;\n\tprivate ImageIcon warningIcon = GUIPrism.getIconFromImage(\"smallError.png\");\n\n\tpublic FileRenderer()\n\t{\n\t\tpanel = new JPanel(new BorderLayout());\n\t\trenderer = new JLabel();\n\t\tpanel.add(renderer, BorderLayout.CENTER);\n\t}\n\n\tpublic Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row,\n\t\t\tint column)\n\t{\n\t\t//renderer.setMargin(new Insets(0, 2, 4, 2));\n\n\t\tif (isSelected) {\n\t\t\trenderer.setForeground(table.getSelectionForeground());\n\t\t\tpanel.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\trenderer.setForeground(table.getForeground());\n\t\t\tpanel.setBackground(table.getBackground());\n\t\t}\n\n\t\tif (hasFocus) {\n\t\t\trenderer.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t} else {\n\t\t\trenderer.setBorder(new EmptyBorder(1, 2, 2, 1));\n\t\t}\n\n\t\tif (value instanceof File) {\n\t\t\tFile file = (File) value;\n\t\t\trenderer.setText(file.toString());\n\t\t\trenderer.setEnabled(isEnabled);\n\t\t\tif (owner instanceof FileSetting) {\n\t\t\t\tFileSetting fset = (FileSetting) owner;\n\t\t\t\tif (!fset.isValidFile()) {\n\t\t\t\t\trenderer.setIcon(warningIcon);\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setIcon(null);\n\t\t\t\t}\n\t\t\t}\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tFile last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof File) {\n\t\t\t\t\t\tFile str = (File) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\tFile file = last;\n\t\t\t\t\trenderer.setText(file.toString());\n\t\t\t\t\trenderer.setEnabled(isEnabled);\n\t\t\t\t\tif (owner instanceof FileSetting) {\n\t\t\t\t\t\tFileSetting fset = (FileSetting) owner;\n\t\t\t\t\t\tif (!fset.isValidFile()) {\n\t\t\t\t\t\t\trenderer.setIcon(warningIcon);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\trenderer.setIcon(null);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setText(\"(Different values)\");\n\t\t\t\t\trenderer.setEnabled(isEnabled);\n\t\t\t\t\trenderer.setBackground(Color.lightGray);\n\t\t\t\t\tpanel.setBackground(Color.lightGray);\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\t//sort out the height\n\n\t\treturn panel;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/FileSelector.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.io.*;\nimport java.awt.*;\n\npublic interface FileSelector\n{\n\tpublic File getFile(Frame parent, File defaultFile);\n}\n"
  },
  {
    "path": "prism/src/settings/FileSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.awt.*;\nimport java.io.*;\nimport javax.swing.*;\n\npublic class FileSetting extends Setting \n{\n    private static FileRenderer renderer;\n    private static FileEditor editor;\n    \n\tprivate static FileSelector defaultSelector()\n\t{\n\t\ttry {\n\t\t\treturn new FileSelector()\n\t\t\t{\n\t\t\t\tJFileChooser choose = new JFileChooser();\n\t\t\t\t\n\t\t\t\tpublic File getFile(Frame parent, File defaultFile)\n\t\t\t\t{\n\t\t\t\t\tchoose.setSelectedFile(defaultFile);\n\t\t\t\t\tint choice = choose.showOpenDialog(parent);\n\t\t\t\t\tif(choice == JFileChooser.CANCEL_OPTION) return null;\n\t\t\t\t\telse return choose.getSelectedFile();\n\t\t\t\t\t\n\t\t\t\t}\n\t\t\t};\n\t\t}\n\t\t// Catch any problems that occur when running in headless mode\n\t\t// (e.g. the command-line version of PRISM)\n\t\t// (in this case, you don't need this object anyway)\n\t\tcatch (HeadlessException e) {\n\t\t\treturn null;\n\t\t}\n\t\tcatch (Error e) {\n\t\t\treturn null;\n\t\t}\n\t}\n    \n\tprivate boolean validFile;\n\tprivate FileSelector selector;\n    \n    /** Creates a new instance of FileSetting */\n\tpublic FileSetting(String name, File value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n\t\tif(value != null) validFile = value.isFile();\n\t\telse validFile = false;\n    }\n\t\n    public FileSetting(String name, File value, String comment, SettingOwner owner, boolean editableWhenMultiple, FontColorConstraint constraint)\n    {\n        super(name, value, comment, owner, editableWhenMultiple, constraint);\n\t\tif(value != null) validFile = value.isFile();\n\t\telse validFile = false;\n    }\n\t\n\tpublic void checkObjectWithConstraints(Object obj) throws SettingException\n\t{\n\t\tsuper.checkObjectWithConstraints(obj);\n\t\tif(obj instanceof File)\n\t\t{\n\t\t\tFile f = (File)obj;\n\t\t\tvalidFile = f.isFile();\n\t\t}\n\t\telse \n\t\t\tvalidFile = false;\n\t}\n    \n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n        \teditor = new FileEditor();\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n        \trenderer = new FileRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return File.class;\n    }\n\t\n    public File getFileValue()\n    {\n\t\tif(getValue() != null)\n\t\t\treturn (File)getValue();\n\t\telse return null;\n\t\t\n    }\n\t\n\tpublic boolean isValidFile()\n\t{\n\t\treturn validFile;\n\t}\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\treturn new File(string);\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\tif(getFileValue() == null) return \"\";\n\t\telse\n\t\t{\n\t\t\treturn getFileValue().getPath();\n\t\t}\n\t}\n\t\n\tpublic void setFileSelector(FileSelector selector)\n\t{\n\t\tthis.selector = selector;\n\t}\n\t\n\tpublic FileSelector getFileSelector()\n\t{\n\t\tif (selector == null) {\n\t\t\tselector = defaultSelector();\n\t\t}\n\t\treturn selector;\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/FontChooser.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <Properties>\n    <Property name=\"resizable\" type=\"boolean\" value=\"false\"/>\n  </Properties>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-102,0,0,1,-85\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JTabbedPane\" name=\"theTabs\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"North\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"fontPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Font\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Font\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel35\">\n              <Properties>\n                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[450, 2147483647]\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel36\">\n                  <Properties>\n                    <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[450, 100]\"/>\n                    </Property>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[450, 100]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"Center\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"jPanel37\">\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\"/>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JPanel\" name=\"jPanel38\">\n                          <Properties>\n                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[200, 183]\"/>\n                            </Property>\n                          </Properties>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel39\">\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"North\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Component class=\"javax.swing.JTextField\" name=\"fontBox\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n                                </Component>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel40\">\n                                  <Properties>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 10]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 10]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel41\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"North\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JLabel\" name=\"jLabel4\">\n                                      <Properties>\n                                        <Property name=\"displayedMnemonic\" type=\"int\" value=\"70\"/>\n                                        <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                                          <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                                        </Property>\n                                        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n                                          <ComponentRef name=\"fontList\"/>\n                                        </Property>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Font:\"/>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n                                    </Component>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel42\">\n                                      <Properties>\n                                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"West\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel43\">\n                              <Properties>\n                                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[269, 100]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"Center\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane4\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JList\" name=\"fontList\">\n                                    </Component>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel44\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                        <Container class=\"javax.swing.JPanel\" name=\"jPanel45\">\n                          <Properties>\n                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[100, 163]\"/>\n                            </Property>\n                          </Properties>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel46\">\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel47\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"North\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JTextField\" name=\"styleBox\">\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n                                    </Component>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel48\">\n                                      <Properties>\n                                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"West\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                    </Container>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel49\">\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"North\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                      <SubComponents>\n                                        <Component class=\"javax.swing.JLabel\" name=\"jLabel5\">\n                                          <Properties>\n                                            <Property name=\"displayedMnemonic\" type=\"int\" value=\"121\"/>\n                                            <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                                              <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                                            </Property>\n                                            <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                            <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n                                              <ComponentRef name=\"styleList\"/>\n                                            </Property>\n                                            <Property name=\"text\" type=\"java.lang.String\" value=\"Font style:\"/>\n                                          </Properties>\n                                          <Constraints>\n                                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                              <BorderConstraints direction=\"Center\"/>\n                                            </Constraint>\n                                          </Constraints>\n                                        </Component>\n                                        <Container class=\"javax.swing.JPanel\" name=\"jPanel50\">\n                                          <Properties>\n                                            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                              <Dimension value=\"[5, 10]\"/>\n                                            </Property>\n                                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                              <Dimension value=\"[5, 10]\"/>\n                                            </Property>\n                                          </Properties>\n                                          <Constraints>\n                                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                              <BorderConstraints direction=\"West\"/>\n                                            </Constraint>\n                                          </Constraints>\n\n                                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                        </Container>\n                                      </SubComponents>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel51\">\n                                  <Properties>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[269, 100]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane5\">\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                      <SubComponents>\n                                        <Component class=\"javax.swing.JList\" name=\"styleList\">\n                                        </Component>\n                                      </SubComponents>\n                                    </Container>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel52\">\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"West\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                        <Container class=\"javax.swing.JPanel\" name=\"jPanel53\">\n                          <Properties>\n                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[100, 163]\"/>\n                            </Property>\n                          </Properties>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel54\">\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"North\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Component class=\"javax.swing.JTextField\" name=\"sizeBox\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n                                </Component>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel55\">\n                                  <Properties>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 10]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 10]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel56\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"North\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JLabel\" name=\"jLabel6\">\n                                      <Properties>\n                                        <Property name=\"displayedMnemonic\" type=\"int\" value=\"83\"/>\n                                        <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                                          <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                                        </Property>\n                                        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n                                          <ComponentRef name=\"sizeList\"/>\n                                        </Property>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Size:\"/>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n                                    </Component>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel57\">\n                                      <Properties>\n                                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"West\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel58\">\n                              <Properties>\n                                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[269, 100]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"Center\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane6\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JList\" name=\"sizeList\">\n                                    </Component>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel59\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel60\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Preview\">\n                          <Font PropertyName=\"font\" name=\"Dialog\" size=\"12\" style=\"0\"/>\n                        </TitledBorder>\n                      </Border>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"South\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Component class=\"javax.swing.JLabel\" name=\"previewLabel\">\n                      <Properties>\n                        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                        </Property>\n                        <Property name=\"horizontalAlignment\" type=\"int\" value=\"0\"/>\n                        <Property name=\"text\" type=\"java.lang.String\" value=\"AaBbCcDdEeFf123456789!&quot;£$%^\"/>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n                            <LineBorder/>\n                          </Border>\n                        </Property>\n                        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                          <Dimension value=\"[207, 75]\"/>\n                        </Property>\n                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                          <Dimension value=\"[207, 75]\"/>\n                        </Property>\n                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                          <Dimension value=\"[207, 75]\"/>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"North\"/>\n                        </Constraint>\n                      </Constraints>\n                    </Component>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Component class=\"javax.swing.JColorChooser\" name=\"colorChooser\">\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"4\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Colour\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Colour\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n        </Component>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel32\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n        <Property name=\"columns\" type=\"int\" value=\"0\"/>\n        <Property name=\"rows\" type=\"int\" value=\"1\"/>\n      </Layout>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel33\">\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n            <Property name=\"alignment\" type=\"int\" value=\"0\"/>\n          </Layout>\n          <SubComponents>\n            <Component class=\"javax.swing.JButton\" name=\"defaultButton\">\n              <Properties>\n                <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                  <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                </Property>\n                <Property name=\"mnemonic\" type=\"int\" value=\"68\"/>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Default...\"/>\n              </Properties>\n            </Component>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel34\">\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n            <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n          </Layout>\n          <SubComponents>\n            <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n              <Properties>\n                <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                  <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                </Property>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"OK\"/>\n                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n              </Properties>\n            </Component>\n            <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n              <Properties>\n                <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                  <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                </Property>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n              </Properties>\n            </Component>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/settings/FontChooser.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.awt.*;\nimport javax.swing.*;\nimport javax.swing.event.*;\nimport java.awt.event.*;\n\npublic class FontChooser extends javax.swing.JDialog implements ListSelectionListener, ActionListener, FocusListener, ChangeListener\n{\n    \n    protected Font lastFont;\n    protected Color lastColor;\n    \n    \n    protected Font defaultFont;\n    protected Color defaultColor;\n    \n    protected boolean shouldReturn;\n    \n    \n    /** Creates new form FontChooser */\n    public FontChooser(java.awt.Frame parent)\n    {\n        super(parent, true);\n        initComponents();\n        this.getRootPane().setDefaultButton(okayButton);\n        previewLabel.setBackground(Color.white);\n        doListModels();\n        doListeners();\n        shouldReturn = true;\n\t\tsetLocationRelativeTo(getParent()); // centre\n    }\n    \n    public FontChooser(Dialog parent)\n    {\n        super(parent, true);\n        initComponents();\n        previewLabel.setBackground(Color.white);\n        doListModels();\n        doListeners();\n        shouldReturn = true;\n    }\n    \n    public static FontColorPair getFont(Dialog parent, Font startFont, Color startColor, Font defaultFont, Color defaultColor)\n    {\n        FontChooser choose = new FontChooser(parent);\n        \n        choose.shouldReturn = true;\n        choose.defaultFont = defaultFont;\n        choose.defaultColor = defaultColor;\n        choose.lastColor = startColor;\n        choose.lastFont = startFont;\n        choose.colorChooser.setColor(choose.lastColor);\n        choose.setFont(choose.lastFont);\n        choose.updatePreview();\n        \n        choose.show();\n        \n        FontColorPair pair = new FontColorPair();\n        pair.f = choose.lastFont;\n        pair.c = choose.lastColor;\n        \n        if(choose.shouldReturn)return pair;\n        else return null;\n    }\n    \n    public static FontColorPair getFont(Frame parent, Font startFont, Color startColor, Font defaultFont, Color defaultColor)\n    {\n        FontChooser choose = new FontChooser(parent);\n        \n        choose.shouldReturn = true;\n        choose.defaultFont = defaultFont;\n        choose.defaultColor = defaultColor;\n        choose.lastColor = startColor;\n        choose.lastFont = startFont;\n        choose.colorChooser.setColor(choose.lastColor);\n        choose.setFont(choose.lastFont);\n        choose.updatePreview();\n        \n        choose.show();\n        \n        FontColorPair pair = new FontColorPair();\n        pair.f = choose.lastFont;\n        pair.c = choose.lastColor;\n        \n        if(choose.shouldReturn)return pair;\n        else return null;\n    }\n    \n    private void doListModels()\n    {\n        GraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();\n        String [] allFonts = ge.getAvailableFontFamilyNames();\n        //Font[]allFonts = ge.getAllFonts();\n        String [] styles =\n        { \"Plain\", \"Bold\", \"Italic\", \"Bold Italic\" };\n        String [] sizes =\n        { \"8\",\"9\",\"10\",\"11\",\"12\",\"14\",\"16\",\"18\",\"20\" };\n        \n        DefaultComboBoxModel fontModel = new DefaultComboBoxModel(allFonts);\n        DefaultComboBoxModel styleModel = new DefaultComboBoxModel(styles);\n        DefaultComboBoxModel sizeModel = new DefaultComboBoxModel(sizes);\n        \n        fontList.setModel(fontModel);\n        styleList.setModel(styleModel);\n        sizeList.setModel(sizeModel);\n    }\n    \n    private void doListeners()\n    {\n        fontList.addListSelectionListener(this);\n        styleList.addListSelectionListener(this);\n        sizeList.addListSelectionListener(this);\n        \n        fontBox.addActionListener(this);\n        styleBox.addActionListener(this);\n        sizeBox.addActionListener(this);\n        \n        okayButton.addActionListener(this);\n        cancelButton.addActionListener(this);\n        defaultButton.addActionListener(this);\n        \n        fontPanel.addFocusListener(this);\n        theTabs.addChangeListener(this);\n        \n    }\n    /** This method is called from within the constructor to\n     * initialize the form.\n     * WARNING: Do NOT modify this code. The content of this method is\n     * always regenerated by the Form Editor.\n     */\n    private void initComponents()//GEN-BEGIN:initComponents\n    {\n        theTabs = new javax.swing.JTabbedPane();\n        fontPanel = new javax.swing.JPanel();\n        jPanel35 = new javax.swing.JPanel();\n        jPanel36 = new javax.swing.JPanel();\n        jPanel37 = new javax.swing.JPanel();\n        jPanel38 = new javax.swing.JPanel();\n        jPanel39 = new javax.swing.JPanel();\n        fontBox = new javax.swing.JTextField();\n        jPanel40 = new javax.swing.JPanel();\n        jPanel41 = new javax.swing.JPanel();\n        jLabel4 = new javax.swing.JLabel();\n        jPanel42 = new javax.swing.JPanel();\n        jPanel43 = new javax.swing.JPanel();\n        jScrollPane4 = new javax.swing.JScrollPane();\n        fontList = new javax.swing.JList();\n        jPanel44 = new javax.swing.JPanel();\n        jPanel45 = new javax.swing.JPanel();\n        jPanel46 = new javax.swing.JPanel();\n        jPanel47 = new javax.swing.JPanel();\n        styleBox = new javax.swing.JTextField();\n        jPanel48 = new javax.swing.JPanel();\n        jPanel49 = new javax.swing.JPanel();\n        jLabel5 = new javax.swing.JLabel();\n        jPanel50 = new javax.swing.JPanel();\n        jPanel51 = new javax.swing.JPanel();\n        jScrollPane5 = new javax.swing.JScrollPane();\n        styleList = new javax.swing.JList();\n        jPanel52 = new javax.swing.JPanel();\n        jPanel53 = new javax.swing.JPanel();\n        jPanel54 = new javax.swing.JPanel();\n        sizeBox = new javax.swing.JTextField();\n        jPanel55 = new javax.swing.JPanel();\n        jPanel56 = new javax.swing.JPanel();\n        jLabel6 = new javax.swing.JLabel();\n        jPanel57 = new javax.swing.JPanel();\n        jPanel58 = new javax.swing.JPanel();\n        jScrollPane6 = new javax.swing.JScrollPane();\n        sizeList = new javax.swing.JList();\n        jPanel59 = new javax.swing.JPanel();\n        jPanel60 = new javax.swing.JPanel();\n        previewLabel = new javax.swing.JLabel();\n        colorChooser = new javax.swing.JColorChooser();\n        jPanel32 = new javax.swing.JPanel();\n        jPanel33 = new javax.swing.JPanel();\n        defaultButton = new javax.swing.JButton();\n        jPanel34 = new javax.swing.JPanel();\n        okayButton = new javax.swing.JButton();\n        cancelButton = new javax.swing.JButton();\n\n        setResizable(false);\n        addWindowListener(new java.awt.event.WindowAdapter()\n        {\n            public void windowClosing(java.awt.event.WindowEvent evt)\n            {\n                closeDialog(evt);\n            }\n        });\n\n        fontPanel.setLayout(new java.awt.BorderLayout());\n\n        jPanel35.setLayout(new java.awt.BorderLayout());\n\n        jPanel35.setMaximumSize(new java.awt.Dimension(450, 2147483647));\n        jPanel36.setLayout(new java.awt.BorderLayout());\n\n        jPanel36.setMaximumSize(new java.awt.Dimension(450, 100));\n        jPanel36.setPreferredSize(new java.awt.Dimension(450, 100));\n        jPanel37.setLayout(new javax.swing.BoxLayout(jPanel37, javax.swing.BoxLayout.X_AXIS));\n\n        jPanel38.setLayout(new java.awt.BorderLayout());\n\n        jPanel38.setPreferredSize(new java.awt.Dimension(200, 183));\n        jPanel39.setLayout(new java.awt.BorderLayout());\n\n        jPanel39.add(fontBox, java.awt.BorderLayout.CENTER);\n\n        jPanel40.setMinimumSize(new java.awt.Dimension(5, 10));\n        jPanel40.setPreferredSize(new java.awt.Dimension(5, 10));\n        jPanel39.add(jPanel40, java.awt.BorderLayout.WEST);\n\n        jPanel41.setLayout(new java.awt.BorderLayout());\n\n        jLabel4.setDisplayedMnemonic('F');\n        jLabel4.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n        jLabel4.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel4.setLabelFor(fontList);\n        jLabel4.setText(\"Font:\");\n        jPanel41.add(jLabel4, java.awt.BorderLayout.CENTER);\n\n        jPanel42.setMinimumSize(new java.awt.Dimension(5, 10));\n        jPanel42.setPreferredSize(new java.awt.Dimension(5, 10));\n        jPanel41.add(jPanel42, java.awt.BorderLayout.WEST);\n\n        jPanel39.add(jPanel41, java.awt.BorderLayout.NORTH);\n\n        jPanel38.add(jPanel39, java.awt.BorderLayout.NORTH);\n\n        jPanel43.setLayout(new java.awt.BorderLayout());\n\n        jPanel43.setPreferredSize(new java.awt.Dimension(269, 100));\n        jScrollPane4.setViewportView(fontList);\n\n        jPanel43.add(jScrollPane4, java.awt.BorderLayout.CENTER);\n\n        jPanel43.add(jPanel44, java.awt.BorderLayout.WEST);\n\n        jPanel38.add(jPanel43, java.awt.BorderLayout.CENTER);\n\n        jPanel37.add(jPanel38);\n\n        jPanel45.setLayout(new javax.swing.BoxLayout(jPanel45, javax.swing.BoxLayout.X_AXIS));\n\n        jPanel45.setPreferredSize(new java.awt.Dimension(100, 163));\n        jPanel46.setLayout(new java.awt.BorderLayout());\n\n        jPanel47.setLayout(new java.awt.BorderLayout());\n\n        jPanel47.add(styleBox, java.awt.BorderLayout.CENTER);\n\n        jPanel48.setMinimumSize(new java.awt.Dimension(5, 10));\n        jPanel48.setPreferredSize(new java.awt.Dimension(5, 10));\n        jPanel47.add(jPanel48, java.awt.BorderLayout.WEST);\n\n        jPanel49.setLayout(new java.awt.BorderLayout());\n\n        jLabel5.setDisplayedMnemonic('y');\n        jLabel5.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n        jLabel5.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel5.setLabelFor(styleList);\n        jLabel5.setText(\"Font style:\");\n        jPanel49.add(jLabel5, java.awt.BorderLayout.CENTER);\n\n        jPanel50.setMinimumSize(new java.awt.Dimension(5, 10));\n        jPanel50.setPreferredSize(new java.awt.Dimension(5, 10));\n        jPanel49.add(jPanel50, java.awt.BorderLayout.WEST);\n\n        jPanel47.add(jPanel49, java.awt.BorderLayout.NORTH);\n\n        jPanel46.add(jPanel47, java.awt.BorderLayout.NORTH);\n\n        jPanel51.setLayout(new java.awt.BorderLayout());\n\n        jPanel51.setPreferredSize(new java.awt.Dimension(269, 100));\n        jScrollPane5.setViewportView(styleList);\n\n        jPanel51.add(jScrollPane5, java.awt.BorderLayout.CENTER);\n\n        jPanel51.add(jPanel52, java.awt.BorderLayout.WEST);\n\n        jPanel46.add(jPanel51, java.awt.BorderLayout.CENTER);\n\n        jPanel45.add(jPanel46);\n\n        jPanel37.add(jPanel45);\n\n        jPanel53.setLayout(new java.awt.BorderLayout());\n\n        jPanel53.setPreferredSize(new java.awt.Dimension(100, 163));\n        jPanel54.setLayout(new java.awt.BorderLayout());\n\n        jPanel54.add(sizeBox, java.awt.BorderLayout.CENTER);\n\n        jPanel55.setMinimumSize(new java.awt.Dimension(5, 10));\n        jPanel55.setPreferredSize(new java.awt.Dimension(5, 10));\n        jPanel54.add(jPanel55, java.awt.BorderLayout.WEST);\n\n        jPanel56.setLayout(new java.awt.BorderLayout());\n\n        jLabel6.setDisplayedMnemonic('S');\n        jLabel6.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n        jLabel6.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel6.setLabelFor(sizeList);\n        jLabel6.setText(\"Size:\");\n        jPanel56.add(jLabel6, java.awt.BorderLayout.CENTER);\n\n        jPanel57.setMinimumSize(new java.awt.Dimension(5, 10));\n        jPanel57.setPreferredSize(new java.awt.Dimension(5, 10));\n        jPanel56.add(jPanel57, java.awt.BorderLayout.WEST);\n\n        jPanel54.add(jPanel56, java.awt.BorderLayout.NORTH);\n\n        jPanel53.add(jPanel54, java.awt.BorderLayout.NORTH);\n\n        jPanel58.setLayout(new java.awt.BorderLayout());\n\n        jPanel58.setPreferredSize(new java.awt.Dimension(269, 100));\n        jScrollPane6.setViewportView(sizeList);\n\n        jPanel58.add(jScrollPane6, java.awt.BorderLayout.CENTER);\n\n        jPanel58.add(jPanel59, java.awt.BorderLayout.WEST);\n\n        jPanel53.add(jPanel58, java.awt.BorderLayout.CENTER);\n\n        jPanel37.add(jPanel53);\n\n        jPanel36.add(jPanel37, java.awt.BorderLayout.CENTER);\n\n        jPanel35.add(jPanel36, java.awt.BorderLayout.CENTER);\n\n        jPanel60.setLayout(new java.awt.BorderLayout());\n\n        jPanel60.setBorder(new javax.swing.border.TitledBorder(null, \"Preview\", javax.swing.border.TitledBorder.DEFAULT_JUSTIFICATION, javax.swing.border.TitledBorder.DEFAULT_POSITION, new java.awt.Font(\"Dialog\", 0, 12)));\n        previewLabel.setBackground(new java.awt.Color(255, 255, 255));\n        previewLabel.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);\n        previewLabel.setText(\"AaBbCcDdEeFf123456789!\\\"\\u00a3$%^\");\n        previewLabel.setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0)));\n        previewLabel.setMaximumSize(new java.awt.Dimension(207, 75));\n        previewLabel.setMinimumSize(new java.awt.Dimension(207, 75));\n        previewLabel.setPreferredSize(new java.awt.Dimension(207, 75));\n        jPanel60.add(previewLabel, java.awt.BorderLayout.NORTH);\n\n        jPanel35.add(jPanel60, java.awt.BorderLayout.SOUTH);\n\n        fontPanel.add(jPanel35, java.awt.BorderLayout.CENTER);\n\n        theTabs.addTab(\"Font\", fontPanel);\n\n        theTabs.addTab(\"Colour\", colorChooser);\n\n        getContentPane().add(theTabs, java.awt.BorderLayout.NORTH);\n\n        jPanel32.setLayout(new java.awt.GridLayout(1, 0));\n\n        jPanel33.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.LEFT));\n\n        defaultButton.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n        defaultButton.setMnemonic('D');\n        defaultButton.setText(\"Default...\");\n        jPanel33.add(defaultButton);\n\n        jPanel32.add(jPanel33);\n\n        jPanel34.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n        okayButton.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n        okayButton.setText(\"OK\");\n        okayButton.setMaximumSize(new java.awt.Dimension(89, 25));\n        okayButton.setMinimumSize(new java.awt.Dimension(89, 25));\n        okayButton.setPreferredSize(new java.awt.Dimension(89, 25));\n        jPanel34.add(okayButton);\n\n        cancelButton.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n        cancelButton.setText(\"Cancel\");\n        cancelButton.setMaximumSize(new java.awt.Dimension(89, 25));\n        cancelButton.setMinimumSize(new java.awt.Dimension(89, 25));\n        cancelButton.setPreferredSize(new java.awt.Dimension(89, 25));\n        jPanel34.add(cancelButton);\n\n        jPanel32.add(jPanel34);\n\n        getContentPane().add(jPanel32, java.awt.BorderLayout.SOUTH);\n        \n        pack();\n    }//GEN-END:initComponents\n    \n    /** Closes the dialog */\n    private void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n    {\n        setVisible(false);\n        dispose();\n    }//GEN-LAST:event_closeDialog\n    \n    /**\n     * @param args the command line arguments\n     */\n    public static void main(String args[])\n    {\n        new FontChooser(new javax.swing.JFrame()).show();\n    }\n    \n    public void caretUpdate(CaretEvent e)\n    {/*\n        if(e.getSource() == fontBox)\n        {\n            String str = fontBox.getText();\n            for(int i = 0; i < fontList.getModel().getSize(); i++)\n            {\n                String listStr = (String)fontList.getModel().getElementAt(i);\n                if(listStr.startsWith(str))\n                {\n                    fontList.setSelectedIndex(i);\n                    break;\n                }\n            }\n        }*/\n    }\n    \n    public void actionPerformed(ActionEvent e)\n    {\n        if(e.getSource() == fontBox)\n        {\n            String str = fontBox.getText();\n            for(int i = 0; i < fontList.getModel().getSize(); i++)\n            {\n                String listStr = ((String)fontList.getModel().getElementAt(i)).toLowerCase();\n                \n                if(listStr.startsWith(str.toLowerCase()))\n                {\n                    Object value = fontList.getModel().getElementAt(i);\n                    fontList.setSelectedValue(value, true);\n                    break;\n                }\n            }\n            tempValue = (String)fontList.getSelectedValue();\n            if(tempValue != null)\n            {\n                fontBox.setText(tempValue);\n            }\n            else fontBox.setText(\"\");\n        }\n        else if(e.getSource() == styleBox)\n        {\n            String str = styleBox.getText();\n            for(int i = 0; i < styleList.getModel().getSize(); i++)\n            {\n                String listStr = ((String)styleList.getModel().getElementAt(i)).toLowerCase();\n                \n                if(listStr.startsWith(str.toLowerCase()))\n                {\n                    Object value = styleList.getModel().getElementAt(i);\n                    styleList.setSelectedValue(value, true);\n                    break;\n                }\n            }\n            tempValue = (String)styleList.getSelectedValue();\n            if(tempValue != null)\n            {\n                fontBox.setText(tempValue);\n            }\n            else fontBox.setText(\"\");\n        }\n        else if(e.getSource() == sizeBox)\n        {\n            String str = sizeBox.getText();\n            boolean found = false;\n            for(int i = 0; i < sizeList.getModel().getSize(); i++)\n            {\n                String listStr = ((String)sizeList.getModel().getElementAt(i)).toLowerCase();\n                \n                if(listStr.startsWith(str.toLowerCase()))\n                {\n                    found = true;\n                    Object value = sizeList.getModel().getElementAt(i);\n                    sizeList.setSelectedValue(value, true);\n                    tempValue = (String)sizeList.getSelectedValue();\n                    if(tempValue != null)\n                    {\n                        sizeBox.setText(tempValue);\n                    }\n                    else sizeBox.setText(\"\");\n                    break;\n                }\n            }\n            if(!found)\n            {\n                sizeList.setSelectedIndex(-1);\n            }\n            \n            \n        }\n        else if(e.getSource() == defaultButton)\n        {\n            if(defaultFont != null && defaultColor != null)\n            {\n                setFont(defaultFont);\n                colorChooser.setColor(defaultColor);\n                lastColor = colorChooser.getColor();\n                \n                updatePreview();\n            }\n        }\n        else if(e.getSource() == okayButton)\n        {\n            hide();\n        }\n        else if(e.getSource() == cancelButton)\n        {\n            shouldReturn = false;\n            hide();\n        }\n        \n        if(fontValid())\n        {\n            this.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n            this.lastColor = colorChooser.getColor();\n            \n            updatePreview();\n        }\n    }\n    \n    public String getFontName()\n    {\n        return fontBox.getText();\n    }\n    \n    public int getFontStyle()\n    {\n        int style = Font.PLAIN;\n        switch(styleList.getSelectedIndex())\n        {\n            case 0: style = Font.PLAIN;break;\n            case 1: style = Font.BOLD;break;\n            case 2: style = Font.ITALIC;break;\n            case 3: style = Font.BOLD|Font.ITALIC;\n        }\n        return style;\n    }\n    \n    \n    public int getFontSize()\n    {\n        int size = 12;\n        try\n        {\n            size = Integer.parseInt(sizeBox.getText());\n        }\n        catch(NumberFormatException e)\n        {\n        }\n        return size;\n    }\n    \n    public boolean fontValid()\n    {\n        boolean valid = false;\n        \n        String str = fontBox.getText();\n        for(int i = 0; i < fontList.getModel().getSize(); i++)\n            {\n                String listStr = ((String)fontList.getModel().getElementAt(i)).toLowerCase();\n                \n                if(listStr.startsWith(str.toLowerCase()))\n                {\n                    valid = true;\n                }\n            }\n        if(!valid) return false;\n        \n        return valid;\n    }\n    \n    public void setFont(Font f)\n    {\n        if(f != null)\n        {\n            String str = f.getName();\n            int style = f.getStyle();\n            String size = \"\"+f.getSize();\n            \n            for(int i = 0; i < fontList.getModel().getSize(); i++)\n            {\n                String listStr = ((String)fontList.getModel().getElementAt(i)).toLowerCase();\n                \n                if(listStr.equals(str.toLowerCase()))\n                {\n                    Object value = fontList.getModel().getElementAt(i);\n                    fontList.setSelectedValue(value, true);\n                    fontBox.setText((String)value);\n                    break;\n                }\n            }\n            \n            switch(style)\n            {\n                case Font.PLAIN: styleList.setSelectedIndex(0);break;\n                case Font.ITALIC: styleList.setSelectedIndex(2);break;\n                case Font.BOLD: styleList.setSelectedIndex(1); break;\n                case Font.BOLD | Font.ITALIC: styleList.setSelectedIndex(3); break;\n            }\n            \n            boolean found = false;\n            for(int i = 0; i < sizeList.getModel().getSize(); i++)\n            {\n                String listStr = ((String)sizeList.getModel().getElementAt(i)).toLowerCase();\n                \n                if(listStr.equals(size.toLowerCase()))\n                {\n                    Object value = sizeList.getModel().getElementAt(i);\n                    sizeList.setSelectedValue(value, true);\n                    sizeBox.setText((String)value);\n                    found = true;\n                    break;\n                }\n            }\n            if(!found)\n            {\n                sizeBox.setText(size);\n            }\n            \n        }\n    }\n    \n    String tempValue;\n    public void valueChanged(ListSelectionEvent e)\n    {\n        if(e.getSource() == fontList)\n        {\n            tempValue = (String)fontList.getSelectedValue();\n            if(tempValue != null)\n            {\n                fontBox.setText(tempValue);\n            }\n            else fontBox.setText(\"\");\n        }\n        else if(e.getSource() == styleList)\n        {\n            tempValue = (String)styleList.getSelectedValue();\n            if(tempValue != null)\n            {\n                styleBox.setText(tempValue);\n            }\n            else styleBox.setText(\"\");\n        }\n        else if(e.getSource() == sizeList)\n        {\n            tempValue = (String)sizeList.getSelectedValue();\n            if(tempValue != null)\n            {\n                sizeBox.setText(tempValue);\n            }\n            else sizeBox.setText(\"\");\n        }\n        \n        if(fontValid())\n        {\n            this.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n            this.lastColor = colorChooser.getColor();\n            \n            updatePreview();\n        }\n    }\n    \n    public void updatePreview()\n    {\n        if(lastFont != null && lastColor !=null)\n        {\n            previewLabel.setForeground(lastColor);\n            previewLabel.setFont(lastFont);\n        }\n    }\n    \n    public void focusGained(FocusEvent e)\n    {\n        if(fontValid())\n        {\n            this.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n            this.lastColor = colorChooser.getColor();\n            \n            updatePreview();\n        }\n    }    \n    \n    public void focusLost(FocusEvent e)\n    {\n        if(fontValid())\n        {\n            this.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n            this.lastColor = colorChooser.getColor();\n            \n            updatePreview();\n        }\n    }\n    \n    public void stateChanged(ChangeEvent e)\n    {\n        if(fontValid())\n        {\n            this.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n            this.lastColor = colorChooser.getColor();\n            \n            updatePreview();\n        }\n    }\n    \n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JButton cancelButton;\n    protected javax.swing.JColorChooser colorChooser;\n    private javax.swing.JButton defaultButton;\n    private javax.swing.JTextField fontBox;\n    private javax.swing.JList fontList;\n    private javax.swing.JPanel fontPanel;\n    private javax.swing.JLabel jLabel4;\n    private javax.swing.JLabel jLabel5;\n    private javax.swing.JLabel jLabel6;\n    private javax.swing.JPanel jPanel32;\n    private javax.swing.JPanel jPanel33;\n    private javax.swing.JPanel jPanel34;\n    private javax.swing.JPanel jPanel35;\n    private javax.swing.JPanel jPanel36;\n    private javax.swing.JPanel jPanel37;\n    private javax.swing.JPanel jPanel38;\n    private javax.swing.JPanel jPanel39;\n    private javax.swing.JPanel jPanel40;\n    private javax.swing.JPanel jPanel41;\n    private javax.swing.JPanel jPanel42;\n    private javax.swing.JPanel jPanel43;\n    private javax.swing.JPanel jPanel44;\n    private javax.swing.JPanel jPanel45;\n    private javax.swing.JPanel jPanel46;\n    private javax.swing.JPanel jPanel47;\n    private javax.swing.JPanel jPanel48;\n    private javax.swing.JPanel jPanel49;\n    private javax.swing.JPanel jPanel50;\n    private javax.swing.JPanel jPanel51;\n    private javax.swing.JPanel jPanel52;\n    private javax.swing.JPanel jPanel53;\n    private javax.swing.JPanel jPanel54;\n    private javax.swing.JPanel jPanel55;\n    private javax.swing.JPanel jPanel56;\n    private javax.swing.JPanel jPanel57;\n    private javax.swing.JPanel jPanel58;\n    private javax.swing.JPanel jPanel59;\n    private javax.swing.JPanel jPanel60;\n    private javax.swing.JScrollPane jScrollPane4;\n    private javax.swing.JScrollPane jScrollPane5;\n    private javax.swing.JScrollPane jScrollPane6;\n    private javax.swing.JButton okayButton;\n    private javax.swing.JLabel previewLabel;\n    private javax.swing.JTextField sizeBox;\n    private javax.swing.JList sizeList;\n    private javax.swing.JTextField styleBox;\n    private javax.swing.JList styleList;\n    private javax.swing.JTabbedPane theTabs;\n    // End of variables declaration//GEN-END:variables\n    \n}\n\n\n"
  },
  {
    "path": "prism/src/settings/FontColorConstraint.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic abstract class FontColorConstraint implements SettingConstraint\n{\n\t\n\t/** Creates a new instance of FontColorConstraint */\n\tpublic FontColorConstraint()\n\t{\n\t}\n\t\n\tpublic void checkValue(Object value) throws SettingException\n\t{\n\t\tif(value instanceof FontColorPair)\n\t\t{\n\t\t\tcheckValueFontColor((FontColorPair)value);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tthrow new SettingException(\"Invalid type for property, should be a Font Colour pair.\");\n\t\t}\n\t}\n\t\n\tpublic abstract void checkValueFontColor(FontColorPair col) throws SettingException;\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/FontColorEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport java.awt.event.*;\nimport javax.swing.event.*;\nimport java.util.*;\n\npublic class FontColorEditor implements SettingEditor, ActionListener, FocusListener\n{\n\tprivate JLabel renderer;\n\tprivate JPanel panel;\n\tprivate Font font = new Font(\"monospaced\", Font.ITALIC, 12);\n\tprivate JButton button;\n\tprivate JTable lastTable = null;\n\tprivate int tableRow = -1;\n\tprivate int tableCol = -1;\n\tprivate JPanel blank1;\n\n\tprivate boolean dialogFocus = false;\n\n\tprivate boolean modified = false;\n\n\tpublic FontColorEditor()\n\t{\n\t\tpanel = new JPanel();\n\t\tpanel.setLayout(new BorderLayout());\n\t\trenderer = new JLabel();\n\n\t\trenderer = new javax.swing.JLabel();\n\t\tblank1 = new javax.swing.JPanel();\n\t\tbutton = new javax.swing.JButton(\"...\");\n\n\t\tbutton.setFont(new Font(\"serif\", Font.PLAIN, 7));\n\n\t\tpanel.add(renderer, BorderLayout.CENTER);\n\n\t\tblank1.setLayout(new FlowLayout(FlowLayout.CENTER, 0, 0));\n\n\t\tblank1.setPreferredSize(new Dimension(18, 2));\n\n\t\tbutton.setPreferredSize(new Dimension(16, 12));\n\t\tblank1.add(button);\n\t\tpanel.add(blank1, BorderLayout.EAST);\n\n\t\tbutton.addActionListener(this);\n\n\t\tbutton.addFocusListener(this);\n\t}\n\n\tpublic Object getEditorValue()\n\t{\n\t\tif (modified) {\n\t\t\tmodified = false;\n\t\t\treturn new FontColorPair(renderer.getFont(), renderer.getForeground());\n\t\t} else\n\t\t\treturn NOT_CHANGED_VALUE;\n\t}\n\n\tpublic Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n\t{\n\t\tif (isSelected) {\n\t\t\trenderer.setForeground(table.getSelectionForeground());\n\t\t\trenderer.setBackground(table.getSelectionBackground());\n\t\t\tpanel.setBackground(table.getSelectionBackground());\n\t\t\tblank1.setBackground(table.getSelectionBackground());\n\t\t\tbutton.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\trenderer.setForeground(table.getForeground());\n\t\t\trenderer.setBackground(table.getBackground());\n\t\t\tpanel.setBackground(table.getBackground());\n\t\t\tblank1.setBackground(table.getBackground());\n\t\t\tbutton.setBackground(table.getBackground());\n\t\t}\n\n\t\tpanel.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\n\t\tif (value instanceof FontColorPair) {\n\t\t\tFontColorPair fcp = (FontColorPair) value;\n\n\t\t\trenderer.setForeground(fcp.c);\n\n\t\t\trenderer.setText(fcp.f.getName() + \" \" + fcp.f.getSize());\n\n\t\t\trenderer.setFont(fcp.f);\n\n\t\t\tint heightWanted = Math.max(table.getRowHeight(), fcp.f.getSize() + 3);\n\t\t\t//if(hasFocus) heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n\t\t\tif (heightWanted != table.getRowHeight(row))\n\t\t\t\ttable.setRowHeight(row, heightWanted);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tFontColorPair last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof FontColorPair) {\n\t\t\t\t\t\tFontColorPair str = (FontColorPair) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\trenderer.setForeground(last.c);\n\n\t\t\t\t\trenderer.setText(last.f.getName() + \" \" + last.f.getSize());\n\n\t\t\t\t\trenderer.setFont(last.f);\n\n\t\t\t\t\tint heightWanted = Math.max(table.getRowHeight(), last.f.getSize() + 3);\n\t\t\t\t\t//if(hasFocus) heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n\t\t\t\t\tif (heightWanted != table.getRowHeight(row))\n\t\t\t\t\t\ttable.setRowHeight(row, heightWanted);\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setText(\"(Different values)\");\n\n\t\t\t\t\trenderer.setFont(new Font(\"monospaced\", Font.ITALIC, 12));\n\n\t\t\t\t\tint heightWanted = Math.max(table.getRowHeight(), last.f.getSize() + 3);\n\t\t\t\t\t//if(hasFocus) heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n\t\t\t\t\tif (heightWanted != table.getRowHeight(row))\n\t\t\t\t\t\ttable.setRowHeight(row, heightWanted);\n\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\tlastTable = table;\n\t\ttableRow = row;\n\t\ttableCol = column;\n\t\treturn panel;\n\t}\n\n\tpublic void stopEditing()\n\t{\n\t}\n\n\tpublic void actionPerformed(ActionEvent e)\n\t{\n\t\tdialogFocus = true;\n\t\tFontColorPair fcp = FontChooser.getFont(new Frame(), renderer.getFont(), renderer.getForeground(), font, Color.black);\n\t\tif (fcp != null) {\n\t\t\trenderer.setForeground(fcp.c);\n\n\t\t\trenderer.setText(fcp.f.getName() + \" \" + fcp.f.getSize());\n\n\t\t\trenderer.setFont(fcp.f);\n\n\t\t\tif (dialogFocus) {\n\t\t\t\tdialogFocus = false;\n\t\t\t\tif (lastTable != null)\n\t\t\t\t\tlastTable.editingStopped(new ChangeEvent(this));\n\t\t\t} else //must have lost the focus during editing\n\t\t\t{\n\t\t\t\tif (lastTable != null) {\n\t\t\t\t\tlastTable.setValueAt(getEditorValue(), tableRow, tableCol);\n\t\t\t\t\tint heightWanted = Math.max(lastTable.getRowHeight(), fcp.f.getSize() + 3);\n\t\t\t\t\t//if(hasFocus) heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n\t\t\t\t\tif (heightWanted != lastTable.getRowHeight(tableRow))\n\t\t\t\t\t\tlastTable.setRowHeight(tableRow, heightWanted);\n\t\t\t\t}\n\t\t\t}\n\t\t\tmodified = true;\n\t\t}\n\t\tif (lastTable != null)\n\t\t\tlastTable.editingStopped(new ChangeEvent(this));\n\t}\n\n\tpublic void focusGained(FocusEvent e)\n\t{\n\t}\n\n\tpublic void focusLost(FocusEvent e)\n\t{\n\t\tdialogFocus = false;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/FontColorPair.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.awt.*;\n\npublic class FontColorPair\n    {\n        \n        public FontColorPair(Font f, Color c)\n        {\n            this.f = f;\n            this.c = c;\n        }\n        public FontColorPair()\n        {\n           \n        }\n        public Font f;\n        public Color c;\n    }\n"
  },
  {
    "path": "prism/src/settings/FontColorRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\npublic class FontColorRenderer implements SettingRenderer\n{\n\tprivate JLabel renderer;\n\tprivate JPanel panel;\n\n\tpublic FontColorRenderer()\n\t{\n\t\tpanel = new JPanel(new BorderLayout());\n\t\trenderer = new JLabel();\n\t\tpanel.add(renderer, BorderLayout.CENTER);\n\t}\n\n\tpublic Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row,\n\t\t\tint column)\n\t{\n\t\t//renderer.setMargin(new Insets(0, 2, 4, 2));\n\n\t\tif (isSelected) {\n\t\t\trenderer.setForeground(table.getSelectionForeground());\n\t\t\tpanel.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\trenderer.setForeground(table.getForeground());\n\t\t\tpanel.setBackground(table.getBackground());\n\t\t}\n\n\t\tif (hasFocus) {\n\t\t\trenderer.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t} else {\n\t\t\trenderer.setBorder(new EmptyBorder(1, 2, 2, 1));\n\t\t}\n\n\t\tif (value instanceof FontColorPair) {\n\t\t\tFontColorPair fcp = (FontColorPair) value;\n\n\t\t\trenderer.setForeground(fcp.c);\n\n\t\t\trenderer.setText(fcp.f.getName() + \" \" + fcp.f.getSize());\n\n\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\trenderer.setFont(fcp.f);\n\n\t\t\tint heightWanted = Math.max(table.getRowHeight(), fcp.f.getSize() + 3);\n\t\t\t//if(hasFocus) heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n\t\t\tif (heightWanted != table.getRowHeight(row))\n\t\t\t\ttable.setRowHeight(row, heightWanted);\n\t\t} else if (value instanceof ArrayList) {\n\t\t\tArrayList<?> values = (ArrayList<?>) value;\n\t\t\tif (values.size() > 0) {\n\t\t\t\t//if we have multiple properties selected.\n\t\t\t\tFontColorPair last = null;\n\t\t\t\tboolean allSame = true;\n\t\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\t\tif (values.get(i) instanceof FontColorPair) {\n\t\t\t\t\t\tFontColorPair str = (FontColorPair) values.get(i);\n\t\t\t\t\t\tif (last != null) {\n\t\t\t\t\t\t\tif (!str.equals(last)) {\n\t\t\t\t\t\t\t\tallSame = false;\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tlast = str;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (allSame) {\n\t\t\t\t\trenderer.setForeground(last.c);\n\n\t\t\t\t\trenderer.setText(last.f.getName() + \" \" + last.f.getSize());\n\n\t\t\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\t\t\trenderer.setFont(last.f);\n\n\t\t\t\t\tint heightWanted = Math.max(table.getRowHeight(), last.f.getSize() + 3);\n\t\t\t\t\t//if(hasFocus) heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n\t\t\t\t\tif (heightWanted != table.getRowHeight(row))\n\t\t\t\t\t\ttable.setRowHeight(row, heightWanted);\n\t\t\t\t} else {\n\t\t\t\t\trenderer.setText(\"(Different values)\");\n\n\t\t\t\t\trenderer.setEnabled(isEnabled);\n\n\t\t\t\t\trenderer.setFont(new Font(\"monospaced\", Font.ITALIC, 12));\n\n\t\t\t\t\trenderer.setBackground(Color.lightGray);\n\t\t\t\t\tpanel.setBackground(Color.lightGray);\n\n\t\t\t\t\tint heightWanted = Math.max(table.getRowHeight(), last.f.getSize() + 3);\n\t\t\t\t\t//if(hasFocus) heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n\t\t\t\t\tif (heightWanted != table.getRowHeight(row))\n\t\t\t\t\t\ttable.setRowHeight(row, heightWanted);\n\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\t//sort out the height\n\n\t\treturn panel;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/settings/FontColorSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.util.*;\nimport java.awt.*;\n\npublic class FontColorSetting extends Setting \n{\n    private static FontColorRenderer renderer;\n    private static FontColorEditor editor;\n\n    /** Creates a new instance of FontColorSetting */\n\tpublic FontColorSetting(String name, FontColorPair value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n    }\n\t\n    public FontColorSetting(String name, FontColorPair value, String comment, SettingOwner owner, boolean editableWhenMultiple, FontColorConstraint constraint)\n    {\n        super(name, value, comment, owner, editableWhenMultiple, constraint);\n    }\n    \n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n            editor = new FontColorEditor();\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n            renderer = new FontColorRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return FontColorPair.class;\n    }\n    \n    public FontColorPair getFontColorValue()\n    {\n        return ((FontColorPair)getValue());\n    }\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\ttry\n        {\n            StringTokenizer tokens = new StringTokenizer(string, \",\");\n            String name = tokens.nextToken();\n            int size = Integer.parseInt(tokens.nextToken());\n            int style = Integer.parseInt(tokens.nextToken());\n\t\t\tint r = Integer.parseInt(tokens.nextToken());\n\t\t\tint g = Integer.parseInt(tokens.nextToken());\n\t\t\tint b = Integer.parseInt(tokens.nextToken());\n            \n            return new FontColorPair(new Font(name, style, size), new Color(r,g,b));\n        }\n        catch(NumberFormatException e)\n        {\n            throw new SettingException(\"Error when parsing: \"+string+\" as a FontColorPair value.\");\n        }\n        catch(NoSuchElementException e)\n        {\n            throw new SettingException(\"Error when parsing: \"+string+\" as a FontColorPair value.\");\n        }\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\tColor c = getFontColorValue().c;\n\t\tFont f = getFontColorValue().f;\n\t\t\n\t\treturn f.getName()+\",\"+f.getSize()+\",\"+f.getStyle()+\",\"+c.getRed()+\",\"+c.getGreen()+\",\"+c.getBlue();\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/IntegerEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.event.*;\nimport java.awt.event.*;\nimport java.util.*;\n\npublic class IntegerEditor implements SettingEditor, CaretListener, FocusListener\n{\n    private JTextField field;\n    private Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n    private Font font2 = new Font(\"monospaced\", Font.PLAIN, 12);\n    \n    private JTable lastTable = null;\n    private int tableCol = -1;\n    private int tableRow = -1;\n    \n    private boolean valueGot = true;\n    \n    /** Creates a new instance of SingleLineStringEditor */\n    public IntegerEditor()\n    {\n        field = new JTextField();\n        field.addCaretListener(this);\n        field.addFocusListener(this);\n    }\n    \n    public Object getEditorValue() throws SettingException\n    {\n        if(field.getText().equals(\"\")) return NOT_CHANGED_VALUE;\n        valueGot = true;\n        try\n        {\n            return Integer.valueOf(field.getText());\n        }\n        catch(NumberFormatException e)\n        {\n            throw new SettingException(\"The value entered is not a valid number.\");\n        }\n    }\n    \n    public Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n    {\n        field.setMargin(new Insets(0, 2, 4, 2));\n        if (isSelected)\n        {\n            field.setForeground(table.getSelectionForeground());\n            field.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            field.setForeground(table.getForeground());\n            field.setBackground(table.getBackground());\n        }\n        \n        \n        field.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        \n        \n        if(value instanceof Integer)\n        {\n            Integer str = (Integer)value;\n            \n            field.setText(str.toString());\n            \n            \n            field.setCaretColor(Color.black);\n            \n            field.setFont(font);\n        }\n        else if(value instanceof ArrayList)\n        {\n            ArrayList values = (ArrayList)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                Integer last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof Integer)\n                    {\n                        Integer str = (Integer)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    field.setText(\"\"+last.intValue());\n                    \n                    field.setFont(font);\n                }\n                else\n                {\n                    field.setText(\"\");\n                    \n                    field.setFont(font2);\n                }\n                \n            }\n        }\n        \n        lastTable = table;\n        tableRow = row;\n        tableCol = column;\n        valueGot = false;\n        \n        return field;\n    }\n    \n    public void stopEditing()\n    {\n    }\n    \n    public void caretUpdate(CaretEvent e)\n    {\n        field.getCaret().setVisible(true);\n    }\n    \n    public void focusGained(FocusEvent e)\n    {\n    }\n    \n    public void focusLost(FocusEvent e)\n    {\n        if(!valueGot && lastTable != null)\n        {\n            valueGot = true;\n            Object value;\n            if(field.getText().equals(\"\"))\n                value = NOT_CHANGED_VALUE;\n            else\n            {\n                try\n                {\n                    value = Integer.valueOf(field.getText());\n                }\n                catch(NumberFormatException ex)\n                {\n                    value = new SettingException(\"The value entered is not a valid number.\");\n                }\n            }\n            lastTable.setValueAt(value, tableRow, tableCol);\n            if(lastTable.getCellEditor() != null) lastTable.removeEditor();\n        }\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/settings/IntegerRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.awt.*;\nimport java.util.*;\nimport javax.swing.*;\nimport javax.swing.border.*;\n\npublic class IntegerRenderer implements SettingRenderer\n{\n    private JTextField renderer = new JTextField();\n    private Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n    private Font font2 = new Font(\"monospaced\", Font.ITALIC, 12);\n    \n    \n    public Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row, int column)\n    {\n        renderer.setMargin(new Insets(0, 2, 4, 2));\n        if (isSelected)\n        {\n            renderer.setForeground(table.getSelectionForeground());\n            renderer.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            renderer.setForeground(table.getForeground());\n            renderer.setBackground(table.getBackground());\n        }\n        \n        if(hasFocus)\n        {\n            renderer.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        }\n        else\n        {\n            renderer.setBorder(new EmptyBorder(1, 2, 2, 1));\n        }\n        \n        if(value instanceof Integer)\n        {\n            Integer dob = (Integer)value;\n            \n            renderer.setText(\"\"+dob.intValue());\n\n\t    renderer.setEnabled(isEnabled);\n            \n            renderer.setFont(font);\n        }\n        else if(value instanceof ArrayList)\n        {\n            ArrayList values = (ArrayList)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                Integer last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof Integer)\n                    {\n                        Integer str = (Integer)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    renderer.setText(\"\"+last.intValue());\n\n                    renderer.setEnabled(isEnabled);\n            \n                    renderer.setFont(font);\n                }\n                else\n                {\n                    renderer.setText(\"(Different values)\");\n                    \n                    renderer.setEnabled(isEnabled);\n            \n                    renderer.setFont(font2);\n                    \n                    renderer.setBackground(Color.lightGray);\n                }\n                \n            }\n        }\n        \n        \n        return renderer;\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/settings/IntegerSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic class IntegerSetting extends Setting \n{\n    private static IntegerRenderer renderer;\n    private static IntegerEditor editor;\n\n    /** Creates a new instance of DoubleSetting */\n\tpublic IntegerSetting(String name, Integer value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n    }\n\t\n    public IntegerSetting(String name, Integer value, String comment, SettingOwner owner, boolean editableWhenMultiple, NumericConstraint constraint)\n    {\n        super(name, value, comment, owner, editableWhenMultiple, constraint);\n    }\n    \n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n            editor = new IntegerEditor();\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n            renderer = new IntegerRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return Integer.class;\n    }\n    \n    public int getIntegerValue()\n    {\n        return ((Integer)getValue()).intValue();\n    }\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\ttry\n\t\t{\n\t\t\treturn Integer.valueOf(string);\n\t\t}\n\t\tcatch(NumberFormatException e)\n\t\t{\n\t\t\tthrow new SettingException(\"Error when parsing: \"+string+\" as an Integer value.\");\n\t\t}\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"\"+getIntegerValue();\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/LongEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.event.*;\nimport java.awt.event.*;\nimport java.util.*;\n\npublic class LongEditor implements SettingEditor, CaretListener, FocusListener\n{\n    private JTextField field;\n    private Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n    private Font font2 = new Font(\"monospaced\", Font.PLAIN, 12);\n    \n    private JTable lastTable = null;\n    private int tableCol = -1;\n    private int tableRow = -1;\n    \n    private boolean valueGot = true;\n    \n    /** Creates a new instance of LongEditor */\n    public LongEditor()\n    {\n        field = new JTextField();\n        field.addCaretListener(this);\n        field.addFocusListener(this);\n    }\n    \n    public Object getEditorValue() throws SettingException\n    {\n        if(field.getText().equals(\"\")) return NOT_CHANGED_VALUE;\n        valueGot = true;\n        try\n        {\n            return Long.valueOf(field.getText());\n        }\n        catch(NumberFormatException e)\n        {\n            throw new SettingException(\"The value entered is not a valid number.\");\n        }\n    }\n    \n    public Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n    {\n        field.setMargin(new Insets(0, 2, 4, 2));\n        if (isSelected)\n        {\n            field.setForeground(table.getSelectionForeground());\n            field.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            field.setForeground(table.getForeground());\n            field.setBackground(table.getBackground());\n        }\n        \n        \n        field.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        \n        \n        if(value instanceof Long)\n        {\n            Long str = (Long)value;\n            \n            field.setText(str.toString());\n            \n            \n            field.setCaretColor(Color.black);\n            \n            field.setFont(font);\n        }\n        else if(value instanceof ArrayList)\n        {\n            ArrayList values = (ArrayList)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                Long last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof Long)\n                    {\n                        Long str = (Long)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    field.setText(\"\"+last.longValue());\n                    \n                    field.setFont(font);\n                }\n                else\n                {\n                    field.setText(\"\");\n                    \n                    field.setFont(font2);\n                }\n                \n            }\n        }\n        \n        lastTable = table;\n        tableRow = row;\n        tableCol = column;\n        valueGot = false;\n        \n        return field;\n    }\n    \n    public void stopEditing()\n    {\n    }\n    \n    public void caretUpdate(CaretEvent e)\n    {\n        field.getCaret().setVisible(true);\n    }\n    \n    public void focusGained(FocusEvent e)\n    {\n    }\n    \n    public void focusLost(FocusEvent e)\n    {\n        if(!valueGot && lastTable != null)\n        {\n            valueGot = true;\n            Object value;\n            if(field.getText().equals(\"\"))\n                value = NOT_CHANGED_VALUE;\n            else\n            {\n                try\n                {\n                    value = Long.valueOf(field.getText());\n                }\n                catch(NumberFormatException ex)\n                {\n                    value = new SettingException(\"The value entered is not a valid number.\");\n                }\n            }\n            lastTable.setValueAt(value, tableRow, tableCol);\n            if(lastTable.getCellEditor() != null) lastTable.removeEditor();\n        }\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/settings/LongRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.awt.*;\nimport java.util.*;\nimport javax.swing.*;\nimport javax.swing.border.*;\n\npublic class LongRenderer implements SettingRenderer\n{\n    private JTextField renderer = new JTextField();\n    private Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n    private Font font2 = new Font(\"monospaced\", Font.ITALIC, 12);\n    \n    \n    public Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row, int column)\n    {\n        renderer.setMargin(new Insets(0, 2, 4, 2));\n        if (isSelected)\n        {\n            renderer.setForeground(table.getSelectionForeground());\n            renderer.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            renderer.setForeground(table.getForeground());\n            renderer.setBackground(table.getBackground());\n        }\n        \n        if(hasFocus)\n        {\n            renderer.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        }\n        else\n        {\n            renderer.setBorder(new EmptyBorder(1, 2, 2, 1));\n        }\n        \n        if(value instanceof Long)\n        {\n            Long dob = (Long)value;\n            \n            renderer.setText(\"\"+dob.longValue());\n\n\t    renderer.setEnabled(isEnabled);\n            \n            renderer.setFont(font);\n        }\n        else if(value instanceof ArrayList)\n        {\n            ArrayList values = (ArrayList)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                Long last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof Long)\n                    {\n                        Long str = (Long)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    renderer.setText(\"\"+last.longValue());\n\n                    renderer.setEnabled(isEnabled);\n            \n                    renderer.setFont(font);\n                }\n                else\n                {\n                    renderer.setText(\"(Different values)\");\n                    \n                    renderer.setEnabled(isEnabled);\n            \n                    renderer.setFont(font2);\n                    \n                    renderer.setBackground(Color.lightGray);\n                }\n                \n            }\n        }\n        \n        \n        return renderer;\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/settings/LongSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic class LongSetting extends Setting \n{\n    private static LongRenderer renderer;\n    private static LongEditor editor;\n\n    /** Creates a new instance of LongSetting */\n\tpublic LongSetting(String name, Long value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n    }\n\t\n    public LongSetting(String name, Long value, String comment, SettingOwner owner, boolean editableWhenMultiple, NumericConstraint constraint)\n    {\n        super(name, value, comment, owner, editableWhenMultiple, constraint);\n    }\n    \n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n            editor = new LongEditor();\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n            renderer = new LongRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return Long.class;\n    }\n    \n    public long getLongValue()\n    {\n        return ((Long)getValue()).longValue();\n    }\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\ttry\n\t\t{\n\t\t\treturn Long.valueOf(string);\n\t\t}\n\t\tcatch(NumberFormatException e)\n\t\t{\n\t\t\tthrow new SettingException(\"Error when parsing: \"+string+\" as a Long value.\");\n\t\t}\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"\"+getLongValue();\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/MultipleLineStringEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport java.awt.event.*;\nimport javax.swing.event.*;\nimport javax.swing.text.BadLocationException;\nimport java.util.*;\n\npublic class MultipleLineStringEditor implements SettingEditor, KeyListener, CaretListener, FocusListener\n{\n    private JTextArea area;\n    private Font font;\n    \n    private JTable lastTable = null;\n    private int tableRow = -1;\n    private int tableCol = -1;\n    \n    private boolean valueGot = true;\n    \n    private boolean multiDifferent = false;\n    \n    public MultipleLineStringEditor()\n    {\n        area = new JTextArea();\n        area.setLineWrap(true);\n        area.setWrapStyleWord(true);\n        font = new Font(\"monospaced\", Font.PLAIN, 12);\n        \n        area.addCaretListener(this);\n        area.addKeyListener(this);\n        area.addFocusListener(this);\n    }\n    \n    public Object getEditorValue()\n    {\n        if(multiDifferent && area.getText().equals(\"\"))\n        {\n            valueGot = true;\n            multiDifferent = false;\n            return NOT_CHANGED_VALUE;\n        }\n        else\n        {\n            valueGot = true;\n            return area.getText();\n        }\n    }\n    \n    public Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n    {\n        \n        area.setMargin(new Insets(0, 2, 4, 2));\n        if (isSelected)\n        {\n            //unselect if selected!\n            table.getSelectionModel().setSelectionInterval(-1, -1);\n            area.setForeground(table.getSelectionForeground());\n            area.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            area.setForeground(table.getForeground());\n            area.setBackground(table.getBackground());\n        }\n        \n        \n        area.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        multiDifferent = false;\n        \n        if(value instanceof String)\n        {\n            String str = (String)value;\n            \n            area.setText(str);\n            \n            area.setCaretColor(Color.black);\n            \n            area.setFont(font);\n            \n            \n        }\n        else if(value instanceof ArrayList)\n        {\n            ArrayList values = (ArrayList)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                String last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof String)\n                    {\n                        String str = (String)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    area.setText(last);\n                    \n                    area.setFont(font);\n                }\n                else\n                {\n                    area.setText(\"\");\n                    multiDifferent = true;\n                }\n                \n            }\n        }\n        //sort out the height\n        int heightWanted = (int)area.getPreferredSize().getHeight();\n        heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n        if(heightWanted != table.getRowHeight(row))\n            table.setRowHeight(row, heightWanted);\n        \n        lastTable = table;\n        tableRow = row;\n        tableCol = column;\n        valueGot = false;\n        return area;\n    }\n    \n    public void stopEditing()\n    {\n    }\n    \n    public void keyPressed(KeyEvent e)\n    {\n        \n        try\n        {\n            int startOfLastLine = area.getLineStartOffset(area.getLineCount()-1);\n            int endOfFirstLine = area.getLineEndOffset(0);\n            int currentPosition = area.getCaretPosition();\n            \n            //override the behaviour of pressing the up key, if we are on the top row of the multiline text.\n            if(e.getKeyCode() == KeyEvent.VK_UP)\n            {\n                if(currentPosition < endOfFirstLine)\n                {\n                    if(lastTable != null)\n                    {\n                        lastTable.editingStopped(new ChangeEvent(this));\n                        \n                        int newPosition = tableRow-1;\n                        if(newPosition <0) newPosition = lastTable.getRowCount()-1;\n                        \n                        lastTable.getSelectionModel().setSelectionInterval(newPosition, newPosition);\n                        \n                    }\n                }\n            }\n            //override the behaviour of pressing the down key, if we on the bottom row of multiline text\n            else if(e.getKeyCode() == KeyEvent.VK_DOWN)\n            {\n                if(currentPosition >= startOfLastLine || area.getText().length() == 0)\n                {\n                    lastTable.editingStopped(new ChangeEvent(this));\n                    \n                    int newPosition = (tableRow+1)%lastTable.getRowCount();\n                    \n                    lastTable.getSelectionModel().setSelectionInterval(newPosition, newPosition);\n                }\n            }\n            else if(e.getKeyCode() == KeyEvent.VK_ENTER)\n            {\n                \n                //is the shift key being pressed?\n                if((e.getModifiersEx() & KeyEvent.SHIFT_DOWN_MASK) != 0)\n                {\n                    e.setModifiers(0); //consume the shift, so that it does not stop the editing\n                }\n                else\n                {\n                    lastTable.editingStopped(new ChangeEvent(this));\n                    int newPosition = (tableRow+1)%lastTable.getRowCount();\n                    \n                    lastTable.getSelectionModel().setSelectionInterval(newPosition, newPosition);\n                }\n            }\n        }\n        catch(BadLocationException ex)\n        {\n            //ignore\n        }\n    }\n    \n    public void keyReleased(KeyEvent e)\n    {\n    }\n    \n    public void keyTyped(KeyEvent e)\n    {\n    }\n    \n    public void caretUpdate(CaretEvent e)\n    {\n        if(lastTable == null) return;\n        area.getCaret().setVisible(true);\n        int heightWanted = (int)area.getPreferredSize().getHeight();\n        heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n        if(heightWanted != lastTable.getRowHeight(tableRow))\n            lastTable.setRowHeight(tableRow, heightWanted);\n    }\n    \n    public void focusGained(FocusEvent e)\n    {\n    }\n    \n    public void focusLost(FocusEvent e)\n    {\n        if(!valueGot && lastTable != null)\n        {\n            if(multiDifferent && area.getText().equals(\"\"))\n            {\n                valueGot = true;\n                multiDifferent = false;\n            }\n            else\n            {\n                valueGot = true;\n                lastTable.setValueAt(area.getText(), tableRow, tableCol);\n            }\n            if(lastTable.getCellEditor() != null) lastTable.removeEditor();\n        }\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/settings/MultipleLineStringRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.util.*;\nimport java.awt.*;\nimport javax.swing.*;\nimport javax.swing.border.*;\n\npublic class MultipleLineStringRenderer implements SettingRenderer\n{\n    private JTextArea area = new JTextArea();\n    private Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n    private Font font2 = new Font(\"monospaced\", Font.ITALIC, 12);\n    \n    \n    public Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row, int column)\n    {\n        area.setMargin(new Insets(0, 2, 4, 2));\n        if (isSelected)\n        {\n            area.setForeground(table.getSelectionForeground());\n            area.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            area.setForeground(table.getForeground());\n            area.setBackground(table.getBackground());\n        }\n        \n        if(hasFocus)\n        {\n            area.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        }\n        else\n        {\n            area.setBorder(new EmptyBorder(1, 2, 2, 1));\n        }\n        \n        if(value instanceof String)\n        {\n            String str = (String)value;\n            \n            area.setText(str);\n\n\t    area.setEnabled(isEnabled);\n            area.setEditable(isEnabled);\n            area.setCaretColor(isEnabled?Color.black:Color.white);\n            \n            area.setFont(font);\n            \n        }\n        else if(value instanceof ArrayList)\n        {\n            ArrayList values = (ArrayList)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                String last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof String)\n                    {\n                        String str = (String)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    area.setText(last);\n                    \n                    area.setEnabled(isEnabled);\n                    area.setEditable(isEnabled);\n                    area.setCaretColor(isEnabled?Color.black:Color.white);\n            \n                    area.setFont(font);\n                }\n                else\n                {\n                    area.setText(\"(Different values)\");\n                    \n                    area.setEnabled(isEnabled);\n                    area.setEditable(isEnabled);\n                    area.setCaretColor(isEnabled?Color.black:Color.white);\n                    area.setBackground(Color.lightGray);\n                    area.setFont(font2);\n                }\n                \n            }\n        }\n        //sort out the height\n        int heightWanted = (int)area.getPreferredSize().getHeight();\n        if(hasFocus) heightWanted++; //this is a hack (for some reason the UIManager provides a border that is 1 pixel too small for the cell highlight!!)\n        if(heightWanted != table.getRowHeight(row))\n            table.setRowHeight(row, heightWanted);\n        \n        return area;\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/settings/MultipleLineStringSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic class MultipleLineStringSetting extends Setting \n{\n    private static MultipleLineStringRenderer renderer;\n    private static MultipleLineStringEditor editor;\n\n    /** Creates a new instance of MultipleLineStringSetting */\n\tpublic MultipleLineStringSetting(String name, String value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n    }\n\t\n    public MultipleLineStringSetting(String name, String value, String comment, SettingOwner owner, boolean editableWhenMultiple, StringConstraint constraint)\n    {\n        super(name, value, comment, owner, editableWhenMultiple, constraint);\n    }\n    \n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n            editor = new MultipleLineStringEditor();\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n            renderer = new MultipleLineStringRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return String.class;\n    }\n    \n    public String getStringValue()\n    {\n        return getValue().toString();\n    }\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\treturn string;\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn getStringValue();\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/NumericConstraint.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic abstract class NumericConstraint implements SettingConstraint\n{\n\t\n\t/** Creates a new instance of NumericConstraint */\n\tpublic NumericConstraint()\n\t{\n\t}\n\t\n\tpublic void checkValue(Object value) throws SettingException\n\t{\n\t\tif(value instanceof Double)\n\t\t{\n\t\t\tcheckValueDouble(((Double)value).doubleValue());\n\t\t}\n\t\telse if(value instanceof Integer)\n\t\t{\n\t\t\tcheckValueInteger(((Integer)value).intValue());\n\t\t}\n\t\telse if(value instanceof Long)\n\t\t{\n\t\t\tcheckValueLong(((Long)value).longValue());\n\t\t}\n\t\telse\n\t\t{\n\t\t\tthrow new SettingException(\"Invalid type for property, should be numeric.\");\n\t\t}\n\t}\n\t\n\tpublic abstract void checkValueDouble(double value) throws SettingException;\n\t\n\tpublic abstract void checkValueInteger(int value) throws SettingException;\n\t\n\tpublic abstract void checkValueLong(long value) throws SettingException;\n}\n"
  },
  {
    "path": "prism/src/settings/RangeConstraint.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.util.*;\n\npublic class RangeConstraint extends NumericConstraint\n{\n    private double lower, upper;\n    private boolean inclusiveLower, inclusiveUpper;\n    \n    /** Creates a new instance of RangeConstraint */\n    public RangeConstraint(String parseThis)\n    {\n\t\tStringTokenizer tokens = new StringTokenizer(parseThis, \",\");\n        int count = tokens.countTokens();\n        \n        if(!parseThis.startsWith(\",\"))\n        {\n            //lower and upper\n            if(count == 2)\n            {\n                try\n                {\n                    lower = Double.parseDouble(tokens.nextToken());\n                    upper = Double.parseDouble(tokens.nextToken());\n                }\n                catch(NumberFormatException e)\n                {\n                    lower = Double.NEGATIVE_INFINITY;\n\t\t\t\t\tupper = Double.POSITIVE_INFINITY;\n                }\n            }\n            //lower only\n            else if(count == 1)\n            {\n                try\n                {\n                    lower = Double.parseDouble(tokens.nextToken());\n\t\t\t\t\tupper = Double.POSITIVE_INFINITY;\n                }\n                catch(NumberFormatException e)\n                {\n                    lower = Double.NEGATIVE_INFINITY;\n\t\t\t\t\tupper = Double.POSITIVE_INFINITY;\n                }\n            }\n            else\n            {\n                lower = Double.NEGATIVE_INFINITY;\n\t\t\t\tupper = Double.POSITIVE_INFINITY;\n            }\n        }\n        else // should start with , and then a number\n        {\n            try\n            {\n                upper = Double.parseDouble(tokens.nextToken());\n\t\t\t\tlower = Double.NEGATIVE_INFINITY;\n            }\n            catch(NumberFormatException e)\n            {\n                lower = Double.NEGATIVE_INFINITY;\n\t\t\t\tupper = Double.POSITIVE_INFINITY;\n            }\n        }\n\t\t\n\t\tinclusiveLower = true;\n\t\tinclusiveUpper = true;\n    }\n    \n    public RangeConstraint(double lower, double upper, boolean inclusiveLower, boolean inclusiveUpper)\n    {\n        this.lower = lower;\n        this.upper = upper;\n        this.inclusiveLower = inclusiveLower;\n        this.inclusiveUpper = inclusiveUpper;\n    }\n\t\n\tpublic RangeConstraint(int lower, int upper, boolean inclusiveLower, boolean inclusiveUpper)\n\t{\n\t\tthis.lower = lower;\n        this.upper = upper;\n        this.inclusiveLower = inclusiveLower;\n        this.inclusiveUpper = inclusiveUpper;\n\t}\n    \n\tpublic void checkValueDouble(double value) throws SettingException\n\t{\n\t\tif(inclusiveLower)\n\t\t{\n\t\t\tif(value < lower) throw new SettingException(\"The value: \"+value+\" should be >=\"+lower);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tif(value <= lower) throw new SettingException(\"The value: \"+value+\" should be >\"+lower);\n\t\t}\n\t\t\n\t\tif(inclusiveUpper)\n\t\t{\n\t\t\tif(value > upper) throw new SettingException(\"The value: \"+value+\"should be <=\"+upper);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tif(value >= upper) throw new SettingException(\"The value: \"+value+\"should be <\"+upper);\n\t\t}\n\t}\n\t\n\tpublic void checkValueInteger(int value) throws SettingException\n\t{\n\t\tif(inclusiveLower)\n\t\t{\n\t\t\tif(value < lower) throw new SettingException(\"The value: \"+value+\" should be >=\"+(int)lower);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tif(value <= lower) throw new SettingException(\"The value: \"+value+\" should be >\"+(int)lower);\n\t\t}\n\t\t\n\t\tif(inclusiveUpper)\n\t\t{\n\t\t\tif(value > upper) throw new SettingException(\"The value: \"+value+\"should be <=\"+(int)upper);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tif(value >= upper) throw new SettingException(\"The value: \"+value+\"should be <\"+(int)upper);\n\t\t}\n\t}\n\t\n\tpublic void checkValueLong(long value) throws SettingException\n\t{\n\t\tif(inclusiveLower)\n\t\t{\n\t\t\tif(value < lower) throw new SettingException(\"The value: \"+value+\" should be >=\"+(long)lower);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tif(value <= lower) throw new SettingException(\"The value: \"+value+\" should be >\"+(long)lower);\n\t\t}\n\t\t\n\t\tif(inclusiveUpper)\n\t\t{\n\t\t\tif(value > upper) throw new SettingException(\"The value: \"+value+\"should be <=\"+(long)upper);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tif(value >= upper) throw new SettingException(\"The value: \"+value+\"should be <\"+(long)upper);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/settings/Setting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.util.*;\n\npublic abstract class Setting\n{\n    private String key;\n    private String name;\n    private String comment;\n    private Object value;\n    private boolean editableWhenMultiple;\n    private boolean enabled;\n    private ArrayList constraints;\n\tprivate String version;\n    \n    private SettingOwner owner;\n    \n    public Setting(String name, Object value, String comment, SettingOwner owner, boolean editableWhenMultiple, SettingConstraint constraint)\n    {\n        this.name = name;\n        this.key = name; //you should set this to something better though.\n        this.value = value;\n        this.comment = comment;\n        this.owner = owner;\n        this.editableWhenMultiple = editableWhenMultiple;\n        this.enabled = true;\n\t\tthis.version = null;\n        \n        constraints = new ArrayList();\n        if(constraint != null) addConstraint(constraint);\n    }\n    \n    public Setting(String name, Object value, String comment, SettingOwner owner, SettingConstraint constraint)\n    {\n        this(name, value, comment, owner, false, constraint);\n    }\n    \n    public Setting(String name, Object value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        this(name, value, comment, owner, editableWhenMultiple, null);\n    }\n    \n    public Setting(String name, Object value, String comment, SettingOwner owner)\n    {\n        this(name, value, comment, owner, false, null);\n    }\n    \n    public void addConstraint(SettingConstraint constraint)\n    {\n        if(constraint != null) constraints.add(constraint);\n    }\n    \n    public void removeConstraint(SettingConstraint constraint)\n    {\n        constraints.remove(constraint);\n    }\n    \n    public int getNumConstraints()\n    {\n        return constraints.size();\n    }\n    \n    public SettingConstraint getConstraint(int i)\n    {\n        return (SettingConstraint)constraints.get(i);\n    }\n    \n\tpublic void setVersion(String s)\n\t{\n\t\tversion = s;\n\t}\n\t\n    /**\n     *  Return the name of this setting\n     */\n    public String getName()\n    {\n        return name;\n    }\n    \n    /**\n     *  Return a comment or description of this setting\n     */\n    public String getComment()\n    {\n        return comment;\n    }\n    \n    /**\n     *  Returns the owner of this setting\n     */\n    public SettingOwner getOwner()\n    {\n        return owner;\n    }\n    \n    /**\n     *  Should this property be editable if it has been selected along with\n     *  others of the same name. \n     */\n    public boolean isEditableWhenMultiple()\n    {\n        return editableWhenMultiple;\n    }\n    \n    /**\n     *  Returns the renderer responsible for this setting\n     */\n    public abstract SettingRenderer getSettingRenderer();\n    \n    /**\n     *  Returns the editor for this setting\n     */\n    public abstract SettingEditor getSettingEditor();\n    \n    /**\n     *  This method can be overridden if necessary, but do call super(obj)\n     */\n    public void checkObjectWithConstraints(Object obj) throws SettingException\n    {\n        for(int i = 0; i < getNumConstraints(); i++)\n        {\n            getConstraint(i).checkValue(obj);\n        }\n    }\n    \n    /**\n     *  Returns the value of this setting\n     */\n    public Object getValue()\n    {\n        return value;\n    }\n    \n    /**\n     *  Returns the class type of the value being stored\n     */\n    public abstract Class getValueClass();\n    \n    /**\n     *  Sets the value, with some type checking.  A set is expected to be done\n     *  by the SettingOwner and so the owner notifySettingChanged method is not\n     *  called.  This will cause only the renderer to display the new value.\n     */\n    public void setValue(Object obj) throws SettingException\n    {\n        SettingEditor editor = getSettingEditor();\n        if(editor != null) editor.stopEditing();\n        \n        if(obj.getClass().isAssignableFrom(getValueClass())) //do a check that the object is in the correct format\n        {\n            //System.out.println(\"checking constraints\");\n            checkObjectWithConstraints(obj);\n            this.value = obj;\n            SettingDisplay display = getOwner().getDisplay();\n            if(display != null) display.redisplaySetting(this);\n        }\n        else\n        {\n            throw new SettingException(\"Invalid type for property: \"+name);\n        }\n    }\n    \n    /**\n     *  Sets the value, with some type checking.  The edit is expected to be\n     *  done either by one of the editors, or by an object that is not the\n     *  SettingOwner.  Therefore, the SettingOwner will be notified and the\n     *  renderer will display the new value.\n     */\n    public void editValue(Object obj) throws SettingException\n    {\n        SettingEditor editor = getSettingEditor();\n        if(editor != null) editor.stopEditing();\n    \n        if(obj.getClass().isAssignableFrom(this.getValueClass()))\n        {\n            checkObjectWithConstraints(obj);\n            this.value = obj;\n            SettingDisplay display = getOwner().getDisplay();\n            if(display != null) display.redisplaySetting(this);\n            getOwner().notifySettingChanged(this);\n        }\n        else\n        {\n            throw new SettingException(\"Invalid type for property: \"+name);\n        }\n    }\n    \n    public void setEnabled(boolean enable)\n    {\n        this.enabled = enable;\n        getSettingEditor().stopEditing();\n        \n    }\n    \n    public boolean isEnabled()\n    {\n        return enabled;\n    }\n    \n    public void setKey(String key)\n    {\n        this.key = key;\n    }\n    \n    public String getKey()\n    {\n        return key;\n    }\n\t\n\tpublic String getVersion()\n\t{\n\t\treturn version;\n\t}\n\n\t/**\n\t *\tMust be overridden to define what this setting should be written like to\n\t *\ta file, so that it can be read in again\n\t */\n\tpublic abstract String toString();\n    \n\t/**\n\t *\tMust be overridden to return an object of the appropriate type, which is\n\t *\ta parsed version of the string.\n\t */\n\tpublic abstract Object parseStringValue(String string) throws SettingException;\n    \n}\n"
  },
  {
    "path": "prism/src/settings/SettingConstraint.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\n/**\n * Implement this interface to enforce constraints on properties.\n */\npublic interface SettingConstraint\n{\n    \n    /*\n     *  This method checks that the value parameter is valid for the\n     *  constraint.  It can also be used to adjust other settings, so that they\n     *  become valid for the given parameter.\n     */\n    public void checkValue(Object value) throws SettingException;\n    \n}\n"
  },
  {
    "path": "prism/src/settings/SettingDisplay.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic interface SettingDisplay\n{\n    public void redisplaySetting(Setting setting);\n}\n"
  },
  {
    "path": "prism/src/settings/SettingEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\n\npublic interface SettingEditor\n{\n    public static final String NOT_CHANGED_VALUE = \"$%^&*NOTCHANGED*&^%$\";\n    \n    public Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column);\n    \n    public void stopEditing();\n    \n    //throw the exception if the value that has been entered into the editor is invalid\n    public Object getEditorValue() throws SettingException;\n    \n}\n"
  },
  {
    "path": "prism/src/settings/SettingException.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic class SettingException extends Exception\n{\n    /** Creates a new instance of SettingException */\n    public SettingException(String message)\n    {\n        super(message);\n    }\n}\n"
  },
  {
    "path": "prism/src/settings/SettingOwner.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic interface SettingOwner extends Comparable\n{\n    /**\n     *  One for each type of owner\n     */\n    public int getSettingOwnerID();\n    \n    /** One for each owner\n     *  This will be displayed when only\n     *  this owner is being displayed.\n     */\n    public String getSettingOwnerName();\n    \n    /** ONe for each type of property collection\n     *  When only one owner is being displayed,\n     *  we see the result of this method, and then\n     *  the result of getDescriptor.\n     *  If there is more than one owner being\n     *  displayed, we see the number of\n     *  owners, then the result of this method\n     *  followed by an \"s\".\n     */\n    public String getSettingOwnerClassName();\n    \n    public int getNumSettings();\n    \n    public Setting getSetting(int index);\n    \n    /**\n     *  Called if a setting has been changed externally to this SettingOwner.\n     */\n    public void notifySettingChanged(Setting setting);\n    \n    /**\n     *  Return null if no display\n     */\n    public SettingDisplay getDisplay();\n    \n    public void setDisplay(SettingDisplay display);\n    \n}\n"
  },
  {
    "path": "prism/src/settings/SettingRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport java.awt.*;\nimport javax.swing.*;\n\npublic interface SettingRenderer\n{\n    \n    public Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row, int column);\n    \n}\n"
  },
  {
    "path": "prism/src/settings/SettingTable.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"true\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JSplitPane\" name=\"jSplitPane1\">\n          <Properties>\n            <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n              <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n            </Property>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"null\"/>\n            </Property>\n            <Property name=\"dividerSize\" type=\"int\" value=\"3\"/>\n            <Property name=\"orientation\" type=\"int\" value=\"0\"/>\n            <Property name=\"resizeWeight\" type=\"double\" value=\"1.0\"/>\n            <Property name=\"oneTouchExpandable\" type=\"boolean\" value=\"true\"/>\n          </Properties>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"true\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane1\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n                    <LineBorder>\n                      <Color PropertyName=\"color\" blue=\"80\" green=\"80\" id=\"Text Inactive Text\" palette=\"2\" red=\"80\" type=\"palette\"/>\n                    </LineBorder>\n                  </Border>\n                </Property>\n                <Property name=\"horizontalScrollBarPolicy\" type=\"int\" value=\"31\"/>\n              </Properties>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"jScrollPane1.getViewport().setBackground(Color.white);\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                  <JSplitPaneConstraints position=\"left\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n              <SubComponents>\n                <Component class=\"javax.swing.JTable\" name=\"theTable\">\n                  <Properties>\n                    <Property name=\"model\" type=\"javax.swing.table.TableModel\" editor=\"org.netbeans.modules.form.editors2.TableModelEditor\">\n                      <Table columnCount=\"4\" rowCount=\"4\">\n                        <Column editable=\"true\" title=\"Title 1\" type=\"java.lang.Object\"/>\n                        <Column editable=\"true\" title=\"Title 2\" type=\"java.lang.Object\"/>\n                        <Column editable=\"true\" title=\"Title 3\" type=\"java.lang.Object\"/>\n                        <Column editable=\"true\" title=\"Title 4\" type=\"java.lang.Object\"/>\n                      </Table>\n                    </Property>\n                    <Property name=\"doubleBuffered\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"gridColor\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                      <Color blue=\"c5\" green=\"c5\" red=\"c6\" type=\"rgb\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_CreateCodeCustom\" type=\"java.lang.String\" value=\"new JTable()&#xa;            {&#xa;&#x9;&#x9;&#x9;&#x9;public void editingStopped(ChangeEvent e) &#xa;&#x9;&#x9;&#x9;&#x9;{&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;// Take in the new value&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;TableCellEditor editor = getCellEditor();&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;if (editor != null) &#xa;&#x9;&#x9;&#x9;&#x9;&#x9;{&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;Object value = editor.getCellEditorValue();&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;setValueAt(value, editingRow, editingColumn);&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;if(shouldRemove)&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;{&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;removeEditor();&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;getSelectionModel().setSelectionInterval(editingRow, editingRow);&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;getColumnModel().getSelectionModel().setSelectionInterval(editingColumn, editingColumn);&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;}&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;else&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;{&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;getSelectionModel().setSelectionInterval(editingRow, editingRow);&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;getColumnModel().getSelectionModel().setSelectionInterval(editingColumn, editingColumn);&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;}&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;&#x9;shouldRemove = false;&#xa;&#x9;&#x9;&#x9;&#x9;&#x9;}&#xa;&#x9;&#x9;&#x9;&#x9;}&#xa;&#x9;&#x9;&#x9;&#x9;&#xa;&#x9;&#x9;&#x9;&#x9;&#xa;                //This method is a fix from http://www.codeguru.com/java/articles/180.shtml by Zafir Anjum, cheers!&#xa;                //this is required because there is a bug in JTable where the &#xa;                //just saying tableScroll.setColumnHeader(null); does not work as it should&#xa;                //Unfortunately, it overrides a deprecated API, so let&apos;s hope they &#xa;                //sort it out by Java 5.0, nice one Sun...&#xa;                protected void configureEnclosingScrollPane()&#xa;                {&#xa;                    Container p = getParent();&#xa;                    if (p instanceof JViewport)&#xa;                    {&#xa;                        Container gp = p.getParent();&#xa;                        if (gp instanceof JScrollPane)&#xa;                        {&#xa;                            JScrollPane scrollPane = (JScrollPane)gp;&#xa;                            // Make certain we are the viewPort&apos;s view and not, for&#xa;                            // example, the rowHeaderView of the scrollPane -&#xa;                            // an implementor of fixed columns might do this.&#xa;                            JViewport viewport = scrollPane.getViewport();&#xa;                            if (viewport == null || viewport.getView() != this)&#xa;                            {&#xa;                                return;&#xa;                            }&#xa;                            //                scrollPane.setColumnHeaderView(getTableHeader());&#xa;                            scrollPane.getViewport().setBackingStoreEnabled(true);&#xa;                            scrollPane.setBorder(UIManager.getBorder(&quot;Table.scrollPaneBorder&quot;));&#xa;                        }&#xa;                    }&#xa;                }&#xa;                &#xa;            };&#xa;            theTable.setModel(theModel);&#xa;            theTable.setSelectionMode(DefaultListSelectionModel.SINGLE_SELECTION);&#xa;            theTable.setRowSelectionAllowed(false);&#xa;            theTable.setColumnSelectionAllowed(false);&#xa;            theTable.setCellSelectionEnabled(true);\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                </Component>\n              </SubComponents>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n                    <LineBorder>\n                      <Color PropertyName=\"color\" blue=\"80\" green=\"80\" id=\"Inactive Caption\" palette=\"2\" red=\"80\" type=\"palette\"/>\n                    </LineBorder>\n                  </Border>\n                </Property>\n                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[10, 75]\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[100, 75]\"/>\n                </Property>\n              </Properties>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"true\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                  <JSplitPaneConstraints position=\"right\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n              <SubComponents>\n                <Component class=\"javax.swing.JTextArea\" name=\"commentText\">\n                  <Properties>\n                    <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                      <Color blue=\"cc\" green=\"cc\" id=\"Panel.background\" palette=\"3\" red=\"cc\" type=\"palette\"/>\n                    </Property>\n                    <Property name=\"columns\" type=\"int\" value=\"1\"/>\n                    <Property name=\"editable\" type=\"boolean\" value=\"false\"/>\n                    <Property name=\"lineWrap\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"wrapStyleWord\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"null\"/>\n                    </Property>\n                    <Property name=\"doubleBuffered\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"focusable\" type=\"boolean\" value=\"false\"/>\n                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[100, 75]\"/>\n                    </Property>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[100, 75]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"Center\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"commentLabel\">\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"North\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"North\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Component class=\"javax.swing.JComboBox\" name=\"theCombo\">\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"North\"/>\n            </Constraint>\n          </Constraints>\n        </Component>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/settings/SettingTable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport javax.swing.event.*;\nimport java.awt.*;\nimport java.awt.event.*;\nimport java.util.*;\nimport javax.swing.table.*;\n\npublic class SettingTable extends JPanel implements ListSelectionListener, TableModelListener, ItemListener, SettingDisplay\n{\n\tprivate Component parent;\n\tprivate SettingTableModel theModel;\n\t\n\tprivate int lineWidth;\n\t\n\tprivate boolean shouldRemove;\n\t/** Creates new form PropertyTable */\n\tpublic SettingTable(Component parent)\n\t{\n\t\tsuper();\n\t\tthis.parent = parent;\n\t\ttheModel = new SettingTableModel();\n\t\tinitComponents();\n\t\t\n\t\ttheModel.setJTable(theTable);\n\t\ttheModel.addTableModelListener(this);\n\t\tlineWidth = theTable.getRowHeight();\n\t\ttheTable.setModel(theModel);\n\t\ttheTable.setRowSelectionAllowed(false);\n\t\ttheTable.setColumnSelectionAllowed(false);\n\t\t//theTable.setCellSelectionEnabled(true);\n\t\ttheTable.getSelectionModel().addListSelectionListener(this);\n\t\ttheTable.setAutoResizeMode(JTable.AUTO_RESIZE_LAST_COLUMN);\n\t\ttheCombo.setModel(theModel.getComboModel());\n\t\ttheCombo.addItemListener(this);\n\t\ttheTable.setSurrendersFocusOnKeystroke(true);\n\t\t\n\t\t\n\t\ttheTable.getColumnModel().getColumn(0).setMinWidth(30);\n\t\t\n\t\ttheTable.setRequestFocusEnabled(false);\n\t\t\n\t\tTableColumn column = theTable.getColumnModel().getColumn(1);\n\t\tcolumn.setCellRenderer(new SettingCellRenderer());\n\t\tcolumn.setCellEditor(new SettingCellEditor());\n\t\t\n\t\tTableResizer tr = new TableResizer(theTable);\n\t\t\n\t\ttheTable.addMouseListener(tr);\n\t\ttheTable.addMouseMotionListener(tr);\n\t\t\n\t\tdoChoiceBox();\n\t\t\n\t\tcommentLabel.setFont(new Font(\"serif\", Font.BOLD, 12));\n\t\t\n\t\tshouldRemove = true;\n\t\t\n\t}\n\t\n\tpublic void setOwners(ArrayList owners)\n\t{\n\t\ttheModel.setOwners(owners);\n\t}\n\t\n\tpublic void refreshGroupNames()\n\t{\n\t\ttheModel.refreshGroupNames();\n\t\t\n\t\t//doChoiceBox();\n\t\t//repaint();\n\t}\n\t\n\tpublic void setNameColumnWidth(int width)\n\t{\n\t\t//theTable.getColumnModel().getColumn(0).setMinWidth(width);\n\t\t//theTable.getColumnModel().getColumn(0).setMaxWidth(width);\n\t\t//theTable.getColumnModel().getColumn(0).setPreferredWidth(width);\n\t\t//theTable.getColumnModel().getColumn(0).setMaxWidth(width);\n\t\t//theTable.repaint();\n\t}\n\t\n\tprivate void doChoiceBox()\n\t{\n\t\t//System.out.println(\"calling doChoiceBox()\");\n\t\tif(theModel.getNumGroups() == 0)\n\t\t{\n\t\t\t//System.out.println(\"0 groups\");\n\t\t\ttopPanel.removeAll();\n\t\t\tJLabel lab = new JLabel(\"\");\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\ttopPanel.add(lab, BorderLayout.CENTER);\n\t\t}\n\t\telse if(theModel.getNumGroups() == 1)\n\t\t{\n\t\t\t//System.out.println(\"1 group\");\n\t\t\ttopPanel.removeAll();\n\t\t\tJLabel lab = new JLabel(theCombo.getModel().getElementAt(0).toString());\n\t\t\t//System.out.println(theCombo.getModel().getElementAt(0).toString());\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\ttopPanel.add(lab, BorderLayout.CENTER);\n\t\t}\n\t\telse\n\t\t{\n\t\t\t//System.out.println(\"2 group\");\n\t\t\ttopPanel.removeAll();\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\ttopPanel.add(theCombo, BorderLayout.CENTER);\n\t\t}\n\t\tthis.revalidate();\n\t}\n\t\n\tpublic void stopEditing()\n\t{\n\t\tif(theTable.getCellEditor() != null) \n\t\t{\n\t\t\ttheTable.getCellEditor().stopCellEditing();\n\t\t\ttheTable.removeEditor();\t\t\n\t\t}\n\t\t//        if(ce != null)ce.stopEditing();\n\t}\n\t\n\t//    public void setCurrEditor(SettingEditor ce)\n\t//    {\n\t//\t\tTableColumn column = theTable.getColumnModel().getColumn(1);\n\t//\t\tcolumn.setCellEditor(ce);\n\t//\t\t//if(this.ce != ce) System.out.println(\"THE CURREDITOR HAS CHANGED\");\n\t//\n\t//        this.ce = ce;\n\t//    }\n\t//\n\t//    private SettingEditor ce;\n\t\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n    private void initComponents()//GEN-BEGIN:initComponents\n    {\n        javax.swing.JPanel jPanel1;\n        javax.swing.JPanel jPanel3;\n        javax.swing.JSplitPane jSplitPane1;\n\n        jPanel1 = new javax.swing.JPanel();\n        jSplitPane1 = new javax.swing.JSplitPane();\n        jScrollPane1 = new javax.swing.JScrollPane();\n        jScrollPane1.getViewport().setBackground(Color.white);\n        theTable = new JTable()\n        {\n            public void editingStopped(ChangeEvent e)\n            {\n                // Take in the new value\n                TableCellEditor editor = getCellEditor();\n                if (editor != null)\n                {\n                    Object value = editor.getCellEditorValue();\n                    setValueAt(value, editingRow, editingColumn);\n                    if(shouldRemove)\n                    {\n                        removeEditor();\n                        getSelectionModel().setSelectionInterval(editingRow, editingRow);\n                        getColumnModel().getSelectionModel().setSelectionInterval(editingColumn, editingColumn);\n                    }\n                    else\n                    {\n                        getSelectionModel().setSelectionInterval(editingRow, editingRow);\n                        getColumnModel().getSelectionModel().setSelectionInterval(editingColumn, editingColumn);\n\n                    }\n                    shouldRemove = false;\n                }\n            }\n\n            //This method is a fix from http://www.codeguru.com/java/articles/180.shtml by Zafir Anjum, cheers!\n            //this is required because there is a bug in JTable where the\n            //just saying tableScroll.setColumnHeader(null); does not work as it should\n            //Unfortunately, it overrides a deprecated API, so let's hope they\n            //sort it out by Java 5.0, nice one Sun...\n            protected void configureEnclosingScrollPane()\n            {\n                Container p = getParent();\n                if (p instanceof JViewport)\n                {\n                    Container gp = p.getParent();\n                    if (gp instanceof JScrollPane)\n                    {\n                        JScrollPane scrollPane = (JScrollPane)gp;\n                        // Make certain we are the viewPort's view and not, for\n                        // example, the rowHeaderView of the scrollPane -\n                        // an implementor of fixed columns might do this.\n                        JViewport viewport = scrollPane.getViewport();\n                        if (viewport == null || viewport.getView() != this)\n                        {\n                            return;\n                        }\n                        //                scrollPane.setColumnHeaderView(getTableHeader());\n                        scrollPane.getViewport().setBackingStoreEnabled(true);\n                        scrollPane.setBorder(UIManager.getBorder(\"Table.scrollPaneBorder\"));\n                    }\n                }\n            }\n\n        };\n        theTable.setModel(theModel);\n        theTable.setSelectionMode(DefaultListSelectionModel.SINGLE_SELECTION);\n        theTable.setRowSelectionAllowed(false);\n        theTable.setColumnSelectionAllowed(false);\n        theTable.setCellSelectionEnabled(true);\n        jPanel3 = new javax.swing.JPanel();\n        commentText = new javax.swing.JTextArea();\n        jScrollPaneCommentText = new javax.swing.JScrollPane(commentText);\n        commentLabel = new javax.swing.JLabel();\n        topPanel = new javax.swing.JPanel();\n        theCombo = new javax.swing.JComboBox();\n\n        setLayout(new java.awt.BorderLayout());\n\n        jPanel1.setLayout(new java.awt.BorderLayout());\n\n        jSplitPane1.setBackground(new java.awt.Color(255, 255, 255));\n        jSplitPane1.setBorder(null);\n        jSplitPane1.setDividerSize(3);\n        jSplitPane1.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);\n        jSplitPane1.setResizeWeight(1.0);\n        jSplitPane1.setOneTouchExpandable(true);\n        jScrollPane1.setBackground(new java.awt.Color(255, 255, 255));\n        jScrollPane1.setBorder(new javax.swing.border.LineBorder(java.awt.SystemColor.textInactiveText));\n        jScrollPane1.setHorizontalScrollBarPolicy(javax.swing.JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);\n        theTable.setModel(new javax.swing.table.DefaultTableModel(\n            new Object [][]\n            {\n                {null, null, null, null},\n                {null, null, null, null},\n                {null, null, null, null},\n                {null, null, null, null}\n            },\n            new String []\n            {\n                \"Title 1\", \"Title 2\", \"Title 3\", \"Title 4\"\n            }\n        ));\n        theTable.setDoubleBuffered(true);\n        theTable.setGridColor(new java.awt.Color(198, 197, 197));\n        jScrollPane1.setViewportView(theTable);\n\n        jSplitPane1.setLeftComponent(jScrollPane1);\n\n        jPanel3.setLayout(new java.awt.BorderLayout());\n\n        jPanel3.setBorder(new javax.swing.border.LineBorder(java.awt.SystemColor.inactiveCaption));\n        jPanel3.setMinimumSize(new java.awt.Dimension(10, 75));\n        jPanel3.setPreferredSize(new java.awt.Dimension(100, 75));\n        commentText.setBackground(javax.swing.UIManager.getDefaults().getColor(\"Panel.background\"));\n        commentText.setColumns(1);\n        commentText.setEditable(false);\n        commentText.setLineWrap(true);\n        commentText.setWrapStyleWord(true);\n        commentText.setBorder(null);\n        commentText.setDoubleBuffered(true);\n        commentText.setFocusable(false);\n        jScrollPaneCommentText.setMinimumSize(new java.awt.Dimension(100, 75));\n        jScrollPaneCommentText.setPreferredSize(new java.awt.Dimension(100, 75));\n        jScrollPaneCommentText.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);\n        jScrollPaneCommentText.setVerticalScrollBarPolicy(JScrollPane.VERTICAL_SCROLLBAR_AS_NEEDED);\n        jPanel3.add(jScrollPaneCommentText, java.awt.BorderLayout.CENTER);\n\n        jPanel3.add(commentLabel, java.awt.BorderLayout.NORTH);\n\n        jSplitPane1.setRightComponent(jPanel3);\n\n        jPanel1.add(jSplitPane1, java.awt.BorderLayout.CENTER);\n\n        add(jPanel1, java.awt.BorderLayout.CENTER);\n\n        topPanel.setLayout(new java.awt.BorderLayout());\n\n        topPanel.add(theCombo, java.awt.BorderLayout.NORTH);\n\n        add(topPanel, java.awt.BorderLayout.NORTH);\n\n    }//GEN-END:initComponents\n\t\n\t/** Override set font to update row heights at same time */\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\tif (theTable != null) theTable.setRowHeight(getFontMetrics(font).getHeight()+4);\n\t}\n\n\tpublic void valueChanged(ListSelectionEvent e)\n\t{\n\t\t//System.out.println(\"list VALUE CHANGED\");\n\t\tSetting selected = theModel.getSelectedProperty(theTable.getSelectedRow());\n\t\t\n\t\tif(selected != null)\n\t\t{\n\t\t\tcommentLabel.setText(selected.getName());\n\t\t\tcommentText.setText(selected.getComment());\n\t\t\tcommentText.setCaretPosition(0);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tcommentLabel.setText(\"\");\n\t\t\tcommentText.setText(\"\");\n\t\t\tcommentText.setCaretPosition(0);\n\t\t}\n\t\t\n\t\t//                for(int i = 0; i < theModel.getRowCount(); i++)\n\t\t//                {\n\t\t//                    ////System.out.println(\"Row \"+i);\n\t\t//                    String value = theModel.getValueAt(i, 1).toString();\n\t\t//                    int lines = 1;\n\t\t//\n\t\t//                    if(theModel.getValueAt(i, 1) instanceof FontColorProperty)\n\t\t//                    {\n\t\t//                int height = ((FontColorProperty)theModel.getValueAt(i,1)).getFontColorPair().f.getSize();\n\t\t//                height = Math.max(height, (lineWidth-2));\n\t\t//                theTable.setRowHeight(i, (height*lines)+4);\n\t\t//            }\n\t\t//            else if(theModel.getValueAt(i, 1) instanceof SingleProperty)\n\t\t//            {\n\t\t//                //lines = getNumLines(value);\n\t\t//                //int heightWanted =\n\t\t//                //theTable.setRowHeight(i, (lineWidth*lines)+2);\n\t\t//            }\n\t\t//        }\n\t}\n\t\n\tpublic void tableChanged(TableModelEvent e)\n\t{\n\t\tSetting selected = theModel.getSelectedProperty(theTable.getSelectedRow());\n\t\t\n\t\tif(selected != null)\n\t\t{\n\t\t\tcommentLabel.setText(selected.getName());\n\t\t\tcommentText.setText(selected.getComment());\n\t\t\tcommentText.setCaretPosition(0);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tcommentLabel.setText(\"\");\n\t\t\tcommentText.setText(\"\");\n\t\t\tcommentText.setCaretPosition(0);\n\t\t}\n\t\t//System.out.println(\"TABLE CHANGED\");\n\t\t//       CellEditor ce = theTable.getCellEditor();\n\t\t//        if(ce != null) ce.cancelCellEditing();\n\t\t//        theCombo.setModel(theModel.getComboModel());\n\t\t//        for(int i = 0; i < theModel.getRowCount(); i++)\n\t\t//        {\n\t\t//            ////System.out.println(\"Row \"+i);\n\t\t//            String value = theModel.getValueAt(i, 1).toString();\n\t\t//            int lines = 1;\n\t\t//\n\t\t//            if(theModel.getValueAt(i, 1) instanceof FontColorProperty)\n\t\t//            {\n\t\t//                int height = ((FontColorProperty)theModel.getValueAt(i,1)).getFontColorPair().f.getSize();\n\t\t//\n\t\t//                height = Math.max(height, (lineWidth-2));\n\t\t//                theTable.setRowHeight(i, (height*lines)+4);\n\t\t//            }\n\t\t//            else if(theModel.getValueAt(i, 1) instanceof SingleProperty)\n\t\t//            {\n\t\t//                //lines = getNumLines(value);\n\t\t//                //theTable.setRowHeight(i, (lineWidth*lines)+2);\n\t\t//                //int heightWanted = (int)area.getPreferredSize().getHeight();\n\t\t//                  ///  if(heightWanted != theTable.getRowHeight(row));\n\t\t//                   // theTable.setRowHeight(row, heightWanted);\n\t\t//            }\n\t\t//            else if(theModel.getValueAt(i, 1) instanceof MultipleProperty)\n\t\t//            {\n\t\t//                lines = getNumLines(value);\n\t\t//                theTable.setRowHeight(i, (lineWidth*lines)+2);\n\t\t//            }\n\t\t//\n\t\t//\n\t\t//\n\t\t//        }\n\t\t//        doChoiceBox();\n\t\t//theTable.s\n\t\t//System.out.println(\"getting the combomodel\");\n\t\ttheCombo.setModel(theModel.getComboModel());\n\t\tdoChoiceBox();\n\t}\n\t\n\t//    public static int getNumLines(String str)\n\t//    {\n\t//        int count = 1;\n\t//        for(int i = 0; i < str.length(); i++)\n\t//        {\n\t//            char curr = str.charAt(i);\n\t//            if(curr=='\\n') count++;\n\t//        }\n\t//        ////System.out.println(\"count = \"+count);\n\t//        return count;\n\t//    }\n\t\n\tpublic void itemStateChanged(ItemEvent e)\n\t{\n\t\ttheModel.setCurrentGroup(theCombo.getSelectedIndex());\n\t}\n\t\n\tpublic void redisplaySetting(Setting setting)\n\t{\n\t\tSetting selected = theModel.getSelectedProperty(theTable.getSelectedRow());\n\t\t\n\t\tif(selected != null)\n\t\t{\n\t\t\tcommentLabel.setText(selected.getName());\n\t\t\tcommentText.setText(selected.getComment());\n\t\t\tcommentText.setCaretPosition(0);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tcommentLabel.setText(\"\");\n\t\t\tcommentText.setText(\"\");\n\t\t\tcommentText.setCaretPosition(0);\n\t\t}\n\t\ttheModel.fireTableDataChanged();\n\t\ttheTable.repaint();\n\t}\n\t\n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    javax.swing.JLabel commentLabel;\n    javax.swing.JTextArea commentText;\n    private javax.swing.JScrollPane jScrollPane1;\n    private javax.swing.JScrollPane jScrollPaneCommentText;\n    javax.swing.JComboBox theCombo;\n    javax.swing.JTable theTable;\n    javax.swing.JPanel topPanel;\n    // End of variables declaration//GEN-END:variables\n\t\n\t\n\t\n\tclass SettingCellRenderer implements TableCellRenderer\n\t{\n\t\t\n\t\t/**\n\t\t *  In this case value will be instanceof Setting\n\t\t */\n\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t\t{\n\t\t\t\n\t\t\tif(value instanceof Setting)\n\t\t\t{\n\t\t\t\tSetting setting = (Setting)value;\n\t\t\t\t\n\t\t\t\t//the getSettingRenderer() method returns a static SettingRenderer object for each Setting class, this is called with the actual\n\t\t\t\t//renderable data.\n\t\t\t\treturn setting.getSettingRenderer().getTableCellRendererComponent(table, setting, setting.getValue(), isSelected, hasFocus, setting.isEnabled(), row, column);\n\t\t\t\t\n\t\t\t}\n\t\t\telse if(value instanceof ArrayList)\n\t\t\t{\n\t\t\t\tArrayList settings = (ArrayList)value;\n\t\t\t\tArrayList values = new ArrayList();\n\t\t\t\tboolean enabled = true;\n\t\t\t\tSetting first = null;\n\t\t\t\tfor(int i = 0; i < settings.size();i++)\n\t\t\t\t{\n\t\t\t\t\tif(settings.get(i) instanceof Setting)\n\t\t\t\t\t{\n\t\t\t\t\t\tSetting setting = (Setting)settings.get(i);\n\t\t\t\t\t\tif(i == 0)first = setting;\n\t\t\t\t\t\tif(!setting.isEnabled()) enabled = false;\n\t\t\t\t\t\tvalues.add(setting.getValue());\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif(first != null)\n\t\t\t\t\treturn first.getSettingRenderer().getTableCellRendererComponent(table, first, values, isSelected, hasFocus, enabled, row, column);\n\t\t\t\telse\n\t\t\t\t\treturn new JLabel(\"ERRORRRRR!!!!\");\n\t\t\t}\n\t\t\telse return new JLabel(\"ERRRORRRRRR!!!!\");\n\t\t}\n\t\t\n\t}\n\t\n\tclass SettingCellEditor extends AbstractCellEditor implements TableCellEditor\n\t{\n\t\tprivate SettingEditor currentEditor;\n\t\t\n\t\tpublic Object getCellEditorValue()\n\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\treturn currentEditor.getEditorValue();\n\t\t\t}\n\t\t\tcatch(SettingException e)\n\t\t\t{\n\t\t\t\treturn e; //actually return the exception for display\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic boolean stopCellEditing() { \n\t\t\tfireEditingStopped(); \n\t\t\treturn shouldRemove;\n\t\t}\n\t\t\n\t\tpublic Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column)\n\t\t{\n\t\t\t\n\t\t\t\n\t\t\tif(value instanceof Setting)\n\t\t\t{\n\t\t\t\tSetting setting = (Setting)value;\n\t\t\t\tcurrentEditor = setting.getSettingEditor();\n\t\t\t\t\n\t\t\t\t//the getSettingRenderer() method returns a static SettingRenderer object for each Setting class, this is called with the actual\n\t\t\t\t//renderable data.\n\t\t\t\treturn currentEditor.getTableCellEditorComponent(table, setting, setting.getValue(), isSelected, row, column);\n\t\t\t\t\n\t\t\t}\n\t\t\telse if(value instanceof ArrayList)\n\t\t\t{\n\t\t\t\tArrayList settings = (ArrayList)value;\n\t\t\t\tArrayList values = new ArrayList();\n\t\t\t\tboolean enabled = true;\n\t\t\t\tSetting first = null;\n\t\t\t\tfor(int i = 0; i < settings.size();i++)\n\t\t\t\t{\n\t\t\t\t\tif(settings.get(i) instanceof Setting)\n\t\t\t\t\t{\n\t\t\t\t\t\tSetting setting = (Setting)settings.get(i);\n\t\t\t\t\t\tif(i == 0)first = setting;\n\t\t\t\t\t\tif(!setting.isEnabled()) enabled = false;\n\t\t\t\t\t\tvalues.add(setting.getValue());\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif(first != null)\n\t\t\t\t{\n\t\t\t\t\tcurrentEditor = first.getSettingEditor();\n\t\t\t\t\treturn currentEditor.getTableCellEditorComponent(table, first, values, isSelected, row, column);\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t\treturn new JLabel(\"ERRORRRRR!!!!\");\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\treturn new JLabel(\"NEVER!!!!\");\n\t\t\t}\n\t\t}\n\t\t\n\t}\n\t\n\tclass SettingTableModel extends AbstractTableModel\n\t{\n\t\t//All of the data\n\t\tprivate ArrayList owners;\n\t\t\n\t\t//Current sorted data\n\t\tprivate ArrayList groupNames;\n\t\tprivate ArrayList groupStarts;\n\t\tprivate ArrayList groupSizes;\n\t\tprivate int currentGroup;\n\t\t\n\t\tprivate DefaultComboBoxModel comboModel;\n\t\t\n\t\tprivate JTable theTable;\n\t\t\n\t\tpublic SettingTableModel()\n\t\t{\n\t\t\tsuper();\n\t\t\tthis.theTable = null;\n\t\t\tgroupNames = new ArrayList();\n\t\t\tgroupStarts = new ArrayList();\n\t\t\tgroupSizes = new ArrayList();\n\t\t\towners = new ArrayList();\n\t\t\tcomboModel = new DefaultComboBoxModel();\n\t\t}\n\t\t\n\t\tpublic void setJTable(JTable tab)\n\t\t{\n\t\t\tthis.theTable = tab;\n\t\t}\n\t\t\n\t\tpublic void setOwners(ArrayList owners)\n\t\t{\n\t\t\tthis.owners = owners;\n\t\t\tCollections.sort(owners);\n\t\t\t\n\t\t\tIterator it = owners.iterator();\n\t\t\tSettingOwner last = null;\n\t\t\tint currGroupCount = 0;\n\t\t\tString tempName = \"\";\n\t\t\tgroupNames = new ArrayList();\n\t\t\tgroupStarts = new ArrayList();\n\t\t\tgroupSizes = new ArrayList();\n\t\t\tint index = 0;\n\t\t\t\n\t\t\tString ownerList = \"\";\n\t\t\twhile(it.hasNext())\n\t\t\t{\n\t\t\t\t\n\t\t\t\t\n\t\t\t\tSettingOwner po = (SettingOwner)it.next();\n\t\t\t\t//            for(int i = 0; i < po.getNumProperties(); i++)\n\t\t\t\t//            {\n\t\t\t\t//                po.getProperty(i).addObserver(this);\n\t\t\t\t//                po.getProperty(i).setOwningModel(this);\n\t\t\t\t//            }\n\t\t\t\tif(last == null)\n\t\t\t\t{\n\t\t\t\t\t//this is the first group\n\t\t\t\t\tcurrGroupCount++;\n\t\t\t\t\tif(!po.getSettingOwnerName().equals(\"\"))ownerList += \"\\'\"+po.getSettingOwnerName()+\"\\'\";\n\t\t\t\t\ttempName = po.getSettingOwnerClassName();\n\t\t\t\t\tgroupStarts.add(Integer.valueOf(0));\n\t\t\t\t}\n\t\t\t\telse if(po.getSettingOwnerID() == last.getSettingOwnerID())\n\t\t\t\t{\n\t\t\t\t\t//this is for the second or after in the sequence\n\t\t\t\t\tcurrGroupCount++;\n\t\t\t\t\t//tempName = \"\"+currGroupCount+\" \"+po.getClassDescriptor()+\"s\";\n\t\t\t\t\tif(!po.getSettingOwnerClassName().endsWith(\"s\"))\n\t\t\t\t\t\ttempName = po.getSettingOwnerClassName()+\"s\";\n\t\t\t\t\tif(!po.getSettingOwnerName().equals(\"\"))ownerList += \", \\'\"+po.getSettingOwnerName()+\"\\'\";\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\t//this starts a new group\n\t\t\t\t\ttempName+=\" \"+ownerList+\"\";\n\t\t\t\t\townerList = \"\";\n\t\t\t\t\tgroupNames.add(tempName);\n\t\t\t\t\tgroupSizes.add(Integer.valueOf(currGroupCount));\n\t\t\t\t\tcurrGroupCount = 0;\n\t\t\t\t\tcurrGroupCount++;\n\t\t\t\t\townerList += \"\\'\"+po.getSettingOwnerName()+\"\\'\";\n\t\t\t\t\tif(!po.getSettingOwnerName().equals(\"\"))tempName = po.getSettingOwnerClassName()+\" \\'\"+po.getSettingOwnerName()+\"\\'\";\n\t\t\t\t\tgroupStarts.add(Integer.valueOf(index));\n\t\t\t\t}\n\t\t\t\tlast = po;\n\t\t\t\tindex++;\n\t\t\t}\n\t\t\tif(owners.size() != 0)\n\t\t\t{\n\t\t\t\ttempName += \" \"+ownerList+\"\";\n\t\t\t\tgroupNames.add(tempName);\n\t\t\t\tgroupSizes.add(Integer.valueOf(currGroupCount));\n\t\t\t}\n\t\t\tif(currentGroup > owners.size()-1) currentGroup = 0;\n\t\t\tcomboModel = new DefaultComboBoxModel(groupNames.toArray());\n\t\t\tfireTableDataChanged();\n\t\t}\n\t\t\n\t\tpublic void refreshGroupNames()\n\t\t{\n\t\t\t//System.out.println(\"refreshing group names\");\n\t\t\tIterator it = owners.iterator();\n\t\t\tSettingOwner last = null;\n\t\t\tint currGroupCount = 0;\n\t\t\tString tempName = \"\";\n\t\t\tgroupNames = new ArrayList();\n\t\t\tint index = 0;\n\t\t\t\n\t\t\tString ownerList = \"\";\n\t\t\twhile(it.hasNext())\n\t\t\t{\n\t\t\t\t\n\t\t\t\t\n\t\t\t\tSettingOwner po = (SettingOwner)it.next();\n\t\t\t\tif(last == null)\n\t\t\t\t{\n\t\t\t\t\t//this is the first group\n\t\t\t\t\tcurrGroupCount++;\n\t\t\t\t\tif(!po.getSettingOwnerName().equals(\"\"))ownerList += \"\\'\"+po.getSettingOwnerName()+\"\\'\";\n\t\t\t\t\ttempName = po.getSettingOwnerClassName();\n\t\t\t\t\t//groupStarts.add(Integer.valueOf(0));\n\t\t\t\t}\n\t\t\t\telse if(po.getSettingOwnerID() == last.getSettingOwnerID())\n\t\t\t\t{\n\t\t\t\t\t//this is for the second or after in the sequence\n\t\t\t\t\tcurrGroupCount++;\n\t\t\t\t\t//tempName = \"\"+currGroupCount+\" \"+po.getClassDescriptor()+\"s\";\n\t\t\t\t\tif(!po.getSettingOwnerClassName().endsWith(\"s\"))\n\t\t\t\t\t\ttempName = po.getSettingOwnerClassName()+\"s\";\n\t\t\t\t\tif(!po.getSettingOwnerName().equals(\"\"))ownerList += \", \\'\"+po.getSettingOwnerName()+\"\\'\";\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\t//this starts a new group\n\t\t\t\t\ttempName+=\" \"+ownerList+\"\";\n\t\t\t\t\townerList = \"\";\n\t\t\t\t\tgroupNames.add(tempName);\n\t\t\t\t\t//System.out.println(\"adding: \"+tempName);\n\t\t\t\t\t//groupSizes.add(Integer.valueOf(currGroupCount));\n\t\t\t\t\tcurrGroupCount = 0;\n\t\t\t\t\tcurrGroupCount++;\n\t\t\t\t\townerList += \"\\'\"+po.getSettingOwnerName()+\"\\'\";\n\t\t\t\t\tif(!po.getSettingOwnerName().equals(\"\"))tempName = po.getSettingOwnerClassName()+\" \\'\"+po.getSettingOwnerName()+\"\\'\";\n\t\t\t\t\t//groupStarts.add(Integer.valueOf(index));\n\t\t\t\t}\n\t\t\t\tlast = po;\n\t\t\t\tindex++;\n\t\t\t}\n\t\t\tif(owners.size() != 0)\n\t\t\t{\n\t\t\t\ttempName += \" \"+ownerList+\"\";\n\t\t\t\tgroupNames.add(tempName);\n\t\t\t\t//System.out.println(\"adding \"+tempName);\n\t\t\t\t//groupSizes.add(Integer.valueOf(currGroupCount));\n\t\t\t}\n\t\t\t//if(currentGroup > owners.size()-1) currentGroup = 0;\n\t\t\tcomboModel = new DefaultComboBoxModel(groupNames.toArray());\n\t\t\t\n\t\t\t\n\t\t\tfireTableDataChanged();\n\t\t}\n\t\t\n\t\tpublic String getGroupName(int i)\n\t\t{\n\t\t\treturn (String)groupNames.get(i);\n\t\t}\n\t\t\n\t\tpublic int getNumGroupNames()\n\t\t{\n\t\t\treturn groupNames.size();\n\t\t}\n\t\t\n\t\t\n\t\tpublic int getRowCount()\n\t\t{\n\t\t\tif(groupNames.size() == 0) return 0;\n\t\t\tSettingOwner firstInGroup = (SettingOwner)owners.get(((Integer)groupStarts.get(currentGroup)).intValue());\n\t\t\treturn firstInGroup.getNumSettings();\n\t\t}\n\t\t\n\t\tpublic int getColumnCount()\n\t\t{\n\t\t\treturn 2;\n\t\t}\n\t\t\n\t\tpublic String getColumnName(int column)\n\t\t{\n\t\t\tif(column == 0) return \"Property\";\n\t\t\telse return \"Value\";\n\t\t}\n\t\t\n\t\tpublic Object getValueAt(int row, int column)\n\t\t{\n\t\t\tif(column == 0)\n\t\t\t{\n\t\t\t\tSettingOwner firstInGroup = (SettingOwner)owners.get(((Integer)groupStarts.get(currentGroup)).intValue());\n\t\t\t\t//System.out.println(\"firstInGroup = \"+firstInGroup);\n\t\t\t\treturn firstInGroup.getSetting(row).getName();\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\t\n\t\t\t\t//Simple if the selected owner group has only 1 member\n\t\t\t\tif(getCurrentGroupSize() == 1)\n\t\t\t\t{\n\t\t\t\t\tSettingOwner firstInGroup = getOwner(getCurrentGroupStart());\n\t\t\t\t\treturn firstInGroup.getSetting(row);\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\tArrayList currProps = new ArrayList();\n\t\t\t\t\tfor(int i = getCurrentGroupStart(); i < getCurrentGroupStart()+getCurrentGroupSize(); i++)\n\t\t\t\t\t{\n\t\t\t\t\t\tSettingOwner prop = getOwner(i);\n\t\t\t\t\t\tcurrProps.add(prop.getSetting(row));\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\treturn currProps;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic boolean isCellEditable(int row, int column)\n\t\t{\n\t\t\tif(column == 0)\n\t\t\t{\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\treturn getSelectedProperty(row).isEnabled();\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic Setting getSelectedProperty(int listIndex)\n\t\t{\n\t\t\tif(listIndex < 0) return null;\n\t\t\tSettingOwner firstInGroup = getOwner(getCurrentGroupStart());\n\t\t\treturn firstInGroup.getSetting(listIndex);\n\t\t\t\n\t\t}\n\t\t\n\t\tpublic void setValueAt(Object obj, int row, int column)\n\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\t//Simple if the selected owner group has only 1 member\n\t\t\t\tif(column == 1)\n\t\t\t\t{\n\t\t\t\t\tif(getCurrentGroupSize() == 1)\n\t\t\t\t\t{\n\t\t\t\t\t\t//System.out.println(\"setting called obj class is \"+obj.getClass().toString());\n\t\t\t\t\t\t//System.out.println(\"value = \"+obj.toString());\n\t\t\t\t\t\tSettingOwner firstInGroup = getOwner(getCurrentGroupStart());\n\t\t\t\t\t\tif(!obj.equals(SettingEditor.NOT_CHANGED_VALUE))\n\t\t\t\t\t\t\tfirstInGroup.getSetting(row).editValue(obj);\n\t\t\t\t\t}\n\t\t\t\t\telse\n\t\t\t\t\t{\n\t\t\t\t\t\t\n\t\t\t\t\t\tfor(int i = getCurrentGroupStart(); i < getCurrentGroupStart()+getCurrentGroupSize(); i++)\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tSettingOwner prop = getOwner(i);\n\t\t\t\t\t\t\tif(!obj.equals(SettingEditor.NOT_CHANGED_VALUE))\n\t\t\t\t\t\t\t\tprop.getSetting(row).editValue(obj);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tshouldRemove = true;\n\t\t\t}\n\t\t\tcatch(SettingException e)\n\t\t\t{\n\t\t\t\tString message;\n\t\t\t\tif(obj instanceof SettingException) //if the message has been passed by the editor\n\t\t\t\t{\n\t\t\t\t\tmessage = ((SettingException)obj).getMessage();\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\tmessage = e.getMessage();\n\t\t\t\t}\n\t\t\t\tJOptionPane.showMessageDialog(parent,message, \"Error\", JOptionPane.ERROR_MESSAGE);\n\t\t\t\tshouldRemove = false;\n\t\t\t}\n\t\t}\n\t\t\n\t\t/** Getter for property currentGroup.\n\t\t * @return Value of property currentGroup.\n\t\t *\n\t\t */\n\t\tpublic int getCurrentGroup()\n\t\t{\n\t\t\treturn currentGroup;\n\t\t}\n\t\t\n\t\tprotected int getCurrentGroupSize()\n\t\t{\n\t\t\treturn ((Integer)groupSizes.get(currentGroup)).intValue();\n\t\t}\n\t\t\n\t\tprotected int getCurrentGroupStart()\n\t\t{\n\t\t\treturn ((Integer)groupStarts.get(currentGroup)).intValue();\n\t\t}\n\t\t\n\t\tprotected String getCurrentGroupName()\n\t\t{\n\t\t\treturn (String)groupNames.get(currentGroup);\n\t\t}\n\t\t\n\t\tprotected SettingOwner getOwner(int i)\n\t\t{\n\t\t\treturn (SettingOwner)owners.get(i);\n\t\t}\n\t\t\n\t\tpublic int getNumGroups()\n\t\t{\n\t\t\treturn groupNames.size();\n\t\t}\n\t\t\n\t\t\n\t\t/** Setter for property currentGroup.\n\t\t * @param currentGroup New value of property currentGroup.\n\t\t *\n\t\t */\n\t\tpublic void setCurrentGroup(int currentGroup)\n\t\t{\n\t\t\tthis.currentGroup = currentGroup;\n\t\t\tfireTableDataChanged();\n\t\t}\n\t\t\n\t\t\n\t\t\n\t\t\n\t\t/** Getter for property comboModel.\n\t\t * @return Value of property comboModel.\n\t\t *\n\t\t */\n\t\tpublic javax.swing.DefaultComboBoxModel getComboModel()\n\t\t{\n\t\t\treturn comboModel;\n\t\t}\n\t\t\n\t}\n\t\n\tpublic static void printArray(ArrayList a)\n\t{\n\t\tSystem.out.print(\"(\");\n\t\tfor(int i = 0; i < a.size(); i++)\n\t\t\tSystem.out.print(a.get(i)+\" \");\n\t\t//System.out.println(\")\");\n\t}\n\t\n\t\n\t\n\t\n\t\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/SingleLineStringEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.event.*;\nimport java.awt.event.*;\nimport java.util.*;\n\npublic class SingleLineStringEditor implements SettingEditor, CaretListener, FocusListener\n{\n    private JTextField field;\n    private Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n    \n    private JTable lastTable = null;\n    private int tableCol = -1;\n    private int tableRow = -1;\n    \n    private boolean valueGot = true;\n    \n    private boolean multiDifferent = false;\n    \n    \n    /** Creates a new instance of SingleLineStringEditor */\n    public SingleLineStringEditor()\n    {\n        field = new JTextField();\n        field.addCaretListener(this);\n        field.addFocusListener(this);\n    }\n    \n    public Object getEditorValue()\n    {\n        if(multiDifferent && field.getText().equals(\"\"))\n        {\n            valueGot = true;\n            multiDifferent =false;\n            return NOT_CHANGED_VALUE;\n        }\n        else\n        {\n            valueGot = true;\n            return field.getText();\n        }\n    }\n    \n    public Component getTableCellEditorComponent(JTable table, Setting owner, Object value, boolean isSelected, int row, int column)\n    {\n        field.setMargin(new Insets(0, 2, 4, 2));\n        if (isSelected)\n        {\n            field.setForeground(table.getSelectionForeground());\n            field.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            field.setForeground(table.getForeground());\n            field.setBackground(table.getBackground());\n        }\n        \n        \n        field.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        \n        multiDifferent = false;\n        \n        if(value instanceof String)\n        {\n            String str = (String)value;\n            \n            field.setText(str);\n\n\t    \n            field.setCaretColor(Color.black);\n            \n            field.setFont(font);\n        }\n        else if(value instanceof ArrayList)\n        {\n            ArrayList values = (ArrayList)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                String last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof String)\n                    {\n                        String str = (String)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    field.setText(last);\n                    \n                    field.setFont(font);\n                }\n                else\n                {\n                    field.setText(\"\");\n                    field.setFont(font);\n                    multiDifferent = true;\n                }\n                \n            }\n        }\n        \n        lastTable = table;\n        tableRow = row;\n        tableCol = column;\n        valueGot = false;\n        \n        return field;\n    }\n    \n    public void stopEditing()\n    {\n    \t\n    }\n    \n    public void caretUpdate(CaretEvent e)\n    {\n        field.getCaret().setVisible(true);\n    }\n    \n    public void focusGained(FocusEvent e)\n    {\n    }\n    \n    public void focusLost(FocusEvent e)\n    {\n        if(!valueGot && lastTable != null)\n        {\n            if(multiDifferent && field.getText().equals(\"\"))\n            {\n                valueGot = true;\n                multiDifferent = false;\n            }\n            else\n            {\n                valueGot = true;\n                lastTable.setValueAt(field.getText(), tableRow, tableCol);\n            }\n            if(lastTable.getCellEditor() != null) lastTable.removeEditor();\n        }\n        else\n        {\n            multiDifferent = false;\n        }\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/settings/SingleLineStringRenderer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\npublic class SingleLineStringRenderer implements SettingRenderer \n{\n    private JTextField field = new JTextField();\n    private Font font = new Font(\"monospaced\", Font.PLAIN, 12);\n    private Font font2 = new Font(\"monospaced\", Font.ITALIC, 12);\n    \n    \n    public Component getTableCellRendererComponent(JTable table, Setting owner, Object value, boolean isSelected, boolean hasFocus, boolean isEnabled, int row, int column)\n    {\n        field.setMargin(new Insets(0, 2, 4, 2));\n        if (isSelected)\n        {\n            field.setForeground(table.getSelectionForeground());\n            field.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            field.setForeground(table.getForeground());\n            field.setBackground(table.getBackground());\n        }\n        \n        if(hasFocus)\n        {\n            field.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        }\n        else\n        {\n            field.setBorder(new EmptyBorder(1, 2, 2, 1));\n        }\n        \n        if(value instanceof String)\n        {\n            String str = (String)value;\n            \n            field.setText(str);\n            \n            field.setEnabled(isEnabled);\n            field.setEditable(isEnabled);\n            field.setCaretColor(isEnabled?Color.black:Color.white);\n            \n            field.setFont(font);\n        }\n        else if(value instanceof ArrayList)\n        {\n            ArrayList values = (ArrayList)value;\n            if(values.size() > 0)\n            {\n                //if we have multiple properties selected.\n                String last = null;\n                boolean allSame = true;\n                for(int i = 0; i < values.size(); i++)\n                {\n                    if(values.get(i) instanceof String)\n                    {\n                        String str = (String)values.get(i);\n                        if(last != null)\n                        {\n                            if(!str.equals(last))\n                            {\n                                allSame = false; break;\n                            }\n                            last = str;\n                        }\n                        else\n                        {\n                            last = str;\n                        }\n                    }\n                }\n                if(allSame)\n                {\n                    field.setText(last);\n                    \n                    field.setEnabled(isEnabled);\n                    field.setEditable(isEnabled);\n                    field.setCaretColor(isEnabled?Color.black:Color.white);\n            \n                    field.setFont(font);\n                }\n                else\n                {\n                    field.setText(\"(Different values)\");\n                    \n                    field.setEnabled(isEnabled);\n                    field.setEditable(isEnabled);\n                    field.setCaretColor(isEnabled?Color.black:Color.white);\n                    field.setBackground(Color.lightGray);\n                    field.setFont(font2);\n                }\n                \n            }\n        }\n        \n        \n        return field;\n    }\n\t\n}\n"
  },
  {
    "path": "prism/src/settings/SingleLineStringSetting.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic class SingleLineStringSetting extends Setting\n{\n    private static SingleLineStringRenderer renderer;\n    private static SingleLineStringEditor editor;\n    \n    /** Creates a new instance of SingleLineStringSetting */\n\tpublic SingleLineStringSetting(String name, String value, String comment, SettingOwner owner, boolean editableWhenMultiple, StringConstraint constraint)\n    {\n        super(name, value, comment, owner, editableWhenMultiple, constraint);\n    }\n\t\n    public SingleLineStringSetting(String name, String value, String comment, SettingOwner owner, boolean editableWhenMultiple)\n    {\n        super(name, value, comment, owner, editableWhenMultiple);\n    }\n    \n    public SettingEditor getSettingEditor()\n    {\n        if (editor == null) {\n            editor = new SingleLineStringEditor();\n        }\n        return editor;\n    }\n    \n    public SettingRenderer getSettingRenderer()\n    {\n        if (renderer == null) {\n            renderer = new SingleLineStringRenderer();\n        }\n        return renderer;\n    }\n    \n    public Class getValueClass()\n    {\n        return String.class;\n    }\n    \n    public void checkObjectWithConstraints(Object obj) throws SettingException\n    {\n        super.checkObjectWithConstraints(obj);\n\t\t\n\t\tif(obj.toString().lastIndexOf('\\n') != -1) //search for newline breaks.\n\t\t\tthrow new SettingException(\"Single line settings cannot contain newline breaks.\");\n    }\n    \n    public String getStringValue()\n    {\n        return getValue().toString();\n    }\n    \n\tpublic Object parseStringValue(String string) throws SettingException\n\t{\n\t\treturn string;\n\t}\t\n    \n\tpublic String toString()\n\t{\n\t\treturn getStringValue();\n\t}\n    \n}\n"
  },
  {
    "path": "prism/src/settings/StringConstraint.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\npublic abstract class StringConstraint implements SettingConstraint\n{\n\t/** Creates a new instance of StringConstraint */\n\tpublic StringConstraint()\n\t{\n\t}\n\t\n\tpublic void checkValue(Object value) throws SettingException\n\t{\n\t\tcheckValueString(value.toString());\n\t}\n\t\n\tpublic abstract void checkValueString(String str) throws SettingException;\n}\n"
  },
  {
    "path": "prism/src/settings/TableResizer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage settings;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport java.awt.event.*;\nimport javax.swing.event.*;\n\npublic class TableResizer extends MouseInputAdapter\n{\n    \n    \n    private int col;\n    private boolean colSel;\n    private boolean colSelectionAllowed;\n    private int startWidth;\n    private int startX;\n    private JTable table;\n    private boolean active;\n    private boolean rowSelectionAllowed;\n    private int row;\n    private int startY;\n    private int startHeight;\n    private static final int PIXELS = 5;\n    private Cursor lastCursor;\n    private static Cursor S_resizeCursor = Cursor.getPredefinedCursor(Cursor.S_RESIZE_CURSOR);\n    private static Cursor E_resizeCursor = Cursor.getPredefinedCursor(Cursor.E_RESIZE_CURSOR);\n    \n    \n    \n    public TableResizer(JTable table)\n    {\n        this.table = table;\n        this.table.addMouseListener(this);\n        this.table.addMouseMotionListener(this);\n        this.row = -1;\n        this.col = -1;\n    }\n    \n    \n    public void done()\n    {\n        if (this.table == null) return;\n        this.table.removeMouseListener(this);\n        this.table.removeMouseMotionListener(this);\n    }\n    \n    \n    public void mouseMoved(MouseEvent e)\n    {\n        Point p = e.getPoint();\n        if (this.isMouseOverColMargin(p))\n        {\n            if (this.lastCursor == null)\n            {\n                this.lastCursor = this.table.getCursor();\n            }\n            this.table.setCursor(E_resizeCursor);\n        } \n        else\n        {\n            this.table.setCursor(this.lastCursor);\n        }\n    }\n    \n    public void mousePressed(MouseEvent e)\n    {\n        Point p = e.getPoint();\n        if (this.isMouseOverColMargin(p))\n        {\n            this.active = true;\n            this.startX = p.x;\n            //this.startWidth = table.getWidth();\n            startWidth = this.table.getColumnModel().getColumn(col).getWidth();\n            this.colSelectionAllowed = this.table.getColumnSelectionAllowed();\n            this.table.setColumnSelectionAllowed(false);\n            colSel = true;\n        }\n    }\n    \n    public void mouseDragged(MouseEvent e)\n    {\n        Point p = e.getPoint();\n        if (!active) return;\n        if (colSel)\n        {\n            int newWidth = e.getX();\n            newWidth = Math.max(10, newWidth);\n            \n            if(newWidth > table.getWidth()-10) newWidth = table.getWidth()-10;\n            this.table.getColumnModel().getColumn(col).setMinWidth(newWidth);\n            this.table.getColumnModel().getColumn(col).setMaxWidth(newWidth);\n            this.table.getColumnModel().getColumn(col).setPreferredWidth(newWidth);\n        }\n    }\n    \n    public void mouseReleased(MouseEvent e)\n    {\n        if (!active) return;\n        if (colSel)\n        {\n            this.table.setColumnSelectionAllowed(this.colSelectionAllowed);\n            this.col = -1;\n            colSel = false;\n        }\n        this.active = false;\n        \n    }\n    \n    private boolean isMouseOverColMargin(Point p)\n    {\n        if (!table.isEnabled()) return false;\n        this.row = table.rowAtPoint(p);\n        this.col = table.columnAtPoint(p);\n        if (row == -1 || col == -1) return false;\n        Rectangle r = table.getCellRect(row, col, true);\n        if (p.x >= r.x + r.width - PIXELS)\n        {\n            return true;\n        }\n        return false;\n    }\n    \n    public static void main(String[]args)\n    {\n        JFrame frame = new JFrame(\"Test\");\n        \n        String [][] data = { {\"a\", \"b\"}, {\"c\", \"d\"}, {\"e\",\"f\"}};\n        String [] columns = { \"1\", \"2\"};\n        \n        JTable tab = new JTable(data, columns);\n        frame.getContentPane().setLayout(new BorderLayout());\n        frame.getContentPane().add(tab, BorderLayout.CENTER);\n        \n        tab.setPreferredSize(new Dimension(200,200));\n        \n        TableResizer lll = new TableResizer(tab);\n        \n        tab.addMouseListener(lll);\n        tab.addMouseMotionListener(lll);\n        \n        tab.setAutoResizeMode(JTable.AUTO_RESIZE_SUBSEQUENT_COLUMNS);\n        \n        frame.pack();\n        frame.show();\n    }\n}\n"
  },
  {
    "path": "prism/src/settings/package-info.java",
    "content": "/**\n * Generic 'settings' functionality.\n */\npackage settings;\n"
  },
  {
    "path": "prism/src/simulator/Choice.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport parser.State;\nimport parser.VarList;\nimport parser.ast.Expression;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLangException;\n\n/**\n * Representation of a single (nondeterministic) choice in a PRISM model,\n * i.e, a list of transitions, each specified by updates to variables.\n */\npublic interface Choice<Value>\n{\n\t/**\n\t * Scale probability/rate of all transitions, multiplying by d.\n\t */\n\tpublic void scaleProbabilitiesBy(Value d);\n\t\n\t/**\n\t * Get the module/action for this choice, as an integer index\n\t * (-i for independent in ith module, i for synchronous on ith action)\n\t * (in both cases, modules/actions are 1-indexed)\n\t */\n\tpublic int getModuleOrActionIndex();\n\t\n\t/**\n\t * Get the module/action for this choice, as a string\n\t * (form is \"module\" or \"[action]\")\n\t */\n\tpublic String getModuleOrAction();\n\t\n\t/**\n\t * For real-time models, get the clock ,\n\t * i.e., an expression over clock variables denoting when it can be taken.\n\t * If there is no guard, this returns null;\n\t */\n\tpublic default Expression getClockGuard()\n\t{\n\t\treturn null;\n\t}\n\t\n\t/**\n\t * Get the number of transitions in this choice.\n\t */\n\tpublic int size();\n\t\n\t/**\n\t * Get the updates of the ith transition, as a string.\n\t * This is in abbreviated form, i.e. x'=1, rather than x'=x+1.\n\t * Format is: x'=1, y'=0, with empty string for empty update.\n\t * Only variables updated are included in list (even if unchanged).\n\t */\n\tpublic String getUpdateString(int i, State currentState) throws PrismLangException;\n\t\n\t/**\n\t * Get the updates of the ith transition, as a string.\n\t * This is in full, i.e. of the form x'=x+1, rather than x'=1.\n\t * Format is: (x'=x+1) & (y'=y-1), with empty string for empty update.\n\t * Only variables updated are included in list.\n\t * Note that expressions may have been simplified from original model. \n\t */\n\tpublic String getUpdateStringFull(int i);\n\t\n\t/**\n\t * Compute the target for the ith transition, based on a current state,\n\t * returning the result as a new State object copied from the existing one.\n\t */\n\tpublic State computeTarget(int i, State currentState, VarList varList) throws PrismLangException;\n\t\n\t/**\n\t * Compute the target for the ith transition, based on a current state.\n\t * Apply changes in variables to a provided copy of the State object.\n\t * (i.e. currentState and newState should be equal when passed in.) \n\t */\n\tpublic void computeTarget(int i, State currentState, State newState, VarList varList) throws PrismLangException;\n\t\n\t/**\n\t * Get the probability/rate for the ith transition.\n\t */\n\tpublic Value getProbability(int i);\n\t\n\t/**\n\t * Get the sum of probabilities/rates for all transitions.\n\t */\n\tpublic Value getProbabilitySum();\n\t\n\t/**\n\t * Return the index of a transition according to a probability (or rate) sum, x.\n\t * i.e. return the index of the first transition in this choice for which the\n\t * sum of probabilities/rates for that and all prior transitions exceeds x.\n\t */\n\tpublic int getIndexByProbabilitySum(Value x);\n\t\n\tpublic void checkValid(ModelType modelType) throws PrismException;\n\t\n\t/**\n\t * Check whether the transitions in this choice (from a particular state)\n\t * would cause any errors, mainly variable overflows.\n\t * Variable ranges are specified in the passed in VarList.\n\t * Throws an exception if such an error occurs.\n\t */\n\tpublic void checkForErrors(State currentState, VarList varList) throws PrismException;\n}\n"
  },
  {
    "path": "prism/src/simulator/ChoiceListFlexi.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.State;\nimport parser.VarList;\nimport parser.ast.Command;\nimport parser.ast.Expression;\nimport parser.ast.Update;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLangException;\n\n/**\n * A mutable implementation of {@link simulator.Choice},\n * i.e, a representation of a single (nondeterministic) choice in a PRISM model,\n * in the form of a list of transitions, each specified by updates to variables.\n */\npublic class ChoiceListFlexi<Value> implements Choice<Value>\n{\n\t// Evaluator for values/states\n\tprotected Evaluator<Value> eval;\n\t\n\t// Module/action info, encoded as an integer.\n\t// For an independent (non-synchronous) choice, this is -i,\n\t// where i is the 1-indexed module index.\n\t// For a synchronous choice, this is the 1-indexed action index.\n\tprotected int moduleOrActionIndex;\n\n\t// List of multiple updates and associated probabilities/rates\n\t// Probabilities/rates are already (partially) evaluated,\n\t// target states are just stored as lists of updates (for efficiency)\n\tprotected List<List<Update>> updates;\n\tprotected List<Value> probability;\n\t\n\t// For real-time models, the clock guard,\n\t// i.e., an expression over clock variables\n\t// denoting when it can be taken.\n\tprotected Expression clockGuard;\n\n\t/**\n\t * Create empty choice.\n\t */\n\tpublic ChoiceListFlexi(Evaluator<Value> eval)\n\t{\n\t\t// Store evaluator\n\t\tthis.eval = eval;\n\t\t// Initialise\n\t\tupdates = new ArrayList<List<Update>>();\n\t\tprobability = new ArrayList<Value>();\n\t\tclockGuard = null;\n\t}\n\n\t/**\n\t * Copy constructor.\n\t * NB: Does a shallow, not deep, copy with respect to references to probability/update objects.\n\t */\n\tpublic ChoiceListFlexi(ChoiceListFlexi<Value> ch)\n\t{\n\t\teval = ch.eval;\n\t\tmoduleOrActionIndex = ch.moduleOrActionIndex;\n\t\tupdates = new ArrayList<List<Update>>(ch.updates.size());\n\t\tfor (List<Update> list : ch.updates) {\n\t\t\tList<Update> listNew = new ArrayList<Update>(list.size()); \n\t\t\tupdates.add(listNew);\n\t\t\tfor (Update up : list) {\n\t\t\t\tlistNew.add(up);\n\t\t\t}\n\t\t}\n\t\tprobability = new ArrayList<Value>(ch.size());\n\t\tfor (Value p : ch.probability) {\n\t\t\tprobability.add(p);\n\t\t}\n\t\tclockGuard = ch.clockGuard;\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Set the module/action for this choice, encoded as an integer\n\t * (-i for independent in ith module, i for synchronous on ith action)\n\t * (in both cases, modules/actions are 1-indexed)\n\t */\n\tpublic void setModuleOrActionIndex(int moduleOrActionIndex)\n\t{\n\t\tthis.moduleOrActionIndex = moduleOrActionIndex;\n\t}\n\n\t/**\n\t * Set the clock guard\n\t */\n\tpublic void setClockGuard(Expression clockGuard)\n\t{\n\t\tthis.clockGuard = clockGuard;\n\t}\n\n\t/**\n\t * Add a transition to this choice.\n\t * @param probability Probability (or rate) of the transition\n\t * @param ups List of Update objects defining transition\n\t */\n\tpublic void add(Value probability, List<Update> ups)\n\t{\n\t\tthis.updates.add(ups);\n\t\tthis.probability.add(probability);\n\t}\n\n\t@Override\n\tpublic void scaleProbabilitiesBy(Value d)\n\t{\n\t\tint i, n;\n\t\tn = size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tprobability.set(i, eval.multiply(probability.get(i), d));\n\t\t}\n\t}\n\n\t/**\n\t * Modify this choice, constructing product of it with another.\n\t */\n\tpublic void productWith(ChoiceListFlexi<Value> ch)\n\t{\n\t\tList<Update> list;\n\t\tint i, j, n, n2;\n\t\tValue pi;\n\n\t\tn = ch.size();\n\t\tn2 = size();\n\t\t// Loop through each (ith) element of new choice (skipping first)\n\t\tfor (i = 1; i < n; i++) {\n\t\t\tpi = ch.getProbability(i);\n\t\t\t// Loop through each (jth) element of existing choice\n\t\t\tfor (j = 0; j < n2; j++) {\n\t\t\t\t// Create new element (i,j) of product \n\t\t\t\tlist = new ArrayList<Update>(updates.get(j).size() + ch.updates.get(i).size());\n\t\t\t\tfor (Update u : updates.get(j)) {\n\t\t\t\t\tlist.add(u);\n\t\t\t\t}\n\t\t\t\tfor (Update u : ch.updates.get(i)) {\n\t\t\t\t\tlist.add(u);\n\t\t\t\t}\n\t\t\t\tadd(eval.multiply(pi, getProbability(j)), list);\n\t\t\t}\n\t\t}\n\t\t// Modify elements of current choice to get (0,j) elements of product\n\t\tpi = ch.getProbability(0);\n\t\tfor (j = 0; j < n2; j++) {\n\t\t\tfor (Update u : ch.updates.get(0)) {\n\t\t\t\tupdates.get(j).add(u);\n\t\t\t}\n\t\t\tprobability.set(j, eval.multiply(pi, probability.get(j)));\n\t\t}\n\t\tif (ch.clockGuard != null) {\n\t\t\tclockGuard = (clockGuard == null) ? ch.clockGuard : Expression.And(clockGuard, ch.clockGuard);\n\t\t}\n\t}\n\n\t// Get methods\n\n\t@Override\n\tpublic int getModuleOrActionIndex()\n\t{\n\t\treturn moduleOrActionIndex;\n\t}\n\n\t@Override\n\tpublic String getModuleOrAction()\n\t{\n\t\t// Action label (or absence of) will be the same for all updates in a choice\n\t\tUpdate u = updates.get(0).get(0);\n\t\tCommand c = u.getParent().getParent();\n\t\tif (\"\".equals(c.getSynch()))\n\t\t\treturn c.getParent().getName();\n\t\telse\n\t\t\treturn \"[\" + c.getSynch() + \"]\";\n\t}\n\n\t@Override\n\tpublic Expression getClockGuard()\n\t{\n\t\treturn clockGuard;\n\t}\n\t\n\t@Override\n\tpublic int size()\n\t{\n\t\treturn probability.size();\n\t}\n\n\t@Override\n\tpublic String getUpdateString(int i, State currentState) throws PrismLangException\n\t{\n\t\tint j, n;\n\t\tString s = \"\";\n\t\tboolean first = true;\n\t\tfor (Update up : updates.get(i)) {\n\t\t\tn = up.getNumElements();\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\tif (first)\n\t\t\t\t\tfirst = false;\n\t\t\t\telse\n\t\t\t\t\ts += \", \";\n\t\t\t\ts += up.getVar(j) + \"'=\" + up.getExpression(j).evaluate(currentState);\n\t\t\t}\n\t\t}\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic String getUpdateStringFull(int i)\n\t{\n\t\tString s = \"\";\n\t\tboolean first = true;\n\t\tfor (Update up : updates.get(i)) {\n\t\t\tif (up.getNumElements() == 0)\n\t\t\t\tcontinue;\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\ts += \" & \";\n\t\t\ts += up;\n\t\t}\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic State computeTarget(int i, State currentState, VarList varList) throws PrismLangException\n\t{\n\t\tState newState = new State(currentState);\n\t\tfor (Update up : updates.get(i))\n\t\t\tup.update(currentState, newState, eval.exact(), varList);\n\t\treturn newState;\n\t}\n\n\t@Override\n\tpublic void computeTarget(int i, State currentState, State newState, VarList varList) throws PrismLangException\n\t{\n\t\tfor (Update up : updates.get(i))\n\t\t\tup.update(currentState, newState, eval.exact(), varList);\n\t}\n\n\t@Override\n\tpublic Value getProbability(int i)\n\t{\n\t\treturn probability.get(i);\n\t}\n\n\t@Override\n\tpublic Value getProbabilitySum()\n\t{\n\t\tValue sum = eval.zero();\n\t\tfor (Value p : probability) {\n\t\t\tsum = eval.add(sum, p);\n\t\t}\n\t\treturn sum;\n\t}\n\n\t@Override\n\tpublic int getIndexByProbabilitySum(Value x)\n\t{\n\t\tValue d = eval.zero();\n\t\tint n = size();\n\t\tint i;\n\t\tfor (i = 0; eval.geq(x, d) && i < n; i++) {\n\t\t\td = eval.add(d, probability.get(i));\n\t\t}\n\t\treturn i - 1;\n\t}\n\t\n\t@Override\n\tpublic void checkValid(ModelType modelType) throws PrismException\n\t{\n\t\t// Currently nothing to do here:\n\t\t// Checks for bad probabilities/rates done earlier.\n\t}\n\t\n\t@Override\n\tpublic void checkForErrors(State currentState, VarList varList) throws PrismException\n\t{\n\t\tint i, n;\n\t\tn = size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tfor (Update up : updates.get(i))\n\t\t\t\tup.checkUpdate(currentState, varList);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i, n;\n\t\tboolean first = true;\n\t\tString s = \"\";\n\t\tif (clockGuard != null) {\n\t\t\ts += \"(\" + clockGuard + \")\";\n\t\t}\n\t\tn = size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\ts += \" + \";\n\t\t\ts += getProbability(i) + \":\" + updates.get(i);\n\t\t}\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/GenerateSimulationPath.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.io.File;\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.State;\nimport parser.VarList;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\nimport prism.PrismLogWrapper;\nimport userinterface.graph.Graph;\n\n/**\n * Class to generate a path in the simulator (i.e., in an instance of SimulatorEngine).\n * It is assumed that the model to be simulated has already been loaded into the simulator.\n * Path generation is configurable via a command-line style string.\n */\npublic class GenerateSimulationPath\n{\n\t// The simulator engine and a log for output\n\tprivate SimulatorEngine engine;\n\tprivate PrismLog mainLog;\n\n\t// Store warnings\n\tprivate List<String> warnings = new ArrayList<String>();\n\n\t// Enums\n\tprivate enum PathType {\n\t\tSIM_PATH_NUM_STEPS, SIM_PATH_TIME, SIM_PATH_DEADLOCK\n\t};\n\n\t// Basic info needed for path\n\tprivate State initialState;\n\tprivate long maxPathLength;\n\tprivate File file;\n\n\t// Path configuration options\n\tprivate PathType simPathType = null;\n\tprivate int simPathLength = 0;\n\tprivate double simPathTime = 0.0;\n\tprivate String simPathSep = \" \";\n\tprivate ArrayList<Integer> simVars = null;\n\tprivate boolean simLoopCheck = true;\n\tprivate int simPathRepeat = 1;\n\tprivate boolean simPathShowProbs = false;\n\tprivate boolean simPathShowRewards = false;\n\tprivate boolean simPathShowChangesOnly = false;\n\tprivate boolean simPathSnapshots = false;\n\tprivate double simPathSnapshotTime = 0.0;\n\n\tpublic int getNumWarnings()\n\t{\n\t\treturn warnings.size();\n\t}\n\n\tpublic List<String> getWarnings()\n\t{\n\t\treturn warnings;\n\t}\n\n\t/**\n\t * Send a warning messages to the log;\n\t * also, store a copy for later retrieval.\n\t */\n\tprivate void warning(String msg)\n\t{\n\t\tmainLog.printWarning(msg + \".\");\n\t\twarnings.add(msg);\n\t}\n\n\tpublic GenerateSimulationPath(SimulatorEngine engine, PrismLog mainLog)\n\t{\n\t\tthis.engine = engine;\n\t\tthis.mainLog = mainLog;\n\t}\n\n\t/**\n\t * Generate and export a random path through a model with the simulator.\n\t * @param initialState Initial state (if null, is selected randomly)\n\t * @param details Information about the path to be generated\n\t * @param file File to output the path to (stdout if null)\n\t */\n\tpublic void generateSimulationPath(State initialState, String details, long maxPathLength, File file) throws PrismException\n\t{\n\t\tthis.initialState = initialState;\n\t\tthis.maxPathLength = maxPathLength;\n\t\tthis.file = file;\n\t\twarnings.clear();\n\n\t\tparseDetails(details);\n\t\tPathDisplayer displayer = generateDisplayerForExport();\n\t\tif (simPathType == PathType.SIM_PATH_DEADLOCK)\n\t\t\tgenerateMultiplePaths(displayer);\n\t\telse\n\t\t\tgeneratePath(displayer);\n\t\tdisplayer.close();\n\t}\n\n\t/**\n\t * Generate and plot a random path through a model with the simulator.\n\t * @param initialState Initial state (if null, is selected randomly)\n\t * @param details Information about the path to be generated\n\t */\n\tpublic void generateAndPlotSimulationPath(State initialState, String details, long maxPathLength, Graph graphModel)\n\t\t\tthrows PrismException\n\t{\n\t\tthis.initialState = initialState;\n\t\tthis.maxPathLength = maxPathLength;\n\n\t\tparseDetails(details);\n\t\tPathDisplayer displayer = generateDisplayerForPlotting(graphModel);\n\t\tif (simPathType == PathType.SIM_PATH_DEADLOCK)\n\t\t\tgenerateMultiplePaths(displayer);\n\t\telse\n\t\t\tgeneratePath(displayer);\n\t}\n\n\t/**\n\t * Generate and plot a random path through a model with the simulator, in a separate thread.\n\t * @param initialState Initial state (if null, is selected randomly)\n\t * @param details Information about the path to be generated\n\t */\n\tpublic void generateAndPlotSimulationPathInThread(State initialState, String details, long maxPathLength, Graph graphModel)\n\t\t\tthrows PrismException\n\t{\n\t\tnew GenerateAndPlotThread(initialState, details, maxPathLength, graphModel).start();\n\t}\n\n\t/**\n\t * Parse a string specifying how to generate a simulation path.\n\t */\n\tprivate void parseDetails(String details) throws PrismException\n\t{\n\t\tString s, ss[];\n\t\tint i, j, n;\n\t\tboolean done;\n\t\tboolean varsOptionGiven = false;\n\t\tboolean changesFalseOptionGiven = false;\n\n\t\tss = details.split(\",\");\n\t\tn = ss.length;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (ss[i].indexOf(\"time=\") == 0) {\n\t\t\t\t// path with upper time limit\n\t\t\t\tsimPathType = PathType.SIM_PATH_TIME;\n\t\t\t\ttry {\n\t\t\t\t\tsimPathTime = Double.parseDouble(ss[i].substring(5));\n\t\t\t\t\tif (simPathTime < 0.0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid path time limit \\\"\" + ss[i] + \"\\\"\");\n\t\t\t\t}\n\t\t\t} else if (ss[i].equals(\"deadlock\")) {\n\t\t\t\t// path until deadlock\n\t\t\t\tsimPathType = PathType.SIM_PATH_DEADLOCK;\n\t\t\t} else if (ss[i].indexOf(\"sep=\") == 0) {\n\t\t\t\t// specify column separator to display path\n\t\t\t\tsimPathSep = ss[i].substring(4);\n\t\t\t\tif (simPathSep.equals(\"space\")) {\n\t\t\t\t\tsimPathSep = \" \";\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (simPathSep.equals(\"tab\")) {\n\t\t\t\t\tsimPathSep = \"\\t\";\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (simPathSep.equals(\"comma\")) {\n\t\t\t\t\tsimPathSep = \",\";\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tthrow new PrismException(\"Separator must be one of: \\\"space\\\", \\\"tab\\\", \\\"comma\\\"\");\n\t\t\t} else if (ss[i].indexOf(\"vars=\") == 0) {\n\t\t\t\tvarsOptionGiven = true;\n\t\t\t\t// Build list of indices of variables to display\n\t\t\t\tVarList varList = engine.getModel().createVarList();\n\t\t\t\tsimVars = new ArrayList<Integer>();\n\t\t\t\tdone = false;\n\t\t\t\ts = ss[i].substring(5);\n\t\t\t\tif (s.length() < 1 || s.charAt(0) != '(')\n\t\t\t\t\tthrow new PrismException(\"Invalid format for \\\"vars=(...)\\\"\");\n\t\t\t\ts = s.substring(1);\n\t\t\t\tif (s.indexOf(')') > -1) {\n\t\t\t\t\ts = s.substring(0, s.length() - 1);\n\t\t\t\t\tdone = true;\n\t\t\t\t}\n\t\t\t\tif (s.length() > 0) {\n\t\t\t\t\tj = varList.getIndex(s);\n\t\t\t\t\tif (j == -1)\n\t\t\t\t\t\tthrow new PrismException(\"Unknown variable \\\"\" + s + \"\\\" in \\\"vars=(...)\\\" list\");\n\t\t\t\t\tsimVars.add(j);\n\t\t\t\t}\n\t\t\t\twhile (i < n && !done) {\n\t\t\t\t\ts = ss[++i];\n\t\t\t\t\tif (s.indexOf(')') > -1) {\n\t\t\t\t\t\ts = s.substring(0, s.length() - 1);\n\t\t\t\t\t\tdone = true;\n\t\t\t\t\t}\n\t\t\t\t\tj = varList.getIndex(s);\n\t\t\t\t\tif (j == -1)\n\t\t\t\t\t\tthrow new PrismException(\"Unknown variable \\\"\" + s + \"\\\" in \\\"vars=(...)\\\" list\");\n\t\t\t\t\tsimVars.add(j);\n\t\t\t\t}\n\t\t\t} else if (ss[i].indexOf(\"loopcheck=\") == 0) {\n\t\t\t\t// switch loop detection on/off (default is on)\n\t\t\t\ts = ss[i].substring(10);\n\t\t\t\tif (s.equals(\"true\")) {\n\t\t\t\t\tsimLoopCheck = true;\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tif (s.equals(\"false\")) {\n\t\t\t\t\tsimLoopCheck = false;\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\t\t\t\tthrow new PrismException(\"Value for \\\"loopcheck\\\" flag must be \\\"true\\\" or \\\"false\\\"\");\n\t\t\t} else if (ss[i].indexOf(\"repeat=\") == 0) {\n\t\t\t\t// how many times to repeat path generation until successful (for \"deadlock\" option)\n\t\t\t\ttry {\n\t\t\t\t\tsimPathRepeat = Integer.parseInt(ss[i].substring(7));\n\t\t\t\t\tif (simPathRepeat < 1)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Value for \\\"repeat\\\" option must be a positive integer\");\n\t\t\t\t}\n\t\t\t} else if (ss[i].indexOf(\"snapshot=\") == 0) {\n\t\t\t\t// print timed snapshots of path\n\t\t\t\ttry {\n\t\t\t\t\tsimPathSnapshots = true;\n\t\t\t\t\tsimPathSnapshotTime = Double.parseDouble(ss[i].substring(9));\n\t\t\t\t\tif (simPathSnapshotTime <= 0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Value for \\\"snapshot\\\" option must be a positive double\");\n\t\t\t\t}\n\t\t\t} else if (ss[i].indexOf(\"probs=\") == 0) {\n\t\t\t\t// display probabilities/rates?\n\t\t\t\tString bool = ss[i].substring(6).toLowerCase();\n\t\t\t\tif (bool.equals(\"true\"))\n\t\t\t\t\tsimPathShowProbs = true;\n\t\t\t\telse if (bool.equals(\"false\"))\n\t\t\t\t\tsimPathShowProbs = false;\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Value for \\\"rewards\\\" option must \\\"true\\\" or \\\"false\\\"\");\n\t\t\t} else if (ss[i].indexOf(\"rewards=\") == 0) {\n\t\t\t\t// display rewards?\n\t\t\t\tString bool = ss[i].substring(8).toLowerCase();\n\t\t\t\tif (bool.equals(\"true\"))\n\t\t\t\t\tsimPathShowRewards = true;\n\t\t\t\telse if (bool.equals(\"false\"))\n\t\t\t\t\tsimPathShowRewards = false;\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Value for \\\"rewards\\\" option must \\\"true\\\" or \\\"false\\\"\");\n\t\t\t} else if (ss[i].indexOf(\"changes=\") == 0) {\n\t\t\t\t// display changes only?\n\t\t\t\tString bool = ss[i].substring(8).toLowerCase();\n\t\t\t\tif (bool.equals(\"true\")) {\n\t\t\t\t\tsimPathShowChangesOnly = true;\n\t\t\t\t} else if (bool.equals(\"false\")) {\n\t\t\t\t\tchangesFalseOptionGiven = true;\n\t\t\t\t\tsimPathShowChangesOnly = false;\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t\tthrow new PrismException(\"Value for \\\"changes\\\" option must \\\"true\\\" or \\\"false\\\"\");\n\t\t\t} else {\n\t\t\t\t// path of fixed number of steps\n\t\t\t\tsimPathType = PathType.SIM_PATH_NUM_STEPS;\n\t\t\t\ttry {\n\t\t\t\t\tsimPathLength = Integer.parseInt(ss[i]);\n\t\t\t\t\tif (simPathLength < 0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\tthrow new PrismException(\"Invalid path option \\\"\" + ss[i] + \"\\\"\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (simPathType == null)\n\t\t\tthrow new PrismException(\"Invalid path details \\\"\" + details + \"\\\"\");\n\n\t\t// Be default, set changes=true if vars=() was specified\n\t\tif (varsOptionGiven && !changesFalseOptionGiven) {\n\t\t\tsimPathShowChangesOnly = true;\n\t\t}\n\t\t\n\t\t// Display warning if attempt to use \"repeat=\" option and not \"deadlock\" option\n\t\tif (simPathRepeat > 1 && simPathType != PathType.SIM_PATH_DEADLOCK) {\n\t\t\tsimPathRepeat = 1;\n\t\t\tmainLog.printWarning(\"Ignoring \\\"repeat\\\" option - it is only valid when looking for deadlocks.\");\n\t\t}\n\t}\n\n\t/**\n\t * Print bulleted list of options to a log (used by -help switch). \n\t */\n\tpublic static void printOptions(PrismLog mainLog)\n\t{\n\t\tmainLog.println(\" * <n> - generate a path of <n> steps\");\n\t\tmainLog.println(\" * time=<x> - generate a path of at least <x> time units\");\n\t\tmainLog.println(\" * deadlock - generate a path until a deadlock is reached\");\n\t\tmainLog.println(\" * repeat=<n> - try <n> paths until a deadlock is found\");\n\t\t\n\t\tmainLog.println(\" * sep=<val> - use <val> as column separator (space, tab, comma)\");\n\t\tmainLog.println(\" * vars=<x1,x2,...> - show values for variables x1,x2,.. only\");\n\t\tmainLog.println(\" * loopcheck=<true|false> - whether to detect deterministic loops\");\n\t\tmainLog.println(\" * snapshot=<x> - view states at fixed timepoints of interval <x>\");\n\t\tmainLog.println(\" * probs=<true|false> - display probability (or rate) of transitions taken\");\n\t\tmainLog.println(\" * rewards=<true|false> - display state/transition rewards\");\n\t\tmainLog.println(\" * changes=<true|false> - only display states where displayed variables change\");\n\t}\n\n\t/**\n\t * Create a PathDisplayer object for file export\n\t */\n\tprivate PathDisplayer generateDisplayerForExport() throws PrismException\n\t{\n\t\tPrismLog log;\n\t\tPathToText displayer;\n\n\t\tif (file != null) {\n\t\t\tlog = new PrismFileLog(file.getPath());\n\t\t} else {\n\t\t\tlog = new PrismLogWrapper(mainLog);\n\t\t}\n\t\tdisplayer = new PathToText(log, engine.getModel(), engine.getRewardGenerator());\n\t\tdisplayer.setColSep(simPathSep);\n\t\tdisplayer.setVarsToShow(simVars);\n\t\tdisplayer.setShowProbs(simPathShowProbs);\n\t\tdisplayer.setShowRewards(simPathShowRewards);\n\t\tdisplayer.setShowChangesOnly(simPathShowChangesOnly);\n\t\tif (simPathSnapshots)\n\t\t\tdisplayer.setToShowSnapShots(simPathSnapshotTime);\n\n\t\treturn displayer;\n\t}\n\n\t/**\n\t * Create a PathDisplayer object for graph plotting\n\t */\n\tprivate PathDisplayer generateDisplayerForPlotting(Graph graphModel) throws PrismException\n\t{\n\t\tPathToGraph displayer;\n\n\t\tdisplayer = new PathToGraph(graphModel, engine.getModel(), engine.getRewardGenerator());\n\t\tdisplayer.setVarsToShow(simVars);\n\t\tdisplayer.setShowProbs(simPathShowProbs);\n\t\tdisplayer.setShowRewards(simPathShowRewards);\n\t\tdisplayer.setShowChangesOnly(simPathShowChangesOnly);\n\t\tif (simPathSnapshots)\n\t\t\tdisplayer.setToShowSnapShots(simPathSnapshotTime);\n\n\t\treturn displayer;\n\t}\n\n\t/**\n\t * Generate a random (on-the-fly) path using the simulator.\n\t */\n\tprivate void generatePath(PathDisplayer displayer) throws PrismException\n\t{\n\t\tPath path = null;\n\t\tlong i = 0;\n\t\tboolean done;\n\n\t\t// Print details\n\t\tswitch (simPathType) {\n\t\tcase SIM_PATH_NUM_STEPS:\n\t\t\tmainLog.println(\"\\nGenerating random path of length \" + simPathLength + \" steps...\");\n\t\t\tbreak;\n\t\tcase SIM_PATH_TIME:\n\t\t\tmainLog.println(\"\\nGenerating random path with time limit \" + simPathTime + \"...\");\n\t\t\tbreak;\n\t\t}\n\n\t\t// Create path\n\t\tengine.createNewOnTheFlyPath();\n\t\t// Build path\n\t\tpath = engine.getPath();\n\t\tengine.initialisePath(initialState);\n\t\t\n\t\tif (displayer instanceof PathToText && file == null) {\n\t\t\tmainLog.println();\n\t\t}\n\t\tdisplayer.start(path.getCurrentState(), path.getCurrentStateRewards());\n\t\ti = 0;\n\t\tdone = false;\n\t\twhile (!done) {\n\t\t\t// Generate a single step of path\n\t\t\tengine.automaticTransition();\n\t\t\ti++;\n\t\t\tif (simPathType != PathType.SIM_PATH_DEADLOCK) {\n\t\t\t\tdisplayer.step(path.getTimeInPreviousState(), path.getTotalTime(), path.getPreviousActionString(), path.getPreviousProbability(),\n\t\t\t\t\t\tpath.getPreviousTransitionRewards(), path.size(), path.getCurrentState(), path.getCurrentStateRewards());\n\t\t\t}\n\t\t\t// Check for termination (depending on type)\n\t\t\tswitch (simPathType) {\n\t\t\tcase SIM_PATH_NUM_STEPS:\n\t\t\t\tif (i >= simPathLength || engine.queryIsDeadlock())\n\t\t\t\t\tdone = true;\n\t\t\t\tbreak;\n\t\t\tcase SIM_PATH_TIME:\n\t\t\t\tif (path.getTotalTime() >= simPathTime || i >= maxPathLength || engine.queryIsDeadlock())\n\t\t\t\t\tdone = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t// Stop if a loop was found (and loop checking was not disabled)\n\t\t\tif (simLoopCheck && engine.isPathLooping())\n\t\t\t\tbreak;\n\t\t}\n\t\tdisplayer.end();\n\n\t\t// Display warnings if needed\n\t\tif (simLoopCheck && engine.isPathLooping()) {\n\t\t\twarning(\"Deterministic loop detected after \" + engine.getPathSize() + \" steps (use loopcheck=false option to extend path)\");\n\t\t}\n\t\tif (simPathType == PathType.SIM_PATH_TIME && path.getTotalTime() < simPathTime) {\n\t\t\twarning(\"Path terminated before time \" + simPathTime + \" because maximum path length (\" + maxPathLength + \") was reached\");\n\t\t}\n\n\t\t// Print summary of path\n\t\tmainLog.print(\"\\nGenerated path: \" + path.size() + \" step\" + (path.size() == 1 ? \"\" : \"s\"));\n\t\tif (engine.getModel().getModelType().continuousTime()) {\n\t\t\tmainLog.print(\", total time \" + path.getTotalTime());\n\t\t}\n\t\tif (file != null) {\n\t\t\tmainLog.println(\" (exported to \" + file + \")\");\n\t\t} else {\n\t\t\tmainLog.println();\n\t\t}\n\t}\n\n\t/**\n\t * Generate multiple random paths using the simulator.\n\t * Note: these are not on-the-fly paths since we don't in advance if they are to be displayed.\n\t */\n\tprivate void generateMultiplePaths(PathDisplayer displayer) throws PrismException\n\t{\n\t\tPath path = null;\n\t\tint i = 0, j = 0;\n\t\tboolean done;\n\n\t\t// Print details\n\t\tswitch (simPathType) {\n\t\tcase SIM_PATH_DEADLOCK:\n\t\t\tmainLog.println(\"\\nGenerating random path(s) until deadlock state...\");\n\t\t\tbreak;\n\t\t}\n\n\t\t// Create path\n\t\tengine.createNewPath();\n\t\t// Build path\n\t\tfor (j = 0; j < simPathRepeat; j++) {\n\t\t\tpath = engine.getPath();\n\t\t\tengine.initialisePath(initialState);\n\t\t\ti = 0;\n\t\t\tdone = false;\n\t\t\twhile (!done) {\n\t\t\t\t// Generate a single step of path\n\t\t\t\tengine.automaticTransition();\n\t\t\t\ti++;\n\t\t\t\t// Check for termination (depending on type)\n\t\t\t\tswitch (simPathType) {\n\t\t\t\tcase SIM_PATH_DEADLOCK:\n\t\t\t\t\tif (engine.queryIsDeadlock() || i >= maxPathLength)\n\t\t\t\t\t\tdone = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\t// Stop if a loop was found (and loop checking was not disabled)\n\t\t\t\tif (simLoopCheck && engine.isPathLooping())\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\t// Stop generating paths if done\n\t\t\tif (engine.queryIsDeadlock())\n\t\t\t\tbreak;\n\t\t}\n\t\tif (j < simPathRepeat)\n\t\t\tj++;\n\n\t\t// Bail out if we didn't build a suitable path \n\t\tif (!engine.queryIsDeadlock()) {\n\t\t\tmainLog.print(\"\\nNo deadlock state found within \" + maxPathLength + \" steps\");\n\t\t\tif (simPathRepeat > 1)\n\t\t\t\tmainLog.print(\" (generated \" + simPathRepeat + \" paths)\");\n\t\t\tmainLog.println(\".\");\n\t\t\treturn;\n\t\t}\n\n\t\t// Display path\n\t\tif (file == null)\n\t\t\tmainLog.println();\n\t\tengine.getPathFull().display(displayer);\n\n\t\t// Print summary of path(s)\n\t\tif (simPathRepeat > 1 && j > 1)\n\t\t\tmainLog.print(\"\\nGenerated \" + j + \" paths. Final path: \");\n\t\telse\n\t\t\tmainLog.print(\"\\nGenerated path: \");\n\t\tmainLog.print(path.size() + \" steps\");\n\t\tif (engine.getModel().getModelType().continuousTime()) {\n\t\t\tmainLog.print(\", total time \" + path.getTotalTime());\n\t\t}\n\t\tif (file != null) {\n\t\t\tmainLog.println(\" (exported to \" + file + \")\");\n\t\t} else {\n\t\t\tmainLog.println();\n\t\t}\n\t}\n\n\tclass GenerateAndPlotThread extends Thread\n\t{\n\t\tprivate parser.State initialState;\n\t\tprivate String details;\n\t\tprivate long maxPathLength;\n\t\tprivate Graph graphModel;\n\n\t\tpublic GenerateAndPlotThread(parser.State initialState, String details, long maxPathLength, Graph graphModel)\n\t\t{\n\t\t\tthis.initialState = initialState;\n\t\t\tthis.details = details;\n\t\t\tthis.maxPathLength = maxPathLength;\n\t\t\tthis.graphModel = graphModel;\n\t\t}\n\n\t\tpublic void run()\n\t\t{\n\t\t\ttry {\n\t\t\t\tgenerateAndPlotSimulationPath(initialState, details, maxPathLength, graphModel);\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// Just report errors passively to log\n\t\t\t\tmainLog.printWarning(\"Error occured during path plot: \" + e.getMessage());\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/LoopDetector.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport prism.ModelGenerator;\nimport prism.PrismException;\n\n/**\n * Detects deterministic loops in a path though a model.\n * (Currently, only detects single-step loops.)\n */\npublic class LoopDetector\n{\n\t// Deterministic loop info\n\tprivate boolean isLooping;\n\tprivate long loopStart;\n\tprivate long loopEnd;\n\n\t/**\n\t * Initialise the loop detector.\n\t */\n\tpublic void initialise()\n\t{\n\t\tisLooping = false;\n\t\tloopStart = loopEnd = -1;\n\t}\n\t\n\t/**\n\t * Update loop detector after a step has just been added to the path.\n\t */\n\tpublic void addStep(Path path, ModelGenerator modelGen)\n\t\n\t{\n\t\t// If already looping, nothing to do\n\t\tif (isLooping) {\n\t\t\treturn;\n\t\t}\n\t\t// Deterministic loops cannot occur in continuous-time models\n\t\tif (path.continuousTime()) {\n\t\t\treturn;\n\t\t}\n\t\t// Check transitions from previous step were deterministic\n\t\ttry {\n\t\t\tif (!modelGen.isDeterministic()) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\t// In case of problems, just don't check\n\t\t\treturn;\n\t\t}\n\t\t// Check successive states were identical\n\t\tif (path.getPreviousState().equals(path.getCurrentState())) {\n\t\t\tisLooping = true;\n\t\t\tloopStart = path.size() - 1;\n\t\t\tloopEnd = path.size();\n\t\t}\n\t}\n\t\n\t/**\n\t * Update loop detector after a backtrack within the path has been made.\n\t */\n\tpublic void backtrack(Path path)\n\t{\n\t\tif (isLooping) {\n\t\t\tif (path.size() < loopEnd) {\n\t\t\t\tisLooping = false;\n\t\t\t\tloopStart = loopEnd = -1;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Update loop detector after a prefix of the path has been removed.\n\t * @param path Path object (already updated)\n\t * @param step Index of old path that is now start of path (i.e. num states removed)\n\t */\n\tpublic void removePrecedingStates(Path path, int step)\n\t{\n\t\tif (isLooping) {\n\t\t\tif (step > loopStart) {\n\t\t\t\tisLooping = false;\n\t\t\t\tloopStart = loopEnd = -1;\n\t\t\t} else {\n\t\t\t\tloopStart -= step;\n\t\t\t\tloopEnd -= step;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Does the path contain a deterministic loop?\n\t */\n\tpublic boolean isLooping()\n\t{\n\t\treturn isLooping;\n\t}\n\t\n\t/**\n\t * What is the step index of the start of the deterministic loop, if it exists?\n\t */\n\tpublic long loopStart()\n\t{\n\t\treturn loopStart;\n\t}\n\t\n\t/**\n\t * What is the step index of the end of the deterministic loop, if it exists?\n\t */\n\tpublic long loopEnd()\n\t{\n\t\treturn loopEnd;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/ModulesFileModelGenerator.java",
    "content": "package simulator;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport common.Interval;\nimport param.BigRational;\nimport param.Function;\nimport param.FunctionFactory;\nimport parser.EvaluateContext;\nimport parser.EvaluateContextState;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.ConstantList;\nimport parser.ast.DeclarationType;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionConstant;\nimport parser.ast.ExpressionLiteral;\nimport parser.ast.LabelList;\nimport parser.ast.ModulesFile;\nimport parser.ast.RewardStruct;\nimport parser.type.Type;\nimport parser.type.TypeClock;\nimport parser.visitor.ASTTraverseModify;\nimport prism.Evaluator;\nimport prism.ModelGenerator;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismNotSupportedException;\nimport prism.RewardGenerator;\n\npublic class ModulesFileModelGenerator<Value> implements ModelGenerator<Value>, RewardGenerator<Value>\n{\n\t// Parent PrismComponent (logs, settings etc.)\n\tprotected PrismComponent parent;\n\t\n\t// Evaluator for values/states\n\tprotected Evaluator<Value> eval;\n\t\n\t// Interval evaluator for probability intervals, if needed\n\tprotected Evaluator<Interval<Value>> evalInt;\n\t\n\t// Evaluation context for expressions\n\tprotected EvaluateContextState ec;\n\t\n\t// PRISM model info\n\t/** The original modules file (might have unresolved constants) */\n\tprotected ModulesFile originalModulesFile;\n\t/** The modules file used for generating (has no unresolved constants after {@code initialise}) */\n\tprotected ModulesFile modulesFile;\n\tprotected ModelType modelType;\n\tprotected Values mfConstants;\n\tprotected VarList varList;\n\tprotected LabelList labelList;\n\tprotected List<String> labelNames;\n\t\n\t// Model exploration info\n\t\n\t// State currently being explored\n\tprotected State exploreState;\n\t\n\t// Updater object for model\n\tprotected Updater<Value> updater;\n\t// List of currently available transitions\n\tprotected TransitionList<Value> transitionList;\n\t// Has the transition list been built? \n\tprotected boolean transitionListBuilt;\n\t\n\t// List of currently available transitions (interval models)\n\tprotected TransitionList<Interval<Value>> transitionListInt;\n\t// Updater object for model (interval models)\n\tprotected Updater<Interval<Value>> updaterInt;\n\t// Has the transition list been built? (interval models)\n\tprotected boolean transitionListIntBuilt;\n\t\n\t// Global clock invariant (conjunction of per-module invariants)\n\tprotected Expression invariant;\n\t\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * This method assumes that doubles are used to represent probabilities (rather than, say, exact arithmetic).\n\t * The method takes care of {@link Evaluator} creation so should be preferred to calling constructors directly.\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\tpublic static ModulesFileModelGenerator<?> create(ModulesFile modulesFile, PrismComponent parent) throws PrismException\n\t{\n\t\treturn create(modulesFile, false, parent);\n\t}\n\t\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * If {@code exact} is true, the ModelGenerator will use {@link BigRational}s not doubles for probabilities.\n\t * The method takes care of {@link Evaluator} creation so should be preferred to calling constructors directly.\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param exact Use exact arithmetic?\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\tpublic static ModulesFileModelGenerator<?> create(ModulesFile modulesFile, boolean exact, PrismComponent parent) throws PrismException\n\t{\n\t\treturn new ModulesFileModelGenerator<>(modulesFile, createEvaluator(modulesFile, exact), parent);\n\t}\n\t\n\t/**\n\t * Helper function to create an Evaluator of the appropriate type.\n\t */\n\tprivate static Evaluator<?> createEvaluator(ModulesFile modulesFile, boolean exact) throws PrismException\n\t{\n\t\tif (!exact) {\n\t\t\treturn Evaluator.forDouble();\n\t\t} else {\n\t\t\treturn Evaluator.forBigRational();\n\t\t}\n\t}\n\t\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * This method assumes that doubles are used to represent probabilities (rather than, say, exact arithmetic).\n\t * Use this method to guarantee getting a {@code ModulesFileModelGenerator<Double>}.\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\tpublic static ModulesFileModelGenerator<Double> createForDoubles(ModulesFile modulesFile, PrismComponent parent) throws PrismException\n\t{\n\t\tEvaluator<Double> eval = Evaluator.forDouble();\n\t\treturn new ModulesFileModelGenerator<>(modulesFile, eval, parent);\n\t}\n\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * This method assumes that {@link BigRational}s are used to represent probabilities exactly.\n\t * Use this method to guarantee getting a {@code ModulesFileModelGenerator<BigRational>}.\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\tpublic static ModulesFileModelGenerator<BigRational> createForRationals(ModulesFile modulesFile, PrismComponent parent) throws PrismException\n\t{\n\t\tEvaluator<BigRational> eval = Evaluator.forBigRational();\n\t\treturn new ModulesFileModelGenerator<>(modulesFile, eval, parent);\n\t}\n\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * This method assumes that Functions are used to represent probabilities parametrically.\n\t * Use this method to guarantee getting a {@code ModulesFileModelGenerator<Function>}.\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param paramNames names of parameters\n\t * @param lowerStr lower bounds of parameters as strings\n\t * @param upperStr upper bounds of parameters as strings\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\tpublic static ModulesFileModelGenerator<Function> createForRationalFunctions(ModulesFile modulesFile, String[] paramNames, String[] lowerStr, String[] upperStr, PrismComponent parent) throws PrismException\n\t{\n\t\tFunctionFactory functionFactory = FunctionFactory.create(paramNames, lowerStr, upperStr, parent.getSettings());\n\t\treturn createForRationalFunctions(modulesFile, functionFactory, parent);\n\t}\n\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * This method assumes that Functions are used to represent probabilities parametrically,\n\t * but that all probabilities are in fact constant, i.e., represented by rationals.\n\t * Use this method to guarantee getting a {@code ModulesFileModelGenerator<Function>}.\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\tpublic static ModulesFileModelGenerator<Function> createForRationalFunctions(ModulesFile modulesFile, PrismComponent parent) throws PrismException\n\t{\n\t\t// Uncertain models not supported - catch here for better error message\n\t\tif (modulesFile.getModelType().uncertain()) {\n\t\t\tthrow new PrismNotSupportedException(\"Exact \" + modulesFile.getModelType() + \"s are not supported\");\n\t\t}\n\t\t// Set up a dummy parameter (not used)\n\t\tString[] paramNames = new String[] { \"dummy\" };\n\t\tString[] lowerStr = new String[] { \"0\" };\n\t\tString[] upperStr = new String[] { \"1\" };\n\t\tFunctionFactory functionFactory = FunctionFactory.create(paramNames, lowerStr, upperStr, parent.getSettings());\n\t\treturn createForRationalFunctions(modulesFile, functionFactory, parent);\n\t}\n\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * This method builds a generator for a parametric model using the function factory provided.\n\t * Use this method to guarantee getting a {@code ModulesFileModelGenerator<Function>}.\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param functionFactory Factory for creating/manipulating rational functions\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\tpublic static ModulesFileModelGenerator<Function> createForRationalFunctions(ModulesFile modulesFile, FunctionFactory functionFactory, PrismComponent parent) throws PrismException\n\t{\n\t\tEvaluator<Function> eval = Evaluator.forRationalFunction(functionFactory);\n\t\treturn new ModulesFileModelGenerator<>(modulesFile, eval, parent);\n\t}\n\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * This constructor assumes that doubles are used to represent probabilities (rather than, say, exact arithmetic).\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t */\n\tpublic ModulesFileModelGenerator(ModulesFile modulesFile) throws PrismException\n\t{\n\t\tthis(modulesFile, (PrismComponent) null);\n\t}\n\t\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * This constructor assumes that doubles are used to represent probabilities (rather than, say, exact arithmetic).\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic ModulesFileModelGenerator(ModulesFile modulesFile, PrismComponent parent) throws PrismException\n\t{\n\t\tthis(modulesFile, (Evaluator<Value>) Evaluator.forDouble(), parent);\n\t}\n\t\n\t/**\n\t * Build a ModulesFileModelGenerator for a particular PRISM model, represented by a {@link ModulesFile} instance.\n\t * Takes in an {@link Evaluator}{@code <Value>} to match the type parameter {@code Value} of this class.\n\t * Throw an explanatory exception if the model generator cannot be created.\n\t * @param modulesFile The PRISM model\n\t * @param eval Evaluator matching the type parameter {@code Value} of this class\n\t * @param parent Parent, used e.g. for settings (can be null)\n\t */\n\tpublic ModulesFileModelGenerator(ModulesFile modulesFile, Evaluator<Value> eval, PrismComponent parent) throws PrismException\n\t{\n\t\tthis.parent = parent;\n\t\tthis.eval = eval;\n\t\tif (modulesFile.getModelType().uncertain()) {\n\t\t\tevalInt = eval.createIntervalEvaluator();\n\t\t}\n\t\t\n\t\t// No support for system...endsystem yet\n\t\tif (modulesFile.getSystemDefn() != null) {\n\t\t\tthrow new PrismNotSupportedException(\"The system...endsystem construct is not currently supported\");\n\t\t}\n\t\t\n\t\t// Store basic model info\n\t\tthis.modulesFile = modulesFile;\n\t\tthis.originalModulesFile = modulesFile;\n\t\tmodelType = modulesFile.getModelType();\n\t\t\n\t\t// If there are no constants to define, go ahead and initialise;\n\t\t// Otherwise, setSomeUndefinedConstants needs to be called when the values are available  \n\t\tmfConstants = modulesFile.getConstantValues();\n\t\tif (mfConstants != null) {\n\t\t\tinitialise();\n\t\t}\n\t\t\n\t\t// Create evaluate context for re-use\n\t\tec = new EvaluateContextState(mfConstants, new State(modulesFile.getNumVars()));\n\t\tec.setEvaluationMode(eval.evalMode());\n\t}\n\t\n\t/**\n\t * (Re-)Initialise the class ready for model exploration\n\t * (can only be done once any constants needed have been provided)\n\t */\n\tprivate void initialise() throws PrismException\n\t{\n\t\t// Evaluate and replace constants on (a copy) of the modules file\n\t\t// We do this using a custom traversal, rather than just calling\n\t\t// replaceConstants() or evaluatePartially() because we also need\n\t\t// to expand undefined constants (e.g., for parametric model checking)\n\t\tmodulesFile = (ModulesFile) modulesFile.deepCopy();\n\t\tConstantList constantList = modulesFile.getConstantList();\n\t\tmodulesFile = (ModulesFile) modulesFile.accept(new ASTTraverseModify()\n\t\t{\n\t\t\tpublic Object visit(ExpressionConstant e) throws PrismLangException\n\t\t\t{\n\t\t\t\tString name = e.getName();\n\t\t\t\t// Constants whose values have been fixed (directly or indirectly)\n\t\t\t\t// are replaced with constant literals\n\t\t\t\tint i = mfConstants.getIndexOf(name);\n\t\t\t\tif (i != -1) {\n\t\t\t\t\treturn new ExpressionLiteral(e.getType(), mfConstants.getValue(i));\n\t\t\t\t}\n\t\t\t\t// Otherwise, see if there is definition (in terms of other constants)\n\t\t\t\t// in the model's constant list\n\t\t\t\tint i2 = constantList.getConstantIndex(e.getName());\n\t\t\t\tif (i2 != -1 && constantList.getConstant(i2) != null) {\n\t\t\t\t\treturn constantList.getConstant(i2).accept(this);\n\t\t\t\t}\n\t\t\t\t// If not, the constant cannot be defined (might, for example,\n\t\t\t\t// be a parameter in parametric model checking). So leave unchanged.\n\t\t\t\treturn e;\n\t\t\t}\n\t\t\t\n\t\t});\n\t\t// Optimise arithmetic expressions (not in exact mode: can create some round-off issues)\n\t\tif (!eval.exact()) {\n\t\t\tmodulesFile = (ModulesFile) modulesFile.simplify();\n\t\t}\n\t\t// Get info\n\t\tvarList = modulesFile.createVarList();\n\t\tlabelList = modulesFile.getLabelList();\n\t\tlabelNames = labelList.getLabelNames();\n\t\t\n\t\t// Create data structures for exploring model\n\t\tif (!modelType.uncertain()) {\n\t\t\tupdater = new Updater<Value>(modulesFile, varList, eval, parent);\n\t\t\ttransitionList = new TransitionList<Value>(eval);\n\t\t} else {\n\t\t\tupdaterInt = new Updater<Interval<Value>>(modulesFile, varList, evalInt, parent);\n\t\t\ttransitionListInt = new TransitionList<Interval<Value>>(evalInt);\n\t\t}\n\t\ttransitionListBuilt = false;\n\t\ttransitionListIntBuilt = false;\n\t}\n\t\n\t// Methods for ModelInfo interface\n\t\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn modelType;\n\t}\n\n\t@Override\n\tpublic void setSomeUndefinedConstants(EvaluateContext ecUndefined) throws PrismException\n\t{\n\t\t// We start again with a copy of the original modules file\n\t\t// and set the constants in the copy.\n\t\t// As {@code initialise()} can replace references to constants\n\t\t// with the concrete values in modulesFile, this ensures that we\n\t\t// start again at a place where references to constants have not\n\t\t// yet been replaced.\n\t\tmodulesFile = (ModulesFile) originalModulesFile.deepCopy();\n\t\tmodulesFile.setSomeUndefinedConstants(ecUndefined);\n\t\tmfConstants = modulesFile.getConstantValues();\n\t\tec.setConstantValues(mfConstants);\n\t\tinitialise();\n\t}\n\t\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn mfConstants;\n\t}\n\t\n\t@Override\n\tpublic boolean containsUnboundedVariables()\n\t{\n\t\treturn modulesFile.containsUnboundedVariables();\n\t}\n\t\n\t@Override\n\tpublic int getNumVars()\n\t{\n\t\treturn modulesFile.getNumVars();\n\t}\n\t\n\t@Override\n\tpublic List<String> getVarNames()\n\t{\n\t\treturn modulesFile.getVarNames();\n\t}\n\n\t@Override\n\tpublic List<Type> getVarTypes()\n\t{\n\t\treturn modulesFile.getVarTypes();\n\t}\n\n\t@Override\n\tpublic DeclarationType getVarDeclarationType(int i) throws PrismException\n\t{\n\t\treturn modulesFile.getVarDeclarationType(i);\n\t}\n\t\n\t@Override\n\tpublic int getVarModuleIndex(int i)\n\t{\n\t\treturn modulesFile.getVarModuleIndex(i);\n\t}\n\t\n\t@Override\n\tpublic String getModuleName(int i)\n\t{\n\t\treturn modulesFile.getModuleName(i);\n\t}\n\t\n\t@Override\n\tpublic VarList createVarList() throws PrismException\n\t{\n\t\treturn varList;\n\t}\n\t\n\t@Override\n\tpublic boolean isVarObservable(int i)\n\t{\n\t\treturn modulesFile.isVarObservable(i);\n\t}\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\treturn modulesFile.getActions();\n\t}\n\n\t@Override\n\tpublic int getNumLabels()\n\t{\n\t\treturn labelList.size();\t\n\t}\n\n\t@Override\n\tpublic String getActionStringDescription()\n\t{\n\t\treturn \"Module/[action]\";\n\t}\n\t\n\t@Override\n\tpublic List<String> getLabelNames()\n\t{\n\t\treturn labelNames;\n\t}\n\t\n\t@Override\n\tpublic String getLabelName(int i) throws PrismException\n\t{\n\t\treturn labelList.getLabelName(i);\n\t}\n\t\n\t@Override\n\tpublic int getLabelIndex(String label)\n\t{\n\t\treturn labelList.getLabelIndex(label);\n\t}\n\t\n\t@Override\n\tpublic List<String> getObservableNames()\n\t{\n\t\treturn modulesFile.getObservableNames();\n\t}\n\t\n\t// Methods for ModelGenerator interface\n\t\n\t@Override\n\tpublic Evaluator<Value> getEvaluator()\n\t{\n\t\treturn eval;\n\t}\n\t\n\t@Override\n\tpublic Evaluator<Interval<Value>> getIntervalEvaluator()\n\t{\n\t\treturn evalInt;\n\t}\n\t\n\t@Override\n\tpublic boolean hasSingleInitialState() throws PrismException\n\t{\n\t\treturn modulesFile.getInitialStates() == null;\n\t}\n\t\n\t@Override\n\tpublic State getInitialState() throws PrismException\n\t{\n\t\tif (modulesFile.getInitialStates() == null) {\n\t\t\treturn modulesFile.getDefaultInitialState();\n\t\t} else {\n\t\t\t// Inefficient but probably won't be called\n\t\t\treturn getInitialStates().get(0);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic List<State> getInitialStates() throws PrismException\n\t{\n\t\tList<State> initStates = new ArrayList<State>();\n\t\t// Easy (normal) case: just one initial state\n\t\tif (modulesFile.getInitialStates() == null) {\n\t\t\tState state = modulesFile.getDefaultInitialState();\n\t\t\tinitStates.add(state);\n\t\t}\n\t\t// Otherwise, there may be multiple initial states\n\t\t// For now, we handle this is in a very inefficient way\n\t\telse {\n\t\t\tExpression init = modulesFile.getInitialStates();\n\t\t\tList<State> allPossStates = varList.getAllStates();\n\t\t\tfor (State possState : allPossStates) {\n\t\t\t\tif (init.evaluateBoolean(ec.setState(possState))) {\n\t\t\t\t\tinitStates.add(possState);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn initStates;\n\t}\n\n\t@Override\n\tpublic void exploreState(State exploreState) throws PrismException\n\t{\n\t\tthis.exploreState = exploreState;\n\t\ttransitionListBuilt = false;\n\t\ttransitionListIntBuilt = false;\n\t}\n\t\n\t@Override\n\tpublic int getNumChoices() throws PrismException\n\t{\n\t\treturn getTransitionList().getNumChoices();\n\t}\n\n\t@Override\n\tpublic int getNumTransitions() throws PrismException\n\t{\n\t\treturn getTransitionList().getNumTransitions();\n\t}\n\n\t@Override\n\tpublic int getNumTransitions(int i) throws PrismException\n\t{\n\t\treturn getTransitionList().getChoice(i).size();\n\t}\n\n\t@Override\n\tpublic int getChoiceIndexOfTransition(int index) throws PrismException\n\t{\n\t\treturn getTransitionList().getChoiceIndexOfTransition(index);\n\t}\n\t\n\t@Override\n\tpublic int getChoiceOffsetOfTransition(int index) throws PrismException\n\t{\n\t\treturn getTransitionList().getChoiceOffsetOfTransition(index);\n\t}\n\t\n\t@Override\n\tpublic int getTotalIndexOfTransition(int i, int offset) throws PrismException\n\t{\n\t\treturn getTransitionList().getTotalIndexOfTransition(i, offset);\n\t}\n\t\n\t@Override\n\tpublic Object getTransitionAction(int i, int offset) throws PrismException\n\t{\n\t\tTransitionList<?> transitions = getTransitionList();\n\t\tint a = transitions.getTransitionModuleOrActionIndex(transitions.getTotalIndexOfTransition(i, offset));\n\t\treturn a < 0 ? null : modulesFile.getSynch(a - 1);\n\t}\n\n\t@Override\n\tpublic String getTransitionActionString(int i, int offset) throws PrismException\n\t{\n\t\tTransitionList<?> transitions = getTransitionList();\n\t\tint a = transitions.getTransitionModuleOrActionIndex(transitions.getTotalIndexOfTransition(i, offset));\n\t\treturn getDescriptionForModuleOrActionIndex(a);\n\t}\n\t\n\t@Override\n\tpublic Object getChoiceAction(int index) throws PrismException\n\t{\n\t\tTransitionList<?> transitions = getTransitionList();\n\t\tint a = transitions.getChoiceModuleOrActionIndex(index);\n\t\treturn a < 0 ? null : modulesFile.getSynch(a - 1);\n\t}\n\n\t@Override\n\tpublic String getChoiceActionString(int index) throws PrismException\n\t{\n\t\tTransitionList<?> transitions = getTransitionList();\n\t\tint a = transitions.getChoiceModuleOrActionIndex(index);\n\t\treturn getDescriptionForModuleOrActionIndex(a);\n\t}\n\n\t/**\n\t * Utility method to get a description for an action label:\n\t * \"[a]\" for a synchronous action a and \"M\" for an unlabelled\n\t * action belonging to a module M. Takes in an integer index:\n\t * -i for independent in ith module, i for synchronous on ith action\n\t * (in both cases, modules/actions are 1-indexed) \n\t */ \n\tprivate String getDescriptionForModuleOrActionIndex(int a)\n\t{\n\t\tif (a < 0) {\n\t\t\treturn modulesFile.getModuleName(-a - 1);\n\t\t} else if (a > 0) {\n\t\t\treturn \"[\" + modulesFile.getSynchs().get(a - 1) + \"]\";\n\t\t} else {\n\t\t\treturn \"?\";\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic Expression getChoiceClockGuard(int i) throws PrismException\n\t{\n\t\tTransitionList<?> transitions = getTransitionList();\n\t\treturn transitions.getChoice(i).getClockGuard();\n\t}\n\t\n\t@Override\n\tpublic Value getTransitionProbability(int i, int offset) throws PrismException\n\t{\n\t\tTransitionList<Value> transitions = getTransitionListScalars();\n\t\tif (transitions != null) {\n\t\t\treturn transitions.getChoice(i).getProbability(offset);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Cannot get scalar transition probability for \" + getModelType());\n\t\t}\n\t}\n\n\t@Override\n\tpublic Value getChoiceProbabilitySum(int i) throws PrismException\n\t{\n\t\tTransitionList<Value> transitions = getTransitionListScalars();\n\t\tif (transitions != null) {\n\t\t\treturn transitions.getChoice(i).getProbabilitySum();\n\t\t} else {\n\t\t\tthrow new PrismException(\"Cannot get scalar transition probability for \" + getModelType());\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic Value getProbabilitySum() throws PrismException\n\t{\n\t\tTransitionList<Value> transitions = getTransitionListScalars();\n\t\tif (transitions != null) {\n\t\t\treturn transitions.getProbabilitySum();\n\t\t} else {\n\t\t\tthrow new PrismException(\"Cannot get scalar transition probability for \" + getModelType());\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic Interval<Value> getTransitionProbabilityInterval(int i, int offset) throws PrismException\n\t{\n\t\tTransitionList<Interval<Value>> transitions = getTransitionListIntervals();\n\t\tif (transitions != null) {\n\t\t\treturn transitions.getChoice(i).getProbability(offset);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Cannot get transition probability interval for \" + getModelType());\n\t\t}\n\t}\n\n\t@Override\n\tpublic String getTransitionUpdateString(int i, int offset) throws PrismException\n\t{\n\t\tTransitionList<?> transitions = getTransitionList();\n\t\treturn transitions.getTransitionUpdateString(transitions.getTotalIndexOfTransition(i, offset), exploreState);\n\t}\n\t\n\t@Override\n\tpublic String getTransitionUpdateStringFull(int i, int offset) throws PrismException\n\t{\n\t\tTransitionList<?> transitions = getTransitionList();\n\t\treturn transitions.getTransitionUpdateStringFull(transitions.getTotalIndexOfTransition(i, offset));\n\t}\n\t\n\t@Override\n\tpublic State computeTransitionTarget(int index, int offset) throws PrismException\n\t{\n\t\treturn getTransitionList().getChoice(index).computeTarget(offset, exploreState, varList);\n\t}\n\n\t@Override\n\tpublic boolean isLabelTrue(int i) throws PrismException\n\t{\n\t\tExpression expr = labelList.getLabel(i);\n\t\treturn expr.evaluateBoolean(ec.setState(exploreState));\n\t}\n\t\n\t@Override\n\tpublic Expression getClockInvariant() throws PrismException\n\t{\n\t\t// Compute the conjunction of all per-module invariants, if not already done\n\t\tif (invariant == null) {\n\t\t\tint numModules = modulesFile.getNumModules();\n\t\t\tfor (int m = 0; m < numModules; m++) {\n\t\t\t\tExpression invariantMod = modulesFile.getModule(m).getInvariant();\n\t\t\t\tif (invariantMod != null) {\n\t\t\t\t\tinvariant = (invariant == null) ? invariantMod : Expression.And(invariant, invariantMod);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (invariant == null) {\n\t\t\treturn null;\n\t\t}\n\t\t// Replace non-clock variables with their values and simplify\n\t\tint numVars = varList.getNumVars();\n\t\tState stateNoClocks = new State(exploreState);\n\t\tfor (int v = 0; v < numVars; v++) {\n\t\t\tif (varList.getType(v) instanceof TypeClock) {\n\t\t\t\tstateNoClocks.varValues[v] = null;\n\t\t\t}\n\t\t}\n\t\treturn (Expression) invariant.deepCopy().evaluatePartially(ec.setState(stateNoClocks)).simplify();\n\t}\n\t\n\t@Override\n\tpublic State getObservation(State state) throws PrismException\n\t{\n\t\tif (!modelType.partiallyObservable()) {\n\t\t\treturn null;\n\t\t}\n\t\tint numObservables = getNumObservables();\n\t\tState sObs = new State(numObservables);\n\t\tfor (int i = 0; i < numObservables; i++) {\n\t\t\tObject oObs = modulesFile.getObservable(i).getDefinition().evaluate(ec.setState(state));\n\t\t\tsObs.setValue(i, oObs);\n\t\t}\n\t\treturn sObs;\n\t}\n\t\n\t// Methods for RewardGenerator interface\n\n\t@Override\n\tpublic Evaluator<Value> getRewardEvaluator()\n\t{\n\t\treturn eval;\n\t}\n\t\n\t@Override\n\tpublic List<String> getRewardStructNames()\n\t{\n\t\treturn modulesFile.getRewardStructNames();\n\t}\n\t\n\t@Override\n\tpublic boolean rewardStructHasStateRewards(int i)\n\t{\n\t\treturn modulesFile.rewardStructHasStateRewards(i);\n\t}\n\t\n\t@Override\n\tpublic boolean rewardStructHasTransitionRewards(int i)\n\t{\n\t\treturn modulesFile.rewardStructHasTransitionRewards(i);\n\t}\n\t\n\t@Override\n\tpublic Value getStateReward(int r, State state, boolean allowNegative) throws PrismException\n\t{\n\t\tRewardStruct rewStr = modulesFile.getRewardStruct(r);\n\t\tint n = rewStr.getNumItems();\n\t\tValue d = eval.zero();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (!rewStr.getRewardStructItem(i).isTransitionReward()) {\n\t\t\t\tExpression guard = rewStr.getStates(i);\n\t\t\t\tboolean guardSat = guard.evaluateBoolean(ec.setState(state));\n\t\t\t\tif (guardSat) {\n\t\t\t\t\tValue rew = eval.evaluate(rewStr.getReward(i), modulesFile.getConstantValues(), state);\n\t\t\t\t\t// Check reward is finite/non-negative (would be checked at model construction time,\n\t\t\t\t\t// but more fine grained error reporting can be done here)\n\t\t\t\t\t// We omit the check in symbolic (parametric) cases - too expensive\n\t\t\t\t\t// Note use of original model since modulesFile may have been simplified\n\t\t\t\t\tif (!eval.isSymbolic()) {\n\t\t\t\t\t\tif (!eval.isFinite(rew)) {\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Reward structure is not finite at state \" + state, rewStr.getReward(i));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (!allowNegative && !eval.geq(rew, eval.zero())) {\n\t\t\t\t\t\t\tthrow new PrismLangException(\"Reward structure is negative (\" + rew + \") at state \" + state, originalModulesFile.getRewardStruct(r).getReward(i));\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\td = eval.add(d, rew);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic Value getStateActionReward(int r, State state, Object action, boolean allowNegative) throws PrismException\n\t{\n\t\tRewardStruct rewStr = modulesFile.getRewardStruct(r);\n\t\tint n = rewStr.getNumItems();\n\t\tValue d = eval.zero();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (rewStr.getRewardStructItem(i).isTransitionReward()) {\n\t\t\t\tExpression guard = rewStr.getStates(i);\n\t\t\t\tString cmdAction = rewStr.getSynch(i);\n\t\t\t\tif (action == null ? (cmdAction.isEmpty()) : action.equals(cmdAction)) {\n\t\t\t\t\tboolean guardSat = guard.evaluateBoolean(ec.setState(state));\n\t\t\t\t\tif (guardSat) {\n\t\t\t\t\t\tValue rew = eval.evaluate(rewStr.getReward(i), modulesFile.getConstantValues(), state);\n\t\t\t\t\t\t// Check reward is finite/non-negative (would be checked at model construction time,\n\t\t\t\t\t\t// but more fine grained error reporting can be done here)\n\t\t\t\t\t\t// We omit the check in symbolic (parametric) cases - too expensive\n\t\t\t\t\t\t// Note use of original model since modulesFile may have been simplified\n\t\t\t\t\t\tif (!eval.isSymbolic()) {\n\t\t\t\t\t\t\tif (!eval.isFinite(rew)) {\n\t\t\t\t\t\t\t\tthrow new PrismLangException(\"Reward structure is not finite at state \" + state, rewStr.getReward(i));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tif (!allowNegative && !eval.geq(rew, eval.zero())) {\n\t\t\t\t\t\t\t\tthrow new PrismLangException(\"Reward structure is negative (\" + rew + \") at state \" + state, originalModulesFile.getRewardStruct(r).getReward(i));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\td = eval.add(d, rew);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn d;\n\t}\n\n\t// Local utility methods\n\t\n\t/**\n\t * Returns the current list of available transitions, generating it first if this has not yet been done.\n\t */\n\tprivate TransitionList<?> getTransitionList() throws PrismException\n\t{\n\t\treturn modelType.uncertain() ? getTransitionListIntervals() : getTransitionListScalars();\n\t}\n\t\n\t/**\n\t * Returns the current list of available transitions, generating it first if this has not yet been done.\n\t */\n\tprivate TransitionList<Value> getTransitionListScalars() throws PrismException\n\t{\n\t\tif (modelType.uncertain()) {\n\t\t\treturn null;\n\t\t}\n\t\t// Compute the current transition list, if required\n\t\tif (!transitionListBuilt) {\n\t\t\tupdater.calculateTransitions(exploreState, transitionList);\n\t\t\ttransitionListBuilt = true;\n\t\t}\n\t\treturn transitionList;\n\t}\n\t\n\t/**\n\t * Returns the current list of available transitions (interval models), generating it first if this has not yet been done.\n\t */\n\tprivate TransitionList<Interval<Value>> getTransitionListIntervals() throws PrismException\n\t{\n\t\tif (!modelType.uncertain()) {\n\t\t\treturn null;\n\t\t}\n\t\t// Compute the current transition list, if required\n\t\tif (!transitionListIntBuilt) {\n\t\t\tupdaterInt.calculateTransitions(exploreState, transitionListInt);\n\t\t\ttransitionListIntBuilt = true;\n\t\t}\n\t\treturn transitionListInt;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/Path.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport parser.EvaluateContext.EvalMode;\nimport parser.EvaluateContextFull;\nimport parser.State;\nimport parser.ast.Expression;\nimport parser.type.TypeBool;\nimport prism.ModelGenerator;\nimport prism.PrismLangException;\n\n/**\n * Classes that store and manipulate a path though a model.\n */\npublic abstract class Path\n{\n\t// MUTATORS\n\t\n\t/**\n\t * Initialise the path with an initial state, observation and rewards.\n\t * Note: State objects and array will be copied, not stored directly.\n\t */\n\tpublic abstract void initialise(State initialState, State initialObs, double[] initialStateRewards);\n\n\t/**\n\t * Add a step to the path.\n\t * Note: State object and arrays will be copied, not stored directly.\n\t */\n\tpublic abstract void addStep(int choice, Object action, String actionString, Object probability, double[] transRewards, State newState, State newObs, double[] newStateRewards, ModelGenerator modelGen);\n\n\t/**\n\t * Add a timed step to the path.\n\t * Note: State object and arrays will be copied, not stored directly.\n\t */\n\tpublic abstract void addStep(double time, int choice, Object action, String actionString, Object probability, double[] transRewards, State newState, State newObs, double[] newStateRewards, ModelGenerator modelGen);\n\n\t/**\n\t * Set the strategy info (mode and next decision) for the current state.\n\t */\n\tpublic abstract void setStrategyInfoForCurrentState(int memory, Object decision);\n\t\n\t// ACCESSORS\n\n\t/**\n\t * Check whether this path includes continuous-time information, e.g. delays for a CTMC.\n\t */\n\tpublic abstract boolean continuousTime();\n\n\t/**\n\t * Get the size of the path (number of steps; or number of states - 1).\n\t */\n\tpublic abstract long size();\n\n\t/**\n\t * Get the number of states in the path (0 if not initialised; otherwise size() + 1).\n\t */\n\tpublic abstract long numStates();\n\n\t/**\n\t * Get the previous state, i.e. the penultimate state of the current path.\n\t */\n\tpublic abstract State getPreviousState();\n\n\t/**\n\t * Get the current state, i.e. the current final state of the path.\n\t */\n\tpublic abstract State getCurrentState();\n\n\t/**\n\t * Get the observation for the previous state, i.e. for the penultimate state of the current path.\n\t */\n\tpublic abstract State getPreviousObservation();\n\n\t/**\n\t * Get the observation for the current state, i.e. for the current final state of the path.\n\t */\n\tpublic abstract State getCurrentObservation();\n\n\t/**\n\t * Get the action taken in the previous step.\n\t */\n\tpublic abstract Object getPreviousAction();\n\t\n\t/**\n\t * Get a string describing the action taken in the previous step.\n\t */\n\tpublic abstract String getPreviousActionString();\n\t\n\t/**\n\t * Get the probability or rate associated wuth the previous step.\n\t */\n\tpublic abstract Object getPreviousProbability();\n\t\n\t/**\n\t * Get the total time elapsed so far (where zero time has been spent in the current (final) state).\n\t * For discrete-time models, this is just the number of steps (but returned as a double).\n\t */\n\tpublic abstract double getTotalTime();\n\t\n\t/**\n\t * For paths with continuous-time info, get the time spent in the previous state.\n\t */\n\tpublic abstract double getTimeInPreviousState();\n\t\n\t/**\n\t * Get the total reward accumulated so far\n\t * (includes reward for previous transition but no state reward for current (final) state).\n\t * @param rsi Reward structure index\n\t */\n\tpublic abstract double getTotalCumulativeReward(int rsi);\n\t\n\t/**\n\t * Get the state reward for the previous state.\n\t * (For continuous-time models, need to multiply this by time spent in the state.)\n\t * @param rsi Reward structure index\n\t */\n\tpublic abstract double getPreviousStateReward(int rsi);\n\t\n\t/**\n\t * Get the state rewards for the previous state.\n\t * (For continuous-time models, need to multiply these by time spent in the state.)\n\t */\n\tpublic abstract double[] getPreviousStateRewards();\n\t\n\t/**\n\t * Get the transition reward for the transition between the previous and current states.\n\t * @param rsi Reward structure index\n\t */\n\tpublic abstract double getPreviousTransitionReward(int rsi);\n\n\t/**\n\t * Get the transition rewards for the transition between the previous and current states.\n\t */\n\tpublic abstract double[] getPreviousTransitionRewards();\n\n\t/**\n\t * Get the state reward for the current state.\n\t * (For continuous-time models, need to multiply this by time spent in the state.)\n\t * @param rsi Reward structure index\n\t */\n\tpublic abstract double getCurrentStateReward(int rsi);\n\t\n\t/**\n\t * Get the state rewards for the current state.\n\t * (For continuous-time models, need to multiply these by time spent in the state.)\n\t */\n\tpublic abstract double[] getCurrentStateRewards();\n\t\n\t/**\n\t * Get the memory of the strategy (if present) for the current state.\n\t */\n\tpublic abstract int getCurrentStrategyMemory();\n\t\n\t/**\n\t * Get the decision taken by the strategy (if present) in the current state.\n\t */\n\tpublic abstract Object getCurrentStrategyDecision();\n\t\n\t/**\n\t * Does the path contain a deterministic loop?\n\t */\n\tpublic abstract boolean isLooping();\n\t\n\t/**\n\t * What is the step index of the start of the deterministic loop, if it exists?\n\t */\n\tpublic abstract long loopStart();\n\t\n\t/**\n\t * What is the step index of the end of the deterministic loop, if it exists?\n\t */\n\tpublic abstract long loopEnd();\n\t\n\t// UTILITY METHODS\n\n\t/**\n\t * Evaluate an expression in the current state of the path.\n\t * This takes in to account both the state variables and observables.\n\t */\n\tpublic Object evaluateInCurrentState(Expression expr) throws PrismLangException\n\t{\n\t\tEvaluateContextFull ec = new EvaluateContextFull(getCurrentState(), getCurrentObservation());\n\t\treturn expr.evaluate(ec);\n\t}\n\t\n\t/**\n\t * Evaluate a Boolean-valued expression in the current state of the path.\n\t * This takes in to account both the state variables and observables.\n\t */\n\tpublic boolean evaluateBooleanInCurrentState(Expression expr) throws PrismLangException\n\t{\n\t\tEvaluateContextFull ec = new EvaluateContextFull(getCurrentState(), getCurrentObservation());\n\t\treturn TypeBool.getInstance().castValueTo(expr.evaluate(ec), EvalMode.FP);\n\t}\n\n\t/**\n\t * Evaluate an expression in the penultimate state of the path.\n\t * This takes in to account both the state variables and observables.\n\t */\n\tpublic Object evaluateInPreviousState(Expression expr) throws PrismLangException\n\t{\n\t\tEvaluateContextFull ec = new EvaluateContextFull(getPreviousState(), getPreviousObservation());\n\t\treturn expr.evaluate(ec);\n\t}\n\t\n\t/**\n\t * Evaluate a Boolean-valued expression in the penultimate state of the path.\n\t * This takes in to account both the state variables and observables.\n\t */\n\tpublic boolean evaluateBooleanInPreviousState(Expression expr) throws PrismLangException\n\t{\n\t\tEvaluateContextFull ec = new EvaluateContextFull(getPreviousState(), getPreviousObservation());\n\t\treturn TypeBool.getInstance().castValueTo(expr.evaluate(ec), EvalMode.FP);\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/PathDisplayer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport parser.State;\n\n/**\n * Abstract class for classes that \"display\" a simulation path.\n */\npublic abstract class PathDisplayer\n{\n\t/** Should we display (timed) snapshots, rather than steps? */\n\tprotected boolean showSnapshots = false;\n\t/** If we are displaying snapshots, how often? */\n\tprotected double snapshotTimeStep = 0.0;\n\t/** If we are displaying snapshots, when is the next one due? */\n\tprotected double nextTime = 0.0;\n\n\t/** Should we show changes in state only, or all steps? (not for snapshot mode) */\n\tprotected boolean showChangesOnly = true;\n\t\n\t/** Indices of variables to show (null = all) */\n\tprotected List<Integer> varsToShow = null;\n\n\t/** Should we show transition probabilities/rates? */\n\tprotected boolean showProbs = false;\n\t\n\t/** Should we display rewards? */\n\tprotected boolean showRewards = false;\n\n\t// Getters for config\n\n\t/**\n\t * Should we display (timed) snapshots, rather than steps?\n\t */\n\tpublic boolean getShowSnapshots()\n\t{\n\t\treturn showSnapshots;\n\t}\n\n\t/**\n\t * If we are displaying snapshots, how often?\n\t */\n\tpublic double getSnapshotTimeStep()\n\t{\n\t\treturn snapshotTimeStep;\n\t}\n\n\t/**\n\t * Should we show changes in state only, or all steps? (not for snapshot mode)\n\t */\n\tpublic boolean getShowChangesOnly()\n\t{\n\t\treturn showChangesOnly;\n\t}\n\t\n\t/**\n\t * Should we display transition probabilities/rates?\n\t */\n\tpublic boolean getShowProbs()\n\t{\n\t\treturn showProbs;\n\t}\n\t\n\t/**\n\t * Should we display rewards?\n\t */\n\tpublic boolean getShowRewards()\n\t{\n\t\treturn showRewards;\n\t}\n\t\n\t// Setters for config\n\n\t/**\n\t * Set to display (timed) snapshots, rather than steps.\n\t */\n\tpublic void setToShowSteps()\n\t{\n\t\tthis.showSnapshots = false;\n\t}\n\n\t/**\n\t * Set to display steps, rather than (timed) snapshots.\n\t */\n\tpublic void setToShowSnapShots(double timeStep)\n\t{\n\t\tthis.showSnapshots = true;\n\t\tthis.snapshotTimeStep = timeStep;\n\t}\n\n\t/**\n\t * Set whether we show changes in state only, or all steps (not for snapshot mode).\n\t */\n\tpublic void setShowChangesOnly(boolean showChangesOnly)\n\t{\n\t\tthis.showChangesOnly = showChangesOnly;\n\t}\n\n\t/**\n\t * Set (indices of) vars to show values of (null = all).\n\t */\n\tpublic void setVarsToShow(List<Integer> varsToShow)\n\t{\n\t\t// Take a copy of var index list\n\t\tthis.varsToShow = varsToShow == null ? null : new ArrayList<Integer>(varsToShow);\n\t}\n\n\t/**\n\t * Set whether we show the probability/rate for each transition\n\t */\n\tpublic void setShowProbs(boolean showProbs)\n\t{\n\t\tthis.showProbs = showProbs;\n\t}\n\n\t/**\n\t * Set whether we we display rewards.\n\t */\n\tpublic void setShowRewards(boolean showRewards)\n\t{\n\t\tthis.showRewards = showRewards;\n\t}\n\n\t// Methods called by path owner\n\n\tpublic void start(State initialState, double[] initialStateRewards)\n\t{\n\t\tstartDisplay(initialState, initialStateRewards);\n\t\tif (showSnapshots) {\n\t\t\tnextTime = snapshotTimeStep;\n\t\t}\n\t}\n\n\tpublic void step(double timeSpent, double timeCumul, String actionString, Object probability, double[] transitionRewards, long newStateIndex, State newState, double[] newStateRewards)\n\t{\n\t\tif (showSnapshots) {\n\t\t\tif (timeCumul < nextTime) {\n\t\t\t\treturn;\n\t\t\t} else {\n\t\t\t\twhile (timeCumul >= nextTime) {\n\t\t\t\t\tdisplaySnapshot(nextTime, newStateIndex, newState, newStateRewards);\n\t\t\t\t\tnextTime += snapshotTimeStep;\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\tdisplayStep(timeSpent, timeCumul, actionString, probability, transitionRewards, newStateIndex, newState, newStateRewards);\n\t\t}\n\t}\n\n\tpublic void end()\n\t{\n\t\tendDisplay();\n\t}\n\n\t// Display methods to be implemented by subclasses\n\n\t/**\n\t * Start displaying a path beginning with state {@code initialState}.\n\t */\n\tpublic abstract void startDisplay(State initialState, double[] initialStateRewards);\n\n\t/**\n\t * Displaying a step of a path.\n\t */\n\tpublic abstract void displayStep(double timeSpent, double timeCumul, String actionString, Object probability, double[] transitionRewards, long newStateIndex, State newState, double[] newStateRewards);\n\n\t/**\n\t * Displaying a snapshot of a path at a particular time instant.\n\t */\n\tpublic abstract void displaySnapshot(double timeCumul, long newStateIndex, State newState, double[] newStateRewards);\n\n\t/**\n\t * Finish displaying a path.\n\t */\n\tpublic abstract void endDisplay();\n\n\t/**\n\t * \"Close\" this displayer (e.g., if it is to a file, close the file).\n\t */\n\tpublic void close()\n\t{\n\t\t// By default, do nothing\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/PathFull.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.util.ArrayList;\n\nimport parser.State;\nimport prism.ModelGenerator;\nimport prism.ModelInfo;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.RewardGenerator;\nimport userinterface.graph.Graph;\n\n/**\n * Stores and manipulates a path though a model.\n * The full path is stored, i.e. all info at all steps.\n * State objects and arrays are copied for storage.\n */\npublic class PathFull extends Path implements PathFullInfo\n{\n\t// Model to which the path corresponds\n\tprivate ModelInfo modelInfo;\n\tprivate RewardGenerator rewardGen;\n\t// Does model use continuous time?\n\tprivate boolean continuousTime;\n\t// Model info/stats\n\tprivate int numRewardStructs;\n\n\t// The path, i.e. list of states, etc.\n\tprivate ArrayList<Step> steps;\n\t// The path length (just for convenience; equal to steps.size() - 1)\n\tprivate int size;\n\n\t// Loop detector for path\n\tprotected LoopDetector loopDet;\n\n\t/**\n\t * Constructor: creates a new (empty) PathFull object for a specific model.\n\t */\n\tpublic PathFull(ModelInfo modelInfo, RewardGenerator rewardGen)\n\t{\n\t\t// Store model and info\n\t\tthis.modelInfo = modelInfo;\n\t\tcontinuousTime = modelInfo.getModelType().continuousTime();\n\t\tthis.rewardGen = rewardGen;\n\t\tnumRewardStructs = rewardGen.getNumRewardStructs();\n\t\t// Create list to store path\n\t\tsteps = new ArrayList<Step>(100);\n\t\t// Initialise variables\n\t\tclear();\n\t\t// Create loop detector\n\t\tloopDet = new LoopDetector();\n\t}\n\n\t/**\n\t * Clear the path.\n\t */\n\tprotected void clear()\n\t{\n\t\tsteps.clear();\n\t\tsize = 0;\n\t}\n\n\t// MUTATORS (for Path)\n\n\t@Override\n\tpublic void initialise(State initialState, State initialObs, double[] initialStateRewards)\n\t{\n\t\tclear();\n\t\t// Add new step item to the path\n\t\tStep step = new Step();\n\t\tsteps.add(step);\n\t\t// Add (copies of) initial state and state rewards to new step\n\t\tstep.state = new State(initialState);\n\t\tstep.obs = initialObs == null ? null : new State(initialObs);\n\t\tstep.stateRewards = initialStateRewards.clone();\n\t\t// Set cumulative time/reward (up until entering this state)\n\t\tstep.timeCumul = 0.0;\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\tstep.rewardsCumul[i] = 0.0;\n\t\t}\n\t\t// Initialise loop detector\n\t\tloopDet.initialise();\n\t}\n\n\t@Override\n\tpublic void addStep(int choice, Object action, String actionString, Object probability, double[] transitionRewards, State newState, State newObs, double[] newStateRewards,\n\t\t\tModelGenerator modelGen)\n\t{\n\t\taddStep(1.0, choice, action, actionString, probability, transitionRewards, newState, newObs, newStateRewards, modelGen);\n\t}\n\n\t@Override\n\tpublic void addStep(double time, int choice, Object action, String actionString, Object probability, double[] transitionRewards, State newState,\n\t\t\tState newObs, double[] newStateRewards, ModelGenerator modelGen)\n\t{\n\t\tStep stepOld, stepNew;\n\t\t// Add info to last existing step\n\t\tstepOld = steps.get(steps.size() - 1);\n\t\tstepOld.time = time;\n\t\tstepOld.choice = choice;\n\t\tstepOld.action = action;\n\t\tstepOld.actionString = actionString;\n\t\tstepOld.probability = probability;\n\t\tstepOld.transitionRewards = transitionRewards.clone();\n\t\t// Add new step item to the path\n\t\tstepNew = new Step();\n\t\tsteps.add(stepNew);\n\t\t// Add (copies of) new state, observation and state rewards to new step\n\t\tstepNew.state = new State(newState);\n\t\tstepNew.obs = newObs == null ? null : new State(newObs);\n\t\tstepNew.stateRewards = newStateRewards.clone();\n\t\t// Set cumulative time/rewards (up until entering this state)\n\t\tstepNew.timeCumul = stepOld.timeCumul + time;\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\tstepNew.rewardsCumul[i] = stepOld.rewardsCumul[i];\n\t\t\tif (continuousTime)\n\t\t\t\tstepNew.rewardsCumul[i] += stepOld.stateRewards[i] * time;\n\t\t\telse\n\t\t\t\tstepNew.rewardsCumul[i] += stepOld.stateRewards[i];\n\t\t\tstepNew.rewardsCumul[i] += transitionRewards[i];\n\t\t}\n\t\t// Update size too\n\t\tsize++;\n\t\t// Update loop detector\n\t\tloopDet.addStep(this, modelGen);\n\t}\n\n\t@Override\n\tpublic void setStrategyInfoForCurrentState(int memory, Object decision)\n\t{\n\t\tsteps.get(steps.size() - 1).stratMemory = memory;\n\t\tsteps.get(steps.size() - 1).stratDecision = decision;\n\t}\n\t\n\t// MUTATORS (additional)\n\n\t/**\n\t * Backtrack to a particular step within the current path.\n\t * @param step The step of the path to backtrack to (step >= 0)\n\t */\n\tpublic void backtrack(int step)\n\t{\n\t\tint i, n;\n\t\t// Remove steps after index 'step'\n\t\tn = steps.size() - 1;\n\t\tfor (i = n; i > step; i--)\n\t\t\tsteps.remove(i);\n\t\t// Update info in last step of path\n\t\tStep last = steps.get(steps.size() - 1);\n\t\tlast.time = 0.0;\n\t\tlast.choice = -1;\n\t\tlast.action = null;\n\t\tlast.actionString = null;\n\t\tlast.probability = 0.0;\n\t\tfor (i = 0; i < numRewardStructs; i++)\n\t\t\tlast.transitionRewards[i] = 0.0;\n\t\t// Update size too\n\t\tsize = step;\n\t\t// Update loop detector\n\t\tloopDet.backtrack(this);\n\t}\n\n\t/**\n\t * Remove the prefix of the current path up to the given path step.\n\t * Index step should be >=0 and <= the total path size. \n\t * @param step The step before which states will be removed.\n\t */\n\tpublic void removePrecedingStates(int step)\n\t{\n\t\tint i, j, numKeep, sizeOld;\n\t\tdouble timeCumul, rewardsCumul[];\n\n\t\t// Ignore trivial case\n\t\tif (step == 0)\n\t\t\treturn;\n\t\t// Get cumulative time/reward for index 'step'\n\t\ttimeCumul = getCumulativeTime(step);\n\t\trewardsCumul = new double[numRewardStructs];\n\t\tfor (j = 0; j < numRewardStructs; j++)\n\t\t\trewardsCumul[j] = getCumulativeReward(step, j);\n\t\t// Move later steps of path 'step' places forward \n\t\t// and subtract time/reward as appropriate \n\t\tnumKeep = steps.size() - step;\n\t\tfor (i = 0; i < numKeep; i++) {\n\t\t\tStep tmp = steps.get(i + step);\n\t\t\ttmp.timeCumul -= timeCumul;\n\t\t\tfor (j = 0; j < numRewardStructs; j++)\n\t\t\t\ttmp.rewardsCumul[j] -= rewardsCumul[j];\n\t\t\tsteps.set(i, tmp);\n\t\t}\n\t\t// Remove steps after index 'step'\n\t\tsizeOld = steps.size();\n\t\tfor (i = sizeOld - 1; i >= numKeep; i--)\n\t\t\tsteps.remove(i);\n\t\t// Update size too\n\t\tsize = steps.size() - 1;\n\t\t// Update loop detector\n\t\tloopDet.removePrecedingStates(this, step);\n\t}\n\n\t// ACCESSORS (for Path (and some of PathFullInfo))\n\n\t@Override\n\tpublic boolean continuousTime()\n\t{\n\t\treturn continuousTime;\n\t}\n\n\t@Override\n\tpublic long size()\n\t{\n\t\treturn size;\n\t}\n\n\t@Override\n\tpublic long numStates()\n\t{\n\t\treturn steps.size();\n\t}\n\n\t@Override\n\tpublic State getPreviousState()\n\t{\n\t\treturn steps.get(steps.size() - 2).state;\n\t}\n\n\t@Override\n\tpublic State getCurrentState()\n\t{\n\t\treturn steps.get(steps.size() - 1).state;\n\t}\n\n\t@Override\n\tpublic State getPreviousObservation()\n\t{\n\t\treturn steps.get(steps.size() - 2).obs;\n\t}\n\n\t@Override\n\tpublic State getCurrentObservation()\n\t{\n\t\treturn steps.get(steps.size() - 1).obs;\n\t}\n\n\t@Override\n\tpublic Object getPreviousAction()\n\t{\n\t\treturn steps.get(steps.size() - 2).action;\n\t}\n\n\t@Override\n\tpublic String getPreviousActionString()\n\t{\n\t\treturn steps.get(steps.size() - 2).actionString;\n\t}\n\n\t@Override\n\tpublic Object getPreviousProbability()\n\t{\n\t\treturn steps.get(steps.size() - 2).probability;\n\t}\n\n\t@Override\n\tpublic double getTotalTime()\n\t{\n\t\treturn size < 1 ? 0.0 : steps.get(steps.size() - 1).timeCumul;\n\t}\n\n\t@Override\n\tpublic double getTimeInPreviousState()\n\t{\n\t\treturn steps.get(steps.size() - 2).time;\n\t}\n\n\t@Override\n\tpublic double getTotalCumulativeReward(int rsi)\n\t{\n\t\treturn steps.get(steps.size() - 1).rewardsCumul[rsi];\n\t}\n\n\t@Override\n\tpublic double getPreviousStateReward(int rsi)\n\t{\n\t\treturn steps.get(steps.size() - 2).stateRewards[rsi];\n\t}\n\n\t@Override\n\tpublic double[] getPreviousStateRewards()\n\t{\n\t\treturn steps.get(steps.size() - 2).stateRewards;\n\t}\n\n\t@Override\n\tpublic double getPreviousTransitionReward(int rsi)\n\t{\n\t\treturn steps.get(steps.size() - 2).transitionRewards[rsi];\n\t}\n\n\t@Override\n\tpublic double[] getPreviousTransitionRewards()\n\t{\n\t\treturn steps.get(steps.size() - 2).transitionRewards;\n\t}\n\n\t@Override\n\tpublic double getCurrentStateReward(int rsi)\n\t{\n\t\treturn steps.get(steps.size() - 1).stateRewards[rsi];\n\t}\n\n\t@Override\n\tpublic double[] getCurrentStateRewards()\n\t{\n\t\treturn steps.get(steps.size() - 1).stateRewards;\n\t}\n\n\t@Override\n\tpublic int getCurrentStrategyMemory()\n\t{\n\t\treturn steps.get(steps.size() - 1).stratMemory;\n\t}\n\t\n\t@Override\n\tpublic Object getCurrentStrategyDecision()\n\t{\n\t\treturn steps.get(steps.size() - 1).stratDecision;\n\t}\n\t\n\t@Override\n\tpublic boolean isLooping()\n\t{\n\t\treturn loopDet.isLooping();\n\t}\n\n\t@Override\n\tpublic long loopStart()\n\t{\n\t\treturn loopDet.loopStart();\n\t}\n\n\t@Override\n\tpublic long loopEnd()\n\t{\n\t\treturn loopDet.loopEnd();\n\t}\n\n\t// ACCESSORS (for PathFullInfo)\n\n\t@Override\n\tpublic State getState(int step)\n\t{\n\t\treturn steps.get(step).state;\n\t}\n\n\t@Override\n\tpublic State getObservation(int step)\n\t{\n\t\treturn steps.get(step).obs;\n\t}\n\t\n\t@Override\n\tpublic double getStateReward(int step, int rsi)\n\t{\n\t\treturn steps.get(step).stateRewards[rsi];\n\t}\n\n\t/**\n\t * Get an array of state rewards for the state at a given step of the path.\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tprotected double[] getStateRewards(int step)\n\t{\n\t\treturn steps.get(step).stateRewards;\n\t}\n\n\t@Override\n\tpublic double getCumulativeTime(int step)\n\t{\n\t\treturn steps.get(step).timeCumul;\n\t}\n\n\t@Override\n\tpublic double getCumulativeReward(int step, int rsi)\n\t{\n\t\treturn steps.get(step).rewardsCumul[rsi];\n\t}\n\n\t@Override\n\tpublic int getStrategyMemory(int step)\n\t{\n\t\treturn steps.get(step).stratMemory;\n\t}\n\t\n\t@Override\n\tpublic Object getStrategyDecision(int step)\n\t{\n\t\treturn steps.get(step).stratDecision;\n\t}\n\t\n\t@Override\n\tpublic double getTime(int step)\n\t{\n\t\treturn steps.get(step).time;\n\t}\n\n\t@Override\n\tpublic int getChoice(int step)\n\t{\n\t\treturn steps.get(step).choice;\n\t}\n\n\t@Override\n\tpublic Object getAction(int step)\n\t{\n\t\treturn steps.get(step).action;\n\t}\n\n\t@Override\n\tpublic String getActionString(int step)\n\t{\n\t\treturn steps.get(step).actionString;\n\t}\n\n\t/**\n\t * Get the probability or rate associated with a given step.\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic Object getProbability(int step)\n\t{\n\t\treturn steps.get(steps.size() - 2).probability;\n\t}\n\n\t@Override\n\tpublic double getTransitionReward(int step, int rsi)\n\t{\n\t\treturn steps.get(step).transitionRewards[rsi];\n\t}\n\n\t/**\n\t * Get an array of transitions reward associated with a given step.\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tprotected double[] getTransitionRewards(int step)\n\t{\n\t\treturn steps.get(step).transitionRewards;\n\t}\n\n\t@Override\n\tpublic boolean hasRewardInfo()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean hasChoiceInfo()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean hasActionInfo()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean hasTimeInfo()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic boolean hasLoopInfo()\n\t{\n\t\treturn true;\n\t}\n\n\t// Other methods\n\n\t/**\n\t * Pass the path to a PathDisplayer object.\n\t * @param displayer The PathDisplayer\n\t */\n\tpublic void display(PathDisplayer displayer) throws PrismException\n\t{\n\t\t// In the absence of model info, do nothing\n\t\tif (modelInfo == null) {\n\t\t\treturn;\n\t\t}\n\t\t// Display path\n\t\tdisplayer.start(getState(0), getStateRewards(0));\n\t\t// Get length (non-on-the-fly paths will never exceed length Integer.MAX_VALUE) \n\t\tlong nLong = size();\n\t\tif (nLong > Integer.MAX_VALUE)\n\t\t\tthrow new PrismException(\"PathFull cannot deal with paths over length \" + Integer.MAX_VALUE);\n\t\tint n = (int) nLong;\n\t\t// Loop\n\t\tfor (int i = 1; i <= n; i++) {\n\t\t\tdisplayer.step(getTime(i - 1), getCumulativeTime(i), getActionString(i - 1), getProbability(i - 1), getTransitionRewards(i), i, getState(i),\n\t\t\t\t\tgetStateRewards(i));\n\t\t}\n\t\tdisplayer.end();\n\t}\n\n\t/**\n\t * Pass the path to a PathDisplayer object, running in a new thread. \n\t * @param displayer The PathDisplayer\n\t */\n\tpublic void displayThreaded(PathDisplayer displayer) throws PrismException\n\t{\n\t\t// In the absence of model info, do nothing\n\t\tif (modelInfo == null) {\n\t\t\treturn;\n\t\t}\n\t\t// Display path\n\t\tnew DisplayThread(displayer).start();\n\t}\n\n\t/**\n\t * Export path to a PrismLog (e.g. file, stdout).\n\t * @param log PrismLog to which the path should be exported to.\n\t * @param showTimeCumul Show time in cumulative form?\n\t * @param colSep String used to separate columns in display\n\t * @param vars Restrict printing to these variables (indices) and steps which change them (ignore if null)\n\t */\n\tpublic void exportToLog(PrismLog log, boolean showTimeCumul, String colSep, ArrayList<Integer> vars) throws PrismException\n\t{\n\t\texportToLog(log, showTimeCumul, false, colSep, vars);\n\t}\n\n\t/**\n\t * Export path to a PrismLog (e.g. file, stdout).\n\t * @param log PrismLog to which the path should be exported to.\n\t * @param showTimeCumul Show time in cumulative form?\n\t * @param showRewards Show rewards?\n\t * @param colSep String used to separate columns in display\n\t * @param vars Restrict printing to these variables (indices) and steps which change them (ignore if null)\n\t */\n\tpublic void exportToLog(PrismLog log, boolean showTimeCumul, boolean showRewards, String colSep, ArrayList<Integer> vars) throws PrismException\n\t{\n\t\tPathToText displayer = new PathToText(log, modelInfo, rewardGen);\n\t\tdisplayer.setShowTimeCumul(showTimeCumul);\n\t\tdisplayer.setColSep(colSep);\n\t\tdisplayer.setVarsToShow(vars);\n\t\tdisplayer.setShowRewards(showRewards);\n\t\tdisplay(displayer);\n\t}\n\n\t/**\n\t * Plot path on a graph.\n\t * @param graphModel Graph on which to plot path\n\t */\n\tpublic void plotOnGraph(Graph graphModel) throws PrismException\n\t{\n\t\tPathToGraph displayer = new PathToGraph(graphModel, modelInfo, rewardGen);\n\t\tdisplayThreaded(displayer);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\tint i;\n\t\tString s = \"\";\n\t\tfor (i = 0; i <= size; i++) {\n\t\t\ts += getState(i) + \"\\n\";\n\t\t}\n\t\treturn s;\n\t}\n\n\t/**\n\t * Inner class to store info about a single path step.\n\t */\n\tclass Step\n\t{\n\t\tpublic Step()\n\t\t{\n\t\t\t// Set (unknown) defaults and initialise arrays\n\t\t\tstate = null;\n\t\t\tobs = null;\n\t\t\tstateRewards = new double[numRewardStructs];\n\t\t\ttimeCumul = 0.0;\n\t\t\trewardsCumul = new double[numRewardStructs];\n\t\t\ttime = 0.0;\n\t\t\tchoice = -1;\n\t\t\taction = null;\n\t\t\tactionString = null;\n\t\t\tprobability = 0.0;\n\t\t\ttransitionRewards = new double[numRewardStructs];\n\t\t}\n\n\t\t// Current state (before transition)\n\t\tpublic State state;\n\t\t// Observation for current state\n\t\tpublic State obs;\n\t\t// State rewards for current state\n\t\tpublic double stateRewards[];\n\t\t// Cumulative time spent up until entering this state\n\t\tpublic double timeCumul;\n\t\t// Cumulative rewards spent up until entering this state\n\t\tpublic double rewardsCumul[];\n\t\t// Current memory of strategy (if present) on entering this state\n\t\tpublic int stratMemory;\n\t\t// Next decision of strategy (if present) for current state\n\t\tpublic Object stratDecision;\n\t\t// Time spent in state\n\t\tpublic double time;\n\t\t// Index of the choice taken\n\t\tpublic int choice;\n\t\t// Action taken\n\t\tpublic Object action;\n\t\t// String describing the action taken\n\t\tpublic String actionString;\n\t\t// Probability or rate of step\n\t\tpublic Object probability;\n\t\t// Transition rewards associated with step\n\t\tpublic double transitionRewards[];\n\t}\n\n\tclass DisplayThread extends Thread\n\t{\n\t\tprivate PathDisplayer displayer = null;\n\n\t\tpublic DisplayThread(PathDisplayer displayer)\n\t\t{\n\t\t\tthis.displayer = displayer;\n\t\t}\n\n\t\tpublic void run()\n\t\t{\n\t\t\ttry {\n\t\t\t\tdisplay(displayer);\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// Just ignore problems\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/PathFullInfo.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport parser.State;\n\n/**\n * Interface for classes that provide (read) access to a path through a model.\n */\npublic interface PathFullInfo\n{\n\t/**\n\t * Get the size of the path (number of steps; or number of states - 1).\n\t */\n\tpublic abstract long size();\n\t\n\t/**\n\t * Get the state at a given step of the path.\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic abstract State getState(int step);\n\n\t/**\n\t * Get the observation at a given step of the path.\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic abstract State getObservation(int step);\n\n\t/**\n\t * Get a state reward for the state at a given step of the path.\n\t * If no reward info is stored ({@link #hasRewardInfo()} is false), returns 0.0. \n\t * @param step Step index (0 = initial state/step of path)\n\t * @param rsi Reward structure index\n\t */\n\tpublic abstract double getStateReward(int step, int rsi);\n\n\t/**\n\t * Get the total time spent up until entering a given step of the path.\n\t * If no time info is stored ({@link #hasTimeInfo()} is false), returns 0.0. \n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic abstract double getCumulativeTime(int step);\n\n\t/**\n\t * Get the total (state and transition) reward accumulated up until entering a given step of the path.\n\t * If no reward info is stored ({@link #hasRewardInfo()} is false), returns 0.0. \n\t * @param step Step index (0 = initial state/step of path)\n\t * @param rsi Reward structure index\n\t */\n\tpublic abstract double getCumulativeReward(int step, int rsi);\n\n\t/**\n\t * Get the memory of the strategy (if present) at a given step of the path.\n\t */\n\tpublic abstract int getStrategyMemory(int step);\n\t\n\t/**\n\t * Get the decision taken by the strategy (if present) in a given step of the path.\n\t */\n\tpublic abstract Object getStrategyDecision(int step);\n\t\n\t/**\n\t * Get the time spent in a state at a given step of the path.\n\t * If no time info is stored ({@link #hasTimeInfo()} is false), returns 0.0. \n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic abstract double getTime(int step);\n\n\t/**\n\t * Get the index of the choice taken for a given step.\n\t * If no choice info is stored ({@link #hasChoiceInfo()} is false), returns 0. \n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic abstract int getChoice(int step);\n\n\t/**\n\t * Get the action taken in a given step.\n\t * If no action info is stored ({@link #hasActionInfo()} is false), returns \"\". \n\t */\n\tpublic abstract Object getAction(int step);\n\t\n\t/**\n\t * Get a string describing the action taken a given step.\n\t * If no action info is stored ({@link #hasActionInfo()} is false), returns \"\". \n\t */\n\tpublic abstract String getActionString(int step);\n\t\n\t/**\n\t * Get a transition reward associated with a given step.\n\t * If no reward info is stored ({@link #hasRewardInfo()} is false), returns 0.0. \n\t * @param step Step index (0 = initial state/step of path)\n\t * @param rsi Reward structure index\n\t */\n\tpublic abstract double getTransitionReward(int step, int rsi);\n\t\n\t/**\n\t * Does the path contain a deterministic loop?\n\t * If no loop info is stored ({@link #hasLoopInfo()} is false), returns false. \n\t */\n\tpublic abstract boolean isLooping();\n\t\n\t/**\n\t * What is the step index of the start of the deterministic loop, if it exists?\n\t * If no loop info is stored ({@link #hasLoopInfo()} is false), returns 0. \n\t */\n\tpublic abstract long loopStart();\n\t\n\t/**\n\t * What is the step index of the end of the deterministic loop, if it exists?\n\t * If no loop info is stored ({@link #hasLoopInfo()} is false), returns 0. \n\t */\n\tpublic abstract long loopEnd();\n\t\n\t/**\n\t * Does this object store information about rewards?\n\t */\n\tpublic abstract boolean hasRewardInfo();\n\t\n\t/**\n\t * Does this object store information about which choices were taken?\n\t */\n\tpublic abstract boolean hasChoiceInfo();\n\t\n\t/**\n\t * Does this object store information about rewards?\n\t */\n\tpublic abstract boolean hasActionInfo();\n\t\n\t/**\n\t * Does this object store information about time elapse (for continuous-time models)?\n\t */\n\tpublic abstract boolean hasTimeInfo();\n\t\n\t/**\n\t * Does this object store information about loops in the path?\n\t */\n\tpublic abstract boolean hasLoopInfo();\n}\n"
  },
  {
    "path": "prism/src/simulator/PathFullPrefix.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport parser.*;\nimport prism.ModelGenerator;\n\n/**\n * Represents a prefix of an existing PathFull object.\n * Used by Samplers (which expect a Path) to iterate over a whole path. \n */\npublic class PathFullPrefix extends Path\n{\n\t// Path of which this a prefix\n\tprivate PathFull pathFull;\n\t// Length (number of states) in the prefix\n\tprivate int prefixLength;\n\t\n\t/**\n\t * Constructor: create from an existing PathFull object and a prefix length.\n\t */\n\tpublic PathFullPrefix(PathFull pathFull, int prefixLength)\n\t{\n\t\tthis.pathFull = pathFull;\n\t\tthis.prefixLength = prefixLength;\n\t}\n\n\t// MUTATORS (for Path)\n\n\t@Override\n\tpublic void initialise(State initialState, State initialObs, double[] initialStateRewards)\n\t{\n\t\t// Do nothing (we are not allowed to modify the underlying PathFull)\n\t}\n\n\t@Override\n\tpublic void addStep(int choice, Object action, String actionString, Object probability, double[] transitionRewards, State newState, State newObs, double[] newStateRewards, ModelGenerator modelGen)\n\t{\n\t\t// Do nothing (we are not allowed to modify the underlying PathFull)\n\t}\n\n\t@Override\n\tpublic void addStep(double time, int choice, Object action, String actionString, Object probability, double[] transitionRewards, State newState, State newObs, double[] newStateRewards, ModelGenerator modelGen)\n\t{\n\t\t// Do nothing (we are not allowed to modify the underlying PathFull)\n\t}\n\n\t@Override\n\tpublic void setStrategyInfoForCurrentState(int memory, Object decision)\n\t{\n\t\t// Do nothing (we are not allowed to modify the underlying PathFull)\n\t}\n\t\n\t// MUTATORS (additional)\n\t\n\tpublic void setPrefixLength(int prefixLength)\n\t{\n\t\tthis.prefixLength = prefixLength;\n\t}\n\t\n\t// ACCESSORS (for Path)\n\n\t@Override\n\tpublic boolean continuousTime()\n\t{\n\t\treturn pathFull.continuousTime();\n\t}\n\t\n\t@Override\n\tpublic long size()\n\t{\n\t\treturn prefixLength + 1;\n\t}\n\n\t@Override\n\tpublic long numStates()\n\t{\n\t\treturn prefixLength;\n\t}\n\n\t@Override\n\tpublic State getPreviousState()\n\t{\n\t\treturn pathFull.getState(prefixLength - 1);\n\t}\n\n\t@Override\n\tpublic State getCurrentState()\n\t{\n\t\treturn pathFull.getState(prefixLength);\n\t}\n\n\t@Override\n\tpublic State getPreviousObservation()\n\t{\n\t\treturn pathFull.getObservation(prefixLength - 1);\n\t}\n\n\t@Override\n\tpublic State getCurrentObservation()\n\t{\n\t\treturn pathFull.getObservation(prefixLength);\n\t}\n\n\t@Override\n\tpublic Object getPreviousAction()\n\t{\n\t\treturn pathFull.getAction(prefixLength - 1);\n\t}\n\t\n\t@Override\n\tpublic String getPreviousActionString()\n\t{\n\t\treturn pathFull.getActionString(prefixLength - 1);\n\t}\n\t\n\t@Override\n\tpublic Object getPreviousProbability()\n\t{\n\t\treturn pathFull.getProbability(prefixLength - 1);\n\t}\n\n\t@Override\n\tpublic double getTotalTime()\n\t{\n\t\treturn pathFull.getCumulativeTime(prefixLength);\n\t}\n\n\t@Override\n\tpublic double getTimeInPreviousState()\n\t{\n\t\treturn pathFull.getTime(prefixLength - 1);\n\t}\n\n\t@Override\n\tpublic double getTotalCumulativeReward(int rsi)\n\t{\n\t\treturn pathFull.getCumulativeReward(prefixLength, rsi);\n\t}\n\t\n\t@Override\n\tpublic double getPreviousStateReward(int rsi)\n\t{\n\t\treturn pathFull.getStateReward(prefixLength - 1, rsi);\n\t}\n\t\n\t@Override\n\tpublic double[] getPreviousStateRewards()\n\t{\n\t\treturn pathFull.getStateRewards(prefixLength - 1);\n\t}\n\t\n\t@Override\n\tpublic double getPreviousTransitionReward(int rsi)\n\t{\n\t\treturn pathFull.getTransitionReward(prefixLength - 1, rsi);\n\t}\n\t\n\t@Override\n\tpublic double[] getPreviousTransitionRewards()\n\t{\n\t\treturn pathFull.getTransitionRewards(prefixLength - 1);\n\t}\n\t\n\t@Override\n\tpublic double getCurrentStateReward(int rsi)\n\t{\n\t\treturn pathFull.getStateReward(prefixLength, rsi);\n\t}\n\t\n\t@Override\n\tpublic double[] getCurrentStateRewards()\n\t{\n\t\treturn pathFull.getStateRewards(prefixLength);\n\t}\n\t\n\t@Override\n\tpublic int getCurrentStrategyMemory()\n\t{\n\t\treturn pathFull.getStrategyMemory(prefixLength);\n\t}\n\t\n\t@Override\n\tpublic Object getCurrentStrategyDecision()\n\t{\n\t\treturn pathFull.getStrategyDecision(prefixLength);\n\t}\n\t\n\t@Override\n\tpublic boolean isLooping()\n\t{\n\t\treturn pathFull.isLooping() && pathFull.loopEnd() < prefixLength;\n\t}\n\t\n\t@Override\n\tpublic long loopStart()\n\t{\n\t\treturn isLooping() ? pathFull.loopStart() : -1;\n\t}\n\t\n\t@Override\n\tpublic long loopEnd()\n\t{\n\t\treturn isLooping() ? pathFull.loopEnd() : -1;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/PathOnTheFly.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport parser.State;\nimport prism.ModelGenerator;\nimport prism.ModelInfo;\nimport prism.RewardGenerator;\n\n/**\n * Stores and manipulates a path though a model.\n * Minimal info is stored - just enough to allow checking of properties.\n */\npublic class PathOnTheFly extends Path\n{\n\t// Model to which the path corresponds\n\tprotected ModelInfo modelInfo;\n\t// Does model use continuous time?\n\tprotected boolean continuousTime;\n\t// Model info/stats\n\tprotected int numRewardStructs;\n\n\t// Path info required to implement Path abstract class:\n\tprotected long size;\n\tprotected boolean init;\n\tprotected State previousState;\n\tprotected State currentState;\n\tprotected State previousObs;\n\tprotected State currentObs;\n\tprotected Object previousAction;\n\tprotected String previousActionString;\n\tprotected Object previousProbability;\n\tprotected double totalTime;\n\tdouble timeInPreviousState;\n\tprotected double totalRewards[];\n\tprotected double previousStateRewards[];\n\tprotected double previousTransitionRewards[];\n\tprotected double currentStateRewards[];\n\tprotected int currentStrategyMemory;\n\tprotected Object currentStrategyDecision;\n\t\n\t// Loop detector for path\n\tprotected LoopDetector loopDet;\n\n\t/**\n\t * Constructor: creates a new (empty) PathOnTheFly object for a specific model.\n\t */\n\tpublic PathOnTheFly(ModelInfo modelInfo, RewardGenerator rewardGen)\n\t{\n\t\t// Store model and info\n\t\tthis.modelInfo = modelInfo;\n\t\tcontinuousTime = modelInfo.getModelType().continuousTime();\n\t\tnumRewardStructs = rewardGen.getNumRewardStructs();\n\t\t// Create State objects for current/previous state\n\t\tpreviousState = new State(modelInfo.getNumVars());\n\t\tcurrentState = new State(modelInfo.getNumVars());\n\t\tpreviousObs = null;\n\t\tcurrentObs = null;\n\t\tif (modelInfo.getModelType().partiallyObservable()) {\n\t\t\tpreviousObs = new State(modelInfo.getNumObservables());\n\t\t\tcurrentObs = new State(modelInfo.getNumObservables());\n\t\t}\n\t\t// Create arrays to store totals\n\t\ttotalRewards = new double[numRewardStructs];\n\t\tpreviousStateRewards = new double[numRewardStructs];\n\t\tpreviousTransitionRewards = new double[numRewardStructs];\n\t\tcurrentStateRewards = new double[numRewardStructs];\n\t\t// Initialise path info\n\t\tclear();\n\t\t// Create loop detector\n\t\tloopDet = new LoopDetector();\n\t}\n\n\t/**\n\t * Clear the path.\n\t */\n\tprotected void clear()\n\t{\n\t\t// Initialise all path info\n\t\tsize = 0;\n\t\tinit = false;\n\t\tpreviousState.clear();\n\t\tcurrentState.clear();\n\t\ttotalTime = 0.0;\n\t\ttimeInPreviousState = 0.0;\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\ttotalRewards[i] = 0.0;\n\t\t\tpreviousStateRewards[i] = 0.0;\n\t\t\tpreviousTransitionRewards[i] = 0.0;\n\t\t\tcurrentStateRewards[i] = 0.0;\n\t\t}\n\t}\n\n\t// MUTATORS (for Path)\n\n\t@Override\n\tpublic void initialise(State initialState, State initialObs, double[] initialStateRewards)\n\t{\n\t\tclear();\n\t\tinit = true;\n\t\tcurrentState.copy(initialState);\n\t\tif (initialObs != null) {\n\t\t\tcurrentObs.copy(initialObs);\n\t\t}\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\tcurrentStateRewards[i] = initialStateRewards[i];\n\t\t}\n\t\t// Initialise loop detector\n\t\tloopDet.initialise();\n\t}\n\n\t@Override\n\tpublic void addStep(int choice, Object action, String actionString, Object probability, double[] transRewards, State newState, State newObs, double[] newStateRewards, ModelGenerator modelGen)\n\t{\n\t\taddStep(1.0, choice, action, actionString, probability, transRewards, newState, newObs, newStateRewards, modelGen);\n\t}\n\n\t@Override\n\tpublic void addStep(double time, int choice, Object action, String actionString, Object probability, double[] transRewards, State newState, State newObs, double[] newStateRewards, ModelGenerator modelGen)\n\t{\n\t\tsize++;\n\t\tpreviousState.copy(currentState);\n\t\tcurrentState.copy(newState);\n\t\tif (newObs != null) {\n\t\t\tpreviousObs.copy(currentObs);\n\t\t\tcurrentObs.copy(newObs);\n\t\t}\n\t\tpreviousAction = action;\n\t\tpreviousActionString = actionString;\n\t\tpreviousProbability = probability;\n\t\ttotalTime += time;\n\t\ttimeInPreviousState = time;\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\tif (continuousTime) {\n\t\t\t\ttotalRewards[i] += currentStateRewards[i] * time + transRewards[i];\n\t\t\t} else {\n\t\t\t\ttotalRewards[i] += currentStateRewards[i] + transRewards[i];\n\t\t\t}\n\t\t\tpreviousStateRewards[i] = currentStateRewards[i];\n\t\t\tpreviousTransitionRewards[i] = transRewards[i];\n\t\t\tcurrentStateRewards[i] = newStateRewards[i];\n\t\t}\n\t\t// Update loop detector\n\t\tloopDet.addStep(this, modelGen);\n\t}\n\n\t@Override\n\tpublic void setStrategyInfoForCurrentState(int memory, Object decision)\n\t{\n\t\tcurrentStrategyMemory = memory;\n\t\tcurrentStrategyDecision = decision;\n\t}\n\t\n\t// ACCESSORS (for Path)\n\n\t@Override\n\tpublic boolean continuousTime()\n\t{\n\t\treturn continuousTime;\n\t}\n\t\n\t@Override\n\tpublic long size()\n\t{\n\t\treturn size;\n\t}\n\n\t@Override\n\tpublic long numStates()\n\t{\n\t\treturn init ? size + 1 : 0;\n\t}\n\n\t@Override\n\tpublic State getPreviousState()\n\t{\n\t\treturn previousState;\n\t}\n\n\t@Override\n\tpublic State getCurrentState()\n\t{\n\t\treturn currentState;\n\t}\n\n\t@Override\n\tpublic State getPreviousObservation()\n\t{\n\t\treturn previousObs;\n\t}\n\n\t@Override\n\tpublic State getCurrentObservation()\n\t{\n\t\treturn currentObs;\n\t}\n\n\t@Override\n\tpublic Object getPreviousAction()\n\t{\n\t\treturn previousAction;\n\t}\n\t\t\n\t@Override\n\tpublic String getPreviousActionString()\n\t{\n\t\treturn previousActionString;\n\t}\n\n\t@Override\n\tpublic Object getPreviousProbability()\n\t{\n\t\treturn previousProbability;\n\t}\n\n\t@Override\n\tpublic double getTotalTime()\n\t{\n\t\treturn totalTime;\n\t}\n\n\t@Override\n\tpublic double getTimeInPreviousState()\n\t{\n\t\treturn timeInPreviousState;\n\t}\n\n\t@Override\n\tpublic double getTotalCumulativeReward(int rsi)\n\t{\n\t\treturn totalRewards[rsi];\n\t}\n\t\n\t@Override\n\tpublic double getPreviousStateReward(int rsi)\n\t{\n\t\treturn previousStateRewards[rsi];\n\t}\n\t\n\t@Override\n\tpublic double[] getPreviousStateRewards()\n\t{\n\t\treturn previousStateRewards;\n\t}\n\t\n\t@Override\n\tpublic double getPreviousTransitionReward(int rsi)\n\t{\n\t\treturn previousTransitionRewards[rsi];\n\t}\n\t\n\t@Override\n\tpublic double[] getPreviousTransitionRewards()\n\t{\n\t\treturn previousTransitionRewards;\n\t}\n\t\n\t@Override\n\tpublic double getCurrentStateReward(int rsi)\n\t{\n\t\treturn currentStateRewards[rsi];\n\t}\n\t\n\t@Override\n\tpublic double[] getCurrentStateRewards()\n\t{\n\t\treturn currentStateRewards;\n\t}\n\t\n\t@Override\n\tpublic int getCurrentStrategyMemory()\n\t{\n\t\treturn currentStrategyMemory;\n\t}\n\t\n\t@Override\n\tpublic Object getCurrentStrategyDecision()\n\t{\n\t\treturn currentStrategyDecision;\n\t}\n\t\n\t@Override\n\tpublic boolean isLooping()\n\t{\n\t\treturn loopDet.isLooping();\n\t}\n\t\n\t@Override\n\tpublic long loopStart()\n\t{\n\t\treturn loopDet.loopStart();\n\t}\n\t\n\t@Override\n\tpublic long loopEnd()\n\t{\n\t\treturn loopDet.loopEnd();\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/PathToGraph.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\n\nimport org.jfree.data.xy.XYDataItem;\n\nimport parser.State;\nimport parser.type.TypeDouble;\nimport prism.ModelInfo;\nimport prism.PrismException;\nimport prism.RewardGenerator;\nimport userinterface.graph.Graph;\nimport userinterface.graph.Graph.SeriesKey;\n\n/**\n * Class to display a simulation path in text form, sending to a PrismLog.\n */\npublic class PathToGraph extends PathDisplayer\n{\n\t/** Graph on which to plot path */\n\tprivate Graph graphModel = null;\n\tprivate List<SeriesKey> varSeriesKeys = null;\n\tprivate List<SeriesKey> rewardSeriesKeys = null;\n\n\t// Model/reward info\n\tprivate ModelInfo modelInfo;\n\tprivate int numVars;\n\tprivate RewardGenerator<Double> rewardGen;\n\tprivate int numRewardStructs;\n\n\t// Displayer state\n\tprivate double lastTime;\n\tprivate State lastState;\n\tprivate double[] lastStateRewards;\n\t/** For each variable/reward, whether we skipped plotting a point last time */\n\tprivate BitSet skippedVars = new BitSet();\n\tprivate BitSet skippedRewards = new BitSet();\n\n\t/**\n\t * Construct a {@link PathToGraph} object\n\t * @param graphModel Graph on which to plot path\n\t * @param modelInfo Model associated with path\n\t * @param rewardGen Rewards associated with path\n\t */\n\tpublic PathToGraph(Graph graphModel, ModelInfo modelInfo, RewardGenerator<Double> rewardGen)\n\t{\n\t\tthis.graphModel = graphModel;\n\t\tthis.modelInfo = modelInfo;\n\t\tthis.rewardGen = rewardGen;\n\n\t\t// Get model/reward info\n\t\tnumVars = modelInfo.getNumVars();\n\t\tnumRewardStructs = rewardGen.getNumRewardStructs();\n\t}\n\n\t// Display methods\n\n\t@Override\n\tpublic void startDisplay(State initialState, double[] initialStateRewards)\n\t{\n\t\t// Configure axes\n\t\tgraphModel.getXAxisSettings().setHeading(\"Time\");\n\t\tgraphModel.getYAxisSettings().setHeading(\"Value\");\n\n\t\t// Create series\n\t\tvarSeriesKeys = new ArrayList<Graph.SeriesKey>();\n\t\tif (varsToShow == null) {\n\t\t\tfor (int j = 0; j < numVars; j++) {\n\t\t\t\tvarSeriesKeys.add(graphModel.addSeries(modelInfo.getVarName(j)));\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int j = 0; j < numVars; j++) {\n\t\t\t\tif (varsToShow != null && varsToShow.contains(j))\n\t\t\t\t\tvarSeriesKeys.add(graphModel.addSeries(modelInfo.getVarName(j)));\n\t\t\t\telse\n\t\t\t\t\tvarSeriesKeys.add(null);\n\t\t\t}\n\t\t}\n\t\tif (showRewards) {\n\t\t\trewardSeriesKeys = new ArrayList<Graph.SeriesKey>();\n\t\t\tfor (int j = 0; j < numRewardStructs; j++) {\n\t\t\t\trewardSeriesKeys.add(graphModel.addSeries(rewardGen.getRewardStructNames().get(j)));\n\t\t\t}\n\t\t}\n\n\t\t// Display initial state\n\t\tlastState = new State(initialState.varValues.length);\n\t\tif (showRewards)\n\t\t\tlastStateRewards = explicit.Utils.cloneDoubleArray(initialStateRewards);\n\t\tdisplayState(0.0, initialState, initialStateRewards, true);\n\t}\n\n\t@Override\n\tpublic void displayStep(double timeSpent, double timeCumul, String actionString, Object probability, double[] transitionRewards, long newStateIndex, State newState, double[] newStateRewards)\n\t{\n\t\tdisplayState(timeCumul, newState, newStateRewards, !showChangesOnly);\n\t}\n\n\t@Override\n\tpublic void displaySnapshot(double timeCumul, long newStateIndex, State newState, double[] newStateRewards)\n\t{\n\t\tdisplayState(timeCumul, newState, newStateRewards, !showChangesOnly);\n\t}\n\n\tprivate void displayState(double time, State state, double[] stateRewards, boolean force)\n\t{\n\t\tif (varsToShow == null) {\n\t\t\tfor (int j = 0; j < numVars; j++) {\n\t\t\t\tObject val = state.varValues[j];\n\t\t\t\tboolean plot = force || !val.equals(lastState.varValues[j]);\n\t\t\t\tif (plot) {\n\t\t\t\t\tif (skippedVars.get(j))\n\t\t\t\t\t\taddPoint(varSeriesKeys.get(j), lastTime, lastState.varValues[j]);\n\t\t\t\t\taddPoint(varSeriesKeys.get(j), time, val);\n\t\t\t\t}\n\t\t\t\tskippedVars.set(j, !plot);\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int j : varsToShow) {\n\t\t\t\tObject val = state.varValues[j];\n\t\t\t\tboolean plot = force || !val.equals(lastState.varValues[j]);\n\t\t\t\tif (plot) {\n\t\t\t\t\tif (skippedVars.get(j))\n\t\t\t\t\t\taddPoint(varSeriesKeys.get(j), lastTime, lastState.varValues[j]);\n\t\t\t\t\taddPoint(varSeriesKeys.get(j), time, val);\n\t\t\t\t}\n\t\t\t\tskippedVars.set(j, !plot);\n\t\t\t}\n\t\t}\n\t\tif (showRewards) {\n\t\t\tfor (int j = 0; j < numRewardStructs; j++) {\n\t\t\t\tdouble d = stateRewards[j];\n\t\t\t\tboolean plot = force || lastStateRewards[j] != stateRewards[j];\n\t\t\t\tif (plot) {\n\t\t\t\t\tif (skippedRewards.get(j))\n\t\t\t\t\t\tgraphModel.addPointToSeries(rewardSeriesKeys.get(j), new XYDataItem(lastTime, lastStateRewards[j]));\n\t\t\t\t\tgraphModel.addPointToSeries(rewardSeriesKeys.get(j), new XYDataItem(time, d));\n\t\t\t\t}\n\t\t\t\tskippedRewards.set(j, !plot);\n\t\t\t}\n\t\t}\n\t\tlastTime = time;\n\t\tlastState.copy(state);\n\t\tif (showRewards) {\n\t\t\texplicit.Utils.copyDoubleArray(stateRewards, lastStateRewards);\n\t\t}\n\t}\n\n\t/**\n\t * Add a point to a given graph series. X-value is {@code x}.\n\t * Y-value is {@code value}, which will mapped to a double as appropriate.\n\t */\n\tprivate void addPoint(SeriesKey seriesKey, double x, Object val)\n\t{\n\t\tdouble d;\n\t\ttry {\n\t\t\td = TypeDouble.getInstance().castValueTo(val).doubleValue();\n\t\t\tgraphModel.addPointToSeries(seriesKey, new XYDataItem(x, d));\n\t\t} catch (PrismException e) {\n\t\t\tif (val instanceof Boolean) {\n\t\t\t\td = ((Boolean) val).booleanValue() ? 1.0 : 0.0;\n\t\t\t\tgraphModel.addPointToSeries(seriesKey, new XYDataItem(x, d));\n\t\t\t}\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void endDisplay()\n\t{\n\t\t// Always display last points to ensure complete plot lines\n\t\t// (it's OK to overwrite points)\n\t\tdisplayState(lastTime, lastState, lastStateRewards, true);\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/PathToText.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport parser.State;\nimport prism.ModelInfo;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\nimport prism.RewardGenerator;\n\n/**\n * Class to display a simulation path in text form, sending to a PrismLog.\n */\npublic class PathToText extends PathDisplayer\n{\n\t/** Log to display path to */\n\tprivate PrismLog log;\n\n\t// Model/reward info\n\tprivate ModelInfo modelInfo;\n\tprivate int numVars;\n\tprivate boolean contTime;\n\tprivate RewardGenerator rewardGen;\n\tprivate int numRewardStructs;\n\n\t// Config\n\tprivate boolean showTimeCumul = true;\n\tprivate boolean showTimeSpent = false;\n\tprivate String colSep = \" \";\n\n\t// Displayer state\n\t/** Is the next column the first? */\n\tprivate boolean firstCol;\n\t/** Last state */\n\tprivate State lastState;\n\t/** Last state rewards */\n\tprivate double[] lastStateRewards;\n\t/** Did the displayed info change in the current step? */\n\tprivate boolean changed;\n\n\t/**\n\t * Construct a {@link PathToText} object, which writes to a {@link PrismLog}.\n\t * The log will be {@code close()}d when {@link #close()} is called.\n\t * @param log Log to output path to\n\t * @param modelInfo Model associated with path\n\t * @param rewardGen Rewards associated with path\n\t */\n\tpublic PathToText(PrismLog log, ModelInfo modelInfo, RewardGenerator rewardGen)\n\t{\n\t\tthis.log = log;\n\t\tthis.modelInfo = modelInfo;\n\t\tthis.rewardGen = rewardGen;\n\n\t\t// Get model/reward info\n\t\tnumVars = modelInfo.getNumVars();\n\t\tcontTime = modelInfo.getModelType().continuousTime();\n\t\tnumRewardStructs = rewardGen.getNumRewardStructs();\n\t}\n\n\t// Setters\n\n\t/**\n\t * Set whether we show cumulative time (for continuous models only)\n\t */\n\tpublic void setShowTimeCumul(boolean showTimeCumul)\n\t{\n\t\tthis.showTimeCumul = showTimeCumul;\n\t}\n\n\t/**\n\t * Set whether we show time spent in each state (for continuous models only)\n\t */\n\tpublic void setShowTimeSpent(boolean showTimeSpent)\n\t{\n\t\tthis.showTimeSpent = showTimeSpent;\n\t}\n\n\t/**\n\t * Set the column separator for the table of path contents\n\t */\n\tpublic void setColSep(String colSep)\n\t{\n\t\tthis.colSep = colSep;\n\t}\n\n\t// Display methods\n\n\t@Override\n\tpublic void startDisplay(State initialState, double[] initialStateRewards)\n\t{\n\t\tint j;\n\n\t\t// Display header\n\t\tfirstCol = true;\n\t\tif (!getShowSnapshots()) {\n\t\t\tlog.print(getColSep() + \"action\");\n\t\t\tif (showProbs)\n\t\t\t\tlog.print(getColSep() + \"probability\");\n\t\t}\n\t\tlog.print(getColSep() + \"step\");\n\t\tif (contTime && showTimeCumul)\n\t\t\tlog.print(getColSep() + \"time\");\n\t\tif (varsToShow == null)\n\t\t\tfor (j = 0; j < numVars; j++)\n\t\t\t\tlog.print(getColSep() + modelInfo.getVarName(j));\n\t\telse\n\t\t\tfor (int v : varsToShow)\n\t\t\t\tlog.print(getColSep() + modelInfo.getVarName(v));\n\t\tif (getShowRewards()) {\n\t\t\tif (numRewardStructs == 1) {\n\t\t\t\tlog.print(getColSep() + \"state_reward\");\n\t\t\t\tif (!getShowSnapshots())\n\t\t\t\t\tlog.print(getColSep() + \"transition_reward\");\n\t\t\t} else {\n\t\t\t\tfor (j = 0; j < numRewardStructs; j++) {\n\t\t\t\t\tlog.print(getColSep() + \"state_reward\" + (j + 1));\n\t\t\t\t\tif (!getShowSnapshots())\n\t\t\t\t\t\tlog.print(getColSep() + \"transition_reward\" + (j + 1));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (!getShowSnapshots()) {\n\t\t\tif (contTime && showTimeSpent)\n\t\t\t\tlog.print(getColSep() + \"time_in_state\");\n\t\t}\n\t\tlog.println();\n\n\t\t// Display initial step\n\t\tchanged = true;\n\t\tfirstCol = true;\n\t\tif (!getShowSnapshots()) {\n\t\t\tlog.print(getColSep() + \"-\");\n\t\t\tif (showProbs)\n\t\t\t\tlog.print(getColSep() + \"-\");\n\t\t}\n\t\tlog.print(getColSep() + \"0\");\n\t\tif (contTime && showTimeCumul)\n\t\t\tlog.print(getColSep() + \"0.0\");\n\t\tlastState = new State(initialState.varValues.length);\n\t\tdisplayState(initialState);\n\t\tif (getShowRewards()) {\n\t\t\tlastStateRewards = explicit.Utils.cloneDoubleArray(initialStateRewards);\n\t\t}\n\t\tif (getShowSnapshots()) {\n\t\t\tlog.println();\n\t\t}\n\t}\n\n\t@Override\n\tpublic void displayStep(double timeSpent, double timeCumul, String actionString, Object probability, double[] transitionRewards, long newStateIndex, State newState, double[] newStateRewards)\n\t{\n\t\tif (!showChangesOnly || changed) {\n\t\t\t// display rewards for last state\n\t\t\tif (getShowRewards()) {\n\t\t\t\tfor (int j = 0; j < numRewardStructs; j++) {\n\t\t\t\t\tlog.print(getColSep() + lastStateRewards[j]);\n\t\t\t\t\tlog.print(getColSep() + transitionRewards[j]);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// display time spent in state\n\t\t\tif (contTime && showTimeSpent)\n\t\t\t\tlog.print(getColSep() + timeSpent);\n\t\t\tlog.println();\n\t\t}\n\n\t\t// if required, check whether the info to be displayed changed\n\t\tif (showChangesOnly) {\n\t\t\tchanged = stateChanged(lastState, newState) || rewardsChanged(lastStateRewards, newStateRewards);\n\t\t\tif (!changed)\n\t\t\t\treturn;\n\t\t}\n\n\t\tfirstCol = true;\n\n\t\t// display action\n\t\tlog.print(getColSep() + actionString);\n\t\t// display probability/rate\n\t\tif (showProbs)\n\t\t\tlog.print(getColSep() + probability);\n\t\t// display state index\n\t\tlog.print(getColSep() + newStateIndex);\n\t\t// display cumulative time\n\t\tif (contTime && showTimeCumul)\n\t\t\tlog.print(getColSep() + timeCumul);\n\t\t// display state\n\t\tdisplayState(newState);\n\t\t// store state rewards\n\t\tif (getShowRewards()) {\n\t\t\texplicit.Utils.copyDoubleArray(newStateRewards, lastStateRewards);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void displaySnapshot(double timeCumul, long newStateIndex, State newState, double[] newStateRewards)\n\t{\n\t\tfirstCol = true;\n\n\t\t// display state index\n\t\tlog.print(getColSep() + newStateIndex);\n\t\t// display cumulative time\n\t\tif (contTime && showTimeCumul)\n\t\t\tlog.print(getColSep() + timeCumul);\n\t\t// display state\n\t\tdisplayState(newState);\n\t\t// display state rewards\n\t\tif (getShowRewards()) {\n\t\t\tfor (int j = 0; j < numRewardStructs; j++) {\n\t\t\t\tlog.print(getColSep() + newStateRewards[j]);\n\t\t\t}\n\t\t}\n\t\tlog.println();\n\t}\n\n\tprivate void displayState(State state)\n\t{\n\t\tint j;\n\t\tif (varsToShow == null) {\n\t\t\tfor (j = 0; j < numVars; j++) {\n\t\t\t\tlog.print(getColSep());\n\t\t\t\tlog.print(state.varValues[j]);\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int v : varsToShow) {\n\t\t\t\tlog.print(getColSep());\n\t\t\t\tlog.print(state.varValues[v]);\n\t\t\t}\n\t\t}\n\t\tlastState.copy(state);\n\t}\n\n\tprivate String getColSep()\n\t{\n\t\tif (firstCol) {\n\t\t\tfirstCol = false;\n\t\t\treturn \"\";\n\t\t} else {\n\t\t\treturn colSep;\n\t\t}\n\t}\n\n\tprivate boolean stateChanged(State lastState, State newState)\n\t{\n\t\tif (varsToShow == null) {\n\t\t\tfor (int j = 0; j < numVars; j++) {\n\t\t\t\tif (!newState.varValues[j].equals(lastState.varValues[j])) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int v : varsToShow) {\n\t\t\t\tif (!newState.varValues[v].equals(lastState.varValues[v])) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\tprivate boolean rewardsChanged(double[] lastStateRewards, double[] newStateRewards)\n\t{\n\t\tif (!showRewards)\n\t\t\treturn false;\n\t\tfor (int j = 0; j < numRewardStructs; j++) {\n\t\t\tif (newStateRewards[j] != lastStateRewards[j]) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic void endDisplay()\n\t{\n\t\tif (!getShowSnapshots() && (!showChangesOnly || changed)) {\n\t\t\t// display state rewards for last state\n\t\t\t// (transition rewards unknown because no outgoing transition)\n\t\t\tif (getShowRewards()) {\n\t\t\t\tfor (int j = 0; j < numRewardStructs; j++) {\n\t\t\t\t\tlog.print(getColSep() + lastStateRewards[j]);\n\t\t\t\t\tlog.print(getColSep() + \"?\");\n\t\t\t\t}\n\t\t\t}\n\t\t\t// display (zero) time spent in state\n\t\t\tif (contTime && showTimeSpent)\n\t\t\t\tlog.print(getColSep() + 0.0);\n\t\t\tlog.println();\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void close()\n\t{\n\t\tif (log instanceof PrismFileLog) {\n\t\t\tlog.close();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/RandomNumberGenerator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.util.Date;\n\nimport cern.jet.random.Exponential;\nimport cern.jet.random.Uniform;\nimport cern.jet.random.engine.MersenneTwister;\n\n/**\n * Random number generator for the simulator.\n * Currently, uses the Colt library.\n */\npublic class RandomNumberGenerator\n{\n\tprivate MersenneTwister random;\n\tprivate Uniform uniform;\n\tprivate Exponential exponential;\n\n\t/**\n\t * Create a new random number generator (seeded, by default, with the current time).\n\t */\n\tpublic RandomNumberGenerator()\n\t{\n\t\tthis((int) new Date().getTime());\n\t}\n\n\t/**\n\t * Create a new random number generator, with a specific initial seed.\n\t */\n\tpublic RandomNumberGenerator(int seed)\n\t{\n\t\trandom = new MersenneTwister(seed);\n\t\tuniform = new Uniform(random);\n\t\t// Create exponential generator (rate 1.0 but this is ignored from now on)\n\t\texponential = new Exponential(1.0, random);\n\t}\n\n\t/**\n\t * Pick a (uniformly distributed) random integer in the range [0,...,n-1].\n\t */\n\tpublic int randomUnifInt(int n)\n\t{\n\t\treturn uniform.nextIntFromTo(0, n - 1);\n\t}\n\n\t/**\n\t * Pick a (uniformly distributed) random double in the range (0,1).\n\t */\n\tpublic double randomUnifDouble()\n\t{\n\t\treturn random.nextDouble();\n\t}\n\n\t/**\n\t * Pick a (uniformly distributed) random double in range (0,x).\n\t */\n\tpublic double randomUnifDouble(double x)\n\t{\n\t\treturn x * random.nextDouble();\n\t}\n\n\t/**\n\t * Pick a random double according to exponential distribution with rate x.\n\t */\n\tpublic double randomExpDouble(double x)\n\t{\n\t\treturn exponential.nextDouble(x);\n\t\t//return (-Math.log(random.nextDouble())) / x;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/SimulatorEngine.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.io.File;\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.List;\n\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionFilter;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.LabelList;\nimport parser.ast.PropertiesFile;\nimport parser.type.Type;\nimport prism.ModelGenerator;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLangException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.PrismUtils;\nimport prism.Result;\nimport prism.ResultsCollection;\nimport prism.RewardGenerator;\nimport prism.UndefinedConstants;\nimport simulator.method.SimulationMethod;\nimport simulator.sampler.Sampler;\nimport strat.Strategy;\nimport strat.StrategyGenerator;\nimport userinterface.graph.Graph;\n\n/**\n * A discrete event simulation engine.\n * \n * The SimulatorEngine class provides support for:\n * <UL>\n * <LI> Manual/random generation of paths through a model\n * <LI> Statistical model checking via Monte-Carlo sampling techniques\n * </UL>\n * \n * After creating a SimulatorEngine object, you load a model with the methods:\n * <UL>\n * <LI> {@link #loadModel}\n * </UL>\n * The input to these methods is a model (ModelGenerator),\n * in which all constants have already been defined,\n * and a RewardGenerator for its reward definitions.\n * The latter can be omitted if not needed.\n * \n * You can initialise creation of a path with:\n * <UL>\n * <LI> {@link #createNewPath} if you want to create a path that will be stored in full\n * <LI> {@link #createNewOnTheFlyPath} if you don't need the full path\n * </UL>\n * \n * At this point, you can also load labels and properties into the simulator, whose values\n * will be available during path generation. Use:\n * <UL>\n * <LI> {@link #addLabel}\n * <LI> {@link #addProperty}\n * </UL>\n * \n * To actually initialise the path with an initial state (or to reinitialise later) use:\n * <UL>\n * <LI> {@link #initialisePath}\n * </UL>\n * \n * For statistical model checking, instead of path creation, use:\n * <UL>\n * <LI> {@link #isPropertyOKForSimulation}\n * <LI> {@link #checkPropertyForSimulation}\n * <LI> {@link #modelCheckSingleProperty}\n * <LI> {@link #modelCheckMultipleProperties}\n * <LI> {@link #modelCheckExperiment}\n * </UL>\n */\npublic class SimulatorEngine extends PrismComponent\n{\n\t// The current parsed model + info\n\tprivate ModelGenerator<Double> modelGen;\n\tprivate RewardGenerator<Double> rewardGen;\n\tprivate ModelType modelType;\n\t// Variable info\n\tprivate VarList varList;\n\tprivate int numVars;\n\t// Constant definitions from model file\n\tprivate Values mfConstants;\n\n\t// Loaded strategy\n\tprivate StrategyGenerator<Double> stratGen;\n\t// Whether the strategy should be enforced\n\tprivate boolean stratEnforced;\n\n\t// Labels + properties info\n\tprotected List<Expression> labels;\n\tprivate List<Expression> properties;\n\tprivate List<Sampler> propertySamplers;\n\n\t// Current path info\n\tprotected Path path;\n\tprotected boolean onTheFly;\n\t// Current state (note: this info is duplicated in the path - it is always the same\n\t// as path.getCurrentState(); we maintain it separately for efficiency,\n\t// i.e. to avoid creating new State objects at every step)\n\tprotected State currentState;\n\t\n\t// State for which transition list applies\n\t// (if null, just the default - i.e. the last state in the current path)\n\tprotected State transitionListState;\n\t// Index of step for which transition list applies\n\t// (if -1, just the default - i.e. the last state in the current path)\n\tprotected int transitionListStep;\n\t\n\t// Temporary storage for manipulating states/rewards\n\tprotected double tmpStateRewards[];\n\tprotected double tmpTransitionRewards[];\n\n\t// Random number generator\n\tprivate RandomNumberGenerator rng;\n\n\t/**\n\t * Utility class to store a reference to a transition,\n\t * broken up into the index of its (nondetermnistic) choice {@code i}\n\t * and the index {@code offset} within transitions of the choice.\n\t */\n\tpublic class Ref\n\t{\n\t\tpublic int i;\n\t\tpublic int offset;\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Basic setup + model loading\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Constructor for the simulator engine.\n\t */\n\tpublic SimulatorEngine(PrismComponent parent)\n\t{\n\t\tsuper(parent);\n\t\tmodelGen = null;\n\t\tmodelType = null;\n\t\tvarList = null;\n\t\tnumVars = 0;\n\t\tmfConstants = null;\n\t\tlabels = null;\n\t\tproperties = null;\n\t\tpropertySamplers = null;\n\t\tpath = null;\n\t\tonTheFly = true;\n\t\tcurrentState = null;\n\t\ttransitionListState = null;\n\t\ttransitionListStep = -1;\n\t\ttmpStateRewards = null;\n\t\ttmpTransitionRewards = null;\n\t\trng = new RandomNumberGenerator();\n\t}\n\n\t/**\n\t * Re-initialise the random number generator using a specified seed.\n\t */\n\tpublic void setRandomNumberGeneratorSeed(int seed)\n\t{\n\t\trng = new RandomNumberGenerator(seed);\n\t}\n\n\t/**\n\t * Loads a new model (and its rewards) into the simulator.\n\t * Note: All constants in the model must have already been defined.\n\t * @param modelGen The model generator for simulation\n\t * @param rewardGen Reward generator for simulation (null if not needed)\n\t */\n\tpublic void loadModel(ModelGenerator<Double> modelGen, RewardGenerator<Double> rewardGen) throws PrismException\n\t{\n\t\t// Create an empty RewardGenerator if missing\n\t\tif (rewardGen == null) {\n\t\t\trewardGen = new RewardGenerator<Double>() {} ;\n\t\t}\n\t\t\n\t\t// Store model, some info and constants\n\t\tthis.modelGen = modelGen;\n\t\tthis.rewardGen = rewardGen;\n\t\tmodelType = modelGen.getModelType();\n\t\tmfConstants = modelGen.getConstantValues();\n\n\t\t// Get variable list (symbol table) for model \n\t\tvarList = modelGen.createVarList();\n\t\tnumVars = varList.getNumVars();\n\t\t\n\t\t// Clear storage for strategy\n\t\tstratGen = null;\n\n\t\t// Initialise storage (should be re-done for each new path etc. but doesn't hurt)\n\t\tinitialise();\n\t}\n\n\t/**\n\t * Loads a new model (without any rewards) into the simulator.\n\t * Note: All constants in the model must have already been defined.\n\t * Typically, {@link #loadModel(ModelGenerator, RewardGenerator) is used.\n\t * @param modelGen The model generator for simulation\n\t */\n\tpublic void loadModel(ModelGenerator<Double> modelGen) throws PrismException\n\t{\n\t\tloadModel(modelGen, null);\n\t}\n\t\n\t/**\n\t * Initialise: Set up (or reset) variables for simulation.\n\t */\n\tprivate void initialise() throws PrismException\n\t{\n\t\t// Create state/transition/rewards storage\n\t\tcurrentState = new State(numVars);\n\t\ttmpStateRewards = new double[rewardGen.getNumRewardStructs()];\n\t\ttmpTransitionRewards = new double[rewardGen.getNumRewardStructs()];\n\n\t\t// Create storage for labels/properties\n\t\tlabels = new ArrayList<Expression>();\n\t\tproperties = new ArrayList<Expression>();\n\t\tpropertySamplers = new ArrayList<Sampler>();\n\t}\n\n\t/**\n\t * Get access to the currently loaded model\n\t */\n\tpublic ModelGenerator<Double> getModel()\n\t{\n\t\treturn modelGen;\n\t}\n\t\n\t/**\n\t * Get access to the currently loaded reward generator\n\t */\n\tpublic RewardGenerator<Double> getRewardGenerator()\n\t{\n\t\treturn rewardGen;\n\t}\n\t\n\t// ------------------------------------------------------------------------------\n\t// Attaching strategies\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Load a strategy for the currently loaded model into the simulator.\n\t * This will be enforced (during automated exploration or path generation)\n\t * by default; call {@code setStrategyEnforced(false)} to disable.\n\t */\n\tpublic void loadStrategy(StrategyGenerator<Double> stratGen)\n\t{\n\t\tthis.stratGen = stratGen;\n\t\tsetStrategyEnforced(true);\n\t}\n\n\t/**\n\t * Set whether the currently loaded strategy (if present)\n\t * is enforced during automated exploration or path generation.\n\t */\n\tpublic void setStrategyEnforced(boolean stratEnforced)\n\t{\n\t\tthis.stratEnforced = stratEnforced;\n\t}\n\n\t/**\n\t * Whether or not there is a currently loaded strategy available.\n\t */\n\tpublic boolean hasStrategyInfo()\n\t{\n\t\treturn stratGen != null;\n\t}\n\n\t/**\n\t * Get the strategy currently loaded into the simulator, if present.\n\t * Returns null if none loaded.\n\t */\n\tpublic StrategyGenerator<Double> getStrategy()\n\t{\n\t\treturn stratGen;\n\t}\n\n\t/**\n\t * Whether or not the currently loaded strategy (if any)\n\t * is being enforced during automated exploration or path generation.\n\t */\n\tpublic boolean isStrategyEnforced()\n\t{\n\t\treturn stratEnforced;\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Path creation and modification\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Create a new path for the current model.\n\t */\n\tpublic void createNewPath() throws PrismException\n\t{\n\t\t// Reset simulation variables\n\t\tinitialise();\n\t\t// Create empty (full) path object associated with this model\n\t\tpath = new PathFull(modelGen, rewardGen);\n\t\tonTheFly = false;\n\t}\n\n\t/**\n\t * Create a new on-the-fly path for the current model.\n\t */\n\tpublic void createNewOnTheFlyPath() throws PrismException\n\t{\n\t\t// Reset simulation variables\n\t\tinitialise();\n\t\t// Create empty (on-the-fly_ path object associated with this model\n\t\tpath = new PathOnTheFly(modelGen, rewardGen);\n\t\tonTheFly = true;\n\t}\n\n\t/**\n\t * Initialise (or re-initialise) the simulation path, starting with a specific (or random) initial state.\n\t * @param initialState Initial state (if null, use default, selecting randomly if needed)\n\t */\n\tpublic void initialisePath(State initialState) throws PrismException\n\t{\n\t\t// Store passed in state as current state\n\t\tif (initialState != null) {\n\t\t\tcurrentState.copy(initialState);\n\t\t}\n\t\t// Or pick default/random one\n\t\telse {\n\t\t\tif (modelGen.hasSingleInitialState()) {\n\t\t\t\tcurrentState.copy(modelGen.getInitialState());\n\t\t\t} else {\n\t\t\t\tthrow new PrismNotSupportedException(\"Random choice of multiple initial states not yet supported\");\n\t\t\t}\n\t\t}\n\t\t// Get initial observation\n\t\tState currentObs = modelGen.getObservation(currentState);\n\t\t// Get initial state reward\n\t\tcalculateStateRewards(currentState, tmpStateRewards);\n\t\t// Initialise stored path\n\t\tpath.initialise(currentState, currentObs, tmpStateRewards);\n\t\t// Initialise the strategy (if loaded)\n\t\tinitialiseStrategy();\n\t\t// Explore initial state in model generator\n\t\tcomputeTransitionsForCurrentState();\n\t\t// Reset and then update samplers for any loaded properties\n\t\tresetSamplers();\n\t\tupdateSamplers();\n\t}\n\n\t/**\n\t * Execute a transition from the current transition list, specified by its index\n\t * within the (whole) list. If this is a continuous-time model, the time to be spent\n\t * in the state before leaving is picked randomly.\n\t */\n\tpublic void manualTransition(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\tif (modelType.continuousTime()) {\n\t\t\tdouble r = modelGen.getProbabilitySum();\n\t\t\texecuteTimedTransition(i, offset, rng.randomExpDouble(r), index);\n\t\t} else {\n\t\t\texecuteTransition(i, offset, index);\n\t\t}\n\t}\n\n\t/**\n\t * Execute a transition from the current transition list, specified by its index\n\t * within the (whole) list. In addition, specify the amount of time to be spent in\n\t * the current state before this transition occurs.\n\t * [continuous-time models only]\n\t */\n\tpublic void manualTransition(int index, double time) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\texecuteTimedTransition(i, offset, time, index);\n\t}\n\n\t/**\n\t * Select, at random, a transition from the current transition list and execute it.\n\t * For continuous-time models, the time to be spent in the state before leaving is also picked randomly.\n\t * If there is currently a deadlock, no transition is taken and the function returns false.\n\t * Otherwise, the function returns true indicating that a transition was successfully taken. \n\t */\n\tpublic boolean automaticTransition() throws PrismException\n\t{\n\n\t\t// Check for deadlock; if so, stop and return false\n\t\tif (modelGen.getNumChoices() == 0)\n\t\t\treturn false;\n\t\t//throw new PrismException(\"Deadlock found at state \" + path.getCurrentState().toString(modelGen));\n\n\t\tRef ref;\n\t\tdouble d, r;\n\t\tint i, j;\n\t\tswitch (modelType) {\n\t\tcase DTMC:\n\t\t\t// Pick a random number to determine choice/transition\n\t\t\td = rng.randomUnifDouble();\n\t\t\tref = new Ref();\n\t\t\tgetChoiceIndexByProbabilitySum(d, ref);\n\t\t\t// Execute\n\t\t\texecuteTransition(ref.i, ref.offset, -1);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\tcase POMDP:\n\t\t\t// Pick choice (from strategy or randomly) and random transition\n\t\t\ti = getAutomaticChoiceIndex();\n\t\t\td = rng.randomUnifDouble();\n\t\t\tj = getTransitionIndexByProbabilitySum(i, d);\n\t\t\t// Execute\n\t\t\texecuteTransition(i, j, -1);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\t// Get sum of all rates\n\t\t\tr = modelGen.getProbabilitySum();\n\t\t\t// Pick a random number to determine choice/transition\n\t\t\td = rng.randomUnifDouble(r);\n\t\t\tref = new Ref();\n\t\t\tgetChoiceIndexByProbabilitySum(d, ref);\n\t\t\t// Execute\n\t\t\texecuteTimedTransition(ref.i, ref.offset, rng.randomExpDouble(r), -1);\n\t\t\tbreak;\n\t\tcase LTS:\n\t\t\t// Pick choice (from strategy or randomly)\n\t\t\ti = getAutomaticChoiceIndex();\n\t\t\t// Execute\n\t\t\texecuteTransition(i, 0, -1);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Automatic exploration not supported for \" + modelType + \"s\");\n\t\t}\n\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get the index of the choice to be automatically selected in the current state.\n\t * If a strategy is loaded (and to be enforced, and defined for the current state), this will be used.\n\t * If not, a choice is sampled (uniformly) at random.\n\t */\n\tprivate int getAutomaticChoiceIndex() throws PrismException\n\t{\n\t\tint i = -1;\n\t\t// Extract a choice from the strategy, if present\n\t\tif (hasStrategyInfo() && isStrategyEnforced()) {\n\t\t\tObject decision = path.getCurrentStrategyDecision();\n\t\t\tObject act = stratGen.sampleChoiceAction(decision, rng);\n\t\t\tif (act != Strategy.UNDEFINED) {\n\t\t\t\ti = modelGen.getChoiceIndexByAction(act);\n\t\t\t\tif (i == -1) {\n\t\t\t\t\tthrow new PrismException(\"Action \" + act + \" requested by strategy is unavailable\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// If unknown/undefined, sample randomly\n\t\tif (i == -1) {\n\t\t\ti = rng.randomUnifInt(modelGen.getNumChoices());\n\t\t}\n\t\treturn i;\n\t}\n\t\n\t/**\n\t * Get a reference to a transition according to a total probability (or rate) sum, x.\n\t * i.e.the first transition for which the sum of probabilities/rates of that and all prior\n\t * transitions (across all choices) exceeds x.\n\t * @param x Probability (or rate) sum\n\t * @param ref Empty transition reference to store result\n\t */\n\tprivate void getChoiceIndexByProbabilitySum(double x, Ref ref) throws PrismException\n\t{\n\t\tint numChoices = modelGen.getNumChoices();\n\t\tdouble d = 0.0, tot = 0.0;\n\t\tint i = 0;\n\t\t// Add up choice prob/rate sums to find choice\n\t\tfor (i = 0; x >= tot && i < numChoices; i++) {\n\t\t\td = modelGen.getChoiceProbabilitySum(i);\n\t\t\ttot += d;\n\t\t}\n\t\tref.i = i - 1;\n\t\t// Pick transition within choice\n\t\tref.offset = getTransitionIndexByProbabilitySum(i - 1, x - (tot - d));\n\t}\n\n\t/**\n\t * Get the index of a transition (within a choice) according to a probability (or rate) sum, x.\n\t * i.e. the first transition for which the sum of probabilities/rates of that and all prior\n\t * transitions (across all choices) exceeds x.\n\t * @param i Index of the choice\n\t * @param x Probability (or rate) sum\n\t */\n\tprivate int getTransitionIndexByProbabilitySum(int i, double x) throws PrismException\n\t{\n\t\tint numTransitions = modelGen.getNumTransitions(i);\n\t\tif (numTransitions > 1) {\n\t\t\tdouble tot = 0.0;\n\t\t\tint offset = 0;\n\t\t\tfor (offset = 0; x >= tot && offset < numTransitions; offset++) {\n\t\t\t\ttot += modelGen.getTransitionProbability(i, offset);\n\t\t\t}\n\t\t\treturn offset - 1;\n\t\t} else {\n\t\t\treturn 0;\n\t\t}\n\t}\n\n\t/**\n\t * Select, at random, n successive transitions and execute them.\n\t * For continuous-time models, the time to be spent in each state before leaving is also picked randomly.\n\t * If a deadlock is found, the process stops.\n\t * Optionally, if a deterministic loop is detected, the process stops.\n\t * The function returns the number of transitions successfully taken. \n\t */\n\tpublic int automaticTransitions(int n, boolean stopOnLoops) throws PrismException\n\t{\n\t\tint i = 0;\n\t\twhile (i < n && !(stopOnLoops && path.isLooping())) {\n\t\t\tif (!automaticTransition())\n\t\t\t\tbreak;\n\t\t\ti++;\n\t\t}\n\t\treturn i;\n\t}\n\n\t/**\n\t * Randomly select and execute transitions until the specified time delay is first exceeded.\n\t * (Time is measured from the initial execution of this method, not total time.)\n\t * (For discrete-time models, this just results in ceil(time) steps being executed.)\n\t * If a deadlock is found, the process stops.\n\t * The function returns the number of transitions successfully taken. \n\t */\n\tpublic int automaticTransitions(double time, boolean stopOnLoops) throws PrismException\n\t{\n\t\t// For discrete-time models, this just results in ceil(time) steps being executed.\n\t\tif (!modelType.continuousTime()) {\n\t\t\treturn automaticTransitions((int) Math.ceil(time), false);\n\t\t} else {\n\t\t\tint i = 0;\n\t\t\tdouble targetTime = path.getTotalTime() + time;\n\t\t\twhile (path.getTotalTime() < targetTime) {\n\t\t\t\tif (automaticTransition())\n\t\t\t\t\ti++;\n\t\t\t\telse\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\treturn i;\n\t\t}\n\t}\n\n\t/**\n\t * Backtrack to a particular step within the current path.\n\t * Time point should be >=0 and <= the total path size. \n\t * (Not applicable for on-the-fly paths)\n\t * @param step The step to backtrack to.\n\t */\n\tpublic void backtrackTo(int step) throws PrismException\n\t{\n\t\t// Check step is valid\n\t\tif (step < 0) {\n\t\t\tthrow new PrismException(\"Cannot backtrack to a negative step index\");\n\t\t}\n\t\tif (step > path.size()) {\n\t\t\tthrow new PrismException(\"There is no step \" + step + \" to backtrack to\");\n\t\t}\n\t\t// Back track in path\n\t\t((PathFull) path).backtrack(step);\n\t\t// Update current state\n\t\tcurrentState.copy(path.getCurrentState());\n\t\t// Reset the strategy (if loaded)\n\t\tresetStrategy();\n\t\t// Re-explore current state in model generator\n\t\tcomputeTransitionsForCurrentState();\n\t\t// Recompute samplers for any loaded properties\n\t\trecomputeSamplers();\n\t}\n\n\t/**\n\t * Backtrack to a particular (continuous) time point within the current path.\n\t * Time point should be >=0 and <= the total path time. \n\t * (Not applicable for on-the-fly paths)\n\t * @param time The amount of time to backtrack.\n\t */\n\tpublic void backtrackTo(double time) throws PrismException\n\t{\n\t\t// Check step is valid\n\t\tif (time < 0) {\n\t\t\tthrow new PrismException(\"Cannot backtrack to a negative time point\");\n\t\t}\n\t\tif (time > path.getTotalTime()) {\n\t\t\tthrow new PrismException(\"There is no time point \" + time + \" to backtrack to\");\n\t\t}\n\t\tPathFull pathFull = (PathFull) path;\n\t\t// Get length (non-on-the-fly paths will never exceed length Integer.MAX_VALUE) \n\t\tlong nLong = path.size();\n\t\tif (nLong > Integer.MAX_VALUE)\n\t\t\tthrow new PrismException(\"PathFull cannot deal with paths over length \" + Integer.MAX_VALUE);\n\t\tint n = (int) nLong;\n\t\t// Find the index of the step we are in at that point\n\t\t// i.e. the first state whose cumulative time on entering exceeds 'time'\n\t\tint step;\n\t\tfor (step = 0; step <= n && pathFull.getCumulativeTime(step) < time; step++)\n\t\t\t;\n\t\t// Then backtrack to this step\n\t\tbacktrackTo(step);\n\t}\n\n\t/**\n\t * Remove the prefix of the current path up to the given path step.\n\t * Index step should be >=0 and <= the total path size. \n\t * (Not applicable for on-the-fly paths)\n\t * @param step The step before which state will be removed.\n\t */\n\tpublic void removePrecedingStates(int step) throws PrismException\n\t{\n\t\t// Check step is valid\n\t\tif (step < 0) {\n\t\t\tthrow new PrismException(\"Cannot remove states before a negative step index\");\n\t\t}\n\t\tif (step > path.size()) {\n\t\t\tthrow new PrismException(\"There is no step \" + step + \" in the path\");\n\t\t}\n\t\t// Modify path\n\t\t((PathFull) path).removePrecedingStates(step);\n\t\t// (No need to update currentState or re-generate transitions) \n\t\t// Recompute samplers for any loaded properties\n\t\trecomputeSamplers();\n\t}\n\n\t/**\n\t * Compute the transition table for an earlier step in the path.\n\t * (Not applicable for on-the-fly paths)\n\t * If you do this mid-path, don't forget to reset the transition table\n\t * with <code>computeTransitionsForCurrentState</code> because this\n\t * is not kept track of by the simulator.\n\t */\n\tpublic void computeTransitionsForStep(int step) throws PrismException\n\t{\n\t\tcomputeTransitionsForState(((PathFull) path).getState(step));\n\t\ttransitionListStep = step;\n\t}\n\n\t/**\n\t * Re-compute the transition table for the current state.\n\t */\n\tpublic void computeTransitionsForCurrentState() throws PrismException\n\t{\n\t\tcomputeTransitionsForState(path.getCurrentState());\n\t\ttransitionListStep = (int) path.size();\n\t}\n\n\t/**\n\t * Re-compute the transition table for a particular state.\n\t */\n\tprivate void computeTransitionsForState(State state) throws PrismException\n\t{\n\t\tmodelGen.exploreState(state);\n\t\ttransitionListState = state;\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Methods for loading objects from model checking: paths, etc.\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Construct a path through the currently loaded model to match a supplied path,\n\t * specified as a PathFullInfo object. createNewPath() should have already been called.\n\t * @param newPath Path to match\n\t */\n\tpublic void loadPath(PathFullInfo newPath) throws PrismException\n\t{\n\t\tlong numStepsLong = newPath.size();\n\t\tif (numStepsLong > Integer.MAX_VALUE)\n\t\t\tthrow new PrismException(\"PathFull cannot deal with paths over length \" + Integer.MAX_VALUE);\n\t\tint numSteps = (int) numStepsLong;\n\t\t\n\t\tState nextState, state = newPath.getState(0);\n\t\tinitialisePath(state);\n\t\tfor (int i = 0; i < numSteps; i++) {\n\t\t\tnextState = newPath.getState(i + 1);\n\t\t\t// Find matching transition\n\t\t\t// (just look at states for now)\n\t\t\tint numChoices = modelGen.getNumChoices();\n\t\t\tboolean found = false;\n\t\t\tfor (int j = 0; j < numChoices; j++) {\n\t\t\t\tint numTransitions = modelGen.getNumTransitions(j);\n\t\t\t\tfor (int offset = 0; offset < numTransitions; offset++) {\n\t\t\t\t\tif (modelGen.computeTransitionTarget(j, offset).equals(nextState)) {\n\t\t\t\t\t\tfound = true;\n\t\t\t\t\t\tint index = modelGen.getTotalIndexOfTransition(j, offset);\n\t\t\t\t\t\tif (modelType.continuousTime() && newPath.hasTimeInfo())\n\t\t\t\t\t\t\tmanualTransition(index, newPath.getTime(i));\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\tmanualTransition(index);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (found) {\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!found) {\n\t\t\t\tthrow new PrismException(\"Path loading failed at step \" + (i + 1));\n\t\t\t}\n\t\t\tstate = nextState;\n\t\t}\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Methods for adding/querying labels and properties\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Add a label to the simulator, whose value will be computed during path generation.\n\t * The resulting index of the label is returned: this is used for later queries about the property.\n\t * Any constants/formulas etc. appearing in the label must have been defined in the current model.\n\t * If there are additional constants (e.g. from a properties file),\n\t * then use the {@link #addLabel(Expression, PropertiesFile)} method. \n\t */\n\tpublic int addLabel(Expression label) throws PrismLangException\n\t{\n\t\treturn addLabel(label, null);\n\t}\n\n\t/**\n\t * Add a label to the simulator, whose value will be computed during path generation.\n\t * The resulting index of the label is returned: this is used for later queries about the property.\n\t * Any constants/formulas etc. appearing in the label must have been defined in the current model\n\t * or be supplied in the (optional) passed in PropertiesFile.\n\t */\n\tpublic int addLabel(Expression label, PropertiesFile pf) throws PrismLangException\n\t{\n\t\t// Take a copy, get rid of any constants and simplify\n\t\tExpression labelNew = label.deepCopy();\n\t\tlabelNew = (Expression) labelNew.replaceConstants(mfConstants);\n\t\tif (pf != null) {\n\t\t\tlabelNew = (Expression) labelNew.replaceConstants(pf.getConstantValues());\n\t\t}\n\t\tlabelNew = (Expression) labelNew.simplify();\n\t\t// Add to list and return index\n\t\tlabels.add(labelNew);\n\t\treturn labels.size() - 1;\n\t}\n\n\t/**\n\t * Add a (path) property to the simulator, whose value will be computed during path generation.\n\t * The resulting index of the property is returned: this is used for later queries about the property.\n\t * Any constants/formulas etc. appearing in the label must have been defined in the current model.\n\t * If there are additional constants (e.g. from a properties file),\n\t * then use the {@link #addProperty(Expression, PropertiesFile)} method.\n\t * <br><br> \n\t * Really, this should be called after path creation, but before initialisation;\n\t * however if possible the status of the  property will be updated to reflect an existing\n\t * path if this is not done (not possible for on-the-fly paths with steps already added).\n\t */\n\tpublic int addProperty(Expression prop) throws PrismException\n\t{\n\t\treturn addProperty(prop, null);\n\t}\n\n\t/**\n\t * Add a (path) property to the simulator, whose value will be computed during path generation.\n\t * The resulting index of the property is returned: this is used for later queries about the property.\n\t * Any constants/formulas etc. appearing in the property must have been defined in the current model\n\t * or be supplied in the (optional) passed in PropertiesFile.\n\t * In case of error, the property is not added an exception is thrown.\n\t * <br><br> \n\t * Really, this should be called after path creation, but before initialisation;\n\t * however if possible the status of the  property will be updated to reflect an existing\n\t * path if this is not done (not possible for on-the-fly paths with steps already added).\n\t */\n\tpublic int addProperty(Expression prop, PropertiesFile pf) throws PrismException\n\t{\n\t\t// Take a copy\n\t\tExpression propNew = prop.deepCopy();\n\t\t// Combine label lists from model/property file, then expand property refs/labels in property\n\t\t// For now, model labels are only handled if stored in pf.getCombinedLabelList(),\n\t\t// which currently only happens if the model came from a ModulesFile\n\t\tLabelList combinedLabelList = (pf == null) ? null : pf.getCombinedLabelList();\n\t\tpropNew = (Expression) propNew.expandPropRefsAndLabels(pf, combinedLabelList);\n\t\t// Then get rid of any constants and simplify\n\t\tpropNew = (Expression) propNew.replaceConstants(mfConstants);\n\t\tif (pf != null) {\n\t\t\tpropNew = (Expression) propNew.replaceConstants(pf.getConstantValues());\n\t\t}\n\t\tpropNew = (Expression) propNew.simplify();\n\t\t// Create sampler\n\t\tSampler sampler = Sampler.createSampler(propNew, modelGen, rewardGen);\n\t\t// Update lists and return index\n\t\t// (do this right at the end so that lists only get updated if there are no errors)\n\t\tproperties.add(propNew);\n\t\tpropertySamplers.add(sampler);\n\t\t// If the path has already been initialised (and it is possible to),\n\t\t// update the samplers to reflect the existing path\n\t\tif (path != null && path.numStates() > 0) {\n\t\t\t// Non on-the-fly paths: recompute\n\t\t\tif (!onTheFly) {\n\t\t\t\trecomputeSamplers(Collections.singletonList(sampler));\n\t\t\t}\n\t\t\t// On-the-fly path but with just the initial state added\n\t\t\telse if (path.numStates() == 1) {\n\t\t\t\tsampler.update(path, modelGen);\n\t\t\t}\n\t\t\t// Too late\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Too late to add a property to an on-the-fly path\");\n\t\t\t}\n\t\t}\n\t\treturn properties.size() - 1;\n\t}\n\n\t/**\n\t * Get the current value of a previously added label (specified by its index).\n\t */\n\tpublic boolean queryLabel(int index) throws PrismLangException\n\t{\n\t\treturn labels.get(index).evaluateBoolean(path.getCurrentState());\n\t}\n\n\t/**\n\t * Get the value, at the specified path step, of a previously added label (specified by its index).\n\t * (Not applicable for on-the-fly paths)\n\t * @param step The index of the step to check for\n\t */\n\tpublic boolean queryLabel(int index, int step) throws PrismLangException\n\t{\n\t\treturn labels.get(index).evaluateBoolean(((PathFull) path).getState(step));\n\t}\n\n\t/**\n\t * Check whether the current state is an initial state.\n\t */\n\tpublic boolean queryIsInitial() throws PrismException\n\t{\n\t\t// Currently multiple initial states are not supported so this is easy to check\n\t\treturn path.getCurrentState().equals(modelGen.getInitialState());\n\t}\n\n\t/**\n\t * Check whether a particular step in the current path is an initial state.\n\t * @param step The index of the step to check for\n\t * (Not applicable for on-the-fly paths)\n\t */\n\tpublic boolean queryIsInitial(int step) throws PrismException\n\t{\n\t\t// Currently multiple initial states are not supported so this is easy to check\n\t\treturn ((PathFull) path).getState(step).equals(modelGen.getInitialState());\n\t}\n\n\t/**\n\t * Check whether the current state is a deadlock.\n\t */\n\tpublic boolean queryIsDeadlock() throws PrismException\n\t{\n\t\treturn modelGen.isDeadlock();\n\t}\n\n\t/**\n\t * Check whether a particular step in the current path is a deadlock.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step The index of the step to check for\n\t */\n\tpublic boolean queryIsDeadlock(int step) throws PrismException\n\t{\n\t\t// By definition, earlier states in the path cannot be deadlocks\n\t\treturn step == path.size() ? modelGen.getNumChoices() == 0 : false;\n\t}\n\n\t/**\n\t * Check the value for a particular property in the current path.\n\t * If the value is not known yet, the result will be null.\n\t * @param index The index of the property to check\n\t */\n\tpublic Object queryProperty(int index)\n\t{\n\t\tif (index < 0 || index >= propertySamplers.size()) {\n\t\t\tmainLog.printWarning(\"Can't query property \" + index + \".\");\n\t\t\treturn null;\n\t\t}\n\t\tSampler sampler = propertySamplers.get(index);\n\t\treturn sampler.isCurrentValueKnown() ? sampler.getCurrentValue() : null;\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Private methods for path creation and modification\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Utility method for computing state rewards for all reward structs.\n\t */\n\tprivate void calculateStateRewards(State state, double[] stateRewards) throws PrismException\n\t{\n\t\tint numRewardStructs = rewardGen.getNumRewardStructs();\n\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\tif (rewardGen.rewardStructHasStateRewards(r)) {\n\t\t\t\tstateRewards[r] = rewardGen.getStateReward(r, state);\n\t\t\t} else {\n\t\t\t\tstateRewards[r] = 0.0;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Utility method for computing transition rewards for all reward structs.\n\t */\n\tprivate void calculateTransitionRewards(State state, Object action, double[] transitionRewards) throws PrismException\n\t{\n\t\tint numRewardStructs = rewardGen.getNumRewardStructs();\n\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\tif (rewardGen.rewardStructHasTransitionRewards(r)) {\n\t\t\t\ttransitionRewards[r] = rewardGen.getStateActionReward(r, state, action);\n\t\t\t} else {\n\t\t\t\ttransitionRewards[r] = 0.0;\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * Execute a transition from the current transition list and update path (if being stored).\n\t * Transition is specified by index of its choice and offset within it. If known, its index\n\t * (within the whole list) can optionally be specified (since this may be needed for storage\n\t * in the path). If this is -1, it will be computed automatically if needed.\n\t * @param i Index of choice containing transition to execute\n\t * @param offset Index within choice of transition to execute\n\t * @param index (Optionally) index of transition within whole list (-1 if unknown)\n\t */\n\tprivate void executeTransition(int i, int offset, int index) throws PrismException\n\t{\n\t\t// If required (for full paths), calculate transition index\n\t\tif (!onTheFly && index == -1) {\n\t\t\tindex = modelGen.getTotalIndexOfTransition(i, offset);\n\t\t}\n\t\t// Get probability and action for transition\n\t\tObject p = modelGen.getTransitionProbabilityObject(i, offset);\n\t\tObject action = modelGen.getTransitionAction(i, offset);\n\t\tString actionString = modelGen.getTransitionActionDescription(i, offset);\n\t\t// Compute its transition rewards\n\t\tcalculateTransitionRewards(path.getCurrentState(), action, tmpTransitionRewards);\n\t\t// Compute next state\n\t\tcurrentState.copy(modelGen.computeTransitionTarget(i, offset));\n\t\t// Compute observation for new state\n\t\tState currentObs = modelGen.getObservation(currentState);\n\t\t// Compute state rewards for new state\n\t\tcalculateStateRewards(currentState, tmpStateRewards);\n\t\t// Update path\n\t\tpath.addStep(index, action, actionString, p, tmpTransitionRewards, currentState, currentObs, tmpStateRewards, modelGen);\n\t\t// Update strategy (if loaded)\n\t\tupdateStrategy();\n\t\t// Explore new state in model generator\n\t\tcomputeTransitionsForCurrentState();\n\t\t// Update samplers for any loaded properties\n\t\tupdateSamplers();\n\t}\n\n\t/**\n\t * Execute a (timed) transition from the current transition list and update path (if being stored).\n\t * Transition is specified by index of its choice and offset within it. If known, its index\n\t * (within the whole list) can optionally be specified (since this may be needed for storage\n\t * in the path). If this is -1, it will be computed automatically if needed.\n\t * In addition, the amount of time to be spent in the current state before this transition occurs should be specified.\n\t * [continuous-time models only]\n\t * @param i Index of choice containing transition to execute\n\t * @param offset Index within choice of transition to execute\n\t * @param time Time for transition\n\t * @param index (Optionally) index of transition within whole list (-1 if unknown)\n\t */\n\tprivate void executeTimedTransition(int i, int offset, double time, int index) throws PrismException\n\t{\n\t\t// If required (for full paths), calculate transition index\n\t\tif (!onTheFly && index == -1) {\n\t\t\tindex = modelGen.getTotalIndexOfTransition(i, offset);\n\t\t}\n\t\t// Get probability and action for transition\n\t\tObject p = modelGen.getTransitionProbabilityObject(i, offset);\n\t\tObject action = modelGen.getTransitionAction(i, offset);\n\t\tString actionString = modelGen.getTransitionActionDescription(i, offset);\n\t\t// Compute its transition rewards\n\t\tcalculateTransitionRewards(path.getCurrentState(), action, tmpTransitionRewards);\n\t\t// Compute next state\n\t\tcurrentState.copy(modelGen.computeTransitionTarget(i, offset));\n\t\t// Compute observation for new state\n\t\tState currentObs = modelGen.getObservation(currentState);\n\t\t// Compute state rewards for new state\n\t\tcalculateStateRewards(currentState, tmpStateRewards);\n\t\t// Update path\n\t\tpath.addStep(time, index, action, actionString, p, tmpTransitionRewards, currentState, currentObs, tmpStateRewards, modelGen);\n\t\t// Update strategy (if loaded)\n\t\tupdateStrategy();\n\t\t// Explore new state in model generator\n\t\tcomputeTransitionsForCurrentState();\n\t\t// Update samplers for any loaded properties\n\t\tupdateSamplers();\n\t}\n\n\t/**\n\t * Reset samplers for any loaded properties.\n\t */\n\tprivate void resetSamplers() throws PrismLangException\n\t{\n\t\tfor (Sampler sampler : propertySamplers) {\n\t\t\tsampler.reset();\n\t\t}\n\t}\n\n\t/**\n\t * Notify samplers for any loaded properties that a new step has occurred.\n\t */\n\tprivate void updateSamplers() throws PrismException\n\t{\n\t\tfor (Sampler sampler : propertySamplers) {\n\t\t\tsampler.update(path, modelGen);\n\t\t}\n\t}\n\n\t/**\n\t * Recompute the state of samplers for any loaded properties based on the whole current path.\n\t * (Not applicable for on-the-fly paths)\n\t */\n\tprivate void recomputeSamplers() throws PrismException\n\t{\n\t\trecomputeSamplers(propertySamplers);\n\t}\n\n\t/**\n\t * Recompute the state of some property samplers based on the whole current path.\n\t * (Not applicable for on-the-fly paths)\n\t */\n\tprivate void recomputeSamplers(List<Sampler> samplers) throws PrismException\n\t{\n\t\t// Reset samplers\n\t\tfor (Sampler sampler : propertySamplers) {\n\t\t\tsampler.reset();\n\t\t}\n\t\t// Get length (non-on-the-fly paths will never exceed length Integer.MAX_VALUE) \n\t\tlong nLong = path.size();\n\t\tif (nLong > Integer.MAX_VALUE) {\n\t\t\tthrow new PrismLangException(\"PathFull cannot deal with paths over length \" + Integer.MAX_VALUE);\n\t\t}\n\t\tint n = (int) nLong;\n\t\t// Update samplers with prefixes of current path\n\t\tPathFullPrefix prefix = new PathFullPrefix((PathFull) path, 0);\n\t\tfor (int i = 0; i <= n; i++) {\n\t\t\tprefix.setPrefixLength(i);\n\t\t\tfor (Sampler sampler : propertySamplers) {\n\t\t\t\tsampler.update(prefix, null);\n\t\t\t\t// TODO: fix this optimisation \n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Initialise the state of the loaded strategy, if present, based on the current state.\n\t */\n\tprivate void initialiseStrategy()\n\t{\n\t\tif (stratGen != null) {\n\t\t\tstratGen.initialise(getCurrentState());\n\t\t\tint memory = stratGen.getCurrentMemory();\n\t\t\tObject decision = stratGen.getCurrentChoiceAction();\n\t\t\tpath.setStrategyInfoForCurrentState(memory, decision);\n\t\t}\n\t}\n\n\t/**\n\t * Update the state of the loaded strategy, if present, based on the last step that occurred.\n\t */\n\tprivate void updateStrategy()\n\t{\n\t\tif (stratGen != null) {\n\t\t\tstratGen.update(path.getPreviousAction(), getCurrentState());\n\t\t\tint memory = stratGen.getCurrentMemory();\n\t\t\tObject decision = stratGen.getCurrentChoiceAction();\n\t\t\tpath.setStrategyInfoForCurrentState(memory, decision);\n\t\t}\n\t}\n\n\t/**\n\t * Reset the state of the loaded strategy, if present, based on the last step that occurred.\n\t */\n\tprivate void resetStrategy()\n\t{\n\t\tif (stratGen != null) {\n\t\t\tstratGen.reset(getCurrentState(), path.getCurrentStrategyMemory());\n\t\t}\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Queries regarding model\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Returns the number of variables in the current model.\n\t */\n\tpublic int getNumVariables()\n\t{\n\t\treturn numVars;\n\t}\n\n\t/**\n\t * Returns the name of the ith variable in the current model.\n\t * (Returns null if index i is out of range.)\n\t */\n\tpublic String getVariableName(int i)\n\t{\n\t\treturn (i < numVars && i >= 0) ? varList.getName(i) : null;\n\t}\n\n\t/**\n\t * Returns the type of the ith variable in the current model.\n\t * (Returns null if index i is out of range.)\n\t */\n\tpublic Type getVariableType(int i)\n\t{\n\t\treturn (i < numVars && i >= 0) ? varList.getType(i) : null;\n\t}\n\n\t/**\n\t * Returns the index of a variable name, as stored by the simulator for the current model.\n\t * Returns -1 if the action name does not exist. \n\t */\n\tpublic int getIndexOfVar(String name) throws PrismException\n\t{\n\t\treturn varList.getIndex(name);\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Querying of current state and its available choices/transitions\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Get the state for which the simulator is currently supplying information about its transitions. \n\t * Usually, this is the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be this state instead.\n\t */\n\tpublic State getTransitionListState()\n\t{\n\t\treturn transitionListState;\n\t\t\n\t}\n\t\n\t/**\n\t * Returns the current number of available choices.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic int getNumChoices() throws PrismException\n\t{\n\t\treturn modelGen.getNumChoices();\n\t}\n\n\t/**\n\t * Returns the current (total) number of available transitions.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic int getNumTransitions() throws PrismException\n\t{\n\t\treturn modelGen.getNumTransitions();\n\t}\n\n\t/**\n\t * Returns the current number of available transitions in choice i.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic int getNumTransitions(int i) throws PrismException\n\t{\n\t\treturn modelGen.getNumTransitions(i);\n\t}\n\n\t/**\n\t * Get the index of the choice containing a transition of a given index.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic int getChoiceIndexOfTransition(int index) throws PrismException\n\t{\n\t\treturn modelGen.getChoiceIndexOfTransition(index);\n\t}\n\n\t/**\n\t * Get the action label of a transition, specified by its index/offset.\n\t * (null for asynchronous/independent transitions)\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic Object getTransitionAction(int i, int offset) throws PrismException\n\t{\n\t\treturn modelGen.getTransitionAction(i, offset);\n\t}\n\n\t/**\n\t * Get the action label of a transition, specified by its index.\n\t * (null for asynchronous/independent transitions)\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic Object getTransitionAction(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\treturn modelGen.getTransitionAction(i, offset);\n\t}\n\n\t/**\n\t * Get a string representation of the action of a transition, specified by its index/offset.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionActionString(int i, int offset) throws PrismException\n\t{\n\t\treturn modelGen.getTransitionActionString(i, offset);\n\t}\n\n\t/**\n\t * Get a string describing the action of a transition, specified by its index/offset.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionActionDescription(int i, int offset) throws PrismException\n\t{\n\t\treturn modelGen.getTransitionActionDescription(i, offset);\n\t}\n\n\t/**\n\t * Get a string representation of the action of a transition, specified by its index.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionActionString(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\treturn getTransitionActionString(i, offset);\n\t}\n\n\t/**\n\t * Get a string describing the action of a transition, specified by its index.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionActionDescription(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\treturn getTransitionActionDescription(i, offset);\n\t}\n\n\t/**\n\t * Get the probability/rate of a transition within a choice, specified by its index/offset.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic double getTransitionProbability(int i, int offset) throws PrismException\n\t{\n\t\treturn modelGen.getTransitionProbability(i, offset);\n\t}\n\n\t/**\n\t * Get the probability/rate of a transition, specified by its index.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic double getTransitionProbability(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\treturn getTransitionProbability(i, offset);\n\t}\n\n\t/**\n\t * Get a string for the probability/rate of a transition within a choice, specified by its index/offset.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionProbabilityString(int i, int offset) throws PrismException\n\t{\n\t\treturn modelGen.getTransitionProbabilityString(i, offset);\n\t}\n\n\t/**\n\t * Get a string for the probability/rate of a transition, specified by its index.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionProbabilityString(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\treturn getTransitionProbabilityString(i, offset);\n\t}\n\n\t/**\n\t * Get a string describing the update comprising a transition, specified by its index/offset.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionUpdateString(int i, int offset) throws PrismException\n\t{\n\t\treturn modelGen.getTransitionUpdateString(i, offset);\n\t}\n\n\t/**\n\t * Get a string describing the update comprising a transition, specified by its index.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionUpdateString(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\treturn getTransitionUpdateString(i, offset);\n\t}\n\n\t/**\n\t * Get a verbose string describing the update comprising a transition, specified by its index/offset.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionUpdateStringFull(int i, int offset) throws PrismException\n\t{\n\t\treturn modelGen.getTransitionUpdateStringFull(i, offset);\n\t}\n\n\t/**\n\t * Get a verbose string describing the update comprising a transition, specified by its index.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getTransitionUpdateStringFull(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\treturn getTransitionUpdateStringFull(i, offset);\n\t}\n\n\t/**\n\t * Get the target (as a new State object) of a transition within a choice, specified by its index/offset.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic State computeTransitionTarget(int i, int offset) throws PrismException\n\t{\n\t\treturn modelGen.computeTransitionTarget(i, offset);\n\t}\n\n\t/**\n\t * Get the target of a transition (as a new State object), specified by its index.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic State computeTransitionTarget(int index) throws PrismException\n\t{\n\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\tint offset = modelGen.getChoiceOffsetOfTransition(index);\n\t\treturn computeTransitionTarget(i, offset);\n\t}\n\n\t/**\n\t * Is a transition, specified by its index, enabled by the current strategy (if any).\n\t * This will return true if no strategy is loaded (i.e., if {@link #hasStrategyInfo()} returns false.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic boolean isTransitionEnabledByStrategy(int index) throws PrismException\n\t{\n\t\t// No strategy - assume enabled\n\t\tif (!hasStrategyInfo()) {\n\t\t\treturn true;\n\t\t}\n\t\tObject decision = transitionListStep == path.size() ? path.getCurrentStrategyDecision() : ((PathFull) path).getStrategyDecision(transitionListStep);\n\t\t// Undefined by strategy - assume enabled\n\t\tif (decision == Strategy.UNDEFINED) {\n\t\t\treturn true;\n\t\t}\n\t\t// Otherwise interpret decision stored from strategy\n\t\telse {\n\t\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\t\tObject act = modelGen.getChoiceAction(i);\n\t\t\treturn stratGen.isActionChosen(decision, act);\n\t\t}\n\t}\n\n\t/**\n\t * Get a string describing the decision to be made by the current strategy (if any)\n\t * with respect to a transition, specified by its index.\n\t * This will return \"\" if no strategy is loaded (i.e., if {@link #hasStrategyInfo()} returns false.\n\t * and return \"?\" if the choice is undefined by the strategy.\n\t * Usually, this is for the current (final) state of the path but, if you called {@link #computeTransitionsForStep(int step)}, it will be for this state instead.\n\t */\n\tpublic String getStrategyDecisionString(int index) throws PrismException\n\t{\n\t\t// No strategy\n\t\tif (!hasStrategyInfo()) {\n\t\t\treturn \"\";\n\t\t}\n\t\tObject decision = transitionListStep == path.size() ? path.getCurrentStrategyDecision() : ((PathFull) path).getStrategyDecision(transitionListStep);\n\t\t// Undefined by strategy\n\t\tif (decision == Strategy.UNDEFINED) {\n\t\t\treturn \"?\";\n\t\t}\n\t\telse {\n\t\t\t// Otherwise interpret decision stored from strategy\n\t\t\tint i = modelGen.getChoiceIndexOfTransition(index);\n\t\t\tObject act = modelGen.getChoiceAction(i);\n\t\t\t// Randomised strategy: show probability\n\t\t\tif (stratGen.isRandomised()) {\n\t\t\t\treturn stratGen.getChoiceActionProbability(decision, act) + \"\";\n\t\t\t}\n\t\t\t// Deterministic strategy: mark selected choice with an arrow (\"->\")\n\t\t\telse {\n\t\t\t\treturn stratGen.isActionChosen(decision, act) ? \"->\" : \"\";\n\t\t\t}\n\t\t}\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Querying of current path (full or on-the-fly)\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Get access to the {@code Path} object storing the current path.\n\t * This object is only valid until the next time {@link #createNewPath} is called. \n\t */\n\tpublic Path getPath()\n\t{\n\t\treturn (Path) path;\n\t}\n\n\t/**\n\t * Get the size of the current path (number of steps; or number of states - 1).\n\t */\n\tpublic long getPathSize()\n\t{\n\t\treturn path.size();\n\t}\n\n\t/**\n\t * Returns the current state being explored by the simulator.\n\t */\n\tpublic State getCurrentState()\n\t{\n\t\treturn path.getCurrentState();\n\t}\n\n\t/**\n\t * Returns the previous state of the current path in the simulator.\n\t */\n\tpublic State getPreviousState()\n\t{\n\t\treturn path.getPreviousState();\n\t}\n\n\t/**\n\t * Get the total time elapsed so far (where zero time has been spent in the current (final) state).\n\t * For discrete-time models, this is just the number of steps (but returned as a double).\n\t */\n\tpublic double getTotalTimeForPath()\n\t{\n\t\treturn path.getTotalTime();\n\t}\n\n\t/**\n\t * Get the total reward accumulated so far\n\t * (includes reward for previous transition but no state reward for current (final) state).\n\t * @param rsi Reward structure index\n\t */\n\tpublic double getTotalCumulativeRewardForPath(int rsi)\n\t{\n\t\treturn path.getTotalCumulativeReward(rsi);\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Querying of current path (full paths only)\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Get access to the {@code PathFull} object storing the current path.\n\t * (Not applicable for on-the-fly paths)\n\t * This object is only valid until the next time {@link #createNewPath} is called. \n\t */\n\tpublic PathFull getPathFull()\n\t{\n\t\treturn (PathFull) path;\n\t}\n\n\t/**\n\t * Get the value of a variable at a given step of the path.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t * @param varIndex The index of the variable to look up\n\t */\n\tpublic Object getVariableValueOfPathStep(int step, int varIndex)\n\t{\n\t\treturn ((PathFull) path).getState(step).varValues[varIndex];\n\t}\n\n\t/**\n\t * Get the state at a given step of the path.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic State getStateOfPathStep(int step)\n\t{\n\t\treturn ((PathFull) path).getState(step);\n\t}\n\n\t/**\n\t * Get the observation at a given step of the path.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic State getObservationOfPathStep(int step)\n\t{\n\t\treturn ((PathFull) path).getObservation(step);\n\t}\n\n\t/**\n\t * Get a state reward for the state at a given step of the path.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t * @param rsi Reward structure index\n\t */\n\tpublic double getStateRewardOfPathStep(int step, int rsi)\n\t{\n\t\treturn ((PathFull) path).getStateReward(step, rsi);\n\t}\n\n\t/**\n\t * Get the total time spent up until entering a given step of the path.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic double getCumulativeTimeUpToPathStep(int step)\n\t{\n\t\treturn ((PathFull) path).getCumulativeTime(step);\n\t}\n\n\t/**\n\t * Get the total (state and transition) reward accumulated up until entering a given step of the path.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t * @param rsi Reward structure index\n\t */\n\tpublic double getCumulativeRewardUpToPathStep(int step, int rsi)\n\t{\n\t\treturn ((PathFull) path).getCumulativeReward(step, rsi);\n\t}\n\n\t/**\n\t * Get the time spent in a state at a given step of the path.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic double getTimeSpentInPathStep(int step)\n\t{\n\t\treturn ((PathFull) path).getTime(step);\n\t}\n\n\t/**\n\t * Get the index of the choice taken for a given step.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic int getChoiceOfPathStep(int step)\n\t{\n\t\treturn ((PathFull) path).getChoice(step);\n\t}\n\n\t/**\n\t * Get the action taken in a given step.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic Object getActionOfPathStep(int step)\n\t{\n\t\treturn ((PathFull) path).getAction(step);\n\t}\n\n\t/**\n\t * Get a string describing the action taken in a given step.\n\t * (Not applicable for on-the-fly paths)\n\t * @param step Step index (0 = initial state/step of path)\n\t */\n\tpublic String getActionStringOfPathStep(int step)\n\t{\n\t\treturn ((PathFull) path).getActionString(step);\n\t}\n\n\t/**\n\t * Get a transition reward associated with a given step.\n\t * @param step Step index (0 = initial state/step of path)\n\t * @param rsi Reward structure index\n\t */\n\tpublic double getTransitionRewardOfPathStep(int step, int rsi)\n\t{\n\t\treturn ((PathFull) path).getTransitionReward(step, rsi);\n\t}\n\n\t/**\n\t * Check whether the current path is in a deterministic loop.\n\t */\n\tpublic boolean isPathLooping()\n\t{\n\t\treturn path.isLooping();\n\t}\n\n\t/**\n\t * Get at which step a deterministic loop (if present) starts.\n\t */\n\tpublic long loopStart()\n\t{\n\t\treturn path.loopStart();\n\t}\n\n\t/**\n\t * Get at which step a deterministic loop (if present) ends.\n\t */\n\tpublic long loopEnd()\n\t{\n\t\treturn path.loopEnd();\n\t}\n\n\t/**\n\t * Export the current path to a file in a simple space separated format.\n\t * (Not applicable for on-the-fly paths)\n\t * @param file File to which the path should be exported to (mainLog if null).\n\t */\n\tpublic void exportPath(File file) throws PrismException\n\t{\n\t\texportPath(file, false);\n\t}\n\n\t/**\n\t * Export the current path to a file in a simple space separated format.\n\t * (Not applicable for on-the-fly paths)\n\t * @param file File to which the path should be exported to (mainLog if null).\n\t * @param showRewards Export reward information with the path\n\t */\n\tpublic void exportPath(File file, boolean showRewards) throws PrismException\n\t{\n\t\texportPath(file, false, showRewards, \" \", null);\n\t}\n\n\t/**\n\t * Export the current path to a file.\n\t * (Not applicable for on-the-fly paths)\n\t * @param file File to which the path should be exported to (mainLog if null).\n\t * @param timeCumul Show time in cumulative form?\n\t * @param colSep String used to separate columns in display\n\t * @param vars Restrict printing to these variables (indices) and steps which change them (ignore if null)\n\t */\n\tpublic void exportPath(File file, boolean timeCumul, String colSep, ArrayList<Integer> vars) throws PrismException\n\t{\n\t\texportPath(file, timeCumul, false, colSep, vars);\n\t}\n\n\t/**\n\t * Export the current path to a file.\n\t * (Not applicable for on-the-fly paths)\n\t * @param file File to which the path should be exported to (mainLog if null).\n\t * @param timeCumul Show time in cumulative form?\n\t * @param showRewards Export reward information with the path\n\t * @param colSep String used to separate columns in display\n\t * @param vars Restrict printing to these variables (indices) and steps which change them (ignore if null)\n\t */\n\tpublic void exportPath(File file, boolean timeCumul, boolean showRewards, String colSep, ArrayList<Integer> vars) throws PrismException\n\t{\n\t\tif (path == null) {\n\t\t\tthrow new PrismException(\"There is no path to export\");\n\t\t}\n\t\ttry (PrismLog log = getPrismLogForFile(file)) {\n\t\t\tmainLog.println(\"\\nExporting path \" + getDestinationStringForFile(file));\n\t\t\t((PathFull) path).exportToLog(log, timeCumul, showRewards, colSep, vars);\n\t\t}\n\t}\n\n\t/**\n\t * Plot the current path on a Graph.\n\t * @param graphModel Graph on which to plot path\n\t */\n\tpublic void plotPath(Graph graphModel) throws PrismException\n\t{\n\t\t((PathFull) path).plotOnGraph(graphModel);\n\t}\n\n\t// ------------------------------------------------------------------------------\n\t// Model checking (statistical/approximate)\n\t// ------------------------------------------------------------------------------\n\n\t/**\n\t * Check whether a property is suitable for statistical/approximate model checking using the simulator.\n\t */\n\tpublic boolean isPropertyOKForSimulation(Expression expr)\n\t{\n\t\treturn isPropertyOKForSimulationString(expr) == null;\n\t}\n\n\t/**\n\t * Check whether a property is suitable for statistical/approximate model checking using the simulator.\n\t * If not, an explanatory error message is thrown as an exception.\n\t */\n\tpublic void checkPropertyForSimulation(Expression expr) throws PrismException\n\t{\n\t\tString errMsg = isPropertyOKForSimulationString(expr);\n\t\tif (errMsg != null)\n\t\t\tthrow new PrismNotSupportedException(errMsg);\n\t}\n\n\t/**\n\t * Check whether a property is suitable for statistical/approximate model checking using the simulator.\n\t * If yes, return null; if not, return an explanatory error message.\n\t */\n\tprivate String isPropertyOKForSimulationString(Expression expr)\n\t{\n\t\t// Simulator can only be applied to P or R properties (without filters)\n\t\tif (!(expr instanceof ExpressionProb || expr instanceof ExpressionReward)) {\n\t\t\tif (expr instanceof ExpressionFilter) {\n\t\t\t\tif (((ExpressionFilter) expr).getOperand() instanceof ExpressionProb || ((ExpressionFilter) expr).getOperand() instanceof ExpressionReward)\n\t\t\t\t\treturn \"Simulator cannot handle P or R properties with filters\";\n\t\t\t}\n\t\t\treturn \"Simulator can only handle P or R properties\";\n\t\t}\n\t\t// Check that there are no nested probabilistic operators\n\t\ttry {\n\t\t\tif (expr.computeProbNesting() > 1) {\n\t\t\t\treturn \"Simulator cannot handle nested P, R or S operators\";\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\treturn \"Simulator cannot handle this property: \" + e.getMessage();\n\t\t}\n\t\t// Simulator cannot handle cumulative reward properties without a time bound\n\t\tif (expr instanceof ExpressionReward) {\n\t\t\tExpression exprTemp = ((ExpressionReward) expr).getExpression();\n\t\t\tif (exprTemp instanceof ExpressionTemporal) {\n\t\t\t\tif (((ExpressionTemporal) exprTemp).getOperator() == ExpressionTemporal.R_C) {\n\t\t\t\t\tif (((ExpressionTemporal) exprTemp).getUpperBound() == null) {\n\t\t\t\t\t\treturn \"Simulator cannot handle cumulative reward properties without time bounds\";\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// No errors\n\t\treturn null;\n\t}\n\n\t/**\n\t * Perform statistical/approximate model checking of a property on the current model, using the simulator.\n\t * Sampling starts from the initial state provided or, if null, the default\n\t * initial state is used, selecting randomly (each time) if there are more than one.\n\t * Returns a Result object, except in case of error, where an Exception is thrown.\n\t * Note: All constants in the model/property files must have already been defined.\n\t * @param propertiesFile Properties file containing property to check, constants defined\n\t * @param expr The property to check\n\t * @param initialState Initial state (if null, is selected randomly)\n\t * @param maxPathLength The maximum path length for sampling\n\t * @param simMethod Object specifying details of method to use for simulation\n\t */\n\tpublic Result modelCheckSingleProperty(PropertiesFile propertiesFile, Expression expr, State initialState, long maxPathLength,\n\t\t\tSimulationMethod simMethod) throws PrismException\n\t{\n\t\tArrayList<Expression> exprs;\n\t\tResult res[];\n\n\t\t// Just do this via the 'multiple properties' method\n\t\texprs = new ArrayList<Expression>();\n\t\texprs.add(expr);\n\t\tres = modelCheckMultipleProperties(propertiesFile, exprs, initialState, maxPathLength, simMethod);\n\n\t\tif (res[0].getResult() instanceof PrismException)\n\t\t\tthrow (PrismException) res[0].getResult();\n\t\telse\n\t\t\treturn res[0];\n\t}\n\n\t/**\n\t * Perform statistical/approximate model checking of properties on the current model, using the simulator.\n\t * Sampling starts from the initial state provided or, if null, the default\n\t * initial state is used, selecting randomly (each time) if there are more than one.\n\t * Returns an array of results, some of which may contain Exception objects if there were errors.\n\t * In the case of an error which affects all properties, an exception is thrown.\n\t * Note: All constants in the model/property files must have already been defined.\n\t * @param propertiesFile Properties file containing property to check, constants defined\n\t * @param exprs The properties to check\n\t * @param initialState Initial state (if null, is selected randomly)\n\t * @param maxPathLength The maximum path length for sampling\n\t * @param simMethod Object specifying details of method to use for simulation\n\t */\n\tpublic Result[] modelCheckMultipleProperties(PropertiesFile propertiesFile, List<Expression> exprs, State initialState,\n\t\t\tlong maxPathLength, SimulationMethod simMethod) throws PrismException\n\t{\n\t\t// Create path to be used\n\t\tcreateNewOnTheFlyPath();\n\n\t\t// Make sure any missing parameters that can be computed before simulation\n\t\t// are computed now (sometimes this has been done already, e.g. for GUI display).\n\t\tsimMethod.computeMissingParameterBeforeSim();\n\n\t\t// Print details to log\n\t\tmainLog.println(\"\\nSimulation method: \" + simMethod.getName() + \" (\" + simMethod.getFullName() + \")\");\n\t\tmainLog.println(\"Simulation method parameters: \" + simMethod.getParametersString());\n\t\tmainLog.println(\"Simulation parameters: max path length=\" + maxPathLength);\n\n\t\t// Add the properties to the simulator (after a check that they are valid)\n\t\tResult[] results = new Result[exprs.size()];\n\t\tint[] indices = new int[exprs.size()];\n\t\tint validPropsCount = 0;\n\t\tfor (int i = 0; i < exprs.size(); i++) {\n\t\t\ttry {\n\t\t\t\tcheckPropertyForSimulation(exprs.get(i));\n\t\t\t\tindices[i] = addProperty(exprs.get(i), propertiesFile);\n\t\t\t\tvalidPropsCount++;\n\t\t\t\t// Attach a SimulationMethod object to each property's sampler\n\t\t\t\tSimulationMethod simMethodNew = simMethod.clone();\n\t\t\t\tpropertySamplers.get(indices[i]).setSimulationMethod(simMethodNew);\n\t\t\t\t// Pass property details to SimuationMethod\n\t\t\t\t// (note that we use the copy stored in properties, which has been processed)\n\t\t\t\ttry {\n\t\t\t\t\tsimMethodNew.setExpression(properties.get(indices[i]));\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t// In case of error, also need to remove property/sampler from list\n\t\t\t\t\tproperties.remove(indices[i]);\n\t\t\t\t\tpropertySamplers.remove(indices[i]);\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\tresults[i] = new Result(e);\n\t\t\t\tindices[i] = -1;\n\t\t\t}\n\t\t}\n\n\t\t// As long as there are at least some valid props, do sampling\n\t\tif (validPropsCount > 0) {\n\t\t\tdoSampling(initialState, maxPathLength);\n\t\t}\n\n\t\t// Process the results\n\t\tfor (int i = 0; i < results.length; i++) {\n\t\t\t// If there was no earlier error, extract result etc.\n\t\t\tif (indices[i] != -1) {\n\t\t\t\tSampler sampler = propertySamplers.get(indices[i]);\n\t\t\t\tSimulationMethod sm = sampler.getSimulationMethod();\n\t\t\t\t// Compute/print any missing parameters that need to be done after simulation\n\t\t\t\tsm.computeMissingParameterAfterSim();\n\t\t\t\t// Extract result from SimulationMethod and store\n\t\t\t\ttry {\n\t\t\t\t\tresults[i] = new Result(sm.getResult(sampler));\n\t\t\t\t\tresults[i].setAccuracy(sampler.getSimulationMethod().getResultAccuracy(sampler));\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\tresults[i] = new Result(e);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Warning for nondeterministic models\n\t\tif (results.length > 0) {\n\t\t\tModelType currentModelType = modelGen.getModelType();\n\t\t\tif (currentModelType.nondeterministic() && currentModelType.removeNondeterminism() != currentModelType) {\n\t\t\t\tmainLog.println(\"Warning: Nondeterminism in \" + currentModelType.name() + \" was resolved uniformly\");\n\t\t\t}\n\t\t}\n\n\t\t\n\t\t// Display results to log\n\t\tif (results.length == 1) {\n\t\t\tif (!(results[0].getResult() instanceof PrismException))\n\t\t\t\tmainLog.println(\"\\nResult: \" + results[0].getResultAndAccuracy());\n\t\t} else {\n\t\t\tmainLog.println(\"\\nResults:\");\n\t\t\tfor (int i = 0; i < results.length; i++)\n\t\t\t\tmainLog.println(exprs.get(i) + \" : \" + results[i].getResultAndAccuracy());\n\t\t}\n\t\t\n\t\treturn results;\n\t}\n\n\t/**\n\t * Perform a statistical/approximate model checking experiment on the current model, using the simulator\n\t * (specified by values for undefined constants from the property only).\n\t * Sampling starts from the initial state provided or, if null, the default\n\t * initial state is used, selecting randomly (each time) if there are more than one.\n\t * Results are stored in the ResultsCollection object passed in,\n\t * some of which may be Exception objects if there were errors.\n\t * In the case of an error which affects all properties, an exception is thrown.\n\t * Note: All constants in the model file must have already been defined.\n\t * @param propertiesFile Properties file containing property to check, constants defined\n\t * @param undefinedConstants Details of constant ranges defining the experiment\n\t * @param resultsCollection Where to store the results\n\t * @param expr The property to check\n\t * @param initialState Initial state (if null, is selected randomly)\n\t * @param maxPathLength The maximum path length for sampling\n\t * @param simMethod Object specifying details of method to use for simulation\n\t * @throws PrismException if something goes wrong with the sampling algorithm\n\t * @throws InterruptedException if the thread is interrupted\n\t */\n\tpublic void modelCheckExperiment(PropertiesFile propertiesFile, UndefinedConstants undefinedConstants,\n\t\t\tResultsCollection resultsCollection, Expression expr, State initialState, long maxPathLength, SimulationMethod simMethod) throws PrismException,\n\t\t\tInterruptedException\n\t{\n\t\t// Create path to be used\n\t\tcreateNewOnTheFlyPath();\n\n\t\t// Make sure any missing parameters that can be computed before simulation\n\t\t// are computed now (sometimes this has been done already, e.g. for GUI display).\n\t\tsimMethod.computeMissingParameterBeforeSim();\n\n\t\t// Print details to log\n\t\tmainLog.println(\"\\nSimulation method: \" + simMethod.getName() + \" (\" + simMethod.getFullName() + \")\");\n\t\tmainLog.println(\"Simulation method parameters: \" + simMethod.getParametersString());\n\t\tmainLog.println(\"Simulation parameters: max path length=\" + maxPathLength);\n\n\t\t// Add the properties to the simulator (after a check that they are valid)\n\t\tint n = undefinedConstants.getNumPropertyIterations();\n\t\tValues definedPFConstants = new Values();\n\t\tResult[] results = new Result[n];\n\t\tValues[] pfcs = new Values[n];\n\t\tint[] indices = new int[n];\n\n\t\tint validPropsCount = 0;\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tdefinedPFConstants = undefinedConstants.getPFConstantValues();\n\t\t\tpfcs[i] = definedPFConstants;\n\t\t\t// for simulation, use non-exact constant evaluation\n\t\t\tpropertiesFile.setSomeUndefinedConstants(definedPFConstants, false);\n\t\t\ttry {\n\t\t\t\tcheckPropertyForSimulation(expr);\n\t\t\t\tindices[i] = addProperty(expr, propertiesFile);\n\t\t\t\tvalidPropsCount++;\n\t\t\t\t// Attach a SimulationMethod object to each property's sampler\n\t\t\t\tSimulationMethod simMethodNew = simMethod.clone();\n\t\t\t\tpropertySamplers.get(indices[i]).setSimulationMethod(simMethodNew);\n\t\t\t\t// Pass property details to SimuationMethod\n\t\t\t\t// (note that we use the copy stored in properties, which has been processed)\n\t\t\t\ttry {\n\t\t\t\t\tsimMethodNew.setExpression(properties.get(indices[i]));\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t// In case of error, also need to remove property/sampler from list\n\t\t\t\t\t// (NB: this will be at the end of the list so no re-indexing issues)\n\t\t\t\t\tproperties.remove(indices[i]);\n\t\t\t\t\tpropertySamplers.remove(indices[i]);\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\tresults[i] = new Result(e);\n\t\t\t\tindices[i] = -1;\n\t\t\t}\n\t\t\tundefinedConstants.iterateProperty();\n\t\t}\n\n\t\t// As long as there are at least some valid props, do sampling\n\t\tif (validPropsCount > 0) {\n\t\t\tdoSampling(initialState, maxPathLength);\n\t\t}\n\n\t\t// Process the results\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\t// If there was no earlier error, extract result etc.\n\t\t\tif (indices[i] != -1) {\n\t\t\t\tSampler sampler = propertySamplers.get(indices[i]);\n\t\t\t\tSimulationMethod sm = sampler.getSimulationMethod();\n\t\t\t\t// Compute/print any missing parameters that need to be done after simulation\n\t\t\t\tsm.computeMissingParameterAfterSim();\n\t\t\t\t// Extract result from SimulationMethod and store\n\t\t\t\ttry {\n\t\t\t\t\tresults[i] = new Result(sm.getResult(sampler));\n\t\t\t\t\tresults[i].setAccuracy(sampler.getSimulationMethod().getResultAccuracy(sampler));\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\tresults[i] = new Result(e);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Store result in the ResultsCollection\n\t\t\tresultsCollection.setResult(undefinedConstants.getMFConstantValues(), pfcs[i], results[i].getResult());\n\t\t}\n\n\t\t// Display results to log\n\t\tmainLog.println(\"\\nResults:\");\n\t\tfor (int i = 0; i < results.length; i++)\n\t\t\tmainLog.println(pfcs[i] + \" : \" + results[i].getResultAndAccuracy());\n\t\t//mainLog.print(resultsCollection.toStringPartial(undefinedConstants.getMFConstantValues(), true, \" \", \" : \", false));\n\t}\n\n\t/**\n\t * Execute sampling for the set of currently loaded properties.\n\t * Sample paths are from the specified initial state and maximum length.\n\t * Termination of the sampling process occurs when the SimulationMethod object\n\t * for all properties indicate that it is finished.\n\t * @param initialState Initial state (if null, is selected randomly)\n\t * @param maxPathLength The maximum path length for sampling\n\t */\n\tprivate void doSampling(State initialState, long maxPathLength) throws PrismException\n\t{\n\t\tint iters;\n\t\tlong i;\n\t\t// Flags\n\t\tboolean stoppedEarly = false;\n\t\tboolean deadlocksFound = false;\n\t\tboolean allDone = false;\n\t\tboolean allKnown = false;\n\t\tboolean someUnknownButBounded = false;\n\t\tboolean shouldStopSampling = false;\n\t\t// Path stats\n\t\tdouble avgPathLength = 0;\n\t\tlong minPathFound = 0, maxPathFound = 0;\n\t\t// Progress info\n\t\tint lastPercentageDone = 0;\n\t\tint percentageDone = 0;\n\t\t// Timing info\n\t\tlong start, stop;\n\t\tdouble time_taken;\n\n\t\t// Start\n\t\tstart = System.currentTimeMillis();\n\t\tmainLog.print(\"\\nSampling progress: [\");\n\t\tmainLog.flush();\n\n\t\t// Main sampling loop\n\t\titers = 0;\n\t\twhile (!shouldStopSampling) {\n\n\t\t\t// See if all properties are done; if so, stop sampling\n\t\t\tallDone = true;\n\t\t\tfor (Sampler sampler : propertySamplers) {\n\t\t\t\tif (!sampler.getSimulationMethod().shouldStopNow(iters, sampler))\n\t\t\t\t\tallDone = false;\n\t\t\t}\n\t\t\tif (allDone)\n\t\t\t\tbreak;\n\n\t\t\t// Display progress (of slowest property)\n\t\t\tpercentageDone = 100;\n\t\t\tfor (Sampler sampler : propertySamplers) {\n\t\t\t\tpercentageDone = Math.min(percentageDone, sampler.getSimulationMethod().getProgress(iters, sampler));\n\t\t\t}\n\t\t\tif (percentageDone > lastPercentageDone) {\n\t\t\t\tlastPercentageDone = percentageDone;\n\t\t\t\tmainLog.print(\" \" + lastPercentageDone + \"%\");\n\t\t\t\tmainLog.flush();\n\t\t\t}\n\n\t\t\titers++;\n\n\t\t\t// Start the new path for this iteration (sample)\n\t\t\tinitialisePath(initialState);\n\n\t\t\t// Generate a path\n\t\t\tallKnown = false;\n\t\t\tsomeUnknownButBounded = false;\n\t\t\ti = 0;\n\t\t\twhile ((!allKnown && i < maxPathLength) || someUnknownButBounded) {\n\t\t\t\t// Check status of samplers\n\t\t\t\tallKnown = true;\n\t\t\t\tsomeUnknownButBounded = false;\n\t\t\t\tfor (Sampler sampler : propertySamplers) {\n\t\t\t\t\tif (!sampler.isCurrentValueKnown()) {\n\t\t\t\t\t\tallKnown = false;\n\t\t\t\t\t\tif (sampler.needsBoundedNumSteps())\n\t\t\t\t\t\t\tsomeUnknownButBounded = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Stop when all answers are known or we have reached max path length\n\t\t\t\t// (but don't stop yet if there are \"bounded\" samplers with unkown values)\n\t\t\t\tif ((allKnown || i >= maxPathLength) && !someUnknownButBounded)\n\t\t\t\t\tbreak;\n\t\t\t\t// Make a random transition\n\t\t\t\tautomaticTransition();\n\t\t\t\ti++;\n\t\t\t}\n\n\t\t\t// TODO: Detect deadlocks so we can report a warning\n\n\t\t\t// Update path length statistics\n\t\t\tavgPathLength = (avgPathLength * (iters - 1) + (i)) / iters;\n\t\t\tminPathFound = (iters == 1) ? i : Math.min(minPathFound, i);\n\t\t\tmaxPathFound = (iters == 1) ? i : Math.max(maxPathFound, i);\n\n\t\t\t// If not all samplers could produce values, this an error\n\t\t\tif (!allKnown) {\n\t\t\t\tstoppedEarly = true;\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t// Update state of samplers based on last path\n\t\t\tfor (Sampler sampler : propertySamplers) {\n\t\t\t\tsampler.updateStats();\n\t\t\t}\n\t\t}\n\n\t\t// Print details\n\t\tif (!stoppedEarly) {\n\t\t\tif (!shouldStopSampling)\n\t\t\t\tmainLog.print(\" 100% ]\");\n\t\t\tmainLog.println();\n\t\t\tstop = System.currentTimeMillis();\n\t\t\ttime_taken = (stop - start) / 1000.0;\n\t\t\tmainLog.print(\"\\nSampling complete: \");\n\t\t\tmainLog.print(iters + \" iterations in \" + time_taken + \" seconds (average \" + PrismUtils.formatDouble(2, time_taken / iters) + \")\\n\");\n\t\t\tmainLog.print(\"Path length statistics: average \" + PrismUtils.formatDouble(2, avgPathLength) + \", min \" + minPathFound + \", max \" + maxPathFound\n\t\t\t\t\t+ \"\\n\");\n\t\t} else {\n\t\t\tmainLog.print(\" ...\\n\\nSampling terminated early after \" + iters + \" iterations.\\n\");\n\t\t}\n\n\t\t// Print a warning if deadlocks occurred at any point\n\t\tif (deadlocksFound)\n\t\t\tmainLog.printWarning(\"Deadlocks were found during simulation: self-loops were added.\");\n\n\t\t// Print a warning if simulation was stopped by the user\n\t\tif (shouldStopSampling)\n\t\t\tmainLog.printWarning(\"Simulation was terminated before completion.\");\n\n\t\t// write to feedback file with true to indicate that we have finished sampling\n\t\t// Write_Feedback(iteration_counter, numIters, true);\n\n\t\tif (stoppedEarly) {\n\t\t\tthrow new PrismException(\n\t\t\t\t\t\"One or more of the properties being sampled could not be checked on a sample. Consider increasing the maximum path length\");\n\t\t}\n\t}\n\n\t/**\n\t * Halt the sampling algorithm in its tracks (not implemented).\n\t */\n\tpublic void stopSampling()\n\t{\n\t\t// TODO\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/TransitionList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.util.*;\n\nimport parser.*;\nimport prism.*;\n\npublic class TransitionList<Value>\n{\n\t// Evaluator for values/states\n\tpublic Evaluator<Value> eval;\n\t\n\tprivate ArrayList<Choice<Value>> choices;\n\t/** The index of the choice containing each transition. */\n\tprivate ArrayList<Integer> transitionIndices;\n\t/** The offset with the choice containing each transition. */\n\tprivate ArrayList<Integer> transitionOffsets;\n\tprivate int numChoices;\n\tprivate int numTransitions;\n\n\t// TODO: document this\n\tpublic class Ref\n\t{\n\t\tpublic int i;\n\t\tpublic int offset;\n\t\t//int index;\n\t\t//Choice ch;\n\t}\n\n\tpublic TransitionList(Evaluator<Value> eval)\n\t{\n\t\t// Store evaluator\n\t\tthis.eval = eval;\n\t\t// Initialise\n\t\tchoices = new ArrayList<Choice<Value>>();\n\t\ttransitionIndices = new ArrayList<Integer>();\n\t\ttransitionOffsets = new ArrayList<Integer>();\n\t\tnumChoices = 0;\n\t\tnumTransitions = 0;\n\t}\n\t\n\tpublic void clear()\n\t{\n\t\tchoices.clear();\n\t\ttransitionIndices.clear();\n\t\ttransitionOffsets.clear();\n\t\tnumChoices = 0;\n\t\tnumTransitions = 0;\n\t}\n\n\tpublic void add(Choice<Value> tr)\n\t{\n\t\tint i, n;\n\t\tchoices.add(tr);\n\t\tn = tr.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ttransitionIndices.add(choices.size() - 1);\n\t\t\ttransitionOffsets.add(i);\n\t\t}\n\t\tnumChoices++;\n\t\tnumTransitions += tr.size();\n\t}\n\t\n\t/**\n\t * Scale probability/rate of all transitions in all choices, multiplying by d.\n\t */\n\tpublic void scaleProbabilitiesBy(Value d)\n\t{\n\t\tfor (int i = 0; i < numChoices; i++) {\n\t\t\tgetChoice(i).scaleProbabilitiesBy(d);\n\t\t}\n\t}\n\t\n\t// ACCESSORS\n\n\t/**\n\t * Get the number of choices.\n\t */\n\tpublic int getNumChoices()\n\t{\n\t\treturn numChoices;\n\t}\n\n\t/**\n\t * Get the number of transitions.\n\t */\n\tpublic int getNumTransitions()\n\t{\n\t\treturn numTransitions;\n\t}\n\n\t/**\n\t * Get the total sum of all probabilities (or rates).\n\t */\n\tpublic Value getProbabilitySum()\n\t{\n\t\tValue probSum = eval.zero();\n\t\tfor (Choice<Value> ch : choices) {\n\t\t\tprobSum = eval.add(probSum, ch.getProbabilitySum());\n\t\t}\n\t\treturn probSum;\n\t}\n\n\t// Get access to Choice objects \n\n\t/**\n\t * Get the ith choice.\n\t */\n\tpublic Choice<Value> getChoice(int i)\n\t{\n\t\treturn choices.get(i);\n\t}\n\n\t/**\n\t * Get the choice containing a transition of a given index.\n\t */\n\tpublic Choice<Value> getChoiceOfTransition(int index)\n\t{\n\t\treturn choices.get(transitionIndices.get(index));\n\t}\n\n\t// Get index/offset info\n\n\t/**\n\t * Get the index of the choice containing a transition of a given index.\n\t */\n\tpublic int getChoiceIndexOfTransition(int index)\n\t{\n\t\treturn transitionIndices.get(index);\n\t}\n\n\t/**\n\t * Get the offset of a transition within its containing choice.\n\t */\n\tpublic int getChoiceOffsetOfTransition(int index)\n\t{\n\t\treturn transitionOffsets.get(index);\n\t}\n\n\t/**\n\t * Get the (total) index of a transition from the index of its containing choice and its offset within it.\n\t */\n\tpublic int getTotalIndexOfTransition(int i, int offset)\n\t{\n\t\treturn transitionIndices.indexOf(i) + offset;\n\t}\n\n\t// Random selection of a choice \n\n\t/**\n\t * Get a reference to a transition according to a total probability (or rate) sum, x.\n\t * i.e.the first transition for which the sum of probabilities/rates of that and all prior\n\t * transitions (across all choices) exceeds x.\n\t * @param x Probability (or rate) sum\n\t * @param ref Empty transition reference to store result\n\t */\n\tpublic void getChoiceIndexByProbabilitySum(Value x, Ref ref)\n\t{\n\t\tint i;\n\t\tChoice<Value> choice;\n\t\tValue d = eval.zero(), tot = eval.zero();\n\t\t// Add up choice prob/rate sums to find choice\n\t\tfor (i = 0; eval.geq(x, tot) && i < numChoices; i++) {\n\t\t\td = getChoice(i).getProbabilitySum();\n\t\t\ttot = eval.add(tot,  d);\n\t\t}\n\t\tref.i = i - 1;\n\t\t// Pick transition within choice \n\t\tchoice = getChoice(i - 1);\n\t\tif (choice.size() > 1) {\n\t\t\tref.offset = choice.getIndexByProbabilitySum(eval.subtract(x, (eval.subtract(tot, d))));\n\t\t} else {\n\t\t\tref.offset = 0;\n\t\t}\n\t}\n\n\t// Direct access to transition info\n\n\t/**\n\t * Get a string describing the action/module of a transition, specified by its index.\n\t * (form is \"module\" or \"[action]\")\n\t */\n\tpublic String getTransitionModuleOrAction(int index)\n\t{\n\t\treturn getChoiceOfTransition(index).getModuleOrAction();\n\t}\n\n\t/**\n\t * Get the index of the action/module of a transition, specified by its index.\n\t * (-i for independent in ith module, i for synchronous on ith action)\n\t * (in both cases, modules/actions are 1-indexed)\n\t */\n\tpublic int getTransitionModuleOrActionIndex(int index)\n\t{\n\t\treturn getChoiceOfTransition(index).getModuleOrActionIndex();\n\t}\n\n\t/**\n\t * Get a string describing the action/module of a choice, specified by its index.\n\t * (form is \"module\" or \"[action]\")\n\t */\n\tpublic String getChoiceModuleOrAction(int index)\n\t{\n\t\treturn getChoice(index).getModuleOrAction();\n\t}\n\n\t/**\n\t * Get the index of the action/module of a choice, specified by its index.\n\t * (-i for independent in ith module, i for synchronous on ith action)\n\t * (in both cases, modules/actions are 1-indexed)\n\t */\n\tpublic int getChoiceModuleOrActionIndex(int index)\n\t{\n\t\treturn getChoice(index).getModuleOrActionIndex();\n\t}\n\n\t/**\n\t * Get the probability/rate of a transition, specified by its index.\n\t */\n\tpublic Value getTransitionProbability(int index)\n\t{\n\t\treturn getChoiceOfTransition(index).getProbability(transitionOffsets.get(index));\n\t}\n\n\t/**\n\t * Get a string describing the updates making up a transition, specified by its index.\n\t * This is in abbreviated form, i.e. x'=1, rather than x'=x+1.\n\t * Format is: x'=1, y'=0, with empty string for empty update.\n\t * Only variables updated are included in list (even if unchanged).\n\t */\n\tpublic String getTransitionUpdateString(int index, State currentState) throws PrismLangException\n\t{\n\t\treturn getChoiceOfTransition(index).getUpdateString(transitionOffsets.get(index), currentState);\n\t}\n\n\t/**\n\t * Get a string describing the updates making up a transition, specified by its index.\n\t * This is in full, i.e. of the form x'=x+1, rather than x'=1.\n\t * Format is: (x'=x+1) & (y'=y-1), with empty string for empty update.\n\t * Only variables updated are included in list.\n\t * Note that expressions may have been simplified from original model. \n\t */\n\tpublic String getTransitionUpdateStringFull(int index)\n\t{\n\t\treturn getChoiceOfTransition(index).getUpdateStringFull(transitionOffsets.get(index));\n\t}\n\n\t/**\n\t * Get the target of a transition (as a new State object), specified by its index.\n\t */\n\tpublic State computeTransitionTarget(int index, State currentState, VarList varList) throws PrismLangException\n\t{\n\t\treturn getChoiceOfTransition(index).computeTarget(transitionOffsets.get(index), currentState, varList);\n\t}\n\t\n\t// Other checks and queries\n\t\n\t/**\n\t * Is there a deadlock (i.e. no available transitions)?\n\t */\n\tpublic boolean isDeadlock()\n\t{\n\t\treturn numChoices == 0;\n\t}\n\n\t/**\n\t * Are the choices deterministic? (i.e. a single probability 1.0 transition)\n\t * (will also return true for a continuous-time model matching this\n\t * definition, since TransitionList does not know about model type)\n\t */\n\tpublic boolean isDeterministic()\n\t{\n\t\treturn numTransitions == 1 && eval.isOne(getChoice(0).getProbability(0));\n\t}\n\n\t/**\n\t * Is there a deterministic self-loop, i.e. do all transitions go to the current state.\n\t */\n\tpublic boolean isDeterministicSelfLoop(State currentState, VarList varList)\n\t{\n\t\t// TODO: make more efficient, and also limit calls to it\n\t\t// (e.g. only if already stayed in state twice?)\n\t\tint i, n;\n\t\tState newState = new State(currentState);\n\t\ttry {\n\t\t\tfor (Choice<Value> ch : choices) {\n\t\t\t\tn = ch.size();\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\tch.computeTarget(i, currentState, newState, varList);\n\t\t\t\t\tif (!currentState.equals(newState)) {\n\t\t\t\t\t\t// Found a non-loop\n\t\t\t\t\t\treturn false;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (PrismLangException e) {\n\t\t\t// If anything goes wrong when evaluating, just return false.\n\t\t\treturn false;\n\t\t}\n\t\t// All targets loop\n\t\treturn true;\n\t}\n\n\t/**\n\t * Check the validity of the available transitions for a given model type.\n\t * Throw a PrismException if an error is found.\n\t */\n\tpublic void checkValid(ModelType modelType) throws PrismException\n\t{\n\t\tfor (Choice<Value> ch : choices) {\n\t\t\tch.checkValid(modelType);\n\t\t}\n\t}\n\t\n\t/**\n\t * Check whether the available transitions (from a particular state)\n\t * would cause any errors, mainly variable overflows.\n\t * Variable ranges are specified in the passed in VarList.\n\t * Throws an exception if such an error occurs.\n\t */\n\tpublic void checkForErrors(State currentState, VarList varList) throws PrismException\n\t{\n\t\tfor (Choice<Value> ch : choices) {\n\t\t\tch.checkForErrors(currentState, varList);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic String toString()\n\t{\n\t\tString s = \"\";\n\t\tboolean first = true;\n\t\tfor (Choice<Value> ch : choices) {\n\t\t\tif (first)\n\t\t\t\tfirst = false;\n\t\t\telse\n\t\t\t\ts += \", \";\n\t\t\ts += ch.toString();\n\t\t}\n\t\treturn s;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/Updater.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.HashSet;\nimport java.util.List;\nimport java.util.Map;\n\nimport parser.EvaluateContextState;\nimport parser.State;\nimport parser.VarList;\nimport parser.ast.Command;\nimport parser.ast.Expression;\nimport parser.ast.Module;\nimport parser.ast.ModulesFile;\nimport parser.ast.Update;\nimport parser.ast.Updates;\nimport parser.type.TypeClock;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismSettings;\n\npublic class Updater<Value> extends PrismComponent\n{\n\t// Evaluator for values/states\n\tpublic Evaluator<Value> eval;\n\t\n\t// Evaluation context for expressions\n\tprotected EvaluateContextState ec;\n\t\n\t// Settings:\n\t// Do we check that probabilities sum to 1?\n\tprotected boolean doProbChecks = true;\n\t\n\t// Info on model being explored\n\tprotected ModulesFile modulesFile;\n\tprotected ModelType modelType;\n\tprotected int numModules;\n\tprotected VarList varList;\n\t// Synchronising action info\n\tprotected List<String> synchs;\n\tprotected int numSynchs;\n\tprotected int synchModuleCounts[];\n\t// Model info/stats\n\tprotected int numRewardStructs;\n\t// For real-time models, info about which vars are clocks (bitset over variable indices)\n\tprotected BitSet clockVars;\n\t\n\t// Temporary storage:\n\n\t// Element i,j of updateLists is a list of the updates from module i labelled with action j\n\t// (where j=0 denotes independent, otherwise 1-indexed action label)\n\tprotected List<List<List<Updates>>> updateLists;\n\t// Bit j of enabledSynchs is set iff action j is currently enabled\n\t// (where j=0 denotes independent, otherwise 1-indexed action label)\n\tprotected BitSet enabledSynchs;\n\t// Element j of enabledModules is a BitSet showing modules which enable action j\n\t// (where j=0 denotes independent, otherwise 1-indexed action label)\n\tprotected BitSet enabledModules[];\n\t// For real-time models, the guards over clock variables attached to (some) Updates\n\tprotected Map<Updates,Expression> clockGuards;\n\n\tpublic Updater(ModulesFile modulesFile, VarList varList, Evaluator<Value> eval)\n\t{\n\t\tthis(modulesFile, varList, eval, null);\n\t}\n\t\n\tpublic Updater(ModulesFile modulesFile, VarList varList, Evaluator<Value> eval, PrismComponent parent)\n\t{\n\t\t// Store some settings\n\t\tdoProbChecks = parent.getSettings().getBoolean(PrismSettings.PRISM_DO_PROB_CHECKS);\n\t\t\n\t\t// Get info from model\n\t\tthis.modulesFile = modulesFile;\n\t\tmodelType = modulesFile.getModelType();\n\t\tnumModules = modulesFile.getNumModules();\n\t\tsynchs = modulesFile.getSynchs();\n\t\tnumSynchs = synchs.size();\n\t\tnumRewardStructs = modulesFile.getNumRewardStructs();\n\t\tthis.varList = varList;\n\n\t\t// Store evaluator\n\t\tthis.eval = eval;\n\t\t\n\t\t// Create evaluate context for re-use\n\t\tec = new EvaluateContextState(modulesFile.getConstantValues(), new State(modulesFile.getNumVars()));\n\t\tec.setEvaluationMode(eval.evalMode());\n\t\t\n\t\t// For real-time models, store info about which vars are clocks\n\t\tif (modelType.realTime()) {\n\t\t\tint numVars = varList.getNumVars();\n\t\t\tclockVars = new BitSet();\n\t\t\tfor (int v = 0; v < numVars; v++) {\n\t\t\t\tif (varList.getType(v) instanceof TypeClock) {\n\t\t\t\t\tclockVars.set(v);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Compute count of number of modules using each synch action\n\t\t// First, compute and cache the synch actions for each of the modules\n\t\tList<HashSet<String>> synchsPerModule = new ArrayList<HashSet<String>>(numModules);\n\t\tfor (int i = 0; i < numModules; i++) {\n\t\t\tsynchsPerModule.add(new HashSet<String>(modulesFile.getModule(i).getAllSynchs()));\n\t\t}\n\t\t// Second, do the counting\n\t\tsynchModuleCounts = new int[numSynchs];\n\t\tfor (int j = 0; j < numSynchs; j++) {\n\t\t\tsynchModuleCounts[j] = 0;\n\t\t\tString s = synchs.get(j);\n\t\t\tfor (int i = 0; i < numModules; i++) {\n\t\t\t\tif (synchsPerModule.get(i).contains(s))\n\t\t\t\t\tsynchModuleCounts[j]++;\n\t\t\t}\n\t\t}\n\n\t\t// Build lists/bitsets for later use\n\t\tupdateLists = new ArrayList<List<List<Updates>>>(numModules);\n\t\tfor (int i = 0; i < numModules; i++) {\n\t\t\tupdateLists.add(new ArrayList<List<Updates>>(numSynchs + 1));\n\t\t\tfor (int j = 0; j < numSynchs + 1; j++) {\n\t\t\t\tupdateLists.get(i).add(new ArrayList<Updates>());\n\t\t\t}\n\t\t}\n\t\tenabledSynchs = new BitSet(numSynchs + 1);\n\t\tenabledModules = new BitSet[numSynchs + 1];\n\t\tfor (int j = 0; j < numSynchs + 1; j++) {\n\t\t\tenabledModules[j] = new BitSet(numModules);\n\t\t}\n\t\tclockGuards = new HashMap<Updates, Expression>();\n\t}\n\n\t/**\n\t * Determine the set of outgoing transitions from state 'state' and store in 'transitionList'.\n\t * @param state State from which to explore\n\t * @param transitionList TransitionList object in which to store result\n\t */\n\tpublic void calculateTransitions(State state, TransitionList<Value> transitionList) throws PrismException\n\t{\n\t\tList<ChoiceListFlexi<Value>> chs;\n\t\tint i, j, k, l, n, count;\n\n\t\t// Clear lists/bitsets\n\t\ttransitionList.clear();\n\t\tfor (i = 0; i < numModules; i++) {\n\t\t\tfor (j = 0; j < numSynchs + 1; j++) {\n\t\t\t\tupdateLists.get(i).get(j).clear();\n\t\t\t}\n\t\t}\n\t\tenabledSynchs.clear();\n\t\tfor (i = 0; i < numSynchs + 1; i++) {\n\t\t\tenabledModules[i].clear();\n\t\t}\n\t\tclockGuards.clear();\n\n\t\t// Calculate the available updates for each module/action\n\t\t// (update information in updateLists, clockGuards, enabledSynchs and enabledModules)\n\t\tfor (i = 0; i < numModules; i++) {\n\t\t\tcalculateUpdatesForModule(i, state);\n\t\t}\n\t\t//System.out.println(\"updateLists: \" + updateLists);\n\n\t\t// Add independent transitions for each (enabled) module to list\n\t\tfor (i = enabledModules[0].nextSetBit(0); i >= 0; i = enabledModules[0].nextSetBit(i + 1)) {\n\t\t\tfor (Updates ups : updateLists.get(i).get(0)) {\n\t\t\t\tChoiceListFlexi<Value> ch = processUpdatesAndCreateNewChoice(-(i + 1), ups, state);\n\t\t\t\tif (ch.size() > 0)\n\t\t\t\t\ttransitionList.add(ch);\n\t\t\t}\n\t\t}\n\t\t// Add synchronous transitions to list\n\t\tchs = new ArrayList<ChoiceListFlexi<Value>>();\n\t\tfor (i = enabledSynchs.nextSetBit(1); i >= 0; i = enabledSynchs.nextSetBit(i + 1)) {\n\t\t\tchs.clear();\n\t\t\t// Check counts to see if this action is blocked by some module\n\t\t\tif (enabledModules[i].cardinality() < synchModuleCounts[i - 1])\n\t\t\t\tcontinue;\n\t\t\t// If not, proceed...\n\t\t\tfor (j = enabledModules[i].nextSetBit(0); j >= 0; j = enabledModules[i].nextSetBit(j + 1)) {\n\t\t\t\tcount = updateLists.get(j).get(i).size();\n\t\t\t\t// Case where there is only 1 Updates for this module\n\t\t\t\tif (count == 1) {\n\t\t\t\t\tUpdates ups = updateLists.get(j).get(i).get(0);\n\t\t\t\t\t// Case where this is the first Choice created\n\t\t\t\t\tif (chs.size() == 0) {\n\t\t\t\t\t\tChoiceListFlexi<Value> ch = processUpdatesAndCreateNewChoice(i, ups, state);\n\t\t\t\t\t\tif (ch.size() > 0)\n\t\t\t\t\t\t\tchs.add(ch);\n\t\t\t\t\t}\n\t\t\t\t\t// Case where there are existing Choices\n\t\t\t\t\telse {\n\t\t\t\t\t\t// Product with all existing choices\n\t\t\t\t\t\tfor (ChoiceListFlexi<Value> ch : chs) {\n\t\t\t\t\t\t\tprocessUpdatesAndAddToProduct(ups, state, ch);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Case where there are multiple Updates (i.e. local nondeterminism)\n\t\t\t\telse {\n\t\t\t\t\t// Case where there are no existing choices\n\t\t\t\t\tif (chs.size() == 0) {\n\t\t\t\t\t\tfor (Updates ups : updateLists.get(j).get(i)) {\n\t\t\t\t\t\t\tChoiceListFlexi<Value> ch = processUpdatesAndCreateNewChoice(i, ups, state);\n\t\t\t\t\t\t\tif (ch.size() > 0)\n\t\t\t\t\t\t\t\tchs.add(ch);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Case where there are existing Choices\n\t\t\t\t\telse {\n\t\t\t\t\t\t// Duplicate (count-1 copies of) current Choice list\n\t\t\t\t\t\tn = chs.size();\n\t\t\t\t\t\tfor (k = 0; k < count - 1; k++)\n\t\t\t\t\t\t\tfor (l = 0; l < n; l++)\n\t\t\t\t\t\t\t\tchs.add(new ChoiceListFlexi<Value>(chs.get(l)));\n\t\t\t\t\t\t// Products with existing choices\n\t\t\t\t\t\tfor (k = 0; k < count; k++) {\n\t\t\t\t\t\t\tUpdates ups = updateLists.get(j).get(i).get(k);\n\t\t\t\t\t\t\tfor (l = 0; l < n; l++) {\n\t\t\t\t\t\t\t\tprocessUpdatesAndAddToProduct(ups, state, chs.get(k * n + l));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Add all new choices to transition list\n\t\t\tfor (ChoiceListFlexi<Value> ch : chs) {\n\t\t\t\ttransitionList.add(ch);\n\t\t\t}\n\t\t}\n\t\t\n\t\t// For a DTMC, we need to normalise across all transitions\n\t\t// This is partly to handle \"local nondeterminism\"\n\t\t// and also to handle any dubious trickery done by disabling probability checks\n\t\tif (modelType == ModelType.DTMC) {\n\t\t\tValue probSum = transitionList.getProbabilitySum();\n\t\t\ttransitionList.scaleProbabilitiesBy(eval.divide(eval.one(), probSum));\n\t\t}\n\t\n\t\t// Check validity of the computed transitions\n\t\t// (not needed currently)\n\t\t//transitionList.checkValid(modelType);\n\t\t\n\t\t// Check for errors (e.g. overflows) in the computed transitions\n\t\t//transitionList.checkForErrors(state, varList);\n\t\t\n\t\t//System.out.println(transitionList);\n\t}\n\t\n\t// Private helpers\n\t\n\t/**\n\t * Determine the enabled updates for the 'm'th module from (global) state 'state'.\n\t * Update information in updateLists, enabledSynchs and enabledModules.\n\t * @param m The module index\n\t * @param state State from which to explore\n\t */\n\tprotected void calculateUpdatesForModule(int m, State state) throws PrismLangException\n\t{\n\t\tModule module = modulesFile.getModule(m);\n\t\tint n = module.getNumCommands();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tCommand command = module.getCommand(i);\n\t\t\t// See if the guard is satisfied\n\t\t\tboolean guardSat = false;\n\t\t\tExpression clockGuard = null;\n\t\t\t// For real-time models, we only evaluate in terms of non-clock vars, and store any clock guard\n\t\t\tif (modelType.realTime()) {\n\t\t\t\tState stateNoClocks = new State(state);\n\t\t\t\tfor (int v = clockVars.nextSetBit(0); v >= 0; v = clockVars.nextSetBit(v + 1)) {\n\t\t\t\t\tstateNoClocks.varValues[v] = null;\n\t\t\t\t}\n\t\t\t\tclockGuard = command.getGuard().deepCopy();\n\t\t\t\tclockGuard = (Expression) clockGuard.evaluatePartially(ec.setState(stateNoClocks)).simplify();\n\t\t\t\tif (!Expression.isFalse(clockGuard)) {\n\t\t\t\t\tguardSat = true;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tguardSat = command.getGuard().evaluateBoolean(ec.setState(state));\n\t\t\t}\n\t\t\t// If the command is enabled, update stored info\n\t\t\tif (guardSat) {\n\t\t\t\tint j = command.getSynchIndex();\n\t\t\t\tupdateLists.get(m).get(j).add(command.getUpdates());\n\t\t\t\tenabledSynchs.set(j);\n\t\t\t\tenabledModules[j].set(m);\n\t\t\t\tif (modelType.realTime()) {\n\t\t\t\t\tclockGuards.put(command.getUpdates(), clockGuard);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Evaluate the probability (or rate) of the ith update, in the context of a state.\n\t * If the probability is not specified in the update, it is assumed to be 1.\n\t */\n\tprotected Value getProbabilityInState(Updates ups, int i, State state) throws PrismLangException\n\t{\n\t\tExpression p = ups.getProbability(i);\n\t\tif (p == null) {\n\t\t\treturn eval.one();\n\t\t} else {\n\t\t\treturn eval.evaluate(p, state);\n\t\t}\n\t}\n\t\n\t/**\n\t * Create a new Choice object (currently ChoiceListFlexi) based on an Updates object\n\t * and a (global) state. Check for negative probabilities/rates and, if appropriate,\n\t * check probabilities sum to 1 too.\n\t * @param moduleOrActionIndex Module/action for the choice, encoded as an integer (see Choice)\n\t * @param ups The Updates object \n\t * @param state Global state\n\t */\n\tprivate ChoiceListFlexi<Value> processUpdatesAndCreateNewChoice(int moduleOrActionIndex, Updates ups, State state) throws PrismLangException\n\t{\n\t\tChoiceListFlexi<Value> ch;\n\t\tList<Update> list;\n\t\tint i, n;\n\t\tValue p, sum;\n\n\t\t// Create choice and add all info\n\t\tch = new ChoiceListFlexi<Value>(eval);\n\t\tch.setModuleOrActionIndex(moduleOrActionIndex);\n\t\tn = ups.getNumUpdates();\n\t\tsum = eval.zero();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t// Compute probability/rate\n\t\t\tp = getProbabilityInState(ups, i, state);\n\t\t\t// Check that probabilities/rates are finite (non-infinite, non-NaN) and non-negative\n\t\t\t// We omit the check in symbolic (parametric) cases - too expensive\n\t\t\t// Note: we indicate errors in whole Updates object because the offending\n\t\t\t// probability expression has probably been simplified from original form.\n\t\t\tif (!eval.isSymbolic()) {\n\t\t\t\tif (!eval.isFinite(p)) {\n\t\t\t\t\tString msg = modelType.probabilityOrRate() + \" is not finite in state \" + state.toString(modulesFile);\n\t\t\t\t\tthrow new PrismLangException(msg, ups);\n\t\t\t\t}\n\t\t\t\tif (!eval.geq(p, eval.zero())) {\n\t\t\t\t\tString msg = modelType.probabilityOrRate() + \" is negative in state \" + state.toString(modulesFile);\n\t\t\t\t\tthrow new PrismLangException(msg, ups);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Skip transitions with zero probability/rate\n\t\t\tif (eval.isZero(p))\n\t\t\t\tcontinue;\n\t\t\tsum  = eval.add(sum, p);\n\t\t\tlist = new ArrayList<Update>();\n\t\t\tlist.add(ups.getUpdate(i));\n\t\t\tch.add(p, list);\n\t\t}\n\t\t// For now, PRISM treats empty (all zero probs/rates) distributions as an error.\n\t\t// Later, when errors in symbolic model construction are improved, this might be relaxed.\n\t\tif (ch.size() == 0) {\n\t\t\tString msg = modelType.probabilityOrRate();\n\t\t\tmsg += (ups.getNumUpdates() > 1) ? \" values sum to \" : \" is \";\n\t\t\tmsg += \"zero for updates in state \" + state.toString(modulesFile);\n\t\t\tthrow new PrismLangException(msg, ups);\n\t\t}\n\t\t// Check distribution sums to 1 (if required, and if is non-empty)\n\t\t// As above, we omit the check in symbolic (parametric) cases - too expensive\n\t\tif (doProbChecks && ch.size() > 0 && modelType.choicesSumToOne() && !eval.isSymbolic()) {\n\t\t\ttry {\n\t\t\t\teval.checkProbabilitySum(sum);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow new PrismLangException(e.getMessage() + \" in state \" + state.toString(modulesFile), ups);\n\t\t\t}\n\t\t}\n\t\tif (modelType.realTime() && clockGuards.containsKey(ups)) {\n\t\t\tch.setClockGuard(clockGuards.get(ups));\n\t\t}\n\t\treturn ch;\n\t}\n\n\t/**\n\t * Create a new Choice object (currently ChoiceListFlexi) based on the product\n\t * of an existing ChoiceListFlexi and an Updates object, for some (global) state.\n\t * If appropriate, check probabilities sum to 1 too.\n\t * @param ups The Updates object \n\t * @param state Global state\n\t * @param ch The existing Choices object\n\t */\n\tprivate void processUpdatesAndAddToProduct(Updates ups, State state, ChoiceListFlexi<Value> ch) throws PrismLangException\n\t{\n\t\t// Create new choice (action index is 0 - not needed)\n\t\tChoiceListFlexi<Value> chNew = processUpdatesAndCreateNewChoice(0, ups, state);\n\t\t// Build product with existing\n\t\tch.productWith(chNew);\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/ACIconfidence.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.PrismException;\nimport simulator.sampler.Sampler;\nimport cern.jet.stat.Probability;\n\n/**\n * SimulationMethod class for the ACI (\"asymptotic confidence interval\") approach.\n * Case where 'confidence' is unknown parameter.\n */\npublic final class ACIconfidence extends CIMethod\n{\n\t// Estimate of variance (from sampling)\n\tprivate double varEstimator;\n\n\tpublic ACIconfidence(double width, int iterations)\n\t{\n\t\tthis.width = width;\n\t\tthis.numSamples = iterations;\n\t\tvarEstimator = 0.0;\n\t}\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"ACI\";\n\t}\n\n\t@Override\n\tpublic String getFullName()\n\t{\n\t\treturn \"Asymptotic Confidence Interval\";\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterAfterSim()\n\t{\n\t\tconfidence = 2 * (1.0 - Probability.normal(width * Math.sqrt(numSamples / varEstimator)));\n\t\tmissingParameterComputed = true;\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tthrow new PrismException(\"Missing parameter not computed yet\");\n\t\treturn confidence;\n\t}\n\t\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"width=\" + width + \", confidence=\" + \"unknown\" + \", number of samples=\" + numSamples;\n\t\telse\n\t\t\treturn \"width=\" + width + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\n\t@Override\n\tpublic boolean shouldStopNow(int iters, Sampler sampler)\n\t{\n\t\tif (iters >= numSamples) {\n\t\t\t// Store final variance for confidence computation later\n\t\t\tvarEstimator = sampler.getVariance();\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic int getProgress(int iters, Sampler sampler)\n\t{\n\t\t// Easy: percentage of iters done so far\n\t\treturn ((10 * iters) / numSamples) * 10;\n\t}\n\t\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tACIconfidence m = new ACIconfidence(width, numSamples);\n\t\t// Remaining CIMethod stuff\n\t\tm.confidence = confidence;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\t// Local stuff\n\t\tm.varEstimator = varEstimator;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/ACIiterations.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.PrismException;\nimport simulator.sampler.Sampler;\nimport cern.jet.stat.Probability;\n\n/**\n * SimulationMethod class for the ACI (\"asymptotic confidence interval\") approach.\n * Case where 'iterations' (number of samples) is unknown parameter.\n */\npublic final class ACIiterations extends CIMethod\n{\n\t// For reward properties, manually specified number of iterations\n\t// after which to conclude whether we are in S^2=0 case or not\n\tprivate int reqIterToConclude;\n\tprivate boolean reqIterToConcludeGiven;\n\t// For reward properties, maximum value of reward allows\n\t// automatic detection of whether we are in S^2=0 case or not\n\tprivate double maxReward;\n\t// Final number of iterations of sampling \n\tprivate int computedIterations;\n\t// Square of quantile\n\tprivate double squaredQuantile;\n\n\t// CONSTRUCTORS\n\n\t// probabilities, automatic\n\tpublic ACIiterations(double confidenceLevel, double width)\n\t{\n\t\tthis.confidence = confidenceLevel;\n\t\tthis.width = width;\n\t\treqIterToConclude = 0;\n\t\treqIterToConcludeGiven = false;\n\t\tmaxReward = 1.0;\n\t\tcomputedIterations = 0;\n\t\tsquaredQuantile = 0.0;\n\t}\n\n\t// probabilities or rewards, manual\n\tpublic ACIiterations(double confidenceLevel, double width, int reqIterToConclude)\n\t{\n\t\tthis.confidence = confidenceLevel;\n\t\tthis.width = width;\n\t\tthis.reqIterToConclude = reqIterToConclude;\n\t\treqIterToConcludeGiven = true;\n\t\tmaxReward = 1.0;\n\t\tcomputedIterations = 0;\n\t\tsquaredQuantile = 0.0;\n\t}\n\n\t// rewards, automatic\n\tpublic ACIiterations(double confidenceLevel, double width, double maxReward)\n\t{\n\t\tthis.confidence = confidenceLevel;\n\t\tthis.width = width;\n\t\tthis.maxReward = maxReward;\n\t\treqIterToConclude = 0;\n\t\treqIterToConcludeGiven = false;\n\t\tcomputedIterations = 0;\n\t\tsquaredQuantile = 0.0;\n\t}\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"ACI\";\n\t}\n\n\t@Override\n\tpublic String getFullName()\n\t{\n\t\treturn \"Asymptotic Confidence Interval\";\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterAfterSim()\n\t{\n\t\t// Store iters (computed earlier)\n\t\tnumSamples = computedIterations;\n\t\tmissingParameterComputed = true;\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tthrow new PrismException(\"Missing parameter not computed yet\");\n\t\treturn numSamples;\n\t}\n\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"width=\" + width + \", confidence=\" + confidence + \", number of samples=unknown\";\n\t\telse\n\t\t\treturn \"width=\" + width + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\n\t@Override\n\tpublic boolean shouldStopNow(int iters, Sampler sampler)\n\t{\n\t\tdouble quantile = 0.0;\n\n\t\t// Need at least 2 iterations\n\t\t// (Student's t-distribution only defined for v > 1)\n\t\t// (and variance is always 0 for iters = 1)\n\t\tif (iters < 2)\n\t\t\treturn false;\n\n\t\t// We cannot conclude yet whether it is a \"S^2=0\" case or if the estimator is still valid (i.e. std error > 0)\n\t\tif (sampler.getVariance() <= 0.0) {\n\t\t\t// automatic\n\t\t\tif (!reqIterToConcludeGiven && maxReward / width > iters)\n\t\t\t\treturn false;\n\t\t\t// \"manual\"\n\t\t\tif (reqIterToConcludeGiven && reqIterToConclude > iters)\n\t\t\t\treturn false;\n\t\t}\n\n\t\t// The required number of iterations for the expected confidence is not reached yet\n\t\tquantile = Probability.normalInverse(1.0 - confidence / 2.0);\n\t\tsquaredQuantile = quantile * quantile;\n\t\tif (sampler.getVariance() > 0.0 && (iters + 1) < sampler.getVariance() * squaredQuantile / (width * width))\n\t\t\treturn false;\n\n\t\t// Store final number of iterations (to compute missing parameter later)\n\t\tcomputedIterations = iters;\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic int getProgress(int iters, Sampler sampler)\n\t{\n\t\t// 2 iterations needed to compute variance of the sampler\n\t\tif (sampler.getVariance() <= 0.0 || iters < 2)\n\t\t\treturn 0;\n\t\treturn 10 * ((int) (100.0 * (double) (iters + 1) * width * width / (sampler.getVariance() * squaredQuantile)) / 10);\n\t}\n\t\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tACIiterations m = new ACIiterations(confidence, width);\n\t\t// Remaining CIMethod stuff\n\t\tm.numSamples = numSamples;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\t// Local stuff\n\t\tm.reqIterToConclude = reqIterToConclude;\n\t\tm.reqIterToConcludeGiven = reqIterToConcludeGiven;\n\t\tm.maxReward = maxReward;\n\t\tm.computedIterations = computedIterations;\n\t\tm.squaredQuantile = squaredQuantile;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/ACIwidth.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.Accuracy;\nimport prism.PrismException;\nimport simulator.sampler.Sampler;\nimport cern.jet.stat.Probability;\n\n/**\n * SimulationMethod class for the ACI (\"asymptotic confidence interval\") approach.\n * Case where 'width' is unknown parameter.\n */\npublic final class ACIwidth extends CIMethod\n{\n\t// Estimate of variance (from sampling)\n\tprivate double varEstimator;\n\n\tpublic ACIwidth(double confidenceLevel, int iterations)\n\t{\n\t\tthis.confidence = confidenceLevel;\n\t\tthis.numSamples = iterations;\n\t\tvarEstimator = 0.0;\n\t}\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"ACI\";\n\t}\n\n\t@Override\n\tpublic String getFullName()\n\t{\n\t\treturn \"Asymptotic Confidence Interval\";\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterAfterSim()\n\t{\n\t\twidth = Probability.normalInverse(1.0 - confidence / 2.0) * Math.sqrt(varEstimator / numSamples);\n\t\tmissingParameterComputed = true;\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tthrow new PrismException(\"Missing parameter not computed yet\");\n\t\treturn width;\n\t}\n\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"width=\" + \"unknown\" + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t\telse\n\t\t\treturn \"width=\" + width + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\n\t@Override\n\tpublic boolean shouldStopNow(int iters, Sampler sampler)\n\t{\n\t\tif (iters >= numSamples) {\n\t\t\t// Store final variance for confidence computation later\n\t\t\tvarEstimator = sampler.getVariance();\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic int getProgress(int iters, Sampler sampler)\n\t{\n\t\t// Easy: percentage of iters done so far\n\t\treturn ((10 * iters) / numSamples) * 10;\n\t}\n\n\t@Override\n\tpublic Object getResult(Sampler sampler) throws PrismException\n\t{\n\t\t// We may use 'width' to compute the result, so compute if necessary\n\t\t// (this should never happen)\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterAfterSim();\n\t\treturn super.getResult(sampler);\n\t}\n\t\n\t@Override\n\tpublic Accuracy getResultAccuracy(Sampler sampler) throws PrismException\n\t{\n\t\t// We may use 'width' to compute the result, so compute if necessary\n\t\t// (this should never happen)\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterAfterSim();\n\t\treturn super.getResultAccuracy(sampler);\n\t}\n\t\n\t@Override\n\tpublic String getResultExplanation(Sampler sampler) throws PrismException\n\t{\n\t\t// We may use 'width' to compute the result, so compute if necessary\n\t\t// (this should never happen)\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterAfterSim();\n\t\treturn super.getResultExplanation(sampler);\n\t}\n\t\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tACIwidth m = new ACIwidth(confidence, numSamples);\n\t\t// Remaining CIMethod stuff\n\t\tm.width = width;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\t// Local stuff\n\t\tm.varEstimator = varEstimator;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/APMCMethod.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.RelOp;\nimport prism.Accuracy;\nimport prism.PrismException;\nimport prism.Accuracy.AccuracyLevel;\nimport prism.Accuracy.AccuracyType;\nimport simulator.sampler.Sampler;\n\n/**\n * SimulationMethod class(es) for the APMC (\"approximate probabilistic model checking\")\n * approach of Herault/Lassaigne/Magniette/Peyronnet (VMCAI'04).\n */\npublic abstract class APMCMethod extends SimulationMethod\n{\n\t// Has the missing parameter been computed yet?\n\tprotected boolean missingParameterComputed;\n\t\n\t// APMC parameters:\n\t// Approximation (epsilon)\n\tprotected double approximation;\n\t// Confidence (delta)\n\tprotected double confidence;\n\t// Number of samples\n\tprotected int numSamples;\n\n\t// Property info\n\t// Operator in P/R: 0=quantitative, -1=lower bound, 1=upper bound\n\tprotected int prOp;\n\t// Probability/reward bound (if any)\n\tprotected double theta;\n\t\n\t/**\n\t * Constructor: initialise but don't set any parameters.\n\t */\n\tpublic APMCMethod()\n\t{\n\t\tmissingParameterComputed = false;\n\t\tapproximation = 0.0;\n\t\tconfidence = 0.0;\n\t\tnumSamples = 0;\n\t}\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"APMC\";\n\t}\n\n\t@Override\n\tpublic String getFullName()\n\t{\n\t\treturn \"Approximate Probabilistic Model Checking\";\n\t}\n\n\t@Override\n\tpublic void reset()\n\t{\n\t\tmissingParameterComputed = false;\n\t}\n\n\tpublic abstract void computeMissingParameterBeforeSim() throws PrismException;\n\t\n\t@Override\n\tpublic void setExpression(Expression expr) throws PrismException\n\t{\n\t\tExpression bound;\n\t\tRelOp relOp;\n\t\t\n\t\t// For P properties...\n\t\tif (expr instanceof ExpressionProb) {\n\t\t\tbound = ((ExpressionProb) expr).getProb();\n\t\t\trelOp = ((ExpressionProb) expr).getRelOp();\n\t\t}\n\t\t// For R properties...\n\t\telse if (expr instanceof ExpressionReward) {\n\t\t\tbound = ((ExpressionReward) expr).getReward();\n\t\t\trelOp = ((ExpressionReward) expr).getRelOp();\n\t\t}\n\t\t// Other (error)\n\t\telse {\n\t\t\tthrow new PrismException(\"Cannot approximate \" + expr + \" using simulation\");\n\t\t}\n\n\t\t// Process bound/relop\n\t\tif (bound == null) {\n\t\t\tprOp = 0;\n\t\t\ttheta = -1.0; // junk\n\t\t} else {\n\t\t\tprOp = relOp.isLowerBound() ? -1 : 1;\n\t\t\ttheta = bound.evaluateDouble();\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic void computeMissingParameterAfterSim()\n\t{\n\t\t// Nothing to do (always computed before simulation)\n\t}\n\n\tpublic abstract Object getMissingParameter() throws PrismException;\n\t\n\tpublic abstract String getParametersString();\n\t\n\t@Override\n\tpublic boolean shouldStopNow(int iters, Sampler sampler)\n\t{\n\t\treturn iters >= numSamples;\n\t}\n\n\t@Override\n\tpublic int getProgress(int iters, Sampler sampler)\n\t{\n\t\t// Easy: percentage of iters done so far\n\t\treturn ((10 * iters) / numSamples) * 10;\n\t}\n\n\t@Override\n\tpublic Object getResult(Sampler sampler) throws PrismException\n\t{\n\t\tdouble estimate = sampler.getMeanValue();\n\t\tswitch (prOp) {\n\t\tcase 0: // 0=quantitative\n\t\t\treturn Double.valueOf(estimate);\n\t\tcase -1: // -1=lower bound\n\t\t\tif (estimate >= theta + approximation)\n\t\t\t\treturn Boolean.valueOf(true);\n\t\t\telse if (estimate <= theta - approximation)\n\t\t\t\treturn Boolean.valueOf(false);\n\t\t\telse\n\t\t\t\tthrow new PrismException(\"Approximation is not precise enough to get a result\");\n\t\tcase 1: // 1=upper bound\n\t\t\tif (estimate >= theta + approximation)\n\t\t\t\treturn Boolean.valueOf(false);\n\t\t\telse if (estimate <= theta - approximation)\n\t\t\t\treturn Boolean.valueOf(true);\n\t\t\telse\n\t\t\t\tthrow new PrismException(\"Approximation is not precise enough to get a result\");\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown property type\");\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic Accuracy getResultAccuracy(Sampler sampler){\n\t\tAccuracy accuracy;\n\t\t// Quantitative\n\t\tif (prOp == 0) {\n\t\t\taccuracy = new Accuracy(AccuracyLevel.PROBABLY_BOUNDED, approximation, AccuracyType.ABSOLUTE);\n\t\t}\n\t\t// Bounded (accuracy error bound is meaningless)\n\t\telse {\n\t\t\taccuracy = new Accuracy(AccuracyLevel.PROBABLY_BOUNDED, 0.0, AccuracyType.ABSOLUTE);\n\t\t}\n\t\taccuracy.setProbability(1.0 - confidence);\n\t\treturn accuracy;\n\t}\n\t\n\t@Override\n\tpublic String getResultExplanation(Sampler sampler){\n\t\treturn \"Pr(|ans - \" + sampler.getMeanValue() + \"| < \" + approximation + \") > \" + (1.0 - confidence);\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/APMCapproximation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.PrismException;\nimport simulator.sampler.Sampler;\n\n/**\n * SimulationMethod class for the APMC (\"approximate probabilistic model checking\")\n * approach of Herault/Lassaigne/Magniette/Peyronnet (VMCAI'04).\n * Case where 'approximation' is unknown parameter.\n */\npublic class APMCapproximation extends APMCMethod\n{\n\tpublic APMCapproximation(double confidence, int iterations)\n\t{\n\t\tthis.confidence = confidence;\n\t\tthis.numSamples = iterations;\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterBeforeSim() throws PrismException\n\t{\n\t\tapproximation = Math.sqrt((0.5 * Math.log(2.0 / confidence)) / numSamples);\n\t\tmissingParameterComputed = true;\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterBeforeSim();\n\t\treturn approximation;\n\t}\n\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"approximation=\" + \"unknown\" + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t\telse\n\t\t\treturn \"approximation=\" + approximation + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\n\t@Override\n\tpublic Object getResult(Sampler sampler) throws PrismException\n\t{\n\t\t// We may use 'approximation' to compute the result, so compute if necessary\n\t\t// (this should never happen)\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterBeforeSim();\n\t\treturn super.getResult(sampler);\n\t}\n\t\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tAPMCapproximation m = new APMCapproximation(confidence, numSamples);\n\t\tm.approximation = approximation;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/APMCconfidence.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.PrismException;\n\n/**\n * SimulationMethod class for the APMC (\"approximate probabilistic model checking\")\n * approach of Herault/Lassaigne/Magniette/Peyronnet (VMCAI'04).\n * Case where 'confidence' is unknown parameter.\n */\npublic class APMCconfidence extends APMCMethod\n{\n\tpublic APMCconfidence(double approximation, int iterations)\n\t{\n\t\tthis.approximation = approximation;\n\t\tthis.numSamples = iterations;\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterBeforeSim() throws PrismException\n\t{\n\t\tif (approximation * approximation * numSamples < Math.log(2.0) / 2.0) {\n\t\t\tString msg = \"For APMC, samples (N) and approximation (eps) must satisfy N*eps^2 >= ln(2)/2\";\n\t\t\tmsg += \". Increase samples and/or approximation\";\n\t\t\tthrow new PrismException(msg);\n\t\t}\n\t\tconfidence = 2.0 / Math.exp((numSamples * approximation * approximation) * 2.0);\n\t\tmissingParameterComputed = true;\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterBeforeSim();\n\t\treturn confidence;\n\t}\n\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"approximation=\" + approximation + \", confidence=\" + \"unknown\" + \", number of samples=\" + numSamples;\n\t\telse\n\t\t\treturn \"approximation=\" + approximation + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\t\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tAPMCconfidence m = new APMCconfidence(approximation, numSamples);\n\t\tm.confidence = confidence;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/APMCiterations.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.PrismException;\n\n/**\n * SimulationMethod class for the APMC (\"approximate probabilistic model checking\")\n * approach of Herault/Lassaigne/Magniette/Peyronnet (VMCAI'04).\n * Case where 'iterations' (number of samples) is unknown parameter.\n */\npublic class APMCiterations extends APMCMethod\n{\n\tpublic APMCiterations(double confidence, double approximation)\n\t{\n\t\tthis.confidence = confidence;\n\t\tthis.approximation = approximation;\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterBeforeSim() throws PrismException\n\t{\n\t\tdouble missing = Math.ceil(0.5 * Math.log(2.0 / confidence) / (approximation * approximation));\n\t\tif (missing < (double) Integer.MAX_VALUE) {\n\t\t\tnumSamples = (int) missing;\n\t\t\tmissingParameterComputed = true;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Overflow in APMC method: required number of iterations is too high\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterBeforeSim();\n\t\treturn numSamples;\n\t}\n\t\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"approximation=\" + approximation + \", confidence=\" + confidence + \", number of samples=\" + \"unknown\";\n\t\telse\n\t\t\treturn \"approximation=\" + approximation + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\t\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tAPMCiterations m = new APMCiterations(confidence, approximation);\n\t\tm.numSamples = numSamples;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/CIMethod.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.RelOp;\nimport prism.Accuracy;\nimport prism.PrismException;\nimport prism.Accuracy.AccuracyLevel;\nimport prism.Accuracy.AccuracyType;\nimport simulator.sampler.Sampler;\n\n/**\n * SimulationMethod class(es) for the CI (\"confidence interval\") approach.\n */\npublic abstract class CIMethod extends SimulationMethod\n{\n\t// Has the missing parameter been computed yet?\n\tprotected boolean missingParameterComputed;\n\n\t// CI parameters:\n\t// Interval width\n\tprotected double width;\n\t// Confidence level (alpha)\n\tprotected double confidence;\n\t// Number of samples\n\tprotected int numSamples;\n\n\t// Property info\n\t// Operator in P/R: 0=quantitative, -1=lower bound, 1=upper bound\n\tprotected int prOp;\n\t// Probability/reward bound (if any)\n\tprotected double theta;\n\n\tpublic CIMethod()\n\t{\n\t\tmissingParameterComputed = false;\n\t\twidth = 0.0;\n\t\tconfidence = 0.0;\n\t\tnumSamples = 0;\n\t}\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"CI\";\n\t}\n\n\t@Override\n\tpublic String getFullName()\n\t{\n\t\treturn \"Confidence Interval\";\n\t}\n\n\t@Override\n\tpublic void reset()\n\t{\n\t\tmissingParameterComputed = false;\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterBeforeSim() throws PrismException\n\t{\n\t\t// Nothing to do (always computed after simulation)\n\t}\n\n\t@Override\n\tpublic void setExpression(Expression expr) throws PrismException\n\t{\n\t\tExpression bound;\n\t\tRelOp relOp;\n\n\t\t// For P properties...\n\t\tif (expr instanceof ExpressionProb) {\n\t\t\tbound = ((ExpressionProb) expr).getProb();\n\t\t\trelOp = ((ExpressionProb) expr).getRelOp();\n\t\t}\n\t\t// For R properties...\n\t\telse if (expr instanceof ExpressionReward) {\n\t\t\tbound = ((ExpressionReward) expr).getReward();\n\t\t\trelOp = ((ExpressionReward) expr).getRelOp();\n\t\t}\n\t\t// Other (error)\n\t\telse {\n\t\t\tthrow new PrismException(\"Cannot approximate \" + expr + \" using simulation\");\n\t\t}\n\n\t\t// Process bound/relop\n\t\tif (bound == null) {\n\t\t\tprOp = 0;\n\t\t\ttheta = -1.0; // junk\n\t\t} else {\n\t\t\tprOp = relOp.isLowerBound() ? -1 : 1;\n\t\t\ttheta = bound.evaluateDouble();\n\t\t}\n\t}\n\n\tpublic abstract void computeMissingParameterAfterSim();\n\n\tpublic abstract Object getMissingParameter() throws PrismException;\n\n\tpublic abstract String getParametersString();\n\n\tpublic abstract boolean shouldStopNow(int iters, Sampler sampler);\n\n\tpublic abstract int getProgress(int iters, Sampler sampler);\n\n\t@Override\n\tpublic Object getResult(Sampler sampler) throws PrismException\n\t{\n\t\tdouble mean = sampler.getMeanValue();\n\t\t//double variance = sampler.getVariance();\n\t\t//double stddev = Math.sqrt(variance);\n\t\tswitch (prOp) {\n\t\tcase 0: // 0=quantitative\n\t\t\treturn Double.valueOf(mean);\n\t\t\t//return new prism.Interval(mean - stddev, mean + stddev);\n\t\t\t//return Double.valueOf(stddev / mean); // noise\n\t\tcase -1: // -1=lower bound\n\t\t\tif (mean >= theta + width)\n\t\t\t\treturn Boolean.valueOf(true);\n\t\t\telse if (mean <= theta - width)\n\t\t\t\treturn Boolean.valueOf(false);\n\t\t\telse\n\t\t\t\tthrow new PrismException(\"Approximation is not precise enough to get a result\");\n\t\tcase 1: // 1=upper bound\n\t\t\tif (mean >= theta + width)\n\t\t\t\treturn Boolean.valueOf(false);\n\t\t\telse if (mean <= theta - width)\n\t\t\t\treturn Boolean.valueOf(true);\n\t\t\telse\n\t\t\t\tthrow new PrismException(\"Approximation is not precise enough to get a result\");\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown property type\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic Accuracy getResultAccuracy(Sampler sampler) throws PrismException\n\t{\n\t\tAccuracy accuracy;\n\t\t// Quantitative\n\t\tif (prOp == 0) {\n\t\t\taccuracy = new Accuracy(AccuracyLevel.PROBABLY_BOUNDED, width, AccuracyType.ABSOLUTE);\n\t\t}\n\t\t// Bounded (accuracy error bound is meaningless)\n\t\telse {\n\t\t\taccuracy = new Accuracy(AccuracyLevel.PROBABLY_BOUNDED, 0.0, AccuracyType.ABSOLUTE);\n\t\t}\n\t\taccuracy.setProbability(1.0 - confidence);\n\t\treturn accuracy;\n\t}\n\n\t@Override\n\tpublic String getResultExplanation(Sampler sampler) throws PrismException\n\t{\n\t\treturn \"confidence interval is \" + sampler.getMeanValue() + \" +/- \" + width + \", based on \" + (100.0 * (1.0 - confidence)) + \"% confidence level\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/CIconfidence.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.PrismException;\nimport simulator.sampler.Sampler;\nimport cern.jet.stat.Probability;\n\n/**\n * SimulationMethod class for the CI (\"confidence interval\") approach.\n * Case where 'confidence' is unknown parameter.\n */\npublic final class CIconfidence extends CIMethod\n{\n\t// Estimate of variance (from sampling)\n\tprivate double varEstimator;\n\n\tpublic CIconfidence(double width, int iterations)\n\t{\n\t\tthis.width = width;\n\t\tthis.numSamples = iterations;\n\t\tvarEstimator = 0.0;\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterAfterSim()\n\t{\n\t\t// Only compute for numSamples > 1\n\t\t// (Student's t-distribution only defined for v > 0)\n\t\tif (numSamples > 1) {\n\t\t\tdouble prob, x;\n\t\t\tx = width * Math.sqrt(numSamples / varEstimator);\n\t\t\t// Note: need to hard-code case x=Inf\n\t\t\tif (Double.isInfinite(x)) {\n\t\t\t\tprob = 1.0;\n\t\t\t}\n\t\t\t// (Note: Colt's studentT seems to break for v=1 so do manually)\n\t\t\telse if (numSamples - 1 > 1) {\n\t\t\t\tprob = Probability.studentT(x, numSamples - 1);\n\t\t\t} else {\n\t\t\t\t// PDF for v=1 is 1/2 + arctan(x)/pi\n\t\t\t\tprob = 0.5 + Math.atan(x) / Math.PI;\n\t\t\t}\n\t\t\tconfidence = 2 * (1.0 - prob);\n\t\t\tmissingParameterComputed = true;\n\t\t}\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tthrow new PrismException(\"Missing parameter not computed yet\");\n\t\treturn confidence;\n\t}\n\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"width=\" + width + \", confidence=\" + \"unknown\" + \", number of samples=\" + numSamples;\n\t\telse\n\t\t\treturn \"width=\" + width + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\n\t@Override\n\tpublic boolean shouldStopNow(int iters, Sampler sampler)\n\t{\n\t\tif (iters >= numSamples) {\n\t\t\t// Store final variance for confidence computation later\n\t\t\tvarEstimator = sampler.getVariance();\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic int getProgress(int iters, Sampler sampler)\n\t{\n\t\t// Easy: percentage of iters done so far\n\t\treturn ((10 * iters) / numSamples) * 10;\n\t}\n\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tCIconfidence m = new CIconfidence(width, numSamples);\n\t\t// Remaining CIMethod stuff\n\t\tm.confidence = confidence;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\t// Local stuff\n\t\tm.varEstimator = varEstimator;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/CIiterations.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.PrismException;\nimport simulator.sampler.Sampler;\nimport cern.jet.stat.Probability;\n\n/**\n * SimulationMethod class for the CI (\"confidence interval\") approach.\n * Case where 'iterations' (number of samples) is unknown parameter.\n */\npublic final class CIiterations extends CIMethod\n{\n\t// For reward properties, manually specified number of iterations\n\t// after which to conclude whether we are in S^2=0 case or not\n\tprivate int reqIterToConclude;\n\tprivate boolean reqIterToConcludeGiven;\n\t// For reward properties, maximum value of reward allows\n\t// automatic detection of whether we are in S^2=0 case or not\n\tprivate double maxReward;\n\t// Final number of iterations of sampling \n\tprivate int computedIterations;\n\t// Square of quantile\n\tprivate double squaredQuantile;\n\n\t// CONSTRUCTORS\n\n\t// probabilities, automatic\n\tpublic CIiterations(double confidenceLevel, double width)\n\t{\n\t\tthis.confidence = confidenceLevel;\n\t\tthis.width = width;\n\t\treqIterToConclude = 0;\n\t\treqIterToConcludeGiven = false;\n\t\tmaxReward = 1.0;\n\t\tcomputedIterations = 0;\n\t\tsquaredQuantile = 0.0;\n\t}\n\n\t// probabilities or rewards, manual\n\tpublic CIiterations(double confidenceLevel, double width, int reqIterToConclude)\n\t{\n\t\tthis.confidence = confidenceLevel;\n\t\tthis.width = width;\n\t\tthis.reqIterToConclude = reqIterToConclude;\n\t\treqIterToConcludeGiven = true;\n\t\tmaxReward = 1.0;\n\t\tcomputedIterations = 0;\n\t\tsquaredQuantile = 0.0;\n\t}\n\n\t// rewards, automatic\n\tpublic CIiterations(double confidenceLevel, double width, double maxReward)\n\t{\n\t\tthis.confidence = confidenceLevel;\n\t\tthis.width = width;\n\t\tthis.maxReward = maxReward;\n\t\treqIterToConclude = 0;\n\t\treqIterToConcludeGiven = false;\n\t\tcomputedIterations = 0;\n\t\tsquaredQuantile = 0.0;\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterAfterSim()\n\t{\n\t\t// Store iters (computed earlier)\n\t\tnumSamples = computedIterations;\n\t\tmissingParameterComputed = true;\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tthrow new PrismException(\"Missing parameter not computed yet\");\n\t\treturn numSamples;\n\t}\n\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"width=\" + width + \", confidence=\" + confidence + \", number of samples=unknown\";\n\t\telse\n\t\t\treturn \"width=\" + width + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\n\t@Override\n\tpublic boolean shouldStopNow(int iters, Sampler sampler)\n\t{\n\t\tdouble quantile = 0.0;\n\n\t\t// Need at least 2 iterations\n\t\t// (Student's t-distribution only defined for v > 0)\n\t\t// (and variance is always 0 for iters = 1)\n\t\tif (iters < 2)\n\t\t\treturn false;\n\n\t\t// We cannot conclude yet whether it is a \"S^2=0\" case or if the estimator is still valid (i.e. std error > 0)\n\t\tif (sampler.getVariance() <= 0.0) {\n\t\t\t// automatic\n\t\t\tif (!reqIterToConcludeGiven && maxReward / width > iters)\n\t\t\t\treturn false;\n\t\t\t// \"manual\"\n\t\t\tif (reqIterToConcludeGiven && reqIterToConclude > iters)\n\t\t\t\treturn false;\n\t\t}\n\n\t\t// See if required number of iterations for the expected confidence is reached yet\n\t\t// (Note: Colt's studentTinverse seems to break for v=1 so do manually)\n\t\tif (iters - 1 > 1) {\n\t\t\tquantile = Probability.studentTInverse(confidence, iters - 1);\n\t\t} else {\n\t\t\t// PDF for v=1 is 1/2 + arctan(x)/pi\n\t\t\t// Want x for pdf = 1-conf/2 \n\t\t\tquantile = Math.tan((0.5 - confidence / 2) * Math.PI);\n\t\t}\n\t\tsquaredQuantile = quantile * quantile;\n\t\tif (sampler.getVariance() > 0.0 && iters < sampler.getVariance() * squaredQuantile / (width * width))\n\t\t\treturn false;\n\n\t\t// Store final number of iterations (to compute missing parameter later)\n\t\tcomputedIterations = iters;\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic int getProgress(int iters, Sampler sampler)\n\t{\n\t\t// 2 iterations needed to compute variance of the sampler\n\t\tif (sampler.getVariance() <= 0.0 || iters < 2)\n\t\t\treturn 0;\n\t\treturn 10 * ((int) (100.0 * (double) (iters + 1) / (sampler.getVariance() * squaredQuantile / (width * width))) / 10);\n\t}\n\t\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tCIiterations m = new CIiterations(confidence, width);\n\t\t// Remaining CIMethod stuff\n\t\tm.numSamples = numSamples;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\t// Local stuff\n\t\tm.reqIterToConclude = reqIterToConclude;\n\t\tm.reqIterToConcludeGiven = reqIterToConcludeGiven;\n\t\tm.maxReward = maxReward;\n\t\tm.computedIterations = computedIterations;\n\t\tm.squaredQuantile = squaredQuantile;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/CIwidth.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport prism.Accuracy;\nimport prism.PrismException;\nimport simulator.sampler.Sampler;\nimport cern.jet.stat.Probability;\n\n/**\n * SimulationMethod class for the CI (\"confidence interval\") approach.\n * Case where 'width' is unknown parameter.\n */\npublic final class CIwidth extends CIMethod\n{\n\t// Estimate of variance (from sampling)\n\tprivate double varEstimator;\n\n\tpublic CIwidth(double confidenceLevel, int iterations)\n\t{\n\t\tthis.confidence = confidenceLevel;\n\t\tthis.numSamples = iterations;\n\t\tvarEstimator = 0.0;\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterAfterSim()\n\t{\n\t\tdouble quantile;\n\t\t// Only compute for numSamples > 1\n\t\t// (Student's t-distribution only defined for v > 0)\n\t\tif (numSamples > 1) {\n\t\t\t// (Note: Colt's studentTinverse seems to break for v=1 so do manually)\n\t\t\tif (numSamples - 1 > 1) {\n\t\t\t\tquantile = Probability.studentTInverse(confidence, numSamples - 1);\n\t\t\t} else {\n\t\t\t\t// PDF for v=1 is 1/2 + arctan(x)/pi\n\t\t\t\t// Want x for pdf = 1-conf/2 \n\t\t\t\tquantile = Math.tan((0.5 - confidence / 2) * Math.PI);\n\t\t\t}\n\t\t\twidth = quantile * Math.sqrt(varEstimator / numSamples);\n\t\t\tmissingParameterComputed = true;\n\t\t}\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tthrow new PrismException(\"Missing parameter not computed yet\");\n\t\treturn width;\n\t}\n\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"width=\" + \"unknown\" + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t\telse\n\t\t\treturn \"width=\" + width + \", confidence=\" + confidence + \", number of samples=\" + numSamples;\n\t}\n\n\t@Override\n\tpublic boolean shouldStopNow(int iters, Sampler sampler)\n\t{\n\t\tif (iters >= numSamples) {\n\t\t\t// Store final variance for confidence computation later\n\t\t\tvarEstimator = sampler.getVariance();\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic int getProgress(int iters, Sampler sampler)\n\t{\n\t\t// Easy: percentage of iters done so far\n\t\treturn ((10 * iters) / numSamples) * 10;\n\t}\n\n\t@Override\n\tpublic Object getResult(Sampler sampler) throws PrismException\n\t{\n\t\t// We may use 'width' to compute the result, so compute if necessary\n\t\t// (this should never happen)\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterAfterSim();\n\t\treturn super.getResult(sampler);\n\t}\n\n\t@Override\n\tpublic Accuracy getResultAccuracy(Sampler sampler) throws PrismException\n\t{\n\t\t// We may use 'width' to compute the result, so compute if necessary\n\t\t// (this should never happen)\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterAfterSim();\n\t\treturn super.getResultAccuracy(sampler);\n\t}\n\t\n\t@Override\n\tpublic String getResultExplanation(Sampler sampler) throws PrismException\n\t{\n\t\t// We may use 'width' to compute the result, so compute if necessary\n\t\t// (this should never happen)\n\t\tif (!missingParameterComputed)\n\t\t\tcomputeMissingParameterAfterSim();\n\t\treturn super.getResultExplanation(sampler);\n\t}\n\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tCIwidth m = new CIwidth(confidence, numSamples);\n\t\t// Remaining CIMethod stuff\n\t\tm.width = width;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\tm.prOp = prOp;\n\t\tm.theta = theta;\n\t\t// Local stuff\n\t\tm.varEstimator = varEstimator;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/SPRTMethod.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.RelOp;\nimport prism.Accuracy;\nimport prism.PrismException;\nimport prism.Accuracy.AccuracyLevel;\nimport prism.Accuracy.AccuracyType;\nimport simulator.sampler.Sampler;\nimport simulator.sampler.SamplerDouble;\n\n/**\n * SimulationMethod class for the SPRT (Sequential probability ratio test) approach,\n * as used by Younes/Simmons (CAV'02).\n * See also Younes/Kwiatkowska/Norman/Parker (TACAS'04) and Vincent Nimal's MSc thesis.\n */\npublic final class SPRTMethod extends SimulationMethod\n{\n\t// Hypothesis H0: probability/expectation >= theta + delta\n\t// Hypothesis H1: probability/expectation <= theta - delta\n\n\t// SPRT parameters\n\t// alpha: probability of type I error (false acceptance of H1)\n\tprivate double alpha;\n\t// beta: probability of type II error (false acceptance of H0)\n\tprivate double beta;\n\t// delta: half the width of the indifference region\n\tprivate double delta;\n\n\t// Probability/expectation for hypothesis 0/1 (used for likelihood ratio)\n\tprivate double p0;\n\tprivate double p1;\n\t// Decision: is H0 true?\n\tprivate boolean h0true;\n\t// Total number of iters (samples) needed\n\tprivate int computedIterations;\n\t// Is missing parameter (num iter) computed yet? \n\tprivate boolean missingParameterComputed;\n\n\t/**\n\t * Construct SimulationMethod for SPRT.\n\t * @param alpha Probability of type I error\n\t * @param beta Probability of type II error\n\t * @param delta Indifference parameter\n\t */\n\tpublic SPRTMethod(double alpha, double beta, double delta)\n\t{\n\t\tthis.alpha = alpha;\n\t\tthis.beta = beta;\n\t\tthis.delta = delta;\n\t\tthis.p0 = 0;\n\t\tthis.p1 = 0;\n\t\tthis.h0true = false;\n\t\tthis.computedIterations = 0;\n\t\tthis.missingParameterComputed = false;\n\t}\n\n\t@Override\n\tpublic String getName()\n\t{\n\t\treturn \"SPRT\";\n\t}\n\n\t@Override\n\tpublic String getFullName()\n\t{\n\t\treturn \"Sequential Probability Ratio Test\";\n\t}\n\n\t@Override\n\tpublic void reset()\n\t{\n\t\tthis.h0true = false;\n\t\tthis.missingParameterComputed = false;\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterBeforeSim() throws PrismException\n\t{\n\t\t// Nothing to do (num iters computed on-the-fly)\n\t}\n\n\t@Override\n\tpublic void setExpression(Expression expr) throws PrismException\n\t{\n\t\tExpression bound;\n\t\tRelOp relOp;\n\t\tdouble theta;\n\n\t\t// For P properties...\n\t\tif (expr instanceof ExpressionProb) {\n\t\t\tbound = ((ExpressionProb) expr).getProb();\n\t\t\trelOp = ((ExpressionProb) expr).getRelOp();\n\t\t}\n\t\t// For R properties...\n\t\telse if (expr instanceof ExpressionReward) {\n\t\t\tbound = ((ExpressionReward) expr).getReward();\n\t\t\trelOp = ((ExpressionReward) expr).getRelOp();\n\t\t}\n\t\t// Other (error)\n\t\telse {\n\t\t\tthrow new PrismException(\"Cannot approximate \" + expr + \" using simulation\");\n\t\t}\n\n\t\t// There must be a probability/reward bound to use SPRT\n\t\tif (bound == null) {\n\t\t\tthrow new PrismException(\"Cannot use SPRT on a quantitative (=?) property\");\n\t\t} else {\n\t\t\ttheta = bound.evaluateDouble();\n\t\t\t// Check of out-of-range errors\n\t\t\tif (theta - delta <= 0) {\n\t\t\t\tString s = \"Indifference for SPRT method (\" + delta + \") is too wide\";\n\t\t\t\ts += \" (bound \" + theta + \" is too close to 0)\";\n\t\t\t\tthrow new PrismException(s);\n\t\t\t}\n\t\t\tif (theta + delta > 1 && expr instanceof ExpressionProb) {\n\t\t\t\tString s = \"Indifference for SPRT method (\" + delta + \") is too wide\";\n\t\t\t\ts += \" (bound \" + theta + \" is too close to 1)\";\n\t\t\t\tthrow new PrismException(s);\n\t\t\t}\n\t\t\t// Set p0/p1 values for two hypotheses\n\t\t\t// Default case is that H0 means probability/reward >= theta + delta\n\t\t\tif (relOp.isLowerBound()) {\n\t\t\t\tp0 = theta + delta;\n\t\t\t\tp1 = theta - delta;\n\t\t\t}\n\t\t\t// If the bound is reversed, just swap p0/p1\n\t\t\telse {\n\t\t\t\tp0 = theta - delta;\n\t\t\t\tp1 = theta + delta;\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void computeMissingParameterAfterSim()\n\t{\n\t\t// Nothing to do (this is done in shouldStopNow)\n\t}\n\n\t@Override\n\tpublic Object getMissingParameter() throws PrismException\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\tthrow new PrismException(\"Missing parameter not computed yet\");\n\t\treturn computedIterations;\n\t}\n\n\t@Override\n\tpublic String getParametersString()\n\t{\n\t\tif (!missingParameterComputed)\n\t\t\treturn \"type I error=\" + alpha + \", type II error=\" + beta + \", delta=\" + delta + \", iterations=unknown\";\n\t\telse\n\t\t\treturn \"type I error=\" + alpha + \", type II error=\" + beta + \", delta=\" + delta + \", iterations=\" + computedIterations;\n\t}\n\n\t@Override\n\tpublic boolean shouldStopNow(int iters, Sampler sampler)\n\t{\n\t\t// Too soon\n\t\tif (iters < 2)\n\t\t\treturn false;\n\t\t// Get likelihood ratio; any problems, don't stop\n\t\tdouble likelihoodRatio;\n\t\ttry {\n\t\t\tlikelihoodRatio = sampler.getLikelihoodRatio(p1, p0);\n\t\t} catch (PrismException e) {\n\t\t\treturn false;\n\t\t}\n\t\tif (sampler instanceof SamplerDouble && (likelihoodRatio <= 0.0 || Double.isInfinite(likelihoodRatio)))\n\t\t\treturn false;\n\n\t\t// Accept H0\n\t\tif (likelihoodRatio <= beta / (1 - alpha)) {\n\t\t\th0true = true;\n\t\t\tmissingParameterComputed = true;\n\t\t\tcomputedIterations = iters;\n\t\t\treturn true;\n\t\t}\n\t\t// Accept H1\n\t\tif (likelihoodRatio >= (1 - beta) / alpha) {\n\t\t\th0true = false;\n\t\t\tmissingParameterComputed = true;\n\t\t\tcomputedIterations = iters;\n\t\t\treturn true;\n\t\t}\n\t\t// Not done yet\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic int getProgress(int iters, Sampler sampler)\n\t{\n\t\t// No good measure of progress unfortunately\n\t\treturn 0;\n\t}\n\n\t@Override\n\tpublic Object getResult(Sampler sampler) throws PrismException\n\t{\n\t\t// Is hypothesis H0 true?\n\t\treturn Boolean.valueOf(h0true);\n\t}\n\n\t@Override\n\tpublic Accuracy getResultAccuracy(Sampler sampler) throws PrismException\n\t{\n\t\t// Boolean result so accuracy error bound is meaningless\n\t\tAccuracy accuracy = new Accuracy(AccuracyLevel.PROBABLY_BOUNDED, 0.0, AccuracyType.ABSOLUTE);\n\t\t// TODO: handle case where alpha != beta (not used in PRISM atm)\n\t\taccuracy.setProbability(1.0 - alpha);\n\t\treturn accuracy;\n\t}\n\n\t@Override\n\tpublic String getResultExplanation(Sampler sampler){\n\t\treturn computedIterations + \" samples needed to decide property \" + h0true;\n\t}\n\t\n\t@Override\n\tpublic SimulationMethod clone()\n\t{\n\t\tSPRTMethod m = new SPRTMethod(alpha, beta, delta);\n\t\tm.p0 = p0;\n\t\tm.p1 = p1;\n\t\tm.h0true = h0true;\n\t\tm.computedIterations = computedIterations;\n\t\tm.missingParameterComputed = missingParameterComputed;\n\t\treturn m;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/method/SimulationMethod.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.method;\n\nimport parser.ast.Expression;\nimport prism.Accuracy;\nimport prism.PrismException;\nimport simulator.sampler.Sampler;\n\n/**\n * Classes to control simulation-based (approximate/statistical) model checking.\n */\npublic abstract class SimulationMethod implements Cloneable\n{\n\t/**\n\t * Get the (short) name of this method.\n\t */\n\tpublic abstract String getName();\n\t\n\t/**\n\t * Get the (full) name of this method.\n\t */\n\tpublic abstract String getFullName();\n\t\n\t/**\n\t * Reset the status of this method (but not values of any parameters that have\n\t * been set). Typically called if this instance is going to be re-used for\n\t * another run of approximate verification. \n\t */\n\tpublic abstract void reset();\n\n\t/**\n\t * Compute the missing parameter (typically there are multiple parameters,\n\t * one of which can be left free) *before* simulation. This is not always\n\t * possible - sometimes the parameter cannot be determined until afterwards.\n\t * This method may get called multiple times.\n\t * @throws PrismException if the parameters set so far are invalid.\n\t */\n\tpublic abstract void computeMissingParameterBeforeSim() throws PrismException;\n\n\t/**\n\t * Set the Expression (property) that simulation is going to be used to approximate.\n\t * It will be either an ExpressionProb or ExpressionReward object.\n\t * All constants should have already been defined and replaced.\n\t * @throws PrismException if property is inappropriate somehow for this method.\n\t */\n\tpublic abstract void setExpression(Expression expr) throws PrismException;\n\t\n\t/**\n\t * Compute the missing parameter (typically there are multiple parameters,\n\t * one of which can be left free) *after* simulation. (Sometimes the parameter\n\t * cannot be determined before simulation.)\n\t * This method may get called multiple times. \n\t */\n\tpublic abstract void computeMissingParameterAfterSim();\n\n\t/**\n\t * Get the missing (computed) parameter. If it has not already been computed and\n\t * this can be done *before* simulation, calling this method will trigger its computation.\n\t * If it can only be done *after*, an exception is thrown.\n\t * @return the computed missing parameter (as an Integer or Double object)\n\t * @throws PrismException if missing parameter is not and cannot be computed yet\n\t * or if the parameters set so far are invalid.\n\t */\n\tpublic abstract Object getMissingParameter() throws PrismException;\n\n\t/**\n\t * Get the parameters of the simulation (including the computed one) as a string.\n\t */\n\tpublic abstract String getParametersString();\n\n\t/**\n\t * Determine whether or not simulation should stop now, based on the stopping\n\t * criteria of this method, and the current state of simulation (the number of\n\t * iterations so far and the corresponding Sampler object).\n\t * Note: This method may continue being called after 'true' is returned,\n\t * e.g. if multiple properties are being simulated simultaneously.\n\t * @param iters The number of iterations (samples) done so far\n\t * @param sampler The Sampler object for this simulation\n\t * @return true if the simulation should stop, false otherwise\n\t */\n\tpublic abstract boolean shouldStopNow(int iters, Sampler sampler);\n\n\t/**\n\t * Get an indication of progress so far for simulation, i.e. an approximate value\n\t * for the percentage of work (samples) done. The value is a multiple of 10 in the range [0,100].\n\t * This estimate may not be linear (e.g. for CI/ACI where 'iterations' is computed).\n\t * It is assumed that this method is called *after* the call to shouldStopNow(...).\n\t * Note: The iteration count may exceed that dictated by this method,\n\t * e.g. if multiple properties are being simulated simultaneously.\n\t * TODO: check methods for this\n\t * @param iters The number of iterations (samples) done so far\n\t * @param sampler The Sampler object for this simulation\n\t */\n\tpublic abstract int getProgress(int iters, Sampler sampler);\n\n\t/**\n\t * Get the (approximate) result for the property that simulation is being used to approximate.\n\t * This should be a Boolean/Double for bounded/quantitative properties, respectively.\n\t * @param sampler The Sampler object for this simulation\n\t * @throws PrismException if we can't get a result for some reason.\n\t */\n\tpublic abstract Object getResult(Sampler sampler) throws PrismException;\n\t\n\t/**\n\t * Get the accuracy of the (approximate) result for the property that simulation is being used to approximate.\n\t * @param sampler The Sampler object for this simulation\n\t * @throws PrismException if we can't get a result for some reason.\n\t */\n\tpublic abstract Accuracy getResultAccuracy(Sampler sampler) throws PrismException;\n\t\n\t/**\n\t * Get an explanation for the result of the simulation as a string.\n\t * @param sampler The Sampler object for this simulation (e.g. to get mean)\n\t * @throws PrismException if we can't get a result for some reason.\n\t */\n\tpublic abstract String getResultExplanation(Sampler sampler) throws PrismException;\n\t\n\t@Override\n\tpublic abstract SimulationMethod clone();\n\t\n}\n"
  },
  {
    "path": "prism/src/simulator/method/package-info.java",
    "content": "/**\n * Implementation of approximate/statistical model checking techniques using the discrete event simulation engine.\n */\npackage simulator.method;\n"
  },
  {
    "path": "prism/src/simulator/package-info.java",
    "content": "/**\n * The discrete event simulation engine and approximate (statistical) model checking code.\n */\npackage simulator;\n"
  },
  {
    "path": "prism/src/simulator/sampler/Sampler.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport prism.ModelGenerator;\nimport prism.ModelInfo;\nimport prism.PrismException;\nimport prism.RewardGenerator;\nimport simulator.Path;\nimport simulator.method.SimulationMethod;\n\n/**\n * A Sampler determines values corresponding to a path property based on a sequence of simulation paths.\n * It determines the corresponding value for a single path, and also keeps track of the mean/variance\n * of this value over multiple traces. A Sampler can also be connected to a SimulationMethod object,\n * which is responsible for determining how many paths are required and how the final value is used.\n */\npublic abstract class Sampler\n{\n\tprotected boolean valueKnown;\n\tprotected SimulationMethod simulationMethod;\n\n\t/**\n\t * Is the current value of the sampler known, based on the path seen so far?\n\t */\n\tpublic boolean isCurrentValueKnown()\n\t{\n\t\treturn valueKnown;\n\t}\n\n\t/**\n\t * Does this sampler only require a bounded number of path steps?\n\t * i.e. is it safe to keep sampling beyond the maximum path length\n\t * even if this sampler does not know its value yet?\n\t * Conservatively, we assume \"no\"; override if required. \n\t */\n\tpublic boolean needsBoundedNumSteps()\n\t{\n\t\treturn false;\n\t}\n\n\t/**\n\t * Reset the current value of the sampler and whether it is known or not.\n\t */\n\tpublic abstract void reset();\n\n\t/**\n\t * Reset all statistics for the sampler.\n\t */\n\tpublic abstract void resetStats();\n\n\t/**\n\t * Update the current value of the sampler based on the current simulation path.\n\t * It is assumed that this is called at every step of the path.\n\t * We also need the transition list for the current (end) state of the path\n\t * to check if there is a deadlock or self-loop.\n\t * This returns true if the sampler's value becomes (or is already) known.\n\t */\n\tpublic abstract boolean update(Path path, ModelGenerator modelGen) throws PrismException;\n\n\t/**\n\t * Update the statistics for the sampler, assuming that the current path is finished.\n\t */\n\tpublic abstract void updateStats();\n\n\t/**\n\t * Get the current value of the sampler.\n\t */\n\tpublic abstract Object getCurrentValue();\n\n\t/**\n\t * Get the (estimated) mean value from the sampler, over all paths seen.\n\t */\n\tpublic abstract double getMeanValue();\n\n\t/**\n\t * Get the (estimated) variance from the sampler, over all paths seen.\n\t */\n\tpublic abstract double getVariance();\n\n\t/**\n\t * Get the ratio of the likelihoods for the distribution followed by the samples of this sampler\n\t * with the given parameters for hypotheses H1 and H0).\n\t * @param p1 Probability (or expectation) for hypothesis H1\n\t * @param p0 Probability (or expectation) for hypothesis H0\n\t */\n\tpublic abstract double getLikelihoodRatio(double p1, double p0) throws PrismException;\n\n\t/**\n\t * Set the attached SimulationMethod object.\n\t */\n\tpublic void setSimulationMethod(SimulationMethod simulationMethod)\n\t{\n\t\tthis.simulationMethod = simulationMethod;\n\t}\n\t\n\t/**\n\t * Get the attached SimulationMethod object.\n\t */\n\tpublic SimulationMethod getSimulationMethod()\n\t{\n\t\treturn simulationMethod;\n\t}\n\t\n\t/**\n\t * Get an explanation of the result for the attached SimulationMethod object.\n\t * @throws PrismException if we can't get a result for some reason.\n\t */\n\tpublic String getSimulationMethodResultExplanation() throws PrismException\n\t{\n\t\treturn simulationMethod.getResultExplanation(this);\n\t}\n\t\n\t// Static methods for sampler creation\n\n\t/**\n\t * Create a sampler for an expression (P=? or R=?).\n\t * Expression should contain no constants/formula/etc.\n\t * The model to which the property applies should also be specified. \n\t */\n\tpublic static Sampler createSampler(Expression expr, ModelInfo modelInfo, RewardGenerator rewardGen) throws PrismException\n\t{\n\t\tSampler sampler = null;\n\t\t// P=?\n\t\tif (expr instanceof ExpressionProb) {\n\t\t\tExpressionProb propProb = (ExpressionProb) expr;\n\t\t\t// Test whether this is a simple path formula (i.e. non-LTL)\n\t\t\tif (propProb.getExpression().isSimplePathFormula()) {\n\t\t\t\tsampler = createSamplerForProbPathPropertySimple(propProb.getExpression(), modelInfo);\n\t\t\t} else {\n\t\t\t\tthrow new PrismException(\"LTL-style path formulas are not supported by the simulator\");\n\t\t\t}\n\t\t}\n\t\t// R=?\n\t\telse if (expr instanceof ExpressionReward) {\n\t\t\tsampler = createSamplerForRewardProperty((ExpressionReward) expr, modelInfo, rewardGen);\n\t\t}\n\t\t// Neither\n\t\telse {\n\t\t\tthrow new PrismException(\"Can't create sampler for property \\\"\" + expr + \"\\\"\");\n\t\t}\n\t\treturn sampler;\n\t}\n\n\tprivate static SamplerBoolean createSamplerForProbPathPropertySimple(Expression expr, ModelInfo modelInfo) throws PrismException\n\t{\n\t\t// Negation/parentheses\n\t\tif (expr instanceof ExpressionUnaryOp) {\n\t\t\tExpressionUnaryOp exprUnary = (ExpressionUnaryOp) expr;\n\t\t\t// Parentheses\n\t\t\tif (exprUnary.getOperator() == ExpressionUnaryOp.PARENTH) {\n\t\t\t\t// Recurse\n\t\t\t\treturn createSamplerForProbPathPropertySimple(exprUnary.getOperand(), modelInfo);\n\t\t\t}\n\t\t\t// Negation\n\t\t\telse if (exprUnary.getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\t\t// Recurse, then negate meaning\n\t\t\t\tSamplerBoolean sampler = createSamplerForProbPathPropertySimple(exprUnary.getOperand(), modelInfo);\n\t\t\t\tsampler.negate();\n\t\t\t\treturn sampler;\n\t\t\t}\n\t\t}\n\t\t// Temporal operators\n\t\telse if (expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\t// Next\n\t\t\tif (exprTemp.getOperator() == ExpressionTemporal.P_X) {\n\t\t\t\treturn new SamplerNext(exprTemp);\n\t\t\t}\n\t\t\t// Until\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\t\tif (modelInfo.getModelType().continuousTime()) {\n\t\t\t\t\t\t// Continuous-time bounded until\n\t\t\t\t\t\treturn new SamplerBoundedUntilCont(exprTemp);\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// Discrete-time bounded until\n\t\t\t\t\t\treturn new SamplerBoundedUntilDisc(exprTemp);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// Unbounded until\n\t\t\t\t\treturn new SamplerUntil(exprTemp);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Anything else - convert to until and recurse\n\t\t\telse {\n\t\t\t\treturn createSamplerForProbPathPropertySimple(exprTemp.convertToUntilForm(), modelInfo);\n\t\t\t}\n\t\t}\n\n\t\tthrow new PrismException(\"Can't create sampler for property \\\"\" + expr + \"\\\"\");\n\t}\n\n\tprivate static SamplerDouble createSamplerForRewardProperty(ExpressionReward expr, ModelInfo modelInfo, RewardGenerator rewardGen) throws PrismException\n\t{\n\t\t// Extract reward structure index\n\t\tint rsi = expr.getRewardStructIndexByIndexObject(rewardGen, null);\n\t\t// Construct sampler based on type\n\t\tif (!(expr.getExpression() instanceof ExpressionTemporal)) {\n\t\t\t// catch complex co-safety reward specifications\n\t\t\tthrow new PrismException(\"Can't create sampler for property \\\"\" + expr + \"\\\"\");\n\t\t}\n\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr.getExpression();\n\t\tswitch (exprTemp.getOperator()) {\n\t\tcase ExpressionTemporal.R_C:\n\t\t\tif (modelInfo.getModelType().continuousTime()) {\n\t\t\t\t// Continuous-time cumulative reward\n\t\t\t\treturn new SamplerRewardCumulCont(exprTemp, rsi);\n\t\t\t} else {\n\t\t\t\t// Discrete-time cumulative reward\n\t\t\t\treturn new SamplerRewardCumulDisc(exprTemp, rsi);\n\t\t\t}\n\t\tcase ExpressionTemporal.R_I:\n\t\t\tif (modelInfo.getModelType().continuousTime()) {\n\t\t\t\t// Continuous-time instantaneous reward\n\t\t\t\treturn new SamplerRewardInstCont(exprTemp, rsi);\n\t\t\t} else {\n\t\t\t\t// Discrete-time instantaneous reward\n\t\t\t\treturn new SamplerRewardInstDisc(exprTemp, rsi);\n\t\t\t}\n\t\tcase ExpressionTemporal.P_F:\n\t\t\t// reachability reward\n\n\t\t\t// catch the case of a complex co-safety path formula\n\t\t\tif (!exprTemp.isSimplePathFormula()) {\n\t\t\t\tthrow new PrismException(\"Can't create sampler for property \\\"\" + exprTemp + \"\\\"\");\n\t\t\t}\n\n\t\t\treturn new SamplerRewardReach(exprTemp, rsi);\n\t\t}\n\n\t\tthrow new PrismException(\"Can't create sampler for property \\\"\" + expr + \"\\\"\");\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerBoolean.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\n/**\n * Samplers for properties that associate a simulation path with a Boolean value.\n */\npublic abstract class SamplerBoolean extends Sampler\n{\n\t// Value of current path\n\tprotected boolean value;\n\t// Whether the actual value should be the negation of 'value'\n\tprotected boolean negated = false;\n\t// Stats over all paths\n\tprotected int numSamples;\n\tprotected int numTrue;\n\n\t@Override\n\tpublic void reset()\n\t{\n\t\tvalueKnown = false;\n\t\tvalue = false;\n\t}\n\n\t@Override\n\tpublic void resetStats()\n\t{\n\t\tnumSamples = 0;\n\t\tnumTrue = 0;\n\t}\n\n\t@Override\n\tpublic abstract boolean update(Path path, ModelGenerator modelGen) throws PrismException;\n\n\t@Override\n\tpublic void updateStats()\n\t{\n\t\tnumSamples++;\n\t\t// XOR: value && !negated || !value && negated \n\t\tif (value != negated)\n\t\t\tnumTrue++;\n\t}\n\n\t@Override\n\tpublic Object getCurrentValue()\n\t{\n\t\t// XOR: value && !negated || !value && negated \n\t\treturn Boolean.valueOf(value != negated);\n\t}\n\n\t@Override\n\tpublic double getMeanValue()\n\t{\n\t\treturn numTrue / (double) numSamples;\n\t}\n\n\t@Override\n\tpublic double getVariance()\n\t{\n\t\t// Estimator to the variance (see p.24 of Vincent Nimal's MSc thesis)\n\t\tif (numSamples <= 1) {\n\t\t\treturn 0.0;\n\t\t} else {\n\t\t\treturn (numTrue * ((double) numSamples - numTrue) / ( numSamples * (numSamples - 1.0))); \n\t\t}\n\t\t\n\t\t// An alternative, below, would be to use the empirical mean\n\t\t// (this is not equivalent (or unbiased) but, asymptotically, is the same)\n\t\t//double mean = numTrue / (double) numSamples;\n\t\t//return mean * (1.0 - mean);\n\t}\n\n\t@Override\n\tpublic double getLikelihoodRatio(double p1, double p0) throws PrismException\n\t{\n\t\t// See Sec 5.3 of Vincent Nimal's MSc thesis for details\n\t\treturn Math.pow(p1 / p0, numTrue) * Math.pow((1 - p1) / (1 - p0), numSamples - numTrue);\n\t}\n\n\t/**\n\t * Negate the meaning of this sampler.\n\t */\n\tpublic boolean negate()\n\t{\n\t\treturn negated = !negated;\n\t}\n\n\t/**\n\t * Is this sampler negated?\n\t */\n\tpublic boolean getNegated()\n\t{\n\t\treturn negated;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerBoundedUntilCont.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport simulator.*;\nimport prism.*;\nimport parser.ast.*;\n\n/**\n * Construct a sampler for a (continuous-time) bounded until property.\n * Passed in ExpressionTemporal should be a formula of this type.\n * All constants should have already been evaluated/replaced.\n */\npublic class SamplerBoundedUntilCont extends SamplerBoolean\n{\n\tprivate Expression left;\n\tprivate Expression right;\n\tprivate double lb;\n\tprivate double ub;\n\n\t/**\n\t * Construct a sampler for a (continuous) time-bounded until formula.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerBoundedUntilCont(ExpressionTemporal expr) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.P_U)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\tleft = expr.getOperand1();\n\t\tright = expr.getOperand2();\n\n\t\tlb = expr.getLowerBound() == null ? 0.0 : expr.getLowerBound().evaluateDouble();\n\t\tif (lb < 0) {\n\t\t\tthrow new PrismException(\"Invalid lower bound \" + lb + \" in time-bounded until formula\");\n\t\t}\n\n\t\tif (expr.getUpperBound() == null) {\n\t\t\tub = Double.POSITIVE_INFINITY;\n\t\t} else {\n\t\t\tub = expr.getUpperBound().evaluateDouble();\n\t\t\tif (ub < 0 || (ub == 0 && expr.upperBoundIsStrict())) {\n\t\t\t\tString bound = (expr.upperBoundIsStrict() ? \"<\" : \"<=\") + ub;\n\t\t\t\tthrow new PrismException(\"Invalid upper bound \" + bound + \" in time-bounded until formula\");\n\t\t\t}\n\t\t\tif (ub < lb) {\n\t\t\t\tthrow new PrismException(\"Upper bound must exceed lower bound in time-bounded until formula\");\n\t\t\t}\n\t\t}\n\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\t\t\n\t\t// For continuous-time bounded until, we may need to look back at previous state.\n\t\t// So, treat first/subsequent calls to update() differently. \n\n\t\t// First path state:\n\t\tif (path.size() == 0) {\n\t\t\t// Initially, zero time has elapsed so to satisfy the until,\n\t\t\t// we need a lower time bound of 0 and the RHS to be satisfied \n\t\t\tif (lb == 0.0 && path.evaluateBooleanInCurrentState(right)) {\n\t\t\t\tvalueKnown = true;\n\t\t\t\tvalue = true;\n\t\t\t}\n\t\t\t// If LHS of the until violated, will never be true\n\t\t\telse if (!path.evaluateBooleanInCurrentState(left)) {\n\t\t\t\tvalueKnown = true;\n\t\t\t\tvalue = false;\n\t\t\t}\n\t\t}\n\t\t// Second and subsequent path states:\n\t\telse {\n\t\t\tdouble timeSoFar = path.getTotalTime();\n\t\t\t// As soon as upper time bound exceeded, we can decide\n\t\t\tif (timeSoFar > ub) {\n\t\t\t\t// Upper time bound was exceeded (for first time) in *previous* state\n\t\t\t\t// Had we reached the target (i.e. RHS of until)?\n\t\t\t\tif (path.evaluateBooleanInPreviousState(right)) {\n\t\t\t\t\tvalueKnown = true;\n\t\t\t\t\tvalue = true;\n\t\t\t\t}\n\t\t\t\t// If not, it's too late now\n\t\t\t\telse {\n\t\t\t\t\tvalueKnown = true;\n\t\t\t\t\tvalue = false;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Lower bound not yet exceeded but LHS of until violated\n\t\t\t// (no need to check RHS because too early)\n\t\t\telse if (timeSoFar <= lb) {\n\t\t\t\tif (!path.evaluateBooleanInCurrentState(left)) {\n\t\t\t\t\tvalueKnown = true;\n\t\t\t\t\tvalue = false;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Current time is between lower/upper bounds...\n\t\t\telse {\n\t\t\t\t// Have we reached the target (i.e. RHS of until)?\n\t\t\t\tif (path.evaluateBooleanInCurrentState(right)) {\n\t\t\t\t\tvalueKnown = true;\n\t\t\t\t\tvalue = true;\n\t\t\t\t}\n\t\t\t\t// Or, if not, have we violated the LHS of the until?\n\t\t\t\telse if (!path.evaluateBooleanInCurrentState(left)) {\n\t\t\t\t\tvalueKnown = true;\n\t\t\t\t\tvalue = false;\n\t\t\t\t}\n\t\t\t\t// If the lower bound was exceeded for the first time in the\n\t\t\t\t// previous state, and that one satisfies the RHS of the until...\n\t\t\t\telse if (timeSoFar - path.getTimeInPreviousState() <= lb) {\n\t\t\t\t\tif (path.evaluateBooleanInPreviousState(right)) {\n\t\t\t\t\t\tvalueKnown = true;\n\t\t\t\t\t\tvalue = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// Or, if we are now at a deadlock\n\t\t\t\telse if (modelGen != null && modelGen.isDeadlock()) {\n\t\t\t\t\tvalueKnown = true;\n\t\t\t\t\tvalue = false;\n\t\t\t\t}\n\t\t\t\t// Otherwise, don't know\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn valueKnown;\n\t}\n\t\n\t@Override\n\tpublic boolean needsBoundedNumSteps()\n\t{\n\t\t// Bounded if there is a non-finite upper-bound (although we don't know the exact num steps, just the time bound)\n\t\treturn ub < Double.POSITIVE_INFINITY;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerBoundedUntilDisc.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionTemporal;\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\npublic class SamplerBoundedUntilDisc extends SamplerBoolean\n{\n\tprivate Expression left;\n\tprivate Expression right;\n\tprivate int lb;\n\tprivate int ub;\n\tprivate boolean haveUpperBound;\n\n\t/**\n\t * Construct a sampler for a (discrete-time) bounded until property.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerBoundedUntilDisc(ExpressionTemporal expr) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.P_U)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\tleft = expr.getOperand1();\n\t\tright = expr.getOperand2();\n\t\t// Lower bound\n\t\tif (expr.getLowerBound() != null) {\n\t\t\tlb = expr.getLowerBound().evaluateInt();\n\t\t\tif (expr.lowerBoundIsStrict()) {\n\t\t\t\t// Convert to non-strict bound:  >lb  <=>  >=lb+1\n\t\t\t\tlb = lb + 1;\n\t\t\t}\n\t\t} else {\n\t\t\t// No lower bound\n\t\t\tlb = 0;\n\t\t}\n\t\tif (lb < 0) {\n\t\t\tthrow new PrismException(\"Invalid lower bound in \"+expr);\n\t\t}\n\t\t// Upper bound\n\t\tif (expr.getUpperBound() != null) {\n\t\t\thaveUpperBound = true;\n\t\t\tub = expr.getUpperBound().evaluateInt();\n\t\t\tif (expr.upperBoundIsStrict()) {\n\t\t\t\t// Convert to non-strict bound:  <ub  <=>  <=ub-1\n\t\t\t\tub = ub - 1;\n\t\t\t}\n\n\t\t\tif (ub < 0) {\n\t\t\t\tthrow new PrismException(\"Invalid upper bound in \"+expr);\n\t\t\t}\n\t\t} else {\n\t\t\t// No upper bound\n\t\t\thaveUpperBound = false;\n\t\t}\n\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\t\t\n\t\tlong pathSize = path.size();\n\t\t// Upper bound exceeded\n\t\tif (haveUpperBound && pathSize > ub) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = false;\n\t\t}\n\t\t// Lower bound not yet exceeded but LHS of until violated\n\t\t// (no need to check RHS because too early)\n\t\telse if (pathSize < lb) {\n\t\t\tif (!path.evaluateBooleanInCurrentState(left)) {\n\t\t\t\tvalueKnown = true;\n\t\t\t\tvalue = false;\n\t\t\t}\n\t\t}\n\t\t// Current time is between lower/upper bounds...\n\t\telse {\n\t\t\t// Have we reached the target (i.e. RHS of until)?\n\t\t\tif (path.evaluateBooleanInCurrentState(right)) {\n\t\t\t\tvalueKnown = true;\n\t\t\t\tvalue = true;\n\t\t\t}\n\t\t\t// Or, if not, have we violated the LHS of the until?\n\t\t\telse if (!path.evaluateBooleanInCurrentState(left)) {\n\t\t\t\tvalueKnown = true;\n\t\t\t\tvalue = false;\n\t\t\t}\n\t\t\t// Or, if we are now at a deadlock\n\t\t\telse if (modelGen != null && modelGen.isDeadlock()) {\n\t\t\t\tvalueKnown = true;\n\t\t\t\tvalue = false;\n\t\t\t}\n\t\t\t// Otherwise, don't know\n\t\t}\n\t\t\n\t\treturn valueKnown;\n\t}\n\t\n\t@Override\n\tpublic boolean needsBoundedNumSteps()\n\t{\n\t\t// Bounded if there is an upper bound\n\t\treturn haveUpperBound;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerDouble.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Marcin Copik <mcopik@gmail.com>\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\n/**\n * Samplers for properties that associate a simulation path with a real (double) value.\n */\npublic abstract class SamplerDouble extends Sampler\n{\n\t/** Value of current path */\n\tprotected double value;\n\t\n\t// Stats over all paths\n\t\n\t/** Number of samples so far */\n\tprotected int numSamples;\n\t/** Sum of values (used to compute mean) */\n\tprotected double valueSum;\n\t/** Correction value used when tracking variance */\n\tprotected double correctionTerm;\n\t/** Sum of values, each shifted by the correction term (see below) */\n\tprotected double valueSumShifted;\n\t/** Sum of squares of values, each shifted by the correction term (see below) */\n\tprotected double valueSumShiftedSq;\n\n\t/**\n\t * NB: In order to improve the numerical stability for the computation of variance,\n\t * we stored a shifted version of the mean, using a correction term that is an\n\t * estimate of the mean (for which, we just use the first value sampled). \n\t * Source: \"Algorithms for Computing the Sample Variance: Analysis and Recommendations\", T.F. Chan et al.\n\t */\n\t\n\t@Override\n\tpublic void reset()\n\t{\n\t\tvalueKnown = false;\n\t\tvalue = 0.0;\n\t}\n\n\t@Override\n\tpublic void resetStats()\n\t{\n\t\tvalueSum = 0.0;\n\t\tvalueSumShifted = 0.0;\n\t\tvalueSumShiftedSq = 0.0;\n\t\tnumSamples = 0;\n\t}\n\n\t@Override\n\tpublic abstract boolean update(Path path, ModelGenerator modelGen) throws PrismException;\n\n\t@Override\n\tpublic void updateStats()\n\t{\n\t\tif (numSamples == 0)\n\t\t\tcorrectionTerm = value;\n\t\tvalueSum += value;\n\t\tvalueSumShifted += value - correctionTerm;\n\t\tvalueSumShiftedSq += Math.pow(value - correctionTerm, 2);\n\t\tnumSamples++;\n\t}\n\n\t@Override\n\tpublic Object getCurrentValue()\n\t{\n\t\treturn Double.valueOf(value);\n\t}\n\n\t@Override\n\tpublic double getMeanValue()\n\t{\n\t\treturn valueSum / numSamples;\n\t}\n\n\t@Override\n\tpublic double getVariance()\n\t{\n\t\t// Return estimator to the variance\n\t\tif (numSamples <= 1) {\n\t\t\treturn 0.0;\n\t\t} else {\n\t\t\tdouble meanShifted = valueSumShifted / numSamples;\n\t\t\treturn (valueSumShiftedSq - numSamples * meanShifted * meanShifted) / (numSamples - 1.0);\n\t\t}\n\t\t\n\t\t// Note:\n\t\t// * As explained at the top of this class, variance is computed using\n\t\t//   a shifted version of the mean to improve numerical stability\n\t\t// * We divide by numSamples -1. An alternative would be to use the empirical mean, i.e. dividing by numSamples. \n\t\t//   This is not equivalent (or unbiased) but, asymptotically, is the same.\n\t\t//   See p.24 of: Vincent Nimal, \"Statistical Approaches for Probabilistic Model Checking\", MSc Thesis\n\t}\n\n\t@Override\n\tpublic double getLikelihoodRatio(double p1, double p0) throws PrismException\n\t{\n\t\t// For details, see Sec 6.3 of: Vincent Nimal, \"Statistical Approaches for Probabilistic Model Checking\", MSc Thesis\n\t\t// (in which mu1=p1 and mu0=p0)\n\t\tif (numSamples <= 1)\n\t\t\treturn 0.0;\n\t\tif (valueSumShiftedSq == 0)\n\t\t\tthrow new PrismException(\"Cannot compute likelihood ratio with null variance\");\n\t\t// Compute maximum likelihood estimator of variance\n\t\tdouble MLE = valueSumShiftedSq / numSamples - (valueSumShifted * valueSumShifted) / numSamples / numSamples;\n\t\tdouble lr = (-1 / (2 * MLE)) * (numSamples * (p1 * p1 - p0 * p0) - 2 * valueSum * (p1 - p0));\n\t\tif (Double.isNaN(lr)) {\n\t\t\tthrow new PrismException(\"Error computing likelihood ratio\");\n\t\t}\n\t\treturn Math.exp(lr);\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerNext.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionTemporal;\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\npublic class SamplerNext extends SamplerBoolean\n{\n\tprivate Expression target;\n\n\t/**\n\t * Construct a sampler for a \"next\" property.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerNext(ExpressionTemporal expr) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.P_X)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\ttarget = expr.getOperand2();\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\t\t\n\t\t// X \"target\" is true iff state 1 satisfies \"target\"\n\t\tif (path.size() == 1) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = path.evaluateBooleanInCurrentState(target);\n\t\t}\n\t\t// Nothing else to do: if path size is 0, can't decide;\n\t\t// if path size > 1 (should never happen), nothing changes\n\t\t\n\t\treturn valueKnown;\n\t}\n\t\n\t@Override\n\tpublic boolean needsBoundedNumSteps()\n\t{\n\t\t// Always bounded\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerRewardCumulCont.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.ExpressionTemporal;\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\npublic class SamplerRewardCumulCont extends SamplerDouble\n{\n\tprivate double timeBound;\n\tprivate int rewardStructIndex;\n\n\t/**\n\t * Construct a sampler for a (continuous-time) cumulative reward property.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * Reward structure index should also be specified.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerRewardCumulCont(ExpressionTemporal expr, int rewardStructIndex) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.R_C)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\t\n\t\ttimeBound = expr.getUpperBound().evaluateDouble();\n\t\tthis.rewardStructIndex = rewardStructIndex;\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\t\t\n\t\t// As soon as time bound exceeded, compute reward total\n\t\tif (path.getTotalTime() >= timeBound) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = path.getTotalCumulativeReward(rewardStructIndex);\n\t\t\t// Compute excess time, i.e. how long ago time bound was reached\n\t\t\tdouble excessTime = path.getTotalTime() - timeBound;\n\t\t\t// If this is > 0 (very likely, unless time bound = 0),\n\t\t\t// need to subtract reward accumulated in excess time and transition reward\n\t\t\t// Note that this cannot be the case for the first state of path,\n\t\t\t// so the call to getTimeInPreviousState() is safe.\n\t\t\tif (excessTime > 0) {\n\t\t\t\t// Note: Time so far > 0 so cannot be first state,\n\t\t\t\t// so safe to look at previous state.\n\t\t\t\tvalue -= path.getPreviousStateReward(rewardStructIndex) * excessTime;\n\t\t\t\tvalue -= path.getPreviousTransitionReward(rewardStructIndex);\n\t\t\t}\n\t\t}\n\t\t// Or, if we are now at a deadlock\n\t\telse if (modelGen != null && modelGen.isDeadlock()) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = path.getTotalCumulativeReward(rewardStructIndex);\n\t\t\t// Compute remaining time, i.e. how long left until time bound will be reached\n\t\t\tdouble remainingTime = timeBound - path.getTotalTime();\n\t\t\tvalue += path.getCurrentStateReward(rewardStructIndex) * remainingTime;\n\t\t}\n\t\t\n\t\treturn valueKnown;\n\t}\n\t\n\t@Override\n\tpublic boolean needsBoundedNumSteps()\n\t{\n\t\t// Always bounded (although we don't know the exact num steps, just the time bound)\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerRewardCumulDisc.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.ExpressionTemporal;\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\npublic class SamplerRewardCumulDisc extends SamplerDouble\n{\n\tprivate int timeBound;\n\tprivate int rewardStructIndex;\n\n\t/**\n\t * Construct a sampler for a (discrete-time) cumulative reward property.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * Reward structure index should also be specified.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerRewardCumulDisc(ExpressionTemporal expr, int rewardStructIndex) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.R_C)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\t\n\t\ttimeBound = expr.getUpperBound().evaluateInt();\n\t\tthis.rewardStructIndex = rewardStructIndex;\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\t\t\n\t\t// As soon as time bound reached, store current reward total\n\t\tif (path.size() == timeBound) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = path.getTotalCumulativeReward(rewardStructIndex);\n\t\t}\n\t\t\n\t\treturn valueKnown;\n\t}\n\t\n\t@Override\n\tpublic boolean needsBoundedNumSteps()\n\t{\n\t\t// Always bounded\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerRewardInstCont.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.ExpressionTemporal;\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\npublic class SamplerRewardInstCont extends SamplerDouble\n{\n\tprivate double time;\n\tprivate int rewardStructIndex;\n\n\t/**\n\t * Construct a sampler for a (continuous-time) instantaneous reward property.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * Reward structure index should also be specified.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerRewardInstCont(ExpressionTemporal expr, int rewardStructIndex) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.R_I)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\ttime = expr.getUpperBound().evaluateDouble();\n\t\tthis.rewardStructIndex = rewardStructIndex;\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\t\t\n\t\t// As soon as time bound exceeded, compute reward\n\t\tif (path.getTotalTime() >= time) {\n\t\t\tvalueKnown = true;\n\t\t\t// Time bound was exceeded in either previous or current state\n\t\t\t// (unless the time bound is 0, the latter is very unlikely)\n\t\t\tif (path.getTotalTime() > time) {\n\t\t\t\t// Note: Time so far > 0 so cannot be first state,\n\t\t\t\t// so safe to look at previous state.\n\t\t\t\tvalue = path.getPreviousStateReward(rewardStructIndex);\n\t\t\t} else {\n\t\t\t\tvalue = path.getCurrentStateReward(rewardStructIndex);\n\t\t\t}\n\t\t}\n\t\t// Or, if we are now at a deadlock\n\t\telse if (modelGen != null && modelGen.isDeadlock()) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = path.getCurrentStateReward(rewardStructIndex);\n\t\t}\n\t\t// Otherwise, don't know\n\t\t\n\t\treturn valueKnown;\n\t}\n\t\n\t@Override\n\tpublic boolean needsBoundedNumSteps()\n\t{\n\t\t// Always bounded (although we don't know the exact num steps, just the time bound)\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerRewardInstDisc.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.ExpressionTemporal;\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\npublic class SamplerRewardInstDisc extends SamplerDouble\n{\n\tprivate int time;\n\tprivate int rewardStructIndex;\n\n\t/**\n\t * Construct a sampler for a (discrete-time) instantaneous reward property.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * Reward structure index should also be specified.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerRewardInstDisc(ExpressionTemporal expr, int rewardStructIndex) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.R_I)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\ttime = expr.getUpperBound().evaluateInt();\n\t\tthis.rewardStructIndex = rewardStructIndex;\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\t\t\n\t\t// As soon as time bound reached, store current state reward\n\t\tif (path.size() == time) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = path.getCurrentStateReward(rewardStructIndex);\n\t\t}\n\t\t// Or, if we are now at a deadlock\n\t\telse if (modelGen != null && modelGen.isDeadlock()) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = path.getCurrentStateReward(rewardStructIndex);\n\t\t}\n\t\t// Otherwise, don't know\n\t\t\n\t\treturn valueKnown;\n\t}\n\t\n\t@Override\n\tpublic boolean needsBoundedNumSteps()\n\t{\n\t\t// Always bounded\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerRewardReach.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionTemporal;\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\npublic class SamplerRewardReach extends SamplerDouble\n{\n\tprivate Expression target;\n\tprivate int rewardStructIndex;\n\n\t/**\n\t * Construct a sampler for a reachability reward property.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * Reward structure index should also be specified.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerRewardReach(ExpressionTemporal expr, int rewardStructIndex) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.P_F)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\ttarget = expr.getOperand2();\n\t\tthis.rewardStructIndex = rewardStructIndex;\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\t\tif (path.evaluateBooleanInCurrentState(target)) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = path.getTotalCumulativeReward(rewardStructIndex);\n\t\t}\n\t\t\n\t\treturn valueKnown;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/SamplerUntil.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage simulator.sampler;\n\nimport parser.ast.Expression;\nimport parser.ast.ExpressionTemporal;\nimport prism.ModelGenerator;\nimport prism.PrismException;\nimport simulator.Path;\n\npublic class SamplerUntil extends SamplerBoolean\n{\n\tprivate Expression left;\n\tprivate Expression right;\n\n\t/**\n\t * Construct a sampler for a (unbounded) until property.\n\t * Passed in ExpressionTemporal should be a property of this type.\n\t * All constants should have already been evaluated/replaced.\n\t */\n\tpublic SamplerUntil(ExpressionTemporal expr) throws PrismException\n\t{\n\t\t// Make sure expression is of the correct type\n\t\t// Then extract other required info\n\t\tif (expr.getOperator() != ExpressionTemporal.P_U)\n\t\t\tthrow new PrismException(\"Error creating Sampler\");\n\t\tleft = expr.getOperand1();\n\t\tright = expr.getOperand2();\n\t\t// Initialise sampler info\n\t\treset();\n\t\tresetStats();\n\t}\n\n\t@Override\n\tpublic boolean update(Path path, ModelGenerator modelGen) throws PrismException\n\t{\n\t\t// If the answer is already known we should do nothing\n\t\tif (valueKnown)\n\t\t\treturn true;\n\n\t\t// Have we reached the target (i.e. RHS of until)?\n\t\tif (path.evaluateBooleanInCurrentState(right)) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = true;\n\t\t}\n\t\t// Or, if not, have we violated the LHS of the until?\n\t\telse if (!path.evaluateBooleanInCurrentState(left)) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = false;\n\t\t}\n\t\t// Or, if we are now at a deadlock/self-loop\n\t\telse if (modelGen != null && (modelGen.isDeadlock() || path.isLooping())) {\n\t\t//else if (transList != null && (transList.isDeadlock() || transList.isDeterministicSelfLoop(currentState))) {\n\t\t\tvalueKnown = true;\n\t\t\tvalue = false;\n\t\t}\n\t\t// Otherwise, don't know\n\n\t\treturn valueKnown;\n\t}\n}\n"
  },
  {
    "path": "prism/src/simulator/sampler/package-info.java",
    "content": "/**\n * Code for checking properties against simulation paths generated by discrete event simulation engine.\n */\npackage simulator.sampler;\n"
  },
  {
    "path": "prism/src/sparse/NDSparseMatrix.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage sparse;\n\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport odd.ODDNode;\nimport prism.PrismException;\n\n/**\n * A wrapper class around a native sparse representation of an MDP.\n */\npublic class NDSparseMatrix\n{\n\t// JNI methods\n\t\n\tprivate static native int PS_NDGetActionIndex(long ptr, int s, int i);\n\n\tprivate static native long PS_BuildNDSparseMatrix(long trans, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv);\n\n\tprivate static native long PS_BuildSubNDSparseMatrix(long trans, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long rewards);\n\n\tprivate static native void PS_AddActionsToNDSparseMatrix(long trans, long trans_actions, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long ndsm);\n\t\n\tprivate static native void PS_DeleteNDSparseMatrix(long ptr_matrix);\n\n\tstatic {\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t} catch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t/** Pointer to C++ data structure. **/\n\tprivate long ptr;\n\n\t/**\n\t * Constructor (from a C++ pointer).\n\t */\n\tprivate NDSparseMatrix(long ptr)\n\t{\n\t\tthis.ptr = ptr;\n\t}\n\n\t/**\n\t * Returns the pointer to the native C++ data structure.\n\t */\n\tpublic long getPtr()\n\t{\n\t\treturn ptr;\n\t}\n\n\t/**\n\t * Get the index of the action label (if any) for choice {@code i} of state {@code s}.\n\t */\n\tpublic int getActionIndex(int s, int i)\n\t{\n\t\treturn PS_NDGetActionIndex(ptr, s, i);\n\t}\n\t\n\t/**\n\t * Deletes the matrix.\n\t */\n\tpublic void delete()\n\t{\n\t\tPS_DeleteNDSparseMatrix(this.ptr);\n\t}\n\n\t// Static methods to construct NDSparseMatrix objects\n\n\tpublic static NDSparseMatrix BuildNDSparseMatrix(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet) throws PrismException\n\t{\n\t\tlong ptr = PS_BuildNDSparseMatrix(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n());\n\t\tif (ptr == 0)\n\t\t\tthrow new PrismException(PrismSparse.getErrorMessage());\n\t\treturn new NDSparseMatrix(ptr);\n\t}\n\n\tpublic static NDSparseMatrix BuildSubNDSparseMatrix(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode rewards)\n\t\t\tthrows PrismException\n\t{\n\t\tlong ptr = PS_BuildSubNDSparseMatrix(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), rewards.ptr());\n\t\tif (ptr == 0)\n\t\t\tthrow new PrismException(PrismSparse.getErrorMessage());\n\t\treturn new NDSparseMatrix(ptr);\n\t}\n\n\tpublic static void AddActionsToNDSparseMatrix(JDDNode trans, JDDNode transActions, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, NDSparseMatrix ndsm) throws PrismException\n\t{\n\t\tPS_AddActionsToNDSparseMatrix(trans.ptr(), transActions.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), ndsm.getPtr());\n\t}\n}\n"
  },
  {
    "path": "prism/src/sparse/PS_ExportMC.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportMC\n  (JNIEnv *, jclass, jlongArray, jstring, jlong, jint, jlong, jint, jlong, jint, jstring, jint);\n\n\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportMC\n(\nJNIEnv *env,\njclass cls,\njlongArray __jlongpointerArray tpa,\t// actions\njobject synchs,\njstring na,\t\t// matrix name\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer od,\t// odd\njint et,\t\t// export type\njstring fn\t\t// filename\n)\n{\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tODDNode *odd = jlong_to_ODDNode(od);\n\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\t// action info\n\tjstring *action_names_jstrings = NULL;\n\tconst char** action_names = NULL;\n\tint num_actions;\n\t// model stats\n\tint n, nnz, i, j, l, h, r, c, a;\n\tdouble d;\n\tconst char *export_name;\n\t\n\tDdNode **trans_per_action;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// store export info\n\tif (!store_export_info(et, fn, env)) return -1;\n\texport_name = na ? env->GetStringUTFChars(na, 0) : \"M\";\n\t\n\t// extract matrices for each action\n    int num_matrices = env->GetArrayLength(tpa);\n    jlong *tpa_longs = env->GetLongArrayElements(tpa, NULL);\n    trans_per_action = new DdNode*[num_matrices];\n    for (a = 0; a < num_matrices; a++) {\n\t    trans_per_action[a] = jlong_to_DdNode(tpa_longs[a]);\n    }\n    env->ReleaseLongArrayElements(tpa, tpa_longs, 0);\n\t\n\t// build sparse matrix\n\trmsm = build_rm_sparse_matrix_act(ddman, trans_per_action, num_matrices, rvars, cvars, num_rvars, odd);\n\tn = rmsm->n;\n\tnnz = rmsm->nnz;\n\t\n\t// also extract list of action names\n\tif (synchs != NULL) {\n\t\tget_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n\t}\n\t\n\t// print file header\n\tswitch (export_type) {\n\tcase EXPORT_PLAIN: export_string(\"%d %d\\n\", n, nnz); break;\n\tcase EXPORT_MATLAB: export_string(\"%s = sparse(%d,%d);\\n\", export_name, n, n); break;\n\tcase EXPORT_DOT: case EXPORT_DOT_STATES: export_string(\"digraph %s {\\nnode [shape=box];\\n\", export_name); break;\n\tcase EXPORT_MRMC: export_string(\"STATES %d\\nTRANSITIONS %d\\n\", n, nnz); break;\n\tcase EXPORT_ROWS: export_string(\"%d %d\\n\", n, nnz); break;\n\t}\n\t\n\t// print main part of file\n\t// first get data structure info\n\tdouble *non_zeros;\n\tunsigned char *row_counts;\n\tint *row_starts;\n\tbool use_counts;\n\tunsigned int *cols;\n\tunsigned int *actions;\n\tdouble *dist;\n\tint dist_shift;\n\tint dist_mask;\n\tnon_zeros = rmsm->non_zeros;\n\trow_counts = rmsm->row_counts;\n\trow_starts = (int *)rmsm->row_counts;\n\tuse_counts = rmsm->use_counts;\n\tcols = rmsm->cols;\n\tactions = rmsm->actions;\n\t// then traverse data structure\n\th = 0;\n\tfor (i = 0; i < n; i++) {\n\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\telse { l = h; h += row_counts[i]; }\n\t\tif (export_type == EXPORT_ROWS) export_string(\"%d\", i);\n\t\tfor (j = l; j < h; j++) {\n\t\t\tr = i;\n\t\t\tc = cols[j];\n\t\t\td = non_zeros[j];\n\t\t\tswitch (export_type) {\n\t\t\tcase EXPORT_PLAIN:\n\t\t\t\texport_string(\"%d %d %.*g\", r, c, export_model_precision, d);\n\t\t\t\tif (actions != NULL && actions[j]>0) export_string(\" %s\", action_names[actions[j]-1]);\n\t\t\t\texport_string(\"\\n\");\n\t\t\t\tbreak;\n\t\t\tcase EXPORT_MATLAB: export_string(\"%s(%d,%d)=%.*g;\\n\", export_name, r+1, c+1, export_model_precision, d); break;\n\t\t\tcase EXPORT_DOT: case EXPORT_DOT_STATES:\n\t\t\t\texport_string(\"%d -> %d [ label=\\\"%.*g\", r, c, export_model_precision, d);\n\t\t\t\tif (actions != NULL && actions[j]>0) export_string(\":%s\", (actions[j]>0?action_names[actions[j]-1]:\"\"));\n\t\t\t\texport_string(\"\\\" ];\\n\", r, c, export_model_precision, d);\n\t\t\t\tbreak;\n\t\t\tcase EXPORT_MRMC: export_string(\"%d %d %.*g\\n\", r+1, c+1, export_model_precision, d); break;\n\t\t\tcase EXPORT_ROWS: export_string(\" %.*g:%d\", export_model_precision, d, c); break;\n\t\t\t}\n\t\t}\n\t\tif (export_type == EXPORT_ROWS) export_string(\"\\n\");\n\t}\n\t\n\t// print file footer\n\tswitch (export_type) {\n\t// Note: no footer for EXPORT_DOT_STATES\n\tcase EXPORT_DOT: export_string(\"}\\n\"); break;\n\t}\n\t\n\t// close file, etc.\n\tif (export_file) fclose(export_file);\n\tif (na) env->ReleaseStringUTFChars(na, export_name);\n\t\n\t// catch exceptions: return (undocumented) error code for memout\n\t} catch (std::bad_alloc e) {\n\t\treturn -2;\n\t}\n\t\n\t// free memory\n\tif (trans_per_action) delete trans_per_action;\n\tif (rmsm) delete rmsm;\n\t//if (action_names != NULL) release_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n\t\n\treturn 0;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ExportMDP.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportMDP\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer m,\t// mdp\njlong __jlongpointer ta,\t// trans action labels\njobject synchs,\njstring na, \t\t// mdp name\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer od,\t// odd\njint et,\t\t// export type\njstring fn\t\t// filename\n)\n{\n\tDdNode *mdp = jlong_to_DdNode(m);\t\t\t\t// mdp\n\tDdNode *trans_actions = jlong_to_DdNode(ta);\t// trans action labels\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tODDNode *odd = jlong_to_ODDNode(od);\n\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL;\n\t// action info\n\tjstring *action_names_jstrings = NULL;\n\tconst char** action_names = NULL;\n\tint num_actions;\n\t// model stats\n\tint i, j, k, n, nc, l1, h1, l2, h2;\n\tlong nnz;\n\tconst char *export_name;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// store export info\n\tif (!store_export_info(et, fn, env)) return -1;\n\texport_name = na ? env->GetStringUTFChars(na, 0) : \"S\";\n\t\n\t// build sparse matrix\n\tndsm = build_nd_sparse_matrix(ddman, mdp, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tn = ndsm->n;\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\t\n\t// if needed, and if info is available, build a vector of action indices for the mdp\n\t// also extract list of action names\n\tif (true && trans_actions != NULL) {\n\t\tbuild_nd_action_vector(ddman, mdp, trans_actions, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\tget_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n\t}\n\t\n\t// print file header\n\tswitch (export_type) {\n\tcase EXPORT_PLAIN: export_string(\"%d %d %ld\\n\", n, nc, nnz); break;\n\tcase EXPORT_MATLAB: for (i = 0; i < ndsm->k; i++) export_string(\"%s%d = sparse(%d,%d);\\n\", export_name, i+1, n, n); break;\n\tcase EXPORT_DOT: case EXPORT_DOT_STATES: export_string(\"digraph %s {\\nnode [shape=box];\\n\", export_name); break;\n\tcase EXPORT_ROWS: export_string(\"%d %d %ld\\n\", n, nc, nnz); break;\n\t}\n\t\n\t// print main part of file\n\t// first get data structure info\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\tint *actions = ndsm->actions;\n\t// then traverse data structure\n\th1 = h2 = 0;\n\tfor (i = 0; i < n; i++) {\n\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\tif (export_type == EXPORT_ROWS) export_string(\"%d\", i);\n\t\t\telse if (export_type == EXPORT_DOT || export_type == EXPORT_DOT_STATES) {\n\t\t\t\texport_string(\"%d -> n%d_%d [ arrowhead=none,label=\\\"%d\", i, i, j-l1, j-l1);\n\t\t\t\tif (actions != NULL) export_string(\":%s\", (actions[j]>0?action_names[actions[j]-1]:\"\"));\n\t\t\t\texport_string(\"\\\" ];\\n\");\n\t\t\t\texport_string(\"n%d_%d [ shape=point,width=0.1,height=0.1,label=\\\"\\\" ];\\n\", i, j-l1);\n\t\t\t}\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\tswitch (export_type) {\n\t\t\t\tcase EXPORT_PLAIN:\n\t\t\t\t\texport_string(\"%d %d %d %.*g\", i, j-l1, cols[k], export_model_precision, non_zeros[k]);\n\t\t\t\t\tif (actions != NULL && actions[j]>0) export_string(\" %s\", action_names[actions[j]-1]);\n\t\t\t\t\texport_string(\"\\n\");\n\t\t\t\t\tbreak;\n\t\t\t\tcase EXPORT_MATLAB: export_string(\"%s%d(%d,%d)=%.*g;\\n\", export_name, j-l1+1, i+1, cols[k]+1, export_model_precision, non_zeros[k]); break;\n\t\t\t\tcase EXPORT_DOT: case EXPORT_DOT_STATES: export_string(\"n%d_%d -> %d [ label=\\\"%.*g\\\" ];\\n\", i, j-l1, cols[k], export_model_precision, non_zeros[k]); break;\n\t\t\t\tcase EXPORT_ROWS: export_string(\" %.*g:%d\", export_model_precision, non_zeros[k], cols[k]); break;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (export_type == EXPORT_ROWS && actions != NULL) export_string(\" %s\", (actions[j]>0?action_names[actions[j]-1]:\"\"));\n\t\t\tif (export_type == EXPORT_ROWS) export_string(\"\\n\");\n\t\t}\n\t}\n\t\n\t// print file footer\n\tswitch (export_type) {\n\t// Note: no footer for EXPORT_DOT_STATES\n\tcase EXPORT_DOT: export_string(\"}\\n\"); break;\n\t}\n\t\n\t// close file, etc.\n\tif (export_file) fclose(export_file);\n\tif (na) env->ReleaseStringUTFChars(na, export_name);\n\t\n\t// catch exceptions: return (undocumented) error code for memout\n\t} catch (std::bad_alloc e) {\n\t\treturn -2;\n\t}\n\t\n\t// free memory\n\tif (ndsm) delete ndsm;\n\t//if (action_names != NULL) release_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n\t\n\treturn 0;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ExportMatrix.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportMatrix\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer m,\t// matrix\njstring na,\t\t// matrix name\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer od,\t// odd\njint et,\t\t// export type\njstring fn,\t\t// filename\njstring rsn,    // reward struct name\njboolean neh    // noexportheaders\n)\n{\n\tDdNode *matrix = jlong_to_DdNode(m);\t\t// matrix\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tODDNode *odd = jlong_to_ODDNode(od);\n\n\t// flags\n\tbool compact_tr;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// model stats\n\tint n, nnz, i, j, l, h, r, c;\n\tdouble d;\n\tconst char *export_name;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// store export info\n\tif (!store_export_info(et, fn, env)) return -1;\n\texport_name = na ? env->GetStringUTFChars(na, 0) : \"M\";\n\t\n\t// build sparse matrix\n\t// if requested, try and build a \"compact\" version\n\tcompact_tr = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, matrix, rvars, cvars, num_rvars, odd);\n\tif (cmsrsm != NULL) {\n\t\tn = cmsrsm->n;\n\t\tnnz = cmsrsm->nnz;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_tr = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, matrix, rvars, cvars, num_rvars, odd);\n\t\tn = rmsm->n;\n\t\tnnz = rmsm->nnz;\n\t}\n\t\n\t// print file header\n\tif (export_type == EXPORT_PLAIN && !neh) {\n\t\texport_string(\"# Reward structure\");\n\t\tif (env->GetStringUTFLength(rsn) > 0) {\n\t\t\tconst char *header = env->GetStringUTFChars(rsn,0);\n\t\t\texport_string(\" \\\"%s\\\"\", header);\n\t\t\tenv->ReleaseStringUTFChars(rsn, header);\n\t\t}\n\t\texport_string(\"\\n\");\n\t\texport_string(\"# Transition rewards\\n\");\n\t}\n\tswitch (export_type) {\n\tcase EXPORT_PLAIN: export_string(\"%d %d\\n\", n, nnz); break;\n\tcase EXPORT_MATLAB: export_string(\"%s = sparse(%d,%d);\\n\", export_name, n, n); break;\n\tcase EXPORT_DOT: case EXPORT_DOT_STATES: export_string(\"digraph %s {\\nnode [shape=box];\\n\", export_name); break;\n\tcase EXPORT_MRMC: export_string(\"STATES %d\\nTRANSITIONS %d\\n\", n, nnz); break;\n\tcase EXPORT_ROWS: export_string(\"%d %d\\n\", n, nnz); break;\n\t}\n\t\n\t// print main part of file\n\t// first get data structure info\n\tdouble *non_zeros;\n\tunsigned char *row_counts;\n\tint *row_starts;\n\tbool use_counts;\n\tunsigned int *cols;\n\tdouble *dist;\n\tint dist_shift;\n\tint dist_mask;\n\tif (!compact_tr) {\n\t\tnon_zeros = rmsm->non_zeros;\n\t\trow_counts = rmsm->row_counts;\n\t\trow_starts = (int *)rmsm->row_counts;\n\t\tuse_counts = rmsm->use_counts;\n\t\tcols = rmsm->cols;\n\t} else {\n\t\trow_counts = cmsrsm->row_counts;\n\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\tuse_counts = cmsrsm->use_counts;\n\t\tcols = cmsrsm->cols;\n\t\tdist = cmsrsm->dist;\n\t\tdist_shift = cmsrsm->dist_shift;\n\t\tdist_mask = cmsrsm->dist_mask;\n\t}\n\t// then traverse data structure\n\th = 0;\n\tfor (i = 0; i < n; i++) {\n\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\telse { l = h; h += row_counts[i]; }\n\t\tif (export_type == EXPORT_ROWS) export_string(\"%d\", i);\n\t\tfor (j = l; j < h; j++) {\n\t\t\tr = i;\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_tr) {\n\t\t\t\tc = cols[j];\n\t\t\t\td = non_zeros[j];\n\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\telse {\n\t\t\t\tc = (int)(cols[j] >> dist_shift);\n\t\t\t\td = dist[(int)(cols[j] & dist_mask)];\n\t\t\t}\n\t\t\tswitch (export_type) {\n\t\t\tcase EXPORT_PLAIN: export_string(\"%d %d %.*g\\n\", r, c, export_model_precision, d); break;\n\t\t\tcase EXPORT_MATLAB: export_string(\"%s(%d,%d)=%.*g;\\n\", export_name, r+1, c+1, export_model_precision, d); break;\n\t\t\tcase EXPORT_DOT: case EXPORT_DOT_STATES: export_string(\"%d -> %d [ label=\\\"%.*g\\\" ];\\n\", r, c, export_model_precision, d); break;\n\t\t\tcase EXPORT_MRMC: export_string(\"%d %d %.*g\\n\", r+1, c+1, export_model_precision, d); break;\n\t\t\tcase EXPORT_ROWS: export_string(\" %.*g:%d\", export_model_precision, d, c); break;\n\t\t\t}\n\t\t}\n\t\tif (export_type == EXPORT_ROWS) export_string(\"\\n\");\n\t}\n\t\n\t// print file footer\n\tswitch (export_type) {\n\t// Note: no footer for EXPORT_DOT_STATES\n\tcase EXPORT_DOT: export_string(\"}\\n\"); break;\n\t}\n\t\n\t// close file, etc.\n\tif (export_file) fclose(export_file);\n\tif (na) env->ReleaseStringUTFChars(na, export_name);\n\t\n\t// catch exceptions: return (undocumented) error code for memout\n\t} catch (std::bad_alloc e) {\n\t\treturn -2;\n\t}\n\t\n\t// free memory\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\t\n\treturn 0;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ExportSubMDP.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_sparse_PrismSparse_PS_1ExportSubMDP\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer m,\t// mdp\njlong __jlongpointer sm,\t// sub mdp\njstring na,\t\t// sub mdp name\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer od,\t// odd\njint et,\t\t// export type\njstring fn,\t\t// filename\njstring rsn,    // reward struct name\njboolean neh    // noexportheaders\n)\n{\n\tDdNode *mdp = jlong_to_DdNode(m);\t\t// mdp\n\tDdNode *submdp = jlong_to_DdNode(sm);\t\t// sub-mdp\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tODDNode *odd = jlong_to_ODDNode(od);\n\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL;\n\t// model stats\n\tint i, j, k, n, nc, l1, h1, l2, h2;\n\tlong nnz;\n\tconst char *export_name;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// store export info\n\tif (!store_export_info(et, fn, env)) return -1;\n\texport_name = na ? env->GetStringUTFChars(na, 0) : \"S\";\n\t\n\t// build sparse matrix\n\tndsm = build_sub_nd_sparse_matrix(ddman, mdp, submdp, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\tn = ndsm->n;\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\t\n\t// print file header\n\tif (export_type == EXPORT_PLAIN && !neh) {\n\t\texport_string(\"# Reward structure\");\n\t\tif (env->GetStringUTFLength(rsn) > 0) {\n\t\t\tconst char *header = env->GetStringUTFChars(rsn,0);\n\t\t\texport_string(\" \\\"%s\\\"\", header);\n\t\t\tenv->ReleaseStringUTFChars(rsn, header);\n\t\t}\n\t\texport_string(\"\\n\");\n\t\texport_string(\"# Transition rewards\\n\");\n\t}\n\tswitch (export_type) {\n\tcase EXPORT_PLAIN: export_string(\"%d %d %ld\\n\", n, nc, nnz); break;\n\tcase EXPORT_MATLAB: for (i = 0; i < ndsm->k; i++) export_string(\"%s%d = sparse(%d,%d);\\n\", export_name, i+1, n, n); break;\n\tcase EXPORT_ROWS: export_string(\"%d %d %ld\\n\", n, nc, nnz); break;\n\t}\n\t\n\t// print main part of file\n\t// first get data structure info\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\t// then traverse data structure\n\th1 = h2 = 0;\n\tfor (i = 0; i < n; i++) {\n\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\tif (export_type == EXPORT_ROWS) export_string(\"%d\", i);\n\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\tswitch (export_type) {\n\t\t\t\tcase EXPORT_PLAIN: export_string(\"%d %d %d %.*g\\n\", i, j-l1, cols[k], export_model_precision, non_zeros[k]); break;\n\t\t\t\tcase EXPORT_MATLAB: export_string(\"%s%d(%d,%d)=%.*g;\\n\", export_name, j-l1+1, i+1, cols[k]+1, export_model_precision, non_zeros[k]); break;\n\t\t\t\tcase EXPORT_ROWS: export_string(\" %.*g:%d\", export_model_precision, non_zeros[k], cols[k]); break;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (export_type == EXPORT_ROWS) export_string(\"\\n\");\n\t\t}\n\t}\n\t\n\t// close file, etc.\n\tif (export_file) fclose(export_file);\n\tif (na) env->ReleaseStringUTFChars(na, export_name);\n\t\n\t// catch exceptions: return (undocumented) error code for memout\n\t} catch (std::bad_alloc e) {\n\t\treturn -2;\n\t}\n\t\n\t// free memory\n\tif (ndsm) delete ndsm;\n\t\n\treturn 0;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_JOR.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <memory>\n#include <new>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Jacobi/JOR\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1JOR\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble omega\t\t// omega (over-relaxation parameter)\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_a, compact_d, compact_b;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *diags_vec = NULL, *b_vec = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\tDistVector *diags_dist = NULL, *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, l, h, iters;\n\tdouble d, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_a = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_a = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_a?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = compact_a ? cmsr_negative_row_sums(cmsrsm, transpose) : rm_negative_row_sums(rmsm, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, init, rvars, num_rvars, odd);\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PS_JOR (\");\n\t\ttitle += (omega == 1.0)?\"Jacobi\": (\"JOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_a) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t\n\t\t\td = (b == NULL) ? 0.0 : ((!compact_b) ? b_vec[i] : b_dist->dist[b_dist->ptrs[i]]);\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_a) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td -= non_zeros[j] * soln[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td -= dist[(int)(cols[j] & dist_mask)] * soln[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// divide by diagonal (multiply by inverted diagonal)\n\t\t\tif (!compact_d) d *= diags_vec[i]; else d *= diags_dist->dist[diags_dist->ptrs[i]];\n\t\t\t// over-relaxation\n\t\t\tif (omega != 1.0) {\n\t\t\t\td = ((1-omega) * soln[i]) + (omega * d);\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln2, n, 0);\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln, soln2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\t\t\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", (omega == 1.0)?\"Jacobi\":\"JOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_JORInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Jacobi/JOR, interval variant\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1JORInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble omega,\t\t// omega (over-relaxation parameter)\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t\t// upper bound values\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_a, compact_d, compact_b;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *diags_vec = NULL, *b_vec = NULL, *soln_below = NULL, *soln_below2 = NULL, *soln_above = NULL, *soln_above2 = NULL, *tmpsoln = NULL;\n\tDistVector *diags_dist = NULL, *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, l, h, iters;\n\tdouble d_below, d_above, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tif (omega <= 0.0 || omega > 1.0) {\n\t\tPN_SetErrorMessage(\"Interval iteration requires 0 < omega <= 1.0, have omega = %g\", omega);\n\t\treturn ptr_to_jlong(NULL);\n\t}\n\n\tIntervalIteration helper(flags);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_a = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_a = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_a?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = compact_a ? cmsr_negative_row_sums(cmsrsm, transpose) : rm_negative_row_sums(rmsm, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tsoln_above = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tsoln_below2 = new double[n];\n\tsoln_above2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 4*kb;\n\tPN_PrintMemoryToMainLog(env, \"[4 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PS_JOR (\");\n\t\ttitle += (omega == 1.0)?\"Jacobi\":(\"JOR omega=\" + std::to_string(omega));\n\t\ttitle += \"), interval\";\n\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_a) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply (below and above simultaneously)\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t\n\t\t\td_below = (b == NULL) ? 0.0 : ((!compact_b) ? b_vec[i] : b_dist->dist[b_dist->ptrs[i]]);\n\t\t\td_above = d_below;\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_a) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td_below -= non_zeros[j] * soln_below[cols[j]];\n\t\t\t\t\td_above -= non_zeros[j] * soln_above[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td_below -= dist[(int)(cols[j] & dist_mask)] * soln_below[(int)(cols[j] >> dist_shift)];\n\t\t\t\t\td_above -= dist[(int)(cols[j] & dist_mask)] * soln_above[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// divide by diagonal (multiply by inverted diagonal)\n\t\t\tif (!compact_d) d_below *= diags_vec[i]; else d_below *= diags_dist->dist[diags_dist->ptrs[i]];\n\t\t\tif (!compact_d) d_above *= diags_vec[i]; else d_above *= diags_dist->dist[diags_dist->ptrs[i]];\n\t\t\t// over-relaxation\n\t\t\tif (omega != 1.0) {\n\t\t\t\td_below = ((1-omega) * soln_below[i]) + (omega * d_below);\n\t\t\t\td_above = ((1-omega) * soln_above[i]) + (omega * d_above);\n\t\t\t}\n\t\t\t// set vector element\n\t\t\thelper.updateValueFromBelow(soln_below2[i], soln_below[i], d_below);\n\t\t\thelper.updateValueFromAbove(soln_above2[i], soln_above[i], d_above);\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below2, n, 0);\n\t\t\titerationExport->exportVector(soln_above2, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below2, soln_above2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln_below;\n\t\tsoln_below = soln_below2;\n\t\tsoln_below2 = tmpsoln;\n\t\ttmpsoln = soln_above;\n\t\tsoln_above = soln_above2;\n\t\tsoln_above2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", (omega == 1.0)?\"Jacobi\":\"JOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln_below2) delete[] soln_below2;\n\tif (soln_above) delete[] soln_above;\n\tif (soln_above2) delete[] soln_above2;\n\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njint bound,\t\t// time bound\njboolean min\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a = NULL;\n\t// model stats\n\tint n, nc;\n\tlong nnz;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL;\n\t// vectors\n\tdouble *yes_vec = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, k, l1, h1, l2, h2, iters;\n\tdouble d1, d2, kb, kbt;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get a - filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\tndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\tkb = ndsm->mem;\n\tkbt = kb;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector for yes\n\tPN_PrintToMainLog(env, \"Creating vector for yes... \");\n\tyes_vec = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is yes\n\tfor (i = 0; i < n; i++) {\n\t\tsoln[i] = yes_vec[i];\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros = ndsm->non_zeros;\n\t\tunsigned char *row_counts = ndsm->row_counts;\n\t\tint *row_starts = (int *)ndsm->row_counts;\n\t\tunsigned char *choice_counts = ndsm->choice_counts;\n\t\tint *choice_starts = (int *)ndsm->choice_counts;\n\t\tbool use_counts = ndsm->use_counts;\n\t\tunsigned int *cols = ndsm->cols;\n\t\t\n\t\t// do matrix multiplication and min/max\n\t\th1 = h2 = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = min ? 2 : -1;\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\td2 = 0;\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\td2 += non_zeros[k] * soln[cols[k]];\n\t\t\t\t}\n\t\t\t\tif (min) {\n\t\t\t\t\tif (d2 < d1) d1 = d2;\n\t\t\t\t} else {\n\t\t\t\t\tif (d2 > d1) d1 = d2;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\t// (if no choices, use value of yes)\n\t\t\tsoln2[i] = (h1 > l1) ? d1 : yes_vec[i];\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (ndsm) delete ndsm;\n\tif (yes_vec) delete[] yes_vec;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetCumulReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetCumulReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njint bound,\t\t\t\t\t// time bound\njboolean min\t\t\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\n\t// model stats\n\tint n, nc, nc_r;\n\tlong nnz, nnz_r;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL, *ndsm_r = NULL;\n\t// vectors\n\tdouble *sr_vec = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, iters;\n\tdouble d1, d2, x, kb, kbt;\n\tbool first;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix (probs)\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix (transitions)... \");\n\tndsm = build_nd_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\tkb = (nnz*12.0+nc*4.0+n*4.0)/1024.0;\n\tkbt = kb;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// build sparse matrix (rewards)\n\tPN_PrintToMainLog(env, \"Building sparse matrix (transition rewards)... \");\n\tndsm_r = build_sub_nd_sparse_matrix(ddman, trans, trans_rewards, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz_r = ndsm_r->nnz;\n\tnc_r = ndsm_r->nc;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc_r, nnz_r, ndsm_r->k);\n\tkb = (nnz_r*12.0+nc_r*4.0+n*4.0)/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector for state rewards\n\tPN_PrintToMainLog(env, \"Creating vector for state rewards... \");\n\tsr_vec = mtbdd_to_double_vector(ddman, state_rewards, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\t// initial solution is zero\n\tfor (i = 0; i < n; i++) {\n\t\tsoln[i] = 0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\t// store local copies of stuff\n\t// firstly for transition matrix\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\t// and then for transition rewards matrix\n\t// (note: we don't need row_counts/row_starts for\n\t// this since choice structure mirrors transition matrix)\n\tdouble *non_zeros_r = ndsm_r->non_zeros;\n\tunsigned char *choice_counts_r = ndsm_r->choice_counts;\n\tint *choice_starts_r = (int *)ndsm_r->choice_counts;\n\tbool use_counts_r = ndsm_r->use_counts;\n\tunsigned int *cols_r = ndsm_r->cols;\n\t\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\n\t\t// do matrix multiplication and min/max\n\t\th1 = h2 = h2_r = 0;\n\t\t// loop through states\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = 0.0; // initial value doesn't matter\n\t\t\tfirst = true; // (because we also remember 'first')\n\t\t\t// get pointers to nondeterministic choices for state i\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t// loop through those choices\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t// compute the reward value for state i for this iteration\n\t\t\t\t// start with state reward for this state\n\t\t\t\td2 = sr_vec[i];\n\t\t\t\t// get pointers to transitions\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t// and get pointers to transition rewards\n\t\t\t\tif (!use_counts_r) { l2_r = choice_starts_r[j]; h2_r = choice_starts_r[j+1]; }\n\t\t\t\telse { l2_r = h2_r; h2_r += choice_counts_r[j]; }\n\t\t\t\t// loop through transitions\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// find corresponding transition reward if any\n\t\t\t\t\tk_r = l2_r; while (k_r < h2_r && cols_r[k_r] != cols[k]) k_r++;\n\t\t\t\t\t// if there is one, add reward * prob to reward value\n\t\t\t\t\tif (k_r < h2_r) { d2 += non_zeros_r[k_r] * non_zeros[k]; k_r++; }\n\t\t\t\t\t// add prob * corresponding reward from previous iteration\n\t\t\t\t\td2 += non_zeros[k] * soln[cols[k]];\n\t\t\t\t}\n\t\t\t\t// see if this value is the min/max so far\n\t\t\t\tif (first || (min&&(d2<d1)) || (!min&&(d2>d1))) {\n\t\t\t\t\td1 = d2;\n\t\t\t\t}\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d1;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (ndsm) delete ndsm;\n\tif (ndsm_r) delete ndsm_r;\n\tif (sr_vec) delete[] sr_vec;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetInstReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetInstReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njint bound,\t\t\t// time bound\njboolean min,\t\t// min or max probabilities (true = min, false = max)\njlong __jlongpointer in\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *init = jlong_to_DdNode(in);\n\t\n\t// model stats\n\tint n, nc;\n\tlong nnz;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL;\n\t// vectors\n\tdouble *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, k, l1, h1, l2, h2, iters;\n\tdouble d1, d2, kb, kbt;\n\tbool first;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix (probs)\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix (transitions)... \");\n\tndsm = build_nd_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\tkb = (nnz*12.0+nc*4.0+n*4.0)/1024.0;\n\tkbt = kb;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\t// (solution is initialised to the state rewards)\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, state_rewards, rvars, num_rvars, odd);\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros = ndsm->non_zeros;\n\t\tunsigned char *row_counts = ndsm->row_counts;\n\t\tint *row_starts = (int *)ndsm->row_counts;\n\t\tunsigned char *choice_counts = ndsm->choice_counts;\n\t\tint *choice_starts = (int *)ndsm->choice_counts;\n\t\tbool use_counts = ndsm->use_counts;\n\t\tunsigned int *cols = ndsm->cols;\n\t\t\n\t\t// do matrix multiplication and min/max\n\t\th1 = h2 = 0;\n\t\t// loop through states\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = 0.0;\n\t\t\tfirst = true;\n\t\t\t// get pointers to nondeterministic choices for state i\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t// loop through those choices\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t// compute the reward value for state i for this iteration\n\t\t\t\t// start with state reward for this state\n\t\t\t\td2 = 0.0;\n\t\t\t\t// get pointers to transitions\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t// loop through transitions\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// add prob * corresponding reward from previous iteration\n\t\t\t\t\td2 += non_zeros[k] * soln[cols[k]];\n\t\t\t\t}\n\t\t\t\t// see if this value is the min/max so far\n\t\t\t\tif (min) {\n\t\t\t\t\tif (first | (d2 < d1)) d1 = d2;\n\t\t\t\t} else {\n\t\t\t\t\tif (first | (d2 > d1)) d1 = d2;\n\t\t\t\t}\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t\t// set vector element\n\t\t\t// (if there were no choices from this state, reward is zero)\n\t\t\tsoln2[i] = (h1 > l1) ? d1 : 0;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t\t\n//\t\tPN_PrintToMainLog(env, \"%i: %f\\n\", iters, get_first_from_bdd(ddman, soln, init, rvars, num_rvars, odd));\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (ndsm) delete ndsm;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetMultiObj.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n#include <string>\n\n//The following gives more output on stdout. In fact quite a lot of it, usable only for ~10 state examples \n//#define MORE_OUTPUT\n\n//The following number is used to determine when to consider a number equal to 0.\n//Will be multiplied by minimal weights to make sure we don't do too much roundoffs for small weights\n#define ZERO_ROUNDOFF 10e-11\n\nJNIEXPORT jdoubleArray __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetMultiObj\n(\n JNIEnv *env,\n jclass cls,\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv,  // nondet vars\n jint num_ndvars,\n jboolean min,        // min or max probabilities (true = min, false = max)\n jlong __jlongpointer _start, // initial state(s)\n jlong _adversary,\n jlong __jlongpointer _ndsm, //pointer to trans sparse matrix\n jobject synchs,\n jlongArray _yes_vec, //pointer to yes vector array\n jintArray _prob_step_bounds, //step bounds for probabilistic operators\n jlongArray  _ndsm_r, //pointer to reward sparse matrix array\n jdoubleArray _weights, //weights of rewards and yes_vec vectors\n jintArray _ndsm_r_step_bounds //step bounds for rewards\n  )\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(od);      // reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);   // row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);   // col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n\tDdNode *start = jlong_to_DdNode(_start); // initial state(s)\n    \n\t// mtbdds\n\tDdNode *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n, nc;\n\tlong nnz;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL;\n\tNDSparseMatrix **ndsm_r = NULL;\n\t// vectors\n\tdouble **yes_vec = NULL;\n\tdouble *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\tdouble **psoln = NULL, **psoln2 = NULL;  \n    \n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// adversary stuff\n\tint export_adv_enabled = export_adv;\n\tFILE *fp_adv = NULL;\n\tint adv_j;\n\tint *adv = NULL;\n\t// action info\n\tjstring *action_names_jstrings;\n\tconst char** action_names = NULL;\n\tint num_actions;\n\t// misc\n\tint i, j, k, l1, h1, l2, h2, iters;\n\tint *k_r = NULL, *l2_r = NULL, *h2_r= NULL;\n\tdouble d1, d2, kb, kbt;\n\tdouble *pd1 = NULL, *pd2 = NULL;\n\tbool done, weightedDone, first;\n\tint num_yes = 0;\n\tint start_index;\n\tunsigned int *row_starts1, *predecessors;\n\tunsigned int extra_node;\n\t// storage for result array (0 means error)\n\tjdoubleArray ret = 0;\n\t// local copy of max_iters, since we will change it\n\tint max_iters_local = max_iters;\n\t// whether to export individual solution vectors (with adversaries)\n\tbool export_vectors = false;\n\t\n\t// Extract some info about objectives\n\tbool has_rewards = _ndsm_r != 0;\n\tbool has_yes_vec = _yes_vec != 0;\n\tjsize lenRew = (has_rewards) ? env->GetArrayLength(_ndsm_r) : 0;\n\tjsize lenProb = (has_yes_vec) ? env->GetArrayLength(_yes_vec) : 0;\n\tjlong *ptr_ndsm_r = (has_rewards) ? env->GetLongArrayElements(_ndsm_r, 0) : NULL;\n\tjlong *ptr_yes_vec = (has_yes_vec) ? env->GetLongArrayElements(_yes_vec, 0) : NULL;\n\tdouble* weights = env->GetDoubleArrayElements(_weights, 0);\n\tint* step_bounds_r = (has_rewards) ? (int*)env->GetIntArrayElements(_ndsm_r_step_bounds, 0) : NULL;\n\tint* step_bounds = (has_yes_vec) ? (int*)env->GetIntArrayElements(_prob_step_bounds, 0) : NULL;\n\t\n\t// We will ignore one of the rewards and compute its value from the other ones and\n\t// from the combined value. We must make sure that this reward has nonzero weight,\n\t// otherwise we can't compute it.\n\tint ignoredWeight = -1;\n\t\n\t/* HOTFIX: not used for numerical problems\n\tfor (i = lenProb + lenRew - 1; i>=0; i--) {\n\t\tif (weights[i] > 0) {\n\t\t\tignoredWeight = i;\n\t\t\tbreak;\n\t\t}\n\t}*/\n\t\n\t//determine the minimal nonzero weight\n\tdouble min_weight = 1;\n\tfor (i = 0; i < lenProb + lenRew; i++)\n\t\tif (weights[i] > 0 && weights[i] < min_weight)\n\t\t\tmin_weight = weights[i];\n\tdouble near_zero = min_weight * ZERO_ROUNDOFF;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\t// start clocks \n\t\tstart1 = start2 = util_cpu_time();\n\t\t\n\t\t// get number of states\n\t\tn = odd->eoff + odd->toff;\n\t\t\n\t\t// build sparse matrix\n\t\tndsm = (NDSparseMatrix *) jlong_to_NDSparseMatrix(_ndsm);\n\t\t\n\t\t// if needed, and if info is available, get action names\n\t\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t\tif (synchs != NULL) {\n\t\t\t\tget_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n\t\t\t}\n\t\t}\n\t\n\t\t// get number of transitions/choices\n\t\tnnz = ndsm->nnz;\n\t\tnc = ndsm->nc;\n\t\tkb = ndsm->mem;\n\t\tkbt = kb;\n\t\t\n\t\tNDSparseMatrix *ndsm_r[lenRew];\n\t\t\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tndsm_r[rewi] = (NDSparseMatrix *) jlong_to_NDSparseMatrix(ptr_ndsm_r[rewi]);\n\t\t\n\t\tint max_step_bound = 0;\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++) {\n\t\t\tif (step_bounds_r[rewi] == -1)\n\t\t\t\tstep_bounds_r[rewi] = max_iters_local;\n\t\t\telse if (max_step_bound < step_bounds_r[rewi]) {\n\t\t\t\tmax_step_bound = step_bounds_r[rewi];\n\t\t\t}\n\t\t}\n\t\t\n\t\tfor(int probi = 0; probi < lenProb; probi++) {\n\t\t\tif (step_bounds[probi] == -1) {\n\t\t\t\tstep_bounds[probi] = max_iters_local;\n\t\t\t} else if (max_step_bound < step_bounds[probi]) {\n\t\t\t\tmax_step_bound = step_bounds[probi];\n\t\t\t}\n\t\t}\n\t\t\n\t\t// get vector for yes\n\t\tyes_vec = new double *[lenProb];\n\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\tyes_vec[probi] = (double *) jlong_to_ptr(ptr_yes_vec[probi]);\n#ifdef MORE_OUTPUT\n\t\tPN_PrintToMainLog(env, \"yes_vec %d: \", probi);\n\t\tfor (int o = 0; o < n; o++)\n\t\t\tPN_PrintToMainLog(env, \"%f, \", yes_vec[probi][o]);\n\t\tPN_PrintToMainLog(env, \"\\n\");\n#endif\n\t\t}\n\t\t\n\t\tkb = n*8.0/1024.0;\n\t\tkbt += kb;\n\t\t\n\t\t// create solution/iteration vectors\n\t\tsoln = new double[n];\n\t\tsoln2 = new double[n];\n\t\tpsoln = new double *[lenProb + lenRew];\n\t\tpsoln2 = new double *[lenProb + lenRew];\n\t\tfor (int it = 0; it < lenProb + lenRew ; it++) {\n\t\t\tif (it != ignoredWeight) {\n\t\t\t\tpsoln[it] = new double[n];\n\t\t\t\tpsoln2[it] = new double[n];\n\t\t\t}\n\t\t}\n\t\tpd1 = new double[lenProb + lenRew];\n\t\tpd2 = new double[lenProb + lenRew];\n\t\t\n\t\tkb = n*8.0/1024.0;\n\t\tkbt += 2*kb;\n\t\t\n\t\t// if required, create storage for adversary and initialise\n\t\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t\tadv = new int[n];\n\t\t\t// Initialise all entries to -1 (\"don't know\")\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tadv[i] = -1;\n\t\t\t}\n\t\t}\n\t\n\t\t// Get index of single (first) initial state\n\t\tstart_index = get_index_of_first_from_bdd(ddman, start, rvars, num_rvars, odd);\n\t\t\n\t\t// initial solution\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t// combined value initialised to weighted sum of yes vectors (for unbounded probability objectives)\n\t\t\t// or 0 (for anything else: step-bounded probabilities, or cumulative rewards)\n\t\t\tsoln[i] = 0;\n\t\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\t\tif (step_bounds[probi] == max_iters_local) {\n\t\t\t\t\tsoln[i] += weights[probi] * yes_vec[probi][i];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// individual objectives\n\t\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\t\tif (probi != ignoredWeight) {\n\t\t\t\t\tif (step_bounds[probi] == max_iters_local) {\n\t\t\t\t\t\tpsoln[probi][i] = 0;//yes_vec[probi][i];\n\t\t\t\t\t}\n\t\t\t\t\telse {\n\t\t\t\t\t\tpsoln[probi][i] = 0;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++) {\n\t\t\t\tif (lenProb + rewi != ignoredWeight) {\n\t\t\t\t\tpsoln[rewi + lenProb][i] = 0;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// soln2 vector(s) just initialised to zero (not read until updated again)\n\t\t\tsoln2[i] = 0;\n\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\tpsoln2[it][i] = 0;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n#ifdef MORE_OUTPUT\n\t\tPN_PrintToMainLog(env, \"Initial soln: \");\n\t\tfor (int o = 0; o < n; o++)\n\t\t\tPN_PrintToMainLog(env, \"%f, \", soln[o]);\n\t\tPN_PrintToMainLog(env, \"\\n\");\n\t\t\n\t\t\n\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\tif (it != ignoredWeight) {\n\t\t\t\tPN_PrintToMainLog(env, \"psoln: \");\n\t\t\t\tfor (int o = 0; o < n; o++)\n\t\t\t\t\tPN_PrintToMainLog(env, \"%f, \", psoln[it][o]);\n\t\t\t\tPN_PrintToMainLog(env, \"\\n\");\n\t\t\t} else {\n\t\t\t\tPN_PrintToMainLog(env, \"psoln: (ignored)\\n\");\n\t\t\t}\n\t\t}\n#endif\n\t\t// get setup time\n\t\tstop = util_cpu_time();\n\t\ttime_for_setup = (double)(stop - start2)/1000;\n\t\tstart2 = stop;\n\t\t\n\t\t// start iterations\n\t\titers = 0;\n\t\tdone = false;\n\t\tweightedDone = false;\n\t\t//PN_PrintToMainLog(env, \"Starting iterations...\\n\");\n\t\t\n\t\t// open file to store adversary (if required)\n\t\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t\tfp_adv = fopen(export_adv_filename, \"w\");\n\t\t\tif (!fp_adv) {\n\t\t\t\tPN_PrintWarningToMainLog(env, \"Adversary generation cancelled (could not open file \\\"%s\\\").\", export_adv_filename);\n\t\t\t\texport_adv_enabled = EXPORT_ADV_NONE;\n\t\t\t}\n\t\t}\n\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros = ndsm->non_zeros;\n\t\tunsigned char *row_counts = ndsm->row_counts;\n\t\tint *row_starts = (int *)ndsm->row_counts;\n\t\tunsigned char *choice_counts = ndsm->choice_counts;\n\t\tint *choice_starts = (int *)ndsm->choice_counts;\n\t\tbool use_counts = ndsm->use_counts;\n\t\tunsigned int *cols = ndsm->cols;\n\t\t\n\t\tdouble *non_zeros_r[lenRew];\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tnon_zeros_r[rewi] = ndsm_r[rewi]->non_zeros;\n\t\t\n\t\tunsigned char *choice_counts_r[lenRew];\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tchoice_counts_r[rewi] = ndsm_r[rewi]->choice_counts;\n\t\t\n\t\tint *choice_starts_r[lenRew];\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tchoice_starts_r[rewi] = (int*)ndsm_r[rewi]->choice_counts;\n\t\t\n\t\tunsigned int *cols_r[lenRew];\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tcols_r[rewi] = ndsm_r[rewi]->cols;\n\t\t\n\t\tbool doneBeforeBounded = false;\n\t\t\n\t\th2_r = new int[lenRew];\n\t\tl2_r = new int[lenRew];\n\t\tk_r = new int[lenRew];\n\t\twhile (!done && iters < max_iters_local) {\n\t\t\titers++;\n\t\t\t\n\t\t\t// do matrix multiplication and min/max\n\t\t\th1 = h2 = 0;\n\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++)\n\t\t\t\th2_r[rewi] = 0;\n\t\t\t\n\t\t\t// loop through states\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tfirst = true;\n\t\t\t\t\n\t\t\t\t// first, get the decision of the adversary optimizing the combined reward\n\t\t\t\td1 = -INFINITY;\n\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++)\n\t\t\t\t\tif (it != ignoredWeight)\n\t\t\t\t\t\tpd1[it] = -INFINITY;\n\t\t\t\t\n\t\t\t\t// get pointers to nondeterministic choices for state i\n\t\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t\t// loop through those choices\n\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\t// compute, for state i for this iteration,\n\t\t\t\t\t// the combined and individual reward values\n\t\t\t\t\t// start with 0 (we don't have any state rewards)\n\t\t\t\t\td2 = 0;\n\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++)\n\t\t\t\t\t\tif (it != ignoredWeight)\n\t\t\t\t\t\t\tpd2[it] = 0;\n\t\t\t\t\t// get pointers to transitions\n\t\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t\t// and get pointers to transition rewards\n\t\t\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++) {\n\t\t\t\t\t\tif (!ndsm_r[rewi]->use_counts) {\n\t\t\t\t\t\t\tl2_r[rewi] = choice_starts_r[rewi][j];\n\t\t\t\t\t\t\th2_r[rewi] = choice_starts_r[rewi][j+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2_r[rewi] = h2_r[rewi];\n\t\t\t\t\t\t\th2_r[rewi] += choice_counts_r[rewi][j];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// loop through transitions\n\t\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t\t// for each reward structure\n\t\t\t\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++) {\n\t\t\t\t\t\t\t// find corresponding transition reward if any\n\t\t\t\t\t\t\tk_r[rewi] = l2_r[rewi];\n\t\t\t\t\t\t\twhile (k_r[rewi] < h2_r[rewi] && cols_r[rewi][k_r[rewi]] != cols[k]) k_r[rewi]++;\n\t\t\t\t\t\t\t// if there is one, add reward * prob to combined and individual reward values\n\t\t\t\t\t\t\tif (k_r[rewi] < h2_r[rewi] && max_iters_local - iters < step_bounds_r[rewi]) {\n\t\t\t\t\t\t\t\td2 += weights[rewi + lenProb] * non_zeros_r[rewi][k_r[rewi]] * non_zeros[k];\n\t\t\t\t\t\t\t\tif (lenProb + rewi != ignoredWeight) {\n\t\t\t\t\t\t\t\t\tpd2[rewi + lenProb] += non_zeros_r[rewi][k_r[rewi]] * non_zeros[k];\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tk_r[rewi]++;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// add prob * corresponding reward from previous iteration\n\t\t\t\t\t\t// (for both combined and individual rewards)\n\t\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\t\t\t\tpd2[it] += non_zeros[k] * psoln[it][cols[k]];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\td2 += non_zeros[k] * soln[cols[k]];\n\t\t\t\t\t}\n\t\t\t\t\t// see if the combined reward value is the min/max so far\n\t\t\t\t\tbool pickThis = first || (min&&(d2<d1)) || (!min&&(d2>d1));\n\n\t\t\t\t\t// if it equals the min/max do far for the combined reward value,\n\t\t\t\t\t// but it is better for some individual reward, we choose it.\n\t\t\t\t\t// not sure why\n\t\t\t\t\tif (!pickThis && (d2==d1)) {\n\t\t\t\t\t\tfor (int it = 0; it < lenProb + lenRew; it++) {\n\t\t\t\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\t\t\t\tif ((min&&(pd2[it]<pd1[it])) || (!min&&(pd2[it]>pd1[it]))) {\n\t\t\t\t\t\t\t\t\tpickThis = true;\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (pickThis) {\n\t\t\t\t\t\t// store optimal values for combined and individual rewards\n\t\t\t\t\t\td1 = d2;\n\t\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++)\n\t\t\t\t\t\t\tif (it != ignoredWeight)\n\t\t\t\t\t\t\t\tpd1[it] = pd2[it];\n\t\t\t\t\t\t// if adversary generation is enabled, store optimal choice\n\t\t\t\t\t\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t\t\t\t\t\t// if this is the first choice to be picked, always store it\n\t\t\t\t\t\t\tif (adv[i] == -1) {\n\t\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t// normally, we extract optimal choice differently for max\n\t\t\t\t\t\t\t\t// (only remember strictly better choices)\n\t\t\t\t\t\t\t\t// (which resolves problems with end components)\n\t\t\t\t\t\t\t\t// but here it's hard to know when it is max, due to the\n\t\t\t\t\t\t\t\t// mix of objectives and some being negated\n\t\t\t\t\t\t\t\t// so we just always only pick strictly better ones\n\t\t\t\t\t\t\t\tif ((min&&(d1<soln[i])) || (!min&&(d1>soln[i]))) {\n\t\t\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tfirst = false;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// HOTFIX: it seems that on self loops d1 can be unchanged because the other for cycle is not executed, which is not desirable\n\t\t\t\tif (d1 == -INFINITY) {\n\t\t\t\t\td1 = 0;\n\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\t\t\tpd1[it] = 0;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tdouble val_yes = 0.0;\n\t\t\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\t\t\tif (max_iters_local - iters < step_bounds[probi])\n\t\t\t\t\t\tval_yes += weights[probi] * yes_vec[probi][i];\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t//TODO: we need to handle val_yes somehow\n\t\t\t\tif (val_yes == 0 || d1>val_yes) {\n\t\t\t\t\tfor (int it = 0; it < lenProb + lenRew; it++) {\n\t\t\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\t\t\tpsoln2[it][i] = pd1[it];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tsoln2[i] = d1;\n\t\t\t\t} else {\n\t\t\t\t\tsoln2[i] = 0;\n\t\t\t\t\tfor (int probi = 0; probi < lenProb; probi++)\n\t\t\t\t\t\tif(max_iters_local - iters < step_bounds[probi])\n\t\t\t\t\t\t\tsoln2[i] += weights[probi] * yes_vec[probi][i];\n\t\t\t\t\t\n\t\t\t\t\tfor (int probi = 0; probi < lenProb; probi++)\n\t\t\t\t\t\tif (probi != ignoredWeight && max_iters_local - iters < step_bounds[probi])\n\t\t\t\t\t\t\tpsoln2[probi][i] = yes_vec[probi][i];\n\n\t\t\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++)\n\t\t\t\t\t\tif (lenProb + rewi != ignoredWeight)\n\t\t\t\t\t\t\tpsoln2[rewi + lenProb][i] = 0;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t//round small numbers to zero\n\t\t\tfor (int o = 0; o < n; o++) {\n\t\t\t\tif (fabs(soln[o]) < near_zero) soln[o] = 0;\n\t\t\t\tif (fabs(soln2[o]) < near_zero) soln2[o] = 0;\n\t\t\t}\n\t\t\tfor (int it = 0; it < lenRew + lenProb; it++)\n\t\t\t\tif (ignoredWeight != it)\n\t\t\t\t\tfor (int o = 0; o < n; o++) {\n\t\t\t\t\t\tif (fabs(psoln[it][o]) < near_zero) psoln[it][o] = 0;\n\t\t\t\t\t\tif (fabs(psoln2[it][o]) < near_zero) psoln2[it][o] = 0;\n\t\t\t\t\t}\n\n\t\t\t// check convergence\n\t\t\t// (note: doing outside loop means may not need to check all elements)\n\t\t\tswitch (term_crit) {\n\t\t\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\t\t\tif (!weightedDone) {\n\t\t\t\t\t\tweightedDone = true;\n\t\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\t\tif (fabs(soln2[i] - soln[i]) > term_crit_param) {\n\t\t\t\t\t\t\t\tweightedDone = false;\n\t\t\t\t\t\t\t\tgoto end_switch;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (!doneBeforeBounded) {\n\t\t\t\t\t\tdone = true;\n\t\t\t\t\t\tdoneBeforeBounded = true;\n\t\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\t\tfor (int it = 0; it < lenProb + lenRew; it++) {\n\t\t\t\t\t\t\t\tif (it != ignoredWeight && fabs(psoln2[it][i] - psoln[it][i]) > term_crit_param) {\n\t\t\t\t\t\t\t\t\tdone = false;\n\t\t\t\t\t\t\t\t\tdoneBeforeBounded = false;\n\t\t\t\t\t\t\t\t\tgoto end_switch;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\tcase TERM_CRIT_RELATIVE:\n\t\t\t\t\tif (!weightedDone) {\n\t\t\t\t\t\tweightedDone = true;\n\t\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\t\tif (fabs(soln2[i] - soln[i])/fabs(soln2[i]) > term_crit_param) {\n\t\t\t\t\t\t\t\tweightedDone = false;\n\t\t\t\t\t\t\t\tgoto end_switch;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (!doneBeforeBounded) {\n\t\t\t\t\t\tdone = true;\n\t\t\t\t\t\tdoneBeforeBounded = true;\n\t\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\t\tfor (int it = 0; it < lenProb + lenRew; it++) {\n\t\t\t\t\t\t\t\tif (it != ignoredWeight && fabs(psoln2[it][i] - psoln[it][i])/fabs(psoln2[it][i]) > term_crit_param) {\n\t\t\t\t\t\t\t\t\tdone = false;\n\t\t\t\t\t\t\t\t\tdoneBeforeBounded = false;\n\t\t\t\t\t\t\t\t\tgoto end_switch;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t\t\n\t\t\t//we can't stop if some of the objectives are step bounded,\n\t\t\t//maybe they were deactivated until now, so set the iters count so that\n\t\t\t//max_step_bound more iterations will be performed\n\t\t\tend_switch: if (done && max_step_bound > 0) {\n\t\t\t\tdone = false;\n\t\t\t\tif (iters < max_iters_local - max_step_bound) {\n\t\t\t\t\tmax_iters_local = iters + max_step_bound;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// prepare for next iteration\n\t\t\ttmpsoln = soln;\n\t\t\tsoln = soln2;\n\t\t\tsoln2 = tmpsoln;\n\t\t\t\n#ifdef MORE_OUTPUT\n\t\t\tPN_PrintToMainLog(env, \"Soln: \");\n\t\t\tfor (int o = 0; o < n; o++)\n\t\t\t\tPN_PrintToMainLog(env, \"%e, \", soln[o]);\n\t\t\tPN_PrintToMainLog(env, \"\\n\"); \n\t\t\tPN_PrintToMainLog(env, \"Soln2: \");\n\t\t\tfor (int o = 0; o < n; o++)\n\t\t\t\tPN_PrintToMainLog(env, \"%e, \", soln[o]);\n\t\t\tPN_PrintToMainLog(env, \"\\n\");   \n#endif\n\t\t\t\n\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\ttmpsoln = psoln[it];\n\t\t\t\t\tpsoln[it] = psoln2[it];\n\t\t\t\t\tpsoln2[it] = tmpsoln;\n\t\t\t\t}\n#ifdef MORE_OUTPUT\n\t\t\t\tPN_PrintToMainLog(env, \"psoln: \");\n\t\t\t\tif (ignoredWeight != it)\n\t\t\t\t\tfor (int o = 0; o < n; o++)\n\t\t\t\t\t\tPN_PrintToMainLog(env, \"%e, \", psoln[it][o]);\n\t\t\t\tPN_PrintToMainLog(env, \"\\n\"); \n\t\t\t\tPN_PrintToMainLog(env, \"psoln2: \");\n\t\t\t\tif (ignoredWeight != it)\n\t\t\t\t\tfor (int o = 0; o < n; o++)\n\t\t\t\t\t\tPN_PrintToMainLog(env, \"%e, \", psoln2[it][o]);\n\t\t\t\tPN_PrintToMainLog(env, \"\\n\"); \n#endif          \n\t\t\t}\n\t\t}\n\t\t\n\t\t// Traverse matrix to extract adversary\n\t\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t\t// Do two passes: first to compute the number of transitions,\n\t\t\t// the second to actually do the export\n\t\t\tint num_choice = 0;\n\t\t\tint num_trans = 0;\n\t\t\tfor (int pass = 1; pass <= 2; pass++) {\n\t\t\t\tif (pass == 2) {\n\t\t\t\t\tif (export_adv_enabled == EXPORT_ADV_DTMC) {\n\t\t\t\t\t\tfprintf(fp_adv, \"%d %d\\n\", n, num_trans);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tfprintf(fp_adv, \"%d %d %d\\n\", n, num_choice, num_trans);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\th1 = h2 = 0;\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t\t\t// Have to loop through all choices (to compute offsets)\n\t\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t\t\t// But only output a choice if it is in the adversary\n\t\t\t\t\t\tif (j == adv[i]) {\n\t\t\t\t\t\t\tswitch (pass) {\n\t\t\t\t\t\t\tcase 1:\n\t\t\t\t\t\t\t\tnum_choice++;;\n\t\t\t\t\t\t\t\tnum_trans += (h2-l2);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\tcase 2:\n\t\t\t\t\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t\t\t\t\tswitch (export_adv_enabled) {\n\t\t\t\t\t\t\t\t\tcase EXPORT_ADV_DTMC:\n\t\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\t\tcase EXPORT_ADV_MDP:\n\t\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d 0 %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\tif (ndsm->actions != NULL) fprintf(fp_adv, \" %s\", ndsm->actions[j]>0?action_names[ndsm->actions[j]-1]:\"\");\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"\\n\");\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\n\t\t// stop clocks\n\t\tstop = util_cpu_time();\n\t\ttime_for_iters = (double)(stop - start2)/1000;\n\t\ttime_taken = (double)(stop - start1)/1000;\n\t\t\n\t\t// print iterations/timing info\n\t\tPN_PrintToMainLog(env, \"Iterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\t\n\t\t// if the iterative method didn't terminate, this is an error\n\t\tif (!doneBeforeBounded) { // || !weightedDone) {\n\t\t\tPN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\t\tthrow 1;\n\t\t}\n\n\t\t//store the result\n\t\tret = env->NewDoubleArray(lenProb + lenRew);   \n\t\tjdouble *retNative = env->GetDoubleArrayElements(ret, 0);\n\t\t\n\t\t// Display result\n\t\tPN_PrintToMainLog(env, \"Optimal value for weights [\");\n\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\tPN_PrintToMainLog(env, \"%s%f\", (it>0?\",\":\"\"), weights[it]);\n\t\t}\n\t\tPN_PrintToMainLog(env, \"] from initial state: %f\\n\", soln[start_index]);\n\t\t\n\t\t//copy all computed elements\n\t\tfor (int it = 0; it < lenRew + lenProb; it++)\n\t\t\tif (it != ignoredWeight)\n\t\t\t\tretNative[it] = psoln[it][start_index];\n\t\t//compute the last element\n\t\tif (ignoredWeight != -1) {\n\t\t\tdouble last = soln[start_index];\n\t\t\tfor (int it = 0; it < lenRew + lenProb; it++)\n\t\t\t\tif (it != ignoredWeight)\n\t\t\t\t\tlast -= weights[it] * retNative[it];\n\t\t\tretNative[ignoredWeight] = (weights[ignoredWeight] > 0) ? (last / weights[ignoredWeight]) : 0.0;\n\t\t}\n\t\t\n\t\tenv->ReleaseDoubleArrayElements(ret, retNative, 0);\n\n\t\t// close file to store adversary (if required)\n\t\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t\tfclose(fp_adv);\n\t\t\tPN_PrintToMainLog(env, \"\\nAdversary written to file \\\"%s\\\".\\n\", export_adv_filename);\n\t\t}\n\n\t\t// export individual solution vectors\n\t\tif (export_adv_enabled != EXPORT_ADV_NONE && export_vectors) {\n\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\tstd::string export_vect_filename(export_adv_filename);\n\t\t\t\t\texport_vect_filename += \".vec\";\n\t\t\t\t\texport_vect_filename += std::to_string(it);\n\t\t\t\t\tFILE *fp_vect = fopen(export_vect_filename.c_str(), \"w\");\n\t\t\t\t\tif (fp_vect) {\n\t\t\t\t\t\tPN_PrintWarningToMainLog(env, \"Exporting solution vector %d to file %s.\", it, export_vect_filename.c_str());\n\t\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\t\tfprintf(fp_vect, \"%d %g\\n\", i, psoln[it][i]);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tfclose(fp_vect);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tret = 0;\n\t} catch (int e) {\n\t\tif (e==1) //1 means error was set above and exception was thrown to end the computation\n\t\t\tret = 0;\n\t\telse \n\t\t\tPN_SetErrorMessage(\"Unknown error.\");\n\t}\n\n\t// free memory\n\tif (soln2) delete[] soln2;\n\tif (soln) delete[] soln;\n\tif (yes_vec) delete[] yes_vec;\n\tif (h2_r) delete[] h2_r;\n\tif (l2_r) delete[] l2_r;\n\tif (k_r) delete[] k_r;\n\tif (pd1) delete[] pd1;\n\tif (pd2) delete[] pd2;\n\tfor (int it = 0; it < lenProb + lenRew; it++) {\n\t\tif (it != ignoredWeight) {\n\t\t\tif (psoln2[it]) delete[] psoln2[it];\n\t\t\tif (psoln[it]) delete[] psoln[it];\n\t\t}\n\t}\n\tif (psoln2) delete[] psoln2;\n\tif (psoln) delete[] psoln;\n\tif (adv) delete[] adv;\n\tif (action_names != NULL) {\n\t\trelease_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n\t}\n\n\treturn ret;\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetMultiObjGS.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//The following gives more output on stdout. In fact quite a lot of it, usable only for ~10 state examples \n//#define MORE_OUTPUT\n\n//The following number is used to determine when to consider a number equal to 0.\n//Will be multiplied by minimal weights to make sure we don't do too much roundoffs for small weights\n#define ZERO_ROUNDOFF 10e-11\n\nJNIEXPORT jdoubleArray __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetMultiObjGS\n(\n JNIEnv *env,\n jclass cls,\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv,  // nondet vars\n jint num_ndvars,\n jboolean min,        // min or max probabilities (true = min, false = max)\n jlong __jlongpointer _start, // initial state(s)\n jlong _adversary,\n jlong __jlongpointer _ndsm, //pointer to trans sparse matrix\n jlongArray _yes_vec, //pointer to yes vector array\n jlongArray  _ndsm_r, //pointer to reward sparse matrix array\n jdoubleArray _weights //weights of rewards and yes_vec vectors\n )\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(od);      // reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);   // row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);   // col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n\tDdNode *start = jlong_to_DdNode(_start); // initial state(s)\n    \n\t// mtbdds\n\tDdNode *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n, nc;\n\tlong nnz;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL;\n\tNDSparseMatrix **ndsm_r = NULL;\n\t// vectors\n\tdouble **yes_vec = NULL;\n\tdouble *soln = NULL, *tmpsoln = NULL;\n\tdouble **psoln = NULL;  \n    \n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// adversary stuff\n\tint export_adv_enabled = export_adv;\n\tFILE *fp_adv = NULL;\n\tint adv_j;\n\t//int *adv = NULL;\n\t// action info\n\tint *actions = NULL;\n\tjstring *action_names_jstrings;\n\tint num_actions;\n\t// misc\n\tint i, j, k, l1, h1, l2, h2, iters;\n\tint *k_r = NULL, *l2_r = NULL, *h2_r = NULL;\n\tdouble d1, d2, max_diff, kb, kbt;\n\tdouble *pd1 = NULL, *pd2 = NULL;\n\tbool done, weightedDone, first;\n\tconst char** action_names;\n\tint num_yes = 0;\n\tint start_index;\n\tunsigned int *row_starts1, *predecessors;\n\tunsigned int extra_node;\n\t// storage for result array (0 means error)\n\tjdoubleArray ret = 0;\n\t\n\t// Extract some info about objectives\n\tbool has_rewards = _ndsm_r != 0;\n\tbool has_yes_vec = _yes_vec != 0;\n\tjsize lenRew = (has_rewards) ? env->GetArrayLength(_ndsm_r) : 0;\n\tjsize lenProb = (has_yes_vec) ? env->GetArrayLength(_yes_vec) : 0;\n\tjlong *ptr_ndsm_r = (has_rewards) ? env->GetLongArrayElements(_ndsm_r, 0) : NULL;\n\tjlong *ptr_yes_vec = (has_yes_vec) ? env->GetLongArrayElements(_yes_vec, 0) : NULL;\n\tdouble* weights = env->GetDoubleArrayElements(_weights, 0);\n\t\n\t// We will ignore one of the rewards and compute its value from the other ones and\n\t// from the combined value. We must make sure that this reward has nonzero weight,\n\t// otherwise we can't compute it.\n\tint ignoredWeight = -1;\n\t\n\t/* HOTFIX: not used for numerical problems\n\tfor (i = lenProb + lenRew - 1; i>=0; i--) {\n\t\tif (weights[i] > 0) {\n\t\t\tignoredWeight = i;\n\t\t\tbreak;\n\t\t}\n\t}*/\n\t\n\t//determine the minimal nonzero weight\n\tdouble min_weight = 1;\n\tfor (i = 0; i < lenProb + lenRew; i++)\n\t\tif (weights[i] > 0 && weights[i] < min_weight)\n\t\t\tmin_weight = weights[i];\n\tdouble near_zero = min_weight * ZERO_ROUNDOFF;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\t// start clocks \n\t\tstart1 = start2 = util_cpu_time();\n\t\t\n\t\t// get number of states\n\t\tn = odd->eoff + odd->toff;\n\t\t\n\t\t// build sparse matrix\n\t\tndsm = (NDSparseMatrix *) jlong_to_NDSparseMatrix(_ndsm);\n\t\t\n\t\t// get number of transitions/choices\n\t\tnnz = ndsm->nnz;\n\t\tnc = ndsm->nc;\n\t\tkb = ndsm->mem;\n\t\tkbt = kb;\n\t\t\n\t\tNDSparseMatrix *ndsm_r[lenRew];\n\t\t\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tndsm_r[rewi] = (NDSparseMatrix *) jlong_to_NDSparseMatrix(ptr_ndsm_r[rewi]);\n\t\t\n\t\t// get vector for yes\n\t\tyes_vec = new double *[lenProb];\n\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\tyes_vec[probi] = (double *) jlong_to_ptr(ptr_yes_vec[probi]);\n\t\t}\n\t\t\n\t\tkb = n*8.0/1024.0;\n\t\tkbt += kb;\n\t\t\n\t\t// create solution/iteration vectors\n\t\tsoln = new double[n];\n\t\tpsoln = new double *[lenProb + lenRew];\n\t\tfor (int it = 0; it < lenProb + lenRew ; it++) {\n\t\t\tif (it != ignoredWeight) {\n\t\t\t\tpsoln[it] = new double[n];\n\t\t\t}\n\t\t}\n\t\tpd1 = new double[lenProb + lenRew];\n\t\tpd2 = new double[lenProb + lenRew];\n\t\t\n\t\tkb = n*8.0/1024.0;\n\t\tkbt += 2*kb;\n\t\t\n\t\t// Get index of single (first) initial state\n\t\tstart_index = get_index_of_first_from_bdd(ddman, start, rvars, num_rvars, odd);\n\t\t\n\t\t// initial solution\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t// combined value initialised to weighted sum of yes vectors\n\t\t\t// (for probability objectives) or 0 (for cumulative rewards)\n\t\t\tsoln[i] = 0;\n\t\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\t\tsoln[i] += weights[probi] * yes_vec[probi][i];\n\t\t\t}\n\t\t\t// individual objectives\n\t\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\t\tif (probi != ignoredWeight) {\n\t\t\t\t\tpsoln[probi][i] = 0;//yes_vec[probi][i];\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++) {\n\t\t\t\tif (lenProb + rewi != ignoredWeight) {\n\t\t\t\t\tpsoln[rewi + lenProb][i] = 0;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n#ifdef MORE_OUTPUT\n\t\tPN_PrintToMainLog(env, \"Initial soln: \");\n\t\tfor (int o = 0; o < n; o++)\n\t\t\tPN_PrintToMainLog(env, \"%f, \", soln[o]);\n\t\tPN_PrintToMainLog(env, \"\\n\");\n\t\t\n\t\t\n\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\tif (it != ignoredWeight) {\n\t\t\t\tPN_PrintToMainLog(env, \"psoln: \");\n\t\t\t\tfor (int o = 0; o < n; o++)\n\t\t\t\t\tPN_PrintToMainLog(env, \"%f, \", psoln[it][o]);\n\t\t\t\tPN_PrintToMainLog(env, \"\\n\");\n\t\t\t} else {\n\t\t\t\tPN_PrintToMainLog(env, \"psoln: (ignored)\\n\");\n\t\t\t}\n\t\t}\n#endif\n\t\t// get setup time\n\t\tstop = util_cpu_time();\n\t\ttime_for_setup = (double)(stop - start2)/1000;\n\t\tstart2 = stop;\n\t\t\n\t\t// start iterations\n\t\titers = 0;\n\t\tdone = false;\n\t\tweightedDone = false;\n\t\t//PN_PrintToMainLog(env, \"Starting iterations...\\n\");\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros = ndsm->non_zeros;\n\t\tunsigned char *row_counts = ndsm->row_counts;\n\t\tint *row_starts = (int *)ndsm->row_counts;\n\t\tunsigned char *choice_counts = ndsm->choice_counts;\n\t\tint *choice_starts = (int *)ndsm->choice_counts;\n\t\tbool use_counts = ndsm->use_counts;\n\t\tunsigned int *cols = ndsm->cols;\n\t\t\n\t\tdouble *non_zeros_r[lenRew];\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tnon_zeros_r[rewi] = ndsm_r[rewi]->non_zeros;\n\t\t\n\t\tunsigned char *choice_counts_r[lenRew];\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tchoice_counts_r[rewi] = ndsm_r[rewi]->choice_counts;\n\t\t\n\t\tint *choice_starts_r[lenRew];\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tchoice_starts_r[rewi] = (int*)ndsm_r[rewi]->choice_counts;\n\t\t\n\t\tunsigned int *cols_r[lenRew];\n\t\tfor(int rewi = 0; rewi < lenRew; rewi++)\n\t\t\tcols_r[rewi] = ndsm_r[rewi]->cols;\n\t\t\n\t\th2_r = new int[lenRew];\n\t\tl2_r = new int[lenRew];\n\t\tk_r = new int[lenRew];\n\t\twhile (!done && iters < max_iters) {\n\t\t\titers++;\n\t\t\tmax_diff = 0;  \n\t\t\t\n\t\t\t// do matrix multiplication and min/max\n\t\t\th1 = h2 = 0;\n\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++)\n\t\t\t\th2_r[rewi] = 0;\n\t\t\t\n\t\t\t// loop through states\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tfirst = true;\n\t\t\t\t\n\t\t\t\t// first, get the decision of the adversary optimizing the combined reward\n\t\t\t\td1 = -INFINITY;\n\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++)\n\t\t\t\t\tif (it != ignoredWeight)\n\t\t\t\t\t\tpd1[it] = -INFINITY;\n\t\t\t\t\n\t\t\t\t// get pointers to nondeterministic choices for state i\n\t\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t\t// loop through those choices\n\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\t// compute, for state i for this iteration,\n\t\t\t\t\t// the combined and individual reward values\n\t\t\t\t\t// start with 0 (we don't have any state rewards)\n\t\t\t\t\td2 = 0;\n\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++)\n\t\t\t\t\t\tif (it != ignoredWeight)\n\t\t\t\t\t\t\tpd2[it] = 0;\n\t\t\t\t\t// get pointers to transitions\n\t\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t\t// and get pointers to transition rewards\n\t\t\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++) {\n\t\t\t\t\t\tif (!ndsm_r[rewi]->use_counts) {\n\t\t\t\t\t\t\tl2_r[rewi] = choice_starts_r[rewi][j];\n\t\t\t\t\t\t\th2_r[rewi] = choice_starts_r[rewi][j+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2_r[rewi] = h2_r[rewi];\n\t\t\t\t\t\t\th2_r[rewi] += choice_counts_r[rewi][j];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// loop through transitions\n\t\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t\t// for each reward structure\n\t\t\t\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++) {\n\t\t\t\t\t\t\t// find corresponding transition reward if any\n\t\t\t\t\t\t\tk_r[rewi] = l2_r[rewi];\n\t\t\t\t\t\t\twhile (k_r[rewi] < h2_r[rewi] && cols_r[rewi][k_r[rewi]] != cols[k]) k_r[rewi]++;\n\t\t\t\t\t\t\t// if there is one, add reward * prob to combined and individual reward values\n\t\t\t\t\t\t\tif (k_r[rewi] < h2_r[rewi]) {\n\t\t\t\t\t\t\t\td2 += weights[rewi + lenProb] * non_zeros_r[rewi][k_r[rewi]] * non_zeros[k];\n\t\t\t\t\t\t\t\tif (lenProb + rewi != ignoredWeight) {\n\t\t\t\t\t\t\t\t\tpd2[rewi + lenProb] += non_zeros_r[rewi][k_r[rewi]] * non_zeros[k];\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tk_r[rewi]++;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// add prob * corresponding reward from previous iteration\n\t\t\t\t\t\t// (for both combined and individual rewards)\n\t\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\t\t\t\tpd2[it] += non_zeros[k] * psoln[it][cols[k]];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\td2 += non_zeros[k] * soln[cols[k]];\n\t\t\t\t\t}\n\t\t\t\t\t// see if the combined reward value is the min/max so far\n\t\t\t\t\tbool pickThis = first || (min&&(d2<d1)) || (!min&&(d2>d1));\n\t\t\t\t\t//HOTFIX for cumulative reward\n\t\t\t\t\tif (!pickThis && (d2==d1)) {\n\t\t\t\t\t\tfor (int it = 0; it < lenProb + lenRew; it++) {\n\t\t\t\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\t\t\t\tif ((min&&(pd2[it]<pd1[it])) || (!min&&(pd2[it]>pd1[it]))) {\n\t\t\t\t\t\t\t\t\tpickThis = true;\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tif (pickThis) {\n\t\t\t\t\t\t// store optimal values for combined and individual rewards\n\t\t\t\t\t\tif (fabs(d2) < near_zero)\n\t\t\t\t\t\t\td1 = 0;\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\td1 = d2;\n\t\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\t\t\t\tif (fabs(pd2[it]) < near_zero)\n\t\t\t\t\t\t\t\t\tpd1[it] = 0; //round off small numbers to 0\n\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\tpd1[it] = pd2[it];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tfirst = false;\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// HOTFIX: it seems that on self loops d1 can be unchanged because the other for cycle is not executed, which is not desirable\n\t\t\t\tif (d1 == -INFINITY) {\n\t\t\t\t\td1 = 0;\n\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\t\t\tpd1[it] = 0;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tdouble val_yes = 0.0;  \n\t\t\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\t\t\tif (probi != ignoredWeight && yes_vec[probi]!=NULL) {\n\t\t\t\t\t\tval_yes += weights[probi] * yes_vec[probi][i];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t//TODO: we need to handle val_yes somehow\n\t\t\t\tif (val_yes == 0 || d1>val_yes)\n\t\t\t\t{\n\t\t\t\t\tswitch (term_crit) {\n\t\t\t\t\t\tcase TERM_CRIT_RELATIVE:\n\t\t\t\t\t\t\tif (fabs((soln[i] - d1)/d1) > max_diff)\n\t\t\t\t\t\t\t\tmax_diff = fabs((soln[i] - d1)/d1);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\t\t\t\t\tif (fabs(soln[i] - d1) > max_diff)\n\t\t\t\t\t\t\t\tmax_diff = fabs(soln[i] - d1);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\n\t\t\t\t\tsoln[i] = d1;\n\t\t\t\t\t\n\t\t\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\t\t\tswitch (term_crit) {\n\t\t\t\t\t\t\t\tcase TERM_CRIT_RELATIVE:\n\t\t\t\t\t\t\t\t\tif (weightedDone && fabs((psoln[it][i] - pd1[it])/pd1[it]) > max_diff)\n\t\t\t\t\t\t\t\t\t\tmax_diff = fabs((psoln[it][i] - pd1[it])/pd1[it]);\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\t\t\t\t\t\t\tif (weightedDone && fabs(psoln[it][i] - pd1[it]) > max_diff)\n\t\t\t\t\t\t\t\t\t\tmax_diff = fabs(psoln[it][i] - pd1[it]);\n\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tpsoln[it][i] = pd1[it];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tdouble tmpval = 0;\n\t\t\t\t\t\n\t\t\t\t\tfor (int probi = 0; probi < lenProb; probi++)\n\t\t\t\t\t\ttmpval += weights[probi] * yes_vec[probi][i];\n\t\t\t\t\t\n\t\t\t\t\t//NB we don't round tmpval to zero, it should not be\n\t\t\t\t\t//too small given that it'sonly based on weights and yes_vec\n\t\t\t\t\t\n\t\t\t\t\tswitch (term_crit) {\n\t\t\t\t\t\tcase TERM_CRIT_RELATIVE:\n\t\t\t\t\t\t\tif (fabs((soln[i] - tmpval)/tmpval) > max_diff)\n\t\t\t\t\t\t\t\tmax_diff = fabs((soln[i] - tmpval)/tmpval);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\t\t\t\t\tif (fabs(soln[i] - tmpval) > max_diff)\n\t\t\t\t\t\t\t\tmax_diff = fabs(soln[i] - tmpval);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\n\t\t\t\t\tsoln[i]=tmpval;\n\t\t\t\t\t\n\t\t\t\t\tfor (int probi = 0; probi < lenProb; probi++) {\n\t\t\t\t\t\tif (probi != ignoredWeight) {\n\t\t\t\t\t\t\tswitch (term_crit) {\n\t\t\t\t\t\t\t\tcase TERM_CRIT_RELATIVE:\n\t\t\t\t\t\t\t\t\tif (weightedDone && fabs((psoln[probi][i] - yes_vec[probi][i])/yes_vec[probi][i]) > max_diff)\n\t\t\t\t\t\t\t\t\t\tmax_diff = fabs((psoln[probi][i] -  yes_vec[probi][i])/yes_vec[probi][i]);\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\tcase TERM_CRIT_ABSOLUTE:\n\t\t\t\t\t\t\t\t\tif (weightedDone && fabs(psoln[probi][i] - yes_vec[probi][i]) > max_diff)\n\t\t\t\t\t\t\t\t\t\tmax_diff = fabs(psoln[probi][i] -  yes_vec[probi][i]);\n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tpsoln[probi][i] = yes_vec[probi][i];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tfor (int rewi = 0; rewi < lenRew; rewi++) {\n\t\t\t\t\t\tif (lenProb + rewi != ignoredWeight)\n\t\t\t\t\t\t\tpsoln[rewi + lenProb][i] = 0;\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t}\n\t\t\t}\n\n#ifdef MORE_OUTPUT\n\t\t\tPN_PrintToMainLog(env, \"soln: \");\n\t\t\tfor (int o = 0; o < n; o++)\n\t\t\t\tPN_PrintToMainLog(env, \"%e, \", soln[o]);\n\t\t\tPN_PrintToMainLog(env, \"\\n\");\n\n\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\tPN_PrintToMainLog(env, \"psoln: \");\n\t\t\t\t\tfor (int o = 0; o < n; o++)\n\t\t\t\t\t\tPN_PrintToMainLog(env, \"%e, \", psoln[it][o]);\n\t\t\t\t\tPN_PrintToMainLog(env, \"\\n\");\n\t\t\t\t} else {\n\t\t\t\t\tPN_PrintToMainLog(env, \"psoln: (ignored)\\n\");\n\t\t\t\t}\n\t\t\t}\n#endif\n\t\t\t\n\t\t\t// check convergence\n\t\t\t// (note: doing outside loop means may not need to check all elements)\n\t\t\t\n\t\t\tif (!weightedDone) {\n\t\t\t\tif (max_diff <= term_crit_param) {\n\t\t\t\t\tweightedDone = true;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (max_diff <= term_crit_param) {\n\t\t\t\t\tdone = true;\n\t\t\t\t}\t\t\t\t\n\t\t\t}\n\t\t}\n\t\t\n\t\t// stop clocks\n\t\tstop = util_cpu_time();\n\t\ttime_for_iters = (double)(stop - start2)/1000;\n\t\ttime_taken = (double)(stop - start1)/1000;\n\t\t\n\t\t// print iterations/timing info\n\t\tPN_PrintToMainLog(env, \"Iterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\t\n\t\t// if the iterative method didn't terminate, this is an error\n\t\tif (iters == max_iters) {\n\t\t\tPN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\t\tthrow 1;\n\t\t}\n\n\t\t//store the result\n\t\tret = env->NewDoubleArray(lenProb + lenRew);\n\t\tjdouble *retNative = env->GetDoubleArrayElements(ret, 0);\n\n\t\t//copy all computed elements\n\t\tfor (int it = 0; it < lenRew + lenProb; it++)\t\t\n\t\t\tif (it != ignoredWeight)\n\t\t\t\tretNative[it] = max_double_vector_over_bdd(ddman, psoln[it], start, rvars, num_rvars, odd);\n\t\t//compute the last element\n\t\tif (ignoredWeight != -1) {\n\t\t\tdouble last = max_double_vector_over_bdd(ddman, soln, start, rvars, num_rvars, odd);\n\t\t\tfor (int it = 0; it < lenRew + lenProb; it++) {\n\t\t\t\tif (it != ignoredWeight) {\n\t\t\t\t\tlast -= weights[it] * retNative[it];\n\t\t\t\t}\n\t\t\t}\n\t\t\tretNative[ignoredWeight] = (weights[ignoredWeight] > 0) ? (last / weights[ignoredWeight]) : 0.0;\n\t\t}\n\t\tenv->ReleaseDoubleArrayElements(ret, retNative, 0);\n\t\t\n\t\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t} catch (int e) {\n\t\tif (e==1) //1 means error was set above and exception was thrown to end the computation\n\t\t\tret = 0;\n\t\telse \n\t\t\tPN_SetErrorMessage(\"Unknown error.\");\n\t}\n\t\n\tif (soln) delete[] soln;\n\tif (yes_vec) delete[] yes_vec; \n\tif (h2_r) delete[] h2_r;\n\tif (l2_r) delete[] l2_r;\n\tif (k_r) delete[] k_r;\n\tif (pd1) delete[] pd1;\n\tif (pd2) delete[] pd2;\n\tfor (int it = 0; it < lenProb + lenRew; it++) {\n\t\tif (it != ignoredWeight)\n\t\t\tif (psoln && psoln[it]) delete[] psoln[it];\n\t}\n\tif (psoln) delete[] psoln;\n\tif (actions != NULL) {\n\t\tdelete[] actions;\n\t\trelease_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n\t}  \n\n\treturn ret;\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetMultiReach.cc",
    "content": "//==============================================================================\n//  \n//  Copyright (c) 2002-\n//  Authors:\n//  * Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//  * Hongyang Qu <hongyang.qu@comlab.ox.ac.uk> (University of Oxford)\n//  \n//------------------------------------------------------------------------------\n//  \n//  This file is part of PRISM.\n//  \n//  PRISM is free software; you can redistribute it and/or modify\n//  it under the terms of the GNU General Public License as published by\n//  the Free Software Foundation; either version 2 of the License, or\n//  (at your option) any later version.\n//  \n//  PRISM is distributed in the hope that it will be useful,\n//  but WITHOUT ANY WARRANTY; without even the implied warranty of\n//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//  GNU General Public License for more details.\n//  \n//  You should have received a copy of the GNU General Public License\n//  along with PRISM; if not, write to the Free Software Foundation,\n//  Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//  \n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"sparse_adv.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n#include \"lp_lib.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReach\n(\n JNIEnv *env,\n jclass cls,\n jlong __jlongpointer t, // trans matrix\n jlong __jlongpointer ta, // trans action labels\n jobject synchs,\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv, // nondet vars\n jint num_ndvars,\n jlongArray _targets, // target state sets\n jintArray _relops, // target relops (0:=?, 1:>, 2:>=)\n jdoubleArray _bounds, // target probability bounds\n jlong __jlongpointer m, // 'maybe' states\n jlong __jlongpointer _start // initial state(s)\n )\n{\n  // cast function parameters\n  DdNode *trans = jlong_to_DdNode(t); // trans matrix\n  DdNode *trans_actions = jlong_to_DdNode(ta);  // trans action labels\n  ODDNode *odd = jlong_to_ODDNode(od); // reachable states\n  DdNode **rvars = jlong_to_DdNode_array(rv); // row vars\n  DdNode **cvars = jlong_to_DdNode_array(cv); // col vars\n  DdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n  DdNode *maybe = jlong_to_DdNode(m); // 'maybe' states\n  DdNode *start = jlong_to_DdNode(_start); // initial state(s)\n\n  // target info  \n  jlong *target_ptrs = NULL;\n  DdNode **targets = NULL;\n  jint *relops = NULL;\n  double *bounds = NULL;\n  // mtbdds\n  DdNode *a = NULL, **yes = NULL, *maybe_yes = NULL, *loops = NULL, *tmp = NULL;\n  // model stats\n  int num_targets, n, nc, nc_r;\n  long nnz, nnz_r;\n  // sparse matrix\n  NDSparseMatrix *ndsm = NULL, *ndsm_r = NULL;\n  // action info\n  jstring *action_names_jstrings;\n  const char** action_names = NULL;\n  int num_actions;\n  // vectors\n  double **yes_vecs, *maybe_vec = NULL/*, *maybe_vec_r = NULL*/;\n  // timing stuff\n  long start1, start2, start3, stop, stop2;\n  double time_taken, time_for_setup, time_for_lp;\n  // lp stuff\n  lprec *lp = NULL;\n  REAL *arr_reals = NULL;// *lp_soln = NULL;\n  int *arr_ints = NULL;\n  bool selfloop;\n  int arr_size, res;\n  int num_lp_vars;\n  double *lp_soln;\n  double lp_result = 0.0;\n  bool lp_solved = false;\n  // misc\n  int i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, start_index, count;\n  double d1, d2, kb, kbt;\n  bool done, first;\n  jclass vn_cls;\n  jmethodID vn_mid;\n\n  // exception handling around whole function\n  try {\n\n    // start clocks \n    start1 = start2 = util_cpu_time();\n    \n    // Extract arrays of target info from function parameters\n    num_targets = (int)env->GetArrayLength(_targets);\n    target_ptrs = env->GetLongArrayElements(_targets, 0);\n    targets = new DdNode*[num_targets];\n    for (i = 0; i < num_targets; i++) targets[i] = jlong_to_DdNode(target_ptrs[i]);\n    relops = env->GetIntArrayElements(_relops, 0);\n    bounds = env->GetDoubleArrayElements(_bounds, 0);\n    yes = new DdNode*[num_targets];\n    yes_vecs = new double*[num_targets];\n    for(i=0; i<num_targets; i++) yes[i] = targets[i];\n  \n    // Display some info about the targets\n    PN_PrintToMainLog(env, \"\\n%d Targets:\\n\", num_targets);\n    for (i = 0; i < num_targets; i++) {\n      PN_PrintToMainLog(env, \"#%d: \", i);\n      switch (relops[i]) {\n      case 0: PN_PrintToMainLog(env, \"Pmax=?\"); break;\n      case 1: PN_PrintToMainLog(env, \"P>%g\", bounds[i]); break;\n      case 2: PN_PrintToMainLog(env, \"P>=%g\", bounds[i]); break;\n      }\n      PN_PrintToMainLog(env, \" (%.0f states)\\n\", DD_GetNumMinterms(ddman, targets[i], num_rvars));\n    }\n  \n    // Filter out rows, store in \"a\"\n    Cudd_Ref(maybe);\n    maybe_yes = maybe;\n    for (i = 0; i < num_targets; i++) {\n      Cudd_Ref(yes[i]);\n      maybe_yes = DD_Or(ddman, maybe_yes, yes[i]);\n    }\n    Cudd_Ref(trans);\n    Cudd_Ref(maybe_yes);\n    a = DD_Apply(ddman, APPLY_TIMES, trans, maybe_yes);\n\n    // For efficiency, remove any probability 1 self-loops from the model.\n    // For multi-objective, we always do maximum reachability, so these do not matter.\n    Cudd_Ref(a);\n    loops = DD_And(ddman, DD_Equals(ddman, a, 1.0), DD_Identity(ddman, rvars, cvars, num_rvars));\n    loops = DD_ThereExists(ddman, loops, cvars, num_rvars);\n    Cudd_Ref(loops);\n    a = DD_ITE(ddman, loops, DD_Constant(ddman, 0), a);\n    \n    // Get number of states\n    n = odd->eoff + odd->toff;\n\n    // Build sparse matrix\n    PN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n    ndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n    // Get number of transitions/choices\n    nnz = ndsm->nnz;\n    nc = ndsm->nc;\n    kb = ndsm->mem;\n    kbt = kb;\n    // print out info\n    PN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n    // If needed, and if info is available, build a vector of action indices for the MDP\n    if (export_adv != EXPORT_ADV_NONE) {\n      if (trans_actions != NULL) {\n        PN_PrintToMainLog(env, \"Building action information... \");\n        // first need to filter out unwanted rows\n        Cudd_Ref(trans_actions);\n        Cudd_Ref(maybe_yes);\n        tmp = DD_Apply(ddman, APPLY_TIMES, trans_actions, maybe_yes);\n        Cudd_Ref(loops);\n        tmp = DD_ITE(ddman, loops, DD_Constant(ddman, 0), tmp);\n        // then convert to a vector of integer indices\n        build_nd_action_vector(ddman, a, tmp, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n        Cudd_RecursiveDeref(ddman, tmp);\n        kb = n*4.0/1024.0;\n        kbt += kb;\n        PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n        // also extract list of action names from 'synchs'\n        get_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n      } else {\n        PN_PrintWarningToMainLog(env, \"Action labels are not available for adversary generation.\");\n      }\n    }\n  \n    // Get vectors for yes/maybe\n    PN_PrintToMainLog(env, \"Creating vectors for yes... \");\n    for(i=0; i<num_targets; i++) {\n      yes_vecs[i] = mtbdd_to_double_vector(ddman, yes[i], rvars, num_rvars, odd);\n    }\n    kb = n*sizeof(int)/1024.0;\n    kbt += num_targets * kb;\n    PN_PrintToMainLog(env, \"[%d x \", num_targets);\n    PN_PrintMemoryToMainLog(env, \"\", kb, \"]\\n\");\n    PN_PrintToMainLog(env, \"Creating vector for maybe... \");\n    maybe_vec = mtbdd_to_double_vector(ddman, maybe, rvars, num_rvars, odd);\n    kb = n*8.0/1024.0;\n    kbt += kb;\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n    // Get index of single (first) initial state\n    start_index = get_index_of_first_from_bdd(ddman, start, rvars, num_rvars, odd);\n    PN_PrintToMainLog(env, \"Initial state index: %1d\\n\", start_index);\n\n    // Print total memory usage\n    PN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n    // Store local copies of sparse matrix stuff\n    double *non_zeros = ndsm->non_zeros;\n    unsigned char *row_counts = ndsm->row_counts;\n    int *row_starts = (int *)ndsm->row_counts;\n    unsigned char *choice_counts = ndsm->choice_counts;\n    int *choice_starts = (int *)ndsm->choice_counts;\n    bool use_counts = ndsm->use_counts;\n    unsigned int *cols = ndsm->cols;\n\n    // Set up LP problem...\n    PN_PrintToMainLog(env, \"\\nBuilding LP problem...\\n\");\n    \n    int *yes_vec;\n    int *map_var;\n\n    yes_vec = new int[n];\n    map_var = new int[n+1];\n\n    arr_ints = new int[n];\n    int sp;\n\n    \n    // Compute the number of LP variables needed\n    // (one per choice for each 'maybe'/'yes' state + one extra for each yes state)\n    // Also build map_var (mapping from states to first corresponding LP var)\n    // Init counters (maybe_nc/yes_nc = num maybe/yes choices, yes_count = num yes, count = num vars so far)\n    int maybe_nc = 0;\n    int yes_nc = 0;\n    int yes_count = 0;\n    count = 0;\n    // Traverse sparse matrix to get info\n    h1 = h2 = 0;\n    for (i = 0; i < n; i++) {\n      if (!use_counts) {\n        l1 = row_starts[i];\n        h1 = row_starts[i+1];\n      } else {\n        l1 = h1;\n        h1 += row_counts[i];\n      }\n      k=0;\n      for (j = l1; j < h1; j++) {\n        if (!use_counts) {\n          l2 = choice_starts[j];\n          h2 = choice_starts[j+1];\n        } else {\n          l2 = h2;\n          h2 += choice_counts[j];\n        }\n        k++;\n      }\n      // Store first LP var for state i\n      map_var[i] = count;\n      // If a maybe state...\n      if (maybe_vec[i] > 0) {\n        maybe_nc += k;\n        count += k;\n      }\n      else {\n        for (j=0; j<num_targets; j++) {\n          // If a yes state...\n          if (yes_vecs[j][i] > 0) {\n            yes_nc += k;\n            yes_count ++; // each target state has one extra action\n            count += k+1;\n            // Skip any further targets for this state\n            break;\n          }\n        }\n      }\n    }\n    // Compute total var count\n    num_lp_vars = maybe_nc + yes_nc + yes_count;\n    // Store first LP var for final state\n    map_var[n] = num_lp_vars; // maybe need to be modified.   \n    PN_PrintToMainLog(env, \"Number of LP variables = %1d\\n\", num_lp_vars);\n\n    for(i=0; i<n; i++)\n      yes_vec[i] = 0;\n    for(i=0; i<n; i++) {\n      for(j=0; j<num_targets; j++) {\n        if(yes_vecs[j][i]> 0) { // For each state, count the number of targets it belongs to.\n          yes_vec[i]++;\n        }\n      }\n    }\n\n    /*printf(\"map_var = \");\n      for(i=0; i<=n; i++)\n      printf(\" %1d\", map_var[i]);\n      printf(\"\\n\");\n      fflush(stdout);*/\n\n    h1 = h2 = 0;\n    for(i=0; i<n; i++)\n      arr_ints[i] = map_var[i+1]-map_var[i];\n    for (i = 0; i < n; i++) {\n      if (!use_counts) {\n        l1 = row_starts[i];\n        h1 = row_starts[i+1];\n      } else {\n        l1 = h1;\n        h1 += row_counts[i];\n      }\n      for (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n        if (!use_counts) {\n          l2 = choice_starts[j];\n          h2 = choice_starts[j+1];\n        } else {\n          l2 = h2;\n          h2 += choice_counts[j];\n        }\n        if (maybe_vec[i]> 0 || yes_vec[i]> 0)\n          for(k=l2; k<h2; k++) {\n            if(maybe_vec[cols[k]]> 0 || yes_vec[cols[k]]> 0)\n              arr_ints[cols[k]]++;\n          }\n      }\n    }\n    int *constraints_sp;\n    int *constraints_ints;\n    double *constraints_reals;\n    int **constraints_int_ptr;\n    double **constraints_real_ptr;\n    constraints_sp = new int[n];\n    constraints_int_ptr = new int*[n];\n    constraints_real_ptr = new double*[n];\n    for(i=0; i<n; i++)\n      if(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n        //printf(\"i = %1d, \", i);\n        constraints_ints = new int[arr_ints[i]];\n        constraints_reals = new REAL[arr_ints[i]];\n        constraints_sp[i] = map_var[i+1]-map_var[i];\n        constraints_int_ptr[i] = constraints_ints;\n        constraints_real_ptr[i] = constraints_reals;\n        for(j=0; j<map_var[i+1]-map_var[i]; j++) {\n          constraints_ints[j] = map_var[i] + j + 1; // index starts at 1 in lp_solve\n          constraints_reals[j] = 1.0;\n        }\n        for(j=map_var[i+1]-map_var[i]; j<arr_ints[i]; j++) {\n          constraints_ints[j] = -1;\n          constraints_reals[j] = 0;\n        }\n      }\n\n    arr_reals = new REAL[num_lp_vars];\n\n    if ((lp=make_lp(0, num_lp_vars)) == NULL) throw \"Could not create LP problem\";\n    // Lower verbosity: Warnings and errors only\n    set_verbose(lp, IMPORTANT);\n    // Set mode: will create row by row\n    set_add_rowmode(lp, true);\n\n    // Add constraints to LP problem\n    int x;\n    h1 = h2 = 0;\n    for (x = 0; x < n; x++) { // h2: row index\n      if(maybe_vec[x]> 0 || yes_vec[x]> 0) {\n        if (!use_counts) {\n          l1 = row_starts[x];\n          h1 = row_starts[x+1];\n        } else {\n          l1 = h1;\n          h1 += row_counts[x];\n        }\n        count = 0;\n        for (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n          if (!use_counts) {\n            l2 = choice_starts[j];\n            h2 = choice_starts[j+1];\n          } else {\n            l2 = h2;\n            h2 += choice_counts[j];\n          }\n          for(k=l2; k<h2; k++) { // k: column index\n            // get the index of the corresponding variable\n            i = cols[k];\n            if(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n              constraints_ints = constraints_int_ptr[i];\n              constraints_reals = constraints_real_ptr[i];\n              for(k_r=0; k_r<constraints_sp[i]; k_r++)\n                if(constraints_ints[k_r]==map_var[x]+j-l1-count+1)\n                  break;\n\n              if(k_r == constraints_sp[i]) {\n                //count++;\n                constraints_ints[k_r]=map_var[x]+j-l1-count + 1; // index starts at 1 in lp_solve\n                constraints_reals[k_r] = -non_zeros[k];\n                constraints_sp[i]++;\n              } else {\n                constraints_reals[k_r] -= non_zeros[k];\n                if(constraints_reals[k_r] == 0.0) { // In fact, this cannot happen.\n                  //count--;\n                  for(l2_r=k_r; l2_r<constraints_sp[i]-1; l2_r++) {\n                    constraints_reals[l2_r] = constraints_reals[l2_r+1];\n                    constraints_ints[l2_r] = constraints_ints[l2_r+1];\n                  }\n                  constraints_sp[i]--;\n                }\n              }\n            }\n          }\n        }\n      } else if(use_counts) {\n        l1 = h1;\n        h1 += row_counts[x];\n        for (j = l1; j < h1; j++)\n          h2 += choice_counts[j];\n      }\n    }\n\n    for (i = 0; i < n; i++)\n      if (maybe_vec[i]> 0 || yes_vec[i]> 0) {\n        constraints_ints = constraints_int_ptr[i];\n        constraints_reals = constraints_real_ptr[i];\n        add_constraintex(lp, constraints_sp[i], constraints_reals, constraints_ints, EQ, (start_index==i ? 1.0 : 0.0));\n        delete[] constraints_ints;\n        delete[] constraints_reals;\n      }\n    delete[] constraints_sp;\n    delete[] constraints_int_ptr;\n    delete[] constraints_real_ptr;\n    \n    // Add LP constraints for bounded (non-quantitative) objectives\n    PN_PrintToMainLog(env, \"Adding extra constraints for bounded objectives...\\n\");\n    constraints_ints = new int[num_lp_vars];\n    for (i=0; i<num_targets; i++) {\n      // Skip quantitative constraint\n      if (relops[i]==0 || relops[i]>2)\n        continue;\n      count = 0;\n      for(k=0; k<n; k++) {\n        if(yes_vecs[i][k]> 0) {\n          constraints_ints[count] = map_var[k+1];\n          arr_reals[count] = 1.0;\n          count++;\n        }\n      }\n      add_constraintex(lp, count, arr_reals, constraints_ints, GE, bounds[i]);\n    }\n\n    // Set objective function for LP\n    PN_PrintToMainLog(env, \"Setting objective...\\n\");\n    x = 0;\n    if(relops[0]> 0 && relops[0]<=2) {\n      for(i=0; i<n; i++) {\n        if(yes_vec[i]> 0) {\n          constraints_ints[x] = map_var[i+1];\n          arr_reals[x++] = 1.0;\n        }\n      }\n    } else if(relops[0] == 0) {\n      for(i=0; i<n; i++)\n        if(yes_vecs[0][i]> 0) {\n          constraints_ints[x] = map_var[i+1];\n          arr_reals[x++] = 1.0;\n        }\n    }\n    set_maxim(lp);\n    set_obj_fnex(lp, x, arr_reals, constraints_ints);\n    delete[] constraints_ints;\n    \n    // Finished building LP problem\n    set_add_rowmode(lp, false);\n    \n    // Get setup time\n    stop = util_cpu_time();\n    time_for_setup = (double)(stop - start2)/1000;\n    start2 = stop;\n    \n    // Export the MDP to a dot file\n    //export_model(ndsm, n, yes_vec, start_index);\n    \n    // Solve the LP, extract result\n    PN_PrintToMainLog(env, \"Solving LP problem...\\n\");\n    res = solve(lp);\n      \n    //Get LP solving time\n    stop2 = util_cpu_time();  \n    time_for_lp = (double)(stop2 - start2)/1000;\n      \n    if (res != 0) {\n      PN_PrintToMainLog(env, \"No solution\\n\");\n      lp_solved = false;\n    } else {\n      lp_solved = true;\n      lp_result = get_objective(lp);\n      lp_soln = new double[num_lp_vars];\n      get_ptr_variables(lp, &lp_soln);\n        \n      // Generate adversary from the solution, if required\n      if (export_adv != EXPORT_ADV_NONE) {\n\t\t// Adversary generation\n\t\texport_adversary_ltl_tra(export_adv_filename, ndsm, ndsm->actions, action_names, yes_vec, maybe_vec, num_lp_vars, map_var, lp_soln, start_index);\n\t\t//export_adversary_ltl_dot(env, ndsm, n, nnz, yes_vec, maybe_vec, num_lp_vars, map_var, lp_soln, start_index);\n      }\n      /*for (i=0; i<num_lp_vars; i++) {\n        if(lp_soln[i] != 0) {\n          PN_PrintToMainLog(env, \"X%d = %g    \", i, lp_soln[i]);\n          count++;\n        }\n        if(count == 8) {\n          PN_PrintToMainLog(env, \"\\n\");\n          count = 0;\n        }\n      }\n      if(count)\n\t\t\tPN_PrintToMainLog(env, \"\\n\");*/\n    }\n\n    // Modify result based on type\n    if (relops[0] > 0) {\n      // for qualitative queries, return 1/0 for existence of solution or not\n      PN_PrintToMainLog(env, \"LP problem solution %sfound so result is %s\\n\",  lp_solved ? \"\" : \"not \", lp_solved ? \"true\" : \"false\");\n      lp_result = lp_solved ? 1.0 : 0.0;\n    } else {\n      // return NaN for quantitative queries that can't be solved\n      PN_PrintToMainLog(env, \"LP problem solution %sfound; result is %f\\n\",  lp_solved ? \"\" : \"not \", lp_result);\n      if (!lp_solved) lp_result = NAN;\n    }\n  \n    // Print timing info\n    time_taken = time_for_setup + time_for_lp;\n    PN_PrintToMainLog(env, \"\\nLP problem solved in %.2f seconds (setup %.2f, lpsolve %.2f)\\n\", time_taken, time_for_setup, time_for_lp);\n\n    delete yes_vec;\n    delete map_var;\n    \n    // Catch exceptions: register error\n  } catch (std::bad_alloc e) {\n    PN_SetErrorMessage(\"Out of memory\");\n    lp_result = NAN;\n  }\n\n  // Free memory\n  if (lp) delete_lp(lp);\n  if (a) Cudd_RecursiveDeref(ddman, a);\n  if (maybe_yes) Cudd_RecursiveDeref(ddman, maybe_yes);\n  if (loops) Cudd_RecursiveDeref(ddman, loops);\n  if (ndsm) delete ndsm;\n  if (ndsm_r) delete ndsm_r;\n  delete[] maybe_vec;\n  for (i = 0; i < num_targets; i++)\n    delete[] yes_vecs[i];\n  delete[] arr_reals;\n  delete[] arr_ints;\n  if (target_ptrs) env->ReleaseLongArrayElements(_targets, target_ptrs, 0);\n  if (relops) env->ReleaseIntArrayElements(_relops, relops, 0);\n  if (bounds) env->ReleaseDoubleArrayElements(_bounds, bounds, 0);\n  if (action_names != NULL) {\n    release_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n  }\n\n  return lp_result;\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetMultiReach.cc.withrewards",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Hongyang Qu <hongyang.qu@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.\tSee the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA\t02111-1307\tUSA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n#include \"eclipse.h\"\n\ntypedef double REAL;\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReach\n(\n\t\tJNIEnv *env,\n\t\tjclass cls,\n\t\tjlong __jlongpointer t, // trans matrix\n\t\tjlong __jlongpointer od, // odd\n\t\tjlong __jlongpointer rv, // row vars\n\t\tjint num_rvars,\n\t\tjlong __jlongpointer cv, // col vars\n\t\tjint num_cvars,\n\t\tjlong __jlongpointer ndv, // nondet vars\n\t\tjint num_ndvars,\n\t\tjlongArray _targets, // target state sets\n\t\tjintArray _relops, // target relops (0:=?, 1:>, 2:>=)\n\t\tjdoubleArray _bounds, // target probability bounds\n\t\tjlong __jlongpointer m, // 'maybe' states\n\t\tjlong __jlongpointer _start, // initial state(s)\n\t\tjint checkReach, // reachability analysis or LTL model checking\n\n\t\tjlong __jlongpointer m_r, // 'maybe' states for the reward formula\n\t\tjlong __jlongpointer trr // transition rewards\n\t\t// Reward paramters for more complicated cases\n\t\t//jlongArray _rewards,\t// sets of rewards for reward formulas\n\t\t//jlongArray _targets_r,\t// target state sets for reward formulas\n\t\t//jdoubleArray _bounds_r,\t// target probability bounds for reward formulas\n\t\t//jlongArray _maybe_r,\t// maybe state sets for reward formulas\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t); // trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); // reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); // row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); // col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n\tDdNode *maybe = jlong_to_DdNode(m); // 'maybe' states\n\t//DdNode *maybe_r = jlong_to_DdNode(m_r); \t// 'maybe' states for the reward formula\n\tDdNode *start = jlong_to_DdNode(_start); // initial state(s)\n\tDdNode *trans_rewards = NULL; // transition rewards\n\n\t// target info\t\n\tjlong *target_ptrs = NULL;\n\tDdNode **targets = NULL;\n\tjint *relops = NULL;\n\tdouble *bounds = NULL;\n\t// mtbdds\n\tDdNode *a = NULL;\n\t// model stats\n\tint num_targets, n, nc, nc_r;\n\tlong nnz, nnz_r;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL, *ndsm_r = NULL;\n\t// vectors\n\tdouble *yes1_vec = NULL, *yes2_vec = NULL, *maybe_vec = NULL/*, *maybe_vec_r = NULL*/;\n\t// timing stuff\n\tlong start1, start2, start3, stop, stop2;\n\tdouble time_taken, time_for_setup, time_for_lp;\n\t// lp stuff\n\tREAL *arr_reals = NULL;// *lp_soln = NULL;\n\tint *arr_ints = NULL;\n\tbool selfloop;\n\tint arr_size, count, res;\n\t// misc\n\tint i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, start_index;\n\tdouble d1, d2, kb, kbt;\n\tbool done, first;\n\tjclass vn_cls;\n\tjmethodID vn_mid;\n\tint n_maybe_r = 0; // the number of maybe states for rewards\n\n\tdouble lp_result = 0.0;\n\n\t/********************** Multiple rewards ****************************\n\t // Variables for rewards\n\t jlong *rewards_ptrs = env->GetLongArrayElements(_rewards, 0);;\n\t DdNode **rewards;\t// transition rewards\n\t int num_rewards = (int)env->GetArrayLength(_rewards);\n\t rewards = new DdNode*[num_rewards];\n\t for (i = 0; i < num_rewards; i++) \n\t rewards[i] = jlong_to_DdNode(rewards_ptrs[i]);\n\n\t // Variables for reward formulas\n\t jlong *targets_r_ptrs = env->GetLongArrayElements(_targets_r, 0);;\n\t DdNode **targets_r;\t// target sets for reward formulas\n\t int num_targets_r = (int)env->GetArrayLength(_targets_r);\n\t targets_r = new DdNode*[num_targets_r];\n\t double *bounds_r = env->GetDoubleArrayElements(_bounds_r, 0);\n\t for (i = 0; i < num_targets_r; i++) \n\t targets_r[i] = jlong_to_DdNode(targets_r_ptrs[i]);\n\t DdNode* yes_r[num_targets_r];\n\t double* yes_vecs_r[num_targets_r];\n\t for(i=0; i<num_targets_r; i++) \n\t yes_r[i] = targets_r[i];\n\t ********************************************************************/\n\n\t// extract arrays of target info from function parameters\n\tnum_targets = (int)env->GetArrayLength(_targets);\n\ttarget_ptrs = env->GetLongArrayElements(_targets, 0);\n\ttargets = new DdNode*[num_targets];\n\tfor (i = 0; i < num_targets; i++) targets[i] = jlong_to_DdNode(target_ptrs[i]);\n\trelops = env->GetIntArrayElements(_relops, 0);\n\tbounds = env->GetDoubleArrayElements(_bounds, 0);\n\n\t// Display some target info (just a test)\n\tPN_PrintToMainLog(env, \"\\n%d Targets:\\n\", num_targets);\n\tfor (i = 0; i < num_targets; i++) {\n\t\tPN_PrintToMainLog(env, \"#%d: \", i);\n\t\tswitch (relops[i]) {\n\t\t\tcase 0: PN_PrintToMainLog(env, \"Pmax=?\"); break;\n\t\t\tcase 1: PN_PrintToMainLog(env, \">%g\", bounds[i]); break;\n\t\t\tcase 2: PN_PrintToMainLog(env, \">=%g\", bounds[i]); break;\n\t\t\tcase 3: PN_PrintToMainLog(env, \"Rmax=?\"); break;\n\t\t\tcase 4: PN_PrintToMainLog(env, \">=%g\", bounds[i]); break;\n\t\t}\n\t\tPN_PrintToMainLog(env, \" (%.0f states)\\n\", DD_GetNumMinterms(ddman, targets[i], num_rvars));\n\t}\n\n\t//DdNode *yes1 = targets[0];\n\t//DdNode *yes2 = targets[1];\n\tDdNode* yes[num_targets];\n\tdouble* yes_vecs[num_targets];\n\tfor(i=0; i<num_targets; i++)\n\tyes[i] = targets[i];\n\n\t// exception handling around whole function\n\ttry {\n\n\t\t// start clocks\t\n\t\tstart1 = start2 = util_cpu_time();\n\n\t\t// get a - filter out rows\n\t\tCudd_Ref(trans);\n\t\tCudd_Ref(maybe);\n\t\tif(checkReach) // For reachability, we only use maybe\n\t\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\telse { // For LTL formulas, we need both maybe and yes\n\t\t\tDdNode *maybe_yes = maybe;\n\t\t\tfor(i=0; i<num_targets; i++) {\n\t\t\t\tCudd_Ref(yes[i]);\n\t\t\t\tmaybe_yes = DD_Or(ddman, maybe_yes, yes[i]);\n\t\t\t}\n\t\t\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe_yes);\n\t\t}\n\n\t\t// get number of states\n\t\tn = odd->eoff + odd->toff;\n\n\t\t// build sparse matrix\n\t\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t\tndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\t// get number of transitions/choices\n\t\tnnz = ndsm->nnz;\n\t\tnc = ndsm->nc;\n\t\tkb = ndsm->mem;\n\t\tkbt = kb;\n\t\t// print out info\n\t\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%d, k=%d] \", n, nc, nnz, ndsm->k);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n\t\t// get vectors for yes/maybe\n\t\tPN_PrintToMainLog(env, \"Creating vectors for yes... \");\n\t\tfor(i=0; i<num_targets; i++) {\n\t\t\tyes_vecs[i] = mtbdd_to_double_vector(ddman, yes[i], rvars, num_rvars, odd);\n\t\t\tkb = n*8.0/1024.0;\n\t\t\tkbt += kb;\n\t\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t}\n\t\t/*PN_PrintToMainLog(env, \"Creating vectors for yes2... \");\n\t\t yes2_vec = mtbdd_to_double_vector(ddman, yes2, rvars, num_rvars, odd);\n\t\t kb = n*8.0/1024.0;\n\t\t kbt += kb;\n\t\t PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");*/\n\t\tPN_PrintToMainLog(env, \"Creating vector for maybe... \");\n\t\tmaybe_vec = mtbdd_to_double_vector(ddman, maybe, rvars, num_rvars, odd);\n\t\tkb = n*8.0/1024.0;\n\t\tkbt += kb;\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n\t\t// get index of single (first) initial state\n\t\tstart_index = get_index_of_first_from_bdd(ddman, start, rvars, num_rvars, odd);\n\t\tPN_PrintToMainLog(env, \"Initial state index: %1d\\n\", start_index);\n\n\t\t// print total memory usage\n\t\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\t\t// store local copies of sparse matrix stuff\n\t\tdouble *non_zeros = ndsm->non_zeros;\n\t\tunsigned char *row_counts = ndsm->row_counts;\n\t\tint *row_starts = (int *)ndsm->row_counts;\n\t\tunsigned char *choice_counts = ndsm->choice_counts;\n\t\tint *choice_starts = (int *)ndsm->choice_counts;\n\t\tbool use_counts = ndsm->use_counts;\n\t\tunsigned int *cols = ndsm->cols;\n\n\t\t/***************** set up rewards *******************/\n\t\t/*double *non_zeros_r;\n\t\t unsigned char *choice_counts_r;\n\t\t int *choice_starts_r;\n\t\t bool use_counts_r;\n\t\t unsigned int *cols_r;\n\t\t \n\t\t if(relops[0] > 2) {\n\t\t trans_rewards\t= jlong_to_DdNode(trr);\t// transition rewards\t\t\n\t\t Cudd_Ref(trans_rewards);\n\t\t trans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, maybe);\n\t\t PN_PrintToMainLog(env, \"Building sparse matrix (transition rewards)... \");\n\t\t ndsm_r = build_sub_nd_sparse_matrix(ddman, a, trans_rewards, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\t nnz_r = ndsm_r->nnz;\n\t\t nc_r = ndsm_r->nc;\n\t\t // print out info\n\t\t PN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%d, k=%d] \", n, nc_r, nnz_r, ndsm_r->k);\n\t\t kb = (nnz_r*12.0+nc_r*4.0+n*4.0)/1024.0;\n\t\t kbt += kb;\n\t\t PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t non_zeros_r = ndsm_r->non_zeros;\n\t\t choice_counts_r = ndsm_r->choice_counts;\n\t\t choice_starts_r = (int *)ndsm_r->choice_counts;\n\t\t use_counts_r = ndsm_r->use_counts;\n\t\t cols_r = ndsm_r->cols;\n\t\t //for(i=0; i<nnz_r; i++)\n\t\t //\tprintf(\"non_zeros_r[%1d] = %g\\n\", i, non_zeros_r[i]);\n\t\t / *PN_PrintToMainLog(env, \"Creating vector for reward maybe... \");\n\t\t maybe_vec_r = mtbdd_to_double_vector(ddman, maybe_r, rvars, num_rvars, odd);\n\t\t for(i=0; i<n; i++)\n\t\t if(maybe_vec_r[i] > 0)\n\t\t n_maybe_r ++;\n\t\t kb = n*8.0/1024.0;\n\t\t kbt += kb;\n\t\t PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\t* /\n\t\t //maybe_vec_r = maybe_vec;\n\t\t }*/\n\t\t/***************** end of set up *******************/\n\n\t\t// Set up LP problem\n\t\tPN_PrintToMainLog(env, \"\\nBuilding LP problem...\\n\");\n\t\t// Compute number of vars/constraints\n\t\tint maybe_nc = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (maybe_vec[i]> 0) {\n\t\t\t\th1 = use_counts ? row_counts[i] : (row_starts[i+1] - row_starts[i]);\n\t\t\t\tmaybe_nc += h1;\n\t\t\t}\n\t\t}\n\t\tint num_yes12 = 0;\n\t\tint num_maybe = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t//if (yes1_vec[i] > 0 || yes2_vec[i] > 0) num_yes12++;\n\t\t\tfor(j=0; j<num_targets; j++)\n\t\t\tif(yes_vecs[j][i]> 0) {\n\t\t\t\tnum_yes12++;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tif (maybe_vec[i]> 0 ) num_maybe++;\n\t\t}\n\t\tint num_lp_vars = maybe_nc + num_yes12;\n\t\t//printf(\"num_lp_vars = %d + %d = %d\\n\", maybe_nc, num_yes12, num_lp_vars);\n\t\t//int num_constr = num_maybe + num_yes12;\n\t\t//printf(\"num_constr = %d + %d = %d\\n\", num_maybe, num_yes12, num_constr);\n\n\t\t/*yes1_vec = yes_vecs[0];\n\t\t yes2_vec = yes_vecs[1];\n\t\t \n\t\t start3 = util_cpu_time();\n\n\t\t if ((lp=make_lp(n, 0)) == NULL) throw \"Could not create LP problem\";\n\t\t // Lower verbosity: Warnings and errors only\n\t\t //set_verbose(lp, IMPORTANT);\n\n\t\t // Compute array size: max num elements in a row + 1\n\t\t // or number of elements in maybe, which ever is greater\n\t\t arr_size = 0;\n\t\t h1 = h2 = 0;\n\t\t for (i = 0; i < n; i++) {\n\t\t if (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t else { l1 = h1; h1 += row_counts[i]; }\n\t\t for (j = l1; j < h1; j++) {\n\t\t h2 = use_counts ? choice_counts[j] : (choice_starts[j+1] - choice_starts[j]);\n\t\t if (h2 > arr_size) arr_size = h2;\n\t\t }\n\t\t }\n\t\t arr_size++;\n\t\t count = 0;\n\t\t for (i = 0; i < n; i++) if (maybe_vec[i] > 0) count++;\n\t\t if (count > arr_size) arr_size = count;\n\t\t // Allocate vectors for use in building LP problem\n\t\t arr_reals = new REAL[arr_size];\n\t\t arr_ints = new int[arr_size];\n\t\t \n\t\t // Set objective function for LP problem\n\t\t set_maxim(lp); \n\t\t count = 0;\n\t\t / *\tfor (i = 0; i < n; i++) if (maybe_vec[i] > 0) {\n\t\t arr_reals[count] = 1.0;\n\t\t arr_ints[count] = i+1;\n\t\t count++;\n\t\t }\n\t\t set_obj_fnex(lp, count, arr_reals, arr_ints);* /\n\t\t \n\t\t // Add columns to LP problem\n\t\t h1 = h2 = 0;\n\t\t for (i = 0; i < n; i++) {\n\t\t printf(\"%d: %s%s%s\\n\", i, maybe_vec[i]>0?\"1\":\"0\", yes1_vec[i]>0?\"1\":\"0\", yes2_vec[i]>0?\"1\":\"0\");\n\t\t if (yes1_vec[i] > 0 || yes2_vec[i] > 0) {\n\t\t printf(\"yes %d\\n\", i);\n\t\t arr_ints[0] = i+1;\n\t\t arr_reals[0] = 1;\n\t\t count = 1;\n\t\t if (yes2_vec[i] > 0) {\n\t\t \n\t\t count++;\n\t\t }\n\t\t add_columnex(lp, 1, arr_reals, arr_ints);\n\t\t }\n\t\t if (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t else { l1 = h1; h1 += row_counts[i]; }\n\t\t for (j = l1; j < h1; j++) {\n\t\t if (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t else { l2 = h2; h2 += choice_counts[j]; }\n\t\t if (maybe_vec[i] > 0) {\n\t\t arr_ints[0] = i+1;\n\t\t arr_reals[0] = 1.0;\n\t\t count = 1;\n\t\t d2 = 0.0;\n\t\t for (k = l2; k < h2; k++) {\n\t\t printf(\"#%d (%d.%d): %d,%f\\n\", count, i, j, cols[k], non_zeros[k]);\n\t\t // Ignore no cols\n\t\t printf(\"%s%s%s\\n\", maybe_vec[cols[k]]>0?\"1\":\"0\", yes1_vec[cols[k]]>0?\"1\":\"0\", yes2_vec[cols[k]]>0?\"1\":\"0\");\n\t\t if (maybe_vec[cols[k]] == 0 && yes1_vec[cols[k]] == 0 && yes2_vec[cols[k]] == 0) continue;\n\t\t // Normal case\n\t\t if (1) {\n\t\t arr_ints[count] = cols[k]+1;\n\t\t arr_reals[count] = -non_zeros[k];\n\t\t count++;\n\t\t }\n\t\t }\n\t\t for (k = 0; k < count; k++) printf(\" %f\", arr_reals[k]); printf(\"\\n\");\n\t\t for (k = 0; k < count; k++) printf(\" %d\", arr_ints[k]); printf(\"\\n\");\n\t\t add_columnex(lp, count, arr_reals, arr_ints);\n\t\t }\n\t\t }\n\t\t }\n\t\t \n\t\t print_lp(lp);\n\t\t \n\t\t // get setup time\n\t\t stop = util_cpu_time();\n\t\t time_for_setup = (double)(stop - start3)/1000;\n\t\t start2 = stop;\n\n\t\t // Solve LP problem\n\t\t PN_PrintToMainLog(env, \"Solving LP problem...\\n\");\n\t\t res = solve(lp);\n\t\t \n\t\t //Get LP solving time\n\t\t stop2 = util_cpu_time();  \n\t\t time_for_lp = (double)(stop2 - start2)/1000;\n\t\t \n\t\t if (res != 0) throw \"Could not solve LP problem\";\n\t\t get_ptr_variables(lp, &lp_soln);\n\t\t //print_solution(lp, 2);\n\t\t \n\t\t // Reuse yes vector to store/return soln\n\t\t for (i = 0; i < n; i++) {\n\t\t //if (yes2_vec[i] == 0.0) yes2_vec[i] = lp_soln[i];\n\t\t }\n\t\t \n\t\t // stop clocks\n\t\t stop = util_cpu_time();\n\t\t time_for_lp = (double)(stop - start2)/1000;\n\t\t time_taken = (double)(stop - start3)/1000;\n\t\t \n\t\t // print timing info\n\t\t PN_PrintToMainLog(env, \"\\nLP problem solved in %.2f seconds (setup %.2f, lpsolve %.2f)\\n\", time_taken, time_for_setup, time_for_lp);*/\n\n\t\t/*\n\t\t * Hongyang: Use Eclipse with COIN CBC solver \n\t\t */\n\t\tFILE *f; /* FILE pointer */\n\n\t\t// Generate LP for the objectives\n\t\tstart3 = util_cpu_time();\n\n\t\tec_refs Vars;\n\t\tec_ref Cost;\n\t\tpword varlist;\n\t\t//int yes_vec[n];\n\t\t//int map_var[n+1]; \n\t\tint *yes_vec;\n\t\tint *map_var;\n\n\t\tyes_vec = new int[n];\n\t\tmap_var = new int[n+1];\n\n\t\tarr_ints = new int[n];\n\t\tint sp;\n\n\t\tint yes_nc = 0; // the total number of choices of all target states\n\t\t/*int *map_var_r;\n\n\t\t if(relops[0] > 2) {\n\t\t map_var_r = new int[n];\n\t\t k = 0;\n\t\t for(i=0; i<n; i++) \n\t\t if(maybe_vec_r[i] > 0)\n\t\t map_var_r[i] = k++;\n\t\t else\n\t\t map_var_r[i] = -1;\n\t\t }*/\n\n\t\tif(checkReach) {\n\t\t\tPN_PrintToMainLog(env, \"Check reachability...\\n\");\n\t\t\t// Maps states to ECLiPSe variables. \n\t\t\t// Each yes state has a coresponding variable.\n\t\t\t// Each maybe state has one or more variables.\n\n\t\t\t// merge all yes vectors into one\n\t\t\tint flag = 0;\n\t\t\tfor(i=0; i<n; i++) {\n\t\t\t\tflag = 0;\n\t\t\t\tfor(j=0; j<num_targets; j++)\n\t\t\t\tif(yes_vecs[j][i]> 0) {\n\t\t\t\t\tyes_vec[i] = 1;\n\t\t\t\t\tflag = 1;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tif(!flag)\n\t\t\t\tyes_vec[i] = 0;\n\t\t\t}\n\n\t\t\t//if (arr_reals) delete[] arr_reals;\n\t\t\tPN_PrintToMainLog(env, \"Number of LP variables = %1d\\n\", num_lp_vars + n_maybe_r);\n\t\t\tarr_reals = new REAL[num_lp_vars + n_maybe_r];\n\n\t\t\t// create map vector\n\t\t\tcount = 0;\n\t\t\tfor(i=0; i<n; i++) {\n\t\t\t\tif(yes_vec[i]> 0)\n\t\t\t\tmap_var[i] = count++;\n\t\t\t\telse {\n\t\t\t\t\tif(maybe_vec[i]> 0) {\n\t\t\t\t\t\tmap_var[i] = count;\n\t\t\t\t\t\tcount += use_counts ? row_counts[i] : (row_starts[i+1] - row_starts[i]);\n\t\t\t\t\t} else\n\t\t\t\t\tmap_var[i] = count;\n\t\t\t\t}\n\t\t\t}\n\t\t\tmap_var[n] = num_lp_vars;\n\n\t\t\t/*printf(\"map_var = \");\n\t\t\t for(i=0; i<=n; i++)\n\t\t\t printf(\" %1d\", map_var[i]);\n\t\t\t printf(\"\\n\");\n\t\t\t fflush(stdout);*/\n\n\t\t\t// Initialize ECLiPSe\n\t\t\tec_init();\n\n\t\t\t// Load Eplex library\n\t\t\tec_post_string(\"lib(eplex)\");\n\n\t\t\t// Create ECLiPSe variables\n\t\t\tVars = ec_refs_create_newvars(num_lp_vars + n_maybe_r);\n\t\t\tCost = ec_ref_create_newvar();\n\t\t\tvarlist = ec_listofrefs(Vars);\n\n\t\t\t// Define the domain of the variables\n\t\t\tec_post_goal(ec_term(\n\t\t\t\t\t\t\tec_did(\"::\",2),\n\t\t\t\t\t\t\tvarlist,\n\t\t\t\t\t\t\tec_term(ec_did(\"..\",2), ec_double(0.0), ec_double(1e20))));\n\n\t\t\tstop = util_cpu_time();\n\t\t\ttime_for_setup = (double)(stop - start3)/1000;\n\t\t\tstart2 = stop;\n\n\t\t\t// Add constraints to LP problem\n\t\t\tint x;\n\t\t\tl1 = h1 = 0;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t// Add constraints for maybe states\n\t\t\t\tif (maybe_vec[i]> 0) {\n\t\t\t\t\tfor(k=0; k<num_lp_vars; k++)\n\t\t\t\t\tarr_reals[k] = 0.0;\n\n\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\tl1 = row_starts[i];\n\t\t\t\t\t\th1 = row_starts[i+1];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tl1 = h1;\n\t\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t\t}\n\t\t\t\t\tfor (j = l1; j < h1; j++) // \\Sigma_{v\\in V/F} y_{(v, \\gamma)}\n\t\t\t\t\tarr_reals[map_var[i]+j-l1] = 1.0;\n\n\t\t\t\t\tcount = h1-l1;\n\t\t\t\t\tint l3, h3;\n\t\t\t\t\th3 = h2 = 0;\n\t\t\t\t\tfor (x = 0; x < n; x++) { // h2: row index\n\t\t\t\t\t\tif(maybe_vec[x]> 0) {\n\t\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\t\tl3 = row_starts[x];\n\t\t\t\t\t\t\t\th3 = row_starts[x+1];\n\t\t\t\t\t\t\t} else { // Attention: there could exist a bug here!!!!!!!\n\t\t\t\t\t\t\t\tl3 = h3;\n\t\t\t\t\t\t\t\th3 += row_counts[x];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tfor (j = l3; j < h3; j++) { // j: choice index; x+j: variable index \n\t\t\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tl2 = h2;\n\t\t\t\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tfor(k=l2; k<h2; k++) { // k: column index\n\t\t\t\t\t\t\t\t\tif(cols[k] == i) {\n\t\t\t\t\t\t\t\t\t\t// get the index of the corresponding variable\n\t\t\t\t\t\t\t\t\t\tdouble old_value = arr_reals[map_var[x]+j-l3];\n\t\t\t\t\t\t\t\t\t\tarr_reals[map_var[x]+j-l3] -= non_zeros[k];\n\t\t\t\t\t\t\t\t\t\t//printf(\"map_var[%1d]+%1d-%1d = %1d\\n\", x, j, l3, map_var[x]+j-l3);\n\t\t\t\t\t\t\t\t\t\tif(old_value == 0.0 && arr_reals[map_var[x]+j-l3] != 0.0)\n\t\t\t\t\t\t\t\t\t\tcount++;\n\t\t\t\t\t\t\t\t\t\telse if(old_value != 0.0 && arr_reals[map_var[x]+j-l3] == 0.0)\n\t\t\t\t\t\t\t\t\t\tcount--;\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} else if(use_counts) {\n\t\t\t\t\t\t\tl3 = h3;\n\t\t\t\t\t\t\th3 += row_counts[x];\n\t\t\t\t\t\t\tfor (j = l3; j < h3; j++)\n\t\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t/*printf(\"\t\tarr_reals:\");\n\t\t\t\t\t for (k = 0; k < num_lp_vars; k++) \n\t\t\t\t\t printf(\" %1.1f\", arr_reals[k]); \n\t\t\t\t\t printf(\" = %1.1f\", (start_index==i ? 1.0 : 0.0));\n\t\t\t\t\t printf(\"\t\tcount = %1d\\n\", count);\n\t\t\t\t\t fflush(stdout);*/\n\n\t\t\t\t\tpword tail = ec_nil();\n\t\t\t\t\tx = 0;\n\n\t\t\t\t\tfor(k=num_lp_vars-1; k>=0; k--)\n\t\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\t\ttail = ec_list(ec_refs_get(Vars, k), tail);\n\t\t\t\t\tfor(k=0; k<num_lp_vars; k++)\n\t\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\t\tarr_reals[x++] = arr_reals[k];\n\t\t\t\t\tec_post_goal(ec_term(ec_did((\"$=\"),2),\n\t\t\t\t\t\t\t\t\tec_term(ec_did(\"*\",2),\n\t\t\t\t\t\t\t\t\t\t\ttail,\n\t\t\t\t\t\t\t\t\t\t\tec_listofdouble(count, arr_reals)),\n\t\t\t\t\t\t\t\t\tec_double((start_index==i ? 1.0 : 0.0))));\n\t\t\t\t\t/*ec_post_goal(ec_term(ec_did((\"$=\"),2), \n\t\t\t\t\t ec_term(ec_did(\"*\",2), \n\t\t\t\t\t varlist, \n\t\t\t\t\t ec_listofdouble(num_lp_vars, arr_reals)), \n\t\t\t\t\t ec_double((start_index==i ? 1.0 : 0.0))));*/\n\t\t\t\t} else if(use_counts) {\n\t\t\t\t\tl1 = h1;\n\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif(yes_vec[i]> 0) {\n\t\t\t\t\tfor(k=0; k<num_lp_vars; k++)\n\t\t\t\t\tarr_reals[k] = 0.0;\n\n\t\t\t\t\tcount = 1;\n\t\t\t\t\th1 = h2 = 0;\n\t\t\t\t\tfor (x = 0; x < n; x++) { // x: row index\n\t\t\t\t\t\tif(maybe_vec[x]> 0) {\n\t\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\t\tl1 = row_starts[x];\n\t\t\t\t\t\t\t\th1 = row_starts[x+1];\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tl1 = h1;\n\t\t\t\t\t\t\t\th1 += row_counts[x];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tif(x == i) {\n\t\t\t\t\t\t\t\tif(use_counts)\n\t\t\t\t\t\t\t\tfor (j = l1; j < h1; j++)\n\t\t\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tfor (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n\t\t\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tl2 = h2;\n\t\t\t\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tfor(k=l2; k<h2; k++) { // k: column index\n\t\t\t\t\t\t\t\t\tif(cols[k] == i) {\n\t\t\t\t\t\t\t\t\t\t// get the index of the corresponding variable\n\t\t\t\t\t\t\t\t\t\tarr_reals[map_var[x]+j-l1] = -non_zeros[k];\n\t\t\t\t\t\t\t\t\t\t//printf(\"map_var[%1d]+%1d-%1d = %1d\\n\", x, j, l1, map_var[x]+j-l1);\n\t\t\t\t\t\t\t\t\t\t//printf(\"arr_reals[%1d] = %1.1f\\n\", map_var[x]+j-l1, -non_zeros[k]);\n\t\t\t\t\t\t\t\t\t\tcount++;\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} else if(use_counts) {\n\t\t\t\t\t\t\tl1 = h1;\n\t\t\t\t\t\t\th1 += row_counts[x];\n\t\t\t\t\t\t\tfor (j = l1; j < h1; j++)\n\t\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tarr_reals[map_var[i]] = 1.0;\n\t\t\t\t\t/*printf(\"\t\t\t\tarr_reals:\");\n\t\t\t\t\t for (k = 0; k < num_lp_vars; k++) \n\t\t\t\t\t printf(\" %1.1f\", arr_reals[k]);\n\t\t\t\t\t printf(\" = 0.0\");\n\t\t\t\t\t printf(\"\t\tcount = %1d\\n\", count);\n\t\t\t\t\t fflush(stdout);*/\n\n\t\t\t\t\tpword tail = ec_nil();\n\t\t\t\t\tx = 0;\n\n\t\t\t\t\tfor(k=num_lp_vars-1; k>=0; k--)\n\t\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\t\ttail = ec_list(ec_refs_get(Vars, k), tail);\n\t\t\t\t\tfor(k=0; k<num_lp_vars; k++)\n\t\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\t\tarr_reals[x++] = arr_reals[k];\n\t\t\t\t\tec_post_goal(ec_term(ec_did((\"$=\"),2),\n\t\t\t\t\t\t\t\t\tec_term(ec_did(\"*\",2),\n\t\t\t\t\t\t\t\t\t\t\ttail,\n\t\t\t\t\t\t\t\t\t\t\tec_listofdouble(count, arr_reals)),\n\t\t\t\t\t\t\t\t\tec_double(0.0)));\n\n\t\t\t\t\t/*ec_post_goal(ec_term(ec_did((\"$=\"),2), \n\t\t\t\t\t ec_term(ec_did(\"*\",2), \n\t\t\t\t\t varlist, \n\t\t\t\t\t ec_listofdouble(num_lp_vars, arr_reals)), \n\t\t\t\t\t ec_double(0.0)));*/\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tPN_PrintToMainLog(env, \"Adding extra constraints for probabilisitic bounds\\n\");\n\t\t\tfor(i=0; i<num_targets; i++) {\n\t\t\t\tpword tail = ec_nil();\n\t\t\t\tfor(k=n-1; k>=0; k--)\n\t\t\t\tif(yes_vecs[i][k]> 0)\n\t\t\t\ttail = ec_list(ec_refs_get(Vars, map_var[k]), tail);\n\t\t\t\tx=0;\n\t\t\t\tfor(k=0; k<n; k++)\n\t\t\t\tif(yes_vecs[i][k]> 0)\n\t\t\t\tarr_reals[x++] = 1.0;\n\t\t\t\tec_post_goal(ec_term(ec_did(\"$>=\",2),\n\t\t\t\t\t\t\t\tec_term(ec_did(\"*\",2),\n\t\t\t\t\t\t\t\t\t\ttail,\n\t\t\t\t\t\t\t\t\t\tec_listofdouble(x, arr_reals)),\n\t\t\t\t\t\t\t\tec_double(bounds[i])));\n\t\t\t}\n\n\t\t\tPN_PrintToMainLog(env, \"Computing optimisation...\\n\");\n\t\t\tfflush(stdout);\n\t\t\tpword tail = ec_nil();\n\t\t\tx = 0;\n\n\t\t\tif(relops[0]> 0 && relops[0] <= 2) {\n\t\t\t\tfor(k=n-1; k>=0; k--)\n\t\t\t\tif(yes_vec[k]> 0)\n\t\t\t\ttail = ec_list(ec_refs_get(Vars, map_var[k]), tail);\n\t\t\t\tfor(k=0; k<n; k++)\n\t\t\t\tif(yes_vec[k]> 0)\n\t\t\t\tarr_reals[x++] = 1.0;\n\t\t\t} else if(relops[0] == 0) {\n\t\t\t\tfor(k=n-1; k>=0; k--)\n\t\t\t\tif(yes_vecs[0][k]> 0)\n\t\t\t\ttail = ec_list(ec_refs_get(Vars, map_var[k]), tail);\n\t\t\t\tfor(k=0; k<n; k++)\n\t\t\t\tif(yes_vecs[0][k]> 0)\n\t\t\t\tarr_reals[x++] = 1.0;\n\t\t\t} else {\n\t\t\t\t/*x = 1;\n\t\t\t\t arr_reals[0] = 1.0;\n\t\t\t\t tail = ec_list(ec_refs_get(Vars, map_var_r[start_index]+num_lp_vars), tail);*/\n\t\t\t\tPN_PrintToMainLog(env, \"computing max function for rewards ...\\n\");\n\t\t\t\tdouble *non_zeros_r;\n\t\t\t\tunsigned char *choice_counts_r;\n\t\t\t\tint *choice_starts_r;\n\t\t\t\tbool use_counts_r;\n\t\t\t\tunsigned int *cols_r;\n\t\t\t\ttrans_rewards = jlong_to_DdNode(trr); // transition rewards\t\t\n\t\t\t\tCudd_Ref(trans_rewards);\n\t\t\t\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, maybe);\n\t\t\t\tPN_PrintToMainLog(env, \"Building sparse matrix (transition rewards)... \");\n\t\t\t\tndsm_r = build_sub_nd_sparse_matrix(ddman, a, trans_rewards, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\t\t\tnnz_r = ndsm_r->nnz;\n\t\t\t\tnc_r = ndsm_r->nc;\n\t\t\t\t// print out info\n\t\t\t\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%d, k=%d] \", n, nc_r, nnz_r, ndsm_r->k);\n\t\t\t\tkb = (nnz_r*12.0+nc_r*4.0+n*4.0)/1024.0;\n\t\t\t\tkbt += kb;\n\t\t\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t\t\tnon_zeros_r = ndsm_r->non_zeros;\n\t\t\t\tchoice_counts_r = ndsm_r->choice_counts;\n\t\t\t\tchoice_starts_r = (int *)ndsm_r->choice_counts;\n\t\t\t\tuse_counts_r = ndsm_r->use_counts;\n\t\t\t\tcols_r = ndsm_r->cols;\n\n\t\t\t\tfor(i=0; i<num_lp_vars; i++)\n\t\t\t\tarr_reals[i] = 0;\n\n\t\t\t\th1 = h2 = 0;\n\t\t\t\tfor(i=0; i<n; i++)\n\t\t\t\tif(maybe_vec[i]> 0) {\n\t\t\t\t\tif (!use_counts) { // assume we always do not use counts\n\t\t\t\t\t\tl1 = row_starts[i];\n\t\t\t\t\t\th1 = row_starts[i+1];\n\t\t\t\t\t} else { // Problematic\n\t\t\t\t\t\tl1 = h1;\n\t\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t\t}\n\t\t\t\t\tfor (j = l1; j < h1; j++) {// \\Sigma_{v\\in V/F} y_{(v, \\gamma)}*c_{(v, \\gamma)}\n\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2 = h2;\n\t\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (!use_counts_r) {\n\t\t\t\t\t\t\tl2_r = choice_starts_r[j];\n\t\t\t\t\t\t\th2_r = choice_starts_r[j+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2_r = h2_r;\n\t\t\t\t\t\t\th2_r += choice_counts_r[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tk_r = l2_r;\n\t\t\t\t\t\twhile (k_r < h2_r && cols_r[k_r] != cols[l2])\n\t\t\t\t\t\tk_r++;\n\t\t\t\t\t\t// if there is one, add reward * prob to reward value\n\t\t\t\t\t\tif (k_r < h2_r) {\n\t\t\t\t\t\t\tarr_reals[map_var[i]+j-l1] = non_zeros_r[k_r];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else if(use_counts) { // count the number of choices for non maybe nodes. Is it necessary?\n\t\t\t\t\tl1 = h1;\n\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\th2_r += choice_counts_r[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t/*PN_PrintToMainLog(env, \"\t\tarr_reals:\");\n\t\t\t\t for (k = 0; k < num_lp_vars; k++) \n\t\t\t\t PN_PrintToMainLog(env, \" %1.1f\", arr_reals[k]); \n\t\t\t\t fflush(stdout);*/\n\n\t\t\t\tfor(k=num_lp_vars-1; k>=0; k--)\n\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\ttail = ec_list(ec_refs_get(Vars, k), tail);\n\t\t\t\tfor(k=0; k<num_lp_vars; k++)\n\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\tarr_reals[x++] = arr_reals[k];\n\n\t\t\t}\n\n\t\t\tec_post_goal( ec_term(ec_did(\"optimize\", 2),\n\t\t\t\t\t\t\tec_term(ec_did(\"max\", 1),\n\t\t\t\t\t\t\t\t\tec_term(ec_did(\"*\",2), tail, ec_listofdouble(x, arr_reals))),\n\t\t\t\t\t\t\tec_ref_get(Cost)));\n\t\t\t/*ec_post_goal( ec_term(ec_did(\"optimize\", 2),\n\t\t\t ec_term(ec_did(\"max\", 1), \n\t\t\t ec_term(ec_did(\"*\",2), varlist, ec_listofdouble(num_lp_vars, pc))), \n\t\t\t ec_ref_get(Cost)));*/\n\t\t} else { // ------------------------------ LTL model checking ----------------------------\n\t\t\tPN_PrintToMainLog(env, \"Check LTL formulas...\\n\");\n\n\t\t\tint num_map;\n\t\t\tint yes_count = 0; // the number of target states\n\n\t\t\t// Compute the number of lp variables for LTL model checking\n\t\t\tmaybe_nc = 0; // number of variables for maybe states\n\t\t\th1 = h2 = 0;\n\t\t\tcount = 0;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (!use_counts) {\n\t\t\t\t\tl1 = row_starts[i];\n\t\t\t\t\th1 = row_starts[i+1];\n\t\t\t\t} else {\n\t\t\t\t\tl1 = h1;\n\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t}\n\t\t\t\tk=0;\n\t\t\t\tfor (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tl2 = h2;\n\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t}\n\t\t\t\t\tif(h2-l2>1 || cols[l2] != i || non_zeros[l2]!=1.0)\n\t\t\t\t\tk++;\n\t\t\t\t}\n\t\t\t\tif (maybe_vec[i]> 0) {\n\t\t\t\t\tmaybe_nc += k;\n\t\t\t\t\tmap_var[i] = count;\n\t\t\t\t\tcount += k;\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tmap_var[i] = count;\n\t\t\t\t\tfor(j=0; j<num_targets; j++)\n\t\t\t\t\tif(yes_vecs[j][i]> 0) {\n\t\t\t\t\t\tyes_nc += k;\n\t\t\t\t\t\tmap_var[i] = count;\n\t\t\t\t\t\tyes_count ++; // each target state has one extra action\n\t\t\t\t\t\tcount += k+1;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tnum_lp_vars = maybe_nc + yes_nc + yes_count;\n\t\t\tmap_var[n] = num_lp_vars; // maybe need to be modified.\t\t\n\t\t\tPN_PrintToMainLog(env, \"Number of LP variables = %1d\\n\", num_lp_vars);\n\n\t\t\tfor(i=0; i<n; i++)\n\t\t\tyes_vec[i] = 0;\n\t\t\tcount = 0;\n\t\t\tfor(i=0; i<n; i++)\n\t\t\tfor(j=0; j<num_targets; j++)\n\t\t\tif(yes_vecs[j][i]> 0) { // For each state, count the number of targets it belongs to.\n\t\t\t\tyes_vec[i]++;\n\t\t\t\tcount++;\n\t\t\t}\n\n\t\t\t/*printf(\"map_var = \");\n\t\t\t for(i=0; i<=n; i++)\n\t\t\t printf(\" %1d\", map_var[i]);\n\t\t\t printf(\"\\n\");\n\t\t\t fflush(stdout);*/\n\n\t\t\th1 = h2 = 0;\n\t\t\tfor(i=0; i<n; i++)\n\t\t\tarr_ints[i] = map_var[i+1]-map_var[i];\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (!use_counts) {\n\t\t\t\t\tl1 = row_starts[i];\n\t\t\t\t\th1 = row_starts[i+1];\n\t\t\t\t} else {\n\t\t\t\t\tl1 = h1;\n\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t}\n\t\t\t\tfor (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tl2 = h2;\n\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t}\n\t\t\t\t\tif(h2-l2>1 || cols[l2] != i || non_zeros[l2]!=1.0) {\n\t\t\t\t\t\tif (maybe_vec[i]> 0 || yes_vec[i]> 0)\n\t\t\t\t\t\tfor(k=l2; k<h2; k++) {\n\t\t\t\t\t\t\tif(maybe_vec[cols[k]]> 0 || yes_vec[cols[k]]> 0)\n\t\t\t\t\t\t\tarr_ints[cols[k]] ++;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t//int *constraints_ints[n];\n\t\t\t//double *constraints_reals[n];\n\t\t\tint *constraints_sp;\n\t\t\t//int constraints_sp[n];\n\t\t\tint *constraints_ints;\n\t\t\tdouble *constraints_reals;\n\t\t\tunsigned long *constraints_int_ptr;\n\t\t\tunsigned long *constraints_real_ptr;\n\t\t\t//PN_PrintToMainLog(env, \"Allocating memory space\t\t\\n\");\n\t\t\tconstraints_sp = new int[n];\n\t\t\tconstraints_int_ptr = new unsigned long[n];\n\t\t\tconstraints_real_ptr = new unsigned long[n];\n\t\t\tfor(i=0; i<n; i++)\n\t\t\tif(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n\t\t\t\t//printf(\"i = %1d, \", i);\n\t\t\t\tconstraints_ints = new int[arr_ints[i]];\n\t\t\t\tconstraints_reals = new REAL[arr_ints[i]];\n\t\t\t\tconstraints_sp[i] = map_var[i+1]-map_var[i];\n\t\t\t\tconstraints_int_ptr[i] = (unsigned long)constraints_ints;\n\t\t\t\tconstraints_real_ptr[i] = (unsigned long)constraints_reals;\n\t\t\t\tfor(j=0; j<map_var[i+1]-map_var[i]; j++) {\n\t\t\t\t\tconstraints_ints[j] = map_var[i] + j;\n\t\t\t\t\tconstraints_reals[j] = 1.0;\n\t\t\t\t}\n\t\t\t\tfor(j=map_var[i+1]-map_var[i]; j<arr_ints[i]; j++) {\n\t\t\t\t\tconstraints_ints[j] = -1;\n\t\t\t\t\tconstraints_reals[j] = 0;\n\t\t\t\t}\n\n\t\t\t\t//printf(\"arr_ints[%1d] = %1d\\n\", i, arr_ints[i]);\n\t\t\t}\n\n\t\t\t//if (arr_reals) delete[] arr_reals;\n\t\t\tarr_reals = new REAL[num_lp_vars];\n\n\t\t\t// create map vector\n\t\t\t/*count = 0;\n\t\t\t for(i=0; i<n; i++) {\n\t\t\t if(yes_vec[i] > 0 || maybe_vec[i] > 0) {\n\t\t\t map_var[i] = count;\t\n\t\t\t count += use_counts ? row_counts[i] : (row_starts[i+1] - row_starts[i]);\n\t\t\t if(yes_vec[i] > 0)\n\t\t\t count ++; // Add extra transition\n\t\t\t } else \n\t\t\t map_var[i] = count;\n\t\t\t }\n\t\t\t map_var[n] = num_lp_vars; // maybe need to be modified.*/\n\n\t\t\t/* write the LP to file LP.ecl */\n\t\t\t/*f = fopen(\"LP.ecl\", \"w\"); /* create a file for writing * /\n\t\t\t \n\t\t\t if(f==NULL) \n\t\t\t PN_PrintToMainLog(env, \"Cannot create LP.ecl!\\n\");\n\t\t\t \n\t\t\t fprintf(f, \":- lib(eplex).\\n\\n\");\n\t\t\t fprintf(f, \"main1(Cost, Vars) :-\\n\");\n\t\t\t fprintf(f, \"Vars = [\");\n\t\t\t for(i=0; i<num_lp_vars; i++) {\n\t\t\t if(i>0)\n\t\t\t fprintf(f, \", \");\n\t\t\t fprintf(f, \"X%1d\", i+1);\n\t\t\t }\n\t\t\t \n\t\t\t fprintf(f, \"],\\n\");\n\t\t\t fprintf(f, \"Vars :: 0.0..inf,\\n\\n\");*/\n\n\t\t\t/*printf(\"map_var = \");\n\t\t\t for(i=0; i<=n; i++)\n\t\t\t printf(\" %1d\", map_var[i]);\n\t\t\t printf(\"\\n\");\n\t\t\t fflush(stdout);*/\n\n\t\t\t// Initialize ECLiPSe\n\t\t\tec_init();\n\n\t\t\t// Load Eplex library\n\t\t\tec_post_string(\"lib(eplex)\");\n\n\t\t\t// Create ECLiPSe variables\n\t\t\tVars = ec_refs_create_newvars(num_lp_vars);\n\t\t\tCost = ec_ref_create_newvar();\n\t\t\tvarlist = ec_listofrefs(Vars);\n\n\t\t\t// Define the domain of the variables\n\t\t\tec_post_goal(ec_term(\n\t\t\t\t\t\t\tec_did(\"::\",2),\n\t\t\t\t\t\t\tvarlist,\n\t\t\t\t\t\t\tec_term(ec_did(\"..\",2), ec_double(0.0), ec_double(1e20))));\n\n\t\t\tstop = util_cpu_time();\n\t\t\ttime_for_setup = (double)(stop - start3)/1000;\n\t\t\tstart2 = stop;\n\n\t\t\t// Add constraints to LP problem\n\t\t\tint x;\n\t\t\t//h1 = h2 = 0;\n\t\t\t/*for (i = 0; i < n; i++) {\n\t\t\t // Add constraints for maybe and target states\n\t\t\t if (maybe_vec[i] > 0 || yes_vec[i] > 0) \n\t\t\t for (j = 0; j < map_var[i+1]-map_var[i]; j++) {// \\Sigma_{v\\in V/F} y_{(v, \\gamma)}\n\t\t\t printf(\"constraints_ints[%1d][%1d] = %1d, \", i, j, constraints_ints[i][j]);\n\t\t\t printf(\"constraints_reals[%1d][%1d] = %g\\n\", i, j, constraints_reals[i][j]);\n\t\t\t }\n\t\t\t printf(\"constraints_sp[%1d] = %1d\\n\\n\", i, constraints_sp[i]);\n\t\t\t }*/\n\n\t\t\t//count = map_var[i+1] - map_var[i];\n\t\t\th1 = h2 = 0;\n\t\t\tfor (x = 0; x < n; x++) { // h2: row index\n\t\t\t\tif(maybe_vec[x]> 0 || yes_vec[x]> 0) {\n\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\tl1 = row_starts[x];\n\t\t\t\t\t\th1 = row_starts[x+1];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tl1 = h1;\n\t\t\t\t\t\th1 += row_counts[x];\n\t\t\t\t\t}\n\t\t\t\t\tcount = 0;\n\t\t\t\t\tfor (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2 = h2;\n\t\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif(h2-l2==1 && cols[l2] == x)\n\t\t\t\t\t\tcount++;\n\t\t\t\t\t\telse\n\t\t\t\t\t\tfor(k=l2; k<h2; k++) { // k: column index\n\t\t\t\t\t\t\t// get the index of the corresponding variable\n\t\t\t\t\t\t\ti = cols[k];\n\t\t\t\t\t\t\tif(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n\t\t\t\t\t\t\t\t//printf(\"\tx = %1d, i = %1d, nonzeros = %g, j = %1d, l1 = %1d, count = %1d, map_var[x]+j-l1-count = %1d\\n\", \n\t\t\t\t\t\t\t\t//\t\t x, i, non_zeros[k], j, l1, count, map_var[x]+j-l1-count);\n\t\t\t\t\t\t\t\tconstraints_ints = (int *)constraints_int_ptr[i];\n\t\t\t\t\t\t\t\tconstraints_reals = (double *)constraints_real_ptr[i];\n\t\t\t\t\t\t\t\tfor(k_r=0; k_r<constraints_sp[i]; k_r++)\n\t\t\t\t\t\t\t\tif(constraints_ints[k_r]==map_var[x]+j-l1-count)\n\t\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t\t\tif(k_r == constraints_sp[i]) {\n\t\t\t\t\t\t\t\t\t//count++;\n\t\t\t\t\t\t\t\t\tconstraints_ints[k_r]=map_var[x]+j-l1-count;\n\t\t\t\t\t\t\t\t\tconstraints_reals[k_r] = -non_zeros[k];\n\t\t\t\t\t\t\t\t\tconstraints_sp[i]++;\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tconstraints_reals[k_r] -= non_zeros[k];\n\t\t\t\t\t\t\t\t\tif(constraints_reals[k_r] == 0.0) { // In fact, this cannot happen.\n\t\t\t\t\t\t\t\t\t\t//count--;\n\t\t\t\t\t\t\t\t\t\tfor(l2_r=k_r; l2_r<constraints_sp[i]-1; l2_r++) {\n\t\t\t\t\t\t\t\t\t\t\tconstraints_reals[l2_r] = constraints_reals[l2_r+1];\n\t\t\t\t\t\t\t\t\t\t\tconstraints_ints[l2_r] = constraints_ints[l2_r+1];\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\tconstraints_sp[i]--;\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else if(use_counts) {\n\t\t\t\t\tl1 = h1;\n\t\t\t\t\th1 += row_counts[x];\n\t\t\t\t\tfor (j = l1; j < h1; j++)\n\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t/*fprintf(f, \"\t\");\n\t\t\t l2 = 0;\n\t\t\t for (k = 0; k < num_lp_vars; k++) \n\t\t\t if(arr_reals[k] != 0) {\n\t\t\t if(arr_reals[k] > 0 && l2 > 0)\n\t\t\t fprintf(f, \"+\");\n\t\t\t fprintf(f, \"%g*X%1d\", arr_reals[k], k+1); \n\t\t\t l2++;\n\t\t\t }\n\t\t\t fprintf(f, \" $= %g,\\n\", (start_index==i ? 1.0 : 0.0));\n\t\t\t //printf(\"\t\tcount = %1d\\n\", count);\n\t\t\t fflush(f);*/\n\n\t\t\t//pword tail = ec_nil();\n\t\t\t//x = 0;\n\n\t\t\t/*for(k=num_lp_vars-1; k>=0; k--)\n\t\t\t if(arr_reals[k] != 0.0) \n\t\t\t tail = ec_list(ec_refs_get(Vars, k), tail);\n\t\t\t for(k=0; k<num_lp_vars; k++)\n\t\t\t if(arr_reals[k] != 0.0) \n\t\t\t arr_reals[x++] = arr_reals[k];*/\n\t\t\t/*printf(\"arr_reals & arr_ints = \");\n\t\t\t for(k=0; k<sp; k++) {\n\t\t\t printf(\"(%1d, %g) \", arr_ints[k], arr_reals[k]);\t\t\n\t\t\t }\n\t\t\t printf(\"\\n\");*/\n\n\t\t\t/*for(k=sp-1; k>=0; k--)\n\t\t\t tail = ec_list(ec_refs_get(Vars, arr_ints[k]), tail);\n\t\t\t ec_post_goal(ec_term(ec_did((\"$=\"),2), \n\t\t\t ec_term(ec_did(\"*\",2), \n\t\t\t tail, \n\t\t\t ec_listofdouble(sp, arr_reals)), \n\t\t\t ec_double((start_index==i ? 1.0 : 0.0))));*/\n\t\t\t/*ec_post_goal(ec_term(ec_did((\"$=\"),2), \n\t\t\t ec_term(ec_did(\"*\",2), \n\t\t\t varlist, \n\t\t\t ec_listofdouble(num_lp_vars, arr_reals)), \n\t\t\t ec_double((start_index==i ? 1.0 : 0.0))));*/\n\t\t\t//printf(\"output LP constraints to ECLiSPe\\n\");\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\tif (maybe_vec[i]> 0 || yes_vec[i]> 0) {\n\t\t\t\tconstraints_ints = (int *)constraints_int_ptr[i];\n\t\t\t\tconstraints_reals = (double *)constraints_real_ptr[i];\n\t\t\t\tpword tail = ec_nil();\n\t\t\t\tfor(k=constraints_sp[i]-1; k>=0; k--)\n\t\t\t\ttail = ec_list(ec_refs_get(Vars, constraints_ints[k]), tail);\n\t\t\t\tec_post_goal(ec_term(ec_did((\"$=\"),2),\n\t\t\t\t\t\t\t\tec_term(ec_did(\"*\",2),\n\t\t\t\t\t\t\t\t\t\ttail,\n\t\t\t\t\t\t\t\t\t\tec_listofdouble(constraints_sp[i], constraints_reals)),\n\t\t\t\t\t\t\t\tec_double((start_index==i ? 1.0 : 0.0))));\n\t\t\t\t/*printf(\"i =%1d, constrains_sp = %1d, \", i, constraints_sp[i]);\n\t\t\t\t for(k=0; k<constraints_sp[i]; k++)\n\t\t\t\t printf(\"(%1d, %g) \", constraints_ints[i][k], constraints_reals[i][k]);\n\t\t\t\t printf(\"\\n\");*/\n\t\t\t\tdelete[] constraints_ints;\n\t\t\t\tdelete[] constraints_reals;\n\t\t\t}\n\t\t\tdelete[] constraints_sp;\n\t\t\tdelete[] constraints_int_ptr;\n\t\t\tdelete[] constraints_real_ptr;\n\t\t\tPN_PrintToMainLog(env, \"Adding extra constraints for probabilisitic bounds\\n\");\n\t\t\tfor(i=0; i<num_targets; i++) {\n\t\t\t\tif(relops[i]==0 || relops[i]>2)\n\t\t\t\tcontinue;\n\t\t\t\t//PN_PrintToMainLog(env, \"num_map = %1d, i = %1d, bound = %1.1f\\n\", num_map, i, bounds[i]);\n\t\t\t\tfor(k=0; k<num_lp_vars; k++)\n\t\t\t\tarr_reals[k] = 0.0;\n\n\t\t\t\tcount = 0; // count the number of extra transitions for the i_th target \n\t\t\t\tfor(k=0; k<n; k++)\n\t\t\t\tif(yes_vecs[i][k]> 0) {\n\t\t\t\t\tarr_reals[map_var[k+1]-1] = 1.0;\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\n\t\t\t\t/*fprintf(f, \"\t\");\n\t\t\t\t l2 = 0;\n\t\t\t\t for (k = 0; k < num_lp_vars; k++) \n\t\t\t\t if(arr_reals[k] != 0) {\n\t\t\t\t if(arr_reals[k] > 0 && l2 > 0)\n\t\t\t\t fprintf(f, \"+\");\n\t\t\t\t fprintf(f, \"%g*X%1d\", arr_reals[k], k+1); \n\t\t\t\t l2++;\n\t\t\t\t }\n\t\t\t\t fprintf(f, \" $>= %g,\\n\", bounds[i]);\n\t\t\t\t fflush(f);*/\n\n\t\t\t\tpword tail = ec_nil();\n\t\t\t\tx = 0;\n\n\t\t\t\tfor(k=num_lp_vars-1; k>=0; k--)\n\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\ttail = ec_list(ec_refs_get(Vars, k), tail);\n\t\t\t\tfor(k=0; k<num_lp_vars; k++)\n\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\tarr_reals[x++] = arr_reals[k];\n\t\t\t\tec_post_goal(ec_term(ec_did((\"$>=\"),2),\n\t\t\t\t\t\t\t\tec_term(ec_did(\"*\",2),\n\t\t\t\t\t\t\t\t\t\ttail,\n\t\t\t\t\t\t\t\t\t\tec_listofdouble(count, arr_reals)),\n\t\t\t\t\t\t\t\tec_double(bounds[i])));\n\n\t\t\t\t/*ec_post_goal(ec_term(ec_did((\"$=\"),2), \n\t\t\t\t ec_term(ec_did(\"*\",2), \n\t\t\t\t varlist, \n\t\t\t\t ec_listofdouble(num_lp_vars, arr_reals)), \n\t\t\t\t ec_double(0.0)));*/\n\t\t\t}\n\n\t\t\t// Adding constraints for rewards\n\t\t\t/*if(relops[0] > 2) {\n\t\t\t for(i=0; i<num_lp_vars; i++)\n\t\t\t arr_reals[i] = 0;\n\n\t\t\t h1 = h2 = h2_r = 0;\n\t\t\t for(i=0; i<n; i++) \n\t\t\t if(maybe_vec_r[i] > 0) {\n\t\t\t for(j=num_lp_vars; j<num_lp_vars + n_maybe_r; j++)\n\t\t\t arr_reals[j] = 0;\n\t\t\t arr_reals[map_var_r[i]+num_lp_vars] = 1.0;\n\n\t\t\t if (!use_counts) { // assume we always do not use counts\n\t\t\t l1 = row_starts[i]; \n\t\t\t h1 = row_starts[i+1]; \n\t\t\t } else { // Problematic\n\t\t\t l1 = h1; \n\t\t\t h1 += row_counts[i]; \n\t\t\t }\n\t\t\t for (j = l1; j < h1; j++) {// \\Sigma_{v\\in V/F} y_{(v, \\gamma)}\n\t\t\t if (!use_counts) { \n\t\t\t l2 = choice_starts[j]; \n\t\t\t h2 = choice_starts[j+1]; \n\t\t\t } else { \n\t\t\t l2 = h2; \n\t\t\t h2 += choice_counts[j]; \n\t\t\t }\n\t\t\t if (!use_counts_r) { \n\t\t\t l2_r = choice_starts_r[j]; \n\t\t\t h2_r = choice_starts_r[j+1]; \n\t\t\t } else { \n\t\t\t l2_r = h2_r; \n\t\t\t h2_r += choice_counts_r[j]; \n\t\t\t }\n\t\t\t for (k = l2; k < h2; k++) {\n\t\t\t // find corresponding transition reward if any\n\t\t\t // Hongyang: Can it be simplified?\n\t\t\t k_r = l2_r; \n\t\t\t while (k_r < h2_r && cols_r[k_r] != cols[k]) \n\t\t\t k_r++;\n\t\t\t // if there is one, add reward * prob to reward value\n\t\t\t if (k_r < h2_r && (maybe_vec[cols[k]] > 0 || yes_vecs[0][cols[k]] > 0)) {\n\t\t\t arr_reals[map_var[i]+j-l1] -= non_zeros_r[k_r] * non_zeros[k]; \n\t\t\t if(maybe_vec[cols[k]] > 0)\n\t\t\t arr_reals[map_var_r[cols[k]]+num_lp_vars] -= non_zeros[k_r];\n\t\t\t }\n\t\t\t }\n\t\t\t \n\t\t\t }\n\t\t\t printf(\"\t\tarr_reals:\");\n\t\t\t for (k = 0; k < num_lp_vars+n_maybe_r; k++) \n\t\t\t printf(\" %1.1f\", arr_reals[k]); \n\t\t\t printf(\" = 0\\n\");\n\t\t\t fflush(stdout);\n\t\t\t \n\t\t\t pword tail = ec_nil();\n\t\t\t x = 0;\n\t\t\t \n\t\t\t for(k=num_lp_vars+n_maybe_r-1; k>=0; k--)\n\t\t\t if(arr_reals[k] != 0.0) \n\t\t\t tail = ec_list(ec_refs_get(Vars, k), tail);\n\t\t\t for(k=0; k<num_lp_vars+n_maybe_r; k++)\n\t\t\t if(arr_reals[k] != 0.0) \n\t\t\t arr_reals[x++] = arr_reals[k];\n\t\t\t ec_post_goal(ec_term(ec_did((\"$=\"),2), \n\t\t\t ec_term(ec_did(\"*\",2), \n\t\t\t tail, \n\t\t\t ec_listofdouble(x, arr_reals)), \n\t\t\t ec_double(0.0)));\n\t\t\t \n\t\t\t }\n\t\t\t }*/\n\n\t\t\tPN_PrintToMainLog(env, \"Computing optimisation...\\n\");\n\t\t\tfflush(stdout);\n\t\t\tpword tail = ec_nil();\n\t\t\tx = 0;\n\t\t\tif(relops[0]> 0 && relops[0]<=2) {\n\t\t\t\t//fprintf(f, \"\toptimize(max(\");\n\t\t\t\t//l2 = 0;\n\t\t\t\tfor(i=0; i<n; i++)\n\t\t\t\tif(yes_vec[i]> 0) {\n\t\t\t\t\ttail = ec_list(ec_refs_get(Vars, map_var[i+1]-1), tail);\n\t\t\t\t\tarr_reals[x++] = 1.0;\n\t\t\t\t\t//if(l2 > 0)\n\t\t\t\t\t//\tfprintf(f, \"+\");\t\t\t\t\n\t\t\t\t\t//fprintf(f, \"X%1d\", map_var[i+1]); \n\t\t\t\t\t//l2++;\n\t\t\t\t}\n\t\t\t\t//fprintf(f, \"), Cost).\\n\");\n\t\t\t\t//fflush(f);\n\t\t\t} else if(relops[0] == 0) {\n\t\t\t\t//fprintf(f, \"\toptimize(max(\");\n\t\t\t\t//l2 = 0;\n\t\t\t\tfor(i=0; i<n; i++)\n\t\t\t\tif(yes_vecs[0][i]> 0) {\n\t\t\t\t\ttail = ec_list(ec_refs_get(Vars, map_var[i+1]-1), tail);\n\t\t\t\t\tarr_reals[x++] = 1.0;\n\t\t\t\t\t//if(l2 > 0)\n\t\t\t\t\t//\tfprintf(f, \"+\");\t\t\t\t\n\t\t\t\t\t//fprintf(f, \"X%1d\", map_var[i+1]); \n\t\t\t\t\t//l2++;\n\t\t\t\t}\n\t\t\t\t//fprintf(f, \"), Cost).\\n\");\n\t\t\t\t//fflush(f);\n\t\t\t} else {\n\t\t\t\t/*x = 1;\n\t\t\t\t arr_reals[0] = 1.0;\n\t\t\t\t tail = ec_list(ec_refs_get(Vars, map_var_r[start_index]+num_lp_vars), tail);*/\n\t\t\t\tPN_PrintToMainLog(env, \"computing max function for rewards ...\\n\");\n\t\t\t\tdouble *non_zeros_r;\n\t\t\t\tunsigned char *choice_counts_r;\n\t\t\t\tint *choice_starts_r;\n\t\t\t\tbool use_counts_r;\n\t\t\t\tunsigned int *cols_r;\n\t\t\t\ttrans_rewards = jlong_to_DdNode(trr); // transition rewards\t\t\n\t\t\t\tCudd_Ref(trans_rewards);\n\t\t\t\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, maybe);\n\t\t\t\tPN_PrintToMainLog(env, \"Building sparse matrix (transition rewards)... \");\n\t\t\t\tndsm_r = build_sub_nd_sparse_matrix(ddman, a, trans_rewards, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\t\t\tnnz_r = ndsm_r->nnz;\n\t\t\t\tnc_r = ndsm_r->nc;\n\t\t\t\t// print out info\n\t\t\t\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%d, k=%d] \", n, nc_r, nnz_r, ndsm_r->k);\n\t\t\t\tkb = (nnz_r*12.0+nc_r*4.0+n*4.0)/1024.0;\n\t\t\t\tkbt += kb;\n\t\t\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t\t\tnon_zeros_r = ndsm_r->non_zeros;\n\t\t\t\tchoice_counts_r = ndsm_r->choice_counts;\n\t\t\t\tchoice_starts_r = (int *)ndsm_r->choice_counts;\n\t\t\t\tuse_counts_r = ndsm_r->use_counts;\n\t\t\t\tcols_r = ndsm_r->cols;\n\n\t\t\t\tfor(i=0; i<num_lp_vars; i++)\n\t\t\t\tarr_reals[i] = 0;\n\n\t\t\t\th1 = h2 = l2_r = h2_r = 0;\n\t\t\t\tfor(i=0; i<n; i++)\n\t\t\t\tif(maybe_vec[i]> 0) {\n\t\t\t\t\tif (!use_counts) { // assume we always do not use counts\n\t\t\t\t\t\tl1 = row_starts[i];\n\t\t\t\t\t\th1 = row_starts[i+1];\n\t\t\t\t\t} else { // Problematic\n\t\t\t\t\t\tl1 = h1;\n\t\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t\t}\n\t\t\t\t\tfor (j = l1; j < h1; j++) {// \\Sigma_{v\\in V/F} y_{(v, \\gamma)}*c_{(v, \\gamma)}\n\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2 = h2;\n\t\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (!use_counts_r) {\n\t\t\t\t\t\t\tl2_r = choice_starts_r[j];\n\t\t\t\t\t\t\th2_r = choice_starts_r[j+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2_r = h2_r;\n\t\t\t\t\t\t\th2_r += choice_counts_r[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tk_r = l2_r;\n\t\t\t\t\t\twhile (k_r < h2_r && cols_r[k_r] != cols[l2])\n\t\t\t\t\t\tk_r++;\n\t\t\t\t\t\t// if there is one, add reward * prob to reward value\n\t\t\t\t\t\tif (k_r < h2_r) {\n\t\t\t\t\t\t\tarr_reals[map_var[i]+j-l1] = non_zeros_r[k_r];\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} else if(use_counts) { // count the number of choices for non maybe nodes. Is it necessary?\n\t\t\t\t\tl1 = h1;\n\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t\th2_r += choice_counts_r[j];\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t/*PN_PrintToMainLog(env, \"\t\tarr_reals:\");\n\t\t\t\t for (k = 0; k < num_lp_vars; k++) \n\t\t\t\t PN_PrintToMainLog(env, \" %1.1f\", arr_reals[k]); \n\t\t\t\t PN_PrintToMainLog(env, \"\\n\");\n\t\t\t\t fflush(stdout);*/\n\n\t\t\t\tfor(k=num_lp_vars-1; k>=0; k--)\n\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\ttail = ec_list(ec_refs_get(Vars, k), tail);\n\t\t\t\tfor(k=0; k<num_lp_vars; k++)\n\t\t\t\tif(arr_reals[k] != 0.0)\n\t\t\t\tarr_reals[x++] = arr_reals[k];\n\t\t\t}\n\t\t\tec_post_goal( ec_term(ec_did(\"optimize\", 2),\n\t\t\t\t\t\t\tec_term(ec_did(\"max\", 1),\n\t\t\t\t\t\t\t\t\tec_term(ec_did(\"*\",2), tail, ec_listofdouble(x, arr_reals))),\n\t\t\t\t\t\t\tec_ref_get(Cost)));\n\t\t\t/*ec_post_goal( ec_term(ec_did(\"optimize\", 2),\n\t\t\t ec_term(ec_did(\"max\", 1), \n\t\t\t ec_term(ec_did(\"*\",2), varlist, ec_listofdouble(num_lp_vars, pc))), \n\t\t\t ec_ref_get(Cost)));*/\n\t\t\t//fclose(f);\n\t\t}\n\n\t\t/* write the produce mdp to file model.dot */\n\t\tprintf(\"Writing the model to model.dot\\n\"); fflush(stdout);\n\n\t\tf = fopen(\"model.dot\", \"w\"); /* create a file for writing */\n\t\tf = NULL;\n\t\tif(f==NULL) {\n\t\t\tPN_PrintToMainLog(env, \"\\nWarning: Output of graph cancelled (could not open file \\\"%s\\\").\\n\", \"model.dot\");\n\t\t} else {\n\t\t\tfprintf(f, \"digraph model {\\n\");\n\t\t\tfor(i=0; i<n; i++)\n\t\t\tif(i == start_index)\n\t\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=ellipse]\\n\", i, i);\n\t\t\telse if(yes_vec[i]> 0)\n\t\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=doublecircle]\\n\", i, i);\n\t\t\telse\n\t\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=circle]\\n\", i, i);\n\t\t\tcount = n; l1 = h1 = l2 = h2 = 0;\n\t\t\tfor(i=0; i<n; i++) {\n\t\t\t\tif (!use_counts) {\n\t\t\t\t\tl1 = row_starts[i];\n\t\t\t\t\th1 = row_starts[i+1];\n\t\t\t\t} else {\n\t\t\t\t\tl1 = h1;\n\t\t\t\t\th1 += row_counts[i];\n\t\t\t\t}\n\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tl2 = h2;\n\t\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t\t}\n\t\t\t\t\tif(h2-l2>1) {\n\t\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=point]\\n\", count);\n\t\t\t\t\t\tfprintf(f, \"\t\t%1d -> %1d\\n\", i, count);\n\t\t\t\t\t\tfor(k=l2; k<h2; k++)\n\t\t\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%g\\\"]\\n\", count,\n\t\t\t\t\t\t\t\tcols[k], non_zeros[k]);\n\t\t\t\t\t\tcount ++;\n\t\t\t\t\t} else\n\t\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%g\\\"]\\n\", i,\n\t\t\t\t\t\t\tcols[l2], non_zeros[l2]);\n\t\t\t\t}\n\t\t\t}\n\t\t\tfprintf(f, \"}\\n\");\n\t\t\tfclose(f);\n\t\t}\n\n\t\t// Get the result from the solver\n\t\tif (ec_resume1(0) == PSUCCEED) { /* solve */\n\t\t\tstop = util_cpu_time();\n\t\t\tif (ec_get_double(ec_ref_get(Cost), &lp_result) == PSUCCEED)\n\t\t\tPN_PrintToMainLog(env, \"Cost is %g\\n\", lp_result);\n\t\t\telse\n\t\t\tPN_PrintToMainLog(env, \"Cost is ?\\n\");\n\n\t\t\tdouble *var_values;\n\t\t\tvar_values = new double[num_lp_vars+n_maybe_r];\n\t\t\tcount = 0;\n\t\t\tfor (i=0; i<num_lp_vars+n_maybe_r; i++) {\n\t\t\t\tvar_values[i] = 0.0;\n\t\t\t\tif (ec_get_double(ec_refs_get(Vars,i), &var_values[i]) == PSUCCEED) {\n\t\t\t\t\tif(var_values[i] != 0) {\n\t\t\t\t\t\tPN_PrintToMainLog(env, \"X%d = %g\t\t\", i, var_values[i]);\n\t\t\t\t\t\tcount++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t//else\n\t\t\t\t//\tPN_PrintToMainLog(env, \"X%d = ?\t\t\");\n\t\t\t\tif(count == 8) {\n\t\t\t\t\tPN_PrintToMainLog(env, \"\\n\");\n\t\t\t\t\tcount = 0;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif(count)\n\t\t\tPN_PrintToMainLog(env, \"\\n\");\n\n\t\t\t/***********************************************************************\n\t\t\t *\n\t\t\t *\n\t\t\t * generate adversary according the solution\n\t\t\t *\n\t\t\t *\n\t\t\t ***********************************************************************/\n\t\t\tchar c = '\\0';\n\t\t\t/*if(n < 100) {\n\t\t\t\tprintf(\"Would you like to see the adversary (Y/N)\\n\"); fflush(stdout);\n\t\t\t\twhile (1) {\n\t\t\t\t\tscanf(\"%c\", &c);\n\t\t\t\t\tif(c == 'Y' || c == 'y' || c == 'N' || c == 'n')\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}*/\n\t\t\tc = 'n';\n\n\t\t\tif(c == 'Y' || c == 'y') {\n\t\t\t\tlong sp_nodes = 0; // pointer of dot nodes\n\t\t\t\tlong extra_node = n; // index of intermediate nodes for actions\n\t\t\t\tlong sp_edges = 0; // pointer of dot edges\n\t\t\t\t//int queue[n]; // search queue\n\t\t\t\tint *queue;\n\t\t\t\tlong head = 0; // pointer to the head of the queue\n\t\t\t\tlong tail = 0; // pointer to the tail of the queue\n\t\t\t\t//int nodes[n]; // indicate whether the node has been visited\n\t\t\t\tint *nodes;\n\n\t\t\t\tqueue = new int[n];\n\t\t\t\tnodes = new int[n];\n\t\t\t\tfor(i=0; i<n; i++)\n\t\t\t\tnodes[i] = 0;\n\n\t\t\t\tif(checkReach) {// Adversary for reachability\n\t\t\t\t\tint (*dot_nodes)[2];\n\t\t\t\t\tint (*dot_edges)[2];\n\t\t\t\t\tdouble *edge_probabilities;\n\t\t\t\t\t//printf(\"allocated memory for local variables:\\n\"); \n\t\t\t\t\t//printf(\"n=%1d, num_lp_vars=%1d, nnz=%1d\\n\", n, num_lp_vars, nnz);\n\t\t\t\t\t//fflush(stdout);\n\n\t\t\t\t\t//int dot_nodes[n+num_lp_vars][2]; // first entry: node number, second: shape \n\t\t\t\t\t//int dot_edges[nnz+num_lp_vars][2]; // first entry: source node, second: target\n\t\t\t\t\t//double edge_probabilities[nnz+num_lp_vars]; // edge's probability\n\n\t\t\t\t\tdot_nodes = new int[n+num_lp_vars][2];\n\t\t\t\t\tdot_edges = new int[nnz+num_lp_vars][2];\n\t\t\t\t\tedge_probabilities = new double[nnz+num_lp_vars];\n\t\t\t\t\t//int dot_nodes[n+maybe_nc][2]; // first entry: node number, second: shape \n\t\t\t\t\t//int dot_edges[nnz+maybe_nc][2]; // first entry: source node, second: target\n\t\t\t\t\t//double edge_probabilities[nnz+maybe_nc]; // edge's probability\n\n\t\t\t\t\t// put the initial state in the queue and dot_nodes\n\t\t\t\t\tqueue[tail++] = start_index;\n\t\t\t\t\tdot_nodes[sp_nodes][0] = start_index;\n\t\t\t\t\tdot_nodes[sp_nodes++][1] = 0; // shape = 0: ellipse, 1: circle, 2: point, 3: doublecircle\n\n\t\t\t\t\t// recursive procedure\n\t\t\t\t\tint head_node = -1;\n\t\t\t\t\twhile(head < tail) {\n\t\t\t\t\t\thead_node = queue[head++];\n\t\t\t\t\t\tnodes[head_node] = 1;\n\t\t\t\t\t\t// If the head node is a target state, do nothing\n\t\t\t\t\t\tif(yes_vec[head_node] == 0 && maybe_vec[head_node]> 0.0) {\n\t\t\t\t\t\t\t// the number of branches in the current state\n\t\t\t\t\t\t\th1 = map_var[head_node+1] - map_var[head_node];\n\t\t\t\t\t\t\t//PN_PrintToMainLog(env, \"h1 = %1d\\n\", h1);\n\n\t\t\t\t\t\t\tdouble sum = 0;\n\t\t\t\t\t\t\tfor(i=0; i<h1; i++)\n\t\t\t\t\t\t\tsum += var_values[map_var[head_node] + i];\n\n\t\t\t\t\t\t\tfor(i=0; i<h1; i++)\n\t\t\t\t\t\t\t// test if the action has non-zero probability\n\t\t\t\t\t\t\tif(var_values[map_var[head_node] + i]> 0) {\n\t\t\t\t\t\t\t\t// get all successor states of this action\n\t\t\t\t\t\t\t\t// First: locate the action\n\t\t\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\t\t\tl1 = row_starts[head_node];\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tl1 = 0;\n\t\t\t\t\t\t\t\t\tfor(j=0; j<head_node; j++)\n\t\t\t\t\t\t\t\t\tl1 += row_counts[j];\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tl1 += i;\n\n\t\t\t\t\t\t\t\t// Second: find all columns for this choice\n\t\t\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\t\t\tl2 = choice_starts[l1];\n\t\t\t\t\t\t\t\t\th2 = choice_starts[l1+1];\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\tl2 = 0;\n\t\t\t\t\t\t\t\t\tfor(j=0; j<l1; j++)\n\t\t\t\t\t\t\t\t\tl2 += choice_counts[j];\n\t\t\t\t\t\t\t\t\th2 = l2 + choice_counts[j];\n\t\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t\tif(h2-l2>1) {\n\t\t\t\t\t\t\t\t\t// add an intermediate node to dot_nodes\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = extra_node;\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 2;\n\t\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = extra_node;\n\t\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? var_values[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\t\tvar_values[map_var[head_node] + i]/sum;\n\n\t\t\t\t\t\t\t\t\tfor(j=l2; j<h2; j++) {\n\t\t\t\t\t\t\t\t\t\t// add the successor state to dot_nodes\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = cols[j];\n\t\t\t\t\t\t\t\t\t\tif(yes_vec[cols[j]]> 0)\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 3;\n\t\t\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 1;\n\n\t\t\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = extra_node;\n\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = cols[j];\n\t\t\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = non_zeros[j];\n\n\t\t\t\t\t\t\t\t\t\tif(maybe_vec[cols[j]]> 0 && nodes[cols[j]] == 0)\n\t\t\t\t\t\t\t\t\t\tqueue[tail++] = cols[j];\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\textra_node++;\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\t// add the successor state to dot_nodes\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = cols[l2];\n\t\t\t\t\t\t\t\t\tif(yes_vec[cols[l2]]> 0)\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 3;\n\t\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 1;\n\t\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = cols[l2];\n\t\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\t\t//edge_probabilities[sp_edges++] = var_values[map_var[head_node] + i];\n\t\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? var_values[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\t\tvar_values[map_var[head_node] + i]/sum;\n\n\t\t\t\t\t\t\t\t\tif(maybe_vec[cols[l2]]> 0 && nodes[cols[l2]] == 0)\n\t\t\t\t\t\t\t\t\tqueue[tail++] = cols[l2];\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// write to file\n\t\t\t\t\tf = fopen(\"adversary.dot\", \"w\"); /* create a file for writing */\n\t\t\t\t\tf = NULL;\n\t\t\t\t\tif(f==NULL) {\n\t\t\t\t\t\tPN_PrintToMainLog(env, \"\\nWarning: Output of adversary cancelled (could not open file \\\"%s\\\").\\n\", \"adversary.dot\");\n\t\t\t\t\t} else {\n\t\t\t\t\t\tfprintf(f, \"digraph adversary {\\n\");\n\t\t\t\t\t\tfor(i=0; i<sp_nodes; i++)\n\t\t\t\t\t\tif(dot_nodes[i][0] >= n)\n\t\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=point]\\n\", dot_nodes[i][0]);\n\t\t\t\t\t\telse\n\t\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=%s]\\n\", dot_nodes[i][0],\n\t\t\t\t\t\t\t\tdot_nodes[i][0],\n\t\t\t\t\t\t\t\t((dot_nodes[i][1]==0)? \"ellipse\" :\n\t\t\t\t\t\t\t\t\t\t((dot_nodes[i][1]==1)? \"circle\" : \"doublecircle\")));\n\t\t\t\t\t\tfor(i=0; i<sp_edges; i++)\n\t\t\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%g\\\"]\\n\", dot_edges[i][0],\n\t\t\t\t\t\t\t\tdot_edges[i][1], edge_probabilities[i]);\n\t\t\t\t\t\tfprintf(f, \"}\\n\");\n\t\t\t\t\t\tfclose(f);\n\t\t\t\t\t}\n\t\t\t\t} else {// Adversary for LTL formulas\n\t\t\t\t\tint (*dot_nodes)[2];\n\t\t\t\t\tint (*dot_edges)[2];\n\t\t\t\t\tdouble *edge_probabilities;\n\t\t\t\t\tint *terminate_nodes;\n\t\t\t\t\t//printf(\"allocated memory for local variables:\\n\"); \n\t\t\t\t\t//printf(\"n=%1d, num_lp_vars=%1d, nnz=%1d\\n\", n, num_lp_vars, nnz);\n\t\t\t\t\t//fflush(stdout);\n\n\t\t\t\t\t//int dot_nodes[n+num_lp_vars][2]; // first entry: node number, second: shape \n\t\t\t\t\t//int dot_edges[nnz+num_lp_vars][2]; // first entry: source node, second: target\n\t\t\t\t\t//double edge_probabilities[nnz+num_lp_vars]; // edge's probability\n\n\t\t\t\t\tdot_nodes = new int[n+num_lp_vars][2];\n\t\t\t\t\tdot_edges = new int[nnz+num_lp_vars][2];\n\t\t\t\t\tedge_probabilities = new double[nnz+num_lp_vars];\n\t\t\t\t\tterminate_nodes = new int[n]; // the entry stores the node number for newly added terminate nodes\n\n\t\t\t\t\t//printf(\"Done\\n\");\n\t\t\t\t\t//fflush(stdout);\n\n\t\t\t\t\tfor(i=0; i<n; i++)\n\t\t\t\t\tterminate_nodes[i] = -1;\n\n\t\t\t\t\t// put the initial state in the queue and dot_nodes\n\t\t\t\t\tqueue[tail++] = start_index;\n\t\t\t\t\tdot_nodes[sp_nodes][0] = start_index;\n\t\t\t\t\tdot_nodes[sp_nodes++][1] = 0; // shape = 0: ellipse, 1: circle, 2: point, 3: doublecircle, 4: box\n\n\t\t\t\t\t// recursive procedure\n\t\t\t\t\tint head_node = -1;\n\t\t\t\t\twhile(head < tail) {\n\t\t\t\t\t\thead_node = queue[head++];\n\n\t\t\t\t\t\tif(nodes[head_node] == 1)\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\tnodes[head_node] = 1;\n\t\t\t\t\t\t// If the head node is a target state, do nothing\n\t\t\t\t\t\tif(yes_vec[head_node]> 0 || maybe_vec[head_node]> 0) {\n\t\t\t\t\t\t\t// the number of branches in the current state\n\t\t\t\t\t\t\th1 = map_var[head_node+1] - map_var[head_node];\n\n\t\t\t\t\t\t\tdouble sum = 0;\n\t\t\t\t\t\t\tfor(i=0; i<h1; i++)\n\t\t\t\t\t\t\tsum += var_values[map_var[head_node] + i];\n\n\t\t\t\t\t\t\tfor(i=0; i<h1; i++)\n\t\t\t\t\t\t\t// test if the action has non-zero probability\n\t\t\t\t\t\t\tif(var_values[map_var[head_node] + i]> 0) {\n\t\t\t\t\t\t\t\tif(yes_vec[head_node]> 0 && i==h1-1) { // extra transition\n\t\t\t\t\t\t\t\t\t// add an intermediate node to dot_nodes\n\t\t\t\t\t\t\t\t\tif(terminate_nodes[head_node] < 0) {\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = extra_node;\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 4;\n\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = extra_node;\n\t\t\t\t\t\t\t\t\t\tterminate_nodes[head_node] = extra_node;\n\t\t\t\t\t\t\t\t\t} else\n\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = terminate_nodes[head_node];\n\t\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\t\t//edge_probabilities[sp_edges++] = var_values[map_var[head_node] + i];\n\t\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? var_values[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\t\tvar_values[map_var[head_node] + i]/sum;\n\t\t\t\t\t\t\t\t\textra_node++;\n\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\t// get all successor states of this action\n\t\t\t\t\t\t\t\t\t// First: locate the action\n\t\t\t\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\t\t\t\tl1 = row_starts[head_node];\n\t\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\t\tl1 = 0;\n\t\t\t\t\t\t\t\t\t\tfor(j=0; j<head_node; j++)\n\t\t\t\t\t\t\t\t\t\tl1 += row_counts[j];\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\tl1 += i;\n\n\t\t\t\t\t\t\t\t\t// Second: find all columns for this choice\n\t\t\t\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\t\t\t\tl2 = choice_starts[l1];\n\t\t\t\t\t\t\t\t\t\th2 = choice_starts[l1+1];\n\t\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\t\tl2 = 0;\n\t\t\t\t\t\t\t\t\t\tfor(j=0; j<l1; j++)\n\t\t\t\t\t\t\t\t\t\tl2 += choice_counts[j];\n\t\t\t\t\t\t\t\t\t\th2 = l2 + choice_counts[j];\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\tif(h2-l2>1) {\n\t\t\t\t\t\t\t\t\t\t// add an intermediate node to dot_nodes\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = extra_node;\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 2;\n\t\t\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = extra_node;\n\t\t\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\t\t\t//edge_probabilities[sp_edges++] = var_values[map_var[head_node] + i];\n\t\t\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? var_values[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\t\t\tvar_values[map_var[head_node] + i]/sum;\n\n\t\t\t\t\t\t\t\t\t\tfor(j=l2; j<h2; j++) {\n\t\t\t\t\t\t\t\t\t\t\t// add the successor state to dot_nodes\n\t\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = cols[j];\n\t\t\t\t\t\t\t\t\t\t\tif(yes_vec[cols[j]]> 0)\n\t\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 3;\n\t\t\t\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 1;\n\n\t\t\t\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = extra_node;\n\t\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = cols[j];\n\t\t\t\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = non_zeros[j];\n\n\t\t\t\t\t\t\t\t\t\t\tif((maybe_vec[cols[j]]> 0 || yes_vec[cols[j]]> 0) &&\n\t\t\t\t\t\t\t\t\t\t\t\t\tnodes[cols[j]] == 0)\n\t\t\t\t\t\t\t\t\t\t\tqueue[tail++] = cols[j];\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\textra_node++;\n\t\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\t\t// add the successor state to dot_nodes\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = cols[l2];\n\t\t\t\t\t\t\t\t\t\tif(yes_vec[cols[l2]]> 0)\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 3;\n\t\t\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 1;\n\t\t\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = cols[l2];\n\t\t\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\t\t\t//edge_probabilities[sp_edges++] = var_values[map_var[head_node] + i];\n\t\t\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? var_values[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\t\t\tvar_values[map_var[head_node] + i]/sum;\n\n\t\t\t\t\t\t\t\t\t\tif((maybe_vec[cols[l2]]> 0 || yes_vec[cols[l2]]> 0) &&\n\t\t\t\t\t\t\t\t\t\t\t\tnodes[cols[l2]] == 0) {\n\t\t\t\t\t\t\t\t\t\t\tqueue[tail++] = cols[l2];\n\t\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\tprintf(\"generating adversary file\\n\"); fflush(stdout);\n\n\t\t\t\t\t// write to file\n\t\t\t\t\tf = fopen(\"adversary.dot\", \"w\"); /* create a file for writing */\n\t\t\t\t\tif(f==NULL) {\n\t\t\t\t\t\tPN_PrintToMainLog(env, \"\\nWarning: Output of adversary cancelled (could not open file \\\"%s\\\").\\n\", \"adversary.dot\");\n\t\t\t\t\t} else {\n\t\t\t\t\t\tfprintf(f, \"digraph adversary {\\n\");\n\t\t\t\t\t\tfor(i=0; i<sp_nodes; i++)\n\t\t\t\t\t\tif(dot_nodes[i][0] >= n) {\n\t\t\t\t\t\t\tif(dot_nodes[i][1] == 2)\n\t\t\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=point]\\n\", dot_nodes[i][0]);\n\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=box, fillcolor=black]\\n\", dot_nodes[i][0]);\n\t\t\t\t\t\t} else\n\t\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=%s]\\n\", dot_nodes[i][0],\n\t\t\t\t\t\t\t\tdot_nodes[i][0],\n\t\t\t\t\t\t\t\t((dot_nodes[i][1]==0)? \"ellipse\" :\n\t\t\t\t\t\t\t\t\t\t((dot_nodes[i][1]==1)? \"circle\" : \"doublecircle\")));\n\t\t\t\t\t\tfor(i=0; i<sp_edges; i++)\n\t\t\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%g\\\"]\\n\", dot_edges[i][0],\n\t\t\t\t\t\t\t\tdot_edges[i][1], edge_probabilities[i]);\n\t\t\t\t\t\tfprintf(f, \"}\\n\");\n\t\t\t\t\t\tfclose(f);\n\t\t\t\t\t}\n\n\t\t\t\t\tdelete[] dot_nodes;\n\t\t\t\t\tdelete[] dot_edges;\n\t\t\t\t\tdelete[] edge_probabilities;\n\t\t\t\t\tdelete[] terminate_nodes;\n\t\t\t\t}\n\n\t\t\t\tdelete[] queue;\n\t\t\t\tdelete[] nodes;\n\t\t\t}\n\t\t\tdelete[] var_values;\n\t\t}\n\t\telse PN_PrintToMainLog(env, \"No solution\\n\");\n\n\t\t// Destroy variables and clean up\n\t\tec_refs_destroy(Vars);\n\t\tec_ref_destroy(Cost);\n\t\tec_cleanup();\n\n\t\t//stop = util_cpu_time();\n\t\ttime_for_lp = (double)(stop - start2)/1000;\n\t\ttime_taken = (double)(stop - start3)/1000;\n\t\tPN_PrintToMainLog(env, \"\\nCBC: LP problem solved in %.2f seconds (setup %.2f, lpsolve %.2f)\\n\", time_taken, time_for_setup, time_for_lp);\n\n\t\tdelete yes_vec;\n\t\tdelete map_var;\n\t\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (yes2_vec) delete[] yes2_vec;\n\t\tyes2_vec = 0;\n\t\tif (target_ptrs) env->ReleaseLongArrayElements(_targets, target_ptrs, 0);\n\t\tif (relops) env->ReleaseIntArrayElements(_relops, relops, 0);\n\t\tif (bounds) env->ReleaseDoubleArrayElements(_bounds, bounds, 0);\n\t} catch (const char *err) {\n\t\tPN_SetErrorMessage(err);\n\t\tif (yes2_vec) delete yes2_vec;\n\t\tyes2_vec = 0;\n\t\tif (target_ptrs) env->ReleaseLongArrayElements(_targets, target_ptrs, 0);\n\t\tif (relops) env->ReleaseIntArrayElements(_relops, relops, 0);\n\t\tif (bounds) env->ReleaseDoubleArrayElements(_bounds, bounds, 0);\n\t}\n\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\tif (ndsm) delete ndsm;\n\tif (ndsm_r) delete ndsm_r;\n\t//if (yes1_vec) delete[] yes1_vec;\n\tdelete[] maybe_vec;\n\tfor(i=0; i<num_targets; i++)\n\tdelete[] yes_vecs[i];\n\tdelete[] arr_reals;\n\tdelete[] arr_ints;\n\tif (target_ptrs) env->ReleaseLongArrayElements(_targets, target_ptrs, 0);\n\tif (relops) env->ReleaseIntArrayElements(_relops, relops, 0);\n\tif (bounds) env->ReleaseDoubleArrayElements(_bounds, bounds, 0);\n\n\treturn lp_result;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetMultiReach1.cc",
    "content": "//==============================================================================\n//  \n//  Copyright (c) 2002-\n//  Authors:\n//  * Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//  * Hongyang Qu <hongyang.qu@comlab.ox.ac.uk> (University of Oxford)\n//  \n//------------------------------------------------------------------------------\n//  \n//  This file is part of PRISM.\n//  \n//  PRISM is free software; you can redistribute it and/or modify\n//  it under the terms of the GNU General Public License as published by\n//  the Free Software Foundation; either version 2 of the License, or\n//  (at your option) any later version.\n//  \n//  PRISM is distributed in the hope that it will be useful,\n//  but WITHOUT ANY WARRANTY; without even the implied warranty of\n//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//  GNU General Public License for more details.\n//  \n//  You should have received a copy of the GNU General Public License\n//  along with PRISM; if not, write to the Free Software Foundation,\n//  Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//  \n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"sparse_adv.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n#include \"lp_lib.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReach1\n(\n JNIEnv *env,\n jclass cls,\n jlong __jlongpointer t, // trans matrix\n jlong __jlongpointer ta, // trans action labels\n jobject synchs,\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv, // nondet vars\n jint num_ndvars,\n jlongArray _targets, // target state sets\n jlongArray _combinations, // combinations of target state sets\n jintArray _combinationIDs, // combinations' ID\n jintArray _relops, // target relops (0:=?, 1:>, 2:>=)\n jdoubleArray _bounds, // target probability bounds\n jlong __jlongpointer m, // 'maybe' states\n jlong __jlongpointer _start // initial state(s)\n )\n{\n  // cast function parameters\n  DdNode *trans = jlong_to_DdNode(t); // trans matrix\n  DdNode *trans_actions = jlong_to_DdNode(ta);  // trans action labels\n  ODDNode *odd = jlong_to_ODDNode(od); // reachable states\n  DdNode **rvars = jlong_to_DdNode_array(rv); // row vars\n  DdNode **cvars = jlong_to_DdNode_array(cv); // col vars\n  DdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n  DdNode *maybe = jlong_to_DdNode(m); // 'maybe' states\n  DdNode *start = jlong_to_DdNode(_start); // initial state(s)\n\n  // target info  \n  jlong *target_ptrs = NULL;\n  DdNode **targets = NULL;\n  jlong *combination_ptrs = NULL;\n  DdNode **combinations = NULL;\n  jint *relops = NULL, *combinationIDs = NULL;\n  double *bounds = NULL;\n  // mtbdds\n  DdNode *a = NULL, **yes = NULL, *maybe_yes = NULL, *loops = NULL, *tmp = NULL;\n  // model stats\n  int num_targets, num_combinations, n, nc, nc_r;\n  long nnz, nnz_r;\n  // sparse matrix\n  NDSparseMatrix *ndsm = NULL, *ndsm_r = NULL;\n  // action info\n  jstring *action_names_jstrings;\n  const char** action_names = NULL;\n  int num_actions;\n  // vectors\n  double **yes_vecs, **combination_vecs, *maybe_vec = NULL/*, *maybe_vec_r = NULL*/;\n  // timing stuff\n  long start1, start2, start3, stop, stop2;\n  double time_taken, time_for_setup, time_for_lp;\n  // lp stuff\n  lprec *lp = NULL;\n  REAL *arr_reals = NULL;// *lp_soln = NULL;\n  int *arr_ints = NULL;\n  bool selfloop;\n  int arr_size, res;\n  int num_lp_vars;\n  double *lp_soln;\n  double lp_result = 0.0;\n  bool lp_solved = false;\n  // misc\n  int i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, start_index, count;\n  double d1, d2, kb, kbt;\n  bool done, first;\n  jclass vn_cls;\n  jmethodID vn_mid;\n\n  // exception handling around whole function\n  try {\n\n    // start clocks \n    start1 = start2 = util_cpu_time();\n    \n    // Extract arrays of target info from function parameters\n    num_targets = (int)env->GetArrayLength(_targets);\n    target_ptrs = env->GetLongArrayElements(_targets, 0);\n    targets = new DdNode*[num_targets];\n    for (i = 0; i < num_targets; i++) \n      targets[i] = jlong_to_DdNode(target_ptrs[i]);\n    relops = env->GetIntArrayElements(_relops, 0);\n    bounds = env->GetDoubleArrayElements(_bounds, 0);\n\n    num_combinations = (int)env->GetArrayLength(_combinations);\n    combination_ptrs = env->GetLongArrayElements(_combinations, 0);\n    combinations = new DdNode*[num_combinations];\n    combination_vecs = new double*[num_combinations];\n    for (i = 0; i < num_combinations; i++) {\n      combinations[i] = jlong_to_DdNode(combination_ptrs[i]);\n    }\n    combinationIDs = env->GetIntArrayElements(_combinationIDs, 0);\n\n    yes = new DdNode*[num_targets];\n    yes_vecs = new double*[num_targets];\n    for(i=0; i<num_targets; i++) \n      yes[i] = targets[i];\n  \n    // Display some info about the targets/combinations\n    PN_PrintToMainLog(env, \"\\n%d Targets:\\n\", num_targets);\n    for (i = 0; i < num_targets; i++) {\n      PN_PrintToMainLog(env, \"#%d: \", i);\n      switch (relops[i]) {\n      case 0: PN_PrintToMainLog(env, \"Pmax=?\"); break;\n      case 1: PN_PrintToMainLog(env, \"P>%g\", bounds[i]); break;\n      case 2: PN_PrintToMainLog(env, \"P>=%g\", bounds[i]); break;\n      }\n      PN_PrintToMainLog(env, \" (%.0f states)\\n\", DD_GetNumMinterms(ddman, targets[i], num_rvars));\n    }\n    PN_PrintToMainLog(env, \"%d Target combinations:\\n\", num_combinations);\n    for (i = 0; i < num_combinations; i++) {\n      PN_PrintToMainLog(env, \"#%d: \", i);\n      PN_PrintToMainLog(env, \"%d \", (int)combinationIDs[i]);\n      PN_PrintToMainLog(env, \" (%.0f states)\\n\", DD_GetNumMinterms(ddman, combinations[i], num_rvars));\n    }\n  \n    // Filter out rows, store in \"a\"\n    Cudd_Ref(maybe);\n    maybe_yes = maybe;\n    for (i = 0; i < num_targets; i++) {\n      Cudd_Ref(yes[i]);\n      maybe_yes = DD_Or(ddman, maybe_yes, yes[i]);\n    }\n    for (i = 0; i < num_combinations; i++) {\n      Cudd_Ref(combinations[i]);\n      maybe_yes = DD_Or(ddman, maybe_yes, combinations[i]);\n    }\n    Cudd_Ref(trans);\n    Cudd_Ref(maybe_yes);\n    a = DD_Apply(ddman, APPLY_TIMES, trans, maybe_yes);\n\n    // For efficiency, remove any probability 1 self-loops from the model.\n    // For multi-objective, we always do maximum reachability, so these do not matter.\n    Cudd_Ref(a);\n    loops = DD_And(ddman, DD_Equals(ddman, a, 1.0), DD_Identity(ddman, rvars, cvars, num_rvars));\n    loops = DD_ThereExists(ddman, loops, cvars, num_rvars);\n    Cudd_Ref(loops);\n    a = DD_ITE(ddman, loops, DD_Constant(ddman, 0), a);\n    \n    // Get number of states\n    n = odd->eoff + odd->toff;\n\n    // Build sparse matrix\n    PN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n    ndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n    // Get number of transitions/choices\n    nnz = ndsm->nnz;\n    nc = ndsm->nc;\n    kb = ndsm->mem;\n    kbt = kb;\n    // print out info\n    PN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n    // If needed, and if info is available, build a vector of action indices for the MDP\n    if (export_adv != EXPORT_ADV_NONE) {\n      if (trans_actions != NULL) {\n        PN_PrintToMainLog(env, \"Building action information... \");\n        // first need to filter out unwanted rows\n        Cudd_Ref(trans_actions);\n        Cudd_Ref(maybe_yes);\n        tmp = DD_Apply(ddman, APPLY_TIMES, trans_actions, maybe_yes);\n        Cudd_Ref(loops);\n        tmp = DD_ITE(ddman, loops, DD_Constant(ddman, 0), tmp);\n        // then convert to a vector of integer indices\n        build_nd_action_vector(ddman, a, tmp, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n        Cudd_RecursiveDeref(ddman, tmp);\n        kb = n*4.0/1024.0;\n        kbt += kb;\n        PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n        // also extract list of action names from 'synchs'\n        get_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n      } else {\n        PN_PrintWarningToMainLog(env, \"Action labels are not available for adversary generation.\");\n      }\n    }\n  \n    // Get vectors for yes/maybe\n    PN_PrintToMainLog(env, \"Creating vectors for yes \");\n    for(i=0; i<num_targets; i++) {\n      yes_vecs[i] = mtbdd_to_double_vector(ddman, yes[i], rvars, num_rvars, odd);\n    }\n    PN_PrintToMainLog(env, \"and combinations... \");\n    for(i=0; i<num_combinations; i++) {\n      combination_vecs[i] = mtbdd_to_double_vector(ddman, combinations[i], rvars, num_rvars, odd);\n    }\n    kb = n*sizeof(int)/1024.0;\n    kbt += num_targets * kb;\n    PN_PrintToMainLog(env, \"[%d x \", num_targets);\n    PN_PrintMemoryToMainLog(env, \"\", kb, \"]\\n\");\n    PN_PrintToMainLog(env, \"Creating vector for maybe... \");\n    maybe_vec = mtbdd_to_double_vector(ddman, maybe, rvars, num_rvars, odd);\n    kb = n*8.0/1024.0;\n    kbt += kb;\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n    // Get index of single (first) initial state\n    start_index = get_index_of_first_from_bdd(ddman, start, rvars, num_rvars, odd);\n    PN_PrintToMainLog(env, \"Initial state index: %1d\\n\", start_index);\n\n    // Print total memory usage\n    PN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n    // Store local copies of sparse matrix stuff\n    double *non_zeros = ndsm->non_zeros;\n    unsigned char *row_counts = ndsm->row_counts;\n    int *row_starts = (int *)ndsm->row_counts;\n    unsigned char *choice_counts = ndsm->choice_counts;\n    int *choice_starts = (int *)ndsm->choice_counts;\n    bool use_counts = ndsm->use_counts;\n    unsigned int *cols = ndsm->cols;\n\n    // Set up LP problem...\n    PN_PrintToMainLog(env, \"\\nBuilding LP problem...\\n\");\n    \n\n    int *yes_vec;\n    int *map_var;\n\n    yes_vec = new int[n];\n    map_var = new int[n+1];\n\n    arr_ints = new int[n];\n    int sp;\n\n    \n    // Compute the number of LP variables needed\n    // (one per choice for each 'maybe'/'yes' state + one extra for each yes state)\n    // Also build map_var (mapping from states to first corresponding LP var)\n    // Init counters (maybe_nc/yes_nc = num maybe/yes choices, yes_count = num yes, count = num vars so far)\n    int maybe_nc = 0;\n    int yes_nc = 0;\n    int yes_count = 0;\n    count = 0;\n    int yc = 0;\n    // Traverse sparse matrix to get info\n    h1 = h2 = 0;\n    for (i = 0; i < n; i++) {\n      if (!use_counts) {\n        l1 = row_starts[i];\n        h1 = row_starts[i+1];\n      } else {\n        l1 = h1;\n        h1 += row_counts[i];\n      }\n      k=0;\n      for (j = l1; j < h1; j++) {\n        if (!use_counts) {\n          l2 = choice_starts[j];\n          h2 = choice_starts[j+1];\n        } else {\n          l2 = h2;\n          h2 += choice_counts[j];\n        }\n        k++;\n      }\n      // Store first LP var for state i\n      map_var[i] = count;\n      // If a maybe state...\n      if (maybe_vec[i] > 0) {\n        maybe_nc += k;\n        count += k;\n      }\n      else {\n        yc = 0;\n        for (j=0; j<num_targets; j++) \n          // If a yes state...\n          if (yes_vecs[j][i] > 0) \n            yc++;\n        for (j=0; j<num_combinations; j++) \n          // If a yes state...\n          if (combination_vecs[j][i] > 0) \n            yc++;\n\n        yes_nc += k;\n        // each target state may have more than one extra action\n        yes_count += yc; \n        count += k+yc;\n        //printf(\"i=%d, yes_nc=%d, yes_count=%d, count=%d\\n\", i, yes_nc, yes_count, count);\n      }\n    }\n    // Compute total var count\n    num_lp_vars = maybe_nc + yes_nc + yes_count;\n    // Store first LP var for final state\n    map_var[n] = num_lp_vars; // maybe need to be modified.   \n    PN_PrintToMainLog(env, \"Number of LP variables = %1d\\n\", num_lp_vars);\n\n    for(i=0; i<n; i++)\n      yes_vec[i] = 0;\n    for(i=0; i<n; i++) {\n      for(j=0; j<num_targets; j++) {\n        if(yes_vecs[j][i]> 0) { // For each state, count the number of targets it belongs to.\n          yes_vec[i]++;\n        }\n      }\n      for(j=0; j<num_combinations; j++) {\n        if(combination_vecs[j][i]> 0) { // For each state, count the number of targets it belongs to.\n          yes_vec[i]++;\n        }\n      }\n    }\n\n    h1 = h2 = 0;\n    for(i=0; i<n; i++)\n      arr_ints[i] = map_var[i+1]-map_var[i];\n    for (i = 0; i < n; i++) {\n      if (!use_counts) {\n        l1 = row_starts[i];\n        h1 = row_starts[i+1];\n      } else {\n        l1 = h1;\n        h1 += row_counts[i];\n      }\n      for (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n        if (!use_counts) {\n          l2 = choice_starts[j];\n          h2 = choice_starts[j+1];\n        } else {\n          l2 = h2;\n          h2 += choice_counts[j];\n        }\n        if (maybe_vec[i]> 0 || yes_vec[i]> 0)\n          for(k=l2; k<h2; k++) {\n            if(maybe_vec[cols[k]]> 0 || yes_vec[cols[k]]> 0)\n              arr_ints[cols[k]]++;\n          }\n      }\n    }\n\n    int *constraints_sp;\n    int *constraints_ints;\n    double *constraints_reals;\n    int **constraints_int_ptr;\n    double **constraints_real_ptr;\n    constraints_sp = new int[n];\n    constraints_int_ptr = new int*[n];\n    constraints_real_ptr = new double*[n];\n    for(i=0; i<n; i++)\n      if(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n        //printf(\"i = %1d, \", i);\n        constraints_ints = new int[arr_ints[i]];\n        constraints_reals = new REAL[arr_ints[i]];\n        constraints_sp[i] = map_var[i+1]-map_var[i];\n        constraints_int_ptr[i] = constraints_ints;\n        constraints_real_ptr[i] = constraints_reals;\n        for(j=0; j<map_var[i+1]-map_var[i]; j++) {\n          constraints_ints[j] = map_var[i] + j + 1; // index starts at 1 in lp_solve\n          constraints_reals[j] = 1.0;\n        }\n        for(j=map_var[i+1]-map_var[i]; j<arr_ints[i]; j++) {\n          constraints_ints[j] = -1;\n          constraints_reals[j] = 0;\n        }\n      }\n\n    arr_reals = new REAL[num_lp_vars];\n\n    if ((lp=make_lp(0, num_lp_vars)) == NULL) throw \"Could not create LP problem\";\n    // Lower verbosity: Warnings and errors only\n    set_verbose(lp, IMPORTANT);\n    // Set mode: will create row by row\n    set_add_rowmode(lp, true);\n\n    // Add constraints to LP problem\n    int x;\n    h1 = h2 = 0;\n    for (x = 0; x < n; x++) { // h2: row index\n      if(maybe_vec[x]> 0 || yes_vec[x]> 0) {\n        if (!use_counts) {\n          l1 = row_starts[x];\n          h1 = row_starts[x+1];\n        } else {\n          l1 = h1;\n          h1 += row_counts[x];\n        }\n        count = 0;\n        for (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n          if (!use_counts) {\n            l2 = choice_starts[j];\n            h2 = choice_starts[j+1];\n          } else {\n            l2 = h2;\n            h2 += choice_counts[j];\n          }\n          for(k=l2; k<h2; k++) { // k: column index\n            // get the index of the corresponding variable\n            i = cols[k];\n            if(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n              constraints_ints = constraints_int_ptr[i];\n              constraints_reals = constraints_real_ptr[i];\n              for(k_r=0; k_r<constraints_sp[i]; k_r++)\n                if(constraints_ints[k_r]==map_var[x]+j-l1-count+1)\n                  break;\n\n              if(k_r == constraints_sp[i]) {\n                //count++;\n                constraints_ints[k_r]=map_var[x]+j-l1-count + 1; // index starts at 1 in lp_solve\n                constraints_reals[k_r] = -non_zeros[k];\n                constraints_sp[i]++;\n              } else {\n                constraints_reals[k_r] -= non_zeros[k];\n                if(constraints_reals[k_r] == 0.0) { // In fact, this cannot happen.\n                  //count--;\n                  for(l2_r=k_r; l2_r<constraints_sp[i]-1; l2_r++) {\n                    constraints_reals[l2_r] = constraints_reals[l2_r+1];\n                    constraints_ints[l2_r] = constraints_ints[l2_r+1];\n                  }\n                  constraints_sp[i]--;\n                }\n              }\n            }\n          }\n        }\n      } else if(use_counts) {\n        l1 = h1;\n        h1 += row_counts[x];\n        for (j = l1; j < h1; j++)\n          h2 += choice_counts[j];\n      }\n    }\n\n    for (i = 0; i < n; i++)\n      if (maybe_vec[i]> 0 || yes_vec[i]> 0) {\n        constraints_ints = constraints_int_ptr[i];\n        constraints_reals = constraints_real_ptr[i];\n        add_constraintex(lp, constraints_sp[i], constraints_reals, constraints_ints, EQ, (start_index==i ? 1.0 : 0.0));\n        delete[] constraints_ints;\n        delete[] constraints_reals;\n      }\n    delete[] constraints_sp;\n    delete[] constraints_int_ptr;\n    delete[] constraints_real_ptr;\n    \n    // Add LP constraints for bounded (non-quantitative) objectives\n    PN_PrintToMainLog(env, \"Adding extra constraints for bounded objectives...\\n\");\n    constraints_ints = new int[num_lp_vars];\n    int varsp, index;\n    for (i=0; i<num_targets; i++) {\n      // Skip quantitative constraint\n      if (relops[i]==0 || relops[i]>2)\n        continue;\n      // Build array for constraint (1 iff is an extra transition for the i_th target)\n      count = 0;\n      for(k=0; k<n; k++) {\n        varsp = 0;\n        for(j=0; j<num_targets; j++) {\n          if(yes_vecs[j][k]> 0) {\n            if(j == i) {\n              constraints_ints[count] = map_var[k+1]-yes_vec[k]+varsp + 1;\n              arr_reals[count] = 1.0;\n              count++;\n            }\n            varsp++;\n          }\n        }\n        for(j=0; j<num_combinations; j++) {\n          if(combination_vecs[j][k]> 0) {\n            index = 1;\n            index = index << i;\n            if((index & combinationIDs[j]) > 0) {\n              constraints_ints[count] = map_var[k+1]-yes_vec[k]+varsp + 1;\n              arr_reals[count] = 1.0;\n              count++;\n            }\n            varsp++;\n          }\n        }\n      }\n      add_constraintex(lp, count, arr_reals, constraints_ints, GE, bounds[i]);\n    }\n\n    // Set objective function for LP\n    PN_PrintToMainLog(env, \"Setting objective...\\n\");\n    x = 0;\n    if(relops[0]> 0 && relops[0]<=2) {\n      for(i=0; i<n; i++) {\n        for(j=0; j<yes_vec[i]; j++) {\n          constraints_ints[x] = map_var[i+1]-yes_vec[i]+j + 1;\n          arr_reals[x++] = 1.0;\n        }\n      }\n    } else if(relops[0] == 0) {\n      for(i=0; i<n; i++) {\n        varsp = 0;\n        if(yes_vecs[0][i]> 0) {\n          constraints_ints[x] = map_var[i+1] - yes_vec[i] + 1;\n          arr_reals[x++] = 1.0;\n          varsp++;\n        }\n        for(j=1; j<num_targets; j++) \n          if(yes_vecs[j][i]> 0)\n            varsp++;\n        for(j=0; j<num_combinations; j++) {\n          if(combination_vecs[j][i]> 0) {\n            if((combinationIDs[j] & 1) > 0) {\n              constraints_ints[x] = map_var[i+1] - yes_vec[i] + varsp + 1;\n              arr_reals[x++] = 1.0;\n            }\n            varsp++;\n          }\n        }\n      }\n    }\n    set_maxim(lp);\n    set_obj_fnex(lp, x, arr_reals, constraints_ints);\n    delete[] constraints_ints;\n    \n    // Finished building LP problem\n    set_add_rowmode(lp, false);\n    \n    // Get setup time\n    stop = util_cpu_time();\n    time_for_setup = (double)(stop - start2)/1000;\n    start2 = stop;\n    \n    // Export the MDP to a dot file\n    //export_model(ndsm, n, yes_vec, start_index);\n    \n    // Solve the LP, extract result\n    PN_PrintToMainLog(env, \"Solving LP problem...\\n\");\n    res = solve(lp);\n      \n    //Get LP solving time\n    stop2 = util_cpu_time();  \n    time_for_lp = (double)(stop2 - start2)/1000;  \n      \n    if (res != 0) {\n      PN_PrintToMainLog(env, \"No solution\\n\");\n      lp_solved = false;\n    } else {\n      lp_solved = true;\n      lp_result = get_objective(lp);\n      lp_soln = new double[num_lp_vars];\n      get_ptr_variables(lp, &lp_soln);\n\n      // Generate adversary from the solution, if required\n      if (export_adv != EXPORT_ADV_NONE) {\n\t\t// Adversary generation\n\t\texport_adversary_ltl_tra(export_adv_filename, ndsm, ndsm->actions, action_names, yes_vec, maybe_vec, num_lp_vars, map_var, lp_soln, start_index);\n\t\t//export_adversary_ltl_dot(env, ndsm, n, nnz, yes_vec, maybe_vec, num_lp_vars, map_var, lp_soln, start_index);\n      }\n      /*for (i=0; i<num_lp_vars; i++) {\n        if(lp_soln[i] != 0) {\n          PN_PrintToMainLog(env, \"X%d = %g    \", i, lp_soln[i]);\n          count++;\n        }\n        if(count == 8) {\n          PN_PrintToMainLog(env, \"\\n\");\n          count = 0;\n        }\n      }\n      if(count)\n\t\t\tPN_PrintToMainLog(env, \"\\n\");*/\n    }\n\n    // Modify result based on type\n    if (relops[0] > 0) {\n      // for qualitative queries, return 1/0 for existence of solution or not\n      PN_PrintToMainLog(env, \"LP problem solution %sfound so result is %s\\n\",  lp_solved ? \"\" : \"not \", lp_solved ? \"true\" : \"false\");\n      lp_result = lp_solved ? 1.0 : 0.0;\n    } else {\n      // return NaN for quantitative queries that can't be solved\n      PN_PrintToMainLog(env, \"LP problem solution %sfound; result is %f\\n\",  lp_solved ? \"\" : \"not \", lp_result);\n      if (!lp_solved) lp_result = NAN;\n    }\n  \n    // Print timing info\n    time_taken = time_for_setup + time_for_lp;\n    PN_PrintToMainLog(env, \"\\nLP problem solved in %.2f seconds (setup %.2f, lpsolve %.2f)\\n\", time_taken, time_for_setup, time_for_lp);\n\n    delete yes_vec;\n    delete map_var;\n    \n    // Catch exceptions: register error\n  } catch (std::bad_alloc e) {\n    PN_SetErrorMessage(\"Out of memory\");\n    lp_result = NAN;\n  }\n\n  // Free memory\n  if (lp) delete_lp(lp);\n  if (a) Cudd_RecursiveDeref(ddman, a);\n  if (maybe_yes) Cudd_RecursiveDeref(ddman, maybe_yes);\n  if (loops) Cudd_RecursiveDeref(ddman, loops);\n  if (ndsm) delete ndsm;\n  if (ndsm_r) delete ndsm_r;\n  delete[] maybe_vec;\n  for (i = 0; i < num_targets; i++)\n    delete[] yes_vecs[i];\n  delete[] arr_reals;\n  delete[] arr_ints;\n  if (target_ptrs) env->ReleaseLongArrayElements(_targets, target_ptrs, 0);\n  if (relops) env->ReleaseIntArrayElements(_relops, relops, 0);\n  if (bounds) env->ReleaseDoubleArrayElements(_bounds, bounds, 0);\n  if (action_names != NULL) {\n    release_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n  }\n\n  return lp_result;\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetMultiReachReward.cc",
    "content": "//==============================================================================\n//  \n//  Copyright (c) 2002-\n//  Authors:\n//  * Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//  * Hongyang Qu <hongyang.qu@comlab.ox.ac.uk> (University of Oxford)\n//  \n//------------------------------------------------------------------------------\n//  \n//  This file is part of PRISM.\n//  \n//  PRISM is free software; you can redistribute it and/or modify\n//  it under the terms of the GNU General Public License as published by\n//  the Free Software Foundation; either version 2 of the License, or\n//  (at your option) any later version.\n//  \n//  PRISM is distributed in the hope that it will be useful,\n//  but WITHOUT ANY WARRANTY; without even the implied warranty of\n//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//  GNU General Public License for more details.\n//  \n//  You should have received a copy of the GNU General Public License\n//  along with PRISM; if not, write to the Free Software Foundation,\n//  Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//  \n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"sparse_adv.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n#include \"lp_lib.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReachReward\n(\n JNIEnv *env,\n jclass cls,\n jlong __jlongpointer t, // trans matrix\n jlong __jlongpointer ta, // trans action labels\n jobject synchs,\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv, // nondet vars\n jint num_ndvars,\n jlongArray _targets, // target state sets\n jintArray _relopsProb, // target relops (0:=?, 1:>, 2:>=)\n jdoubleArray _boundsProb, // target probability bounds\n jintArray _relopsReward, // target relops (0:=?, 1:>, 2:>=)\n jdoubleArray _boundsReward, // target probability bounds\n jlong __jlongpointer m, // 'maybe' states\n jlong __jlongpointer _start, // initial state(s)\n //jlong __jlongpointer m_r, // 'maybe' states for the reward formula\n jlongArray _trrs, // transition rewards\n jlong _becs // bottom end components in no states\n // Reward paramters for more complicated cases\n //jlongArray _rewards, // sets of rewards for reward formulas\n //jlongArray _targets_r, // target state sets for reward formulas\n //jdoubleArray _bounds_r,  // target probability bounds for reward formulas\n )\n{\n  // cast function parameters\n  DdNode *trans = jlong_to_DdNode(t); // trans matrix\n  DdNode *trans_actions = jlong_to_DdNode(ta);  // trans action labels\n  ODDNode *odd = jlong_to_ODDNode(od); // reachable states\n  DdNode **rvars = jlong_to_DdNode_array(rv); // row vars\n  DdNode **cvars = jlong_to_DdNode_array(cv); // col vars\n  DdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n  DdNode *maybe = jlong_to_DdNode(m); // 'maybe' states\n  DdNode *start = jlong_to_DdNode(_start); // initial state(s)\n  DdNode *bottomec = jlong_to_DdNode(_becs); // bottom end compoment states\n\n  // target info  \n  jlong *target_ptrs = NULL;\n  DdNode **targets = NULL;\n  jint *relops = NULL;\n  double *bounds = NULL;\n  // mtbdds\n  DdNode *a = NULL, **yes = NULL, *maybe_yes = NULL, *loops = NULL, *tmp = NULL;\n  // model stats\n  int num_targets, n, nc, nc_r;\n  long nnz, nnz_r;\n  // sparse matrix\n  NDSparseMatrix *ndsm = NULL, *ndsm_r = NULL;\n  // action info\n  jstring *action_names_jstrings;\n  const char** action_names = NULL;\n  int num_actions;\n  // vectors\n  double **yes_vecs, *maybe_vec = NULL, *bottomec_vec = NULL/*, *maybe_vec_r = NULL*/;\n  // timing stuff\n  long start1, start2, start3, stop, stop2;\n  double time_taken, time_for_setup, time_for_lp;\n  // lp stuff\n  lprec *lp = NULL;\n  REAL *arr_reals = NULL;// *lp_soln = NULL;\n  REAL *back_arr_reals = NULL;\n  int *arr_ints = NULL;\n  bool selfloop;\n  int arr_size, res;\n  int num_lp_vars;\n  double *lp_soln;\n  double lp_result = 0.0;\n  bool lp_solved = false;\n  // misc\n  int i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, start_index, count;\n  double d1, d2, kb, kbt;\n  bool done, first;\n  jclass vn_cls;\n  jmethodID vn_mid;\n\n  // Reward info\n  jlong *reward_ptrs = NULL;\n  DdNode **rewards = NULL;\n  jint *relopsReward = NULL;\n  double *boundsReward = NULL;\n  int num_rewards;\n\n  // exception handling around whole function\n  try {\n\n    // start clocks \n    start1 = start2 = util_cpu_time();\n    \n    // Extract arrays of target info from function parameters\n    num_targets = (int)env->GetArrayLength(_targets);\n    target_ptrs = env->GetLongArrayElements(_targets, 0);\n    targets = new DdNode*[num_targets];\n    for (i = 0; i < num_targets; i++) targets[i] = jlong_to_DdNode(target_ptrs[i]);\n    relops = env->GetIntArrayElements(_relopsProb, 0);\n    bounds = env->GetDoubleArrayElements(_boundsProb, 0);\n    yes = new DdNode*[num_targets];\n    yes_vecs = new double*[num_targets];\n    for(i=0; i<num_targets; i++) yes[i] = targets[i];\n\n    // Extract arrays for rewards\n    num_rewards = (int)env->GetArrayLength(_trrs);\n    reward_ptrs = env->GetLongArrayElements(_trrs, 0);\n    rewards = new DdNode*[num_rewards];\n    for (i = 0; i < num_rewards; i++) rewards[i] = jlong_to_DdNode(reward_ptrs[i]);\n    relopsReward = env->GetIntArrayElements(_relopsReward, 0);\n    boundsReward = env->GetDoubleArrayElements(_boundsReward, 0);\n  \n    // Display some info about the targets\n    PN_PrintToMainLog(env, \"\\n%d Targets:\\n\", num_targets);\n    for (i = 0; i < num_targets; i++) {\n      PN_PrintToMainLog(env, \"#%d: \", i);\n      switch (relops[i]) {\n      case 0: PN_PrintToMainLog(env, \"Pmax=?\"); break;\n      case 1: PN_PrintToMainLog(env, \"P>%g\", bounds[i]); break;\n      case 2: PN_PrintToMainLog(env, \"P>=%g\", bounds[i]); break;\n      }\n      PN_PrintToMainLog(env, \" (%.0f states)\\n\", DD_GetNumMinterms(ddman, targets[i], num_rvars));\n    }\n\n    // Display some info about the rewards\n    PN_PrintToMainLog(env, \"\\n%d Rewards:\\n\", num_rewards);\n    bool disable_selfloop = true;\n    for (i = 0; i < num_rewards; i++) {\n      PN_PrintToMainLog(env, \"#%d: \", i);\n      switch (relopsReward[i]) {\n      case 3: PN_PrintToMainLog(env, \"Rmax=?\\n\"); disable_selfloop = false; break;\n      case 8: PN_PrintToMainLog(env, \"Rmin=?\\n\"); break;\n      case 4: PN_PrintToMainLog(env, \"R>=%g\\n\", boundsReward[i]); disable_selfloop = false; break;\n      case 9: PN_PrintToMainLog(env, \"R<=%g\\n\", boundsReward[i]); break;\n      }\n    }\n  \n    // Filter out rows, store in \"a\"\n    Cudd_Ref(maybe);\n    maybe_yes = maybe;\n    for (i = 0; i < num_targets; i++) {\n      Cudd_Ref(yes[i]);\n      maybe_yes = DD_Or(ddman, maybe_yes, yes[i]);\n    }\n    Cudd_Ref(trans);\n    Cudd_Ref(maybe_yes);\n    a = DD_Apply(ddman, APPLY_TIMES, trans, maybe_yes);\n\n    // For efficiency, remove any probability 1 self-loops from the model.\n    // For multi-objective, we always do maximum reachability, so these do not matter.\n    if (!disable_selfloop) {\n\t    Cudd_Ref(a);\n\t    loops = DD_And(ddman, DD_Equals(ddman, a, 1.0), DD_Identity(ddman, rvars, cvars, num_rvars));\n\t    loops = DD_ThereExists(ddman, loops, cvars, num_rvars);\n\t    Cudd_Ref(loops);\n\t    a = DD_ITE(ddman, loops, DD_Constant(ddman, 0), a);\n    }\n    \n    // Get number of states\n    n = odd->eoff + odd->toff;\n\n    // Build sparse matrix\n    PN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n    ndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n    // Get number of transitions/choices\n    nnz = ndsm->nnz;\n    nc = ndsm->nc;\n    kb = ndsm->mem;\n    kbt = kb;\n    // print out info\n    PN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n    // If needed, and if info is available, build a vector of action indices for the MDP\n    if (export_adv != EXPORT_ADV_NONE) {\n      if (trans_actions != NULL) {\n        PN_PrintToMainLog(env, \"Building action information... \");\n        // first need to filter out unwanted rows\n        Cudd_Ref(trans_actions);\n        Cudd_Ref(maybe_yes);\n        tmp = DD_Apply(ddman, APPLY_TIMES, trans_actions, maybe_yes);\n        if (!disable_selfloop) {\n            Cudd_Ref(loops);\n            tmp = DD_ITE(ddman, loops, DD_Constant(ddman, 0), tmp);\n        }\n        // then convert to a vector of integer indices\n        build_nd_action_vector(ddman, a, tmp, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n        Cudd_RecursiveDeref(ddman, tmp);\n        kb = n*4.0/1024.0;\n        kbt += kb;\n        PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n        // also extract list of action names from 'synchs'\n        get_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n      } else {\n        PN_PrintWarningToMainLog(env, \"Action labels are not available for adversary generation.\");\n      }\n    }\n  \n    // Get vectors for yes/maybe\n    PN_PrintToMainLog(env, \"Creating vectors for yes... \");\n    for(i=0; i<num_targets; i++) {\n      yes_vecs[i] = mtbdd_to_double_vector(ddman, yes[i], rvars, num_rvars, odd);\n    }\n    kb = n*sizeof(int)/1024.0;\n    kbt += num_targets * kb;\n    PN_PrintToMainLog(env, \"[%d x \", num_targets);\n    PN_PrintMemoryToMainLog(env, \"\", kb, \"]\\n\");\n    PN_PrintToMainLog(env, \"Creating vector for maybe... \");\n    maybe_vec = mtbdd_to_double_vector(ddman, maybe, rvars, num_rvars, odd);\n    kb = n*8.0/1024.0;\n    kbt += kb;\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n    PN_PrintToMainLog(env, \"Creating vector for bottom end components... \");\n    bottomec_vec = mtbdd_to_double_vector(ddman, bottomec, rvars, num_rvars, odd);\n    kb = n*8.0/1024.0;\n    kbt += kb;\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n    // Get index of single (first) initial state\n    start_index = get_index_of_first_from_bdd(ddman, start, rvars, num_rvars, odd);\n    PN_PrintToMainLog(env, \"Initial state index: %1d\\n\", start_index);\n\n    // Print total memory usage\n    PN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n    // Store local copies of sparse matrix stuff\n    double *non_zeros = ndsm->non_zeros;\n    unsigned char *row_counts = ndsm->row_counts;\n    int *row_starts = (int *)ndsm->row_counts;\n    unsigned char *choice_counts = ndsm->choice_counts;\n    int *choice_starts = (int *)ndsm->choice_counts;\n    bool use_counts = ndsm->use_counts;\n    unsigned int *cols = ndsm->cols;\n\n    // Set up LP problem...\n    PN_PrintToMainLog(env, \"\\nBuilding LP problem...\\n\");\n    \n    int *yes_vec;\n    int *map_var;\n\n    yes_vec = new int[n];\n    map_var = new int[n+1];\n\n    arr_ints = new int[n];\n    int sp;\n\n    \n    // Compute the number of LP variables needed\n    // (one per choice for each 'maybe'/'yes' state + one extra for each yes state)\n    // Also build map_var (mapping from states to first corresponding LP var)\n    // Init counters (maybe_nc/yes_nc = num maybe/yes choices, yes_count = num yes, count = num vars so far)\n    int maybe_nc = 0;\n    int yes_nc = 0;\n    int yes_count = 0;\n    int bottomec_nc = 0;\n    count = 0;\n    // Traverse sparse matrix to get info\n    h1 = h2 = 0;\n    for (i = 0; i < n; i++) {\n      if (!use_counts) {\n        l1 = row_starts[i];\n        h1 = row_starts[i+1];\n      } else {\n        l1 = h1;\n        h1 += row_counts[i];\n      }\n      k=0;\n      for (j = l1; j < h1; j++) {\n        if (!use_counts) {\n          l2 = choice_starts[j];\n          h2 = choice_starts[j+1];\n        } else {\n          l2 = h2;\n          h2 += choice_counts[j];\n        }\n        k++;\n      }\n      // Store first LP var for state i\n      map_var[i] = count;\n      if(bottomec_vec[i] > 0) {\n        // each state in a bottom end component has an extra action\n        bottomec_nc += k+1;\n        count += k+1;\n      } else if (maybe_vec[i] > 0) {\n        // If a maybe state...\n        maybe_nc += k;\n        count += k;\n      } else {\n        for (j=0; j<num_targets; j++) {\n          // If a yes state...\n          if (yes_vecs[j][i] > 0) {\n            yes_nc += k;\n            yes_count ++; // each target state has one extra action\n            count += k+1;\n            // Skip any further targets for this state\n            break;\n          }\n        }\n      }\n    }\n    // Compute total var count\n    num_lp_vars = maybe_nc + yes_nc + yes_count + bottomec_nc;\n    // Store first LP var for final state\n    map_var[n] = num_lp_vars; // maybe need to be modified.   \n    PN_PrintToMainLog(env, \"Number of LP variables = %1d\\n\", num_lp_vars);\n\n    for(i=0; i<n; i++)\n      yes_vec[i] = 0;\n    for(i=0; i<n; i++) {\n      for(j=0; j<num_targets; j++) {\n        if(yes_vecs[j][i]> 0) { // For each state, count the number of targets it belongs to.\n          yes_vec[i]++;\n        }\n      }\n    }\n\n    h1 = h2 = 0;\n    for(i=0; i<n; i++)\n      arr_ints[i] = map_var[i+1]-map_var[i];\n    for (i = 0; i < n; i++) {\n      if (!use_counts) {\n        l1 = row_starts[i];\n        h1 = row_starts[i+1];\n      } else {\n        l1 = h1;\n        h1 += row_counts[i];\n      }\n      for (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n        if (!use_counts) {\n          l2 = choice_starts[j];\n          h2 = choice_starts[j+1];\n        } else {\n          l2 = h2;\n          h2 += choice_counts[j];\n        }\n        if (maybe_vec[i]> 0 || yes_vec[i]> 0)\n          for(k=l2; k<h2; k++) {\n            //if(maybe_vec[cols[k]]> 0 || yes_vec[cols[k]]> 0)\n            arr_ints[cols[k]]++;\n          }\n      }\n    }\n    int *constraints_sp;\n    int *constraints_ints;\n    double *constraints_reals;\n    int **constraints_int_ptr;\n    double **constraints_real_ptr;\n    constraints_sp = new int[n];\n    constraints_int_ptr = new int*[n];\n    constraints_real_ptr = new double*[n];\n    for(i=0; i<n; i++)\n      if(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n        constraints_ints = new int[arr_ints[i]];\n        constraints_reals = new REAL[arr_ints[i]];\n        constraints_sp[i] = map_var[i+1]-map_var[i];\n        constraints_int_ptr[i] = constraints_ints;\n        constraints_real_ptr[i] = constraints_reals;\n        for(j=0; j<map_var[i+1]-map_var[i]; j++) {\n          constraints_ints[j] = map_var[i] + j + 1;\n          constraints_reals[j] = 1.0;\n        }\n        for(j=map_var[i+1]-map_var[i]; j<arr_ints[i]; j++) {\n          constraints_ints[j] = -1;\n          constraints_reals[j] = 0;\n        }\n      }\n\n    arr_reals = new REAL[num_lp_vars];\n\n    if ((lp=make_lp(0, num_lp_vars)) == NULL) throw \"Could not create LP problem\";\n    // Lower verbosity: Warnings and errors only\n    set_verbose(lp, IMPORTANT);\n    // Set mode: will create row by row\n    set_add_rowmode(lp, true);\n\n\n    // Add constraints to LP problem\n    int x;\n    h1 = h2 = 0;\n    for (x = 0; x < n; x++) { // h2: row index\n      if(maybe_vec[x]> 0 || yes_vec[x]> 0) {\n        if (!use_counts) {\n          l1 = row_starts[x];\n          h1 = row_starts[x+1];\n        } else {\n          l1 = h1;\n          h1 += row_counts[x];\n        }\n        count = 0;\n        for (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n          if (!use_counts) {\n            l2 = choice_starts[j];\n            h2 = choice_starts[j+1];\n          } else {\n            l2 = h2;\n            h2 += choice_counts[j];\n          }\n          for(k=l2; k<h2; k++) { // k: column index\n            // get the index of the corresponding variable\n            i = cols[k];\n            if(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n              constraints_ints = constraints_int_ptr[i];\n              constraints_reals = constraints_real_ptr[i];\n              for(k_r=0; k_r<constraints_sp[i]; k_r++)\n                if(constraints_ints[k_r]==map_var[x]+j-l1-count + 1)\n                  break;\n\n              if(k_r == constraints_sp[i]) {\n                //count++;\n                constraints_ints[k_r]=map_var[x]+j-l1-count + 1;\n                constraints_reals[k_r] = -non_zeros[k];\n                constraints_sp[i]++;\n              } else {\n                constraints_reals[k_r] -= non_zeros[k];\n                if(constraints_reals[k_r] == 0.0) { // In fact, this cannot happen.\n                  //count--;\n                  for(l2_r=k_r; l2_r<constraints_sp[i]-1; l2_r++) {\n                    constraints_reals[l2_r] = constraints_reals[l2_r+1];\n                    constraints_ints[l2_r] = constraints_ints[l2_r+1];\n                  }\n                  constraints_sp[i]--;\n                }\n              }\n            }\n          }\n        }\n      } else if(use_counts) {\n        l1 = h1;\n        h1 += row_counts[x];\n        for (j = l1; j < h1; j++)\n          h2 += choice_counts[j];\n      }\n    }\n    \n    for (i = 0; i < n; i++)\n      if (maybe_vec[i]> 0 || yes_vec[i]> 0) {\n        constraints_ints = constraints_int_ptr[i];\n        constraints_reals = constraints_real_ptr[i];\n        add_constraintex(lp, constraints_sp[i], constraints_reals, constraints_ints, EQ, (start_index==i ? 1.0 : 0.0));\n        delete[] constraints_ints;\n        delete[] constraints_reals;\n      }\n    delete[] constraints_sp;\n    delete[] constraints_int_ptr;\n    delete[] constraints_real_ptr;\n    \n    // Add LP constraints for bounded (non-quantitative) objectives\n    PN_PrintToMainLog(env, \"Adding extra constraints for bounded objectives...\\n\");\n    constraints_ints = new int[num_lp_vars];\n    for (i=0; i<num_targets; i++) {\n      // Skip quantitative constraint\n      if (relops[i]==0 || relops[i]>2)\n        continue;\n      count = 0;\n      for(k=0; k<n; k++) {\n        if(yes_vecs[i][k]> 0) {\n          constraints_ints[count] = map_var[k+1];\n          arr_reals[count] = 1.0;\n          count++;\n        }\n      }\n      add_constraintex(lp, count, arr_reals, constraints_ints, GE, bounds[i]);\n    }\n      \n    /*****************************************************************\n     * Reward\n     *****************************************************************/\n    PN_PrintToMainLog(env, \"computing max function for rewards ...\\n\");\n    double *non_zeros_r;\n    unsigned char *choice_counts_r;\n    int *choice_starts_r;\n    bool use_counts_r;\n    unsigned int *cols_r;\n    bool isMax;\n    DdNode *trans_rewards;\n\n    for (int ii=num_rewards-1; ii>=0; ii--) {\n      isMax = true;\n      ndsm_r = build_sub_nd_sparse_matrix(ddman, a, rewards[ii], rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n      nnz_r = ndsm_r->nnz;\n      nc_r = ndsm_r->nc;\n      non_zeros_r = ndsm_r->non_zeros;\n      choice_counts_r = ndsm_r->choice_counts;\n      choice_starts_r = (int *)ndsm_r->choice_counts;\n      use_counts_r = ndsm_r->use_counts;\n      cols_r = ndsm_r->cols;\n      \n      h1 = h2 = l2_r = h2_r = x = 0;\n      for(i=0; i<n; i++) \n        if(maybe_vec[i] > 0 || yes_vec[i]> 0) {\n          if (!use_counts) { // assume we always do not use counts\n            l1 = row_starts[i]; \n            h1 = row_starts[i+1]; \n          } else { // Problematic\n            l1 = h1; \n            h1 += row_counts[i]; \n          }\n          for (j = l1; j < h1; j++) {// \\Sigma_{v\\in V/F} y_{(v, \\gamma)}*c_{(v, \\gamma)}\n            if (!use_counts) { \n              l2 = choice_starts[j]; \n              h2 = choice_starts[j+1]; \n            } else { \n              l2 = h2; \n              h2 += choice_counts[j]; \n            }\n            if (!use_counts_r) { \n              l2_r = choice_starts_r[j]; \n              h2_r = choice_starts_r[j+1]; \n            } else { \n              l2_r = h2_r; \n              h2_r += choice_counts_r[j]; \n            }\n            k_r = l2_r; \n            while (k_r < h2_r && cols_r[k_r] != cols[l2]) \n              k_r++;\n            // if there is one, add reward * prob to reward value\n            if (k_r < h2_r) {\n              constraints_ints[x] = map_var[i]+j-l1 + 1;\n              arr_reals[x++] = non_zeros_r[k_r]; \n            }\n          }\n        } else if(use_counts) { // count the number of choices for non maybe nodes. Is it necessary?\n          l1 = h1;\n          h1 += row_counts[i];\n          for (j = l1; j < h1; j++) {\n            h2 += choice_counts[j];\n            h2_r += choice_counts_r[j];\n          }\n        }\n\n      if (export_adv != EXPORT_ADV_NONE) {\n        back_arr_reals = new REAL[num_lp_vars];\n        memcpy (back_arr_reals, arr_reals, sizeof(REAL)*num_lp_vars);\n      }\n\n      // Skip quantitative constraint\n      if (relopsReward[ii]==3 || relopsReward[ii]==8)\n        break;\n      else if(relopsReward[ii]==9)\n        isMax = false;\n      if(isMax)\n        add_constraintex(lp, x, arr_reals, constraints_ints, GE, boundsReward[ii]);\n      else\n        add_constraintex(lp, x, arr_reals, constraints_ints, LE, boundsReward[ii]);\n    }\n\n    // Set objective function for LP\n    PN_PrintToMainLog(env, \"Setting objective...\\n\");\n    isMax = true;\n    if(num_targets > 0 && relops[0] == 0) {\n      x = 0;\n      for(i=0; i<n; i++)\n        if(yes_vecs[0][i]> 0) {\n          constraints_ints[x] = map_var[i+1];\n          arr_reals[x++] = 1.0;\n        }\n    } else if(relopsReward[0] == 3) { // Rmax     \n    } else if(relopsReward[0] == 8) { // Rmin\n      isMax = false;\n    } else if(relops[0]==2) {\n      x = 0;\n      for(i=0; i<n; i++) {\n        if(yes_vec[i]> 0) {\n          constraints_ints[x] = map_var[i+1];\n          arr_reals[x++] = 1.0;\n        }\n      }\n    } \n    if(isMax)\n      set_maxim(lp);\n    else\n      set_minim(lp);\n    set_obj_fnex(lp, x, arr_reals, constraints_ints);\n    delete[] constraints_ints;\n    \n    // Finished building LP problem\n    set_add_rowmode(lp, false);\n    \n    // Get setup time\n    stop = util_cpu_time();\n    time_for_setup = (double)(stop - start2)/1000;\n    start2 = stop;\n    \n    // Export the MDP to a dot file\n    //export_model(ndsm, n, yes_vec, start_index);\n    \n    // Solve the LP, extract result\n    PN_PrintToMainLog(env, \"Solving LP problem...\\n\");\n    res = solve(lp);\n    \n    //Get LP solving time\n    stop2 = util_cpu_time();  \n    time_for_lp = (double)(stop2 - start2)/1000;  \n      \n    if (res != 0) {\n      PN_PrintToMainLog(env, \"No solution\\n\");\n      lp_solved = false;\n    } else {\n      lp_solved = true;\n      lp_result = get_objective(lp);\n      lp_soln = new double[num_lp_vars];\n      get_ptr_variables(lp, &lp_soln);\n      \n      // Generate adversary from the solution, if required\n\t  if (export_adv != EXPORT_ADV_NONE) {\n          // Adversary generation\n\t\t\texport_adversary_ltl_tra(export_adv_filename, ndsm, ndsm->actions, action_names, yes_vec, maybe_vec, num_lp_vars, map_var, lp_soln, start_index);\n\t\t\t//export_adversary_ltl_dot(env, ndsm, n, nnz, yes_vec, maybe_vec, num_lp_vars, map_var, lp_soln, start_index);\n      }\n      \n      /*for (i=0; i<num_lp_vars; i++) {\n        if(lp_soln[i] != 0) {\n          PN_PrintToMainLog(env, \"X%d = %g    \", i, lp_soln[i]);\n          count++;\n        }\n        if(count == 8) {\n          PN_PrintToMainLog(env, \"\\n\");\n          count = 0;\n        }\n      }\n      if(count)\n\t\t\tPN_PrintToMainLog(env, \"\\n\");*/\n    }\n\n    // Modify result based on type\n    if (relops[0] != 0 && relopsReward[0] != 3 && relopsReward[0] != 8) {\n      // for qualitative queries, return 1/0 for existence of solution or not\n      PN_PrintToMainLog(env, \"LP problem solution %sfound so result is %s\\n\",  lp_solved ? \"\" : \"not \", lp_solved ? \"true\" : \"false\");\n      lp_result = lp_solved ? 1.0 : 0.0;\n    } else {\n      // return NaN for quantitative queries that can't be solved\n      PN_PrintToMainLog(env, \"LP problem solution %sfound; result is %f\\n\",  lp_solved ? \"\" : \"not \", lp_result);\n      if (!lp_solved) lp_result = NAN;\n    }\n  \n    // Print timing info\n    time_taken = time_for_setup + time_for_lp;\n    PN_PrintToMainLog(env, \"\\nLP problem solved in %.2f seconds (setup %.2f, lpsolve %.2f)\\n\", time_taken, time_for_setup, time_for_lp);\n\n    delete yes_vec;\n    delete map_var;\n    \n    // Catch exceptions: register error\n  } catch (std::bad_alloc e) {\n    PN_SetErrorMessage(\"Out of memory\");\n    lp_result = NAN;\n  }\n\n  // Free memory\n  if (lp) delete_lp(lp);\n  if (a) Cudd_RecursiveDeref(ddman, a);\n  if (maybe_yes) Cudd_RecursiveDeref(ddman, maybe_yes);\n  if (loops) Cudd_RecursiveDeref(ddman, loops);\n  if (ndsm) delete ndsm;\n  if (ndsm_r) delete ndsm_r;\n  delete[] maybe_vec;\n  for (i = 0; i < num_targets; i++)\n    delete[] yes_vecs[i];\n  delete[] arr_reals;\n  if(back_arr_reals)\n    delete[] back_arr_reals;\n  delete[] arr_ints;\n  if (target_ptrs) env->ReleaseLongArrayElements(_targets, target_ptrs, 0);\n  if (relops) env->ReleaseIntArrayElements(_relopsProb, relops, 0);\n  if (bounds) env->ReleaseDoubleArrayElements(_boundsProb, bounds, 0);\n  if (reward_ptrs) env->ReleaseLongArrayElements(_trrs, reward_ptrs, 0);\n  if (relopsReward) env->ReleaseIntArrayElements(_relopsReward, relopsReward, 0);\n  if (boundsReward) env->ReleaseDoubleArrayElements(_boundsReward, boundsReward, 0);\n  //if (rewards)\n  //  for(i = 0; i<num_rewards; i++)\n  //    Cudd_RecursiveDeref(ddman, rewards[i]);\n  if (action_names != NULL) {\n    release_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n  }\n\n  return lp_result;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetMultiReachReward1.cc",
    "content": "//==============================================================================\n//  \n//  Copyright (c) 2002-\n//  Authors:\n//  * Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//  * Hongyang Qu <hongyang.qu@comlab.ox.ac.uk> (University of Oxford)\n//  \n//------------------------------------------------------------------------------\n//  \n//  This file is part of PRISM.\n//  \n//  PRISM is free software; you can redistribute it and/or modify\n//  it under the terms of the GNU General Public License as published by\n//  the Free Software Foundation; either version 2 of the License, or\n//  (at your option) any later version.\n//  \n//  PRISM is distributed in the hope that it will be useful,\n//  but WITHOUT ANY WARRANTY; without even the implied warranty of\n//  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//  GNU General Public License for more details.\n//  \n//  You should have received a copy of the GNU General Public License\n//  along with PRISM; if not, write to the Free Software Foundation,\n//  Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//  \n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"sparse_adv.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n#include \"lp_lib.h\"\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jdouble __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetMultiReachReward1\n(\n JNIEnv *env,\n jclass cls,\n jlong __jlongpointer t, // trans matrix\n jlong __jlongpointer ta, // trans action labels\n jobject synchs,\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv, // nondet vars\n jint num_ndvars,\n jlongArray _targets, // target state sets\n jlongArray _combinations, // combinations of target state sets\n jintArray _combinationIDs, // combinations' ID\n jintArray _relopsProb, // target relops (0:=?, 1:>, 2:>=)\n jdoubleArray _boundsProb, // target probability bounds\n jintArray _relopsReward, // target relops (0:=?, 1:>, 2:>=)\n jdoubleArray _boundsReward, // target probability bounds\n jlong __jlongpointer m, // 'maybe' states\n jlong __jlongpointer _start, // initial state(s)\n //jlong __jlongpointer m_r, // 'maybe' states for the reward formula\n jlongArray _trrs, // transition rewards\n jlong _becs // bottom end components in no states\n // Reward paramters for more complicated cases\n //jlongArray _rewards, // sets of rewards for reward formulas\n //jlongArray _targets_r, // target state sets for reward formulas\n //jdoubleArray _bounds_r,  // target probability bounds for reward formulas\n )\n{\n  // cast function parameters\n  DdNode *trans = jlong_to_DdNode(t); // trans matrix\n  DdNode *trans_actions = jlong_to_DdNode(ta);  // trans action labels\n  ODDNode *odd = jlong_to_ODDNode(od); // reachable states\n  DdNode **rvars = jlong_to_DdNode_array(rv); // row vars\n  DdNode **cvars = jlong_to_DdNode_array(cv); // col vars\n  DdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n  DdNode *maybe = jlong_to_DdNode(m); // 'maybe' states\n  DdNode *start = jlong_to_DdNode(_start); // initial state(s)\n  DdNode *bottomec = jlong_to_DdNode(_becs); // bottom end compoment states\n\n  // target info  \n  jlong *target_ptrs = NULL;\n  DdNode **targets = NULL;\n  jlong *combination_ptrs = NULL;\n  DdNode **combinations = NULL;\n  jint *relops = NULL, *combinationIDs = NULL;\n  double *bounds = NULL;\n  // mtbdds\n  DdNode *a = NULL, **yes = NULL, *maybe_yes = NULL, *loops = NULL, *tmp = NULL;\n  // model stats\n  int num_targets, num_combinations, n, nc, nc_r;\n  long nnz, nnz_r;\n  // sparse matrix\n  NDSparseMatrix *ndsm = NULL, *ndsm_r = NULL;\n  // action info\n  jstring *action_names_jstrings;\n  const char** action_names = NULL;\n  int num_actions;\n  // vectors\n  double **yes_vecs, **combination_vecs, *maybe_vec = NULL, *bottomec_vec = NULL/*, *maybe_vec_r = NULL*/;\n  // timing stuff\n  long start1, start2, start3, stop, stop2;\n  double time_taken, time_for_setup, time_for_lp;\n  // lp stuff\n  lprec *lp = NULL;\n  REAL *arr_reals = NULL;// *lp_soln = NULL;\n  REAL *back_arr_reals = NULL;\n  int *arr_ints = NULL;\n  bool selfloop;\n  int arr_size, res;\n  int num_lp_vars;\n  double *lp_soln;\n  double lp_result = 0.0;\n  bool lp_solved = false;\n  // misc\n  int i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, start_index, count;\n  double d1, d2, kb, kbt;\n  bool done, first;\n  jclass vn_cls;\n  jmethodID vn_mid;\n\n  // Reward info\n  jlong *reward_ptrs = NULL;\n  DdNode **rewards = NULL;\n  jint *relopsReward = NULL;\n  double *boundsReward = NULL;\n  int num_rewards;\n\n  // exception handling around whole function\n  try {\n\n    // start clocks \n    start1 = start2 = util_cpu_time();\n    \n    // Extract arrays of target info from function parameters\n    num_targets = (int)env->GetArrayLength(_targets);\n    target_ptrs = env->GetLongArrayElements(_targets, 0);\n    targets = new DdNode*[num_targets];\n    for (i = 0; i < num_targets; i++) \n      targets[i] = jlong_to_DdNode(target_ptrs[i]);\n    relops = env->GetIntArrayElements(_relopsProb, 0);\n    bounds = env->GetDoubleArrayElements(_boundsProb, 0);\n\n    num_combinations = (int)env->GetArrayLength(_combinations);\n    combination_ptrs = env->GetLongArrayElements(_combinations, 0);\n    combinations = new DdNode*[num_combinations];\n    combination_vecs = new double*[num_combinations];\n    for (i = 0; i < num_combinations; i++) {\n      combinations[i] = jlong_to_DdNode(combination_ptrs[i]);\n    }\n    combinationIDs = env->GetIntArrayElements(_combinationIDs, 0);\n\n    yes = new DdNode*[num_targets];\n    yes_vecs = new double*[num_targets];\n    for(i=0; i<num_targets; i++) yes[i] = targets[i];\n\n    // Extract arrays for rewards\n    num_rewards = (int)env->GetArrayLength(_trrs);\n    reward_ptrs = env->GetLongArrayElements(_trrs, 0);\n    rewards = new DdNode*[num_rewards];\n    for (i = 0; i < num_rewards; i++) rewards[i] = jlong_to_DdNode(reward_ptrs[i]);\n    relopsReward = env->GetIntArrayElements(_relopsReward, 0);\n    boundsReward = env->GetDoubleArrayElements(_boundsReward, 0);\n  \n    // Display some info about the targets/combinations\n    PN_PrintToMainLog(env, \"\\n%d Targets:\\n\", num_targets);\n    for (i = 0; i < num_targets; i++) {\n      PN_PrintToMainLog(env, \"#%d: \", i);\n      switch (relops[i]) {\n      case 0: PN_PrintToMainLog(env, \"Pmax=?\"); break;\n      case 1: PN_PrintToMainLog(env, \"P>%g\", bounds[i]); break;\n      case 2: PN_PrintToMainLog(env, \"P>=%g\", bounds[i]); break;\n      }\n      PN_PrintToMainLog(env, \" (%.0f states)\\n\", DD_GetNumMinterms(ddman, targets[i], num_rvars));\n    }\n    PN_PrintToMainLog(env, \"%d Target combinations:\\n\", num_combinations);\n    for (i = 0; i < num_combinations; i++) {\n      PN_PrintToMainLog(env, \"#%d: \", i);\n      PN_PrintToMainLog(env, \"%d \", (int)combinationIDs[i]);\n      PN_PrintToMainLog(env, \" (%.0f states)\\n\", DD_GetNumMinterms(ddman, combinations[i], num_rvars));\n    }\n\n    // Display some info about the rewards\n    PN_PrintToMainLog(env, \"\\n%d Rewards:\\n\", num_rewards);\n    bool disable_selfloop = true;\n    for (i = 0; i < num_rewards; i++) {\n      PN_PrintToMainLog(env, \"#%d: \", i);\n      switch (relopsReward[i]) {\n      case 3: PN_PrintToMainLog(env, \"Rmax=?\\n\"); disable_selfloop = false; break;\n      case 8: PN_PrintToMainLog(env, \"Rmin=?\\n\"); break;\n      case 4: PN_PrintToMainLog(env, \"R>=%g\\n\", boundsReward[i]); disable_selfloop = false; break;\n      case 9: PN_PrintToMainLog(env, \"R<=%g\\n\", boundsReward[i]); break;\n      }\n    }\n  \n    // Filter out rows, store in \"a\"\n    Cudd_Ref(maybe);\n    maybe_yes = maybe;\n    for (i = 0; i < num_targets; i++) {\n      Cudd_Ref(yes[i]);\n      maybe_yes = DD_Or(ddman, maybe_yes, yes[i]);\n    }\n    for (i = 0; i < num_combinations; i++) {\n      Cudd_Ref(combinations[i]);\n      maybe_yes = DD_Or(ddman, maybe_yes, combinations[i]);\n    }\n    Cudd_Ref(trans);\n    Cudd_Ref(maybe_yes);\n    a = DD_Apply(ddman, APPLY_TIMES, trans, maybe_yes);\n\n    // For efficiency, remove any probability 1 self-loops from the model.\n    // For multi-objective, we always do maximum reachability, so these do not matter.\n    if(!disable_selfloop) {\n\t    Cudd_Ref(a);\n\t    loops = DD_And(ddman, DD_Equals(ddman, a, 1.0), DD_Identity(ddman, rvars, cvars, num_rvars));\n\t    loops = DD_ThereExists(ddman, loops, cvars, num_rvars);\n\t    Cudd_Ref(loops);\n\t    a = DD_ITE(ddman, loops, DD_Constant(ddman, 0), a);\n    }\n    \n    // Get number of states\n    n = odd->eoff + odd->toff;\n\n    // Build sparse matrix\n    PN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n    ndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n    // Get number of transitions/choices\n    nnz = ndsm->nnz;\n    nc = ndsm->nc;\n    kb = ndsm->mem;\n    kbt = kb;\n    // print out info\n    PN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n    // If needed, and if info is available, build a vector of action indices for the MDP\n    if (export_adv != EXPORT_ADV_NONE) {\n      if (trans_actions != NULL) {\n        PN_PrintToMainLog(env, \"Building action information... \");\n        // first need to filter out unwanted rows\n        Cudd_Ref(trans_actions);\n        Cudd_Ref(maybe_yes);\n        tmp = DD_Apply(ddman, APPLY_TIMES, trans_actions, maybe_yes);\n        Cudd_Ref(loops);\n        tmp = DD_ITE(ddman, loops, DD_Constant(ddman, 0), tmp);\n        // then convert to a vector of integer indices\n        build_nd_action_vector(ddman, a, tmp, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n        Cudd_RecursiveDeref(ddman, tmp);\n        kb = n*4.0/1024.0;\n        kbt += kb;\n        PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n        // also extract list of action names from 'synchs'\n        get_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n      } else {\n        PN_PrintWarningToMainLog(env, \"Action labels are not available for adversary generation.\");\n      }\n    }\n  \n    // Get vectors for yes/maybe\n    PN_PrintToMainLog(env, \"Creating vectors for yes \");\n    for(i=0; i<num_targets; i++) {\n      yes_vecs[i] = mtbdd_to_double_vector(ddman, yes[i], rvars, num_rvars, odd);\n    }\n    PN_PrintToMainLog(env, \"and combinations... \");\n    for(i=0; i<num_combinations; i++) {\n      combination_vecs[i] = mtbdd_to_double_vector(ddman, combinations[i], rvars, num_rvars, odd);\n    }\n    kb = n*sizeof(int)/1024.0;\n    kbt += num_targets * kb;\n    PN_PrintToMainLog(env, \"[%d x \", num_targets);\n    PN_PrintMemoryToMainLog(env, \"\", kb, \"]\\n\");\n    PN_PrintToMainLog(env, \"Creating vector for maybe... \");\n    maybe_vec = mtbdd_to_double_vector(ddman, maybe, rvars, num_rvars, odd);\n    kb = n*8.0/1024.0;\n    kbt += kb;\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n    PN_PrintToMainLog(env, \"Creating vector for bottom end components... \");\n    bottomec_vec = mtbdd_to_double_vector(ddman, bottomec, rvars, num_rvars, odd);\n    kb = n*8.0/1024.0;\n    kbt += kb;\n    PN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n    // Get index of single (first) initial state\n    start_index = get_index_of_first_from_bdd(ddman, start, rvars, num_rvars, odd);\n    PN_PrintToMainLog(env, \"Initial state index: %1d\\n\", start_index);\n\n    // Print total memory usage\n    PN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n    // Store local copies of sparse matrix stuff\n    double *non_zeros = ndsm->non_zeros;\n    unsigned char *row_counts = ndsm->row_counts;\n    int *row_starts = (int *)ndsm->row_counts;\n    unsigned char *choice_counts = ndsm->choice_counts;\n    int *choice_starts = (int *)ndsm->choice_counts;\n    bool use_counts = ndsm->use_counts;\n    unsigned int *cols = ndsm->cols;\n\n    // Set up LP problem...\n    PN_PrintToMainLog(env, \"\\nBuilding LP problem...\\n\");\n    \n    int *yes_vec;\n    int *map_var;\n\n    yes_vec = new int[n];\n    map_var = new int[n+1];\n\n    arr_ints = new int[n];\n    int sp;\n\n    \n    // Compute the number of LP variables needed\n    // (one per choice for each 'maybe'/'yes' state + one extra for each yes state)\n    // Also build map_var (mapping from states to first corresponding LP var)\n    // Init counters (maybe_nc/yes_nc = num maybe/yes choices, yes_count = num yes, count = num vars so far)\n    int maybe_nc = 0;\n    int yes_nc = 0;\n    int yes_count = 0;\n    int bottomec_nc = 0;\n    count = 0;\n    int yc = 0;\n    // Traverse sparse matrix to get info\n    h1 = h2 = 0;\n    for (i = 0; i < n; i++) {\n      if (!use_counts) {\n        l1 = row_starts[i];\n        h1 = row_starts[i+1];\n      } else {\n        l1 = h1;\n        h1 += row_counts[i];\n      }\n      k=0;\n      for (j = l1; j < h1; j++) {\n        if (!use_counts) {\n          l2 = choice_starts[j];\n          h2 = choice_starts[j+1];\n        } else {\n          l2 = h2;\n          h2 += choice_counts[j];\n        }\n        k++;\n      }\n      // Store first LP var for state i\n      map_var[i] = count;\n      if(bottomec_vec[i] > 0) {\n        // each state in a bottom end component has an extra action\n        bottomec_nc += k+1;\n        count += k+1;\n      } else if (maybe_vec[i] > 0) {\n        // If a maybe state...\n        maybe_nc += k;\n        count += k;\n      } else {\n        yc = 0;\n        for (j=0; j<num_targets; j++) \n          // If a yes state...\n          if (yes_vecs[j][i] > 0) \n            yc++;\n        for (j=0; j<num_combinations; j++) \n          // If a yes state...\n          if (combination_vecs[j][i] > 0) \n            yc++;\n\n        yes_nc += k;\n        // each target state may have more than one extra action\n        yes_count += yc; \n        count += k+yc;\n        //printf(\"i=%d, yes_nc=%d, yes_count=%d, count=%d\\n\", i, yes_nc, yes_count, count); \n      }\n    }\n    // Compute total var count\n    num_lp_vars = maybe_nc + yes_nc + yes_count + bottomec_nc;\n    // Store first LP var for final state\n    map_var[n] = num_lp_vars; // maybe need to be modified.   \n    PN_PrintToMainLog(env, \"Number of LP variables = %1d\\n\", num_lp_vars);\n\n    for(i=0; i<n; i++)\n      yes_vec[i] = 0;\n    for(i=0; i<n; i++) {\n      for(j=0; j<num_targets; j++) {\n        if(yes_vecs[j][i]> 0) { // For each state, count the number of targets it belongs to.\n          yes_vec[i]++;\n        }\n      }\n      for(j=0; j<num_combinations; j++) {\n        if(combination_vecs[j][i]> 0) { // For each state, count the number of targets it belongs to.\n          yes_vec[i]++;\n        }\n      }\n    }\n\n    h1 = h2 = 0;\n    for(i=0; i<n; i++)\n      arr_ints[i] = map_var[i+1]-map_var[i];\n    for (i = 0; i < n; i++) {\n      if (!use_counts) {\n        l1 = row_starts[i];\n        h1 = row_starts[i+1];\n      } else {\n        l1 = h1;\n        h1 += row_counts[i];\n      }\n      for (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n        if (!use_counts) {\n          l2 = choice_starts[j];\n          h2 = choice_starts[j+1];\n        } else {\n          l2 = h2;\n          h2 += choice_counts[j];\n        }\n        if (maybe_vec[i]> 0 || yes_vec[i]> 0)\n          for(k=l2; k<h2; k++) {\n            arr_ints[cols[k]]++;\n          }\n      }\n    }\n    int *constraints_sp;\n    int *constraints_ints;\n    double *constraints_reals;\n    int **constraints_int_ptr;\n    double **constraints_real_ptr;\n    constraints_sp = new int[n];\n    constraints_int_ptr = new int*[n];\n    constraints_real_ptr = new double*[n];\n    for(i=0; i<n; i++)\n      if(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n        constraints_ints = new int[arr_ints[i]];\n        constraints_reals = new REAL[arr_ints[i]];\n        constraints_sp[i] = map_var[i+1]-map_var[i];\n        constraints_int_ptr[i] = constraints_ints;\n        constraints_real_ptr[i] = constraints_reals;\n        for(j=0; j<map_var[i+1]-map_var[i]; j++) {\n          constraints_ints[j] = map_var[i] + j + 1;\n          constraints_reals[j] = 1.0;\n        }\n        for(j=map_var[i+1]-map_var[i]; j<arr_ints[i]; j++) {\n          constraints_ints[j] = -1;\n          constraints_reals[j] = 0;\n        }\n      }\n\n    arr_reals = new REAL[num_lp_vars];\n\n    if ((lp=make_lp(0, num_lp_vars)) == NULL) throw \"Could not create LP problem\";\n    // Lower verbosity: Warnings and errors only\n    set_verbose(lp, IMPORTANT);\n    // Set mode: will create row by row\n    set_add_rowmode(lp, true);\n\n    // Add constraints to LP problem\n    int x;\n    h1 = h2 = 0;\n    for (x = 0; x < n; x++) { // h2: row index\n      if(maybe_vec[x]> 0 || yes_vec[x]> 0) {\n        if (!use_counts) {\n          l1 = row_starts[x];\n          h1 = row_starts[x+1];\n        } else {\n          l1 = h1;\n          h1 += row_counts[x];\n        }\n        count = 0;\n        for (j = l1; j < h1; j++) { // j: choice index; x+j: variable index \n          if (!use_counts) {\n            l2 = choice_starts[j];\n            h2 = choice_starts[j+1];\n          } else {\n            l2 = h2;\n            h2 += choice_counts[j];\n          }\n          for(k=l2; k<h2; k++) { // k: column index\n            // get the index of the corresponding variable\n            i = cols[k];\n            if(maybe_vec[i]> 0 || yes_vec[i]> 0) {\n              constraints_ints = constraints_int_ptr[i];\n              constraints_reals = constraints_real_ptr[i];\n              for(k_r=0; k_r<constraints_sp[i]; k_r++)\n                if(constraints_ints[k_r]==map_var[x]+j-l1-count + 1)\n                  break;\n\n              if(k_r == constraints_sp[i]) {\n                //count++;\n                constraints_ints[k_r]=map_var[x]+j-l1-count + 1;\n                constraints_reals[k_r] = -non_zeros[k];\n                constraints_sp[i]++;\n              } else {\n                constraints_reals[k_r] -= non_zeros[k];\n                if(constraints_reals[k_r] == 0.0) { // In fact, this cannot happen.\n                  //count--;\n                  for(l2_r=k_r; l2_r<constraints_sp[i]-1; l2_r++) {\n                    constraints_reals[l2_r] = constraints_reals[l2_r+1];\n                    constraints_ints[l2_r] = constraints_ints[l2_r+1];\n                  }\n                  constraints_sp[i]--;\n                }\n              }\n            }\n          }\n        }\n      } else if(use_counts) {\n        l1 = h1;\n        h1 += row_counts[x];\n        for (j = l1; j < h1; j++)\n          h2 += choice_counts[j];\n      }\n    }\n    \n    for (i = 0; i < n; i++)\n      if (maybe_vec[i]> 0 || yes_vec[i]> 0) {\n        constraints_ints = constraints_int_ptr[i];\n        constraints_reals = constraints_real_ptr[i];\n        add_constraintex(lp, constraints_sp[i], constraints_reals, constraints_ints, EQ, (start_index==i ? 1.0 : 0.0));\n        delete[] constraints_ints;\n        delete[] constraints_reals;\n      }\n    delete[] constraints_sp;\n    delete[] constraints_int_ptr;\n    delete[] constraints_real_ptr;\n    \n    // Add LP constraints for bounded (non-quantitative) objectives\n    PN_PrintToMainLog(env, \"Adding extra constraints for bounded objectives...\\n\"); \n    constraints_ints = new int[num_lp_vars];\n    int varsp, index;\n    for (i=0; i<num_targets; i++) {\n      // Skip quantitative constraint\n      if (relops[i]==0 || relops[i]>2)\n        continue;\n      count = 0;\n      for(k=0; k<n; k++) {\n        varsp = 0;\n        for(j=0; j<num_targets; j++) {\n          if(yes_vecs[j][k]> 0) {\n            if(j == i) {\n              constraints_ints[count] = map_var[k+1]-yes_vec[k]+varsp + 1;\n              arr_reals[count] = 1.0;\n              count++;\n            }\n            varsp++;\n          }\n        }\n        for(j=0; j<num_combinations; j++) {\n          if(combination_vecs[j][k]> 0) {\n            index = 1;\n            index = index << i;\n            if((index & combinationIDs[j]) > 0) {\n              constraints_ints[count] = map_var[k+1]-yes_vec[k]+varsp + 1;\n              arr_reals[count] = 1.0;\n              count++;\n            }\n            varsp++;\n          }\n        }\n      }\n      add_constraintex(lp, count, arr_reals, constraints_ints, GE, bounds[i]);\n    }\n      \n    /*****************************************************************\n     * Reward\n     *****************************************************************/\n    PN_PrintToMainLog(env, \"computing max function for rewards ...\\n\");\n    double *non_zeros_r;\n    unsigned char *choice_counts_r;\n    int *choice_starts_r;\n    bool use_counts_r;\n    unsigned int *cols_r;\n    bool isMax;\n    DdNode *trans_rewards;\n\n    for (int ii=num_rewards-1; ii>=0; ii--) {\n      isMax = true;\n      // Build array for constraint (1 iff is an extra transition for the i_th target)\n      for(k=0; k<num_lp_vars; k++)\n        arr_reals[k] = 0.0;\n      //count = 0;\n\n      ndsm_r = build_sub_nd_sparse_matrix(ddman, a, rewards[ii], rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n      nnz_r = ndsm_r->nnz;\n      nc_r = ndsm_r->nc;\n      non_zeros_r = ndsm_r->non_zeros;\n      choice_counts_r = ndsm_r->choice_counts;\n      choice_starts_r = (int *)ndsm_r->choice_counts;\n      use_counts_r = ndsm_r->use_counts;\n      cols_r = ndsm_r->cols;\n      \n      h1 = h2 = l2_r = h2_r = x = 0;\n      for(i=0; i<n; i++) \n        if(maybe_vec[i] > 0 || yes_vec[i]> 0) {\n          if (!use_counts) { // assume we always do not use counts\n            l1 = row_starts[i]; \n            h1 = row_starts[i+1]; \n          } else { // Problematic\n            l1 = h1; \n            h1 += row_counts[i]; \n          }\n          for (j = l1; j < h1; j++) {// \\Sigma_{v\\in V/F} y_{(v, \\gamma)}*c_{(v, \\gamma)}\n            if (!use_counts) { \n              l2 = choice_starts[j]; \n              h2 = choice_starts[j+1]; \n            } else { \n              l2 = h2; \n              h2 += choice_counts[j]; \n            }\n            if (!use_counts_r) { \n              l2_r = choice_starts_r[j]; \n              h2_r = choice_starts_r[j+1]; \n            } else { \n              l2_r = h2_r; \n              h2_r += choice_counts_r[j]; \n            }\n            k_r = l2_r; \n            while (k_r < h2_r && cols_r[k_r] != cols[l2]) \n              k_r++;\n            // if there is one, add reward * prob to reward value\n            if (k_r < h2_r) {\n              constraints_ints[x] = map_var[i]+j-l1 + 1;\n              arr_reals[x++] = non_zeros_r[k_r]; \n            }\n          }\n        } else if(use_counts) { // count the number of choices for non maybe nodes. Is it necessary?\n          l1 = h1;\n          h1 += row_counts[i];\n          for (j = l1; j < h1; j++) {\n            h2 += choice_counts[j];\n            h2_r += choice_counts_r[j];\n          }\n        }\n\n      if (export_adv != EXPORT_ADV_NONE) {\n        back_arr_reals = new REAL[num_lp_vars];\n        memcpy (back_arr_reals, arr_reals, sizeof(REAL)*num_lp_vars);\n      }\n\n      // Skip quantitative constraint\n      if (relopsReward[ii]==3 || relopsReward[ii]==8)\n        break;\n      else if(relopsReward[ii]==9)\n        isMax = false;\n      if(isMax)\n        add_constraintex(lp, x, arr_reals, constraints_ints, GE, boundsReward[ii]);\n      else\n        add_constraintex(lp, x, arr_reals, constraints_ints, LE, boundsReward[ii]);\n    }\n\n    // Set objective function for LP\n    PN_PrintToMainLog(env, \"Setting objective...\\n\");\n    isMax = true;\n    if(num_targets > 0 && relops[0] == 0) {\n      x = 0;\n      for(i=0; i<n; i++) {\n        varsp = 0;\n        if(yes_vecs[0][i]> 0) {\n          constraints_ints[x] = map_var[i+1] - yes_vec[i] + 1;\n          arr_reals[x++] = 1.0;\n          varsp++;\n        }\n        for(j=1; j<num_targets; j++) \n          if(yes_vecs[j][i]> 0)\n            varsp++;\n        for(j=0; j<num_combinations; j++) {\n          if(combination_vecs[j][i]> 0) {\n            if((combinationIDs[j] & 1) > 0) {\n              constraints_ints[x] = map_var[i+1] - yes_vec[i] + varsp + 1;\n              arr_reals[x++] = 1.0;\n            }\n            varsp++;\n          }\n        }\n      }\n    } else if(relopsReward[0] == 3) { // Rmax     \n    } else if(relopsReward[0] == 8) { // Rmin\n      isMax = false;\n    } else if(relops[0]==2) {\n      x = 0;\n      for(i=0; i<n; i++) {\n        for(j=0; j<yes_vec[i]; j++) {\n          constraints_ints[x] = map_var[i+1]-yes_vec[i]+j + 1;\n          arr_reals[x++] = 1.0;\n        }\n      }\n    } \n    if(isMax)\n      set_maxim(lp);\n    else\n      set_minim(lp);\n    set_obj_fnex(lp, x, arr_reals, constraints_ints);\n    delete[] constraints_ints;\n    \n    // Finished building LP problem\n    set_add_rowmode(lp, false);\n    \n    // Get setup time\n    stop = util_cpu_time();\n    time_for_setup = (double)(stop - start2)/1000;\n    start2 = stop;\n    \n    // Export the MDP to a dot file\n    //export_model(ndsm, n, yes_vec, start_index);\n    \n    // Solve the LP, extract result\n    PN_PrintToMainLog(env, \"Solving LP problem...\\n\");\n    res = solve(lp);\n      \n    //Get LP solving time\n    stop2 = util_cpu_time();  \n    time_for_lp = (double)(stop2 - start2)/1000;\n      \n    if (res != 0) {\n      PN_PrintToMainLog(env, \"No solution\\n\");\n      lp_solved = false;\n    } else {\n      lp_solved = true;\n      lp_result = get_objective(lp);\n      lp_soln = new double[num_lp_vars];\n      get_ptr_variables(lp, &lp_soln);\n\n\t\t// Generate adversary from the solution, if required\n\t\tif (export_adv != EXPORT_ADV_NONE) {\n\t\t\t// Adversary generation\n\t\t\texport_adversary_ltl_tra(export_adv_filename, ndsm, ndsm->actions, action_names, yes_vec, maybe_vec, num_lp_vars, map_var, lp_soln, start_index);\n\t\t\t//export_adversary_ltl_dot(env, ndsm, n, nnz, yes_vec, maybe_vec, num_lp_vars, map_var, lp_soln, start_index);\n\t\t}\n\t\t\n      /*for (i=0; i<num_lp_vars; i++) {\n        if(lp_soln[i] != 0) {\n          PN_PrintToMainLog(env, \"X%d = %g    \", i, lp_soln[i]);\n          count++;\n        }\n        if(count == 8) {\n          PN_PrintToMainLog(env, \"\\n\");\n          count = 0;\n        }\n      }\n      if(count)\n\t\t\tPN_PrintToMainLog(env, \"\\n\");*/\n    }\n\n    // Modify result based on type\n    if (relops[0] != 0 && relopsReward[0] != 3 && relopsReward[0] != 8) {\n      // for qualitative queries, return 1/0 for existence of solution or not\n      PN_PrintToMainLog(env, \"LP problem solution %sfound so result is %s\\n\",  lp_solved ? \"\" : \"not \", lp_solved ? \"true\" : \"false\");\n      lp_result = lp_solved ? 1.0 : 0.0;\n    } else {\n      // return NaN for quantitative queries that can't be solved\n      PN_PrintToMainLog(env, \"LP problem solution %sfound; result is %f\\n\",  lp_solved ? \"\" : \"not \", lp_result);\n      if (!lp_solved) lp_result = NAN;\n    }\n  \n    // Print timing info\n    time_taken = time_for_setup + time_for_lp;\n    PN_PrintToMainLog(env, \"\\nLP problem solved in %.2f seconds (setup %.2f, lpsolve %.2f)\\n\", time_taken, time_for_setup, time_for_lp);\n\n    delete yes_vec;\n    delete map_var;\n    \n    // Catch exceptions: register error\n  } catch (std::bad_alloc e) {\n    PN_SetErrorMessage(\"Out of memory\");\n    lp_result = NAN;\n  }\n\n  // Free memory\n  if (lp) delete_lp(lp);\n  if (a) Cudd_RecursiveDeref(ddman, a);\n  if (maybe_yes) Cudd_RecursiveDeref(ddman, maybe_yes);\n  if (loops) Cudd_RecursiveDeref(ddman, loops);\n  if (ndsm) delete ndsm;\n  if (ndsm_r) delete ndsm_r;\n  delete[] maybe_vec;\n  for (i = 0; i < num_targets; i++)\n    delete[] yes_vecs[i];\n  delete[] arr_reals;\n  if(back_arr_reals)\n    delete[] back_arr_reals;\n  delete[] arr_ints;\n  if (target_ptrs) env->ReleaseLongArrayElements(_targets, target_ptrs, 0);\n  if (relops) env->ReleaseIntArrayElements(_relopsProb, relops, 0);\n  if (bounds) env->ReleaseDoubleArrayElements(_boundsProb, bounds, 0);\n  if (reward_ptrs) env->ReleaseLongArrayElements(_trrs, reward_ptrs, 0);\n  if (relopsReward) env->ReleaseIntArrayElements(_relopsReward, relopsReward, 0);\n  if (boundsReward) env->ReleaseDoubleArrayElements(_boundsReward, boundsReward, 0);\n  //if (rewards)\n  //  for(i = 0; i<num_rewards; i++)\n  //    Cudd_RecursiveDeref(ddman, rewards[i]);\n  if (action_names != NULL) {\n    release_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n  }\n\n  return lp_result;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetReachReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"ExportIterations.h\"\n#include <memory>\n#include \"Measures.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetReachReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t\t// trans matrix\njlong __jlongpointer ta,\t// trans action labels\njobject synchs,\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer g,\t\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t\t// 'maybe' states\njboolean min\t\t\t\t// min or max probabilities (true = min, false = max)\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t\t\t// trans matrix\n\tDdNode *trans_actions = jlong_to_DdNode(ta);\t// trans action labels\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t\t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a, *tmp = NULL;\n\t// model stats\n\tint n, nc, nc_r;\n\tlong nnz, nnz_r;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL, *ndsm_r = NULL;\n\t// vectors\n\tdouble *sr_vec = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL, *inf_vec = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// adversary stuff\n\tint export_adv_enabled = export_adv;\n\tFILE *fp_adv = NULL;\n\tint adv_j;\n\tint *adv = NULL;\n\t// action info\n\tjstring *action_names_jstrings;\n\tconst char** action_names = NULL;\n\tint num_actions;\n\t// misc\n\tint i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, iters;\n\tdouble d1, d2, kb, kbt;\n\tbool done, first;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// also remove goal and infinity states from state rewards vector\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// and from transition rewards matrix\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(maybe);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, maybe);\n\t\n\t// build sparse matrix (probs)\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix (transitions)... \");\n\tndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\tkb = (nnz*12.0+nc*4.0+n*4.0)/1024.0;\n\tkbt = kb;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// if needed, and if info is available, build a vector of action indices for the MDP\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tif (trans_actions != NULL) {\n\t\t\tPN_PrintToMainLog(env, \"Building action information... \");\n\t\t\t// first need to filter out unwanted rows\n\t\t\tCudd_Ref(trans_actions);\n\t\t\tCudd_Ref(maybe);\n\t\t\ttmp = DD_Apply(ddman, APPLY_TIMES, trans_actions, maybe);\n\t\t\t// then convert to a vector of integer indices\n\t\t\tbuild_nd_action_vector(ddman, a, tmp, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\tkb = n*4.0/1024.0;\n\t\t\tkbt += kb;\n\t\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t\t// also extract list of action names from 'synchs'\n\t\t\tget_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n\t\t} else {\n\t\t\tPN_PrintWarningToMainLog(env, \"Action labels are not available for adversary generation.\");\n\t\t}\n\t}\n\t\n\t// build sparse matrix (rewards)\n\tPN_PrintToMainLog(env, \"Building sparse matrix (transition rewards)... \");\n\tndsm_r = build_sub_nd_sparse_matrix(ddman, a, trans_rewards, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz_r = ndsm_r->nnz;\n\tnc_r = ndsm_r->nc;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc_r, nnz_r, ndsm_r->k);\n\tkb = (nnz_r*12.0+nc_r*4.0+n*4.0)/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector for state rewards\n\tPN_PrintToMainLog(env, \"Creating vector for state rewards... \");\n\tsr_vec = mtbdd_to_double_vector(ddman, state_rewards, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector for yes\n\tPN_PrintToMainLog(env, \"Creating vector for inf... \");\n\tinf_vec = mtbdd_to_double_vector(ddman, inf, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\n\t// if required, create storage for adversary and initialise\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tPN_PrintToMainLog(env, \"Allocating adversary vector... \");\n\t\tadv = new int[n];\n\t\tkb = n*sizeof(int)/1024.0;\n\t\tkbt += kb;\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t// Initialise all entries to -1 (\"don't know\")\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tadv[i] = -1;\n\t\t}\n\t}\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\t// initial solution is infinity in 'inf' states, zero elsewhere\n\tfor (i = 0; i < n; i++) {\n\t\tsoln[i] = (inf_vec[i] > 0) ? HUGE_VAL : 0.0;\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PS_NondetReachReward\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\n\t// open file to store adversary (if required)\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tfp_adv = fopen(export_adv_filename, \"w\");\n\t\tif (!fp_adv) {\n\t\t\tPN_PrintWarningToMainLog(env, \"Adversary generation cancelled (could not open file \\\"%s\\\").\", export_adv_filename);\n\t\t\texport_adv_enabled = EXPORT_ADV_NONE;\n\t\t}\n\t}\n\t\n\t// store local copies of stuff\n\t// firstly for transition matrix\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\t// and then for transition rewards matrix\n\t// (note: we don't need row_counts/row_starts for\n\t// this since choice structure mirrors transition matrix)\n\tdouble *non_zeros_r = ndsm_r->non_zeros;\n\tunsigned char *choice_counts_r = ndsm_r->choice_counts;\n\tint *choice_starts_r = (int *)ndsm_r->choice_counts;\n\tbool use_counts_r = ndsm_r->use_counts;\n\tunsigned int *cols_r = ndsm_r->cols;\n\t\t\n\twhile (!done && iters < max_iters) {\n\t\n\t\titers++;\n\n\t\t// do matrix multiplication and min/max\n\t\th1 = h2 = h2_r = 0;\n\t\t// loop through states\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = 0.0; // initial value doesn't matter\n\t\t\tfirst = true; // (because we also remember 'first')\n\t\t\t// get pointers to nondeterministic choices for state i\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t// loop through those choices\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t// compute the reward value for state i for this iteration\n\t\t\t\t// start with state reward for this state\n\t\t\t\td2 = sr_vec[i];\n\t\t\t\t// get pointers to transitions\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t// and get pointers to transition rewards\n\t\t\t\tif (!use_counts_r) { l2_r = choice_starts_r[j]; h2_r = choice_starts_r[j+1]; }\n\t\t\t\telse { l2_r = h2_r; h2_r += choice_counts_r[j]; }\n\t\t\t\t// loop through transitions\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// find corresponding transition reward if any\n\t\t\t\t\tk_r = l2_r; while (k_r < h2_r && cols_r[k_r] != cols[k]) k_r++;\n\t\t\t\t\t// if there is one, add reward * prob to reward value\n\t\t\t\t\tif (k_r < h2_r) { d2 += non_zeros_r[k_r] * non_zeros[k]; k_r++; }\n\t\t\t\t\t// add prob * corresponding reward from previous iteration\n\t\t\t\t\td2 += non_zeros[k] * soln[cols[k]];\n\t\t\t\t}\n\t\t\t\t// see if this value is the min/max so far\n\t\t\t\tif (first || (min&&(d2<d1)) || (!min&&(d2>d1))) {\n\t\t\t\t\td1 = d2;\n\t\t\t\t\t// if adversary generation is enabled, remember optimal choice\n\t\t\t\t\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t\t\t\t\t// for max, only remember strictly better choices\n\t\t\t\t\t\t// (this resolves problems with end components)\n\t\t\t\t\t\tif (!min) {\n\t\t\t\t\t\t\tif (adv[i] == -1 || (d1>soln[i])) {\n\t\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// for min, this is straightforward\n\t\t\t\t\t\t// (in fact, could do it at the end of value iteration, but we don't)\n\t\t\t\t\t\telse {\n\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t\t// set vector element\n\t\t\t// (if there were no choices from this state, reward is zero/infinity)\n\t\t\tsoln2[i] = (h1 > l1) ? d1 : inf_vec[i] > 0 ? HUGE_VAL : 0;\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln2, n, 0);\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln, soln2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// Traverse matrix to extract adversary\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t// Do two passes: first to compute the number of transitions,\n\t\t// the second to actually do the export\n\t\tint num_choice = 0;\n\t\tint num_trans = 0;\n\t\tfor (int pass = 1; pass <= 2; pass++) {\n\t\t\tif (pass == 2) {\n\t\t\t\tif (export_adv_enabled == EXPORT_ADV_DTMC) {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d\\n\", n, num_trans);\n\t\t\t\t} else {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d %d\\n\", n, num_choice, num_trans);\n\t\t\t\t}\n\t\t\t}\n\t\t\th1 = h2 = 0;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t\t// Have to loop through all choices (to compute offsets)\n\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t\t// But only output a choice if it is in the adversary\n\t\t\t\t\tif (j == adv[i]) {\n\t\t\t\t\t\tswitch (pass) {\n\t\t\t\t\t\tcase 1:\n\t\t\t\t\t\t\tnum_choice++;;\n\t\t\t\t\t\t\tnum_trans += (h2-l2);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase 2:\n\t\t\t\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t\t\t\tswitch (export_adv_enabled) {\n\t\t\t\t\t\t\t\tcase EXPORT_ADV_DTMC:\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\tcase EXPORT_ADV_MDP:\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d 0 %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tif (ndsm->actions != NULL) fprintf(fp_adv, \" %s\", ndsm->actions[j]>0?action_names[ndsm->actions[j]-1]:\"\");\n\t\t\t\t\t\t\t\tfprintf(fp_adv, \"\\n\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// close file to store adversary (if required)\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tfclose(fp_adv);\n\t\tPN_PrintToMainLog(env, \"\\nAdversary written to file \\\"%s\\\".\\n\", export_adv_filename);\n\t}\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (state_rewards) Cudd_RecursiveDeref(ddman, state_rewards);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\tif (ndsm) delete ndsm;\n\tif (ndsm_r) delete ndsm_r;\n\tif (inf_vec) delete[] inf_vec;\n\tif (sr_vec) delete[] sr_vec;\n\tif (soln2) delete[] soln2;\n\tif (adv) delete[] adv;\n\tif (action_names != NULL) {\n\t\trelease_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n\t}\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetReachRewardInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include \"Measures.h\"\n#include <memory>\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetReachRewardInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t\t// trans matrix\njlong __jlongpointer ta,\t// trans action labels\njobject synchs,\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer g,\t\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t\t// 'maybe' states\njlong __jlongpointer l,\t\t// lower bound\njlong __jlongpointer u,\t\t// upper bound\njboolean min,\t\t\t\t// min or max probabilities (true = min, false = max)\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t\t\t// trans matrix\n\tDdNode *trans_actions = jlong_to_DdNode(ta);\t// trans action labels\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t\t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t\t// 'maybe' states\n\tDdNode *lower = jlong_to_DdNode(l); \t\t\t// lower bound\n\tDdNode *upper = jlong_to_DdNode(u); \t\t\t// upper bound\n\n\t// mtbdds\n\tDdNode *a, *tmp = NULL;\n\t// model stats\n\tint n, nc, nc_r;\n\tlong nnz, nnz_r;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL, *ndsm_r = NULL;\n\t// vectors\n\tdouble *sr_vec = NULL, *soln_below = NULL, *soln_below2 = NULL, *soln_above = NULL, *soln_above2 = NULL, *tmpsoln = NULL, *inf_vec = NULL, *lower_vec = NULL, *upper_vec = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// adversary stuff\n\tint export_adv_enabled = export_adv;\n\tFILE *fp_adv = NULL;\n\tint adv_j;\n\tint *adv = NULL;\n\t// action info\n\tjstring *action_names_jstrings;\n\tconst char** action_names = NULL;\n\tint num_actions;\n\t// misc\n\tint i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, iters;\n\tdouble d1, d2, x, sup_norm, kb, kbt;\n\tbool done, first;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// also remove goal and infinity states from state rewards vector\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// and from transition rewards matrix\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(maybe);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, maybe);\n\t\n\t// build sparse matrix (probs)\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix (transitions)... \");\n\tndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\tkb = (nnz*12.0+nc*4.0+n*4.0)/1024.0;\n\tkbt = kb;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// if needed, and if info is available, build a vector of action indices for the MDP\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tif (trans_actions != NULL) {\n\t\t\tPN_PrintToMainLog(env, \"Building action information... \");\n\t\t\t// first need to filter out unwanted rows\n\t\t\tCudd_Ref(trans_actions);\n\t\t\tCudd_Ref(maybe);\n\t\t\ttmp = DD_Apply(ddman, APPLY_TIMES, trans_actions, maybe);\n\t\t\t// then convert to a vector of integer indices\n\t\t\tbuild_nd_action_vector(ddman, a, tmp, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\tkb = n*4.0/1024.0;\n\t\t\tkbt += kb;\n\t\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t\t// also extract list of action names from 'synchs'\n\t\t\tget_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n\t\t} else {\n\t\t\tPN_PrintWarningToMainLog(env, \"Action labels are not available for adversary generation.\");\n\t\t}\n\t}\n\t\n\t// build sparse matrix (rewards)\n\tPN_PrintToMainLog(env, \"Building sparse matrix (transition rewards)... \");\n\tndsm_r = build_sub_nd_sparse_matrix(ddman, a, trans_rewards, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz_r = ndsm_r->nnz;\n\tnc_r = ndsm_r->nc;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc_r, nnz_r, ndsm_r->k);\n\tkb = (nnz_r*12.0+nc_r*4.0+n*4.0)/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector for state rewards\n\tPN_PrintToMainLog(env, \"Creating vector for state rewards... \");\n\tsr_vec = mtbdd_to_double_vector(ddman, state_rewards, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector for yes\n\tPN_PrintToMainLog(env, \"Creating vector for inf... \");\n\tinf_vec = mtbdd_to_double_vector(ddman, inf, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n\t// get vector for lower bounds\n\tPN_PrintToMainLog(env, \"Creating vector for lower bounds... \");\n\tlower_vec = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n\t// get vector for lower bounds\n\tPN_PrintToMainLog(env, \"Creating vector for upper bounds... \");\n\tupper_vec = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = new double[n];\n\tsoln_below2 = new double[n];\n\tsoln_above = new double[n];\n\tsoln_above2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 4*kb;\n\tPN_PrintMemoryToMainLog(env, \"[4 x \", kb, \"]\\n\");\n\n\t// if required, create storage for adversary and initialise\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tPN_PrintToMainLog(env, \"Allocating adversary vector... \");\n\t\tadv = new int[n];\n\t\tkb = n*sizeof(int)/1024.0;\n\t\tkbt += kb;\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t// Initialise all entries to -1 (\"don't know\")\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tadv[i] = -1;\n\t\t}\n\t}\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\t// initial solution from below is infinity in 'inf' states, lower elsewhere\n\t// initial solution from above is infinity in 'inf' states, upper elsewhere\n\tfor (i = 0; i < n; i++) {\n\t\tsoln_below[i] = (inf_vec[i] > 0) ? HUGE_VAL : lower_vec[i];\n\t\tsoln_above[i] = (inf_vec[i] > 0) ? HUGE_VAL : upper_vec[i];\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PS_NondetReachReward (interval)\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations (interval iteration)...\\n\");\n\n\t// open file to store adversary (if required)\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tfp_adv = fopen(export_adv_filename, \"w\");\n\t\tif (!fp_adv) {\n\t\t\tPN_PrintWarningToMainLog(env, \"Adversary generation cancelled (could not open file \\\"%s\\\").\", export_adv_filename);\n\t\t\texport_adv_enabled = EXPORT_ADV_NONE;\n\t\t}\n\t}\n\t\n\t// store local copies of stuff\n\t// firstly for transition matrix\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\t// and then for transition rewards matrix\n\t// (note: we don't need row_counts/row_starts for\n\t// this since choice structure mirrors transition matrix)\n\tdouble *non_zeros_r = ndsm_r->non_zeros;\n\tunsigned char *choice_counts_r = ndsm_r->choice_counts;\n\tint *choice_starts_r = (int *)ndsm_r->choice_counts;\n\tbool use_counts_r = ndsm_r->use_counts;\n\tunsigned int *cols_r = ndsm_r->cols;\n\t\t\n\twhile (!done && iters < max_iters) {\n\t\n\t\titers++;\n\n\t\t// do matrix multiplication and min/max (from below)\n\t\th1 = h2 = h2_r = 0;\n\t\t// loop through states\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = 0.0; // initial value doesn't matter\n\t\t\tfirst = true; // (because we also remember 'first')\n\t\t\t// get pointers to nondeterministic choices for state i\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t// loop through those choices\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t// compute the reward value for state i for this iteration\n\t\t\t\t// start with state reward for this state\n\t\t\t\td2 = sr_vec[i];\n\t\t\t\t// get pointers to transitions\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t// and get pointers to transition rewards\n\t\t\t\tif (!use_counts_r) { l2_r = choice_starts_r[j]; h2_r = choice_starts_r[j+1]; }\n\t\t\t\telse { l2_r = h2_r; h2_r += choice_counts_r[j]; }\n\t\t\t\t// loop through transitions\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// find corresponding transition reward if any\n\t\t\t\t\tk_r = l2_r; while (k_r < h2_r && cols_r[k_r] != cols[k]) k_r++;\n\t\t\t\t\t// if there is one, add reward * prob to reward value\n\t\t\t\t\tif (k_r < h2_r) { d2 += non_zeros_r[k_r] * non_zeros[k]; k_r++; }\n\t\t\t\t\t// add prob * corresponding reward from previous iteration\n\t\t\t\t\td2 += non_zeros[k] * soln_below[cols[k]];\n\t\t\t\t}\n\t\t\t\t// see if this value is the min/max so far\n\t\t\t\tif (first || (min&&(d2<d1)) || (!min&&(d2>d1))) {\n\t\t\t\t\td1 = d2;\n\t\t\t\t\t// if adversary generation is enabled, remember optimal choice\n\t\t\t\t\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t\t\t\t\t// for max, only remember strictly better choices\n\t\t\t\t\t\t// (this resolves problems with end components)\n\t\t\t\t\t\tif (!min) {\n\t\t\t\t\t\t\tif (adv[i] == -1 || (d1>soln_below[i])) {\n\t\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// for min, this is straightforward\n\t\t\t\t\t\t// (in fact, could do it at the end of value iteration, but we don't)\n\t\t\t\t\t\telse {\n\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t\t// set vector element\n\t\t\t// (if there were no choices from this state, reward is zero/infinity)\n\t\t\thelper.updateValueFromBelow(soln_below2[i], soln_below[i], (h1 > l1) ? d1 : inf_vec[i] > 0 ? HUGE_VAL : 0);\n\t\t}\n\n\n\t\t// do matrix multiplication and min/max (from above)\n\t\th1 = h2 = h2_r = 0;\n\t\t// loop through states\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = 0.0; // initial value doesn't matter\n\t\t\tfirst = true; // (because we also remember 'first')\n\t\t\t// get pointers to nondeterministic choices for state i\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t// loop through those choices\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t// compute the reward value for state i for this iteration\n\t\t\t\t// start with state reward for this state\n\t\t\t\td2 = sr_vec[i];\n\t\t\t\t// get pointers to transitions\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t// and get pointers to transition rewards\n\t\t\t\tif (!use_counts_r) { l2_r = choice_starts_r[j]; h2_r = choice_starts_r[j+1]; }\n\t\t\t\telse { l2_r = h2_r; h2_r += choice_counts_r[j]; }\n\t\t\t\t// loop through transitions\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t// find corresponding transition reward if any\n\t\t\t\t\tk_r = l2_r; while (k_r < h2_r && cols_r[k_r] != cols[k]) k_r++;\n\t\t\t\t\t// if there is one, add reward * prob to reward value\n\t\t\t\t\tif (k_r < h2_r) { d2 += non_zeros_r[k_r] * non_zeros[k]; k_r++; }\n\t\t\t\t\t// add prob * corresponding reward from previous iteration\n\t\t\t\t\td2 += non_zeros[k] * soln_above[cols[k]];\n\t\t\t\t}\n\t\t\t\t// see if this value is the min/max so far\n\t\t\t\tif (first || (min&&(d2<d1)) || (!min&&(d2>d1))) {\n\t\t\t\t\td1 = d2;\n\t\t\t\t}\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t\t// set vector element\n\t\t\t// (if there were no choices from this state, reward is zero/infinity)\n\t\t\thelper.updateValueFromAbove(soln_above2[i], soln_above[i], (h1 > l1) ? d1 : inf_vec[i] > 0 ? HUGE_VAL : 0);\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below2, n, 0);\n\t\t\titerationExport->exportVector(soln_above2, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below2, soln_above2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln_below;\n\t\tsoln_below = soln_below2;\n\t\tsoln_below2 = tmpsoln;\n\t\ttmpsoln = soln_above;\n\t\tsoln_above = soln_above2;\n\t\tsoln_above2 = tmpsoln;\n\t}\n\t\n\t// Traverse matrix to extract adversary\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t// Do two passes: first to compute the number of transitions,\n\t\t// the second to actually do the export\n\t\tint num_choice = 0;\n\t\tint num_trans = 0;\n\t\tfor (int pass = 1; pass <= 2; pass++) {\n\t\t\tif (pass == 2) {\n\t\t\t\tif (export_adv_enabled == EXPORT_ADV_DTMC) {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d\\n\", n, num_trans);\n\t\t\t\t} else {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d %d\\n\", n, num_choice, num_trans);\n\t\t\t\t}\n\t\t\t}\n\t\t\th1 = h2 = 0;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t\t// Have to loop through all choices (to compute offsets)\n\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t\t// But only output a choice if it is in the adversary\n\t\t\t\t\tif (j == adv[i]) {\n\t\t\t\t\t\tswitch (pass) {\n\t\t\t\t\t\tcase 1:\n\t\t\t\t\t\t\tnum_choice++;;\n\t\t\t\t\t\t\tnum_trans += (h2-l2);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase 2:\n\t\t\t\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t\t\t\tswitch (export_adv_enabled) {\n\t\t\t\t\t\t\t\tcase EXPORT_ADV_DTMC:\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\tcase EXPORT_ADV_MDP:\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d 0 %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tif (ndsm->actions != NULL) fprintf(fp_adv, \" %s\", ndsm->actions[j]>0?action_names[ndsm->actions[j]-1]:\"\");\n\t\t\t\t\t\t\t\tfprintf(fp_adv, \"\\n\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\t\n\t// close file to store adversary (if required)\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tfclose(fp_adv);\n\t\tPN_PrintToMainLog(env, \"\\nAdversary written to file \\\"%s\\\".\\n\", export_adv_filename);\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (state_rewards) Cudd_RecursiveDeref(ddman, state_rewards);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\tif (ndsm) delete ndsm;\n\tif (ndsm_r) delete ndsm_r;\n\tif (inf_vec) delete[] inf_vec;\n\tif (lower_vec) delete[] lower_vec;\n\tif (upper_vec) delete[] upper_vec;\n\tif (sr_vec) delete[] sr_vec;\n\tif (soln_above) delete[] soln_above;\n\tif (soln_above2) delete[] soln_above2;\n\tif (soln_below2) delete[] soln_below2;\n\tif (adv) delete[] adv;\n\tif (action_names != NULL) {\n\t\trelease_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n\t}\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <new>\n#include <memory>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t\t// trans matrix\njlong __jlongpointer ta,\t// trans action labels\njobject synchs,\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t\t// 'yes' states\njlong __jlongpointer m,\t\t// 'maybe' states\njboolean min,\t\t\t\t// min or max probabilities (true = min, false = max)\njlong _strat\t\t\t\t// strategy storage\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t\t\t// trans matrix\n\tDdNode *trans_actions = jlong_to_DdNode(ta);\t// trans action labels\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t\t// 'maybe' states\n\tint *strat = (int *)jlong_to_ptr(_strat);\t\t// strategy storage\n\n\t// mtbdds\n\tDdNode *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n, nc;\n\tlong nnz;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL;\n\t// vectors\n\tdouble *yes_vec = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// adversary stuff\n\tint export_adv_enabled = export_adv;\n\tFILE *fp_adv = NULL;\n\tint adv_j;\n\tint *adv = NULL;\n\t// action info\n\tjstring *action_names_jstrings;\n\tconst char** action_names = NULL;\n\tint num_actions;\n\t// misc\n\tint i, j, k, l1, h1, l2, h2, iters;\n\tdouble d1, d2, kb, kbt;\n\tbool done, first;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get a - filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// When computing maximum reachability probabilities,\n\t// we can safely remove any probability 1 self-loops for efficiency.\n\t// This might leave some states with no choices (only if no precomp done)\n\t// but this is not a problem, for value iteration.\n\t// This is also motivated by the fact that this fixes some simple problem\n\t// cases for adversary generation.\n\tif (!min) {\n\t\tCudd_Ref(a);\n\t\ttmp = DD_And(ddman, DD_Equals(ddman, a, 1.0), DD_Identity(ddman, rvars, cvars, num_rvars));\n\t\ta = DD_ITE(ddman, tmp, DD_Constant(ddman, 0), a);\n\t}\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\tndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\tkb = ndsm->mem;\n\tkbt = kb;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// if needed, and if info is available, build a vector of action indices for the MDP\n\tif (export_adv_enabled != EXPORT_ADV_NONE || strat != NULL) {\n\t\tif (trans_actions != NULL) {\n\t\t\tPN_PrintToMainLog(env, \"Building action information... \");\n\t\t\t// first need to filter out unwanted rows\n\t\t\tCudd_Ref(trans_actions);\n\t\t\tCudd_Ref(maybe);\n\t\t\ttmp = DD_Apply(ddman, APPLY_TIMES, trans_actions, maybe);\n\t\t\t// then convert to a vector of integer indices\n\t\t\tbuild_nd_action_vector(ddman, a, tmp, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\tkb = n*4.0/1024.0;\n\t\t\tkbt += kb;\n\t\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t\t// also extract list of action names from 'synchs'\n\t\t\tget_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n\t\t} else {\n\t\t\tPN_PrintWarningToMainLog(env, \"Action labels are not available for adversary generation.\");\n\t\t}\n\t}\n\t\n\t// get vector for yes\n\tPN_PrintToMainLog(env, \"Creating vector for yes... \");\n\tyes_vec = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// if required, create storage for adversary and initialise\n\tif (export_adv_enabled != EXPORT_ADV_NONE || strat != NULL) {\n\t\tPN_PrintToMainLog(env, \"Allocating adversary vector... \");\n\t\t// Use passed in (pre-filled) array, if provided\n\t\tif (strat) {\n\t\t\tadv = strat;\n\t\t} else {\n\t\t\tadv = new int[n];\n\t\t\t// Initialise all entries to -1 (\"don't know\")\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tadv[i] = -1;\n\t\t\t}\n\t\t}\n\t\tkb = n*sizeof(int)/1024.0;\n\t\tkbt += kb;\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is yes\n\tfor (i = 0; i < n; i++) {\n\t\tsoln[i] = yes_vec[i];\n//\t\tif (soln[i]) printf(\"yes[%d] := %f;\\n\", i+1, yes[i]);\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PS_NondetUntil\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// open file to store adversary (if required)\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tfp_adv = fopen(export_adv_filename, \"w\");\n\t\tif (!fp_adv) {\n\t\t\tPN_PrintWarningToMainLog(env, \"Adversary generation cancelled (could not open file \\\"%s\\\").\", export_adv_filename);\n\t\t\texport_adv_enabled = EXPORT_ADV_NONE;\n\t\t}\n\t}\n\t\n\t// store local copies of stuff\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\t\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// do matrix multiplication and min/max\n\t\th1 = h2 = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = 0.0; // initial value doesn't matter\n\t\t\tfirst = true; // (because we also remember 'first')\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\td2 = 0;\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\td2 += non_zeros[k] * soln[cols[k]];\n\t\t\t\t}\n\t\t\t\tif (first || (min&&(d2<d1)) || (!min&&(d2>d1))) {\n\t\t\t\t\td1 = d2;\n\t\t\t\t\t// if adversary generation is enabled, remember optimal choice\n\t\t\t\t\tif (export_adv_enabled != EXPORT_ADV_NONE || strat != NULL) {\n\t\t\t\t\t\t// for max, only remember strictly better choices\n\t\t\t\t\t\t// (this resolves problems with end components)\n\t\t\t\t\t\tif (!min) {\n\t\t\t\t\t\t\tif (adv[i] == -1 || (d1>soln[i])) {\n\t\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// for min, this is straightforward\n\t\t\t\t\t\t// (in fact, could do it at the end of value iteration, but we don't)\n\t\t\t\t\t\telse {\n\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t\t// set vector element\n\t\t\t// (if no choices, use value of yes)\n\t\t\tsoln2[i] = (h1 > l1) ? d1 : yes_vec[i];\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln2, n, 0);\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln, soln2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// Traverse matrix to extract adversary\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t// Do two passes: first to compute the number of choices/transitions,\n\t\t// the second to actually do the export\n\t\tint num_choice = 0;\n\t\tint num_trans = 0;\n\t\tfor (int pass = 1; pass <= 2; pass++) {\n\t\t\tif (pass == 2) {\n\t\t\t\tif (export_adv_enabled == EXPORT_ADV_DTMC) {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d\\n\", n, num_trans);\n\t\t\t\t} else {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d %d\\n\", n, num_choice, num_trans);\n\t\t\t\t}\n\t\t\t}\n\t\t\th1 = h2 = 0;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t\t// Have to loop through all choices (to compute offsets)\n\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t\t// But only output a choice if it is in the adversary\n\t\t\t\t\tif (j == adv[i]) {\n\t\t\t\t\t\tswitch (pass) {\n\t\t\t\t\t\tcase 1:\n\t\t\t\t\t\t\tnum_choice++;;\n\t\t\t\t\t\t\tnum_trans += (h2-l2);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase 2:\n\t\t\t\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t\t\t\tswitch (export_adv_enabled) {\n\t\t\t\t\t\t\t\tcase EXPORT_ADV_DTMC:\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\tcase EXPORT_ADV_MDP:\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d 0 %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tif (ndsm->actions != NULL) fprintf(fp_adv, \" %s\", ndsm->actions[j]>0?action_names[ndsm->actions[j]-1]:\"\");\n\t\t\t\t\t\t\t\tfprintf(fp_adv, \"\\n\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// close file to store adversary (if required)\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tfclose(fp_adv);\n\t\tPN_PrintToMainLog(env, \"\\nAdversary written to file \\\"%s\\\".\\n\", export_adv_filename);\n\t}\n\t\t\n\t// convert strategy indices from choices to actions\n\tif (strat != NULL) {\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (adv[i] > 0) strat[i] = ndsm->actions[adv[i]] - 1;\n\t\t}\n\t}\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (ndsm) delete ndsm;\n\tif (yes_vec) delete[] yes_vec;\n\tif (soln2) delete[] soln2;\n\tif (strat == NULL && adv) delete[] adv;\n\tif (action_names != NULL) {\n\t\trelease_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n\t}\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/sparse/PS_NondetUntilInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"prism.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1NondetUntilInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t\t// trans matrix\njlong __jlongpointer ta,\t// trans action labels\njobject synchs,\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ndv,\t// nondet vars\njint num_ndvars,\njlong __jlongpointer y,\t\t// 'yes' states\njlong __jlongpointer m,\t\t// 'maybe' states\njboolean min,\t\t\t\t// min or max probabilities (true = min, false = max)\njlong _strat,\t\t\t\t// strategy storage\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t\t\t// trans matrix\n\tDdNode *trans_actions = jlong_to_DdNode(ta);\t// trans action labels\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode **ndvars = jlong_to_DdNode_array(ndv);\t// nondet vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t\t// 'maybe' states\n\tint *strat = (int *)jlong_to_ptr(_strat);\t\t// strategy storage\n\n\t// mtbdds\n\tDdNode *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n, nc;\n\tlong nnz;\n\t// sparse matrix\n\tNDSparseMatrix *ndsm = NULL;\n\t// vectors\n\tdouble *yes_vec = NULL, *maybe_vec = NULL;\n\tdouble *soln_below = NULL, *soln_below2 = NULL;\n\tdouble *soln_above = NULL, *soln_above2 = NULL;\n\tdouble *tmpsoln = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// adversary stuff\n\tint export_adv_enabled = export_adv;\n\tFILE *fp_adv = NULL;\n\tint adv_j;\n\tint *adv = NULL;\n\t// action info\n\tjstring *action_names_jstrings;\n\tconst char** action_names = NULL;\n\tint num_actions;\n\t// misc\n\tint i, j, k, l1, h1, l2, h2, iters;\n\tdouble d1, d2, kb, kbt;\n\tbool done, first;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to enforce monotonicity from below.\\n\");\n\t}\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get a - filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// When computing maximum reachability probabilities,\n\t// we can safely remove any probability 1 self-loops for efficiency.\n\t// This might leave some states with no choices (only if no precomp done)\n\t// but this is not a problem, for value iteration.\n\t// This is also motivated by the fact that this fixes some simple problem\n\t// cases for adversary generation.\n\tif (!min) {\n\t\tCudd_Ref(a);\n\t\ttmp = DD_And(ddman, DD_Equals(ddman, a, 1.0), DD_Identity(ddman, rvars, cvars, num_rvars));\n\t\ta = DD_ITE(ddman, tmp, DD_Constant(ddman, 0), a);\n\t}\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\tndsm = build_nd_sparse_matrix(ddman, a, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t// get number of transitions/choices\n\tnnz = ndsm->nnz;\n\tnc = ndsm->nc;\n\tkb = ndsm->mem;\n\tkbt = kb;\n\t// print out info\n\tPN_PrintToMainLog(env, \"[n=%d, nc=%d, nnz=%ld, k=%d] \", n, nc, nnz, ndsm->k);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// if needed, and if info is available, build a vector of action indices for the MDP\n\tif (export_adv_enabled != EXPORT_ADV_NONE || strat != NULL) {\n\t\tif (trans_actions != NULL) {\n\t\t\tPN_PrintToMainLog(env, \"Building action information... \");\n\t\t\t// first need to filter out unwanted rows\n\t\t\tCudd_Ref(trans_actions);\n\t\t\tCudd_Ref(maybe);\n\t\t\ttmp = DD_Apply(ddman, APPLY_TIMES, trans_actions, maybe);\n\t\t\t// then convert to a vector of integer indices\n\t\t\tbuild_nd_action_vector(ddman, a, tmp, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t\t\tCudd_RecursiveDeref(ddman, tmp);\n\t\t\tkb = n*4.0/1024.0;\n\t\t\tkbt += kb;\n\t\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\t\t// also extract list of action names from 'synchs'\n\t\t\tget_string_array_from_java(env, synchs, action_names_jstrings, action_names, num_actions);\n\t\t} else {\n\t\t\tPN_PrintWarningToMainLog(env, \"Action labels are not available for adversary generation.\");\n\t\t}\n\t}\n\t\n\t// get vector for yes\n\tPN_PrintToMainLog(env, \"Creating vector for yes... \");\n\tyes_vec = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector for yes\n\tPN_PrintToMainLog(env, \"Creating vector for maybe... \");\n\tmaybe_vec = mtbdd_to_double_vector(ddman, maybe, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = new double[n];\n\tsoln_below2 = new double[n];\n\tsoln_above = new double[n];\n\tsoln_above2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 4*kb;\n\tPN_PrintMemoryToMainLog(env, \"[4 x \", kb, \"]\\n\");\n\t\n\t// if required, create storage for adversary and initialise\n\tif (export_adv_enabled != EXPORT_ADV_NONE || strat != NULL) {\n\t\tPN_PrintToMainLog(env, \"Allocating adversary vector... \");\n\t\t// Use passed in (pre-filled) array, if provided\n\t\tif (strat) {\n\t\t\tadv = strat;\n\t\t} else {\n\t\t\tadv = new int[n];\n\t\t\t// Initialise all entries to -1 (\"don't know\")\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tadv[i] = -1;\n\t\t\t}\n\t\t}\n\t\tkb = n*sizeof(int)/1024.0;\n\t\tkbt += kb;\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution for below is yes, from above is 1 (expect for no states)\n\tfor (i = 0; i < n; i++) {\n\t\tsoln_below[i] = yes_vec[i];\n\t\tif (yes_vec[i] != 0.0 || maybe_vec[i] != 0.0) {\n\t\t\tsoln_above[i] = 1.0;\n\t\t} else {\n\t\t\t// no state\n\t\t\tsoln_above[i] = 0.0;\n\t\t}\n//\t\tif (soln[i]) printf(\"yes[%d] := %f;\\n\", i+1, yes[i]);\n\t}\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PS_NondetUntil_Interval\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations (interval iteration)...\\n\");\n\t\n\t// open file to store adversary (if required)\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tfp_adv = fopen(export_adv_filename, \"w\");\n\t\tif (!fp_adv) {\n\t\t\tPN_PrintWarningToMainLog(env, \"Adversary generation cancelled (could not open file \\\"%s\\\").\", export_adv_filename);\n\t\t\texport_adv_enabled = EXPORT_ADV_NONE;\n\t\t}\n\t}\n\t\n\t// store local copies of stuff\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\t\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// do matrix multiplication and min/max for below, optionally generate adversary\n\t\th1 = h2 = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = 0.0; // initial value doesn't matter\n\t\t\tfirst = true; // (because we also remember 'first')\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\td2 = 0;\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\td2 += non_zeros[k] * soln_below[cols[k]];\n\t\t\t\t}\n\t\t\t\tif (first || (min&&(d2<d1)) || (!min&&(d2>d1))) {\n\t\t\t\t\td1 = d2;\n\t\t\t\t\t// if adversary generation is enabled, remember optimal choice\n\t\t\t\t\tif (export_adv_enabled != EXPORT_ADV_NONE || strat != NULL) {\n\t\t\t\t\t\t// for max, only remember strictly better choices\n\t\t\t\t\t\t// (this resolves problems with end components)\n\t\t\t\t\t\tif (!min) {\n\t\t\t\t\t\t\tif (adv[i] == -1 || (d1>soln_below[i])) {\n\t\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// for min, this is straightforward\n\t\t\t\t\t\t// (in fact, could do it at the end of value iteration, but we don't)\n\t\t\t\t\t\telse {\n\t\t\t\t\t\t\tadv[i] = j;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t\t// set vector element\n\t\t\t// (if no choices, use value of yes)\n\t\t\thelper.updateValueFromBelow(soln_below2[i], soln_below[i], (h1 > l1) ? d1 : yes_vec[i]);\n\t\t}\n\n\t\t// do matrix multiplication and min/max for above (don't generate adversary, done above in \"from below\" iteration)\n\t\th1 = h2 = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td1 = 0.0; // initial value doesn't matter\n\t\t\tfirst = true; // (because we also remember 'first')\n\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\td2 = 0;\n\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\td2 += non_zeros[k] * soln_above[cols[k]];\n\t\t\t\t}\n\t\t\t\tif (first || (min&&(d2<d1)) || (!min&&(d2>d1))) {\n\t\t\t\t\td1 = d2;\n\t\t\t\t}\n\t\t\t\tfirst = false;\n\t\t\t}\n\t\t\t// set vector element\n\t\t\t// (if no choices, use value of yes)\n\t\t\thelper.updateValueFromAbove(soln_above2[i], soln_above[i], (h1 > l1) ? d1 : yes_vec[i]);\n\t\t}\n\n//\t\tprintf(\"sol_above:\\n\");\n//\t\tfor (i = 0; i < n; i++) {\n//\t\t\tprintf(\"%f \", soln_above[i]);\n//\t\t}\n//\t\tprintf(\"\\nsol_below:\\n\");\n//\t\tfor (i = 0; i < n; i++) {\n//\t\t\tprintf(\"%f \", soln_below[i]);\n//\t\t}\n//\t\tprintf(\"\\n\");\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below2, n, 0);\n\t\t\titerationExport->exportVector(soln_above2, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below2, soln_above2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln_below;\n\t\tsoln_below = soln_below2;\n\t\tsoln_below2 = tmpsoln;\n\t\ttmpsoln = soln_above;\n\t\tsoln_above = soln_above2;\n\t\tsoln_above2 = tmpsoln;\n\t}\n\n\t// Traverse matrix to extract adversary\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\t// Do two passes: first to compute the number of transitions,\n\t\t// the second to actually do the export\n\t\tint num_choice = 0;\n\t\tint num_trans = 0;\n\t\tfor (int pass = 1; pass <= 2; pass++) {\n\t\t\tif (pass == 2) {\n\t\t\t\tif (export_adv_enabled == EXPORT_ADV_DTMC) {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d\\n\", n, num_trans);\n\t\t\t\t} else {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d %d\\n\", n, num_choice, num_trans);\n\t\t\t\t}\n\t\t\t}\n\t\t\th1 = h2 = 0;\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\t\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\t\t\t// Have to loop through all choices (to compute offsets)\n\t\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t\t\t// But only output a choice if it is in the adversary\n\t\t\t\t\tif (j == adv[i]) {\n\t\t\t\t\t\tswitch (pass) {\n\t\t\t\t\t\tcase 1:\n\t\t\t\t\t\t\tnum_choice++;;\n\t\t\t\t\t\t\tnum_trans += (h2-l2);\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase 2:\n\t\t\t\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\t\t\t\tswitch (export_adv_enabled) {\n\t\t\t\t\t\t\t\tcase EXPORT_ADV_DTMC:\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\tcase EXPORT_ADV_MDP:\n\t\t\t\t\t\t\t\t\tfprintf(fp_adv, \"%d 0 %d %g\", i, cols[k], non_zeros[k]); break;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tif (ndsm->actions != NULL) fprintf(fp_adv, \" %s\", ndsm->actions[j]>0?action_names[ndsm->actions[j]-1]:\"\");\n\t\t\t\t\t\t\t\tfprintf(fp_adv, \"\\n\");\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// close file to store adversary (if required)\n\tif (export_adv_enabled != EXPORT_ADV_NONE) {\n\t\tfclose(fp_adv);\n\t\tPN_PrintToMainLog(env, \"\\nAdversary written to file \\\"%s\\\".\\n\", export_adv_filename);\n\t}\n\t\t\n\t// convert strategy indices from choices to actions\n\tif (strat != NULL) {\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tif (adv[i] > 0) strat[i] = ndsm->actions[adv[i]] - 1;\n\t\t}\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (ndsm) delete ndsm;\n\tif (yes_vec) delete[] yes_vec;\n\tif (maybe_vec) delete[] maybe_vec;\n\tif (soln_above) delete[] soln_above;\n\tif (soln_above2) delete[] soln_above2;\n\tif (soln_below2) delete[] soln_below2;\n\tif (strat == NULL && adv) delete[] adv;\n\tif (action_names != NULL) {\n\t\trelease_string_array_from_java(env, action_names_jstrings, action_names, num_actions);\n\t}\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/sparse/PS_Power.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <memory>\n#include <new>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=x with the Power method\n// in addition, solutions may be provided for additional states in the vector b\n// these states are assumed not to have non-zero rows in the matrix A\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1Power\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose\t// transpose A? (i.e. solve xA=x not Ax=x?)\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_a, compact_b;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *b_vec = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\tDistVector *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, l, h, iters;\n\tdouble d, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_a = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_a = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_a?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, init, rvars, num_rvars, odd);\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PS_Power\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_a) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t\n\t\t\td = (b == NULL) ? 0.0 : ((!compact_b) ? b_vec[i] : b_dist->dist[b_dist->ptrs[i]]);\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_a) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += non_zeros[j] * soln[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += dist[(int)(cols[j] & dist_mask)] * soln[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln2, n, 0);\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln, soln2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, (measure.isRelative()?\"relative \":\"\"), measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\nPower method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_PowerInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=x with the Power method (interval variant)\n// in addition, solutions may be provided for additional states in the vector b\n// these states are assumed not to have non-zero rows in the matrix A\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1PowerInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=x not Ax=x?)\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t\t// upper bound values\n\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_a, compact_b;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *b_vec = NULL, *soln_below = NULL, *soln_below2 = NULL, *soln_above = NULL, *soln_above2 = NULL, *tmpsoln = NULL;\n\tDistVector *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, l, h, iters;\n\tdouble d_below, d_above, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tIntervalIteration helper(flags);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_a = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_a = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_a?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tsoln_above = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tsoln_below2 = new double[n];\n\tsoln_above2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 4*kb;\n\tPN_PrintMemoryToMainLog(env, \"[4 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\titerationExport.reset(new ExportIterations(\"PS_PowerInterval\"));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_a) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply (below & above simultaneously)\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t\n\t\t\td_below = (b == NULL) ? 0.0 : ((!compact_b) ? b_vec[i] : b_dist->dist[b_dist->ptrs[i]]);\n\t\t\td_above = d_below;\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_a) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td_below += non_zeros[j] * soln_below[cols[j]];\n\t\t\t\t\td_above += non_zeros[j] * soln_above[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td_below += dist[(int)(cols[j] & dist_mask)] * soln_below[(int)(cols[j] >> dist_shift)];\n\t\t\t\t\td_above += dist[(int)(cols[j] & dist_mask)] * soln_above[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\thelper.updateValueFromBelow(soln_below2[i], soln_below[i], d_below);\n\t\t\thelper.updateValueFromAbove(soln_above2[i], soln_above[i], d_above);\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below2, n, 0);\n\t\t\titerationExport->exportVector(soln_above2, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below2, soln_above2, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln_below;\n\t\tsoln_below = soln_below2;\n\t\tsoln_below2 = tmpsoln;\n\t\ttmpsoln = soln_above;\n\t\tsoln_above = soln_above2;\n\t\tsoln_above2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\nPower method (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln_above) delete[] soln_above;\n\tif (soln_below2) delete[] soln_below2;\n\tif (soln_above2) delete[] soln_above2;\n\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ProbBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1ProbBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njint bound\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *a = NULL;\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_tr, compact_y;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *yes_vec = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\tDistVector *yes_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, l, h, iters;\n\tdouble d, kb, kbt;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get a - filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_tr = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_tr = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_tr?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of yes\n\tPN_PrintToMainLog(env, \"Creating vector for yes... \");\n\tyes_vec = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\t// try and convert to compact form if required\n\tcompact_y = false;\n\tif (compact) {\n\t\tif ((yes_dist = double_vector_to_dist(yes_vec, n))) {\n\t\t\tcompact_y = true;\n\t\t\tdelete[] yes_vec; yes_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_y) ? n*8.0/1024.0 : (yes_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_y) PN_PrintToMainLog(env, \"[dist=%d, compact] \", yes_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is q\n\tfor (i = 0; i < n; i++) {\n\t\tsoln[i] = (!compact_y) ? yes_vec[i] : yes_dist->dist[yes_dist->ptrs[i]];\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_tr) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td = 0.0;\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_tr) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += non_zeros[j] * soln[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += dist[(int)(cols[j] & dist_mask)] * soln[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set yes states to 1\n\t\t\tif (!compact_y) { if (yes_vec[i]) d = 1.0; } else { if (yes_dist->dist[yes_dist->ptrs[i]]) d = 1.0; }\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (yes_vec) delete[] yes_vec;\n\tif (yes_dist) delete yes_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ProbCumulReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1ProbCumulReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njint bound\t\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *all_rewards = NULL;\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_tr, compact_r;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *rew_vec = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\tDistVector *rew_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, l, h, iters;\n\tdouble d, kb, kbt;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_tr = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_tr = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_tr?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// then combine state and transition rewards and put in a vector\n\tCudd_Ref(trans_rewards);\n\tCudd_Ref(trans);\n\tall_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, trans);\n\tall_rewards = DD_SumAbstract(ddman, all_rewards, cvars, num_cvars);\n\tCudd_Ref(state_rewards);\n\tall_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, all_rewards);\n\n\t// get vector of rewards\n\tPN_PrintToMainLog(env, \"Creating vector for rewards... \");\n\trew_vec = mtbdd_to_double_vector(ddman, all_rewards, rvars, num_rvars, odd);\n\t// try and convert to compact form if required\n\tcompact_r = false;\n\tif (compact) {\n\t\tif ((rew_dist = double_vector_to_dist(rew_vec, n))) {\n\t\t\tcompact_r = true;\n\t\t\tdelete[] rew_vec; rew_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_r) ? n*8.0/1024.0 : (rew_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_r) PN_PrintToMainLog(env, \"[dist=%d, compact] \", rew_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = new double[n];\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// initial solution is zero\n\tfor (i = 0; i < n; i++) {\n\t\tsoln[i] = 0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_tr) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td = (!compact_r) ? rew_vec[i] : rew_dist->dist[rew_dist->ptrs[i]];\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_tr) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += non_zeros[j] * soln[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += dist[(int)(cols[j] & dist_mask)] * soln[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (all_rewards) Cudd_RecursiveDeref(ddman, all_rewards);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (rew_vec) delete[] rew_vec;\n\tif (rew_dist) delete rew_dist;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ProbInstReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1ProbInstReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njint bound\t\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\t\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_tr;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, l, h, iters;\n\tdouble d, kb, kbt;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_tr = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_tr = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_tr?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\t// (solution is initialised to the state rewards)\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, state_rewards, rvars, num_rvars, odd);\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < bound; iters++) {\n\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_tr) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td = 0.0;\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_tr) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += non_zeros[j] * soln[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += dist[(int)(cols[j] & dist_mask)] * soln[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)bound);\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iterations/timing info\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ProbReachReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1ProbReachReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m\t// 'maybe' states\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n;\n\t// vectors\n\tdouble *soln = NULL, *inf_vec = NULL;\n\t// misc\n\tint i;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// take copy of state/trans rewards\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(trans_rewards);\n\t\n\t// remove goal and infinity states from state rewards vector\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\t\n\t// combine state and transition rewards and put in a vector\n\tCudd_Ref(trans_rewards);\n\tstate_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, trans_rewards);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, 1.0)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, lin_eq_method_param)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(state_rewards), false, false, lin_eq_method_param, false)); break;\n\t\tdefault:\n\t\t\tPN_SetErrorMessage(\"Pseudo Gauss-Seidel/SOR methods are currently not supported by the sparse engine\"); return 0;\n\t}\n\t\n\t// set reward for infinity states to infinity\n\tif (soln != NULL) {\n\t\t// first, generate vector for inf\n\t\tinf_vec = mtbdd_to_double_vector(ddman, inf, rvars, num_rvars, odd);\n\t\t// go thru setting elements of soln to infinity\n\t\tfor (i = 0; i < n; i++) if (inf_vec[i] > 0) soln[i] = HUGE_VAL;\n\t\tdelete[] inf_vec;\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free remaining memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (state_rewards) Cudd_RecursiveDeref(ddman, state_rewards);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ProbReachRewardInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"IntervalIteration.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1ProbReachRewardInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer g,\t// 'goal' states\njlong __jlongpointer in,\t// 'inf' states\njlong __jlongpointer m,\t// 'maybe' states\njlong __jlongpointer l,  // lower bound\njlong __jlongpointer u,   // upper bound\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *goal = jlong_to_DdNode(g);\t\t// 'goal' states\n\tDdNode *inf = jlong_to_DdNode(in); \t\t// 'inf' states\n\tDdNode *maybe = jlong_to_DdNode(m); \t\t// 'maybe' states\n\tDdNode *lower = jlong_to_DdNode(l);\t\t// lower bound\n\tDdNode *upper = jlong_to_DdNode(u);\t\t// upper bound\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n;\n\t// vectors\n\tdouble *soln = NULL, *inf_vec = NULL;\n\t// misc\n\tint i;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows (goal states and infinity states) from matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// take copy of state/trans rewards\n\tCudd_Ref(state_rewards);\n\tCudd_Ref(trans_rewards);\n\t\n\t// remove goal and infinity states from state rewards vector\n\tCudd_Ref(maybe);\n\tstate_rewards = DD_Apply(ddman, APPLY_TIMES, state_rewards, maybe);\n\t\n\t// multiply transition rewards by transition probs and sum rows\n\t// (note also filters out unwanted states at the same time)\n\tCudd_Ref(a);\n\ttrans_rewards = DD_Apply(ddman, APPLY_TIMES, trans_rewards, a);\n\ttrans_rewards = DD_SumAbstract(ddman, trans_rewards, cvars, num_cvars);\n\t\n\t// combine state and transition rewards and put in a vector\n\tCudd_Ref(trans_rewards);\n\tstate_rewards = DD_Apply(ddman, APPLY_PLUS, state_rewards, trans_rewards);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1PowerInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, flags)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, flags)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, false, flags)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, flags)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(state_rewards), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, false, flags)); break;\n\t\tdefault:\n\t\t\tPN_SetErrorMessage(\"Pseudo Gauss-Seidel/SOR methods are currently not supported by the sparse engine\"); return 0;\n\t}\n\t\n\t// set reward for infinity states to infinity\n\tif (soln != NULL) {\n\t\t// first, generate vector for inf\n\t\tinf_vec = mtbdd_to_double_vector(ddman, inf, rvars, num_rvars, odd);\n\t\t// go thru setting elements of soln to infinity\n\t\tfor (i = 0; i < n; i++) if (inf_vec[i] > 0) soln[i] = HUGE_VAL;\n\t\tdelete[] inf_vec;\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free remaining memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (state_rewards) Cudd_RecursiveDeref(ddman, state_rewards);\n\tif (trans_rewards) Cudd_RecursiveDeref(ddman, trans_rewards);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ProbTransient.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include <prism.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1ProbTransient\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer in,\t// initial distribution (note: this will be deleted afterwards)\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njint time\t\t// time\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tdouble *init = jlong_to_double(in);\t\t\t// initial distribution\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_tr;\n\t// sparse matrix\n\tCMSparseMatrix *cmsm = NULL;\n\tCMSCSparseMatrix *cmscsm = NULL;\n\t// vectors\n\tdouble *soln = NULL, *soln2 = NULL, *tmpsoln = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint i, j, l, h, iters;\n\tdouble d, kb, kbt;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_tr = true;\n\tcmscsm = NULL;\n\tif (compact) cmscsm = build_cmsc_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\tif (cmscsm != NULL) {\n\t\tnnz = cmscsm->nnz;\n\t\tkb = cmscsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_tr = false;\n\t\tcmsm = build_cm_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\t\tnnz = cmsm->nnz;\n\t\tkb = cmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_tr?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\t// for soln, we just use init (since we are free to modify/delete this vector)\n\t// we also report the memory usage of this vector here, even though it has already been created\n\tsoln = init;\n\tsoln2 = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 2*kb;\n\tPN_PrintMemoryToMainLog(env, \"[2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 0; iters < time && !done; iters++) {\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *col_counts;\n\t\tint *col_starts;\n\t\tbool use_counts;\n\t\tunsigned int *rows;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_tr) {\n\t\t\tnon_zeros = cmsm->non_zeros;\n\t\t\tcol_counts = cmsm->col_counts;\n\t\t\tcol_starts = (int *)cmsm->col_counts;\n\t\t\tuse_counts = cmsm->use_counts;\n\t\t\trows = cmsm->rows;\n\t\t} else {\n\t\t\tcol_counts = cmscsm->col_counts;\n\t\t\tcol_starts = (int *)cmscsm->col_counts;\n\t\t\tuse_counts = cmscsm->use_counts;\n\t\t\trows = cmscsm->rows;\n\t\t\tdist = cmscsm->dist;\n\t\t\tdist_shift = cmscsm->dist_shift;\n\t\t\tdist_mask = cmscsm->dist_mask;\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td = 0.0;\n\t\t\tif (!use_counts) { l = col_starts[i]; h = col_starts[i+1]; }\n\t\t\telse { l = h; h += col_counts[i]; }\n\t\t\t// \"column major\" version\n\t\t\tif (!compact_tr) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += non_zeros[j] * soln[rows[j]];\n\t\t\t\t}\n\t\t\t// \"compact msc\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += dist[(int)(rows[j] & dist_mask)] * soln[(int)(rows[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) {\n\t\t\tmeasure.reset();\n\t\t\tmeasure.measure(soln, soln2, n);\n\t\t\tif (measure.value() < term_crit_param) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d (of %d): \", iters, (int)time);\n\t\t\tif (do_ss_detect) PN_PrintToMainLog(env, \"max %sdiff=%f, \", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (done) PN_PrintToMainLog(env, \"\\nSteady state detected at iteration %d\\n\", iters);\n\tPN_PrintToMainLog(env, \"\\nIterative method: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (cmsm) delete cmsm;\n\tif (cmscsm) delete cmscsm;\n\tif (soln2) delete[] soln2;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ProbUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1ProbUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m\t// 'maybe' states\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL, *b = NULL, *tmp = NULL;\n\t// vectors\n\tdouble *soln = NULL;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp = DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// build b\n\tCudd_Ref(yes);\n\tb = yes;\n\t\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, 1.0)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, lin_eq_method_param)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(b), false, false, lin_eq_method_param, false)); break;\n\t\tdefault:\n\t\t\tPN_SetErrorMessage(\"Pseudo Gauss-Seidel/SOR methods are currently not supported by the sparse engine\"); return 0;\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (b) Cudd_RecursiveDeref(ddman, b);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_ProbUntilInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"IntervalIteration.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1ProbUntilInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer t,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer y,\t// 'yes' states\njlong __jlongpointer m,\t// 'maybe' states\njint flags\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(t);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od); \t\t// reachable states\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(y);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(m);\t\t// 'maybe' states\n\n\t// mtbdds\n\tDdNode *reach = NULL, *a = NULL, *b = NULL, *lower = NULL, *upper = NULL, *tmp = NULL;\n\t// vectors\n\tdouble *soln = NULL;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// filter out rows\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\ta = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// subtract a from identity (unless we are going to solve with the power method)\n\tif (lin_eq_method != LIN_EQ_METHOD_POWER) {\n\t\ttmp = DD_Identity(ddman, rvars, cvars, num_rvars);\n\t\tCudd_Ref(reach);\n\t\ttmp = DD_And(ddman, tmp, reach);\n\t\ta = DD_Apply(ddman, APPLY_MINUS, tmp, a);\n\t}\n\t\n\t// build b\n\tCudd_Ref(yes);\n\tb = yes;\n\t// lower bounds = b\n\tCudd_Ref(b);\n\tlower = b;\n\n\t// build upper (yes and maybe = 1)\n\tCudd_Ref(yes);\n\tCudd_Ref(maybe);\n\tupper = DD_Or(ddman, yes, maybe);\n\n\tIntervalIteration helper(flags);\n\tif (!helper.flag_ensure_monotonic_from_above()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from above.\\n\");\n\t}\n\tif (!helper.flag_ensure_monotonic_from_below()) {\n\t\tPN_PrintToMainLog(env, \"Note: Interval iteration is configured to not enforce monotonicity from below.\\n\");\n\t}\n\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1PowerInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, flags)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, flags)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, 1.0, false, flags)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, flags)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, true, flags)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SORInterval(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), ptr_to_jlong(b), ptr_to_jlong(lower), ptr_to_jlong(upper), false, false, lin_eq_method_param, false, flags)); break;\n\t\tdefault:\n\t\t\tPN_SetErrorMessage(\"Pseudo Gauss-Seidel/SOR methods are currently not supported by the sparse engine\"); return 0;\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (b) Cudd_RecursiveDeref(ddman, b);\n\tif (lower) Cudd_RecursiveDeref(ddman, lower);\n\tif (upper) Cudd_RecursiveDeref(ddman, upper);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_SOR.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include <memory>\n#include <new>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Gauss-Seidel/SOR\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1SOR\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _init,\t// init soln\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble omega,\t\t// omega (over-relaxation parameter)\njboolean forwards\t// forwards or backwards?\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *init = jlong_to_DdNode(_init);\t\t// init soln\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_a, compact_d, compact_b;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *diags_vec = NULL, *b_vec = NULL, *soln = NULL;\n\tDistVector *diags_dist = NULL, *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, fb, l, h, iters;\n\tdouble d, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_a = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_a = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_a?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = compact_a ? cmsr_negative_row_sums(cmsrsm, transpose) : rm_negative_row_sums(rmsm, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vector... \");\n\tsoln = mtbdd_to_double_vector(ddman, init, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += kb;\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PS_SOR (\");\n\t\ttitle += forwards?\"\":\"Backwards \";\n\t\ttitle += (omega == 1.0)?\"Gauss-Seidel\":(\"SOR omega=\" + std::to_string(omega));\n\t\ttitle += \")\";\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln, n, 0);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\tmeasure.reset();\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_a) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply\n\t\tl = nnz; h = 0;\n\t\tfor (fb = 0; fb < n; fb++) {\n\t\t\t\n\t\t\t// loop actually over i\n\t\t\t// (can do forwards or backwards sor/gs)\n\t\t\ti = (forwards) ? fb : n-1-fb;\n\t\t\t\n\t\t\td = (b == NULL) ? 0.0 : ((!compact_b) ? b_vec[i] : b_dist->dist[b_dist->ptrs[i]]);\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse if (forwards) { l = h; h += row_counts[i]; }\n\t\t\telse { h = l; l -= row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_a) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td -= non_zeros[j] * soln[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td -= dist[(int)(cols[j] & dist_mask)] * soln[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// divide by diagonal (multiply by inverted diagonal)\n\t\t\tif (!compact_d) d *= diags_vec[i]; else d *= diags_dist->dist[diags_dist->ptrs[i]];\n\t\t\t// over-relaxation\n\t\t\tif (omega != 1.0) {\n\t\t\t\td = ((1-omega) * soln[i]) + (omega * d);\n\t\t\t}\n\t\t\t// compute norm for convergence\n\t\t\t// (note we must do this inside the loop because we only store one vector for sor/gauss-seidel)\n\t\t\tmeasure.measure(soln[i], d);\n\t\t\t// set vector element\n\t\t\tsoln[i] = d;\n\t\t}\n\n\t\tif (iterationExport)\n\t\t\titerationExport->exportVector(soln, n, 0);\n\n\t\t// check convergence\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tdone = true;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s%s: %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", forwards?\"\":\"Backwards \", (omega == 1.0)?\"Gauss-Seidel\":\"SOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) { delete[] soln; soln = NULL; PN_SetErrorMessage(\"Iterative method did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters); }\n\t\n\t// the difference between vector values is not a reliable error bound\n\t// but we store it anyway in case it is useful for estimating a bound\n\tlast_error_bound = measure.value();\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_SORInterval.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include \"ExportIterations.h\"\n#include \"IntervalIteration.h\"\n#include <memory>\n#include <new>\n\n//------------------------------------------------------------------------------\n\n// solve the linear equation system Ax=b with Gauss-Seidel/SOR, interval variant\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1SORInterval\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer _odd,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer _a,\t// matrix A\njlong __jlongpointer _b,\t// vector b (if null, assume all zero)\njlong __jlongpointer _lower,\t// lower bound values\njlong __jlongpointer _upper,\t// upper bound values\njboolean transpose,\t// transpose A? (i.e. solve xA=b not Ax=b?)\njboolean row_sums,\t// use row sums for diags instead? (strictly speaking: negative sum of non-diagonal row elements)\njdouble omega,\t\t// omega (over-relaxation parameter)\njboolean forwards,\t// forwards or backwards?\njint flags\n)\n{\n\t// cast function parameters\n\tODDNode *odd = jlong_to_ODDNode(_odd);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv); \t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv); \t// col vars\n\tDdNode *a = jlong_to_DdNode(_a);\t\t// matrix A\n\tDdNode *b = jlong_to_DdNode(_b);\t\t// vector b\n\tDdNode *lower = jlong_to_DdNode(_lower);\t\t// lower bound values\n\tDdNode *upper = jlong_to_DdNode(_upper);\t\t// upper bound values\n\n\t// mtbdds\n\tDdNode *reach = NULL, *diags = NULL, *id = NULL;\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_a, compact_d, compact_b;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *diags_vec = NULL, *b_vec = NULL, *soln_below = NULL, *soln_above = NULL;\n\tDistVector *diags_dist = NULL, *b_dist = NULL;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tint i, j, fb, l, h, iters;\n\tdouble d_below, d_above, kb, kbt;\n\tbool done;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\n\tif (omega <= 0.0 || omega > 1.0) {\n\t\tPN_SetErrorMessage(\"Interval iteration requires 0 < omega <= 1.0, have omega = %g\", omega);\n\t\treturn ptr_to_jlong(NULL);\n\t}\n\n\tIntervalIteration helper(flags);\n\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// get reachable states\n\treach = odd->dd;\n\t\n\t// make local copy of a\n\tCudd_Ref(a);\n\t\n\t// remove and keep diagonal entries of matrix A\n\tid =  DD_Identity(ddman, rvars, cvars, num_rvars);\n\tCudd_Ref(reach);\n\tid = DD_And(ddman, id, reach);\n\tCudd_Ref(id);\n\tCudd_Ref(a);\n\tdiags = DD_Apply(ddman, APPLY_TIMES, id, a);\n\tCudd_Ref(id);\n\ta = DD_ITE(ddman, id, DD_Constant(ddman, 0), a);\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_a = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_a = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, a, rvars, cvars, num_rvars, odd, transpose);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_a?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diags, either by extracting from mtbdd or\n\t// by doing (negative, non-diagonal) row sums of original A matrix\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tif (!row_sums) {\n\t\tdiags = DD_MaxAbstract(ddman, diags, cvars, num_cvars);\n\t\tdiags_vec = mtbdd_to_double_vector(ddman, diags, rvars, num_rvars, odd);\n\t} else {\n\t\tdiags_vec = compact_a ? cmsr_negative_row_sums(cmsrsm, transpose) : rm_negative_row_sums(rmsm, transpose);\n\t}\n\t// if any of the diagonals are zero, set them to one - avoids division by zero errors later\n\t// strictly speaking, such matrices shouldn't work for this iterative method\n\t// but they do occur, e.g. for steady-state computation of a bscc, this fixes it\n\tfor (i = 0; i < n; i++) diags_vec[i] = (diags_vec[i] == 0) ? 1.0 : diags_vec[i];\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags_vec, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete diags_vec; diags_vec = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// invert diagonal\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags_vec[i] = 1.0 / diags_vec[i];\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = 1.0 / diags_dist->dist[i];\n\t}\n\t\n\t// build b vector (if present)\n\tif (b != NULL) {\n\t\tPN_PrintToMainLog(env, \"Creating vector for RHS... \");\n\t\tb_vec = mtbdd_to_double_vector(ddman, b, rvars, num_rvars, odd);\n\t\t// try and convert to compact form if required\n\t\tcompact_b = false;\n\t\tif (compact) {\n\t\t\tif ((b_dist = double_vector_to_dist(b_vec, n))) {\n\t\t\t\tcompact_b = true;\n\t\t\t\tdelete b_vec; b_vec = NULL;\n\t\t\t}\n\t\t}\n\t\tkb = (!compact_b) ? n*8.0/1024.0 : (b_dist->num_dist*8.0+n*2.0)/1024.0;\n\t\tkbt += kb;\n\t\tif (compact_b) PN_PrintToMainLog(env, \"[dist=%d, compact] \", b_dist->num_dist);\n\t\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln_below = mtbdd_to_double_vector(ddman, lower, rvars, num_rvars, odd);\n\tsoln_above = mtbdd_to_double_vector(ddman, upper, rvars, num_rvars, odd);\n\tkb = n*8.0/1024.0;\n\tkbt += 2 * kb;\n\tPN_PrintMemoryToMainLog(env, \"[ 2 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\n\tstd::unique_ptr<ExportIterations> iterationExport;\n\tif (PN_GetFlagExportIterations()) {\n\t\tstd::string title(\"PS_SOR (\");\n\t\ttitle += forwards?\"\":\"Backwards \";\n\t\ttitle += (omega == 1.0)?\"Gauss-Seidel\":(\"SOR omega=\" + std::to_string(omega));\n\t\ttitle += \"), interval\";\n\t\titerationExport.reset(new ExportIterations(title.c_str()));\n\t\tPN_PrintToMainLog(env, \"Exporting iterations to %s\\n\", iterationExport->getFileName().c_str());\n\t\titerationExport->exportVector(soln_below, n, 0);\n\t\titerationExport->exportVector(soln_above, n, 1);\n\t}\n\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start iterations\n\titers = 0;\n\tdone = false;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\twhile (!done && iters < max_iters) {\n\t\t\n\t\titers++;\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_a) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// matrix multiply (below and above simultaneously)\n\t\tl = nnz; h = 0;\n\t\tfor (fb = 0; fb < n; fb++) {\n\t\t\t\n\t\t\t// loop actually over i\n\t\t\t// (can do forwards or backwards sor/gs)\n\t\t\ti = (forwards) ? fb : n-1-fb;\n\t\t\t\n\t\t\td_below = (b == NULL) ? 0.0 : ((!compact_b) ? b_vec[i] : b_dist->dist[b_dist->ptrs[i]]);\n\t\t\td_above = d_below;\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse if (forwards) { l = h; h += row_counts[i]; }\n\t\t\telse { h = l; l -= row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_a) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td_below -= non_zeros[j] * soln_below[cols[j]];\n\t\t\t\t\td_above -= non_zeros[j] * soln_above[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td_below -= dist[(int)(cols[j] & dist_mask)] * soln_below[(int)(cols[j] >> dist_shift)];\n\t\t\t\t\td_above -= dist[(int)(cols[j] & dist_mask)] * soln_above[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// divide by diagonal (multiply by inverted diagonal)\n\t\t\tif (!compact_d) d_below *= diags_vec[i]; else d_below *= diags_dist->dist[diags_dist->ptrs[i]];\n\t\t\tif (!compact_d) d_above *= diags_vec[i]; else d_above *= diags_dist->dist[diags_dist->ptrs[i]];\n\t\t\t// over-relaxation\n\t\t\tif (omega != 1.0) {\n\t\t\t\td_below = ((1-omega) * soln_below[i]) + (omega * d_below);\n\t\t\t\td_above = ((1-omega) * soln_above[i]) + (omega * d_above);\n\t\t\t}\n\t\t\t// set vector element\n\t\t\thelper.updateValueFromBelow(soln_below[i], soln_below[i], d_below);\n\t\t\thelper.updateValueFromAbove(soln_above[i], soln_above[i], d_above);\n\t\t}\n\n\t\tif (iterationExport) {\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_above, n, 1);\n\t\t}\n\n\t\t// check convergence\n\t\tmeasure.reset();\n\t\tmeasure.measure(soln_below, soln_above, n);\n\t\tif (measure.value() < term_crit_param) {\n\t\t\tPN_PrintToMainLog(env, \"Max %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tdone = true;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %d: max %sdiff=%f\", iters, measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \", %.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tPN_PrintToMainLog(env, \"\\n%s%s (interval iteration): %d iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", forwards?\"\":\"Backwards \", (omega == 1.0)?\"Gauss-Seidel\":\"SOR\", iters, time_taken, time_for_iters/iters, time_for_setup);\n\t\n\t// if the iterative method didn't terminate, this is an error\n\tif (!done) {\n\t\tdelete[] soln_below;\n\t\tsoln_below = NULL;\n\t\tPN_SetErrorMessage(\"Iterative method (interval iteration) did not converge within %d iterations.\\nConsider using a different numerical method or increasing the maximum number of iterations\", iters);\n\t\tPN_PrintToMainLog(env, \"Max remaining %sdiff between upper and lower bound on convergence: %G\", measure.isRelative()?\"relative \":\"\", measure.value());\n\t}\n\n\tif (helper.flag_select_midpoint() && soln_below) { // we did converge, select midpoint\n\t\tlast_error_bound = measure.value();\n\t\thelper.selectMidpoint(soln_below, soln_above, n);\n\n\t\tif (iterationExport) {\n\t\t\t// export result vector as below and above\n\t\t\titerationExport->exportVector(soln_below, n, 0);\n\t\t\titerationExport->exportVector(soln_below, n, 1);\n\t\t}\n\t}\n\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln_below) delete[] soln_below;\n\t\tsoln_below = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\tif (id) Cudd_RecursiveDeref(ddman, id);\n\tif (diags) Cudd_RecursiveDeref(ddman, diags);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (diags_vec) delete[] diags_vec;\n\tif (diags_dist) delete diags_dist;\n\tif (b_vec) delete[] b_vec;\n\tif (b_dist) delete b_dist;\n\tif (soln_above) delete soln_above;\n\t\n\treturn ptr_to_jlong(soln_below);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_StochBoundedUntil.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include <prism.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"prism.h\"\n#include \"Measures.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1StochBoundedUntil\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njlong __jlongpointer ye,\t// 'yes' states\njlong __jlongpointer ma,\t// 'maybe' states\njdouble time,\t\t// time bound\njlong __jlongpointer mu\t// probs for multiplying\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\tDdNode *yes = jlong_to_DdNode(ye);\t\t// 'yes' states\n\tDdNode *maybe = jlong_to_DdNode(ma);\t\t// 'maybe' states\n\tdouble *mult = jlong_to_double(mu);\t\t// probs for multiplying\n\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// mtbdds\t\n\tDdNode *r = NULL;\n\t// flags\n\tbool compact_tr, compact_d;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *diags = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL, *sum = NULL;\n\tDistVector *diags_dist = NULL;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint j, l, h;\n\tlong i, iters, num_iters;\n\tdouble d, x, max_diag, weight, kb, kbt, unif, term_crit_param_unif;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// count number of states to be made absorbing\n\tx = DD_GetNumMinterms(ddman, maybe, num_rvars);\n\tPN_PrintToMainLog(env, \"\\nNumber of non-absorbing states: %.0f of %d (%.1f%%)\\n\", x,  n, 100.0*(x/n));\n\t\n\t// filter out rows from rate matrix\n\tCudd_Ref(trans);\n\tCudd_Ref(maybe);\n\tr = DD_Apply(ddman, APPLY_TIMES, trans, maybe);\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_tr = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, r, rvars, cvars, num_rvars, odd);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_tr = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, r, rvars, cvars, num_rvars, odd);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_tr?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diagonals\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tdiags = compact_tr ? cmsr_negative_row_sums(cmsrsm) : rm_negative_row_sums(rmsm);\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete diags; diags = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// find max diagonal element\n\tif (!compact_d) {\n\t\tmax_diag = diags[0];\n\t\tfor (i = 1; i < n; i++) if (diags[i] < max_diag) max_diag = diags[i];\n\t} else {\n\t\tmax_diag = diags_dist->dist[0];\n\t\tfor (i = 1; i < diags_dist->num_dist; i++) if (diags_dist->dist[i] < max_diag) max_diag = diags_dist->dist[i];\n\t}\n\tmax_diag = -max_diag;\n\t\n\t// constant for uniformization\n\tunif = 1.02*max_diag;\n\t\n\t// modify diagonals\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags[i] = diags[i] / unif + 1;\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = diags_dist->dist[i] / unif + 1;\n\t}\n\t\n\t// uniformization\n\tif (!compact_tr) {\n\t\tfor (i = 0; i < nnz; i++) rmsm->non_zeros[i] /= unif;\n\t} else {\n\t\tfor (i = 0; i < cmsrsm->dist_num; i++) cmsrsm->dist[i] /= unif;\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\tsoln = mtbdd_to_double_vector(ddman, yes, rvars, num_rvars, odd);\n\tsoln2 = new double[n];\n\tsum = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// multiply initial solution by 'mult' probs\n\tif (mult != NULL) {\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln[i] *= mult[i];\n\t\t}\n\t}\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) throw \"Overflow in Fox-Glynn computation (time bound too big?)\";\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n\t// set up vectors\n\tfor (i = 0; i < n; i++) {\n\t\tsum[i] = 0.0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start transient analysis\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// if necessary, do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) for (i = 0; i < n; i++) {\n\t\tsum[i] += fgw.weights[0] * soln[i];\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_tr) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td = (!compact_d) ? (diags[i] * soln[i]) : (diags_dist->dist[diags_dist->ptrs[i]] * soln[i]);\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_tr) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += non_zeros[j] * soln[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += dist[(int)(cols[j] & dist_mask)] * soln[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) {\n\t\t\tmeasure.reset();\n\t\t\tmeasure.measure(soln, soln2, n);\n\t\t\tif (measure.value() < term_crit_param_unif) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = 1.0;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tfor (i = 0; i < n; i++) sum[i] += weight * soln2[i];\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tif (do_ss_detect) PN_PrintToMainLog(env, \"max %sdiff=%f, \", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t\t\n\t\t// add to sum\n\t\tif (iters >= fgw.left) {\n\t\t\tfor (i = 0; i < n; i++) sum[i] += fgw.weights[iters-fgw.left] * soln[i];\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t} catch (const char *err) {\n\t\tPN_SetErrorMessage(\"%s\", err);\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t}\n\t\n\t// free memory\n\tif (r) Cudd_RecursiveDeref(ddman, r);\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (diags) delete[] diags;\n\tif (diags_dist) delete diags_dist;\n\tif (soln) delete[] soln;\n\tif (soln2) delete[] soln2;\n\tif (fgw.weights) delete[] fgw.weights;\n\t\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_StochCumulReward.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include <prism.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1StochCumulReward\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer sr,\t// state rewards\njlong __jlongpointer trr,\t// transition rewards\njlong __jlongpointer od,\t// odd\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njdouble time\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tDdNode *state_rewards = jlong_to_DdNode(sr);\t// state rewards\n\tDdNode *trans_rewards = jlong_to_DdNode(trr);\t// transition rewards\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *tmp = NULL;\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_tr, compact_d;\n\t// sparse matrix\n\tRMSparseMatrix *rmsm = NULL;\n\tCMSRSparseMatrix *cmsrsm = NULL;\n\t// vectors\n\tdouble *diags = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL, *sum = NULL;\n\tDistVector *diags_dist = NULL;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint j, l, h;\n\tlong i, iters, num_iters;\n\tdouble d, max_diag, weight, kb, kbt, unif, term_crit_param_unif;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_tr = true;\n\tcmsrsm = NULL;\n\tif (compact) cmsrsm = build_cmsr_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\tif (cmsrsm != NULL) {\n\t\tnnz = cmsrsm->nnz;\n\t\tkb = cmsrsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_tr = false;\n\t\trmsm = build_rm_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\t\tnnz = rmsm->nnz;\n\t\tkb = rmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_tr?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diagonals\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tdiags = compact_tr ? cmsr_negative_row_sums(cmsrsm) : rm_negative_row_sums(rmsm);\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete diags; diags = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// find max diagonal element\n\tif (!compact_d) {\n\t\tmax_diag = diags[0];\n\t\tfor (i = 1; i < n; i++) if (diags[i] < max_diag) max_diag = diags[i];\n\t} else {\n\t\tmax_diag = diags_dist->dist[0];\n\t\tfor (i = 1; i < diags_dist->num_dist; i++) if (diags_dist->dist[i] < max_diag) max_diag = diags_dist->dist[i];\n\t}\n\tmax_diag = -max_diag;\n\t\n\t// constant for uniformization\n\tunif = 1.02*max_diag;\n\t\n\t// modify diagonals\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags[i] = diags[i] / unif + 1;\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = diags_dist->dist[i] / unif + 1;\n\t}\n\t\n\t// uniformization\n\tif (!compact_tr) {\n\t\tfor (i = 0; i < nnz; i++) rmsm->non_zeros[i] /= unif;\n\t} else {\n\t\tfor (i = 0; i < cmsrsm->dist_num; i++) cmsrsm->dist[i] /= unif;\n\t}\n\t\n\t// combine state/transition rewards into a single vector\n\t// new state rewards = c + (R.C)1\n\t// first, multiply transition rates by transition rewards and sum rows\n\t// = (R.C)1\n\tCudd_Ref(trans);\n\tCudd_Ref(trans_rewards);\n\ttmp = DD_Apply(ddman, APPLY_TIMES, trans, trans_rewards);\n\ttmp = DD_SumAbstract(ddman, tmp, cvars, num_cvars);\n\t// then add state rewards\n\t// = c + (R.C)1\n\tCudd_Ref(state_rewards);\n\ttmp = DD_Apply(ddman, APPLY_PLUS, tmp, state_rewards);\n\tsoln = mtbdd_to_double_vector(ddman, tmp, rvars, num_rvars, odd);\n\tCudd_RecursiveDeref(ddman, tmp);\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\t// soln has already been created and initialised to rewards vector as required\n\t// need to create soln2 and sum\n\tsoln2 = new double[n];\n\tsum = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) throw \"Overflow in Fox-Glynn computation (time bound too big?)\";\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n\t// modify the poisson probabilities to what we need for this computation\n\t// first make the kth value equal to the sum of the values for 0...k\n\tfor (i = fgw.left+1; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] += fgw.weights[i-1-fgw.left];\n\t}\n\t// then subtract from 1 and divide by uniformisation constant (q) to give mixed poisson probabilities\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] = (1 - fgw.weights[i-fgw.left]) / unif;\n\t}\n\t\n\t// set up vectors\n\tfor (i = 0; i < n; i++) {\n\t\tsum[i] = 0.0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start transient analysis\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) {\n\t\tfor (i = 0; i < n; i++) sum[i] += fgw.weights[0] * soln[i];\n\t} else {\n\t\tfor (i = 0; i < n; i++) sum[i] += soln[i] / unif;\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *row_counts;\n\t\tint *row_starts;\n\t\tbool use_counts;\n\t\tunsigned int *cols;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_tr) {\n\t\t\tnon_zeros = rmsm->non_zeros;\n\t\t\trow_counts = rmsm->row_counts;\n\t\t\trow_starts = (int *)rmsm->row_counts;\n\t\t\tuse_counts = rmsm->use_counts;\n\t\t\tcols = rmsm->cols;\n\t\t} else {\n\t\t\trow_counts = cmsrsm->row_counts;\n\t\t\trow_starts = (int *)cmsrsm->row_counts;\n\t\t\tuse_counts = cmsrsm->use_counts;\n\t\t\tcols = cmsrsm->cols;\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_shift = cmsrsm->dist_shift;\n\t\t\tdist_mask = cmsrsm->dist_mask;\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td = (!compact_d) ? (diags[i] * soln[i]) : (diags_dist->dist[diags_dist->ptrs[i]] * soln[i]);\n\t\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\t\telse { l = h; h += row_counts[i]; }\n\t\t\t// \"row major\" version\n\t\t\tif (!compact_tr) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += non_zeros[j] * soln[cols[j]];\n\t\t\t\t}\n\t\t\t// \"compact msr\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += dist[(int)(cols[j] & dist_mask)] * soln[(int)(cols[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) {\n\t\t\tmeasure.reset();\n\t\t\tmeasure.measure(soln, soln2, n);\n\t\t\tif (measure.value() < term_crit_param_unif) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = time - iters/unif;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tfor (i = 0; i < n; i++) sum[i] += weight * soln2[i];\n\t\t\t\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tif (do_ss_detect) PN_PrintToMainLog(env, \"max %sdiff=%f, \", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t\t\n\t\t// add to sum\n\t\tif (iters < fgw.left) {\n\t\t\tfor (i = 0; i < n; i++) sum[i] += soln[i] / unif;\n\t\t} else {\n\t\t\tfor (i = 0; i < n; i++) sum[i] += fgw.weights[iters-fgw.left] * soln[i];\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t} catch (const char *err) {\n\t\tPN_SetErrorMessage(\"%s\", err);\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t}\n\t\n\t// free memory\n\tif (rmsm) delete rmsm;\n\tif (cmsrsm) delete cmsrsm;\n\tif (diags) delete[] diags;\n\tif (diags_dist) delete diags_dist;\n\tif (soln) delete[] soln;\n\tif (soln2) delete[] soln2;\n\tif (fgw.weights) delete[] fgw.weights;\n\t\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_StochSteadyState.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1StochSteadyState\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t\t// trans matrix\njlong __jlongpointer od,\t\t// odd\njlong __jlongpointer in,\t\t// init soln\njlong __jlongpointer rv,\t\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t\t// col vars\njint num_cvars\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tDdNode *init = jlong_to_DdNode(in);\t\t// init soln\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// mtbdds\n\tDdNode *diags = NULL, *q = NULL, *a = NULL, *tmp = NULL;\n\t// model stats\n\tint n;\n\t// vectors\n\tdouble *soln = NULL;\n\t// misc\n\tint i;\n\tdouble deltat, d;\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// if we are going to solve with the power method, we have to modify the matrix a bit\n\tif (lin_eq_method == LIN_EQ_METHOD_POWER) {\n\t\t\n\t\t// technically, this is a little bit wasteful\n\t\t// for sparse/hybrid, we can avoid constructing the diagonals and rate matrix as mtbdds\n\t\t// (as used to be done in version <=2.1 before the power method was generic)\n\t\t// shouldn't be too disasterous though\n\t\t// and if you are that bothered about efficiency, you won't be using the power method anyway...\n\t\t\n\t\t// compute diagonals\n\t\tCudd_Ref(trans);\n\t\tdiags = DD_SumAbstract(ddman, trans, cvars, num_rvars);\n\t\tdiags = DD_Apply(ddman, APPLY_TIMES, diags, DD_Constant(ddman, -1));\n\t\t\n\t\t// choose deltat\n\t\tdeltat = -0.99 / DD_FindMin(ddman, diags);\n\t\t\n\t\t// build generator matrix q from trans and diags\n\t\t// note that any self loops are effectively removed because we include their rates\n\t\t// in the 'diags' row sums and then subtract these from the original rate matrix\n\t\tCudd_Ref(trans);\n\t\tCudd_Ref(diags);\n\t\tq = DD_Apply(ddman, APPLY_PLUS, trans, DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), diags));\n\t\t\n\t\t// build iteration matrix\n\t\tPN_PrintToMainLog(env, \"\\nBuilding power method iteration matrix MTBDD... \");\n\t\t// (includes a \"fix\" for when we are solving a subsystem e.g. BSCC)\n\t\t// (although i don't think we actually need this for the power method)\n\t\tCudd_Ref(diags);\n\t\ttmp = DD_LessThan(ddman, diags, 0);\n\t\tCudd_Ref(q);\n\t\ta = DD_Apply(ddman, APPLY_PLUS, DD_Apply(ddman, APPLY_TIMES, DD_Constant(ddman, deltat), q), DD_Apply(ddman, APPLY_TIMES, DD_Identity(ddman, rvars, cvars, num_rvars), tmp));\n\t\ti = DD_GetNumNodes(ddman, a);\n\t\tPN_PrintToMainLog(env, \"[nodes=%d] [%.1f Kb]\", i, i*20.0/1024.0);\n\t\t\n\t\t// deref unneeded mtbdds\n\t\tCudd_RecursiveDeref(ddman, diags);\n\t\tCudd_RecursiveDeref(ddman, q);\n\t}\n\telse {\n\t\t// technically, we should remove self loops (i.e. diagonals) from the rate matrix\n\t\t// but the iterative solution methods remove all diagonals before doing\n\t\t// solution (and before doing row sums) so we don't need to bother\n\t\tCudd_Ref(trans);\n\t\ta = trans;\n\t}\n\t\n\t// call iterative method\n\tsoln = NULL;\n\tswitch (lin_eq_method) {\n\t\tcase LIN_EQ_METHOD_POWER:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1Power(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true)); break;\n\t\tcase LIN_EQ_METHOD_JACOBI:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, 1.0)); break;\n\t\tcase LIN_EQ_METHOD_GAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, 1.0, true)); break;\n\t\tcase LIN_EQ_METHOD_BGAUSSSEIDEL:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, 1.0, false)); break;\n\t\tcase LIN_EQ_METHOD_JOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1JOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, lin_eq_method_param)); break;\n\t\tcase LIN_EQ_METHOD_SOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, lin_eq_method_param, true)); break;\n\t\tcase LIN_EQ_METHOD_BSOR:\n\t\t\tsoln = jlong_to_double(Java_sparse_PrismSparse_PS_1SOR(env, cls, ptr_to_jlong(odd), ptr_to_jlong(rvars), num_rvars, ptr_to_jlong(cvars), num_cvars, ptr_to_jlong(a), 0, ptr_to_jlong(init), true, true, lin_eq_method_param, false)); break;\n\t\tdefault:\n\t\t\tPN_SetErrorMessage(\"Pseudo Gauss-Seidel/SOR methods are currently not supported by the sparse engine\"); return 0;\n\t}\n\t\n\t// normalise\n\tif (soln != NULL) {\n\t\td = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td += soln[i];\n\t\t}\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tsoln[i] /= d;\n\t\t}\n\t}\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (soln) delete[] soln;\n\t\tsoln = 0;\n\t}\n\t\n\t// free memory\n\tif (a) Cudd_RecursiveDeref(ddman, a);\n\t\n\treturn ptr_to_jlong(soln);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PS_StochTransient.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n// includes\n#include \"PrismSparse.h\"\n#include <cmath>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include <odd.h>\n#include <dv.h>\n#include <prism.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n#include \"Measures.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_PrismSparse_PS_1StochTransient\n(\nJNIEnv *env,\njclass cls,\njlong __jlongpointer tr,\t// trans matrix\njlong __jlongpointer od,\t// odd\njlong __jlongpointer in,\t// initial distribution (note: this will be deleted afterwards)\njlong __jlongpointer rv,\t// row vars\njint num_rvars,\njlong __jlongpointer cv,\t// col vars\njint num_cvars,\njdouble time\t\t// time bound\n)\n{\n\t// cast function parameters\n\tDdNode *trans = jlong_to_DdNode(tr);\t\t// trans matrix\n\tODDNode *odd = jlong_to_ODDNode(od);\t\t// odd\n\tdouble *init = jlong_to_double(in);\t\t\t// initial distribution\n\tDdNode **rvars = jlong_to_DdNode_array(rv);\t// row vars\n\tDdNode **cvars = jlong_to_DdNode_array(cv);\t// col vars\n\n\t// model stats\n\tint n;\n\tlong nnz;\n\t// flags\n\tbool compact_tr, compact_d;\n\t// sparse matrix\n\tCMSparseMatrix *cmsm = NULL;\n\tCMSCSparseMatrix *cmscsm = NULL;\n\t// vectors\n\tdouble *diags = NULL, *soln = NULL, *soln2 = NULL, *tmpsoln = NULL, *sum = NULL;\n\tDistVector *diags_dist = NULL;\n\t// fox glynn stuff\n\tFoxGlynnWeights fgw;\n\t// timing stuff\n\tlong start1, start2, start3, stop;\n\tdouble time_taken, time_for_setup, time_for_iters;\n\t// misc\n\tbool done;\n\tint j, l, h;\n\tlong i, iters, num_iters;\n\tdouble d, max_diag, weight, kb, kbt, unif, term_crit_param_unif;\n\t// measure for convergence termination check\n\tMeasureSupNorm measure(term_crit == TERM_CRIT_RELATIVE);\n\t\n\t// exception handling around whole function\n\ttry {\n\t\n\t// start clocks\t\n\tstart1 = start2 = util_cpu_time();\n\t\n\t// get number of states\n\tn = odd->eoff + odd->toff;\n\t\n\t// build sparse matrix\n\tPN_PrintToMainLog(env, \"\\nBuilding sparse matrix... \");\n\t// if requested, try and build a \"compact\" version\n\tcompact_tr = true;\n\tcmscsm = NULL;\n\tif (compact) cmscsm = build_cmsc_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\tif (cmscsm != NULL) {\n\t\tnnz = cmscsm->nnz;\n\t\tkb = cmscsm->mem;\n\t}\n\t// if not or if it wasn't possible, built a normal one\n\telse {\n\t\tcompact_tr = false;\n\t\tcmsm = build_cm_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, odd);\n\t\tnnz = cmsm->nnz;\n\t\tkb = cmsm->mem;\n\t}\n\tkbt = kb;\n\t// print some info\n\tPN_PrintToMainLog(env, \"[n=%d, nnz=%ld%s] \", n, nnz, compact_tr?\", compact\":\"\");\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// get vector of diagonals\n\tPN_PrintToMainLog(env, \"Creating vector for diagonals... \");\n\tdiags = compact_tr ? cmsc_negative_row_sums(cmscsm) : cm_negative_row_sums(cmsm);\n\t// try and convert to compact form if required\n\tcompact_d = false;\n\tif (compact) {\n\t\tif ((diags_dist = double_vector_to_dist(diags, n))) {\n\t\t\tcompact_d = true;\n\t\t\tdelete diags; diags = NULL;\n\t\t}\n\t}\n\tkb = (!compact_d) ? n*8.0/1024.0 : (diags_dist->num_dist*8.0+n*2.0)/1024.0;\n\tkbt += kb;\n\tif (compact_d) PN_PrintToMainLog(env, \"[dist=%d, compact] \", diags_dist->num_dist);\n\tPN_PrintMemoryToMainLog(env, \"[\", kb, \"]\\n\");\n\t\n\t// find max diagonal element\n\tif (!compact_d) {\n\t\tmax_diag = diags[0];\n\t\tfor (i = 1; i < n; i++) if (diags[i] < max_diag) max_diag = diags[i];\n\t} else {\n\t\tmax_diag = diags_dist->dist[0];\n\t\tfor (i = 1; i < diags_dist->num_dist; i++) if (diags_dist->dist[i] < max_diag) max_diag = diags_dist->dist[i];\n\t}\n\tmax_diag = -max_diag;\n\t\n\t// constant for uniformization\n\tunif = 1.02*max_diag;\n\t\n\t// modify diagonals\n\tif (!compact_d) {\n\t\tfor (i = 0; i < n; i++) diags[i] = diags[i] / unif + 1;\n\t} else {\n\t\tfor (i = 0; i < diags_dist->num_dist; i++) diags_dist->dist[i] = diags_dist->dist[i] / unif + 1;\n\t}\n\t\n\t// uniformization\n\tif (!compact_tr) {\n\t\tfor (i = 0; i < nnz; i++) cmsm->non_zeros[i] /= unif;\n\t} else {\n\t\tfor (i = 0; i < cmscsm->dist_num; i++) cmscsm->dist[i] /= unif;\n\t}\n\t\n\t// create solution/iteration vectors\n\tPN_PrintToMainLog(env, \"Allocating iteration vectors... \");\n\t// for soln, we just use init (since we are free to modify/delete this vector)\n\t// we also report the memory usage of this vector here, even though it has already been created\n\tsoln = init;\n\tsoln2 = new double[n];\n\tsum = new double[n];\n\tkb = n*8.0/1024.0;\n\tkbt += 3*kb;\n\tPN_PrintMemoryToMainLog(env, \"[3 x \", kb, \"]\\n\");\n\t\n\t// print total memory usage\n\tPN_PrintMemoryToMainLog(env, \"TOTAL: [\", kbt, \"]\\n\");\n\t\n\t// compute new termination criterion parameter (epsilon/8)\n\tterm_crit_param_unif = term_crit_param / 8.0;\n\t\n\t// compute poisson probabilities (fox/glynn)\n\tPN_PrintToMainLog(env, \"\\nUniformisation: q.t = %f x %f = %f\\n\", unif, time, unif * time);\n\tfgw = fox_glynn(unif * time, 1.0e-300, 1.0e+300, term_crit_param_unif);\n\tif (fgw.right < 0) throw \"Overflow in Fox-Glynn computation (time bound too big?)\";\n\tfor (i = fgw.left; i <= fgw.right; i++) {\n\t\tfgw.weights[i-fgw.left] /= fgw.total_weight;\n\t}\n\tPN_PrintToMainLog(env, \"Fox-Glynn: left = %ld, right = %ld\\n\", fgw.left, fgw.right);\n\t\n\t// set up vectors\n\tfor (i = 0; i < n; i++) {\n\t\tsum[i] = 0.0;\n\t}\n\t\n\t// get setup time\n\tstop = util_cpu_time();\n\ttime_for_setup = (double)(stop - start2)/1000;\n\tstart2 = stop;\n\tstart3 = stop;\n\t\n\t// start transient analysis\n\tdone = false;\n\tnum_iters = -1;\n\tPN_PrintToMainLog(env, \"\\nStarting iterations...\\n\");\n\t\n\t// if necessary, do 0th element of summation (doesn't require any matrix powers)\n\tif (fgw.left == 0) for (i = 0; i < n; i++) {\n\t\tsum[i] += fgw.weights[0] * soln[i];\n\t}\n\t\n\t// note that we ignore max_iters as we know how any iterations _should_ be performed\n\tfor (iters = 1; (iters <= fgw.right) && !done; iters++) {\n\t\t\n\t\t// store local copies of stuff\n\t\tdouble *non_zeros;\n\t\tunsigned char *col_counts;\n\t\tint *col_starts;\n\t\tbool use_counts;\n\t\tunsigned int *rows;\n\t\tdouble *dist;\n\t\tint dist_shift;\n\t\tint dist_mask;\n\t\tif (!compact_tr) {\n\t\t\tnon_zeros = cmsm->non_zeros;\n\t\t\tcol_counts = cmsm->col_counts;\n\t\t\tcol_starts = (int *)cmsm->col_counts;\n\t\t\tuse_counts = cmsm->use_counts;\n\t\t\trows = cmsm->rows;\n\t\t} else {\n\t\t\tcol_counts = cmscsm->col_counts;\n\t\t\tcol_starts = (int *)cmscsm->col_counts;\n\t\t\tuse_counts = cmscsm->use_counts;\n\t\t\trows = cmscsm->rows;\n\t\t\tdist = cmscsm->dist;\n\t\t\tdist_shift = cmscsm->dist_shift;\n\t\t\tdist_mask = cmscsm->dist_mask;\n\t\t}\n\t\t\n\t\t// do matrix vector multiply bit\n\t\th = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\td = (!compact_d) ? (diags[i] * soln[i]) : (diags_dist->dist[diags_dist->ptrs[i]] * soln[i]);\n\t\t\tif (!use_counts) { l = col_starts[i]; h = col_starts[i+1]; }\n\t\t\telse { l = h; h += col_counts[i]; }\n\t\t\t// \"column major\" version\n\t\t\tif (!compact_tr) {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += non_zeros[j] * soln[rows[j]];\n\t\t\t\t}\n\t\t\t// \"compact msc\" version\n\t\t\t} else {\n\t\t\t\tfor (j = l; j < h; j++) {\n\t\t\t\t\td += dist[(int)(rows[j] & dist_mask)] * soln[(int)(rows[j] >> dist_shift)];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// set vector element\n\t\t\tsoln2[i] = d;\n\t\t}\n\t\t\n\t\t// check for steady state convergence\n\t\tif (do_ss_detect) {\n\t\t\tmeasure.reset();\n\t\t\tmeasure.measure(soln, soln2, n);\n\t\t\tif (measure.value() < term_crit_param_unif) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// special case when finished early (steady-state detected)\n\t\tif (done) {\n\t\t\t// work out sum of remaining poisson probabilities\n\t\t\tif (iters <= fgw.left) {\n\t\t\t\tweight = 1.0;\n\t\t\t} else {\n\t\t\t\tweight = 0.0;\n\t\t\t\tfor (i = iters; i <= fgw.right; i++) {\n\t\t\t\t\tweight += fgw.weights[i-fgw.left];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add to sum\n\t\t\tfor (i = 0; i < n; i++) sum[i] += weight * soln2[i];\n\t\t\tPN_PrintToMainLog(env, \"\\nSteady state detected at iteration %ld\\n\", iters);\n\t\t\tnum_iters = iters;\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print occasional status update\n\t\tif ((util_cpu_time() - start3) > UPDATE_DELAY) {\n\t\t\tPN_PrintToMainLog(env, \"Iteration %ld (of %ld): \", iters, fgw.right);\n\t\t\tif (do_ss_detect) PN_PrintToMainLog(env, \"max %sdiff=%f, \", measure.isRelative()?\"relative \":\"\", measure.value());\n\t\t\tPN_PrintToMainLog(env, \"%.2f sec so far\\n\", ((double)(util_cpu_time() - start2)/1000));\n\t\t\tstart3 = util_cpu_time();\n\t\t}\n\t\t\n\t\t// prepare for next iteration\n\t\ttmpsoln = soln;\n\t\tsoln = soln2;\n\t\tsoln2 = tmpsoln;\n\t\t\n\t\t// add to sum\n\t\tif (iters >= fgw.left) {\n\t\t\tfor (i = 0; i < n; i++) sum[i] += fgw.weights[iters-fgw.left] * soln[i];\n\t\t}\n\t}\n\t\n\t// stop clocks\n\tstop = util_cpu_time();\n\ttime_for_iters = (double)(stop - start2)/1000;\n\ttime_taken = (double)(stop - start1)/1000;\n\t\n\t// print iters/timing info\n\tif (num_iters == -1) num_iters = fgw.right;\n\tPN_PrintToMainLog(env, \"\\nIterative method: %ld iterations in %.2f seconds (average %.6f, setup %.2f)\\n\", num_iters, time_taken, time_for_iters/num_iters, time_for_setup);\n\t\n\t// catch exceptions: register error, free memory\n\t} catch (std::bad_alloc e) {\n\t\tPN_SetErrorMessage(\"Out of memory\");\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t} catch (const char *err) {\n\t\tPN_SetErrorMessage(\"%s\", err);\n\t\tif (sum) delete[] sum;\n\t\tsum = 0;\n\t}\n\t\n\t// free memory\n\tif (cmscsm) delete cmscsm;\n\tif (cmsm) delete cmsm;\n\tif (diags) delete[] diags;\n\tif (diags_dist) delete diags_dist;\n\t// nb: we *do* free soln (which was originally init)\n\tif (soln) delete[] soln;\n\tif (soln2) delete[] soln2;\n\tif (fgw.weights) delete[] fgw.weights;\n\t\n\treturn ptr_to_jlong(sum);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PrismSparse.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include \"PrismSparse.h\"\n#include \"NDSparseMatrix.h\"\n#include <cstdio>\n#include <cstdarg>\n#include <climits>\n#include <util.h>\n#include <cudd.h>\n#include <dd.h>\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include \"jnipointer.h\"\n\n//------------------------------------------------------------------------------\n// Sparse matrix\n//------------------------------------------------------------------------------\n\nJNIEXPORT jint JNICALL Java_sparse_NDSparseMatrix_PS_1NDGetActionIndex\n(JNIEnv *env, jclass cls,\n jlong __jlongpointer _ndsm, // NDSparseMatrix ptr\n jint __jlongpointer s, // state index\n jint __jlongpointer i // choice index\n )\n{\n    NDSparseMatrix * ndsm = (NDSparseMatrix *) jlong_to_NDSparseMatrix(_ndsm);\n\tbool use_counts = ndsm->use_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *row_counts = ndsm->row_counts;\n\t\n\tint l1 = 0;\n\tif (!use_counts) { l1 = row_starts[s]; }\n\telse { for (int i = 0; i < s; i++) l1 += row_counts[i]; }\n\treturn ndsm->actions[l1];\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_NDSparseMatrix_PS_1BuildNDSparseMatrix\n(JNIEnv *env, jclass cls,\n jlong __jlongpointer t,    // trans\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv,  // nondet vars\n jint num_ndvars\n )\n{\n    NDSparseMatrix *ndsm = NULL;\n    \n    DdNode *trans = jlong_to_DdNode(t); //trans/reward matrix\n    DdNode **rvars = jlong_to_DdNode_array(rv);   // row vars\n    DdNode **cvars = jlong_to_DdNode_array(cv);   // col vars\n    DdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n    ODDNode *odd = jlong_to_ODDNode(od);      // reachable states\n    \n\tndsm = build_nd_sparse_matrix(ddman, trans, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n    \n    return ptr_to_jlong(ndsm);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT jlong __jlongpointer JNICALL Java_sparse_NDSparseMatrix_PS_1BuildSubNDSparseMatrix\n(JNIEnv *env, jclass cls,\n jlong __jlongpointer t,    // trans\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv,  // nondet vars\n jint num_ndvars,\n jlong __jlongpointer r    // reward\n )\n{\n    NDSparseMatrix *ndsm = NULL;\n    \n    DdNode *trans = jlong_to_DdNode(t); //trans/reward matrix\n    DdNode **rvars = jlong_to_DdNode_array(rv);   // row vars\n    DdNode **cvars = jlong_to_DdNode_array(cv);   // col vars\n    DdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n    ODDNode *odd = jlong_to_ODDNode(od);      // reachable states\n    DdNode *rewards = jlong_to_DdNode(r);\n    \n\tndsm = build_sub_nd_sparse_matrix(ddman, trans, rewards, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n    \n    return ptr_to_jlong(ndsm);\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void JNICALL Java_sparse_NDSparseMatrix_PS_1AddActionsToNDSparseMatrix\n(JNIEnv *env, jclass cls,\n jlong __jlongpointer t,    // trans\n jlong __jlongpointer ta,    // trans action labels\n jlong __jlongpointer od, // odd\n jlong __jlongpointer rv, // row vars\n jint num_rvars,\n jlong __jlongpointer cv, // col vars\n jint num_cvars,\n jlong __jlongpointer ndv,  // nondet vars\n jint num_ndvars,\n jlong __jlongpointer nd    // sparse matrix\n )\n{\n    DdNode *trans = jlong_to_DdNode(t); \t\t\t//trans/reward matrix\n\tDdNode *trans_actions = jlong_to_DdNode(ta);\t// trans action labels\n    ODDNode *odd = jlong_to_ODDNode(od);      // reachable states\n    DdNode **rvars = jlong_to_DdNode_array(rv);   // row vars\n    DdNode **cvars = jlong_to_DdNode_array(cv);   // col vars\n    DdNode **ndvars = jlong_to_DdNode_array(ndv); // nondet vars\n\tNDSparseMatrix *ndsm = (NDSparseMatrix *) jlong_to_NDSparseMatrix(nd); // sparse matrix\n    \n\tjstring *action_names_jstrings;\n\tconst char** action_names = NULL;\n\tint num_actions;\n\t\n\tif (trans_actions != NULL) {\n\t\tbuild_nd_action_vector(ddman, trans, trans_actions, ndsm, rvars, cvars, num_rvars, ndvars, num_ndvars, odd);\n\t}\n}\n\n//------------------------------------------------------------------------------\n\nJNIEXPORT void __jlongpointer JNICALL Java_sparse_NDSparseMatrix_PS_1DeleteNDSparseMatrix\n(JNIEnv *env, jclass cls,\n jlong __jlongpointer _ndsm)\n{\n    NDSparseMatrix * ndsm = (NDSparseMatrix *) jlong_to_NDSparseMatrix(_ndsm);\n    if (ndsm) delete ndsm;\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/PrismSparse.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage sparse;\n\nimport java.io.FileNotFoundException;\nimport java.util.List;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport odd.ODDNode;\nimport odd.ODDUtils;\nimport prism.NativeIntArray;\nimport prism.OpsAndBoundsList;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNative;\nimport prism.PrismNotSupportedException;\nimport dv.DoubleVector;\nimport dv.IntegerVector;\n\n//----------------------------------------------------------------------------------------------\n\npublic class PrismSparse\n{\n\t//----------------------------------------------------------------------------------------------\n\t// load jni stuff from shared library\n\t//----------------------------------------------------------------------------------------------\n\n\tstatic\n\t{\n\t\ttry {\n\t\t\tSystem.loadLibrary(\"prism\");\n\t\t}\n\t\tcatch (UnsatisfiedLinkError e) {\n\t\t\tSystem.out.println(e);\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t//----------------------------------------------------------------------------------------------\n\t// initialise/close down methods\n\t//----------------------------------------------------------------------------------------------\n\n\t/**\n\t * Check that number of reachable states is in a range that can be handled by\n\t * the sparse engine methods.\n\t * @throws PrismNotSupportedException if that is not the case\n\t */\n\tprivate static void checkNumStates(ODDNode odd) throws PrismNotSupportedException\n\t{\n\t\t// currently, the sparse engine internally uses int (signed 32bit) index values\n\t\t// so, if the number of states is larger than Integer.MAX_VALUE, there is a problem\n\t\tODDUtils.checkInt(odd, \"Currently, the sparse engine cannot handle models\");\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// error message\n\t//------------------------------------------------------------------------------\n\t\n\tpublic static String getErrorMessage()\n\t{\n\t\treturn PrismNative.PN_GetErrorMessage();\n\t}\n\n\t/**\n\t * Generate the proper exception for an error from the native layer.\n\t * Gets the error message and returns the corresponding exception,\n\t * i.e., if the message contains \"not supported\" then a PrismNotSupportedException\n\t * is returned, otherwise a plain PrismException.\n\t */\n\tprivate static PrismException generateExceptionForError()\n\t{\n\t\tString msg = getErrorMessage();\n\t\tif (msg.contains(\"not supported\")) {\n\t\t\treturn new PrismNotSupportedException(msg);\n\t\t} else {\n\t\t\treturn new PrismException(msg);\n\t\t}\n\t}\n\n\t//----------------------------------------------------------------------------------------------\n\t// JNI wrappers for blocks of sparse code\n\t//----------------------------------------------------------------------------------------------\n\n\t//----------------------------------------------------------------------------------------------\n\t// probabilistic/dtmc stuff\n\t//----------------------------------------------------------------------------------------------\n\n\t// pctl bounded until (probabilistic/dtmc)\n\tprivate static native long PS_ProbBoundedUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe, int bound);\n\tpublic static DoubleVector ProbBoundedUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, int bound) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_ProbBoundedUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), bound);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// pctl until (probabilistic/dtmc)\n\tprivate static native long PS_ProbUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe);\n\tpublic static DoubleVector ProbUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_ProbUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl until (probabilistic/dtmc), interval variant\n\tprivate static native long PS_ProbUntilInterval(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe, int flags);\n\tpublic static DoubleVector ProbUntilInterval(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_ProbUntilInterval(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl cumulative reward (probabilistic/dtmc)\n\tprivate static native long PS_ProbCumulReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, int bound);\n\tpublic static DoubleVector ProbCumulReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, int bound) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_ProbCumulReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), bound);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl inst reward (probabilistic/dtmc)\n\tprivate static native long PS_ProbInstReward(long trans, long sr, long odd, long rv, int nrv, long cv, int ncv, int time);\n\tpublic static DoubleVector ProbInstReward(JDDNode trans, JDDNode sr, ODDNode odd, JDDVars rows, JDDVars cols, int time) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_ProbInstReward(trans.ptr(), sr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl reach reward (probabilistic/dtmc)\n\tprivate static native long PS_ProbReachReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long goal, long inf, long maybe);\n\tpublic static DoubleVector ProbReachReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode goal, JDDNode inf, JDDNode maybe) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_ProbReachReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), goal.ptr(), inf.ptr(), maybe.ptr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl reach reward (probabilistic/dtmc), interval variant\n\tprivate static native long PS_ProbReachRewardInterval(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long goal, long inf, long maybe, long lower, long upper, int flags);\n\tpublic static DoubleVector ProbReachRewardInterval(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode goal, JDDNode inf, JDDNode maybe, JDDNode lower, JDDNode upper, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_ProbReachRewardInterval(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), goal.ptr(), inf.ptr(), maybe.ptr(), lower.ptr(), upper.ptr(), flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// transient (probabilistic/dtmc)\n\tprivate static native long PS_ProbTransient(long trans, long odd, long init, long rv, int nrv, long cv, int ncv, int time);\n\tpublic static DoubleVector ProbTransient(JDDNode trans, ODDNode odd, DoubleVector init, JDDVars rows, JDDVars cols, int time) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_ProbTransient(trans.ptr(), odd.ptr(), init.getPtr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t//----------------------------------------------------------------------------------------------\n\t// nondeterministic/mdp stuff\n\t//----------------------------------------------------------------------------------------------\n\n\t// pctl bounded until (nondeterministic/mdp)\n\tprivate static native long PS_NondetBoundedUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, int time, boolean minmax);\n\tpublic static DoubleVector NondetBoundedUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, int time, boolean minmax) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_NondetBoundedUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), time, minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// pctl until (nondeterministic/mdp)\n\tprivate static native long PS_NondetUntil(long trans, long trans_actions, List<String> synchs, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, boolean minmax, long strat);\n\tpublic static DoubleVector NondetUntil(JDDNode trans, JDDNode transActions, List<String> synchs, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, boolean minmax, IntegerVector strat) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_NondetUntil(trans.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), minmax, (strat == null) ? 0 : strat.getPtr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl until (nondeterministic/mdp), interval iteration\n\tprivate static native long PS_NondetUntilInterval(long trans, long trans_actions, List<String> synchs, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long yes, long maybe, boolean minmax, long strat, int flags);\n\tpublic static DoubleVector NondetUntilInterval(JDDNode trans, JDDNode transActions, List<String> synchs, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode yes, JDDNode maybe, boolean minmax, IntegerVector strat, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_NondetUntilInterval(trans.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), yes.ptr(), maybe.ptr(), minmax, (strat == null) ? 0 : strat.getPtr(), flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl cumulative reward (probabilistic/mdp)\n\tprivate static native long PS_NondetCumulReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, int bound, boolean minmax);\n\tpublic static DoubleVector NondetCumulReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, int bound, boolean minmax) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_NondetCumulReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), bound, minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl inst reward (nondeterministic/mdp)\n\tprivate static native long PS_NondetInstReward(long trans, long sr, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, int time, boolean minmax, long init);\n\tpublic static DoubleVector NondetInstReward(JDDNode trans, JDDNode sr, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, int time, boolean minmax, JDDNode init) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_NondetInstReward(trans.ptr(), sr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), time, minmax, init.ptr());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl reach reward (nondeterministic/mdp)\n\tprivate static native long PS_NondetReachReward(long trans, long trans_actions, List<String> synchs, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long goal, long inf, long maybe, boolean minmax);\n\tpublic static DoubleVector NondetReachReward(JDDNode trans, JDDNode transActions, List<String> synchs, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode goal, JDDNode inf, JDDNode maybe, boolean minmax) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_NondetReachReward(trans.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), goal.ptr(), inf.ptr(), maybe.ptr(), minmax);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// pctl reach reward (nondeterministic/mdp), interval iteration\n\tprivate static native long PS_NondetReachRewardInterval(long trans, long trans_actions, List<String> synchs, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long goal, long inf, long maybe, long lower, long upper, boolean minmax, int flags);\n\tpublic static DoubleVector NondetReachRewardInterval(JDDNode trans, JDDNode transActions, List<String> synchs, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, JDDNode goal, JDDNode inf, JDDNode maybe, JDDNode lower, JDDNode upper, boolean minmax, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_NondetReachRewardInterval(trans.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), goal.ptr(), inf.ptr(), maybe.ptr(), lower.ptr(), upper.ptr(), minmax, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\tprivate static native double[] PS_NondetMultiObj(long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, boolean minmax, long start, long ptr_adversary, long ptr_TransSparseMatrix, List<String> synchs, long[] ptr_yes_vec, int[] probStepBounds, long[] ptr_RewSparseMatrix, double[] rewardWeights, int[] rewardStepBounds);\n\tpublic static double[] NondetMultiObj(ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, boolean minmax, JDDNode start, NativeIntArray adversary, NDSparseMatrix transSparseMatrix, List<String> synchs, DoubleVector[] yes_vec, int[] probStepBounds, NDSparseMatrix[] rewSparseMatrix, double[] rewardWeights, int[] rewardStepBounds) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong[] ptr_ndsp_r = null;\n\t\tif (rewSparseMatrix != null) {\n\t\t\tptr_ndsp_r = new long[rewSparseMatrix.length];\n\t\t\tfor (int i = 0; i < ptr_ndsp_r.length; i++)\n\t\t\t\tptr_ndsp_r[i] = (rewSparseMatrix[i]!=null) ? rewSparseMatrix[i].getPtr() : 0;\n\t\t}\n\t\t\t\n\t\tlong[] ptr_yes_vec = null;\n\t\tif (yes_vec != null) {\n\t\t\tptr_yes_vec = new long[yes_vec.length];\n\t\t\tfor (int i = 0; i < yes_vec.length; i++)\n\t\t\t\tptr_yes_vec[i] = (yes_vec[i]!=null) ? yes_vec[i].getPtr() : 0;\n\t\t}\n\t\t\n\t\tdouble[] ret = PS_NondetMultiObj(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), minmax, start.ptr(), adversary.getPtr(), transSparseMatrix.getPtr(), synchs, ptr_yes_vec, probStepBounds, ptr_ndsp_r, rewardWeights, rewardStepBounds);\n\t\tif (ret == null)\n\t\t\tthrow new PrismException(getErrorMessage());\n\t\telse\n\t\t\treturn ret;\n\t\n\t}\n\t\n\tprivate static native double[] PS_NondetMultiObjGS(long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, boolean minmax, long start, long ptr_adversary, long ptr_TransSparseMatrix, long[] ptr_yes_vec, long[] ptr_RewSparseMatrix, double[] rewardWeights);\n\tpublic static double[] NondetMultiObjGS(ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, boolean minmax, JDDNode start, NativeIntArray adversary, NDSparseMatrix transSparseMatrix, DoubleVector[] yes_vec, NDSparseMatrix[] rewSparseMatrix, double[] rewardWeights) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong[] ptr_ndsp_r = null;\n\t\tif (rewSparseMatrix != null) {\n\t\t\tptr_ndsp_r = new long[rewSparseMatrix.length];\n\t\t\tfor (int i = 0; i < ptr_ndsp_r.length; i++)\n\t\t\t\tptr_ndsp_r[i] = (rewSparseMatrix[i]!=null) ? rewSparseMatrix[i].getPtr() : 0;\n\t\t}\n\t\t\t\n\t\tlong[] ptr_yes_vec = null;\n\t\tif (yes_vec != null) {\n\t\t\tptr_yes_vec = new long[yes_vec.length];\n\t\t\tfor (int i = 0; i < yes_vec.length; i++)\n\t\t\t\tptr_yes_vec[i] = (yes_vec[i]!=null) ? yes_vec[i].getPtr() : 0;\n\t\t}\n\t\t\n\t\tdouble[] ret = PS_NondetMultiObjGS(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), minmax, start.ptr(), adversary.getPtr(), transSparseMatrix.getPtr(), ptr_yes_vec, ptr_ndsp_r, rewardWeights);\n\t\tif (ret == null)\n\t\t\tthrow new PrismException(getErrorMessage());\n\t\telse\n\t\t\treturn ret;\n\t}\n\n\t// multi-objective (nondeterministic/mdp)\n\tprivate static native double PS_NondetMultiReach(long trans, long trans_actions, List<String> synchs, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long targets[], int relops[], double bounds[], long maybe, long start);\n\tpublic static double NondetMultiReach(JDDNode trans, JDDNode transActions, List<String> synchs, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, List<JDDNode> targets, OpsAndBoundsList opsAndBounds, JDDNode maybe, JDDNode start) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\t// Convert lists to arrays for passing to JNI\n\t\tint i, n = targets.size();\n\t\tlong targetsArr[] = new long[n];\n\t\tint relOpsArr[] = new int[n];\n\t\tdouble boundsArr[] = new double[n];\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ttargetsArr[i] = targets.get(i).ptr();\n\t\t\trelOpsArr[i] = opsAndBounds.getProbOperator(i).toNumber();\n\t\t\tboundsArr[i] = opsAndBounds.getProbBound(i);\n\t\t}\n\t\tdouble res = //relOps.get(0).intValue()>2 ? \n\t\t\t\tPS_NondetMultiReach(trans.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), targetsArr, relOpsArr, boundsArr, maybe.ptr(), start.ptr()); //:\n\t\t\t\t\t//PS_NondetMultiReach(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), targetsArr, relOpsArr, boundsArr, maybe.ptr(), start.ptr(), (checkReach? 1 : 0),\n\t\t\t\t\t\t\t//0, 0);\n\t\tif (res == -1) throw new PrismException(getErrorMessage());\n\t\treturn res;\n\t}\n\t\n\tprivate static native double PS_NondetMultiReach1(long trans, long trans_actions, List<String> synchs, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long targets[], long combinations[], int combinationIDs[], int relops[], double bounds[], long maybe, long start);\n\tpublic static double NondetMultiReach1(JDDNode trans, JDDNode transActions, List<String> synchs, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, List<JDDNode> targets, List<JDDNode> combinations, List<Integer> combinationIDs, OpsAndBoundsList opsAndBounds, JDDNode maybe, JDDNode start) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\t// Convert lists to arrays for passing to JNI\n\t\tint i, n = targets.size();\n\t\tlong targetsArr[] = new long[n];\n\t\tint relOpsArr[] = new int[n];\n\t\tdouble boundsArr[] = new double[n];\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ttargetsArr[i] = targets.get(i).ptr();\n\t\t\trelOpsArr[i] = opsAndBounds.getProbOperator(i).toNumber();\n\t\t\tboundsArr[i] = opsAndBounds.getProbBound(i);\n\t\t}\n\t\tlong combinationsArr[] = new long[combinations.size()];\n\t\tint combinationIDsArr[] = new int[combinationIDs.size()];\n\t\tfor(i=0; i<combinations.size(); i++) {\n\t\t\tcombinationsArr[i] = combinations.get(i).ptr();\n\t\t}\n\t\tfor(i=0; i<combinationIDs.size(); i++)\n\t\t\tcombinationIDsArr[i] = combinationIDs.get(i);\n\t\tdouble res = //relOps.get(0).intValue()>2 ? \n\t\t\t\tPS_NondetMultiReach1(trans.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), targetsArr, combinationsArr, combinationIDsArr, relOpsArr, boundsArr, maybe.ptr(), start.ptr()); //:\n\t\t\t\t\t//PS_NondetMultiReach(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), targetsArr, relOpsArr, boundsArr, maybe.ptr(), start.ptr(), (checkReach? 1 : 0),\n\t\t\t\t\t\t\t//0, 0);\n\t\tif (res == -1) throw new PrismException(getErrorMessage());\n\t\treturn res;\n\t}\n\t\n\t// multi-objective (nondeterministic/mdp)\n\tprivate static native double PS_NondetMultiReachReward(long trans, long trans_actions, List<String> synchs, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long targets[], int relopsProb[], double boundsProb[], int relopsReward[], double boundsReward[], long maybe, long start, long trr[], long becs);\n\tpublic static double NondetMultiReachReward(JDDNode trans, JDDNode transActions, List<String> synchs, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, List<JDDNode> targets, OpsAndBoundsList opsAndBounds, JDDNode maybe, JDDNode start,\n\t\t\tList<JDDNode> trr, JDDNode becs) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\t// Convert lists to arrays for passing to JNI\n\t\tint i;//, n = targets.size();\n\t\tlong targetsArr[] = new long[targets.size()];\n\t\tint relOpsProbArr[] = new int[opsAndBounds.probSize()];\n\t\tdouble boundsProbArr[] = new double[opsAndBounds.probSize()];\n\t\tint relOpsRewardArr[] = new int[opsAndBounds.rewardSize()];\n\t\tdouble boundsRewardArr[] = new double[opsAndBounds.rewardSize()];\n\t\tlong trrArr[] = new long[trr.size()];\n\t\tlong becsArr = becs.ptr();\n\t\tfor (i = 0; i < targets.size(); i++) \n\t\t\ttargetsArr[i] = targets.get(i).ptr();\n\t\tfor (i = 0; i < opsAndBounds.probSize(); i++) {\n\t\t\trelOpsProbArr[i] = opsAndBounds.getProbOperator(i).toNumber();\n\t\t\tboundsProbArr[i] = opsAndBounds.getProbBound(i);\n\t\t}\n\t\tfor (i = 0; i < opsAndBounds.rewardSize(); i++) {\n\t\t\trelOpsRewardArr[i] = opsAndBounds.getRewardOperator(i).toNumber();\n\t\t\tboundsRewardArr[i] = opsAndBounds.getRewardBound(i);\n\t\t}\n\t\tfor (i = 0; i < trr.size(); i++) \n\t\t\ttrrArr[i] = trr.get(i).ptr();\n\t\t\n\t\tdouble res = //relOps.get(0).intValue()>2 ? \n\t\t\t\tPS_NondetMultiReachReward(trans.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), targetsArr, relOpsProbArr, boundsProbArr, relOpsRewardArr, boundsRewardArr, maybe.ptr(), start.ptr(),\n\t\t\t\ttrrArr, becsArr); //:\n\t\t\t\t\t//PS_NondetMultiReach(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), targetsArr, relOpsArr, boundsArr, maybe.ptr(), start.ptr(), (checkReach? 1 : 0),\n\t\t\t\t\t\t\t//0, 0);\n\t\tif (res == -1) throw new PrismException(getErrorMessage());\n\t\treturn res;\n\t}\n\tprivate static native double PS_NondetMultiReachReward1(long trans, long trans_actions, List<String> synchs, long odd, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long targets[], long combinations[], int combinationIDs[], int relopsProb[], double boundsProb[], int relopsReward[], double boundsReward[], long maybe, long start, long trr[], long becs);\n\tpublic static double NondetMultiReachReward1(JDDNode trans, JDDNode transActions, List<String> synchs, ODDNode odd, JDDVars rows, JDDVars cols, JDDVars nondet, List<JDDNode> targets, List<JDDNode> combinations, List<Integer> combinationIDs, OpsAndBoundsList opsAndBounds, JDDNode maybe, JDDNode start,\n\t\t\tList<JDDNode> trr, JDDNode becs) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\t// Convert lists to arrays for passing to JNI\n\t\tint i;//, n = targets.size();\n\t\tlong targetsArr[] = new long[targets.size()];\n\t\tint relOpsProbArr[] = new int[opsAndBounds.probSize()];\n\t\tdouble boundsProbArr[] = new double[opsAndBounds.probSize()];\n\t\tint relOpsRewardArr[] = new int[opsAndBounds.rewardSize()];\n\t\tdouble boundsRewardArr[] = new double[opsAndBounds.rewardSize()];\n\t\tlong trrArr[] = new long[trr.size()];\n\t\tlong becsArr = becs.ptr();\n\t\tfor (i = 0; i < targets.size(); i++) \n\t\t\ttargetsArr[i] = targets.get(i).ptr();\n\t\tfor (i = 0; i < opsAndBounds.probSize(); i++) {\n\t\t\trelOpsProbArr[i] = opsAndBounds.getProbOperator(i).toNumber();\n\t\t\tboundsProbArr[i] = opsAndBounds.getProbBound(i);\n\t\t}\n\t\tfor (i = 0; i < opsAndBounds.rewardSize(); i++) {\n\t\t\trelOpsRewardArr[i] = opsAndBounds.getRewardOperator(i).toNumber(); \n\t\t\tboundsRewardArr[i] = opsAndBounds.getRewardBound(i);\n\t\t}\n\t\tfor (i = 0; i < trr.size(); i++) \n\t\t\ttrrArr[i] = trr.get(i).ptr();\n\t\tlong combinationsArr[] = new long[combinations.size()];\n\t\tint combinationIDsArr[] = new int[combinationIDs.size()];\n\t\tfor(i=0; i<combinations.size(); i++) {\n\t\t\tcombinationsArr[i] = combinations.get(i).ptr();\n\t\t}\n\t\tfor(i=0; i<combinationIDs.size(); i++)\n\t\t\tcombinationIDsArr[i] = combinationIDs.get(i);\n\t\t\n\t\tdouble res = //relOps.get(0).intValue()>2 ? \n\t\t\t\tPS_NondetMultiReachReward1(trans.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), targetsArr, combinationsArr, combinationIDsArr, relOpsProbArr, boundsProbArr, relOpsRewardArr, boundsRewardArr, maybe.ptr(), start.ptr(),\n\t\t\t\ttrrArr, becsArr); //:\n\t\t\t\t\t//PS_NondetMultiReach(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), targetsArr, relOpsArr, boundsArr, maybe.ptr(), start.ptr(), (checkReach? 1 : 0),\n\t\t\t\t\t\t\t//0, 0);\n\t\tif (res == -1) throw new PrismException(getErrorMessage());\n\t\treturn res;\n\t}\n\t\t\n\t//----------------------------------------------------------------------------------------------\n\t// stochastic/ctmc stuff\n\t//----------------------------------------------------------------------------------------------\n\n\t// csl time bounded until (stochastic/ctmc)\n\tprivate static native long PS_StochBoundedUntil(long trans, long odd, long rv, int nrv, long cv, int ncv, long yes, long maybe, double time, long mult);\n\tpublic static DoubleVector StochBoundedUntil(JDDNode trans, ODDNode odd, JDDVars rows, JDDVars cols, JDDNode yes, JDDNode maybe, double time, DoubleVector multProbs) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong mult = (multProbs == null) ? 0 : multProbs.getPtr();\n\t\tlong ptr = PS_StochBoundedUntil(trans.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), yes.ptr(), maybe.ptr(), time, mult);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// csl cumulative reward (stochastic/ctmc)\n\tprivate static native long PS_StochCumulReward(long trans, long sr, long trr, long odd, long rv, int nrv, long cv, int ncv, double time);\n\tpublic static DoubleVector StochCumulReward(JDDNode trans, JDDNode sr, JDDNode trr, ODDNode odd, JDDVars rows, JDDVars cols, double time) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_StochCumulReward(trans.ptr(), sr.ptr(), trr.ptr(), odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// steady state (stochastic/ctmc)\n\tprivate static native long PS_StochSteadyState(long trans, long odd, long init, long rv, int nrv, long cv, int ncv);\n\tpublic static DoubleVector StochSteadyState(JDDNode trans, ODDNode odd, JDDNode init, JDDVars rows, JDDVars cols) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_StochSteadyState(trans.ptr(), odd.ptr(), init.ptr(), rows.array(), rows.n(), cols.array(), cols.n());\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\t\n\t// transient (stochastic/ctmc)\n\tprivate static native long PS_StochTransient(long trans, long odd, long init, long rv, int nrv, long cv, int ncv, double time);\n\tpublic static DoubleVector StochTransient(JDDNode trans, ODDNode odd, DoubleVector init, JDDVars rows, JDDVars cols, double time) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_StochTransient(trans.ptr(), odd.ptr(), init.getPtr(), rows.array(), rows.n(), cols.array(), cols.n(), time);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// export methods\n\t//------------------------------------------------------------------------------\n\n\t// export matrix\n\tprivate static native int PS_ExportMatrix(long matrix, String name, long rv, int nrv, long cv, int ncv, long odd, int exportType, String filename, String rewardStructName, boolean noexportheaders);\n\tpublic static void ExportMatrix(JDDNode matrix, String name, JDDVars rows, JDDVars cols, ODDNode odd, int exportType, String filename, int precision, String rewardStructName, boolean noexportheaders) throws FileNotFoundException, PrismException\n\t{\n\t\tPrismNative.setExportModelPrecision(precision);\n\t\tcheckNumStates(odd);\n\t\tint res = PS_ExportMatrix(matrix.ptr(), name, rows.array(), rows.n(), cols.array(), cols.n(), odd.ptr(), exportType, filename, rewardStructName, noexportheaders);\n\t\tif (res == -1) {\n\t\t\tthrow new FileNotFoundException();\n\t\t}\n\t\telse if (res == -2) {\n\t\t\tthrow new PrismException(\"Out of memory building matrix for export\");\n\t\t}\n\t}\n\n\t// export markov chain (with actions)\n\tprivate static native int PS_ExportMC(long[] trans_per_action, List<String> synchs, String name, long rv, int nrv, long cv, int ncv, long odd, int exportType, String filename);\n\tpublic static void ExportMC(JDDNode[] transPerAction, List<String> synchs, String name, JDDVars rows, JDDVars cols, ODDNode odd, int exportType, String filename, int precision) throws FileNotFoundException, PrismException\n\t{\n\t\tPrismNative.setExportModelPrecision(precision);\n\t\tcheckNumStates(odd);\n\t\tint res = PS_ExportMC(JDDNode.ptrs(transPerAction), synchs, name, rows.array(), rows.n(), cols.array(), cols.n(), odd.ptr(), exportType, filename);\n\t\tif (res == -1) {\n\t\t\tthrow new FileNotFoundException();\n\t\t}\n\t\telse if (res == -2) {\n\t\t\tthrow new PrismException(\"Out of memory building matrix for export\");\n\t\t}\n\t}\n\n\t// export mdp\n\tprivate static native int PS_ExportMDP(long mdp, long trans_actions, List<String> synchs, String name, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long odd, int exportType, String filename);\n\tpublic static void ExportMDP(JDDNode mdp, JDDNode transActions, List<String> synchs, String name, JDDVars rows, JDDVars cols, JDDVars nondet, ODDNode odd, int exportType, String filename, int precision) throws FileNotFoundException, PrismException\n\t{\n\t\tPrismNative.setExportModelPrecision(precision);\n\t\tcheckNumStates(odd);\n\t\tint res = PS_ExportMDP(mdp.ptr(), (transActions == null) ? 0 : transActions.ptr(), synchs, name, rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), odd.ptr(), exportType, filename);\n\t\tif (res == -1) {\n\t\t\tthrow new FileNotFoundException();\n\t\t}\n\t\telse if (res == -2) {\n\t\t\tthrow new PrismException(\"Out of memory building matrix for export\");\n\t\t}\n\t}\n\t\n\t// export sub-mdp, i.e. mdp transition rewards\n\tprivate static native int PS_ExportSubMDP(long mdp, long submdp, String name, long rv, int nrv, long cv, int ncv, long ndv, int nndv, long odd, int exportType, String filename, String rewardStructName, boolean noexportheaders);\n\tpublic static void ExportSubMDP(JDDNode mdp, JDDNode submdp, String name, JDDVars rows, JDDVars cols, JDDVars nondet, ODDNode odd, int exportType, String filename, int precision, String rewardStructName, boolean noexportheaders) throws FileNotFoundException, PrismException\n\t{\n\t\tPrismNative.setExportModelPrecision(precision);\n\t\tcheckNumStates(odd);\n\t\tint res = PS_ExportSubMDP(mdp.ptr(), submdp.ptr(), name, rows.array(), rows.n(), cols.array(), cols.n(), nondet.array(), nondet.n(), odd.ptr(), exportType, filename, rewardStructName, noexportheaders);\n\t\tif (res == -1) {\n\t\t\tthrow new FileNotFoundException();\n\t\t}\n\t\telse if (res == -2) {\n\t\t\tthrow new PrismException(\"Out of memory building matrix for export\");\n\t\t}\n\t}\n\n\t//------------------------------------------------------------------------------\n\t// generic iterative solution methods\n\t//------------------------------------------------------------------------------\n\n\t// power method\n\tprivate static native long PS_Power(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose);\n\tpublic static DoubleVector Power(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_Power(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// power method, interval variant\n\tprivate static native long PS_PowerInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, int flags);\n\tpublic static DoubleVector PowerInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_PowerInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// jor method\n\tprivate static native long PS_JOR(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose, boolean row_sums, double omega);\n\tpublic static DoubleVector JOR(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose, boolean row_sums, double omega) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_JOR(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose, row_sums, omega);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// jor method, interval variant\n\tprivate static native long PS_JORInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, boolean row_sums, double omega, int flags);\n\tpublic static DoubleVector JORInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, boolean row_sums, double omega, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_JORInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, row_sums, omega, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// sor method\n\tprivate static native long PS_SOR(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long init, boolean transpose, boolean row_sums, double omega, boolean forwards);\n\tpublic static DoubleVector SOR(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode init, boolean transpose, boolean row_sums, double omega, boolean forwards) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_SOR(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), init.ptr(), transpose, row_sums, omega, forwards);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t// sor method, interval variant\n\tprivate static native long PS_SORInterval(long odd, long rv, int nrv, long cv, int ncv, long a, long b, long lower, long upper, boolean transpose, boolean row_sums, double omega, boolean forwards, int flags);\n\tpublic static DoubleVector SORInterval(ODDNode odd, JDDVars rows, JDDVars cols, JDDNode a, JDDNode b, JDDNode lower, JDDNode upper, boolean transpose, boolean row_sums, double omega, boolean forwards, int flags) throws PrismException\n\t{\n\t\tcheckNumStates(odd);\n\t\tPrismNative.resetModelCheckingInfo();\n\t\tlong ptr = PS_SORInterval(odd.ptr(), rows.array(), rows.n(), cols.array(), cols.n(), a.ptr(), b.ptr(), lower.ptr(), upper.ptr(), transpose, row_sums, omega, forwards, flags);\n\t\tif (ptr == 0) throw generateExceptionForError();\n\t\treturn new DoubleVector(ptr, (int)(odd.getEOff() + odd.getTOff()));\n\t}\n\n\t//----------------------------------------------------------------------------------------------\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/sparse/package-info.java",
    "content": "/**\n * Access to the \"Sparse\" engine: sparse matrix data structures and corresponding implementations of model checking algorithms.\n */\npackage sparse;\n"
  },
  {
    "path": "prism/src/sparse/sparse.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Rashid Mehmood <rxm@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n#include <cmath>\n#include \"dv.h\"\n#include \"sparse.h\"\n#include \"PrismNativeGlob.h\"\n#include <new>\n\n//------------------------------------------------------------------------------\n\n// local function prototypes\n\nstatic void split_mdp_rec(DdManager *ddman, DdNode *dd, DdNode **ndvars, int num_ndvars, int level, DdNode **matrices);\nstatic void split_mdp_and_sub_mdp_rec(DdManager *ddman, DdNode *dd, DdNode *subdd, DdNode **ndvars, int num_ndvars, int level, DdNode **matrices, DdNode **submatrices);\nstatic void traverse_mtbdd_matr_rec(DdManager *ddman, DdNode *dd, DdNode **rvars, DdNode **cvars, int num_vars, int level, ODDNode *row, ODDNode *col, int r, int c, int code, bool transpose);\nstatic void traverse_mtbdd_vect_rec(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, int level, ODDNode *odd, int i, int code);\n\n// global variables (used by local functions)\nstatic int count;\nstatic int *starts, *starts2;\nstatic int *actions;\nstatic int action_count;\nstatic RMSparseMatrix *rmsm;\nstatic CMSparseMatrix *cmsm;\nstatic RCSparseMatrix *rcsm;\nstatic CMSRSparseMatrix *cmsrsm;\nstatic CMSCSparseMatrix *cmscsm;\nstatic NDSparseMatrix *ndsm;\n\n//------------------------------------------------------------------------------\n// Data structure constructors/deconstructors\n//------------------------------------------------------------------------------\n\nEXPORT RMSparseMatrix::RMSparseMatrix()\n{\n\tn = 0;\n\tnnz = 0;\n\tuse_counts = false;\n\tmem = 0.0;\n\tnon_zeros = NULL;\n\tcols = NULL;\n\trow_counts = NULL;\n\tactions = NULL;\n}\n\nEXPORT RMSparseMatrix::~RMSparseMatrix()\n{\n\tif (non_zeros) delete[] non_zeros;\n\tif (cols) delete[] cols;\n\tif (row_counts) delete[] row_counts;\n\tif (actions) delete[] actions;\n}\n\n//------------------------------------------------------------------------------\n\nEXPORT CMSparseMatrix::CMSparseMatrix()\n{\n\tn = 0;\n\tnnz = 0;\n\tuse_counts = false;\n\tmem = 0.0;\n\tnon_zeros = NULL;\n\trows = NULL;\n\tcol_counts = NULL;\n}\n\nEXPORT CMSparseMatrix::~CMSparseMatrix()\n{\n\tif (non_zeros) delete[] non_zeros;\n\tif (rows) delete[] rows;\n\tif (col_counts) delete[] col_counts;\n}\n\n//------------------------------------------------------------------------------\n\nEXPORT RCSparseMatrix::RCSparseMatrix()\n{\n\tn = 0;\n\tnnz = 0;\n\tuse_counts = false;\n\tmem = 0.0;\n\tnon_zeros = NULL;\n\trows = NULL;\n\tcols = NULL;\n}\n\nEXPORT RCSparseMatrix::~RCSparseMatrix()\n{\n\tif (non_zeros) delete[] non_zeros;\n\tif (rows) delete[] rows;\n\tif (cols) delete[] cols;\n}\n\n//------------------------------------------------------------------------------\n\nEXPORT CMSRSparseMatrix::CMSRSparseMatrix()\n{\n\tn = 0;\n\tnnz = 0;\n\tuse_counts = false;\n\tmem = 0.0;\n\tdist = NULL;\n\tdist_num = 0;\n\tdist_shift = 0;\n\tdist_mask = 0;\n\tcols = NULL;\n\trow_counts = NULL;\n}\n\nEXPORT CMSRSparseMatrix::~CMSRSparseMatrix()\n{\n\tif (dist) delete[] dist;\n\tif (cols) delete[] cols;\n\tuse_counts ? delete[] row_counts : delete[] (int*)row_counts;\n}\n\n//------------------------------------------------------------------------------\n\nEXPORT CMSCSparseMatrix::CMSCSparseMatrix()\n{\n\tn = 0;\n\tnnz = 0;\n\tuse_counts = false;\n\tmem = 0.0;\n\tdist = NULL;\n\tdist_num = 0;\n\tdist_shift = 0;\n\tdist_mask = 0;\n\trows = NULL;\n\tcol_counts = NULL;\n}\n\nEXPORT CMSCSparseMatrix::~CMSCSparseMatrix()\n{\n\tif (dist) delete[] dist;\n\tif (rows) delete[] rows;\n\tuse_counts ? delete[] col_counts : delete[] (int*)col_counts;\n}\n\n//------------------------------------------------------------------------------\n\nEXPORT NDSparseMatrix::NDSparseMatrix()\n{\n\tn = 0;\n\tnc = 0;\n\tnnz = 0;\n\tk = 0;\n\tuse_counts = false;\n\tmem = 0.0;\n\tnon_zeros = NULL;\n\tcols = NULL;\n\trow_counts = NULL;\n\tchoice_counts = NULL;\n\tactions = NULL;\n}\n\nEXPORT NDSparseMatrix::~NDSparseMatrix()\n{\n\tif (non_zeros) delete[] non_zeros;\n\tif (cols) delete[] cols;\n\tif (row_counts) delete[] row_counts;\n\tif (choice_counts) delete[] choice_counts;\n\tif (actions) delete[] actions;\n}\n\n//------------------------------------------------------------------------------\n// sparse utility functions\n//------------------------------------------------------------------------------\n\n// build row major (rm) sparse matrix\n// if tranpose flag is true, actually construct for tranpose\n// throws std::bad_alloc on out-of-memory\n\nRMSparseMatrix *build_rm_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd)\n{ return build_rm_sparse_matrix(ddman, matrix, rvars, cvars, num_vars, odd, false); }\n\nRMSparseMatrix *build_rm_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose)\n{\n\tint i, n, nnz, max;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\trmsm = NULL; rmsm = new RMSparseMatrix();\n\t\n\t// get number of states from odd\n\tn = rmsm->n = odd->eoff+odd->toff;\n\t// get num of transitions\n\tnnz = rmsm->nnz = (int)DD_GetNumMinterms(ddman, matrix, num_vars*2);\n\t\n\t// create arrays\n\trmsm->non_zeros = new double[nnz];\n\trmsm->cols = new unsigned int[nnz];\n\tstarts = NULL; starts = new int[n+1];\n\t\n\t// first traverse the mtbdd to compute how many entries are in each row\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 1, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a row)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\trmsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// now traverse the mtbdd again to get the actual matrix entries\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 2, transpose);\n\t// and recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// and if it's safe to do so, replace starts with (smaller) array of counts\n\tif (rmsm->use_counts) {\n\t\trmsm->row_counts = new unsigned char[n];\n\t\tfor (i = 0; i < n; i++) rmsm->row_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\tdelete[] starts; starts = NULL;\n\t\trmsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + n * sizeof(unsigned char)) / 1024.0;\n\t} else {\n\t\trmsm->row_counts = (unsigned char*)starts;\n\t\trmsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + n * sizeof(int)) / 1024.0;\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (rmsm) delete rmsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn rmsm;\n}\n\n// build row major (rm) sparse matrix with actions\n// if tranpose flag is true, actually construct for tranpose\n// throws std::bad_alloc on out-of-memory\n\nRMSparseMatrix *build_rm_sparse_matrix_act(DdManager *ddman, DdNode **matrices, int num_actions, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd)\n{ return build_rm_sparse_matrix_act(ddman, matrices, num_actions, rvars, cvars, num_vars, odd, false); }\n\nRMSparseMatrix *build_rm_sparse_matrix_act(DdManager *ddman, DdNode **matrices, int num_actions, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose)\n{\n\tint i, n, nnz, max;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\trmsm = NULL; rmsm = new RMSparseMatrix();\n\t\n\t// get number of states from odd\n\tn = rmsm->n = odd->eoff+odd->toff;\n\t// get num of transitions\n\tfor (int a = 0; a < num_actions; a++) {\n\t\trmsm->nnz += (int)DD_GetNumMinterms(ddman, matrices[a], num_vars*2);\n\t}\n\tnnz = rmsm->nnz;\n\t\n\t// create arrays\n\trmsm->non_zeros = new double[nnz];\n\trmsm->cols = new unsigned int[nnz];\n\trmsm->actions = new unsigned int[nnz];\n\tstarts = NULL; starts = new int[n+1];\n\t\n\t// first traverse the mtbdd to compute how many entries are in each row\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\tfor (int a = 0; a < num_actions; a++) {\n\t\ttraverse_mtbdd_matr_rec(ddman, matrices[a], rvars, cvars, num_vars, 0, odd, odd, 0, 0, 1, transpose);\n\t}\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a row)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\trmsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// now traverse the mtbdd again to get the actual matrix entries\n\tfor (int a = 0; a < num_actions; a++) {\n\t\taction_count = a;\n\t\ttraverse_mtbdd_matr_rec(ddman, matrices[a], rvars, cvars, num_vars, 0, odd, odd, 0, 0, 12, transpose);\n\t}\n\t// and recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// and if it's safe to do so, replace starts with (smaller) array of counts\n\tif (rmsm->use_counts) {\n\t\trmsm->row_counts = new unsigned char[n];\n\t\tfor (i = 0; i < n; i++) rmsm->row_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\tdelete[] starts; starts = NULL;\n\t\trmsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + n * sizeof(unsigned char)) / 1024.0;\n\t} else {\n\t\trmsm->row_counts = (unsigned char*)starts;\n\t\trmsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + n * sizeof(int)) / 1024.0;\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (rmsm) delete rmsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn rmsm;\n}\n\n//------------------------------------------------------------------------------\n\n// build column major (cm) sparse matrix\n// if tranpose flag is true, actually construct for tranpose\n// throws std::bad_alloc on out-of-memory\n\nCMSparseMatrix *build_cm_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd)\n{ return build_cm_sparse_matrix(ddman, matrix, rvars, cvars, num_vars, odd, false); }\n\nCMSparseMatrix *build_cm_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose)\n{\n\tint i, n, nnz, max;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\tcmsm = NULL; cmsm = new CMSparseMatrix();\n\t\n\t// get number of states from odd\n\tn = cmsm->n = odd->eoff+odd->toff;\n\t// get num of transitions\n\tnnz = cmsm->nnz = (int)DD_GetNumMinterms(ddman, matrix, num_vars*2);\n\t\n\t// create arrays\n\tcmsm->non_zeros = new double[nnz];\n\tcmsm->rows = new unsigned int[nnz];\n\tstarts = NULL; starts = new int[n+1];\n\t\n\t// first traverse the mtbdd to compute how many entries are in each column\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 3, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a column)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\tcmsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// now traverse the mtbdd again to get the actual matrix entries\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 4, transpose);\n\t// and recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// and if it's safe to do so, replace starts with (smaller) array of counts\n\tif (cmsm->use_counts) {\n\t\tcmsm->col_counts = new unsigned char[n];\n\t\tfor (i = 0; i < n; i++) cmsm->col_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\tdelete[] starts; starts = NULL;\n\t\tcmsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + n * sizeof(unsigned char)) / 1024.0;\n\t} else {\n\t\tcmsm->col_counts = (unsigned char*)starts;\n\t\tcmsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + n * sizeof(int)) / 1024.0;\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (cmsm) delete cmsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn cmsm;\n}\n\n//------------------------------------------------------------------------------\n\n// build row/column (rc) sparse matrix\n// if tranpose flag is true, actually construct for tranpose\n// throws std::bad_alloc on out-of-memory\n\nRCSparseMatrix *build_rc_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd)\n{ return build_rc_sparse_matrix(ddman, matrix, rvars, cvars, num_vars, odd, false); }\n\nRCSparseMatrix *build_rc_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose)\n{\n\tint n, nnz;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\trcsm = NULL; rcsm = new RCSparseMatrix();\n\t\n\t// get number of states from odd\n\tn = rcsm->n = odd->eoff+odd->toff;\n\t// get num of transitions\n\tnnz = rcsm->nnz = (int)DD_GetNumMinterms(ddman, matrix, num_vars*2);\n\t\n\t// create arrays\n\trcsm->non_zeros = new double[nnz];\n\trcsm->rows = new unsigned int[nnz];\n\trcsm->cols = new unsigned int[nnz];\n\t\n\t// traverse the mtbdd to get the matrix entries\n\tcount = 0;\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 5, transpose);\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (rcsm) delete rcsm;\n\t\tthrow e;\n\t}\n\t\n\treturn rcsm;\n}\n\n//------------------------------------------------------------------------------\n\n// build compact modified sparse row (cmsr) sparse matrix\n// if tranpose flag is true, actually construct for tranpose\n// throws std::bad_alloc on out-of-memory\n\nCMSRSparseMatrix *build_cmsr_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd)\n{ return build_cmsr_sparse_matrix(ddman, matrix, rvars, cvars, num_vars, odd, false); }\n\nCMSRSparseMatrix *build_cmsr_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose)\n{\n\tint i, n, nnz, max, sparebits;\n\tunsigned int maxsize;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\tcmsrsm = NULL; cmsrsm = new CMSRSparseMatrix();\n\t\n\t// get number of states from odd\n\tn = cmsrsm->n = odd->eoff+odd->toff;\n\t\n\t// determine number of distinct values\n\t// and see if compact storage is feasible; if not, abandon it\n\tcmsrsm->dist_num = DD_GetNumTerminals(ddman, matrix);\n\tcmsrsm->dist_shift = (int)ceil(logtwo(cmsrsm->dist_num));\n\tif (cmsrsm->dist_shift == 0) cmsrsm->dist_shift++;\n\t// this is how many bits are free to store row/column indices\n\tsparebits = 8*sizeof(unsigned int) - cmsrsm->dist_shift;\n\tif (sparebits == 8*sizeof(unsigned int)) sparebits--;\n\t// so this is the max size of sparse matrix we can afford\n\tmaxsize = 1 << sparebits;\n\tif (n > maxsize) {\n\t\tdelete cmsrsm;\n\t\treturn NULL;\n\t}\n\t \n\t// compute mask, allocate array for distinct vals\n\tcmsrsm->dist_mask = (1 << cmsrsm->dist_shift) - 1;\n\tcmsrsm->dist = new double[cmsrsm->dist_num];\n\t// reset total to zero because we haven't actually stored any values yet\n\tcmsrsm->dist_num = 0;\n\t\n\t// get num of transitions\n\tnnz = cmsrsm->nnz = (int)DD_GetNumMinterms(ddman, matrix, num_vars*2);\n\t\n\t// allocate temporary array to store start of each row\n\tstarts = NULL; starts = new int[n+1];\n\t\n\t// first traverse the mtbdd to compute how many entries are in each row\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 6, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a row)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\tcmsrsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// allocate other array\n\tcmsrsm->cols = new unsigned int[nnz];\n\t\n\t// now traverse the mtbdd again to get the actual matrix entries\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 7, transpose);\n\t// and recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// and if it's safe to do so, replace starts with (smaller) array of counts\n\tif (cmsrsm->use_counts) {\n\t\tcmsrsm->row_counts = new unsigned char[n];\n\t\tfor (i = 0; i < n; i++) cmsrsm->row_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\tdelete[] starts; starts = NULL;\n\t\tcmsrsm->mem = (cmsrsm->dist_num * sizeof(double) + nnz * sizeof(unsigned int) + n * sizeof(unsigned char)) / 1024.0;\n\t} else {\n\t\tcmsrsm->row_counts = (unsigned char*)starts;\n\t\tcmsrsm->mem = (cmsrsm->dist_num * sizeof(double) + nnz * sizeof(unsigned int) + n * sizeof(int)) / 1024.0;\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (cmsrsm) delete cmsrsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn cmsrsm;\n}\n\n//------------------------------------------------------------------------------\n\n// build compact modified sparse column (cmsc) sparse matrix\n// if tranpose flag is true, actually construct for tranpose\n// throws std::bad_alloc on out-of-memory\n\nCMSCSparseMatrix *build_cmsc_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd)\n{ return build_cmsc_sparse_matrix(ddman, matrix, rvars, cvars, num_vars, odd, false); }\n\nCMSCSparseMatrix *build_cmsc_sparse_matrix(DdManager *ddman, DdNode *matrix, DdNode **rvars, DdNode **cvars, int num_vars, ODDNode *odd, bool transpose)\n{\n\tint i, n, nnz, max, sparebits;\n\tunsigned int maxsize;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\tcmscsm = NULL; cmscsm = new CMSCSparseMatrix();\n\t\n\t// get number of states from odd\n\tn = cmscsm->n = odd->eoff+odd->toff;\n\t\n\t// determine number of distinct values\n\t// and see if compact storage is feasible; if not, abandon it\n\tcmscsm->dist_num = DD_GetNumTerminals(ddman, matrix);\n\tcmscsm->dist_shift = (int)ceil(logtwo(cmscsm->dist_num));\n\tif (cmscsm->dist_shift == 0) cmscsm->dist_shift++;\n\t// this is how many bits are free to store row/column indices\n\tsparebits = 8*sizeof(unsigned int) - cmscsm->dist_shift;\n\tif (sparebits == 8*sizeof(unsigned int)) sparebits--;\n\t// so this is the max size of sparse matrix we can afford\n\tmaxsize = 1 << sparebits;\n\tif (n > maxsize) {\n\t\tdelete cmscsm;\n\t\treturn NULL;\n\t}\n\t \n\t// compute mask, allocate array for distinct vals\n\tcmscsm->dist_mask = (1 << cmscsm->dist_shift) - 1;\n\tcmscsm->dist = new double[cmscsm->dist_num];\n\t// reset total to zero because we haven't actually stored any values yet\n\tcmscsm->dist_num = 0;\n\t\n\t// get num of transitions\n\tnnz = cmscsm->nnz = (int)DD_GetNumMinterms(ddman, matrix, num_vars*2);\n\t\n\t// allocate temporary array to store start of each row\n\tstarts = NULL; starts = new int[n+1];\n\t\n\t// first traverse the mtbdd to compute how many entries are in each column\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 8, transpose);\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num entries in a column)\n\tmax = 0;\n\tfor (i = 1; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\t// max num entries determines whether we store counts or starts:\n\tcmscsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// allocate other array\n\tcmscsm->rows = new unsigned int[nnz];\n\t\n\t// now traverse the mtbdd again to get the actual matrix entries\n\ttraverse_mtbdd_matr_rec(ddman, matrix, rvars, cvars, num_vars, 0, odd, odd, 0, 0, 9, transpose);\n\t// and recompute starts info because we've messed with it during previous traversal\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// and if it's safe to do so, replace starts with (smaller) array of counts\n\tif (cmscsm->use_counts) {\n\t\tcmscsm->col_counts = new unsigned char[n];\n\t\tfor (i = 0; i < n; i++) cmscsm->col_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\tdelete[] starts; starts = NULL;\n\t\tcmscsm->mem = (cmscsm->dist_num * sizeof(double) + nnz * sizeof(unsigned int) + n * sizeof(unsigned char)) / 1024.0;\n\t} else {\n\t\tcmscsm->col_counts = (unsigned char*)starts;\n\t\tcmscsm->mem = (cmscsm->dist_num * sizeof(double) + nnz * sizeof(unsigned int) + n * sizeof(int)) / 1024.0;\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (cmscsm) delete cmscsm;\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\treturn cmscsm;\n}\n\n//-----------------------------------------------------------------------------------\n\n// build nondeterministic (mdp) sparse matrix\n// throws std::bad_alloc on out-of-memory\n\nNDSparseMatrix *build_nd_sparse_matrix(DdManager *ddman, DdNode *mdp, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, ODDNode *odd)\n{\n\tint i, n, nm, nc, nnz, max, max2;\n\tDdNode *tmp = NULL, **matrices = NULL, **matrices_bdds = NULL;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\tndsm = NULL; ndsm = new NDSparseMatrix();\n\t\n\t// get number of states from odd\n\tn = ndsm->n = odd->eoff+odd->toff;\n\t// get num of choices (prob. distributions)\n\tCudd_Ref(mdp);\n\ttmp = DD_ThereExists(ddman, DD_Not(ddman, DD_Equals(ddman, mdp, 0)), cvars, num_vars);\n\tnc = ndsm->nc = (int)DD_GetNumMinterms(ddman, tmp, num_vars+num_ndvars);\n\t// get num of transitions\n\tnnz = ndsm->nnz = (int)DD_GetNumMinterms(ddman, mdp, num_vars*2+num_ndvars);\n\t// break the mdp mtbdd into several (nm) mtbdds\n\ttmp = DD_ThereExists(ddman, tmp, rvars, num_vars);\n\tnm = (int)DD_GetNumMinterms(ddman, tmp, num_ndvars);\n\tCudd_RecursiveDeref(ddman, tmp);\n\tmatrices = new DdNode*[nm];\n\tcount = 0;\n\tsplit_mdp_rec(ddman, mdp, ndvars, num_ndvars, 0, matrices);\n\t// and for each one create a bdd storing which rows/choices are non-empty\n\tmatrices_bdds = new DdNode*[nm];\n\tfor (i = 0; i < nm; i++) {\n\t\tCudd_Ref(matrices[i]);\n\t\tmatrices_bdds[i] = DD_ThereExists(ddman, DD_Not(ddman, DD_Equals(ddman, matrices[i], 0)), cvars, num_vars);\n\t}\n\t\n\t// create arrays\n\tndsm->non_zeros = new double[nnz];\n\tndsm->cols = new unsigned int[nnz];\n\tstarts = NULL; starts = new int[n+1];\n\tstarts2 = NULL; starts2 = new int[nc+1];\n\t\n\t// first traverse mtbdds to compute how many choices are in each row\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\tfor (i = 0; i < nm; i++) {\n\t\ttraverse_mtbdd_vect_rec(ddman, matrices_bdds[i], rvars, num_vars, 0, odd, 0, 1);\n\t}\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num choices in a state)\n\tmax = 0;\n\tfor (i = 1 ; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\tndsm->k = max;\n\t\n\t// now traverse mtbdds to compute how many transitions in each choice\n\tfor (i = 0; i < nc+1; i++) starts2[i] = 0;\n\tfor (i = 0; i < nm; i++) {\n\t\ttraverse_mtbdd_matr_rec(ddman, matrices[i], rvars, cvars, num_vars, 0, odd, odd, 0, 0, 10, false);\n\t\ttraverse_mtbdd_vect_rec(ddman, matrices_bdds[i], rvars, num_vars, 0, odd, 0, 2);\n\t}\n\t// and use this to compute the starts2 information\n\t// (and at same time, compute max num transitions in a choice)\n\tmax2 = 0;\n\tfor (i = 1; i < nc+1; i++) {\n\t\tif (starts2[i] > max2) max2 = starts2[i];\n\t\tstarts2[i] += starts2[i-1];\n\t}\n\t// recompute starts (because we altered them during last traversal)\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t\n\t// max num choices/transitions determines whether we store counts or starts:\n\tndsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\tndsm->use_counts &= (max2 < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// now traverse the mtbdd again to get the actual matrix entries\n\tfor (i = 0; i < nm; i++) {\n\t\ttraverse_mtbdd_matr_rec(ddman, matrices[i], rvars, cvars, num_vars, 0, odd, odd, 0, 0, 11, false);\n\t\ttraverse_mtbdd_vect_rec(ddman, matrices_bdds[i], rvars, num_vars, 0, odd, 0, 2);\n\t}\n\t// recompute starts (because we altered them during last traversal)\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// recompute starts2 (likewise)\n\tfor (i = nc; i > 0; i--) {\n\t\tstarts2[i] = starts2[i-1];\n\t}\n\tstarts2[0] = 0;\n\t\n\t// if it's safe to do so, replace starts/starts2 with (smaller) arrays of counts\n\tif (ndsm->use_counts) {\n\t\tndsm->row_counts = new unsigned char[n];\n\t\tfor (i = 0; i < n; i++) ndsm->row_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\tdelete[] starts; starts = NULL;\n\t\tndsm->choice_counts = new unsigned char[nc];\n\t\tfor (i = 0; i < nc; i++) ndsm->choice_counts[i] = (unsigned char)(starts2[i+1] - starts2[i]);\n\t\tdelete[] starts2; starts2 = NULL;\n\t\tndsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + (n+nc) * sizeof(unsigned char)) / 1024.0;\n\t} else {\n\t\tndsm->row_counts = (unsigned char*)starts;\n\t\tndsm->choice_counts = (unsigned char*)starts2;\n\t\tndsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + (n+nc) * sizeof(int)) / 1024.0;\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (ndsm) delete ndsm;\n\t\tif (matrices) delete[] matrices;\n\t\tif (matrices_bdds) {\n\t\t\tfor (i = 0; i < nm; i++) Cudd_RecursiveDeref(ddman, matrices_bdds[i]);\n\t\t\tdelete[] matrices_bdds;\n\t\t}\n\t\tif (starts) delete[] starts;\n\t\tif (starts2) delete[] starts2;\n\t\tthrow e;\n\t}\n\t\n\t// clear up memory\n\tfor (i = 0; i < nm; i++) {\n\t\tCudd_RecursiveDeref(ddman, matrices_bdds[i]);\n\t\t// nb: don't deref matrices array because that was just pointers, not new copies\n\t}\n\tdelete[] matrices;\n\tdelete[] matrices_bdds;\n\t\n\treturn ndsm;\n}\n\n//-----------------------------------------------------------------------------------\n\n// Build nondeterministic (MDP) sparse matrix for \"sub-MDP\".\n// This function basically exists to construct a sparse matrix representing the transition rewards for an MDP.\n// The complication is that we need to use the nondeterministic choice indexing of the main\n// MDP matrix, not the rewards matrix, otherwise we can't tell which reward is on which transition.\n// throws std::bad_alloc on out-of-memory\n\nNDSparseMatrix *build_sub_nd_sparse_matrix(DdManager *ddman, DdNode *mdp, DdNode *submdp, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, ODDNode *odd)\n{\n\tint i, n, nm, nc, nnz, max, max2;\n\tDdNode *tmp = NULL, **matrices = NULL, **submatrices = NULL, **matrices_bdds = NULL;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// create new data structure\n\tndsm = NULL; ndsm = new NDSparseMatrix();\n\t\n\t// get number of states from odd\n\tn = ndsm->n = odd->eoff+odd->toff;\n\t// get num of choices (prob. distributions) (USING MDP)\n\tCudd_Ref(mdp);\n\ttmp = DD_ThereExists(ddman, DD_Not(ddman, DD_Equals(ddman, mdp, 0)), cvars, num_vars);\n\tnc = ndsm->nc = (int)DD_GetNumMinterms(ddman, tmp, num_vars+num_ndvars);\n\t// get num of transitions (USING SUB-MDP)\n\tnnz = ndsm->nnz = (int)DD_GetNumMinterms(ddman, submdp, num_vars*2+num_ndvars);\n\t// break the two mtbdds (MDP AND SUB-MDP) into several (nm) mtbdds\n\ttmp = DD_ThereExists(ddman, tmp, rvars, num_vars);\n\tnm = (int)DD_GetNumMinterms(ddman, tmp, num_ndvars);\n\tCudd_RecursiveDeref(ddman, tmp);\n\tmatrices = new DdNode*[nm];\n\tsubmatrices = new DdNode*[nm];\n\tcount = 0;\n\tsplit_mdp_and_sub_mdp_rec(ddman, mdp, submdp, ndvars, num_ndvars, 0, matrices, submatrices);\n\t// and for each one create a bdd storing which rows/choices are non-empty (USING MDP)\n\tmatrices_bdds = new DdNode*[nm];\n\tfor (i = 0; i < nm; i++) {\n\t\tCudd_Ref(matrices[i]);\n\t\tmatrices_bdds[i] = DD_ThereExists(ddman, DD_Not(ddman, DD_Equals(ddman, matrices[i], 0)), cvars, num_vars);\n\t}\n\t\n\t// create arrays\n\tndsm->non_zeros = new double[nnz];\n\tndsm->cols = new unsigned int[nnz];\n\tstarts = NULL; starts = new int[n+1];\n\tstarts2 = NULL; starts2 = new int[nc+1];\n\t\n\t// first traverse mtbdds to compute how many choices are in each row (USING MDP)\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\tfor (i = 0; i < nm; i++) {\n\t\ttraverse_mtbdd_vect_rec(ddman, matrices_bdds[i], rvars, num_vars, 0, odd, 0, 1);\n\t}\n\t// and use this to compute the starts information\n\t// (and at same time, compute max num choices in a state)\n\tmax = 0;\n\tfor (i = 1 ; i < n+1; i++) {\n\t\tif (starts[i] > max) max = starts[i];\n\t\tstarts[i] += starts[i-1];\n\t}\n\tndsm->k = max;\n\t\n\t// now traverse mtbdds to compute how many transitions in each choice (USING SUB-MDP)\n\tfor (i = 0; i < nc+1; i++) starts2[i] = 0;\n\tfor (i = 0; i < nm; i++) {\n\t\ttraverse_mtbdd_matr_rec(ddman, submatrices[i], rvars, cvars, num_vars, 0, odd, odd, 0, 0, 10, false);\n\t\ttraverse_mtbdd_vect_rec(ddman, matrices_bdds[i], rvars, num_vars, 0, odd, 0, 2);\n\t}\n\t// and use this to compute the starts2 information\n\t// (and at same time, compute max num transitions in a choice)\n\tmax2 = 0;\n\tfor (i = 1; i < nc+1; i++) {\n\t\tif (starts2[i] > max2) max2 = starts2[i];\n\t\tstarts2[i] += starts2[i-1];\n\t}\n\t// recompute starts (because we altered them during last traversal)\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t\n\t// max num choices/transitions determines whether we store counts or starts:\n\tndsm->use_counts = (max < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\tndsm->use_counts &= (max2 < (unsigned int)(1 << (8*sizeof(unsigned char))));\n\t\n\t// now traverse the mtbdd again to get the actual matrix entries (USING SUB-MDP)\n\tfor (i = 0; i < nm; i++) {\n\t\ttraverse_mtbdd_matr_rec(ddman, submatrices[i], rvars, cvars, num_vars, 0, odd, odd, 0, 0, 11, false);\n\t\ttraverse_mtbdd_vect_rec(ddman, matrices_bdds[i], rvars, num_vars, 0, odd, 0, 2);\n\t}\n\t// recompute starts (because we altered them during last traversal)\n\tfor (i = n; i > 0; i--) {\n\t\tstarts[i] = starts[i-1];\n\t}\n\tstarts[0] = 0;\n\t// recompute starts2 (likewise)\n\tfor (i = nc; i > 0; i--) {\n\t\tstarts2[i] = starts2[i-1];\n\t}\n\tstarts2[0] = 0;\n\t\n\t// if it's safe to do so, replace starts/starts2 with (smaller) arrays of counts\n\tif (ndsm->use_counts) {\n\t\tndsm->row_counts = new unsigned char[n];\n\t\tfor (i = 0; i < n; i++) ndsm->row_counts[i] = (unsigned char)(starts[i+1] - starts[i]);\n\t\tdelete[] starts; starts = NULL;\n\t\tndsm->choice_counts = new unsigned char[nc];\n\t\tfor (i = 0; i < nc; i++) ndsm->choice_counts[i] = (unsigned char)(starts2[i+1] - starts2[i]);\n\t\tdelete[] starts2; starts2 = NULL;\n\t\tndsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + (n+nc) * sizeof(unsigned char)) / 1024.0;\n\t} else {\n\t\tndsm->row_counts = (unsigned char*)starts;\n\t\tndsm->choice_counts = (unsigned char*)starts2;\n\t\tndsm->mem = (nnz * (sizeof(double) + sizeof(unsigned int)) + (n+nc) * sizeof(int)) / 1024.0;\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (ndsm) delete ndsm;\n\t\tif (matrices) delete[] matrices;\n\t\tif (submatrices) delete[] submatrices;\n\t\tif (matrices_bdds) {\n\t\t\tfor (i = 0; i < nm; i++) Cudd_RecursiveDeref(ddman, matrices_bdds[i]);\n\t\t\tdelete[] matrices_bdds;\n\t\t}\n\t\tif (starts) delete[] starts;\n\t\tif (starts2) delete[] starts2;\n\t\tthrow e;\n\t}\n\t\n\t// clear up memory\n\tfor (i = 0; i < nm; i++) {\n\t\tCudd_RecursiveDeref(ddman, matrices_bdds[i]);\n\t\t// nb: don't deref matrices/submatrices array because that was just pointers, not new copies\n\t}\n\tdelete[] matrices;\n\tdelete[] submatrices;\n\tdelete[] matrices_bdds;\n\t\n\treturn ndsm;\n}\n\n//------------------------------------------------------------------------------\n\n// Build nondeterministic (mdp) action vector to accompany a sparse matrix\n// (i.e. a vector containing for every state and nondet choice, an index\n// into the list of all action labels).\n// Store the resulting vector in the 'actions' member of the passed in NDSparseMatrix.\n// throws std::bad_alloc on out-of-memory\nvoid build_nd_action_vector(DdManager *ddman, DdNode *mdp, DdNode *trans_actions, NDSparseMatrix *mdp_ndsm, DdNode **rvars, DdNode **cvars, int num_vars, DdNode **ndvars, int num_ndvars, ODDNode *odd)\n{\n\tint i, n, nm, nc;\n\tDdNode *tmp = NULL, **matrices = NULL, **submatrices = NULL, **matrices_bdds = NULL;\n\t\n\t// try/catch for memory allocation/deallocation\n\ttry {\n\t\n\t// get stats from mdp sparse storage (num states/choices)\n\tn = mdp_ndsm->n;\n\tnc = mdp_ndsm->nc;\n\t// break the mtbdd storing the action info into several (nm) mtbdds\n\t// like for build_sub_nd_sparse_matrix above, we have to simultaneously traverse and\n\t// split the mtbdd for the mdp itself - this to make sure that all our indices match up\n\t// (more precisely, things go wrong where mtbdd storing the action info has a zero - meaning\n\t// there is no action label - where there is a non-zero probability in the mdp)\n\tCudd_Ref(mdp);\n\ttmp = DD_ThereExists(ddman, DD_Not(ddman, DD_Equals(ddman, mdp, 0)), cvars, num_vars);\n\ttmp = DD_ThereExists(ddman, tmp, rvars, num_vars);\n\tnm = (int)DD_GetNumMinterms(ddman, tmp, num_ndvars);\n\tCudd_RecursiveDeref(ddman, tmp);\n\tmatrices = new DdNode*[nm];\n\tsubmatrices = new DdNode*[nm];\n\tcount = 0;\n\tsplit_mdp_and_sub_mdp_rec(ddman, mdp, trans_actions, ndvars, num_ndvars, 0, matrices, submatrices);\n\t// and for each one create a bdd storing which rows are non-empty\n\tmatrices_bdds = new DdNode*[nm];\n\tfor (i = 0; i < nm; i++) {\n\t\tCudd_Ref(matrices[i]);\n\t\tmatrices_bdds[i] = DD_ThereExists(ddman, DD_Not(ddman, DD_Equals(ddman, matrices[i], 0)), cvars, num_vars);\n\t}\n\t\n\t// create arrays\n\tactions = NULL; actions = new int[nc];\n\tstarts = NULL; starts = new int[n+1];\n\t\n\t// build the (temporary) array 'starts' (like was done when building the sparse matrix for the mdp).\n\t// in fact, this information is retrievable from the sparse matrix, but it may have\n\t// been converted to counts, rather than offsets, so its easier to rebuild it.\n\t// first traverse mtbdds to compute how many choices are in each row\n\tfor (i = 0; i < n+1; i++) starts[i] = 0;\n\tfor (i = 0; i < nm; i++) {\n\t\ttraverse_mtbdd_vect_rec(ddman, matrices_bdds[i], rvars, num_vars, 0, odd, 0, 1);\n\t}\n\t// and use this to compute the starts information\n\tfor (i = 1 ; i < n+1; i++) {\n\t\tstarts[i] += starts[i-1];\n\t}\n\t\n\t// initialise the 'actions' array\n\t// (necessary because tau actions, with index 0, are not discovered\n\t//  by the call to traverse_mtbdd_vect_rec(..., 3) below)\n\tfor (i = 0; i < nc; i++) actions[i] = 0;\n\t// now traverse the mtbdd to get the actual entries (action indices)\n\tfor (i = 0; i < nm; i++) {\n\t\ttraverse_mtbdd_vect_rec(ddman, submatrices[i], rvars, num_vars, 0, odd, 0, 3);\n\t\ttraverse_mtbdd_vect_rec(ddman, matrices_bdds[i], rvars, num_vars, 0, odd, 0, 2);\n\t}\n\t\n\t// try/catch for memory allocation/deallocation\n\t} catch(std::bad_alloc e) {\n\t\tif (actions) delete[] actions;\n\t\tif (matrices) delete[] matrices;\n\t\tif (submatrices) delete[] submatrices;\n\t\tif (matrices_bdds) {\n\t\t\tfor (i = 0; i < nm; i++) Cudd_RecursiveDeref(ddman, matrices_bdds[i]);\n\t\t\tdelete[] matrices_bdds;\n\t\t}\n\t\tif (starts) delete[] starts;\n\t\tthrow e;\n\t}\n\t\n\t// clear up memory\n\tfor (i = 0; i < nm; i++) {\n\t\tCudd_RecursiveDeref(ddman, matrices_bdds[i]);\n\t\t// nb: don't deref matrices/submatrices array because that was just pointers, not new copies\n\t}\n\tdelete[] starts;\n\tdelete[] matrices;\n\tdelete[] submatrices;\n\tdelete[] matrices_bdds;\n\n\tmdp_ndsm->actions = actions;\n}\n\n//------------------------------------------------------------------------------\n\nvoid split_mdp_rec(DdManager *ddman, DdNode *dd, DdNode **ndvars, int num_ndvars, int level, DdNode **matrices)\n{\n\tDdNode *e, *t;\n\t\n\t// base case - empty matrix\n\tif (dd == Cudd_ReadZero(ddman)) return;\n\t\n\t// base case - nonempty matrix\n\tif (level == num_ndvars) {\n\t\tmatrices[count++] = dd;\n\t\treturn;\n\t}\n\t\n\t// recurse\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(ndvars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\t\n\tsplit_mdp_rec(ddman, e, ndvars, num_ndvars, level+1, matrices);\n\tsplit_mdp_rec(ddman, t, ndvars, num_ndvars, level+1, matrices);\n}\n\nvoid split_mdp_and_sub_mdp_rec(DdManager *ddman, DdNode *dd, DdNode *subdd, DdNode **ndvars, int num_ndvars, int level, DdNode **matrices, DdNode **submatrices)\n{\n\tDdNode *e, *t, *e2, *t2;\n\t\n\t// base case - empty matrix\n\tif (dd == Cudd_ReadZero(ddman)) return;\n\t\n\t// base case - nonempty matrix\n\tif (level == num_ndvars) {\n\t\tmatrices[count] = dd;\n\t\tsubmatrices[count] = subdd;\n\t\tcount++;\n\t\treturn;\n\t}\n\t\n\t// recurse\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(ndvars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\tif (Cudd_NodeReadIndex(subdd) > Cudd_NodeReadIndex(ndvars[level])) {\n\t\te2 = t2 = subdd;\n\t}\n\telse {\n\t\te2 = Cudd_E(subdd);\n\t\tt2 = Cudd_T(subdd);\n\t}\n\t\n\tsplit_mdp_and_sub_mdp_rec(ddman, e, e2, ndvars, num_ndvars, level+1, matrices, submatrices);\n\tsplit_mdp_and_sub_mdp_rec(ddman, t, t2, ndvars, num_ndvars, level+1, matrices, submatrices);\n}\n\n//------------------------------------------------------------------------------\n\n// traverses the mtbdd and gets all the MATRIX entries out\n// does different things depending on the value of 'code'\n// if tranpose flag is true, actually extract from tranpose of matrix\n\nvoid traverse_mtbdd_matr_rec(DdManager *ddman, DdNode *dd, DdNode **rvars, DdNode **cvars, int num_vars, int level, ODDNode *row, ODDNode *col, int r, int c, int code, bool transpose)\n{\n\tDdNode *e, *t, *ee, *et, *te, *tt;\n\tint i, dist_num;\n\tdouble *dist, d;\n\t\n\t// base case - zero terminal\n\tif (dd == Cudd_ReadZero(ddman)) return;\n\t\n\t// base case - non zero terminal\n\tif (level == num_vars) {\n\t\tswitch (code) {\n\t\t\n\t\t// row major - first pass\n\t\tcase 1:\n\t\t\tstarts[(transpose?c:r)+1]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// row major - second pass\n\t\tcase 2:\n\t\t\trmsm->non_zeros[starts[(transpose?c:r)]] = Cudd_V(dd);\n\t\t\trmsm->cols[starts[(transpose?c:r)]] = (transpose?r:c);\n\t\t\tstarts[(transpose?c:r)]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// column major - first pass\n\t\tcase 3:\n\t\t\tstarts[(transpose?r:c)+1]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// column major - second pass\n\t\tcase 4:\n\t\t\tcmsm->non_zeros[starts[(transpose?r:c)]] = Cudd_V(dd);\n\t\t\tcmsm->rows[starts[(transpose?r:c)]] = (transpose?c:r);\n\t\t\tstarts[(transpose?r:c)]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// row/column - only pass\n\t\tcase 5:\n\t\t\trcsm->non_zeros[count] = Cudd_V(dd);\n\t\t\trcsm->rows[count] = (transpose?c:r);\n\t\t\trcsm->cols[count] = (transpose?r:c);\n\t\t\tcount++;\n\t\t\tbreak;\n\t\t\t\n\t\t// compact modified sparse row - first pass\n\t\tcase 6:\n\t\t\tstarts[(transpose?c:r)+1]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// compact modified sparse row - second pass\n\t\tcase 7:\n\t\t\t// try and find value\n\t\t\tdist = cmsrsm->dist;\n\t\t\tdist_num = cmsrsm->dist_num;\n\t\t\td = Cudd_V(dd);\n\t\t\tfor (i = 0; i < dist_num; i++) if (dist[i] == d) break;\n\t\t\t// if it's not there, add it\n\t\t\tif (i == dist_num) {\n\t\t\t\tdist[i] = d;\n\t\t\t\tcmsrsm->dist_num++;\n\t\t\t}\n\t\t\t// store info\n\t\t\tcmsrsm->cols[starts[(transpose?c:r)]] = (unsigned int)(((unsigned int)(transpose?r:c) << cmsrsm->dist_shift) + (unsigned int)i);\n\t\t\tstarts[(transpose?c:r)]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// compact modified sparse column - first pass\n\t\tcase 8:\n\t\t\tstarts[(transpose?r:c)+1]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// compact modified sparse column - second pass\n\t\tcase 9:\n\t\t\t// try and find value\n\t\t\tdist = cmscsm->dist;\n\t\t\tdist_num = cmscsm->dist_num;\n\t\t\td = Cudd_V(dd);\n\t\t\tfor (i = 0; i < dist_num; i++) if (dist[i] == d) break;\n\t\t\t// if it's not there, add it\n\t\t\tif (i == dist_num) {\n\t\t\t\tdist[i] = d;\n\t\t\t\tcmscsm->dist_num++;\n\t\t\t}\n\t\t\t// store info\n\t\t\tcmscsm->rows[starts[(transpose?r:c)]] = (unsigned int)(((unsigned int)(transpose?c:r) << cmscsm->dist_shift) + (unsigned int)i);\n\t\t\tstarts[(transpose?r:c)]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// mdp - first pass\n\t\tcase 10:\n\t\t\tstarts2[starts[(transpose?c:r)]+1]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// mdp - second pass\n\t\tcase 11:\n\t\t\tndsm->non_zeros[starts2[starts[(transpose?c:r)]]] = Cudd_V(dd);\n\t\t\tndsm->cols[starts2[starts[(transpose?c:r)]]] = (transpose?r:c);\n\t\t\tstarts2[starts[(transpose?c:r)]]++;\n\t\t\tbreak;\n\t\t\n\t\t// row major - second pass with actions\n\t\tcase 12:\n\t\t\trmsm->non_zeros[starts[(transpose?c:r)]] = Cudd_V(dd);\n\t\t\trmsm->cols[starts[(transpose?c:r)]] = (transpose?r:c);\n\t\t\trmsm->actions[starts[(transpose?c:r)]] = action_count;\n\t\t\tstarts[(transpose?c:r)]++;\n\t\t\tbreak;\n\t\t}\n\t\treturn;\n\t}\n\t\n\t// recurse\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(cvars[level])) {\n\t\tee = et = te = tt = dd;\n\t}\n\telse if (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(rvars[level])) {\n\t\tee = te = Cudd_E(dd);\n\t\tet = tt = Cudd_T(dd);\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tif (Cudd_NodeReadIndex(e) > Cudd_NodeReadIndex(cvars[level])) {\n\t\t\tee = et = e;\n\t\t}\n\t\telse {\n\t\t\tee = Cudd_E(e);\n\t\t\tet = Cudd_T(e);\n\t\t}\n\t\tt = Cudd_T(dd);\n\t\tif (Cudd_NodeReadIndex(t) > Cudd_NodeReadIndex(cvars[level])) {\n\t\t\tte = tt = t;\n\t\t}\n\t\telse {\n\t\t\tte = Cudd_E(t);\n\t\t\ttt = Cudd_T(t);\n\t\t}\n\t}\n\n\ttraverse_mtbdd_matr_rec(ddman, ee, rvars, cvars, num_vars, level+1, row->e, col->e, r, c, code, transpose);\n\ttraverse_mtbdd_matr_rec(ddman, et, rvars, cvars, num_vars, level+1, row->e, col->t, r, c+col->eoff, code, transpose);\n\ttraverse_mtbdd_matr_rec(ddman, te, rvars, cvars, num_vars, level+1, row->t, col->e, r+row->eoff, c, code, transpose);\n\ttraverse_mtbdd_matr_rec(ddman, tt, rvars, cvars, num_vars, level+1, row->t, col->t, r+row->eoff, c+col->eoff, code, transpose);\n}\n\n//------------------------------------------------------------------------------\n\n// traverses the mtbdd and gets all the VECTOR entries out\n// does different things depending on the value of 'code'\n\nvoid traverse_mtbdd_vect_rec(DdManager *ddman, DdNode *dd, DdNode **vars, int num_vars, int level, ODDNode *odd, int i, int code)\n{\n\tDdNode *e, *t;\n\t\n\t// base case - zero terminal\n\tif (dd == Cudd_ReadZero(ddman)) return;\n\t\n\t// base case - non zero terminal\n\tif (level == num_vars) {\n\t\tswitch (code) {\n\t\t\n\t\t// mdp - first pass\n\t\tcase 1:\n\t\t\tstarts[i+1]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// mdp - second pass\n\t\tcase 2:\n\t\t\tstarts[i]++;\n\t\t\tbreak;\n\t\t\t\n\t\t// mdp action vector - single pass\n\t\tcase 3:\n\t\t\tactions[starts[i]] = (int)Cudd_V(dd);\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\treturn;\n\t}\n\t\n\t// recurse\n\tif (Cudd_NodeReadIndex(dd) > Cudd_NodeReadIndex(vars[level])) {\n\t\te = t = dd;\n\t}\n\telse {\n\t\te = Cudd_E(dd);\n\t\tt = Cudd_T(dd);\n\t}\n\n\ttraverse_mtbdd_vect_rec(ddman, e, vars, num_vars, level+1, odd->e, i, code);\n\ttraverse_mtbdd_vect_rec(ddman, t, vars, num_vars, level+1, odd->t, i+odd->eoff, code);\n}\n\n//-----------------------------------------------------------------------------------\n\n// compute negative sum of elements in each row\n// if transpose flag is true, matrix was previously transposed so sum for columns instead\n// throws std::bad_alloc on out-of-memory\n\ndouble *rm_negative_row_sums(RMSparseMatrix *rmsm) { return rm_negative_row_sums(rmsm, false); }\ndouble *cm_negative_row_sums(CMSparseMatrix *cmsm) { return cm_negative_row_sums(cmsm, false); }\ndouble *cmsr_negative_row_sums(CMSRSparseMatrix *cmsrsm) { return cmsr_negative_row_sums(cmsrsm, false); }\ndouble *cmsc_negative_row_sums(CMSCSparseMatrix *cmscsm) { return cmsc_negative_row_sums(cmscsm, false); }\n\ndouble *rm_negative_row_sums(RMSparseMatrix *rmsm, bool transpose)\n{\n\tint i, j, l, h;\n\tdouble *diags = NULL;\n\tint n = rmsm->n;\n\tdouble *non_zeros = rmsm->non_zeros;\n\tunsigned char *row_counts = rmsm->row_counts;\n\tint *row_starts = (int *)rmsm->row_counts;\n\tbool use_counts = rmsm->use_counts;\n\tunsigned int *cols = rmsm->cols;\n\t\n\t// allocate new vector\n\tdiags = new double[n];\n\tfor (i = 0; i < n; i++) {\n\t\tdiags[i] = 0;\n\t}\n\t// loop through rows\n\th = 0;\n\tfor (i = 0; i < n; i++) {\n\t\t// loop through entries in this row\n\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\telse { l = h; h += row_counts[i]; }\n\t\tfor (j = l; j < h; j++) {\n\t\t\tdiags[(transpose?cols[j]:i)] -= non_zeros[j];\n\t\t}\n\t}\n\t\n\treturn diags;\n}\n\ndouble *cm_negative_row_sums(CMSparseMatrix *cmsm, bool transpose)\n{\n\tint i, j, l, h;\n\tdouble *diags = NULL;\n\tint n = cmsm->n;\n\tdouble *non_zeros = cmsm->non_zeros;\n\tunsigned char *col_counts = cmsm->col_counts;\n\tint *col_starts = (int *)cmsm->col_counts;\n\tbool use_counts = cmsm->use_counts;\n\tunsigned int *rows = cmsm->rows;\n\t\n\t// allocate new vector\n\tdiags = new double[n];\n\tfor (i = 0; i < n; i++) {\n\t\tdiags[i] = 0;\n\t}\n\t// loop through columns\n\th = 0;\n\tfor (i = 0; i < n; i++) {\n\t\t// loop through entries in this column\n\t\tif (!use_counts) { l = col_starts[i]; h = col_starts[i+1]; }\n\t\telse { l = h; h += col_counts[i]; }\n\t\tfor (j = l; j < h; j++) {\n\t\t\tdiags[(transpose?i:rows[j])] -= non_zeros[j];\n\t\t}\n\t}\n\t\n\treturn diags;\n}\n\ndouble *cmsr_negative_row_sums(CMSRSparseMatrix *cmsrsm, bool transpose)\n{\n\tint i, j, l, h;\n\tdouble *diags = NULL;\n\tint n = cmsrsm->n;\n\tunsigned char *row_counts = cmsrsm->row_counts;\n\tint *row_starts = (int *)cmsrsm->row_counts;\n\tbool use_counts = cmsrsm->use_counts;\n\tunsigned int *cols = cmsrsm->cols;\n\tdouble *dist = cmsrsm->dist;\n\tint dist_shift = cmsrsm->dist_shift;\n\tint dist_mask = cmsrsm->dist_mask;\n\t\n\t// allocate new vector\n\tdiags = new double[n];\n\tfor (i = 0; i < n; i++) {\n\t\tdiags[i] = 0;\n\t}\n\t// loop through rows of submatrix\n\th = 0;\n\tfor (i = 0; i < n; i++) {\n\t\t// loop through entries in this row\n\t\tif (!use_counts) { l = row_starts[i]; h = row_starts[i+1]; }\n\t\telse { l = h; h += row_counts[i]; }\n\t\tfor (j = l; j < h; j++) {\n\t\t\tdiags[(transpose?((int)(cols[j] >> dist_shift)):i)] -= dist[(int)(cols[j] & dist_mask)];\n\t\t}\n\t}\n\t\n\treturn diags;\n}\n\ndouble *cmsc_negative_row_sums(CMSCSparseMatrix *cmscsm, bool transpose)\n{\n\tint i, j, l, h;\n\tdouble *diags = NULL;\n\tint n = cmscsm->n;\n\tunsigned char *col_counts = cmscsm->col_counts;\n\tint *col_starts = (int *)cmscsm->col_counts;\n\tbool use_counts = cmscsm->use_counts;\n\tunsigned int *rows = cmscsm->rows;\n\tdouble *dist = cmscsm->dist;\n\tint dist_shift = cmscsm->dist_shift;\n\tint dist_mask = cmscsm->dist_mask;\n\t\n\t// allocate new vector\n\tdiags = new double[n];\n\tfor (i = 0; i < n; i++) {\n\t\tdiags[i] = 0;\n\t}\n\t// loop through columns of submatrix\n\th = 0;\n\tfor (i = 0; i < n; i++) {\n\t\t// loop through entries in this column\n\t\tif (!use_counts) { l = col_starts[i]; h = col_starts[i+1]; }\n\t\telse { l = h; h += col_counts[i]; }\n\t\tfor (j = l; j < h; j++) {\n\t\t\tdiags[(transpose?i:((int)(rows[j] >> dist_shift)))] -= dist[(int)(rows[j] & dist_mask)];\n\t\t}\n\t}\n\t\n\treturn diags;\n}\n\n//------------------------------------------------------------------------------\n\n"
  },
  {
    "path": "prism/src/sparse/sparse_adv.cc",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t* Hongyang Qu <hongyang.qu@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n//#include <cmath>\n//#include \"dv.h\"\n#include \"sparse_adv.h\"\n//#include \"PrismNativeGlob.h\"\n//#include <new>\n\n//------------------------------------------------------------------------------\n\n// Export the model (MDP) as a dot file\n\nvoid export_model(NDSparseMatrix *ndsm, int n, int *yes_vec, int start_index)\n{\n\tFILE *f;\n\tint i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, count;\n\tdouble d1, d2, kb, kbt;\n\t\n\t// Extract required info from sparse matrix\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\t\n\t/* write the produce mdp to file model.dot */\n\tprintf(\"Writing the model to model.dot\\n\"); fflush(stdout);\n\n\tf = fopen(\"model.dot\", \"w\"); /* create a file for writing */\n\t//f = NULL;\n\tif(f==NULL) {\n\t\tprintf(\"\\nWarning: Output of graph cancelled (could not open file \\\"%s\\\").\\n\", \"model.dot\");\n\t} else {\n\t\tfprintf(f, \"digraph model {\\n\");\n\t\tfor(i=0; i<n; i++)\n\t\tif(i == start_index)\n\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=ellipse]\\n\", i, i);\n\t\telse if(yes_vec[i]> 0)\n\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=doublecircle]\\n\", i, i);\n\t\telse\n\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=circle]\\n\", i, i);\n\t\tcount = n; l1 = h1 = l2 = h2 = 0;\n\t\tfor(i=0; i<n; i++) {\n\t\t\tif (!use_counts) {\n\t\t\t\tl1 = row_starts[i];\n\t\t\t\th1 = row_starts[i+1];\n\t\t\t} else {\n\t\t\t\tl1 = h1;\n\t\t\t\th1 += row_counts[i];\n\t\t\t}\n\t\t\tfor (j = l1; j < h1; j++) {\n\t\t\t\tif (!use_counts) {\n\t\t\t\t\tl2 = choice_starts[j];\n\t\t\t\t\th2 = choice_starts[j+1];\n\t\t\t\t} else {\n\t\t\t\t\tl2 = h2;\n\t\t\t\t\th2 += choice_counts[j];\n\t\t\t\t}\n\t\t\t\tif(h2-l2>1) {\n\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=point]\\n\", count);\n\t\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%d\\\"]\\n\", i, count, j);\n\t\t\t\t\tfor(k=l2; k<h2; k++)\n\t\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%g(%d)\\\"]\\n\", count,\n\t\t\t\t\t\t\tcols[k], non_zeros[k], k);\n\t\t\t\t\tcount ++;\n\t\t\t\t} else\n\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%d:%g(%d)\\\"]\\n\", i,\n\t\t\t\t\t\tcols[l2], j, non_zeros[l2], l2);\n\t\t\t}\n\t\t}\n\t\tfprintf(f, \"}\\n\");\n\t\tfclose(f);\n\t}\n}\n\n//------------------------------------------------------------------------------\n\n// Export the adversary (as a dot file)\n\nvoid export_adversary_ltl_dot(NDSparseMatrix *ndsm, int n, long nnz, int *yes_vec, double *maybe_vec, int num_lp_vars, int *map_var, double *lp_soln, int start_index)\n{\n\tlong sp_nodes = 0; // pointer of dot nodes\n\tlong extra_node = n; // index of intermediate nodes for actions\n\tlong sp_edges = 0; // pointer of dot edges\n\t//int queue[n]; // search queue\n\tint *queue;\n\tlong head = 0; // pointer to the head of the queue\n\tlong tail = 0; // pointer to the tail of the queue\n\t//int nodes[n]; // indicate whether the node has been visited\n\tint *nodes;\n\n\tFILE *f;\n\tint i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, count;\n\tdouble d1, d2, kb, kbt;\n\n\t// Extract required info from sparse matrix\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\t\n\tqueue = new int[n];\n\tnodes = new int[n];\n\tfor(i=0; i<n; i++)\n\t\tnodes[i] = 0;\n\t\n\tint (*dot_nodes)[2];\n\tint (*dot_edges)[2];\n\tdouble *edge_probabilities;\n\tint *terminate_nodes;\n\t//printf(\"allocated memory for local variables:\\n\"); \n\t//printf(\"n=%1d, num_lp_vars=%1d, nnz=%1d\\n\", n, num_lp_vars, nnz);\n\t//fflush(stdout);\n\t\n\t//int dot_nodes[n+num_lp_vars][2]; // first entry: node number, second: shape \n\t//int dot_edges[nnz+num_lp_vars][2]; // first entry: source node, second: target\n\t//double edge_probabilities[nnz+num_lp_vars]; // edge's probability\n\t\n\tdot_nodes = new int[n+num_lp_vars][2];\n\tdot_edges = new int[nnz+num_lp_vars][2];\n\tedge_probabilities = new double[nnz+num_lp_vars];\n\tterminate_nodes = new int[n]; // the entry stores the node number for newly added terminate nodes\n\t\n\tfor(i=0; i<n; i++)\n\t\tterminate_nodes[i] = -1;\n\t\n\t// put the initial state in the queue and dot_nodes\n\tqueue[tail++] = start_index;\n\tdot_nodes[sp_nodes][0] = start_index;\n\tdot_nodes[sp_nodes++][1] = 0; // shape = 0: ellipse, 1: circle, 2: point, 3: doublecircle, 4: box\n\t\n\t// recursive procedure\n\tint head_node = -1;\n\twhile(head < tail) {\n\t\thead_node = queue[head++];\n\t\t\n\t\tif(nodes[head_node] == 1)\n\t\t\tcontinue;\n\t\tnodes[head_node] = 1;\n\t\t// If the head node is a target state, do nothing\n\t\tif(yes_vec[head_node]> 0 || maybe_vec[head_node]> 0) {\n\t\t\t\t\t\t\t// the number of branches in the current state\n\t\t\th1 = map_var[head_node+1] - map_var[head_node];\n\t\t\t\n\t\t\tdouble sum = 0;\n\t\t\tfor(i=0; i<h1; i++)\n\t\t\t\tsum += lp_soln[map_var[head_node] + i];\n\t\t\t\n\t\t\tfor(i=0; i<h1; i++) {\n\t\t\t\t// test if the action has non-zero probability\n\t\t\t\tif(lp_soln[map_var[head_node] + i]> 0) {\n\t\t\t\t\tif(yes_vec[head_node]> 0 && i==h1-1) { // extra transition\n\t\t\t\t\t\t// add an intermediate node to dot_nodes\n\t\t\t\t\t\tif(terminate_nodes[head_node] < 0) {\n\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = extra_node;\n\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 4;\n\t\t\t\t\t\t\tdot_edges[sp_edges][1] = extra_node;\n\t\t\t\t\t\t\tterminate_nodes[head_node] = extra_node;\n\t\t\t\t\t\t} else\n\t\t\t\t\t\t\tdot_edges[sp_edges][1] = terminate_nodes[head_node];\n\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t//edge_probabilities[sp_edges++] = lp_soln[map_var[head_node] + i];\n\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? lp_soln[map_var[head_node] + i] :\n\t\t\t\t\t\t\tlp_soln[map_var[head_node] + i]/sum;\n\t\t\t\t\t\textra_node++;\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// get all successor states of this action\n\t\t\t\t\t\t// First: locate the action\n\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\tl1 = row_starts[head_node];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl1 = 0;\n\t\t\t\t\t\t\tfor(j=0; j<head_node; j++)\n\t\t\t\t\t\t\t\tl1 += row_counts[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tl1 += i;\n\t\t\t\t\t\t\n\t\t\t\t\t\t// Second: find all columns for this choice\n\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\tl2 = choice_starts[l1];\n\t\t\t\t\t\t\th2 = choice_starts[l1+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2 = 0;\n\t\t\t\t\t\t\tfor(j=0; j<l1; j++)\n\t\t\t\t\t\t\t\tl2 += choice_counts[j];\n\t\t\t\t\t\t\th2 = l2 + choice_counts[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif(h2-l2>1) {\n\t\t\t\t\t\t\t// add an intermediate node to dot_nodes\n\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = extra_node;\n\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 2;\n\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\tdot_edges[sp_edges][1] = extra_node;\n\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t//edge_probabilities[sp_edges++] = lp_soln[map_var[head_node] + i];\n\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? lp_soln[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\tlp_soln[map_var[head_node] + i]/sum;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tfor(j=l2; j<h2; j++) {\n\t\t\t\t\t\t\t\t// add the successor state to dot_nodes\n\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = cols[j];\n\t\t\t\t\t\t\t\tif(yes_vec[cols[j]]> 0)\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 3;\n\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 1;\n\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = extra_node;\n\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = cols[j];\n\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = non_zeros[j];\n\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\tif((maybe_vec[cols[j]]> 0 || yes_vec[cols[j]]> 0) &&\n\t\t\t\t\t\t\t\t\t nodes[cols[j]] == 0)\n\t\t\t\t\t\t\t\t\tqueue[tail++] = cols[j];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\textra_node++;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t// add the successor state to dot_nodes\n\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = cols[l2];\n\t\t\t\t\t\t\tif(yes_vec[cols[l2]]> 0)\n\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 3;\n\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 1;\n\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\tdot_edges[sp_edges][1] = cols[l2];\n\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t//edge_probabilities[sp_edges++] = lp_soln[map_var[head_node] + i];\n\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? lp_soln[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\tlp_soln[map_var[head_node] + i]/sum;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tif((maybe_vec[cols[l2]]> 0 || yes_vec[cols[l2]]> 0) &&\n\t\t\t\t\t\t\t\t nodes[cols[l2]] == 0) {\n\t\t\t\t\t\t\t\tqueue[tail++] = cols[l2];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\t\n\t\n\tprintf(\"generating adversary file\\n\"); fflush(stdout);\n\t\n\t// write to file\n\tf = fopen(\"adversary.dot\", \"w\"); /* create a file for writing */\n\tif(f==NULL) {\n\t\tprintf(\"\\nWarning: Output of adversary cancelled (could not open file \\\"%s\\\").\\n\", \"adversary.dot\");\n\t} else {\n\t\tfprintf(f, \"digraph adversary {\\n\");\n\t\tfor(i=0; i<sp_nodes; i++) {\n\t\t\tif(dot_nodes[i][0] >= n) {\n\t\t\t\tif(dot_nodes[i][1] == 2)\n\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=point]\\n\", dot_nodes[i][0]);\n\t\t\t\telse\n\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=box, fillcolor=black]\\n\", dot_nodes[i][0]);\n\t\t\t} else\n\t\t\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=%s]\\n\", dot_nodes[i][0],\n\t\t\t\t\t\t\t\tdot_nodes[i][0],\n\t\t\t\t\t\t\t\t((dot_nodes[i][1]==0)? \"ellipse\" :\n\t\t\t\t\t\t\t\t ((dot_nodes[i][1]==1)? \"circle\" : \"doublecircle\")));\n\t\t}\n\t\tfor(i=0; i<sp_edges; i++) {\n\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%g\\\"]\\n\", dot_edges[i][0],\n\t\t\t\t\t\t\tdot_edges[i][1], edge_probabilities[i]);\n\t\t}\n\t\tfprintf(f, \"}\\n\");\n\t\tfclose(f);\n\t}\n\t\n\tdelete[] dot_nodes;\n\tdelete[] dot_edges;\n\tdelete[] edge_probabilities;\n\tdelete[] terminate_nodes;\n\t\n\tdelete[] queue;\n\tdelete[] nodes;\n}\n\n\n//------------------------------------------------------------------------------\n\n// Export the adversary (as a dot file)\n\nvoid export_adversary_ltl_dot_reward(const char *export_adv_filename, NDSparseMatrix *ndsm, \n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t int *actions, const char** action_names, \n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t int n, long nnz, int *yes_vec, double *maybe_vec, \n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t int num_lp_vars, int *map_var, double *lp_soln, double *back_arr_reals, \n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t int start_index)\n{\n\tlong sp_nodes = 0; // pointer of dot nodes\n\tlong extra_node = n; // index of intermediate nodes for actions\n\tlong sp_edges = 0; // pointer of dot edges\n\t//int queue[n]; // search queue\n\tint *queue;\n\tlong head = 0; // pointer to the head of the queue\n\tlong tail = 0; // pointer to the tail of the queue\n\t//int nodes[n]; // indicate whether the node has been visited\n\tint *nodes;\n\n\tFILE *f, *f1;\n\tint i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, count;\n\tdouble d1, d2, kb, kbt;\n\n\t// Extract required info from sparse matrix\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\n\tqueue = new int[n];\n\tnodes = new int[n];\n\tfor(i=0; i<n; i++)\n\t\tnodes[i] = 0;\n\t\n\tint (*dot_nodes)[2];\n\tint (*dot_edges)[2];\n\tint headnode_sp;\n\tint headnode_len;\n\tdouble *edge_probabilities;\n\tconst char**edge_labels;\n\tint *edge_weight;\n\tint *terminate_nodes;\n\t//printf(\"allocated memory for local variables:\\n\"); \n\t//printf(\"n=%1d, num_lp_vars=%1d, nnz=%1d\\n\", n, num_lp_vars, nnz);\n\t//fflush(stdout);\n\t\n\t//int dot_nodes[n+num_lp_vars][2]; // first entry: node number, second: shape \n\t//int dot_edges[nnz+num_lp_vars][2]; // first entry: source node, second: target\n\t//double edge_probabilities[nnz+num_lp_vars]; // edge's probability\n\t\n\tdot_nodes = new int[n+num_lp_vars][2];\n\tdot_edges = new int[nnz+num_lp_vars][2];\n\tedge_probabilities = new double[nnz+num_lp_vars];\n\tedge_labels = new const char*[nnz+num_lp_vars];\n\tedge_weight = new int[nnz+num_lp_vars];\n\tterminate_nodes = new int[n]; // the entry stores the node number for newly added terminate nodes\n\t\n\tfor(i=0; i<n; i++)\n\t\tterminate_nodes[i] = -1;\n\t\n\t// put the initial state in the queue and dot_nodes\n\tqueue[tail++] = start_index;\n\tdot_nodes[sp_nodes][0] = start_index;\n\tdot_nodes[sp_nodes++][1] = 0; // shape = 0: ellipse, 1: circle, 2: point, 3: doublecircle, 4: box\n\t\n\t// recursive procedure\n\tint head_node = -1;\n\twhile(head < tail) {\n\t\thead_node = queue[head++];\n\t\t\n\t\tif(nodes[head_node] == 1)\n\t\t\tcontinue;\n\t\tnodes[head_node] = 1;\n\t\t// If the head node is a target state, do nothing\n\t\tif(yes_vec[head_node]> 0 || maybe_vec[head_node]> 0) {\n\t\t\tif (!use_counts) {\n\t\t\t\theadnode_sp = row_starts[head_node];\n\t\t\t\theadnode_len = row_starts[head_node+1] - row_starts[head_node];\n\t\t\t} else {\n\t\t\t\theadnode_sp = 0;\n\t\t\t\tfor(j=0; j<head_node; j++)\n\t\t\t\t\theadnode_sp += row_counts[j];\n\t\t\t\theadnode_len = row_counts[head_node];\n\t\t\t}\n\t\t\t// the number of branches in the current state\n\t\t\th1 = map_var[head_node+1] - map_var[head_node];\n\t\t\t\n\t\t\tdouble sum = 0;\n\t\t\tfor(i=0; i<h1; i++)\n\t\t\t\tsum += lp_soln[map_var[head_node] + i];\n\t\t\t\n\t\t\tfor(i=0; i<h1; i++) {\n\t\t\t\t// test if the action has non-zero probability\n\t\t\t\tif(lp_soln[map_var[head_node] + i]> 0) {\n\t\t\t\t\tif(yes_vec[head_node]> 0 && i>=headnode_len) { // extra transition\n\t\t\t\t\t\t// add an intermediate node to dot_nodes\n\t\t\t\t\t\tif(terminate_nodes[head_node] < 0) {\n\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = extra_node;\n\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 4;\n\t\t\t\t\t\t\tdot_edges[sp_edges][1] = extra_node;\n\t\t\t\t\t\t\tterminate_nodes[head_node] = extra_node;\n\t\t\t\t\t\t} else\n\t\t\t\t\t\t\tdot_edges[sp_edges][1] = terminate_nodes[head_node];\n\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t//edge_probabilities[sp_edges++] = lp_soln[map_var[head_node] + i];\n\t\t\t\t\t\tedge_labels[sp_edges] = 0;\n\t\t\t\t\t\tedge_weight[sp_edges] = 0;\n\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? lp_soln[map_var[head_node] + i] :\n\t\t\t\t\t\t\tlp_soln[map_var[head_node] + i]/sum;\n\t\t\t\t\t\textra_node++;\n\t\t\t\t\t} else if(i<headnode_len) {\n\t\t\t\t\t\t// get all successor states of this action\n\t\t\t\t\t\t// First: locate the action\n\t\t\t\t\t\tl1 = headnode_sp + i;\n\t\t\t\t\t\t\n\t\t\t\t\t\t// Second: find all columns for this choice\n\t\t\t\t\t\tif (!use_counts) {\n\t\t\t\t\t\t\tl2 = choice_starts[l1];\n\t\t\t\t\t\t\th2 = choice_starts[l1+1];\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tl2 = 0;\n\t\t\t\t\t\t\tfor(j=0; j<l1; j++)\n\t\t\t\t\t\t\t\tl2 += choice_counts[j];\n\t\t\t\t\t\t\th2 = l2 + choice_counts[j];\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif(h2-l2>1) {\n\t\t\t\t\t\t\t// add an intermediate node to dot_nodes\n\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = extra_node;\n\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 2;\n\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\tdot_edges[sp_edges][1] = extra_node;\n\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t//edge_probabilities[sp_edges++] = lp_soln[map_var[head_node] + i];\n\t\t\t\t\t\t\t//printf(\"headnode = %d, l1 = %d\\n\", head_node, l1);\n\t\t\t\t\t\t\tedge_labels[sp_edges] = (actions != NULL && actions[l1]>0) ? action_names[actions[l1]-1] : 0;\n\t\t\t\t\t\t\tedge_weight[sp_edges] = back_arr_reals[map_var[head_node] + i] > 0.0 ? 1 : 0;\n\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? lp_soln[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\tlp_soln[map_var[head_node] + i]/sum;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tfor(j=l2; j<h2; j++) {\n\t\t\t\t\t\t\t\t// add the successor state to dot_nodes\n\t\t\t\t\t\t\t\tk=1;\n\t\t\t\t\t\t\t\tfor(k_r=0; k_r<sp_nodes; k_r++) \n\t\t\t\t\t\t\t\t\tif(dot_nodes[k_r][0] == cols[j]) {\n\t\t\t\t\t\t\t\t\t\tk=0; \n\t\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\tif(k) {\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = cols[j];\n\t\t\t\t\t\t\t\t\tif(yes_vec[cols[j]]> 0)\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 3;\n\t\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 1;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\t\tdot_edges[sp_edges][0] = extra_node;\n\t\t\t\t\t\t\t\tdot_edges[sp_edges][1] = cols[j];\n\t\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t\tedge_labels[sp_edges] = 0;\n\t\t\t\t\t\t\t\tedge_weight[sp_edges] = 0;\n\t\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = non_zeros[j];\n\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\tif((maybe_vec[cols[j]]> 0 || yes_vec[cols[j]]> 0) &&\n\t\t\t\t\t\t\t\t\t nodes[cols[j]] == 0)\n\t\t\t\t\t\t\t\t\tqueue[tail++] = cols[j];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\textra_node++;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t// add the successor state to dot_nodes\n\t\t\t\t\t\t\tk=1;\n\t\t\t\t\t\t\tfor(j=0; j<sp_nodes; j++) \n\t\t\t\t\t\t\t\tif(dot_nodes[j][0] == cols[l2]) {\n\t\t\t\t\t\t\t\t\tk=0; \n\t\t\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tif(k) {\n\t\t\t\t\t\t\t\tdot_nodes[sp_nodes][0] = cols[l2];\n\t\t\t\t\t\t\t\tif(yes_vec[cols[l2]]> 0)\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 3;\n\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\tdot_nodes[sp_nodes++][1] = 1;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// add an edge to dot_edges\n\t\t\t\t\t\t\tdot_edges[sp_edges][0] = head_node;\n\t\t\t\t\t\t\tdot_edges[sp_edges][1] = cols[l2];\n\t\t\t\t\t\t\t// add the probability to the edge\n\t\t\t\t\t\t\t//edge_probabilities[sp_edges++] = lp_soln[map_var[head_node] + i];\n\t\t\t\t\t\t\t//printf(\"headnode = %d, len = %d, l1 = %d\\n\", head_node, headnode_len, l1);\n\t\t\t\t\t\t\tedge_labels[sp_edges] = (actions != NULL && actions[l1]>0) ? action_names[actions[l1]-1] : 0;\n\t\t\t\t\t\t\tedge_weight[sp_edges] = back_arr_reals[map_var[head_node] + i] > 0.0 ? 1 : 0;\n\t\t\t\t\t\t\tedge_probabilities[sp_edges++] = sum == 1 ? lp_soln[map_var[head_node] + i] :\n\t\t\t\t\t\t\t\tlp_soln[map_var[head_node] + i]/sum;\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tif((maybe_vec[cols[l2]]> 0 || yes_vec[cols[l2]]> 0) &&\n\t\t\t\t\t\t\t\t nodes[cols[l2]] == 0) {\n\t\t\t\t\t\t\t\tqueue[tail++] = cols[l2];\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\t\n\t\n\tprintf(\"generating adversary file\\n\"); fflush(stdout);\n\t\n\t// write to file\n\tint len = strlen(export_adv_filename);\n\tchar style[] = \", style=bold\";\n\tchar *fname = new char[len+5];\n\tmemcpy (fname, export_adv_filename, len+1);\n\tfname[len] = '.';\n\tfname[len+1] = 'd';\n\tfname[len+2] = 'o';\n\tfname[len+3] = 't';\n\tfname[len+4] = '\\0';\n\tf = fopen(fname, \"w\"); /* create a file for writing */\n\n\tif(f==NULL) {\n\t\tprintf(\"\\nWarning: Output of adversary cancelled (could not open file \\\"%s\\\").\\n\", fname);\n\t} else {\n\t\tf1 = fopen(\"product-multi.dot\", \"r\");\n\t\tchar states[n][200];\n\t\tint state_sp = 0;\n\t\tchar *lb, *rb;\n\t\tif(f1 != NULL) {\n\t\t\tprintf(\"\\nUsing product-multi.dot to extract state information\\n\");\n\t\t\tchar line[200];\n\t\t\twhile (fgets(line, sizeof(line), f1) != NULL ) {\n\t\t\t\tlb = strchr(line, '(');\n\t\t\t\trb = strchr(line, ')');\n\t\t\t\tif(lb != NULL && rb != NULL && rb > lb) {\n\t\t\t\t\t*(rb+1) = '\\0';\n\t\t\t\t\tstrcpy(states[state_sp++], lb); \n\t\t\t\t}\n\t\t\t}\n\t\t\tfclose (f1);\n\t\t}\n\t\tfprintf(f, \"digraph adversary {\\n\");\n\t\tfor(i=0; i<sp_nodes; i++) {\n\t\t\tif(dot_nodes[i][0] >= n) {\n\t\t\t\tif(dot_nodes[i][1] == 2)\n\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=point]\\n\", dot_nodes[i][0]);\n\t\t\t\telse\n\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"\\\", shape=box, fillcolor=black]\\n\", dot_nodes[i][0]);\n\t\t\t} else {\n\t\t\t\tif(dot_nodes[i][0]<state_sp)\n\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\\n%s\\\", shape=%s]\\n\", dot_nodes[i][0], \n\t\t\t\t\t\t\t\t\tdot_nodes[i][0], states[dot_nodes[i][0]],\n\t\t\t\t\t\t\t\t\t((dot_nodes[i][1]==0)? \"ellipse\" :\n\t\t\t\t\t\t\t\t\t ((dot_nodes[i][1]==1)? \"octagon\" : \"doubleoctagon\")));\n\t\t\t\telse\n\t\t\t\t\tfprintf(f, \"\t%1d [label=\\\"%1d\\\", shape=%s]\\n\", dot_nodes[i][0],\n\t\t\t\t\t\t\t\t\tdot_nodes[i][0],\n\t\t\t\t\t\t\t\t\t((dot_nodes[i][1]==0)? \"ellipse\" :\n\t\t\t\t\t\t\t\t\t ((dot_nodes[i][1]==1)? \"octagon\" : \"doubleoctagon\")));\n\t\t\t}\n\t\t}\n\t\tfor(i=0; i<sp_edges; i++) {\n\t\t\t//printf(\"printing edges %d\\n\", i); fflush(stdout);\n\t\t\tif(edge_labels[i])\n\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%g, %s\\\"%s]\\n\", dot_edges[i][0],\n\t\t\t\t\t\t\t\tdot_edges[i][1], edge_probabilities[i], edge_labels[i], edge_weight[i] ? style : \"\");\n\t\t\telse\n\t\t\t\tfprintf(f, \"\t\t%1d -> %1d [label=\\\"%g\\\"%s]\\n\", dot_edges[i][0],\n\t\t\t\t\t\t\t\tdot_edges[i][1], edge_probabilities[i], edge_weight[i] ? style : \"\");\n\t\t}\n\t\tfprintf(f, \"}\\n\");\n\t\tfclose(f);\n\t}\n\t\n\tdelete[] dot_nodes;\n\tdelete[] dot_edges;\n\tdelete[] edge_probabilities;\n\tdelete[] edge_labels;\n\tdelete[] edge_weight;\n\tdelete[] terminate_nodes;\n\t\n\tdelete[] queue;\n\tdelete[] nodes;\n}\n//------------------------------------------------------------------------------\n\n// Export the adversary (as a tra file)\n\nvoid export_adversary_ltl_tra(const char *export_adv_filename, NDSparseMatrix *ndsm, int *actions, const char** action_names, int *yes_vec, double *maybe_vec, int num_lp_vars, int *map_var, double *lp_soln, int start_index)\n{\n\tFILE *f;\n\tint i, j, k, k_r, l1, h1, l2, h2, l2_r, h2_r, count;\n\tdouble d1, d2, kb, kbt;\n\n\tFILE *fp_adv;\n\tdouble sum, d;\n\t\n\t// Extract required info from sparse matrix\n\tint n = ndsm->n;\n\tint nnz = ndsm->nnz;\n\tdouble *non_zeros = ndsm->non_zeros;\n\tunsigned char *row_counts = ndsm->row_counts;\n\tint *row_starts = (int *)ndsm->row_counts;\n\tunsigned char *choice_counts = ndsm->choice_counts;\n\tint *choice_starts = (int *)ndsm->choice_counts;\n\tbool use_counts = ndsm->use_counts;\n\tunsigned int *cols = ndsm->cols;\n\n\t// Open file to store adversary\n\tfp_adv = fopen(export_adv_filename, \"w\");\n\tif (fp_adv) {\n\t\tfprintf(fp_adv, \"%d ?\\n\", n);\n\t} else {\n\t\tprintf(\"\\nWarning: Adversary generation cancelled (could not open file \\\"%s\\\").\\n\", export_adv_filename);\n\t\treturn;\n\t}\n\t\n\t// Traverse sparse matrix to get adversary\n\th1 = h2 = 0;\n\tfor (i = 0; i < n; i++) {\n\t\t// Compute sum of adversary choice weights for this state\n\t\tsum = 0.0;\n\t\tfor (j = 0; j < (map_var[i+1] - map_var[i]); j++)\n\t\t\tsum += lp_soln[map_var[i] + j];\n\t\t// Go through choices\n\t\tif (!use_counts) { l1 = row_starts[i]; h1 = row_starts[i+1]; }\n\t\telse { l1 = h1; h1 += row_counts[i]; }\n\t\tfor (j = l1; j < h1; j++) {\n\t\t\tif (!use_counts) { l2 = choice_starts[j]; h2 = choice_starts[j+1]; }\n\t\t\telse { l2 = h2; h2 += choice_counts[j]; }\n\t\t\t// Get weight for this choice\n\t\t\td = lp_soln[map_var[i] + j - l1];\n\t\t\tif (d > 0) {\n\t\t\t\t// Normalise weight to get prob\n\t\t\t\td /= sum;\n\t\t\t\tfor (k = l2; k < h2; k++) {\n\t\t\t\t\tfprintf(fp_adv, \"%d %d %g\", i, cols[k], d * non_zeros[k]);\n\t\t\t\t\tif (actions != NULL) fprintf(fp_adv, \" %s\", actions[j]>0?action_names[actions[j]-1]:\"-\");\n\t\t\t\t\tfprintf(fp_adv, \"\\n\");\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Add action to loop in this EC, if required\n\t\tif (yes_vec[i] && lp_soln[map_var[i + 1] - 1] > 0) {\n\t\t\tfprintf(fp_adv, \"%d %d %g _ec\\n\", i, i, lp_soln[map_var[i + 1] - 1] / sum);\n\t\t}\n\t}\n\t\n\t// Close file\n\tfclose(fp_adv);\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/strat/FMDObsStrategyBeliefs.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport explicit.*;\nimport explicit.graphviz.Decoration;\nimport explicit.graphviz.Decorator;\nimport parser.State;\nimport prism.PrismException;\nimport prism.PrismLog;\n\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.List;\nimport java.util.stream.Collectors;\nimport java.util.stream.IntStream;\n\n/**\n * Class to store finite-memory deterministic (FMD) observation-based strategies\n * using a belief MDP fragment for a POMDP.\n */\npublic class FMDObsStrategyBeliefs<Value> extends StrategyExplicit<Value>\n{\n\t/** Another copy of the model (to minimise casting) */\n\tprotected POMDP<Value> pomdp;\n\t\n\t/** Finite-memory strategy represented as an MDP with 1 choice per state */\n\tprotected MDP<Value> mdpStrat;\n\n\t/** States of the MDP: pairs of indices of POMDP observables and unobservable beliefs */\n\tprotected List<int[]> mdpStates;\n\n\t/** List of beliefs over unobservables, as stored in MDP states */\n\tprotected List<double[]> unobsBeliefs;\n\n\t/**\n\t * Creates an FMDObsStrategyBeliefs.\n\t */\n\tpublic FMDObsStrategyBeliefs(POMDP<Value> pomdp, MDP<Value> mdpStrat, List<int[]> mdpStates, List<double[]> unobsBeliefs)\n\t{\n\t\tsuper(pomdp);\n\t\tthis.pomdp = pomdp;\n\t\tthis.mdpStrat = mdpStrat;\n\t\tthis.mdpStates = mdpStates;\n\t\tthis.unobsBeliefs = unobsBeliefs;\n\t}\n\n\t@Override\n\tpublic Memory memory()\n\t{\n\t\treturn Memory.FINITE;\n\t}\n\t\n\t@Override\n\tpublic Object getChoiceAction(int s, int m)\n\t{\n\t\t// Find a matching state in the MDP and look up the action for it\n\t\tint o = pomdp.getObservation(s);\n\t\tint i = findMatchingMDPState(o, m);\n\t\treturn i == -1 ? Strategy.UNDEFINED : getActionPickedByMDP(i);\n\t}\n\n\t@Override\n\tpublic int getChoiceIndex(int s, int m)\n\t{\n\t\t// Find a matching state in the MDP and look up the action for it\n\t\tint o = pomdp.getObservation(s);\n\t\tint i = findMatchingMDPState(o, m);\n\t\tif (i == -1) {\n\t\t\treturn -1;\n\t\t}\n\t\tObject act = getActionPickedByMDP(i);\n\t\tint actIndex = -1;\n\t\tif (act != UNDEFINED) {\n\t\t\tint[] mdpState = mdpStates.get(i);\n\t\t\tactIndex = pomdp.getChoiceByActionForObservation(mdpState[0], act);\n\t\t}\n\t\treturn actIndex;\n\t}\n\t\n\t@Override\n\tpublic int getMemorySize()\n\t{\n\t\treturn unobsBeliefs.size();\n\t}\n\t\n\t@Override\n\tpublic int getInitialMemory(int sInit)\n\t{\n\t\tint oInit = pomdp.getObservation(sInit);\n\t\tint i = mdpStrat.getFirstInitialState();\n\t\tif (mdpStates.get(i)[0] != oInit) {\n\t\t\treturn -1;\n\t\t} else {\n\t\t\treturn mdpStates.get(i)[1];\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic int getUpdatedMemory(int m, Object action, int sNext)\n\t{\n\t\t// If the current memory is unknown, we don't know how to update it\n\t\tif (m == -1) {\n\t\t\treturn -1;\n\t\t}\n\t\t// Look for a matching transition in the MDP and find the memory update\n\t\t// (inefficiently, since they are not sorted)\n\t\tint oNext = pomdp.getObservation(sNext);\n\t\tint n = mdpStates.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (mdpStates.get(i)[1] == m) {\n\t\t\t\tint j = findMatchingMemoryUpdate(i, oNext);\n\t\t\t\tif (j != -1) {\n\t\t\t\t\treturn j;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\t\n\t@Override\n    public String getMemoryString(int m)\n    {\n\t\treturn m == -1 ? \"?\" : Belief.toStringUnobs(unobsBeliefs.get(m), pomdp);\n    }\n\n\t@Override\n\tpublic explicit.Model<Value> constructInducedModel(StrategyExportOptions options) throws PrismException\n\t{\n\t\tConstructStrategyProduct csp = new ConstructStrategyProduct();\n\t\tcsp.setMode(options.getMode());\n\t\tModel<Value> prodModel = csp.constructProductModel(model, this);\n\t\treturn prodModel;\n\t}\n\n\t@Override\n\tpublic void exportActions(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tint n = mdpStrat.getNumStates();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tObject act = getActionPickedByMDP(i);\n\t\t\tif (act != UNDEFINED) {\n\t\t\t\tint[] mdpState = mdpStates.get(i);\n\t\t\t\tif (options.getShowStates()) {\n\t\t\t\t\tout.print(Belief.toString(mdpState[0], unobsBeliefs.get(mdpState[1]), pomdp));\n\t\t\t\t} else {\n\t\t\t\t\tout.print(mdpState[0] + \",\" + mdpState[1]);\n\t\t\t\t}\n\t\t\t\tout.println(\"=\" + (act == null ? \"\" : act));\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportIndices(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tint n = mdpStrat.getNumStates();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tObject act = getActionPickedByMDP(i);\n\t\t\tif (act != UNDEFINED) {\n\t\t\t\tint[] mdpState = mdpStates.get(i);\n\t\t\t\tint actIndex = pomdp.getChoiceByActionForObservation(mdpState[0], act);\n\t\t\t\tout.println(mdpState[0] + \",\" + mdpState[1] + \"=\" + actIndex);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportInducedModel(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tif (options.getMergeObservations()) {\n\t\t\texportInducedModelObs(out, options);\n\t\t} else {\n\t\t\texportInducedModelNonObs(out, options);\n\t\t}\n\t}\n\n\tpublic void exportInducedModelObs(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tmdpStrat.exportToPrismExplicitTra(out, options.getModelPrecision());\n\t}\n\n\tpublic void exportInducedModelNonObs(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tModel<Value> prodModel = constructInducedModel(options);\n\t\tprodModel.exportToPrismExplicitTra(out, options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void exportDotFile(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tif (options.getMergeObservations()) {\n\t\t\texportDotFileObs(out, options);\n\t\t} else {\n\t\t\texportDotFileNonObs(out, options);\n\t\t}\n\t}\n\n\tpublic void exportDotFileObs(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\t// Use the already constructed strategy model for export\n\t\tList<Decorator> decorators = new ArrayList<>();\n\t\tif (options.getShowStates()) {\n\t\t\tdecorators.add(new Decorator()\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic Decoration decorateState(int state, Decoration d)\n\t\t\t\t{\n\t\t\t\t\td.labelAddBelow(Belief.toString(mdpStates.get(state)[0], unobsBeliefs.get(mdpStates.get(state)[1]), pomdp));\n\t\t\t\t\treturn d;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\tmdpStrat.exportToDotFile(out, decorators, options.getModelPrecision());\n\t}\n\n\tpublic void exportDotFileNonObs(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\t// Construct the strategy-induced product model\n\t\tModel<Value> prodModel = constructInducedModel(options);\n\t\tList<State> stateList = prodModel.getStatesList();\n\t\t// Export product model to dot file, with (if needed) a custom decorator\n\t\t// to extract the final value of each state and convert to a belief\n\t\tList<Decorator> decorators = new ArrayList<>();\n\t\tif (options.getShowStates()) {\n\t\t\tdecorators.add(new Decorator()\n\t\t\t{\n\t\t\t\t@Override\n\t\t\t\tpublic Decoration decorateState(int state, Decoration d)\n\t\t\t\t{\n\t\t\t\t\tObject[] varValues = stateList.get(state).varValues;\n\t\t\t\t\tint numVars = varValues.length;\n\t\t\t\t\tString s = \"(\";\n\t\t\t\t\tfor (int i = 0; i < numVars - 1; i++) {\n\t\t\t\t\t\tif (i > 0)\n\t\t\t\t\t\t\ts += \",\";\n\t\t\t\t\t\ts += State.valueToString(varValues[i]);\n\t\t\t\t\t}\n\t\t\t\t\ts += \"),\";\n\t\t\t\t\tint m = (int) varValues[numVars - 1];\n\t\t\t\t\ts += getMemoryString(m);\n\t\t\t\t\td.labelAddBelow(s);\n\t\t\t\t\treturn d;\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\tprodModel.exportToDotFile(out, decorators, options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tmdpStrat = null;\n\t\tmdpStates = null;\n\t\tunobsBeliefs = null;\n\t}\n\n\t// Utility methods\n\n\t/**\n\t * Find the index of a state (o,m) in the MDP, if there is one\n\t */\n\tprivate int findMatchingMDPState(int o, int m)\n\t{\n\t\t// If memory value is unknown, there are no matching states\n\t\tif (m == -1) {\n\t\t\treturn -1;\n\t\t}\n\t\t// Look for a matching state in the MDP\n\t\t// (inefficiently, since they are not sorted)\n\t\tint n = mdpStates.size();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (mdpStates.get(i)[0] == o && mdpStates.get(i)[1] == m) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\t// No match\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Find a transition in the i-th state of the MDP whose destination state\n\t * has observable oNext, if there is one, and return the automaton state\n\t */\n\tprivate int findMatchingMemoryUpdate(int i, int oNext)\n\t{\n\t\tfor (SuccessorsIterator succ = mdpStrat.getSuccessors(i); succ.hasNext();) {\n\t\t\tint j = succ.nextInt();\n\t\t\tif (mdpStates.get(j)[0] == oNext) {\n\t\t\t\treturn mdpStates.get(j)[1];\n\t\t\t}\n\t\t}\n\t\t// No match\n\t\treturn -1;\n\t}\n\n\t/**\n\t * Get the action picked by a state of the MDP. Returns {@link StrategyInfo#UNDEFINED} if undefined.\n\t * @param i MDP state index\n \t */\n\tprivate Object getActionPickedByMDP(int i)\n\t{\n\t\tif (i < 0 || i >= mdpStrat.getNumStates() || mdpStrat.isDeadlockState(i)) {\n\t\t\treturn UNDEFINED;\n\t\t}\n\t\treturn mdpStrat.getAction(i, 0);\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + IntStream.range(0, mdpStrat.getNumStates())\n\t\t\t\t.mapToObj(s -> mdpStates.get(s)[0] + \",\" + mdpStates.get(s)[1]\n\t\t\t\t\t+ \"=\" + getActionPickedByMDP(s))\n\t\t\t\t.collect(Collectors.joining(\",\")) + \"]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/FMDStrategyProduct.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport explicit.ConstructInducedModel;\nimport explicit.ConstructStrategyProduct;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport explicit.Product;\nimport explicit.SuccessorsIterator;\nimport parser.State;\nimport prism.PrismException;\nimport prism.PrismLog;\n\nimport java.util.List;\nimport java.util.stream.Collectors;\nimport java.util.stream.IntStream;\n\n/**\n * Class to store finite-memory deterministic (FMD) strategies\n * using a memoryless Strategy and an explicit engine product model.\n */\npublic class FMDStrategyProduct<Value> extends StrategyExplicit<Value>\n{\n\t// Product model associated with the strategy\n\tprivate Product<?> product;\n\t// Memoryless strategy over product model\n\tprivate MDStrategy<Value> strat;\n\t\n\t/**\n\t * Creates an FMDStrategyProduct from a memoryless Strategy and an explicit engine product model.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic FMDStrategyProduct(Product<?> product, MDStrategy<Value> strat)\n\t{\n\t\tsuper((NondetModel<Value>) product.getOriginalModel());\n\t\tthis.product = product;\n\t\tthis.strat = strat;\n\t}\n\n\t@Override\n\tpublic Memory memory()\n\t{\n\t\treturn Memory.FINITE;\n\t}\n\t\n\t@Override\n\tpublic Object getChoiceAction(int s, int m)\n\t{\n\t\t// Find a matching state in the product and look up the strategy for it\n\t\tint i = findMatchingProductState(s, m);\n\t\treturn i == -1 ? Strategy.UNDEFINED : strat.getChoiceAction(i);\n\t}\n\t\n\t@Override\n\tpublic int getChoiceIndex(int s, int m)\n\t{\n\t\t// Find a matching state in the product and look up strategy for it\n\t\tint i = findMatchingProductState(s, m);\n\t\treturn i == -1 ? -1 : strat.getChoiceIndex(i);\n\t}\n\t\n\t/**\n\t * Find the index of a state (s,m) in the product, if there is one\n\t */\n\tprivate int findMatchingProductState(int s, int m)\n\t{\n\t\t// If memory value is unknown, there are no matching states\n\t\tif (m == -1) {\n\t\t\treturn -1;\n\t\t}\n\t\t// Look for a matching state in the product\n\t\t// (inefficiently, since they are not sorted)\n\t\tint n = product.getProductModel().getNumStates();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (product.getModelState(i) == s && product.getAutomatonState(i) == m) {\n\t\t\t\treturn i;\n\t\t\t}\n\t\t}\n\t\t// No match\n\t\treturn -1;\n\t}\n\t\n\t@Override\n\tpublic int getMemorySize()\n\t{\n\t\treturn product.getAutomatonSize();\n\t}\n\t\n\t@Override\n\tpublic int getInitialMemory(int sInit)\n\t{\n\t\t// We don't have access to the original automaton, so we\n\t\t// look for an initial state in the product with this model state\n\t\t// (inefficiently, since they are not sorted)\n\t\tfor (int i : product.getProductModel().getInitialStates()) {\n\t\t\tif (product.getModelState(i) == sInit) {\n\t\t\t\treturn product.getAutomatonState(i);\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\t\n\t@Override\n\tpublic int getUpdatedMemory(int m, Object action, int sNext)\n\t{\n\t\t// If the current memory is unknown, we don't know how to update it\n\t\tif (m == -1) {\n\t\t\treturn -1;\n\t\t}\n\t\t// We don't have access to the original automaton, so we\n\t\t// look for a matching transition in the product and find the memory update\n\t\t// (inefficiently, since they are not sorted)\n\t\tint n = product.getProductModel().getNumStates();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (product.getAutomatonState(i) == m) {\n\t\t\t\tint j = findMatchingMemoryUpdate(i, sNext);\n\t\t\t\tif (j != -1) {\n\t\t\t\t\treturn j;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn -1;\n\t}\n\t\n\t/**\n\t * Find a transition in the i-th state of the product whose destination\n\t * has model state sNext, if there is one, and return the automaton state\n\t */\n\tprivate int findMatchingMemoryUpdate(int i, int sNext)\n\t{\n\t\tfor (SuccessorsIterator succ = product.getProductModel().getSuccessors(i); succ.hasNext(); ) {\n\t\t\tint j = succ.nextInt();\n\t\t\tif (product.getModelState(j) == sNext) {\n\t\t\t\treturn product.getAutomatonState(j);\n\t\t\t}\n\t\t}\n\t\t// No match\n\t\treturn -1;\n\t}\n\n\t@Override\n\tpublic explicit.Model<Value> constructInducedModel(StrategyExportOptions options) throws PrismException\n\t{\n\t\tConstructStrategyProduct csp = new ConstructStrategyProduct();\n\t\tcsp.setMode(options.getMode());\n\t\tModel<Value> prodModel = csp.constructProductModel(model, this);\n\t\treturn prodModel;\n\t}\n\n\t@Override\n\tpublic void exportActions(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tList<State> states = model.getStatesList();\n\t\tboolean showStates = options.getShowStates() && states != null;\n\t\tint n = product.getProductModel().getNumStates();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tint s = product.getModelState(i);\n\t\t\tint m = product.getAutomatonState(i);\n\t\t\tObject act = strat.getChoiceAction(i);\n\t\t\tif (act != UNDEFINED) {\n\t\t\t\tout.println((showStates ? states.get(s) : s) + \",\" + m + \"=\" + (act == null ? \"\" : act.toString()));\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportIndices(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tint n = product.getProductModel().getNumStates();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tint s = product.getModelState(i);\n\t\t\tint m = product.getAutomatonState(i);\n\t\t\tout.println(s + \",\" + m + \"=\" + strat.getChoiceIndex(i));\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportInducedModel(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\t// If restricting to reachable states, construct product afresh\n\t\tif (options.getReachOnly()) {\n\t\t\tModel<Value> prodModel = constructInducedModel(options);\n\t\t\tprodModel.exportToPrismExplicitTra(out, options.getModelPrecision());\n\t\t}\n\t\t// Otherwise, just export MD strategy, unmodified\n\t\telse {\n\t\t\tstrat.exportInducedModel(out, options);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportDotFile(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tConstructStrategyProduct csp = new ConstructStrategyProduct();\n\t\tcsp.setMode(options.getMode());\n\t\tModel<Value> prodModel = csp.constructProductModel(model, this);\n\t\tprodModel.exportToDotFile(out, null, options.getShowStates(), options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tstrat.clear();\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + IntStream.range(0, getNumStates())\n\t\t\t\t.mapToObj(s -> IntStream.range(0, getMemorySize())\n\t\t\t\t.mapToObj(m -> s + \",\" + m + \"=\" + getChoiceActionString(s, m))\n\t\t\t\t.collect(Collectors.joining(\",\")))\n\t\t\t\t.collect(Collectors.joining(\",\")) + \"]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/FMDStrategyStep.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.stream.Collectors;\nimport java.util.stream.IntStream;\n\nimport explicit.ConstructInducedModel;\nimport explicit.ConstructStrategyProduct;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport parser.State;\nimport prism.PrismException;\nimport prism.PrismLog;\n\n/**\n * Class to store finite-memory deterministic (FMD) strategies\n * giving a different choice for each state across k steps of execution.\n * So the memory is simply the number of elapsed steps.\n */\npublic class FMDStrategyStep<Value> extends StrategyExplicit<Value>\n{\n\t// Model size\n\tprivate int numStates;\n\t// Max number of steps considered\n\tprivate int k;\n\t// Memoryless strategy over product model\n\tprivate ArrayList<StepChoices> choices;\n\t\n\t/**\n\t * Create a blank FMDStrategyStep for a specified model and maximum step count.\n\t */\n\tpublic FMDStrategyStep(NondetModel<Value> model, int k)\n\t{\n\t\tsuper(model);\n\t\tnumStates = model.getNumStates();\n\t\tthis.k = k;\n\t\tchoices = new ArrayList<>(numStates);\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tchoices.add(new StepChoicesArray(k));\n\t\t}\n\t}\n\n\t/**\n\t * Set the choice to be taken in state s at step i,\n\t * specified by the index of the choice in the corresponding model.\n\t */\n\tpublic void setStepChoice(int s, int i, int ch)\n\t{\n\t\tchoices.get(s).setChoiceForStep(i, ch);\n\t}\n\t\n\t/**\n\t * Set the choices to be taken in all states at step i,\n\t * specified by the indices of the choices in the corresponding model.\n\t */\n\tpublic void setStepChoices(int i, int ch[])\n\t{\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tchoices.get(s).setChoiceForStep(i, ch[s]);\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic Memory memory()\n\t{\n\t\treturn Memory.FINITE;\n\t}\n\t\n\t@Override\n\tpublic Object getChoiceAction(int s, int m)\n\t{\n\t\tint c = getChoiceIndex(s, m);\n\t\treturn c >= 0 ? model.getAction(s, c) : Strategy.UNDEFINED;\n\t}\n\t\n\t@Override\n\tpublic int getChoiceIndex(int s, int m)\n\t{\n\t\t// Only defined for 0...k-1\n\t\treturn m < k ? choices.get(s).getChoiceForStep(m) : -1;\n\t}\n\t\n\t@Override\n\tpublic int getMemorySize()\n\t{\n\t\treturn k + 1;\n\t}\n\t\n\t@Override\n\tpublic int getInitialMemory(int sInit)\n\t{\n\t\t// Step count initially zero\n\t\treturn 0;\n\t}\n\t\n\t@Override\n\tpublic int getUpdatedMemory(int m, Object action, int sNext)\n\t{\n\t\t// Step count increases by 1 each time (up to k)\n\t\treturn m >= k ? k : m + 1;\n\t}\n\n\t@Override\n\tpublic explicit.Model<Value> constructInducedModel(StrategyExportOptions options) throws PrismException\n\t{\n\t\tConstructStrategyProduct csp = new ConstructStrategyProduct();\n\t\tcsp.setMode(options.getMode());\n\t\tModel<Value> prodModel = csp.constructProductModel(model, this);\n\t\treturn prodModel;\n\t}\n\n\t@Override\n\tpublic void exportActions(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tList<State> states = model.getStatesList();\n\t\tboolean showStates = options.getShowStates() && states != null;\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tfor (int m = 0; m < k; m++) {\n\t\t\t\tif (isChoiceDefined(s, m)) {\n\t\t\t\t\tout.println((showStates ? states.get(s) : s) + \",\" + m + \"=\" + getChoiceActionString(s, m));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportIndices(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tfor (int m = 0; m < k; m++) {\n\t\t\t\tif (isChoiceDefined(s, m)) {\n\t\t\t\t\tout.println(s + \",\" + m + \"=\" + getChoiceIndex(s, m));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportInducedModel(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tModel<Value> prodModel = constructInducedModel(options);\n\t\tprodModel.exportToPrismExplicitTra(out, options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void exportDotFile(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tModel<Value> prodModel = constructInducedModel(options);\n\t\tprodModel.exportToDotFile(out, null, options.getShowStates(), options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tchoices = null;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + IntStream.range(0, getNumStates())\n\t\t\t\t.mapToObj(s -> IntStream.range(0, k)\n\t\t\t\t.mapToObj(m -> s + \",\" + m + \"=\" + getChoiceActionString(s, m))\n\t\t\t\t.collect(Collectors.joining(\",\")))\n\t\t\t\t.collect(Collectors.joining(\",\")) + \"]\";\n\t}\n\n\t// Classes to store the choice for each step (0...k-1) in one state\n\t\n\t/**\n\t * Abstract class to store the choice for each step (0...k-1) in one state\n\t */\n\tabstract class StepChoices\n\t{\n\t\t/**\n\t\t * Set the choice for a given step\n\t\t */\n\t\tabstract void setChoiceForStep(int step, int ch);\n\t\t\n\t\t/**\n\t\t * Get the choice for a given step\n\t\t */\n\t\tabstract int getChoiceForStep(int step);\n\t}\n\t\n\t/**\n\t * Simple implementation of {@link StepChoices},\n\t * just storing choice indices in an array of size k\n\t */\n\tclass StepChoicesArray extends StepChoices\n\t{\n\t\tint stepChoices[];\n\t\t\n\t\tStepChoicesArray(int stepBound)\n\t\t{\n\t\t\tstepChoices = new int[stepBound];\n\t\t\t// All unknown (-1) initially\n\t\t\tfor (int i = 0; i < stepBound; i++) {\n\t\t\t\tstepChoices[i] = -1;\n\t\t\t}\n\t\t}\n\t\t\n\t\t@Override\n\t\tvoid setChoiceForStep(int step, int ch)\n\t\t{\n\t\t\tstepChoices[step] = ch;\n\t\t}\n\t\t\n\t\t@Override\n\t\tint getChoiceForStep(int step)\n\t\t{\n\t\t\treturn stepChoices[step];\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/MDStrategy.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Aistis Simaitis <aistis.aimaitis@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport prism.PrismLog;\n\n/**\n * Interface for classes to store memoryless deterministic (MD) strategies.\n */\npublic interface MDStrategy<Value> extends Strategy<Value>\n{\n\t// Additional queries for memoryless strategies (just ignore memory)\n\t\n\t/**\n\t * Get the action chosen by the strategy in the state index s\n\t * Returns {@link StrategyInfo#UNDEFINED} if undefined.\n\t */\n\tpublic default Object getChoiceAction(int s)\n\t{\n\t\treturn getChoiceAction(s, -1);\n\t}\n\t\n\t/**\n\t * Get the index of the choice picked by the strategy in the state index s.\n\t * The index is defined with respect to a particular model, stored locally.\n\t * Returns a negative value (not necessarily -1) if undefined.\n\t */\n\tpublic default int getChoiceIndex(int s)\n\t{\n\t\treturn getChoiceIndex(s, -1);\n\t}\n\n\t/**\n\t * Is a choice defined by the strategy in the state index s.\n\t */\n\tpublic default boolean isChoiceDefined(int s)\n\t{\n\t\treturn isChoiceDefined(s, -1);\n\t}\n\n\t/**\n\t * Get a string representing the choice made by the strategy in the state index s.\n\t * For unlabelled choices, this should return \"\", not null.\n\t * This may also indicate the reason why it is undefined, if it is.\n\t */\n\tpublic default String getChoiceActionString(int s)\n\t{\n\t\treturn getChoiceActionString(s, -1);\n\t}\n\n\t// Methods for Strategy\n\t\n\t@Override\n\tpublic default void exportActions(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tint n = getNumStates();\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tif (isChoiceDefined(s))\n\t\t\t\tout.println(s + \"=\" + getChoiceActionString(s));\n\t\t}\n\t}\n\n\t@Override\n\tpublic default void exportIndices(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tint n = getNumStates();\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tif (isChoiceDefined(s))\n\t\t\t\tout.println(s + \"=\" + getChoiceIndex(s));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/MDStrategyArray.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport explicit.ConstructInducedModel;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport parser.State;\nimport prism.PrismException;\nimport prism.PrismLog;\n\nimport java.util.List;\nimport java.util.stream.Collectors;\nimport java.util.stream.IntStream;\n\n/**\n * Class to store a memoryless deterministic (MD) strategy\n * as a (Java) array of choice indices associated with an explicit engine model.\n */\npublic class MDStrategyArray<Value> extends StrategyExplicit<Value> implements MDStrategy<Value>\n{\n\t// Index of choice taken in each state (wrt model above)\n\t// Other possible values: -1 (unknown), -2 (arbitrary), -3 (unreachable)\n\tprivate int choices[];\n\n\t/**\n\t * Creates an MDStrategyArray from an integer array of choices.\n\t * The array may later be modified/delete - take a copy if you want to keep it.\n\t */\n\tpublic MDStrategyArray(NondetModel<Value> model, int choices[])\n\t{\n\t\tsuper(model);\n\t\tthis.choices = choices;\n\t}\n\n\t@Override\n\tpublic Object getChoiceAction(int s, int m)\n\t{\n\t\tint c = choices[s];\n\t\treturn c >= 0 ? model.getAction(s, c) : Strategy.UNDEFINED;\n\t}\n\n\t@Override\n\tpublic int getChoiceIndex(int s, int m)\n\t{\n\t\treturn choices[s];\n\t}\n\n\t@Override\n\tpublic UndefinedReason whyUndefined(int s, int m)\n\t{\n\t\tswitch (choices[s]) {\n\t\tcase -1:\n\t\t\treturn UndefinedReason.UNKNOWN;\n\t\tcase -2:\n\t\t\treturn UndefinedReason.ARBITRARY;\n\t\tcase -3:\n\t\t\treturn UndefinedReason.UNREACHABLE;\n\t\tdefault:\n\t\t\treturn null;\n\t\t}\n\t}\n\n\t@Override\n\tpublic explicit.Model<Value> constructInducedModel(StrategyExportOptions options) throws PrismException\n\t{\n\t\tConstructInducedModel cim = new ConstructInducedModel();\n\t\tcim.setMode(options.getMode()).setReachOnly(options.getReachOnly());\n\t\tModel<Value> inducedModel = cim.constructInducedModel(model, this);\n\t\t// NB: for reach=false (and MDPs), it would be slightly cheaper to use:\n\t\t//Model<Value> inducedModel = model.constructInducedModel(this);\n\t\treturn inducedModel;\n\t}\n\n\t@Override\n\tpublic void exportActions(PrismLog out, StrategyExportOptions options)\n\t{\n\t\tList<State> states = model.getStatesList();\n\t\tboolean showStates = options.getShowStates() && states != null;\n\t\tint n = getNumStates();\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tif (isChoiceDefined(s)) {\n\t\t\t\tout.println((showStates ? states.get(s) : s) + \"=\" + getChoiceActionString(s));\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportInducedModel(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tModel<Value> inducedModel = constructInducedModel(options);\n\t\tinducedModel.exportToPrismExplicitTra(out, options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void exportDotFile(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tModel<Value> inducedModel = constructInducedModel(options);\n\t\tinducedModel.exportToDotFile(out, null, options.getShowStates(), options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tchoices = null;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + IntStream.range(0, getNumStates())\n\t\t\t\t.mapToObj(s -> s + \"=\" + getChoiceActionString(s))\n\t\t\t\t.collect(Collectors.joining(\",\")) + \"]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/MDStrategyIV.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport java.util.List;\nimport java.util.stream.Collectors;\nimport java.util.stream.IntStream;\n\nimport dv.IntegerVector;\nimport explicit.ConstructStrategyProduct;\nimport explicit.NondetModel;\nimport symbolic.model.Model;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\n\n/**\n * Class to store a memoryless deterministic (MD) strategy\n * as an IntegerVector (i.e. stored natively as an array)\n * associated with a sparse/symbolic engine model.\n */\npublic class MDStrategyIV extends StrategyWithStates<Double> implements MDStrategy<Double>\n{\n\t// Model associated with the strategy\n\tprivate Model model;\n\t// Other model info\n\tprivate List<String> actions;\n\t// Array storing MD strategy: *action* index (not choice index) for each state\n\tprivate IntegerVector iv;\n\t\n\t/**\n\t * Create an MDStrategyIV from an IntegerVector.\n\t */\n\tpublic MDStrategyIV(Model model, IntegerVector iv)\n\t{\n\t\tthis.model = model;\n\t\tactions = model.getSynchs();\n\t\tthis.iv = iv;\n\t\tsetStateLookUp(state -> {\n\t\t\ttry {\n\t\t\t\treturn model.getReachableStates().getIndexOfState(state);\n\t\t\t} catch (PrismNotSupportedException e) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t});\n\t}\n\t\n\t@Override\n\tpublic Object getChoiceAction(int s, int m)\n\t{\n\t\tint c = iv.getElement(s);\n\t\treturn c >= 0 ? actions.get(c) : Strategy.UNDEFINED;\n\t}\n\t\n\t@Override\n\tpublic int getChoiceIndex(int s, int m)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\t\n\t@Override\n\tpublic UndefinedReason whyUndefined(int s, int m)\n\t{\n\t\tswitch (iv.getElement(s)) {\n\t\tcase -1:\n\t\t\treturn UndefinedReason.UNKNOWN;\n\t\tcase -2:\n\t\t\treturn UndefinedReason.ARBITRARY;\n\t\tcase -3:\n\t\t\treturn UndefinedReason.UNREACHABLE;\n\t\tdefault:\n\t\t\treturn null;\n\t\t}\n\t}\n\n\t@Override\n\tpublic prism.Model<Double> getModel()\n\t{\n\t\treturn model;\n\t}\n\n\t@Override\n\tpublic Model constructInducedModel(StrategyExportOptions options) throws PrismException\n\t{\n\t\tthrow new PrismException(\"Induced model construction not yet supported for symbolic engines\");\n\t}\n\n\t@Override\n\tpublic void exportInducedModel(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tthrow new PrismException(\"Induced model construction not yet supported for symbolic engines\");\n\t}\n\n\t@Override\n\tpublic void exportDotFile(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tthrow new PrismException(\"Strategy dot export not yet supported for symbolic engines\");\n\t}\n\t\n\t@Override\n\tpublic void clear()\n\t{\n\t\tiv.clear();\n\t\tiv = null;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + IntStream.range(0, getNumStates())\n\t\t\t\t.mapToObj(s -> s + \"=\" + getChoiceActionString(s))\n\t\t\t\t.collect(Collectors.joining(\",\")) + \"]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/MRStrategy.java",
    "content": "package strat;\n\nimport explicit.ConstructInducedModel;\nimport explicit.Distribution;\nimport explicit.DistributionOver;\nimport explicit.Model;\nimport explicit.NondetModel;\nimport parser.State;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.stream.Collectors;\nimport java.util.stream.IntStream;\n\n/**\n * Class to store a memoryless randomised (MR) strategy\n * associated with an explicit engine model.\n */\npublic class MRStrategy<Value> extends StrategyExplicit<Value>\n{\n\t// Probability of selecting choice indices in each state\n\tprotected List<Distribution<Value>> choiceProbs;\n\n\t/**\n\t * Create a blank MRStrategy for a specified model.\n\t */\n\tpublic MRStrategy(NondetModel<Value> model)\n\t{\n\t\tsuper(model);\n\t\tint numStates = model.getNumStates();\n\t\tchoiceProbs = new ArrayList<>(numStates);\n\t\tfor (int i = 0; i < numStates; i++) {\n\t\t\tchoiceProbs.add(new Distribution<>(model.getEvaluator()));\n\t\t}\n\t}\n\n\t/**\n\t * Set the probability of selecting choice index i in state s to p\n\t */\n\tpublic void setChoiceProbability(int s, int i, Value p)\n\t{\n\t\tchoiceProbs.get(s).set(i, p);\n\t}\n\n\t@Override\n\tpublic boolean isRandomised()\n\t{\n\t\treturn true;\n\t}\n\n\t@Override\n\tpublic Object getChoiceAction(int s, int m)\n\t{\n\t\tDistribution<Value> probs = choiceProbs.get(s);\n\t\treturn probs.isEmpty() ? Strategy.UNDEFINED : DistributionOver.create(probs, i -> model.getAction(s, i));\n\t}\n\n\t@Override\n\tpublic int getChoiceIndex(int s, int m)\n\t{\n\t\t// N/A for randomised strategy\n\t\treturn -1;\n\t}\n\n\t@Override\n\tpublic explicit.Model<Value> constructInducedModel(StrategyExportOptions options) throws PrismException\n\t{\n\t\tConstructInducedModel cim = new ConstructInducedModel();\n\t\tcim.setMode(options.getMode()).setReachOnly(options.getReachOnly());\n\t\tModel<Value> inducedModel = cim.constructInducedModel(model, this);\n\t\treturn inducedModel;\n\t}\n\n\t@Override\n\tpublic void exportActions(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tList<State> states = model.getStatesList();\n\t\tboolean showStates = options.getShowStates() && states != null;\n\t\tint n = getNumStates();\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tObject probs = getChoiceAction(s, -1);\n\t\t\tif (probs != UNDEFINED) {\n\t\t\t\tout.println((showStates ? states.get(s) : s) + \"=\" + probs);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportIndices(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tList<State> states = model.getStatesList();\n\t\tboolean showStates = options.getShowStates() && states != null;\n\t\tint n = getNumStates();\n\t\tfor (int s = 0; s < n; s++) {\n\t\t\tDistribution<Value> probs = choiceProbs.get(s);\n\t\t\tif (!probs.isEmpty()) {\n\t\t\t\tout.println((showStates ? states.get(s) : s) + \"=\" + probs);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportInducedModel(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tModel<Value> inducedModel = constructInducedModel(options);\n\t\tinducedModel.exportToPrismExplicitTra(out, options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void exportDotFile(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tModel<Value> inducedModel = constructInducedModel(options);\n\t\tinducedModel.exportToDotFile(out, null, options.getShowStates(), options.getModelPrecision());\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tchoiceProbs = null;\n\t}\n\n\t@Override\n\tpublic String toString()\n\t{\n\t\treturn \"[\" + IntStream.range(0, getNumStates())\n\t\t\t\t.mapToObj(s -> s + \"=\" + getChoiceActionString(s, -1))\n\t\t\t\t.collect(Collectors.joining(\",\")) + \"]\";\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/Strategy.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Aistis Simaitis <aistis.aimaitis@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport explicit.Distribution;\nimport explicit.MDPSimple;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismPrintStreamLog;\nimport simulator.RandomNumberGenerator;\n\n/**\n * Interface for classes to represent strategies,\n * as built in the context of a constructed model.\n * This means that the information is queried by state index.\n * This is for a general class of strategies that may use memory,\n * but this can simply be ignored (e.g., set to -1) if not applicable.\n * This is a generic class where {@code Value} should match the accompanying model.\n * This is also needed for probabilities when the strategy is randomised.\n */\npublic interface Strategy<Value> extends StrategyInfo<Value>\n{\n\t/**\n\t * Get the action chosen by the strategy in the state index s\n\t * and where the current memory of the strategy (if applicable) is m.\n\t * Returns {@link StrategyInfo#UNDEFINED} if undefined.\n\t * For a randomised strategy (and if defined), this method returns\n\t * an instance of DistributionOver&lt;Object&gt; instead of Object.\n\t * Pass an arbitrary value (e.g. -1) for m if memory is not relevant.\n\t */\n\tpublic Object getChoiceAction(int s, int m);\n\t\n\t/**\n\t * Get the probability with which an action is chosen by the strategy in the state index s\n\t * and where the current memory of the strategy (if applicable) is m.\n\t * Pass an arbitrary value (e.g. -1) for m if memory is not relevant.\n\t */\n\tpublic default Value getChoiceActionProbability(int s, int m, Object act)\n\t{\n\t\treturn getChoiceActionProbability(getChoiceAction(s, m), act);\n\t}\n\t\n\t/**\n\t * Is an action chosen by the strategy in the state index s\n\t * and where the current memory of the strategy (if applicable) is m?\n\t * For a randomised strategy: is the action chosen with positive probability?\n\t * Pass an arbitrary value (e.g. -1) for m if memory is not relevant.\n\t */\n\tpublic default boolean isActionChosen(int s, int m, Object act)\n\t{\n\t\treturn isActionChosen(getChoiceAction(s, m), act);\n\t}\n\t\n\t/**\n\t * Sample an action chosen by the strategy in the state index s\n\t * and where the current memory of the strategy (if applicable) is m.\n\t * For a deterministic strategy, this returns the (unique) chosen action;\n\t * for a randomised strategy, an action is sampled according to the strategy's distribution.\n\t * Returns {@link StrategyInfo#UNDEFINED} if undefined.\n\t * Pass an arbitrary value (e.g. -1) for m if memory is not relevant.\n\t */\n\tpublic default Object sampleChoiceAction(int s, int m, RandomNumberGenerator rng)\n\t{\n\t\treturn sampleChoiceAction(getChoiceAction(s, m), rng);\n\t}\n\t\n\t/**\n\t * Get the index of the choice picked by the strategy in the state index s\n\t * and where the current memory of the strategy (if applicable) is m\n\t * (assuming it is deterministic).\n\t * The index is defined with respect to a particular model, stored locally.\n\t * Returns a negative value (not necessarily -1) if undefined.\n\t * Pass an arbitrary value (e.g. -1) for m if memory is not relevant.\n\t */\n\tpublic int getChoiceIndex(int s, int m);\n\n\t/**\n\t * Is a choice defined by the strategy in the state index s\n\t * and where the current memory of the strategy (if applicable) is m.\n\t * Pass an arbitrary value (e.g. -1) for m if memory is not relevant.\n\t */\n\tpublic default boolean isChoiceDefined(int s, int m)\n\t{\n\t\treturn getChoiceAction(s, m) != UNDEFINED;\n\t}\n\t\n\t/**\n\t * Optionally, return reason why a choice is undefined by the strategy in the state index s\n\t * and where the current memory of the strategy (if applicable) is m.\n\t * Returns null if there is no reason.\n\t * Pass an arbitrary value (e.g. -1) for m if memory is not relevant.\n\t */\n\tpublic default UndefinedReason whyUndefined(int s, int m)\n\t{\n\t\t// No reason provided by default\n\t\treturn null;\n\t}\n\t\n\t/**\n\t * Get a string representing the choice made by the strategy in the state index s\n\t * and where the current memory of the strategy (if applicable) is m.\n\t * For unlabelled choices, this should return \"\", not null.\n\t * This may also indicate the reason why it is undefined, if it is.\n\t * Pass an arbitrary value (e.g. -1) for m if memory is not relevant.\n\t */\n\tpublic default String getChoiceActionString(int s, int m)\n\t{\n\t\tObject action = getChoiceAction(s, m);\n\t\tif (action != UNDEFINED) {\n\t\t\treturn action == null ? \"\" : action.toString();\n\t\t} else {\n\t\t\tUndefinedReason why = whyUndefined(s, m);\n\t\t\tif (why == null) {\n\t\t\t\treturn \"?\";\n\t\t\t}\n\t\t\tswitch (why) {\n\t\t\tcase UNKNOWN:\n\t\t\t\treturn \"?\";\n\t\t\tcase ARBITRARY:\n\t\t\t\treturn \"\";\n\t\t\tcase UNREACHABLE:\n\t\t\t\treturn \"-\";\n\t\t\tdefault:\n\t\t\t\treturn \"?\";\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\n\t * For a strategy with memory, get the size of the memory\n\t * (memory values are then assumed to be 0...memSize-1.\n\t * A memoryless strategy should return 0. \n\t */\n    public default int getMemorySize()\n    {\n    \t// No memory by default\n    \treturn 0;\n    }\n    \n\t/**\n\t * For a strategy with memory, get the initial value of the memory\n\t * based on the initial state of the model.\n\t * @param sInit Index of initial model state\n\t */\n    public default int getInitialMemory(int sInit)\n    {\n    \t// No memory by default\n    \treturn -1;\n    }\n    \n\t/**\n\t * For a strategy with memory, get the updated value of the memory\n\t * based on its current value and the new current state of the model\n\t * (plus the action that was taken to get there).\n\t * @param m Current strategy memory value\n\t * @param action Last action taken in model\n\t * @param sNext Index of new model state\n\t */\n    public default int getUpdatedMemory(int m, Object action, int sNext)\n    {\n    \t// No memory by default\n    \treturn -1;\n    }\n\n\t/**\n\t * Get the model associated with this strategy.\n\t */\n\tpublic prism.Model<Value> getModel();\n\n\t/**\n\t * Get the number of states of the model associated with this strategy.\n\t */\n\tpublic default int getNumStates()\n\t{\n\t\treturn getModel().getNumStates();\n\t}\n\n\t/**\n\t * Get the number of players of the model associated with this strategy.\n\t */\n\tpublic default int getNumModelPlayers()\n\t{\n\t\treturn getModel().getNumPlayers();\n\t}\n\n\t/**\n\t * Get the type of model induced by this strategy when applied to its associated model.\n\t * Returns null if the model type cannot be deduced.\n\t * @param mode Mode of induced model construction (\"restrict\" or \"reduce\")\n\t */\n\tpublic default ModelType getInducedModelType(StrategyExportOptions.InducedModelMode mode)\n\t{\n\t\treturn getInducedModelType(getModel().getModelType(), getNumModelPlayers(), mode);\n\t}\n\n\t/**\n\t * Export the model induced by this strategy to a PrismLog.\n\t */\n\tpublic default prism.Model<Value> constructInducedModel() throws PrismException\n\t{\n\t\treturn constructInducedModel(new StrategyExportOptions());\n\t}\n\n\t/**\n\t * Export the model induced by this strategy to a PrismLog.\n\t */\n\tpublic prism.Model<Value> constructInducedModel(StrategyExportOptions options) throws PrismException;\n\n\t/**\n\t * Export the strategy to a PrismLog, with specified export type and options.\n\t */\n\tpublic default void export(PrismLog out, StrategyExportOptions options) throws PrismException\n\t{\n\t\tswitch (options.getType()) {\n\t\t\tcase ACTIONS:\n\t\t\t\texportActions(out, options);\n\t\t\t\tbreak;\n\t\t\tcase INDICES:\n\t\t\t\texportIndices(out, options);\n\t\t\t\tbreak;\n\t\t\tcase INDUCED_MODEL:\n\t\t\t\texportInducedModel(out, options);\n\t\t\t\tbreak;\n\t\t\tcase DOT_FILE:\n\t\t\t\texportDotFile(out, options);\n\t\t\t\tbreak;\n\t\t}\n\t}\n\n\t/**\n\t * Export the strategy to a PrismLog, displaying strategy choices as action names.\n\t */\n\tpublic default void exportActions(PrismLog out) throws PrismException\n\t{\n\t\texportActions(out, new StrategyExportOptions());\n\t}\n\n\t/**\n\t * Export the strategy to a PrismLog, displaying strategy choices as action names.\n\t * @param options The options for export\n\t */\n\tpublic void exportActions(PrismLog out, StrategyExportOptions options) throws PrismException;\n\n\t/**\n\t * Export the strategy to a PrismLog, displaying strategy choices as indices.\n\t */\n\tpublic default void exportIndices(PrismLog out) throws PrismException\n\t{\n\t\texportIndices(out, new StrategyExportOptions());\n\t}\n\n\t/**\n\t * Export the strategy to a PrismLog, displaying strategy choices as indices.\n\t * @param options The options for export\n\t */\n\tpublic void exportIndices(PrismLog out, StrategyExportOptions options) throws PrismException;\n\n\t/**\n\t * Export the model induced by this strategy to a PrismLog.\n\t */\n\tdefault void exportInducedModel(PrismLog out) throws PrismException\n\t{\n\t\texportInducedModel(out, new StrategyExportOptions());\n\t}\n\n\t/**\n\t * Export the model induced by this strategy to a PrismLog.\n\t * @param options The options for export\n\t */\n\tpublic void exportInducedModel(PrismLog out, StrategyExportOptions options) throws PrismException;\n\n\t/**\n\t * Export the strategy to a dot file (of the model showing the strategy).\n\t */\n\tdefault void exportDotFile(PrismLog out) throws PrismException\n\t{\n\t\texportDotFile(out, new StrategyExportOptions());\n\t}\n\n\t/**\n\t * Export the strategy to a dot file (of the model showing the strategy).\n\t * @param options The options for export\n\t */\n\tpublic void exportDotFile(PrismLog out, StrategyExportOptions options) throws PrismException;\n\t\n\t/**\n\t * Clear storage of the strategy.\n\t */\n\tpublic void clear();\n\n\t/**\n\t * Test code.\n\t */\n\tpublic static void main(String[] args)\n\t{\n\t\tPrismLog mainLog = new PrismPrintStreamLog(System.out);\n\n\t\tMDPSimple mdp = new MDPSimple(2);\n\t\tmdp.addInitialState(0);\n\t\tDistribution distr2 = Distribution.ofDouble();\n\t\tdistr2.add(0, 0.4);\n\t\tdistr2.add(1, 0.6);\n\t\tDistribution distr1 = Distribution.ofDouble();\n\t\tdistr1.add(0, 1.0);\n\t\tmdp.addActionLabelledChoice(0, distr1, \"a\");\n\t\tmdp.addActionLabelledChoice(0, distr2, \"b\");\n\t\tmdp.addActionLabelledChoice(1, distr1, \"c\");\n\t\tmdp.addActionLabelledChoice(1, distr2, \"d\");\n\n\t\ttry {\n\t\t\tSystem.out.println(\"MDP: \" + mdp);\n\n\t\t\tStrategy strat = null;\n\n\t\t\tstrat = new MDStrategyArray(mdp, new int[] {0,1});\n\t\t\tSystem.out.println(\"MDStrategyArray: \" + strat);\n\t\t\tstrat.exportActions(mainLog);\n\t\t\t((explicit.Model) strat.constructInducedModel()).exportToPrismExplicitTra(\"stdout\");\n\t\t\tSystem.out.println();\n\n\t\t\tstrat = new FMDStrategyStep(mdp, 2);\n\t\t\t((FMDStrategyStep) strat).setStepChoices(0, new int[] {0,1});\n\t\t\t((FMDStrategyStep) strat).setStepChoices(1, new int[] {1,1});\n\t\t\tSystem.out.println(\"FMDStrategyStep: \" + strat);\n\t\t\tstrat.exportActions(mainLog);\n\t\t\t((explicit.Model) strat.constructInducedModel()).exportToPrismExplicitTra(\"stdout\");\n\t\t\tSystem.out.println();\n\n\t\t\tstrat = new MRStrategy(mdp);\n\t\t\t((MRStrategy) strat).setChoiceProbability(0, 0, 0.1);\n\t\t\t((MRStrategy) strat).setChoiceProbability(0, 1, 0.9);\n\t\t\t((MRStrategy) strat).setChoiceProbability(1, 0, 1.0);\n\t\t\tSystem.out.println(\"MRStrategy: \" + strat);\n\t\t\tstrat.exportActions(mainLog);\n\t\t\t((explicit.Model) strat.constructInducedModel(new StrategyExportOptions().setMode(StrategyExportOptions.InducedModelMode.REDUCE))).exportToPrismExplicitTra(\"stdout\");\n\t\t\t((explicit.Model) strat.constructInducedModel(new StrategyExportOptions().setMode(StrategyExportOptions.InducedModelMode.RESTRICT))).exportToPrismExplicitTra(\"stdout\");\n\t\t\tSystem.out.println();\n\n\t\t} catch (PrismException e) {\n\t\t\tthrow new RuntimeException(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/StrategyExplicit.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport explicit.NondetModel;\nimport prism.Evaluator;\n\n/**\n * Base class for implementations of Strategy associated with an explicit engine model.\n */\npublic abstract class StrategyExplicit<Value> extends StrategyWithStates<Value>\n{\n\t// Model associated with the strategy\n\tprotected NondetModel<Value> model;\n\n\tpublic StrategyExplicit(NondetModel<Value> model)\n\t{\n\t\tthis.model = model;\n\t\tif (model.getStatesList() != null) {\n\t\t\tsetStateLookUp(state -> model.getStatesList().indexOf(state));\n\t\t} else {\n\t\t\tsetStateLookUp(state -> -1);\n\t\t}\n\t}\n\n\t@Override\n\tpublic NondetModel<Value> getModel()\n\t{\n\t\treturn model;\n\t}\n\n\t@Override\n\tpublic Evaluator<Value> getEvaluator()\n\t{\n\t\treturn model.getEvaluator();\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/StrategyExportOptions.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2023-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage strat;\n\nimport static prism.PrismSettings.DEFAULT_EXPORT_MODEL_PRECISION;\n\nimport java.util.Optional;\n\n/**\n * Class to represent options for exporting strategies.\n */\npublic class StrategyExportOptions implements Cloneable\n{\n\t/**\n\t * Types of strategy export\n\t */\n\tpublic enum StrategyExportType {\n\t\tACTIONS, INDICES, INDUCED_MODEL, DOT_FILE;\n\t\tpublic String description()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase ACTIONS:\n\t\t\t\t\treturn \"as actions\";\n\t\t\t\tcase INDICES:\n\t\t\t\t\treturn \"as indices\";\n\t\t\t\tcase INDUCED_MODEL:\n\t\t\t\t\treturn \"as an induced model\";\n\t\t\t\tcase DOT_FILE:\n\t\t\t\t\treturn \"as a dot file\";\n\t\t\t\tdefault:\n\t\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Type of strategy export\n\t */\n\tprivate StrategyExportType type;\n\n\t/**\n\t * Modes of construction for an induced model:\n\t * \"restrict\" (same model type but restrict to selected action choices); or\n\t * \"reduce\" (change mode type by removing nondeterminism)\n\t */\n\tpublic enum InducedModelMode {\n\t\tRESTRICT, REDUCE;\n\t\tpublic String description()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\t\tcase RESTRICT:\n\t\t\t\t\treturn \"restricted\";\n\t\t\t\tcase REDUCE:\n\t\t\t\t\treturn \"reduced\";\n\t\t\t\tdefault:\n\t\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Mode of construction for an induced model.\n\t */\n\tprivate Optional<InducedModelMode> mode = Optional.empty();\n\n\t/**\n\t * Whether to restrict strategy/model to reachable states\n\t */\n\tprivate Optional<Boolean> reachOnly = Optional.empty();\n\n\t/**\n\t * Whether to show full state details\n\t */\n\tprivate Optional<Boolean> showStates = Optional.empty();\n\n\t/**\n\t * Whether to merge observationally equivalent states in partially observable models\n\t */\n\tprivate Optional<Boolean> mergeObs = Optional.empty();\n\n\t/**\n\t * Precision to export probabilities/etc. (number of significant decimal places)\n\t */\n\tprivate Optional<Integer> modelPrecision = Optional.empty();\n\n\t// Constructors\n\n\t/**\n\t * Construct a StrategyExportOptions with default options.\n\t */\n\tpublic StrategyExportOptions()\n\t{\n\t\tthis(StrategyExportType.ACTIONS);\n\t}\n\n\t/**\n\t * Construct a StrategyExportOptions with specified export type and default options.\n\t */\n\tpublic StrategyExportOptions(StrategyExportType type)\n\t{\n\t\tthis.type = type;\n\t}\n\n\t// Set methods\n\n\t/**\n\t * Set the type of strategy export.\n\t */\n\tpublic StrategyExportOptions setType(StrategyExportType type)\n\t{\n\t\tthis.type = type;\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set the mode of construction for an induced model:\n\t * \"restrict\" (same model type but restrict to selected action choices); or\n\t * \"reduce\" (change mode type by removing nondeterminism)\n\t */\n\tpublic StrategyExportOptions setMode(InducedModelMode mode)\n\t{\n\t\tthis.mode = Optional.of(mode);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to restrict strategy/model to reachable states.\n\t */\n\tpublic StrategyExportOptions setReachOnly(boolean reachOnly)\n\t{\n\t\tthis.reachOnly = Optional.of(reachOnly);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to show full state details.\n\t */\n\tpublic StrategyExportOptions setShowStates(boolean showStates)\n\t{\n\t\tthis.showStates = Optional.of(showStates);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set whether to merge observationally equivalent states in partially observable models.\n\t */\n\tpublic StrategyExportOptions setMergeObservations(boolean mergeObs)\n\t{\n\t\tthis.mergeObs = Optional.of(mergeObs);\n\t\treturn this;\n\t}\n\n\t/**\n\t * Set precision to export probabilities/etc. (number of significant decimal places).\n\t */\n\tpublic StrategyExportOptions setModelPrecision(int modelPrecision)\n\t{\n\t\tthis.modelPrecision = Optional.of(modelPrecision);\n\t\treturn this;\n\t}\n\n\t// Get methods\n\n\t/**\n\t * Get the type of strategy export.\n\t */\n\tpublic StrategyExportType getType()\n\t{\n\t\treturn type;\n\t}\n\n\t/**\n\t * Get the mode of construction for an induced model.\n\t */\n\tpublic InducedModelMode getMode()\n\t{\n\t\treturn mode.orElse(InducedModelMode.REDUCE);\n\t}\n\n\t/**\n\t * Whether to restrict strategy/model to reachable states.\n\t */\n\tpublic boolean getReachOnly()\n\t{\n\t\treturn reachOnly.orElse(!getType().equals(StrategyExportType.INDUCED_MODEL));\n\t}\n\n\t/**\n\t * Whether to show full state details.\n\t */\n\tpublic boolean getShowStates()\n\t{\n\t\treturn showStates.orElse(true);\n\t}\n\n\t/**\n\t * Whether to merge observationally equivalent states in partially observable models.\n\t */\n\tpublic boolean getMergeObservations()\n\t{\n\t\treturn mergeObs.orElse(true);\n\t}\n\n\t/**\n\t * Precision to export probabilities/etc. (number of significant decimal places).\n\t */\n\tpublic int getModelPrecision()\n\t{\n\t\treturn modelPrecision.orElse(DEFAULT_EXPORT_MODEL_PRECISION);\n\t}\n\n\t/**\n\t * Get string description for type of strategy export.\n\t */\n\tpublic String description()\n\t{\n\t\tString s = getType().description();\n\t\tif (getType() == StrategyExportType.INDUCED_MODEL) {\n\t\t\ts += \" (\" + getMode().description() + \")\";\n\t\t}\n\t\treturn s;\n\t}\n\n\t/**\n\t * Perform a shallow copy of the options.\n\t */\n\t@Override\n\tpublic StrategyExportOptions clone()\n\t{\n\t\ttry {\n\t\t\treturn (StrategyExportOptions) super.clone();\n\t\t} catch (CloneNotSupportedException e) {\n\t\t\tthrow new InternalError(\"Object#clone is expected to work for Cloneable objects\", e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/StrategyGenerator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport parser.State;\nimport simulator.RandomNumberGenerator;\n\n/**\n * Interface for classes to represent strategies which are queried by State.\n * <br><br>\n * The querying is done interactively: the classes are informed which states are visited,\n * via {@link #initialise(State)} and {@link #update(Object, State)} and the current\n * action to be taken in the latest state is available by calling {@link #getCurrentChoiceAction()}.\n * <br><br>\n * If the strategy has memory, this is kept track of and obtained via {@link #getCurrentMemory()}.\n * The strategy can be reset, in order to query the action to be taken for arbitrary states\n * and arbitrary current memory values, by calling {@link #reset(State, int)}. \n * <br><br>\n * This is a generic class where {@code Value} should match the accompanying model.\n * This is also needed for probabilities when the strategy is randomised.\n */\npublic interface StrategyGenerator<Value> extends StrategyInfo<Value>\n{\n\t/**\n\t * Initialise the strategy, based on an initial model state.\n\t * @param state Initial state of the model\n\t */\n\tpublic StrategyGenerator<Value> initialise(State state);\n\n\t/**\n\t * Update the strategy, based on the next step in a model's history.\n\t * @param action The action taken in the previous state of the model\n\t * @param state The new state of the model\n\t */\n\tpublic StrategyGenerator<Value> update(Object action, State state);\n\t\n\t/**\n\t * Reset the strategy to provide action choices for a particular state\n\t * and a particular current memory value for the strategy.\n\t * @param state The current state of the model\n\t * @param memory The current memory for the strategy (-1 if not applicable)\n\t */\n\tpublic StrategyGenerator<Value> reset(State state, int memory);\n\t\n\t/**\n\t * Get the action chosen by the strategy in the current state (assuming it is deterministic). \n\t * Returns {@link StrategyInfo#UNDEFINED} if undefined.\n\t * For a randomised strategy (and if defined), this method returns\n\t * an instance of DistributionOver&lt;Object&gt; instead of Object.\n\t */\n\tpublic Object getCurrentChoiceAction();\n\t\n\t/**\n\t * Get the probability with which an action is chosen by the strategy in the current state.\n\t */\n\tpublic default Value getCurrentChoiceActionProbability(Object act)\n\t{\n\t\treturn getChoiceActionProbability(getCurrentChoiceAction(), act);\n\t}\n\t\n\t/**\n\t * Is an action chosen by the strategy in the current state?\n\t * For a randomised strategy: is the action chosen with positive probability?\n\t */\n\tpublic default boolean isActionChosenCurrently(Object act)\n\t{\n\t\treturn isActionChosen(getCurrentChoiceAction(), act);\n\t}\n\t\n\t/**\n\t * Sample an action chosen by the strategy in the current state.\n\t * For a deterministic strategy, this returns the (unique) chosen action;\n\t * for a randomised strategy, an action is sampled according to the strategy's distribution.\n\t * Returns {@link StrategyInfo#UNDEFINED} if undefined.\n\t */\n\tpublic default Object sampleCurrentChoiceAction(RandomNumberGenerator rng)\n\t{\n\t\treturn sampleChoiceAction(getCurrentChoiceAction(), rng);\n\t}\n\t\n\t/**\n\t * Get the current value of the memory for the strategy (-1 if not applicable).\n\t */\n\tpublic int getCurrentMemory();\n\t\n\t/**\n\t * Get a description of the current value of the memory for the strategy.\n\t * By default, this is a just the integer value of the memory as a string,\n\t * but some strategies will provide a more meaningful representation.\n\t * Returns \"?\" if memory is not applicable (or unknown).\n\t */\n\tpublic default String getCurrentMemoryString()\n\t{\n\t\treturn getMemoryString(getCurrentMemory());\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/StrategyInfo.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport java.util.Objects;\n\nimport explicit.DistributionOver;\nimport prism.Evaluator;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismNotSupportedException;\nimport simulator.RandomNumberGenerator;\nimport strat.StrategyExportOptions.InducedModelMode;\n\n/**\n * Super-interface for Strategy and StrategyGenerator interfaces.\n * Constants, enums and methods for basic information about strategies. \n * This is a generic class where {@code Value} is the type of\n * probabilities when the strategy is randomised.\n */\npublic interface StrategyInfo<Value>\n{\n\t// Constants / enums\n\t\n\t/** Strategy classes in terms of memory used */\n\tpublic enum Memory {\n\t\tNONE, FINITE, INFINITE;\n\t};\n\t\n\t/** Action returned when choice is undefined by strategy */\n\tpublic static final Object UNDEFINED = \"?\";\n\t\n\t/** Possible reasons for a choice being undefined */\n\tpublic enum UndefinedReason {\n\t\tUNKNOWN, ARBITRARY, UNREACHABLE;\n\t};\n\t\n\t// Methods\n\t\n\t/**\n\t * Strategy class in terms of memory use\n\t */\n\tpublic default Memory memory()\n\t{\n\t\t// Default to memoryless; override for other cases\n\t\treturn Memory.NONE;\n\t}\n\t\n\t/**\n\t * Does the strategy use memory?\n\t */\n\tpublic default boolean hasMemory()\n\t{\n\t\treturn memory() != Memory.NONE;\n\t}\n\t\n\t/**\n\t * Does the strategy use randomisation for action selection?\n\t */\n\tpublic default boolean isRandomised()\n\t{\n\t\t// Default to deterministic\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get the probability with which an action is chosen by the strategy,\n\t * extracting this information from a decision taken by the strategy,\n\t * as returned by getChoiceAction().\n\t * @param decision The decision taken by the strategy\n\t * @param act The action to check\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic default Value getChoiceActionProbability(Object decision, Object act)\n\t{\n\t\tif (decision instanceof DistributionOver) {\n\t\t\treturn ((DistributionOver<Value,Object>) decision).getProbability(act);\n\t\t} else {\n\t\t\treturn Objects.equals(act, decision) ? getEvaluator().one() : getEvaluator().zero();\n\t\t}\n\t}\n\t\n\t/**\n\t * Is an action chosen by the strategy,\n\t * extracting this information from a decision taken by the strategy,\n\t * as returned by getChoiceAction()?\n\t * For a randomised strategy: is the action chosen with positive probability?\n\t * @param decision The decision taken by the strategy\n\t * @param act The action to check\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic default boolean isActionChosen(Object decision, Object act)\n\t{\n\t\tif (decision instanceof DistributionOver) {\n\t\t\t// Randomised strategy: check positive probability\n\t\t\tValue prob = ((DistributionOver<Value,Object>) decision).getProbability(act);\n\t\t\treturn getEvaluator().gt(prob, getEvaluator().zero());\n\t\t} else {\n\t\t\t// Deterministic strategy: check equality (including nulls)\n\t\t\treturn Objects.equals(act, decision);\n\t\t}\n\t}\n\t\n\t/**\n\t * Sample an action chosen by the strategy,\n\t * extracting this information from a decision taken by the strategy,\n\t * as returned by getChoiceAction().\n\t * For a deterministic strategy, this returns the (unique) chosen action;\n\t * for a randomised strategy, an action is sampled according to the strategy's distribution.\n\t * Returns {@link StrategyInfo#UNDEFINED} if undefined.\n\t * @param decision The decision taken by the strategy\n\t * @param rng Random number generator\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic default Object sampleChoiceAction(Object decision, RandomNumberGenerator rng)\n\t{\n\t\tif (decision == UNDEFINED) {\n\t\t\treturn decision;\n\t\t}\n\t\tif (decision instanceof DistributionOver) {\n\t\t\t// Randomised strategy: sample from distribution\n\t\t\treturn ((DistributionOver<Value,Object>) decision).sample(rng);\n\t\t} else {\n\t\t\t// Deterministic strategy: return unique action choice\n\t\t\treturn decision;\n\t\t}\n\t}\n\n\t/**\n\t * Get the action label for a choice in the model induced by this strategy.\n\t * For a deterministic strategy, it is unchanged.\n\t * For a randomised strategy, a descriptive string identifier is created.\n\t * @param decision The decision taken by the strategy\n\t * @param act The action to check\n\t */\n\tpublic default Object getInducedAction(Object decision, Object act)\n\t{\n\t\tif (decision == UNDEFINED) {\n\t\t\treturn null;\n\t\t}\n\t\tif (decision instanceof DistributionOver) {\n\t\t\treturn Prism.toIdentifier(decision);\n\t\t} else {\n\t\t\treturn decision;\n\t\t}\n\t}\n\n\t/**\n\t * For a strategy with memory, get a description of a given memory value.\n\t * By default, this is a just the integer value of the memory as a string,\n\t * but some strategies will provide a more meaningful representation.\n\t * Returns \"?\" if memory is not applicable (or unknown).\n\t * @param m Memory value to look up\n\t */\n    public default String getMemoryString(int m)\n    {\n\t\treturn m == -1 ? \"?\" : Integer.toString(m);\n    }\n\n\t/**\n\t * Get the type of model induced by this strategy when applied to a type of model.\n\t * Returns null if the model type cannot be deduced.\n\t * @param modelType The type of model to which the strategy will be applied\n\t * @param numPlayers The number of players in the model (if relevant)\n\t * @param mode Mode of induced model construction (\"restrict\" or \"reduce\")\n\t */\n\tpublic default ModelType getInducedModelType(ModelType modelType, int numPlayers, InducedModelMode mode)\n\t{\n\t\tModelType inducedModelType = null;\n\t\tif (mode == InducedModelMode.REDUCE) {\n\t\t\tswitch (modelType) {\n\t\t\t\tcase MDP:\n\t\t\t\tcase POMDP:\n\t\t\t\tcase STPG:\n\t\t\t\t\tinducedModelType = ModelType.DTMC;\n\t\t\t\t\tbreak;\n\t\t\t\tcase IMDP:\n\t\t\t\t\tinducedModelType = ModelType.IDTMC;\n\t\t\t\t\tbreak;\n\t\t\t}\n\t\t} else {\n\t\t\tinducedModelType = modelType;\n\t\t}\n\t\treturn inducedModelType;\n\t}\n\n\t/**\n\t * Get an Evaluator for the probability values returned when this strategy is randomised.\n\t * By default, this is an evaluator for the (usual) case when Value is Double.\n\t */\n\t@SuppressWarnings(\"unchecked\")\n\tpublic default Evaluator<Value> getEvaluator()\n\t{\n\t\treturn (Evaluator<Value>) Evaluator.forDouble();\n\t}\t\n}\n"
  },
  {
    "path": "prism/src/strat/StrategyWithStates.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage strat;\n\nimport java.util.function.Function;\n\nimport parser.State;\nimport prism.PrismException;\n\n/**\n * Base class for implementations of Strategy\n * with additional support to query by State (i.e., StrategyGenerator)\n */\npublic abstract class StrategyWithStates<Value> implements Strategy<Value>, StrategyGenerator<Value>\n{\n\t// State look-up functionality\n\t\n\t/** State lookup function; should return -1 for \"not found\" */\n\tprotected Function<State,Integer> stateLookUp = null;\n\t\n\t/**\n\t * Set the state look-up mechanism\n\t */\n\tpublic void setStateLookUp(Function<State,Integer> stateLookUp)\n\t{\n\t\tthis.stateLookUp = stateLookUp;\n\t}\n\t\n\t/**\n\t * Get the index of a state, provided as a {@code State} object.\n\t * Returns -1 if the state is not known.\n\t * Throws an exception if there is no way to look this up.\n\t */\n\tpublic int getStateIndex(State state) throws PrismException\n\t{\n\t\tif (stateLookUp == null) {\n\t\t\tthrow new PrismException(\"Strategy does not support state look-up\");\n\t\t}\n\t\treturn stateLookUp.apply(state);\n\t}\n\t\n\t// Implement StrategyGenerator interface via Strategy methods and state look-up\n\t\n\tprotected State currentState = null;\n\tprotected int currentStateIndex = -1;\n\tprotected int currentMemory = -1;\n\t\n\t@Override\n\tpublic StrategyGenerator<Value> initialise(State state)\n\t{\n\t\tcurrentState = state;\n\t\tcurrentStateIndex = stateLookUp.apply(state);\n\t\tcurrentMemory = getInitialMemory(currentStateIndex);\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic StrategyGenerator<Value> update(Object action, State state)\n\t{\n\t\tcurrentState = state;\n\t\tcurrentStateIndex = stateLookUp.apply(state);\n\t\tcurrentMemory = getUpdatedMemory(currentMemory, null, currentStateIndex);\n\t\treturn this;\n\t}\n\t\n\t@Override\n\tpublic StrategyGenerator<Value> reset(State state, int memory)\n\t{\n\t\tcurrentState = state;\n\t\tcurrentStateIndex = stateLookUp.apply(state);\n\t\tcurrentMemory = memory;\n\t\treturn this;\n\t}\n\t\n\t@Override\n\tpublic Object getCurrentChoiceAction()\n\t{\n\t\treturn getChoiceAction(currentStateIndex, currentMemory);\n\t}\n\t\n\t@Override\n\tpublic int getCurrentMemory()\n\t{\n\t\treturn currentMemory;\n\t}\n}\n"
  },
  {
    "path": "prism/src/strat/package-info.java",
    "content": "/**\n * Classes to represent/manipulate strategies (of MDPs, games, etc.)\n */\npackage strat;\n"
  },
  {
    "path": "prism/src/symbolic/build/ExplicitFiles2MTBDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t* Ludwig Pauly <ludwigpauly@gmail.com> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.build;\n\nimport java.util.LinkedHashMap;\nimport java.util.Vector;\nimport java.util.Map.Entry;\n\nimport io.ExplicitModelImporter;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.DeclarationType;\nimport prism.*;\nimport symbolic.model.Model;\nimport symbolic.model.ModelSymbolic;\nimport symbolic.model.ModelVariablesDD;\nimport symbolic.model.NondetModel;\nimport symbolic.model.ProbModel;\nimport symbolic.model.StochModel;\n\n/**\n * Class to convert explicit-state file storage of a model to symbolic representation.\n */\npublic class ExplicitFiles2MTBDD extends PrismNativeComponent\n{\n\t// Importer / files to read in from\n\tprivate ExplicitModelImporter importer;\n\n\t// Model info\n\tprivate ModelInfo modelInfo;\n\tprivate ModelType modelType;\n\tprivate VarList varList;\n\tprivate int numVars;\n\tprivate int numStates;\n\n\t// Explicit storage of states\n\tprivate int statesArray[][] = null;\n\n\t// Reward info\n\tprivate RewardInfo rewardInfo;\n\n\t// mtbdd stuff\n\n\tprivate ModelSymbolic model = null;\n\n\t// dds/dd vars - whole system\n\tprivate JDDNode trans; // transition matrix dd\n\tprivate JDDNode start; // dd for start state\n\tprivate JDDNode stateRewards[]; // array of dds for state rewards\n\tprivate JDDNode transRewards[]; // array of dds for transition rewards\n\tprivate JDDVars allDDRowVars; // all dd vars (rows)\n\tprivate JDDVars allDDColVars; // all dd vars (cols)\n\tprivate JDDVars allDDNondetVars; // all dd vars (all non-det.)\n\t// dds/dd vars - variables\n\tprivate JDDVars[] varDDRowVars; // dd vars (row/col) for each module variable\n\tprivate JDDVars[] varDDColVars;\n\t// dds/dd vars - nondeterminism\n\n\tprivate ModelVariablesDD modelVariables;\n\t\n\t// action info\n\tprivate Vector<String> synchs; // list of action names\n\tprivate JDDNode transActions; // dd for transition action labels (MDPs)\n\tprivate Vector<JDDNode> transPerAction; // dds for transition action labels (D/CTMCs)\n\n\tprivate int maxNumChoices = 0;\n\tprivate LinkedHashMap<String, JDDNode> labelsDD;\n\tprivate JDDNode labelDeadlock;\n\n\t// Progress info\n\tprivate ProgressDisplay progress;\n\tprivate int transitionsImported;\n\n\tpublic ExplicitFiles2MTBDD(Prism prism) throws PrismException\n\t{\n\t\tsuper(prism);\n\t}\n\n\t/**\n\t * Build a Model corresponding to the passed in states/transitions/labels files.\n\t * Variable info and model type is taken from a {@code ModelInfo} object.\n\t * The number of states should also be passed in as {@code numStates}.\n\t */\n\tpublic Model build(ExplicitModelImporter importer) throws PrismException\n\t{\n\t\tthis.importer = importer;\n\t\tmodelInfo = importer.getModelInfo();\n\t\tmodelType = modelInfo.getModelType();\n\t\tvarList = modelInfo.createVarList();\n\t\tnumVars = varList.getNumVars();\n\t\tnumStates = importer.getNumStates();\n\t\tmodelVariables = new ModelVariablesDD();\n\t\trewardInfo = importer.getRewardInfo();\n\n\t\t// Check model is defined as doubles\n\t\tif (importer.modelIsExact()) {\n\t\t\tthrow new PrismException(\"Cannot import an exact model unless in exact mode\");\n\t\t}\n\n\t\t// Tell importer we need state-indexed transition rewards\n\t\timporter.setTransitionRewardIndexing(ExplicitModelImporter.TransitionRewardIndexing.STATE);\n\n\t\t// Tell importer not to fix deadlocks; we do it here\n\t\timporter.setFixDeadlocks(false);\n\n\t\t// Build states list, if info is available\n\t\t// (importer can handle case where it is unavailable, but we bypass this)\n\t\tif (importer.providesStates()) {\n\t\t\treadStatesFromFile();\n\t\t}\n\n\t\treturn buildModel();\n\t}\n\n\t/** read info about reachable state space from file and store explicitly */\n\tprivate void readStatesFromFile() throws PrismException\n\t{\n\t\tstatesArray = new int[numStates][];\n\t\tfor (int s = 0; s < numStates; s++) {\n\t\t\tstatesArray[s] = new int[numVars];\n\t\t}\n\t\timporter.extractStates((s, i, o) -> statesArray[s][i] = varList.encodeToInt(i, o));\n\t}\n\n\t/** build model */\n\tprivate Model buildModel() throws PrismException\n\t{\n\t\tJDDNode tmp, tmp2;\n\t\tJDDVars ddv;\n\t\tint i;\n\n\t\t// for an mdp, compute the max number of choices in a state\n\t\tif (modelType == ModelType.MDP) {\n\t\t\tmaxNumChoices = importer.computeMaxNumChoices();\n\t\t}\n\n\t\t// allocate dd variables\n\t\tallocateDDVars();\n\n\t\t// construct transition matrix from file\n\t\tbuildTrans();\n\n\t\t// get rid of any nondet dd variables not needed\n\t\tif (modelType == ModelType.MDP) {\n\t\t\ttmp = JDD.GetSupport(trans);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDRowVars);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDColVars);\n\t\t\ttmp2 = tmp;\n\t\t\tddv = new JDDVars();\n\t\t\twhile (!tmp2.equals(JDD.ONE)) {\n\t\t\t\tddv.addVar(JDD.Var(tmp2.getIndex()));\n\t\t\t\ttmp2 = tmp2.getThen();\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t\tallDDNondetVars.derefAll();\n\t\t\tallDDNondetVars = ddv;\n\t\t}\n\n\t\t// \t\t// print dd variables actually used (support of trans)\n\t\t// \t\tmainLog.print(\"\\nMTBDD variables used (\" + allDDRowVars.n() + \"r, \" + allDDRowVars.n() + \"c\");\n\t\t// \t\tif (modelType == ModelType.MDP) mainLog.print(\", \" + allDDNondetVars.n() + \"nd\");\n\t\t// \t\tmainLog.print(\"):\");\n\t\t// \t\ttmp = JDD.GetSupport(trans);\n\t\t// \t\ttmp2 = tmp;\n\t\t// \t\twhile (!tmp2.isConstant()) {\n\t\t// \t\t\t//mainLog.print(\" \" + tmp2.getIndex() + \":\" + ddVarNames.elementAt(tmp2.getIndex()));\n\t\t// \t\t\tmainLog.print(\" \" + ddVarNames.elementAt(tmp2.getIndex()));\n\t\t// \t\t\ttmp2 = tmp2.getThen();\n\t\t// \t\t}\n\t\t// \t\tmainLog.println();\n\t\t// \t\tJDD.Deref(tmp);\n\n\t\t// construct labels and init state info\n\t\tbuildLabelsAndInitialStates();\n\n\t\t// create new Model object to be returned\n\t\t// they need a module name list, so we fake that\n\t\tint numModules = 1;\n\t\tString moduleNames[] = new String[] { \"M\" };\n\t\tString rewardStructNames[] = (String[]) rewardInfo.getRewardStructNames().toArray(new String[0]);\n\n\t\tif (modelType == ModelType.DTMC) {\n\t\t\tmodel = new ProbModel(trans, start, allDDRowVars, allDDColVars, modelVariables,\n\t\t\t\t\tvarList, varDDRowVars, varDDColVars);\n\t\t} else if (modelType == ModelType.MDP) {\n\t\t\tmodel = new NondetModel(trans, start, allDDRowVars, allDDColVars, allDDNondetVars, modelVariables,\n\t\t\t\t\tvarList, varDDRowVars, varDDColVars);\n\t\t} else if (modelType == ModelType.CTMC) {\n\t\t\tmodel = new StochModel(trans, start, allDDRowVars, allDDColVars, modelVariables,\n\t\t\t\t\tvarList, varDDRowVars, varDDColVars);\n\t\t}\n\t\tmodel.setConstantValues(modelInfo.getConstantValues());\n\n\t\t// compute/set rewards\n\t\tbuildStateRewards();\n\t\tbuildTransitionRewards();\n\t\tmodel.setRewards(stateRewards, transRewards, rewardStructNames);\n\n\t\t// set action info\n\t\t// TODO: disable if not required?\n\t\tmodel.setSynchs(synchs);\n\t\tif (modelType != ModelType.MDP) {\n\t\t\t((ProbModel) model).setTransPerAction((JDDNode[]) transPerAction.toArray(new JDDNode[0]));\n\t\t} else {\n\t\t\t((NondetModel) model).setTransActions(transActions);\n\t\t}\n\n\t\t// do reachability (or not)\n\t\tif (prism.getDoReach()) {\n\t\t\tmainLog.print(\"\\nComputing reachable states...\\n\");\n\t\t\tmodel.doReachability();\n\t\t\tmodel.filterReachableStates();\n\t\t} else {\n\t\t\tmainLog.print(\"\\nSkipping reachable state computation.\\n\");\n\t\t\tmodel.skipReachability();\n\t\t\tmodel.filterReachableStates();\n\t\t}\n\n\t\t// Print some info (if extraddinfo flag on)\n\t\tif (prism.getExtraDDInfo()) {\n\t\t\tmainLog.print(\"Reach: \" + JDD.GetNumNodes(model.getReach()) + \" nodes\\n\");\n\t\t}\n\n\t\t// find any deadlocks\n\t\tmodel.findDeadlocks(prism.getFixDeadlocks());\n\n\t\t// attach labels\n\t\tattachLabels(model);\n\t\tmodel.addDeadlocks(labelDeadlock);\n\n\t\t// deref spare dds\n\t\tif (labelsDD != null) {\n\t\t\tfor (JDDNode d : labelsDD.values()) {\n\t\t\t\tJDD.Deref(d);\n\t\t\t}\n\t\t}\n\n\t\treturn model;\n\t}\n\n\t/**\n\t * allocate DD vars for system\n\t * i.e. decide on variable ordering and request variables from CUDD\n\t */\n\tprivate void allocateDDVars() throws PrismException\n\t{\n\t\tint i, j, n;\n\n\t\tmodelVariables = new ModelVariablesDD();\n\n\t\tmodelVariables.preallocateExtraActionVariables(settings.getInteger(PrismSettings.PRISM_DD_EXTRA_ACTION_VARS));\n\t\t\n\t\t// create arrays/etc. first\n\n\t\t// module variable (row/col) vars\n\t\tvarDDRowVars = new JDDVars[numVars];\n\t\tvarDDColVars = new JDDVars[numVars];\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\tvarDDRowVars[i] = new JDDVars();\n\t\t\tvarDDColVars[i] = new JDDVars();\n\t\t}\n\n\t\t// now allocate variables\n\n\t\t// allocate nondeterministic variables\n\t\tif (modelType == ModelType.MDP) {\n\t\t\tallDDNondetVars = new JDDVars();\n\t\t\tfor (i = 0; i < maxNumChoices; i++) {\n\t\t\t\tallDDNondetVars.addVar(modelVariables.allocateVariable(\"l\" + i));\n\t\t\t}\n\t\t}\n\n\t\t// allocate dd variables for module variables (i.e. rows/cols)\n\t\t// go through all vars in order (incl. global variables)\n\t\t// so overall ordering can be specified by ordering in the input file\n\t\tallDDRowVars = new JDDVars();\n\t\tallDDColVars = new JDDVars();\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\tDeclarationType declType = varList.getDeclarationType(i);\n\t\t\tif (declType.isUnbounded()) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Cannot build a model that contains a variable with unbounded range (try the explicit engine instead)\");\n\t\t\t}\n\t\t\t// get number of dd variables needed\n\t\t\t// (ceiling of log2 of range of variable)\n\t\t\tn = varList.getRangeLogTwo(i);\n\t\t\t// add pairs of variables (row/col)\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\t// new dd row variable\n\t\t\t\tvarDDRowVars[i].addVar(modelVariables.allocateVariable(varList.getName(i) + \".\" + j));\n\t\t\t\t// new dd col variable\n\t\t\t\tvarDDColVars[i].addVar(modelVariables.allocateVariable(varList.getName(i) + \"'.\" + j));\n\t\t\t}\n\t\t\tallDDRowVars.copyVarsFrom(varDDRowVars[i]);\n\t\t\tallDDColVars.copyVarsFrom(varDDColVars[i]);\n\t\t}\n\t}\n\n\t/** Construct transition matrix from file */\n\tprivate void buildTrans() throws PrismException\n\t{\n\t\t// Initial output\n\t\tmainLog.print(\"Importing transitions... \");\n\t\tprogress = new ProgressDisplay(mainLog);\n\t\tprogress.start();\n\t\tprogress.setTotalCount(importer.getNumTransitions());\n\t\ttransitionsImported = 0;\n\t\t// Initialise storage/MTBDDs\n\t\tsynchs = new Vector<String>();\n\t\ttrans = JDD.Constant(0);\n\t\tif (modelType != ModelType.MDP) {\n\t\t\ttransPerAction = new Vector<JDDNode>();\n\t\t\ttransPerAction.add(JDD.Constant(0));\n\t\t} else {\n\t\t\ttransActions = JDD.Constant(0);\n\t\t}\n\t\t// Import transitions\n\t\tif (modelType != ModelType.MDP) {\n\t\t\timporter.extractMCTransitions((s, s2, d, a) -> storeMCTransition(s, s2, d, a));\n\t\t} else {\n\t\t\timporter.extractMDPTransitions((s, i, s2, d, a) -> storeMDPTransition(s, i, s2, d, a));\n\t\t}\n\t\t// Finish progress display\n\t\tprogress.update(transitionsImported);\n\t\tprogress.end();\n\t}\n\n\t/**\n\t * Stores transRewards in the required format for mtbdd.\n\t *\n\t * @param s source state index\n\t * @param s2 target state index\n\t * @param d probability value\n\t * @param a action (optional)\n\t */\n\tprotected void storeMCTransition(int s, int s2, double d, Object a)\n\t{\n\t\t// construct element of vector mtbdd\n\t\tJDDNode elem = encodeStatePair(s, s2);\n\n\t\t// add it into mtbdds for transition matrix\n\t\tJDD.Ref(elem);\n\t\ttrans = JDD.Apply(JDD.PLUS, trans, JDD.Apply(JDD.TIMES, JDD.Constant(d), elem));\n\t\t// look up action name\n\t\tString aStr = a == null ? \"\" : a.toString();\n\t\tint j = 0;\n\t\tif (!(\"\".equals(aStr))) {\n\t\t\tj = synchs.indexOf(aStr);\n\t\t\t// add to list if first time seen\n\t\t\tif (j == -1) {\n\t\t\t\tsynchs.add(aStr);\n\t\t\t\tj = synchs.size() - 1;\n\t\t\t}\n\t\t\tj++;\n\t\t}\n\t\t// get (or create) dd for action j\n\t\tJDDNode tmp;\n\t\tif (j < transPerAction.size()) {\n\t\t\ttmp = transPerAction.get(j);\n\t\t} else {\n\t\t\ttmp = JDD.Constant(0);\n\t\t\ttransPerAction.add(tmp);\n\t\t}\n\t\t// add element to matrix\n\t\tJDD.Ref(elem);\n\t\ttmp = JDD.Apply(JDD.PLUS, tmp, JDD.Apply(JDD.TIMES, JDD.Constant(d), elem));\n\t\ttransPerAction.set(j, tmp);\n\t\t// deref element dd\n\t\tJDD.Deref(elem);\n\t\t// Print some progress info occasionally\n\t\tprogress.updateIfReady(++transitionsImported);\n\t}\n\n\t/**\n\t * Stores transRewards in the required format for mtbdd.\n\t *\n\t * @param s source state index\n\t * @param i choice index\n\t * @param s2 target state index\n\t * @param d probability value\n\t * @param a action (optional)\n\t */\n\tprotected void storeMDPTransition(int s, int i, int s2, double d, Object a)\n\t{\n\t\t// construct element of vector mtbdd\n\t\tJDDNode elem = encodeStatePair(s, s2);\n\t\telem = JDD.Apply(JDD.TIMES, elem, JDD.SetVectorElement(JDD.Constant(0), allDDNondetVars, i, 1));\n\n\t\t// add it into mtbdds for transition matrix\n\t\tJDD.Ref(elem);\n\t\ttrans = JDD.Apply(JDD.PLUS, trans, JDD.Apply(JDD.TIMES, JDD.Constant(d), elem));\n\t\t// look up action name\n\t\tString aStr = a == null ? \"\" : a.toString();\n\t\tint j = 0;\n\t\tif (!(\"\".equals(aStr))) {\n\t\t\tj = synchs.indexOf(aStr);\n\t\t\t// add to list if first time seen\n\t\t\tif (j == -1) {\n\t\t\t\tsynchs.add(aStr);\n\t\t\t\tj = synchs.size() - 1;\n\t\t\t}\n\t\t\tj++;\n\t\t}\n\t\tJDD.Ref(elem);\n\t\tJDDNode tmp = JDD.ThereExists(elem, allDDColVars);\n\t\t// use max here because we see multiple transitions for a sinlge choice\n\t\ttransActions = JDD.Apply(JDD.MAX, transActions, JDD.Apply(JDD.TIMES, JDD.Constant(j), tmp));\n\t\t// deref element dd\n\t\tJDD.Deref(elem);\n\t\t// Print some progress info occasionally\n\t\tprogress.updateIfReady(++transitionsImported);\n\t}\n\n\t/** Load info on labels and initial states from importer */\n\tprivate void buildLabelsAndInitialStates() throws PrismException\n\t{\n\t\t// Initialise BDDs\n\t\tstart = JDD.Constant(0);\n\t\tlabelDeadlock = JDD.Constant(0);\n\t\tint numLabels = modelInfo.getNumLabels();\n\t\tJDDNode[] labelDDs = new JDDNode[numLabels];\n\t\tfor (int l = 0; l < numLabels; l++) {\n\t\t\tlabelDDs[l] = JDD.Constant(0);\n\t\t}\n\t\t// Extract info\n\t\timporter.extractLabelsAndInitialStates((s, l) -> {\n\t\t\tlabelDDs[l] = JDD.Or(labelDDs[l], encodeState(s));\n\t\t}, s -> {\n\t\t\tstart = JDD.Or(start, encodeState(s));\n\t\t}, s -> {\n\t\t\tlabelDeadlock = JDD.Or(labelDeadlock, encodeState(s));\n\t\t});\n\t\tif (start == null || start.equals(JDD.ZERO)) {\n\t\t\tthrow new PrismException(\"No initial states found\");\n\t\t}\n\t\t// Store label map\n\t\tlabelsDD = new LinkedHashMap<>();\n\t\tfor (int l = 0; l < numLabels; l++) {\n\t\t\tlabelsDD.put(modelInfo.getLabelName(l), labelDDs[l]);\n\t\t}\n\t}\n\n\t/** Attach the computed label information to the model */\n\tprivate void attachLabels(ModelSymbolic model)\n\t{\n\t\tif (labelsDD == null) {\n\t\t\treturn;\n\t\t}\n\t\tfor (Entry<String, JDDNode> e : labelsDD.entrySet()) {\n\t\t\tmodel.addLabelDD(e.getKey(), e.getValue().copy());\n\t\t}\n\t}\n\n\t/**\n\t * Load state rewards from the ExplicitFilesRewardGenerator.\n\t */\n\tprivate void buildStateRewards() throws PrismException\n\t{\n\t\tint numRewardStructs = rewardInfo.getNumRewardStructs();\n\t\tstateRewards = new JDDNode[numRewardStructs];\n\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\tstateRewards[r] = JDD.Constant(0);\n\t\t\tint finalR = r;\n\t\t\timporter.extractStateRewards(r, (i, d) -> storeStateReward(finalR, i, d));\n\t\t}\n\t}\n\n\t/**\n\t * Load transition rewards from the ExplicitFilesRewardGenerator.\n\t */\n\tprivate void buildTransitionRewards() throws PrismException\n\t{\n\t\tint numRewardStructs = rewardInfo.getNumRewardStructs();\n\t\ttransRewards = new JDDNode[numRewardStructs];\n\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\ttransRewards[r] = JDD.Constant(0);\n\t\t\tint finalR = r;\n\t\t\tif (!modelType.nondeterministic()) {\n\t\t\t\timporter.extractMCTransitionRewards(r, (s, s2, d) -> storeMCTransitionReward(finalR, s, s2, d), Evaluator.forDouble());\n\t\t\t} else {\n\t\t\t\timporter.extractMDPTransitionRewards(r, (s, i, d) -> storeMDPTransitionReward(finalR, s, i, d));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Stores stateRewards in the required format for mtbdd.\n\t *\n\t * @param rewardStructIndex reward structure index\n\t * @param s state index\n\t * @param d reward value\n\t */\n\tprotected void storeStateReward(int rewardStructIndex, int s, double d)\n\t{\n\t\t// Construct element of vector MTBDD\n\t\tJDDNode tmp = encodeState(s);\n\t\t// Add it into MTBDD for state rewards\n\t\tstateRewards[rewardStructIndex] = JDD.Plus(stateRewards[rewardStructIndex], JDD.Times(JDD.Constant(d), tmp));\n\t}\n\n\t/**\n\t * Stores transRewards in the required format for mtbdd.\n\t *\n\t * @param rewardStructIndex reward structure index\n\t * @param s source state index\n\t * @param s2 target state index\n\t * @param d reward value\n\t */\n\tprotected void storeMCTransitionReward(int rewardStructIndex, int s, int s2, double d)\n\t{\n\t\t// Construct element of matrix MTBDD\n\t\tJDDNode tmp = encodeStatePair(s, s2);\n\t\t// Add it into MTBDD for state rewards\n\t\ttransRewards[rewardStructIndex] = JDD.Plus(transRewards[rewardStructIndex], JDD.Times(JDD.Constant(d), tmp));\n\t}\n\n\t/**\n\t * Stores transRewards in the required format for mtbdd.\n\t *\n\t * @param rewardStructIndex reward structure index\n\t * @param s source state index\n\t * @param i choice index\n\t * @param d reward value\n\t */\n\tprotected void storeMDPTransitionReward(int rewardStructIndex, int s, int i, double d)\n\t{\n\t\t// Construct element of matrix MTBDD\n\t\tJDDNode tmp = encodeState(s);\n\t\ttmp = JDD.Apply(JDD.TIMES, tmp, JDD.SetVectorElement(JDD.Constant(0), allDDNondetVars, i, 1));\n\t\ttmp = JDD.And(tmp, model.getTrans01().copy());\n\t\t// Add it into MTBDD for transition rewards\n\t\ttransRewards[rewardStructIndex] = JDD.Plus(transRewards[rewardStructIndex], JDD.Times(JDD.Constant(d), tmp));\n\t}\n\n\t/**\n\t * Stores transRewards in the required format for mtbdd.\n\t *\n\t * @param rewardStructIndex reward structure index\n\t * @param s source state index\n\t * @param i choice index\n\t * @param s2 target state index\n\t * @param d reward value\n\t */\n\tprotected void storeMDPTransitionReward(int rewardStructIndex, int s, int i, int s2, double d)\n\t{\n\t\t// Construct element of matrix MTBDD\n\t\tJDDNode tmp = encodeStatePair(s, s2);\n\t\ttmp = JDD.Apply(JDD.TIMES, tmp, JDD.SetVectorElement(JDD.Constant(0), allDDNondetVars, i, 1));\n\t\t// Add it into MTBDD for transition rewards\n\t\ttransRewards[rewardStructIndex] = JDD.Plus(transRewards[rewardStructIndex], JDD.Times(JDD.Constant(d), tmp));\n\t}\n\n\t/**\n\t * Encode a state index into BDD vars (referencing the result).\n\t * @param s state index\n\t */\n\tprivate JDDNode encodeState(int s)\n\t{\n\t\tJDDNode res;\n\t\t// Case where there is no state list...\n\t\tif (statesArray == null) {\n\t\t\tres = JDD.SetVectorElement(JDD.Constant(0), varDDRowVars[0], s, 1.0);\n\t\t}\n\t\t// Case where there is a state list...\n\t\telse {\n\t\t\tres = JDD.Constant(1);\n\t\t\tfor (int j = 0; j < numVars; j++) {\n\t\t\t\tres = JDD.Times(res, JDD.SetVectorElement(JDD.Constant(0), varDDRowVars[j], statesArray[s][j], 1));\n\t\t\t}\n\t\t}\n\t\treturn res;\n\t}\n\n\t/**\n\t * Encode a state index pair into BDD vars (referencing the result).\n\t * @param s source state index\n\t * @param s2 target state index\n\t */\n\tprivate JDDNode encodeStatePair(int s, int s2)\n\t{\n\t\t// Note: could do this with a conjunction of BDDs from two\n\t\t// calls to encodeState but this way should be more efficient\n\n\t\tJDDNode res;\n\t\t// Case where there is no state list...\n\t\tif (statesArray == null) {\n\t\t\tres = JDD.SetMatrixElement(JDD.Constant(0), varDDRowVars[0], varDDColVars[0], s, s2, 1.0);\n\t\t}\n\t\t// Case where there is a state list...\n\t\telse {\n\t\t\tres = JDD.Constant(1);\n\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\tres = JDD.Apply(JDD.TIMES, res, JDD.SetVectorElement(JDD.Constant(0), varDDRowVars[i], statesArray[s][i], 1.0));\n\t\t\t\tres = JDD.Apply(JDD.TIMES, res, JDD.SetVectorElement(JDD.Constant(0), varDDColVars[i], statesArray[s2][i], 1.0));\n\t\t\t}\n\t\t}\n\t\treturn res;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/build/ExplicitModel2MTBDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.build;\n\nimport java.util.*;\n\nimport jdd.*;\nimport parser.*;\nimport parser.ast.*;\nimport explicit.*;\nimport prism.*;\nimport symbolic.model.ModelVariablesDD;\nimport symbolic.model.ProbModel;\nimport symbolic.model.StochModel;\n\n/**\n * Class to convert explicit-state representation of a model to a symbolic one.\n */\npublic class ExplicitModel2MTBDD extends PrismNativeComponent\n{\n\t// Explicit-state model\n\tprivate explicit.Model<Double> modelExpl;\n\n\t// ModulesFile object, essentially just to store variable info\n\tprivate ModulesFile modulesFile;\n\n\t// model info\n\n\t// type\n\tprivate ModelType modelType; // model type (dtmc/mdp/ctmc.)\n\t// vars info\n\tprivate int numVars; // total number of variables\n\tprivate VarList varList; // VarList object to store all var info \n\t// explicit storage of states\n\tprivate int numStates = 0;\n\tprivate List<State> statesList = null;\n\n\t// mtbdd stuff\n\n\t// dds/dd vars - whole system\n\tprivate JDDNode trans; // transition matrix dd\n\tprivate JDDNode start; // dd for start state\n\tprivate JDDNode stateRewards; // dd of state rewards\n\tprivate JDDNode transRewards; // dd of transition rewards\n\tprivate JDDVars allDDRowVars; // all dd vars (rows)\n\tprivate JDDVars allDDColVars; // all dd vars (cols)\n\tprivate JDDVars allDDNondetVars; // all dd vars (all non-det.)\n\t// dds/dd vars - variables\n\tprivate JDDVars[] varDDRowVars; // dd vars (row/col) for each module variable\n\tprivate JDDVars[] varDDColVars;\n\n\tprivate ModelVariablesDD modelVariables;\n\t\n\t// action info\n\tprivate Vector<String> synchs; // list of action names\n\tprivate JDDNode transActions; // dd for transition action labels (MDPs)\n\tprivate Vector<JDDNode> transPerAction; // dds for transition action labels (D/CTMCs)\n\t// max num choices (MDP only)\n\tprivate int maxNumChoices = 0;\n\n\t// constructor\n\n\tpublic ExplicitModel2MTBDD(Prism prism) throws PrismException\n\t{\n\t\tsuper(prism);\n\t}\n\n\t// Build model\n\n\t/**\n\t * Construct a symbolic model from an explicit state one.  \n\t * If provided, {@code statesList} is used to encode states using model variables,\n\t * in which case a corresponding {@code ModulesFile} must be provided for variable\n\t * details (and e.g. module names). If both are null, a single variable x is assumed. \n\t */\n\tpublic symbolic.model.Model buildModel(explicit.Model<Double> modelExpl, List<State> statesList, ModulesFile modulesFile, boolean doReach) throws PrismException\n\t{\n\t\tsymbolic.model.ModelSymbolic model = null;\n\t\tJDDNode tmp, tmp2;\n\t\tJDDVars ddv;\n\t\tint i;\n\n\t\t// Store model/type/states\n\t\tthis.modelExpl = modelExpl;\n\t\tthis.modelType = modelExpl.getModelType();\n\t\tthis.numStates = modelExpl.getNumStates();\n\t\tthis.statesList = statesList;\n\n\t\t// Store modules files or create dummy one if needed\n\t\tif (statesList != null) {\n\t\t\tthis.modulesFile = modulesFile;\n\t\t} else {\n\t\t\tthis.modulesFile = modulesFile = new ModulesFile();\n\t\t\tparser.ast.Module m = new parser.ast.Module(\"M\");\n\t\t\tDeclaration d = new Declaration(\"x\", new DeclarationInt(Expression.Int(0), Expression.Int(numStates - 1)));\n\t\t\td.setStart(Expression.Int(0));\n\t\t\tm.addDeclaration(d);\n\t\t\tmodulesFile.addModule(m);\n\t\t\tmodulesFile.tidyUp();\n\t\t}\n\n\t\t// Get variable info from ModulesFile\n\t\tvarList = modulesFile.createVarList();\n\t\tnumVars = varList.getNumVars();\n\n\t\t// For an mdp, compute the max number of choices in a state\n\t\tif (modelType == ModelType.MDP)\n\t\t\tmaxNumChoices = ((MDPSimple) modelExpl).getMaxNumChoices();\n\n\t\t// Allocate dd variables\n\t\tallocateDDVars();\n\n\t\t// Construct transition matrix from file\n\t\tbuildTrans(modelExpl);\n\n\t\t// Get rid of any nondet dd variables not needed\n\t\tif (modelType == ModelType.MDP) {\n\t\t\ttmp = JDD.GetSupport(trans);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDRowVars);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDColVars);\n\t\t\ttmp2 = tmp;\n\t\t\tddv = new JDDVars();\n\t\t\twhile (!tmp2.equals(JDD.ONE)) {\n\t\t\t\tddv.addVar(JDD.Var(tmp2.getIndex()));\n\t\t\t\ttmp2 = tmp2.getThen();\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t\tallDDNondetVars.derefAll();\n\t\t\tallDDNondetVars = ddv;\n\t\t}\n\n\t\t// Calculate BDD for initial state\n\t\tbuildInit();\n\n\t\t// Compute state rewards\n\t\tcomputeStateRewards();\n\n\t\tint numModules = 1; // just one module\n\t\tString moduleNames[] = modulesFile.getModuleNames(); // whose name is stored here\n\t\tValues constantValues = new Values(); // no constants\n\n\t\t/*JDDNode stateRewardsArray[] = new JDDNode[1];\n\t\tstateRewardsArray[0] = stateRewards;\n\t\tJDDNode transRewardsArray[] = new JDDNode[1];\n\t\ttransRewardsArray[0] = transRewards;\n\t\tString rewardStructNames[] = new String[1];\n\t\trewardStructNames[0] = \"\";*/\n\t\tJDDNode stateRewardsArray[] = new JDDNode[0];\n\t\tJDDNode transRewardsArray[] = new JDDNode[0];\n\t\tString rewardStructNames[] = new String[0];\n\n\t\t// Create new Model object to be returned\n\t\tif (modelType == ModelType.DTMC) {\n\t\t\tmodel = new ProbModel(trans, start, allDDRowVars, allDDColVars, modelVariables,\n\t\t\t\t\tvarList, varDDRowVars, varDDColVars);\n\t\t} else if (modelType == ModelType.MDP) {\n\t\t\tmodel = new symbolic.model.NondetModel(trans, start, allDDRowVars, allDDColVars,\n\t\t\t\t\tallDDNondetVars, modelVariables, varList,\n\t\t\t\t\tvarDDRowVars, varDDColVars);\n\t\t} else if (modelType == ModelType.CTMC) {\n\t\t\tmodel = new StochModel(trans, start, allDDRowVars, allDDColVars, modelVariables,\n\t\t\t\t\tvarList, varDDRowVars, varDDColVars);\n\t\t}\n\t\tmodel.setRewards(stateRewardsArray, transRewardsArray, rewardStructNames);\n\t\tmodel.setConstantValues(constantValues);\n\t\t// Set action info\n\t\t// TODO: disable if not required?\n\t\tmodel.setSynchs(synchs);\n\t\tif (modelType != ModelType.MDP) {\n\t\t\t((ProbModel) model).setTransPerAction((JDDNode[]) transPerAction.toArray(new JDDNode[0]));\n\t\t} else {\n\t\t\t((symbolic.model.NondetModel) model).setTransActions(transActions);\n\t\t}\n\n\t\t// Do reachability (if required)\n\t\tif (doReach) {\n\t\t\tmainLog.print(\"\\nComputing reachable states...\\n\");\n\t\t\tmodel.doReachability();\n\t\t\tmodel.filterReachableStates();\n\t\t} else {\n\t\t\t// If not, assume any non-empty row/column is a reachable state\n\t\t\tJDD.Ref(trans);\n\t\t\ttmp = JDD.GreaterThan(trans, 0);\n\t\t\tif (modelType == ModelType.MDP)\n\t\t\t\ttmp = JDD.ThereExists(tmp, allDDNondetVars);\n\t\t\tJDD.Ref(tmp);\n\t\t\ttmp2 = JDD.ThereExists(tmp, allDDRowVars);\n\t\t\ttmp2 = JDD.SwapVariables(tmp2, allDDColVars, allDDRowVars);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDColVars);\n\t\t\ttmp = JDD.Or(tmp, tmp2);\n\t\t\tmodel.setReach(tmp);\n\t\t\tmodel.filterReachableStates();\n\t\t}\n\n\t\t// Print some info (if extraddinfo flag on)\n\t\tif (prism.getExtraDDInfo()) {\n\t\t\tmainLog.print(\"Reach: \" + JDD.GetNumNodes(model.getReach()) + \" nodes\\n\");\n\t\t}\n\n\t\t// Find any deadlocks\n\t\tmodel.findDeadlocks(prism.getFixDeadlocks());\n\n\t\treturn model;\n\t}\n\n\t// allocate DD vars for system\n\t// i.e. decide on variable ordering and request variables from CUDD\n\n\tprivate void allocateDDVars()\n\t{\n\t\tint i, j, n;\n\n\t\tmodelVariables = new ModelVariablesDD();\n\n\t\tmodelVariables.preallocateExtraActionVariables(settings.getInteger(PrismSettings.PRISM_DD_EXTRA_ACTION_VARS));\n\n\t\t// create arrays/etc. first\n\n\t\t// module variable (row/col) vars\n\t\tvarDDRowVars = new JDDVars[numVars];\n\t\tvarDDColVars = new JDDVars[numVars];\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\tvarDDRowVars[i] = new JDDVars();\n\t\t\tvarDDColVars[i] = new JDDVars();\n\t\t}\n\n\t\t// now allocate variables\n\n\t\t// allocate nondeterministic variables\n\t\tif (modelType == ModelType.MDP) {\n\t\t\tallDDNondetVars = new JDDVars();\n\t\t\tfor (i = 0; i < maxNumChoices; i++) {\n\t\t\t\tallDDNondetVars.addVar(modelVariables.allocateVariable(\"l\" + i));\n\t\t\t}\n\t\t}\n\n\t\t// allocate dd variables for module variables (i.e. rows/cols)\n\t\t// go through all vars in order (incl. global variables)\n\t\t// so overall ordering can be specified by ordering in the input file\n\t\tallDDRowVars = new JDDVars();\n\t\tallDDColVars = new JDDVars();\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t// get number of dd variables needed\n\t\t\t// (ceiling of log2 of range of variable)\n\t\t\tn = varList.getRangeLogTwo(i);\n\t\t\t// add pairs of variables (row/col)\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\t// new dd row variable\n\t\t\t\tvarDDRowVars[i].addVar(modelVariables.allocateVariable(varList.getName(i) + \".\" + j));\n\t\t\t\t// new dd col variable\n\t\t\t\tvarDDColVars[i].addVar(modelVariables.allocateVariable(varList.getName(i) + \"'.\" + j));\n\t\t\t}\n\t\t\tallDDRowVars.copyVarsFrom(varDDRowVars[i]);\n\t\t\tallDDColVars.copyVarsFrom(varDDColVars[i]);\n\t\t}\n\t}\n\n\t/**\n\t * Construct (symbolic) transition matrix from explicit-state model. \n\t */\n\tprivate void buildTrans(explicit.Model<Double> modelExpl) throws PrismException\n\t{\n\t\tString a;\n\t\tint j, r, c, k = 0;\n\t\tint nnz, count;\n\t\tdouble d;\n\t\tJDDNode elem, tmp;\n\t\tProgressDisplay progress;\n\n\t\tmainLog.print(\"Converting to MTBDD: \");\n\n\t\t// Initialise action list\n\t\tsynchs = new Vector<String>();\n\t\t// Initialise mtbdds\n\t\ttrans = JDD.Constant(0);\n\t\ttransRewards = JDD.Constant(0);\n\t\tif (modelType != ModelType.MDP) {\n\t\t\ttransPerAction = new Vector<JDDNode>();\n\t\t\ttransPerAction.add(JDD.Constant(0));\n\t\t} else {\n\t\t\ttransActions = JDD.Constant(0);\n\t\t}\n\t\t// Initialise transition counter/progress display\n\t\tnnz = modelExpl.getNumTransitions();\n\t\tcount = 0;\n\t\tprogress = new ProgressDisplay(mainLog);\n\t\tprogress.setTotalCount(nnz);\n\t\tprogress.start();\n\t\t// Case for DTMCs/CTMCs...\n\t\tif (modelType == ModelType.DTMC || modelType == ModelType.CTMC) {\n\t\t\tDTMC<Double> dtmc = (DTMC<Double>) modelExpl;\n\t\t\tfor (r = 0; r < numStates; r++) {\n\t\t\t\tIterator<Map.Entry<Integer, Double>> iter = dtmc.getTransitionsIterator(r);\n\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\tMap.Entry<Integer, Double> e = iter.next();\n\t\t\t\t\tc = (Integer) e.getKey();\n\t\t\t\t\td = (Double) e.getValue();\n\t\t\t\t\ta = \"\";\n\t\t\t\t\t// construct element of matrix mtbdd\n\t\t\t\t\telem = encodeStatePair(r, c);\n\t\t\t\t\t// add it into mtbdds for transition matrix and transition rewards\n\t\t\t\t\tJDD.Ref(elem);\n\t\t\t\t\ttrans = JDD.Apply(JDD.PLUS, trans, JDD.Apply(JDD.TIMES, JDD.Constant(d), elem));\n\t\t\t\t\t// look up action name\n\t\t\t\t\tif (!(\"\".equals(a))) {\n\t\t\t\t\t\tj = synchs.indexOf(a);\n\t\t\t\t\t\t// add to list if first time seen \n\t\t\t\t\t\tif (j == -1) {\n\t\t\t\t\t\t\tsynchs.add(a);\n\t\t\t\t\t\t\tj = synchs.size() - 1;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tj++;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tj = 0;\n\t\t\t\t\t}\n\t\t\t\t\t// get (or create) dd for action j\n\t\t\t\t\tif (j < transPerAction.size()) {\n\t\t\t\t\t\ttmp = transPerAction.get(j);\n\t\t\t\t\t} else {\n\t\t\t\t\t\ttmp = JDD.Constant(0);\n\t\t\t\t\t\ttransPerAction.add(tmp);\n\t\t\t\t\t}\n\t\t\t\t\t// add element to matrix\n\t\t\t\t\tJDD.Ref(elem);\n\t\t\t\t\ttmp = JDD.Apply(JDD.PLUS, tmp, JDD.Apply(JDD.TIMES, JDD.Constant(d), elem));\n\t\t\t\t\ttransPerAction.set(j, tmp);\n\t\t\t\t\t// deref element dd\n\t\t\t\t\tJDD.Deref(elem);\n\t\t\t\t\t// Print some progress info occasionally\n\t\t\t\t\tprogress.updateIfReady(++count);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t// Case for MDPs...\n\t\telse if (modelType == ModelType.MDP) {\n\t\t\tMDP<Double> mdp = (MDP<Double>) modelExpl;\n\t\t\tfor (r = 0; r < numStates; r++) {\n\t\t\t\tint nc = mdp.getNumChoices(r);\n\t\t\t\tfor (k = 0; k < nc; k++) {\n\t\t\t\t\tIterator<Map.Entry<Integer, Double>> iter = mdp.getTransitionsIterator(r, k);\n\t\t\t\t\twhile (iter.hasNext()) {\n\t\t\t\t\t\tMap.Entry<Integer, Double> e = iter.next();\n\t\t\t\t\t\tc = (Integer) e.getKey();\n\t\t\t\t\t\td = (Double) e.getValue();\n\t\t\t\t\t\ta = \"\";\n\t\t\t\t\t\t// construct element of matrix mtbdd\n\t\t\t\t\t\telem = JDD.SetVectorElement(JDD.Constant(0), allDDNondetVars, k, 1.0);\n\t\t\t\t\t\telem = JDD.Apply(JDD.TIMES, elem, encodeStatePair(r, c));\n\t\t\t\t\t\t// add it into mtbdds for transition matrix and transition rewards\n\t\t\t\t\t\tJDD.Ref(elem);\n\t\t\t\t\t\ttrans = JDD.Apply(JDD.PLUS, trans, JDD.Apply(JDD.TIMES, JDD.Constant(d), elem));\n\t\t\t\t\t\t// look up action name\n\t\t\t\t\t\tif (!(\"\".equals(a))) {\n\t\t\t\t\t\t\tj = synchs.indexOf(a);\n\t\t\t\t\t\t\t// add to list if first time seen \n\t\t\t\t\t\t\tif (j == -1) {\n\t\t\t\t\t\t\t\tsynchs.add(a);\n\t\t\t\t\t\t\t\tj = synchs.size() - 1;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tj++;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tj = 0;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tJDD.Ref(elem);\n\t\t\t\t\t\ttmp = JDD.ThereExists(elem, allDDColVars);\n\t\t\t\t\t\t// use max here because we see multiple transitions for a single choice\n\t\t\t\t\t\ttransActions = JDD.Apply(JDD.MAX, transActions, JDD.Apply(JDD.TIMES, JDD.Constant(j), tmp));\n\t\t\t\t\t\t// deref element dd\n\t\t\t\t\t\tJDD.Deref(elem);\n\t\t\t\t\t\t// Print some progress info occasionally\n\t\t\t\t\t\tprogress.updateIfReady(++count);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\tthrow new PrismException(\"Unknown model type\");\n\t\t}\n\t\t// Tidy up progress display\n\t\tprogress.update(nnz);\n\t\tprogress.end();\n\t}\n\n\t// Build BDD for initial state(s)\n\n\tprivate void buildInit() throws PrismException\n\t{\n\t\tstart = JDD.Constant(0);\n\t\tfor (int r : modelExpl.getInitialStates()) {\n\t\t\tstart = JDD.Or(start, encodeState(r));\n\t\t}\n\t}\n\n\t// read info about state rewards from states file\n\n\tpublic void computeStateRewards() throws PrismException\n\t{\n\t\t/*BufferedReader in;\n\t\tString s, ss[];\n\t\tint i, j, lineNum = 0;\n\t\tdouble d;\n\t\tJDDNode tmp;\n\n\t\t// initialise mtbdd\n\t\tstateRewards = JDD.Constant(0);\n\n\t\tif (statesFile == null)\n\t\t\treturn;\n\n\t\ttry {\n\t\t\t// open file for reading\n\t\t\tin = new BufferedReader(new FileReader(statesFile));\n\t\t\t// skip first line\n\t\t\tin.readLine();\n\t\t\tlineNum = 1;\n\t\t\t// read remaining lines\n\t\t\ts = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\t// skip blank lines\n\t\t\t\ts = s.trim();\n\t\t\t\tif (s.length() > 0) {\n\t\t\t\t\t// split into two/three parts\n\t\t\t\t\tss = s.split(\":\");\n\t\t\t\t\t// determine which state this line describes\n\t\t\t\t\ti = Integer.parseInt(ss[0]);\n\t\t\t\t\t// if there is a state reward...\n\t\t\t\t\tss = ss[1].split(\"=\");\n\t\t\t\t\tif (ss.length == 2) {\n\t\t\t\t\t\t// determine value\n\t\t\t\t\t\td = Double.parseDouble(ss[1]);\n\t\t\t\t\t\t// construct element of vector mtbdd\n\t\t\t\t\t\ttmp = encodeState(i);\n\t\t\t\t\t\t// add it into mtbdd for state rewards\n\t\t\t\t\t\tstateRewards = JDD.Apply(JDD.PLUS, stateRewards, JDD.Apply(JDD.TIMES, JDD.Constant(d), tmp));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// read next line\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t\t// close file\n\t\t\tin.close();\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + statesFile + \"\\\"\");\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error detected at line \" + lineNum + \" of states file \\\"\" + statesFile + \"\\\"\");\n\t\t}*/\n\t}\n\n\t/**\n\t * Encode a state index into BDD vars (referencing the result).\n\t * @param s State index\n\t */\n\tprivate JDDNode encodeState(int s)\n\t{\n\t\tJDDNode res;\n\t\tint i, j = 0;\n\t\t// Case where there is no state list...\n\t\tif (statesList == null) {\n\t\t\tres = JDD.SetVectorElement(JDD.Constant(0), varDDRowVars[0], s, 1.0);\n\t\t}\n\t\t// Case where there is a state list...\n\t\telse {\n\t\t\tres = JDD.Constant(1);\n\t\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t\ttry {\n\t\t\t\t\tj = varList.encodeToInt(i, statesList.get(s).varValues[i]);\n\t\t\t\t} catch (PrismLangException e) {\n\t\t\t\t\t// Won't happen\n\t\t\t\t}\n\t\t\t\tres = JDD.Apply(JDD.TIMES, res, JDD.SetVectorElement(JDD.Constant(0), varDDRowVars[i], j, 1.0));\n\t\t\t}\n\t\t}\n\t\treturn res;\n\t}\n\n\t/**\n\t * Encode a state index pair into BDD vars (referencing the result).\n\t * @param r State row index\n\t * @param c State column index\n\t */\n\tprivate JDDNode encodeStatePair(int r, int c)\n\t{\n\t\tJDDNode res;\n\t\tint i, j = 0, k = 0;\n\n\t\t// Note: could do this with a conjunction of BDDs from two\n\t\t// calls to encodeState but this way should be more efficient \n\n\t\t// Case where there is no state list...\n\t\tif (statesList == null) {\n\t\t\tres = JDD.SetMatrixElement(JDD.Constant(0), varDDRowVars[0], varDDColVars[0], r, c, 1.0);\n\t\t}\n\t\t// Case where there is a state list...\n\t\telse {\n\t\t\tres = JDD.Constant(1);\n\t\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t\ttry {\n\t\t\t\t\tj = varList.encodeToInt(i, statesList.get(r).varValues[i]);\n\t\t\t\t\tk = varList.encodeToInt(i, statesList.get(c).varValues[i]);\n\t\t\t\t} catch (PrismLangException e) {\n\t\t\t\t\t// Won't happen\n\t\t\t\t}\n\t\t\t\tres = JDD.Apply(JDD.TIMES, res, JDD.SetVectorElement(JDD.Constant(0), varDDRowVars[i], j, 1.0));\n\t\t\t\tres = JDD.Apply(JDD.TIMES, res, JDD.SetVectorElement(JDD.Constant(0), varDDColVars[i], k, 1.0));\n\t\t\t}\n\t\t}\n\t\treturn res;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/build/MTBDD2ExplicitModel.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2025-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage symbolic.build;\n\nimport common.SafeCast;\nimport explicit.CTMCSimple;\nimport explicit.DTMC;\nimport explicit.DTMCSimple;\nimport explicit.Distribution;\nimport explicit.MDP;\nimport explicit.MDPSimple;\nimport explicit.ModelExplicit;\nimport explicit.SuccessorsIterator;\nimport explicit.rewards.Rewards;\nimport explicit.rewards.Rewards2RewardGenerator;\nimport explicit.rewards.RewardsExplicit;\nimport explicit.rewards.RewardsSimple;\nimport io.IOUtils;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport odd.ODDNode;\nimport prism.Evaluator;\nimport prism.Pair;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.RewardGenerator;\nimport prism.RewardInfo;\nimport symbolic.model.NondetModel;\nimport symbolic.model.ProbModel;\nimport symbolic.states.StateListMTBDD;\n\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.function.IntConsumer;\n\n/**\n * Class to convert symbolic representations of models to explicit-state ones.\n */\npublic class MTBDD2ExplicitModel extends PrismComponent\n{\n\tpublic MTBDD2ExplicitModel()\n\t{\n\t\tsuper();\n\t}\n\n\tpublic MTBDD2ExplicitModel(PrismComponent parent)\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Convert a symbolically stored model to an explicit-state one.\n\t * @param modelSymb The symbolic model\n\t */\n\tpublic explicit.Model<Double> convertModel(symbolic.model.Model modelSymb) throws PrismException\n\t{\n\t\tModelExplicit<Double> modelExpl;\n\t\tDTMCSimple<Double> dtmcExpl;\n\t\tCTMCSimple<Double> ctmcExpl;\n\t\tMDPSimple<Double> mdpExpl;\n\t\tint numStates = modelSymb.getNumStates();\n\t\t// Build new model and convert/add transitions\n\t\tswitch (modelSymb.getModelType()) {\n\t\t\tcase DTMC:\n\t\t\t\tmodelExpl = dtmcExpl = new DTMCSimple<>(numStates);\n\t\t\t\tmodelExpl.setActions(modelSymb.getActions());\n\t\t\t\tconvertMarkovChainTransitions((ProbModel) modelSymb, dtmcExpl);\n\t\t\t\tbreak;\n\t\t\tcase CTMC:\n\t\t\t\tmodelExpl = ctmcExpl = new CTMCSimple<>(numStates);\n\t\t\t\tmodelExpl.setActions(modelSymb.getActions());\n\t\t\t\tconvertMarkovChainTransitions((ProbModel) modelSymb, ctmcExpl);\n\t\t\t\tbreak;\n\t\t\tcase MDP:\n\t\t\t\tmodelExpl = mdpExpl = new MDPSimple<>(numStates);\n\t\t\t\tmodelExpl.setActions(modelSymb.getActions());\n\t\t\t\tconvertMDPTransitions((NondetModel) modelSymb, mdpExpl);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Can't do symbolic-explicit conversion for \" + modelSymb.getModelType() + \"s\");\n\t\t}\n\t\t// Convert/add initial states\n\t\ttraverseStatesBDD(modelSymb.getStart(), modelSymb.getAllDDRowVars(), modelSymb.getODD(), modelExpl::addInitialState);\n\t\t// If the symbolic model has labels attached, convert/add them\n\t\tfor (String label : modelSymb.getLabels()) {\n\t\t\tBitSet labelStates = new BitSet();\n\t\t\ttraverseStatesBDD(modelSymb.getLabelDD(label), modelSymb.getAllDDRowVars(), modelSymb.getODD(), labelStates::set);\n\t\t\tmodelExpl.addLabel(label, labelStates);\n\t\t}\n\t\t// If the symbolic model has deadlock info attached, convert/add it\n\t\tif (modelSymb.getDeadlocks() != null) {\n\t\t\tBitSet deadlockStates = new BitSet();\n\t\t\ttraverseStatesBDD(modelSymb.getDeadlocks(), modelSymb.getAllDDRowVars(), modelSymb.getODD(), deadlockStates::set);\n\t\t\tfor (int s = deadlockStates.nextSetBit(0); s >= 0; s = deadlockStates.nextSetBit(s + 1)) {\n\t\t\t\tmodelExpl.addDeadlockState(s);\n\t\t\t}\n\t\t}\n\t\t// Convert/add state information\n\t\tmodelExpl.setStatesList(((StateListMTBDD) modelSymb.getReachableStates()).getAsListOfStates());\n\t\treturn modelExpl;\n\t}\n\n\t/**\n\t * Get a {@link RewardGenerator}, which converts the rewards for a\n\t * symbolically stored model to explicit-state reward storage.\n\t * @param modelSymb The symbolic model\n\t * @param modelExpl The corresponding explicit-state model\n\t * @param rewardInfo Reward info\n\t */\n\tpublic RewardGenerator<Double> getRewardConverter(symbolic.model.Model modelSymb, explicit.Model<Double> modelExpl, RewardInfo rewardInfo) throws PrismException\n\t{\n\t\treturn new Rewards2RewardGenerator<>(rewardInfo, modelExpl, Evaluator.forDouble())\n\t\t{\n\t\t\t@Override\n\t\t\tpublic Rewards<Double> getTheRewardObject(int r) throws PrismException\n\t\t\t{\n\t\t\t\treturn convertRewards(modelSymb, modelExpl, r, rewardInfo);\n\t\t\t}\n\t\t};\n\t}\n\n\t/**\n\t * Converts the rewards for a symbolically stored model to explicit-state reward storage.\n\t * @param modelSymb The symbolic model\n\t * @param modelExpl The corresponding explicit-state model\n\t * @param r The index of the reward structure\n\t * @param rewardInfo Reward info\n\t */\n\tpublic explicit.rewards.Rewards<Double> convertRewards(symbolic.model.Model modelSymb, explicit.Model<Double> modelExpl, int r, RewardInfo rewardInfo) throws PrismException\n\t{\n\t\t// Construct new Rewards object\n\t\tRewardsSimple<Double> rewards = new RewardsSimple<>(modelSymb.getNumStates());\n\t\t// Extract state rewards (if present)\n\t\tif (rewardInfo.rewardStructHasStateRewards(r)) {\n\t\t\tJDDNode stateRewards = modelSymb.getStateRewards(r);\n\t\t\ttraverseVectorDD(stateRewards, modelSymb.getAllDDRowVars(), modelSymb.getODD(), rewards::addToStateReward);\n\t\t}\n\t\t// Extract transition rewards (if present)\n\t\tif (rewardInfo.rewardStructHasTransitionRewards(r)) {\n\t\t\tJDDNode transRewards = modelSymb.getTransRewards(r);\n\t\t\tswitch (modelSymb.getModelType()) {\n\t\t\t\tcase DTMC:\n\t\t\t\tcase CTMC:\n\t\t\t\t\tconvertMarkovChainTransitionRewards((ProbModel) modelSymb, (DTMC<Double>) modelExpl, transRewards, rewards);\n\t\t\t\t\tbreak;\n\t\t\t\tcase MDP:\n\t\t\t\t\tconvertMDPTransitionRewards((NondetModel) modelSymb, (MDP<Double>) modelExpl, transRewards, rewards);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Can't do symbolic-explicit reward conversion for \" + modelSymb.getModelType() + \"s\");\n\t\t\t}\n\t\t}\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Convert the transitions and actions for a symbolically represented Markov chain\n\t * @param mcSymb The symbolic Markov chain\n\t * @param mcExpl The explicit-state Markov chain to add to\n\t */\n\tprivate void convertMarkovChainTransitions(symbolic.model.ProbModel mcSymb, DTMCSimple<Double> mcExpl) throws PrismException\n\t{\n\t\t// Get action info\n\t\tList<Object> actions = mcSymb.getActions();\n\t\tJDDNode[] transPerAction = mcSymb.getTransPerAction();\n\t\t// If action info is stored, extract each DD separately\n\t\tif (transPerAction != null) {\n\t\t\tint n = transPerAction.length;\n\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\tObject iAct = actions.get(i);\n\t\t\t\ttraverseMatrixDD(transPerAction[i], mcSymb.getAllDDRowVars(), mcSymb.getAllDDColVars(), mcSymb.getODD(), ((s, s2, p, a) -> {\n\t\t\t\t\tmcExpl.addToProbability(s, s2, p, iAct);\n\t\t\t\t}));\n\t\t\t}\n\t\t}\n\t\t// Otherwise, just use the main transition matrix DD\n\t\telse {\n\t\t\ttraverseMatrixDD(mcSymb.getTrans(), mcSymb.getAllDDRowVars(), mcSymb.getAllDDColVars(), mcSymb.getODD(), mcExpl::addToProbability);\n\t\t}\n\t}\n\n\t/**\n\t * Convert the transitions and actions for a symbolically represented MDP\n\t * @param mdpSymb The symbolic MDP\n\t * @param mdpExpl The explicit-state MDP to add to\n\t */\n\tprivate void convertMDPTransitions(symbolic.model.NondetModel mdpSymb, MDPSimple<Double> mdpExpl) throws PrismException\n\t{\n\t\t// Get action info\n\t\tList<Object> actions = mdpSymb.getActions();\n\t\t// Split the transition/action DDs across nondeterministic choices\n\t\tList<Pair<JDDNode,JDDNode>> mdpDDs = splitMDPDD(mdpSymb.getTrans(), mdpSymb.getTransActions(), mdpSymb.getAllDDNondetVars());\n\t\t// For each one\n\t\tfor (Pair<JDDNode,JDDNode> ddPair : mdpDDs) {\n\t\t\t// Store the transitions in a map from source state to distribution\n\t\t\tJDDNode dd = ddPair.getKey();\n\t\t\tHashMap<Integer, Distribution<Double>> distrs = new HashMap<>();\n\t\t\ttraverseMatrixDD(dd, mdpSymb.getAllDDRowVars(), mdpSymb.getAllDDColVars(), mdpSymb.getODD(), (s,s2,v,a) -> {\n\t\t\t\tDistribution<Double> distr = distrs.get(s);\n\t\t\t\tif (distr == null) {\n\t\t\t\t\tdistrs.put(s, distr = Distribution.ofDouble());\n\t\t\t\t}\n\t\t\t\tdistr.add(s2, v);\n\t\t\t});\n\t\t\t// Store any actions in a map from state to action\n\t\t\tJDDNode ddActions = ddPair.getValue();\n\t\t\tHashMap<Integer, Object> distrActions = new HashMap<>();\n\t\t\ttraverseVectorDD(ddActions, mdpSymb.getAllDDRowVars(), mdpSymb.getODD(), (s, v) -> {\n\t\t\t\tint a = (int) Math.round(v);\n\t\t\t\tif (a < actions.size()) {\n\t\t\t\t\tObject act = actions.get(a);\n\t\t\t\t\tif (act != null) {\n\t\t\t\t\t\tdistrActions.put(s, act);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t\t// Add info to the MDP\n\t\t\tdistrs.forEach((s, d) -> mdpExpl.addActionLabelledChoice(s, d, distrActions.get(s)));\n\t\t\tJDD.Deref(dd);\n\t\t\tJDD.Deref(ddActions);\n\t\t}\n\t}\n\n\t/**\n\t * Convert the transitions and actions for a symbolically represented Markov chain\n\t * @param mcSymb The symbolic Markov chain\n\t * @param mcExpl The explicit Markov chain\n\t * @param rewardsSymb symbolic rewards to convert\n\t * @param rewardsExpl The explicit-state reward storage to add to\n\t */\n\tprivate void convertMarkovChainTransitionRewards(symbolic.model.ProbModel mcSymb, DTMC<Double> mcExpl, JDDNode rewardsSymb, RewardsExplicit<Double> rewardsExpl) throws PrismException\n\t{\n\t\t// Traverse the DD to extract the rewards\n\t\ttraverseMatrixDD(rewardsSymb, mcSymb.getAllDDRowVars(), mcSymb.getAllDDColVars(), mcSymb.getODD(), (s, s2, v, a) -> {\n\t\t\t// Find successor index for state s2 (from state s)\n\t\t\tSuccessorsIterator it = mcExpl.getSuccessors(s);\n\t\t\tint i = 0;\n\t\t\twhile (it.hasNext()) {\n\t\t\t\tif (it.nextInt() == s2) {\n\t\t\t\t\trewardsExpl.setTransitionReward(s, i, v);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\ti++;\n\t\t\t}\n\t\t});\n\t}\n\n\t/**\n\t * Convert the transitions and actions for a symbolically represented Markov chain\n\t * @param mdpSymb The symbolic MDP\n\t * @param mdpExpl The explicit MDP\n\t * @param rewardsSymb symbolic rewards to convert\n\t * @param rewardsExpl The explicit-state reward storage to add to\n\t */\n\tprivate void convertMDPTransitionRewards(symbolic.model.NondetModel mdpSymb, MDP<Double> mdpExpl, JDDNode rewardsSymb, RewardsExplicit<Double> rewardsExpl) throws PrismException\n\t{\n\t\tint numStates = mdpSymb.getNumStates();\n\t\tint[] choiceIndices = new int[numStates];\n\t\t// Split the transition/reward DDs across nondeterministic choices\n\t\tList<Pair<JDDNode,JDDNode>> mdpDDs = splitMDPDD(mdpSymb.getTrans01(), rewardsSymb, mdpSymb.getAllDDNondetVars());\n\t\t// For each one\n\t\tfor (Pair<JDDNode,JDDNode> ddPair : mdpDDs) {\n\t\t\t// Update counts of choices for each state\n\t\t\tJDDNode ddChoices = JDD.ThereExists(ddPair.getKey(), mdpSymb.getAllDDColVars());\n\t\t\ttraverseStatesBDD(ddChoices, mdpSymb.getAllDDRowVars(), mdpSymb.getODD(), s -> choiceIndices[s]++);\n\t\t\t// Store transition rewards\n\t\t\t// (note: assumes regards are non-negative)\n\t\t\tJDDNode ddRewards = JDD.MaxAbstract(ddPair.getValue(), mdpSymb.getAllDDColVars());\n\t\t\ttraverseVectorDD(ddRewards, mdpSymb.getAllDDRowVars(), mdpSymb.getODD(), (s, v) -> {\n\t\t\t\trewardsExpl.setTransitionReward(s, choiceIndices[s] - 1, v);\n\t\t\t});\n\t\t\tJDD.Deref(ddChoices);\n\t\t\tJDD.Deref(ddRewards);\n\t\t}\n\t}\n\n\t/**\n\t * Split the DD for an MDP's transition function,\n\t * and a corresponding DD defined for a subset of the transitions,\n\t * into (pairs of) separate DDs, resolving nondeterminism.\n\t * @param trans MDP transition function DD\n\t * @param dd Choice actions DD\n\t * @param ddNondetVars DD variables for nondeterminism\n\t */\n\tprivate List<Pair<JDDNode,JDDNode>> splitMDPDD(JDDNode trans, JDDNode dd, JDDVars ddNondetVars)\n\t{\n\t\tList<Pair<JDDNode,JDDNode>> mdpDDs = new ArrayList<>();\n\t\tsplitMDPDDRec(trans, dd, ddNondetVars, 0, mdpDDs);\n\t\treturn mdpDDs;\n\t}\n\n\t/**\n\t * Recursive helper for {@link #splitMDPDD(JDDNode, JDDNode, JDDVars)}.\n\t * @param trans MDP transition function DD\n\t * @param transActions Choice actions DD\n\t * @param ddNondetVars DD variables for nondeterminism\n\t * @param level Level of recursion\n\t * @param mdpDDs List to store DD pairs\n\t */\n\tprivate void splitMDPDDRec(JDDNode trans, JDDNode transActions, JDDVars ddNondetVars, int level, List<Pair<JDDNode,JDDNode>> mdpDDs)\n\t{\n\t\t// Base case: zero terminal\n\t\tif (trans.equals(JDD.ZERO)) {\n\t\t\treturn;\n\t\t}\n\t\t// Base case: non-zero terminal\n\t\tif (level == ddNondetVars.n()) {\n\t\t\t// Store DDs\n\t\t\tmdpDDs.add(new Pair<>(trans.copy(), transActions.copy()));\n\t\t\treturn;\n\t\t}\n\t\t// Recurse\n\t\tJDDNode e, t;\n\t\tif (trans.getIndex() > ddNondetVars.getVarIndex(level)) {\n\t\t\te = t = trans;\n\t\t}\n\t\telse {\n\t\t\te = trans.getElse();\n\t\t\tt = trans.getThen();\n\t\t}\n\t\tJDDNode eActions, tActions;\n\t\tif (transActions.getIndex() > ddNondetVars.getVarIndex(level)) {\n\t\t\teActions = tActions = transActions;\n\t\t}\n\t\telse {\n\t\t\teActions = transActions.getElse();\n\t\t\ttActions = transActions.getThen();\n\t\t}\n\t\tsplitMDPDDRec(e, eActions, ddNondetVars, level + 1, mdpDDs);\n\t\tsplitMDPDDRec(t, tActions, ddNondetVars, level + 1, mdpDDs);\n\t}\n\n\t/**\n\t * Traverse a BDD representing a set of states and extract the indices of those states\n\t * @param dd The BDD\n\t * @param ddVars The BDD variables\n\t * @param odd The ODD\n\t * @param consumer Consumer to accept indices\n\t */\n\tprivate void traverseStatesBDD(JDDNode dd, JDDVars ddVars, ODDNode odd, IntConsumer consumer) throws PrismException\n\t{\n\t\ttraverseStatesBDDRec(dd, ddVars, 0, odd, 0, consumer);\n\t}\n\n\t/**\n\t * Recursive helper for {@link #traverseStatesBDD(JDDNode, JDDVars, ODDNode, IntConsumer)}.\n\t * @param dd The BDD\n\t * @param ddVars The BDD variables\n\t * @param level Level of recursion\n\t * @param odd The ODD\n\t * @param i State index counter\n\t * @param consumer Consumer to accept indices\n\t */\n\tprivate void traverseStatesBDDRec(JDDNode dd, JDDVars ddVars, int level, ODDNode odd, long i, IntConsumer consumer) throws PrismException\n\t{\n\t\t// Base case: zero terminal\n\t\tif (dd.equals(JDD.ZERO)) {\n\t\t\treturn;\n\t\t}\n\t\t// Base case: non-zero terminal\n\t\tif (level == ddVars.n()) {\n\t\t\tconsumer.accept(SafeCast.toInt(i));\n\t\t\treturn;\n\t\t}\n\t\t// Recurse\n\t\tJDDNode e, t;\n\t\tif (dd.getIndex() > ddVars.getVarIndex(level)) {\n\t\t\te = t = dd;\n\t\t}\n\t\telse {\n\t\t\te = dd.getElse();\n\t\t\tt = dd.getThen();\n\t\t}\n\t\ttraverseStatesBDDRec(e, ddVars, level + 1, odd.getElse(), i, consumer);\n\t\ttraverseStatesBDDRec(t, ddVars, level + 1, odd.getThen(), i + odd.getEOff(), consumer);\n\t}\n\n\t/**\n\t * Traverse a DD representing a state-indexed vector of doubles and extract the non-zero elements of the vector\n\t * @param dd The DD\n\t * @param ddVars The DD variables\n\t * @param odd The ODD\n\t * @param consumer Consumer to accept indices/values\n\t */\n\tprivate void traverseVectorDD(JDDNode dd, JDDVars ddVars, ODDNode odd, IOUtils.StateValueConsumer<Double> consumer) throws PrismException\n\t{\n\t\ttraverseVectorDDRec(dd, ddVars, 0, odd, 0, consumer);\n\t}\n\n\t/**\n\t * Recursive helper for {@link #traverseVectorDD(JDDNode, JDDVars, ODDNode, IOUtils.StateValueConsumer)}\n\t * @param dd The DD\n\t * @param ddVars The DD variables\n\t * @param level Level of recursion\n\t * @param odd The ODD\n\t * @param i State index counter\n\t * @param consumer Consumer to accept indices/values\n\t */\n\tprivate void traverseVectorDDRec(JDDNode dd, JDDVars ddVars, int level, ODDNode odd, long i, IOUtils.StateValueConsumer<Double> consumer) throws PrismException\n\t{\n\t\t// Base case: zero terminal\n\t\tif (dd.equals(JDD.ZERO)) {\n\t\t\treturn;\n\t\t}\n\t\t// Base case: non-zero terminal\n\t\tif (level == ddVars.n()) {\n\t\t\tconsumer.accept(SafeCast.toInt(i), dd.getValue());\n\t\t\treturn;\n\t\t}\n\t\t// Recurse\n\t\tJDDNode e, t;\n\t\tif (dd.getIndex() > ddVars.getVarIndex(level)) {\n\t\t\te = t = dd;\n\t\t}\n\t\telse {\n\t\t\te = dd.getElse();\n\t\t\tt = dd.getThen();\n\t\t}\n\t\ttraverseVectorDDRec(e, ddVars, level + 1, odd.getElse(), i, consumer);\n\t\ttraverseVectorDDRec(t, ddVars, level + 1, odd.getThen(), i + odd.getEOff(), consumer);\n\t}\n\n\t/**\n\t * Traverse a DD representing a state-indexed matrix of doubles and extract the non-zero elements of the vector\n\t *\n\t * @param dd        The DD\n\t * @param ddRowVars The DD variables for rows\n\t * @param ddColVars The DD variables for cols\n\t * @param odd       The ODD\n\t * @param consumer  Consumer to accept indices/values\n\t */\n\tprivate void traverseMatrixDD(JDDNode dd, JDDVars ddRowVars, JDDVars ddColVars, ODDNode odd, IOUtils.MCTransitionConsumer<Double> consumer) throws PrismException\n\t{\n\t\ttraverseMatrixDD(dd, ddRowVars, ddColVars, 0, odd, odd, 0, 0, consumer);\n\t}\n\n\t/**\n\t * Recursive helper for {@link #traverseMatrixDD(JDDNode, JDDVars, JDDVars, ODDNode, IOUtils.MCTransitionConsumer)}.\n\t * @param dd The DD\n\t * @param ddRowVars The DD variables for rows\n\t * @param ddColVars The DD variables for cols\n\t * @param level Level of recursion\n\t * @param oddRow The ODD for rows\n\t * @param oddCol The ODD for cols\n\t * @param r State index counter for rows\n\t * @param c State index counter for cols\n\t * @param consumer Consumer to accept indices/values\n\t */\n\tprivate void traverseMatrixDD(JDDNode dd, JDDVars ddRowVars, JDDVars ddColVars, int level, ODDNode oddRow, ODDNode oddCol, long r, long c, IOUtils.MCTransitionConsumer<Double> consumer) throws PrismException\n\t{\n\t\t// Base case: zero terminal\n\t\tif (dd.equals(JDD.ZERO)) {\n\t\t\treturn;\n\t\t}\n\t\t// Base case: non-zero terminal\n\t\tif (level == ddRowVars.n()) {\n\t\t\tconsumer.accept(SafeCast.toInt(r), SafeCast.toInt(c), dd.getValue(), null);\n\t\t\treturn;\n\t\t}\n\t\t// Recurse\n\t\tJDDNode e, t, ee, et, te, tt;\n\t\tif (dd.getIndex() > ddColVars.getVarIndex(level)) {\n\t\t\tee = et = te = tt = dd;\n\t\t}\n\t\telse if (dd.getIndex() > ddRowVars.getVarIndex(level)) {\n\t\t\tee = te = dd.getElse();\n\t\t\tet = tt = dd.getThen();\n\t\t}\n\t\telse {\n\t\t\te = dd.getElse();\n\t\t\tif (e.getIndex() > ddColVars.getVarIndex(level)) {\n\t\t\t\tee = et = e;\n\t\t\t}\n\t\t\telse {\n\t\t\t\tee = e.getElse();\n\t\t\t\tet = e.getThen();\n\t\t\t}\n\t\t\tt = dd.getThen();\n\t\t\tif (t.getIndex() > ddColVars.getVarIndex(level)) {\n\t\t\t\tte = tt = t;\n\t\t\t}\n\t\t\telse {\n\t\t\t\tte = t.getElse();\n\t\t\t\ttt = t.getThen();\n\t\t\t}\n\t\t}\n\t\ttraverseMatrixDD(ee, ddRowVars, ddColVars, level + 1, oddRow.getElse(), oddCol.getElse(), r, c, consumer);\n\t\ttraverseMatrixDD(et, ddRowVars, ddColVars, level + 1, oddRow.getElse(), oddCol.getThen(), r, c + oddCol.getEOff(), consumer);\n\t\ttraverseMatrixDD(te, ddRowVars, ddColVars, level + 1, oddRow.getThen(), oddCol.getElse(), r + oddRow.getEOff(), c, consumer);\n\t\ttraverseMatrixDD(tt, ddRowVars, ddColVars, level + 1, oddRow.getThen(), oddCol.getThen(), r + oddRow.getEOff(), c + oddCol.getEOff(), consumer);\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/build/ModelGenerator2MTBDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.build;\n\nimport java.util.LinkedList;\nimport java.util.Vector;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.DeclarationClock;\nimport parser.ast.DeclarationIntUnbounded;\nimport parser.ast.DeclarationType;\nimport prism.*;\nimport symbolic.model.Model;\nimport symbolic.model.ModelSymbolic;\nimport symbolic.model.ModelVariablesDD;\nimport symbolic.model.NondetModel;\nimport symbolic.model.ProbModel;\nimport symbolic.model.StochModel;\n\n/**\n * Class to construct a symbolic representation from a ModelGenerator object.\n */\npublic class ModelGenerator2MTBDD extends PrismNativeComponent\n{\n\t// Source model generators\n\tprivate ModelGenerator<Double> modelGen;\n\tprivate RewardGenerator<Double> rewardGen;\n\n\t// Model info\n\tprivate ModelType modelType;\n\tprivate VarList varList;\n\tprivate int numLabels;\n\tprivate int numVars;\n\tprivate int numRewardStructs;\n\tprivate String[] rewardStructNames;\n\n\t// mtbdd stuff\n\n\t// dds/dd vars - whole system\n\tprivate JDDNode trans; // transition matrix dd\n\tprivate JDDNode start; // dd for start state\n\tprivate JDDNode reach; // dd for reachable states\n\tprivate JDDVars allDDRowVars; // all dd vars (rows)\n\tprivate JDDVars allDDColVars; // all dd vars (cols)\n\tprivate JDDVars allDDNondetVars; // all dd vars (all non-det.)\n\t// dds/dd vars - variables\n\tprivate JDDVars[] varDDRowVars; // dd vars (row/col) for each module variable\n\tprivate JDDVars[] varDDColVars;\n\n\tprivate ModelVariablesDD modelVariables;\n\n\t// action info\n\tprivate Vector<String> synchs; // list of action names\n\tprivate JDDNode transActions; // dd for transition action labels (MDPs)\n\tprivate Vector<JDDNode> transPerAction; // dds for transition action labels (D/CTMCs)\n\t// labels\n\tprivate JDDNode[] labelsArray;\n\t// rewards\n\tprivate JDDNode[] stateRewardsArray;\n\tprivate JDDNode[] transRewardsArray;\n\t\n\tprivate int maxNumChoices = 0;\n\n\tpublic ModelGenerator2MTBDD(Prism prism) throws PrismException\n\t{\n\t\tsuper(prism);\n\t}\n\n\t/**\n\t * Build a Model corresponding to the passed in model generator.\n\t */\n\tpublic Model build(ModelGenerator<Double> modelGen, RewardGenerator<Double> rewardGen) throws PrismException\n\t{\n\t\tthis.modelGen = modelGen;\n\t\tthis.rewardGen = rewardGen;\n\t\tmodelType = modelGen.getModelType();\n\t\tvarList = modelGen.createVarList();\n\t\tnumLabels = modelGen.getNumLabels();\n\t\tnumVars = varList.getNumVars();\n\t\tmodelVariables = new ModelVariablesDD();\n\t\tnumRewardStructs = rewardGen.getNumRewardStructs();\n\t\trewardStructNames = rewardGen.getRewardStructNames().toArray(new String[0]);\n\t\treturn buildModel();\n\t}\n\n\t/** build model */\n\tprivate Model buildModel() throws PrismException\n\t{\n\t\tModelSymbolic model = null;\n\t\tJDDNode tmp, tmp2;\n\t\tJDDVars ddv;\n\t\tint i;\n\n\t\t// for an mdp, compute the max number of choices in a state\n\t\tif (modelType == ModelType.MDP)\n\t\t\tmaxNumChoices = 32; // TODO: un-hard-code\n\n\t\t// allocate dd variables\n\t\tallocateDDVars();\n\n\t\t// construct transition matrix and rewards\n\t\tbuildTransAndRewards();\n\n\t\t// get rid of any nondet dd variables not needed\n\t\tif (modelType == ModelType.MDP) {\n\t\t\ttmp = JDD.GetSupport(trans);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDRowVars);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDColVars);\n\t\t\ttmp2 = tmp;\n\t\t\tddv = new JDDVars();\n\t\t\twhile (!tmp2.equals(JDD.ONE)) {\n\t\t\t\tddv.addVar(JDD.Var(tmp2.getIndex()));\n\t\t\t\ttmp2 = tmp2.getThen();\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t\tallDDNondetVars.derefAll();\n\t\t\tallDDNondetVars = ddv;\n\t\t}\n\n\t\t// \t\t// print dd variables actually used (support of trans)\n\t\t// \t\tmainLog.print(\"\\nMTBDD variables used (\" + allDDRowVars.n() + \"r, \" + allDDRowVars.n() + \"c\");\n\t\t// \t\tif (modelType == ModelType.MDP) mainLog.print(\", \" + allDDNondetVars.n() + \"nd\");\n\t\t// \t\tmainLog.print(\"):\");\n\t\t// \t\ttmp = JDD.GetSupport(trans);\n\t\t// \t\ttmp2 = tmp;\n\t\t// \t\twhile (!tmp2.isConstant()) {\n\t\t// \t\t\t//mainLog.print(\" \" + tmp2.getIndex() + \":\" + ddVarNames.elementAt(tmp2.getIndex()));\n\t\t// \t\t\tmainLog.print(\" \" + ddVarNames.elementAt(tmp2.getIndex()));\n\t\t// \t\t\ttmp2 = tmp2.getThen();\n\t\t// \t\t}\n\t\t// \t\tmainLog.println();\n\t\t// \t\tJDD.Deref(tmp);\n\n\t\tint numModules = 1; // just one module\n\t\tString moduleNames[] = new String[] { \"M\" };\n\t\tValues constantValues = modelGen.getConstantValues();\n\n\t\t// create new Model object to be returned\n\t\tif (modelType == ModelType.DTMC) {\n\t\t\tmodel = new ProbModel(trans, start, allDDRowVars, allDDColVars, modelVariables,\n\t\t\t\t\tvarList, varDDRowVars, varDDColVars);\n\t\t} else if (modelType == ModelType.MDP) {\n\t\t\tmodel = new NondetModel(trans, start, allDDRowVars, allDDColVars, allDDNondetVars, modelVariables,\n\t\t\t\t\tvarList, varDDRowVars, varDDColVars);\n\t\t} else if (modelType == ModelType.CTMC) {\n\t\t\tmodel = new StochModel(trans, start, allDDRowVars, allDDColVars, modelVariables,\n\t\t\t\t\tvarList, varDDRowVars, varDDColVars);\n\t\t}\n\t\tmodel.setRewards(stateRewardsArray, transRewardsArray, rewardStructNames);\n\t\tmodel.setConstantValues(constantValues);\n\t\t// set action info\n\t\t// TODO: disable if not required?\n\t\tmodel.setSynchs(synchs);\n\t\tif (modelType != ModelType.MDP) {\n\t\t\t((ProbModel) model).setTransPerAction((JDDNode[]) transPerAction.toArray(new JDDNode[0]));\n\t\t} else {\n\t\t\t((NondetModel) model).setTransActions(transActions);\n\t\t}\n\n\t\t// no need to do reachability\n\t\tmodel.setReach(reach);\n\t\tmodel.filterReachableStates();\n\n\t\t// Print some info (if extraddinfo flag on)\n\t\tif (prism.getExtraDDInfo()) {\n\t\t\tmainLog.print(\"Reach: \" + JDD.GetNumNodes(model.getReach()) + \" nodes\\n\");\n\t\t}\n\n\t\t// find any deadlocks\n\t\tmodel.findDeadlocks(prism.getFixDeadlocks());\n\n\t\t// attach labels\n\t\tfor (int l = 0; l < numLabels; l++) {\n\t\t\tmodel.addLabelDD(modelGen.getLabelName(l), labelsArray[l]);\n\t\t}\n\n\t\treturn model;\n\t}\n\n\t/**\n\t * allocate DD vars for system\n\t * i.e. decide on variable ordering and request variables from CUDD\n\t */\n\tprivate void allocateDDVars() throws PrismException\n\t{\n\t\tJDDNode vr, vc;\n\t\tint i, j, n;\n\n\t\tmodelVariables.preallocateExtraActionVariables(settings.getInteger(PrismSettings.PRISM_DD_EXTRA_ACTION_VARS));\n\n\t\t// create arrays/etc. first\n\n\t\t// module variable (row/col) vars\n\t\tvarDDRowVars = new JDDVars[numVars];\n\t\tvarDDColVars = new JDDVars[numVars];\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\tvarDDRowVars[i] = new JDDVars();\n\t\t\tvarDDColVars[i] = new JDDVars();\n\t\t}\n\n\t\t// now allocate variables\n\n\t\t// allocate nondeterministic variables\n\t\tif (modelType == ModelType.MDP) {\n\t\t\tallDDNondetVars = new JDDVars();\n\t\t\tfor (i = 0; i < maxNumChoices; i++) {\n\t\t\t\tallDDNondetVars.addVar(modelVariables.allocateVariable(\"l\" + i));\n\t\t\t}\n\t\t}\n\n\t\t// allocate dd variables for module variables (i.e. rows/cols)\n\t\t// go through all vars in order (incl. global variables)\n\t\t// so overall ordering can be specified by ordering in the input file\n\t\tallDDRowVars = new JDDVars();\n\t\tallDDColVars = new JDDVars();\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\tDeclarationType declType = varList.getDeclarationType(i);\n\t\t\tif (declType.isUnbounded()) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Cannot build a model that contains a variable with unbounded range (try the explicit engine instead)\");\n\t\t\t}\n\t\t\t// get number of dd variables needed\n\t\t\t// (ceiling of log2 of range of variable)\n\t\t\tn = varList.getRangeLogTwo(i);\n\t\t\t// add pairs of variables (row/col)\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\t// new dd row variable\n\t\t\t\tvr = modelVariables.allocateVariable(varList.getName(i) + \".\" + j);\n\t\t\t\t// new dd col variable\n\t\t\t\tvc = modelVariables.allocateVariable(varList.getName(i) + \"'.\" + j);\n\t\t\t\tvarDDRowVars[i].addVar(vr);\n\t\t\t\tvarDDColVars[i].addVar(vc);\n\t\t\t}\n\t\t\tallDDRowVars.copyVarsFrom(varDDRowVars[i]);\n\t\t\tallDDColVars.copyVarsFrom(varDDColVars[i]);\n\t\t}\n\t}\n\n\t/** Construct transition matrix and rewards */\n\tprivate void buildTransAndRewards() throws PrismException\n\t{\n\t\tJDDNode elem, tmp;\n\n\t\t// initialise action list\n\t\tsynchs = new Vector<String>();\n\n\t\t// initialise mtbdds\n\t\ttrans = JDD.Constant(0);\n\t\tif (modelType != ModelType.MDP) {\n\t\t\ttransPerAction = new Vector<JDDNode>();\n\t\t\ttransPerAction.add(JDD.Constant(0));\n\t\t} else {\n\t\t\ttransActions = JDD.Constant(0);\n\t\t}\n\t\tstart = JDD.Constant(0); \n\t\treach = JDD.Constant(0);\n\t\tlabelsArray = new JDDNode[numLabels];\n\t\tfor (int l = 0; l < numLabels; l++) {\n\t\t\tlabelsArray[l] = JDD.Constant(0);\n\t\t}\n\t\tstateRewardsArray = new JDDNode[numRewardStructs];\n\t\ttransRewardsArray = new JDDNode[numRewardStructs];\n\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\tstateRewardsArray[r] = JDD.Constant(0);\n\t\t\ttransRewardsArray[r] = JDD.Constant(0);\n\t\t}\n\t\t\n\t\tLinkedList<State> explore = new LinkedList<State>();\n\t\t// Add initial state(s) to 'explore', update start/reach\n\t\tfor (State initState : modelGen.getInitialStates()) {\n\t\t\texplore.add(initState);\n\t\t\tJDDNode ddState = encodeState(initState, varDDRowVars);\n\t\t\tstart = JDD.Or(start, ddState.copy());\n\t\t\treach = JDD.Or(reach, ddState);\n\t\t}\n\t\t// Explore...\n\t\twhile (!explore.isEmpty()) {\n\t\t\t// Pick next state to explore\n\t\t\tState state = explore.removeFirst();\n\t\t\tJDDNode ddState = encodeState(state, varDDRowVars);\n\t\t\t// Explore all choices/transitions from this state\n\t\t\tmodelGen.exploreState(state);\n\t\t\t// Look at each outgoing choice in turn\n\t\t\tint nc = modelGen.getNumChoices();\n\t\t\tif (modelType == ModelType.MDP && nc > maxNumChoices) {\n\t\t\t\tString msg = \"Too many nondeterministic choices (\" + nc + \") at state \" + state.toString(modelGen);\n\t\t\t\tmsg += \". Maximum is currently hard-coded at \" + maxNumChoices;\n\t\t\t\tthrow new PrismException(msg);\n\t\t\t}\n\t\t\tfor (int i = 0; i < nc; i++) {\n\t\t\t\tObject o = modelGen.getChoiceAction(i);\n\t\t\t\tString a = o == null ? null : o.toString();\n\t\t\t\t// Look at each transition in the choice\n\t\t\t\tint nt = modelGen.getNumTransitions(i);\n\t\t\t\tfor (int j = 0; j < nt; j++) {\n\t\t\t\t\tState stateNew = modelGen.computeTransitionTarget(i, j);\n\t\t\t\t\tdouble d = modelGen.getTransitionProbability(i, j);\n\t\t\t\t\tJDDNode ddStateNew = encodeState(stateNew, varDDRowVars);\n\t\t\t\t\t// Is this a new state?\n\t\t\t\t\tif (!JDD.AreIntersecting(reach, ddStateNew)) {\n\t\t\t\t\t\t// If so, add to the explore list\n\t\t\t\t\t\texplore.add(stateNew);\n\t\t\t\t\t\t// And to model\n\t\t\t\t\t\treach = JDD.Or(reach, ddStateNew.copy());\n\t\t\t\t\t}\n\t\t\t\t\t// Build MTBDD for transition\n\t\t\t\t\telem = JDD.Apply(JDD.TIMES, ddState.copy(), JDD.PermuteVariables(ddStateNew.copy(), allDDRowVars, allDDColVars));\n\t\t\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\t\t\telem = JDD.Apply(JDD.TIMES, elem, JDD.SetVectorElement(JDD.Constant(0), allDDNondetVars, i, 1));\n\t\t\t\t\t}\n\t\t\t\t\t// add it into mtbdds for transition matrix and transition rewards\n\t\t\t\t\ttrans = JDD.Apply(JDD.PLUS, trans, JDD.Apply(JDD.TIMES, JDD.Constant(d), elem.copy()));\n\t\t\t\t\t// look up action name\n\t\t\t\t\tint k;\n\t\t\t\t\tif (!(a == null || \"\".equals(a))) {\n\t\t\t\t\t\tk = synchs.indexOf(a);\n\t\t\t\t\t\t// add to list if first time seen \n\t\t\t\t\t\tif (k == -1) {\n\t\t\t\t\t\t\tsynchs.add(a);\n\t\t\t\t\t\t\tk = synchs.size() - 1;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tk++;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tk = 0;\n\t\t\t\t\t}\n\t\t\t\t\t/// ...for dtmcs/ctmcs...\n\t\t\t\t\tif (modelType != ModelType.MDP) {\n\t\t\t\t\t\t// get (or create) dd for action k\n\t\t\t\t\t\tif (k < transPerAction.size()) {\n\t\t\t\t\t\t\ttmp = transPerAction.get(k);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\ttmp = JDD.Constant(0);\n\t\t\t\t\t\t\ttransPerAction.add(tmp);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// add element to matrix\n\t\t\t\t\t\ttmp = JDD.Apply(JDD.PLUS, tmp, JDD.Apply(JDD.TIMES, JDD.Constant(d), elem.copy()));\n\t\t\t\t\t\ttransPerAction.set(k, tmp);\n\t\t\t\t\t}\n\t\t\t\t\t/// ...for mdps...\n\t\t\t\t\telse {\n\t\t\t\t\t\ttmp = JDD.ThereExists(elem.copy(), allDDColVars);\n\t\t\t\t\t\t// use max here because we see multiple transitions for a single choice\n\t\t\t\t\t\ttransActions = JDD.Apply(JDD.MAX, transActions, JDD.Apply(JDD.TIMES, JDD.Constant(k), tmp));\n\t\t\t\t\t}\n\n\t\t\t\t\t// Add action rewards\n\t\t\t\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\t\t\t\tdouble tr = rewardGen.getStateActionReward(r, state, o);\n\t\t\t\t\t\ttransRewardsArray[r] = JDD.Apply(JDD.PLUS, transRewardsArray[r], JDD.Apply(JDD.TIMES, JDD.Constant(tr), elem.copy()));\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\t// deref element dd\n\t\t\t\t\tJDD.Deref(elem);\n\t\t\t\t\tJDD.Deref(ddStateNew);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// Print some progress info occasionally\n\t\t\t\t// TODO progress.updateIfReady(src + 1);\n\t\t\t}\n\t\t\t\n\t\t\tfor (int l = 0; l < numLabels; l++) {\n\t\t\t\tif (modelGen.isLabelTrue(l)) {\n\t\t\t\t\tlabelsArray[l] = JDD.Or(labelsArray[l], ddState.copy());\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// Add state rewards\n\t\t\tfor (int r = 0; r < numRewardStructs; r++) {\n\t\t\t\tdouble sr = rewardGen.getStateReward(r, state);\n\t\t\t\tstateRewardsArray[r] = JDD.Apply(JDD.PLUS, stateRewardsArray[r], JDD.Apply(JDD.TIMES, JDD.Constant(sr), ddState.copy()));\n\t\t\t}\n\t\t\t\n\t\t\tJDD.Deref(ddState);\n\t\t}\n\t}\n\t\n\t/**\n\t * Encode a state into a BDD (referencing the result).\n\t */\n\tprivate JDDNode encodeState(State state, JDDVars[] varDDVars) throws PrismException\n\t{\n\t\tJDDNode res;\n\t\tint i, j = 0;\n\t\tres = JDD.Constant(1);\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\ttry {\n\t\t\t\tj = varList.encodeToInt(i, state.varValues[i]);\n\t\t\t} catch (PrismLangException e) {\n\t\t\t\tthrow new PrismException(\"Error during JDD encodeState for state value at index \" + i);\n\t\t\t}\n\t\t\tres = JDD.Apply(JDD.TIMES, res, JDD.SetVectorElement(JDD.Constant(0), varDDVars[i], j, 1.0));\n\t\t}\n\t\treturn res;\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/build/Modules2MTBDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.build;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.HashSet;\nimport java.util.Iterator;\n\nimport jdd.*;\nimport parser.*;\nimport parser.ast.*;\nimport prism.*;\nimport symbolic.comp.StateModelChecker;\nimport symbolic.model.ModelSymbolic;\nimport symbolic.model.ModelVariablesDD;\nimport symbolic.model.Model;\nimport symbolic.model.NondetModel;\nimport symbolic.model.ProbModel;\nimport symbolic.model.StochModel;\n\n// class to translate a modules description file into an MTBDD model\n\npublic class Modules2MTBDD extends PrismNativeComponent\n{\n\t// StateModelChecker for expression -> MTBDD conversion\n\tprivate StateModelChecker expr2mtbdd;\n\t\n\t// ModulesFile object to store syntax tree from parser\n\tprivate ModulesFile modulesFile;\n\t\n\t// model info\n\t\n\t// type\n\tprivate ModelType modelType;\t\t\t\t// model type (dtmc/mdp/ctmc)\n\t// modules\n\tprivate int numModules;\t\t\t// number of modules\n\tprivate String[] moduleNames;\t// module names\n\t// vars/constants\n\tprivate int numVars;\t\t\t// total number of module variables\n\tprivate VarList varList;\t\t// list of module variables\n\tprivate Values constantValues;\t// values of constants\n\t// synch info\n\tprivate int numSynchs;\t\t\t// number of synchronisations\n\tprivate List<String> synchs;\t\t\t// synchronisations\n\t// rewards\n\tprivate int numRewardStructs;\t\t// number of reward structs\n\tprivate String[] rewardStructNames;\t// reward struct names\n\t\n\t// mtbdd stuff\n\t\n\t// dds/dd vars - whole system\n\tprivate JDDNode trans;\t\t\t\t// transition matrix dd\n\tprivate JDDNode range;\t\t\t\t// dd giving range for system\n\tprivate JDDNode start;\t\t\t\t// dd for start state\n\tprivate JDDNode stateRewards[];\t\t// dds for state rewards\n\tprivate JDDNode transRewards[];\t\t// dds for transition rewards\n\tprivate JDDNode transActions;\t// dd for transition action labels (MDPs)\n\tprivate JDDNode transPerAction[];\t// dds for transitions for each action (D/CTMCs)\n\tprivate JDDNode transInd;\t// dds for independent bits of trans\n\tprivate JDDNode transSynch[];\t// dds for synch action parts of trans\n\tprivate JDDVars allDDRowVars;\t\t// all dd vars (rows)\n\tprivate JDDVars allDDColVars;\t\t// all dd vars (cols)\n\tprivate JDDVars allDDSynchVars;\t\t// all dd vars (synchronising actions)\n\tprivate JDDVars allDDSchedVars;\t\t// all dd vars (scheduling)\n\tprivate JDDVars allDDChoiceVars;\t// all dd vars (internal non-det.)\n\tprivate JDDVars allDDNondetVars;\t// all dd vars (all non-det.)\n\t// dds/dd vars - globals\n\tprivate JDDVars globalDDRowVars;\t// dd vars for all globals (rows)\n\tprivate JDDVars globalDDColVars;\t// dd vars for all globals (cols)\n\t// dds/dd vars - modules\n\tprivate JDDVars[] moduleDDRowVars;\t// dd vars for each module (rows)\n\tprivate JDDVars[] moduleDDColVars;\t// dd vars for each module (cols)\n\tprivate JDDNode[] moduleRangeDDs;\t// dd giving range for each module\n\tprivate JDDNode[] moduleIdentities;\t// identity matrix for each module\n\t// dds/dd vars - variables\n\tprivate JDDVars[] varDDRowVars;\t\t// dd vars (row/col) for each module variable\n\tprivate JDDVars[] varDDColVars;\n\tprivate JDDNode[] varRangeDDs;\t\t// dd giving range for each module variable\n\tprivate JDDNode[] varColRangeDDs;\t// dd giving range for each module variable (in col vars)\n\tprivate JDDNode[] varIdentities;\t// identity matrix for each module variable\n\t// dds/dd vars - nondeterminism\n\tprivate JDDNode[] ddSynchVars;\t\t// individual dd vars for synchronising actions\n\tprivate JDDNode[] ddSchedVars;\t\t// individual dd vars for scheduling non-det.\n\tprivate JDDNode[] ddChoiceVars;\t\t// individual dd vars for local non-det.\n\n\tprivate ModelVariablesDD modelVariables;\n\t\n\t// flags for keeping track of which variables have been used\n\tprivate boolean[] varsUsed;\n\t\n\t// symmetry info\n\tprivate boolean doSymmetry;\t\t\t// use symmetry reduction\n\tprivate JDDNode symm; \t\t\t\t// dd of symmetric states\n\tprivate JDDNode nonSymms[];\t\t\t// dds of non-(i,i+1)-symmetric states (i=0...numSymmModules-1)\n\tprivate int numModulesBeforeSymm;\t// number of modules in the PRISM file before the symmetric ones\n\tprivate int numModulesAfterSymm;\t// number of modules in the PRISM file after the symmetric ones\n\tprivate int numSymmModules;\t\t\t// number of symmetric components\n\t\n\t// hidden option - do we also store each part of the transition matrix separately? (now defunct)\n\tprivate boolean storeTransParts = false; \n\t// hidden option - do we also store action info for the transition matrix? (supersedes the above)\n\tprivate boolean storeTransActions = true; \n\t\n\n\t/** Flag, tracking whether the model was already constructed (to know how much cleanup we have to do) */\n\tprivate boolean modelWasBuilt = false;\n\n\t/** Data structure to store mtbdds for a command */\n\tprivate static class CommandDDs\n\t{\n\t\t/** BDD for the guard of a command */\n\t\tpublic JDDNode guard;\n\t\t/** MTBDD for the updates of a command */\n\t\tpublic JDDNode up;\n\n\t\t/** Constructor, assigning ZERO to guard and up */\n\t\tpublic CommandDDs()\n\t\t{\n\t\t\tguard = JDD.Constant(0.0);\n\t\t\tup = JDD.Constant(0.0);\n\t\t}\n\n\t\t/** Constructor */\n\t\tpublic CommandDDs(JDDNode guardDD, JDDNode upDD)\n\t\t{\n\t\t\tthis.guard = guardDD;\n\t\t\tthis.up = upDD;\n\t\t}\n\n\t\t/** Deref the dds (if not null) */\n\t\tpublic void clear()\n\t\t{\n\t\t\tJDD.DerefNonNull(guard);\n\t\t\tJDD.DerefNonNull(up);\n\t\t}\n\t}\n\n\t/**\n\t * Data structure used to store mtbdds and related info\n\t * for an update\n\t */\n\tprivate static class UpdateDDs\n\t{\n\t\t/** MTBDD for the updates */\n\t\tpublic JDDNode up;\n\n\t\tpublic UpdateDDs(JDDNode up)\n\t\t{\n\t\t\tthis.up = up;\n\t\t}\n\n\t\tpublic void clear() {\n\t\t\tJDD.DerefNonNull(up);\n\t\t}\n\t}\n\n\t/**\n\t * Data structure used to store mtbdds and related info\n\t * for some component of the whole model\n\t */\n\tprivate class ComponentDDs\n\t{\n\t\t/** BDD for guards */\n\t\tpublic JDDNode guards;\n\t\t/** MTBDD for transitions */\n\t\tpublic JDDNode trans;\n\t\t/** MTBDD for each reward structure */\n\t\tpublic JDDNode rewards[];\n\t\t/** minimal index of dd vars used for local nondeterminism */\n\t\tpublic int min;\n\t\t/** max index of dd vars used for local nondeterminism */\n\t\tpublic int max;\n\n\t\tpublic ComponentDDs()\n\t\t{\n\t\t\trewards = new JDDNode[modulesFile.getNumRewardStructs()];\n\t\t}\n\t}\n\n\t/**\n\t * Data structure used to store mtbdds and related info\n\t * for some part of the system definition\n\t */\n\tprivate static class SystemDDs\n\t{\n\t\t/** The information for independent bit (i.e. tau action) */\n\t\tpublic ComponentDDs ind;\n\t\t/** The information for each synchronising action */\n\t\tpublic ComponentDDs[] synchs;\n\t\t/** MTBDD for identity matrix */\n\t\tpublic JDDNode id;\n\t\t/** Set of all synchs used (syntactic) */\n\t\tpublic HashSet<String> allSynchs;\n\n\t\tpublic SystemDDs(int n)\n\t\t{\n\t\t\tsynchs = new ComponentDDs[n];\n\t\t\tallSynchs = new HashSet<String>();\n\t\t}\n\t}\n\t\n\t// constructor\n\t\n\tpublic Modules2MTBDD(Prism prism, ModulesFile mf) throws PrismException\n\t{\n\t\tsuper(prism);\n\t\tmodulesFile = mf;\n\t\t// get symmetry reduction info\n\t\tString s = settings.getString(PrismSettings.PRISM_SYMM_RED_PARAMS);\n\t\tdoSymmetry = !(s == null || s == \"\");\n\t}\n\t\n\t@SuppressWarnings(\"unchecked\") // for clone of vector in translate()\n\n\t// main method - translate\n\tpublic Model translate() throws PrismException\n\t{\n\t\tModelSymbolic model = null;\n\t\tJDDNode tmp, tmp2;\n\t\tJDDVars ddv;\n\t\tint i;\n\t\t\n\t\t// get variable info from ModulesFile\n\t\tvarList = modulesFile.createVarList();\n\t\tif (modulesFile.containsUnboundedVariables())\n\t\t\tthrow new PrismNotSupportedException(\"Cannot build a model that contains a variable with unbounded range (try the explicit engine instead)\");\n\t\tnumVars = varList.getNumVars();\n\t\tconstantValues = modulesFile.getConstantValues();\n\t\t\n\t\t// get basic system info\n\t\tmodelType = modulesFile.getModelType();\n\t\tmoduleNames = modulesFile.getModuleNames();\n\t\tnumModules = modulesFile.getNumModules();\n\t\tsynchs = modulesFile.getSynchs();\n\t\tnumSynchs = synchs.size();\n\t\t\n\t\t// check model type is supported\n\t\tif (!(modelType == ModelType.DTMC || modelType == ModelType.MDP || modelType == ModelType.CTMC)) {\n\t\t\tthrow new PrismException(\"Symbolic construction of \" + modelType + \"s not supported\");\n\t\t}\n\t\t\n\t\ttry {\n\t\t\t// allocate dd variables\n\t\t\tallocateDDVars();\n\t\t\tsortDDVars();\n\t\t\tsortIdentities();\n\t\t\tsortRanges();\n\t\t\t\n\t\t\t// create stripped-down StateModelChecker for expression to MTBDD conversions\n\t\t\texpr2mtbdd = new StateModelChecker(prism, varList, allDDRowVars, varDDRowVars, constantValues);\n\t\t\t\n\t\t\t// translate modules file into dd\n\t\t\ttranslateModules();\n\t\t\t\n\t\t\t// get rid of any nondet dd variables not needed\n\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\ttmp = JDD.GetSupport(trans);\n\t\t\t\ttmp = JDD.ThereExists(tmp, allDDRowVars);\n\t\t\t\ttmp = JDD.ThereExists(tmp, allDDColVars);\n\t\t\t\ttmp2 = tmp;\n\t\t\t\tddv = new JDDVars();\n\t\t\t\twhile (!tmp2.equals(JDD.ONE)) {\n\t\t\t\t\tddv.addVar(JDD.Var(tmp2.getIndex()));\n\t\t\t\t\ttmp2 = tmp2.getThen();\n\t\t\t\t}\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\tallDDNondetVars.derefAll();\n\t\t\t\tallDDNondetVars = ddv;\n\t\t\t}\n\n// \t\t// print dd variables actually used (support of trans)\n// \t\tmainLog.print(\"\\nMTBDD variables used (\" + allDDRowVars.n() + \"r, \" + allDDRowVars.n() + \"c\");\n// \t\tif (type == ModulesFile.NONDETERMINISTIC) mainLog.print(\", \" + allDDNondetVars.n() + \"nd\");\n// \t\tmainLog.print(\"):\");\n// \t\ttmp = JDD.GetSupport(trans);\n// \t\ttmp2 = tmp;\n// \t\twhile (!tmp2.isConstant()) {\n// \t\t\t//mainLog.print(\" \" + tmp2.getIndex() + \":\" + ddVarNames.elementAt(tmp2.getIndex()));\n// \t\t\tmainLog.print(\" \" + ddVarNames.elementAt(tmp2.getIndex()));\n// \t\t\ttmp2 = tmp2.getThen();\n// \t\t}\n// \t\tmainLog.println();\n// \t\tJDD.Deref(tmp);\n\n\t\t\t// Print some info (if extraddinfo flag on)\n\t\t\tif (prism.getExtraDDInfo()) {\n\t\t\t\tmainLog.print(\"Transition matrix (pre-reachability): \");\n\t\t\t\tmainLog.print(JDD.GetNumNodes(trans) + \" nodes (\");\n\t\t\t\tmainLog.print(JDD.GetNumTerminals(trans) + \" terminal)\\n\");\n\t\t\t}\n\n\t\t\t// build bdd for initial state(s)\n\t\t\tbuildInitialStates();\n\n\t\t\t// store reward struct names\n\t\t\trewardStructNames = new String[numRewardStructs];\n\t\t\tfor (i = 0; i < numRewardStructs; i++) {\n\t\t\t\trewardStructNames[i] = modulesFile.getRewardStruct(i).getName();\n\t\t\t}\n\n\t\t\t// create new Model object to be returned\n\t\t\tif (modelType == ModelType.DTMC) {\n\t\t\t\tmodel = new ProbModel(trans, start, allDDRowVars, allDDColVars, modelVariables,\n\t\t\t\t                      varList, varDDRowVars, varDDColVars);\n\t\t\t}\n\t\t\telse if (modelType == ModelType.MDP) {\n\t\t\t\tmodel = new NondetModel(trans, start, allDDRowVars, allDDColVars, allDDNondetVars, modelVariables,\n\t\t\t\t\t\t\t\t\t    varList, varDDRowVars, varDDColVars);\n\t\t\t}\n\t\t\telse if (modelType == ModelType.CTMC) {\n\t\t\t\tmodel = new StochModel(trans, start, allDDRowVars, allDDColVars, modelVariables,\n\t\t\t\t                       varList, varDDRowVars, varDDColVars);\n\t\t\t}\n\t\t\tmodel.setRewards(stateRewards, transRewards, rewardStructNames);\n\t\t\tmodel.setConstantValues(constantValues);\n\t\t\tmodelWasBuilt = true;\n\n\t\t\t// We also store a copy of the list of action label names\n\t\t\tmodel.setSynchs(new ArrayList<>(synchs));\n\t\t\n\t\t\t// For MDPs, we also store the DDs used to construct the part\n\t\t\t// of the transition matrix that corresponds to each action\n\t\t\tif (modelType == ModelType.MDP && storeTransParts) {\n\t\t\t\t((NondetModel)model).setTransInd(transInd);\n\t\t\t\t((NondetModel)model).setTransSynch(transSynch);\n\t\t\t}\n\n\t\t\t// If required, we also store info about action labels\n\t\t\tif (storeTransActions) {\n\t\t\t\t// Note: one of these will be null, depending on model type\n\t\t\t\t// but this is fine: null = none stored.\n\t\t\t\tif (modelType != ModelType.MDP) {\n\t\t\t\t\t((ProbModel) model).setTransPerAction(transPerAction);\n\t\t\t\t} else {\n\t\t\t\t\t((NondetModel) model).setTransActions(transActions);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// do reachability (or not)\n\t\t\tif (prism.getDoReach()) {\n\t\t\t\tmainLog.print(\"\\nComputing reachable states...\\n\");\n\t\t\t\tmodel.doReachability();\n\t\t\t\tmodel.filterReachableStates();\n\t\t\t}\n\t\t\telse {\n\t\t\t\tmainLog.print(\"\\nSkipping reachable state computation.\\n\");\n\t\t\t\tmodel.skipReachability();\n\t\t\t\tmodel.filterReachableStates();\n\t\t\t}\n\n\t\t\t// Print some info (if extraddinfo flag on)\n\t\t\tif (prism.getExtraDDInfo()) {\n\t\t\t\tmainLog.print(\"Reach: \" + JDD.GetNumNodes(model.getReach()) + \" nodes\\n\");\n\t\t\t}\n\n\t\t\t// symmetrification\n\t\t\tif (doSymmetry) doSymmetry(model);\n\n\t\t\t// find/fix any deadlocks\n\t\t\tmodel.findDeadlocks(prism.getFixDeadlocks());\n\n\t\t} catch (Exception e) {\n\t\t\t// if the model was already built when the exception occurred, clear it.\n\t\t\tif (model != null)\n\t\t\t\tmodel.clear();\n\t\t\tthrow e;\n\t\t} finally {\n\t\t\t// always clean up the Modules2MTBDD variables\n\t\t\tcleanup();\n\t\t}\n\n\t\treturn model;\n\t}\n\n\t/**\n\t * Perform dd cleanup after translate call. \n\t */\n\tprivate void cleanup()\n\t{\n\t\t// deref spare dds\n\t\tif (globalDDRowVars != null)\n\t\t\tglobalDDRowVars.derefAll();\n\t\tif (globalDDColVars != null)\n\t\t\tglobalDDColVars.derefAll();\n\t\tif (moduleDDRowVars != null)\n\t\t\tJDDVars.derefAllArray(moduleDDRowVars);\n\t\tif (moduleDDColVars != null)\n\t\t\tJDDVars.derefAllArray(moduleDDColVars);\n\t\tJDD.DerefArrayNonNull(moduleIdentities, numModules);\n\t\tJDD.DerefArrayNonNull(moduleRangeDDs, numModules);\n\t\tJDD.DerefArrayNonNull(varIdentities, numVars);\n\t\tJDD.DerefArrayNonNull(varRangeDDs, numVars);\n\t\tJDD.DerefArrayNonNull(varColRangeDDs, numVars);\n\t\tJDD.DerefNonNull(range);\n\t\tJDD.DerefArrayNonNull(ddSynchVars);\n\t\tJDD.DerefArrayNonNull(ddSchedVars);\n\t\tJDD.DerefArrayNonNull(ddChoiceVars);\n\t\tif (allDDSynchVars != null)\n\t\t\tallDDSynchVars.derefAll();\n\t\tif (allDDSchedVars != null)\n\t\t\tallDDSchedVars.derefAll();\n\t\tif (allDDChoiceVars != null)\n\t\t\tallDDChoiceVars.derefAll();\n\n\t\tif (doSymmetry) {\n\t\t\tJDD.Deref(symm);\n\t\t\tJDD.DerefArray(nonSymms, numSymmModules - 1);\n\t\t}\n\n\t\tif (!modelWasBuilt) {\n\t\t\t// if the Model object was not yet constructed, we have to do more cleanup\n\t\t\tJDD.DerefNonNull(trans);\n\t\t\tJDD.DerefNonNull(start);\n\t\t\tJDD.DerefArrayNonNull(stateRewards, numRewardStructs);\n\t\t\tJDD.DerefArrayNonNull(transRewards, numRewardStructs);\n\t\t\tJDD.DerefNonNull(transActions);\n\t\t\tJDD.DerefArrayNonNull(transPerAction);\n\t\t\tJDD.DerefNonNull(transInd);\n\t\t\tJDD.DerefArrayNonNull(transSynch);\n\n\t\t\tif (allDDRowVars != null)\n\t\t\t\tallDDRowVars.derefAll();\n\t\t\tif (allDDColVars != null)\n\t\t\t\tallDDColVars.derefAll();\n\t\t\tif (allDDNondetVars != null)\n\t\t\t\tallDDNondetVars.derefAll();\n\n\t\t\tJDDVars.derefAllArray(varDDRowVars);\n\t\t\tJDDVars.derefAllArray(varDDColVars);\n\n\t\t\tif (modelVariables != null)\n\t\t\t\tmodelVariables.clear();\n\t\t}\n\n\t\tif (expr2mtbdd != null)\n\t\t\texpr2mtbdd.clearDummyModel();\n\t}\n\n\t// allocate DD vars for system\n\t// i.e. decide on variable ordering and request variables from CUDD\n\t\t\t\n\tprivate void allocateDDVars()\n\t{\n\t\tint i, j, m, n, last;\n\t\t\n\t\tmodelVariables = new ModelVariablesDD();\n\t\t\n\t\tswitch (prism.getOrdering()) {\n\t\t\n\t\tcase 1:\n\t\t// ordering: (a ... a) (s ... s) (l ... l) (r c ... r c)\n\t\t\n\t\t\tmodelVariables.preallocateExtraActionVariables(settings.getInteger(PrismSettings.PRISM_DD_EXTRA_ACTION_VARS));\n\n\t\t\t// create arrays/etc. first\n\t\t\t\n\t\t\t// nondeterministic variables\n\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\t// synchronizing action variables\n\t\t\t\tddSynchVars = new JDDNode[numSynchs];\n\t\t\t\t// sched nondet vars\n\t\t\t\tddSchedVars = new JDDNode[numModules];\n\t\t\t\t// local nondet vars\n\t\t\t\t// max num needed = total num of commands in all modules + num of modules\n\t\t\t\t// (actually, might need more for complex parallel compositions? hmmm...)\n\t\t\t\tm = numModules;\n\t\t\t\tfor (i = 0; i < numModules; i++) {\n\t\t\t\t\tm += modulesFile.getModule(i).getNumCommands();\n\t\t\t\t}\n\t\t\t\tddChoiceVars = new JDDNode[m];\n\t\t\t}\n\t\t\t// module variable (row/col) vars\n\t\t\tvarDDRowVars = new JDDVars[numVars];\n\t\t\tvarDDColVars = new JDDVars[numVars];\n\t\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t\tvarDDRowVars[i] = new JDDVars();\n\t\t\t\tvarDDColVars[i] = new JDDVars();\n\t\t\t}\n\t\t\t\n\t\t\t// now allocate variables\n\n\t\t\t// allocate synchronizing action variables\n\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\t// allocate vars\n\t\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\t\tddSynchVars[i] = modelVariables.allocateVariable(synchs.get(i)+\".a\");\n\t\t\t\t}\n\t\t\t}\n\t\t\n\t\t\t// allocate scheduling nondet dd variables\n\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\t// allocate vars\n\t\t\t\tfor (i = 0; i < numModules; i++) {\n\t\t\t\t\tddSchedVars[i] = modelVariables.allocateVariable(moduleNames[i] + \".s\");\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// allocate internal nondet choice dd variables\n\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\tm = ddChoiceVars.length;\n\t\t\t\tfor (i = 0; i < m; i++) {\n\t\t\t\t\tddChoiceVars[i] = modelVariables.allocateVariable(\"l\" + i);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// create a gap in the dd variables\n\t\t\t// this allows to prepend additional row/col vars, e.g. for constructing\n\t\t\t// a product model when doing LTL model checking\n\t\t\tmodelVariables.preallocateExtraStateVariables(settings.getInteger(PrismSettings.PRISM_DD_EXTRA_STATE_VARS));\n\n\t\t\t\n\t\t\t// allocate dd variables for module variables (i.e. rows/cols)\n\t\t\t// go through all vars in order (incl. global variables)\n\t\t\t// so overall ordering can be specified by ordering in the input file\n\t\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t\t// get number of dd variables needed\n\t\t\t\t// (ceiling of log2 of range of variable)\n\t\t\t\tn = varList.getRangeLogTwo(i);\n\t\t\t\t// add pairs of variables (row/col)\n\t\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\t\t// new dd row variable\n\t\t\t\t\tvarDDRowVars[i].addVar(modelVariables.allocateVariable(varList.getName(i) + \".\" + j));\n\t\t\t\t\t// new dd col variable\n\t\t\t\t\tvarDDColVars[i].addVar(modelVariables.allocateVariable(varList.getName(i) + \"'.\" + j));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tbreak;\n\t\t\t\n\t\tcase 2:\n\t\t// ordering: (a ... a) (l ... l) (s r c ... r c) (s r c ... r c) ...\n\t\n\t\t\tmodelVariables.preallocateExtraActionVariables(settings.getInteger(PrismSettings.PRISM_DD_EXTRA_ACTION_VARS));\n\n\t\t\t// create arrays/etc. first\n\t\t\t\n\t\t\t// nondeterministic variables\n\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\t// synchronizing action variables\n\t\t\t\tddSynchVars = new JDDNode[numSynchs];\n\t\t\t\t// sched nondet vars\n\t\t\t\tddSchedVars = new JDDNode[numModules];\n\t\t\t\t// local nondet vars: num = total num of commands in all modules + num of modules\n\t\t\t\tm = numModules;\n\t\t\t\tfor (i = 0; i < numModules; i++) {\n\t\t\t\t\tm += modulesFile.getModule(i).getNumCommands();\n\t\t\t\t}\n\t\t\t\tddChoiceVars = new JDDNode[m];\n\t\t\t}\n\t\t\t// module variable (row/col) vars\n\t\t\tvarDDRowVars = new JDDVars[numVars];\n\t\t\tvarDDColVars = new JDDVars[numVars];\n\t\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t\tvarDDRowVars[i] = new JDDVars();\n\t\t\t\tvarDDColVars[i] = new JDDVars();\n\t\t\t}\n\t\t\t\n\t\t\t// now allocate variables\n\t\t\t\n\t\t\t// allocate synchronizing action variables\n\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\t\tddSynchVars[i] = modelVariables.allocateVariable(synchs.get(i)+\".a\");\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// allocate internal nondet choice dd variables\n\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\tm = ddChoiceVars.length;\n\t\t\t\tfor (i = 0; i < m; i++) {\n\t\t\t\t\tddChoiceVars[i] = modelVariables.allocateVariable(\"l\" + i);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// TODO: For the other variable order (-o1, used for sparse/hybrid by default,\n\t\t\t// see above), we preallocate a certain number of state variables.\n\t\t\t// For consistency, it would make sense to do the same here. However,\n\t\t\t// we should first do some testing to see if this negatively impacts\n\t\t\t// performance.\n\n\t\t\t// go through all vars in order (incl. global variables)\n\t\t\t// so overall ordering can be specified by ordering in the input file\n\t\t\t// use 'last' to detect when starting a new module\n\t\t\tlast = -1; // globals are -1\n\t\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t\t// if at the start of a module's variables\n\t\t\t\t// and model is an mdp...\n\t\t\t\tif ((modelType == ModelType.MDP) && (last != varList.getModule(i))) {\n\t\t\t\t\t// add scheduling dd var(s) (may do multiple ones here if modules have no vars)\n\t\t\t\t\tfor (j = last+1; j <= varList.getModule(i); j++) {\n\t\t\t\t\t\tddSchedVars[j] = modelVariables.allocateVariable(moduleNames[j] + \".s\");\n\t\t\t\t\t}\n\t\t\t\t\t// change 'last'\n\t\t\t\t\tlast = varList.getModule(i);\n\t\t\t\t}\n\t\t\t\t// now add row/col dd vars for the variable\n\t\t\t\t// get number of dd variables needed\n\t\t\t\t// (ceiling of log2 of range of variable)\n\t\t\t\tn = varList.getRangeLogTwo(i);\n\t\t\t\t// add pairs of variables (row/col)\n\t\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\t\tvarDDRowVars[i].addVar(modelVariables.allocateVariable(varList.getName(i) + \".\" + j));\n\t\t\t\t\tvarDDColVars[i].addVar(modelVariables.allocateVariable(varList.getName(i) + \"'.\" + j));\n\t\t\t\t}\n\t\t\t}\n\t\t\t// add any remaining scheduling dd var(s) (happens if some modules have no vars)\n\t\t\tif (modelType == ModelType.MDP) for (j = last+1; j <numModules; j++) {\n\t\t\t\tddSchedVars[j] = modelVariables.allocateVariable(moduleNames[j] + \".s\");\n\t\t\t}\n\t\t\tbreak;\n\t\t\t\n\t\tdefault:\n\t\t\tmainLog.printWarning(\"Invalid MTBDD ordering selected - it's all going to go wrong.\");\n\t\t\tbreak;\n\t\t}\n\t\t\n\t\t// print out all mtbdd variables allocated\n//\t\tmainLog.print(\"\\nMTBDD variables:\");\n//\t\tfor (i = 0; i < ddVarNames.size(); i++) {\n//\t\t\tmainLog.print(\" (\" + i + \")\" + ddVarNames.elementAt(i));\n//\t\t}\n//\t\tmainLog.println();\n\t}\n\n\t// sort out DD variables and the arrays they are stored in\n\t// (more than one copy of most variables is stored)\n\t\t\t\n\tprivate void sortDDVars()\n\t{\n\t\tint i, m;\n\t\t\n\t\t// put refs for all globals and all vars in each module together\n\t\t// create arrays\n\t\tglobalDDRowVars = new JDDVars();\n\t\tglobalDDColVars = new JDDVars();\n\t\tmoduleDDRowVars = new JDDVars[numModules];\n\t\tmoduleDDColVars = new JDDVars[numModules];\n\t\tfor (i = 0; i < numModules; i++) {\n\t\t\tmoduleDDRowVars[i] = new JDDVars();\n\t\t\tmoduleDDColVars[i] = new JDDVars();\n\t\t}\n\t\t// go thru all variables\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t// check which module it belongs to\n\t\t\tm = varList.getModule(i);\n\t\t\t// if global...\n\t\t\tif (m == -1) {\n\t\t\t\tglobalDDRowVars.copyVarsFrom(varDDRowVars[i]);\n\t\t\t\tglobalDDColVars.copyVarsFrom(varDDColVars[i]);\n\t\t\t}\n\t\t\t// otherwise...\n\t\t\telse {\n\t\t\t\tmoduleDDRowVars[m].copyVarsFrom(varDDRowVars[i]);\n\t\t\t\tmoduleDDColVars[m].copyVarsFrom(varDDColVars[i]);\n\t\t\t}\n\t\t}\n\t\t\n\t\t// put refs for all vars in whole system together\n\t\t// create arrays\n\t\tallDDRowVars = new JDDVars();\n\t\tallDDColVars = new JDDVars();\n\t\tif (modelType == ModelType.MDP) {\n\t\t\tallDDSynchVars = new JDDVars();\n\t\t\tallDDSchedVars = new JDDVars();\n\t\t\tallDDChoiceVars = new JDDVars();\n\t\t\tallDDNondetVars = new JDDVars();\n\t\t}\n\t\t// go thru all variables\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t// add to list\n\t\t\tallDDRowVars.copyVarsFrom(varDDRowVars[i]);\n\t\t\tallDDColVars.copyVarsFrom(varDDColVars[i]);\n\t\t}\n\t\tif (modelType == ModelType.MDP) {\n\t\t\t// go thru all syncronising action vars\n\t\t\tfor (i = 0; i < ddSynchVars.length; i++) {\n\t\t\t\t// add to list\n\t\t\t\tallDDSynchVars.addVar(ddSynchVars[i].copy());\n\t\t\t\tallDDNondetVars.addVar(ddSynchVars[i].copy());\n\t\t\t}\n\t\t\t// go thru all scheduler nondet vars\n\t\t\tfor (i = 0; i < ddSchedVars.length; i++) {\n\t\t\t\t// add to list\n\t\t\t\tallDDSchedVars.addVar(ddSchedVars[i].copy());\n\t\t\t\tallDDNondetVars.addVar(ddSchedVars[i].copy());\n\t\t\t}\n\t\t\t// go thru all local nondet vars\n\t\t\tfor (i = 0; i < ddChoiceVars.length; i++) {\n\t\t\t\t// add to list\n\t\t\t\tallDDChoiceVars.addVar(ddChoiceVars[i].copy());\n\t\t\t\tallDDNondetVars.addVar(ddChoiceVars[i].copy());\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// sort DDs for identities\n\t\n\tprivate void sortIdentities()\n\t{\n\t\tint i, j;\n\t\tJDDNode id;\n\t\t\n\t\t// variable identities\n\t\tvarIdentities = new JDDNode[numVars];\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t// set each element of the identity matrix\n\t\t\tid = JDD.Constant(0);\n\t\t\tfor (j = 0; j < varList.getRange(i); j++) {\n\t\t\t\tid = JDD.SetMatrixElement(id, varDDRowVars[i], varDDColVars[i], j, j, 1);\n\t\t\t}\n\t\t\tvarIdentities[i] = id;\n\t\t}\n\t\t// module identities\n\t\tmoduleIdentities = new JDDNode[numModules];\n\t\tfor (i = 0; i < numModules; i++) {\n\t\t\t// product of identities for vars in module\n\t\t\tid = JDD.Constant(1);\n\t\t\tfor (j = 0; j < numVars; j++) {\n\t\t\t\tif (varList.getModule(j) == i) {\n\t\t\t\t\tid = JDD.Apply(JDD.TIMES, id, varIdentities[j].copy());\n\t\t\t\t}\n\t\t\t}\n\t\t\tmoduleIdentities[i] = id;\n\t\t}\n\t}\n\n\t// Sort DDs for ranges\n\t\n\tprivate void sortRanges()\n\t{\n\t\tint i;\n\t\t\n\t\t// initialise raneg for whole system\n\t\trange = JDD.Constant(1);\n\t\t\n\t\t// variable ranges\t\t\n\t\tvarRangeDDs = new JDDNode[numVars];\n\t\tvarColRangeDDs = new JDDNode[numVars];\n\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t// obtain range dd by abstracting from identity matrix\n\t\t\tvarRangeDDs[i] = JDD.SumAbstract(varIdentities[i].copy(), varDDColVars[i]);\n\t\t\t// obtain range dd by abstracting from identity matrix\n\t\t\tvarColRangeDDs[i] = JDD.SumAbstract(varIdentities[i].copy(), varDDRowVars[i]);\n\t\t\t// build up range for whole system as we go\n\t\t\trange = JDD.Apply(JDD.TIMES, range, varRangeDDs[i].copy());\n\t\t}\n\t\t// module ranges\n\t\tmoduleRangeDDs = new JDDNode[numModules];\n\t\tfor (i = 0; i < numModules; i++) {\n\t\t\t// obtain range dd by abstracting from identity matrix\n\t\t\tmoduleRangeDDs[i] = JDD.SumAbstract(moduleIdentities[i].copy(), moduleDDColVars[i]);\n\t\t}\n\t}\n\n\t// translate modules decription to dds\n\t\n\tprivate void translateModules() throws PrismException\n\t{\n\t\tSystemFullParallel sys;\n\t\tJDDNode tmp;\n\t\tint i;\n\t\t\n\t\tvarsUsed = new boolean[numVars];\n\t\t\n\t\tif (modulesFile.getSystemDefn() == null) {\n\t\t\tsys = new SystemFullParallel();\n\t\t\tfor (i = 0; i < numModules; i++) {\n\t\t\t\tsys.addOperand(new SystemModule(moduleNames[i]));\n\t\t\t}\n\t\t\ttranslateSystemDefn(sys);\n\t\t}\n\t\telse {\n\t\t\ttranslateSystemDefn(modulesFile.getSystemDefn());\n\t\t}\n\t\t\n//\t\tif (type == ModulesFile.PROBABILISTIC) {\n//\t\t\t// divide each row by number of modules\n//\t\t\ttrans = JDD.Apply(JDD.DIVIDE, trans, JDD.Constant(numModules));\n//\t\t}\n\t\t\n\t\t// for dtmcs, need to normalise each row to remove local nondeterminism\n\t\tif (modelType == ModelType.DTMC) {\n\t\t\t// divide each row by row sum\n\t\t\ttmp = JDD.SumAbstract(trans.copy(), allDDColVars);\n\t\t\ttrans = JDD.Apply(JDD.DIVIDE, trans, tmp.copy());\n\t\t\t// also divide action info if needed\n\t\t\tif (storeTransActions) {\n\t\t\t\tfor (i = 0; i < numSynchs + 1; i++) {\n\t\t\t\t\ttransPerAction[i] = JDD.Apply(JDD.DIVIDE, transPerAction[i], tmp.copy());\n\t\t\t\t}\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t}\n\t}\n\n\t// build system according to composition expression\n\t\n\tprivate void translateSystemDefn(SystemDefn sys) throws PrismException\n\t{\n\t\tSystemDDs sysDDs;\n\t\tJDDNode tmp, v;\n\t\tint i, j, n, max;\n\t\tint[] synchMin;\n\t\t\n\t\t// initialise some values for synchMin\n\t\t// (stores min indices of dd vars to use for local nondet)\n\t\tsynchMin = new int[numSynchs];\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\tsynchMin[i] = 0;\n\t\t}\n\t\t\n\t\t// build system recursively (descend parse tree)\n\t\tsysDDs = translateSystemDefnRec(sys, synchMin);\n\t\t\n\t\t// for the nondeterministic case, add extra mtbdd variables to encode nondeterminism\n\t\tif (modelType == ModelType.MDP) {\n\t\t\t// need to make sure all parts have the same number of dd variables for nondeterminism\n\t\t\t// so we don't generate lots of extra nondeterministic choices\n\t\t\t// first compute max number of variables used\n\t\t\tmax = sysDDs.ind.max;\n\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\tif (sysDDs.synchs[i].max > max) {\n\t\t\t\t\tmax = sysDDs.synchs[i].max;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// check independent bit has this many variables\n\t\t\tif (max > sysDDs.ind.max) {\n\t\t\t\ttmp = JDD.Constant(1);\n\t\t\t\tfor (i = sysDDs.ind.max; i < max; i++) {\n\t\t\t\t\tv = ddChoiceVars[ddChoiceVars.length-i-1];\n\t\t\t\t\tJDD.Ref(v);\n\t\t\t\t\ttmp = JDD.And(tmp, JDD.Not(v));\n\t\t\t\t}\n\t\t\t\tsysDDs.ind.trans = JDD.Apply(JDD.TIMES, sysDDs.ind.trans, tmp);\n\t\t\t\tsysDDs.ind.max = max;\n\t\t\t}\n\t\t\t// check each synchronous bit has this many variables\n\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\tif (max > sysDDs.synchs[i].max) {\n\t\t\t\t\ttmp = JDD.Constant(1);\n\t\t\t\t\tfor (j = sysDDs.synchs[i].max; j < max; j++) {\n\t\t\t\t\t\tv = ddChoiceVars[ddChoiceVars.length-j-1];\n\t\t\t\t\t\tJDD.Ref(v);\n\t\t\t\t\t\ttmp = JDD.And(tmp, JDD.Not(v));\n\t\t\t\t\t}\n\t\t\t\t\tsysDDs.synchs[i].trans = JDD.Apply(JDD.TIMES, sysDDs.synchs[i].trans, tmp);\n\t\t\t\t\tsysDDs.synchs[i].max = max;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// now add in new mtbdd variables to distinguish between actions\n\t\t\t// independent bit\n\t\t\ttmp = JDD.Constant(1);\n\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\ttmp = JDD.And(tmp, JDD.Not(ddSynchVars[i].copy()));\n\t\t\t}\n\t\t\tsysDDs.ind.trans = JDD.Apply(JDD.TIMES, tmp, sysDDs.ind.trans);\n\t\t\t// synchronous bits\n\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\ttmp = JDD.Constant(1);\n\t\t\t\tfor (j = 0; j < numSynchs; j++) {\n\t\t\t\t\tif (j == i) {\n\t\t\t\t\t\ttmp = JDD.And(tmp, ddSynchVars[j].copy());\n\t\t\t\t\t}\n\t\t\t\t\telse {\n\t\t\t\t\t\ttmp = JDD.And(tmp, JDD.Not(ddSynchVars[j].copy()));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tsysDDs.synchs[i].trans = JDD.Apply(JDD.TIMES, tmp, sysDDs.synchs[i].trans);\n\t\t\t}\n\t\t}\n\t\t\n\t\t// build state and transition rewards\n\t\tcomputeRewards(sysDDs);\n\t\t\n\t\t// now, for all model types, transition matrix can be built by summing over all actions\n\t\t// also build transition rewards at the same time\n\t\tn = modulesFile.getNumRewardStructs();\n\t\ttrans = sysDDs.ind.trans.copy();\n\t\tfor (j = 0; j < n; j++) {\n\t\t\ttransRewards[j] = sysDDs.ind.rewards[j];\n\t\t}\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\ttrans = JDD.Apply(JDD.PLUS, trans, sysDDs.synchs[i].trans.copy());\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\ttransRewards[j] = JDD.Apply(JDD.PLUS, transRewards[j], sysDDs.synchs[i].rewards[j]);\n\t\t\t}\n\t\t}\n\t\t// For D/CTMCs, final rewards are scaled by dividing by total prob/rate for each transition\n\t\t// (when individual transition rewards are computed, they are multiplied by individual probs/rates).\n\t\t// Need to do this (for D/CTMCs) because transition prob/rate can be the sum of values from\n\t\t// several different actions; this gives us the \"expected\" reward for each transition.\n\t\t// (Note, for MDPs, nondeterministic choices are always kept separate so this never occurs.)\n\t\tif (modelType != ModelType.MDP) {\n\t\t\tn = modulesFile.getNumRewardStructs();\n\t\t\tfor (j = 0; j < n; j++) {\n\t\t\t\ttransRewards[j] = JDD.Apply(JDD.DIVIDE, transRewards[j], trans.copy());\n\t\t\t}\n\t\t}\n\t\t\n\t\t// For MDPs, we take a copy of the DDs used to construct the part\n\t\t// of the transition matrix that corresponds to each action\n\t\tif (modelType == ModelType.MDP && storeTransParts) {\n\t\t\ttransInd = JDD.ThereExists(JDD.GreaterThan(sysDDs.ind.trans.copy(), 0), allDDColVars);\n\t\t\ttransSynch = new JDDNode[numSynchs];\n\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\ttransSynch[i] = JDD.ThereExists(JDD.GreaterThan(sysDDs.synchs[i].trans.copy(), 0), allDDColVars);\n\t\t\t}\n\t\t}\n\t\t\n\t\t// If required, we also build MTBDD(s) to store the action labels for each transition.\n\t\t// The indexing of actions is as follows:\n\t\t// independent (\"tau\", non-action-labelled) transitions have index 0;\n\t\t// action-labelled transitions are 1-indexed using the ordering from the model file,\n\t\t// i.e. adding 1 to the list of actions from modulesFile.getSynchs().\n\t\t// What is actually stored differs for each model type.\n\t\t// For MDPs, we just store the action (index) for each state and nondet choice\n\t\t// (as an MTBDD 'transActions' over allDDRowVars and allDDNondetVars, with terminals giving index).  \n\t\t// For D/CTMCs, we have store to store a copy of the transition matrix for each action\n\t\t// (as numSynchs+1 MTBDDs 'transPerAction' over allDDRowVars/allDDColVars, with terminals giving prob/rate)  \n\t\t// because one global transition can come from several different actions.\n\t\tif (storeTransActions) {\n\t\t\t// Initialise storage to null so we know what we have used\n\t\t\ttransActions = null;\n\t\t\ttransPerAction = null;\n\t\t\tswitch (modelType) {\n\t\t\tcase MDP:\n\t\t\t\ttransActions = JDD.Constant(0);\n\t\t\t\t// Don't need to store info for independent (action-less) transitions\n\t\t\t\t// as they are encoded as 0 anyway\n\t\t\t\t//JDD.Ref(sysDDs.ind.trans);\n\t\t\t\t//tmp = JDD.ThereExists(JDD.GreaterThan(sysDDs.ind.trans, 0), allDDColVars);\n\t\t\t\t//transActions = JDD.Apply(JDD.PLUS, transActions, JDD.Apply(JDD.TIMES, tmp, JDD.Constant(1)));\n\t\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\t\ttmp = JDD.ThereExists(JDD.GreaterThan(sysDDs.synchs[i].trans.copy(), 0), allDDColVars);\n\t\t\t\t\ttransActions = JDD.Apply(JDD.PLUS, transActions, JDD.Apply(JDD.TIMES, tmp, JDD.Constant(1+i)));\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase DTMC:\n\t\t\tcase CTMC:\n\t\t\t\t// Just reference DDs and copy them to new array\n\t\t\t\ttransPerAction = new JDDNode[numSynchs + 1];\n\t\t\t\ttransPerAction[0] = sysDDs.ind.trans.copy();\n\t\t\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\t\ttransPerAction[i + 1] = sysDDs.synchs[i].trans.copy();\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// deref bits of ComponentDD objects - we don't need them any more\n\t\tJDD.Deref(sysDDs.ind.guards);\n\t\tJDD.Deref(sysDDs.ind.trans);\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\tJDD.Deref(sysDDs.synchs[i].guards);\n\t\t\tJDD.Deref(sysDDs.synchs[i].trans);\n\t\t}\n\t\tJDD.Deref(sysDDs.id);\n\t}\n\n\t// recursive part of system composition (descend parse tree)\n\t\n\tprivate SystemDDs translateSystemDefnRec(SystemDefn sys, int[] synchMin) throws PrismException\n\t{\n\t\tSystemDDs sysDDs;\n\t\t\n\t\t// determine type of current parse tree node\n\t\t// and pass to relevant method\n\t\tif (sys instanceof SystemModule) {\n\t\t\tsysDDs = translateSystemModule((SystemModule)sys, synchMin);\n\t\t}\n\t\telse if (sys instanceof SystemBrackets) {\n\t\t\tsysDDs = translateSystemDefnRec(((SystemBrackets)sys).getOperand(), synchMin);\n\t\t}\n\t\telse if (sys instanceof SystemFullParallel) {\n\t\t\tsysDDs = translateSystemFullParallel((SystemFullParallel)sys, synchMin);\n\t\t}\n\t\telse if (sys instanceof SystemInterleaved) {\n\t\t\tsysDDs = translateSystemInterleaved((SystemInterleaved)sys, synchMin);\n\t\t}\n\t\telse if (sys instanceof SystemParallel) {\n\t\t\tsysDDs = translateSystemParallel((SystemParallel)sys, synchMin);\n\t\t}\n\t\telse if (sys instanceof SystemHide) {\n\t\t\tsysDDs = translateSystemHide((SystemHide)sys, synchMin);\n\t\t}\n\t\telse if (sys instanceof SystemRename) {\n\t\t\tsysDDs = translateSystemRename((SystemRename)sys, synchMin);\n\t\t}\n\t\telse if (sys instanceof SystemReference) {\n\t\t\tString name = ((SystemReference) sys).getName();\n\t\t\tSystemDefn sysRef = modulesFile.getSystemDefnByName(name);\n\t\t\tif (sysRef == null)\n\t\t\t\tthrow new PrismLangException(\"Reference to system \" + sys + \" which does not exist\", sys);\n\t\t\tsysDDs = translateSystemDefnRec(sysRef, synchMin);\n\t\t}\n\t\telse {\n\t\t\tthrow new PrismLangException(\"Unknown operator in model construction\", sys);\n\t\t}\n\t\t\n\t\treturn sysDDs;\n\t}\n\n\t// system composition (module)\n\t\n\tprivate SystemDDs translateSystemModule(SystemModule sys, int[] synchMin) throws PrismException\n\t{\n\t\tSystemDDs sysDDs;\n\t\tparser.ast.Module module;\n\t\tString synch;\n\t\tint i, m;\n\t\t\n\t\t// create object to store result\n\t\tsysDDs = new SystemDDs(numSynchs);\n\t\t\n\t\t// determine which module it is\n\t\tm = modulesFile.getModuleIndex(sys.getName());\n\t\tmodule = modulesFile.getModule(m);\n\t\t\n\t\t// build mtbdd for independent bit\n\t\tsysDDs.ind = translateModule(m, module, \"\", 0);\n\t\t// build mtbdd for each synchronising action\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\tsynch = synchs.get(i);\n\t\t\tsysDDs.synchs[i] = translateModule(m, module, synch, synchMin[i]);\n\t\t}\n\t\t// store identity matrix\n\t\tsysDDs.id = moduleIdentities[m].copy();\n\t\t\n\t\t// store synchs used\n\t\tsysDDs.allSynchs.addAll(module.getAllSynchs());\n\t\t\n\t\treturn sysDDs;\n\t}\n\n\t// system composition (full parallel)\n\t\n\tprivate SystemDDs translateSystemFullParallel(SystemFullParallel sys, int[] synchMin) throws PrismException\n\t{\n\t\tSystemDDs sysDDs1, sysDDs2, sysDDs;\n\t\tint[] newSynchMin;\n\t\tint i, j;\n\t\t\n\t\t// construct mtbdds for first operand\n\t\tsysDDs = translateSystemDefnRec(sys.getOperand(0), synchMin);\n\t\t\n\t\t// loop through all other operands in the parallel operator\n\t\tfor (i = 1; i < sys.getNumOperands(); i++) {\n\t\t\n\t\t\t// change min to max for potentially synchronising actions\n\t\t\t// store this in new array - old one may still be used elsewhere\n\t\t\tnewSynchMin = new int[numSynchs];\n\t\t\tfor (j = 0; j < numSynchs; j++) {\n\t\t\t\tif (sysDDs.allSynchs.contains(synchs.get(j))) {\n\t\t\t\t\tnewSynchMin[j] = sysDDs.synchs[j].max;\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tnewSynchMin[j] = synchMin[j];\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// construct mtbdds for next operand\n\t\t\tsysDDs2 = translateSystemDefnRec(sys.getOperand(i), newSynchMin);\n\t\t\t// move sysDDs (operands composed so far) into sysDDs1\n\t\t\tsysDDs1 = sysDDs;\n\t\t\t// we are going to combine sysDDs1 and sysDDs2 and put the result into sysDDs\n\t\t\tsysDDs = new SystemDDs(numSynchs);\n\t\t\t\n\t\t\t// combine mtbdds for independent bit\n\t\t\tsysDDs.ind = translateNonSynchronising(sysDDs1.ind, sysDDs2.ind, sysDDs1.id, sysDDs2.id);\n\t\t\t\n\t\t\t// combine mtbdds for each synchronising action\n\t\t\tfor (j = 0; j < numSynchs; j++) {\n\t\t\t\t// if one operand does not use this action,\n\t\t\t\t// do asynchronous parallel composition\n\t\t\t\tif ((sysDDs1.allSynchs.contains(synchs.get(j))?1:0) + (sysDDs2.allSynchs.contains(synchs.get(j))?1:0) == 1) {\n\t\t\t\t\tsysDDs.synchs[j] = translateNonSynchronising(sysDDs1.synchs[j], sysDDs2.synchs[j], sysDDs1.id, sysDDs2.id);\n\t\t\t\t}\n\t\t\t\telse {\n\t\t\t\t\tsysDDs.synchs[j] = translateSynchronising(sysDDs1.synchs[j], sysDDs2.synchs[j]);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t// compute identity\n\t\t\tsysDDs.id = JDD.Apply(JDD.TIMES, sysDDs1.id, sysDDs2.id);\n\t\t\t\n\t\t\t// combine lists of synchs\n\t\t\tsysDDs.allSynchs.addAll(sysDDs1.allSynchs);\n\t\t\tsysDDs.allSynchs.addAll(sysDDs2.allSynchs);\n\t\t}\n\t\t\n\t\treturn sysDDs;\n\t}\n\n\t// system composition (interleaved)\n\t\t\n\tprivate SystemDDs translateSystemInterleaved(SystemInterleaved sys, int[] synchMin) throws PrismException\n\t{\n\t\tSystemDDs sysDDs1, sysDDs2, sysDDs;\n\t\tint i, j;\n\t\n\t\t// construct mtbdds for first operand\n\t\tsysDDs = translateSystemDefnRec(sys.getOperand(0), synchMin);\n\t\t\n\t\t// loop through all other operands in the parallel operator\n\t\tfor (i = 1; i < sys.getNumOperands(); i++) {\n\t\t\n\t\t\t// construct mtbdds for next operand\n\t\t\tsysDDs2 = translateSystemDefnRec(sys.getOperand(i), synchMin);\n\t\t\t// move sysDDs (operands composed so far) into sysDDs1\n\t\t\tsysDDs1 = sysDDs;\n\t\t\t// we are going to combine sysDDs1 and sysDDs2 and put the result into sysDDs\n\t\t\tsysDDs = new SystemDDs(numSynchs);\n\t\t\t\n\t\t\t// combine mtbdds for independent bit\n\t\t\tsysDDs.ind = translateNonSynchronising(sysDDs1.ind, sysDDs2.ind, sysDDs1.id, sysDDs2.id);\n\t\t\t\n\t\t\t// combine mtbdds for each synchronising action\n\t\t\tfor (j = 0; j < numSynchs; j++) {\n\t\t\t\tsysDDs.synchs[j] = translateNonSynchronising(sysDDs1.synchs[j], sysDDs2.synchs[j], sysDDs1.id, sysDDs2.id);\n\t\t\t}\n\t\t\t\n\t\t\t// compute identity\n\t\t\tsysDDs.id = JDD.Apply(JDD.TIMES, sysDDs1.id, sysDDs2.id);\n\t\t\t\n\t\t\t// combine lists of synchs\n\t\t\tsysDDs.allSynchs.addAll(sysDDs1.allSynchs);\n\t\t\tsysDDs.allSynchs.addAll(sysDDs2.allSynchs);\n\t\t}\n\t\t\n\t\treturn sysDDs;\n\t}\n\n\t// system composition (parallel over actions)\n\t\n\tprivate SystemDDs translateSystemParallel(SystemParallel sys, int[] synchMin) throws PrismException\n\t{\n\t\tSystemDDs sysDDs1, sysDDs2, sysDDs;\n\t\tboolean[] synchBool;\n\t\tint[] newSynchMin;\n\t\tint i;\n\t\t\n\t\t// go thru all synchronising actions and decide if we will synchronise on each one\n\t\tsynchBool = new boolean[numSynchs];\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\tsynchBool[i] = sys.containsAction(synchs.get(i));\n\t\t}\n\t\t\n\t\t// construct mtbdds for first operand\n\t\tsysDDs1 = translateSystemDefnRec(sys.getOperand1(), synchMin);\n\t\t\n\t\t// change min to max for synchronising actions\n\t\t// store this in new array - old one may still be used elsewhere\n\t\tnewSynchMin = new int[numSynchs];\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\tif (synchBool[i]) {\n\t\t\t\tnewSynchMin[i] = sysDDs1.synchs[i].max;\n\t\t\t}\n\t\t\telse {\n\t\t\t\tnewSynchMin[i] = synchMin[i];\n\t\t\t}\n\t\t}\n\t\t\n\t\t// construct mtbdds for second operand\n\t\tsysDDs2 = translateSystemDefnRec(sys.getOperand2(), newSynchMin);\n\t\t\n\t\t// create object to store mtbdds\n\t\tsysDDs = new SystemDDs(numSynchs);\n\t\t\n\t\t// combine mtbdds for independent bit\n\t\tsysDDs.ind = translateNonSynchronising(sysDDs1.ind, sysDDs2.ind, sysDDs1.id, sysDDs2.id);\n\t\t\n\t\t// combine mtbdds for each synchronising action\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\tif (synchBool[i]) {\n\t\t\t\tsysDDs.synchs[i] = translateSynchronising(sysDDs1.synchs[i], sysDDs2.synchs[i]);\n\t\t\t}\n\t\t\telse {\n\t\t\t\tsysDDs.synchs[i] = translateNonSynchronising(sysDDs1.synchs[i], sysDDs2.synchs[i], sysDDs1.id, sysDDs2.id);\n\t\t\t}\n\t\t}\n\t\t\n\t\t// combine mtbdds for identity matrices\n\t\tsysDDs.id = JDD.Apply(JDD.TIMES, sysDDs1.id, sysDDs2.id);\n\t\t\n\t\t// combine lists of synchs\n\t\tsysDDs.allSynchs.addAll(sysDDs1.allSynchs);\n\t\tsysDDs.allSynchs.addAll(sysDDs2.allSynchs);\n\t\t\n\t\treturn sysDDs;\n\t}\n\t\n\t// system composition (hide)\n\t\n\tprivate SystemDDs translateSystemHide(SystemHide sys, int[] synchMin) throws PrismException\n\t{\n\t\tSystemDDs sysDDs1, sysDDs;\n\t\tint[] newSynchMin;\n\t\tint i;\n\t\t\n\t\t// reset synchMin to 0 for actions to be hidden\n\t\t// store this in new array - old one may still be used elsewhere\n\t\tnewSynchMin = new int[numSynchs];\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\tif (sys.containsAction(synchs.get(i))) {\n\t\t\t\tnewSynchMin[i] = 0;\n\t\t\t}\n\t\t\telse {\n\t\t\t\tnewSynchMin[i] = synchMin[i];\n\t\t\t}\n\t\t}\n\t\t\n\t\t// construct mtbdds for operand\n\t\tsysDDs1 = translateSystemDefnRec(sys.getOperand(), newSynchMin);\n\t\t\n\t\t// create object to store mtbdds for result\n\t\tsysDDs = new SystemDDs(numSynchs);\n\t\t\n\t\t// copy across independent bit\n\t\tsysDDs.ind = sysDDs1.ind;\n\t\t\n\t\t// go thru all synchronising actions\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t\n\t\t\t// if the action is in the set to be hidden, hide it...\n\t\t\t// note that it doesn't matter if an action is included more than once in the set\n\t\t\t// (although this would be picked up during the syntax check anyway)\n\t\t\tif (sys.containsAction(synchs.get(i))) {\n\t\t\t\t\n\t\t\t\t// move these transitions into the independent bit\n\t\t\t\tsysDDs.ind = combineComponentDDs(sysDDs.ind, sysDDs1.synchs[i]);\n\t\t\t\t\n\t\t\t\t// create empty mtbdd for action\n\t\t\t\tsysDDs.synchs[i] = new ComponentDDs();\n\t\t\t\tsysDDs.synchs[i].guards = JDD.Constant(0);\n\t\t\t\tsysDDs.synchs[i].trans = JDD.Constant(0);\n\t\t\t\tsysDDs.synchs[i].min = 0;\n\t\t\t\tsysDDs.synchs[i].max = 0;\n\t\t\t}\n\t\t\t// otherwise just copy it across\n\t\t\telse {\n\t\t\t\tsysDDs.synchs[i] = sysDDs1.synchs[i];\n\t\t\t}\n\t\t}\n\t\t\n\t\t// copy identity too\n\t\tsysDDs.id = sysDDs1.id;\n\t\t\n\t\t// modify list of synchs\n\t\tsysDDs.allSynchs.addAll(sysDDs1.allSynchs);\n\t\tfor (i = 0; i < sys.getNumActions(); i++) {\n\t\t\tsysDDs.allSynchs.remove(sys.getAction(i));\n\t\t}\n\t\t\n\t\treturn sysDDs;\n\t}\n\n\t// system composition (rename)\n\t\n\tprivate SystemDDs translateSystemRename(SystemRename sys, int[] synchMin) throws PrismException\n\t{\n\t\tSystemDDs sysDDs1, sysDDs;\n\t\tint[] newSynchMin;\n\t\tint i, j;\n\t\tString s;\n\t\tIterator<String> iter;\n\t\t\n\t\t// swap some values in synchMin due to renaming\n\t\t// store this in new array - old one may still be used elsewhere\n\t\tnewSynchMin = new int[numSynchs];\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\t// find out what this action is renamed to\n\t\t\t// (this may be itself, i.e. it's not renamed)\n\t\t\ts = sys.getNewName(synchs.get(i));\n\t\t\tj = synchs.indexOf(s);\n\t\t\tif (j == -1) {\n\t\t\t\tthrow new PrismLangException(\"Invalid action name \\\"\" + s + \"\\\" in renaming\", sys);\n\t\t\t}\n\t\t\tnewSynchMin[i] = synchMin[j];\n\t\t}\n\t\t\n\t\t// construct mtbdds for operand\n\t\tsysDDs1 = translateSystemDefnRec(sys.getOperand(), newSynchMin);\n\t\t\n\t\t// create object to store mtbdds for result\n\t\tsysDDs = new SystemDDs(numSynchs);\n\t\t\n\t\t// copy across independent bit\n\t\tsysDDs.ind = sysDDs1.ind;\n\t\t\n\t\t// initially there are no mtbdds in result\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\tsysDDs.synchs[i] = new ComponentDDs();\n\t\t\tsysDDs.synchs[i].guards = JDD.Constant(0);\n\t\t\tsysDDs.synchs[i].trans = JDD.Constant(0);\n\t\t\tsysDDs.synchs[i].min = 0;\n\t\t\tsysDDs.synchs[i].max = 0;\n\t\t}\n\t\t\n\t\t// go thru all synchronising actions\n\t\tfor (i = 0; i < numSynchs; i++) {\n\t\t\n\t\t\t// find out what this action is renamed to\n\t\t\t// (this may be itself, i.e. it's not renamed)\n\t\t\t// then add it to result\n\t\t\ts = sys.getNewName(synchs.get(i));\n\t\t\tj = synchs.indexOf(s);\n\t\t\tif (j == -1) {\n\t\t\t\tthrow new PrismLangException(\"Invalid action name \\\"\" + s + \"\\\" in renaming\", sys);\n\t\t\t}\n\t\t\tsysDDs.synchs[j] = combineComponentDDs(sysDDs.synchs[j], sysDDs1.synchs[i]);\n\t\t}\n\t\t\n\t\t// copy identity too\n\t\tsysDDs.id = sysDDs1.id;\n\t\t\n\t\t// modify list of synchs\n\t\titer = sysDDs1.allSynchs.iterator();\n\t\twhile (iter.hasNext()) {\n\t\t\tsysDDs.allSynchs.add(sys.getNewName(iter.next()));\n\t\t}\n\t\t\n\t\treturn sysDDs;\n\t}\n\n\tprivate ComponentDDs translateSynchronising(ComponentDDs compDDs1, ComponentDDs compDDs2) throws PrismException\n\t{\n\t\tComponentDDs compDDs;\n\t\t\n\t\t// create object to store result\n\t\tcompDDs = new ComponentDDs();\n\t\t\n\t\t// combine parts synchronously\n\t\t// first guards\n\t\tJDD.Ref(compDDs1.guards);\n\t\tJDD.Ref(compDDs2.guards);\n\t\tcompDDs.guards = JDD.And(compDDs1.guards, compDDs2.guards);\n\t\t// then transitions\n\t\tJDD.Ref(compDDs1.trans);\n\t\tJDD.Ref(compDDs2.trans);\n\t\tcompDDs.trans = JDD.Apply(JDD.TIMES, compDDs1.trans, compDDs2.trans);\n\t\t// compute new min/max\n\t\tcompDDs.min = (compDDs1.min < compDDs2.min) ? compDDs1.min : compDDs2.min;\n\t\tcompDDs.max = (compDDs1.max > compDDs2.max) ? compDDs1.max : compDDs2.max;\n\t\t\n\t\t// deref old stuff\n\t\tJDD.Deref(compDDs1.guards);\n\t\tJDD.Deref(compDDs2.guards);\n\t\tJDD.Deref(compDDs1.trans);\n\t\tJDD.Deref(compDDs2.trans);\n\t\t\n\t\treturn compDDs;\n\t}\n\n\tprivate ComponentDDs translateNonSynchronising(ComponentDDs compDDs1, ComponentDDs compDDs2, JDDNode id1, JDDNode id2) throws PrismException\n\t{\n\t\tComponentDDs compDDs;\n\t\t\n\t\t// add identities to mtbdds for transitions\n\t\tJDD.Ref(id2);\n\t\tcompDDs1.trans = JDD.Apply(JDD.TIMES, compDDs1.trans, id2);\n\t\tJDD.Ref(id1);\n\t\tcompDDs2.trans = JDD.Apply(JDD.TIMES, compDDs2.trans, id1);\n\t\t\n\t\tcompDDs = combineComponentDDs(compDDs1, compDDs2);\n\t\t\n\t\treturn compDDs;\n\t}\n\n\tprivate ComponentDDs combineComponentDDs(ComponentDDs compDDs1, ComponentDDs compDDs2) throws PrismException\n\t{\n\t\tComponentDDs compDDs;\n\t\tJDDNode tmp, v;\n\t\tint i;\n\t\t\n\t\t// create object to store result\n\t\tcompDDs = new ComponentDDs();\n\t\t\n\t\t// if no nondeterminism - just add\n\t\tif (modelType != ModelType.MDP) {\n\t\t\tcompDDs.guards = JDD.Or(compDDs1.guards, compDDs2.guards);\n\t\t\tcompDDs.trans = JDD.Apply(JDD.PLUS, compDDs1.trans, compDDs2.trans);\n\t\t\tcompDDs.min = 0;\n\t\t\tcompDDs.max = 0;\n\t\t}\n\t\t// if there's nondeterminism, but one part is empty, it's also easy\n\t\telse if (compDDs1.trans.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(compDDs1.guards);\n\t\t\tcompDDs.guards = compDDs2.guards;\n\t\t\tJDD.Deref(compDDs1.trans);\n\t\t\tcompDDs.trans = compDDs2.trans;\n\t\t\tcompDDs.min = compDDs2.min;\n\t\t\tcompDDs.max = compDDs2.max;\n\t\t}\n\t\telse if (compDDs2.trans.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(compDDs2.guards);\n\t\t\tcompDDs.guards = compDDs1.guards;\n\t\t\tJDD.Deref(compDDs2.trans);\n\t\t\tcompDDs.trans = compDDs1.trans;\n\t\t\tcompDDs.min = compDDs1.min;\n\t\t\tcompDDs.max = compDDs1.max;\n\t\t}\n\t\t// otherwise, it's a bit more complicated...\n\t\telse {\n\t\t\t// make sure two bits have the same number of dd variables for nondeterminism\n\t\t\t// (so we don't generate lots of extra nondeterministic choices)\n\t\t\tif (compDDs1.max > compDDs2.max) {\n\t\t\t\ttmp = JDD.Constant(1);\n\t\t\t\tfor (i = compDDs2.max; i < compDDs1.max; i++) {\n\t\t\t\t\tv = ddChoiceVars[ddChoiceVars.length-i-1];\n\t\t\t\t\tJDD.Ref(v);\n\t\t\t\t\ttmp = JDD.And(tmp, JDD.Not(v));\n\t\t\t\t}\n\t\t\t\tcompDDs2.trans = JDD.Apply(JDD.TIMES, compDDs2.trans, tmp);\n\t\t\t\tcompDDs2.max = compDDs1.max;\n\t\t\t}\n\t\t\telse if (compDDs2.max > compDDs1.max) {\n\t\t\t\ttmp = JDD.Constant(1);\n\t\t\t\tfor (i = compDDs1.max; i < compDDs2.max; i++) {\n\t\t\t\t\tv = ddChoiceVars[ddChoiceVars.length-i-1];\n\t\t\t\t\tJDD.Ref(v);\n\t\t\t\t\ttmp = JDD.And(tmp, JDD.Not(v));\n\t\t\t\t}\n\t\t\t\tcompDDs1.trans = JDD.Apply(JDD.TIMES, compDDs1.trans, tmp);\n\t\t\t\tcompDDs1.max = compDDs2.max;\n\t\t\t}\n\t\t\t// and then combine\n\t\t\tif (ddChoiceVars.length-compDDs1.max-1 < 0)\n\t\t\t\tthrow new PrismException(\"Insufficient BDD variables allocated for nondeterminism - please report this as a bug. Thank you\");\n\t\t\tv = ddChoiceVars[ddChoiceVars.length-compDDs1.max-1];\n\t\t\tcompDDs.guards = JDD.Or(compDDs1.guards, compDDs2.guards);\n\t\t\tJDD.Ref(v);\n\t\t\tcompDDs.trans = JDD.ITE(v, compDDs2.trans, compDDs1.trans);\n\t\t\tcompDDs.min = compDDs1.min;\n\t\t\tcompDDs.max = compDDs1.max+1;\n\t\t}\n\t\t\n\t\treturn compDDs;\n\t}\n\t\n\t// translate a single module to a dd\n\t// for a given synchronizing action (\"\" = none)\n\t\n\tprivate ComponentDDs translateModule(int m, parser.ast.Module module, String synch, int synchMin) throws PrismException\n\t{\n\t\tComponentDDs compDDs;\n\t\tCommandDDs[] commandsDDs;\n\t\tCommand command;\n\t\tint l, numCommands;\n\t\tboolean match;\n\t\t\n\t\t// get number of commands and set up array accordingly\n\t\tnumCommands = module.getNumCommands();\n\t\tcommandsDDs = new CommandDDs[numCommands];\n\n\t\t// translate guard/updates for each command of the module\n\t\tfor (l = 0; l < numCommands; l++) {\n\t\t\tcommand = module.getCommand(l);\n\t\t\t// check if command matches requested synch\n\t\t\tmatch = false;\n\t\t\tif (synch == \"\") {\n\t\t\t\tif (command.getSynch() == \"\") match = true;\n\t\t\t}\n\t\t\telse {\n\t\t\t\tif (command.getSynch().equals(synch)) match = true;\n\t\t\t}\n\t\t\t// if so translate\n\t\t\tif (match) {\n\t\t\t\t// store in array\n\t\t\t\tcommandsDDs[l] = translateCommand(m, module, l, command);\n\t\t\t}\n\t\t\t// otherwise use 0\n\t\t\telse {\n\t\t\t\tcommandsDDs[l] = new CommandDDs();\n\t\t\t}\n\t\t}\n\n\t\t// combine guard/updates dds for each command\n\t\tif (modelType == ModelType.DTMC) {\n\t\t\tcompDDs = combineCommandsProb(m, commandsDDs);\n\t\t} else if (modelType == ModelType.MDP) {\n\t\t\tcompDDs = combineCommandsNondet(m, commandsDDs, synchMin);\n\t\t} else if (modelType == ModelType.CTMC) {\n\t\t\tcompDDs = combineCommandsStoch(m, commandsDDs);\n\t\t} else {\n\t\t\tthrow new PrismException(\"Unknown model type\");\n\t\t}\n\n\t\t// deref guards/updates\n\t\tfor (CommandDDs c : commandsDDs) {\n\t\t\tc.clear();\n\t\t}\n\n\t\treturn compDDs;\n\t}\n\n\t/**\n\t * Translate a command to a CommandDDs.\n\t * <br>[ REFs: <i>result</i> ]\n\t */\n\tprivate CommandDDs translateCommand(int m, parser.ast.Module module, int l, Command command) throws PrismException\n\t{\n\t\tJDDNode guardDD, upDD = null;\n\t\t// translate guard\n\t\tguardDD = translateExpression(command.getGuard());\n\t\tguardDD = JDD.Times(guardDD, range.copy());\n\t\t// check for false guard\n\t\tif (guardDD.equals(JDD.ZERO)) {\n\t\t\t// display a warning (unless guard is \"false\", in which case was probably intentional\n\t\t\tif (!Expression.isFalse(command.getGuard())) {\n\t\t\t\tString s = \"Guard for command \" + (l+1) + \" of module \\\"\" + module.getName() + \"\\\" is never satisfied.\";\n\t\t\t\tmainLog.printWarning(s);\n\t\t\t}\n\t\t\t// no point bothering to compute the mtbdds for the update\n\t\t\t// if the guard is never satisfied\n\t\t\tupDD = JDD.Constant(0);\n\t\t}\n\t\telse {\n\t\t\t// translate updates and do some checks on probs/rates\n\t\t\tUpdateDDs up = null;\n\t\t\ttry {\n\t\t\t\tup = translateUpdates(m, l, command.getUpdates(), (command.getSynch()==\"\")?false:true, guardDD);\n\t\t\t\tup.up = JDD.Times(up.up, guardDD.copy());\n\t\t\t\tupDD = up.up.copy();\n\t\t\t\tcheckCommandProbRates(m, module, l, command, guardDD, upDD);\n\t\t\t} catch (Throwable e) {\n\t\t\t\tJDD.DerefNonNull(guardDD, upDD);\n\t\t\t\tthrow e;\n\t\t\t} finally {\n\t\t\t\tif (up != null) {\n\t\t\t\t\tup.clear();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\treturn new CommandDDs(guardDD, upDD);\n\t}\n\n\t/**\n\t * Check the probabilities/rate of a command for errors (in which case an exception is thrown).\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t * @param m the module index\n\t * @param module the Module AST element\n\t * @param l the command index (inside the module)\n\t * @param command the Command AST element\n\t * @param guardDD the guard dd\n\t * @param upDD the update dd\n\t */\n\tprivate void checkCommandProbRates(int m, parser.ast.Module module, int l, Command command, JDDNode guardDD, JDDNode upDD) throws PrismLangException\n\t{\n\t\t// are all probs/rates non-negative?\n\t\tdouble dmin = JDD.FindMin(upDD);\n\t\tif (dmin < 0) {\n\t\t\tString s = (modelType == ModelType.CTMC) ? \"Rates\" : \"Probabilities\";\n\t\t\ts += \" in command \" + (l+1) + \" of module \\\"\" + module.getName() + \"\\\" are negative\";\n\t\t\ts += \" (\" + dmin + \") for some states.\\n\";\n\t\t\ts += \"Perhaps the guard needs to be strengthened\";\n\t\t\tthrow new PrismLangException(s, command);\n\t\t}\n\t\t// only do remaining checks if 'doprobchecks' flag is set\n\t\tif (prism.getDoProbChecks()) {\n\t\t\t// sum probs/rates in updates\n\t\t\tJDDNode tmp = JDD.SumAbstract(upDD.copy(), moduleDDColVars[m]);\n\t\t\ttmp = JDD.SumAbstract(tmp, globalDDColVars);\n\t\t\t// put 1s in for sums which are not covered by this guard\n\t\t\ttmp = JDD.ITE(guardDD.copy(), tmp, JDD.Constant(1));\n\t\t\t// compute min/max sums\n\t\t\tdmin = JDD.FindMin(tmp);\n\t\t\tdouble dmax = JDD.FindMax(tmp);\n\t\t\t// check sums for NaNs\n\t\t\tif (Double.isNaN(dmin) || Double.isNaN(dmax)) {\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\tString s = (modelType == ModelType.CTMC) ? \"Rates\" : \"Probabilities\";\n\t\t\t\ts += \" in command \" + (l+1) + \" of module \\\"\" + module.getName() + \"\\\" have errors (NaN) for some states. \";\n\t\t\t\ts += \"Check for zeros in divide or modulo operations. \";\n\t\t\t\ts += \"Perhaps the guard needs to be strengthened\";\n\t\t\t\tthrow new PrismLangException(s, command);\n\t\t\t}\n\t\t\t// check min sums - 1 (ish) for dtmcs/mdps, 0 for ctmcs\n\t\t\tif (modelType != ModelType.CTMC && !PrismUtils.doublesAreEqual(dmin, 1.0)) {\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\tString s = \"Probabilities in command \" + (l+1) + \" of module \\\"\" + module.getName() + \"\\\" sum to less than one\";\n\t\t\t\ts += \" (e.g. \" + dmin + \") for some states. \";\n\t\t\t\ts += \"Perhaps some of the updates give out-of-range values. \";\n\t\t\t\ts += \"One possible solution is to strengthen the guard\";\n\t\t\t\tthrow new PrismLangException(s, command);\n\t\t\t}\n\t\t\tif (modelType == ModelType.CTMC && dmin <= 0) {\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\t// note can't sum to less than zero - already checked for negative rates above\n\t\t\t\tString s = \"Rates in command \" + (l+1) + \" of module \\\"\" + module.getName() + \"\\\" sum to zero for some states. \";\n\t\t\t\ts += \"Perhaps some of the updates give out-of-range values. \";\n\t\t\t\ts += \"One possible solution is to strengthen the guard\";\n\t\t\t\tthrow new PrismLangException(s, command);\n\t\t\t}\n\t\t\t// check max sums - 1 (ish) for dtmcs/mdps, infinity for ctmcs\n\t\t\tif (modelType != ModelType.CTMC && !PrismUtils.doublesAreEqual(dmax, 1.0)) {\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\tString s = \"Probabilities in command \" + (l+1) + \" of module \\\"\" + module.getName() + \"\\\" sum to more than one\";\n\t\t\t\ts += \" (e.g. \" + dmax + \") for some states. \";\n\t\t\t\ts += \"Perhaps the guard needs to be strengthened\";\n\t\t\t\tthrow new PrismLangException(s, command);\n\t\t\t}\n\t\t\tif (modelType == ModelType.CTMC && Double.isInfinite(dmax)) {\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\tString s = \"Rates in command \" + (l+1) + \" of module \\\"\" + module.getName() + \"\\\" sum to infinity for some states. \";\n\t\t\t\ts += \"Perhaps the guard needs to be strengthened\";\n\t\t\t\tthrow new PrismLangException(s, command);\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t}\n\t}\n\n\t/**\n\t * Go thru guard/updates dds for all commands of a prob. module and combine.\n\t * Also check for any guard overlaps, etc...\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param m the module index\n\t * @param commandsDDs array of command dds (guard and updates)\n\t */\n\tprivate ComponentDDs combineCommandsProb(int m, CommandDDs[] commandsDDs)\n\t{\n\t\tComponentDDs compDDs;\n\t\tint i;\n\t\tJDDNode covered, transDD, tmp;\n\t\t\n\t\t// create object to return result\n\t\tcompDDs = new ComponentDDs();\n\t\t\n\t\t// use 'transDD' to build up MTBDD for transitions\n\t\ttransDD = JDD.Constant(0);\n\t\t// use 'covered' to track states covered by guards\n\t\tcovered = JDD.Constant(0);\n\t\t// loop thru commands...\n\t\tint numCommands = commandsDDs.length;\n\t\tfor (i = 0; i < numCommands; i++) {\n\t\t\tJDDNode guardDD = commandsDDs[i].guard;\n\t\t\tJDDNode upDD = commandsDDs[i].up;\n\n\t\t\t// do nothing if guard is empty\n\t\t\tif (guardDD.equals(JDD.ZERO)) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\t// check if command overlaps with previous ones\n\t\t\ttmp = JDD.And(guardDD.copy(), covered.copy());\n\t\t\tif (!(tmp.equals(JDD.ZERO))) {\n\t\t\t\t// if so, output a warning (but carry on regardless)\n\t\t\t\tmainLog.printWarning(\"Guard for command \" + (i+1) + \" of module \\\"\"\n\t\t\t\t\t+ moduleNames[m] + \"\\\" overlaps with previous commands.\");\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t\t// add this command's guard to 'covered'\n\t\t\tcovered = JDD.Or(covered, guardDD.copy());\n\t\t\t// add transitions\n\t\t\ttransDD = JDD.Plus(transDD, JDD.Times(guardDD.copy(), upDD.copy()));\n\t\t}\n\t\t\n\t\t// store result\n\t\tcompDDs.guards = covered;\n\t\tcompDDs.trans = transDD;\n\t\tcompDDs.min = 0;\n\t\tcompDDs.max = 0;\n\t\t\n\t\treturn compDDs;\n\t}\n\n\t/**\n\t * Go thru guard/updates dds for all commands of a stoch. module and combine.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param m the module index\n\t * @param commandsDDs array of command dds (guard and updates)\n\t */\n\tprivate ComponentDDs combineCommandsStoch(int m, CommandDDs[] commandsDDs)\n\t{\n\t\tComponentDDs compDDs;\n\t\tint i;\n\t\tJDDNode covered, transDD;\n\t\t\n\t\t// create object to return result\n\t\tcompDDs = new ComponentDDs();\n\t\t\n\t\t// use 'transDD 'to build up MTBDD for transitions\n\t\ttransDD = JDD.Constant(0);\n\t\t// use 'covered' to track states covered by guards\n\t\tcovered = JDD.Constant(0);\n\t\t\n\t\t// loop thru commands...\n\t\tint numCommands = commandsDDs.length;\n\t\tfor (i = 0; i < numCommands; i++) {\n\t\t\tJDDNode guardDD = commandsDDs[i].guard;\n\t\t\tJDDNode upDD = commandsDDs[i].up;\n\n\t\t\t// do nothing if guard is empty\n\t\t\tif (guardDD.equals(JDD.ZERO)) {\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\t// add this command's guard to 'covered'\n\t\t\tcovered = JDD.Or(covered, guardDD.copy());\n\t\t\t// add transitions\n\t\t\ttransDD = JDD.Plus(transDD, JDD.Times(guardDD.copy(), upDD.copy()));\n\t\t}\n\t\t\n\t\t// store result\n\t\tcompDDs.guards = covered;\n\t\tcompDDs.trans = transDD;\n\t\tcompDDs.min = 0;\n\t\tcompDDs.max = 0;\n\t\t\n\t\treturn compDDs;\n\t}\n\n\t/**\n\t * Go thru guard/updates dds for all commands of a non-det. module,\n\t * work out guard overlaps and sort out non determinism accordingly.\n\t * (non recursive version)\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param m the module index\n\t * @param commandsDDs array of command dds (guard and updates)\n\t * @param synchMin the minimal synch variable that can be used for this module\n\t */\n\tprivate ComponentDDs combineCommandsNondet(int m, CommandDDs[] commandsDDs, int synchMin) throws PrismException\n\t{\n\t\tComponentDDs compDDs;\n\t\tint i, j, k, maxChoices, numDDChoiceVarsUsed;\n\t\tJDDNode covered, transDD, overlaps, equalsi, tmp, tmp2, tmp3;\n\t\tJDDNode[] transDDbits, frees;\n\t\tJDDVars ddChoiceVarsUsed;\n\t\t\n\t\t// create object to return result\n\t\tcompDDs = new ComponentDDs();\n\t\t\n\t\t// use 'transDD' to build up MTBDD for transitions\n\t\ttransDD = JDD.Constant(0);\n\t\t// use 'covered' to track states covered by guards\n\t\tcovered = JDD.Constant(0);\n\n\t\tint numCommands = commandsDDs.length;\n\n\t\t// find overlaps in guards by adding them all up\n\t\toverlaps = JDD.Constant(0);\n\t\tfor (i = 0; i < numCommands; i++) {\n\t\t\tJDDNode guardDD = commandsDDs[i].guard;\n\t\t\toverlaps = JDD.Plus(overlaps, guardDD.copy());\n\t\t\t// compute bdd of all guards at same time\n\t\t\tcovered = JDD.Or(covered, guardDD.copy());\n\t\t}\n\t\t\n\t\t// find the max number of overlaps\n\t\t// (i.e. max number of nondet. choices)\n\t\tmaxChoices = (int)Math.round(JDD.FindMax(overlaps));\n\t\t\n\t\t// if all the guards were false, we're done already\n\t\tif (maxChoices == 0) {\n\t\t\tcompDDs.guards = covered;\n\t\t\tcompDDs.trans = transDD;\n\t\t\tcompDDs.min = synchMin;\n\t\t\tcompDDs.max = synchMin;\n\t\t\tJDD.Deref(overlaps);\n\t\t\treturn compDDs;\n\t\t}\n\t\t\n\t\t// likewise, if there are no overlaps, it's also pretty easy\n\t\tif (maxChoices == 1) {\n\t\t\t// add up dds for all commands\n\t\t\tfor (i = 0; i < numCommands; i++) {\n\t\t\t\tJDDNode guardDD = commandsDDs[i].guard;\n\t\t\t\tJDDNode upDD = commandsDDs[i].up;\n\t\t\t\t// add up transitions\n\t\t\t\ttransDD = JDD.Plus(transDD, JDD.Times(guardDD.copy(), upDD.copy()));\n\t\t\t}\n\t\t\tcompDDs.guards = covered;\n\t\t\tcompDDs.trans = transDD;\n\t\t\tcompDDs.min = synchMin;\n\t\t\tcompDDs.max = synchMin;\n\t\t\tJDD.Deref(overlaps);\t\n\t\t\treturn compDDs;\n\t\t}\n\t\t\n\t\t// otherwise, it's a bit more complicated...\n\t\t\n\t\t// first, calculate how many dd vars will be needed\n\t\tnumDDChoiceVarsUsed = (int)Math.ceil(PrismUtils.log2(maxChoices));\n\t\t\n\t\t// select the variables we will use and put them in a JDDVars\n\t\tddChoiceVarsUsed = new JDDVars();\n\t\tfor (i = 0; i < numDDChoiceVarsUsed; i++) {\n\t\t\tif (ddChoiceVars.length-synchMin-numDDChoiceVarsUsed+i < 0)\n\t\t\t\tthrow new PrismException(\"Insufficient BDD variables allocated for nondeterminism - please report this as a bug. Thank you.\");\n\t\t\tddChoiceVarsUsed.addVar(ddChoiceVars[ddChoiceVars.length-synchMin-numDDChoiceVarsUsed+i]);\n\t\t}\n\t\t\n\t\t// for each i (i = 1 ... max number of nondet. choices)\n\t\tfor (i = 1; i <= maxChoices; i++) {\n\t\t\t\n\t\t\t// find sections of state space\n\t\t\t// which have exactly i nondet. choices in this module\n\t\t\tequalsi = JDD.Equals(overlaps.copy(), (double)i);\n\t\t\t// if there aren't any for this i, skip the iteration\n\t\t\tif (equalsi.equals(JDD.ZERO)) {\n\t\t\t\tJDD.Deref(equalsi);\n\t\t\t\tcontinue;\n\t\t\t}\n\t\t\t\n\t\t\t// create arrays of size i to store dds\n\t\t\ttransDDbits = new JDDNode[i];\n\t\t\tfrees = new JDDNode[i];\n\t\t\tfor (j = 0; j < i; j++) {\n\t\t\t\ttransDDbits[j] = JDD.Constant(0);\n\t\t\t\tfrees[j] = equalsi.copy();\n\t\t\t}\n\t\t\t\n\t\t\t// go thru each command of the module...\n\t\t\tfor (j = 0; j < numCommands; j++) {\n\t\t\t\tJDDNode guardDD = commandsDDs[j].guard;\n\t\t\t\tJDDNode upDD = commandsDDs[j].up;\n\t\t\t\t\n\t\t\t\t// see if this command's guard overlaps with 'equalsi'\n\t\t\t\ttmp = JDD.And(guardDD.copy(), equalsi.copy());\n\t\t\t\t// if it does...\n\t\t\t\tif (!tmp.equals(JDD.ZERO)) {\n\t\t\t\t\t\n\t\t\t\t\t// split it up into nondet. choices as necessary\n\t\t\t\t\t\n\t\t\t\t\ttmp2 = tmp.copy();\n\t\t\t\t\t\n\t\t\t\t\t// for each possible nondet. choice (1...i) involved...\n\t\t\t\t\tfor (k = 0; k < i; k ++) {\n\t\t\t\t\t\t// see how much of the command can go in nondet. choice k\n\t\t\t\t\t\ttmp3 = JDD.And(tmp2.copy(), frees[k].copy());\n\t\t\t\t\t\t// if some will fit in...\n\t\t\t\t\t\tif (!tmp3.equals(JDD.ZERO)) {\n\t\t\t\t\t\t\tfrees[k] = JDD.And(frees[k], JDD.Not(tmp3.copy()));\n\t\t\t\t\t\t\ttransDDbits[k] = JDD.Plus(transDDbits[k], JDD.Times(tmp3.copy(), upDD.copy()));\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// take out the bit just put in this choice\n\t\t\t\t\t\ttmp2 = JDD.And(tmp2, JDD.Not(tmp3));\n\t\t\t\t\t\tif (tmp2.equals(JDD.ZERO)) {\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tJDD.Deref(tmp2);\n\t\t\t\t}\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t}\n\t\t\t\n\t\t\t// now add the nondet. choices for this value of i\n\t\t\tfor (j = 0; j < i; j++) {\n\t\t\t\ttmp = JDD.SetVectorElement(JDD.Constant(0), ddChoiceVarsUsed, j, 1);\n\t\t\t\ttransDD = JDD.Plus(transDD, JDD.Times(tmp, transDDbits[j]));\n\t\t\t\tJDD.Deref(frees[j]);\n\t\t\t}\n\t\t\t\n\t\t\t// take the i bits out of 'overlaps'\n\t\t\toverlaps = JDD.Times(overlaps, JDD.Not(equalsi));\n\t\t}\n\t\tJDD.Deref(overlaps);\n\t\t\n\t\t// store result\n\t\tcompDDs.guards = covered;\n\t\tcompDDs.trans = transDD;\n\t\tcompDDs.min = synchMin;\n\t\tcompDDs.max = synchMin + numDDChoiceVarsUsed;\n\t\t\n\t\treturn compDDs;\n\t}\n\n\t/**\n\t * Translate the updates part of a command.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param m the module index\n\t * @param l the command index inside the module\n\t * @param u the updates AST element\n\t * @param synch true if this command is synchronising (named action)\n\t * @param guard the guard\n\t */\n\tprivate UpdateDDs translateUpdates(int m, int l, Updates u, boolean synch, JDDNode guard) throws PrismException\n\t{\n\t\tint i, n;\n\t\tExpression p;\n\t\tJDDNode dd, udd, pdd = null;\n\t\tUpdateDDs updateDDs;\n\t\tboolean warned;\n\t\tString msg;\n\t\t\n\t\t// sum up over possible updates\n\t\tdd = JDD.Constant(0);\n\t\tn = u.getNumUpdates();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\t// translate a single update\n\t\t\ttry {\n\t\t\t\tupdateDDs = translateUpdate(m, u.getUpdate(i), synch, guard);\n\t\t\t\tudd = updateDDs.up;\n\t\t\t} catch (Exception|StackOverflowError e) {\n\t\t\t\tJDD.Deref(dd);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t\t// check for zero update\n\t\t\twarned = false;\n\t\t\tif (udd.equals(JDD.ZERO)) {\n\t\t\t\twarned = true;\n\t\t\t\t// Use a PrismLangException to get line numbers displayed\n\t\t\t\tmsg = \"Update \" + (i+1) + \" of command \" + (l+1);\n\t\t\t\tmsg += \" of module \\\"\" + moduleNames[m] + \"\\\" doesn't do anything\";\n\t\t\t\tmainLog.printWarning(new PrismLangException(msg, u.getUpdate(i)).getMessage());\n\t\t\t}\n\t\t\t// multiply by probability/rate\n\t\t\tp = u.getProbability(i);\n\t\t\tif (p == null) p = Expression.Double(1.0);\n\t\t\ttry {\n\t\t\t\tpdd = translateExpression(p);\n\t\t\t} catch (Exception|StackOverflowError e) {\n\t\t\t\tJDD.Deref(dd, udd);\n\t\t\t\tJDD.DerefNonNull(pdd);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t\tudd = JDD.Times(udd, pdd);\n\t\t\t// check (again) for zero update\n\t\t\tif (!warned && udd.equals(JDD.ZERO)) {\n\t\t\t\t// Use a PrismLangException to get line numbers displayed\n\t\t\t\tmsg = \"Update \" + (i+1) + \" of command \" + (l+1);\n\t\t\t\tmsg += \" of module \\\"\" + moduleNames[m] + \"\\\" doesn't do anything\";\n\t\t\t\tmainLog.printWarning(new PrismLangException(msg, u.getUpdate(i)).getMessage());\n\t\t\t}\n\t\t\tdd = JDD.Plus(dd, udd);\n\t\t}\n\t\t\n\t\treturn new UpdateDDs(dd);\n\t}\n\n\t/**\n\t * Translate an update.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param m the module index\n\t * @param c the update AST element\n\t * @param synch true if this command is synchronising (named action)\n\t * @param guard the guard\n\t */\n\tprivate UpdateDDs translateUpdate(int m, Update c, boolean synch, JDDNode guard) throws PrismException\n\t{\n\t\tint n;\n\t\t\n\t\t// clear varsUsed flag array to indicate no vars used yet\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tvarsUsed[i] = false;\n\t\t}\n\t\t// take product of clauses\n\t\tJDDNode dd = JDD.Constant(1);\n\t\tn = c.getNumElements();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\ttry {\n\t\t\t\tUpdateDDs udd = translateUpdateElement(m, c, i, synch, guard);\n\t\t\t\tdd = JDD.Times(dd, udd.up);\n\t\t\t} catch (Exception|StackOverflowError e) {\n\t\t\t\tJDD.Deref(dd);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\t\t// if a variable from this module or a global variable\n\t\t// does not appear in this update assume it does not change value\n\t\t// so multiply by its identity matrix\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tif ((varList.getModule(i) == m || varList.getModule(i) == -1) && !varsUsed[i]) {\n\t\t\t\tdd = JDD.Times(dd, varIdentities[i].copy());\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn new UpdateDDs(dd);\n\t}\n\n\t/**\n\t * Translate a single update element, i.e., (x'=...) in an update.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param m the module index\n\t * @param c the Update AST element\n\t * @param i the element index for the update element in c\n\t * @param synch true if this command is synchronising (named action)\n\t * @param guard the guard for this command\n\t */\n\tprivate UpdateDDs translateUpdateElement(int m, Update c, int i, boolean synch, JDDNode guard) throws PrismException\n\t{\n\t\t// get variable\n\t\tString s = c.getVar(i);\n\t\tint v = varList.getIndex(s);\n\t\tif (v == -1) {\n\t\t\tthrow new PrismLangException(\"Unknown variable \\\"\" + s + \"\\\" in update\", c.getVarIdent(i));\n\t\t}\n\t\tvarsUsed[v] = true;\n\t\t// check if the variable to be modified is valid\n\t\t// (i.e. belongs to this module or is global)\n\t\tif (varList.getModule(v) != -1 && varList.getModule(v) != m) {\n\t\t\tthrow new PrismLangException(\"Cannot modify variable \\\"\" + s + \"\\\" from module \\\"\" + moduleNames[m] + \"\\\"\", c.getVarIdent(i));\n\t\t}\n\t\t// print out a warning if this update is in a command with a synchronising\n\t\t// action AND it modifies a global variable\n\t\tif (varList.getModule(v) == -1 && synch) {\n\t\t\tthrow new PrismLangException(\"Synchronous command cannot modify global variable\", c.getVarIdent(i));\n\t\t}\n\t\t// get some info on the variable\n\t\tint l = varList.getLow(v);\n\t\tint h = varList.getHigh(v);\n\t\t// create dd\n\t\tJDDNode tmp1 = JDD.Constant(0);\n\t\tfor (int j = l; j <= h; j++) {\n\t\t\ttmp1 = JDD.SetVectorElement(tmp1, varDDColVars[v], j - l, j);\n\t\t}\n\t\tJDDNode tmp2 = translateExpression(c.getExpression(i));\n\t\ttmp2 = JDD.Times(tmp2, guard.copy());\n\t\tJDDNode cl = JDD.Apply(JDD.EQUALS, tmp1, tmp2);\n\t\tcl = JDD.Times(cl, guard.copy());\n\t\t// filter out bits not in range\n\t\tcl = JDD.Times(cl, varColRangeDDs[v].copy());\n\t\tcl = JDD.Times(cl, range.copy());\n\n\t\treturn new UpdateDDs(cl);\n\t}\n\n\t/**\n\t * Translate an arbitrary expression.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t * @param e the expression (AST element)\n\t */\n\tprivate JDDNode translateExpression(Expression e) throws PrismException\n\t{\n\t\t// pass this work onto the Expression2MTBDD object\n\t\t// states of interest = JDD.ONE = true = all possible states\n\t\treturn expr2mtbdd.checkExpressionDD(e, JDD.ONE.copy());\n\t}\n\n\t// build state and transition rewards\n\t\n\tprivate void computeRewards(SystemDDs sysDDs) throws PrismException\n\t{\n\t\tRewardStruct rs;\n\t\tint i, j, k, n;\n\t\tdouble d;\n\t\tString synch, s;\n\t\tJDDNode rewards, states, item;\n\t\tComponentDDs compDDs;\n\t\t\n\t\t// how many reward structures?\n\t\tnumRewardStructs = modulesFile.getNumRewardStructs();\n\t\t\n\t\t// initially rewards zero\n\t\tstateRewards = new JDDNode[numRewardStructs];\n\t\ttransRewards = new JDDNode[numRewardStructs];\n\t\tfor (j = 0; j < numRewardStructs; j++) {\n\t\t\tstateRewards[j] = JDD.Constant(0);\n\t\t\tsysDDs.ind.rewards[j] = JDD.Constant(0);\n\t\t\tfor (i = 0; i < numSynchs; i++) sysDDs.synchs[i].rewards[j] = JDD.Constant(0);\n\t\t}\n\t\t\n\t\t// for each reward structure...\n\t\tfor (j = 0; j < numRewardStructs; j++) {\n\t\t\t\n\t\t\t// get reward struct\n\t\t\trs = modulesFile.getRewardStruct(j);\n\t\t\t\n\t\t\t// work through list of items in reward struct\n\t\t\tn = rs.getNumItems();\n\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\n\t\t\t\t// translate states predicate and reward expression\n\t\t\t\tstates = translateExpression(rs.getStates(i));\n\t\t\t\trewards = translateExpression(rs.getReward(i));\n\t\t\t\t\n\t\t\t\t// first case: item corresponds to state rewards\n\t\t\t\tsynch = rs.getSynch(i);\n\t\t\t\tif (synch == null) {\n\t\t\t\t\t// restrict rewards to relevant states\n\t\t\t\t\titem = JDD.Times(states, rewards);\n\t\t\t\t\t// check for infinite/NaN/negative rewards\n\t\t\t\t\tdouble dmin = JDD.FindMin(item);\n\t\t\t\t\tdouble dmax = JDD.FindMax(item);\n\t\t\t\t\tif (!Double.isFinite(dmin)) {\n\t\t\t\t\t\ts = \"Reward structure item contains non-finite rewards (\" + dmin + \").\";\n\t\t\t\t\t\ts += \"\\nNote that these may correspond to states which are unreachable.\";\n\t\t\t\t\t\ts += \"\\nIf this is the case, try strengthening the predicate.\";\n\t\t\t\t\t\tthrow new PrismLangException(s, rs.getRewardStructItem(i));\n\t\t\t\t\t}\n\t\t\t\t\tif (!Double.isFinite(dmax)) {\n\t\t\t\t\t\ts = \"Reward structure item contains non-finite rewards (\" + dmax + \").\";\n\t\t\t\t\t\ts += \"\\nNote that these may correspond to states which are unreachable.\";\n\t\t\t\t\t\ts += \"\\nIf this is the case, try strengthening the predicate.\";\n\t\t\t\t\t\tthrow new PrismLangException(s, rs.getRewardStructItem(i));\n\t\t\t\t\t}\n\t\t\t\t\t/*if (dmin < 0) {\n\t\t\t\t\t\ts = \"Reward structure item contains negative rewards (\" + dmin + \").\";\n\t\t\t\t\t\ts += \"\\nNote that these may correspond to states which are unreachable.\";\n\t\t\t\t\t\ts += \"\\nIf this is the case, try strengthening the predicate.\";\n\t\t\t\t\t\tthrow new PrismLangException(s, rs.getRewardStructItem(i));\n\t\t\t\t\t}*/\n\t\t\t\t\t// add to state rewards\n\t\t\t\t\tstateRewards[j] = JDD.Plus(stateRewards[j], item);\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// second case: item corresponds to transition rewards\n\t\t\t\telse {\n\t\t\t\t\t// work out which (if any) action this is for\n\t\t\t\t\tif (\"\".equals(synch)) {\n\t\t\t\t\t\tcompDDs = sysDDs.ind;\n\t\t\t\t\t} else if ((k = synchs.indexOf(synch)) != -1) {\n\t\t\t\t\t\tcompDDs = sysDDs.synchs[k];\n\t\t\t\t\t} else {\n\t\t\t\t\t\tthrow new PrismLangException(\"Invalid action name \\\"\" + synch + \"\\\" in reward structure item\", rs.getRewardStructItem(i));\n\t\t\t\t\t}\n\t\t\t\t\t// identify corresponding transitions\n\t\t\t\t\t// (for dtmcs/ctmcs, keep actual values - need to weight rewards; for mdps just store 0/1)\n\t\t\t\t\tif (modelType == ModelType.MDP) {\n\t\t\t\t\t\titem = JDD.GreaterThan(compDDs.trans.copy(), 0);\n\t\t\t\t\t} else {\n\t\t\t\t\t\titem = compDDs.trans.copy();\n\t\t\t\t\t}\n\t\t\t\t\t// restrict to relevant states\n\t\t\t\t\titem = JDD.Times(item, states);\n\t\t\t\t\t// multiply by reward values\n\t\t\t\t\titem = JDD.Times(item, rewards);\n\t\t\t\t\t// check for infinite/NaN/negative rewards\n\t\t\t\t\tdouble dmin = JDD.FindMin(item);\n\t\t\t\t\tdouble dmax = JDD.FindMax(item);\n\t\t\t\t\tif (!Double.isFinite(dmin)) {\n\t\t\t\t\t\ts = \"Reward structure item contains non-finite rewards (\" + dmin + \").\";\n\t\t\t\t\t\ts += \"\\nNote that these may correspond to states which are unreachable.\";\n\t\t\t\t\t\ts += \"\\nIf this is the case, try strengthening the predicate.\";\n\t\t\t\t\t\tthrow new PrismLangException(s, rs.getRewardStructItem(i));\n\t\t\t\t\t}\n\t\t\t\t\tif (!Double.isFinite(dmax)) {\n\t\t\t\t\t\ts = \"Reward structure item contains non-finite rewards (\" + dmax + \").\";\n\t\t\t\t\t\ts += \"\\nNote that these may correspond to states which are unreachable.\";\n\t\t\t\t\t\ts += \"\\nIf this is the case, try strengthening the predicate.\";\n\t\t\t\t\t\tthrow new PrismLangException(s, rs.getRewardStructItem(i));\n\t\t\t\t\t}\n\t\t\t\t\t/*if (dmin < 0) {\n\t\t\t\t\t\ts = \"Reward structure item contains negative rewards (\" + dmin + \").\";\n\t\t\t\t\t\ts += \"\\nNote that these may correspond to states which are unreachable.\";\n\t\t\t\t\t\ts += \"\\nIf this is the case, try strengthening the predicate.\";\n\t\t\t\t\t\tthrow new PrismLangException(s, rs.getRewardStructItem(i));\n\t\t\t\t\t}*/\n\t\t\t\t\t// add result to rewards\n\t\t\t\t\tcompDDs.rewards[j] = JDD.Plus(compDDs.rewards[j], item);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// calculate dd for initial state(s)\n\t\n\tprivate void buildInitialStates() throws PrismException\n\t{\n\t\tint i;\n\t\tJDDNode tmp;\n\t\t\n\t\t// first, handle case where multiple initial states specified with init...endinit\n\t\tif (modulesFile.getInitialStates() != null) {\n\t\t\tstart = translateExpression(modulesFile.getInitialStates());\n\t\t\tJDD.Ref(range);\n\t\t\tstart = JDD.And(start, range);\n\t\t\tif (start.equals(JDD.ZERO)) throw new PrismLangException(\"No initial states: \\\"init\\\" construct evaluates to false\", modulesFile.getInitialStates());\n\t\t}\n\t\t// second, handle case where initial state determined by init values for variables\n\t\telse {\n\t\t\tstart = JDD.Constant(1);\n\t\t\tfor (i = 0; i < numVars; i++) {\n\t\t\t\tObject startObj = modulesFile.getVarDeclaration(i).getStartOrDefault().evaluate(constantValues);\n\t\t\t\ttry {\n\t\t\t\t\tint startInt = varList.encodeToInt(i, startObj);\n\t\t\t\t\ttmp = JDD.SetVectorElement(JDD.Constant(0), varDDRowVars[i], startInt, 1);\n\t\t\t\t\tstart = JDD.And(start, tmp);\n\t\t\t\t} catch (PrismLangException e) {\n\t\t\t\t\t// attach initial value spec for better error reporting\n\t\t\t\t\te.setASTElement(modulesFile.getVarDeclaration(i).getStart());\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t// symmetrification\n\t\n\tprivate void doSymmetry(ModelSymbolic model) throws PrismException\n\t{\n\t\tJDDNode tmp, transNew, reach, trans, transRewards[];\n\t\tint i, j, k, numSwaps;\n\t\tboolean done;\n\t\tlong clock;\n\t\tString ss[];\n\t\t\n\t\t// parse symmetry reduction parameters\n\t\tss = settings.getString(PrismSettings.PRISM_SYMM_RED_PARAMS).split(\" \");\n\t\tif (ss.length != 2) throw new PrismException (\"Invalid parameters for symmetry reduction\");\n\t\ttry {\n\t\t\tnumModulesBeforeSymm = Integer.parseInt(ss[0].trim());\n\t\t\tnumModulesAfterSymm = Integer.parseInt(ss[1].trim());\n\t\t}\n\t\tcatch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Invalid parameters for symmetry reduction\");\n\t\t}\n\n\t\tclock = System.currentTimeMillis();\n\t\t\n\t\t// get a copies of model (MT)BDDs\n\t\treach = model.getReach();\n\t\tJDD.Ref(reach);\n\t\ttrans =  model.getTrans();\n\t\tJDD.Ref(trans);\n\t\ttransRewards = new JDDNode[numRewardStructs];\n\t\tfor (i = 0; i < numRewardStructs; i++) {\n\t\t\ttransRewards[i] =  model.getTransRewards(i);\n\t\t\tJDD.Ref(transRewards[i]);\n\t\t}\n\t\t\n\t\tmainLog.print(\"\\nApplying symmetry reduction...\\n\");\n\t\t\n\t\t//identifySymmetricModules();\n\t\tnumSymmModules = numModules - (numModulesBeforeSymm + numModulesAfterSymm);\n\t\tcomputeSymmetryFilters(reach);\n\t\t\n\t\t// compute number of local states\n// \t\tJDD.Ref(reach);\n// \t\ttmp = reach;\n// \t\tfor (i = 0; i < numModules; i++) {\n// \t\t\tif (i != numModulesBeforeSymm) tmp = JDD.ThereExists(tmp, moduleDDRowVars[i]);\n// \t\t}\n// \t\ttmp = JDD.ThereExists(tmp, globalDDRowVars);\n// \t\tmainLog.println(\"Local states: \" + (int)JDD.GetNumMinterms(tmp, moduleDDRowVars[numModulesBeforeSymm].n()));\n// \t\tJDD.Deref(tmp);\n\t\t\n\t\t//ODDNode odd = ODDUtils.BuildODD(reach, allDDRowVars);\n\t\t//try {sparse.PrismSparse.NondetExport(trans, allDDRowVars, allDDColVars, allDDNondetVars, odd, Prism.EXPORT_PLAIN, \"trans-full.tra\"); } catch (FileNotFoundException e) {}\n\t\t\n\t\tmainLog.println(\"\\nNumber of states before before symmetry reduction: \" + model.getNumStatesString());\n\t\tmainLog.println(\"DD sizes before symmetry reduction:\");\n\t\t\n\t\t// trans - rows\n\t\tmainLog.print(\"trans: \");\n\t\tmainLog.println(JDD.GetInfoString(trans, (modelType==ModelType.MDP)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\tJDD.Ref(symm);\n\t\ttrans = JDD.Apply(JDD.TIMES, trans, symm);\n\t\t//mainLog.print(\"trans (symm): \");\n\t\t//mainLog.println(JDD.GetInfoString(trans, (type==ModulesFile.NONDETERMINISTIC)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t\n\t\t// trans rewards - rows\n\t\tfor (k = 0; k < numRewardStructs; k++) {\n\t\t\tmainLog.print(\"transrew[\"+k+\"]: \");\n\t\t\tmainLog.println(JDD.GetInfoString(transRewards[k], (modelType==ModelType.MDP)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t\tJDD.Ref(symm);\n\t\t\ttransRewards[k] = JDD.Apply(JDD.TIMES, transRewards[k], symm);\n\t\t\t//mainLog.print(\"transrew[\"+k+\"] (symm): \");\n\t\t\t//mainLog.println(JDD.GetInfoString(transRewards[k], (type==ModulesFile.NONDETERMINISTIC)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t}\n\t\t\n\t\tmainLog.println(\"Starting quicksort...\");\n\t\tdone = false;\n\t\tnumSwaps = 0;\n\t\tfor (i = numSymmModules; i > 1 && !done; i--) {\n\t\t\t// store trans from previous iter\n\t\t\tJDD.Ref(trans);\n\t\t\ttransNew = trans;\n\t\t\tfor (j = 0; j < i-1; j++) {\n\t\t\t\t\n\t\t\t\t// are there any states where j+1>j+2?\n\t\t\t\tif (nonSymms[j].equals(JDD.ZERO)) continue;\n\t\t\t\t\n\t\t\t\t// identify offending block in trans\n\t\t\t\tJDD.Ref(transNew);\n\t\t\t\tJDD.Ref(nonSymms[j]);\n\t\t\t\ttmp = JDD.Apply(JDD.TIMES, transNew, JDD.PermuteVariables(nonSymms[j], allDDRowVars, allDDColVars));\n\t\t\t\t//mainLog.print(\"bad block: \");\n\t\t\t\t//mainLog.println(JDD.GetInfoString(tmp, (type==ModulesFile.NONDETERMINISTIC)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t\t\t\n\t\t\t\tif (tmp.equals(JDD.ZERO)) { JDD.Deref(tmp); continue; }\n\t\t\t\tnumSwaps++;\n\t\t\t\tmainLog.println(\"Iteration \"+(numSymmModules-i+1)+\".\"+(j+1));\n\t\t\t\t\n\t\t\t\t// swap\n\t\t\t\ttmp = JDD.SwapVariables(tmp, moduleDDColVars[numModulesBeforeSymm+j], moduleDDColVars[numModulesBeforeSymm+j+1]);\n\t\t\t\t//mainLog.print(\"bad block (swapped): \");\n\t\t\t\t//mainLog.println(JDD.GetInfoString(tmp, (type==ModulesFile.NONDETERMINISTIC)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t\t\t\n\t\t\t\t// insert swapped block\n\t\t\t\tJDD.Ref(nonSymms[j]);\n\t\t\t\tJDD.Ref(tmp);\n\t\t\t\ttransNew = JDD.ITE(JDD.PermuteVariables(nonSymms[j], allDDRowVars, allDDColVars), JDD.Constant(0), JDD.Apply(JDD.PLUS, transNew, tmp));\n\t\t\t\t//mainLog.print(\"trans (symm): \");\n\t\t\t\t//mainLog.println(JDD.GetInfoString(transNew, (type==ModulesFile.NONDETERMINISTIC)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\t\n\t\t\t\tfor (k = 0; k < numRewardStructs; k++) {\n\t\t\t\t\t// identify offending block in trans rewards\n\t\t\t\t\tJDD.Ref(transRewards[k]);\n\t\t\t\t\tJDD.Ref(nonSymms[j]);\n\t\t\t\t\ttmp = JDD.Apply(JDD.TIMES, transRewards[k], JDD.PermuteVariables(nonSymms[j], allDDRowVars, allDDColVars));\n\t\t\t\t\t//mainLog.print(\"bad block: \");\n\t\t\t\t\t//mainLog.println(JDD.GetInfoString(tmp, (type==ModulesFile.NONDETERMINISTIC)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t\t\t\t\n\t\t\t\t\t// swap\n\t\t\t\t\ttmp = JDD.SwapVariables(tmp, moduleDDColVars[numModulesBeforeSymm+j], moduleDDColVars[numModulesBeforeSymm+j+1]);\n\t\t\t\t\t//mainLog.print(\"bad block (swapped): \");\n\t\t\t\t\t//mainLog.println(JDD.GetInfoString(tmp, (type==ModulesFile.NONDETERMINISTIC)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t\t\t\t\n\t\t\t\t\t// insert swapped block\n\t\t\t\t\tJDD.Ref(nonSymms[j]);\n\t\t\t\t\tJDD.Ref(tmp);\n\t\t\t\t\ttransRewards[k] = JDD.ITE(JDD.PermuteVariables(nonSymms[j], allDDRowVars, allDDColVars), JDD.Constant(0), JDD.Apply(JDD.PLUS, transRewards[k], tmp));\n\t\t\t\t\t//mainLog.print(\"transrew[\"+k+\"] (symm): \");\n\t\t\t\t\t//mainLog.println(JDD.GetInfoString(transRewards[k], (type==ModulesFile.NONDETERMINISTIC)?(allDDRowVars.n()*2+allDDNondetVars.n()):(allDDRowVars.n()*2)));\n\t\t\t\t\tJDD.Deref(tmp);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tif (transNew.equals(trans)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tJDD.Deref(trans);\n\t\t\ttrans = transNew;\n\t\t}\n\t\t\n\t\t// reset (MT)BDDs in model\n\t\tmodel.resetTrans(trans);\n\t\tfor (i = 0; i < numRewardStructs; i++) {\n\t\t\tmodel.resetTransRewards(i, transRewards[i]);\n\t\t}\n\t\t\n\t\t// reset reach bdd, etc.\n\t\tJDD.Ref(symm);\n\t\treach = JDD.And(reach, symm);\n\t\t\n\t\tmodel.setReach(reach);\n\t\tmodel.filterReachableStates();\n\t\t\n\t\tclock = System.currentTimeMillis() - clock;\n\t\tmainLog.println(\"Symmetry complete: \" + (numSymmModules-i) + \" iterations, \" + numSwaps + \" swaps, \" + clock/1000.0 + \" seconds\");\n\t}\n\n\tprivate void computeSymmetryFilters(JDDNode reach) throws PrismException\n\t{\n\t\tint i;\n\t\tJDDNode tmp;\n\t\t\n\t\t// array for non-symmetric parts\n\t\tnonSymms = new JDDNode[numSymmModules-1];\n\t\t// dd for all symmetric states\n\t\tJDD.Ref(reach);\n\t\tsymm = reach;\n\t\t// loop through symmetric module pairs\n\t\tfor (i = 0; i < numSymmModules-1; i++) {\n\t\t\t// (locally) symmetric states, i.e. where i+1 <= i+2\n\t\t\ttmp = JDD.VariablesLessThanEquals(moduleDDRowVars[numModulesBeforeSymm+i], moduleDDRowVars[numModulesBeforeSymm+i+1]);\n\t\t\t// non-(locally)-symmetric states\n\t\t\tJDD.Ref(tmp);\n\t\t\tJDD.Ref(reach);\n\t\t\tnonSymms[i] = JDD.And(JDD.Not(tmp), reach);\n\t\t\t// all symmetric states\n\t\t\tsymm = JDD.And(symm, tmp);\n\t\t}\n\t}\n\n\t// old version of computeSymmetryFilters()\n\t/*private void computeSymmetryFilters() throws PrismException\n\t{\n\t\tint i, j, k, n;\n\t\tString varNames[][] = null;\n\t\tJDDNode tmp;\n\t\tExpression expr, exprTmp;\n\t\t\n\t\t// get var names for each symm module\n\t\tn = modulesFile.getModule(numModulesBeforeSymm).getNumDeclarations();\n\t\tvarNames = new String[numModules][];\n\t\tfor (i = numModulesBeforeSymm; i < numModulesBeforeSymm+numSymmModules; i++) {\n\t\t\tvarNames[i-numModulesBeforeSymm] = new String[n];\n\t\t\tj = 0;\n\t\t\twhile (j < numVars && varList.getModule(j) != i) j++;\n\t\t\tfor (k = 0; k < n; k++) {\n\t\t\t\tvarNames[i-numModulesBeforeSymm][k] = varList.getName(j+k);\n\t\t\t}\n\t\t}\n\t\t\n\t\t// array for non-symmetric parts\n\t\tnonSymms = new JDDNode[numSymmModules-1];\n\t\t// dd for all symmetric states\n\t\tJDD.Ref(reach);\n\t\tsymm = reach;\n\t\t// loop through symmetric module pairs\n\t\tfor (i = 0; i < numSymmModules-1; i++) {\n\t\t\t// expression for (locally) symmetric states, i.e. where i+1 <= i+2\n\t\t\texpr = new ExpressionTrue();\n\t\t\tfor (j = varNames[0].length-1; j >= 0 ; j--) {\n\t\t\t\texprTmp = new ExpressionAnd();\n\t\t\t\t((ExpressionAnd)exprTmp).addOperand(new ExpressionBrackets(new ExpressionRelOp(new ExpressionVar(varNames[i][j], 0), \"=\", new ExpressionVar(varNames[i+1][j], 0))));\n\t\t\t\t((ExpressionAnd)exprTmp).addOperand(new ExpressionBrackets(expr));\n\t\t\t\texpr = exprTmp;\n\t\t\t\texprTmp = new ExpressionOr();\n\t\t\t\t((ExpressionOr)exprTmp).addOperand(new ExpressionBrackets(new ExpressionRelOp(new ExpressionVar(varNames[i][j], 0), \"<\", new ExpressionVar(varNames[i+1][j], 0))));\n\t\t\t\t((ExpressionOr)exprTmp).addOperand(expr);\n\t\t\t\texpr = exprTmp;\n\t\t\t}\n\t\t\tmainLog.println(expr);\n\t\t\t// bdd for (locally) symmetric states, i.e. where i+1 <= i+2\n\t\t\ttmp = expr2mtbdd.translateExpression(expr);\n\t\t\t// non-(locally)-symmetric states\n\t\t\tJDD.Ref(tmp);\n\t\t\tJDD.Ref(reach);\n\t\t\tnonSymms[i] = JDD.And(JDD.Not(tmp), reach);\n\t\t\t// all symmetric states\n\t\t\tsymm = JDD.And(symm, tmp);\n\t\t}\n\t}*/\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/comp/ECComputer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Carlos S. Bederian (Universidad Nacional de Cordoba)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.util.List;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismSettings;\nimport symbolic.model.NondetModel;\n\n/**\n * Abstract class for (symbolic) classes that compute (M)ECs, i.e. (maximal) end components,\n * for a nondeterministic model such as an MDP.\n */\npublic abstract class ECComputer extends PrismComponent\n{\n\t// setting(s)\n\tprotected double sumRoundOff;\n\n\t// model info\n\tprotected JDDNode trans;\n\tprotected JDDNode trans01;\n\tprotected JDDNode reach;\n\tprotected JDDVars allDDRowVars;\n\tprotected JDDVars allDDColVars;\n\tprotected JDDVars allDDNondetVars;\n\n\t// stuff for ECs\n\tprotected List<JDDNode> mecs;\n\n\t/**\n\t * Static method to create a new ECComputer object, depending on current settings.\n\t */\n\tpublic static ECComputer createECComputer(PrismComponent parent, NondetModel model) throws PrismException\n\t{\n\t\treturn createECComputer(parent, model.getReach(), model.getTrans(), model.getTrans01(), model.getAllDDRowVars(), model.getAllDDColVars(),\n\t\t\t\tmodel.getAllDDNondetVars());\n\t}\n\n\t/**\n\t * Static method to create a new ECComputer object, depending on current settings.\n\t */\n\tpublic static ECComputer createECComputer(PrismComponent parent, JDDNode reach, JDDNode trans, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars,\n\t\t\tJDDVars allDDNondetVars) throws PrismException\n\t{\n\t\t// Only one algorithm implemented currently\n\t\treturn new ECComputerDefault(parent, reach, trans, trans01, allDDRowVars, allDDColVars, allDDNondetVars);\n\t}\n\n\t/**\n\t * Base constructor.\n\t */\n\tpublic ECComputer(PrismComponent parent, JDDNode reach, JDDNode trans, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars, JDDVars allDDNondetVars)\n\t\t\tthrows PrismException\n\t{\n\t\tsuper(parent);\n\t\tthis.reach = reach;\n\t\tthis.trans = trans;\n\t\tthis.trans01 = trans01;\n\t\tthis.allDDRowVars = allDDRowVars;\n\t\tthis.allDDColVars = allDDColVars;\n\t\tthis.allDDNondetVars = allDDNondetVars;\n\t\tsumRoundOff = settings.getDouble(PrismSettings.PRISM_SUM_ROUND_OFF);\n\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans, allDDRowVars, allDDColVars, allDDNondetVars);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, allDDRowVars, allDDColVars, allDDNondetVars);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(reach, allDDRowVars);\n\t\t}\n\t}\n\n\t/**\n\t * Compute states of all maximal end components (MECs) and store them.\n\t * They can be retrieved using {@link #getMECStates()}.\n\t * You will need to to deref these afterwards.\n\t */\n\tpublic abstract void computeMECStates() throws PrismException;\n\n\t/**\n\t * Compute states of all maximal end components (MECs) in the submodel obtained\n\t * by restricting this one to the set of states {@code restrict}, and store them.\n\t * They can be retrieved using {@link #getMECStates()}.\n\t * You will need to to deref these afterwards.\n\t * If {@code restrict} is null, we look at the whole model, not a submodel.\n\t * @param restrict BDD for the set of states to restrict to\n\t */\n\tpublic abstract void computeMECStates(JDDNode restrict) throws PrismException;\n\n\t/**\n\t * Compute states of all accepting maximal end components (MECs) in the submodel obtained\n\t * by restricting this one to the set of states {@code restrict}, and store them,\n\t * where acceptance is defined as those which intersect with {@code accept}.\n\t * They can be retrieved using {@link #getMECStates()}.\n\t * You will need to to deref these afterwards.\n\t * If {@code restrict} is null, we look at the whole model, not a submodel.\n\t * If {@code accept} is null, the acceptance condition is trivially satisfied.\n\t * @param restrict BDD for the set of states to restrict to\n\t * @param accept BDD for the set of accepting states\n\t */\n\tpublic abstract void computeMECStates(JDDNode restrict, JDDNode accept) throws PrismException;\n\n\t/**\n\t * Get the list of states for computed MECs.\n\t * You need to deref these BDDs when you are finished with them.\n\t */\n\tpublic List<JDDNode> getMECStates()\n\t{\n\t\treturn mecs;\n\t}\n\n\t/**\n\t * Returns the maximal stable set of states contained in {@code candidateStates},\n\t * i.e. the maximal subset of states which have a choice whose transitions remain in the subset.\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: candidateStates ]\n\t * @param candidateStates BDD for a set of states (over allDDRowVars)\n\t * @return A referenced BDD with the maximal stable set in candidateStates\n\t */\n\tpublic JDDNode findMaximalStableSet(JDDNode candidateStates)\n\t{\n\t\t// Store two copies to allow check for fixed point\n\t\tJDDNode current = candidateStates;\n\t\tJDDNode old = JDD.Constant(0);\n\t\t// Fixed point\n\t\twhile (!current.equals(old)) {\n\t\t\t// Remember last set\n\t\t\tJDD.Deref(old);\n\t\t\tJDD.Ref(current);\n\t\t\told = current;\n\t\t\t// Find transitions starting in current\n\t\t\tJDD.Ref(trans01);\n\t\t\tJDD.Ref(current);\n\t\t\tJDDNode currTrans = JDD.Apply(JDD.TIMES, trans01, current);\n\t\t\t// Find transitions starting in current *and* ending in current\n\t\t\tcurrent = JDD.PermuteVariables(current, allDDRowVars, allDDColVars);\n\t\t\tJDD.Ref(currTrans);\n\t\t\tJDDNode currTrans2 = JDD.Apply(JDD.TIMES, currTrans, current);\n\t\t\t// Find transitions leaving current\n\t\t\tJDD.Ref(currTrans2);\n\t\t\tcurrTrans = JDD.And(currTrans, JDD.Not(currTrans2));\n\t\t\t// Find choices leaving current\n\t\t\tcurrTrans = JDD.ThereExists(currTrans, allDDColVars);\n\t\t\t// Remove leaving choices\n\t\t\tcurrTrans2 = JDD.ThereExists(currTrans2, allDDColVars);\n\t\t\tcurrTrans2 = JDD.And(currTrans2, JDD.Not(currTrans));\n\t\t\t// Keep states with at least one choice\n\t\t\tcurrent = JDD.ThereExists(currTrans2, allDDNondetVars);\n\t\t}\n\t\tJDD.Deref(old);\n\t\treturn current;\n\t}\n\n\t/**\n\t * Returns the transition relation of a state set,\n\t * i.e., a 0-1 MTBDD over row and col variables containing\n\t * those pairs (s,t) for which there exists an alpha\n\t * with P(s,alpha,t) > 0 and all alpha-successors of\n\t * s are again in the state set.\n\t *\n\t * <br>[REFS: <i>result</i>, DEREFS: stateSet ]\n\t */\n\tpublic JDDNode getStableTransReln(JDDNode stateSet)\n\t{\n\t\treturn JDD.ThereExists(getStableTransitions(stateSet), allDDNondetVars);\n\t}\n\n\t/**\n\t * Get the set of transitions (s,alpha,t) that remain in the state set,\n\t * i.e., with a choice alpha that ensures that the successor states\n\t * are all in the state set again.\n\t *\n\t * Returns a 0/1-MTBDD over row, col and nondet vars.\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>stateSet</i> ]\n\t * @param stateSet state set DD over the row variables\n\t */\n\tpublic JDDNode getStableTransitions(JDDNode stateSet) {\n\t\t// trans01 from the state set\n\t\tJDDNode transFromSet = JDD.And(stateSet.copy(), trans01.copy());\n\t\t// ... and back to the state set\n\t\tJDDNode transToSet = JDD.And(transFromSet.copy(), JDD.PermuteVariables(stateSet.copy(), allDDRowVars, allDDColVars));\n\t\t// (s,alpha) pairs that have at least one successor back in the set\n\t\tJDDNode stateActionsToSet = JDD.ThereExists(transToSet, allDDColVars);\n\n\t\t// those transitions where at least one successor remains in set\n\t\tJDDNode candidateTrans = JDD.And(transFromSet, stateActionsToSet);\n\t\t// filter: those transitions where at least one successor goes outside the set\n\t\tJDDNode transSomewhereElse = JDD.And(candidateTrans.copy(), JDD.Not(JDD.PermuteVariables(stateSet.copy(), allDDRowVars, allDDColVars)));\n\t\t// the corresponding (s,alpha) pairs, where a successor is outside the set\n\t\tJDDNode stateActionsBad = JDD.ThereExists(transSomewhereElse, allDDColVars);\n\t\t// restrict to only those transitions where all successors are in the set\n\t\tJDDNode result = JDD.And(candidateTrans, JDD.Not(stateActionsBad));\n\n\t\tJDD.Deref(stateSet);\n\n\t\treturn result;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/symbolic/comp/ECComputerDefault.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Carlos S. Bederian (Universidad Nacional de Cordoba)\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.util.List;\nimport java.util.Stack;\nimport java.util.Vector;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismComponent;\nimport prism.PrismException;\n\n/**\n * Symbolic maximal end component computer for a nondeterministic model such as an MDP.\n */\n@SuppressWarnings(\"unused\")\npublic class ECComputerDefault extends ECComputer\n{\n\t/**\n\t * Build (M)EC computer for a given model.\n\t */\n\tpublic ECComputerDefault(PrismComponent parent, JDDNode reach, JDDNode trans, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars,\n\t\t\t\t\t\t\t JDDVars allDDNondetVars) throws PrismException\n\t{\n\t\tsuper(parent, reach, trans, trans01, allDDRowVars, allDDColVars, allDDNondetVars);\n\t}\n\n\t// Methods for ECComputer interface\n\n\t@Override\n\tpublic void computeMECStates() throws PrismException\n\t{\n\t\tmecs = findEndComponents(null, null);\n\t}\n\n\t@Override\n\tpublic void computeMECStates(JDDNode restrict) throws PrismException\n\t{\n\t\tmecs = findEndComponents(restrict, null);\n\t}\n\n\t@Override\n\tpublic void computeMECStates(JDDNode restrict, JDDNode accept) throws PrismException\n\t{\n\t\tmecs = findEndComponents(restrict, accept);\n\t}\n\n\t// Computation\n\n\t/**\n\t * Find all accepting maximal end components (MECs) in the submodel obtained\n\t * by restricting this one to the set of states {@code restrict},\n\t * where acceptance is defined as those which intersect with {@code accept}.\n\t * If {@code restrict} is null, we look at the whole model, not a submodel.\n\t * If {@code accept} is null, the acceptance condition is trivially satisfied.\n\t * @param restrict BDD for the set of states to restrict to\n\t * @param accept BDD for the set of accepting states\n\t * @return a list of (referenced) BDDs representing the MECs\n\t */\n\tprivate List<JDDNode> findEndComponents(JDDNode restrict, JDDNode accept) throws PrismException\n\t{\n\t\tVector<JDDNode> mecs = new Vector<JDDNode>();\n\t\tSCCComputer sccComputer;\n\n\t\t// Initial set of candidates for MECs just contains the whole set we are searching\n\t\t// (which, if null, is all states)\n\t\tif (restrict == null)\n\t\t\trestrict = reach;\n\t\tStack<JDDNode> candidates = new Stack<JDDNode>();\n\t\tJDD.Ref(restrict);\n\t\tcandidates.push(restrict);\n\n\t\t// Go through each candidate set\n\t\twhile (!candidates.isEmpty()) {\n\t\t\tJDDNode candidate = candidates.pop();\n\t\t\t\n\t\t\t// Compute its maximal stable set\n\t\t\tJDD.Ref(candidate);\n\t\t\tJDDNode stableSet = findMaximalStableSet(candidate);\n\t\t\t\n\t\t\t// Drop empty sets\n\t\t\tif (stableSet.equals(JDD.ZERO)) {\n\t\t\t\tJDD.Deref(stableSet);\n\t\t\t\tJDD.Deref(candidate);\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\tif (stableSet.equals(candidate) && JDD.isSingleton(stableSet, allDDRowVars)) {\n\t\t\t\tmecs.add(candidate);\n\t\t\t\tJDD.Deref(stableSet);\n\t\t\t\tcontinue;\n\t\t\t}\n\n\t\t\t// Filter bad transitions\n\t\t\tJDDNode stableSetTrans = getStableTransReln(stableSet.copy());\n\n\t\t\t// Find the maximal SCCs in (stableSet, stableSetTrans)\n\t\t\tsccComputer = SCCComputer.createSCCComputer(this, stableSet, stableSetTrans, allDDRowVars, allDDColVars);\n\t\t\tif (accept != null)\n\t\t\t\tsccComputer.computeSCCs(accept);\n\t\t\telse\n\t\t\t\tsccComputer.computeSCCs();\n\t\t\tJDD.Deref(stableSet);\n\t\t\tJDD.Deref(stableSetTrans);\n\t\t\tList<JDDNode> sccs = sccComputer.getSCCs();\n\t\t\tJDD.Deref(sccComputer.getNotInSCCs());\n\t\t\t\n\t\t\t// If there are no SCCs, do nothing \n\t\t\tif (sccs.size() == 0) {\n\t\t\t}\n\t\t\t// If the whole sub-MDP is one SCC, we found an MEC\n\t\t\telse if (sccs.size() == 1 && sccs.get(0).equals(candidate)) {\n\t\t\t\tmecs.add(sccs.get(0));\n\t\t\t}\n\t\t\t// Otherwise add SCCs as candidates and proceed\n\t\t\telse {\n\t\t\t\tcandidates.addAll(sccs);\n\t\t\t}\n\t\t\tJDD.Deref(candidate);\n\t\t}\n\t\treturn mecs;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/symbolic/comp/LTLModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Carlos S. Bederian (Universidad Nacional de Cordoba)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Vector;\n\nimport acceptance.AcceptanceBuchiDD;\nimport acceptance.AcceptanceGenRabinDD;\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceOmegaDD;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceRabinDD;\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceType;\nimport automata.DA;\nimport automata.LTL2DA;\nimport automata.LTL2WDBA;\nimport common.StopWatch;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport jltl2ba.SimpleLTL;\nimport parser.VarList;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationInt;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionBinaryOp;\nimport parser.ast.ExpressionLabel;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.type.TypeBool;\nimport parser.type.TypePathBool;\nimport prism.ModelType;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport prism.PrismUtils;\nimport symbolic.comp.ECComputer;\nimport symbolic.comp.ModelChecker;\nimport symbolic.comp.NondetModelChecker;\nimport symbolic.comp.ProbModelChecker;\nimport symbolic.comp.SCCComputer;\nimport symbolic.model.Model;\nimport symbolic.model.ModelVariablesDD;\nimport symbolic.model.NondetModel;\nimport symbolic.model.ProbModel;\nimport symbolic.model.Product;\n\n/**\n * LTL model checking functionality\n */\npublic class LTLModelChecker extends PrismComponent\n{\n\t/**\n\t * A wrapper for the product of a model (DTMC, MDP) and\n\t * a deterministic omega-automaton for some linear-temporal property.\n\t * <br>\n\t * Provides methods to obtain the product model, the acceptance condition and\n\t * for translating a result in the product back to the original model.\n\t * @param <M> the underlying model type (ProbModel, NondetModel)\n\t */\n\tpublic static class LTLProduct<M extends Model> extends Product<M>\n\t{\n\t\t/**\n\t\t * The omega-regular acceptance condition, lifted to the product model,\n\t\t * but not necessarily restricted to the product model's reachable states.\n\t\t */\n\t\tprivate AcceptanceOmegaDD acceptance;\n\n\t\t/**\n\t\t * The omega-regular acceptance condition, lifted to the product model,\n\t\t * restricted to the product model's reachable states.\n\t\t * <br>\n\t\t * Computed on demand.\n\t\t */\n\t\tprivate AcceptanceOmegaDD prodAcceptance = null;\n\n\t\t/**\n\t\t * Constructor.\n\t\t * <br>\n\t\t * Takes ownership of the product model, the acceptance condition,\n\t\t * the productStatesOfInterest and the automatonRowVars.\n\t\t * clears those when clear() is called.\n\t\t * <br>[ STORES: productModel, acceptance, productStatesOfInterest, automatonRowVars ]\n\t\t */\n\t\tpublic LTLProduct(M productModel, M originalModel, AcceptanceOmegaDD acceptance, JDDNode productStatesOfInterest, JDDVars automatonRowVars)\n\t\t{\n\t\t\tsuper(productModel, originalModel, productStatesOfInterest, automatonRowVars);\n\t\t\tthis.acceptance = acceptance;\n\t\t}\n\n\t\t/**\n\t\t * Get the acceptance condition for the product (not a copy).\n\t\t * <br>\n\t\t * The acceptance sets are not necessarily restricted to the\n\t\t * reachable part of the state space of the product model.\n\t\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic AcceptanceOmegaDD getAcceptance() {\n\t\t\treturn acceptance;\n\t\t}\n\n\n\t\t/**\n\t\t * Get the acceptance condition for the product, restricted\n\t\t * to the reachable state space of the product model (not a copy).\n\t\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t\t */\n\t\tpublic AcceptanceOmegaDD getProductAcceptance() {\n\t\t\tif (prodAcceptance == null) {\n\t\t\t\t// compute on demand, intersect with getReach() from product model\n\t\t\t\tprodAcceptance = acceptance.clone();\n\t\t\t\tprodAcceptance.intersect(getProductModel().getReach());\n\t\t\t}\n\t\t\treturn prodAcceptance;\n\t\t}\n\n\t\t/**\n\t\t * Set the acceptance condition for the product (takes\n\t\t * ownership of the provided acceptance object, clears\n\t\t * previously stored acceptance condition).\n\t\t * <br>[ STORES: acceptance ]\n\t\t */\n\t\tpublic void setAcceptance(AcceptanceOmegaDD acceptance) {\n\t\t\tif (this.acceptance != null) {\n\t\t\t\tthis.acceptance.clear();\n\t\t\t}\n\t\t\tthis.acceptance = acceptance;\n\t\t}\n\n\t\t@Override\n\t\tpublic void clear() {\n\t\t\tsuper.clear();\n\t\t\tacceptance.clear();\n\t\t\tacceptance = null;\n\t\t\tif (prodAcceptance != null) {\n\t\t\t\tprodAcceptance.clear();\n\t\t\t\tprodAcceptance = null;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Create a new LTLModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic LTLModelChecker(PrismComponent parent) throws PrismException\n\t{\n\t\tsuper(parent);\n\t}\n\n\t/**\n\t * Returns {@code true} if expression {@code expr} is a formula that can be handled by\n\t * LTLModelChecker for the given ModelType.\n\t */\n\tpublic static boolean isSupportedLTLFormula(ModelType modelType, Expression expr) throws PrismLangException\n\t{\n\t\tif (!expr.isPathFormula(true)) {\n\t\t\treturn false;\n\t\t}\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tif (modelType.continuousTime()) {\n\t\t\t\t// Only support temporal bounds for discrete time models\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\t\n\t\t\tif (!expr.isSimplePathFormula()) {\n\t\t\t\t// Only support temporal bounds for simple path formulas\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Extract maximal state formula from an LTL path formula, model check them (with passed in model checker) and\n\t * replace them with ExpressionLabel objects L0, L1, etc. Expression passed in is modified directly, but the result\n\t * is also returned. As an optimisation, expressions that results in true/false for all states are converted to an\n\t * actual true/false, and duplicate results (or their negations) reuse the same label. BDDs giving the states which\n\t * satisfy each label are put into the vector labelDDs, which should be empty when this function is called.\n\t */\n\tpublic Expression checkMaximalStateFormulas(ModelChecker mc, Model model, Expression expr, Vector<JDDNode> labelDDs) throws PrismException\n\t{\n\t\t// A state formula\n\t\tif (expr.getType() instanceof TypeBool) {\n\t\t\t// Model check\n\t\t\tJDDNode dd = mc.checkExpressionDD(expr, model.getReach().copy());\n\t\t\t// Detect special cases (true, false) for optimisation\n\t\t\tif (dd.equals(JDD.ZERO)) {\n\t\t\t\tJDD.Deref(dd);\n\t\t\t\treturn Expression.False();\n\t\t\t}\n\t\t\tif (dd.equals(model.getReach())) {\n\t\t\t\tJDD.Deref(dd);\n\t\t\t\treturn Expression.True();\n\t\t\t}\n\t\t\t// See if we already have an identical result\n\t\t\t// (in which case, reuse it)\n\t\t\tint i = labelDDs.indexOf(dd);\n\t\t\tif (i != -1) {\n\t\t\t\tJDD.Deref(dd);\n\t\t\t\treturn new ExpressionLabel(\"L\" + i);\n\t\t\t}\n\t\t\t// Also, see if we already have the negation of this result\n\t\t\t// (in which case, reuse it)\n\t\t\tJDD.Ref(dd);\n\t\t\tJDD.Ref(model.getReach());\n\t\t\tJDDNode ddNeg = JDD.And(JDD.Not(dd), model.getReach());\n\t\t\ti = labelDDs.indexOf(ddNeg);\n\t\t\tJDD.Deref(ddNeg);\n\t\t\tif (i != -1) {\n\t\t\t\tJDD.Deref(dd);\n\t\t\t\treturn Expression.Not(new ExpressionLabel(\"L\" + i));\n\t\t\t}\n\t\t\t// Otherwise, add result to list, return new label\n\t\t\tlabelDDs.add(dd);\n\t\t\treturn new ExpressionLabel(\"L\" + (labelDDs.size() - 1));\n\t\t}\n\t\t// A path formula (recurse, modify, return)\n\t\telse if (expr.getType() instanceof TypePathBool) {\n\t\t\tif (expr instanceof ExpressionBinaryOp) {\n\t\t\t\tExpressionBinaryOp exprBinOp = (ExpressionBinaryOp) expr;\n\t\t\t\texprBinOp.setOperand1(checkMaximalStateFormulas(mc, model, exprBinOp.getOperand1(), labelDDs));\n\t\t\t\texprBinOp.setOperand2(checkMaximalStateFormulas(mc, model, exprBinOp.getOperand2(), labelDDs));\n\t\t\t} else if (expr instanceof ExpressionUnaryOp) {\n\t\t\t\tExpressionUnaryOp exprUnOp = (ExpressionUnaryOp) expr;\n\t\t\t\texprUnOp.setOperand(checkMaximalStateFormulas(mc, model, exprUnOp.getOperand(), labelDDs));\n\t\t\t} else if (expr instanceof ExpressionTemporal) {\n\t\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\t\tif (exprTemp.getOperand1() != null) {\n\t\t\t\t\texprTemp.setOperand1(checkMaximalStateFormulas(mc, model, exprTemp.getOperand1(), labelDDs));\n\t\t\t\t}\n\t\t\t\tif (exprTemp.getOperand2() != null) {\n\t\t\t\t\texprTemp.setOperand2(checkMaximalStateFormulas(mc, model, exprTemp.getOperand2(), labelDDs));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn expr;\n\t}\n\n\t/**\n\t * Constructs a deterministic finite automaton (DFA) for the given syntactically co-safe\n\t * LTL formula, for use in reward computations for co-safe LTL.\n\t * <br>\n\t * First, extracted maximal state formulas are model checked with the passed in model checker.\n\t * The maximal state formulas are assigned labels (L0, L1, etc.) which become the atomic\n\t * propositions in the resulting DA. DDNodes giving the states which satisfy each label\n\t * are put into the vector {@code labelDDs}, which should be empty when this function is called.\n\t * <br>\n\t * To achieve \"strong\" semantics for the next-step operator, an additional atomic\n\t * proposition is added and X phi is transformed to X (phi & fresh_ap). This\n\t * ensures that, e.g., X X true results in two steps of accumulation.\n\t * @param mc the underlying model checker (for recursively handling maximal state formulas)\n\t * @param model the model\n\t * @param expr the co-safe LTL formula\n \t * @param labelDDs empty vector to be filled with JDDNodes for subformulas\n\t * @return a DA with AcceptanceReach acceptance condition\n\t */\n\tpublic DA<BitSet, AcceptanceReach> constructDFAForCosafetyRewardLTL(ModelChecker mc, Model model, Expression expr, Vector<JDDNode> labelDDs) throws PrismException\n\t{\n\t\t// Model check maximal state formulas\n\t\tExpression ltl = checkMaximalStateFormulas(mc, model, expr.deepCopy(), labelDDs);\n\n\t\tSimpleLTL sltl = ltl.convertForJltl2ba();\n\t\t// convert to positive normal form (negation only in front of APs)\n\t\tsltl = sltl.toBasicOperators();\n\t\tsltl = sltl.pushNegation();\n\t\tif (sltl.hasNextStep()) {\n\t\t\t// we have do add another atomic proposition\n\t\t\tString stepLabel = \"L\" + labelDDs.size();\n\t\t\tlabelDDs.add(model.getReach().copy());\n\t\t\tsltl = sltl.extendNextStepWithAP(stepLabel);\n\t\t\t// mainLog.println(\"Adding step label \" + stepLabel);\n\t\t}\n\n\t\t// Convert LTL formula to deterministic automaton, with Reach acceptance\n\t\tLTL2WDBA ltl2wdba = new LTL2WDBA(this);\n\t\tmainLog.println(\"\\nBuilding deterministic finite automaton via LTL2WDBA construction (for \" + sltl + \")...\");\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"constructing DFA\");\n\t\tDA<BitSet, AcceptanceReach> dfa = ltl2wdba.cosafeltl2dfa(sltl);\n\t\ttimer.stop(\"DFA has \" + dfa.size() + \" states\");\n\n\t\treturn dfa;\n\t}\n\n\t/**\n\t * Construct a deterministic automaton (DA) for an LTL formula, having first extracted maximal state formulas\n\t * and model checked them with the passed in model checker. The maximal state formulas are assigned labels\n\t * (L0, L1, etc.) which become the atomic propositions in the resulting DA. JDDNodes giving the states which\n\t * satisfy each label are put into the vector {@code labelBS}, which should be empty when this function is called.\n\t *\n\t * @param mc a ModelChecker, used for checking maximal state formulas\n\t * @param model the model\n\t * @param expr a path expression, i.e. the LTL formula\n\t * @param labelBS empty vector to be filled with JDDNodes for subformulas \n\t * @param allowedAcceptance the allowed acceptance types\n\t * @return the DA\n\t */\n\tpublic DA<BitSet,? extends AcceptanceOmega> constructDAForLTLFormula(ModelChecker mc, Model model, Expression expr, Vector<JDDNode> labelDDs, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tif (model.getModelType().continuousTime()) {\n\t\t\t\tthrow new PrismException(\"DA construction for time-bounded operators not supported for \" + model.getModelType()+\".\");\n\t\t\t}\n\n\t\t\tif (!expr.isSimplePathFormula()) {\n\t\t\t\tthrow new PrismException(\"Time-bounded operators not supported in LTL: \" + expr);\n\t\t\t}\n\t\t}\n\n\t\t// Model check maximal state formulas\n\t\tExpression ltl = checkMaximalStateFormulas(mc, model, expr.deepCopy(), labelDDs);\n\n\t\t// Convert LTL formula to deterministic automaton (DA)\n\t\tmainLog.println(\"\\nBuilding deterministic automaton (for \" + ltl + \")...\");\n\t\tlong time  = System.currentTimeMillis();\n\t\tLTL2DA ltl2da = new LTL2DA(this);\n\t\tDA<BitSet, ? extends AcceptanceOmega> da = ltl2da.convertLTLFormulaToDA(ltl, mc.getConstantValues(), allowedAcceptance);\n\t\tda.checkForCanonicalAPs(labelDDs.size());\n\t\tmainLog.println(da.getAutomataType()+\" has \" + da.size() + \" states, \" + da.getAcceptance().getSizeStatistics() + \".\");\n\t\ttime = System.currentTimeMillis() - time;\n\t\tmainLog.println(\"Time for deterministic automaton translation: \" + time / 1000.0 + \" seconds.\");\n\t\t// If required, export DA\n\t\tif (getSettings().getExportPropAut()) {\n\t\t\tmainLog.println(\"Exporting DA to file \\\"\" + getSettings().getExportPropAutFilename() + \"\\\"...\");\n\t\t\tPrintStream out = PrismUtils.newPrintStream(getSettings().getExportPropAutFilename());\n\t\t\tda.print(out, getSettings().getExportPropAutType());\n\t\t\tout.close();\n\t\t}\n\n\t\treturn da;\n\t}\n\n\n\t/**\n\t * Construct the product of a DA and a DTMC/CTMC, starting from a given set\n\t * of states of interest. The corresponding states in the product become\n\t * the initial states in the product model.\n\t *\n\t * <br>[ REFS: <i>returned ProbModel</i>, DEREFS: statesOfInterest]\n\t * @param da The DA\n\t * @param model The DTMC/CTMC\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t * @param statesOfInterest the states in the model that serve as the starting point for the DA product\n\t */\n\tpublic ProbModel constructProductMC(DA<BitSet, ? extends AcceptanceOmega> da, ProbModel model, Vector<JDDNode> labelDDs, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\treturn constructProductMC(da, model, labelDDs, null, null, statesOfInterest);\n\t}\n\n\t/**\n\t * Construct the product of a DA and a DTMC/CTMC.\n\t * <br>Deprecated legacy method, use variant with statesOfInterest.\n\t * With this method, the initial states of the product model correspond to\n\t * the initial states of the original model, but the product is constructed\n\t * from all states of the original model.\n\t * @param da The DA\n\t * @param model The DTMC/CTMC\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t */\n\t@Deprecated\n\tpublic ProbModel constructProductMC(DA<BitSet, ? extends AcceptanceOmega> da, ProbModel model, Vector<JDDNode> labelDDs) throws PrismException\n\t{\n\t\treturn constructProductMC(da, model, labelDDs, null, null, true);\n\t}\n\n\t/**\n\t * Construct the product of a DA and a DTMC/CTMC.\n\t * <br>Deprecated legacy method, use variant with statesOfInterest.\n\t * With this method, the initial states of the product model correspond to\n\t * the initial states of the original model, but the product is constructed\n\t * from all states of the original model.\n\t * @param da The DA\n\t * @param model The  DTMC/CTMC\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t * @param daDDRowVarsCopy (Optionally) empty JDDVars object to obtain copy of DD row vars for DA\n\t * @param daDDColVarsCopy (Optionally) empty JDDVars object to obtain copy of DD col vars for DA\n\t */\n\t@Deprecated\n\tpublic ProbModel constructProductMC(DA<BitSet, ? extends AcceptanceOmega> da, ProbModel model, Vector<JDDNode> labelDDs, JDDVars daDDRowVarsCopy, JDDVars daDDColVarsCopy)\n\t\t\tthrows PrismException\n\t{\n\t\treturn constructProductMC(da, model, labelDDs, daDDRowVarsCopy, daDDColVarsCopy, true);\n\t}\n\n\t/**\n\t * Construct the product of a DA and a DTMC/CTMC.\n\t * <br>Deprecated legacy method, use variant with statesOfInterest.\n\t * With this method, if {@code allInit} is {@code true},\n\t * the initial states of the product model correspond to the initial states\n\t * of the original model, but the product is constructed\n\t * from all states of the original model.\n\t * If {@code allInit} is {@code false}, the product is only constructed\n\t * from the initial states of the original model.\n\t * @param da The DA\n\t * @param model The  DTMC/CTMC\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t * @param daDDRowVarsCopy (Optionally) empty JDDVars object to obtain copy of DD row vars for DA\n\t * @param daDDColVarsCopy (Optionally) empty JDDVars object to obtain copy of DD col vars for DA\n\t * @param allInit Do we assume that all states of the original model are initial states?\n\t *        (just for the purposes of reachability)\n\t */\n\t@Deprecated\n\tpublic ProbModel constructProductMC(DA<BitSet, ? extends AcceptanceOmega> da, ProbModel model, Vector<JDDNode> labelDDs, JDDVars daDDRowVarsCopy, JDDVars daDDColVarsCopy,\n\t\t\tboolean allInit) throws PrismException\n\t{\n\t\t// construct suitable statesOfInterest\n\t\tJDDNode statesOfInterest = allInit ? model.getReach().copy() : model.getStart().copy();\n\n\t\t// generate temporary storage for row / col vars if needed\n\t\tJDDVars daDDRowVars = daDDRowVarsCopy == null ? new JDDVars() : daDDRowVarsCopy;\n\t\tJDDVars daDDColVars = daDDColVarsCopy == null ? new JDDVars() : daDDColVarsCopy;\n\n\t\t// construct product using statesOfInterest-based method\n\t\tProbModel modelProd = constructProductMC(da, model, labelDDs, daDDRowVars, daDDColVars, statesOfInterest);\n\n\t\t// Reset initial state (to mimic legacy behavior)\n\t\tJDDNode newStart = buildStartMask(da, labelDDs, daDDRowVars);\n\t\tJDD.Ref(model.getStart());\n\t\tnewStart = JDD.And(model.getStart(), newStart);\n\t\tmodelProd.setStart(newStart);\n\n\t\t// deref temporary storage for row / col vars if needed\n\t\tif (daDDRowVarsCopy == null)\n\t\t\tdaDDRowVars.derefAll();\n\t\tif (daDDColVarsCopy == null)\n\t\t\tdaDDColVars.derefAll();\n\n\t\treturn modelProd;\n\t}\n\n\t/**\n\t * Construct the product of a DA and a DTMC/CTMC, starting from a given set\n\t * of states of interest. The corresponding states in the product become\n\t * the initial states in the product model.\n\t *\n\t * <br>[ REFS: <i>returned ProbModel</i>, DEREFS: statesOfInterest]\n\t * @param da The DA\n\t * @param model The DTMC/CTMC\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t * @param daDDRowVarsCopy (Optionally) empty JDDVars object to obtain copy of DD row vars for DA\n\t * @param daDDColVarsCopy (Optionally) empty JDDVars object to obtain copy of DD col vars for DA\n\t * @param statesOfInterest the states in the model that serve as the starting point for the DA product\n\t */\n\tpublic ProbModel constructProductMC(DA<BitSet, ? extends AcceptanceOmega> da, ProbModel model,\n\t                                    Vector<JDDNode> labelDDs,\n                                        JDDVars daDDRowVarsCopy, JDDVars daDDColVarsCopy,\n                                        JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Existing model - dds, vars, etc.\n\t\tJDDVars varDDRowVars[];\n\t\tJDDVars varDDColVars[];\n\t\tJDDVars allDDRowVars;\n\t\tJDDVars allDDColVars;\n\t\tVarList varList;\n\t\t// New (product) model - dds, vars, etc.\n\t\tJDDNode newTrans, newStart;\n\t\tJDDVars newVarDDRowVars[], newVarDDColVars[];\n\t\tJDDVars newAllDDRowVars, newAllDDColVars;\n\t\tModelVariablesDD newModelVariables;\n\t\tVarList newVarList;\n\t\tString daVar;\n\t\t// DA stuff\n\t\tJDDVars daDDRowVars, daDDColVars;\n\t\t// Misc\n\t\tint i, n;\n\t\tboolean before;\n\n\t\t// Get details of old model (no copy, does not need to be cleaned up)\n\t\tvarDDRowVars = model.getVarDDRowVars();\n\t\tvarDDColVars = model.getVarDDColVars();\n\t\tallDDRowVars = model.getAllDDRowVars();\n\t\tallDDColVars = model.getAllDDColVars();\n\t\tvarList = model.getVarList();\n\n\t\t// Create a (new, unique) name for the variable that will represent DA states\n\t\tdaVar = \"_da\";\n\t\twhile (varList.exists(daVar)) {\n\t\t\tdaVar = \"_\" + daVar;\n\t\t}\n\n\t\tnewModelVariables = model.getModelVariables().copy();\n\t\t\n\t\t// See how many new dd vars will be needed for DA\n\t\t// and whether there is room to put them before rather than after the existing vars\n\t\t// (if DA only has one state, we add an extra dummy state)\n\t\tn = (int) Math.ceil(PrismUtils.log2(da.size()));\n\t\tn = Math.max(n, 1);\n\t\tbefore = newModelVariables.canPrependExtraStateVariable(n);\n\t\t\n\t\tdaDDRowVars = new JDDVars();\n\t\tdaDDColVars = new JDDVars();\n\t\t// Create the new dd variables\n\t\tJDDVars daVars = newModelVariables.allocateExtraStateVariable(n, daVar, before);\n\t\t\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tdaDDRowVars.addVar(daVars.getVar(2*i));\n\t\t\tdaDDColVars.addVar(daVars.getVar(2*i+1));\n\t\t}\n\t\t\n\t\t// Create/populate new lists\n\t\tnewVarDDRowVars = new JDDVars[varDDRowVars.length + 1];\n\t\tnewVarDDColVars = new JDDVars[varDDRowVars.length + 1];\n\t\tnewVarDDRowVars[before ? 0 : varDDRowVars.length] = daDDRowVars.copy();\n\t\tnewVarDDColVars[before ? 0 : varDDColVars.length] = daDDColVars.copy();\n\t\tfor (i = 0; i < varDDRowVars.length; i++) {\n\t\t\tnewVarDDRowVars[before ? i + 1 : i] = varDDRowVars[i].copy();\n\t\t\tnewVarDDColVars[before ? i + 1 : i] = varDDColVars[i].copy();\n\t\t}\n\t\tif (before) {\n\t\t\tnewAllDDRowVars = daDDRowVars.copy();\n\t\t\tnewAllDDColVars = daDDColVars.copy();\n\t\t\tnewAllDDRowVars.copyVarsFrom(allDDRowVars);\n\t\t\tnewAllDDColVars.copyVarsFrom(allDDColVars);\n\t\t} else {\n\t\t\tnewAllDDRowVars = allDDRowVars.copy();\n\t\t\tnewAllDDColVars = allDDColVars.copy();\n\t\t\tnewAllDDRowVars.copyVarsFrom(daDDRowVars);\n\t\t\tnewAllDDColVars.copyVarsFrom(daDDColVars);\n\t\t}\n\t\tnewVarList = (VarList) varList.clone();\n\t\t// NB: if DA only has one state, we add an extra dummy state\n\t\tDeclaration decl = new Declaration(daVar, new DeclarationInt(Expression.Int(0), Expression.Int(Math.max(da.size() - 1, 1))));\n\t\tif (before) {\n\t\t\tnewVarList.addVarAtStart(decl, 1);\n\t\t} else {\n\t\t\tnewVarList.addVar(decl, 1);\n\t\t}\n\n\t\t// Build transition matrix for product\n\t\tnewTrans = buildTransMask(da, labelDDs, allDDRowVars, allDDColVars, daDDRowVars, daDDColVars);\n\t\tJDD.Ref(model.getTrans());\n\t\tnewTrans = JDD.Apply(JDD.TIMES, model.getTrans(), newTrans);\n\n\t\t// Build set of initial states for product\n\t\t// We use the product states between the states of interest and the corresponding\n\t\t// DA states as the initial states of the product model (used for reachability)\n\t\tnewStart = buildStartMask(da, labelDDs, daDDRowVars);\n\t\tnewStart = JDD.And(model.getReach().copy(), statesOfInterest.copy(), newStart);\n\n\t\t// Create a new model model object to store the product model\n\t\tProbModel modelProd = new ProbModel(\n\t\t// New transition matrix/start state\n\t\t\t\tnewTrans, newStart,\n\t\t\t\t// New list of all row/col vars\n\t\t\t\tnewAllDDRowVars, newAllDDColVars,\n\t\t\t\t// New model variables\n\t\t\t\tnewModelVariables,\n\t\t\t\t// New var info\n\t\t\t\tnewVarList, newVarDDRowVars, newVarDDColVars);\n\t\t// Constants (no change)\n\t\tmodelProd.setConstantValues(model.getConstantValues());\n\n\t\t// Do reachability/etc. for the new model\n\t\tmodelProd.doReachability();\n\t\tmodelProd.filterReachableStates();\n\t\tmodelProd.findDeadlocks(false);\n\t\tif (modelProd.getDeadlockStates().size() > 0) {\n\t\t\t// Assuming original model has no deadlocks, neither should product\n\t\t\tthrow new PrismException(\"Model-\"+da.getAutomataType()+\" product has deadlock states\");\n\t\t}\n\n\t\t// if possible, return copies of the DA DD variables via the method parameters\n\t\tif (daDDRowVarsCopy != null)\n\t\t\tdaDDRowVarsCopy.copyVarsFrom(daDDRowVars);\n\t\tif (daDDColVarsCopy != null)\n\t\t\tdaDDColVarsCopy.copyVarsFrom(daDDColVars);\n\n\t\tJDD.Deref(statesOfInterest);\n\t\tdaDDRowVars.derefAll();\n\t\tdaDDColVars.derefAll();\n\n\t\treturn modelProd;\n\t}\n\n\t/**\n\t * Construct the product of a DA and an MDP, starting from a given set\n\t * of states of interest. The corresponding states in the product become\n\t * the initial states in the product model.\n\t *\n\t * <br>[ REFS: <i>returned NondetModel</i>, DEREFS: statesOfInterest]\n\t * @param da The DA\n\t * @param model The MDP\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t */\n\tpublic NondetModel constructProductMDP(DA<BitSet, ? extends AcceptanceOmega> da, NondetModel model, Vector<JDDNode> labelDDs, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\treturn constructProductMDP(da, model, labelDDs, null, null, statesOfInterest);\n\t}\n\n\t/**\n\t * Construct the product of a DA and an MDP.\n\t * <br>Deprecated legacy method, use variant with statesOfInterest.\n\t * With this method, the initial states of the product model correspond to\n\t * the initial states of the original model, but the product is constructed\n\t * from all states of the original model.\n\t * @param da The DA\n\t * @param model The MDP\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t */\n\t@Deprecated\n\tpublic NondetModel constructProductMDP(DA<BitSet, ? extends AcceptanceOmega> da, NondetModel model, Vector<JDDNode> labelDDs) throws PrismException\n\t{\n\t\treturn constructProductMDP(da, model, labelDDs, null, null, true, null);\n\t}\n\n\t/**\n\t * Construct the product of a DTMC with a deterministic automaton for the given LTL expression.\n\t * <br>[ REFS: <i>returned LTLProduct</i>, DEREFS: statesOfInterest]\n\t */\n\tpublic LTLProduct<ProbModel> constructProductMC(ProbModelChecker mc, ProbModel model, Expression expr, JDDNode statesOfInterest, AcceptanceType... allowedAcceptance) throws PrismException\n\t{\n\t\tVector<JDDNode> labelDDs = new Vector<JDDNode>();\n\t\tDA<BitSet, ? extends AcceptanceOmega> da;\n\n\t\tda = constructDAForLTLFormula(mc, model, expr, labelDDs, allowedAcceptance);\n\n\t\treturn constructProductMC(model, da, labelDDs, statesOfInterest);\n\t}\n\n\t/**\n\t * Construct the product of a DTMC with the given deterministic automaton (with AP set L0,L1,...),\n\t * returning an LTLProduct.\n\t * <br>\n\t * The state sets corresponding to each AP label are given via the labelDDs vector,\n\t * which will be dereferenced after this method call.\n\t * <br>[ REFS: <i>returned LTLProduct</i>, DEREFS: statesOfInterest, labelDDs]\n\t */\n\tpublic LTLProduct<ProbModel> constructProductMC(ProbModel model, DA<BitSet, ? extends AcceptanceOmega> da, Vector<JDDNode> labelDDs, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of Markov chain and automaton\n\t\tmainLog.println(\"\\nConstructing MC-\"+da.getAutomataType()+\" product...\");\n\t\tJDDVars daDDRowVars = new JDDVars();\n\t\tJDDVars daDDColVars = new JDDVars();\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"product construction\");\n\t\tProbModel modelProduct = constructProductMC(da, model, labelDDs, daDDRowVars, daDDColVars, statesOfInterest);\n\t\ttimer.stop();\n\t\tmainLog.println();\n\t\tmodelProduct.printTransInfo(mainLog, false);\n\n\t\tAcceptanceOmegaDD acceptance = da.getAcceptance().toAcceptanceDD(daDDRowVars);\n\n\t\tdaDDColVars.derefAll();\n\t\tfor (int i = 0; i < labelDDs.size(); i++) {\n\t\t\tJDD.Deref(labelDDs.get(i));\n\t\t}\n\n\t\treturn new LTLProduct<ProbModel>(modelProduct, model, acceptance, modelProduct.getStart().copy(), daDDRowVars);\n\t}\n\n\t/**\n\t * Construct the product of a DA and an MDP.\n\t * <br>Deprecated legacy method, use variant with statesOfInterest.\n\t * With this method, the initial states of the product model correspond to\n\t * the initial states of the original model, but the product is constructed\n\t * from all states of the original model.\n\t * @param da The DA\n\t * @param model The MDP\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t * @param daDDRowVarsCopy (Optionally) empty JDDVars object to obtain copy of DD row vars for DA\n\t * @param daDDColVarsCopy (Optionally) empty JDDVars object to obtain copy of DD col vars for DA\n\t */\n\t@Deprecated\n\tpublic NondetModel constructProductMDP(DA<BitSet, ? extends AcceptanceOmega> da, NondetModel model, Vector<JDDNode> labelDDs, JDDVars daDDRowVarsCopy, JDDVars daDDColVarsCopy)\n\t\t\tthrows PrismException\n\t{\n\t\treturn constructProductMDP(da, model, labelDDs, daDDRowVarsCopy, daDDColVarsCopy, true, null);\n\t}\n\n\n\t/**\n\t * Construct the product of a DA and an MDP.\n\t * <br>Deprecated legacy method, use variant with statesOfInterest.\n\t * With this method, if {@code allInit} is {@code true},\n\t * the initial states of the product model correspond to the initial states\n\t * of the original model, but the product is constructed\n\t * from all the states in {@code init}.\n\t * If {@code allInit} is {@code false}, the product is only constructed\n\t * from the initial states of the original model.\n\t * @param da The DA\n\t * @param model The MDP\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t * @param daDDRowVarsCopy (Optionally) empty JDDVars object to obtain copy of DD row vars for DA\n\t * @param daDDColVarsCopy (Optionally) empty JDDVars object to obtain copy of DD col vars for DA\n\t * @param allInit Do we assume that all states of the original model are initial states?\n\t *        (just for the purposes of reachability) If not, the required initial states should be given\n\t * @param init The initial state(s) (of the original model) used to build the product;\n\t *        if null; we just take the existing initial states from model.getStart().\n\t */\n\t@Deprecated\n\tpublic NondetModel constructProductMDP(DA<BitSet, ? extends AcceptanceOmega> da, NondetModel model, Vector<JDDNode> labelDDs, JDDVars daDDRowVarsCopy, JDDVars daDDColVarsCopy,\n\t\t\tboolean allInit, JDDNode init) throws PrismException\n\t{\n\t\t// construct suitable statesOfInterest\n\t\tJDDNode statesOfInterest = allInit ? model.getReach().copy() : init.copy();\n\n\t\t// generate temporary storage for row / col vars if needed\n\t\tJDDVars daDDRowVars = daDDRowVarsCopy == null ? new JDDVars() : daDDRowVarsCopy;\n\t\tJDDVars daDDColVars = daDDColVarsCopy == null ? new JDDVars() : daDDColVarsCopy;\n\n\t\t// construct product using statesOfInterest-based method\n\t\tNondetModel modelProd = constructProductMDP(da, model, labelDDs, daDDRowVars, daDDColVars, statesOfInterest);\n\n\t\t// Reset initial state (to mimic legacy behavior)\n\t\tJDDNode newStart = buildStartMask(da, labelDDs, daDDRowVars);\n\t\tJDD.Ref(init != null ? init : model.getStart());\n\t\tnewStart = JDD.And(init != null ? init : model.getStart(), newStart);\n\t\tmodelProd.setStart(newStart);\n\n\t\t// deref temporary storage for row / col vars if needed\n\t\tif (daDDRowVarsCopy == null)\n\t\t\tdaDDRowVars.derefAll();\n\t\tif (daDDColVarsCopy == null)\n\t\t\tdaDDColVars.derefAll();\n\n\t\treturn modelProd;\n\t}\n\n\t/**\n\t * Construct the product of a DA and an MDP, starting from a given set\n\t * of states of interest. The corresponding states in the product become\n\t * the initial states in the product model.\n\t *\n\t * <br>[ REFS: <i>returned NondetModel</i>, DEREFS: statesOfInterest]\n\t * @param da The DA\n\t * @param model The MDP\n\t * @param labelDDs BDDs giving the set of states for each AP in the DA\n\t * @param daDDRowVarsCopy (Optionally) empty JDDVars object to obtain copy of DD row vars for DA\n\t * @param daDDColVarsCopy (Optionally) empty JDDVars object to obtain copy of DD col vars for DA\n\t * @param statesOfInterest the states of interest, serving as the starting point for the MPD-DA product\n\t */\n\tpublic NondetModel constructProductMDP(DA<BitSet, ? extends AcceptanceOmega> da, NondetModel model,\n\t                                       Vector<JDDNode> labelDDs,\n\t                                       JDDVars daDDRowVarsCopy, JDDVars daDDColVarsCopy,\n\t                                       JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Existing model - dds, vars, etc.\n\t\tJDDVars varDDRowVars[];\n\t\tJDDVars varDDColVars[];\n\t\tJDDVars allDDRowVars;\n\t\tJDDVars allDDColVars;\n\t\tVarList varList;\n\t\t// New (product) model - dds, vars, etc.\n\t\tJDDNode newTrans, newStart;\n\t\tJDDVars newVarDDRowVars[], newVarDDColVars[];\n\t\tJDDVars newAllDDRowVars, newAllDDColVars;\n\t\tModelVariablesDD newModelVariables;\n\t\tVarList newVarList;\n\t\tString daVar;\n\t\t// DA stuff\n\t\tJDDVars daDDRowVars, daDDColVars;\n\t\t// Misc\n\t\tint i, n;\n\t\tboolean before;\n\n\t\t// Get details of old model (no copy, does not need to be cleaned up)\n\t\tvarDDRowVars = model.getVarDDRowVars();\n\t\tvarDDColVars = model.getVarDDColVars();\n\t\tallDDRowVars = model.getAllDDRowVars();\n\t\tallDDColVars = model.getAllDDColVars();\n\t\tvarList = model.getVarList();\n\n\t\t// Create a (new, unique) name for the variable that will represent DA states\n\t\tdaVar = \"_da\";\n\t\twhile (varList.exists(daVar)) {\n\t\t\tdaVar = \"_\" + daVar;\n\t\t}\n\n\t\tnewModelVariables = model.getModelVariables().copy();\n\t\t\n\t\t// See how many new dd vars will be needed for DA\n\t\t// and whether there is room to put them before rather than after the existing vars\n\t\t// (if DA only has one state, we add an extra dummy state)\n\t\tn = (int) Math.ceil(PrismUtils.log2(da.size()));\n\t\tn = Math.max(n, 1);\n\t\tbefore = newModelVariables.canPrependExtraStateVariable(n);\n\n\t\tdaDDRowVars = new JDDVars();\n\t\tdaDDColVars = new JDDVars();\n\t\t// Create the new dd variables\n\t\tJDDVars daVars = newModelVariables.allocateExtraStateVariable(n, daVar, before);\n\t\t\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tdaDDRowVars.addVar(daVars.getVar(2*i));\n\t\t\tdaDDColVars.addVar(daVars.getVar(2*i+1));\n\t\t}\n\t\t\n\t\t// Create/populate new lists\n\t\tnewVarDDRowVars = new JDDVars[varDDRowVars.length + 1];\n\t\tnewVarDDColVars = new JDDVars[varDDRowVars.length + 1];\n\t\tnewVarDDRowVars[before ? 0 : varDDRowVars.length] = daDDRowVars.copy();\n\t\tnewVarDDColVars[before ? 0 : varDDColVars.length] = daDDColVars.copy();\n\t\tfor (i = 0; i < varDDRowVars.length; i++) {\n\t\t\tnewVarDDRowVars[before ? i + 1 : i] = varDDRowVars[i].copy();\n\t\t\tnewVarDDColVars[before ? i + 1 : i] = varDDColVars[i].copy();\n\t\t}\n\t\tif (before) {\n\t\t\tnewAllDDRowVars = daDDRowVars.copy();\n\t\t\tnewAllDDColVars = daDDColVars.copy();\n\t\t\tnewAllDDRowVars.copyVarsFrom(allDDRowVars);\n\t\t\tnewAllDDColVars.copyVarsFrom(allDDColVars);\n\t\t} else {\n\t\t\tnewAllDDRowVars = allDDRowVars.copy();\n\t\t\tnewAllDDColVars = allDDColVars.copy();\n\t\t\tnewAllDDRowVars.copyVarsFrom(daDDRowVars);\n\t\t\tnewAllDDColVars.copyVarsFrom(daDDColVars);\n\t\t}\n\t\tnewVarList = (VarList) varList.clone();\n\t\t// NB: if DA only has one state, we add an extra dummy state\n\t\tDeclaration decl = new Declaration(daVar, new DeclarationInt(Expression.Int(0), Expression.Int(Math.max(da.size() - 1, 1))));\n\t\tif (before) {\n\t\t\tnewVarList.addVarAtStart(decl, 1);\n\t\t} else {\n\t\t\tnewVarList.addVar(decl, 1);\n\t\t}\n\n\t\t// Build transition matrix for product\n\t\tnewTrans = buildTransMask(da, labelDDs, allDDRowVars, allDDColVars, daDDRowVars, daDDColVars);\n\t\tJDD.Ref(model.getTrans());\n\t\tnewTrans = JDD.Apply(JDD.TIMES, model.getTrans(), newTrans);\n\n\t\t// Build set of initial states for product\n\t\t// We use the product states between the states of interest and the corresponding\n\t\t// DA states as the initial states of the product model (used for reachability)\n\t\tnewStart = buildStartMask(da, labelDDs, daDDRowVars);\n\t\tnewStart = JDD.And(model.getReach().copy(), statesOfInterest.copy(), newStart);\n\n\t\t// Create a new model model object to store the product model\n\t\tNondetModel modelProd = new NondetModel(\n\t\t// New transition matrix/start state\n\t\t\t\tnewTrans, newStart,\n\t\t\t\t// New list of all row/col vars\n\t\t\t\tnewAllDDRowVars, newAllDDColVars,\n\t\t\t\t// Nondet variables (unchanged)\n\t\t\t\tmodel.getAllDDNondetVars().copy(),\n\t\t\t\t// New model variables\n\t\t\t\tnewModelVariables,\n\t\t\t\t// New var info\n\t\t\t\tnewVarList, newVarDDRowVars, newVarDDColVars);\n\t\t// Constants (no change)\n\t\tmodelProd.setConstantValues(model.getConstantValues());\n\n\t\t// Copy action info MTBDD across directly\n\t\t// If present, just needs filtering to reachable states,\n\t\t// which will get done below.\n\t\tif (model.getTransActions() != null) {\n\t\t\tJDD.Ref(model.getTransActions());\n\t\t\tmodelProd.setTransActions(model.getTransActions());\n\t\t}\n\t\t// Also need to copy set of action label strings\n\t\tmodelProd.setSynchs(new Vector<String>(model.getSynchs()));\n\n\t\t// Do reachability/etc. for the new model\n\t\tmodelProd.doReachability();\n\t\tmodelProd.filterReachableStates();\n\t\tmodelProd.findDeadlocks(false);\n\t\tif (modelProd.getDeadlockStates().size() > 0) {\n\t\t\t// Assuming original model has no deadlocks, neither should product\n\t\t\tthrow new PrismException(\"Model-DA product has deadlock states\");\n\t\t}\n\n\n\t\t//try { prism.exportStatesToFile(modelProd, Prism.EXPORT_PLAIN, new java.io.File(\"prod.sta\")); }\n\t\t//catch (java.io.FileNotFoundException e) {}\n\n\t\t// return copies of the DA DD variables via the method parameters if possible\n\t\tif (daDDRowVarsCopy != null)\n\t\t\tdaDDRowVarsCopy.copyVarsFrom(daDDRowVars);\n\t\tif (daDDColVarsCopy != null)\n\t\t\tdaDDColVarsCopy.copyVarsFrom(daDDColVars);\n\n\t\tJDD.Deref(statesOfInterest);\n\t\tdaDDRowVars.derefAll();\n\t\tdaDDColVars.derefAll();\n\n\t\treturn modelProd;\n\t}\n\n\t/**\n\t * Construct the product of an MDP with a deterministic automaton for the given LTL expression.\n\t */\n\tpublic LTLProduct<NondetModel> constructProductMDP(NondetModelChecker mc, NondetModel model, Expression expr, JDDNode statesOfInterest, AcceptanceType... allowedAcceptance) throws PrismException {\n\t\tVector<JDDNode> labelDDs = new Vector<JDDNode>();\n\t\tDA<BitSet, ? extends AcceptanceOmega> da;\n\n\t\tda = constructDAForLTLFormula(mc, model, expr, labelDDs, allowedAcceptance);\n\n\t\treturn constructProductMDP(model, da, labelDDs, statesOfInterest);\n\t}\n\n\t/**\n\t * Construct the product of an MDP with the given deterministic automaton (with AP set L0,L1,...),\n\t * returning an LTLProduct.\n\t * <br>\n\t * The state sets corresponding to each AP label are given via the labelDDs vector,\n\t * which will be dereferenced after this method call.\n\t */\n\tpublic LTLProduct<NondetModel> constructProductMDP(NondetModel model, DA<BitSet, ? extends AcceptanceOmega> da, Vector<JDDNode> labelDDs, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Build product of MDP and automaton\n\t\tmainLog.println(\"\\nConstructing MDP-\"+da.getAutomataType()+\" product...\");\n\t\tJDDVars daDDRowVars = new JDDVars();\n\t\tJDDVars daDDColVars = new JDDVars();\n\t\tStopWatch timer = new StopWatch(getLog());\n\t\ttimer.start(\"product construction\");\n\t\tNondetModel modelProduct = constructProductMDP(da, model, labelDDs, daDDRowVars, daDDColVars, statesOfInterest);\n\t\ttimer.stop();\n\t\tmainLog.println();\n\t\tmodelProduct.printTransInfo(mainLog, getSettings().getBoolean(PrismSettings.PRISM_EXTRA_DD_INFO));\n\n\t\tAcceptanceOmegaDD acceptance = da.getAcceptance().toAcceptanceDD(daDDRowVars);\n\n\t\tdaDDColVars.derefAll();\n\t\tfor (int i = 0; i < labelDDs.size(); i++) {\n\t\t\tJDD.Deref(labelDDs.get(i));\n\t\t}\n\n\t\treturn new LTLProduct<NondetModel>(modelProduct, model, acceptance, modelProduct.getStart().copy(), daDDRowVars);\n\t}\n\n\t/**\n\t * Builds a (referenced) mask BDD representing all possible transitions in a product built with\n\t * DA {@code da}, i.e. all the transitions ((s,q),(s',q')) where q' = delta(q, label(s')) in the DA.\n\t * So the BDD is over column variables for model states (permuted from those found in the BDDs in\n\t * {@code labelDDs}) and row/col variables for the DA (from {@code daDDRowVars}, {@code daDDColVars}).\n\t */\n\tpublic JDDNode buildTransMask(DA<BitSet, ? extends AcceptanceOmega> da, Vector<JDDNode> labelDDs, JDDVars allDDRowVars, JDDVars allDDColVars, JDDVars daDDRowVars,\n\t\t\tJDDVars daDDColVars)\n\t{\n\t\tJDDNode daMask, label, exprBDD, transition;\n\t\tint i, j, k, numAPs, numStates, numEdges;\n\n\t\tnumAPs = da.getAPList().size();\n\t\tdaMask = JDD.Constant(0);\n\t\t// Iterate through all (states and) transitions of DA\n\t\tnumStates = da.size();\n\t\tfor (i = 0; i < numStates; i++) {\n\t\t\tnumEdges = da.getNumEdges(i);\n\t\t\tfor (j = 0; j < numEdges; j++) {\n\t\t\t\t// Build a transition label BDD for each edge\n\t\t\t\tlabel = JDD.Constant(1);\n\t\t\t\tfor (k = 0; k < numAPs; k++) {\n\t\t\t\t\t// Get the expression BDD for AP k (via label \"Lk\")\n\t\t\t\t\texprBDD = labelDDs.get(Integer.parseInt(da.getAPList().get(k).substring(1)));\n\t\t\t\t\tJDD.Ref(exprBDD);\n\t\t\t\t\tif (!da.getEdgeLabel(i, j).get(k)) {\n\t\t\t\t\t\texprBDD = JDD.Not(exprBDD);\n\t\t\t\t\t}\n\t\t\t\t\tlabel = JDD.And(label, exprBDD);\n\t\t\t\t}\n\t\t\t\t// Switch label BDD to col vars\n\t\t\t\tlabel = JDD.PermuteVariables(label, allDDRowVars, allDDColVars);\n\t\t\t\t// Build a BDD for the edge\n\t\t\t\ttransition = JDD.SetMatrixElement(JDD.Constant(0), daDDRowVars, daDDColVars, i, da.getEdgeDest(i, j), 1);\n\t\t\t\t// Now get the conjunction of the two\n\t\t\t\ttransition = JDD.And(transition, label);\n\t\t\t\t// Add edge BDD to the DA transition mask\n\t\t\t\tdaMask = JDD.Or(daMask, transition);\n\t\t\t}\n\t\t}\n\n\t\treturn daMask;\n\t}\n\n\t/**\n\t * Builds a (referenced) mask BDD representing all possible \"start\" states for a product built with\n\t * DA {@code da}, i.e. all the states (s,q) where q = delta(q_init, label(s)) in the DA.\n\t * So the BDD is over row variables for model states (as found in the BDDs in {@code labelDDs})\n\t * and row variables for the DA (from {@code daDDRowVars}).\n\t */\n\tpublic JDDNode buildStartMask(DA<BitSet,? extends AcceptanceOmega> da, Vector<JDDNode> labelDDs, JDDVars daDDRowVars)\n\t{\n\t\tJDDNode startMask, label, exprBDD, dest, tmp;\n\t\tint i, j, k, numAPs, numEdges;\n\n\t\tnumAPs = da.getAPList().size();\n\t\tstartMask = JDD.Constant(0);\n\t\t// Iterate through all transitions of start state of DA\n\t\ti = da.getStartState();\n\t\tnumEdges = da.getNumEdges(i);\n\t\tfor (j = 0; j < numEdges; j++) {\n\t\t\t// Build a transition label BDD for each edge\n\t\t\tlabel = JDD.Constant(1);\n\t\t\tfor (k = 0; k < numAPs; k++) {\n\t\t\t\t// Get the expression BDD for AP k (via label \"Lk\")\n\t\t\t\texprBDD = labelDDs.get(Integer.parseInt(da.getAPList().get(k).substring(1)));\n\t\t\t\tJDD.Ref(exprBDD);\n\t\t\t\tif (!da.getEdgeLabel(i, j).get(k)) {\n\t\t\t\t\texprBDD = JDD.Not(exprBDD);\n\t\t\t\t}\n\t\t\t\tlabel = JDD.And(label, exprBDD);\n\t\t\t}\n\t\t\t// Build a BDD for the DA destination state\n\t\t\tdest = JDD.Constant(0);\n\t\t\tdest = JDD.SetVectorElement(dest, daDDRowVars, da.getEdgeDest(i, j), 1);\n\n\t\t\t// Now get the conjunction of the two\n\t\t\ttmp = JDD.And(dest, label);\n\n\t\t\t// Add this destination to our start mask\n\t\t\tstartMask = JDD.Or(startMask, tmp);\n\t\t}\n\n\t\treturn startMask;\n\t}\n\n\t/**\n\t * Find the set of accepting BSCCs in a model wrt an omega acceptance condition.\n\t * @param acceptance the acceptance condition, with BDD based storage\n\t * @param model The model\n\t * @return A referenced BDD for the union of all states in accepting BSCCs\n\t */\n\tpublic JDDNode findAcceptingBSCCs(AcceptanceOmegaDD acceptance, ProbModel model) throws PrismException\n\t{\n\t\tJDDNode allAcceptingStates;\n\t\tList<JDDNode> vectBSCCs;\n\n\t\tallAcceptingStates = JDD.Constant(0);\n\t\t// Compute all BSCCs for model\n\t\tSCCComputer sccComputer = SCCComputer.createSCCComputer(this, model);\n\t\tsccComputer.computeBSCCs();\n\t\tvectBSCCs = sccComputer.getBSCCs();\n\t\tJDD.Deref(sccComputer.getNotInBSCCs());\n\n\t\t// Go through the BSCC\n\t\tfor (JDDNode bscc : vectBSCCs) {\n\t\t\t// Check for acceptance\n\t\t\tif (acceptance.isBSCCAccepting(bscc)) {\n\t\t\t\t// This BSCC is accepting: add to allAcceptingStates\n\t\t\t\tJDD.Ref(bscc);\n\t\t\t\tallAcceptingStates = JDD.Or(allAcceptingStates, bscc);\n\t\t\t}\n\t\t\tJDD.Deref(bscc);\n\t\t}\n\n\t\treturn allAcceptingStates;\n\t}\n\n\t/**\n\t * Find the set of states in accepting end components (ECs) in a nondeterministic model wrt an acceptance condition.\n\t * @param acceptance the acceptance condition\n\t * @param model The model\n\t * @param daDDRowVars BDD row variables for the DA part of the model\n\t * @param daDDColVars BDD column variables for the DA part of the model\n\t * @param fairness Consider fairness?\n\t * @return A referenced BDD for the union of all states in accepting MECs\n\t */\n\tpublic JDDNode findAcceptingECStates(AcceptanceOmegaDD acceptance, NondetModel model, JDDVars daDDRowVars, JDDVars daDDColVars, boolean fairness)\n\t\t\tthrows PrismException\n\t{\n\t\tswitch (acceptance.getType()) {\n\t\tcase BUCHI:\n\t\t\treturn findAcceptingECStatesForBuchi((AcceptanceBuchiDD) acceptance, model, fairness);\n\t\tcase RABIN:\n\t\t\treturn findAcceptingECStatesForRabin((AcceptanceRabinDD) acceptance, model, daDDRowVars, daDDColVars, fairness);\n\t\tcase GENERALIZED_RABIN:\n\t\t\treturn findAcceptingECStatesForGeneralizedRabin((AcceptanceGenRabinDD) acceptance, model, daDDRowVars, daDDColVars, fairness);\n\t\tdefault:\n\t\t\tthrow new PrismNotSupportedException(\"Computing the accepting EC states for \"+acceptance.getTypeName()+\" acceptance is not yet implemented (symbolic engine)\");\n\t\t}\n\t}\n\n\t/**\n\t * Find the set of states in accepting end components (ECs) in a nondeterministic model wrt a Büchi acceptance condition.\n\t * @param acceptance the Büchi acceptance condition\n\t * @param model The model\n\t * @param fairness Consider fairness?\n\t * @return A referenced BDD for the union of all states in accepting MECs\n\t */\n\tpublic JDDNode findAcceptingECStatesForBuchi(AcceptanceBuchiDD acceptance, NondetModel model, boolean fairness) throws PrismException\n\t{\n\t\tJDDNode acceptingStates = null;\n\n\t\t// Normal case (no fairness): find accepting MECs\n\t\tif (!fairness) {\n\t\t\tList<JDDNode> ecs = findMECStates(model, model.getReach().copy());\n\t\t\tacceptingStates = filteredUnion(ecs, acceptance.getAcceptingStates());\n\t\t}\n\t\t// For case of fairness...\n\t\telse {\n\t\t\t// Compute the backward set of F, i.e., all states that can reach F\n\t\t\tJDDNode edges = model.getTransReln().copy();\n\t\t\tJDDNode filterStates = backwardSet(model, acceptance.getAcceptingStates(), edges);\n\t\t\t// Find the accepting states under fairness: the fair ECs that\n\t\t\t// can stay in filterStates, as those can infinitely often visit F\n\t\t\tacceptingStates = findFairECs(model, filterStates);\n\t\t}\n\n\t\treturn acceptingStates;\n\t}\n\n\t/**\n\t * Find the set of states in accepting end components (ECs) in a nondeterministic model wrt a Rabin acceptance condition.\n\t * @param acceptance the Rabin acceptance condition\n\t * @param model The model\n\t * @param draDDRowVars BDD row variables for the DRA part of the model\n\t * @param draDDColVars BDD column variables for the DRA part of the model\n\t * @param fairness Consider fairness?\n\t * @return A referenced BDD for the union of all states in accepting MECs\n\t */\n\tpublic JDDNode findAcceptingECStatesForRabin(AcceptanceRabinDD acceptance, NondetModel model, JDDVars draDDRowVars, JDDVars draDDColVars, boolean fairness)\n\t\t\tthrows PrismException\n\t{\n\t\tJDDNode acceptingStates = null, allAcceptingStates, acceptanceVector_L_not, acceptanceVector_K, candidateStates;\n\t\tint i;\n\n\t\tallAcceptingStates = JDD.Constant(0);\n\n\t\tif (acceptance.size() > 1) {\n\t\t\tacceptanceVector_L_not = JDD.Constant(0);\n\t\t\tacceptanceVector_K = JDD.Constant(0);\n\t\t\tArrayList<JDDNode> statesLnot = new ArrayList<JDDNode>();\n\t\t\tArrayList<JDDNode> statesK = new ArrayList<JDDNode>();\n\n\t\t\tfor (i = 0; i < acceptance.size(); i++) {\n\t\t\t\tJDDNode tmpLnot = JDD.Not(acceptance.get(i).getL());\n\t\t\t\tJDDNode tmpK = acceptance.get(i).getK();\n\t\t\t\tstatesLnot.add(tmpLnot);\n\t\t\t\tJDD.Ref(tmpLnot);\n\t\t\t\tacceptanceVector_L_not = JDD.Or(acceptanceVector_L_not, tmpLnot);\n\t\t\t\tstatesK.add(tmpK);\n\t\t\t\tJDD.Ref(tmpK);\n\t\t\t\tacceptanceVector_K = JDD.Or(acceptanceVector_K, tmpK);\n\t\t\t}\n\n\t\t\tJDD.Ref(model.getTrans01());\n\t\t\tJDD.Ref(acceptanceVector_L_not);\n\t\t\tcandidateStates = JDD.Apply(JDD.TIMES, model.getTrans01(), acceptanceVector_L_not);\n\t\t\tacceptanceVector_L_not = JDD.PermuteVariables(acceptanceVector_L_not, draDDRowVars, draDDColVars);\n\t\t\tcandidateStates = JDD.Apply(JDD.TIMES, candidateStates, acceptanceVector_L_not);\n\t\t\tcandidateStates = JDD.ThereExists(candidateStates, model.getAllDDColVars());\n\t\t\tcandidateStates = JDD.ThereExists(candidateStates, model.getAllDDNondetVars());\n\t\t\t// find all maximal end components\n\t\t\tList<JDDNode> allecs = findMECStates(model, candidateStates, acceptanceVector_K);\n\t\t\tJDD.Deref(acceptanceVector_K);\n\t\t\tJDD.Deref(candidateStates);\n\n\t\t\tfor (i = 0; i < acceptance.size(); i++) {\n\t\t\t\t// build the acceptance vectors L_i and K_i\n\t\t\t\tacceptanceVector_L_not = statesLnot.get(i);\n\t\t\t\tacceptanceVector_K = statesK.get(i);\n\t\t\t\tfor (JDDNode ec : allecs) {\n\t\t\t\t\tif (fairness) {\n\t\t\t\t\t\t// The goal states in this EC, have to be visited infinitely often\n\t\t\t\t\t\tJDDNode goal = JDD.And(ec.copy(), acceptanceVector_K.copy());\n\t\t\t\t\t\t// The safe states in this EC, only they may be visited\n\t\t\t\t\t\tJDDNode safeStates = JDD.And(ec.copy(), acceptanceVector_L_not.copy());\n\n\t\t\t\t\t\t// Compute the backward set for goal in this EC\n\t\t\t\t\t\tJDDNode ecEdges = model.getTransReln().copy();\n\t\t\t\t\t\t// we only care about the outgoing edges of safe states\n\t\t\t\t\t\tecEdges = JDD.And(ecEdges, safeStates.copy());\n\t\t\t\t\t\tJDDNode canReachGoal = backwardSet(model, goal, ecEdges);\n\n\t\t\t\t\t\t// The good states are those that are safe and can reach goal\n\t\t\t\t\t\tJDDNode goodStates = JDD.And(safeStates, canReachGoal);\n\n\t\t\t\t\t\t// Find accepting states under fairness:\n\t\t\t\t\t\t// Those states in goodStates where *all* outgoing transitions\n\t\t\t\t\t\t// remain in goodStates, forever.\n\t\t\t\t\t\tacceptingStates = findFairECs(model, goodStates);\n\n\t\t\t\t\t\tallAcceptingStates = JDD.Or(allAcceptingStates, acceptingStates);\n\n\t\t\t\t\t\t// look at next EC\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\t\t\t\t\t// build bdd of accepting states (under L_i) in the product model\n\t\t\t\t\tList<JDDNode> ecs;\n\t\t\t\t\tJDD.Ref(ec);\n\t\t\t\t\tJDD.Ref(acceptanceVector_L_not);\n\t\t\t\t\tcandidateStates = JDD.And(ec, acceptanceVector_L_not);\n\t\t\t\t\tif (candidateStates.equals(ec)) {\n\t\t\t\t\t\t//mainLog.println(\" ------------- ec is not modified ------------- \");\n\t\t\t\t\t\tecs = new Vector<JDDNode>();\n\t\t\t\t\t\t// store copy of ec in ecs\n\t\t\t\t\t\tJDD.Ref(ec);\n\t\t\t\t\t\tecs.add(ec);\n\t\t\t\t\t} else if (candidateStates.equals(JDD.ZERO)) {\n\t\t\t\t\t\t//mainLog.println(\" ------------- ec is ZERO ------------- \");\n\t\t\t\t\t\tJDD.Deref(candidateStates);\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t} else { // recompute maximal end components\n\t\t\t\t\t\t//mainLog.println(\" ------------- ec is recomputed ------------- \");\n\t\t\t\t\t\tJDD.Ref(model.getTrans01());\n\t\t\t\t\t\tJDD.Ref(candidateStates);\n\t\t\t\t\t\tJDDNode newcandidateStates = JDD.Apply(JDD.TIMES, model.getTrans01(), candidateStates);\n\t\t\t\t\t\tcandidateStates = JDD.PermuteVariables(candidateStates, draDDRowVars, draDDColVars);\n\t\t\t\t\t\tnewcandidateStates = JDD.Apply(JDD.TIMES, candidateStates, newcandidateStates);\n\t\t\t\t\t\tnewcandidateStates = JDD.ThereExists(newcandidateStates, model.getAllDDColVars());\n\t\t\t\t\t\tcandidateStates = JDD.ThereExists(newcandidateStates, model.getAllDDNondetVars());\n\t\t\t\t\t\tecs = findMECStates(model, candidateStates, acceptanceVector_K);\n\t\t\t\t\t}\n\t\t\t\t\tJDD.Deref(candidateStates);\n\n\t\t\t\t\t// find ECs in acceptingStates that are accepting under K_i\n\t\t\t\t\tacceptingStates = JDD.Constant(0);\n\t\t\t\t\tfor (JDDNode set : ecs) {\n\t\t\t\t\t\tif (JDD.AreIntersecting(set, acceptanceVector_K))\n\t\t\t\t\t\t\tacceptingStates = JDD.Or(acceptingStates, set);\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\tJDD.Deref(set);\n\t\t\t\t\t}\n\t\t\t\t\tallAcceptingStates = JDD.Or(allAcceptingStates, acceptingStates);\n\t\t\t\t}\n\t\t\t\tJDD.Deref(acceptanceVector_K);\n\t\t\t\tJDD.Deref(acceptanceVector_L_not);\n\t\t\t}\n\t\t\tfor (JDDNode ec : allecs)\n\t\t\t\tJDD.Deref(ec);\n\t\t} else {\n\t\t\t// Go through the DRA acceptance pairs (L_i, K_i) \n\t\t\tfor (i = 0; i < acceptance.size(); i++) {\n\t\t\t\t// Build BDDs for !L_i and K_i\n\t\t\t\tJDDNode statesLi_not = JDD.Not(acceptance.get(i).getL());\n\t\t\t\tJDDNode statesK_i = acceptance.get(i).getK();\n\t\t\t\t// Find states in the model for which there are no transitions leaving !L_i\n\t\t\t\t// (this will allow us to reduce the problem to finding MECs, not ECs)\n\t\t\t\t// TODO: I don't think this next step is needed,\n\t\t\t\t// since the ECComputer restricts the model in this way anyway.\n\t\t\t\t// However, for fairness, the restriction of the candidateStates\n\t\t\t\t// to statesLi_not has to happen for correctness.\n\t\t\t\tJDD.Ref(model.getTrans01());\n\t\t\t\tJDD.Ref(statesLi_not);\n\t\t\t\tcandidateStates = JDD.Apply(JDD.TIMES, model.getTrans01(), statesLi_not);\n\t\t\t\tstatesLi_not = JDD.PermuteVariables(statesLi_not, draDDRowVars, draDDColVars);\n\t\t\t\tcandidateStates = JDD.Apply(JDD.TIMES, candidateStates, statesLi_not);\n\t\t\t\tcandidateStates = JDD.ThereExists(candidateStates, model.getAllDDColVars());\n\t\t\t\tcandidateStates = JDD.ThereExists(candidateStates, model.getAllDDNondetVars());\n\t\t\t\t// Normal case (no fairness): find accepting MECs within !L_i \n\t\t\t\tif (!fairness) {\n\t\t\t\t\tList<JDDNode> ecs = findMECStates(model, candidateStates);\n\t\t\t\t\tJDD.Deref(candidateStates);\n\t\t\t\t\tacceptingStates = filteredUnion(ecs, statesK_i);\n\t\t\t\t}\n\t\t\t\t// For case of fairness...\n\t\t\t\telse {\n\t\t\t\t\t// Compute the backward set of S x !L_i\n\t\t\t\t\tJDD.Ref(candidateStates);\n\t\t\t\t\tJDDNode tmp = JDD.And(candidateStates, statesK_i);\n\t\t\t\t\tJDD.Ref(model.getTrans01());\n\t\t\t\t\tJDDNode edges = JDD.ThereExists(model.getTrans01(), model.getAllDDNondetVars());\n\t\t\t\t\tJDDNode filterStates = backwardSet(model, tmp, edges);\n\t\t\t\t\t// Filter out states that can't reach a state in !L'_i\n\t\t\t\t\tcandidateStates = JDD.And(candidateStates, filterStates);\n\t\t\t\t\t// Find accepting states in S x !L_i\n\t\t\t\t\tacceptingStates = findFairECs(model, candidateStates);\n\t\t\t\t}\n\n\t\t\t\t// Add states to our destination BDD\n\t\t\t\tallAcceptingStates = JDD.Or(allAcceptingStates, acceptingStates);\n\t\t\t}\n\t\t}\n\n\t\treturn allAcceptingStates;\n\t}\n\n\t/**\n\t * Find the set of states in accepting end components (ECs) in a nondeterministic model wrt a Generalized Rabin acceptance condition.\n\t * @param acceptance the Generalized Rabin acceptance condition\n\t * @param model The model\n\t * @param draDDRowVars BDD row variables for the DRA part of the model\n\t * @param draDDColVars BDD column variables for the DRA part of the model\n\t * @param fairness Consider fairness?\n\t * @return A referenced BDD for the union of all states in accepting MECs\n\t */\n\tpublic JDDNode findAcceptingECStatesForGeneralizedRabin(AcceptanceGenRabinDD acceptance, NondetModel model, JDDVars draDDRowVars, JDDVars draDDColVars, boolean fairness)\n\t\t\tthrows PrismException\n\t{\n\t\t\n\t\tif (fairness) {\n\t\t\tthrow new PrismNotSupportedException(\"Accepting end-component computation for generalized Rabin is currently not supported with fairness\");\n\t\t}\n\n\t\tJDDNode allAcceptingStates;\n\n\t\tallAcceptingStates = JDD.Constant(0);\n\n\t\t// Go through the GR acceptance pairs (L_i, K_i_1, ..., K_i_n) \n\t\tfor (int i = 0; i < acceptance.size(); i++) {\n\t\t\t\t\t\n\t\t\t// Filter out L_i states from the model and find the MECs\n\t\t\tJDDNode notL = JDD.Not(acceptance.get(i).getL());\n\t\t\tJDD.Ref(model.getTrans01());\n\t\t\tJDD.Ref(notL);\n\t\t\tJDDNode candidateStates = JDD.Apply(JDD.TIMES, model.getTrans01(), notL);\n\t\t\tnotL = JDD.PermuteVariables(notL, draDDRowVars, draDDColVars);\n\t\t\tcandidateStates = JDD.Apply(JDD.TIMES, candidateStates,\tnotL);\n\t\t\tcandidateStates = JDD.ThereExists(candidateStates, model.getAllDDColVars());\n\t\t\tcandidateStates = JDD.ThereExists(candidateStates, model.getAllDDNondetVars());\n\t\t\tList<JDDNode> mecs = findMECStates(model, candidateStates);\n\t\t\tJDD.Deref(candidateStates);\n\n\t\t\t// Check which MECs are accepting for this pair, calculate union\n\t\t\tJDDNode acceptingStates = JDD.Constant(0);\n\t\t\tfor (int k = 0; k < mecs.size(); k++) {\n\t\t\t\t// Is the induced BSCC by this MEC accepting?\n\t\t\t\t// (note we only really need to check K_i_1, ..., K_i_n here, not L too,\n\t\t\t\t// but this should not really affect efficiency)\n\t\t\t\tif (acceptance.get(i).isBSCCAccepting(mecs.get(k))) {\n\t\t\t\t\tacceptingStates = JDD.Or(acceptingStates, mecs.get(k));\n\t\t\t\t} else {\n\t\t\t\t\tJDD.Deref(mecs.get(k));\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Add to the set of accepting states for all pairs\n\t\t\tallAcceptingStates = JDD.Or(allAcceptingStates, acceptingStates);\n\t\t}\n\n\t\treturn allAcceptingStates;\n\t}\n\n\tpublic JDDNode findMultiAcceptingStates(DA<BitSet,AcceptanceRabin> dra, NondetModel model, JDDVars draDDRowVars, JDDVars draDDColVars, boolean fairness,\n\t\t\tList<JDDNode> allecs, List<JDDNode> statesH, List<JDDNode> statesL) throws PrismException\n\t{\n\t\tJDDNode acceptingStates = null, allAcceptingStates, candidateStates;\n\t\tJDDNode acceptanceVector_H, acceptanceVector_L;\n\t\tint i;\n\n\t\tallAcceptingStates = JDD.Constant(0);\n\n\t\t// for each acceptance pair (H_i, L_i) in the DRA, build H'_i = S x H_i\n\t\t// and compute the maximal ECs in H'_i\n\t\tfor (i = 0; i < dra.getAcceptance().size(); i++) {\n\t\t\t// build the acceptance vectors H_i and L_i\n\t\t\tacceptanceVector_H = statesH.get(i);\n\t\t\tacceptanceVector_L = statesL.get(i);\n\t\t\tfor (JDDNode ec : allecs) {\n\t\t\t\t// build bdd of accepting states (under H_i) in the product model\n\t\t\t\tList<JDDNode> ecs = null;\n\t\t\t\tJDD.Ref(ec);\n\t\t\t\tJDD.Ref(acceptanceVector_H);\n\t\t\t\tcandidateStates = JDD.And(ec, acceptanceVector_H);\n\t\t\t\tif (candidateStates.equals(ec)) {\n\t\t\t\t\t//mainLog.println(\" ------------- ec is not modified ------------- \");\n\t\t\t\t\tecs = new Vector<JDDNode>();\n\t\t\t\t\tecs.add(ec.copy());\n\t\t\t\t\tJDD.Deref(candidateStates);\n\t\t\t\t} else if (candidateStates.equals(JDD.ZERO)) {\n\t\t\t\t\t//mainLog.println(\" ------------- ec is ZERO ------------- \");\n\t\t\t\t\tJDD.Deref(candidateStates);\n\t\t\t\t\tcontinue;\n\t\t\t\t} else { // recompute maximal end components\n\t\t\t\t\t//mainLog.println(\" ------------- ec is recomputed ------------- \");\n\t\t\t\t\tJDD.Ref(model.getTrans01());\n\t\t\t\t\tJDD.Ref(candidateStates);\n\t\t\t\t\tJDDNode newcandidateStates = JDD.Apply(JDD.TIMES, model.getTrans01(), candidateStates);\n\t\t\t\t\tcandidateStates = JDD.PermuteVariables(candidateStates, draDDRowVars, draDDColVars);\n\t\t\t\t\tnewcandidateStates = JDD.Apply(JDD.TIMES, candidateStates, newcandidateStates);\n\t\t\t\t\tnewcandidateStates = JDD.ThereExists(newcandidateStates, model.getAllDDColVars());\n\t\t\t\t\tcandidateStates = JDD.ThereExists(newcandidateStates, model.getAllDDNondetVars());\n\t\t\t\t\tecs = findMECStates(model, candidateStates, acceptanceVector_L);\n\t\t\t\t\tJDD.Deref(candidateStates);\n\t\t\t\t}\n\n\t\t\t\t//StateListMTBDD vl;\n\t\t\t\t//int count = 0;\n\t\t\t\tacceptingStates = JDD.Constant(0);\n\t\t\t\tfor (JDDNode set : ecs) {\n\t\t\t\t\tif (JDD.AreIntersecting(set, acceptanceVector_L))\n\t\t\t\t\t\tacceptingStates = JDD.Or(acceptingStates, set);\n\t\t\t\t\telse\n\t\t\t\t\t\tJDD.Deref(set);\n\t\t\t\t}\n\t\t\t\t// Add states to our destination BDD\n\t\t\t\tallAcceptingStates = JDD.Or(allAcceptingStates, acceptingStates);\n\t\t\t}\n\t\t\tJDD.Deref(acceptanceVector_L);\n\t\t\tJDD.Deref(acceptanceVector_H);\n\t\t}\n\n\t\treturn allAcceptingStates;\n\t}\n\n\tpublic void findMultiConflictAcceptingStates(DA<BitSet,AcceptanceRabin>[] dra, NondetModel model, JDDVars[] draDDRowVars, JDDVars[] draDDColVars, List<JDDNode> targetDDs,\n\t\t\tList<List<JDDNode>> allstatesH, List<List<JDDNode>> allstatesL, List<JDDNode> combinations, List<List<Integer>> combinationIDs)\n\t\t\tthrows PrismException\n\t{\n\t\tList<queueElement> queue = new ArrayList<queueElement>();\n\t\tint sp = 0;\n\n\t\tfor (int i = 0; i < dra.length; i++) {\n\t\t\tList<Integer> ids = new ArrayList<Integer>();\n\t\t\tids.add(i);\n\t\t\tqueueElement e = new queueElement(allstatesH.get(i), allstatesL.get(i), targetDDs.get(i), ids, i + 1);\n\t\t\tqueue.add(e);\n\t\t}\n\n\t\twhile (sp < queue.size()) {\n\t\t\tcomputeCombinations(dra, model, draDDRowVars, draDDColVars, targetDDs, allstatesH, allstatesL, queue, sp);\n\t\t\tsp++;\n\t\t}\n\n\t\t// subtract children from targetDD\n\t\tfor (queueElement e : queue)\n\t\t\tif (e.children != null) {\n\t\t\t\tJDDNode newtarget = e.targetDD;\n\t\t\t\t//JDD.Ref(newtarget);\n\t\t\t\tfor (queueElement e1 : e.children) {\n\t\t\t\t\tJDD.Ref(e1.targetDD);\n\t\t\t\t\tnewtarget = JDD.And(newtarget, JDD.Not(e1.targetDD));\n\t\t\t\t}\n\t\t\t\t//JDD.Deref(e.targetDD);\n\t\t\t\te.targetDD = newtarget;\n\t\t\t}\n\t\ttargetDDs.clear();\n\t\tfor (int i = 0; i < dra.length; i++) {\n\t\t\ttargetDDs.add(queue.get(i).targetDD);\n\t\t}\n\t\tfor (int i = dra.length; i < queue.size(); i++) {\n\t\t\tcombinations.add(queue.get(i).targetDD);\n\t\t\tcombinationIDs.add(queue.get(i).draIDs);\n\t\t}\n\t}\n\n\tprivate void computeCombinations(DA<BitSet,AcceptanceRabin>[] dra, NondetModel model, JDDVars[] draDDRowVars, JDDVars[] draDDColVars, List<JDDNode> targetDDs,\n\t\t\tList<List<JDDNode>> allstatesH, List<List<JDDNode>> allstatesL, List<queueElement> queue, int sp) throws PrismException\n\t{\n\t\tqueueElement e = queue.get(sp);\n\t\tint bound = queue.size();\n\t\t//StateListMTBDD vl = null;\n\t\t//mainLog.println(\"  ------------- Processing \" + e.draIDs + \": -------------\");\n\n\t\tfor (int i = e.next; i < dra.length; i++) {\n\t\t\tList<JDDNode> newstatesH = new ArrayList<JDDNode>();\n\t\t\tList<JDDNode> newstatesL = new ArrayList<JDDNode>();\n\t\t\t//if(e.draIDs.size() >= 2 || sp > 0 /*|| queue.size() > 3*/)\n\t\t\t//\tbreak;\n\t\t\t//mainLog.println(\"             combinations \" + e.draIDs + \", \" + i + \": \");\n\t\t\tJDDNode allAcceptingStates = JDD.Constant(0);\n\t\t\t// compute conjunction of e and next\n\t\t\tList<JDDNode> nextstatesH = allstatesH.get(i);\n\t\t\tList<JDDNode> nextstatesL = allstatesL.get(i);\n\t\t\tJDD.Ref(e.targetDD);\n\t\t\tJDD.Ref(targetDDs.get(i));\n\t\t\tJDDNode intersection = JDD.And(e.targetDD, targetDDs.get(i));\n\t\t\tfor (int j = 0; j < e.statesH.size(); j++) {\n\t\t\t\tJDD.Ref(intersection);\n\t\t\t\tJDD.Ref(e.statesH.get(j));\n\t\t\t\tJDDNode candidateStates = JDD.And(intersection, e.statesH.get(j));\n\t\t\t\tfor (int k = 0; k < nextstatesH.size(); k++) {\n\t\t\t\t\tJDD.Ref(candidateStates);\n\t\t\t\t\tJDD.Ref(nextstatesH.get(k));\n\t\t\t\t\tJDDNode candidateStates1 = JDD.And(candidateStates, nextstatesH.get(k));\n\n\t\t\t\t\t// Find end components in candidateStates1\n\t\t\t\t\tJDD.Ref(model.getTrans01());\n\t\t\t\t\tJDD.Ref(candidateStates1);\n\t\t\t\t\tJDDNode newcandidateStates = JDD.Apply(JDD.TIMES, model.getTrans01(), candidateStates1);\n\t\t\t\t\t/*for(int x=0; x<e.draIDs.size(); x++)\n\t\t\t\t\t\tcandidateStates1 = JDD.PermuteVariables(candidateStates1, draDDRowVars[e.draIDs.get(x)], draDDColVars[e.draIDs.get(x)]);\n\t\t\t\t\tcandidateStates1 = JDD.PermuteVariables(candidateStates1, draDDRowVars[i], draDDColVars[i]);*/\n\t\t\t\t\tcandidateStates1 = JDD.PermuteVariables(candidateStates1, model.getAllDDRowVars(), model.getAllDDColVars());\n\t\t\t\t\tnewcandidateStates = JDD.Apply(JDD.TIMES, candidateStates1, newcandidateStates);\n\t\t\t\t\tnewcandidateStates = JDD.ThereExists(newcandidateStates, model.getAllDDColVars());\n\t\t\t\t\tcandidateStates1 = JDD.ThereExists(newcandidateStates, model.getAllDDNondetVars());\n\t\t\t\t\tJDD.Ref(e.statesL.get(j));\n\t\t\t\t\tJDD.Ref(nextstatesL.get(k));\n\t\t\t\t\tJDDNode acceptanceVector_L = JDD.And(e.statesL.get(j), nextstatesL.get(k));\n\t\t\t\t\tList<JDDNode> ecs = null;\n\t\t\t\t\tecs = findMECStates(model, candidateStates1, acceptanceVector_L);\n\t\t\t\t\tJDD.Deref(candidateStates1);\n\n\t\t\t\t\t// For each ec, test if it has non-empty intersection with L states\n\t\t\t\t\tif (ecs != null) {\n\t\t\t\t\t\tboolean valid = false;\n\t\t\t\t\t\tfor (JDDNode set : ecs) {\n\t\t\t\t\t\t\tif (JDD.AreIntersecting(set, acceptanceVector_L)) {\n\t\t\t\t\t\t\t\tallAcceptingStates = JDD.Or(allAcceptingStates, set);\n\t\t\t\t\t\t\t\tvalid = true;\n\t\t\t\t\t\t\t} else\n\t\t\t\t\t\t\t\tJDD.Deref(set);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (valid) {\n\t\t\t\t\t\t\t//mainLog.println(\"          adding j = \" + j + \", k = \" + k + \" to nextstateH & L \");\n\t\t\t\t\t\t\tJDD.Ref(e.statesH.get(j));\n\t\t\t\t\t\t\tJDD.Ref(nextstatesH.get(k));\n\t\t\t\t\t\t\tJDDNode ttt = JDD.And(e.statesH.get(j), nextstatesH.get(k));\n\t\t\t\t\t\t\tnewstatesH.add(ttt);\n\t\t\t\t\t\t\tJDD.Ref(acceptanceVector_L);\n\t\t\t\t\t\t\tnewstatesL.add(acceptanceVector_L);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t//if(!valid)\n\t\t\t\t\tJDD.Deref(acceptanceVector_L);\n\t\t\t\t}\n\t\t\t\tJDD.Deref(candidateStates);\n\t\t\t}\n\t\t\tJDD.Deref(intersection);\n\n\t\t\tif (!newstatesH.isEmpty() /*&& i+1 < dra.length*/) {\n\t\t\t\t// generate a new element and put it into queue\n\t\t\t\tList<Integer> ids = new ArrayList<Integer>(e.draIDs);\n\t\t\t\tids.add(i);\n\t\t\t\tqueueElement e1 = new queueElement(newstatesH, newstatesL, allAcceptingStates, ids, i + 1);\n\t\t\t\tqueue.add(e1);\n\t\t\t\t// add link to e\n\t\t\t\te.addChildren(e1);\n\t\t\t} else\n\t\t\t\tJDD.Deref(allAcceptingStates);\n\n\t\t\t/*String s = \"\";\n\t\t\tfor(int j=0; j<e.draIDs.size(); j++) \n\t\t\t\ts += e.draIDs.*/\n\t\t\t/*vl = new StateListMTBDD(allAcceptingStates, model);\n\t\t\tvl.print(mainLog);\n\t\t\tmainLog.flush();*/\n\t\t}\n\n\t\t// add children generated by other elements to e\n\t\tfor (int i = bound - 1; i > sp; i--) {\n\t\t\tqueueElement e2 = queue.get(i);\n\t\t\tif (e2.draIDs.size() <= e.draIDs.size())\n\t\t\t\tbreak;\n\t\t\tif (e2.draIDs.containsAll(e.draIDs))\n\t\t\t\te.addChildren(e2);\n\t\t}\n\n\t\tif (e.draIDs.size() > 1) {\n\t\t\t//mainLog.println(\"          releaseing statesH & L \");\n\t\t\tfor (int i = 0; i < e.statesH.size(); i++) {\n\t\t\t\tJDD.Deref(e.statesH.get(i));\n\t\t\t\tJDD.Deref(e.statesL.get(i));\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Returns all end components in candidateStates under the fairness\n\t * assumption that all non-deterministic choices are treated fairly,\n\t * i.e., for each state that is visited infinitely often,\n\t * all non-deterministic choices are taken infinitely often as well.\n\t *\n\t * Iteratively removes all states from candidateStates that have any outgoing\n\t * transitions outside of candidateStates. The remaining states are those\n\t * states in candidateStates that will stay in candidateStates,\n\t * no matter which transition is taken.\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>candidateStates</i> ]\n\t * @param candidateStates Set of candidate states\n\t * @return subset of candidateStates that will never leave candidateStates (under fairness)\n\t */\n\tprivate JDDNode findFairECs(NondetModel model, JDDNode candidateStates)\n\t{\n\n\t\tJDDNode old = JDD.Constant(0);\n\t\tJDDNode current = candidateStates;\n\n\t\twhile (!current.equals(old)) {\n\t\t\tJDD.Deref(old);\n\t\t\tJDD.Ref(current);\n\t\t\told = current;\n\n\t\t\tJDD.Ref(current);\n\t\t\tJDD.Ref(model.getTrans01());\n\t\t\t// Select transitions starting in current\n\t\t\tJDDNode currTrans01 = JDD.And(model.getTrans01(), current);\n\t\t\tJDD.Ref(current);\n\t\t\t// mask of transitions that end outside current\n\t\t\tJDDNode mask = JDD.Not(JDD.PermuteVariables(current, model.getAllDDRowVars(), model.getAllDDColVars()));\n\t\t\tmask = JDD.And(currTrans01, mask);\n\t\t\t// mask of states that have bad transitions\n\t\t\tmask = JDD.ThereExists(mask, model.getAllDDColVars());\n\t\t\tmask = JDD.ThereExists(mask, model.getAllDDNondetVars());\n\t\t\t// Filter states with bad transitions\n\t\t\tcurrent = JDD.And(current, JDD.Not(mask));\n\t\t}\n\t\tJDD.Deref(old);\n\t\treturn current;\n\t}\n\n\t/**\n\t * Return the set of states that reach nodes through edges.\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: nodes, edges ]\n\t * @param nodes set of target states (BDD)\n\t * @param edges the edge relation to consider (BDD)\n\t */\n\tprivate JDDNode backwardSet(NondetModel model, JDDNode nodes, JDDNode edges)\n\t{\n\t\tJDDNode old = JDD.Constant(0);\n\t\tJDDNode current = nodes;\n\t\twhile (!current.equals(old)) {\n\t\t\tJDD.Deref(old);\n\t\t\tJDD.Ref(current);\n\t\t\told = current;\n\t\t\tJDD.Ref(current);\n\t\t\tJDD.Ref(edges);\n\t\t\tcurrent = JDD.Or(current, preimage(model, current, edges));\n\t\t}\n\t\tJDD.Deref(edges);\n\t\tJDD.Deref(old);\n\t\treturn current;\n\t}\n\n\t/**\n\t * Return the preimage of nodes in edges\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: nodes, edges ]\n\t */\n\t// FIXME: Refactor this out (duplicated in SCCComputers)\n\tprivate JDDNode preimage(NondetModel model, JDDNode nodes, JDDNode edges)\n\t{\n\t\tJDDNode tmp;\n\n\t\t// Get transitions that end at nodes\n\t\ttmp = JDD.PermuteVariables(nodes, model.getAllDDRowVars(), model.getAllDDColVars());\n\t\ttmp = JDD.And(edges, tmp);\n\t\t// Get pre(nodes)\n\t\ttmp = JDD.ThereExists(tmp, model.getAllDDColVars());\n\t\treturn tmp;\n\t}\n\n\t/**\n\t * Find (states of) all maximal end components (MECs) contained within {@code states}.\n\t *\n\t * <br>[ REFS: <i>results</i>, DEREFS: <i>none</i> ]\n\t * @param states BDD of the set of containing states\n\t * @return a vector of (referenced) BDDs representing the ECs\n\t */\n\tpublic List<JDDNode> findMECStates(NondetModel model, JDDNode states) throws PrismException\n\t{\n\t\tECComputer ecComputer = ECComputer.createECComputer(this, model);\n\t\tecComputer.computeMECStates(states, null);\n\t\treturn ecComputer.getMECStates();\n\t}\n\n\t/**\n\t * Find (states of) all accepting maximal end components (MECs) contained within {@code states},\n\t * where acceptance is defined as those which intersect with {@code filter}.\n\t * (If {@code filter} is null, the acceptance condition is trivially satisfied.)\n\t *\n\t * <br>[ REFS: <i>results</i>, DEREFS: <i>none</i> ]\n\t * @param states BDD of the set of containing states\n\t * @param filter BDD for the set of accepting states\n\t * @return a vector of (referenced) BDDs representing the ECs\n\t */\n\tpublic List<JDDNode> findMECStates(NondetModel model, JDDNode states, JDDNode filter) throws PrismException\n\t{\n\t\tECComputer ecComputer = ECComputer.createECComputer(this, model);\n\t\tecComputer.computeMECStates(states, filter);\n\t\treturn ecComputer.getMECStates();\n\t}\n\n\t/**\n\t * Find all maximal end components (ECs) contained within {@code states}\n\t * and whose states have no outgoing transitions.\n\t * @param states BDD of the set of containing states\n\t * @return a vector of (referenced) BDDs representing the ECs\n\t */\n\tpublic List<JDDNode> findBottomEndComponents(NondetModel model, JDDNode states) throws PrismException\n\t{\n\t\tList<JDDNode> ecs = findMECStates(model, states);\n\t\tList<JDDNode> becs = new Vector<JDDNode>();\n\t\tJDDNode out;\n\n\t\tfor (JDDNode scc : ecs) {\n\t\t\tJDD.Ref(model.getTrans01());\n\t\t\tJDD.Ref(scc);\n\t\t\tout = JDD.And(model.getTrans01(), scc);\n\t\t\tJDD.Ref(scc);\n\t\t\tout = JDD.And(out, JDD.Not(JDD.PermuteVariables(scc, model.getAllDDRowVars(), model.getAllDDColVars())));\n\t\t\tif (out.equals(JDD.ZERO)) {\n\t\t\t\tbecs.add(scc);\n\t\t\t} else {\n\t\t\t\tJDD.Deref(scc);\n\t\t\t}\n\t\t\tJDD.Deref(out);\n\t\t}\n\t\treturn becs;\n\t}\n\n\tpublic JDDNode maxStableSetTrans1(NondetModel model, JDDNode b)\n\t{\n\n\t\tJDD.Ref(b);\n\t\tJDD.Ref(model.getTrans());\n\t\t// Select transitions starting in b\n\t\tJDDNode currTrans = JDD.Apply(JDD.TIMES, model.getTrans(), b);\n\t\tJDDNode mask = JDD.PermuteVariables(b, model.getAllDDRowVars(), model.getAllDDColVars());\n\t\t// Select transitions starting in current and ending in current\n\t\tmask = JDD.Apply(JDD.TIMES, currTrans, mask);\n\t\t// Sum all successor probabilities for each (state, action) tuple\n\t\tmask = JDD.SumAbstract(mask, model.getAllDDColVars());\n\t\t// If the sum for a (state,action) tuple is 1,\n\t\t// there is an action that remains in the stable set with prob 1\n\t\tmask = JDD.GreaterThan(mask, 1 - settings.getDouble(PrismSettings.PRISM_SUM_ROUND_OFF));\n\t\t// select the transitions starting in these tuples\n\t\tJDD.Ref(model.getTrans01());\n\t\tJDDNode stableTrans01 = JDD.And(model.getTrans01(), mask);\n\t\t// Abstract over actions\n\t\treturn stableTrans01;\n\t}\n\n\t/**\n\t * Return the union of sets from {@code sets} which have a non-empty intersection with {@code filter}.\n\t * @param sets List of BDDs representing sets (dereferenced after calling this function)\n\t * @param filter BDD of states to test for intersection (dereferenced after calling)\n\t * @return Referenced BDD representing the filtered union\n\t */\n\tprivate JDDNode filteredUnion(List<JDDNode> sets, JDDNode filter)\n\t{\n\t\tJDDNode union = JDD.Constant(0);\n\t\tfor (JDDNode set : sets) {\n\t\t\tif (JDD.AreIntersecting(set, filter))\n\t\t\t\tunion = JDD.Or(union, set);\n\t\t\telse\n\t\t\t\tJDD.Deref(set);\n\t\t}\n\t\tJDD.Deref(filter);\n\t\treturn union;\n\t}\n\n\tclass queueElement\n\t{\n\t\tList<JDDNode> statesH;\n\t\tList<JDDNode> statesL;\n\t\tJDDNode targetDD;\n\t\tList<Integer> draIDs;\n\t\tint next;\n\t\tList<queueElement> children;\n\n\t\tpublic queueElement(List<JDDNode> statesH, List<JDDNode> statesL, JDDNode targetDD, List<Integer> draIDs, int next)\n\t\t{\n\t\t\tthis.statesH = statesH;\n\t\t\tthis.statesL = statesL;\n\t\t\tthis.targetDD = targetDD;\n\t\t\tthis.draIDs = draIDs;\n\t\t\tthis.next = next;\n\t\t}\n\n\t\tpublic void addChildren(queueElement child)\n\t\t{\n\t\t\tif (children == null)\n\t\t\t\tchildren = new ArrayList<queueElement>();\n\t\t\tchildren.add(child);\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/symbolic/comp/ModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport jdd.JDDNode;\nimport parser.Values;\nimport parser.ast.*;\nimport prism.PrismException;\nimport prism.Result;\nimport symbolic.states.StateValues;\n\n// interface for model checker classes\n\npublic interface ModelChecker\n{\n\t/**\n\t * Model check an expression, process, print and return the result.\n\t */\n\tpublic Result check(Expression expr) throws PrismException;\n\n\t/**\n\t * Model check an expression and return a vector of result values,\n\t * with valid results for at least all states of interest.\n\t *\n\t * @param expr the expression\n\t * @param statesOfInterest the states of interest.\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tpublic StateValues checkExpression(Expression expr, JDDNode statesOfInterest) throws PrismException;\n\n\t/**\n\t * Model check expression, convert to symbolic form (if not already), return BDD.\n\t * <br>\n\t * Will have valid results at least for all states of interest.\n\t * @param expr the expression\n\t * @param statesOfInterest the states of interest\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tpublic JDDNode checkExpressionDD(Expression expr, JDDNode statesOfInterest) throws PrismException;\n\n\t/** Get the constant values (both from the modules file and the properties file) */\n\tpublic Values getConstantValues();\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/comp/MultiObjModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t* Hongyang Qu <hongyang.qu@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.io.FileNotFoundException;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Vector;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport mtbdd.PrismMTBDD;\nimport parser.ast.Expression;\nimport parser.ast.RelOp;\nimport prism.*;\nimport sparse.NDSparseMatrix;\nimport sparse.PrismSparse;\nimport acceptance.AcceptanceRabin;\nimport automata.DA;\nimport automata.LTL2DA;\nimport dv.DoubleVector;\nimport symbolic.model.NondetModel;\n\n/**\n * Multi-objective model checking functionality\n */\npublic class MultiObjModelChecker extends PrismNativeComponent\n{\n\tprotected boolean verbose;\n\n\t/**\n\t * Create a new MultiObjModelChecker, inherit basic state from parent (unless null).\n\t */\n\tpublic MultiObjModelChecker(Prism prism) throws PrismException\n\t{\n\t\tsuper(prism);\n\t\tthis.verbose = settings.getBoolean(PrismSettings.PRISM_VERBOSE);\n\t}\n\n\t//TODO: dra's element is changed here, not neat.\n\tprotected NondetModel constructDRAandProductMulti(NondetModel model, LTLModelChecker mcLtl, ModelChecker modelChecker, Expression ltl, int i,\n\t\t\t\t\t\t\t\t\t\t\t\t\t  DA<BitSet, AcceptanceRabin> dra[], Operator operator, Expression pathFormula, JDDVars draDDRowVars, JDDVars draDDColVars, JDDNode ddStateIndex)\n\t\t\tthrows PrismException\n\t{\n\n\t\t// TODO (JK): Adapt to support simple path formulas with bounds via DRA construction\n\n\t\t// Model check maximal state formulas\n\t\tVector<JDDNode> labelDDs = new Vector<JDDNode>();\n\t\tltl = mcLtl.checkMaximalStateFormulas(modelChecker, model, pathFormula.deepCopy(), labelDDs);\n\n\t\t// Convert LTL formula to deterministic Rabin automaton (DRA)\n\t\t// For min probabilities, need to negate the formula\n\t\t// (add parentheses to allow re-parsing if required)\n\t\tif (Operator.isMinOrLe(operator))\n\t\t\tltl = Expression.Not(Expression.Parenth(ltl));\n\t\tmainLog.println(\"\\nBuilding deterministic Rabin automaton (for \" + ltl + \")...\");\n\t\tlong l = System.currentTimeMillis();\n\t\tLTL2DA ltl2da = new LTL2DA(this);\n\t\tdra[i] = ltl2da.convertLTLFormulaToDRA(ltl, modelChecker.getConstantValues());\n\t\tmainLog.print(\"DRA has \" + dra[i].size() + \" states, \" + dra[i].getAcceptance().getSizeStatistics() + \".\");\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"Time for Rabin translation: \" + l / 1000.0 + \" seconds.\");\n\t\t// If required, export DRA \n\t\tif (settings.getExportPropAut()) {\n\t\t\tString exportPropAutFilename = PrismUtils.addCounterSuffixToFilename(settings.getExportPropAutFilename(), i + 1);\n\t\t\tmainLog.println(\"Exporting DRA to file \\\"\" + exportPropAutFilename + \"\\\"...\");\n\t\t\tPrintStream out = PrismUtils.newPrintStream(exportPropAutFilename);\n\t\t\tdra[i].print(out, settings.getExportPropAutType());\n\t\t\tout.close();\n\t\t}\n\n\t\t// Build product of MDP and automaton\n\t\tmainLog.println(\"\\nConstructing MDP-DRA product...\");\n\n\t\tNondetModel modelNew = mcLtl.constructProductMDP(dra[i], model, labelDDs, draDDRowVars, draDDColVars, (i == 0 ? ddStateIndex : model.getStart()).copy());\n\n\t\tmodelNew.printTransInfo(mainLog, prism.getExtraDDInfo());\n\t\t// Deref label BDDs\n\t\tfor (int j = 0; j < labelDDs.size(); j++) {\n\t\t\tJDD.Deref(labelDDs.get(j));\n\t\t}\n\t\treturn modelNew;\n\t}\n\n\t/**\n\t * \n\t * @param modelProduct\n\t * @param rewardsIndex\n\t * @param opsAndBounds\n\t * @return True if some transitions were removed\n\t */\n\tprotected boolean removeNonZeroRewardTrans(NondetModel modelProduct, List<JDDNode> rewardsIndex, OpsAndBoundsList opsAndBounds)\n\t{\n\t\tboolean transchanged = false;\n\t\tfor (int i = 0; i < rewardsIndex.size(); i++)\n\t\t\tif (opsAndBounds.getRewardOperator(i) == Operator.R_MIN || opsAndBounds.getRewardOperator(i) == Operator.R_LE) {\n\t\t\t\t// Get non-zero reward actions\n\t\t\t\tJDD.Ref(rewardsIndex.get(i));\n\t\t\t\tJDDNode actions = JDD.GreaterThan(rewardsIndex.get(i), 0.0);\n\t\t\t\tif (!actions.equals(JDD.ZERO)) {\n\t\t\t\t\t//mainLog.println(\"Removing non-zero reward actions in reward #\" + i);\n\t\t\t\t\tif (!transchanged)\n\t\t\t\t\t\tJDD.Ref(modelProduct.getTrans());\n\t\t\t\t\tmodelProduct.resetTrans(JDD.ITE(actions.copy(), JDD.Constant(0), modelProduct.getTrans().copy()));\n\t\t\t\t\tif (!transchanged)\n\t\t\t\t\t\tJDD.Ref(modelProduct.getTrans01());\n\t\t\t\t\tmodelProduct.resetTrans01(JDD.ITE(actions, JDD.Constant(0), modelProduct.getTrans01().copy()));\n\t\t\t\t\ttranschanged = true;\n\t\t\t\t}\n\t\t\t}\n\t\treturn transchanged;\n\t}\n\n\tprotected List<JDDNode> computeAllEcs(NondetModel modelProduct, LTLModelChecker mcLtl, ArrayList<ArrayList<JDDNode>> allstatesH,\n\t\t\tArrayList<ArrayList<JDDNode>> allstatesL, JDDNode acceptanceVector_H, JDDNode acceptanceVector_L, JDDVars draDDRowVars[], JDDVars draDDColVars[],\n\t\t\tOpsAndBoundsList opsAndBounds, int numTargets) throws PrismException\n\t{\n\t\t//use acceptanceVector_H and acceptanceVector_L to speed up scc computation\n\t\tJDD.Ref(acceptanceVector_H);\n\t\tJDD.Ref(modelProduct.getTrans01());\n\t\tJDDNode candidateStates = JDD.Apply(JDD.TIMES, modelProduct.getTrans01(), acceptanceVector_H);\n\t\tfor (int i = 0; i < numTargets; i++)\n\t\t\tif (opsAndBounds.isProbabilityObjective(i)) {\n\t\t\t\tacceptanceVector_H = JDD.PermuteVariables(acceptanceVector_H, draDDRowVars[i], draDDColVars[i]);\n\t\t\t}\n\t\tcandidateStates = JDD.Apply(JDD.TIMES, candidateStates, acceptanceVector_H);\n\t\tcandidateStates = JDD.ThereExists(candidateStates, modelProduct.getAllDDColVars());\n\t\tcandidateStates = JDD.ThereExists(candidateStates, modelProduct.getAllDDNondetVars());\n\t\t// find all maximal end components\n\t\tList<JDDNode> allecs = mcLtl.findMECStates(modelProduct, candidateStates, acceptanceVector_L);\n\t\tJDD.Deref(candidateStates);\n\t\tJDD.Deref(acceptanceVector_L);\n\t\treturn allecs;\n\t}\n\n\t//computes accepting end component for the Rabin automaton dra.\n\t//Vojta: in addition to calling a method which does the computation\n\t//there are some other bits which I don't currently understand\n\tprotected JDDNode computeAcceptingEndComponent(DA<BitSet, AcceptanceRabin> dra, NondetModel modelProduct, JDDVars draDDRowVars, JDDVars draDDColVars,\n\t\t\tList<JDDNode> allecs, List<JDDNode> statesH, List<JDDNode> statesL, //Vojta: at the time of writing this I have no idea what these two parameters do, so I don't know how to call them\n\t\t\tLTLModelChecker mcLtl, boolean conflictformulaeGtOne) throws PrismException\n\t{\n\t\tlong l = System.currentTimeMillis();\n\t\t// increase ref count for checking conflict formulas\n\t\tif (conflictformulaeGtOne) {\n\t\t\tfor (JDDNode n : statesH)\n\t\t\t\tJDD.Ref(n);\n\t\t\tfor (JDDNode n : statesL)\n\t\t\t\tJDD.Ref(n);\n\t\t}\n\t\tJDDNode ret = mcLtl.findMultiAcceptingStates(dra, modelProduct, draDDRowVars, draDDColVars, false, allecs, statesH, statesL);\n\t\t//targetDDs.add(mcLtl.findMultiAcceptingStates(dra[i], modelProduct, draDDRowVars[i], draDDColVars[i], false));\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"Time for end component identification: \" + l / 1000.0 + \" seconds.\");\n\t\treturn ret;\n\t}\n\n\tprotected void removeNonZeroMecsForMax(NondetModel modelProduct, LTLModelChecker mcLtl, List<JDDNode> rewardsIndex, OpsAndBoundsList opsAndBounds,\n\t\t\tint numTargets, DA<BitSet, AcceptanceRabin> dra[], JDDVars draDDRowVars[], JDDVars draDDColVars[]) throws PrismException\n\t{\n\t\tList<JDDNode> mecs = mcLtl.findMECStates(modelProduct, modelProduct.getReach());\n\t\tJDDNode removedActions = JDD.Constant(0);\n\t\tJDDNode rmecs = JDD.Constant(0);\n\t\tfor (int i = 0; i < rewardsIndex.size(); i++)\n\t\t\tif (opsAndBounds.getRewardOperator(i) == Operator.R_MAX || opsAndBounds.getRewardOperator(i) == Operator.R_GE) {\n\t\t\t\tJDD.Ref(rewardsIndex.get(i));\n\t\t\t\tJDDNode actions = JDD.GreaterThan(rewardsIndex.get(i), 0.0);\n\t\t\t\tif (!actions.equals(JDD.ZERO))\n\t\t\t\t\tfor (int j = 0; j < mecs.size(); j++) {\n\t\t\t\t\t\tJDDNode mec = mecs.get(j);\n\t\t\t\t\t\tJDD.Ref(mec);\n\t\t\t\t\t\tJDDNode mecactions = mcLtl.maxStableSetTrans1(modelProduct, mec);\n\t\t\t\t\t\tJDD.Ref(actions);\n\t\t\t\t\t\tmecactions = JDD.And(actions, mecactions);\n\t\t\t\t\t\tif (!mecactions.equals(JDD.ZERO)) {\n\t\t\t\t\t\t\tJDD.Ref(mec);\n\t\t\t\t\t\t\trmecs = JDD.Or(rmecs, mec);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tremovedActions = JDD.Or(removedActions, mecactions);\n\t\t\t\t\t}\n\t\t\t\tJDD.Deref(actions);\n\t\t\t}\n\t\tfor (JDDNode mec : mecs)\n\t\t\tJDD.Deref(mec);\n\t\t// TODO: check if the model satisfies the LTL constraints \n\t\tif (!rmecs.equals(JDD.ZERO)) {\n\t\t\tboolean constraintViolated = false;\n\t\t\tif (JDD.AreIntersecting(modelProduct.getStart(), rmecs)) {\n\t\t\t\tconstraintViolated = true;\n\t\t\t\tJDD.Deref(rmecs);\n\t\t\t} else {\n\t\t\t\t// find all action pointing to mecs from outside a\n\t\t\t\tJDD.Ref(rmecs);\n\t\t\t\tJDDNode rtarget = JDD.PermuteVariables(rmecs, modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars());\n\t\t\t\tJDD.Ref(modelProduct.getTrans01());\n\t\t\t\trtarget = JDD.And(modelProduct.getTrans01(), rtarget);\n\t\t\t\trtarget = JDD.And(rtarget, JDD.Not(rmecs));\n\t\t\t\t//rtarget = JDD.ThereExists(rtarget, modelProduct.getAllDDColVars());\n\t\t\t\t// find target states for LTL formulae\n\t\t\t\tVector<JDDNode> tmptargetDDs = new Vector<JDDNode>();\n\t\t\t\tList<JDDNode> tmpmultitargetDDs = new ArrayList<JDDNode>();\n\t\t\t\tList<Integer> tmpmultitargetIDs = new ArrayList<Integer>();\n\t\t\t\tArrayList<DA<BitSet, AcceptanceRabin>> tmpdra = new ArrayList<DA<BitSet, AcceptanceRabin>>();\n\t\t\t\tArrayList<JDDVars> tmpdraDDRowVars = new ArrayList<JDDVars>();\n\t\t\t\tArrayList<JDDVars> tmpdraDDColVars = new ArrayList<JDDVars>();\n\t\t\t\tint count = 0;\n\t\t\t\tfor (int i = 0; i < numTargets; i++)\n\t\t\t\t\tif (opsAndBounds.isProbabilityObjective(i) && opsAndBounds.getOperator(i) != Operator.P_MAX\n\t\t\t\t\t\t\t&& opsAndBounds.getOperator(i) != Operator.P_MIN) {\n\t\t\t\t\t\ttmpdra.add(dra[i]);\n\t\t\t\t\t\ttmpdraDDRowVars.add(draDDRowVars[i]);\n\t\t\t\t\t\ttmpdraDDColVars.add(draDDColVars[i]);\n\t\t\t\t\t\tcount++;\n\t\t\t\t\t}\n\t\t\t\tif (count > 0) {\n\t\t\t\t\t// TODO: distinguish whether rtarget is empty\n\t\t\t\t\tDA<BitSet, AcceptanceRabin> newdra[] = new DA[count];\n\t\t\t\t\ttmpdra.toArray(newdra);\n\t\t\t\t\tJDDVars newdraDDRowVars[] = new JDDVars[count];\n\t\t\t\t\ttmpdraDDRowVars.toArray(newdraDDRowVars);\n\t\t\t\t\tJDDVars newdraDDColVars[] = new JDDVars[count];\n\t\t\t\t\ttmpdraDDColVars.toArray(newdraDDColVars);\n\n\t\t\t\t\tfindTargetStates(modelProduct, mcLtl, count, count, new boolean[count], newdra, newdraDDRowVars, newdraDDColVars, tmptargetDDs,\n\t\t\t\t\t\t\ttmpmultitargetDDs, tmpmultitargetIDs);\n\n\t\t\t\t\tOpsAndBoundsList tmpOpsAndBounds = new OpsAndBoundsList();\n\n\t\t\t\t\tfor (int i = 0; i < opsAndBounds.probSize(); i++) {\n\t\t\t\t\t\tif (opsAndBounds.getProbOperator(i) != Operator.P_MAX) {\n\t\t\t\t\t\t\ttmpOpsAndBounds.add(opsAndBounds.getOpRelOpBound(i), opsAndBounds.getProbOperator(i), opsAndBounds.getProbBound(i),\n\t\t\t\t\t\t\t\t\topsAndBounds.getProbStepBound(i), i);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\ttmpOpsAndBounds.add(new OpRelOpBound(\"R\", RelOp.MAX, -1.0), Operator.R_MAX, -1.0, -1, opsAndBounds.probSize());\n\n\t\t\t\t\tArrayList<JDDNode> tmprewards = new ArrayList<JDDNode>(1);\n\t\t\t\t\ttmprewards.add(rtarget);\n\t\t\t\t\tdouble prob = (Double) computeMultiReachProbs(modelProduct, mcLtl, tmprewards, modelProduct.getStart(), tmptargetDDs, tmpmultitargetDDs,\n\t\t\t\t\t\t\ttmpmultitargetIDs, tmpOpsAndBounds, count > 1);\n\t\t\t\t\tif (prob > 0.0) { // LTL formulae can be satisfied\n\t\t\t\t\t\tconstraintViolated = true;\n\t\t\t\t\t} else if (Double.isNaN(prob))\n\t\t\t\t\t\tthrow new PrismException(\"The LTL formulae in multi-objective query cannot be satisfied!\\n\");\n\t\t\t\t} else {\n\t\t\t\t\t// end components with non-zero rewards can always be reached\n\t\t\t\t\tconstraintViolated = true;\n\t\t\t\t}\n\n\t\t\t\t//JDD.Deref(rtarget);\n\t\t\t\tfor (JDDNode tt : tmptargetDDs)\n\t\t\t\t\tJDD.Deref(tt);\n\t\t\t\tfor (JDDNode tt : tmpmultitargetDDs)\n\t\t\t\t\tJDD.Deref(tt);\n\t\t\t}\n\t\t\tif (constraintViolated) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Cannot use multi-objective model checking with maximising objectives and non-zero reward end compoments\");\n\t\t\t}\n\n\t\t\tJDD.Ref(removedActions);\n\t\t\tmodelProduct.resetTrans(JDD.Apply(JDD.TIMES, modelProduct.getTrans().copy(), JDD.Not(removedActions)));\n\t\t\tmodelProduct.resetTrans01(JDD.Apply(JDD.TIMES, modelProduct.getTrans01().copy(), JDD.Not(removedActions)));\n\t\t} else {\n\t\t\tJDD.Deref(rmecs);\n\t\t\tJDD.Deref(removedActions);\n\t\t}\n\n\t}\n\n\t//TODO is conflictformulae actually just no of prob?\n\tprotected void checkConflictsInObjectives(NondetModel modelProduct, LTLModelChecker mcLtl, int conflictformulae, int numTargets,\n\t\t\tOpsAndBoundsList opsAndBounds, DA<BitSet, AcceptanceRabin> dra[], JDDVars draDDRowVars[], JDDVars draDDColVars[], List<JDDNode> targetDDs,\n\t\t\tList<ArrayList<JDDNode>> allstatesH, List<ArrayList<JDDNode>> allstatesL, List<JDDNode> multitargetDDs, List<Integer> multitargetIDs)\n\t\t\tthrows PrismException\n\t{\n\t\tDA<BitSet, AcceptanceRabin>[] tmpdra = new DA[conflictformulae];\n\t\tJDDVars[] tmpdraDDRowVars = new JDDVars[conflictformulae];\n\t\tJDDVars[] tmpdraDDColVars = new JDDVars[conflictformulae];\n\t\tList<JDDNode> tmptargetDDs = new ArrayList<JDDNode>(conflictformulae);\n\t\tList<List<JDDNode>> tmpallstatesH = new ArrayList<List<JDDNode>>(conflictformulae);\n\t\tList<List<JDDNode>> tmpallstatesL = new ArrayList<List<JDDNode>>(conflictformulae);\n\t\tint count = 0;\n\t\tfor (int i = 0; i < numTargets; i++)\n\t\t\tif (opsAndBounds.isProbabilityObjective(i)) {\n\t\t\t\ttmpdra[count] = dra[i];\n\t\t\t\ttmpdraDDRowVars[count] = draDDRowVars[i];\n\t\t\t\ttmpdraDDColVars[count] = draDDColVars[i];\n\t\t\t\t// tricky part; double check when reachExpr is set for efficiency\n\t\t\t\ttmptargetDDs.add(targetDDs.get(count));\n\t\t\t\ttmpallstatesH.add(allstatesH.get(i));\n\t\t\t\ttmpallstatesL.add(allstatesL.get(i));\n\t\t\t\tcount++;\n\t\t\t}\n\t\tList<List<Integer>> tmpmultitargetIDs = new ArrayList<List<Integer>>();\n\n\t\tmcLtl.findMultiConflictAcceptingStates(tmpdra, modelProduct, tmpdraDDRowVars, tmpdraDDColVars, tmptargetDDs, tmpallstatesH, tmpallstatesL,\n\t\t\t\tmultitargetDDs, tmpmultitargetIDs);\n\t\t// again. double check when reachExpr is set\n\t\tcount = 0;\n\t\tfor (int i = 0; i < numTargets; i++)\n\t\t\tif (opsAndBounds.isProbabilityObjective(i)) {\n\t\t\t\ttargetDDs.remove(count);\n\t\t\t\ttargetDDs.add(count, tmptargetDDs.get(count));\n\t\t\t\tcount++;\n\t\t\t}\n\n\t\t// deal with reachability targets\n\t\tfor (int i = 0; i < tmpmultitargetIDs.size(); i++) {\n\t\t\tmultitargetIDs.add(changeToInteger(tmpmultitargetIDs.get(i)));\n\t\t\t//System.out.println(\"multitargetIDs[\"+i+\"] = \" + multitargetIDs.get(i));\n\t\t}\n\n\t\tfor (int i = 0; i < numTargets; i++)\n\t\t\tif (opsAndBounds.isProbabilityObjective(i)) {\n\t\t\t\tList<JDDNode> tmpLH = allstatesH.get(i);\n\t\t\t\tfor (JDDNode n : tmpLH)\n\t\t\t\t\tJDD.Deref(n);\n\t\t\t\ttmpLH = allstatesL.get(i);\n\t\t\t\tfor (JDDNode n : tmpLH)\n\t\t\t\t\tJDD.Deref(n);\n\t\t\t}\n\t}\n\n\tprotected void findTargetStates(NondetModel modelProduct, LTLModelChecker mcLtl, int numTargets, int conflictformulae, boolean reachExpr[],\n\t\t\tDA<BitSet, AcceptanceRabin> dra[], JDDVars draDDRowVars[], JDDVars draDDColVars[], List<JDDNode> targetDDs, List<JDDNode> multitargetDDs,\n\t\t\tList<Integer> multitargetIDs) throws PrismException\n\t{\n\t\tint i, j;\n\t\tlong l;\n\n\t\t// Compute all maximal end components\n\t\tArrayList<ArrayList<JDDNode>> allstatesH = new ArrayList<ArrayList<JDDNode>>(numTargets);\n\t\tArrayList<ArrayList<JDDNode>> allstatesL = new ArrayList<ArrayList<JDDNode>>(numTargets);\n\t\tJDDNode acceptanceVector_H = JDD.Constant(0);\n\t\tJDDNode acceptanceVector_L = JDD.Constant(0);\n\t\tfor (i = 0; i < numTargets; i++) {\n\t\t\tif (!reachExpr[i]) {\n\t\t\t\tArrayList<JDDNode> statesH = new ArrayList<JDDNode>();\n\t\t\t\tArrayList<JDDNode> statesL = new ArrayList<JDDNode>();\n\t\t\t\tfor (int k = 0; k < dra[i].getAcceptance().size(); k++) {\n\t\t\t\t\tJDDNode tmpH = JDD.Constant(0);\n\t\t\t\t\tJDDNode tmpL = JDD.Constant(0);\n\t\t\t\t\tfor (j = 0; j < dra[i].size(); j++) {\n\t\t\t\t\t\tif (!dra[i].getAcceptance().get(k).getL().get(j)) {\n\t\t\t\t\t\t\ttmpH = JDD.SetVectorElement(tmpH, draDDRowVars[i], j, 1.0);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (dra[i].getAcceptance().get(k).getK().get(j)) {\n\t\t\t\t\t\t\ttmpL = JDD.SetVectorElement(tmpL, draDDRowVars[i], j, 1.0);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tstatesH.add(tmpH);\n\t\t\t\t\tJDD.Ref(tmpH);\n\t\t\t\t\tacceptanceVector_H = JDD.Or(acceptanceVector_H, tmpH);\n\t\t\t\t\tstatesL.add(tmpL);\n\t\t\t\t\tJDD.Ref(tmpL);\n\t\t\t\t\tacceptanceVector_L = JDD.Or(acceptanceVector_L, tmpL);\n\t\t\t\t}\n\t\t\t\tallstatesH.add(i, statesH);\n\t\t\t\tallstatesL.add(i, statesL);\n\t\t\t} else {\n\t\t\t\tallstatesH.add(i, null);\n\t\t\t\tallstatesL.add(i, null);\n\t\t\t}\n\t\t}\n\n\t\t// Find accepting maximum end components for each LTL formula\n\t\tList<JDDNode> allecs = null;\n\t\t//use acceptanceVector_H and acceptanceVector_L to speed up scc computation\n\t\t/*// check number of states in each scc\n\t\tallecs = mcLtl.findEndComponents(modelProduct, modelProduct.getReach());\n\t\tStateListMTBDD vl;\n\t\tint totalNum = 0;\n\t\tfor(JDDNode set : allecs) {\n\t\t\tvl = new StateListMTBDD(set, modelProduct);\n\t\t\ttotalNum += vl.size() - 1;\n\t\t}\n\t\tmainLog.println(\"Total number of states can be saved: \" + totalNum);*/\n\n\t\tJDD.Ref(acceptanceVector_H);\n\t\tJDD.Ref(modelProduct.getTrans01());\n\t\tJDDNode candidateStates = JDD.Apply(JDD.TIMES, modelProduct.getTrans01(), acceptanceVector_H);\n\t\tfor (i = 0; i < numTargets; i++)\n\t\t\tif (!reachExpr[i]) {\n\t\t\t\tacceptanceVector_H = JDD.PermuteVariables(acceptanceVector_H, draDDRowVars[i], draDDColVars[i]);\n\t\t\t}\n\t\tcandidateStates = JDD.Apply(JDD.TIMES, candidateStates, acceptanceVector_H);\n\t\tcandidateStates = JDD.ThereExists(candidateStates, modelProduct.getAllDDColVars());\n\t\tcandidateStates = JDD.ThereExists(candidateStates, modelProduct.getAllDDNondetVars());\n\t\t// find all maximal end components\n\t\tallecs = mcLtl.findMECStates(modelProduct, candidateStates, acceptanceVector_L);\n\t\tJDD.Deref(candidateStates);\n\t\tJDD.Deref(acceptanceVector_L);\n\n\t\tfor (i = 0; i < numTargets; i++) {\n\t\t\tif (!reachExpr[i]) {\n\t\t\t\t//mainLog.println(\"\\nFinding accepting end components for \" + targetName[i] + \"...\");\n\t\t\t\tl = System.currentTimeMillis();\n\t\t\t\t// increase ref count for checking conflict formulas\n\t\t\t\tif (conflictformulae > 1) {\n\t\t\t\t\tList<JDDNode> tmpLH = allstatesH.get(i);\n\t\t\t\t\tfor (JDDNode n : tmpLH)\n\t\t\t\t\t\tJDD.Ref(n);\n\t\t\t\t\ttmpLH = allstatesL.get(i);\n\t\t\t\t\tfor (JDDNode n : tmpLH)\n\t\t\t\t\t\tJDD.Ref(n);\n\t\t\t\t}\n\t\t\t\ttargetDDs.add(mcLtl.findMultiAcceptingStates(dra[i], modelProduct, draDDRowVars[i], draDDColVars[i], false, allecs, allstatesH.get(i),\n\t\t\t\t\t\tallstatesL.get(i)));\n\t\t\t\t//targetDDs.add(mcLtl.findMultiAcceptingStates(dra[i], modelProduct, draDDRowVars[i], draDDColVars[i], false));\n\t\t\t\tl = System.currentTimeMillis() - l;\n\t\t\t\tmainLog.println(\"Time for end component identification: \" + l / 1000.0 + \" seconds.\");\n\t\t\t} /*else {\n\t\t\t\t// Fixme: maybe not efficient\n\t\t\t\tif(targetExprs.get(i) != null) {\n\t\t\t\t\tdd = checkExpressionDD(targetExprs.get(i));\n\t\t\t\t\tJDD.Ref(modelProduct.getReach());\n\t\t\t\t\tdd = JDD.And(dd, modelProduct.getReach());\n\t\t\t\t\ttargetDDs.add(dd);\n\t\t\t\t}\n\t\t\t\t}*/\n\t\t\t//mainLog.print(\"\\n    number of targets = \" + JDD.GetNumMintermsString(targetDDs.get(i), modelProduct.getAllDDRowVars().n()));\n\t\t\t//if(i>0)\n\t\t\t//\tmainLog.print(\"\\n  total number of targets = \" + \n\t\t\t//\t\t\tJDD.GetNumMintermsString(JDD.Or(targetDDs.get(i), targetDDs.get(i-1)), modelProduct.getAllDDRowVars().n()));\n\t\t}\n\n\t\t// check if there are conflicts in objectives\n\t\tif (conflictformulae > 1) {\n\t\t\tDA<BitSet, AcceptanceRabin>[] tmpdra = new DA[conflictformulae];\n\t\t\tJDDVars[] tmpdraDDRowVars = new JDDVars[conflictformulae];\n\t\t\tJDDVars[] tmpdraDDColVars = new JDDVars[conflictformulae];\n\t\t\tList<JDDNode> tmptargetDDs = new ArrayList<JDDNode>(conflictformulae);\n\t\t\tList<List<JDDNode>> tmpallstatesH = new ArrayList<List<JDDNode>>(conflictformulae);\n\t\t\tList<List<JDDNode>> tmpallstatesL = new ArrayList<List<JDDNode>>(conflictformulae);\n\t\t\tint count = 0;\n\t\t\tfor (i = 0; i < numTargets; i++)\n\t\t\t\tif (!reachExpr[i]) {\n\t\t\t\t\ttmpdra[count] = dra[i];\n\t\t\t\t\ttmpdraDDRowVars[count] = draDDRowVars[i];\n\t\t\t\t\ttmpdraDDColVars[count] = draDDColVars[i];\n\t\t\t\t\t// tricky part; double check when reachExpr is set for efficiency\n\t\t\t\t\ttmptargetDDs.add(targetDDs.get(count));\n\t\t\t\t\ttmpallstatesH.add(allstatesH.get(i));\n\t\t\t\t\ttmpallstatesL.add(allstatesL.get(i));\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t//multitargetDDs = new ArrayList<JDDNode>();\n\t\t\tList<List<Integer>> tmpmultitargetIDs = new ArrayList<List<Integer>>();\n\n\t\t\tmcLtl.findMultiConflictAcceptingStates(tmpdra, modelProduct, tmpdraDDRowVars, tmpdraDDColVars, tmptargetDDs, tmpallstatesH, tmpallstatesL,\n\t\t\t\t\tmultitargetDDs, tmpmultitargetIDs);\n\t\t\t// again. double check when reachExpr is set\n\t\t\tcount = 0;\n\t\t\tfor (i = 0; i < numTargets; i++)\n\t\t\t\tif (!reachExpr[i]) {\n\t\t\t\t\ttargetDDs.remove(count);\n\t\t\t\t\ttargetDDs.add(count, tmptargetDDs.get(count));\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\n\t\t\t// deal with reachability targets\n\t\t\t//multitargetIDs = new ArrayList<Integer>(tmpmultitargetIDs.size());\n\t\t\tfor (i = 0; i < tmpmultitargetIDs.size(); i++) {\n\t\t\t\tmultitargetIDs.add(changeToInteger(tmpmultitargetIDs.get(i)));\n\t\t\t}\n\n\t\t\tfor (i = 0; i < numTargets; i++)\n\t\t\t\tif (!reachExpr[i]) {\n\t\t\t\t\tList<JDDNode> tmpLH = allstatesH.get(i);\n\t\t\t\t\tfor (JDDNode n : tmpLH)\n\t\t\t\t\t\tJDD.Deref(n);\n\t\t\t\t\ttmpLH = allstatesL.get(i);\n\t\t\t\t\tfor (JDDNode n : tmpLH)\n\t\t\t\t\t\tJDD.Deref(n);\n\t\t\t\t}\n\t\t}\n\n\t\tfor (JDDNode ec : allecs)\n\t\t\tJDD.Deref(ec);\n\t}\n\n\tprivate int changeToInteger(List<Integer> ids)\n\t{\n\t\tint k = 0;\n\t\tfor (int i = 0; i < ids.size(); i++) {\n\t\t\tint j = 1;\n\t\t\tif (ids.get(i) > 0)\n\t\t\t\tj = j << ids.get(i);\n\t\t\tk += j;\n\t\t}\n\t\treturn k;\n\t}\n\n\t/**\n\t * Perform multi-objective model checking computation.\n\t * Solves achievability, numerical or Pareto queries over n objectives.\n\t *  \n\t * @param model The MDP\n\t * @param mcLtl An LTL model checker (for finding end components)\n\t * @param transRewards MTBDDs for transition rewards (reward objectives only)  \n\t * @param start BDD giving the (initial) state for which values are to be computed\n\t * @param targets BDDs giving sets of target states (probability objectives only)\n\t * @param combinations\n\t * @param combinationIDs\n\t * @param opsAndBounds Information about the list of objectives \n\t * @param hasconflictobjectives\n\t */\n\tprotected Object computeMultiReachProbs(NondetModel model, LTLModelChecker mcLtl, List<JDDNode> transRewards, JDDNode start, List<JDDNode> targets,\n\t\t\tList<JDDNode> combinations, List<Integer> combinationIDs, OpsAndBoundsList opsAndBounds, boolean hasconflictobjectives) throws PrismException\n\t{\n\t\tJDDNode yes, no, maybe, bottomec = null;\n\t\tObject value;\n\t\tint i, j, numTargets;\n\t\t//JDDNode maybe_r = null; // maybe states for the reward formula\n\t\t//JDDNode trr = null; // transition rewards\n\t\t//int op1 = relOps.get(0).intValue(); // the operator of the first objective query\n\n\t\t// Get number of targets\n\t\tnumTargets = targets.size();\n\n\t\tJDDNode labels[] = new JDDNode[numTargets];\n\t\t// Build temporary DDs for combined targets\n\t\tfor (i = 0; i < numTargets; i++) {\n\t\t\tJDD.Ref(targets.get(i));\n\t\t\tJDDNode tmp = targets.get(i);\n\t\t\tif (combinations != null) {\n\t\t\t\tfor (j = 0; j < combinations.size(); j++) {\n\t\t\t\t\tif ((combinationIDs.get(j) & (1 << i)) > 0) {\n\t\t\t\t\t\tJDD.Ref(combinations.get(j));\n\t\t\t\t\t\ttmp = JDD.Or(tmp, combinations.get(j));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tlabels[i] = tmp;\n\t\t}\n\n\t\t// If required, export info about target states \n\t\tif (prism.getExportTarget()) {\n\t\t\tJDDNode labels2[] = new JDDNode[numTargets + 1];\n\t\t\tString labelNames[] = new String[numTargets + 1];\n\t\t\tlabels2[0] = model.getStart();\n\t\t\tlabelNames[0] = \"init\";\n\t\t\tfor (i = 0; i < numTargets; i++) {\n\t\t\t\tlabels2[i + 1] = labels[i];\n\t\t\t\tlabelNames[i + 1] = \"target\" + i;\n\t\t\t}\n\t\t\ttry {\n\t\t\t\tmainLog.print(\"\\nExporting target states info to file \\\"\" + prism.getExportTargetFilename() + \"\\\"...\");\n\t\t\t\tPrismMTBDD.ExportLabels(labels2, labelNames, \"l\", model.getAllDDRowVars(), model.getODD(), Prism.EXPORT_PLAIN, prism.getExportTargetFilename());\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.println(\"\\nWarning: Could not export target to file \\\"\" + prism.getExportTargetFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t// yes - union of targets (just to compute no)\n\t\tyes = JDD.Constant(0);\n\t\t//n = targets.size();\n\t\tfor (i = 0; i < numTargets; i++) {\n\t\t\tJDD.Ref(targets.get(i));\n\t\t\tyes = JDD.Or(yes, targets.get(i));\n\t\t}\n\t\tif (combinations != null)\n\t\t\tfor (i = 0; i < combinations.size(); i++) {\n\t\t\t\tJDD.Ref(combinations.get(i));\n\t\t\t\tyes = JDD.Or(yes, combinations.get(i));\n\t\t\t}\n\n\t\tif (opsAndBounds.rewardSize() == 0)\n\t\t\tno = PrismMTBDD.Prob0A(model.getTrans01(), model.getReach(), model.getAllDDRowVars(), model.getAllDDColVars(), model.getAllDDNondetVars(),\n\t\t\t\t\tmodel.getReach(), yes);\n\t\telse {\n\t\t\tno = JDD.Constant(0);\n\t\t\tbottomec = PrismMTBDD.Prob0A(model.getTrans01(), model.getReach(), model.getAllDDRowVars(), model.getAllDDColVars(), model.getAllDDNondetVars(),\n\t\t\t\t\tmodel.getReach(), yes);\n\t\t\tList<JDDNode> becs = mcLtl.findMECStates(model, bottomec);\n\t\t\tJDD.Deref(bottomec);\n\t\t\tbottomec = JDD.Constant(0);\n\t\t\tfor (JDDNode ec : becs)\n\t\t\t\tbottomec = JDD.Or(bottomec, ec);\n\t\t}\n\n\t\t/*if(op1>2) { // the first query is about reward\n\t\t\tJDDNode no_r = PrismMTBDD.Prob0A(modelProduct.getTrans01(), modelProduct.getReach(), \n\t\t\t\t\tmodelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(), \n\t\t\t\t\tmodelProduct.getAllDDNondetVars(), modelProduct.getReach(), targets.get(0));\n\t\t\tJDD.Ref(no_r);\n\t\t\tmaybe_r = JDD.And(modelProduct.getReach(), JDD.Not(JDD.Or(targets.get(0), no_r)));\n\t\t\ttrr = modelProduct.getTransRewards();\n\t\t}*/\n\n\t\t// maybe\n\t\tJDD.Ref(model.getReach());\n\t\tJDD.Ref(yes);\n\t\tJDD.Ref(no);\n\t\tmaybe = JDD.And(model.getReach(), JDD.Not(JDD.Or(yes, no)));\n\n\t\tfor (i = 0; i < transRewards.size(); i++) {\n\t\t\tJDDNode tmp = transRewards.remove(i);\n\t\t\tJDD.Ref(no);\n\t\t\ttmp = JDD.Apply(JDD.TIMES, tmp, JDD.Not(no));\n\t\t\ttransRewards.add(i, tmp);\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\nyes = \" + JDD.GetNumMintermsString(yes, model.getAllDDRowVars().n()));\n\t\tmainLog.print(\", no = \" + JDD.GetNumMintermsString(no, model.getAllDDRowVars().n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, model.getAllDDRowVars().n()) + \"\\n\");\n\n\t\t// compute probabilities\n\t\tmainLog.println(\"\\nComputing remaining probabilities...\");\n\n\t\t// Local copies of settings\n\t\tint engine = settings.getChoice(PrismSettings.PRISM_ENGINE);\n\t\tint method = prism.getMDPMultiSolnMethod();\n\n\t\t// Switch engine, if necessary\n\t\tif (engine == Prism.HYBRID) {\n\t\t\tmainLog.println(\"Switching engine since only sparse engine currently supports this computation...\");\n\t\t\tengine = Prism.SPARSE;\n\t\t}\n\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\n\t\ttry {\n\t\t\t// Check for unsupported options\n\t\t\tif (engine != Prism.SPARSE) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Currently only sparse engine supports multi-objective properties\");\n\t\t\t}\n\t\t\tif (method == Prism.MDP_MULTI_LP && opsAndBounds.numberOfNumerical() > 1) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Pareto curve generation is not currently supported using linear programming\");\n\t\t\t}\n\n\t\t\t// Do computation\n\t\t\t// Linear programming\n\t\t\tif (method == Prism.MDP_MULTI_LP) {\n\n\t\t\t\tif (opsAndBounds.numberOfStepBounded() > 0) {\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Step-bounded objectives are not currently supported with linear programming\");\n\t\t\t\t}\n\n\t\t\t\tif (opsAndBounds.rewardSize() > 0) {\n\t\t\t\t\tif (hasconflictobjectives) {\n\t\t\t\t\t\tvalue = PrismSparse.NondetMultiReachReward1(model.getTrans(), model.getTransActions(), model.getSynchs(), model.getODD(),\n\t\t\t\t\t\t\t\tmodel.getAllDDRowVars(), model.getAllDDColVars(), model.getAllDDNondetVars(), targets, combinations, combinationIDs,\n\t\t\t\t\t\t\t\topsAndBounds, maybe, start, transRewards, bottomec);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tvalue = PrismSparse.NondetMultiReachReward(model.getTrans(), model.getTransActions(), model.getSynchs(), model.getODD(),\n\t\t\t\t\t\t\t\tmodel.getAllDDRowVars(), model.getAllDDColVars(), model.getAllDDNondetVars(), targets, opsAndBounds, maybe, start, transRewards,\n\t\t\t\t\t\t\t\tbottomec);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tif (hasconflictobjectives) {\n\t\t\t\t\t\tvalue = PrismSparse.NondetMultiReach1(model.getTrans(), model.getTransActions(), model.getSynchs(), model.getODD(),\n\t\t\t\t\t\t\t\tmodel.getAllDDRowVars(), model.getAllDDColVars(), model.getAllDDNondetVars(), targets, combinations, combinationIDs,\n\t\t\t\t\t\t\t\topsAndBounds, maybe, start);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tvalue = PrismSparse.NondetMultiReach(model.getTrans(), model.getTransActions(), model.getSynchs(), model.getODD(),\n\t\t\t\t\t\t\t\tmodel.getAllDDRowVars(), model.getAllDDColVars(), model.getAllDDNondetVars(), targets, opsAndBounds, maybe, start);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Value iteration\n\t\t\telse if (method == Prism.MDP_MULTI_GAUSSSEIDEL || method == Prism.MDP_MULTI_VALITER) {\n\t\t\t\tdouble timePre = System.currentTimeMillis();\n\t\t\t\tvalue = weightedMultiReachProbs(model, yes, maybe, start, labels, transRewards, opsAndBounds);\n\t\t\t\tdouble timePost = System.currentTimeMillis();\n\t\t\t\tdouble time = ((double) (timePost - timePre)) / 1000.0;\n\t\t\t\tmainLog.println(\"Multi-objective value iterations took \" + time + \" s.\");\n\t\t\t}\n\t\t\t// Unknown method (shouldn't happen)\n\t\t\telse {\n\t\t\t\tthrow new PrismException(\"Unknown multi-objective model checking method\");\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tthrow e;\n\t\t} finally {\n\t\t\t// derefs\n\t\t\tif (opsAndBounds.rewardSize() > 0)\n\t\t\t\tJDD.Deref(bottomec);\n\t\t\tJDD.Deref(yes);\n\t\t\tJDD.Deref(no);\n\t\t\tJDD.Deref(maybe);\n\t\t\tfor (int k = 0; k < labels.length; k++)\n\t\t\t\tJDD.Deref(labels[k]);\n\t\t\tfor (i = 0; i < transRewards.size(); i++) {\n\t\t\t\tJDD.Deref(transRewards.get(i));\n\t\t\t}\n\t\t}\n\n\t\treturn value;\n\t}\n\n\tprotected Object weightedMultiReachProbs(NondetModel modelProduct, JDDNode yes_ones, JDDNode maybe, JDDNode start, JDDNode[] targets, List<JDDNode> rewards,\n\t\t\tOpsAndBoundsList opsAndBounds) throws PrismException\n\t{\n\t\tint numNumericalObjectives = opsAndBounds.numberOfNumerical();\n\n\t\t// Check for unsupported computations\n\t\tif (numNumericalObjectives > 2) {\n\t\t\tthrow new PrismException(\"Pareto curve generation is currently only supported for 2 objectives\");\n\t\t}\n\t\tif (numNumericalObjectives >= 2 && opsAndBounds.probSize() + opsAndBounds.rewardSize() > numNumericalObjectives) {\n\t\t\tthrow new PrismException(\"Pareto curve generation is currently not allowed if there are other (bounded) objectives\");\n\t\t}\n\n\t\t// Pareto computation or achievability/numerical computation\n\t\tif (numNumericalObjectives >= 2) {\n\t\t\treturn generateParetoCurve(modelProduct, yes_ones, maybe, start, targets, rewards, opsAndBounds);\n\t\t} else {\n\t\t\treturn targetDrivenMultiReachProbs(modelProduct, yes_ones, maybe, start, targets, rewards, opsAndBounds);\n\t\t}\n\t}\n\n\tprotected TileList generateParetoCurve(NondetModel modelProduct, JDDNode yes_ones, JDDNode maybe, final JDDNode st, JDDNode[] targets,\n\t\t\t\t\t\t\t\t\t\t   List<JDDNode> rewards, OpsAndBoundsList opsAndBounds) throws PrismException\n\t{\n\t\t//TODO this method does not work for more than 2 objectives\n\t\tint numberOfPoints = 0;\n\t\tint rewardStepBounds[] = new int[rewards.size()];\n\t\tfor (int i = 0; i < rewardStepBounds.length; i++)\n\t\t\trewardStepBounds[i] = opsAndBounds.getRewardStepBound(i);\n\n\t\tint probStepBounds[] = new int[targets.length];\n\t\tfor (int i = 0; i < probStepBounds.length; i++)\n\t\t\tprobStepBounds[i] = opsAndBounds.getProbStepBound(i);\n\n\t\tdouble timer = System.currentTimeMillis();\n\t\tboolean min = false;\n\t\tint advCounter = 0;\n\n\t\t// Determine whether we are using Gauss-Seidel value iteration\n\t\tboolean useGS = (settings.getChoice(PrismSettings.PRISM_MDP_SOLN_METHOD) == Prism.MDP_MULTI_GAUSSSEIDEL);\n\t\tif (opsAndBounds.numberOfStepBounded() > 0) {\n\t\t\tmainLog.println(\"Not using Gauss-Seidel since there are step-bounded objectives\");\n\t\t\tuseGS = false;\n\t\t}\n\n\t\t//convert minimizing rewards to maximizing\n\t\tfor (int i = 0; i < opsAndBounds.rewardSize(); i++) {\n\t\t\tif (opsAndBounds.getRewardOperator(i) == Operator.R_LE) {\n\t\t\t\tJDDNode negated = JDD.Apply(JDD.TIMES, JDD.Constant(-1), rewards.get(i));\n\t\t\t\t//JDD.Ref(negated);\n\t\t\t\trewards.set(i, negated);\n\t\t\t\t//boundsRewards.set(i, -1 * boundsRewards.get(i));\n\t\t\t}\n\n\t\t\tif (opsAndBounds.getRewardOperator(i) == Operator.R_MIN) {\n\t\t\t\tJDDNode negated = JDD.Apply(JDD.TIMES, JDD.Constant(-1), rewards.get(i));\n\t\t\t\t//JDD.Ref(negated);\n\t\t\t\trewards.set(i, negated);\n\t\t\t\t//boundsRewards.set(i, -1 * boundsRewards.get(i));\n\t\t\t}\n\t\t}\n\n\t\tdouble tolerance = settings.getDouble(PrismSettings.PRISM_PARETO_EPSILON);\n\t\tint maxIters = settings.getInteger(PrismSettings.PRISM_MULTI_MAX_POINTS);\n\n\t\tint exportAdvSetting = settings.getChoice(PrismSettings.PRISM_EXPORT_ADV);\n\n\t\tNativeIntArray adversary = new NativeIntArray(modelProduct.getNumStates());\n\t\tint dimProb = targets.length;\n\t\tint dimReward = rewards.size();\n\t\tPoint targetPoint = new Point(dimProb + dimReward);\n\t\tArrayList<Point> computedPoints = new ArrayList<Point>();\n\t\tArrayList<Point> computedDirections = new ArrayList<Point>();\n\t\tArrayList<Point> pointsForInitialTile = new ArrayList<Point>();\n\n\t\t//create vectors and sparse matrices for the objectives\n\t\tfinal DoubleVector[] probDoubleVectors = new DoubleVector[dimProb];\n\t\tfinal NDSparseMatrix[] rewSparseMatrices = new NDSparseMatrix[dimReward];\n\n\t\tJDD.Ref(modelProduct.getTrans());\n\t\tJDD.Ref(modelProduct.getReach());\n\n\t\t//create a sparse matrix for transitions\n\t\tJDDNode a = JDD.Apply(JDD.TIMES, modelProduct.getTrans(), modelProduct.getReach());\n\n\t\tif (!min && dimReward == 0) {\n\t\t\tJDD.Ref(a);\n\t\t\tJDDNode tmp = JDD.And(JDD.Equals(a, 1.0), JDD.Identity(modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars()));\n\t\t\ta = JDD.ITE(tmp, JDD.Constant(0), a);\n\t\t}\n\n\t\tNDSparseMatrix trans_matrix = NDSparseMatrix.BuildNDSparseMatrix(a, modelProduct.getODD(), modelProduct.getAllDDRowVars(),\n\t\t\t\tmodelProduct.getAllDDColVars(), modelProduct.getAllDDNondetVars());\n\n\t\t// If adversary generation is enabled, we build/store action info\n\t\tif (settings.getChoice(PrismSettings.PRISM_EXPORT_ADV) != Prism.EXPORT_ADV_NONE) {\n\t\t\tNDSparseMatrix.AddActionsToNDSparseMatrix(a, modelProduct.getTransActions(), modelProduct.getODD(), modelProduct.getAllDDRowVars(),\n\t\t\t\t\tmodelProduct.getAllDDColVars(), modelProduct.getAllDDNondetVars(), trans_matrix);\n\t\t}\n\n\t\t//create double vectors for probabilistic objectives\n\t\tfor (int i = 0; i < dimProb; i++) {\n\t\t\tprobDoubleVectors[i] = new DoubleVector(targets[i], modelProduct.getAllDDRowVars(), modelProduct.getODD());\n\t\t}\n\n\t\t//create sparse matrices for reward objectives\n\t\tfor (int i = 0; i < dimReward; i++) {\n\t\t\tNDSparseMatrix rew_matrix = NDSparseMatrix.BuildSubNDSparseMatrix(a, modelProduct.getODD(), modelProduct.getAllDDRowVars(),\n\t\t\t\t\tmodelProduct.getAllDDColVars(), modelProduct.getAllDDNondetVars(), rewards.get(i));\n\t\t\trewSparseMatrices[i] = rew_matrix;\n\t\t}\n\n\t\tJDD.Deref(a);\n\n\t\tfor (int i = 0; i < dimProb; i++) {\n\t\t\tdouble[] result = null;\n\n\t\t\t// Optimise in direction of probability objective i\n\t\t\tPoint direction = new Point(dimProb + dimReward);\n\t\t\tdirection.setCoord(i, 1);\n\t\t\ttry {\n\t\t\t\t// If adversary generation is enabled, we amend the filename so that multiple adversaries can be exported\n\t\t\t\tString advFileName = settings.getString(PrismSettings.PRISM_EXPORT_ADV_FILENAME);\n\t\t\t\tif (settings.getChoice(PrismSettings.PRISM_EXPORT_ADV) != Prism.EXPORT_ADV_NONE) {\n\t\t\t\t\tPrismNative.setExportAdvFilename(PrismUtils.addCounterSuffixToFilename(advFileName, ++advCounter));\n\t\t\t\t}\n\t\t\t\tmainLog.println(\"Optimising weighted sum for probability objective \" + (i + 1) + \"/\" + dimProb + \": weights \" + direction);\n\t\t\t\tif (useGS) {\n\t\t\t\t\tresult = PrismSparse.NondetMultiObjGS(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, probDoubleVectors, rewSparseMatrices, direction.getCoords());\n\t\t\t\t} else {\n\t\t\t\t\tresult = PrismSparse.NondetMultiObj(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, modelProduct.getSynchs(), probDoubleVectors, probStepBounds,\n\t\t\t\t\t\t\trewSparseMatrices, direction.getCoords(), rewardStepBounds);\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// If anything went wrong (in particular, non-convergence of the computation), use another direction\n\t\t\t\tmainLog.println(\"Ignoring the last multi-objective computation since it did not complete successfully\");\n\t\t\t\t// Optimise in almost the direction of probability objective i\n\t\t\t\tdouble large = 10000;\n\t\t\t\tfor (int j = 0; j < dimProb + dimReward; j++) {\n\t\t\t\t\tdirection.setCoord(j, j == i ? large : 1);\n\t\t\t\t}\n\t\t\t\tdirection = direction.normalize();\n\t\t\t\tmainLog.println(\"Optimising weighted sum for probability objective \" + (i + 1) + \"/\" + dimProb + \": weights \" + direction);\n\t\t\t\tif (useGS) {\n\t\t\t\t\tresult = PrismSparse.NondetMultiObjGS(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, probDoubleVectors, rewSparseMatrices, direction.getCoords());\n\t\t\t\t} else {\n\t\t\t\t\tresult = PrismSparse.NondetMultiObj(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, modelProduct.getSynchs(), probDoubleVectors, probStepBounds,\n\t\t\t\t\t\t\trewSparseMatrices, direction.getCoords(), rewardStepBounds);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t//The following is thrown because in this case the i-th dimension is\n\t\t\t//zero and we might have problems when getting an separating hyperplane.\n\t\t\t/*if (result[0] == 0)\n\t\t\t\tthrow new PrismException(\"The probabilistic objective number \" + i + \" is degenerate since the optimal value is also the least optimal value.\" );\n\t\t\t*/\n\t\t\ttargetPoint = new Point(result);\n\t\t\tmainLog.println(\"Computed point: \" + targetPoint);\n\t\t\tpointsForInitialTile.add(targetPoint);\n\t\t}\n\n\t\tfor (int i = 0; i < dimReward; i++) {\n\n\t\t\tdouble[] result = null;\n\t\t\t// Optimise in direction of reward objective i\n\t\t\tPoint direction = new Point(dimProb + dimReward);\n\t\t\tdirection.setCoord(dimProb + i, 1);\n\t\t\ttry {\n\t\t\t\t// If adversary generation is enabled, we amend the filename so that multiple adversaries can be exported\n\t\t\t\tString advFileName = settings.getString(PrismSettings.PRISM_EXPORT_ADV_FILENAME);\n\t\t\t\tif (settings.getChoice(PrismSettings.PRISM_EXPORT_ADV) != Prism.EXPORT_ADV_NONE) {\n\t\t\t\t\tPrismNative.setExportAdvFilename(PrismUtils.addCounterSuffixToFilename(advFileName, ++advCounter));\n\t\t\t\t}\n\t\t\t\tmainLog.println(\"Optimising weighted sum for reward objective \" + (i + 1) + \"/\" + dimReward + \": weights \" + direction);\n\t\t\t\tif (useGS) {\n\t\t\t\t\tresult = PrismSparse.NondetMultiObjGS(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, probDoubleVectors, rewSparseMatrices, direction.getCoords());\n\t\t\t\t} else {\n\t\t\t\t\tresult = PrismSparse.NondetMultiObj(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, modelProduct.getSynchs(), probDoubleVectors, probStepBounds,\n\t\t\t\t\t\t\trewSparseMatrices, direction.getCoords(), rewardStepBounds);\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// If anything went wrong (in particular, non-convergence of the computation), use another direction\n\t\t\t\tmainLog.println(\"Ignoring the last multi-objective computation since it did not complete successfully\");\n\t\t\t\t// Optimise in almost the direction of reward objective i\n\t\t\t\tdouble large = 10000;\n\t\t\t\tfor (int j = 0; j < dimProb + dimReward; j++) {\n\t\t\t\t\tdirection.setCoord(j, j == dimProb + i ? large : 1);\n\t\t\t\t}\n\t\t\t\tdirection = direction.normalize();\n\t\t\t\tmainLog.println(\"Optimising weighted sum for reward objective \" + (i + 1) + \"/\" + dimReward + \": weights \" + direction);\n\t\t\t\tif (useGS) {\n\t\t\t\t\tresult = PrismSparse.NondetMultiObjGS(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, probDoubleVectors, rewSparseMatrices, direction.getCoords());\n\t\t\t\t} else {\n\t\t\t\t\tresult = PrismSparse.NondetMultiObj(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, modelProduct.getSynchs(), probDoubleVectors, probStepBounds,\n\t\t\t\t\t\t\trewSparseMatrices, direction.getCoords(), rewardStepBounds);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tnumberOfPoints++;\n\t\t\ttargetPoint = new Point(result);\n\t\t\tmainLog.println(\"Computed point: \" + targetPoint);\n\t\t\tpointsForInitialTile.add(targetPoint);\n\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.println(\"Upper bound is \" + Arrays.toString(result));\n\t\t\t}\n\t\t}\n\n\t\tif (verbose)\n\t\t\tmainLog.println(\"Points for the initial tile: \" + pointsForInitialTile);\n\n\t\tTile initialTile = new Tile(pointsForInitialTile);\n\t\tTileList tileList = new TileList(initialTile, opsAndBounds, tolerance);\n\n\t\tPoint direction = tileList.getCandidateHyperplane();\n\n\t\tif (verbose) {\n\t\t\tmainLog.println(\"The initial direction is \" + direction);\n\t\t}\n\n\t\tboolean decided = false;\n\t\tint iters = 0;\n\t\twhile (iters < maxIters) {\n\t\t\titers++;\n\n\t\t\t// If adversary generation is enabled, we amend the filename so that multiple adversaries can be exported\n\t\t\tString advFileName = settings.getString(PrismSettings.PRISM_EXPORT_ADV_FILENAME);\n\t\t\tif (settings.getChoice(PrismSettings.PRISM_EXPORT_ADV) != Prism.EXPORT_ADV_NONE) {\n\t\t\t\tPrismNative.setExportAdvFilename(PrismUtils.addCounterSuffixToFilename(advFileName, ++advCounter));\n\t\t\t}\n\t\t\tmainLog.println(\"Optimising weighted sum of objectives: weights \" + direction);\n\t\t\tdouble[] result;\n\t\t\tif (useGS) {\n\t\t\t\tresult = PrismSparse.NondetMultiObjGS(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, probDoubleVectors, rewSparseMatrices, direction.getCoords());\n\t\t\t} else {\n\t\t\t\tresult = PrismSparse.NondetMultiObj(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, modelProduct.getSynchs(), probDoubleVectors, probStepBounds,\n\t\t\t\t\t\trewSparseMatrices, direction.getCoords(), rewardStepBounds);\n\t\t\t}\n\n\t\t\t/*\t//Minimizing operators are negated, and for Pareto we need to maximize.\n\t\t\t\tfor (int i = 0; i < dimProb; i++) {\n\t\t\t\t\tif (opsAndBounds.getOperator(i) == Operator.P_MIN) {\n\t\t\t\t\t\tresult[i] = -(1-result[i]);\n\t\t\t\t\t}\n\t\t\t\t} */\n\n\t\t\tnumberOfPoints++;\n\n\t\t\t//collect the numbers obtained from methods executed above.\n\t\t\tPoint newPoint = new Point(result);\n\t\t\tmainLog.println(\"Computed point: \" + newPoint);\n\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.println(\"\\n\" + numberOfPoints + \": New point is \" + newPoint + \".\");\n\t\t\t\tmainLog.println(\"TileList:\" + tileList);\n\t\t\t}\n\n\t\t\tcomputedPoints.add(newPoint);\n\t\t\tcomputedDirections.add(direction);\n\n\t\t\ttileList.addNewPoint(newPoint);\n\t\t\t//mainLog.println(\"\\nTiles after adding: \" + tileList);\n\t\t\t//compute new direction\n\t\t\tdirection = tileList.getCandidateHyperplane();\n\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.println(\"New direction is \" + direction);\n\t\t\t\t//mainLog.println(\"TileList: \" + tileList);\n\n\t\t\t}\n\n\t\t\tif (direction == null) {\n\t\t\t\t//no tile could be improved\n\t\t\t\tdecided = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"The value iteration(s) took \" + timer / 1000.0 + \" seconds altogether.\");\n\t\tmainLog.println(\"Number of weight vectors used: \" + numberOfPoints);\n\n\t\tif (!decided)\n\t\t\tthrow new PrismException(\"The computation did not finish in \" + maxIters\n\t\t\t\t\t+ \" target point iterations, try increasing this number using the -multimaxpoints switch.\");\n\t\telse {\n\t\t\tString paretoFile = settings.getString(PrismSettings.PRISM_EXPORT_PARETO_FILENAME);\n\n\t\t\t//export to file if required\n\t\t\tif (paretoFile != null && !paretoFile.equals(\"\")) {\n\t\t\t\tMultiObjUtils.exportPareto(tileList, paretoFile);\n\t\t\t\tmainLog.println(\"Exported Pareto curve. To see it, run\\n etc/scripts/prism-pareto.py \" + paretoFile);\n\t\t\t}\n\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.print(\"Computed \" + tileList.getNumberOfDifferentPoints() + \" points altogether: \");\n\t\t\t\tmainLog.println(tileList.getPoints().toString());\n\t\t\t}\n\n\t\t\treturn tileList;\n\t\t}\n\t}\n\n\tprotected double targetDrivenMultiReachProbs(NondetModel modelProduct, JDDNode yes_ones, JDDNode maybe, final JDDNode st, JDDNode[] targets,\n\t\t\tList<JDDNode> rewards, OpsAndBoundsList opsAndBounds) throws PrismException\n\t{\n\t\tint numberOfPoints = 0;\n\t\tint rewardStepBounds[] = new int[rewards.size()];\n\t\tfor (int i = 0; i < rewardStepBounds.length; i++)\n\t\t\trewardStepBounds[i] = opsAndBounds.getRewardStepBound(i);\n\n\t\tint probStepBounds[] = new int[targets.length];\n\t\tfor (int i = 0; i < probStepBounds.length; i++)\n\t\t\tprobStepBounds[i] = opsAndBounds.getProbStepBound(i);\n\n\t\tdouble timer = System.currentTimeMillis();\n\t\tboolean min = false;\n\n\t\t// Determine whether we are using Gauss-Seidel value iteration\n\t\tboolean useGS = (settings.getChoice(PrismSettings.PRISM_MDP_SOLN_METHOD) == Prism.MDP_MULTI_GAUSSSEIDEL);\n\t\tif (opsAndBounds.numberOfStepBounded() > 0) {\n\t\t\tmainLog.println(\"Not using Gauss-Seidel since there are step-bounded objectives\");\n\t\t\tuseGS = false;\n\t\t}\n\n\t\t//convert minimizing rewards to maximizing\n\t\tfor (int i = 0; i < opsAndBounds.rewardSize(); i++) {\n\t\t\tif (opsAndBounds.getRewardOperator(i) == Operator.R_LE) {\n\t\t\t\tJDDNode negated = JDD.Apply(JDD.TIMES, JDD.Constant(-1), rewards.get(i));\n\t\t\t\t//JDD.Ref(negated);\n\t\t\t\trewards.set(i, negated);\n\t\t\t\t//boundsRewards.set(i, -1 * boundsRewards.get(i));\n\t\t\t}\n\n\t\t\tif (opsAndBounds.getRewardOperator(i) == Operator.R_MIN) {\n\t\t\t\tJDDNode negated = JDD.Apply(JDD.TIMES, JDD.Constant(-1), rewards.get(i));\n\t\t\t\t//JDD.Ref(negated);\n\t\t\t\trewards.set(i, negated);\n\t\t\t\t//boundsRewards.set(i, -1 * boundsRewards.get(i));\n\t\t\t}\n\t\t}\n\n\t\tboolean maximizingProb = (opsAndBounds.probSize() > 0 && (opsAndBounds.getProbOperator(0) == Operator.P_MAX || opsAndBounds.getProbOperator(0) == Operator.P_MIN));\n\t\tboolean maximizingReward = (opsAndBounds.rewardSize() > 0 && (opsAndBounds.getRewardOperator(0) == Operator.R_MAX || opsAndBounds.getRewardOperator(0) == Operator.R_MIN));\n\t\tboolean maximizingNegated = (maximizingProb && opsAndBounds.getProbOperator(0) == Operator.P_MIN)\n\t\t\t\t|| (maximizingReward && opsAndBounds.getRewardOperator(0) == Operator.R_MIN);\n\n\t\tint maxIters = settings.getInteger(PrismSettings.PRISM_MULTI_MAX_POINTS);\n\n\t\tNativeIntArray adversary = new NativeIntArray(modelProduct.getNumStates());\n\t\tint dimProb = targets.length;\n\t\tint dimReward = rewards.size();\n\t\tPoint targetPoint = new Point(dimProb + dimReward);\n\t\tArrayList<Point> computedPoints = new ArrayList<Point>();\n\t\tArrayList<Point> computedDirections = new ArrayList<Point>();\n\n\t\t//create vectors and sparse matrices for the objectives\n\t\tfinal DoubleVector[] probDoubleVectors = new DoubleVector[dimProb];\n\t\tfinal NDSparseMatrix[] rewSparseMatrices = new NDSparseMatrix[dimReward];\n\n\t\tJDD.Ref(modelProduct.getTrans());\n\t\tJDD.Ref(modelProduct.getReach());\n\n\t\t//create a sparse matrix for transitions\n\t\tJDDNode a = JDD.Apply(JDD.TIMES, modelProduct.getTrans(), modelProduct.getReach());\n\n\t\tif (!min && dimReward == 0) {\n\t\t\tJDD.Ref(a);\n\t\t\tJDDNode tmp = JDD.And(JDD.Equals(a, 1.0), JDD.Identity(modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars()));\n\t\t\ta = JDD.ITE(tmp, JDD.Constant(0), a);\n\t\t}\n\n\t\tNDSparseMatrix trans_matrix = NDSparseMatrix.BuildNDSparseMatrix(a, modelProduct.getODD(), modelProduct.getAllDDRowVars(),\n\t\t\t\tmodelProduct.getAllDDColVars(), modelProduct.getAllDDNondetVars());\n\n\t\t//create double vectors for probabilistic objectives\n\t\tfor (int i = 0; i < dimProb; i++) {\n\t\t\tprobDoubleVectors[i] = new DoubleVector(targets[i], modelProduct.getAllDDRowVars(), modelProduct.getODD());\n\t\t}\n\n\t\t//create sparse matrices for reward objectives\n\t\tfor (int i = 0; i < dimReward; i++) {\n\t\t\tNDSparseMatrix rew_matrix = NDSparseMatrix.BuildSubNDSparseMatrix(a, modelProduct.getODD(), modelProduct.getAllDDRowVars(),\n\t\t\t\t\tmodelProduct.getAllDDColVars(), modelProduct.getAllDDNondetVars(), rewards.get(i));\n\t\t\trewSparseMatrices[i] = rew_matrix;\n\t\t}\n\n\t\tJDD.Deref(a);\n\n\t\t//initialize the target point\n\t\tfor (int i = 0; i < dimProb; i++) {\n\t\t\ttargetPoint.setCoord(i, opsAndBounds.getProbBound(i));\n\t\t}\n\t\tif (maximizingProb) {\n\t\t\ttargetPoint.setCoord(0, 1.0);\n\t\t}\n\n\t\tfor (int i = 0; i < dimReward; i++) {\n\t\t\t//multiply by -1 in case of minimizing, that converts it to maximizing.\n\t\t\tdouble t = (opsAndBounds.getRewardOperator(i) == Operator.R_LE) ? -opsAndBounds.getRewardBound(i) : opsAndBounds.getRewardBound(i);\n\t\t\ttargetPoint.setCoord(i + dimProb, t);\n\t\t}\n\t\tif (maximizingReward) {\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.println(\"Getting an upper bound on maximizing objective\");\n\t\t\t}\n\n\t\t\tdouble[] result;\n\t\t\tif (useGS) {\n\t\t\t\t//System.out.println(\"Doing GS\");\n\t\t\t\tresult = PrismSparse.NondetMultiObjGS(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, null, new NDSparseMatrix[] { rewSparseMatrices[0] },\n\t\t\t\t\t\tnew double[] { 1.0 });\n\t\t\t} else {\n\t\t\t\t//System.out.println(\"Not doing GS\");\n\t\t\t\tresult = PrismSparse.NondetMultiObj(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, modelProduct.getSynchs(), null, null,\n\t\t\t\t\t\tnew NDSparseMatrix[] { rewSparseMatrices[0] }, new double[] { 1.0 }, new int[] { rewardStepBounds[0] });\n\t\t\t}\n\t\t\tnumberOfPoints++;\n\n\t\t\ttargetPoint.setCoord(dimProb, result[0]);\n\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.println(\"Upper bound is \" + result[0]);\n\t\t\t}\n\t\t}\n\n\t\tPoint direction = MultiObjUtils.getWeights(targetPoint, computedPoints);\n\n\t\tif (verbose) {\n\t\t\tmainLog.println(\"The initial target point is \" + targetPoint);\n\t\t\tmainLog.println(\"The initial direction is \" + direction);\n\t\t}\n\n\t\tboolean decided = false;\n\t\tboolean isAchievable = false;\n\t\tint iters = 0;\n\t\twhile (iters < maxIters) {\n\t\t\titers++;\n\n\t\t\t//create the weights array\n\t\t\tdouble[] weights = new double[dimProb + dimReward];\n\t\t\tfor (int i = 0; i < dimProb + dimReward; i++) {\n\t\t\t\tweights[i] = direction.getCoord(i);\n\t\t\t}\n\n\t\t\tdouble[] result;\n\t\t\tif (useGS) {\n\t\t\t\tresult = PrismSparse.NondetMultiObjGS(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, probDoubleVectors, rewSparseMatrices, weights);\n\t\t\t} else {\n\t\t\t\tresult = PrismSparse.NondetMultiObj(modelProduct.getODD(), modelProduct.getAllDDRowVars(), modelProduct.getAllDDColVars(),\n\t\t\t\t\t\tmodelProduct.getAllDDNondetVars(), false, st, adversary, trans_matrix, modelProduct.getSynchs(), probDoubleVectors, probStepBounds,\n\t\t\t\t\t\trewSparseMatrices, weights, rewardStepBounds);\n\t\t\t}\n\t\t\tnumberOfPoints++;\n\n\t\t\t//collect the numbers obtained from methods executed above.\n\t\t\tPoint newPoint = new Point(result);\n\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.println(\"New point is \" + newPoint + \".\");\n\t\t\t}\n\n\t\t\tcomputedPoints.add(newPoint);\n\t\t\tcomputedDirections.add(direction);\n\n\t\t\t//if (prism.getExportMultiGraphs())\n\t\t\t//\tMultiObjUtils.printGraphFileDebug(targetPoint, computedPoints, computedDirections, prism.getExportMultiGraphsDir(), output++);\n\n\t\t\t//check if the new point together with the direction shows the point is unreachable\n\t\t\tdouble dNew = 0.0;\n\t\t\tfor (int i = 0; i < dimProb + dimReward; i++) {\n\t\t\t\tdNew += newPoint.getCoord(i) * direction.getCoord(i);\n\t\t\t}\n\n\t\t\tdouble dTarget = 0.0;\n\t\t\tfor (int i = 0; i < dimProb + dimReward; i++) {\n\t\t\t\tdTarget += targetPoint.getCoord(i) * direction.getCoord(i);\n\t\t\t}\n\n\t\t\tif (dTarget > dNew) {\n\t\t\t\tif (maximizingProb || maximizingReward) {\n\t\t\t\t\tint maximizingCoord = (maximizingProb) ? 0 : dimProb;\n\t\t\t\t\tdouble rest = dNew - (dTarget - direction.getCoord(maximizingCoord) * targetPoint.getCoord(maximizingCoord));\n\t\t\t\t\tif ((!maximizingNegated && rest < 0) || (maximizingNegated && rest > 0)) {\n\t\t\t\t\t\t//target can't be lowered\n\t\t\t\t\t\tdecided = true;\n\t\t\t\t\t\ttargetPoint.setCoord(maximizingCoord, Double.NaN);\n\t\t\t\t\t\tif (verbose)\n\t\t\t\t\t\t\tmainLog.println(\"Decided, target is \" + targetPoint);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tdouble lowered = rest / direction.getCoord(maximizingCoord);\n\t\t\t\t\t\ttargetPoint.setCoord(maximizingCoord, lowered);\n\t\t\t\t\t\t//HACK\n\t\t\t\t\t\tif (lowered == Double.NEGATIVE_INFINITY) {\n\t\t\t\t\t\t\ttargetPoint.setCoord(maximizingCoord, Double.NaN);\n\t\t\t\t\t\t\tmainLog.println(\"\\nThe constraints are not achievable!\\n\");\n\t\t\t\t\t\t\tdecided = true;\n\t\t\t\t\t\t\tisAchievable = false;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (verbose)\n\t\t\t\t\t\t\tmainLog.println(\"Target lowered to \" + targetPoint);\n\n\t\t\t\t\t\t//if (prism.getExportMultiGraphs())\n\t\t\t\t\t\t//\tMultiObjUtils.printGraphFileDebug(targetPoint, computedPoints, computedDirections, prism.getExportMultiGraphsDir(), output++);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tdecided = true;\n\t\t\t\t\tisAchievable = false;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t//compute new direction\n\t\t\tdirection = MultiObjUtils.getWeights(targetPoint, computedPoints);\n\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.println(\"New direction is \" + direction);\n\t\t\t}\n\n\t\t\tif (direction == null || computedDirections.contains(direction)) //The second disjunct is for convergence\n\t\t\t{\n\t\t\t\t//there is no hyperplane strictly separating the target from computed points\n\t\t\t\t//hence we can conclude that the point is reachable\n\t\t\t\tdecided = true;\n\t\t\t\tisAchievable = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"The value iteration(s) took \" + timer / 1000.0 + \" seconds altogether.\");\n\t\tmainLog.println(\"Number of weight vectors used: \" + numberOfPoints);\n\n\t\tif (!decided)\n\t\t\tthrow new PrismException(\"The computation did not finish in \" + maxIters\n\t\t\t\t\t+ \" target point iterations, try increasing this number using the -multimaxpoints switch.\");\n\t\tif (maximizingProb || maximizingReward) {\n\t\t\tint maximizingCoord = (maximizingProb) ? 0 : dimProb;\n\t\t\treturn (maximizingNegated) ? -targetPoint.getCoord(maximizingCoord) : targetPoint.getCoord(maximizingCoord);\n\t\t} else {\n\t\t\treturn (isAchievable) ? 1.0 : 0.0;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/comp/NonProbModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.Vector;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionExists;\nimport parser.ast.ExpressionForAll;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.ast.PropertiesFile;\nimport cex.CexPathAsBDDs;\nimport cex.CexPathStates;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismNotSupportedException;\nimport symbolic.states.StateValues;\nimport symbolic.states.StateValuesMTBDD;\nimport symbolic.model.Model;\nimport symbolic.model.NondetModel;\n\n/*\n * Non probabilistic model checker, initially for CTL.\n */\npublic class NonProbModelChecker extends StateModelChecker\n{\n\t// Counterexample stuff\n\tprivate boolean doGenCex = true;\n\n\t// Constructor\n\n\tpublic NonProbModelChecker(Prism prism, Model m, PropertiesFile pf) throws PrismException\n\t{\n\t\t// Initialise\n\t\tsuper(prism, m, pf);\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// Check a property, i.e. an expression\n\t// -----------------------------------------------------------------------------------\n\n\t// Check expression (recursive)\n\t@Override\n\tpublic StateValues checkExpression(Expression expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res;\n\n\t\t// E operator\n\t\tif (expr instanceof ExpressionExists) {\n\t\t\tres = checkExpressionExists(((ExpressionExists) expr).getExpression(), statesOfInterest);\n\t\t}\n\t\t// A operator\n\t\telse if (expr instanceof ExpressionForAll) {\n\t\t\tres = checkExpressionForAll(((ExpressionForAll) expr).getExpression(), statesOfInterest);\n\t\t}\n\t\t// Otherwise, use the superclass\n\t\telse {\n\t\t\tres = super.checkExpression(expr, statesOfInterest);\n\t\t}\n\n\t\t// Filter out non-reachable states from solution\n\t\t// (only necessary for symbolically stored vectors)\n\t\tif (res instanceof StateValuesMTBDD)\n\t\t\tres.filter(reach);\n\n\t\treturn res;\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// Check method for each operator\n\t// -----------------------------------------------------------------------------------\n\n\t/**\n\t * Model check a CTL exists (E) operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionExists(Expression expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res = null;\n\n\t\t// Check whether this is a simple path formula (i.e. CTL, not LTL)\n\t\tif (!expr.isSimplePathFormula()) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"(Non-probabilistic) LTL model checking is not supported\");\n\t\t}\n\n\t\tif (prism.getFairness()) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"Non-probabilistic CTL model checking is not supported with fairness\");\n\t\t}\n\n\t\t// Negation/parentheses\n\t\tif (expr instanceof ExpressionUnaryOp) {\n\t\t\tExpressionUnaryOp exprUnary = (ExpressionUnaryOp) expr;\n\t\t\t// Parentheses\n\t\t\tif (exprUnary.getOperator() == ExpressionUnaryOp.PARENTH) {\n\t\t\t\t// Recurse\n\t\t\t\tres = checkExpressionExists(exprUnary.getOperand(), statesOfInterest);\n\t\t\t}\n\t\t\t// Negation\n\t\t\telse if (exprUnary.getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\t\t// Compute, then negate \n\t\t\t\tres = checkExpressionForAll(exprUnary.getOperand(), statesOfInterest);\n\t\t\t\tres.subtractFromOne();\n\t\t\t}\n\t\t}\n\t\t// Temporal operators\n\t\telse if (expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\tthrow new PrismNotSupportedException(\"Model checking of bounded CTL operators is not supported\");\n\t\t\t}\n\t\t\t// Next (EX)\n\t\t\tif (exprTemp.getOperator() == ExpressionTemporal.P_X) {\n\t\t\t\tres = checkNext(exprTemp, false, statesOfInterest);\n\t\t\t}\n\t\t\t// Until (EU)\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\tres = checkExistsUntil(exprTemp, statesOfInterest);\n\t\t\t}\n\t\t\t// Globally (EG)\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_G) {\n\t\t\t\tres = checkExistsGlobally(exprTemp, statesOfInterest);\n\t\t\t}\n\t\t\t// Anything else - convert to until and recurse\n\t\t\telse {\n\t\t\t\tres = checkExpressionExists(exprTemp.convertToUntilForm(), statesOfInterest);\n\t\t\t}\n\t\t}\n\n\t\tif (res == null)\n\t\t\tthrow new PrismException(\"Unrecognised path operator in E operator\");\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check a CTL forall (A) operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionForAll(Expression expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res = null;\n\n\t\t// Check whether this is a simple path formula (i.e. CTL, not LTL)\n\t\tif (!expr.isSimplePathFormula()) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"(Non-probabilistic) LTL model checking is not supported\");\n\t\t}\n\n\t\tif (prism.getFairness()) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"Non-probabilistic CTL model checking is not supported with fairness\");\n\t\t}\n\n\t\t// Negation/parentheses\n\t\tif (expr instanceof ExpressionUnaryOp) {\n\t\t\tExpressionUnaryOp exprUnary = (ExpressionUnaryOp) expr;\n\t\t\t// Parentheses\n\t\t\tif (exprUnary.getOperator() == ExpressionUnaryOp.PARENTH) {\n\t\t\t\t// Recurse\n\t\t\t\tres = checkExpressionForAll(exprUnary.getOperand(), statesOfInterest);\n\t\t\t}\n\t\t\t// Negation\n\t\t\telse if (exprUnary.getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\t\t// Compute, then negate \n\t\t\t\tres = checkExpressionExists(exprUnary.getOperand(), statesOfInterest);\n\t\t\t\tres.subtractFromOne();\n\t\t\t}\n\t\t}\n\t\t// Temporal operators\n\t\telse if (expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\tthrow new PrismNotSupportedException(\"Model checking of bounded CTL operators is not supported\");\n\t\t\t}\n\t\t\t// Next (AX)\n\t\t\tif (exprTemp.getOperator() == ExpressionTemporal.P_X) {\n\t\t\t\tres = checkNext(exprTemp, true, statesOfInterest);\n\t\t\t}\n\t\t\t// Until (AU)\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\t// Reduce to ENF (i.e. phi1 AU phi2 == !E[!phi2 U !phi1&!phi2] & !EG !phi2)\n\t\t\t\tExpression notPhi1 = Expression.Not(exprTemp.getOperand1().deepCopy());\n\t\t\t\tExpression notPhi2 = Expression.Not(exprTemp.getOperand2().deepCopy());\n\t\t\t\tExpression notBoth = Expression.And(notPhi1.deepCopy(), notPhi2.deepCopy());\n\t\t\t\tExpression lhs = new ExpressionTemporal(ExpressionTemporal.P_U, notPhi2, notBoth);\n\t\t\t\tlhs = Expression.Not(new ExpressionExists(lhs));\n\t\t\t\tExpression rhs = new ExpressionTemporal(ExpressionTemporal.P_G, null, notPhi2);\n\t\t\t\trhs = Expression.Not(new ExpressionExists(rhs));\n\t\t\t\tExpression enf = Expression.And(lhs, rhs);\n\t\t\t\tres = checkExpression(enf, statesOfInterest);\n\t\t\t}\n\t\t\t// Eventually (AF)\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_F) {\n\t\t\t\t// Reduce to EG (i.e. AF phi == !EG !phi)\n\t\t\t\tExpressionTemporal exprCopy = (ExpressionTemporal) exprTemp.deepCopy();\n\t\t\t\texprCopy.setOperator(ExpressionTemporal.P_G);\n\t\t\t\texprCopy.setOperand2(Expression.Not(exprCopy.getOperand2()));\n\t\t\t\tres = checkExpressionExists(exprCopy, statesOfInterest);\n\t\t\t\tres.subtractFromOne();\n\t\t\t}\n\t\t\t// Anything else - convert to until and recurse\n\t\t\telse {\n\t\t\t\tres = checkExpressionForAll(exprTemp.convertToUntilForm(), statesOfInterest);\n\t\t\t}\n\t\t}\n\n\t\tif (res == null)\n\t\t\tthrow new PrismException(\"Unrecognised path operator in E operator\");\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check a CTL exists/forall next (EX/AX) operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkNext(ExpressionTemporal expr, boolean forall, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b, transRel, pre;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// Model check operands first, statesOfInterest = all\n\t\tb = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\n\t\t// Get transition relation\n\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\tJDD.Ref(trans01);\n\t\t\ttransRel = JDD.ThereExists(trans01, ((NondetModel) model).getAllDDNondetVars());\n\t\t} else {\n\t\t\tJDD.Ref(trans01);\n\t\t\ttransRel = trans01;\n\t\t}\n\n\t\t// Find predecessors\n\t\tJDD.Ref(b);\n\t\tJDD.Ref(transRel);\n\t\tif (forall) {\n\t\t\tpre = JDD.ForAll(JDD.Implies(transRel, JDD.PermuteVariables(b, allDDRowVars, allDDColVars)), allDDColVars);\n\t\t} else {\n\t\t\tpre = JDD.ThereExists(JDD.And(JDD.PermuteVariables(b, allDDRowVars, allDDColVars), transRel), allDDColVars);\n\t\t}\n\n\t\t// Derefs\n\t\tJDD.Deref(b);\n\t\tJDD.Deref(transRel);\n\n\t\treturn new StateValuesMTBDD(pre, model);\n\t}\n\n\t/**\n\t * Model check a CTL exists until (EU) operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExistsUntil(ExpressionTemporal expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b1, b2, transRel, tmp, tmp2, tmp3, init = null;\n\t\tArrayList<JDDNode> cexDDs = null;\n\t\tJDDNode cexInit = null;\n\t\tboolean done, cexDone = false;\n\t\tVector<String> cexActions;\n\t\tint iters, i;\n\t\tlong l;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// Model check operands first, statesOfInterest = all\n\t\tb1 = checkExpressionDD(expr.getOperand1(), model.getReach().copy());\n\t\ttry {\n\t\t\tb2 = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b1);\n\t\t\tthrow e;\n\t\t}\n\n\t\tl = System.currentTimeMillis();\n\n\t\t// Create storage for counterexample, if required\n\t\tif (doGenCex) {\n\t\t\tcexDDs = new ArrayList<JDDNode>();\n\t\t\tcexDone = false;\n\t\t\tinit = model.getStart();\n\t\t}\n\n\t\t// Get transition relation\n\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\tJDD.Ref(trans01);\n\t\t\ttransRel = JDD.ThereExists(trans01, ((NondetModel) model).getAllDDNondetVars());\n\t\t} else {\n\t\t\tJDD.Ref(trans01);\n\t\t\ttransRel = trans01;\n\t\t}\n\n\t\t// Fixpoint loop\n\t\tdone = false;\n\t\titers = 0;\n\t\ttmp = JDD.Constant(0);\n\t\twhile (!done) {\n\t\t\titers++;\n\t\t\tJDD.Ref(tmp);\n\t\t\ttmp2 = JDD.PermuteVariables(tmp, allDDRowVars, allDDColVars);\n\t\t\tJDD.Ref(transRel);\n\t\t\ttmp2 = JDD.And(tmp2, transRel);\n\t\t\ttmp2 = JDD.ThereExists(tmp2, allDDColVars);\n\t\t\tJDD.Ref(b1);\n\t\t\ttmp2 = JDD.And(b1, tmp2);\n\t\t\tJDD.Ref(b2);\n\t\t\ttmp2 = JDD.Or(b2, tmp2);\n\t\t\tif (tmp2.equals(tmp)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\t// Store counterexample info, if required (and not finished)\n\t\t\tif (doGenCex && !cexDone) {\n\t\t\t\t// Store the newly discovered states from this iteration\n\t\t\t\tJDD.Ref(tmp);\n\t\t\t\tJDD.Ref(tmp2);\n\t\t\t\tcexDDs.add(JDD.And(tmp2, JDD.Not(tmp)));\n\t\t\t\t// See if we have found the initial state yet, and if so, don't store any more info\n\t\t\t\tif (JDD.AreIntersecting(tmp2, init)) {\n\t\t\t\t\tcexDone = true;\n\t\t\t\t\t// Choose an initial state (in case there are several) which intersects\n\t\t\t\t\tJDD.Ref(tmp2);\n\t\t\t\t\tJDD.Ref(init);\n\t\t\t\t\tcexInit = JDD.And(tmp2, init);\n\t\t\t\t\tcexInit = JDD.RestrictToFirst(cexInit, allDDRowVars);\n\t\t\t\t}\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t\ttmp = tmp2;\n\t\t}\n\n\t\t// Print iterations/timing info\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"\\nCTL EU fixpoint: \" + iters + \" iterations in \" + (l / 1000.0) + \" seconds\");\n\n\t\t// Process the counterexample info to produce a trace \n\t\tif (doGenCex) {\n\t\t\tif (!cexDone) {\n\t\t\t\tfor (i = 0; i < cexDDs.size(); i++) {\n\t\t\t\t\tJDD.Deref(cexDDs.get(i));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tmainLog.println(\"Processing counterexample trace (\" + cexDDs.size() + \" states long)...\");\n\t\t\t\t// First state of counterexample (at end of array) is initial state\n\t\t\t\tJDD.Deref(cexDDs.get(cexDDs.size() - 1));\n\t\t\t\tcexDDs.set(cexDDs.size() - 1, cexInit);\n\t\t\t\t// Go through remaining steps of counterexample\n\t\t\t\tfor (i = cexDDs.size() - 2; i >= 0; i--) {\n\t\t\t\t\t// Get states that are a successor of the previous state of the counterexample\n\t\t\t\t\tJDD.Ref(cexDDs.get(i + 1));\n\t\t\t\t\tJDD.Ref(transRel);\n\t\t\t\t\ttmp3 = JDD.And(cexDDs.get(i + 1), transRel);\n\t\t\t\t\ttmp3 = JDD.ThereExists(tmp3, allDDRowVars);\n\t\t\t\t\ttmp3 = JDD.PermuteVariables(tmp3, allDDColVars, allDDRowVars);\n\t\t\t\t\t// Intersect with possible states for this step of the counterexample\n\t\t\t\t\tJDD.Ref(cexDDs.get(i));\n\t\t\t\t\ttmp3 = JDD.And(tmp3, cexDDs.get(i));\n\t\t\t\t\t// Pick one of these state (the first)\n\t\t\t\t\ttmp3 = JDD.PermuteVariables(JDD.RestrictToFirst(tmp3, allDDColVars), allDDColVars, allDDRowVars);\n\t\t\t\t\t// Replace this state in the counterexample\n\t\t\t\t\tJDD.Deref(cexDDs.get(i));\n\t\t\t\t\tcexDDs.set(i, tmp3);\n\t\t\t\t}\n\t\t\t\t// Construct counterexample object\n\t\t\t\tCexPathStates cex = new CexPathStates(model);\n\t\t\t\tfor (i = cexDDs.size() - 1; i >= 0; i--) {\n\t\t\t\t\tcex.addState(model.convertBddToState(cexDDs.get(i)));\n\t\t\t\t\tJDD.Deref(cexDDs.get(i));\n\t\t\t\t}\n\t\t\t\tresult.setCounterexample(cex);\n\t\t\t\tif (1 == 2) {\n\t\t\t\t\t// For an MDP model, build a list of actions from counterexample\n\t\t\t\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\t\t\t\tcexActions = new Vector<String>();\n\t\t\t\t\t\tfor (i = cexDDs.size() - 1; i >= 1; i--) {\n\t\t\t\t\t\t\tJDD.Ref(trans01);\n\t\t\t\t\t\t\tJDD.Ref(cexDDs.get(i));\n\t\t\t\t\t\t\ttmp3 = JDD.And(trans01, cexDDs.get(i));\n\t\t\t\t\t\t\tJDD.Ref(cexDDs.get(i - 1));\n\t\t\t\t\t\t\ttmp3 = JDD.And(tmp3, JDD.PermuteVariables(cexDDs.get(i - 1), allDDRowVars, allDDColVars));\n\t\t\t\t\t\t\ttmp3 = JDD.ThereExists(tmp3, allDDColVars);\n\t\t\t\t\t\t\tJDD.Ref(transActions);\n\t\t\t\t\t\t\ttmp3 = JDD.Apply(JDD.TIMES, tmp3, transActions);\n\t\t\t\t\t\t\tint action = (int) JDD.FindMax(tmp3);\n\t\t\t\t\t\t\tcexActions.add(action > 0 ? model.getSynchs().get(action - 1) : \"\");\n\t\t\t\t\t\t\tJDD.Deref(tmp3);\n\t\t\t\t\t\t\tJDD.Deref(cexDDs.get(i));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tJDD.Deref(cexDDs.get(0));\n\t\t\t\t\t\tmainLog.println(\"Counterexample (action sequence): \" + cexActions);\n\t\t\t\t\t\tresult.setCounterexample(cexActions);\n\t\t\t\t\t}\n\t\t\t\t\t// Otherwise, convert list of BDDs to list of states\n\t\t\t\t\telse {\n\t\t\t\t\t\tCexPathAsBDDs cexBDDs = new CexPathAsBDDs(model);\n\t\t\t\t\t\tfor (i = cexDDs.size() - 1; i >= 0; i--) {\n\t\t\t\t\t\t\tcexBDDs.addState(cexDDs.get(i));\n\t\t\t\t\t\t\tJDD.Deref(cexDDs.get(i));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tresult.setCounterexample(cexBDDs);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Derefs\n\t\tJDD.Deref(b1);\n\t\tJDD.Deref(b2);\n\t\tJDD.Deref(transRel);\n\n\t\treturn new StateValuesMTBDD(tmp, model);\n\t}\n\n\t/**\n\t * Model check a CTL exists globally (EG) operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExistsGlobally(ExpressionTemporal expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b2, transRel, tmp, tmp2;\n\t\tboolean done;\n\t\tint iters, i;\n\t\tlong l;\n\t\t// SCC stuff\n\t\tList<JDDNode> sccs = null;\n\t\tJDDNode notInSCCs = null;\n\t\tint numSCCs = 0;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// Model check operand first, statesOfInterest = all\n\t\tb2 = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\n\t\tl = System.currentTimeMillis();\n\n\t\t// Get transition relation\n\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\tJDD.Ref(trans01);\n\t\t\ttransRel = JDD.ThereExists(trans01, ((NondetModel) model).getAllDDNondetVars());\n\t\t} else {\n\t\t\tJDD.Ref(trans01);\n\t\t\ttransRel = trans01;\n\t\t}\n\n\t\t// Strip out non-b2 states\n\t\tJDD.Ref(b2);\n\t\ttransRel = JDD.And(transRel, b2);\n\t\tJDD.Ref(b2);\n\t\ttransRel = JDD.And(transRel, JDD.PermuteVariables(b2, allDDRowVars, allDDColVars));\n\n\t\t// Find SCCs in resulting stripped down transition relation\n\t\tSCCComputer sccComputer = prism.getSCCComputer(reach, transRel, allDDRowVars, allDDColVars);\n\t\tsccComputer.computeSCCs();\n\t\tsccs = sccComputer.getSCCs();\n\t\tnotInSCCs = sccComputer.getNotInSCCs();\n\t\tnumSCCs = sccs.size();\n\n\t\t// Collect states from non-trivial SCCs in 'target'\n\t\t// (non-trivial = has a transition)\n\t\tJDDNode target = JDD.Create();\n\t\tfor (i = 0; i < numSCCs; i++) {\n\t\t\tJDDNode scc = sccs.get(i);\n\t\t\tif (scc != null) {\n\t\t\t\tif (JDD.AreIntersecting(scc, transRel)) {\n\t\t\t\t\tJDD.Ref(scc);\n\t\t\t\t\ttarget = JDD.Or(target, scc);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tmainLog.println(\"\\nCTL EG non-trivial SCC states: \" + JDD.GetNumMintermsString(target, allDDRowVars.n()));\n\n\t\t// Fixpoint loop - backwards reach\n\t\tdone = false;\n\t\titers = 0;\n\t\ttmp = JDD.Constant(0);\n\t\twhile (!done) {\n\t\t\titers++;\n\t\t\tJDD.Ref(tmp);\n\t\t\ttmp2 = JDD.PermuteVariables(tmp, allDDRowVars, allDDColVars);\n\t\t\tJDD.Ref(transRel);\n\t\t\ttmp2 = JDD.And(tmp2, transRel);\n\t\t\ttmp2 = JDD.ThereExists(tmp2, allDDColVars);\n\t\t\tJDD.Ref(target);\n\t\t\ttmp2 = JDD.Or(target, tmp2);\n\t\t\tif (tmp2.equals(tmp)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t\ttmp = tmp2;\n\t\t}\n\n\t\t// Print iterations/timing info\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"CTL EG reachability fixpoint: \" + iters + \" iterations in \" + (l / 1000.0) + \" seconds\");\n\n\t\t// Derefs\n\t\tJDD.Deref(b2);\n\t\tJDD.Deref(target);\n\t\tJDD.Deref(transRel);\n\t\tfor (i = 0; i < numSCCs; i++) {\n\t\t\tif (sccs.get(i) != null)\n\t\t\t\tJDD.Deref(sccs.get(i));\n\t\t}\n\t\tif (notInSCCs != null)\n\t\t\tJDD.Deref(notInSCCs);\n\n\t\treturn new StateValuesMTBDD(tmp, model);\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/comp/NondetModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t* Hongyang Qu <hongyang.qu@cs.ox.ac.uk> (University of Oxford)\n//\t* Carlos S. Bederian (Universidad Nacional de Cordoba)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport hybrid.PrismHybrid;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.io.PrintStream;\nimport java.util.ArrayList;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Vector;\n\nimport io.ModelExportFormat;\nimport io.ModelExportOptions;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport mtbdd.PrismMTBDD;\nimport parser.BooleanUtils;\nimport parser.ast.Coalition;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionFunc;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionQuant;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionStrategy;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.ast.PropertiesFile;\nimport parser.ast.RelOp;\nimport parser.type.TypeBool;\nimport parser.type.TypeDouble;\nimport parser.type.TypePathBool;\nimport parser.type.TypePathDouble;\nimport prism.AccuracyFactory;\nimport prism.IntegerBound;\nimport symbolic.comp.LTLModelChecker.LTLProduct;\nimport prism.OpRelOpBound;\nimport prism.Operator;\nimport prism.OpsAndBoundsList;\nimport prism.OptionsIntervalIteration;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismNative;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport prism.PrismUtils;\nimport symbolic.states.StateValues;\nimport symbolic.states.StateValuesDV;\nimport symbolic.states.StateValuesMTBDD;\nimport symbolic.states.StateValuesVoid;\nimport prism.TileList;\nimport sparse.PrismSparse;\nimport strat.MDStrategyIV;\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceOmegaDD;\nimport acceptance.AcceptanceRabin;\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceReachDD;\nimport acceptance.AcceptanceType;\nimport automata.DA;\nimport common.StopWatch;\nimport dv.DoubleVector;\nimport dv.IntegerVector;\nimport explicit.MinMax;\nimport symbolic.model.MDPQuotient;\nimport symbolic.model.Model;\nimport symbolic.model.NondetModel;\n\n/*\n * Model checker for MDPs\n */\npublic class NondetModelChecker extends NonProbModelChecker\n{\n\t// Model (MDP)\n\tprotected NondetModel model;\n\n\t// Extra (MDP) model info\n\tprotected JDDNode nondetMask;\n\tprotected JDDVars allDDNondetVars;\n\n\t// Options (in addition to those inherited from StateModelChecker):\n\n\t// Use 0,1 precomputation algorithms?\n\t// if 'precomp' is false, this disables all (non-essential) use of prob0/prob1\n\t// if 'precomp' is true, the values of prob0/prob1 determine what is used\n\t// (currently prob0/prob are not under user control)\n\tprotected boolean precomp;\n\tprotected boolean prob0;\n\tprotected boolean prob1;\n\t// Use fairness?\n\tprotected boolean fairness;\n\n\t// Constructor\n\n\tpublic NondetModelChecker(Prism prism, Model m, PropertiesFile pf) throws PrismException\n\t{\n\t\t// Initialise\n\t\tsuper(prism, m, pf);\n\t\tif (!(m instanceof NondetModel)) {\n\t\t\tthrow new PrismException(\"Wrong model type passed to NondetModelChecker.\");\n\t\t}\n\t\tmodel = (NondetModel) m;\n\t\tnondetMask = model.getNondetMask();\n\t\tallDDNondetVars = model.getAllDDNondetVars();\n\n\t\t// Inherit some options from parent Prism object and store locally.\n\t\tprecomp = prism.getPrecomp();\n\t\tprob0 = prism.getProb0();\n\t\tprob1 = prism.getProb1();\n\t\tfairness = prism.getFairness();\n\n\t\t// Display warning and/or make changes for some option combinations\n\t\tboolean advGenNeeded = genStrat || (prism.getExportAdv() != Prism.EXPORT_ADV_NONE);\n\t\tif (advGenNeeded) {\n\t\t\tif (engine != Prism.SPARSE) {\n\t\t\t\tmainLog.println(\"Switching engine since only sparse engine currently supports this computation...\");\n\t\t\t\tengine = Prism.SPARSE;\n\t\t\t}\n\t\t\tif (precomp && prob1) {\n\t\t\t\tmainLog.printWarning(\"Disabling Prob1 since this is needed for adversary generation\");\n\t\t\t\tprob1 = false;\n\t\t\t}\n\t\t}\n\n\t\t// Pass some options onto native code.\n\t\tPrismNative.setCompact(prism.getCompact());\n\t\tPrismNative.setTermCrit(prism.getTermCrit());\n\t\tPrismNative.setTermCritParam(prism.getTermCritParam());\n\t\tPrismNative.setMaxIters(prism.getMaxIters());\n\t\tPrismNative.setSBMaxMem(prism.getSBMaxMem());\n\t\tPrismNative.setNumSBLevels(prism.getNumSBLevels());\n\t\tPrismNative.setExportAdv(prism.getExportAdv());\n\t\tPrismNative.setExportAdvFilename(prism.getExportAdvFilename());\n\t}\n\n\tpublic NondetModelChecker createNewModelChecker(Prism prism, Model m, PropertiesFile pf) throws PrismException\n\t{\n\t\treturn new NondetModelChecker(prism, m, pf);\n\t}\n\n\t// Model checking functions\n\n\t@Override\n\tpublic StateValues checkExpression(Expression expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res;\n\n\t\t// <<>> or [[]] operator\n\t\tif (expr instanceof ExpressionStrategy) {\n\t\t\tres = checkExpressionStrategy((ExpressionStrategy) expr, statesOfInterest);\n\t\t}\n\t\t// P operator\n\t\telse if (expr instanceof ExpressionProb) {\n\t\t\tres = checkExpressionProb((ExpressionProb) expr, statesOfInterest);\n\t\t}\n\t\t// R operator\n\t\telse if (expr instanceof ExpressionReward) {\n\t\t\tres = checkExpressionReward((ExpressionReward) expr, statesOfInterest);\n\t\t}\n\t\t// Multi-objective\n\t\telse if (expr instanceof ExpressionFunc) {\n\t\t\t// Detect \"multi\" function\n\t\t\tif (((ExpressionFunc) expr).getName().equals(\"multi\")) {\n\t\t\t\tres = checkExpressionMultiObjective((ExpressionFunc) expr, statesOfInterest);\n\t\t\t}\n\t\t\t// For any other function, check as normal\n\t\t\telse {\n\t\t\t\tres = super.checkExpression(expr, statesOfInterest);\n\t\t\t}\n\t\t}\n\t\t// Otherwise, use the superclass\n\t\telse {\n\t\t\tres = super.checkExpression(expr, statesOfInterest);\n\t\t}\n\n\t\t// Filter out non-reachable states from solution\n\t\t// (only necessary for symbolically stored vectors)\n\t\tif (res instanceof StateValuesMTBDD)\n\t\t\tres.filter(reach);\n\n\t\treturn res;\n\t}\n\n\t/**\n\t * Model check a <<>> or [[]] operator expression.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionStrategy(ExpressionStrategy expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Will we be quantifying universally or existentially over strategies/adversaries?\n\t\tboolean forAll = !expr.isThereExists();\n\t\t\n\t\t// Extract coalition info\n\t\tCoalition coalition = expr.getCoalition();\n\t\t// Deal with the coalition operator here and then remove it\n\t\tif (coalition != null) {\n\t\t\tif (coalition.isEmpty()) {\n\t\t\t\t// An empty coalition negates the quantification (\"*\" has no effect)\n\t\t\t\tforAll = !forAll;\n\t\t\t}\n\t\t\tcoalition = null;\n\t\t}\n\n\t\t// Process operand(s)\n\t\tList<Expression> exprs = expr.getOperands();\n\t\t// Pass onto relevant method:\n\t\t// Single P operator\n\t\tif (exprs.size() == 1 && exprs.get(0) instanceof ExpressionProb) {\n\t\t\treturn checkExpressionProb((ExpressionProb) exprs.get(0), forAll, statesOfInterest);\n\t\t}\n\t\t// Single R operator\n\t\telse if (exprs.size() == 1 && exprs.get(0) instanceof ExpressionReward) {\n\t\t\treturn checkExpressionReward((ExpressionReward) exprs.get(0), forAll, statesOfInterest);\n\t\t}\n\t\t// Anything else is treated as multi-objective \n\t\telse {\n\t\t\treturn checkExpressionMultiObjective(exprs, forAll, statesOfInterest);\n\t\t}\n\t}\n\t\n\t/**\n\t * Model check a P operator expression.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionProb(ExpressionProb expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Use the default semantics for a standalone P operator\n\t\t// (i.e. quantification over all strategies)\n\t\treturn checkExpressionProb(expr, true, statesOfInterest);\n\t}\n\t\n\t/**\n\t * Model check a P operator expression.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t *\n\t * @param expr The P operator expression\n\t * @param forAll Are we checking \"for all strategies\" (true) or \"there exists a strategy\" (false)? [irrelevant for numerical (=?) queries]\n\t */\n\tprotected StateValues checkExpressionProb(ExpressionProb expr, boolean forAll, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Get info from P operator\n\t\tOpRelOpBound opInfo = expr.getRelopBoundInfo(constantValues);\n\t\tMinMax minMax = opInfo.getMinMax(model.getModelType(), forAll);\n\t\t\n\t\t// Check for trivial (i.e. stupid) cases\n\t\tif (opInfo.isTriviallyTrue()) {\n\t\t\tmainLog.printWarning(\"Checking for probability \" + opInfo.relOpBoundString() + \" - formula trivially satisfies all states\");\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\treturn new StateValuesMTBDD(reach, model, AccuracyFactory.doublesFromQualitative());\n\t\t} else if (opInfo.isTriviallyFalse()) {\n\t\t\tmainLog.printWarning(\"Checking for probability \" + opInfo.relOpBoundString() + \" - formula trivially satisfies no states\");\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\treturn new StateValuesMTBDD(JDD.Constant(0), model, AccuracyFactory.doublesFromQualitative());\n\t\t}\n\n\t\t// Compute probabilities\n\t\tboolean qual = opInfo.isQualitative() && precomp && prob0 && prob1;\n\t\tStateValues probs = checkProbPathFormula(expr.getExpression(), qual, minMax.isMin(), statesOfInterest);\n\n\t\t// Print out probabilities\n\t\tif (verbose) {\n\t\t\tmainLog.print(\"\\n\" + (minMax.isMin() ? \"Minimum\" : \"Maximum\") + \" probabilities (non-zero only) for all states:\\n\");\n\t\t\tprobs.print(mainLog);\n\t\t}\n\n\t\t// For =? properties, just return values\n\t\tif (opInfo.isNumeric()) {\n\t\t\treturn probs;\n\t\t}\n\t\t// Otherwise, compare against bound to get set of satisfying states\n\t\telse {\n\t\t\tJDDNode sol = probs.getBDDFromInterval(opInfo.getRelOp(), opInfo.getBound());\n\t\t\t// remove unreachable states from solution\n\t\t\tJDD.Ref(reach);\n\t\t\tsol = JDD.And(sol, reach);\n\t\t\t// free vector\n\t\t\tprobs.clear();\n\t\t\treturn new StateValuesMTBDD(sol, model);\n\t\t}\n\t}\n\n\t/**\n\t * Model check an R operator expression.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionReward(ExpressionReward expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Use the default semantics for a standalone R operator\n\t\t// (i.e. quantification over all strategies)\n\t    return checkExpressionReward(expr, true, statesOfInterest);\n\t}\n\t\n\t/**\n\t * Model check an R operator expression.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t *\n\t * @param expr The R operator expression\n\t * @param forAll Are we checking \"for all strategies\" (true) or \"there exists a strategy\" (false)? [irrelevant for numerical (=?) queries]\n\t */\n\tprotected StateValues checkExpressionReward(ExpressionReward expr, boolean forAll, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Get info from R operator\n\t\tOpRelOpBound opInfo = expr.getRelopBoundInfo(constantValues);\n\t\tMinMax minMax = opInfo.getMinMax(model.getModelType(), forAll);\n\n\t\t// Get rewards\n\t\tObject rs = expr.getRewardStructIndex();\n\t\tJDDNode stateRewards = getStateRewardsByIndexObject(rs, model, constantValues);\n\t\tcheckNegativeRewards(stateRewards, \"State\");\n\t\tJDDNode transRewards = getTransitionRewardsByIndexObject(rs, model, constantValues);\n\t\tcheckNegativeRewards(transRewards, \"Transition\");\n\n\t\t// Compute rewards\n\t\tStateValues rewards = null;\n\t\tExpression expr2 = expr.getExpression();\n\t\tif (expr2.getType() instanceof TypePathDouble) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr2;\n\t\t\tswitch (exprTemp.getOperator()) {\n\t\t\tcase ExpressionTemporal.R_C:\n\t\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\t\trewards = checkRewardCumul(exprTemp, stateRewards, transRewards, minMax.isMin(), statesOfInterest);\n\t\t\t\t} else {\n\t\t\t\t\trewards = checkRewardTotal(exprTemp, stateRewards, transRewards, minMax.isMin(), statesOfInterest);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ExpressionTemporal.R_I:\n\t\t\t\trewards = checkRewardInst(exprTemp, stateRewards, transRewards, minMax.isMin(), statesOfInterest);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t} else if (expr2.getType() instanceof TypePathBool || expr2.getType() instanceof TypeBool) {\n\t\t\trewards = checkRewardPathFormula(expr2, stateRewards, transRewards, minMax.isMin(), statesOfInterest);\n\t\t}\n\n\t\tif (rewards == null)\n\t\t\tthrow new PrismException(\"Unrecognised operator in R operator\");\n\n\t\t// print out rewards\n\t\tif (verbose) {\n\t\t\tmainLog.print(\"\\n\" + (minMax.isMin() ? \"Minimum\" : \"Maximum\") + \" rewards (non-zero only) for all states:\\n\");\n\t\t\trewards.print(mainLog);\n\t\t}\n\n\t\t// For =? properties, just return values\n\t\tif (opInfo.isNumeric()) {\n\t\t\treturn rewards;\n\t\t}\n\t\t// Otherwise, compare against bound to get set of satisfying states\n\t\telse {\n\t\t\tJDDNode sol = rewards.getBDDFromInterval(opInfo.getRelOp(), opInfo.getBound());\n\t\t\t// remove unreachable states from solution\n\t\t\tJDD.Ref(reach);\n\t\t\tsol = JDD.And(sol, reach);\n\t\t\t// free vector\n\t\t\trewards.clear();\n\t\t\treturn new StateValuesMTBDD(sol, model);\n\t\t}\n\t}\n\n\t/**\n\t * Model check a multi-objective query (from the contents of a strategy operator).\n\t * Return the result as a StateValues object (usually this gives values for all states,\n\t * but for a multi-objective query, we just give a single value, i.e., the statesOfInterest should be a singleton set).\n\t *\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t * @param exprs The list of Expressions specifying the objectives\n\t * @param forAll Are we checking \"for all strategies\" (true) or \"there exists a strategy\" (false)? [irrelevant for numerical (=?) queries]\n\t * @param statesOfInterest the states of interest\n\t */\n\tprotected StateValues checkExpressionMultiObjective(List<Expression> exprs, boolean forAll, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tif (fairness) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"Multi-objective reasoning under fairness currently not supported\");\n\t\t}\n\n\t\t// For now, just support a single expression (which may encode a Boolean combination of objectives)\n\t\tif (exprs.size() > 1) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Cannot currently check strategy operators with lists of expressions\");\n\t\t}\n\t\tExpression exprSub = exprs.get(0);\n\n\t\t// Boolean\n\t\tif (exprSub.getType() instanceof TypeBool) {\n\t\t\t// Copy expression because we will modify it\n\t\t\texprSub = (ExpressionStrategy) exprSub.deepCopy();\n\t\t\t// We will solve an existential query, so negate if universal\n\t\t\tif (forAll) {\n\t\t\t\texprSub = Expression.Not(exprSub);\n\t\t\t}\n\t\t\t// Convert to DNF\n\t\t\tList<List<Expression>> dnf = BooleanUtils.convertToDNFLists(exprSub);\n\t\t\t// Check all \"propositions\" of DNF are valid\n\t\t\tfor (List<Expression> conjunction : dnf) {\n\t\t\t\tfor (Expression prop : conjunction) {\n\t\t\t\t\tif (Expression.isNot(prop)) {\n\t\t\t\t\t\tprop = ((ExpressionUnaryOp) prop).getOperand();\n\t\t\t\t\t}\n\t\t\t\t\tif (!(prop instanceof ExpressionQuant)) {\n\t\t\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\t\t\tthrow new PrismException(\"Expression \" + prop + \" is not allowed in a multi-objective query\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Push negation inside objectives\n\t\t\tfor (List<Expression> conjunction : dnf) {\n\t\t\t\tfor (int j = 0; j < conjunction.size(); j++) {\n\t\t\t\t\tExpression prop = conjunction.get(j);\n\t\t\t\t\tif (Expression.isNot(prop)) {\n\t\t\t\t\t\tExpressionQuant exprQuant = (ExpressionQuant) ((ExpressionUnaryOp) prop).getOperand();\n\t\t\t\t\t\texprQuant.setRelOp(exprQuant.getRelOp().negate());\n\t\t\t\t\t\tconjunction.set(j, exprQuant);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Print reduced query\n\t\t\tmainLog.println(\"\\nReducing multi-objective query to DNF: \" + BooleanUtils.convertDNFListsToExpression(dnf));\n\n\t\t\t// Only handle a single disjunct for now\n\t\t\tif (dnf.size() > 1) {\n\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\tthrow new PrismException(\"Multi-objective model checking of multiple disjuncts not yet supported\");\n\t\t\t}\n\t\t\t// Convert to multi(...)\n\t\t\tExpressionFunc exprMulti = new ExpressionFunc(\"multi\");\n\t\t\tfor (Expression conjunct : dnf.get(0)) {\n\t\t\t\texprMulti.addOperand(conjunct);\n\t\t\t}\n\t\t\t// Handle negation\n\t\t\tif (forAll) {\n\t\t\t\treturn checkExpression(Expression.Not(exprMulti), statesOfInterest);\n\t\t\t} else {\n\t\t\t\treturn checkExpressionMultiObjective(exprMulti, statesOfInterest);\n\t\t\t}\n\t\t} else if (exprSub.getType() instanceof TypeDouble) {\n\t\t\treturn checkExpressionMultiObjective(exprs, statesOfInterest);\n\t\t} else {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Multi-objective model checking not supported for: \" + exprSub);\n\t\t}\n\t}\n\t\n\t/**\n\t * Model check a multi-objective expression and return the result.\n\t * For multi-objective queries, we only find the value for one state.\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionMultiObjective(ExpressionFunc expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Extract objective list from 'multi' function\n\t\tList<Expression> exprs = new ArrayList<Expression>();\n\t\tint n = expr.getNumOperands();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\texprs.add(expr.getOperand(i));\n\t\t}\n\t\treturn checkExpressionMultiObjective(exprs, statesOfInterest);\n\t}\n\t\n\t/**\n\t * Model check a multi-objective expression and return the result.\n\t * For multi-objective queries, we only find the value for one state.\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionMultiObjective(List<Expression> exprs, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Objective/target info\n\t\tList<JDDNode> multitargetDDs = null;\n\t\tList<Integer> multitargetIDs = null;\n\n\t\t// LTL/product model stuff\n\t\tNondetModel modelProduct, modelNew;\n\t\tJDDVars[] draDDRowVars, draDDColVars;\n\t\tMultiObjModelChecker mcMo;\n\t\tLTLModelChecker mcLtl;\n\t\tExpression[] ltl;\n\t\tDA<BitSet,AcceptanceRabin>[] dra;\n\t\t// State index info\n\t\t// Misc\n\t\tboolean negateresult = false;\n\t\tint conflictformulae = 0;\n\t\tboolean hasMaxReward = false;\n\t\t//boolean hasLTLconstraint = false;\n\n\t\tif (fairness) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"Multi-objective reasoning under fairness currently not supported\");\n\t\t}\n\n\t\tif (doIntervalIteration) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"Interval iteration currently not supported for multi-objective reasoning\");\n\t\t}\n\n\t\t// Make sure we are only expected to compute a value for a single state,\n\t\t// i.e., that statesOfInterest is a singleton\n\t\tif (!JDD.isSingleton(statesOfInterest, model.getAllDDRowVars())) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Multi-objective model checking can only compute values from a single state\");\n\t\t}\n\t\tJDDNode stateOfInterest = statesOfInterest;\n\n\t\t// Can't do LTL with time-bounded variants of the temporal operators\n\t\t// TODO removed since it is allowed for valiter.\n\t\t// TODO make sure it is treated correctly for all params\n\t\t/*if (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tthrow new PrismException(\"Time-bounded operators not supported in LTL: \" + expr);\n\t\t}*/\n\n\t\t// Check format and extract bounds/etc.\n\t\tint numObjectives = exprs.size();\n\t\tOpsAndBoundsList opsAndBounds = new OpsAndBoundsList();\n\t\tList<JDDNode> transRewardsList = new ArrayList<JDDNode>();\n\t\tList<Expression> pathFormulas = new ArrayList<Expression>(numObjectives);\n\t\tfor (int i = 0; i < numObjectives; i++) {\n\t\t\textractInfoFromMultiObjectiveOperand((ExpressionQuant) exprs.get(i), opsAndBounds, transRewardsList, pathFormulas, i);\n\t\t}\n\n\t\t//currently we do 1 numerical subject to booleans, or multiple numericals only \n\t\tif (opsAndBounds.numberOfNumerical() > 1 &&\n\t\t\t\topsAndBounds.numberOfNumerical() < opsAndBounds.probSize() + opsAndBounds.rewardSize()) {\n\t\t\tJDD.Deref(stateOfInterest);\n\t\t\tthrow new PrismException(\"Multiple min/max queries cannot be combined with boolean queries.\");\n\t\t}\n\t\t\n\t\tnegateresult = opsAndBounds.contains(Operator.P_MIN);\n\t\thasMaxReward = opsAndBounds.contains(Operator.R_GE) || opsAndBounds.contains(Operator.R_MAX);\n\n\t\t// Multi-objective model checking\n\n\t\t// Create arrays to store LTL/DRA info\n\t\tltl = new Expression[numObjectives];\n\t\tdra = new DA[numObjectives];\n\t\tdraDDRowVars = new JDDVars[numObjectives];\n\t\tdraDDColVars = new JDDVars[numObjectives];\n\n\t\t// For LTL/multi-obj model checking routines\n\t\tmcLtl = new LTLModelChecker(prism);\n\t\tmcMo = new MultiObjModelChecker(prism);\n\n\t\t// Product is initially just the original model (we build it recursively)\n\t\tmodelProduct = model;\n\n\t\t// Go through probabilistic objectives and construct product MDP.\n\t\tlong l = System.currentTimeMillis();\n\t\tboolean originalmodel = true;\n\t\tfor (int i = 0; i < numObjectives; i++) {\n\t\t\tif (opsAndBounds.isProbabilityObjective(i)) {\n\t\t\t\tdraDDRowVars[i] = new JDDVars();\n\t\t\t\tdraDDColVars[i] = new JDDVars();\n\t\t\t\tmodelNew = mcMo.constructDRAandProductMulti(modelProduct, mcLtl, this, ltl[i], i, dra, opsAndBounds.getOperator(i), pathFormulas.get(i),\n\t\t\t\t\t\tdraDDRowVars[i], draDDColVars[i], stateOfInterest);\n\t\t\t\t// Deref old product (unless is the original model)\n\t\t\t\tif (i > 0 & !originalmodel)\n\t\t\t\t\tmodelProduct.clear();\n\t\t\t\t// Store new product\n\t\t\t\tmodelProduct = modelNew;\n\t\t\t\toriginalmodel = false;\n\t\t\t}\n\t\t}\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"Total time for product construction: \" + l / 1000.0 + \" seconds.\");\n\n\t\t// TODO: move this above\n\t\t// Replace min by max and <= by >=\n\t\topsAndBounds.makeAllProbUp();\n\n\t\t// Print some info\n\t\toutputProductMulti(modelProduct);\n\n\t\t// Construct rewards for product model\n\t\tList<JDDNode> transRewardsListProduct = new ArrayList<JDDNode>();\n\t\tfor (JDDNode transRewards : transRewardsList) {\n\t\t\tJDD.Ref(transRewards);\n\t\t\tJDD.Ref(modelProduct.getTrans01());\n\t\t\ttransRewardsListProduct.add(JDD.Apply(JDD.TIMES, transRewards, modelProduct.getTrans01()));\n\t\t}\n\n\t\t// Removing actions with non-zero reward from the product for maximum cases\n\t\tif (hasMaxReward /*& hasLTLconstraint*/) {\n\t\t\tmcMo.removeNonZeroMecsForMax(modelProduct, mcLtl, transRewardsList, opsAndBounds, numObjectives, dra, draDDRowVars, draDDColVars);\n\t\t}\n\n\t\t// Remove all non-zero reward from trans in order to search for zero reward end components\n\t\tJDDNode tmptrans = modelProduct.getTrans();\n\t\tJDDNode tmptrans01 = modelProduct.getTrans01();\n\t\tboolean transchanged = mcMo.removeNonZeroRewardTrans(modelProduct, transRewardsList, opsAndBounds);\n\n\t\t// Compute all maximal end components\n\t\tArrayList<ArrayList<JDDNode>> allstatesH = new ArrayList<ArrayList<JDDNode>>(numObjectives);\n\t\tArrayList<ArrayList<JDDNode>> allstatesL = new ArrayList<ArrayList<JDDNode>>(numObjectives);\n\t\tJDDNode acceptanceVector_H = JDD.Constant(0);\n\t\tJDDNode acceptanceVector_L = JDD.Constant(0);\n\t\tfor (int i = 0; i < numObjectives; i++) {\n\t\t\tif (opsAndBounds.isProbabilityObjective(i)) {\n\t\t\t\tArrayList<JDDNode> statesH = new ArrayList<JDDNode>();\n\t\t\t\tArrayList<JDDNode> statesL = new ArrayList<JDDNode>();\n\t\t\t\tfor (int k = 0; k < dra[i].getAcceptance().size(); k++) {\n\t\t\t\t\tJDDNode tmpH = JDD.Constant(0);\n\t\t\t\t\tJDDNode tmpL = JDD.Constant(0);\n\t\t\t\t\tfor (int j = 0; j < dra[i].size(); j++) {\n\t\t\t\t\t\tif (!dra[i].getAcceptance().get(k).getL().get(j)) {\n\t\t\t\t\t\t\ttmpH = JDD.SetVectorElement(tmpH, draDDRowVars[i], j, 1.0);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tif (dra[i].getAcceptance().get(k).getK().get(j)) {\n\t\t\t\t\t\t\ttmpL = JDD.SetVectorElement(tmpL, draDDRowVars[i], j, 1.0);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tstatesH.add(tmpH);\n\t\t\t\t\tJDD.Ref(tmpH);\n\t\t\t\t\tacceptanceVector_H = JDD.Or(acceptanceVector_H, tmpH);\n\t\t\t\t\tstatesL.add(tmpL);\n\t\t\t\t\tJDD.Ref(tmpL);\n\t\t\t\t\tacceptanceVector_L = JDD.Or(acceptanceVector_L, tmpL);\n\t\t\t\t}\n\t\t\t\tallstatesH.add(i, statesH);\n\t\t\t\tallstatesL.add(i, statesL);\n\t\t\t} else {\n\t\t\t\tallstatesH.add(i, null);\n\t\t\t\tallstatesL.add(i, null);\n\t\t\t}\n\t\t}\n\n\t\t// Find accepting maximum end components for each LTL formula\n\t\tList<JDDNode> allecs = mcMo.computeAllEcs(modelProduct, mcLtl, allstatesH, allstatesL, acceptanceVector_H, acceptanceVector_L, draDDRowVars, draDDColVars,\n\t\t\t\topsAndBounds, numObjectives);\n\n\t\t// Create array to store BDDs for targets (i.e. accepting EC states); probability objectives only \n\t\tList<JDDNode> targetDDs = new ArrayList<JDDNode>(numObjectives);\n\t\tfor (int i = 0; i < numObjectives; i++) {\n\t\t\tif (opsAndBounds.isProbabilityObjective(i)) {\n\t\t\t\tmainLog.println(\"\\nFinding accepting end components for \" + pathFormulas.get(i).toString() + \"...\");\n\t\t\t\ttargetDDs.add(mcMo.computeAcceptingEndComponent(dra[i], modelProduct, draDDRowVars[i], draDDColVars[i], allecs, allstatesH.get(i),\n\t\t\t\t\t\tallstatesL.get(i), mcLtl, conflictformulae > 1));\n\t\t\t} else {\n\t\t\t\t// (not used currently)\n\t\t\t\t// Fixme: maybe not efficient\n\t\t\t\tif (pathFormulas.get(i) != null) {\n\t\t\t\t\tJDDNode dd = checkExpressionDD(pathFormulas.get(i), model.getReach().copy());\n\t\t\t\t\tJDD.Ref(modelProduct.getReach());\n\t\t\t\t\tdd = JDD.And(dd, modelProduct.getReach());\n\t\t\t\t\ttargetDDs.add(dd);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// check if there are conflicts in objectives\n\t\tif (conflictformulae > 1) {\n\t\t\tmultitargetDDs = new ArrayList<JDDNode>();\n\t\t\tmultitargetIDs = new ArrayList<Integer>();\n\t\t\tmcMo.checkConflictsInObjectives(modelProduct, mcLtl, conflictformulae, numObjectives, opsAndBounds, dra, draDDRowVars, draDDColVars, targetDDs, allstatesH,\n\t\t\t\t\tallstatesL, multitargetDDs, multitargetIDs);\n\t\t}\n\n\t\tfor (JDDNode ec : allecs)\n\t\t\tJDD.Deref(ec);\n\n\t\t//new StateListMTBDD(modelProduct.getReach(), modelProduct).print(mainLog);\n\t\t//try { prism.exportTransToFile(modelProduct, true, Prism.EXPORT_DOT_STATES, new java.io.File(\"product.dot\")); } catch(Exception e) {}\n\n\t\t// Note: for multi-objective model checking, we construct the product MDP for only a single initial state\n\t\t// (unlike for normal LTL model checking) so it is safe to use modelProduct.getStart() here to pass in the initial states.\n\n\t\t// Add a dummy LTL formula to get generate target states when there is no LTL formula in the query\n\t\t// TODO most probably this is not needed for non-LP solution methods\n\t\tif (targetDDs.isEmpty() && prism.getMDPSolnMethod() == Prism.MDP_MULTI_LP) {\n\t\t\taddDummyFormula(modelProduct, mcLtl, targetDDs, opsAndBounds);\n\t\t}\n\n\t\t// Put unmodified trans and trans01 to modelProduct\n\t\tif (transchanged) {\n\t\t\tmodelProduct.resetTrans(tmptrans);\n\t\t\tmodelProduct.resetTrans01(tmptrans01);\n\t\t}\n\n\t\tObject value;\n\t\ttry {\n\t\t\t// Do multi-objective computation\n\t\t\tvalue = mcMo.computeMultiReachProbs(modelProduct, mcLtl, transRewardsListProduct, modelProduct.getStart(), targetDDs, multitargetDDs, multitargetIDs, opsAndBounds,\n\t\t\t                                    conflictformulae > 1);\n\t\t} finally {\n\t\t\t// Deref, clean up\n\t\t\tJDD.Deref(stateOfInterest);\n\t\t\tif (modelProduct != null && modelProduct != model)\n\t\t\t\tmodelProduct.clear();\n\t\t\tfor (int i = 0; i < numObjectives; i++) {\n\t\t\t\tif (opsAndBounds.isProbabilityObjective(i)) {\n\t\t\t\t\tdraDDRowVars[i].derefAll();\n\t\t\t\t\tdraDDColVars[i].derefAll();\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (JDDNode t : targetDDs)\n\t\t\t\tJDD.Deref(t);\n\t\t\tif (multitargetDDs != null)\n\t\t\t\tfor (JDDNode t : multitargetDDs)\n\t\t\t\t\tJDD.Deref(t);\n\t\t}\n\n\t\tif (value instanceof TileList) {\n\t\t\tif (opsAndBounds.numberOfNumerical() == 2) {\t\t\t\n\t\t\t\tsynchronized(TileList.getStoredTileLists()) {\n\t\t\t\t\tTileList.storedFormulasX.add(exprs.get(0));\n\t\t\t\t\tTileList.storedFormulasY.add(exprs.get(1));\n\n\t\t\t\t\tTileList.storedFormulas.add(exprs);\n\t\t\t\t\tTileList.storedTileLists.add((TileList) value);\n\t\t\t\t}\n\t\t\t} //else, i.e. in 3D, the output was treated in the algorithm itself.\n\n\t\t\treturn new StateValuesVoid(value);\n\t\t}\n\t\telse if (value instanceof Double) {\n\t\t\t// Return result. Note: we only compute the value for a single state.\n\t\t\tif (negateresult) {\n\t\t\t\tvalue = 1 - (Double) value;\n\t\t\t}\n\t\n\t\t\treturn new StateValuesMTBDD(JDD.Constant((Double) value), model);\n\t\t}\n\t\telse throw new PrismException(\"Do not know how to treat the returned value \" + value);\n\t\t\t\n\t}\n\n\t/**\n\t * Extract the information from the operator defining one objective of a multi-objective query,\n\t * store the info in the passed in arrays and so some checks.\n\t *  \n\t * @param exprQuant The operator for the objective\n\t * @param opsAndBounds Where to add info about ops/bounds\n\t * @param transRewardsList Where to add the transition rewards (R operators only)\n\t * @param pathFormulas Where to store the path formulas (for P operators; null for R operators)\n\t * @param origPosition The position (starting from 0) at which this operand occured in the call of multi(...)\n\t */\n\tprotected void extractInfoFromMultiObjectiveOperand(ExpressionQuant exprQuant, OpsAndBoundsList opsAndBounds, List<JDDNode> transRewardsList,\n\t\t\tList<Expression> pathFormulas, int origPosition) throws PrismException\n\t{\n\t\tExpressionProb exprProb = null;\n\t\tExpressionReward exprReward = null;\n\t\t\n\t\t// Check if it's a P or an R operator\n\t\tif (exprQuant instanceof ExpressionProb) {\n\t\t\texprProb = (ExpressionProb) exprQuant;\n\t\t\texprReward = null;\n\t\t} else if (exprQuant instanceof ExpressionReward) {\n\t\t\texprReward = (ExpressionReward) exprQuant;\n\t\t\texprProb = null;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Multi-objective properties can only contain P and R operators\");\n\t\t}\n\n\t\t// For a reward objective, store the transition rewards\n\t\tif (exprReward != null) {\n\t\t\tObject rs = exprReward.getRewardStructIndex();\n\t\t\t// Check there are no state rewards (which are not currently supported), and throw an exception if there are\n\t\t\tJDDNode stateRewards = getStateRewardsByIndexObject(rs, model, constantValues);\n\t\t\tif (stateRewards != null && !stateRewards.equals(JDD.ZERO)) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Multi-objective model checking does not support state rewards; please convert to transition rewards\");\n\t\t\t}\n\t\t\t// Add transition rewards to list\n\t\t\tJDDNode transRewards = getTransitionRewardsByIndexObject(rs, model, constantValues);\n\t\t\tcheckNegativeRewards(transRewards, \"Transition\");\n\t\t\ttransRewardsList.add(transRewards);\n\t\t}\n\t\t\n\t\t// Check that the temporal/reward operator is supported, and store step bounds if present\n\t\tint stepBound = 0;\n\t\tif (exprProb != null) {\n\t\t\t// F<=k is allowed\n\t\t\tExpression expr = exprProb.getExpression();\n\t\t\tif (expr.isSimplePathFormula() && Expression.isReach(expr)) {\n\t\t\t\tExpressionTemporal exprTemp = ((ExpressionTemporal) expr);\n\t\t\t\tif (exprTemp.getLowerBound() != null) {\n\t\t\t\t\tthrow new PrismException(\"Lower time bounds are not supported in multi-objective queries\");\n\t\t\t\t}\n\t\t\t\tif (exprTemp.getUpperBound() != null) {\n\t\t\t\t\tstepBound = exprTemp.getUpperBound().evaluateInt(constantValues);\n\t\t\t\t} else {\n\t\t\t\t\tstepBound = -1;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\t\t\tthrow new PrismException(\"Time bounds in multi-objective queries can only be on F or C operators\");\n\t\t\t\t} else {\n\t\t\t\t\tstepBound = -1;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif (exprReward != null) {\n\t\t\tExpressionTemporal exprTemp = ((ExpressionTemporal) exprReward.getExpression());\n\t\t\t// We only allow C or C<=k reward operators, others such as F are not supported currently\n\t\t\tif (exprTemp.getOperator() != ExpressionTemporal.R_C) {\n\t\t\t\tthrow new PrismException(\"Only the C and C>=k reward operators are currently supported for multi-objective properties (not \"\n\t\t\t\t\t\t+ exprTemp.getOperatorSymbol() + \")\");\n\t\t\t}\n\t\t\t// R [ C<=k ]\n\t\t\tif (exprTemp.getUpperBound() != null) {\n\t\t\t\tstepBound = exprTemp.getUpperBound().evaluateInt(constantValues);\n\t\t\t}\n\t\t\t// R [ C ]\n\t\t\telse {\n\t\t\t\tstepBound = -1;\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Get/check/store info about relational operator and bound\n\t\tOpRelOpBound opInfo = exprQuant.getRelopBoundInfo(constantValues);\n\t\tRelOp relOp = opInfo.getRelOp();\n\t\tif (relOp.isStrict()) {\n\t\t\tthrow new PrismException(\"Multi-objective properties can not use strict inequalities on P/R operators\");\n\t\t}\n\t\tOperator op;\n\t\tif (relOp == RelOp.MAX) {\n\t\t\top = (exprProb != null) ? Operator.P_MAX : Operator.R_MAX;\n\t\t} else if (relOp == RelOp.GEQ) {\n\t\t\top = (exprProb != null) ? Operator.P_GE : Operator.R_GE;\n\t\t} else if (relOp == RelOp.MIN) {\n\t\t\top = (exprProb != null) ? Operator.P_MIN : Operator.R_MIN;\n\t\t} else if (relOp == RelOp.LEQ) {\n\t\t\top = (exprProb != null) ? Operator.P_LE : Operator.R_LE;\n\t\t} else {\n\t\t\tthrow new PrismException(\"Multi-objective properties can only contain P/R operators with max/min=? or lower/upper probability bounds\");\n\t\t}\n\t\t// Find bound\n\t\tdouble p = opInfo.isNumeric() ? -1.0 : opInfo.getBound();\n\t\t// Subtract bound from 1 if of the form P<=p\n\t\tif (opInfo.isProbabilistic() && opInfo.getRelOp().isUpperBound()) {\n\t\t\tp = 1 - p;\n\t\t}\n\t\t// Store bound\n\t\topsAndBounds.add(opInfo, op, p, stepBound, origPosition);\n\n\t\t// Finally, extract path formulas\n\t\tif (exprProb != null) {\n\t\t\tpathFormulas.add(exprProb.getExpression());\n\t\t}\n\t\tif (exprReward != null) {\n\t\t\tpathFormulas.add(null);\n\t\t}\n\t}\n\n\tprotected void addDummyFormula(NondetModel modelProduct, LTLModelChecker mcLtl, List<JDDNode> targetDDs, OpsAndBoundsList opsAndBounds)\n\t\t\tthrows PrismException\n\t{\n\t\tList<JDDNode> tmpecs = mcLtl.findMECStates(modelProduct, modelProduct.getReach());\n\t\tJDDNode acceptingStates = JDD.Constant(0);\n\t\tfor (JDDNode set : tmpecs)\n\t\t\tacceptingStates = JDD.Or(acceptingStates, set);\n\t\ttargetDDs.add(acceptingStates);\n\t\tOpRelOpBound opInfo = new OpRelOpBound(\"P\", RelOp.GEQ, 0.0);\n\t\topsAndBounds.add(opInfo, Operator.P_GE, 0.0, -1, -1);\n\t}\n\n\t//Prints info about the product model in multi-objective\n\tprotected void outputProductMulti(NondetModel modelProduct) throws PrismException\n\t{\n\t\t// Print product info\n\t\tmainLog.println();\n\t\tmodelProduct.printTransInfo(mainLog, prism.getExtraDDInfo());\n\n\t\t// Output product, if required\n\t\tif (prism.getExportProductTrans()) {\n\t\t\ttry {\n\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions();\n\t\t\t\texportOptions.setModelPrecision(getSettings().getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION));\n\t\t\t\tmainLog.println(\"\\nExporting product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"...\");\n\t\t\t\tmodelProduct.exportToFile(new File(prism.getExportProductTransFilename()), exportOptions);\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.printWarning(\"Could not export product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\t\tif (prism.getExportProductStates()) {\n\t\t\tmainLog.println(\"\\nExporting product state space to file \\\"\" + prism.getExportProductStatesFilename() + \"\\\"...\");\n\t\t\tPrismFileLog out = new PrismFileLog(prism.getExportProductStatesFilename());\n\t\t\tmodelProduct.exportStates(Prism.EXPORT_PLAIN, out);\n\t\t\tout.close();\n\t\t}\n\t}\n\n\t// Model checking functions\n\t\n\t/**\n\t * Compute probabilities for the contents of a P operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbPathFormula(Expression expr, boolean qual, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Test whether this is a simple path formula (i.e. PCTL)\n\t\t// and whether we want to use the corresponding algorithms\n\t\tboolean useSimplePathAlgo = expr.isSimplePathFormula();\n\n\t\tif (useSimplePathAlgo && settings.getBoolean(PrismSettings.PRISM_PATH_VIA_AUTOMATA) &&\n\t\t    LTLModelChecker.isSupportedLTLFormula(model.getModelType(), expr)) {\n\t\t\t// If PRISM_PATH_VIA_AUTOMATA is true, we want to use the LTL engine\n\t\t\t// whenever possible\n\t\t\tuseSimplePathAlgo = false;\n\t\t}\n\n\t\tif (useSimplePathAlgo) {\n\t\t\treturn checkProbPathFormulaSimple(expr, qual, min, statesOfInterest);\n\t\t} else {\n\t\t\treturn checkProbPathFormulaLTL(expr, qual, min, statesOfInterest);\n\t\t}\n\t}\n\n\t/**\n\t * Compute probabilities for a simple, non-LTL path operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbPathFormulaSimple(Expression expr, boolean qual, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tboolean negated = false;\n\t\tStateValues probs = null;\n\n\t\texpr = Expression.convertSimplePathFormulaToCanonicalForm(expr);\n\n\t\t// Negation\n\t\tif (expr instanceof ExpressionUnaryOp &&\n\t\t    ((ExpressionUnaryOp)expr).getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\t// mark as negated, switch from min to max and vice versa\n\t\t\tnegated = true;\n\t\t\tmin = !min;\n\t\t\texpr = ((ExpressionUnaryOp)expr).getOperand();\n\t\t}\n\n\t\tif (expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\t// Next\n\t\t\tif (exprTemp.getOperator() == ExpressionTemporal.P_X) {\n\t\t\t\tprobs = checkProbNext(exprTemp, min, statesOfInterest);\n\t\t\t}\n\t\t\t// Until\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\t\tprobs = checkProbBoundedUntil(exprTemp, min, statesOfInterest);\n\t\t\t\t} else {\n\t\t\t\t\tprobs = checkProbUntil(exprTemp, qual, min, statesOfInterest);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (probs == null)\n\t\t\tthrow new PrismException(\"Unrecognised path operator in P operator\");\n\n\t\tif (negated) {\n\t\t\t// Subtract from 1 for negation\n\t\t\tprobs.subtractFromOne();\n\t\t}\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute probabilities for a next operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbNext(ExpressionTemporal expr, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b;\n\t\tStateValues probs = null;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// model check operand first, statesOfInterest = all\n\t\tb = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb = \" + JDD.GetNumMintermsString(b,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\t// compute probabilities\n\t\tprobs = computeNextProbs(trans, b, min);\n\n\t\t// derefs\n\t\tJDD.Deref(b);\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute probabilities for a bounded until operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbBoundedUntil(ExpressionTemporal expr, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b1, b2;\n\t\tStateValues probs = null;\n\t\tInteger lowerBound;\n\t\tIntegerBound bounds;\n\t\tint i;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// get and check bounds information\n\t\tbounds = IntegerBound.fromExpressionTemporal(expr, constantValues, true);\n\n\t\t// model check operands first, statesOfInterest = all\n\t\tb1 = checkExpressionDD(expr.getOperand1(), model.getReach().copy());\n\t\ttry {\n\t\t\tb2 = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b1);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb1 = \" + JDD.GetNumMintermsString(b1,\n\t\t// allDDRowVars.n()));\n\t\t// mainLog.print(\" states, b2 = \" + JDD.GetNumMintermsString(b2,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\tif (bounds.hasLowerBound()) {\n\t\t\tlowerBound = bounds.getLowestInteger();\n\t\t} else {\n\t\t\tlowerBound = 0;\n\t\t}\n\n\t\tInteger windowSize = null;  // unbounded\n\t\tif (bounds.hasUpperBound()) {\n\t\t\twindowSize = bounds.getHighestInteger() - lowerBound;\n\t\t}\n\n\t\t// compute probabilities for Until<=windowSize\n\t\tif (windowSize == null) {\n\t\t\t// unbounded\n\t\t\ttry {\n\t\t\t\tprobs = checkProbUntil(b1, b2, false, min);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(b1);\n\t\t\t\tJDD.Deref(b2);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t} else if (windowSize == 0) {\n\t\t\t// the trivial case: windowSize = 0\n\t\t\t// prob is 1 in b2 states, 0 otherwise\n\t\t\tJDD.Ref(b2);\n\t\t\tprobs = new StateValuesMTBDD(b2, model, AccuracyFactory.doublesFromQualitative());\n\t\t} else {\n\t\t\ttry {\n\t\t\t\tprobs = computeBoundedUntilProbs(trans, trans01, b1, b2, windowSize, min);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(b1);\n\t\t\t\tJDD.Deref(b2);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\t// perform lowerBound restricted next-step computations to\n\t\t// deal with lower bound.\n\t\tif (lowerBound > 0) {\n\t\t\tfor (i = 0; i < lowerBound; i++) {\n\t\t\t\tprobs = computeRestrictedNext(trans, b1, probs, min);\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(b1);\n\t\tJDD.Deref(b2);\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute probabilities for an (unbounded) until operator.\n\t * Note: This method is split into two steps so that the LTL model checker can use the second part directly.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbUntil(ExpressionTemporal expr, boolean qual, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b1, b2;\n\t\tStateValues probs = null;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// model check operands first\n\t\tb1 = checkExpressionDD(expr.getOperand1(), model.getReach().copy());\n\t\ttry {\n\t\t\tb2 = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b1);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb1 = \" + JDD.GetNumMintermsString(b1,\n\t\t// allDDRowVars.n()));\n\t\t// mainLog.print(\" states, b2 = \" + JDD.GetNumMintermsString(b2,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\ttry {\n\t\t\tprobs = checkProbUntil(b1, b2, qual, min);\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b1);\n\t\t\tJDD.Deref(b2);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(b1);\n\t\tJDD.Deref(b2);\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute probabilities for an (unbounded) until operator (b1 U b2).\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t *\n\t * @param b1 Remain in these states\n\t * @param b2 Target states\n\t * @param qual True if only qualititative (0/1) results are needed\n\t * @param min Min or max probabilities (true=min, false=max)\n\t */\n\tprotected StateValues checkProbUntil(JDDNode b1, JDDNode b2, boolean qual, boolean min) throws PrismException\n\t{\n\t\tJDDNode splus, newb1, newb2;\n\t\tStateValues probs = null;\n\t\tlong l;\n\n\t\t// compute probabilities\n\n\t\t// if doing min with fairness, we solve a different problem\n\t\t// (as in christel's habilitation)\n\t\tif (min && fairness) {\n\n\t\t\t// print out reminder that we have to do conversion for fairness\n\t\t\tmainLog.print(\"\\nDoing conversion for fairness...\\n\");\n\t\t\t// start timer\n\t\t\tl = System.currentTimeMillis();\n\t\t\t// convert to new problem\n\t\t\tnewb2 = PrismMTBDD.Prob0A(trans01, reach, allDDRowVars, allDDColVars, allDDNondetVars, b1, b2);\n\t\t\tJDD.Ref(newb2);\n\t\t\tsplus = JDD.Not(newb2);\n\t\t\tJDD.Ref(splus);\n\t\t\tJDD.Ref(b2);\n\t\t\tnewb1 = JDD.And(splus, JDD.Not(b2));\n\t\t\tJDD.Deref(splus);\n\t\t\tJDD.Ref(reach);\n\t\t\tnewb1 = JDD.And(reach, newb1);\n\t\t\tJDD.Ref(reach);\n\t\t\tnewb2 = JDD.And(reach, newb2);\n\t\t\t// stop timer\n\t\t\tl = System.currentTimeMillis() - l;\n\t\t\t// print out conversion info\n\t\t\tmainLog.print(\"\\nTime for fairness conversion: \" + l / 1000.0 + \" seconds.\\n\");\n\t\t\t// mainLog.print(\"\\nb1 = \" + JDD.GetNumMintermsString(newb1, allDDRowVars.n()));\n\t\t\t// mainLog.print(\" states, b2 = \" + JDD.GetNumMintermsString(newb2, allDDRowVars.n()) + \" states\\n\");\n\t\t} else {\n\t\t\tJDD.Ref(b1);\n\t\t\tnewb1 = b1;\n\t\t\tJDD.Ref(b2);\n\t\t\tnewb2 = b2;\n\t\t}\n\n\t\t// if requested (i.e. when prob bound is 0 or 1 and precomputation algorithms are enabled),\n\t\t// compute probabilities qualitatively\n\t\tif (qual) {\n\t\t\tmainLog.print(\"\\nProbability bound in formula is 0/1 so not computing exact probabilities...\\n\");\n\t\t\t// for fairness, we compute max here\n\t\t\tprobs = computeUntilProbsQual(trans01, newb1, newb2, min && !fairness);\n\t\t}\n\t\t// otherwise actually compute probabilities\n\t\telse {\n\t\t\t// for fairness, we compute max here\n\t\t\ttry {\n\t\t\t\tprobs = computeUntilProbs(trans, transActions, trans01, newb1, newb2, min && !fairness);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(newb1);\n\t\t\t\tJDD.Deref(newb2);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\t// if we're doing min with fairness,\n\t\t// we need to subtract the probabilities from\n\t\t// one to get the actual answer\n\t\tif (min && fairness) {\n\t\t\tprobs.subtractFromOne();\n\t\t}\n\n\t\t// Derefs\n\t\tJDD.Deref(newb1);\n\t\tJDD.Deref(newb2);\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute probabilities for an LTL path formula\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbPathFormulaLTL(Expression expr, boolean qual, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tLTLModelChecker mcLtl;\n\t\tStateValues probsProduct = null, probs = null;\n\t\tVector<JDDNode> labelDDs = new Vector<JDDNode>();\n\t\tDA<BitSet, ? extends AcceptanceOmega> da;\n\t\tNondetModel modelProduct;\n\t\tNondetModelChecker mcProduct;\n\t\tJDDNode startMask;\n\t\tJDDVars daDDRowVars, daDDColVars;\n\t\tint i;\n\t\tlong l;\n\n\t\t// For min probabilities, need to negate the formula\n\t\t// (But check fairness setting since this may affect min/max)\n\t\t// (add parentheses to allow re-parsing if required)\n\t\tif (min && !fairness) {\n\t\t\texpr = Expression.Not(Expression.Parenth(expr));\n\t\t}\n\n\t\t// Can't do \"dfa\" properties yet\n\t\tif (expr instanceof ExpressionFunc && ((ExpressionFunc) expr).getName().equals(\"dfa\")) {\n\t\t\tthrow new PrismException(\"Model checking for \\\"dfa\\\" specifications not supported yet\");\n\t\t}\n\n\t\t// For LTL model checking routines\n\t\tmcLtl = new LTLModelChecker(prism);\n\t\t\n\t\t// Convert LTL formula to deterministic automaton (DA)\n\t\tAcceptanceType[] allowedAcceptance = {\n\t\t\t\tAcceptanceType.BUCHI,\n\t\t\t\tAcceptanceType.RABIN,\n\t\t\t\tAcceptanceType.GENERALIZED_RABIN,\n\t\t\t\tAcceptanceType.REACH\n\t\t};\n\t\ttry {\n\t\t\tda = mcLtl.constructDAForLTLFormula(this, model, expr, labelDDs, allowedAcceptance);\n\t\t} catch (Exception e) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Build product of MDP and automaton\n\t\tl = System.currentTimeMillis();\n\t\tmainLog.println(\"\\nConstructing MDP-\"+da.getAutomataType()+\" product...\");\n\t\tdaDDRowVars = new JDDVars();\n\t\tdaDDColVars = new JDDVars();\n\t\tmodelProduct = mcLtl.constructProductMDP(da, model, labelDDs, daDDRowVars, daDDColVars, statesOfInterest);\n\t\tl = System.currentTimeMillis() - l;\n\t\tmainLog.println(\"Time for product construction: \" + l / 1000.0 + \" seconds.\");\n\t\tmainLog.println();\n\t\tmodelProduct.printTransInfo(mainLog, prism.getExtraDDInfo());\n\t\t// Output product, if required\n\t\tif (prism.getExportProductTrans()) {\n\t\t\ttry {\n\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions();\n\t\t\t\texportOptions.setModelPrecision(getSettings().getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION));\n\t\t\t\tmainLog.println(\"\\nExporting product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"...\");\n\t\t\t\tmodelProduct.exportToFile(new File(prism.getExportProductTransFilename()), exportOptions);\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.printWarning(\"Could not export product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\t\tif (prism.getExportProductStates()) {\n\t\t\tmainLog.println(\"\\nExporting product state space to file \\\"\" + prism.getExportProductStatesFilename() + \"\\\"...\");\n\t\t\tPrismFileLog out = new PrismFileLog(prism.getExportProductStatesFilename());\n\t\t\tmodelProduct.exportStates(Prism.EXPORT_PLAIN, out);\n\t\t\tout.close();\n\t\t}\n\n\t\t// Find accepting states + compute reachability probabilities\n\t\tAcceptanceOmegaDD acceptance = da.getAcceptance().toAcceptanceDD(daDDRowVars);\n\t\tJDDNode acc;\n\t\tif (acceptance instanceof AcceptanceReachDD) {\n\t\t\tmainLog.println(\"\\nSkipping accepting MEC computation since acceptance is defined via goal states...\");\n\t\t\tacc = ((AcceptanceReachDD) acceptance).getGoalStates();\n\t\t\tJDD.Ref(modelProduct.getReach());\n\t\t\tacc = JDD.And(acc, modelProduct.getReach());\n\t\t} else {\n\t\t\tmainLog.println(\"\\nFinding accepting end components...\");\n\t\t\tacc = mcLtl.findAcceptingECStates(acceptance, modelProduct, daDDRowVars, daDDColVars, fairness);\n\t\t}\n\t\tacceptance.clear();\n\t\tmainLog.println(\"\\nComputing reachability probabilities...\");\n\t\tmcProduct = new NondetModelChecker(prism, modelProduct, null);\n\t\tprobsProduct = mcProduct.checkProbUntil(modelProduct.getReach(), acc, qual, min && fairness);\n\n\t\t// subtract from 1 if we're model checking a negated formula for regular Pmin\n\t\tif (min && !fairness) {\n\t\t\tprobsProduct.subtractFromOne();\n\t\t}\n\n\t\t// Output vector over product, if required\n\t\tif (prism.getExportProductVector()) {\n\t\t\t\tmainLog.println(\"\\nExporting product solution vector matrix to file \\\"\" + prism.getExportProductVectorFilename() + \"\\\"...\");\n\t\t\t\tPrismFileLog out = new PrismFileLog(prism.getExportProductVectorFilename());\n\t\t\t\tprobsProduct.print(out, false, false, false, false);\n\t\t\t\tout.close();\n\t\t}\n\t\t\n\t\t// Convert probability vector to original model\n\t\t// First, filter over DRA start states\n\t\tstartMask = mcLtl.buildStartMask(da, labelDDs, daDDRowVars);\n\t\tJDD.Ref(model.getReach());\n\t\tstartMask = JDD.And(model.getReach(), startMask);\n\t\tprobsProduct.filter(startMask);\n\t\t// Then sum over DD vars for the DRA state\n\t\tprobs = probsProduct.sumOverDDVars(daDDRowVars, model);\n\n\t\t// Deref, clean up\n\t\tprobsProduct.clear();\n\t\tmodelProduct.clear();\n\t\tfor (i = 0; i < labelDDs.size(); i++) {\n\t\t\tJDD.Deref(labelDDs.get(i));\n\t\t}\n\t\tJDD.Deref(acc);\n\t\tJDD.Deref(startMask);\n\t\tdaDDRowVars.derefAll();\n\t\tdaDDColVars.derefAll();\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute rewards for a cumulative reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardCumul(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tint time; // time\n\t\tStateValues rewards = null;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// check that there is an upper time bound\n\t\tif (expr.getUpperBound() == null) {\n\t\t\tthrow new PrismException(\"Cumulative reward operator without time bound (C) is only allowed for multi-objective queries\");\n\t\t}\n\n\t\t// get info from inst reward\n\t\ttime = expr.getUpperBound().evaluateInt(constantValues);\n\t\tif (time < 0) {\n\t\t\tthrow new PrismException(\"Invalid time bound \" + time + \" in cumulative reward formula\");\n\t\t}\n\n\t\t// a trivial case: \"<=0\"\n\t\tif (time == 0) {\n\t\t\trewards = new StateValuesMTBDD(JDD.Constant(0), model, AccuracyFactory.doublesFromQualitative());\n\t\t} else {\n\t\t\t// compute rewards\n\t\t\ttry {\n\t\t\t\trewards = computeCumulRewards(trans, stateRewards, transRewards, time, min);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute rewards for a total reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardTotal(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\t\tStateValues rewards = computeTotalRewards(trans, trans01, transActions, stateRewards, transRewards, min);\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute rewards for an instantaneous reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardInst(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tint time; // time bound\n\t\tStateValues rewards = null;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// get info from bounded until\n\t\ttime = expr.getUpperBound().evaluateInt(constantValues);\n\t\tif (time < 0) {\n\t\t\tthrow new PrismException(\"Invalid bound \" + time + \" in instantaneous reward property\");\n\t\t}\n\n\t\t// compute rewards\n\t\trewards = computeInstRewards(trans, stateRewards, time, min);\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute rewards for a reachability reward operator (either simple reachability or co-safe LTL).\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardPathFormula(Expression expr, JDDNode stateRewards, JDDNode transRewards, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tif (Expression.isReach(expr)) {\n\t\t\treturn checkRewardReach((ExpressionTemporal) expr, stateRewards, transRewards, min, statesOfInterest);\n\t\t}\n\t\telse if (Expression.isCoSafeLTLSyntactic(expr, true)) {\n\t\t\treturn checkRewardCoSafeLTL(expr, stateRewards, transRewards, min, statesOfInterest);\n\t\t}\n\t\tJDD.Deref(statesOfInterest);\n\t\tthrow new PrismException(\"R operator contains a path formula that is not syntactically co-safe: \" + expr);\n\t}\n\n\t/**\n\t * Compute rewards for a reachability reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardReach(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b;\n\t\tStateValues rewards = null;\n\n\t\tif (fairness && !min) {\n\t\t\t// Rmax with fairness not supported; Rmin computation is unaffected\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"Maximum reward computation currently not supported under fairness.\");\n\t\t}\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// No time bounds allowed\n\t\tif (expr.hasBounds()) {\n\t\t\tthrow new PrismNotSupportedException(\"R operator cannot contain a bounded F operator: \" + expr);\n\t\t}\n\t\t\n\t\t// model check operand first, statesOfInterest = all\n\t\tb = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb = \" + JDD.GetNumMintermsString(b,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\t// compute rewards\n\t\ttry {\n\t\t\trewards = computeReachRewards(trans, transActions, trans01, stateRewards, transRewards, b, min);\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(b);\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute rewards for a co-safe LTL reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardCoSafeLTL(Expression expr, JDDNode stateRewards, JDDNode transRewards, boolean min, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tLTLModelChecker mcLtl;\n\t\tStateValues rewardsProduct = null, rewards = null;\n\t\tVector<JDDNode> labelDDs = new Vector<JDDNode>();\n\t\tDA<BitSet, AcceptanceReach> da;\n\t\tLTLProduct<NondetModel> modelProduct;\n\t\tNondetModelChecker mcProduct;\n\t\tlong l;\n\n\t\tif (fairness && !min) {\n\t\t\t// Rmax with fairness not supported; Rmin computation is unaffected\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismNotSupportedException(\"Maximum reward computation currently not supported under fairness.\");\n\t\t}\n\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tif (model.getModelType().continuousTime()) {\n\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\tthrow new PrismException(\"DA construction for time-bounded operators not supported for \" + model.getModelType()+\".\");\n\t\t\t}\n\n\t\t\tif (expr.isSimplePathFormula()) {\n\t\t\t\t// Convert simple path formula to canonical form,\n\t\t\t\t// DA is then generated by LTL2RabinLibrary.\n\t\t\t\t//\n\t\t\t\t// The conversion to canonical form has to happen here, because once\n\t\t\t\t// checkMaximalStateFormulas has been called, the formula should not be modified\n\t\t\t\t// anymore, as converters may expect that the generated labels for maximal state\n\t\t\t\t// formulas only appear positively\n\t\t\t\texpr = Expression.convertSimplePathFormulaToCanonicalForm(expr);\n\t\t\t} else {\n\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\tthrow new PrismException(\"Time-bounded operators not supported in LTL: \" + expr);\n\t\t\t}\n\t\t}\n\n\t\t// Can't do \"dfa\" properties yet\n\t\tif (expr instanceof ExpressionFunc && ((ExpressionFunc) expr).getName().equals(\"dfa\")) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Model checking for \\\"dfa\\\" specifications not supported yet\");\n\t\t}\n\n\t\t// For LTL model checking routines\n\t\tmcLtl = new LTLModelChecker(prism);\n\n\t\t// Model check maximal state formulas and construct DFA, with the special\n\t\t// handling needed for cosafety reward translation\n\t\tda = mcLtl.constructDFAForCosafetyRewardLTL(this, model, expr, labelDDs);\n\n\t\t// If required, export DA\n\t\tif (settings.getExportPropAut()) {\n\t\t\tmainLog.println(\"Exporting DA to file \\\"\" + settings.getExportPropAutFilename() + \"\\\"...\");\n\t\t\tPrintStream out = PrismUtils.newPrintStream(settings.getExportPropAutFilename());\n\t\t\tda.print(out, settings.getExportPropAutType());\n\t\t\tout.close();\n\t\t\t//da.printDot(new java.io.PrintStream(\"da.dot\"));\n\t\t}\n\n\t\t// Build product of MDP and automaton\n\t\tmodelProduct = mcLtl.constructProductMDP(model, da, labelDDs, statesOfInterest);\n\t\t// Output product, if required\n\t\tif (prism.getExportProductTrans()) {\n\t\t\ttry {\n\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions();\n\t\t\t\texportOptions.setModelPrecision(getSettings().getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION));\n\t\t\t\tmainLog.println(\"\\nExporting product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"...\");\n\t\t\t\tmodelProduct.getProductModel().exportToFile(new File(prism.getExportProductTransFilename()), exportOptions);\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.printWarning(\"Could not export product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\t\tif (prism.getExportProductStates()) {\n\t\t\tmainLog.println(\"\\nExporting product state space to file \\\"\" + prism.getExportProductStatesFilename() + \"\\\"...\");\n\t\t\tPrismFileLog out = new PrismFileLog(prism.getExportProductStatesFilename());\n\t\t\tmodelProduct.getProductModel().exportStates(Prism.EXPORT_PLAIN, out);\n\t\t\tout.close();\n\t\t}\n\n\t\t// Adapt reward info to product model\n\t\tJDDNode stateRewardsProduct = JDD.Apply(JDD.TIMES, stateRewards.copy(), modelProduct.getProductModel().getReach().copy());\n\t\tJDDNode transRewardsProduct = JDD.Apply(JDD.TIMES, transRewards.copy(), modelProduct.getProductModel().getTrans01().copy());\n\t\t\n\t\t// Find accepting states + compute reachability rewards\n\t\tAcceptanceReachDD acceptance = (AcceptanceReachDD) modelProduct.getProductAcceptance();\n\t\t// acc is already restricted to the product model's reachable states\n\t\tJDDNode acc = acceptance.getGoalStates();\n\n\t\tmainLog.println(\"\\nComputing reachability rewards...\");\n\t\tmcProduct = createNewModelChecker(prism, modelProduct.getProductModel(), null);\n\t\trewardsProduct = mcProduct.computeReachRewards(modelProduct.getProductModel().getTrans(),\n\t\t                                               modelProduct.getProductModel().getTransActions(),\n\t\t                                               modelProduct.getProductModel().getTrans01(),\n\t\t                                               stateRewardsProduct,\n\t\t                                               transRewardsProduct,\n\t\t                                               acc,\n\t\t                                               min);\n\n\t\t// Convert reward vector to original model\n\t\trewards = modelProduct.projectToOriginalModel(rewardsProduct);\n\n\t\t// Deref, clean up\n\t\tJDD.Deref(stateRewardsProduct);\n\t\tJDD.Deref(transRewardsProduct);\n\t\tmodelProduct.clear();\n\t\tJDD.Deref(acc);\n\n\t\treturn rewards;\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// probability computation methods\n\t// -----------------------------------------------------------------------------------\n\n\t// compute probabilities for next\n\n\tprotected StateValues computeNextProbs(JDDNode tr, JDDNode b, boolean min)\n\t{\n\t\tJDDNode tmp;\n\t\tStateValues probs = null;\n\n\t\t// matrix multiply: trans * b\n\t\tJDD.Ref(b);\n\t\ttmp = JDD.PermuteVariables(b, allDDRowVars, allDDColVars);\n\t\tJDD.Ref(tr);\n\t\ttmp = JDD.MatrixMultiply(tr, tmp, allDDColVars, JDD.BOULDER);\n\t\t// (then min or max)\n\t\tif (min) {\n\t\t\t// min\n\t\t\tJDD.Ref(nondetMask);\n\t\t\ttmp = JDD.Apply(JDD.MAX, tmp, nondetMask);\n\t\t\ttmp = JDD.MinAbstract(tmp, allDDNondetVars);\n\t\t} else {\n\t\t\t// max\n\t\t\ttmp = JDD.MaxAbstract(tmp, allDDNondetVars);\n\t\t}\n\t\tprobs = new StateValuesMTBDD(tmp, model);\n\t\tprobs.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Given a value vector x, compute the probability:\n\t *   v(s) = min/max sched [ Sum_s' P_sched(s,s')*x(s') ]  for s labeled with a,\n\t *   v(s) = 0   for s not labeled with a.\n\t *\n\t * Clears the StateValues object x.\n\t *\n\t * @param tr the transition matrix\n\t * @param a the set of states labeled with a\n\t * @param x the value vector\n\t * @param min compute min instead of max\n\t */\n\tprotected StateValues computeRestrictedNext(JDDNode tr, JDDNode a, StateValues x, boolean min)\n\t{\n\t\tJDDNode tmp;\n\t\tStateValuesMTBDD probs = null;\n\n\t\t// ensure that values are given in MTBDD format\n\t\tStateValuesMTBDD ddX = x.convertToStateValuesMTBDD();\n\n\t\ttmp = ddX.getJDDNode();\n\t\tJDD.Ref(tmp);\n\t\ttmp = JDD.PermuteVariables(tmp, allDDRowVars, allDDColVars);\n\t\tJDD.Ref(tr);\n\t\ttmp = JDD.MatrixMultiply(tr, tmp, allDDColVars, JDD.BOULDER);\n\t\t// (then min or max)\n\t\tif (min) {\n\t\t\t// min\n\t\t\tJDD.Ref(nondetMask);\n\t\t\ttmp = JDD.Apply(JDD.MAX, tmp, nondetMask);\n\t\t\ttmp = JDD.MinAbstract(tmp, allDDNondetVars);\n\t\t} else {\n\t\t\t// max\n\t\t\ttmp = JDD.MaxAbstract(tmp, allDDNondetVars);\n\t\t}\n\n\t\t// label is 0/1 BDD, MIN sets all values to 0 for states not in a\n\t\tJDD.Ref(a);\n\t\ttmp = JDD.Apply(JDD.MIN, tmp, a);\n\n\t\tddX.clear();\n\t\tprobs = new StateValuesMTBDD(tmp, model);\n\t\tprobs.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\treturn probs;\n\t}\n\n\t// compute probabilities for bounded until\n\n\tprotected StateValues computeBoundedUntilProbs(JDDNode tr, JDDNode tr01, JDDNode b1, JDDNode b2, int time, boolean min) throws PrismException\n\t{\n\t\tJDDNode yes, no, maybe;\n\t\tJDDNode probsMTBDD;\n\t\tDoubleVector probsDV;\n\t\tStateValues probs = null;\n\n\t\t// compute yes/no/maybe states\n\t\tif (b2.equals(JDD.ZERO)) {\n\t\t\tyes = JDD.Constant(0);\n\t\t\tJDD.Ref(reach);\n\t\t\tno = reach;\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else if (b1.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(b2);\n\t\t\tyes = b2;\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(b2);\n\t\t\tno = JDD.And(reach, JDD.Not(b2));\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else {\n\t\t\t// yes\n\t\t\tJDD.Ref(b2);\n\t\t\tyes = b2;\n\t\t\t// no\n\t\t\tif (yes.equals(reach)) {\n\t\t\t\tno = JDD.Constant(0);\n\t\t\t} else if (precomp && prob0) {\n\t\t\t\tif (min) {\n\t\t\t\t\t// \"min prob = 0\" equates to \"there exists a prob 0\"\n\t\t\t\t\tno = PrismMTBDD.Prob0E(tr01, reach, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, b1, yes);\n\t\t\t\t} else {\n\t\t\t\t\t// \"max prob = 0\" equates to \"all probs 0\"\n\t\t\t\t\tno = PrismMTBDD.Prob0A(tr01, reach, allDDRowVars, allDDColVars, allDDNondetVars, b1, yes);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tJDD.Ref(b1);\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\tno = JDD.And(reach, JDD.Not(JDD.Or(b1, b2)));\n\t\t\t}\n\t\t\t// maybe\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(yes);\n\t\t\tJDD.Ref(no);\n\t\t\tmaybe = JDD.And(reach, JDD.Not(JDD.Or(yes, no)));\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\nyes = \" + JDD.GetNumMintermsString(yes, allDDRowVars.n()));\n\t\tmainLog.print(\", no = \" + JDD.GetNumMintermsString(no, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\t// if maybe is empty, we have the probabilities already\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(yes);\n\t\t\tprobs = new StateValuesMTBDD(yes, model);\n\t\t\tprobs.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise explicitly compute the remaining probabilities\n\t\telse {\n\t\t\t// compute probabilities\n\t\t\tmainLog.println(\"\\nComputing probabilities...\");\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\tprobsMTBDD = PrismMTBDD.NondetBoundedUntil(tr, odd, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, time, min);\n\t\t\t\t\tprobs = new StateValuesMTBDD(probsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\tprobsDV = PrismSparse.NondetBoundedUntil(tr, odd, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, time, min);\n\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tprobsDV = PrismHybrid.NondetBoundedUntil(tr, odd, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, time, min);\n\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t\t// Set accuracy info\n\t\t\t\tprobs.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(yes);\n\t\t\t\tJDD.Deref(no);\n\t\t\t\tJDD.Deref(maybe);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(yes);\n\t\tJDD.Deref(no);\n\t\tJDD.Deref(maybe);\n\n\t\treturn probs;\n\t}\n\n\t// compute probabilities for until (for qualitative properties)\n\n\t// note: this function doesn't need to know anything about fairness\n\t// it is just told whether to compute min or max probabilities\n\n\tprotected StateValues computeUntilProbsQual(JDDNode tr01, JDDNode b1, JDDNode b2, boolean min)\n\t{\n\t\tJDDNode yes = null, no = null, maybe;\n\t\tStateValues probs = null;\n\n\t\t// note: we know precomputation is enabled else this function wouldn't\n\t\t// have been called\n\n\t\t// compute yes/no/maybe states\n\t\tif (b2.equals(JDD.ZERO)) {\n\t\t\tyes = JDD.Constant(0);\n\t\t\tJDD.Ref(reach);\n\t\t\tno = reach;\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else if (b1.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(b2);\n\t\t\tyes = b2;\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(b2);\n\t\t\tno = JDD.And(reach, JDD.Not(b2));\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else {\n\t\t\t// min\n\t\t\tif (min) {\n\t\t\t\t// no: \"min prob = 0\" equates to \"there exists an adversary prob equals 0\"\n\t\t\t\tno = PrismMTBDD.Prob0E(tr01, reach, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, b1, b2);\n\t\t\t\t// yes: \"min prob = 1\" equates to \"for all adversaries prob equals 1\"\n\t\t\t\tyes = PrismMTBDD.Prob1A(tr01, reach, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, no, b2);\n\t\t\t}\n\t\t\t// max\n\t\t\telse {\n\t\t\t\t// no: \"max prob = 0\" equates to \"for all adversaries prob equals 0\"\n\t\t\t\tno = PrismMTBDD.Prob0A(tr01, reach, allDDRowVars, allDDColVars, allDDNondetVars, b1, b2);\n\t\t\t\t// yes: \"max prob = 1\" equates to \"there exists an adversary prob equals 1\"\n\t\t\t\tyes = PrismMTBDD.Prob1E(tr01, reach, allDDRowVars, allDDColVars, allDDNondetVars, b1, b2, no);\n\t\t\t}\n\t\t\t// maybe\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(yes);\n\t\t\tJDD.Ref(no);\n\t\t\tmaybe = JDD.And(reach, JDD.Not(JDD.Or(yes, no)));\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\nyes = \" + JDD.GetNumMintermsString(yes, allDDRowVars.n()));\n\t\tmainLog.print(\", no = \" + JDD.GetNumMintermsString(no, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\t// if maybe is empty, we have the answer already...\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(yes);\n\t\t\tprobs = new StateValuesMTBDD(yes, model);\n\t\t\tprobs.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise we set the probabilities for maybe states to be 0.5\n\t\t// (actual probabilities for these states are unknown but definitely >0\n\t\t// and <1)\n\t\t// (this is safe because the results of this function will only be used\n\t\t// to compare against 0/1 bounds)\n\t\t// (this is not entirely elegant but is simpler and less error prone\n\t\t// than\n\t\t// trying to work out whether to use 0/1 for all case of min/max,\n\t\t// fairness, future/global, etc.)\n\t\telse {\n\t\t\tJDD.Ref(yes);\n\t\t\tJDD.Ref(maybe);\n\t\t\tprobs = new StateValuesMTBDD(JDD.Apply(JDD.PLUS, yes, JDD.Apply(JDD.TIMES, maybe, JDD.Constant(0.5))), model);\n\t\t\t// No accuracy info, but should end up as a Boolean, not numerical, value anyway \n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(yes);\n\t\tJDD.Deref(no);\n\t\tJDD.Deref(maybe);\n\n\t\treturn probs;\n\t}\n\n\t// compute probabilities for until (general case)\n\n\t// note: this function doesn't need to know anything about fairness\n\t// it is just told whether to compute min or max probabilities\n\n\tprotected StateValues computeUntilProbs(JDDNode tr, JDDNode tra, JDDNode tr01, JDDNode b1, JDDNode b2, boolean min) throws PrismException\n\t{\n\t\tJDDNode yes, no, maybe;\n\t\tJDDNode probsMTBDD;\n\t\tDoubleVector probsDV;\n\t\tStateValues probs = null;\n\n\t\tboolean doPmaxQuotient = getSettings().getBoolean(PrismSettings.PRISM_PMAX_QUOTIENT);\n\n\t\tif (doIntervalIteration) {\n\t\t\tif (!(precomp && prob0 && prob1)) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Precomputations (Prob0 & Prob1) must be enabled for interval iteration\");\n\t\t\t}\n\n\t\t\tif (!min) {\n\t\t\t\t// for Pmax and interval iteration, pmaxQuotient is required\n\t\t\t\tdoPmaxQuotient = true;\n\t\t\t}\n\t\t}\n\n\t\tif (doPmaxQuotient && min) {\n\t\t\t// don't do pmaxQuotient for min\n\t\t\tdoPmaxQuotient = false;\n\t\t}\n\n\t\tif (doPmaxQuotient) {\n\t\t\tif (!(precomp && prob0 && prob1)) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Precomputations (Prob0 & Prob1) must be enabled for -pmaxquotient setting\");\n\t\t\t}\n\t\t}\n\n\t\t// If required, export info about target states \n\t\tif (prism.getExportTarget()) {\n\t\t\tJDDNode labels[] = { model.getStart(), b2 };\n\t\t\tString labelNames[] = { \"init\", \"target\" };\n\t\t\ttry {\n\t\t\t\tmainLog.println(\"\\nExporting target states info to file \\\"\" + prism.getExportTargetFilename() + \"\\\"...\");\n\t\t\t\tPrismMTBDD.ExportLabels(labels, labelNames, \"l\", model.getAllDDRowVars(), model.getODD(), Prism.EXPORT_PLAIN, prism.getExportTargetFilename());\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.printWarning(\"Could not export target to file \\\"\" + prism.getExportTargetFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t// compute yes/no/maybe states\n\t\tif (b2.equals(JDD.ZERO)) {\n\t\t\tyes = JDD.Constant(0);\n\t\t\tJDD.Ref(reach);\n\t\t\tno = reach;\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else if (b1.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(b2);\n\t\t\tyes = b2;\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(b2);\n\t\t\tno = JDD.And(reach, JDD.Not(b2));\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else {\n\t\t\t// no\n\t\t\t// if precomputation enabled\n\t\t\t// (nb: prob1 needs prob0)\n\t\t\tif (precomp && (prob0 || prob1)) {\n\t\t\t\t// min\n\t\t\t\tif (min) {\n\t\t\t\t\t// no: \"min prob = 0\" equates to \"there exists an adversary prob equals 0\"\n\t\t\t\t\tno = PrismMTBDD.Prob0E(tr01, reach, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, b1, b2);\n\t\t\t\t}\n\t\t\t\t// max\n\t\t\t\telse {\n\t\t\t\t\t// no: \"max prob = 0\" equates to \"for all adversaries prob equals 0\"\n\t\t\t\t\tno = PrismMTBDD.Prob0A(tr01, reach, allDDRowVars, allDDColVars, allDDNondetVars, b1, b2);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// if precomputation not enabled\n\t\t\telse {\n\t\t\t\t// no\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tJDD.Ref(b1);\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\tno = JDD.And(reach, JDD.Not(JDD.Or(b1, b2)));\n\t\t\t}\n\t\t\t// yes\n\t\t\t// if precomputation enabled\n\t\t\tif (precomp && prob1) {\n\t\t\t\t// min\n\t\t\t\tif (min) {\n\t\t\t\t\t// yes: \"min prob = 1\" equates to \"for all adversaries prob equals 1\"\n\t\t\t\t\tyes = PrismMTBDD.Prob1A(tr01, reach, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, no, b2);\n\t\t\t\t}\n\t\t\t\t// max\n\t\t\t\telse {\n\t\t\t\t\t// yes: \"max prob = 1\" equates to \"there exists an adversary prob equals 1\"\n\t\t\t\t\tyes = PrismMTBDD.Prob1E(tr01, reach, allDDRowVars, allDDColVars, allDDNondetVars, b1, b2, no);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// if precomputation not enabled\n\t\t\telse {\n\t\t\t\t// yes\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\tyes = b2;\n\t\t\t}\n\t\t\t// maybe\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(yes);\n\t\t\tJDD.Ref(no);\n\t\t\tmaybe = JDD.And(reach, JDD.Not(JDD.Or(yes, no)));\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\nyes = \" + JDD.GetNumMintermsString(yes, allDDRowVars.n()));\n\t\tmainLog.print(\", no = \" + JDD.GetNumMintermsString(no, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\t// if maybe is empty, we have the answer already...\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(yes);\n\t\t\tprobs = new StateValuesMTBDD(yes, model);\n\t\t\tprobs.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise we compute the actual probabilities\n\t\telse {\n\t\t\t// compute probabilities\n\t\t\tmainLog.println(\"\\nComputing remaining probabilities...\");\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tMDPQuotient transform = null;\n\t\t\t\tNondetModel transformed = null;\n\t\t\t\tJDDNode yesInQuotient = null;\n\t\t\t\tJDDNode maybeInQuotient = null;\n\n\t\t\t\tif (doPmaxQuotient) {\n\t\t\t\t\tif (!tr.equals(model.getTrans()) ||\n\t\t\t\t\t    !tra.equals(model.getTransActions()) ||\n\t\t\t\t\t    !tr01.equals(model.getTrans01())) {\n\t\t\t\t\t\tthrow new PrismException(\"Can currently not compute MEC quotient for changed functions\");\n\t\t\t\t\t}\n\n\t\t\t\t\tmainLog.println(\"\\nBuilding quotient MDP, collapsing maximal end components as well as yes and no states...\");\n\t\t\t\t\tStopWatch ecWatch = new StopWatch(mainLog);\n\t\t\t\t\tecWatch.start(\"computing maximal end components\");\n\t\t\t\t\tECComputer ec = ECComputer.createECComputer(this, model);\n\t\t\t\t\t// find MECs in the maybe states\n\t\t\t\t\tec.computeMECStates(maybe);\n\t\t\t\t\tecWatch.stop(\"found \" + ec.getMECStates().size() + \" MECs\");\n\n\t\t\t\t\tList<JDDNode> ecs = new ArrayList<JDDNode>(ec.getMECStates());\n\n\t\t\t\t\tecs.add(yes.copy());\n\t\t\t\t\tecs.add(no.copy());\n\n\t\t\t\t\tStopWatch watchTransform = new StopWatch(mainLog);\n\t\t\t\t\twatchTransform.start(\"building MEC quotient\");\n\t\t\t\t\ttransform = MDPQuotient.transform(this, model, ecs, model.getReach().copy());\n\t\t\t\t\twatchTransform.stop();\n\n\t\t\t\t\tif (false) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions(ModelExportFormat.DOT);\n\t\t\t\t\t\t\texportOptions.setModelPrecision(getSettings().getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION));\n\t\t\t\t\t\t\tmodel.exportToFile(new File(\"model.dot\"), exportOptions);\n\t\t\t\t\t\t\ttransform.getTransformedModel().exportToFile(new File(\"quotient.dot\"), exportOptions);\n\t\t\t\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\ttransformed = transform.getTransformedModel();\n\n\t\t\t\t\tmainLog.println(\"\\nQuotient MDP:\");\n\t\t\t\t\ttransformed.printTransInfo(mainLog);\n\n\t\t\t\t\tyesInQuotient = transform.mapStateSetToQuotient(yes.copy());\n\t\t\t\t\tmaybeInQuotient = transform.mapStateSetToQuotient(maybe.copy());\n\t\t\t\t}\n\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\tif (transform != null) {\n\t\t\t\t\t\t\tprobsMTBDD = PrismMTBDD.NondetUntilInterval(transformed.getTrans(),\n\t\t\t\t\t\t\t                                            transformed.getODD(),\n\t\t\t\t\t\t\t                                            transformed.getNondetMask(),\n\t\t\t\t\t\t\t                                            transformed.getAllDDRowVars(),\n\t\t\t\t\t\t\t                                            transformed.getAllDDColVars(),\n\t\t\t\t\t\t\t                                            transformed.getAllDDNondetVars(),\n\t\t\t\t\t\t\t                                            yesInQuotient,\n\t\t\t\t\t\t\t                                            maybeInQuotient,\n\t\t\t\t\t\t\t                                            min,\n\t\t\t\t\t\t\t                                            prism.getIntervalIterationFlags());\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tprobsMTBDD = PrismMTBDD.NondetUntilInterval(tr, odd, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, min, prism.getIntervalIterationFlags());\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (transform != null) {\n\t\t\t\t\t\t\tprobsMTBDD = PrismMTBDD.NondetUntil(transformed.getTrans(),\n\t\t\t\t\t\t\t                                    transformed.getODD(),\n\t\t\t\t\t\t\t                                    transformed.getNondetMask(),\n\t\t\t\t\t\t\t                                    transformed.getAllDDRowVars(),\n\t\t\t\t\t\t\t                                    transformed.getAllDDColVars(),\n\t\t\t\t\t\t\t                                    transformed.getAllDDNondetVars(),\n\t\t\t\t\t\t\t                                    yesInQuotient,\n\t\t\t\t\t\t\t                                    maybeInQuotient,\n\t\t\t\t\t\t\t                                    min);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tprobsMTBDD = PrismMTBDD.NondetUntil(tr, odd, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, min);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tprobs = new StateValuesMTBDD(probsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\tIntegerVector strat = null;\n\t\t\t\t\tif (genStrat) {\n\t\t\t\t\t\t// prepare strategy storage for the sparse engine computation\n\t\t\t\t\t\tJDDNode ddStrat = JDD.ITE(yes.copy(), JDD.Constant(-2), JDD.Constant(-1));\n\t\t\t\t\t\t// restrict to the reachable state space of the model (required for conversion to integer array)\n\t\t\t\t\t\tddStrat = JDD.Times(ddStrat, reach.copy());\n\t\t\t\t\t\tstrat = new IntegerVector(ddStrat, allDDRowVars, odd);\n\t\t\t\t\t\tJDD.Deref(ddStrat);\n\t\t\t\t\t}\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\tif (transform != null) {\n\t\t\t\t\t\t\t// strategy generation with the quotient not yet supported\n\t\t\t\t\t\t\tif (strat != null) {\n\t\t\t\t\t\t\t\tstrat.clear();\n\t\t\t\t\t\t\t\tstrat = null;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tprobsDV = PrismSparse.NondetUntilInterval(transformed.getTrans(),\n\t\t\t\t\t\t\t                                          transformed.getTransActions(),\n\t\t\t\t\t\t\t                                          transformed.getSynchs(),\n\t\t\t\t\t\t\t                                          transformed.getODD(),\n\t\t\t\t\t\t\t                                          transformed.getAllDDRowVars(),\n\t\t\t\t\t\t\t                                          transformed.getAllDDColVars(),\n\t\t\t\t\t\t\t                                          transformed.getAllDDNondetVars(),\n\t\t\t\t\t\t\t                                          yesInQuotient,\n\t\t\t\t\t\t\t                                          maybeInQuotient,\n\t\t\t\t\t\t\t                                          min,\n\t\t\t\t\t\t\t                                          strat,\n\t\t\t\t\t\t\t                                          prism.getIntervalIterationFlags());\n\t\t\t\t\t\t\tprobs = new StateValuesDV(probsDV, transformed);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tprobsDV = PrismSparse.NondetUntilInterval(tr, tra, model.getSynchs(), odd, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, min, strat, prism.getIntervalIterationFlags());\n\t\t\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (transform != null) {\n\t\t\t\t\t\t\t// strategy generation with the quotient not yet supported\n\t\t\t\t\t\t\tif (strat != null) {\n\t\t\t\t\t\t\t\tstrat.clear();\n\t\t\t\t\t\t\t\tstrat = null;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\tprobsDV = PrismSparse.NondetUntil(transformed.getTrans(),\n\t\t\t\t\t\t\t                                  transformed.getTransActions(),\n\t\t\t\t\t\t\t                                  transformed.getSynchs(),\n\t\t\t\t\t\t\t                                  transformed.getODD(),\n\t\t\t\t\t\t\t                                  transformed.getAllDDRowVars(),\n\t\t\t\t\t\t\t                                  transformed.getAllDDColVars(),\n\t\t\t\t\t\t\t                                  transformed.getAllDDNondetVars(),\n\t\t\t\t\t\t\t                                  yesInQuotient,\n\t\t\t\t\t\t\t                                  maybeInQuotient,\n\t\t\t\t\t\t\t                                  min,\n\t\t\t\t\t\t\t                                  strat);\n\t\t\t\t\t\t\tprobs = new StateValuesDV(probsDV, transformed);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tprobsDV = PrismSparse.NondetUntil(tr, tra, model.getSynchs(), odd, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, min, strat);\n\t\t\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (genStrat && strat != null && result != null) {\n\t\t\t\t\t\tresult.setStrategy(new MDStrategyIV(model, strat));\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\tif (transform != null) {\n\t\t\t\t\t\t\tprobsDV = PrismHybrid.NondetUntilInterval(transformed.getTrans(),\n\t\t\t\t\t\t\t                                          transformed.getODD(),\n\t\t\t\t\t\t\t                                          transformed.getAllDDRowVars(),\n\t\t\t\t\t\t\t                                          transformed.getAllDDColVars(),\n\t\t\t\t\t\t\t                                          transformed.getAllDDNondetVars(),\n\t\t\t\t\t\t\t                                          yesInQuotient,\n\t\t\t\t\t\t\t                                          maybeInQuotient,\n\t\t\t\t\t\t\t                                          min,\n\t\t\t\t\t\t\t                                          prism.getIntervalIterationFlags());\n\t\t\t\t\t\t\tprobs = new StateValuesDV(probsDV, transformed);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tprobsDV = PrismHybrid.NondetUntilInterval(tr, odd, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, min, prism.getIntervalIterationFlags());\n\t\t\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tif (transform != null) {\n\t\t\t\t\t\t\tprobsDV = PrismHybrid.NondetUntil(transformed.getTrans(),\n\t\t\t\t\t\t\t                                  transformed.getODD(),\n\t\t\t\t\t\t\t                                  transformed.getAllDDRowVars(),\n\t\t\t\t\t\t\t                                  transformed.getAllDDColVars(),\n\t\t\t\t\t\t\t                                  transformed.getAllDDNondetVars(),\n\t\t\t\t\t\t\t                                  yesInQuotient,\n\t\t\t\t\t\t\t                                  maybeInQuotient,\n\t\t\t\t\t\t\t                                  min);\n\t\t\t\t\t\t\tprobs = new StateValuesDV(probsDV, transformed);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tprobsDV = PrismHybrid.NondetUntil(tr, odd, allDDRowVars, allDDColVars, allDDNondetVars, yes, maybe, min);\n\t\t\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t\t// Set accuracy info\n\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\tprobs.setAccuracy(AccuracyFactory.guaranteedNumericalIterative(PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t\t} else {\n\t\t\t\t\tprobs.setAccuracy(AccuracyFactory.valueIteration(PrismNative.getTermCritParam(), PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t\t}\n\n\t\t\t\tif (transform != null) {\n\t\t\t\t\t// we have to project back to the original\n\t\t\t\t\tprobs = transform.projectToOriginalModel(probs);\n\t\t\t\t\ttransform.clear();\n\t\t\t\t\tJDD.Deref(yesInQuotient, maybeInQuotient);\n\t\t\t\t}\n\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(yes);\n\t\t\t\tJDD.Deref(no);\n\t\t\t\tJDD.Deref(maybe);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(yes);\n\t\tJDD.Deref(no);\n\t\tJDD.Deref(maybe);\n\n\t\treturn probs;\n\t}\n\n\t// compute cumulative rewards\n\n\tprotected StateValues computeCumulRewards(JDDNode tr, JDDNode sr, JDDNode trr, int time, boolean min) throws PrismException\n\t{\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\t\t// Local copy of setting\n\t\tint engine = this.engine;\n\n\t\t// compute rewards\n\t\tmainLog.println(\"\\nComputing rewards...\");\n\t\t// switch engine, if necessary\n\t\tif (engine == Prism.HYBRID) {\n\t\t\tmainLog.println(\"Switching engine since hybrid engine does yet support this computation...\");\n\t\t\tengine = Prism.SPARSE;\n\t\t}\n\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\ttry {\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\tthrow new PrismNotSupportedException(\"MTBDD engine does not yet support this type of property (use the sparse engine instead)\");\n\t\t\tcase Prism.SPARSE:\n\t\t\t\trewardsDV = PrismSparse.NondetCumulReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, allDDNondetVars, time, min);\n\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.HYBRID:\n\t\t\t\tthrow new PrismNotSupportedException(\"Hybrid engine does not yet support this type of property (use the sparse engine instead)\");\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t}\n\t\t\t// Set accuracy info\n\t\t\trewards.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\t} catch (PrismException e) {\n\t\t\tthrow e;\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t// compute total rewards\n\n\tprotected StateValues computeTotalRewards(JDDNode tr, JDDNode tr01, JDDNode tra, JDDNode sr, JDDNode trr, boolean min) throws PrismException\n\t{\n\t\tif (min) {\n\t\t\tthrow new PrismNotSupportedException(\"Expected minimum total reward (C) is not yet supported for MDPs.\");\n\t\t} else {\n\t\t\t// max. We don't know if there are positive ECs, so we can't skip precomputation\n\t\t\treturn computeTotalRewardsMax(tr, tr01, tra, sr, trr, false);\n\t\t}\n\t}\n\n\tprotected StateValues computeTotalRewardsMax(JDDNode tr, JDDNode tr01, JDDNode tra, JDDNode sr, JDDNode trr, boolean noPositiveECs) throws PrismException\n\t{\n\t\tJDDNode inf, maybe;\n\t\tJDDNode rewardsMTBDD;\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\t\t// Local copy of setting\n\t\tint engine = this.engine;\n\n\t\t// For Rmax[ C ] computation, fairness does not affect the result\n\n\t\tif (doIntervalIteration) {\n\t\t\tthrow new PrismNotSupportedException(\"Interval iteration for total rewards is currently not supported\");\n\t\t}\n\n\t\t// Start expected total reward\n\t\tmainLog.println(\"\\nStarting total expected reward (max)...\");\n\n\t\tlong timer = System.currentTimeMillis();\n\n\t\tif (noPositiveECs) {\n\t\t\t// no inf states\n\t\t\tinf = JDD.Constant(0);\n\t\t\tmaybe = reach.copy();\n\t\t} else {\n\t\t\tmainLog.println(\"Precomputation: Find positive end components...\");\n\n\t\t\tlong timerPre = System.currentTimeMillis();\n\n\t\t\tJDDNode posRewStates = JDD.GreaterThan(sr.copy(), 0);\n\t\t\tJDDNode posRewTrans = JDD.GreaterThan(trr.copy(), 0);\n\n\t\t\tECComputer ecComp = new ECComputerDefault(prism, reach, trans, trans01,\n\t\t\t                                          model.getAllDDRowVars(),\n\t\t\t                                          model.getAllDDColVars(),\n\t\t\t                                          model.getAllDDNondetVars());\n\t\t\tecComp.computeMECStates();\n\n\t\t\tJDDNode positiveECs = JDD.Constant(0);\n\n\t\t\tfor (JDDNode ec : ecComp.getMECStates()) {\n\t\t\t\tboolean positive = false;\n\t\t\t\tif (JDD.AreIntersecting(ec, posRewStates)) {\n\t\t\t\t\tpositive = true;\n\t\t\t\t} else {\n\t\t\t\t\t// check for positive transition rewards\n\t\t\t\t\tJDDNode ecTrans = ecComp.getStableTransitions(ec.copy());\n\t\t\t\t\tif (JDD.AreIntersecting(ecTrans, posRewTrans)) {\n\t\t\t\t\t\tpositive = true;\n\t\t\t\t\t}\n\t\t\t\t\tJDD.Deref(ecTrans);\n\t\t\t\t}\n\n\t\t\t\tif (positive) {\n\t\t\t\t\tpositiveECs = JDD.Or(positiveECs, ec.copy());\n\t\t\t\t}\n\t\t\t\tJDD.Deref(ec);\n\t\t\t}\n\n\t\t\tJDD.Deref(posRewStates, posRewTrans);\n\n\t\t\t// inf = Pmax[ <> positiveECs ] > 0\n\t\t\t//     = ! (Pmax[ <> positiveECs ] = 0)\n\t\t\tmaybe = PrismMTBDD.Prob0A(trans01, reach,  // Pmax[ <> positiveECs ] = 0\n\t\t\t                          model.getAllDDRowVars(),\n\t\t\t                          model.getAllDDColVars(),\n\t\t\t                          model.getAllDDNondetVars(),\n\t\t\t                          reach,\n\t\t\t                          positiveECs);\n\t\t\tinf = JDD.And(reach.copy(), JDD.Not(maybe.copy()));  // !(Pmax[ <> positive ECs ] = 0) = Pmax[ <> positiveECs ] > 0\n\n\t\t\tJDD.Deref(positiveECs);\n\n\t\t\ttimerPre = System.currentTimeMillis() - timerPre;\n\t\t\tmainLog.print(\"Total expected reward precomputation took \" + timerPre / 1000.0 + \" seconds, \");\n\t\t\tmainLog.print(JDD.GetNumMintermsString(inf, allDDRowVars.n()) + \" infinite states, \");\n\t\t\tmainLog.println(JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \" states remaining.\");\n\t\t}\n\n\t\t// if maybe is empty, we have the rewards already\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\trewards = new StateValuesMTBDD(JDD.ITE(inf.copy(), JDD.PlusInfinity(), JDD.Constant(0)), model);\n\t\t\trewards.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t\tJDD.Deref(maybe, inf);\n\t\t}\n\t\t// otherwise we compute the actual rewards\n\t\telse {\n\t\t\t// compute the rewards\n\t\t\tmainLog.println(\"\\nComputing remaining total rewards...\");\n\t\t\t// switch engine, if necessary\n\t\t\tif (engine == Prism.HYBRID) {\n\t\t\t\tmainLog.println(\"Switching engine since hybrid engine does yet support this computation...\");\n\t\t\t\tengine = Prism.SPARSE;\n\t\t\t}\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\trewardsMTBDD = PrismMTBDD.NondetReachReward(tr, sr, trr, odd, nondetMask,\n\t\t\t\t\t                                            allDDRowVars, allDDColVars, allDDNondetVars,\n\t\t\t\t\t                                            JDD.ZERO,  // goal = empty set\n\t\t\t\t\t                                            inf,\n\t\t\t\t\t                                            maybe,\n\t\t\t\t\t                                            false);  // max\n\t\t\t\t\trewards = new StateValuesMTBDD(rewardsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\trewardsDV = PrismSparse.NondetReachReward(tr, tra, model.getSynchs(), sr, trr, odd,\n\t\t\t\t\t                                          allDDRowVars, allDDColVars, allDDNondetVars,\n\t\t\t\t\t                                          JDD.ZERO,  // goal = empty set\n\t\t\t\t\t                                          inf,\n\t\t\t\t\t                                          maybe,\n\t\t\t\t\t                                          false);  // max\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tthrow new PrismNotSupportedException(\"Hybrid engine does not yet support this type of property (use sparse or MTBDD engine instead)\");\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t\t// Set accuracy info\n\t\t\t\trewards.setAccuracy(AccuracyFactory.valueIteration(PrismNative.getTermCritParam(), PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t} finally {\n\t\t\t\tJDD.Deref(inf);\n\t\t\t\tJDD.Deref(maybe);\n\t\t\t}\n\t\t}\n\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"Time for total reward computation: \" + timer/1000.0 + \" seconds.\");\n\n\t\treturn rewards;\n\t}\n\n\t// compute rewards for inst reward\n\n\tprotected StateValues computeInstRewards(JDDNode tr, JDDNode sr, int time, boolean min) throws PrismException\n\t{\n\t\tJDDNode rewardsMTBDD;\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\t\t// Local copy of setting\n\t\tint engine = this.engine;\n\n\t\t// a trivial case: \"=0\"\n\t\tif (time == 0) {\n\t\t\tJDD.Ref(sr);\n\t\t\trewards = new StateValuesMTBDD(sr, model);\n\t\t\trewards.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise we compute the actual rewards\n\t\telse {\n\t\t\t// compute the rewards\n\t\t\tmainLog.println(\"\\nComputing rewards...\");\n\t\t\t// switch engine, if necessary\n\t\t\tif (engine == Prism.HYBRID) {\n\t\t\t\tmainLog.println(\"Switching engine since hybrid engine does yet support this computation...\");\n\t\t\t\tengine = Prism.SPARSE;\n\t\t\t}\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\trewardsMTBDD = PrismMTBDD.NondetInstReward(tr, sr, odd, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, time, min, start);\n\t\t\t\t\trewards = new StateValuesMTBDD(rewardsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\trewardsDV = PrismSparse.NondetInstReward(tr, sr, odd, allDDRowVars, allDDColVars, allDDNondetVars, time, min, start);\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tthrow new PrismException(\"Hybrid engine does not yet support this type of property (use sparse or MTBDD engine instead)\");\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t\t// Set accuracy info\n\t\t\t\trewards.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t// compute rewards for reach reward\n\n\tprotected StateValues computeReachRewards(JDDNode tr, JDDNode tra, JDDNode tr01, JDDNode sr, JDDNode trr, JDDNode b, boolean min) throws PrismException\n\t{\n\t\tJDDNode inf, maybe, prob1, no;\n\t\tJDDNode rewardsMTBDD;\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\t\t// Local copy of setting\n\t\tint engine = this.engine;\n\n\t\tList<JDDNode> zeroCostEndComponents = null;\n\n\t\tif (doIntervalIteration && min) {\n\t\t\tthrow new PrismNotSupportedException(\"Currently, Rmin is not supported with interval iteration and the symbolic engines\");\n\t\t}\n\n\t\t// If required, export info about target states\n\t\tif (prism.getExportTarget()) {\n\t\t\tJDDNode labels[] = { model.getStart(), b };\n\t\t\tString labelNames[] = { \"init\", \"target\" };\n\t\t\ttry {\n\t\t\t\tmainLog.println(\"\\nExporting target states info to file \\\"\" + prism.getExportTargetFilename() + \"\\\"...\");\n\t\t\t\tPrismMTBDD.ExportLabels(labels, labelNames, \"l\", model.getAllDDRowVars(), model.getODD(), Prism.EXPORT_PLAIN, prism.getExportTargetFilename());\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.printWarning(\"Could not export target to file \\\"\" + prism.getExportTargetFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\t// compute states which can't reach goal with probability 1\n\t\tif (b.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(reach);\n\t\t\tinf = reach;\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else if (b.equals(reach)) {\n\t\t\tinf = JDD.Constant(0);\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else {\n\t\t\tif (!min) {\n\t\t\t\t// compute states for which some adversaries don't reach goal with probability 1\n\t\t\t\t// note that prob1a (unlike prob1e) requires no/b2, not b1/b2\n\t\t\t\t// hence we have to call prob0e first\n\t\t\t\tno = PrismMTBDD.Prob0E(tr01, reach, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, reach, b);\n\t\t\t\tprob1 = PrismMTBDD.Prob1A(tr01, reach, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, no, b);\n\t\t\t\tJDD.Deref(no);\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tinf = JDD.And(reach, JDD.Not(prob1));\n\t\t\t} else {\n\n\t\t\t\tif (prism.getCheckZeroLoops()) {\n\t\t\t\t\t// find states transitions that have no cost\n\t\t\t\t\tJDD.Ref(sr);\n\t\t\t\t\tJDD.Ref(reach);\n\t\t\t\t\tJDDNode zeroReach = JDD.And(reach, JDD.Apply(JDD.EQUALS, sr, JDD.Constant(0)));\n\t\t\t\t\tJDD.Ref(b);\n\t\t\t\t\tzeroReach = JDD.And(zeroReach, JDD.Not(b));\n\t\t\t\t\tJDD.Ref(trr);\n\t\t\t\t\tJDDNode zeroTrr = JDD.Apply(JDD.EQUALS, trr, JDD.Constant(0));\n\t\t\t\t\tJDD.Ref(trans);\n\t\t\t\t\tJDD.Ref(zeroTrr);\n\t\t\t\t\tJDDNode zeroTrans = JDD.And(trans, zeroTrr);\n\t\t\t\t\tJDD.Ref(trans01);\n\t\t\t\t\tJDDNode zeroTrans01 = JDD.And(trans01, zeroTrr);\n\n\t\t\t\t\tECComputer ecComp = new ECComputerDefault(prism, zeroReach, zeroTrans, zeroTrans01, model.getAllDDRowVars(), model.getAllDDColVars(),\n\t\t\t\t\t\t\tmodel.getAllDDNondetVars());\n\t\t\t\t\tecComp.computeMECStates();\n\n\t\t\t\t\tzeroCostEndComponents = ecComp.getMECStates();\n\n\t\t\t\t\tJDD.Deref(zeroReach);\n\t\t\t\t\tJDD.Deref(zeroTrans);\n\t\t\t\t\tJDD.Deref(zeroTrans01);\n\t\t\t\t}\n\n\t\t\t\t// compute states for which all adversaries don't reach goal with probability 1\n\t\t\t\tno = PrismMTBDD.Prob0A(tr01, reach, allDDRowVars, allDDColVars, allDDNondetVars, reach, b);\n\t\t\t\tprob1 = PrismMTBDD.Prob1E(tr01, reach, allDDRowVars, allDDColVars, allDDNondetVars, reach, b, no);\n\t\t\t\tJDD.Deref(no);\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tinf = JDD.And(reach, JDD.Not(prob1));\n\t\t\t}\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(inf);\n\t\t\tJDD.Ref(b);\n\t\t\tmaybe = JDD.And(reach, JDD.Not(JDD.Or(inf, b)));\n\t\t}\n\n\t\tif (prism.getCheckZeroLoops()) {\n\t\t\t// need to deal with zero loops yet\n\t\t\tif (min && zeroCostEndComponents != null && zeroCostEndComponents.size() > 0) {\n\t\t\t\tmainLog.printWarning(\"PRISM detected your model contains \" + zeroCostEndComponents.size() + \" zero-reward \"\n\t\t\t\t\t\t+ ((zeroCostEndComponents.size() == 1) ? \"loop.\" : \"loops.\\n\") + \"Your minimum rewards may be too low...\");\n\t\t\t}\n\t\t} else if (min) {\n\t\t\tmainLog.printWarning(\"PRISM hasn't checked for zero-reward loops.\\n\" + \"Your minimum rewards may be too low...\");\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\ngoal = \" + JDD.GetNumMintermsString(b, allDDRowVars.n()));\n\t\tmainLog.print(\", inf = \" + JDD.GetNumMintermsString(inf, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\tJDDNode lower = null;\n\t\tJDDNode upper = null;\n\n\t\t// if maybe is empty, we have the rewards already\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(inf);\n\t\t\trewards = new StateValuesMTBDD(JDD.ITE(inf, JDD.PlusInfinity(), JDD.Constant(0)), model);\n\t\t\trewards.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise we compute the actual rewards\n\t\telse {\n\n\t\t\tif (doIntervalIteration) {\n\t\t\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\t\t\tdouble upperBound;\n\t\t\t\tif (iiOptions.hasManualUpperBound()) {\n\t\t\t\t\tupperBound = iiOptions.getManualUpperBound();\n\t\t\t\t\tgetLog().printWarning(\"Upper bound for interval iteration manually set to \" + upperBound);\n\t\t\t\t} else {\n\t\t\t\t\tupperBound = ProbModelChecker.computeReachRewardsUpperBound(this, model, tr, sr, trr, b, maybe);\n\t\t\t\t}\n\t\t\t\tupper = JDD.ITE(maybe.copy(), JDD.Constant(upperBound), JDD.Constant(0));\n\n\t\t\t\tdouble lowerBound;\n\t\t\t\tif (iiOptions.hasManualLowerBound()) {\n\t\t\t\t\tlowerBound = iiOptions.getManualLowerBound();\n\t\t\t\t\tgetLog().printWarning(\"Lower bound for interval iteration manually set to \" + lowerBound);\n\t\t\t\t} else {\n\t\t\t\t\tlowerBound = 0.0;\n\t\t\t\t}\n\t\t\t\tlower = JDD.ITE(maybe.copy(), JDD.Constant(lowerBound), JDD.Constant(0));\n\t\t\t}\n\n\t\t\t// compute the rewards\n\t\t\tmainLog.println(\"\\nComputing remaining rewards...\");\n\t\t\t// switch engine, if necessary\n\t\t\tif (engine == Prism.HYBRID) {\n\t\t\t\tmainLog.println(\"Switching engine since hybrid engine does yet support this computation...\");\n\t\t\t\tengine = Prism.SPARSE;\n\t\t\t}\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\trewardsMTBDD = PrismMTBDD.NondetReachRewardInterval(tr, sr, trr, odd, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, b, inf, maybe, lower, upper, min, prism.getIntervalIterationFlags());\n\t\t\t\t\t} else {\n\t\t\t\t\t\trewardsMTBDD = PrismMTBDD.NondetReachReward(tr, sr, trr, odd, nondetMask, allDDRowVars, allDDColVars, allDDNondetVars, b, inf, maybe, min);\n\t\t\t\t\t}\n\t\t\t\t\trewards = new StateValuesMTBDD(rewardsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\trewardsDV = PrismSparse.NondetReachRewardInterval(tr, tra, model.getSynchs(), sr, trr, odd, allDDRowVars, allDDColVars, allDDNondetVars, b, inf,\n\t\t\t\t\t\t\t\tmaybe, lower, upper, min, prism.getIntervalIterationFlags());\n\t\t\t\t\t} else {\n\t\t\t\t\t\trewardsDV = PrismSparse.NondetReachReward(tr, tra, model.getSynchs(), sr, trr, odd, allDDRowVars, allDDColVars, allDDNondetVars, b, inf,\n\t\t\t\t\t\t\t\tmaybe, min);\n\t\t\t\t\t}\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tthrow new PrismException(\"Hybrid engine does not yet support this type of property (use sparse or MTBDD engine instead)\");\n\t\t\t\t\t// rewardsDV = PrismHybrid.NondetReachReward(tr, sr, trr,\n\t\t\t\t\t// odd, allDDRowVars, allDDColVars, allDDNondetVars, b, inf,\n\t\t\t\t\t// maybe, min);\n\t\t\t\t\t// rewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\t// break;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t\t// Set accuracy info\n\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\trewards.setAccuracy(AccuracyFactory.guaranteedNumericalIterative(PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t\t} else {\n\t\t\t\t\trewards.setAccuracy(AccuracyFactory.valueIteration(PrismNative.getTermCritParam(), PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(inf);\n\t\t\t\tJDD.Deref(maybe);\n\t\t\t\tif (lower != null) JDD.Deref(lower);\n\t\t\t\tif (upper != null) JDD.Deref(upper);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\tif (zeroCostEndComponents != null)\n\t\t\tfor (JDDNode zcec : zeroCostEndComponents)\n\t\t\t\tJDD.Deref(zcec);\n\n\t\tif (doIntervalIteration) {\n\t\t\tdouble max_v = rewards.maxFiniteOverBDD(maybe);\n\t\t\tif (max_v != Double.NEGATIVE_INFINITY) {\n\t\t\t\tmainLog.println(\"Maximum finite value in solution vector at end of interval iteration: \" + max_v);\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(inf);\n\t\tJDD.Deref(maybe);\n\t\tif (lower != null) JDD.Deref(lower);\n\t\tif (upper != null) JDD.Deref(upper);\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Check whether state set represented by dd is \"weak absorbing\",\n\t * i.e. whether set is closed under all successors.\n\t * Note: does not deref dd.\n\t */\n\tprivate boolean checkWeakAbsorbing(JDDNode dd, NondetModel model)\n\t{\n\t\tboolean result;\n\n\t\tJDD.Ref(model.getTrans01());\n\t\tJDD.Ref(dd);\n\t\tJDDNode tmp = JDD.And(model.getTrans01(), dd);\n\t\ttmp = JDD.SwapVariables(tmp, model.getAllDDRowVars(), model.getAllDDColVars());\n\t\ttmp = JDD.ThereExists(tmp, model.getAllDDNondetVars());\n\t\ttmp = JDD.ThereExists(tmp, model.getAllDDColVars());\n\t\tJDD.Ref(model.getReach());\n\t\ttmp = JDD.And(model.getReach(), tmp);\n\t\tJDD.Ref(dd);\n\t\ttmp = JDD.And(tmp, JDD.Not(dd));\n\t\tresult = tmp.equals(JDD.ZERO);\n\t\tJDD.Deref(tmp);\n\n\t\treturn result;\n\t}\n\n\t\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/comp/ProbModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport hybrid.PrismHybrid;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.io.PrintStream;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Vector;\n\nimport acceptance.AcceptanceOmega;\nimport acceptance.AcceptanceOmegaDD;\nimport acceptance.AcceptanceReach;\nimport acceptance.AcceptanceReachDD;\nimport acceptance.AcceptanceType;\nimport automata.DA;\nimport common.StopWatch;\nimport io.ModelExportOptions;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport mtbdd.PrismMTBDD;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionFunc;\nimport parser.ast.ExpressionProb;\nimport parser.ast.ExpressionReward;\nimport parser.ast.ExpressionSS;\nimport parser.ast.ExpressionTemporal;\nimport parser.ast.ExpressionUnaryOp;\nimport parser.ast.PropertiesFile;\nimport parser.ast.RelOp;\nimport parser.type.TypeBool;\nimport parser.type.TypePathBool;\nimport parser.type.TypePathDouble;\nimport prism.AccuracyFactory;\nimport prism.IntegerBound;\nimport symbolic.comp.LTLModelChecker.LTLProduct;\nimport prism.ModelType;\nimport prism.OpRelOpBound;\nimport prism.OptionsIntervalIteration;\nimport prism.Prism;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismNative;\nimport prism.PrismNotSupportedException;\nimport prism.PrismSettings;\nimport prism.PrismUtils;\nimport symbolic.states.StateValues;\nimport symbolic.states.StateValuesDV;\nimport symbolic.states.StateValuesMTBDD;\nimport sparse.PrismSparse;\nimport dv.DoubleVector;\nimport explicit.ExportIterations;\nimport symbolic.model.Model;\nimport symbolic.model.NondetModel;\nimport symbolic.model.ProbModel;\n\n/*\n * Model checker for DTMCs.\n */\npublic class ProbModelChecker extends NonProbModelChecker\n{\n\t// Model (DTMC or CTMC)\n\tprotected ProbModel model;\n\n\t// Options (in addition to those inherited from StateModelChecker):\n\n\t// Use 0,1 precomputation algorithms?\n\t// if 'precomp' is false, this disables all (non-essential) use of prob0/prob1\n\t// if 'precomp' is true, the values of prob0/prob1 determine what is used\n\t// (currently prob0/prob are not under user control)\n\tprotected boolean precomp;\n\tprotected boolean prob0;\n\tprotected boolean prob1;\n\t// Do BSCC computation?\n\tprotected boolean bsccComp;\n\n\t// Constructor\n\n\tpublic ProbModelChecker(Prism prism, Model m, PropertiesFile pf) throws PrismException\n\t{\n\t\t// Initialise\n\t\tsuper(prism, m, pf);\n\t\tif (!(m instanceof ProbModel)) {\n\t\t\tthrow new PrismException(\"Wrong model type passed to ProbModelChecker.\");\n\t\t}\n\t\tmodel = (ProbModel) m;\n\n\t\t// Inherit some options from parent Prism object.\n\t\t// Store locally and/or pass onto native code.\n\t\tprecomp = prism.getPrecomp();\n\t\tprob0 = prism.getProb0();\n\t\tprob1 = prism.getProb1();\n\t\tbsccComp = prism.getBSCCComp();\n\t\tPrismNative.setCompact(prism.getCompact());\n\t\tPrismNative.setLinEqMethod(prism.getLinEqMethod());\n\t\tPrismNative.setLinEqMethodParam(prism.getLinEqMethodParam());\n\t\tPrismNative.setTermCrit(prism.getTermCrit());\n\t\tPrismNative.setTermCritParam(prism.getTermCritParam());\n\t\tPrismNative.setMaxIters(prism.getMaxIters());\n\t\tPrismNative.setSBMaxMem(prism.getSBMaxMem());\n\t\tPrismNative.setNumSBLevels(prism.getNumSBLevels());\n\t\tPrismNative.setSORMaxMem(prism.getSORMaxMem());\n\t\tPrismNative.setNumSORLevels(prism.getNumSORLevels());\n\t\tPrismNative.setDoSSDetect(prism.getDoSSDetect());\n\t\tPrismNative.setExportAdv(prism.getExportAdv());\n\t\tPrismNative.setExportAdvFilename(prism.getExportAdvFilename());\n\t}\n\n\t// Override-able \"Constructor\"\n\n\tpublic ProbModelChecker createNewModelChecker(Prism prism, Model m, PropertiesFile pf) throws PrismException\n\t{\n\t\treturn new ProbModelChecker(prism, m, pf);\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// Check a property, i.e. an expression\n\t// -----------------------------------------------------------------------------------\n\n\t// Check expression (recursive)\n\t@Override\n\tpublic StateValues checkExpression(Expression expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res;\n\n\t\t// P operator\n\t\tif (expr instanceof ExpressionProb) {\n\t\t\tres = checkExpressionProb((ExpressionProb) expr, statesOfInterest);\n\t\t}\n\t\t// R operator\n\t\telse if (expr instanceof ExpressionReward) {\n\t\t\tres = checkExpressionReward((ExpressionReward) expr, statesOfInterest);\n\t\t}\n\t\t// S operator\n\t\telse if (expr instanceof ExpressionSS) {\n\t\t\tres = checkExpressionSteadyState((ExpressionSS) expr, statesOfInterest);\n\t\t}\n\t\t// Otherwise, use the superclass\n\t\telse {\n\t\t\tres = super.checkExpression(expr, statesOfInterest);\n\t\t}\n\n\t\t// Filter out non-reachable states from solution\n\t\t// (only necessary for symbolically stored vectors)\n\t\tif (res instanceof StateValuesMTBDD)\n\t\t\tres.filter(reach);\n\n\t\treturn res;\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// Check method for each operator\n\t// -----------------------------------------------------------------------------------\n\n\t// P operator\n\n\t/**\n\t * Check a P (probability) operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionProb(ExpressionProb expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Get info from P operator\n\t\tOpRelOpBound opInfo = expr.getRelopBoundInfo(constantValues);\n\n\t\t// Check for trivial (i.e. stupid) cases\n\t\tif (opInfo.isTriviallyTrue()) {\n\t\t\tmainLog.printWarning(\"Checking for probability \" + opInfo.relOpBoundString() + \" - formula trivially satisfies all states\");\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\treturn new StateValuesMTBDD(reach, model, AccuracyFactory.doublesFromQualitative());\n\t\t} else if (opInfo.isTriviallyFalse()) {\n\t\t\tmainLog.printWarning(\"Checking for probability \" + opInfo.relOpBoundString() + \" - formula trivially satisfies no states\");\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\treturn new StateValuesMTBDD(JDD.Constant(0), model, AccuracyFactory.doublesFromQualitative());\n\t\t}\n\n\t\t// Print a warning if Pmin/Pmax used\n\t\tif (opInfo.getRelOp() == RelOp.MIN || opInfo.getRelOp() == RelOp.MAX) {\n\t\t\tmainLog.printWarning(\"\\\"Pmin=?\\\" and \\\"Pmax=?\\\" operators are identical to \\\"P=?\\\" for DTMCs/CTMCs\");\n\t\t}\n\n\t\t// Compute probabilities\n\t\tboolean qual = opInfo.isQualitative() && precomp && prob0 && prob1;\n\t\tStateValues probs = checkProbPathFormula(expr.getExpression(), qual, statesOfInterest);\n\n\t\t// Print out probabilities\n\t\tif (prism.getVerbose()) {\n\t\t\tmainLog.print(\"\\nProbabilities (non-zero only) for all states:\\n\");\n\t\t\tprobs.print(mainLog);\n\t\t}\n\n\t\t// For =? properties, just return values\n\t\tif (opInfo.isNumeric()) {\n\t\t\treturn probs;\n\t\t}\n\t\t// Otherwise, compare against bound to get set of satisfying states\n\t\telse {\n\t\t\tJDDNode sol = probs.getBDDFromInterval(opInfo.getRelOp(), opInfo.getBound());\n\t\t\t// remove unreachable states from solution\n\t\t\tJDD.Ref(reach);\n\t\t\tsol = JDD.And(sol, reach);\n\t\t\t// free vector\n\t\t\tprobs.clear();\n\t\t\treturn new StateValuesMTBDD(sol, model);\n\t\t}\n\t}\n\n\t// R operator\n\t\n\t/**\n\t * Check an R (reward) operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionReward(ExpressionReward expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Get info from R operator\n\t\tOpRelOpBound opInfo = expr.getRelopBoundInfo(constantValues);\n\t\t\n\t\t// Get rewards\n\t\tObject rs = expr.getRewardStructIndex();\n\t\tJDDNode stateRewards = getStateRewardsByIndexObject(rs, model, constantValues);\n\t\tcheckNegativeRewards(stateRewards, \"State\");\n\t\tJDDNode transRewards = getTransitionRewardsByIndexObject(rs, model, constantValues);\n\t\tcheckNegativeRewards(transRewards, \"Transition\");\n\n\t\t// Print a warning if Rmin/Rmax used\n\t\tif (opInfo.getRelOp() == RelOp.MIN || opInfo.getRelOp() == RelOp.MAX) {\n\t\t\tmainLog.printWarning(\"\\\"Rmin=?\\\" and \\\"Rmax=?\\\" operators are identical to \\\"R=?\\\" for DTMCs/CTMCs\");\n\t\t}\n\n\t\t// Compute rewards\n\t\tStateValues rewards = null;\n\t\tExpression expr2 = expr.getExpression();\n\t\tif (expr2.getType() instanceof TypePathDouble) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr2;\n\t\t\tswitch (exprTemp.getOperator()) {\n\t\t\tcase ExpressionTemporal.R_C:\n\t\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\t\trewards = checkRewardCumul(exprTemp, stateRewards, transRewards, statesOfInterest);\n\t\t\t\t} else {\n\t\t\t\t\trewards = checkRewardTotal(exprTemp, stateRewards, transRewards, statesOfInterest);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ExpressionTemporal.R_I:\n\t\t\t\trewards = checkRewardInst(exprTemp, stateRewards, transRewards, statesOfInterest);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionTemporal.R_S:\n\t\t\t\trewards = checkRewardSS(exprTemp, stateRewards, transRewards, statesOfInterest);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t} else if (expr2.getType() instanceof TypePathBool || expr2.getType() instanceof TypeBool) {\n\t\t\trewards = checkRewardPathFormula(expr2, stateRewards, transRewards, statesOfInterest);\n\t\t}\n\t\t\n\t\tif (rewards == null)\n\t\t\tthrow new PrismException(\"Unrecognised operator in R operator\");\n\n\t\t// Print out rewards\n\t\tif (prism.getVerbose()) {\n\t\t\tmainLog.print(\"\\nRewards (non-zero only) for all states:\\n\");\n\t\t\trewards.print(mainLog);\n\t\t}\n\n\t\t// For =? properties, just return values\n\t\tif (opInfo.isNumeric()) {\n\t\t\treturn rewards;\n\t\t}\n\t\t// Otherwise, compare against bound to get set of satisfying states\n\t\telse {\n\t\t\tJDDNode sol = rewards.getBDDFromInterval(opInfo.getRelOp(), opInfo.getBound());\n\t\t\t// remove unreachable states from solution\n\t\t\tJDD.Ref(reach);\n\t\t\tsol = JDD.And(sol, reach);\n\t\t\t// free vector\n\t\t\trewards.clear();\n\t\t\treturn new StateValuesMTBDD(sol, model);\n\t\t}\n\t}\n\n\t// S operator\n\n\t/**\n\t * Check an S (steady-state) operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionSteadyState(ExpressionSS expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// BSCC stuff\n\t\tList<JDDNode> bsccs = null;\n\t\tJDDNode notInBSCCs = null;\n\t\t// MTBDD stuff\n\t\tJDDNode b = null, bscc, sol, tmp;\n\t\t// Other stuff\n\t\tStateValues probs = null, totalProbs = null;\n\t\tint i, numBSCCs = 0;\n\t\tdouble d, probBSCCs[];\n\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// Get info from S operator\n\t\tOpRelOpBound opInfo = expr.getRelopBoundInfo(constantValues);\n\n\t\t// Check for trivial (i.e. stupid) cases\n\t\tif (opInfo.isTriviallyTrue()) {\n\t\t\tmainLog.printWarning(\"Checking for probability \" + opInfo.relOpBoundString() + \" - formula trivially satisfies all states\");\n\t\t\tJDD.Ref(reach);\n\t\t\treturn new StateValuesMTBDD(reach, model, AccuracyFactory.doublesFromQualitative());\n\t\t} else if (opInfo.isTriviallyFalse()) {\n\t\t\tmainLog.printWarning(\"Checking for probability \" + opInfo.relOpBoundString() + \" - formula trivially satisfies no states\");\n\t\t\treturn new StateValuesMTBDD(JDD.Constant(0), model, AccuracyFactory.doublesFromQualitative());\n\t\t}\n\n\t\ttry {\n\t\t\t// Model check argument with stateOfInterest = all\n\t\t\tb = checkExpressionDD(expr.getExpression(), model.getReach().copy());\n\n\t\t\t// Compute bottom strongly connected components (BSCCs)\n\t\t\tif (bsccComp) {\n\t\t\t\tSCCComputer sccComputer = prism.getSCCComputer(model);\n\t\t\t\tsccComputer.computeBSCCs();\n\t\t\t\tbsccs = sccComputer.getBSCCs();\n\t\t\t\tnotInBSCCs = sccComputer.getNotInBSCCs();\n\t\t\t\tnumBSCCs = bsccs.size();\n\t\t\t}\n\t\t\t// Unless we've been told to skip it\n\t\t\telse {\n\t\t\t\tmainLog.println(\"\\nSkipping BSCC computation...\");\n\t\t\t\tbsccs = new Vector<JDDNode>();\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tbsccs.add(reach);\n\t\t\t\tnotInBSCCs = JDD.Constant(0);\n\t\t\t\tnumBSCCs = 1;\n\t\t\t}\n\n\t\t\t// Compute steady-state probability for each BSCC...\n\t\t\tprobBSCCs = new double[numBSCCs];\n\t\t\tfor (i = 0; i < numBSCCs; i++) {\n\t\t\t\tmainLog.println(\"\\nComputing steady state probabilities for BSCC \" + (i + 1));\n\t\t\t\tbscc = bsccs.get(i);\n\t\t\t\t// Compute steady state probabilities\n\t\t\t\tprobs = computeSteadyStateProbsForBSCC(trans, bscc);\n\t\t\t\tif (verbose) {\n\t\t\t\t\tmainLog.print(\"\\nBSCC \" + (i + 1) + \" steady-state probabilities: \\n\");\n\t\t\t\t\tprobs.print(mainLog);\n\t\t\t\t}\n\t\t\t\t// Sum probabilities over BDD b\n\t\t\t\td = probs.sumOverBDD(b);\n\t\t\t\tprobBSCCs[i] = d;\n\t\t\t\tmainLog.print(\"\\nBSCC \" + (i + 1) + \" probability: \" + d + \"\\n\");\n\t\t\t\t// Free vector\n\t\t\t\tprobs.clear();\n\t\t\t}\n\n\t\t\t// If every state is in a BSCC, it's much easier...\n\t\t\tif (notInBSCCs.equals(JDD.ZERO)) {\n\t\t\t\tmainLog.println(\"\\nAll states are in BSCCs (so no reachability probabilities computed)\");\n\t\t\t\t// There are more efficient ways to do this if we just create the solution BDD directly\n\t\t\t\t// But we actually build the prob vector so it can be printed out if necessary\n\t\t\t\ttmp = JDD.Constant(0);\n\t\t\t\tfor (i = 0; i < numBSCCs; i++) {\n\t\t\t\t\tbscc = bsccs.get(i);\n\t\t\t\t\tJDD.Ref(bscc);\n\t\t\t\t\ttmp = JDD.Apply(JDD.PLUS, tmp, JDD.Apply(JDD.TIMES, JDD.Constant(probBSCCs[i]), bscc));\n\t\t\t\t}\n\t\t\t\ttotalProbs = new StateValuesMTBDD(tmp, model);\n\t\t\t}\n\t\t\t// Otherwise we have to do more work...\n\t\t\telse {\n\n\t\t\t\t// Initialise total probabilities vector\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\ttotalProbs = new StateValuesMTBDD(JDD.Constant(0), model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\ttotalProbs = new StateValuesDV(new DoubleVector(model.getNumStates()), model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\ttotalProbs = new StateValuesDV(new DoubleVector(model.getNumStates()), model);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\n\t\t\t\t// Compute probabilities of reaching each BSCC...\n\t\t\t\tfor (i = 0; i < numBSCCs; i++) {\n\t\t\t\t\t// Skip BSCCs with zero probability\n\t\t\t\t\tif (probBSCCs[i] == 0.0)\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\tmainLog.println(\"\\nComputing probabilities of reaching BSCC \" + (i + 1));\n\t\t\t\t\tbscc = bsccs.get(i);\n\t\t\t\t\t// Compute probabilities\n\t\t\t\t\tprobs = computeUntilProbs(trans, trans01, notInBSCCs, bscc);\n\t\t\t\t\tif (verbose) {\n\t\t\t\t\t\tmainLog.print(\"\\nBSCC \" + (i + 1) + \" reachability probabilities: \\n\");\n\t\t\t\t\t\tprobs.print(mainLog);\n\t\t\t\t\t}\n\t\t\t\t\t// Multiply by BSCC prob, add to total\n\t\t\t\t\tprobs.timesConstant(probBSCCs[i]);\n\t\t\t\t\ttotalProbs.add(probs);\n\t\t\t\t\t// Free vector\n\t\t\t\t\tprobs.clear();\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// print out probabilities\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.print(\"\\nS operator probabilities: \\n\");\n\t\t\t\ttotalProbs.print(mainLog);\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\t// Tidy up and pass on the exception\n\t\t\tif (b != null)\n\t\t\t\tJDD.Deref(b);\n\t\t\tfor (i = 0; i < numBSCCs; i++) {\n\t\t\t\tif (bsccs.get(i) != null)\n\t\t\t\t\tJDD.Deref(bsccs.get(i));\n\t\t\t}\n\t\t\tif (notInBSCCs != null)\n\t\t\t\tJDD.Deref(notInBSCCs);\n\t\t\tif (totalProbs != null)\n\t\t\t\ttotalProbs.clear();\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Tidy up\n\t\tif (b != null)\n\t\t\tJDD.Deref(b);\n\t\tfor (i = 0; i < numBSCCs; i++) {\n\t\t\tif (bsccs.get(i) != null)\n\t\t\t\tJDD.Deref(bsccs.get(i));\n\t\t}\n\t\tif (notInBSCCs != null)\n\t\t\tJDD.Deref(notInBSCCs);\n\n\t\t// For =? properties, just return values\n\t\tif (opInfo.isNumeric()) {\n\t\t\treturn totalProbs;\n\t\t}\n\t\t// Otherwise, compare against bound to get set of satisfying states\n\t\telse {\n\t\t\tsol = totalProbs.getBDDFromInterval(opInfo.getRelOp(), opInfo.getBound());\n\t\t\t// remove unreachable states from solution\n\t\t\tJDD.Ref(reach);\n\t\t\tsol = JDD.And(sol, reach);\n\t\t\t// free vector\n\t\t\ttotalProbs.clear();\n\t\t\treturn new StateValuesMTBDD(sol, model);\n\t\t}\n\t}\n\n\t// Contents of a P operator\n\n\t/**\n\t * Check a P operator path formula.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t *\n\t * @param qual perform qualitative model checking\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbPathFormula(Expression expr, boolean qual, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Test whether this is a simple path formula (i.e. PCTL)\n\t\t// and whether we want to use the corresponding algorithms\n\t\tboolean useSimplePathAlgo = expr.isSimplePathFormula();\n\n\t\tif (useSimplePathAlgo && settings.getBoolean(PrismSettings.PRISM_PATH_VIA_AUTOMATA) &&\n\t\t    LTLModelChecker.isSupportedLTLFormula(model.getModelType(), expr)) {\n\t\t\t// If PRISM_PATH_VIA_AUTOMATA is true, we want to use the LTL engine\n\t\t\t// whenever possible\n\t\t\tuseSimplePathAlgo = false;\n\t\t}\n\n\t\tif (useSimplePathAlgo) {\n\t\t\treturn checkProbPathFormulaSimple(expr, qual, statesOfInterest);\n\t\t} else {\n\t\t\treturn checkProbPathFormulaLTL(expr, qual, statesOfInterest);\n\t\t}\n\t}\n\n\t/**\n\t * Check a P operator simple path formula (single, non-nested temporal operator).\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t *\n\t * @param qual perform qualitative model checking\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbPathFormulaSimple(Expression expr, boolean qual, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tboolean negated = false;\n\t\tStateValues probs = null;\n\n\t\texpr = Expression.convertSimplePathFormulaToCanonicalForm(expr);\n\n\t\t// Negation\n\t\tif (expr instanceof ExpressionUnaryOp &&\n\t\t    ((ExpressionUnaryOp)expr).getOperator() == ExpressionUnaryOp.NOT) {\n\t\t\tnegated = true;\n\t\t\texpr = ((ExpressionUnaryOp)expr).getOperand();\n\t\t}\n\n\t\tif (expr instanceof ExpressionTemporal) {\n\t\t\tExpressionTemporal exprTemp = (ExpressionTemporal) expr;\n\t\t\t// Next\n\t\t\tif (exprTemp.getOperator() == ExpressionTemporal.P_X) {\n\t\t\t\tprobs = checkProbNext(exprTemp, statesOfInterest);\n\t\t\t}\n\t\t\t// Until\n\t\t\telse if (exprTemp.getOperator() == ExpressionTemporal.P_U) {\n\t\t\t\tif (exprTemp.hasBounds()) {\n\t\t\t\t\tprobs = checkProbBoundedUntil(exprTemp, statesOfInterest);\n\t\t\t\t} else {\n\t\t\t\t\tprobs = checkProbUntil(exprTemp, qual, statesOfInterest);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tif (probs == null)\n\t\t\tthrow new PrismException(\"Unrecognised path operator in P operator\");\n\n\t\tif (negated) {\n\t\t\t// Subtract from 1 for negation\n\t\t\tprobs.subtractFromOne();\n\t\t}\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Check a P operator LTL-like path formula.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t *\n\t * @param qual perform qualitative model checking\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbPathFormulaLTL(Expression expr, boolean qual, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tLTLModelChecker mcLtl;\n\t\tStateValues probsProduct = null, probs = null;\n\t\tVector<JDDNode> labelDDs = new Vector<JDDNode>();\n\t\tDA<BitSet, ? extends AcceptanceOmega> da;\n\t\tProbModel modelProduct;\n\t\tProbModelChecker mcProduct;\n\t\tJDDNode startMask;\n\t\tJDDVars daDDRowVars, daDDColVars;\n\t\tint i;\n\n\t\tAcceptanceType[] allowedAcceptance = {\n\t\t\t\tAcceptanceType.REACH,\n\t\t\t\tAcceptanceType.BUCHI,\n\t\t\t\tAcceptanceType.RABIN,\n\t\t\t\tAcceptanceType.STREETT,\n\t\t\t\tAcceptanceType.GENERALIZED_RABIN,\n\t\t\t\tAcceptanceType.GENERIC\n\t\t};\n\t\tmcLtl = new LTLModelChecker(prism);\n\t\ttry {\n\t\t\tda = mcLtl.constructDAForLTLFormula(this, model, expr, labelDDs, allowedAcceptance);\n\t\t} catch (Exception e) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Build product of Markov chain and automaton\n\t\t// (note: might be a CTMC - StochModelChecker extends this class)\n\t\tmainLog.println(\"\\nConstructing MC-\"+da.getAutomataType()+\" product...\");\n\t\tdaDDRowVars = new JDDVars();\n\t\tdaDDColVars = new JDDVars();\n\t\tmodelProduct = mcLtl.constructProductMC(da, model, labelDDs, daDDRowVars, daDDColVars, statesOfInterest);\n\t\tmainLog.println();\n\t\tmodelProduct.printTransInfo(mainLog, prism.getExtraDDInfo());\n\t\t// Output product, if required\n\t\tif (prism.getExportProductTrans()) {\n\t\t\ttry {\n\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions();\n\t\t\t\texportOptions.setModelPrecision(getSettings().getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION));\n\t\t\t\tmainLog.println(\"\\nExporting product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"...\");\n\t\t\t\tmodelProduct.exportToFile(new File(prism.getExportProductTransFilename()), exportOptions);\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.printWarning(\"Could not export product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\t\tif (prism.getExportProductStates()) {\n\t\t\tmainLog.println(\"\\nExporting product state space to file \\\"\" + prism.getExportProductStatesFilename() + \"\\\"...\");\n\t\t\tPrismFileLog out = new PrismFileLog(prism.getExportProductStatesFilename());\n\t\t\tmodelProduct.exportStates(Prism.EXPORT_PLAIN, out);\n\t\t\tout.close();\n\t\t}\n\n\t\t// Find accepting states + compute reachability probabilities\n\t\tAcceptanceOmegaDD acceptance = da.getAcceptance().toAcceptanceDD(daDDRowVars);\n\t\tJDDNode acc;\n\t\tif (acceptance instanceof AcceptanceReachDD) {\n\t\t\tmainLog.println(\"\\nSkipping BSCC computation since acceptance is defined via goal states...\");\n\t\t\tacc = ((AcceptanceReachDD) acceptance).getGoalStates();\n\t\t\tJDD.Ref(modelProduct.getReach());\n\t\t\tacc = JDD.And(acc, modelProduct.getReach());\n\t\t} else {\n\t\t\tmainLog.println(\"\\nFinding accepting BSCCs...\");\n\t\t\tacc = mcLtl.findAcceptingBSCCs(acceptance, modelProduct);\n\t\t}\n\t\tacceptance.clear();\n\t\tmainLog.println(\"\\nComputing reachability probabilities...\");\n\t\tmcProduct = createNewModelChecker(prism, modelProduct, null);\n\t\tprobsProduct = mcProduct.checkProbUntil(modelProduct.getReach(), acc, qual);\n\n\t\t// Convert probability vector to original model\n\t\t// First, filter over DRA start states\n\t\tstartMask = mcLtl.buildStartMask(da, labelDDs, daDDRowVars);\n\t\tJDD.Ref(model.getReach());\n\t\tstartMask = JDD.And(model.getReach(), startMask);\n\t\tprobsProduct.filter(startMask);\n\t\t// Then sum over DD vars for the DA state (could also have used,\n\t\t// e.g. max, since there is just one state for each valuation of daDDRowVars) \n\t\tprobs = probsProduct.sumOverDDVars(daDDRowVars, model);\n\n\t\t// Deref, clean up\n\t\tprobsProduct.clear();\n\t\tmodelProduct.clear();\n\t\tfor (i = 0; i < labelDDs.size(); i++) {\n\t\t\tJDD.Deref(labelDDs.get(i));\n\t\t}\n\t\tJDD.Deref(acc);\n\t\tJDD.Deref(startMask);\n\t\tdaDDRowVars.derefAll();\n\t\tdaDDColVars.derefAll();\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Check a P operator with a next operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbNext(ExpressionTemporal expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b;\n\t\tStateValues probs = null;\n\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// model check operand first, stateOfInterest = all\n\t\tb = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb = \" + JDD.GetNumMintermsString(b,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\t// compute probabilities\n\t\tprobs = computeNextProbs(trans, b);\n\n\t\t// derefs\n\t\tJDD.Deref(b);\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Check a P operator with a bounded until operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkProbBoundedUntil(ExpressionTemporal expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b1, b2;\n\t\tStateValues probs = null;\n\t\tInteger lowerBound;\n\t\tIntegerBound bounds;\n\t\tint i;\n\n\t\t// currently, we ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// get and check bounds information\n\t\tbounds = IntegerBound.fromExpressionTemporal(expr, constantValues, true);\n\n\t\t// model check operands first, statesOfInterest = all\n\t\tb1 = checkExpressionDD(expr.getOperand1(), model.getReach().copy());\n\t\ttry {\n\t\t\tb2 = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b1);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb1 = \" + JDD.GetNumMintermsString(b1,\n\t\t// allDDRowVars.n()));\n\t\t// mainLog.print(\" states, b2 = \" + JDD.GetNumMintermsString(b2,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\tif (bounds.hasLowerBound()) {\n\t\t\tlowerBound = bounds.getLowestInteger();\n\t\t} else {\n\t\t\tlowerBound = 0;\n\t\t}\n\n\t\tInteger windowSize = null;  // unbounded\n\t\tif (bounds.hasUpperBound()) {\n\t\t\twindowSize = bounds.getHighestInteger() - lowerBound;\n\t\t}\n\n\t\t// compute probabilities for Until<=windowSize\n\t\tif (windowSize == null) {\n\t\t\t// unbounded\n\t\t\ttry {\n\t\t\t\tprobs = computeUntilProbs(trans, trans01, b1, b2);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(b1);\n\t\t\t\tJDD.Deref(b2);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t} else if (windowSize == 0) {\n\t\t\t// the trivial case: windowSize = 0\n\t\t\t// prob is 1 in b2 states, 0 otherwise\n\t\t\tJDD.Ref(b2);\n\t\t\tprobs = new StateValuesMTBDD(b2, model, AccuracyFactory.doublesFromQualitative());\n\t\t} else {\n\t\t\ttry {\n\t\t\t\tprobs = computeBoundedUntilProbs(trans, trans01, b1, b2, windowSize);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(b1);\n\t\t\t\tJDD.Deref(b2);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\t// perform lowerBound restricted next-step computations to\n\t\t// deal with lower bound.\n\t\tif (lowerBound > 0) {\n\t\t\tfor (i = 0; i < lowerBound; i++) {\n\t\t\t\tprobs = computeRestrictedNext(trans, b1, probs);\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(b1);\n\t\tJDD.Deref(b2);\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Check a P operator with an unbounded until operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\t// this method is split into two steps so that the LTL model checker can use the second part directly\n\tprotected StateValues checkProbUntil(ExpressionTemporal expr, boolean qual, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b1, b2;\n\t\tStateValues probs = null;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// model check operands first, statesOfInterest = all\n\t\tb1 = checkExpressionDD(expr.getOperand1(), model.getReach().copy());\n\t\ttry {\n\t\t\tb2 = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b1);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb1 = \" + JDD.GetNumMintermsString(b1,\n\t\t// allDDRowVars.n()));\n\t\t// mainLog.print(\" states, b2 = \" + JDD.GetNumMintermsString(b2,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\ttry {\n\t\t\tprobs = checkProbUntil(b1, b2, qual);\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b1);\n\t\t\tJDD.Deref(b2);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(b1);\n\t\tJDD.Deref(b2);\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Check a P operator with an unbounded until operator (b1 U b2)\n\t * @param qual perform qualitative model checking?\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tprotected StateValues checkProbUntil(JDDNode b1, JDDNode b2, boolean qual) throws PrismException\n\t{\n\t\tStateValues probs = null;\n\n\t\t// compute probabilities\n\n\t\t// if requested (i.e. when prob bound is 0 or 1 and precomputation algorithms are enabled),\n\t\t// compute probabilities qualitatively\n\t\tif (qual) {\n\t\t\tmainLog.print(\"\\nProbability bound in formula is 0/1 so not computing exact probabilities...\\n\");\n\t\t\tprobs = computeUntilProbsQual(trans01, b1, b2);\n\t\t}\n\t\t// otherwise actually compute probabilities\n\t\telse {\n\t\t\tprobs = computeUntilProbs(trans, trans01, b1, b2);\n\t\t}\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Check a cumulative reward operator (C<=t).\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardCumul(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tint time; // time\n\t\tStateValues rewards = null;\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// check that there is an upper time bound\n\t\tif (expr.getUpperBound() == null) {\n\t\t\tthrow new PrismException(\"Cumulative reward operator without time bound (C) is only allowed for multi-objective queries\");\n\t\t}\n\n\t\t// get info from inst reward\n\t\ttime = expr.getUpperBound().evaluateInt(constantValues);\n\t\tif (time < 0) {\n\t\t\tthrow new PrismException(\"Invalid time bound \" + time + \" in cumulative reward formula\");\n\t\t}\n\n\t\t// compute rewards\n\n\t\t// a trivial case: \"<=0\"\n\t\tif (time == 0) {\n\t\t\trewards = new StateValuesMTBDD(JDD.Constant(0), model, AccuracyFactory.doublesFromQualitative());\n\t\t} else {\n\t\t\t// compute rewards\n\t\t\ttry {\n\t\t\t\trewards = computeCumulRewards(trans, trans01, stateRewards, transRewards, time);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Check a total reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardTotal(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// currently, we ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\tStateValues rewards = computeTotalRewards(trans, trans01, stateRewards, transRewards);\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Check an instantaneous reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardInst(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tint time; // time\n\t\tStateValues rewards = null;\n\n\t\t// currently, we ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// get info from inst reward\n\t\ttime = expr.getUpperBound().evaluateInt(constantValues);\n\t\tif (time < 0) {\n\t\t\tthrow new PrismException(\"Invalid bound \" + time + \" in instantaneous reward property\");\n\t\t}\n\n\t\t// compute rewards\n\t\trewards = computeInstRewards(trans, stateRewards, time);\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Check a reachability reward operator (either simple or using co-safety LTL).\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardPathFormula(Expression expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tif (Expression.isReach(expr)) {\n\t\t\treturn checkRewardReach((ExpressionTemporal) expr, stateRewards, transRewards, statesOfInterest);\n\t\t}\n\t\telse if (Expression.isCoSafeLTLSyntactic(expr, true)) {\n\t\t\treturn checkRewardCoSafeLTL(expr, stateRewards, transRewards, statesOfInterest);\n\t\t}\n\t\tJDD.Deref(statesOfInterest);\n\t\tthrow new PrismException(\"R operator contains a path formula that is not syntactically co-safe: \" + expr);\n\t}\n\n\t/**\n\t * Check a reachability reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardReach(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tJDDNode b;\n\t\tStateValues rewards = null;\n\n\t\t// currently, we ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// No time bounds allowed\n\t\tif (expr.hasBounds()) {\n\t\t\tthrow new PrismNotSupportedException(\"R operator cannot contain a bounded F operator: \" + expr);\n\t\t}\n\t\t\n\t\t// model check operand first\n\t\tb = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb = \" + JDD.GetNumMintermsString(b,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\t// compute rewards\n\t\ttry {\n\t\t\trewards = computeReachRewards(trans, trans01, stateRewards, transRewards, b);\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(b);\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Check a co-safe LTL reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardCoSafeLTL(Expression expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tLTLModelChecker mcLtl;\n\t\tStateValues rewardsProduct = null, rewards = null;\n\t\tExpression ltl;\n\t\tVector<JDDNode> labelDDs = new Vector<JDDNode>();\n\t\tLTLProduct<ProbModel> modelProduct;\n\t\tProbModelChecker mcProduct;\n\t\tlong l;\n\n\t\tif (Expression.containsTemporalTimeBounds(expr)) {\n\t\t\tif (model.getModelType().continuousTime()) {\n\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\tthrow new PrismException(\"DA construction for time-bounded operators not supported for \" + model.getModelType()+\".\");\n\t\t\t}\n\n\t\t\tif (!expr.isSimplePathFormula()) {\n\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\tthrow new PrismException(\"Time-bounded operators not supported in LTL: \" + expr);\n\t\t\t}\n\t\t}\n\n\t\t// Can't do \"dfa\" properties yet\n\t\tif (expr instanceof ExpressionFunc && ((ExpressionFunc) expr).getName().equals(\"dfa\")) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Model checking for \\\"dfa\\\" specifications not supported yet\");\n\t\t}\n\n\t\t// For LTL model checking routines\n\t\tmcLtl = new LTLModelChecker(prism);\n\n\t\t// Model check maximal state formulas and construct DFA, with the special\n\t\t// handling needed for cosafety reward translation\n\t\tDA<BitSet, AcceptanceReach> da = mcLtl.constructDFAForCosafetyRewardLTL(this, model, expr, labelDDs);\n\n\t\t// If required, export DA \n\t\tif (settings.getExportPropAut()) {\n\t\t\tmainLog.println(\"Exporting DA to file \\\"\" + settings.getExportPropAutFilename() + \"\\\"...\");\n\t\t\tPrintStream out = PrismUtils.newPrintStream(settings.getExportPropAutFilename());\n\t\t\tda.print(out, settings.getExportPropAutType());\n\t\t\tout.close();\n\t\t\t//da.printDot(new java.io.PrintStream(\"da.dot\"));\n\t\t}\n\n\t\t// Build product of Markov chain and automaton\n\t\tmodelProduct = mcLtl.constructProductMC(model, da, labelDDs, statesOfInterest);\n\t\t// Output product, if required\n\t\tif (prism.getExportProductTrans()) {\n\t\t\ttry {\n\t\t\t\tModelExportOptions exportOptions = new ModelExportOptions();\n\t\t\t\texportOptions.setModelPrecision(getSettings().getInteger(PrismSettings.PRISM_EXPORT_MODEL_PRECISION));\n\t\t\t\tmainLog.println(\"\\nExporting product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"...\");\n\t\t\t\tmodelProduct.getProductModel().exportToFile(new File(prism.getExportProductTransFilename()), exportOptions);\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.printWarning(\"Could not export product transition matrix to file \\\"\" + prism.getExportProductTransFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\t\tif (prism.getExportProductStates()) {\n\t\t\tmainLog.println(\"\\nExporting product state space to file \\\"\" + prism.getExportProductStatesFilename() + \"\\\"...\");\n\t\t\tPrismFileLog out = new PrismFileLog(prism.getExportProductStatesFilename());\n\t\t\tmodelProduct.getProductModel().exportStates(Prism.EXPORT_PLAIN, out);\n\t\t\tout.close();\n\t\t}\n\n\t\t// Adapt reward info to product model\n\t\tJDDNode stateRewardsProduct = JDD.Apply(JDD.TIMES, stateRewards.copy(), modelProduct.getProductModel().getReach().copy());\n\t\tJDDNode transRewardsProduct = JDD.Apply(JDD.TIMES, transRewards.copy(), modelProduct.getProductModel().getTrans01().copy());\n\t\t\n\t\t// Find accepting states + compute reachability rewards\n\t\tAcceptanceReachDD acceptance = (AcceptanceReachDD) modelProduct.getProductAcceptance();\n\t\t// acc is already restricted to the product model's reachable states\n\t\tJDDNode acc = acceptance.getGoalStates();\n\n\t\tmainLog.println(\"\\nComputing reachability rewards...\");\n\t\tmcProduct = createNewModelChecker(prism, modelProduct.getProductModel(), null);\n\t\trewardsProduct = mcProduct.computeReachRewards(modelProduct.getProductModel().getTrans(),\n\t\t                                               modelProduct.getProductModel().getTrans01(),\n\t\t                                               stateRewardsProduct,\n\t\t                                               transRewardsProduct,\n\t\t                                               acc);\n\n\t\t// Convert reward vector to original model\n\t\trewards = modelProduct.projectToOriginalModel(rewardsProduct);\n\n\t\t// Deref, clean up\n\t\tJDD.Deref(stateRewardsProduct);\n\t\tJDD.Deref(transRewardsProduct);\n\t\tmodelProduct.clear();\n\t\tJDD.Deref(acc);\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Check a steady-state reward operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkRewardSS(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// bscc stuff\n\t\tList<JDDNode> vectBSCCs;\n\t\tJDDNode notInBSCCs;\n\t\t// mtbdd stuff\n\t\tJDDNode newStateRewards, bscc, tmp;\n\t\t// other stuff\n\t\tStateValues probs = null, rewards = null;\n\t\tint i, numBSCCs;\n\t\tdouble d, rewBSCCs[];\n\n\t\t// currently, ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// compute rewards corresponding to each state\n\t\tJDD.Ref(trans);\n\t\tJDD.Ref(transRewards);\n\t\tnewStateRewards = JDD.SumAbstract(JDD.Apply(JDD.TIMES, trans, transRewards), allDDColVars);\n\t\tJDD.Ref(stateRewards);\n\t\tnewStateRewards = JDD.Apply(JDD.PLUS, newStateRewards, stateRewards);\n\n\t\t// compute bottom strongly connected components (bsccs)\n\t\tif (bsccComp) {\n\t\t\tSCCComputer sccComputer = prism.getSCCComputer(model);\n\t\t\tsccComputer.computeBSCCs();\n\t\t\tvectBSCCs = sccComputer.getBSCCs();\n\t\t\tnotInBSCCs = sccComputer.getNotInBSCCs();\n\t\t\tnumBSCCs = vectBSCCs.size();\n\t\t}\n\t\t// unless we've been told to skip it\n\t\telse {\n\t\t\tmainLog.println(\"\\nSkipping BSCC computation...\");\n\t\t\tvectBSCCs = new Vector<JDDNode>();\n\t\t\tJDD.Ref(reach);\n\t\t\tvectBSCCs.add(reach);\n\t\t\tnotInBSCCs = JDD.Constant(0);\n\t\t\tnumBSCCs = 1;\n\t\t}\n\n\t\t// compute steady state for each bscc...\n\t\trewBSCCs = new double[numBSCCs];\n\t\tfor (i = 0; i < numBSCCs; i++) {\n\n\t\t\tmainLog.println(\"\\nComputing steady state probabilities for BSCC \" + (i + 1));\n\n\t\t\t// get bscc\n\t\t\tbscc = vectBSCCs.get(i);\n\n\t\t\t// compute steady state probabilities\n\t\t\ttry {\n\t\t\t\tprobs = computeSteadyStateProbsForBSCC(trans, bscc);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(newStateRewards);\n\t\t\t\tfor (i = 0; i < numBSCCs; i++) {\n\t\t\t\t\tJDD.Deref(vectBSCCs.get(i));\n\t\t\t\t}\n\t\t\t\tJDD.Deref(notInBSCCs);\n\t\t\t\tthrow e;\n\t\t\t}\n\n\t\t\t// print out probabilities\n\t\t\tif (verbose) {\n\t\t\t\tmainLog.print(\"\\nBSCC \" + (i + 1) + \" steady-state probabilities: \\n\");\n\t\t\t\tprobs.print(mainLog);\n\t\t\t}\n\n\t\t\t// do weighted sum of probabilities and rewards\n\t\t\tJDD.Ref(bscc);\n\t\t\tJDD.Ref(newStateRewards);\n\t\t\ttmp = JDD.Apply(JDD.TIMES, bscc, newStateRewards);\n\t\t\td = probs.sumOverMTBDD(tmp);\n\t\t\trewBSCCs[i] = d;\n\t\t\tmainLog.print(\"\\nBSCC \" + (i + 1) + \" Reward: \" + d + \"\\n\");\n\t\t\tJDD.Deref(tmp);\n\n\t\t\t// free vector\n\t\t\tprobs.clear();\n\t\t}\n\n\t\t// if every state is in a bscc, it's much easier...\n\t\tif (notInBSCCs.equals(JDD.ZERO)) {\n\n\t\t\tmainLog.println(\"\\nAll states are in BSCCs (so no reachability probabilities computed)\");\n\n\t\t\t// build the reward vector\n\t\t\ttmp = JDD.Constant(0);\n\t\t\tfor (i = 0; i < numBSCCs; i++) {\n\t\t\t\tbscc = vectBSCCs.get(i);\n\t\t\t\tJDD.Ref(bscc);\n\t\t\t\ttmp = JDD.Apply(JDD.PLUS, tmp, JDD.Apply(JDD.TIMES, JDD.Constant(rewBSCCs[i]), bscc));\n\t\t\t}\n\t\t\trewards = new StateValuesMTBDD(tmp, model);\n\t\t}\n\t\t// otherwise we have to do more work...\n\t\telse {\n\n\t\t\t// initialise rewards vector\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\trewards = new StateValuesMTBDD(JDD.Constant(0), model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\t\trewards = new StateValuesDV(new DoubleVector(model.getNumStates()), model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.HYBRID:\n\t\t\t\trewards = new StateValuesDV(new DoubleVector(model.getNumStates()), model);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t// compute probabilities of reaching each bscc...\n\t\t\tfor (i = 0; i < numBSCCs; i++) {\n\n\t\t\t\t// skip bsccs with zero reward\n\t\t\t\tif (rewBSCCs[i] == 0.0)\n\t\t\t\t\tcontinue;\n\n\t\t\t\tmainLog.println(\"\\nComputing probabilities of reaching BSCC \" + (i + 1));\n\n\t\t\t\t// get bscc\n\t\t\t\tbscc = vectBSCCs.get(i);\n\n\t\t\t\t// compute probabilities\n\t\t\t\tprobs = computeUntilProbs(trans, trans01, notInBSCCs, bscc);\n\n\t\t\t\t// print out probabilities\n\t\t\t\tif (verbose) {\n\t\t\t\t\tmainLog.print(\"\\nBSCC \" + (i + 1) + \" reachability probabilities: \\n\");\n\t\t\t\t\tprobs.print(mainLog);\n\t\t\t\t}\n\n\t\t\t\t// times by bscc reward, add to total\n\t\t\t\tprobs.timesConstant(rewBSCCs[i]);\n\t\t\t\trewards.add(probs);\n\n\t\t\t\t// free vector\n\t\t\t\tprobs.clear();\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(newStateRewards);\n\t\tfor (i = 0; i < numBSCCs; i++) {\n\t\t\tJDD.Deref(vectBSCCs.get(i));\n\t\t}\n\t\tJDD.Deref(notInBSCCs);\n\n\t\treturn rewards;\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// do steady state computation\n\t// -----------------------------------------------------------------------------------\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doSteadyState() throws PrismException\n\t{\n\t\treturn doSteadyState((StateValues) null);\n\t}\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Optionally, use the passed in file initDistFile to give the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doSteadyState(File initDistFile) throws PrismException\n\t{\n\t\tStateValues initDist = readDistributionFromFile(initDistFile);\n\t\treturn doSteadyState(initDist);\n\t}\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Optionally, use the passed in vector initDist as the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * For reasons of efficiency, when a vector is passed in, it will be trampled over and\n\t * then deleted afterwards, so if you wanted it, take a copy. \n\t */\n\tpublic StateValues doSteadyState(StateValues initDist) throws PrismException\n\t{\n\t\tStateValues initDistNew = (initDist == null) ? buildInitialDistribution() : initDist;\n\t\treturn computeSteadyStateProbs(trans, initDistNew);\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// do transient computation\n\t// -----------------------------------------------------------------------------------\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doTransient(int time) throws PrismException\n\t{\n\t\treturn doTransient(time, (StateValues) null);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Optionally, use the passed in file initDistFile to give the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doTransient(int time, File initDistFile) throws PrismException\n\t{\n\t\tStateValues initDist = readDistributionFromFile(initDistFile);\n\t\treturn doTransient(time, initDist);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Optionally, use the passed in vector initDist as the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * For reasons of efficiency, when a vector is passed in, it will be trampled over and\n\t * then deleted afterwards, so if you wanted it, take a copy. \n\t */\n\tpublic StateValues doTransient(int time, StateValues initDist) throws PrismException\n\t{\n\t\tStateValues initDistNew = (initDist == null) ? buildInitialDistribution() : initDist;\n\t\treturn computeTransientProbs(trans, initDistNew, time);\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// Utility methods for probability distributions\n\t// -----------------------------------------------------------------------------------\n\n\t/**\n\t * Generate a probability distribution, stored as a StateValues object, from a file.\n\t * The type of storage (MTBDD or double vector) matches the current engine.\n\t * If {@code distFile} is null, so is the return value.\n\t */\n\tpublic StateValues readDistributionFromFile(File distFile) throws PrismException\n\t{\n\t\tStateValues dist = null;\n\n\t\tif (distFile != null) {\n\t\t\tmainLog.println(\"\\nImporting probability distribution from file \\\"\" + distFile + \"\\\"...\");\n\t\t\t// Build an empty vector of the appropriate type \n\t\t\tif (engine == Prism.MTBDD) {\n\t\t\t\tdist = new StateValuesMTBDD(JDD.Constant(0), model);\n\t\t\t} else {\n\t\t\t\tdist = new StateValuesDV(new DoubleVector(model.getNumStates()), model);\n\t\t\t}\n\t\t\t// Populate vector from file\n\t\t\tdist.readFromFile(distFile);\n\t\t}\n\n\t\treturn dist;\n\t}\n\n\t/**\n\t * Build a probability distribution, stored as a StateValues object,\n\t * from the initial states info of the current model: either probability 1 for\n\t * the (single) initial state or equiprobable over multiple initial states.\n\t * The type of storage (MTBDD or double vector) matches the current engine.\n\t */\n\tprivate StateValues buildInitialDistribution() throws PrismException\n\t{\n\t\tStateValues dist = null;\n\t\tJDDNode init;\n\n\t\t// first construct as MTBDD\n\t\t// get initial states of model\n\t\tstart = model.getStart();\n\t\t// compute initial probability distribution (equiprobable over all start states)\n\t\tJDD.Ref(start);\n\t\tinit = JDD.Apply(JDD.DIVIDE, start, JDD.Constant(JDD.GetNumMinterms(start, allDDRowVars.n())));\n\t\t// if using MTBDD engine, distribution needs to be an MTBDD\n\t\tif (engine == Prism.MTBDD) {\n\t\t\tdist = new StateValuesMTBDD(init, model);\n\t\t}\n\t\t// for sparse/hybrid engines, distribution needs to be a double vector\n\t\telse {\n\t\t\tdist = new StateValuesDV(init, model);\n\t\t\tJDD.Deref(init);\n\t\t}\n\n\t\treturn dist;\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// probability computation methods\n\t// -----------------------------------------------------------------------------------\n\n\t// compute probabilities for next\n\n\tprotected StateValues computeNextProbs(JDDNode tr, JDDNode b)\n\t{\n\t\tJDDNode tmp;\n\t\tStateValues probs = null;\n\n\t\t// matrix multiply: trans * b\n\t\tJDD.Ref(b);\n\t\ttmp = JDD.PermuteVariables(b, allDDRowVars, allDDColVars);\n\t\tJDD.Ref(tr);\n\t\ttmp = JDD.MatrixMultiply(tr, tmp, allDDColVars, JDD.BOULDER);\n\t\tprobs = new StateValuesMTBDD(tmp, model);\n\t\tprobs.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Given a value vector x, compute the probability:\n\t *   v(s) = Sum_s' P(s,s')*x(s')   for s labeled with a,\n\t *   v(s) = 0                      for s not labeled with a.\n\t *\n\t * Clears the StateValues object x.\n\t *\n\t * @param tr the transition matrix\n\t * @param a the set of states labeled with a\n\t * @param x the value vector\n\t */\n\tprotected StateValues computeRestrictedNext(JDDNode tr, JDDNode a, StateValues x)\n\t{\n\t\tJDDNode tmp;\n\t\tStateValuesMTBDD probs = null;\n\n\t\t// ensure that values are given in MTBDD format\n\t\tStateValuesMTBDD ddX = x.convertToStateValuesMTBDD();\n\n\t\ttmp = ddX.getJDDNode();\n\t\tJDD.Ref(tmp);\n\t\ttmp = JDD.PermuteVariables(tmp, allDDRowVars, allDDColVars);\n\t\tJDD.Ref(tr);\n\t\ttmp = JDD.MatrixMultiply(tr, tmp, allDDColVars, JDD.BOULDER);\n\n\t\t// label is 0/1 BDD, MIN sets all values to 0 for states not in a\n\t\tJDD.Ref(a);\n\t\ttmp = JDD.Apply(JDD.MIN, tmp, a);\n\n\t\tddX.clear();\n\t\tprobs = new StateValuesMTBDD(tmp, model);\n\t\tprobs.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\treturn probs;\n\t}\n\n\t// compute probabilities for bounded until\n\n\tprotected StateValues computeBoundedUntilProbs(JDDNode tr, JDDNode tr01, JDDNode b1, JDDNode b2, int time) throws PrismException\n\t{\n\t\tJDDNode yes, no, maybe;\n\t\tJDDNode probsMTBDD;\n\t\tDoubleVector probsDV;\n\t\tStateValues probs = null;\n\n\t\t// compute yes/no/maybe states\n\t\tif (b2.equals(JDD.ZERO)) {\n\t\t\tyes = JDD.Constant(0);\n\t\t\tJDD.Ref(reach);\n\t\t\tno = reach;\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else if (b1.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(b2);\n\t\t\tyes = b2;\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(b2);\n\t\t\tno = JDD.And(reach, JDD.Not(b2));\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else {\n\t\t\t// yes\n\t\t\tJDD.Ref(b2);\n\t\t\tyes = b2;\n\t\t\t// no\n\t\t\tif (yes.equals(reach)) {\n\t\t\t\tno = JDD.Constant(0);\n\t\t\t} else if (precomp && prob0) {\n\t\t\t\tno = PrismMTBDD.Prob0(tr01, reach, allDDRowVars, allDDColVars, b1, yes);\n\t\t\t} else {\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tJDD.Ref(b1);\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\tno = JDD.And(reach, JDD.Not(JDD.Or(b1, b2)));\n\t\t\t}\n\t\t\t// maybe\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(yes);\n\t\t\tJDD.Ref(no);\n\t\t\tmaybe = JDD.And(reach, JDD.Not(JDD.Or(yes, no)));\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\nyes = \" + JDD.GetNumMintermsString(yes, allDDRowVars.n()));\n\t\tmainLog.print(\", no = \" + JDD.GetNumMintermsString(no, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\t// if maybe is empty, we have the probabilities already\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(yes);\n\t\t\tprobs = new StateValuesMTBDD(yes, model);\n\t\t\tprobs.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise explicitly compute the remaining probabilities\n\t\telse {\n\t\t\t// compute probabilities\n\t\t\tmainLog.println(\"\\nComputing probabilities...\");\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\tprobsMTBDD = PrismMTBDD.ProbBoundedUntil(tr, odd, allDDRowVars, allDDColVars, yes, maybe, time);\n\t\t\t\t\tprobs = new StateValuesMTBDD(probsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\tprobsDV = PrismSparse.ProbBoundedUntil(tr, odd, allDDRowVars, allDDColVars, yes, maybe, time);\n\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tprobsDV = PrismHybrid.ProbBoundedUntil(tr, odd, allDDRowVars, allDDColVars, yes, maybe, time);\n\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t\t// Set accuracy info\n\t\t\t\tprobs.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(yes);\n\t\t\t\tJDD.Deref(no);\n\t\t\t\tJDD.Deref(maybe);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(yes);\n\t\tJDD.Deref(no);\n\t\tJDD.Deref(maybe);\n\n\t\treturn probs;\n\t}\n\n\t// compute probabilities for until (for qualitative properties)\n\n\tprotected StateValues computeUntilProbsQual(JDDNode tr01, JDDNode b1, JDDNode b2)\n\t{\n\t\tJDDNode yes, no, maybe;\n\t\tStateValues probs = null;\n\n\t\t// note: we know precomputation is enabled else this function wouldn't\n\t\t// have been called\n\n\t\t// compute yes/no/maybe states\n\t\tif (b2.equals(JDD.ZERO)) {\n\t\t\tyes = JDD.Constant(0);\n\t\t\tJDD.Ref(reach);\n\t\t\tno = reach;\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else if (b1.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(b2);\n\t\t\tyes = b2;\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(b2);\n\t\t\tno = JDD.And(reach, JDD.Not(b2));\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else {\n\t\t\t// no/yes\n\t\t\tno = PrismMTBDD.Prob0(tr01, reach, allDDRowVars, allDDColVars, b1, b2);\n\t\t\tyes = PrismMTBDD.Prob1(tr01, reach, allDDRowVars, allDDColVars, b1, b2, no);\n\t\t\t// maybe\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(yes);\n\t\t\tJDD.Ref(no);\n\t\t\tmaybe = JDD.And(reach, JDD.Not(JDD.Or(yes, no)));\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\nyes = \" + JDD.GetNumMintermsString(yes, allDDRowVars.n()));\n\t\tmainLog.print(\", no = \" + JDD.GetNumMintermsString(no, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\t// if maybe is empty, we have the probabilities already\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(yes);\n\t\t\tprobs = new StateValuesMTBDD(yes, model);\n\t\t}\n\t\t// otherwise we set the probabilities for maybe states to be 0.5\n\t\t// (actual probabilities for these states are unknown but definitely >0\n\t\t// and <1)\n\t\t// (this is safe because the results of this function will only be used\n\t\t// to compare against 0/1 bounds)\n\t\t// (this is not entirely elegant but is simpler and less error prone\n\t\t// than\n\t\t// trying to work out whether to use 0/1 for all case of future/global, etc.)\n\t\telse {\n\t\t\tJDD.Ref(yes);\n\t\t\tJDD.Ref(maybe);\n\t\t\tprobs = new StateValuesMTBDD(JDD.Apply(JDD.PLUS, yes, JDD.Apply(JDD.TIMES, maybe, JDD.Constant(0.5))), model);\n\t\t\t// No accuracy info, but should end up as a Boolean, not numerical, value anyway \n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(yes);\n\t\tJDD.Deref(no);\n\t\tJDD.Deref(maybe);\n\n\t\treturn probs;\n\t}\n\n\t// compute probabilities for until (general case)\n\n\tprotected StateValues computeUntilProbs(JDDNode tr, JDDNode tr01, JDDNode b1, JDDNode b2) throws PrismException\n\t{\n\t\tJDDNode yes, no, maybe;\n\t\tJDDNode probsMTBDD;\n\t\tDoubleVector probsDV;\n\t\tStateValues probs = null;\n\n\t\t// If required, export info about target states \n\t\tif (prism.getExportTarget()) {\n\t\t\tJDDNode labels[] = { model.getStart(), b2 };\n\t\t\tString labelNames[] = { \"init\", \"target\" };\n\t\t\ttry {\n\t\t\t\tmainLog.println(\"\\nExporting target states info to file \\\"\" + prism.getExportTargetFilename() + \"\\\"...\");\n\t\t\t\tPrismMTBDD.ExportLabels(labels, labelNames, \"l\", model.getAllDDRowVars(), model.getODD(), Prism.EXPORT_PLAIN, prism.getExportTargetFilename());\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tmainLog.printWarning(\"Could not export target to file \\\"\" + prism.getExportTargetFilename() + \"\\\"\");\n\t\t\t}\n\t\t}\n\n\t\tif (doIntervalIteration && !(precomp && prob0 && prob1)) {\n\t\t\tthrow new PrismNotSupportedException(\"Need precomputation for interval iteration, computing Until probabilities in DTMC\");\n\t\t}\n\n\t\t// compute yes/no/maybe states\n\t\tif (b2.equals(JDD.ZERO)) {\n\t\t\tyes = JDD.Constant(0);\n\t\t\tJDD.Ref(reach);\n\t\t\tno = reach;\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else if (b1.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(b2);\n\t\t\tyes = b2;\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(b2);\n\t\t\tno = JDD.And(reach, JDD.Not(b2));\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else {\n\t\t\t// no/yes\n\t\t\tif (precomp && (prob0 || prob1)) {\n\t\t\t\tno = PrismMTBDD.Prob0(tr01, reach, allDDRowVars, allDDColVars, b1, b2);\n\t\t\t} else {\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tJDD.Ref(b1);\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\tno = JDD.And(reach, JDD.Not(JDD.Or(b1, b2)));\n\t\t\t}\n\t\t\tif (precomp && prob1) {\n\t\t\t\tyes = PrismMTBDD.Prob1(tr01, reach, allDDRowVars, allDDColVars, b1, b2, no);\n\t\t\t} else {\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\tyes = b2;\n\t\t\t}\n\t\t\t// maybe\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(yes);\n\t\t\tJDD.Ref(no);\n\t\t\tmaybe = JDD.And(reach, JDD.Not(JDD.Or(yes, no)));\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\nyes = \" + JDD.GetNumMintermsString(yes, allDDRowVars.n()));\n\t\tmainLog.print(\", no = \" + JDD.GetNumMintermsString(no, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\t// if maybe is empty, we have the probabilities already\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\t// we make sure to return a vector of the appropriate type\n\t\t\t// (doublevector for hybrid/sparse, mtbdd for mtbdd)\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\tJDD.Ref(yes);\n\t\t\t\tprobs = new StateValuesMTBDD(yes, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\tcase Prism.HYBRID:\n\t\t\t\tprobs = new StateValuesDV(yes, model);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t// Set accuracy info\n\t\t\tprobs.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise we compute the actual probabilities\n\t\telse {\n\t\t\t// compute probabilities\n\t\t\tmainLog.println(\"\\nComputing remaining probabilities...\");\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\tprobsMTBDD = PrismMTBDD.ProbUntilInterval(tr, odd, allDDRowVars, allDDColVars, yes, maybe, prism.getIntervalIterationFlags());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tprobsMTBDD = PrismMTBDD.ProbUntil(tr, odd, allDDRowVars, allDDColVars, yes, maybe);\n\t\t\t\t\t}\n\t\t\t\t\tprobs = new StateValuesMTBDD(probsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\tprobsDV = PrismSparse.ProbUntilInterval(tr, odd, allDDRowVars, allDDColVars, yes, maybe, prism.getIntervalIterationFlags());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tprobsDV = PrismSparse.ProbUntil(tr, odd, allDDRowVars, allDDColVars, yes, maybe);\n\t\t\t\t\t}\n\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\tprobsDV = PrismHybrid.ProbUntilInterval(tr, odd, allDDRowVars, allDDColVars, yes, maybe, prism.getIntervalIterationFlags());\n\t\t\t\t\t} else {\n\t\t\t\t\t\tprobsDV = PrismHybrid.ProbUntil(tr, odd, allDDRowVars, allDDColVars, yes, maybe);\n\t\t\t\t\t}\n\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t\t// Set accuracy info\n\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\tprobs.setAccuracy(AccuracyFactory.guaranteedNumericalIterative(PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t\t} else {\n\t\t\t\t\tprobs.setAccuracy(AccuracyFactory.valueIteration(PrismNative.getTermCritParam(), PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(yes);\n\t\t\t\tJDD.Deref(no);\n\t\t\t\tJDD.Deref(maybe);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(yes);\n\t\tJDD.Deref(no);\n\t\tJDD.Deref(maybe);\n\n\t\treturn probs;\n\t}\n\n\t// compute cumulative rewards\n\n\tprotected StateValues computeCumulRewards(JDDNode tr, JDDNode tr01, JDDNode sr, JDDNode trr, int time) throws PrismException\n\t{\n\t\tJDDNode rewardsMTBDD;\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\n\t\t// compute rewards\n\t\tmainLog.println(\"\\nComputing rewards...\");\n\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\ttry {\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\trewardsMTBDD = PrismMTBDD.ProbCumulReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\trewards = new StateValuesMTBDD(rewardsMTBDD, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\t\trewardsDV = PrismSparse.ProbCumulReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.HYBRID:\n\t\t\t\trewardsDV = PrismHybrid.ProbCumulReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t}\n\t\t\t// Set accuracy info\n\t\t\trewards.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\t} catch (PrismException e) {\n\t\t\tthrow e;\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t// compute total rewards\n\n\tprotected StateValues computeTotalRewards(JDDNode tr, JDDNode tr01, JDDNode sr, JDDNode trr) throws PrismException\n\t{\n\t\tJDDNode rewardsMTBDD;\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\t\t// BSCC stuff\n\t\tList<JDDNode> bsccs = null;\n\t\tJDDNode notInBSCCs = null;\n\t\tint numBSCCs = 0;\n\n\t\tif (doIntervalIteration) {\n\t\t\tthrow new PrismNotSupportedException(\"Interval iteration for total rewards is currently not supported\");\n\t\t}\n\n\t\t// Compute bottom strongly connected components (BSCCs)\n\t\tSCCComputer sccComputer = prism.getSCCComputer(model);\n\t\tsccComputer.computeBSCCs();\n\t\tbsccs = sccComputer.getBSCCs();\n\t\tnotInBSCCs = sccComputer.getNotInBSCCs();\n\t\tnumBSCCs = bsccs.size();\n\n\t\t// Find BSCCs with non-zero reward\n\t\tJDD.Ref(sr);\n\t\tJDDNode srNonZero = JDD.GreaterThan(sr, 0);\n\t\tJDD.Ref(trr);\n\t\tJDDNode trrNonZero = JDD.GreaterThan(trr, 0);\n\t\tJDDNode bsccsNonZero = JDD.Constant(0);\n\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\tif (JDD.AreIntersecting(bsccs.get(b), srNonZero) || JDD.AreIntersecting(bsccs.get(b), trrNonZero)) {\n\t\t\t\tJDD.Ref(bsccs.get(b));\n\t\t\t\tbsccsNonZero = JDD.Or(bsccsNonZero, bsccs.get(b));\n\t\t\t}\n\t\t}\n\t\tJDD.Deref(srNonZero);\n\t\tJDD.Deref(trrNonZero);\n\t\tmainLog.print(\"States in non-zero reward BSCCs: \" + JDD.GetNumMintermsString(bsccsNonZero, allDDRowVars.n()));\n\n\t\t// Find states with infinite reward (those reach a non-zero reward BSCC with prob > 0)  \n\t\tJDDNode inf = PrismMTBDD.Prob0(tr01, reach, allDDRowVars, allDDColVars, reach, bsccsNonZero);\n\t\tinf = JDD.And(reach.copy(), JDD.Not(inf));\n\t\tJDDNode maybe = JDD.And(reach.copy(), JDD.Not(inf.copy()));\n\t\tJDD.Deref(bsccsNonZero);\n\n\t\t// Print out inf/maybe\n\t\tmainLog.print(\"\\ninf = \" + JDD.GetNumMintermsString(inf, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\t// If maybe is empty, we have the rewards already\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(inf);\n\t\t\trewards = new StateValuesMTBDD(JDD.ITE(inf, JDD.PlusInfinity(), JDD.Constant(0)), model);\n\t\t\trewards.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// Otherwise we compute the actual rewards\n\t\telse {\n\t\t\t// Compute the rewards\n\t\t\t// (do this using the functions for \"reward reachability\" properties but with no targets)\n\t\t\tmainLog.println(\"\\nComputing remaining rewards...\");\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\trewardsMTBDD = PrismMTBDD.ProbReachReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, JDD.ZERO, inf, maybe);\n\t\t\t\t\trewards = new StateValuesMTBDD(rewardsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\trewardsDV = PrismSparse.ProbReachReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, JDD.ZERO, inf, maybe);\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\trewardsDV = PrismHybrid.ProbReachReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, JDD.ZERO, inf, maybe);\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(inf);\n\t\t\t\tJDD.Deref(maybe);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t\t// Set accuracy info\n\t\t\trewards.setAccuracy(AccuracyFactory.valueIteration(PrismNative.getTermCritParam(), PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t}\n\n\t\t// Tidy up\n\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\tif (bsccs.get(b) != null)\n\t\t\t\tJDD.Deref(bsccs.get(b));\n\t\t}\n\t\tif (start != notInBSCCs)\n\t\t\tJDD.Deref(notInBSCCs);\n\t\tJDD.Deref(inf);\n\t\tJDD.Deref(maybe);\n\n\t\treturn rewards;\n\t}\n\n\t// compute rewards for inst reward\n\n\tprotected StateValues computeInstRewards(JDDNode tr, JDDNode sr, int time) throws PrismException\n\t{\n\t\tJDDNode rewardsMTBDD;\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\n\t\t// a trivial case: \"=0\"\n\t\tif (time == 0) {\n\t\t\tJDD.Ref(sr);\n\t\t\trewards = new StateValuesMTBDD(sr, model);\n\t\t\trewards.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise we compute the actual rewards\n\t\telse {\n\t\t\t// compute the rewards\n\t\t\tmainLog.println(\"\\nComputing rewards...\");\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\trewardsMTBDD = PrismMTBDD.ProbInstReward(tr, sr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\t\trewards = new StateValuesMTBDD(rewardsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\trewardsDV = PrismSparse.ProbInstReward(tr, sr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\trewardsDV = PrismHybrid.ProbInstReward(tr, sr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t\t// Set accuracy info\n\t\t\trewards.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward, method determined by setting.\n\t * Works for both DTMCs and MDPs.\n\t * @param tr the transition relation\n\t * @param stateRewards the state rewards\n\t * @param transRewards the trans rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @return upper bound on R=?[ F target ] for all states\n\t */\n\tprotected static double computeReachRewardsUpperBound(PrismComponent parent, Model model, JDDNode tr, JDDNode stateRewards, JDDNode transRewards, JDDNode target, JDDNode maybe) throws PrismException\n\t{\n\t\tdouble upperBound = Double.POSITIVE_INFINITY;\n\t\tString method = null;\n\t\tswitch (OptionsIntervalIteration.from(parent).getBoundMethod()) {\n\t\tcase VARIANT_1_COARSE:\n\t\t\tupperBound = computeReachRewardsUpperBoundVariant1Coarse(parent, model, tr, stateRewards, transRewards, target, maybe);\n\t\t\tmethod = \"variant 1, coarse\";\n\t\t\tbreak;\n\t\tcase VARIANT_1_FINE:\n\t\t\tupperBound = computeReachRewardsUpperBoundVariant1Fine(parent, model, tr, stateRewards, transRewards, target, maybe);\n\t\t\tmethod = \"variant 1, fine\";\n\t\t\tbreak;\n\t\tcase VARIANT_2:\n\t\tcase DEFAULT:\n\t\t\tupperBound = computeReachRewardsUpperBoundVariant2(parent, model, tr, stateRewards, transRewards, target, maybe);\n\t\t\tmethod = \"variant 2\";\n\t\t\tbreak;\n\t\tcase DSMPI:\n\t\t\tthrow new PrismNotSupportedException(\"Upper bound heuristic Dijkstra Sweep MPI currently not supported for symbolic engines\");\n\t\t}\n\n\t\tif (method == null) {\n\t\t\tthrow new PrismException(\"Unsupported upper bound heuristic\");\n\t\t}\n\n\t\tparent.getLog().print(\"Upper bound for \");\n\t\tif (model.getModelType() == ModelType.MDP)\n\t\t\tparent.getLog().print(\"max \");\n\t\tparent.getLog().println(\"expectation (\" + method + \"): \" + upperBound);\n\n\t\tif (!Double.isFinite(upperBound)) {\n\t\t\tthrow new PrismException(\"Problem computing an upper bound for the expectation, did not get finite result. Perhaps choose a different method using -intervaliterboundmethod\");\n\t\t}\n\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 1, coarse),\n\t * i.e., does not compute separate q_t / p_t per SCC.\n\t * Works for both DTMCs and MDPs.\n\t * Uses Rs = S, i.e., does not take reachability into account.\n\t * @param tr the transition relation\n\t * @param stateRewards the state rewards\n\t * @param transRewards the trans rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @return upper bound on R=?[ F target ] / Rmax=?[ F target ] for all states\n\t */\n\tprotected static double computeReachRewardsUpperBoundVariant1Coarse(PrismComponent parent, Model model, JDDNode tr, JDDNode stateRewards, JDDNode transRewards, JDDNode target, JDDNode maybe) throws PrismException\n\t{\n\t\tJDDNode boundsOnExpectedVisits;\n\t\tJDDNode Ct = JDD.Constant(0);\n\n\t\tassert(model.getModelType() == ModelType.DTMC || model.getModelType() == ModelType.MDP);\n\n\t\tStopWatch timer = new StopWatch(parent.getLog());\n\t\ttimer.start(\"computing an upper bound for expected reward\");\n\n\t\tSCCComputer sccs = SCCComputer.createSCCComputer(parent, model);\n\t\tsccs.computeSCCs(maybe); // only do SCC computation in maybe states\n\t\tJDDNode inSCC = JDD.Constant(0.0);\n\n\t\tJDDNode tr01 = JDD.GreaterThan(tr.copy(), 0.0);\n\n\t\tdouble q = 0;\n\t\tfor (JDDNode scc : sccs.getSCCs()) {\n\t\t\t// StateValuesMTBDD.print(parent.getLog(), scc.copy(), model, \"scc\");\n\t\t\tdouble cardinality = JDD.GetNumMinterms(scc, model.getNumDDRowVars());\n\t\t\t// parent.getLog().println(\"cardinality = \" + cardinality);\n\t\t\tCt = JDD.ITE(scc.copy(), JDD.Constant(cardinality), Ct);\n\t\t\t// StateValuesMTBDD.print(parent.getLog(), Ct.copy(), model, \"Ct\");\n\n\t\t\tdouble probRemain = 0;\n\t\t\tJDDNode sccCol = JDD.PermuteVariables(scc.copy(), model.getAllDDRowVars(), model.getAllDDColVars());\n\t\t\tJDDNode tr01FromSCC = JDD.And(tr01.copy(), scc.copy());\n\t\t\tJDDNode tr01SomeLeaveSCC = JDD.And(tr01FromSCC, JDD.Not(sccCol.copy()));\n\t\t\ttr01SomeLeaveSCC = JDD.ThereExists(tr01SomeLeaveSCC, model.getAllDDColVars());\n\n\t\t\tJDDNode transRemainInScc = JDD.Times(tr.copy(), scc.copy(), sccCol);\n\t\t\ttransRemainInScc = JDD.Times(transRemainInScc, tr01SomeLeaveSCC);\n\t\t\tJDDNode ddProbRemain = JDD.SumAbstract(transRemainInScc, model.getAllDDColVars());\n\t\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\t\tddProbRemain = JDD.MaxAbstract(ddProbRemain, ((NondetModel)model).getAllDDNondetVars());\n\t\t\t}\n\t\t\t// StateValuesMTBDD.print(parent.getLog(), ddProbRemain.copy(), model, \"ddProbRemain\");\n\t\t\tprobRemain = JDD.FindMax(ddProbRemain);\n\t\t\tJDD.Deref(ddProbRemain);\n\n\t\t\t// parent.getLog().println(\"probRemain = \" + probRemain);\n\t\t\tq = Math.max(q, probRemain);\n\t\t\t// parent.getLog().println(\"q = \" + q);\n\n\t\t\tinSCC = JDD.Or(inSCC, scc);\n\t\t}\n\n\t\tdouble p = JDD.FindMinPositive(tr);\n\n\t\tJDDNode trivial = sccs.getNotInSCCs();\n\t\ttrivial = JDD.And(trivial, maybe.copy());\n\n//\t\tboundsOnExpectedVisits[s] = 1 / (Math.pow(p, Ct[s]-1) * (1.0-q));\n\t\tJDDNode Ct_minus_1 = JDD.Apply(JDD.MINUS, Ct.copy(), JDD.Constant(1.0));\n\t\t// StateValuesMTBDD.print(parent.getLog(), Ct_minus_1.copy(), model, \"|Ct|-1\");\n\t\tJDDNode bound = JDD.Apply(JDD.POW, JDD.Constant(p), Ct_minus_1);\n\t\t// StateValuesMTBDD.print(parent.getLog(), bound.copy(), model, \"bound (1)\");\n\t\tbound = JDD.Times(bound, JDD.Constant(1.0 - q));\n\t\t// StateValuesMTBDD.print(parent.getLog(), bound.copy(), model, \"bound (2)\");\n\t\tbound = JDD.Apply(JDD.DIVIDE, JDD.Constant(1.0), bound);\n\t\t// StateValuesMTBDD.print(parent.getLog(), bound.copy(), model, \"bound (3)\");\n\t\tboundsOnExpectedVisits = JDD.Times(maybe.copy(), bound);\n\t\t// StateValuesMTBDD.print(parent.getLog(), boundsOnExpectedVisits.copy(), model, \"bound (4)\");\n\n\t\t// trivial SCC states: seen at most once\n\t\tboundsOnExpectedVisits = JDD.ITE(trivial, JDD.Constant(1.0), boundsOnExpectedVisits);\n\n\t\t// target: counted at most zero times\n\t\tboundsOnExpectedVisits = JDD.ITE(target.copy(), JDD.Constant(0.0), boundsOnExpectedVisits);\n\n\t\tJDDNode transRewardsUsed = JDD.Times(tr01.copy(), transRewards.copy());\n\t\tJDDNode maxRew = JDD.MaxAbstract(transRewardsUsed, model.getAllDDColVars());\n\t\tmaxRew = JDD.Apply(JDD.PLUS, maxRew, stateRewards.copy());\n\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\tmaxRew = JDD.MaxAbstract(maxRew, ((NondetModel)model).getAllDDNondetVars());\n\t\t}\n\t\tJDDNode expReward = JDD.Times(maxRew, boundsOnExpectedVisits.copy());\n\t\tJDDNode ddUpperBound = JDD.SumAbstract(expReward, model.getAllDDRowVars());\n\t\tdouble upperBound = ddUpperBound.getValue();\n\t\tJDD.Deref(ddUpperBound);\n\n\t\ttimer.stop();\n\n\t\tif (OptionsIntervalIteration.from(parent).isBoundComputationVerbose()) {\n\t\t\tparent.getLog().println(\"Upper bound for max expectation computation (variant 1, coarse):\");\n\t\t\tparent.getLog().println(\"p = \" + p);\n\t\t\tparent.getLog().println(\"q = \" + q);\n\t\t\tStateValuesMTBDD.print(parent.getLog(), Ct.copy(), model, \"|Ct|\");\n\t\t\tStateValuesMTBDD.print(parent.getLog(), boundsOnExpectedVisits.copy(), model, \"ζ*\");\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(tr01);\n\t\tJDD.Deref(inSCC);\n\t\tJDD.Deref(boundsOnExpectedVisits);\n\t\tJDD.Deref(Ct);\n\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 1, fine),\n\t * Works for both DTMCs and MDPs.\n\t * Uses Rs = S, i.e., does not take reachability into account.\n\t * @param tr the transition relation\n\t * @param stateRewards the state rewards\n\t * @param transRewards the trans rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @return upper bound on R=?[ F target ] / Rmax=?[ F target ] for all states\n\t */\n\tprotected static double computeReachRewardsUpperBoundVariant1Fine(PrismComponent parent, Model model, JDDNode tr, JDDNode stateRewards, JDDNode transRewards, JDDNode target, JDDNode maybe) throws PrismException\n\t{\n\t\tJDDNode boundsOnExpectedVisits;\n\t\tJDDNode Ct = JDD.Constant(0);\n\t\tJDDNode pt = JDD.Constant(0), qt = JDD.Constant(0.0);\n\n\t\tassert(model.getModelType() == ModelType.DTMC || model.getModelType() == ModelType.MDP);\n\n\t\tStopWatch timer = new StopWatch(parent.getLog());\n\t\ttimer.start(\"computing an upper bound for expected reward\");\n\n\t\tSCCComputer sccs = SCCComputer.createSCCComputer(parent, model);\n\t\tsccs.computeSCCs(maybe); // only do SCC computation in maybe states\n\t\tJDDNode inSCC = JDD.Constant(0.0);\n\n\t\tJDDNode tr01 = JDD.GreaterThan(tr.copy(), 0.0);\n\n\t\tfor (JDDNode scc : sccs.getSCCs()) {\n\t\t\t// StateValuesMTBDD.print(parent.getLog(), scc.copy(), model, \"scc\");\n\t\t\tdouble cardinality = JDD.GetNumMinterms(scc, model.getNumDDRowVars());\n\t\t\t// parent.getLog().println(\"cardinality = \" + cardinality);\n\t\t\tCt = JDD.ITE(scc.copy(), JDD.Constant(cardinality), Ct);\n\t\t\t// StateValuesMTBDD.print(parent.getLog(), Ct.copy(), model, \"Ct\");\n\n\t\t\tdouble probRemain = 0;\n\t\t\tJDDNode sccCol = JDD.PermuteVariables(scc.copy(), model.getAllDDRowVars(), model.getAllDDColVars());\n\t\t\tJDDNode tr01FromSCC = JDD.And(tr01.copy(), scc.copy());\n\t\t\tJDDNode tr01SomeLeaveSCC = JDD.And(tr01FromSCC, JDD.Not(sccCol.copy()));\n\t\t\ttr01SomeLeaveSCC = JDD.ThereExists(tr01SomeLeaveSCC, model.getAllDDColVars());\n\n\t\t\tJDDNode transRemainInScc = JDD.Times(tr.copy(), scc.copy(), sccCol);\n\t\t\tdouble ptInSCC = JDD.FindMinPositive(transRemainInScc);\n\t\t\tpt = JDD.ITE(scc.copy(), JDD.Constant(ptInSCC), pt);\n\t\t\ttransRemainInScc = JDD.Times(transRemainInScc, tr01SomeLeaveSCC);\n\t\t\tJDDNode ddProbRemain = JDD.SumAbstract(transRemainInScc, model.getAllDDColVars());\n\t\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\t\tddProbRemain = JDD.MaxAbstract(ddProbRemain, ((NondetModel)model).getAllDDNondetVars());\n\t\t\t}\n\t\t\t// StateValuesMTBDD.print(parent.getLog(), ddProbRemain.copy(), model, \"ddProbRemain\");\n\t\t\tprobRemain = JDD.FindMax(ddProbRemain);\n\t\t\tJDD.Deref(ddProbRemain);\n\n\t\t\t// parent.getLog().println(\"probRemain = \" + probRemain);\n\t\t\tqt = JDD.ITE(scc.copy(), JDD.Constant(probRemain), qt);\n\n\t\t\tinSCC = JDD.Or(inSCC, scc);\n\t\t}\n\n\t\tJDDNode trivial = sccs.getNotInSCCs();\n\t\ttrivial = JDD.And(trivial, maybe.copy());\n\n\t\t// boundsOnExpectedVisits[s] = 1 / (Math.pow(p, Ct[s]-1) * (1.0-qt));\n\t\tJDDNode Ct_minus_1 = JDD.Apply(JDD.MINUS, Ct.copy(), JDD.Constant(1.0));\n\t\t// StateValuesMTBDD.print(parent.getLog(), Ct_minus_1.copy(), model, \"|Ct|-1\");\n\t\tJDDNode bound = JDD.Apply(JDD.POW, pt.copy(), Ct_minus_1);\n\t\t// StateValuesMTBDD.print(parent.getLog(), bound.copy(), model, \"bound (1)\");\n\t\tbound = JDD.Times(bound, JDD.Apply(JDD.MINUS, JDD.Constant(1.0), qt.copy()));\n\t\t// StateValuesMTBDD.print(parent.getLog(), bound.copy(), model, \"bound (2)\");\n\t\tbound = JDD.Apply(JDD.DIVIDE, JDD.Constant(1.0), bound);\n\t\t// StateValuesMTBDD.print(parent.getLog(), bound.copy(), model, \"bound (3)\");\n\t\tboundsOnExpectedVisits = JDD.Times(maybe.copy(), bound);\n\t\t// StateValuesMTBDD.print(parent.getLog(), boundsOnExpectedVisits.copy(), model, \"bound (4)\");\n\n\t\t// trivial SCC states: seen at most once\n\t\tboundsOnExpectedVisits = JDD.ITE(trivial, JDD.Constant(1.0), boundsOnExpectedVisits);\n\n\t\t// target: counted at most zero times\n\t\tboundsOnExpectedVisits = JDD.ITE(target.copy(), JDD.Constant(0.0), boundsOnExpectedVisits);\n\n\t\tJDDNode transRewardsUsed = JDD.Times(tr01.copy(), transRewards.copy());\n\t\tJDDNode maxRew = JDD.MaxAbstract(transRewardsUsed, model.getAllDDColVars());\n\t\tmaxRew = JDD.Apply(JDD.PLUS, maxRew, stateRewards.copy());\n\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\tmaxRew = JDD.MaxAbstract(maxRew, ((NondetModel)model).getAllDDNondetVars());\n\t\t}\n\t\tJDDNode expReward = JDD.Times(maxRew, boundsOnExpectedVisits.copy());\n\t\tJDDNode ddUpperBound = JDD.SumAbstract(expReward, model.getAllDDRowVars());\n\t\tdouble upperBound = ddUpperBound.getValue();\n\t\tJDD.Deref(ddUpperBound);\n\n\t\ttimer.stop();\n\n\t\tif (OptionsIntervalIteration.from(parent).isBoundComputationVerbose()) {\n\t\t\tparent.getLog().println(\"Upper bound for max expectation computation (variant 1, fine):\");\n\t\t\tStateValuesMTBDD.print(parent.getLog(), pt.copy(), model, \"pt\");\n\t\t\tStateValuesMTBDD.print(parent.getLog(), qt.copy(), model, \"qt\");\n\t\t\tStateValuesMTBDD.print(parent.getLog(), Ct.copy(), model, \"|Ct|\");\n\t\t\tStateValuesMTBDD.print(parent.getLog(), boundsOnExpectedVisits.copy(), model, \"ζ*\");\n\t\t}\n\n\n\t\t// derefs\n\t\tJDD.Deref(tr01);\n\t\tJDD.Deref(inSCC);\n\t\tJDD.Deref(boundsOnExpectedVisits);\n\t\tJDD.Deref(Ct);\n\t\tJDD.Deref(qt);\n\t\tJDD.Deref(pt);\n\n\t\treturn upperBound;\n\t}\n\n\t/**\n\t * Compute upper bound for maximum expected reward (variant 2),\n\t * Works for both DTMCs and MDPs.\n\t * @param tr the transition relation\n\t * @param stateRewards the state rewards\n\t * @param transRewards the trans rewards\n\t * @param target the target states\n\t * @param unknown the states that are not target or infinity states\n\t * @return upper bound on R=?[ F target ] / Rmax=?[ F target ] for all states\n\t */\n\tprotected static double computeReachRewardsUpperBoundVariant2(PrismComponent parent, Model model, JDDNode tr, JDDNode stateRewards, JDDNode transRewards, JDDNode target, JDDNode maybe) throws PrismException\n\t{\n\t\tJDDNode boundsOnExpectedVisits;\n\n\t\tassert(model.getModelType() == ModelType.DTMC || model.getModelType() == ModelType.MDP);\n\n\t\tStopWatch timer = new StopWatch(parent.getLog());\n\t\ttimer.start(\"computing an upper bound for expected reward\");\n\n\t\tSCCComputer sccs = SCCComputer.createSCCComputer(parent, model);\n\t\tsccs.computeSCCs(maybe); // only do SCC computation in maybe states\n\n\t\tJDDNode tr01 = JDD.GreaterThan(tr.copy(), 0.0);\n\n\t\tJDDNode sameSCC = JDD.Constant(0.0);\n\n\t\tfor (JDDNode scc : sccs.getSCCs()) {\n\t\t\t// StateValuesMTBDD.print(parent.getLog(), scc.copy(), model, \"scc\");\n\t\t\tJDDNode sccCol = JDD.PermuteVariables(scc.copy(), model.getAllDDRowVars(), model.getAllDDColVars());\n\t\t\tJDDNode inThisSameSCC = JDD.And(scc.copy(), sccCol);\n\t\t\tsameSCC = JDD.Or(sameSCC, inThisSameSCC);\n\n\t\t\tJDD.Deref(scc);\n\t\t}\n\n\t\t// d_t = 1 for all target states\n\t\tJDDNode dt = target.copy();\n\n\t\tJDDNode T = target.copy();\n\t\tJDDNode tr01FromMaybe = JDD.And(tr01.copy(), maybe.copy());\n\t\tJDDNode remain = maybe.copy();\n\t\twhile (!remain.equals(JDD.ZERO)) {\n\t\t\t// compute S_i\n\t\t\tJDDNode Tcol = JDD.PermuteVariables(T.copy(), model.getAllDDRowVars(), model.getAllDDColVars());\n\t\t\tJDDNode intoT = JDD.And(tr01FromMaybe.copy(), Tcol);\n\t\t\tintoT = JDD.ThereExists(intoT, model.getAllDDColVars());\n\n\t\t\t// S_i = all actions have at probability > 0 to reach T\n\t\t\tJDDNode S_i;\n\t\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\t\tJDDNode tmp = JDD.Max(intoT, ((NondetModel)model).getNondetMask().copy());\n\t\t\t\tS_i = JDD.ForAll(tmp, ((NondetModel)model).getAllDDNondetVars());\n\t\t\t} else {\n\t\t\t\tS_i = intoT;\n\t\t\t}\n\n\t\t\t// compute dt for the S_i states\n\t\t\t// tmp = tr restricted to \"from S_i\" and to \"T_{i-1}\"\n\t\t\tJDDNode tmp = JDD.Times(tr.copy(), S_i.copy(), JDD.PermuteVariables(T.copy(), model.getAllDDRowVars(), model.getAllDDColVars()));\n\n\t\t\tJDDNode sameSCC_S_i = JDD.And(S_i.copy(), sameSCC.copy());\n\t\t\tJDDNode du = JDD.PermuteVariables(dt.copy(), model.getAllDDRowVars(), model.getAllDDColVars());\n\t\t\tJDDNode dtu = JDD.ITE(sameSCC_S_i, du, JDD.Constant(1.0));\n\t\t\ttmp = JDD.Times(tmp, dtu);\n\t\t\ttmp = JDD.SumAbstract(tmp, model.getAllDDColVars());\n\t\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\t\ttmp = JDD.Max(tmp, ((NondetModel)model).getNondetMask().copy());\n\t\t\t\ttmp = JDD.MinAbstract(tmp, ((NondetModel)model).getAllDDNondetVars());\n\t\t\t}\n\n\t\t\tdt = JDD.ITE(S_i.copy(), tmp, dt);\n\n\t\t\t// remove S_i from remain\n\t\t\tremain = JDD.And(remain, JDD.Not(S_i.copy()));\n\t\t\ttr01FromMaybe = JDD.And(tr01FromMaybe, JDD.Not(S_i.copy()));\n\t\t\tT = JDD.Or(T, S_i);\n\t\t}\n\t\tJDD.Deref(remain);\n\t\tJDD.Deref(tr01FromMaybe);\n\t\tJDD.Deref(T);\n\n\t\tJDDNode trivial = sccs.getNotInSCCs();\n\t\ttrivial = JDD.And(trivial, maybe.copy());\n\n\t\t// boundsOnExpectedVisits[s] = 1 / dt\n\t\tboundsOnExpectedVisits = JDD.Apply(JDD.DIVIDE, JDD.Constant(1.0), dt.copy());\n\t\t// StateValuesMTBDD.print(parent.getLog(), bound.copy(), model, \"bound (3)\");\n\t\tboundsOnExpectedVisits = JDD.Times(maybe.copy(), boundsOnExpectedVisits);\n\t\t// StateValuesMTBDD.print(parent.getLog(), boundsOnExpectedVisits.copy(), model, \"bound (4)\");\n\n\t\t// trivial SCC states: seen at most once\n\t\tboundsOnExpectedVisits = JDD.ITE(trivial, JDD.Constant(1.0), boundsOnExpectedVisits);\n\n\t\t// target: counted at most zero times\n\t\tboundsOnExpectedVisits = JDD.ITE(target.copy(), JDD.Constant(0.0), boundsOnExpectedVisits);\n\n\t\tJDDNode transRewardsUsed = JDD.Times(model.getTrans01().copy(), transRewards.copy());\n\t\tJDDNode maxRew = JDD.MaxAbstract(transRewardsUsed, model.getAllDDColVars());\n\t\tmaxRew = JDD.Apply(JDD.PLUS, maxRew, stateRewards.copy());\n\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\tmaxRew = JDD.MaxAbstract(maxRew, ((NondetModel)model).getAllDDNondetVars());\n\t\t}\n\t\tJDDNode expReward = JDD.Times(maxRew, boundsOnExpectedVisits.copy());\n\t\tJDDNode ddUpperBound = JDD.SumAbstract(expReward, model.getAllDDRowVars());\n\t\tdouble upperBound = ddUpperBound.getValue();\n\t\tJDD.Deref(ddUpperBound);\n\n\t\ttimer.stop();\n\n\t\tif (OptionsIntervalIteration.from(parent).isBoundComputationVerbose()) {\n\t\t\tparent.getLog().println(\"Upper bound for max expectation computation (variant 1, fine):\");\n\t\t\tStateValuesMTBDD.print(parent.getLog(), dt.copy(), model, \"dt\");\n\t\t\tStateValuesMTBDD.print(parent.getLog(), boundsOnExpectedVisits.copy(), model, \"ζ*\");\n\t\t}\n\n\n\t\t// derefs\n\t\tJDD.Deref(tr01);\n\t\tJDD.Deref(boundsOnExpectedVisits);\n\t\tJDD.Deref(dt);\n\t\tJDD.Deref(sameSCC);\n\n\t\treturn upperBound;\n\t}\n\n\t// compute rewards for reach reward\n\n\tprotected StateValues computeReachRewards(JDDNode tr, JDDNode tr01, JDDNode sr, JDDNode trr, JDDNode b) throws PrismException\n\t{\n\t\tJDDNode inf, maybe;\n\t\tJDDNode rewardsMTBDD;\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\n\t\t// compute states which can't reach goal with probability 1\n\t\tif (b.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(reach);\n\t\t\tinf = reach;\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else if (b.equals(reach)) {\n\t\t\tinf = JDD.Constant(0);\n\t\t\tmaybe = JDD.Constant(0);\n\t\t} else {\n\t\t\tJDDNode no = PrismMTBDD.Prob0(tr01, reach, allDDRowVars, allDDColVars, reach, b);\n\t\t\tJDDNode prob1 = PrismMTBDD.Prob1(tr01, reach, allDDRowVars, allDDColVars, reach, b, no);\n\t\t\tJDD.Deref(no);\n\t\t\tJDD.Ref(reach);\n\t\t\tinf = JDD.And(reach, JDD.Not(prob1));\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(inf);\n\t\t\tJDD.Ref(b);\n\t\t\tmaybe = JDD.And(reach, JDD.Not(JDD.Or(inf, b)));\n\t\t}\n\n\t\t// print out yes/no/maybe\n\t\tmainLog.print(\"\\ngoal = \" + JDD.GetNumMintermsString(b, allDDRowVars.n()));\n\t\tmainLog.print(\", inf = \" + JDD.GetNumMintermsString(inf, allDDRowVars.n()));\n\t\tmainLog.print(\", maybe = \" + JDD.GetNumMintermsString(maybe, allDDRowVars.n()) + \"\\n\");\n\n\t\tJDDNode lower = null;\n\t\tJDDNode upper = null;\n\n\t\t// if maybe is empty, we have the rewards already\n\t\tif (maybe.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(inf);\n\t\t\trewards = new StateValuesMTBDD(JDD.ITE(inf, JDD.PlusInfinity(), JDD.Constant(0)), model);\n\t\t\trewards.setAccuracy(AccuracyFactory.doublesFromQualitative());\n\t\t}\n\t\t// otherwise we compute the actual rewards\n\t\telse {\n\t\t\t// compute the rewards\n\n\t\t\tif (doIntervalIteration) {\n\t\t\t\tOptionsIntervalIteration iiOptions = OptionsIntervalIteration.from(this);\n\n\t\t\t\tdouble upperBound;\n\t\t\t\tif (iiOptions.hasManualUpperBound()) {\n\t\t\t\t\tupperBound = iiOptions.getManualUpperBound();\n\t\t\t\t\tgetLog().printWarning(\"Upper bound for interval iteration manually set to \" + upperBound);\n\t\t\t\t} else {\n\t\t\t\t\tupperBound = computeReachRewardsUpperBound(this, model, tr, sr, trr, b, maybe);\n\t\t\t\t}\n\t\t\t\tupper = JDD.ITE(maybe.copy(), JDD.Constant(upperBound), JDD.Constant(0));\n\n\t\t\t\tdouble lowerBound;\n\t\t\t\tif (iiOptions.hasManualLowerBound()) {\n\t\t\t\t\tlowerBound = iiOptions.getManualLowerBound();\n\t\t\t\t\tgetLog().printWarning(\"Lower bound for interval iteration manually set to \" + lowerBound);\n\t\t\t\t} else {\n\t\t\t\t\tlowerBound = 0.0;\n\t\t\t\t}\n\t\t\t\tlower = JDD.ITE(maybe.copy(), JDD.Constant(lowerBound), JDD.Constant(0));\n\t\t\t}\n\n\t\t\tmainLog.println(\"\\nComputing remaining rewards...\");\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\trewardsMTBDD = PrismMTBDD.ProbReachRewardInterval(tr, sr, trr, odd, allDDRowVars, allDDColVars, b, inf, maybe, lower, upper, prism.getIntervalIterationFlags());\n\t\t\t\t\t} else {\n\t\t\t\t\t\trewardsMTBDD = PrismMTBDD.ProbReachReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, b, inf, maybe);\n\t\t\t\t\t}\n\t\t\t\t\trewards = new StateValuesMTBDD(rewardsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\trewardsDV = PrismSparse.ProbReachRewardInterval(tr, sr, trr, odd, allDDRowVars, allDDColVars, b, inf, maybe, lower, upper, prism.getIntervalIterationFlags());\n\t\t\t\t\t} else {\n\t\t\t\t\t\trewardsDV = PrismSparse.ProbReachReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, b, inf, maybe);\n\t\t\t\t\t}\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\t\trewardsDV = PrismHybrid.ProbReachRewardInterval(tr, sr, trr, odd, allDDRowVars, allDDColVars, b, inf, maybe, lower, upper, prism.getIntervalIterationFlags());\n\t\t\t\t\t} else {\n\t\t\t\t\t\trewardsDV = PrismHybrid.ProbReachReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, b, inf, maybe);\n\t\t\t\t\t}\n\t\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tdefault:\n\t\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t\t}\n\t\t\t\t// Set accuracy info\n\t\t\t\tif (doIntervalIteration) {\n\t\t\t\t\trewards.setAccuracy(AccuracyFactory.guaranteedNumericalIterative(PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t\t} else {\n\t\t\t\t\trewards.setAccuracy(AccuracyFactory.valueIteration(PrismNative.getTermCritParam(), PrismNative.getLastErrorBound(), PrismNative.getTermCrit() == Prism.ABSOLUTE));\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\tJDD.Deref(inf);\n\t\t\t\tJDD.Deref(maybe);\n\t\t\t\tif (lower != null) JDD.Deref(lower);\n\t\t\t\tif (upper != null) JDD.Deref(upper);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\tif (doIntervalIteration) {\n\t\t\tdouble max_v = rewards.maxFiniteOverBDD(maybe);\n\t\t\tif (max_v != Double.NEGATIVE_INFINITY) {\n\t\t\t\tmainLog.println(\"Maximum finite value in solution vector at end of interval iteration: \" + max_v);\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(inf);\n\t\tJDD.Deref(maybe);\n\t\tif (lower != null) JDD.Deref(lower);\n\t\tif (upper != null) JDD.Deref(upper);\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute steady-state probability distribution (forwards).\n\t * Use the passed in vector initDist as the initial probability distribution (time 0).\n\t * The type of this should match the current engine\n\t * (i.e. StateValuesMTBDD for MTBDD, StateValuesDV for sparse/hybrid). \n\t * For reasons of efficiency, this vector will be trampled over and\n\t * then deleted afterwards, so if you wanted it, take a copy. \n\t * @param tr The transition probability matrix for the DTMC\n\t * @param initDist Initial distribution (will be overwritten)\n\t */\n\tpublic StateValues computeSteadyStateProbs(JDDNode tr, StateValues initDist) throws PrismException\n\t{\n\t\t// BSCC stuff\n\t\tList<JDDNode> bsccs = null;\n\t\tJDDNode notInBSCCs = null;\n\t\t// MTBDD stuff\n\t\tJDDNode start = null, bscc;\n\t\t// Other stuff\n\t\tStateValues probs = null, solnProbs = null;\n\t\tdouble probBSCCs[];\n\t\tint numBSCCs = 0, allInOneBSCC = -1;\n\n\t\ttry {\n\n\t\t\t// Compute bottom strongly connected components (BSCCs)\n\t\t\tif (bsccComp) {\n\t\t\t\tSCCComputer sccComputer = prism.getSCCComputer(model);\n\t\t\t\tsccComputer.computeBSCCs();\n\t\t\t\tbsccs = sccComputer.getBSCCs();\n\t\t\t\tnotInBSCCs = sccComputer.getNotInBSCCs();\n\t\t\t\tnumBSCCs = bsccs.size();\n\t\t\t}\n\t\t\t// Unless we've been told to skip it\n\t\t\telse {\n\t\t\t\tmainLog.println(\"\\nSkipping BSCC computation...\");\n\t\t\t\tbsccs = new Vector<JDDNode>();\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tbsccs.add(reach);\n\t\t\t\tnotInBSCCs = JDD.Constant(0);\n\t\t\t\tnumBSCCs = 1;\n\t\t\t}\n\n\t\t\t// See which states in the initial distribution have non-zero prob\n\t\t\tstart = initDist.getBDDFromInterval(\">\", 0);\n\t\t\t// Determine whether initial states are all in a single BSCC \n\t\t\tallInOneBSCC = -1;\n\t\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t\tif (JDD.IsContainedIn(start, bsccs.get(b))) {\n\t\t\t\t\tallInOneBSCC = b;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// If all initial states are in a single BSCC, it's easy...\n\t\t\t// Just compute steady-state probabilities for the BSCC\n\t\t\tif (allInOneBSCC != -1) {\n\t\t\t\tmainLog.println(\"\\nInitial states all in one BSCC (so no reachability probabilities computed)\");\n\t\t\t\tbscc = bsccs.get(allInOneBSCC);\n\t\t\t\tsolnProbs = computeSteadyStateProbsForBSCC(trans, bscc);\n\t\t\t}\n\n\t\t\t// Otherwise, have to consider all the BSCCs\n\t\t\telse {\n\n\t\t\t\t// Initialise total probabilities vector\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\tsolnProbs = new StateValuesMTBDD(JDD.Constant(0), model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\tsolnProbs = new StateValuesDV(new DoubleVector(model.getNumStates()), model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tsolnProbs = new StateValuesDV(new DoubleVector(model.getNumStates()), model);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\n\t\t\t\t// Compute probability of reaching each BSCC from initial distribution \n\t\t\t\tprobBSCCs = new double[numBSCCs];\n\t\t\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t\t\tmainLog.println(\"\\nComputing probability of reaching BSCC \" + (b + 1));\n\t\t\t\t\tbscc = bsccs.get(b);\n\t\t\t\t\t// Compute probabilities\n\t\t\t\t\tprobs = computeUntilProbs(trans, trans01, notInBSCCs, bscc);\n\t\t\t\t\t// Compute probability of reaching BSCC, which is dot product of\n\t\t\t\t\t// vectors for initial distribution and probabilities of reaching it\n\t\t\t\t\tprobBSCCs[b] = probs.dotProduct(initDist);\n\t\t\t\t\tmainLog.print(\"\\nProbability of reaching BSCC \" + (b + 1) + \": \" + probBSCCs[b] + \"\\n\");\n\t\t\t\t\t// Free vector\n\t\t\t\t\tprobs.clear();\n\t\t\t\t}\n\n\t\t\t\t// Compute steady-state probs for each BSCC\n\t\t\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t\t\tmainLog.println(\"\\nComputing steady-state probabilities for BSCC \" + (b + 1));\n\t\t\t\t\tbscc = bsccs.get(b);\n\t\t\t\t\t// Compute steady-state probabilities for the BSCC\n\t\t\t\t\tprobs = computeSteadyStateProbsForBSCC(trans, bscc);\n\t\t\t\t\t// Print out probabilities\n\t\t\t\t\tif (verbose) {\n\t\t\t\t\t\tmainLog.print(\"\\nBSCC \" + (b + 1) + \" Steady-State Probabilities: \\n\");\n\t\t\t\t\t\tprobs.print(mainLog);\n\t\t\t\t\t}\n\t\t\t\t\t// Multiply by BSCC reach prob, add to total\n\t\t\t\t\tprobs.timesConstant(probBSCCs[b]);\n\t\t\t\t\tsolnProbs.add(probs);\n\t\t\t\t\t// Free vector\n\t\t\t\t\tprobs.clear();\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\t// Tidy up and pass on the exception\n\t\t\tif (start != null)\n\t\t\t\tJDD.Deref(start);\n\t\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\t\tif (bsccs.get(b) != null)\n\t\t\t\t\tJDD.Deref(bsccs.get(b));\n\t\t\t}\n\t\t\tif (start != notInBSCCs)\n\t\t\t\tJDD.Deref(notInBSCCs);\n\t\t\tif (solnProbs != null)\n\t\t\t\tsolnProbs.clear();\n\t\t\tif (initDist != null)\n\t\t\t\tinitDist.clear();\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Tidy up\n\t\tif (start != null)\n\t\t\tJDD.Deref(start);\n\t\tfor (int b = 0; b < numBSCCs; b++) {\n\t\t\tif (bsccs.get(b) != null)\n\t\t\t\tJDD.Deref(bsccs.get(b));\n\t\t}\n\t\tif (start != notInBSCCs)\n\t\t\tJDD.Deref(notInBSCCs);\n\t\tif (initDist != null)\n\t\t\tinitDist.clear();\n\n\t\treturn solnProbs;\n\t}\n\n\t/**\n\t * Compute steady-state probabilities for a BSCC\n\t * i.e. compute the long-run probability of being in each state of the BSCC.\n\t * No initial distribution is specified since it does not affect the result.\n\t * The result will be stored in a full vector whose size equals the number of states in the DTMC.\n\t * @param tr The transition probability matrix for the whole DTMC\n\t * @param bscc The BSCC to be analysed\n\t */\n\tprotected StateValues computeSteadyStateProbsForBSCC(JDDNode tr, JDDNode bscc) throws PrismException\n\t{\n\t\tJDDNode trf, init;\n\t\tint n;\n\t\tJDDNode probsMTBDD;\n\t\tDoubleVector probsDV;\n\t\tStateValues probs = null;\n\n\t\t// work out number of states in the BSCC\n\t\tif (bscc.equals(reach)) {\n\t\t\t// avoid a call to GetNumMinterms in this simple (and common) case\n\t\t\tn = model.getNumStates();\n\t\t} else {\n\t\t\tn = (int) Math.round(JDD.GetNumMinterms(bscc, allDDRowVars.n()));\n\t\t}\n\n\t\t// special case: 1 state BSCC (in fact, we *need* to check for this\n\t\t// special case because the general  solution work breaks)\n\t\tif (n == 1) {\n\t\t\t// answer is trivially one in the single state\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\tJDD.Ref(bscc);\n\t\t\t\treturn new StateValuesMTBDD(bscc, model);\n\t\t\tcase Prism.SPARSE:\n\t\t\t\treturn new StateValuesDV(bscc, model);\n\t\t\tcase Prism.HYBRID:\n\t\t\t\treturn new StateValuesDV(bscc, model);\n\t\t\t}\n\t\t}\n\n\t\t// filter out unwanted states from transition matrix\n\t\tJDD.Ref(tr);\n\t\tJDD.Ref(bscc);\n\t\ttrf = JDD.Apply(JDD.TIMES, tr, bscc);\n\t\tJDD.Ref(bscc);\n\t\ttrf = JDD.Apply(JDD.TIMES, trf, JDD.PermuteVariables(bscc, allDDRowVars, allDDColVars));\n\n\t\t// compute initial solution (equiprobable)\n\t\tJDD.Ref(bscc);\n\t\tinit = JDD.Apply(JDD.DIVIDE, bscc, JDD.Constant(n));\n\n\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\tString filename = ExportIterations.getUniqueFilename(\"iterations-ss-bscc\");\n\t\t\tPrismNative.setDefaultExportIterationsFilename(filename);\n\t\t}\n\n\t\t// compute remaining probabilities\n\t\tmainLog.println(\"\\nComputing probabilities...\");\n\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\ttry {\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\tprobsMTBDD = PrismMTBDD.StochSteadyState(trf, odd, init, allDDRowVars, allDDColVars);\n\t\t\t\tprobs = new StateValuesMTBDD(probsMTBDD, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\t\tprobsDV = PrismSparse.StochSteadyState(trf, odd, init, allDDRowVars, allDDColVars);\n\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.HYBRID:\n\t\t\t\tprobsDV = PrismHybrid.StochSteadyState(trf, odd, init, allDDRowVars, allDDColVars);\n\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(trf);\n\t\t\tJDD.Deref(init);\n\t\t\tthrow e;\n\t\t} finally {\n\t\t\tif (settings.getBoolean(PrismSettings.PRISM_EXPORT_ITERATIONS)) {\n\t\t\t\tPrismNative.setDefaultExportIterationsFilename(ExportIterations.getDefaultFilename());\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(trf);\n\t\tJDD.Deref(init);\n\n\t\treturn probs;\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Use the passed in vector initDist as the initial probability distribution (time 0).\n\t * The type of this should match the current engine\n\t * (i.e. StateValuesMTBDD for MTBDD, StateValuesDV for sparse/hybrid). \n\t * For reasons of efficiency, this vector will be trampled over and\n\t * then deleted afterwards, so if you wanted it, take a copy. \n\t * @param tr The transition probability matrix for the DTMC\n\t * @param initDist Initial distribution (will be overwritten)\n\t * @param time Time step\n\t */\n\tprotected StateValues computeTransientProbs(JDDNode tr, StateValues initDist, int time) throws PrismException\n\t{\n\t\tJDDNode probsMTBDD;\n\t\tDoubleVector probsDV;\n\t\tStateValues probs = null;\n\n\t\t// special case: time = 0\n\t\tif (time == 0) {\n\t\t\t// we are allowed to keep the init vector, so no need to clone\n\t\t\treturn initDist;\n\t\t}\n\n\t\t// general case\n\t\tmainLog.println(\"\\nComputing probabilities...\");\n\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\ttry {\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\tprobsMTBDD = PrismMTBDD.ProbTransient(tr, odd, ((StateValuesMTBDD) initDist).getJDDNode(), allDDRowVars, allDDColVars, time);\n\t\t\t\tprobs = new StateValuesMTBDD(probsMTBDD, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\t\tprobsDV = PrismSparse.ProbTransient(tr, odd, ((StateValuesDV) initDist).getDoubleVector(), allDDRowVars, allDDColVars, time);\n\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.HYBRID:\n\t\t\t\tprobsDV = PrismHybrid.ProbTransient(tr, odd, ((StateValuesDV) initDist).getDoubleVector(), allDDRowVars, allDDColVars, time);\n\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t}\n\t\t\t// Set accuracy info\n\t\t\tprobs.setAccuracy(AccuracyFactory.boundedNumericalIterations());\n\t\t} catch (PrismException e) {\n\t\t\tthrow e;\n\t\t}\n\n\t\treturn probs;\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/comp/SCCComputer.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Carlos S. Bederian (Universidad Nacional de Cordoba)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.util.List;\nimport java.util.Vector;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.Prism;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismSettings;\nimport symbolic.model.Model;\n\n/**\n * Abstract class for (symbolic) classes that compute (B)SCCs,\n * i.e. (bottom) strongly connected components, for a model's transition graph.\n */\npublic abstract class SCCComputer extends PrismComponent\n{\n\t// model info\n\tprotected JDDNode trans01;\n\tprotected JDDNode reach;\n\tprotected JDDVars allDDRowVars;\n\tprotected JDDVars allDDColVars;\n\n\t// stuff for SCCs\n\tprotected Vector<JDDNode> sccs;\n\tprotected JDDNode notInSCCs;\n\tprotected JDDNode trivialSCCs;\n\t// stuff for BSCCs\n\tprotected Vector<JDDNode> bsccs;\n\tprotected JDDNode notInBSCCs;\n\n\t/**\n\t * Static method to create a new SCCComputer object, depending on current settings.\n\t */\n\tpublic static SCCComputer createSCCComputer(PrismComponent parent, Model model) throws PrismException\n\t{\n\t\treturn createSCCComputer(parent, model.getReach(), model.getTransReln(), model.getAllDDRowVars(), model.getAllDDColVars());\n\t}\n\n\t/**\n\t * Static method to create a new SCCComputer object, depending on current settings.\n\t */\n\tpublic static SCCComputer createSCCComputer(PrismComponent parent, JDDNode reach, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars)\n\t\t\tthrows PrismException\n\t{\n\t\treturn createSCCComputer(parent, parent.getSettings().getChoice(PrismSettings.PRISM_SCC_METHOD), reach, trans01, allDDRowVars, allDDColVars);\n\t}\n\n\t/**\n\t * Static method to create a new SCCComputer object, depending on requested method.\n\t */\n\tpublic static SCCComputer createSCCComputer(PrismComponent parent, int sccMethod, JDDNode reach, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars)\n\t\t\tthrows PrismException\n\t{\n\t\tSCCComputer sccComputer;\n\t\tswitch (sccMethod) {\n\t\tcase Prism.LOCKSTEP:\n\t\t\tsccComputer = new SCCComputerLockstep(parent, reach, trans01, allDDRowVars, allDDColVars);\n\t\t\tbreak;\n\t\tcase Prism.SCCFIND:\n\t\t\tsccComputer = new SCCComputerSCCFind(parent, reach, trans01, allDDRowVars, allDDColVars);\n\t\t\tbreak;\n\t\tcase Prism.XIEBEEREL:\n\t\t\tsccComputer = new SCCComputerXB(parent, reach, trans01, allDDRowVars, allDDColVars);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tsccComputer = new SCCComputerLockstep(parent, reach, trans01, allDDRowVars, allDDColVars);\n\t\t}\n\t\treturn sccComputer;\n\t}\n\n\t/**\n\t * Base constructor.\n\t */\n\tpublic SCCComputer(PrismComponent parent, JDDNode reach, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars) throws PrismException\n\t{\n\t\tsuper(parent);\n\t\tthis.trans01 = trans01;\n\t\tthis.reach = reach;\n\t\tthis.allDDRowVars = allDDRowVars;\n\t\tthis.allDDColVars = allDDColVars;\n\n\t\tif (jdd.SanityJDD.enabled) {\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(trans01, allDDRowVars, allDDColVars);\n\t\t\tjdd.SanityJDD.checkIsDDOverVars(reach, allDDRowVars);\n\t\t}\n\t}\n\n\t/**\n\t * Compute (non-trivial) strongly connected components (SCCs) and store them.\n\t * They should be retrieved using {@link #getSCCs()}.\n\t * States in trivial SCCs (those comprising a single state without a self-loop) are also stored.\n\t * They should be retrieved using {@link #getNotInSCCs()}.\n\t * You will need to to deref all of these afterwards.\n\t */\n\tpublic abstract void computeSCCs() throws PrismException;\n\n\t/**\n\t * Compute (non-trivial) strongly connected components (SCCs) containing a state from {@code filter} and store them.\n\t * They should be retrieved using {@link #getSCCs()}.\n\t * States in trivial SCCs (those comprising a single state without a self-loop) are also stored.\n\t * They should be retrieved using {@link #getNotInSCCs()}.\n\t * You will need to to deref all of these afterwards.\n\t */\n\tpublic abstract void computeSCCs(JDDNode filter) throws PrismException;\n\n\t/**\n\t * Get the list of computed (non-trivial) SCCs.\n\t * You need to deref these BDDs when you are finished with them.\n\t */\n\tpublic List<JDDNode> getSCCs()\n\t{\n\t\treturn sccs;\n\t}\n\n\t/**\n\t * Get the states not in any (non-trivial) SCC.\n\t * In other words, this is all states in trivial SCCs (those comprising a single state without a self-loop).\n\t * You need to deref this BDD when you are finished with it.\n\t */\n\tpublic JDDNode getNotInSCCs()\n\t{\n\t\treturn notInSCCs;\n\t}\n\n\t/**\n\t * Get the list of computed BSCCs.\n\t * You need to deref these BDDs when you are finished with them.\n\t */\n\tpublic List<JDDNode> getBSCCs()\n\t{\n\t\treturn bsccs;\n\t}\n\n\t/**\n\t * Get the states not in any BSCC.\n\t * You need to deref this BDDs when you are finished with it.\n\t */\n\tpublic JDDNode getNotInBSCCs()\n\t{\n\t\treturn notInBSCCs;\n\t}\n\n\t/**\n\t * Compute bottom strongly connected components (BSCCs) and store them.\n\t * They should be retrieved using {@link #getBSCCs()}.\n\t * States that are not in any BSCC are also stored.\n\t * They should be retrieved using {@link #getNotInBSCCs()}.\n\t * You will need to to deref all of these afterwards.\n\t */\n\tpublic void computeBSCCs() throws PrismException\n\t{\n\t\tJDDNode scc, out;\n\t\tint i, n;\n\n\t\t// First compute SCCs\n\t\tcomputeSCCs();\n\n\t\t// Now check which ones are BSCCs and keep them\n\t\tbsccs = new Vector<JDDNode>();\n\t\tnotInBSCCs = notInSCCs;\n\t\tn = sccs.size();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tscc = sccs.elementAt(i);\n\t\t\tJDD.Ref(trans01);\n\t\t\tJDD.Ref(scc);\n\t\t\tout = JDD.And(trans01, scc);\n\t\t\tJDD.Ref(scc);\n\t\t\tout = JDD.And(out, JDD.Not(JDD.PermuteVariables(scc, allDDRowVars, allDDColVars)));\n\t\t\tif (out.equals(JDD.ZERO)) {\n\t\t\t\tbsccs.addElement(scc);\n\t\t\t} else {\n\t\t\t\tJDD.Ref(scc);\n\t\t\t\tnotInBSCCs = JDD.Or(scc, notInBSCCs);\n\t\t\t\tJDD.Deref(scc);\n\t\t\t}\n\t\t\tJDD.Deref(out);\n\t\t}\n\n\t\t// Print out some info\n\t\tmainLog.print(\"\\nSCCs: \" + sccs.size()); // Note: the BDDs in sccs have been derefed but the array still exists\n\t\tmainLog.print(\", BSCCs: \" + bsccs.size());\n\t\tmainLog.println(\", non-BSCC states: \" + JDD.GetNumMintermsString(notInBSCCs, allDDRowVars.n()));\n\n\t\tboolean verbose = getSettings().getBoolean(PrismSettings.PRISM_VERBOSE);\n\t\tif (!verbose && bsccs.size() > 10) {\n\t\t\tmainLog.print(\"BSCC sizes: More than 10 BSCCs, use verbose mode to view sizes for all.\\n\");\n\t\t} else {\n\t\t\tmainLog.print(\"BSCC sizes:\");\n\t\t\tfor (i = 0; i < bsccs.size(); i++) {\n\t\t\t\tmainLog.print(\" \" + (i + 1) + \":\" + JDD.GetNumMintermsString(bsccs.elementAt(i), allDDRowVars.n()));\n\t\t\t}\n\t\t\tmainLog.println();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/comp/SCCComputerLockstep.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Carlos S. Bederian (Universidad Nacional de Cordoba)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.util.Stack;\nimport java.util.Vector;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport symbolic.comp.SCCComputer;\n\n/**\n * SCC (strongly connected component) decomposition using lockstep search with trimming\n * (from Bloem/Gabow/Somenzi 2000)\n */\npublic class SCCComputerLockstep extends SCCComputer\n{\n\tprivate class DecompTask\n\t{\n\t\tJDDNode _nodes;\n\t\tJDDNode _edges;\n\n\t\tDecompTask(JDDNode nodes, JDDNode edges)\n\t\t{\n\t\t\t_nodes = nodes;\n\t\t\t_edges = edges;\n\t\t}\n\n\t\tJDDNode getNodes()\n\t\t{\n\t\t\treturn _nodes;\n\t\t}\n\n\t\tJDDNode getEdges()\n\t\t{\n\t\t\treturn _edges;\n\t\t}\n\t}\n\n\tprivate JDDNode allSCCs;\n\tprivate Stack<DecompTask> tasks;\n\n\t/**\n\t * Build (B)SCC computer for a given model.\n\t */\n\tpublic SCCComputerLockstep(PrismComponent parent, JDDNode reach, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars) throws PrismException\n\t{\n\t\tsuper(parent, reach, trans01, allDDRowVars, allDDColVars);\n\t}\n\n\t// Methods for SCCComputer\n\n\t@Override\n\tpublic void computeSCCs()\n\t{\n\t\tsccs = new Vector<JDDNode>();\n\t\tallSCCs = JDD.Constant(0);\n\t\ttasks = new Stack<DecompTask>();\n\t\tJDD.Ref(reach);\n\t\tJDD.Ref(trans01);\n\t\ttasks.push(new DecompTask(reach, trans01));\n\t\twhile (!tasks.isEmpty()) {\n\t\t\tlockstep(tasks.pop());\n\t\t}\n\t\tJDD.Ref(reach);\n\t\tnotInSCCs = JDD.And(reach, JDD.Not(allSCCs));\n\t}\n\n\t@Override\n\tpublic void computeSCCs(JDDNode filter)\n\t{\n\t\t//computeSCCs();\n\t\tsccs = new Vector<JDDNode>();\n\t\tallSCCs = JDD.Constant(0);\n\t\ttasks = new Stack<DecompTask>();\n\t\tJDD.Ref(reach);\n\t\tJDD.Ref(trans01);\n\t\ttasks.push(new DecompTask(reach, trans01));\n\t\twhile (!tasks.isEmpty()) {\n\t\t\tlockstep(tasks.pop(), filter);\n\t\t}\n\t\tJDD.Ref(reach);\n\t\tnotInSCCs = JDD.And(reach, JDD.Not(allSCCs));\n\t}\n\n\t// Computation\n\n\t// Return the image of nodes in edges\n\t// Refs: result\n\t// Derefs: edges, nodes\n\tprivate JDDNode image(JDDNode nodes, JDDNode edges)\n\t{\n\t\tJDDNode tmp;\n\n\t\t// Get transitions that start at nodes\n\t\ttmp = JDD.Apply(JDD.TIMES, edges, nodes);\n\t\t// Get img(nodes)\n\t\ttmp = JDD.ThereExists(tmp, allDDRowVars);\n\t\ttmp = JDD.PermuteVariables(tmp, allDDColVars, allDDRowVars);\n\t\treturn tmp;\n\t}\n\n\t// Return the preimage of nodes in edges\n\t// Refs: result\n\t// Derefs: edges, nodes\n\tprivate JDDNode preimage(JDDNode nodes, JDDNode edges)\n\t{\n\t\tJDDNode tmp;\n\n\t\t// Get transitions that end at nodes\n\t\ttmp = JDD.PermuteVariables(nodes, allDDRowVars, allDDColVars);\n\t\ttmp = JDD.Apply(JDD.TIMES, edges, tmp);\n\t\t// Get pre(nodes)\n\t\ttmp = JDD.ThereExists(tmp, allDDColVars);\n\t\treturn tmp;\n\t}\n\n\t// Report a SCC found by lockstep\n\tprivate void report(JDDNode nodes)\n\t{\n\t\tif (nodes.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(nodes);\n\t\t\treturn;\n\t\t}\n\t\t// Sanity check, partitioning of the state space should prevent this\n\t\tassert !sccs.contains(nodes);\n\n\t\t/* if (prism.getVerbose()) {\n\t\t\tlog.println(\"Found SCC:\");\n\t\t\tJDD.PrintVector(nodes, rows);\n\t\t} */\n\t\tsccs.addElement(nodes);\n\t\tJDD.Ref(nodes);\n\t\tallSCCs = JDD.Or(allSCCs, nodes);\n\t}\n\n\t// Trim nodes that have no path to a node in a nontrivial SCC\n\t// or have no path from a node in a nontrivial SCC\n\t// Refs: result\n\t// Derefs: nodes, edges\n\tprivate JDDNode trim(JDDNode nodes, JDDNode edges)\n\t{\n\t\tJDDNode old;\n\t\tJDDNode current;\n\t\tJDDNode img;\n\t\tJDDNode pre;\n\t\t//int i = 1;\n\n\t\tJDD.Ref(nodes);\n\t\tcurrent = nodes;\n\t\tdo {\n\t\t\told = current;\n\t\t\tJDD.Ref(current);\n\t\t\tJDD.Ref(edges);\n\t\t\timg = image(current, edges);\n\t\t\tJDD.Ref(current);\n\t\t\tJDD.Ref(edges);\n\t\t\tpre = preimage(current, edges);\n\t\t\tcurrent = JDD.And(current, JDD.And(img, pre));\n\t\t\t/*if (prism.getVerbose()) {\n\t\t\t\tlog.println(\"Trimming pass \" + i + \":\");\n\t\t\t\tJDD.PrintVector(current, rows);\n\t\t\t\ti++;\n\t\t\t}*/\n\t\t} while (!current.equals(old));\n\t\tJDD.Deref(nodes);\n\t\tJDD.Deref(edges);\n\n\t\treturn current;\n\t}\n\n\t// Lockstep SCC decomposition with trimming from [BGS00]\n\t// Refs: reported result\n\t// Derefs: nodes and edges in the DecompTask\n\tprivate void lockstep(DecompTask task)\n\t{\n\n\t\tJDDNode nodes = task.getNodes();\n\t\tJDDNode edges = task.getEdges();\n\t\tJDDNode tmp;\n\n\t\tif (nodes.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(nodes);\n\t\t\tJDD.Deref(edges);\n\t\t\treturn;\n\t\t}\n\n\t\t/* if (prism.getVerbose()) {\n\t\t\tlog.println(\"Lockstep pass on nodes: \");\n\t\t\tJDD.PrintVector(nodes, rows);\n\t\t} */\n\n\t\t// trim nodes\n\t\tJDD.Ref(edges);\n\t\tnodes = trim(nodes, edges);\n\t\tJDD.Ref(nodes);\n\t\tedges = JDD.Apply(JDD.TIMES, edges, nodes);\n\t\tJDD.Ref(nodes);\n\t\tedges = JDD.Apply(JDD.TIMES, edges, JDD.PermuteVariables(nodes, allDDRowVars, allDDColVars));\n\n\t\t// pick a starting node\n\t\tJDD.Ref(nodes);\n\t\tJDDNode v = JDD.RestrictToFirst(nodes, allDDRowVars);\n\t\t// mainLog.println(\"Lockstep - picked node:\");\n\t\t// JDD.PrintVector(v, allDDRowVars);\n\n\t\tJDDNode f = v; // forward set of v\n\t\tJDDNode ffront = v; // last update to f\n\t\tJDD.Ref(f);\n\t\tJDD.Ref(ffront);\n\n\t\tJDDNode b = v; // backward set of v\n\t\tJDDNode bfront = v; // last update to b\n\t\tJDD.Ref(b);\n\t\tJDD.Ref(bfront);\n\n\t\tJDD.Deref(v);\n\n\t\t// Compute forward and backward sets in lockstep until either one converges\n\t\twhile (!ffront.equals(JDD.ZERO) && !bfront.equals(JDD.ZERO)) {\n\n\t\t\tJDD.Ref(edges);\n\t\t\t// Get the image of the last update\n\t\t\ttmp = image(ffront, edges);\n\t\t\t// find new states in this update\n\t\t\tJDD.Ref(f);\n\t\t\tffront = JDD.And(tmp, JDD.Not(f));\n\t\t\t// add states to the forward set\n\t\t\tJDD.Ref(ffront);\n\t\t\tf = JDD.Or(f, ffront);\n\n\t\t\tJDD.Ref(edges);\n\t\t\t// Get the preimage of the last update\n\t\t\ttmp = preimage(bfront, edges);\n\t\t\t// find new states in this update\n\t\t\tJDD.Ref(b);\n\t\t\tbfront = JDD.And(tmp, JDD.Not(b));\n\t\t\t// add states to the backward set\n\t\t\tJDD.Ref(bfront);\n\t\t\tb = JDD.Or(b, bfront);\n\t\t}\n\n\t\tJDDNode convergedSet; // set that converged first\n\t\tJDDNode sccUpdate; // update in the last approximation of the scc\n\n\t\t// if ffront is empty, the forward set converged first\n\t\tif (ffront.equals(JDD.ZERO)) {\n\t\t\tconvergedSet = f;\n\t\t\tJDD.Ref(convergedSet);\n\n\t\t\t// keep looking for states in the backward set until\n\t\t\t// its intersection with the forward set stops growing\n\t\t\tJDD.Ref(bfront);\n\t\t\tJDD.Ref(f);\n\t\t\tsccUpdate = JDD.And(bfront, f);\n\t\t\twhile (!sccUpdate.equals(JDD.ZERO)) {\n\t\t\t\tJDD.Deref(sccUpdate);\n\t\t\t\tJDD.Ref(edges);\n\t\t\t\tJDD.Ref(b);\n\t\t\t\tbfront = JDD.And(preimage(bfront, edges), JDD.Not(b));\n\t\t\t\tJDD.Ref(bfront);\n\t\t\t\tb = JDD.Or(bfront, b);\n\t\t\t\tJDD.Ref(f);\n\t\t\t\tJDD.Ref(bfront);\n\t\t\t\tsccUpdate = JDD.And(bfront, f);\n\t\t\t}\n\t\t}\n\n\t\t// bfront is empty, the backward set converged first\n\t\telse {\n\t\t\tconvergedSet = b;\n\t\t\tJDD.Ref(convergedSet);\n\n\t\t\t// keep looking for states in the backward set until\n\t\t\t// its intersection with the forward set stops growing\n\t\t\tJDD.Ref(ffront);\n\t\t\tJDD.Ref(b);\n\t\t\tsccUpdate = JDD.And(ffront, b);\n\t\t\twhile (!sccUpdate.equals(JDD.ZERO)) {\n\t\t\t\tJDD.Deref(sccUpdate);\n\t\t\t\tJDD.Ref(edges);\n\t\t\t\tJDD.Ref(f);\n\t\t\t\tffront = JDD.And(image(ffront, edges), JDD.Not(f));\n\t\t\t\tJDD.Ref(ffront);\n\t\t\t\tf = JDD.Or(ffront, f);\n\t\t\t\tJDD.Ref(b);\n\t\t\t\tJDD.Ref(ffront);\n\t\t\t\tsccUpdate = JDD.And(ffront, b);\n\t\t\t}\n\t\t}\n\t\tJDD.Deref(sccUpdate);\n\t\tJDD.Deref(ffront);\n\t\tJDD.Deref(bfront);\n\n\t\t// Found our SCC\n\t\tJDDNode scc = JDD.Apply(JDD.TIMES, f, b);\n\n\t\t// check if SCC is nontrivial and report\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.PermuteVariables(scc, allDDRowVars, allDDColVars);\n\t\tJDD.Ref(edges);\n\t\ttmp = JDD.And(tmp, edges);\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.And(tmp, scc);\n\t\tif (!tmp.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(scc);\n\t\t\treport(scc);\n\t\t}\n\t\tJDD.Deref(tmp);\n\n\t\t// FIXME: restricting newEdges isn't necessary, needs benchmarking\n\t\t//        (speed vs memory?)\n\t\t// newNodes1 = convergedSet \\ scc\n\t\t//JDD.Ref(scc);\n\t\tJDD.Ref(convergedSet);\n\t\tJDDNode newNodes1 = JDD.And(convergedSet, JDD.Not(scc));\n\t\t// newEdges1 = edges \\intersect (newNodes x newNodes^t)\n\t\tJDD.Ref(edges);\n\t\tJDD.Ref(newNodes1);\n\t\tJDDNode newEdges1 = JDD.Apply(JDD.TIMES, edges, newNodes1);\n\t\tJDD.Ref(newNodes1);\n\t\ttmp = JDD.PermuteVariables(newNodes1, allDDRowVars, allDDColVars);\n\t\tnewEdges1 = JDD.Apply(JDD.TIMES, newEdges1, tmp);\n\n\t\t// newNodes2 = nodes \\ convergedSet\n\t\t//JDD.Ref(nodes);\n\t\t//JDD.Ref(convergedSet);\n\t\tJDDNode newNodes2 = JDD.And(nodes, JDD.Not(convergedSet));\n\t\t// newEdges2 = edges \\intersect (newNodes x newNodes^t)\n\t\t//JDD.Ref(edges);\n\t\tJDD.Ref(newNodes2);\n\t\tJDDNode newEdges2 = JDD.Apply(JDD.TIMES, edges, newNodes2);\n\t\tJDD.Ref(newNodes2);\n\t\ttmp = JDD.PermuteVariables(newNodes2, allDDRowVars, allDDColVars);\n\t\tnewEdges2 = JDD.Apply(JDD.TIMES, newEdges2, tmp);\n\n\t\t// Queue new sets for search\n\t\ttasks.push(new DecompTask(newNodes2, newEdges2));\n\t\ttasks.push(new DecompTask(newNodes1, newEdges1));\n\n\t\t//JDD.Deref(scc);\n\t\t//JDD.Deref(convergedSet);\n\t\t//JDD.Deref(nodes);\n\t\t//JDD.Deref(edges);\n\t}\n\n\tprivate void lockstep(DecompTask task, JDDNode filter)\n\t{\n\n\t\tJDDNode nodes = task.getNodes();\n\t\tJDDNode edges = task.getEdges();\n\t\tJDDNode tmp;\n\n\t\tif (nodes.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(nodes);\n\t\t\tJDD.Deref(edges);\n\t\t\treturn;\n\t\t}\n\n\t\t/* if (prism.getVerbose()) {\n\t\t\tlog.println(\"Lockstep pass on nodes: \");\n\t\t\tJDD.PrintVector(nodes, rows);\n\t\t} */\n\n\t\t// trim nodes\n\t\tJDD.Ref(edges);\n\t\tnodes = trim(nodes, edges);\n\t\tJDD.Ref(nodes);\n\t\tedges = JDD.Apply(JDD.TIMES, edges, nodes);\n\t\tJDD.Ref(nodes);\n\t\tedges = JDD.Apply(JDD.TIMES, edges, JDD.PermuteVariables(nodes, allDDRowVars, allDDColVars));\n\n\t\t// pick a starting node\n\t\tJDD.Ref(nodes);\n\t\tJDDNode v = JDD.RestrictToFirst(nodes, allDDRowVars);\n\t\t// mainLog.println(\"Lockstep - picked node:\");\n\t\t// JDD.PrintVector(v, allDDRowVars);\n\n\t\tJDDNode f = v; // forward set of v\n\t\tJDDNode ffront = v; // last update to f\n\t\tJDD.Ref(f);\n\t\tJDD.Ref(ffront);\n\n\t\tJDDNode b = v; // backward set of v\n\t\tJDDNode bfront = v; // last update to b\n\t\tJDD.Ref(b);\n\t\tJDD.Ref(bfront);\n\n\t\tJDD.Deref(v);\n\n\t\t// Compute forward and backward sets in lockstep until either one converges\n\t\twhile (!ffront.equals(JDD.ZERO) && !bfront.equals(JDD.ZERO)) {\n\n\t\t\tJDD.Ref(edges);\n\t\t\t// Get the image of the last update\n\t\t\ttmp = image(ffront, edges);\n\t\t\t// find new states in this update\n\t\t\tJDD.Ref(f);\n\t\t\tffront = JDD.And(tmp, JDD.Not(f));\n\t\t\t// add states to the forward set\n\t\t\tJDD.Ref(ffront);\n\t\t\tf = JDD.Or(f, ffront);\n\n\t\t\tJDD.Ref(edges);\n\t\t\t// Get the preimage of the last update\n\t\t\ttmp = preimage(bfront, edges);\n\t\t\t// find new states in this update\n\t\t\tJDD.Ref(b);\n\t\t\tbfront = JDD.And(tmp, JDD.Not(b));\n\t\t\t// add states to the backward set\n\t\t\tJDD.Ref(bfront);\n\t\t\tb = JDD.Or(b, bfront);\n\t\t}\n\n\t\tJDDNode convergedSet; // set that converged first\n\t\tJDDNode sccUpdate; // update in the last approximation of the scc\n\n\t\t// if ffront is empty, the forward set converged first\n\t\tif (ffront.equals(JDD.ZERO)) {\n\t\t\tconvergedSet = f;\n\t\t\tJDD.Ref(convergedSet);\n\n\t\t\t// keep looking for states in the backward set until\n\t\t\t// its intersection with the forward set stops growing\n\t\t\tJDD.Ref(bfront);\n\t\t\tJDD.Ref(f);\n\t\t\tsccUpdate = JDD.And(bfront, f);\n\t\t\twhile (!sccUpdate.equals(JDD.ZERO)) {\n\t\t\t\tJDD.Deref(sccUpdate);\n\t\t\t\tJDD.Ref(edges);\n\t\t\t\tJDD.Ref(b);\n\t\t\t\tbfront = JDD.And(preimage(bfront, edges), JDD.Not(b));\n\t\t\t\tJDD.Ref(bfront);\n\t\t\t\tb = JDD.Or(bfront, b);\n\t\t\t\tJDD.Ref(f);\n\t\t\t\tJDD.Ref(bfront);\n\t\t\t\tsccUpdate = JDD.And(bfront, f);\n\t\t\t}\n\t\t}\n\n\t\t// bfront is empty, the backward set converged first\n\t\telse {\n\t\t\tconvergedSet = b;\n\t\t\tJDD.Ref(convergedSet);\n\n\t\t\t// keep looking for states in the backward set until\n\t\t\t// its intersection with the forward set stops growing\n\t\t\tJDD.Ref(ffront);\n\t\t\tJDD.Ref(b);\n\t\t\tsccUpdate = JDD.And(ffront, b);\n\t\t\twhile (!sccUpdate.equals(JDD.ZERO)) {\n\t\t\t\tJDD.Deref(sccUpdate);\n\t\t\t\tJDD.Ref(edges);\n\t\t\t\tJDD.Ref(f);\n\t\t\t\tffront = JDD.And(image(ffront, edges), JDD.Not(f));\n\t\t\t\tJDD.Ref(ffront);\n\t\t\t\tf = JDD.Or(ffront, f);\n\t\t\t\tJDD.Ref(b);\n\t\t\t\tJDD.Ref(ffront);\n\t\t\t\tsccUpdate = JDD.And(ffront, b);\n\t\t\t}\n\t\t}\n\t\tJDD.Deref(sccUpdate);\n\t\tJDD.Deref(ffront);\n\t\tJDD.Deref(bfront);\n\n\t\t// Found our SCC\n\t\tJDDNode scc = JDD.Apply(JDD.TIMES, f, b);\n\n\t\t// check if SCC is nontrivial and report\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.PermuteVariables(scc, allDDRowVars, allDDColVars);\n\t\tJDD.Ref(edges);\n\t\ttmp = JDD.And(tmp, edges);\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.And(tmp, scc);\n\t\tif (!tmp.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(scc);\n\t\t\treport(scc);\n\t\t}\n\t\tJDD.Deref(tmp);\n\n\t\t// FIXME: restricting newEdges isn't necessary, needs benchmarking\n\t\t//        (speed vs memory?)\n\t\t// newNodes1 = convergedSet \\ scc\n\t\t//JDD.Ref(scc);\n\t\tJDD.Ref(convergedSet);\n\t\tJDDNode newNodes1 = JDD.And(convergedSet, JDD.Not(scc));\n\t\tif (JDD.AreIntersecting(newNodes1, filter)) {\n\t\t\t// newEdges1 = edges \\intersect (newNodes x newNodes^t)\n\t\t\tJDD.Ref(edges);\n\t\t\tJDD.Ref(newNodes1);\n\t\t\tJDDNode newEdges1 = JDD.Apply(JDD.TIMES, edges, newNodes1);\n\t\t\tJDD.Ref(newNodes1);\n\t\t\ttmp = JDD.PermuteVariables(newNodes1, allDDRowVars, allDDColVars);\n\t\t\tnewEdges1 = JDD.Apply(JDD.TIMES, newEdges1, tmp);\n\n\t\t\ttasks.push(new DecompTask(newNodes1, newEdges1));\n\t\t} else\n\t\t\tJDD.Deref(newNodes1);\n\n\t\t// newNodes2 = nodes \\ convergedSet\n\t\t//JDD.Ref(nodes);\n\t\t//JDD.Ref(convergedSet);\n\t\tJDDNode newNodes2 = JDD.And(nodes, JDD.Not(convergedSet));\n\t\tif (JDD.AreIntersecting(newNodes2, filter)) {\n\t\t\t// newEdges2 = edges \\intersect (newNodes x newNodes^t)\n\t\t\tJDD.Ref(edges);\n\t\t\tJDD.Ref(newNodes2);\n\t\t\tJDDNode newEdges2 = JDD.Apply(JDD.TIMES, edges, newNodes2);\n\t\t\tJDD.Ref(newNodes2);\n\t\t\ttmp = JDD.PermuteVariables(newNodes2, allDDRowVars, allDDColVars);\n\t\t\tnewEdges2 = JDD.Apply(JDD.TIMES, newEdges2, tmp);\n\n\t\t\t// Queue new sets for search\n\t\t\ttasks.push(new DecompTask(newNodes2, newEdges2));\n\t\t} else\n\t\t\tJDD.Deref(newNodes2);\n\n\t\t//JDD.Deref(scc);\n\t\t//JDD.Deref(convergedSet);\n\t\t//JDD.Deref(nodes);\n\t\tJDD.Deref(edges);\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/comp/SCCComputerSCCFind.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Carlos S. Bederian (Universidad Nacional de Cordoba)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.util.Stack;\nimport java.util.Vector;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport prism.PrismSettings;\nimport symbolic.comp.SCCComputer;\n\n/**\n * SCC (strongly connected component) decomposition using SCC-Find search\n * (from Gentilini/Piazza/Policriti 2003)\n */\npublic class SCCComputerSCCFind extends SCCComputer\n{\n\tprivate class DecompTask\n\t{\n\t\tJDDNode nodes;\n\t\tJDDNode edges;\n\t\tJDDNode spineSetPath;\n\t\tJDDNode spineSetNode;\n\n\t\tDecompTask(JDDNode nodes_, JDDNode edges_, JDDNode spineSetPath_, JDDNode spineSetNode_)\n\t\t{\n\t\t\tnodes = nodes_;\n\t\t\tedges = edges_;\n\t\t\tspineSetPath = spineSetPath_;\n\t\t\tspineSetNode = spineSetNode_;\n\t\t}\n\t}\n\n\tprivate JDDNode allSCCs;\n\tprivate Stack<DecompTask> tasks;\n\n\t/**\n\t * Build (B)SCC computer for a given model.\n\t */\n\tpublic SCCComputerSCCFind(PrismComponent parent, JDDNode reach, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars) throws PrismException\n\t{\n\t\tsuper(parent, reach, trans01, allDDRowVars, allDDColVars);\n\t}\n\n\t// Methods for SCCComputer\n\n\t@Override\n\tpublic void computeSCCs()\n\t{\n\t\tsccs = new Vector<JDDNode>();\n\t\tallSCCs = JDD.Constant(0);\n\t\ttasks = new Stack<DecompTask>();\n\t\tJDD.Ref(reach);\n\t\tJDD.Ref(trans01);\n\t\tJDDNode trimmedNodes = trim(reach, trans01);\n\t\tJDD.Ref(trans01);\n\t\ttasks.push(new DecompTask(trimmedNodes, trans01, JDD.Constant(0), JDD.Constant(0)));\n\t\twhile (!tasks.isEmpty()) {\n\t\t\tsccFind(tasks.pop());\n\t\t}\n\t\tJDD.Ref(reach);\n\t\tnotInSCCs = JDD.And(reach, JDD.Not(allSCCs));\n\t}\n\n\t@Override\n\tpublic void computeSCCs(JDDNode filter)\n\t{\n\t\t//computeSCCs();\n\t\tsccs = new Vector<JDDNode>();\n\t\tallSCCs = JDD.Constant(0);\n\t\ttasks = new Stack<DecompTask>();\n\t\tJDD.Ref(reach);\n\t\tJDD.Ref(trans01);\n\t\tJDDNode trimmedNodes = trim(reach, trans01);\n\t\tJDD.Ref(trans01);\n\t\ttasks.push(new DecompTask(trimmedNodes, trans01, JDD.Constant(0), JDD.Constant(0)));\n\t\twhile (!tasks.isEmpty()) {\n\t\t\t//mainLog.println(\"length of scc queue = \" + tasks.size());\n\t\t\tsccFind(tasks.pop(), filter);\n\t\t}\n\t\tJDD.Ref(reach);\n\t\tnotInSCCs = JDD.And(reach, JDD.Not(allSCCs));\n\t}\n\n\t// Computation\n\t\n\t// Return the image of nodes in edges\n\t// Refs: result\n\t// Derefs: edges, nodes\n\tprivate JDDNode image(JDDNode nodes, JDDNode edges)\n\t{\n\t\tJDDNode tmp;\n\n\t\t// Get transitions that start at nodes\n\t\ttmp = JDD.Apply(JDD.TIMES, edges, nodes);\n\t\t// Get the img(nodes)\n\t\ttmp = JDD.ThereExists(tmp, allDDRowVars);\n\t\ttmp = JDD.PermuteVariables(tmp, allDDColVars, allDDRowVars);\n\t\treturn tmp;\n\t}\n\n\t// Return the preimage of nodes in edges\n\t// Refs: result\n\t// Derefs: edges, nodes\n\tprivate JDDNode preimage(JDDNode nodes, JDDNode edges)\n\t{\n\t\tJDDNode tmp;\n\n\t\t// Get transitions that end at nodes\n\t\ttmp = JDD.PermuteVariables(nodes, allDDRowVars, allDDColVars);\n\t\ttmp = JDD.Apply(JDD.TIMES, edges, tmp);\n\t\t// Get the pre(nodes)\n\t\ttmp = JDD.ThereExists(tmp, allDDColVars);\n\t\treturn tmp;\n\t}\n\n\t// Trim nodes that have no path to a node in a nontrivial SCC\n\t// or have no path from a node in a nontrivial SCC\n\t// Refs: result\n\t// Derefs: nodes, edges\n\tprivate JDDNode trim(JDDNode nodes, JDDNode edges)\n\t{\n\t\tJDDNode old;\n\t\tJDDNode current;\n\t\tJDDNode img;\n\t\tJDDNode pre;\n\t\tint i = 1;\n\n\t\tJDD.Ref(nodes);\n\t\tcurrent = nodes;\n\t\tdo {\n\t\t\told = current;\n\t\t\tJDD.Ref(current);\n\t\t\tJDD.Ref(edges);\n\t\t\timg = image(current, edges);\n\t\t\tJDD.Ref(current);\n\t\t\tJDD.Ref(edges);\n\t\t\tpre = preimage(current, edges);\n\t\t\tcurrent = JDD.And(current, JDD.And(img, pre));\n\t\t\tif (settings.getBoolean(PrismSettings.PRISM_VERBOSE)) {\n\t\t\t\tmainLog.println(\"Trimming pass \" + i + \":\");\n\t\t\t\tJDD.PrintVector(current, allDDRowVars);\n\t\t\t\ti++;\n\t\t\t}\n\t\t} while (!current.equals(old));\n\t\tJDD.Deref(nodes);\n\t\tJDD.Deref(edges);\n\n\t\treturn current;\n\t}\n\n\t// Report a SCC found by SCC-Find\n\tprivate void report(JDDNode nodes)\n\t{\n\t\tif (nodes.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(nodes);\n\t\t\treturn;\n\t\t}\n\t\t// Sanity check, partitioning of the state space should prevent this\n\t\tassert !sccs.contains(nodes);\n\n\t\t/* if (prism.getVerbose()) {\n\t\t\tmainLog.println(\"Found SCC:\");\n\t\t\tJDD.PrintVector(nodes, rows);\n\t\t} */\n\t\tsccs.addElement(nodes);\n\t\tJDD.Ref(nodes);\n\t\tallSCCs = JDD.Or(allSCCs, nodes);\n\t}\n\n\tprivate class SkelForwardResult\n\t{\n\t\tJDDNode forwardSet;\n\t\tJDDNode spineSetPath;\n\t\tJDDNode spineSetNode;\n\n\t\tSkelForwardResult(JDDNode forwardSet_, JDDNode spineSetPath_, JDDNode spineSetNode_)\n\t\t{\n\t\t\tforwardSet = forwardSet_;\n\t\t\tspineSetPath = spineSetPath_;\n\t\t\tspineSetNode = spineSetNode_;\n\t\t}\n\t}\n\n\t// Compute a forward set and skeleton of node\n\t// Derefs: nothing\n\t// Refs: SkelForwardResult contents\n\tprivate SkelForwardResult skelForward(JDDNode nodes, JDDNode edges, JDDNode node)\n\t{\n\n\t\tStack<JDDNode> stack = new Stack<JDDNode>();\n\n\t\tJDD.Ref(node);\n\t\tJDDNode level = node;\n\t\tJDDNode forwardSet = JDD.Constant(0);\n\t\twhile (!level.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(level);\n\t\t\tstack.push(level);\n\t\t\tJDD.Ref(level);\n\t\t\tforwardSet = JDD.Or(forwardSet, level);\n\t\t\tJDD.Ref(forwardSet);\n\t\t\tJDD.Ref(edges);\n\t\t\tlevel = JDD.And(image(level, edges), JDD.Not(forwardSet));\n\t\t}\n\t\tJDD.Deref(level);\n\n\t\tlevel = stack.pop();\n\t\tJDDNode newNode = JDD.RestrictToFirst(level, allDDRowVars);\n\t\tJDD.Ref(newNode);\n\t\tJDDNode newPath = newNode;\n\t\twhile (!stack.isEmpty()) {\n\t\t\tlevel = stack.pop();\n\t\t\tJDD.Ref(newPath);\n\t\t\tJDD.Ref(edges);\n\t\t\tnewPath = JDD.Or(newPath, JDD.RestrictToFirst(JDD.And(preimage(newPath, edges), level), allDDRowVars));\n\t\t}\n\t\treturn new SkelForwardResult(forwardSet, newPath, newNode);\n\t}\n\n\t// SCC-Find decomposition\n\t// Refs: reported result\n\t// Derefs: DecompTask contents\n\tprivate void sccFind(DecompTask task)\n\t{\n\t\tJDDNode nodes = task.nodes;\n\t\tJDDNode edges = task.edges;\n\t\tJDDNode spineSetPath = task.spineSetPath;\n\t\tJDDNode spineSetNode = task.spineSetNode;\n\t\tJDDNode tmp;\n\n\t\tif (nodes.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(nodes);\n\t\t\tJDD.Deref(edges);\n\t\t\tJDD.Deref(spineSetPath);\n\t\t\tJDD.Deref(spineSetNode);\n\t\t\treturn;\n\t\t}\n\n\t\t/* if (prism.getVerbose()) {\n\t\t\tmainLog.println(\"SCC-Find pass on nodes: \");\n\t\t\tJDD.PrintVector(nodes, rows);\n\t\t} */\n\n\t\tif (spineSetPath.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(spineSetNode);\n\t\t\t// Pick a node\n\t\t\tJDD.Ref(nodes);\n\t\t\tspineSetNode = JDD.RestrictToFirst(nodes, allDDRowVars);\n\t\t}\n\n\t\tSkelForwardResult skelFw = skelForward(nodes, edges, spineSetNode);\n\t\tJDDNode forwardSet = skelFw.forwardSet;\n\t\tJDDNode newSpineSetPath = skelFw.spineSetPath;\n\t\tJDDNode newSpineSetNode = skelFw.spineSetNode;\n\n\t\tJDD.Ref(spineSetNode);\n\t\tJDDNode scc = spineSetNode;\n\t\tJDD.Ref(scc);\n\t\tJDD.Ref(edges);\n\t\tJDD.Ref(forwardSet);\n\t\tJDDNode intersection = JDD.And(preimage(scc, edges), forwardSet);\n\t\tJDD.Ref(intersection);\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.And(intersection, JDD.Not(scc));\n\t\twhile (!tmp.equals(JDD.ZERO)) {\n\t\t\tscc = JDD.Or(scc, intersection);\n\t\t\tJDD.Ref(scc);\n\t\t\tJDD.Ref(edges);\n\t\t\tJDD.Ref(forwardSet);\n\t\t\tintersection = JDD.And(preimage(scc, edges), forwardSet);\n\t\t\tJDD.Ref(intersection);\n\t\t\tJDD.Ref(scc);\n\t\t\tJDD.Deref(tmp);\n\t\t\ttmp = JDD.And(intersection, JDD.Not(scc));\n\t\t}\n\t\tJDD.Deref(tmp);\n\t\tJDD.Deref(intersection);\n\n\t\t// check if SCC is nontrivial and report\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.PermuteVariables(scc, allDDRowVars, allDDColVars);\n\t\tJDD.Ref(edges);\n\t\ttmp = JDD.And(tmp, edges);\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.And(tmp, scc);\n\t\tif (!tmp.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(scc);\n\t\t\treport(scc);\n\t\t}\n\t\tJDD.Deref(tmp);\n\n\t\t// FIXME: restricting newEdges isn't necessary, needs benchmarking\n\t\t//        (speed vs memory?)\n\t\t// newNodes1 = nodes \\ forwardSet\n\t\tJDD.Ref(nodes);\n\t\tJDD.Ref(forwardSet);\n\t\tJDDNode newNodes1 = JDD.And(nodes, JDD.Not(forwardSet));\n\t\t// newEdges1 = edges \\intersect (newNodes1 x newNodes1^t)\n\t\tJDD.Ref(edges);\n\t\tJDD.Ref(newNodes1);\n\t\tJDDNode newEdges1 = JDD.Apply(JDD.TIMES, edges, newNodes1);\n\t\tJDD.Ref(newNodes1);\n\t\tnewEdges1 = JDD.Apply(JDD.TIMES, newEdges1, JDD.PermuteVariables(newNodes1, allDDRowVars, allDDColVars));\n\t\t// newS1 = spineSetPath \\ scc\n\t\tJDD.Ref(spineSetPath);\n\t\tJDD.Ref(scc);\n\t\tJDDNode newSpineSetPath1 = JDD.And(spineSetPath, JDD.Not(scc));\n\t\t// newNode1 = preimage(scc \\intersect spineSetPath) \\intersect (spineSetPath \\ scc)\n\t\tJDD.Ref(scc);\n\t\tJDD.Ref(spineSetPath);\n\t\tJDD.Ref(edges);\n\t\tJDD.Ref(newSpineSetPath1);\n\t\tJDDNode newSpineSetNode1 = JDD.And(preimage(JDD.And(scc, spineSetPath), edges), newSpineSetPath1);\n\n\t\t// newNodes2 = forwardSet \\ scc\n\t\t//JDD.Ref(forwardSet);\n\t\tJDD.Ref(scc);\n\t\tJDDNode newNodes2 = JDD.And(forwardSet, JDD.Not(scc));\n\t\t// newEdges2 = edges \\intersect (newNodes2 x newNodes2^t)\n\t\tJDD.Ref(edges);\n\t\tJDD.Ref(newNodes2);\n\t\tJDDNode newEdges2 = JDD.Apply(JDD.TIMES, edges, newNodes2);\n\t\tJDD.Ref(newNodes2);\n\t\tnewEdges2 = JDD.Apply(JDD.TIMES, newEdges2, JDD.PermuteVariables(newNodes2, allDDRowVars, allDDColVars));\n\t\t// newS2 = newS \\ scc\n\t\tJDD.Ref(scc);\n\t\tJDDNode newSpineSetPath2 = JDD.And(newSpineSetPath, JDD.Not(scc));\n\t\t// newNode2 = newNode \\ scc\n\t\t//JDD.Ref(scc);\n\t\tJDDNode newSpineSetNode2 = JDD.And(newSpineSetNode, JDD.Not(scc));\n\n\t\ttasks.push(new DecompTask(newNodes2, newEdges2, newSpineSetPath2, newSpineSetNode2));\n\t\ttasks.push(new DecompTask(newNodes1, newEdges1, newSpineSetPath1, newSpineSetNode1));\n\n\t\t//JDD.Deref(forwardSet);\n\t\tJDD.Deref(spineSetNode);\n\t\tJDD.Deref(spineSetPath);\n\t\t//JDD.Deref(scc);\n\t\tJDD.Deref(nodes);\n\t\tJDD.Deref(edges);\n\t}\n\n\tprivate void sccFind(DecompTask task, JDDNode filter)\n\t{\n\n\t\tJDDNode nodes = task.nodes;\n\t\tJDDNode edges = task.edges;\n\t\tJDDNode spineSetPath = task.spineSetPath;\n\t\tJDDNode spineSetNode = task.spineSetNode;\n\t\tJDDNode tmp;\n\n\t\tif (nodes.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(nodes);\n\t\t\tJDD.Deref(edges);\n\t\t\tJDD.Deref(spineSetPath);\n\t\t\tJDD.Deref(spineSetNode);\n\t\t\treturn;\n\t\t}\n\n\t\t/* if (prism.getVerbose()) {\n\t\t\tmainLog.println(\"SCC-Find pass on nodes: \");\n\t\t\tJDD.PrintVector(nodes, rows);\n\t\t} */\n\n\t\tif (spineSetPath.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(spineSetNode);\n\t\t\t// Pick a node\n\t\t\tJDD.Ref(nodes);\n\t\t\tspineSetNode = JDD.RestrictToFirst(nodes, allDDRowVars);\n\t\t}\n\n\t\tSkelForwardResult skelFw = skelForward(nodes, edges, spineSetNode);\n\t\tJDDNode forwardSet = skelFw.forwardSet;\n\t\tJDDNode newSpineSetPath = skelFw.spineSetPath;\n\t\tJDDNode newSpineSetNode = skelFw.spineSetNode;\n\n\t\tJDD.Ref(spineSetNode);\n\t\tJDDNode scc = spineSetNode;\n\t\tJDD.Ref(scc);\n\t\tJDD.Ref(edges);\n\t\tJDD.Ref(forwardSet);\n\t\tJDDNode intersection = JDD.And(preimage(scc, edges), forwardSet);\n\t\tJDD.Ref(intersection);\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.And(intersection, JDD.Not(scc));\n\t\twhile (!tmp.equals(JDD.ZERO)) {\n\t\t\tscc = JDD.Or(scc, intersection);\n\t\t\tJDD.Ref(scc);\n\t\t\tJDD.Ref(edges);\n\t\t\tJDD.Ref(forwardSet);\n\t\t\tintersection = JDD.And(preimage(scc, edges), forwardSet);\n\t\t\tJDD.Ref(intersection);\n\t\t\tJDD.Ref(scc);\n\t\t\tJDD.Deref(tmp);\n\t\t\ttmp = JDD.And(intersection, JDD.Not(scc));\n\t\t}\n\t\tJDD.Deref(tmp);\n\t\tJDD.Deref(intersection);\n\n\t\t// check if SCC is nontrivial and report\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.PermuteVariables(scc, allDDRowVars, allDDColVars);\n\t\tJDD.Ref(edges);\n\t\ttmp = JDD.And(tmp, edges);\n\t\tJDD.Ref(scc);\n\t\ttmp = JDD.And(tmp, scc);\n\t\tif (!tmp.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(scc);\n\t\t\treport(scc);\n\t\t}\n\t\tJDD.Deref(tmp);\n\n\t\t// FIXME: restricting newEdges isn't necessary, needs benchmarking\n\t\t//        (speed vs memory?)\n\t\t// newNodes1 = nodes \\ forwardSet\n\t\tJDD.Ref(nodes);\n\t\tJDD.Ref(forwardSet);\n\t\tJDDNode newNodes1 = JDD.And(nodes, JDD.Not(forwardSet));\n\t\tif (JDD.AreIntersecting(newNodes1, filter)) {\n\t\t\t// newEdges1 = edges \\intersect (newNodes1 x newNodes1^t)\n\t\t\tJDD.Ref(edges);\n\t\t\tJDD.Ref(newNodes1);\n\t\t\tJDDNode newEdges1 = JDD.Apply(JDD.TIMES, edges, newNodes1);\n\t\t\tJDD.Ref(newNodes1);\n\t\t\tnewEdges1 = JDD.Apply(JDD.TIMES, newEdges1, JDD.PermuteVariables(newNodes1, allDDRowVars, allDDColVars));\n\t\t\t// newS1 = spineSetPath \\ scc\n\t\t\tJDD.Ref(spineSetPath);\n\t\t\tJDD.Ref(scc);\n\t\t\tJDDNode newSpineSetPath1 = JDD.And(spineSetPath, JDD.Not(scc));\n\t\t\t// newNode1 = preimage(scc \\intersect spineSetPath) \\intersect (spineSetPath \\ scc)\n\t\t\tJDD.Ref(scc);\n\t\t\tJDD.Ref(spineSetPath);\n\t\t\tJDD.Ref(edges);\n\t\t\tJDD.Ref(newSpineSetPath1);\n\t\t\tJDDNode newSpineSetNode1 = JDD.And(preimage(JDD.And(scc, spineSetPath), edges), newSpineSetPath1);\n\n\t\t\ttasks.push(new DecompTask(newNodes1, newEdges1, newSpineSetPath1, newSpineSetNode1));\n\t\t} else\n\t\t\tJDD.Deref(newNodes1);\n\n\t\t// newNodes2 = forwardSet \\ scc\n\t\t//JDD.Ref(forwardSet);\n\t\tJDD.Ref(scc);\n\t\tJDDNode newNodes2 = JDD.And(forwardSet, JDD.Not(scc));\n\t\tif (JDD.AreIntersecting(newNodes2, filter)) {\n\t\t\t// newEdges2 = edges \\intersect (newNodes2 x newNodes2^t)\n\t\t\tJDD.Ref(edges);\n\t\t\tJDD.Ref(newNodes2);\n\t\t\tJDDNode newEdges2 = JDD.Apply(JDD.TIMES, edges, newNodes2);\n\t\t\tJDD.Ref(newNodes2);\n\t\t\tnewEdges2 = JDD.Apply(JDD.TIMES, newEdges2, JDD.PermuteVariables(newNodes2, allDDRowVars, allDDColVars));\n\t\t\t// newS2 = newS \\ scc\n\t\t\tJDD.Ref(scc);\n\t\t\tJDDNode newSpineSetPath2 = JDD.And(newSpineSetPath, JDD.Not(scc));\n\t\t\t// newNode2 = newNode \\ scc\n\t\t\tJDD.Ref(scc);\n\t\t\tJDDNode newSpineSetNode2 = JDD.And(newSpineSetNode, JDD.Not(scc));\n\n\t\t\ttasks.push(new DecompTask(newNodes2, newEdges2, newSpineSetPath2, newSpineSetNode2));\n\t\t} else {\n\t\t\tJDD.Deref(newNodes2);\n\t\t\tJDD.Deref(newSpineSetPath);\n\t\t\tJDD.Deref(newSpineSetNode);\n\t\t}\n\n\t\t//JDD.Deref(forwardSet);\n\t\tJDD.Deref(spineSetNode);\n\t\tJDD.Deref(spineSetPath);\n\t\tJDD.Deref(scc);\n\t\tJDD.Deref(nodes);\n\t\tJDD.Deref(edges);\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/comp/SCCComputerXB.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.util.Vector;\n\nimport jdd.*;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport symbolic.comp.SCCComputer;\n\n/**\n * SCC (strongly connected component) decomposition\n * (from Xie/Beerel 1999)\n*/\npublic class SCCComputerXB extends SCCComputer\n{\n\t/**\n\t * Build (B)SCC computer for a given model.\n\t */\n\tpublic SCCComputerXB(PrismComponent parent, JDDNode reach, JDDNode trans01, JDDVars allDDRowVars, JDDVars allDDColVars) throws PrismException\n\t{\n\t\tsuper(parent, reach, trans01, allDDRowVars, allDDColVars);\n\t}\n\t\n\t// Methods for SCCComputer\n\n\t@Override\n\tpublic void computeSCCs()\n\t{\n\t\tJDDNode v, s, back;\n\t\t\n\t\tmainLog.println(\"\\nComputing (B)SCCs...\");\n\t\t\n\t\t// vector to be filled with SCCs\n\t\tsccs = new Vector<JDDNode>();\n\t\t// BDD of non-SCC states (initially zero BDD)\n\t\tnotInSCCs = JDD.Constant(0);\n\t\t\n\t\t// Compute all SCCs\n\t\t// (using algorithm of xie/beerel'99)\n\t\tJDD.Ref(reach);\n\t\tv = reach;\n\t\twhile (!v.equals(JDD.ZERO)) {\n\t\t\ts = pickRandomState(v);\n\t\t\tback = computeBackwardSet(s, v);\n\t\t\tcomputeSCCsRec(s, back);\n\t\t\tJDD.Ref(reach);\n\t\t\tv = JDD.And(v, JDD.And(reach, JDD.Not(JDD.Or(s, back))));\n\t\t}\n\t\tJDD.Deref(v);\n\t}\n\t\n\t@Override\n\tpublic void computeSCCs(JDDNode filter) throws PrismException\n\t{\n\t\tthrow new PrismException(\"Not implemented yet\");\n\t\t// TODO: why is filter ignored here?\n\t\t// computeSCCs();\n\t}\n\t\n\t// Computation\n\t\n\t// pick a random (actually the first) state from set (set not empty)\n\t\n\tprotected JDDNode pickRandomState(JDDNode set)\n\t{\n\t\tint i, n;\n\t\tJDDNode tmp, tmp2, res, var;\n\t\t\n\t\tJDD.Ref(set);\n\t\ttmp = set;\n\t\tres = JDD.Constant(1);\n\t\tn = allDDRowVars.n();\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tJDD.Ref(allDDRowVars.getVar(i));\n\t\t\tvar = allDDRowVars.getVar(i);\n\t\t\tJDD.Ref(var);\n\t\t\tJDD.Ref(tmp);\n\t\t\ttmp2 = JDD.And(tmp, JDD.Not(var));\n\t\t\tif (!tmp2.equals(JDD.ZERO)) {\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\ttmp = tmp2;\n\t\t\t\tJDD.Ref(var);\n\t\t\t\tres = JDD.And(res, JDD.Not(var));\n\t\t\t}\n\t\t\telse {\n\t\t\t\tJDD.Deref(tmp2);\n\t\t\t\tJDD.Ref(var);\n\t\t\t\ttmp = JDD.And(tmp, var);\n\t\t\t\tJDD.Ref(var);\n\t\t\t\tres = JDD.And(res, var);\n\t\t\t}\n\t\t\tJDD.Deref(var);\n\t\t}\n\t\t\n\t\tJDD.Deref(tmp);\n\t\t\n\t\treturn res;\n\t}\n\t\n\t// find backward set of state s restricted to set v\n\t\n\tprotected JDDNode computeBackwardSet(JDDNode s, JDDNode v)\n\t{\n\t\tJDDNode back, tmp;\n\t\tboolean done = false;\n\t\t\n\t\t// do one step of loop first (s not nec. in forward set of s)\n\t\tJDD.Ref(s);\n\t\tJDD.Ref(trans01);\n\t\tback = JDD.ThereExists(JDD.And(JDD.PermuteVariables(s, allDDRowVars, allDDColVars), trans01), allDDColVars);\n\n\t\t// fixpoint\n\t\twhile (!done) {\n\t\t\tJDD.Ref(back);\n\t\t\ttmp = JDD.PermuteVariables(back, allDDRowVars, allDDColVars);\n\t\t\tJDD.Ref(trans01);\n\t\t\ttmp = JDD.And(tmp, trans01);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDColVars);\n\t\t\tJDD.Ref(back);\n\t\t\ttmp = JDD.Or(tmp, back);\n\t\t\tJDD.Ref(v);\n\t\t\ttmp = JDD.And(v, tmp);\n\t\t\t\n\t\t\tif (tmp.equals(back)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\t\n\t\t\tJDD.Deref(back);\n\t\t\tback = tmp;\n\t\t}\n\t\t\n\t\treturn back;\n\t}\n\t\n\t// find forward set of state s restricted to set v\n\t\n\tprotected JDDNode computeForwardSet(JDDNode s, JDDNode v)\n\t{\n\t\tJDDNode forw, v2, tmp;\n\t\tboolean done = false;\n\t\t\n\t\t// do one step of loop first (s not nec. in forward set of s)\n\t\tJDD.Ref(s);\n\t\tJDD.Ref(trans01);\n\t\tforw = JDD.ThereExists(JDD.And(s, trans01), allDDRowVars);\n\t\t\n\t\t// transpose a copy of v\n\t\tJDD.Ref(v);\n\t\tv2 = JDD.PermuteVariables(v, allDDRowVars, allDDColVars);\n\t\t\n\t\t// fixpoint\n\t\twhile (!done) {\n\t\t\tJDD.Ref(forw);\n\t\t\ttmp = JDD.PermuteVariables(forw, allDDColVars, allDDRowVars);\n\t\t\tJDD.Ref(trans01);\n\t\t\ttmp = JDD.And(tmp, trans01);\n\t\t\ttmp = JDD.ThereExists(tmp, allDDRowVars);\n\t\t\tJDD.Ref(forw);\n\t\t\ttmp = JDD.Or(tmp, forw);\n\t\t\tJDD.Ref(v2);\n\t\t\ttmp = JDD.And(v2, tmp);\n\t\t\t\n\t\t\tif (tmp.equals(forw)) {\n\t\t\t\tdone = true;\n\t\t\t}\n\t\t\t\n\t\t\tJDD.Deref(forw);\n\t\t\tforw = tmp;\n\t\t}\n\t\t\n\t\t// tidy up\n\t\tJDD.Deref(v2);\n\t\t\n\t\treturn JDD.PermuteVariables(forw, allDDColVars, allDDRowVars);\n\t}\n\t\n\t// compute fmd (finite maximum distance) predecessors of set w\n\t\n\tprotected JDDNode computeFMDPred(JDDNode w, JDDNode u)\n\t{\n\t\tJDDNode pred, front, bound, x, y;\n\t\t\n\t\tpred = JDD.Constant(0);\n\t\tJDD.Ref(w);\n\t\tfront = w;\n\t\tJDD.Ref(u);\n\t\tbound = u;\n\t\t\n\t\twhile (!front.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(trans01);\n\t\t\tJDD.Ref(bound);\n\t\t\tx = JDD.ThereExists(JDD.And(JDD.PermuteVariables(front, allDDRowVars, allDDColVars), JDD.And(trans01, bound)), allDDColVars);\n\t\t\tJDD.Ref(bound);\n\t\t\tJDD.Ref(trans01);\n\t\t\tJDD.Ref(bound);\n\t\t\ty = JDD.ThereExists(JDD.And(JDD.PermuteVariables(bound, allDDRowVars, allDDColVars), JDD.And(trans01, bound)), allDDColVars);\n\t\t\tJDD.Ref(reach);\n\t\t\tfront = JDD.And(x, JDD.And(reach, JDD.Not(y)));\n\t\t\tJDD.Ref(front);\n\t\t\tpred = JDD.Or(pred, front);\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(front);\n\t\t\tbound = JDD.And(bound, JDD.And(reach, JDD.Not(front)));\n\t\t}\n\t\t\n\t\tJDD.Deref(front);\n\t\tJDD.Deref(bound);\n\t\t\n\t\treturn pred;\n\t}\n\t\n\t// recursively compute SCCs in back\n\t// (store SCCs in first vector,\n\t//  store states not in an SCC in first element of second vector)\n\t\n\tprotected void computeSCCsRec(JDDNode s, JDDNode back)\n\t{\n\t\tJDDNode forw, x, r, y, ip, s2, back2, tmp;\n\t\t\n\t\tforw = computeForwardSet(s, back);\n\t\tif (forw.equals(JDD.ZERO)) {\n\t\t\tJDD.Ref(s);\n\t\t\tnotInSCCs = JDD.Or(notInSCCs, s);\n\t\t}\n\t\telse {\n\t\t\tJDD.Ref(forw);\n\t\t\tsccs.addElement(forw);\n\t\t}\n\t\tJDD.Ref(forw);\n\t\tJDD.Ref(s);\n\t\tx = JDD.Or(forw, s);\n\t\tJDD.Ref(back);\n\t\tJDD.Ref(x);\n\t\tJDD.Ref(reach);\n\t\tr = JDD.And(back, JDD.And(reach, JDD.Not(x)));\n\t\ty = computeFMDPred(x, r);\n\t\tJDD.Ref(y);\n\t\tnotInSCCs = JDD.Or(notInSCCs, y);\n\t\tJDD.Ref(y);\n\t\tJDD.Ref(reach);\n\t\tr = JDD.And(r, JDD.And(reach, JDD.Not(y)));\n\t\tJDD.Ref(x);\n\t\tJDD.Ref(y);\n\t\ttmp = JDD.Or(y, x);\n\t\tip = computeBackwardSet(tmp, r);\n\t\tJDD.Deref(tmp);\n\t\t\n\t\twhile (!r.equals(JDD.ZERO)) {\n\t\t\ts2 = pickRandomState(ip);\n\t\t\tback2 = computeBackwardSet(s2, r);\n\t\t\tcomputeSCCsRec(s2, back2);\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(s2);\n\t\t\tJDD.Ref(back2);\n\t\t\tr = JDD.And(r, JDD.And(reach, JDD.Not(JDD.Or(s2, back2))));\n\t\t\tJDD.Ref(reach);\n\t\t\tJDD.Ref(s2);\n\t\t\tJDD.Ref(back2);\n\t\t\tip = JDD.And(ip, JDD.And(reach, JDD.Not(JDD.Or(s2, back2))));\n\t\t\tJDD.Deref(s2);\n\t\t\tJDD.Deref(back2);\n\t\t}\n\t\t\n\t\tJDD.Deref(forw);\n\t\tJDD.Deref(x);\n\t\tJDD.Deref(r);\n\t\tJDD.Deref(y);\n\t\tJDD.Deref(ip);\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/comp/StateModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.Set;\nimport java.util.TreeSet;\nimport java.util.Vector;\n\nimport io.ModelExportFormat;\nimport io.ModelExportOptions;\nimport io.ModelExportTask;\nimport mtbdd.PrismMTBDD;\nimport dv.DoubleVector;\nimport jdd.*;\nimport odd.*;\nimport parser.*;\nimport parser.ast.*;\nimport parser.ast.ExpressionFilter.FilterOperator;\nimport parser.type.*;\nimport parser.visitor.ReplaceLabels;\nimport prism.*;\nimport prism.Filter;\nimport symbolic.model.ModelSymbolic;\nimport symbolic.model.NondetModel;\nimport symbolic.states.StateListMTBDD;\nimport symbolic.states.StateValues;\nimport symbolic.states.StateValuesDV;\nimport symbolic.states.StateValuesMTBDD;\nimport symbolic.states.StateValuesVoid;\nimport symbolic.model.Model;\nimport symbolic.model.ProbModel;\n\n// Base class for model checkers - does state-based evaluations (no temporal/probabilistic)\n\npublic class StateModelChecker extends PrismNativeComponent implements ModelChecker\n{\n\t// Properties file\n\tprotected PropertiesFile propertiesFile;\n\n\t// Constant values\n\tprotected Values constantValues;\n\n\t// Model info\n\tprotected Model model;\n\tprotected VarList varList;\n\tprotected JDDNode trans;\n\tprotected JDDNode trans01;\n\tprotected JDDNode transActions;\n\tprotected JDDNode start;\n\tprotected JDDNode reach;\n\tprotected ODDNode odd;\n\tprotected JDDVars allDDRowVars;\n\tprotected JDDVars allDDColVars;\n\tprotected JDDVars[] varDDRowVars;\n\n\t// The filter to be applied to the current property\n\tprotected prism.Filter currentFilter;\n\n\t// The result of model checking will be stored here\n\tprotected Result result;\n\n\t// Options:\n\n\t// Which engine to use\n\tprotected int engine;\n\t// Parameter for termination criterion\n\tprotected double termCritParam;\n\t// Use interval iteration?\n\tprotected boolean doIntervalIteration;\n\t// Verbose mode?\n\tprotected boolean verbose;\n\t// Store the final results vector after model checking?\n\tprotected boolean storeVector = false; \n\t// Generate/store a strategy during model checking?\n\tprotected boolean genStrat = false;\n\n\t// Constructor\n\n\tpublic StateModelChecker(Prism prism, Model m, PropertiesFile pf) throws PrismException\n\t{\n\t\t// Initialise\n\t\tsuper(prism);\n\t\tmodel = m;\n\t\tpropertiesFile = pf;\n\t\tconstantValues = new Values();\n\t\tconstantValues.addValues(model.getConstantValues());\n\t\tif (pf != null)\n\t\t\tconstantValues.addValues(pf.getConstantValues());\n\t\tvarList = model.getVarList();\n\t\ttrans = model.getTrans();\n\t\ttrans01 = model.getTrans01();\n\t\tif (m instanceof NondetModel) {\n\t\t\ttransActions = ((NondetModel) model).getTransActions();\n\t\t}\n\t\tstart = model.getStart();\n\t\treach = model.getReach();\n\t\todd = model.getODD();\n\t\tallDDRowVars = model.getAllDDRowVars();\n\t\tallDDColVars = model.getAllDDColVars();\n\t\tvarDDRowVars = model.getVarDDRowVars();\n\n\t\t// Inherit some options from parent Prism object\n\t\t// Store locally and/or pass onto engines\n\t\tengine = prism.getEngine();\n\t\ttermCritParam = prism.getTermCritParam();\n\t\tdoIntervalIteration = settings.getBoolean(PrismSettings.PRISM_INTERVAL_ITER);\n\t\tverbose = prism.getVerbose();\n\t\tstoreVector = prism.getStoreVector();\n\t\tgenStrat = prism.getGenStrat();\n\t}\n\n\t/**\n\t * Additional constructor for creating stripped down StateModelChecker for\n\t * expression to MTBDD conversions (no colum variables, no transition function, ...).\n\t * <br>\n\t * The dummy model constructed for these purposes has to be cleared by calling\n\t * {@code clearDummyModel()} later.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic StateModelChecker(Prism prism, VarList varList, JDDVars allDDRowVars, JDDVars[] varDDRowVars, Values constantValues) throws PrismException\n\t{\n\t\t// Initialise\n\t\tsuper(prism);\n\t\tthis.varList = varList;\n\t\tthis.allDDRowVars = allDDRowVars;\n\t\tthis.varDDRowVars = varDDRowVars;\n\t\tthis.constantValues = constantValues;\n\t\t// Create dummy model\n\t\treach = null;\n\t\tProbModel probModel = new ProbModel(JDD.Constant(0),  // trans\n\t\t                      JDD.Constant(0),  // start\n\t\t                      allDDRowVars.copy(), // allDDRowVars\n\t\t                      new JDDVars(),    // allDDColVars\n\t\t                      null,             // ddVarNames\n\t\t                      varList,          // varList\n\t\t                      JDDVars.copyArray(varDDRowVars), // varDDRowVars\n\t\t                      null              // varDDColVars\n\t\t                     );\n\t\tprobModel.setConstantValues(constantValues);\n\t\tmodel = probModel;\n\t}\n\n\t/**\n\t * Create a model checker (a subclass of this one) for a given model type\n\t */\n\tpublic static StateModelChecker createModelChecker(ModelType modelType, Prism prism, Model model, PropertiesFile propertiesFile) throws PrismException\n\t{\n\t\tStateModelChecker mc = null;\n\t\tswitch (modelType) {\n\t\tcase DTMC:\n\t\t\tmc = new ProbModelChecker(prism, model, propertiesFile);\n\t\t\tbreak;\n\t\tcase MDP:\n\t\t\tmc = new NondetModelChecker(prism, model, propertiesFile);\n\t\t\tbreak;\n\t\tcase CTMC:\n\t\t\tmc = new StochModelChecker(prism, model, propertiesFile);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Cannot create model checker for model type \" + modelType);\n\t\t}\n\t\treturn mc;\n\t}\n\n\t/**\n\t * Create a model checker (a subclass of this one) for a given model,\n\t * deducing the model type and reusing the PropertiesFile and Prism objects\n\t * of the current model checker.\n\t */\n\tpublic ModelChecker createModelChecker(Model newModel) throws PrismException\n\t{\n\t\treturn createModelChecker(newModel.getModelType(), prism, newModel, propertiesFile);\n\t}\n\n\t/**\n\t * Clean up the dummy model created when using the abbreviated constructor\n\t */\n\tpublic void clearDummyModel()\n\t{\n\t\tmodel.clear();\n\t}\n\n\t@Override\n\tpublic Result check(Expression expr) throws PrismException\n\t{\n\t\tlong timer = 0;\n\t\tStateValues vals;\n\t\tString resultString;\n\n\t\t// Create storage for result\n\t\tresult = new Result();\n\n\t\t// Remove any existing filter info\n\t\tcurrentFilter = null;\n\n\t\t// If we need to store a copy of the results vector, add a \"store\" filter to represent this\n\t\tif (storeVector) {\n\t\t\tExpressionFilter exprFilter = new ExpressionFilter(\"store\", expr);\n\t\t\texprFilter.setInvisible(true);\n\t\t\texprFilter.typeCheck();\n\t\t\texpr = exprFilter;\n\t\t}\n\t\t// Wrap a filter round the property, if needed\n\t\t// (in order to extract the final result of model checking) \n\t\texpr = ExpressionFilter.addDefaultFilterIfNeeded(expr, model.getNumInitialStates() == 1);\n\t\t\n\t\t// Do model checking and store result vector\n\t\ttimer = System.currentTimeMillis();\n\t\t// check expression, statesOfInterest = all reachable states\n\t\tvals = checkExpression(expr, model.getReach().copy());\n\t\ttimer = System.currentTimeMillis() - timer;\n\t\tmainLog.println(\"\\nTime for model checking: \" + timer / 1000.0 + \" seconds.\");\n\n\t\t// Print result to log\n\t\tresultString = \"Result\";\n\t\tif (!(\"Result\".equals(expr.getResultName())))\n\t\t\tresultString += \" (\" + expr.getResultName().toLowerCase() + \")\";\n\t\tresultString += \": \" + result.getResultAndAccuracy();\n\t\tmainLog.print(\"\\n\" + resultString + \"\\n\");\n\n\t\t// Clean up\n\t\tvals.clear();\n\n\t\t// Return result\n\t\treturn result;\n\t}\n\n\t@Override\n\tpublic StateValues checkExpression(Expression expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res;\n\n\t\t// If-then-else\n\t\tif (expr instanceof ExpressionITE) {\n\t\t\tres = checkExpressionITE((ExpressionITE) expr, statesOfInterest);\n\t\t}\n\t\t// Binary ops\n\t\telse if (expr instanceof ExpressionBinaryOp) {\n\t\t\tres = checkExpressionBinaryOp((ExpressionBinaryOp) expr, statesOfInterest);\n\t\t}\n\t\t// Unary ops\n\t\telse if (expr instanceof ExpressionUnaryOp) {\n\t\t\tres = checkExpressionUnaryOp((ExpressionUnaryOp) expr, statesOfInterest);\n\t\t}\n\t\t// Functions\n\t\telse if (expr instanceof ExpressionFunc) {\n\t\t\tres = checkExpressionFunc((ExpressionFunc) expr, statesOfInterest);\n\t\t}\n\t\t// Identifiers\n\t\telse if (expr instanceof ExpressionIdent) {\n\t\t\t// Should never happen\n\t\t\tthrow new PrismException(\"Unknown identifier \\\"\" + ((ExpressionIdent) expr).getName() + \"\\\"\");\n\t\t}\n\t\t// Literals\n\t\telse if (expr instanceof ExpressionLiteral) {\n\t\t\tres = checkExpressionLiteral((ExpressionLiteral) expr, statesOfInterest);\n\t\t}\n\t\t// Constants\n\t\telse if (expr instanceof ExpressionConstant) {\n\t\t\tres = checkExpressionConstant((ExpressionConstant) expr, statesOfInterest);\n\t\t}\n\t\t// Formulas\n\t\telse if (expr instanceof ExpressionFormula) {\n\t\t\t// This should have been defined or expanded by now.\n\t\t\tif (((ExpressionFormula) expr).getDefinition() != null)\n\t\t\t\treturn checkExpression(((ExpressionFormula) expr).getDefinition(), statesOfInterest);\n\t\t\telse\n\t\t\t\tthrow new PrismException(\"Unexpanded formula \\\"\" + ((ExpressionFormula) expr).getName() + \"\\\"\");\n\t\t}\n\t\t// Variables\n\t\telse if (expr instanceof ExpressionVar) {\n\t\t\tres = checkExpressionVar((ExpressionVar) expr, statesOfInterest);\n\t\t}\n\t\t// Labels\n\t\telse if (expr instanceof ExpressionLabel) {\n\t\t\tres = checkExpressionLabel((ExpressionLabel) expr, statesOfInterest);\n\t\t}\n\t\t// Property refs\n\t\telse if (expr instanceof ExpressionProp) {\n\t\t\tres = checkExpressionProp((ExpressionProp) expr, statesOfInterest);\n\t\t}\n\t\t// Filter\n\t\telse if (expr instanceof ExpressionFilter) {\n\t\t\tres = checkExpressionFilter((ExpressionFilter) expr, statesOfInterest);\n\t\t}\n\t\t// Anything else - error\n\t\telse {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Couldn't check \" + expr.getClass());\n\t\t}\n\n\t\t// Filter out non-reachable states from solution\n\t\t// (only necessary for symbolically stored vectors)\n\t\t// (skip if reach is null, e.g. if just being used to convert arbitrary expressions)\n\t\tif (res instanceof StateValuesMTBDD && reach != null)\n\t\t\tres.filter(reach);\n\n\t\treturn res;\n\t}\n\n\t@Override\n\tpublic JDDNode checkExpressionDD(Expression expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValuesMTBDD sv = checkExpression(expr, statesOfInterest).convertToStateValuesMTBDD();\n\t\tJDDNode result = sv.getJDDNode().copy();\n\t\tsv.clear();\n\t\treturn result;\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// Check method for each operator\n\t// -----------------------------------------------------------------------------------\n\n\t/*\n\t * These check methods (and similar ones in subclasses of this class) return\n\t * a StateValues object which is a vector, over all states, of values. This can\n\t * be represented either symbolically (as an (MT)BDD, encapsulated in a StateValuesMTBDD\n\t * object) or explicitly (as an array of doubles, encapsulated in a StateValuesDV\n\t * object, containing a DoubleVector object).\n\t * \n\t * It is always possible to convert between these two forms but this will not always be\n\t * efficient. In particular, we want to avoid creating: (a) explicit vectors for very large\n\t * models where the vector can only be feasibly stored as an MTBDD; (b) and symbolic\n\t * vectors for irregular vectors which are small enough to be stored explicitly but would\n\t * blow up as an MTBDD.\n\t * \n\t * Various schemes (and user preferences/configurations) are possible. Currently:\n\t * \n\t * - simple, atomic expressions (constants, variable references, etc.) are\n\t *   created symbolically (since this is easy and usually efficient)\n\t * - for arithmetic operations, the result is stored explicitly if one or\n\t *   more of its operands is explicit and symbolic otherwise\n\t * - operators with Boolean results are always stored symbolically\n\t * \n\t * So, currently the only time that explicit vectors are created anew is (in subclasses\n\t * of this model checker) for e.g. the result of P=?, R=?, S=?, etc. operators. And for\n\t * these operators, the result will be symbolic if the MTBDD engine is being used (or\n\t * in some cases where the answer is trivial, e.g. 1 for all states). For P>p etc.\n\t * properties, the vector will be stored symbolically since values are Booleans. \n\t */\n\n\t/**\n\t * Check an 'if-then-else' expression.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionITE(ExpressionITE expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null, res2 = null, res3 = null;\n\t\tJDDNode dd, dd1, dd2, dd3;\n\t\tDoubleVector dv2, dv3;\n\n\t\t// Check operands recursively\n\t\ttry {\n\t\t\tres1 = checkExpression(expr.getOperand1(), statesOfInterest.copy());\n\t\t\tres2 = checkExpression(expr.getOperand2(), statesOfInterest.copy());\n\t\t\tres3 = checkExpression(expr.getOperand3(), statesOfInterest.copy());\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tif (res2 != null)\n\t\t\t\tres2.clear();\n\t\t\tthrow e;\n\t\t} finally {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t}\n\n\t\t// Operand 1 is boolean so should be symbolic\n\t\tdd1 = res1.convertToStateValuesMTBDD().getJDDNode();\n\n\t\t// If both operands 2/3 are symbolic, result will be symbolic\n\t\tif (res2 instanceof StateValuesMTBDD && res3 instanceof StateValuesMTBDD) {\n\t\t\tdd2 = ((StateValuesMTBDD) res2).getJDDNode();\n\t\t\tdd3 = ((StateValuesMTBDD) res3).getJDDNode();\n\t\t\tdd = JDD.ITE(dd1, dd2, dd3);\n\t\t\treturn new StateValuesMTBDD(dd, model);\n\t\t}\n\t\t// Otherwise result will be explicit\n\t\telse {\n\t\t\tdv2 = res2.convertToStateValuesDV().getDoubleVector();\n\t\t\tdv2.filter(dd1, allDDRowVars, odd);\n\t\t\tdv3 = res3.convertToStateValuesDV().getDoubleVector();\n\t\t\tdd1 = JDD.Not(dd1);\n\t\t\tdv3.filter(dd1, allDDRowVars, odd);\n\t\t\tdv2.add(dv3);\n\t\t\tdv3.clear();\n\t\t\tJDD.Deref(dd1);\n\t\t\treturn new StateValuesDV(dv2, model);\n\t\t}\n\t}\n\n\t/**\n\t * Check a binary operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionBinaryOp(ExpressionBinaryOp expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null, res2 = null;\n\t\tJDDNode dd, dd1, dd2;\n\t\tDoubleVector dv1, dv2;\n\t\tint i, n, op = expr.getOperator();\n\n\t\t// Optimisations are possible for relational operators\n\t\t// (note dubious use of knowledge that op IDs are consecutive)\n\t\tif (op >= ExpressionBinaryOp.EQ && op <= ExpressionBinaryOp.LE) {\n\t\t\treturn checkExpressionRelOp(op, expr.getOperand1(), expr.getOperand2(), statesOfInterest);\n\t\t}\n\n\t\t// Check operands recursively\n\t\ttry {\n\t\t\tres1 = checkExpression(expr.getOperand1(), statesOfInterest.copy());\n\t\t\tres2 = checkExpression(expr.getOperand2(), statesOfInterest.copy());\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tthrow e;\n\t\t} finally {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t}\n\n\t\t// If both operands are symbolic, result will be symbolic\n\t\tif (res1 instanceof StateValuesMTBDD && res2 instanceof StateValuesMTBDD) {\n\t\t\tdd1 = ((StateValuesMTBDD) res1).getJDDNode();\n\t\t\tdd2 = ((StateValuesMTBDD) res2).getJDDNode();\n\t\t\t// Apply operation\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionBinaryOp.IMPLIES:\n\t\t\t\tdd = JDD.Or(JDD.Not(dd1), dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.IFF:\n\t\t\t\tdd = JDD.Not(JDD.Xor(dd1, dd2));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.OR:\n\t\t\t\tdd = JDD.Or(dd1, dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.AND:\n\t\t\t\tdd = JDD.And(dd1, dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.PLUS:\n\t\t\t\tdd = JDD.Apply(JDD.PLUS, dd1, dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.MINUS:\n\t\t\t\tdd = JDD.Apply(JDD.MINUS, dd1, dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.TIMES:\n\t\t\t\tdd = JDD.Apply(JDD.TIMES, dd1, dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.DIVIDE:\n\t\t\t\tdd = JDD.Apply(JDD.DIVIDE, dd1, dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.POW:\n\t\t\t\t// Deref dd1/dd2 because may still need below\n\t\t\t\tJDD.Ref(dd1);\n\t\t\t\tJDD.Ref(dd2);\n\t\t\t\tdd = JDD.Apply(JDD.POW, dd1, dd2);\n\t\t\t\t// Check for some possible problems in case of integer power\n\t\t\t\t// (denote error with NaN for states with problems)\n\t\t\t\tif (expr.getType() instanceof TypeInt) {\n\t\t\t\t\t// Negative exponent not allowed for integer power\n\t\t\t\t\tJDD.Ref(dd2);\n\t\t\t\t\tdd = JDD.ITE(JDD.LessThan(dd2, 0), JDD.Constant(0.0 / 0.0), dd);\n\t\t\t\t\t// Check for integer overflow\n\t\t\t\t\tJDD.Ref(dd);\n\t\t\t\t\tdd = JDD.ITE(JDD.GreaterThan(dd, Integer.MAX_VALUE), JDD.Constant(0.0 / 0.0), dd);\n\t\t\t\t}\n\t\t\t\t// Late deref of dd1/dd2 because needed above\n\t\t\t\tJDD.Deref(dd1);\n\t\t\t\tJDD.Deref(dd2);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown binary operator\");\n\t\t\t}\n\t\t\treturn new StateValuesMTBDD(dd, model);\n\t\t}\n\t\t// Otherwise result will be explicit\n\t\telse {\n\t\t\tdv1 = res1.convertToStateValuesDV().getDoubleVector();\n\t\t\tdv2 = res2.convertToStateValuesDV().getDoubleVector();\n\t\t\tn = dv1.getSize();\n\t\t\t// Apply operation\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionBinaryOp.IMPLIES:\n\t\t\tcase ExpressionBinaryOp.OR:\n\t\t\tcase ExpressionBinaryOp.AND:\n\t\t\t\tthrow new PrismException(\"Internal error: Explicit evaluation of Boolean\");\n\t\t\t\t//for (i = 0; i < n; i++) dv1.setElement(i, (!(dv1.getElement(i)>0) || (dv2.getElement(i)>0)) ? 1.0 : 0.0);\n\t\t\t\t//for (i = 0; i < n; i++) dv1.setElement(i, ((dv1.getElement(i)>0) || (dv2.getElement(i)>0)) ? 1.0 : 0.0);\n\t\t\t\t//for (i = 0; i < n; i++) dv1.setElement(i, ((dv1.getElement(i)>0) && (dv2.getElement(i)>0)) ? 1.0 : 0.0);\n\t\t\tcase ExpressionBinaryOp.PLUS:\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, dv1.getElement(i) + dv2.getElement(i));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.MINUS:\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, dv1.getElement(i) - dv2.getElement(i));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.TIMES:\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, dv1.getElement(i) * dv2.getElement(i));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.DIVIDE:\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, dv1.getElement(i) / dv2.getElement(i));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.POW:\n\t\t\t\t// For integer power, have to check for errors and flag as NaN\n\t\t\t\tif (expr.getType() instanceof TypeInt) {\n\t\t\t\t\tdouble base, exp, pow;\n\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\tbase = dv1.getElement(i);\n\t\t\t\t\t\texp = dv2.getElement(i);\n\t\t\t\t\t\tpow = Math.pow(base, exp);\n\t\t\t\t\t\tdv1.setElement(i, (exp < 0 || pow > Integer.MAX_VALUE) ? 0.0 / 0.0 : pow);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\t\tdv1.setElement(i, Math.pow(dv1.getElement(i), dv2.getElement(i)));\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown binary operator\");\n\t\t\t}\n\t\t\tdv2.clear();\n\t\t\treturn new StateValuesDV(dv1, model);\n\t\t}\n\t}\n\n\t/**\n\t * Check a relational operator (=, !=, >, >=, < <=).\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionRelOp(int op, Expression expr1, Expression expr2, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null, res2 = null;\n\t\tJDDNode dd, dd1, dd2;\n\t\tString s;\n\n\t\t// Check for some easy (and common) special cases before resorting to\n\t\t// the general case\n\n\t\t// var relop int\n\t\tif (expr1 instanceof ExpressionVar && expr2.isConstant() && expr2.getType() instanceof TypeInt) {\n\t\t\tJDD.Deref(statesOfInterest);\n\n\t\t\tExpressionVar e1;\n\t\t\tExpression e2;\n\t\t\tint i, j, l, h, v;\n\t\t\te1 = (ExpressionVar) expr1;\n\t\t\te2 = expr2;\n\t\t\t// get var's index\n\t\t\ts = e1.getName();\n\t\t\tv = varList.getIndex(s);\n\t\t\tif (v == -1) {\n\t\t\t\tthrow new PrismLangException(\"Unknown variable \\\"\" + e1.getName() + \"\\\" (no index information)\", e1);\n\t\t\t}\n\t\t\t// get some info on the variable\n\t\t\tl = varList.getLow(v);\n\t\t\th = varList.getHigh(v);\n\t\t\t// create dd\n\t\t\tdd = JDD.Constant(0);\n\t\t\ti = e2.evaluateInt(constantValues);\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionBinaryOp.EQ:\n\t\t\t\tif (i >= l && i <= h)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], i - l, 1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.NE:\n\t\t\t\tif (i >= l && i <= h)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], i - l, 1);\n\t\t\t\tdd = JDD.Not(dd);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.GT:\n\t\t\t\tfor (j = i + 1; j <= h; j++)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], j - l, 1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.GE:\n\t\t\t\tfor (j = i; j <= h; j++)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], j - l, 1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.LT:\n\t\t\t\tfor (j = i - 1; j >= l; j--)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], j - l, 1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.LE:\n\t\t\t\tfor (j = i; j >= l; j--)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], j - l, 1);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown relational operator\");\n\t\t\t}\n\t\t\treturn new StateValuesMTBDD(dd, model);\n\t\t}\n\t\t// int relop var\n\t\telse if (expr1.isConstant() && expr1.getType() instanceof TypeInt && expr2 instanceof ExpressionVar) {\n\t\t\tJDD.Deref(statesOfInterest);\n\n\t\t\tExpression e1;\n\t\t\tExpressionVar e2;\n\t\t\tint i, j, l, h, v;\n\t\t\te1 = expr1;\n\t\t\te2 = (ExpressionVar) expr2;\n\t\t\t// get var's index\n\t\t\ts = e2.getName();\n\t\t\tv = varList.getIndex(s);\n\t\t\tif (v == -1) {\n\t\t\t\tthrow new PrismLangException(\"Unknown variable \\\"\" + e2.getName() + \"\\\" (no index information)\", e2);\n\t\t\t}\n\t\t\t// get some info on the variable\n\t\t\tl = varList.getLow(v);\n\t\t\th = varList.getHigh(v);\n\t\t\t// create dd\n\t\t\tdd = JDD.Constant(0);\n\t\t\ti = e1.evaluateInt(constantValues);\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionBinaryOp.EQ:\n\t\t\t\tif (i >= l && i <= h)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], i - l, 1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.NE:\n\t\t\t\tif (i >= l && i <= h)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], i - l, 1);\n\t\t\t\tdd = JDD.Not(dd);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.GT:\n\t\t\t\tfor (j = i - 1; j >= l; j--)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], j - l, 1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.GE:\n\t\t\t\tfor (j = i; j >= l; j--)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], j - l, 1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.LT:\n\t\t\t\tfor (j = i + 1; j <= h; j++)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], j - l, 1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionBinaryOp.LE:\n\t\t\t\tfor (j = i; j <= h; j++)\n\t\t\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], j - l, 1);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown relational operator\");\n\t\t\t}\n\t\t\treturn new StateValuesMTBDD(dd, model);\n\t\t}\n\n\t\t// General case.\n\t\t// Since the result is a Boolean and thus returned as an MTBDD, we\n\t\t// just convert both operands to MTBDDs first. Optimisations would be possible here.\n\t\t// Check operands recursively\n\t\ttry {\n\t\t\tres1 = checkExpression(expr1, statesOfInterest.copy());\n\t\t\tres2 = checkExpression(expr2, statesOfInterest.copy());\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tthrow e;\n\t\t} finally {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t}\n\t\tdd1 = res1.convertToStateValuesMTBDD().getJDDNode();\n\t\tdd2 = res2.convertToStateValuesMTBDD().getJDDNode();\n\t\tswitch (op) {\n\t\tcase ExpressionBinaryOp.EQ:\n\t\t\tdd = JDD.Apply(JDD.EQUALS, dd1, dd2);\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.NE:\n\t\t\tdd = JDD.Apply(JDD.NOTEQUALS, dd1, dd2);\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.GT:\n\t\t\tdd = JDD.Apply(JDD.GREATERTHAN, dd1, dd2);\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.GE:\n\t\t\tdd = JDD.Apply(JDD.GREATERTHANEQUALS, dd1, dd2);\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.LT:\n\t\t\tdd = JDD.Apply(JDD.LESSTHAN, dd1, dd2);\n\t\t\tbreak;\n\t\tcase ExpressionBinaryOp.LE:\n\t\t\tdd = JDD.Apply(JDD.LESSTHANEQUALS, dd1, dd2);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tthrow new PrismException(\"Unknown relational operator\");\n\t\t}\n\t\treturn new StateValuesMTBDD(dd, model);\n\t}\n\n\t/**\n\t * Check a unary operator.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionUnaryOp(ExpressionUnaryOp expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null;\n\t\tJDDNode dd, dd1;\n\t\tDoubleVector dv1;\n\t\tint i, n, op = expr.getOperator();\n\n\t\t// Check operand recursively\n\t\tres1 = checkExpression(expr.getOperand(), statesOfInterest);\n\n\t\t// Parentheses are easy - nothing to do:\n\t\tif (op == ExpressionUnaryOp.PARENTH)\n\t\t\treturn res1;\n\n\t\t// If operand is symbolic, result will be symbolic\n\t\tif (res1 instanceof StateValuesMTBDD) {\n\t\t\tdd1 = ((StateValuesMTBDD) res1).getJDDNode();\n\t\t\t// Apply operation\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionUnaryOp.NOT:\n\t\t\t\tdd = JDD.Not(dd1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionUnaryOp.MINUS:\n\t\t\t\tdd = JDD.Apply(JDD.MINUS, JDD.Constant(0), dd1);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown unary operator\");\n\t\t\t}\n\t\t\treturn new StateValuesMTBDD(dd, model);\n\t\t}\n\t\t// Otherwise result will be explicit\n\t\telse {\n\t\t\tdv1 = res1.convertToStateValuesDV().getDoubleVector();\n\t\t\tn = dv1.getSize();\n\t\t\t// Apply operation\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionUnaryOp.NOT:\n\t\t\t\tthrow new PrismException(\"Internal error: Explicit evaluation of Boolean\");\n\t\t\t\t//for (i = 0; i < n; i++) dv1.setElement(i, (dv1.getElement(i)>0) ? 0.0 : 1.0);\n\t\t\tcase ExpressionUnaryOp.MINUS:\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, -dv1.getElement(i));\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown unary operator\");\n\t\t\t}\n\t\t\treturn new StateValuesDV(dv1, model);\n\t\t}\n\t}\n\n\t/**\n\t * Check a 'function'.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionFunc(ExpressionFunc expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tswitch (expr.getNameCode()) {\n\t\tcase ExpressionFunc.MIN:\n\t\tcase ExpressionFunc.MAX:\n\t\t\treturn checkExpressionFuncNary(expr, statesOfInterest);\n\t\tcase ExpressionFunc.FLOOR:\n\t\tcase ExpressionFunc.CEIL:\n\t\tcase ExpressionFunc.ROUND:\n\t\t\treturn checkExpressionFuncUnary(expr, statesOfInterest);\n\t\tcase ExpressionFunc.POW:\n\t\tcase ExpressionFunc.MOD:\n\t\tcase ExpressionFunc.LOG:\n\t\t\treturn checkExpressionFuncBinary(expr, statesOfInterest);\n\t\tcase ExpressionFunc.MULTI:\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Multi-objective model checking is not supported for \" + model.getModelType() + \"s\");\n\t\tdefault:\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Unrecognised function \\\"\" + expr.getName() + \"\\\"\");\n\t\t}\n\t}\n\n\t/**\n\t * Check a unary 'function'.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionFuncUnary(ExpressionFunc expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null;\n\t\tJDDNode dd1;\n\t\tDoubleVector dv1;\n\t\tint i, n, op = expr.getNameCode();\n\n\t\t// Check operand recursively\n\t\tres1 = checkExpression(expr.getOperand(0), statesOfInterest);\n\t\t// Symbolic\n\t\tif (res1 instanceof StateValuesMTBDD) {\n\t\t\tdd1 = ((StateValuesMTBDD) res1).getJDDNode();\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionFunc.FLOOR:\n\t\t\t\t// NB: Floor result kept as double, so don't need to check if operand is NaN\n\t\t\t\tdd1 = JDD.MonadicApply(JDD.FLOOR, dd1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionFunc.CEIL:\n\t\t\t\t// NB: Ceil result kept as double, so don't need to check if operand is NaN\n\t\t\t\tdd1 = JDD.MonadicApply(JDD.CEIL, dd1);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionFunc.ROUND:\n\t\t\t\t// NB: Round result kept as double, so don't need to check if operand is NaN\n\t\t\t\tdd1 = JDD.MonadicApply(JDD.FLOOR, JDD.Plus(dd1, JDD.Constant(0.5)));\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\treturn new StateValuesMTBDD(dd1, model);\n\t\t}\n\t\t// Explicit\n\t\telse {\n\t\t\tdv1 = res1.convertToStateValuesDV().getDoubleVector();\n\t\t\tn = dv1.getSize();\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionFunc.FLOOR:\n\t\t\t\t// NB: Floor result kept as double, so don't need to check if operand is NaN\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, Math.floor(dv1.getElement(i)));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionFunc.CEIL:\n\t\t\t\t// NB: Ceil result kept as double, so don't need to check if operand is NaN\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, Math.ceil(dv1.getElement(i)));\n\t\t\t\tbreak;\n\t\t\tcase ExpressionFunc.ROUND:\n\t\t\t\t// NB: Round result kept as double, so don't need to check if operand is NaN\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, Math.round(dv1.getElement(i)));\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\treturn new StateValuesDV(dv1, model);\n\t\t}\n\t}\n\n\t/**\n\t * Check a binary 'function'.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionFuncBinary(ExpressionFunc expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null, res2 = null;\n\t\tJDDNode dd = null, dd1, dd2;\n\t\tDoubleVector dv1, dv2;\n\t\tint i, n, op = expr.getNameCode();\n\t\tdouble d = 0.0;\n\n\t\t// Check operands recursively\n\t\ttry {\n\t\t\tres1 = checkExpression(expr.getOperand(0), statesOfInterest.copy());\n\t\t\tres2 = checkExpression(expr.getOperand(1), statesOfInterest.copy());\n\t\t} catch (PrismException e) {\n\t\t\tif (res1 != null)\n\t\t\t\tres1.clear();\n\t\t\tthrow e;\n\t\t} finally {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t}\n\t\t// If both operands are symbolic, result will be symbolic\n\t\tif (res1 instanceof StateValuesMTBDD && res2 instanceof StateValuesMTBDD) {\n\t\t\tdd1 = ((StateValuesMTBDD) res1).getJDDNode();\n\t\t\tdd2 = ((StateValuesMTBDD) res2).getJDDNode();\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionFunc.POW:\n\t\t\t\t// Deref dd1/dd2 because may still need below\n\t\t\t\tJDD.Ref(dd1);\n\t\t\t\tJDD.Ref(dd2);\n\t\t\t\tdd = JDD.Apply(JDD.POW, dd1, dd2);\n\t\t\t\t// Check for some possible problems in case of integer power\n\t\t\t\t// (denote error with NaN for states with problems)\n\t\t\t\tif (expr.getType() instanceof TypeInt) {\n\t\t\t\t\t// Negative exponent not allowed for integer power\n\t\t\t\t\tJDD.Ref(dd2);\n\t\t\t\t\tdd = JDD.ITE(JDD.LessThan(dd2, 0), JDD.Constant(0.0 / 0.0), dd);\n\t\t\t\t\t// Check for integer overflow \n\t\t\t\t\tJDD.Ref(dd);\n\t\t\t\t\tdd = JDD.ITE(JDD.GreaterThan(dd, Integer.MAX_VALUE), JDD.Constant(0.0 / 0.0), dd);\n\t\t\t\t}\n\t\t\t\t// Late deref of dd1/dd2 because needed above\n\t\t\t\tJDD.Deref(dd1);\n\t\t\t\tJDD.Deref(dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionFunc.MOD:\n\t\t\t\tdd = JDD.Apply(JDD.MOD, dd1, dd2);\n\t\t\t\tbreak;\n\t\t\tcase ExpressionFunc.LOG:\n\t\t\t\tdd = JDD.Apply(JDD.LOGXY, dd1, dd2);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\treturn new StateValuesMTBDD(dd, model);\n\t\t}\n\t\t// Otherwise result will be explicit\n\t\telse {\n\t\t\tdv1 = res1.convertToStateValuesDV().getDoubleVector();\n\t\t\tdv2 = res2.convertToStateValuesDV().getDoubleVector();\n\t\t\tn = dv1.getSize();\n\t\t\tswitch (op) {\n\t\t\tcase ExpressionFunc.POW:\n\t\t\t\t// For integer power, have to check for errors and flag as NaN\n\t\t\t\tif (expr.getType() instanceof TypeInt) {\n\t\t\t\t\tdouble base, exp, pow;\n\t\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\t\tbase = dv1.getElement(i);\n\t\t\t\t\t\texp = dv2.getElement(i);\n\t\t\t\t\t\tpow = Math.pow(base, exp);\n\t\t\t\t\t\tdv1.setElement(i, (exp < 0 || pow > Integer.MAX_VALUE) ? 0.0 / 0.0 : pow);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\t\tdv1.setElement(i, Math.pow(dv1.getElement(i), dv2.getElement(i)));\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ExpressionFunc.MOD:\n\t\t\t\tfor (i = 0; i < n; i++) {\n\t\t\t\t\tdouble div = (int) dv2.getElement(i);\n\t\t\t\t\t// Non-positive divisor not allowed (flag as NaN)\n\t\t\t\t\td = (div <= 0) ? Double.NaN : (int) dv1.getElement(i) % (int) div;\n\t\t\t\t\t// Take care of negative case (% is remainder, not modulo)\n\t\t\t\t\tdv1.setElement(i, d < 0 ? d + div : d);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase ExpressionFunc.LOG:\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t\tdv1.setElement(i, PrismUtils.log(dv1.getElement(i), dv2.getElement(i)));\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tdv2.clear();\n\t\t\treturn new StateValuesDV(dv1, model);\n\t\t}\n\t}\n\n\t/**\n\t * Check an n-ary 'function'.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionFuncNary(ExpressionFunc expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tStateValues res1 = null, res2 = null;\n\t\tJDDNode dd1, dd2;\n\t\tDoubleVector dv1, dv2;\n\t\tint i, i2, n, n2, op = expr.getNameCode();\n\t\tboolean symbolic;\n\n\t\t// Check first operand recursively\n\t\tres1 = checkExpression(expr.getOperand(0), statesOfInterest.copy());\n\t\t// Go through remaining operands\n\t\t// Switch to explicit as soon as an operand is explicit\n\t\tn = expr.getNumOperands();\n\t\tsymbolic = (res1 instanceof StateValuesMTBDD);\n\t\tfor (i = 1; i < n; i++) {\n\t\t\ttry {\n\t\t\t\tres2 = checkExpression(expr.getOperand(i), statesOfInterest.copy());\n\t\t\t} catch (PrismException e) {\n\t\t\t\tif (res2 != null)\n\t\t\t\t\tres2.clear();\n\t\t\t\tJDD.Deref(statesOfInterest);\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t\t// Explicit\n\t\t\tif (!symbolic || !(res2 instanceof StateValuesMTBDD)) {\n\t\t\t\tsymbolic = false;\n\t\t\t\tdv1 = res1.convertToStateValuesDV().getDoubleVector();\n\t\t\t\tdv2 = res2.convertToStateValuesDV().getDoubleVector();\n\t\t\t\tn2 = dv1.getSize();\n\t\t\t\tswitch (op) {\n\t\t\t\tcase ExpressionFunc.MIN:\n\t\t\t\t\tfor (i2 = 0; i2 < n2; i2++)\n\t\t\t\t\t\tdv1.setElement(i2, Math.min(dv1.getElement(i), dv2.getElement(i)));\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionFunc.MAX:\n\t\t\t\t\tfor (i2 = 0; i2 < n2; i2++)\n\t\t\t\t\t\tdv1.setElement(i2, Math.max(dv1.getElement(i), dv2.getElement(i)));\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tdv2.clear();\n\t\t\t\tres1 = new StateValuesDV(dv1, model);\n\t\t\t}\n\t\t\t// Symbolic\n\t\t\telse {\n\t\t\t\tdd1 = ((StateValuesMTBDD) res1).getJDDNode();\n\t\t\t\tdd2 = ((StateValuesMTBDD) res2).getJDDNode();\n\t\t\t\tswitch (op) {\n\t\t\t\tcase ExpressionFunc.MIN:\n\t\t\t\t\tdd1 = JDD.Apply(JDD.MIN, dd1, dd2);\n\t\t\t\t\tbreak;\n\t\t\t\tcase ExpressionFunc.MAX:\n\t\t\t\t\tdd1 = JDD.Apply(JDD.MAX, dd1, dd2);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tres1 = new StateValuesMTBDD(dd1, model);\n\t\t\t}\n\t\t}\n\n\t\tJDD.Deref(statesOfInterest);\n\t\treturn res1;\n\t}\n\n\t/**\n\t * Check a literal.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionLiteral(ExpressionLiteral expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// it's more efficient to return the constant node\n\t\t// instead of a MTBDD function for ITE(statesOfInterest, value, 0),\n\t\t// so we ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\tdouble d = encodeToDouble(expr.getType(), expr.evaluate());\n\t\treturn new StateValuesMTBDD(JDD.Constant(d), model);\n\t}\n\n\t/**\n\t * Check a constant.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionConstant(ExpressionConstant expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// it's more efficient to return the constant node\n\t\t// instead of a MTBDD function for ITE(statesOfInterest, value, 0),\n\t\t// so we ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\tdouble d = encodeToDouble(expr.getType(), expr.evaluate(constantValues));\n\t\treturn new StateValuesMTBDD(JDD.Constant(d), model);\n\t}\n\n\t/**\n\t * Check a variable reference.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionVar(ExpressionVar expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tString s;\n\t\tint v, l, h, i;\n\t\tJDDNode dd;\n\n\t\t// it's generally more efficient not to restrict to statesOfInterest here\n\t\t// so we ignore statesOfInterest\n\t\tJDD.Deref(statesOfInterest);\n\n\t\ts = expr.getName();\n\t\t// get the variable's index\n\t\tv = varList.getIndex(s);\n\t\tif (v == -1) {\n\t\t\tthrow new PrismLangException(\"Unknown variable \\\"\" + expr.getName() + \"\\\"\", expr);\n\t\t}\n\t\t// get some info on the variable\n\t\tl = varList.getLow(v);\n\t\th = varList.getHigh(v);\n\t\t// create dd\n\t\tdd = JDD.Constant(0);\n\t\tfor (i = l; i <= h; i++) {\n\t\t\tdd = JDD.SetVectorElement(dd, varDDRowVars[v], i - l, i);\n\t\t}\n\n\t\treturn new StateValuesMTBDD(dd, model);\n\t}\n\n\t/**\n\t * Check a label.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionLabel(ExpressionLabel expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tLabelList ll;\n\t\tJDDNode dd;\n\t\tint i;\n\n\t\t// treat special cases\n\t\tif (expr.isDeadlockLabel()) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tdd = model.getDeadlocks();\n\t\t\tJDD.Ref(dd);\n\t\t\treturn new StateValuesMTBDD(dd, model);\n\t\t} else if (expr.isInitLabel()) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tdd = start;\n\t\t\tJDD.Ref(dd);\n\t\t\treturn new StateValuesMTBDD(dd, model);\n\t\t} else if (model.hasLabelDD(expr.getName())) {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tdd = model.getLabelDD(expr.getName());\n\t\t\treturn new StateValuesMTBDD(dd.copy(), model);\n\t\t} else {\n\t\t\t// get expression associated with label\n\t\t\tll = getLabelList();\n\t\t\ti = -1;\n\t\t\tif (ll != null)\n\t\t\t\ti = ll.getLabelIndex(expr.getName());\n\t\t\tif (i == -1)\n\t\t\t\tthrow new PrismException(\"Unknown label \\\"\" + expr.getName() + \"\\\" in property\");\n\t\t\t// check recursively\n\t\t\treturn checkExpression(ll.getLabel(i), statesOfInterest);\n\t\t}\n\t}\n\n\n\t/**\n\t * Check a property reference.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionProp(ExpressionProp expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Look up property and check recursively\n\t\tProperty prop = propertiesFile.lookUpPropertyObjectByName(expr.getName());\n\t\tif (prop != null) {\n\t\t\tmainLog.println(\"\\nModel checking : \" + prop);\n\t\t\treturn checkExpression(prop.getExpression(), statesOfInterest);\n\t\t} else {\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow new PrismException(\"Unknown property reference \" + expr);\n\t\t}\n\t}\n\n\t/**\n\t * Check a filter.\n\t * The result will have valid results at least for the states of interest (use model.getReach().copy() for all reachable states)\n\t * <br>[ REFS: <i>result</i>, DEREFS: statesOfInterest ]\n\t */\n\tprotected StateValues checkExpressionFilter(ExpressionFilter expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// Translate filter\n\t\tExpression filter = expr.getFilter();\n\t\t// Create default filter (true) if none given\n\t\tif (filter == null)\n\t\t\tfilter = Expression.True();\n\t\t// Remember whether filter is \"true\"\n\t\tboolean filterTrue = Expression.isTrue(filter);\n\t\t// Store some more info\n\t\tString filterStatesString = filterTrue ? \"all states\" : \"states satisfying filter\";\n\t\tJDDNode ddFilter = checkExpressionDD(filter,  model.getReach().copy());\n\t\tStateListMTBDD statesFilter = new StateListMTBDD(ddFilter, model);\n\t\t// Check if filter state set is empty; we treat this as an error\n\t\tif (ddFilter.equals(JDD.ZERO)) {\n\t\t\tthrow new PrismException(\"Filter satisfies no states\");\n\t\t}\n\t\t// Remember whether filter is for the initial state and, if so, whether there's just one\n\t\tboolean filterInit = (filter instanceof ExpressionLabel && ((ExpressionLabel) filter).isInitLabel());\n\t\tboolean filterInitSingle = filterInit & model.getNumInitialStates() == 1;\n\n\t\t// For some types of filter, store info that may be used to optimise model checking\n\t\tFilterOperator op = expr.getOperatorType();\n\t\tif (op == FilterOperator.STATE && ODDUtils.hasIntValue(odd)) {\n\t\t\t// Check filter satisfied by exactly one state\n\t\t\tif (statesFilter.size() != 1) {\n\t\t\t\tString s = \"Filter should be satisfied in exactly 1 state\";\n\t\t\t\ts += \" (but \\\"\" + filter + \"\\\" is true in \" + statesFilter.size() + \" states)\";\n\t\t\t\tthrow new PrismException(s);\n\t\t\t}\n\t\t\tcurrentFilter = new prism.Filter(Filter.FilterOperator.STATE, ODDUtils.GetIndexOfFirstFromDD(ddFilter, odd, allDDRowVars));\n\t\t} else if (op == FilterOperator.FORALL && filterInit && filterInitSingle && ODDUtils.hasIntValue(odd)) {\n\t\t\tcurrentFilter = new prism.Filter(Filter.FilterOperator.STATE, ODDUtils.GetIndexOfFirstFromDD(ddFilter, odd, allDDRowVars));\n\t\t} else if (op == FilterOperator.FIRST && filterInit && filterInitSingle && ODDUtils.hasIntValue(odd)) {\n\t\t\tcurrentFilter = new prism.Filter(Filter.FilterOperator.STATE, ODDUtils.GetIndexOfFirstFromDD(ddFilter, odd, allDDRowVars));\n\t\t} else {\n\t\t\tcurrentFilter = null;\n\t\t}\n\n\t\tStateValues vals = null;\n\t\ttry {\n\t\t\t// Check operand recursively, using the filter as the states of interest\n\t\t\tvals = checkExpression(expr.getOperand(), ddFilter.copy());\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(ddFilter);\n\t\t\tJDD.Deref(statesOfInterest);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// Print out number of states satisfying filter\n\t\tif (!filterInit && !expr.isInvisible()) {\n\t\t\tmainLog.println(\"\\nStates satisfying filter \" + filter + \": \" + statesFilter.sizeString());\n\t\t}\n\n\t\t// Compute result according to filter type\n\t\top = expr.getOperatorType();\n\t\tStateValues resVals = null;\n\t\tJDDNode ddMatch = null, dd = null;\n\t\tStateListMTBDD states;\n\t\tdouble d = 0.0, d2 = 0.0;\n\t\tboolean b = false;\n\t\tString resultExpl = null;\n\t\tObject resObj = null;\n\t\tAccuracy resAcc = null;\n\t\tswitch (op) {\n\t\tcase PRINT:\n\t\tcase PRINTALL:\n\t\t\t// Format of print-out depends on type\n\t\t\tif (expr.getType() instanceof TypeBool) {\n\t\t\t\t// NB: 'usual' case for filter(print,...) on Booleans is to use no filter\n\t\t\t\tmainLog.print(\"\\nSatisfying states\");\n\t\t\t\tmainLog.println(filterTrue ? \":\" : \" that are also in filter \" + filter + \":\");\n\t\t\t\tdd = vals.deepCopy().convertToStateValuesMTBDD().getJDDNode();\n\t\t\t\tJDD.Ref(ddFilter);\n\t\t\t\tdd = JDD.And(dd, ddFilter);\n\t\t\t\tnew StateListMTBDD(dd, model).print(mainLog);\n\t\t\t\tJDD.Deref(dd);\n\t\t\t} else {\n\t\t\t\t// TODO: integer-typed case: either add to print method or store in StateValues\n\t\t\t\tif (op == FilterOperator.PRINT) {\n\t\t\t\t\tmainLog.println(\"\\nResults (non-zero only) for filter \" + filter + \":\");\n\t\t\t\t\tvals.printFiltered(mainLog, ddFilter);\n\t\t\t\t} else {\n\t\t\t\t\tmainLog.println(\"\\nResults (including zeros) for filter \" + filter + \":\");\n\t\t\t\t\tvals.printFiltered(mainLog, ddFilter, false, false, true);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Result vector is unchanged; for PRINT/PRINTALL, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = vals;\n\t\t\t// Set vals to null to stop it being cleared below\n\t\t\tvals = null;\n\t\t\tbreak;\n\t\tcase STORE:\n\t\t\t// Not much to do here - will be handled below when we store in the Result object\n\t\t\t// Result vector is unchanged; like PRINT/PRINTALL, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = vals;\n\t\t\t// Set vals to null to stop it being cleared below\n\t\t\tvals = null;\n\t\t\tbreak;\n\t\tcase MIN:\n\t\t\t// Compute min\n\t\t\td = vals.minOverBDD(ddFilter);\n\t\t\t// Store as object/vector (note crazy Object cast to avoid Integer->int auto conversion)\n\t\t\tresObj = decodeFromDouble(expr.getType(), d);\n\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(d), model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Minimum value over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\t// Also find states that (are close to) selected value for display to log\n\t\t\tddMatch = vals.getBDDFromCloseValue(d);\n\t\t\tJDD.Ref(ddFilter);\n\t\t\tddMatch = JDD.And(ddMatch, ddFilter);\n\t\t\tbreak;\n\t\tcase MAX:\n\t\t\t// Compute max\n\t\t\td = vals.maxOverBDD(ddFilter);\n\t\t\t// Store as object/vector (note crazy Object cast to avoid Integer->int auto conversion)\n\t\t\tresObj = decodeFromDouble(expr.getType(), d);\n\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(d), model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Maximum value over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\t// Also find states that (are close to) selected value for display to log\n\t\t\tddMatch = vals.getBDDFromCloseValue(d);\n\t\t\tJDD.Ref(ddFilter);\n\t\t\tddMatch = JDD.And(ddMatch, ddFilter);\n\t\t\tbreak;\n\t\tcase ARGMIN:\n\t\t\t// Compute/display min\n\t\t\td = vals.minOverBDD(ddFilter);\n\t\t\tmainLog.print(\"\\nMinimum value over \" + filterStatesString + \": \");\n\t\t\tmainLog.println(decodeFromDouble(expr.getType(), d));\n\t\t\t// Find states that (are close to) selected value\n\t\t\tddMatch = vals.getBDDFromCloseValue(d);\n\t\t\tJDD.Ref(ddFilter);\n\t\t\tddMatch = JDD.And(ddMatch, ddFilter);\n\t\t\t// Store states in vector; for ARGMIN, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = new StateValuesMTBDD(ddMatch, model);\n\t\t\t// Print out number of matching states, but not the actual states\n\t\t\tmainLog.println(\"\\nNumber of states with minimum value: \" + resVals.getNNZString());\n\t\t\tddMatch = null;\n\t\t\tbreak;\n\t\tcase ARGMAX:\n\t\t\t// Compute/display max\n\t\t\td = vals.maxOverBDD(ddFilter);\n\t\t\tmainLog.print(\"\\nMaximum value over \" + filterStatesString + \": \");\n\t\t\tmainLog.println(decodeFromDouble(expr.getType(), d));\n\t\t\t// Find states that (are close to) selected value\n\t\t\tddMatch = vals.getBDDFromCloseValue(d);\n\t\t\tJDD.Ref(ddFilter);\n\t\t\tddMatch = JDD.And(ddMatch, ddFilter);\n\t\t\t// Store states in vector; for ARGMAX, don't store a single value (in resObj)\n\t\t\t// Also, don't bother with explanation string\n\t\t\tresVals = new StateValuesMTBDD(ddMatch, model);\n\t\t\t// Print out number of matching states, but not the actual states\n\t\t\tmainLog.println(\"\\nNumber of states with maximum value: \" + resVals.getNNZString());\n\t\t\tddMatch = null;\n\t\t\tbreak;\n\t\tcase COUNT:\n\t\t\t// Compute count\n\t\t\tvals.filter(ddFilter);\n\t\t\td = vals.getNNZ();\n\t\t\t// Store as object/vector\n\t\t\tresObj = Integer.valueOf((int) d);\n\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(d), model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = filterTrue ? \"Count of satisfying states\" : \"Count of satisfying states also in filter\";\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase SUM:\n\t\t\t// Compute sum\n\t\t\td = vals.sumOverBDD(ddFilter);\n\t\t\t// Store as object/vector (note crazy Object cast to avoid Integer->int auto conversion)\n\t\t\tresObj = decodeFromDouble(expr.getType(), d);\n\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(d), model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Sum over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase AVG:\n\t\t\t// Compute average\n\t\t\td = vals.sumOverBDD(ddFilter) / JDD.GetNumMinterms(ddFilter, allDDRowVars.n());\n\t\t\t// Store as object/vector\n\t\t\tresObj = Double.valueOf(d);\n\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(d), model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Average over \" + filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase FIRST:\n\t\t\t// Find first value\n\t\t\td = vals.firstFromBDD(ddFilter);\n\t\t\t// Store as object/vector\n\t\t\tresObj = decodeFromDouble(expr.getType(), d);\n\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(d), model);\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Value in \";\n\t\t\tif (filterInit) {\n\t\t\t\tresultExpl += filterInitSingle ? \"the initial state\" : \"first initial state\";\n\t\t\t} else {\n\t\t\t\tresultExpl += filterTrue ? \"the first state\" : \"first state satisfying filter\";\n\t\t\t}\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase RANGE:\n\t\t\t// Find range of values\n\t\t\td = vals.minOverBDD(ddFilter);\n\t\t\td2 = vals.maxOverBDD(ddFilter);\n\t\t\t// Store as object\n\t\t\tif (expr.getOperand().getType() instanceof TypeInt) {\n\t\t\t\tresObj = new prism.Interval((int) d, (int) d2);\n\t\t\t} else {\n\t\t\t\tresObj = new prism.Interval(d, d2);\n\t\t\t}\n\t\t\t// Leave result vector unchanged: for a range, result is only available from Result object\n\t\t\tresVals = vals;\n\t\t\t// Set vals to null to stop it being cleared below\n\t\t\tvals = null;\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Range of values over \";\n\t\t\tresultExpl += filterInit ? \"initial states\" : filterStatesString;\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tcase FORALL:\n\t\t\t// Get access to BDD for this\n\t\t\tdd = vals.convertToStateValuesMTBDD().getJDDNode();\n\t\t\t// Check \"for all\" over filter, store result\n\t\t\tJDD.Ref(ddFilter);\n\t\t\tdd = JDD.And(dd, ddFilter);\n\t\t\tstates = new StateListMTBDD(dd, model);\n\t\t\tb = dd.equals(ddFilter);\n\t\t\t// Store as object/vector\n\t\t\tresObj = Boolean.valueOf(b);\n\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(b ? 1.0 : 0.0), model);\n\t\t\t// Set vals to null so that is not clear()-ed twice\n\t\t\tvals = null;\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Property \" + (b ? \"\" : \"not \") + \"satisfied in \";\n\t\t\tmainLog.print(\"\\nProperty satisfied in \" + states.sizeString());\n\t\t\tif (filterInit) {\n\t\t\t\tif (filterInitSingle) {\n\t\t\t\t\tresultExpl += \"the initial state\";\n\t\t\t\t} else {\n\t\t\t\t\tresultExpl += \"all initial states\";\n\t\t\t\t}\n\t\t\t\tmainLog.println(\" of \" + model.getNumInitialStatesString() + \" initial states.\");\n\t\t\t} else {\n\t\t\t\tif (filterTrue) {\n\t\t\t\t\tresultExpl += \"all states\";\n\t\t\t\t\tmainLog.println(\" of all \" + model.getNumStatesString() + \" states.\");\n\t\t\t\t} else {\n\t\t\t\t\tresultExpl += \"all filter states\";\n\t\t\t\t\tmainLog.println(\" of \" + statesFilter.sizeString() + \" filter states.\");\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Derefs\n\t\t\tJDD.Deref(dd);\n\t\t\tbreak;\n\t\tcase EXISTS:\n\t\t\t// Get access to BDD for this\n\t\t\tdd = vals.convertToStateValuesMTBDD().getJDDNode();\n\t\t\t// Check \"there exists\" over filter\n\t\t\tJDD.Ref(ddFilter);\n\t\t\tdd = JDD.And(dd, ddFilter);\n\t\t\tb = !dd.equals(JDD.ZERO);\n\t\t\t// Store as object/vector\n\t\t\tresObj = Boolean.valueOf(b);\n\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(b ? 1.0 : 0.0), model);\n\t\t\t// Set vals to null so that is not clear()-ed twice\n\t\t\tvals = null;\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Property satisfied in \";\n\t\t\tif (filterTrue) {\n\t\t\t\tresultExpl += b ? \"at least one state\" : \"no states\";\n\t\t\t} else {\n\t\t\t\tresultExpl += b ? \"at least one filter state\" : \"no filter states\";\n\t\t\t}\n\t\t\tmainLog.println(\"\\n\" + resultExpl);\n\t\t\t// Derefs\n\t\t\tJDD.Deref(dd);\n\t\t\tbreak;\n\t\tcase STATE:\n\t\t\t// Results of type void are handled differently\n\t\t\tif (expr.getType() instanceof TypeVoid) {\n\t\t\t\t// Extract result from StateValuesVoid object \n\t\t\t\tresObj = ((StateValuesVoid) vals).getValue();\n\t\t\t\t// Leave result vector unchanged: for a range, result is only available from Result object\n\t\t\t\tresVals = vals;\n\t\t\t\t// Set vals to null to stop it being cleared below\n\t\t\t\tvals = null;\n\t\t\t} else {\n\t\t\t\t// Find first (only) value\n\t\t\t\td = vals.firstFromBDD(ddFilter);\n\t\t\t\t// Store as object/vector\n\t\t\t\tresObj = decodeFromDouble(expr.getType(), d);\n\t\t\t\tresAcc = vals.getAccuracy();\n\t\t\t\tresVals = new StateValuesMTBDD(JDD.Constant(d), model);\n\t\t\t}\n\t\t\t// Create explanation of result and print some details to log\n\t\t\tresultExpl = \"Value in \";\n\t\t\tif (filterInit) {\n\t\t\t\tresultExpl += \"the initial state\";\n\t\t\t} else {\n\t\t\t\tresultExpl += \"the filter state\";\n\t\t\t}\n\t\t\tmainLog.println(\"\\n\" + resultExpl + \": \" + resObj);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tJDD.Deref(ddFilter);\n\t\t\tthrow new PrismException(\"Unrecognised filter type \\\"\" + expr.getOperatorName() + \"\\\"\");\n\t\t}\n\n\t\t// For some operators, print out some matching states\n\t\tif (ddMatch != null) {\n\t\t\tstates = new StateListMTBDD(ddMatch, model);\n\t\t\tmainLog.print(\"\\nThere are \" + states.sizeString() + \" states with \");\n\t\t\tmainLog.print((expr.getType() instanceof TypeDouble ? \"(approximately) \" : \"\") + \"this value\");\n\t\t\tif (!verbose && (states.size() == -1 || states.size() > 10)) {\n\t\t\t\tmainLog.print(\".\\nThe first 10 states are displayed below. To view them all, enable verbose mode or use a print filter.\\n\");\n\t\t\t\tstates.print(mainLog, 10);\n\t\t\t} else {\n\t\t\t\tmainLog.print(\":\\n\");\n\t\t\t\tstates.print(mainLog);\n\t\t\t}\n\t\t\tJDD.Deref(ddMatch);\n\t\t}\n\n\t\t// Store result\n\t\tresult.setResult(resObj);\n\t\tresult.setAccuracy(resAcc);\n\t\t// Set result explanation (if none or disabled, clear)\n\t\tif (expr.getExplanationEnabled() && resultExpl != null) {\n\t\t\tresult.setExplanation(resultExpl.toLowerCase());\n\t\t} else {\n\t\t\tresult.setExplanation(null);\n\t\t}\n\t\t// Store vector if requested\n\t\tif (op == FilterOperator.STORE) {\n\t\t\tresult.setVector(resVals);\n\t\t}\n\t\t// Clear old vector if present\n\t\t// (and if the vector was not stored previously)\n\t\tif (vals != null && !(Expression.isFilter(expr.getOperand(), FilterOperator.STORE))) {\n\t\t\tvals.clear();\n\t\t}\n\t\t// Other derefs\n\t\tJDD.Deref(ddFilter);\n\t\tJDD.Deref(statesOfInterest);\n\n\t\treturn resVals;\n\t}\n\n\t// Utility functions for symbolic model checkers \n\t\n\t/**\n\t * Convert a value stored as an Object to its encoding as a double (for the MTBDD). \n\t */\n\tpublic static double encodeToDouble(Type type, Object val) throws PrismException {\n\t\t// Integer type\n\t\tif (type instanceof TypeInt) {\n\t\t\treturn ((TypeInt) type).castValueTo(val).intValue();\n\t\t}\n\t\t// Double type\n\t\telse if (type instanceof TypeDouble) {\n\t\t\treturn ((TypeDouble) type).castValueTo(val).doubleValue();\n\t\t}\n\t\t// Boolean type\n\t\telse if (type instanceof TypeBool) {\n\t\t\treturn ((TypeBool) type).castValueTo(val).booleanValue() ? 1.0 : 0.0;\n\t\t}\n\t\t// Anything else\n\t\tthrow new PrismException(\"Could not encode type \" + type + \" into an MTBDD\");\n\t}\n\t\n\t/**\n\t * Get a value as an Object, from its encoding as a double (for the MTBDD). \n\t */\n\tpublic static Object decodeFromDouble(Type type, double val) {\n\t\t// Integer type\n\t\tif (type instanceof TypeInt) {\n\t\t\treturn (int) val;\n\t\t}\n\t\t// Double type\n\t\telse if (type instanceof TypeDouble) {\n\t\t\treturn val;\n\t\t}\n\t\t// Boolean type\n\t\telse if (type instanceof TypeBool) {\n\t\t\treturn val > 0;\n\t\t}\n\t\t// Anything else\n\t\treturn null;\n\t}\n\t\n\t/**\n\t * Method for handling the recursive part of PCTL* checking, i.e.,\n\t * recursively checking maximal state subformulas and replacing them\n\t * with labels and the corresponding satisfaction sets.\n\t * <br>\n\t * Extracts maximal state formula from an LTL path formula,\n\t * model checks them (with the current model checker and the current model)\n\t * and replaces them with ExpressionLabel objects that correspond\n\t * to freshly generated labels attached to the model.\n\t * <br>\n\t * Returns the modified Expression.\n\t *\n\t * @param expr the expression (a path formula)\n\t */\n\tpublic Expression handleMaximalStateFormulas(Expression expr) throws PrismException\n\t{\n\t\tif (!(model instanceof ModelSymbolic)) {\n\t\t\t// needs a ModelSymbolic to allow attaching labels in the handleMaximalStateFormulas step\n\t\t\tthrow new PrismNotSupportedException(\"Need ModelSymbolic for LTL checking in this instance\");\n\t\t}\n\n\t\tVector<JDDNode> labelDD = new Vector<JDDNode>();\n\n\t\t// construct LTL model checker, using this model checker instance\n\t\t// (which is specialised for the model type) for the recursive\n\t\t// model checking computation\n\t\tLTLModelChecker ltlMC = new LTLModelChecker(this);\n\n\t\t// check the maximal state subformulas and gather\n\t\t// the satisfaction sets in labelBS, with index i\n\t\t// in the vector corresponding to label Li in the\n\t\t// returned formula\n\t\tExpression exprNew = ltlMC.checkMaximalStateFormulas(this, model, expr.deepCopy(), labelDD);\n\n\t\tHashMap<String, String> labelReplacements = new HashMap<String, String>();\n\t\tfor (int i=0; i < labelDD.size(); i++) {\n\t\t\tString currentLabel = \"L\"+i;\n\t\t\t// Attach satisfaction set for Li to the model, record necessary\n\t\t\t// label renaming\n\t\t\tString newLabel = ((ModelSymbolic) model).addUniqueLabelDD(\"phi\", labelDD.get(i), getDefinedLabelNames());\n\t\t\tlabelReplacements.put(currentLabel, newLabel);\n\t\t}\n\t\t// rename the labels\n\t\treturn (Expression) exprNew.accept(new ReplaceLabels(labelReplacements));\n\t}\n\n\t// Utility functions for symbolic model checkers \n\t\n\t/**\n\t * Get the state rewards (from a model) corresponding to the index of this R operator.\n\t * Throws an exception (with explanatory message) if it cannot be found.\n\t */\n\tpublic JDDNode getStateRewardsByIndexObject(Object rs, Model model, Values constantValues) throws PrismException\n\t{\n\t\tJDDNode stateRewards = null;\n\t\tif (model.getNumRewardStructs() == 0)\n\t\t\tthrow new PrismException(\"Model has no rewards specified\");\n\t\tif (rs == null) {\n\t\t\tstateRewards = model.getStateRewards(0);\n\t\t} else if (rs instanceof Expression) {\n\t\t\tint i = ((Expression) rs).evaluateInt(constantValues);\n\t\t\trs = Integer.valueOf(i); // for better error reporting below\n\t\t\tstateRewards = model.getStateRewards(i - 1);\n\t\t} else if (rs instanceof String) {\n\t\t\tstateRewards = model.getStateRewards((String) rs);\n\t\t}\n\t\tif (stateRewards == null)\n\t\t\tthrow new PrismException(\"Invalid reward structure index \\\"\" + rs + \"\\\"\");\n\t\treturn stateRewards; \n\t}\n\t\n\t/**\n\t * Get the transition rewards (from a model) corresponding to the index of this R operator.\n\t * Throws an exception (with explanatory message) if it cannot be found.\n\t */\n\tpublic JDDNode getTransitionRewardsByIndexObject(Object rs, Model model, Values constantValues) throws PrismException\n\t{\n\t\tJDDNode transRewards = null;\n\t\tif (model.getNumRewardStructs() == 0)\n\t\t\tthrow new PrismException(\"Model has no rewards specified\");\n\t\tif (rs == null) {\n\t\t\ttransRewards = model.getTransRewards(0);\n\t\t} else if (rs instanceof Expression) {\n\t\t\tint i = ((Expression) rs).evaluateInt(constantValues);\n\t\t\trs = Integer.valueOf(i); // for better error reporting below\n\t\t\ttransRewards = model.getTransRewards(i - 1);\n\t\t} else if (rs instanceof String) {\n\t\t\ttransRewards = model.getTransRewards((String) rs);\n\t\t}\n\t\tif (transRewards == null)\n\t\t\tthrow new PrismException(\"Invalid reward structure index \\\"\" + rs + \"\\\"\");\n\t\treturn transRewards; \n\t}\n\n\t/**\n\t * Check that rewards contained in an MTBDD are non-negative.\n\t * Throws an exception (with explanatory message) if negative rewards are found.\n\t * @param rewards The rewards MTBDD to check\n\t * @param rewardType A string describing the type of rewards: \"State\" or \"Transition\"\n\t */\n\tpublic void checkNegativeRewards(JDDNode rewards, String rewardType) throws PrismException\n\t{\n\t\tdouble rmin = JDD.FindMin(rewards);\n\t\tif (rmin < 0) {\n\t\t\tthrow new PrismException(rewardType + \" rewards are negative (\" + rmin + \") for some states\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn constantValues;\n\t}\n\n\t/**\n\t * Get the label list (combined list from properties file, if attached).\n\t * @return the label list for the properties/modules file, or {@code null} if not available.\n\t */\n\tpublic LabelList getLabelList()\n\t{\n\t\tif (propertiesFile != null) {\n\t\t\treturn propertiesFile.getCombinedLabelList(); // combined list from properties and modules file\n\t\t} else {\n\t\t\treturn null;\n\t\t}\n\t}\n\n\t/**\n\t * Return the set of label names that are defined\n\t * either by the model (from the modules file)\n\t * or properties file (if attached to the model checker).\n\t */\n\tpublic Set<String> getDefinedLabelNames()\n\t{\n\t\tTreeSet<String> definedLabelNames = new TreeSet<String>();\n\n\t\t// labels from the label list\n\t\tLabelList labelList = getLabelList();\n\t\tif (labelList != null) {\n\t\t\tdefinedLabelNames.addAll(labelList.getLabelNames());\n\t\t}\n\n\t\treturn definedLabelNames;\n\t}\n\n\t/**\n\t * Export the model.\n\t * @param exportTask Export task (destination, which parts of the model to export, options)\n\t */\n\tpublic void exportModel(ModelExportTask exportTask) throws PrismException\n\t{\n\t\tModelExportOptions exportOptions = exportTask.getExportOptions();\n\t\tFile file = exportTask.getFile();\n\t\tif (exportOptions.getFormat() == ModelExportFormat.DD_DOT) {\n\t\t\tJDD.ExportDDToDotFileLabelled(model.getTrans(), file.getPath(), model.getDDVarNames());\n\t\t\treturn;\n\t\t}\n\t\tif (exportOptions.getFormat() == ModelExportFormat.DRN || exportOptions.getFormat() == ModelExportFormat.UMB) {\n\t\t\tthrow new PrismException(\"Export \" + exportOptions.getFormat().description() + \" not yet supported by the symbolic engine\");\n\t\t}\n\n\t\ttry {\n\t\t\tmodel.exportToFile(file, exportOptions);\n\t\t} catch (FileNotFoundException e) {\n\t\t\tthrow new PrismException(\"Could not open file \\\"\" + file.getName() + \"\\\" for output\");\n\t\t}\n\n\t\t// For export to Dot with states, need to insert states info into file\n\t\tif (exportOptions.getFormat() == ModelExportFormat.DOT) {\n\t\t\ttry (PrismLog out = getPrismLogForFile(file, true)) {\n\t\t\t\tmodel.getReachableStates().printDot(out);\n\t\t\t\t// Print footer\n\t\t\t\tout.println(\"}\");\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Export the transition function/matrix.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportTransitions(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\texportModel(ModelExportTask.fromOptions(file, exportOptions));\n\t}\n\n\t/**\n\t * Export the state rewards for one reward structure.\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportStateRewards(int r, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\ttry {\n\t\t\tmodel.exportStateRewardsToFile(r, file, exportOptions);\n\t\t} catch (FileNotFoundException e) {\n\t\t\tthrow new PrismException(\"Could not open file \\\"\" + file.getName() + \"\\\" for output\");\n\t\t}\n\t}\n\n\t/**\n\t * Export the transition rewards for one reward structure.\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportTransRewards(int r, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\ttry {\n\t\t\tmodel.exportTransRewardsToFile(r, file, exportOptions);\n\t\t} catch (FileNotFoundException e) {\n\t\t\tthrow new PrismException(\"Could not open file \\\"\" + file.getName() + \"\\\" for output\");\n\t\t}\n\t}\n\n\t/**\n\t * Export the set of states.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportStates(File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\ttry (PrismLog out = getPrismLogForFile(file)) {\n\t\t\tmodel.exportStates(Prism.convertExportType(exportOptions), out);\n\t\t}\n\t}\n\n\t/**\n\t * Export a set of labels and the states that satisfy them.\n\t * @param labelNames The name of each label\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tpublic void exportLabels(List<String> labelNames, File file, ModelExportOptions exportOptions) throws PrismException\n\t{\n\t\t// Convert labels to BDDs\n\t\tint numLabels = labelNames.size();\n\t\tJDDNode labels[] = new JDDNode[numLabels];\n\t\tfor (int i = 0; i < numLabels; i++) {\n\t\t\tlabels[i] = checkExpressionDD(new ExpressionLabel(labelNames.get(i)), model.getReach().copy());\n\t\t}\n\n\t\t// Export them using the MTBDD engine\n\t\tString matlabVarName = \"l\";\n\t\tString labelNamesArr[] = labelNames.toArray(new String[labelNames.size()]);\n\t\ttry {\n\t\t\tPrismMTBDD.ExportLabels(labels, labelNamesArr, matlabVarName, allDDRowVars, odd, Prism.convertExportType(exportOptions), (file != null) ? file.getPath() : null);\n\t\t} catch (FileNotFoundException e) {\n\t\t\tthrow new PrismException(\"Could not open file \\\"\" + file.getName() + \"\\\" for output\");\n\t\t}\n\n\t\t// Derefs\n\t\tfor (int i = 0; i < numLabels; i++) {\n\t\t\tJDD.Deref(labels[i]);\n\t\t}\n\t}\n\n\t/**\n\t * Export the transition matrix to a Spy file.\n\t * @param file File to export to\n\t */\n\tpublic void exportTransitionsToSpyFile(File file) throws PrismException\n\t{\n\t\t// choose depth\n\t\tint depth = model.getAllDDRowVars().n();\n\t\tif (depth > 9)\n\t\t\tdepth = 9;\n\n\t\t// get rid of non det vars if necessary\n\t\tJDDNode tmp = model.getTrans();\n\t\tJDD.Ref(tmp);\n\t\tif (model.getModelType() == ModelType.MDP) {\n\t\t\ttmp = JDD.MaxAbstract(tmp, ((NondetModel) model).getAllDDNondetVars());\n\t\t}\n\n\t\t// export to spy file\n\t\tJDD.ExportMatrixToSpyFile(tmp, model.getAllDDRowVars(), model.getAllDDColVars(), depth, file.getPath());\n\t\tJDD.Deref(tmp);\n\t}\n}\n\n// ------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/comp/StochModelChecker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.comp;\n\nimport java.io.*;\n\nimport jdd.*;\nimport dv.*;\nimport mtbdd.*;\nimport prism.Prism;\nimport prism.PrismException;\nimport symbolic.states.StateValues;\nimport symbolic.states.StateValuesDV;\nimport symbolic.states.StateValuesMTBDD;\nimport sparse.*;\nimport hybrid.*;\nimport parser.ast.*;\nimport symbolic.model.Model;\nimport symbolic.model.ProbModel;\nimport symbolic.model.StochModel;\n\n/*\n * Model checker for CTMCs.\n * \n * Much of StochModelChecker's functionality is inherited from the parent\n * class ProbModelChecker (for DTMCs). Main differences are:\n * \n *  - Time-bounded operators have bounds that are doubles so the processing\n *    and computation for these is different. Methods:\n *    + checkProbBoundedUntil/checkRewardCumul/checkRewardInst\n *    + computeBoundedUntilProbs/computeCumulRewards\n *    \n *  - Likewise, transient probabilities are different. Methods:\n *    + doTransient/computeTransientProbs\n *    \n *  - In various cases, before we can reuse the numerical computation\n *    code from ProbModelChecker, we have to wrap the methods with code\n *    that first computes the embedded DTMC for the CTMC. This includes:\n *    + computeNextProbs/computeUntilProbs/computeReachRewards\n *      (for computeReachRewards we also modify the rewards)\n */\npublic class StochModelChecker extends ProbModelChecker\n{\n\t// Constructor\n\n\tpublic StochModelChecker(Prism prism, Model m, PropertiesFile pf) throws PrismException\n\t{\n\t\t// Initialise\n\t\tsuper(prism, m, pf);\n\t}\n\n\t// Override-able \"Constructor\"\n\n\tpublic ProbModelChecker createNewModelChecker(Prism prism, Model m, PropertiesFile pf) throws PrismException\n\t{\n\t\treturn new StochModelChecker(prism, m, pf);\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// Check method for each operator\n\t// -----------------------------------------------------------------------------------\n\n\t// bounded until\n\t@Override\n\tprotected StateValues checkProbBoundedUntil(ExpressionTemporal expr, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tdouble lTime, uTime; // time bounds\n\t\tExpression exprTmp;\n\t\tJDDNode b1, b2, tmp;\n\t\tStateValues tmpProbs = null, probs = null;\n\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// get info from bounded until\n\n\t\t// lower bound is 0 if not specified\n\t\t// (i.e. if until is of form U<=t)\n\t\texprTmp = expr.getLowerBound();\n\t\tif (exprTmp != null) {\n\t\t\tlTime = exprTmp.evaluateDouble(constantValues);\n\t\t\tif (lTime < 0) {\n\t\t\t\tthrow new PrismException(\"Invalid lower bound \" + lTime + \" in time-bounded until formula\");\n\t\t\t}\n\t\t} else {\n\t\t\tlTime = 0;\n\t\t}\n\t\t// upper bound is -1 if not specified\n\t\t// (i.e. if until is of form U>=t)\n\t\texprTmp = expr.getUpperBound();\n\t\tif (exprTmp != null) {\n\t\t\tuTime = exprTmp.evaluateDouble(constantValues);\n\t\t\tif (uTime < 0 || (uTime == 0 && expr.upperBoundIsStrict())) {\n\t\t\t\tString bound = (expr.upperBoundIsStrict() ? \"<\" : \"<=\") + uTime;\n\t\t\t\tthrow new PrismException(\"Invalid upper bound \" + bound + \" in time-bounded until formula\");\n\t\t\t}\n\t\t\tif (uTime < lTime) {\n\t\t\t\tthrow new PrismException(\"Upper bound must exceed lower bound in time-bounded until formula\");\n\t\t\t}\n\t\t} else {\n\t\t\tuTime = -1;\n\t\t}\n\n\t\t// model check operands first, statesOfInterest = all\n\t\tb1 = checkExpressionDD(expr.getOperand1(), model.getReach().copy());\n\t\ttry {\n\t\t\tb2 = checkExpressionDD(expr.getOperand2(), model.getReach().copy());\n\t\t} catch (PrismException e) {\n\t\t\tJDD.Deref(b1);\n\t\t\tthrow e;\n\t\t}\n\n\t\t// print out some info about num states\n\t\t// mainLog.print(\"\\nb1 = \" + JDD.GetNumMintermsString(b1,\n\t\t// allDDRowVars.n()));\n\t\t// mainLog.print(\" states, b2 = \" + JDD.GetNumMintermsString(b2,\n\t\t// allDDRowVars.n()) + \" states\\n\");\n\n\t\t// compute probabilities\n\n\t\t// a trivial case: \"U<=0\"\n\t\tif (lTime == 0 && uTime == 0) {\n\t\t\t// prob is 1 in b2 states, 0 otherwise\n\t\t\tJDD.Ref(b2);\n\t\t\tprobs = new StateValuesMTBDD(b2, model);\n\t\t} else {\n\n\t\t\t// break down into different cases to compute probabilities\n\n\t\t\t// >= lTime\n\t\t\tif (uTime == -1) {\n\t\t\t\t// check for special case of lTime == 0, this is actually an\n\t\t\t\t// unbounded until\n\t\t\t\tif (lTime == 0) {\n\t\t\t\t\t// compute probs\n\t\t\t\t\ttry {\n\t\t\t\t\t\tprobs = computeUntilProbs(trans, trans01, b1, b2);\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\tJDD.Deref(b1);\n\t\t\t\t\t\tJDD.Deref(b2);\n\t\t\t\t\t\tthrow e;\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// compute unbounded until probs\n\t\t\t\t\ttry {\n\t\t\t\t\t\ttmpProbs = computeUntilProbs(trans, trans01, b1, b2);\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\tJDD.Deref(b1);\n\t\t\t\t\t\tJDD.Deref(b2);\n\t\t\t\t\t\tthrow e;\n\t\t\t\t\t}\n\t\t\t\t\t// compute bounded until probs\n\t\t\t\t\ttry {\n\t\t\t\t\t\tprobs = computeBoundedUntilProbs(trans, trans01, b1, b1, lTime, tmpProbs);\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\ttmpProbs.clear();\n\t\t\t\t\t\tJDD.Deref(b1);\n\t\t\t\t\t\tJDD.Deref(b2);\n\t\t\t\t\t\tthrow e;\n\t\t\t\t\t}\n\t\t\t\t\ttmpProbs.clear();\n\t\t\t\t}\n\t\t\t}\n\t\t\t// <= uTime\n\t\t\telse if (lTime == 0) {\n\t\t\t\t// nb: uTime != 0 since would be caught above (trivial case)\n\t\t\t\tJDD.Ref(b1);\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\ttmp = JDD.And(b1, JDD.Not(b2));\n\t\t\t\ttry {\n\t\t\t\t\tprobs = computeBoundedUntilProbs(trans, trans01, b2, tmp, uTime, null);\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\tJDD.Deref(tmp);\n\t\t\t\t\tJDD.Deref(b1);\n\t\t\t\t\tJDD.Deref(b2);\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\t// set values to exactly 1 for target (b2) states\n\t\t\t\t// (these are computed inexactly during uniformisation)\n\t\t\t\tprobs.maxMTBDD(b2);\n\t\t\t}\n\t\t\t// [lTime,uTime] (including where lTime == uTime)\n\t\t\telse {\n\t\t\t\tJDD.Ref(b1);\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\ttmp = JDD.And(b1, JDD.Not(b2));\n\t\t\t\ttry {\n\t\t\t\t\ttmpProbs = computeBoundedUntilProbs(trans, trans01, b2, tmp, uTime - lTime, null);\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\tJDD.Deref(tmp);\n\t\t\t\t\tJDD.Deref(b1);\n\t\t\t\t\tJDD.Deref(b2);\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\t\t\t\tJDD.Deref(tmp);\n\t\t\t\ttry {\n\t\t\t\t\tprobs = computeBoundedUntilProbs(trans, trans01, b1, b1, lTime, tmpProbs);\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\ttmpProbs.clear();\n\t\t\t\t\tJDD.Deref(b1);\n\t\t\t\t\tJDD.Deref(b2);\n\t\t\t\t\tthrow e;\n\t\t\t\t}\n\t\t\t\ttmpProbs.clear();\n\t\t\t}\n\t\t}\n\n\t\t// derefs\n\t\tJDD.Deref(b1);\n\t\tJDD.Deref(b2);\n\n\t\treturn probs;\n\t}\n\n\t// cumulative reward\n\t@Override\n\tprotected StateValues checkRewardCumul(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest)\n\t\t\tthrows PrismException\n\t{\n\t\tdouble time; // time\n\t\tStateValues rewards = null;\n\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// get info from inst reward\n\t\ttime = expr.getUpperBound().evaluateDouble(constantValues);\n\t\tif (time < 0) {\n\t\t\tthrow new PrismException(\"Invalid time bound \" + time + \" in cumulative reward formula\");\n\t\t}\n\n\t\t// compute rewards\n\n\t\t// a trivial case: \"<=0\"\n\t\tif (time == 0) {\n\t\t\trewards = new StateValuesMTBDD(JDD.Constant(0), model);\n\t\t} else {\n\t\t\t// compute rewards\n\t\t\ttry {\n\t\t\t\trewards = computeCumulRewards(trans, trans01, stateRewards, transRewards, time);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t// inst reward\n\n\t@Override\n\tprotected StateValues checkRewardInst(ExpressionTemporal expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest)\n\t\t\tthrows PrismException\n\t{\n\t\tdouble time; // time\n\t\tStateValues sr = null, rewards = null;\n\n\t\tJDD.Deref(statesOfInterest);\n\n\t\t// get info from inst reward\n\t\ttime = expr.getUpperBound().evaluateDouble(constantValues);\n\t\tif (time < 0) {\n\t\t\tthrow new PrismException(\"Invalid bound \" + time + \" in instantaneous reward property\");\n\t\t}\n\n\t\t// compute rewards\n\n\t\t// a trivial case: \"=0\"\n\t\tif (time == 0) {\n\t\t\tJDD.Ref(stateRewards);\n\t\t\trewards = new StateValuesMTBDD(stateRewards, model);\n\t\t} else {\n\t\t\t// convert state rewards vector to appropriate type (depending on\n\t\t\t// engine)\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\tJDD.Ref(stateRewards);\n\t\t\t\tsr = new StateValuesMTBDD(stateRewards, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\t\tsr = new StateValuesDV(stateRewards, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.HYBRID:\n\t\t\t\tsr = new StateValuesDV(stateRewards, model);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t// and for the computation, we can reuse the computation for\n\t\t\t// time-bounded until formulae\n\t\t\t// which is nice\n\t\t\ttry {\n\t\t\t\trewards = computeBoundedUntilProbs(trans, trans01, reach, reach, time, sr);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tsr.clear();\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t\tsr.clear();\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t\n\t@Override\n\tprotected StateValues checkRewardCoSafeLTL(Expression expr, JDDNode stateRewards, JDDNode transRewards, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\t// compute state sets for the maximal state formulas,\n\t\t// attach as fresh labels which replace the state formulas in\n\t\t// expr\n\t\texpr = handleMaximalStateFormulas(expr);\n\n\t\t// Compute embedded Markov chain, don't convert reward structures of the\n\t\t// model, as we use the rewards given as parameters\n\t\tProbModel embeddedDTMC = ((StochModel)model).getEmbeddedDTMC(mainLog, false);\n\n\t\tJDDNode stateRewardsDTMC = null;\n\t\ttry {\n\t\t\t// state rewards are scaled, nothing to do for transition rewards\n\t\t\tJDDNode diags = JDD.SumAbstract(trans.copy(), allDDColVars);\n\t\t\tstateRewardsDTMC = JDD.Apply(JDD.DIVIDE, stateRewards.copy(), diags);\n\n\t\t\tProbModelChecker embeddedMC = (ProbModelChecker) createModelChecker(embeddedDTMC);\n\t\t\tStateValues sv = embeddedMC.checkRewardCoSafeLTL(expr, stateRewardsDTMC, transRewards, statesOfInterest);\n\n\t\t\t// update the model in the StateValues object back to the CTMC\n\t\t\tsv.switchModel(model);\n\t\t\treturn sv;\n\t\t} finally {\n\t\t\tembeddedDTMC.clear();\n\t\t\tif (stateRewardsDTMC != null)\n\t\t\t\tJDD.Deref(stateRewardsDTMC);\n\t\t}\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// do transient computation\n\t// -----------------------------------------------------------------------------------\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doTransient(double time) throws PrismException\n\t{\n\t\treturn doTransient(time, (StateValues) null);\n\t}\n\t\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Optionally, use the passed in file initDistFile to give the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t */\n\tpublic StateValues doTransient(double time, File initDistFile) throws PrismException\n\t{\n\t\tStateValues initDist = null;\n\n\t\tif (initDistFile != null) {\n\t\t\tmainLog.println(\"\\nImporting initial probability distribution from file \\\"\" + initDistFile + \"\\\"...\");\n\t\t\t// Build an empty vector of the appropriate type \n\t\t\tif (engine == Prism.MTBDD) {\n\t\t\t\tinitDist = new StateValuesMTBDD(JDD.Constant(0), model);\n\t\t\t} else {\n\t\t\t\tinitDist = new StateValuesDV(new DoubleVector(model.getNumStates()), model);\n\t\t\t}\n\t\t\t// Populate vector from file\n\t\t\tinitDist.readFromFile(initDistFile);\n\t\t}\n\t\t\n\t\treturn doTransient(time, initDist);\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Optionally, use the passed in vector initDist as the initial probability distribution (time 0).\n\t * If null, start from initial state (or uniform distribution over multiple initial states).\n\t * For reasons of efficiency, when a vector is passed in, it will be trampled over and\n\t * then deleted afterwards, so if you wanted it, take a copy. \n\t */\n\tpublic StateValues doTransient(double time, StateValues initDist) throws PrismException\n\t{\n\t\t// mtbdd stuff\n\t\tJDDNode start, init;\n\t\t// other stuff\n\t\tStateValues initDistNew = null, probs = null;\n\n\t\t// build initial distribution (if not specified)\n\t\tif (initDist == null) {\n\t\t\t// first construct as MTBDD\n\t\t\t// get initial states of model\n\t\t\tstart = model.getStart();\n\t\t\t// compute initial probability distribution (equiprobable over all start states)\n\t\t\tJDD.Ref(start);\n\t\t\tinit = JDD.Apply(JDD.DIVIDE, start, JDD.Constant(JDD.GetNumMinterms(start, allDDRowVars.n())));\n\t\t\t// if using MTBDD engine, distribution needs to be an MTBDD\n\t\t\tif (engine == Prism.MTBDD) {\n\t\t\t\tinitDistNew = new StateValuesMTBDD(init, model);\n\t\t\t}\n\t\t\t// for sparse/hybrid engines, distribution needs to be a double vector\n\t\t\telse {\n\t\t\t\tinitDistNew = new StateValuesDV(init, model);\n\t\t\t\tJDD.Deref(init);\n\t\t\t}\n\t\t} else {\n\t\t\tinitDistNew = initDist;\n\t\t}\n\t\t\n\t\t// compute transient probabilities\n\t\tprobs = computeTransientProbs(trans, initDistNew, time);\n\n\t\treturn probs;\n\t}\n\n\t// -----------------------------------------------------------------------------------\n\t// probability computation methods\n\t// -----------------------------------------------------------------------------------\n\n\t// compute probabilities for next\n\t@Override\n\tprotected StateValues computeNextProbs(JDDNode tr, JDDNode b)\n\t{\n\t\tJDDNode diags, emb;\n\t\tStateValues probs = null;\n\n\t\t// Compute embedded Markov chain\n\t\tJDD.Ref(tr);\n\t\tdiags = JDD.SumAbstract(tr, allDDColVars);\n\t\tJDD.Ref(tr);\n\t\tJDD.Ref(diags);\n\t\temb = JDD.Apply(JDD.DIVIDE, trans, diags);\n\t\tmainLog.println(\"\\nDiagonals vector: \" + JDD.GetInfoString(diags, allDDRowVars.n()));\n\t\tmainLog.println(\"Embedded Markov chain: \" + JDD.GetInfoString(emb, allDDRowVars.n() * 2));\n\n\t\t// And then use superclass (ProbModelChecker)\n\t\t// to compute probabilities\n\t\tprobs = super.computeNextProbs(emb, b);\n\n\t\t// derefs\n\t\tJDD.Deref(diags);\n\t\tJDD.Deref(emb);\n\n\t\treturn probs;\n\t}\n\n\t// compute probabilities for bounded until\n\n\t// nb: this is a generic function used by several different parts of the csl\n\t// bounded until\n\t// model checking algorithm. it actually computes, for each state, the sum\n\t// over 'b2' states\n\t// of the probability of being in that state at time 'time' multiplied by\n\t// the corresponding\n\t// probability in the vector 'multProbs', assuming that all states not in\n\t// 'nonabs' are absorbing\n\t// nb: if 'multProbs' is null it is assumed to be all 1s\n\t// nb: if not null, the type (StateValuesDV/MTBDD) of 'multProbs' must match\n\t// the current engine\n\t// i.e. DV for sparse/hybrid, MTBDD for mtbdd\n\n\tprotected StateValues computeBoundedUntilProbs(JDDNode tr, JDDNode tr01, JDDNode b2, JDDNode nonabs, double time,\n\t\t\tStateValues multProbs) throws PrismException\n\t{\n\t\tJDDNode multProbsMTBDD, probsMTBDD;\n\t\tDoubleVector multProbsDV, probsDV;\n\t\tStateValues probs = null;\n\n\t\t// if nonabs is empty and multProbs was null, we don't need to do any\n\t\t// further solution\n\t\t// likewise if time = 0 (and in this case we know multProbs will be null\n\t\t// anyway\n\t\t// because U[0,0] is treated as a special case)\n\t\tif ((nonabs.equals(JDD.ZERO) && multProbs == null) || (time == 0)) {\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\tJDD.Ref(b2);\n\t\t\t\tprobs = new StateValuesMTBDD(b2, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\tcase Prism.HYBRID:\n\t\t\t\tprobs = new StateValuesDV(b2, model);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\t// otherwise explicitly compute the probabilities\n\t\telse {\n\t\t\t// compute probabilities\n\t\t\tmainLog.println(\"\\nComputing probabilities...\");\n\t\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\t\ttry {\n\t\t\t\tswitch (engine) {\n\t\t\t\tcase Prism.MTBDD:\n\t\t\t\t\tmultProbsMTBDD = (multProbs == null) ? null : ((StateValuesMTBDD) multProbs).getJDDNode();\n\t\t\t\t\tprobsMTBDD = PrismMTBDD.StochBoundedUntil(tr, odd, allDDRowVars, allDDColVars, b2, nonabs, time,\n\t\t\t\t\t\t\tmultProbsMTBDD);\n\t\t\t\t\tprobs = new StateValuesMTBDD(probsMTBDD, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.SPARSE:\n\t\t\t\t\tmultProbsDV = (multProbs == null) ? null : ((StateValuesDV) multProbs).getDoubleVector();\n\t\t\t\t\tprobsDV = PrismSparse.StochBoundedUntil(tr, odd, allDDRowVars, allDDColVars, b2, nonabs, time,\n\t\t\t\t\t\t\tmultProbsDV);\n\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\tcase Prism.HYBRID:\n\t\t\t\t\tmultProbsDV = (multProbs == null) ? null : ((StateValuesDV) multProbs).getDoubleVector();\n\t\t\t\t\tprobsDV = PrismHybrid.StochBoundedUntil(tr, odd, allDDRowVars, allDDColVars, b2, nonabs, time,\n\t\t\t\t\t\t\tmultProbsDV);\n\t\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\tthrow e;\n\t\t\t}\n\t\t}\n\n\t\treturn probs;\n\t}\n\n\t// compute probabilities for until (general case)\n\t@Override\n\tprotected StateValues computeUntilProbs(JDDNode tr, JDDNode tr01, JDDNode b1, JDDNode b2) throws PrismException\n\t{\n\t\tJDDNode diags, emb;\n\t\tStateValues probs = null;\n\n\t\t// Compute embedded Markov chain\n\t\tJDD.Ref(tr);\n\t\tdiags = JDD.SumAbstract(tr, allDDColVars);\n\t\tJDD.Ref(tr);\n\t\tJDD.Ref(diags);\n\t\temb = JDD.Apply(JDD.DIVIDE, trans, diags);\n\t\tmainLog.println(\"\\nDiagonals vector: \" + JDD.GetInfoString(diags, allDDRowVars.n()));\n\t\tmainLog.println(\"Embedded Markov chain: \" + JDD.GetInfoString(emb, allDDRowVars.n() * 2));\n\n\t\t// And then use superclass (ProbModelChecker)\n\t\t// to compute probabilities\n\t\tprobs = super.computeUntilProbs(emb, tr01, b1, b2);\n\n\t\t// derefs\n\t\tJDD.Deref(diags);\n\t\tJDD.Deref(emb);\n\n\t\treturn probs;\n\t}\n\n\t// compute cumulative rewards\n\n\tprotected StateValues computeCumulRewards(JDDNode tr, JDDNode tr01, JDDNode sr, JDDNode trr, double time)\n\t\t\tthrows PrismException\n\t{\n\t\tJDDNode rewardsMTBDD;\n\t\tDoubleVector rewardsDV;\n\t\tStateValues rewards = null;\n\n\t\t// compute rewards\n\t\tmainLog.println(\"\\nComputing rewards...\");\n\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\ttry {\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\trewardsMTBDD = PrismMTBDD.StochCumulReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\trewards = new StateValuesMTBDD(rewardsMTBDD, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\t\trewardsDV = PrismSparse.StochCumulReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.HYBRID:\n\t\t\t\trewardsDV = PrismHybrid.StochCumulReward(tr, sr, trr, odd, allDDRowVars, allDDColVars, time);\n\t\t\t\trewards = new StateValuesDV(rewardsDV, model);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tthrow e;\n\t\t}\n\n\t\treturn rewards;\n\t}\n\n\t// compute total rewards\n\n\t@Override\n\tprotected StateValues computeTotalRewards(JDDNode tr, JDDNode tr01, JDDNode sr, JDDNode trr) throws PrismException\n\t{\n\t\tJDDNode diags, emb, srNew;\n\t\tStateValues rewards = null;\n\n\t\t// Compute embedded Markov chain\n\t\tJDD.Ref(tr);\n\t\tdiags = JDD.SumAbstract(tr, allDDColVars);\n\t\tJDD.Ref(tr);\n\t\tJDD.Ref(diags);\n\t\temb = JDD.Apply(JDD.DIVIDE, trans, diags);\n\t\tmainLog.println(\"\\nDiagonals vector: \" + JDD.GetInfoString(diags, allDDRowVars.n()));\n\t\tmainLog.println(\"Embedded Markov chain: \" + JDD.GetInfoString(emb, allDDRowVars.n() * 2));\n\n\t\t// Convert rewards\n\t\tJDD.Ref(sr);\n\t\tJDD.Ref(diags);\n\t\tsrNew = JDD.Apply(JDD.DIVIDE, sr, diags);\n\n\t\t// And then use superclass (ProbModelChecker)\n\t\t// to compute rewards\n\t\trewards = super.computeTotalRewards(emb, tr01, srNew, trr);\n\n\t\t// derefs\n\t\tJDD.Deref(diags);\n\t\tJDD.Deref(emb);\n\t\tJDD.Deref(srNew);\n\n\t\treturn rewards;\n\t}\n\t\n\t// compute rewards for reach reward\n\t@Override\n\tprotected StateValues computeReachRewards(JDDNode tr, JDDNode tr01, JDDNode sr, JDDNode trr, JDDNode b)\n\t\t\tthrows PrismException\n\t{\n\t\tJDDNode diags, emb, srNew;\n\t\tStateValues rewards = null;\n\n\t\t// Compute embedded Markov chain\n\t\tJDD.Ref(tr);\n\t\tdiags = JDD.SumAbstract(tr, allDDColVars);\n\t\tJDD.Ref(tr);\n\t\tJDD.Ref(diags);\n\t\temb = JDD.Apply(JDD.DIVIDE, trans, diags);\n\t\tmainLog.println(\"\\nDiagonals vector: \" + JDD.GetInfoString(diags, allDDRowVars.n()));\n\t\tmainLog.println(\"Embedded Markov chain: \" + JDD.GetInfoString(emb, allDDRowVars.n() * 2));\n\n\t\t// Convert rewards\n\t\tJDD.Ref(sr);\n\t\tJDD.Ref(diags);\n\t\tsrNew = JDD.Apply(JDD.DIVIDE, sr, diags);\n\n\t\t// And then use superclass (ProbModelChecker)\n\t\t// to compute rewards\n\t\trewards = super.computeReachRewards(emb, tr01, srNew, trr, b);\n\n\t\t// derefs\n\t\tJDD.Deref(diags);\n\t\tJDD.Deref(emb);\n\t\tJDD.Deref(srNew);\n\n\t\treturn rewards;\n\t}\n\n\t/**\n\t * Compute transient probability distribution (forwards).\n\t * Use the passed in vector initDist as the initial probability distribution (time 0).\n\t * The type of this should match the current engine\n\t * (i.e. StateValuesMTBDD for MTBDD, StateValuesDV for sparse/hybrid). \n\t * For reasons of efficiency, this vector will be trampled over and\n\t * then deleted afterwards, so if you wanted it, take a copy. \n\t */\n\tprotected StateValues computeTransientProbs(JDDNode tr, StateValues initDist, double time) throws PrismException\n\t{\n\t\tJDDNode probsMTBDD;\n\t\tDoubleVector probsDV;\n\t\tStateValues probs = null;\n\n\t\t// special case: time = 0\n\t\tif (time == 0.0) {\n\t\t\t// we are allowed to keep the init vector, so no need to clone\n\t\t\treturn initDist;\n\t\t}\n\t\t\n\t\t// general case\n\t\tmainLog.println(\"\\nComputing probabilities...\");\n\t\tmainLog.println(\"Engine: \" + Prism.getEngineString(engine));\n\t\ttry {\n\t\t\tswitch (engine) {\n\t\t\tcase Prism.MTBDD:\n\t\t\t\tprobsMTBDD = PrismMTBDD.StochTransient(tr, odd, ((StateValuesMTBDD) initDist).getJDDNode(), allDDRowVars, allDDColVars, time);\n\t\t\t\tprobs = new StateValuesMTBDD(probsMTBDD, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.SPARSE:\n\t\t\t\tprobsDV = PrismSparse.StochTransient(tr, odd, ((StateValuesDV) initDist).getDoubleVector(), allDDRowVars, allDDColVars, time);\n\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\tbreak;\n\t\t\tcase Prism.HYBRID:\n\t\t\t\tprobsDV = PrismHybrid.StochTransient(tr, odd, ((StateValuesDV) initDist).getDoubleVector(), allDDRowVars, allDDColVars, time);\n\t\t\t\tprobs = new StateValuesDV(probsDV, model);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tthrow new PrismException(\"Unknown engine\");\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tthrow e;\n\t\t}\n\n\t\treturn probs;\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/MDPQuotient.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2016-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de>\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage symbolic.model;\n\nimport java.util.List;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport jdd.SanityJDD;\nimport symbolic.comp.ECComputer;\nimport prism.PrismComponent;\nimport prism.PrismException;\nimport symbolic.states.StateValues;\nimport symbolic.states.StateValuesMTBDD;\n\n/**\n * Transformation for obtaining the quotient MDP for an MDP, given an\n * equivalence relation.\n * <br>\n * Given a list of equivalent classes (have to be disjoint, but don't need\n * to cover the whole state space), each class is collapsed to a single state,\n * the representative for the class.\n * <br>\n * Transitions from and to a state in an equivalence class are attached\n * to the representative instead.\n * To allow a symbolic treatment, several new non-deterministic choice\n * variables are introduced, yielding action labels of the form (t,s,alpha):\n * <ul>\n * <li>(!tau, 0, alpha) corresponds to an action alpha in the original model (not originating\n *     from a state in an equivalence class)</li>\n * <li>(tau, s, alpha) corresponds to an action alpha that originated from state s in some equivalence class</li>\n * </ul>\n * Self-loop actions on the representative, i.e., actions where the representative is the\n * only successor, are removed in most cases. They are only retained if the representative\n * would become a deadlock state otherwise.\n * <br>\n * Rewards are handled as follows:\n * <ul>\n * <li>State rewards for all states in equivalence classes are set to zero</li>\n * <li>Transition rewards for all state-action pairs where all successors\n *     remain in the equivalence class are set to zero as well (this is visible for the self-loops on\n *     representatives that would be deadlocks otherwise)</li>\n * </ul>\n * <br>\n * Labels attached to the original model are currently effectively stripped,\n * i.e., they are replaced with JDD.ZERO. In the future, more advanced treatment\n * may be added.\n * <br>\n * Note as well that evaluating expressions in the quotient model will not lead to correct results.\n */\npublic class MDPQuotient implements ModelTransformation<NondetModel,NondetModel>\n{\n\tprivate NondetModel originalModel;\n\tprivate NondetModel transformedModel;\n\tprivate MDPQuotientOperator transform;\n\tprivate JDDNode transformedStatesOfInterest;\n\n\t/** Private constructor */\n\tprivate MDPQuotient(NondetModel originalModel, NondetModel transformedModel, MDPQuotientOperator transform, JDDNode transformedStatesOfInterest)\n\t{\n\t\tthis.originalModel = originalModel;\n\t\tthis.transformedModel = transformedModel;\n\t\tthis.transform = transform;\n\t\tthis.transformedStatesOfInterest = transformedStatesOfInterest;\n\t}\n\n\t@Override\n\tpublic NondetModel getOriginalModel()\n\t{\n\t\treturn originalModel;\n\t}\n\n\t@Override\n\tpublic NondetModel getTransformedModel()\n\t{\n\t\treturn transformedModel;\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\ttransformedModel.clear();\n\t\ttransform.clear();\n\t\tJDD.Deref(transformedStatesOfInterest);\n\t}\n\n\t@Override\n\tpublic StateValues projectToOriginalModel(StateValues svTransformedModel) throws PrismException\n\t{\n\t\tStateValuesMTBDD sv = svTransformedModel.convertToStateValuesMTBDD();\n\t\tJDDNode v = sv.getJDDNode().copy();\n\t\tsv.clear();\n\n\t\tv = transform.liftFromRepresentatives(v);\n\n\t\treturn new StateValuesMTBDD(v, transform.originalModel);\n\t}\n\n\t/** Map the given state set from the original model to the quotient model */\n\tpublic JDDNode mapStateSetToQuotient(JDDNode S)\n\t{\n\t\treturn transform.mapStateSet(S);\n\t}\n\n\t@Override\n\tpublic JDDNode getTransformedStatesOfInterest()\n\t{\n\t\treturn transformedStatesOfInterest;\n\t}\n\n\t/**\n\t * Compute the quotient MDP, collapsing each maximal end component (MEC) to a single state.\n\t * Only collapses MECs contained in {@code restrict}.\n\t *\n\t * <br>[ REFs: <i>result</i>, DEREFs: restrict ]\n\t */\n\tpublic static MDPQuotient mecQuotient(PrismComponent parent, final NondetModel model, JDDNode restrict, JDDNode statesOfInterest) throws PrismException\n\t{\n\t\tECComputer ec = ECComputer.createECComputer(parent, model);\n\t\tec.computeMECStates(restrict);\n\t\tJDD.Deref(restrict);\n\n\t\treturn transform(parent, model, ec.getMECStates(), statesOfInterest);\n\t}\n\n\t/**\n\t * Compute the quotient MDP for the given list of equivalence classes (the classes have to be disjoint).\n\t *\n\t * <br>[ REFs: <i>result</i>, DEREFs: equivalenceClasses, statesOfInterest ]\n\t */\n\tpublic static MDPQuotient transform(PrismComponent parent, final NondetModel model, List<JDDNode> equivalentClasses, JDDNode statesOfInterest)\n\t\t\tthrows PrismException\n\t{\n\t\tfinal MDPQuotientOperator transform = new MDPQuotientOperator(parent, model, equivalentClasses);\n\t\tfinal JDDNode transformedStatesOfInterest = transform.mapStateSet(statesOfInterest);\n\n\t\tfinal NondetModel quotient = model.getTransformed(transform);\n\n\t\treturn new MDPQuotient(model, quotient, transform, transformedStatesOfInterest);\n\t}\n\n\t/** The transformation operator for the MDPQuotient operation. */\n\tpublic static class MDPQuotientOperator extends NondetModelTransformationOperator\n\t{\n\t\t/** the list of equivalence classes */\n\t\tprivate List<JDDNode> equivalentClasses;\n\n\t\t/**\n\t\t * A symbolic mapping (0/1-ADD) from states (row vars) to their representative (col vars)\n\t\t * in the quotient model.<br>\n\t\t * For states in equivalence classes map to the representative, states not contained in\n\t\t * an equivalent class are mapped to themselves.\n\t\t */\n\t\tprivate JDDNode map;\n\n\t\t/** State set: states contained in equivalence classes */\n\t\tprivate JDDNode inEC;\n\n\t\t/** State set: states not contained in equivalence classes */\n\t\tprivate JDDNode notInEC;\n\n\t\t/** State set: representative states for equivalence classes */\n\t\tprivate JDDNode representatives = JDD.Constant(0);\n\n\t\t/**\n\t\t * n JDDVars, where n = number of row vars in the original model.\n\t\t * Used to store the original originating state of a transition in\n\t\t * the quotient model.\n\t\t */\n\t\tprivate JDDVars actFromStates;\n\n\t\t/** Set of (s,alpha) where all successors are again in the same equivalence class */\n\t\tprivate JDDNode stateActionsInsideECs;\n\n\t\t/** The transition relation of the quotient model */\n\t\tprivate JDDNode newTrans;\n\t\t/** The 0/1-transition relation of the quotient model */\n\t\tprivate JDDNode newTrans01;\n\t\t/** Self loops on quotient representative states that are not to be dropped */\n\t\tprivate JDDNode ecRemainingSelfLoops = JDD.Constant(0);\n\n\t\t/** New transition matrix already computed? */\n\t\tprivate boolean computed = false;\n\n\t\t/** The parent prism component (for logging) */\n\t\tprivate PrismComponent parent;\n\n\t\t/** Debug: Verbose output? */\n\t\tprivate boolean verbose = false;\n\n\t\t/** Constructor */\n\t\tpublic MDPQuotientOperator(PrismComponent parent, NondetModel model, List<JDDNode> equivalentClasses)\n\t\t{\n\t\t\tsuper(model);\n\n\t\t\tthis.equivalentClasses = equivalentClasses;\n\t\t\tthis.parent = parent;\n\n\t\t\tmap = JDD.Constant(0);\n\t\t\tinEC = JDD.Constant(0);\n\t\t\tstateActionsInsideECs = JDD.Constant(0);\n\n\t\t\tfor (JDDNode ec : equivalentClasses) {\n\t\t\t\t// determine representative for the EC\n\t\t\t\tJDDNode rep = JDD.RestrictToFirst(ec.copy(), model.getAllDDRowVars());\n\t\t\t\t// map = { s in EC } -> representative'\n\t\t\t\tmap = JDD.Or(map, JDD.And(ec.copy(),\n\t\t\t\t\t\tJDD.PermuteVariables(rep.copy(),\n\t\t\t\t\t\t\t\tmodel.getAllDDRowVars(),\n\t\t\t\t\t\t\t\tmodel.getAllDDColVars())));\n\t\t\t\t// remember all states in ECs\n\t\t\t\tinEC = JDD.Or(inEC, ec.copy());\n\t\t\t\trepresentatives = JDD.Or(representatives, rep);\n\n\t\t\t\tJDDNode ecCol = JDD.PermuteVariables(ec.copy(), model.getAllDDRowVars(), model.getAllDDColVars());\n\t\t\t\tJDDNode transFromEC01 = JDD.And(ec.copy(), model.getTrans01().copy());\n\t\t\t\tJDDNode selfLoop = JDD.Times(transFromEC01.copy(), ecCol.copy());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), selfLoop.copy(), \"selfLoop\");\n\t\t\t\tJDDNode stateActionWithSelfLoop = JDD.ThereExists(selfLoop, originalModel.getAllDDColVars());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionWithSelfLoop.copy(), \"stateActionWithSelfLoop\");\n\n\t\t\t\t// from the state action pairs with self loop, find those that also go somewhere\n\t\t\t\t// else\n\t\t\t\tJDDNode stateActionElse = JDD.And(stateActionWithSelfLoop.copy(), transFromEC01.copy());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionElse.copy(), \"stateActionElse\");\n\t\t\t\tstateActionElse = JDD.And(stateActionElse, JDD.Not(ecCol.copy()));\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionElse.copy(), \"stateActionElse (2)\");\n\t\t\t\tstateActionElse = JDD.ThereExists(stateActionElse, originalModel.getAllDDColVars());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionElse.copy(), \"stateActionElse (3)\");\n\t\t\t\tJDDNode stateActionWithOnlySelfLoop = JDD.And(stateActionWithSelfLoop, JDD.Not(stateActionElse));\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionWithOnlySelfLoop.copy(), \"stateActionOnlySelfLoop\");\n\n\t\t\t\tstateActionsInsideECs = JDD.Or(stateActionsInsideECs, stateActionWithOnlySelfLoop);\n\n\t\t\t\tJDD.Deref(ecCol, transFromEC01);\n\t\t\t}\n\n\t\t\t// all states not in EC\n\t\t\tnotInEC = JDD.And(model.getReach().copy(),\n\t\t\t\t\tJDD.Not(inEC.copy()));\n\n\t\t\t// map all states not in EC to themselves\n\t\t\tmap = JDD.ITE(notInEC.copy(),\n\t\t\t\t\tJDD.Identity(model.getAllDDRowVars(), model.getAllDDColVars()),\n\t\t\t\t\tmap);\n\t\t}\n\n\t\t@Override\n\t\tpublic void clear()\n\t\t{\n\t\t\tfor (JDDNode ec : equivalentClasses) {\n\t\t\t\tJDD.Deref(ec);\n\t\t\t}\n\t\t\tJDD.Deref(map);\n\t\t\tJDD.Deref(inEC);\n\t\t\tJDD.Deref(notInEC);\n\t\t\tJDD.Deref(representatives);\n\t\t\tJDD.Deref(stateActionsInsideECs);\n\t\t\tJDD.Deref(ecRemainingSelfLoops);\n\t\t\tif (newTrans != null) JDD.Deref(newTrans);\n\t\t\tif (newTrans01 != null) JDD.Deref(newTrans01);\n\t\t\tif (actFromStates != null)\n\t\t\t\tactFromStates.derefAll();\n\t\t\tsuper.clear();\n\t\t}\n\n\t\t@Override\n\t\tpublic int getExtraStateVariableCount()\n\t\t{\n\t\t\treturn 0;\n\t\t}\n\n\t\t@Override\n\t\tpublic int getExtraActionVariableCount()\n\t\t{\n\t\t\t// 1 bit (tau) for normal vs special action (leaving a representative),\n\t\t\t// numDDRowVar bits to remember original originating state\n\t\t\t// for the states leaving a representative\n\t\t\treturn originalModel.getNumDDRowVars() + 1;\n\t\t}\n\n\t\t@Override\n\t\tpublic void hookExtraActionVariableAllocation(JDDVars extraActionVars)\n\t\t{\n\t\t\t// call super to store extraActionVars\n\t\t\tsuper.hookExtraActionVariableAllocation(extraActionVars);\n\n\t\t\t// initialize actFromStates\n\t\t\tactFromStates = new JDDVars();\n\t\t\tfor (int i = 1; i < extraActionVars.n(); i++) {\n\t\t\t\tactFromStates.addVar(extraActionVars.getVar(i).copy());\n\t\t\t}\n\t\t}\n\n\t\t/** Get the tau action variable */\n\t\tpublic JDDNode getTauVar()\n\t\t{\n\t\t\treturn extraActionVars.getVar(0).copy();\n\t\t}\n\n\t\t/** Get the marker for a tau action */\n\t\tpublic JDDNode tau()\n\t\t{\n\t\t\treturn getTauVar();\n\t\t}\n\n\t\t/** Get the marker for a non-tau action (!tau & zeros for all other extra action vars) */\n\t\tpublic JDDNode notTau()\n\t\t{\n\t\t\tJDDNode notTau = JDD.Not(getTauVar());\n\t\t\tnotTau = JDD.And(notTau, actFromStates.allZero());\n\t\t\treturn notTau;\n\t\t}\n\n\t\tprivate void compute() throws PrismException\n\t\t{\n\t\t\tJDDNode trans = originalModel.getTrans().copy();\n\n\t\t\t// first run: collapse the target state ECs\n\n\t\t\tif (verbose) parent.getLog().println(\"Collapsing target states\");\n\t\t\tfor (JDDNode ec : equivalentClasses) {\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), trans.copy(), \"trans\");\n\t\t\t\tJDDNode ecCol = JDD.PermuteVariables(ec.copy(), originalModel.getAllDDRowVars(), originalModel.getAllDDColVars());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), ec.copy(), \"EC\");\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), ecCol.copy(), \"EC'\");\n\n\t\t\t\tJDDNode representative = JDD.RestrictToFirst(ec.copy(), originalModel.getAllDDRowVars());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), representative.copy(), \"rep\");\n\t\t\t\tJDDNode representativeCol = JDD.PermuteVariables(representative.copy(), originalModel.getAllDDRowVars(), originalModel.getAllDDColVars());\n\n\t\t\t\tJDDNode transToEC = JDD.Times(trans.copy(), ecCol.copy());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transToEC.copy(), \"transToEC\");\n\t\t\t\ttransToEC = JDD.SumAbstract(transToEC, originalModel.getAllDDColVars());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transToEC.copy(), \"transToEC (2)\");\n\t\t\t\ttransToEC = JDD.Times(transToEC, representativeCol.copy());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transToEC.copy(), \"transToEC (3)\");\n\n\t\t\t\ttrans = JDD.ITE(ecCol, transToEC, trans);\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), trans.copy(), \"trans''\");\n\n\t\t\t\tJDD.Deref(representative, representativeCol);\n\t\t\t}\n\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), trans.copy(), \"trans (after collapsing target states)\");\n\n\t\t\tnewTrans = JDD.Constant(0);\n\t\t\tif (verbose) parent.getLog().println(\"\\nCollapsing from states\");\n\t\t\tfor (JDDNode ec : equivalentClasses) {\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), ec.copy(), \"EC\");\n\n\t\t\t\tJDDNode representative = JDD.RestrictToFirst(ec.copy(), originalModel.getAllDDRowVars());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), representative.copy(), \"rep\");\n\t\t\t\tJDDNode representativeCol = JDD.PermuteVariables(representative.copy(), originalModel.getAllDDRowVars(), originalModel.getAllDDColVars());\n\n\t\t\t\tJDDNode transFromEC = JDD.Times(ec.copy(), trans.copy());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transFromEC.copy(), \"transFromEC\");\n\n\t\t\t\t// shift from states to actFromEC\n\t\t\t\ttransFromEC = JDD.PermuteVariables(transFromEC, originalModel.getAllDDRowVars(), actFromStates);\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transFromEC.copy(), \"transFromEC (2)\");\n\t\t\t\ttransFromEC = JDD.Times(tau(), representative.copy(), transFromEC);\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transFromEC.copy(), \"transFromEC (3)\");\n\n\t\t\t\t// remove self-loop actions back to the EC,\n\t\t\t\t// i.e. actions representative,a where all successors go back to\n\t\t\t\t// the representative\n\t\t\t\tJDDNode transFromEC01 = JDD.GreaterThan(transFromEC.copy(), 0);\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transFromEC01.copy(), \"transFromEC01\");\n\t\t\t\tJDDNode selfLoop = JDD.Times(transFromEC01.copy(), representativeCol.copy());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), selfLoop.copy(), \"selfLoop\");\n\t\t\t\tJDDNode stateActionWithSelfLoop = JDD.ThereExists(selfLoop, originalModel.getAllDDColVars());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionWithSelfLoop.copy(), \"stateActionWithSelfLoop\");\n\n\t\t\t\t// from the state action pairs with self loop, find those that also go somewhere\n\t\t\t\t// else\n\t\t\t\tJDDNode stateActionElse = JDD.And(stateActionWithSelfLoop.copy(), transFromEC01.copy());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionElse.copy(), \"stateActionElse\");\n\t\t\t\tstateActionElse = JDD.And(stateActionElse, JDD.Not(representativeCol.copy()));\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionElse.copy(), \"stateActionElse (2)\");\n\t\t\t\tstateActionElse = JDD.ThereExists(stateActionElse, originalModel.getAllDDColVars());\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionElse.copy(), \"stateActionElse (3)\");\n\t\t\t\tJDDNode stateActionWithOnlySelfLoop = JDD.And(stateActionWithSelfLoop, JDD.Not(stateActionElse));\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionWithOnlySelfLoop.copy(), \"stateActionOnlySelfLoop\");\n\n\t\t\t\t// find states where removing those actions would lead to deadlocks\n\t\t\t\tJDDNode trans01Removed = JDD.Times(transFromEC01, JDD.Not(stateActionWithOnlySelfLoop.copy()));\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), trans01Removed.copy(), \"trans01Removed\");\n\t\t\t\tJDDNode notDeadlocked = JDD.ThereExists(trans01Removed, originalModel.getAllDDColVars());\n\t\t\t\tnotDeadlocked = JDD.ThereExists(notDeadlocked, originalModel.getAllDDNondetVars());\n\t\t\t\tnotDeadlocked = JDD.ThereExists(notDeadlocked, extraActionVars);\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), notDeadlocked.copy(), \"notDeadlocked\");\n\n\t\t\t\tJDDNode stateActionsToRemove = JDD.And(stateActionWithOnlySelfLoop.copy(), notDeadlocked);\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), stateActionsToRemove.copy(), \"stateActionsToRemove\");\n\t\t\t\ttransFromEC = JDD.Times(transFromEC, JDD.Not(stateActionsToRemove.copy()));\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transFromEC.copy(), \"transFromEC\");\n\n\t\t\t\tJDDNode selfLoopRemaining = JDD.And(stateActionWithOnlySelfLoop, JDD.Not(stateActionsToRemove));\n\t\t\t\tecRemainingSelfLoops = JDD.Or(ecRemainingSelfLoops, selfLoopRemaining);\n\n\t\t\t\tnewTrans = JDD.Apply(JDD.MAX, newTrans, transFromEC);\n\t\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), newTrans.copy(), \"newTrans\");\n\n\t\t\t\tJDD.Deref(representative, representativeCol);\n\t\t\t}\n\n\t\t\tJDDNode transUntouched = JDD.Times(trans.copy(), notInEC.copy());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transUntouched.copy(), \"transUntouched\");\n\t\t\ttransUntouched = JDD.Times(transUntouched, notTau());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transUntouched.copy(), \"transUntouched (2)\");\n\t\t\tnewTrans = JDD.Apply(JDD.MAX, newTrans, transUntouched);\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), newTrans.copy(), \"newTrans\");\n\n\t\t\tnewTrans01 = JDD.GreaterThan(newTrans.copy(), 0);\n\n\t\t\tJDD.Deref(trans);\n\n\t\t\tcomputed = true;\n\t\t}\n\n\t\t/**\n\t\t * Maps a state set from the original model to the corresponding state set\n\t\t * in the quotient model.\n\t\t * [ REFS: <i>result</i>, DEREFS: s ]\n\t\t */\n\t\tpublic JDDNode mapStateSet(JDDNode S)\n\t\t{\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), S.copy(), \"S\");\n\t\t\tJDDNode mapped = JDD.And(S, map.copy());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), mapped.copy(), \"mapped\");\n\n\t\t\tmapped = JDD.ThereExists(mapped, originalModel.getAllDDRowVars());\n\t\t\tmapped = JDD.PermuteVariables(mapped, originalModel.getAllDDColVars(), originalModel.getAllDDRowVars());\n\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), mapped.copy(), \"mapped (result)\");\n\t\t\treturn mapped;\n\t\t}\n\n\t\t@Override\n\t\tpublic JDDNode getTransformedTrans() throws PrismException\n\t\t{\n\t\t\tif (!computed) compute();\n\t\t\treturn newTrans.copy();\n\t\t}\n\n\t\t@Override\n\t\tpublic JDDNode getTransformedStart() throws PrismException\n\t\t{\n\t\t\treturn mapStateSet(originalModel.getStart().copy());\n\t\t}\n\n\t\t@Override\n\t\tpublic JDDNode getTransformedStateReward(JDDNode rew) throws PrismException\n\t\t{\n\t\t\tif (!computed) compute();\n\n\t\t\tif (SanityJDD.enabled) {\n\t\t\t\tSanityJDD.checkIsDDOverVars(rew, originalModel.getAllDDRowVars());\n\t\t\t}\n\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rew.copy(), \"state rew\");\n\t\t\t// set state rewards for all EC states to zero\n\t\t\tJDDNode result = JDD.Times(rew.copy(), JDD.Not(inEC.copy()));\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), result.copy(), \"state rew (transformed)\");\n\n\t\t\treturn result;\n\t\t}\n\n\t\t@Override\n\t\tpublic JDDNode getTransformedTransReward(JDDNode rew) throws PrismException\n\t\t{\n\t\t\tif (!computed) compute();\n\n\t\t\tif (SanityJDD.enabled) {\n\t\t\t\tSanityJDD.checkIsDDOverVars(rew, originalModel.getAllDDRowVars(), originalModel.getAllDDNondetVars(), originalModel.getAllDDColVars());\n\t\t\t}\n\n\t\t\t// outgoing actions from ECs\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rew.copy(), \"trans rew\");\n\t\t\tJDDNode rewFromEC = JDD.Times(rew.copy(), inEC.copy());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rewFromEC.copy(), \"rewFromEC (1)\");\n\t\t\trewFromEC = JDD.PermuteVariables(rewFromEC, originalModel.getAllDDRowVars(), actFromStates);\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rewFromEC.copy(), \"rewFromEC (2)\");\n\t\t\trewFromEC = JDD.Times(tau(), rewFromEC);\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rewFromEC.copy(), \"rewFromEC (3)\");\n\t\t\trewFromEC = JDD.PermuteVariables(rewFromEC, originalModel.getAllDDColVars(), originalModel.getAllDDRowVars());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rewFromEC.copy(), \"rewFromEC (4)\");\n\t\t\trewFromEC = JDD.Times(rewFromEC, map.copy());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rewFromEC.copy(), \"rewFromEC (5)\");\n\t\t\trewFromEC = JDD.SumAbstract(rewFromEC, originalModel.getAllDDRowVars());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rewFromEC.copy(), \"rewFromEC (6)\");\n\t\t\trewFromEC = JDD.Times(rewFromEC, newTrans01.copy());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rewFromEC.copy(), \"rewFromEC (7)\");\n\n\t\t\t// for the remaining self loops from ECs (to avoid deadlocks), we strip the\n\t\t\t// transition rewards\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), ecRemainingSelfLoops.copy(), \"ecRemainingSelfLoops\");\n\t\t\trewFromEC = JDD.Times(rewFromEC, JDD.Not(ecRemainingSelfLoops.copy()));\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rewFromEC.copy(), \"rewFromEC (8)\");\n\n\t\t\t// transformedRew is the combination of the outgoing actions from the ECs\n\t\t\t// and the original actions (tagged with notTau)\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), rew.copy(), \"trans rew\");\n\t\t\tJDDNode transformedRew = JDD.Apply(JDD.MAX, JDD.Times(notTau(), rew.copy()), rewFromEC);\n\t\t\ttransformedRew = JDD.Times(transformedRew, newTrans01.copy());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transformedRew.copy(), \"transformedRew\");\n\n\t\t\treturn transformedRew;\n\t\t}\n\n\t\t@Override\n\t\tpublic JDDNode getTransformedTransActions()\n\t\t{\n\t\t\tif (originalModel.getTransActions() == null) {\n\t\t\t\treturn null;\n\t\t\t}\n\n\t\t\tJDDNode transActionsNormal = originalModel.getTransActions().copy();\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transActionsNormal.copy(), \"transActionsNormal (1)\");\n\t\t\ttransActionsNormal = JDD.Times(transActionsNormal, notTau());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transActionsNormal.copy(), \"transActionsNormal (2)\");\n\n\t\t\tJDDNode transActionsFromEC = originalModel.getTransActions().copy();\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transActionsFromEC.copy(), \"transActionsFromEC (1)\");\n\t\t\t// shift from states to actFromEC\n\t\t\ttransActionsFromEC = JDD.PermuteVariables(transActionsFromEC, originalModel.getAllDDRowVars(), actFromStates);\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transActionsFromEC.copy(), \"transActionsFromEC (2)\");\n\t\t\ttransActionsFromEC = JDD.Times(transActionsFromEC, tau());\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transActionsFromEC.copy(), \"transActionsFromEC (3)\");\n\n\t\t\tJDDNode transformedTransActions = JDD.Apply(JDD.MAX, transActionsNormal, transActionsFromEC);\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transformedTransActions.copy(), \"transformedTransActions\");\n\n\t\t\ttransformedTransActions = JDD.Times(transformedTransActions, JDD.ThereExists(newTrans01.copy(), originalModel.getAllDDColVars()));\n\n\t\t\t//transformedTransActions = JDD.Times(transformedTransActions, newTrans01);\n\t\t\tif (verbose) JDD.PrintMinterms(parent.getLog(), transformedTransActions.copy(), \"transformedTransActions\");\n\n\t\t\treturn transformedTransActions;\n\t\t}\n\n\t\t@Override\n\t\tpublic JDDNode getTransformedLabelStates(JDDNode oldLabelStates, JDDNode transformedReach)\n\t\t{\n\t\t\t// we always return 'false' here, as it's difficult to decide how to label\n\t\t\t// the representative states if not all the states in the EC are labelled\n\t\t\t// the same\n\t\t\treturn JDD.Constant(0);\n\t\t}\n\n\t\t/** Provide the set of reachable states */\n\t\tpublic JDDNode getReachableStates()\n\t\t{\n\t\t\t// reachable states in the quotient MDP:\n\t\t\t//  remove non-representative states contained in ECs\n\t\t\t//  from the reachable states in the original model\n\t\t\tJDDNode removed = JDD.And(inEC.copy(), JDD.Not(representatives.copy()));\n\t\t\tJDDNode newReach = JDD.And(originalModel.getReach().copy(), JDD.Not(removed));\n\n\t\t\treturn newReach;\n\t\t}\n\n\t\t/**\n\t\t * Lift an ADD over row variables from the quotient model to the original model,\n\t\t * by copying the values from the representatives to the other states in the EC.\n\t\t */\n\t\tpublic JDDNode liftFromRepresentatives(JDDNode n)\n\t\t{\n\t\t\t// we first shift the result to the column variables\n\t\t\tJDDNode result = JDD.PermuteVariables(n, originalModel.getAllDDRowVars(), originalModel.getAllDDColVars());\n\t\t\t// combine with the map. we now have (state,representative) -> value\n\t\t\tresult = JDD.Times(result, map.copy());\n\t\t\t// as there is exactly one representative per state, we can abstract using SumAbstract\n\t\t\t// (works for positive and negative values)\n\t\t\tresult = JDD.SumAbstract(result, originalModel.getAllDDColVars());\n\t\t\treturn result;\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/Model.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport io.ModelExportOptions;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport odd.ODDNode;\nimport odd.ODDUtils;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport symbolic.states.StateList;\nimport symbolic.states.StateListMTBDD;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.BitSet;\nimport java.util.List;\nimport java.util.Set;\nimport java.util.Vector;\n\nimport static prism.PrismSettings.DEFAULT_EXPORT_MODEL_PRECISION;\n\n/**\n * Interface for classes that store models symbolically, as (MT)BDDs.\n * For clarity, this interface provides read-only access to the model.\n * See {@link ModelSymbolic} for the writeable base class.\n */\npublic interface Model extends prism.Model<Double>\n{\n\t// Accessors (basic model info)\n\n\t/**\n\t * Get a BDD storing the set of initial states.\n\t */\n\tJDDNode getStart();\n\n\t/**\n\t * Get a StateList storing the set of initial states.\n\t */\n\tdefault StateList getStartStates()\n\t{\n\t\treturn new StateListMTBDD(getStart(), this);\n\t}\n\n\t/**\n\t * Get a BDD storing the set of states that are/were deadlocks.\n\t * (Such states may have been fixed at build-time by adding self-loops)\n\t */\n\tJDDNode getDeadlocks();\n\n\t/**\n\t * Get a StateList storing the set of states that are/were deadlocks.\n\t * (Such states may have been fixed at build-time by adding self-loops)\n\t */\n\tdefault StateList getDeadlockStates()\n\t{\n\t\treturn new StateListMTBDD(getDeadlocks(), this);\n\t}\n\n\t/**\n\t * Get a BDD storing the set of reachable states.\n\t */\n\tJDDNode getReach();\n\n\t/**\n\t * Get an ODD storing the set of reachable states.\n\t */\n\tODDNode getODD();\n\n\t/**\n\t * Get a StateList storing the set of reachable states.\n\t */\n\tdefault StateList getReachableStates()\n\t{\n\t\treturn new StateListMTBDD(getReach(), this);\n\t}\n\n\t/**\n\t * Get an (MT)BDD representing the transition function/matrix.\n\t */\n\tJDDNode getTrans();\n\n\t/**\n\t * Get a BDD representing the underlying transition graph.\n\t */\n\tJDDNode getTrans01();\n\n\t/**\n\t * Get a BDD storing the underlying transition relation of the model.\n\t * If it is not stored already, it will be computed.\n\t */\n\tJDDNode getTransReln();\n\n\t/**\n\t * Get access to the VarList (optionally stored).\n\t */\n\tVarList getVarList();\n\n\t/**\n\t * Get access to a list of constant values (optionally stored).\n\t */\n\tValues getConstantValues();\n\n\t/**\n\t * Get the list of action labels for the model.\n\t */\n\tList<String> getSynchs();\n\n\t/**\n\t * Get a BDD (over row variables) for the states satisfying a label.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t * @param label the label name\n\t * @return JDDNode for the label, {@code null} if none is stored\n\t */\n\tJDDNode getLabelDD(String label);\n\n\t/**\n\t * Is a BDD state set stored for this label?\n\t */\n\tdefault boolean hasLabelDD(String label)\n\t{\n\t\treturn getLabels().contains(label);\n\t}\n\n\t/**\n\t * Get the (read-only) set of label names that are (optionally) stored in the model.\n\t * Returns an empty set if there are none.\n\t */\n\tSet<String> getLabels();\n\n\t/**\n\t * Get the number of reward structures.\n\t */\n\tint getNumRewardStructs();\n\n\t/**\n\t * Get the name of the {@code i}th reward structure.\n\t */\n\tString getRewardStructName(int i);\n\n\t/**\n\t * Get an MTBDD for the state rewards for the {@code i}th reward structure.\n\t */\n\tJDDNode getStateRewards(int i);\n\n\t/**\n\t * Get an MTBDD for the state rewards for the named reward structure.\n\t */\n\tJDDNode getStateRewards(String name);\n\n\t/**\n\t * Get an MTBDD for the state rewards for the first reward structure.\n\t */\n\tdefault JDDNode getStateRewards()\n\t{\n\t\treturn getStateRewards(0);\n\t}\n\n\t/**\n\t * Get an MTBDD for the transition rewards for the {@code i}th reward structure.\n\t */\n\tJDDNode getTransRewards(int i);\n\n\t/**\n\t * Get an MTBDD for the transition rewards for the named reward structure.\n\t */\n\tJDDNode getTransRewards(String name);\n\n\t/**\n\t * Get an MTBDD for the transition rewards for the first reward structure.\n\t */\n\tdefault JDDNode getTransRewards()\n\t{\n\t\treturn getTransRewards(0);\n\t}\n\n\t// Accessors (DD variables)\n\n\t/**\n\t * Get the information about the model's DD variables\n\t */\n\tModelVariablesDD getModelVariables();\n\n\t/**\n\t * Get the names of the model's DD variables\n\t */\n\tdefault Vector<String> getDDVarNames()\n\t{\n\t\treturn getModelVariables().getDDVarNames();\n\t}\n\n\t/**\n\t * Get the DD variables for rows (source states) of the model\n\t */\n\tJDDVars getAllDDRowVars();\n\n\t/**\n\t * Get the DD variables for column (destination states) of the model\n\t */\n\tJDDVars getAllDDColVars();\n\n\t/**\n\t * Get the number of DD variables for rows (source states) of the model\n\t */\n\tdefault int getNumDDRowVars()\n\t{\n\t\treturn getAllDDRowVars().n();\n\t}\n\n\t/**\n\t * Get the number DD variables for column (destination states) of the model\n\t */\n\tdefault int getNumDDColVars()\n\t{\n\t\treturn getAllDDColVars().n();\n\t}\n\n\t/**\n\t * Get the number of DD variables used to represent the transition function/matrix of the model\n\t */\n\tint getNumDDVarsInTrans();\n\n\t/**\n\t * Get the DD variables for rows (source states) for each of the model's variables\n\t */\n\tJDDVars[] getVarDDRowVars();\n\n\t/**\n\t * Get the DD variables for column (destination states) for each of the model's variables\n\t */\n\tJDDVars[] getVarDDColVars();\n\n\t/**\n\t * Get the DD variables for rows (source states) for the {@code i}th model variable\n\t */\n\tJDDVars getVarDDRowVars(int i);\n\n\t/**\n\t * Get the DD variables for column (destination states) for the {@code i}th model variable\n\t */\n\tJDDVars getVarDDColVars(int i);\n\n\t// Print and export methods\n\n\t/**\n\t * Print basic information about the model to a log.\n\t */\n\tdefault void printTransInfo(PrismLog log)\n\t{\n\t\tprintTransInfo(log, false);\n\t}\n\n\t/**\n\t * Print basic (and, optionally, more detailed) information about the model to a log.\n\t */\n\tvoid printTransInfo(PrismLog log, boolean extra);\n\n\t/**\n\t * Get a string summarising the number of DD variables in the transition matrix DD,\n\t * e.g. \"31r/31c\" or \"31r/31c/8nd\".\n\t */\n\tString getTransDDVarSummary();\n\n\t/**\n\t * Get text listing the DD variables in the transition matrix DD.\n\t */\n\tString getTransDDVarInfo();\n\n\t/**\n\t * Export the transition function/matrix.\n\t * @param exportType The format in which to export\n\t * @param explicit Whether to order by state\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\tdefault void exportToFile(int exportType, boolean explicit, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportToFile(exportType, explicit, file, DEFAULT_EXPORT_MODEL_PRECISION);\n\t}\n\n\t/**\n\t * Export the transition function/matrix.\n\t * @param exportType The format in which to export\n\t * @param explicit Whether to order by state\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param precision Model export precision (number of significant digits, >= 1)\n\t */\n\tvoid exportToFile(int exportType, boolean explicit, File file, int precision) throws FileNotFoundException, PrismException;\n\n\t/**\n\t * Export the transition function/matrix.\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tvoid exportToFile(File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException;\n\n\t/**\n\t * Export (non-zero) state rewards for one reward structure of the model.\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param exportType The format in which to export\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\tdefault void exportStateRewardsToFile(int r, int exportType, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportStateRewardsToFile(r, exportType, file, DEFAULT_EXPORT_MODEL_PRECISION, false);\n\t}\n\n\t/**\n\t * Export (non-zero) state rewards for one reward structure of the model.\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param exportType The format in which to export\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param precision Model export precision (number of significant digits, >= 1)\n\t * @param noexportheaders disables export headers for srew files\n\t */\n\tvoid exportStateRewardsToFile(int r, int exportType, File file, int precision, boolean noexportheaders) throws FileNotFoundException, PrismException;\n\n\t/**\n\t * Export (non-zero) state rewards for one reward structure of the model.\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tvoid exportStateRewardsToFile(int r, File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException;\n\n\t/**\n\t * Export (non-zero) transition rewards for one reward structure of the model.\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param exportType The format in which to export\n\t * @param ordered Do the entries need to be printed in order?\n\t * @param file File to export to (if null, print to the log instead)\n\t */\n\tdefault void exportTransRewardsToFile(int r, int exportType, boolean ordered, File file) throws FileNotFoundException, PrismException\n\t{\n\t\texportTransRewardsToFile(r, exportType, ordered, file, DEFAULT_EXPORT_MODEL_PRECISION, false);\n\t}\n\n\t/**\n\t * Export (non-zero) transition rewards for one reward structure of the model.\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param exportType The format in which to export\n\t * @param ordered Do the entries need to be printed in order?\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param precision number of significant digits >= 1\n\t * @param noexportheaders disables export headers for trew files\n\t */\n\tvoid exportTransRewardsToFile(int r, int exportType, boolean ordered, File file, int precision, boolean noexportheaders) throws FileNotFoundException, PrismException;\n\n\t/**\n\t * Export (non-zero) transition rewards for one reward structure of the model.\n\t * @param r Index of reward structure to export (0-indexed)\n\t * @param file File to export to (if null, print to the log instead)\n\t * @param exportOptions The options for export\n\t */\n\tvoid exportTransRewardsToFile(int r, File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException;\n\n\t/**\n\t * Export the list of reachable states of the model.\n\t * @param exportType The format in which to export\n\t * @param log Where to export\n\t */\n\tvoid exportStates(int exportType, PrismLog log);\n\n\t// Other methods\n\n\t/**\n\t * Convert a BDD (over row variables) representing a single state\n\t * to a corresponding {@link State} object.\n\t * @param dd 0/1-MTBDD, representing a single state\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tdefault State convertBddToState(JDDNode dd)\n\t{\n\t\treturn convertBddToState(dd, getAllDDRowVars(), getVarList());\n\t}\n\n\t/**\n\t * Convert a BDD (over the given row variables, encoding variables according to the VarList)\n\t * representing a single state to a corresponding {@link State} object.\n\t * @param dd 0/1-MTBDD, representing a single state\n\t * @param allDDRowVars the list of row variables\n\t * @param varList the VarList, specifying the encoding of the individual state variables\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic static State convertBddToState(JDDNode dd, JDDVars allDDRowVars, VarList varList)\n\t{\n\t\t// First convert path through BDD to a bit vector\n\t\tJDDNode ptr = dd;\n\t\tint n = allDDRowVars.n();\n\t\tBitSet bits = new BitSet(n);\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (ptr.getIndex() > allDDRowVars.getVarIndex(i)) {\n\t\t\t} else if (!ptr.getElse().equals(JDD.ZERO)) {\n\t\t\t\tptr = ptr.getElse();\n\t\t\t} else {\n\t\t\t\tbits.set(i, true);\n\t\t\t\tptr = ptr.getThen();\n\t\t\t}\n\t\t}\n\t\t// Then convert to State object\n\t\treturn varList.convertBitSetToState(bits);\n\t}\n\n\t/**\n\t * Convert a BDD (over row variables) representing a single state\n\t * to an index into the list of reachable states.\n\t */\n\tdefault int convertBddToIndex(JDDNode dd) throws PrismNotSupportedException\n\t{\n\t\tODDNode odd = getODD();\n\t\tODDUtils.checkInt(odd, \"Cannot convert Bdd to index in model\");\n\t\t// Traverse BDD and ODD simultaneously to compute index\n\t\tJDDVars allDDRowVars = getAllDDRowVars();\n\t\tJDDNode ptr = dd;\n\t\tODDNode oddPtr = odd;\n\t\tint n = allDDRowVars.n();\n\t\tint index = 0;\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tif (ptr.getIndex() > allDDRowVars.getVarIndex(i)) {\n\t\t\t\toddPtr = oddPtr.getElse();\n\t\t\t} else if (!ptr.getElse().equals(JDD.ZERO)) {\n\t\t\t\tptr = ptr.getElse();\n\t\t\t\toddPtr = oddPtr.getElse();\n\t\t\t} else {\n\t\t\t\tptr = ptr.getThen();\n\t\t\t\tindex += oddPtr.getEOff();\n\t\t\t\toddPtr = oddPtr.getThen();\n\t\t\t}\n\t\t}\n\t\treturn index;\n\t}\n\n\t/**\n\t * Get the name of the transition function/matrix (e.g. \"Transition matrix\")\n\t */\n\tString getTransName();\n\n\t/**\n\t * Get the symbolic of the transition function/matrix when exporting (e.g. \"P\")\n\t */\n\tString getTransSymbol();\n\n\t/**\n\t * Can be called once the model is finished with, e.g. to clear local storage.\n\t */\n\tvoid clear();\n\n\t// Convenience methods for getting variable info\n\n\t/**\n\t * Get the number of model variables\n\t */\n\tdefault int getNumVars()\n\t{\n\t\treturn getVarList().getNumVars();\n\t}\n\n\t/**\n\t * Get the name of the {@code i}th model variable\n\t */\n\tdefault String getVarName(int i)\n\t{\n\t\treturn getVarList().getName(i);\n\t}\n\n\t/**\n\t * Get the index of model variable {@code name}\n\t */\n\tdefault int getVarIndex(String name)\n\t{\n\t\treturn getVarList().getIndex(name);\n\t}\n\n\t/**\n\t * Get the low value of the {@code i}th model variable\n\t */\n\tdefault int getVarLow(int i)\n\t{\n\t\treturn getVarList().getLow(i);\n\t}\n\n\t/**\n\t * Get the high value of the {@code i}th model variable\n\t */\n\tdefault int getVarHigh(int i)\n\t{\n\t\treturn getVarList().getHigh(i);\n\t}\n\n\t/**\n\t * Get the range of the {@code i}th model variable\n\t */\n\tdefault int getVarRange(int i)\n\t{\n\t\treturn getVarList().getRange(i);\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/symbolic/model/ModelExpressionTransformation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n\npackage symbolic.model;\n\nimport parser.ast.Expression;\nimport symbolic.model.Model;\nimport symbolic.model.ModelTransformation;\n\n/**\n * Interface for a model and expression transformation.<br>\n *\n * Implementing classes provide a combined model and expression transformation, allowing the calculation\n * of a (potentially simpler) expression in the transformed model to calculate the result of the\n * original expression in the original model.<br>\n *\n * The general idea is the following sequence of calls:<br>\n *\n * {@code ModelExpressionTransformation t = ...;}<br>\n * {@code StateValues resultTransformed = check t.getTransformedExpression() in t.getTransformedModel()}<br>\n * {@code StateValues result = t.projectToOriginalModel(resultTransformed);}\n */\npublic interface ModelExpressionTransformation<OriginalModel extends Model, TransformedModel extends Model>\n       extends ModelTransformation<OriginalModel, TransformedModel>\n{\n\n\t/** Get the transformed expression. */\n\tpublic Expression getTransformedExpression();\n\n\t/** Get the original expression. */\n\tpublic Expression getOriginalExpression();\n\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/ModelExpressionTransformationNested.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport jdd.JDDNode;\nimport parser.ast.Expression;\nimport prism.PrismException;\nimport symbolic.states.StateValues;\n\n/**\n * Nesting of two model/expression transformations.\n * <br>\n * original -(innerTransformation)-&gt; intermediate -(outerTransformation)-&gt; transformed\n */\n\npublic class ModelExpressionTransformationNested<OriginalModel extends Model, IntermediateModel extends Model, TransformedModel extends Model> implements\n\t\tModelExpressionTransformation<OriginalModel, TransformedModel>\n{\n\n\t/** The inner transformation */\n\tprotected ModelExpressionTransformation<OriginalModel, IntermediateModel> innerTransformation;\n\t/** The outer transformation */\n\tprotected ModelExpressionTransformation<IntermediateModel,TransformedModel> outerTransformation;\n\n\t/**\n\t * Constructor, chain the two transformations.\n\t * <br>\n\t * The transformations will be cleared on a call to {@code clear()}.\n\t * <br>\n\t * [STORE: innerTransformation, outerTransformation ]\n\t */\n\tpublic ModelExpressionTransformationNested(ModelExpressionTransformation<OriginalModel, IntermediateModel> innerTransformation,\n\t\t\tModelExpressionTransformation<IntermediateModel, TransformedModel> outerTransformation)\n\t{\n\t\tthis.innerTransformation = innerTransformation;\n\t\tthis.outerTransformation = outerTransformation;\n\n\t\tif (innerTransformation.getTransformedModel() != outerTransformation.getOriginalModel()) {\n\t\t\tthrow new IllegalArgumentException(\"Trying to nest unrelated ModelExpressionTransformations.\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic TransformedModel getTransformedModel()\n\t{\n\t\treturn outerTransformation.getTransformedModel();\n\t}\n\n\t@Override\n\tpublic StateValues projectToOriginalModel(StateValues svTransformedModel) throws PrismException\n\t{\n\t\tStateValues svIntermediate = outerTransformation.projectToOriginalModel(svTransformedModel);\n\t\tStateValues svOriginal = innerTransformation.projectToOriginalModel(svIntermediate);\n\t\treturn svOriginal;\n\t}\n\n\t@Override\n\tpublic Expression getTransformedExpression()\n\t{\n\t\treturn outerTransformation.getTransformedExpression();\n\t}\n\n\t@Override\n\tpublic OriginalModel getOriginalModel() {\n\t\treturn innerTransformation.getOriginalModel();\n\t}\n\n\t@Override\n\tpublic Expression getOriginalExpression()\n\t{\n\t\treturn innerTransformation.getOriginalExpression();\n\t}\n\n\t@Override\n\tpublic JDDNode getTransformedStatesOfInterest()\n\t{\n\t\treturn outerTransformation.getTransformedStatesOfInterest();\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\touterTransformation.clear();\n\t\tinnerTransformation.clear();\n\t}\n}"
  },
  {
    "path": "prism/src/symbolic/model/ModelSymbolic.java",
    "content": "//==============================================================================\n//\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\n//------------------------------------------------------------------------------\n//\n//\tThis file is part of PRISM.\n//\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\n//==============================================================================\n\npackage symbolic.model;\n\nimport io.ModelExportOptions;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport jdd.SanityJDD;\nimport mtbdd.PrismMTBDD;\nimport odd.ODDNode;\nimport odd.ODDUtils;\nimport parser.Values;\nimport parser.VarList;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismUtils;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.List;\nimport java.util.Map;\nimport java.util.Set;\nimport java.util.TreeMap;\n\n/**\n * Base class for symbolic (BDD-based) model representations.\n */\npublic abstract class ModelSymbolic implements Model\n{\n\t// Model info\n\n\t// Vars/consts\n\t/** Model variable info */\n\tprotected VarList varList;\n\t/** Values of constants (optional) */\n\tprotected Values constantValues;\n\t// Actions\n\t/** Number of action labels */\n\tprotected int numSynchs;\n\t/** Action label names */\n\tprotected List<String> synchs;\n\t// Rewards\n\t/** Number of reward structs */\n\tprotected int numRewardStructs;\n\t/** Reward struct names */\n\tprotected String[] rewardStructNames = new String[0];\n\t// Stats\n\t/** Number of states */\n\tprotected double numStates;\n\t/** Number of transitions */\n\tprotected double numTransitions;\n\t/** Nmber of initial states */\n\tprotected double numStartStates;\n\n\t// (MT)BDDs and variables\n\n\t/** Transition matrix DD */\n\tprotected JDDNode trans;\n\t/** 0-1 transition matrix BDD underlying graph structure) */\n\tprotected JDDNode trans01;\n\t/** Initial states BDD */\n\tprotected JDDNode start; //\n\t/** Reachable states NBDD */\n\tprotected JDDNode reach;\n\t/** Deadlock states BDD (may have been fixed) */\n\tprotected JDDNode deadlocks;\n\t/** State rewards MTBDDs */\n\tprotected JDDNode stateRewards[] = new JDDNode[0];\n\t/** Transition rewards MTBDDs */\n\tprotected JDDNode transRewards[] = new JDDNode[0];\n\n\t/** DD variable info */\n\tprotected ModelVariablesDD modelVariables;\n\t/** DD vars for each model variable (rows) */\n\tprotected JDDVars[] varDDRowVars;\n\t/** DD vars for each model variable (columns) */\n\tprotected JDDVars[] varDDColVars;\n\t/** All DD vars for rows */\n\tprotected JDDVars allDDRowVars;\n\t/** All DD vars for columns */\n\tprotected JDDVars allDDColVars;\n\n\t/** Map from label names to BDDs for sets of satisfying states */\n\tprotected Map<String, JDDNode> labelsDD = new TreeMap<>();\n\n\t/** ODD representing reachable states */\n\tprotected ODDNode odd; // odd\n\n\t// Constructor\n\n\tpublic ModelSymbolic(JDDNode trans, JDDNode start, JDDVars allDDRowVars, JDDVars allDDColVars, ModelVariablesDD modelVariables,\n\t\t\t\t\t\t VarList varList, JDDVars[] varDDRowVars, JDDVars[] varDDColVars)\n\t{\n\t\tthis.trans = trans;\n\t\tthis.start = start;\n\t\tthis.allDDRowVars = allDDRowVars;\n\t\tthis.allDDColVars = allDDColVars;\n\t\tthis.modelVariables = modelVariables;\n\t\tthis.varList = varList;\n\t\tthis.varDDRowVars = varDDRowVars;\n\t\tthis.varDDColVars = varDDColVars;\n\n\t\t// calculate 0-1 version of trans\n\t\tJDD.Ref(trans);\n\t\ttrans01 = JDD.GreaterThan(trans, 0);\n\n\t\t// work out number of initial states\n\t\tnumStartStates = JDD.GetNumMinterms(start, allDDRowVars.n());\n\t}\n\n\t// Mutators\n\n\t/**\n\t * Set the initial state(s) BDD (but don't re-do reachability).\n\t * The old BDD is derefed if set already.\n\t */\n\tpublic void setStart(JDDNode start)\n\t{\n\t\tif (this.start != null) {\n\t\t\tJDD.Deref(this.start);\n\t\t}\n\t\tthis.start = start;\n\n\t\t// Recompute number of initial states\n\t\tnumStartStates = JDD.GetNumMinterms(start, allDDRowVars.n());\n\t}\n\n\t/**\n\t * Set reachable states BDD (and compute number of states and ODD)\n\t */\n\tpublic void setReach(JDDNode reach) throws PrismException\n\t{\n\t\tif (this.reach != null)\n\t\t\tJDD.Deref(this.reach);\n\t\tthis.reach = reach;\n\n\t\t// work out number of reachable states\n\t\tnumStates = JDD.GetNumMinterms(reach, allDDRowVars.n());\n\n\t\t// build odd, clear old one\n\t\tif (odd != null) {\n\t\t\tODDUtils.ClearODD(odd);\n\t\t\todd = null;\n\t\t}\n\t\todd = ODDUtils.BuildODD(reach, allDDRowVars);\n\t}\n\n\t/**\n\t * Reset transition matrix DD.\n\t * The old one (if present) will be deref-ed.\n\t * Note: Update reachable states and call {@code filterReachableStates}\n\t * afterwards to update related information (trans01, odd, etc).\n\t * If the reachable states do not change, you probably still want\n\t * to call {@link #resetTrans01(JDDNode)}.\n\t *\n\t * <br>[ STORES: trans, DEREFS: <i>old transition matrix DD</i> ]\n\t */\n\tpublic void resetTrans(JDDNode trans)\n\t{\n\t\tif (this.trans != null) {\n\t\t\tJDD.Deref(this.trans);\n\t\t}\n\t\tthis.trans = trans;\n\t}\n\n\t/**\n\t * Reset 0-1 transition matrix DD.\n\t * The old one (if present) will be deref-ed.\n\t *\n\t * <br>[ STORES: trans01, DEREFS: <i>old 0-1 transition matrix DD</i> ]\n\t */\n\tpublic void resetTrans01(JDDNode trans01)\n\t{\n\t\tif (this.trans01 != null) {\n\t\t\tJDD.Deref(this.trans01);\n\t\t}\n\t\tthis.trans01 = trans01;\n\t}\n\n\t/**\n\t * Set list of action label names.\n\t */\n\tpublic void setSynchs(List<String> synchs)\n\t{\n\t\tthis.synchs = synchs;\n\t\tthis.numSynchs = synchs.size();\n\t}\n\n\t/**\n\t * Stores a JDDNode state set (over the row variables) for the given label.\n\t * If the label already exists, the old state set is derefed and overwritten.\n\t * <br>\n\t * Note that a stored label takes precedence over the on-the-fly calculation\n\t * of an ExpressionLabel during model checking.\n\t *\n\t * <br>[ STORES: labelDD, deref on later call to clear() ]\n\t * @param label the label name\n\t * @param labelDD the JDDNode with the state set for the label\n\t */\n\tpublic void addLabelDD(String label, JDDNode labelDD)\n\t{\n\t\tJDDNode old = labelsDD.put(label, labelDD);\n\t\tif (old != null) JDD.Deref(old);\n\t}\n\n\t/**\n\t * Add a label with corresponding state set, ensuring a unique, non-existing label.\n\t * The label will be either \"X\" or \"X_i\" where X is the content of the {@code prefix} argument\n\t * and i is a non-negative integer.\n\t * <br>\n\t * Optionally, a set of defined label names can be passed so that those labels\n\t * can be avoided. This can be obtained from the model checker via {@code getDefinedLabelNames()}.\n\t * <br>\n\t * Note that a stored label takes precedence over the on-the-fly calculation\n\t * of an ExpressionLabel during model checking.\n\t *\n\t * <br>[ STORES: labelDD, deref on later call to clear() ]\n\t * @param prefix the prefix for the unique label\n\t * @param labelDD the JDDNode with the state set for the label\n\t * @param definedLabelNames set of names (optional, may be {@code null}) to check for existing labels\n\t * @return the generated unique label\n\t */\n\tpublic String addUniqueLabelDD(String prefix, JDDNode labelDD, Set<String> definedLabelNames)\n\t{\n\t\tString label;\n\t\tint i = 0;\n\t\tlabel = prefix;  // first, try without appending _i\n\t\twhile (true) {\n\t\t\tboolean labelOk = !hasLabelDD(label);  // not directly attached to model\n\t\t\tif (definedLabelNames != null) {\n\t\t\t\tlabelOk &= !definedLabelNames.contains(label);  // not defined\n\t\t\t}\n\n\t\t\tif (labelOk) {\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\t// prepare next label to try\n\t\t\tlabel = prefix+\"_\"+i;\n\t\t\tif (i == Integer.MAX_VALUE)\n\t\t\t\tthrow new UnsupportedOperationException(\"Integer overflow trying to add unique label\");\n\n\t\t\ti++;\n\t\t}\n\n\t\taddLabelDD(label, labelDD);\n\t\treturn label;\n\t}\n\n\t/**\n\t * Set all reward info and DDs.\n\t *\n\t * <br>[ STORES: stateRewards, transRewards, deref on later call to clear() ]\n\t */\n\tpublic void setRewards(JDDNode[] stateRewards, JDDNode[] transRewards, String[] rewardStructNames)\n\t{\n\t\tthis.stateRewards = stateRewards;\n\t\tthis.transRewards = transRewards;\n\t\tthis.numRewardStructs = stateRewards.length;\n\t\tthis.rewardStructNames = rewardStructNames;\n\t}\n\n\t/**\n\t * Reset transition rewards DD for reward with index i.\n\t *\n\t * <br>[ STORES: transRewards, DEREFS: <i>old trans reward DD</i> ]\n\t */\n\tpublic void resetTransRewards(int i, JDDNode transRewards)\n\t{\n\t\tif (this.transRewards[i] != null) {\n\t\t\tJDD.Deref(this.transRewards[i]);\n\t\t}\n\t\tthis.transRewards[i] = transRewards;\n\t}\n\n\t/**\n\t * Reset state rewards DD for reward with index i.\n\t *\n\t * <br>[ STORES: stateRewards, DEREFS: <i>old state reward DD</i> ]\n\t */\n\tpublic void resetStateRewards(int i, JDDNode stateRewards)\n\t{\n\t\tif (this.stateRewards[i] != null) {\n\t\t\tJDD.Deref(this.stateRewards[i]);\n\t\t}\n\t\tthis.stateRewards[i] = stateRewards;\n\t}\n\n\t/**\n\t * Set the associated (read-only) constant values.\n\t */\n\tpublic void setConstantValues(Values constantValues)\n\t{\n\t\tthis.constantValues = constantValues;\n\t}\n\n\t/**\n\t * Compute and store the set of reachable states.\n\t * <br/>\n\t * Starts reachability computation from the union of {@code seed} and {@start}.\n\t * <br/>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic void doReachability() throws PrismException\n\t{\n\t\t// compute reachable states\n\t\tsetReach(PrismMTBDD.Reachability(trans01, allDDRowVars, allDDColVars, start));\n\t}\n\n\t/**\n\t * Compute and store the set of reachable states, where the parameter {@seed}\n\t * provides an initial set of states known to be reachable.\n\t * <br/>\n\t * Starts reachability computation from the union of {@code seed} and {@start}.\n\t * <br/>[ REFS: <i>result</i>, DEREFS: seed ]\n\t * @param seed set of states (over ddRowVars) that is known to be reachable\n\t */\n\tpublic void doReachability(JDDNode seed) throws PrismException\n\t{\n\t\t// do sanity check on seed if checking is enabled\n\t\tif (SanityJDD.enabled)\n\t\t\tSanityJDD.checkIsStateSet(seed, getAllDDRowVars());\n\n\t\t// S = union of initial states and seed. seed is dereferenced here.\n\t\tJDDNode S = JDD.Or(start.copy(), seed);\n\t\t// compute and store reachable states\n\t\tsetReach(PrismMTBDD.Reachability(trans01, allDDRowVars, allDDColVars, S));\n\t\tJDD.Deref(S);\n\t}\n\n\t/**\n\t * This method allows you to skip the reachability phase.\n\t * It is only here for experimental purposes - not general use.\n\t */\n\tpublic void skipReachability() throws PrismException\n\t{\n\t\t// don't compute reachable states - assume all reachable\n\t\treach = JDD.Constant(1);\n\n\t\t// work out number of reachable states\n\t\tnumStates = Math.pow(2, allDDRowVars.n());\n\n\t\t// build odd, clear old one\n\t\tif (odd != null) {\n\t\t\tODDUtils.ClearODD(odd);\n\t\t\todd = null;\n\t\t}\n\t\todd = ODDUtils.BuildODD(reach, allDDRowVars);\n\t}\n\n\t/**\n\t * Remove non-reachable states from various DDs\n\t * (and calculate num transitions)\n\t */\n\tpublic void filterReachableStates()\n\t{\n\t\t// remove non-reachable states from transition matrix\n\t\tJDD.Ref(reach);\n\t\ttrans = JDD.Apply(JDD.TIMES, reach, trans);\n\t\tJDD.Ref(reach);\n\t\tJDDNode tmp = JDD.PermuteVariables(reach, allDDRowVars, allDDColVars);\n\t\ttrans = JDD.Apply(JDD.TIMES, tmp, trans);\n\n\t\t// recalculate 0-1 version of trans\n\t\tJDD.Deref(trans01);\n\t\tJDD.Ref(trans);\n\t\ttrans01 = JDD.GreaterThan(trans, 0);\n\n\t\t// remove non-reachable states from state/transition rewards\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\t// state rewards vector\n\t\t\tJDD.Ref(reach);\n\t\t\tstateRewards[i] = JDD.Apply(JDD.TIMES, reach, stateRewards[i]);\n\t\t\t// transition reward matrix\n\t\t\tJDD.Ref(reach);\n\t\t\ttransRewards[i] = JDD.Apply(JDD.TIMES, reach, transRewards[i]);\n\t\t\tJDD.Ref(reach);\n\t\t\ttmp = JDD.PermuteVariables(reach, allDDRowVars, allDDColVars);\n\t\t\ttransRewards[i] = JDD.Apply(JDD.TIMES, tmp, transRewards[i]);\n\t\t}\n\n\t\t// filter start states, work out number of initial states\n\t\tJDD.Ref(reach);\n\t\tstart = JDD.Apply(JDD.TIMES, reach, start);\n\t\tnumStartStates = JDD.GetNumMinterms(start, allDDRowVars.n());\n\n\t\t// work out number of transitions\n\t\tnumTransitions = JDD.GetNumMinterms(trans01, getNumDDVarsInTrans());\n\t}\n\n\t/**\n\t * Find all deadlock states and store this information in the model.\n\t * If requested (if fix=true), fix deadlocks by adding self-loops in these states.\n\t * The set of deadlocks (before any possible fixing) can be obtained from {@link #getDeadlocks()}.\n\t */\n\tpublic abstract void findDeadlocks(boolean fix);\n\n\t/**\n\t * Mark additional states as deadlocks.\n\t *\n\t * <br>[ DEREFS: moreDeadlocks ]\n\t */\n\tpublic void addDeadlocks(JDDNode moreDeadlocks)\n\t{\n\t\tif (deadlocks == null) {\n\t\t\tdeadlocks = moreDeadlocks;\n\t\t} else {\n\t\t\tdeadlocks = JDD.Or(deadlocks, moreDeadlocks);\n\t\t}\n\t}\n\n\t// Accessors (for prism.Model & symbolic.Model interface)\n\n\t@Override\n\tpublic List<Object> getActions()\n\t{\n\t\t// Over-approximate and assume that unlabelled actions could occur\n\t\tArrayList<Object> actions = new ArrayList<>();\n\t\tactions.add(null);\n\t\tactions.addAll(synchs);\n\t\treturn actions;\n\t}\n\n\t@Override\n\tpublic List<Object> findActionsUsed()\n\t{\n\t\t// Not yet implemented\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic int getNumStates()\n\t{\n\t\treturn (numStates > Integer.MAX_VALUE) ? -1 : (int) Math.round(numStates);\n\t}\n\n\t@Override\n\tpublic int getNumInitialStates()\n\t{\n\t\treturn (numStartStates > Integer.MAX_VALUE) ? -1 : (int) Math.round(numStartStates);\n\t}\n\n\t@Override\n\tpublic int getNumTransitions()\n\t{\n\t\treturn (numTransitions > Integer.MAX_VALUE) ? -1 : (int) Math.round(numTransitions);\n\t}\n\n\t@Override\n\tpublic boolean numStatesExceedsInt()\n\t{\n\t\treturn numStates > Integer.MAX_VALUE;\n\t}\n\n\t@Override\n\tpublic String getNumStatesString()\n\t{\n\t\treturn PrismUtils.bigIntToString(numStates);\n\t}\n\n\t@Override\n\tpublic String getNumInitialStatesString()\n\t{\n\t\treturn PrismUtils.bigIntToString(numStartStates);\n\t}\n\n\t@Override\n\tpublic String getNumTransitionsString()\n\t{\n\t\treturn PrismUtils.bigIntToString(numTransitions);\n\t}\n\n\t@Override\n\tpublic JDDNode getStart()\n\t{\n\t\treturn start;\n\t}\n\n\t@Override\n\tpublic JDDNode getDeadlocks()\n\t{\n\t\treturn deadlocks;\n\t}\n\n\t@Override\n\tpublic JDDNode getReach()\n\t{\n\t\treturn reach;\n\t}\n\n\t@Override\n\tpublic ODDNode getODD()\n\t{\n\t\treturn odd;\n\t}\n\n\t@Override\n\tpublic JDDNode getTrans()\n\t{\n\t\treturn trans;\n\t}\n\n\t@Override\n\tpublic JDDNode getTrans01()\n\t{\n\t\treturn trans01;\n\t}\n\n\t@Override\n\tpublic JDDNode getTransReln()\n\t{\n\t\treturn trans01;\n\t}\n\n\t@Override\n\tpublic VarList getVarList()\n\t{\n\t\treturn varList;\n\t}\n\n\t@Override\n\tpublic Values getConstantValues()\n\t{\n\t\treturn constantValues;\n\t}\n\n\t@Override\n\tpublic List<String> getSynchs()\n\t{\n\t\treturn synchs;\n\t}\n\n\t@Override\n\tpublic JDDNode getLabelDD(String label)\n\t{\n\t\treturn labelsDD.get(label);\n\t}\n\n\t@Override\n\tpublic Set<String> getLabels()\n\t{\n\t\treturn Collections.unmodifiableSet(labelsDD.keySet());\n\t}\n\n\t@Override\n\tpublic int getNumRewardStructs()\n\t{\n\t\treturn numRewardStructs;\n\t}\n\n\t@Override\n\tpublic String getRewardStructName(int i)\n\t{\n\t\treturn rewardStructNames[i];\n\t}\n\n\t@Override\n\tpublic JDDNode getStateRewards(int i)\n\t{\n\t\treturn (i >= 0 && i < numRewardStructs) ? stateRewards[i] : null;\n\t}\n\n\t@Override\n\tpublic JDDNode getStateRewards(String name)\n\t{\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\tif (rewardStructNames[i].equals(name)) {\n\t\t\t\treturn stateRewards[i];\n\t\t\t}\n\t\t}\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic JDDNode getTransRewards(int i)\n\t{\n\t\treturn (i >= 0 && i < numRewardStructs) ? transRewards[i] : null;\n\t}\n\n\t@Override\n\tpublic JDDNode getTransRewards(String name)\n\t{\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\tif (rewardStructNames[i].equals(name)) {\n\t\t\t\treturn transRewards[i];\n\t\t\t}\n\t\t}\n\t\treturn null;\n\t}\n\n\t@Override\n\tpublic ModelVariablesDD getModelVariables()\n\t{\n\t\treturn modelVariables;\n\t}\n\n\t@Override\n\tpublic JDDVars getAllDDRowVars()\n\t{\n\t\treturn allDDRowVars;\n\t}\n\n\t@Override\n\tpublic JDDVars getAllDDColVars()\n\t{\n\t\treturn allDDColVars;\n\t}\n\n\t@Override\n\tpublic int getNumDDVarsInTrans()\n\t{\n\t\treturn getNumDDRowVars() * 2;\n\t}\n\n\t@Override\n\tpublic JDDVars[] getVarDDRowVars()\n\t{\n\t\treturn varDDRowVars;\n\t}\n\n\t@Override\n\tpublic JDDVars[] getVarDDColVars()\n\t{\n\t\treturn varDDColVars;\n\t}\n\n\t@Override\n\tpublic JDDVars getVarDDRowVars(int i)\n\t{\n\t\treturn varDDRowVars[i];\n\t}\n\n\t@Override\n\tpublic JDDVars getVarDDColVars(int i)\n\t{\n\t\treturn varDDColVars[i];\n\t}\n\n\t// Print and export methods\n\n\t@Override\n\tpublic void printTransInfo(PrismLog log, boolean extra)\n\t{\n\t\tint i, j, n;\n\n\t\tlog.print(\"States:      \" + getNumStatesString() + \" (\" + getNumInitialStatesString() + \" initial)\" + \"\\n\");\n\t\tlog.print(\"Transitions: \" + getNumTransitionsString() + \"\\n\");\n\n\t\tlog.println();\n\n\t\tlog.print(getTransName() + \": \" + JDD.GetInfoString(trans, getNumDDVarsInTrans()));\n\t\tlog.print(\", vars: \" + getTransDDVarSummary() + \"\\n\");\n\t\tif (extra) {\n\t\t\tlog.print(getTransDDVarInfo() + \"\\n\");\n\t\t\tlog.print(getTransName() + \" terminals: \" + JDD.GetTerminalsAndNumbersString(trans, getNumDDVarsInTrans()) + \"\\n\");\n\t\t\tlog.print(\"Reach: \" + JDD.GetNumNodes(reach) + \" nodes\\n\");\n\t\t\tlog.print(\"ODD: \" + ODDUtils.GetNumODDNodes() + \" nodes\\n\");\n\t\t\tfor (i = 0; i < numRewardStructs; i++) {\n\t\t\t\tif (stateRewards[i] != null && !stateRewards[i].equals(JDD.ZERO)) {\n\t\t\t\t\tlog.print(\"State rewards (\" + (i + 1) + ((\"\".equals(rewardStructNames[i])) ? \"\" : (\":\\\"\" + rewardStructNames[i] + \"\\\"\")) + \"): \");\n\t\t\t\t\tlog.print(JDD.GetNumNodes(stateRewards[i]) + \" nodes (\");\n\t\t\t\t\tlog.print(JDD.GetNumTerminals(stateRewards[i]) + \" terminal), \");\n\t\t\t\t\tlog.print(JDD.GetNumMintermsString(stateRewards[i], getNumDDRowVars()) + \" minterms\\n\");\n\t\t\t\t\tif (extra) {\n\t\t\t\t\t\tlog.print(\"State rewards terminals (\" + (i + 1) + ((\"\".equals(rewardStructNames[i])) ? \"\" : (\":\\\"\" + rewardStructNames[i] + \"\\\"\"))\n\t\t\t\t\t\t\t\t+ \"): \");\n\t\t\t\t\t\tlog.print(JDD.GetTerminalsAndNumbersString(stateRewards[i], getNumDDRowVars()) + \"\\n\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (transRewards[i] != null && !transRewards[i].equals(JDD.ZERO)) {\n\t\t\t\t\tlog.print(\"Transition rewards (\" + (i + 1) + ((\"\".equals(rewardStructNames[i])) ? \"\" : (\":\\\"\" + rewardStructNames[i] + \"\\\"\")) + \"): \");\n\t\t\t\t\tlog.print(JDD.GetNumNodes(transRewards[i]) + \" nodes (\");\n\t\t\t\t\tlog.print(JDD.GetNumTerminals(transRewards[i]) + \" terminal), \");\n\t\t\t\t\tlog.print(JDD.GetNumMintermsString(transRewards[i], getNumDDVarsInTrans()) + \" minterms\\n\");\n\t\t\t\t\tif (extra) {\n\t\t\t\t\t\tlog.print(\"Transition rewards terminals (\" + (i + 1) + ((\"\".equals(rewardStructNames[i])) ? \"\" : (\":\\\"\" + rewardStructNames[i] + \"\\\"\"))\n\t\t\t\t\t\t\t\t+ \"): \");\n\t\t\t\t\t\tlog.print(JDD.GetTerminalsAndNumbersString(transRewards[i], getNumDDVarsInTrans()) + \"\\n\");\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic String getTransDDVarSummary()\n\t{\n\t\treturn getNumDDRowVars() + \"r/\" + getNumDDColVars() + \"c\";\n\t}\n\n\t@Override\n\tpublic String getTransDDVarInfo()\n\t{\n\t\tString s = \"DD vars (r/c):\";\n\t\tint n = allDDRowVars.getNumVars();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tint j = allDDRowVars.getVarIndex(i);\n\t\t\ts += \" \" + j + \":\" + getDDVarNames().get(j);\n\t\t\tj = allDDColVars.getVarIndex(i);\n\t\t\ts += \" \" + j + \":\" + getDDVarNames().get(j);\n\t\t}\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic void exportStateRewardsToFile(int r, int exportType, File file, int precision, boolean noexportheaders)\n\t\t\tthrows FileNotFoundException, PrismException\n\t{\n\t\tPrismMTBDD.ExportVector(stateRewards[r], \"c\" + (r + 1), allDDRowVars, odd, exportType, (file == null) ? null : file.getPath(), precision,\n\t\t\t\trewardStructNames[r], noexportheaders);\n\t}\n\n\t@Override\n\tpublic void exportStateRewardsToFile(int r, File file, ModelExportOptions exportOptions)\n\t\t\tthrows FileNotFoundException, PrismException\n\t{\n\t\tint exportType = Prism.convertExportType(exportOptions);\n\t\tint precision = exportOptions.getModelPrecision();\n\t\tboolean noexportheaders = !exportOptions.getPrintHeaders();\n\t\tPrismMTBDD.ExportVector(stateRewards[r], \"c\" + (r + 1), allDDRowVars, odd, exportType, (file == null) ? null : file.getPath(), precision,\n\t\t\t\trewardStructNames[r], noexportheaders);\n\t}\n\n\t@Override\n\tpublic void exportStates(int exportType, PrismLog log)\n\t{\n\t\t// Print header: list of model vars\n\t\tif (exportType == Prism.EXPORT_MATLAB)\n\t\t\tlog.print(\"% \");\n\t\tlog.print(\"(\");\n\t\tint numVars = getNumVars();\n\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\tlog.print(getVarName(i));\n\t\t\tif (i < numVars - 1)\n\t\t\t\tlog.print(\",\");\n\t\t}\n\t\tlog.println(\")\");\n\t\tif (exportType == Prism.EXPORT_MATLAB)\n\t\t\tlog.println(\"states=[\");\n\n\t\t// Print states\n\t\tif (exportType != Prism.EXPORT_MATLAB)\n\t\t\tgetReachableStates().print(log);\n\t\telse\n\t\t\tgetReachableStates().printMatlab(log);\n\n\t\t// Print footer\n\t\tif (exportType == Prism.EXPORT_MATLAB)\n\t\t\tlog.println(\"];\");\n\t}\n\n\t// Other methods\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\t// Clear the model (deref all DDs and DD variables)\n\t\tfor (Map.Entry<String, JDDNode> labelDD : labelsDD.entrySet()) {\n\t\t\tJDD.Deref(labelDD.getValue());\n\t\t}\n\t\tlabelsDD.clear();\n\n\t\tif (varDDRowVars != null)\n\t\t\tJDDVars.derefAllArray(varDDRowVars);\n\t\tif (varDDColVars != null)\n\t\t\tJDDVars.derefAllArray(varDDColVars);\n\n\t\tallDDRowVars.derefAll();\n\t\tallDDColVars.derefAll();\n\t\tJDD.Deref(trans);\n\t\tJDD.Deref(trans01);\n\t\tJDD.Deref(start);\n\t\tif (reach != null)\n\t\t\tJDD.Deref(reach);\n\t\tif (deadlocks != null)\n\t\t\tJDD.Deref(deadlocks);\n\t\tfor (int i = 0; i < numRewardStructs; i++) {\n\t\t\tJDD.Deref(stateRewards[i]);\n\t\t\tJDD.Deref(transRewards[i]);\n\t\t}\n\n\t\tif (odd != null) {\n\t\t\t// clear ODD\n\t\t\tODDUtils.ClearODD(odd);\n\t\t\todd = null;\n\t\t}\n\n\t\tif (modelVariables != null)\n\t\t\tmodelVariables.clear();\n\t}\n\n\t// Other accessors\n\n\t/**\n\t * Get the number of states, as a long.\n\t */\n\tpublic long getNumStatesLong()\n\t{\n\t\treturn (numStates > Long.MAX_VALUE) ? -1 : Math.round(numStates);\n\t}\n\n\t/**\n\t * Get the number of initial states, as a long.\n\t */\n\tpublic long getNumInitialStatesLong()\n\t{\n\t\treturn (numStartStates > Long.MAX_VALUE) ? -1 : Math.round(numStartStates);\n\t}\n\n\t/**\n\t * Get the total number of transitions, as a long.\n\t */\n\tpublic long getNumTransitionsLong()\n\t{\n\t\treturn (numTransitions > Long.MAX_VALUE) ? -1 : Math.round(numTransitions);\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/ModelTransformation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport jdd.JDDNode;\nimport prism.PrismException;\nimport symbolic.states.StateValues;\n\n/**\n * Interface for a model transformation.\n */\npublic interface ModelTransformation<OriginalModel extends Model, TransformedModel extends Model> {\n\n\t/** Get the original model. */\n\tpublic OriginalModel getOriginalModel();\n\n\t/** Get the transformed model. */\n\tpublic TransformedModel getTransformedModel();\n\n\t/** Clear the transformed model and all other intermediate BDD information.\n\t *  Should be called when the transformation is not needed anymore. Does not clear the\n\t *  original model.\n\t */\n\tpublic void clear();\n\n\t/**\n\t * Take a {@code StateValues} object for the transformed model and\n\t * project the values to the original model.\n\t * <br>\n\t * The {@code svTransformedModel} argument is consumed/cleared and should not be\n\t * used afterwards.\n\t * @param svTransformedModel a {@code StateValues} object for the transformed model\n\t * @return a corresponding {@code StateValues} object for the original model.\n\t */\n\tpublic StateValues projectToOriginalModel(StateValues svTransformedModel) throws PrismException;\n\n\t/**\n\t * Get the transformed state set of the states of interest,\n\t * i.e., the set of states that should be calculated to allow a successful\n\t * application of the projectToOriginalModel method.\n\t *\n\t * <br>[REF: <i>result</i>]\n\t */\n\tpublic JDDNode getTransformedStatesOfInterest();\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/ModelTransformationNested.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport jdd.JDDNode;\nimport prism.PrismException;\nimport symbolic.states.StateValues;\n\n/**\n * Nesting of two model transformations.\n * <br>\n * originalModel -(innerTransformation)-&gt; intermediateModel -(outerTransformation)-&gt; transformedModel\n */\npublic class ModelTransformationNested<OriginalModel extends Model, IntermediateModel extends Model, TransformedModel extends Model> implements\n\t\tModelTransformation<OriginalModel, TransformedModel>\n{\n\n\t/** The inner transformation */\n\tprotected ModelTransformation<OriginalModel, IntermediateModel> innerTransformation;\n\t/** The outer transformation */\n\tprotected ModelTransformation<IntermediateModel,TransformedModel> outerTransformation;\n\n\t/**\n\t * Constructor, chain the two transformations.\n\t * <br>\n\t * The transformations will be cleared on a call to {@code clear()}.\n\t * <br>\n\t * [STORE: innerTransformation, outerTransformation ]\n\t */\n\tpublic ModelTransformationNested(ModelTransformation<OriginalModel, IntermediateModel> innerTransformation,\n\t\t\tModelTransformation<IntermediateModel, TransformedModel> outerTransformation) throws PrismException\n\t{\n\t\tthis.innerTransformation = innerTransformation;\n\t\tthis.outerTransformation = outerTransformation;\n\n\t\tif (innerTransformation.getTransformedModel() != outerTransformation.getOriginalModel()) {\n\t\t\tthrow new PrismException(\"Trying to nest unrelated ModelExpressionTransformations.\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic TransformedModel getTransformedModel()\n\t{\n\t\treturn outerTransformation.getTransformedModel();\n\t}\n\n\t@Override\n\tpublic StateValues projectToOriginalModel(StateValues svTransformedModel) throws PrismException\n\t{\n\t\tStateValues svIntermediate = outerTransformation.projectToOriginalModel(svTransformedModel);\n\t\tStateValues svOriginal = innerTransformation.projectToOriginalModel(svIntermediate);\n\t\treturn svOriginal;\n\t}\n\n\t@Override\n\tpublic OriginalModel getOriginalModel()\n\t{\n\t\treturn innerTransformation.getOriginalModel();\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\touterTransformation.clear();\n\t\tinnerTransformation.clear();\n\t}\n\n\t@Override\n\tpublic JDDNode getTransformedStatesOfInterest()\n\t{\n\t\treturn outerTransformation.getTransformedStatesOfInterest();\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/ModelVariablesDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport java.util.Vector;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismException;\n\n/**\n * Management and information storage about the DD variables\n * used by a symbolic model.\n * <br>\n * After use, the variable references should be cleared by\n * calling {@code clear()}.\n */\npublic class ModelVariablesDD\n{\n\t/** Vector of DD variable names for the allocated variables */\n\tprivate Vector<String> ddVarNames = new Vector<String>();\n\t/** The allocated variables */\n\tprivate JDDVars ddVariables = new JDDVars();\n\t/** The next free variable index */\n\tprivate int nextDDVarIndex = 0;\n\n\t/** Storage for the preallocated extra state variables */\n\tprivate JDDVars extraStateVariables = new JDDVars();\n\t/** Storage for the preallocated extra action variables */\n\tprivate JDDVars extraActionVariables = new JDDVars();\n\n\t/** Constructor */\n\tpublic ModelVariablesDD()\n\t{\n\t}\n\n\t/**\n\t * Create a copy of this ModelVariablesDD.\n\t * All variable information is copied, i.e., the\n\t * result has to be cleared after use.\n\t */\n\tpublic ModelVariablesDD copy()\n\t{\n\t\tModelVariablesDD result = new ModelVariablesDD();\n\t\tresult.ddVarNames = new Vector<String>(ddVarNames);\n\t\tresult.ddVariables = ddVariables.copy();\n\t\tresult.extraStateVariables = extraStateVariables.copy();\n\t\tresult.extraActionVariables = extraActionVariables.copy();\n\t\tresult.nextDDVarIndex = nextDDVarIndex;\n\n\t\treturn result;\n\t}\n\n\t/** Clear all variable references */\n\tpublic void clear()\n\t{\n\t\tddVariables.derefAll();\n\t\textraStateVariables.derefAll();\n\t\textraActionVariables.derefAll();\n\t}\n\n\t/** Return the vector with variable names for a given variable index */\n\tpublic Vector<String> getDDVarNames()\n\t{\n\t\treturn ddVarNames;\n\t}\n\n\t/**\n\t * Allocate a new variable for the model.\n\t * <br>[ REFS: <i>result</i> ]\n\t * @param name a name for the variable\n\t */\n\tpublic JDDNode allocateVariable(String name)\n\t{\n\t\tJDDNode v = JDD.Var(nextDDVarIndex);\n\t\tnextDDVarIndex++;\n\n\t\tddVariables.addVar(v.copy());\n\n\t\tddVarNames.add(name);\n\t\treturn v;\n\t}\n\n\t/** Preallocate the given number of state variables */\n\tpublic void preallocateExtraStateVariables(int count)\n\t{\n\t\tfor (int i=0; i<count; i++) {\n\t\t\tJDDNode v = allocateVariable(\"\");\n\t\t\textraStateVariables.addVar(v);\n\t\t}\n\t}\n\n\t/**\n\t * Allocate a new state variable from the pool of\n\t * preallocated state variables.\n\t * <br>\n\t * If the pool is empty, allocate a new variable\n\t * at the end.\n\t * <br> [ REFS: <i>result</i> ]\n\t * @param name the name for the variable\n\t */\n\tpublic JDDNode allocateExtraStateVariable(String name)\n\t{\n\t\tJDDNode v;\n\t\tif (extraStateVariables.getNumVars() > 0) {\n\t\t\tv = extraStateVariables.getVar(0);\n\t\t\textraStateVariables.removeVar(v);\n\n\t\t\tddVarNames.set(v.getIndex(), name);\n\t\t} else {\n\t\t\t// allocate at the end\n\t\t\tv = allocateVariable(name);\n\t\t}\n\t\treturn v;\n\t}\n\n\t/**\n\t * Returns true if there are enough preallocated state variables\n\t * such that {@code 2*bits} variables can be allocated from the pool\n\t */\n\tpublic boolean canPrependExtraStateVariable(int bits)\n\t{\n\t\treturn (bits*2 <= extraStateVariables.getNumVars());\n\t}\n\n\t/**\n\t * Allocate {@code bits} pairs of row and col variables.\n\t * <br>\n\t * If {@code prepend} is true and there is not enough space\n\t * in the preallocated state variable pool, throws an exception.\n\t * <br>[ REFS: <i>result</i> ]\n\t * @param bits number of state variable pairs\n\t * @param name the name of the variable\n\t * @param prepend should the variables be allocated from the preallocated pool?\n\t */\n\tpublic JDDVars allocateExtraStateVariable(int bits, String name, boolean prepend) throws PrismException\n\t{\n\t\tint newVarCount = 2*bits;\n\n\t\tJDDVars result = new JDDVars();\n\t\tif (newVarCount == 0) return result;\n\n\t\tif (prepend) {\n\t\t\tif (!canPrependExtraStateVariable(bits)) {\n\t\t\t\tthrow new PrismException(\"Can not prepend \"+(newVarCount)+\" extra row/col variables\");\n\t\t\t}\n\n\t\t\t// take the bottom nVarCount extra variables from the\n\t\t\t// extraStateVariables array, starting with index v\n\t\t\tint v = extraStateVariables.getNumVars() - newVarCount;\n\t\t\tfor (int i=0; i < bits; i++) {\n\t\t\t\t// transfer row, col from extraStateVariables to result,\n\t\t\t\t// no need to ref again\n\t\t\t\tJDDNode row_var = extraStateVariables.getVar(v++);\n\t\t\t\tJDDNode col_var = extraStateVariables.getVar(v++);\n\n\t\t\t\tresult.addVar(row_var);\n\t\t\t\tresult.addVar(col_var);\n\n\t\t\t\tddVarNames.set(row_var.getIndex(), name+\".\"+i);\n\t\t\t\tddVarNames.set(col_var.getIndex(), name+\"'.\"+i);\n\t\t\t}\n\n\t\t\t// remove variables from extraStateVariables\n\t\t\textraStateVariables.removeVars(result);\n\n\t\t\treturn result;\n\t\t} else {\n\t\t\tfor (int i=0; i < bits; i++) {\n\t\t\t\tresult.addVar(allocateVariable(name+\".\"+i));\n\t\t\t\tresult.addVar(allocateVariable(name+\"'.\"+i));\n\t\t\t}\n\t\t}\n\n\t\treturn result;\n\t}\n\n\t/** Preallocate the given number of action variables */\n\tpublic void preallocateExtraActionVariables(int count)\n\t{\n\t\tfor (int i=0;i<count;i++) {\n\t\t\tJDDNode v = allocateVariable(\"\");\n\t\t\textraActionVariables.addVar(v);\n\t\t}\n\t}\n\n\t/**\n\t * Allocate {@code n} action variables.\n\t * <br>\n\t * If there is not enough space in the preallocated variable pool, throws an exception.\n\t * <br>[ REFS: <i>result</i> ]\n\t * @param n number of action variables to allocate\n\t * @param name the name of the variable\n\t * \t */\n\tpublic JDDVars allocateExtraActionVariable(int n, String name) throws PrismException\n\t{\n\t\tJDDVars result = new JDDVars();\n\t\tif (n == 0) return result;\n\n\t\tif (extraActionVariables.getNumVars() < n) {\n\t\t\tthrow new PrismException(\"Not enough extra action variables preallocated, please increase using -ddextraactionvars switch!\");\n\t\t}\n\n\t\tint v = extraActionVariables.getNumVars() - n;\n\t\tfor (int i=0; i < n; i++) {\n\t\t\t// transfer action var from extraActionVariables to result,\n\t\t\t// no need to ref again\n\t\t\tJDDNode action_var = extraActionVariables.getVar(v++);\n\t\t\tresult.addVar(action_var);\n\t\t\tddVarNames.set(action_var.getIndex(), name+\".\"+i);\n\t\t}\n\n\t\t// remove variables from extraActionVariables\n\t\textraActionVariables.removeVars(result);\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Get the extra state variables.\n\t * This is not a copy.\n\t *\n\t * <br>[ REFs: <i>none</i>, DEREFs: <i>none</i> ]\n\t */\n\tpublic JDDVars getExtraStateVariables() {\n\t\treturn extraStateVariables;\n\t}\n\n\t/**\n\t * Get the extra action variables.\n\t * This is not a copy.\n\t *\n\t * <br>[ REFs: <i>none</i>, DEREFs: <i>none</i> ]\n\t */\n\tpublic JDDVars getExtraActionVariables() {\n\t\treturn extraActionVariables;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/NondetModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport io.ModelExportOptions;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport jdd.SanityJDD;\nimport mtbdd.PrismMTBDD;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationInt;\nimport parser.ast.Expression;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismUtils;\nimport sparse.PrismSparse;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.ArrayList;\nimport java.util.Map.Entry;\n\n/**\n * Class for symbolic (BDD-based) representation of an MDP.\n */\npublic class NondetModel extends ModelSymbolic\n{\n\t// Extra (MT)BDDs and variables\n\n\t/** BDD (over row and nondet variables) representing a \"mask\"\n\t * for the nondeterministic choices, with a 0 where there is a\n\t * choice present, and a 1 where there is none.\n\t * Used for minimising over nondeterminism. */\n\tprotected JDDNode nondetMask;\n\t/** DD variables used to represent nondeterminism */\n\tprotected JDDVars allDDNondetVars;\n\t/** BDD (over row and nondet variables) for choices that not action-labelled */\n\tprotected JDDNode transInd;\n\t/** BDD (over row and nondet variables) for choices labelled with each action */\n\tprotected JDDNode transSynch[];\n\t/** BDD for the transition relation (just state pairs) */\n\tprotected JDDNode transReln;\n\t/** MTBDDs (over row and nondet DD variables) used to store the action\n\t * for each choice, as a 1-indexed action index for each state-choice pair. */\n\tprotected JDDNode transActions;\n\n\t// Extra statistics\n\n\t/** Total number of choices */\n\tprotected double numChoices;\n\n\t// Constructor\n\n\tpublic NondetModel(JDDNode trans, JDDNode start, JDDVars allDDRowVars, JDDVars allDDColVars, JDDVars allDDNondetVars, ModelVariablesDD modelVariables,\n\t\t\t\t\t VarList varList, JDDVars[] varDDRowVars, JDDVars[] varDDColVars)\n\t{\n\t\tsuper(trans, start, allDDRowVars, allDDColVars, modelVariables, varList, varDDRowVars, varDDColVars);\n\t\tthis.allDDNondetVars = allDDNondetVars;\n\t}\n\n\t// Mutators\n\n\t/**\n\t * Set the MTBDDs (over row and nondet DD variables) used to store the action\n\t * for each choice, as a 1-indexed action index for each state-choice pair.\n\t */\n\tpublic void setTransActions(JDDNode transActions)\n\t{\n\t\tthis.transActions = transActions;\n\t}\n\n\t/**\n\t * Set the BDD (over row and nondet variables) for choices that not action-labelled\n\t */\n\tpublic void setTransInd(JDDNode transInd)\n\t{\n\t\tthis.transInd = transInd;\n\t}\n\n\t/**\n\t * Set the BDDs (over row and nondet variables) for choices labelled with each action\n\t */\n\tpublic void setTransSynch(JDDNode[] transSynch)\n\t{\n\t\tthis.transSynch = transSynch;\n\t}\n\n\t@Override\n\tpublic void doReachability() throws PrismException\n\t{\n\t\tJDDNode tmp;\n\n\t\t// remove any nondeterminism\n\t\tJDD.Ref(trans01);\n\t\ttmp = JDD.MaxAbstract(trans01, allDDNondetVars);\n\n\t\t// compute reachable states\n\t\tJDDNode reachable = PrismMTBDD.Reachability(tmp, allDDRowVars, allDDColVars, start);\n\t\tJDD.Deref(tmp);\n\n\t\t// set the reachable states, compute numStates, create the ODD, etc\n\t\tsetReach(reachable);\n\t}\n\n\t@Override\n\tpublic void doReachability(JDDNode seed) throws PrismException\n\t{\n\t\tJDDNode tmp;\n\n\t\t// do sanity check on seed if checking is enabled\n\t\tif (SanityJDD.enabled)\n\t\t\tSanityJDD.checkIsStateSet(seed, getAllDDRowVars());\n\n\t\t// remove any nondeterminism from the 0/1-transition function\n\t\tJDD.Ref(trans01);\n\t\ttmp = JDD.MaxAbstract(trans01, allDDNondetVars);\n\n\t\t// S = union of initial states and seed. seed is dereferenced here.\n\t\tJDDNode S = JDD.Or(start.copy(), seed);\n\n\t\t// compute reachable states\n\t\tJDDNode reachable = PrismMTBDD.Reachability(tmp, allDDRowVars, allDDColVars, S);\n\t\tJDD.Deref(tmp);\n\t\tJDD.Deref(S);\n\n\t\t// set the reachable states, compute numStates, create the ODD, etc\n\t\tsetReach(reachable);\n\t}\n\n\t@Override\n\tpublic void filterReachableStates()\n\t{\n\t\t// remove non-reachable states from various dds\n\t\t// (and calculate num transitions, etc.)\n\t\t// (and build mask)\n\n\t\tsuper.filterReachableStates();\n\t\t// also filter transInd/tranSynch DDs (if necessary)\n\t\tif (transInd != null) {\n\t\t\tJDD.Ref(reach);\n\t\t\ttransInd = JDD.Apply(JDD.TIMES, reach, transInd);\n\t\t\tfor (int i = 0; i < numSynchs; i++) {\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\ttransSynch[i] = JDD.Apply(JDD.TIMES, reach, transSynch[i]);\n\t\t\t}\n\t\t}\n\t\t// also filter transReln DD (if necessary)\n\t\tif (transReln != null) {\n\t\t\tJDD.Ref(reach);\n\t\t\ttransReln = JDD.Apply(JDD.TIMES, reach, transReln);\n\t\t}\n\n\t\t// build mask for nondeterminstic choices\n\t\t// (and work out number of choices)\n\t\tJDD.Ref(trans01);\n\t\tJDD.Ref(reach);\n\t\tif (this.nondetMask != null)\n\t\t\tJDD.Deref(this.nondetMask);\n\t\t// nb: this assumes that there are no deadlock states\n\t\tnondetMask = JDD.And(JDD.ThereExists(trans01, allDDColVars), reach);\n\t\tnumChoices = JDD.GetNumMinterms(nondetMask, getNumDDRowVars() + getNumDDNondetVars());\n\t\tJDD.Ref(reach);\n\t\tnondetMask = JDD.And(JDD.Not(nondetMask), reach);\n\t\t// Action label index info\n\t\tif (transActions != null) {\n\t\t\t// transActions just stored per state so only filter rows\n\t\t\tJDD.Ref(reach);\n\t\t\ttransActions = JDD.Apply(JDD.TIMES, reach, transActions);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix)\n\t{\n\t\t// find states with at least one transition\n\t\tJDD.Ref(trans01);\n\t\tdeadlocks = JDD.ThereExists(trans01, allDDColVars);\n\t\tdeadlocks = JDD.ThereExists(deadlocks, allDDNondetVars);\n\n\t\t// find reachable states with no transitions\n\t\tJDD.Ref(reach);\n\t\tdeadlocks = JDD.And(reach, JDD.Not(deadlocks));\n\n\t\tif (fix && !deadlocks.equals(JDD.ZERO)) {\n\t\t\t// remove deadlocks by adding self-loops to trans\n\t\t\t// (also update transInd (if necessary) at same time)\n\t\t\t// (note: we don't need to update transActions since\n\t\t\t//  action-less transitions are encoded as 0 anyway)\n\t\t\t// (note: would need to update transPerAction[0]\n\t\t\t//  but this is not stored for MDPs)\n\t\t\tJDDNode tmp;\n\t\t\tJDD.Ref(deadlocks);\n\t\t\ttmp = JDD.SetVectorElement(JDD.Constant(0), allDDNondetVars, 0, 1);\n\t\t\ttmp = JDD.And(tmp, JDD.Identity(allDDRowVars, allDDColVars));\n\t\t\ttmp = JDD.And(deadlocks, tmp);\n\t\t\tJDD.Ref(tmp);\n\t\t\ttrans = JDD.Apply(JDD.PLUS, trans, tmp);\n\t\t\tJDD.Ref(tmp);\n\t\t\ttrans01 = JDD.Apply(JDD.PLUS, trans01, tmp);\n\t\t\tif (transInd != null) {\n\t\t\t\tJDD.Ref(tmp);\n\t\t\t\ttransInd = JDD.Or(transInd, JDD.ThereExists(tmp, allDDColVars));\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t\t// recompute transReln (if needed)\n\t\t\tif (transReln != null) {\n\t\t\t\tJDD.Deref(transReln);\n\t\t\t\tJDD.Ref(trans01);\n\t\t\t\ttransReln = JDD.ThereExists(trans01, allDDNondetVars);\n\t\t\t}\n\t\t\t// update transition count\n\t\t\tnumTransitions = JDD.GetNumMinterms(trans01, getNumDDVarsInTrans());\n\t\t\t// re-build mask for nondeterminstic choices\n\t\t\t// (and work out number of choices)\n\t\t\tJDD.Ref(trans01);\n\t\t\tJDD.Ref(reach);\n\t\t\tif (this.nondetMask != null)\n\t\t\t\tJDD.Deref(this.nondetMask);\n\t\t\tnondetMask = JDD.And(JDD.ThereExists(trans01, allDDColVars), reach);\n\t\t\tnumChoices = JDD.GetNumMinterms(nondetMask, getNumDDRowVars() + getNumDDNondetVars());\n\t\t\tJDD.Ref(reach);\n\t\t\tnondetMask = JDD.And(JDD.Not(nondetMask), reach);\n\t\t}\n\t}\n\n\t// Accessors (for Model)\n\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn ModelType.MDP;\n\t}\n\n\t@Override\n\tpublic JDDNode getTransReln()\n\t{\n\t\t// First, compute the transition relation if it is not there\n\t\tif (transReln == null) {\n\t\t\tJDD.Ref(trans01);\n\t\t\ttransReln = JDD.ThereExists(trans01, allDDNondetVars);\n\t\t}\n\t\treturn transReln;\n\t}\n\n\t@Override\n\tpublic int getNumDDVarsInTrans()\n\t{\n\t\treturn allDDRowVars.n() * 2 + allDDNondetVars.n();\n\t}\n\n\t@Override\n\tpublic void printTransInfo(PrismLog log, boolean extra)\n\t{\n\t\tsuper.printTransInfo(log, extra);\n\t\tif (extra) {\n\t\t\tif (transActions != null) {\n\t\t\t\tlog.print(\"Choice action info: \");\n\t\t\t\tlog.println(JDD.GetInfoString(transActions, allDDRowVars.n() + allDDNondetVars.n()));\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic String getTransDDVarSummary()\n\t{\n\t\treturn super.getTransDDVarSummary() + \"/\" + getNumDDNondetVars() + \"nd\";\n\t}\n\n\t@Override\n\tpublic String getTransDDVarInfo()\n\t{\n\t\tString s = \"DD vars (nd):\";\n\t\tint n = allDDNondetVars.getNumVars();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tint j = allDDNondetVars.getVarIndex(i);\n\t\t\ts += \" \" + j + \":\" + getDDVarNames().get(j);\n\t\t}\n\t\ts += \"\\n\" + super.getTransDDVarInfo();\n\t\treturn s;\n\t}\n\n\t@Override\n\tpublic void exportToFile(int exportType, boolean explicit, File file, int precision) throws FileNotFoundException, PrismException\n\t{\n\t\tif (!explicit) {\n\t\t\t// can only do explicit (sparse matrix based) export for mdps\n\t\t} else {\n\t\t\tPrismSparse.ExportMDP(trans, transActions, getSynchs(), getTransSymbol(), allDDRowVars, allDDColVars, allDDNondetVars, odd, exportType,\n\t\t\t\t\t(file != null) ? file.getPath() : null, precision);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportToFile(File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\tint exportType = Prism.convertExportTypeTrans(exportOptions);\n\t\tint precision = exportOptions.getModelPrecision();\n\t\tJDDNode transActions = exportOptions.getShowActions() ? this.transActions : null;\n\t\tPrismSparse.ExportMDP(trans, transActions, getSynchs(), getTransSymbol(), allDDRowVars, allDDColVars, allDDNondetVars, odd, exportType,\n\t\t\t\t(file != null) ? file.getPath() : null, precision);\n\t}\n\n\t@Override\n\tpublic void exportTransRewardsToFile(int r, int exportType, boolean ordered, File file, int precision, boolean noexportheaders) throws FileNotFoundException, PrismException\n\t{\n\t\tif (!ordered) {\n\t\t\t// can only do explicit (sparse matrix based) export for mdps\n\t\t} else {\n\t\t\tPrismSparse.ExportSubMDP(trans, transRewards[r], \"C\" + (r + 1), allDDRowVars, allDDColVars, allDDNondetVars, odd, exportType, (file == null) ? null : file.getPath(), precision, rewardStructNames[r], noexportheaders);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportTransRewardsToFile(int r, File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\tint exportType = Prism.convertExportTypeTrans(exportOptions);\n\t\tint precision = exportOptions.getModelPrecision();\n\t\tboolean noexportheaders = !exportOptions.getPrintHeaders();\n\t\tPrismSparse.ExportSubMDP(trans, transRewards[r], \"C\" + (r + 1), allDDRowVars, allDDColVars, allDDNondetVars, odd, exportType, (file == null) ? null : file.getPath(), precision, rewardStructNames[r], noexportheaders);\n\t}\n\n\t@Override\n\tpublic String getTransName()\n\t{\n\t\treturn \"Transition matrix\";\n\t}\n\n\t@Override\n\tpublic String getTransSymbol()\n\t{\n\t\treturn \"S\";\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tsuper.clear();\n\t\tallDDNondetVars.derefAll();\n\t\tJDD.Deref(nondetMask);\n\t\tif (transInd != null)\n\t\t\tJDD.Deref(transInd);\n\t\tif (transSynch != null)\n\t\t\tfor (int i = 0; i < numSynchs; i++) {\n\t\t\t\tJDD.Deref(transSynch[i]);\n\t\t\t}\n\t\tif (transReln != null)\n\t\t\tJDD.Deref(transReln);\n\t\tif (transActions != null) {\n\t\t\tJDD.Deref(transActions);\n\t\t}\n\t}\n\n\t// Accessors (for MDPs)\n\n\t/**\n\t * Get the total number of choices.\n\t */\n\tpublic long getNumChoices()\n\t{\n\t\treturn (numChoices > Long.MAX_VALUE) ? -1 : Math.round(numChoices);\n\t}\n\n\t/**\n\t * Get the total number of choices as a string.\n\t */\n\tpublic String getNumChoicesString()\n\t{\n\t\treturn PrismUtils.bigIntToString(numChoices);\n\t}\n\n\t/**\n\t * Get a BDD (over row and nondet variables) representing a \"mask\"\n\t * for the nondeterministic choices, with a 0 where there is a\n\t * choice present, and a 1 where there is none.\n\t * Used for minimising over nondeterminism.\n\t */\n\tpublic JDDNode getNondetMask()\n\t{\n\t\treturn nondetMask;\n\t}\n\n\t/**\n\t * Get (all) the DD variables used to represent nondeterminism.\n\t */\n\tpublic JDDVars getAllDDNondetVars()\n\t{\n\t\treturn allDDNondetVars;\n\t}\n\n\t/**\n\t * Get the total number of DD variables used to represent nondeterminism.\n\t */\n\tpublic int getNumDDNondetVars()\n\t{\n\t\treturn allDDNondetVars.n();\n\t}\n\n\t/**\n\t * Get the BDD (over row and nondet variables) for choices that not action-labelled\n\t */\n\tpublic JDDNode getTransInd()\n\t{\n\t\treturn transInd;\n\t}\n\n\t/**\n\t * Set the BDDs (over row and nondet variables) for choices labelled with each action\n\t */\n\tpublic JDDNode[] getTransSynch()\n\t{\n\t\treturn transSynch;\n\t}\n\n\t/**\n\t * Get the MTBDDs (over row and nondet DD variables) used to store the action\n\t * for each choice, as a 1-indexed action index for each state-choice pair.\n\t */\n\tpublic JDDNode getTransActions()\n\t{\n\t\treturn transActions;\n\t}\n\n\t/**\n\t * Do all choices in each state have a unique action label?\n\t */\n\tpublic boolean areAllChoiceActionsUnique()\n\t{\n\t\t// Action labels\n\t\tfor (int i = 0; i < numSynchs; i++) {\n\t\t\tJDD.Ref(transActions);\n\t\t\tJDDNode tmp = JDD.Equals(transActions, i + 1);\n\t\t\ttmp = JDD.SumAbstract(tmp, allDDNondetVars);\n\t\t\tdouble max = JDD.FindMax(tmp);\n\t\t\tJDD.Deref(tmp);\n\t\t\tif (max > 1)\n\t\t\t\treturn false;\n\t\t}\n\t\t// Unlabelled choices\n\t\tJDD.Ref(reach);\n\t\tJDD.Ref(transActions);\n\t\tJDD.Ref(nondetMask);\n\t\tJDDNode tmp = JDD.And(reach, JDD.And(JDD.LessThanEquals(transActions, 0), JDD.Not(nondetMask)));\n\t\ttmp = JDD.SumAbstract(tmp, allDDNondetVars);\n\t\tdouble max = JDD.FindMax(tmp);\n\t\tJDD.Deref(tmp);\n\t\tif (max > 1)\n\t\t\treturn false;\n\n\t\treturn true;\n\t}\n\n\t/**\n\t * Apply the given model transformation operator to this model\n\t * and return the resulting, transformed model.\n\t * @param transformation the information about the transformation\n\t * @return the transformed model (needs to be cleared after use)\n\t */\n\tpublic NondetModel getTransformed(NondetModelTransformationOperator transformation) throws PrismException\n\t{\n\t\t// New (transformed) model - dds, vars, etc.\n\t\tJDDNode newTrans, newStart;\n\t\tJDDVars newVarDDRowVars[], newVarDDColVars[];\n\t\tJDDVars newAllDDRowVars, newAllDDColVars;\n\t\tJDDVars newAllDDNondetVars;\n\t\tJDDNode newStateRewards[], newTransRewards[];\n\t\tModelVariablesDD newModelVariables;\n\t\tVarList newVarList;\n\t\tString extraStateVar, extraActionVar;\n\t\t// extra variable stuff\n\t\tJDDVars extraDDRowVars, extraDDColVars, extraActionVars;\n\t\t// Misc\n\t\tint i, nStateVars, nActionVars;\n\t\tboolean before;\n\n\t\t// Create a (new, unique) name for the variable that will represent extra states\n\t\textraStateVar = transformation.getExtraStateVariableName();\n\t\twhile (varList.exists(extraStateVar)) {\n\t\t\textraStateVar = \"_\" + extraStateVar;\n\t\t}\n\n\t\t// Create a (new, unique) name for the variable that will represent extra actions\n\t\textraActionVar = transformation.getExtraActionVariableName();\n\t\twhile (varList.exists(extraActionVar)) {\n\t\t\textraActionVar = \"_\" + extraActionVar;\n\t\t}\n\n\t\tnewModelVariables = this.getModelVariables().copy();\n\n\t\t// See how many new dd vars will be needed for extra state variables\n\t\t// and whether there is room to put them before rather than after the existing vars\n\t\tnStateVars = transformation.getExtraStateVariableCount();\n\t\tbefore = newModelVariables.canPrependExtraStateVariable(nStateVars);\n\n\t\textraDDRowVars = new JDDVars();\n\t\textraDDColVars = new JDDVars();\n\t\t// Create the new dd state variables\n\t\tJDDVars extraStateVars = newModelVariables.allocateExtraStateVariable(nStateVars, extraStateVar, before);\n\n\t\tfor (i = 0; i < nStateVars; i++) {\n\t\t\textraDDRowVars.addVar(extraStateVars.getVar(2*i));\n\t\t\textraDDColVars.addVar(extraStateVars.getVar(2*i+1));\n\t\t}\n\n\t\t// notify the transformation about the allocated state variables\n\t\ttransformation.hookExtraStateVariableAllocation(extraDDRowVars.copy(), extraDDColVars.copy());\n\n\t\t// allocate action vars\n\t\tnActionVars = transformation.getExtraActionVariableCount();\n\t\textraActionVars = newModelVariables.allocateExtraActionVariable(nActionVars, extraActionVar);\n\n\t\t// notify the transformation about the allocated action variables\n\t\ttransformation.hookExtraActionVariableAllocation(extraActionVars.copy());\n\n\t\t// Generate new newAllDDNondetVars\n\t\tnewAllDDNondetVars = new JDDVars();\n\t\tnewAllDDNondetVars.copyVarsFrom(extraActionVars);\n\t\tnewAllDDNondetVars.copyVarsFrom(this.allDDNondetVars);\n\n\t\t// Create/populate new state variable lists\n\t\tif (nStateVars == 0) {\n\t\t\t// no additional state vars, we can just copy everything\n\t\t\tnewVarDDRowVars = JDDVars.copyArray(varDDRowVars);\n\t\t\tnewVarDDColVars = JDDVars.copyArray(varDDColVars);\n\t\t\tnewAllDDRowVars = allDDRowVars.copy();\n\t\t\tnewAllDDColVars = allDDColVars.copy();\n\t\t\tnewVarList = (VarList) varList.clone();\n\t\t} else {\n\t\t\t// insert new variable either before or after the other variables\n\t\t\tnewVarDDRowVars = new JDDVars[varDDRowVars.length + 1];\n\t\t\tnewVarDDColVars = new JDDVars[varDDRowVars.length + 1];\n\t\t\tnewVarDDRowVars[before ? 0 : varDDRowVars.length] = extraDDRowVars.copy();\n\t\t\tnewVarDDColVars[before ? 0 : varDDColVars.length] = extraDDColVars.copy();\n\t\t\tfor (i = 0; i < varDDRowVars.length; i++) {\n\t\t\t\tnewVarDDRowVars[before ? i + 1 : i] = varDDRowVars[i].copy();\n\t\t\t\tnewVarDDColVars[before ? i + 1 : i] = varDDColVars[i].copy();\n\t\t\t}\n\t\t\tif (before) {\n\t\t\t\tnewAllDDRowVars = extraDDRowVars.copy();\n\t\t\t\tnewAllDDColVars = extraDDColVars.copy();\n\t\t\t\tnewAllDDRowVars.copyVarsFrom(allDDRowVars);\n\t\t\t\tnewAllDDColVars.copyVarsFrom(allDDColVars);\n\t\t\t} else {\n\t\t\t\tnewAllDDRowVars = allDDRowVars.copy();\n\t\t\t\tnewAllDDColVars = allDDColVars.copy();\n\t\t\t\tnewAllDDRowVars.copyVarsFrom(extraDDRowVars);\n\t\t\t\tnewAllDDColVars.copyVarsFrom(extraDDColVars);\n\t\t\t}\n\t\t\tnewVarList = (VarList) varList.clone();\n\t\t\tDeclaration decl = new Declaration(extraStateVar, new DeclarationInt(Expression.Int(0), Expression.Int((1 << nStateVars) - 1)));\n\t\t\tif (before) {\n\t\t\t\tnewVarList.addVarAtStart(decl, 1);\n\t\t\t} else {\n\t\t\t\tnewVarList.addVar(decl, 1);\n\t\t\t}\n\t\t}\n\n\t\t// Build transition matrix for transformed model\n\t\tnewTrans = transformation.getTransformedTrans();\n\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(newTrans, newAllDDRowVars, newAllDDColVars, newAllDDNondetVars);\n\t\t}\n\n\t\t// Build set of initial states for transformed model\n\t\tnewStart = transformation.getTransformedStart();\n\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsStateSet(newStart, newAllDDRowVars);\n\t\t}\n\n\n\t\t// Build transformed reward information\n\t\tnewStateRewards = new JDDNode[stateRewards.length];\n\t\tfor (i=0; i < stateRewards.length; i++) {\n\t\t\tnewStateRewards[i] = transformation.getTransformedStateReward(stateRewards[i]);\n\n\t\t\tif (SanityJDD.enabled) {\n\t\t\t\tSanityJDD.checkIsDDOverVars(newStateRewards[i], newAllDDRowVars);\n\t\t\t}\n\t\t}\n\t\tnewTransRewards = new JDDNode[transRewards.length];\n\t\tfor (i=0; i < transRewards.length; i++) {\n\t\t\tnewTransRewards[i] = transformation.getTransformedTransReward(transRewards[i]);\n\n\t\t\tif (SanityJDD.enabled) {\n\t\t\t\tSanityJDD.checkIsDDOverVars(newTransRewards[i], newAllDDRowVars, newAllDDColVars, newAllDDNondetVars);\n\t\t\t}\n\t\t}\n\n\t\t// Create a new model model object to store the product model\n\t\tNondetModel result = new NondetModel(\n\t\t// New transition matrix/start state\n\t\t\t\tnewTrans, newStart,\n\t\t\t\t// New list of all row/col vars\n\t\t\t\tnewAllDDRowVars, newAllDDColVars,\n\t\t\t\t// Nondet variables (unchanged)\n\t\t\t\tnewAllDDNondetVars,\n\t\t\t\t// New model variables\n\t\t\t\tnewModelVariables,\n\t\t\t\t// New var info\n\t\t\t\tnewVarList, newVarDDRowVars, newVarDDColVars);\n\t\t// New reward information\n\t\tresult.setRewards(newStateRewards, newTransRewards, this.rewardStructNames.clone());\n\t\t// Constants (no change)\n\t\tresult.setConstantValues(this.getConstantValues());\n\n\t\t// Set new transActions\n\t\tresult.setTransActions(transformation.getTransformedTransActions());\n\n\t\t// Also need to copy set of action label strings\n\t\tresult.setSynchs(new ArrayList<String>(this.getSynchs()));\n\n\n\t\t// Do reachability/etc. for the new model\n\t\tJDDNode S;\n\t\tif ( (S = transformation.getReachableStates()) != null) {\n\t\t\t// the transformation operator knows the reachable state set\n\t\t\tresult.setReach(S);\n\t\t} else if ( (S = transformation.getReachableStateSeed()) != null ) {\n\t\t\t// the transformation operator knows a seed for the reachability computation\n\t\t\tresult.doReachability(S);\n\t\t} else {\n\t\t\t// otherwise: do standard reachability\n\t\t\tresult.doReachability();\n\t\t}\n\t\tresult.filterReachableStates();\n\n\t\tif (!transformation.deadlocksAreFine()) {\n\t\t\tresult.findDeadlocks(false);\n\t\t\tif (result.getDeadlockStates().size() > 0) {\n\t\t\t\t// Assuming original model has no deadlocks, neither should the transformed model\n\t\t\t\tthrow new PrismException(\"Transformed model has deadlock states\");\n\t\t\t}\n\t\t}\n\n\t\t// lift labels attached to the model\n\t\tfor (Entry<String, JDDNode> entry : labelsDD.entrySet()) {\n\t\t\tJDDNode labelStates = entry.getValue();\n\t\t\tJDDNode transformedLabelStates = transformation.getTransformedLabelStates(labelStates, result.getReach());\n\t\t\tresult.labelsDD.put(entry.getKey(), transformedLabelStates);\n\t\t}\n\n\n\t\textraDDRowVars.derefAll();\n\t\textraDDColVars.derefAll();\n\t\textraActionVars.derefAll();\n\n\t\treturn result;\n\t}\n\n\t/**\n\t * Apply the given model transformation, specified as a\n\t * ProbModelTransformationOperator, on this model\n\t * and return the resulting, transformed model.\n\t * <br>\n\t * This convenience method does the transformation via a\n\t * NondetModelTransformationOperation that is constructed on-the-fly\n\t * from the given transformation. For this to work properly,\n\t * the getTrans method has to preserve the action information,\n\t * i.e., simply augment the state space in some way.\n\t * <br>\n\t * As an example, a simple product construction with a deterministic\n\t * automaton would work fine, as that does not change the structure\n\t * of the transitions.\n\t *\n\t * @param transformation the transformation operator\n\t * @return the transformed model (needs to be cleared after use)\n\t */\n\tpublic NondetModel getTransformed(final ProbModelTransformationOperator transformation) throws PrismException\n\t{\n\t\tNondetModelTransformationOperator ndTransformation = new NondetModelTransformationOperator(this) {\n\t\t\t@Override\n\t\t\tpublic int getExtraStateVariableCount()\n\t\t\t{\n\t\t\t\treturn transformation.getExtraStateVariableCount();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic int getExtraActionVariableCount()\n\t\t\t{\n\t\t\t\t// we don't change the nondeterministic choices\n\t\t\t\treturn 0;\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic JDDNode getTransformedTrans() throws PrismException\n\t\t\t{\n\t\t\t\t// pass through\n\t\t\t\treturn transformation.getTransformedTrans();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic JDDNode getTransformedStart() throws PrismException\n\t\t\t{\n\t\t\t\t// pass through\n\t\t\t\treturn transformation.getTransformedStart();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic String getExtraStateVariableName()\n\t\t\t{\n\t\t\t\t// pass through\n\t\t\t\treturn transformation.getExtraStateVariableName();\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic void hookExtraStateVariableAllocation(JDDVars extraRowVars, JDDVars extraColVars)\n\t\t\t{\n\t\t\t\t// pass through\n\t\t\t\ttransformation.hookExtraStateVariableAllocation(extraRowVars, extraColVars);\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic void hookExtraActionVariableAllocation(JDDVars extraActionVars)\n\t\t\t{\n\t\t\t\tif (extraActionVars.n() != 0) {\n\t\t\t\t\tthrow new RuntimeException(\"NondetModel.getTransformed(ProbModelTransformation) has not requested action variables\");\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic JDDNode getTransformedStateReward(JDDNode oldReward) throws PrismException\n\t\t\t{\n\t\t\t\t// pass through\n\t\t\t\treturn transformation.getTransformedStateReward(oldReward);\n\t\t\t}\n\n\t\t\t@Override\n\t\t\tpublic JDDNode getTransformedTransReward(JDDNode oldReward) throws PrismException\n\t\t\t{\n\t\t\t\t// pass through\n\t\t\t\treturn transformation.getTransformedTransReward(oldReward);\n\t\t\t}\n\t\t};\n\n\t\t// do transformation with the NondetModelTransformationOperator\n\t\treturn getTransformed(ndTransformation);\n\t}\n}\n\n"
  },
  {
    "path": "prism/src/symbolic/model/NondetModelTransformationOperator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismException;\nimport symbolic.model.NondetModel;\n\n/**\n * Description of a transformation operation for a NondetModel (MDP).\n * The transformation can request the allocation of extra state and action variables,\n * and specify new transition matrix, initial states and reward information.\n * <br>\n * After use, the transformation should be cleared by calling {@code clear()}.\n */\npublic abstract class NondetModelTransformationOperator\n{\n\t/** The original model */\n\tprotected NondetModel originalModel;\n\t/** The extra state variables (rows) */\n\tprotected JDDVars extraRowVars;\n\t/** The extra state variables (columns) */\n\tprotected JDDVars extraColVars;\n\t/** The extra action (non-deterministic choice) variables */\n\tprotected JDDVars extraActionVars;\n\n\t/**\n\t * Constructor with the original model that is to be transformed.\n\t * The original model is not changed and will not be cleared when\n\t * {@code clear()} is called.\n\t */\n\tpublic NondetModelTransformationOperator(NondetModel model)\n\t{\n\t\toriginalModel = model;\n\t}\n\n\t/**\n\t * Clear the transformation.\n\t */\n\tpublic void clear()\n\t{\n\t\tif (extraRowVars != null) {\n\t\t\textraRowVars.derefAll();\n\t\t}\n\t\tif (extraColVars != null) {\n\t\t\textraColVars.derefAll();\n\t\t}\n\t\tif (extraActionVars != null) {\n\t\t\textraActionVars.derefAll();\n\t\t}\n\t}\n\n\t/**\n\t * Return the name (prefix) to use for any new extra state variables.\n\t * Default implementation: Return \"extra\".\n\t */\n\tpublic String getExtraStateVariableName()\n\t{\n\t\treturn \"extra\";\n\t}\n\n\t/**\n\t * Return the name (prefix) to use for any new extra action variable.\n\t * Default implementation: Return \"tau\".\n\t */\n\tpublic String getExtraActionVariableName()\n\t{\n\t\treturn \"tau\";\n\t}\n\n\t/**\n\t * Get the number of extra state variables needed for this transformation.\n\t * This is the number n of state variables and will lead to the allocation of\n\t * 2*n variables, n row and n column variables (interleaved).\n\t */\n\tpublic abstract int getExtraStateVariableCount();\n\n\t/**\n\t * Get the number of needed extra action variables for this transformation.\n\t * This will result in the allocation of n additional non-deterministic choice variables.\n\t */\n\tpublic abstract int getExtraActionVariableCount();\n\n\t/**\n\t * This method is called to notify the transformation operator\n\t * about the state variables that were allocated.\n\t * <br>\n\t * The extraRowVars and extraColVars are copies, i.e., this method is responsible\n\t * to ensure that they will be derefed eventually.\n\t * <br>\n\t * Default implementation: Store in extraRowVars and extraColVars fields.\n\t * <br>[ STORES: extraRowVars, extraColVars ]\n\t */\n\tpublic void hookExtraStateVariableAllocation(JDDVars extraRowVars, JDDVars extraColVars)\n\t{\n\t\tthis.extraRowVars = extraRowVars;\n\t\tthis.extraColVars = extraColVars;\n\t}\n\n\t/**\n\t * This method is called to notify the transformation about the action variables\n\t * that were allocated.\n\t * <br>\n\t * The extraActionsVars are copies, i.e., this method is responsible\n\t * to ensure that they will be derefed eventually.\n\t * <br>\n\t * Default implementation: store in extraActionVars field.\n\t * <br>[ STORES: extraActionVars ]\n\t */\n\tpublic void hookExtraActionVariableAllocation(JDDVars extraActionVars)\n\t{\n\t\tthis.extraActionVars = extraActionVars;\n\t}\n\n\t/**\n\t * Get the transformed transition function.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic abstract\tJDDNode getTransformedTrans() throws PrismException;\n\n\t/**\n\t * Get the transformed start function.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic abstract JDDNode getTransformedStart() throws PrismException;\n\n\t/**\n\t * Get the transformed state reward relation, given the old reward relation.\n\t * <br>\n\t * Default implementation: Return the old reward relation, unchanged.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getTransformedStateReward(JDDNode oldReward) throws PrismException\n\t{\n\t\treturn oldReward.copy();\n\t}\n\n\t/**\n\t * Get the transformed transition reward relation, given the old reward relation.\n\t * <br>\n\t * Default implementation: Return the old reward relation, unchanged.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getTransformedTransReward(JDDNode oldReward) throws PrismException\n\t{\n\t\treturn oldReward.copy();\n\t}\n\n\t/**\n\t * Get the transformed trans actions relation,\n\t * mapping (state,action) to action index.\n\t * Action index 0 indicates unnamed action.\n\t * <br>\n\t * Default implementation: The old trans action relation is returned.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getTransformedTransActions() throws PrismException\n\t{\n\t\tif (originalModel.getTransActions() == null)\n\t\t\treturn null;\n\t\treturn originalModel.getTransActions().copy();\n\t}\n\n\t/**\n\t * Get the transformed (lifted) state set corresponding to a label in the original model.\n\t * As a convenience, the reachable states in the transformed model are provided as well.\n\t * <br>\n\t * Default implementation: Return the old state set, i.e.,\n\t * assume don't cares for the extra state variables.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getTransformedLabelStates(JDDNode oldLabelStates, JDDNode transformedReach)\n\t{\n\t\treturn oldLabelStates.copy();\n\t}\n\n\t/**\n\t * Directly provide the set of reachable states in the transformed model (optional).\n\t * If the set of reachable states is not known, this function should return {@code null}\n\t * and normal reachability computations will be performed.\n\t * <br/>\n\t * Default implementation: return {@code null}\n\t * <br>[ REFS: <i>result</i> ]\n\t */\n\tpublic JDDNode getReachableStates() throws PrismException {\n\t\treturn null;\n\t}\n\n\t/**\n\t * Provide a set of states in the transformed model that is known to be reachable,\n\t * which is then used as a seed in the subsequent reachability computation (speed-up).\n\t * <br>\n\t * If this transformation operator does not want to provide this information,\n\t * this function should return {@code null} and normal reachability computations\n\t * will be performed (from the start states).\n\t * <br/>\n\t * Default implementation: return {@code null}\n\t * <br>[ REFS: <i>result</i> ]\n\t */\n\tpublic JDDNode getReachableStateSeed() throws PrismException {\n\t\treturn null;\n\t}\n\n\t/**\n\t * If true, this transformation may produce deadlock states and the normal\n\t * deadlock check should not be invoked for the transformed model.\n\t * <br>\n\t * Default implementation: return {@code false}\n\t */\n\tpublic boolean deadlocksAreFine()\n\t{\n\t\treturn false;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/ProbModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport io.ModelExportOptions;\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport jdd.SanityJDD;\nimport mtbdd.PrismMTBDD;\nimport parser.Values;\nimport parser.VarList;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationInt;\nimport parser.ast.Expression;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport sparse.PrismSparse;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\nimport java.util.Map;\n\n/**\n * Class for symbolic (BDD-based) representation of a DTMC.\n */\npublic class ProbModel extends ModelSymbolic\n{\n\t/** Optionally, a separate transition matrix MTBDD for each action label */\n\tprotected JDDNode transPerAction[];\n\n\t// Constructor\n\n\tpublic ProbModel(JDDNode trans, JDDNode start, JDDVars allDDRowVars, JDDVars allDDColVars, ModelVariablesDD modelVariables,\n\t\t\t\t\t VarList varList, JDDVars[] varDDRowVars, JDDVars[] varDDColVars)\n\t{\n\t\tsuper(trans, start, allDDRowVars, allDDColVars, modelVariables, varList, varDDRowVars, varDDColVars);\n\t}\n\n\t// Mutators\n\n\t/**\n\t * Set the transition matrix MTBDDs for each action label\n\t */\n\tpublic void setTransPerAction(JDDNode[] transPerAction)\n\t{\n\t\tthis.transPerAction = transPerAction;\n\t}\n\n\t@Override\n\tpublic void filterReachableStates()\n\t{\n\t\tsuper.filterReachableStates();\n\t\t// Action label index info\n\t\tif (transPerAction != null) {\n\t\t\t// transPerAction stored as matrix so filter both rows/cols\n\t\t\tfor (int i = 0; i < numSynchs + 1; i++) {\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\ttransPerAction[i] = JDD.Apply(JDD.TIMES, reach, transPerAction[i]);\n\t\t\t\tJDD.Ref(reach);\n\t\t\t\tJDDNode tmp = JDD.PermuteVariables(reach, allDDRowVars, allDDColVars);\n\t\t\t\ttransPerAction[i] = JDD.Apply(JDD.TIMES, tmp, transPerAction[i]);\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void findDeadlocks(boolean fix)\n\t{\n\t\t// find states with at least one transition\n\t\tJDD.Ref(trans01);\n\t\tdeadlocks = JDD.ThereExists(trans01, allDDColVars);\n\n\t\t// find reachable states with no transitions\n\t\tJDD.Ref(reach);\n\t\tdeadlocks = JDD.And(reach, JDD.Not(deadlocks));\n\n\t\tif (fix && !deadlocks.equals(JDD.ZERO)) {\n\t\t\t// remove deadlocks by adding self-loops\n\t\t\t// also update transPerAction info, if present\n\t\t\tJDDNode tmp;\n\t\t\tJDD.Ref(deadlocks);\n\t\t\ttmp = JDD.And(deadlocks, JDD.Identity(allDDRowVars, allDDColVars));\n\t\t\tJDD.Ref(tmp);\n\t\t\ttrans = JDD.Apply(JDD.PLUS, trans, tmp);\n\t\t\tJDD.Ref(tmp);\n\t\t\ttrans01 = JDD.Apply(JDD.PLUS, trans01, tmp);\n\t\t\tif (transPerAction != null) {\n\t\t\t\tJDD.Ref(tmp);\n\t\t\t\ttransPerAction[0] = JDD.Apply(JDD.PLUS, transPerAction[0], tmp);\n\t\t\t}\n\t\t\tJDD.Deref(tmp);\n\t\t\t// update model stats\n\t\t\tnumTransitions = JDD.GetNumMinterms(trans01, getNumDDVarsInTrans());\n\t\t}\n\t}\n\n\t// Accessors (for Model)\n\n\t@Override\n\tpublic ModelType getModelType()\n\t{\n\t\treturn ModelType.DTMC;\n\t}\n\n\t@Override\n\tpublic void printTransInfo(PrismLog log, boolean extra)\n\t{\n\t\tsuper.printTransInfo(log, extra);\n\t\tif (extra) {\n\t\t\tif (transPerAction != null) {\n\t\t\t\tfor (int i = 0; i < numSynchs + 1; i++) {\n\t\t\t\t\tlog.print(\"Transition action info: \");\n\t\t\t\t\tlog.print((i == 0 ? \"\" : synchs.get(i - 1)) + \"): \");\n\t\t\t\t\tlog.println(JDD.GetInfoString(transPerAction[i], getNumDDVarsInTrans()));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportToFile(int exportType, boolean explicit, File file, int precision) throws FileNotFoundException, PrismException\n\t{\n\t\tif (!explicit) {\n\t\t\tPrismMTBDD.ExportMatrix(trans, getTransSymbol(), allDDRowVars, allDDColVars, odd, exportType, (file != null) ? file.getPath() : null, precision, null, true);\n\t\t} else {\n\t\t\tPrismSparse.ExportMatrix(trans, getTransSymbol(), allDDRowVars, allDDColVars, odd, exportType, (file != null) ? file.getPath() : null, precision, null, true);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportToFile(File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\tint exportType = Prism.convertExportTypeTrans(exportOptions);\n\t\tint precision = exportOptions.getModelPrecision();\n\t\tif (exportOptions.getShowActions() && transPerAction != null) {\n\t\t\tPrismSparse.ExportMC(transPerAction, getSynchs(), getTransSymbol(), allDDRowVars, allDDColVars, odd, exportType, (file != null) ? file.getPath() : null, precision);\n\t\t} else {\n\t\t\tPrismSparse.ExportMatrix(trans, getTransSymbol(), allDDRowVars, allDDColVars, odd, exportType, (file != null) ? file.getPath() : null, precision, null, true);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportTransRewardsToFile(int r, int exportType, boolean ordered, File file, int precision, boolean noexportheaders) throws FileNotFoundException, PrismException\n\t{\n\t\tif (!ordered) {\n\t\t\tPrismMTBDD.ExportMatrix(transRewards[r], \"C\" + (r + 1), allDDRowVars, allDDColVars, odd, exportType, (file == null) ? null : file.getPath(), precision, rewardStructNames[r], noexportheaders);\n\t\t} else {\n\t\t\tPrismSparse.ExportMatrix(transRewards[r], \"C\" + (r + 1), allDDRowVars, allDDColVars, odd, exportType, (file == null) ? null : file.getPath(), precision, rewardStructNames[r], noexportheaders);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void exportTransRewardsToFile(int r, File file, ModelExportOptions exportOptions) throws FileNotFoundException, PrismException\n\t{\n\t\tint exportType = Prism.convertExportTypeTrans(exportOptions);\n\t\tint precision = exportOptions.getModelPrecision();\n\t\tboolean noexportheaders = !exportOptions.getPrintHeaders();\n\t\tPrismSparse.ExportMatrix(transRewards[r], \"C\" + (r + 1), allDDRowVars, allDDColVars, odd, exportType, (file == null) ? null : file.getPath(), precision, rewardStructNames[r], noexportheaders);\n\t}\n\n\t@Override\n\tpublic String getTransName()\n\t{\n\t\treturn \"Transition matrix\";\n\t}\n\n\t@Override\n\tpublic String getTransSymbol()\n\t{\n\t\treturn \"P\";\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tsuper.clear();\n\t\tif (transPerAction != null) {\n\t\t\tfor (int i = 0; i < numSynchs + 1; i++) {\n\t\t\t\tJDD.Deref(transPerAction[i]);\n\t\t\t}\n\t\t}\n\t}\n\n\t// Accessors (for DTMCs)\n\n\t/**\n\t * Get the transition matrix MTBDDs for each action label\n\t */\n\tpublic JDDNode[] getTransPerAction()\n\t{\n\t\treturn transPerAction;\n\t}\n\n\t/**\n\t * Apply the given model transformation operator to this model\n\t * and return the resulting, transformed model.\n\t * @param transformation the transformation operator\n\t * @return the transformed model (needs to be cleared after use)\n\t */\n\tpublic ProbModel getTransformed(ProbModelTransformationOperator transformation) throws PrismException\n\t{\n\t\t// New (transformed) model - dds, vars, etc.\n\t\tJDDNode newTrans, newStart;\n\t\tJDDVars newVarDDRowVars[], newVarDDColVars[];\n\t\tJDDVars newAllDDRowVars, newAllDDColVars;\n\t\tJDDNode newStateRewards[], newTransRewards[];\n\t\tModelVariablesDD newModelVariables;\n\t\tVarList newVarList;\n\t\tString extraVar;\n\t\t// DRA stuff\n\t\tJDDVars extraDDRowVars, extraDDColVars;\n\t\t// Misc\n\t\tint i, n;\n\t\tboolean before;\n\n\t\t// Create a (new, unique) name for the variable that will represent the extra states\n\t\textraVar = transformation.getExtraStateVariableName();\n\t\twhile (varList.exists(extraVar)) {\n\t\t\textraVar = \"_\" + extraVar;\n\t\t}\n\n\t\tnewModelVariables = this.getModelVariables().copy();\n\n\t\t// See how many new dd vars will be needed for the extra variables\n\t\t// and whether there is room to put them before rather than after the existing vars\n\t\tn = transformation.getExtraStateVariableCount();\n\t\tbefore = newModelVariables.canPrependExtraStateVariable(n);\n\n\t\textraDDRowVars = new JDDVars();\n\t\textraDDColVars = new JDDVars();\n\t\t// Create the new dd state variables\n\t\tJDDVars draVars = newModelVariables.allocateExtraStateVariable(n, extraVar, before);\n\n\t\tfor (i = 0; i < n; i++) {\n\t\t\textraDDRowVars.addVar(draVars.getVar(2*i));\n\t\t\textraDDColVars.addVar(draVars.getVar(2*i+1));\n\t\t}\n\n\t\t// notify the transformation operator about the allocated state variables\n\t\ttransformation.hookExtraStateVariableAllocation(extraDDRowVars.copy(), extraDDColVars.copy());\n\n\t\t// Create/populate new state variable lists\n\t\tif (n==0) {\n\t\t\t// no additional state vars, we can just copy everything\n\t\t\tnewVarDDRowVars = JDDVars.copyArray(varDDRowVars);\n\t\t\tnewVarDDColVars = JDDVars.copyArray(varDDColVars);\n\t\t\tnewAllDDRowVars = allDDRowVars.copy();\n\t\t\tnewAllDDColVars = allDDColVars.copy();\n\t\t\tnewVarList = (VarList) varList.clone();\n\t\t} else {\n\t\t\t// insert new variable either before or after the other variables\n\t\t\tnewVarDDRowVars = new JDDVars[varDDRowVars.length + 1];\n\t\t\tnewVarDDColVars = new JDDVars[varDDRowVars.length + 1];\n\t\t\tnewVarDDRowVars[before ? 0 : varDDRowVars.length] = extraDDRowVars.copy();\n\t\t\tnewVarDDColVars[before ? 0 : varDDColVars.length] = extraDDColVars.copy();\n\t\t\tfor (i = 0; i < varDDRowVars.length; i++) {\n\t\t\t\tnewVarDDRowVars[before ? i + 1 : i] = varDDRowVars[i].copy();\n\t\t\t\tnewVarDDColVars[before ? i + 1 : i] = varDDColVars[i].copy();\n\t\t\t}\n\t\t\tif (before) {\n\t\t\t\tnewAllDDRowVars = extraDDRowVars.copy();\n\t\t\t\tnewAllDDColVars = extraDDColVars.copy();\n\t\t\t\tnewAllDDRowVars.copyVarsFrom(allDDRowVars);\n\t\t\t\tnewAllDDColVars.copyVarsFrom(allDDColVars);\n\t\t\t} else {\n\t\t\t\tnewAllDDRowVars = allDDRowVars.copy();\n\t\t\t\tnewAllDDColVars = allDDColVars.copy();\n\t\t\t\tnewAllDDRowVars.copyVarsFrom(extraDDRowVars);\n\t\t\t\tnewAllDDColVars.copyVarsFrom(extraDDColVars);\n\t\t\t}\n\t\t\tnewVarList = (VarList) varList.clone();\n\t\t\tDeclaration decl = new Declaration(extraVar, new DeclarationInt(Expression.Int(0), Expression.Int((1 << n) - 1)));\n\t\t\tif (before) {\n\t\t\t\tnewVarList.addVarAtStart(decl, 1);\n\t\t\t} else {\n\t\t\t\tnewVarList.addVar(decl, 1);\n\t\t\t}\n\t\t}\n\n\t\t// Build transition matrix for transformed model\n\t\tnewTrans = transformation.getTransformedTrans();\n\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsDDOverVars(newTrans, newAllDDRowVars, newAllDDColVars);\n\t\t}\n\n\t\t// Build set of initial states for transformed model\n\t\tnewStart = transformation.getTransformedStart();\n\n\t\tif (SanityJDD.enabled) {\n\t\t\tSanityJDD.checkIsStateSet(newStart, newAllDDRowVars);\n\t\t}\n\n\n\t\t// Build transformed reward information\n\t\tnewStateRewards = new JDDNode[stateRewards.length];\n\t\tfor (i=0; i < stateRewards.length; i++) {\n\t\t\tnewStateRewards[i] = transformation.getTransformedStateReward(stateRewards[i]);\n\n\t\t\tif (SanityJDD.enabled) {\n\t\t\t\tSanityJDD.checkIsDDOverVars(newStateRewards[i], newAllDDRowVars);\n\t\t\t}\n\t\t}\n\n\t\tnewTransRewards = new JDDNode[transRewards.length];\n\t\tfor (i=0; i < transRewards.length; i++) {\n\t\t\tnewTransRewards[i] = transformation.getTransformedTransReward(transRewards[i]);\n\n\t\t\tif (SanityJDD.enabled) {\n\t\t\t\tSanityJDD.checkIsDDOverVars(newTransRewards[i], newAllDDRowVars, newAllDDColVars);\n\t\t\t}\n\t\t}\n\n\n\t\t// Create a new model model object to store the transformed model\n\t\tProbModel result = new ProbModel(\n\t\t\t\t// New transition matrix/start state\n\t\t\t\tnewTrans, newStart,\n\t\t\t\t// New list of all row/col vars\n\t\t\t\tnewAllDDRowVars, newAllDDColVars,\n\t\t\t\t// New model variables\n\t\t\t\tnewModelVariables,\n\t\t\t\t// New var info\n\t\t\t\tnewVarList, newVarDDRowVars, newVarDDColVars);\n\t\t// New reward information\n\t\tresult.setRewards(newStateRewards, newTransRewards, this.rewardStructNames.clone());\n\t\t// Constants (no change)\n\t\tresult.setConstantValues(this.getConstantValues());\n\n\t\t// Do reachability/etc. for the new model\n\t\tJDDNode S;\n\t\tif ( (S = transformation.getReachableStates()) != null) {\n\t\t\t// the transformation operator knows the reachable state set\n\t\t\tresult.setReach(S);\n\t\t} else if ( (S = transformation.getReachableStateSeed()) != null ) {\n\t\t\t// the transformation operator knows a seed for the reachability computation\n\t\t\tresult.doReachability(S);\n\t\t} else {\n\t\t\t// otherwise: do standard reachability\n\t\t\tresult.doReachability();\n\t\t}\n\t\tresult.filterReachableStates();\n\n\t\tif (!transformation.deadlocksAreFine()) {\n\t\t\tresult.findDeadlocks(false);\n\t\t\tif (result.getDeadlockStates().size() > 0) {\n\t\t\t\t// Assuming original model has no deadlocks, neither should the transformed model\n\t\t\t\tthrow new PrismException(\"Transformed model has deadlock states\");\n\t\t\t}\n\t\t}\n\n\t\t// lift labels attached to the model\n\t\tfor (Map.Entry<String, JDDNode> entry : labelsDD.entrySet()) {\n\t\t\tJDDNode labelStates = entry.getValue();\n\t\t\tJDDNode transformedLabelStates = transformation.getTransformedLabelStates(labelStates, result.getReach());\n\t\t\tresult.labelsDD.put(entry.getKey(), transformedLabelStates);\n\t\t}\n\n\t\textraDDRowVars.derefAll();\n\t\textraDDColVars.derefAll();\n\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/ProbModelTransformationOperator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2015-\n//\tAuthors:\n//\t* Joachim Klein <klein@tcs.inf.tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismException;\nimport symbolic.model.ProbModel;\n\n/**\n * Description of a transformation operation for a ProbModel (DTMC/CTMC).\n * The transformation can request the allocation of extra state variables,\n * and specify new transition matrix, initial states and reward information.\n * <br>\n * After use, the transformation should be cleared by calling {@code clear()}.\n * <br>\n * Use ProbModel.getTransformed() to obtain a transformed model.\n */\npublic abstract class ProbModelTransformationOperator\n{\n\t/** The original model */\n\tprotected ProbModel originalModel;\n\t/** The extra state variables (rows) */\n\tprotected JDDVars extraRowVars;\n\t/** The extra state variables (columns) */\n\tprotected JDDVars extraColVars;\n\n\t/**\n\t * Constructor with the original model that is to be transformed.\n\t * The original model is not changed and will not be cleared when\n\t * {@code clear()} is called.\n \t */\n\tpublic ProbModelTransformationOperator(ProbModel model)\n\t{\n\t\toriginalModel = model;\n\t}\n\n\t/**\n\t * Clear the transformation.\n\t */\n\tpublic void clear()\n\t{\n\t\tif (extraRowVars != null) {\n\t\t\textraRowVars.derefAll();\n\t\t}\n\t\tif (extraColVars != null) {\n\t\t\textraColVars.derefAll();\n\t\t}\n\t}\n\n\t/**\n\t * Return the name (prefix) to use for any new extra state variables.\n\t * Default implementation: Return \"extra\".\n\t */\n\tpublic String getExtraStateVariableName()\n\t{\n\t\treturn \"extra\";\n\t}\n\n\t/**\n\t * Get the number of extra state variables needed for this transformation.\n\t * This is the number n of state variables and will lead to the allocation of\n\t * 2*n variables, n row and n column variables (interleaved).\n\t */\n\tpublic abstract int getExtraStateVariableCount();\n\n\t/**\n\t * This method is called to notify the transformation operator\n\t * about the state variables that were allocated.\n\t * <br>\n\t * The extraRowVars and extraColVars are copies, i.e., this method is responsible\n\t * to ensure that they will be derefed eventually.\n\t * <br>\n\t * Default implementation: Store in extraRowVars and extraColVars fields.\n\t * <br>[ STORES: extraRowVars, extraColVars ]\n\t */\n\tpublic void hookExtraStateVariableAllocation(JDDVars extraRowVars, JDDVars extraColVars)\n\t{\n\t\tthis.extraRowVars = extraRowVars;\n\t\tthis.extraColVars = extraColVars;\n\t}\n\n\t/**\n\t * Get the transformed transition function.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic abstract\tJDDNode getTransformedTrans();\n\n\t/**\n\t * Get the transformed start function.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic abstract JDDNode getTransformedStart();\n\n\t/**\n\t * Get the transformed state reward relation, given the old reward relation.\n\t * <br>\n\t * Default implementation: Return the old reward relation, unchanged.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getTransformedStateReward(JDDNode oldReward)\n\t{\n\t\treturn oldReward.copy();\n\t}\n\n\t/**\n\t * Get the transformed transition reward relation, given the old reward relation.\n\t * <br>\n\t * Default implementation: Return the old reward relation, unchanged.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getTransformedTransReward(JDDNode oldReward)\n\t{\n\t\treturn oldReward.copy();\n\t}\n\n\t/**\n\t * Get the transformed (lifted) state set corresponding to a label in the original model.\n\t * As a convenience, the reachable states in the transformed model are provided as well.\n\t * <br>\n\t * Default implementation: Return the old state set, i.e.,\n\t * assume don't cares for the extra state variables.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getTransformedLabelStates(JDDNode oldLabelStates, JDDNode transformedReach)\n\t{\n\t\treturn oldLabelStates.copy();\n\t}\n\n\t/**\n\t * Directly provide the set of reachable states in the transformed model (optional).\n\t * If the set of reachable states is not known, this function should return {@code null}\n\t * and normal reachability computations will be performed.\n\t * <br/>\n\t * Default implementation: return {@code null}\n\t * <br>[ REFS: <i>result</i> ]\n\t */\n\tpublic JDDNode getReachableStates() throws PrismException\n\t{\n\t\treturn null;\n\t}\n\n\t/**\n\t * Provide a set of states in the transformed model that is known to be reachable,\n\t * which is then used as a seed in the subsequent reachability computation (speed-up).\n\t * <br>\n\t * If this transformation operator does not want to provide this information,\n\t * this function should return {@code null} and normal reachability computations\n\t * will be performed (from the start states).\n\t * <br/>\n\t * Default implementation: return {@code null}\n\t * <br>[ REFS: <i>result</i> ]\n\t */\n\tpublic JDDNode getReachableStateSeed() throws PrismException {\n\t\treturn null;\n\t}\n\n\t/**\n\t * If true, this transformation may produce deadlock states and the normal\n\t * deadlock check should not be invoked for the transformed model.\n\t * <br>\n\t * Default implementation: return {@code false}\n\t */\n\tpublic boolean deadlocksAreFine()\n\t{\n\t\treturn false;\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/Product.java",
    "content": "package symbolic.model;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.PrismException;\nimport symbolic.states.StateValues;\n\n/**\n * Base class for the results of a product operation between a symbolic model and\n * an automaton. Provides infrastructure for converting information on the\n * states between the original model, the automaton and the product model.\n *\n * @param <M> The type of the product model, e.g, DTMC, MDP, ...\n */\npublic class Product<M extends Model> implements ModelTransformation<M, M>\n{\n\tprotected M originalModel = null;\n\tprotected M productModel = null;\n\tprotected JDDNode productStatesOfInterest = null;\n\tprotected JDDVars automatonRowVars = null;\n\n\t/**\n\t * Constructor.\n\t * <br>\n\t * Takes ownership of productModel, productStatesOfInterest and automatonRowVars,\n\t * clears those when clear() is called.\n\t * <br>[ STORES: productModel, productStatesOfInterest, automatonRowVars ]\n \t * @param productModel the product model\n \t * @param originalModel the original model\n \t * @param productStatesOfInterest the statesOfInterest in the product (starting points of the product construction)\n \t * @param automatonRowVars the DD row vars of the automaton\n\t */\n\tpublic Product(M productModel, M originalModel, JDDNode productStatesOfInterest, JDDVars automatonRowVars) {\n\t\tthis.originalModel = originalModel;\n\t\tthis.productModel = productModel;\n\t\tthis.productStatesOfInterest = productStatesOfInterest;\n\t\tthis.automatonRowVars = automatonRowVars;\n\t}\n\n\t/**\n\t * Get the product model (not a copy).\n\t */\n\tpublic M getProductModel()\n\t{\n\t\treturn productModel;\n\t}\n\n\t@Override\n\tpublic M getTransformedModel()\n\t{\n\t\treturn getProductModel();\n\t}\n\n\t@Override\n\tpublic M getOriginalModel()\n\t{\n\t\treturn originalModel;\n\t}\n\n\t/**\n\t * Provides access to the row variables of the automaton part of the product.\n\t * <br>[ REFS: <i>none</i>, DEREFS: <i>none</i> ]\n\t */\n\tpublic JDDVars getAutomatonRowVars() {\n\t\treturn automatonRowVars;\n\t}\n\n\t/** Clear the product model and the other JDD references */\n\tpublic void clear() {\n\t\tif (productModel != null) productModel.clear();\n\t\tif (productStatesOfInterest != null) JDD.Deref(productStatesOfInterest);\n\t\tif (automatonRowVars != null) automatonRowVars.derefAll();\n\t}\n\n\t/**\n\t * Project state values from the product model back to the original model. Clears svTransformed.\n\t * <br>\n\t * Note: This assumes that the product construction results in each state of interest\n\t * in the original model having a unique corresponding state in the product,\n\t * provided by productStatesOfInterest.\n\t * @param svTransformed the state values in the product model\n\t * @return the corresponding state values in the original model\n\t */\n\t@Override\n\tpublic StateValues projectToOriginalModel(StateValues svTransformed) throws PrismException\n\t{\n\t\t// Filter against the productStatesOfInterest, i.e.,\n\t\t// set values to 0 for all states that do not correspond to the states of interest\n\t\tsvTransformed.filter(productStatesOfInterest);\n\t\t// Then sum over the DD vars introduced for the automata modes to\n\t\t// get StateValues in the original model\n\t\tStateValues svOriginal = svTransformed.sumOverDDVars(automatonRowVars, originalModel);\n\n\t\tsvTransformed.clear();\n\t\treturn svOriginal;\n\t}\n\n\t@Override\n\tpublic JDDNode getTransformedStatesOfInterest()\n\t{\n\t\treturn productStatesOfInterest.copy();\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/model/StochModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.model;\n\nimport jdd.JDD;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport parser.Values;\nimport parser.VarList;\nimport prism.ModelType;\nimport prism.PrismException;\nimport prism.PrismLog;\n\nimport java.util.Map.Entry;\n\n/**\n * Class for symbolic (BDD-based) representation of a CTMC.\n */\npublic class StochModel extends ProbModel\n{\n\t// Constructor\n\n\tpublic StochModel(JDDNode trans, JDDNode start, JDDVars allDDRowVars, JDDVars allDDColVars, ModelVariablesDD modelVariables,\n\t\t\t\t\t  VarList varList, JDDVars[] varDDRowVars, JDDVars[] varDDColVars)\n\t{\n\t\tsuper(trans, start, allDDRowVars, allDDColVars, modelVariables, varList, varDDRowVars, varDDColVars);\n\t}\n\n\t// Accessors (for Model)\n\n\tpublic ModelType getModelType()\n\t{\n\t\treturn ModelType.CTMC;\n\t}\n\n\tpublic String getTransName()\n\t{\n\t\treturn \"Rate matrix\";\n\t}\n\n\tpublic String getTransSymbol()\n\t{\n\t\treturn \"R\";\n\t}\n\n\t// Accessors (for CTMCs)\n\n\t/**\n\t * Get the embedded DTMC for this CTMC.\n\t * <br>\n\t * If parameter {@code log} is non-{@code null}, print some statistics.\n\t * <br>\n\t * If parameter {@code convertRewards} is {@code true}, transforms the rewards as well,\n\t * otherwise the reward structures are stripped.\n\t * <br>[ REFS: <i>result</i>, DEREFS: <i>nothing</i> ]\n\t * @param log the log for printing statistics (may be {@code null})\n\t * @param convertRewards if true, rewards are transformed, otherwise they are stripped\n\t * @return the embedded DTMC\n\t */\n\tpublic ProbModel getEmbeddedDTMC(PrismLog log, boolean convertRewards) throws PrismException\n\t{\n\t\t// Compute embedded Markov chain\n\t\tJDDNode diags = JDD.SumAbstract(trans.copy(), allDDColVars);\n\t\tJDDNode embeddedTrans = JDD.Apply(JDD.DIVIDE, trans.copy(), diags.copy());\n\t\tlog.println(\"\\nDiagonals vector: \" + JDD.GetInfoString(diags, allDDRowVars.n()));\n\t\tlog.println(\"Embedded Markov chain: \" + JDD.GetInfoString(embeddedTrans, allDDRowVars.n() * 2));\n\n\t\t// Convert rewards\n\t\tJDDNode[] embStateRewards;\n\t\tJDDNode[] embTransRewards;\n\t\tString[] embRewardStructNames;\n\t\tif (convertRewards) {\n\t\t\tembStateRewards = new JDDNode[stateRewards.length];\n\t\t\tembTransRewards = new JDDNode[stateRewards.length];\n\t\t\tembRewardStructNames = rewardStructNames.clone();\n\t\t\tfor (int i = 0; i < stateRewards.length; i++) {\n\t\t\t\t// state rewards are scaled\n\t\t\t\tembStateRewards[i] = JDD.Apply(JDD.DIVIDE, stateRewards[i].copy(), diags.copy());\n\t\t\t\t// trans rewards are simply copied\n\t\t\t\tembTransRewards[i] = transRewards[i].copy();\n\t\t\t}\n\t\t} else {\n\t\t\t// strip reward information\n\t\t\tembStateRewards = new JDDNode[0];\n\t\t\tembTransRewards = new JDDNode[0];\n\t\t\tembRewardStructNames = new String[0];\n\t\t}\n\n\t\tJDD.Deref(diags);\n\n\t\tProbModel result = new ProbModel(embeddedTrans,\n\t\t                                 start.copy(),\n\t\t                                 allDDRowVars.copy(),\n\t\t                                 allDDColVars.copy(),\n\t\t                                 modelVariables.copy(),\n\t\t                                 varList, // pass by reference, will not be changed\n\t\t                                 JDDVars.copyArray(varDDRowVars),\n\t\t                                 JDDVars.copyArray(varDDColVars)\n\t\t                                );\n\t\tresult.setRewards(embStateRewards, embTransRewards, embRewardStructNames);\n\t\t// Constants (no change)\n\t\tresult.setConstantValues(constantValues);\n\n\t\t// set reachable states to be the same as for the CTMC\n\t\tresult.setReach(getReach().copy());\n\n\t\t// copy labels\n\t\tfor (Entry<String, JDDNode> label : labelsDD.entrySet()) {\n\t\t\tresult.addLabelDD(label.getKey(), label.getValue().copy());\n\t\t}\n\n\t\treturn result;\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/states/StateList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.states;\n\nimport java.util.List;\n\nimport jdd.*;\nimport parser.State;\nimport parser.Values;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\n\n/**\n * Interface for classes that store a list of states.\n */\npublic interface StateList\n{\n\t/**\n\t * Get the number of states in the list.\n\t */\n\tint size();\n\t\n\t/**\n\t * Get the number of states in the list as a string\n\t * (useful when the number is too big to fit in an integer).\n\t */\n\tString sizeString();\n\t\n\t/**\n\t * Print the states to a log.\n\t */\n\tvoid print(PrismLog log);\n\t\n\t/**\n\t * Print the first {@code n} states in the list to a log.\n\t */\n\tvoid print(PrismLog log, int n);\n\t\n\t/**\n\t * Print the states to a log, in Matlab format.\n\t */\n\tvoid printMatlab(PrismLog log);\n\t\n\t/**\n\t * Print the first {@code n} states in the list to a log, in Matlab format.\n\t */\n\tvoid printMatlab(PrismLog log, int n);\n\n\t/**\n\t * Print the states to a log, in Dot format.\n\t */\n\tvoid printDot(PrismLog log) throws PrismException;\n\n\t/**\n\t * Format the list of states as a list of strings.\n\t */\n\tpublic List<String> exportToStringList();\n\t\n\t/**\n\t * Check whether a set of states, specified as a BDD, is *partially* included in this list,\n\t * i.e. whether there is any intersection between the two sets. \n\t */\n\tboolean includes(JDDNode set);\n\t\n\t/**\n\t * Check whether a set of states, specified as a BDD, is *fully* included in this list,\n\t * i.e. whether every state in {@code set} is in this list. \n\t */\n\tboolean includesAll(JDDNode set);\n\t\n\t/**\n\t * Get the first state in this list, as a {@link parser.Values} object.\n\t */\n\tValues getFirstAsValues() throws PrismException;\n\t\n\t/**\n\t * Get the index of a state in the list, specified as a State object.\n\t * Returns -1 if the state is not on the list or there is a problem with the lookup. \n\t */\n\tint getIndexOfState(State state) throws PrismNotSupportedException;\n\n\t/**\n\t * Free any memory associated with storing this list of states.\n\t */\n\tvoid clear();\n}\n"
  },
  {
    "path": "prism/src/symbolic/states/StateListMTBDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.states;\n\nimport java.util.*;\nimport java.util.function.Consumer;\n\nimport jdd.*;\nimport odd.*;\nimport parser.State;\nimport parser.Values;\nimport parser.VarList;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport symbolic.model.Model;\n\n/**\n * Stores a list of states as a BDD (or as a 0-1 MTBDD).\n */\npublic class StateListMTBDD implements StateList\n{\n\t// States list, as a (0-1) MTBDD\n\tprotected JDDNode states;\n\t\n\t// Info needed from model\n\tprotected JDDVars vars;\n\tprotected int numVars;\n\tprotected ODDNode odd;\n\tprotected VarList varList;\n\tprotected double size;\n\t\n\t// stuff to keep track of variable values in print method\n\tprotected int[] varSizes;\n\tprotected int[] varValues;\n\tprotected int currentVar;\n\tprotected int currentVarLevel;\n\t\n\t// stuff to control printing limit\n\tprotected boolean limit;\n\tprotected int numToPrint;\n\tprotected int count;\n\t\n\t// log for output from print method\n\tprotected PrismLog outputLog;\n\t\n\t// string array when exporting\n\tprotected List<String> strList;\n\t\n\t// output format\n\tprotected enum OutputFormat { NORMAL, MATLAB, DOT, STRINGS };\n\tprotected OutputFormat outputFormat = OutputFormat.NORMAL;\n\t\n\t// Constructors\n\n\t/**\n\t * Create a states list from a BDD and the associated model.\n\t * @param states The list of states\n\t * @param model The model\n\t */\n\tpublic StateListMTBDD(JDDNode states, Model model)\n\t{\n\t\tint i;\n\t\t\n\t\t// store states list bdd\n\t\tthis.states = states;\n\t\t\n\t\t// get info from model\n\t\tvars = model.getAllDDRowVars();\n\t\tnumVars = vars.n();\n\t\todd = model.getODD();\n\t\tvarList = model.getVarList();\n\t\t\n\t\t// count number of states in list\n\t\tsize = JDD.GetNumMinterms(states, model.getNumDDRowVars());\n\t\t\n\t\t// initialise arrays\n\t\tvarSizes = new int[varList.getNumVars()];\n\t\tfor (i = 0; i < varList.getNumVars(); i++) {\n\t\t\tvarSizes[i] = varList.getRangeLogTwo(i);\n\t\t}\n\t\tvarValues = new int[varList.getNumVars()];\n\t}\n\n\t/**\n\t * Create a states list from a BDD and the associated info about variables/indexing.\n\t * @param states The list of states\n\t * @param vars BDD variables used to represent states\n\t * @param odd ODD storing state indexing info\n\t * @param varList Information about (language-level) variables\n\t */\n\tpublic StateListMTBDD(JDDNode states, JDDVars vars, ODDNode odd, VarList varList)\n\t{\n\t\tint i;\n\n\t\t// store states vector mtbdd\n\t\tthis.states = states;\n\n\t\t// store variable/indexing info\n\t\tthis.vars = vars;\n\t\tthis.numVars = vars.n();\n\t\tthis.odd = odd;\n\t\tthis.varList = varList;\n\n\t\t// count number of states in list\n\t\tsize = JDD.GetNumMinterms(states, numVars);\n\n\t\t// initialise arrays\n\t\tvarSizes = new int[varList.getNumVars()];\n\t\tfor (i = 0; i < varList.getNumVars(); i++) {\n\t\t\tvarSizes[i] = varList.getRangeLogTwo(i);\n\t\t}\n\t\tvarValues = new int[varList.getNumVars()];\n\t}\n\n\t@Override\n\tpublic int size()\n\t{\n\t\treturn (size > Integer.MAX_VALUE) ? -1 : (int)Math.round(size);\n\t}\n\t\n\t@Override\n\tpublic String sizeString()\n\t{\n\t\treturn (size > Long.MAX_VALUE) ? \"\" + size : \"\" + Math.round(size);\n\t}\n\n\t@Override\n\tpublic void print(PrismLog log)\n\t{\n\t\toutputFormat = OutputFormat.NORMAL;\n\t\tlimit = false;\n\t\toutputLog = log;\n\t\tdoPrint();\n\t\tif (count == 0)\n\t\t\toutputLog.println(\"(none)\");\n\t}\n\t\n\t@Override\n\tpublic void print(PrismLog log, int n)\n\t{\n\t\toutputFormat = OutputFormat.NORMAL;\n\t\tlimit = true;\n\t\tnumToPrint = n;\n\t\toutputLog = log;\n\t\tdoPrint();\n\t\tif (count == 0)\n\t\t\toutputLog.println(\"(none)\");\n\t}\n\t\n\t@Override\n\tpublic void printMatlab(PrismLog log)\n\t{\n\t\toutputFormat = OutputFormat.MATLAB;\n\t\tlimit = false;\n\t\toutputLog = log;\n\t\tdoPrint();\n\t}\n\t\n\t@Override\n\tpublic void printMatlab(PrismLog log, int n)\n\t{\n\t\toutputFormat = OutputFormat.MATLAB;\n\t\tlimit = true;\n\t\tnumToPrint = n;\n\t\toutputLog = log;\n\t\tdoPrint();\n\t}\n\t\n\t@Override\n\tpublic void printDot(PrismLog log) throws PrismException\n\t{\n\t\toutputFormat = OutputFormat.DOT;\n\t\tlimit = false;\n\t\toutputLog = log;\n\n\t\tif (odd == null) {\n\t\t\tthrow new PrismNotSupportedException(\"Cannot export state list as DOT, too many states\");\n\t\t}\n\t\tdoPrint();\n\t}\n\t\n\t@Override\n\tpublic List<String> exportToStringList()\n\t{\n\t\tstrList = new ArrayList<String>((int)size);\n\t\toutputFormat = OutputFormat.STRINGS;\n\t\tlimit = false;\n\t\tdoPrint();\n\t\treturn strList;\n\t}\n\t\n\t/**\n\t * Implementation of printing.\n\t */\n\tprivate void doPrint()\n\t{\n\t\tint i;\n\t\t\n\t\tcount = 0;\n\t\tfor (i = 0; i < varList.getNumVars(); i++) {\n\t\t\tvarValues[i] = 0;\n\t\t}\n\t\tcurrentVar = 0;\n\t\tcurrentVarLevel = 0;\n\t\tprintRec(states, 0, odd, 0);\n\t\t//log.println();\n\t}\n\n\t/**\n\t * Main recursive part of state printing.\n\t * NB: Traversal of the MTBDD/ODD is quite simple; the  tricky bit is keeping track of variable values\n\t * throughout traversal - we want to be efficient and not compute the values from scratch each\n\t * time, but we also want to avoid passing arrays into the recursive method.\n\t */\n\tprivate void printRec(JDDNode dd, int level, ODDNode o, long n)\n\t{\n\t\tint i, j;\n\t\tJDDNode e, t;\n\t\tString varsString;\n\t\t\n\t\t// if we've printed enough states, stop\n\t\tif (limit) if (count >= numToPrint) return;\n\t\t\n\t\t// zero constant - bottom out of recursion\n\t\tif (dd.equals(JDD.ZERO)) return;\n\t\t\n\t\t// base case - at bottom (nonzero terminal)\n\t\tif (level == numVars) {\n\t\t\t\n\t\t\tswitch (outputFormat) {\n\t\t\tcase NORMAL:\n\t\t\t\tif (o != null) {\n\t\t\t\t\toutputLog.print(n + \":(\");\n\t\t\t\t} else {\n\t\t\t\t\t// we have no index\n\t\t\t\t\toutputLog.print(\"(\");\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase MATLAB: break;\n\t\t\tcase DOT:\n\t\t\t\tassert(o != null);  // should not happen, missing ODD is caught before\n\t\t\t\toutputLog.print(n + \" [label=\\\"\" + n + \"\\\\n(\");\n\t\t\t\tbreak;\n\t\t\tcase STRINGS: break;\n\t\t\t}\n\t\t\tj = varList.getNumVars();\n\t\t\tvarsString = \"\";\n\t\t\tfor (i = 0; i < j; i++) {\n\t\t\t\tvarsString += varList.decodeFromInt(i, varValues[i]).toString();\n\t\t\t\tif (i < j-1) {\n\t\t\t\t\tvarsString += \",\";\n\t\t\t\t}\n\t\t\t}\n\t\t\tswitch (outputFormat) {\n\t\t\tcase NORMAL: outputLog.println(varsString + \")\"); break;\n\t\t\tcase MATLAB: outputLog.println(varsString); break;\n\t\t\tcase DOT: outputLog.println(varsString + \")\\\"];\"); break;\n\t\t\tcase STRINGS: strList.add(varsString);\n\t\t\t}\n\t\t\tcount++;\n\t\t\t\n\t\t\treturn;\n\t\t}\n\t\t\n\t\t// select else and then branches\n\t\telse if (dd.getIndex() > vars.getVarIndex(level)) {\n\t\t\te = t = dd;\n\t\t}\n\t\telse {\n\t\t\te = dd.getElse();\n\t\t\tt = dd.getThen();\n\t\t}\n\n\t\tODDNode oe = (o != null ? o.getElse() : null);\n\t\tODDNode ot = (o != null ? o.getThen() : null);\n\t\tlong eoff = (o != null ? o.getEOff() : 0);\n\n\t\t// then recurse...\n\t\tcurrentVarLevel++; if (currentVarLevel == varSizes[currentVar]) { currentVar++; currentVarLevel=0; }\n\t\tprintRec(e, level+1, oe, n);\n\t\tcurrentVarLevel--; if (currentVarLevel == -1) { currentVar--; currentVarLevel=varSizes[currentVar]-1; }\n\t\tvarValues[currentVar] += (1 << (varSizes[currentVar]-1-currentVarLevel));\n\t\tcurrentVarLevel++; if (currentVarLevel == varSizes[currentVar]) { currentVar++; currentVarLevel=0; }\n\t\tprintRec(t, level+1, ot, n + eoff);\n\t\tcurrentVarLevel--; if (currentVarLevel == -1) { currentVar--; currentVarLevel=varSizes[currentVar]-1; }\n\t\tvarValues[currentVar] -= (1 << (varSizes[currentVar]-1-currentVarLevel));\n\t}\n\n\t@Override\n\tpublic boolean includes(JDDNode set)\n\t{\n\t\tJDDNode tmp;\n\t\tboolean incl;\n\t\t\n\t\tJDD.Ref(states);\n\t\tJDD.Ref(set);\n\t\ttmp = JDD.And(states, set);\n\t\tincl = !tmp.equals(JDD.ZERO);\n\t\tJDD.Deref(tmp);\n\t\t\n\t\treturn incl;\t\n\t}\n\n\t@Override\n\tpublic boolean includesAll(JDDNode set)\n\t{\n\t\tJDDNode tmp;\n\t\tboolean incl;\n\t\t\n\t\tJDD.Ref(states);\n\t\tJDD.Ref(set);\n\t\ttmp = JDD.And(states, set);\n\t\tincl = tmp.equals(set);\n\t\tJDD.Deref(tmp);\n\t\t\n\t\treturn incl;\t\n\t}\n\n\t@Override\n\tpublic Values getFirstAsValues() throws PrismException\n\t{\n\t\tValues values;\n\t\tint i, j, n, n2, level, v;\n\t\tJDDNode first, tmp;\n\t\tObject o;\n\t\t\n\t\t// check there is a first state\n\t\tif (size < 1) throw new PrismException(\"The state list contains no states\");\n\t\t\n\t\t// get bdd of first state\n\t\tJDD.Ref(states);\n\t\tfirst = JDD.RestrictToFirst(states, vars);\n\t\t\n\t\t// traverse bdd, top to bottom, getting val (v) for each var\n\t\ttmp = states;\n\t\tvalues = new Values();\n\t\tn = varList.getNumVars();\n\t\tlevel = 0;\n\t\tfor (i = 0; i < n; i++) {\n\t\t\tv = 0;\n\t\t\tn2 = varSizes[i];\n\t\t\tfor (j = 0; j < n2; j++) {\n\t\t\t\tif (tmp.getIndex() > vars.getVarIndex(level)) {\n\t\t\t\t\t// tmp = tmp;\n\t\t\t\t} else if (!tmp.getElse().equals(JDD.ZERO)) {\n\t\t\t\t\ttmp = tmp.getElse();\n\t\t\t\t} else {\n\t\t\t\t\ttmp = tmp.getThen();\n\t\t\t\t\tv += (1 << (n2-1-j));\n\t\t\t\t}\n\t\t\t\tlevel++;\n\t\t\t}\n\t\t\to = varList.decodeFromInt(i, v);\n\t\t\tvalues.addValue(varList.getName(i), o);\n\t\t}\n\t\t\n\t\t// derefs\n\t\tJDD.Deref(first);\n\t\t\n\t\treturn values;\n\t}\n\n\t/**\n\t * Convert this state list to a {@link List} of {@link State} objects.\n\t */\n\tpublic List<State> getAsListOfStates()\n\t{\n\t\tList<State> list = new ArrayList<>();\n\t\t// Initialise variable info storage for recursion\n\t\tfor (int i = 0; i < varList.getNumVars(); i++) {\n\t\t\tvarValues[i] = 0;\n\t\t}\n\t\tcurrentVar = 0;\n\t\tcurrentVarLevel = 0;\n\t\t// Traverse BDD to extract states\n\t\tgetAsListOfStatesRec(states, 0, odd, 0, list::add);\n\t\treturn list;\n\t}\n\n\t/**\n\t * Recursive helper for {@link #getAsListOfStates()}.\n\t * @param dd The BDD\n\t * @param level Level of recursion\n\t * @param o The ODD\n\t * @param n State index counter\n\t * @param consumer Consumer to accept states\n\t */\n\tprivate void getAsListOfStatesRec(JDDNode dd, int level, ODDNode o, long n, Consumer<State> consumer)\n\t{\n\t\t// Base case: zero terminal\n\t\tif (dd.equals(JDD.ZERO)) {\n\t\t\treturn;\n\t\t}\n\t\t// Base case: non-zero terminal\n\t\tif (level == numVars) {\n\t\t\tint numVars = varList.getNumVars();\n\t\t\tState state = new State(numVars);\n\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\tstate.setValue(i, varList.decodeFromInt(i, varValues[i]));\n\t\t\t}\n\t\t\tconsumer.accept(state);\n\t\t\treturn;\n\t\t}\n\t\t// Recurse\n\t\tJDDNode e, t;\n\t\tif (dd.getIndex() > vars.getVarIndex(level)) {\n\t\t\te = t = dd;\n\t\t}\n\t\telse {\n\t\t\te = dd.getElse();\n\t\t\tt = dd.getThen();\n\t\t}\n\t\tODDNode oe = (o != null ? o.getElse() : null);\n\t\tODDNode ot = (o != null ? o.getThen() : null);\n\t\tlong eoff = (o != null ? o.getEOff() : 0);\n\t\tcurrentVarLevel++; if (currentVarLevel == varSizes[currentVar]) { currentVar++; currentVarLevel = 0; }\n\t\tgetAsListOfStatesRec(e, level + 1, oe, n, consumer);\n\t\tcurrentVarLevel--; if (currentVarLevel == -1) { currentVar--; currentVarLevel = varSizes[currentVar] - 1; }\n\t\tvarValues[currentVar] += (1 << (varSizes[currentVar] - 1 - currentVarLevel));\n\t\tcurrentVarLevel++; if (currentVarLevel == varSizes[currentVar]) { currentVar++; currentVarLevel = 0; }\n\t\tgetAsListOfStatesRec(t, level + 1, ot, n + eoff, consumer);\n\t\tcurrentVarLevel--; if (currentVarLevel == -1) { currentVar--; currentVarLevel = varSizes[currentVar] - 1; }\n\t\tvarValues[currentVar] -= (1 << (varSizes[currentVar] - 1 - currentVarLevel));\n\t}\n\n\t@Override\n\tpublic int getIndexOfState(State state) throws PrismNotSupportedException\n\t{\n\t\t// Traverse BDD/ODD, top to bottom, computing index\n\t\tJDDNode ptr = states;\n\t\tODDNode o = odd;\n\n\t\tODDUtils.checkInt(odd, \"Cannot get index of state in model\");\n\n\t\tint level = 0;\n\t\tint index = 0;\n\t\t// Iterate through variables\n\t\tint n = varList.getNumVars();\n\t\tfor (int i = 0; i < n; i++) {\n\t\t\tint valInt = -1;\n\t\t\ttry {\n\t\t\t\tvalInt = varList.encodeToInt(i, state.varValues[i]); \n\t\t\t} catch (PrismLangException e) {\n\t\t\t\t// Problem looking up variable - bail out \n\t\t\t\treturn -1;\n\t\t\t}\n\t\t\t// Iterate through bits for this variable\n\t\t\tint n2 = varSizes[i];\n\t\t\tfor (int j = 0; j < n2; j++) {\n\t\t\t\t// Traverse BDD (need to double check state is in the set)\n\t\t\t\tif (ptr.equals(JDD.ZERO)) {\n\t\t\t\t\treturn -1;\n\t\t\t\t} else if (ptr.getIndex() > vars.getVarIndex(level)) {\n\t\t\t\t\t// ptr = ptr;\n\t\t\t\t} else if ((valInt & (1 << (n2-1-j))) == 0) {\n\t\t\t\t\tptr = ptr.getElse();\n\t\t\t\t} else {\n\t\t\t\t\tptr.getThen();\t\t\t\t\t\n\t\t\t\t}\n\t\t\t\tlevel++;\n\t\t\t\t// Traverse ODD (to get index)\n\t\t\t\tif ((valInt & (1 << (n2-1-j))) == 0) {\n\t\t\t\t\to = o.getElse();\n\t\t\t\t} else {\n\t\t\t\t\tindex += o.getEOff();\n\t\t\t\t\to = o.getThen();\t\n\t\t\t\t}\n\t\t\t\t\n\t\t\t}\n\t\t}\n\t\treturn index;\n\t}\n\t\n\t@Override\n\tpublic void clear()\n\t{\n\t\tJDD.Deref(states);\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/states/StateValues.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.states;\n\nimport java.io.File;\n\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport parser.ast.RelOp;\nimport prism.Accuracy;\nimport prism.Accuracy.AccuracyType;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.ResultTesting;\nimport prism.StateAndValueConsumer;\nimport prism.StateVector;\nimport symbolic.model.Model;\n\n/**\n * Interface for classes for state-indexed vectors of (integer or double) values\n */\npublic interface StateValues extends StateVector\n{\n\t/** Converts to StateValuesDV, destroys (clear) this vector */\n\tStateValuesDV convertToStateValuesDV() throws PrismException;\n\n\t/** Converts to StateValuesMTBDD, destroys (clear) this vector */\n\tStateValuesMTBDD convertToStateValuesMTBDD();\n\n\t/**\n\t * Switch the underlying model of this StateValues object.\n\t * The new model has to be compatible with the old one,\n\t * i.e., it has to have the same row variables and reachable states.\n\t * <br>\n\t * An example would be to switch between a CTMC and the embedded DTMC,\n\t * i.e., where both models by construction have the same structure and state space.\n\t * <br>\n\t * Note that there are currently <b>no sanity checks</b>, so be careful when\n\t * using this method.\n\t * @param newModel the new model\n\t */\n\tvoid switchModel(Model newModel);\n\n\t/**\n\t * Set the accuracy of the result.\n\t */\n\tvoid setAccuracy(Accuracy accuracy);\n\t\n\t/**\n\t * Set the elements of this vector by reading them in from a file.\n\t */\n\tvoid readFromFile(File file) throws PrismException;\n\n\t/** Round the values of this vector to the given number of decimal places. */\n\tvoid roundOff(int places);\n\n\t/** Subtract all values of this vector from 1 */\n\tvoid subtractFromOne();\n\n\t/**\n\t * Add the values of the other StateValues vector to the values of this vector.\n\t * <br>\n\t * The other StateValues vector has to have the same class as this vector.\n\t */\n\tvoid add(StateValues sp);\n\n\t/** Multiplies the values of this vector with the constant {@code d}. */\n\tvoid timesConstant(double d);\n\n\t/**\n\t * Compute dot (inner) product of this and another vector.\n\t * <br>\n\t * The other StateValues vector has to have the same class as this vector.\n\t */\n\tdouble dotProduct(StateValues sp);\n\n\t/**\n\t * Filter this vector using a BDD (set elements not in filter to 0).\n\t * <br>[ DEREFS: <i>none</i> ]\n\t */\n\tvoid filter(JDDNode filter);\n\n\t/**\n\t * Filter this vector using a BDD (set elements not in filter to constant {@code d}).\n\t * <br>[ DEREFS: <i>none</i> ]\n\t */\n\tvoid filter(JDDNode filter, double d);\n\n\t/**\n\t * Apply max operator, i.e. vec[i] = max(vec[i], vec2[i]), where vec2 is an MTBDD\n\t * <br>[ DEREFS: <i>none</i> ]\n\t */\n\tpublic void maxMTBDD(JDDNode vec2);\n\n\t/** Clear the stored information. */\n\tvoid clear();\n\n\t/** Get the number of non-zero values in this vector. */\n\tint getNNZ();\n\n\t/** Get the number of non-zero values in this vector as a String. */\n\tString getNNZString();\n\n\t/**\n\t * Get the value of the first vector element that is in the (BDD) filter.\n\t * <br>\n\t * Should be called with a non-empty filter. For an empty filter, will return\n\t * {@code Double.NaN}.\n\t * <br>[ DEREFS: <i>none</i> ]\n\t */\n\tdouble firstFromBDD(JDDNode filter);\n\n\t/**\n\t * Get the minimum value of those that are in the (BDD) filter.\n\t * <br>\n\t * If the filter is empty for this vector, returns positive infinity.\n\t * <br>[ DEREFS: <i>none</i> ]\n\t */\n\tdouble minOverBDD(JDDNode filter);\n\n\t/**\n\t * Get the maximum value of those that are in the (BDD) filter.\n\t * <br>\n\t * If the filter is empty for this vector, returns negative infinity.\n\t * <br>[ DEREFS: <i>none</i> ]\n\t */\n\tdouble maxOverBDD(JDDNode filter);\n\n\t/**\n\t * Get the maximum finite value of those that are in the (BDD) filter.\n\t * <br>\n\t * If the filter is empty for this vector or all values for the filter are non-finite,\n\t * returns negative infinity.\n\t * <br>[ DEREFS: <i>none</i> ]\n\t */\n\tpublic double maxFiniteOverBDD(JDDNode filter);\n\n\t/**\n\t * Get the sum of those elements that are in the (BDD) filter.\n\t * If the filter is empty for this vector, returns 0.\n \t * <br>[ DEREFS: <i>none</i> ]\n\t */\n\tdouble sumOverBDD(JDDNode filter);\n\n\t/**\n\t * Do a weighted sum of the elements of the vector and the values the MTBDD passed in\n\t * (used for CSL reward steady state operator).\n\t */\n\tdouble sumOverMTBDD(JDDNode mult);\n\n\t/**\n\t* Sum up the elements of the vector, over a subset of its DD vars,\n\t* store the result in a new StateValues (for newModel).\n\t* <br>[ DEREFS: <i>none</i> ]\n\t*/\n\tStateValues sumOverDDVars(JDDVars sumVars, Model newModel) throws PrismException;\n\n\t/** Returns an Object with the value of the i-th entry in this vector. */\n\tObject getValue(int i) throws PrismNotSupportedException;\n\n\t/**\n\t * Generate BDD for states in the given interval\n\t * (interval specified as relational operator and bound)\n\t * <br>[ REFS: <i>result</i> ]\n\t */\n\tJDDNode getBDDFromInterval(String relOpString, double bound);\n\n\t/**\n\t * Generate BDD for states in the given interval\n\t * (interval specified as relational operator and bound)\n\t * <br>[ REFS: <i>result</i> ]\n\t */\n\tJDDNode getBDDFromInterval(RelOp relOp, double bound);\n\n\t/**\n\t * Generate BDD for states in the given interval\n\t * (interval specified as inclusive lower/upper bound)\n\t * <br>[ REFS: <i>result</i> ]\n\t */\n\tJDDNode getBDDFromInterval(double lo, double hi);\n\n\t/**\n\t * Generate BDD for states whose value is close to 'value'\n\t * (if present, accuracy info used to determine closeness)\n\t * <br>[ REFS: <i>result</i> ]\n\t * @param val the value\n\t * @param epsilon the error bound\n\t * @param abs true for absolute error calculation\n\t */\n\tdefault JDDNode getBDDFromCloseValue(double val)\n\t{\n\t\tAccuracy accuracy = ResultTesting.getTestingAccuracy(getAccuracy());\n\t\treturn getBDDFromCloseValue(val, accuracy.getErrorBound(), accuracy.getType() == AccuracyType.ABSOLUTE);\n\t}\n\n\t/**\n\t * Generate BDD for states whose value is close to 'value'\n\t * (within either absolute or relative error 'epsilon')\n\t * <br>[ REFS: <i>result</i> ]\n\t * @param val the value\n\t * @param epsilon the error bound\n\t * @param abs true for absolute error calculation\n\t */\n\tJDDNode getBDDFromCloseValue(double val, double epsilon, boolean abs);\n\n\t/**\n\t * Generate BDD for states whose value is close to 'value'\n\t * (within absolute error 'epsilon')\n\t * <br>[ REFS: <i>result</i> ]\n\t * @param val the value\n\t * @param epsilon the error bound\n\t */\n\tJDDNode getBDDFromCloseValueAbs(double val, double epsilon);\n\n\t/**\n\t * Generate BDD for states whose value is close to 'value'\n\t * (within relative error 'epsilon')\n\t * <br>[ REFS: <i>result</i> ]\n\t * @param val the value\n\t * @param epsilon the error bound\n\t */\n\tJDDNode getBDDFromCloseValueRel(double val, double epsilon);\n\n\t/**\n\t * Get the accuracy of the result.\n\t */\n\tAccuracy getAccuracy();\n\t\n\t/**\n\t * Print vector to a log/file (non-zero entries only)\n\t */\n\tdefault void print(PrismLog log) throws PrismException\n\t{\n\t\tprint(log, true, false, true, true);\n\t}\n\n\t/**\n\t * Print vector to a log/file.\n\t * @param log The log\n\t * @param printSparse Print non-zero elements only?\n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print states (variable values) for each element?\n\t */\n\tdefault void print(PrismLog log, boolean printSparse, boolean printMatlab, boolean printStates) throws PrismException\n\t{\n\t\tprint(log, printSparse, printMatlab, printStates, true);\n\t}\n\n\t/**\n\t * Print vector to a log/file.\n\t * @param log The log\n\t * @param printSparse Print non-zero elements only?\n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print states (variable values) for each element?\n\t * @param printIndices Print state indices for each element?\n\t */\n\tvoid print(PrismLog log, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices) throws PrismException;\n\n\t/**\n\t * Print part of a vector to a log/file (non-zero entries only).\n\t * <br>[ DEREFS: <i>none</i> ]\n\t * @param log The log\n\t * @param filter A BDD specifying which states to print for.\n\t */\n\tdefault void printFiltered(PrismLog log, JDDNode filter) throws PrismException\n\t{\n\t\tprintFiltered(log, filter, true, false, true);\n\t}\n\n\t/**\n\t * Print part of a vector to a log/file (non-zero entries only).\n\t * <br>[ DEREFS: <i>none</i> ]\n\t * @param log The log\n\t * @param filter A BDD specifying which states to print for.\n\t * @param printSparse Print non-zero elements only?\n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print states (variable values) for each element?\n\t */\n\tdefault void printFiltered(PrismLog log, JDDNode filter, boolean printSparse, boolean printMatlab, boolean printStates) throws PrismException\n\t{\n\t\tprintFiltered(log, filter, printSparse, printMatlab, printStates, true);\n\t}\n\n\t/**\n\t * Print part of a vector to a log/file (non-zero entries only).\n\t * <br>[ DEREFS: <i>none</i> ]\n\t * @param log The log\n\t * @param filter A BDD specifying which states to print for.\n\t * @param printSparse Print non-zero elements only?\n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print states (variable values) for each element?\n\t * @param printIndices Print state indices for each element?\n\t */\n\tvoid printFiltered(PrismLog log, JDDNode filter, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices) throws PrismException;\n\n\t/**\n\t * Iterate over all state/value pairs\n\t * and call {@code consumer.accept()} for each.\n\t * @param consumer the consumer\n\t * @param sparse only call accept for non-zero values\n\t */\n\tvoid iterate(StateAndValueConsumer consumer, boolean sparse);\n\n\t/**\n\t * Iterate over all state/value pairs\n\t * where the state is included in the filter DD and\n\t * call {@code consumer.accept()} for each.\n\t * @param consumer the consumer\n\t * @param sparse only call accept for non-zero values\n\t */\n\tvoid iterateFiltered(JDDNode filter, StateAndValueConsumer consumer, boolean sparse);\n\n\t/**\n\t * Make a (deep) copy of this vector\n\t */\n\tStateValues deepCopy() throws PrismException; \n}\n"
  },
  {
    "path": "prism/src/symbolic/states/StateValuesDV.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.states;\n\nimport java.io.*;\n\nimport dv.*;\nimport jdd.*;\nimport odd.*;\nimport parser.VarList;\nimport parser.ast.RelOp;\nimport prism.Accuracy;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.StateAndValueConsumer;\nimport prism.StateAndValuePrinter;\nimport symbolic.model.Model;\n\n/**\n * Class for state-indexed vectors of (integer or double) values,\n * represented by a vector of doubles.\n */\npublic class StateValuesDV implements StateValues\n{\n\t/** Double vector storing values */\n\tDoubleVector values;\n\n\t/** Accuracy info */\n\tAccuracy accuracy;\n\t\n\t// info from model\n\t/** The underlying model */\n\tModel model;\n\t/** The BDD row variables of the underlying model */\n\tJDDVars vars;\n\t/** The number of BDD row variables in the underlying model */\n\tint numVars;\n\t/** The ODD for the reachable states of the underlying model */\n\tODDNode odd;\n\t/** The VarList of the underlying model*/\n\tVarList varList;\n\n\t// CONSTRUCTORS\n\n\t/**\n\t * Constructor from a double vector (which is stored, not copied).\n\t * @param values the double vector\n\t * @param model the underlying model\n\t */\n\tpublic StateValuesDV(DoubleVector values, Model model)\n\t{\n\t\tthis (values, model, null);\n\t}\n\n\t/**\n\t * Constructor from a double vector (which is stored, not copied).\n\t * Also set the accuracy info.\n\t * @param values the double vector\n\t * @param model the underlying model\n\t * @param accuracy result accuracy info\n\t */\n\tpublic StateValuesDV(DoubleVector values, Model model, Accuracy accuracy)\n\t{\n\t\t// store values vector and accuracy\n\t\tthis.values = values;\n\t\tsetAccuracy(accuracy);\n\t\t// get info from model\n\t\tsetModel(model);\n\t}\n\n\t/**\n\t * Constructor from an MTBDD.\n\t * <br>\n\t * Note: The JDDNode dd must only be non-zero for reachable states\n\t * (otherwise bad things happen)\n\t * <br>[ DEREFS: <i>none</i> ]\n\t * @param dd the double vector\n\t * @param model the underlying model\n\t */\n\tpublic StateValuesDV(JDDNode dd, Model model) throws PrismException\n\t{\n\t\t// TODO: Enforce/check that dd is zero for all non-reachable states\n\t\tthis(dd, model, null);\n\t}\n\n\t/**\n\t * Constructor from an MTBDD.\n\t * Also set the accuracy info.\n\t * <br>\n\t * Note: The JDDNode dd must only be non-zero for reachable states\n\t * (otherwise bad things happen)\n\t * <br>[ DEREFS: <i>none</i> ]\n\t * @param dd the double vector\n\t * @param model the underlying model\n\t * @param accuracy result accuracy info\n\t */\n\tpublic StateValuesDV(JDDNode dd, Model model, Accuracy accuracy) throws PrismException\n\t{\n\t\t// TODO: Enforce/check that dd is zero for all non-reachable states\n\t\tthis(new DoubleVector(dd, model.getAllDDRowVars(), model.getODD()), model, accuracy);\n\t}\n\n\t/** Helper method: Store information about the underlying model */\n\tprivate void setModel(Model model)\n\t{\n\t\tthis.model = model;\n\t\tvars = model.getAllDDRowVars();\n\t\tnumVars = vars.n();\n\t\todd = model.getODD();\n\t\tvarList = model.getVarList();\n\t}\n\n\t@Override\n\tpublic void switchModel(Model newModel)\n\t{\n\t\tsetModel(newModel);\n\t}\n\n\t@Override\n\tpublic void setAccuracy(Accuracy accuracy)\n\t{\n\t\tthis.accuracy = accuracy;\n\t}\n\t\n\t// CONVERSION METHODS\n\n\t@Override\n\tpublic StateValuesDV convertToStateValuesDV()\n\t{\n\t\t// convert to StateValuesDV (nothing to do)\n\t\treturn this;\n\t}\n\n\t@Override\n\tpublic StateValuesMTBDD convertToStateValuesMTBDD()\n\t{\n\t\t// convert to StateValuesMTBDD, destroy (clear) old vector\n\t\tStateValuesMTBDD res = new StateValuesMTBDD(values.convertToMTBDD(vars, odd), model, accuracy);\n\t\tclear();\n\t\treturn res;\n\t}\n\n\t// METHODS TO MODIFY VECTOR\n\n\t/**\n\t * Set element i of this vector to value d. \n\t */\n\tprivate void setElement(int i, double d)\n\t{\n\t\tvalues.setElement(i, d);\n\t}\n\n\t@Override\n\tpublic void readFromFile(File file) throws PrismException\n\t{\n\t\tBufferedReader in;\n\t\tString s;\n\t\tint lineNum = 0, count = 0;\n\t\tdouble d;\n\t\tboolean hasIndices = false;\n\t\tint size = values.getSize();\n\n\t\ttry {\n\t\t\t// Open file for reading\n\t\t\tin = new BufferedReader(new FileReader(file));\n\t\t\t// Read remaining lines\n\t\t\ts = in.readLine();\n\t\t\tlineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\ts = s.trim();\n\t\t\t\tif (!(\"\".equals(s))) {\n\t\t\t\t\t// If entry is of form \"i=x\", use i as index not count\n\t\t\t\t\t// (otherwise, assume line i contains value for state index i)\n\t\t\t\t\tif (s.contains(\"=\")) {\n\t\t\t\t\t\thasIndices = true;\n\t\t\t\t\t\tString ss[] = s.split(\"=\");\n\t\t\t\t\t\tcount = Integer.parseInt(ss[0]);\n\t\t\t\t\t\ts = ss[1];\n\t\t\t\t\t}\n\t\t\t\t\tif (count + 1 > size) {\n\t\t\t\t\t\tin.close();\n\t\t\t\t\t\tthrow new PrismException(\"Too many values in file \\\"\" + file + \"\\\" (more than \" + size + \")\");\n\t\t\t\t\t}\n\t\t\t\t\td = Double.parseDouble(s);\n\t\t\t\t\tsetElement(count, d);\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t\ts = in.readLine();\n\t\t\t\tlineNum++;\n\t\t\t}\n\t\t\t// Close file\n\t\t\tin.close();\n\t\t\t// Check size\n\t\t\tif (!hasIndices && count < size)\n\t\t\t\tthrow new PrismException(\"Too few values in file \\\"\" + file + \"\\\" (\" + count + \", not \" + size + \")\");\n\t\t} catch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t} catch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error detected at line \" + lineNum + \" of file \\\"\" + file + \"\\\"\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void roundOff(int places)\n\t{\n\t\tvalues.roundOff(places);\n\t}\n\n\t@Override\n\tpublic void subtractFromOne()\n\t{\n\t\tvalues.subtractFromOne();\n\t}\n\n\t@Override\n\tpublic void add(StateValues sp)\n\t{\n\t\tvalues.add(((StateValuesDV) sp).values);\n\t}\n\n\t@Override\n\tpublic void timesConstant(double d)\n\t{\n\t\tvalues.timesConstant(d);\n\t}\n\n\t@Override\n\tpublic double dotProduct(StateValues sv)\n\t{\n\t\treturn values.dotProduct(((StateValuesDV) sv).values);\n\t}\n\n\t@Override\n\tpublic void filter(JDDNode filter)\n\t{\n\t\tvalues.filter(filter, vars, odd);\n\t}\n\n\t@Override\n\tpublic void filter(JDDNode filter, double d)\n\t{\n\t\tvalues.filter(filter, d, vars, odd);\n\t}\n\n\t@Override\n\tpublic void maxMTBDD(JDDNode vec2)\n\t{\n\t\tvalues.maxMTBDD(vec2, vars, odd);\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\tvalues.clear();\n\t}\n\n\t// METHODS TO ACCESS VECTOR DATA\n\n\t@Override\n\tpublic int getSize()\n\t{\n\t\treturn values.getSize();\n\t}\n\t\n\t@Override\n\tpublic Object getValue(int i)\n\t{\n\t\t// TODO: cast to Integer or Double as required?\n\t\treturn values.getElement(i);\n\t}\n\n\t/** Get the underlying double vector of this StateValuesDV */\n\tpublic DoubleVector getDoubleVector()\n\t{\n\t\treturn values;\n\t}\n\n\t@Override\n\tpublic int getNNZ()\n\t{\n\t\treturn values.getNNZ();\n\t}\n\n\t@Override\n\tpublic String getNNZString()\n\t{\n\t\treturn \"\" + getNNZ();\n\t}\n\n\t// Filter operations\n\n\t@Override\n\tpublic double firstFromBDD(JDDNode filter)\n\t{\n\t\treturn values.firstFromBDD(filter, vars, odd);\n\t}\n\n\t@Override\n\tpublic double minOverBDD(JDDNode filter)\n\t{\n\t\treturn values.minOverBDD(filter, vars, odd);\n\t}\n\n\t@Override\n\tpublic double maxOverBDD(JDDNode filter)\n\t{\n\t\treturn values.maxOverBDD(filter, vars, odd);\n\t}\n\n\t@Override\n\tpublic double maxFiniteOverBDD(JDDNode filter)\n\t{\n\t\treturn values.maxFiniteOverBDD(filter, vars, odd);\n\t}\n\n\t@Override\n\tpublic double sumOverBDD(JDDNode filter)\n\t{\n\t\treturn values.sumOverBDD(filter, vars, odd);\n\t}\n\n\t@Override\n\tpublic double sumOverMTBDD(JDDNode mult)\n\t{\n\t\treturn values.sumOverMTBDD(mult, vars, odd);\n\t}\n\n\t@Override\n\tpublic StateValues sumOverDDVars(JDDVars sumVars, Model newModel) throws PrismException\n\t{\n\t\tDoubleVector tmp;\n\n\t\ttmp = values.sumOverDDVars(model.getAllDDRowVars(), odd, newModel.getODD(), sumVars.getMinVarIndex(), sumVars.getMaxVarIndex());\n\n\t\treturn (StateValues) new StateValuesDV(tmp, newModel);\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromInterval(String relOpString, double bound)\n\t{\n\t\treturn getBDDFromInterval(RelOp.parseSymbol(relOpString), bound);\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromInterval(RelOp relOp, double bound)\n\t{\n\t\treturn values.getBDDFromInterval(relOp, bound, vars, odd);\n\t}\n\n\t/**\n\t * \tGenerate BDD for states in the given interval\n\t * (interval specified as lower/upper bound)\n\t */\n\tpublic JDDNode getBDDFromInterval(double lo, double hi)\n\t{\n\t\treturn values.getBDDFromInterval(lo, hi, vars, odd);\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValue(double value, double epsilon, boolean abs)\n\t{\n\t\tif (abs)\n\t\t\treturn values.getBDDFromCloseValueAbs(value, epsilon, vars, odd);\n\t\telse\n\t\t\treturn values.getBDDFromCloseValueRel(value, epsilon, vars, odd);\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValueAbs(double value, double epsilon)\n\t{\n\t\treturn values.getBDDFromCloseValueAbs(value, epsilon, vars, odd);\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValueRel(double value, double epsilon)\n\t{\n\t\treturn values.getBDDFromCloseValueRel(value, epsilon, vars, odd);\n\t}\n\n\t@Override\n\tpublic Accuracy getAccuracy()\n\t{\n\t\treturn accuracy;\n\t}\n\t\n\t// PRINTING STUFF\n\n\t@Override\n\tpublic void print(PrismLog log, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices) throws PrismException\n\t{\n\t\t// header for matlab format\n\t\tif (printMatlab)\n\t\t\tlog.println(!printSparse ? \"v = [\" : \"v = sparse(\" + values.getSize() + \",1);\");\n\n\t\t// check if all zero\n\t\tif (printSparse && !printMatlab && values.getNNZ() == 0) {\n\t\t\tlog.println(\"(all zero)\");\n\t\t\treturn;\n\t\t}\n\n\t\t// set up and call recursive print\n\t\titerate(new StateAndValuePrinter(log, varList, printSparse, printMatlab, printStates, printIndices), printSparse);\n\n\t\t// footer for matlab format\n\t\tif (printMatlab && !printSparse)\n\t\t\tlog.println(\"];\");\n\t}\n\n\t/**\n\t * Print part of a vector to a log/file (non-zero entries only).\n\t * @param log The log\n\t * @param filter A BDD specifying which states to print for.\n\t * @param printSparse Print non-zero elements only? \n\t * @param printMatlab Print in Matlab format?\n\t * @param printStates Print states (variable values) for each element?\n\t * @param printIndizes Print indizes before states? \n\t */\n\tpublic void printFiltered(PrismLog log, JDDNode filter, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices)\n\t\t\tthrows PrismException\n\t{\n\t\t// header for matlab format\n\t\tif (printMatlab)\n\t\t\tlog.println(!printSparse ? \"v = [\" : \"v = sparse(\" + values.getSize() + \",1);\");\n\n\t\tStateAndValuePrinter printer = new StateAndValuePrinter(log, varList, printSparse, printMatlab, printStates, printIndices);\n\t\titerateFiltered(filter, printer, printSparse);\n\n\t\t// check if all zero\n\t\tif (printSparse && !printMatlab && !printer.hadOutput()) {\n\t\t\tlog.println(\"(all zero)\");\n\t\t\treturn;\n\t\t}\n\n\t\t// footer for matlab format\n\t\tif (printMatlab && !printSparse)\n\t\t\tlog.println(\"];\");\n\t}\n\n\t@Override\n\tpublic void iterate(StateAndValueConsumer consumer, boolean sparse)\n\t{\n\t\tif (!sparse) {\n\t\t\tStateAndValuesIterator it = new StateAndValuesIterator(consumer);\n\t\t\tit.iterate();\n\t\t} else {\n\t\t\tStateAndValueConsumer sparseConsumer = (int varValues[], double value, long stateIndex) -> {\n\t\t\t\tif (value != 0) {\n\t\t\t\t\tconsumer.accept(varValues, value, stateIndex);\n\t\t\t\t}\n\t\t\t};\n\t\t\tStateAndValuesIterator it = new StateAndValuesIterator(sparseConsumer);\n\t\t\tit.iterate();\n\t\t}\n\t}\n\n\t@Override\n\tpublic void iterateFiltered(JDDNode filter, StateAndValueConsumer consumer, boolean sparse)\n\t{\n\t\tif (!sparse) {\n\t\t\tStateAndValuesIterator it = new StateAndValuesIterator(consumer);\n\t\t\tit.iterateFiltered(filter);\n\t\t} else {\n\t\t\tStateAndValueConsumer sparseConsumer = (int varValues[], double value, long stateIndex) -> {\n\t\t\t\tif (value != 0) {\n\t\t\t\t\tconsumer.accept(varValues, value, stateIndex);\n\t\t\t\t}\n\t\t\t};\n\t\t\tStateAndValuesIterator it = new StateAndValuesIterator(sparseConsumer);\n\t\t\tit.iterateFiltered(filter);\n\t\t}\n\t}\n\n\tprivate class StateAndValuesIterator {\n\t\tprivate int[] varSizes;\n\t\tprivate int[] varValues;\n\t\tprivate int currentVar;\n\t\tprivate int currentVarLevel;\n\n\t\tprivate StateAndValueConsumer consumer;\n\n\t\tpublic StateAndValuesIterator(StateAndValueConsumer consumer)\n\t\t{\n\t\t\tthis.consumer = consumer;\n\n\t\t\tvarValues = new int[varList.getNumVars()];\n\t\t\tfor (int i = 0; i < varList.getNumVars(); i++) {\n\t\t\t\tvarValues[i] =  varList.getLow(i);\n\t\t\t}\n\n\t\t\tvarSizes = new int[varList.getNumVars()];\n\t\t\tfor (int i = 0; i < varList.getNumVars(); i++) {\n\t\t\t\tvarSizes[i] = varList.getRangeLogTwo(i);\n\t\t\t}\n\n\t\t\tcurrentVar = 0;\n\t\t\tcurrentVarLevel = 0;\n\t\t}\n\n\t\tpublic void iterate()\n\t\t{\n\t\t\titerateRec(0, odd, 0);\n\t\t}\n\n\t\tpublic void iterateFiltered(JDDNode filter)\n\t\t{\n\t\t\titerateRecFiltered(0, odd, 0, filter);\n\t\t}\n\n\t\t/**\n\t\t * Recursive part of state/value iteration.\n\t\t *\n\t\t * (NB: this would be very easy - i.e. not even\n\t\t *  any recursion - if we didn't want to print\n\t\t *  out the values of the module variables as well\n\t\t *  which requires traversal of the odd as well\n\t\t *  as the vector)\n\t\t * (NB2: traversal of vector/odd is still quite simple;\n\t\t *  tricky bit is keeping track of variable values\n\t\t *  throughout traversal - we want to be efficient\n\t\t *  and not compute the values from scratch each\n\t\t *  time, but we also want to avoid passing arrays\n\t\t *  into the recursive method)\n\t\t */\n\t\tprivate void iterateRec(int level, ODDNode o, int n)\n\t\t{\n\t\t\tdouble d;\n\n\t\t\t// base case - at bottom\n\t\t\tif (level == numVars) {\n\t\t\t\td = values.getElement(n);\n\t\t\t\tconsumer.accept(varValues, d, n);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t// recurse\n\t\t\telse {\n\t\t\t\tif (o.getEOff() > 0) {\n\t\t\t\t\tcurrentVarLevel++;\n\t\t\t\t\tif (currentVarLevel == varSizes[currentVar]) {\n\t\t\t\t\t\tcurrentVar++;\n\t\t\t\t\t\tcurrentVarLevel = 0;\n\t\t\t\t\t}\n\t\t\t\t\titerateRec(level + 1, o.getElse(), n);\n\t\t\t\t\tcurrentVarLevel--;\n\t\t\t\t\tif (currentVarLevel == -1) {\n\t\t\t\t\t\tcurrentVar--;\n\t\t\t\t\t\tcurrentVarLevel = varSizes[currentVar] - 1;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (o.getTOff() > 0) {\n\t\t\t\t\tvarValues[currentVar] += (1 << (varSizes[currentVar] - 1 - currentVarLevel));\n\t\t\t\t\tcurrentVarLevel++;\n\t\t\t\t\tif (currentVarLevel == varSizes[currentVar]) {\n\t\t\t\t\t\tcurrentVar++;\n\t\t\t\t\t\tcurrentVarLevel = 0;\n\t\t\t\t\t}\n\t\t\t\t\titerateRec(level + 1, o.getThen(), (int) (n + o.getEOff()));\n\t\t\t\t\tcurrentVarLevel--;\n\t\t\t\t\tif (currentVarLevel == -1) {\n\t\t\t\t\t\tcurrentVar--;\n\t\t\t\t\t\tcurrentVarLevel = varSizes[currentVar] - 1;\n\t\t\t\t\t}\n\t\t\t\t\tvarValues[currentVar] -= (1 << (varSizes[currentVar] - 1 - currentVarLevel));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Recursive part of filtered state/value iteration.\n\t\t *\n\t\t * So we need to traverse filter too.\n\t\t * See also notes above for iterateRec.\n\t\t */\n\t\tprivate void iterateRecFiltered(int level, ODDNode o, int n, JDDNode filter)\n\t\t{\n\t\t\tdouble d;\n\t\t\tJDDNode newFilter;\n\n\t\t\t// skip if the filter is zero\n\t\t\tif (filter.equals(JDD.ZERO)) {\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// base case - at bottom\n\t\t\tif (level == numVars) {\n\t\t\t\td = values.getElement(n);\n\t\t\t\tconsumer.accept(varValues, d, n);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t// recurse\n\t\t\telse {\n\t\t\t\tif (o.getEOff() > 0) {\n\t\t\t\t\tcurrentVarLevel++;\n\t\t\t\t\tif (currentVarLevel == varSizes[currentVar]) {\n\t\t\t\t\t\tcurrentVar++;\n\t\t\t\t\t\tcurrentVarLevel = 0;\n\t\t\t\t\t}\n\t\t\t\t\tJDD.Ref(filter);\n\t\t\t\t\tJDD.Ref(vars.getVar(level));\n\t\t\t\t\tnewFilter = JDD.Apply(JDD.TIMES, filter, JDD.Not(vars.getVar(level)));\n\t\t\t\t\titerateRecFiltered(level + 1, o.getElse(), n, newFilter);\n\t\t\t\t\tJDD.Deref(newFilter);\n\t\t\t\t\tcurrentVarLevel--;\n\t\t\t\t\tif (currentVarLevel == -1) {\n\t\t\t\t\t\tcurrentVar--;\n\t\t\t\t\t\tcurrentVarLevel = varSizes[currentVar] - 1;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tif (o.getTOff() > 0) {\n\t\t\t\t\tvarValues[currentVar] += (1 << (varSizes[currentVar] - 1 - currentVarLevel));\n\t\t\t\t\tcurrentVarLevel++;\n\t\t\t\t\tif (currentVarLevel == varSizes[currentVar]) {\n\t\t\t\t\t\tcurrentVar++;\n\t\t\t\t\t\tcurrentVarLevel = 0;\n\t\t\t\t\t}\n\t\t\t\t\tJDD.Ref(filter);\n\t\t\t\t\tJDD.Ref(vars.getVar(level));\n\t\t\t\t\tnewFilter = JDD.Apply(JDD.TIMES, filter, vars.getVar(level));\n\t\t\t\t\titerateRecFiltered(level + 1, o.getThen(), (int) (n + o.getEOff()), newFilter);\n\t\t\t\t\tJDD.Deref(newFilter);\n\t\t\t\t\tcurrentVarLevel--;\n\t\t\t\t\tif (currentVarLevel == -1) {\n\t\t\t\t\t\tcurrentVar--;\n\t\t\t\t\t\tcurrentVarLevel = varSizes[currentVar] - 1;\n\t\t\t\t\t}\n\t\t\t\t\tvarValues[currentVar] -= (1 << (varSizes[currentVar] - 1 - currentVarLevel));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic StateValuesDV deepCopy() throws PrismException\n\t{\n\t\t// Clone vector\n\t\tDoubleVector dv = new DoubleVector(values.getSize());\n\t\tdv.add(values);\n\t\t// Return copy\n\t\treturn new StateValuesDV(dv, model, accuracy);\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/states/StateValuesMTBDD.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.states;\n\nimport java.io.BufferedReader;\nimport java.io.File;\nimport java.io.FileReader;\nimport java.io.IOException;\n\nimport jdd.*;\nimport odd.*;\nimport parser.VarList;\nimport parser.ast.RelOp;\nimport prism.Accuracy;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.PrismNotSupportedException;\nimport prism.StateAndValueConsumer;\nimport prism.StateAndValuePrinter;\nimport symbolic.model.Model;\n\n/**\n * Class for state-indexed vectors of (integer or double) values, represented by an MTBDD\n */\npublic class StateValuesMTBDD implements StateValues\n{\n\t/** MTBDD storing vector of values */\n\tJDDNode values;\n\n\t/** Accuracy info */\n\tAccuracy accuracy;\n\t\n\t// info from model\n\t/** The underlying model */\n\tModel model;\n\t/** The BDD row variables of the underlying model */\n\tJDDVars vars;\n\tJDDNode reach;\n\t/** The number of BDD row variables in the underlying model */\n\tint numDDRowVars;\n\t/** The number of BDD row variables in the underlying model */\n\tint numVars;\n\t/** The ODD for the reachable states of the underlying model */\n\tODDNode odd;\n\t/** The VarList of the underlying model*/\n\tVarList varList;\n\n\t// CONSTRUCTOR\n\t\n\t/**\n\t * Constructor from a JDDNode (which is stored, not copied).\n\t * Also set the accuracy info.\n\t * <br>[ STORES: values, derefed on later call to clear() ]\n\t * @param values the JddNode for the values\n\t * @param model the underlying model\n\t */\n\tpublic StateValuesMTBDD(JDDNode values, Model model)\n\t{\n\t\tthis (values, model, null);\n\t}\n\n\t/**\n\t * Constructor from a JDDNode (which is stored, not copied).\n\t * Also set the accuracy info.\n\t * <br>[ STORES: values, derefed on later call to clear() ]\n\t * @param values the JddNode for the values\n\t * @param model the underlying model\n\t * @param accuracy result accuracy info\n\t */\n\tpublic StateValuesMTBDD(JDDNode values, Model model, Accuracy accuracy)\n\t{\n\t\t// store values vector mtbdd and accuracy\n\t\tthis.values = values;\n\t\tsetAccuracy(accuracy);\n\t\t// get info from model\n\t\tsetModel(model);\n\t}\n\n\t/** Helper method: Store information about the underlying model */\n\tprivate void setModel(Model model)\n\t{\n\t\tthis.model = model;\n\t\tvars = model.getAllDDRowVars();\n\t\treach = model.getReach();\n\t\tnumDDRowVars = model.getNumDDRowVars();\n\t\tnumVars = vars.n();\n\t\todd = model.getODD();\n\t\tvarList = model.getVarList();\n\t}\n\n\t@Override\n\tpublic void switchModel(Model newModel)\n\t{\n\t\tsetModel(newModel);\n\t}\n\n\t@Override\n\tpublic void setAccuracy(Accuracy accuracy)\n\t{\n\t\tthis.accuracy = accuracy;\n\t}\n\t\n\t// CONVERSION METHODS\n\t\n\t@Override\n\tpublic StateValuesDV convertToStateValuesDV() throws PrismException\n\t{\n\t\t// convert to StateValuesDV, destroy (clear) old vector\n\t\tStateValuesDV res = new StateValuesDV(values, model, accuracy);\n\t\tclear();\n\t\treturn res;\n\t}\n\n\t@Override\n\tpublic StateValuesMTBDD convertToStateValuesMTBDD()\n\t{\n\t\t// convert to StateValuesMTBDD (nothing to do)\n\t\treturn this;\n\t}\n\n\t// METHODS TO MODIFY VECTOR\n\n\t/**\n\t * Set element i of this vector to value d. \n\t */\n\tpublic void setElement(int i, double d) throws PrismNotSupportedException\n\t{\n\t\tODDNode ptr;\n\t\tJDDNode dd;\n\t\tint j, k;\n\n\t\tODDUtils.checkInt(odd, \"Cannot set element via index for model\");\n\n\t\t// Use ODD to build BDD for state index i\n\t\tdd = JDD.Constant(1);\n\t\tptr = odd;\n\t\tj = i;\n\t\tfor (k = 0; k < numVars; k++) {\n\t\t\tJDD.Ref(vars.getVar(k));\n\t\t\tif (j >= ptr.getEOff()) {\n\t\t\t\tj -= ptr.getEOff();\n\t\t\t\tdd = JDD.And(dd, vars.getVar(k));\n\t\t\t\tptr = ptr.getThen();\n\t\t\t} else {\n\t\t\t\tdd = JDD.And(dd, JDD.Not(vars.getVar(k)));\n\t\t\t\tptr = ptr.getElse();\n\t\t\t}\n\t\t}\n\t\t\n\t\t// Add element to vector MTBDD\n\t\tvalues = JDD.ITE(dd, JDD.Constant(d), values);\n\t}\n\n\t@Override\n\tpublic void readFromFile(File file) throws PrismException\n\t{\n\t\tBufferedReader in;\n\t\tString s;\n\t\tint lineNum = 0, count = 0;\n\t\tdouble d;\n\t\tboolean hasIndices = false;\n\t\tint size = model.getNumStates();\n\t\t\n\t\ttry {\n\t\t\t// open file for reading\n\t\t\tin = new BufferedReader(new FileReader(file));\n\t\t\t// read remaining lines\n\t\t\ts = in.readLine(); lineNum++;\n\t\t\twhile (s != null) {\n\t\t\t\ts = s.trim();\n\t\t\t\tif (!(\"\".equals(s))) {\n\t\t\t\t\t// If entry is of form \"i=x\", use i as index not count\n\t\t\t\t\t// (otherwise, assume line i contains value for state index i)\n\t\t\t\t\tif (s.contains(\"=\")) {\n\t\t\t\t\t\thasIndices = true;\n\t\t\t\t\t\tString ss[] = s.split(\"=\");\n\t\t\t\t\t\tcount = Integer.parseInt(ss[0]);\n\t\t\t\t\t\ts = ss[1];\n\t\t\t\t\t}\n\t\t\t\t\tif (count + 1 > size) {\n\t\t\t\t\t\tin.close();\n\t\t\t\t\t\tthrow new PrismException(\"Too many values in file \\\"\" + file + \"\\\" (more than \" + size + \")\");\n\t\t\t\t\t}\n\t\t\t\t\td = Double.parseDouble(s);\n\t\t\t\t\tsetElement(count, d);\n\t\t\t\t\tcount++;\n\t\t\t\t}\n\t\t\t\ts = in.readLine(); lineNum++;\n\t\t\t}\n\t\t\t// Close file\n\t\t\tin.close();\n\t\t\t// Check size\n\t\t\tif (!hasIndices && count < size)\n\t\t\t\tthrow new PrismException(\"Too few values in file \\\"\" + file + \"\\\" (\" + count + \", not \" + size + \")\");\n\t\t}\n\t\tcatch (IOException e) {\n\t\t\tthrow new PrismException(\"File I/O error reading from \\\"\" + file + \"\\\"\");\n\t\t}\n\t\tcatch (NumberFormatException e) {\n\t\t\tthrow new PrismException(\"Error detected at line \" + lineNum + \" of file \\\"\" + file + \"\\\"\");\n\t\t}\n\t}\n\n\t@Override\n\tpublic void roundOff(int places)\n\t{\n\t\tvalues = JDD.RoundOff(values, places);\n\t}\n\n\t@Override\n\tpublic void subtractFromOne() \n\t{\n\t\tJDD.Ref(reach);\n\t\tvalues = JDD.Apply(JDD.MINUS, reach, values);\n\t}\n\n\t@Override\n\tpublic void add(StateValues sp) \n\t{\n\t\tStateValuesMTBDD spm = (StateValuesMTBDD) sp;\n\t\tJDD.Ref(spm.values);\n\t\tvalues = JDD.Apply(JDD.PLUS, values, spm.values);\n\t}\n\n\t@Override\n\tpublic void timesConstant(double d) \n\t{\n\t\tvalues = JDD.Apply(JDD.TIMES, values, JDD.Constant(d));\n\t}\n\n\t@Override\n\tpublic double dotProduct(StateValues sp) \n\t{\n\t\tStateValuesMTBDD spm = (StateValuesMTBDD) sp;\n\t\tJDD.Ref(values);\n\t\tJDD.Ref(spm.values);\n\t\tJDDNode tmp = JDD.Apply(JDD.TIMES, values, spm.values);\n\t\ttmp = JDD.SumAbstract(tmp, vars);\n\t\tdouble d = JDD.FindMax(tmp);\n\t\tJDD.Deref(tmp);\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic void filter(JDDNode filter)\n\t{\n\t\tJDD.Ref(filter);\n\t\tvalues = JDD.Apply(JDD.TIMES, values, filter);\n\t}\n\n\t@Override\n\tpublic void filter(JDDNode filter, double d)\n\t{\n\t\t// If filter, then keep value, else constant d,\n\t\t// but only for the reachable states\n\t\tvalues = JDD.Times(reach.copy(), JDD.ITE(filter.copy(), values, JDD.Constant(d)));\n\t}\n\n\t@Override\n\tpublic void maxMTBDD(JDDNode vec2)\n\t{\n\t\tJDD.Ref(vec2);\n\t\tvalues = JDD.Apply(JDD.MAX, values, vec2);\n\t}\n\t\n\t@Override\n\tpublic void clear()\n\t{\n\t\tJDD.Deref(values);\n\t}\n\n\t// METHODS TO ACCESS VECTOR DATA\n\t\n\t@Override\n\tpublic int getSize()\n\t{\n\t\treturn model.getNumStates();\n\t}\n\n\t@Override\n\tpublic Object getValue(int i) throws PrismNotSupportedException\n\t{\n\t\tJDDNode dd = values;\n\n\t\tODDUtils.checkInt(odd, \"Cannot get value for state index in model\");\n\n\t\tODDNode ptr = odd;\n\t\tint o = 0;\n\t\tfor (int k = 0; k < numVars; k++) {\n\t\t\tif (ptr.getEOff() > i - o) {\n\t\t\t\tdd = dd.getIndex() > vars.getVarIndex(k) ? dd : dd.getElse();\n\t\t\t\tptr = ptr.getElse();\n\t\t\t} else {\n\t\t\t\tdd = dd.getIndex() > vars.getVarIndex(k) ? dd : dd.getThen();\n\t\t\t\to += ptr.getEOff();\n\t\t\t\tptr = ptr.getThen();\n\t\t\t}\n\t\t}\n\t\t// TODO: cast to Integer or Double as required?\n\t\treturn dd.getValue();\n\t}\n\n\t/**\n\t * Get the underlying JDDNode of this StateValuesMTBDD.\n\t * <br>\n\t * Note: The returned JDDNode is NOT a copy, i.e., the caller\n\t * is responsible that the node does not get derefed.\n\t * <br>[ REFS: <i>none</i> ]\n\t */\n\tpublic JDDNode getJDDNode()\n\t{\n\t\treturn values;\n\t}\n\n\t@Override\n\tpublic int getNNZ()\n\t{\n\t\tdouble nnz = JDD.GetNumMinterms(values, numDDRowVars);\n\t\treturn (nnz > Integer.MAX_VALUE) ? -1 : (int)Math.round(nnz);\n\t}\n\n\t@Override\n\tpublic String getNNZString()\n\t{\n\t\treturn \"\" + getNNZ();\n\t}\n\n\t// Filter operations\n\n\t@Override\n\tpublic double firstFromBDD(JDDNode filter)\n\t{\n\t\tJDDNode tmp;\n\t\tdouble d;\n\t\t\n\t\t// filter filter\n\t\tJDD.Ref(filter);\n\t\tJDD.Ref(reach);\n\t\ttmp = JDD.And(filter, reach);\n\t\t\n\t\t// This shouldn't really be called with an empty filter.\n\t\t// But we check for this anyway and return NaN.\n\t\t// This is unfortunately indistinguishable from the case\n\t\t// where the vector does actually contain NaN. Ho hum.\n\t\tif (tmp.equals(JDD.ZERO)) return Double.NaN;\n\t\t\t\t\n\t\t// remove all but first element of filter\n\t\ttmp = JDD.RestrictToFirst(tmp, vars);\n\t\t\n\t\t// then apply filter to values\n\t\tJDD.Ref(values);\n\t\ttmp = JDD.Apply(JDD.TIMES, values, tmp);\n\t\t\n\t\t// extract single value (we use SumAbstract could use e.g. MaxAbstract, etc.)\n\t\ttmp = JDD.SumAbstract(tmp, vars);\n\t\td = tmp.getValue();\n\t\tJDD.Deref(tmp);\n\t\t\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double minOverBDD(JDDNode filter)\n\t{\n\t\tJDDNode tmp;\n\t\tdouble d;\n\t\t\n\t\t// filter filter\n\t\tJDD.Ref(filter);\n\t\tJDD.Ref(reach);\n\t\ttmp = JDD.And(filter, reach);\n\t\t\n\t\t// min of an empty set is +infinity\n\t\tif (tmp.equals(JDD.ZERO)) return Double.POSITIVE_INFINITY;\n\t\t\n\t\t// set non-reach states to infinity\n\t\tJDD.Ref(values);\n\t\ttmp = JDD.ITE(tmp, values, JDD.PlusInfinity());\n\t\t\n\t\td = JDD.FindMin(tmp);\n\t\tJDD.Deref(tmp);\n\t\t\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double maxOverBDD(JDDNode filter)\n\t{\n\t\tJDDNode tmp;\n\t\tdouble d;\n\t\t\n\t\t// filter filter\n\t\tJDD.Ref(filter);\n\t\tJDD.Ref(reach);\n\t\ttmp = JDD.And(filter, reach);\n\t\t\n\t\t// max of an empty set is -infinity\n\t\tif (tmp.equals(JDD.ZERO)) return Double.NEGATIVE_INFINITY;\n\t\t\n\t\t// set non-reach states to infinity\n\t\tJDD.Ref(values);\n\t\ttmp = JDD.ITE(tmp, values, JDD.MinusInfinity());\n\t\t\n\t\td = JDD.FindMax(tmp);\n\t\tJDD.Deref(tmp);\n\t\t\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double maxFiniteOverBDD(JDDNode filter)\n\t{\n\t\tJDDNode tmp;\n\t\tdouble d;\n\n\t\t// filter filter\n\t\tJDD.Ref(filter);\n\t\tJDD.Ref(reach);\n\t\ttmp = JDD.And(filter, reach);\n\n\t\t// max of an empty set is -infinity\n\t\tif (tmp.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(tmp);\n\t\t\treturn Double.NEGATIVE_INFINITY;\n\t\t}\n\n\t\t// set non-reach states to infinity\n\t\tJDD.Ref(values);\n\t\ttmp = JDD.ITE(tmp, values, JDD.MinusInfinity());\n\n\t\td = JDD.FindMaxFinite(tmp);\n\t\tJDD.Deref(tmp);\n\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double sumOverBDD(JDDNode filter)\n\t{\n\t\tJDDNode tmp;\n\t\tdouble d;\n\t\t\n\t\tJDD.Ref(values);\n\t\tJDD.Ref(filter);\n\t\ttmp = JDD.Apply(JDD.TIMES, values, filter);\n\t\ttmp = JDD.SumAbstract(tmp, vars);\n\t\td = tmp.getValue();\n\t\tJDD.Deref(tmp);\n\t\t\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic double sumOverMTBDD(JDDNode mult)\n\t{\n\t\tJDDNode tmp;\n\t\tdouble d;\n\t\t\n\t\tJDD.Ref(values);\n\t\tJDD.Ref(mult);\n\t\ttmp = JDD.Apply(JDD.TIMES, values, mult);\n\t\ttmp = JDD.SumAbstract(tmp, vars);\n\t\td = tmp.getValue();\n\t\tJDD.Deref(tmp);\n\t\t\n\t\treturn d;\n\t}\n\n\t@Override\n\tpublic StateValues sumOverDDVars(JDDVars sumVars, Model newModel)\n\t{\n\t\tJDDNode tmp;\n\t\t\n\t\tJDD.Ref(values);\n\t\ttmp = JDD.SumAbstract(values, sumVars);\n\t\t\n\t\treturn new StateValuesMTBDD(tmp, newModel);\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromInterval(String relOpString, double bound)\n\t{\n\t\treturn getBDDFromInterval(RelOp.parseSymbol(relOpString), bound);\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromInterval(RelOp relOp, double bound)\n\t{\n\t\tJDDNode sol = null;\n\t\t\n\t\tJDD.Ref(values);\n\t\tswitch (relOp) {\n\t\tcase GEQ:\n\t\t\tsol = JDD.GreaterThanEquals(values, bound);\n\t\t\tbreak;\n\t\tcase GT:\n\t\t\tsol = JDD.GreaterThan(values, bound);\n\t\t\tbreak;\n\t\tcase LEQ:\n\t\t\tsol = JDD.LessThanEquals(values, bound);\n\t\t\tbreak;\n\t\tcase LT:\n\t\t\tsol = JDD.LessThan(values, bound);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\t// Don't handle\n\t\t}\n\t\t\n\t\treturn sol;\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromInterval(double lo, double hi)\n\t{\n\t\tJDDNode sol;\n\t\t\n\t\tJDD.Ref(values);\n\t\tsol = JDD.Interval(values, lo, hi);\n\t\t\n\t\treturn sol;\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValue(double value, double epsilon, boolean abs)\n\t{\n\t\tif (abs)\n\t\t\treturn getBDDFromCloseValueAbs(value, epsilon);\n\t\telse\n\t\t\treturn getBDDFromCloseValueRel(value, epsilon);\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValueAbs(double value, double epsilon)\n\t{\n\t\tJDDNode sol;\n\t\t\n\t\t// TODO: infinite cases\n\t\t// if (isinf(values[i])) return (isinf(value) && (values[i] > 0) == (value > 0)) ? 1 : 0\n\t\t// else (fabs(values[i] - value) < epsilon);\n\t\t\n\t\tJDD.Ref(values);\n\t\tsol = JDD.Interval(values, value - epsilon, value + epsilon);\n\t\t\n\t\treturn sol;\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValueRel(double value, double epsilon)\n\t{\n\t\tJDDNode sol;\n\t\t\n\t\t// TODO: infinite cases\n\t\t// if (isinf(values[i])) return (isinf(value) && (values[i] > 0) == (value > 0)) ? 1 : 0\n\t\t// else (fabs(values[i] - value) < epsilon);\n\n\t\t// TODO: this should be relative, not absolute error\n\t\t// (see doubles_are_close_rel in dv.cc for reference)\n\t\tJDD.Ref(values);\n\t\tsol = JDD.Interval(values, value - epsilon, value + epsilon);\n\t\t\n\t\treturn sol;\n\t}\n\n\t@Override\n\tpublic Accuracy getAccuracy()\n\t{\n\t\treturn accuracy;\n\t}\n\t\n\t// PRINTING STUFF\n\n\t/**\n\t * Print the state values for a JDDNode, representing an MTBDD over the row vars of a model.\n\t * <br>[ REFS: <i>none</i>, DEREFS: value ]\n\t * @param log the output log\n\t * @param values the MTBDD node\n\t * @param model the Model (for the variable information)\n\t * @param description an optional description for printing (may be {@code null})\n\t */\n\tpublic static void print(PrismLog log, JDDNode values, Model model, String description) throws PrismException\n\t{\n\t\tStateValuesMTBDD sv = null;\n\t\ttry {\n\t\t\tsv = new StateValuesMTBDD(values, model);\n\t\t\tif (description != null) log.println(description);\n\t\t\tsv.print(log);\n\t\t} finally {\n\t\t\tif (sv != null)\n\t\t\t\tsv.clear();\n\t\t}\n\t}\n\n\t@Override\n\tpublic void print(PrismLog log, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices) throws PrismException\n\t{\n\t\tif (odd == null) {\n\t\t\tif (printMatlab && printSparse) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Cannot print in sparse Matlab format, as there is no ODD\");\n\t\t\t}\n\t\t\t// we have no index information -> can't print state index\n\t\t\tprintIndices = false;\n\t\t}\n\n\t\t// header for matlab format\n\t\tif (printMatlab)\n\t\t\tlog.println(!printSparse ? \"v = [\" : \"v = sparse(\" + getSize() + \",1);\");\n\n\t\t// check if all zero\n\t\tif (printSparse && !printMatlab && values.equals(JDD.ZERO)) {\n\t\t\tlog.println(\"(all zero)\");\n\t\t\treturn;\n\t\t}\n\n\t\t// set up and call recursive print\n\t\tStateIterator it = new StateIterator(new StateAndValuePrinter(log, varList, printSparse, printMatlab, printStates, printIndices));\n\t\tif (printSparse) {\n\t\t\tit.iterateSparse(values);\n\t\t} else {\n\t\t\tit.iterateFiltered(model.getReach(), values);\n\t\t}\n\n\t\t// footer for matlab format\n\t\tif (printMatlab && !printSparse)\n\t\t\tlog.println(\"];\");\n\t}\n\n\tprivate class StateIterator {\n\t\tprivate int[] varSizes;\n\t\tprivate int[] varValues;\n\t\tprivate int currentVar;\n\t\tprivate int currentVarLevel;\n\n\t\tprivate StateAndValueConsumer consumer;\n\n\t\tpublic StateIterator(StateAndValueConsumer consumer)\n\t\t{\n\t\t\tthis.consumer = consumer;\n\n\t\t\tvarValues = new int[varList.getNumVars()];\n\t\t\tfor (int i = 0; i < varList.getNumVars(); i++) {\n\t\t\t\tvarValues[i] =  varList.getLow(i);\n\t\t\t}\n\n\t\t\tvarSizes = new int[varList.getNumVars()];\n\t\t\tfor (int i = 0; i < varList.getNumVars(); i++) {\n\t\t\t\tvarSizes[i] = varList.getRangeLogTwo(i);\n\t\t\t}\n\n\t\t\tcurrentVar = 0;\n\t\t\tcurrentVarLevel = 0;\n\t\t}\n\n\t\tpublic void iterateSparse(JDDNode dd)\n\t\t{\n\t\t\t// if we don't have an ODD, we set the index to -1\n\t\t\tlong stateIndex = (odd == null ? -1 : 0);\n\t\t\titerateSparseRec(dd, 0, odd, stateIndex);\n\t\t}\n\n\t\t/**\n\t\t * Iterate over all state/value pairs in ddValue that\n\t\t * are included in the 0/1-DD ddFilter.\n\t\t *\n\t\t * @param ddFilter 0/1-DD for the states that should be considered\n\t\t * @param ddValue the values for the states (has to be zero for all states not in ddFilter)\n\t\t */\n\t\tpublic void iterateFiltered(JDDNode ddFilter, JDDNode ddValue)\n\t\t{\n\t\t\t// if we don't have an ODD, we set the index to -1\n\t\t\tlong stateIndex = (odd == null ? -1 : 0);\n\t\t\titerateRec(ddFilter, ddValue, 0, odd, stateIndex);\n\t\t}\n\n\t\t/**\n\t\t * Recursive part of iteration (only non-zero values).\n\t\t *\n\t\t * (NB: this would be very easy - i.e. not even\n\t\t *  any recursion - if we didn't want to print\n\t\t *  out the values of the module variables as well\n\t\t *  which requires traversal of the odd as well\n\t\t *  as the vector)\n\t\t * (NB2: traversal of vector/odd is still quite simple;\n\t\t *  tricky bit is keeping track of variable values\n\t\t *  throughout traversal - we want to be efficient\n\t\t *  and not compute the values from scratch each\n\t\t *  time, but we also want to avoid passing arrays\n\t\t *  into the recursive method)\n\t\t */\n\t\tprivate void iterateSparseRec(JDDNode dd, int level, ODDNode o, long stateIndex)\n\t\t{\n\t\t\tJDDNode e, t;\n\n\t\t\t// zero constant - bottom out of recursion\n\t\t\tif (dd.equals(JDD.ZERO)) return;\n\n\t\t\t// base case - at bottom (nonzero terminal)\n\t\t\tif (level == numVars) {\n\t\t\t\tconsumer.accept(varValues, dd.getValue(), stateIndex);\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// select 'else' and 'then' branches\n\t\t\telse if (dd.getIndex() > vars.getVarIndex(level)) {\n\t\t\t\te = t = dd;\n\t\t\t}\n\t\t\telse {\n\t\t\t\te = dd.getElse();\n\t\t\t\tt = dd.getThen();\n\t\t\t}\n\n\t\t\tODDNode oe = (o != null ? o.getElse() : null);\n\t\t\tODDNode ot = (o != null ? o.getThen() : null);\n\t\t\tlong eoff = (o != null ? o.getEOff() : 0);\n\n\t\t\t// then recurse...\n\t\t\tcurrentVarLevel++; if (currentVarLevel == varSizes[currentVar]) { currentVar++; currentVarLevel=0; }\n\t\t\titerateSparseRec(e, level+1, oe, stateIndex);\n\t\t\tcurrentVarLevel--; if (currentVarLevel == -1) { currentVar--; currentVarLevel=varSizes[currentVar]-1; }\n\t\t\tvarValues[currentVar] += (1 << (varSizes[currentVar]-1-currentVarLevel));\n\t\t\tcurrentVarLevel++; if (currentVarLevel == varSizes[currentVar]) { currentVar++; currentVarLevel=0; }\n\t\t\titerateSparseRec(t, level+1, ot, stateIndex + eoff);\n\t\t\tcurrentVarLevel--; if (currentVarLevel == -1) { currentVar--; currentVarLevel=varSizes[currentVar]-1; }\n\t\t\tvarValues[currentVar] -= (1 << (varSizes[currentVar]-1-currentVarLevel));\n\t\t}\n\n\t\t/**\n\t\t * Recursive part of iteration (all elements,\n\t\t * including where the value is zero).\n\t\t *\n\t\t * @param ddFilter 0/1-DD for the states that should be considered\n\t\t * @param ddValue the values for the states (has to be zero for all states not in ddFilter)\n\t\t * @param level the current variable level\n\t\t * @param o the current node in the ODD\n\t\t * @param n the current state index\n\t\t */\n\t\tprivate void iterateRec(JDDNode ddFilter, JDDNode ddValue, int level, ODDNode o, long stateIndex)\n\t\t{\n\t\t\t/*\n\t\t\t * (NB: this would be very easy - i.e. not even\n\t\t\t *  any recursion - if we didn't want to print\n\t\t\t *  out the values of the module variables as well\n\t\t\t *  which requires traversal of the odd as well\n\t\t\t *  as the vector)\n\t\t\t * (NB2: traversal of vector/odd is still quite simple;\n\t\t\t *  tricky bit is keeping track of variable values\n\t\t\t *  throughout traversal - we want to be efficient\n\t\t\t *  and not compute the values from scratch each\n\t\t\t *  time, but we also want to avoid passing arrays\n\t\t\t *  into the recursive method)\n\t\t\t */\n\n\t\t\t// ddFilter is zero - bottom out of recursion\n\t\t\tif (ddFilter.equals(JDD.ZERO)) return;\n\n\t\t\t// base case - at bottom (nonzero terminal)\n\t\t\tif (level == numVars) {\n\t\t\t\tconsumer.accept(varValues, ddValue.getValue(), stateIndex);\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\tJDDNode eFilter, tFilter, eValue, tValue;\n\n\t\t\t// select 'else' and 'then' branches ( filter dd )\n\t\t\tif (ddFilter.getIndex() > vars.getVarIndex(level)) {\n\t\t\t\teFilter = tFilter = ddFilter;\n\t\t\t} else {\n\t\t\t\teFilter = ddFilter.getElse();\n\t\t\t\ttFilter = ddFilter.getThen();\n\t\t\t}\n\n\t\t\t// select 'else' and 'then' branches ( value dd )\n\t\t\tif (ddValue.getIndex() > vars.getVarIndex(level)) {\n\t\t\t\teValue = tValue = ddValue;\n\t\t\t} else {\n\t\t\t\teValue = ddValue.getElse();\n\t\t\t\ttValue = ddValue.getThen();\n\t\t\t}\n\n\t\t\tODDNode oe = (o != null ? o.getElse() : null);\n\t\t\tODDNode ot = (o != null ? o.getThen() : null);\n\t\t\tlong eoff = (o != null ? o.getEOff() : 0);\n\n\t\t\t// then recurse...\n\t\t\tcurrentVarLevel++; if (currentVarLevel == varSizes[currentVar]) { currentVar++; currentVarLevel=0; }\n\t\t\titerateRec(eFilter, eValue, level+1, oe, stateIndex);\n\t\t\tcurrentVarLevel--; if (currentVarLevel == -1) { currentVar--; currentVarLevel=varSizes[currentVar]-1; }\n\t\t\tvarValues[currentVar] += (1 << (varSizes[currentVar]-1-currentVarLevel));\n\t\t\tcurrentVarLevel++; if (currentVarLevel == varSizes[currentVar]) { currentVar++; currentVarLevel=0; }\n\t\t\titerateRec(tFilter, tValue, level+1, ot, stateIndex + eoff);\n\t\t\tcurrentVarLevel--; if (currentVarLevel == -1) { currentVar--; currentVarLevel=varSizes[currentVar]-1; }\n\t\t\tvarValues[currentVar] -= (1 << (varSizes[currentVar]-1-currentVarLevel));\n\t\t}\n\t}\n\n\t@Override\n\tpublic void iterate(StateAndValueConsumer consumer, boolean sparse)\n\t{\n\t\tStateIterator it = new StateIterator(consumer);\n\t\tif (sparse) {\n\t\t\tit.iterateSparse(values);\n\t\t} else {\n\t\t\tit.iterateFiltered(reach, values);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void iterateFiltered(JDDNode filter, StateAndValueConsumer consumer, boolean sparse)\n\t{\n\t\t// filter out\n\t\tJDDNode tmp = JDD.Apply(JDD.TIMES, values.copy(), filter.copy());\n\n\t\tStateIterator it = new StateIterator(consumer);\n\n\t\tif (sparse) {\n\t\t\tit.iterateSparse(tmp);\n\t\t} else {\n\t\t\tit.iterateFiltered(filter, tmp);\n\t\t}\n\n\t\tJDD.Deref(tmp);\n\t}\n\n\t@Override\n\tpublic void printFiltered(PrismLog log, JDDNode filter, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices) throws PrismException\n\t{\n\t\tJDDNode tmp;\n\n\t\tif (odd == null) {\n\t\t\tif (printMatlab && printSparse) {\n\t\t\t\tthrow new PrismNotSupportedException(\"Cannot print in sparse Matlab format, as there is no ODD\");\n\t\t\t}\n\t\t\t// we have no index information -> can't print state index\n\t\t\tprintIndices = false;\n\t\t}\n\n\t\t// filter out\n\t\tJDD.Ref(values);\n\t\tJDD.Ref(filter);\n\t\ttmp = JDD.Apply(JDD.TIMES, values, filter);\n\n\t\t// header for matlab format\n\t\tif (printMatlab)\n\t\t\tlog.println(!printSparse ? \"v = [\" : \"v = sparse(\" + getSize() + \",1);\");\n\n\t\t// check if all zero\n\t\tif (printSparse && !printMatlab && tmp.equals(JDD.ZERO)) {\n\t\t\tJDD.Deref(tmp);\n\t\t\tlog.println(\"(all zero)\");\n\t\t\treturn;\n\t\t}\n\n\t\t// set up and call recursive print\n\t\tStateIterator it = new StateIterator(new StateAndValuePrinter(log, varList, printSparse, printMatlab, printStates, printIndices));\n\t\tif (printSparse) {\n\t\t\tit.iterateSparse(tmp);\n\t\t} else {\n\t\t\tit.iterateFiltered(filter, tmp);\n\t\t}\n\n\t\t// footer for matlab format\n\t\tif (printMatlab && !printSparse)\n\t\t\tlog.println(\"];\");\n\n\t\t//log.println();\n\t\tJDD.Deref(tmp);\n\t}\n\n\t/**\n\t * Make a (deep) copy of this vector\n\t */\n\tpublic StateValuesMTBDD deepCopy() throws PrismException\n\t{\n\t\tJDD.Ref(values);\n\t\treturn new StateValuesMTBDD(values, model, accuracy);\n\t}\n}\n"
  },
  {
    "path": "prism/src/symbolic/states/StateValuesVoid.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage symbolic.states;\n\nimport java.io.File;\n\nimport parser.ast.RelOp;\nimport jdd.JDDNode;\nimport jdd.JDDVars;\nimport prism.Accuracy;\nimport prism.PrismException;\nimport prism.PrismLog;\nimport prism.StateAndValueConsumer;\nimport symbolic.model.Model;\n\n/**\n * Dummy class implementing StateValues to return miscellaneous (single valued) results, typically of type \"void\".\n */\npublic class StateValuesVoid implements StateValues\n{\n\t/** The stored object */\n\tprivate Object value = null;\n\n\t/** Constructor, store value */\n\tpublic StateValuesVoid(Object value)\n\t{\n\t\tthis.value = value;\n\t}\n\n\t@Override\n\tpublic void switchModel(Model newModel)\n\t{\n\t\t// nothing to do...\n\t}\n\n\t@Override\n\tpublic int getSize()\n\t{\n\t\treturn 1;\n\t}\n\n\t@Override\n\tpublic Object getValue(int i)\n\t{\n\t\treturn value;\n\t}\n\n\t/** Get the value */\n\tpublic Object getValue()\n\t{\n\t\treturn value;\n\t}\n\n\t/** Set the value */\n\tpublic void setValue(Object value)\n\t{\n\t\tthis.value = value;\n\t}\n\n\t@Override\n\tpublic void setAccuracy(Accuracy accuracy)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\t\n\t@Override\n\tpublic StateValuesDV convertToStateValuesDV()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic StateValuesMTBDD convertToStateValuesMTBDD()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void readFromFile(File file) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void roundOff(int places)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void subtractFromOne()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void add(StateValues sp)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void timesConstant(double d)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic double dotProduct(StateValues sp)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void filter(JDDNode filter)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void filter(JDDNode filter, double d)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void maxMTBDD(JDDNode vec2)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void clear()\n\t{\n\t\t// Do nothing\n\t}\n\n\t@Override\n\tpublic int getNNZ()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic String getNNZString()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic double firstFromBDD(JDDNode filter)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic double minOverBDD(JDDNode filter)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic double maxOverBDD(JDDNode filter)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic double maxFiniteOverBDD(JDDNode filter)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic double sumOverBDD(JDDNode filter)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic double sumOverMTBDD(JDDNode mult)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic StateValues sumOverDDVars(JDDVars sumVars, Model newModel) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromInterval(String relOpString, double bound)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromInterval(RelOp relOp, double bound)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromInterval(double lo, double hi)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValue(double val, double epsilon, boolean abs)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValueAbs(double val, double epsilon)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic JDDNode getBDDFromCloseValueRel(double val, double epsilon)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic Accuracy getAccuracy()\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\t\n\t@Override\n\tpublic void print(PrismLog log, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndices) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void printFiltered(PrismLog log, JDDNode filter, boolean printSparse, boolean printMatlab, boolean printStates, boolean printIndizes) throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void iterate(StateAndValueConsumer consumer, boolean sparse)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic void iterateFiltered(JDDNode filter, StateAndValueConsumer consumer, boolean sparse)\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n\n\t@Override\n\tpublic StateValues deepCopy() throws PrismException\n\t{\n\t\tthrow new UnsupportedOperationException();\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/CheckBoxList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport java.awt.Component;\nimport java.awt.event.MouseAdapter;\nimport java.awt.event.MouseEvent;\n\nimport javax.swing.JCheckBox;\nimport javax.swing.JList;\nimport javax.swing.ListCellRenderer;\nimport javax.swing.ListSelectionModel;\nimport javax.swing.UIManager;\nimport javax.swing.border.Border;\nimport javax.swing.border.EmptyBorder;\n\n/**\n * Extension of JList containing JCheckBoxes.\n */\n@SuppressWarnings(\"serial\")\npublic class CheckBoxList extends JList\n{\n\tprotected static Border noFocusBorder = new EmptyBorder(1, 1, 1, 1);\n\n\tpublic CheckBoxList()\n\t{\n\t\tsetCellRenderer(new CellRenderer());\n\t\taddMouseListener(new MouseAdapter()\n\t\t{\n\t\t\tpublic void mousePressed(MouseEvent e)\n\t\t\t{\n\t\t\t\tint index = locationToIndex(e.getPoint());\n\t\t\t\tif (index != -1) {\n\t\t\t\t\tJCheckBox checkbox = (JCheckBox) getModel().getElementAt(index);\n\t\t\t\t\tcheckbox.setSelected(!checkbox.isSelected());\n\t\t\t\t\trepaint();\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\tsetSelectionMode(ListSelectionModel.SINGLE_SELECTION);\n\t}\n\n\tprotected class CellRenderer implements ListCellRenderer\n\t{\n\t\tpublic Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus)\n\t\t{\n\t\t\tJCheckBox checkbox = (JCheckBox) value;\n\t\t\tcheckbox.setBackground(isSelected ? getSelectionBackground() : getBackground());\n\t\t\tcheckbox.setForeground(isSelected ? getSelectionForeground() : getForeground());\n\t\t\tcheckbox.setEnabled(isEnabled());\n\t\t\tcheckbox.setFont(getFont());\n\t\t\tcheckbox.setFocusPainted(false);\n\t\t\tcheckbox.setBorderPainted(true);\n\t\t\tcheckbox.setBorder(isSelected ? UIManager.getBorder(\"List.focusCellHighlightBorder\") : noFocusBorder);\n\t\t\treturn checkbox;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIClipboard.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport java.awt.Toolkit;\nimport java.awt.datatransfer.Clipboard;\nimport java.awt.datatransfer.FlavorEvent;\nimport java.awt.datatransfer.FlavorListener;\nimport java.awt.event.*;\nimport javax.swing.*;\n\nimport userinterface.util.*;\n\n/**\n * This class gets notified through pluginChanged when the plugin in\n * focus has changed. The undo/redo actions can be implemented cleanly\n * by implementing the getUndoManager() function in GUIPlugin. Once this \n * is done it should work automatically, including enabledness of these actions.\n * \n * The clipboard functions paste/copy/cut/select all/delete work slightly more\n * complicated. This class listens on the focussed plugin's selectionChangeManager \n * and calls canDoClipboardFunction on this plugin to determine enabledness. \n * There is no need to pass changes in the clipboard state to the \n * selectionChangeManager, as this is done automatically. Hence, only notify when \n * a change in selection occurs.\n * \n * All actions can be and should be used as menu items.\n */\npublic class GUIClipboard extends GUIPlugin\n{\n\t/* the current GUIPlugin undoManager */\n\tprivate GUIPrism prism;\n\tprivate GUIPlugin plugin;\n\tprivate GUIUndoManager undoManager;\n    private JMenu editMenu;\n    private JToolBar editToolBar;\n    private Action actionUndo, actionRedo, actionCut, actionCopy, actionPaste, actionDelete, actionSelectAll;\n        \n    /** Creates a new instance of GUIClipboard */\n    public GUIClipboard(GUIPrism pr)\n    {\n        super(pr, false);\n        this.prism = pr;\n        initComponents();\n        doUndoManagerEnables();\n        doClipboardEnables();\n        \n        /* Listen to clipboard events. */\n        Clipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();\n        clipboard.addFlavorListener(new FlavorListener() {\n        \tpublic void flavorsChanged(FlavorEvent e) {\n        \t\tdoClipboardEnables();\n        \t}\n        });\n    }\n    \n    /* gets called when plugin changes. should implement this as an\n     * GUIEvent really */\n    public void pluginChanged(GUIPlugin plugin)\n    {\n    \tif (plugin != null)\n    \t\tplugin.getSelectionChangeHandler().clear();\n    \t\n    \t// remove listener\n\t\tif (undoManager != null)\n\t\t\tundoManager.clear();\n\t\t\n\t\tthis.plugin = null;\n\t\tthis.undoManager = null;\t\t\n\t\t\n    \tif (plugin != null)\n    \t{\n    \t\tthis.plugin = plugin;\n    \t\t/* get notified when enabledness of clipboard actions may change */\n    \t\tthis.plugin.getSelectionChangeHandler().addListener(new GUIEventListener() {\n    \t\t\tpublic boolean processGUIEvent(GUIEvent e) {\n    \t\t\t\tdoClipboardEnables();\n    \t\t\t\treturn true;\n    \t\t\t}\n    \t\t});    \n    \t\t\n    \t\tif (plugin.getUndoManager() != null)\n    \t\t{\n    \t\t\tundoManager = plugin.getUndoManager();\n\t    \t\t\n\t    \t\t/* get notified when undo history may change */\n\t    \t\tundoManager.addListener(new GUIEventListener() {\n\t    \t\t\tpublic boolean processGUIEvent(GUIEvent e) {\n\t    \t\t\t\tif (e instanceof GUIUndoManagerEvent)\n\t    \t\t\t\t{\n\t    \t\t\t\t\tdoUndoManagerEnables();\n\t    \t\t\t\t\treturn true;\n\t    \t\t\t\t}\n\t    \t\t\t\t\n\t    \t\t\t\treturn false;    \t\t\t\t\t\n\t    \t\t\t}\n\t    \t\t});\n    \t\t}\n    \t}\n    \t\n    \tdoUndoManagerEnables();\n    \tdoClipboardEnables();\n    }\n    \n\tprivate void doClipboardEnables() \n\t{ \n\t\tactionCopy.setEnabled(plugin != null && plugin.canDoClipBoardAction(actionCopy));\n\t\tactionCut.setEnabled(plugin != null && plugin.canDoClipBoardAction(actionCut));\n\t\tactionPaste.setEnabled(plugin != null && plugin.canDoClipBoardAction(actionPaste));\n\t\tactionDelete.setEnabled(plugin != null && plugin.canDoClipBoardAction(actionDelete));\n\t\tactionSelectAll.setEnabled(plugin != null && plugin.canDoClipBoardAction(actionSelectAll));\t\t\n\t}\n\n\tpublic void takeCLArgs(String args[])\n\t{\n\t}\n    \n    public boolean displaysTab()\n    {\n        return false;\n    }\n    \n    public javax.swing.JMenu getMenu()\n    {\n        return editMenu;\n    }\n    \n    public String getTabText()\n    {\n        return \"\";\n    }\n    \n    public javax.swing.JToolBar getToolBar()\n    {\n        return editToolBar;\n    }\n    \n    public String getXMLIDTag()\n    {\n        return null;\n    }\n    \n    public Object getXMLSaveTree()\n    {\n        return null;\n    }\n    \n    public void loadXML(Object c)\n    {\n    }\n    \n    public boolean processGUIEvent(GUIEvent e)\n    {\n\t\treturn false;\n    }\n    \n    public void doUndoManagerEnables()\n    {\n    \tactionUndo.setEnabled(undoManager != null && undoManager.canUndo());\n    \tactionRedo.setEnabled(undoManager != null && undoManager.canRedo());\n    }\n    \n    private void initComponents()\n    {\n        setupActions();\n        editMenu = new javax.swing.JMenu();\n        {\n        \teditMenu.setMnemonic(KeyEvent.VK_E);\n            editMenu.setText(\"Edit\");\n            \n            editMenu.add(new JMenuItem(actionUndo));\n            editMenu.add(new JMenuItem(actionRedo));\n            editMenu.add(new JSeparator());\n            editMenu.add(new JMenuItem(actionCut));\n            editMenu.add(new JMenuItem(actionCopy));\n            editMenu.add(new JMenuItem(actionPaste));\n            editMenu.add(new JMenuItem(actionDelete));\n            editMenu.add(new JSeparator());\n            editMenu.add(new JMenuItem(actionSelectAll));\n        }\n        \n        editToolBar = new JToolBar();\n        {\n        \t\n    \tJButton b6 = new JButton(actionUndo);\n\t    b6.setToolTipText(\"Undo\");\n\t    b6.setText(\"\");\n\t    editToolBar.add(b6);\n\t    \n\t    JButton b7 = new JButton(actionRedo);\n\t    b7.setToolTipText(\"Redo\");\n\t    b7.setText(\"\");\n\t    editToolBar.add(b7);\n\t    \n\t    //editToolBar.add(new JSeparator());\n        \t\n\t    JButton b1 = new JButton(actionCut);\n\t    b1.setToolTipText(\"Cut\");\n\t    b1.setText(\"\");\n\t    \n\t    editToolBar.add(b1);\n\t    \n\t    JButton b2 = new JButton(actionCopy);\n\t    b2.setToolTipText(\"Copy\");\n\t    b2.setText(\"\");\n\t    editToolBar.add(b2);\n\t    \n\t    JButton b3 = new JButton(actionPaste);\n\t    b3.setToolTipText(\"Paste\");\n\t    b3.setText(\"\");\n\t    editToolBar.add(b3);\n\t    \n\t    JButton b4 = new JButton(actionDelete);\n\t    b4.setToolTipText(\"Delete\");\n\t    b4.setText(\"\");\n\t    editToolBar.add(b4);\n\t    \n\t    //editToolBar.add(new JSeparator());\n\t    \n\t    JButton b5 = new JButton(actionSelectAll);\n\t    b5.setToolTipText(\"Select all\");\n\t    b5.setText(\"\");\n\t    editToolBar.add(b5);\n        }\n        editToolBar.setFloatable(false);\n    }\n    \n    /* Send GUIClipboardEvents to the focussed GUIPlugin */\n    \n    private void setupActions()\n    {\n    \tactionUndo = new AbstractAction()\n        {\n            public void actionPerformed(ActionEvent e)\n            {\n                notifyEventListeners(new GUIClipboardEvent(GUIClipboardEvent.UNDO, getFocussedComponent()));\n            }\n        };\n        actionUndo.putValue(Action.LONG_DESCRIPTION, \"Undo the last edit.\");\n        actionUndo.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_U));\n        actionUndo.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_Z, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        actionUndo.putValue(Action.NAME, \"Undo\");\n        actionUndo.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallUndo.png\"));\n        \n        actionRedo = new AbstractAction()\n        {\n            public void actionPerformed(ActionEvent e)\n            {\n                notifyEventListeners(new GUIClipboardEvent(GUIClipboardEvent.REDO, getFocussedComponent()));\n            }\n        };\n        actionRedo.putValue(Action.LONG_DESCRIPTION, \"Redo the last edit.\");\n        actionRedo.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_R));\n        actionRedo.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_Y, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        actionRedo.putValue(Action.NAME, \"Redo\");\n        actionRedo.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallRedo.png\"));\n       \n    \t\n        actionCut = new AbstractAction()\n        {\n            public void actionPerformed(ActionEvent e)\n            {\n                notifyEventListeners(new GUIClipboardEvent(GUIClipboardEvent.CUT, getFocussedComponent()));\n            }\n        };\n        actionCut.putValue(Action.LONG_DESCRIPTION, \"Copys the currently selected item/text to the clipboard and then removes it.\");\n        actionCut.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_C));\n        actionCut.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_X, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        actionCut.putValue(Action.NAME, \"Cut\");\n        actionCut.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallCut.png\"));\n         \n        actionCopy = new AbstractAction()\n        {\n            public void actionPerformed(ActionEvent e)\n            {\n                 notifyEventListeners(new GUIClipboardEvent(GUIClipboardEvent.COPY, getFocussedComponent()));\n            }\n        };\n        actionCopy.putValue(Action.LONG_DESCRIPTION, \"Copys the currently selected item/text to the clipboard.\");\n        actionCopy.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_O));\n        actionCopy.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_C, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        actionCopy.putValue(Action.NAME, \"Copy\");\n        actionCopy.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallCopy.png\"));\n                \n        actionPaste = new AbstractAction()\n        {\n            public void actionPerformed(ActionEvent e)\n            {\n                notifyEventListeners(new GUIClipboardEvent(GUIClipboardEvent.PASTE, getFocussedComponent()));\n            }\n        };\n        actionPaste.putValue(Action.LONG_DESCRIPTION, \"Pastes the contents of the clipboard.\");\n        actionPaste.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_P));\n        actionPaste.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_V, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        actionPaste.putValue(Action.NAME, \"Paste\");\n        actionPaste.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPaste.png\"));\n              \n        \n        actionDelete = new AbstractAction()\n        {\n            public void actionPerformed(ActionEvent e)\n            {\n                notifyEventListeners(new GUIClipboardEvent(GUIClipboardEvent.DELETE, getFocussedComponent()));\n            }\n        };\n        actionDelete.putValue(Action.LONG_DESCRIPTION, \"Removes the currently selected item\");        \n        actionDelete.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_D));\n        actionDelete.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_D, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        actionDelete.putValue(Action.NAME, \"Delete\");\n        actionDelete.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDelete.png\"));\n        \n        actionSelectAll = new AbstractAction()\n        {\n            public void actionPerformed(ActionEvent e)\n            {\n                notifyEventListeners(new GUIClipboardEvent(GUIClipboardEvent.SELECT_ALL, getFocussedComponent()));\n            }\n        };\n        actionSelectAll.putValue(Action.LONG_DESCRIPTION, \"Selects all items of the focussed component.\");\n        actionSelectAll.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n        actionSelectAll.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_A, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        actionSelectAll.putValue(Action.NAME, \"Select all\");\n        actionSelectAll.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSelectAll.png\"));     \n    }\n    \n    public void notifySettings(prism.PrismSettings settings)\n    {}\n\n    public Action getUndoAction() {\n\t\treturn actionUndo;\n\t}\n    \n\tpublic Action getRedoAction() {\n\t\treturn actionRedo;\n\t}\n\n\tpublic Action getCutAction() {\n\t\treturn actionCut;\n\t}\n\n\tpublic Action getCopyAction() {\n\t\treturn actionCopy;\n\t}\n\n\tpublic Action getPasteAction() {\n\t\treturn actionPaste;\n\t}\n\n\tpublic Action getDeleteAction() {\n\t\treturn actionDelete;\n\t}\n\n\tpublic Action getSelectAllAction() {\n\t\treturn actionSelectAll;\n\t}\n\n\t\n\t\n\t\n\t\n\t\n    \n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIClipboardEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport java.awt.*;\n\nimport userinterface.util.*;\n\npublic class GUIClipboardEvent extends GUIEvent\n{\n    public static final int COPY = 0;\n    public static final int CUT = 1;\n    public static final int PASTE = 2;\n    public static final int DELETE = 3;\n    public static final int SELECT_ALL = 4;\n    public static final int UNDO = 5;\n    public static final int REDO = 6;    \n    \n    static int counter =0;\n    /** Creates a new instance of GUIClipboardEvent */\n    public GUIClipboardEvent(int id, GUIPlugin comp)\n    {\n        super(id, comp);\n        counter++;\n        //System.out.println(\"clipboard event \"+counter);\n    }\n    \n    public Component getComponent()\n    {\n        return (GUIPlugin)getData();\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIComputationThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport common.StackTraceHelper;\nimport prism.*;\n\n/**\n * Class providing a few convenience methods for the various computation/*Thread classes.\n */\npublic class GUIComputationThread extends Thread\n{\n\tprotected GUIPlugin plug;\n\tprotected Prism prism;\n\n\t/** Limit on number of lines for logging a stack trace */\n\tprotected int STACK_TRACE_LIMIT = StackTraceHelper.DEFAULT_STACK_TRACE_LIMIT;\n\n\t/** Creates a new instance of GUIComputationThread */\n\tpublic GUIComputationThread(GUIPlugin plug)\n\t{\n\t\tthis.plug = plug;\n\t\tprism = plug.getPrism();\n\t}\n\t\n\t/** Report an error (in log and popup dialog) */\n\tpublic void error(String s)\n\t{\n\t\terrorLog(s);\n\t\terrorDialog(s);\n\t}\n\n\t/**\n\t * Report an error for an Exception/Error/Throwable (in log and popup dialog).\n\t * <br>\n\t * In case of a serious error that is unlikely to be recovered from\n\t * (i.e., an Error that is not a StackOverflowError), rethrow the error.\n\t */\n\tpublic void error(Throwable e) {\n\t\tif (e instanceof jdd.JDD.CuddOutOfMemoryException) {\n\t\t\terror(e.getMessage()+\".\\nTry increasing the value of \\\"CUDD max. memory\\\" in the options and then restart PRISM\");\n\t\t} else if (e instanceof PrismException) {\n\t\t\terror(e.getMessage());\n\t\t} else if (e instanceof StackOverflowError) {\n\t\t\tString hint = \"\\nTry increasing the value of the Java stack size (via the -javastack argument)\";\n\n\t\t\t// use message with stack trace for log\n\t\t\terrorLog(e.toString() + \"\\n\" + StackTraceHelper.asString(e, STACK_TRACE_LIMIT) + hint);\n\n\t\t\t// use short message, without stack trace, for dialog\n\t\t\terrorDialog(e.toString() + hint);\n\t\t} else {\n\t\t\terror(e.toString()+\"\\nThis is an unexpected error, it might be a good idea to restart PRISM\");\n\t\t}\n\n\t\t// for a serious error, i.e., derived from Error, except stack overflow, rethrow the error\n\t\tif (e instanceof Error && !(e instanceof StackOverflowError)) {\n\t\t\tthrow (Error)e;\n\t\t}\n\t}\n\n\t/** Report an error (in log) */\n\tpublic void errorLog(String s)\n\t{\n\t\tlogln(\"\\nError: \" + s + \".\");\n\t}\n\n\t/** Report an Exception/Throwable error (in log) */\n\tpublic void errorLog(Throwable e)\n\t{\n\t\tif (e instanceof PrismException || e instanceof jdd.JDD.CuddOutOfMemoryException) {\n\t\t\tlogln(\"\\nError: \" + e.getMessage() + \".\");\n\t\t} else {\n\t\t\tlogln(\"\\nError: \" + e.toString() +\".\");\n\t\t}\n\t}\n\n\t\n\t// send messages to log\n\tpublic void log(Object o) { plug.log(o); }\n\tpublic void log(int i) { plug.log(i); }\n\tpublic void log(double d) { plug.log(d); }\n\tpublic void log(float f) { plug.log(f); }\n\tpublic void log(short s) { plug.log(s); }\n\tpublic void log(byte b) { plug.log(b); }\n\tpublic void log(boolean b) { plug.log(b); }\n\tpublic void logln() { plug.logln(); }\n\tpublic void logln(Object o) { plug.logln(o); }\n\tpublic void logln(int i) { plug.logln(i); }\n\tpublic void logln(double d) { plug.logln(d); }\n\tpublic void logln(float f) { plug.logln(f); }\n\tpublic void logln(short s) { plug.logln(s); }\n\tpublic void logln(byte b) { plug.logln(b); }\n\tpublic void logln(boolean b) { plug.logln(b); }\n\tpublic void logSeparator() { plug.logSeparator(); }\n\tpublic void logWarning(String s) { plug.logWarning(s); }\n\t\n\t/** pop up an error dialog */\n\tpublic void errorDialog(String s)\n\t{\n\t\tplug.error(s);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIConstantsPicker.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel5\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Component class=\"javax.swing.JLabel\" name=\"jLabel1\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Please define the following constants:\"/>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n        </Component>\n        <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel6\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n        <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n      </Layout>\n      <SubComponents>\n        <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n          </Events>\n        </Component>\n        <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n          </Events>\n        </Component>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/GUIConstantsPicker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport java.awt.BorderLayout;\nimport java.awt.Dimension;\nimport java.util.ArrayList;\n\nimport javax.swing.Action;\nimport javax.swing.BoxLayout;\nimport javax.swing.DefaultListSelectionModel;\nimport javax.swing.JPanel;\nimport javax.swing.JScrollPane;\nimport javax.swing.JTable;\nimport javax.swing.border.TitledBorder;\nimport javax.swing.table.AbstractTableModel;\n\nimport parser.Values;\nimport prism.PrismException;\nimport prism.UndefinedConstants;\n\npublic class GUIConstantsPicker extends javax.swing.JDialog\n{\n\tpublic static final int NO_VALUES = 0;\n\tpublic static final int VALUES_DONE = 1;\n\tpublic static final int CANCELLED = 2;\n\t\n\tprivate boolean cancelled = true;\n\t\n\tprivate JTable propTable;\n\tprivate DefineConstantTable propTableModel;\n\tprivate JTable modelTable;\n\tprivate DefineConstantTable modelTableModel;\n\t\n\tprivate boolean areModel, areProp;\n\t\n\tprivate Action okAction;\n\tprivate Action cancelAction;\n\t\n\tprivate javax.swing.JButton okayButton;\n\t\n\tprivate UndefinedConstants undef;\n\t\n\tprivate GUIPrism gui;\n\t\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tjavax.swing.JPanel topPanel;\n\t// End of variables declaration//GEN-END:variables\n\n\t/** Creates new form GUIConstantsPicker */\n\tpublic GUIConstantsPicker(GUIPrism parent, UndefinedConstants undef, boolean areModel, boolean areProp, Values modelDefaults, Values propDefaults)\n\t{\n\t\tsuper(parent, \"Define Constants\", true);\n\t\tthis.areModel = areModel;\n\t\tthis.areProp  = areProp;\n\t\tthis.undef = undef;\n\t\tthis.gui = parent;\n\t\t\n\t\t//setup tables\n\t\tpropTableModel = new DefineConstantTable();\n\t\tmodelTableModel = new DefineConstantTable();\n\t\tpropTable = new JTable();\n\t\tmodelTable = new JTable();\n\t\tpropTable.setModel(propTableModel);\n\t\tmodelTable.setModel(modelTableModel);\n\t\tpropTable.setSelectionMode(DefaultListSelectionModel.SINGLE_INTERVAL_SELECTION);\n\t\tmodelTable.setSelectionMode(DefaultListSelectionModel.SINGLE_INTERVAL_SELECTION);\n\t\tpropTable.setCellSelectionEnabled(true);\n\t\tmodelTable.setCellSelectionEnabled(true);\n\t\tpropTable.setRowHeight(getFontMetrics(propTable.getFont()).getHeight() + 4);\n\t\tmodelTable.setRowHeight(getFontMetrics(modelTable.getFont()).getHeight() + 4);\n\t\t\n\t\t//initialise\n\t\tinitComponents();\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\t\tinitTables(areModel, areProp);\n\t\tinitValues(undef, modelDefaults, propDefaults);\n\t\t\n\t\tsetResizable(false);\n\t\t\n\t\tpack();\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t}\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\tprivate void initComponents()//GEN-BEGIN:initComponents\n\t{\n\t\tjavax.swing.JButton cancelButton;\n\t\tjava.awt.GridBagConstraints gridBagConstraints;\n\t\tjavax.swing.JLabel jLabel1;\n\t\tjavax.swing.JPanel jPanel1;\n\t\tjavax.swing.JPanel jPanel2;\n\t\tjavax.swing.JPanel jPanel3;\n\t\tjavax.swing.JPanel jPanel4;\n\t\tjavax.swing.JPanel jPanel5;\n\t\tjavax.swing.JPanel jPanel6;\n\t\t\n\t\t\n\t\tjPanel1 = new javax.swing.JPanel();\n\t\tjPanel2 = new javax.swing.JPanel();\n\t\tjPanel3 = new javax.swing.JPanel();\n\t\tjPanel4 = new javax.swing.JPanel();\n\t\tjPanel5 = new javax.swing.JPanel();\n\t\tjLabel1 = new javax.swing.JLabel();\n\t\ttopPanel = new javax.swing.JPanel();\n\t\tjPanel6 = new javax.swing.JPanel();\n\t\tokayButton = new javax.swing.JButton();\n\t\tcancelButton = new javax.swing.JButton();\n\t\t\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\t\t\n\t\tjPanel1.setLayout(new java.awt.GridBagLayout());\n\t\t\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel1.add(jPanel2, gridBagConstraints);\n\t\t\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel1.add(jPanel3, gridBagConstraints);\n\t\t\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 2;\n\t\tjPanel1.add(jPanel4, gridBagConstraints);\n\t\t\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 4;\n\t\tjPanel1.add(jPanel5, gridBagConstraints);\n\t\t\n\t\tjLabel1.setText(\"Please define the following constants:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(jLabel1, gridBagConstraints);\n\t\t\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 3;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tjPanel1.add(topPanel, gridBagConstraints);\n\t\t\n\t\tgetContentPane().add(jPanel1, java.awt.BorderLayout.CENTER);\n\t\t\n\t\tjPanel6.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\t\t\n\t\tokayButton.setText(\"Okay\");\n\t\tokayButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\tokayButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\t\t\n\t\tjPanel6.add(okayButton);\n\t\t\n\t\tcancelButton.setText(\"Cancel\");\n\t\tcancelButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\tcancelButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\t\t\n\t\tjPanel6.add(cancelButton);\n\t\t\n\t\tgetContentPane().add(jPanel6, java.awt.BorderLayout.SOUTH);\n\t\t\n\t\tpack();\n\t}//GEN-END:initComponents\n\n\tprivate void initTables(boolean areModel, boolean areProp)\n\t{\n\t\tif(areModel && areProp)\n\t\t\t{\n\t\t\t\ttopPanel.setLayout(new BoxLayout(topPanel, BoxLayout.Y_AXIS));\n\t\t\t\tJPanel topTopPanel = new JPanel();\n\t\t\t\ttopTopPanel.setBorder(new TitledBorder(\"Model Constants\"));\n\t\t\t\ttopTopPanel.setLayout(new BorderLayout());\n\t\t\t\tJScrollPane sp = new JScrollPane();\n\t\t\t\t\n\t\t\t\tsp.setViewportView(modelTable);\n\t\t\t\ttopTopPanel.add(sp);\n\t\t\t\tJPanel bottomTopPanel = new JPanel();\n\t\t\t\tbottomTopPanel.setBorder(new TitledBorder(\"Property Constants\"));\n\t\t\t\tbottomTopPanel.setLayout(new BorderLayout());\n\t\t\t\tJScrollPane sp2 = new JScrollPane();\n\t\t\t\t\n\t\t\t\tsp2.setViewportView(propTable);\n\t\t\t\tbottomTopPanel.add(sp2);\n\t\t\t\ttopPanel.add(topTopPanel);\n\t\t\t\ttopPanel.add(bottomTopPanel);\n\t\t\t}\n\t\t\telse if(areModel)\n\t\t\t{\n\t\t\t\ttopPanel.setBorder(new TitledBorder(\"Model Constants\"));\n\t\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\t\tJScrollPane sp = new JScrollPane();\n\t\t\t\tsp.setViewportView(modelTable);\n\t\t\t\ttopPanel.add(sp);\n\t\t\t}\n\t\t\telse if(areProp)\n\t\t\t{\n\t\t\t\ttopPanel.setBorder(new TitledBorder(\"Property Constants\"));\n\t\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\t\tJScrollPane sp = new JScrollPane();\n\t\t\t\tsp.setViewportView(propTable);\n\t\t\t\ttopPanel.add(sp);\n\t\t\t}\n\t\t\t\n\t\t\ttopPanel.setPreferredSize(new Dimension(500,200));\n\t}\n\n\tprivate void initValues(UndefinedConstants undef, Values modelDef, Values propDef)\n\t{\n\t\tfor(int i = 0; i < undef.getMFNumUndefined(); i++)\n\t\t{\n\t\t\tConstant c = new Constant(undef.getMFUndefinedName(i), undef.getMFUndefinedType(i), \"\");\n\t\t\tif(modelDef != null)\n\t\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\tObject o = modelDef.getValueOf(c.name);\n\t\t\t\tc.value = o;\n\t\t\t}\n\t\t\tcatch(Exception e)\n\t\t\t{}\n\t\t\t}\n\t\t\tmodelTableModel.addConstant(c);\n\t\t}\n\t\tfor(int i = 0; i < undef.getPFNumUndefined(); i++)\n\t\t{\n\t\t\tConstant c = new Constant(undef.getPFUndefinedName(i), undef.getPFUndefinedType(i), \"\");\n\t\t\tif(propDef != null)\n\t\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\tObject o = propDef.getValueOf(c.name);\n\t\t\t\tc.value = o;\n\t\t\t}\n\t\t\tcatch(Exception e)\n\t\t\t{}\n\t\t\t}\n\t\t\tpropTableModel.addConstant(c);\n\t\t}\n\t}\n\n\t/** Call this static method to construct a new GUIConstantsPicker to define\n\t *  undef.  If you don't want any default values, then pass in null for\n\t *  modelDefaults and propDefaults\n\t */\n\tpublic static int defineConstantsWithDialog(GUIPrism parent, UndefinedConstants undef, Values modelDefaults, Values propDefaults)\n\t{\n\t\tboolean areModel = undef.getMFNumUndefined() > 0;\n\t\tboolean areProp  = undef.getPFNumUndefined() > 0;\n\t\tif(areModel || areProp)\n\t\t{\n\t\t\treturn new GUIConstantsPicker(parent, undef, areModel, areProp, modelDefaults, propDefaults).defineValues();\n\t\t}\n\t\telse return NO_VALUES;\n\t}\n\n\tpublic int defineValues()\n\t{\n\t\tshow();\n\t\tif(cancelled) return CANCELLED;\n\t\telse return VALUES_DONE;\n\t}\n\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\tint i, n;\n\tConstant c;\n\t\n\tif(areProp && propTable.getCellEditor() != null)propTable.getCellEditor().stopCellEditing();\n\tif(areModel && modelTable.getCellEditor() != null)modelTable.getCellEditor().stopCellEditing();\n\ttry\n\t{\n\t\t//undef.defineUsingConstSwitch(getConstSwitch());\n\t\t\n\t\t// passing info to UndefinedConstants object\n\t\tn = modelTableModel.getNumConstants();\n\t\tfor (i = 0; i < n; i++)\n\t\t{\n\t\tc = modelTableModel.getConstant(i);\n\t\tundef.defineConstant(c.name, \"\"+c.value);\n\t\t}\n\t\tn = propTableModel.getNumConstants();\n\t\tfor (i = 0; i < n; i++)\n\t\t{\n\t\tc = propTableModel.getConstant(i);\n\t\tundef.defineConstant(c.name, \"\"+c.value);\n\t\t}\n\t\tundef.checkAllDefined();\n\t\tundef.initialiseIterators();\n\t\t\n\t\tcancelled = false;\n\t\tdispose();\n\t}\n\tcatch(PrismException e)\n\t{\n\t\tgui.errorDialog(e.getMessage());\n\t}\n\t}//GEN-LAST:event_okayButtonActionPerformed\n\n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\tdispose();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n\t\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\tsetVisible(false);\n\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\n\tclass DefineConstantTable extends AbstractTableModel\n\t{\n\tArrayList constants;\n\t\n\tpublic DefineConstantTable()\n\t{\n\t\tconstants = new ArrayList();\n\t}\n\t\n\tpublic void addConstant(Constant c)\n\t{\n\t\tconstants.add(c);\n\t\tfireTableRowsInserted(constants.size()-1, constants.size()-1);\n\t}\n\t\n\tpublic int getNumConstants()\n\t{\n\t\treturn constants.size();\n\t}\n\t\n\tpublic Constant getConstant(int i)\n\t{\n\t\treturn (Constant)constants.get(i);\n\t}\n\t\n\tpublic int getColumnCount()\n\t{\n\t\treturn 3;\n\t}\n\t\n\tpublic int getRowCount()\n\t{\n\t\treturn constants.size();\n\t}\n\t\n\tpublic Object getValueAt(int rowIndex, int columnIndex)\n\t{\n\t\t\n\t\tConstant c = (Constant)constants.get(rowIndex);\n\t\tswitch(columnIndex)\n\t\t{\n\t\tcase 0: return c.name;\n\t\tcase 1: return c.type.getTypeString();\n\t\tcase 2: return c.value.toString();\n\t\tdefault: return \"\";\n\t\t}\n\t}\n\t\n\tpublic String getColumnName(int columnIndex)\n\t{\n\t\tswitch(columnIndex)\n\t\t{\n\t\tcase 0: return \"Name\";\n\t\tcase 1: return \"Type\";\n\t\tcase 2: return \"Value\";\n\t\tdefault: return \"\";\n\t\t}\n\t}\n\t\n\tpublic boolean isCellEditable(int rowIndex, int columnIndex)\n\t{\n\t\tif(columnIndex == 2) return true;\n\t\telse return false;\n\t}\n\t\n\tpublic void setValueAt(Object aValue, int rowIndex, int columnIndex)\n\t{\n\t\tif(columnIndex == 2)\n\t\t{\n\t\tConstant c = (Constant)constants.get(rowIndex);\n\t\tString s = (String)aValue;\n\t\tc.value = s;\n\t\tfireTableCellUpdated(rowIndex, columnIndex);\n\t\t}\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\tString str = \"\";\n\t\tfor(int i = 0 ; i < constants.size(); i++)\n\t\t{\n\t\tConstant c = (Constant)constants.get(i);\n\t\tstr+=c.toString();\n\t\tif(i!= constants.size()-1) str+=\",\";\n\t\t}\n\t\treturn str;\n\t}\n\t\n\t}\n\t\n\tclass Constant\n\t{\n\tString name;\n\tparser.type.Type type;\n\tObject value;\n\t\n\tpublic Constant(String name, parser.type.Type type, Object value)\n\t{\n\t\tthis.name = name;\n\t\tthis.type = type;\n\t\tthis.value = value;\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn name+\"=\"+value.toString();\n\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIFileMenu.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport javax.swing.JMenu;\nimport javax.swing.Action;\nimport javax.swing.AbstractAction;\n\nimport java.awt.Toolkit;\nimport java.awt.event.*;\nimport javax.swing.*;\n\nimport userinterface.util.*;\n\npublic class GUIFileMenu extends GUIPlugin\n{\n    private JMenu menu;\n    private Action exitAction;\n    \n    public GUIFileMenu(GUIPrism pr)\n    {\n        super(pr, false);\n        initComponents();\n    }\n    \n\tpublic void takeCLArgs(String args[])\n\t{\n\t}\n    \n    public boolean displaysTab()\n    {\n        return false;\n    }\n    \n    public javax.swing.JMenu getMenu()\n    {\n        return menu;\n    }\n    \n    public String getTabText()\n    {\n        return \"\";\n    }\n    \n    public javax.swing.JToolBar getToolBar()\n    {\n        return null;\n    }\n    \n    public String getXMLIDTag()\n    {\n        return \"\";\n    }\n    \n    public Object getXMLSaveTree()\n    {\n        return null;\n    }\n    \n    public void loadXML(Object c)\n    {\n    }\n    \n    public boolean processGUIEvent(GUIEvent e)\n    {\n\t\treturn false;\n    }\n    \n    private void initComponents()\n    {\n        menu = new JMenu(\"File\");\n        menu.setMnemonic('F');\n        exitAction = new AbstractAction()\n        {\n            public void actionPerformed(ActionEvent e)\n            {\n                getGUI().exit();\n            }\n        };\n        exitAction.putValue(Action.LONG_DESCRIPTION, \"Exits the application\");\n        //exitAction.putValue(Action.SHORT_DESCRIPTION, \"Exit\");\n        exitAction.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_X));\n        exitAction.putValue(Action.NAME, \"Exit\");\n        exitAction.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallExit.png\"));\n        exitAction.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_Q, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        menu.add(exitAction);\n    }\n    \n    public void notifySettings(prism.PrismSettings settings)\n    {}\n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIOptionsDialog.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-6,0,0,1,-105\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JTabbedPane\" name=\"theTabs\">\n          <Properties>\n            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[400, 50]\"/>\n            </Property>\n            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[400, 500]\"/>\n            </Property>\n          </Properties>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\"/>\n        </Container>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[400, 35]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n            <Property name=\"alignment\" type=\"int\" value=\"0\"/>\n          </Layout>\n          <SubComponents>\n            <Component class=\"javax.swing.JButton\" name=\"defaultButton\">\n              <Properties>\n                <Property name=\"mnemonic\" type=\"int\" value=\"68\"/>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Load Defaults\"/>\n                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[220, 50]\"/>\n                </Property>\n              </Properties>\n              <Events>\n                <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"defaultButtonActionPerformed\"/>\n              </Events>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n              </AuxValues>\n            </Component>\n            <Component class=\"javax.swing.JButton\" name=\"saveSettingsButton\">\n              <Properties>\n                <Property name=\"mnemonic\" type=\"int\" value=\"83\"/>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Save Options\"/>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[120, 25]\"/>\n                </Property>\n              </Properties>\n              <Events>\n                <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"saveSettingsButtonActionPerformed\"/>\n              </Events>\n            </Component>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"East\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n            <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n          </Layout>\n          <SubComponents>\n            <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"OK\"/>\n                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[200, 50]\"/>\n                </Property>\n                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[80, 25]\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[80, 25]\"/>\n                </Property>\n              </Properties>\n              <Events>\n                <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n              </Events>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n              </AuxValues>\n            </Component>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/GUIOptionsDialog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\nimport java.util.*;\nimport javax.swing.*;\nimport prism.*;\nimport settings.*;\n\npublic class GUIOptionsDialog extends javax.swing.JDialog\n{\n\t\n\tprivate ArrayList panels;\n\tprivate PrismSettings settings;\n\t\n\t/** Creates new form GUIOptionsDialog */\n\tpublic GUIOptionsDialog(GUIPrism parent)\n\t{\n\t\tsuper(parent, true);\n\t\tsettings = parent.getPrism().getSettings();\n\t\tpanels = new ArrayList();\n\t\tinitComponents();\n\t\tthis.getRootPane().setDefaultButton(cancelButton);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t\t//setResizable(false);\n\t\t\n\t\tfor(int i = 0; i < settings.optionOwners.length; i++)\n\t\t{\n\t\t\tSettingTable table = new SettingTable(this);\n\t\t\t\n\t\t\tArrayList al = new ArrayList();\n\t\t\tsettings.optionOwners[i].setDisplay(table);\n\t\t\tal.add(settings.optionOwners[i]);\n\t\t\ttable.setOwners(al);\n\t\t\tpanels.add(table);\n\t\t\ttheTabs.add(table);\n\t\t\ttheTabs.setTitleAt(panels.indexOf(table), settings.propertyOwnerNames[i]);\n\t\t}\n\t}\n\t\n\tpublic void show()\n\t{\n\t\tsuper.show();\n\t}\n\t\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\tprivate void initComponents()//GEN-BEGIN:initComponents\n\t{\n\t\tjPanel1 = new javax.swing.JPanel();\n\t\ttheTabs = new javax.swing.JTabbedPane();\n\t\tjPanel2 = new javax.swing.JPanel();\n\t\tjPanel3 = new javax.swing.JPanel();\n\t\tdefaultButton = new javax.swing.JButton();\n\t\tsaveSettingsButton = new javax.swing.JButton();\n\t\tjPanel4 = new javax.swing.JPanel();\n\t\tcancelButton = new javax.swing.JButton();\n\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel1.setLayout(new java.awt.BorderLayout());\n\n\t\ttheTabs.setMinimumSize(new java.awt.Dimension(400, 50));\n\t\ttheTabs.setPreferredSize(new java.awt.Dimension(600, 500));\n\t\tjPanel1.add(theTabs, java.awt.BorderLayout.CENTER);\n\n\t\tgetContentPane().add(jPanel1, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel2.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel2.setMinimumSize(new java.awt.Dimension(400, 35));\n\t\tjPanel3.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.LEFT));\n\n\t\tdefaultButton.setMnemonic('D');\n\t\tdefaultButton.setText(\"Load Defaults\");\n\t\tdefaultButton.setMaximumSize(new java.awt.Dimension(220, 50));\n\t\tdefaultButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tdefaultButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel3.add(defaultButton);\n\n\t\tsaveSettingsButton.setMnemonic('S');\n\t\tsaveSettingsButton.setText(\"Save Options\");\n\t\tsaveSettingsButton.setPreferredSize(new java.awt.Dimension(120, 25));\n\t\tsaveSettingsButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tsaveSettingsButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel3.add(saveSettingsButton);\n\n\t\tjPanel2.add(jPanel3, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel4.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tcancelButton.setText(\"Okay\");\n\t\tcancelButton.setMaximumSize(new java.awt.Dimension(200, 50));\n\t\tcancelButton.setMinimumSize(new java.awt.Dimension(80, 25));\n\t\tcancelButton.setPreferredSize(new java.awt.Dimension(80, 25));\n\t\tcancelButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tcancelButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel4.add(cancelButton);\n\n\t\tjPanel2.add(jPanel4, java.awt.BorderLayout.EAST);\n\n\t\tgetContentPane().add(jPanel2, java.awt.BorderLayout.SOUTH);\n\t\t\n\t\tpack();\n\t}//GEN-END:initComponents\n\t\n\t\n\t\n\tprivate void saveSettingsButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_saveSettingsButtonActionPerformed\n\t{//GEN-HEADEREND:event_saveSettingsButtonActionPerformed\n\t\t\n\t\tsettings.notifySettingsListeners();\n\t\t\n\t\ttry\n\t\t{\n\t\t\tsettings.saveSettingsFile();\n\t\t}\n\t\tcatch(PrismException e)\n\t\t{\n\t\t\tGUIPrism.getGUI().errorDialog(\"Error saving settings:\\n\"+e.getMessage());\n\t\t}\n\t\t\n\t}//GEN-LAST:event_saveSettingsButtonActionPerformed\n\t\n\t\n\t\n\tprivate void defaultButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_defaultButtonActionPerformed\n\t{//GEN-HEADEREND:event_defaultButtonActionPerformed\n\t\t\n\t\tString[] selection =\n\t\t{\"Yes\", \"No\"};\n\t\tint selectionNo = -1;\n\t\t\n\t\tselectionNo = JOptionPane.showOptionDialog(this, \"Are you sure you wish to load the default settings?\\nAll previous settings will be lost.\", \"Save Settings\", JOptionPane.YES_NO_OPTION, JOptionPane.QUESTION_MESSAGE, null, selection, selection[0]);\n\t\tif (selectionNo == 0) {\n\t\t\tsettings.loadDefaults();\n\t\t\tsettings.notifySettingsListeners();\n\t\t}\n\t\t\n\t}//GEN-LAST:event_defaultButtonActionPerformed\n\t\n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\t\thide();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n\t\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\t\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tjavax.swing.JButton cancelButton;\n\tjavax.swing.JButton defaultButton;\n\tprivate javax.swing.JPanel jPanel1;\n\tprivate javax.swing.JPanel jPanel2;\n\tprivate javax.swing.JPanel jPanel3;\n\tprivate javax.swing.JPanel jPanel4;\n\tprivate javax.swing.JButton saveSettingsButton;\n\tjavax.swing.JTabbedPane theTabs;\n\t// End of variables declaration//GEN-END:variables\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIPlugin.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport java.awt.Dimension;\nimport java.io.File;\nimport java.util.Collection;\nimport java.util.Collections;\nimport java.util.List;\n\nimport javax.swing.Action;\nimport javax.swing.JFileChooser;\nimport javax.swing.JMenu;\nimport javax.swing.JOptionPane;\nimport javax.swing.JPanel;\nimport javax.swing.JToolBar;\nimport javax.swing.filechooser.FileFilter;\n\nimport prism.Prism;\nimport prism.PrismSettingsListener;\nimport userinterface.util.GUIEvent;\nimport userinterface.util.GUIEventHandler;\nimport userinterface.util.GUIEventListener;\nimport userinterface.util.GUILogEvent;\nimport userinterface.util.GUIUndoManager;\n\n/** This abstract class should be overridden to implement a component to be plugged\n * in to the PRISM GUI.  It extends JPanel so that it can be directly added to the\n * tabbed pane within a GUIPrism object.  A subclass should provide implementations for access\n * methods which will contain information concerning:\n * <UL>\n *\t<LI>Whether the plugin should be displayed as a tab,\n *\t<LI>The display text for that tab,\n *\t<LI>A Menu (added to the top of the GUI)\n *\t<LI>An Options Panel (added to the options dialog contained within the GUI)\n *\t<LI>Any File Filters\n * </UL>\n * A subclass should also be able to handle GUIEvents by implementing the\n * processGUIEvent method, which will be called whenever a GUIEvent is generated\n * via the event handler associated with the GUIPrism object.\n * <BR>\n * This class provides access to all utilities that may be\n * required by the components:\n * <UL>\n *\t<LI>Error messages\n *\t<LI>Message dialogs\n *\t<LI>Option dialogs\n *\t<LI>File choosers\n *\t<LI>Setting the taskbar text\n *\t<LI>Notifying other plugins of GUIEvents\n *\t<LI>Setting the state of the progress bar\n *\t<LI>Making log entries\n *\t<LI>Enabling this plugin\n *\t<LI>Switching this plugin to the front of the gui\n *\t<LI>Switching the log of the gui to the front\n * </UL>\n */\npublic abstract class GUIPlugin extends JPanel implements GUIEventListener, PrismSettingsListener\n{\n\tprivate static final long serialVersionUID = 1L;\n\t\n\t//ATTRIBUTES\n\tprivate GUIPrism gui;\n\tprivate Prism prism;\n\t\n\t/** Whenever the state of the cut/copy/delete/selectall buttons should change\n\t * notify this handler. This will in turn call the canDoClipBoardAction to\n\t * determine which buttons should be enabled.\n\t */\n\tprotected GUIEventHandler selectionChangeHandler;\n\t\n\t//CONSTRUCTORS\n\t\n\t/** This is the super constructor that all implementing subclasses should call, it\n\t * sets up the interaction with the top level GUI, and also optionally sets up the\n\t * interaction with the event\n\t * handler.\n\t * @param gui The parent GUI\n\t * @param listens Should this plugin listen to gui events?\n\t */\t\n\tpublic GUIPlugin(GUIPrism gui, boolean listens)\n\t{\n\t\tthis.gui = gui;\n\t\tthis.prism = gui.getPrism();\n\t\tselectionChangeHandler = new GUIEventHandler(gui);\n\t\tif(listens)gui.getEventHandler().addListener(this);\n\t\tsetPreferredSize(new Dimension(800,600));\n\t}\n\t\n\t\n\tpublic GUIEventHandler getSelectionChangeHandler() \n\t{\t\n\t\treturn selectionChangeHandler;\n\t}\n\n\n\n\t/** This is the super constructor that all implementing subclasses should call, it\n\t * sets up the interaction with the top level GUI, and also sets up the\n\t * interaction with the event\n\t * handler.\n\t * @param gui The parent GUI\n\t */\t\n\tpublic GUIPlugin(GUIPrism gui)\n\t{\n\t\tthis(gui, true);\n\t}\n\t\n\t//ACCESS METHODS\n\t\n\t/** Abstract access method to be implemented to return the text that should describe\n\t * this plugin in a tabbed environment.\n\t * @return The tab text for this plugin.\n\t */\t\n\tpublic abstract String getTabText();\n\t\n\t/** Abstract access method to be implemented to provide the JMenu object that should\n\t * be added to the top level GUI to provide menu functionality for this plugin.\n\t * If multiple menus are to be added, use getMenus() instead.\n\t * @return The JMenu to be displayed in the GUI.  Returns null if no menu is required\n\t */\t\n\tpublic abstract JMenu getMenu();\n\t\n\t/** Abstract access method to be implemented to provide the JMenu object that should\n\t * be added to the top level GUI to provide menu functionality for this plugin.\n\t * @return The JMenus to be displayed in the GUI.  Returns null if no menus are required\n\t */\n\tpublic List<JMenu> getMenus()\n\t{\n\t\t// Default implementation: just one menu\n\t\treturn Collections.singletonList(getMenu());\n\t}\n\t\n\t/** Abstract access method to be implemented to provide a toolbar to be displayed in\n\t * the top level GUI.\n\t * @return The toolbar to be displayed in the GUI.  Returns null if no toolbar is required.\n\t */\t\n\tpublic abstract JToolBar getToolBar();\n\t\n\t/** Returns an XML representation of this plugin, for use in saving the state of the\n\t * system to a file\n\t * @return The XML description\n\t * @deprecated This method was intended for use in projects.  Projects are no longer going to\n\t * be included in the project.\n\t */\n\t@Deprecated\n\tpublic abstract Object getXMLSaveTree();\n\t\n\t/** Returns an XML tag for this plugin\n\t * @return An XML tag\n\t * @deprecated This method was intended for use in projects.  Projects are no longer going to\n\t * be included in the project.\n\t */\n\t@Deprecated\n\tpublic abstract String getXMLIDTag();\n\t\n\t/** Returns a boolean stating whether this plugin should be displayed as a tab\n\t * within the top level GUI.\n\t * @return A boolean stating whether this plugin should be used as a tab.\n\t */\t\n\tpublic abstract boolean displaysTab();\n\t\n\t/** Utility access method to the Prism object stored within the top level user\n\t * interface.\n\t * @return The Prism Object.\n\t */\t\n\tpublic Prism getPrism()\n\t{\n\t\treturn prism;\n\t}\n\t\n\t/** Returns the top level user interface\n\t * @return the GUI.\n\t */\t\n\tpublic GUIPrism getGUI()\n\t{\n\t\treturn gui;\n\t}\n\t\n\t/** Returns the top level user interface\n\t * @return the GUI.\n\t */\t\n\tpublic GUIUndoManager getUndoManager()\n\t{\n\t\treturn null;\n\t}\n\t\t\n\t/** Determine whether or not this action should be enabled.\n\t * @param action An action in GUIClipboard (but not undo/redo).\n\t */\t\n\tpublic boolean canDoClipBoardAction(Action action)\n\t{\n\t\treturn false;\n\t}\t\n\t\n\t/** Utility access method to access which component is focussed in the top level\n\t * GUI.\n\t * @return The focussed component in the GUI.\n\t */\t\n\tpublic GUIPlugin getFocussedComponent()\n\t{\n\t\treturn gui.getFocussedPlugin();\n\t}\n\t\n\t/** Method to get the file selected by the filechooser\n\t * @return The file from the file chooser\n\t */\t\n\tpublic File getChooserFile()\n\t{\n\t\treturn gui.getChooser().getSelectedFile();\n\t}\n\t\n\t\n\t//UPDATE/UTILITY METHODS\n\t\n\t/** Do any initial actions, as rpompted by command-line args */\n\tpublic abstract void takeCLArgs(String args[]);\n\t\n\t/** When a GUIEvent is generated from some other GUIPlugin object or the parent\n\t * GUIPrism object, if this plugin has been assigned to listen to events, this\n\t * method is called.  It should be implemented to handle GUIEvents.  Note this\n\t * method will catch GUIEvents generated from this class, so be careful to avoid\n\t * recursive effects.\n\t * An implementation should return false by default,\n\t * unless the event should not be passed on to any more listeners,\n\t * in which case it should returns true.\n\t * @param e A GUIEvent from elsewhere in the userinterface.\n\t */\t\n\tpublic abstract boolean processGUIEvent(GUIEvent e);\n\n\t/**\n\t * Hook that is called for each GUIPlugin after the GUI startup has completed.\n\t */\n\tpublic void onInitComponentsCompleted()\n\t{\n\t\t// default: do nothing\n\t}\n\t\n\t/** Loads an XML tree stored in 'c'.\n\t * @param c The XML tree\n\t * @deprecated This method was intended for use in projects.  Projects are no longer going to\n\t * be included in the project.\n\t */\t\n\t@Deprecated\n\tpublic abstract void loadXML(Object c); //the object will be an xml parse tree\n\t\n\t/** A utility method which is simply a wrapper of the corresponding method in the\n\t * parent GUIPrism\n\t * @param title The title of the error dialog\n\t * @param message The message to be displayed in the error dialog.\n\t */\t\n\tpublic void error(String title, String message)\n\t{\n\t\tgui.errorDialog(title, \"Error: \" + message + \".\");\n\t}\n\t\n\t/** A utility method which is simply a wrapper of the corresponding method in the\n\t * parent GUIPrism\n\t * @param message The message to be displayed in the error dialog.\n\t */\t\n\tpublic void error(String message)\n\t{\n\t\tgui.errorDialog(\"Error: \" + message + \".\");\n\t}\n\t\n\t/** A utility method to display a message that is modal to the parent GUIPrism.\n\t * @param title The string to be displayed in the title of the dialog.\n\t * @param message An object containing the message to be displayed.\n\t */\t\n\tpublic void message(String title, Object message)\n\t{\n\t\tJOptionPane.showMessageDialog(gui, message, title, JOptionPane.INFORMATION_MESSAGE);\n\t}\n\t\n\t/** A utility method to display a message that is modal to the parent GUIPrism.\n\t * @param message An object containing the message to be displayed.\n\t */\t\n\tpublic void message(Object message)\n\t{\n\t\tmessage(\"Information\", message);\n\t}\n\t\n\t/** A utility method to display a warning message that is modal to the parent GUIPrism.\n\t * @param title The string to be displayed in the title of the dialog.\n\t * @param message An object containing the message to be displayed.\n\t */\t\n\tpublic void warning(String title, Object message)\n\t{\n\t\tJOptionPane.showMessageDialog(gui, \"Warning: \"+message+\".\", title, JOptionPane.WARNING_MESSAGE);\n\t}\n\t\n\t/** A utility method to display a warning message that is modal to the parent GUIPrism.\n\t * @param message An object containing the message to be displayed.\n\t */\t\n\tpublic void warning(Object message)\n\t{\n\t\twarning(\"Warning\", message);\n\t}\n\t\n\t/** A utility method to display a question dialog that is modal to the parent GUIPrism.\n\t * @param title The string to be displayed in the title of the dialog.\n\t * @param message An object containing the message to be displayed.\n\t */\t\n\tpublic int question(String title, Object message, Object[] options, int defaultOption)\n\t{\n\t\tif (defaultOption < 0 || defaultOption > options.length) defaultOption = 0;\n\t\tint res = JOptionPane.showOptionDialog(gui, message, title, JOptionPane.DEFAULT_OPTION , JOptionPane.QUESTION_MESSAGE, null, options, options[defaultOption]);\n\t\tif (res == JOptionPane.CLOSED_OPTION) return -1;\n\t\treturn res;\n\t}\n\t\n\tpublic int question(String title, Object message, Object[] options) { return question(title, message, options, 0); } \n\tpublic int question(Object message, Object[] options) { return question(\"Question\", message, options, 0); }\n\tpublic int question(Object message, Object[] options, int defaultOption) { return question(\"Question\", message, options, defaultOption); }\n\t\n\tpublic int questionYesNo(String title, Object message, int defaultOption)\n\t{\n\t\tString options[] = {\"Yes\", \"No\"};\n\t\treturn question(title, message, options, defaultOption);\n\t}\n\t\n\tpublic int questionYesNo(String title, Object message) { return questionYesNo(title, message, 0); } \n\tpublic int questionYesNo(Object message) { return questionYesNo(\"Question\", message, 0); }\n\tpublic int questionYesNo(Object message, int defaultOption) { return questionYesNo(\"Question\", message, defaultOption); }\n\t\n\t/** A utility method to display an option pane and return the resulting selection.\n\t * @param message The message to be displayed.\n\t * @param title The title of the option pane.\n\t * @param buttonType The type of button to be used.  Use JOptionPane button type constants.\n\t * @param messageType The type of message to be displayed. Use JOptionPane message type constants\n\t * @param choices A String Array of the choices to be placed on the buttons of the option pane.\n\t * @param defa The default selection string.\n\t * @return Returns the index of the selected button.  The index is the corresponding index\n\t * of the selection in 'choices'.\n\t */\t\n\tpublic int optionPane(String message, String title, int buttonType, int messageType, String[]choices, String defa)\n\t{\n\t\treturn JOptionPane.showOptionDialog(gui, message, title, buttonType, messageType, null, choices, defa);\n\t}\n\t\n\t/**\n\t * A utility method to show a file opening dialog with a specified file filter\n\t * \n\t * @param fileFilter The file filter to be used within the file chooser.\n\t * @return An integer which is one of the JFileChooser selection constants.\n\t */\t\n\tpublic int showOpenFileDialog(FileFilter fileFilter)\n\t{\n\t\treturn showOpenFileDialog(Collections.singletonList(fileFilter), fileFilter);\n\t}\n\t\n\t/**\n\t * A utility method to show a file opening dialog with a selection of file filters and one as the default.\n\t * \n\t * @param fileFilters The file filters to be used within the file chooser.\n\t * @param defaultFilter The file filter to be used as the default within the filechooser.\n\t * @return An integer which is one of the JFileChooser selection constants.\n\t */\t\n\tpublic int showOpenFileDialog(Collection<FileFilter> fileFilters, FileFilter defaultFilter)\n\t{\n\t\tJFileChooser choose = gui.getChooser();\n\t\tchoose.resetChoosableFileFilters();\n\t\tfor (FileFilter ff : fileFilters) {\n\t\t\tchoose.addChoosableFileFilter(ff);\n\t\t}\n\t\tchoose.setFileFilter(defaultFilter);\n\t\tchoose.setSelectedFile(new File(\"\"));\n\t\treturn choose.showOpenDialog(gui);\n\t}\n\t\n\t/**\n\t * A utility method to show a file saving dialog with a specified file filter\n\t * \n\t * @param fileFilter The file filter to be used within the file chooser.\n\t * @return An integer which is one of the JFileChooser selection constants.\n\t */\t\n\tpublic int showSaveFileDialog(FileFilter fileFilter)\n\t{\n\t\treturn showSaveFileDialog(Collections.singletonList(fileFilter), fileFilter);\n\t}\n\t\n\t/**\n\t * A utility method to show a file saving dialog with a selection of file filters and one as the default.\n\t * \n\t * @param fileFilters The file filters to be used within the file chooser.\n\t * @param defaultFilter The file filter to be used as the default within the filechooser.\n\t * @return An integer which is one of the JFileChooser selection constants.\n\t */\t\n\tpublic int showSaveFileDialog(Collection<FileFilter> fileFilters, FileFilter defaultFilter)\n\t{\n\t\tJFileChooser choose = gui.getChooser();\n\t\tchoose.resetChoosableFileFilters();\n\t\tfor (FileFilter ff : fileFilters) {\n\t\t\tchoose.addChoosableFileFilter(ff);\n\t\t}\n\t\tchoose.setFileFilter(defaultFilter);\n\t\tchoose.setSelectedFile(new File(\"\"));\n\t\tint res = choose.showSaveDialog(gui);\n\t\tif (res != JFileChooser.APPROVE_OPTION) return res;\n\t\tFile file = choose.getSelectedFile();\n\t\t// check file is non-null\n\t\tif (file == null) {\n\t\t\terror(\"No file selected\");\n\t\t\treturn JFileChooser.CANCEL_OPTION;\n\t\t}\n\t\t// check for file overwrite\n\t\tif (file.exists()) {\n\t\t\tint selectionNo = JOptionPane.CANCEL_OPTION;\n\t\t\tselectionNo = optionPane(\"File \\\"\"+file.getPath()+\"\\\" exists. Overwrite?\", \"Confirm Overwrite\", JOptionPane.OK_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE, null, null);\n\t\t\tif (selectionNo != JOptionPane.OK_OPTION) return JFileChooser.CANCEL_OPTION;\n\t\t}\n\t\treturn JFileChooser.APPROVE_OPTION;\n\t}\n\t\n\t/** A utility update method which calls the corresponding method in the parent\n\t * GUIPrism object.\n\t * @param message The message to be displayed on the taskbar.\n\t */\t\n\tpublic void setTaskBarText(String message)\n\t{\n\t\tgui.setTaskBarText(message);\n\t}\n\t\n\t/** Utility method to notify the event handler of a GUIEvent.\n\t * @param e The GUIEvent to be handled.\n\t */\t\n\tpublic void notifyEventListeners(GUIEvent e)\n\t{\n\t\tgui.notifyEventListeners(e);\n\t}\n\t\n\t/** Utility method that calls the corresponding method in the parent GUIPrism. */\t\n\tpublic void startProgress()\n\t{\n\t\tgui.startProgress();\n\t}\n\t\n\t/** Utility method that calls the corresponding method in the parent GUIPrism. */\t\n\tpublic void stopProgress()\n\t{\n\t\tgui.stopProgress();\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t */\t\n\tpublic void logln()\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(\"\"));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logln(Object message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logln(int message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logln(double message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logln(float message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logln(long message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logln(short message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logln(byte message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logln(boolean message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void log(Object message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINT, message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void log(int message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINT, message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void log(double message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINT, message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void log(float message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINT, message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void log(short message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINT, message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void log(byte message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINT, message));\n\t}\n\t\n\t/** Method to add an entry to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void log(boolean message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINT, message));\n\t}\n\t\n\t/** Utility method to change the enabled status of this GUIPlugin.\n\t * @param enabled Flag to state whether this plugin should be enabled or not.\n\t */\t\n\tpublic void setTabEnabled(boolean enabled)\n\t{\n\t\tgui.enableTab(this, enabled);\n\t}\n\t\n\t/** Method to add a separator to the log contained within the parent GUIPrism.\n\t */\t\n\tpublic void logSeparator()\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINTSEPARATOR, \"\"));\n\t}\n\t\n\t/** Method to add a warning message to the log contained within the parent GUIPrism.\n\t * @param message The message to be added to the log\n\t */\t\n\tpublic void logWarning(String message)\n\t{\n\t\tnotifyEventListeners(new GUILogEvent(GUILogEvent.PRINTWARNING, message));\n\t}\n\t\n\t/** Utility method to automatically jump this plugin to the front of the tabs\n\t * contained within the parent GUIPrism.\n\t */\t\n\tpublic void tabToFront()\n\t{\n\t\tgui.showTab(this);\n\t}\n\t\n\t/** Utility method to automatically jump to the log contained within the parent\n\t * GUIPrism.\n\t */\t\n\tpublic void logToFront()\n\t{\n\t\tgui.showLogTab();\n\t}\n\t\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIPrism.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\n//Java Packages\nimport java.awt.BorderLayout;\nimport java.awt.Component;\nimport java.awt.Dimension;\nimport java.awt.EventQueue;\nimport java.awt.FlowLayout;\nimport java.awt.Font;\nimport java.awt.Toolkit;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.InputEvent;\nimport java.awt.event.KeyEvent;\nimport java.io.File;\nimport java.io.IOException;\nimport java.net.URL;\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.Action;\nimport javax.swing.ImageIcon;\nimport javax.swing.JFileChooser;\nimport javax.swing.JFrame;\nimport javax.swing.JMenu;\nimport javax.swing.JMenuBar;\nimport javax.swing.JOptionPane;\nimport javax.swing.JPanel;\nimport javax.swing.JProgressBar;\nimport javax.swing.JTabbedPane;\nimport javax.swing.KeyStroke;\nimport javax.swing.SwingUtilities;\nimport javax.swing.UIManager;\nimport javax.swing.event.ChangeEvent;\nimport javax.swing.event.ChangeListener;\nimport javax.swing.plaf.FontUIResource;\nimport javax.swing.plaf.metal.MetalLookAndFeel;\nimport javax.swing.plaf.metal.MetalTheme;\n\nimport prism.Prism;\n//Prism Packages\nimport prism.PrismException;\nimport prism.PrismFileLog;\nimport prism.PrismLog;\nimport prism.PrismNative;\nimport userinterface.util.GUIComputationEvent;\nimport userinterface.util.GUIEvent;\nimport userinterface.util.GUIEventHandler;\nimport userinterface.util.GUIException;\nimport userinterface.util.GUIExitEvent;\nimport userinterface.util.PresentationMetalTheme;\n\n/**  PRISM Graphical User Interface\n *  This class is the top level class for the PRISM GUI. It acts as a container\n *  for GUIPlugin objects.  The method getPluginArray() is defined to allow any\n *  class that implements this interface to be added to the user interface.  The aim\n *  of this is to make transferral between different versions of the system easier.\n *  As a top level class, GUIPrism contains some utility methods, that can be used\n *  via the GUIPlugin class.  This class is also a container of a Prism object,\n *  which acts as the link between the user interface and the underlying PRISM code.\n */\npublic class GUIPrism extends JFrame\n{\n\t//CONSTANTS\n\t//defaults\n\t/** The default width of the main window */\n\tpublic static final int DEFAULT_WINDOW_WIDTH = 1024;\n\t/** The default height of the main window */\n\tpublic static final int DEFAULT_WINDOW_HEIGHT = 640;\n\t/** The minimum width of the main window */\n\tpublic static final int MINIMUM_WINDOW_WIDTH = 10;\n\t/** The minimum height of the main window. */\n\tpublic static final int MINIMUM_WINDOW_HEIGHT = 10;\n\n\t//STATIC MEMBERS\n\n\tprivate static GUIPrismSplash splash;\n\tprivate static GUIPrism gui;\n\tprivate boolean doExit;\n\tprivate static GUIClipboard clipboardPlugin;\n\n\t//STATIC METHODS\n\n\t/** The entry point of the program from the command line.\n\t * @param args the command line arguments\n\t */\n\tpublic static void main(String[] args)\n\t{\n\t\ttry {\n\t\t\t//Show the splash screen\n\t\t\tsplash = new GUIPrismSplash(\"images/splash.png\");\n\t\t\tsplash.display();\n\t\t\tgui = new GUIPrism(args);\n\t\t\tgui.setVisible(true);\n\t\t\tEventQueue.invokeLater(new GUIPrism.SplashScreenCloser());\n\t\t\tgui.passCLArgs();\n\t\t} catch (GUIException e) {\n\t\t\tSystem.err.println(\"Error: Could not load the PRISM GUI: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t} catch (PrismException e) {\n\t\t\tSystem.err.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t} catch (jdd.JDD.CuddOutOfMemoryException e) {\n\t\t\tSystem.err.println(\"Error: \" + e.getMessage());\n\t\t\tSystem.exit(1);\n\t\t}\n\t}\n\n\t/**\n\t * Define this method to add plugins to the GUI. Returns an ArrayList of Plugin objects.\n\t * @param g The instance of GUIPrism to associate with the GUIPlugin objects.\n\t * @return An ArrayList of GUIPlugins to be included in the user interface\n\t */\n\tpublic static ArrayList<GUIPlugin> getPluginArray(GUIPrism g)\n\t{\n\t\t// Plugins\n\t\tuserinterface.GUIFileMenu fileMenu;\n\t\tuserinterface.model.GUIMultiModel model;\n\t\tuserinterface.properties.GUIMultiProperties props;\n\t\tuserinterface.simulator.GUISimulator sim;\n\t\tuserinterface.log.GUILog log;\n\t\t// Create\n\t\tfileMenu = new userinterface.GUIFileMenu(g);\n\t\tclipboardPlugin = new GUIClipboard(g);\n\t\tmodel = new userinterface.model.GUIMultiModel(g);\n\t\tsim = new userinterface.simulator.GUISimulator(g);\n\t\tprops = new userinterface.properties.GUIMultiProperties(g, sim);\n\t\tlog = new userinterface.log.GUILog(g);\n\t\t// Add to list\n\t\tArrayList<GUIPlugin> plugs = new ArrayList<GUIPlugin>();\n\t\tplugs.add(fileMenu);\n\t\tplugs.add(clipboardPlugin);\n\t\tplugs.add(model);\n\t\tplugs.add(props);\n\t\tplugs.add(sim);\n\t\tplugs.add(log);\n\t\t// Make some plugins aware of others\n\t\tsim.setGUIMultiModel(model);\n\t\t// Return list\n\t\treturn plugs;\n\t}\n\n\tpublic static GUIPrism getGUI()\n\t{\n\t\treturn gui;\n\t}\n\n\t//ATTRIBUTES\n\t//properties\n\tprivate Prism prism;\n\tprivate PrismLog theLog;\n\t\n\t// command-line args to be passed on to components\n\tprivate String args[];\n\t// initial directory for file chooser (optional)\n\tprivate String chooserDir;\n\n\t//gui components\n\tprivate ArrayList<GUIPlugin> plugs;\n\tprivate JTabbedPane theTabs;\n\tprivate GUIPlugin logPlug;\n\tprivate GUIEventHandler eventHandle;\n\tprivate GUIOptionsDialog options;\n\tprivate JFileChooser choose;\n\tprivate JProgressBar progress;\n\tprivate GUITaskBar taskbar;\n\tprivate String taskbarText = \"\";\n\tprivate Action prismOptions;\n\tprivate Action fontIncrease;\n\tprivate Action fontDecrease;\n\n\t//CONSTRUCTORS AND INITIALISATION METHODS\n\n\t/** Creates a new instance of GUIPrism.  By calling setupResources(), setupPrism()\n\t * and then initComponents().\n\t * @throws GUIException Thrown if there is an error in initialising the user interface.\n\t */\n\tpublic GUIPrism() throws GUIException, PrismException\n\t{\n\t\tthis(new String[0]);\n\t}\n\n\t/** Creates a new instance of GUIPrism.  By calling setupResources(), setupPrism()\n\t * and then initComponents().\n\t * @throws GUIException Thrown if there is an error in initialising the user interface.\n\t */\n\tpublic GUIPrism(String args[]) throws GUIException, PrismException\n\t{\n\t\tsuper();\n\t\tthis.args = processCLArgs(args);\n\t\tsetupResources();\n\t\tsetupPrism();\n\t\tinitComponents();\n\t\tprism.getSettings().notifySettingsListeners();\n\t}\n\n\t/**\n\t *  Sets the URL for images properly, so that they are loaded from the\n\t *  correct directory.  This also loads in all of the resouces for\n\t *  internationalization support.  Also sets up the file chooser and event handler.\n\t *  Throws a GUIException if there is a problem with the resources.\n\t */\n\tprivate void setupResources() throws GUIException\n\t{\n\t\ttry {\n\t\t\tMetalTheme theme = new PresentationMetalTheme(0);\n\t\t\tMetalLookAndFeel.setCurrentTheme(theme);\n\t\t\tUIManager.setLookAndFeel(UIManager.getCrossPlatformLookAndFeelClassName());\n\t\t\t//UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());\n\t\t} catch (Exception e) {\n\t\t\tthrow new GUIException(\"Failed to Initialise:\\nLook and Feel Invalid\");\n\t\t}\n\n\t\t// Create new file chooser which starts in current directory\n\t\t// (or in the directory specified with command-line arg -dir)\n\t\tFile currentDir = new File(chooserDir == null ? \".\" : chooserDir);\n\t\t// If current directory is the bin directory, go up one level (mainly for Windows version)\n\t\ttry {\n\t\t\tcurrentDir = currentDir.getCanonicalFile();\n\t\t\tif (currentDir.getName().equals(\"bin\"))\n\t\t\t\tcurrentDir = currentDir.getParentFile();\n\t\t} catch (IOException e) {\n\t\t\tcurrentDir = new File(\".\");\n\t\t}\n\t\t// create the chooser\n\t\tchoose = new JFileChooser(currentDir);\n\n\t\tlogPlug = null;\n\t\teventHandle = new GUIEventHandler(this);\n\n\t\t//Load resources here\n\t\t/********************/\n\t\t//This will provide for internationalisation support, if necessary\n\t\t//optimism zone\n\t}\n\n\tprivate void setupPrism() throws PrismException\n\t{\n\t\ttheLog = new userinterface.log.GUIWindowLog();\n\t\tprism = new Prism(theLog);\n\t\tprism.loadUserSettingsFile();\n\t\tprism.initialise();\n\t}\n\n\t/**\n\t *  This initialises all of the graphical user interface componenets.\n\t *  The structure of the user interface should be\n\t *  <UL>\n\t *\t  <LI>Menu Bar at the Top\n\t *\t  <LI>Toolbar just below\n\t *\t  <LI>Tabs with all of the pluggable \"screens\"\n\t *\t  <LI>Status Bar at the bottom\n\t *  </UL>\n\t */\n\tprivate void initComponents() throws GUIException\n\t{\n\t\tJMenuBar menuBar = new JMenuBar();\n\t\tJPanel toolPanel = new JPanel();\n\t\ttoolPanel.setLayout(new FlowLayout(FlowLayout.LEFT));\n\t\toptions = new GUIOptionsDialog(this);\n\t\t//options.addPanel(new GUIPrismOptionsPanel(prism));\n\t\tJPanel thePanel = new JPanel(); // panel to store tabs\n\t\ttheTabs = new JTabbedPane();\n\t\ttheTabs.addChangeListener(new ChangeListener()\n\t\t{\n\t\t\tpublic void stateChanged(ChangeEvent e)\n\t\t\t{\n\t\t\t\tclipboardPlugin.pluginChanged(getFocussedPlugin());\n\t\t\t}\n\t\t});\n\t\t//Setup pluggable screens in here\n\t\tplugs = getPluginArray(this);\n\t\tfor (GUIPlugin plug : plugs) {\n\t\t\tif (plug.displaysTab()) {\n\t\t\t\ttheTabs.addTab(plug.getTabText(), plug);\n\t\t\t\ttheTabs.setEnabledAt(theTabs.getComponentCount() - 1, plug.isEnabled());\n\t\t\t}\n\t\t\tif (plug.getMenus() != null) {\n\t\t\t\tfor (JMenu menu : plug.getMenus()) {\n\t\t\t\t\tif (menu != null) {\n\t\t\t\t\t\tmenuBar.add(menu);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (plug.getToolBar() != null) {\n\t\t\t\ttoolPanel.add(plug.getToolBar());\n\t\t\t}\n\t\t\tif (plug instanceof userinterface.log.GUILog) {\n\t\t\t\tlogPlug = (userinterface.log.GUILog) plug;\n\t\t\t}\n\t\t\tprism.getSettings().addSettingsListener(plug);\n\t\t}\n\t\ttheTabs.setTabPlacement(JTabbedPane.BOTTOM);\n\t\tthePanel.setLayout(new BorderLayout());\n\t\tthePanel.setPreferredSize(new Dimension(DEFAULT_WINDOW_WIDTH, DEFAULT_WINDOW_HEIGHT));\n\t\tthePanel.setMinimumSize(new Dimension(MINIMUM_WINDOW_WIDTH, MINIMUM_WINDOW_HEIGHT));\n\t\tthePanel.add(theTabs, BorderLayout.CENTER);\n\n\t\tJMenu optionsMenu = new JMenu(\"Options\");\n\t\tmenuBar.add(optionsMenu);\n\n\t\tAction tabSwapper = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tnextTab();\n\t\t\t}\n\t\t};\n\t\ttabSwapper.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_TAB, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\n\t\tprismOptions = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\toptions.show();\n\t\t\t}\n\t\t};\n\t\tprismOptions.putValue(Action.LONG_DESCRIPTION, \"Brings up an option dialog for setting PRISM and user interface parameters.\");\n\t\tprismOptions.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_O));\n\t\tprismOptions.putValue(Action.NAME, \"Options\");\n\t\tprismOptions.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallOptions.png\"));\n\n\t\toptionsMenu.add(prismOptions);\n\t\toptionsMenu.setMnemonic('O');\n\n\t\tfontIncrease = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tadjustFont(1);\n\t\t\t}\n\t\t};\n\t\tfontIncrease.putValue(Action.LONG_DESCRIPTION, \"Increase the application font size.\");\n\t\tfontIncrease.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_I));\n\t\tfontIncrease.putValue(Action.NAME, \"Increase font size\");\n\t\tfontIncrease.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFontIncrease.png\"));\n\t\tfontIncrease.putValue(Action.ACCELERATOR_KEY,\n\t\t\t\tKeyStroke.getKeyStroke(KeyEvent.VK_EQUALS, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask() | InputEvent.SHIFT_MASK));\n\n\t\toptionsMenu.add(fontIncrease);\n\t\toptionsMenu.setMnemonic('I');\n\n\t\tfontDecrease = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tadjustFont(-1);\n\t\t\t}\n\t\t};\n\t\tfontDecrease.putValue(Action.LONG_DESCRIPTION, \"Decrease the application font size.\");\n\t\tfontDecrease.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_D));\n\t\tfontDecrease.putValue(Action.NAME, \"Decrease font size\");\n\t\tfontDecrease.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFontDecrease.png\"));\n\t\tfontDecrease.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_MINUS, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\n\t\toptionsMenu.add(fontDecrease);\n\t\toptionsMenu.setMnemonic('D');\n\n\t\tJPanel bottomPanel = new JPanel();\n\t\t{\n\t\t\tprogress = new JProgressBar(0, 100);\n\t\t\tprogress.setBorder(null);\n\t\t\ttaskbar = new GUITaskBar();\n\t\t\ttaskbar.setText(\"Welcome to PRISM...\");\n\t\t\tbottomPanel.setBorder(new javax.swing.border.EtchedBorder());\n\t\t\tbottomPanel.setLayout(new BorderLayout());\n\t\t\tbottomPanel.add(progress, BorderLayout.EAST);\n\t\t\tbottomPanel.add(taskbar, BorderLayout.CENTER);\n\t\t}\n\n\t\tsetJMenuBar(menuBar);\n\t\tsetTitle(Prism.getToolName() + \" \" + Prism.getVersion());\n\t\tsetDefaultCloseOperation(javax.swing.JFrame.DO_NOTHING_ON_CLOSE);\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\texit();\n\t\t\t}\n\t\t});\n\t\tgetContentPane().add(toolPanel, java.awt.BorderLayout.NORTH);\n\t\tgetContentPane().add(thePanel, java.awt.BorderLayout.CENTER);\n\t\tgetContentPane().add(bottomPanel, java.awt.BorderLayout.SOUTH);\n\t\tsetIconImage(GUIPrism.getIconFromImage(\"smallPrism.png\").getImage());\n\t\tgetContentPane().setSize(new java.awt.Dimension(800, 600));\n\t\tpack();\n\n\t\tfor (GUIPlugin plug : plugs) {\n\t\t\tplug.onInitComponentsCompleted();\n\t\t}\n\t}\n\n\tpublic String[] processCLArgs(String args[])\n\t{\n\t\t// before (later) passing any command-line args to all plugins\n\t\t// we first remove any -javamaxmem/-javastack arguments (ignored)\n\t\t// and any -dir argument (processed here first)\n\t\tList<String> argsCopy = new ArrayList<String>();\n\t\tfor (int i = 0; i < args.length; i++) {\n\t\t\tif (args[i].charAt(0) == '-') {\n\t\t\t\tString sw = args[i].substring(1);\n\t\t\t\t// remove optional second \"-\" (i.e. we allow switches of the form --sw too)\n\t\t\t\tif (sw.charAt(0) == '-')\n\t\t\t\t\tsw = sw.substring(1);\n\t\t\t\t// java max mem & java stack size & java parameters\n\t\t\t\tif (sw.equals(\"javamaxmem\") || sw.equals(\"javastack\") || sw.equals(\"javaparams\")) {\n\t\t\t\t\t// ignore argument and subsequent value, this is dealt with before java is launched\n\t\t\t\t\ti++;\n\t\t\t\t} else if (sw.equals(\"dir\")) {\n\t\t\t\t\tif (i < args.length - 1) {\n\t\t\t\t\t\tString workingDir = args[++i];\n\t\t\t\t\t\t// set working dir for PRISM\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tPrism.setWorkingDirectory(workingDir);\n\t\t\t\t\t\t} catch (PrismException ex) {\n\t\t\t\t\t\t\tSystem.err.println(\"Error: \" + ex.getMessage());\n\t\t\t\t\t\t\tSystem.exit(1);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t// also store locally to initialise file chooser\n\t\t\t\t\t\tchooserDir = workingDir;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tSystem.err.println(\"Error: No value specified for -\" + sw + \" switch\");\n\t\t\t\t\t\tSystem.exit(1);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\targsCopy.add(args[i]);\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\targsCopy.add(args[i]);\n\t\t\t}\n\t\t}\n\t\treturn argsCopy.toArray(new String[0]);\n\t}\n\t\n\tpublic void passCLArgs()\n\t{\n\t\tfor (GUIPlugin plug : plugs) {\n\t\t\tplug.takeCLArgs(args);\n\t\t}\n\t}\n\n\t/**\n\t *  Adjust the main font for the GUI (+1 = one size up, -1 = one size down)\n\t */\n\tpublic void adjustFont(int adjust)\n\t{\n\t\tObject[] objs = UIManager.getLookAndFeel().getDefaults().keySet().toArray();\n\t\tfor (int i = 0; i < objs.length; i++) {\n\t\t\tif (objs[i].toString().toUpperCase().indexOf(\".FONT\") != -1) {\n\t\t\t\tFont font = UIManager.getFont(objs[i]);\n\t\t\t\tfont = font.deriveFont((float) (font.getSize() + adjust));\n\t\t\t\tUIManager.put(objs[i], new FontUIResource(font));\n\t\t\t}\n\t\t}\n\t\tSwingUtilities.updateComponentTreeUI(this);\n\t\tSwingUtilities.updateComponentTreeUI(choose);\n\t\tSwingUtilities.updateComponentTreeUI(options);\n\t\trepaint();\n\t}\n\n\t//EXITERS\n\tpublic void exit()\n\t{\n\t\tdoExit = true;\n\t\tnotifyEventListeners(new GUIExitEvent(GUIExitEvent.REQUEST_EXIT));\n\n\t\t// Don't bug user to save defaults on exit\n\t\t/*if (prism.getSettings().isModified()) {\n\t\t    \n\t\t    String[] selection =\n\t\t    {\"Yes\", \"No\", \"Cancel\"};\n\t\t    int selectionNo = -1;\n\t\t    \n\t\t    selectionNo = JOptionPane.showOptionDialog(this, \"Prism settings have been modified. Do you wish to save them?\", \"Save Settings\", JOptionPane.OK_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE, null, selection, selection[0]);\n\t\t    switch(selectionNo)\n\t\t    {\n\t\t        case 0: \n\t\t        {\n\t\t            try\n\t\t            {\n\t\t                prism.getSettings().saveSettingsFile(); break;\n\t\t            }\n\t\t            catch(PrismException e)\n\t\t            {\n\t\t                errorDialog(\"Error: Could not save settings\",e.getMessage());\n\t\t            }\n\t\t        }\n\t\t        case 1: {break;}\n\t\t        case 2: doExit = false;\n\t\t        default: doExit = false;\n\t\t    }\n\t\t}*/\n\n\t\tif (doExit) {\n\t\t\tif (prism != null) {\n\t\t\t\tprism.closeDown(true);\n\t\t\t}\n\t\t\tSystem.exit(0);\n\t\t}\n\t}\n\n\t//ACCESS METHODS\n\n\t/** Utility access method to access the functionality contained within 'prism'.\n\t * @return The Prism object contained within this class.\n\t */\n\tpublic Prism getPrism()\n\t{\n\t\treturn prism;\n\t}\n\n\t/** Utility access method to acquire information stored within 'options'.\n\t * @return The GUIOptionsDialog object contained within this class.\n\t */\n\tpublic GUIOptionsDialog getOptions()\n\t{\n\t\treturn options;\n\t}\n\n\t/** Utility Access method access the event handler.\n\t * @return The event handler.\n\t */\n\tpublic GUIEventHandler getEventHandler()\n\t{\n\t\treturn eventHandle;\n\t}\n\n\t/** Utility access method which takes in a string filename and attempts to retrieve\n\t * the file from the images directory.\n\t * @return An ImageIcon\n\t * @param file The name of the file to be loaded.\n\t */\n\tpublic static ImageIcon getIconFromImage(String file)\n\t{\n\t\tURL url = GUIPrism.class.getClassLoader().getResource(\"images/\" + file);\n\t\tif (url == null) {\n\t\t\tSystem.out.println(\"Warning: Failed to load icon file \\\"\" + file + \"\\\"\");\n\t\t\treturn null;\n\t\t}\n\t\treturn new ImageIcon(url);\n\t}\n\n\t/** Utility access method for the file chooser used in the user interface.\n\t * @return The file chooser for the PRISM GUI.\n\t */\n\tpublic JFileChooser getChooser()\n\t{\n\t\treturn choose;\n\t}\n\n\t/** Access method to return the GUIPlugin object that is currently viewable on the\n\t * screen.\n\t * @return The foccused GUIPlugin object.\n\t */\n\tpublic GUIPlugin getFocussedPlugin()\n\t{\n\t\treturn (GUIPlugin) theTabs.getComponentAt(theTabs.getSelectedIndex());\n\t}\n\n\t/** Access utility method for the PrismLog.\n\t * @return The PrismLog contained within this class.\n\t */\n\tpublic PrismLog getLog()\n\t{\n\t\treturn theLog;\n\t}\n\n\t//UPDATE METHODS\n\n\t/** Utility method to notify the event handler of a GUIEvent.\n\t * @param e The GUIEvent to be handled.\n\t */\n\tpublic void notifyEventListeners(GUIEvent e)\n\t{\n\t\tgetEventHandler().notifyListeners(e);\n\t}\n\n\t/** Responsible for passing on user interface events to the options panel.\n\t * @param e A GUIEvent.\n\t */\n\tpublic boolean processGUIEvent(GUIEvent e)\n\t{\n\t\tif (e instanceof GUIComputationEvent) {\n\t\t\tif (e.getID() == GUIComputationEvent.COMPUTATION_START) {\n\t\t\t\tprismOptions.setEnabled(false);\n\t\t\t} else if (e.getID() == GUIComputationEvent.COMPUTATION_DONE) {\n\t\t\t\tprismOptions.setEnabled(true);\n\t\t\t\tappendWarningsNoteToTaskBarText(prism.getMainLog());\n\t\t\t} else if (e.getID() == GUIComputationEvent.COMPUTATION_ERROR) {\n\t\t\t\tprismOptions.setEnabled(true);\n\t\t\t}\n\t\t} else if (e instanceof GUIExitEvent) {\n\t\t\tif (e.getID() == GUIExitEvent.CANCEL_EXIT) {\n\t\t\t\tdoExit = false;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/** Update method that takes the GUIPlugin object 'tab' and either disables its\n\t * userinterface, or enables it according to 'enable'\n\t * @param tab The GUIPlugin object to change\n\t * @param enable Should it be enabled?\n\t */\n\tpublic void enableTab(GUIPlugin tab, boolean enable)\n\t{\n\t\tfor (int i = 0; i < theTabs.getComponentCount(); i++) {\n\t\t\tComponent c = theTabs.getComponentAt(i);\n\t\t\tif (c instanceof GUIPlugin) {\n\t\t\t\tGUIPlugin pl = (GUIPlugin) c;\n\n\t\t\t\tif (pl == tab) {\n\t\t\t\t\ttheTabs.setEnabledAt(i, enable);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/** Moves the view to the next GUIPlugin component which has a tab.  If the last one\n\t * has been reached, this sets the view back to the first one.\n\t */\n\tpublic void nextTab()\n\t{\n\t\ttheTabs.setSelectedIndex((theTabs.getSelectedIndex() + 1) % theTabs.getComponentCount());\n\t}\n\n\t/** Moves the view to the given GUIPlugin object.\n\t * @param tab The GUIPlugin object to view.\n\t */\n\tpublic void showTab(GUIPlugin tab)\n\t{\n\t\tfor (int i = 0; i < theTabs.getComponentCount(); i++) {\n\t\t\tComponent c = theTabs.getComponentAt(i);\n\t\t\tif (c == tab) {\n\t\t\t\ttheTabs.setSelectedIndex(i);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\t/** This shows the GUIPlugin associated with the log. */\n\tpublic void showLogTab()\n\t{\n\t\tif (logPlug != null) {\n\t\t\tshowTab(logPlug);\n\t\t}\n\t}\n\n\t/** Utility update method to set the text on the taskbar to 'message'\n\t * @param message The message for the taskbar.\n\t */\n\tpublic void setTaskBarText(String message)\n\t{\n\t\ttaskbar.setText(message);\n\t\t// Store message to in case we want to append a (single) warning later\n\t\ttaskbarText = message;\n\t}\n\n\t/** Utility update method to append a note about warnings to the taskbar\n\t * @param log PrismLog to check for warnings\n\t */\n\tpublic void appendWarningsNoteToTaskBarText(PrismLog log)\n\t{\n\t\tint numWarnings = log.getNumberOfWarnings();\n\t\tString message = null;\n\t\tif (numWarnings == 1)\n\t\t\tmessage = \"[ There was 1 warning - see log for details ]\";\n\t\telse if (numWarnings > 1)\n\t\t\tmessage = \"[ There were \" + numWarnings + \" warnings - see log for details ]\";\n\t\tif (message != null) {\n\t\t\tString taskbarTextNew = taskbarText;\n\t\t\tif (taskbarTextNew == null)\n\t\t\t\ttaskbarTextNew = \"\";\n\t\t\tif (taskbarTextNew.length() > 0)\n\t\t\t\ttaskbarTextNew += \"  \";\n\t\t\ttaskbarTextNew += message;\n\t\t\ttaskbar.setText(taskbarTextNew);\n\t\t}\n\t}\n\n\t/** Utility update method to set the JProgressBar to an indeterminate state. */\n\tpublic void startProgress()\n\t{\n\t\tprogress.setIndeterminate(true);\n\t}\n\n\t/** Utility update method to set the state of the JProgressBar to stopped. */\n\tpublic void stopProgress()\n\t{\n\t\tprogress.setIndeterminate(false);\n\t}\n\n\t/** Produces an error dialog box and puts it to the screen with the given message\n\t * and default heading\n\t * @param errorMessage The error message to be displayed.\n\t */\n\tpublic void errorDialog(String errorMessage)\n\t{\n\t\terrorDialog(\"Error\", errorMessage);\n\t}\n\n\t/** Produces an error dialog box and puts it to the screen with the given message\n\t * and a given heading\n\t * @param errorHeading The error dialog box's heading\n\t * @param errorMessage The error message to be displayed.\n\t */\n\tpublic void errorDialog(String errorHeading, String errorMessage)\n\t{\n\t\tJOptionPane.showMessageDialog(this, errorMessage, errorHeading, JOptionPane.ERROR_MESSAGE);\n\t\t//taskbar.setText(errorHeading);\n\t}\n\n\t//THREADS\n\n\t/** Thread to close the splash screen\n\t */\n\tprivate static final class SplashScreenCloser implements Runnable\n\t{\n\t\tpublic void run()\n\t\t{\n\t\t\tsplash.dispose();\n\t\t}\n\t}\n\n\tpublic static GUIClipboard getClipboardPlugin()\n\t{\n\t\treturn clipboardPlugin;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUIPrismOptionsPanel.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n  <NonVisualComponents>\n    <Component class=\"javax.swing.ButtonGroup\" name=\"iterativeButtonGroup\">\n    </Component>\n    <Component class=\"javax.swing.ButtonGroup\" name=\"terminationButtonGroup\">\n    </Component>\n    <Component class=\"javax.swing.ButtonGroup\" name=\"engineButtonGroup\">\n    </Component>\n  </NonVisualComponents>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-58,0,0,3,35\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Properties>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[12, 12]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[12, 12]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[12, 12]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"4\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n      <Properties>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[20, 10]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"6\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel5\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"8\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel6\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel7\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"9\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel8\">\n      <Properties>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 10]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"13\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel9\">\n      <Properties>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 5]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 5]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 5]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"15\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel10\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"18\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel11\">\n      <Properties>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 5]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 5]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 5]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"21\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel12\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"23\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel1\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"verboseCheck\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Flags:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JCheckBox\" name=\"verboseCheck\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"86\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Verbose\"/>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JCheckBox\" name=\"fairnessCheck\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"70\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Use fairness\"/>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"fairnessCheckActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JCheckBox\" name=\"preCompCheck\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"80\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Use precomputation\"/>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"preCompCheckActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"3\" gridWidth=\"3\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel2\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"powerRadio\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Iterative method:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"1\" gridY=\"10\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"powerRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"119\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Power\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"iterativeButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"powerRadioActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"10\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"jacobiRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"74\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Jacobi\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"iterativeButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"jacobiRadioActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"11\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"gaussSeidelRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"71\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Gauss-Seidel\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"iterativeButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"gaussSeidelRadioActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"12\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"jorRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"79\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"JOR\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"iterativeButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"jorRadioActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"13\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"sorRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"79\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"SOR\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"iterativeButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"sorRadioActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"14\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jorParameterLabel\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"jorParameterField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Over-relaxation parameter:\"/>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"15\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"jorParameterField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"5\" gridY=\"15\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JCheckBox\" name=\"backwardsButton\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Backwards\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"16\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel4\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"relativeRadio\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Termination criteria:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"7\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"relativeRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"82\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Relative\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"terminationButtonGroup\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"absoluteRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"65\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Absolute\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"terminationButtonGroup\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel5\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"maxIterationsField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Max. iterations:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel6\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"epsilonField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Epsilon:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"maxIterationsField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"11\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"epsilonField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"11\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel7\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"mtbddRadio\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Engine:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"7\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"mtbddRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"77\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"MTBDD\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"engineButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"mtbddRadioActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"sparseRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"83\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Sparse\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"engineButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"sparseRadioActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"7\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"hybridRadio\">\n      <Properties>\n        <Property name=\"mnemonic\" type=\"int\" value=\"72\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Hybrid\"/>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"engineButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"hybridRadioActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"8\" gridWidth=\"1\" gridHeight=\"1\" fill=\"3\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"noLevelsLabel\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"noLevelsField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Num. levels\"/>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"10\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"noLevelsField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"11\" gridY=\"10\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"maxMemoryLabel\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"maxMemoryField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Max. memory\"/>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"11\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"maxMemoryField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"11\" gridY=\"11\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel13\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"10\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel14\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"5\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel3\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"CUDD:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"1\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"cuddLabel\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"jorParameterField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Max Memory (KB):\"/>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"cuddMaxMemoryField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"5\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"epsilonCuddLabel\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"jorParameterField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Epsilon:\"/>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"7\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"cuddEpsilonField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"5\" gridY=\"7\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel15\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 5]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 4]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"16\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel17\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"12\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel8\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Hybrid:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"7\" gridY=\"10\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"noLevelsGSSOR\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"maxMemoryField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Num. levels (GS/SOR):\"/>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"12\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"noLevelsGSSORField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"11\" gridY=\"12\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"maxMemoryGSSOR\">\n      <Properties>\n        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n          <ComponentRef name=\"maxMemoryField\"/>\n        </Property>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Max. memory (GS/SOR):\"/>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"9\" gridY=\"13\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"maxMemoryGSSORField\">\n      <Properties>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[63, 20]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"11\" gridY=\"13\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JCheckBox\" name=\"pseudoButton\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Pseudo\"/>\n        <Property name=\"alignmentY\" type=\"float\" value=\"0.4\"/>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"pseudoButtonActionPerformed\"/>\n      </Events>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"17\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JCheckBox\" name=\"compactCheck\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Use &quot;compact&quot; schemes\"/>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"compactCheckActionPerformed\"/>\n      </Events>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/GUIPrismSplash.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\nimport java.awt.*;\nimport prism.*;\nimport java.net.URL;\n\npublic class GUIPrismSplash extends Frame \n{\n\tprivate String filename;\n\tprivate MediaTracker mt;\n\tprivate Image image;\n\t\n\tpublic GUIPrismSplash(String filename) \n\t{\n\t\tthis.filename = filename;\n\t}\n\t\n\tpublic void display() \n\t{\n\t\tmt = new MediaTracker(this);\n\t\t\n\t\tURL imageURL = GUIPrismSplash.class.getClassLoader().getResource(filename);\n\t\tif (imageURL == null) \n\t\t{\n\t\t\tSystem.out.println(\"Warning: Failed to load icon file \\\"\" + filename + \"\\\"\");\n\t\t}\n\t\t\n\t\t\n\t\timage = Toolkit.getDefaultToolkit().getImage(imageURL);\n\t\tDimension screen = Toolkit.getDefaultToolkit().getScreenSize();\n\t\tRectangle frame = getBounds();\n\t\tsetLocation((screen.width - frame.width)/2, (screen.height - frame.height)/2);\n\t\t\n\t\tmt.addImage(image, 0);\n\t\ttry \n\t\t{\n\t\t\tmt.waitForID(0);\n\t\t}\n\t\tcatch(InterruptedException ie) \n\t\t{\n\t\t\tSystem.out.println(\"Error in media tracker\");\n\t\t}\n\t\t\n\t\tSplashWindow splashWindow = new SplashWindow(this,image);\n\t}\n\t\n\t//Thanks to http://www.javapractices.com/Topic149.cjp for the SplashWindow class\n\tprivate class SplashWindow extends Window \n\t{\n\t\tSplashWindow(Frame aParent, Image aImage) \n\t\t{\n\t\t\tsuper(aParent);\n\t\t\tfImage = aImage;\n\t\t\tsetSize(fImage.getWidth(null), fImage.getHeight(null));\n\t\t\tDimension screen = Toolkit.getDefaultToolkit().getScreenSize();\n\t\t\tRectangle window = getBounds();\n\t\t\tsetLocation((screen.width - window.width) / 2, (screen.height - window.height) / 2);\n\t\t\tsetVisible(true);\n\t\t}\n\t\tpublic void paint(Graphics graphics) \n\t\t{\n\t\t\tif (fImage != null) \n\t\t\t{\n\t\t\t\tgraphics.drawImage(fImage,0,0,this);\n\t\t\t\tFont theFont = new Font (\"monospaced\", Font.BOLD, 10);\n\t\t\t\tgraphics.setFont(theFont);\n\t\t\t\tint x = (int)(getBounds().width - theFont.getSize2D()*(Prism.getVersion().length()+1)*(5.0/8.0) - 10);\n\t\t\t\tint y = (int)(getBounds().height - theFont.getSize2D() - 10);\n\t\t\t\tgraphics.drawString(Prism.getVersion() + \" \", x, y);\n\t\t\t}\n\t\t}\n\t\tprivate Image fImage;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUISimulationPicker.form.outofdate",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-85,0,0,2,-114\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel6\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n        <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n      </Layout>\n      <SubComponents>\n        <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n          </Events>\n        </Component>\n        <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n          </Events>\n        </Component>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel7\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                <TitledBorder title=\"Initial State\"/>\n              </Border>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"0\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel5\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"0\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"1\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel10\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"East\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\">\n            <Property name=\"axis\" type=\"int\" value=\"1\"/>\n          </Layout>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel8\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                    <TitledBorder title=\"Sampling Parameters\"/>\n                  </Border>\n                </Property>\n              </Properties>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel9\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JLabel\" name=\"jLabel4\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Automatically Calculate:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"jLabel5\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Approximation:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"jLabel6\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Confidence:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"7\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"jLabel7\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Number of Samples:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"8\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel11\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[10, 5]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"5\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel12\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"2\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JComboBox\" name=\"automaticCalculateCombo\">\n                  <Properties>\n                    <Property name=\"model\" type=\"javax.swing.ComboBoxModel\" editor=\"org.netbeans.modules.form.editors2.ComboBoxModelEditor\">\n                      <StringArray count=\"3\">\n                        <StringItem index=\"0\" value=\"Number of samples\"/>\n                        <StringItem index=\"1\" value=\"Approximation\"/>\n                        <StringItem index=\"2\" value=\"Confidence\"/>\n                      </StringArray>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"automaticCalculateComboActionPerformed\"/>\n                  </Events>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"4\" gridWidth=\"2\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel13\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"5\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JTextField\" name=\"approximationField\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[65, 20]\"/>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"approximationFieldActionPerformed\"/>\n                  </Events>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"6\" gridWidth=\"2\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JTextField\" name=\"confidenceField\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[60, 20]\"/>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"confidenceFieldActionPerformed\"/>\n                  </Events>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"7\" gridWidth=\"2\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JTextField\" name=\"iterationsField\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[60, 20]\"/>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"iterationsFieldActionPerformed\"/>\n                  </Events>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"8\" gridWidth=\"2\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel14\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"9\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n              </SubComponents>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel15\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                    <TitledBorder title=\"Path Parameters\"/>\n                  </Border>\n                </Property>\n              </Properties>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel16\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JLabel\" name=\"jLabel2\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Maximum Path Length:\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[150, 15]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel17\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JTextField\" name=\"pathLengthField\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[158, 20]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"1\" gridWidth=\"2\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel18\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[118, 10]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"2\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel19\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"6\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel20\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JCheckBox\" name=\"distributedCheck\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Distributed?\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"18\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/GUISimulationPicker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport java.util.*;\nimport java.util.List;\nimport java.awt.*;\nimport java.awt.event.*;\nimport javax.swing.*;\nimport javax.swing.table.*;\n\nimport parser.*;\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.*;\nimport simulator.method.*;\n\n/**\n *  GUISimulationPicker is a dialog to collect the details required for\n *  approximate (simulation-based) model checking: initial state, max path length,\n *  simulation method + parameters, etc.\n */\npublic class GUISimulationPicker extends javax.swing.JDialog implements KeyListener\n{\n\t// Default serial version ID\n\tprivate static final long serialVersionUID = 1L;\n\n\t//STATICS\n\n\tpublic static final int NO_VALUES = 0;\n\tpublic static final int VALUES_DONE = 1;\n\tpublic static final int CANCELLED = 2;\n\n\tpublic static SimulationInformation lastSimulationInformation = null;\n\n\t//ATTRIBUTES\n\n\tprivate GUIPrism gui;\n\tprivate ModulesFile modulesFile;\n\tprivate SimulationInformation information;\n\n\tprivate boolean cancelled = true;\n\n\tprivate JTable initValuesTable;\n\tprivate DefineValuesTable initValuesModel;\n\n\t// Last valid contents of text boxes\n\tprivate String lastWidth;\n\tprivate String lastConf;\n\tprivate String lastNumSamples;\n\n\tprivate boolean atLeastOneRwd;\n\tprivate boolean atLeastOneQuant;\n\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\t// Note: this code has now been modified manually; form is no longer used.\n\tjavax.swing.JTextField widthField;\n\tjavax.swing.JComboBox selectSimulationMethod;\n\tjavax.swing.JComboBox automaticCalculateCombo;\n\tprivate javax.swing.JButton cancelButton;\n\tjavax.swing.JTextField confidenceField;\n\tjavax.swing.JTextField numberToDecide;\n\t//private javax.swing.JCheckBox distributedCheck;\n\tjavax.swing.JTextField numSamplesField;\n\tprivate javax.swing.JLabel jLabel2;\n\tprivate javax.swing.JLabel jLabelSSM;\n\tprivate javax.swing.JLabel jLabel4;\n\tprivate javax.swing.JLabel jLabel5;\n\tprivate javax.swing.JLabel jLabel6;\n\tprivate javax.swing.JLabel jLabel7;\n\tprivate javax.swing.JPanel jPanel1;\n\tprivate javax.swing.JPanel jPanel10;\n\tprivate javax.swing.JPanel jPanel11;\n\tprivate javax.swing.JPanel jPanel12;\n\tprivate javax.swing.JPanel jPanel13;\n\tprivate javax.swing.JPanel jPanel14;\n\tprivate javax.swing.JPanel jPanel15;\n\tprivate javax.swing.JPanel jPanel16;\n\tprivate javax.swing.JPanel jPanel17;\n\tprivate javax.swing.JPanel jPanel18;\n\tprivate javax.swing.JPanel jPanel19;\n\tprivate javax.swing.JPanel jPanel2;\n\tprivate javax.swing.JPanel jPanel20;\n\tprivate javax.swing.JPanel jPanel3;\n\tprivate javax.swing.JPanel jPanel4;\n\tprivate javax.swing.JPanel jPanel5;\n\tprivate javax.swing.JPanel jPanel6;\n\tprivate javax.swing.JPanel jPanel7;\n\tprivate javax.swing.JPanel jPanel8;\n\tprivate javax.swing.JPanel jPanel9;\n\tprivate javax.swing.JButton okayButton;\n\tjavax.swing.JTextField pathLengthField;\n\tjavax.swing.JPanel topPanel;\n\tjavax.swing.JCheckBox useDefaultInitialCheck;\n\n\t// End of variables declaration//GEN-END:variables\n\n\t/**\n\t * Create a new GUIConstantsPicker dialog to define info for simulation-based property checking.\n\t * @param parent Parent GUI window\n\t * @param exprs The properties to be checked (note: constants may not be defined)\n\t * @param modulesFile The model that will be simulated (for initial state info)\n\t * @param titleExtra Optional string to append to dialog (null if not needed)\n\t * @throws PrismException if there is a problem getting initial state info from the model.\n\t */\n\tpublic GUISimulationPicker(GUIPrism parent, List<Expression> exprs, ModulesFile modulesFile, String titleExtra) throws PrismException\n\t{\n\t\tsuper(parent, \"Simulation Parameters\" + ((titleExtra != null) ? (\" - \" + titleExtra) : \"\"), true);\n\t\tthis.gui = parent;\n\t\tthis.modulesFile = modulesFile;\n\n\t\t// See if there are any reward props in the list to be checked\n\t\tatLeastOneRwd = false;\n\t\tfor (Expression expr : exprs) {\n\t\t\tif (expr instanceof ExpressionReward) {\n\t\t\t\tatLeastOneRwd = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\t// See if there are any quantitative (=?) props in the list to be checked\n\t\tatLeastOneQuant = false;\n\t\tfor (Expression expr : exprs) {\n\t\t\tif (Expression.isQuantitative(expr)) {\n\t\t\t\tatLeastOneQuant = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\t// Create a SimulationInformation object to store info in this dialog,\n\t\t// (or re-use last one if user prefers to do that)\n\t\tPrismSettings settings = parent.getPrism().getSettings();\n\t\tif (lastSimulationInformation == null || settings.getString(PrismSettings.SIMULATOR_FIELD_CHOICE).equals(\"Always use defaults\")) {\n\t\t\tlastSimulationInformation = new SimulationInformation(settings);\n\t\t\t// Pick a default method (CI for quantitative, SPRT for bounded)\n\t\t\tlastSimulationInformation.setMethod(atLeastOneQuant ? SimulationInformation.Method.CI : SimulationInformation.Method.SPRT);\n\t\t}\n\n\t\t// Make sure method choice is valid (if remembered)\n\t\tif (atLeastOneRwd && lastSimulationInformation.getMethod() == SimulationInformation.Method.APMC) {\n\t\t\tlastSimulationInformation.setMethod(SimulationInformation.Method.CI);\n\t\t}\n\t\tif (atLeastOneQuant && lastSimulationInformation.getMethod() == SimulationInformation.Method.SPRT) {\n\t\t\tlastSimulationInformation.setMethod(SimulationInformation.Method.CI);\n\t\t}\n\n\t\tlastSimulationInformation.setPropReward(atLeastOneRwd);\n\n\t\tlastWidth = \"\" + lastSimulationInformation.getWidth();\n\t\tlastConf = \"\" + lastSimulationInformation.getConfidence();\n\t\tlastNumSamples = \"\" + lastSimulationInformation.getNumSamples();\n\n\t\t// create \"initial state\" table\n\t\tinitValuesModel = new DefineValuesTable();\n\t\tinitValuesTable = new GreyableJTable();\n\t\tinitValuesTable.setModel(initValuesModel);\n\t\tinitValuesTable.setSelectionMode(DefaultListSelectionModel.SINGLE_INTERVAL_SELECTION);\n\t\tinitValuesTable.setCellSelectionEnabled(true);\n\n\t\t// set up simulation information based on previous info (or defaults - see above)\n\t\tinformation = lastSimulationInformation;\n\n\t\t// currently, we deliberately do not recall the last initial state used\n\t\t// since it may no longer be valid due to changes in the model\n\t\tinformation.setInitialState(null);\n\t\t\n\t\t// initialise\n\t\tinitComponents();\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\n\t\tinitTable();\n\t\tinitValues();\n\t\twidthField.addKeyListener(this);\n\t\tconfidenceField.addKeyListener(this);\n\t\tnumSamplesField.addKeyListener(this);\n\t\tdoEnablesAndCalculations(true);\n\t\tsetResizable(false);\n\n\t\tpack();\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t}\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t * Note: this code has now been modified manually; form is no longer used.\n\t */\n\tprivate void initComponents()//GEN-BEGIN:initComponents\n\t{\n\t\tjava.awt.GridBagConstraints gridBagConstraints;\n\n\t\tjPanel6 = new javax.swing.JPanel();\n\t\tokayButton = new javax.swing.JButton();\n\t\tcancelButton = new javax.swing.JButton();\n\t\tjPanel7 = new javax.swing.JPanel();\n\t\tjPanel1 = new javax.swing.JPanel();\n\t\tjPanel2 = new javax.swing.JPanel();\n\t\tjPanel3 = new javax.swing.JPanel();\n\t\tjPanel4 = new javax.swing.JPanel();\n\t\tjPanel5 = new javax.swing.JPanel();\n\t\ttopPanel = new javax.swing.JPanel();\n\t\tjPanel10 = new javax.swing.JPanel();\n\t\tjPanel8 = new javax.swing.JPanel();\n\t\tjPanel9 = new javax.swing.JPanel();\n\t\tjLabelSSM = new javax.swing.JLabel();\n\t\tjLabel4 = new javax.swing.JLabel();\n\t\tjLabel5 = new javax.swing.JLabel();\n\t\tjLabel6 = new javax.swing.JLabel();\n\t\tjLabel7 = new javax.swing.JLabel();\n\t\tjPanel11 = new javax.swing.JPanel();\n\t\tjPanel12 = new javax.swing.JPanel();\n\t\tselectSimulationMethod = new javax.swing.JComboBox(); // new\n\t\tautomaticCalculateCombo = new javax.swing.JComboBox();\n\t\tjPanel13 = new javax.swing.JPanel();\n\t\twidthField = new javax.swing.JTextField();\n\t\tconfidenceField = new javax.swing.JTextField();\n\t\tnumberToDecide = new javax.swing.JTextField();\n\t\tnumSamplesField = new javax.swing.JTextField();\n\t\tjPanel14 = new javax.swing.JPanel();\n\t\tjPanel15 = new javax.swing.JPanel();\n\t\tjPanel16 = new javax.swing.JPanel();\n\t\tjLabel2 = new javax.swing.JLabel();\n\t\tjPanel17 = new javax.swing.JPanel();\n\t\tpathLengthField = new javax.swing.JTextField();\n\t\tjPanel18 = new javax.swing.JPanel();\n\t\tjPanel19 = new javax.swing.JPanel();\n\t\tjPanel20 = new javax.swing.JPanel();\n\t\t//distributedCheck = new javax.swing.JCheckBox();\n\t\tuseDefaultInitialCheck = new javax.swing.JCheckBox();\n\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel6.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tokayButton.setText(\"Okay\");\n\t\tokayButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tokayButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel6.add(okayButton);\n\n\t\tcancelButton.setText(\"Cancel\");\n\t\tcancelButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tcancelButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel6.add(cancelButton);\n\n\t\tgetContentPane().add(jPanel6, java.awt.BorderLayout.SOUTH);\n\n\t\tjPanel7.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel1.setLayout(new java.awt.GridBagLayout());\n\n\t\tjPanel1.setBorder(new javax.swing.border.TitledBorder(\"Initial state\"));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel1.add(jPanel2, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel1.add(jPanel3, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 2;\n\t\tjPanel1.add(jPanel4, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 4;\n\t\tjPanel1.add(jPanel5, gridBagConstraints);\n\t\t\n\t\tuseDefaultInitialCheck.setText(\"Use default initial state\");\n\t\tuseDefaultInitialCheck.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tuseDefaultInitialCheckActionPerformed(evt);\n\t\t\t}\n\t\t});\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tjPanel1.add(useDefaultInitialCheck, gridBagConstraints);\n\t\t\n\t\ttopPanel.setLayout(new java.awt.BorderLayout());\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 3;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tjPanel1.add(topPanel, gridBagConstraints);\n\n\t\tjPanel7.add(jPanel1, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel10.setLayout(new javax.swing.BoxLayout(jPanel10, javax.swing.BoxLayout.Y_AXIS));\n\n\t\tjPanel8.setLayout(new java.awt.GridBagLayout());\n\n\t\tjPanel8.setBorder(new javax.swing.border.TitledBorder(\"Sampling parameters\"));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tjPanel8.add(jPanel9, gridBagConstraints);\n\n\t\tjLabelSSM.setText(\"Simulation method:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 3;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel8.add(jLabelSSM, gridBagConstraints);\n\n\t\tjLabel4.setText(\"Automatically calculate:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 4;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel8.add(jLabel4, gridBagConstraints);\n\n\t\tjLabel5.setText(\"Width:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 6;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel8.add(jLabel5, gridBagConstraints);\n\n\t\tjLabel6.setText(\"Confidence:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 7;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel8.add(jLabel6, gridBagConstraints);\n\n\t\tjLabel7.setText(\"Number of samples:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 8;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel8.add(jLabel7, gridBagConstraints);\n\n\t\tjPanel11.setPreferredSize(new java.awt.Dimension(10, 5));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 5;\n\t\tjPanel8.add(jPanel11, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 3;\n\t\tjPanel8.add(jPanel12, gridBagConstraints);\n\n\t\t// Populate simulation method choices\n\t\tVector<String> methods = new Vector<String>();\n\t\tmethods.add(\"CI\");\n\t\tmethods.add(\"ACI\");\n\t\tif (!atLeastOneRwd)\n\t\t\tmethods.add(\"APMC\");\n\t\tif (!atLeastOneQuant)\n\t\t\tmethods.add(\"SPRT\");\n\t\tselectSimulationMethod.setModel(new javax.swing.DefaultComboBoxModel(methods));\n\n\t\tselectSimulationMethod.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tselectSimulationMethodActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tautomaticCalculateCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { }));\n\t\tautomaticCalculateCombo.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tautomaticCalculateComboActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 3;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tjPanel8.add(selectSimulationMethod, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 4;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tjPanel8.add(automaticCalculateCombo, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 5;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel8.add(jPanel13, gridBagConstraints);\n\n\t\twidthField.setPreferredSize(new java.awt.Dimension(65, 20));\n\t\twidthField.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\twidthFieldActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 6;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tjPanel8.add(widthField, gridBagConstraints);\n\n\t\tconfidenceField.setPreferredSize(new java.awt.Dimension(60, 20));\n\t\tconfidenceField.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tconfidenceFieldActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 7;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tjPanel8.add(confidenceField, gridBagConstraints);\n\n\t\tnumSamplesField.setPreferredSize(new java.awt.Dimension(60, 20));\n\t\tnumSamplesField.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tnumSamplesFieldActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 8;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tjPanel8.add(numSamplesField, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 9;\n\t\tjPanel8.add(jPanel14, gridBagConstraints);\n\n\t\tjPanel10.add(jPanel8);\n\n\t\tjPanel15.setLayout(new java.awt.GridBagLayout());\n\n\t\tjPanel15.setBorder(new javax.swing.border.TitledBorder(\"Path parameters\"));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel15.add(jPanel16, gridBagConstraints);\n\n\t\tjLabel2.setText(\"Maximum path length:\");\n\t\tjLabel2.setPreferredSize(new java.awt.Dimension(150, 15));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel15.add(jLabel2, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel15.add(jPanel17, gridBagConstraints);\n\n\t\tpathLengthField.setPreferredSize(new java.awt.Dimension(158, 20));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tjPanel15.add(pathLengthField, gridBagConstraints);\n\n\t\tjPanel18.setPreferredSize(new java.awt.Dimension(118, 10));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tjPanel15.add(jPanel18, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 6;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel15.add(jPanel19, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 3;\n\t\tjPanel15.add(jPanel20, gridBagConstraints);\n\n\t\t//distributedCheck.setText(\"Distributed?\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 2;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.NORTHWEST;\n\t\t//jPanel15.add(distributedCheck, gridBagConstraints);\n\n\t\tjPanel10.add(jPanel15);\n\n\t\tjPanel7.add(jPanel10, java.awt.BorderLayout.EAST);\n\n\t\tgetContentPane().add(jPanel7, java.awt.BorderLayout.CENTER);\n\n\t\tpack();\n\t}//GEN-END:initComponents\n\n\tprivate void numSamplesFieldActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_numSamplesFieldActionPerformed\n\t{//GEN-HEADEREND:event_numSamplesFieldActionPerformed\n\t\tdoEnablesAndCalculations(false);\n\t}//GEN-LAST:event_numSamplesFieldActionPerformed\n\n\tprivate void confidenceFieldActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_confidenceFieldActionPerformed\n\t{//GEN-HEADEREND:event_confidenceFieldActionPerformed\n\t\tdoEnablesAndCalculations(false);\n\t}//GEN-LAST:event_confidenceFieldActionPerformed\n\n\tprivate void widthFieldActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_approximationFieldActionPerformed\n\t{//GEN-HEADEREND:event_widthFieldActionPerformed\n\t\tdoEnablesAndCalculations(false);\n\t}//GEN-LAST:event_widthFieldActionPerformed\n\n\tprivate void selectSimulationMethodActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_automaticCalculateComboActionPerformed\n\t{//GEN-HEADEREND:event_selectSimulationMethodActionPerformed\n\t\tdoChangeSimulationMethod();\n\t}//GEN-LAST:event_selectSimulationMethodActionPerformed\n\n\tprivate void automaticCalculateComboActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_automaticCalculateComboActionPerformed\n\t{//GEN-HEADEREND:event_automaticCalculateComboActionPerformed\n\t\tdoEnablesAndCalculations(true);\n\t}//GEN-LAST:event_automaticCalculateComboActionPerformed\n\n\tprivate static boolean isValidDoubleOrEmpty(String s)\n\t{\n\t\tif (s.isEmpty())\n\t\t\treturn true;\n\t\ttry {\n\t\t\tDouble.parseDouble(s);\n\t\t} catch (NumberFormatException e) {\n\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\tprivate void doChangeSimulationMethod()\n\t{\n\t\t// Remember choice for \"Automatically calculate\"\n\t\tint automaticCalculateComboIndex = automaticCalculateCombo.getSelectedIndex();\n\t\t// Store method, change text labels, and\n\t\t// populate \"Automatically calculate\" choices based on method\n\t\tinformation.setMethodByName((String) selectSimulationMethod.getSelectedItem());\n\t\tswitch (information.getMethod()) {\n\t\tcase CI:\n\t\t\tjLabel5.setText(\"Width:\");\n\t\t\tjLabel6.setText(\"Confidence:\");\n\t\t\tautomaticCalculateCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"Width\", \"Confidence\", \"Number of samples\" }));\n\t\t\tbreak;\n\t\tcase ACI:\n\t\t\tjLabel5.setText(\"Width:\");\n\t\t\tjLabel6.setText(\"Confidence:\");\n\t\t\tautomaticCalculateCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"Width\", \"Confidence\", \"Number of samples\" }));\n\t\t\tbreak;\n\t\tcase APMC:\n\t\t\tjLabel5.setText(\"Approximation:\");\n\t\t\tjLabel6.setText(\"Confidence:\");\n\t\t\tautomaticCalculateCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"Approximation\", \"Confidence\", \"Number of samples\" }));\n\t\t\tbreak;\n\t\tcase SPRT:\n\t\t\tjLabel5.setText(\"Indifference:\");\n\t\t\tjLabel6.setText(\"Type I/II error:\");\n\t\t\tautomaticCalculateCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"Number of samples\" }));\n\t\t\tbreak;\n\t\t}\n\t\t// Restore choice for \"Automatically calculate\"\n\t\t// (unless empty list, indicated by -1 indexx, which means this the initial setup)\n\t\tif (automaticCalculateComboIndex != -1) {\n\t\t\t// If choice invalid due to list size change, reset to 0\n\t\t\tif (automaticCalculateComboIndex > automaticCalculateCombo.getItemCount() - 1)\n\t\t\t\tautomaticCalculateComboIndex = 0;\n\t\t\tautomaticCalculateCombo.setSelectedIndex(automaticCalculateComboIndex);\n\t\t}\n\t}\n\n\t/**\n\t * Update dialog after a change in one of the controls.\n\t * Enable/disable text fields as necessary.\n\t * Compute new value for unknown fields.\n\t * @param autoChange indicates that the \"method\" or \"auto calc\" has changed\n\t */\n\tprivate void doEnablesAndCalculations(boolean autoChange)\n\t{\n\t\tdouble width, confidence;\n\t\tint numSamples;\n\t\t\n\t\t// Save valid values for later\n\t\tif (isValidDoubleOrEmpty(confidenceField.getText()))\n\t\t\tlastConf = confidenceField.getText();\n\t\tif (isValidDoubleOrEmpty(numSamplesField.getText()))\n\t\t\tlastNumSamples = numSamplesField.getText();\n\t\tif (isValidDoubleOrEmpty(widthField.getText()))\n\t\t\tlastWidth = widthField.getText();\n\n\t\t// Store current unknown parameter\n\t\tinformation.setUnknownByName((String) automaticCalculateCombo.getSelectedItem());\n\n\t\t// Enable all text fields (then disable some below)\n\t\twidthField.setEnabled(true);\n\t\tconfidenceField.setEnabled(true);\n\t\tnumSamplesField.setEnabled(true);\n\n\t\tswitch (information.getMethod()) {\n\n\t\tcase CI:\n\t\tcase ACI:\n\t\t\tswitch (information.getUnknown()) {\n\t\t\tcase WIDTH:\n\t\t\t\twidthField.setEnabled(false);\n\t\t\t\twidthField.setText(\"Unknown before sim.\");\n\t\t\t\twidthField.setCaretPosition(0);\n\t\t\t\t// If method changes, display last valid values\n\t\t\t\tif (autoChange) {\n\t\t\t\t\tnumSamplesField.setText(lastNumSamples);\n\t\t\t\t\tnumSamplesField.setCaretPosition(0);\n\t\t\t\t\tconfidenceField.setText(lastConf);\n\t\t\t\t\tconfidenceField.setCaretPosition(0);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase CONFIDENCE:\n\t\t\t\tconfidenceField.setEnabled(false);\n\t\t\t\tconfidenceField.setText(\"Unknown before sim.\");\n\t\t\t\tconfidenceField.setCaretPosition(0);\n\t\t\t\t// If method changes, display last valid values\n\t\t\t\tif (autoChange) {\n\t\t\t\t\twidthField.setText(lastWidth);\n\t\t\t\t\twidthField.setCaretPosition(0);\n\t\t\t\t\tnumSamplesField.setText(lastNumSamples);\n\t\t\t\t\tnumSamplesField.setCaretPosition(0);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase NUM_SAMPLES:\n\t\t\t\tnumSamplesField.setEnabled(false);\n\t\t\t\tnumSamplesField.setText(\"Unknown before sim.\");\n\t\t\t\tnumSamplesField.setCaretPosition(0);\n\t\t\t\t// If method changes, display last valid values\n\t\t\t\tif (autoChange) {\n\t\t\t\t\twidthField.setText(lastWidth);\n\t\t\t\t\twidthField.setCaretPosition(0);\n\t\t\t\t\tconfidenceField.setText(lastConf);\n\t\t\t\t\tconfidenceField.setCaretPosition(0);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase APMC:\n\t\t\tswitch (information.getUnknown()) {\n\t\t\tcase WIDTH:\n\t\t\t\twidthField.setEnabled(false);\n\t\t\t\ttry {\n\t\t\t\t\tconfidence = Double.parseDouble(confidenceField.getText());\n\t\t\t\t\tnumSamples = Integer.parseInt(numSamplesField.getText());\n\t\t\t\t\tif (confidence > 0 && confidence < 1 && numSamples > 0) {\n\t\t\t\t\t\twidthField.setText(\"\" + (new APMCapproximation(confidence, numSamples)).getMissingParameter());\n\t\t\t\t\t\twidthField.setCaretPosition(0);\n\t\t\t\t\t}\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t// Any problems, don't update text field\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t// Any problems, don't update text field\n\t\t\t\t}\n\t\t\t\t// If method changes, display last valid values\n\t\t\t\tif (autoChange) {\n\t\t\t\t\tnumSamplesField.setText(lastNumSamples);\n\t\t\t\t\tnumSamplesField.setCaretPosition(0);\n\t\t\t\t\tconfidenceField.setText(lastConf);\n\t\t\t\t\tconfidenceField.setCaretPosition(0);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase CONFIDENCE:\n\t\t\t\tconfidenceField.setEnabled(false);\n\t\t\t\ttry {\n\t\t\t\t\twidth = Double.parseDouble(widthField.getText());\n\t\t\t\t\tnumSamples = Integer.parseInt(numSamplesField.getText());\n\t\t\t\t\tif (width > 0 && numSamples > 0) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tconfidenceField.setText(\"\" + (new APMCconfidence(width, numSamples)).getMissingParameter());\n\t\t\t\t\t\t\tconfidenceField.setCaretPosition(0);\n\t\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t\t// Catch this error to set helpful message\n\t\t\t\t\t\t\tconfidenceField.setText(\"Incr. approx/samples\");\n\t\t\t\t\t\t\tconfidenceField.setCaretPosition(0);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t// Any problems, don't update text field\n\t\t\t\t}\n\t\t\t\t// If method changes, display last valid values\n\t\t\t\tif (autoChange) {\n\t\t\t\t\twidthField.setText(lastWidth);\n\t\t\t\t\twidthField.setCaretPosition(0);\n\t\t\t\t\tnumSamplesField.setText(lastNumSamples);\n\t\t\t\t\tnumSamplesField.setCaretPosition(0);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\tcase NUM_SAMPLES:\n\t\t\t\tnumSamplesField.setEnabled(false);\n\t\t\t\ttry {\n\t\t\t\t\twidth = Double.parseDouble(widthField.getText());\n\t\t\t\t\tconfidence = Double.parseDouble(confidenceField.getText());\n\t\t\t\t\tif (width > 0 && confidence > 0 && confidence < 1) {\n\t\t\t\t\t\tnumSamplesField.setText(\"\" + (new APMCiterations(confidence, width)).getMissingParameter());\n\t\t\t\t\t\tnumSamplesField.setCaretPosition(0);\n\t\t\t\t\t}\n\t\t\t\t} catch (NumberFormatException e) {\n\t\t\t\t\t// Any problems, don't update text field\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t// Any problems, don't update text field\n\t\t\t\t}\n\t\t\t\t// If method changes, display last valid values\n\t\t\t\tif (autoChange) {\n\t\t\t\t\twidthField.setText(lastWidth);\n\t\t\t\t\twidthField.setCaretPosition(0);\n\t\t\t\t\tconfidenceField.setText(lastConf);\n\t\t\t\t\tconfidenceField.setCaretPosition(0);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\tbreak;\n\n\t\tcase SPRT:\n\t\t\tnumSamplesField.setEnabled(false);\n\t\t\tnumSamplesField.setText(\"Unknown before sim.\");\n\t\t\tnumSamplesField.setCaretPosition(0);\n\t\t\t// If method changes, display last valid values\n\t\t\tif (autoChange) {\n\t\t\t\twidthField.setText(lastWidth);\n\t\t\t\twidthField.setCaretPosition(0);\n\t\t\t\tconfidenceField.setText(lastConf);\n\t\t\t\tconfidenceField.setCaretPosition(0);\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t}\n\n\tprivate void initTable()\n\t{\n\t\tJScrollPane sp = new JScrollPane();\n\n\t\tsp.setViewportView(initValuesTable);\n\t\ttopPanel.add(sp);\n\n\t\ttopPanel.setPreferredSize(new Dimension(300, 300));\n\t}\n\n\t/**\n\t * Populate dialog using 'information' field.\n\t */\n\tprivate void initValues()\n\t{\n\t\t// Use default initial state?\n\t\t// (currently always the case on initialisation)\n\t\tif (information.getInitialState() == null) {\n\t\t\t// Tick box\n\t\t\tuseDefaultInitialCheck.setSelected(true);\n\t\t\t// Put variable names in table, but no values\n\t\t\tfor (int i = 0; i < modulesFile.getNumVars(); i++) {\n\t\t\t\tinitValuesModel.addValue(new Value(modulesFile.getVarName(i), modulesFile.getVarType(i), null));\n\t\t\t}\n\t\t\t// Disable table\n\t\t\tif (initValuesTable.getCellEditor() != null)\n\t\t\tinitValuesTable.getCellEditor().stopCellEditing();\n\t\t\tinitValuesTable.getSelectionModel().clearSelection();\n\t\t\tinitValuesTable.setEnabled(false);\n\t\t} else {\n\t\t\t// Untick box\n\t\t\tuseDefaultInitialCheck.setSelected(false);\n\t\t\t// Set up table (from information)\n\t\t\t// Need to add to add some validity checks here if re-enabled\n\t\t\tfor (int i = 0; i < modulesFile.getNumVars(); i++) {\n\t\t\t\tinitValuesModel.addValue(new Value(modulesFile.getVarName(i), modulesFile.getVarType(i), information.getInitialState().getValue(i)));\n\t\t\t}\n\t\t\tinitValuesTable.setEnabled(true);\n\t\t}\n\n\t\t// populate parameter text boxes\n\t\twidthField.setText(\"\" + information.getWidth());\n\t\twidthField.setCaretPosition(0);\n\t\tconfidenceField.setText(\"\" + information.getConfidence());\n\t\tconfidenceField.setCaretPosition(0);\n\t\tnumSamplesField.setText(\"\" + information.getNumSamples());\n\t\tnumSamplesField.setCaretPosition(0);\n\t\t// note: do this after above \"setText\"s because it triggers a doEnablesAndCalculations()\n\t\tselectSimulationMethod.setSelectedItem(information.getMethodName());\n\t\tautomaticCalculateCombo.setSelectedItem(information.getUnknownName());\n\n\t\tpathLengthField.setText(\"\" + information.getMaxPathLength());\n\t\t//distributedCheck.setSelected(information.isDistributed());\n\t}\n\n\t/**\n\t * Create a new GUIConstantsPicker dialog to define info for simulation-based property checking.\n\t * @param parent Parent GUI window\n\t * @param exprs The properties to be checked (note: constants may not be defined)\n\t * @param modulesFile The model that will be simulated (for initial state info)\n\t * @param titleExtra Optional string to append to dialog (null if not needed)\n\t * @throws PrismException if there is a problem getting initial state info from the model.\n\t */\n\tpublic static SimulationInformation defineSimulationWithDialog(GUIPrism parent, List<Expression> exprs, ModulesFile modulesFile, String titleExtra)\n\t\t\tthrows PrismException\n\t{\n\t\treturn new GUISimulationPicker(parent, exprs, modulesFile, titleExtra).defineValues();\n\t}\n\n\t/**\n\t * Create a new GUIConstantsPicker dialog to define info for simulation-based property checking.\n\t * @param parent Parent GUI window\n\t * @param expr The property to be checked (note: constants may not be defined)\n\t * @param modulesFile The model that will be simulated (for initial state info)\n\t * @param titleExtra Optional string to append to dialog (null if not needed)\n\t * @throws PrismException if there is a problem getting initial state info from the model.\n\t */\n\tpublic static SimulationInformation defineSimulationWithDialog(GUIPrism parent, Expression expr, ModulesFile modulesFile, String titleExtra)\n\t\t\tthrows PrismException\n\t{\n\t\tList<Expression> exprs = new ArrayList<Expression>(1);\n\t\texprs.add(expr);\n\t\treturn new GUISimulationPicker(parent, exprs, modulesFile, titleExtra).defineValues();\n\t}\n\n\tpublic SimulationInformation defineValues()\n\t{\n\t\tsetVisible(true);\n\t\tif (cancelled)\n\t\t\treturn null;\n\t\telse\n\t\t\treturn information;\n\t}\n\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\t\tint i;\n\n\t\tdoEnablesAndCalculations(false);\n\n\t\tif (initValuesTable.getCellEditor() != null)\n\t\t\tinitValuesTable.getCellEditor().stopCellEditing();\n\n\t\tString parameter = \"\";\n\t\ttry {\n\t\t\t// Check (editable) simulation parameters are ok, store in SimulationInformation\n\t\t\tif (widthField.isEnabled()) {\n\t\t\t\tparameter = jLabel5.getText().substring(0, jLabel5.getText().length() - 1);\n\t\t\t\tdouble width = Double.parseDouble(widthField.getText());\n\t\t\t\tif (width <= 0) {\n\t\t\t\t\tgui.errorDialog(\"Parameter \\\"\" + parameter + \"\\\" most be positive\");\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tinformation.setWidth(width);\n\t\t\t}\n\t\t\tif (confidenceField.isEnabled()) {\n\t\t\t\tparameter = jLabel6.getText().substring(0, jLabel6.getText().length() - 1);\n\t\t\t\tdouble confidence = Double.parseDouble(confidenceField.getText());\n\t\t\t\tif (confidence <= 0 || confidence >= 1) {\n\t\t\t\t\tgui.errorDialog(\"Parameter \\\"\" + parameter + \"\\\" most be between 0 and 1\");\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tinformation.setConfidence(confidence);\n\t\t\t}\n\t\t\tif (numSamplesField.isEnabled()) {\n\t\t\t\tparameter = \"Number of samples\";\n\t\t\t\tint numSamples = Integer.parseInt(numSamplesField.getText());\n\t\t\t\tif (numSamples <= 0) {\n\t\t\t\t\tgui.errorDialog(\"Parameter \\\"\" + parameter + \"\\\" most be positive\");\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tinformation.setNumSamples(numSamples);\n\t\t\t}\n\t\t\t// Create SimulationMethod object, just to check parameters are ok\n\t\t\ttry {\n\t\t\t\tinformation.createSimulationMethod().computeMissingParameterBeforeSim();\n\t\t\t} catch (PrismException e) {\n\t\t\t\tgui.errorDialog(e.getMessage());\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t// Check/store max path length\n\t\t\tparameter = \"Maximum path length\";\n\t\t\tlong maxPathLength = Long.parseLong(pathLengthField.getText());\n\t\t\tif (maxPathLength <= 0) {\n\t\t\t\tgui.errorDialog(\"Parameter \\\"\" + parameter + \"\\\" most be positive\");\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tinformation.setMaxPathLength(maxPathLength);\n\t\t\t// Store initial state\n\t\t\tif (useDefaultInitialCheck.isSelected()) {\n\t\t\t\tinformation.setInitialState(null);\n\t\t\t} else {\n\t\t\t\tValues newInitState = new Values();\n\t\t\t\tfor (i = 0; i < initValuesModel.getNumValues(); i++) {\n\t\t\t\t\tparameter = initValuesModel.getValue(i).name;\n\t\t\t\t\tObject parameterValue = null;\n\t\t\t\t\tif (initValuesModel.getValue(i).type instanceof TypeBool) {\n\t\t\t\t\t\tString bool = initValuesModel.getValue(i).value.toString();\n\t\t\t\t\t\tif (!(bool.equals(\"true\") || bool.equals(\"false\")))\n\t\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t\tparameterValue = Boolean.valueOf(bool);\n\t\t\t\t\t} else if (initValuesModel.getValue(i).type instanceof TypeInt) {\n\t\t\t\t\t\tparameterValue = Integer.valueOf(initValuesModel.getValue(i).value.toString());\n\t\t\t\t\t} else { \n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t}\n\t\t\t\t\tnewInitState.addValue(parameter, parameterValue);\n\t\t\t\t}\n\t\t\t\tinformation.setInitialState(newInitState);\n\t\t\t}\n\t\t\t\n\t\t\t//information.setDistributed(distributedCheck.isSelected());\n\t\t\tcancelled = false;\n\t\t\tlastSimulationInformation = information;\n\t\t\tdispose();\n\t\t} catch (NumberFormatException e) {\n\t\t\tgui.errorDialog(\"Invalid value entered for parameter \\\"\" + parameter + \"\\\"\");\n\t\t}\n\n\t}//GEN-LAST:event_okayButtonActionPerformed\n\n\tprivate void useDefaultInitialCheckActionPerformed(java.awt.event.ActionEvent evt)\n\t{\n\t\t// If ticking...\n\t\tif (useDefaultInitialCheck.isSelected()) {\n\t\t\t// Clear values in table\n\t\t\tfor (int i = 0; i < modulesFile.getNumVars(); i++) {\n\t\t\t\tinitValuesModel.getValue(i).value = null;\n\t\t\t}\n\t\t\t// Disable table\n\t\t\tif (initValuesTable.getCellEditor() != null)\n\t\t\tinitValuesTable.getCellEditor().stopCellEditing();\n\t\t\tinitValuesTable.getSelectionModel().clearSelection();\n\t\t\tinitValuesTable.setEnabled(false);\n\t\t}\n\t\t// If unticking\n\t\telse {\n\t\t\t// Set up table (based on default initial state)\n\t\t\ttry {\n\t\t\t\tState defaultInitialState = modulesFile.getDefaultInitialState();\n\t\t\t\tif (defaultInitialState == null)\n\t\t\t\t\tthrow new PrismException(\"\");\n\t\t\t\tfor (int i = 0; i < modulesFile.getNumVars(); i++) {\n\t\t\t\t\tinitValuesModel.getValue(i).value = defaultInitialState.varValues[i];\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\t// In case of error, clear values\n\t\t\t\tfor (int i = 0; i < modulesFile.getNumVars(); i++) {\n\t\t\t\t\tinitValuesModel.getValue(i).value = null;\n\t\t\t\t}\n\t\t\t}\n\t\t\tinitValuesTable.setEnabled(true);\n\t\t}\n\t}\n\t\n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\t\tdispose();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\n\tpublic void keyPressed(KeyEvent e)\n\t{\n\t}\n\n\tpublic void keyReleased(KeyEvent e)\n\t{\n\t\tdoEnablesAndCalculations(false);\n\t}\n\n\tpublic void keyTyped(KeyEvent e)\n\t{\n\n\t}\n\n\tclass DefineValuesTable extends AbstractTableModel\n\t{\n\t\tArrayList<Value> values;\n\n\t\tpublic DefineValuesTable()\n\t\t{\n\t\t\tvalues = new ArrayList<Value>();\n\t\t}\n\n\t\tpublic void addValue(Value v)\n\t\t{\n\t\t\tvalues.add(v);\n\t\t\tfireTableRowsInserted(values.size() - 1, values.size() - 1);\n\t\t}\n\n\t\tpublic int getNumValues()\n\t\t{\n\t\t\treturn values.size();\n\t\t}\n\n\t\tpublic Value getValue(int i)\n\t\t{\n\t\t\treturn values.get(i);\n\t\t}\n\n\t\tpublic int getColumnCount()\n\t\t{\n\t\t\treturn 3;\n\t\t}\n\n\t\tpublic int getRowCount()\n\t\t{\n\t\t\treturn values.size();\n\t\t}\n\n\t\tpublic Object getValueAt(int rowIndex, int columnIndex)\n\t\t{\n\n\t\t\tValue v = values.get(rowIndex);\n\t\t\tswitch (columnIndex) {\n\t\t\tcase 0:\n\t\t\t\treturn v.name;\n\t\t\tcase 1:\n\t\t\t\treturn v.type.getTypeString();\n\t\t\tcase 2:\n\t\t\t\treturn v.value == null ? \"\" : v.value.toString();\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\n\t\tpublic String getColumnName(int columnIndex)\n\t\t{\n\t\t\tswitch (columnIndex) {\n\t\t\tcase 0:\n\t\t\t\treturn \"Name\";\n\t\t\tcase 1:\n\t\t\t\treturn \"Type\";\n\t\t\tcase 2:\n\t\t\t\treturn \"Value\";\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\n\t\tpublic boolean isCellEditable(int rowIndex, int columnIndex)\n\t\t{\n\t\t\tif (columnIndex == 2)\n\t\t\t\treturn true;\n\t\t\telse\n\t\t\t\treturn false;\n\t\t}\n\n\t\tpublic void setValueAt(Object aValue, int rowIndex, int columnIndex)\n\t\t{\n\t\t\tif (columnIndex == 2) {\n\t\t\t\tValue v = values.get(rowIndex);\n\t\t\t\tString s = (String) aValue;\n\t\t\t\tv.value = s;\n\t\t\t\tfireTableCellUpdated(rowIndex, columnIndex);\n\t\t\t}\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\tString str = \"\";\n\t\t\tfor (int i = 0; i < values.size(); i++) {\n\t\t\t\tValue c = values.get(i);\n\t\t\t\tstr += c.toString();\n\t\t\t\tif (i != values.size() - 1)\n\t\t\t\t\tstr += \",\";\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\n\t}\n\n\tclass Value\n\t{\n\t\tString name;\n\t\tparser.type.Type type;\n\t\tObject value;\n\n\t\tpublic Value(String name, parser.type.Type type, Object value)\n\t\t{\n\t\t\tthis.name = name;\n\t\t\tthis.type = type;\n\t\t\tthis.value = value;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn name + \"=\" + value;\n\t\t}\n\t}\n\n\tpublic class GreyableJTable extends JTable\n\t{\n\t\tprivate static final long serialVersionUID = 1L;\n\t\tprivate TableCellRenderer tableCellRenderer = new TableCellRenderer()\n\t\t{\n\t\t\tprivate static final long serialVersionUID = 1L;\n\n\t\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t\t\t{\n\t\t\t\tComponent c = GreyableJTable.super.getCellRenderer(row, column).getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);\n\t\t\t\tc.setEnabled(table != null && table.isEnabled());\n\t\t\t\treturn c;\n\t\t\t}\n\t\t};\n\n\t\tpublic TableCellRenderer getCellRenderer(int row, int column)\n\t\t{\n\t\t\treturn tableCellRenderer;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/GUITaskBar.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport javax.swing.*;\n\n\n/** This class is really for convienience.  It extends JLabel.  It sets up desirable properties for a\n * bar at the bottom of the screen describing what is currently going on and also\n * provides a simple method of removing text.\n */\npublic class GUITaskBar extends JLabel\n{\n    //CONSTANTS\n    public static final int MINIMUM_WIDTH = 45;\n    public static final int MINIMUM_HEIGHT = 20;\n    //Constructor\n    \n    /** Creates a new GUITaskBar. */\n    public GUITaskBar()\n    {\n\tsuper();\n\tsetHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n\t//setBorder(new javax.swing.border.EtchedBorder());\n\tsetMinimumSize(new java.awt.Dimension(MINIMUM_WIDTH, MINIMUM_HEIGHT));\n    }\n    \n    //Update methods\n    \n    /** Removes all text from this label. */\n    public void removeText()\n    {\n\tsetText(\" \");\n\trepaint();\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/SimulationInformation.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface;\n\nimport parser.*;\nimport prism.PrismSettings;\nimport simulator.method.*;\n\npublic class SimulationInformation\n{\n\t// PRISM settings object\n\tprivate PrismSettings settings;\n\n\t// Simulation method\n\tpublic enum Method { CI, ACI, APMC, SPRT };\n\tprivate Method method;\n\t// Unknown variable\n\tpublic enum Unknown { WIDTH, CONFIDENCE, NUM_SAMPLES };\n\tprivate Unknown unknown;\n\n\t// Settings\n\tprivate Values initialState;\n\n\n\tprivate double width;\n\tprivate double confidence;\n\tprivate int numSamples;\n\tprivate long maxPathLength;\n\n\tprivate boolean distributed;\n\tprivate boolean maxRewardGiven;\n\n\t/**\n\t * Create a new SimulationInformation object.\n\t * Default values for simulator settings are extracted from PrismSettings.\n\t * PrismSettings object is retained for other settings needed later. \n\t */\n\tpublic SimulationInformation(PrismSettings settings)\n\t{\n\t\tthis.settings = settings;\n\n\t\tthis.initialState = null;\n\n\t\tthis.method = Method.CI;\n\t\tthis.unknown = Unknown.WIDTH;\n\t\tthis.width = settings.getDouble(PrismSettings.SIMULATOR_DEFAULT_WIDTH);\n\t\tthis.confidence = settings.getDouble(PrismSettings.SIMULATOR_DEFAULT_CONFIDENCE);\n\t\tthis.numSamples = settings.getInteger(PrismSettings.SIMULATOR_DEFAULT_NUM_SAMPLES);\n\t\tthis.maxPathLength = settings.getLong(PrismSettings.SIMULATOR_DEFAULT_MAX_PATH);\n\n\n\t\tthis.distributed = false;\n\n\t\tthis.maxRewardGiven = false;\n\t}\n\n\tpublic void setMethod(Method method)\n\t{\n\t\tthis.method = method;\n\t}\n\n\tpublic Method getMethod()\n\t{\n\t\treturn method;\n\t}\n\n\tpublic void setMethodByName(String name)\n\t{\n\t\tsetMethod(Method.valueOf(name));\n\t}\n\n\tpublic String getMethodName()\n\t{\n\t\treturn method.toString();\n\t}\n\n\tpublic void setUnknown(Unknown unknown)\n\t{\n\t\tthis.unknown = unknown;\n\t}\n\n\tpublic void setUnknownByName(String name)\n\t{\n\t\tif (name.equals(\"Width\") || name.equals(\"Approximation\")) {\n\t\t\tsetUnknown(Unknown.WIDTH);\n\t\t} else if  (name.equals(\"Confidence\")) {\n\t\t\tsetUnknown(Unknown.CONFIDENCE);\n\t\t} else if (name.equals(\"Number of samples\")) {\n\t\t\tsetUnknown(Unknown.NUM_SAMPLES);\n\t\t}\n\t}\n\n\tpublic String getUnknownName()\n\t{\n\t\tswitch (unknown) {\n\t\tcase WIDTH:\n\t\t\treturn (method == Method.APMC) ? \"Approximation\" : \"Width\";\n\t\tcase CONFIDENCE:\n\t\t\treturn \"Confidence\";\n\t\tcase NUM_SAMPLES:\n\t\t\treturn \"Number of samples\";\n\t\t}\n\t\treturn null;\n\t}\n\n\tpublic Unknown getUnknown()\n\t{\n\t\treturn unknown;\n\t}\n\t\n\t/**\n\t * Getter for property initialState.\n\t * @return Value of property initialState.\n\t */\n\tpublic parser.Values getInitialState()\n\t{\n\t\treturn initialState;\n\t}\n\n\t/**\n\t * Setter for property initialState.\n\t * @param initialState New value of property initialState.\n\t */\n\tpublic void setInitialState(parser.Values initialState)\n\t{\n\t\tthis.initialState = initialState;\n\t}\n\n\tpublic double getWidth()\n\t{\n\t\treturn width;\n\t}\n\n\tpublic void setWidth(double width)\n\t{\n\t\tthis.width = width;\n\t}\n\n\t/**\n\t * Getter for property confidence.\n\t * @return Value of property confidence.\n\t */\n\tpublic double getConfidence()\n\t{\n\t\treturn confidence;\n\t}\n\n\t/**\n\t * Setter for property confidence.\n\t * @param confidence New value of property confidence.\n\t */\n\tpublic void setConfidence(double confidence)\n\t{\n\t\tthis.confidence = confidence;\n\t}\n\n\tpublic int getNumSamples()\n\t{\n\t\treturn numSamples;\n\t}\n\n\tpublic void setNumSamples(int numSamples)\n\t{\n\t\tthis.numSamples = numSamples;\n\t}\n\n\t/**\n\t * Getter for property maxPathLength.\n\t * @return Value of property maxPathLength.\n\t */\n\tpublic long getMaxPathLength()\n\t{\n\t\treturn maxPathLength;\n\t}\n\n\t/**\n\t * Setter for property maxPathLength.\n\t * @param maxPathLength New value of property maxPathLength.\n\t */\n\tpublic void setMaxPathLength(long maxPathLength)\n\t{\n\t\tthis.maxPathLength = maxPathLength;\n\t}\n\n\tpublic void setPropReward(boolean b)\n\t{\n\t\tthis.maxRewardGiven = b;\n\t}\n\n\t/**\n\t * Getter for property distributed.\n\t * @return Value of property distributed.\n\t */\n\tpublic boolean isDistributed()\n\t{\n\t\treturn distributed;\n\t}\n\n\t/**\n\t * Setter for property distributed.\n\t * @param distributed New value of property distributed.\n\t */\n\tpublic void setDistributed(boolean distributed)\n\t{\n\t\tthis.distributed = distributed;\n\t}\n\n\t/**\n\t * create and return the selected method of simulation\n\t * @return the method of simulation\n\t */\n\tpublic SimulationMethod createSimulationMethod()\n\t{\n\t\t// Extract some simulator options, in case needed, from PRISM settings\n\t\tdouble maxReward = settings.getDouble(PrismSettings.SIMULATOR_MAX_REWARD);\n\t\tboolean numberToDecideGiven = settings.getBoolean(PrismSettings.SIMULATOR_DECIDE);\n\t\tint numberToDecide = settings.getInteger(PrismSettings.SIMULATOR_ITERATIONS_TO_DECIDE);\n\n\t\tswitch (method) {\n\t\tcase CI:\n\t\t\tswitch (unknown) {\n\t\t\tcase WIDTH:\n\t\t\t\treturn new CIwidth(confidence, numSamples);\n\t\t\tcase CONFIDENCE:\n\t\t\t\treturn new CIconfidence(width, numSamples);\n\t\t\tcase NUM_SAMPLES:\n\t\t\t\tif (numberToDecideGiven) {\n\t\t\t\t\treturn new CIiterations(confidence, width, numberToDecide);\n\t\t\t\t} else {\n\t\t\t\t\tif (maxRewardGiven)\n\t\t\t\t\t\treturn new CIiterations(confidence, width, maxReward);\n\t\t\t\t\telse\n\t\t\t\t\t\treturn new CIiterations(confidence, width);\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t\t}\n\t\tcase ACI:\n\t\t\tswitch (unknown) {\n\t\t\tcase WIDTH:\n\t\t\t\treturn new ACIwidth(confidence, numSamples);\n\t\t\tcase CONFIDENCE:\n\t\t\t\treturn new ACIconfidence(width, numSamples);\n\t\t\tcase NUM_SAMPLES:\n\t\t\t\tif (numberToDecideGiven) {\n\t\t\t\t\treturn new ACIiterations(confidence, width, numberToDecide);\n\t\t\t\t} else {\n\t\t\t\t\tif (maxRewardGiven)\n\t\t\t\t\t\treturn new ACIiterations(confidence, width, maxReward);\n\t\t\t\t\telse\n\t\t\t\t\t\treturn new ACIiterations(confidence, width);\n\t\t\t\t}\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t\t}\n\t\tcase APMC:\n\t\t\tswitch (unknown) {\n\t\t\tcase WIDTH:\n\t\t\t\treturn new APMCapproximation(confidence, numSamples);\n\t\t\tcase CONFIDENCE:\n\t\t\t\treturn new APMCconfidence(width, numSamples);\n\t\t\tcase NUM_SAMPLES:\n\t\t\t\treturn new APMCiterations(confidence, width);\n\t\t\tdefault:\n\t\t\t\treturn null;\n\t\t\t}\n\t\tcase SPRT:\n\t\t\treturn new SPRTMethod(confidence, confidence, width);\n\t\tdefault:\n\t\t\treturn null;\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/src/userinterface/graph/AxisSettings.java",
    "content": "//==============================================================================\r\n//\t\r\n//\tCopyright (c) 2002-\r\n//\tAuthors:\r\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\r\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\r\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\r\n//\t* Alistair John Strachan <alistair@devzero.co.uk> (University of Edinburgh)\r\n//\t* Mike Arthur <mike@mikearthur.co.uk> (University of Edinburgh)\r\n//\t* Zak Cohen <zakcohen@gmail.com> (University of Edinburgh)\r\n//\t\r\n//------------------------------------------------------------------------------\r\n//\t\r\n//\tThis file is part of PRISM.\r\n//\t\r\n//\tPRISM is free software; you can redistribute it and/or modify\r\n//\tit under the terms of the GNU General Public License as published by\r\n//\tthe Free Software Foundation; either version 2 of the License, or\r\n//\t(at your option) any later version.\r\n//\t\r\n//\tPRISM is distributed in the hope that it will be useful,\r\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r\n//\tGNU General Public License for more details.\r\n//\t\r\n//\tYou should have received a copy of the GNU General Public License\r\n//\talong with PRISM; if not, write to the Free Software Foundation,\r\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n//\t\r\n//==============================================================================\r\n\r\npackage userinterface.graph;\r\n\r\nimport settings.*;\r\n\r\nimport java.awt.*;\r\nimport java.text.DecimalFormat;\r\nimport java.text.NumberFormat;\r\nimport java.util.*;\r\n\r\nimport org.jfree.chart.*;\r\n\r\nimport org.jfree.chart.plot.*;\r\nimport org.jfree.chart.axis.*;\r\nimport org.jfree.data.*;\r\nimport org.jfree.data.xy.*;\r\n\r\nimport org.w3c.dom.Element;\r\n\r\n/**\r\n * Representation of an axis of a Graph.\r\n * The settings are propagated to the JFreeChart library.\r\n */\r\npublic class AxisSettings extends Observable implements SettingOwner\r\n{\r\n\tprivate String name;\r\n\tprivate SettingDisplay display;\r\n\t\r\n\t/** Our graph object. */\r\n\tprivate Graph graph;\r\n\t\r\n\t/** JFreeChart representation of graphs. */\r\n\tprivate JFreeChart chart;\r\n\t\r\n\t/** XYPlot of this JFreeChart */\r\n\tprivate XYPlot plot;\r\n\t\r\n\t/** JFreeChart representation of this axis. */\r\n\tprivate ValueAxis axis;\r\n\t\r\n\t/** True when this reprents the domain axis. */\r\n\tprivate boolean isDomain;\r\n\t\r\n\tprivate SingleLineStringSetting heading;\r\n\tprivate FontColorSetting headingFont;\r\n\tprivate FontColorSetting numberFont;\r\n\t\r\n\tprivate BooleanSetting showGrid;\r\n\tprivate ColorSetting gridColour;\r\n\tprivate ChoiceSetting scaleType;\r\n\t\r\n\tprivate BooleanSetting autoScale;\r\n\tprivate DoubleSetting minValue;\r\n\tprivate DoubleSetting maxValue;\r\n\tprivate DoubleSetting gridInterval;\r\n\tprivate DoubleSetting minimumPower;\r\n\tprivate DoubleSetting maximumPower;\r\n\t\r\n\tprivate DoubleSetting logBase;\r\n\tprivate ChoiceSetting logStyle;\r\n\t\r\n\t/** Choice for scale. Displays a linear scale */\r\n\tpublic static final int NORMAL_SCALE = 0;\r\n\t/** Choice for scale. Displays a logarithmic scale */\r\n\tpublic static final int LOGARITHMIC_SCALE = 1;\r\n\t\r\n\t/** Choice for display of logarithmic scale. Displays actual values (0.1, 10, 1000, etc.). */\r\n\tpublic static final int VALUES = 0;\r\n\t/** Choice for display of logarithmic scale. Displays values in scientific form (10^-1, 10^1, 10^3, etc.). */\r\n\tpublic static final int BASE_AND_EXPONENT = 1;\r\n\t\r\n\tpublic NumberFormat valuesFormatter;\r\n\t\t\r\n\tboolean activated = false;\r\n\t\r\n\tpublic AxisSettings(String name, boolean isDomain, Graph graph)\r\n\t{\r\n\t\tthis.name = name;\r\n\t\tthis.isDomain = isDomain;\r\n\t\tthis.graph = graph;\r\n\t\tthis.chart = graph.getChart();\r\n\t\tthis.plot = chart.getXYPlot();\r\n\t\tthis.axis = (isDomain) ? this.plot.getDomainAxis() : this.plot.getRangeAxis();\r\n\t\t\r\n\t\tthis.valuesFormatter = NumberFormat.getInstance(Locale.UK);\r\n\t\t\r\n\t\tif (this.valuesFormatter instanceof DecimalFormat)\r\n\t\t\t((DecimalFormat) this.valuesFormatter).applyPattern(\"###,###,###,###,###,###,###,###.########################\");\r\n\t\t\t\t\r\n\t\t/* Initialise all the settings. */\r\n\t\theading = new SingleLineStringSetting(\"heading\", name, \"The heading for this axis\", this, true);\r\n\t\theadingFont = new FontColorSetting(\"heading font\", new FontColorPair(new Font(\"SansSerif\", Font.PLAIN, 12), Color.black), \"The font for this axis' heading.\", this, true);\r\n\t\tnumberFont = new FontColorSetting(\"numbering font\", new FontColorPair(new Font(\"SansSerif\", Font.PLAIN, 12), Color.black), \"The font used to number the axis.\", this, true);\r\n\t\t\r\n\t\tshowGrid = new BooleanSetting(\"show gridlines\", Boolean.valueOf(true), \"Should the gridlines be visible\", this, true);\r\n\t\tgridColour = new ColorSetting(\"gridline colour\", new Color(204,204,204), \"The colour of the gridlines\", this, true);\r\n\t\t\r\n\t\tString[] logarithmicChoices = {\"Normal\", \"Logarithmic\"};\r\n\t\tscaleType = new ChoiceSetting(\"scale type\", logarithmicChoices, logarithmicChoices[0], \"Should the scale be normal, or logarithmic\", this, true);\r\n\t\tautoScale = new BooleanSetting(\"auto-scale\", Boolean.valueOf(true), \"When set to true, all minimum values, maximum values, grid intervals, maximum logarithmic powers and minimum logarithmic powers are automatically set and maintained when the data changes.\", this, true);\r\n\t\tminValue = new DoubleSetting(\"minimum value\", Double.valueOf(0.0), \"The minimum value for the axis\", this, true);\r\n\t\tmaxValue = new DoubleSetting(\"maximum value\", Double.valueOf(1.0), \"The maximum value for the axis\", this, true);\r\n\t\tgridInterval = new DoubleSetting(\"gridline interval\", Double.valueOf(0.2), \"The interval between gridlines\", this, false, new RangeConstraint(0, Double.POSITIVE_INFINITY, false, true));\r\n\t\tlogBase = new DoubleSetting(\"log base\", Double.valueOf(10), \"The base for the logarithmic scale\", this, false, new RangeConstraint(\"1,\"));\r\n\t\t\r\n\t\tminimumPower = new DoubleSetting(\"minimum power\", Double.valueOf(\"0.0\"), \"The minimum logarithmic power that should be displayed on the scale\", this, true);\r\n\t\tmaximumPower = new DoubleSetting(\"maximum power\", Double.valueOf(\"1.0\"), \"The maximum logarithmic power that should be displayed on the scale\", this, true);\r\n\t\t\r\n\t\tString[] logStyleChoices = {\"Values\", \"Base and exponent\"};\r\n\t\tlogStyle = new ChoiceSetting(\"logarithmic number style\", logStyleChoices, logStyleChoices[1], \"Should the style of the logarithmic scale show the actual values, or the base with the exponent.\", this, false);\r\n\t\t\r\n\t\t/* Add constraints. */\t\t\r\n\t\tminValue.addConstraint(new NumericConstraint()\r\n\t\t{\r\n\t\t\tpublic void checkValueDouble(double d) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && d >= maxValue.getDoubleValue()) throw new SettingException(\"Minimum value should be < Maximum value\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tpublic void checkValueInteger(int i) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && i >= maxValue.getDoubleValue()) throw new SettingException(\"Minimum value should be < Maximum value\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tpublic void checkValueLong(long i) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && i >= maxValue.getDoubleValue()) throw new SettingException(\"Minimum value should be < Maximum value\");\r\n\t\t\t}\r\n\t\t});\r\n\t\tmaxValue.addConstraint(new NumericConstraint()\r\n\t\t{\r\n\t\t\tpublic void checkValueDouble(double d) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && d <= minValue.getDoubleValue()) throw new SettingException(\"Maximum value should be > Minimum value\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tpublic void checkValueInteger(int i) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && i <= minValue.getDoubleValue()) throw new SettingException(\"Maximum value should be > Minimum value\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tpublic void checkValueLong(long i) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && i <= maxValue.getDoubleValue()) throw new SettingException(\"Minimum value should be > Maximum value\");\r\n\t\t\t}\r\n\t\t});\r\n\t\tminimumPower.addConstraint(new NumericConstraint()\r\n\t\t{\r\n\t\t\tpublic void checkValueDouble(double d) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && d >= maximumPower.getDoubleValue()) throw new SettingException(\"Minimum power should be < Maximum power\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tpublic void checkValueInteger(int i) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && i >= maximumPower.getDoubleValue()) throw new SettingException(\"Minimum power should be < Maximum power\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tpublic void checkValueLong(long i) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && i >= maximumPower.getDoubleValue()) throw new SettingException(\"Minimum power should be < Maximum power\");\r\n\t\t\t}\r\n\t\t});\r\n\t\tmaximumPower.addConstraint(new NumericConstraint()\r\n\t\t{\r\n\t\t\tpublic void checkValueDouble(double d) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && d <= minimumPower.getDoubleValue()) throw new SettingException(\"Maximum power should be > Minimum power\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tpublic void checkValueInteger(int i) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && i <= minimumPower.getDoubleValue()) throw new SettingException(\"Maximum power should be > Minimum power\");\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tpublic void checkValueLong(long i) throws SettingException\r\n\t\t\t{\r\n\t\t\t\tif(activated && i <= minimumPower.getDoubleValue()) throw new SettingException(\"Maximum power should be > Minimum power\");\r\n\t\t\t}\r\n\t\t});\r\n\t\t\r\n\t\tdoEnables();\r\n\t\tdisplay = null;\t\t\r\n\t\tactivated = true;\r\n\t\t\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers();\r\n\t}\r\n\t\r\n\tpublic int compareTo(Object o)\r\n\t{\r\n\t\tif(o instanceof SettingOwner)\r\n\t\t{\r\n\t\t\tSettingOwner po = (SettingOwner) o;\r\n\t\t\tif(getSettingOwnerID() < po.getSettingOwnerID() )return -1;\r\n\t\t\telse if(getSettingOwnerID() > po.getSettingOwnerID()) return 1;\r\n\t\t\telse return 0;\r\n\t\t}\r\n\t\telse return 0;\r\n\t}\r\n\t\r\n\tpublic String getClassDescriptor()\r\n\t{\r\n\t\treturn \"Axis\";\r\n\t}\r\n\t\r\n\tpublic String getDescriptor()\r\n\t{\r\n\t\treturn name;\r\n\t}\r\n\t\r\n\tpublic int getNumSettings()\r\n\t{\r\n\t\treturn 14;\r\n\t}\r\n\t\r\n\tpublic String getSettingOwnerName()\r\n\t{\r\n\t\treturn heading.getStringValue();\r\n\t}\r\n\t\r\n\tpublic Setting getSetting(int index)\r\n\t{\r\n\t\tswitch(index)\r\n\t\t{\r\n\t\t\tcase 0 : return heading;\r\n\t\t\tcase 1 : return headingFont;\r\n\t\t\tcase 2 : return numberFont;\r\n\t\t\tcase 3 : return showGrid;\r\n\t\t\tcase 4 : return gridColour;\r\n\t\t\tcase 5 : return scaleType;\r\n\t\t\tcase 6 : return autoScale;\r\n\t\t\tcase 7 : return minValue;\r\n\t\t\tcase 8 : return maxValue;\r\n\t\t\tcase 9: return gridInterval;\r\n\t\t\tcase 10: return minimumPower;\r\n\t\t\tcase 11: return maximumPower;\r\n\t\t\tcase 12: return logBase;\r\n\t\t\tcase 13: return logStyle;\r\n\t\t\tdefault: return null;\t\t\t\r\n\t\t}\r\n\t}\r\n\t\r\n\tpublic int getSettingOwnerID()\r\n\t{\r\n\t\treturn prism.PropertyConstants.AXIS;\r\n\t}\r\n\t\r\n\tpublic String getSettingOwnerClassName()\r\n\t{\r\n\t\treturn \"Axis\";\r\n\t}\t\t\r\n\t\r\n\tpublic void doEnables()\r\n\t{\r\n\t\tminimumPower.setEnabled(!autoScale.getBooleanValue() && scaleType.getCurrentIndex() == LOGARITHMIC_SCALE);\r\n\t\tmaximumPower.setEnabled(!autoScale.getBooleanValue() && scaleType.getCurrentIndex() == LOGARITHMIC_SCALE);\r\n\t\tlogBase.setEnabled(scaleType.getCurrentIndex()== LOGARITHMIC_SCALE);\r\n\t\tlogStyle.setEnabled(scaleType.getCurrentIndex()== LOGARITHMIC_SCALE);\r\n\t\tminValue.setEnabled(!autoScale.getBooleanValue() && scaleType.getCurrentIndex() == NORMAL_SCALE);\r\n\t\tmaxValue.setEnabled(!autoScale.getBooleanValue() && scaleType.getCurrentIndex() == NORMAL_SCALE);\r\n\t\tgridInterval.setEnabled(!autoScale.getBooleanValue() && scaleType.getCurrentIndex() == NORMAL_SCALE);\r\n\t}\t\r\n\t\r\n\tpublic void notifySettingChanged(Setting setting)\r\n\t{\r\n\t\tdoEnables();\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers(this);\t\t\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property heading.\r\n\t * @return Value of property heading.\r\n\t */\r\n\tpublic String getHeading()\r\n\t{\r\n\t\treturn heading.getStringValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property heading.\r\n\t * @param value Value of property heading.\r\n\t */\r\n\tpublic void setHeading(String value)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\theading.setValue(value);\r\n\t\t\tdoEnables();\r\n\t\t\tupdateAxis();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\t\r\n\t\r\n\t/**\r\n\t * Getter for property headingFont.\r\n\t * @return Value of property headingFont.\r\n\t */\r\n\tpublic FontColorPair getHeadingFont()\r\n\t{\r\n\t\treturn headingFont.getFontColorValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property headingfont.\r\n\t * @param value Value of property headingfont.\r\n\t */\r\n\tpublic void setHeadingFont(FontColorPair value)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\theadingFont.setValue(value);\r\n\t\t\tdoEnables();\r\n\t\t\tupdateAxis();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\r\n\t\t\r\n\t/**\r\n\t * Getter for property numberFont.\r\n\t * @return Value of property numberFont.\r\n\t */\r\n\tpublic FontColorPair getNumberFont()\r\n\t{\r\n\t\treturn numberFont.getFontColorValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property numberfont.\r\n\t * @param value Value of property numberfont.\r\n\t */\r\n\tpublic void setNumberFont(FontColorPair value)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\tnumberFont.setValue(value);\r\n\t\t\tdoEnables();\r\n\t\t\tupdateAxis();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property autoScale.\r\n\t * @return Value of property autoScale.\r\n\t */\r\n\tpublic boolean isAutoScale()\r\n\t{\r\n\t\treturn autoScale.getBooleanValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property autoScale.\r\n\t * @param value Value of property autoScale.\r\n\t */\r\n\tpublic void setAutoScale(boolean value)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\tautoScale.setValue(Boolean.valueOf(value));\r\n\t\t\tdoEnables();\r\n\t\t\tupdateAxis();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property showGrid.\r\n\t * @return Value of property showGrid.\r\n\t */\r\n\tpublic boolean showGrid()\r\n\t{\r\n\t\treturn showGrid.getBooleanValue();\r\n\t}\r\n\t\r\n\t\r\n\t\r\n\t/**\r\n\t * Setter for property showGrid.\r\n\t * @param value Value of property showGrid.\r\n\t */\r\n\tpublic void showGrid(boolean value)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\tshowGrid.setValue(Boolean.valueOf(value));\r\n\t\t\tdoEnables();\r\n\t\t\tupdateAxis();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property gridColour.\r\n\t * @return Value of property gridColour.\r\n\t */\r\n\tpublic Color getGridColour() \r\n\t{\r\n\t\treturn gridColour.getColorValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property gridColour.\r\n\t * @param value Value of property gridColour.\r\n\t */\r\n\tpublic void setGridColour(Color value)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\tgridColour.setValue(value);\r\n\t\t\tdoEnables();\r\n\t\t\tupdateAxis();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\r\n\t\t\r\n\t/**\r\n\t * Getter for property scaleType.\r\n\t * @return Value of property scaleType (either NORMAL_SCALE, or LOGARITHMIC_SCALE).\r\n\t */\r\n\tpublic int getScaleType()\r\n\t{\r\n\t\treturn scaleType.getCurrentIndex();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property scaleType.\r\n\t * @param value Value of property scaleType (either NORMAL_SCALE, or LOGARITHMIC_SCALE).\r\n\t */\r\n\tpublic void setScaleType(int value) throws SettingException\r\n\t{\t\t\r\n\t\tscaleType.setSelectedIndex(value);\r\n\t\tdoEnables();\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers(this);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Checks whether this axis has a logarithmic scale.\r\n\t * @return (getScaleType() == LOGARITHMIC_SCALE).\r\n\t */\r\n\tpublic boolean isLogarithmic()\r\n\t{\r\n\t\treturn (scaleType.getCurrentIndex() == LOGARITHMIC_SCALE);\r\n\t}\t\r\n\t\r\n\t/**\r\n\t * Getter for property logarithmic.\r\n\t * @return Value of property logarithmic (either VALUES, or BASE_AND_EXPONENT).\r\n\t */\r\n\tpublic int getLogStyle()\r\n\t{\r\n\t\treturn logStyle.getCurrentIndex();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property logarithmic.\r\n\t * @param value Value of property logarithmic (either VALUES, or BASE_AND_EXPONENT).\r\n\t */\r\n\tpublic void setLogStyle(int value) throws SettingException\r\n\t{\t\t\r\n\t\tlogStyle.setSelectedIndex(value);\r\n\t\tdoEnables();\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers(this);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property minValue.\r\n\t * @return Value of property minValue.\r\n\t */\r\n\tpublic double getMinValue()\r\n\t{\r\n\t\treturn minValue.getDoubleValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property minValue.\r\n\t * @param value Value of property minValue.\r\n\t */\r\n\tpublic void setMinValue(double value) throws SettingException\r\n\t{\t\t\r\n\t\tminValue.setValue(value);\r\n\t\tdoEnables();\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers(this);\r\n\t}\r\n\t\t\r\n\t/**\r\n\t * Getter for property maxValue.\r\n\t * @return Value of property maxValue.\r\n\t */\r\n\tpublic double getMaxValue()\r\n\t{\r\n\t\treturn maxValue.getDoubleValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property maxValue.\r\n\t * @param value Value of property maxValue.\r\n\t */\r\n\tpublic void setMaxValue(double value) throws SettingException\r\n\t{\t\t\r\n\t\tmaxValue.setValue(value);\r\n\t\tdoEnables();\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers(this);\r\n\t}\r\n\t\t\r\n\t/**\r\n\t * Getter for property gridInterval.\r\n\t * @return Value of property gridInterval.\r\n\t */\r\n\tpublic double getGridInterval()\r\n\t{\r\n\t\treturn gridInterval.getDoubleValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property gridInterval.\r\n\t * @param value Value of property gridInterval.\r\n\t */\r\n\tpublic void setGridInterval(Double value)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\tgridInterval.setValue(value);\r\n\t\t\tdoEnables();\r\n\t\t\tupdateAxis();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property logBase.\r\n\t * @return Value of property logBase.\r\n\t */\r\n\tpublic double getLogBase()\r\n\t{\r\n\t\treturn logBase.getDoubleValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property logBase.\r\n\t * @param value Value of property logBase.\r\n\t */\r\n\tpublic void setLogBase(double value) throws SettingException\r\n\t{\t\t\r\n\t\tlogBase.setValue(value);\r\n\t\tdoEnables();\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers(this);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property minimumPower.\r\n\t * @return Value of property minimumPower.\r\n\t */\r\n\tpublic double getMinimumPower()\r\n\t{\r\n\t\treturn minimumPower.getDoubleValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property minimumPower.\r\n\t * @param value Value of property minimumPower.\r\n\t */\r\n\tpublic void setMinimumPower(double value) throws SettingException\r\n\t{\t\t\r\n\t\tminimumPower.setValue(Double.valueOf(value));\r\n\t\tdoEnables();\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers(this);\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property maximumPower.\r\n\t * @return Value of property maximumPower.\r\n\t */\r\n\tpublic double getMaximumPower()\r\n\t{\r\n\t\treturn maximumPower.getDoubleValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property maximumPower.\r\n\t * @param value Value of property maximumPower.\r\n\t */\r\n\tpublic void setMaximumPower(double value) throws SettingException\r\n\t{\t\t\r\n\t\tmaximumPower.setValue(Double.valueOf(value));\r\n\t\tdoEnables();\r\n\t\tupdateAxis();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers(this);\r\n\t}\r\n\r\n\tpublic SettingDisplay getDisplay() \r\n\t{\t\t\r\n\t\treturn display;\r\n\t}\r\n\r\n\tpublic void setDisplay(SettingDisplay display) \r\n\t{\r\n\t\tthis.display = display;\r\n\t}\r\n\t\r\n\tprivate void updateAxis()\r\n\t{\r\n\t\t/** -- First check whether we still have the right axis object */\r\n\t\t\r\n\t\t/* If we do not have a logarithmic scale, but the axis settings want one, then change the axis. */\r\n\t\tif (axis instanceof NumberAxis && isLogarithmic())\r\n\t\t{\r\n\t\t\t/** Update xAxis such that other settings can be checked for consistency. */\r\n\t\t\tPrismLogarithmicAxis newAxis = new PrismLogarithmicAxis(getHeading());\r\n\t\t\t\r\n\t\t\t/** We need to discard all negative and zero values should there be any. */\r\n\t\t\t/* TODO: Do this in a more elegant way. */\r\n\t\t\tsynchronized (graph.getSeriesLock())\r\n\t\t\t{\r\n\t\t\t\tfor (Graph.SeriesKey key : graph.getAllSeriesKeys())\r\n\t\t\t\t{\t\t\t\t\t\r\n\t\t\t\t\tXYSeries series = graph.getXYSeries(key);\r\n\t\t\t\t\t\r\n\t\t\t\t\tif (series instanceof PrismXYSeries)\r\n\t\t\t\t\t{\r\n\t\t\t\t\t\tPrismXYSeries prismSeries = (PrismXYSeries)series;\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\tif (isDomain)\r\n\t\t\t\t\t\t\tprismSeries.setLogarithmicDomainAxis(true);\r\n\t\t\t\t\t\telse\r\n\t\t\t\t\t\t\tprismSeries.setLogarithmicRangeAxis(true);\r\n\t\t\t\t\t}\t\t\t\t\t\t\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tif (isDomain)\r\n\t\t\t{\r\n\t\t\t\tthis.plot.setDomainAxis(newAxis);\r\n\t\t\t\taxis = this.plot.getDomainAxis();\r\n\t\t\t}\r\n\t\t\telse\r\n\t\t\t{\r\n\t\t\t\tthis.plot.setRangeAxis(newAxis);\r\n\t\t\t\taxis = this.plot.getRangeAxis();\r\n\t\t\t}\t\t\t\t\r\n\t\t}\r\n\t\t\r\n\t\t/* If we have a logarithmic scale, but the axis settings want a normal scale, then change the axis. */\r\n\t\tif (axis instanceof PrismLogarithmicAxis && !isLogarithmic())\r\n\t\t{\r\n\t\t\t/** Update xAxis such that other settings can be checked for consistency. */\r\n\t\t\tif (isDomain) \r\n\t\t\t{\r\n\t\t\t\tthis.plot.setDomainAxis(new NumberAxis(getHeading()));\r\n\t\t\t\taxis = this.plot.getDomainAxis();\r\n\t\t\t}\r\n\t\t\telse\r\n\t\t\t{\r\n\t\t\t\tthis.plot.setRangeAxis(new NumberAxis(getHeading()));\r\n\t\t\t\taxis = this.plot.getRangeAxis();\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\t/** It could be we discarded some negative and zero values, lets bring them back. */\r\n\t\t\tsynchronized (graph.getSeriesLock())\r\n\t\t\t{\r\n\t\t\t\tfor (Graph.SeriesKey key : graph.getAllSeriesKeys())\r\n\t\t\t\t{\t\t\t\t\t\r\n\t\t\t\t\tXYSeries series = graph.getXYSeries(key);\r\n\t\t\t\t\t\r\n\t\t\t\t\tif (series instanceof PrismXYSeries)\r\n\t\t\t\t\t{\r\n\t\t\t\t\t\tPrismXYSeries prismSeries = (PrismXYSeries)series;\r\n\t\t\t\t\t\t\r\n\t\t\t\t\t\tif (isDomain)\r\n\t\t\t\t\t\t\tprismSeries.setLogarithmicDomainAxis(false);\r\n\t\t\t\t\t\telse\r\n\t\t\t\t\t\t\tprismSeries.setLogarithmicRangeAxis(false);\r\n\t\t\t\t\t}\t\t\t\t\t\t\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t\t\r\n\t\t/** -- Check done, now look for smaller changes. */\t\t\r\n\t\t\r\n\t\t/* If the heading of the axis does not match the heading set in the settings... */\r\n\t\tif (!(axis.getLabel().equals(getHeading())))\r\n\t\t{\r\n\t\t\taxis.setLabel(getHeading());\r\n\t\t}\r\n\t\t\r\n\t\t/* Update axis heading font if appropriate */\r\n\t\tif (!(axis.getLabelFont().equals(getHeadingFont().f)))\r\n\t\t{\r\n\t\t\taxis.setLabelFont(getHeadingFont().f);\r\n\t\t}\t\r\n\t\t\r\n\t\t/* Update axis heading colour if appropriate */\r\n\t\tif (!(axis.getLabelPaint().equals(getHeadingFont().c)))\r\n\t\t{\r\n\t\t\taxis.setLabelPaint(getHeadingFont().c);\r\n\t\t}\r\n\t\t\r\n\t\t/* Update axis numbering font if appropriate */\r\n\t\tif (!(axis.getTickLabelFont().equals(getNumberFont().f)))\r\n\t\t{\r\n\t\t\taxis.setTickLabelFont(getNumberFont().f);\r\n\t\t}\t\r\n\t\t\r\n\t\t/* Update axis numbering colour if appropriate */\r\n\t\tif (!(axis.getTickLabelPaint().equals(getNumberFont().c)))\r\n\t\t{\r\n\t\t\taxis.setTickLabelPaint(getNumberFont().c);\r\n\t\t}\r\n\t\t\r\n\t\t/* Update gridlines if appropriate. */\r\n\t\tif (isDomain && (plot.isDomainGridlinesVisible() != showGrid.getBooleanValue()))\r\n\t\t{\r\n\t\t\tplot.setDomainGridlinesVisible(showGrid.getBooleanValue());\r\n\t\t}\t\t\r\n\t\t\r\n\t\tif (!isDomain && (plot.isRangeGridlinesVisible() != showGrid.getBooleanValue()))\r\n\t\t{\r\n\t\t\tplot.setRangeGridlinesVisible(showGrid.getBooleanValue());\r\n\t\t}\r\n\t\t\r\n\t\t/* Update gridline colour if appropriate. */\r\n\t\tif (isDomain && (!plot.getDomainGridlinePaint().equals(gridColour.getColorValue())))\r\n\t\t{\r\n\t\t\tplot.setDomainGridlinePaint(gridColour.getColorValue());\r\n\t\t}\r\n\t\t\r\n\t\tif (!isDomain && (!plot.getRangeGridlinePaint().equals(gridColour.getColorValue())))\r\n\t\t{\r\n\t\t\tplot.setRangeGridlinePaint(gridColour.getColorValue());\r\n\t\t}\t\t\r\n\t\t\r\n\t\t/** Check properties specific to logarithmic axis. */\r\n\t\tif (axis instanceof PrismLogarithmicAxis)\r\n\t\t{\r\n\t\t\tPrismLogarithmicAxis logAxis = (PrismLogarithmicAxis)axis;\r\n\t\t\t\r\n\t\t\tif ((logStyle.getCurrentIndex() == BASE_AND_EXPONENT) != logAxis.isBaseAndExponentFormatOverride())\r\n\t\t\t{\t\t\t\t\r\n\t\t\t\tlogAxis.setBaseAndExponentFormatOverride(logStyle.getCurrentIndex() == BASE_AND_EXPONENT);\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\tif ((logStyle.getCurrentIndex() == VALUES) && logAxis.getNumberFormatOverride() != this.valuesFormatter)\r\n\t\t\t{\t\t\t\t\r\n\t\t\t\tlogAxis.setNumberFormatOverride(this.valuesFormatter);\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\t/* Switched from auto to manual? */\t\t\t\r\n\t\t\tif (logAxis.isAutoRange() && !autoScale.getBooleanValue())\r\n\t\t\t{\r\n\t\t\t\tRange range = logAxis.getRange();\r\n\t\t\t\tlogAxis.setAutoRange(false);\r\n\t\t\t\t\r\n\t\t\t\ttry\r\n\t\t\t\t{\r\n\t\t\t\t\tthis.minimumPower.setValue(logAxis.calculateLog(range.getLowerBound()));\r\n\t\t\t\t\tthis.maximumPower.setValue(logAxis.calculateLog(range.getUpperBound()));\r\n\t\t\t\t}\r\n\t\t\t\tcatch (SettingException e)\r\n\t\t\t\t{\r\n\t\t\t\t\t// best effort.\r\n\t\t\t\t}\t\t\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\t/* Switched from manual to auto? */\r\n\t\t\tif (!axis.isAutoRange() && autoScale.getBooleanValue())\r\n\t\t\t{\t\t\t\r\n\t\t\t\taxis.setAutoRange(true);\t\t\t\t\t\t\t\r\n\t\t\t}\t\r\n\t\t\t\r\n\t\t\t/* If the log base is wrong. */\r\n\t\t\tif (logBase.getDoubleValue() != logAxis.getBase())\r\n\t\t\t{\r\n\t\t\t\tRange range = axis.getRange();\r\n\t\t\t\t\t\t\t\r\n\t\t\t\tlogAxis.setBase(logBase.getDoubleValue());\r\n\t\t\t\t\r\n\t\t\t\ttry\r\n\t\t\t\t{\r\n\t\t\t\t\tthis.minimumPower.setValue(logAxis.calculateLog(range.getLowerBound()));\t\t\t\t\r\n\t\t\t\t\tthis.maximumPower.setValue(logAxis.calculateLog(range.getUpperBound()));\r\n\t\t\t\t}\r\n\t\t\t\tcatch (SettingException e)\r\n\t\t\t\t{\r\n\t\t\t\t\t// best effort\r\n\t\t\t\t}\r\n\t\t\t\t\r\n\t\t\t\tif (Math.round(logBase.getDoubleValue()) == logBase.getDoubleValue())\r\n\t\t\t\t\tlogAxis.setMinorTickCount((int)logBase.getDoubleValue());\r\n\t\t\t\telse\r\n\t\t\t\t\tlogAxis.setMinorTickCount(1);\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\t/* If manual, logarithmic, and range does not match our settings, then update */\r\n\t\t\tif (!axis.isAutoRange())\r\n\t\t\t{\t\r\n\t\t\t\tRange range = logAxis.getRange();\r\n\t\t\t\t\t\t\t\t\r\n\t\t\t\tif (range.getLowerBound() != logAxis.calculateValue(minimumPower.getDoubleValue()) || range.getUpperBound() != logAxis.calculateValue(maximumPower.getDoubleValue()))\r\n\t\t\t\t{\r\n\t\t\t\t\taxis.setRange(logAxis.calculateValue(minimumPower.getDoubleValue()), logAxis.calculateValue(maximumPower.getDoubleValue()));\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\t\t\r\n\t\t\r\n\t\t/** Check properties specific to numeric axis. */\r\n\t\tif (axis instanceof NumberAxis)\r\n\t\t{\r\n\t\t\tNumberAxis numAxis = (NumberAxis)axis;\r\n\t\t\t\r\n\t\t\t/* Switched from auto to manual? */\r\n\t\t\tif (axis.isAutoRange() && !autoScale.getBooleanValue())\r\n\t\t\t{\r\n\t\t\t\tRange range = axis.getRange();\r\n\t\t\t\taxis.setAutoRange(false);\r\n\t\t\t\taxis.setAutoTickUnitSelection(false);\t\t\t\t\t\t\t\t\t\t\r\n\t\t\t\r\n\t\t\t\ttry\r\n\t\t\t\t{\r\n\t\t\t\t\tthis.minValue.setValue(range.getLowerBound());\r\n\t\t\t\t\tthis.maxValue.setValue(range.getUpperBound());\r\n\t\t\t\t\tthis.gridInterval.setValue(numAxis.getTickUnit().getSize());\r\n\t\t\t\t}\r\n\t\t\t\tcatch (SettingException e)\r\n\t\t\t\t{\r\n\t\t\t\t\t// best effort.\r\n\t\t\t\t}\t\t\t\t\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\t/* Switched from manual to auto? */\r\n\t\t\tif (!axis.isAutoRange() && autoScale.getBooleanValue())\r\n\t\t\t{\t\t\t\r\n\t\t\t\taxis.setAutoRange(true);\r\n\t\t\t\taxis.setAutoTickUnitSelection(true);\t\t\t\t\r\n\t\t\t}\r\n\t\t\t\r\n\t\t\t/* If manual, numeric, and range does not match our settings, then update */\r\n\t\t\tif (!axis.isAutoRange())\r\n\t\t\t{\r\n\t\t\t\tRange range = axis.getRange();\r\n\t\t\t\t\r\n\t\t\t\tif (range.getLowerBound() != minValue.getDoubleValue() || range.getUpperBound() != maxValue.getDoubleValue())\r\n\t\t\t\t{\r\n\t\t\t\t\taxis.setRange(minValue.getDoubleValue(), maxValue.getDoubleValue());\r\n\t\t\t\t}\r\n\t\t\t\t\r\n\t\t\t\tif (gridInterval.getDoubleValue() != numAxis.getTickUnit().getSize())\r\n\t\t\t\t{\r\n\t\t\t\t\t// FIXME: With i.e. interval 0.01 it rounds \"0.10\" to \"0.1\"\r\n\t\t\t\t\tnumAxis.setTickUnit(new NumberTickUnit(gridInterval.getDoubleValue()));\r\n\t\t\t\t\t// Some experimental code to make axis display only odd numbers:\r\n\t\t\t\t\t/*if (axisShouldOnlyShowOdd) numAxis.setNumberFormatOverride(new DecimalFormat()\r\n\t\t\t\t\t{ public StringBuffer format(double number, StringBuffer toAppendTo, FieldPosition pos) {\r\n\t\t\t\t\t\t\treturn ((int)number % 2 == 0) ? new StringBuffer(\"\") : super.format(number, toAppendTo, pos);\r\n\t\t\t\t\t} });*/\r\n\t\t\t\t}\r\n\t\t\t}\r\n\t\t}\r\n\t}\r\n\t\r\n\tpublic void save(Element axis) throws SettingException\r\n\t{\r\n\t\taxis.setAttribute(\"heading\", getHeading());\r\n\t\t\r\n\t\tFont headingFont = getHeadingFont().f;\r\n\t\taxis.setAttribute(\"headingFontName\", headingFont.getName());\r\n\t\taxis.setAttribute(\"headingFontSize\", \"\" + headingFont.getSize());\r\n\t\taxis.setAttribute(\"headingFontStyle\", \"\" + headingFont.getStyle());\r\n\t\t\r\n\t\tColor headingFontColor = getHeadingFont().c;\r\n\t\taxis.setAttribute(\"headingFontColourR\", \"\" + headingFontColor.getRed());\r\n\t\taxis.setAttribute(\"headingFontColourG\", \"\" + headingFontColor.getGreen());\r\n\t\taxis.setAttribute(\"headingFontColourB\", \"\" + headingFontColor.getBlue());\r\n\t\t\r\n\t\tFont numberFont = getNumberFont().f;\r\n\t\taxis.setAttribute(\"numberFontName\", numberFont.getName());\r\n\t\taxis.setAttribute(\"numberFontSize\", \"\" + numberFont.getSize());\r\n\t\taxis.setAttribute(\"numberFontStyle\", \"\" + numberFont.getStyle());\r\n\t\t\r\n\t\tColor numberFontColor = getHeadingFont().c;\r\n\t\taxis.setAttribute(\"numberFontColourR\", \"\" + numberFontColor.getRed());\r\n\t\taxis.setAttribute(\"numberFontColourG\", \"\" + numberFontColor.getGreen());\r\n\t\taxis.setAttribute(\"numberFontColourB\", \"\" + numberFontColor.getBlue());\r\n\t\t\r\n\t\taxis.setAttribute(\"showMajor\", showGrid() ? \"true\" : \"false\");\r\n\t\t\r\n\t\tColor gridColor = gridColour.getColorValue();\t\t\r\n\t\taxis.setAttribute(\"majorColourR\", \"\" + gridColor.getRed());\r\n\t\taxis.setAttribute(\"majorColourG\", \"\" + gridColor.getGreen());\r\n\t\taxis.setAttribute(\"majorColourB\", \"\" + gridColor.getBlue());\r\n\t\t\r\n\t\taxis.setAttribute(\"logarithmic\", isLogarithmic() ? \"true\" : \"false\");\r\n\t\t\r\n\t\taxis.setAttribute(\"minValue\", \"\" + getMinValue());\r\n\t\taxis.setAttribute(\"maxValue\", \"\" + getMaxValue());\r\n\t\t\r\n\t\taxis.setAttribute(\"majorGridInterval\", \"\" + getGridInterval());\r\n\t\taxis.setAttribute(\"logBase\", \"\" + getLogBase());\r\n\t\taxis.setAttribute(\"logStyle\", \"\" + getLogStyle());\r\n\t\t\r\n\t\taxis.setAttribute(\"minimumPower\", \"\" + getMinimumPower());\r\n\t\taxis.setAttribute(\"maximumPower\", \"\" + getMaximumPower());\r\n\t\t\r\n\t\taxis.setAttribute(\"autoscale\", isAutoScale() ? \"true\" : \"false\");\r\n\t}\r\n\t\r\n\tpublic void load(Element axis) throws SettingException\r\n\t{\r\n\t\tsetHeading(axis.getAttribute(\"heading\")); \r\n  \r\n\t\tString headingFontName = axis.getAttribute(\"headingFontName\");\r\n\t\tString headingFontSize = axis.getAttribute(\"headingFontSize\");\r\n\t\tString headingFontStyle = axis.getAttribute(\"headingFontStyle\");\r\n\t  \r\n\t\tFont headingFont = Graph.parseFont( headingFontName, headingFontStyle, headingFontSize);\r\n\t\t\r\n\t\tString headingFontColourR = axis.getAttribute(\"headingFontColourR\");\r\n\t\tString headingFontColourG = axis.getAttribute(\"headingFontColourG\");\r\n\t\tString headingFontColourB = axis.getAttribute(\"headingFontColourB\");\r\n\t\t\r\n\t\tColor headingFontColor = Graph.parseColor(headingFontColourR, headingFontColourG, headingFontColourB);\r\n\t\t\r\n\t\tsetHeadingFont(new FontColorPair(headingFont, headingFontColor));\r\n\t\t\t\t\r\n\t\tString numberFontName = axis.getAttribute(\"numberFontName\"); \r\n\t\tString numberFontSize = axis.getAttribute(\"numberFontSize\"); \r\n\t\tString numberFontStyle = axis.getAttribute(\"numberFontStyle\"); \r\n\t\t\r\n\t\tFont numberFont = Graph.parseFont(numberFontName, numberFontStyle, numberFontSize ); \r\n\t\t\r\n\t\tString numberFontColourR = axis.getAttribute(\"numberFontColourR\");\r\n\t\tString numberFontColourG = axis.getAttribute(\"numberFontColourG\");\r\n\t\tString numberFontColourB = axis.getAttribute(\"numberFontColourB\");\r\n\t  \r\n\t\tColor numberFontColor = Graph.parseColor(numberFontColourR, numberFontColourG, numberFontColourB);\r\n\t  \r\n\t\tsetNumberFont(new FontColorPair(numberFont, numberFontColor));\r\n\t\t\r\n\t   // axis autoScale property \r\n\t\tboolean autoScale = Graph.parseBoolean(axis.getAttribute(\"autoscale\"));\r\n\t\tsetAutoScale(autoScale);\r\n\t\t\r\n\t\t// axis minValue property \r\n\t\tdouble minValue = Graph.parseDouble(axis.getAttribute(\"minValue\"));\r\n\t\tdouble maxValue = Graph.parseDouble(axis.getAttribute(\"maxValue\"));\r\n\t\tdouble majorGridInterval = Graph.parseDouble(axis.getAttribute(\"majorGridInterval\"));\r\n\t\t\r\n\t\tif (!Double.isNaN(minValue) && !Double.isNaN(maxValue))\r\n\t\t{\r\n\t\t\tif (minValue > getMaxValue())\r\n\t\t\t{\t\t\t\r\n\t\t\t\tsetMaxValue(maxValue);\r\n\t\t\t\tsetMinValue(minValue);\r\n\t\t\t}\r\n\t\t\telse\r\n\t\t\t{\r\n\t\t\t\tsetMinValue(minValue);\r\n\t\t\t\tsetMaxValue(maxValue);\r\n\t\t\t}\r\n\t\t}\r\n\t\t\t\t\r\n\t\tif (!Double.isNaN(majorGridInterval))\r\n\t\t{\r\n\t\t\tsetGridInterval(majorGridInterval);\r\n\t\t}\r\n\t\t\r\n\t\tString majorGridColourR = axis.getAttribute(\"majorColourR\");\r\n\t\tString majorGridColourG = axis.getAttribute(\"majorColourG\");\r\n\t\tString majorGridColourB = axis.getAttribute(\"majorColourB\");\r\n\t  \r\n\t\tColor majorGridColour = Graph.parseColor(majorGridColourR, majorGridColourG, majorGridColourB);\r\n\t\t\r\n\t\tshowGrid(Graph.parseBoolean(axis.getAttribute(\"showMajor\")));\r\n\t \tsetScaleType(Graph.parseBoolean(axis.getAttribute(\"logarithmic\")) ? LOGARITHMIC_SCALE : NORMAL_SCALE);\r\n\t\t\r\n\t \tsetLogBase(Graph.parseDouble(axis.getAttribute(\"logBase\")));\r\n\t \tsetLogStyle(Graph.parseInt(axis.getAttribute(\"logStyle\")));\r\n\t \t\r\n\t \tdouble minimumPower = Graph.parseDouble(axis.getAttribute(\"minimumPower\"));\r\n\t\tdouble maximumPower = Graph.parseDouble(axis.getAttribute(\"maximumPower\"));\r\n\t\t\r\n\t\tif (!Double.isNaN(minimumPower) && !Double.isNaN(maximumPower))\r\n\t\t{\r\n\t\t\tif (minimumPower > getMaximumPower())\r\n\t\t\t{\t\t\t\r\n\t\t\t\tsetMaximumPower(maximumPower);\r\n\t\t\t\tsetMinimumPower(minimumPower);\r\n\t\t\t}\r\n\t\t\telse\r\n\t\t\t{\r\n\t\t\t\tsetMinimumPower(minimumPower);\r\n\t\t\t\tsetMaximumPower(maximumPower);\r\n\t\t\t}\r\n\t\t}\r\n\t\t\r\n\t\tsetAutoScale(autoScale);\r\n\t}\r\n}\r\n\r\n"
  },
  {
    "path": "prism/src/userinterface/graph/DisplaySettings.java",
    "content": "//==============================================================================\r\n//\t\r\n//\tCopyright (c) 2002-\r\n//\tAuthors:\r\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\r\n//\t\r\n//------------------------------------------------------------------------------\r\n//\t\r\n//\tThis file is part of PRISM.\r\n//\t\r\n//\tPRISM is free software; you can redistribute it and/or modify\r\n//\tit under the terms of the GNU General Public License as published by\r\n//\tthe Free Software Foundation; either version 2 of the License, or\r\n//\t(at your option) any later version.\r\n//\t\r\n//\tPRISM is distributed in the hope that it will be useful,\r\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\r\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\r\n//\tGNU General Public License for more details.\r\n//\t\r\n//\tYou should have received a copy of the GNU General Public License\r\n//\talong with PRISM; if not, write to the Free Software Foundation,\r\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\r\n//\t\r\n//==============================================================================\r\n\r\npackage userinterface.graph;\r\n\r\nimport java.util.Observable;\r\n\r\nimport org.jfree.chart.JFreeChart;\r\nimport org.jfree.chart.plot.XYPlot;\r\n\r\nimport settings.BooleanSetting;\r\nimport settings.ColorSetting;\r\nimport settings.Setting;\r\nimport settings.SettingDisplay;\r\nimport settings.SettingException;\r\nimport settings.SettingOwner;\r\n\r\nimport java.awt.*;\r\n\r\nimport javax.swing.UIManager;\r\n\r\n/**\r\n * Representation of the display settings of a Graph.\r\n * The settings are propagated to the JFreeChart library.\r\n */\r\npublic class DisplaySettings extends Observable implements SettingOwner\r\n{\r\n\t/* Display for settings. */\r\n\tprivate SettingDisplay display;\r\n\t\r\n\t/** Our graph object. */\r\n\tprivate Graph graph;\r\n\t\r\n\t/** JFreeChart representation of graphs. */\r\n\tprivate JFreeChart chart;\r\n\t\r\n\t/** XYPlot of this JFreeChart */\r\n\tprivate XYPlot plot;\r\n\t\r\n\tprivate BooleanSetting antiAlias;\t\r\n\tprivate ColorSetting backgroundColor;\t\r\n\t\r\n\tpublic DisplaySettings(Graph graph)\r\n\t{\r\n\t\tthis.graph = graph;\r\n\t\tthis.chart = graph.getChart();\r\n\t\tthis.plot = chart.getXYPlot();\r\n\t\t\r\n\t\tantiAlias = new BooleanSetting(\"anti-aliasing\", Boolean.valueOf(true), \"Should the graph be rendered using anti-aliasing?\", this, false);\r\n\t\tColor defaultColor = Color.white; \r\n\t\t\r\n\t\t//Color defaultColor =  UIManager.getColor(\"Panel.background\");\r\n\t\t\r\n\t\t//if (chart.getBackgroundPaint() instanceof Color)\r\n\t\t//\tdefaultColor = ((Color)chart.getBackgroundPaint());\r\n\t\t\r\n\t\tbackgroundColor = new ColorSetting(\"background colour\", defaultColor, \"The background colour of the graph panel\", this, false);\r\n\t\t\r\n\t\tupdateDisplay();\r\n\t\tsetChanged();\r\n\t\tnotifyObservers();\r\n\t}\t\r\n\t\r\n\tpublic SettingDisplay getDisplay() \r\n\t{\r\n\t\treturn display;\r\n\t}\r\n\r\n\tpublic int getNumSettings() \r\n\t{\r\n\t\treturn 2;\r\n\t}\r\n\r\n\tpublic Setting getSetting(int index) \r\n\t{\r\n\t\tswitch(index)\r\n\t\t{\r\n\t\t\tcase 0: return antiAlias;\r\n\t\t\tcase 1: return backgroundColor;\r\n\t\t\tdefault: return null;\t\t\t\r\n\t\t}\r\n\t}\r\n\r\n\tpublic String getSettingOwnerClassName() {\r\n\t\treturn \"Display\";\t\t\r\n\t}\r\n\r\n\tpublic int getSettingOwnerID() {\r\n\t\treturn prism.PropertyConstants.GRAPH_DISPLAY;\r\n\t}\r\n\r\n\tpublic String getSettingOwnerName() \r\n\t{\r\n\t\tif (graph != null && graph.getName() != null)\r\n\t\t\treturn graph.getName();\r\n\t\t\t\r\n\t\treturn \"\";\r\n\t}\r\n\r\n\tpublic void notifySettingChanged(Setting setting) {\r\n\t\tupdateDisplay();\r\n\t\tsetChanged();\t\t\r\n\t\tnotifyObservers(this);\t\r\n\t}\r\n\r\n\tpublic void setDisplay(SettingDisplay display) {\r\n\t\tthis.display = display;\r\n\t}\r\n\r\n\tpublic int compareTo(Object o)\r\n\t{\r\n\t\tif(o instanceof SettingOwner)\r\n\t\t{\r\n\t\t\tSettingOwner po = (SettingOwner) o;\r\n\t\t\tif(getSettingOwnerID() < po.getSettingOwnerID() )return -1;\r\n\t\t\telse if(getSettingOwnerID() > po.getSettingOwnerID()) return 1;\r\n\t\t\telse return 0;\r\n\t\t}\r\n\t\telse return 0;\r\n\t}\t\r\n\t\r\n\t/**\r\n\t * Getter for property antiAlias.\r\n\t * @return Value of property antiAlias.\r\n\t */\r\n\tpublic boolean isAntiAliased()\r\n\t{\r\n\t\treturn antiAlias.getBooleanValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property antiAlias.\r\n\t * @param value Value of property antiAlias.\r\n\t */\r\n\tpublic void setAntiAliased(boolean value)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\tantiAlias.setValue(Boolean.valueOf(value));\r\n\t\t\tupdateDisplay();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\r\n\t\r\n\t/**\r\n\t * Getter for property backgroundColor.\r\n\t * @return Value of property backgroundColor.\r\n\t */\r\n\tpublic Color getBackgroundColor()\r\n\t{\r\n\t\treturn backgroundColor.getColorValue();\r\n\t}\r\n\t\r\n\t/**\r\n\t * Setter for property backgroundColor.\r\n\t * @param background Value of property backgroundColor.\r\n\t */\r\n\tpublic void setBackgroundColor(Color background)\r\n\t{\r\n\t\ttry\r\n\t\t{\r\n\t\t\tbackgroundColor.setValue(background);\r\n\t\t\tupdateDisplay();\r\n\t\t\tsetChanged();\r\n\t\t\tnotifyObservers(this);\r\n\t\t}\r\n\t\tcatch (SettingException e)\r\n\t\t{\r\n\t\t\t// Shouldn't happen.\r\n\t\t}\r\n\t}\r\n\t\r\n\tprivate void updateDisplay()\r\n\t{\r\n\t\t/* Draw anti-aliased?. */\r\n\t\tif (isAntiAliased() != this.chart.getAntiAlias())\r\n\t\t{\t\t\r\n\t\t\tthis.chart.setAntiAlias(isAntiAliased());\r\n\t\t}\r\n\t\t\r\n\t\t/* Background changed? */\r\n\t\tif (!(this.chart.getBackgroundPaint() instanceof Color) || !backgroundColor.getColorValue().equals(this.chart.getBackgroundPaint()))\r\n\t\t{\r\n\t\t\tthis.chart.setBackgroundPaint(backgroundColor.getColorValue());\r\n\t\t}\r\n\t}\r\n}\r\n"
  },
  {
    "path": "prism/src/userinterface/graph/GUIImageExportDialog.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.2\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <Properties>\n    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n      <Dimension value=\"[550, 350]\"/>\n    </Property>\n  </Properties>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"2\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,2,38\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"allPanel\">\n      <Properties>\n        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n          </Border>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"bottomPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"South\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Component class=\"javax.swing.JLabel\" name=\"warningLabel\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Please enter positive integers\"/>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"0\" left=\"5\" right=\"0\" top=\"0\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <AccessibilityProperties>\n                <Property name=\"AccessibleContext.accessibleName\" type=\"java.lang.String\" value=\"Please enter a positive integer for both width and height\"/>\n              </AccessibilityProperties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Container class=\"javax.swing.JPanel\" name=\"buttonPanel\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"East\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n                <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n              </Layout>\n              <SubComponents>\n                <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                <TitledBorder title=\"Image properties\"/>\n              </Border>\n            </Property>\n            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[400, 200]\"/>\n            </Property>\n            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[400, 200]\"/>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"innerTopPanel\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"North\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                <Property name=\"columns\" type=\"int\" value=\"2\"/>\n                <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                <Property name=\"rows\" type=\"int\" value=\"4\"/>\n                <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n              </Layout>\n              <SubComponents>\n                <Component class=\"javax.swing.JLabel\" name=\"widthInputLabel\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Width:\"/>\n                  </Properties>\n                </Component>\n                <Component class=\"javax.swing.JTextField\" name=\"widthInputField\">\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"heightInputLabel\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Height:\"/>\n                  </Properties>\n                </Component>\n                <Component class=\"javax.swing.JTextField\" name=\"heightInputField\">\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"imageTypeInputLabel\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Image format:\"/>\n                  </Properties>\n                </Component>\n                <Component class=\"javax.swing.JComboBox\" name=\"imageTypeInputField\">\n                  <Properties>\n                    <Property name=\"model\" type=\"javax.swing.ComboBoxModel\" editor=\"org.netbeans.modules.form.editors2.ComboBoxModelEditor\">\n                      <StringArray count=\"3\">\n                        <StringItem index=\"0\" value=\"JPEG\"/>\n                        <StringItem index=\"1\" value=\"PNG\"/>\n                        <StringItem index=\"2\" value=\"EPS\"/>\n                      </StringArray>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"imageTypeInputFieldActionPerformed\"/>\n                  </Events>\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"alphaInputLabel\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Transparent background:\"/>\n                  </Properties>\n                </Component>\n                <Component class=\"javax.swing.JCheckBox\" name=\"alphaInputField\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                        <EmptyBorder bottom=\"0\" left=\"0\" right=\"0\" top=\"0\"/>\n                      </Border>\n                    </Property>\n                    <Property name=\"margin\" type=\"java.awt.Insets\" editor=\"org.netbeans.beaninfo.editors.InsetsEditor\">\n                      <Insets value=\"[0, 0, 0, 0]\"/>\n                    </Property>\n                  </Properties>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/graph/GUIImageExportDialog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport javax.swing.*;\n\nimport java.awt.*;\nimport javax.swing.event.DocumentEvent;\nimport javax.swing.event.DocumentListener;\nimport userinterface.*;\n\npublic class GUIImageExportDialog extends JDialog implements DocumentListener\n{         \n\t//ATTRIBUTES    \n\tprivate Action okAction;\n\tprivate Action cancelAction;\n\t\t\n\tprivate GUIPrism gui;\n\t \n\tprivate int exportWidth;\n\tprivate int exportHeight;\n\t\n\tprivate boolean cancelled;\t\n\t\n\tpublic static final int JPEG = 0;\n\tpublic static final int PNG = 1;\n\tpublic static final int EPS = 2;\n\t\n\t\n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JPanel allPanel;\n    private javax.swing.JCheckBox alphaInputField;\n    private javax.swing.JLabel alphaInputLabel;\n    private javax.swing.JPanel bottomPanel;\n    private javax.swing.JPanel buttonPanel;\n    private javax.swing.JButton cancelButton;\n    private javax.swing.JTextField heightInputField;\n    private javax.swing.JLabel heightInputLabel;\n    private javax.swing.JComboBox imageTypeInputField;\n    private javax.swing.JLabel imageTypeInputLabel;\n    private javax.swing.JPanel innerTopPanel;\n    private javax.swing.JButton okayButton;\n    private javax.swing.JPanel topPanel;\n    private javax.swing.JLabel warningLabel;\n    private javax.swing.JTextField widthInputField;\n    private javax.swing.JLabel widthInputLabel;\n    // End of variables declaration//GEN-END:variables\n    \n\t/** Creates new form GUIConstantsPicker */\n\tpublic GUIImageExportDialog(GUIPrism parent, Graph graph, int defaultImageType)\n\t{\n\t\tsuper(parent, \"Provide rendering information\", true);\n\t\t\n\t\tthis.exportWidth = graph.getWidth();\n\t\tthis.exportHeight = graph.getHeight();\n        \t\t\n\t\tinitComponents();\n\t\t\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\t\t\n\t\tthis.cancelled = false;\n\t\t\n\t\tthis.warningLabel.setIcon(GUIPrism.getIconFromImage(\"smallError.png\"));\n\t\tthis.warningLabel.setVisible(false);\n\t\t\n\t\tthis.widthInputField.getDocument().addDocumentListener(this);\n\t\tthis.heightInputField.getDocument().addDocumentListener(this);\n\t\t\n\t\tthis.widthInputField.setText(\"\" + exportWidth);\n\t\tthis.heightInputField.setText(\"\" + exportHeight);\n\t\t\n\t\tthis.imageTypeInputField.setSelectedIndex(defaultImageType);\n\t\t\n\t\tthis.alphaInputField.setSelected(false);\n\t\tthis.alphaInputField.setEnabled(defaultImageType == PNG);\n\t\tthis.alphaInputLabel.setEnabled(defaultImageType == PNG);\n\t\t\t\t\n\t\tsuper.setBounds(new Rectangle(550, 300));\n\t\tsetResizable(true);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t\t\t\t\n\t\t\n\t\tthis.setVisible(true);\n\t}\n    \n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n    // <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n    private void initComponents() {\n        allPanel = new javax.swing.JPanel();\n        bottomPanel = new javax.swing.JPanel();\n        warningLabel = new javax.swing.JLabel();\n        buttonPanel = new javax.swing.JPanel();\n        okayButton = new javax.swing.JButton();\n        cancelButton = new javax.swing.JButton();\n        topPanel = new javax.swing.JPanel();\n        innerTopPanel = new javax.swing.JPanel();\n        widthInputLabel = new javax.swing.JLabel();\n        widthInputField = new javax.swing.JTextField();\n        heightInputLabel = new javax.swing.JLabel();\n        heightInputField = new javax.swing.JTextField();\n        imageTypeInputLabel = new javax.swing.JLabel();\n        imageTypeInputField = new javax.swing.JComboBox();\n        alphaInputLabel = new javax.swing.JLabel();\n        alphaInputField = new javax.swing.JCheckBox();\n\n        setMinimumSize(new java.awt.Dimension(550, 350));\n        addWindowListener(new java.awt.event.WindowAdapter() {\n            public void windowClosing(java.awt.event.WindowEvent evt) {\n                closeDialog(evt);\n            }\n        });\n\n        allPanel.setLayout(new java.awt.BorderLayout());\n\n        allPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        bottomPanel.setLayout(new java.awt.BorderLayout());\n\n        warningLabel.setText(\"Please enter positive integers for width and height.\");\n        warningLabel.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 5, 0, 0));\n        bottomPanel.add(warningLabel, java.awt.BorderLayout.CENTER);\n        warningLabel.getAccessibleContext().setAccessibleName(\"Please enter a positive integer for both width and height.\");\n\n        buttonPanel.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n        okayButton.setText(\"Okay\");\n        okayButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                okayButtonActionPerformed(evt);\n            }\n        });\n\n        buttonPanel.add(okayButton);\n\n        cancelButton.setText(\"Cancel\");\n        cancelButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                cancelButtonActionPerformed(evt);\n            }\n        });\n\n        buttonPanel.add(cancelButton);\n\n        bottomPanel.add(buttonPanel, java.awt.BorderLayout.EAST);\n\n        allPanel.add(bottomPanel, java.awt.BorderLayout.SOUTH);\n\n        topPanel.setLayout(new java.awt.BorderLayout());\n\n        topPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Image properties\"));\n        topPanel.setMinimumSize(new java.awt.Dimension(400, 200));\n        topPanel.setPreferredSize(new java.awt.Dimension(400, 200));\n        innerTopPanel.setLayout(new java.awt.GridLayout(4, 2, 5, 5));\n\n        innerTopPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        widthInputLabel.setText(\"Width:\");\n        innerTopPanel.add(widthInputLabel);\n\n        innerTopPanel.add(widthInputField);\n\n        heightInputLabel.setText(\"Height:\");\n        innerTopPanel.add(heightInputLabel);\n\n        innerTopPanel.add(heightInputField);\n\n        imageTypeInputLabel.setText(\"Image format:\");\n        innerTopPanel.add(imageTypeInputLabel);\n\n        imageTypeInputField.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"JPEG\", \"PNG\", \"EPS\" }));\n        imageTypeInputField.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                imageTypeInputFieldActionPerformed(evt);\n            }\n        });\n\n        innerTopPanel.add(imageTypeInputField);\n\n        alphaInputLabel.setText(\"Transparent background:\");\n        innerTopPanel.add(alphaInputLabel);\n\n        alphaInputField.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0));\n        alphaInputField.setMargin(new java.awt.Insets(0, 0, 0, 0));\n        innerTopPanel.add(alphaInputField);\n\n        topPanel.add(innerTopPanel, java.awt.BorderLayout.NORTH);\n\n        allPanel.add(topPanel, java.awt.BorderLayout.CENTER);\n\n        getContentPane().add(allPanel, java.awt.BorderLayout.CENTER);\n\n    }// </editor-fold>//GEN-END:initComponents\n\n    private void imageTypeInputFieldActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_imageTypeInputFieldActionPerformed\n\n    \tboolean canHandleAlpha = (imageTypeInputField.getSelectedIndex() == PNG);\n    \t\n    \talphaInputField.setEnabled(canHandleAlpha);\n    \talphaInputLabel.setEnabled(canHandleAlpha);\n    \t    \t\t\n    }//GEN-LAST:event_imageTypeInputFieldActionPerformed\n\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\t\tdispose();\n\t}//GEN-LAST:event_okayButtonActionPerformed\n        \n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\t\tcancelled = true;\n\t\tdispose();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n        \n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\t\t\n\tpublic int getImageType()\n\t{\n\t\treturn imageTypeInputField.getSelectedIndex();\n\t}\n\t\n\tpublic boolean isCancelled() \n\t{\n\t\treturn cancelled;\n\t}\n\n\tpublic int getExportWidth() \n\t{\n\t\treturn exportWidth;\n\t}\n\t\n\tpublic int getExportHeight() \n\t{\n\t\treturn exportHeight;\n\t}\n\t\n\tpublic boolean getAlpha() \n\t{\n\t\treturn alphaInputField.isSelected();\n\t}\n\t\n\tpublic void changedUpdate(DocumentEvent e) \n\t{\n\t\ttry\n\t\t{\n\t\t\texportWidth = Integer.parseInt(widthInputField.getText());\n\t\t\tif (exportWidth <= 0) throw new NumberFormatException();\n\t\t\texportHeight = Integer.parseInt(heightInputField.getText());\n\t\t\tif (exportHeight <= 0) throw new NumberFormatException();\n\t\t\tGUIImageExportDialog.this.warningLabel.setVisible(false);\n\t\t\tGUIImageExportDialog.this.okayButton.setEnabled(true);\n\t\t}\n\t\tcatch (NumberFormatException nfe)\n\t\t{\n\t\t\tGUIImageExportDialog.this.warningLabel.setVisible(true);\n\t\t\tGUIImageExportDialog.this.okayButton.setEnabled(false);\n\t\t}\t\t\t\t\n\t}\n\t\t\n\tpublic void removeUpdate(DocumentEvent e) {changedUpdate(e);}\t\t\t\n\tpublic void insertUpdate(DocumentEvent e) {changedUpdate(e);}\n}\n\n\n"
  },
  {
    "path": "prism/src/userinterface/graph/Graph.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Alistair John Strachan <alistair@devzero.co.uk> (University of Edinburgh)\n//\t* Mike Arthur <mike@mikearthur.co.uk> (University of Edinburgh)\n//\t* Zak Cohen <zakcohen@gmail.com> (University of Edinburgh)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport java.awt.*;\nimport java.awt.print.*;\nimport java.io.*;\nimport java.util.*;\nimport java.awt.image.*;\n\nimport org.w3c.dom.DOMException;\nimport org.w3c.dom.Document;\nimport org.w3c.dom.Element;\nimport org.w3c.dom.NodeList;\nimport org.xml.sax.*;\n\nimport javax.xml.parsers.*;\nimport javax.xml.transform.*;\nimport javax.xml.transform.dom.*;\nimport javax.xml.transform.stream.*;\n\nimport org.jfree.ui.*;\nimport org.jfree.chart.*;\nimport org.jfree.chart.plot.*;\nimport org.jfree.chart.title.*;\nimport org.jfree.chart.axis.*;\nimport org.jfree.data.xy.*;\nimport org.jfree.chart.renderer.xy.*;\nimport org.jfree.chart.encoders.*;\n\nimport net.sf.epsgraphics.*;\n\nimport prism.*;\nimport settings.*;\n\n/**\n * This class represents multiple series on a single unit graph; all series are\n * rendered together by MultiGraphView.\n */\npublic class Graph extends ChartPanel implements SettingOwner, EntityResolver, Observer, Printable\n{\n\t/** Interval for graph updates (in ms). */\n\tprivate static final long updateInterval = 250;\n\n\t/** Actual JFreeChart representation of datasets. */\n\tprivate JFreeChart chart;\n\n\t/** XYPlot of this JFreeChart */\n\tprivate XYPlot plot;\n\n\t/**\n\t * List of currently available series data to plot. (Make sure to\n\t * synchronize)\n\t */\n\tprivate XYSeriesCollection seriesCollection;\n\n\t/**\n\t * Maps SeriesKeys to a XYSeries. (Make sure to synchronize on\n\t * seriesCollection)\n\t */\n\tprivate HashMap<SeriesKey, XYSeries> keyToSeries;\n\n\t/**\n\t * Maps SeriesKeys to a Graph Series. (Make sure to synchronize on\n\t * seriesCollection)\n\t */\n\tprivate HashMap<SeriesKey, SeriesSettings> keyToGraphSeries;\t\n\t\n\t/**\n\t * Allows us to batch graph points (JFreeChart is not realtime). (Make sure\n\t * to synchronize on seriesCollection)\n\t */\n\tprivate HashMap<SeriesKey, LinkedList<XYDataItem>> graphCache;\n\n\t/** Display for settings. Required to implement SettingsOwner */\n\tprivate SettingDisplay display;\n\n\t/** Settings of this graph. */\n\tprivate MultipleLineStringSetting graphTitle;\n\tprivate FontColorSetting titleFont;\n\tprivate BooleanSetting legendVisible;\n\tprivate ChoiceSetting legendPosition;\n\tprivate FontColorSetting legendFont;\n\n\t/** Settings of the axis. */\n\tprivate AxisSettings xAxisSettings;\n\n\tprivate AxisSettings yAxisSettings;\n\n\t/** Display settings */\n\tprivate DisplaySettings displaySettings;\n\t\n\t/** GraphSeriesList */\n\tprivate SeriesSettingsList seriesList;\n\n\t/** legend position */\n\tpublic static final int LEFT = 0;\n\tpublic static final int RIGHT = 1;\n\tpublic static final int BOTTOM = 2;\n\tpublic static final int TOP = 3;\n\n\t/**\n\t * Initialises the GraphModel's series and canvas list. Also starts off the\n\t * graph update timer (one per chart).\n\t */\n\tpublic Graph() \n\t{\n\t\tthis(\"\");\n\t}\n\t\n\t/**\n\t * Initialises the GraphModel's series and canvas list. Also starts off the\n\t * graph update timer (one per chart).\n\t * \n\t * @param title\n\t *            Title of the graph.\n\t */\n\tpublic Graph(String title) \n\t{\n\t\tsuper(ChartFactory.createXYLineChart(title, \"X\", \"Y\",\n\t\t\t\tnew XYSeriesCollection(), PlotOrientation.VERTICAL, true, true,\n\t\t\t\tfalse));\n\n\t\t\n\t\tgraphCache = new HashMap<SeriesKey, LinkedList<XYDataItem>>();\n\t\tkeyToSeries = new HashMap<SeriesKey, XYSeries>();\n\t\tkeyToGraphSeries = new HashMap<SeriesKey, SeriesSettings>();\n\t\tgraphTitle = new MultipleLineStringSetting(\"title\", title,\n\t\t\t\t\"The main title heading for the chart.\", this, false);\n\t\ttitleFont = new FontColorSetting(\"title font\", new FontColorPair(\n\t\t\t\tnew Font(\"SansSerif\", Font.PLAIN, 14), Color.black),\n\t\t\t\t\"The font for the chart's title\", this, false);\n\t\tlegendVisible = new BooleanSetting(\n\t\t\t\t\"legend visible?\",\n\t\t\t\tBoolean.valueOf(true),\n\t\t\t\t\"Should the legend, which displays all of the series headings, be displayed?\",\n\t\t\t\tthis, false);\n\n\t\tString[] choices = { \"Left\", \"Right\", \"Bottom\", \"Top\" };\n\t\tlegendPosition = new ChoiceSetting(\"legend position\", choices,\n\t\t\t\tchoices[RIGHT], \"The position of the legend\", this, false);\n\t\tlegendFont = new FontColorSetting(\"legend font\", new FontColorPair(\n\t\t\t\tnew Font(\"SansSerif\", Font.PLAIN, 11), Color.black),\n\t\t\t\t\"The font for the legend\", this, false);\n\n\t\t// Some easy references\n\t\tchart = super.getChart();\n\t\tplot = chart.getXYPlot();\n\t\tplot.setBackgroundPaint((Paint)Color.white);\n\t\tseriesCollection = (XYSeriesCollection) plot.getDataset();\n\t\t\n\t\txAxisSettings = new AxisSettings(\"X\", true, this);\n\t\tyAxisSettings = new AxisSettings(\"Y\", false, this);\n\n\t\txAxisSettings.addObserver(this);\n\t\tyAxisSettings.addObserver(this);\n\n\t\tdisplaySettings = new DisplaySettings(this);\n\t\tdisplaySettings.addObserver(this);\n\t\t\n\t\tseriesList = new SeriesSettingsList(this);\n\t\t\n\t\t// create a regular XY line chart\n\t\tXYItemRenderer r = plot.getRenderer();\n\t\t// if possible, try to match the old grapher\n\t\tif (r instanceof XYLineAndShapeRenderer) {\n\t\t\tXYLineAndShapeRenderer renderer = (XYLineAndShapeRenderer) r;\n\t\t\trenderer.setBaseShapesVisible(true);\n\t\t\trenderer.setBaseShapesFilled(true);\n\t\t\trenderer.setDrawSeriesLineAsPath(true);\n\t\t\trenderer.setAutoPopulateSeriesPaint(true);\n\t\t\trenderer.setAutoPopulateSeriesShape(true);\n\t\t}\n\t\t\n\t\tplot.setDrawingSupplier(new DefaultDrawingSupplier(\n\t\t\t\tSeriesSettings.DEFAULT_PAINTS,\n\t\t\t\tDefaultDrawingSupplier.DEFAULT_OUTLINE_PAINT_SEQUENCE,\n\t\t\t\tDefaultDrawingSupplier.DEFAULT_STROKE_SEQUENCE,\n\t\t\t\tDefaultDrawingSupplier.DEFAULT_OUTLINE_STROKE_SEQUENCE,\n\t\t\t\tSeriesSettings.DEFAULT_SHAPES\n\t\t));\t\n\n\t\tsuper.setPopupMenu(null);\n\n\t\t/* Make sure the graph resembles its default settings. */\n\t\tupdateGraph();\n\n\t\t// schedule a periodic timer for graph updates\n\t\tnew java.util.Timer().scheduleAtFixedRate(new GraphUpdateTask(), 0, // start now\n\t\t\t\tupdateInterval);\n\t}\n\n\tpublic int compareTo(Object o) {\n\t\tif (o instanceof SettingOwner) {\n\t\t\tSettingOwner po = (SettingOwner) o;\n\t\t\tif (getSettingOwnerID() < po.getSettingOwnerID())\n\t\t\t\treturn -1;\n\t\t\telse if (getSettingOwnerID() > po.getSettingOwnerID())\n\t\t\t\treturn 1;\n\t\t\telse\n\t\t\t\treturn 0;\n\t\t} else\n\t\t\treturn 0;\n\t}\n\n\tpublic int getNumSettings() {\n\t\treturn 5;\n\t}\n\n\tpublic Setting getSetting(int index) {\n\t\tswitch (index) {\n\t\tcase 0:\n\t\t\treturn graphTitle;\n\t\tcase 1:\n\t\t\treturn titleFont;\n\t\tcase 2:\n\t\t\treturn legendVisible;\n\t\tcase 3:\n\t\t\treturn legendPosition;\n\t\tcase 4:\n\t\t\treturn legendFont;\n\t\tdefault:\n\t\t\treturn null;\n\t\t}\n\t}\n\n\tpublic String getSettingOwnerClassName() {\n\t\treturn \"Model\";\n\t}\n\n\tpublic int getSettingOwnerID() {\n\t\treturn prism.PropertyConstants.MODEL;\n\t}\n\n\tpublic String getSettingOwnerName() {\n\t\treturn graphTitle.getStringValue();\n\t}\n\n\tpublic void doEnables() {\n\t\tlegendPosition.setEnabled(legendVisible.getBooleanValue());\n\t\tlegendFont.setEnabled(legendVisible.getBooleanValue());\n\t}\n\n\tpublic void update(Observable o, Object arg) {\n\t\tif (o == xAxisSettings) {\n\t\t\t/* X axis changed */\n\t\t\tsuper.repaint();\n\t\t} else if (o == yAxisSettings) {\n\t\t\t/* Y axis changed */\n\t\t\tsuper.repaint();\n\t\t} else if (o == displaySettings) {\n\t\t\t/* Display settings changed */\n\t\t\tsuper.repaint();\n\t\t} else {\n\t\t\tfor (Map.Entry<SeriesKey, SeriesSettings> entry : keyToGraphSeries.entrySet())\n\t\t\t{\n\t\t\t\t/* Graph series settings changed */\n\t\t\t\tif (entry.getValue().equals(o))\n\t\t\t\t\trepaint();\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void notifySettingChanged(Setting setting) {\n\t\tupdateGraph();\n\t}\n\n\tprivate void updateGraph() {\n\t\t/* Update title if necessary. */\n\t\tif (!this.chart.getTitle().equals(graphTitle)) {\n\t\t\tthis.chart.setTitle(graphTitle.getStringValue());\n\t\t}\n\n\t\t/* Update title font if necessary. */\n\t\tif (!titleFont.getFontColorValue().f.equals(this.chart.getTitle()\n\t\t\t\t.getFont())) {\n\t\t\tthis.chart.getTitle().setFont(titleFont.getFontColorValue().f);\n\t\t}\n\n\t\t/* Update title colour if necessary. */\n\t\tif (!titleFont.getFontColorValue().c.equals(this.chart.getTitle()\n\t\t\t\t.getPaint())) {\n\t\t\tthis.chart.getTitle().setPaint(titleFont.getFontColorValue().c);\n\t\t}\n\n\t\tif (legendVisible.getBooleanValue() != (this.chart.getLegend() != null)) {\n\t\t\tif (!legendVisible.getBooleanValue()) {\n\t\t\t\tthis.chart.removeLegend();\n\t\t\t} else {\n\t\t\t\tLegendTitle legend = new LegendTitle(plot.getRenderer());\n\t\t\t\tlegend.setBackgroundPaint(Color.white);\n\t\t\t\tlegend.setBorder(1, 1, 1, 1);\n\n\t\t\t\tthis.chart.addLegend(legend);\n\t\t\t}\n\t\t}\n\n\t\tif (this.chart.getLegend() != null) {\n\t\t\tLegendTitle legend = this.chart.getLegend();\n\n\t\t\t/* Put legend on the left if appropriate. */\n\t\t\tif ((legendPosition.getCurrentIndex() == LEFT)\n\t\t\t\t\t&& !legend.getPosition().equals(RectangleEdge.LEFT)) {\n\t\t\t\tlegend.setPosition(RectangleEdge.LEFT);\n\t\t\t}\n\t\t\t/* Put legend on the right if appropriate. */\n\t\t\tif ((legendPosition.getCurrentIndex() == RIGHT)\n\t\t\t\t\t&& !legend.getPosition().equals(RectangleEdge.RIGHT)) {\n\t\t\t\tlegend.setPosition(RectangleEdge.RIGHT);\n\t\t\t}\n\t\t\t/* Put legend on the top if appropriate. */\n\t\t\tif ((legendPosition.getCurrentIndex() == TOP)\n\t\t\t\t\t&& !legend.getPosition().equals(RectangleEdge.TOP)) {\n\t\t\t\tlegend.setPosition(RectangleEdge.TOP);\n\t\t\t}\n\t\t\t/* Put legend on the bottom if appropriate. */\n\t\t\tif ((legendPosition.getCurrentIndex() == BOTTOM)\n\t\t\t\t\t&& !legend.getPosition().equals(RectangleEdge.BOTTOM)) {\n\t\t\t\tlegend.setPosition(RectangleEdge.BOTTOM);\n\t\t\t}\n\n\t\t\t/* Set legend font. */\n\t\t\tif (!legend.getItemFont().equals(legendFont.getFontColorValue().f)) {\n\t\t\t\tlegend.setItemFont(legendFont.getFontColorValue().f);\n\t\t\t}\n\t\t\t/* Set legend font colour. */\n\t\t\tif (!legend.getItemPaint().equals(legendFont.getFontColorValue().c)) {\n\t\t\t\tlegend.setItemPaint(legendFont.getFontColorValue().c);\n\t\t\t}\n\t\t}\n\n\t\tsuper.repaint();\n\t\tdoEnables();\n\t}\n\n\tpublic void setDisplay(SettingDisplay display) \n\t{\n\t\tthis.display = display;\n\t}\n\n\tpublic SettingDisplay getDisplay() \n\t{\n\t\treturn display;\n\t}\n\t\n\t/** \n\t * Returns an object that you have to synchronise in one case:\n\t * - You depend on series not changing.\n\t */\n\tpublic Object getSeriesLock()\n\t{\n\t\treturn seriesCollection;\n\t}\n\t\n\tpublic java.util.Vector<SeriesKey> getAllSeriesKeys()\n\t{\n\t\tsynchronized (seriesCollection)\n\t\t{\n\t\t\tjava.util.Vector<SeriesKey> result = new java.util.Vector<SeriesKey>();\n\t\t\t\n\t\t\tfor (Map.Entry<SeriesKey, XYSeries> entries : keyToSeries.entrySet())\n\t\t\t{\n\t\t\t\tresult.add(entries.getKey());\n\t\t\t}\n\t\t\n\t\t\treturn result;\n\t\t}\n\t}\n\t\n\tpublic SeriesSettingsList getGraphSeriesList()\n\t{\n\t\treturn seriesList;\n\t}\n\t\n\t/**\n\t * Should always be synchronised on seriesCollection when called.\n\t */\n\tpublic SeriesSettings getGraphSeries(SeriesKey key)\n\t{\n\t\tsynchronized (seriesCollection)\n\t\t{\n\t\t\tif (keyToGraphSeries.containsKey(key))\n\t\t\t{\n\t\t\t\treturn keyToGraphSeries.get(key);\n\t\t\t}\n\t\t\n\t\t\treturn null;\n\t\t}\n\t}\n\t\n\t/**\n\t * Should always be synchronised on seriesCollection when called.\n\t */\n\tpublic XYSeries getXYSeries(SeriesKey key)\n\t{\n\t\tsynchronized (seriesCollection)\n\t\t{\n\t\t\tif (keyToSeries.containsKey(key))\n\t\t\t{\n\t\t\t\treturn keyToSeries.get(key);\n\t\t\t}\n\t\t\n\t\t\treturn null;\n\t\t}\n\t}\n\t\t\n\t/**\n\t * Should always be synchronised on seriesCollection when called.\n\t * @return >0 when series found.\n\t */\n\tpublic int getJFreeChartIndex(SeriesKey key)\n\t{\n\t\tsynchronized (seriesCollection) \n\t\t{\n\t\t\tXYSeries series = keyToSeries.get(key);\n\t\t\t\n\t\t\tfor (int i = 0; i < seriesCollection.getSeriesCount(); i++)\n\t\t\t{\n\t\t\t\tif (seriesCollection.getSeries(i).equals((series)))\n\t\t\t\t\treturn i;\n\t\t\t}\n\t\t\t\n\t\t\treturn -1;\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property graphTitle.\n\t * @return Value of property graphTitle.\n\t */\n\tpublic String getTitle()\n\t{\n\t\treturn graphTitle.getStringValue();\n\t}\n\t\n\t/**\n\t * Setter for property graphTitle.\n\t * @param value Value of property graphTitle.\n\t */\n\tpublic void setTitle(String value)\n\t{\n\t\ttry\n\t\t{\n\t\t\tgraphTitle.setValue(value);\n\t\t\tdoEnables();\n\t\t\tupdateGraph();\n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\t// Shouldn't happen.\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property titleFont.\n\t * @return Value of property titleFont.\n\t */\n\tpublic FontColorPair getTitleFont()\n\t{\n\t\treturn titleFont.getFontColorValue();\n\t}\n\t\n\t/**\n\t * Setter for property titleFont.\n\t * @param font Value of property titleFont.\n\t */\n\tpublic void setTitleFont(FontColorPair font)\n\t{\n\t\ttry\n\t\t{\n\t\t\ttitleFont.setValue(font);\n\t\t\tdoEnables();\n\t\t\tupdateGraph();\n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\t// Shouldn't happen.\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property legendFont.\n\t * @return Value of property legendFont.\n\t */\n\tpublic FontColorPair getLegendFont()\n\t{\n\t\treturn legendFont.getFontColorValue();\n\t}\n\t\n\t/**\n\t * Setter for property legendFont.\n\t * @param font Value of property legendFont.\n\t */\n\tpublic void setLegendFont(FontColorPair font)\n\t{\n\t\ttry\n\t\t{\n\t\t\tlegendFont.setValue(font);\n\t\t\tdoEnables();\n\t\t\tupdateGraph();\n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\t// Shouldn't happen.\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property legendVisible.\n\t * @return Value of property legendVisible.\n\t */\n\tpublic boolean isLegendVisible()\n\t{\n\t\treturn legendVisible.getBooleanValue();\n\t}\n\t\n\t/**\n\t * Setter for property legendVisible.\n\t * @param visible Value of property legendVisible.\n\t */\n\tpublic void setLegendVisible(boolean visible)\n\t{\n\t\ttry\n\t\t{\n\t\t\tlegendVisible.setValue(visible);\n\t\t\tdoEnables();\n\t\t\tupdateGraph();\n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\t// Shouldn't happen.\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property logarithmic.\n\t * @return the legend's position index:\n\t * <ul>\n\t *\t<li>0: LEFT\n\t *\t<li>1: RIGHT\n\t *\t<li>2: BOTTOM\n\t *  <li>3: TOP\n\t * </ul>\n\t */\n\tpublic int getLegendPosition()\n\t{\n\t\treturn legendPosition.getCurrentIndex();\n\t}\n\t\n\t/**\n\t * Setter for property logarithmic.\n\t * @param value Represents legend position\n\t * <ul>\n\t *\t<li>0: LEFT\n\t *\t<li>1: RIGHT\n\t *\t<li>2: BOTTOM\n\t *\t<li>4: TOP\n\t * </ul>\n\t */\n\tpublic void setLegendPosition(int value) throws SettingException\n\t{\t\t\n\t\tlegendPosition.setSelectedIndex(value);\n\t\tdoEnables();\n\t\tupdateGraph();\n\t}\n\t\n\t/**\n\t * Return settings of the x-Axis.\n\t * \n\t * @return Settings of the x-Axis.\n\t */\n\tpublic AxisSettings getXAxisSettings() {\n\t\treturn xAxisSettings;\n\t}\n\n\t/**\n\t * Return settings of the y-Axis.\n\t * \n\t * @return Settings of the y-Axis.\n\t */\n\tpublic AxisSettings getYAxisSettings() {\n\t\treturn yAxisSettings;\n\t}\n\n\t/**\n\t * Return display settings of the graph.\n\t * \n\t * @return Display settings of the graph.\n\t */\n\tpublic DisplaySettings getDisplaySettings() {\n\t\treturn displaySettings;\n\t}\n\t\n\tprivate String getUniqueSeriesName(String seriesName)\n\t{\n\t\tsynchronized (seriesCollection) \n\t\t{\n\t\t\tint counter = 0;\n\t\t\tString name = seriesName;\n\t\t\t\t\n\t\t\t/* Name sure seriesName is unique */\n\t\t\twhile (true)\n\t\t\t{\n\t\t\t\tboolean nameExists = false;\n\t\t\t\t\n\t\t\t\tfor (Map.Entry<SeriesKey, XYSeries> entry : keyToSeries.entrySet())\n\t\t\t\t{\n\t\t\t\t\tif (name.equals(entry.getValue().getKey()))\n\t\t\t\t\t{\n\t\t\t\t\t\tnameExists = true;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif (nameExists)\n\t\t\t\t{\n\t\t\t\t\tcounter++;\n\t\t\t\t\tname = seriesName + \" (\" + counter + \")\";\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\tbreak;\n\t\t\t\t}\t\t\t\t \n\t\t\t}\n\t\t\t\n\t\t\treturn name;\n\t\t}\t\n\t}\n\t\n\tpublic void moveUp(java.util.Vector<SeriesKey> keys)\n\t{\n\t\tsynchronized (seriesCollection)\n\t\t{\n\t\t\tXYSeries[] newOrder = new XYSeries[seriesCollection.getSeriesCount()];\n\t\t\tjava.util.Vector<XYSeries> moveUpSet = new java.util.Vector<XYSeries>();\n\t\t\t\n\t\t\tfor (int i = 0; i < newOrder.length; i++)\n\t\t\t\tnewOrder[i] = seriesCollection.getSeries(i);\n\t\t\t\n\t\t\tfor (SeriesKey key : keys)\n\t\t\t{\t\n\t\t\t\tif (keyToSeries.containsKey(key))\n\t\t\t\t\tmoveUpSet.add(keyToSeries.get(key));\t\t\t\n\t\t\t}\n\t\t\t\t\t\t\n\t\t\tfor (int i = 1; i < newOrder.length; i++)\n\t\t\t{\n\t\t\t\tif (moveUpSet.contains(newOrder[i]))\n\t\t\t\t{\n\t\t\t\t\tXYSeries tmp = newOrder[i];\n\t\t\t\t\tnewOrder[i] = newOrder[i-1];\n\t\t\t\t\tnewOrder[i-1] = tmp;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tXYSeriesCollection newCollection = new XYSeriesCollection();\n\t\t\t\n\t\t\tfor (int i = 0; i < newOrder.length; i++)\n\t\t\t\tnewCollection.addSeries(newOrder[i]);\n\t\t\t\n\t\t\tplot.setDataset(newCollection);\n\t\t\t\n\t\t\tthis.seriesCollection = newCollection;\t\t\t\n\t\t\tthis.seriesList.updateSeriesList();\t\t\n\t\t}\n\t}\n\t\n\tpublic void moveDown(java.util.Vector<SeriesKey> keys)\n\t{\n\t\tsynchronized (seriesCollection)\n\t\t{\n\t\t\tXYSeries[] newOrder = new XYSeries[seriesCollection.getSeriesCount()];\n\t\t\tjava.util.Vector<XYSeries> moveDownSet = new java.util.Vector<XYSeries>();\n\t\t\t\n\t\t\tfor (int i = 0; i < newOrder.length; i++)\n\t\t\t\tnewOrder[i] = seriesCollection.getSeries(i);\n\t\t\t\n\t\t\tfor (SeriesKey key : keys)\n\t\t\t{\t\n\t\t\t\tif (keyToSeries.containsKey(key))\n\t\t\t\t\tmoveDownSet.add(keyToSeries.get(key));\t\t\t\n\t\t\t}\n\t\t\t\t\t\t\n\t\t\tfor (int i = newOrder.length - 2; i >= 0; i--)\n\t\t\t{\n\t\t\t\tif (moveDownSet.contains(newOrder[i]))\n\t\t\t\t{\n\t\t\t\t\tXYSeries tmp = newOrder[i];\n\t\t\t\t\tnewOrder[i] = newOrder[i+1];\n\t\t\t\t\tnewOrder[i+1] = tmp;\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tXYSeriesCollection newCollection = new XYSeriesCollection();\n\t\t\t\n\t\t\tfor (int i = 0; i < newOrder.length; i++)\n\t\t\t\tnewCollection.addSeries(newOrder[i]);\n\t\t\t\n\t\t\tplot.setDataset(newCollection);\n\t\t\t\n\t\t\tthis.seriesCollection = newCollection;\t\t\t\n\t\t\tthis.seriesList.updateSeriesList();\t\t\n\t\t}\n\t}\n\n\t/**\n\t * Add a series to the buffered graph data.\n\t * \n\t * @param seriesName\n\t *            Name of series to add to graph.\n\t */\n\tpublic SeriesKey addSeries(String seriesName) \n\t{\n\t\tSeriesKey key;\n\t\t\n\t\tsynchronized (seriesCollection) \n\t\t{\n\t\t\tseriesName = getUniqueSeriesName(seriesName);\n\t\t\t\n\t\t\t// create a new XYSeries without sorting, disallowing duplicates\n\t\t\tXYSeries newSeries = new PrismXYSeries(seriesName);\n\t\t\tthis.seriesCollection.addSeries(newSeries);\n\t\t\t// allocate a new cache for this series\n\n\t\t\tkey = new SeriesKey();\n\n\t\t\tthis.keyToSeries.put(key, newSeries);\n\t\t\tthis.graphCache.put(key, new LinkedList<XYDataItem>());\n\t\t\t\n\t\t\tSeriesSettings graphSeries = new SeriesSettings(this, key);\n\t\t\tthis.keyToGraphSeries.put(key, graphSeries);\n\t\t\tgraphSeries.addObserver(this);\n\t\t\t\n\t\t\tthis.seriesList.updateSeriesList();\t\t\t\n\t\t}\t\t\n\t\t\n\t\treturn key;\t\t\n\t}\n\t\n\t/**\n\t * Changes the name of a series.\n\t * \n\t * @param key The key identifying the series.\n\t * @param seriesName New name of series.\n\t */\n\tpublic void changeSeriesName(SeriesKey key, String seriesName) \n\t{\n\t\tsynchronized (seriesCollection) \n\t\t{\n\t\t\tseriesName = getUniqueSeriesName(seriesName);\n\t\t\t\n\t\t\tif (keyToSeries.containsKey(key))\n\t\t\t{\n\t\t\t\tXYSeries series = keyToSeries.get(key);\n\t\t\t\tseries.setKey(seriesName);\n\t\t\t}\t\t\t\n\t\t}\t\n\t}\n\n\t/**\n\t * Wholly remove a series from the current graph, by key.\n\t * @param seriesKey SeriesKey of series to remove.\n\t */\n\tpublic void removeSeries(SeriesKey seriesKey) \n\t{\n\t\tsynchronized (seriesCollection) {\n\t\t\t// Delete from keyToSeries and seriesCollection.\n\t\t\tif (keyToSeries.containsKey(seriesKey)) {\n\t\t\t\tXYSeries series = keyToSeries.get(seriesKey);\n\t\t\t\tseriesCollection.removeSeries(series);\n\t\t\t\tkeyToSeries.remove(seriesKey);\n\t\t\t}\n\n\t\t\t// Remove any cache.\n\t\t\tif (graphCache.containsKey(seriesKey)) {\n\t\t\t\tgraphCache.remove(seriesKey);\n\t\t\t}\n\t\t\t\n\t\t\tif (keyToGraphSeries.containsKey(seriesKey))\n\t\t\t{\n\t\t\t\tkeyToGraphSeries.get(seriesKey).deleteObservers();\t\t\t\t\n\t\t\t\tkeyToGraphSeries.remove(seriesKey);\n\t\t\t}\n\t\t\t\n\t\t\tthis.seriesList.updateSeriesList();\t\n\t\t}\n\t\t\n\t\tseriesList.updateSeriesList();\n\t}\n\n\t/**\n\t * Add a point to the specified graph series.\n\t * @param seriesKey Key of series to update.\n\t * @param dataItem XYDataItem object to insert into this series.\n\t */\n\tpublic void addPointToSeries(SeriesKey seriesKey, XYDataItem dataItem) {\n\t\t\n\t\tsynchronized (seriesCollection) {\n\t\t\tif (graphCache.containsKey(seriesKey)) {\n\t\t\t\t\n\t\t\t\tif (true) {\n\t\t\t\t\tLinkedList<XYDataItem> seriesCache = graphCache\n\t\t\t\t\t\t\t.get(seriesKey);\n\t\t\t\t\tseriesCache.add(dataItem);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Remove all points from a graph series and its cache.\n\t * \n\t * @param seriesKey\n\t *            Key of series to update.\n\t */\n\tpublic void removeAllPoints(SeriesKey seriesKey) {\n\t\tsynchronized (seriesCollection) {\n\t\t\tif (graphCache.containsKey(seriesKey)) {\n\t\t\t\tLinkedList<XYDataItem> seriesCache = graphCache.get(seriesKey);\n\t\t\t\tseriesCache.clear();\n\t\t\t}\n\n\t\t\tif (keyToSeries.containsKey(seriesKey)) {\n\t\t\t\tXYSeries series = keyToSeries.get(seriesKey);\n\t\t\t\tseries.clear();\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * TODO: Document this!\n\t */\n\tpublic InputSource resolveEntity(String publicId, String systemId)\n\t\t\tthrows SAXException, IOException {\n\t\tInputSource inputSource = null;\n\n\t\t// override the resolve method for the dtd\n\t\tif (systemId.endsWith(\"dtd\")) {\n\t\t\t// get appropriate dtd from classpath\n\t\t\tInputStream inputStream = Graph.class.getClassLoader().getResourceAsStream(\"dtds/chartformat.dtd\");\n\t\t\tif (inputStream != null)\n\t\t\t\tinputSource = new InputSource(inputStream);\n\t\t}\n\t\treturn inputSource;\n\t}\n\n\t/** Refactored out from load(), parses an Axis. */\n\tpublic static void parseAxis(ValueAxis axis, String minValue,\n\t\t\tString maxValue, String majorGridInterval, String minorGridInterval) {\n\t\tdouble min, max, major, minor;\n\n\t\t// can't work with null axis\n\t\tif (axis == null)\n\t\t\treturn;\n\n\t\ttry {\n\t\t\tmin = Double.parseDouble(minValue);\n\t\t} catch (NumberFormatException e) {\n\t\t\tmin = 0;\n\t\t}\n\t\ttry {\n\t\t\tmax = Double.parseDouble(maxValue);\n\t\t} catch (NumberFormatException e) {\n\t\t\tif (min < 1) {\n\t\t\t\tmax = 1.0;\n\t\t\t} else {\n\t\t\t\tmax = min + 1;\n\t\t\t}\n\t\t}\n\t\ttry {\n\t\t\tmajor = Double.parseDouble(majorGridInterval);\n\t\t} catch (NumberFormatException e) {\n\t\t\tmajor = max / 5;\n\t\t}\n\t\ttry {\n\t\t\tminor = Double.parseDouble(minorGridInterval);\n\t\t} catch (NumberFormatException e) {\n\t\t\tminor = major / 10;\n\t\t}\n\n\t\t// set parameters for axis\n\t\taxis.setLowerBound(min);\n\t\taxis.setUpperBound(max);\n\t\taxis.setTickMarkInsideLength((float) minor);\n\t\taxis.setTickMarkInsideLength((float) major);\n\t}\n\t\n\tpublic static boolean parseBoolean(String boolStr)\n\t{\n\t\treturn (\"true\").equals(boolStr);\n\t}\n\t\n\tpublic static int parseInt(String intStr)\n\t{\n\t\ttry \n\t\t{\n\t\t\tint d = Integer.parseInt(intStr);\n\t\t\treturn d;\n\t\t} \n\t\tcatch (NumberFormatException e) \n\t\t{\n\t\t\treturn 0;\n\t\t}\n\t}\n\t\n\tpublic static double parseDouble(String doubleStr)\n\t{\n\t\ttry \n\t\t{\n\t\t\tdouble d = Double.parseDouble(doubleStr);\n\t\t\treturn d;\n\t\t} \n\t\tcatch (NumberFormatException e) \n\t\t{\n\t\t\treturn Double.NaN;\n\t\t}\n\t}\n\n\t/** Refactored out from load(), parses a Font */\n\tpublic static Font parseFont(String fontName, String fontStyle,\n\t\t\tString fontSize) {\n\t\tint style, size;\n\t\ttry {\n\t\t\tsize = Integer.parseInt(fontSize);\n\t\t\tstyle = Integer.parseInt(fontStyle);\n\t\t} catch (NumberFormatException e) {\n\t\t\t// If there's an error, set defaults\n\t\t\tsize = 14;\n\t\t\tstyle = Font.PLAIN;\n\t\t}\n\t\tif (size <= 0)\n\t\t\tsize = 12;\n\t\tif (fontName.equals(\"\"))\n\t\t\tfontName = \"SansSerif\";\n\n\t\treturn new Font(fontName, style, size);\n\t}\n\n\t/** Refactored out from load(), parses a Color. */\n\tpublic static Color parseColor(String red, String green, String blue) {\n\t\tint r, g, b;\n\n\t\ttry {\n\t\t\tr = Integer.parseInt(red);\n\t\t\tg = Integer.parseInt(green);\n\t\t\tb = Integer.parseInt(blue);\n\n\t\t\tif (r > 255)\n\t\t\t\tr = 255;\n\t\t\tif (r < 0)\n\t\t\t\tr = 0;\n\t\t\tif (g > 255)\n\t\t\t\tg = 255;\n\t\t\tif (g < 0)\n\t\t\t\tg = 0;\n\t\t\tif (b > 255)\n\t\t\t\tb = 255;\n\t\t\tif (b < 0)\n\t\t\t\tb = 0;\n\t\t} catch (NumberFormatException e) {\n\t\t\t// If theres an error, set defaults\n\t\t\tr = 0;\n\t\t\tg = 0;\n\t\t\tb = 0;\n\t\t}\n\t\treturn new Color(r, g, b);\n\t}\n\n\t/**\n\t * Method to load a PRISM 'gra' file into the application.\n\t * @param file Name of the file to load.\n\t * @return The model of the graph contained in the file.\n\t * @throws GraphException if I/O errors have occurred.\n\t */\n\tpublic static Graph load(File file) throws GraphException {\n\t\t\t\t\n\t\t  Graph graph = new Graph();\n\t\t  \n\t\t  try \n\t\t  { \n\t\t\t  DocumentBuilderFactory factory = DocumentBuilderFactory.newInstance();\n\t\t  \n\t\t\t  factory.setValidating(true);\n\t\t\t  factory.setIgnoringElementContentWhitespace(true); DocumentBuilder\n\t\t\t  builder = factory.newDocumentBuilder();\n\t\t\t  builder.setEntityResolver(graph); Document doc = builder.parse(file);\n\t\t\t  Element chartFormat = doc.getDocumentElement();\n\t\t  \n\t\t\t  graph.setTitle(chartFormat.getAttribute(\"graphTitle\"));\n\t\t\t  \n\t\t\t  String titleFontName = chartFormat.getAttribute(\"titleFontName\");\n\t\t\t  String titleFontSize = chartFormat.getAttribute(\"titleFontSize\");\n\t\t\t  String titleFontStyle = chartFormat.getAttribute(\"titleFontStyle\");\n\t\t\t  \n\t\t\t  Font titleFont = parseFont( titleFontName, titleFontStyle, titleFontSize ); \n\t\t\t  \t\t\t  \n\t\t\t  String titleFontColourR = chartFormat.getAttribute(\"titleFontColourR\"); \n\t\t\t  String titleFontColourG = chartFormat.getAttribute(\"titleFontColourG\"); \n\t\t\t  String titleFontColourB = chartFormat.getAttribute(\"titleFontColourB\"); \n\t\t\t  Color titleFontColour = parseColor(titleFontColourR, titleFontColourG, titleFontColourB);\n\t\t\t  \n\t\t\t  graph.setTitleFont(new FontColorPair(titleFont, titleFontColour));\n\t\t\t  graph.setLegendVisible(parseBoolean(chartFormat.getAttribute(\"legendVisible\")));\n\t\t\t  \n\t\t\t  String legendPosition = chartFormat.getAttribute(\"legendPosition\");\n\t\t\t\n\t\t\t  // Facilitate for bugs export in previous prism versions.\n\t\t\t  if (chartFormat.getAttribute(\"versionString\").equals(\"\"))\n\t\t\t\t  graph.setLegendPosition(RIGHT);\n\t\t\t  else\n\t\t\t  {\n\t\t\t\t  if (legendPosition.equals(\"left\"))\n\t\t\t\t\t  graph.setLegendPosition(LEFT);\n\t\t\t\t  else if (legendPosition.equals(\"right\"))\n\t\t\t\t\t  graph.setLegendPosition(RIGHT);\n\t\t\t\t  else if (legendPosition.equals(\"bottom\"))\n\t\t\t\t\t  graph.setLegendPosition(BOTTOM);\n\t\t\t\t  else if (legendPosition.equals(\"top\"))\n\t\t\t\t\t  graph.setLegendPosition(TOP);\n\t\t\t\t  else // Probably was manual, now depricated\n\t\t\t\t\t  graph.setLegendPosition(RIGHT);\n\t\t\t  }\n\t\t\t  \n\t\t\t  //Get the nodes used to describe the various parts of the graph\n\t\t\t  NodeList rootChildren = chartFormat.getChildNodes(); \n\t\t\t  \n\t\t\t  // Element layout is depricated for now. \n\t\t\t  Element layout = (Element) rootChildren.item(0); \n\t\t\t  Element xAxis = (Element) rootChildren.item(1); \n\t\t\t  Element yAxis = (Element) rootChildren.item(2);\n\t\t\t  \n\t\t\t  graph.getXAxisSettings().load(xAxis);\n\t\t\t  graph.getYAxisSettings().load(yAxis);\n\t\t\t  \n\t\t\t  //Read the headings and widths for each series \n\t\t\t  for (int i = 3; i < rootChildren.getLength(); i++) \n\t\t\t  { \n\t\t\t\t  Element series = (Element)rootChildren.item(i);\n\t\t\t\t  SeriesKey key = graph.addSeries(series.getAttribute(\"seriesHeading\"));\n\t\t\t\t  \n\t\t\t\t  synchronized (graph.getSeriesLock())\n\t\t\t\t  {\n\t\t\t\t\t  SeriesSettings seriesSettings = graph.getGraphSeries(key);\n\t\t\t\t\t  seriesSettings.load(series);\n\t\t\t\t\t  \n\t\t\t\t\t  NodeList graphChildren = series.getChildNodes();\n\t\t\t\t\t  \n\t\t\t\t\t  //Read each series out of the file and add its points to the graph\n\t\t\t\t\t  for (int j = 0; j < graphChildren.getLength(); j++) \n\t\t\t\t\t  { \n\t\t\t\t\t\t  Element point = (Element) graphChildren.item(j);\n\t\t\t\t\t\t  graph.addPointToSeries(key, new XYDataItem(parseDouble(point.getAttribute(\"x\")), parseDouble(point.getAttribute(\"y\"))));\n\t\t\t\t\t  }\n\t\t\t\t  }\n\t\t\t  }\t\t  \n\t\t\t \n\t\t\t  \n\t\t\t  \n\t\t\t  //Return the model of the graph \n\t\t\t  return graph; \n\t\t  } \n\t\t  catch (Exception e) \n\t\t  {\n\t\t\t  throw new GraphException(\"Error in loading chart: \" + e); \n\t\t  }\n\t}\n\n\t/**\n\t * Allows graphs to be saved to the PRISM 'gra' file format.\n\t * \n\t * @param file\n\t *            The file to save the graph to.\n\t * @throws GraphException\n\t *             If the file cannot be written.\n\t */\n\tpublic void save(File file) throws PrismException \n\t{\n\t\ttry \n\t\t{ \n\t\t\tJFreeChart chart = getChart(); \n\t\t \tDocumentBuilderFactory factory = DocumentBuilderFactory.newInstance(); \n\t\t \tDocumentBuilder builder = factory.newDocumentBuilder(); \n\t\t \tDocument doc = builder.newDocument();\n\t\t  \n\t\t \tElement chartFormat = doc.createElement(\"chartFormat\");\n\t\t  \n\t\t \tchartFormat.setAttribute(\"versionString\", prism.Prism.getVersion());\n\t\t \tchartFormat.setAttribute(\"graphTitle\", getTitle()); \n\t\t \t\n\t\t \tFont titleFont = getTitleFont().f;\n\t\t \tchartFormat.setAttribute(\"titleFontName\", titleFont.getName());\n\t\t \tchartFormat.setAttribute(\"titleFontSize\", \"\" + titleFont.getSize()); \n\t\t \tchartFormat.setAttribute(\"titleFontStyle\", \"\" + titleFont.getStyle()); \n\t\t \t\n\t\t \tColor titleFontColor = (Color) getTitleFont().c;\n\t\t \tchartFormat.setAttribute(\"titleFontColourR\", \"\" + titleFontColor.getRed());\n\t\t \tchartFormat.setAttribute(\"titleFontColourG\", \"\" + titleFontColor.getGreen());\n\t\t \tchartFormat.setAttribute(\"titleFontColourB\", \"\" + titleFontColor.getBlue());\n\t\t  \n\t\t \tchartFormat.setAttribute(\"legendVisible\", isLegendVisible() ? \"true\" : \"false\");\n\t\t \t\n\t\t \tFont legendFont = getLegendFont().f;\t\t    \n\t\t \tchartFormat.setAttribute(\"legendFontName\", \"\" + legendFont.getName()); \n\t\t \tchartFormat.setAttribute(\"legendFontSize\", \"\" + legendFont.getSize()); \n\t\t \tchartFormat.setAttribute(\"legendFontStyle\", \"\" + legendFont.getStyle()); \n\t\t \t\n\t\t \tColor legendFontColor = getLegendFont().c;\n\t\t \t\n\t\t \tchartFormat.setAttribute(\"legendFontColourR\", \"\" + legendFontColor.getRed());\n\t\t\tchartFormat.setAttribute(\"legendFontColourG\", \"\" + legendFontColor.getGreen());\n\t\t\tchartFormat.setAttribute(\"legendFontColourB\", \"\" + legendFontColor.getBlue());\n\t\t\t\n\t\t\t\n\t\t\tswitch (getLegendPosition()) \n\t\t\t{ \n\t\t  \t\tcase LEFT:\n\t\t  \t\t\tchartFormat.setAttribute(\"legendPosition\", \"left\"); \n\t\t  \t\tbreak; \n\t\t  \t\tcase BOTTOM:\n\t\t  \t\t\tchartFormat.setAttribute(\"legendPosition\", \"bottom\");\n\t\t  \t\tbreak; \n\t\t\t  \tcase TOP:\n\t\t  \t\t\tchartFormat.setAttribute(\"legendPosition\", \"top\"); \n\t\t  \t\tbreak; \n\t\t  \t\tdefault:\n\t\t  \t\t\tchartFormat.setAttribute(\"legendPosition\", \"right\"); \n\t\t\t}\n\t\t\t\n\t\t\tElement layout = doc.createElement(\"layout\");\n\t\t\tchartFormat.appendChild(layout);\n\t\t\t\n\t\t\tElement xAxis = doc.createElement(\"axis\");\n\t\t\tgetXAxisSettings().save(xAxis);\n\t\t\tchartFormat.appendChild(xAxis);\n\t\t\t\n\t\t\tElement yAxis = doc.createElement(\"axis\");\n\t\t\tgetYAxisSettings().save(yAxis);\n\t\t\tchartFormat.appendChild(yAxis);\n\t\t\t\n\t\t\tsynchronized (getSeriesLock()) \n\t\t\t{\n\t\t\t\t/* Make sure we preserve ordering. */\n\t\t\t\tfor (int i = 0; i < seriesList.getSize(); i++)\n\t\t\t\t{\n\t\t\t\t\tSeriesKey key = seriesList.getKeyAt(i);\n\t\t\t\t\t\n\t\t\t\t\tElement series = doc.createElement(\"graph\");\n\t\t\t\t\tSeriesSettings seriesSettings = getGraphSeries(key);\n\t\t\t\t\tseriesSettings.save(series);\n\t\t\t\t\t\n\t\t\t\t\tXYSeries seriesData = getXYSeries(key);\n\t\t\t\t\t\n\t\t\t\t\tfor (int j = 0; j < seriesData.getItemCount(); j++)\n\t\t\t\t\t{ \n\t\t\t\t\t\tElement point = doc.createElement(\"point\");\n\t\t\t\t\t\t \n\t\t\t\t\t\tpoint.setAttribute(\"x\", \"\" + seriesData.getX(j));\n\t\t\t\t\t\tpoint.setAttribute(\"y\", \"\" + seriesData.getY(j));\n\t\t\t\t\t\t\n\t\t\t\t\t\tseries.appendChild(point);\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tchartFormat.appendChild(series);\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\tdoc.appendChild(chartFormat);\n\n\t\t\t// File writing \n\t\t\tTransformer t = TransformerFactory.newInstance().newTransformer();\n\t\t\tt.setOutputProperty(\"doctype-system\", \"chartformat.dtd\");\n\t\t\tt.setOutputProperty(\"indent\", \"yes\"); \n\t\t\tt.transform( new DOMSource(doc), new StreamResult(new FileOutputStream(file)) ); \n\t\t}\n\t\tcatch (IOException e) \n\t\t{ \n\t\t\tthrow new PrismException(e.getMessage()); \n\t\t} \n\t\tcatch (DOMException e) \n\t\t{ \n\t\t\tthrow new PrismException(\"Problem saving graph: DOM Exception: \" + e); \n\t\t} \n\t\tcatch (ParserConfigurationException e) \n\t\t{\n\t\t\tthrow new PrismException(\"Problem saving graph: Parser Exception: \" + e); \n\t\t} \n\t\tcatch (TransformerConfigurationException e) \n\t\t{ \n\t\t\tthrow new PrismException( \"Problem saving graph: Error in creating XML: \" + e); \n\t\t}\n\t\tcatch (TransformerException e) \n\t\t{ \n\t\t\tthrow new PrismException( \"Problem saving graph: Transformer Exception: \" + e); \n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\tthrow new PrismException(e.getMessage());\n\t\t}\n\t}\n\n\t/**\n\t * Exports the current graph to Matlab file format.\n\t * @param f The file to write the data to.\n\t */\n\tpublic void exportToMatlab(File f) throws IOException\n\t{\n\t\tPrintWriter out = new PrintWriter(new FileWriter(f));\n\t\t\n\t\tout.println(\"%=========================================\");\n\t\tout.println(\"%Generated by PRISM Chart Package\");\n\t\tout.println(\"%=========================================\");\n\t\tout.println();\n\t\t\n\t\t//Seriesdata\n\t\tsynchronized (getSeriesLock()) \n\t\t{\n\t\t\t/* Make sure we preserve ordering. */\n\t\t\tfor (int i = 0; i < seriesList.getSize(); i++)\n\t\t\t{\n\t\t\t\tStringBuffer x = new StringBuffer(\"x\"+i+\" = [\");\n\t\t\t\tStringBuffer y = new StringBuffer(\"y\"+i+\" = [\");\n\t\t\t\t\t\n\t\t\t\tSeriesKey key = seriesList.getKeyAt(i);\n\t\t\t\t\n\t\t\t\tXYSeries seriesData = getXYSeries(key);\n\t\t\t\t\n\t\t\t\tfor (int j = 0; j < seriesData.getItemCount(); j++)\n\t\t\t\t{ \n\t\t\t\t\tx.append(seriesData.getX(j) + \" \");\n\t\t\t\t\ty.append(seriesData.getY(j) + \" \");\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tx.append(\"];\");\n\t\t\t\ty.append(\"];\");\n\t\t\t\t\n\t\t\t\tout.println(x.toString());\n\t\t\t\tout.println(y.toString());\n\t\t\t}\n\t\t\n\t\t\n\t\t\t//Create a figure\n\t\t\tout.println();\n\t\t\tout.println(\"figure1 = figure('Color', [1 1 1], 'PaperPosition',[0.6345 6.345 20.3 15.23],'PaperSize',[20.98 29.68]);\");\n\t\t\t\n\t\t\t//Create axes\n\t\t\tboolean xLog = getXAxisSettings().isLogarithmic();\n\t\t\tboolean yLog = getYAxisSettings().isLogarithmic();\n\t\t\t\n\t\t\tout.println();\n\t\t\t\n\t\t\tif(xLog && yLog)\n\t\t\t\tout.println(\"axes1 = axes('Parent', figure1, 'FontSize', 16, 'XScale', 'log', 'YScale', 'log');\");\n\t\t\telse if(xLog)\n\t\t\t\tout.println(\"axes1 = axes('Parent', figure1, 'FontSize', 16, 'XScale', 'log');\");\n\t\t\telse if(yLog)\n\t\t\t\tout.println(\"axes1 = axes('Parent', figure1, 'FontSize', 16, 'YScale', 'log');\");\n\t\t\telse\n\t\t\t\tout.println(\"axes1 = axes('Parent', figure1, 'FontSize', 16);\");\n\t\t\t\n\t\t\tout.println(\"xlabel(axes1, '\" + getXAxisSettings().getHeading() + \"');\");\n\t\t\tout.println(\"ylabel(axes1, '\" + getYAxisSettings().getHeading() + \"');\");\n\t\t\t\n\t\t\tout.println(\"box(axes1, 'on');\");\n\t\t\tout.println(\"hold(axes1, 'all');\");\n\t\t\t\n\t\t\t//Graph title\n\t\t\tout.println();\n\t\t\t\n\t\t\tString title = \"\";\n\t\t\tStringTokenizer st = new StringTokenizer(getTitle(), \"\\n\");\n\t\t\t\n\t\t\tint num = st.countTokens();\n\t\t\tfor(int i = 0; i < num; i++)\n\t\t\t{\n\t\t\t\ttitle += \"'\"+ st.nextToken()+\"'\";\n\t\t\t\tif(i < num - 1) \n\t\t\t\t\ttitle += \", char(10),\";\n\t\t\t}\n\t\t\t\n\t\t\tout.println(\"title(axes1,[\"+title+\"])\");\n\t\t\t\t\n\t\t\t//Sort out logarithmic scales\n\t\t\tString scaleType = \"plot\";\n\t\t\tif(seriesList.getSize() > 0)\n\t\t\t{\n\t\t\t\tif(xLog && yLog)\n\t\t\t\t\tscaleType = \"loglog\";\n\t\t\t\telse if(xLog)\n\t\t\t\t\tscaleType = \"semilogx\";\n\t\t\t\telse if(yLog)\n\t\t\t\t\tscaleType = \"semilogy\";\n\t\t\t}\n\t\t\n\t\t\t//Create plots\n\t\t\tfor(int i = 0; i < seriesList.getSize(); i++)\n\t\t\t{\n\t\t\t\tSeriesKey key = seriesList.getKeyAt(i);\n\t\t\t\tSeriesSettings seriesSettings = getGraphSeries(key);\n\t\t\t\t\n\t\t\t\tString marker = \"'\";\n\t\t\t\tif(seriesSettings.showPoints() && seriesSettings.getSeriesShape() != SeriesSettings.NONE)\n\t\t\t\t{\n\t\t\t\t\tswitch(seriesSettings.getSeriesShape())\n\t\t\t\t\t{\n\t\t\t\t\t\tcase SeriesSettings.CIRCLE: \n\t\t\t\t\t\t\tmarker += \"o\";\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase SeriesSettings.SQUARE: \n\t\t\t\t\t\t\tmarker += \"s\";\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase SeriesSettings.TRIANGLE: \n\t\t\t\t\t\t\tmarker += \"^\";\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase SeriesSettings.RECTANGLE_H: \n\t\t\t\t\t\t\tmarker += \"d\"; \n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase SeriesSettings.RECTANGLE_V: \n\t\t\t\t\t\t\tmarker += \"x\"; \n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tif(seriesSettings.showLines())\n\t\t\t\t{\n\t\t\t\t\tswitch(seriesSettings.getLineStyle())\n\t\t\t\t\t{\n\t\t\t\t\t\tcase SeriesSettings.SOLID: \n\t\t\t\t\t\t\tmarker += \"-\";\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase SeriesSettings.DASHED: \n\t\t\t\t\t\t\tmarker += \"--\";\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\tcase SeriesSettings.DOT_DASHED: \n\t\t\t\t\t\t\tmarker += \"-.\";\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tmarker+=\"'\";\n\t\t\t\tout.println(\"plot\"+i+\" = \"+scaleType+\"(x\"+i+\", y\"+i+\", \"+marker+\", 'Parent', axes1, 'LineWidth', 2);\");\n\t\t\t}\n\t\t\t\n\t\t\t//\t\t\tCreate legend\n\t\t\tString seriesNames = \"\";\n\t\t\tfor(int i = 0; i < seriesList.getSize(); i++)\n\t\t\t{\n\t\t\t\tSeriesKey key = seriesList.getKeyAt(i);\n\t\t\t\tSeriesSettings seriesSettings = getGraphSeries(key);\n\t\t\t\t\n\t\t\t\tseriesNames+=\"'\" + seriesSettings.getSeriesHeading() + \"'\";\n\t\t\t\tif(i < seriesList.getSize() - 1) seriesNames+=\", \";\n\t\t\t}\n\t\t\t\n\t\t\t//Determine location\n\t\t\t\n\t\t\tString loc = \"\";\n\t\t\tswitch(legendPosition.getCurrentIndex())\n\t\t\t{\n\t\t\t\tcase LEFT: loc = \"'WestOutside'\";break;\n\t\t\t\tcase RIGHT: loc = \"'EastOutside'\";break;\n\t\t\t\tcase BOTTOM: loc = \"'SouthOutside'\";break;\n\t\t\t\tcase TOP: loc = \"'NorthOutside'\";break;\n\t\t\t}\n\t\t\t\n\t\t\tif(isLegendVisible())\n\t\t\t\tout.println(\"legend1 = legend(axes1,{\"+seriesNames+\"},'Location', \"+loc+\");\");\n\t\t\t\n\t\t\tout.flush();\n\t\t\tout.close();\n\t\t}\n\t}\n\t\n\t/**\n\t * Renders the current graph to a JPEG file.\n\t * \n\t * @param file\n\t *             The file to export the JPEG data to.\n\t * @throws GraphException, IOException\n\t *             If file cannot be written to.\n\t */\n\tpublic void exportToJPEG(File file, int width, int height) throws GraphException, IOException\n\t{\t\n\t\tChartUtilities.saveChartAsJPEG(file, 1.0f, this.chart, width, height);\n\t}\n\t\n\tpublic void exportToEPS(File file, int width, int height) throws GraphException, IOException\n\t{\n\t\tFileOutputStream fileOutputStream = new FileOutputStream(file);\n\t\t\n\t\tEpsGraphics g2d = new EpsGraphics(this.getTitle(), fileOutputStream, 0, 0, width, height, ColorMode.COLOR_RGB);\n\t\t\n\t\t// Don't export fonts as vectors, no hope of getting same font as publication.\n\t\t// g2d.setAccurateTextMode(false); // Does not rotate y-axis label.\n\t\t\n        chart.draw(g2d, new Rectangle(width, height));\n        \n        g2d.close();\n        g2d.dispose();\n\t}\n\t\t\n\t/**\n\t * Renders the current graph to a JPEG file.\n\t * \n\t * @param file\n\t *             The file to export the JPEG data to.\n\t * @throws GraphException, IOException\n\t *             If file cannot be written to.\n\t */\n\tpublic void exportToPNG(File file, int width, int height, boolean alpha) throws GraphException, IOException\n\t{\t\n\t\t\n\t\tFileOutputStream fileOutputStream = new FileOutputStream(file);\n\t\t\n\t\tKeypointPNGEncoderAdapter encoder = new KeypointPNGEncoderAdapter();\n\t\tencoder.setEncodingAlpha(alpha);\n\t\t\n\t\tPaint bgPaint = chart.getBackgroundPaint();\n\t\t\n\t\tif (alpha)\n\t\t{\n\t\t\tchart.setBackgroundPaint(null);\t\t\t\n\t\t}\n\t\t\n\t\tBufferedImage bufferedImage = chart.createBufferedImage(width, height, alpha ? BufferedImage.TYPE_INT_ARGB : BufferedImage.TYPE_INT_RGB, null);\n\t\t\n\t\tif (alpha)\n\t\t{\n\t\t\tchart.setBackgroundPaint(bgPaint);\t\t\t\n\t\t}\n\t\t\n\t\tencoder.encode(bufferedImage, fileOutputStream);\n\t\t\n\t\tfileOutputStream.flush();\n\t\tfileOutputStream.close();\n\t\t\n\t\t//ChartUtilities.saveChartAsPNG(file, this.chart, width, height, null, alpha, 9);\n\t}\n\t\n\t/**\n\t * Exports the current data sets to a comma seperated value file.\n\t * \n\t * @param file\n\t *            The file to export the csv data to.\n\t * @throws GraphException\n\t *             If file cannont be written to.\n\t */\n\tpublic void exportToCSV(File file) throws GraphException \n\t{\t\t\n\t\t/*try \n\t\t{ \n\t\t\tPrintWriter out = new PrintWriter(new FileWriter(file)); \n\t\t\t\n\t\t\t// Create the header, this is a comma seperate list of the titles \n\t\t\t// of the series followed by an x or y String header = \"\"; \n\t\t\t  \n\t\t\tsynchronize(this.getSeriesLock())\n\t\t\t{\n\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\tint largestGraph = 0;\n\t\t\t \n\t\t\t// Consider every series in this model \n\t\t\tfor (int i = 0; i < getNumSeries(); i++) \n\t\t\t{ \n\t\t\t\t// While were iterating through the graphs, record the size of the largest graph \n\t\t\t\tif (getGraphPoints(i).getItemCount() > largestGraph) \n\t\t\t\t{ \n\t\t\t\t\tlargestGraph = getGraphPoints(i).getItemCount(); \n\t\t\t\t}\n\t\t\t   \n\t\t\t\t// Add the series titles \n\t\t\t\theader += \"[\" + getGraphPoints(i).getKey() + \"].x,\"; \n\t\t\t\theader += \"[\" + getGraphPoints(i).getKey() + \"].y\";\n\t\t\t \n\t\t\t\t// If this isnt the last series add the comma \n\t\t\t\tif (i < getNumSeries() - * 1) \n\t\t\t\t\theader += \", \"; \n\t\t\t}\n\t\t\t\n\t\t\t// Print the header to the file\n\t\t    out.println(header);\n\t\t \n\t\t    // Format of the file has the data in columns, so iterate through \n\t\t    // the points in all the graphs adding the next point from each graph \n\t\t    // on the same line \n\t\t    \n\t\t    String line = \"\"; \n\t\t  \n\t\t    for (int i = 0; i < largestGraph; i++) \n\t\t    { \n\t\t    \tline = \"\";\n\t\t  \n\t\t    \t// For each point, iterate through all the graphs \n\t\t    \tfor (int j = 0; j < getNumSeries(); j++) \n\t\t    \t{ \n\t\t    \t\tXYSeries gs = getGraphPoints(j);\n\t\t    \t\t  \n\t\t    \t\t// If the current graph doesnt have this point, ie its smaller \n\t\t    \t\t// than the largest supply \"\",\"\" for the data \n\t\t  \n\t\t\t\t\tif (i >= gs.getItemCount()) \n\t\t\t\t\t{ \n\t\t\t\t\t\tline += \"\\\"\\\",\\\"\\\"\"; \n\t\t\t\t\t} \n\t\t\t\t\telse \n\t\t\t\t\t{ \n\t\t\t\t\t\t// Otherwise add the next data point \n\t\t\t\t\t\tline += gs.getX(i) + \",\"; line += gs.getY(i); \n\t\t\t\t\t}\n\t\t  \n\t\t\t\t\tif (j < getNumSeries() - 1) \n\t\t\t\t\t\tline += \", \"; \n\t\t    \t}\n\t\t \n\t\t    \tout.println(line); \n\t\t    }\n\t\t    \n\t\t    out.flush(); \n\t\t    out.close();\n\t\t} \n\t\tcatch (Exception e) \n\t\t{ \n\t\t\tthrow new ChartException(e); \n\t\t}\t\n\t\t*/  \n\t}\n\n\t/**\n\t * This inner class provides a means of asynchronously performing graph\n\t * updates. This has two advantages.\n\t * \n\t * Firstly, it improves the callee's performance as adding data is\n\t * effectively non-blocking.\n\t * \n\t * Secondly, it improves the interactive response of the chart, as fewer\n\t * draws are performed. According to JFreeChart's own FAQ, it is not\n\t * designed for real-time charting.\n\t */\n\tprivate class GraphUpdateTask extends TimerTask {\n\t\tprivate void processGraphCache(\n\t\t\t\tHashMap<SeriesKey, LinkedList<XYDataItem>> graphCache) {\n\t\t\tsynchronized (seriesCollection) {\n\t\t\t\tfor (Map.Entry<SeriesKey, LinkedList<XYDataItem>> entry : graphCache\n\t\t\t\t\t\t.entrySet()) {\n\t\t\t\t\t\n\t\t\t\t\t/* The series key should map to a series. */\n\t\t\t\t\tif (keyToSeries.containsKey(entry.getKey())) {\n\t\t\t\t\t\tXYSeries series = keyToSeries.get(entry.getKey());\n\t\t\t\t\t\tLinkedList<XYDataItem> seriesCache = entry.getValue();\n\n\t\t\t\t\t\twhile (!seriesCache.isEmpty()) {\n\t\t\t\t\t\t\tXYDataItem item = seriesCache.removeFirst();\n\t\t\t\t\t\t\tseries.addOrUpdate(item.getX(), item.getY());\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tpublic void run() {\n\t\t\tprocessGraphCache(graphCache);\n\t\t}\n\t}\n\n\t/**\n\t * This is a dummy class used to be able to index Series in this graph.\n\t * Previously this was done using integers, which was unsafe if removeSeries\n\t * was used. The hashcode() and equals() implementation of Object (based on\n\t * object identity) are sufficient to use this as the key of a HashMap.\n\t * In addition, we add a 'next' field, to allow the same class to be used\n\t * to store (linked) lists of keys.\n\t */\n\tpublic class SeriesKey \n\t{\n\t\tpublic SeriesKey next = null;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/graph/GraphException.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\npublic class GraphException extends Exception\n{\n\tpublic GraphException(String s)\n\t{\n\t\tsuper(s);\n\t}\n\n\tpublic GraphException(Exception e)\n\t{\n\t\tsuper(e);\n\t}\n\n\tpublic String toString()\n\t{\n\t\treturn \"Error: \" + getMessage() + \".\";\n\t}\n}\n\n//------------------------------------------------------------------------------\n"
  },
  {
    "path": "prism/src/userinterface/graph/GraphOptions.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport java.awt.event.*;\n\nimport userinterface.*;\n\n/**\n * This class is to make the new chart package compatible with the old.\n */\npublic class GraphOptions extends JDialog\n{\n\tprivate GraphOptionsPanel gop;\n\t/** Creates a new instance of MultiGraphOptions */\n\tpublic GraphOptions(GUIPlugin plugin, Graph theModel, JFrame gui, String title)\n\t{\n\t\tsuper(gui, title);\n\t\t\n\t\tgop = new GraphOptionsPanel(plugin, gui, theModel); \n\t\t\n\t\tgop.setPreferredSize(new Dimension(400,650));\n\t\t\n\t\tthis.getContentPane().add(gop);\n\t\t\n\t\tJPanel p = new JPanel(new FlowLayout(FlowLayout.RIGHT));\n\t\tthis.getContentPane().add(p, BorderLayout.SOUTH);\n\t\t\n\t\tthis.getContentPane().setSize(400,650);\n\t\t\n\t\tJButton jb = new JButton(\"Close\");\n\t\t\n\t\tjb.addActionListener(new ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tgop.stopEditors();\n\t\t\t\tsetVisible(false);\n\t\t\t}\n\t\t}\n\t\t);\n\t\t\n\t\tjb.addFocusListener(new FocusListener()\n\t\t{\n\t\t\t/**\n\t\t\t * Invoked when a component gains the keyboard focus.\n\t\t\t */\n\t\t\tpublic void focusGained(FocusEvent e){}\n\t\t\t\n\t\t\t/**\n\t\t\t * Invoked when a component loses the keyboard focus.\n\t\t\t */\n\t\t\tpublic void focusLost(FocusEvent e)\n\t\t\t{ \n\t\t\t\t//gop.stopEditors();\n\t\t\t}\n\t\t\t\n\t\t});\n\t\t\n\t\tp.add(jb);\n\t\t\n\t\t\n\t\tpack();\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t\t//show();\n\t\tsetDefaultCloseOperation(javax.swing.JFrame.DISPOSE_ON_CLOSE);\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/graph/GraphOptionsPanel.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-9,0,0,2,45\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JTabbedPane\" name=\"tabbedPanel\">\n      <Events>\n        <EventHandler event=\"stateChanged\" listener=\"javax.swing.event.ChangeListener\" parameters=\"javax.swing.event.ChangeEvent\" handler=\"tabbedPanelStateChanged\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"true\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"graphOptionsPanel\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n              </Border>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Graph\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Graph\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"innerGraphOptionsPanel\">\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"innerGraphOptionsPanel.add(graphPropertiesTable, java.awt.BorderLayout.CENTER);\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"axisOptionsPanel\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n              </Border>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Axes\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Axes\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"innerAxesOptionsPanel\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JSplitPane\" name=\"axesOptionPanelSplitPane\">\n                  <Properties>\n                    <Property name=\"dividerLocation\" type=\"int\" value=\"80\"/>\n                    <Property name=\"orientation\" type=\"int\" value=\"0\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"Center\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"axesTopPanel\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                          <JSplitPaneConstraints position=\"left\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JPanel\" name=\"axesInnerTopPanel\">\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"Center\"/>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Component class=\"javax.swing.JLabel\" name=\"axesLabel\">\n                              <Properties>\n                                <Property name=\"text\" type=\"java.lang.String\" value=\"Select Axis:\"/>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"North\"/>\n                                </Constraint>\n                              </Constraints>\n                            </Component>\n                            <Container class=\"javax.swing.JPanel\" name=\"axesListPanel\">\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"Center\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JPanel\" name=\"axesInnerListPanel\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                                      <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.75\" weightY=\"1.0\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Container class=\"javax.swing.JScrollPane\" name=\"axesListScrollPane\">\n                                      <Properties>\n                                        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[32767, 120]\"/>\n                                        </Property>\n                                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[20, 22]\"/>\n                                        </Property>\n                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[3, 120]\"/>\n                                        </Property>\n                                      </Properties>\n                                      <AuxValues>\n                                        <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"axesListScrollPane.setViewportView(axesList); \"/>\n                                      </AuxValues>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                      </SubComponents>\n                    </Container>\n                    <Container class=\"javax.swing.JPanel\" name=\"axesBottomPanel\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <AuxValues>\n                        <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"axesBottomPanel.add(axisPropertiesTable, BorderLayout.CENTER);&#xa;        \"/>\n                      </AuxValues>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                          <JSplitPaneConstraints position=\"right\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                    </Container>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"seriesOptionsPanel\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n              </Border>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Series\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Series\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JSplitPane\" name=\"seriesOptionPanelSplitPane\">\n              <Properties>\n                <Property name=\"orientation\" type=\"int\" value=\"0\"/>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"seriesTopPanel\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                        <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                      </Border>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                      <JSplitPaneConstraints position=\"left\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"seriesInnerTopPanel\">\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                      <SubComponents>\n                        <Component class=\"javax.swing.JLabel\" name=\"seriesLabel\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Select Series:\"/>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"North\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                        <Container class=\"javax.swing.JPanel\" name=\"seriesListPanel\">\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"Center\"/>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"seriesInnerListPanel\">\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                                  <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.75\" weightY=\"1.0\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JScrollPane\" name=\"seriesListScrollPane\">\n                                  <Properties>\n                                    <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[32767, 120]\"/>\n                                    </Property>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[20, 22]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[3, 120]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <AuxValues>\n                                    <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"seriesListScrollPane.setViewportView(seriesList);&#xa;\"/>\n                                  </AuxValues>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                            <Container class=\"javax.swing.JPanel\" name=\"seriesButtonPanel\">\n                              <Properties>\n                                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[2147483647, 105]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                                  <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"5\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"11\" weightX=\"0.25\" weightY=\"1.0\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                                <Property name=\"columns\" type=\"int\" value=\"1\"/>\n                                <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                                <Property name=\"rows\" type=\"int\" value=\"5\"/>\n                                <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                              </Layout>\n                              <SubComponents>\n                                <Component class=\"javax.swing.JButton\" name=\"addSeries\">\n                                  <Properties>\n                                    <Property name=\"text\" type=\"java.lang.String\" value=\"Add\"/>\n                                    <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 25]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 25]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Events>\n                                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"addSeriesActionPerformed\"/>\n                                  </Events>\n                                  <AuxValues>\n                                    <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"addSeries.setIcon(new ImageIcon(ClassLoader.getSystemResource(&quot;images/smallAdd.gif&quot;)));\"/>\n                                  </AuxValues>\n                                </Component>\n                                <Component class=\"javax.swing.JButton\" name=\"removeSeries\">\n                                  <Properties>\n                                    <Property name=\"text\" type=\"java.lang.String\" value=\"Remove\"/>\n                                    <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 25]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 25]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Events>\n                                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"removeSeriesActionPerformed\"/>\n                                  </Events>\n                                  <AuxValues>\n                                    <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"removeSeries.setIcon(new ImageIcon(ClassLoader.getSystemResource(&quot;images/smallDelete.gif&quot;)));\"/>\n                                  </AuxValues>\n                                </Component>\n                                <Component class=\"javax.swing.JButton\" name=\"moveUp\">\n                                  <Properties>\n                                    <Property name=\"text\" type=\"java.lang.String\" value=\"Move Up\"/>\n                                    <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 25]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 25]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Events>\n                                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"moveUpActionPerformed\"/>\n                                  </Events>\n                                  <AuxValues>\n                                    <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"moveUp.setIcon(new ImageIcon(ClassLoader.getSystemResource(&quot;images/smallUp.gif&quot;)));\"/>\n                                  </AuxValues>\n                                </Component>\n                                <Component class=\"javax.swing.JButton\" name=\"moveDown\">\n                                  <Properties>\n                                    <Property name=\"text\" type=\"java.lang.String\" value=\"Move Down\"/>\n                                    <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 25]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 25]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Events>\n                                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"moveDownActionPerformed\"/>\n                                  </Events>\n                                  <AuxValues>\n                                    <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"moveDown.setIcon(new ImageIcon(ClassLoader.getSystemResource(&quot;images/smallDown.gif&quot;)));\"/>\n                                  </AuxValues>\n                                </Component>\n                                <Component class=\"javax.swing.JButton\" name=\"viewData\">\n                                  <Properties>\n                                    <Property name=\"text\" type=\"java.lang.String\" value=\"Edit Data\"/>\n                                    <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                  </Properties>\n                                  <Events>\n                                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"viewDataActionPerformed\"/>\n                                  </Events>\n                                  <AuxValues>\n                                    <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"viewData.setIcon(new ImageIcon(ClassLoader.getSystemResource(&quot;images/gridSnap.gif&quot;)));\"/>\n                                  </AuxValues>\n                                </Component>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"seriesBottomPanel\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                        <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                      </Border>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"seriesBottomPanel.add(seriesPropertiesTable, BorderLayout.CENTER);\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                      <JSplitPaneConstraints position=\"right\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"displayOptionsPanel\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n              </Border>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Display\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Display\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"innerDisplayOptionsPanel\">\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"innerDisplayOptionsPanel.add(displayPropertiesTable, java.awt.BorderLayout.CENTER);&#xa;\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/graph/GraphOptionsPanel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport java.awt.*;\nimport java.util.*;\n\nimport javax.swing.*;\nimport javax.swing.event.*;\n\nimport settings.*;\nimport userinterface.*;\n\npublic class GraphOptionsPanel extends JPanel implements ListSelectionListener\n{\n\tprivate SettingTable graphPropertiesTable, axisPropertiesTable, displayPropertiesTable, seriesPropertiesTable;\n\t\n\tprivate JList seriesList, axesList;\n\t\n\tprivate Graph theModel;\n\tprivate AxisSettings xAxisSettings;\n\tprivate AxisSettings yAxisSettings;\n\tprivate DisplaySettings displaySettings;\n\t\n\tprivate JFrame parent;\n\tprivate GUIPlugin plugin;\n\t\n\t/** Creates new form GraphOptionsPanel */\n\tpublic GraphOptionsPanel(GUIPlugin plugin, JFrame parent, Graph theModel)\n\t{\n\t\tthis.plugin = plugin;\n\t\tthis.parent = parent;\n\t\tthis.theModel = theModel;\n\t\t\n\t\t/* TODO: Use generic container. */ \n\t\tArrayList own = new ArrayList();\n\t\town.add(theModel);\n\t\t\n\t\tgraphPropertiesTable = new SettingTable(parent);\n\t\tgraphPropertiesTable.setOwners(own);\n\t\ttheModel.setDisplay(graphPropertiesTable);\n\t\t\n\t\txAxisSettings = theModel.getXAxisSettings();\n\t\tyAxisSettings = theModel.getYAxisSettings();\n\t\tdisplaySettings = theModel.getDisplaySettings();\n\t\t\n\t\tString[] axes = {\"x-Axis\", \"y-Axis\"};\n\t\taxesList = new JList(axes);\n\t\taxesList.setSelectedIndex(0);\n\t\t\n\t\taxesList.addListSelectionListener(this);\n\t\t\n\t\town = new ArrayList();\t\t\n\t\town.add(xAxisSettings);\t\t\n\t\taxisPropertiesTable = new SettingTable(parent);\n\t\taxisPropertiesTable.setOwners(own);\n\t\txAxisSettings.setDisplay(axisPropertiesTable);\n\t\tyAxisSettings.setDisplay(axisPropertiesTable);\n\t\t\n\t\town = new ArrayList();\t\t\n\t\town.add(displaySettings);\n\t\tdisplayPropertiesTable = new SettingTable(parent);\n\t\tdisplayPropertiesTable.setOwners(own);\t\t\n\t\tdisplaySettings.setDisplay(displayPropertiesTable);\n\t\t\n\t\tseriesList = new JList(theModel.getGraphSeriesList());\t\t\n\t\tseriesList.addListSelectionListener(this);\n\t\tseriesList.setCellRenderer(new ListCellRenderer() {\n\t\t\t\t\t\n\t\t\tpublic Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) \n\t\t\t{\n\t\t\t\tJLabel label = new JLabel((value == null) ? \"undefined\" : value.toString());\n\t\t\t\tJPanel panel = new JPanel();\n\t\t\t\t\n\t\t\t\tpanel.setLayout(new FlowLayout(FlowLayout.LEFT, 5, 0));\n\t\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\tif (isSelected) \n\t\t\t\t{\n\t\t\t\t\tpanel.setBackground(list.getSelectionBackground());\n\t\t\t\t\tpanel.setForeground(list.getSelectionForeground());\n\t\t        } \n\t\t\t\telse \n\t\t        {\n\t\t\t\t\tpanel.setBackground(list.getBackground());\n\t\t        \tpanel.setForeground(list.getForeground());\n\t\t        }\n\t\t\t\t\n\t\t\t\tif (value instanceof SeriesSettings)\n\t\t\t\t{\n\t\t\t\t\tSeriesSettings graphSeries = (SeriesSettings)value;\n\t\t\t\t\tpanel.add(graphSeries.getIcon());\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tpanel.add(label);\n\t\t\t\t\t\t\t\t\n\t\t\t\treturn panel;\n\t\t\t}\n\t\t});\n\t\t\t\n\t\tseriesPropertiesTable = new SettingTable(parent);\n\t\t\n\t\t\n\t\t/*seriesList = theModel.getSeriesList();\n\t\tseriesList.addListSelectionListener(this);\n\t\t//seriesModel = new PropertyTableModel();\n\t\tArrayList ss = seriesList.getSelectedSeries();\n\t\t//seriesModel.setOwners(ss);\n\t\t\n\t\tseriesProperties = new SettingTable(parent);\n\t\tseriesProperties.setOwners(ss);*/\n\t\tinitComponents();\n\t\t//addSeries.setEnabled(ss.size() > 0);\n\t\t/*removeSeries.setEnabled(ss.size() > 0);\n\t\tmoveUp.setEnabled(ss.size() > 0);\n\t\tmoveDown.setEnabled(ss.size() > 0);\n\t\tviewData.setEnabled(ss.size() > 0);*/\n\t\t\n\t\t\n\t}\n\t\n\tpublic void stopEditors()\n\t{\n\t\tgraphPropertiesTable.stopEditing();\n\t\taxisPropertiesTable.stopEditing();\n\t\tseriesPropertiesTable.stopEditing();\n\t\tdisplayPropertiesTable.stopEditing();\n\t}\n\t\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\t//javax.swing.JPanel jPanel6;\n    // <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n    private void initComponents() {\n        java.awt.GridBagConstraints gridBagConstraints;\n        javax.swing.JTabbedPane tabbedPanel;\n\n        tabbedPanel = new javax.swing.JTabbedPane();\n        graphOptionsPanel = new javax.swing.JPanel();\n        innerGraphOptionsPanel = new javax.swing.JPanel();\n        axisOptionsPanel = new javax.swing.JPanel();\n        innerAxesOptionsPanel = new javax.swing.JPanel();\n        axesOptionPanelSplitPane = new javax.swing.JSplitPane();\n        axesTopPanel = new javax.swing.JPanel();\n        axesInnerTopPanel = new javax.swing.JPanel();\n        axesLabel = new javax.swing.JLabel();\n        axesListPanel = new javax.swing.JPanel();\n        axesInnerListPanel = new javax.swing.JPanel();\n        axesListScrollPane = new javax.swing.JScrollPane();\n        axesBottomPanel = new javax.swing.JPanel();\n        seriesOptionsPanel = new javax.swing.JPanel();\n        seriesOptionPanelSplitPane = new javax.swing.JSplitPane();\n        seriesTopPanel = new javax.swing.JPanel();\n        seriesInnerTopPanel = new javax.swing.JPanel();\n        seriesLabel = new javax.swing.JLabel();\n        seriesListPanel = new javax.swing.JPanel();\n        seriesInnerListPanel = new javax.swing.JPanel();\n        seriesListScrollPane = new javax.swing.JScrollPane();\n        seriesButtonPanel = new javax.swing.JPanel();\n        addSeries = new javax.swing.JButton();\n        removeSeries = new javax.swing.JButton();\n        moveUp = new javax.swing.JButton();\n        moveDown = new javax.swing.JButton();\n        viewData = new javax.swing.JButton();\n        seriesBottomPanel = new javax.swing.JPanel();\n        displayOptionsPanel = new javax.swing.JPanel();\n        innerDisplayOptionsPanel = new javax.swing.JPanel();\n\n        setLayout(new java.awt.BorderLayout());\n\n        tabbedPanel.addChangeListener(new javax.swing.event.ChangeListener() {\n            public void stateChanged(javax.swing.event.ChangeEvent evt) {\n                tabbedPanelStateChanged(evt);\n            }\n        });\n\n        graphOptionsPanel.setLayout(new java.awt.BorderLayout());\n\n        graphOptionsPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        innerGraphOptionsPanel.setLayout(new java.awt.BorderLayout());\n\n        innerGraphOptionsPanel.add(graphPropertiesTable, java.awt.BorderLayout.CENTER);\n        graphOptionsPanel.add(innerGraphOptionsPanel, java.awt.BorderLayout.CENTER);\n\n        tabbedPanel.addTab(\"Graph\", graphOptionsPanel);\n\n        axisOptionsPanel.setLayout(new java.awt.BorderLayout());\n\n        axisOptionsPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        innerAxesOptionsPanel.setLayout(new java.awt.BorderLayout());\n\n        axesOptionPanelSplitPane.setDividerLocation(80);\n        axesOptionPanelSplitPane.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);\n        axesTopPanel.setLayout(new java.awt.BorderLayout());\n\n        axesTopPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        axesInnerTopPanel.setLayout(new java.awt.BorderLayout());\n\n        axesLabel.setText(\"Select Axis:\");\n        axesInnerTopPanel.add(axesLabel, java.awt.BorderLayout.NORTH);\n\n        axesListPanel.setLayout(new java.awt.GridBagLayout());\n\n        axesInnerListPanel.setLayout(new java.awt.BorderLayout());\n\n        axesListScrollPane.setMaximumSize(new java.awt.Dimension(32767, 120));\n        axesListScrollPane.setMinimumSize(new java.awt.Dimension(20, 22));\n        axesListScrollPane.setPreferredSize(new java.awt.Dimension(3, 120));\n        axesListScrollPane.setViewportView(axesList);\n        axesInnerListPanel.add(axesListScrollPane, java.awt.BorderLayout.CENTER);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n        gridBagConstraints.weightx = 0.75;\n        gridBagConstraints.weighty = 1.0;\n        axesListPanel.add(axesInnerListPanel, gridBagConstraints);\n\n        axesInnerTopPanel.add(axesListPanel, java.awt.BorderLayout.CENTER);\n\n        axesTopPanel.add(axesInnerTopPanel, java.awt.BorderLayout.CENTER);\n\n        axesOptionPanelSplitPane.setLeftComponent(axesTopPanel);\n\n        axesBottomPanel.setLayout(new java.awt.BorderLayout());\n\n        axesBottomPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        axesBottomPanel.add(axisPropertiesTable, BorderLayout.CENTER);\n\n        axesOptionPanelSplitPane.setRightComponent(axesBottomPanel);\n\n        innerAxesOptionsPanel.add(axesOptionPanelSplitPane, java.awt.BorderLayout.CENTER);\n\n        axisOptionsPanel.add(innerAxesOptionsPanel, java.awt.BorderLayout.CENTER);\n\n        tabbedPanel.addTab(\"Axes\", axisOptionsPanel);\n\n        seriesOptionsPanel.setLayout(new java.awt.BorderLayout());\n\n        seriesOptionsPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        seriesOptionPanelSplitPane.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);\n        seriesTopPanel.setLayout(new java.awt.BorderLayout());\n\n        seriesTopPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        seriesInnerTopPanel.setLayout(new java.awt.BorderLayout());\n\n        seriesLabel.setText(\"Select Series:\");\n        seriesInnerTopPanel.add(seriesLabel, java.awt.BorderLayout.NORTH);\n\n        seriesListPanel.setLayout(new java.awt.GridBagLayout());\n\n        seriesInnerListPanel.setLayout(new java.awt.BorderLayout());\n\n        seriesListScrollPane.setMaximumSize(new java.awt.Dimension(32767, 120));\n        seriesListScrollPane.setMinimumSize(new java.awt.Dimension(20, 22));\n        seriesListScrollPane.setPreferredSize(new java.awt.Dimension(3, 120));\n        seriesListScrollPane.setViewportView(seriesList);\n\n        seriesInnerListPanel.add(seriesListScrollPane, java.awt.BorderLayout.CENTER);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n        gridBagConstraints.weightx = 0.75;\n        gridBagConstraints.weighty = 1.0;\n        seriesListPanel.add(seriesInnerListPanel, gridBagConstraints);\n\n        seriesButtonPanel.setLayout(new java.awt.GridLayout(5, 1, 5, 5));\n\n        seriesButtonPanel.setMaximumSize(new java.awt.Dimension(2147483647, 105));\n        addSeries.setText(\"Add\");\n        addSeries.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        addSeries.setMinimumSize(new java.awt.Dimension(5, 25));\n        addSeries.setPreferredSize(new java.awt.Dimension(5, 25));\n        addSeries.setIcon(GUIPrism.getIconFromImage(\"smallAdd.png\"));\n        addSeries.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                addSeriesActionPerformed(evt);\n            }\n        });\n\n        seriesButtonPanel.add(addSeries);\n\n        removeSeries.setText(\"Remove\");\n        removeSeries.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        removeSeries.setMinimumSize(new java.awt.Dimension(5, 25));\n        removeSeries.setPreferredSize(new java.awt.Dimension(5, 25));\n        removeSeries.setIcon(GUIPrism.getIconFromImage(\"smallRemove.png\"));\n        removeSeries.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                removeSeriesActionPerformed(evt);\n            }\n        });\n\n        seriesButtonPanel.add(removeSeries);\n\n        moveUp.setText(\"Move Up\");\n        moveUp.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        moveUp.setMinimumSize(new java.awt.Dimension(5, 25));\n        moveUp.setPreferredSize(new java.awt.Dimension(5, 25));\n        moveUp.setIcon(GUIPrism.getIconFromImage(\"smallArrowUp.png\"));\n        moveUp.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                moveUpActionPerformed(evt);\n            }\n        });\n\n        seriesButtonPanel.add(moveUp);\n\n        moveDown.setText(\"Move Down\");\n        moveDown.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        moveDown.setMinimumSize(new java.awt.Dimension(5, 25));\n        moveDown.setPreferredSize(new java.awt.Dimension(5, 25));\n        moveDown.setIcon(GUIPrism.getIconFromImage(\"smallArrowDown.png\"));\n        moveDown.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                moveDownActionPerformed(evt);\n            }\n        });\n\n        seriesButtonPanel.add(moveDown);\n\n        viewData.setText(\"Edit Data\");\n        viewData.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        viewData.setIcon(GUIPrism.getIconFromImage(\"smallEditData.png\"));\n        viewData.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                viewDataActionPerformed(evt);\n            }\n        });\n\n        seriesButtonPanel.add(viewData);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.NORTH;\n        gridBagConstraints.weightx = 0.25;\n        gridBagConstraints.weighty = 1.0;\n        gridBagConstraints.insets = new java.awt.Insets(0, 5, 0, 0);\n        seriesListPanel.add(seriesButtonPanel, gridBagConstraints);\n\n        seriesInnerTopPanel.add(seriesListPanel, java.awt.BorderLayout.CENTER);\n\n        seriesTopPanel.add(seriesInnerTopPanel, java.awt.BorderLayout.CENTER);\n\n        seriesOptionPanelSplitPane.setLeftComponent(seriesTopPanel);\n\n        seriesBottomPanel.setLayout(new java.awt.BorderLayout());\n\n        seriesBottomPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        seriesBottomPanel.add(seriesPropertiesTable, BorderLayout.CENTER);\n        seriesOptionPanelSplitPane.setRightComponent(seriesBottomPanel);\n\n        seriesOptionsPanel.add(seriesOptionPanelSplitPane, java.awt.BorderLayout.CENTER);\n\n        tabbedPanel.addTab(\"Series\", seriesOptionsPanel);\n\n        displayOptionsPanel.setLayout(new java.awt.BorderLayout());\n\n        displayOptionsPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        innerDisplayOptionsPanel.setLayout(new java.awt.BorderLayout());\n\n        innerDisplayOptionsPanel.add(displayPropertiesTable, java.awt.BorderLayout.CENTER);\n\n        displayOptionsPanel.add(innerDisplayOptionsPanel, java.awt.BorderLayout.CENTER);\n\n        tabbedPanel.addTab(\"Display\", displayOptionsPanel);\n\n        add(tabbedPanel, java.awt.BorderLayout.CENTER);\n\n    }// </editor-fold>//GEN-END:initComponents\n\t\n    private void viewDataActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_viewDataActionPerformed\n\t\t\n    \tsynchronized (theModel.getSeriesLock())\n\t\t{\n\t\t\tint[] sel = seriesList.getSelectedIndices();\n\t\t\t\n\t\t\tjava.util.List<Graph.SeriesKey> selected = new ArrayList<Graph.SeriesKey>();\n\t\t\n\t\t\tfor (int i = 0; i < sel.length; i++)\n\t\t\t{\n\t\t\t\tselected.add(((SeriesSettings)theModel.getGraphSeriesList().getElementAt(sel[i])).getSeriesKey());\n\t\t\t}\n\t\t\t\n\t\t\tSeriesEditorDialog.makeSeriesEditor(plugin, parent, theModel, selected);\n\t\t}\n    \t\n\t\t/*ArrayList ss = seriesList.getSelectedSeries();\n\t\tif(ss.size() > 1)\n\t\t{\n\t\t\tGraphListEditor.showEditors(parent, seriesList.getEditors());\n\t\t}\n\t\telse if(seriesList.getSelectedSeries().size() == 1)\n\t\t\t((GraphList)ss.get(0)).getEditor().showEditor(parent);*/\n    \t\n    }//GEN-LAST:event_viewDataActionPerformed\n\t\n    private void tabbedPanelStateChanged(javax.swing.event.ChangeEvent evt) {//GEN-FIRST:event_tabbedPanelStateChanged\n\t\t\n\t\tstopEditors();\n    }//GEN-LAST:event_tabbedPanelStateChanged\n\t\n\tprivate void moveDownActionPerformed(java.awt.event.ActionEvent evt)                                         \n\t{\t\t\n\t\tsynchronized (theModel.getSeriesLock())\n\t\t{\n\t\t\tint[] sel = seriesList.getSelectedIndices();\n\t\t\t\n\t\t\tSeriesSettingsList listModel = theModel.getGraphSeriesList();\n\t\t\t\n\t\t\tVector<Graph.SeriesKey> toMove = new Vector<Graph.SeriesKey>();\n\t\t\t\n\t\t\tfor (int i = 0; i < sel.length; i++)\n\t\t\t{\n\t\t\t\tSeriesSettings series = (SeriesSettings)listModel.getElementAt(sel[i]);\n\t\t\t\ttoMove.add(series.getSeriesKey());\n\t\t\t}\n\t\t\t\n\t\t\ttheModel.moveDown(toMove);\n\t\t\t\n\t\t\tint[] newSel = new int[sel.length];\n\t\t\t                       \n\t\t    for (int i = 0; i < sel.length; i++)\n\t\t    {\n\t\t    \tnewSel[i] = (sel[i] < listModel.getSize() - 1) ? (sel[i] + 1) : (0);\n\t\t    }\n\t\t\t\n\t\t\tseriesList.setSelectedIndices(newSel);\n\t\t}\n\t}\n\t\n\t\n\tprivate void moveUpActionPerformed(java.awt.event.ActionEvent evt)                                       \n\t{\n\t\tsynchronized (theModel.getSeriesLock())\n\t\t{\n\t\t\tint[] sel = seriesList.getSelectedIndices();\n\t\t\t\n\t\t\tSeriesSettingsList listModel = theModel.getGraphSeriesList();\n\t\t\t\n\t\t\tVector<Graph.SeriesKey> toMove = new Vector<Graph.SeriesKey>();\n\t\t\t\n\t\t\tfor (int i = 0; i < sel.length; i++)\n\t\t\t{\n\t\t\t\tSeriesSettings series = (SeriesSettings)listModel.getElementAt(sel[i]);\n\t\t\t\ttoMove.add(series.getSeriesKey());\n\t\t\t}\n\t\t\t\n\t\t\ttheModel.moveUp(toMove);\n\t\t\t\n\t\t\tint[] newSel = new int[sel.length];\n\t\t\t                       \n\t\t    for (int i = 0; i < sel.length; i++)\n\t\t    {\n\t\t    \tnewSel[i] = (sel[i] > 1) ? (sel[i] -1) : (0);\n\t\t    }\n\t\t\t\n\t\t\tseriesList.setSelectedIndices(newSel);\t\t\t\n\t\t}\n\t}\n\t\n\tprivate void removeSeriesActionPerformed(java.awt.event.ActionEvent evt)                                             \n\t{\n\t\tsynchronized (theModel.getSeriesLock())\n\t\t{\n\t\t\tint[] sel = seriesList.getSelectedIndices();\n\t\t\t\n\t\t\tSeriesSettingsList listModel = theModel.getGraphSeriesList();\n\t\t\t\n\t\t\tVector<Graph.SeriesKey> toRemove = new Vector<Graph.SeriesKey>();\n\t\t\t\n\t\t\tfor (int i = 0; i < sel.length; i++)\n\t\t\t{\n\t\t\t\tSeriesSettings series = (SeriesSettings)listModel.getElementAt(sel[i]);\n\t\t\t\ttoRemove.add(series.getSeriesKey());\n\t\t\t}\n\t\t\t\n\t\t\tfor (Graph.SeriesKey key : toRemove)\n\t\t\t{\n\t\t\t\ttheModel.removeSeries(key);\n\t\t\t}\n\t\t\t\n\t\t\tlistModel.updateSeriesList();\n\t\t}\n\t\t\n\t\tseriesList.clearSelection();\n\t}\n\t\n\tprivate void addSeriesActionPerformed(java.awt.event.ActionEvent evt)                                          \n\t{\n\t\ttheModel.addSeries(\"New Series\");\n\t}\n\t\n\tpublic void doEnables()\n\t{\n\t\tboolean hasFirst = false;\n\t\tboolean hasLast = false;\n\t\t\n\t\tfor (int i = 0; i < seriesList.getSelectedIndices().length; i++)\n\t\t{\n\t\t\tif (seriesList.getSelectedIndices()[i] == 0)\n\t\t\t\thasFirst = true;\n\t\t\tif (seriesList.getSelectedIndices()[i] == theModel.getGraphSeriesList().getSize() - 1)\n\t\t\t\thasLast = true;\n\t\t}\n\t\t\n\t\tremoveSeries.setEnabled(seriesList.getSelectedIndices().length >= 1);\n\t\t\t\t\n\t\tmoveUp.setEnabled(!hasFirst && seriesList.getSelectedIndices().length >= 1);\n\t\tmoveDown.setEnabled(!hasLast && seriesList.getSelectedIndices().length >= 1);\n\t\t\n\t\tviewData.setEnabled(seriesList.getSelectedIndices().length >= 1);\n\t}\n\t\t\n\tpublic void valueChanged(ListSelectionEvent e)\n\t{\t\n\t\tstopEditors();\n\t\tdoEnables();\n\t\t\n\t\tif (e.getSource() == axesList)\n\t\t{\n\t\t\tint [] sel = axesList.getSelectedIndices();\n\t\t\t\n\t\t\tArrayList own = new ArrayList();\n\t\t\t\n\t\t\tfor (int i = 0; i < sel.length; i++)\n\t\t\t{\n\t\t\t\tif (sel[i] == 0)\n\t\t\t\t\town.add(xAxisSettings);\n\t\t\t\telse if (sel[i] == 1)\n\t\t\t\t\town.add(yAxisSettings);\n\t\t\t}\n\t\t\taxisPropertiesTable.setOwners(own);\n\t\t}\n\t\telse if (e.getSource() == seriesList)\n\t\t{\n\t\t\tsynchronized (theModel.getSeriesLock())\n\t\t\t{\n\t\t\t\tint[] sel = seriesList.getSelectedIndices();\n\t\t\t\t\n\t\t\t\tArrayList own = new ArrayList();\n\t\t\t\t//seriesPropertiesTable.setOwners(own);\n\t\t\t\t\n\t\t\t\tfor (int i = 0; i < sel.length; i++)\n\t\t\t\t{\n\t\t\t\t\town.add(theModel.getGraphSeriesList().getElementAt(sel[i]));\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t//seriesPropertiesTable = new SettingTable(parent);\n\t\t\t\tseriesPropertiesTable.setOwners(own);\n\t\t\t}\n\t\t}\n\t}\n\t\n\tpublic void errorDialog(String error, String title)\n\t{\n\t\tJOptionPane.showMessageDialog(parent,\n\t\terror,\n\t\ttitle, JOptionPane.ERROR_MESSAGE);\n\t}\n\t\n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JButton addSeries;\n    private javax.swing.JPanel axesBottomPanel;\n    private javax.swing.JPanel axesInnerListPanel;\n    private javax.swing.JPanel axesInnerTopPanel;\n    private javax.swing.JLabel axesLabel;\n    private javax.swing.JPanel axesListPanel;\n    private javax.swing.JScrollPane axesListScrollPane;\n    private javax.swing.JSplitPane axesOptionPanelSplitPane;\n    private javax.swing.JPanel axesTopPanel;\n    private javax.swing.JPanel axisOptionsPanel;\n    private javax.swing.JPanel displayOptionsPanel;\n    private javax.swing.JPanel graphOptionsPanel;\n    private javax.swing.JPanel innerAxesOptionsPanel;\n    private javax.swing.JPanel innerDisplayOptionsPanel;\n    private javax.swing.JPanel innerGraphOptionsPanel;\n    private javax.swing.JButton moveDown;\n    private javax.swing.JButton moveUp;\n    private javax.swing.JButton removeSeries;\n    private javax.swing.JPanel seriesBottomPanel;\n    private javax.swing.JPanel seriesButtonPanel;\n    private javax.swing.JPanel seriesInnerListPanel;\n    private javax.swing.JPanel seriesInnerTopPanel;\n    private javax.swing.JLabel seriesLabel;\n    private javax.swing.JPanel seriesListPanel;\n    private javax.swing.JScrollPane seriesListScrollPane;\n    private javax.swing.JSplitPane seriesOptionPanelSplitPane;\n    private javax.swing.JPanel seriesOptionsPanel;\n    private javax.swing.JPanel seriesTopPanel;\n    private javax.swing.JButton viewData;\n    // End of variables declaration//GEN-END:variables\n\t\n\t\n   /* public static void main(String[]args)\n\t{\n\t\tjavax.swing.JFrame f = new javax.swing.JFrame(\"Graph Options Test\");\n\t\n\t\tGraphOptionsPanel gop = new GraphOptionsPanel();\n\t\n\t\tf.getContentPane().add(gop);\n\t\n\t\tf.pack();\n\t\tf.show();\n\t\tf.setDefaultCloseOperation(javax.swing.JFrame.EXIT_ON_CLOSE);\n\t\n\t}*/\n}\n"
  },
  {
    "path": "prism/src/userinterface/graph/GraphResultListener.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport param.BigRational;\nimport parser.*;\nimport prism.*;\n\nimport org.jfree.data.xy.*;\n\n// TODO: When either the graph or the resultset seizes to exist, then so should this listener.\n\n/**\n * This class is responsible for mapping output of a ResultsCollection to the input of a GraphModel. Used to be called Displayable Data.\n */\npublic class GraphResultListener implements ResultListener\n{\n\t// A graph.\n\tprivate Graph graph;\n\t// The name of the series.\n\tprivate Graph.SeriesKey seriesKey;\t\t\n\t// The constant on the x-axis.\n\tprivate String rangeConstant;\n\t// The other constants.\n\tprivate Values otherValues;\t\n\t\t\n\t/** \n\t * Creates a new instance of GraphResultListener \n\t * It presumes that the seriesKey is returned by a call of {@link userinterface.graph.Graph#addSeries graph.addSeries(...)}. \n\t * @param graph The graph to notify when new results are found.\n\t * @param seriesKey The key of the series this listener represents.\n\t * @param rangeConstant The ranging constant (x-axis value) (required to identify the series from the results). \n\t * @param otherValues Values of all other constants of this series (required to identify the series from the results). \n\t */\n\tpublic GraphResultListener(Graph graph, Graph.SeriesKey seriesKey, String rangeConstant, Values otherValues)\n\t{\n\t\tthis.graph = graph;\n\t\tthis.seriesKey = seriesKey;\n\t\tthis.rangeConstant = rangeConstant;\n\t\tthis.otherValues = otherValues;\t\t\n\t}\t\n\t\n\t\n\tpublic void notifyResult(ResultsCollection resultsCollection, Values values, Object result)\n\t{\n\t\tObject xObj = isInSeries(values);\n\t\t\n\t\t/* This is a result of our series, xObj is our x-coordinate. */\n\t\tif(xObj != null)\n\t\t{\n\t\t\tdouble x,y;\n\t\t\t\n\t\t\t// Get x coordinate\n\t\t\tif(xObj instanceof Integer) {\t\n\t\t\t\tx = ((Integer)xObj).intValue(); // Use integer value.  \t\n\t\t\t} else if(xObj instanceof Double) {\n\t\t\t\tx = ((Double)xObj).doubleValue(); // Use double value.\n\t\t\t} else if(xObj instanceof BigRational) {\n\t\t\t\tx = ((BigRational)xObj).doubleValue(); // Use double value.\n\t\t\t} else return; // Cancel if non integer/double\t\t\t\n\t\t\t\n\t\t\t// Cancel if x = +/- infinity or NaN\n\t\t\tif (x == Double.POSITIVE_INFINITY || x == Double.NEGATIVE_INFINITY || Double.isNaN(x)) \n\t\t\t\treturn;\n\t\t\t\t\t\t\n\t\t\t// Add point to graph (if of valid type) \n\t\t\tif (result instanceof Double) {\n\t\t\t\ty = ((Double) result).doubleValue();\n\t\t\t\tgraph.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t} else if (result instanceof Integer) {\n\t\t\t\ty = ((Integer) result).intValue();\n\t\t\t\tgraph.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t} else if (result instanceof BigRational) {\n\t\t\t\ty = ((BigRational) result).doubleValue();\n\t\t\t\tgraph.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t} else if (result instanceof Interval) {\n\t\t\t\tInterval interval = (Interval) result;\n\t\t\t\tif (interval.lower instanceof Double) {\n\t\t\t\t\ty = ((Double) interval.lower).doubleValue();\n\t\t\t\t\tgraph.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t\t\ty = ((Double) interval.upper).doubleValue();\n\t\t\t\t\tgraph.addPointToSeries(seriesKey.next, new XYDataItem(x, y));\n\t\t\t\t} else if (result instanceof Integer) {\n\t\t\t\t\ty = ((Integer) interval.lower).intValue();\n\t\t\t\t\tgraph.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t\t\ty = ((Integer) interval.upper).intValue();\n\t\t\t\t\tgraph.addPointToSeries(seriesKey.next, new XYDataItem(x, y));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/**\t\n\t *  Looks at the values and sees whether it matches otherValues, apart\n\t *\tfrom one which should match 'rangeConstant'. If so this method returns\n\t *\tthe value of the rangeConstant (x-axis). If not this returns null. \n\t **/\n\tprivate Object isInSeries(Values v)\n\t{\n\t\tfor(int i = 0; i < otherValues.getNumValues(); i++)\n\t\t{\n\t\t\tString name = otherValues.getName(i);\n\t\t\tObject value = otherValues.getValue(i);\n\t\t\tif(!name.equals(rangeConstant))\n\t\t\t{\n\t\t\t\ttry\n\t\t\t\t{\n\t\t\t\t\tObject compare = v.getValueOf(name);\n\t\t\t\t\tif(compare.equals(value))\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\telse throw new PrismException(\"value not same\");\n\t\t\t\t}\n\t\t\t\tcatch(PrismException e)\n\t\t\t\t{\n\t\t\t\t\treturn null;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\ttry\n\t\t{\n\t\t\tObject value = v.getValueOf(rangeConstant);\n\t\t\treturn value;\n\t\t}\n\t\tcatch(PrismException e)\n\t\t{\n\t\t\treturn null;\n\t\t}\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/graph/PrismLogarithmicAxis.java",
    "content": "//==============================================================================\n//\t\n//\tThis file is a modification of the following JFreeChart files:\n//\t* org.jfree.chart.axis.LogarithmicAxis      (version  1.0.6)\n//\t* org.jfree.experimental.chart.axis.LogAxis (revision 1.1.2.2)\n//\t\n//\tThe notices of these files follow below.\n//\t\n//\tThe modification combines features of both implementations. Most notably, it\n//\tis possible to select a custom base value (like LogAxis), render points \n//\tsmaller than the base value more sensibly (e.g. negative powers like \n//\t10*2^(-3)), and chooses more sensible grid lines.\n//\t\n//\tThese modifications are copyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\n/* ===========================================================\n * JFreeChart : a free chart library for the Java(tm) platform\n * ===========================================================\n *\n * (C) Copyright 2000-2007, by Object Refinery Limited and Contributors.\n *\n * Project Info:  http://www.jfree.org/jfreechart/index.html\n *\n * This library is free software; you can redistribute it and/or modify it\n * under the terms of the GNU Lesser General Public License as published by\n * the Free Software Foundation; either version 2.1 of the License, or\n * (at your option) any later version.\n *\n * This library is distributed in the hope that it will be useful, but\n * WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY\n * or FITNESS FOR A PARTICULAR PURPOSE. See the GNU Lesser General Public\n * License for more details.\n *\n * You should have received a copy of the GNU Lesser General Public\n * License along with this library; if not, write to the Free Software\n * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA  02110-1301, \n * USA.  \n *\n * [Java is a trademark or registered trademark of Sun Microsystems, Inc.\n * in the United States and other countries.]\n *\n * --------------------\n * LogarithmicAxis.java\n * --------------------\n * (C) Copyright 2000-2007, by Object Refinery Limited and Contributors.\n *\n * Original Author:  Michael Duffy / Eric Thomas;\n * Contributor(s):   David Gilbert (for Object Refinery Limited);\n *                   David M. O'Donnell;\n *                   Scott Sams;\n *                   Sergei Ivanov;\n *\n * $Id: LogarithmicAxis.java,v 1.11.2.5 2007/03/22 12:13:27 mungady Exp $\n *\n * Changes\n * -------\n * 14-Mar-2002 : Version 1 contributed by Michael Duffy (DG);\n * 19-Apr-2002 : drawVerticalString() is now drawRotatedString() in\n *               RefineryUtilities (DG);\n * 23-Apr-2002 : Added a range property (DG);\n * 15-May-2002 : Modified to be able to deal with negative and zero values (via\n *               new 'adjustedLog10()' method);  occurrences of \"Math.log(10)\"\n *               changed to \"LOG10_VALUE\"; changed 'intValue()' to\n *               'longValue()' in 'refreshTicks()' to fix label-text value\n *               out-of-range problem; removed 'draw()' method; added\n *               'autoRangeMinimumSize' check; added 'log10TickLabelsFlag'\n *               parameter flag and implementation (ET);\n * 25-Jun-2002 : Removed redundant import (DG);\n * 25-Jul-2002 : Changed order of parameters in ValueAxis constructor (DG);\n * 16-Jul-2002 : Implemented support for plotting positive values arbitrarily\n *               close to zero (added 'allowNegativesFlag' flag) (ET).\n * 05-Sep-2002 : Updated constructor reflecting changes in the Axis class (DG);\n * 02-Oct-2002 : Fixed errors reported by Checkstyle (DG);\n * 08-Nov-2002 : Moved to new package com.jrefinery.chart.axis (DG);\n * 22-Nov-2002 : Bug fixes from David M. O'Donnell (DG);\n * 14-Jan-2003 : Changed autoRangeMinimumSize from Number --> double (DG);\n * 20-Jan-2003 : Removed unnecessary constructors (DG);\n * 26-Mar-2003 : Implemented Serializable (DG);\n * 08-May-2003 : Fixed plotting of datasets with lower==upper bounds when\n *               'minAutoRange' is very small; added 'strictValuesFlag'\n *               and default functionality of throwing a runtime exception\n *               if 'allowNegativesFlag' is false and any values are less\n *               than or equal to zero; added 'expTickLabelsFlag' and\n *               changed to use \"1e#\"-style tick labels by default\n *               (\"10^n\"-style tick labels still supported via 'set'\n *               method); improved generation of tick labels when range of\n *               values is small; changed to use 'NumberFormat.getInstance()'\n *               to create 'numberFormatterObj' (ET);\n * 14-May-2003 : Merged HorizontalLogarithmicAxis and\n *               VerticalLogarithmicAxis (DG);\n * 29-Oct-2003 : Added workaround for font alignment in PDF output (DG);\n * 07-Nov-2003 : Modified to use new NumberTick class (DG);\n * 08-Apr-2004 : Use numberFormatOverride if set - see patch 930139 (DG);\n * 11-Jan-2005 : Removed deprecated code in preparation for 1.0.0 release (DG);\n * 21-Apr-2005 : Added support for upper and lower margins; added\n *               get/setAutoRangeNextLogFlag() methods and changed\n *               default to 'autoRangeNextLogFlag'==false (ET);\n * 22-Apr-2005 : Removed refreshTicks() and fixed names and parameters for\n *               refreshHorizontalTicks() & refreshVerticalTicks();\n *               changed javadoc on setExpTickLabelsFlag() to specify\n *               proper default (ET);\n * 22-Apr-2005 : Renamed refreshHorizontalTicks --> refreshTicksHorizontal\n *               (and likewise the vertical version) for consistency with\n *               other axis classes (DG);\n * ------------- JFREECHART 1.0.x ---------------------------------------------\n * 02-Feb-2007 : Removed author tags all over JFreeChart sources (DG);\n * 02-Mar-2007 : Applied patch 1671069 to fix zooming (DG);\n * 22-Mar-2007 : Use new defaultAutoRange attribute (DG);\n *\n * ------------\n * LogAxis.java\n * ------------\n * (C) Copyright 2006, 2007, by Object Refinery Limited and Contributors.\n *\n * Original Author:  David Gilbert (for Object Refinery Limited);\n * Contributor(s):   -;\n *\n * $Id: LogAxis.java,v 1.1.2.2 2007/03/22 16:39:18 mungady Exp $\n *\n * Changes\n * -------\n * 24-Aug-2006 : Version 1 (DG);\n * 22-Mar-2007 : Use defaultAutoArrange attribute (DG);\n */\n\npackage userinterface.graph;\n\nimport java.awt.Graphics2D;\nimport java.awt.geom.Rectangle2D;\nimport java.text.NumberFormat;\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport org.jfree.chart.axis.AxisState;\nimport org.jfree.chart.axis.LogarithmicAxis;\nimport org.jfree.chart.axis.NumberAxis;\nimport org.jfree.chart.axis.NumberTick;\nimport org.jfree.chart.axis.NumberTickUnit;\nimport org.jfree.chart.axis.ValueAxis;\nimport org.jfree.chart.event.AxisChangeEvent;\nimport org.jfree.chart.plot.Plot;\nimport org.jfree.chart.plot.PlotRenderingInfo;\nimport org.jfree.chart.plot.ValueAxisPlot;\nimport org.jfree.data.Range;\nimport org.jfree.ui.RectangleEdge;\nimport org.jfree.ui.TextAnchor;\n\n/**\n * A numerical axis that uses a logarithmic scale.  The plan is for this class\n * to replace the {@link LogarithmicAxis} class.\n * \n * WARNING: THIS CLASS IS NOT PART OF THE STANDARD JFREECHART API AND IS \n * SUBJECT TO ALTERATION OR REMOVAL.  DO NOT RELY ON THIS CLASS FOR \n * PRODUCTION USE.  Please experiment with this code and provide feedback.\n */\n\n// TODO: support for margins that get inherited from ValueAxis\n// TODO: add auto tick unit selection\n\npublic class PrismLogarithmicAxis extends ValueAxis {\n\n    /** The logarithm base. */\n    private double base = 10.0;\n    \n    /** The logarithm of the base value - cached for performance. */\n    private double baseLog = Math.log(10.0);\n    \n    /**  The smallest value permitted on the axis. */\n    private double smallestValue = 1E-100;\n    \n    /** The current tick unit. */\n    private NumberTickUnit tickUnit;\n    \n    /** The override number format. */\n    private NumberFormat numberFormatOverride;\n    \n    /** Exponential display override, necessary as NumberFormat is always base 10. */\n    private boolean baseAndExponentFormatOverride;\n\n    /** The number of minor ticks per major tick unit. */\n    private int minorTickCount; \n    \n    /**\n     * Creates a new <code>LogAxis</code> with no label.\n     */\n    public PrismLogarithmicAxis() {\n        this(null);    \n    }\n    \n    /**\n     * Creates a new <code>LogAxis</code> with the given label.\n     * \n     * @param label  the axis label (<code>null</code> permitted).\n     */\n    public PrismLogarithmicAxis(String label) {\n        super(label, NumberAxis.createIntegerTickUnits());\n        setDefaultAutoRange(new Range(0.01, 1.0));\n        this.tickUnit = new NumberTickUnit(1.0);\n        this.minorTickCount = 10;\n        this.setTickMarksVisible(false);\n        this.baseAndExponentFormatOverride = true;\n    }\n    \n    /**\n     * Returns the base for the logarithm calculation.\n     * \n     * @return The base for the logarithm calculation.\n     */\n    public double getBase() {\n        return this.base;\n    }\n    \n    /**\n     * Sets the base for the logarithm calculation and sends an \n     * {@link AxisChangeEvent} to all registered listeners.\n     * \n     * @param base  the base value (must be > 1.0).\n     */\n    public void setBase(double base) {\n        if (base <= 1.0) {\n            throw new IllegalArgumentException(\"Requires 'base' > 1.0.\");\n        }\n        this.base = base;\n        this.baseLog = Math.log(base);\n        notifyListeners(new AxisChangeEvent(this));\n    }\n    \n       \n    public boolean isBaseAndExponentFormatOverride() \n    {\n\t\treturn baseAndExponentFormatOverride;\n\t}\n\n\tpublic void setBaseAndExponentFormatOverride(boolean baseAndExponentFormatOverride) \n\t{\n\t\tthis.baseAndExponentFormatOverride = baseAndExponentFormatOverride;\n\t}\n\n\t/**\n     * Returns the smallest value represented by the axis.\n     * \n     * @return The smallest value represented by the axis.\n     */\n    public double getSmallestValue() {\n        return this.smallestValue;\n    }\n    \n    /**\n     * Sets the smallest value represented by the axis.\n     * \n     * @param value  the value.\n     */\n    public void setSmallestValue(double value) {\n        if (value <= 0.0) {\n            throw new IllegalArgumentException(\"Requires 'value' > 0.0.\");\n        }\n        this.smallestValue = value;\n    }\n    \n    /**\n     * Returns the current tick unit.\n     * \n     * @return The current tick unit.\n     */\n    public NumberTickUnit getTickUnit() {\n        return this.tickUnit;\n    }\n    \n    /**\n     * Sets the tick unit for the axis and sends an {@link AxisChangeEvent} to \n     * all registered listeners.  A side effect of calling this method is that\n     * the \"auto-select\" feature for tick units is switched off (you can \n     * restore it using the {@link ValueAxis#setAutoTickUnitSelection(boolean)}\n     * method).\n     *\n     * @param unit  the new tick unit (<code>null</code> not permitted).\n     */\n    public void setTickUnit(NumberTickUnit unit) {\n        // defer argument checking...\n        setTickUnit(unit, true, true);\n    }\n\n    /**\n     * Sets the tick unit for the axis and, if requested, sends an \n     * {@link AxisChangeEvent} to all registered listeners.  In addition, an \n     * option is provided to turn off the \"auto-select\" feature for tick units \n     * (you can restore it using the \n     * {@link ValueAxis#setAutoTickUnitSelection(boolean)} method).\n     *\n     * @param unit  the new tick unit (<code>null</code> not permitted).\n     * @param notify  notify listeners?\n     * @param turnOffAutoSelect  turn off the auto-tick selection?\n     */\n    public void setTickUnit(NumberTickUnit unit, boolean notify, \n                            boolean turnOffAutoSelect) {\n\n        if (unit == null) {\n            throw new IllegalArgumentException(\"Null 'unit' argument.\");   \n        }\n        this.tickUnit = unit;\n        if (turnOffAutoSelect) {\n            setAutoTickUnitSelection(false, false);\n        }\n        if (notify) {\n            notifyListeners(new AxisChangeEvent(this));\n        }\n\n    }\n    \n    /**\n     * Returns the number format override.  If this is non-null, then it will \n     * be used to format the numbers on the axis.\n     *\n     * @return The number formatter (possibly <code>null</code>).\n     */\n    public NumberFormat getNumberFormatOverride() {\n        return this.numberFormatOverride;\n    }\n\n    /**\n     * Sets the number format override.  If this is non-null, then it will be \n     * used to format the numbers on the axis.\n     *\n     * @param formatter  the number formatter (<code>null</code> permitted).\n     */\n    public void setNumberFormatOverride(NumberFormat formatter) {\n        this.numberFormatOverride = formatter;\n        notifyListeners(new AxisChangeEvent(this));\n    }\n\n    /**\n     * Returns the number of minor tick marks to display.\n     * \n     * @return The number of minor tick marks to display.\n     */\n    public int getMinorTickCount() {\n        return this.minorTickCount;\n    }\n    \n    /**\n     * Sets the number of minor tick marks to display.\n     * \n     * @param count  the count.\n     */\n    public void setMinorTickCount(int count) {\n        if (count <= 0) {\n            throw new IllegalArgumentException(\"Requires 'count' > 0.\");\n        }\n        this.minorTickCount = count;\n        notifyListeners(new AxisChangeEvent(this));\n    }\n    \n    /**\n     * Calculates the log of the given value, using the current base.\n     * \n     * @param value  the value.\n     * \n     * @return The log of the given value.\n     * \n     * @see #getBase()\n     */\n    public double calculateLog(double value) {\n        return Math.log(value) / this.baseLog;  \n    }\n    \n    /**\n     * Calculates the value from a given log.\n     * \n     * @param log  the log value (must be > 0.0).\n     * \n     * @return The value with the given log.\n     */\n    public double calculateValue(double log) {\n        return Math.pow(this.base, log);\n    }\n    \n    /**\n     * Converts a Java2D coordinate to an axis value, assuming that the\n     * axis covers the specified <code>edge</code> of the <code>area</code>.\n     * \n     * @param java2DValue  the Java2D coordinate.\n     * @param area  the area.\n     * @param edge  the edge that the axis belongs to.\n     * \n     * @return A value along the axis scale.\n     */\n    public double java2DToValue(double java2DValue, Rectangle2D area, \n            RectangleEdge edge) {\n        \n        Range range = getRange();\n        double axisMin = calculateLog(range.getLowerBound());\n        double axisMax = calculateLog(range.getUpperBound());\n\n        double min = 0.0;\n        double max = 0.0;\n        if (RectangleEdge.isTopOrBottom(edge)) {\n            min = area.getX();\n            max = area.getMaxX();\n        }\n        else if (RectangleEdge.isLeftOrRight(edge)) {\n            min = area.getMaxY();\n            max = area.getY();\n        }\n        double log = 0.0;\n        if (isInverted()) {\n            log = axisMax - (java2DValue - min) / (max - min) \n                    * (axisMax - axisMin);\n        }\n        else {\n            log = axisMin + (java2DValue - min) / (max - min) \n                    * (axisMax - axisMin);\n        }\n        return calculateValue(log);\n    }\n\n    /**\n     * Converts a value on the axis scale to a Java2D coordinate relative to \n     * the given <code>area</code>, based on the axis running along the \n     * specified <code>edge</code>.\n     * \n     * @param value  the data value.\n     * @param area  the area.\n     * @param edge  the edge.\n     * \n     * @return The Java2D coordinate corresponding to <code>value</code>.\n     */\n    public double valueToJava2D(double value, Rectangle2D area, \n            RectangleEdge edge) {\n        \n        Range range = getRange();\n        double axisMin = calculateLog(range.getLowerBound());\n        double axisMax = calculateLog(range.getUpperBound());\n        value = calculateLog(value);\n        \n        double min = 0.0;\n        double max = 0.0;\n        if (RectangleEdge.isTopOrBottom(edge)) {\n            min = area.getX();\n            max = area.getMaxX();\n        }\n        else if (RectangleEdge.isLeftOrRight(edge)) {\n            max = area.getMinY();\n            min = area.getMaxY();\n        }\n        if (isInverted()) {\n            return max \n                   - ((value - axisMin) / (axisMax - axisMin)) * (max - min);\n        }\n        else {\n            return min \n                   + ((value - axisMin) / (axisMax - axisMin)) * (max - min);\n        }\n    }\n    \n    /**\n     * Configures the axis.  This method is typically called when an axis\n     * is assigned to a new plot.\n     */\n    public void configure() {\n        if (isAutoRange()) {\n            autoAdjustRange();\n        }\n    }\n\n    /**\n     * Adjusts the axis range to match the data range that the axis is\n     * required to display.\n     */\n    protected void autoAdjustRange() {\n        Plot plot = getPlot();\n        if (plot == null) {\n            return;  // no plot, no data\n        }\n\n        if (plot instanceof ValueAxisPlot) {\n            ValueAxisPlot vap = (ValueAxisPlot) plot;\n\n            Range r = vap.getDataRange(this);\n            if (r == null) {\n                r = getDefaultAutoRange();\n            }\n            \n            double upper = r.getUpperBound();\n            double lower = r.getLowerBound();\n            double range = upper - lower;\n\n            // if fixed auto range, then derive lower bound...\n            double fixedAutoRange = getFixedAutoRange();\n            if (fixedAutoRange > 0.0) {\n                lower = Math.max(upper - fixedAutoRange, this.smallestValue);\n            }\n            else {\n                // ensure the autorange is at least <minRange> in size...\n                double minRange = getAutoRangeMinimumSize();\n                if (range < minRange) {\n                    double expand = (minRange - range) / 2;\n                    upper = upper + expand;\n                    lower = lower - expand;\n                }\n               \n                // apply the margins - these should apply to the exponent range\n                //upper = upper + getUpperMargin() * range;\n                //lower = lower - getLowerMargin() * range;\n            }\n            \n            setRange(new Range(lower, upper), false, false);\n        }\n\n    }\n\n    /**\n     * Draws the axis on a Java 2D graphics device (such as the screen or a \n     * printer).\n     *\n     * @param g2  the graphics device (<code>null</code> not permitted).\n     * @param cursor  the cursor location (determines where to draw the axis).\n     * @param plotArea  the area within which the axes and plot should be drawn.\n     * @param dataArea  the area within which the data should be drawn.\n     * @param edge  the axis location (<code>null</code> not permitted).\n     * @param plotState  collects information about the plot \n     *                   (<code>null</code> permitted).\n     * \n     * @return The axis state (never <code>null</code>).\n     */\n    public AxisState draw(Graphics2D g2, double cursor, Rectangle2D plotArea, \n            Rectangle2D dataArea, RectangleEdge edge, \n            PlotRenderingInfo plotState) {\n        \n        AxisState state = null;\n        // if the axis is not visible, don't draw it...\n        if (!isVisible()) {\n            state = new AxisState(cursor);\n            // even though the axis is not visible, we need ticks for the \n            // gridlines...\n            List ticks = refreshTicks(g2, state, dataArea, edge); \n            state.setTicks(ticks);\n            return state;\n        }\n        state = drawTickMarksAndLabels(g2, cursor, plotArea, dataArea, edge);\n        state = drawLabel(getLabel(), g2, plotArea, dataArea, edge, state);\n        return state;\n    }\n\n    /**\n     * Calculates the positions of the tick labels for the axis, storing the \n     * results in the tick label list (ready for drawing).\n     *\n     * @param g2  the graphics device.\n     * @param state  the axis state.\n     * @param dataArea  the area in which the plot should be drawn.\n     * @param edge  the location of the axis.\n     * \n     * @return A list of ticks.\n     *\n     */\n    public List refreshTicks(Graphics2D g2, AxisState state, \n            Rectangle2D dataArea, RectangleEdge edge) {\n\n        List result = new java.util.ArrayList();\n        if (RectangleEdge.isTopOrBottom(edge)) {\n            result = refreshTicksHorizontal(g2, dataArea, edge);\n        }\n        else if (RectangleEdge.isLeftOrRight(edge)) {\n            result = refreshTicksVertical(g2, dataArea, edge);\n        }\n        return result;\n\n    }\n\n    /**\n     * Returns a list of ticks for an axis at the top or bottom of the chart.\n     * \n     * @param g2  the graphics device.\n     * @param dataArea  the data area.\n     * @param edge  the edge.\n     * \n     * @return A list of ticks.\n     */\n    protected List refreshTicksHorizontal(Graphics2D g2, Rectangle2D dataArea, \n            RectangleEdge edge) {\n        Range range = getRange();\n        List ticks = new ArrayList();\n        double start = Math.floor(calculateLog(getLowerBound()));\n        double end = Math.ceil(calculateLog(getUpperBound()));\n        double current = start;\n        while (current <= end) {\n\n        \tdouble v = calculateValue(current);\n            if (range.contains(v)) {\n                ticks.add(new NumberTick(Double.valueOf(v), createTickLabel(v), \n                        TextAnchor.TOP_CENTER, TextAnchor.CENTER, 0.0));\n            }\n            // add minor ticks (for gridlines)\n            double next = Math.pow(this.base, current \n                    + this.tickUnit.getSize());\n            for (int i = 1; i < this.minorTickCount; i++) {\n                double minorV = v + i * ((next - v) / this.minorTickCount);\n                if (range.contains(minorV)) {\n                    ticks.add(new NumberTick(Double.valueOf(minorV), \n                        \"\", TextAnchor.TOP_CENTER, TextAnchor.CENTER, 0.0));\n                }\n            }\n            current = current + this.tickUnit.getSize();\n        }\n        return ticks;\n    }\n    \n    /**\n     * Returns a list of ticks for an axis at the left or right of the chart.\n     * \n     * @param g2  the graphics device.\n     * @param dataArea  the data area.\n     * @param edge  the edge.\n     * \n     * @return A list of ticks.\n     */\n    protected List refreshTicksVertical(Graphics2D g2, Rectangle2D dataArea, \n            RectangleEdge edge) {\n        Range range = getRange();\n        List ticks = new ArrayList();\n        double start = Math.floor(calculateLog(getLowerBound()));\n        double end = Math.ceil(calculateLog(getUpperBound()));\n        double current = start;\n        \n        while (current <= end) {\n        \t\n        \t\n            double v = calculateValue(current);\n            if (range.contains(v)) {\n                ticks.add(new NumberTick(Double.valueOf(v), createTickLabel(v), \n                        TextAnchor.CENTER_RIGHT, TextAnchor.CENTER, 0.0));\n            }\n            // add minor ticks (for gridlines)\n            double next = Math.pow(this.base, current \n                    + this.tickUnit.getSize());\n            for (int i = 1; i < this.minorTickCount; i++) {\n                double minorV = v + i * ((next - v) / this.minorTickCount);\n                if (range.contains(minorV)) {\n                    ticks.add(new NumberTick(Double.valueOf(minorV), \"\", \n                            TextAnchor.CENTER_RIGHT, TextAnchor.CENTER, 0.0));\n                }\n            }\n            current = current + this.tickUnit.getSize();\n        }\n        return ticks;\n    }\n\n    /**\n     * Creates a tick label for the specified value.\n     * \n     * @param value  the value.\n     * \n     * @return The label.\n     */\n    private String createTickLabel(double value) {\n        if (baseAndExponentFormatOverride)\n        {\n        \tif (Math.round(base) == base)\n        \t\t// This is a precise integer value.        \t\t\n        \t\treturn \"\" + Math.round(base) + \"^\" + Math.round(calculateLog(value));\n        \telse\n        \t\t// This is a precise integer value.        \t\t\n        \t\treturn \"\" + base + \"^\" + Math.round(calculateLog(value));\n        }\n        else\n        {\n        \tif (this.numberFormatOverride != null) {\n\t    \t\treturn this.numberFormatOverride.format(value);\n\t        }\n\t        else {\n\t        \treturn this.tickUnit.valueToString(value);\n\t        }    \t\n        }\n    }\n\n}\n\n"
  },
  {
    "path": "prism/src/userinterface/graph/PrismXYSeries.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport java.util.*;\n\nimport org.jfree.data.xy.*;\nimport org.jfree.data.general.*;\n\npublic class PrismXYSeries extends XYSeries\n{\n\t/** Do not allow negative and zero values on the x axis. */\n\tprivate boolean logXAxis;\n\t\n\t/** Do not allow negative and zero values on the y axis. */\n\tprivate boolean logYAxis;\n\t\n\t/** When in logarithmic mode for either axis, we might have to discard values temporarily. */\n\tprivate XYSeries discardedItems;\n\t\n\t/**\n\t * A XYSeries that is always sorted, and in which it is allowed to add the same x value twice.\n\t * Additionally there are constructs in this class to prevent it from returning negative or zero values\n\t * when \n\t * \n\t * @param key\n\t */\n\tpublic PrismXYSeries(Comparable key) \n\t{\n\t\tsuper(key, true, false);\n\t\t\n\t\tthis.logXAxis = false;\n\t\tthis.logYAxis = false;\n\t\t\n\t\tdiscardedItems = new XYSeries(\"dummy\", true, false);\n\t}\n\t\n\t/**\n\t * Checks validity of XYDataItem. We do NOT allow positive or negative\n\t * infinity on x-axis, on the y-axis we allow them but replace them by NaN.\n\t * Validity means this is a value we should store, otherwise we can discard it.\n\t * @param item The item to check, may be changed.\n\t * @return True if valid, false otherwise.\n\t */\t\n\tprivate boolean checkValidity(XYDataItem item)\n\t{\n\t\tif (Double.isInfinite(item.getX().doubleValue()) ||\n\t\t\tDouble.isNaN(item.getX().doubleValue()))\n\t\t\treturn false;\n\t\t\t\n\t\tif (Double.isInfinite(item.getY().doubleValue()))\n\t\t\titem.setY(Double.NaN);\n\t\t\n\t\treturn true;\t\t\n\t}\n\t\n\tpublic void setLogarithmicDomainAxis(boolean logXAxis) \n\t{\n\t\tif (this.logXAxis != logXAxis)\n\t\t{\n\t\t\tthis.logXAxis = logXAxis;\n\t\t}\n\t\t\n\t\tcheckData();\n\t}\n\n\tpublic void setLogarithmicRangeAxis(boolean logYAxis) \n\t{\n\t\tif (this.logYAxis != logYAxis)\n\t\t{\n\t\t\tthis.logYAxis = logYAxis;\n\t\t}\n\t\t\n\t\tcheckData();\n\t}\n\t\n\t@Override\n\tpublic void add(double x, double y) {\n\t\tadd(Double.valueOf(x), Double.valueOf(y), true);\n\t}\n\n\t@Override\n\tpublic void add(double x, double y, boolean notify) {\n\t\tadd(Double.valueOf(x), Double.valueOf(y), notify);\n\t}\n\t\n\t@Override\n\tpublic void add(double x, Number y) {\n\t\tadd(Double.valueOf(x), y);\n\t}\n\n\t@Override\n\tpublic void add(double x, Number y, boolean notify) {\n\t\tadd(Double.valueOf(x), y, notify);\n\t}\n\n\t@Override\n\tpublic void add(Number x, Number y) {\n\t\tadd(x, y, true);\n\t}\n\t\n\t@Override\n\tpublic void add(Number x, Number y, boolean notify) {\n\t\tXYDataItem item = new XYDataItem(x, y);\n        add(item, notify);\n\t}\n\n\t@Override\n\tpublic void add(XYDataItem item) {\n\t\tadd(item, true);\n\t}\n\t\n\t/**\n\t * This method is the one that implements some different\n\t * aspects to the XYSeries class.\n\t */\n\tpublic void add(XYDataItem item, boolean notify) \n\t{\n\t\tif (checkValidity(item))\n\t\t{\t\n\t\t\tif (checkDataItem(item))\n\t\t\t{\t\n\t\t\t\t/* Check in discarded dataset. */\n\t\t\t\tif (discardedItems.indexOf(item.getX()) >= 0)\n\t\t\t\t{\t\t\t\t\t\n\t\t\t\t\tthrow new SeriesException(\"X-value already exists.\");\n\t\t\t\t}\n\t\t\t\tsuper.add(item, notify);\t\t\t\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\t/* Check in main dataset. */\n\t\t\t\tif (super.indexOf(item.getX()) >= 0)\n\t\t\t\t\tthrow new SeriesException(\"X-value already exists.\");\n\t\t\t\t\n\t\t\t\tdiscardedItems.add(item);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t *  @return A copy of the overwritten data item, or <code>null</code> if no \n     *  \t    item was overwritten.\n\t */\n\t@Override\n\tpublic XYDataItem addOrUpdate(Number x, Number y) {\n\t\t\n\t\tXYDataItem item = new XYDataItem(x,y);\n\t\tXYDataItem result = null;\n\t\t\n\t\t/** If this is a valid update. */\n\t\tif (checkValidity(item))\n\t\t{\t\t\t\n\t\t\tint indexD = discardedItems.indexOf(item.getX());\n\t\t\tint indexS = super.indexOf(item.getX());\n\t\t\t\n\t\t\t/* If in discarded items, then remove and return this. */ \n\t\t\tif (indexD >= 0)\n\t\t\t{\n\t\t\t\tresult = discardedItems.remove(indexD);\n\t\t\t}\n\t\t\t\n\t\t\t/* If in main items, then remove and return this. (Should not be both in discarded and main items) */ \n\t\t\tif (indexS >= 0)\n\t\t\t{\n\t\t\t\tresult = super.remove(indexS);\n\t\t\t}\n\t\t\t\n\t\t\tthis.add(item, true);\n\t\t\t\n\t\t\treturn null;\n\t\t}\n\t\t/* This is not a valid data item! */\n\t\telse\n\t\t{\n\t\t\treturn null;\n\t\t}\t\t\n\t}\n\n\t@Override\n\tpublic void update(int index, Number y) \n\t{\n\t\tthis.updateByIndex(index, y);\n\t}\n\n\t@Override\n\tpublic void update(Number x, Number y) \n\t{\n\t\tXYDataItem item = new XYDataItem(x,y);\n\t\tXYDataItem result = null;\n\t\t\n\t\t/** If this is a valid update. */\n\t\tif (checkValidity(item))\n\t\t{\t\t\t\n\t\t\tint indexD = discardedItems.indexOf(item.getX());\n\t\t\tint indexS = super.indexOf(item.getX());\n\t\t\t\n\t\t\t/* If in discarded items, then remove and return this. */ \n\t\t\tif (indexD >= 0)\n\t\t\t{\n\t\t\t\tresult = discardedItems.remove(indexD);\n\t\t\t}\n\t\t\t\n\t\t\t/* If in main items, then remove and return this. (Should not be both in discarded and main items) */ \n\t\t\tif (indexS >= 0)\n\t\t\t{\n\t\t\t\tresult = super.remove(indexS);\n\t\t\t}\n\t\t\t\n\t\t\tif (result != null)\n\t\t\t\tthis.add(item, true);\n\t\t\telse\n\t\t\t\tthrow new SeriesException(\"No observation for x = \" + x);\n\t\t}\t\t\t\n\t}\n\n\t@Override\n\tpublic void updateByIndex(int index, Number y) {\n\t\tXYDataItem existing = getDataItem(index);\n\t\tXYDataItem item = new XYDataItem(existing.getX(), y);\n\t\t\n\t\tif (checkValidity(item))\n\t\t{\n\t\t\tif (checkDataItem(item))\n\t\t\t\tsuper.update(index, y);\n\t\t\telse\n\t\t\t{\n\t\t\t\tsuper.remove(index);\n\t\t\t\tdiscardedItems.add(item);\n\t\t\t}\t\t\t\t\n\t\t}\n\t}\n\n\tprivate void checkData()\n\t{\n\t\tboolean changed = false;\n\t\t\n\t\t/** Check whether we can reintroduce some data we discarded earlier. */\n\t\t\n\t\tint d = 0;\n\t\t\n\t\twhile (d < discardedItems.getItemCount())\n\t\t{\n\t\t\tXYDataItem dataItem = discardedItems.getDataItem(d);\n\t\t\t\n\t\t\tif (checkDataItem(dataItem))\n\t\t\t{\n\t\t\t\t/* Should be reintroduced. */\n\t\t\t\tthis.discardedItems.remove(d);\n\t\t\t\tsuper.add(dataItem);\n\t\t\t\tchanged = true;\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\td++;\n\t\t\t}\n\t\t}\n\t\t\n\t\td = 0;\n\t\t\n\t\t/** Check whether we have to discard some data we discarded earlier. */\n\t\twhile (d < super.getItemCount())\n\t\t{\n\t\t\tXYDataItem dataItem = super.getDataItem(d);\n\t\t\t\n\t\t\tif (!checkDataItem(dataItem))\n\t\t\t{\n\t\t\t\t/* Should be discarded. */\n\t\t\t\tsuper.remove(d);\n\t\t\t\tthis.discardedItems.add(dataItem);\n\t\t\t\tchanged = true;\n\t\t\t}\t\t\t\n\t\t\telse\n\t\t\t{\n\t\t\t\td++;\n\t\t\t}\n\t\t}\n\t\t\n\t\tif (changed && super.getNotify())\n\t\t{\t\t\t\t\t\n\t\t\tfireSeriesChanged();\n\t\t}\n\t}\n\t@Override\n\tpublic XYDataItem getDataItem(int index) \n\t{\n\t\tXYDataItem item = super.getDataItem(index);\n\t\n\t\tif (this.logYAxis && item.getY().doubleValue() <= 0)\n\t\t\treturn new XYDataItem(item.getX(), Double.NaN);\n\t\telse\n\t\t\treturn item;\n\t}\n\n\t@Override\n\tpublic List getItems() \n\t{\n\t\tList items = new LinkedList();\n\t\t\n\t\tfor (int i = 0; i < getItemCount(); i++)\n\t\t{\n\t\t\tXYDataItem item = super.getDataItem(i);\n\t\t\t\n\t\t\tif (this.logYAxis && item.getY().doubleValue() <= 0)\n\t\t\t\titems.add(new XYDataItem(item.getX(), Double.NaN));\n\t\t\telse\n\t\t\t\titems.add(new XYDataItem(item.getX(), item.getY()));\n\t\t}\n\t\t\n\t\treturn items;\n\t}\n\n\t@Override\n\tpublic Number getY(int index) \n\t{\n\t\tNumber res = super.getY(index);\n\t\t\n\t\tif (this.logYAxis && res.doubleValue() <= 0)\n\t\t\treturn Double.NaN;\n\t\telse \n\t\t\treturn res;\n\t}\n\t\n\t@Override\n\tpublic XYDataItem remove(Number x) \n\t{\n\t\tXYDataItem result = null;\n\t\t\n\t\tint indexD = discardedItems.indexOf(x);\n\t\tint indexS = super.indexOf(x);\n\t\t\n\t\t/* If in discarded items, then remove and return this. */ \n\t\tif (indexD >= 0)\n\t\t{\n\t\t\tresult = discardedItems.remove(indexD);\t\t\t\n\t\t}\n\t\t\n\t\t/* If in main items, then remove and return this. (Should not be both in discarded and main items) */ \n\t\tif (indexS >= 0)\n\t\t{\n\t\t\tresult = super.remove(indexS);\t\t\t\n\t\t}\n\t\t\n\t\treturn result;\n\t}\n\n\t/** \n\t * Check whether with the current settings this data item should be in the discarded\n\t * set or in the main dataset\n\t * @param item the XYDataItem\n\t * @return true if it should be in the main set, false otherwise\n\t */\n\tprivate boolean checkDataItem(XYDataItem item)\n\t{\n\t\tif (this.logXAxis && item.getX().doubleValue() <= 0)\n\t\t\treturn false; // If logaritmic x axis and negative or zero x value, then discard for now.\n\t\tif (this.logYAxis && item.getY().doubleValue() <= 0)\n\t\t\treturn true;  // If logaritmic y axis and negative or zero y value, then do not discard, simply return NaN.\n\t\telse \n\t\t\treturn true;  // Nothing wrong\t\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/graph/SeriesEditor.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <Properties>\n    <Property name=\"defaultCloseOperation\" type=\"int\" value=\"2\"/>\n    <Property name=\"title\" type=\"java.lang.String\" value=\"Series Data Editor\"/>\n    <Property name=\"alwaysOnTop\" type=\"boolean\" value=\"true\"/>\n    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n      <Dimension value=\"[550, 350]\"/>\n    </Property>\n  </Properties>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"2\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_layoutCodeTarget\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,94,0,0,2,38\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"allPanel\">\n      <Properties>\n        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n          </Border>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"bottomPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"South\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"buttonPanel\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"East\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n                <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n              </Layout>\n              <SubComponents>\n                <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"editorPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JTabbedPane\" name=\"tabbedPane\">\n              <Properties>\n                <Property name=\"tabPlacement\" type=\"int\" value=\"3\"/>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\"/>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JToolBar\" name=\"toolBar\">\n          <Properties>\n            <Property name=\"floatable\" type=\"boolean\" value=\"false\"/>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"North\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\"/>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/graph/SeriesEditorDialog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport javax.swing.*;\n\nimport java.awt.*;\n\nimport javax.swing.table.*;\n\nimport java.util.*;\nimport java.awt.datatransfer.Clipboard;\nimport java.awt.datatransfer.DataFlavor;\nimport java.awt.datatransfer.StringSelection;\nimport java.awt.datatransfer.Transferable;\nimport java.awt.event.*;\n\nimport userinterface.*;\nimport org.jfree.data.xy.*;\nimport org.jfree.data.general.*;\n\npublic class SeriesEditorDialog extends JDialog\n{         \n\t//ATTRIBUTES    \n\tprivate Action okAction;\n\tprivate Action cancelAction;\n\tprivate GUIPrism gui;\n\tprivate java.util.List<SeriesEditor> editors;\n\t\n\tprivate boolean cancelled;\n\t\t\n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JPanel allPanel;\n    private javax.swing.JPanel bottomPanel;\n    private javax.swing.JPanel buttonPanel;\n    private javax.swing.JButton cancelButton;\n    private javax.swing.JPanel editorPanel;\n    private javax.swing.JButton okayButton;\n    private javax.swing.JTabbedPane tabbedPane;\n    private javax.swing.JToolBar toolBar;\n    // End of variables declaration//GEN-END:variables\n    \n    private GUIPlugin plugin;\n    \n    public static void makeSeriesEditor(GUIPlugin plugin, JFrame parent, Graph graph, java.util.List<Graph.SeriesKey> series)\n    {\n    \tif (graph.getXAxisSettings().isLogarithmic() || graph.getYAxisSettings().isLogarithmic())\n    \t{\n    \t\tplugin.message(\n    \t\t\t\"One of your axes has a logarithmic scale. When a logarithmic scale is active we temporarily \\n\" +\n    \t\t\t\"hide negative and zero values. For this reason it is not safe to edit values when either of \\n\" +\n    \t\t\t\"your axes is logarithmic. Please select numerical axes and switch back later.\");\n    \t\treturn;\n    \t}\n    \t\n    \tsynchronized (graph.getSeriesLock())\n    \t{\n    \t\tSeriesEditorDialog editor = new SeriesEditorDialog(plugin, parent, graph, series);\n    \t\teditor.setVisible(true);\n    \t\t\n    \t\t// DOESN'T CONTINUE UNTILL DISPOSED\n    \t}\n    }\n    \n\t/** Creates new form GUIConstantsPicker */\n\tprivate SeriesEditorDialog(GUIPlugin plugin, JFrame parent, Graph graph, java.util.List<Graph.SeriesKey> series)\n\t{\n\t\tsuper(parent, \"Graph Series Editor\", true);\n     \n\t\tthis.plugin = plugin;\n\t\tthis.editors = new ArrayList<SeriesEditor>();\n\t\t\n\t\tinitComponents();\n\t\t\n\t\tAbstractAction cut = new AbstractAction()\n\t\t{\n\t\t    public void actionPerformed(ActionEvent e)\n\t\t    {\n\t\t\t\teditors.get(tabbedPane.getSelectedIndex()).cut();\t\n\t\t    }\n\t\t};\n\t\tcut.putValue(Action.LONG_DESCRIPTION, \"Cut the current selection to the clipboard\");\n\t\t//exitAction.putValue(Action.SHORT_DESCRIPTION, \"Exit\");\n\t\tcut.putValue(Action.NAME, \"Cut\");\n\t\tcut.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallCut.png\"));\n\t\t//cut.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_X, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\t\t\n\t\tAbstractAction copy = new AbstractAction()\n\t\t{\n\t\t    public void actionPerformed(ActionEvent e)\n\t\t    {\n\t\t    \teditors.get(tabbedPane.getSelectedIndex()).copy();\t\n\t\t    }\n\t\t};\n\t\tcopy.putValue(Action.LONG_DESCRIPTION, \"Copies the current selection to the clipboard\");\n\t\t//exitAction.putValue(Action.SHORT_DESCRIPTION, \"Exit\");\n\t\tcopy.putValue(Action.NAME, \"Copy\");\n\t\tcopy.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallCopy.png\"));\n\t\t//copy.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_C, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\t\t\n\t\tAbstractAction paste = new AbstractAction()\n\t\t{\n\t\t    public void actionPerformed(ActionEvent e)\n\t\t    {\n\t\t    \teditors.get(tabbedPane.getSelectedIndex()).paste();\t\t\n\t\t    }\n\t\t};\n\t\tpaste.putValue(Action.LONG_DESCRIPTION, \"Pastes the clipboard to the current selection\");\n\t\t//exitAction.putValue(Action.SHORT_DESCRIPTION, \"Exit\");\n\t\tpaste.putValue(Action.NAME, \"Paste\");\n\t\tpaste.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPaste.png\"));\n\t\t//paste.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_V, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\t\t\n\t\tAbstractAction delete = new AbstractAction()\n\t\t{\n\t\t    public void actionPerformed(ActionEvent e)\n\t\t    {\n\t\t    \teditors.get(tabbedPane.getSelectedIndex()).delete();\t\t\t\n\t\t    }\n\t\t};\n\t\tdelete.putValue(Action.LONG_DESCRIPTION, \"Deletes the current\");\n\t\t//exitAction.putValue(Action.SHORT_DESCRIPTION, \"Exit\");\n\t\tdelete.putValue(Action.NAME, \"Delete\");\n\t\tdelete.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDelete.png\"));\n\t\t\n\t\t\n\t\tfor (Graph.SeriesKey key : series)\n\t\t{\n\t\t\tSeriesSettings settings = graph.getGraphSeries(key);\n\t\t\tPrismXYSeries xySeries = (PrismXYSeries)graph.getXYSeries(key);\n\t\t\t\n\t\t\tSeriesEditor editor = new SeriesEditor(graph, xySeries, settings, cut, copy, paste, delete);\n\t\t\teditor.setBorder(BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\t\t\n\t\t\ttabbedPane.addTab(settings.getSeriesHeading(), editor);\n\t\t\teditors.add(editor);\n\t\t}\t\t\n\t\t\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\t\t\n\t\t\t\t\n\t\ttoolBar.add(cut);\n\t\ttoolBar.add(copy);\n\t\ttoolBar.add(paste);\n\t\ttoolBar.add(delete);\n\t\t\n\t\t\n\t\tthis.add(toolBar, BorderLayout.NORTH);\n\t\t\n\t\tthis.cancelled = false;\t\t\t\t\t\n\t\t\n\t\tsuper.setBounds(new Rectangle(550, 300));\n\t\tsetResizable(true);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t}\n    \n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n    // <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n    private void initComponents() {\n        allPanel = new javax.swing.JPanel();\n        bottomPanel = new javax.swing.JPanel();\n        buttonPanel = new javax.swing.JPanel();\n        okayButton = new javax.swing.JButton();\n        cancelButton = new javax.swing.JButton();\n        editorPanel = new javax.swing.JPanel();\n        tabbedPane = new javax.swing.JTabbedPane();\n        toolBar = new javax.swing.JToolBar();\n\n        setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);\n        setTitle(\"Series Data Editor\");\n        setAlwaysOnTop(true);\n        setMinimumSize(new java.awt.Dimension(550, 350));\n        addWindowListener(new java.awt.event.WindowAdapter() {\n            public void windowClosing(java.awt.event.WindowEvent evt) {\n                closeDialog(evt);\n            }\n        });\n\n        allPanel.setLayout(new java.awt.BorderLayout());\n\n        allPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n        bottomPanel.setLayout(new java.awt.BorderLayout());\n\n        buttonPanel.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n        okayButton.setText(\"Okay\");\n        okayButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                okayButtonActionPerformed(evt);\n            }\n        });\n\n        buttonPanel.add(okayButton);\n\n        cancelButton.setText(\"Cancel\");\n        cancelButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                cancelButtonActionPerformed(evt);\n            }\n        });\n\n        buttonPanel.add(cancelButton);\n\n        bottomPanel.add(buttonPanel, java.awt.BorderLayout.EAST);\n\n        allPanel.add(bottomPanel, java.awt.BorderLayout.SOUTH);\n\n        editorPanel.setLayout(new java.awt.BorderLayout());\n\n        tabbedPane.setTabPlacement(javax.swing.JTabbedPane.BOTTOM);\n        editorPanel.add(tabbedPane, java.awt.BorderLayout.CENTER);\n\n        allPanel.add(editorPanel, java.awt.BorderLayout.CENTER);\n\n        toolBar.setFloatable(false);\n        allPanel.add(toolBar, java.awt.BorderLayout.NORTH);\n\n        getContentPane().add(allPanel, java.awt.BorderLayout.CENTER);\n\n    }// </editor-fold>//GEN-END:initComponents\n\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\t\tdispose();\n\t}//GEN-LAST:event_okayButtonActionPerformed\n        \n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\t\t\n\t\tdispose();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n        \n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\t\t\n\tpublic boolean isCancelled() \n\t{\n\t\treturn cancelled;\n\t}\n\t\n\t/** \n\t * This class represents the data of a single series. Multiple of these classes are combined\n\t * in one SeriesEditorDialog.\n\t */\t\n\tprivate class SeriesEditor extends JPanel  implements ActionListener\n\t{\n\t\tprivate int bufferSize = 30;\n\t\tprivate java.util.List<Double> xAxisBuffer;\n\t\tprivate java.util.List<Double> yAxisBuffer;\n\t\t\n\t\tprivate Graph graph;\n\t\tprivate SeriesSettings settings;\n\t\tprivate PrismXYSeries xySeries;\n\t\t\n\t\tprivate AbstractTableModel tableModel;\n\t\tprivate JTable table;\n\t\t\n\t\tprivate SeriesEditor(Graph graph, PrismXYSeries xySeries, SeriesSettings settings, Action cut, Action copy, Action paste, Action delete)\n\t\t{\n\t\t\tsuper.setLayout(new BorderLayout());\n\t\t\t\n\t\t\tthis.graph = graph;\n\t\t\tthis.settings = settings;\n\t\t\tthis.xySeries = xySeries;\n\t\t\t\n\t\t\tthis.xAxisBuffer = new ArrayList<Double>(bufferSize);\n\t\t\tthis.yAxisBuffer = new ArrayList<Double>(bufferSize);\n\t\t\t\n\t\t\tfor (int b = 0; b < bufferSize; b++)\n\t\t\t{\n\t\t\t\txAxisBuffer.add(null);\n\t\t\t\tyAxisBuffer.add(null);\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\tthis.xySeries.addChangeListener(new SeriesChangeListener() \n\t\t\t{\n\t\t\t\tpublic void seriesChanged(SeriesChangeEvent event) \n\t\t\t\t{\n\t\t\t\t\tSeriesEditor.this.tableModel.fireTableStructureChanged();\n\t\t\t\t}\t\t\t\t\n\t\t\t});\n\t\t\t\n\t\t\tthis.tableModel = new AbstractTableModel()\n\t\t\t{\n\t\t\t\tpublic int getColumnCount() { return 2; }\n\t\t\t\tpublic int getRowCount() { return SeriesEditor.this.xySeries.getItemCount() + bufferSize; }\n\t\t\t\tpublic boolean isCellEditable(int rowIndex, int columnIndex) { return true; }\n\t\t\t\t\n\t\t\t\tpublic Object getValueAt(int rowIndex, int columnIndex) \n\t\t\t\t{\n\t\t\t\t\tif (rowIndex >= SeriesEditor.this.xySeries.getItemCount())\n\t\t\t\t\t{\n\t\t\t\t\t\tint bufferIndex = rowIndex - SeriesEditor.this.xySeries.getItemCount();\n\t\t\t\t\t\t\n\t\t\t\t\t\tDouble bufferValue = (columnIndex == 0) ? xAxisBuffer.get(bufferIndex) : yAxisBuffer.get(bufferIndex);\n\t\t\t\t\t\t\n\t\t\t\t\t\treturn (bufferValue == null) ? \"\" : bufferValue;\n\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\tXYDataItem dataItem = SeriesEditor.this.xySeries.getDataItem(rowIndex);\n\t\t\t\t\t\n\t\t\t\t\tif (columnIndex == 0)\n\t\t\t\t\t\treturn dataItem.getX();\n\t\t\t\t\telse\n\t\t\t\t\t\treturn dataItem.getY();\n\t\t\t\t}\t\t\t\n\t\t\t\t\n\t\t\t\tpublic String getColumnName(int column) \n\t\t\t\t{\n\t\t\t\t\tif (column == 0)\n\t\t\t\t\t\treturn SeriesEditor.this.graph.getXAxisSettings().getHeading();\n\t\t\t\t\telse\n\t\t\t\t\t\treturn SeriesEditor.this.graph.getYAxisSettings().getHeading();\n\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tpublic void setValueAt(Object aValue, int rowIndex, int columnIndex) \n\t\t\t\t{\n\t\t\t\t\tDouble value = Double.NaN;\n\t\t\t\t\t\n\t\t\t\t\ttry\n\t\t\t\t\t{\n\t\t\t\t\t\tvalue = Double.parseDouble(aValue.toString());\n\t\t\t\t\t}\n\t\t\t\t\tcatch (NumberFormatException e) \n\t\t\t\t\t{\n\t\t\t\t\t\t// Remains NaN\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tif (aValue.toString().trim().equals(\"\"))\n\t\t\t\t\t\tvalue = null;\n\t\t\t\t\t\n\t\t\t\t\t/* If not in current graph. */\n\t\t\t\t\tif (rowIndex >= SeriesEditor.this.xySeries.getItemCount())\n\t\t\t\t\t{\n\t\t\t\t\t\tint bufferIndex = rowIndex - SeriesEditor.this.xySeries.getItemCount();\n\t\t\t\t\t\t\n\t\t\t\t\t\t// Set buffer\n\t\t\t\t\t\tif (columnIndex == 0)\n\t\t\t\t\t\t\txAxisBuffer.set(bufferIndex, value);\n\t\t\t\t\t\telse\n\t\t\t\t\t\t\tyAxisBuffer.set(bufferIndex, value);\n\t\t\t\t\t\t\n\t\t\t\t\t\tDouble otherBufferValue = (columnIndex == 0) ? yAxisBuffer.get(bufferIndex) : xAxisBuffer.get(bufferIndex);\n\t\t\t\t\t\t\n\t\t\t\t\t\t/* If row is filled in, then lets go! */\n\t\t\t\t\t\tif (value != null && otherBufferValue != null)\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tif (columnIndex == 0 && Double.isNaN(value) || columnIndex == 1 && otherBufferValue.isNaN())\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t// Cannot add yet! \n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tclearBufferRow(bufferIndex);\n\t\t\t\t\t\t\t\t\n\t\t\t\t\t\t\t\tif (columnIndex == 0)\n\t\t\t\t\t\t\t\t\tSeriesEditor.this.xySeries.addOrUpdate(Double.valueOf(value), otherBufferValue);\n\t\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\t\tSeriesEditor.this.xySeries.addOrUpdate(otherBufferValue, Double.valueOf(value));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// Updating graph points...\n\t\t\t\t\telse\n\t\t\t\t\t{\t\t\t\t\n\t\t\t\t\t\tXYDataItem dataItem = SeriesEditor.this.xySeries.getDataItem(rowIndex);\n\t\t\t\t\t\t\n\t\t\t\t\t\t// Null values are for in the buffer only. \n\t\t\t\t\t\tif (value == null)\n\t\t\t\t\t\t\tvalue = Double.NaN;\n\t\t\t\t\t\t\n\t\t\t\t\t\t// Updating point on x-axis\n\t\t\t\t\t\tif (columnIndex == 0)\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tif (Double.isNaN(value))\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tObject[] options = {\"Yes\", \"No\"};\n\t\t\t\t\t\t\t\tif (SeriesEditorDialog.this.plugin.question(\n\t\t\t\t\t\t\t\t\t\t\"Invalid value\", \"You have entered an invalid value on the x-axis. This \\n\" +\n\t\t\t\t\t\t\t\t\t\t\"will result in deleting the datapoint. Do you want to continue?\", options, 1) == 1)\n\t\t\t\t\t\t\t\t\treturn;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\n\t\t\t\t\t\t\tDouble yValue = SeriesEditor.this.xySeries.getY(rowIndex).doubleValue();\n\t\t\t\t\t\t\tSeriesEditor.this.xySeries.remove(rowIndex);\n\t\t\t\t\t\t\tSeriesEditor.this.xySeries.addOrUpdate(Double.valueOf(value), yValue);\t\t\t\t\t\t\t\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\t\telse\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\t//\tUpdating point on y-axis\n\t\t\t\t\t\t\tSeriesEditor.this.xySeries.updateByIndex(rowIndex, value);\t\t\t\t\t\t\n\t\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\t\t//super.setValueAt(aValue, rowIndex, columnIndex);\n\t\t\t\t\t}\n\t\t\t\t\t\t\n\t\t\t\t\tfireTableStructureChanged();\n\t\t\t\t}\n\t\t\t};\n\t\t\t\n\t\t\tthis.table = new JTable(tableModel);\t\t\t\n\t\t\t\n\t\t\t//Next 3 lines thanks to\n\t\t\t//http://forum.java.sun.com/thread.jsp?thread=529548&forum=57&message=2546795\n\t\t\t//This is to disable to automatic Ctrl-C put onto JTables, as it does\n\t\t\t//not provide the correct functionality.\n\t\t\tInputMap im =  this.table.getInputMap();\n\t\t\tActionMap am = this.table.getActionMap();\n\t\t\t\n\t\t\tim.put(KeyStroke.getKeyStroke(KeyEvent.VK_X, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"cut\");\n\t\t\tim.put(KeyStroke.getKeyStroke(KeyEvent.VK_C, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"copy\");\n\t\t\tim.put(KeyStroke.getKeyStroke(KeyEvent.VK_V, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"paste\");\n\t\t\tim.put(KeyStroke.getKeyStroke(KeyEvent.VK_DELETE, 0), \"delete\");\n\t\t\t\n\t\t\tam.put(\"cut\", cut);\n\t\t\tam.put(\"copy\", copy);\n\t\t\tam.put(\"paste\", paste);\n\t\t\tam.put(\"delete\", delete);\t\t\t\n\t\t\t\n\t\t\tthis.table.getSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_INTERVAL_SELECTION);\n\t\t\tthis.table.setRowSelectionAllowed(true);\n\t\t\t//this.table.setColumnSelectionAllowed(true);\n\t\t\t\n\t\t\tJScrollPane scroll = new JScrollPane();\n\t\t\tscroll.setViewportView(table);\n\t\t\t\n\t\t\tadd(scroll, BorderLayout.CENTER);\t\n\t\t}\n\t\t\n\t\tpublic void addBufferRow()\n\t\t{\t\n\t\t\txAxisBuffer.add(null);\n\t\t\tyAxisBuffer.add(null);\n\t\t\t\n\t\t\tbufferSize++;\n\t\t\t\n\t\t\ttableModel.fireTableStructureChanged();\n\t\t}\n\t\t\n\t\tpublic boolean isBufferRow(int rowIndex)\n\t\t{\t\n\t\t\treturn (rowIndex >= xySeries.getItemCount());\n\t\t}\n\t\t\n\t\tpublic boolean isClearBufferRow(int rowIndex)\n\t\t{\t\n\t\t\tint bufferRowIndex = rowIndex - xySeries.getItemCount();\n\t\t\treturn isBufferRow(rowIndex) &&  xAxisBuffer.get(bufferRowIndex) == null && yAxisBuffer.get(bufferRowIndex) == null;\n\t\t}\n\t\t\n\t\tpublic void clearBufferRow(int rowIndex)\n\t\t{\t\n\t\t\txAxisBuffer.set(rowIndex, null);\n\t\t\tyAxisBuffer.set(rowIndex, null);\n\t\t\t\n\t\t\ttableModel.fireTableStructureChanged();\n\t\t}\n\t\t\n\t\t/**\n\t\t * Returns row index in terms of table.\n\t\t */\n\t\tpublic int firstClearBufferIndex()\n\t\t{\n\t\t\tfor (int b = 0; b < bufferSize; b++)\n\t\t\t{\n\t\t\t\tif (isClearBufferRow(b + xySeries.getItemCount()))\n\t\t\t\t\treturn b + xySeries.getItemCount();\n\t\t\t}\n\t\t\t\n\t\t\t/* No clear buffer rows, lets add new row. */\n\t\t\taddBufferRow();\n\t\t\treturn bufferSize + xySeries.getItemCount() - 1;\t\t\t\n\t\t}\n\t\t\n\t\tpublic void cut()\n\t\t{\n\t\t\tcopy();\n\t\t\tdelete();\n\t\t}\n\t\t\n\t\tpublic void copy()\n\t\t{\n\t\t\tint[] rows = table.getSelectedRows();\n\t\t\t\n\t\t\tStringBuffer clippy = new StringBuffer();\n\t\t    for(int i = 0; i < rows.length ; i++)\n\t\t    {\n\t\t    \tint row = rows[i];\n\t\t    \t\n\t\t    \tif (row < xySeries.getItemCount())\n\t\t    \t{\n\t\t    \t\tXYDataItem item = xySeries.getDataItem(row);\n\t\t    \t\tclippy.append(item.getX()+\"\\t\"+item.getY()+\"\\n\");\n\t\t    \t}\n\t\t    \telse\n\t\t    \t{\n\t\t    \t\tint bufferRow = row - xySeries.getItemCount();\n\t\t    \t\t\n\t\t    \t\tString x = (xAxisBuffer.get(bufferRow) == null) ? \"\" : xAxisBuffer.get(bufferRow).toString();\n\t\t    \t\tString y = (yAxisBuffer.get(bufferRow) == null) ? \"\" : yAxisBuffer.get(bufferRow).toString();\n\t\t    \t\t\n\t\t    \t\tclippy.append(x + \"\\t\" + y + \"\\n\");\n\t\t    \t}\n\t\t    }\n\t\t\t\n\t\t    Clipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();\n\t\t    StringSelection gs = new StringSelection(clippy.toString());\n\t\t    clipboard.setContents(gs, null);\n\t\t}\n\t\t\n\t\tpublic void paste()\n\t\t{\n\t\t\tClipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();\n\t\t\tTransferable contents = clipboard.getContents(null);\n\t\t\t\n\t\t\tint[] sel = table.getSelectedRows();\n\t\t\t\n\t\t\tint row = -1; \n\t\t\t\n\t\t\t/* If first selected is a buffer row, then paste from there onwards. */\n\t\t\tif (sel.length > 0 && isBufferRow(sel[0]))\n\t\t\t\trow = sel[0];\n\t\t\t\n\t\t\ttry\n\t\t\t{\n\t\t\t    if(contents.isDataFlavorSupported(DataFlavor.stringFlavor))\n\t\t\t    {\n\t\t\t\t\tString str = (String) contents.getTransferData(DataFlavor.stringFlavor);\t\t\t\t\t\n\t\t\t\t\tStringTokenizer rows = new StringTokenizer(str, \"\\n\");\n\t\t\t\t\t\t\t\t\t\t\n\t\t\t\t\twhile(rows.hasMoreTokens())\n\t\t\t\t\t{\n\t\t\t\t\t\tString rowStr = rows.nextToken();\n\t\t\t\t\t\tint tabIndex = rowStr.indexOf(\"\\t\");\n\t\t\t\t\t\t\n\t\t\t\t\t\tif (tabIndex != -1)\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tString xValue = rowStr.substring(0, tabIndex).trim();\n\t\t\t\t\t\t\tString yValue = rowStr.substring(tabIndex, rowStr.length()).trim();\n\t\t\t\t\t    \t\n\t\t\t\t\t\t\tint bufferRow = (row == -1) ? firstClearBufferIndex() : row;\n\t\t\t\t\t    \t\n\t\t\t\t\t    \ttableModel.setValueAt(\"\", bufferRow, 0);\n\t\t\t\t\t    \ttableModel.setValueAt(\"\", bufferRow, 1);\n\t\t\t\t\t    \t\t\t\t\t\t    \t\n\t\t\t\t\t\t    tableModel.setValueAt(xValue, bufferRow, 0);\t\t\t\t\t\t    \n\t\t\t\t\t\t    tableModel.setValueAt(yValue, bufferRow, 1);\n\t\t\t\t\t\t    \n\t\t\t\t\t\t    if (row != -1)\n\t\t\t\t\t\t    {\n\t\t\t\t\t\t    \trow++;\n\t\t\t\t\t\t    \tif (row >= tableModel.getRowCount())\n\t\t\t\t\t\t    \t\taddBufferRow();\n\t\t\t\t\t\t    }\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t    }\n\t\t\t}\n\t\t\tcatch(Exception e)\n\t\t\t{\n\t\t\t    \n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic void delete()\n\t\t{\n\t\t\tint[] selectedRows = table.getSelectedRows();\n\t\t\t\n\t\t\tfor (int row = selectedRows.length -1; row >= 0; row--)\n\t\t\t{\n\t\t\t\tint rowIndex = selectedRows[row];\n\t\t\t\t\n\t\t\t\tif (rowIndex >= xySeries.getItemCount())\n\t\t\t\t{\n\t\t\t\t\tclearBufferRow(rowIndex - xySeries.getItemCount());\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\txySeries.remove(rowIndex);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tpublic SeriesSettings getSettings() \n\t\t{\n\t\t\treturn settings;\n\t\t}\n\n\t\tpublic void setSettings(SeriesSettings settings) \n\t\t{\n\t\t\tthis.settings = settings;\n\t\t}\n\n\t\tpublic PrismXYSeries getXySeries() \n\t\t{\n\t\t\treturn xySeries;\n\t\t}\n\n\t\tpublic void setXySeries(PrismXYSeries xySeries) \n\t\t{\n\t\t\tthis.xySeries = xySeries;\n\t\t}\n\n\t\tpublic void actionPerformed(ActionEvent e) \n\t\t{\n\t\t\tSystem.out.println(e);\t\t\t\n\t\t\tif (e.getActionCommand().equals(\"cut\"))\n\t\t\t\tcut();\n\t\t\telse if (e.getActionCommand().equals(\"copy\"))\n\t\t\t\tcopy();\n\t\t\telse if (e.getActionCommand().equals(\"paste\"))\n\t\t\t\tpaste();\n\t\t\telse if (e.getActionCommand().equals(\"delete\"))\n\t\t\t\tdelete();\n\t\t}\n\t}\n}\n\n\n"
  },
  {
    "path": "prism/src/userinterface/graph/SeriesSettings.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t* Alistair John Strachan <alistair@devzero.co.uk> (University of Edinburgh)\n//\t* Mike Arthur <mike@mikearthur.co.uk> (University of Edinburgh)\n//\t* Zak Cohen <zakcohen@gmail.com> (University of Edinburgh)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport java.util.*;\n\nimport java.awt.*;\nimport java.awt.geom.*;\n\nimport javax.swing.*;\nimport org.jfree.chart.*;\nimport org.jfree.chart.plot.*;\nimport org.jfree.chart.renderer.xy.*;\nimport org.jfree.util.*;\nimport org.w3c.dom.Element;\n\nimport settings.*;\n\n/** \n * A class representing a series of a Graph. This class should not be used to\n * modify data, use Graph for this. The intention is that this class\n * represents all properties (colour, lines, heading, etc.) other than data.\n */\npublic class SeriesSettings extends Observable implements SettingOwner\n{\t\n\t/** shape index constants */    \n    public static final int CIRCLE \t\t= 0;\n    public static final int SQUARE \t\t= 1;\n    public static final int TRIANGLE \t= 2;\n    public static final int RECTANGLE_H = 3;\n    public static final int RECTANGLE_V = 4;\n    public static final int NONE \t\t= 5;\n\t\n    public static final int SOLID       = 0;\n    public static final int DASHED \t\t= 1;\n    public static final int DOT_DASHED \t= 2;\n    \n    public static final int BLUE \t\t= 0;\n    public static final int GREEN \t\t= 1;\n    public static final int RED\t     \t= 2;\n    public static final int CYAN        = 3;\n    public static final int PURPLE      = 4;\n    public static final int YELLOW \t\t= 5;\n    public static final int BROWN \t\t= 5;\n    \n    public static final Shape[] DEFAULT_SHAPE_SEQUENCE = {\n    \tDefaultDrawingSupplier.DEFAULT_SHAPE_SEQUENCE[1], // CIRCLE\n    \tDefaultDrawingSupplier.DEFAULT_SHAPE_SEQUENCE[0], // SQUARE\n    \tDefaultDrawingSupplier.DEFAULT_SHAPE_SEQUENCE[2], // TRIANGLE\n    \tDefaultDrawingSupplier.DEFAULT_SHAPE_SEQUENCE[4], // RECTANGLE_H\n    \tDefaultDrawingSupplier.DEFAULT_SHAPE_SEQUENCE[8], // RECTANGLE_V\n    };\n    \n\t// Use slightly smaller point shapes than the JFreeChart standards\n\tprotected static int triPointsX[] = {-2,2,0};\n\tprotected static int triPointsY[] = {-2,-2,2};\n\t\n\t/* List of all shapes, including empty shape */\n\tprotected static final Shape[] SHAPES = {\n    \tnew Ellipse2D.Double(-2,-2,4,4),\n    \tnew Rectangle2D.Double(-2,-2,4,4),\n    \tnew Polygon(triPointsX, triPointsY, 3),\n    \tnew Rectangle2D.Double(-2,-1,4,2),\n    \tnew Rectangle2D.Double(-1,-2,2,4),\n    \tnew Rectangle2D.Double(0,0,0,0) // NONE    \t\n    };\t\n\t\n\tprotected static final Shape[] DEFAULT_SHAPES = {\n\t\tSHAPES[CIRCLE],\n\t\tSHAPES[SQUARE],\n\t\tSHAPES[TRIANGLE],\n\t\tSHAPES[RECTANGLE_H],\n\t\tSHAPES[RECTANGLE_V] \t\n    };   \n    \n    protected static final Paint[] DEFAULT_PAINTS = {\n    \t    Color.blue,\n    \t    new Color(0, 127, 0),\n    \t    Color.red,\n    \t    new Color(0, 191, 191),\n    \t    new Color(191, 0, 191),\n    \t    new Color(191, 191, 0),\n    \t    new Color(0.6f, 0.2f, 0f)\n    };\n    \n\t/** Graph object. */\n\tprivate Graph graph;\n\t\n\t/** JFreeChart representation of graphs. */\n\tprivate JFreeChart chart;\n\t\n\t/** XYPlot of this JFreeChart */\n\tprivate XYPlot plot;\n\t\n\t/** Key of this series. */\n\tprivate Graph.SeriesKey key;\n\t\n\t/** The XYItemRenderer for this series. */\n\tprivate XYLineAndShapeRenderer renderer;\n\t\n\t/** Settings of a series. */\n\tprivate SingleLineStringSetting seriesHeading;\n    private ColorSetting seriesColour;\n    private BooleanSetting showPoints;\n    private ChoiceSetting seriesShape;\n    private BooleanSetting showLines;\n    private DoubleSetting lineWidth;\n    private ChoiceSetting lineStyle;\n  //  private SeriesDataSetting dataProp;    \n   \n    /** Display for settings. */\n    private SettingDisplay display;\n    \n    private GraphSeriesIcon icon;\n\t\n\tpublic SeriesSettings(Graph graph, Graph.SeriesKey key)\n\t{\n\t\tthis.graph = graph;\n\t\tthis.key = key;\n\t\tthis.chart = graph.getChart();\n\t\tthis.plot = chart.getXYPlot();\n\t\t\t\n\t\t/* This should really be checked first. */\n\t\tthis.renderer = (XYLineAndShapeRenderer) plot.getRenderer();\n\t\t\n\t\tseriesHeading = new SingleLineStringSetting(\"heading\", \"heading\", \"The heading for this series, as displayed in the legend.\", this, true);\n        seriesColour = new ColorSetting(\"colour\", Color.black, \"The colour for all lines and points in this series.\", this, true);\n        showPoints = new BooleanSetting(\"show points\", Boolean.valueOf(true), \"Should points be displayed for this series?\", this, true);\n        String[] choices = { \"Circle\", \"Square\", \"Triangle\", \"Horizontal Rectangle\", \"Vertical Rectangle\", \"None\" };\n        seriesShape = new ChoiceSetting(\"point shape\", choices, choices[0], \"The shape of points for this series.\", this, true);\n        showLines = new BooleanSetting(\"show lines\", Boolean.valueOf(true), \"Should lines be displayed for this series?\", this, true);\n        lineWidth = new DoubleSetting(\"line width\",  Double.valueOf(1.0), \"The line width for this series.\", this, true, new RangeConstraint(\"0.0,\"));\n        String [] styles = { \"---------\", \"- - - - -\", \"- -- - --\" };\n        lineStyle = new ChoiceSetting(\"line style\", styles, styles[0], \"The line style for this series.\", this, true);\n        \n        /** JFreeChart is smart enough to choose sensible values for colours, shapes etc. Lets try to use these if we can. */\n        synchronized (graph.getSeriesLock())\n\t\t{\t\t\t\n\t\t\tint seriesIndex = graph.getJFreeChartIndex(key);\n\t\t\t\n\t\t\tif (seriesIndex >= 0)\n\t\t\t{\t\t\n\t\t\t\t/* Set series colour. */\n\t\t\t\tif (renderer.lookupSeriesPaint(seriesIndex) instanceof Color)\n\t\t\t\t{\n\t\t\t\t\ttry\n\t\t\t\t\t{ \n\t\t\t\t\t\tseriesColour.setValue((Color)renderer.getSeriesPaint(seriesIndex)); \n\t\t\t\t\t}\n\t\t\t\t\tcatch (SettingException e)\n\t\t\t\t\t{}\t\t\t\t\t\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t/* Set series heading. */\n\t\t\t\ttry\n\t\t\t\t{ \n\t\t\t\t\tseriesHeading.setValue(graph.getXYSeries(key).getKey());\n\t\t\t\t}\n\t\t\t\tcatch (SettingException e)\n\t\t\t\t{\t\t\t\t\t\n\t\t\t\t}\t\n\t\t\t\t\n\t\t\t\t/* Set showPoints. */\n\t\t\t\ttry\n\t\t\t\t{ \n\t\t\t\t\t// just do it.\n\t\t\t\t\tBoolean pointsVisibleFlag = true;\n\t\t\t\t\tshowPoints.setValue(Boolean.valueOf(pointsVisibleFlag == null || pointsVisibleFlag.booleanValue())); \n\t\t\t\t}\n\t\t\t\tcatch (SettingException e)\n\t\t\t\t{\t\t\t\t\t\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t/* Set seriesShape. */\t\t\t\t\n\t\t\t\tShape shape = renderer.lookupSeriesShape(seriesIndex);\n\t\t\t\t\n\t\t\t\ttry\n\t\t\t\t{\n\t\t\t\t\tboolean foundShape = false;\n\t\t\t\t\t\n\t\t\t\t\tfor (int i = CIRCLE; i < NONE; i++)\n\t\t\t\t\t{\n\t\t\t\t\t\tif (ShapeUtilities.equal(shape, SHAPES[i]))\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tseriesShape.setSelectedIndex(i);\n\t\t\t\t\t\t\tfoundShape = true;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t\n\t\t\t\t\tif (!foundShape)\n\t\t\t\t\t\tseriesShape.setSelectedIndex(NONE);\n\t\t\t\t}\n\t\t\t\tcatch (SettingException e)\n\t\t\t\t{\t\t\n\t\t\t\t\te.printStackTrace();\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t/* Set showLines. */\n\t\t\t\ttry\n\t\t\t\t{ \n\t\t\t\t\tBoolean linesVisibleFlag = true;\n\t\t\t\t\tshowLines.setValue(Boolean.valueOf(linesVisibleFlag == null || linesVisibleFlag.booleanValue())); \n\t\t\t\t}\n\t\t\t\tcatch (SettingException e)\n\t\t\t\t{\t\t\t\t\t\n\t\t\t\t}\n\t\t\t}\t\t\t\n\t\t}\n        \n        updateSeries();\n   \t}\n\t\n\tpublic SettingDisplay getDisplay() \n\t{\n\t\treturn display;\n\t}\n\n\tpublic int getNumSettings() \n\t{\n\t\treturn 7;\n\t}\n\n\tpublic Setting getSetting(int index) \n\t{\n\t\tswitch(index)\n\t\t{\n\t\t\tcase 0: return seriesHeading;\n\t        case 1: return seriesColour;\n\t        case 2: return showPoints;\n\t        case 3: return seriesShape;\n\t        case 4: return showLines;\n\t        case 5: return lineWidth;\n\t        case 6: return lineStyle;\n\t        default: return null;\t\t\n\t\t}\n\t}\n\n\tpublic String getSettingOwnerClassName() {\n\t\treturn \"Series\";\t\t\n\t}\n\n\tpublic int getSettingOwnerID() {\n\t\treturn prism.PropertyConstants.GRAPH_DISPLAY;\n\t}\n\n\tpublic String getSettingOwnerName() {\n\t\treturn seriesHeading.getStringValue();\n\t}\n\n\tpublic void notifySettingChanged(Setting setting) {\n\t\tupdateSeries();\n\t\tsetChanged();\t\t\n\t\tnotifyObservers(this);\t\n\t}\n\n\tpublic void setDisplay(SettingDisplay display) \n\t{\n\t\tthis.display = display;\n\t}\n\n\tpublic int compareTo(Object o)\n\t{\n\t\tif(o instanceof SettingOwner)\n\t\t{\n\t\t\tSettingOwner po = (SettingOwner) o;\n\t\t\tif(getSettingOwnerID() < po.getSettingOwnerID() )return -1;\n\t\t\telse if(getSettingOwnerID() > po.getSettingOwnerID()) return 1;\n\t\t\telse return 0;\n\t\t}\n\t\telse return 0;\n\t}\t\n\t\n\t/**\n\t * Getter for property seriesHeading.\n\t * @return Value of property seriesHeading.\n\t */\n\tpublic String getSeriesHeading()\n\t{\n\t\treturn seriesHeading.getStringValue();\n\t}\n\t\n\t/**\n\t * Setter for property seriesHeading.\n\t * @param value Value of property seriesHeading.\n\t */\n\tpublic void setSeriesHeading(String value)\n\t{\n\t\ttry\n\t\t{\n\t\t\tseriesHeading.setValue(value);\n\t\t\tupdateSeries();\n\t\t\tsetChanged();\n\t\t\tnotifyObservers(this);\n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\t// Shouldn't happen.\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property seriesColour.\n\t * @return Value of property seriesColour.\n\t */\n\tpublic Color getSeriesColour()\n\t{\n\t\treturn seriesColour.getColorValue();\n\t}\n\t\n\t/**\n\t * Setter for property seriesColour.\n\t * @param value Value of property seriesColour.\n\t */\n\tpublic void setSeriesColour(Color value)\n\t{\n\t\ttry\n\t\t{\n\t\t\tseriesColour.setValue(value);\n\t\t\tupdateSeries();\n\t\t\tsetChanged();\n\t\t\tnotifyObservers(this);\n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\t// Shouldn't happen.\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property showPoints.\n\t * @return Value of property showPoints.\n\t */\n\tpublic boolean showPoints()\n\t{\n\t\treturn showPoints.getBooleanValue();\n\t}\n\t\n\t/**\n\t * Setter for property showPoints.\n\t * @param value Value of property showPoints.\n\t */\n\tpublic void showPoints(boolean value)\n\t{\n\t\ttry\n\t\t{\n\t\t\tshowPoints.setValue(Boolean.valueOf(value));\n\t\t\tupdateSeries();\n\t\t\tsetChanged();\n\t\t\tnotifyObservers(this);\n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\t// Shouldn't happen.\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property seriesShape.\n\t * @return Value of property seriesShape.\n\t */\n\tpublic int getSeriesShape()\n\t{\n\t\treturn seriesShape.getCurrentIndex();\n\t}\n\t\n\t/**\n\t * Setter for property seriesShape.\n\t * @param value Value of property seriesShape.\n\t */\n\tpublic void setSeriesShape(int value) throws SettingException\n\t{\n\t\tseriesShape.setSelectedIndex(Integer.valueOf(value));\n\t\tupdateSeries();\n\t\tsetChanged();\n\t\tnotifyObservers(this);\t\t\n\t}\n\t\n\t/**\n\t * Getter for property showLines.\n\t * @return Value of property showLines.\n\t */\n\tpublic boolean showLines()\n\t{\n\t\treturn showLines.getBooleanValue();\n\t}\n\t\n\t/**\n\t * Setter for property showLines.\n\t * @param value Value of property showLines.\n\t */\n\tpublic void showLines(boolean value)\n\t{\n\t\ttry\n\t\t{\n\t\t\tshowLines.setValue(Boolean.valueOf(value));\n\t\t\tupdateSeries();\n\t\t\tsetChanged();\n\t\t\tnotifyObservers(this);\n\t\t}\n\t\tcatch (SettingException e)\n\t\t{\n\t\t\t// Shouldn't happen.\n\t\t}\n\t}\n\t\n\t/**\n\t * Getter for property lineWidth.\n\t * @return Value of property lineWidth.\n\t */\n\tpublic double getLineWidth()\n\t{\n\t\treturn lineWidth.getDoubleValue();\n\t}\n\t\n\t/**\n\t * Setter for property lineWidth.\n\t * @param value Value of property lineWidth.\n\t */\n\tpublic void setLineWidth(double value) throws SettingException\n\t{\n\t\tlineWidth.setValue(Double.valueOf(value));\n\t\tupdateSeries();\n\t\tsetChanged();\n\t\tnotifyObservers();\t\t\t\t\t\n\t}\n\t\n\t/**\n\t * Getter for property lineStyle.\n\t * @return Value of property lineStyle.\n\t */\n\tpublic int getLineStyle()\n\t{\n\t\treturn lineStyle.getCurrentIndex();\n\t}\n\t\n\t/**\n\t * Setter for property lineStyle.\n\t * @param value Value of property lineStyle (SOLID, DASHED, DOT_DASHED).\n\t */\n\tpublic void setLineStyle(int value) throws SettingException\n\t{\n\t\tlineStyle.setSelectedIndex(Integer.valueOf(value));\n\t\tupdateSeries();\n\t\tsetChanged();\n\t\tnotifyObservers(this);\t\t\n\t}\n\t\n\tpublic String toString()\n\t{\n\t\treturn this.seriesHeading.getStringValue();\n\t}\n\t\n\tpublic void updateSeries()\n\t{\n\t\t// We don't want series to change while we are updating.\n\t\tsynchronized (graph.getSeriesLock())\n\t\t{\t\t\t\n\t\t\tint seriesIndex = graph.getJFreeChartIndex(key);\n\t\t\t\n\t\t\tif (seriesIndex >= 0)\n\t\t\t{\n\t\t\t\t/* Set series colour. */\n\t\t\t\tif (renderer.getSeriesPaint(seriesIndex) == null || \n\t\t\t\t   !renderer.getSeriesPaint(seriesIndex).equals(seriesColour))\n\t\t\t\t{\n\t\t\t\t\trenderer.setSeriesPaint(seriesIndex, seriesColour.getColorValue());\n\t\t\t\t}\t\t\t\t\n\t\t\t\t\n\t\t\t\t/* Set series heading. */\n\t\t\t\tif (!graph.getXYSeries(key).getKey().equals(seriesHeading.getStringValue()))\n\t\t\t\t{\n\t\t\t\t\tgraph.changeSeriesName(key, seriesHeading.getStringValue());\n\t\t\t\t\ttry\n\t\t\t\t\t{\n\t\t\t\t\t\tseriesHeading.setValue(graph.getXYSeries(key).getKey());\n\t\t\t\t\t}\n\t\t\t\t\tcatch (SettingException e)\n\t\t\t\t\t{}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t/* Set showPoints. */\n\t\t\t\tBoolean pointsVisibleFlag = renderer.getSeriesShapesVisible(seriesIndex);\n\t\t\t\t\n\t\t\t\tif (pointsVisibleFlag == null || pointsVisibleFlag.booleanValue() != showPoints.getBooleanValue())\n\t\t\t\t{\n\t\t\t\t\trenderer.setSeriesShapesVisible(seriesIndex, showPoints.getBooleanValue());\n\t\t\t\t}\n\t\t\t\t\t\t\t\t\n\t\t\t\t/* Set seriesShape. */\t\t\t\t\n\t\t\t\tShape shape = renderer.getSeriesShape(seriesIndex);\n\t\t\t\tint shapeIndex = seriesShape.getCurrentIndex();\n\t\t\t\t\t\t\t\t\n\t\t\t\tif (!ShapeUtilities.equal(shape, SHAPES[shapeIndex]))\n\t\t\t\t\trenderer.setSeriesShape(seriesIndex, SHAPES[shapeIndex]);\n\t\t\t\t\t\t\t\t\n\t\t\t\t/* Set showLines. */\n\t\t\t\tBoolean linesVisibleFlag = renderer.getSeriesLinesVisible(seriesIndex);\n\t\t\t\tif (linesVisibleFlag == null || linesVisibleFlag.booleanValue() != showLines.getBooleanValue())\n\t\t\t\t{\n\t\t\t\t\trenderer.setSeriesLinesVisible(seriesIndex, showLines.getBooleanValue());\t\t\t\t\t\t\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t/* Set stroke - hard to check*/\n\t\t\t\tif (lineStyle.getCurrentIndex() == SOLID) // solid\n\t\t\t\t{\n\t\t\t\t\tBasicStroke newStroke = new BasicStroke((float)lineWidth.getDoubleValue(), BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND, 10.0f);\n\t\t\t\t\trenderer.setSeriesStroke(seriesIndex, newStroke);\t\t\t\t\t\n\t\t\t\t} \n\t\t\t\telse if (lineStyle.getCurrentIndex() == DASHED) // Just dash\n\t\t\t\t{\n\t\t\t\t\tfloat dash[] = {2.0f, 3.0f};\n\t\t\t\t\tBasicStroke newStroke = new BasicStroke((float)lineWidth.getDoubleValue(), BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND, 10.0f, dash, 1.0f);\n\t\t\t\t\trenderer.setSeriesStroke(seriesIndex, newStroke);\t\t\t\t\n\t\t\t\t}\n\t\t\t\telse // Funny dash\n\t\t\t\t{\n\t\t\t\t\tfloat dash[] = {1.0f, 3.0f, 5.0f, 3.0f};\n\t\t\t\t\tBasicStroke newStroke = new BasicStroke((float)lineWidth.getDoubleValue(), BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND, 10.0f, dash, 0.0f);\n\t\t\t\t\trenderer.setSeriesStroke(seriesIndex, newStroke);\t\t\t\t\n\t\t\t\t}\t\t\t\t\n\t\t\t}\n\t\t\t\n\t\t\ticon = new GraphSeriesIcon(renderer.getSeriesShape(seriesIndex), renderer.getSeriesStroke(seriesIndex), seriesColour.getColorValue(), showLines.getBooleanValue(), showPoints.getBooleanValue());\n\t\t\ticon.setOpaque(false);\n\t\t\ticon.setMinimumSize(new Dimension(20,10));\n\t\t\ticon.setMaximumSize(new Dimension(50,20));\n\t\t\ticon.setPreferredSize(new Dimension(30,10));\n\t\t}\n\t}\n\t\n\tpublic Graph.SeriesKey getSeriesKey()\n\t{\n\t\treturn key;\n\t}\n\t\n\t/** Creates a renderer for the icon of this series in the options dialog. */\n\tpublic JComponent getIcon()\n\t{\n\t\treturn this.icon;\n\t}\n\t\n\tprivate class GraphSeriesIcon extends JComponent\n\t{\n\t\tprivate Shape shape;\n\t\tprivate Stroke stroke;\n\t\tprivate Color color;\n\t\t\n\t\tprivate boolean showLines;\n\t\tprivate boolean showShapes;\n\t\t\n\t\tpublic GraphSeriesIcon(Shape shape, Stroke stroke, Color color, boolean showLines, boolean showShapes) \n\t\t{\n\t\t\tthis.shape = shape;\n\t\t\tthis.stroke = stroke;\n\t\t\tthis.color = color;\n\t\t\t\n\t\t\tthis.showLines = showLines;\n\t\t\tthis.showShapes = showShapes;\n\t\t}\n\n\t\tprotected void paintComponent(Graphics g) \n\t\t{\n\t\t\tsuper.paintComponent(g);\n\t\t\t\t\n\t\t\tfloat width = this.getWidth();\n\t\t\tfloat height = this.getHeight();\n\t\t\t\n\t\t\tGraphics2D g2d = (Graphics2D) g;\n\t\t\tg2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);\n\t\t\t\n\t\t\tg2d.setColor(color);\t\n\t\t\tg2d.setStroke(stroke);\n\t\t\tg2d.translate(width/2, height/2);\t\t\t\n\t\t\t\n\t\t\tif (showLines)\n\t\t\t\tg2d.drawLine(-(int)width/2,0, (int)width/2, 0);\t\t\t\n\t\t\tif (showShapes)\n\t\t\t\tg2d.fill(shape);\n\t\t\t\n\t\t\tg2d.dispose();\n\t\t}\n\t}\n\t\n\tpublic void save(Element series) throws SettingException\n\t{\n\t\tseries.setAttribute(\"seriesHeading\", getSeriesHeading());\n\t\tseries.setAttribute(\"lineWidth\", \"\" + getLineWidth());\n\t\t\n\t\tColor seriesColor = getSeriesColour();\n\t\tseries.setAttribute(\"seriesColourR\", \"\" + seriesColor.getRed());\n\t\tseries.setAttribute(\"seriesColourG\", \"\" + seriesColor.getGreen());\n\t\tseries.setAttribute(\"seriesColourB\", \"\" + seriesColor.getBlue());\n\t\t\n\t\tseries.setAttribute(\"showPoints\", showPoints() ? \"true\" : \"false\");\n\t\tseries.setAttribute(\"showLines\", showLines() ? \"true\" : \"false\");\n\t\t\n\t\tint lineStyle = getLineStyle();\n\t\t\n\t\tswitch (lineStyle)\n\t\t{\n\t\t\tcase (DASHED) : \n\t\t\t\tseries.setAttribute(\"lineStyle\", \"dashed\");\n\t\t\tbreak;\n\t\t\tcase (DOT_DASHED) : \n\t\t\t\tseries.setAttribute(\"lineStyle\", \"dotDashed\");\n\t\t\tbreak;\n\t\t\tdefault: \n\t\t\t\tseries.setAttribute(\"lineStyle\", \"normal\");\n\t\t}\n\t\t\n\t\tint seriesShape = getSeriesShape();\n\t\t\n\t\tswitch (seriesShape)\n\t\t{\n\t\t\tcase (CIRCLE) : \n\t\t\t\tseries.setAttribute(\"seriesShape\", \"circle\");\n\t\t\tbreak;\n\t\t\tcase (SQUARE) : \n\t\t\t\tseries.setAttribute(\"seriesShape\", \"square\");\n\t\t\tbreak;\n\t\t\tcase (TRIANGLE) : \n\t\t\t\tseries.setAttribute(\"seriesShape\", \"triangle\");\n\t\t\tbreak;\n\t\t\tcase (RECTANGLE_H) : \n\t\t\t\tseries.setAttribute(\"seriesShape\", \"rectangle_h\");\n\t\t\tbreak;\n\t\t\tcase (RECTANGLE_V) : \n\t\t\t\tseries.setAttribute(\"seriesShape\", \"rectangle_v\");\n\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tseries.setAttribute(\"seriesShape\", \"none\");\n\t\t}\n\t}\n\t\n\tpublic void load(Element series) throws SettingException\n\t{\n\t\tsetSeriesHeading(series.getAttribute(\"seriesHeading\"));\n\t\t\n\t\tdouble lineWidth = Graph.parseDouble(series.getAttribute(\"lineWidth\"));\n\t\t\n\t\tif (!Double.isNaN(lineWidth))\n\t\t{\n\t\t\tsetLineWidth(lineWidth);\n\t\t}\n\t\t\n\t\tString seriesColourR = series.getAttribute(\"seriesColourR\");\n\t\tString seriesColourG = series.getAttribute(\"seriesColourG\");\n\t\tString seriesColourB = series.getAttribute(\"seriesColourB\");\n\t\t\n\t\tColor seriesColor = Graph.parseColor(seriesColourR, seriesColourG, seriesColourB);\n\n\t\tsetSeriesColour(seriesColor);\n\t\tshowPoints(Graph.parseBoolean(series.getAttribute(\"showPoints\")));\n\t\tshowLines(Graph.parseBoolean(series.getAttribute(\"showLines\")));\n\t\t\n\t\tString lineStyle = series.getAttribute(\"lineStyle\");\n\t\t\n\t\tif (lineStyle.equals(\"dashed\"))\n\t\t\tthis.setLineStyle(DASHED);\n\t\telse if (lineStyle.equals(\"dotDashed\"))\n\t\t\tthis.setLineStyle(DOT_DASHED);\t\n\t\telse\n\t\t\tthis.setLineStyle(SOLID);\n\t\t\n\t\tString seriesShape = series.getAttribute(\"seriesShape\");\n\t\t\n\t\tif (seriesShape.equals(\"circle\"))\n\t\t\tthis.setSeriesShape(CIRCLE);\n\t\telse if (seriesShape.equals(\"square\"))\n\t\t\tthis.setSeriesShape(SQUARE);\n\t\telse if (seriesShape.equals(\"triangle\"))\n\t\t\tthis.setSeriesShape(TRIANGLE);\n\t\telse if (seriesShape.equals(\"rectangle_h\"))\n\t\t\tthis.setSeriesShape(RECTANGLE_H);\n\t\telse if (seriesShape.equals(\"rectangle_v\"))\n\t\t\tthis.setSeriesShape(RECTANGLE_V);\n\t\telse\n\t\t\tthis.setSeriesShape(NONE);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/graph/SeriesSettingsList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.graph;\n\nimport java.util.*;\n\nimport javax.swing.*;\n\n/**\n * Representation of an axis of a Graph.\n * The settings are propagated to the JFreeChart library.\n */\n@SuppressWarnings(\"serial\")\npublic class SeriesSettingsList extends AbstractListModel implements Observer\n{\n\tprivate Graph graph;\n\t\n\tprivate HashMap<Integer, Graph.SeriesKey> seriesKeys;\n\t\n\tpublic SeriesSettingsList(Graph graph)\n\t{\n\t\tthis.graph = graph;\n\t\tthis.seriesKeys = new HashMap<Integer, Graph.SeriesKey>();\n\t}\t\n\n\tpublic Object getElementAt(int index) \n\t{\n\t\tsynchronized (graph.getSeriesLock())\n\t\t{\n\t\t\treturn graph.getGraphSeries(seriesKeys.get(index));\n\t\t}\t\t\n\t}\n\t\n\tpublic Graph.SeriesKey getKeyAt(int index)\n\t{\n\t\tsynchronized (graph.getSeriesLock())\n\t\t{\n\t\t\treturn seriesKeys.get(index);\n\t\t}\n\t}\n\n\tpublic int getSize() \n\t{\n\t\treturn seriesKeys.size();\n\t}\n\t\n\tpublic void updateSeriesList()\n\t{\n\t\tsynchronized (graph.getSeriesLock())\n\t\t{\n\t\t\tfor (Map.Entry<Integer, Graph.SeriesKey> entry : seriesKeys.entrySet())\n\t\t\t{\t\t\t\n\t\t\t\tSeriesSettings series = graph.getGraphSeries(entry.getValue());\n\t\t\t\tif (series != null)\n\t\t\t\t\tseries.deleteObserver(this);\n\t\t\t}\n\t\t\t\n\t\t\tseriesKeys.clear();\n\t\t\t\n\t\t\tfor (Graph.SeriesKey key: graph.getAllSeriesKeys())\n\t\t\t{\n\t\t\t\tseriesKeys.put(graph.getJFreeChartIndex(key), key);\n\t\t\t\tgraph.getGraphSeries(key).updateSeries();\n\t\t\t\tgraph.getGraphSeries(key).addObserver(this);\t\t\t\t\n\t\t\t}\n\t\t}\n\t\t\n\t\tfireContentsChanged(this, 0, this.getSize());\t\t\n\t}\n\t\n\tpublic void update(Observable o, Object arg) \n\t{\t\t\n\t\tfireContentsChanged(this, 0, this.getSize());\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/graph/package-info.java",
    "content": "/**\n * Graph plotting/editing functionality used in the GUI.\n */\npackage userinterface.graph;\n"
  },
  {
    "path": "prism/src/userinterface/log/GUILog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.log;\n\nimport java.awt.BorderLayout;\nimport java.awt.Color;\nimport java.awt.Font;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.KeyEvent;\nimport java.awt.event.MouseEvent;\nimport java.awt.event.MouseListener;\nimport java.io.File;\nimport java.io.FileWriter;\nimport java.io.IOException;\nimport java.io.PrintWriter;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.Action;\nimport javax.swing.JFileChooser;\nimport javax.swing.JMenu;\nimport javax.swing.JPopupMenu;\nimport javax.swing.JScrollPane;\nimport javax.swing.JSeparator;\nimport javax.swing.JTextArea;\nimport javax.swing.filechooser.FileFilter;\nimport javax.swing.filechooser.FileNameExtensionFilter;\n\nimport prism.PrismLog;\nimport prism.PrismSettings;\nimport prism.PrismSettingsListener;\nimport userinterface.GUIClipboardEvent;\nimport userinterface.GUIPlugin;\nimport userinterface.GUIPrism;\nimport userinterface.util.GUIEvent;\nimport userinterface.util.GUILogEvent;\n\n@SuppressWarnings(\"serial\")\npublic class GUILog extends GUIPlugin implements MouseListener, PrismSettingsListener\n{\n\tprivate PrismLog theLog;\n\tprivate JTextArea text;\n\tprivate JPopupMenu popupMenu;\n\tprivate JMenu logMenu;\n\tprivate FileFilter logFilter;\n\tprivate Action clearAction, saveAction;\n\t\n\t/** Creates a new instance of GUILog */\n\tpublic GUILog(GUIPrism pr)\n\t{\n\t\tsuper(pr, true);\n\t\ttheLog = pr.getLog();\n\t\tif(theLog instanceof GUIWindowLog)\n\t\t{\n\t\t\tGUIWindowLog win = (GUIWindowLog)theLog;\n\t\t\tinitComponentsAsWindowLog(win);\n\t\t}\n\t\telse\n\t\t{\n\t\t\t//other types of log handles here\n\t\t}\n\t}\n\t\n\tpublic void takeCLArgs(String args[])\n\t{\n\t}\n\t\n\tpublic boolean displaysTab()\n\t{\n\t\treturn true;\n\t}\n\t\n\tpublic javax.swing.JMenu getMenu()\n\t{\n\t\treturn logMenu;\n\t}\n\t\n\tpublic String getTabText()\n\t{\n\t\treturn \"Log\";\n\t}\n\t\n\tpublic javax.swing.JToolBar getToolBar()\n\t{\n\t\treturn null;\n\t}\n\t\n\tpublic String getXMLIDTag()\n\t{\n\t\treturn \"\";\n\t}\n\t\n\tpublic Object getXMLSaveTree()\n\t{\n\t\treturn null;\n\t}\n\t\n\tpublic void loadXML(Object c)\n\t{\n\t}\n\t\n\tpublic boolean processGUIEvent(GUIEvent e)\n\t{\n\t\tif(e instanceof GUILogEvent)\n\t\t{\n\t\t\tGUILogEvent le = (GUILogEvent)e;\n\t\t\tif(le.getID() == GUILogEvent.PRINTLN)\n\t\t\t{\n\t\t\t\ttheLog.println(le.getData());\n\t\t\t}\n\t\t\telse if(le.getID() == GUILogEvent.PRINT)\n\t\t\t{\n\t\t\t\ttheLog.print(le.getData());\n\t\t\t}\n\t\t\telse if(le.getID() == GUILogEvent.PRINTSEPARATOR)\n\t\t\t{\n\t\t\t\ttheLog.printSeparator();\n\t\t\t}\n\t\t\telse if(le.getID() == GUILogEvent.PRINTWARNING)\n\t\t\t{\n\t\t\t\ttheLog.printWarning((String) le.getData());\n\t\t\t}\n\t\t}\n\t\telse if (e instanceof GUIClipboardEvent && super.getGUI().getFocussedPlugin() == this)\n\t\t{\n\t\t\tGUIClipboardEvent ce = (GUIClipboardEvent)e;\n\t\t\tif(ce.getID() == GUIClipboardEvent.COPY)\n\t\t\t{\n\t\t\t\t((GUIWindowLog)theLog).copy();\n\t\t\t\treturn true;\n\t\t\t}\n\t\t\telse if(ce.getID() == GUIClipboardEvent.SELECT_ALL)\n\t\t\t{\n\t\t\t\t((GUIWindowLog)theLog).selectAll();\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\t\n\t@Override\n\tpublic boolean canDoClipBoardAction(Action action) \n\t{\n\t\tif (action == GUIPrism.getClipboardPlugin().getCopyAction())\n\t\t{\n\t\t\treturn ((GUIWindowLog)theLog).hasSelectedText();\n\t\t}\n\t\telse if (action == GUIPrism.getClipboardPlugin().getSelectAllAction())\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\tprivate void initComponentsAsWindowLog(GUIWindowLog log)\n\t{\n\t\tJScrollPane logScroller = new JScrollPane();\n\t\t{\n\t\t\ttext = new javax.swing.JTextArea();\n\t\t\ttext.addMouseListener(this);\n\t\t\ttext.setFont(new Font(\"monospaced\", Font.PLAIN, 12));\n\t\t\ttext.setBackground(Color.lightGray);\n\t\t\tlog.open(text, this);\n\t\t\ttext.addMouseListener(this);\n\t\t\ttext.setEditable(false);\n\t\t\ttext.setBorder(new javax.swing.border.TitledBorder(\"Log Output\"));\n\t\t\t\n\t\t\tlogScroller.add(text);\n\t\t\tlogScroller.setViewportView(text);\n\t\t}\n\t\tsetLayout(new BorderLayout());\n\t\tadd(logScroller, BorderLayout.CENTER);\n\t\t\n\t\tpopupMenu = new JPopupMenu();\n\t\tlogMenu = new JMenu(\"Log\");\n\t\t\n\t\t\n\t\tclearAction = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\t((GUIWindowLog)theLog).clear();\n\t\t\t}\n\t\t};\n\t\tclearAction.putValue(Action.SHORT_DESCRIPTION, \"Clear log\");\n\t\tclearAction.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_C));\n\t\tclearAction.putValue(Action.NAME, \"Clear log\");\n\t\tclearAction.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDelete.png\"));\n\t\t\n\t\tsaveAction = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (showSaveFileDialog(logFilter) == JFileChooser.APPROVE_OPTION) {\n\t\t\t\t\tFile file = getChooserFile();\n\t\t\t\t\t// do save...\n\t\t\t\t\ttry\n\t\t\t\t\t{\n\t\t\t\t\t\tPrintWriter out = new PrintWriter(new FileWriter(file));\n\t\t\t\t\t\tout.print(text.getText());\n\t\t\t\t\t\tout.flush();\n\t\t\t\t\t\tout.close();\n\t\t\t\t\t}\n\t\t\t\t\tcatch(IOException ex)\n\t\t\t\t\t{\n\t\t\t\t\t\terror(\"Could not save to file \\\"\" + file + \"\\\"\");\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\tsaveAction.putValue(Action.SHORT_DESCRIPTION, \"Save log as...\");\n\t\tsaveAction.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n\t\tsaveAction.putValue(Action.NAME, \"Save log as...\");\n\t\tsaveAction.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSave.png\"));\n\t\t\n\t\t\n\t\t//popupMenu.add(new JSeparator());\n\t\tpopupMenu.add(saveAction);\n\t\tpopupMenu.add(new JSeparator());\n\t\tpopupMenu.add(GUIPrism.getClipboardPlugin().getCopyAction());\n\t\tpopupMenu.add(clearAction);\n\t\tpopupMenu.add(new JSeparator());\n\t\tpopupMenu.add(GUIPrism.getClipboardPlugin().getSelectAllAction());\n\t\t\n\t\tlogMenu.setMnemonic('L');\n\t\tlogMenu.add(saveAction);\n\t\tlogMenu.add(new JSeparator());\n\t\tlogMenu.add(clearAction);\n\t\t\n\t\tlogFilter = new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\"); \n\t}\n\t\n\tpublic void mouseClicked(MouseEvent e)\n\t{\n\t}\n\t\n\tpublic void mouseEntered(MouseEvent e)\n\t{\n\t}\n\t\n\tpublic void mouseExited(MouseEvent e)\n\t{\n\t}\n\t\n\tpublic void mousePressed(MouseEvent e)\n\t{\n\t\tif(e.isPopupTrigger())\n\t\t{\n\t\t\tif(e.getSource() == text)\n\t\t\t{\n\t\t\t\tpopupMenu.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t}\n\t\t}\n\t}\n\t\n\tpublic void mouseReleased(MouseEvent e)\n\t{\n\t\tif(e.isPopupTrigger())\n\t\t{\n\t\t\tif(e.getSource() == text)\n\t\t\t{\n\t\t\t\tpopupMenu.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t}\n\t\t}\n\t}\n\t\n\tpublic void notifySettings(PrismSettings settings)\n\t{\n\t\tif(theLog instanceof GUIWindowLog)\n\t\t\t((GUIWindowLog)theLog).notifySettings(settings);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/log/GUIWindowLog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.log;\n\nimport javax.swing.*;\nimport javax.swing.event.CaretEvent;\nimport javax.swing.event.CaretListener;\nimport javax.swing.text.BadLocationException;\n\nimport prism.*;\nimport userinterface.util.GUIEvent;\n\npublic class GUIWindowLog extends PrismLog\n{\n\t// text area swing object where all text will be echoed\n\tprivate JTextArea textArea;\n\t// update thread\n\tprivate GUIWindowLogUpdater updater;\n\t// buffer\n\tprivate String buffer;\n\t// clear flag\n\tprivate boolean clearFlag;\n\tprivate GUILog logPlugin;\n\n\tpublic GUIWindowLog()\n\t{\n\t\t\n\t\tbuffer = \"\";\n\t\tclearFlag = false;\n\t\ttextArea = null;\n\t\tupdater = null;\n\t}\n\n\tpublic GUIWindowLog(JTextArea ta, GUILog logPlugin)\n\t{\n\t\tbuffer = \"\";\n\t\tclearFlag = false;\n\t\topen(ta, logPlugin);\n\t}\n\n\tpublic void open(JTextArea ta, GUILog logPlugin)\n\t{\n\t\tthis.logPlugin = logPlugin;\n\t\ttextArea = ta;\n\t\ttextArea.addCaretListener(new CaretListener() {\n\t\t\tpublic void caretUpdate(CaretEvent e) {\n\t\t\t\tif (GUIWindowLog.this.logPlugin != null)\n\t\t\t\t\tGUIWindowLog.this.logPlugin.getSelectionChangeHandler().notifyListeners(new GUIEvent(1));\n\t\t\t}\t\t\t\n\t\t});\n\t\tupdater = new GUIWindowLogUpdater(this, textArea);\n\t\tupdater.start();\n\t}\n\n\t// Methods to implement PrismLog\n\n\t@Override\n\tpublic boolean ready()\n\t{\n\t\treturn (textArea != null);\n\t}\n\n\t@Override\n\tpublic void flush()\n\t{\n\t}\n\n\t@Override\n\tpublic void close()\n\t{\n\t\tflush();\n\t}\n\n\t@Override\n\tpublic void print(boolean b)\n\t{\n\t\taddToBuffer(\"\" + b);\n\t}\n\n\t@Override\n\tpublic void print(char c)\n\t{\n\t\taddToBuffer(\"\" + c);\n\t}\n\n\t@Override\n\tpublic void print(double d)\n\t{\n\t\taddToBuffer(\"\" + d);\n\t}\n\n\t@Override\n\tpublic void print(float f)\n\t{\n\t\taddToBuffer(\"\" + f);\n\t}\n\n\t@Override\n\tpublic void print(int i)\n\t{\n\t\taddToBuffer(\"\" + i);\n\t}\n\n\t@Override\n\tpublic void print(long l)\n\t{\n\t\taddToBuffer(\"\" + l);\n\t}\n\n\t@Override\n\tpublic void print(Object obj)\n\t{\n\t\taddToBuffer(\"\" + obj);\n\t}\n\n\t@Override\n\tpublic void print(String s)\n\t{\n\t\taddToBuffer(s);\n\t}\n\n\t@Override\n\tpublic void println()\n\t{\n\t\taddToBuffer(\"\\n\");\n\t}\n\n\t// Other methods\n\n\tpublic void clear()\n\t{\n\t\tsetClearFlag();\n\t}\n\n\tpublic int getMaxTextLength()\n\t{\n\t\treturn updater.getMaxTextLength();\n\t}\n\n\tpublic void setMaxTextLength(int i)\n\t{\n\t\tupdater.setMaxTextLength(i);\n\t}\n\n\t// add string to buffer\n\t\n\tpublic synchronized void addToBuffer(String s)\n\t{\n\t\tbuffer += s;\n\t}\n\n\t// remove contents of buffer\n\t\n\tpublic synchronized String takeBuffer()\n\t{\n\t\tString s = buffer;\n\t\tbuffer = \"\";\n\t\treturn s;\n\t}\n\n\t// set clear flag\n\t\n\tpublic synchronized void setClearFlag()\n\t{\n\t\tclearFlag = true;\n\t}\n\n\t// get (and reset) clear flag\n\t\n\tpublic synchronized boolean getClearFlag()\n\t{\n\t\tboolean b = clearFlag;\n\t\tclearFlag = false;\n\t\treturn b;\n\t}\n\n\t// thread which periodically checks for any pending input to log and adds it to window\n\t\n\tclass GUIWindowLogUpdater extends Thread\n\t{\n\t\tprivate GUIWindowLog gwl;\n\t\tprivate JTextArea textArea;\n\t\tprivate String text;\n\t\tprivate int textLen = 0;\n\t\tprivate int maxTextLen = 10000;\n\t\tprivate int updateDelay = 1000;\n\t\t\n\t\tpublic GUIWindowLogUpdater(GUIWindowLog gwl, JTextArea textArea)\n\t\t{\n\t\t\tsuper(); \n\t\t\tthis.gwl = gwl;\n\t\t\tthis.textArea = textArea;\n\t\t\ttext = \"\";\n\t\t}\n\n\t\tpublic int getMaxTextLength()\n\t\t{\n\t\t\treturn maxTextLen;\n\t\t}\n\n\t\tpublic void setMaxTextLength(int i)\n\t\t{\n\t\t\tmaxTextLen  = i;\n\t\t}\n\n\t\tpublic void run()\n\t\t{\n\t\t\tString s;\n\t\t\tint newStart, i;\n\t\t\t\n\t\t\twhile (true) {\n\t\t\t\n\t\t\t\t// sleep\n\t\t\t\ttry { Thread.sleep(updateDelay); } catch (InterruptedException e) {}\n\t\t\t\t\n\t\t\t\t// clear log if asked to\n\t\t\t\tif (gwl.getClearFlag()) {\n\t\t\t\t\t// remove (but don't display) and input pending\n\t\t\t\t\tgwl.takeBuffer();\n\t\t\t\t\t// clear log\n\t\t\t\t\ttext = \"\";\n\t\t\t\t\ttextLen += 0;\n\t\t\t\t\t// update text area\n\t\t\t\t\tSwingUtilities.invokeLater(new SetWindowLogText(textArea, text));\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\t// get any new input to log\n\t\t\t\ts = gwl.takeBuffer();\n\t\t\t\t// if there actually is any...\n\t\t\t\tif (s.length() > 0) {\n\t\t\t\t\t// add to text\n\t\t\t\t\ttext += s;\n\t\t\t\t\ttextLen += s.length();\n\t\t\t\t\t// truncate text if necessary\n\t\t\t\t\tif (textLen > maxTextLen) {\n\t\t\t\t\t\t// trim to max text length\n\t\t\t\t\t\tnewStart = textLen - maxTextLen;\n\t\t\t\t\t\t// remove any partial line at start (i.e. cut to next new line)\n\t\t\t\t\t\ti = text.indexOf('\\n', newStart);\n\t\t\t\t\t\tif (i != -1) newStart = i + 1;\n\t\t\t\t\t\ttext = text.substring(newStart);\n\t\t\t\t\t\ttextLen = text.length();\n\t\t\t\t\t}\n\t\t\t\t\t// update text area\n\t\t\t\t\tSwingUtilities.invokeLater(new SetWindowLogText(textArea, text));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t// inner class to actually write to the text area\n\t// must be done as a thread because code is called using invokeLater\n\t\n\tprivate class SetWindowLogText extends Thread\n\t{\n\t\tprivate JTextArea textArea;\n\t\tprivate String s;\n\t\t\n\t\tpublic SetWindowLogText(JTextArea textArea, String s)\n\t\t{\n\t\t\tsuper();\n\t\t\tthis.textArea = textArea;\n\t\t\tthis.s = s;\n\t\t}\n\t\t\n\t\tpublic void run()\n\t\t{\n\t\t\ttry {\n\t\t\t\t// replace all current contents with string s\n\t\t\t\ttextArea.replaceRange(s, 0, textArea.getLineEndOffset(textArea.getLineCount()-1));\n\t\t\t}\n\t\t\tcatch (BadLocationException e) {}\n\t\t}\n\t}\n\n\t// receive notification of settings info\n\t\n\tpublic void notifySettings(PrismSettings settings)\n\t{\n\t\ttextArea.setFont(settings.getFontColorPair(PrismSettings.LOG_FONT).f);\n\t\t//textArea.setSelectionColor(settings.getColor(PrismSettings.LOG_SELECTION_COLOUR));\n\t\ttextArea.setBackground(settings.getColor(PrismSettings.LOG_BG_COLOUR));\n\t\tsetMaxTextLength(settings.getInteger(PrismSettings.LOG_BUFFER_LENGTH));\n\t}\n\n\tpublic boolean hasSelectedText() \n\t{\t\t\n\t\treturn (textArea != null && textArea.getSelectedText() != null);\n\t}\n\t\n\tpublic void copy() \n\t{\t\t\n\t\tif (textArea != null)\n\t\t\ttextArea.copy();\n\t}\n\n\tpublic void selectAll() \n\t{\n\t\tif (textArea != null)\n\t\t\ttextArea.selectAll();\t\t\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/log/package-info.java",
    "content": "/**\n * The \"Log\" tab in the GUI.\n */\npackage userinterface.log;\n"
  },
  {
    "path": "prism/src/userinterface/model/GUIModelEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport javax.swing.*;\n\nimport prism.PrismLangException;\nimport userinterface.util.GUIUndoManager;\n\n@SuppressWarnings(\"serial\")\npublic abstract class GUIModelEditor extends JPanel\n{    \n    public abstract String getParseText();\n    \n    public abstract void newModel();\n    \n    public abstract void undo();\n    \n    public abstract void redo();\n        \n    public abstract void cut();\n    \n    public abstract void copy();\n    \n    public abstract void paste();\n    \n    public abstract void delete();\n    \n    public abstract void selectAll();\n    \n    public void modelParseFailed(PrismLangException parserError, boolean background) {}\n\n    public void modelParseSuccessful() {}\n    \n    public GUIUndoManager getUndoManager()\n    {\n    \treturn null;\n    }\n    \n    public boolean canDoClipBoardAction(Action action)\n\t{\n\t\treturn false;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/GUIModelEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport parser.Values;\nimport parser.ast.ModulesFile;\nimport userinterface.util.GUIEvent;\n\npublic class GUIModelEvent extends GUIEvent\n{\n\t// CONSTANTS\n\tpublic static final int NEW_MODEL = 0; //when no parsed or built model\n\tpublic static final int LOAD_MODEL = 1; //when model is loaded into text editor\n\tpublic static final int IMPORT_MODEL = 2; //when model is imported into text editor\n\tpublic static final int MODEL_PARSED = 3; // when parsed model exists\n\tpublic static final int MODIFIED_SINCE_SAVE = 4; //when text is modified\n\tpublic static final int SAVE_MODEL = 5; //when text is saved to file\n\tpublic static final int MODEL_BUILT = 6; //when built model exists\n\tpublic static final int MODEL_PARSE_FAILED = 7; //when a failed model parse happens\n\tpublic static final int MODEL_BUILD_FAILED = 8; //when a failed model build happens\n\tpublic static final int NEW_LOAD_NOT_RELOAD_MODEL = 9;\n\n\t// DATA ATTRIBUTES\n\tprivate ModulesFile file;\n\tprivate Values buildValues;\n\n\t/** Creates a new instance of GUIModelEvent */\n\tpublic GUIModelEvent(int id, ModulesFile file)\n\t{\n\t\tsuper(id);\n\t\tthis.file = file;\n\t}\n\n\tpublic GUIModelEvent(int id, Values buildValues)\n\t{\n\t\tsuper(id);\n\t\tthis.file = null;\n\t\tthis.buildValues = buildValues;\n\t}\n\n\tpublic GUIModelEvent(int id)\n\t{\n\t\tsuper(id);\n\t\tthis.file = null;\n\t}\n\n\tpublic ModulesFile getModulesFile()\n\t{\n\t\treturn file;\n\t}\n\n\tpublic Values getBuildValues()\n\t{\n\t\treturn buildValues;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/GUIMultiModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport java.awt.BorderLayout;\nimport java.awt.Color;\nimport java.awt.Dimension;\nimport java.awt.Toolkit;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.KeyEvent;\nimport java.io.File;\nimport java.util.HashMap;\nimport java.util.Map;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.Action;\nimport javax.swing.JDialog;\nimport javax.swing.JFileChooser;\nimport javax.swing.JMenu;\nimport javax.swing.JOptionPane;\nimport javax.swing.JPanel;\nimport javax.swing.JPopupMenu;\nimport javax.swing.JScrollPane;\nimport javax.swing.JSeparator;\nimport javax.swing.JTextField;\nimport javax.swing.JToolBar;\nimport javax.swing.KeyStroke;\nimport javax.swing.filechooser.FileFilter;\nimport javax.swing.filechooser.FileNameExtensionFilter;\n\nimport io.ModelExportFormat;\nimport io.ModelExportOptions;\nimport io.ModelExportTask;\nimport io.ModelExportTask.ModelExportEntity;\nimport prism.ModelType;\nimport prism.PrismSettings;\nimport prism.PrismSettingsListener;\nimport userinterface.GUIClipboardEvent;\nimport userinterface.GUIPlugin;\nimport userinterface.GUIPrism;\nimport userinterface.util.GUIComputationEvent;\nimport userinterface.util.GUIEvent;\nimport userinterface.util.GUIExitEvent;\nimport userinterface.util.GUIUndoManager;\n\n@SuppressWarnings(\"serial\")\npublic class GUIMultiModel extends GUIPlugin implements PrismSettingsListener\n{\n\t//Constants\n\tpublic static final int CONTINUE = 0;\n\tpublic static final int CANCEL = 1;\n\n\t//GUI\n\tprivate JTextField fileTextField;\n\tprivate JMenu modelMenu, newMenu, viewMenu, exportMenu, computeMenu, computeExportMenu;\n\tprivate JMenu exportSSMenu, exportTrMenu;\n\tprivate AbstractAction viewStates, viewTrans, viewObs, viewStateRewards, viewTransRewards, viewLabels, viewPrismCode;\n\tprivate AbstractAction computeSS, computeTr, newPRISMModel;\n\tprivate AbstractAction newPEPAModel, loadModel, reloadModel, saveModel, saveAsModel, parseModel, buildModel;\n\tprivate AbstractAction exportStatesPlain, exportStatesMatlab,\n\t\t\texportTransPlain, exportTransMatlab, exportTransDot, exportTransUMB, exportObsPlain, exportObsMatlab, exportStateRewardsPlain, exportStateRewardsMatlab,\n\t\t\texportTransRewardsPlain, exportTransRewardsMatlab, exportLabelsPlain, exportLabelsMatlab,\n\t\t\texportSSPlain, exportSSMatlab, exportTrPlain, exportTrMatlab;\n\tprivate JPopupMenu popup;\n\t//Contents\n\tprivate GUIMultiModelHandler handler;\n\tprivate Map<String,FileFilter> modelFilters;\n\tprivate Map<String,FileFilter> staFilters;\n\tprivate Map<String,FileFilter> traFilters;\n\tprivate Map<String,FileFilter> obsFilters;\n\tprivate Map<String,FileFilter> labFilters;\n\tprivate FileFilter textFilter;\n\tprivate FileFilter matlabFilter;\n\tprivate FileFilter dotFilter;\n\tprivate FileFilter umbFilter;\n\t//State\n\tprivate boolean computing = false;\n\tprivate boolean initialised = false;\n\n\t/** Creates a new instance of GUIMultiModel */\n\tpublic GUIMultiModel(GUIPrism pr)\n\t{\n\t\tsuper(pr);\n\t\tinitialised = false;\n\t\tinitComponents();\n\t\tinitialised = true;\n\t\tdoEnables();\n\t}\n\n\tpublic void takeCLArgs(String args[])\n\t{\n\t\tif (args.length > 0) {\n\t\t\tFile f = new File(args[0]);\n\t\t\t// load the specified model file\n\t\t\thandler.loadModel(f, false);\n\t\t\t// set the default directory of the file chooser\n\t\t\tFile dir = f.getParentFile();\n\t\t\tif (dir == null)\n\t\t\t\tdir = new File(\".\");\n\t\t\tgetGUI().getChooser().setCurrentDirectory(dir);\n\t\t}\n\t}\n\n\t@Override\n\tpublic void onInitComponentsCompleted()\n\t{\n\t\t// forward to multi-model handler\n\t\thandler.onInitComponentsCompleted();\n\t}\n\n\tpublic GUIMultiModelHandler getHandler()\n\t{\n\t\treturn handler;\n\t}\n\n\tpublic JPopupMenu getPopup()\n\t{\n\t\treturn popup;\n\t}\n\n\tpublic boolean getComputing()\n\t{\n\t\treturn computing;\n\t}\n\t\n\tpublic void doEnables()\n\t{\n\t\t// do nothing if not initialised yet\n\t\tif (!initialised)\n\t\t\treturn;\n\t\t// setup file label\n\t\tint mode = handler.getModelMode();\n\t\tString s = \"\";\n\t\tswitch (mode) {\n\t\tcase GUIMultiModelHandler.PRISM_MODE:\n\t\t\ts += \"PRISM Model File: \";\n\t\t\tbreak;\n\t\tcase GUIMultiModelHandler.PEPA_MODE:\n\t\t\ts += \"PEPA Model File: \";\n\t\t\tbreak;\n\t\t}\n\t\ts += handler.getActiveFileName();\n\t\tif (handler.modified())\n\t\t\ts += \"*\";\n\t\tfileTextField.setText(s);\n\t\t// model menu\n\t\tnewPRISMModel.setEnabled(!computing);\n\t\tnewPEPAModel.setEnabled(!computing);\n\t\tloadModel.setEnabled(!computing);\n\t\treloadModel.setEnabled(!computing && handler.hasActiveFile());\n\t\tsaveModel.setEnabled(!computing && handler.modified());\n\t\tsaveAsModel.setEnabled(!computing);\n\t\tparseModel.setEnabled(!computing);\n\t\tbuildModel.setEnabled(!computing);\n\t\tviewStates.setEnabled(!computing);\n\t\tviewTrans.setEnabled(!computing);\n\t\tviewObs.setEnabled(!computing);\n\t\tviewStateRewards.setEnabled(!computing);\n\t\tviewTransRewards.setEnabled(!computing);\n\t\tviewLabels.setEnabled(!computing);\n\t\tviewPrismCode.setEnabled(!computing && handler.getParseState() == GUIMultiModelTree.TREE_SYNCHRONIZED_GOOD);\n\t\tcomputeSS.setEnabled(!computing && (handler.getParsedModelType() == ModelType.CTMC || handler.getParsedModelType() == ModelType.DTMC));\n\t\tcomputeTr.setEnabled(!computing && (handler.getParsedModelType() == ModelType.CTMC || handler.getParsedModelType() == ModelType.DTMC));\n\t\texportStatesPlain.setEnabled(!computing);\n\t\texportStatesMatlab.setEnabled(!computing);\n\t\texportTransPlain.setEnabled(!computing);\n\t\texportTransMatlab.setEnabled(!computing);\n\t\texportTransDot.setEnabled(!computing);\n\t\texportTransUMB.setEnabled(!computing);\n\t\texportObsPlain.setEnabled(!computing);\n\t\texportObsMatlab.setEnabled(!computing);\n\t\texportStateRewardsPlain.setEnabled(!computing);\n\t\texportStateRewardsMatlab.setEnabled(!computing);\n\t\texportTransRewardsPlain.setEnabled(!computing);\n\t\texportTransRewardsMatlab.setEnabled(!computing);\n\t\texportLabelsPlain.setEnabled(!computing);\n\t\texportLabelsMatlab.setEnabled(!computing);\n\t}\n\n\tpublic int doModificationCheck()\n\t{\n\t\tif (!handler.modified())\n\t\t\treturn CONTINUE;\n\t\tif (!handler.hasActiveFile()) {\n\t\t\tString[] selection = { \"Yes\", \"No\", \"Cancel\" };\n\t\t\tint selectionNo = -1;\n\t\t\tselectionNo = optionPane(\"Model has been modified.\\nDo you wish to save it?\", \"Question\", JOptionPane.OK_CANCEL_OPTION,\n\t\t\t\t\tJOptionPane.QUESTION_MESSAGE, selection, selection[0]);\n\t\t\tswitch (selectionNo) {\n\t\t\tcase 0:\n\t\t\t\treturn a_saveModelAs();\n\t\t\tcase 1:\n\t\t\t\treturn CONTINUE;\n\t\t\tcase 2:\n\t\t\t\treturn CANCEL;\n\t\t\tdefault:\n\t\t\t\treturn CANCEL;\n\t\t\t}\n\t\t} else {\n\t\t\tString[] selection = { \"Yes\", \"No\", \"Save As...\", \"Cancel\" };\n\t\t\tint selectionNo = -1;\n\t\t\tselectionNo = optionPane(\"Model has been modified.\\nDo you wish to save it?\", \"Question\", JOptionPane.OK_CANCEL_OPTION,\n\t\t\t\t\tJOptionPane.QUESTION_MESSAGE, selection, selection[0]);\n\t\t\tswitch (selectionNo) {\n\t\t\tcase 0:\n\t\t\t\treturn a_saveModel();\n\t\t\tcase 1:\n\t\t\t\treturn CONTINUE;\n\t\t\tcase 2:\n\t\t\t\treturn a_saveModelAs();\n\t\t\tcase 3:\n\t\t\t\treturn CANCEL;\n\t\t\tdefault:\n\t\t\t\treturn CANCEL;\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void showModel(String modelString)\n\t{\n\t\tJDialog diag = new JDialog(getGUI(), false);\n\n\t\tdiag.setTitle(\"Parsed PRISM Model\");\n\t\tGUITextModelEditor edit = new GUITextModelEditor(modelString, handler);\n\t\tedit.setEditable(false);\n\t\tedit.setBackground(new Color(224, 255, 255));\n\t\t/*\n\t\tPrismEditorKit kit = new PrismEditorKit();\n\t\tedit.setEditorKitForContentType(\"text/prism\", kit);\n\t\tedit.setContentType(\"text/prism\");\n\t\tedit.setPreferredSize(new Dimension(1000,300));\n\t\tedit.setText(modelString);\n\t\tedit.setFont(new Font(\"monospaced\", Font.PLAIN, 12));*/\n\n\t\tJScrollPane scro = new JScrollPane();\n\t\tscro.setPreferredSize(new Dimension(640, 300));\n\t\tscro.setViewportView(edit);\n\t\tdiag.getContentPane().add(scro);\n\n\t\tdiag.setDefaultCloseOperation(JDialog.DISPOSE_ON_CLOSE);\n\t\tdiag.pack();\n\t\tdiag.setLocationRelativeTo(getGUI()); // centre\n\t\tdiag.setVisible(true);\n\t}\n\n\t//Action methods\n\n\tprotected void a_newPRISMModel()\n\t{\n\t\tint cont = doModificationCheck();\n\t\tif (cont == CONTINUE)\n\t\t\thandler.newPRISMModel();\n\t}\n\n\tprotected void a_newPEPAModel()\n\t{\n\t\tint cont = doModificationCheck();\n\t\tif (cont == CONTINUE)\n\t\t\thandler.newPEPAModel();\n\t}\n\n\tprotected void a_openModel()\n\t{\n\t\tint cont = doModificationCheck();\n\t\tif (cont == CONTINUE) {\n\t\t\tString filterName;\n\t\t\tswitch (handler.getModelMode()) {\n\t\t\tcase GUIMultiModelHandler.PEPA_MODE:\n\t\t\t\tfilterName = \"pepa\";\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tfilterName = \"prism\";\n\t\t\t}\n\t\t\tif (showOpenFileDialog(modelFilters.values(), modelFilters.get(filterName)) == JFileChooser.APPROVE_OPTION) {\n\t\t\t\tFile file = getChooserFile();\n\t\t\t\tif (file == null) {\n\t\t\t\t\terror(\"No file selected\");\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t\t\thandler.loadModel(file);\n\t\t\t}\n\t\t}\n\t}\n\n\tprotected void a_reloadModel()\n\t{\n\t\tint cont = doModificationCheck();\n\t\tif (cont == CONTINUE) {\n\t\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t\thandler.reloadActiveFile();\n\t\t}\n\t}\n\n\tprotected int a_saveModel()\n\t{\n\t\tif (!handler.hasActiveFile()) {\n\t\t\treturn a_saveModelAs();\n\t\t} else {\n\t\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t\treturn handler.saveToActiveFile();\n\t\t}\n\t}\n\n\tprotected int a_saveModelAs()\n\t{\n\t\tString filterName;\n\t\tswitch (handler.getModelMode()) {\n\t\tcase GUIMultiModelHandler.PEPA_MODE:\n\t\t\tfilterName = \"pepa\";\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tfilterName = \"prism\";\n\t\t}\n\t\tif (showSaveFileDialog(modelFilters.values(), modelFilters.get(filterName)) != JFileChooser.APPROVE_OPTION) {\n\t\t\treturn CANCEL;\n\t\t}\n\t\t// do save\n\t\treturn handler.saveToFile(getChooserFile());\n\t}\n\n\tprotected void a_refreshParseTree()\n\t{\n\t\thandler.requestParse(true);\n\t}\n\n\tprotected void a_build()\n\t{\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Request build\n\t\thandler.forceBuild();\n\t}\n\n\tprotected void a_exportBuildAs(ModelExportEntity exportEntity, ModelExportFormat exportFormat)\n\t{\n\t\tint res = JFileChooser.CANCEL_OPTION;\n\n\t\t// pop up dialog to select file\n\t\tswitch (exportFormat) {\n\t\t\tcase DOT:\n\t\t\t\tres = showSaveFileDialog(dotFilter);\n\t\t\t\tbreak;\n\t\t\tcase UMB:\n\t\t\t\tres = showSaveFileDialog(umbFilter);\n\t\t\t\tbreak;\n\t\t\tcase MATLAB:\n\t\t\t\tres = showSaveFileDialog(matlabFilter);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\tswitch (exportEntity) {\n\t\t\t\t\tcase STATES:\n\t\t\t\t\t\tres = showSaveFileDialog(staFilters.values(), staFilters.get(\"sta\"));\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase MODEL:\n\t\t\t\t\t\tres = showSaveFileDialog(traFilters.values(), traFilters.get(\"tra\"));\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase OBSERVATIONS:\n\t\t\t\t\t\tres = showSaveFileDialog(obsFilters.values(), obsFilters.get(\"obs\"));\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase LABELS:\n\t\t\t\t\t\tres = showSaveFileDialog(labFilters.values(), labFilters.get(\"lab\"));\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tdefault:\n\t\t\t\t\t\tres = showSaveFileDialog(textFilter);\n\t\t\t\t}\n\t\t\t\tbreak;\n\t\t}\n\t\tif (res != JFileChooser.APPROVE_OPTION) {\n\t\t\treturn;\n\t\t}\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Do export...\n\t\thandler.export(new ModelExportTask(exportEntity, getChooserFile(), new ModelExportOptions(exportFormat)));\n\t}\n\n\tprotected void a_viewBuild(ModelExportEntity exportEntity, ModelExportFormat exportFormat)\n\t{\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Do view...\n\t\thandler.export(new ModelExportTask(exportEntity, (File) null, new ModelExportOptions(exportFormat)));\n\t}\n\n\t// \tprotected void a_viewStates()\n\t// \t{\n\t// \t\thandler.requestViewStates();\n\t// \t}\n\n\tprotected void a_viewCurrentModelBuild()\n\t{\n\t\thandler.requestViewModel();\n\t}\n\n\tprotected void a_exportSteadyState(ModelExportFormat exportFormat)\n\t{\n\t\t// Pop up dialog to select file\n\t\tint res = JFileChooser.CANCEL_OPTION;\n\t\tswitch (exportFormat) {\n\t\t\tcase MATLAB:\n\t\t\t\tres = showSaveFileDialog(matlabFilter);\n\t\t\t\tbreak;\n\t\t\tcase EXPLICIT:\n\t\t\tdefault:\n\t\t\t\tres = showSaveFileDialog(textFilter);\n\t\t\t\tbreak;\n\t\t}\n\t\tif (res != JFileChooser.APPROVE_OPTION) {\n\t\t\treturn;\n\t\t}\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Do steady-state\n\t\thandler.computeSteadyState(new ModelExportTask(ModelExportEntity.MODEL, getChooserFile(), new ModelExportOptions(exportFormat)));\n\t}\n\n\tprotected void a_computeSteadyState()\n\t{\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Do steady-state\n\t\thandler.computeSteadyState(new ModelExportTask(ModelExportEntity.MODEL, (File) null, new ModelExportOptions(ModelExportFormat.EXPLICIT)));\n\t}\n\n\tprotected void a_exportTransient(ModelExportFormat exportFormat)\n\t{\n\t\t// Get time\n\t\tint result = GUITransientTime.requestTime(this.getGUI());\n\t\tif (result != GUITransientTime.OK)\n\t\t\treturn;\n\t\t// Pop up dialog to select file\n\t\tint res = JFileChooser.CANCEL_OPTION;\n\t\tswitch (exportFormat) {\n\t\t\tcase MATLAB:\n\t\t\t\tres = showSaveFileDialog(matlabFilter);\n\t\t\t\tbreak;\n\t\t\tcase EXPLICIT:\n\t\t\tdefault:\n\t\t\t\tres = showSaveFileDialog(textFilter);\n\t\t\t\tbreak;\n\t\t}\n\t\tif (res != JFileChooser.APPROVE_OPTION) {\n\t\t\treturn;\n\t\t}\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Do transient\n\t\thandler.computeTransient(GUITransientTime.getTimeSpec(), new ModelExportTask(ModelExportEntity.MODEL, getChooserFile(), new ModelExportOptions(exportFormat)));\n\t}\n\n\tprotected void a_computeTransient()\n\t{\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Get time\n\t\tint result = GUITransientTime.requestTime(this.getGUI());\n\t\tif (result != GUITransientTime.OK)\n\t\t\treturn;\n\t\t// Do transient\n\t\thandler.computeTransient(GUITransientTime.getTimeSpec(), new ModelExportTask(ModelExportEntity.MODEL, (File) null, new ModelExportOptions(ModelExportFormat.EXPLICIT)));\n\t}\n\n\tprotected void a_convertToPrismTextModel()\n\t{\n\t\tint cont = doModificationCheck();\n\t\tif (cont == CONTINUE && (handler.getModelMode() != GUIMultiModelHandler.PRISM_MODE)) {\n\t\t\tString[] selection = { \"Yes\", \"No\", \"Cancel\" };\n\t\t\tint selectionNo = -1;\n\t\t\tselectionNo = optionPane(\"WARNING: This is a one way operation. Continue?\", \"Question\", JOptionPane.OK_CANCEL_OPTION, JOptionPane.QUESTION_MESSAGE,\n\t\t\t\t\tselection, selection[0]);\n\t\t\tswitch (selectionNo) {\n\t\t\tcase 0:\n\t\t\t\thandler.convertViewToPRISM();\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\tprivate void setupActions()\n\t{\n\t\tnewPRISMModel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_newPRISMModel();\n\t\t\t}\n\t\t};\n\t\tnewPRISMModel.putValue(Action.LONG_DESCRIPTION, \"Removes the current build, and loads a new model editor in PRISM Text Model mode.\");\n\t\t//newPRISMModel.putValue(Action.SHORT_DESCRIPTION, \"New PRISM Text Model\");\n\t\tnewPRISMModel.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_P));\n\t\tnewPRISMModel.putValue(Action.NAME, \"PRISM model\");\n\t\tnewPRISMModel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFilePrism.png\"));\n\t\tnewPRISMModel.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_N, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\n\t\tnewPEPAModel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\t//modified check do later\n\t\t\t\ta_newPEPAModel();\n\t\t\t}\n\t\t};\n\t\tnewPEPAModel.putValue(Action.LONG_DESCRIPTION, \"Removes the current build, and loads a new model editor in PEPA Text Model mode.\");\n\t\t//newPEPAModel.putValue(Action.SHORT_DESCRIPTION, \"New PEPA Text Model\");\n\t\tnewPEPAModel.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_E));\n\t\tnewPEPAModel.putValue(Action.NAME, \"PEPA model\");\n\t\tnewPEPAModel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFilePepa.png\"));\n\n\t\tloadModel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\t//do actions later\n\t\t\t\t//System.out.println(\"realised open action\");\n\t\t\t\ta_openModel();\n\n\t\t\t}\n\t\t};\n\t\tloadModel\n\t\t\t\t.putValue(\n\t\t\t\t\t\tAction.LONG_DESCRIPTION,\n\t\t\t\t\t\t\"Brings up a file loading dialogue and loads the file into the editor.  The editor will change mode according to the format of the file.  The loaded file is active for saving.\");\n\t\t//loadModel.putValue(Action.SHORT_DESCRIPTION, \"Open Model\");\n\t\tloadModel.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_O));\n\t\tloadModel.putValue(Action.NAME, \"Open model...\");\n\t\t//loadModel.putValue(Action.ACTION_COMMAND_KEY,\n\t\tloadModel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallOpen.png\"));\n\t\tloadModel.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_O, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\n\t\treloadModel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_reloadModel();\n\t\t\t}\n\t\t};\n\t\treloadModel.putValue(Action.LONG_DESCRIPTION, \"Reloads the current active file.\");\n\t\t//reloadModel.putValue(Action.SHORT_DESCRIPTION, \"Reload Model\");\n\t\treloadModel.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_R));\n\t\treloadModel.putValue(Action.NAME, \"Reload model\");\n\t\t//loadModel.putValue(Action.ACTION_COMMAND_KEY,\n\t\treloadModel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallReload.png\"));\n\t\treloadModel.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_R, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\n\t\tsaveModel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_saveModel();\n\t\t\t}\n\t\t};\n\t\tsaveModel.putValue(Action.LONG_DESCRIPTION,\n\t\t\t\t\"Brings up a file saving dialogue and saves the current text editor to the active file or to a new file.  The saved file becomes active\");\n\t\t//saveModel.putValue(Action.SHORT_DESCRIPTION, \"Save Model\");\n\t\tsaveModel.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n\t\tsaveModel.putValue(Action.NAME, \"Save model\");\n\t\tsaveModel.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_S, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\t\t//saveModel.putValue(Action.ACTION_COMMAND_KEY,\n\t\tsaveModel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSave.png\"));\n\n\t\tsaveAsModel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_saveModelAs();\n\t\t\t}\n\t\t};\n\t\tsaveAsModel.putValue(Action.LONG_DESCRIPTION,\n\t\t\t\t\"Brings up a file saving dialogue and saves the current text editor to a new file.  The saved file becomes active\");\n\t\t//saveAsModel.putValue(Action.SHORT_DESCRIPTION, \"Save Model As...\");\n\t\tsaveAsModel.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_A));\n\t\tsaveAsModel.putValue(Action.NAME, \"Save model as...\");\n\t\t//saveAsModel.putValue(Action.ACTION_COMMAND_KEY,\n\t\tsaveAsModel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSaveAs.png\"));\n\n\t\tparseModel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_refreshParseTree();\n\t\t\t}\n\t\t};\n\t\tparseModel.putValue(Action.LONG_DESCRIPTION, \"Forces a parse of the model in the editor.  The parsed description is shown in the model tree.\");\n\t\t//parseModel.putValue(Action.SHORT_DESCRIPTION, \"Parse Model\");\n\t\tparseModel.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_P));\n\t\tparseModel.putValue(Action.NAME, \"Parse model\");\n\t\tparseModel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallParse.png\"));\n\t\tparseModel.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F2, 0));\n\t\tbuildModel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_build();\n\t\t\t}\n\t\t};\n\t\tbuildModel.putValue(Action.LONG_DESCRIPTION, \"Builds the model that has been parsed.\");\n\t\t//buildModel.putValue(Action.SHORT_DESCRIPTION, \"Build Model\");\n\t\tbuildModel.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_B));\n\t\tbuildModel.putValue(Action.NAME, \"Build model\");\n\t\tbuildModel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallBuild.png\"));\n\t\tbuildModel.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F3, 0));\n\n\t\texportStatesPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.STATES, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportStatesPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the states to a plain text file\");\n\t\texportStatesPlain.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n\t\texportStatesPlain.putValue(Action.NAME, \"States\");\n\t\texportStatesPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportStatesMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.STATES, ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportStatesMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the states to a Matlab file\");\n\t\texportStatesMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n\t\texportStatesMatlab.putValue(Action.NAME, \"States\");\n\t\texportStatesMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportTransPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.MODEL, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportTransPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the transition matrix to a plain text file\");\n\t\texportTransPlain.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_T));\n\t\texportTransPlain.putValue(Action.NAME, \"Transition matrix\");\n\t\texportTransPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportTransMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.MODEL, ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportTransMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the transition matrix to a Matlab file\");\n\t\texportTransMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_T));\n\t\texportTransMatlab.putValue(Action.NAME, \"Transition matrix\");\n\t\texportTransMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportTransDot = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.MODEL, ModelExportFormat.DOT);\n\t\t\t}\n\t\t};\n\t\texportTransDot.putValue(Action.LONG_DESCRIPTION, \"Exports the model to a Dot file\");\n\t\texportTransDot.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_D));\n\t\texportTransDot.putValue(Action.NAME, \"Dot\");\n\t\texportTransDot.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileDot.png\"));\n\n\t\texportTransUMB = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.MODEL, ModelExportFormat.UMB);\n\t\t\t}\n\t\t};\n\t\texportTransUMB.putValue(Action.LONG_DESCRIPTION, \"Exports the model to a UMB file\");\n\t\texportTransUMB.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_D));\n\t\texportTransUMB.putValue(Action.NAME, \"UMB\");\n\t\texportTransUMB.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportObsPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.OBSERVATIONS, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportObsPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the observations to a plain text file\");\n\t\texportObsPlain.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_O));\n\t\texportObsPlain.putValue(Action.NAME, \"Observations\");\n\t\texportObsPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportObsMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.OBSERVATIONS, ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportObsMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the observations to a Matlab file\");\n\t\texportObsMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_O));\n\t\texportObsMatlab.putValue(Action.NAME, \"Observations\");\n\t\texportObsMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportStateRewardsPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.STATE_REWARDS, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportStateRewardsPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the state rewards vector to a plain text file\");\n\t\texportStateRewardsPlain.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_R));\n\t\texportStateRewardsPlain.putValue(Action.NAME, \"State rewards\");\n\t\texportStateRewardsPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportStateRewardsMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.STATE_REWARDS, ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportStateRewardsMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the state rewards vector to a Matlab file\");\n\t\texportStateRewardsMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_R));\n\t\texportStateRewardsMatlab.putValue(Action.NAME, \"State rewards\");\n\t\texportStateRewardsMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportTransRewardsPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.STATE_REWARDS, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportTransRewardsPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the transition rewards matrix to a plain text file\");\n\t\texportTransRewardsPlain.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_E));\n\t\texportTransRewardsPlain.putValue(Action.NAME, \"Transition rewards\");\n\t\texportTransRewardsPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportTransRewardsMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.TRANSITION_REWARDS, ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportTransRewardsMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the transition rewards matrix to a Matlab file\");\n\t\texportTransRewardsMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_E));\n\t\texportTransRewardsMatlab.putValue(Action.NAME, \"Transition rewards\");\n\t\texportTransRewardsMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportLabelsPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.LABELS, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportLabelsPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the model's labels and their satisfying states to a plain text file\");\n\t\texportLabelsPlain.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_L));\n\t\texportLabelsPlain.putValue(Action.NAME, \"Labels\");\n\t\texportLabelsPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportLabelsMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportBuildAs(ModelExportEntity.LABELS, ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportLabelsMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the model's labels and their satisfying states to a Matlab file\");\n\t\texportLabelsMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_L));\n\t\texportLabelsMatlab.putValue(Action.NAME, \"Labels\");\n\t\texportLabelsMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\tcomputeSS = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_computeSteadyState();\n\t\t\t}\n\t\t};\n\t\tcomputeSS.putValue(Action.LONG_DESCRIPTION, \"Computes steady-state probabilities for the model\");\n\t\t//computeSS.putValue(Action.SHORT_DESCRIPTION, \"Compute steady-state probabilities\");\n\t\tcomputeSS.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n\t\tcomputeSS.putValue(Action.NAME, \"Steady-state probabilities\");\n\t\tcomputeSS.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSteadyState.png\"));\n\t\tcomputeSS.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F4, 0));\n\n\t\tcomputeTr = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_computeTransient();\n\t\t\t}\n\t\t};\n\t\tcomputeTr.putValue(Action.LONG_DESCRIPTION, \"Computes transient probabilities for the model\");\n\t\t//computeTr.putValue(Action.SHORT_DESCRIPTION, \"Compute transient probabilities\");\n\t\tcomputeTr.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_T));\n\t\tcomputeTr.putValue(Action.NAME, \"Transient probabilities\");\n\t\tcomputeTr.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallClockAnim1.png\"));\n\t\tcomputeTr.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F4, KeyEvent.CTRL_DOWN_MASK));\n\n\t\texportSSPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportSteadyState(ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportSSPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the steady-state probabilities to a plain text file\");\n\t\texportSSPlain.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_P));\n\t\texportSSPlain.putValue(Action.NAME, \"Plain text file\");\n\t\texportSSPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileText.png\"));\n\n\t\texportSSMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportSteadyState(ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportSSMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the steady-state probabilities to a Matlab file\");\n\t\texportSSMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_M));\n\t\texportSSMatlab.putValue(Action.NAME, \"Matlab file\");\n\t\texportSSMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileMatlab.png\"));\n\n\t\texportTrPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportTransient(ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportTrPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the transient probabilities to a plain text file\");\n\t\texportTrPlain.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_P));\n\t\texportTrPlain.putValue(Action.NAME, \"Plain text file\");\n\t\texportTrPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileText.png\"));\n\n\t\texportTrMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportTransient(ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportTrMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the transient probabilities to a Matlab file\");\n\t\texportTrMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_M));\n\t\texportTrMatlab.putValue(Action.NAME, \"Matlab file\");\n\t\texportTrMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileMatlab.png\"));\n\n\t\tviewStates = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewBuild(ModelExportEntity.STATES, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\tviewStates.putValue(Action.LONG_DESCRIPTION, \"Print the reachable states to the log\");\n\t\tviewStates.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n\t\tviewStates.putValue(Action.NAME, \"States\");\n\t\tviewStates.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\tviewTrans = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewBuild(ModelExportEntity.MODEL, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\tviewTrans.putValue(Action.LONG_DESCRIPTION, \"Print the transition matrix to the log\");\n\t\tviewTrans.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_T));\n\t\tviewTrans.putValue(Action.NAME, \"Transition matrix\");\n\t\tviewTrans.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\tviewObs = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewBuild(ModelExportEntity.OBSERVATIONS, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\tviewObs.putValue(Action.LONG_DESCRIPTION, \"Print the observations to the log\");\n\t\tviewObs.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n\t\tviewObs.putValue(Action.NAME, \"Observations\");\n\t\tviewObs.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\tviewStateRewards = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewBuild(ModelExportEntity.STATE_REWARDS, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\tviewStateRewards.putValue(Action.LONG_DESCRIPTION, \"Print the state rewards to the log\");\n\t\tviewStateRewards.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_R));\n\t\tviewStateRewards.putValue(Action.NAME, \"State rewards\");\n\t\tviewStateRewards.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\tviewTransRewards = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewBuild(ModelExportEntity.TRANSITION_REWARDS, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\tviewTransRewards.putValue(Action.LONG_DESCRIPTION, \"Print the transition rewards to the log\");\n\t\tviewTransRewards.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_E));\n\t\tviewTransRewards.putValue(Action.NAME, \"Transition rewards\");\n\t\tviewTransRewards.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\tviewLabels = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewBuild(ModelExportEntity.LABELS, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\tviewLabels.putValue(Action.LONG_DESCRIPTION, \"Print the labels and satisfying states to the log\");\n\t\tviewLabels.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_L));\n\t\tviewLabels.putValue(Action.NAME, \"Labels\");\n\t\tviewLabels.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\tviewPrismCode = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewCurrentModelBuild();\n\t\t\t}\n\t\t};\n\t\tviewPrismCode.putValue(Action.LONG_DESCRIPTION, \"This shows the parsed model in a text editor.\");\n\t\tviewPrismCode.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_V));\n\t\tviewPrismCode.putValue(Action.NAME, \"Parsed PRISM model\");\n\t\tviewPrismCode.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFilePrism.png\"));\n\t}\n\n\t//Required to be a GUIPlugin:\n\n\tpublic boolean displaysTab()\n\t{\n\t\treturn true;\n\t}\n\n\tpublic JMenu getMenu()\n\t{\n\t\treturn modelMenu;\n\t}\n\n\tpublic String getTabText()\n\t{\n\t\treturn \"Model\";\n\t}\n\n\tpublic JToolBar getToolBar()\n\t{\n\t\treturn null;\n\t}\n\n\tpublic String getXMLIDTag()\n\t{\n\t\treturn \"\";\n\t}\n\n\tpublic Object getXMLSaveTree()\n\t{\n\t\treturn null;\n\t}\n\n\tpublic void loadXML(Object c)\n\t{\n\n\t}\n\n\t// if return value is true, event should not be passed on to any more listeners\n\n\tpublic boolean processGUIEvent(GUIEvent e)\n\t{\n\t\tif (e instanceof userinterface.properties.GUIPropertiesEvent) {\n\t\t\tif (e.getID() == userinterface.properties.GUIPropertiesEvent.REQUEST_MODEL_PARSE) {\n\t\t\t\thandler.requestParse(false);\n\t\t\t}\n\t\t} else if (e instanceof GUIClipboardEvent && super.getGUI().getFocussedPlugin() == this) {\n\t\t\tGUIClipboardEvent ce = (GUIClipboardEvent) e;\n\t\t\tif (ce.getComponent() == this) {\n\t\t\t\tint id = ce.getID();\n\t\t\t\tif (id == GUIClipboardEvent.CUT)\n\t\t\t\t\thandler.cut();\n\t\t\t\telse if (id == GUIClipboardEvent.COPY)\n\t\t\t\t\thandler.copy();\n\t\t\t\telse if (id == GUIClipboardEvent.PASTE)\n\t\t\t\t\thandler.paste();\n\t\t\t\telse if (id == GUIClipboardEvent.DELETE)\n\t\t\t\t\thandler.delete();\n\t\t\t\telse if (id == GUIClipboardEvent.SELECT_ALL)\n\t\t\t\t\thandler.selectAll();\n\t\t\t\telse if (id == GUIClipboardEvent.UNDO)\n\t\t\t\t\thandler.undo();\n\t\t\t\telse if (id == GUIClipboardEvent.REDO)\n\t\t\t\t\thandler.redo();\n\n\t\t\t}\n\t\t} else if (e instanceof GUIComputationEvent) {\n\t\t\tif (e.getID() == GUIComputationEvent.COMPUTATION_START) {\n\t\t\t\tcomputing = true;\n\t\t\t\tdoEnables();\n\t\t\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t\t\t} else if (e.getID() == GUIComputationEvent.COMPUTATION_DONE) {\n\t\t\t\tcomputing = false;\n\t\t\t\tdoEnables();\n\t\t\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t\t\t} else if (e.getID() == GUIComputationEvent.COMPUTATION_ERROR) {\n\t\t\t\tcomputing = false;\n\t\t\t\tdoEnables();\n\t\t\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t\t\t}\n\t\t} else if (e instanceof GUIExitEvent) {\n\t\t\tif (e.getID() == GUIExitEvent.REQUEST_EXIT) {\n\t\t\t\tif (doModificationCheck() != CONTINUE) {\n\t\t\t\t\tnotifyEventListeners(new GUIExitEvent(GUIExitEvent.CANCEL_EXIT));\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\tprivate JMenu initExportMenu()\n\t{\n\t\tJMenu exportMenu = new JMenu(\"Export\");\n\t\texportMenu.setMnemonic('E');\n\t\texportMenu.setIcon(GUIPrism.getIconFromImage(\"smallExport.png\"));\n\t\tJMenu exportPlainMenu = new JMenu(\"Plain text\");\n\t\texportPlainMenu.setMnemonic('P');\n\t\texportPlainMenu.setIcon(GUIPrism.getIconFromImage(\"smallFileText.png\"));\n\t\texportPlainMenu.add(exportTransPlain);\n\t\texportPlainMenu.add(exportStateRewardsPlain);\n\t\texportPlainMenu.add(exportTransRewardsPlain);\n\t\texportPlainMenu.add(exportLabelsPlain);\n\t\texportPlainMenu.add(exportStatesPlain);\n\t\texportPlainMenu.add(exportObsPlain);\n\t\texportMenu.add(exportPlainMenu);\n\t\texportMenu.add(exportTransDot);\n\t\texportMenu.add(exportTransUMB);\n\t\tJMenu exportMatlabMenu = new JMenu(\"Matlab\");\n\t\texportMatlabMenu.setMnemonic('M');\n\t\texportMatlabMenu.setIcon(GUIPrism.getIconFromImage(\"smallFileMatlab.png\"));\n\t\texportMatlabMenu.add(exportTransMatlab);\n\t\texportMatlabMenu.add(exportStateRewardsMatlab);\n\t\texportMatlabMenu.add(exportTransRewardsMatlab);\n\t\texportMatlabMenu.add(exportLabelsMatlab);\n\t\texportMatlabMenu.add(exportStatesMatlab);\n\t\texportMatlabMenu.add(exportObsMatlab);\n\t\texportMenu.add(exportMatlabMenu);\n\t\treturn exportMenu;\n\t}\n\n\tprivate JMenu initViewMenu()\n\t{\n\t\tJMenu viewMenu = new JMenu(\"View\");\n\t\tviewMenu.setMnemonic('V');\n\t\tviewMenu.setIcon(GUIPrism.getIconFromImage(\"smallView.png\"));\n\t\tviewMenu.add(viewStates);\n\t\tviewMenu.add(viewTrans);\n\t\tviewMenu.add(viewObs);\n\t\tviewMenu.add(viewStateRewards);\n\t\tviewMenu.add(viewTransRewards);\n\t\tviewMenu.add(viewLabels);\n\t\tviewMenu.add(viewPrismCode);\n\t\treturn viewMenu;\n\t}\n\n\tprivate JMenu initComputeMenu()\n\t{\n\t\tJMenu computeMenu = new JMenu(\"Compute\");\n\t\tcomputeMenu.setMnemonic('C');\n\t\tcomputeMenu.setIcon(GUIPrism.getIconFromImage(\"smallCompute.png\"));\n\t\tcomputeMenu.add(computeSS);\n\t\tcomputeMenu.add(computeTr);\n\t\treturn computeMenu;\n\t}\n\n\tprivate JMenu initComputeExportMenu()\n\t{\n\t\tJMenu computeExportMenu = new JMenu(\"Compute/export\");\n\t\tcomputeExportMenu.setMnemonic('X');\n\t\tcomputeExportMenu.setIcon(GUIPrism.getIconFromImage(\"smallCompute.png\"));\n\t\texportSSMenu = new JMenu(\"Steady-state probabilities\");\n\t\texportSSMenu.setMnemonic('S');\n\t\texportSSMenu.setIcon(GUIPrism.getIconFromImage(\"smallSteadyState.png\"));\n\t\texportSSMenu.add(exportSSPlain);\n\t\texportSSMenu.add(exportSSMatlab);\n\t\tcomputeExportMenu.add(exportSSMenu);\n\t\texportTrMenu = new JMenu(\"Transient probabilities\");\n\t\texportTrMenu.setMnemonic('A');\n\t\texportTrMenu.setIcon(GUIPrism.getIconFromImage(\"smallClockAnim1.png\"));\n\t\texportTrMenu.add(exportTrPlain);\n\t\texportTrMenu.add(exportTrMatlab);\n\t\tcomputeExportMenu.add(exportTrMenu);\n\t\treturn computeExportMenu;\n\t}\n\n\tprivate void initComponents()\n\t{\n\t\tsetupActions();\n\n\t\tmodelMenu = new JMenu(\"Model\");\n\t\texportMenu = initExportMenu();\n\t\tviewMenu = initViewMenu();\n\t\tcomputeMenu = initComputeMenu();\n\t\tcomputeExportMenu = initComputeExportMenu();\n\n\t\tJPanel topPanel = new JPanel();\n\t\t{\n\t\t\tfileTextField = new JTextField();\n\t\t\t{\n\t\t\t\tfileTextField.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n\t\t\t\tfileTextField.setBorder(new javax.swing.border.EtchedBorder());\n\t\t\t\tfileTextField.setMinimumSize(new java.awt.Dimension(40, 25));\n\t\t\t\tfileTextField.setEditable(false);\n\t\t\t\tfileTextField.setBackground(null);\n\t\t\t}\n\n\t\t\t//progress = new JProgressBar(0, 100);\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\thandler = new GUIMultiModelHandler(this);\n\t\t\t//topPanel.add(progress, BorderLayout.WEST);\n\t\t\ttopPanel.add(fileTextField, BorderLayout.NORTH);\n\t\t\ttopPanel.add(handler, BorderLayout.CENTER);\n\t\t}\n\n\t\tnewMenu = new JMenu(\"New\");\n\t\tnewMenu.setMnemonic('N');\n\t\tnewMenu.setIcon(GUIPrism.getIconFromImage(\"smallNew.png\"));\n\t\tnewMenu.add(newPRISMModel);\n\t\tnewMenu.add(newPEPAModel);\n\t\tmodelMenu.add(newMenu);\n\t\tmodelMenu.add(new JSeparator());\n\t\tmodelMenu.add(loadModel);\n\t\tmodelMenu.add(reloadModel);\n\t\tmodelMenu.add(new JSeparator());\n\t\tmodelMenu.add(saveModel);\n\t\tmodelMenu.add(saveAsModel);\n\t\tmodelMenu.add(new JSeparator());\n\t\tmodelMenu.setMnemonic(KeyEvent.VK_M);\n\t\tmodelMenu.add(parseModel);\n\t\tmodelMenu.add(buildModel);\n\t\tmodelMenu.add(new JSeparator());\n\n\t\tmodelMenu.add(exportMenu);\n\n\t\tmodelMenu.add(viewMenu);\n\n\t\tmodelMenu.add(computeMenu);\n\n\t\tmodelMenu.add(computeExportMenu);\n\n\t\tpopup = new JPopupMenu();\n\t\t{\n\t\t\tpopup.add(parseModel);\n\t\t\tpopup.add(buildModel);\n\t\t\tpopup.add(viewPrismCode);\n\t\t}\n\n\t\tmodelFilters = new HashMap<String,FileFilter>();\n\t\tmodelFilters.put(\"prism\", new FileNameExtensionFilter(\"PRISM models (*.prism, *.pm, *.nm, *.sm)\", \"prism\", \"pm\", \"nm\", \"sm\")); \n\t\tmodelFilters.put(\"pepa\", new FileNameExtensionFilter(\"PEPA models (*.pepa)\", \"pepa\"));\n\t\tstaFilters = new HashMap<String,FileFilter>();\n\t\tstaFilters.put(\"sta\", new FileNameExtensionFilter(\"State list files (*.sta)\", \"sta\"));\n\t\tstaFilters.put(\"txt\", new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\"));\n\t\tobsFilters = new HashMap<String,FileFilter>();\n\t\tobsFilters.put(\"obs\", new FileNameExtensionFilter(\"Observations files (*.obs)\", \"obs\"));\n\t\tobsFilters.put(\"txt\", new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\"));\n\t\ttraFilters = new HashMap<String,FileFilter>();\n\t\ttraFilters.put(\"tra\", new FileNameExtensionFilter(\"Transition matrix files (*.tra)\", \"tra\"));\n\t\ttraFilters.put(\"txt\", new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\"));\n\t\tlabFilters = new HashMap<String,FileFilter>();\n\t\tlabFilters.put(\"lab\", new FileNameExtensionFilter(\"Label files (*.lab)\", \"lab\"));\n\t\tlabFilters.put(\"txt\", new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\"));\n\t\ttextFilter =  new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\");\n\t\tmatlabFilter = new FileNameExtensionFilter(\"Matlab files (*.m)\", \"m\");\n\t\tdotFilter = new FileNameExtensionFilter(\"Dot files (*.dot)\", \"dot\");\n\t\tumbFilter = new FileNameExtensionFilter(\"UMB files (*.umb)\", \"dot\");\n\n\t\tsetLayout(new BorderLayout());\n\t\tadd(topPanel, BorderLayout.CENTER);\n\n\t\tdoEnables();\n\t}\n\n\tpublic void notifySettings(PrismSettings settings)\n\t{\n\t\t//System.out.println(\"model notifySettings called\");\n\t\thandler.notifySettings(settings);\n\n\t\trepaint();\n\t}\n\n\t@Override\n\tpublic GUIUndoManager getUndoManager()\n\t{\n\t\treturn handler.getUndoManager();\n\t}\n\n\t@Override\n\tpublic boolean canDoClipBoardAction(Action action)\n\t{\n\t\tif (computing)\n\t\t\treturn false;\n\n\t\treturn handler.canDoClipBoardAction(action);\n\t}\n\n\tpublic AbstractAction getParseModel()\n\t{\n\t\treturn parseModel;\n\t}\n\n\tpublic AbstractAction getBuildModel()\n\t{\n\t\treturn buildModel;\n\t}\n\n\tpublic JMenu getViewMenu()\n\t{\n\t\treturn initViewMenu();\n\t}\n\n\tpublic JMenu getExportMenu()\n\t{\n\t\treturn initExportMenu();\n\t}\n\n\tpublic JMenu getComputeMenu()\n\t{\n\t\treturn initComputeMenu();\n\t}\n\n\tpublic JMenu getComputeExportMenu()\n\t{\n\t\treturn initComputeExportMenu();\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/GUIMultiModelHandler.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport java.awt.BorderLayout;\nimport java.awt.Color;\nimport java.awt.Font;\nimport java.awt.GridLayout;\nimport java.io.File;\nimport java.io.FileWriter;\nimport java.io.IOException;\n\nimport javax.swing.Action;\nimport javax.swing.JLabel;\nimport javax.swing.JPanel;\nimport javax.swing.JSplitPane;\nimport javax.swing.SwingUtilities;\nimport javax.swing.border.CompoundBorder;\nimport javax.swing.border.EmptyBorder;\nimport javax.swing.border.TitledBorder;\n\nimport io.ModelExportTask;\nimport parser.Values;\nimport parser.ast.ModulesFile;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismModelListener;\nimport prism.PrismSettings;\nimport prism.UndefinedConstants;\nimport userinterface.GUIConstantsPicker;\nimport userinterface.GUIPlugin;\nimport userinterface.model.computation.BuildModelThread;\nimport userinterface.model.computation.ComputeSteadyStateThread;\nimport userinterface.model.computation.ComputeTransientThread;\nimport userinterface.model.computation.ExportBuiltModelThread;\nimport userinterface.model.computation.LoadPEPAModelThread;\nimport userinterface.model.computation.LoadPRISMModelThread;\nimport userinterface.model.computation.ParseModelThread;\nimport userinterface.model.pepaModel.GUIPepaModelEditor;\nimport userinterface.util.GUIUndoManager;\n\n@SuppressWarnings(\"serial\")\npublic class GUIMultiModelHandler extends JPanel implements PrismModelListener\n{\n\t//Constants\n\tpublic static final int PRISM_MODE = 1;\n\tpublic static final int PEPA_MODE = 2;\n\n\tprivate GUIMultiModel theModel;\n\tprivate GUIMultiModelTree tree;\n\tprivate GUIModelEditor editor;\n\tprivate Prism prism;\n\n\t// State\n\tprivate int currentMode;\n\tprivate boolean modified;\n\tprivate boolean modifiedSinceParse;\n\tprivate File activeFile;\n\tprivate ModulesFile parsedModel;\n\tprivate Values lastMFConstants = null;\n\tprivate PrismException lastBuildError = null;\n\tprivate boolean busy = false;\n\n\t// Options\n\tprivate boolean autoParse;\n\n\tprivate Font prismEditorFontFast;\n\tprivate Color prismEditorColourFast;\n\tprivate Color prismEditorBGColourFast;\n\n\tprivate Style prismEditorNumericFast = Style.defaultStyle();\n\tprivate Style prismEditorVariableFast = Style.defaultStyle();\n\tprivate Style prismEditorKeywordFast = Style.defaultStyle();\n\tprivate Style prismEditorCommentFast = Style.defaultStyle();\n\n\tprivate Font pepaEditorFontFast;\n\tprivate Color pepaEditorColourFast;\n\tprivate Color pepaEditorBGColourFast;\n\n\tprivate Style pepaEditorCommentFast = Style.defaultStyle();\n\n\t// flag to indicate whether onInitComponentsCompleted() has already been called\n\tprivate boolean startupCompleted = false;\n\n\t// Modification Parse updater\n\tprivate WaitParseThread waiter;\n\tprivate boolean parsing = false;\n\tprivate boolean parseAfterParse = false;\n\n\tprivate String lastError;\n\n\tprivate boolean buildAfterReceiveParseNotification = false;\n\tprivate boolean exportAfterReceiveParseNotification = false;\n\tprivate boolean computeSSAfterReceiveParseNotification = false;\n\tprivate boolean computeTransientAfterReceiveParseNotification = false;\n\tprivate ModelExportTask exportTask;\n\tprivate String transientTimeSpec;\n\n\t// GUI\n\tprivate JSplitPane splitter;\n\tprivate JPanel leftHandSide, treeAndBuild;\n\tprivate JLabel builtNoStates, builtNoInitStates, builtNoTransitions;\n\n\t/** Creates a new instance of GUIMultiModelHandler */\n\tpublic GUIMultiModelHandler(GUIMultiModel theModel)\n\t{\n\t\tsuper();\n\t\tthis.theModel = theModel;\n\t\tprism = theModel.getPrism();\n\t\tprism.addModelListener(this);\n\n\t\teditor = new GUITextModelEditor(\"\", this);\n\t\ttree = new GUIMultiModelTree(this);\n\t\tsplitter = new JSplitPane();\n\n\t\tinitComponents();\n\t\tnewPRISMModel();\n\t\t//splitter.setDividerLocation(0);\n\t\t//splitter.setLastDividerLocation(200);\n\n\t\tnotifySettings(theModel.getPrism().getSettings());\n\n\t\tsplitter.setBorder(null);\n\n\t\tsetBorder(new EmptyBorder(5, 5, 5, 5));\n\t}\n\n\t// Initialisation of GUI components\n\tprivate void initComponents()\n\t{\n\t\ttreeAndBuild = new JPanel();\n\t\tJPanel topLeft = new JPanel();\n\t\ttopLeft.setLayout(new BorderLayout());\n\t\ttopLeft.add(tree, BorderLayout.CENTER);\n\t\tJPanel innerBottomLeft = new JPanel(new BorderLayout());\n\t\tinnerBottomLeft.setBorder(new CompoundBorder(new EmptyBorder(5, 0, 0, 0), new TitledBorder(\"Built Model\")));\n\t\t//JToolBar bar = new JToolBar();\n\t\t//bar.setFloatable(false);\n\t\t//JButton but = new JButton(buildModel);\n\t\t//but.setText(\"Build Model\");\n\t\t//bar.add(but);\n\t\t//bar.add(buildModel);\n\t\tJPanel buildPane = new JPanel(new GridLayout(3, 2, 5, 5));\n\n\t\tJLabel statesLabel = new JLabel(\"States:\");\n\t\tstatesLabel.setFont(statesLabel.getFont().deriveFont(Font.BOLD));\n\t\tstatesLabel.setHorizontalAlignment(JLabel.RIGHT);\n\n\t\tbuiltNoStates = new JLabel(\"...\");\n\n\t\tJLabel initStatesLabel = new JLabel(\"Initial states:\");\n\t\tinitStatesLabel.setFont(initStatesLabel.getFont().deriveFont(Font.BOLD));\n\t\tinitStatesLabel.setHorizontalAlignment(JLabel.RIGHT);\n\n\t\tbuiltNoInitStates = new JLabel(\"...\");\n\n\t\tJLabel transLabel = new JLabel(\"Transitions:\");\n\t\ttransLabel.setFont(transLabel.getFont().deriveFont(Font.BOLD));\n\t\ttransLabel.setHorizontalAlignment(JLabel.RIGHT);\n\n\t\tbuiltNoTransitions = new JLabel(\"...\");\n\n\t\tbuildPane.add(statesLabel);\n\t\tbuildPane.add(builtNoStates);\n\t\tbuildPane.add(initStatesLabel);\n\t\tbuildPane.add(builtNoInitStates);\n\t\tbuildPane.add(transLabel);\n\t\tbuildPane.add(builtNoTransitions);\n\n\t\t//buildPane.setPreferredSize(new Dimension(250, 40));\n\t\t//buildPane.setMaximumSize(new Dimension(2000, 40));\n\t\tbuildPane.setBorder(new EmptyBorder(5, 5, 5, 5));\n\t\t//bottomLeft.add(bar, BorderLayout.NORTH);\n\t\tinnerBottomLeft.add(buildPane, BorderLayout.CENTER);\n\t\ttreeAndBuild.setLayout(new BorderLayout());\n\t\ttreeAndBuild.add(topLeft, BorderLayout.CENTER);\n\t\ttreeAndBuild.add(innerBottomLeft, BorderLayout.SOUTH);\n\t\ttreeAndBuild.setBorder(new EmptyBorder(0, 0, 0, 5));\n\t\tsplitter.setOrientation(JSplitPane.HORIZONTAL_SPLIT);\n\n\t\tleftHandSide = new JPanel();\n\t\tleftHandSide.setLayout(new BorderLayout());\n\t\tleftHandSide.add(treeAndBuild, BorderLayout.CENTER);\n\n\t\tsplitter.setLeftComponent(leftHandSide);\n\t\tsplitter.setRightComponent(editor);\n\t\tsplitter.setDividerLocation(0.5);\n\t\tsplitter.setOneTouchExpandable(true);\n\t\tsetLayout(new BorderLayout());\n\t\tadd(splitter, BorderLayout.CENTER);\n\t}\n\n\tprivate synchronized void restartWaitParseThread()\n\t{\n\t\t// If the GUIPrism startup has not been completed, as\n\t\t// indicated by the call to onInitComponentsCompleted(),\n\t\t// ignore requests to start the WaitParseThread. This prevents\n\t\t// it from triggering events that are handled by parts of the\n\t\t// GUI that have not been completely initialised.\n\t\tif (!startupCompleted)\n\t\t\treturn;\n\n\t\t// Don't trigger parsing if the text field is empty\n\t\tif (editor.getParseText().trim().isEmpty())\n\t\t\treturn;\n\t\t\n\t\tif (waiter != null) {\n\t\t\twaiter.interrupt();\n\t\t}\n\t\tint parseDelay = theModel.getPrism().getSettings().getInteger(PrismSettings.MODEL_PARSE_DELAY);\n\t\twaiter = new WaitParseThread(parseDelay, this);\n\t\twaiter.start();\n\t\t//Funky thread waiting stuff\n\t}\n\n\tpublic void onInitComponentsCompleted()\n\t{\n\t\tstartupCompleted = true;\n\n\t\t// initially, start WaitParseThread\n\t\trestartWaitParseThread();\n\t}\n\n\t// New model...\n\n\tpublic void newPRISMModel()\n\t{\n\t\tactiveFile = null;\n\t\tmodified = false;\n\t\tmodifiedSinceParse = false;\n\t\tparsedModel = null;\n\t\tupdateBuiltModelDisplay();\n\t\tif (currentMode == PRISM_MODE) {\n\t\t\teditor.newModel();\n\t\t} else {\n\t\t\teditor = new GUITextModelEditor(\"\", this);\n\t\t\teditor.newModel();\n\t\t\tsplitter.setRightComponent(editor);\n\t\t}\n\t\ttree.newTree(false);\n\t\ttree.update(parsedModel);\n\t\tcurrentMode = PRISM_MODE;\n\t\ttheModel.doEnables();\n\t\tlastError = \"\";\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_MODEL));\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_LOAD_NOT_RELOAD_MODEL));\n\t}\n\n\tpublic void newPEPAModel()\n\t{\n\t\tactiveFile = null;\n\t\tmodified = false;\n\t\tmodifiedSinceParse = false;\n\t\tparsedModel = null;\n\t\tupdateBuiltModelDisplay();\n\t\tif (currentMode == PEPA_MODE) {\n\t\t\teditor.newModel();\n\t\t} else {\n\t\t\t//editor = new GUIPepaModelEditor(this);\n\t\t\teditor.newModel();\n\t\t\t//splitter.setRightComponent(editor);\n\t\t}\n\t\ttree.newTree(false);\n\t\ttree.update(parsedModel);\n\t\tcurrentMode = PEPA_MODE;\n\t\ttheModel.doEnables();\n\t\tlastError = \"\";\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_MODEL));\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_LOAD_NOT_RELOAD_MODEL));\n\t}\n\n\t// Conversions... (not used)\n\n\tpublic void convertViewToPRISM()\n\t{\n\t\ttheModel.doEnables();\n\t}\n\n\tpublic void convertViewToPEPA()//dummy dummy dummy\n\t{\n\t\ttheModel.doEnables();\n\t}\n\n\t// Load model...\n\n\tpublic void loadModel(File f)\n\t{\n\t\tloadModel(f, true);\n\t}\n\n\tpublic void loadModel(File f, boolean inBackground)\n\t{\n\t\t// guess model type based on extension\n\t\tString name = f.getName();\n\t\tif (name.endsWith(\"pm\") | name.endsWith(\"nm\") | name.endsWith(\"sm\"))\n\t\t\tloadPRISMModel(f, inBackground);\n\t\telse if (name.endsWith(\"pepa\"))\n\t\t\tloadPEPAModel(f, inBackground);\n\t\telse\n\t\t\tloadPRISMModel(f, inBackground);\n\t}\n\n\tpublic void loadPRISMModel(File f)\n\t{\n\t\tloadPRISMModel(f, true);\n\t}\n\n\tpublic void loadPRISMModel(File f, boolean inBackground)\n\t{\n\t\tlastError = \"\";\n\t\tThread t = new LoadPRISMModelThread(this, editor, f, false);\n\t\tt.start();\n\t\tif (!inBackground)\n\t\t\ttry {\n\t\t\t\tt.join();\n\t\t\t} catch (InterruptedException e) {\n\t\t\t}\n\t\ttheModel.doEnables();\n\t}\n\n\tpublic synchronized void prismModelLoaded(GUITextModelEditor edit, File f, boolean replaceEditor)\n\t{\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_MODEL));\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_LOAD_NOT_RELOAD_MODEL));\n\t\tactiveFile = f;\n\t\tmodified = false;\n\t\tmodifiedSinceParse = false;\n\t\tparsedModel = null;\n\t\tupdateBuiltModelDisplay();\n\t\tif (replaceEditor) {\n\t\t\teditor = edit;\n\t\t\tsplitter.setRightComponent(editor);\n\t\t}\n\t\ttree.newTree(false);\n\t\ttree.update(parsedModel);\n\t\ttree.makeNotUpToDate();\n\n\t\tcurrentMode = PRISM_MODE;\n\n\t\tupdateAutoParse();\n\t\tlastError = \"\";\n\t\tnew ParseModelThread(this, editor.getParseText(), false, isAutoParse()).start();\n\t\ttree.startParsing();\n\t\tparsing = true;\n\t\ttheModel.doEnables();\n\t\ttheModel.tabToFront();\n\t}\n\n\tpublic void loadPEPAModel(File f)\n\t{\n\t\tloadPEPAModel(f, true);\n\t}\n\n\tpublic void loadPEPAModel(File f, boolean inBackground)\n\t{\n\t\tlastError = \"\";\n\t\tThread t = new LoadPEPAModelThread(this, editor, f, false);\n\t\tt.start();\n\t\tif (!inBackground)\n\t\t\ttry {\n\t\t\t\tt.join();\n\t\t\t} catch (InterruptedException e) {\n\t\t\t}\n\t\ttheModel.doEnables();\n\t}\n\n\tpublic synchronized void pepaModelLoaded(GUIPepaModelEditor edit, File f, boolean replaceEditor)\n\t{\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_MODEL));\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_LOAD_NOT_RELOAD_MODEL));\n\t\tactiveFile = f;\n\t\tmodified = false;\n\t\tmodifiedSinceParse = false;\n\t\tparsedModel = null;\n\t\tupdateBuiltModelDisplay();\n\t\tif (replaceEditor) {\n\t\t\teditor = edit;\n\t\t\tsplitter.setRightComponent(editor);\n\t\t}\n\t\ttree.newTree(false);\n\t\ttree.update(parsedModel);\n\t\ttree.makeNotUpToDate();\n\t\tcurrentMode = PEPA_MODE;\n\n\t\tupdateAutoParse();\n\t\tlastError = \"\";\n\t\tnew ParseModelThread(this, editor.getParseText(), true, isAutoParse()).start();\n\t\ttree.startParsing();\n\t\ttheModel.doEnables();\n\t\ttheModel.tabToFront();\n\t}\n\n\t// Reload model...\n\n\tpublic void reloadActiveFile()\n\t{\n\t\tif (activeFile != null) {\n\t\t\tif (currentMode == PRISM_MODE) {\n\t\t\t\tnew LoadPRISMModelThread(this, editor, activeFile, true).start();\n\t\t\t} else if (currentMode == PEPA_MODE) {\n\t\t\t\tnew LoadPEPAModelThread(this, editor, activeFile, true).start();\n\t\t\t}\n\t\t}\n\t\ttheModel.doEnables();\n\t}\n\n\tpublic synchronized void prismModelReLoaded(File f)\n\t{\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_MODEL));\n\t\tactiveFile = f;\n\t\tmodified = false;\n\t\tparsedModel = null;\n\t\tmodifiedSinceParse = false;\n\t\tupdateBuiltModelDisplay();\n\t\tcurrentMode = PRISM_MODE;\n\t\tupdateAutoParse();\n\t\tif (!parsing) {\n\t\t\tparsing = true;\n\t\t\ttree.makeNotUpToDate();\n\n\t\t\tlastError = \"\";\n\t\t\tnew ParseModelThread(this, editor.getParseText(), false, isAutoParse()).start();\n\t\t\ttree.startParsing();\n\t\t} else {\n\t\t\tparseAfterParse = true;\n\t\t}\n\t\ttheModel.doEnables();\n\t\ttheModel.tabToFront();\n\t}\n\n\tpublic synchronized void pepaModelReLoaded(File f)\n\t{\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.NEW_MODEL));\n\t\tactiveFile = f;\n\t\tmodified = false;\n\t\tparsedModel = null;\n\t\tmodifiedSinceParse = false;\n\t\tupdateBuiltModelDisplay();\n\t\tcurrentMode = PEPA_MODE;\n\t\tupdateAutoParse();\n\t\tif (!parsing) {\n\t\t\tparsing = true;\n\t\t\ttree.makeNotUpToDate();\n\n\t\t\tlastError = \"\";\n\t\t\tnew ParseModelThread(this, editor.getParseText(), true, isAutoParse()).start();\n\t\t\ttree.startParsing();\n\t\t} else {\n\t\t\tparseAfterParse = true;\n\t\t}\n\t\ttheModel.doEnables();\n\t\ttheModel.tabToFront();\n\t}\n\n\t// Save model...\n\n\tpublic int saveToActiveFile()\n\t{\n\t\treturn saveToFile(activeFile);\n\t}\n\n\tpublic int saveToFile(File f)\n\t{\n\t\ttry {\n\t\t\ttheModel.setTaskBarText(\"Saving model...\");\n\t\t\tif (currentMode == PRISM_MODE)\n\t\t\t\t((GUITextModelEditor) editor).write(new FileWriter(f));\n\t\t\telse\n\t\t\t\t((GUIPepaModelEditor) editor).write(new FileWriter(f));\n\t\t} catch (IOException e) {\n\t\t\ttheModel.setTaskBarText(\"Saving model... error.\");\n\t\t\ttheModel.error(\"Could not save to file \\\"\" + f + \"\\\"\");\n\t\t\treturn GUIMultiModel.CANCEL;\n\t\t} catch (ClassCastException e) {\n\t\t\ttheModel.setTaskBarText(\"Saving model... error.\");\n\t\t\ttheModel.error(\"Could not save to file \\\"\" + f + \"\\\"\");\n\t\t\treturn GUIMultiModel.CANCEL;\n\t\t}\n\t\ttheModel.setTaskBarText(\"Saving model... done.\");\n\t\tif (currentMode == PRISM_MODE)\n\t\t\tprismFileWasSaved(f);\n\t\telse\n\t\t\tpepaFileWasSaved(f);\n\t\treturn GUIMultiModel.CONTINUE;\n\t}\n\n\tpublic void prismFileWasSaved(File f)\n\t{\n\t\t//possibly to handle switching\n\t\tactiveFile = f;\n\t\tmodified = false;\n\t\ttree.update(parsedModel);\n\t\ttheModel.doEnables();\n\t}\n\n\tpublic void pepaFileWasSaved(File f)\n\t{\n\t\t//possibly to handle switching\n\t\tactiveFile = f;\n\t\tmodified = false;\n\t\ttree.update(parsedModel);\n\t\ttheModel.doEnables();\n\t}\n\n\t// Parse model...\n\n\tpublic void requestParse(boolean force)\n\t{\n\t\t// only do a parse if we need to (or have been asked to)\n\t\tif (modifiedSinceParse || parsedModel == null || force) {\n\t\t\tif (!parsing) {\n\t\t\t\tlastError = \"\";\n\t\t\t\ttree.makeNotUpToDate();\n\t\t\t\tnew ParseModelThread(this, editor.getParseText(), currentMode == PEPA_MODE, false).start();\n\t\t\t\ttree.startParsing();\n\t\t\t\tparsing = true;\n\t\t\t} else {\n\t\t\t\tparseAfterParse = true;\n\t\t\t}\n\t\t\ttheModel.doEnables();\n\t\t}\n\t\t// otherwise use last successful parse\n\t\telse {\n\t\t\tmodelParsedSuccessful(parsedModel);\n\t\t}\n\t}\n\n\tpublic synchronized void modelParsedSuccessful(ModulesFile m)\n\t{\n\t\ttree.stopParsing();\n\t\tparsing = false;\n\t\tparsedModel = m;\n\t\tmodifiedSinceParse = false;\n\t\tlastError = \"Parse Successful\";\n\n\t\teditor.modelParseSuccessful();\n\n\t\tif (parseAfterParse) {\n\t\t\tparseAfterParse = false;\n\t\t\ttree.makeNotUpToDate();\n\t\t\t//start a new parse thread\n\t\t\tif (isAutoParse()) {\n\t\t\t\trestartWaitParseThread();\n\t\t\t}\n\t\t} else if (buildAfterReceiveParseNotification) {\n\t\t\tbuildAfterParse();\n\t\t} else if (exportAfterReceiveParseNotification) {\n\t\t\texportAfterParse();\n\t\t} else if (computeSSAfterReceiveParseNotification) {\n\t\t\tcomputeSteadyStateAfterParse();\n\t\t} else if (computeTransientAfterReceiveParseNotification) {\n\t\t\tcomputeTransientAfterParse();\n\t\t} else {\n\t\t\ttree.update(parsedModel);\n\t\t}\n\t\ttree.repaint();\n\t\ttheModel.doEnables();\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.MODEL_PARSED, parsedModel));\n\t}\n\n\tpublic synchronized void modelParseFailed(PrismException parserError, boolean background)\n\t{\n\t\tlastError = parserError.getMessage();\n\n\t\tif (parserError instanceof PrismLangException)\n\t\t\teditor.modelParseFailed((PrismLangException) parserError, background);\n\n\t\ttree.stopParsing();\n\t\tparsing = false;\n\t\ttree.lastParseFailed();\n\t\tif (parseAfterParse) {\n\t\t\tparseAfterParse = false;\n\t\t\ttree.makeNotUpToDate();\n\t\t\t//start a new parse thread\n\t\t\tif (isAutoParse()) {\n\t\t\t\trestartWaitParseThread();\n\t\t\t}\n\t\t} else {\n\t\t\tbuildAfterReceiveParseNotification = false;\n\t\t\texportAfterReceiveParseNotification = false;\n\t\t\tcomputeSSAfterReceiveParseNotification = false;\n\t\t\tcomputeTransientAfterReceiveParseNotification = false;\n\t\t}\n\t\ttree.repaint();\n\t\ttheModel.doEnables();\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.MODEL_PARSE_FAILED));\n\t}\n\n\t// Build model...\n\n\tpublic void forceBuild()\n\t{\n\t\t// set flag\n\t\tbuildAfterReceiveParseNotification = true;\n\t\t// do a parse if necessary\n\t\trequestParse(false);\n\t}\n\n\tprivate void buildAfterParse()\n\t{\n\t\tUndefinedConstants unC;\n\n\t\t// switch off flag\n\t\tbuildAfterReceiveParseNotification = false;\n\t\t// get values for undefined consts\n\t\tunC = new UndefinedConstants(parsedModel, null);\n\t\tif (unC.getMFNumUndefined() > 0) {\n\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(theModel.getGUI(), unC, lastMFConstants, null);\n\t\t\tif (result != GUIConstantsPicker.VALUES_DONE)\n\t\t\t\treturn;\n\t\t\tlastMFConstants = unC.getMFConstantValues();\n\t\t}\n\t\ttry {\n\t\t\t// currently, don't evaluate constants exactly\n\t\t\tboolean exact = prism.getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\t\t\tprism.setPRISMModelConstants(unC.getMFConstantValues(), exact);\n\t\t} catch (PrismException e) {\n\t\t\ttheModel.error(e.getMessage());\n\t\t\treturn;\n\t\t}\n\t\tnew BuildModelThread(this).start();\n\t}\n\n\tpublic synchronized void notifyModelBuildSuccessful()\n\t{\n\t\t// Deal with a model build success\n\t\t// Put this in an invokeLater(...) so can be called from another thread\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\teditor.modelParseSuccessful();\n\t\t\t\tupdateBuiltModelDisplay();\n\t\t\t\ttheModel.doEnables();\n\t\t\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.MODEL_BUILT, lastMFConstants));\n\t\t\t}\n\t\t});\n\t}\n\n\tprivate void updateBuiltModelDisplay()\n\t{\n\t\tbuiltNoStates.setText(\"?\");\n\t\tbuiltNoInitStates.setText(\"?\");\n\t\tbuiltNoTransitions.setText(\"?\");\n\t\tprism.Model<?> model = prism.getBuiltModel();\n\t\tif (model != null) {\n\t\t\tbuiltNoStates.setText(\"\" + model.getNumStatesString());\n\t\t\tbuiltNoInitStates.setText(\"\" + model.getNumInitialStatesString());\n\t\t\tbuiltNoTransitions.setText(\"\" + model.getNumTransitionsString());\n\t\t}\n\t}\n\n\tpublic synchronized void notifyModelBuildFailed(PrismException e)\n\t{\n\t\t// Deal with a model build failure\n\t\t// Put this in an invokeLater(...) so can be called from another thread\n\t\tlastBuildError = e;\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tif (lastBuildError != null && lastBuildError instanceof PrismLangException) {\n\t\t\t\t\teditor.modelParseFailed((PrismLangException) lastBuildError, false);\n\t\t\t\t\t// Bring model tab to front, but only if not busy e.g. with experiment\n\t\t\t\t\tif (!theModel.getComputing()) {\n\t\t\t\t\t\ttheModel.tabToFront();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tupdateBuiltModelDisplay();\n\t\t\t\ttheModel.doEnables();\n\t\t\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.MODEL_BUILD_FAILED));\n\t\t\t}\n\t\t});\n\t}\n\n\t// Export model...\n\n\tpublic void export(ModelExportTask exportTask)\n\t{\n\t\t// set flags/store info\n\t\texportAfterReceiveParseNotification = true;\n\t\tthis.exportTask = exportTask;\n\t\t// do a parse if necessary\n\t\trequestParse(false);\n\t}\n\n\tprivate void exportAfterParse()\n\t{\n\t\tUndefinedConstants unC;\n\n\t\t// switch off flag\n\t\texportAfterReceiveParseNotification = false;\n\t\t// get values for undefined consts\n\t\tunC = new UndefinedConstants(parsedModel, null);\n\t\tif (unC.getMFNumUndefined() > 0) {\n\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(theModel.getGUI(), unC, lastMFConstants, null);\n\t\t\tif (result != GUIConstantsPicker.VALUES_DONE)\n\t\t\t\treturn;\n\t\t\tlastMFConstants = unC.getMFConstantValues();\n\t\t}\n\t\ttry {\n\t\t\tboolean exact = prism.getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\t\t\tprism.setPRISMModelConstants(unC.getMFConstantValues(), exact);\n\t\t} catch (PrismException e) {\n\t\t\ttheModel.error(e.getMessage());\n\t\t\treturn;\n\t\t}\n\t\t// if export is being done to log, switch view to log\n\t\tif (exportTask.getFile() == null) {\n\t\t\ttheModel.logToFront();\n\t\t}\n\t\tnew ExportBuiltModelThread(this, exportTask).start();\n\t}\n\n\t// Compute steady-state...\n\n\tpublic void computeSteadyState(ModelExportTask exportTask)\n\t{\n\t\t// set flags/store info\n\t\tcomputeSSAfterReceiveParseNotification = true;\n\t\tthis.exportTask = exportTask;\n\t\t// do a parse if necessary\n\t\trequestParse(false);\n\t}\n\n\tprivate void computeSteadyStateAfterParse()\n\t{\n\t\tUndefinedConstants unC;\n\n\t\t// switch off flag\n\t\tcomputeSSAfterReceiveParseNotification = false;\n\t\t// get values for undefined consts\n\t\tunC = new UndefinedConstants(parsedModel, null);\n\t\tif (unC.getMFNumUndefined() > 0) {\n\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(theModel.getGUI(), unC, lastMFConstants, null);\n\t\t\tif (result != GUIConstantsPicker.VALUES_DONE) {\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tlastMFConstants = unC.getMFConstantValues();\n\t\t}\n\t\ttry {\n\t\t\tboolean exact = prism.getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\t\t\tprism.setPRISMModelConstants(unC.getMFConstantValues(), exact);\n\t\t} catch (PrismException e) {\n\t\t\ttheModel.error(e.getMessage());\n\t\t\treturn;\n\t\t}\n\t\t// if the results are going to the log, switch view to there\n\t\tif (exportTask.getFile() == null) {\n\t\t\ttheModel.logToFront();\n\t\t}\n\t\tnew ComputeSteadyStateThread(this, exportTask).start();\n\t}\n\n\t// Compute transient probabilities...\n\n\tpublic void computeTransient(String timeSpec, ModelExportTask exportTask)\n\t{\n\t\tcomputeTransientAfterReceiveParseNotification = true;\n\t\ttransientTimeSpec = timeSpec;\n\t\tthis.exportTask = exportTask;\n\t\t// do a parse if necessary\n\t\trequestParse(false);\n\t}\n\n\tprivate void computeTransientAfterParse()\n\t{\n\t\tUndefinedConstants unC;\n\n\t\t// switch off flag\n\t\tcomputeTransientAfterReceiveParseNotification = false;\n\t\t// get values for undefined consts\n\t\tunC = new UndefinedConstants(parsedModel, null);\n\t\tif (unC.getMFNumUndefined() > 0) {\n\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(theModel.getGUI(), unC, lastMFConstants, null);\n\t\t\tif (result != GUIConstantsPicker.VALUES_DONE)\n\t\t\t\treturn;\n\t\t\tlastMFConstants = unC.getMFConstantValues();\n\t\t}\n\t\ttry {\n\t\t\tboolean exact = prism.getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\t\t\tprism.setPRISMModelConstants(unC.getMFConstantValues(), exact);\n\t\t} catch (PrismException e) {\n\t\t\ttheModel.error(e.getMessage());\n\t\t\treturn;\n\t\t}\n\t\t// if the results are going to the log, switch view to there\n\t\tif (exportTask.getFile() == null) {\n\t\t\ttheModel.logToFront();\n\t\t}\n\t\tnew ComputeTransientThread(this, transientTimeSpec, exportTask).start();\n\t}\n\n\tpublic void requestViewModel()\n\t{\n\t\tif (parsedModel != null) {\n\t\t\ttheModel.showModel(parsedModel.toString());\n\t\t}\n\t\ttheModel.doEnables();\n\t}\n\n\tpublic void hasModified(boolean attemptReparse)\n\t{\n\t\tmodified = true;\n\t\tif (isBusy()) {\n\t\t\ttheModel.doEnables();\n\t\t\treturn;\n\t\t}\n\n\t\ttree.makeNotUpToDate();\n\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.MODIFIED_SINCE_SAVE));\n\t\tmodifiedSinceParse = true;\n\n\t\tif (!parsing) {\n\t\t\tif (isAutoParse() && attemptReparse) {\n\t\t\t\trestartWaitParseThread();\n\t\t\t}\n\t\t} else {\n\t\t\tparseAfterParse = true;\n\t\t}\n\t\ttheModel.doEnables();\n\t}\n\n\tpublic void undo()\n\t{\n\t\teditor.undo();\n\t}\n\n\tpublic void redo()\n\t{\n\t\teditor.redo();\n\t}\n\n\tpublic void cut()\n\t{\n\t\teditor.cut();\n\t}\n\n\tpublic void copy()\n\t{\n\t\teditor.copy();\n\t}\n\n\tpublic void paste()\n\t{\n\t\teditor.paste();\n\t}\n\n\tpublic void delete()\n\t{\n\t\teditor.delete();\n\t}\n\n\tpublic void selectAll()\n\t{\n\t\teditor.selectAll();\n\t}\n\n\t//Access methods\n\n\tpublic synchronized int getModelMode()\n\t{\n\t\treturn currentMode;\n\t}\n\n\tpublic synchronized boolean hasActiveFile()\n\t{\n\t\treturn activeFile != null;\n\t}\n\n\tpublic synchronized boolean modified()\n\t{\n\t\treturn modified;\n\t}\n\n\tpublic synchronized String getActiveFileName()\n\t{\n\t\tif (hasActiveFile()) {\n\t\t\treturn activeFile.getPath();\n\t\t} else\n\t\t\treturn \"<Untitled>\";\n\t}\n\n\tpublic synchronized String getShortActiveFileName()\n\t{\n\t\tif (hasActiveFile()) {\n\t\t\treturn activeFile.getName();\n\t\t} else\n\t\t\treturn \"<Untitled>\";\n\t}\n\n\t/**\n\t * Is auto-parsing currently enabled?\n\t */\n\tpublic synchronized boolean isAutoParse()\n\t{\n\t\treturn autoParse;\n\t}\n\n\t/**\n\t * Update whether auto-parsing is currently enabled,\n\t * based on current PRISM settings (and the current model size).\n\t */\n\tpublic synchronized void updateAutoParse()\n\t{\n\t\t// Store existing status\n\t\tboolean autoParseOld = autoParse;\n\t\t\n\t\t// Is auto-parse switched on?\n\t\tautoParse = theModel.getPrism().getSettings().getBoolean(PrismSettings.MODEL_AUTO_PARSE);\n\n\t\t// Should we disable auto parsing? (if the model is too big and that option is not disabled)\n\t\tif (isSwitchOnLarge() && autoParse) {\n\t\t\tif (currentMode == PRISM_MODE || currentMode == PEPA_MODE) {\n\t\t\t\t// \"too big\" == 25000 chars = 500 lines at 50 chars per line\n\t\t\t\tif (editor.getParseText().length() > 25000) {\n\t\t\t\t\tautoParse = false;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// If the flag has just been switched ON, do a parse...\n\t\tif (!autoParseOld && autoParse) {\n\t\t\ttree.makeNotUpToDate();\n\t\t\ttheModel.notifyEventListeners(new GUIModelEvent(GUIModelEvent.MODIFIED_SINCE_SAVE));\n\t\t\tif (!parsing) {\n\t\t\t\tif (isAutoParse()) {\n\t\t\t\t\trestartWaitParseThread();\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tparseAfterParse = true;\n\t\t\t}\n\t\t\ttheModel.doEnables();\n\t\t}\n\t}\n\n\t/**\n\t * Should auto=parsing be disabled for large models?\n\t */\n\tpublic synchronized boolean isSwitchOnLarge()\n\t{\n\t\treturn theModel.getPrism().getSettings().getBoolean(PrismSettings.MODEL_AUTO_MANUAL);\n\t}\n\n\tpublic synchronized ModelType getParsedModelType()\n\t{\n\t\tif (parsedModel != null) {\n\t\t\treturn parsedModel.getModelType();\n\t\t} else\n\t\t\treturn ModelType.MDP;\n\t}\n\n\tpublic synchronized String getParseErrorMessage()\n\t{\n\t\treturn lastError;\n\t}\n\n\t//Access to the top level plugin for communication with the rest of the gui\n\tpublic GUIPlugin getGUIPlugin()\n\t{\n\t\treturn theModel;\n\t}\n\n\tpublic int getParseState()\n\t{\n\t\treturn tree.getParseSynchState();\n\t}\n\n\tpublic GUIMultiModelTree getTree()\n\t{\n\t\treturn tree;\n\t}\n\n\t/**\n\t * Getter for property busy.\n\t * @return Value of property busy.\n\t */\n\tpublic boolean isBusy()\n\t{\n\t\treturn busy;\n\t}\n\n\t/**\n\t * Setter for property busy.\n\t * @param busy New value of property busy.\n\t */\n\tpublic void setBusy(boolean busy)\n\t{\n\t\tthis.busy = busy;\n\t}\n\n\tpublic void notifySettings(PrismSettings settings)\n\t{\n\t\tupdateAutoParse();\n\t\t\n\t\tprismEditorFontFast = settings.getFontColorPair(PrismSettings.MODEL_PRISM_EDITOR_FONT).f;\n\t\tif (editor instanceof GUITextModelEditor)\n\t\t\t((GUITextModelEditor) editor).setEditorFont(prismEditorFontFast);\n\t\tprismEditorColourFast = settings.getFontColorPair(PrismSettings.MODEL_PRISM_EDITOR_FONT).c;\n\n\t\tprismEditorBGColourFast = settings.getColor(PrismSettings.MODEL_PRISM_EDITOR_BG_COLOUR);\n\t\tif (editor instanceof GUITextModelEditor)\n\t\t\t((GUITextModelEditor) editor).setEditorBackground(prismEditorBGColourFast);\n\t\tint stt;\n\t\tswitch (settings.getInteger(PrismSettings.MODEL_PRISM_EDITOR_NUMERIC_STYLE)) {\n\t\tcase 0:\n\t\t\tstt = Font.PLAIN;\n\t\t\tbreak;\n\t\tcase 1:\n\t\t\tstt = Font.ITALIC;\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\tstt = Font.BOLD;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tstt = Font.BOLD | Font.ITALIC;\n\t\t\tbreak;\n\t\t}\n\t\tprismEditorNumericFast = new Style(settings.getColor(PrismSettings.MODEL_PRISM_EDITOR_NUMERIC_COLOUR), stt);\n\n\t\tswitch (settings.getInteger(PrismSettings.MODEL_PRISM_EDITOR_IDENTIFIER_STYLE)) {\n\t\tcase 0:\n\t\t\tstt = Font.PLAIN;\n\t\t\tbreak;\n\t\tcase 1:\n\t\t\tstt = Font.ITALIC;\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\tstt = Font.BOLD;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tstt = Font.BOLD | Font.ITALIC;\n\t\t\tbreak;\n\t\t}\n\t\tprismEditorVariableFast = new Style(settings.getColor(PrismSettings.MODEL_PRISM_EDITOR_IDENTIFIER_COLOUR), stt);\n\t\tswitch (settings.getInteger(PrismSettings.MODEL_PRISM_EDITOR_KEYWORD_STYLE)) {\n\t\tcase 0:\n\t\t\tstt = Font.PLAIN;\n\t\t\tbreak;\n\t\tcase 1:\n\t\t\tstt = Font.ITALIC;\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\tstt = Font.BOLD;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tstt = Font.BOLD | Font.ITALIC;\n\t\t\tbreak;\n\t\t}\n\t\tprismEditorKeywordFast = new Style(settings.getColor(PrismSettings.MODEL_PRISM_EDITOR_KEYWORD_COLOUR), stt);\n\t\tswitch (settings.getInteger(PrismSettings.MODEL_PRISM_EDITOR_COMMENT_STYLE)) {\n\t\tcase 0:\n\t\t\tstt = Font.PLAIN;\n\t\t\tbreak;\n\t\tcase 1:\n\t\t\tstt = Font.ITALIC;\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\tstt = Font.BOLD;\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tstt = Font.BOLD | Font.ITALIC;\n\t\t\tbreak;\n\t\t}\n\t\tprismEditorCommentFast = new Style(settings.getColor(PrismSettings.MODEL_PRISM_EDITOR_COMMENT_COLOUR), stt);\n\n\t\tpepaEditorFontFast = settings.getFontColorPair(PrismSettings.MODEL_PEPA_EDITOR_FONT).f;\n\t\tif (editor instanceof GUIPepaModelEditor)\n\t\t\t((GUIPepaModelEditor) editor).setEditorFont(pepaEditorFontFast);\n\t\tpepaEditorColourFast = settings.getColor(PrismSettings.MODEL_PEPA_EDITOR_COMMENT_COLOUR);\n\t\tpepaEditorBGColourFast = settings.getColor(PrismSettings.MODEL_PEPA_EDITOR_BG_COLOUR);\n\t\tif (editor instanceof GUIPepaModelEditor)\n\t\t\t((GUIPepaModelEditor) editor).setEditorBackground(pepaEditorBGColourFast);\n\t\tpepaEditorCommentFast = new Style(settings.getColor(PrismSettings.MODEL_PEPA_EDITOR_COMMENT_COLOUR),\n\t\t\t\tsettings.getInteger(PrismSettings.MODEL_PEPA_EDITOR_COMMENT_STYLE));\n\t}\n\n\t/**\n\t * Getter for property prismEditorFontFast.\n\t * @return Value of property prismEditorFontFast.\n\t */\n\tpublic java.awt.Font getPrismEditorFontFast()\n\t{\n\t\treturn prismEditorFontFast;\n\t}\n\n\t/**\n\t * Getter for property prismEditorColourFast.\n\t * @return Value of property prismEditorColourFast.\n\t */\n\tpublic java.awt.Color getPrismEditorColourFast()\n\t{\n\t\treturn prismEditorColourFast;\n\t}\n\n\t/**\n\t * Getter for property prismEditorBGColourFast.\n\t * @return Value of property prismEditorBGColourFast.\n\t */\n\tpublic java.awt.Color getPrismEditorBGColourFast()\n\t{\n\t\treturn prismEditorBGColourFast;\n\t}\n\n\t/**\n\t * Getter for property pepaEditorFontFast.\n\t * @return Value of property pepaEditorFontFast.\n\t */\n\tpublic java.awt.Font getPepaEditorFontFast()\n\t{\n\t\treturn pepaEditorFontFast;\n\t}\n\n\t/**\n\t * Getter for property pepaEditorColourFast.\n\t * @return Value of property pepaEditorColourFast.\n\t */\n\tpublic java.awt.Color getPepaEditorColourFast()\n\t{\n\t\treturn pepaEditorColourFast;\n\t}\n\n\t/**\n\t * Getter for property pepaEditorBGColourFast.\n\t * @return Value of property pepaEditorBGColourFast.\n\t */\n\tpublic java.awt.Color getPepaEditorBGColourFast()\n\t{\n\t\treturn pepaEditorBGColourFast;\n\t}\n\n\t/**\n\t * Getter for property prismEditorNumericFast.\n\t * @return Value of property prismEditorNumericFast.\n\t */\n\tpublic userinterface.model.Style getPrismEditorNumericFast()\n\t{\n\t\treturn prismEditorNumericFast;\n\t}\n\n\t/**\n\t * Getter for property prismEditorVariableFast.\n\t * @return Value of property prismEditorVariableFast.\n\t */\n\tpublic userinterface.model.Style getPrismEditorVariableFast()\n\t{\n\t\treturn prismEditorVariableFast;\n\t}\n\n\t/**\n\t * Getter for property prismEditorKeywordFast.\n\t * @return Value of property prismEditorKeywordFast.\n\t */\n\tpublic userinterface.model.Style getPrismEditorKeywordFast()\n\t{\n\t\treturn prismEditorKeywordFast;\n\t}\n\n\t/**\n\t * Getter for property prismEditorCommentFast.\n\t * @return Value of property prismEditorCommentFast.\n\t */\n\tpublic userinterface.model.Style getPrismEditorCommentFast()\n\t{\n\t\treturn prismEditorCommentFast;\n\t}\n\n\t/**\n\t * Getter for property pepaEditorCommentFast.\n\t * @return Value of property pepaEditorCommentFast.\n\t */\n\tpublic userinterface.model.Style getPepaEditorCommentFast()\n\t{\n\t\treturn pepaEditorCommentFast;\n\t}\n\n\tclass WaitParseThread extends Thread\n\t{\n\t\tint time;\n\t\tGUIMultiModelHandler handler;\n\t\tParseModelThread parseThread;\n\n\t\tpublic WaitParseThread(int time, GUIMultiModelHandler handler)\n\t\t{\n\t\t\tthis.time = time;\n\t\t\tthis.handler = handler;\n\t\t}\n\n\t\tpublic void run()\n\t\t{\n\t\t\ttry {\n\t\t\t\tsleep(time);\n\t\t\t\tparseThread = new ParseModelThread(handler, editor.getParseText(), currentMode == PEPA_MODE, isAutoParse());\n\t\t\t\tparsing = true;\n\t\t\t\ttree.startParsing();\n\t\t\t\tparseThread.start();\n\t\t\t} catch (InterruptedException e) {\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic GUIUndoManager getUndoManager()\n\t{\n\t\treturn editor.getUndoManager();\n\t}\n\n\tpublic boolean canDoClipBoardAction(Action action)\n\t{\n\t\treturn editor.canDoClipBoardAction(action);\n\t}\n\n\tpublic void jumpToError()\n\t{\n\t\tif (editor != null && editor instanceof GUITextModelEditor)\n\t\t\t((GUITextModelEditor) editor).jumpToError();\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/GUIMultiModelTree.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport java.awt.BorderLayout;\nimport java.awt.Color;\nimport java.awt.Component;\nimport java.awt.Rectangle;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.ActionListener;\nimport java.awt.event.KeyEvent;\nimport java.awt.event.MouseEvent;\nimport java.awt.event.MouseListener;\nimport java.util.ArrayList;\nimport java.util.EventObject;\nimport java.util.Vector;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.Action;\nimport javax.swing.ButtonGroup;\nimport javax.swing.ImageIcon;\nimport javax.swing.JComboBox;\nimport javax.swing.JOptionPane;\nimport javax.swing.JPanel;\nimport javax.swing.JPopupMenu;\nimport javax.swing.JRadioButton;\nimport javax.swing.JScrollPane;\nimport javax.swing.JTextField;\nimport javax.swing.JTree;\nimport javax.swing.ToolTipManager;\nimport javax.swing.event.CellEditorListener;\nimport javax.swing.event.ChangeEvent;\nimport javax.swing.tree.DefaultMutableTreeNode;\nimport javax.swing.tree.DefaultTreeCellEditor;\nimport javax.swing.tree.DefaultTreeCellRenderer;\nimport javax.swing.tree.DefaultTreeModel;\nimport javax.swing.tree.TreeCellEditor;\nimport javax.swing.tree.TreeNode;\nimport javax.swing.tree.TreePath;\n\nimport parser.ast.ConstantList;\nimport parser.ast.Declaration;\nimport parser.ast.DeclarationInt;\nimport parser.ast.Expression;\nimport parser.ast.ExpressionIdent;\nimport parser.ast.Module;\nimport parser.ast.ModulesFile;\nimport parser.type.Type;\nimport parser.type.TypeBool;\nimport parser.type.TypeClock;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport prism.ModelType;\nimport prism.Prism;\nimport prism.PrismException;\nimport userinterface.GUIPrism;\n\n@SuppressWarnings(\"serial\")\npublic class GUIMultiModelTree extends JPanel implements MouseListener\n{\n\t//Constants\n\tpublic static final int TREE_SYNCHRONIZED_GOOD = 0;\n\tpublic static final int TREE_SYNCHRONIZED_BAD = 1;\n\tpublic static final int TREE_NOT_SYNCHRONIZED = 2;\n\n\t//Attributes\n\tprivate GUIMultiModelHandler handler;\n\tprivate boolean editable;\n\n\t//Graphical elements\n\tprivate JTree tree;\n\tprivate JPopupMenu moduleCollectionPopup;\n\tprivate Action addModule;\n\tprivate JPopupMenu declarationCollectionPopup;\n\tprivate Action addBooleanGlobal, addIntegerGlobal;\n\tprivate JPopupMenu constantsCollectionPopup;\n\tprivate Action addBooleanConstant, addDoubleConstant, addIntegerConstant;\n\tprivate JPopupMenu modulePopup;\n\tprivate Action renameModule, removeModule, addBoolean, addInteger;\n\tprivate JPopupMenu declarationPopup;\n\tprivate Action renameDeclaration, removeDeclaration;\n\tprivate JPopupMenu expressionPopup;\n\tprivate Action editExpression;\n\tprivate JPopupMenu modelTypePopup;\n\tprivate JRadioButton non, pro, sto;\n\n\t//Tree nodes\n\tprivate DefaultTreeModel theModel;\n\tprivate ModelRootNode root;\n\tprivate ModelTypeNode modelType;\n\tprivate ModuleCollectionNode modules;\n\tprivate DeclarationCollectionNode declarations;\n\tprivate ConstantCollectionNode constants;\n\n\tprivate ArrayList<ModuleNode> editableModules;\n\tprivate ArrayList<DeclarationNode> editableDeclarations;\n\tprivate ArrayList<ConstantNode> editableConstants;\n\n\tprivate ImageIcon animIcon;\n\tprivate boolean isParsing;\n\tprivate IconThread parseThread;\n\n\tprivate PrismTreeNode lastPopNode;\n\n\t//State\n\tprivate int parseSynchState;\n\n\tpublic GUIMultiModelTree(GUIMultiModelHandler handler, boolean editable)\n\t{\n\t\tthis.handler = handler;\n\t\tthis.editable = editable;\n\t\troot = new ModelRootNode();\n\t\ttheModel = new DefaultTreeModel(root);\n\t\tnewTree(editable);\n\t\tinitComponents();\n\t\tanimIcon = GUIPrism.getIconFromImage(\"smallClockAnim1.png\");\n\t\tisParsing = false;\n\t\ttree.addMouseListener(this);\n\t\ttree.setEditable(true);\n\t\tToolTipManager.sharedInstance().registerComponent(tree);\n\t}\n\n\tpublic GUIMultiModelTree(GUIMultiModelHandler handler)\n\t{\n\t\tthis(handler, false);\n\t}\n\n\tstatic int modCounter = 1;\n\n\tpublic void a_addModule()\n\t{\n\t\tModuleNode newNode = new ModuleNode(\"newModule\" + modCounter, true);\n\t\tnewNode.addVariable(new StateVarNode(newNode));\n\t\teditableModules.add(newNode);\n\t\tmodules.addModule(newNode);\n\t\tint index = modules.getIndex(newNode);\n\t\ttheModel.nodesWereInserted(modules, new int[] { index });\n\t\tmodCounter++;\n\t}\n\n\tpublic ModuleNode a_requestNewModule(String name)\n\t{\n\t\tModuleNode newNode = new ModuleNode(name, true);\n\t\tnewNode.addVariable(new StateVarNode(newNode));\n\t\teditableModules.add(newNode);\n\t\tmodules.addModule(newNode);\n\t\tint index = modules.getIndex(newNode);\n\t\ttheModel.nodesWereInserted(modules, new int[] { index });\n\t\tmodCounter++;\n\t\treturn newNode;\n\t}\n\n\tstatic int globCounter = 1;\n\n\tpublic void a_addIntegerGlobal()\n\t{\n\t\ttry {\n\t\t\tExpression init = Prism.parseSingleExpressionString(\"0\");\n\t\t\tExpression min = Prism.parseSingleExpressionString(\"0\");\n\t\t\tExpression max = Prism.parseSingleExpressionString(\"0\");\n\n\t\t\tGlobalNode newNode = new GlobalNode(\"g\" + globCounter, init, min, max, true);\n\t\t\teditableDeclarations.add(newNode);\n\t\t\tdeclarations.addDeclaration(newNode);\n\t\t\tint index = declarations.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(declarations, new int[] { index });\n\t\t\tglobCounter++;\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(\"UNEXPECTED ERROR: \" + e.getMessage());\n\t\t\te.printStackTrace();\n\t\t\t//This should never happen\n\t\t}\n\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addIntegerGlobal(String name, String mins, String maxs, String inits) throws PrismException\n\t{\n\t\ttry {\n\t\t\tExpression init = Prism.parseSingleExpressionString(inits);\n\t\t\tExpression min = Prism.parseSingleExpressionString(mins);\n\t\t\tExpression max = Prism.parseSingleExpressionString(maxs);\n\n\t\t\tGlobalNode newNode = new GlobalNode(name, init, min, max, true);\n\t\t\teditableDeclarations.add(newNode);\n\t\t\tdeclarations.addDeclaration(newNode);\n\t\t\tint index = declarations.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(declarations, new int[] { index });\n\t\t\tglobCounter++;\n\t\t} catch (Exception e) {\n\t\t\tthrow new PrismException(\"Global integer \" + name + \" has invalid parameter\");\n\t\t}\n\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addBooleanGlobal()\n\t{\n\t\ttry {\n\t\t\tExpression init = Prism.parseSingleExpressionString(\"false\");\n\t\t\tGlobalBoolNode newNode = new GlobalBoolNode(\"g\" + globCounter, init, true);\n\t\t\teditableDeclarations.add(newNode);\n\t\t\tdeclarations.addDeclaration(newNode);\n\t\t\tint index = declarations.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(declarations, new int[] { index });\n\t\t\tglobCounter++;\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(\"UNEXPECTED ERROR: \" + e.getMessage());\n\t\t\te.printStackTrace();\n\t\t\t//This should never happen\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addBooleanGlobal(String name, String inits) throws PrismException\n\t{\n\t\ttry {\n\t\t\tExpression init = Prism.parseSingleExpressionString(inits);\n\t\t\tGlobalBoolNode newNode = new GlobalBoolNode(name, init, true);\n\t\t\teditableDeclarations.add(newNode);\n\t\t\tdeclarations.addDeclaration(newNode);\n\t\t\tint index = declarations.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(declarations, new int[] { index });\n\t\t\tglobCounter++;\n\t\t} catch (Exception e) {\n\t\t\tthrow new PrismException(\"Global boolean \" + name + \" has invalid parameter\");\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tstatic int consCount = 1;\n\n\tpublic void a_addIntegerConstant()\n\t{\n\t\ttry {\n\t\t\tExpression value = Prism.parseSingleExpressionString(\"0\");\n\t\t\tIntegerConstantNode newNode = new IntegerConstantNode(\"c\" + consCount, value, true);\n\t\t\teditableConstants.add(newNode);\n\t\t\tconstants.addConstant(newNode);\n\t\t\tint index = constants.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(constants, new int[] { index });\n\t\t\tconsCount++;\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(\"UNEXPECTED ERROR: \" + e.getMessage());\n\t\t\te.printStackTrace();\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addIntegerConstant(String name, String val) throws PrismException\n\t{\n\t\ttry {\n\t\t\tExpression value;\n\t\t\tif (val == null)\n\t\t\t\tvalue = null;\n\t\t\telse\n\t\t\t\tvalue = Prism.parseSingleExpressionString(val);\n\t\t\tIntegerConstantNode newNode = new IntegerConstantNode(name, value, true);\n\t\t\teditableConstants.add(newNode);\n\t\t\tconstants.addConstant(newNode);\n\t\t\tint index = constants.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(constants, new int[] { index });\n\t\t\tconsCount++;\n\t\t} catch (Exception e) {\n\t\t\tthrow new PrismException(\"Constant integer \" + name + \" has invalid parameter\");\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addBooleanConstant()\n\t{\n\t\ttry {\n\t\t\tExpression value = Prism.parseSingleExpressionString(\"false\");\n\t\t\tBoolConstantNode newNode = new BoolConstantNode(\"c\" + consCount, value, true);\n\t\t\teditableConstants.add(newNode);\n\t\t\tconstants.addConstant(newNode);\n\t\t\tint index = constants.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(constants, new int[] { index });\n\t\t\tconsCount++;\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(\"UNEXPECTED ERROR: \" + e.getMessage());\n\t\t\te.printStackTrace();\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addBooleanConstant(String name, String val) throws PrismException\n\t{\n\t\ttry {\n\t\t\tExpression value;\n\t\t\tif (val == null)\n\t\t\t\tvalue = null;\n\t\t\telse\n\t\t\t\tvalue = Prism.parseSingleExpressionString(val);\n\t\t\tBoolConstantNode newNode = new BoolConstantNode(name, value, true);\n\t\t\teditableConstants.add(newNode);\n\t\t\tconstants.addConstant(newNode);\n\t\t\tint index = constants.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(constants, new int[] { index });\n\t\t\tconsCount++;\n\t\t} catch (Exception e) {\n\t\t\tthrow new PrismException(\"Constant boolean \" + name + \" has invalid parameter\");\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addDoubleConstant()\n\t{\n\t\ttry {\n\t\t\tExpression value = Prism.parseSingleExpressionString(\"0.0\");\n\t\t\tDoubleConstantNode newNode = new DoubleConstantNode(\"c\" + consCount, value, true);\n\t\t\teditableConstants.add(newNode);\n\t\t\tconstants.addConstant(newNode);\n\t\t\tint index = constants.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(constants, new int[] { index });\n\t\t\tconsCount++;\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(\"UNEXPECTED ERROR: \" + e.getMessage());\n\t\t\te.printStackTrace();\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addDoubleConstant(String name, String val) throws PrismException\n\t{\n\t\ttry {\n\t\t\tExpression value;\n\t\t\tif (val == null)\n\t\t\t\tvalue = null;\n\t\t\telse\n\t\t\t\tvalue = Prism.parseSingleExpressionString(val);\n\t\t\tDoubleConstantNode newNode = new DoubleConstantNode(name, value, true);\n\t\t\teditableConstants.add(newNode);\n\t\t\tconstants.addConstant(newNode);\n\t\t\tint index = constants.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(constants, new int[] { index });\n\t\t\tconsCount++;\n\t\t} catch (Exception e) {\n\t\t\tthrow new PrismException(\"Constant double \" + name + \" has invalid parameter\");\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_removeModule(ModuleNode m)\n\t{\n\t\tint index = modules.getIndex(m);\n\t\teditableModules.remove(m);\n\t\tmodules.remove(m);\n\t\ttheModel.nodesWereRemoved(modules, new int[] { index }, new Object[] { m });\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_renameModule(ModuleNode m)\n\t{\n\n\t\tString s = JOptionPane.showInputDialog(\"New module name:\", m.getName());\n\t\tif (s == null)\n\t\t\treturn;\n\n\t\ttry {\n\t\t\tExpression exp = Prism.parseSingleExpressionString(s);\n\t\t\tif (exp instanceof ExpressionIdent) {\n\t\t\t\tm.setName(s);\n\t\t\t\ttheModel.nodeChanged(m);\n\t\t\t\ttheModel.nodeStructureChanged(m);\n\t\t\t} else {\n\t\t\t\thandler.getGUIPlugin().error(\"Invalid module name\");\n\t\t\t}\n\t\t} catch (PrismException exx) {\n\t\t\thandler.getGUIPlugin().error(\"Invalid module name\");\n\t\t}\n\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_renameDeclaration(DeclarationNode d)\n\t{\n\t\tString type = \"\";\n\t\tif (d instanceof BoolNode || d instanceof VarNode)\n\t\t\ttype = \" variable\";\n\t\telse if (d instanceof GlobalNode || d instanceof GlobalBoolNode)\n\t\t\ttype = \" global\";\n\t\telse if (d instanceof ConstantNode)\n\t\t\ttype = \" constant\";\n\n\t\tString s = JOptionPane.showInputDialog(\"New\" + type + \" name:\", d.getName());\n\t\tif (s == null)\n\t\t\treturn;\n\n\t\ttry {\n\t\t\tExpression exp = Prism.parseSingleExpressionString(s);\n\t\t\tif (exp instanceof ExpressionIdent) {\n\t\t\t\td.setName(s);\n\t\t\t\ttheModel.nodeChanged(d);\n\t\t\t\ttheModel.nodeStructureChanged(d);\n\t\t\t} else {\n\t\t\t\thandler.getGUIPlugin().error(\"Invalid declaration name\");\n\t\t\t}\n\t\t} catch (PrismException exx) {\n\t\t\thandler.getGUIPlugin().error(\"Invalid module name\");\n\t\t}\n\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_removeVariable(DeclarationNode d, ModuleNode m)\n\t{\n\t\tint index = m.getIndex(d);\n\t\tm.remove(d);\n\t\ttheModel.nodesWereRemoved(m, new int[] { index }, new Object[] { d });\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_removeGlobal(DeclarationNode d)\n\t{\n\t\tint index = declarations.getIndex(d);\n\t\teditableDeclarations.remove(d);\n\t\tdeclarations.remove(d);\n\t\ttheModel.nodesWereRemoved(declarations, new int[] { index }, new Object[] { d });\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_removeConstant(ConstantNode c)\n\t{\n\t\tint index = constants.getIndex(c);\n\t\teditableConstants.remove(c);\n\t\tconstants.remove(c);\n\t\ttheModel.nodesWereRemoved(constants, new int[] { index }, new Object[] { c });\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addLocalBoolean(ModuleNode m, BooleanVariable var) throws PrismException\n\t{\n\t\ttry {\n\t\t\tExpression init;\n\t\t\tif (var != null)\n\t\t\t\tinit = Prism.parseSingleExpressionString(var.init);\n\t\t\telse\n\t\t\t\tinit = Prism.parseSingleExpressionString(\"false\");\n\n\t\t\tBoolNode newNode = new BoolNode(var.name, init, true);\n\t\t\tm.add(newNode);\n\t\t\tint index = m.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(m, new int[] { index });\n\t\t\tvarCount++;\n\t\t} catch (Exception e) {\n\t\t\tthrow new PrismException(\"Local boolean \" + var.name + \" has an invalid parameter\");\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tstatic int varCount = 1;\n\n\tpublic void a_addLocalBoolean(ModuleNode m)\n\t{\n\t\ttry {\n\t\t\tExpression init = Prism.parseSingleExpressionString(\"false\");\n\n\t\t\tBoolNode newNode = new BoolNode(\"v\" + varCount, init, true);\n\t\t\tm.add(newNode);\n\t\t\tint index = m.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(m, new int[] { index });\n\t\t\tvarCount++;\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(\"UNEXPECTED ERROR: \" + e.getMessage());\n\t\t\te.printStackTrace();\n\t\t\t//This should never happen\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addLocalInteger(ModuleNode m, IntegerVariable var) throws PrismException\n\t{\n\t\ttry {\n\t\t\tExpression init;\n\t\t\tif (var.init == null)\n\t\t\t\tinit = Prism.parseSingleExpressionString(\"0\");\n\t\t\telse\n\t\t\t\tinit = Prism.parseSingleExpressionString(var.init);\n\t\t\tExpression min = Prism.parseSingleExpressionString(var.min);\n\t\t\tExpression max = Prism.parseSingleExpressionString(var.max);\n\n\t\t\tVarNode newNode = new VarNode(var.name, init, min, max, true);\n\t\t\tm.addVariable(newNode);\n\t\t\tint index = m.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(m, new int[] { index });\n\t\t\tvarCount++;\n\t\t} catch (Exception e) {\n\t\t\tthrow new PrismException(\"Local integer \" + var.name + \" has an invalid parameter\");\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_addLocalInteger(ModuleNode m)\n\t{\n\t\ttry {\n\t\t\tExpression init = Prism.parseSingleExpressionString(\"0\");\n\t\t\tExpression min = Prism.parseSingleExpressionString(\"0\");\n\t\t\tExpression max = Prism.parseSingleExpressionString(\"0\");\n\n\t\t\tVarNode newNode = new VarNode(\"v\" + varCount, init, min, max, true);\n\t\t\tm.addVariable(newNode);\n\t\t\tint index = m.getIndex(newNode);\n\t\t\ttheModel.nodesWereInserted(m, new int[] { index });\n\t\t\tvarCount++;\n\t\t} catch (Exception e) {\n\t\t\tSystem.err.println(\"UNEXPECTED ERROR: \" + e.getMessage());\n\t\t\te.printStackTrace();\n\t\t\t//This should never happen\n\t\t}\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_editExpression(ExpressionNode en)\n\t{\n\t\tString defa;\n\t\tif (en.getValue() == null)\n\t\t\tdefa = \"?\";\n\t\telse\n\t\t\tdefa = en.getValue().toString();\n\t\tString s = JOptionPane.showInputDialog(\"New Expression:\", defa);\n\t\tif (s == null)\n\t\t\treturn;\n\t\ttry {\n\t\t\tif (s.equals(\"\")) {\n\t\t\t\ten.setValue(null);\n\t\t\t} else {\n\t\t\t\tExpression exp = Prism.parseSingleExpressionString(s);\n\t\t\t\ten.setValue(exp);\n\t\t\t}\n\t\t\ttheModel.nodeChanged(en);\n\t\t} catch (Exception e) {\n\t\t\thandler.getGUIPlugin().error(\"Syntax error in expression:\\n\" + s);\n\t\t}\n\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic void a_setModelType(ModelType type)\n\t{\n\t\tmodelType.setModelType(type);\n\t\thandler.hasModified(true);\n\t}\n\n\tpublic int getParseSynchState()\n\t{\n\t\treturn parseSynchState;\n\t}\n\n\tpublic void startParsing()\n\t{\n\t\tisParsing = true;\n\t\tif (parseThread != null)\n\t\t\tparseThread.interrupt();\n\t\tparseThread = new IconThread(0);\n\t\tparseThread.start();\n\t}\n\n\tpublic void stopParsing()\n\t{\n\t\tisParsing = false;\n\t\tif (parseThread != null)\n\t\t\tparseThread.interrupt();\n\t\ttree.repaint();\n\t}\n\n\tpublic void newTree()\n\t{\n\t\tthis.newTree(false);\n\t}\n\n\tpublic void newTree(boolean editable)\n\t{\n\t\tthis.editable = editable;\n\t\troot.removeAllChildren();\n\t\tparseSynchState = TREE_NOT_SYNCHRONIZED;\n\t\t{\n\t\t\troot.setUserObject(\"Model: \" + handler.getShortActiveFileName());\n\t\t\tmodelType = new ModelTypeNode(\"<Unknown>\", editable);\n\t\t\troot.add(modelType);\n\t\t\tif (editable) {\n\t\t\t\tmodules = new GUIMultiModelTree.ModuleCollectionNode();\n\t\t\t\tdeclarations = new GUIMultiModelTree.DeclarationCollectionNode();\n\t\t\t\tconstants = new GUIMultiModelTree.ConstantCollectionNode();\n\t\t\t\troot.add(modules);\n\t\t\t\troot.add(declarations);\n\t\t\t\troot.add(constants);\n\t\t\t\ttheModel.nodeStructureChanged(root);\n\t\t\t} else {\n\t\t\t\tmodules = new ModuleCollectionNode();\n\t\t\t\tdeclarations = new DeclarationCollectionNode();\n\t\t\t\tconstants = new ConstantCollectionNode();\n\t\t\t\ttheModel.nodeStructureChanged(root);\n\t\t\t}\n\t\t}\n\t\teditableModules = new ArrayList<ModuleNode>();\n\t\teditableDeclarations = new ArrayList<DeclarationNode>();\n\t\teditableConstants = new ArrayList<ConstantNode>();\n\n\t\tmodCounter = 1;\n\t}\n\n\tpublic void update(ModulesFile parsedModel)\n\t{\n\t\tparseSynchState = (parsedModel == null) ? TREE_NOT_SYNCHRONIZED : TREE_SYNCHRONIZED_GOOD;\n\t\tif (editable)\n\t\t\tupdateEditable(parsedModel);\n\t\telse\n\t\t\tupdateUnEditable(parsedModel);\n\t}\n\n\tprivate void updateUnEditable(ModulesFile parsedModel)\n\t{\n\t\tString fn = handler.getShortActiveFileName();\n\t\tif (!root.getUserObject().equals(fn)) {\n\t\t\troot.setUserObject(\"Model: \" + fn);\n\t\t\ttheModel.nodeChanged(root);\n\t\t}\n\n\t\tif (parsedModel != null) {\n\t\t\tString tp = parsedModel.getTypeString();\n\t\t\tif (!modelType.getValue().equals(tp)) {\n\t\t\t\tmodelType.setUserObject(tp);\n\t\t\t\ttheModel.nodeChanged(modelType);\n\t\t\t}\n\t\t} else {\n\t\t\tString tp = \"<Unknown>\";\n\t\t\tif (!modelType.getValue().equals(tp)) {\n\t\t\t\tmodelType.setUserObject(tp);\n\t\t\t\ttheModel.nodeChanged(modelType);\n\t\t\t}\n\t\t}\n\n\t\tif (tree != null)\n\t\t\ttree.repaint();\n\t}\n\n\tpublic boolean moduleExists(ModuleNode mNode, ArrayList<Module> inTree, ArrayList<Module> outTree)\n\t{\n\t\tfor (int i = 0; i < inTree.size(); i++) {\n\t\t\tModule m = inTree.get(i);\n\t\t\tif (mNode.getName().equals(m.getName())) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\tfor (int i = 0; i < outTree.size(); i++) {\n\t\t\tModule m = outTree.get(i);\n\t\t\tif (mNode.getName().equals(m.getName())) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\tpublic boolean variableExists(DeclarationNode vNode, ArrayList<Declaration> inTree, ArrayList<Declaration> outTree)\n\t{\n\t\tfor (int i = 0; i < inTree.size(); i++) {\n\t\t\tDeclaration d = inTree.get(i);\n\t\t\tif (vNode.getName().equals(d.getName())) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\tfor (int i = 0; i < outTree.size(); i++) {\n\t\t\tDeclaration d = outTree.get(i);\n\t\t\tif (vNode.getName().equals(d.getName())) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\tpublic boolean declarationExists(DeclarationNode vNode, ArrayList<Declaration> inTree, ArrayList<Declaration> outTree)\n\t{\n\t\tfor (int i = 0; i < inTree.size(); i++) {\n\t\t\tDeclaration d = inTree.get(i);\n\t\t\tif (vNode.getName().equals(d.getName())) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\tfor (int i = 0; i < outTree.size(); i++) {\n\t\t\tDeclaration d = outTree.get(i);\n\t\t\tif (vNode.getName().equals(d.getName())) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\tpublic boolean constantExists(ConstantNode cNode, ArrayList<ConstantNode> inTree, ArrayList<ConstantNode> outTree)\n\t{\n\t\tfor (int i = 0; i < inTree.size(); i++) {\n\t\t\tConstantNode c = inTree.get(i);\n\t\t\tif (c.equals(cNode))\n\t\t\t\treturn true;\n\t\t}\n\n\t\tfor (int i = 0; i < outTree.size(); i++) {\n\t\t\tConstantNode c = outTree.get(i);\n\t\t\tif (c.equals(cNode))\n\t\t\t\treturn true;\n\t\t}\n\t\treturn false;\n\t}\n\n\tpublic boolean moduleIsMember(Module aMod)\n\t{\n\t\tboolean member = false;\n\t\tfor (int i = 0; i < modules.getChildCount(); i++) {\n\t\t\tModuleNode node = (ModuleNode) modules.getChildAt(i);\n\t\t\tif (node.getName().equals(aMod.getName())) {\n\t\t\t\tmember = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn member;\n\t}\n\n\tpublic boolean declarationIsMember(Declaration d)\n\t{\n\t\tboolean member = false;\n\t\tfor (int i = 0; i < declarations.getChildCount(); i++) {\n\t\t\tDeclarationNode dec = (DeclarationNode) declarations.getChildAt(i);\n\t\t\tif (dec.getName().equals(d.getName())) //check same name\n\t\t\t{\n\t\t\t\tif (dec instanceof GlobalBoolNode && d.getType() instanceof TypeBool) //check type equality\n\t\t\t\t{\n\t\t\t\t\tmember = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tif (dec instanceof GlobalNode && d.getType() instanceof TypeInt) {\n\t\t\t\t\tmember = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn member;\n\t}\n\n\tpublic boolean constantIsMember(ConstantNode n)\n\t{\n\t\tboolean member = false;\n\t\tfor (int i = 0; i < constants.getChildCount(); i++) {\n\t\t\tConstantNode inC = (ConstantNode) constants.getChildAt(i);\n\t\t\tif (inC.equals(n)) {\n\t\t\t\tmember = true;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn member;\n\t}\n\n\tpublic boolean variableIsMember(Declaration d, ModuleNode node)\n\t{\n\t\tboolean member = false;\n\t\tfor (int i = 0; i < node.getChildCount(); i++) {\n\t\t\tDeclarationNode dec = (DeclarationNode) node.getChildAt(i);\n\t\t\tif (dec.getName().equals(d.getName())) //check same name\n\t\t\t{\n\t\t\t\tif (dec instanceof BoolNode && d.getType() instanceof TypeBool) //check type equality\n\t\t\t\t{\n\t\t\t\t\tmember = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tif (dec instanceof VarNode && d.getType() instanceof TypeInt) {\n\t\t\t\t\tmember = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn member;\n\t}\n\n\tpublic int getVarTreeIndexOf(Declaration d, ModuleNode node)\n\t{\n\t\tint member = -1;\n\t\tfor (int i = 0; i < node.getChildCount(); i++) {\n\t\t\tDeclarationNode vNode = (DeclarationNode) node.getChildAt(i);\n\t\t\tif (vNode.getName().equals(d.getName())) {\n\t\t\t\tmember = i;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn member;\n\t}\n\n\tpublic int getModuleTreeIndexOf(Module aMod)\n\t{\n\t\tint member = -1;\n\t\tfor (int i = 0; i < modules.getChildCount(); i++) {\n\t\t\tModuleNode node = (ModuleNode) modules.getChildAt(i);\n\t\t\tif (node.getName().equals(aMod.getName())) {\n\t\t\t\tmember = i;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn member;\n\t}\n\n\tpublic int getIndexOfDec(Declaration d)\n\t{\n\t\tint member = -1;\n\t\tfor (int i = 0; i < declarations.getChildCount(); i++) {\n\t\t\tDeclarationNode dec = (DeclarationNode) declarations.getChildAt(i);\n\t\t\tif (dec.getName().equals(d.getName())) {\n\t\t\t\tmember = i;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn member;\n\t}\n\n\tpublic int getIndexOfCon(ConstantNode cn)\n\t{\n\t\tint member = -1;\n\n\t\tfor (int i = 0; i < constants.getChildCount(); i++) {\n\t\t\tConstantNode cc = (ConstantNode) constants.getChildAt(i);\n\t\t\tif (cc.equals(cn)) {\n\t\t\t\tmember = i;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn member;\n\t}\n\n\tprivate void updateEditable(ModulesFile parsedModel)\n\t{\n\t\tString fn = handler.getShortActiveFileName();\n\t\tif (!root.getUserObject().equals(fn)) {\n\t\t\troot.setUserObject(\"Model: \" + fn);\n\t\t\ttheModel.nodeChanged(root);\n\t\t}\n\n\t\tif (parsedModel != null) {\n\t\t\tif (!modelType.getValue().equals(parsedModel.getType().toString())) {\n\t\t\t\tmodelType.setModelType(parsedModel.getModelType());\n\t\t\t}\n\n\t\t\t//MODULES\n\n\t\t\t//If there is no module tree, but we need to have modules, add the tre\n\t\t\tif (root.getIndex(modules) == -1 && parsedModel.getNumModules() > 0) {\n\t\t\t\troot.add(modules);\n\t\t\t\ttheModel.nodesWereInserted(root, new int[] { root.getIndex(modules) });\n\t\t\t}\n\n\t\t\t/*  Create 2 ArrayLists.  One of Modules in the tree and one of modules\n\t\t\t *  not in the tree. */\n\t\t\tArrayList<Module> inTree = new ArrayList<Module>();\n\t\t\tArrayList<Module> notInTree = new ArrayList<Module>();\n\n\t\t\tfor (int i = 0; i < parsedModel.getNumModules(); i++) {\n\t\t\t\tModule aMod = parsedModel.getModule(i);\n\t\t\t\tif (moduleIsMember(aMod))\n\t\t\t\t\tinTree.add(aMod);\n\t\t\t\telse\n\t\t\t\t\tnotInTree.add(aMod);\n\t\t\t}\n\n\t\t\t//make sure modules in the tree are valid\n\t\t\tfor (int i = 0; i < inTree.size(); i++) {\n\t\t\t\tModule inTreeMod = inTree.get(i);\n\t\t\t\tint treeIndex = getModuleTreeIndexOf(inTreeMod); //should not be -1\n\t\t\t\tModuleNode inTreeNode = (ModuleNode) modules.getChildAt(treeIndex);\n\n\t\t\t\t/*  Check its variables getting variables which are already there\n\t\t\t\t *  and putting them in varInTree, and getting variables which\n\t\t\t\t *  are not there and putting them in varNotInTree*/\n\t\t\t\tArrayList<Declaration> varInTree = new ArrayList<Declaration>();\n\t\t\t\tArrayList<Declaration> varNotInTree = new ArrayList<Declaration>();\n\n\t\t\t\tfor (int j = 0; j < inTreeMod.getNumDeclarations(); j++) {\n\t\t\t\t\tDeclaration d = inTreeMod.getDeclaration(j);\n\t\t\t\t\tif (variableIsMember(d, inTreeNode))\n\t\t\t\t\t\tvarInTree.add(d);\n\t\t\t\t\telse\n\t\t\t\t\t\tvarNotInTree.add(d);\n\t\t\t\t}\n\n\t\t\t\t//make sure variables in this module tree are valid\n\t\t\t\tfor (int j = 0; j < varInTree.size(); j++) {\n\t\t\t\t\tDeclaration inTreeDec = varInTree.get(j);\n\t\t\t\t\tint decIndex = getVarTreeIndexOf(inTreeDec, inTreeNode);\n\t\t\t\t\tDeclarationNode dNode = (DeclarationNode) inTreeNode.getChildAt(decIndex);\n\t\t\t\t\tif (dNode instanceof VarNode) {\n\t\t\t\t\t\tVarNode vNode = (VarNode) dNode;\n\t\t\t\t\t\tvNode.setInitial(parsedModel.getSystemDefn() == null ? inTreeDec.getStartOrDefault() : null);\n\t\t\t\t\t\tif (inTreeDec.getDeclType() instanceof DeclarationInt) {\n\t\t\t\t\t\t\tDeclarationInt declInt = (DeclarationInt) inTreeDec.getDeclType();\n\t\t\t\t\t\t\tvNode.setMin(declInt.getLow());\n\t\t\t\t\t\t\tvNode.setMax(declInt.getHigh());\n\t\t\t\t\t\t}\n\t\t\t\t\t\ttheModel.nodesChanged(vNode, new int[] { 0, 1, 2 });\n\t\t\t\t\t} else if (dNode instanceof BoolNode) {\n\t\t\t\t\t\tBoolNode bNode = (BoolNode) dNode;\n\t\t\t\t\t\tbNode.setInitial(parsedModel.getSystemDefn() == null ? inTreeDec.getStartOrDefault() : null);\n\t\t\t\t\t\ttheModel.nodesChanged(bNode, new int[] { 0 });\n\t\t\t\t\t}\n\n\t\t\t\t}\n\t\t\t\t//add variable in varNotInTree to the tree\n\t\t\t\tint[] cIndices = new int[varNotInTree.size()];\n\t\t\t\tfor (int j = 0; j < varNotInTree.size(); j++) {\n\t\t\t\t\tDeclaration notTreeDec = varNotInTree.get(j);\n\t\t\t\t\tif (notTreeDec.getType() instanceof TypeInt) {\n\t\t\t\t\t\tif (notTreeDec.getDeclType() instanceof DeclarationInt) {\n\t\t\t\t\t\t\tDeclarationInt declInt = (DeclarationInt) notTreeDec.getDeclType();\n\t\t\t\t\t\t\tVarNode newVariable = new VarNode(notTreeDec.getName(),\n\t\t\t\t\t\t\t\t\tparsedModel.getSystemDefn() == null ? notTreeDec.getStartOrDefault() : null, declInt.getLow(), declInt.getHigh(), false);\n\t\t\t\t\t\t\tinTreeNode.add(newVariable);\n\t\t\t\t\t\t\tcIndices[j] = getVarTreeIndexOf(notTreeDec, inTreeNode);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tVarNode newVariable = new VarNode(notTreeDec.getName(),\n\t\t\t\t\t\t\t\t\tparsedModel.getSystemDefn() == null ? notTreeDec.getStartOrDefault() : null, null, null, false);\n\t\t\t\t\t\t\tinTreeNode.add(newVariable);\n\t\t\t\t\t\t\tcIndices[j] = getVarTreeIndexOf(notTreeDec, inTreeNode);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (notTreeDec.getType() instanceof TypeBool) {\n\t\t\t\t\t\tBoolNode newVariable = new BoolNode(notTreeDec.getName(), parsedModel.getSystemDefn() == null ? notTreeDec.getStartOrDefault() : null,\n\t\t\t\t\t\t\t\tfalse);\n\t\t\t\t\t\tinTreeNode.add(newVariable);\n\t\t\t\t\t\tcIndices[j] = getVarTreeIndexOf(notTreeDec, inTreeNode);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\ttheModel.nodesWereInserted(inTreeNode, cIndices);\n\n\t\t\t\t/*  remove variables which are in the tree but not in varInTree or\n\t\t\t\t *  varNotInTree */\n\t\t\t\tArrayList<DeclarationNode> removeNodes = new ArrayList<DeclarationNode>();\n\t\t\t\tfor (int j = 0; j < inTreeNode.getChildCount(); j++) {\n\t\t\t\t\tDeclarationNode vNode = (DeclarationNode) inTreeNode.getChildAt(j);\n\t\t\t\t\tif (!variableExists(vNode, varInTree, varNotInTree)) {\n\t\t\t\t\t\tremoveNodes.add(vNode);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tObject[] remObj = new Object[removeNodes.size()];\n\t\t\t\tint[] remInd = new int[removeNodes.size()];\n\t\t\t\tfor (int j = 0; j < removeNodes.size(); j++) {\n\t\t\t\t\tDeclarationNode vNode = removeNodes.get(j);\n\t\t\t\t\tint index = inTreeNode.getIndex(vNode);\n\t\t\t\t\tremObj[j] = vNode;\n\t\t\t\t\tremInd[j] = index;\n\t\t\t\t}\n\t\t\t\t//remove nodes backwards\n\t\t\t\tfor (int j = removeNodes.size() - 1; j >= 0; j--) {\n\t\t\t\t\tinTreeNode.remove(remInd[j]);\n\t\t\t\t}\n\t\t\t\ttheModel.nodesWereRemoved(inTreeNode, remInd, remObj);\n\t\t\t}\n\n\t\t\t//add modules which are not in the tree\n\t\t\tfor (int i = 0; i < notInTree.size(); i++) {\n\t\t\t\tModule aMod = notInTree.get(i);\n\t\t\t\tModuleNode newNode = new ModuleNode(aMod.getName(), false);\n\t\t\t\t//add variables to this\n\t\t\t\tfor (int j = 0; j < aMod.getNumDeclarations(); j++) {\n\t\t\t\t\tDeclaration aDec = aMod.getDeclaration(j);\n\n\t\t\t\t\tif (aDec.getType() instanceof TypeInt) {\n\t\t\t\t\t\tif (aDec.getDeclType() instanceof DeclarationInt) {\n\t\t\t\t\t\t\tDeclarationInt declInt = (DeclarationInt) aDec.getDeclType();\n\t\t\t\t\t\t\tVarNode newVariable = new VarNode(aDec.getName(), parsedModel.getSystemDefn() == null ? aDec.getStartOrDefault() : null,\n\t\t\t\t\t\t\t\t\tdeclInt.getLow(), declInt.getHigh(), false);\n\t\t\t\t\t\t\tnewNode.add(newVariable);\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\tVarNode newVariable = new VarNode(aDec.getName(), parsedModel.getSystemDefn() == null ? aDec.getStartOrDefault() : null, null,\n\t\t\t\t\t\t\t\t\tnull, false);\n\t\t\t\t\t\t\tnewNode.add(newVariable);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (aDec.getType() instanceof TypeBool) {\n\t\t\t\t\t\tBoolNode newVariable = new BoolNode(aDec.getName(), parsedModel.getSystemDefn() == null ? aDec.getStartOrDefault() : null, false);\n\t\t\t\t\t\tnewNode.add(newVariable);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tmodules.addModule(newNode);\n\t\t\t\tint index = modules.getIndex(newNode);\n\t\t\t\ttheModel.nodesWereInserted(modules, new int[] { index });\n\t\t\t}\n\t\t\t//remove modules from the tree which are not in either inTree or notInTree\n\t\t\tArrayList<DefaultMutableTreeNode> removeNodes = new ArrayList<DefaultMutableTreeNode>();\n\t\t\tfor (int i = 0; i < modules.getChildCount(); i++) {\n\t\t\t\tModuleNode mNode = (ModuleNode) modules.getChildAt(i);\n\t\t\t\tif (!mNode.isEditable() && !moduleExists(mNode, inTree, notInTree)) {\n\t\t\t\t\tremoveNodes.add(mNode);\n\t\t\t\t}\n\t\t\t}\n\t\t\tObject[] remObj = new Object[removeNodes.size()];\n\t\t\tint[] remInd = new int[removeNodes.size()];\n\t\t\tfor (int i = 0; i < removeNodes.size(); i++) {\n\t\t\t\tModuleNode mNode = (ModuleNode) removeNodes.get(i);\n\t\t\t\tint index = modules.getIndex(mNode);\n\t\t\t\tremObj[i] = mNode;\n\t\t\t\tremInd[i] = index;\n\t\t\t}\n\t\t\t//remove nodes backwards\n\t\t\tfor (int i = removeNodes.size() - 1; i >= 0; i--) {\n\t\t\t\tmodules.remove(remInd[i]);\n\t\t\t}\n\t\t\ttheModel.nodesWereRemoved(modules, remInd, remObj);\n\n\t\t\t//DECLARATIONS\n\n\t\t\t//If there is no declaration tree, but we need to have declarations, add the tre\n\t\t\tif (root.getIndex(declarations) == -1 && parsedModel.getNumGlobals() > 0) {\n\t\t\t\troot.add(declarations);\n\t\t\t\ttheModel.nodesWereInserted(root, new int[] { root.getIndex(declarations) });\n\t\t\t}\n\n\t\t\t/*  Create 2 ArrayLists.  One of Declarations in the tree and one of declarations\n\t\t\t *  not in the tree. */\n\t\t\tArrayList<Declaration> decInTree = new ArrayList<Declaration>();\n\t\t\tArrayList<Declaration> decNotInTree = new ArrayList<Declaration>();\n\n\t\t\tfor (int i = 0; i < parsedModel.getNumGlobals(); i++) {\n\t\t\t\tDeclaration d = parsedModel.getGlobal(i);\n\t\t\t\tif (declarationIsMember(d))\n\t\t\t\t\tdecInTree.add(d);\n\t\t\t\telse\n\t\t\t\t\tdecNotInTree.add(d);\n\t\t\t}\n\n\t\t\t//make sure declarations in this declaration tree are valid\n\t\t\tfor (int i = 0; i < decInTree.size(); i++) {\n\t\t\t\tDeclaration inTreeDec = decInTree.get(i);\n\t\t\t\tint decIndex = getIndexOfDec(inTreeDec);\n\t\t\t\tDeclarationNode dNode = (DeclarationNode) declarations.getChildAt(decIndex);\n\t\t\t\tif (dNode instanceof GlobalNode) {\n\t\t\t\t\tGlobalNode vNode = (GlobalNode) declarations.getChildAt(decIndex);\n\t\t\t\t\tvNode.setInitial(parsedModel.getSystemDefn() == null ? inTreeDec.getStartOrDefault() : null);\n\t\t\t\t\tif (inTreeDec.getDeclType() instanceof DeclarationInt) {\n\t\t\t\t\t\tDeclarationInt declInt = (DeclarationInt) inTreeDec.getDeclType();\n\t\t\t\t\t\tvNode.setMin(declInt.getLow());\n\t\t\t\t\t\tvNode.setMax(declInt.getHigh());\n\t\t\t\t\t}\n\t\t\t\t\ttheModel.nodesChanged(vNode, new int[] { 0, 1, 2 });\n\t\t\t\t} else if (dNode instanceof GlobalBoolNode) {\n\t\t\t\t\tGlobalBoolNode bNode = (GlobalBoolNode) dNode;\n\t\t\t\t\tbNode.setInitial(parsedModel.getSystemDefn() == null ? inTreeDec.getStartOrDefault() : null);\n\t\t\t\t\ttheModel.nodesChanged(bNode, new int[] { 0 });\n\t\t\t\t}\n\n\t\t\t}\n\n\t\t\t//add declarations in decNotInTree to the tree\n\t\t\tint[] cIndices = new int[decNotInTree.size()];\n\t\t\tfor (int i = 0; i < decNotInTree.size(); i++) {\n\t\t\t\tDeclaration notTreeDec = decNotInTree.get(i);\n\t\t\t\tif (notTreeDec.getType() instanceof TypeInt) {\n\t\t\t\t\tif (notTreeDec.getDeclType() instanceof DeclarationInt) {\n\t\t\t\t\t\tDeclarationInt declInt = (DeclarationInt) notTreeDec.getDeclType();\n\t\t\t\t\t\tGlobalNode newVariable = new GlobalNode(notTreeDec.getName(), parsedModel.getSystemDefn() == null ? notTreeDec.getStartOrDefault()\n\t\t\t\t\t\t\t\t: null, declInt.getLow(), declInt.getHigh(), false);\n\t\t\t\t\t\tdeclarations.add(newVariable);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tGlobalNode newVariable = new GlobalNode(notTreeDec.getName(), parsedModel.getSystemDefn() == null ? notTreeDec.getStartOrDefault()\n\t\t\t\t\t\t\t\t: null, null, null, false);\n\t\t\t\t\t\tdeclarations.add(newVariable);\n\t\t\t\t\t}\n\t\t\t\t\tcIndices[i] = getIndexOfDec(notTreeDec);\n\t\t\t\t} else if (notTreeDec.getType() instanceof TypeBool) {\n\t\t\t\t\tGlobalBoolNode newVariable = new GlobalBoolNode(notTreeDec.getName(), parsedModel.getSystemDefn() == null ? notTreeDec.getStartOrDefault()\n\t\t\t\t\t\t\t: null, false);\n\t\t\t\t\tdeclarations.add(newVariable);\n\t\t\t\t\tcIndices[i] = getIndexOfDec(notTreeDec);\n\t\t\t\t}\n\t\t\t}\n\t\t\ttheModel.nodesWereInserted(declarations, cIndices);\n\n\t\t\t/*  remove declarations which are in the tree but not in decInTree or\n\t\t\t *  decNotInTree */\n\t\t\tremoveNodes = new ArrayList<DefaultMutableTreeNode>();\n\t\t\tfor (int i = 0; i < declarations.getChildCount(); i++) {\n\t\t\t\tDeclarationNode vNode = (DeclarationNode) declarations.getChildAt(i);\n\t\t\t\tif (!vNode.isEditable() && !declarationExists(vNode, decInTree, decNotInTree)) {\n\t\t\t\t\tremoveNodes.add(vNode);\n\t\t\t\t}\n\t\t\t}\n\t\t\tremObj = new Object[removeNodes.size()];\n\t\t\tremInd = new int[removeNodes.size()];\n\t\t\tfor (int i = 0; i < removeNodes.size(); i++) {\n\t\t\t\tDeclarationNode vNode = (DeclarationNode) removeNodes.get(i);\n\t\t\t\tint index = declarations.getIndex(vNode);\n\t\t\t\tremObj[i] = vNode;\n\t\t\t\tremInd[i] = index;\n\t\t\t}\n\t\t\t//remove nodes backwards\n\t\t\tfor (int i = removeNodes.size() - 1; i >= 0; i--) {\n\t\t\t\tdeclarations.remove(remInd[i]);\n\t\t\t}\n\t\t\ttheModel.nodesWereRemoved(declarations, remInd, remObj);\n\n\t\t\t//CONSTANTS\n\n\t\t\tConstantList csts = parsedModel.getConstantList();\n\t\t\t//If there is no constant tree, but we need to have constant, add the tre\n\t\t\tif (root.getIndex(constants) == -1 && csts.size() > 0) {\n\t\t\t\troot.add(constants);\n\t\t\t\ttheModel.nodesWereInserted(root, new int[] { root.getIndex(constants) });\n\t\t\t}\n\n\t\t\t/*  Create 2 ArrayLists.  One of Constants in the tree and one of constants\n\t\t\t *  not in the tree. */\n\t\t\tArrayList<ConstantNode> conInTree = new ArrayList<ConstantNode>();\n\t\t\tArrayList<ConstantNode> conNotInTree = new ArrayList<ConstantNode>();\n\n\t\t\tfor (int i = 0; i < csts.size(); i++) {\n\t\t\t\tString name = csts.getConstantName(i);\n\t\t\t\tExpression expr = csts.getConstant(i);\n\t\t\t\tType type = csts.getConstantType(i);\n\t\t\t\tConstantNode cn;\n\t\t\t\tif (type instanceof TypeBool) {\n\t\t\t\t\tcn = new BoolConstantNode(name, expr, false);\n\t\t\t\t} else if (type instanceof TypeDouble) {\n\t\t\t\t\tcn = new DoubleConstantNode(name, expr, false);\n\t\t\t\t} else {\n\t\t\t\t\tcn = new IntegerConstantNode(name, expr, false);\n\t\t\t\t}\n\t\t\t\tif (constantIsMember(cn))\n\t\t\t\t\tconInTree.add(cn);\n\t\t\t\telse\n\t\t\t\t\tconNotInTree.add(cn);\n\t\t\t}\n\n\t\t\t//make sure constants in this declaration tree are valid\n\t\t\tfor (int i = 0; i < conInTree.size(); i++) {\n\t\t\t\tConstantNode inTreeCon = conInTree.get(i);\n\t\t\t\tint conIndex = getIndexOfCon(inTreeCon);\n\t\t\t\tConstantNode cNode = (ConstantNode) constants.getChildAt(conIndex);\n\t\t\t\tif (cNode instanceof IntegerConstantNode) {\n\t\t\t\t\tIntegerConstantNode iNode = (IntegerConstantNode) cNode;\n\n\t\t\t\t\tiNode.setName(inTreeCon.getName());\n\t\t\t\t\tiNode.setValue(inTreeCon.getValue());\n\t\t\t\t\ttheModel.nodesChanged(iNode, new int[] { 0 });\n\t\t\t\t} else if (cNode instanceof BoolConstantNode) {\n\t\t\t\t\tBoolConstantNode bNode = (BoolConstantNode) cNode;\n\n\t\t\t\t\tbNode.setName(inTreeCon.getName());\n\t\t\t\t\tbNode.setValue(inTreeCon.getValue());\n\t\t\t\t\ttheModel.nodesChanged(bNode, new int[] { 0 });\n\t\t\t\t} else if (cNode instanceof DoubleConstantNode) {\n\t\t\t\t\tDoubleConstantNode dNode = (DoubleConstantNode) cNode;\n\n\t\t\t\t\tdNode.setName(inTreeCon.getName());\n\t\t\t\t\tdNode.setValue(inTreeCon.getValue());\n\t\t\t\t\ttheModel.nodesChanged(dNode, new int[] { 0 });\n\t\t\t\t}\n\n\t\t\t}\n\n\t\t\t//add declarations in decNotInTree to the tree\n\t\t\tcIndices = new int[conNotInTree.size()];\n\t\t\tfor (int i = 0; i < conNotInTree.size(); i++) {\n\t\t\t\tConstantNode notTreeCon = conNotInTree.get(i);\n\t\t\t\tconstants.add(notTreeCon);\n\t\t\t\tcIndices[i] = getIndexOfCon(notTreeCon);\n\t\t\t}\n\t\t\ttheModel.nodesWereInserted(constants, cIndices);\n\n\t\t\t/*  remove declarations which are in the tree but not in decInTree or\n\t\t\t *  decNotInTree */\n\t\t\tremoveNodes = new ArrayList<DefaultMutableTreeNode>();\n\t\t\tfor (int i = 0; i < constants.getChildCount(); i++) {\n\t\t\t\tConstantNode cNode = (ConstantNode) constants.getChildAt(i);\n\t\t\t\tif (!cNode.isEditable() && !constantExists(cNode, conInTree, conNotInTree)) {\n\t\t\t\t\tremoveNodes.add(cNode);\n\t\t\t\t}\n\t\t\t}\n\t\t\tremObj = new Object[removeNodes.size()];\n\t\t\tremInd = new int[removeNodes.size()];\n\t\t\tfor (int i = 0; i < removeNodes.size(); i++) {\n\t\t\t\tConstantNode vNode = (ConstantNode) removeNodes.get(i);\n\t\t\t\tint index = constants.getIndex(vNode);\n\t\t\t\tremObj[i] = vNode;\n\t\t\t\tremInd[i] = index;\n\t\t\t}\n\t\t\t//remove nodes backwards\n\t\t\tfor (int i = removeNodes.size() - 1; i >= 0; i--) {\n\t\t\t\tconstants.remove(remInd[i]);\n\t\t\t}\n\t\t\ttheModel.nodesWereRemoved(constants, remInd, remObj);\n\n\t\t} else {\n\t\t\t/*String tp = \"<Unknown>\";\n\t\t\tif(!modelType.getValue().equals(tp))\n\t\t\t{\n\t\t\t        modelType.setUserObject(tp);\n\t\t\t        theModel.nodeChanged(modelType);\n\t\t\t}*/\n\t\t}\n\n\t\tif (tree != null)\n\t\t\ttree.repaint();\n\t}\n\n\tpublic void lastParseFailed()\n\t{\n\t\tparseSynchState = TREE_SYNCHRONIZED_BAD;\n\t\ttree.repaint();\n\t}\n\n\tpublic void makeNotUpToDate()\n\t{\n\t\tparseSynchState = TREE_NOT_SYNCHRONIZED;\n\t\ttree.repaint();\n\t}\n\n\tprivate void initComponents()\n\t{\n\t\ttree = new JTree(theModel)\n\t\t{\n\t\t\tpublic String getToolTipText(MouseEvent event)\n\t\t\t{\n\t\t\t\tString ret = null;\n\t\t\t\tTreePath selectedPath = tree.getPathForLocation(event.getX(), event.getY());\n\t\t\t\tif (selectedPath != null) {\n\t\t\t\t\t//if(selectedPath.getLastPathComponent() instanceof ModelRootNode)\n\t\t\t\t\tif (parseSynchState == TREE_SYNCHRONIZED_BAD)\n\t\t\t\t\t\treturn handler.getParseErrorMessage();\n\t\t\t\t\telse if (parseSynchState == TREE_SYNCHRONIZED_GOOD)\n\t\t\t\t\t\treturn \"Model parsed successfully\";\n\t\t\t\t\telse if (!handler.isAutoParse())\n\t\t\t\t\t\treturn \"Auto-parsing disabled\";\n\t\t\t\t\telse\n\t\t\t\t\t\treturn \"Model not parsed\";\n\t\t\t\t}\n\n\t\t\t\treturn ret;\n\t\t\t}\n\n\t\t\tpublic boolean isPathEditable(TreePath path)\n\t\t\t{\n\t\t\t\tObject c = path.getLastPathComponent();\n\t\t\t\tif (c instanceof ValueNode) {\n\t\t\t\t\tValueNode v = (ValueNode) c;\n\t\t\t\t\treturn v.isEditable();\n\t\t\t\t}\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t};\n\t\tPrismNodeRenderer prnr = new PrismNodeRenderer();\n\t\ttree.setCellRenderer(prnr);\n\t\t/*JComboBox typeCombo = new JComboBox(new Object[]\n\t\t{\"Probabilistic\", \"Non-deterministic\", \"Stochastic\"});\n\t\ttypeCombo.setFont(tree.getFont());\n\t\ttypeCombo.setBackground(tree.getBackground());\n\t\tValueNodeCellEditor cellEdit = new ValueNodeCellEditor(new JTextField(), typeCombo);\n\t\ttree.setCellEditor(new DefaultTreeCellEditor(tree, prnr, cellEdit));*/\n\t\ttree.setEditable(true);\n\t\ttree.setCellEditor(new GUIMultiModelTree.ModelTreeCellEditor(tree, prnr));\n\n\t\tsetLayout(new BorderLayout());\n\t\tJScrollPane scr = new JScrollPane();\n\t\tscr.setViewportView(tree);\n\t\tadd(scr, BorderLayout.CENTER);\n\n\t\tmoduleCollectionPopup = new JPopupMenu();\n\t\taddModule = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_addModule();\n\t\t\t}\n\t\t};\n\t\taddModule.putValue(Action.LONG_DESCRIPTION, \"Adds an editable module to the tree\");\n\t\taddModule.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_A));\n\t\taddModule.putValue(Action.NAME, \"Add Module\");\n\t\tmoduleCollectionPopup.add(addModule);\n\n\t\tdeclarationCollectionPopup = new JPopupMenu();\n\t\taddIntegerGlobal = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_addIntegerGlobal();\n\t\t\t}\n\t\t};\n\t\taddIntegerGlobal.putValue(Action.NAME, \"Add Global Integer\");\n\t\taddBooleanGlobal = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_addBooleanGlobal();\n\t\t\t}\n\t\t};\n\t\taddBooleanGlobal.putValue(Action.NAME, \"Add Global Boolean\");\n\t\tdeclarationCollectionPopup.add(addIntegerGlobal);\n\t\tdeclarationCollectionPopup.add(addBooleanGlobal);\n\n\t\tconstantsCollectionPopup = new JPopupMenu();\n\t\taddIntegerConstant = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_addIntegerConstant();\n\t\t\t}\n\t\t};\n\t\taddIntegerConstant.putValue(Action.NAME, \"Add Integer Constant\");\n\t\taddBooleanConstant = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_addBooleanConstant();\n\t\t\t}\n\t\t};\n\t\taddBooleanConstant.putValue(Action.NAME, \"Add Boolean Constant\");\n\t\taddDoubleConstant = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_addDoubleConstant();\n\t\t\t}\n\t\t};\n\t\taddDoubleConstant.putValue(Action.NAME, \"Add Double Constant\");\n\t\tconstantsCollectionPopup.add(addIntegerConstant);\n\t\tconstantsCollectionPopup.add(addBooleanConstant);\n\t\tconstantsCollectionPopup.add(addDoubleConstant);\n\n\t\tmodulePopup = new JPopupMenu();\n\t\tremoveModule = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (lastPopNode != null && lastPopNode instanceof ModuleNode) {\n\t\t\t\t\ta_removeModule((ModuleNode) lastPopNode);\n\t\t\t\t\tlastPopNode = null;\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\tremoveModule.putValue(Action.NAME, \"Remove\");\n\t\taddBoolean = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (lastPopNode != null && lastPopNode instanceof ModuleNode) {\n\t\t\t\t\ta_addLocalBoolean((ModuleNode) lastPopNode);\n\t\t\t\t\tlastPopNode = null;\n\t\t\t\t}\n\n\t\t\t}\n\t\t};\n\t\taddBoolean.putValue(Action.NAME, \"Add Boolean Variable\");\n\t\taddInteger = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (lastPopNode != null && lastPopNode instanceof ModuleNode) {\n\t\t\t\t\ta_addLocalInteger((ModuleNode) lastPopNode);\n\t\t\t\t\tlastPopNode = null;\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\taddInteger.putValue(Action.NAME, \"Add Integer Variable\");\n\t\trenameModule = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (lastPopNode != null && lastPopNode instanceof ModuleNode) {\n\t\t\t\t\ta_renameModule((ModuleNode) lastPopNode);\n\t\t\t\t\tlastPopNode = null;\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\trenameModule.putValue(Action.NAME, \"Rename\");\n\t\tmodulePopup.add(renameModule);\n\t\tmodulePopup.add(removeModule);\n\t\t//modulePopup.add(new JSplitter());\n\t\tmodulePopup.add(addInteger);\n\t\tmodulePopup.add(addBoolean);\n\n\t\tdeclarationPopup = new JPopupMenu();\n\t\tremoveDeclaration = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (lastPopNode != null) {\n\t\t\t\t\tif (lastPopNode instanceof BoolNode || lastPopNode instanceof VarNode) {\n\t\t\t\t\t\tModuleNode m = whichModule((DeclarationNode) lastPopNode);\n\t\t\t\t\t\tif (m != null)\n\t\t\t\t\t\t\ta_removeVariable((DeclarationNode) lastPopNode, m);\n\t\t\t\t\t} else if (lastPopNode instanceof GlobalNode || lastPopNode instanceof GlobalBoolNode) {\n\t\t\t\t\t\ta_removeGlobal((DeclarationNode) lastPopNode);\n\t\t\t\t\t} else if (lastPopNode instanceof ConstantNode) {\n\t\t\t\t\t\ta_removeConstant((ConstantNode) lastPopNode);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\tremoveDeclaration.putValue(Action.NAME, \"Remove\");\n\t\tdeclarationPopup.add(removeDeclaration);\n\n\t\trenameDeclaration = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (lastPopNode != null) {\n\t\t\t\t\ta_renameDeclaration((DeclarationNode) lastPopNode);\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\trenameDeclaration.putValue(Action.NAME, \"Rename\");\n\t\tdeclarationPopup.add(renameDeclaration);\n\n\t\texpressionPopup = new JPopupMenu();\n\n\t\teditExpression = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (lastPopNode != null) {\n\t\t\t\t\ta_editExpression((ExpressionNode) lastPopNode);\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\teditExpression.putValue(Action.NAME, \"Edit\");\n\t\texpressionPopup.add(editExpression);\n\n\t\tmodelTypePopup = new JPopupMenu();\n\n\t\tnon = new JRadioButton(\"Non-deterministic (mdp)\");\n\t\tpro = new JRadioButton(\"Probabilistic (dtmc)\");\n\t\tsto = new JRadioButton(\"Stochastic (ctmc)\");\n\n\t\tButtonGroup gro = new ButtonGroup();\n\t\tgro.add(non);\n\t\tgro.add(pro);\n\t\tgro.add(sto);\n\n\t\tnon.setSelected(true);\n\n\t\tmodelTypePopup.add(non);\n\t\tmodelTypePopup.add(pro);\n\t\tmodelTypePopup.add(sto);\n\n\t\tnon.addActionListener(new ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (non.isSelected())\n\t\t\t\t\ta_setModelType(ModelType.MDP);\n\t\t\t\tmodelTypePopup.setVisible(false);\n\t\t\t}\n\t\t});\n\n\t\tpro.addActionListener(new ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (pro.isSelected())\n\t\t\t\t\ta_setModelType(ModelType.DTMC);\n\t\t\t\tmodelTypePopup.setVisible(false);\n\t\t\t}\n\t\t});\n\n\t\tsto.addActionListener(new ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (sto.isSelected())\n\t\t\t\t\ta_setModelType(ModelType.CTMC);\n\t\t\t\tmodelTypePopup.setVisible(false);\n\t\t\t}\n\t\t});\n\t}\n\n\tpublic ModuleNode whichModule(DeclarationNode isIt)\n\t{\n\t\tfor (int i = 0; i < editableModules.size(); i++) {\n\t\t\tModuleNode mod = editableModules.get(i);\n\t\t\tint index = mod.getIndex(isIt);\n\t\t\tif (index > -1) {\n\t\t\t\treturn mod;\n\t\t\t}\n\t\t}\n\t\treturn null;\n\t}\n\n\tpublic void mouseClicked(MouseEvent e)\n\t{\n\t}\n\n\tpublic void mouseEntered(MouseEvent e)\n\t{\n\t}\n\n\tpublic void mouseExited(MouseEvent e)\n\t{\n\t}\n\n\tpublic void mousePressed(MouseEvent e)\n\t{\n\t\tif (e.isPopupTrigger()) {\n\t\t\tlastPopNode = null;\n\t\t\t//root popup\n\t\t\tif (tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(root.getPath()))) {\n\t\t\t\ttree.setSelectionPath(new TreePath(root.getPath()));\n\t\t\t\t//now the root is selected, show the popup\n\t\t\t\t//(diabled for now)\n\t\t\t\t//((GUIMultiModel)(handler.getGUIPlugin())).getPopup().show(tree, e.getX(), e.getY());\n\t\t\t}\n\t\t\t//model type node\n\t\t\tif (editable && tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(modelType.getPath()))) {\n\t\t\t\ttree.setSelectionPath(new TreePath(modelType.getPath()));\n\t\t\t\tmodelTypePopup.show(tree, e.getX(), e.getY());\n\t\t\t}\n\t\t\t//module collection popup\n\t\t\telse if (editable && modules != null && tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(modules.getPath()))) {\n\t\t\t\ttree.setSelectionPath(new TreePath(modules.getPath()));\n\t\t\t\tmoduleCollectionPopup.show(tree, e.getX(), e.getY());\n\t\t\t}\n\t\t\t//declaration collection popup\n\t\t\telse if (editable && declarations != null && tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(declarations.getPath()))) {\n\t\t\t\ttree.setSelectionPath(new TreePath(declarations.getPath()));\n\t\t\t\tdeclarationCollectionPopup.show(tree, e.getX(), e.getY());\n\t\t\t} else if (editable && constants != null && tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(constants.getPath())))//constant collection node\n\t\t\t{\n\t\t\t\ttree.setSelectionPath(new TreePath(constants.getPath()));\n\t\t\t\tconstantsCollectionPopup.show(tree, e.getX(), e.getY());\n\t\t\t} else // is the path on a ModuleNode or a DeclarationNode or an ExpressionNode\n\t\t\t{\n\t\t\t\tTreePath selectedPath = tree.getClosestPathForLocation(e.getX(), e.getY());\n\t\t\t\tfor (int i = 0; i < editableModules.size(); i++) //search each module\n\t\t\t\t{\n\t\t\t\t\tModuleNode mn = editableModules.get(i);\n\t\t\t\t\tif (new TreePath(mn.getPath()).equals(selectedPath)) {\n\t\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\t\tif (mn.isEditable()) {\n\t\t\t\t\t\t\tmodulePopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\tlastPopNode = mn;\n\t\t\t\t\t\t}\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t\tfor (int j = 0; j < mn.getChildCount(); j++)//search local variables\n\t\t\t\t\t{\n\t\t\t\t\t\tDeclarationNode dn = (DeclarationNode) mn.getChildAt(j);\n\t\t\t\t\t\tif (new TreePath(dn.getPath()).equals(selectedPath)) {\n\t\t\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\t\t\tif (dn.isEditable()) {\n\t\t\t\t\t\t\t\tdeclarationPopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\t\tlastPopNode = dn;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\treturn;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfor (int i = 0; i < editableDeclarations.size(); i++)//search globals\n\t\t\t\t{\n\t\t\t\t\tDeclarationNode dn = editableDeclarations.get(i);\n\t\t\t\t\tif (new TreePath(dn.getPath()).equals(selectedPath)) {\n\t\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\t\tif (dn.isEditable()) {\n\t\t\t\t\t\t\tdeclarationPopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\tlastPopNode = dn;\n\t\t\t\t\t\t}\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfor (int i = 0; i < editableConstants.size(); i++)//search constants\n\t\t\t\t{\n\t\t\t\t\tDeclarationNode dn = editableConstants.get(i);\n\t\t\t\t\tif (new TreePath(dn.getPath()).equals(selectedPath)) {\n\t\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\t\tif (dn.isEditable()) {\n\t\t\t\t\t\t\tdeclarationPopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\tlastPopNode = dn;\n\t\t\t\t\t\t}\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t//Could be an ExpressionNode\n\t\t\t\tif (tree.getSelectionPath() != null) {\n\t\t\t\t\tTreeNode selectedNode = (TreeNode) tree.getSelectionPath().getLastPathComponent();\n\t\t\t\t\tif (selectedNode instanceof ExpressionNode) {\n\t\t\t\t\t\tExpressionNode en = (ExpressionNode) selectedNode;\n\t\t\t\t\t\tif (en.isEditable()) {\n\t\t\t\t\t\t\texpressionPopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\tlastPopNode = en;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t}\n\n\t\t} else {\n\t\t\tTreePath selectedPath = tree.getClosestPathForLocation(e.getX(), e.getY());\n\t\t\tfor (int i = 0; i < editableModules.size(); i++) //search each module\n\t\t\t{\n\t\t\t\tModuleNode mn = editableModules.get(i);\n\t\t\t\tif (new TreePath(mn.getPath()).equals(selectedPath)) {\n\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t}\n\n\tpublic void mouseReleased(MouseEvent e)\n\t{\n\t\tif (e.isPopupTrigger()) {\n\t\t\tlastPopNode = null;\n\t\t\t//root popup\n\t\t\tif (tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(root.getPath()))) {\n\t\t\t\ttree.setSelectionPath(new TreePath(root.getPath()));\n\t\t\t\t//now the root is selected, show the popup\n\t\t\t\t//(diabled for now)\n\t\t\t\t//((GUIMultiModel)(handler.getGUIPlugin())).getPopup().show(tree, e.getX(), e.getY());\n\t\t\t}\n\t\t\t//model type node\n\t\t\tif (editable && tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(modelType.getPath()))) {\n\t\t\t\ttree.setSelectionPath(new TreePath(modelType.getPath()));\n\t\t\t\tmodelTypePopup.show(tree, e.getX(), e.getY());\n\t\t\t}\n\t\t\t//module collection popup\n\t\t\telse if (editable && modules != null && tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(modules.getPath()))) {\n\t\t\t\ttree.setSelectionPath(new TreePath(modules.getPath()));\n\t\t\t\tmoduleCollectionPopup.show(tree, e.getX(), e.getY());\n\t\t\t}\n\t\t\t//declaration collection popup\n\t\t\telse if (editable && declarations != null && tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(declarations.getPath()))) {\n\t\t\t\ttree.setSelectionPath(new TreePath(declarations.getPath()));\n\t\t\t\tdeclarationCollectionPopup.show(tree, e.getX(), e.getY());\n\t\t\t} else if (editable && constants != null && tree.getClosestPathForLocation(e.getX(), e.getY()).equals(new TreePath(constants.getPath())))//constant collection node\n\t\t\t{\n\t\t\t\ttree.setSelectionPath(new TreePath(constants.getPath()));\n\t\t\t\tconstantsCollectionPopup.show(tree, e.getX(), e.getY());\n\t\t\t} else // is the path on a ModuleNode or a DeclarationNode or an ExpressionNode\n\t\t\t{\n\t\t\t\tTreePath selectedPath = tree.getClosestPathForLocation(e.getX(), e.getY());\n\t\t\t\tfor (int i = 0; i < editableModules.size(); i++) //search each module\n\t\t\t\t{\n\t\t\t\t\tModuleNode mn = editableModules.get(i);\n\t\t\t\t\tif (new TreePath(mn.getPath()).equals(selectedPath)) {\n\t\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\t\tif (mn.isEditable()) {\n\t\t\t\t\t\t\tmodulePopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\tlastPopNode = mn;\n\t\t\t\t\t\t}\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t\tfor (int j = 0; j < mn.getChildCount(); j++)//search local variables\n\t\t\t\t\t{\n\t\t\t\t\t\tDeclarationNode dn = (DeclarationNode) mn.getChildAt(j);\n\t\t\t\t\t\tif (new TreePath(dn.getPath()).equals(selectedPath)) {\n\t\t\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\t\t\tif (dn.isEditable()) {\n\t\t\t\t\t\t\t\tdeclarationPopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\t\tlastPopNode = dn;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\treturn;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfor (int i = 0; i < editableDeclarations.size(); i++)//search globals\n\t\t\t\t{\n\t\t\t\t\tDeclarationNode dn = editableDeclarations.get(i);\n\t\t\t\t\tif (new TreePath(dn.getPath()).equals(selectedPath)) {\n\t\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\t\tif (dn.isEditable()) {\n\t\t\t\t\t\t\tdeclarationPopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\tlastPopNode = dn;\n\t\t\t\t\t\t}\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfor (int i = 0; i < editableConstants.size(); i++)//search constants\n\t\t\t\t{\n\t\t\t\t\tDeclarationNode dn = editableConstants.get(i);\n\t\t\t\t\tif (new TreePath(dn.getPath()).equals(selectedPath)) {\n\t\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\t\tif (dn.isEditable()) {\n\t\t\t\t\t\t\tdeclarationPopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\tlastPopNode = dn;\n\t\t\t\t\t\t}\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t//Could be an ExpressionNode\n\t\t\t\tif (tree.getSelectionPath() != null) {\n\t\t\t\t\tTreeNode selectedNode = (TreeNode) tree.getSelectionPath().getLastPathComponent();\n\t\t\t\t\tif (selectedNode instanceof ExpressionNode) {\n\t\t\t\t\t\tExpressionNode en = (ExpressionNode) selectedNode;\n\t\t\t\t\t\tif (en.isEditable()) {\n\t\t\t\t\t\t\texpressionPopup.show(tree, e.getX(), e.getY());\n\t\t\t\t\t\t\tlastPopNode = en;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t}\n\n\t\t} else {\n\t\t\tTreePath selectedPath = tree.getClosestPathForLocation(e.getX(), e.getY());\n\t\t\tfor (int i = 0; i < editableModules.size(); i++) //search each module\n\t\t\t{\n\t\t\t\tModuleNode mn = editableModules.get(i);\n\t\t\t\tif (new TreePath(mn.getPath()).equals(selectedPath)) {\n\t\t\t\t\ttree.setSelectionPath(selectedPath);\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t}\n\n\tpublic String getToolTipText()\n\t{\n\t\treturn handler.getParseErrorMessage();\n\t}\n\n\tpublic ModelType getModelType()\n\t{\n\t\treturn ModelType.valueOf(modelType.getUserObject().toString());\n\t}\n\n\tpublic static final String TAB = \"\t\";\n\n\tpublic ArrayList<String> getEditableConstantNames()\n\t{\n\t\tArrayList<String> names = new ArrayList<String>();\n\t\tfor (int i = 0; i < editableConstants.size(); i++) {\n\t\t\tDeclarationNode dn = editableConstants.get(i);\n\t\t\tnames.add(dn.getName());\n\t\t}\n\t\treturn names;\n\t}\n\n\tpublic ArrayList<String> getEditableConstantValues()\n\t{\n\t\tArrayList<String> values = new ArrayList<String>();\n\t\tfor (int i = 0; i < editableConstants.size(); i++) {\n\t\t\tConstantNode cn = editableConstants.get(i);\n\t\t\tif (cn.getValue() != null) {\n\t\t\t\tif (!cn.getValue().toString().equals(\"\")) {\n\t\t\t\t\tvalues.add(cn.getValue().toString());\n\t\t\t\t} else\n\t\t\t\t\tvalues.add(null);\n\t\t\t} else\n\t\t\t\tvalues.add(null);\n\t\t}\n\t\treturn values;\n\t}\n\n\tpublic ArrayList<Type> getEditableConstantTypes()\n\t{\n\t\tArrayList<Type> types = new ArrayList<Type>();\n\t\tfor (int i = 0; i < editableConstants.size(); i++) {\n\t\t\tObject node = editableConstants.get(i);\n\t\t\tif (node instanceof BoolConstantNode) {\n\t\t\t\ttypes.add(TypeBool.getInstance());\n\t\t\t} else if (node instanceof IntegerConstantNode) {\n\t\t\t\ttypes.add(TypeInt.getInstance());\n\t\t\t} else if (node instanceof DoubleConstantNode) {\n\t\t\t\ttypes.add(TypeDouble.getInstance());\n\t\t\t} else\n\t\t\t\ttypes.add(null);\n\t\t}\n\t\treturn types;\n\t}\n\n\tpublic ArrayList<String> getEditableGlobalNames()\n\t{\n\t\tArrayList<String> names = new ArrayList<String>();\n\t\tfor (int i = 0; i < editableDeclarations.size(); i++) {\n\t\t\tDeclarationNode dn = editableDeclarations.get(i);\n\t\t\tnames.add(dn.getName());\n\t\t}\n\t\treturn names;\n\t}\n\n\tpublic ArrayList<String> getEditableGlobalMins()\n\t{\n\t\tArrayList<String> mins = new ArrayList<String>();\n\t\tfor (int i = 0; i < editableDeclarations.size(); i++) {\n\t\t\tObject node = editableDeclarations.get(i);\n\t\t\tif (node instanceof GlobalNode) {\n\t\t\t\tGlobalNode gn = (GlobalNode) node;\n\t\t\t\tmins.add(gn.getMin().toString());\n\t\t\t} else\n\t\t\t\tmins.add(null);\n\t\t}\n\t\treturn mins;\n\t}\n\n\tpublic ArrayList<String> getEditableGlobalMaxs()\n\t{\n\t\tArrayList<String> maxs = new ArrayList<String>();\n\t\tfor (int i = 0; i < editableDeclarations.size(); i++) {\n\t\t\tObject node = editableDeclarations.get(i);\n\t\t\tif (node instanceof GlobalNode) {\n\t\t\t\tGlobalNode gn = (GlobalNode) node;\n\t\t\t\tmaxs.add(gn.getMax().toString());\n\t\t\t} else\n\t\t\t\tmaxs.add(null);\n\n\t\t}\n\t\treturn maxs;\n\t}\n\n\tpublic ArrayList<String> getEditableGlobalInits()\n\t{\n\t\tArrayList<String> inits = new ArrayList<String>();\n\t\tfor (int i = 0; i < editableDeclarations.size(); i++) {\n\t\t\tObject node = editableDeclarations.get(i);\n\t\t\tif (node instanceof GlobalNode) {\n\t\t\t\tGlobalNode gn = (GlobalNode) node;\n\t\t\t\tinits.add(gn.getInitial().toString());\n\t\t\t} else if (node instanceof GlobalBoolNode) {\n\t\t\t\tGlobalBoolNode gbn = (GlobalBoolNode) node;\n\t\t\t\tinits.add(gbn.getInitial().toString());\n\t\t\t}\n\t\t}\n\t\treturn inits;\n\t}\n\n\tpublic ArrayList<Type> getEditableGlobalTypes()\n\t{\n\t\tArrayList<Type> types = new ArrayList<Type>();\n\t\tfor (int i = 0; i < editableDeclarations.size(); i++) {\n\t\t\tObject node = editableDeclarations.get(i);\n\t\t\tif (node instanceof GlobalBoolNode) {\n\t\t\t\ttypes.add(TypeBool.getInstance());\n\t\t\t} else if (node instanceof GlobalNode) {\n\t\t\t\ttypes.add(TypeInt.getInstance());\n\t\t\t} else\n\t\t\t\ttypes.add(null);\n\t\t}\n\t\treturn types;\n\t}\n\n\tpublic ArrayList<String> getVariableNames(ModuleNode m)\n\t{\n\t\tArrayList<String> names = new ArrayList<String>();\n\t\tfor (int i = 0; i < m.getChildCount(); i++) {\n\t\t\tDeclarationNode vn = (DeclarationNode) m.getChildAt(i);\n\t\t\tif (!(vn instanceof StateVarNode)) {\n\t\t\t\tnames.add(vn.getName());\n\t\t\t}\n\t\t}\n\t\treturn names;\n\t}\n\n\tpublic ArrayList<Type> getVariableTypes(ModuleNode m)\n\t{\n\t\tArrayList<Type> types = new ArrayList<Type>();\n\t\tfor (int i = 0; i < m.getChildCount(); i++) {\n\t\t\tDeclarationNode dn = (DeclarationNode) m.getChildAt(i);\n\t\t\tif (!(dn instanceof StateVarNode)) {\n\t\t\t\tif (dn instanceof BoolNode)\n\t\t\t\t\ttypes.add(TypeBool.getInstance());\n\t\t\t\telse if (dn instanceof VarNode)\n\t\t\t\t\ttypes.add(TypeInt.getInstance());\n\t\t\t\telse\n\t\t\t\t\ttypes.add(null);\n\t\t\t}\n\t\t}\n\t\treturn types;\n\t}\n\n\tpublic ArrayList<String> getVariableMins(ModuleNode m)\n\t{\n\t\tArrayList<String> mins = new ArrayList<String>();\n\t\tfor (int i = 0; i < m.getChildCount(); i++) {\n\t\t\tDeclarationNode dn = (DeclarationNode) m.getChildAt(i);\n\t\t\tif (!(dn instanceof StateVarNode)) {\n\t\t\t\tif (dn instanceof BoolNode)\n\t\t\t\t\tmins.add(null);\n\t\t\t\telse if (dn instanceof VarNode) {\n\t\t\t\t\tVarNode vn = (VarNode) dn;\n\t\t\t\t\tString s = vn.getMin().toString();\n\t\t\t\t\tmins.add(s);\n\t\t\t\t} else\n\t\t\t\t\tmins.add(null);\n\t\t\t}\n\t\t}\n\t\treturn mins;\n\t}\n\n\tpublic ArrayList<String> getVariableMaxs(ModuleNode m)\n\t{\n\t\tArrayList<String> maxs = new ArrayList<String>();\n\t\tfor (int i = 0; i < m.getChildCount(); i++) {\n\t\t\tDeclarationNode dn = (DeclarationNode) m.getChildAt(i);\n\t\t\tif (!(dn instanceof StateVarNode)) {\n\t\t\t\tif (dn instanceof BoolNode)\n\t\t\t\t\tmaxs.add(null);\n\t\t\t\telse if (dn instanceof VarNode) {\n\t\t\t\t\tVarNode vn = (VarNode) dn;\n\t\t\t\t\tString s = vn.getMax().toString();\n\t\t\t\t\tmaxs.add(s);\n\t\t\t\t} else\n\t\t\t\t\tmaxs.add(null);\n\t\t\t}\n\t\t}\n\t\treturn maxs;\n\t}\n\n\tpublic ArrayList<String> getVariableInits(ModuleNode m)\n\t{\n\t\tArrayList<String> inits = new ArrayList<String>();\n\t\tfor (int i = 0; i < m.getChildCount(); i++) {\n\t\t\tDeclarationNode dn = (DeclarationNode) m.getChildAt(i);\n\t\t\tif (!(dn instanceof StateVarNode)) {\n\t\t\t\tif (dn instanceof BoolNode) {\n\t\t\t\t\tBoolNode bn = (BoolNode) dn;\n\t\t\t\t\tString s = bn.getInitial().toString();\n\t\t\t\t\tinits.add(s);\n\t\t\t\t} else if (dn instanceof VarNode) {\n\t\t\t\t\tVarNode vn = (VarNode) dn;\n\t\t\t\t\tString s = vn.getInitial().toString();\n\t\t\t\t\tinits.add(s);\n\t\t\t\t} else\n\t\t\t\t\tinits.add(null);\n\t\t\t}\n\t\t}\n\t\treturn inits;\n\t}\n\n\tpublic void updateTooltip()\n\t{\n\t\ttree.setToolTipText(handler.getParseErrorMessage());\n\t}\n\n\t//Node Data Structure Classes\n\n\tinterface PrismTreeNode\n\t{\n\t\tpublic boolean isEditable();\n\t}\n\n\tclass ModelRootNode extends DefaultMutableTreeNode implements PrismTreeNode\n\t{\n\t\tpublic ModelRootNode()\n\t\t{\n\t\t\tsuper(\"\", true);\n\t\t}\n\n\t\tpublic boolean isEditable()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t}\n\n\tclass ModuleCollectionNode extends DefaultMutableTreeNode implements PrismTreeNode\n\t{\n\t\tpublic ModuleCollectionNode()\n\t\t{\n\t\t\tsuper(\"Modules\", true);\n\t\t\tsuper.setAllowsChildren(true);\n\t\t}\n\n\t\tpublic void addModule(ModuleNode mod)\n\t\t{\n\t\t\tadd(mod);\n\t\t}\n\n\t\tpublic void removeModule(ModuleNode mod)\n\t\t{\n\t\t\tremove(mod);\n\t\t}\n\n\t\tpublic boolean isEditable()\n\t\t{\n\t\t\treturn editable;\n\t\t}\n\n\t}\n\n\tclass DeclarationCollectionNode extends DefaultMutableTreeNode implements PrismTreeNode\n\t{\n\t\tpublic DeclarationCollectionNode()\n\t\t{\n\t\t\tsuper(\"Global Variables\", true);\n\t\t\tsuper.setAllowsChildren(true);\n\t\t}\n\n\t\tpublic void addDeclaration(DeclarationNode dec)\n\t\t{\n\t\t\tadd(dec);\n\t\t}\n\n\t\tpublic void removeDeclaration(DeclarationNode dec)\n\t\t{\n\t\t\tremove(dec);\n\t\t}\n\n\t\tpublic boolean isEditable()\n\t\t{\n\t\t\treturn editable;\n\t\t}\n\n\t}\n\n\tclass ConstantCollectionNode extends DefaultMutableTreeNode implements PrismTreeNode\n\t{\n\t\tpublic ConstantCollectionNode()\n\t\t{\n\t\t\tsuper(\"Constants\", true);\n\t\t}\n\n\t\tpublic void addConstant(ConstantNode n)\n\t\t{\n\t\t\tadd(n);\n\t\t}\n\n\t\tpublic void removeConstant(ConstantNode n)\n\t\t{\n\t\t\tremove(n);\n\t\t}\n\n\t\tpublic boolean isEditable()\n\t\t{\n\t\t\treturn editable;\n\t\t}\n\t}\n\n\tpublic class ModuleNode extends DefaultMutableTreeNode implements PrismTreeNode\n\t{\n\t\tprivate boolean editable;\n\n\t\tpublic ModuleNode(String moduleName, boolean editable)\n\t\t{\n\t\t\tsuper(moduleName, true);\n\t\t\tthis.editable = editable;\n\t\t}\n\n\t\tpublic void addVariable(VarNode var)\n\t\t{\n\t\t\tadd(var);\n\t\t}\n\n\t\tpublic void removeVariable(VarNode var)\n\t\t{\n\t\t\tremove(var);\n\t\t}\n\n\t\tpublic void setName(String str)\n\t\t{\n\t\t\tsetUserObject(str);\n\t\t}\n\n\t\tpublic String getName()\n\t\t{\n\t\t\treturn (String) getUserObject();\n\t\t}\n\n\t\tpublic boolean isEditable()\n\t\t{\n\t\t\treturn editable;\n\t\t}\n\n\t\tpublic void setEditable(boolean b)\n\t\t{\n\t\t\teditable = b;\n\t\t}\n\n\t\tpublic void childrenChanged()\n\t\t{\n\t\t\ttheModel.nodeChanged(this);\n\t\t\ttheModel.nodeStructureChanged(this);\n\t\t}\n\n\t\tpublic boolean isLeaf()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t}\n\n\t//Editor for ModuleNode\n\tclass ModuleEditor extends JTextField implements TreeCellEditor\n\t{\n\t\tString name;\n\t\tVector<CellEditorListener> listeners = new Vector<CellEditorListener>();\n\t\tprivate static final int minWidth = 64;\n\n\t\tpublic ModuleEditor()\n\t\t{\n\t\t\tsuper(\"\");\n\t\t\taddActionListener(new ActionListener()\n\t\t\t{\n\t\t\t\tpublic void actionPerformed(ActionEvent as)\n\t\t\t\t{\n\t\t\t\t\tif (stopCellEditing())\n\t\t\t\t\t\tfireEditingStopped();\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\tpublic void cancelCellEditing()\n\t\t{\n\t\t\tsetText(\"\");\n\t\t}\n\n\t\tpublic boolean stopCellEditing()\n\t\t{\n\t\t\tExpression exp;\n\t\t\tString str = getText();\n\t\t\ttry {\n\t\t\t\texp = Prism.parseSingleExpressionString(str);\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (exp instanceof ExpressionIdent) {\n\t\t\t\tname = str;\n\t\t\t\treturn true;\n\t\t\t} else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\tpublic Object getCellEditorValue()\n\t\t{\n\t\t\treturn name;\n\t\t}\n\n\t\tpublic boolean isCellEditable(EventObject eo)\n\t\t{\n\t\t\tif ((eo == null) | ((eo instanceof MouseEvent) && (((MouseEvent) eo).isMetaDown()))) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic boolean shouldSelectCell(EventObject eo)\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\tpublic void removeCellEditroLIstner(CellEditorListener cel)\n\t\t{\n\t\t\tlisteners.removeElement(cel);\n\t\t}\n\n\t\tprotected void fireEditingStopped()\n\t\t{\n\t\t\tif (listeners.size() > 0) {\n\t\t\t\tChangeEvent ce = new ChangeEvent(this);\n\t\t\t\tfor (int i = listeners.size() - 1; i >= 0; i--) {\n\t\t\t\t\tlisteners.elementAt(i).editingStopped(ce);\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\t//make sure the JTree gives the editor enough space\n\t\tpublic void setBounds(Rectangle r)\n\t\t{\n\t\t\tr.width = Math.max(minWidth, r.width);\n\t\t\tsuper.setBounds(r);\n\t\t}\n\n\t\tpublic void setBounds(int x, int y, int w, int h)\n\t\t{\n\t\t\tw = Math.max(minWidth, w);\n\t\t\tsuper.setBounds(x, y, w, h);\n\t\t}\n\n\t\tpublic void addCellEditorListener(CellEditorListener l)\n\t\t{\n\t\t\tlisteners.addElement(l);\n\t\t}\n\n\t\tpublic void removeCellEditorListener(CellEditorListener l)\n\t\t{\n\t\t\tlisteners.removeElement(l);\n\t\t}\n\n\t\tpublic Component getTreeCellEditorComponent(JTree tree, Object value, boolean isSelected, boolean expanded, boolean leaf, int row)\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t//same listener and bounds methods as above\n\t}\n\n\tpublic static final int LOCAL_INTEGER = 0;\n\tpublic static final int LOCAL_BOOL = 1;\n\tpublic static final int GLOBAL_INTEGER = 2;\n\tpublic static final int GLOBAL_BOOL = 3;\n\tpublic static final int CONST_INTEGER = 4;\n\tpublic static final int CONST_BOOL = 5;\n\tpublic static final int CONST_DOUBLE = 6;\n\n\tabstract class DeclarationNode extends DefaultMutableTreeNode implements PrismTreeNode\n\t{\n\t\tprivate boolean editable;\n\t\tprivate int type;\n\n\t\tpublic DeclarationNode(int type, String name, boolean editable)\n\t\t{\n\t\t\tsuper(name, true);\n\t\t\tthis.editable = editable;\n\t\t\tthis.type = type;\n\t\t}\n\n\t\tpublic boolean getAllowsChildren()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\tpublic boolean isLeaf()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic boolean isEditable()\n\t\t{\n\t\t\treturn editable;\n\t\t}\n\n\t\tpublic String getName()\n\t\t{\n\t\t\treturn (String) getUserObject();\n\t\t}\n\n\t\tpublic void setName(String str)\n\t\t{\n\t\t\tsetUserObject(str);\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\tString name = getName();\n\t\t\tswitch (type) {\n\t\t\tcase LOCAL_INTEGER:\n\t\t\t\treturn name;\n\t\t\tcase GLOBAL_INTEGER:\n\t\t\tcase CONST_INTEGER:\n\t\t\t\treturn name + \" : int\";\n\t\t\tcase LOCAL_BOOL:\n\t\t\tcase GLOBAL_BOOL:\n\t\t\tcase CONST_BOOL:\n\t\t\t\treturn name + \" : bool\";\n\t\t\tcase CONST_DOUBLE:\n\t\t\t\treturn name + \" : double\";\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\n\t\tpublic abstract String getParseText();\n\t}\n\n\t//Editor for DeclarationNode\n\tclass DeclarationEditor extends JTextField implements TreeCellEditor\n\t{\n\t\tString name;\n\t\tVector<CellEditorListener> listeners = new Vector<CellEditorListener>();\n\t\tprivate static final int minWidth = 64;\n\n\t\tpublic DeclarationEditor()\n\t\t{\n\t\t\tsuper(\"\");\n\t\t\taddActionListener(new ActionListener()\n\t\t\t{\n\t\t\t\tpublic void actionPerformed(ActionEvent as)\n\t\t\t\t{\n\t\t\t\t\tif (stopCellEditing())\n\t\t\t\t\t\tfireEditingStopped();\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\tpublic void cancelCellEditing()\n\t\t{\n\t\t\tsetText(\"\");\n\t\t}\n\n\t\tpublic boolean stopCellEditing()\n\t\t{\n\t\t\tExpression exp;\n\t\t\tString str = getText();\n\t\t\ttry {\n\t\t\t\texp = Prism.parseSingleExpressionString(str);\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t\tif (exp instanceof ExpressionIdent) {\n\t\t\t\tname = str;\n\t\t\t\treturn true;\n\t\t\t} else {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\tpublic Object getCellEditorValue()\n\t\t{\n\t\t\treturn name;\n\t\t}\n\n\t\tpublic boolean isCellEditable(EventObject eo)\n\t\t{\n\t\t\tif ((eo == null) | ((eo instanceof MouseEvent) && (((MouseEvent) eo).isMetaDown()))) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic boolean shouldSelectCell(EventObject eo)\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\tprotected void fireEditingStopped()\n\t\t{\n\t\t\tif (listeners.size() > 0) {\n\t\t\t\tChangeEvent ce = new ChangeEvent(this);\n\t\t\t\tfor (int i = listeners.size() - 1; i >= 0; i--) {\n\t\t\t\t\tlisteners.elementAt(i).editingStopped(ce);\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\t//make sure the JTree gives the editor enough space\n\t\tpublic void setBounds(Rectangle r)\n\t\t{\n\t\t\tr.width = Math.max(minWidth, r.width);\n\t\t\tsuper.setBounds(r);\n\t\t}\n\n\t\tpublic void setBounds(int x, int y, int w, int h)\n\t\t{\n\t\t\tw = Math.max(minWidth, w);\n\t\t\tsuper.setBounds(x, y, w, h);\n\t\t}\n\n\t\tpublic void addCellEditorListener(CellEditorListener l)\n\t\t{\n\t\t\tlisteners.addElement(l);\n\t\t}\n\n\t\tpublic void removeCellEditorListener(CellEditorListener l)\n\t\t{\n\t\t\tlisteners.addElement(l);\n\t\t}\n\n\t\tpublic Component getTreeCellEditorComponent(JTree tree, Object value, boolean isSelected, boolean expanded, boolean leaf, int row)\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t}\n\n\tclass VarNode extends DeclarationNode\n\t{\n\n\t\tpublic VarNode(String name, Expression init, Expression min, Expression max, boolean editable)\n\t\t{\n\t\t\tsuper(LOCAL_INTEGER, name, editable);\n\t\t\tsuper.add(new ExpressionNode(\"min: \", min, editable));\n\t\t\tsuper.add(new ExpressionNode(\"max: \", max, editable));\n\t\t\tsuper.add(new ExpressionNode(\"init: \", init, editable));\n\t\t}\n\n\t\tpublic VarNode(String name, String init, String min, String max, boolean editable)\n\t\t{\n\t\t\tsuper(LOCAL_INTEGER, name, editable);\n\t\t\ttry {\n\t\t\t\tExpression e_init = Prism.parseSingleExpressionString(init);\n\t\t\t\tExpression e_min = Prism.parseSingleExpressionString(min);\n\t\t\t\tExpression e_max = Prism.parseSingleExpressionString(max);\n\t\t\t\tsuper.add(new ExpressionNode(\"min: \", e_min, editable));\n\t\t\t\tsuper.add(new ExpressionNode(\"max: \", e_max, editable));\n\t\t\t\tsuper.add(new ExpressionNode(\"init: \", e_init, editable));\n\t\t\t} catch (Exception e) {\n\t\t\t}\n\t\t}\n\n\t\tpublic void setInitial(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(2);\n\t\t\tn.setUserObject(e);\n\t\t\ttheModel.nodeChanged(getChildAt(2));\n\t\t}\n\n\t\tpublic Expression getInitial()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(2);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic void setMin(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\tn.setUserObject(e);\n\t\t\ttheModel.nodeChanged(getChildAt(0));\n\t\t}\n\n\t\tpublic Expression getMin()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic void setMax(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(1);\n\t\t\tn.setUserObject(e);\n\t\t\ttheModel.nodeChanged(getChildAt(1));\n\t\t}\n\n\t\tpublic Expression getMax()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(1);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic String getParseText()\n\t\t{\n\t\t\tString str = getName() + \" : [\" + getMin() + \"..\" + getMax() + \"] init \" + getInitial() + \";\";\n\t\t\treturn str;\n\t\t}\n\n\t}\n\n\tpublic class StateVarNode extends VarNode\n\t{\n\t\tModuleNode mn;\n\n\t\tpublic StateVarNode(ModuleNode mn)\n\t\t{\n\t\t\tsuper(\"statevariable\", \"0\", \"0\", \"0\", false);\n\t\t\tthis.mn = mn;\n\t\t}\n\n\t\tpublic String getName()\n\t\t{\n\t\t\treturn mn.getName() + \"_s\";\n\t\t}\n\t}\n\n\tclass BoolNode extends DeclarationNode\n\t{\n\t\tpublic BoolNode(String name, Expression init, boolean editable)\n\t\t{\n\t\t\tsuper(LOCAL_BOOL, name, editable);\n\t\t\tsuper.add(new ExpressionNode(\"init: \", init, editable));\n\t\t}\n\n\t\tpublic void setInitial(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\tn.setUserObject(e);\n\t\t}\n\n\t\tpublic Expression getInitial()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic String getParseText()\n\t\t{\n\t\t\tString str = getName() + \" : bool init \" + getInitial() + \";\";\n\t\t\treturn str;\n\t\t}\n\n\t}\n\n\tclass GlobalNode extends DeclarationNode\n\t{\n\n\t\tpublic GlobalNode(String name, Expression init, Expression min, Expression max, boolean editable)\n\t\t{\n\t\t\tsuper(GLOBAL_INTEGER, name, editable);\n\t\t\tsuper.add(new ExpressionNode(\"min: \", min, editable));\n\t\t\tsuper.add(new ExpressionNode(\"max: \", max, editable));\n\t\t\tsuper.add(new ExpressionNode(\"init: \", init, editable));\n\t\t}\n\n\t\tpublic void setInitial(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(2);\n\t\t\tn.setUserObject(e);\n\t\t}\n\n\t\tpublic Expression getInitial()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(2);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic void setMin(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\tn.setUserObject(e);\n\t\t}\n\n\t\tpublic Expression getMin()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic void setMax(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(1);\n\t\t\tn.setUserObject(e);\n\t\t}\n\n\t\tpublic Expression getMax()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(1);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic String getParseText()\n\t\t{\n\t\t\tString str = \"global \" + getName() + \" : [\" + getMin() + \"..\" + getMax() + \"] init \" + getInitial() + \";\";\n\t\t\treturn str;\n\t\t}\n\n\t}\n\n\tclass GlobalBoolNode extends DeclarationNode\n\t{\n\t\tpublic GlobalBoolNode(String name, Expression init, boolean editable)\n\t\t{\n\t\t\tsuper(GLOBAL_BOOL, name, editable);\n\t\t\tsuper.add(new ExpressionNode(\"init: \", init, editable));\n\t\t}\n\n\t\tpublic void setInitial(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\tn.setUserObject(e);\n\t\t}\n\n\t\tpublic Expression getInitial()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic String getParseText()\n\t\t{\n\t\t\tString str = \"global \" + getName() + \" : bool init \" + getInitial() + \";\";\n\t\t\treturn str;\n\t\t}\n\n\t}\n\n\tabstract class ConstantNode extends DeclarationNode\n\t{\n\t\tpublic ConstantNode(int type, String name, boolean editable)\n\t\t{\n\t\t\tsuper(type, name, editable);\n\t\t}\n\n\t\tpublic abstract void setValue(Expression e);\n\n\t\tpublic abstract Expression getValue();\n\n\t\tpublic boolean equals(Object obj)\n\t\t{\n\t\t\tif (obj instanceof ConstantNode) {\n\t\t\t\tConstantNode other = (ConstantNode) obj;\n\t\t\t\tif (!other.getName().equals(getName()))\n\t\t\t\t\treturn false;\n\t\t\t\telse\n\t\t\t\t\treturn true; //can only compare the equality of the names\n\t\t\t} else\n\t\t\t\treturn false;\n\t\t}\n\n\t\tpublic abstract String getParseText();\n\n\t}\n\n\tclass IntegerConstantNode extends ConstantNode\n\t{\n\t\tpublic IntegerConstantNode(String name, Expression value, boolean editable)\n\t\t{\n\t\t\tsuper(CONST_INTEGER, name, editable);\n\t\t\tsuper.add(new ExpressionNode(\"value: \", value, editable));\n\t\t}\n\n\t\tpublic void setValue(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\tn.setUserObject(e);\n\t\t}\n\n\t\tpublic Expression getValue()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic String getParseText()\n\t\t{\n\t\t\tString str = \"const int \" + getName();\n\t\t\tif (getValue() != null) {\n\t\t\t\tstr += \" = \" + getValue() + \";\";\n\t\t\t} else {\n\t\t\t\tstr += \";\";\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\n\t}\n\n\tclass DoubleConstantNode extends ConstantNode\n\t{\n\t\tpublic DoubleConstantNode(String name, Expression value, boolean editable)\n\t\t{\n\t\t\tsuper(CONST_DOUBLE, name, editable);\n\t\t\tsuper.add(new ExpressionNode(\"value: \", value, editable));\n\t\t}\n\n\t\tpublic void setValue(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\tn.setUserObject(e);\n\t\t}\n\n\t\tpublic Expression getValue()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic String getParseText()\n\t\t{\n\t\t\tString str = \"const double \" + getName();\n\t\t\tif (getValue() != null) {\n\t\t\t\tstr += \" = \" + getValue() + \";\";\n\t\t\t} else {\n\t\t\t\tstr += \";\";\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\n\t}\n\n\tclass BoolConstantNode extends ConstantNode\n\t{\n\t\tpublic BoolConstantNode(String name, Expression value, boolean editable)\n\t\t{\n\t\t\tsuper(CONST_BOOL, name, editable);\n\t\t\tsuper.add(new ExpressionNode(\"value: \", value, editable));\n\t\t}\n\n\t\tpublic void setValue(Expression e)\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\tn.setUserObject(e);\n\t\t}\n\n\t\tpublic Expression getValue()\n\t\t{\n\t\t\tExpressionNode n = (ExpressionNode) getChildAt(0);\n\t\t\treturn n.getValue();\n\t\t}\n\n\t\tpublic String getParseText()\n\t\t{\n\t\t\tString str = \"const bool \" + getName();\n\t\t\tif (getValue() != null) {\n\t\t\t\tstr += \" = \" + getValue() + \";\";\n\t\t\t} else {\n\t\t\t\tstr += \";\";\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\n\t}\n\n\tabstract class ValueNode extends DefaultMutableTreeNode implements PrismTreeNode\n\t{\n\t\tprivate String tag;\n\n\t\tpublic ValueNode(String tag, Object value)\n\t\t{\n\t\t\tsuper(value);\n\t\t\tthis.tag = tag;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\tif (getUserObject() == null)\n\t\t\t\treturn tag + \"?\";\n\t\t\telse\n\t\t\t\treturn tag + getUserObject().toString();\n\t\t}\n\n\t\tpublic abstract boolean isEditable();\n\n\t\tpublic boolean isLeaf()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\tpublic void setUserObject(Object obj)\n\t\t{\n\t\t\tsuper.setUserObject(obj);\n\t\t}\n\t}\n\n\tclass StringNode extends ValueNode\n\t{\n\t\tprivate boolean editable;\n\n\t\tpublic StringNode(String tag, String value, boolean editable)\n\t\t{\n\t\t\tsuper(tag, value);\n\t\t\tthis.editable = editable;\n\t\t}\n\n\t\tpublic boolean isEditable()\n\t\t{\n\t\t\treturn editable;\n\t\t}\n\n\t\tpublic String getValue()\n\t\t{\n\t\t\treturn (String) getUserObject();\n\t\t}\n\n\t}\n\n\tclass ExpressionNode extends ValueNode\n\t{\n\t\tprivate boolean editable;\n\n\t\tpublic ExpressionNode(String tag, Expression value, boolean editable)\n\t\t{\n\t\t\tsuper(tag, value);\n\t\t\tthis.editable = editable;\n\t\t}\n\n\t\tpublic boolean isEditable()\n\t\t{\n\t\t\treturn editable;\n\t\t}\n\n\t\tpublic Expression getValue()\n\t\t{\n\t\t\treturn (Expression) getUserObject();\n\t\t}\n\n\t\tpublic void setValue(Expression value)\n\t\t{\n\t\t\tsuper.setUserObject(value);\n\t\t}\n\n\t}\n\n\t/*\n\tclass ExpressionEditor extends javax.swing.DefaultCellEditor\n\t{\n\t        Expression exp;\n\t        int minWidth = 100;\n\t \n\t        public ExpressionEditor()\n\t        {\n\t                super(new JTextField());\n\t        }\n\t \n\t        public Component getComponent()\n\t        {\n\t                return editorComponent;\n\t        }\n\t \n\t        public boolean stopCellEditing()\n\t        {\n\t                String str = ((JTextField)editorComponent).getText();\n\t \n\t                try\n\t                {\n\t                        Expression s = handler.getGUIPlugin().getPrism().parseSingleExpressionString(str);\n\t                        exp = s;\n\t                }\n\t                catch(Exception e)\n\t                {\n\t                        handler.getGUIPlugin().message(\"Error: Syntax Error\");\n\t                        super.fireEditingStopped();\n\t                        return true;\n\t                }\n\t                super.fireEditingStopped();\n\t                return true;\n\t \n\t        }\n\t \n\t        public void setBounds(Rectangle r)\n\t        {\n\t                r.width = Math.max(minWidth, r.width);\n\t                getComponent().setBounds(r);\n\t                tree.repaint();\n\t        }\n\t \n\t        public void setBounds(int x, int y, int w, int h)\n\t        {\n\t                w = Math.max(minWidth, w);\n\t                getComponent().setBounds(x,y,w,h);\n\t                tree.repaint();\n\t        }\n\t}*/\n\n\t//Cell edit for ExpressionNode\n\tclass ExpressionEditor extends JTextField implements TreeCellEditor\n\t{\n\t\tExpression exp;\n\t\tVector<CellEditorListener> listeners = new Vector<CellEditorListener>();\n\t\tprivate static final int minWidth = 64;\n\n\t\tpublic ExpressionEditor()\n\t\t{\n\t\t\tsuper(\"\");\n\t\t\taddActionListener(new ActionListener()\n\t\t\t{\n\t\t\t\tpublic void actionPerformed(ActionEvent as)\n\t\t\t\t{\n\t\t\t\t\tif (stopCellEditing())\n\t\t\t\t\t\tfireEditingStopped();\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\tpublic void cancelCellEditing()\n\t\t{\n\t\t\tsetText(\"\");\n\t\t}\n\n\t\tpublic boolean stopCellEditing()\n\t\t{\n\t\t\tString str = getText();\n\n\t\t\ttry {\n\t\t\t\tExpression s = Prism.parseSingleExpressionString(str);\n\t\t\t\texp = s;\n\t\t\t} catch (Exception e) {\n\t\t\t\thandler.getGUIPlugin().message(\"Error: Syntax Error\");\n\t\t\t\treturn true;\n\t\t\t}\n\t\t\treturn true;\n\n\t\t}\n\n\t\tpublic Object getCellEditorValue()\n\t\t{\n\t\t\treturn exp;\n\t\t}\n\n\t\tpublic boolean isCellEditable(EventObject eo)\n\t\t{\n\t\t\tif ((eo == null) | ((eo instanceof MouseEvent) && (((MouseEvent) eo).isMetaDown()))) {\n\t\t\t\tMouseEvent me = (MouseEvent) eo;\n\t\t\t\tif (me.getClickCount() >= 2) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic boolean shouldSelectCell(EventObject eo)\n\t\t{\n\t\t\tif ((eo == null) | ((eo instanceof MouseEvent) && (((MouseEvent) eo).isMetaDown()))) {\n\t\t\t\tMouseEvent me = (MouseEvent) eo;\n\t\t\t\tif (me.getClickCount() >= 2) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\tprotected void fireEditingStopped()\n\t\t{\n\t\t\tif (listeners.size() > 0) {\n\t\t\t\tChangeEvent ce = new ChangeEvent(this);\n\t\t\t\tfor (int i = listeners.size() - 1; i >= 0; i--) {\n\t\t\t\t\tlisteners.elementAt(i).editingStopped(ce);\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\t//make sure the JTree gives the editor enough space\n\t\tpublic void setBounds(Rectangle r)\n\t\t{\n\t\t\tr.width = Math.max(minWidth, r.width);\n\t\t\tsuper.setBounds(r);\n\t\t\ttree.repaint();\n\t\t}\n\n\t\tpublic void setBounds(int x, int y, int w, int h)\n\t\t{\n\t\t\tw = Math.max(minWidth, w);\n\t\t\tsuper.setBounds(x, y, w, h);\n\t\t\ttree.repaint();\n\t\t}\n\n\t\tpublic void addCellEditorListener(CellEditorListener l)\n\t\t{\n\t\t\tlisteners.addElement(l);\n\t\t}\n\n\t\tpublic void removeCellEditorListener(CellEditorListener l)\n\t\t{\n\t\t\tlisteners.addElement(l);\n\t\t}\n\n\t\tpublic Component getTreeCellEditorComponent(JTree tree, Object value, boolean isSelected, boolean expanded, boolean leaf, int row)\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t}\n\n\tclass ModelTypeNode extends StringNode\n\t{\n\t\tpublic ModelTypeNode(String init, boolean editable)\n\t\t{\n\t\t\tsuper(\"Type: \", init, editable);\n\t\t}\n\n\t\tpublic void setModelType(ModelType type)\n\t\t{\n\t\t\tsetUserObject(type.toString());\n\t\t\tswitch (type) {\n\t\t\tcase MDP:\n\t\t\t\tnon.setSelected(true);\n\t\t\t\tbreak;\n\t\t\tcase DTMC:\n\t\t\t\tpro.setSelected(true);\n\t\t\t\tbreak;\n\t\t\tcase CTMC:\n\t\t\t\tsto.setSelected(true);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\ttheModel.nodeChanged(this);\n\t\t}\n\n\t\tpublic void setUserObject(Object obj)\n\t\t{\n\t\t\tsuper.setUserObject(obj);\n\t\t\t//System.out.println(\"setting model type user object \"+obj);\n\n\t\t}\n\t}\n\n\t//Cell Editor for ModelTypeNode\n\tclass ModelTypeEditor extends JComboBox implements TreeCellEditor\n\t{\n\t\tString value;\n\t\tVector<CellEditorListener> listeners = new Vector<CellEditorListener>();\n\t\tObject[] list;\n\n\t\tpublic ModelTypeEditor(Object[] list)\n\t\t{\n\t\t\tsuper(list);\n\t\t\tsetFont(tree.getFont());\n\t\t\tsetBackground(Color.white);\n\t\t\tsetForeground(Color.blue);\n\n\t\t\tthis.list = list;\n\t\t\tsetEditable(false);//why???\n\t\t\tvalue = list[0].toString();\n\n\t\t\taddActionListener(new ActionListener()\n\t\t\t{\n\t\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t\t{\n\t\t\t\t\tif (stopCellEditing())\n\t\t\t\t\t\tfireEditingStopped();\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\tpublic void setSelectedType(String str)\n\t\t{\n\t\t\tfor (int i = 0; i < list.length; i++) {\n\t\t\t\tString cur = (String) list[i];\n\t\t\t\tif (cur.equals(str)) {\n\t\t\t\t\tsuper.setSelectedIndex(i);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tpublic void cancelCellEditing()\n\t\t{\n\t\t}\n\n\t\tpublic boolean stopCellEditing()\n\t\t{\n\t\t\ttry {\n\t\t\t\tvalue = (String) getSelectedItem();\n\t\t\t\tif (value == null) {\n\t\t\t\t\tvalue = (String) getItemAt(0);\n\t\t\t\t}\n\t\t\t\treturn true;\n\n\t\t\t} catch (Exception e) {\n\t\t\t\treturn false;\n\t\t\t}\n\t\t}\n\n\t\tpublic Object getCellEditorValue()\n\t\t{\n\t\t\treturn value;\n\t\t}\n\n\t\tpublic boolean isCellEditable(EventObject eo)\n\t\t{\n\t\t\tif ((eo == null) || ((eo instanceof MouseEvent) && (((MouseEvent) eo).isMetaDown()))) {\n\t\t\t\tMouseEvent me = (MouseEvent) eo;\n\t\t\t\tif (me.getClickCount() >= 2) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic boolean shouldSelectCell(EventObject eo)\n\t\t{\n\t\t\tif ((eo == null) | ((eo instanceof MouseEvent) && (((MouseEvent) eo).isMetaDown()))) {\n\t\t\t\tMouseEvent me = (MouseEvent) eo;\n\t\t\t\tif (me.getClickCount() >= 2) {\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic void addCellEditorListener(CellEditorListener cel)\n\t\t{\n\t\t\tlisteners.addElement(cel);\n\t\t}\n\n\t\tpublic void removeCellEditorListener(CellEditorListener cel)\n\t\t{\n\t\t\tlisteners.removeElement(cel);\n\t\t}\n\n\t\tprotected void fireEditingStopped()\n\t\t{\n\t\t\tif (listeners.size() > 0) {\n\t\t\t\tChangeEvent ce = new ChangeEvent(this);\n\t\t\t\tfor (int i = listeners.size() - 1; i >= 0; i--) {\n\t\t\t\t\tlisteners.elementAt(i).editingStopped(ce);\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\n\t\tpublic Component getTreeCellEditorComponent(JTree tree, Object value, boolean isSelected, boolean expanded, boolean leaf, int row)\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t/*\n\t\t                //make sure the JTree gives the editor enough space\n\t\t                public void setBounds(Rectangle r)\n\t\t                {\n\t\t                                r.width = Math.max(minWidth, r.width);\n\t\t                                super.setBounds(r);\n\t\t                }\n\t\t \n\t\t                public void setBounds(int x, int y, int w, int h)\n\t\t                {\n\t\t                                w = Math.max(minWidth, w);\n\t\t                                super.setBounds(x,y,w,h);\n\t\t                }*/\n\n\t}\n\n\t//Node Renderer\n\tclass PrismNodeRenderer extends DefaultTreeCellRenderer\n\t{\n\t\tImageIcon VAR = GUIPrism.getIconFromImage(\"smallVariable.png\");\n\t\tImageIcon MOD = GUIPrism.getIconFromImage(\"smallModule.png\");\n\t\t//ImageIcon EXP = GUIPrism.getIconFromImage(\"smallExpression.png\");\n\t\tImageIcon VAL = GUIPrism.getIconFromImage(\"smallValue.png\");\n\t\tImageIcon GOOD = GUIPrism.getIconFromImage(\"smallTick.png\");\n\t\tImageIcon BAD = GUIPrism.getIconFromImage(\"smallCross.png\");\n\t\tImageIcon OUT_OF_SYNCH = GUIPrism.getIconFromImage(\"smallFilePrism.png\");\n\t\tImageIcon CLOCK = GUIPrism.getIconFromImage(\"smallClockAnim1.png\");\n\n\t\tpublic Component getTreeCellRendererComponent(JTree tree, Object value, boolean selected, boolean expanded, boolean leaf, int row, boolean hasFocus)\n\t\t{\n\t\t\tsuper.getTreeCellRendererComponent(tree, value, selected, expanded, leaf, row, hasFocus);\n\t\t\tPrismTreeNode node = (PrismTreeNode) value;\n\n\t\t\tif (node == root) {\n\t\t\t\tif (isParsing) {\n\t\t\t\t\tsetIcon(animIcon);\n\t\t\t\t} else {\n\t\t\t\t\tswitch (parseSynchState) {\n\t\t\t\t\tcase TREE_SYNCHRONIZED_GOOD:\n\t\t\t\t\t\tsetIcon(GOOD);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase TREE_SYNCHRONIZED_BAD:\n\t\t\t\t\t\tsetIcon(BAD);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase TREE_NOT_SYNCHRONIZED:\n\t\t\t\t\t\tsetIcon(OUT_OF_SYNCH);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else if (node instanceof VarNode) {\n\t\t\t\tsetIcon(VAR);\n\t\t\t} else if (node instanceof BoolNode) {\n\t\t\t\tsetIcon(VAR);\n\t\t\t} else if (node instanceof DeclarationNode) {\n\t\t\t\tsetIcon(VAR);\n\t\t\t} else if (node instanceof ModuleNode) {\n\t\t\t\tsetIcon(MOD);\n\t\t\t} else if (node instanceof ValueNode) {\n\t\t\t\t//if(node instanceof ExpressionNode)\n\t\t\t\t//{\n\t\t\t\t//setIcon(EXP);\n\t\t\t\t//}\n\t\t\t\t//else\n\t\t\t\t{\n\t\t\t\t\tsetIcon(VAL);\n\t\t\t\t}\n\t\t\t} else if (node instanceof ModuleCollectionNode || node instanceof DeclarationCollectionNode || node instanceof ConstantCollectionNode) {\n\t\t\t\tsetIcon(this.getDefaultClosedIcon());\n\t\t\t}\n\t\t\tif (node.isEditable()) {\n\t\t\t\tsetForeground(Color.blue);\n\t\t\t} else\n\t\t\t\tsetForeground(Color.black);\n\n\t\t\treturn this;\n\t\t}\n\t}\n\n\tclass ModelTreeCellEditor extends DefaultTreeCellEditor\n\t{\n\t\tModelTypeEditor modelTypeEditor;\n\t\tExpressionEditor expressionEditor;\n\t\tModuleEditor moduleEditor;\n\t\tDeclarationEditor declarationEditor;\n\n\t\tString[] types = new String[] { \"Non-deterministic\", \"Probabilistic\", \"Stochastic\" };\n\n\t\tpublic ModelTreeCellEditor(JTree tree, PrismNodeRenderer renderer)\n\t\t{\n\t\t\tsuper(tree, renderer);\n\t\t\tmodelTypeEditor = new ModelTypeEditor(types);\n\t\t\texpressionEditor = new ExpressionEditor();\n\t\t\tmoduleEditor = new ModuleEditor();\n\t\t\tdeclarationEditor = new DeclarationEditor();\n\t\t\trealEditor = declarationEditor;\n\t\t}\n\n\t\tpublic Component getTreeCellEditorComponent(JTree tree, Object value, boolean isSelected, boolean expanded, boolean leaf, int row)\n\t\t{\n\t\t\tif (value instanceof ExpressionNode) {\n\t\t\t\trealEditor = expressionEditor;\n\t\t\t\t//((JTextField)expressionEditor.getComponent()).setText(((ExpressionNode)value).getValue().toString());\n\t\t\t} else if (value instanceof ModelTypeNode) {\n\t\t\t\trealEditor = modelTypeEditor;\n\t\t\t\tmodelTypeEditor.setSelectedType(((ModelTypeNode) value).getValue());\n\t\t\t\t//tag = \"Type: \";\n\t\t\t} else if (value instanceof ModuleNode) {\n\t\t\t\trealEditor = moduleEditor;\n\t\t\t\tmoduleEditor.setText(((ModuleNode) value).getName());\n\t\t\t} else if (value instanceof DeclarationNode) {\n\t\t\t\trealEditor = declarationEditor;\n\t\t\t\tdeclarationEditor.setText(((DeclarationNode) value).getName());\n\t\t\t}\n\t\t\treturn super.getTreeCellEditorComponent(tree, value, isSelected, expanded, leaf, row);\n\t\t}\n\n\t\tpublic void addCellEditorListener(CellEditorListener l)\n\t\t{\n\n\t\t\tmodelTypeEditor.addCellEditorListener(l);\n\t\t\texpressionEditor.addCellEditorListener(l);\n\n\t\t\tmoduleEditor.addCellEditorListener(l);\n\n\t\t\tdeclarationEditor.addCellEditorListener(l);\n\t\t\tsuper.addCellEditorListener(l);\n\t\t}\n\n\t\tpublic void removeCellEditorListener(CellEditorListener l)\n\t\t{\n\t\t\tmodelTypeEditor.removeCellEditorListener(l);\n\t\t\texpressionEditor.removeCellEditorListener(l);\n\n\t\t\tmoduleEditor.removeCellEditorListener(l);\n\n\t\t\tdeclarationEditor.removeCellEditorListener(l);\n\t\t\tsuper.removeCellEditorListener(l);\n\t\t}\n\t}\n\n\t/*\n\tclass ModelTreeCellEditor_n implements TreeCellEditor\n\t{\n\t        ModelTypeEditor modelTypeEditor;\n\t        ExpressionEditor expressionEditor;\n\t        ModuleEditor moduleEditor;\n\t        DeclarationEditor declarationEditor;\n\t \n\t        CellEditor currentEditor;\n\t \n\t        DefaultTreeCellEditor ttt;\n\t \n\t        String[] types = new String[]\n\t        {\"Non-deterministic\", \"Probabilistic\", \"Stochastic\"};\n\t \n\t        PrismNodeRenderer renderer;\n\t \n\t        public ModelTreeCellEditor_n(PrismNodeRenderer renderer)\n\t        {\n\t                this.renderer = renderer;\n\t                modelTypeEditor = new ModelTypeEditor(types);\n\t                expressionEditor = new ExpressionEditor();\n\t                moduleEditor = new ModuleEditor();\n\t                declarationEditor = new DeclarationEditor();\n\t                currentEditor = declarationEditor;\n\t        }\n\t \n\t \n\t \n\t        public Component getTreeCellEditorComponent(JTree tree, Object value, boolean isSelected, boolean expanded, boolean leaf, int row)\n\t        {\n\t                String tag = \"\";\n\t                if(value instanceof ExpressionNode)\n\t                {\n\t                        currentEditor = expressionEditor;\n\t//\t\t\t\t((JTextField)expressionEditor.getComponent()).setText(((ExpressionNode)value).getValue().toString());\n\t                }\n\t                else if(value instanceof ModelTypeNode)\n\t                {\n\t                        currentEditor = modelTypeEditor;\n\t                        modelTypeEditor.setSelectedType(((ModelTypeNode)value).getValue());\n\t                        tag = \"Type: \";\n\t                }\n\t                else if(value instanceof ModuleNode)\n\t                {\n\t                        currentEditor = moduleEditor;\n\t                        moduleEditor.setText(((ModuleNode)value).getName());\n\t                }\n\t                else if(value instanceof DeclarationNode)\n\t                {\n\t                        currentEditor = declarationEditor;\n\t                        declarationEditor.setText(((DeclarationNode)value).getName());\n\t                }\n\t                DefaultTreeCellRenderer c = (DefaultTreeCellRenderer)renderer.getTreeCellRendererComponent(tree, value, isSelected, expanded, leaf, row, true);\n\t                JPanel p = new JPanel();\n\t                p.setBackground(Color.white);\n\t                p.setLayout(new BorderLayout());\n\t                JLabel l = new JLabel(tag,c.getIcon(), JLabel.HORIZONTAL);\n\t                l.setBackground(Color.white);\n\t                l.setForeground(Color.blue);\n\t                l.setFont(tree.getFont());\n\t                p.add(l, BorderLayout.WEST);\n\t                if(currentEditor instanceof ExpressionEditor)\n\t                {\n\t                        p.add(((ExpressionEditor)currentEditor).getComponent(), BorderLayout.CENTER);\n\t                }\n\t                else\n\t                {\n\t                        p.add((Component)currentEditor, BorderLayout.CENTER);\n\t                }\n\t                return p;//(Component)currentEditor;\n\t        }\n\t \n\t        public Object getCellEditorValue()\n\t        {\n\t                return currentEditor.getCellEditorValue();\n\t \n\t        }\n\t \n\t        public boolean isCellEditable(EventObject event)\n\t        {\n\t                return true;\n\t                //return currentEditor.isCellEditable(event);\n\t        }\n\t \n\t        public boolean shouldSelectCell(EventObject event)\n\t        {\n\t                return currentEditor.shouldSelectCell(event);\n\t        }\n\t \n\t        public boolean stopCellEditing()\n\t        {\n\t                return currentEditor.stopCellEditing();\n\t        }\n\t \n\t        public void cancelCellEditing()\n\t        {\n\t                currentEditor.cancelCellEditing();\n\t        }\n\t \n\t        public void addCellEditorListener(CellEditorListener l)\n\t        {\n\t \n\t                modelTypeEditor.addCellEditorListener(l);\n\t                expressionEditor.addCellEditorListener(l);\n\t \n\t                moduleEditor.addCellEditorListener(l);\n\t \n\t                declarationEditor.addCellEditorListener(l);\n\t        }\n\t \n\t        public void removeCellEditorListener(CellEditorListener l)\n\t        {\n\t                modelTypeEditor.removeCellEditorListener(l);\n\t                expressionEditor.removeCellEditorListener(l);\n\t \n\t                moduleEditor.removeCellEditorListener(l);\n\t \n\t                declarationEditor.removeCellEditorListener(l);\n\t        }\n\t \n\t}\n\t \n\t */\n\n\tclass IconThread extends Thread\n\t{\n\t\tint index;\n\t\tImageIcon[] images;\n\t\tboolean canContinue = false;\n\n\t\tpublic IconThread(int index)\n\t\t{\n\t\t\tthis.index = index;\n\t\t\timages = new ImageIcon[8];\n\t\t\timages[0] = GUIPrism.getIconFromImage(\"smallClockAnim1.png\");\n\t\t\timages[1] = GUIPrism.getIconFromImage(\"smallClockAnim2.png\");\n\t\t\timages[2] = GUIPrism.getIconFromImage(\"smallClockAnim3.png\");\n\t\t\timages[3] = GUIPrism.getIconFromImage(\"smallClockAnim4.png\");\n\t\t\timages[4] = GUIPrism.getIconFromImage(\"smallClockAnim5.png\");\n\t\t\timages[5] = GUIPrism.getIconFromImage(\"smallClockAnim6.png\");\n\t\t\timages[6] = GUIPrism.getIconFromImage(\"smallClockAnim7.png\");\n\t\t\timages[7] = GUIPrism.getIconFromImage(\"smallClockAnim8.png\");\n\t\t}\n\n\t\tpublic void run()\n\t\t{\n\t\t\ttry {\n\t\t\t\tint counter = 0;\n\t\t\t\twhile (!interrupted() && index > -1) {\n\t\t\t\t\tcounter++;\n\t\t\t\t\tcounter = counter % 8;\n\t\t\t\t\tanimIcon = images[counter];\n\t\t\t\t\ttree.repaint();\n\t\t\t\t\tsleep(150);\n\t\t\t\t}\n\t\t\t} catch (InterruptedException e) {\n\t\t\t}\n\t\t\tcanContinue = true;\n\t\t}\n\t}\n\n\tprivate static String removeCarriages(String line)\n\t{\n\t\tString lineBuffer = \"\";\n\t\tfor (int i = 0; i < line.length(); i++) {\n\t\t\tchar c = line.charAt(i);\n\t\t\tif (c != '\\n')\n\t\t\t\tlineBuffer += c;\n\t\t\telse\n\t\t\t\tlineBuffer += \" \";\n\t\t}\n\t\treturn lineBuffer;\n\t}\n\n\tpublic class Variable\n\t{\n\t\tpublic String name;\n\t}\n\t\n\tpublic class IntegerVariable extends Variable\n\t{\n\t\tpublic String min, max, init=\"0\";\n\t\t\n\t\tpublic IntegerVariable(String name, String min, String max, String init)\n\t\t{\n\t\t\tsuper.name = name;\n\t\t\tthis.min = min;\n\t\t\tthis.max = max;\n\t\t\tthis.init = init;\n\t\t}\n\t\t\n\t\tpublic IntegerVariable(String name, String min, String max)\n\t\t{\n\t\t\tthis.name = name;\n\t\t\tthis.min = min;\n\t\t\tthis.max = max;\n\t\t}\n\t}\n\t\n\tpublic class BooleanVariable extends Variable\n\t{\n\t\tpublic String init = \"false\";\n\t\t\n\t\tpublic BooleanVariable(String name, String init)\n\t\t{\n\t\t\tthis.init = init;\n\t\t\tthis.name = name;\n\t\t}\n\t\t\n\t\tpublic BooleanVariable(String name)\n\t\t{\n\t\t\tthis.name = name;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/GUITextModelEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Charles Harley <cd.harley@talk21.com> (University of Edinburgh)\n//\t* Sebastian Vermehren <seb03@hotmail.com> (University of Edinburgh)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport java.awt.BorderLayout;\nimport java.awt.Color;\nimport java.awt.Font;\nimport java.awt.Point;\nimport java.awt.Rectangle;\nimport java.awt.Toolkit;\nimport java.awt.datatransfer.Clipboard;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.KeyEvent;\nimport java.awt.event.MouseEvent;\nimport java.awt.event.MouseListener;\nimport java.io.IOException;\nimport java.io.Reader;\nimport java.io.StringReader;\nimport java.io.Writer;\nimport java.util.HashMap;\nimport java.util.Map;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.Action;\nimport javax.swing.ActionMap;\nimport javax.swing.InputMap;\nimport javax.swing.JEditorPane;\nimport javax.swing.JMenu;\nimport javax.swing.JPopupMenu;\nimport javax.swing.JScrollPane;\nimport javax.swing.JSeparator;\nimport javax.swing.KeyStroke;\nimport javax.swing.event.CaretEvent;\nimport javax.swing.event.CaretListener;\nimport javax.swing.event.DocumentEvent;\nimport javax.swing.event.DocumentListener;\nimport javax.swing.event.UndoableEditEvent;\nimport javax.swing.event.UndoableEditListener;\nimport javax.swing.text.BadLocationException;\nimport javax.swing.text.DefaultHighlighter;\nimport javax.swing.text.Element;\nimport javax.swing.text.PlainDocument;\nimport javax.swing.text.SimpleAttributeSet;\nimport javax.swing.undo.CannotRedoException;\nimport javax.swing.undo.CannotUndoException;\n\nimport prism.PrismLangException;\nimport prism.PrismSettings;\nimport prism.PrismSettingsListener;\nimport userinterface.GUIPrism;\nimport userinterface.util.GUIEvent;\nimport userinterface.util.GUIUndoManager;\n\n/**\n * Editing pane with syntax highlighting and line numbers etc for text \n * model files. Currently supports Prism and Pepa models. It also tells \n * the GUIPrism, of which it is a member, about modified events.\n */\n@SuppressWarnings(\"serial\")\npublic class GUITextModelEditor extends GUIModelEditor implements DocumentListener, MouseListener\n{\n\tprivate GUIMultiModelHandler handler;\n\t/** Standard java editor component for editing the model files. A custom\n\t * editor kit is used to provide syntax highlighting and line numbers.\n\t */\n\tprivate JEditorPane editor;\n\tprivate DefaultHighlighter.DefaultHighlightPainter errorHighlightPainter;\n\t\n\t/** Allows undo/redo operations to be performed on the model editor.\n\t */\n\tprivate GUIUndoManager undoManager;\n\tprivate JScrollPane editorScrollPane;\n\t/** The line numbers etc. gutter for the model editor. */\n\tprivate GUITextModelEditorGutter gutter;\n\t/** Stores the current known Prism setting for the 'show line numbers'\n\t * setting. Makes it possible to check if the setting has changed when\n\t * a Prism setting change notification is issued.\n\t */\n\tprivate boolean showLineNumbersSetting = true;\n\t\n\t/** The popup menu for the context menu. */\n\tprivate JPopupMenu contextPopup;\n\t\n\t/** Actions for the context menu. */\n\tprivate Action actionSearch, actionJumpToError;\n\t\n\t/** More actions */\n\tprivate Action insertDTMC, insertCTMC, insertMDP;\n\t\n\t/* both null if not existent */\n\tprivate PrismLangException parseError;\n\tprivate Object parseErrorHighlightKey;\n\t\t\n\t/** Mouse listener to listen for when the mouse is over the editor pane. */\n\tMouseListener editorMouseListener = new MouseListener()\n\t{\n\t\t\n\t\tpublic void mouseEntered(MouseEvent e)\n\t\t{\n\t\t\t// Horrible hack to get the cursor to change to the text cursor when\n\t\t\t// over the editor pane. Directly setting the cursor on the \n\t\t\t// JEditorPane didn't work.\n\t\t\t//GUIPrism.getGUI().setCursor(Cursor.getPredefinedCursor(Cursor.TEXT_CURSOR));\n\t\t}\n\t\t\n\t\tpublic void mouseExited(MouseEvent e)\n\t\t{\n\t\t\t// Horrible hack to get the cursor to change to the text cursor when\n\t\t\t// over the editor pane. Directly setting the cursor on the \n\t\t\t// JEditorPane didn't work.\n\t\t\t//GUIPrism.getGUI().setCursor(Cursor.getDefaultCursor());\n\t\t}\n\n\t\tpublic void mouseClicked(MouseEvent e) {}\n\n\t\tpublic void mousePressed(MouseEvent e) {}\n\n\t\tpublic void mouseReleased(MouseEvent e) {}\n\t\t\n\t};\n\t\n\t/** \n\t * Constructor, initialises the editor components.\n\t * \n\t * @param initialText The initial text to be displayed in the editor.\n\t * @param handler The GUI handler for this component.\n\t */\n\tpublic GUITextModelEditor(String initialText, GUIMultiModelHandler handler)\n\t{\n\t\tthis.handler = handler;\n\t\tsetLayout(new BorderLayout());\n\t\t\n\t\t// Setup the editor with it's custom editor kits. To switch between\n\t\t// editor kits just use setContentType() for the desired content type. \n\t\teditor = new JEditorPane() \n\t\t{\t\n\t\t\t@Override\n\t\t\tpublic String getToolTipText(MouseEvent event) \n\t\t\t{\t\n\t\t\t\tif (parseError != null)\n\t\t\t\t{\n\t\t\t\t\ttry\n\t\t\t\t\t{\n\t\t\t\t\t\tint offset = this.viewToModel(new Point(event.getX(), event.getY()));\n\t\t\t\t\t\n\t\t\t\t\t\tint startOffset = computeDocumentOffset(parseError.getBeginLine(), parseError.getBeginColumn());\n\t\t\t\t\t\tint endOffset =  computeDocumentOffset(parseError.getEndLine(), parseError.getEndColumn())+1;\n\t\t\t\t\t\t\n\t\t\t\t\t\tif (offset >= startOffset && offset <= endOffset)\n\t\t\t\t\t\t\treturn parseError.getMessage();\n\t\t\t\t\t}\n\t\t\t\t\tcatch (BadLocationException e)\n\t\t\t\t\t{}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\treturn null;\n\t\t\t}\n\t\t};\n\t\t\n\t\teditor.setToolTipText(\"dummy\");\n\t\t\n\t\teditor.setEditorKitForContentType(\"text/prism\", new PrismEditorKit(handler));\n\t\teditor.setEditorKitForContentType(\"text/pepa\", new PepaEditorKit(handler));\n\t\t// The default editor kit is the Prism one.\n\t\teditor.setContentType(\"text/prism\");\n\t\teditor.setBackground(Color.white);\n\t\teditor.addMouseListener(editorMouseListener);\n\t\teditor.setEditable(true);\n\t\teditor.setText(initialText);\n\t\teditor.getDocument().addDocumentListener(this);\n\t\teditor.addCaretListener(new CaretListener() {\n\t\t\tpublic void caretUpdate(CaretEvent e) {\n\t\t\t\tGUITextModelEditor.this.handler.getGUIPlugin().getSelectionChangeHandler().notifyListeners(new GUIEvent(1));\t\t\t\t\n\t\t\t}\n\t\t}); \n\t\teditor.getDocument().putProperty( PlainDocument.tabSizeAttribute, Integer.valueOf(4) );\n\t\t\n\t\teditor.addMouseListener(this);\n\t\terrorHighlightPainter = new DefaultHighlighter.DefaultHighlightPainter(new Color(255,192,192));\n\t\tundoManager = new GUIUndoManager(GUIPrism.getGUI());\n\t\tundoManager.setLimit(200);\t\t\n\t\t\n\t\t// Setup the scrollpane\n\t\teditorScrollPane = new JScrollPane(editor);\n\t\tadd(editorScrollPane, BorderLayout.CENTER);\n\t\tgutter = new GUITextModelEditorGutter(editor);\n\t\t\n\t\t// Get the 'show line numbers' setting to determine \n\t\t// if the line numbers should be shown.\n\t\tshowLineNumbersSetting = handler.getGUIPlugin().getPrism().getSettings().getBoolean(PrismSettings.MODEL_SHOW_LINE_NUMBERS);\n\t\tif (showLineNumbersSetting) {\n\t\t\teditorScrollPane.setRowHeaderView(gutter);\n\t\t}\n\t\t\n\t\t// Add a Prism settings listener to catch changes made to the \n\t\t// 'show line numbers' setting.\n\t\thandler.getGUIPlugin().getPrism().getSettings().addSettingsListener(new PrismSettingsListener ()\n\t\t{\n\t\t\tpublic void notifySettings(PrismSettings settings)\n\t\t\t{\n\t\t\t\t// Check if the setting has changed.\n\t\t\t\tif (settings.getBoolean(PrismSettings.MODEL_SHOW_LINE_NUMBERS) != showLineNumbersSetting) {\n\t\t\t\t\tshowLineNumbersSetting =! showLineNumbersSetting;\n\t\t\t\t\tif (showLineNumbersSetting) {\n\t\t\t\t\t\teditorScrollPane.setRowHeaderView(gutter);\n\t\t\t\t\t} else {\n\t\t\t\t\t\teditorScrollPane.setRowHeaderView(null);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t\t\n\t\t// initialize the actions for the context menu\n\t\tinitActions();\n\t\t\n\t\t// method to initialize the context menu popup\n\t\tinitContextMenu();\n\t\t\t\n\t    InputMap inputMap = editor.getInputMap();\t\n\t    inputMap.clear();\n\t\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_Z, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"prism_undo\");\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_Z, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"prism_undo\");\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_Y, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"prism_redo\");\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_A, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"prism_selectall\");\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_D, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"prism_delete\");\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_X, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"prism_cut\");\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_Z, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask() | java.awt.event.InputEvent.SHIFT_MASK), \"prism_redo\");\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_V, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"prism_paste\");\n\t    inputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_E, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"prism_jumperr\");\n\t    \n\t\tActionMap actionMap = editor.getActionMap();\n\t\tactionMap.put(\"prism_undo\", GUIPrism.getClipboardPlugin().getUndoAction());\n\t\tactionMap.put(\"prism_redo\", GUIPrism.getClipboardPlugin().getRedoAction());\n\t\tactionMap.put(\"prism_selectall\", GUIPrism.getClipboardPlugin().getSelectAllAction());\n\t\tactionMap.put(\"prism_cut\", GUIPrism.getClipboardPlugin().getCutAction());\n\t\tactionMap.put(\"prism_copy\", GUIPrism.getClipboardPlugin().getCopyAction());\n\t\tactionMap.put(\"prism_paste\", GUIPrism.getClipboardPlugin().getPasteAction());\n\t\tactionMap.put(\"prism_delete\", GUIPrism.getClipboardPlugin().getDeleteAction());\n\t\tactionMap.put(\"prism_jumperr\", actionJumpToError);\n\t\t\n\t\t// Attempt to programmatically allow all accelerators\n\t\t/*ArrayList plugins = ((GUIMultiModel)handler.getGUIPlugin()).getGUI().getPlugins();\n\t\tIterator it = plugins.iterator();\n\t\t\n\t\twhile (it.hasNext())\n\t\t{\n\t\t\tGUIPlugin plugin = ((GUIPlugin)it.next());\n\t\t\tSystem.out.println(plugin.getName());\n\t\t\tJMenu firstMenu = plugin.getMenu();\n\t\t\t\n\t\t\tStack<MenuElement> menuStack = new Stack<MenuElement>();\n\t\t\t\n\t\t\tmenuStack.add(firstMenu);\n\t\t\t\n\t\t\twhile (!menuStack.empty())\n\t\t\t{\n\t\t\t\tMenuElement menu = menuStack.pop();\n\t\t\t\t\n\t\t\t\tif (menu instanceof JMenuItem)\n\t\t\t\t{\n\t\t\t\t\tJMenuItem menuItem = ((JMenuItem)menu);\n\t\t\t\t\t\n\t\t\t\t\tKeyStroke accelerator = menuItem.getAccelerator();\n\t\t\t\t\tAction action = menuItem.getAction();\n\t\t\t\t\t\n\t\t\t\t\tif (action != null && accelerator != null && menuItem.getText() != null)\n\t\t\t\t\t{\n\t\t\t\t\t\tSystem.out.println(menuItem.getText() + \" \" + menuItem.getName());\n\t\t\t\t\t\tinputMap.put(accelerator, \"prism_\" + menuItem.getText());\n\t\t\t\t\t\tactionMap.put(\"prism_\" + menuItem.getText(), action);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t\n\t\t\t\tMenuElement[] subelements = menu.getSubElements();\n\t\t\t\t\n\t\t\t\tif (subelements != null)\n\t\t\t\t{\n\t\t\t\t\tfor (int i = 0; i < subelements.length; i++)\n\t\t\t\t\t\tmenuStack.push(subelements[i]);\n\t\t\t\t}\t\t\t\t\t\n\t\t\t}\n\t\t}*/\n\t\t\n\t\t\n\t\t\n\t\teditor.getDocument().addUndoableEditListener(undoManager);\n\t\teditor.getDocument().addUndoableEditListener(new UndoableEditListener() \n\t\t{\n\t\t\tpublic void undoableEditHappened(UndoableEditEvent e) \n\t\t\t{\n\t\t\t\tSystem.out.println(\"adding undo edit\");\t\t\t\t\n\t\t\t}\n\t\t});\n\t}\n\t\n\t/**\n\t * Helper method to initialize the actions used for the buttons.\n\t */\n\tprivate void initActions() {\n\t\t\n\t\t/*actionUndo = new AbstractAction() {\n\t\t\tpublic void actionPerformed(ActionEvent ae) {\n\t\t\t\ttry {\n\t\t\t\t\t// do redo\n\t\t\t\t\tundoManager.undo();\n\t\t\t\t\t\n\t\t\t\t\t// notify undo manager/toolbar of change\n\t\t\t\t\tGUIPrism.getGUI().notifyEventListeners(\n\t\t\t\t\t\t\tnew GUIClipboardEvent(GUIClipboardEvent.UNDOMANAGER_CHANGE, \n\t\t\t\t\t\t\t\t\tGUIPrism.getGUI().getFocussedPlugin().getFocussedComponent()));\n\t\t\t\t} catch (CannotUndoException ex) {\n\t\t\t\t\t//GUIPrism.getGUI().getMultiLogger().logMessage(PrismLogLevel.PRISM_ERROR, ex.getMessage());\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\tactionUndo.putValue(Action.LONG_DESCRIPTION, \"Undo the most recent action.\");\n\t\tactionUndo.putValue(Action.NAME, \"Undo\");\n\t\tactionUndo.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallUndo.png\"));\n\t\t\n\t\tactionRedo = new AbstractAction() {\n\t\t\tpublic void actionPerformed(ActionEvent ae) {\n\t\t\t\ttry {\n\t\t\t\t\t// do redo\n\t\t\t\t\tundoManager.redo();\n\t\t\t\t\t\n\t\t\t\t\t// notify undo manager/toolbar of change\n\t\t\t\t\tGUIPrism.getGUI().notifyEventListeners(\n\t\t\t\t\t\t\tnew GUIClipboardEvent(GUIClipboardEvent.UNDOMANAGER_CHANGE, \n\t\t\t\t\t\t\t\t\tGUIPrism.getGUI().getFocussedPlugin().getFocussedComponent()));\n\t\t\t\t} catch (CannotRedoException ex) {\n\t\t\t\t\t//GUIPrism.getGUI().getMultiLogger().logMessage(PrismLogLevel.PRISM_ERROR, ex.getMessage());\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\t\n\t\t\n\t\tactionRedo.putValue(Action.LONG_DESCRIPTION, \"Redos the most recent undo\");\n\t\tactionRedo.putValue(Action.NAME, \"Redo\");\n\t\tactionRedo.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallRedo.png\"));\n\t\t*/\n\t\tactionJumpToError = new AbstractAction() {\n\t\t\tpublic void actionPerformed(ActionEvent ae) {\n\t\t\t\tjumpToError();\n\t\t\t}\n\t\t};\n\t\t\n\t\tactionJumpToError.putValue(Action.NAME, \"Jump to error\");\n\t\tactionJumpToError.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"tinyError.png\"));\n\t\tactionJumpToError.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_E, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\t\t\n\t\t\n\t\t// search and replace action\n        actionSearch = new AbstractAction() {\n        \tpublic void actionPerformed(ActionEvent ae) {\n        \t\t/*\n        \t\t// System.out.println(\"search button pressed\");\n        \t\tif (GUIMultiModelHandler.isDoingSearch()) {\n\t\t\t\t\t\n\t\t\t\t} else {\n\t\t\t\t\ttry {\n\t\t\t\t\t\tGUIMultiModelHandler.setDoingSearch(true);\n\t\t\t\t\t\tFindReplaceForm.launch(GUIPrism.getGUI().getMultiModel());\n\t\t\t\t\t} catch (PluginNotFoundException pnfe) {\n\t\t\t\t\t\tGUIPrism.getGUI().getMultiLogger().logMessage(prism.log.PrismLogLevel.PRISM_ERROR,\n\t\t\t\t\t\t\t\tpnfe.getMessage());\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t*/\n        \t}\n        };\n        actionSearch.putValue(Action.LONG_DESCRIPTION, \"Opens a find and replace dialog.\");\n        //actionSearch.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"find.png\"));\n        actionSearch.putValue(Action.NAME, \"Find/Replace\");\n        //actionSearch.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_R, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n        \n        insertDTMC = new AbstractAction() {\n        \tpublic void actionPerformed(ActionEvent ae) {\n        \t\tint caretPosition = editor.getCaretPosition();\n        \t\ttry\n        \t    {\n        \t\t\teditor.getDocument().insertString(caretPosition, \"dtmc\", new SimpleAttributeSet());\n        \t    }\n        \t\tcatch (BadLocationException ble)\n        \t\t{\n        \t\t   //todo log?\n        \t\t}\n        \t}\n        };\n        \n        insertDTMC.putValue(Action.LONG_DESCRIPTION, \"Marks this model as a \\\"Discrete-Time Markov Chain\\\"\");\n        //actionSearch.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"find.png\"));\n        insertDTMC.putValue(Action.NAME, \"Probabilistic (DTMC)\");\n        \n        insertCTMC = new AbstractAction() {\n        \tpublic void actionPerformed(ActionEvent ae) {\n        \t\tint caretPosition = editor.getCaretPosition();\n        \t\ttry\n        \t    {\n        \t\t\teditor.getDocument().insertString(caretPosition, \"ctmc\", new SimpleAttributeSet());\n        \t    }\n        \t\tcatch (BadLocationException ble)\n        \t\t{\n        \t\t   //todo log?\n        \t\t}\n        \t}\n        };\n        \n        insertCTMC.putValue(Action.LONG_DESCRIPTION, \"Marks this model as a \\\"Continous-Time Markov Chain\\\"\");\n        //actionSearch.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"find.png\"));\n        insertCTMC.putValue(Action.NAME, \"Stochastic (CTMC)\");\n       \n        insertMDP = new AbstractAction() {\n        \tpublic void actionPerformed(ActionEvent ae) {\n        \t\tint caretPosition = editor.getCaretPosition();\n        \t\ttry\n        \t    {\n        \t\t\teditor.getDocument().insertString(caretPosition, \"mdp\", new SimpleAttributeSet());\n        \t    }\n        \t\tcatch (BadLocationException ble)\n        \t\t{\n        \t\t   //todo log?\n        \t\t}\n        \t}\n        };\n        \n        insertMDP.putValue(Action.LONG_DESCRIPTION, \"Marks this model as a \\\"Markov Decision Process\\\"\");\n        //actionSearch.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"find.png\"));\n        insertMDP.putValue(Action.NAME, \"Non-deterministic (MDP)\");\n\t\n\t}\n\t\n\t/**\n\t * Helper method that initializes the items for the context menu. This\n\t * menu will include cut, copy, paste, undo/redo, and find/replace\n\t * functionality.\n\t *\n\t */\n\tprivate void initContextMenu() {\n\t\t\n\t\tcontextPopup = new JPopupMenu();\t\t\n\t\t// Edit menu stuff\n\t\tcontextPopup.add(GUIPrism.getClipboardPlugin().getUndoAction());\n\t\tcontextPopup.add(GUIPrism.getClipboardPlugin().getRedoAction());\n\t\tcontextPopup.add(new JSeparator());\n\t\tcontextPopup.add(GUIPrism.getClipboardPlugin().getCutAction());\n\t\tcontextPopup.add(GUIPrism.getClipboardPlugin().getCopyAction());\n\t\tcontextPopup.add(GUIPrism.getClipboardPlugin().getPasteAction());\n\t\tcontextPopup.add(GUIPrism.getClipboardPlugin().getDeleteAction());\n\t\tcontextPopup.add(new JSeparator());\n\t\tcontextPopup.add(GUIPrism.getClipboardPlugin().getSelectAllAction());\n\t\tcontextPopup.add(new JSeparator());\n\t\t// Model menu stuff\n\t\tcontextPopup.add(((GUIMultiModel)handler.getGUIPlugin()).getParseModel());\n\t\tcontextPopup.add(((GUIMultiModel)handler.getGUIPlugin()).getBuildModel());\n\t\tcontextPopup.add(new JSeparator());\n\t\tcontextPopup.add(((GUIMultiModel)handler.getGUIPlugin()).getExportMenu());\n\t\tcontextPopup.add(((GUIMultiModel)handler.getGUIPlugin()).getViewMenu());\n\t\tcontextPopup.add(((GUIMultiModel)handler.getGUIPlugin()).getComputeMenu());\n\t\tcontextPopup.add(((GUIMultiModel)handler.getGUIPlugin()).getComputeExportMenu());\n\t\t//contextPopup.add(actionJumpToError);\n\t\t//contextPopup.add(actionSearch);\n\t\t\n\t\t\n\t\tif (editor.getContentType().equals(\"text/prism\"))\n\t\t{\n\t\t\t\n\t\t\tJMenu insertMenu = new JMenu(\"Insert elements\");\n\t\t\tJMenu insertModelTypeMenu = new JMenu(\"Model type\");\n\t\t\tinsertMenu.add(insertModelTypeMenu);\n\t\t\tJMenu insertModule = new JMenu(\"Module\");\n\t\t\tinsertMenu.add(insertModule);\n\t\t\tJMenu insertVariable = new JMenu(\"Variable\");\n\t\t\tinsertMenu.add(insertVariable);\n\t\t\t\n\t\t\tinsertModelTypeMenu.add(insertDTMC);\n\t\t\tinsertModelTypeMenu.add(insertCTMC);\n\t\t\tinsertModelTypeMenu.add(insertMDP);\n\t\t\t//contextPopup.add(new JSeparator());\n\t\t\t//contextPopup.add(insertMenu);\n\t\t}\n\t}\n\t\n\t/** Sets the content type of the editor, currently accepts 'text/prism' \n\t * and 'text/pepa'. Setting the content type changes the editor kit of \n\t * the editor to a kit that provides syntax highlighting etc for that\n\t * content type.\n\t * \n\t * @param contentType The content type\n\t */\n\tpublic void setContentType(String contentType) {\n\t\teditor.setContentType(contentType);\n\t}\n\t\n\t/** Loads the model editor with the text from the given stream reader, \n\t * discards any previous content in the editor.\n\t * \n\t * @param reader A character stream reader\n\t * @param object An object describing the stream; this might be a string, a File, a URL, etc. \n\t * \n\t * @throws IOException Thrown if there was an IO error reading the input stream.\n\t */\n\tpublic void read(Reader reader, Object object) throws IOException\n\t{\n\t\teditor.getDocument().removeUndoableEditListener(undoManager);\n\t\t\n\t\teditor.read(reader, object);\n\t\t\n\t\t// For some unknown reason the listeners have to be added both here\n\t\t// and in the constructor, if they're not added here the editor won't\n\t\t// be listening.\n\t\teditor.getDocument().addDocumentListener(this);\t\n\t\teditor.getDocument().addUndoableEditListener(undoManager);\t\n\t}\n\t\n\tpublic void setText(String text)\n\t{\n\t\teditor.setText(text);\n\t}\n\t\n\tpublic void write(Writer writer) throws IOException\n\t{\n\t\teditor.write(writer);\n\t}\n\t\n\tpublic String getTextString()\n\t{\n\t\treturn editor.getText();\n\t}\n\t\n\t/** Resets the model editor with a blank document.\n\t */\n\tpublic void newModel()\n\t{\n\t\t// Note: we use the read() method instead of setText() because\n\t\t// this avoids triggering the listener methods and hence \n\t\t// unwanted autoparsing.\n\t\ttry\n\t\t{\n\t\t\tread(new StringReader(\"\"), \"\");\n\t\t} catch (IOException ex)\n\t\t{ \n\t\t\t//todo:mark\n\t\t\t//GUIPrism.getGUI().getMultiLogger().logMessage(PrismLogLevel.PRISM_ERROR, ex.getMessage());\n\t\t}\n\t}\n\t\n\t/** Notifies the GUI that the document has been modified.\n\t * \n\t * @param event Event generated by the change in the document.\n\t */\n\tpublic void changedUpdate(DocumentEvent event)\n\t{\n\t\t// No need to notify the GUI as this event is covered by \n\t\t// the insert and delete update methods.\n\t}\n\t\n\t/** Notifies the GUI that the document has been modified.\n\t * \n\t * @param event Event generated by the change in the document.\n\t */\n\tpublic void insertUpdate(DocumentEvent event)\n\t{\n\t\tif (handler != null) \n\t\t\thandler.hasModified(true);\n\t}\n\t\n\t\n\t/** Notifies the GUI that the document has been modified.\n\t * \n\t * @param event Event generated by the change in the document.\n\t */\n\tpublic void removeUpdate(DocumentEvent event)\n\t{\n\t\tif (handler != null) \n\t\t\thandler.hasModified(true);\n\t}\n\t\n\tpublic String getParseText()\n\t{\n\t\treturn editor.getText();\n\t}\n\t\n\t/** Performs an undo operation on the text in the model editor.\n     */\n\tpublic void undo() {\n\t\ttry {\n\t\t\tundoManager.undo();\n\t\t} catch (CannotUndoException ex) {\n\t\t\t\n\t\t\t//GUIPrism.getGUI().getMultiLogger().logMessage(PrismLogLevel.PRISM_ERROR, ex.getMessage());\n\t\t}\n\t}\n\t\n\t/** Performs a redo operation on the text in the model editor.\n     */\n\tpublic void redo() {\n\t\ttry {\n\t\t\tundoManager.redo();\n\t\t} catch (CannotRedoException ex) {\n\t\t\t//GUIPrism.getGUI().getMultiLogger().logMessage(PrismLogLevel.PRISM_ERROR, ex.getMessage());\n\t\t}\n\t}\n\t\n\tpublic void copy()\n\t{\n\t\teditor.copy();\n\t}\n\t\n\tpublic void cut()\n\t{\n\t\teditor.cut();\n\t}\n\t\n\tpublic void paste()\n\t{\n\t\teditor.paste();\n\t}\n\t\n\tpublic void delete()\n\t{\n\t\ttry\n\t\t{\n\t\t\teditor.getDocument().remove(editor.getSelectionStart(), editor.getSelectionEnd()-editor.getSelectionStart());\n\t\t}\n\t\tcatch(BadLocationException ex)\n\t\t{\n\t\t\t//GUIPrism.getGUI().getMultiLogger().logMessage(PrismLogLevel.PRISM_ERROR, ex.getMessage());\n\t\t}\n\t}\n\t\n\tpublic void selectAll()\n\t{\n\t\teditor.selectAll();\n\t}\n\t\n\tpublic boolean isEditable()\n\t{\n\t\treturn editor.isEditable();\n\t}\n\t\n\tpublic void setEditable(boolean b)\n\t{\n\t\teditor.setEditable(b);\n\t}\n\t\n\tpublic void setEditorFont(Font f)\n\t{\n\t\teditor.setFont(f);\n\t}\n\t\n\tpublic void setEditorBackground(Color c)\n\t{\n\t\teditor.setBackground(c);\n\t}\n\t\t\n\t// rajk\n\tpublic JEditorPane getEditorPane(){\n\t\treturn this.editor;\n\t}\n\n\t/**\n\t * Mouse Listener methods.\n\t * \n\t * spv\n\t */\n\tpublic void mouseTriggered(MouseEvent me)\n\t{\n\t\tif (me.isPopupTrigger()) {\n\t\t\tactionJumpToError.setEnabled(parseError != null && parseError.hasLineNumbers());\n\t\t\t((GUIMultiModel)handler.getGUIPlugin()).doEnables();\n\t\t\t\n\t\t\tcontextPopup.show(me.getComponent(), me.getX(), me.getY());\n\t\t\t\n\t\t}\n\t} \n\t \n\tpublic void mouseClicked(MouseEvent me) {}\n\tpublic void mousePressed(MouseEvent me) {\n\t\tmouseTriggered(me);\t\t\n\t}\n\tpublic void mouseEntered(MouseEvent me) {}\n\tpublic void mouseExited(MouseEvent me) {}\n\tpublic void mouseReleased(MouseEvent me) {\n\t\tmouseTriggered(me);\t\n\t}\n\t\n\tpublic void jumpToError()\n\t{\n\t\tif (parseError != null && parseError.hasLineNumbers() )\n\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\tint offset = computeDocumentOffset(parseError.getBeginLine(), parseError.getBeginColumn());\n\t\t\t\t\n\t\t\t\t// scroll to center as much as possible.\n\t\t\t\teditor.setCaretPosition(offset);\n\t\t\t\tRectangle r1 = editor.modelToView(offset);\n\t\t\t\tint dy = (editor.getVisibleRect().height - r1.height) / 2;\n\t\t\t\tRectangle r2 = new Rectangle(0, r1.y - dy,editor.getVisibleRect().width, r1.height + 2*dy);\n\t\t\t\teditor.scrollRectToVisible(r2);\n\t\t\t}\n\t\t\tcatch (BadLocationException e)\n\t\t\t{\n\t\t\t\t\n\t\t\t}\n\t\t}\n\t}\n\t\n\tpublic void refreshErrorDisplay()\n\t{\n\t\tif (parseErrorHighlightKey != null)\n\t\t\teditor.getHighlighter().removeHighlight(parseErrorHighlightKey);\n\t\t\n\t\t/* Mapping for gutter */\n\t    Map<Integer, String> errorLines = new HashMap<Integer, String>();\n\t\t\t    \t\t\n\t\tif (parseError != null && parseError.hasLineNumbers() )\n\t\t{\n\t\t\tString error = parseError.getMessage();\n\t\t\n\t\t\t// Just the first line.\n\t\t\terrorLines.put(parseError.getBeginLine(), error);\n\t\t\t\n\t\t\t// If error spans multiple lines, this code will put\n\t\t\t// an error in every line of the gutter.\n\t\t\t/*for (int line = parseError.getBeginLine();\n\t\t\t     line <= parseError.getEndLine();\n\t\t\t     line++)\n\t\t\t{\n\t\t\t\terrorLines.put(line, error);\n\t\t\t}*/\n\t\t}\n\t\t\n\t\tgutter.setParseErrors(errorLines);\n\t\t\n\t\t/* Highlighting errors in editor */\n\t\tif (parseError != null && parseError.hasLineNumbers())\n\t\t{\n\t\t\t/* Remove existing highlight */\n\t\t\ttry\n\t\t\t{\n\t\t\t\tparseErrorHighlightKey = editor.getHighlighter().addHighlight(\n\t\t\t\t  computeDocumentOffset(parseError.getBeginLine(), parseError.getBeginColumn()), \n\t\t\t\t  computeDocumentOffset(parseError.getEndLine(), parseError.getEndColumn())+1, errorHighlightPainter);\n\t\t\t}\n\t\t\tcatch (BadLocationException e)\n\t\t\t{\n\t\t\t\t\n\t\t\t}\t\t\t\n\t\t}\t\t\n\t}\n\t\n\tpublic int computeDocumentOffset(int line, int column) throws BadLocationException\n\t{\n\t\tif (line < 0 || column < 0) throw new BadLocationException(\"Negative line/col\", -1);\n\t\t\n\t\tElement lineElement = editor.getDocument().getDefaultRootElement().\n\t\tgetElement(line-1);\n\t\t\n\t\tint beginLineOffset = lineElement.getStartOffset();\n\t\tint endLineOffset = lineElement.getEndOffset();\n\t\t\n\t\tString text = editor.getDocument().getText(beginLineOffset, endLineOffset - beginLineOffset);\n\t\t\n\t\tint parserChar = 1;\n\t\tint documentChar = 0;\t\t\n\t\t\n\t\twhile (parserChar < column)\n\t\t{\n\t\t\tif (documentChar < text.length() && text.charAt(documentChar) == '\\t')\n\t\t\t{\n\t\t\t\tparserChar += 8;\n\t\t\t\tdocumentChar += 1;\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\tparserChar += 1;\n\t\t\t\tdocumentChar += 1;\n\t\t\t}\t\t\n\t\t}\n\t\t\t\t\n\t\treturn beginLineOffset+documentChar;\t\t\n\t}\n\t\n\tpublic void modelParseFailed(PrismLangException parserError, boolean background) \n\t{\t\n\t\tthis.parseError = parserError;\t\t\n\t\trefreshErrorDisplay();\t\n\t\tif (!background)\n\t\t\tjumpToError();\t\t\n\t}\n\n\t@Override\n\tpublic void modelParseSuccessful() \n\t{\n\t\tthis.parseError = null;\n\t\t// get rid of any error highlighting\n\t\trefreshErrorDisplay();\n\t}\n\n\tpublic GUIUndoManager getUndoManager() \n\t{\n\t\treturn undoManager;\n\t} \t\n\t\n\tpublic boolean canDoClipBoardAction(Action action) {\n\t\tif (action == GUIPrism.getClipboardPlugin().getPasteAction())\n\t\t{\n\t\t\tClipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();\n\t\t\treturn (clipboard.getContents(null) != null);\n\t\t}\n\t\telse if (\n\t\t  action == GUIPrism.getClipboardPlugin().getCutAction() ||\n\t\t  action == GUIPrism.getClipboardPlugin().getCopyAction() ||\n\t\t  action == GUIPrism.getClipboardPlugin().getDeleteAction())\n\t\t{\n\t\t\treturn (editor.getSelectedText() != null);\n\t\t}\n\t\telse if (action == GUIPrism.getClipboardPlugin().getSelectAllAction())\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\treturn handler.canDoClipBoardAction(action);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/GUITextModelEditorGutter.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Charles Harley <cd.harley@talk21.com> (University of Edinburgh)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport java.awt.Color;\nimport java.awt.Dimension;\nimport java.awt.FontMetrics;\nimport java.awt.Graphics;\nimport java.awt.Rectangle;\nimport java.awt.event.MouseEvent;\nimport java.beans.PropertyChangeEvent;\nimport java.beans.PropertyChangeListener;\nimport java.util.Map;\nimport javax.swing.BorderFactory;\nimport javax.swing.ImageIcon;\nimport javax.swing.JMenu;\nimport javax.swing.JPanel;\nimport javax.swing.JToolBar;\nimport javax.swing.SizeSequence;\nimport javax.swing.event.DocumentEvent;\nimport javax.swing.event.DocumentListener;\nimport javax.swing.text.BadLocationException;\nimport javax.swing.text.Document;\nimport javax.swing.text.Element;\nimport javax.swing.text.JTextComponent;\n\nimport prism.PrismSettings;\nimport userinterface.GUIPrism;\n\n/**\n * Information gutter for the text model editor. It displays line numbers for \n * the text in the given text pane and the location of a parsing error. The \n * font the panel uses is taken from the font for the given text pane.\n */\npublic class GUITextModelEditorGutter extends JPanel implements PropertyChangeListener, DocumentListener\n{\n\n\t/** Rendering information for the current font, used to draw the gutter\n\t * info. It allows the font height and width needed for the panel to\n\t * be calculated.\n\t */\n\tprivate FontMetrics fontMetrics;\n\t/** Text pane that the gutter gets the information from.\n\t */\n\tprivate JTextComponent textPane;\n\t/** The amount of padding applied to the left edge of the line numbers.\n\t */\n\tprivate final int PADDING_LEFT = 20;\n\t/** The amount of padding applied to the right edge of the line numbers, \n\t * between the line numbers and the border.\n\t */\n\tprivate final int PADDING_RIGHT = 4;\n\t/** Colour of the border between the panel and the text pane. */\n\tprivate final static Color BORDER_COLOR = Color.GRAY;\n\t/** Colour of the background of the panel. */\n\tprivate final static Color BACKGROUND_COLOR = new Color(204,204,204);\n\t/** The top padding for the text pane. */\n\tprivate int textPaneTopPadding;\n\t/** The distance from the text's baseline to the top of most \n\t * alphanumeric characters.\n\t */\n\tprivate int textFontAscent;\n\t/** The current height of the text within the text pane. */\n\tprivate int textHeight;\n\t/** The total width of the panel. */\n\tprivate int panelWidth;\n\t/** The width required to display the line numbers for the current line \n\t * count.\n\t */\n\tprivate int requiredLineNumbersWidth;\n\t/** The heights for each of the lines within the text pane. */\n\tprivate SizeSequence lineHeights;\n\t/** The current line count for the text pane. */\n\tprivate int lineCount = 1;\n\t/** The most recent line that was changed in the document. */\n\tprivate int updatedLine = 0;\n\t/** Indicates if the most recent change to the document spanned multiple \n\t * lines.\n\t */\n\tprivate boolean multipleLinesChanged = true;\n\t/** \n\t * Mapping from line numbers to error messages.\n\t */\n\tprivate Map<Integer, String> errorMessages;\n\t/** Error icon displayed along side the line where the parsing error\n\t * has occurred.\n\t */\n\tprivate ImageIcon errorIcon = GUIPrism.getIconFromImage(\"tinyError.png\");\n\n\t/**\n\t * Constructor, the panel is initialised with the information for the \n\t * current text in the given text pane.\n\t * \n\t * @param textPane Text pane to display the information about.\n\t */\n\tpublic GUITextModelEditorGutter(JTextComponent textPane)\n\t{\n\t\t//super(prismGUI, true);\n\t\t// Check that a text pane has been given.\n\t\tif (textPane == null) {\n\t\t\tthrow new IllegalArgumentException(\"The given text pane cannot be null.\");\n\t\t}\n\t\tthis.textPane = textPane;\n\t\tsetBorder(BorderFactory.createMatteBorder(0, 0, 0, 1, BORDER_COLOR));\n\t\t\n\t\tupdatePaintingCache();\n\t\ttextPane.addPropertyChangeListener(this);\n\t\ttextPane.getDocument().addDocumentListener(this);\n\t\t\n\t\tthis.setToolTipText(\"dummy\");\n\t}\t\n\n\t@Override\n\tpublic String getToolTipText(MouseEvent event) \n\t{\n\t\tif (errorMessages != null)\n\t\t{\n\t\t\tint y = event.getY();\n\t\t\t\n\t\t\tint line = lineHeights.getIndex(y);\n\t\t\tif (errorMessages.containsKey(line+1))\n\t\t\t\treturn errorMessages.get(line+1);\n\t\t\telse\n\t\t\t\treturn null;\t\t\t\t\n\t\t}\n\t\telse\n\t\t\treturn null;\t\n\t}\n\n\t/**\n\t * @return The preferred size of the component.\n\t */\n\tpublic Dimension getPreferredSize()\n\t{\n\t\treturn new Dimension(panelWidth, textPane.getHeight());\n\t}\n\t\n\tpublic void paintComponent(Graphics g)\n\t{\n\t\t// Draw the background of the panel.\n\t\tRectangle drawArea = g.getClipBounds();\n\t\tg.setColor(BACKGROUND_COLOR);\n\t\tg.fillRect(drawArea.x, drawArea.y, panelWidth, drawArea.height);\n\t\tg.setColor(getForeground());\n\t\t\n\t\t// Work out which line numbers to draw. Only want the line\n\t\t// numbers that are currently visible.\n\t\tint base = drawArea.y - textPaneTopPadding;\n\t\tint firstLine = lineHeights.getIndex(base);\n\t\tint lastLine = lineHeights.getIndex(base + drawArea.height);\n\n\t\t// Draw the line numbers\n\t\tString numberText = \"\";\n\t\tfor (int i = firstLine; i <= lastLine; i++) {\n\t\t\tnumberText = String.valueOf(i + 1);\n\t\t\tint x = PADDING_LEFT + requiredLineNumbersWidth - fontMetrics.stringWidth(numberText);\n\t\t\tint y = lineHeights.getPosition(i) + textFontAscent + textPaneTopPadding;\n\t\t\t\n\t\t\tboolean isErrorLine = false;\n\t\t\t\n\t\t\tif (errorMessages != null)\n\t\t\t{\n\t\t\t\tif (errorMessages.containsKey(Integer.valueOf(i+1)))\n\t\t\t\t\tisErrorLine = true;\n\t\t\t}\n\t\t\t\n\t\t\tg.setColor(Color.black);\n\t\t\tg.drawString(numberText, x, y);\n\t\t\t\n\t\t\t\n\t\t\t\n\t\t\t// If a parsing error has occurred on this line then display\n\t\t\t// the error icon.\n\t\t\t\n\t\t\tif (isErrorLine)\n\t\t\t\tg.drawImage(errorIcon.getImage(), drawArea.x, lineHeights.getPosition(i) + 3, errorIcon.getImageObserver());\t\t\t\n\t\t}\n\t}\n\t\n\t/** Property change listener for the text component, e.g. the font or tab size. */\n\tpublic void propertyChange(PropertyChangeEvent event)\n\t{\n\t\tObject oldValue = event.getOldValue();\n\t\tObject newValue = event.getNewValue();\n\t\t\n\t\t// If the document has changed, reset the document listeners.\n\t\tif (\"document\".equals(event.getPropertyName())) {\n\t\t\tif (oldValue != null && oldValue instanceof Document) {\n\t\t\t\t((Document) oldValue).removeDocumentListener(this);\n\t\t\t}\n\t\t\tif (newValue != null && newValue instanceof Document) {\n\t\t\t\t((Document) newValue).addDocumentListener(this);\n\t\t\t}\n\t\t}\n\t\t\n\t\tupdatePaintingCache();\n\t\t// The property change affects the whole document so the whole panel\n\t\t// gets redrawn.\n\t\tupdatePanel(0, true);\n\t}\n\n\t/** Insert listener event for the document, updates the panel to reflect\n\t * the change.\n\t */\n\tpublic void insertUpdate(DocumentEvent event)\n\t{\n\t\tdocumentUpdated(event);\n\t}\n\n\t/** Remove listener event for the document, updates the panel to reflect\n\t * the change.\n\t */\n\tpublic void removeUpdate(DocumentEvent event)\n\t{\n\t\tdocumentUpdated(event);\n\t}\n\n\t/** Change listener event for the document, updates the panel to reflect the \n\t * change.\n\t */\n\tpublic void changedUpdate(DocumentEvent event)\n\t{\n\t\t// This event is covered by the insert and delete listeners, \n\t\t// so it's not implemented.\n\t}\t\n\t\n\t/** Returns the height of the given line in the text pane.\n\t * \n\t * @param lineNumber The line number\n\t *            \n\t * @return The height, in pixels, for the given line.\n\t */\n\tprivate int getLineHeight(int lineNumber)\n\t{\n\t\tint position = lineHeights.getPosition(lineNumber) + textPaneTopPadding;\n\t\tint height = textHeight;\n\t\ttry {\n\t\t\tElement rootElement = textPane.getDocument().getDefaultRootElement();\n\t\t\tint lastChar = rootElement.getElement(lineNumber).getEndOffset() - 1;\n\t\t\tRectangle charView = textPane.modelToView(lastChar);\n\t\t\theight = (charView.y - position) + charView.height;\n\t\t} catch (BadLocationException ex) {\n\t\t\t/* Do nothing -- this occurs normally on LnF update */\n\t\t\t//ex.printStackTrace();\n\t\t} catch (NullPointerException ex) {\n\t\t\t/* Do nothing and return height */\n\t\t}\n\t\treturn height;\n\t}\n\t\n\t/* Copied from javax.swing.text.PlainDocument */\n\tprivate int getAdjustedLineCount()\n\t{\n\t\t// There is an implicit break being modeled at the end of the\n\t\t// document to deal with boundary conditions at the end. This\n\t\t// is not desired in the line count, so we detect it and remove\n\t\t// its effect if throwing off the count.\n\t\tElement rootElement = textPane.getDocument().getDefaultRootElement();\n\t\tint count = rootElement.getElementCount();\n\t\tElement lastLine = rootElement.getElement(count - 1);\n\t\tif ((lastLine.getEndOffset() - lastLine.getStartOffset()) > 1) {\n\t\t\treturn count;\n\t\t}\n\n\t\treturn count - 1;\n\t}\n\t\n\t/** Updates the line heights, if needed. */\n\tprivate void updateLineHeights()\n\t{\n\t\t// We only want to update if the document has been changed since\n\t\t// the last time the line heights were updated.\n\t\tif (updatedLine < 0) {\n\t\t\treturn;\n\t\t}\n\n\t\t// If multiple lines were changed then update all the line heights.\n\t\tif (multipleLinesChanged) {\n\t\t\t// Recreate the line sizes info for the whole document.\n\t\t\tint lineCount = getAdjustedLineCount();\n\t\t\tlineHeights = new SizeSequence(lineCount);\n\t\t\tfor (int i = 0; i < lineCount; i++) {\n\t\t\t\tlineHeights.setSize(i, getLineHeight(i));\n\t\t\t}\n\t\t\tmultipleLinesChanged = false;\n\t\t} else {\n\t\t\tlineHeights.setSize(updatedLine, getLineHeight(updatedLine));\n\t\t}\n\n\t\tupdatedLine = -1;\n\t}\n\n\t/** Updates the painting cache as some values used in the painting process \n\t * can be cached to improve performance.\n\t */\n\tprivate void updatePaintingCache()\n\t{\n\t\tupdateLineHeights();\n\t\tlineCount = getAdjustedLineCount();\n\t\ttextPaneTopPadding = textPane.getInsets().top;\n\t\t\n\t\t// Update the font info\n\t\tsetFont(textPane.getFont());\n\t\tfontMetrics = getFontMetrics(getFont());\n\t\ttextHeight = fontMetrics.getHeight();\n\t\ttextFontAscent = fontMetrics.getAscent();\n\n\t\t// Update the panel dimensions\n\t\trequiredLineNumbersWidth = fontMetrics.stringWidth(String.valueOf(lineCount));\n\t\tpanelWidth = PADDING_LEFT + requiredLineNumbersWidth + PADDING_RIGHT;\n\t}\n\n\t/** Indicates that the document was updated and the panel needs to be redrawn. */\n\tprivate void documentUpdated(DocumentEvent event)\n\t{\n\t\t// Get the line where the document was updated.\n\t\tElement rootElement = textPane.getDocument().getDefaultRootElement();\n\t\tint line = rootElement.getElementIndex(event.getOffset());\n\t\t// Get the structure change if there was one and update the panel.\n\t\tDocumentEvent.ElementChange change = event.getChange(rootElement);\n\t\tupdatePanel(line, change != null);\n\t}\n\t\n\t/** Update the panel as a result of a change in the document.\n\t * \n\t * @param updateLine The line that was updated.\n\t * @param multipleLineChange Indicates if the update spanned multiple lines.\n\t */\n\tprivate void updatePanel(int updateLine, boolean multipleLineChange)\n\t{\n\t\t// Make a note of how much changed, used when repainting.\n\t\tthis.updatedLine = updateLine;\n\t\tthis.multipleLinesChanged = multipleLineChange;\n\t\tupdatePaintingCache();\n\t\trevalidate();\n\t\trepaint();\n\t}\n\t\n\t// ----- Methods required by GUIPlugin but not needed. -----\n\n\tpublic boolean displaysTab() {return false;}\n\tpublic JMenu getMenu() {return null;}\n\tpublic String getTabText() {return null;}\n\tpublic JToolBar getToolBar() {return null;}\n\tpublic String getXMLIDTag() {return null;}\n\tpublic Object getXMLSaveTree() {return null;}\n\tpublic void loadXML(Object c) {}\n\tpublic void takeCLArgs(String[] args) {}\n\tpublic void notifySettings(PrismSettings settings) {}\n\n\tpublic void setParseErrors(Map<Integer, String> errorLines) \n\t{\n\t\tthis.errorMessages = errorLines;\n\t\trepaint();\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/GUITransientTime.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <Properties>\n    <Property name=\"defaultCloseOperation\" type=\"int\" value=\"2\"/>\n  </Properties>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,127,0,0,1,-67\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel5\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Component class=\"javax.swing.JLabel\" name=\"jLabel1\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Please specify a time for which to compute transient probabilities:\"/>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n        </Component>\n        <Component class=\"javax.swing.JTextField\" name=\"timeField\">\n          <Properties>\n            <Property name=\"columns\" type=\"int\" value=\"10\"/>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n        </Component>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel6\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n        <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n      </Layout>\n      <SubComponents>\n        <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n          </Events>\n        </Component>\n        <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n          </Events>\n        </Component>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/model/GUITransientTime.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport userinterface.*;\n\npublic class GUITransientTime extends javax.swing.JDialog\n{\n\tpublic static final int OK = 0;\n\tpublic static final int CANCELLED = 1;\n\t\n\tstatic String timeSpec = \"\";\n\tstatic boolean first = true;\n\t\n\tprivate boolean cancelled = true;\n\n\t/** Call this static method to construct a new GUITransientTime to get a time value. */\n\tpublic static int requestTime(GUIPrism parent)\n\t{\n\t\treturn new GUITransientTime(parent).requestTime();\n\t}\n\n\tpublic int requestTime()\n\t{\n\t\tshow();\n\t\treturn cancelled ? CANCELLED : OK;\n\t}\n\n\tpublic static String getTimeSpec()\n\t{\n\t\treturn timeSpec;\n\t}\n\n    /** Creates new form GUITransientTime */\n    public GUITransientTime(java.awt.Frame parent) {\n        super(parent, \"Define time\", true);\n        initComponents();\n        this.getRootPane().setDefaultButton(okayButton);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t\tif (!first) timeField.setText(timeSpec);\n    }\n    \n    /** This method is called from within the constructor to\n     * initialize the form.\n     * WARNING: Do NOT modify this code. The content of this method is\n     * always regenerated by the Form Editor.\n     */\n    private void initComponents() {//GEN-BEGIN:initComponents\n        java.awt.GridBagConstraints gridBagConstraints;\n\n        jPanel1 = new javax.swing.JPanel();\n        jPanel2 = new javax.swing.JPanel();\n        jPanel3 = new javax.swing.JPanel();\n        jPanel4 = new javax.swing.JPanel();\n        jPanel5 = new javax.swing.JPanel();\n        jLabel1 = new javax.swing.JLabel();\n        timeField = new javax.swing.JTextField();\n        jPanel6 = new javax.swing.JPanel();\n        okayButton = new javax.swing.JButton();\n        cancelButton = new javax.swing.JButton();\n\n        setDefaultCloseOperation(javax.swing.WindowConstants.DISPOSE_ON_CLOSE);\n        jPanel1.setLayout(new java.awt.GridBagLayout());\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 0;\n        jPanel1.add(jPanel2, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 2;\n        gridBagConstraints.gridy = 0;\n        jPanel1.add(jPanel3, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 2;\n        jPanel1.add(jPanel4, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 4;\n        jPanel1.add(jPanel5, gridBagConstraints);\n\n        jLabel1.setText(\"Please specify the time(s) for which to compute transient probabilities:\");\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        jPanel1.add(jLabel1, gridBagConstraints);\n\n        timeField.setColumns(10);\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 3;\n        jPanel1.add(timeField, gridBagConstraints);\n\n        getContentPane().add(jPanel1, java.awt.BorderLayout.CENTER);\n\n        jPanel6.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n        okayButton.setText(\"Okay\");\n        okayButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                okayButtonActionPerformed(evt);\n            }\n        });\n\n        jPanel6.add(okayButton);\n\n        cancelButton.setText(\"Cancel\");\n        cancelButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                cancelButtonActionPerformed(evt);\n            }\n        });\n\n        jPanel6.add(cancelButton);\n\n        getContentPane().add(jPanel6, java.awt.BorderLayout.SOUTH);\n        \n        \n        pack();\n    }//GEN-END:initComponents\n\n    private void cancelButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_cancelButtonActionPerformed\n\t\tdispose();\n    }//GEN-LAST:event_cancelButtonActionPerformed\n\n    private void okayButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_okayButtonActionPerformed\n\t\ttimeSpec = timeField.getText();\n\t\tfirst = false;\n\t\tcancelled = false;\n\t\tdispose();\n    }//GEN-LAST:event_okayButtonActionPerformed\n    \n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JButton cancelButton;\n    private javax.swing.JLabel jLabel1;\n    private javax.swing.JPanel jPanel1;\n    private javax.swing.JPanel jPanel2;\n    private javax.swing.JPanel jPanel3;\n    private javax.swing.JPanel jPanel4;\n    private javax.swing.JPanel jPanel5;\n    private javax.swing.JPanel jPanel6;\n    private javax.swing.JButton okayButton;\n    private javax.swing.JTextField timeField;\n    // End of variables declaration//GEN-END:variables\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/PepaEditorKit.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Charles Harley <cd.harley@talk21.com> (University of Edinburgh)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport java.awt.Color;\nimport java.awt.Font;\nimport java.awt.Graphics;\nimport java.awt.Graphics2D;\nimport java.awt.RenderingHints;\nimport java.util.regex.Matcher;\nimport java.util.regex.Pattern;\n\nimport javax.swing.text.BadLocationException;\nimport javax.swing.text.DefaultEditorKit;\nimport javax.swing.text.Document;\nimport javax.swing.text.Element;\nimport javax.swing.text.PlainDocument;\nimport javax.swing.text.PlainView;\nimport javax.swing.text.Segment;\nimport javax.swing.text.StyleContext;\nimport javax.swing.text.Utilities;\nimport javax.swing.text.View;\nimport javax.swing.text.ViewFactory;\n\n/** Pepa model editor kit for the text model editor. Defines the syntax\n * highlighting that the model editor should use.\n */\nclass PepaEditorKit extends DefaultEditorKit\n{\n\t\n\tprivate PepaContext preferences;\n\tprivate GUIMultiModelHandler handler;\n\t\n\t/** Creates a new instance of the Pepa editor kit.\n\t * \n\t * @param handler The GUI handler for this component.\n\t */\n\tpublic PepaEditorKit(GUIMultiModelHandler handler)\n\t{\n\t\tthis.handler = handler;\n\t}\n\t\n\tpublic PepaContext getStylePreferences()\n\t{\n\t\tif (preferences == null)\n\t\t{\n\t\t\tpreferences = new PepaContext(handler);\n\t\t}\n\t\treturn preferences;\n\t}\n\t\n\tpublic void setStylePreferences(PepaContext prefs)\n\t{\n\t\tpreferences = prefs;\n\t}\n\t\n\tpublic String getContentType()\n\t{\n\t\treturn \"text/pepa\";\n\t}\n\t\n\tpublic Document createDefaultDocument()\n\t{\n\t\treturn new PlainDocument();\n\t}\n\t\n\tpublic final ViewFactory getViewFactory()\n\t{\n\t\treturn getStylePreferences();\n\t}\n\t\n}\n\nclass PepaContext extends StyleContext implements ViewFactory\n{\n\n\tpublic static final String COMMENT_D = \"Single Line Comment\";\n\t\n\tprivate GUIMultiModelHandler handler;\n\t\n\t/** Creates a new instance of PepaContext.\n\t * \n\t * @param handler The GUI handler for this component. \n\t */\n\tpublic PepaContext(GUIMultiModelHandler handler)\n\t{\n\t\tthis.handler = handler;\n\t}\n\t\n\tpublic View create(Element elem)\n\t{\n\t\treturn new PepaView(elem, handler);\n\t}\n\t\n}\n\nclass PepaView extends PlainView\n{\n\t\n\tstatic final Style PLAIN_S = new Style(Color.black, Font.PLAIN);\n\tprivate Matcher match;\n\tprivate Pattern pattern;\n\tprivate GUIMultiModelHandler handler;\n\t\n\tpublic PepaView(Element elem, GUIMultiModelHandler handler)\n\t{\n\t\tsuper(elem);\n\t\tthis.handler = handler;\n\t\tpattern = Pattern.compile(\"%.*\");\n\t}\n\t\n\t@Override\n\tprotected float drawUnselectedText(Graphics2D g, float x, float y, int p0, int p1) throws BadLocationException\n\t{\n\t\tint stLine = findStartOfLine(p0, getDocument());\n\t\tint enLine = findEndOfLine(p1, getDocument());\n\t\tg.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\ttry\n\t\t{\n\t\t\tg.setColor(Color.green);\n\t\t\tDocument doc = getDocument();\n\t\t\tString s = doc.getText(stLine, enLine-stLine);\n\t\t\tStyle[] styles = highlight(s, (p0-stLine), (p1-p0));\n\t\t\tString fname = handler.getPepaEditorFontFast().getName();\n\t\t\tint fsize = handler.getPepaEditorFontFast().getSize();\n\t\t\tfor (int curr = 0; curr < styles.length; curr++) {\n\t\t\t\tStyle c = styles[curr];\n\t\t\t\tg.setColor(c.c);\n\t\t\t\tg.setFont(new Font(fname, c.style, fsize));\n\t\t\t\tSegment segm = getLineBuffer();\n\t\t\t\tdoc.getText(p0+curr, 1, segm);\n\t\t\t\tx = Utilities.drawTabbedText(segm, x, y, g, this, p0+curr);\n\t\t\t}\n\t\t\tg.setColor(Color.black);\n\t\t\tg.setFont(new Font(fname, Font.PLAIN, fsize));\n\t\t}\n\t\tcatch(BadLocationException ex) {\n\t\t\t//System.out.println(\"ex = \"+ex);\n\t\t\t//ex.printStackTrace();\n\t\t}\n\t\treturn x;\n\t}\n\t\n\t@Override\n\tprotected float drawSelectedText(Graphics2D g, float x, float y,int p0, int p1) throws BadLocationException\n\t{\n\t\tint stLine = findStartOfLine(p0, getDocument());\n\t\tint enLine = findEndOfLine(p1, getDocument());\n\t\tg.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\ttry {\n\t\t\tg.setColor(Color.green);\n\t\t\tDocument doc = getDocument();\n\t\t\tString s = doc.getText(stLine, enLine-stLine);\n\t\t\tStyle[] styles = highlight(s, (p0-stLine), (p1-p0));\n\t\t\tString fname = handler.getPepaEditorFontFast().getName();\n\t\t\tint fsize = handler.getPepaEditorFontFast().getSize();\n\t\t\tfor (int curr = 0; curr < styles.length; curr++) {\n\t\t\t\tStyle c = styles[curr];\n\t\t\t\tg.setColor(c.c);\n\t\t\t\tg.setFont(new Font(fname, c.style, fsize));\n\t\t\t\tSegment segm = getLineBuffer();\n\t\t\t\tdoc.getText(p0+curr, 1, segm);\n\t\t\t\tx = Utilities.drawTabbedText(segm, x, y, g, this, p0+curr);\n\t\t\t}\n\t\t\tg.setColor(Color.black);\n\t\t\tg.setFont(new Font(fname, Font.PLAIN, fsize));\n\t\t}\n\t\tcatch(BadLocationException ex) {\n\t\t\t//System.out.println(\"ex = \"+ex);\n\t\t\t//ex.printStackTrace();\n\t\t}\n\t\treturn x;\n\t}\n\t\n\tprivate synchronized Style[] highlight(String s, int offset, int length)\n\t{\n\t\tStyle[] styles = new Style[s.length()];\n\t\tfor(int i = 0; i < styles.length; i++)\n\t\t\tstyles[i] = PLAIN_S;\n\t\t\n\t\tmatch = pattern.matcher(s);\n\t\t\n\t\t\n\t\tint starter = 0;\n\t\tint end = 0;\n\t\tboolean contain = match.find();\n\t\twhile(contain)\n\t\t{\n\t\t\tstarter = match.start();\n\t\t\tend = match.end();\n\t\t\t\n\t\t\tfor(int j = starter; j < end; j++)\n\t\t\t{\n\t\t\t\tstyles[j] = handler.getPepaEditorCommentFast();\n\t\t\t}\n\t\t\tcontain = match.find();\n\t\t}\n\t\t\n\t\t//System.out.println(\"styles.length = \"+styles.length);\n\t\t//System.out.println(\"ret.length = \"+length);\n\t\t//System.out.println(\"offset = \"+offset);\n\t\tStyle[]ret = new Style[length];\n\t\tfor(int i = 0; i < ret.length; i++)\n\t\t{\n\t\t\tret[i] = styles[i+offset];\n\t\t}\n\t\t\n\t\treturn ret;\n\t}\n\t\n\t\n\tprivate synchronized int findStartOfLine(int p0, Document d)\n\t{\n\t\tint index = p0;\n\t\tString s = \"\";\n\t\ttry\n\t\t{\n\t\t\ts = d.getText(index, 1);\n\t\t}\n\t\tcatch(BadLocationException e)\n\t\t{\n\t\t\treturn 0;\n\t\t}\n\t\tindex--;\n\t\tif(!(!s.equals(\"\\n\") && index >= -1)) index--;//botch of the century, an alternative good code\n\t\twhile(!s.equals(\"\\n\") && index >= -1)\n\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\ts = d.getText(index, 1);\n\t\t\t}\n\t\t\tcatch(BadLocationException e)\n\t\t\t{\n\t\t\t\treturn 0;\n\t\t\t}\n\t\t\tindex--;\n\t\t}\n\t\tindex+=2;\n\t\treturn index;\n\t}\n\t\n\tprivate synchronized int findEndOfLine(int p1, Document d)\n\t{\n\t\tint index = p1;\n\t\tString s = \"\";\n\t\ttry\n\t\t{\n\t\t\ts = d.getText(index, 1);\n\t\t}\n\t\tcatch(BadLocationException e)\n\t\t{\n\t\t\treturn d.getLength();\n\t\t}\n\t\tindex++;\n\t\twhile(!s.equals(\"\\n\") && index <= d.getLength())\n\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\ts = d.getText(index, 1);\n\t\t\t}\n\t\t\tcatch(BadLocationException e)\n\t\t\t{\n\t\t\t\treturn d.getLength()-1;\n\t\t\t}\n\t\t\tindex++;\n\t\t}\n\t\tindex--;\n\t\treturn index;\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/PrismEditorKit.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Charles Harley <cd.harley@talk21.com> (University of Edinburgh)\n//\t* Sebastian Vermehren <seb03@hotmail.com> (University of Edinburgh)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport java.awt.Color;\nimport java.awt.Font;\nimport java.awt.Graphics2D;\nimport java.awt.RenderingHints;\n\nimport javax.swing.text.BadLocationException;\nimport javax.swing.text.DefaultEditorKit;\nimport javax.swing.text.DefaultStyledDocument;\nimport javax.swing.text.Document;\nimport javax.swing.text.Element;\nimport javax.swing.text.PlainView;\nimport javax.swing.text.Segment;\nimport javax.swing.text.StyleContext;\nimport javax.swing.text.Utilities;\nimport javax.swing.text.View;\nimport javax.swing.text.ViewFactory;\n\nimport prism.PrismLangException;\nimport parser.PrismSyntaxHighlighter;\n\n/** Prism model editor kit for the text model editor. Defines the syntax\n * highlighting that the model editor should use.\n */\nclass PrismEditorKit extends DefaultEditorKit\n{\n\t\n\tprivate PrismContext preferences;\n\tprivate GUIMultiModelHandler handler;\n\t\n\t/** Creates a new instance of the Prism editor kit.\n\t * \n\t * @param handler The GUI handler for this component.\n\t */\n\tpublic PrismEditorKit(GUIMultiModelHandler handler)\n\t{\n\t\tthis.handler = handler;\n\t}\n\n\tpublic PrismContext getStylePreferences()\n\t{\n\t\tif (preferences == null)\n\t\t{\n\t\t\tpreferences = new PrismContext(handler);\n\t\t}\n\t\treturn preferences;\n\t}\n\n\tpublic void setStylePreferences(PrismContext preferences)\n\t{\n\t\tthis.preferences = preferences;\n\t}\n\n\tpublic String getContentType()\n\t{\n\t\treturn \"text/prism\";\n\t}\n\n\tpublic Document createDefaultDocument()\n\t{\n\t\treturn new DefaultStyledDocument();\n\t}\n\n\tpublic final ViewFactory getViewFactory()\n\t{\n\t\treturn getStylePreferences();\n\t}\n\n}\n\nclass PrismContext extends StyleContext implements ViewFactory\n{\n\n\tpublic static final String KEY_WORD_D = \"Prism Keyword\";\n\tpublic static final String NUMERIC_D = \"Numeric\";\n\tpublic static final String VARIABLE_D = \"Variable\";\n\tpublic static final String COMMENT_D = \"Single Line Comment\";\n\t\n\tprivate GUIMultiModelHandler handler;\n\t\n\t/** Creates a new instance of PrismContext.\n\t * \n\t * @param handler The GUI handler for this component. \n\t */\n\tpublic PrismContext(GUIMultiModelHandler handler)\n\t{\n\t\tthis.handler = handler;\n\t}\n\n\tpublic View create(Element element)\n\t{\n\t\treturn new PrismView(element, handler);\n\t}\n\n}\n\nclass PrismView extends PlainView\n{\n\t\n\tstatic final Style PLAIN_S = new Style(Color.black, Font.PLAIN);\n\t\n\tprivate GUIMultiModelHandler handler;\n\n\tpublic PrismView(Element element, GUIMultiModelHandler handler)\n\t{\n\t\tsuper(element);\n\t\tthis.handler = handler;\n\t}\n\n\t@Override\n\tprotected float drawUnselectedText(Graphics2D g, float x, float y, int p0, int p1) throws BadLocationException\n\t{\n\t\tint stLine = p0;// findStartOfLine(p0, getDocument());\n\t\tint enLine = p1;// findEndOfLine(p1-1, getDocument());\n\t\tg.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\ttry {\n\t\t\tg.setColor(Color.green);\n\t\t\tDocument doc = getDocument();\n\t\t\tString s = doc.getText(stLine, enLine-stLine);\n\t\t\tStyle[] styles = highlight(s, (p0-stLine), (p1-p0));\n\t\t\tString fname = handler.getPrismEditorFontFast().getName();\n\t\t\tint fsize = handler.getPrismEditorFontFast().getSize();\n\n\t\t\tfor (int curr = 0; curr < styles.length; curr++) {\n\t\t\t\tStyle c = styles[curr];\n\t\t\t\tg.setColor(c.c);\n\t\t\t\tg.setFont(new Font(fname, c.style, fsize));\n\t\t\t\tSegment segm = new Segment();// getLineBuffer();\n\t\t\t\tdoc.getText(p0+curr, 1, segm);\n\t\t\t\tx = Utilities.drawTabbedText(segm, x, y, g, this, p0+curr);\n\t\t\t}\n\t\t\tg.setColor(Color.black);\n\t\t\tg.setFont(new Font(fname, Font.PLAIN, fsize));\n\t\t}\n\t\tcatch(BadLocationException ex) {\n\t\t\tex.printStackTrace();\n\t\t}\n\t\treturn x;\n\t}\n\n\t@Override\n\tprotected float drawSelectedText(Graphics2D g, float x, float y,int p0, int p1) throws BadLocationException\n\t{\n\t\tint stLine = p0;// findStartOfLine(p0, getDocument());\n\t\tint enLine = p1;// findEndOfLine(p1-1, getDocument());\n\t\tg.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\ttry {\n\t\t\tg.setColor(Color.green);\n\t\t\tDocument doc = getDocument();\n\t\t\tString s = doc.getText(stLine, enLine-stLine);\n\t\t\tStyle[] styles = highlight(s, (p0-stLine), (p1-p0));\n\t\t\tString fname = handler.getPrismEditorFontFast().getName();\n\t\t\tint fsize = handler.getPrismEditorFontFast().getSize();\n\t\t\tfor (int curr = 0; curr < styles.length; curr++) {\n\t\t\t\tStyle c = styles[curr];\n\t\t\t\tg.setColor(c.c);\n\t\t\t\tg.setFont(new Font(fname, c.style, fsize));\n\t\t\t\tSegment segm = new Segment();// getLineBuffer();\n\t\t\t\tdoc.getText(p0+curr, 1, segm);\n\t\t\t\tx = Utilities.drawTabbedText(segm, x, y, g, this, p0+curr);\n\t\t\t}\n\t\t\tg.setColor(Color.black);\n\t\t\tg.setFont(new Font(fname, Font.PLAIN, fsize));\n\t\t}\n\t\tcatch(BadLocationException ex) {\n\t\t\tex.printStackTrace();\n\t\t}\n\t\treturn x;\n\t}\n\n\tprivate synchronized Style[] highlight(String s, int offset, int length)\n\t{\n\t\tint typeArray[];\n\t\tint i, n;\n\t\tif(!s.endsWith(\"\\n\"))\n\t\t\ts += \"\\n\";\n\t\t// s = s.substring(0, s.length()-1);\n\n\t\ttry\n\t\t{\n\t\t\ttypeArray = PrismSyntaxHighlighter.lineForPrismGUI(s);\n\t\t}\n\t\tcatch (PrismLangException e)\n\t\t{\n\t\t\tn = s.length();\n\t\t\ttypeArray = new int[n];\n\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\ttypeArray[i] = PrismSyntaxHighlighter.PUNCTUATION;\n\t\t}\n\n\t\tStyle[] ret = new Style[length];\n\t\tfor (i = 0; i < length; i++)\n\t\t{\n\n\t\t\tif(i+offset < typeArray.length)\n\t\t\t{\n\t\t\t\tswitch (typeArray[i+offset])\n\t\t\t\t{\n\t\t\t\tcase PrismSyntaxHighlighter.PUNCTUATION: ret[i] = PLAIN_S; break;\n\t\t\t\tcase PrismSyntaxHighlighter.COMMENT: ret[i] = handler.getPrismEditorCommentFast(); break;\n\t\t\t\tcase PrismSyntaxHighlighter.WHITESPACE: ret[i] = PLAIN_S; break;\n\t\t\t\tcase PrismSyntaxHighlighter.KEYWORD: ret[i] = handler.getPrismEditorKeywordFast(); break;\n\t\t\t\tcase PrismSyntaxHighlighter.NUMERIC: ret[i] = handler.getPrismEditorNumericFast(); break;\n\t\t\t\tcase PrismSyntaxHighlighter.IDENTIFIER: ret[i] = handler.getPrismEditorVariableFast(); break;\n\t\t\t\tdefault: ret[i] = PLAIN_S; break;\n\t\t\t\t}\n\t\t\t}\n\t\t\telse ret[i] = PLAIN_S;\n\n\t\t}\n\n\t\treturn ret;\n\t}\n\n\t// Legacy code, kept in just in case the original developers decide they need it.\n\t/*private synchronized int findStartOfLine(int p0, Document d)\n\t{\n\t\tint index = p0;\n\t\tString s = \"\";\n\t\ttry\n\t\t{\n\t\t\ts = d.getText(index, 1);\n\t\t}\n\t\tcatch(BadLocationException e)\n\t\t{\n\t\t\treturn 0;\n\t\t}\n\t\tindex--;\n\t\tif(!(!s.equals(\"\\n\") && index >= -1)) index--;// botch of the\n\t\t// century, an\n\t\t// alternative good\n\t\t// code\n\t\twhile(!s.equals(\"\\n\") && index >= -1)\n\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\ts = d.getText(index, 1);\n\t\t\t}\n\t\t\tcatch(BadLocationException e)\n\t\t\t{\n\t\t\t\treturn 0;\n\t\t\t}\n\t\t\tindex--;\n\t\t}\n\t\tindex+=2;\n\t\treturn index;\n\t}\n\n\tprivate synchronized int findEndOfLine(int p1, Document d)\n\t{\n\t\tint index = p1;\n\t\tString s = \"\";\n\t\ttry\n\t\t{\n\t\t\ts = d.getText(index, 1);\n\t\t}\n\t\tcatch(BadLocationException e)\n\t\t{\n\t\t\treturn d.getLength();\n\t\t}\n\t\tindex++;\n\t\twhile(!s.equals(\"\\n\") && index <= d.getLength())\n\t\t{\n\t\t\ttry\n\t\t\t{\n\t\t\t\ts = d.getText(index, 1);\n\t\t\t}\n\t\t\tcatch(BadLocationException e)\n\t\t\t{\n\t\t\t\treturn d.getLength()-1;\n\t\t\t}\n\t\t\tindex++;\n\t\t}\n\t\tindex--;\n\t\treturn index;\n\t}*/\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/Style.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model;\n\nimport java.awt.*;\n\npublic class Style\n{\n    public Color c;\n    public int style;\n\t\n    public Style(Color c, int style)\n    {\n        this.c = c;\n        this.style = style;\n    }\n    \n    public static Style defaultStyle()\n    {\n        Style s = new Style(Color.black, Font.PLAIN);\n        return s;\n    }\n    \n    public Style copy()//grrrr\n    {\n        int r = c.getRed(), g = c.getGreen(), b = c.getBlue();\n        Color cc = new Color(r,g,b);\n        return new Style(cc, style);\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/BuildModelThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport javax.swing.*;\n\nimport userinterface.*;\nimport userinterface.model.*;\nimport prism.*;\nimport userinterface.util.*;\n\n/**\n * Thread that performs model construction, whether needed or not.\n */\npublic class BuildModelThread extends GUIComputationThread\n{\n\t@SuppressWarnings(\"unused\")\n\tprivate GUIMultiModelHandler handler;\n\n\t/** Creates a new instance of BuildModelThread */\n\tpublic BuildModelThread(GUIMultiModelHandler handler)\n\t{\n\t\tsuper(handler.getGUIPlugin());\n\t\tthis.handler = handler;\n\t}\n\n\tpublic void run()\n\t{\n\t\t// Notify user interface of the start of computation\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tplug.startProgress();\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\tplug.setTaskBarText(\"Building model...\");\n\t\t\t}\n\t\t});\n\n\t\t// Do build\n\t\ttry {\n\t\t\tprism.buildModel();\n\t\t} catch (Throwable e) {\n\t\t\terror(e);\n\t\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tplug.stopProgress();\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Building model... error.\");\n\t\t\t\t}\n\t\t\t});\n\t\t\treturn;\n\t\t}\n\n\t\t// If we are here, the build was successful, notify the interface\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tplug.stopProgress();\n\t\t\t\tplug.setTaskBarText(\"Building model... done.\");\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t}\n\t\t});\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/ComputeSteadyStateThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport javax.swing.*;\n\nimport io.ModelExportTask;\nimport userinterface.*;\nimport userinterface.model.*;\nimport userinterface.util.*;\n\n/**\n * Thread that performs steady-state probability computation on a model.\n */\npublic class ComputeSteadyStateThread extends GUIComputationThread\n{\n\t@SuppressWarnings(\"unused\")\n\tprivate GUIMultiModelHandler handler;\n\tprivate ModelExportTask exportTask;\n\n\t/** Creates a new instance of ComputeSteadyStateThread */\n\tpublic ComputeSteadyStateThread(GUIMultiModelHandler handler, ModelExportTask exportTask)\n\t{\n\t\tsuper(handler.getGUIPlugin());\n\t\tthis.handler = handler;\n\t\tthis.exportTask = exportTask;\n\t}\n\n\tpublic void run()\n\t{\n\t\t// Notify the interface that we are starting computation\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tplug.startProgress();\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\tplug.setTaskBarText(\"Computing steady-state probabilities...\");\n\t\t\t}\n\t\t});\n\n\t\t// Do Computation\n\t\ttry {\n\t\t\tprism.exportSteadyStateProbabilities(exportTask.getFile(), exportTask.getExportOptions(), null);\n\t\t} catch (Throwable e) {\n\t\t\terror(e);\n\t\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Computing steady-state probabilities... error.\");\n\t\t\t\t\tplug.stopProgress();\n\t\t\t\t}\n\t\t\t});\n\t\t\treturn;\n\t\t}\n\n\t\t// If we get here, computation was successful\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tplug.setTaskBarText(\"Computing steady-state probabilities... done.\");\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\tplug.stopProgress();\n\t\t\t}\n\t\t});\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/ComputeTransientThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport javax.swing.*;\n\nimport io.ModelExportTask;\nimport userinterface.*;\nimport userinterface.model.*;\nimport userinterface.util.*;\n\n/**\n * Thread that performs transient probability computation on a model.\n */\npublic class ComputeTransientThread extends GUIComputationThread\n{\n\t@SuppressWarnings(\"unused\")\n\tprivate GUIMultiModelHandler handler;\n\tprivate String transientTimeSpec;\n\tprivate ModelExportTask exportTask;\n\n\t/** Creates a new instance of ComputeTransientThread */\n\tpublic ComputeTransientThread(GUIMultiModelHandler handler, String transientTimeSpec, ModelExportTask exportTask)\n\t{\n\t\tsuper(handler.getGUIPlugin());\n\t\tthis.handler = handler;\n\t\tthis.transientTimeSpec = transientTimeSpec;\n\t\tthis.exportTask = exportTask;\n\t}\n\n\tpublic void run()\n\t{\n\t\t// Notify the interface that we are starting computation\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tplug.startProgress();\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\tplug.setTaskBarText(\"Computing transient probabilities...\");\n\t\t\t}\n\t\t});\n\n\t\t// Do Computation\n\t\ttry {\n\t\t\tprism.exportTransientProbabilities(transientTimeSpec, exportTask.getFile(), exportTask.getExportOptions(), null);\n\t\t} catch (Throwable e) {\n\t\t\terror(e);\n\t\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Computing transient probabilities... error.\");\n\t\t\t\t\tplug.stopProgress();\n\t\t\t\t}\n\t\t\t});\n\t\t\treturn;\n\t\t}\n\n\t\t//If we get here, computation was successful\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tplug.setTaskBarText(\"Computing transient probabilities... done.\");\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\tplug.stopProgress();\n\t\t\t}\n\t\t});\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/ExportBuiltModelThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport java.io.*;\nimport javax.swing.*;\n\nimport io.ModelExportTask;\nimport userinterface.*;\nimport userinterface.model.*;\nimport userinterface.util.*;\n\n/**\n * Thread that performs export of a built model.\n */\npublic class ExportBuiltModelThread extends GUIComputationThread\n{\n\tprivate ModelExportTask exportTask;\n\n\t/** Creates a new instance of ExportBuiltModelThread */\n\tpublic ExportBuiltModelThread(GUIMultiModelHandler handler, ModelExportTask exportTask)\n\t{\n\t\tthis(handler.getGUIPlugin(), exportTask);\n\t}\n\n\t/** Creates a new instance of ExportBuiltModelThread */\n\tpublic ExportBuiltModelThread(GUIPlugin plug, ModelExportTask exportTask)\n\t{\n\t\tsuper(plug);\n\t\tthis.exportTask = exportTask;\n\t}\n\n\tpublic void run()\n\t{\n\t\ttry {\n\t\t\t// Notify the interface of the start of computation\n\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tplug.startProgress();\n\t\t\t\t\tplug.setTaskBarText(\"Exporting...\");\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\t}\n\t\t\t});\n\n\t\t\t// Do export\n\t\t\ttry {\n\t\t\t\tprism.exportBuiltModelTask(exportTask);\n\t\t\t} catch (Throwable e2) {\n\t\t\t\terror(e2);\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t\t{\n\t\t\t\t\tpublic void run()\n\t\t\t\t\t{\n\t\t\t\t\t\tplug.stopProgress();\n\t\t\t\t\t\tplug.setTaskBarText(\"Exporting... error.\");\n\t\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t//If we get here export was successful, notify interface\n\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tplug.stopProgress();\n\t\t\t\t\tplug.setTaskBarText(\"Exporting... done.\");\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\t// catch and ignore any thread exceptions\n\t\tcatch (java.lang.InterruptedException e) {\n\t\t} catch (java.lang.reflect.InvocationTargetException e) {\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/LoadPEPAModelThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport java.io.*;\nimport javax.swing.*;\nimport userinterface.*;\nimport userinterface.model.*;\nimport userinterface.model.pepaModel.*;\nimport userinterface.util.*;\n\npublic class LoadPEPAModelThread extends Thread\n{\n\tprivate GUIMultiModelHandler handler;\n\tprivate GUIModelEditor edit;\n\tprivate File f;\n\tprivate boolean reload;\n\tprivate GUIPlugin plug;\n\tprivate GUIPepaModelEditor pepaEdit;\n\tprivate boolean replace;\n\tprivate Exception ex;\n\t\n\t/** Creates a new instance of LoadPEPAModelThread */\n\tpublic LoadPEPAModelThread(GUIMultiModelHandler handler, GUIModelEditor edit, File f, boolean reload)\n\t{\n\t\tthis.handler = handler;\n\t\tthis.edit = edit;\n\t\tthis.f = f;\n\t\tthis.reload = reload;\n\t\tplug = handler.getGUIPlugin(); //to communicate with rest of gui\n\t\treplace = false;\n\t\tex = null;\n\t}\n\t\n\tpublic void run()\n\t{\n\t\tif(edit instanceof GUIPepaModelEditor)\n\t\t{\n\t\t\tpepaEdit = (GUIPepaModelEditor)edit;\n\t\t\treplace = false;\n\t\t}\n\t\telse\n\t\t{\n\t\t\tpepaEdit = new GUIPepaModelEditor(handler);\n\t\t\treplace = true;\n\t\t}\n\t\t\n\t\ttry\n\t\t{\n\t\t\t//notify interface of start of computation and start the read into pepaEdit\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\ttry\n\t\t\t\t{\n\t\t\t\t\tplug.startProgress();\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Loading model...\");\n\t\t\t\t\tpepaEdit.read(new FileReader(f), f);\n\t\t\t\t}\n\t\t\t\tcatch(IOException e)\n\t\t\t\t{\n\t\t\t\t\tex = e;\n\t\t\t\t}\n\t\t\t}});\n\t\t\t\n\t\t\t//If there was a problem with the loading, notify the interface.\n\t\t\tif(ex != null) {\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\t\tplug.stopProgress(); \n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Loading model... error.\");\n\t\t\t\t\tplug.error(\"Could not open file \\\"\" + f + \"\\\"\");\n\t\t\t\t}});\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t\n\t\t\t//If we get here, the load has been successful, notify the interface and tell the handler.\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\tplug.stopProgress(); \n\t\t\t\tplug.setTaskBarText(\"Loading model... done.\");\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\tif(!reload)\n\t\t\t\t\thandler.pepaModelLoaded(pepaEdit, f ,replace);\n\t\t\t\telse\n\t\t\t\t\thandler.pepaModelReLoaded(f);\n\t\t\t}});\n\t\t}\n\t\t// catch and ignore any thread exceptions\n\t\tcatch (java.lang.InterruptedException e) {}\n\t\tcatch (java.lang.reflect.InvocationTargetException e) {}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/LoadPRISMModelThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport java.io.*;\nimport javax.swing.*;\n\nimport userinterface.*;\nimport userinterface.model.*;\nimport userinterface.util.*;\n\npublic class LoadPRISMModelThread extends Thread\n{\n\tprivate GUIMultiModelHandler handler;\n\tprivate GUIModelEditor edit;\n\tprivate File f;\n\tprivate boolean reload;\n\tprivate GUIPlugin plug;\n\tprivate GUITextModelEditor textEdit;\n\tprivate boolean replace;\n\tprivate Exception ex;\n\t\n\t/** Creates a new instance of LoadPRISMModelThread */\n\tpublic LoadPRISMModelThread(GUIMultiModelHandler handler, GUIModelEditor edit, File f, boolean reload)\n\t{\n\t\tthis.handler = handler;\n\t\tthis.edit = edit;\n\t\tthis.f = f;\n\t\tthis.reload = reload;\n\t\tplug = handler.getGUIPlugin(); //to communicate with rest of gui\n\t\treplace = false;\n\t\tex = null;\n\t}\n\n\tpublic void run()\n\t{\n\t\tif(edit instanceof GUITextModelEditor)\n\t\t{\n\t\t\ttextEdit = (GUITextModelEditor)edit;\n\t\t\treplace = false;\n\t\t}\n\t\telse\n\t\t{\n\t\t\ttextEdit = new GUITextModelEditor(\"\",handler);\n\t\t\treplace = true;\n\t\t}\n\t\t\n\t\ttry\n\t\t{\n\t\t\t//notify interface of start of computation and start the read into textEdit\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\ttry\n\t\t\t\t{\n\t\t\t\t\tplug.startProgress();\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Loading model...\");\n\t\t\t\t\ttextEdit.read(new FileReader(f), f);\n\t\t\t\t}\n\t\t\t\tcatch(IOException e)\n\t\t\t\t{\n\t\t\t\t\tex = e;\n\t\t\t\t}\n\t\t\t}});\n\t\t\t\n\t\t\t//If there was a problem with the loading, notify the interface.\n\t\t\tif(ex != null) {\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\t\tplug.stopProgress(); \n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Loading model... error.\");\n\t\t\t\t\tplug.error(\"Could not open file \\\"\" + f + \"\\\"\");\n\t\t\t\t}});\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t\n\t\t\t//If we get here, the load has been successful, notify the interface and tell the handler.\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\tplug.stopProgress(); \n\t\t\t\tplug.setTaskBarText(\"Loading model... done.\");\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\tif(!reload)\n\t\t\t\t\thandler.prismModelLoaded(textEdit, f ,replace);\n\t\t\t\telse\n\t\t\t\t\thandler.prismModelReLoaded(f);\n\t\t\t}});\n\t\t}\n\t\t// catch and ignore any thread exceptions\n\t\tcatch (java.lang.InterruptedException e) {}\n\t\tcatch (java.lang.reflect.InvocationTargetException e) {}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/ParseModelThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport javax.swing.*;\n\nimport userinterface.model.*;\nimport parser.ast.*;\nimport prism.*;\nimport userinterface.util.*;\nimport userinterface.GUIComputationThread;\n\npublic class ParseModelThread extends GUIComputationThread\n{\n\tprivate GUIMultiModelHandler handler;\n\tprivate String parseThis;\n\tprivate boolean isPepa;\n\tprivate boolean background;\n\tprivate ModulesFile mod;\n\tprivate String errMsg;\n\tprivate PrismException parseError;\n\tstatic int counter = 0;\n\tint id;\n\tlong before;\n\n\t/** Creates a new instance of ParseModelThread */\n\tpublic ParseModelThread(GUIMultiModelHandler handler, String parseThis, boolean isPepa, boolean background)\n\t{\n\t\tsuper(handler.getGUIPlugin());\n\t\tthis.handler = handler;\n\t\tthis.parseThis = parseThis;\n\t\tthis.isPepa = isPepa;\n\t\tthis.background = background;\n\t\tid = counter;\n\t\tcounter++;\n\t}\n\n\tpublic void run()\n\t{\n\t\t// Notify user interface of the start of computation\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tif (!background)\n\t\t\t\t\tplug.startProgress();\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\tif (!background)\n\t\t\t\t\tplug.setTaskBarText(\"Parsing model...\");\n\t\t\t}\n\t\t});\n\n\t\t// do parsing\n\t\ttry {\n\t\t\t// normal prism mode\n\t\t\tif (!isPepa) {\n\t\t\t\tif (!background)\n\t\t\t\t\tplug.log(\"\\nParsing model...\\n\");\n\t\t\t\tmod = prism.parseModelString(parseThis);\n\t\t\t}\n\t\t\t// pepa mode\n\t\t\telse {\n\t\t\t\tif (!background)\n\t\t\t\t\tplug.log(\"\\nParsing PEPA model...\\n\");\n\t\t\t\tmod = prism.importPepaString(parseThis);\n\t\t\t}\n\t\t\t// Load into PRISM once done\n\t\t\tprism.loadPRISMModel(mod);\n\t\t} catch (PrismException err) {\n\t\t\tparseError = err;\n\t\t\terrMsg = err.getMessage();\n\t\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tif (!background)\n\t\t\t\t\t\tplug.stopProgress();\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\tif (!background)\n\t\t\t\t\t\tplug.setTaskBarText(\"Parsing model... error.\");\n\t\t\t\t\tif (!background)\n\t\t\t\t\t\terror(errMsg);\n\t\t\t\t\thandler.modelParseFailed(parseError, background);\n\t\t\t\t}\n\t\t\t});\n\t\t\treturn;\n\t\t}\n\n\t\t// If we get here, the parse has been successful, notify the interface and tell the handler.\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tif (!background)\n\t\t\t\t\tplug.stopProgress();\n\t\t\t\tif (!background)\n\t\t\t\t\tplug.setTaskBarText(\"Parsing model... done.\");\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\thandler.modelParsedSuccessful(mod);\n\t\t\t}\n\t\t});\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/SavePEPAModelThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport java.io.*;\nimport javax.swing.*;\nimport userinterface.*;\nimport userinterface.model.*;\nimport userinterface.model.pepaModel.*;\nimport userinterface.util.*;\n\npublic class SavePEPAModelThread extends Thread\n{\n\tprivate GUIModelEditor editor;\n\tprivate GUIMultiModelHandler handler;\n\tprivate File f;\n\tprivate GUIPlugin plug;\n\tprivate Exception ex;\n\t\n\t/** Creates a new instance of SavePEPAModelThread */\n\tpublic SavePEPAModelThread(File f, GUIMultiModelHandler handler, GUIModelEditor editor)\n\t{\n\t\tthis.editor = editor;\n\t\tthis.handler = handler;\n\t\tthis.f = f;\n\t\tplug = handler.getGUIPlugin();\t\n\t\tex = null;\n\t}\n\t\n\tpublic void run()\n\t{\n\t\ttry\n\t\t{\n\t\t\t//notify the interface of the start of computation and save the content of editor to f\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\ttry\n\t\t\t\t{\n\t\t\t\t\tplug.startProgress();\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Saving model...\");\n\t\t\t\t\t((GUIPepaModelEditor)editor).write(new FileWriter(f));\n\t\t\t\t}\n\t\t\t\tcatch(IOException e)\n\t\t\t\t{\n\t\t\t\t\tex = e;\n\t\t\t\t}\n\t\t\t\tcatch(ClassCastException e)\n\t\t\t\t{\n\t\t\t\t\tex = e;\n\t\t\t\t}\n\t\t\t}});\n\t\t\t\n\t\t\t//If there was a problem with the save, notify the interface.\n\t\t\tif(ex != null) {\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\t\tplug.stopProgress(); \n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Saving model... error.\");\n\t\t\t\t\tplug.error(\"Could not save to file \\\"\" + f + \"\\\"\");\n\t\t\t\t}});\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t\n\t\t\t//If we get here, the save has been successful, notify the interface and tell the handler.\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\tplug.stopProgress(); \n\t\t\t\tplug.setTaskBarText(\"Saving model... done.\");\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\thandler.pepaFileWasSaved(f);\n\t\t\t}});\n\t\t}\n\t\t// catch and ignore any thread exceptions\n\t\tcatch (java.lang.InterruptedException e) {}\n\t\tcatch (java.lang.reflect.InvocationTargetException e) {}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/SavePRISMModelThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.computation;\n\nimport java.io.*;\nimport javax.swing.*;\nimport userinterface.*;\nimport userinterface.model.*;\nimport userinterface.util.*;\n\npublic class SavePRISMModelThread extends Thread\n{\n\tprivate GUIModelEditor editor;\n\tprivate GUIMultiModelHandler handler;\n\tprivate File f;\n\tprivate GUIPlugin plug;\n\tprivate Exception ex;\n\t\n\t/** Creates a new instance of SavePRISMModelThread */\n\tpublic SavePRISMModelThread(File f, GUIMultiModelHandler handler, GUIModelEditor editor)\n\t{\n\t\tthis.editor = editor;\n\t\tthis.handler = handler;\n\t\tthis.f = f;\n\t\tplug = handler.getGUIPlugin();\n\t\tex = null;\n\t}\n\t\n\tpublic void run()\n\t{\n\t\ttry\n\t\t{\n\t\t\t//notify the interface of the start of computation and save the contents of editor\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\ttry\n\t\t\t\t{\n\t\t\t\t\tplug.startProgress();\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Saving model...\");\n\t\t\t\t\t((GUITextModelEditor)editor).write(new FileWriter(f));\n\t\t\t\t}\n\t\t\t\tcatch(IOException e)\n\t\t\t\t{\n\t\t\t\t\tex = e;\n\t\t\t\t}\n\t\t\t\tcatch(ClassCastException e)\n\t\t\t\t{\n\t\t\t\t\tex = e;\n\t\t\t\t}\n\t\t\t}});\n\t\t\t\n\t\t\t//If there was a problem with the save, notify the interface.\n\t\t\tif(ex != null) {\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\t\tplug.stopProgress(); \n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\tplug.setTaskBarText(\"Saving model... error.\");\n\t\t\t\t\tplug.error(\"Could not save to file \\\"\" + f + \"\\\"\");\n\t\t\t\t}});\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t\n\t\t\t//If we get here, the save has been successful, notify the interface and tell the handler.\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\tplug.stopProgress(); \n\t\t\t\tplug.setTaskBarText(\"Saving model... done.\");\n\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\thandler.prismFileWasSaved(f);\n\t\t\t}});\n\t\t}\n\t\t// catch and ignore any thread exceptions\n\t\tcatch (java.lang.InterruptedException e) {}\n\t\tcatch (java.lang.reflect.InvocationTargetException e) {}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/computation/package-info.java",
    "content": "/**\n * Computation threads for model construction functionality in the GUI (\"Model\" tab)\n */\npackage userinterface.model.computation;\n"
  },
  {
    "path": "prism/src/userinterface/model/package-info.java",
    "content": "/**\n * Model editing/construction functionality in the GUI (\"Model\" tab)\n */\npackage userinterface.model;\n"
  },
  {
    "path": "prism/src/userinterface/model/pepaModel/GUIPepaModelEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.model.pepaModel;\n\nimport java.awt.BorderLayout;\nimport java.awt.Color;\nimport java.awt.Font;\nimport java.awt.Graphics;\nimport java.awt.Graphics2D;\nimport java.awt.RenderingHints;\nimport java.awt.Shape;\nimport java.io.IOException;\nimport java.io.Reader;\nimport java.io.Writer;\nimport java.util.regex.Matcher;\nimport java.util.regex.Pattern;\n\nimport javax.swing.JEditorPane;\nimport javax.swing.JScrollPane;\nimport javax.swing.event.DocumentEvent;\nimport javax.swing.event.DocumentListener;\nimport javax.swing.text.BadLocationException;\nimport javax.swing.text.DefaultEditorKit;\nimport javax.swing.text.Document;\nimport javax.swing.text.Element;\nimport javax.swing.text.PlainDocument;\nimport javax.swing.text.PlainView;\nimport javax.swing.text.Segment;\nimport javax.swing.text.StyleContext;\nimport javax.swing.text.Utilities;\nimport javax.swing.text.View;\nimport javax.swing.text.ViewFactory;\nimport javax.swing.undo.CannotRedoException;\nimport javax.swing.undo.CannotUndoException;\nimport javax.swing.undo.UndoManager;\n\nimport userinterface.model.GUIModelEditor;\nimport userinterface.model.GUIMultiModelHandler;\nimport userinterface.model.Style;\n\npublic class GUIPepaModelEditor extends GUIModelEditor implements DocumentListener\n{\t\n\tprivate JEditorPane editor;\n\tprivate UndoManager undoManager;\n\tprivate PlainDocument d;\n\tprivate GUIMultiModelHandler handler;\n\t\n\t/** Creates a new instance of GUIPepaModelEditor */\n\tpublic GUIPepaModelEditor(GUIMultiModelHandler handler)\n\t{\n\t\teditor = new JEditorPane();\n\t\tPepaEditorKit kit = new PepaEditorKit();\n\t\teditor.setEditorKitForContentType(\"text/pepa\", kit);\n\t\teditor.setContentType(\"text/pepa\");\n\t\tundoManager = new UndoManager();\n\t\tundoManager.setLimit(200);\n\t\t//editor.setForeground(FOREGROUND_COLOR);\n\t\tthis.handler = handler;\n\t\td = (PlainDocument)editor.getDocument();\n\t\teditor.getDocument().addDocumentListener(this);\n\t\tinitComponents();\n\t\t\n\t}\n\t\n\tprivate void initComponents()\n\t{\n\t\tJScrollPane scroller = new JScrollPane();\n\t\t{\n\t\t\tscroller.setViewportView(editor);\n\t\t}\n\t\tsetLayout(new BorderLayout());\n\t\tadd(scroller, BorderLayout.CENTER);\n\t}\n\t\n\tpublic void changedUpdate(DocumentEvent e)\n\t{\n\t}\n\t\n\tpublic void insertUpdate(DocumentEvent e)\n\t{\n\t\tif (handler != null)handler.hasModified(true);\n\t}\n\t\n\tpublic void removeUpdate(DocumentEvent e)\n\t{\n\t\tif (handler != null)handler.hasModified(true);\n\t}\n\t\n\tpublic String getParseText()\n\t{\n\t\treturn editor.getText();\n\t}\n\t\n\tpublic void newModel()\n\t{\n\t\teditor.setText(\"\");\n\t}\n\t\n\tpublic void read(Reader s, Object obj) throws IOException\n\t{\n\t\teditor.read(s, obj);\n\t\td = (PlainDocument)editor.getDocument();\n\t\td.addDocumentListener(this);\n\t\t// System.out.println(\"here\");\n\t}\n\t\n\tpublic void write(Writer s) throws IOException\n\t{\n\t\teditor.write(s);\n\t}\n\t\n\t/** Performs an undo operation on the text in the model editor.\n     */\n\tpublic void undo() {\n\t\ttry {\n\t\t\tundoManager.undo();\n\t\t} catch (CannotUndoException ex) {\n\t\t\t\n\t\t\t//GUIPrism.getGUI().getMultiLogger().logMessage(PrismLogLevel.PRISM_ERROR, ex.getMessage());\n\t\t}\n\t}\n\t\n\t/** Performs a redo operation on the text in the model editor.\n     */\n\tpublic void redo() {\n\t\ttry {\n\t\t\tundoManager.redo();\n\t\t} catch (CannotRedoException ex) {\n\t\t\t//GUIPrism.getGUI().getMultiLogger().logMessage(PrismLogLevel.PRISM_ERROR, ex.getMessage());\n\t\t}\n\t}\n\t\n\tpublic void copy()\n\t{\n\t\teditor.copy();\n\t}\n\t\n\tpublic void cut()\n\t{\n\t\teditor.cut();\n\t}\n\t\n\tpublic void paste()\n\t{\n\t\teditor.paste();\n\t}\n\t\n\tpublic void delete()\n\t{\n\t\t\n\t}\n\t\n\tpublic void selectAll()\n\t{\n\t\teditor.selectAll();\n\t}\n\t\n\tpublic boolean isEditable()\n\t{\n\t\treturn editor.isEditable();\n\t}\n\t\n\tpublic void setEditorFont(Font f)\n\t{\n\t\teditor.setFont(f);\n\t}\n\t\n\tpublic void setEditorBackground(Color c)\n\t{\n\t\teditor.setBackground(c);\n\t}\n\t\n\tclass PepaEditorKit extends DefaultEditorKit\n\t{\n\t\t\n\t\tprivate PepaContext preferences;\n\t\t/** Creates a new instance of PrismEditorKit */\n\t\tpublic PepaEditorKit()\n\t\t{\n\t\t\tsuper();\n\t\t}\n\t\t\n\t\tpublic PepaContext getStylePreferences()\n\t\t{\n\t\t\tif (preferences == null)\n\t\t\t{\n\t\t\t\tpreferences = new PepaContext();\n\t\t\t}\n\t\t\treturn preferences;\n\t\t}\n\t\t\n\t\tpublic void setStylePreferences(PepaContext prefs)\n\t\t{\n\t\t\tpreferences = prefs;\n\t\t}\n\t\t\n\t\tpublic String getContentType()\n\t\t{\n\t\t\treturn \"text/pepa\";\n\t\t}\n\t\t\n\t\tpublic Document createDefaultDocument()\n\t\t{\n\t\t\treturn new PlainDocument();\n\t\t}\n\t\t\n\t\tpublic final ViewFactory getViewFactory()\n\t\t{\n\t\t\treturn getStylePreferences();\n\t\t}\n\t\t\n\t\t\n\t}\n\t\n\tclass PepaContext extends StyleContext implements ViewFactory\n\t{\n\t\t\n\t\t\n\t\t\n\t\tpublic static final String COMMENT_D = \"Single Line Comment\";\n\t\t\n\t\t/** Creates a new instance of PrismContext */\n\t\tpublic PepaContext()\n\t\t{\n\t\t\tsuper();\n\t\t}\n\t\t\n\t\tpublic View create(Element elem)\n\t\t{\n\t\t\treturn new PepaView(elem);\n\t\t}\n\t\t\n\t\t\n\t}\n\t\n\tstatic final Style PLAIN_S = new Style(Color.black, Font.PLAIN);\n\tclass PepaView extends PlainView\n\t{\n\t\t\n\t\tprivate Matcher match;\n\t\tprivate Pattern pattern;\n\t\tpublic PepaView(Element elem)\n\t\t{\n\t\t\tsuper(elem);\n\t\t\t\n\t\t\tpattern = Pattern.compile(\"%.*\");\n\t\t}\n\t\t\n\t\tpublic void paint(Graphics g, Shape a)\n\t\t{\n\t\t\tsuper.paint(g, a);\n\t\t}\n\t\t\n\t\t@Override\n\t\tprotected float drawUnselectedText(Graphics2D g, float x, float y, int p0, int p1) throws BadLocationException\n\t\t{\n\t\t\tint stLine = findStartOfLine(p0, getDocument());\n\t\t\tint enLine = findEndOfLine(p1, getDocument());\n\t\t\tg.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\ttry {\n\t\t\t\tg.setColor(Color.green);\n\t\t\t\tDocument doc = getDocument();\n\t\t\t\tString s = doc.getText(stLine, enLine-stLine);\n\t\t\t\tStyle[] styles = highlight(s, (p0-stLine), (p1-p0));\n\t\t\t\tString fname = handler.getPepaEditorFontFast().getName();\n\t\t\t\tint fsize = handler.getPepaEditorFontFast().getSize();\n\t\t\t\tfor (int curr = 0; curr < styles.length; curr++) {\n\t\t\t\t\tStyle c = styles[curr];\n\t\t\t\t\tg.setColor(c.c);\n\t\t\t\t\tg.setFont(new Font(fname, c.style, fsize));\n\t\t\t\t\tSegment segm = getLineBuffer();\n\t\t\t\t\tdoc.getText(p0+curr, 1, segm);\n\t\t\t\t\tx = Utilities.drawTabbedText(segm, x, y, g, this, p0+curr);\n\t\t\t\t}\n\t\t\t\tg.setColor(Color.black);\n\t\t\t\tg.setFont(new Font(fname, Font.PLAIN, fsize));\n\t\t\t}\n\t\t\tcatch(BadLocationException ex) {\n\t\t\t\t//System.out.println(\"ex = \"+ex);\n\t\t\t\t//ex.printStackTrace();\n\t\t\t}\n\t\t\treturn x;\n\t\t}\n\t\t\n\t\t@Override\n\t\tprotected float drawSelectedText(Graphics2D g, float x, float y,int p0, int p1) throws BadLocationException\n\t\t{\n\t\t\tint stLine = findStartOfLine(p0, getDocument());\n\t\t\tint enLine = findEndOfLine(p1, getDocument());\n\t\t\tg.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\ttry {\n\t\t\t\tg.setColor(Color.green);\n\t\t\t\tDocument doc = getDocument();\n\t\t\t\tString s = doc.getText(stLine, enLine-stLine);\n\t\t\t\tStyle[] styles = highlight(s, (p0-stLine), (p1-p0));\n\t\t\t\tString fname = handler.getPepaEditorFontFast().getName();\n\t\t\t\tint fsize = handler.getPepaEditorFontFast().getSize();\n\t\t\t\tfor(int curr = 0; curr < styles.length; curr++) {\n\t\t\t\t\tStyle c = styles[curr];\n\t\t\t\t\tg.setColor(c.c);\n\t\t\t\t\tg.setFont(new Font(fname, c.style, fsize));\n\t\t\t\t\tSegment segm = getLineBuffer();\n\t\t\t\t\tdoc.getText(p0+curr, 1, segm);\n\t\t\t\t\tx = Utilities.drawTabbedText(segm, x, y, g, this, p0+curr);\n\t\t\t\t}\n\t\t\t\tg.setColor(Color.black);\n\t\t\t\tg.setFont(new Font(fname, Font.PLAIN, fsize));\n\t\t\t}\n\t\t\tcatch(BadLocationException ex) {\n\t\t\t\t//System.out.println(\"ex = \"+ex);\n\t\t\t\t//ex.printStackTrace();\n\t\t\t}\n\t\t\treturn x;\n\t\t}\n\t\t\n\t\tprivate synchronized Style[] highlight(String s, int offset, int length)\n\t\t{\n\t\t\tStyle[] styles = new Style[s.length()];\n\t\t\tfor(int i = 0; i < styles.length; i++)\n\t\t\t\tstyles[i] = PLAIN_S;\n\t\t\t\n\t\t\tmatch = pattern.matcher(s);\n\t\t\t\n\t\t\t\n\t\t\tint starter = 0;\n\t\t\tint end = 0;\n\t\t\tboolean contain = match.find();\n\t\t\twhile(contain)\n\t\t\t{\n\t\t\t\tstarter = match.start();\n\t\t\t\tend = match.end();\n\t\t\t\t\n\t\t\t\tfor(int j = starter; j < end; j++)\n\t\t\t\t{\n\t\t\t\t\tstyles[j] = handler.getPepaEditorCommentFast();\n\t\t\t\t}\n\t\t\t\tcontain = match.find();\n\t\t\t}\n\t\t\t\n\t\t\t//System.out.println(\"styles.length = \"+styles.length);\n\t\t\t//System.out.println(\"ret.length = \"+length);\n\t\t\t//System.out.println(\"offset = \"+offset);\n\t\t\tStyle[]ret = new Style[length];\n\t\t\tfor(int i = 0; i < ret.length; i++)\n\t\t\t{\n\t\t\t\tret[i] = styles[i+offset];\n\t\t\t}\n\t\t\t\n\t\t\treturn ret;\n\t\t}\n\t\t\n\t\t\n\t\tprivate synchronized int findStartOfLine(int p0, Document d)\n\t\t{\n\t\t\tint index = p0;\n\t\t\tString s = \"\";\n\t\t\ttry\n\t\t\t{\n\t\t\t\ts = d.getText(index, 1);\n\t\t\t}\n\t\t\tcatch(BadLocationException e)\n\t\t\t{\n\t\t\t\treturn 0;\n\t\t\t}\n\t\t\tindex--;\n\t\t\tif(!(!s.equals(\"\\n\") && index >= -1)) index--;//botch of the century, an alternative good code\n\t\t\twhile(!s.equals(\"\\n\") && index >= -1)\n\t\t\t{\n\t\t\t\ttry\n\t\t\t\t{\n\t\t\t\t\ts = d.getText(index, 1);\n\t\t\t\t}\n\t\t\t\tcatch(BadLocationException e)\n\t\t\t\t{\n\t\t\t\t\treturn 0;\n\t\t\t\t}\n\t\t\t\tindex--;\n\t\t\t}\n\t\t\tindex+=2;\n\t\t\treturn index;\n\t\t}\n\t\t\n\t\tprivate synchronized int findEndOfLine(int p1, Document d)\n\t\t{\n\t\t\tint index = p1;\n\t\t\tString s = \"\";\n\t\t\ttry\n\t\t\t{\n\t\t\t\ts = d.getText(index, 1);\n\t\t\t}\n\t\t\tcatch(BadLocationException e)\n\t\t\t{\n\t\t\t\treturn d.getLength();\n\t\t\t}\n\t\t\tindex++;\n\t\t\twhile(!s.equals(\"\\n\") && index <= d.getLength())\n\t\t\t{\n\t\t\t\ttry\n\t\t\t\t{\n\t\t\t\t\ts = d.getText(index, 1);\n\t\t\t\t}\n\t\t\t\tcatch(BadLocationException e)\n\t\t\t\t{\n\t\t\t\t\treturn d.getLength()-1;\n\t\t\t\t}\n\t\t\t\tindex++;\n\t\t\t}\n\t\t\tindex--;\n\t\t\treturn index;\n\t\t}\n\t\t\n\t\t\n\t\t\n\t}\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/model/pepaModel/package-info.java",
    "content": "/**\n * Text editor for PEPA models in the GUI.\n */\npackage userinterface.model.pepaModel;\n"
  },
  {
    "path": "prism/src/userinterface/package-info.java",
    "content": "/**\n * PRISM's graphical user interface (GUI).\n */\npackage userinterface;\n"
  },
  {
    "path": "prism/src/userinterface/properties/ConstantHeader.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n  <Properties>\n    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n      <Dimension value=\"[640, 38]\"/>\n    </Property>\n  </Properties>\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,45,0,0,2,117\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n  <SubComponents>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel1\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Name\"/>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[50, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.1\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel2\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Type\"/>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[150, 15]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[50, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.1\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel3\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Single Value:\"/>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[1079, 15]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[5, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel4\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Start\"/>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[1079, 15]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[5, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"5\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel5\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"End\"/>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[1079, 15]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[5, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"6\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel6\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Step\"/>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[5, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"7\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel7\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"0\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Range:\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"5\" gridY=\"0\" gridWidth=\"3\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Properties>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[21, 21]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[21, 21]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[21, 21]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"2\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n      <Properties>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[21, 21]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[21, 21]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[21, 21]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"4\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/properties/ConstantHeader.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.awt.*;\n\npublic class ConstantHeader extends javax.swing.JPanel\n{\n    \n    /** Creates new form ConstantLine */\n    public ConstantHeader()\n    {\n\t\tinitComponents();\n\t\tsetPreferredSize(new Dimension(1, 2*(getFontMetrics(getFont()).getHeight() + 4)));\n    }\n    \n    /** This method is called from within the constructor to\n     * initialize the form.\n     * WARNING: Do NOT modify this code. The content of this method is\n     * always regenerated by the Form Editor.\n     */\n    // <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n    private void initComponents() {\n        java.awt.GridBagConstraints gridBagConstraints;\n\n        jLabel1 = new javax.swing.JLabel();\n        jLabel2 = new javax.swing.JLabel();\n        jLabel3 = new javax.swing.JLabel();\n        jLabel4 = new javax.swing.JLabel();\n        jLabel5 = new javax.swing.JLabel();\n        jLabel6 = new javax.swing.JLabel();\n        jLabel7 = new javax.swing.JLabel();\n        jPanel1 = new javax.swing.JPanel();\n        jPanel2 = new javax.swing.JPanel();\n\n        setLayout(new java.awt.GridBagLayout());\n\n        setPreferredSize(new java.awt.Dimension(640, 38));\n        jLabel1.setText(\"Name\");\n        jLabel1.setMaximumSize(new java.awt.Dimension(100, 15));\n        jLabel1.setMinimumSize(new java.awt.Dimension(50, 15));\n        jLabel1.setPreferredSize(new java.awt.Dimension(100, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.1;\n        add(jLabel1, gridBagConstraints);\n\n        jLabel2.setText(\"Type\");\n        jLabel2.setMaximumSize(new java.awt.Dimension(150, 15));\n        jLabel2.setMinimumSize(new java.awt.Dimension(50, 15));\n        jLabel2.setPreferredSize(new java.awt.Dimension(100, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.1;\n        add(jLabel2, gridBagConstraints);\n\n        jLabel3.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel3.setText(\"Single Value:\");\n        jLabel3.setMaximumSize(new java.awt.Dimension(1079, 15));\n        jLabel3.setMinimumSize(new java.awt.Dimension(5, 15));\n        jLabel3.setPreferredSize(new java.awt.Dimension(100, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 3;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        add(jLabel3, gridBagConstraints);\n\n        jLabel4.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel4.setText(\"Start\");\n        jLabel4.setMaximumSize(new java.awt.Dimension(1079, 15));\n        jLabel4.setMinimumSize(new java.awt.Dimension(5, 15));\n        jLabel4.setPreferredSize(new java.awt.Dimension(100, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 5;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        add(jLabel4, gridBagConstraints);\n\n        jLabel5.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel5.setText(\"End\");\n        jLabel5.setMaximumSize(new java.awt.Dimension(1079, 15));\n        jLabel5.setMinimumSize(new java.awt.Dimension(5, 15));\n        jLabel5.setPreferredSize(new java.awt.Dimension(100, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 6;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        add(jLabel5, gridBagConstraints);\n\n        jLabel6.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel6.setText(\"Step\");\n        jLabel6.setMinimumSize(new java.awt.Dimension(5, 15));\n        jLabel6.setPreferredSize(new java.awt.Dimension(100, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 7;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        add(jLabel6, gridBagConstraints);\n\n        jLabel7.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);\n        jLabel7.setText(\"Range:\");\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 5;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.gridwidth = 3;\n        add(jLabel7, gridBagConstraints);\n\n        jPanel1.setMaximumSize(new java.awt.Dimension(21, 21));\n        jPanel1.setMinimumSize(new java.awt.Dimension(21, 21));\n        jPanel1.setPreferredSize(new java.awt.Dimension(21, 21));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 2;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.ipadx = 5;\n        add(jPanel1, gridBagConstraints);\n\n        jPanel2.setMaximumSize(new java.awt.Dimension(21, 21));\n        jPanel2.setMinimumSize(new java.awt.Dimension(21, 21));\n        jPanel2.setPreferredSize(new java.awt.Dimension(21, 21));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 4;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.ipadx = 5;\n        add(jPanel2, gridBagConstraints);\n\n    }// </editor-fold>//GEN-END:initComponents\n    \n    \n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JLabel jLabel1;\n    private javax.swing.JLabel jLabel2;\n    private javax.swing.JLabel jLabel3;\n    private javax.swing.JLabel jLabel4;\n    private javax.swing.JLabel jLabel5;\n    private javax.swing.JLabel jLabel6;\n    private javax.swing.JLabel jLabel7;\n    private javax.swing.JPanel jPanel1;\n    private javax.swing.JPanel jPanel2;\n    // End of variables declaration//GEN-END:variables\n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/ConstantLine.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n  <NonVisualComponents>\n    <Component class=\"javax.swing.ButtonGroup\" name=\"choiceButtonGroup\">\n    </Component>\n    <Component class=\"javax.swing.JComboBox\" name=\"boolSingleValueCombo\">\n      <Properties>\n        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n        </Property>\n        <Property name=\"model\" type=\"javax.swing.ComboBoxModel\" editor=\"org.netbeans.modules.form.editors2.ComboBoxModelEditor\">\n          <StringArray count=\"2\">\n            <StringItem index=\"0\" value=\"true\"/>\n            <StringItem index=\"1\" value=\"false\"/>\n          </StringArray>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[4, 19]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[4, 19]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"sizerPanel\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n  </NonVisualComponents>\n  <Properties>\n    <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n      <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n    </Property>\n    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n      <Dimension value=\"[640, 23]\"/>\n    </Property>\n  </Properties>\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,25,0,0,1,-33\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n  <SubComponents>\n    <Component class=\"javax.swing.JLabel\" name=\"nameLabel\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"a\"/>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[50, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.1\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"typeLabel\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"double\"/>\n        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[150, 15]\"/>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[50, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[100, 15]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"1\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.1\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"singleValueField\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.2\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"startValueField\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"5\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.2\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"endValueField\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"6\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.2\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JTextField\" name=\"stepValueField\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"7\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.2\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"singleValueCombo\">\n      <Properties>\n        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n        </Property>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"choiceButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"singleValueComboActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Component class=\"javax.swing.JRadioButton\" name=\"rangeCombo\">\n      <Properties>\n        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n        </Property>\n        <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n          <ComponentRef name=\"choiceButtonGroup\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"rangeComboActionPerformed\"/>\n      </Events>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"4\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/properties/ConstantLine.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//  * Mark Kattenbelt <mxk@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.awt.*;\n\nimport prism.*;\nimport parser.type.*;\n\npublic class ConstantLine extends javax.swing.JPanel\n{\n\tpublic static final String SINGLE_DEFAULT = \"0\";\n\tpublic static final String RANGE_START_DEFAULT = \"0\";\n\tpublic static final String RANGE_END_DEFAULT = \"1\";\n\tpublic static final String STEP_DEFAULT = \"1\";\n\t\n\tprivate Type type;\n\t\n\t/** Creates new form ConstantLine */\n\tpublic ConstantLine(String name, Type type)\n\t{\n\tinitComponents();\n\t//setBorder(new BottomBorder());\n\tsetPreferredSize(new Dimension(1, getFontMetrics(getFont()).getHeight() + 4));\n\tsetConstName(name);\n\tsetConstType(type);\n\tdoDefaults();\n\t}\n\t\n\tpublic void setConstName(String str)\n\t{\n\tnameLabel.setText(str);\n\t}\n\t\n\tpublic void setConstType(Type type)\n\t{\n\t\tthis.type = type;\n\t\tif (type instanceof TypeBool) {\n\t\t\ttypeLabel.setText(\"bool\");\n\t\t\trangeCombo.setEnabled(false);\n\t\t\tsingleValueCombo.setSelected(true);\n\t\t\t\n\t\t\tremove(singleValueField);\n\t\t\tremove(boolSingleValueCombo);\n\t\t\tremove(sizerPanel);\n\t\t\tjava.awt.GridBagConstraints gridBagConstraints = new java.awt.GridBagConstraints();\n\t\t\tgridBagConstraints.gridx = 3;\n\t\t\tgridBagConstraints.gridy = 0;\n\t\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\t\tgridBagConstraints.weightx = 0.2;\n\t\t\tgridBagConstraints.ipadx = 5;\n\t\t\tadd(boolSingleValueCombo, gridBagConstraints);\n\t\t\t//add(sizerPanel, gridBagConstraints);\n\t\t}\n\t\telse if (type instanceof TypeDouble) {\n\t\t\ttypeLabel.setText(\"double\");\n\t\t\trangeCombo.setEnabled(true);\n\t\t\tsingleValueCombo.setSelected(true);\n\t\t\t\n\t\t\tremove(singleValueField);\n\t\t\tremove(boolSingleValueCombo);\n\t\t\tremove(sizerPanel);\n\t\t\tjava.awt.GridBagConstraints gridBagConstraints = new java.awt.GridBagConstraints();\n\t\t\tgridBagConstraints.gridx = 3;\n\t\t\tgridBagConstraints.gridy = 0;\n\t\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\t\tgridBagConstraints.weightx = 0.2;\n\t\t\tgridBagConstraints.ipadx = 5;\n\t\t\tadd(singleValueField, gridBagConstraints);\n\t\t}\n\t\telse if (type instanceof TypeInt) {\n\t\t\ttypeLabel.setText(\"int\");\n\t\t\trangeCombo.setEnabled(true);\n\t\t\tsingleValueCombo.setSelected(true);\n\t\t\tremove(singleValueField);\n\t\t\tremove(boolSingleValueCombo);\n\t\t\tremove(sizerPanel);\n\t\t\tjava.awt.GridBagConstraints gridBagConstraints = new java.awt.GridBagConstraints();\n\t\t\tgridBagConstraints.gridx = 3;\n\t\t\tgridBagConstraints.gridy = 0;\n\t\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\t\tgridBagConstraints.weightx = 0.2;\n\t\t\tgridBagConstraints.ipadx = 5;\n\t\t\tadd(singleValueField, gridBagConstraints);\n\t\t}\n\t\telse {\n\t\t\ttypeLabel.setText(\"unknown\");\n\t\t\trangeCombo.setEnabled(true);\n\t\t\tsingleValueCombo.setSelected(true);\n\t\t\tremove(singleValueField);\n\t\t\tremove(boolSingleValueCombo);\n\t\t\tremove(sizerPanel);\n\t\t\tjava.awt.GridBagConstraints gridBagConstraints = new java.awt.GridBagConstraints();\n\t\t\tgridBagConstraints.gridx = 3;\n\t\t\tgridBagConstraints.gridy = 0;\n\t\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\t\tgridBagConstraints.weightx = 0.2;\n\t\t\tadd(singleValueField, gridBagConstraints);\n\t\t}\n\t}\n\t\n\tpublic void doDefaults()\n\t{\n\tsingleValueField.setText(SINGLE_DEFAULT);\n\tstartValueField.setText(RANGE_START_DEFAULT);\n\tendValueField.setText(RANGE_END_DEFAULT);\n\tstepValueField.setText(STEP_DEFAULT);\n\tsingleValueCombo.setSelected(true);\n\t\n\tdoEnables();\n\t}\n\t\n\tpublic void doEnables()\n\t{\n\tif(singleValueCombo.isSelected())\n\t{\n\t\tstartValueField.setEnabled(false);\n\t\tendValueField.setEnabled(false);\n\t\tstepValueField.setEnabled(false);\n\t\tboolSingleValueCombo.setEnabled(true);\n\t\tsingleValueField.setEnabled(true);\n\t}\n\telse if(rangeCombo.isSelected())\n\t{\n\t\tstartValueField.setEnabled(true);\n\t\tendValueField.setEnabled(true);\n\t\tstepValueField.setEnabled(true);\n\t\tboolSingleValueCombo.setEnabled(false);\n\t\tsingleValueField.setEnabled(false);\n\t}\n\t}\n\t\n\t//ACCESS METHODS\n\t\n\tpublic Type getType()\n\t{\n\t\treturn type;\n\t}\n\t\n\tpublic boolean isRange()\n\t{\n\t\treturn rangeCombo.isSelected();\n\t}\n\t\n\tpublic void setIsRange(boolean b)\n\t{\n\t\trangeCombo.setSelected(b);\n\t\tsingleValueCombo.setSelected(!b);\n\t\tdoEnables();\n\t}\n\t\n\tpublic String getSingleValue()\n\t{\n\t\tif(type instanceof TypeBool)\n\t\t{\n\t\t\treturn boolSingleValueCombo.getSelectedItem().toString();\n\t\t}\n\t\telse\n\t\t{\n\t\t\treturn singleValueField.getText();\n\t\t}\n\t}\n\t\n\tpublic void setSingleValue(String str)\n\t{\n\t\tif(type instanceof TypeBool)\n\t\t{\n\t\t\tif (str != null) boolSingleValueCombo.setSelectedIndex(str.equals(\"true\") ? 0 : 1);\n\t\t\telse boolSingleValueCombo.setSelectedIndex(0); // default\n\t\t}\n\t\telse\n\t\t{\n\t\t\tif (str != null) singleValueField.setText(str);\n\t\t\telse singleValueField.setText(SINGLE_DEFAULT);\n\t\t}\n\t}\n\t\n\tpublic String getStartValue()\n\t{\n\t\treturn startValueField.getText();\n\t}\n\t\n\tpublic void setStartValue(String str)\n\t{\n\t\tstartValueField.setText((str != null) ? str : RANGE_START_DEFAULT);\n\t}\n\t\n\tpublic String getEndValue()\n\t{\n\t\treturn endValueField.getText();\n\t}\n\t\n\tpublic void setEndValue(String str)\n\t{\n\t\tendValueField.setText((str != null) ? str : RANGE_END_DEFAULT);\n\t}\n\t\n\tpublic String getStepValue()\n\t{\n\t\treturn stepValueField.getText();\n\t}\n\t\n\tpublic void setStepValue(String str)\n\t{\n\t\tstepValueField.setText((str != null) ? str : STEP_DEFAULT);\n\t}\n\t\n\tpublic String getName()\n\t{\n\t\treturn nameLabel.getText();\n\t}\n\t\n\tpublic void checkValid() throws PrismException\n\t{\n\t\tString s = \"\";\n\t\t\n\t\tif(type instanceof TypeBool)\n\t\t{\n\t\t\ts = boolSingleValueCombo.getSelectedItem().toString();\n\t\t\tif (!(s.equals(\"true\") | s.equals(\"false\"))) {\n\t\t\t\tthrow new PrismException(\"Invalid value \\\"\"+s+\"\\\" for Boolean constant \\\"\"+getName()+\"\\\"\");\n\t\t\t}\n\t\t}\n\t\telse if(type instanceof TypeInt)\n\t\t{\n\t\t\ttry {\n\t\t\t\ts = singleValueField.getText(); Integer.parseInt(s);\n\t\t\t\tif (isRange()) {\n\t\t\t\t\ts = startValueField.getText(); Integer.parseInt(s);\n\t\t\t\t\ts = endValueField.getText(); Integer.parseInt(s);\n\t\t\t\t\ts = stepValueField.getText(); Integer.parseInt(s);\n\t\t\t\t}\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Invalid value \\\"\"+s+\"\\\" for integer constant \\\"\"+getName()+\"\\\"\");\n\t\t\t}\n\t\t}\n\t\telse if(type instanceof TypeDouble)\n\t\t{\n\t\t\ttry {\n\t\t\t\ts = singleValueField.getText(); DefinedConstant.parseDouble(s);\n\t\t\t\tif (isRange()) {\n\t\t\t\t\ts = startValueField.getText(); DefinedConstant.parseDouble(s);\n\t\t\t\t\ts = endValueField.getText(); DefinedConstant.parseDouble(s);\n\t\t\t\t\ts = stepValueField.getText(); DefinedConstant.parseDouble(s);\n\t\t\t\t}\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tthrow new PrismException(\"Invalid value \\\"\"+s+\"\\\" for double constant \\\"\"+getName()+\"\\\"\");\n\t\t\t}\n\t\t}\n\t\telse {\n\t\t\t// should never happen\n\t\t\tthrow new PrismException(\"Unknown type for constant \\\"\"+getName()+\"\\\"\");\n\t\t}\n\t}\n\t\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n    // <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n    private void initComponents() {\n        java.awt.GridBagConstraints gridBagConstraints;\n\n        choiceButtonGroup = new javax.swing.ButtonGroup();\n        boolSingleValueCombo = new javax.swing.JComboBox();\n        sizerPanel = new javax.swing.JPanel();\n        nameLabel = new javax.swing.JLabel();\n        typeLabel = new javax.swing.JLabel();\n        singleValueField = new javax.swing.JTextField();\n        startValueField = new javax.swing.JTextField();\n        endValueField = new javax.swing.JTextField();\n        stepValueField = new javax.swing.JTextField();\n        singleValueCombo = new javax.swing.JRadioButton();\n        rangeCombo = new javax.swing.JRadioButton();\n\n        boolSingleValueCombo.setBackground(new java.awt.Color(255, 255, 255));\n        boolSingleValueCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"true\", \"false\" }));\n        boolSingleValueCombo.setMinimumSize(new java.awt.Dimension(4, 19));\n        boolSingleValueCombo.setPreferredSize(new java.awt.Dimension(4, 19));\n\n        setLayout(new java.awt.GridBagLayout());\n\n        setBackground(new java.awt.Color(255, 255, 255));\n        setPreferredSize(new java.awt.Dimension(640, 23));\n        nameLabel.setText(\"a\");\n        nameLabel.setMaximumSize(new java.awt.Dimension(100, 15));\n        nameLabel.setMinimumSize(new java.awt.Dimension(50, 15));\n        nameLabel.setPreferredSize(new java.awt.Dimension(100, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.1;\n        add(nameLabel, gridBagConstraints);\n\n        typeLabel.setText(\"double\");\n        typeLabel.setMaximumSize(new java.awt.Dimension(150, 15));\n        typeLabel.setMinimumSize(new java.awt.Dimension(50, 15));\n        typeLabel.setPreferredSize(new java.awt.Dimension(100, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.1;\n        add(typeLabel, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 3;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.weightx = 0.2;\n        add(singleValueField, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 5;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.weightx = 0.2;\n        add(startValueField, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 6;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.weightx = 0.2;\n        add(endValueField, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 7;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.ipadx = 5;\n        gridBagConstraints.weightx = 0.2;\n        add(stepValueField, gridBagConstraints);\n\n        singleValueCombo.setBackground(new java.awt.Color(255, 255, 255));\n        choiceButtonGroup.add(singleValueCombo);\n        singleValueCombo.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                singleValueComboActionPerformed(evt);\n            }\n        });\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 2;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.ipadx = 5;\n        add(singleValueCombo, gridBagConstraints);\n\n        rangeCombo.setBackground(new java.awt.Color(255, 255, 255));\n        choiceButtonGroup.add(rangeCombo);\n        rangeCombo.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                rangeComboActionPerformed(evt);\n            }\n        });\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 4;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.ipadx = 5;\n        add(rangeCombo, gridBagConstraints);\n\n    }// </editor-fold>//GEN-END:initComponents\n\t\n\tprivate void rangeComboActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_rangeComboActionPerformed\n\t{//GEN-HEADEREND:event_rangeComboActionPerformed\n\tdoEnables();\n\t}//GEN-LAST:event_rangeComboActionPerformed\n\t\n\tprivate void singleValueComboActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_singleValueComboActionPerformed\n\t{//GEN-HEADEREND:event_singleValueComboActionPerformed\n\tdoEnables();\n\t}//GEN-LAST:event_singleValueComboActionPerformed\n\t\n\t\n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    javax.swing.JComboBox boolSingleValueCombo;\n    private javax.swing.ButtonGroup choiceButtonGroup;\n    javax.swing.JTextField endValueField;\n    javax.swing.JLabel nameLabel;\n    javax.swing.JRadioButton rangeCombo;\n    javax.swing.JRadioButton singleValueCombo;\n    javax.swing.JTextField singleValueField;\n    javax.swing.JPanel sizerPanel;\n    javax.swing.JTextField startValueField;\n    javax.swing.JTextField stepValueField;\n    javax.swing.JLabel typeLabel;\n    // End of variables declaration//GEN-END:variables\n\t\n\tclass BottomBorder implements javax.swing.border.Border\n\t{\n\tpublic Insets getBorderInsets(Component c)\n\t{\n\t\treturn new Insets(0,0,1,0);\n\t}\n\t\n\tpublic boolean isBorderOpaque()\n\t{\n\t\treturn true;\n\t}\n\t\n\tpublic void paintBorder(Component c, Graphics g, int x, int y, int width, int height)\n\t{\n\t\tg.setColor(Color.lightGray);\n\t\tg.drawLine(x,(y+height-1), (x+width), (y+height-1));\n\t\t\n\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/ConstantPickerList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport javax.swing.*;\nimport javax.swing.border.CompoundBorder;\nimport javax.swing.border.LineBorder;\n\nimport java.awt.*;\nimport java.util.*;\n\n@SuppressWarnings(\"serial\")\npublic class ConstantPickerList extends JPanel implements Scrollable\n{\n\tprivate ArrayList<ConstantLine> rows;\n\tprivate JPanel nextPanel;\n\n\t/** Creates a new instance of ConstantPickerList */\n\tpublic ConstantPickerList()\n\t{\n\t\tsetLayout(new BorderLayout());\n\t\tnextPanel = new JPanel();\n\t\tnextPanel.setLayout(new BorderLayout());\n\t\tadd(nextPanel, BorderLayout.CENTER);\n\t\trows = new ArrayList<ConstantLine>();\n\t}\n\n\tpublic void addConstant(ConstantLine pl)\n\t{\n\t\trows.add(pl);\n\t\tJPanel containPl = new JPanel();\n\t\tcontainPl.setLayout(new BorderLayout());\n\t\tcontainPl.setBorder(new CompoundBorder(pl.new BottomBorder(), new LineBorder(Color.white, 2)));\n\t\tcontainPl.add(pl, BorderLayout.CENTER);\n\t\tnextPanel.add(containPl, BorderLayout.NORTH);\n\t\tJPanel np = new JPanel();\n\t\tnp.setLayout(new BorderLayout());\n\t\tnextPanel.add(np, BorderLayout.CENTER);\n\t\tnextPanel = np;\n\t}\n\n\tpublic Dimension getPreferredScrollableViewportSize()\n\t{\n\t\treturn getPreferredSize();\n\t}\n\n\tpublic int getScrollableBlockIncrement(Rectangle visibleRect, int orientation, int direction)\n\t{\n\t\treturn 20;\n\t}\n\n\tpublic boolean getScrollableTracksViewportHeight()\n\t{\n\t\treturn false;\n\t}\n\n\tpublic boolean getScrollableTracksViewportWidth()\n\t{\n\t\treturn true;\n\t}\n\n\tpublic int getScrollableUnitIncrement(Rectangle visibleRect, int orientation, int direction)\n\t{\n\t\treturn 40;\n\t}\n\n\tpublic int getNumConstants()\n\t{\n\t\treturn rows.size();\n\t}\n\n\tpublic ConstantLine getConstantLine(int i)\n\t{\n\t\treturn rows.get(i);\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIConstant.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.*;\n\nclass GUIConstant\n{\n\tpublic GUIMultiProperties parent;\n\tpublic String name;\n\tpublic String constant;\n\tpublic Type type;\n\tpublic Exception parseError;\n\t\n\tpublic GUIConstant(GUIMultiProperties parent, String name, String constant, Type type)\n\t{\n\t\tthis.parent = parent;\n\t\tthis.name = name;\n\t\tthis.constant = constant;\n\t\tthis.type = type;\n\t\tthis.parseError = null;\n\t}\n\t\n\tpublic void parse()\n\t{\n\t\tExpression expr = null;\n\t\tthis.parseError = null;\n\t\t// See if constant definition is parseable\n\t\ttry {\n\t\t\t// Check name is a valid identifier\n\t\t\ttry { expr = Prism.parseSingleExpressionString(name); }\n\t\t\tcatch (PrismLangException e) { throw new PrismException(\"Invalid constant name \\\"\"+name+\"\\\"\"); }\n\t\t\tif (expr == null || !(expr instanceof ExpressionIdent)) throw new PrismException(\"Invalid constant name \\\"\"+name+\"\\\"\");\n\t\t\t// Check (non-empty) constant definition is valid (single) expression\n\t\t\ttry { if (!(\"\".equals(constant))) Prism.parseSingleExpressionString(constant); }\n\t\t\tcatch (PrismLangException e) { throw new PrismException(\"Invalid expression \\\"\"+constant+\"\\\"\"); }\n\t\t}\n\t\tcatch (PrismException e) {\n\t\t\tthis.parseError = e;\n\t\t}\n\t}\n\t\n\tpublic boolean isParseable() { return parseError==null; }\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"const \"+type.getTypeString()+\" \"+name+getValueString()+\";\";\n\t}\n\t\n\tpublic String getValueString()\n\t{\n\t\tif (\"\".equals(constant)) return \"\";\n\t\telse return \" = \" + constant; \n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIExperiment.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport parser.*;\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.*;\nimport userinterface.*;\n\nimport javax.swing.*;\n\nimport common.StackTraceHelper;\n\nimport java.util.*;\nimport userinterface.util.*;\n\npublic class GUIExperiment\n{\n\tprotected GUIMultiProperties guiProp;\n\tprotected GUIExperimentTable table;\n\tprotected prism.ResultsCollection results;\n\tprotected boolean finished = false;\n\n\tprotected UndefinedConstants cons;\n\tprotected PropertiesFile prop; //contains 1 property only\n\n\tprotected boolean running = false;\n\n\tprotected Thread theThread;\n\n\tprotected boolean useSimulation;\n\n\tprotected Values definedMFConstants;\n\tprotected Values definedPFConstants;\n\tprotected Result res;\n\n\t/** Creates a new instance of GUIExperiment\n\t * @param prop  contains exactly 1 property\n\t */\n\tpublic GUIExperiment(GUIExperimentTable table, GUIMultiProperties guiProp, PropertiesFile prop, UndefinedConstants cons, boolean useSimulation)\n\t{\n\t\tthis(table, guiProp, prop, cons, useSimulation, null);\n\t}\n\n\t/**\n\t * Create an experiment from a result collection.\n\t * As the results are already complete, the experiment is finished and serves as a mockup.\n\t */\n\tpublic GUIExperiment(GUIExperimentTable table, GUIMultiProperties guiProp, PropertiesFile prop, UndefinedConstants cons, boolean useSimulation, ResultsCollection results)\n\t{\n\t\tthis.table = table;\n\t\tthis.guiProp = guiProp;\n\t\tthis.prop = prop;\n\t\tthis.cons = cons;\n\t\tthis.useSimulation = useSimulation;\n\t\tthis.results = (results == null) ? new prism.ResultsCollection(cons, prop.getProperty(0).getResultName()) : results;\n\t}\n\n\t//ACCESS METHODS\n\n\tpublic int getTotalIterations()\n\t{\n\t\treturn cons.getNumIterations();\n\t}\n\n\tpublic int getCurrentIterations()\n\t{\n\t\treturn results.getCurrentIteration();\n\t}\n\n\t@SuppressWarnings(\"rawtypes\")\n\tpublic Vector<DefinedConstant> getRangingConstants()\n\t{\n\t\treturn cons.getRangingConstants();\n\t}\n\n\tpublic String getDefinedConstantsString()\n\t{\n\t\treturn cons.getDefinedConstantsString();\n\t}\n\n\tpublic String getPFDefinedConstantsString()\n\t{\n\t\treturn cons.getPFDefinedConstantsString();\n\t}\n\n\tpublic Property getProperty()\n\t{\n\t\t// prop  contains exactly 1 property\n\t\tint i = prop.getNumProperties() - 1;\n\t\treturn prop.getPropertyObject(i);\n\t}\n\n\tpublic String getExpressionString()\n\t{\n\t\treturn getProperty().getExpression().toString();\n\t}\n\n\tpublic Type getExpressionType()\n\t{\n\t\treturn getProperty().getExpression().getType();\n\t}\n\n\tpublic ResultsCollection getResults()\n\t{\n\t\treturn results;\n\t}\n\n\tpublic boolean isFinished()\n\t{\n\t\treturn finished;\n\t}\n\n\tpublic boolean isUseSimulation()\n\t{\n\t\treturn useSimulation;\n\t}\n\n\tpublic GUIExperimentTable getTable()\n\t{\n\t\treturn table;\n\t}\n\n\t//UPDATE METHODS\n\n\tpublic void startExperiment()\n\t{\n\t\ttheThread = new ExperimentThread(guiProp, cons, prop);\n\t\trunning = true;\n\t\ttheThread.start();\n\t}\n\n\tpublic synchronized void experimentDone()\n\t{\n\t\trunning = false;\n\t\ttheThread = null;\n\t\tfinished = true;\n\t\tthis.table.repaint();\n\t}\n\n\t// note: presently, this is never actually called\n\t// (in case of errors, these are stored as the results of the experiment and things end normally)\n\tpublic synchronized void experimentFailed()\n\t{\n\t\trunning = false;\n\t\ttheThread = null;\n\t\tfinished = true;\n\t\ttable.repaint();\n\t}\n\n\tpublic synchronized void experimentInterrupted()\n\t{\n\t\trunning = false;\n\t\ttheThread = null;\n\t\tfinished = true;\n\t\ttable.repaint();\n\t}\n\n\tpublic synchronized void setResult(Values mfValues, Values pfValues, Result res)\n\t{\n\t\tresults.setResult(mfValues, pfValues, res.getResult());\n\t}\n\n\tpublic synchronized void setMultipleErrors(Values mfValues, Values pfValues, Exception e)\n\t{\n\t\tresults.setMultipleErrors(mfValues, pfValues, e);\n\t}\n\n\tpublic void stop()\n\t{\n\t\tif (running && theThread != null) {\n\t\t\tif (useSimulation)\n\t\t\t\tguiProp.getPrism().getSimulator().stopSampling();\n\t\t\ttheThread.interrupt();\n\t\t}\n\t}\n\n\t//tidy up ResultsCollection when it has been removed (to tidy up graphs)\n\tpublic void clear()\n\t{\n\t}\n\n\tclass ExperimentThread extends GUIComputationThread\n\t{\n\t\tprivate UndefinedConstants undefinedConstants;\n\t\tprivate PropertiesFile propertiesFile;\n\n\t\tpublic ExperimentThread(GUIMultiProperties guiProp, UndefinedConstants undefinedConstants, PropertiesFile propertiesFile)\n\t\t{\n\t\t\tsuper(guiProp);\n\t\t\tthis.undefinedConstants = undefinedConstants;\n\t\t\tthis.propertiesFile = propertiesFile;\n\t\t}\n\n\t\tpublic void run()\n\t\t{\n\t\t\tint i, k;\n\t\t\tint propertyIndex = propertiesFile.getNumProperties() - 1;\n\t\t\tProperty propertyToCheck = propertiesFile.getPropertyObject(propertyIndex);\n\t\t\tSimulationInformation info = null;\n\t\t\tboolean reuseInfo = false, reuseInfoAsked = false;\n\n\t\t\tdefinedMFConstants = null;\n\t\t\tdefinedPFConstants = null;\n\t\t\tres = null;\n\n\t\t\ttry {\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t\t{\n\t\t\t\t\tpublic void run()\n\t\t\t\t\t{\n\t\t\t\t\t\tguiProp.startProgress();\n\t\t\t\t\t\tguiProp.setTaskBarText(\"Running experiment...\");\n\t\t\t\t\t\tguiProp.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, guiProp));\n\t\t\t\t\t\tguiProp.notifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.EXPERIMENT_START));\n\t\t\t\t\t}\n\t\t\t\t});\n\n\t\t\t\t// are we in exact mode?\n\t\t\t\tboolean exact = prism.getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\t\t\t\t// for simulation, don't use exact mode...\n\t\t\t\texact &= !useSimulation;\n\n\t\t\t\tfor (i = 0; i < undefinedConstants.getNumModelIterations(); i++) {\n\n\t\t\t\t\t// set values for ModulesFile constants\n\t\t\t\t\ttry {\n\t\t\t\t\t\tdefinedMFConstants = undefinedConstants.getMFConstantValues();\n\t\t\t\t\t\tprism.setPRISMModelConstants(definedMFConstants, exact);\n\t\t\t\t\t} catch (Exception e) {\n\t\t\t\t\t\t// in case of error, report it (in log only), store as result, and go on to the next model\n\t\t\t\t\t\terrorLog(e);\n\t\t\t\t\t\tsetMultipleErrors(definedMFConstants, null, e);\n\t\t\t\t\t\tundefinedConstants.iterateModel();\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t} catch (StackOverflowError e) {\n\t\t\t\t\t\t// in case of stack overflow, report it (in log only),\n\t\t\t\t\t\t// store as PrismException in result, and go on to the next model\n\t\t\t\t\t\terrorLog(e.toString() + \"\\n\" + StackTraceHelper.asString(e, STACK_TRACE_LIMIT));\n\t\t\t\t\t\tsetMultipleErrors(definedMFConstants, null, new PrismException(\"Stack overflow\"));\n\t\t\t\t\t\tundefinedConstants.iterateModel();\n\t\t\t\t\t\tcontinue;\n\t\t\t\t\t}\n\n\t\t\t\t\t// collect information for simulation if required\n\t\t\t\t\tif (useSimulation && !reuseInfo) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tinfo = null;\n\t\t\t\t\t\t\tinfo = GUISimulationPicker.defineSimulationWithDialog(guiProp.getGUI(), propertyToCheck.getExpression(), prism.getPRISMModel(), \"(\"\n\t\t\t\t\t\t\t\t\t+ definedMFConstants + \")\");\n\t\t\t\t\t\t} catch (Exception e) {\n\t\t\t\t\t\t\t// in case of error, report it (in log only), store as result, and go on to the next model\n\t\t\t\t\t\t\terrorLog(e);\n\t\t\t\t\t\t\tsetMultipleErrors(definedMFConstants, null, e);\n\t\t\t\t\t\t\tundefinedConstants.iterateModel();\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\n\t\t\t\t\t\t// if info is null, the user clicked cancel\n\t\t\t\t\t\tif (info == null)\n\t\t\t\t\t\t\tbreak;\n\n\t\t\t\t\t\t// if there are multiple models, offer the chance to reuse simulation info\n\t\t\t\t\t\tif (undefinedConstants.getNumModelIterations() > 1 && !reuseInfoAsked) {\n\t\t\t\t\t\t\treuseInfoAsked = true;\n\t\t\t\t\t\t\tint q = guiProp.questionYesNo(\"Do you want to reuse the same simulation\\n\"\n\t\t\t\t\t\t\t\t\t+ \"parameters for the remaining models in this experiment?\\n\" + \"If not you will be prompted for new values for each one.\");\n\t\t\t\t\t\t\tif (q == 0)\n\t\t\t\t\t\t\t\treuseInfo = true;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\n\t\t\t\t\t// for simulation where \"simultaneous property checking\" is enabled...\n\t\t\t\t\tif (useSimulation && prism.getSettings().getBoolean(PrismSettings.SIMULATOR_SIMULTANEOUS)\n\t\t\t\t\t\t\t&& undefinedConstants.getNumPropertyIterations() > 1) {\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t// convert initial Values -> State\n\t\t\t\t\t\t\t// (remember: null means use default or pick randomly)\n\t\t\t\t\t\t\tparser.State initialState;\n\t\t\t\t\t\t\tif (info.getInitialState() == null) {\n\t\t\t\t\t\t\t\tinitialState = null;\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tinitialState = new parser.State(info.getInitialState(), prism.getPRISMModel());\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// do simulation\n\t\t\t\t\t\t\tprism.modelCheckSimulatorExperiment(propertiesFile, undefinedConstants, results, propertyToCheck.getExpression(), initialState,\n\t\t\t\t\t\t\t\t\tinfo.getMaxPathLength(), info.createSimulationMethod());\n\t\t\t\t\t\t\t// update progress meter\n\t\t\t\t\t\t\t// (all properties simulated simultaneously so can't get more accurate feedback at the moment anyway)\n\t\t\t\t\t\t\ttable.progressChanged();\n\t\t\t\t\t\t} catch (Exception e) {\n\t\t\t\t\t\t\t// in case of error, report it (in log only), store as result, and go on to the next model\n\t\t\t\t\t\t\terrorLog(e);\n\t\t\t\t\t\t\tsetMultipleErrors(definedMFConstants, null, e);\n\t\t\t\t\t\t\tundefinedConstants.iterateModel();\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t} catch (StackOverflowError e) {\n\t\t\t\t\t\t\t// in case of stack overflow, report it (in log only),\n\t\t\t\t\t\t\t// store as PrismException in result, and go on to the next model\n\t\t\t\t\t\t\terrorLog(e.toString() + \"\\n\" + StackTraceHelper.asString(e, STACK_TRACE_LIMIT));\n\t\t\t\t\t\t\tsetMultipleErrors(definedMFConstants, null, new PrismException(\"Stack overflow\"));\n\t\t\t\t\t\t\tundefinedConstants.iterateModel();\n\t\t\t\t\t\t\tcontinue;\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// iterate through as many properties as necessary\n\t\t\t\t\t\tfor (k = 0; k < undefinedConstants.getNumPropertyIterations(); k++) {\n\t\t\t\t\t\t\t// interrupt if requested\n\t\t\t\t\t\t\tif (interrupted())\n\t\t\t\t\t\t\t\tthrow new InterruptedException();\n\n\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\t// Set values for PropertiesFile constants\n\t\t\t\t\t\t\t\tif (propertiesFile != null) {\n\t\t\t\t\t\t\t\t\tdefinedPFConstants = undefinedConstants.getPFConstantValues();\n\t\t\t\t\t\t\t\t\tpropertiesFile.setSomeUndefinedConstants(definedPFConstants, exact);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t// Normal model checking\n\t\t\t\t\t\t\t\tif (!useSimulation) {\n\t\t\t\t\t\t\t\t\tres = prism.modelCheck(propertiesFile, propertyToCheck);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t// Approximate (simulation-based) model checking\n\t\t\t\t\t\t\t\telse {\n\t\t\t\t\t\t\t\t\t// convert initial Values -> State\n\t\t\t\t\t\t\t\t\t// (remember: null means use default or pick randomly)\n\t\t\t\t\t\t\t\t\tparser.State initialState;\n\t\t\t\t\t\t\t\t\tif (info.getInitialState() == null) {\n\t\t\t\t\t\t\t\t\t\tinitialState = null;\n\t\t\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\t\t\tinitialState = new parser.State(info.getInitialState(), prism.getPRISMModel());\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t\t// do simulation\n\t\t\t\t\t\t\t\t\tres = prism.modelCheckSimulator(propertiesFile, propertyToCheck.getExpression(), definedPFConstants, initialState,\n\t\t\t\t\t\t\t\t\t\t\tinfo.getMaxPathLength(), info.createSimulationMethod());\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t} catch (Exception e) {\n\t\t\t\t\t\t\t\t// in case of error, report it (in log only), store exception as the result and proceed\n\t\t\t\t\t\t\t\terrorLog(e);\n\t\t\t\t\t\t\t\tres = new Result(e);\n\t\t\t\t\t\t\t} catch (StackOverflowError e) {\n\t\t\t\t\t\t\t\t// in case of stack overflow, report it (in log only),\n\t\t\t\t\t\t\t\t// store as PrismException in result, and proceed\n\t\t\t\t\t\t\t\terrorLog(e.toString() + \"\\n\" + StackTraceHelper.asString(e, STACK_TRACE_LIMIT));\n\t\t\t\t\t\t\t\tres = new Result(new PrismException(\"Stack overflow\"));\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t// store result of model checking\n\t\t\t\t\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tpublic void run()\n\t\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t\tGUIExperiment.this.setResult(definedMFConstants, definedPFConstants, res);\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\n\t\t\t\t\t\t\ttable.progressChanged();\n\n\t\t\t\t\t\t\t// iterate to next property\n\t\t\t\t\t\t\tundefinedConstants.iterateProperty();\n\t\t\t\t\t\t\tThread.yield();\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// iterate to next model\n\t\t\t\t\tundefinedConstants.iterateModel();\n\t\t\t\t\tThread.yield();\n\t\t\t\t}\n\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t\t{\n\t\t\t\t\tpublic void run()\n\t\t\t\t\t{\n\t\t\t\t\t\tguiProp.stopProgress();\n\t\t\t\t\t\tguiProp.setTaskBarText(\"Running experiment... done.\");\n\t\t\t\t\t\tguiProp.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, guiProp));\n\t\t\t\t\t\tguiProp.notifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.EXPERIMENT_END));\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\texperimentDone();\n\n\t\t\t\tif (results.containsErrors())\n\t\t\t\t\terrorDialog(\"One or more errors occured during this experiment.\\nSelect \\\"View results\\\" or check the log for more information\");\n\t\t\t} catch (InterruptedException e) {\n\t\t\t\ttry {\n\t\t\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t\t\t{\n\t\t\t\t\t\tpublic void run()\n\t\t\t\t\t\t{\n\n\t\t\t\t\t\t\tguiProp.stopProgress();\n\t\t\t\t\t\t\tguiProp.setTaskBarText(\"Running experiment... interrupted.\");\n\t\t\t\t\t\t\tguiProp.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, guiProp));\n\t\t\t\t\t\t\tguiProp.notifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.EXPERIMENT_END));\n\n\t\t\t\t\t\t}\n\t\t\t\t\t});\n\t\t\t\t}\n\t\t\t\t// catch and ignore possible exceptions from invokeAndWait call\n\t\t\t\tcatch (InterruptedException e2) {\n\t\t\t\t} catch (java.lang.reflect.InvocationTargetException e2) {\n\t\t\t\t}\n\t\t\t\texperimentInterrupted();\n\t\t\t}\n\t\t\t// catch and ignore possible exception from invokeAndWait calls\n\t\t\tcatch (java.lang.reflect.InvocationTargetException e) {\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIExperimentImported.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.util.Vector;\n\nimport parser.Values;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport prism.DefinedConstant;\nimport prism.Result;\nimport prism.ResultsCollection;\nimport prism.UndefinedConstants;\n\n/**\n * A class the represents imported experiment results.\n * Since the results are already present, methods that run/control an experiment do nothing.\n */\npublic class GUIExperimentImported extends GUIExperiment\n{\n\t/**\n\t * Create an experiment from a result collection.\n\t * As the results are already complete, the experiment is finished and serves as a mockup.\n\t */\n\tpublic GUIExperimentImported(GUIExperimentTable table, GUIMultiProperties guiProp, Property property, ResultsCollection results)\n\t{\n\t\tsuper(table, guiProp, asPropertiesFile(property), new UndefinedConstants(property, results), false, results);\n\t\texperimentDone();\n\t}\n\n\tprotected static PropertiesFile asPropertiesFile(Property property)\n\t{\n\t\tPropertiesFile properties = new PropertiesFile(null);\n\t\tproperties.addProperty(property);\n\t\treturn properties;\n\t}\n\n\t@Override\n\tpublic int getTotalIterations()\n\t{\n\t\t// For imported results, the last iteration is the number of total iterations.\n\t\treturn results.getCurrentIteration();\n\t}\n\n\t@SuppressWarnings(\"rawtypes\")\n\t@Override\n\tpublic Vector<DefinedConstant> getRangingConstants()\n\t{\n\t\treturn results.getRangingConstants();\n\t}\n\n\t@Override\n\tpublic void startExperiment()\n\t{\n\t\t// Do nothing since experiment is already done.\n\t}\n\n\t@Override\n\tpublic synchronized void setResult(Values mfValues, Values pfValues, Result res)\n\t{\n\t\t// Do nothing since experiment is already done.\n\t}\n\n\t@Override\n\tpublic void stop()\n\t{\n\t\t// Do nothing since experiment is already done.\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIExperimentPicker.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel5\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Component class=\"javax.swing.JLabel\" name=\"jLabel1\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Please define the following constants:\"/>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n        </Component>\n        <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"1.0\" weightY=\"1.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Component class=\"javax.swing.JCheckBox\" name=\"createGraphCheck\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Create Graph\"/>\n          </Properties>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"5\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n        </Component>\n        <Component class=\"javax.swing.JCheckBox\" name=\"useSimulationCheck\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Use Simulation\"/>\n          </Properties>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n        </Component>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel6\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n        <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n      </Layout>\n      <SubComponents>\n        <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n          </Events>\n        </Component>\n        <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n          </Events>\n        </Component>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIExperimentPicker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\nimport prism.*;\nimport parser.type.*;\nimport userinterface.*;\n\npublic class GUIExperimentPicker extends javax.swing.JDialog\n{\n\tpublic static final int NO_VALUES = 0;\n\tpublic static final int VALUES_DONE = 1;\n\tpublic static final int CANCELLED = 2;\n\tpublic static final int VALUES_DONE_SHOW_GRAPH = 3;\n\tpublic static final int VALUES_DONE_SHOW_GRAPH_AND_SIMULATE = 4;\n\tpublic static final int VALUES_DONE_SIMULATE = 5;\n\t\n\tstatic ArrayList remember;\n\t\n\tstatic boolean lastGraph = true;\n\tstatic boolean lastSimulation = false;\n\t    \n\tprivate boolean cancelled = true;\n\t\n\tprivate ConstantPickerList propTable;\n\tprivate ConstantPickerList modelTable;\n\t\n\tprivate boolean areModel, areProp;\n\t\n\tprivate Action okAction;\n\tprivate Action cancelAction;\n\t\n\tprivate javax.swing.JButton okayButton;\n\t\n\tprivate UndefinedConstants undef;\n\t\n\tprivate GUIPrism gui;\n\t\n\tstatic\n\t{\n\t\tremember = new ArrayList();\n\t}\n\t\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tjavax.swing.JCheckBox createGraphCheck;\n\tjavax.swing.JPanel topPanel;\n\tjavax.swing.JCheckBox useSimulationCheck;\n\t// End of variables declaration//GEN-END:variables\n\t\n\t/** Creates new form GUIConstantsPicker */\n\tpublic GUIExperimentPicker(GUIPrism parent, UndefinedConstants undef, boolean areModel, boolean areProp, boolean offerGraph, boolean offerSimulation)\n\t{\n\t\tsuper(parent, \"Define Constants\", true);\n\t\tthis.areModel = areModel;\n\t\tthis.areProp  = areProp;\n\t\tthis.undef = undef;\n\t\tthis.gui = parent;\n\t\t\n\t\t//setup tables\n\t\tpropTable = new ConstantPickerList();\n\t\tmodelTable = new ConstantPickerList();\n\t\t\n\t\t//initialise\n\t\tinitComponents();\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\t\tif (offerGraph)\n\t\t{\n\t\t\tcreateGraphCheck.setEnabled(true);\n\t\t\tcreateGraphCheck.setSelected(lastGraph);\n\t\t} else\n\t\t{\n\t\t\tcreateGraphCheck.setEnabled(false);\n\t\t\tcreateGraphCheck.setSelected(false);\n\t\t}\n\n\t\tif(offerSimulation)\n\t\t{\n\t\t\tuseSimulationCheck.setEnabled(true);\n\t\t\tuseSimulationCheck.setSelected(lastSimulation);\n\t\t}\n\t\telse\n\t\t{\n\t\t\tuseSimulationCheck.setEnabled(false);\n\t\t\tuseSimulationCheck.setSelected(false);\n\t\t}\n\n\n\t\t\n\t\tinitTables(areModel, areProp);\n\t\tinitValues(undef);\n\t\t\n\t\t//setResizable(false);\n\t\t\n\t\tpack();\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t}\n\t\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\tprivate void initComponents()//GEN-BEGIN:initComponents\n\t{\n\t\tjavax.swing.JButton cancelButton;\n\t\tjava.awt.GridBagConstraints gridBagConstraints;\n\t\tjavax.swing.JLabel jLabel1;\n\t\tjavax.swing.JPanel jPanel1;\n\t\tjavax.swing.JPanel jPanel2;\n\t\tjavax.swing.JPanel jPanel3;\n\t\tjavax.swing.JPanel jPanel4;\n\t\tjavax.swing.JPanel jPanel5;\n\t\tjavax.swing.JPanel jPanel6;\n\t\t\n\t\tjPanel1 = new javax.swing.JPanel();\n\t\tjPanel2 = new javax.swing.JPanel();\n\t\tjPanel3 = new javax.swing.JPanel();\n\t\tjPanel4 = new javax.swing.JPanel();\n\t\tjPanel5 = new javax.swing.JPanel();\n\t\tjLabel1 = new javax.swing.JLabel();\n\t\ttopPanel = new javax.swing.JPanel();\n\t\tcreateGraphCheck = new javax.swing.JCheckBox();\n\t\tuseSimulationCheck = new javax.swing.JCheckBox();\n\t\tjPanel6 = new javax.swing.JPanel();\n\t\tokayButton = new javax.swing.JButton();\n\t\tcancelButton = new javax.swing.JButton();\n\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel1.setLayout(new java.awt.GridBagLayout());\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel1.add(jPanel2, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel1.add(jPanel3, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 2;\n\t\tjPanel1.add(jPanel4, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 4;\n\t\tjPanel1.add(jPanel5, gridBagConstraints);\n\n\t\tjLabel1.setText(\"Please define the following constants:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(jLabel1, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 3;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 1.0;\n\t\tgridBagConstraints.weighty = 1.0;\n\t\tjPanel1.add(topPanel, gridBagConstraints);\n\n\t\tcreateGraphCheck.setText(\"Create Graph\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 5;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(createGraphCheck, gridBagConstraints);\n\n\t\tuseSimulationCheck.setText(\"Use Simulation\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 6;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(useSimulationCheck, gridBagConstraints);\n\n\t\tgetContentPane().add(jPanel1, java.awt.BorderLayout.CENTER);\n\t\t\n\t\t\n\t\tjPanel6.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tokayButton.setText(\"Okay\");\n\t\tokayButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tokayButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel6.add(okayButton);\n\n\t\tcancelButton.setText(\"Cancel\");\n\t\tcancelButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tcancelButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel6.add(cancelButton);\n\n\t\tgetContentPane().add(jPanel6, java.awt.BorderLayout.SOUTH);\n\n\t\tpack();\n\t}//GEN-END:initComponents\n\t\n\tprivate void initTables(boolean areModel, boolean areProp)\n\t{\n\t\tif(areModel && areProp)\n\t\t{\n\t\t\ttopPanel.setLayout(new BoxLayout(topPanel, BoxLayout.Y_AXIS));\n\t\t\tJPanel topTopPanel = new JPanel();\n\t\t\ttopTopPanel.setBorder(new TitledBorder(\"Model Constants\"));\n\t\t\ttopTopPanel.setLayout(new BorderLayout());\n\t\t\tJScrollPane sp = new JScrollPane();\n\t\t\tsp.setViewportView(modelTable);\n\t\t\ttopTopPanel.add(sp);\n\t\t\ttopTopPanel.add(new ConstantHeader(), BorderLayout.NORTH);\n\t\t\t\n\t\t\tJPanel bottomTopPanel = new JPanel();\n\t\t\tbottomTopPanel.setBorder(new TitledBorder(\"Property Constants\"));\n\t\t\tbottomTopPanel.setLayout(new BorderLayout());\n\t\t\tJScrollPane sp2 = new JScrollPane();\n\t\t\t\n\t\t\tsp2.setViewportView(propTable);\n\t\t\tbottomTopPanel.add(sp2);\n\t\t\tbottomTopPanel.add(new ConstantHeader(), BorderLayout.NORTH);\n\t\t\ttopPanel.add(topTopPanel);\n\t\t\ttopPanel.add(bottomTopPanel);\n\t\t}\n\t\telse if(areModel)\n\t\t{\n\t\t\ttopPanel.setBorder(new TitledBorder(\"Model Constants\"));\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\tJScrollPane sp = new JScrollPane();\n\t\t\tsp.setViewportView(modelTable);\n\t\t\ttopPanel.add(sp);\n\t\t\ttopPanel.add(new ConstantHeader(), BorderLayout.NORTH);\n\t\t}\n\t\telse if(areProp)\n\t\t{\n\t\t\ttopPanel.setBorder(new TitledBorder(\"Property Constants\"));\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\tJScrollPane sp = new JScrollPane();\n\t\t\t\n\t\t\tsp.setViewportView(propTable);\n\t\t\ttopPanel.add(sp);\n\t\t\ttopPanel.add(new ConstantHeader(), BorderLayout.NORTH);\n\t\t}\n\t\t\n\t\ttopPanel.setPreferredSize(new Dimension(500,300));\n\t}\n\t\n\tprivate void initValues(UndefinedConstants undef)\n\t{\n\t\tfor(int i = 0; i < undef.getMFNumUndefined(); i++)\n\t\t{\n\t\t\tConstantLine line = new ConstantLine(undef.getMFUndefinedName(i), undef.getMFUndefinedType(i));\n\t\t\tmodelTable.addConstant(line);\n\t\t}\n\t\tfor(int i = 0; i < undef.getPFNumUndefined(); i++)\n\t\t{\n\t\t\tConstantLine line = new ConstantLine(undef.getPFUndefinedName(i), undef.getPFUndefinedType(i));\n\t\t\tpropTable.addConstant(line);\n\t\t}\n\t\t\n\t\t// go through list of remembered values and see if we can use them\n\t\tfor(int i = 0; i < remember.size(); i++)\n\t\t{\n\t\t\tRememberance r = (Rememberance)remember.get(i);\n\t\t\tfor(int j = 0; j < propTable.getNumConstants(); j++)\n\t\t\t{\n\t\t\t\tConstantLine cl = propTable.getConstantLine(j);\n\t\t\t\tif(cl.getName().equals(r.varName) && (cl.getType() == r.type))\n\t\t\t\t{\n\t\t\t\t\tcl.setSingleValue(r.singleValue);\n\t\t\t\t\tcl.setStartValue(r.start);\n\t\t\t\t\tcl.setEndValue(r.end);\n\t\t\t\t\tcl.setStepValue(r.step);\n\t\t\t\t\tcl.setIsRange(r.isRange);\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor(int j = 0; j < modelTable.getNumConstants(); j++)\n\t\t\t{\n\t\t\t\tConstantLine cl = modelTable.getConstantLine(j);\n\t\t\t\tif(cl.getName().equals(r.varName) && (cl.getType() == r.type))\n\t\t\t\t{\n\t\t\t\t\tcl.setSingleValue(r.singleValue);\n\t\t\t\t\tcl.setStartValue(r.start);\n\t\t\t\t\tcl.setEndValue(r.end);\n\t\t\t\t\tcl.setStepValue(r.step);\n\t\t\t\t\tcl.setIsRange(r.isRange);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\t/** Call this static method to construct a new GUIConstantsPicker to define undef. */\n\tpublic static int defineConstantsWithDialog(GUIPrism parent, UndefinedConstants undef, boolean offerGraph, boolean offerSimulation)\n\t{\n\t\tboolean areModel = undef.getMFNumUndefined() > 0;\n\t\tboolean areProp  = undef.getPFNumUndefined() > 0;\n\t\tif(areModel || areProp)\n\t\t{\n\t\t\treturn new GUIExperimentPicker(parent, undef, areModel, areProp, offerGraph, offerSimulation).defineValues();\n\t\t}\n\t\telse return NO_VALUES;\n\t}\n\t\n\tpublic int defineValues()\n\t{\n\t\tshow();\n\t\tif(cancelled)\n\t\t\treturn CANCELLED;\n\t\telse\n\t\t\tif(createGraphCheck.isSelected())\n\t\t\t\tif(useSimulationCheck.isSelected())\n\t\t\t\t\treturn VALUES_DONE_SHOW_GRAPH_AND_SIMULATE;\n\t\t\t\telse\n\t\t\t\t\treturn VALUES_DONE_SHOW_GRAPH;\n\t\t\telse\n\t\t\t\tif(useSimulationCheck.isSelected())\n\t\t\t\t\treturn VALUES_DONE_SIMULATE;\n\t\t\t\telse \n\t\t\t\t\treturn VALUES_DONE;\n\t}\n\t\n\tpublic void rememberValues()\n\t{\n\t\tint i, j;\n\t\tConstantLine cl;\n\t\tRememberance r, rNew;\n\t\t\n\t\tfor(i = 0; i < propTable.getNumConstants(); i++)\n\t\t{\n\t\t\tcl = propTable.getConstantLine(i);\n\t\t\t// store info about this constant\n\t\t\trNew = new GUIExperimentPicker.Rememberance();\n\t\t\trNew.varName = cl.getName();\n\t\t\trNew.type = cl.getType();\n\t\t\trNew.isRange = cl.isRange();\n\t\t\trNew.singleValue = cl.getSingleValue();\n\t\t\trNew.end = cl.getEndValue();\n\t\t\trNew.start = cl.getStartValue();\n\t\t\trNew.step = cl.getStepValue();\n\t\t\t\n\t\t\t// see if we got this constant remembered already\n\t\t\tfor (j = 0; j < remember.size(); j++)\n\t\t\t{\n\t\t\t\tr = (Rememberance)remember.get(j);\n\t\t\t\t// if so, replace it\n\t\t\t\tif (cl.getName().equals(r.varName) && (cl.getType() == r.type))\n\t\t\t\t{\n\t\t\t\t\tremember.set(j, rNew);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// if not, add it\n\t\t\tif (j == remember.size()) remember.add(rNew);\n\t\t}\n\t\tfor(i = 0; i < modelTable.getNumConstants(); i++)\n\t\t{\n\t\t\tcl = modelTable.getConstantLine(i);\n\t\t\t// store info about this constant\n\t\t\trNew = new GUIExperimentPicker.Rememberance();\n\t\t\trNew.varName = cl.getName();\n\t\t\trNew.type = cl.getType();\n\t\t\trNew.isRange = cl.isRange();\n\t\t\trNew.singleValue = cl.getSingleValue();\n\t\t\trNew.end = cl.getEndValue();\n\t\t\trNew.start = cl.getStartValue();\n\t\t\trNew.step = cl.getStepValue();\n\t\t\t// see if we got this constant remembered already\n\t\t\tfor (j = 0; j < remember.size(); j++)\n\t\t\t{\n\t\t\t\tr = (Rememberance)remember.get(j);\n\t\t\t\t// if so, replace it\n\t\t\t\tif (cl.getName().equals(r.varName) && (cl.getType() == r.type))\n\t\t\t\t{\n\t\t\t\t\tremember.set(j, rNew);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\t// if not, add it\n\t\t\tif (j == remember.size()) remember.add(rNew);\n\t\t}\n\t}\n\t\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\t\t\tint i, n;\n\t\t\tConstantLine c;\n\t\t\t\n\t\t\ttry\n\t\t\t{\n\t\t\t\t// passing info to UndefinedConstants object\n\t\t\t\tn = modelTable.getNumConstants();\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t{\n\t\t\t\t\tc = modelTable.getConstantLine(i);\n\t\t\t\t\tc.checkValid();\n\t\t\t\t\tif(c.isRange())\n\t\t\t\t\t{\n\t\t\t\t\t\tundef.defineConstant(c.getName(), c.getStartValue(), c.getEndValue(), c.getStepValue());\n\t\t\t\t\t}\n\t\t\t\t\telse\n\t\t\t\t\t{\n\t\t\t\t\t\tundef.defineConstant(c.getName(), c.getSingleValue());\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tn = propTable.getNumConstants();\n\t\t\t\tfor (i = 0; i < n; i++)\n\t\t\t\t{\n\t\t\t\t\tc = propTable.getConstantLine(i);\n\t\t\t\t\tc.checkValid();\n\t\t\t\t\tif(c.isRange())\n\t\t\t\t\t{\n\t\t\t\t\t\tundef.defineConstant(c.getName(), c.getStartValue(), c.getEndValue(), c.getStepValue());\n\t\t\t\t\t}\n\t\t\t\t\telse\n\t\t\t\t\t{\n\t\t\t\t\t\tundef.defineConstant(c.getName(), c.getSingleValue());\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tundef.checkAllDefined();\n\t\t\t\tundef.initialiseIterators();\n\t\t\t\t\n\t\t\t\tcancelled = false;\n\t\t\t\trememberValues();\n\t\t\t\tlastGraph = this.createGraphCheck.isSelected();\n\t\t\t\tlastSimulation = this.useSimulationCheck.isSelected();\n\t\t\t\tdispose();\n\t\t\t}\n\t\t\tcatch(PrismException e)\n\t\t\t{\n\t\t\t\tgui.errorDialog(e.getMessage());\n\t\t\t}\n\t}//GEN-LAST:event_okayButtonActionPerformed\n\t\t\n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\t\t\tdispose();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n\t\t\n\t\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t\t{\n\t\t\tsetVisible(false);\n\t\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\t\t\n\t\t// remembered values for a single constant\n\t\t\n\t\tstatic class Rememberance\n\t\t{\n\t\t\tString varName;\n\t\t\tparser.type.Type type;\n\t\t\tboolean isRange;\n\t\t\tString singleValue;\n\t\t\tString start;\n\t\t\tString end;\n\t\t\tString step;\n\t\t\tpublic String toString()\n\t\t\t{ return varName+\"(\"+type.getTypeString()+\") : \"+isRange+\",\"+singleValue; }\n\t\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIExperimentTable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.util.*; \nimport java.awt.*;\nimport javax.swing.*;\nimport javax.swing.table.*;\n\nimport parser.ast.*;\nimport prism.*;\n\npublic class GUIExperimentTable extends JTable\n{\n\tprivate static final long serialVersionUID = 1L;\n\t\n\tprivate ExperimentTableModel expModel;\n\tprivate GUIMultiProperties guiProps;\n\t\n\t/** Creates a new instance of GUIExperimentPanel */\n\tpublic GUIExperimentTable(GUIMultiProperties guiProps)\n\t{\n\t\tsuper();\n\t\tthis.guiProps = guiProps;\n\t\tinitComponents();\n\t\tTableColumn col = getColumnModel().getColumn(2);\n\t\tcol.setCellRenderer(new ProgressBarRenderer());\n\t}\n\t\n\t/** Override set font to update row heights at same time */\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\tsetRowHeight(getFontMetrics(font).getHeight() + 4);\n\t}\n\n\t//UPDATE METHODS\n\t\n\tpublic void deleteSelected()\n\t{\n\t\twhile(getSelectedRowCount() > 0)\n\t\t{\n\t\t\tint row = this.getSelectedRow();\n\t\t\tremoveExperiment(row);\n\t\t}\n\t}\n\t\n\t/**\n\t * @param propFile  contains exactly 1 property\n\t */\n\tpublic int newExperiment(PropertiesFile propFile, UndefinedConstants cons, boolean useSimulation)\n\t{\n\t\tGUIExperiment ge = new GUIExperiment(this, guiProps, propFile, cons, useSimulation); \n\t\treturn expModel.addExperiment(ge);\n\t}\n\n\t/**\n\t * Import the results of an experiment into the table.\n\t */\n\tpublic int importExperiment(Property property, ResultsCollection results)\n\t{\n\t\tGUIExperiment ge = new GUIExperimentImported(this, guiProps, property, results); \n\t\treturn expModel.addExperiment(ge);\n\t}\n\n\tpublic void removeExperiment(int i)\n\t{\n\t\texpModel.removeExperiment(i);\n\t}\n\t\n\tpublic void startExperiment(int i)\n\t{\n\t\texpModel.getExperiment(i).startExperiment();\n\t}\n\t\t\n\tpublic void progressChanged()\n\t{\n\t\trepaint();\n\t}\n\t\n\tpublic void stop()\n\t{\n\t\texpModel.stop();\n\t}\n\t\n\t//ACCESS METHODS\n\t\n\tpublic int getNumExperiments()\n\t{\n\t\treturn expModel.getNumExperiments();\n\t}\n\t\n\tpublic GUIExperiment getExperiment(int i)\n\t{\n\t\treturn expModel.getExperiment(i);\n\t}\n\t\n\tprivate void initComponents()\n\t{\n\t\texpModel = new ExperimentTableModel();\n\t\tsetModel(expModel);\n\t}\n\n\tclass ExperimentTableModel extends AbstractTableModel\n\t{\n\t\tprivate static final long serialVersionUID = 1L;\n\t\t\n\t\tArrayList<GUIExperiment> experiments;\n\t\t\n\t\tpublic ExperimentTableModel()\n\t\t{\n\t\t\texperiments = new ArrayList<GUIExperiment>();\n\t\t}\n\t\t\n\t\tpublic String getColumnName(int index)\n\t\t{\n\t\t\tswitch(index)\n\t\t\t{\n\t\t\t\tcase 0: return \"Property\";\n\t\t\t\tcase 1: return \"Defined Constants\";\n\t\t\t\tcase 2: return \"Progress\";\n\t\t\t\tcase 3: return \"Status\";\n\t\t\t\tcase 4: return \"Method\";\n\t\t\t\tdefault: return \"\";\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic int getColumnCount()\n\t\t{\n\t\t\treturn 5;\n\t\t}\n\t\t\n\t\tpublic int getRowCount()\n\t\t{\n\t\t\treturn experiments.size();\n\t\t}\n\t\t\n\t\tpublic Object getValueAt(int rowIndex, int columnIndex)\n\t\t{\n\t\t\tGUIExperiment ge = getExperiment(rowIndex);\n\t\t\tswitch(columnIndex)\n\t\t\t{\n\t\t\t\tcase 0: return ge.getExpressionString();\n\t\t\t\tcase 1: return ge.getDefinedConstantsString();\n\t\t\t\tcase 2:\n\t\t\t\t\t{\n\t\t\t\t\tJProgressBar b = new JProgressBar();\n\t\t\t\t\t// default case\n\t\t\t\t\tif (ge.getTotalIterations() > 0) \n\t\t\t\t\t{\n\t\t\t\t\t\tb.setMaximum(ge.getTotalIterations());\n\t\t\t\t\t\tb.setValue(ge.getCurrentIterations());\n\t\t\t\t\t\tb.setStringPainted(true);\n\t\t\t\t\t\tb.setBackground(Color.white);\n\t\t\t\t\t\tint percent = (int)((double)ge.getCurrentIterations()/(double)ge.getTotalIterations()*100.0);\n\t\t\t\t\t\tb.setString(\"\"+ge.getCurrentIterations()+\"/\"+ge.getTotalIterations()+\" (\"+percent+\"%)\");\n\t\t\t\t\t}\n\t\t\t\t\t\t// special case where there are 0 iterations\n\t\t\t\t\telse \n\t\t\t\t\t{\n\t\t\t\t\t\tb.setMaximum(1);\n\t\t\t\t\t\tb.setValue(1);\n\t\t\t\t\t\tb.setStringPainted(true);\n\t\t\t\t\t\tb.setBackground(Color.white);\n\t\t\t\t\t\tb.setString(\"0/0 (100%)\");\n\t\t\t\t\t}\n\t\t\t\t\treturn b;\n\t\t\t\t}\n\t\t\t\tcase 3:\n\t\t\t\t\t{\n\t\t\t\t\tif (!ge.isFinished()) return \"Running\";\n\t\t\t\t\telse return (ge.getCurrentIterations() < ge.getTotalIterations()) ? \"Stopped\" : \"Done\";\n\t\t\t\t}\n\t\t\t\tcase 4:\n\t\t\t\t\t{\n\t\t\t\t\tif(ge.isUseSimulation()) return \"Simulation\";\n\t\t\t\t\telse return \"Verification\";\n\t\t\t\t}\n\t\t\t\tdefault: return \"\";\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic GUIExperiment getExperiment(int i)\n\t\t{\n\t\t\treturn experiments.get(i);\n\t\t}\n\t\t\n\t\tpublic int getNumExperiments()\n\t\t{\n\t\t\treturn experiments.size();\n\t\t}\n\t\t\n\t\tpublic int addExperiment(GUIExperiment e)\n\t\t{\n\t\t\texperiments.add(e);\n\t\t\tint i = experiments.size()-1;\n\t\t\tfireTableRowsInserted(i, i);\n\t\t\tscrollRectToVisible(getCellRect(i, 0, true));\n\t\t\treturn experiments.indexOf(e);\n\t\t}\n\t\t\n\t\tpublic void removeExperiment(int i)\n\t\t{\n\t\t\tGUIExperiment ge = getExperiment(i);\n\t\t\tge.clear();\n\t\t\texperiments.remove(i);\n\t\t\tfireTableRowsDeleted(i,i);\n\t\t}\n\t\t\n\t\tpublic void stop()\n\t\t{\n\t\t\tfor(int i = 0; i < getNumExperiments(); i++)\n\t\t\t{\n\t\t\t\tgetExperiment(i).stop();\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic Class getColumnClass(int i)\n\t\t{\n\t\t\tswitch(i)\n\t\t\t{\n\t\t\t\tcase 0: \n\t\t\t\tcase 1: return String.class;\n\t\t\t\tcase 2: return JProgressBar.class;\n\t\t\t\tcase 3: return String.class;\n\t\t\t\tdefault: return Object.class;\n\t\t\t}\n\t\t}\n\t}\n\n\tclass ProgressBarRenderer implements TableCellRenderer\n\t{\n\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t\t{\n\t\t\tif(value instanceof JProgressBar)\n\t\t\t{\n\t\t\t\tJProgressBar b = new JProgressBar();\n\t\t\t\tif(isSelected)\n\t\t\t\t{\n\t\t\t\t\tb.setBackground(getSelectionBackground());\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\tb.setBackground(getBackground());\n\t\t\t\t}\n\t\t\t\treturn (JProgressBar)value;\n\t\t\t}\n\t\t\telse return new JPanel();\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIGraphHandler.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.awt.BorderLayout;\nimport java.awt.Color;\nimport java.awt.Graphics;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.KeyEvent;\nimport java.awt.event.MouseEvent;\nimport java.awt.event.MouseListener;\nimport java.io.IOException;\nimport java.util.ArrayList;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.Action;\nimport javax.swing.JFileChooser;\nimport javax.swing.JFrame;\nimport javax.swing.JMenu;\nimport javax.swing.JPanel;\nimport javax.swing.JPopupMenu;\nimport javax.swing.JTabbedPane;\nimport javax.swing.filechooser.FileFilter;\nimport javax.swing.filechooser.FileNameExtensionFilter;\n\nimport prism.PrismException;\nimport userinterface.GUIPlugin;\nimport userinterface.GUIPrism;\nimport userinterface.graph.GUIImageExportDialog;\nimport userinterface.graph.Graph;\nimport userinterface.graph.GraphException;\nimport userinterface.graph.GraphOptions;\n\n@SuppressWarnings(\"serial\")\npublic class GUIGraphHandler extends JPanel implements MouseListener\n{\n\tprivate boolean canDelete;\n\n\tprivate JTabbedPane theTabs;\n\tprivate JPopupMenu backMenu, graphMenu;\n\n\tprivate java.util.List<Graph> models;\n\tprivate java.util.List<GraphOptions> options;\n\n\tprivate GUIPlugin plug;\n\n\tprivate Action graphOptions, zoomIn, zoomOut, zoomDefault;\n\n\tprivate Action printGraph, deleteGraph;\n\tprivate Action exportImageJPG, exportImagePNG, exportImageEPS, exportXML, exportMatlab;\n\tprivate Action importXML;\n\n\tprivate JMenu zoomMenu, exportMenu, importMenu;\n\n\tprivate FileFilter pngFilter, jpgFilter, epsFilter, graFilter, matlabFilter;\n\n\tpublic GUIGraphHandler(JFrame parent, GUIPlugin plug, boolean canDelete)\n\t{\n\t\tthis.plug = plug;\n\t\tthis.canDelete = canDelete;\n\n\t\tthis.graphMenu = new JPopupMenu();\n\t\tthis.backMenu = new JPopupMenu();\n\n\t\tinitComponents();\n\n\t\tpngFilter = new FileNameExtensionFilter(\"PNG files (*.png)\", \"png\");\n\t\tjpgFilter = new FileNameExtensionFilter(\"JPEG files (*.jpg, *.jpeg)\", \"jpg\", \"jpeg\"); \n\t\tepsFilter = new FileNameExtensionFilter(\"Encapsulated PostScript files (*.eps)\", \"eps\");\n\t\tgraFilter = new FileNameExtensionFilter(\"PRISM graph files (*.gra, *.xml)\", \"gra\", \"xml\");\n\t\tmatlabFilter = new FileNameExtensionFilter(\"Matlab files (*.m)\", \"m\");\n\n\t\tmodels = new ArrayList<Graph>();\n\t\toptions = new ArrayList<GraphOptions>();\n\t}\n\n\tprivate void initComponents()\n\t{\n\t\ttheTabs = new JTabbedPane();\n\t\ttheTabs.addMouseListener(this);\n\n\t\tsetLayout(new BorderLayout());\n\t\tadd(theTabs, BorderLayout.CENTER);\n\t\t\n\t\tgraphOptions = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGraphOptions graphOptions = options.get(theTabs.getSelectedIndex());\n\t\t\t\tgraphOptions.setVisible(true);\n\t\t\t}\n\t\t};\n\n\t\tgraphOptions.putValue(Action.NAME, \"Graph options\");\n\t\tgraphOptions.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_G));\n\t\tgraphOptions.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallOptions.png\"));\n\t\tgraphOptions.putValue(Action.LONG_DESCRIPTION, \"Displays the options dialog for the graph.\");\n\n\t\tzoomIn = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGraph mgm = models.get(theTabs.getSelectedIndex());\n\t\t\t\tmgm.zoomInBoth(-1, -1);\n\t\t\t}\n\t\t};\n\n\t\tzoomIn.putValue(Action.NAME, \"In\");\n\t\tzoomIn.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_I));\n\t\tzoomIn.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPlayerFwd.png\"));\n\t\tzoomIn.putValue(Action.LONG_DESCRIPTION, \"Zoom in on the graph.\");\n\n\t\tzoomOut = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGraph mgm = models.get(theTabs.getSelectedIndex());\n\t\t\t\tmgm.zoomOutBoth(-1, -1);\n\t\t\t}\n\t\t};\n\n\t\tzoomOut.putValue(Action.NAME, \"Out\");\n\t\tzoomOut.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_O));\n\t\tzoomOut.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPlayerRew.png\"));\n\t\tzoomOut.putValue(Action.LONG_DESCRIPTION, \"Zoom out of the graph.\");\n\n\t\tzoomDefault = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGraph mgm = models.get(theTabs.getSelectedIndex());\n\t\t\t\tmgm.restoreAutoBounds();\n\t\t\t}\n\t\t};\n\n\t\tzoomDefault.putValue(Action.NAME, \"Default\");\n\t\tzoomDefault.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_D));\n\t\tzoomDefault.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPlayerStart.png\"));\n\t\tzoomDefault.putValue(Action.LONG_DESCRIPTION, \"Set the default zoom for the graph.\");\n\n\t\timportXML = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (plug.showOpenFileDialog(graFilter) != JFileChooser.APPROVE_OPTION)\n\t\t\t\t\treturn;\n\t\t\t\ttry {\n\t\t\t\t\tGraph mgm = Graph.load(plug.getChooserFile());\n\t\t\t\t\taddGraph(mgm);\n\t\t\t\t} catch (GraphException ex) {\n\t\t\t\t\tplug.error(\"Could not import PRISM graph file:\\n\" + ex.getMessage());\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\timportXML.putValue(Action.NAME, \"PRISM graph (*.gra)\");\n\t\timportXML.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_I));\n\t\timportXML.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileGraph.png\"));\n\t\timportXML.putValue(Action.LONG_DESCRIPTION, \"Imports a saved PRISM graph from a file.\");\n\n\t\texportXML = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (plug.showSaveFileDialog(graFilter) != JFileChooser.APPROVE_OPTION)\n\t\t\t\t\treturn;\n\t\t\t\tGraph mgm = models.get(theTabs.getSelectedIndex());\n\t\t\t\ttry {\n\t\t\t\t\tmgm.save(plug.getChooserFile());\n\t\t\t\t} catch (PrismException ex) {\n\t\t\t\t\tplug.error(\"Could not export PRISM graph file:\\n\" + ex.getMessage());\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\texportXML.putValue(Action.NAME, \"PRISM graph (*.gra)\");\n\t\texportXML.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_X));\n\t\texportXML.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileGraph.png\"));\n\t\texportXML.putValue(Action.LONG_DESCRIPTION, \"Export graph as a PRISM graph file.\");\n\n\t\texportImageJPG = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGUIImageExportDialog imageDialog = new GUIImageExportDialog(plug.getGUI(), getModel(theTabs.getSelectedIndex()), GUIImageExportDialog.JPEG);\n\n\t\t\t\tsaveImage(imageDialog);\n\t\t\t}\n\t\t};\n\t\texportImageJPG.putValue(Action.NAME, \"JPEG Interchange Format (*.jpg, *.jpeg)\");\n\t\texportImageJPG.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_J));\n\t\texportImageJPG.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileImage.png\"));\n\t\texportImageJPG.putValue(Action.LONG_DESCRIPTION, \"Export graph as a JPEG file.\");\n\n\t\texportImagePNG = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGUIImageExportDialog imageDialog = new GUIImageExportDialog(plug.getGUI(), getModel(theTabs.getSelectedIndex()), GUIImageExportDialog.PNG);\n\n\t\t\t\tsaveImage(imageDialog);\n\t\t\t}\n\t\t};\n\t\texportImagePNG.putValue(Action.NAME, \"Portable Network Graphics (*.png)\");\n\t\texportImagePNG.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_P));\n\t\texportImagePNG.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileImage.png\"));\n\t\texportImagePNG.putValue(Action.LONG_DESCRIPTION, \"Export graph as a Portable Network Graphics file.\");\n\n\t\texportImageEPS = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGUIImageExportDialog imageDialog = new GUIImageExportDialog(plug.getGUI(), getModel(theTabs.getSelectedIndex()), GUIImageExportDialog.EPS);\n\n\t\t\t\tsaveImage(imageDialog);\n\t\t\t}\n\t\t};\n\t\texportImageEPS.putValue(Action.NAME, \"Encapsulated PostScript (*.eps)\");\n\t\texportImageEPS.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_E));\n\t\texportImageEPS.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFilePdf.png\"));\n\t\texportImageEPS.putValue(Action.LONG_DESCRIPTION, \"Export graph as an Encapsulated PostScript file.\");\n\n\t\texportMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tif (plug.showSaveFileDialog(matlabFilter) != JFileChooser.APPROVE_OPTION)\n\t\t\t\t\treturn;\n\t\t\t\tGraph mgm = models.get(theTabs.getSelectedIndex());\n\n\t\t\t\ttry {\n\t\t\t\t\tmgm.exportToMatlab(plug.getChooserFile());\n\t\t\t\t} catch (IOException ex) {\n\t\t\t\t\tplug.error(\"Could not export Matlab file:\\n\" + ex.getMessage());\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\texportMatlab.putValue(Action.NAME, \"Matlab file (*.m)\");\n\t\texportMatlab.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_M));\n\t\texportMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileMatlab.png\"));\n\t\texportMatlab.putValue(Action.LONG_DESCRIPTION, \"Export graph as a Matlab file.\");\n\n\t\tprintGraph = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGraph graph = models.get(theTabs.getSelectedIndex());\n\n\t\t\t\tif (!graph.getDisplaySettings().getBackgroundColor().equals(Color.white)) {\n\t\t\t\t\tif (plug.questionYesNo(\"Your graph has a coloured background, this background will show up on the \\n\"\n\t\t\t\t\t\t\t+ \"printout. Would you like to make the current background colour white?\") == 0) {\n\t\t\t\t\t\tgraph.getDisplaySettings().setBackgroundColor(Color.white);\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tgraph.createChartPrintJob();\n\t\t\t}\n\t\t};\n\t\tprintGraph.putValue(Action.NAME, \"Print graph\");\n\t\tprintGraph.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_P));\n\t\tprintGraph.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPrint.png\"));\n\t\tprintGraph.putValue(Action.LONG_DESCRIPTION, \"Print the graph to a printer or file\");\n\n\t\tdeleteGraph = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGraph graph = models.get(theTabs.getSelectedIndex());\n\n\t\t\t\tmodels.remove(theTabs.getSelectedIndex());\n\t\t\t\toptions.remove(theTabs.getSelectedIndex());\n\t\t\t\ttheTabs.remove(graph);\n\t\t\t}\n\t\t};\n\t\tdeleteGraph.putValue(Action.NAME, \"Delete graph\");\n\t\tdeleteGraph.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_D));\n\t\tdeleteGraph.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDelete.png\"));\n\t\tdeleteGraph.putValue(Action.LONG_DESCRIPTION, \"Deletes the graph.\");\n\n\t\tzoomMenu = new JMenu(\"Zoom\");\n\t\tzoomMenu.setMnemonic('Z');\n\t\tzoomMenu.setIcon(GUIPrism.getIconFromImage(\"smallView.png\"));\n\t\tzoomMenu.add(zoomIn);\n\t\tzoomMenu.add(zoomOut);\n\t\tzoomMenu.add(zoomDefault);\n\n\t\texportMenu = new JMenu(\"Export graph\");\n\t\texportMenu.setMnemonic('E');\n\t\texportMenu.setIcon(GUIPrism.getIconFromImage(\"smallExport.png\"));\n\t\texportMenu.add(exportXML);\n\t\texportMenu.add(exportImagePNG);\n\t\texportMenu.add(exportImageEPS);\n\t\texportMenu.add(exportImageJPG);\n\n\t\texportMenu.add(exportMatlab);\n\n\t\timportMenu = new JMenu(\"Import graph\");\n\t\timportMenu.setMnemonic('I');\n\t\timportMenu.setIcon(GUIPrism.getIconFromImage(\"smallImport.png\"));\n\t\timportMenu.add(importXML);\n\n\t\tgraphMenu.add(graphOptions);\n\t\tgraphMenu.add(zoomMenu);\n\t\tgraphMenu.addSeparator();\n\t\tgraphMenu.add(printGraph);\n\t\tgraphMenu.add(deleteGraph);\n\t\tgraphMenu.addSeparator();\n\t\tgraphMenu.add(exportMenu);\n\t\tgraphMenu.add(importMenu);\n\n\t\t/* Tab context menu */\n\t\tbackMenu.add(importXML);\n\t}\n\n\tpublic void saveImage(GUIImageExportDialog imageDialog)\n\t{\n\t\tif (!imageDialog.isCancelled()) {\n\t\t\tGraph graph = getModel(theTabs.getSelectedIndex());\n\n\t\t\t/* If background is not white, and it will show up, then lets warn everyone. */\n\t\t\tif (!graph.getDisplaySettings().getBackgroundColor().equals(Color.white)\n\t\t\t\t\t&& (imageDialog.getImageType() != GUIImageExportDialog.PNG || !imageDialog.getAlpha())) {\n\t\t\t\tif (plug.questionYesNo(\"Your graph has a coloured background, this background will show up on the \\n\"\n\t\t\t\t\t\t+ \"exported image. Would you like to make the current background colour white?\") == 0) {\n\t\t\t\t\tgraph.getDisplaySettings().setBackgroundColor(Color.white);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (imageDialog.getImageType() == GUIImageExportDialog.JPEG) {\n\t\t\t\tif (plug.showSaveFileDialog(jpgFilter) != JFileChooser.APPROVE_OPTION)\n\t\t\t\t\treturn;\n\t\t\t\ttry {\n\t\t\t\t\tgraph.exportToJPEG(plug.getChooserFile(), imageDialog.getExportWidth(), imageDialog.getExportHeight());\n\t\t\t\t} catch (GraphException ex) {\n\t\t\t\t\tplug.error(\"Could not export JPEG file:\\n\" + ex.getMessage());\n\t\t\t\t} catch (IOException ex) {\n\t\t\t\t\tplug.error(\"Could not export JPEG file:\\n\" + ex.getMessage());\n\t\t\t\t}\n\t\t\t} else if (imageDialog.getImageType() == GUIImageExportDialog.PNG) {\n\t\t\t\tif (plug.showSaveFileDialog(pngFilter) != JFileChooser.APPROVE_OPTION)\n\t\t\t\t\treturn;\n\t\t\t\ttry {\n\t\t\t\t\tgraph.exportToPNG(plug.getChooserFile(), imageDialog.getExportWidth(), imageDialog.getExportHeight(), imageDialog.getAlpha());\n\t\t\t\t} catch (GraphException ex) {\n\t\t\t\t\tplug.error(\"Could not export PNG file:\\n\" + ex.getMessage());\n\t\t\t\t} catch (IOException ex) {\n\t\t\t\t\tplug.error(\"Could not export PNG file:\\n\" + ex.getMessage());\n\t\t\t\t}\n\t\t\t} else if (imageDialog.getImageType() == GUIImageExportDialog.EPS) {\n\t\t\t\tif (plug.showSaveFileDialog(epsFilter) != JFileChooser.APPROVE_OPTION)\n\t\t\t\t\treturn;\n\t\t\t\ttry {\n\t\t\t\t\tgraph.exportToEPS(plug.getChooserFile(), imageDialog.getExportWidth(), imageDialog.getExportHeight());\n\t\t\t\t} catch (GraphException ex) {\n\t\t\t\t\tplug.error(\"Could not export EPS file:\\n\" + ex.getMessage());\n\t\t\t\t} catch (IOException ex) {\n\t\t\t\t\tplug.error(\"Could not export EPS file:\\n\" + ex.getMessage());\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic Action getPrintGraph()\n\t{\n\t\treturn printGraph;\n\t}\n\n\tpublic Action getDeleteGraph()\n\t{\n\t\tif (canDelete)\n\t\t\treturn deleteGraph;\n\t\treturn null;\n\t}\n\n\tpublic int addGraph(Graph m)\n\t{\n\t\tString name = \"\";\n\n\t\tboolean nameNew;\n\t\tint counter = 1;\n\n\t\twhile (true) {\n\t\t\tname = \"Graph \" + (counter);\n\t\t\tnameNew = true;\n\n\t\t\tfor (int i = 0; i < theTabs.getComponentCount(); i++) {\n\t\t\t\tif (theTabs.getTitleAt(i).equals(name))\n\t\t\t\t\tnameNew = false;\n\t\t\t}\n\n\t\t\tif (nameNew)\n\t\t\t\treturn addGraph(m, name);\n\n\t\t\tcounter++;\n\t\t}\n\t}\n\n\tpublic int addGraph(Graph m, String tabName)\n\t{\n\t\t// add the model to the list of models\n\t\tmodels.add(m);\n\n\t\t// make the graph appear as a tab\n\t\ttheTabs.add(m);\n\t\toptions.add(new GraphOptions(plug, m, plug.getGUI(), \"Options for graph \" + tabName));\n\n\t\t// anything that happens to the graph should propagate\n\t\tm.addMouseListener(this);\n\n\t\t// get the index of this model in the model list\n\t\tint index = models.indexOf(m);\n\n\t\t// increase the graph count and title the tab\n\t\ttheTabs.setTitleAt(index, tabName);\n\n\t\t// make this new tab the default selection\n\t\ttheTabs.setSelectedIndex(theTabs.indexOfComponent(m));\n\n\t\t// return the index of the component\n\t\treturn index;\n\t}\n\n\tpublic void jumpToGraph(Graph m)\n\t{\n\t\tfor (int i = 0; i < models.size(); i++) {\n\t\t\tif (m == models.get(i)) {\n\t\t\t\ttheTabs.setSelectedComponent(m);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic Graph getModel(int i)\n\t{\n\t\treturn models.get(i);\n\t}\n\n\tpublic Graph getModel(String tabHeader)\n\t{\n\t\tfor (int i = 0; i < theTabs.getComponentCount(); i++) {\n\t\t\tif (theTabs.getTitleAt(i).equals(tabHeader)) {\n\t\t\t\treturn getModel(i);\n\t\t\t}\n\t\t}\n\t\treturn null;\n\t}\n\n\tpublic int getNumModels()\n\t{\n\t\treturn models.size();\n\t}\n\n\tpublic String getGraphName(int i)\n\t{\n\t\treturn theTabs.getTitleAt(i);\n\t}\n\n\t// User right clicked on a tab\n\tpublic void mousePressed(MouseEvent e)\n\t{\n\t\tif (e.isPopupTrigger()) {\n\t\t\tpopUpTriggered(e);\n\t\t}\n\t}\n\n\tpublic void mouseClicked(MouseEvent e)\n\t{\n\t\t// Zoom out on double click\n\t\tif (e.getClickCount() == 2) {\n\t\t\tif (e.getSource() instanceof Graph) {\n\t\t\t\t((Graph) e.getSource()).restoreAutoBounds();\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void mouseReleased(MouseEvent e)\n\t{\n\t\tif (e.isPopupTrigger()) {\n\t\t\tpopUpTriggered(e);\n\t\t}\n\t}\n\n\tprivate void popUpTriggered(MouseEvent e)\n\t{\n\t\tif (e.getSource() == theTabs)//just show the background popup\n\t\t{\n\t\t\tint index = theTabs.indexAtLocation(e.getX(), e.getY());\n\t\t\tif (index != -1) {\n\t\t\t\tgraphOptions.setEnabled(true);\n\t\t\t\tzoomMenu.setEnabled(true);\n\n\t\t\t\texportMenu.setEnabled(true);\n\t\t\t\timportMenu.setEnabled(true);\n\n\t\t\t\tprintGraph.setEnabled(true);\n\t\t\t\tdeleteGraph.setEnabled(true);\n\n\t\t\t\ttheTabs.setSelectedIndex(index);\n\n\t\t\t\tthis.graphMenu.show(theTabs, e.getX(), e.getY());\n\t\t\t} else {\n\t\t\t\tgraphOptions.setEnabled(false);\n\t\t\t\tzoomMenu.setEnabled(false);\n\n\t\t\t\texportMenu.setEnabled(false);\n\t\t\t\timportMenu.setEnabled(true);\n\n\t\t\t\tprintGraph.setEnabled(false);\n\t\t\t\tdeleteGraph.setEnabled(false);\n\n\t\t\t\tthis.graphMenu.show(theTabs, e.getX(), e.getY());\n\t\t\t}\n\t\t\treturn;\n\t\t}\n\n\t\tfor (int i = 0; i < models.size(); i++) {\n\t\t\tif (e.getSource() == models.get(i)) {\n\t\t\t\tgraphOptions.setEnabled(true);\n\t\t\t\tzoomMenu.setEnabled(true);\n\n\t\t\t\texportMenu.setEnabled(true);\n\t\t\t\timportMenu.setEnabled(true);\n\n\t\t\t\tprintGraph.setEnabled(true);\n\t\t\t\tdeleteGraph.setEnabled(true);\n\n\t\t\t\ttheTabs.setSelectedIndex(i);\n\t\t\t\tthis.graphMenu.show(models.get(i), e.getX(), e.getY());\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void paintComponent(Graphics g)\n\t{\n\t\tsuper.paintComponent(g);\n\t\tg.clearRect(0, 0, this.getWidth(), this.getHeight());\n\t}\n\n\t// don't implement these for tabs\n\t//public void mouseClicked(MouseEvent e) { }\n\tpublic void mouseEntered(MouseEvent e)\n\t{\n\t}\n\n\tpublic void mouseExited(MouseEvent e)\n\t{\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIGraphPicker.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <NonVisualComponents>\n    <Component class=\"javax.swing.ButtonGroup\" name=\"buttonGroup1\">\n    </Component>\n  </NonVisualComponents>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,76,0,0,1,-7\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JTabbedPane\" name=\"jTabbedPane1\">\n      <Properties>\n        <Property name=\"tabPlacement\" type=\"int\" value=\"2\"/>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                <TitledBorder title=\"Line Graph\"/>\n              </Border>\n            </Property>\n            <Property name=\"focusable\" type=\"boolean\" value=\"false\"/>\n            <Property name=\"enabled\" type=\"boolean\" value=\"false\"/>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"\"/>\n                <Property name=\"tabIcon\" type=\"javax.swing.Icon\" editor=\"org.openide.explorer.propertysheet.editors.IconEditor\">\n                  <Image iconType=\"3\" name=\"/images/lineGraph.gif\"/>\n                </Property>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel5\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JLabel\" name=\"topComboLabel\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Select x axis constant:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel6\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JComboBox\" name=\"selectAxisConstantCombo\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[100, 24]\"/>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"selectAxisConstantComboActionPerformed\"/>\n                  </Events>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel7\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JLabel\" name=\"middleLabel\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Define other constants:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"constantTablePanel\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"4\" gridWidth=\"3\" gridHeight=\"2\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"1.0\" weightY=\"1.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel9\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"6\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel10\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JLabel\" name=\"jLabel3\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Add Series to:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"7\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JRadioButton\" name=\"newGraphRadio\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"New Graph\"/>\n                    <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n                      <ComponentRef name=\"buttonGroup1\"/>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"newGraphRadioActionPerformed\"/>\n                  </Events>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"7\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JRadioButton\" name=\"existingGraphRadio\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Existing Graph\"/>\n                    <Property name=\"buttonGroup\" type=\"javax.swing.ButtonGroup\" editor=\"org.netbeans.modules.form.RADComponent$ButtonGroupPropertyEditor\">\n                      <ComponentRef name=\"buttonGroup1\"/>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"existingGraphRadioActionPerformed\"/>\n                  </Events>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"8\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel11\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"4\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JComboBox\" name=\"existingGraphCombo\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"5\" gridY=\"8\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel12\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"9\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JLabel\" name=\"seriesNameLabel\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Series name:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"10\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JTextField\" name=\"seriesNameField\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"10\" gridWidth=\"3\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n              </SubComponents>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"South\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n                <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n              </Layout>\n              <SubComponents>\n                <Component class=\"javax.swing.JButton\" name=\"lineOkayButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"lineOkayButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"lineCancelButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"lineCancelButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                <TitledBorder title=\"Bar Graph\"/>\n              </Border>\n            </Property>\n            <Property name=\"enabled\" type=\"boolean\" value=\"false\"/>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"\"/>\n                <Property name=\"tabIcon\" type=\"javax.swing.Icon\" editor=\"org.openide.explorer.propertysheet.editors.IconEditor\">\n                  <Image iconType=\"3\" name=\"/images/barGraph.gif\"/>\n                </Property>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIGraphPicker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.util.Vector;\nimport java.util.ArrayList;\nimport javax.swing.*;\nimport java.awt.*;\nimport org.jfree.data.xy.*;\n\nimport userinterface.*;\nimport userinterface.graph.Graph;\nimport userinterface.graph.GraphResultListener;\nimport prism.*;\nimport parser.*;\nimport parser.type.TypeInterval;\n\npublic class GUIGraphPicker extends javax.swing.JDialog\n{\n\tprivate GUIPrism gui;\n\tprivate GUIPlugin plugin;\n\n\tprivate GUIExperiment experiment;\n\tprivate GUIGraphHandler graphHandler;\n\tprivate ResultsCollection resultsCollection;\n\n\tprivate GraphConstantPickerList pickerList;\n\n\tprivate String ranger;\n\tprivate DefinedConstant rangingConstant;\n\n\tprivate Values otherValues;\n\tprivate Vector<DefinedConstant> multiSeries;\n\n\tprivate userinterface.graph.Graph graphModel;\n\tprivate boolean graphCancelled;\n\n\tprivate static final int MAX_NUM_SERIES_BEFORE_QUERY = 11;\n\n\t/** Creates new form GUIGraphPicker \n\t * \n\t * @param parent The parent.\n\t * @param plugin The GUIPlugin (GUIMultiProperties)\n\t * @param experiment The experiment for which to plot a graph.\n\t * @param graphHandler The graph handler in which to display the graph.\n\t * @param resultsKnown If true, simply plot existing results (experiment has been done). \n\t * If false, attach listeners to the results such that plot is made when results become available.\n\t */\n\tpublic GUIGraphPicker(GUIPrism parent, GUIPlugin plugin, GUIExperiment experiment, GUIGraphHandler graphHandler, boolean resultsKnown)\n\t{\n\t\tsuper(parent, true);\n\t\tsetTitle(\"New Graph Series\");\n\n\t\tthis.gui = parent;\n\t\tthis.plugin = plugin;\n\n\t\tthis.experiment = experiment;\n\t\tthis.graphHandler = graphHandler;\n\t\tthis.resultsCollection = experiment.getResults();\n\n\t\t// graphCancelled will be set explicitly to false when the OK button is pressed\n\t\t// (this means if the user closes the dialog, this counts as a cancel)\n\t\tthis.graphCancelled = true;\n\n\t\tthis.multiSeries = new Vector<DefinedConstant>();\n\n\t\tinitComponents();\n\t\tsetResizable(false);\n\n\t\tinit();\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t\tgetRootPane().setDefaultButton(lineOkayButton);\n\n\t\t/* Wait untill OK or Cancel is pressed. */\n\t\tsetVisible(true);\n\n\t\t/* If OK was pressed. */\n\t\tif (!graphCancelled) {\n\t\t\t/* Collect series keys. */\n\t\t\tVector<Graph.SeriesKey> seriesKeys = new Vector<Graph.SeriesKey>();\n\n\t\t\t/* Collect series Values */\n\t\t\tArrayList<Values> seriesValues = new ArrayList<Values>();\n\n\t\t\t/* Add single constant values to each serie */\n\t\t\tseriesValues.add(otherValues);\n\n\t\t\tfor (int i = 0; i < multiSeries.size(); i++) {\n\t\t\t\tArrayList<Values> temp = (ArrayList<Values>) seriesValues.clone();\n\t\t\t\tseriesValues.clear();\n\n\t\t\t\t// For each of the possible value in the range\n\t\t\t\tfor (int j = 0; j < multiSeries.get(i).getNumSteps(); j++) {\n\t\t\t\t\t// Clone the list\n\t\t\t\t\tArrayList copy = (ArrayList<Values>) temp.clone();\n\n\t\t\t\t\t// For each element in the list\n\t\t\t\t\tfor (int k = 0; k < copy.size(); k++) {\n\t\t\t\t\t\tValues v = new Values();\n\t\t\t\t\t\tValues cp = (Values) copy.get(k);\n\t\t\t\t\t\tv.addValues(cp);\n\t\t\t\t\t\tv.addValue(multiSeries.get(i).getName(), multiSeries.get(i).getValue(j));\n\t\t\t\t\t\tseriesValues.add(v);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t/* Do all series settings. */\n\t\t\tfor (int serie = 0; serie < seriesValues.size(); serie++) //each combination of series\n\t\t\t{\n\t\t\t\tValues values = seriesValues.get(serie);\n\t\t\t\tString seriesName = (seriesValues.size() > 1) ? values.toString() : seriesNameField.getText();\n\t\t\t\t// For properties that return an interval, we add a pair of series\n\t\t\t\t// (the pair is stored as a linked list)\n\t\t\t\tif (experiment.getExpressionType() instanceof TypeInterval) {\n\t\t\t\t\tGraph.SeriesKey key = graphModel.addSeries(seriesName + \" (min)\");\n\t\t\t\t\tkey.next = graphModel.addSeries(seriesName + \" (max)\");\n\t\t\t\t\tseriesKeys.add(key);\n\t\t\t\t} else {\n\t\t\t\t\tseriesKeys.add(graphModel.addSeries(seriesName));\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t/* If there are results already, then lets render them! */\n\t\t\tif (resultsKnown && resultsCollection.getCurrentIteration() > 0) {\n\t\t\t\tfor (int series = 0; series < seriesValues.size(); series++) //each combination of series\n\t\t\t\t{\n\t\t\t\t\tValues values = seriesValues.get(series);\n\t\t\t\t\tGraph.SeriesKey seriesKey = seriesKeys.get(series);\n\n\t\t\t\t\t/** Range over x-axis. */\n\t\t\t\t\tfor (int i = 0; i < rangingConstant.getNumSteps(); i++) {\n\t\t\t\t\t\tObject value = rangingConstant.getValue(i);\n\n\t\t\t\t\t\t/** Values used in the one experiment for this series. */\n\t\t\t\t\t\tValues useThis = new Values();\n\t\t\t\t\t\tuseThis.addValues(values);\n\t\t\t\t\t\tuseThis.addValue(ranger, value);\n\n\t\t\t\t\t\t/** Get this particular result. **/\n\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\tObject result = resultsCollection.getResult(useThis);\n\n\t\t\t\t\t\t\tdouble x = 0, y = 0;\n\t\t\t\t\t\t\tboolean validX = true;\n\n\t\t\t\t\t\t\tif (value instanceof Double) {\n\t\t\t\t\t\t\t\tx = ((Double) value).doubleValue();\n\t\t\t\t\t\t\t} else if (value instanceof Integer) {\n\t\t\t\t\t\t\t\tx = ((Integer) value).intValue();\n\t\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t\tvalidX = false;\n\t\t\t\t\t\t\t}\n\n\t\t\t\t\t\t\t// Add point to graph (if of valid type)\n\t\t\t\t\t\t\tif (validX) {\n\t\t\t\t\t\t\t\tif (result instanceof Double) {\n\t\t\t\t\t\t\t\t\ty = ((Double) result).doubleValue();\n\t\t\t\t\t\t\t\t\tgraphModel.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t\t\t\t\t\t} else if (result instanceof Integer) {\n\t\t\t\t\t\t\t\t\ty = ((Integer) result).intValue();\n\t\t\t\t\t\t\t\t\tgraphModel.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t\t\t\t\t\t} else if (result instanceof Interval) {\n\t\t\t\t\t\t\t\t\tInterval interval = (Interval) result;\n\t\t\t\t\t\t\t\t\tif (interval.lower instanceof Double) {\n\t\t\t\t\t\t\t\t\t\ty = ((Double) interval.lower).doubleValue();\n\t\t\t\t\t\t\t\t\t\tgraphModel.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t\t\t\t\t\t\t\ty = ((Double) interval.upper).doubleValue();\n\t\t\t\t\t\t\t\t\t\tgraphModel.addPointToSeries(seriesKey.next, new XYDataItem(x, y));\n\t\t\t\t\t\t\t\t\t} else if (result instanceof Integer) {\n\t\t\t\t\t\t\t\t\t\ty = ((Integer) interval.lower).intValue();\n\t\t\t\t\t\t\t\t\t\tgraphModel.addPointToSeries(seriesKey, new XYDataItem(x, y));\n\t\t\t\t\t\t\t\t\t\ty = ((Integer) interval.upper).intValue();\n\t\t\t\t\t\t\t\t\t\tgraphModel.addPointToSeries(seriesKey.next, new XYDataItem(x, y));\n\t\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t} catch (PrismException pe) {\n\t\t\t\t\t\t\t// No result found. \n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else if (!resultsKnown && resultsCollection.getCurrentIteration() == 0) {\n\t\t\t\tfor (int series = 0; series < seriesValues.size(); series++) //each combination of series\n\t\t\t\t{\n\t\t\t\t\tValues values = seriesValues.get(series);\n\t\t\t\t\tGraph.SeriesKey seriesKey = seriesKeys.get(series);\n\n\t\t\t\t\tGraphResultListener listener = new GraphResultListener(graphModel, seriesKey, ranger, values);\n\t\t\t\t\tresultsCollection.addResultListener(listener);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t/** According to what is stored in 'rc', set up the table to pick the constants\n\t */\n\tprivate void init()\n\t{\n\t\t// set up \"define other constants\" table\n\t\t// create header\n\t\tGraphConstantHeader header = new GraphConstantHeader();\n\t\tconstantTablePanel.add(header, BorderLayout.NORTH);\n\t\t// create scroller\n\t\tJScrollPane scroller = new JScrollPane();\n\t\tconstantTablePanel.add(scroller, BorderLayout.CENTER);\n\t\t// create picker list\n\t\tpickerList = new GraphConstantPickerList();\n\t\tscroller.setViewportView(pickerList);\n\n\t\t// for each ranging constant in rc, add:\n\t\t// (1) a row in the picker list\n\t\t// (2) an item in the \"x axis\" drop down menu\n\t\tfor (int i = 0; i < resultsCollection.getRangingConstants().size(); i++) {\n\t\t\tDefinedConstant dc = (DefinedConstant) resultsCollection.getRangingConstants().get(i);\n\t\t\tpickerList.addConstant(new GraphConstantLine(dc, this));\n\t\t\tthis.selectAxisConstantCombo.addItem(dc.getName());\n\t\t}\n\n\t\t// select the default constant for the x axis\n\t\t// (first property if there is one, if not first model one)\n\t\tif (selectAxisConstantCombo.getItemCount() > 0) {\n\t\t\tif (resultsCollection.getNumPropertyRangingConstants() > 0)\n\t\t\t\tselectAxisConstantCombo.setSelectedIndex(resultsCollection.getNumModelRangingConstants());\n\t\t\telse\n\t\t\t\tselectAxisConstantCombo.setSelectedIndex(0);\n\t\t}\n\t\t// and disable it in the picker list\n\t\tpickerList.disableLine(0);\n\n\t\t// if there is only one ranging constant, disable controls\n\t\tif (resultsCollection.getRangingConstants().size() == 1) {\n\t\t\tselectAxisConstantCombo.setEnabled(false);\n\t\t\tpickerList.setEnabled(false);\n\t\t\theader.setEnabled(false);\n\t\t\tthis.middleLabel.setEnabled(false);\n\t\t\tthis.topComboLabel.setEnabled(false);\n\t\t}\n\n\t\t// default graph option is \"new graph\"\n\t\tthis.newGraphRadio.setSelected(true);\n\n\t\t// add existing graphs to choose from\n\t\tfor (int i = 0; i < graphHandler.getNumModels(); i++) {\n\t\t\texistingGraphCombo.addItem(graphHandler.getGraphName(i));\n\t\t}\n\t\t// default to latest one\n\t\tif (existingGraphCombo.getItemCount() > 0) {\n\t\t\texistingGraphCombo.setSelectedIndex(existingGraphCombo.getItemCount() - 1);\n\t\t}\n\t\t// if there are no graphs, disable control\n\t\telse {\n\t\t\texistingGraphCombo.setEnabled(false);\n\t\t\tthis.existingGraphRadio.setEnabled(false);\n\t\t}\n\n\t\t// create a default series name\n\t\tresetAutoSeriesName();\n\n\t\t// other enables/disables\n\t\tdoEnables();\n\n\t\tpack();\n\t}\n\n\tpublic void doEnables()\n\t{\n\t\tthis.existingGraphCombo.setEnabled(this.existingGraphRadio.isSelected());\n\t}\n\n\t// create a default series name\n\tpublic void resetAutoSeriesName()\n\t{\n\t\tDefinedConstant temp;\n\t\tObject value;\n\n\t\tif (selectAxisConstantCombo.getSelectedItem() == null) {\n\t\t\treturn;\n\t\t}\n\n\t\t// see which constant is on x axis\n\t\tranger = selectAxisConstantCombo.getSelectedItem().toString();\n\t\t// init arrays\n\t\totherValues = new Values();\n\t\tmultiSeries = new Vector<DefinedConstant>();\n\t\t// go through constants in picker list\n\t\tfor (int j = 0; j < pickerList.getNumConstants(); j++) {\n\t\t\t// get constant\n\t\t\ttemp = pickerList.getConstantLine(j).getDC();\n\t\t\t// ignore constant for x-axis\n\t\t\tif (temp.getName().equals(ranger))\n\t\t\t\tcontinue;\n\t\t\t// get value\n\t\t\tvalue = pickerList.getConstantLine(j).getSelectedValue();\n\t\t\t// if we find any constants selected \"All Series\", clear name, disable and bail out\n\t\t\tif (value instanceof String) {\n\t\t\t\tthis.seriesNameLabel.setEnabled(false);\n\t\t\t\tthis.seriesNameField.setText(\"\");\n\t\t\t\tthis.seriesNameField.setEnabled(false);\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t// we add other constants to a list\n\t\t\telse {\n\t\t\t\totherValues.addValue(temp.getName(), value);\n\t\t\t}\n\t\t}\n\t\t// use values object string for name\n\t\tif (otherValues.getNumValues() != 0) {\n\t\t\tthis.seriesNameField.setText(otherValues.toString());\n\t\t} else {\n\t\t\tthis.seriesNameField.setText(\"New Series\");\n\t\t}\n\t\tthis.seriesNameLabel.setEnabled(true);\n\t\tthis.seriesNameField.setEnabled(true);\n\t}\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\tprivate void initComponents()\n\t{\n\t\tjava.awt.GridBagConstraints gridBagConstraints;\n\n\t\tbuttonGroup1 = new javax.swing.ButtonGroup();\n\t\tjTabbedPane1 = new javax.swing.JTabbedPane();\n\t\tjPanel1 = new javax.swing.JPanel();\n\t\tjPanel3 = new javax.swing.JPanel();\n\t\tjPanel5 = new javax.swing.JPanel();\n\t\ttopComboLabel = new javax.swing.JLabel();\n\t\tjPanel6 = new javax.swing.JPanel();\n\t\tselectAxisConstantCombo = new javax.swing.JComboBox();\n\t\tjPanel7 = new javax.swing.JPanel();\n\t\tmiddleLabel = new javax.swing.JLabel();\n\t\tconstantTablePanel = new javax.swing.JPanel();\n\t\tjPanel9 = new javax.swing.JPanel();\n\t\tjPanel10 = new javax.swing.JPanel();\n\t\tjLabel3 = new javax.swing.JLabel();\n\t\tnewGraphRadio = new javax.swing.JRadioButton();\n\t\texistingGraphRadio = new javax.swing.JRadioButton();\n\t\tjPanel11 = new javax.swing.JPanel();\n\t\texistingGraphCombo = new javax.swing.JComboBox();\n\t\tjPanel12 = new javax.swing.JPanel();\n\t\tseriesNameLabel = new javax.swing.JLabel();\n\t\tseriesNameField = new javax.swing.JTextField();\n\t\tjPanel4 = new javax.swing.JPanel();\n\t\tlineOkayButton = new javax.swing.JButton();\n\t\tlineCancelButton = new javax.swing.JButton();\n\t\tjPanel2 = new javax.swing.JPanel();\n\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\n\t\tjTabbedPane1.setTabPlacement(javax.swing.JTabbedPane.LEFT);\n\t\tjPanel1.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel1.setBorder(new javax.swing.border.TitledBorder(\"Line Graph\"));\n\t\tjPanel1.setFocusable(false);\n\t\tjPanel1.setEnabled(false);\n\t\tjPanel3.setLayout(new java.awt.GridBagLayout());\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel3.add(jPanel5, gridBagConstraints);\n\n\t\ttopComboLabel.setText(\"Select x axis constant:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel3.add(topComboLabel, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel3.add(jPanel6, gridBagConstraints);\n\n\t\tselectAxisConstantCombo.setPreferredSize(new java.awt.Dimension(100, 24));\n\t\tselectAxisConstantCombo.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tselectAxisConstantComboActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tjPanel3.add(selectAxisConstantCombo, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 2;\n\t\tjPanel3.add(jPanel7, gridBagConstraints);\n\n\t\tmiddleLabel.setText(\"Define other constants:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 4;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel3.add(middleLabel, gridBagConstraints);\n\n\t\tconstantTablePanel.setLayout(new java.awt.BorderLayout());\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 4;\n\t\tgridBagConstraints.gridwidth = 3;\n\t\tgridBagConstraints.gridheight = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 1.0;\n\t\tgridBagConstraints.weighty = 1.0;\n\t\tjPanel3.add(constantTablePanel, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 6;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel3.add(jPanel9, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 6;\n\t\tjPanel3.add(jPanel10, gridBagConstraints);\n\n\t\tjLabel3.setText(\"Add Series to:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 7;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel3.add(jLabel3, gridBagConstraints);\n\n\t\tnewGraphRadio.setText(\"New Graph\");\n\t\tbuttonGroup1.add(newGraphRadio);\n\t\tnewGraphRadio.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tnewGraphRadioActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 7;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel3.add(newGraphRadio, gridBagConstraints);\n\n\t\texistingGraphRadio.setText(\"Existing Graph\");\n\t\tbuttonGroup1.add(existingGraphRadio);\n\t\texistingGraphRadio.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\texistingGraphRadioActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 8;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel3.add(existingGraphRadio, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 4;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel3.add(jPanel11, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 5;\n\t\tgridBagConstraints.gridy = 8;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel3.add(existingGraphCombo, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 9;\n\t\tjPanel3.add(jPanel12, gridBagConstraints);\n\n\t\tseriesNameLabel.setText(\"Series name:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 10;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel3.add(seriesNameLabel, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 10;\n\t\tgridBagConstraints.gridwidth = 3;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tjPanel3.add(seriesNameField, gridBagConstraints);\n\n\t\tjPanel1.add(jPanel3, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel4.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tlineOkayButton.setText(\"Okay\");\n\t\tlineOkayButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tlineOkayButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel4.add(lineOkayButton);\n\n\t\tlineCancelButton.setText(\"Cancel\");\n\t\tlineCancelButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tlineCancelButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel4.add(lineCancelButton);\n\n\t\tjPanel1.add(jPanel4, java.awt.BorderLayout.SOUTH);\n\n\t\t//jTabbedPane1.addTab(\"\", GUIPrism.getIconFromImage(\"lineGraph.png\"), jPanel1);\n\n\t\tjPanel2.setBorder(new javax.swing.border.TitledBorder(\"Bar Graph\"));\n\t\tjPanel2.setEnabled(false);\n\t\t//jTabbedPane1.addTab(\"\", GUIPrism.getIconFromImage(\"barGraph.png\"), jPanel2);\n\n\t\tgetContentPane().add(jPanel1, java.awt.BorderLayout.CENTER);\n\n\t\tpack();\n\t}\n\n\tpublic boolean isGraphCancelled()\n\t{\n\t\treturn graphCancelled;\n\t}\n\n\tprivate void lineCancelButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{\n\t\tgraphCancelled = true;\n\t\tsetVisible(false);\n\t}\n\n\tprivate void lineOkayButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{\n\t\tint numSeries = 1;\n\n\t\t// see which constant is on x axis\n\t\tranger = selectAxisConstantCombo.getSelectedItem().toString();\n\n\t\t// init arrays\n\t\totherValues = new Values();\n\t\tmultiSeries = new Vector<DefinedConstant>();\n\n\t\t// go through all constants in picker list\n\t\tfor (int j = 0; j < pickerList.getNumConstants(); j++) {\n\t\t\t// get constant\n\t\t\tDefinedConstant tmpConstant = pickerList.getConstantLine(j).getDC();\n\t\t\t// if its the constant for the x-axis, store info about the constant\n\t\t\tif (tmpConstant.getName().equals(ranger)) {\n\t\t\t\trangingConstant = tmpConstant;\n\t\t\t}\n\t\t\t// otherwise store info about the selected values\n\t\t\telse {\n\t\t\t\t// Is this constant just a value, or does it have a range?\n\t\t\t\tObject value = pickerList.getConstantLine(j).getSelectedValue();\n\t\t\t\tif (value instanceof String) {\n\t\t\t\t\t/* Yes, calculate the numSeries. */\n\t\t\t\t\tmultiSeries.add(pickerList.getConstantLine(j).getDC());\n\t\t\t\t\tnumSeries *= tmpConstant.getNumSteps();\n\t\t\t\t} else {\n\t\t\t\t\t/* No, just the one. */\n\t\t\t\t\totherValues.addValue(tmpConstant.getName(), value);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t//sort out which one to add it to\n\t\tif (rangingConstant == null)\n\t\t\treturn;\n\n\t\t// if there are a lot of series, check if this is what the user really wanted\n\t\tif (numSeries > MAX_NUM_SERIES_BEFORE_QUERY) {\n\t\t\tString[] choices = { \"Yes\", \"No\" };\n\t\t\tint choice = -1;\n\t\t\tchoice = plugin.optionPane(\"Warning: This will plot \" + numSeries + \" series.\\nAre you sure you want to continue?\", \"Question\",\n\t\t\t\t\tJOptionPane.YES_NO_OPTION, JOptionPane.QUESTION_MESSAGE, choices, choices[0]);\n\t\t\tif (choice != 0)\n\t\t\t\treturn;\n\t\t}\n\n\t\tif (newGraphRadio.isSelected()) {\n\t\t\t/* Make new graph. */\n\t\t\tgraphModel = new Graph();\n\t\t\tgraphHandler.addGraph(graphModel);\n\n\t\t\tgraphModel.getYAxisSettings().setHeading(resultsCollection.getResultName());\n\t\t\tgraphModel.getXAxisSettings().setHeading(ranger);\n\t\t} else {\n\t\t\t/* Add to an existing graph. */\n\t\t\tgraphModel = graphHandler.getModel(existingGraphCombo.getSelectedItem().toString());\n\t\t\tif (!ranger.equals(graphModel.getXAxisSettings().getHeading())) //FIXME: must do this better in future\n\t\t\t\tif (!roughExists(ranger, graphModel.getXAxisSettings().getHeading()))\n\t\t\t\t\tgraphModel.getXAxisSettings().setHeading(graphModel.getXAxisSettings().getHeading() + \", \" + ranger);\n\t\t}\n\n\t\tgraphCancelled = false;\n\t\tsetVisible(false);\n\t}\n\n\tprivate void existingGraphRadioActionPerformed(java.awt.event.ActionEvent evt)\n\t{\n\t\tdoEnables();\n\t}\n\n\tprivate void newGraphRadioActionPerformed(java.awt.event.ActionEvent evt)\n\t{\n\t\tdoEnables();\n\t}\n\n\tprivate void selectAxisConstantComboActionPerformed(java.awt.event.ActionEvent evt)\n\t{\n\t\tpickerList.disableLine(selectAxisConstantCombo.getSelectedIndex());\n\t\tresetAutoSeriesName();\n\t}\n\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}\n\n\t// Variables declaration - do not modify\n\tprivate javax.swing.ButtonGroup buttonGroup1;\n\tprivate javax.swing.JPanel constantTablePanel;\n\tprivate javax.swing.JComboBox existingGraphCombo;\n\tprivate javax.swing.JRadioButton existingGraphRadio;\n\tprivate javax.swing.JLabel jLabel3;\n\tprivate javax.swing.JPanel jPanel1;\n\tprivate javax.swing.JPanel jPanel10;\n\tprivate javax.swing.JPanel jPanel11;\n\tprivate javax.swing.JPanel jPanel12;\n\tprivate javax.swing.JPanel jPanel2;\n\tprivate javax.swing.JPanel jPanel3;\n\tprivate javax.swing.JPanel jPanel4;\n\tprivate javax.swing.JPanel jPanel5;\n\tprivate javax.swing.JPanel jPanel6;\n\tprivate javax.swing.JPanel jPanel7;\n\tprivate javax.swing.JPanel jPanel9;\n\tprivate javax.swing.JTabbedPane jTabbedPane1;\n\tprivate javax.swing.JButton lineCancelButton;\n\tprivate javax.swing.JButton lineOkayButton;\n\tprivate javax.swing.JLabel middleLabel;\n\tprivate javax.swing.JRadioButton newGraphRadio;\n\tprivate javax.swing.JComboBox selectAxisConstantCombo;\n\tprivate javax.swing.JTextField seriesNameField;\n\tprivate javax.swing.JLabel seriesNameLabel;\n\tprivate javax.swing.JLabel topComboLabel;\n\n\t// End of variables declaration\n\n\tpublic static int factorial(int i)\n\t{\n\t\tif (i < 0)\n\t\t\treturn 1;\n\t\tif (i == 0)\n\t\t\treturn 1;\n\t\telse\n\t\t\treturn i * factorial(i - 1);\n\t}\n\n\tpublic static boolean roughExists(String test, String inThis)\n\t{\n\t\tint i = inThis.indexOf(test);\n\t\tif (i == -1)\n\t\t\treturn false;\n\t\tif (!((i == 0) || (inThis.charAt(i - 1) == ' ')))\n\t\t\treturn false;\n\t\tif (!((inThis.length() == i + 1) || (inThis.charAt(i + 1) == ',')))\n\t\t\treturn false;\n\t\treturn true;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUILabel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport parser.ast.*;\nimport prism.*;\n\npublic class GUILabel\n{\n\tpublic GUIMultiProperties parent;\n\tpublic String name;\n\tpublic String label;\n\tpublic Exception parseError;\n\t\n\tpublic GUILabel(GUIMultiProperties parent, String name, String label)\n\t{\n\t\tthis.parent = parent;\n\t\tthis.name = name;\n\t\tthis.label = label;\n\t\tthis.parseError = null;\n\t}\n\t\n\tpublic void parse()\n\t{\n\t\tExpression expr = null;\n\t\tthis.parseError = null;\n\t\t// See if label definition is parseable\n\t\ttry {\n\t\t\t// Check name is a valid identifier\n\t\t\ttry { expr = parent.getPrism().parseSingleExpressionString(name); }\n\t\t\tcatch (PrismLangException e) { throw new PrismException(\"Invalid label name \\\"\"+name+\"\\\"\"); }\n\t\t\tif (expr == null || !(expr instanceof ExpressionIdent)) throw new PrismException(\"Invalid label name \\\"\"+name+\"\\\"\");\n\t\t\t// Check (non-empty) label definition is valid (single) expression\n\t\t\ttry { if (!(\"\".equals(label))) parent.getPrism().parseSingleExpressionString(label); }\n\t\t\tcatch (PrismLangException e) { throw new PrismException(\"Invalid expression \\\"\"+label+\"\\\"\"); }\n\t\t}\n\t\tcatch (PrismException e) {\n\t\t\tthis.parseError = e;\n\t\t}\n\t}\n\t\n\tpublic boolean isParseable() { return parseError==null; }\n\t\n\tpublic String toString()\n\t{\n\t\treturn \"label \\\"\"+getNameString()+\"\\\" = \"+getValueString()+\";\";\n\t}\n\t\n\tpublic String getNameString()\n\t{\n\t\treturn name;\n\t}\n\t\n\tpublic String getValueString()\n\t{\n\t\treturn label;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIMultiProperties.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t* Mateusz Ujma <mateusz.ujma@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.awt.BorderLayout;\nimport java.awt.Color;\nimport java.awt.Dimension;\nimport java.awt.Font;\nimport java.awt.GridLayout;\nimport java.awt.Rectangle;\nimport java.awt.Toolkit;\nimport java.awt.datatransfer.Clipboard;\nimport java.awt.datatransfer.DataFlavor;\nimport java.awt.datatransfer.StringSelection;\nimport java.awt.datatransfer.Transferable;\nimport java.awt.datatransfer.UnsupportedFlavorException;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.ContainerEvent;\nimport java.awt.event.ContainerListener;\nimport java.awt.event.InputEvent;\nimport java.awt.event.KeyEvent;\nimport java.awt.event.MouseEvent;\nimport java.awt.event.MouseListener;\nimport java.io.File;\nimport java.io.FileWriter;\nimport java.io.IOException;\nimport java.io.PrintWriter;\nimport java.util.ArrayList;\nimport java.util.Collections;\nimport java.util.Comparator;\nimport java.util.HashMap;\nimport java.util.List;\nimport java.util.Map;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.Action;\nimport javax.swing.JButton;\nimport javax.swing.JCheckBoxMenuItem;\nimport javax.swing.JFileChooser;\nimport javax.swing.JMenu;\nimport javax.swing.JOptionPane;\nimport javax.swing.JPanel;\nimport javax.swing.JPopupMenu;\nimport javax.swing.JScrollPane;\nimport javax.swing.JSeparator;\nimport javax.swing.JSplitPane;\nimport javax.swing.JTextArea;\nimport javax.swing.JTextField;\nimport javax.swing.JToolBar;\nimport javax.swing.KeyStroke;\nimport javax.swing.border.TitledBorder;\nimport javax.swing.event.ListSelectionEvent;\nimport javax.swing.event.ListSelectionListener;\nimport javax.swing.filechooser.FileFilter;\nimport javax.swing.filechooser.FileNameExtensionFilter;\n\nimport io.ModelExportFormat;\nimport io.ModelExportOptions;\nimport io.ModelExportTask;\nimport org.jfree.data.xy.XYDataItem;\n\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport parser.ast.Property;\nimport parser.type.Type;\nimport parser.type.TypeDouble;\nimport parser.type.TypeInt;\nimport parser.type.TypeInterval;\nimport prism.PrismException;\nimport prism.PrismSettings;\nimport prism.PrismSettingsListener;\nimport prism.ResultsExporter.ResultsExportShape;\nimport prism.TileList;\nimport prism.UndefinedConstants;\nimport strat.StrategyExportOptions;\nimport strat.StrategyExportOptions.StrategyExportType;\nimport userinterface.GUIClipboardEvent;\nimport userinterface.GUIConstantsPicker;\nimport userinterface.GUIPlugin;\nimport userinterface.GUIPrism;\nimport userinterface.GUISimulationPicker;\nimport userinterface.SimulationInformation;\nimport userinterface.graph.Graph;\nimport userinterface.graph.Graph.SeriesKey;\nimport userinterface.model.GUIModelEvent;\nimport userinterface.model.computation.ExportBuiltModelThread;\nimport userinterface.properties.computation.ExportResultsThread;\nimport userinterface.properties.computation.ExportStrategyThread;\nimport userinterface.properties.computation.ImportResultsThread;\nimport userinterface.properties.computation.LoadPropertiesThread;\nimport userinterface.properties.computation.ModelCheckThread;\nimport userinterface.properties.computation.SimulateModelCheckThread;\nimport userinterface.simulator.GUISimulator;\nimport userinterface.util.GUIComputationEvent;\nimport userinterface.util.GUIEvent;\nimport userinterface.util.GUIExitEvent;\n\n/**\n *  Properties tab of the PRISM GUI.\n */\n@SuppressWarnings(\"serial\")\npublic class GUIMultiProperties extends GUIPlugin implements MouseListener, ListSelectionListener, PrismSettingsListener, ContainerListener\n{\n\t//CONSTANTS\n\tpublic static final int CONTINUE = 0;\n\tpublic static final int CANCEL = 1;\n\n\tpublic static final int WARN_INVALID_PROPS = 1;\n\tpublic static final int NEVER_INVALID_PROPS = 2;\n\n\t// ATTRIBUTES\n\n\t// Current model (gets updated only by event listening to GUIModel)\n\tprivate ModulesFile parsedModel;\n\n\t// State\n\tprivate boolean modified;\n\tprivate boolean computing;\n\tprivate boolean verifyAfterReceiveParseNotification, experimentAfterReceiveParseNotification, simulateAfterReceiveParseNotification, exportLabelsAfterReceiveParseNotification;\n\tprivate PropertiesFile parsedProperties;\n\tprivate ArrayList<GUIProperty> propertiesToBeVerified;\n\tprivate File activeFile;\n\tprivate Values pfConstants;\n\tprivate String argsPropertiesFile;\n\tprivate ModelExportTask exportTask;\n\n\t// GUI\n\tprivate FileFilter propsFilter;\n\tprivate Map<String,FileFilter> traFilters;\n\tprivate Map<String,FileFilter> labFilters;\n\tprivate FileFilter textFilter;\n\tprivate FileFilter csvFilter;\n\tprivate FileFilter dotFilter;\n\t\n\tprivate FileFilter matlabFilter;\n\tprivate JMenu propMenu, stratMenu;\n\tprivate JPopupMenu propertiesPopup, constantsPopup, labelsPopup, experimentPopup;\n\tprivate JMenu stratSubMenu;\n\tprivate GUIExperimentTable experiments;\n\tprivate GUIGraphHandler graphHandler;\n\tprivate JScrollPane expScroller;\n\tprivate JTextField fileTextField;\n\tprivate Action newProps, openProps, saveProps, savePropsAs, insertProps, verifySelected, newProperty, editProperty;\n\tprivate Action generateStrategy, exportStrategyActions, exportStrategyActionsStates, exportStrategyInducedRestrict, exportStrategyInducedReduce, exportStrategyInducedDot;\n\tprivate Action viewStrategyActions, viewStrategyActionsStates, viewStrategyInducedRestrict, viewStrategyInducedReduce, simulateStrategy;\n\tprivate Action newConstant, removeConstant, newLabel, removeLabel;\n\tprivate Action newExperiment, deleteExperiment, stopExperiment, parametric;\n\tprivate Action viewResults, plotResults, exportResultsListText, exportResultsListCSV,\n\t\t\texportResultsMatrixText, exportResultsMatrixCSV, exportResultsDataFrameCSV, exportResultsComment, importResultsDataFrameCSV;\n\tprivate Action simulate, details, exportLabelsPlain, exportModelLabelsPlain, exportLabelsMatlab, exportModelLabelsMatlab;\n\n\t// Current properties\n\tprivate GUIPropertiesList propList;\n\tprivate GUIPropConstantList consTable;\n\tprivate GUIPropLabelList labTable;\n\n\t// Cached copies of settings\n\tprivate Font displayFontFast;\n\tprivate Color backgroundFast, warningFast;\n\n\t// The simulator\n\tprivate GUISimulator simulator;\n\n\t// CONSTRUCTORS\n\n\t/** Creates a new instance of GUIMultiProperties */\n\tpublic GUIMultiProperties(GUIPrism pr, GUISimulator simulator)\n\t{\n\t\tsuper(pr);\n\t\tthis.simulator = simulator;\n\t\tsimulator.setGUIProb(this); // link required\n\t\tinitComponents();\n\t\ta_newList();\n\t\tsetParsedModel(null);\n\t\tdoEnables();\n\t\t//options = new GUIPropertiesOptions(this);\n\t}\n\n\tpublic void takeCLArgs(String args[])\n\t{\n\t\tif (args.length > 1) {\n\t\t\targsPropertiesFile = args[1];\n\t\t}\n\t}\n\n\t//ACCESS METHODS\n\n\tpublic ModulesFile getParsedModel()\n\t{\n\t\treturn parsedModel;\n\t}\n\n\tpublic String getConstantsString()\n\t{\n\t\treturn consTable.getValidConstantsString();\n\t}\n\n\tpublic String getLabelsString()\n\t{\n\t\treturn labTable.getValidLabelsString();\n\t}\n\n\tpublic int getNumConstants()\n\t{\n\t\treturn consTable.getRowCount();\n\t}\n\n\tpublic int getNumLabels()\n\t{\n\t\treturn labTable.getRowCount();\n\t}\n\n\tpublic Font getListFont()\n\t{\n\t\treturn displayFontFast;\n\t}\n\n\tpublic Color getWarningColor()\n\t{\n\t\treturn warningFast;\n\t}\n\n\tpublic Color getSelectionColor()\n\t{\n\t\treturn backgroundFast;\n\t}\n\n\tpublic int getInvalidPropertyStrategy()\n\t{\n\t\treturn getPrism().getSettings().getInteger(PrismSettings.PROPERTIES_ADDITION_STRATEGY) + 1; //note the correction\n\t}\n\n\tpublic GUIGraphHandler getGraphHandler()\n\t{\n\t\treturn graphHandler;\n\t}\n\n\t/* UPDATE METHODS */\n\n\tpublic void repaintList()\n\t{\n\t\tpropList.repaint();\n\t}\n\n\tprotected void verifyAfterParse()\n\t{\n\t\tArrayList<GUIProperty> validGUIProperties;\n\t\tUndefinedConstants uCon;\n\n\t\tverifyAfterReceiveParseNotification = false;\n\n\t\ttry {\n\t\t\t// are we in exact mode?\n\t\t\tboolean exact = getPrism().getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\n\t\t\t// Get valid/selected properties\n\t\t\tString propertiesString = getLabelsString() + \"\\n\" + getConstantsString() + \"\\n\" + propList.getValidSelectedAndReferencedString();\n\t\t\t// Get PropertiesFile for valid/selected properties\n\t\t\tparsedProperties = getPrism().parsePropertiesString(propertiesString);\n\t\t\t// And get list of corresponding GUIProperty objects\n\t\t\tvalidGUIProperties = propList.getValidSelectedProperties();\n\t\t\t// Query user for undefined constant values (if required)\n\t\t\tint n = parsedProperties.getNumProperties();\n\t\t\tArrayList<Property> validProperties = new ArrayList<Property>(n);\n\t\t\tfor (int i = 0; i < n; i++)\n\t\t\t\tvalidProperties.add(parsedProperties.getPropertyObject(i));\n\t\t\tuCon = new UndefinedConstants(parsedModel, parsedProperties, validProperties);\n\t\t\tuCon.setExactMode(exact);\n\t\t\tif (uCon.getMFNumUndefined() + uCon.getPFNumUndefined() > 0) {\n\t\t\t\t// Use previous constant values as defaults in dialog\n\t\t\t\tValues lastModelConstants = getPrism().getUndefinedModelValues();\n\t\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(this.getGUI(), uCon, lastModelConstants, pfConstants);\n\t\t\t\tif (result != GUIConstantsPicker.VALUES_DONE)\n\t\t\t\t\treturn;\n\t\t\t}\n\t\t\t// Store model/property constants\n\t\t\tpfConstants = uCon.getPFConstantValues();\n\t\t\tgetPrism().setPRISMModelConstants(uCon.getMFConstantValues(), exact);\n\t\t\tparsedProperties.setSomeUndefinedConstants(pfConstants, exact);\n\t\t\t// Store properties to be verified\n\t\t\tpropertiesToBeVerified = validGUIProperties;\n\t\t\tfor (GUIProperty gp : propertiesToBeVerified)\n\t\t\t\tgp.setConstants(uCon.getMFConstantValues(), pfConstants);\n\t\t\t// Start model checking\n\t\t\tThread t = new ModelCheckThread(this, parsedProperties, propertiesToBeVerified);\n\t\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\t\tt.start();\n\t\t} catch (PrismException e) {\n\t\t\terror(e.getMessage());\n\t\t\treturn;\n\t\t}\n\t}\n\n\tpublic void simulateAfterParse()\n\t{\n\t\tsimulateAfterReceiveParseNotification = false;\n\t\tArrayList<GUIProperty> validGUIProperties, simulatableGUIProperties;\n\t\tArrayList<Expression> simulatableExprs;\n\t\tUndefinedConstants uCon;\n\t\ttry {\n\t\t\tparsedProperties = getPrism().parsePropertiesString(\n\t\t\t\t\tgetLabelsString() + \"\\n\" + getConstantsString() + \"\\n\" + propList.getValidSelectedAndReferencedString());\n\t\t\tvalidGUIProperties = propList.getValidSelectedProperties();\n\t\t\tif (validGUIProperties.size() == 0) {\n\t\t\t\terror(\"None of the selected properties are suitable for simulation\");\n\t\t\t\treturn;\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\terror(e.getMessage());\n\t\t\treturn;\n\t\t}\n\n\t\t// See which of the (valid) selected properties are ok for simulation\n\t\t// Also store a list of the expression themselves\n\t\tsimulatableGUIProperties = new ArrayList<GUIProperty>();\n\t\tArrayList<Property> simulatableProperties = new ArrayList<Property>();\n\t\tsimulatableExprs = new ArrayList<Expression>();\n\t\tfor (int i = 0; i < validGUIProperties.size(); i++) {\n\t\t\tGUIProperty guiP = validGUIProperties.get(i);\n\t\t\tif (getPrism().isPropertyOKForSimulation(guiP.getProperty())) {\n\t\t\t\tsimulatableGUIProperties.add(guiP);\n\t\t\t\tsimulatableProperties.add(parsedProperties.getPropertyObject(i));\n\t\t\t\tsimulatableExprs.add(guiP.getProperty());\n\t\t\t}\n\t\t}\n\t\tif (simulatableGUIProperties.size() == 0) {\n\t\t\terror(\"None of the selected properties are suitable for simulation\");\n\t\t\treturn;\n\t\t}\n\t\tif (simulatableGUIProperties.size() < validGUIProperties.size()) {\n\t\t\tint q = questionYesNo(\"Warning\", \"Warning: Some of the selected properties are not suitable for simulation. Continue?\");\n\t\t\tif (q != 0)\n\t\t\t\treturn;\n\t\t}\n\n\t\t//find out any undefined constants\n\t\ttry {\n\t\t\tuCon = new UndefinedConstants(parsedModel, parsedProperties, simulatableProperties);\n\t\t\tif (uCon.getMFNumUndefined() + uCon.getPFNumUndefined() > 0) {\n\t\t\t\t// Use previous constant values as defaults in dialog\n\t\t\t\tValues lastModelConstants = getPrism().getUndefinedModelValues();\n\t\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(this.getGUI(), uCon, lastModelConstants, pfConstants);\n\t\t\t\tif (result != GUIConstantsPicker.VALUES_DONE)\n\t\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// Store model/property constants\n\t\t\tpfConstants = uCon.getPFConstantValues();\n\t\t\t// currently, evaluate constants non-exact for simulation\n\t\t\tgetPrism().setPRISMModelConstants(uCon.getMFConstantValues(), false);\n\t\t\tparsedProperties.setSomeUndefinedConstants(pfConstants, false);\n\t\t\tfor (GUIProperty gp : simulatableGUIProperties)\n\t\t\t\tgp.setConstants(uCon.getMFConstantValues(), pfConstants);\n\n\t\t\t// Store properties to be verified\n\t\t\tpropertiesToBeVerified = validGUIProperties;\n\t\t\tfor (GUIProperty gp : propertiesToBeVerified)\n\t\t\t\tgp.setConstants(uCon.getMFConstantValues(), pfConstants);\n\n\t\t\t// Get simulation info with dialog\n\t\t\tSimulationInformation info = GUISimulationPicker.defineSimulationWithDialog(this.getGUI(), simulatableExprs, parsedModel, null);\n\n\t\t\t// If user cancelled simulation, quit \n\t\t\tif (info == null)\n\t\t\t\treturn;\n\n\t\t\tif (parsedModel != null && parsedProperties != null) {\n\t\t\t\tThread t = new SimulateModelCheckThread(this, parsedProperties, simulatableGUIProperties, pfConstants, info);\n\t\t\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\t\t\tt.start();\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\terror(e.getMessage());\n\t\t\treturn;\n\t\t}\n\t}\n\n\tpublic void experimentAfterParse()\n\t{\n\t\texperimentAfterReceiveParseNotification = false;\n\t\tGUIProperty gp = propList.getProperty(propList.getSelectedIndex());\n\t\tType type;\n\n\t\ttry {\n\t\t\t/*//get referenced named properties\n\t\t\tString namedString = \"\";\n\t\t\t//Add named properties\n\t\t\tfor (GUIProperty namedProp : this.propList.getAllNamedProperties()) {\n\t\t\t\tif (gp.getReferencedNames().contains(namedProp.getName())) {\n\t\t\t\t\tnamedString += \"\\\"\" + namedProp.getName() + \"\\\" : \" + namedProp.getPropString() + \"\\n\";\n\t\t\t\t}\n\t\t\t}*/\n\n\t\t\t// parse property to be used for experiment\n\t\t\tparsedProperties = getPrism().parsePropertiesString(\n\t\t\t\t\tgetLabelsString() + \"\\n\" + getConstantsString() + \"\\n\" + propList.getValidSelectedAndReferencedString());\n\t\t\tif (parsedProperties.getNumProperties() <= 0) {\n\t\t\t\terror(\"There are no properties selected\");\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tif (propList.getNumSelectedProperties() > 1) {\n\t\t\t\terror(\"Experiments can only be created for a single property\");\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t// check the type of the property\n\t\t\tint index = parsedProperties.getNumProperties() - 1;\n\t\t\ttype = parsedProperties.getProperty(index).getType();\n\t\t} catch (PrismException e) {\n\t\t\terror(e.getMessage());\n\t\t\treturn;\n\t\t}\n\n\t\t//get Property objects for sorting out undefined constants\n\t\tArrayList<Property> props = new ArrayList<Property>();\n\t\tfor (int i = 0; i < parsedProperties.getNumProperties(); i++) {\n\t\t\tprops.add(parsedProperties.getPropertyObject(i));\n\t\t}\n\n\t\t// sort out undefined constants\n\t\tUndefinedConstants uCon = new UndefinedConstants(parsedModel, parsedProperties, props);\n\t\tuCon.setExactMode(getPrism().getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED));\n\t\tboolean showGraphDialog = false;\n\t\tboolean useSimulation = false;\n\t\tif (uCon.getMFNumUndefined() + uCon.getPFNumUndefined() == 0) {\n\t\t\terror(\"Cannot create an experiment because there are no constants with undefined values\");\n\t\t\treturn;\n\t\t}\n\t\tboolean offerGraph = type instanceof TypeInt || type instanceof TypeDouble || type instanceof TypeInterval;\n\t\tint result = GUIExperimentPicker.defineConstantsWithDialog(this.getGUI(), uCon, offerGraph, gp.isValidForSimulation());\n\t\tif (result == GUIExperimentPicker.VALUES_DONE_SHOW_GRAPH || result == GUIExperimentPicker.VALUES_DONE_SHOW_GRAPH_AND_SIMULATE) {\n\t\t\tshowGraphDialog = true;\n\t\t} else if (result == GUIExperimentPicker.CANCELLED)\n\t\t\treturn;\n\t\tif (result == GUIExperimentPicker.VALUES_DONE_SIMULATE || result == GUIExperimentPicker.VALUES_DONE_SHOW_GRAPH_AND_SIMULATE) {\n\t\t\tuseSimulation = true;\n\t\t}\n\n\t\t//if we are using simulation, make sure the property is ok\n\t\tif (useSimulation) {\n\t\t\ttry {\n\t\t\t\tgetPrism().checkPropertyForSimulation(gp.getProperty());\n\t\t\t} catch (PrismException e) {\n\t\t\t\terror(\"Property is not suitable for simulation: \" + e.getMessage());\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\n\t\t// make sure we can actually create a graph, i.e. that there is >1 result\n\t\tif (showGraphDialog)\n\t\t\tif (uCon.getRangingConstants().size() == 0) {\n\t\t\t\tmessage(\"Cannot create a graph since there is only a single result.\");\n\t\t\t\tshowGraphDialog = false;\n\t\t\t}\n\n\t\t// Use these values to create a new experiment\n\t\tint i = experiments.newExperiment(parsedProperties, uCon, useSimulation);\n\t\tboolean notCancelled = true;\n\t\t// start the experiment, via the graph dialog if appropriate\n\t\tif (showGraphDialog) {\n\t\t\tGUIGraphPicker ggp = new GUIGraphPicker(getGUI(), this, experiments.getExperiment(i), graphHandler, false);\n\t\t\tif (ggp.isGraphCancelled()) {\n\t\t\t\tif (questionYesNo(\"Do you want to cancel the experiment completely?\", 0) == 0)\n\t\t\t\t\tnotCancelled = false;\n\t\t\t}\n\t\t}\n\n\t\tif (notCancelled)\n\t\t\texperiments.startExperiment(i);\n\t\t//else\n\t\t//\texperiments.removeExperiment(i);\n\t}\n\n\tpublic void propertyLoadSuccessful(PropertiesFile pf, File f)\n\t{\n\t\t// note: add constants/labels first to stop property parse errors\n\t\tconsTable.newList();\n\t\tconsTable.addPropertiesFile(pf);\n\t\tlabTable.newList();\n\t\tlabTable.addPropertiesFile(pf);\n\t\tpropList.deleteAll();\n\t\tpropList.addPropertiesFile(pf);\n\t\ttabToFront();\n\t\tsetModified(false);\n\t\tsetActiveFile(f);\n\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.PROPERTIES_LIST_CHANGED));\n\t}\n\n\tpublic void propertyInsertSuccessful(PropertiesFile pf)\n\t{\n\t\tpropList.addPropertiesFile(pf);\n\t\tconsTable.addPropertiesFile(pf);\n\t\tlabTable.addPropertiesFile(pf);\n\t\ttabToFront();\n\t\tsetModified(true);\n\t}\n\n\tpublic void propertySaveSuccessful(File f)\n\t{\n\t\tsetActiveFile(f);\n\t\tsetModified(false);\n\t}\n\n\tpublic void changeProperty(String pctl, String comment, String id)\n\t{\n\t\tint index = propList.getIndexOf(id);\n\t\tif (index < 0) {\n\t\t\tif (pctl != null) {\n\t\t\t\tpropList.addProperty(pctl, comment);\n\t\t\t\tsetModified(true);\n\t\t\t}\n\t\t} else {\n\t\t\tGUIProperty gp = propList.getProperty(index);\n\t\t\tgp.setBeingEdited(false);\n\t\t\tif (pctl != null) {\n\t\t\t\tif (pctl.matches(\"\\\"[^\\\"]*\\\"[ ]*:.*\")) {\n\t\t\t\t\t//the string contains property name\n\t\t\t\t\tint start = pctl.indexOf('\"') + 1;\n\t\t\t\t\tint end = pctl.indexOf('\"', start);\n\t\t\t\t\tString name = pctl.substring(start, end);\n\t\t\t\t\tint colon = pctl.indexOf(':') + 1;\n\t\t\t\t\tpctl = pctl.substring(colon).trim();\n\t\t\t\t\tgp.setPropStringAndName(pctl, name, parsedModel, getConstantsString(), getLabelsString());\n\t\t\t\t} else {\n\t\t\t\t\tgp.setPropStringAndName(pctl, null, parsedModel, getConstantsString(), getLabelsString());\n\t\t\t\t}\n\n\t\t\t\tgp.setComment(comment);\n\t\t\t\tsetModified(true);\n\t\t\t}\n\t\t\t// Force repaint because we modified the GUIProperty directly\n\t\t\trepaintList();\n\t\t}\n\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t\tupdateCommentLabel();\n\t}\n\n\tpublic void cancelProperty(String id)\n\t{\n\t\tint index = propList.getIndexOf(id);\n\t\tif (index >= 0) {\n\t\t\tGUIProperty gp = propList.getProperty(index);\n\t\t\tgp.setBeingEdited(false);\n\t\t\t// Force repaint because we modified the GUIProperty directly\n\t\t\trepaintList();\n\t\t}\n\t}\n\n\t/** Called by the constant list to let us know something changed there */\n\n\tpublic void constantListChanged()\n\t{\n\t\tlabTable.validateLabels();\n\t\t//maybe some constants became valid/invalid, so validate them\n\t\t//before re-validating properties.\n\t\tconsTable.validateConstants();\n\t\tpropList.validateProperties();\n\t\tsetModified(true);\n\t}\n\n\t/** Called by the label list to let us know something changed there */\n\n\tpublic void labelListChanged()\n\t{\n\t\tpropList.validateProperties();\n\t\tsetModified(true);\n\t}\n\n\tprotected void setModified(boolean mod)\n\t{\n\t\tmodified = mod;\n\t\tsetActiveFileLabel();\n\t\tif (modified) {\n\t\t\tdoEnables();\n\t\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.PROPERTIES_LIST_CHANGED));\n\t\t}\n\t}\n\n\tprotected void setComputing(boolean com)\n\t{\n\t\tcomputing = com;\n\t\tdoEnables();\n\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t}\n\n\tprotected void setActiveFile(File f)\n\t{\n\t\tactiveFile = f;\n\t\tsetActiveFileLabel();\n\t}\n\n\tprotected void setActiveFileLabel()\n\t{\n\t\tfileTextField.setText(\"Properties list: \" + ((activeFile == null) ? \"<Untitled>\" : activeFile.getPath()) + (modified ? \"*\" : \"\"));\n\t}\n\n\tprotected void setParsedModel(ModulesFile m)\n\t{\n\t\tparsedModel = m;\n\t\tconsTable.validateConstants();\n\t\tpropList.validateProperties();\n\t\tdoEnables();\n\t}\n\n\tprotected void doEnables()\n\t{\n\t\t// properties panel\n\t\tsetEnabled(true);\n\t\tsetTabEnabled(true);\n\t\t// properties menu\n\t\tnewProps.setEnabled(!computing);\n\t\topenProps.setEnabled(!computing);\n\t\tinsertProps.setEnabled(!computing);\n\t\tsaveProps.setEnabled(!computing);\n\t\tsavePropsAs.setEnabled(!computing);\n\t\tsimulate.setEnabled(!computing && parsedModel != null && propList.existsValidSimulatableSelectedProperties());\n\t\tverifySelected.setEnabled(!computing && parsedModel != null && propList.existsValidSelectedProperties());\n\t\t//exportStrategyMenu.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\texportStrategyActions.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\texportStrategyActionsStates.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\texportStrategyInducedRestrict.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\texportStrategyInducedReduce.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\texportStrategyInducedDot.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\tviewStrategyActions.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\tviewStrategyActionsStates.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\tviewStrategyInducedRestrict.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\tviewStrategyInducedReduce.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\tsimulateStrategy.setEnabled(!computing && parsedModel != null && getGUI().getPrism().getStrategy() != null);\n\t\texportLabelsPlain.setEnabled(!computing && parsedModel != null);\n\t\texportModelLabelsPlain.setEnabled(!computing && parsedModel != null);\n\t\texportLabelsMatlab.setEnabled(!computing && parsedModel != null);\n\t\texportModelLabelsMatlab.setEnabled(!computing && parsedModel != null);\n\t\tdetails.setEnabled(!computing && parsedModel != null && propList.existsValidSelectedProperties());\n\t\t// properties list\n\t\tpropList.setEnabled(!computing);\n\t\tnewProperty.setEnabled(!computing);\n\t\teditProperty.setEnabled(!computing && propList.getSelectedProperties().size() > 0);\n\t\t// constants list\n\t\tconsTable.setEnabled(!computing);\n\t\tremoveConstant.setEnabled(consTable.getSelectedRowCount() > 0);\n\t\t// label list\n\t\tlabTable.setEnabled(!computing);\n\t\tremoveLabel.setEnabled(labTable.getSelectedRowCount() > 0);\n\n\t\t// newExperiment: enabled if there is exactly one prop selected and it is valid\n\t\tnewExperiment.setEnabled(propList.getNumSelectedProperties() == 1 && propList.getValidSelectedProperties().size() == 1);\n\t\t// parametric: enabled if there is exactly one prop selected and it is valid\n\t\tparametric.setEnabled(propList.getNumSelectedProperties() == 1 && propList.getValidSelectedProperties().size() == 1);\n\t\t// deleteExperiments: enabled if one or more experiments selected\n\t\tdeleteExperiment.setEnabled(experiments.getSelectedRowCount() > 0);\n\t\t// viewResults: enabled if at least one experiment is selected\n\t\tviewResults.setEnabled(experiments.getSelectedRowCount() > 0);\n\t\t// plotResults: enabled if exactly one experiment is selected and its type is int/double\n\t\tif (experiments.getSelectedRowCount() == 1) {\n\t\t\tGUIExperiment exp = experiments.getExperiment(experiments.getSelectedRow());\n\t\t\tType type = exp.getExpressionType();\n\t\t\tplotResults.setEnabled(type instanceof TypeInt || type instanceof TypeDouble || type instanceof TypeInterval);\n\t\t} else {\n\t\t\tplotResults.setEnabled(false);\n\t\t}\n\t\t// exportResults: enabled if at least one experiment is selected\n\t\texportResultsListText.setEnabled(experiments.getSelectedRowCount() > 0);\n\t\texportResultsListCSV.setEnabled(experiments.getSelectedRowCount() > 0);\n\t\texportResultsMatrixText.setEnabled(experiments.getSelectedRowCount() > 0);\n\t\texportResultsMatrixCSV.setEnabled(experiments.getSelectedRowCount() > 0);\n\t\texportResultsDataFrameCSV.setEnabled(experiments.getSelectedRowCount() > 0);\n\t\texportResultsComment.setEnabled(experiments.getSelectedRowCount() > 0);\n\t}\n\n\tpublic int doModificationCheck()\n\t{\n\t\tif (modified) {\n\t\t\tif (activeFile == null) {\n\t\t\t\tString[] selection = { \"Yes\", \"No\", \"Cancel\" };\n\t\t\t\tint selectionNo = -1;\n\t\t\t\tselectionNo = optionPane(\"Properties list has been modified.\\nDo you wish to save it?\", \"Question\", JOptionPane.OK_CANCEL_OPTION,\n\t\t\t\t\t\tJOptionPane.QUESTION_MESSAGE, selection, selection[0]);\n\t\t\t\tswitch (selectionNo) {\n\t\t\t\tcase 0:\n\t\t\t\t\treturn a_save();\n\t\t\t\tcase 1:\n\t\t\t\t\treturn CONTINUE;\n\t\t\t\tcase 2:\n\t\t\t\t\treturn CANCEL;\n\t\t\t\tdefault:\n\t\t\t\t\treturn CANCEL;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tString[] selection = { \"Yes\", \"No\", \"Save As...\", \"Cancel\" };\n\t\t\t\tint selectionNo = -1;\n\t\t\t\tselectionNo = optionPane(\"Properties list has been modified.\\nDo you wish to save it?\", \"Question\", JOptionPane.OK_CANCEL_OPTION,\n\t\t\t\t\t\tJOptionPane.QUESTION_MESSAGE, selection, selection[0]);\n\t\t\t\tswitch (selectionNo) {\n\t\t\t\tcase 0:\n\t\t\t\t\treturn a_save();\n\t\t\t\tcase 1:\n\t\t\t\t\treturn CONTINUE;\n\t\t\t\tcase 2:\n\t\t\t\t\treturn a_saveAs();\n\t\t\t\tcase 3:\n\t\t\t\t\treturn CANCEL;\n\t\t\t\tdefault:\n\t\t\t\t\treturn CANCEL;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn CONTINUE;\n\t}\n\n\tprivate void updateCommentLabel()\n\t{\n\t\tArrayList<GUIProperty> selectedProps = propList.getSelectedProperties();\n\t\tif (selectedProps.size() == 1) {\n\t\t\tGUIProperty p = selectedProps.get(0);\n\t\t\tcomLabel.setText(p.getComment());\n\t\t} else {\n\t\t\tcomLabel.setText(\"\");\n\t\t}\n\t}\n\n\t//ACTION METHODS\n\n\tpublic void a_newList()\n\t{\n\t\tif (doModificationCheck() != CONTINUE)\n\t\t\treturn;\n\n\t\tpropList.deleteAll();\n\t\tconsTable.newList();\n\t\tlabTable.newList();\n\t\ttabToFront();\n\t\tsetModified(false);\n\t\tsetActiveFile(null);\n\t\tdoEnables();\n\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.PROPERTIES_LIST_CHANGED));\n\t}\n\n\tpublic void a_open()\n\t{\n\t\tif (doModificationCheck() != CONTINUE)\n\t\t\treturn;\n\n\t\tif (showOpenFileDialog(propsFilter) == JFileChooser.APPROVE_OPTION) {\n\t\t\tFile file = getChooserFile();\n\t\t\tif (file == null) {\n\t\t\t\terror(\"No file selected\");\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tThread t = new LoadPropertiesThread(this, file);\n\t\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\t\tt.start();\n\t\t}\n\t}\n\n\t// Save properties\n\t// NB: This used to be in a thread but I have taken it out because:\n\t//\t (a) We sometimes need to know whether save was successful before continuing\n\t//\t (b) When saving before clearing, clear can occur too early\n\n\tpublic int a_save()\n\t{\n\t\tif (activeFile == null) {\n\t\t\treturn a_saveAs();\n\t\t} else {\n\t\t\t// only allow save if all props valid (can't reopen file otherwise)\n\t\t\tif (!propList.allPropertiesAreValid()) {\n\t\t\t\tmessage(\"Cannot save properties list: some properties are invalid\");\n\t\t\t\treturn CANCEL;\n\t\t\t} else {\n\t\t\t\t// do save\n\t\t\t\ttry {\n\t\t\t\t\tsetTaskBarText(\"Saving properties...\");\n\t\t\t\t\tPrintWriter out = new PrintWriter(new FileWriter(activeFile));\n\t\t\t\t\tout.print(propList.toFileString(activeFile, consTable, labTable));\n\t\t\t\t\tout.flush();\n\t\t\t\t\tout.close();\n\t\t\t\t} catch (IOException e) {\n\t\t\t\t\tsetTaskBarText(\"Saving properties... error.\");\n\t\t\t\t\terror(\"Could not save to file \\\"\" + activeFile + \"\\\"\");\n\t\t\t\t\treturn CANCEL;\n\t\t\t\t}\n\t\t\t\tsetTaskBarText(\"Saving properties... done.\");\n\t\t\t\tpropertySaveSuccessful(activeFile);\n\t\t\t\treturn CONTINUE;\n\t\t\t}\n\t\t}\n\t}\n\n\t// Save properties as\n\t// NB: This used to be in a thread but I have taken it out because:\n\t//\t (a) We sometimes need to know whether save was successful before continuing\n\t//\t (b) When saving before clearing, clear can occur too early\n\n\tpublic int a_saveAs()\n\t{\n\t\t// only allow save if all props valid (can't reopen file otherwise)\n\t\tif (!propList.allPropertiesAreValid()) {\n\t\t\tmessage(\"Cannot save properties list: some properties are invalid\");\n\t\t\treturn CANCEL;\n\t\t}\n\t\tif (!consTable.isConstantListValid()) {\n\t\t\tmessage(\"Cannot save properties list: some constants are invalid\");\n\t\t\treturn CANCEL;\n\t\t}\n\t\tif (showSaveFileDialog(propsFilter) == JFileChooser.APPROVE_OPTION) {\n\t\t\tFile file = getChooserFile();\n\t\t\t// do save\n\t\t\ttry {\n\t\t\t\tsetTaskBarText(\"Saving properties...\");\n\t\t\t\tPrintWriter out = new PrintWriter(new FileWriter(file));\n\t\t\t\tout.print(propList.toFileString(file, consTable, labTable));\n\t\t\t\tout.flush();\n\t\t\t\tout.close();\n\t\t\t} catch (IOException e) {\n\t\t\t\tsetTaskBarText(\"Saving properties... error.\");\n\t\t\t\terror(\"Could not save to file \\\"\" + file + \"\\\"\");\n\t\t\t\treturn CANCEL;\n\t\t\t}\n\t\t\tsetTaskBarText(\"Saving properties... done.\");\n\t\t\tpropertySaveSuccessful(file);\n\t\t\treturn CONTINUE;\n\t\t}\n\t\treturn CANCEL;\n\t}\n\n\tpublic void a_insert()\n\t{\n\t\tif (showOpenFileDialog(propsFilter) == JFileChooser.APPROVE_OPTION) {\n\t\t\tFile file = getChooserFile();\n\t\t\tif (file == null) {\n\t\t\t\terror(\"No file selected\");\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tThread t = new LoadPropertiesThread(this, file, true);\n\t\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\t\tt.start();\n\t\t} else {\n\t\t\treturn;\n\t\t}\n\t}\n\n\tpublic void a_simulateSelected()\n\t{\n\t\tconsTable.correctEditors();\n\t\tlabTable.correctEditors();\n\t\t// Bail out if there are no valid properties to simulate\n\t\t// (probably never occurs - action is disabled in this case)\n\t\tif (!propList.existsValidSimulatableSelectedProperties()) {\n\t\t\terror(\"None of the selected properties are suitable for simulation\");\n\t\t\treturn;\n\t\t}\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Request a parse\n\t\tsimulateAfterReceiveParseNotification = true;\n\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.REQUEST_MODEL_PARSE));\n\t}\n\n\tpublic void a_detailSelected()\n\t{\n\t\tint[] selected = propList.getSelectedIndices();\n\n\t\tfor (int i = 0; i < selected.length; i++) {\n\t\t\tGUIProperty gp = propList.getProperty(selected[i]);\n\t\t\tif (!gp.isBeingEdited()) {\n\t\t\t\tgp.setBeingEdited(true);\n\t\t\t\t// Force repaint because we modified the GUIProperty directly\n\t\t\t\trepaintList();\n\t\t\t\tnew GUIPropertyResultDialog(getGUI(), this, gp).display();\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void a_verifySelected()\n\t{\n\t\tconsTable.correctEditors();\n\t\tlabTable.correctEditors();\n\t\t// Bail out if there are no valid properties to verify\n\t\t// (probably never occurs - action is disabled in this case)\n\t\tif (!propList.existsValidSelectedProperties()) {\n\t\t\terror(\"None of the selected properties are suitable for verification. The model was not built\");\n\t\t\treturn;\n\t\t}\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Request a parse\n\t\tverifyAfterReceiveParseNotification = true;\n\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.REQUEST_MODEL_PARSE));\n\t}\n\n\tpublic void a_verifyDone()\n\t{\n\t\tint[] selected = propList.getSelectedIndices();\n\n\t\t// Display result dialogs\n\t\tfor (int i = 0; i < selected.length; i++) {\n\t\t\tGUIProperty gp = propList.getProperty(selected[i]);\n\t\t\tif (!gp.isBeingEdited()) {\n\t\t\t\tgp.setBeingEdited(true);\n\t\t\t\t// Force repaint because we modified the GUIProperty directly\n\t\t\t\trepaintList();\n\t\t\t\tnew GUIPropertyResultDialog(getGUI(), this, gp).display();\n\t\t\t}\n\t\t}\n\n\t\t// How to plot a parametric result...\n\t\t/*if (selected.length == 1) {\n\t\t\tGUIProperty gp = propList.getProperty(selected[0]);\n\t\t\tif (gp.getResult().getResult() instanceof RegionValues) {\n\t\t\t\tGraph graph = new Graph(\"Param\");\n\t\t\t\tSeriesKey sk = graph.addSeries(\"param\");\n\t\t\t\tRegionValues vals = (RegionValues) gp.getResult().getResult();\n\t\t\t\tparam.Function f = vals.getResult(0).getInitStateValueAsFunction();\n\t\t\t\tint n = 100;\n\t\t\t\tfor (int i = 0; i < n; i++) {\n\t\t\t\t\tBigRational br = f.evaluate(new param.Point(new BigRational[] {new BigRational(i, n)}));\n\t\t\t\t\tXYDataItem di = new XYDataItem(((double)i)/n, br.doubleValue());\n\t\t\t\t\tgraph.addPointToSeries(sk, di);\n\t\t\t\t}\n\t\t\t\tthis.getGraphHandler().addGraph(graph);\n\t\t\t}\n\t\t}*/\n\t\t\n\t\t// For a single property with a displayable counterexample, offer to do show it\n\t\tif (selected.length == 1) {\n\t\t\tGUIProperty gp = propList.getProperty(selected[0]);\n\t\t\tObject cex = gp.getResult().getCounterexample();\n\t\t\tif (cex != null && cex instanceof simulator.PathFullInfo) {\n\t\t\t\tString qu = \"Do you want to view a witness/counterexample for the property in the simulator?\";\n\t\t\t\tif (questionYesNo(\"Question\", qu, 0) == 0) {\n\t\t\t\t\tsimulator.a_loadPath((simulator.PathFullInfo) cex);\n\t\t\t\t\tsimulator.tabToFront();\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t//print Pareto curves for all available TileLists, then clear the storage\n\t\tsynchronized (TileList.getStoredTileLists()) {\n\t\t\tfor (int i = 0; i < TileList.getStoredTileLists().size(); i++) {\n\t\t\t\tTileList tl = TileList.getStoredTileLists().get(i);\n\t\t\t\tif (tl != null && tl.getDimension() == 2) {\n\t\t\t\t\tGraph graph = new Graph(TileList.getStoredFormulas().get(i).toString());\n\t\t\t\t\tgraph.getXAxisSettings().setHeading(TileList.getStoredFormulasX().get(i).toString());\n\t\t\t\t\tgraph.getYAxisSettings().setHeading(TileList.getStoredFormulasY().get(i).toString());\n\t\t\t\t\tSeriesKey sk = graph.addSeries(\"Pareto curve\");\n\n\t\t\t\t\t//Get points in tilelist and sort them. This is required for the graph to show them right\n\t\t\t\t\tList<prism.Point> l = tl.getPoints();\n\t\t\t\t\tComparator<prism.Point> c = new Comparator<prism.Point>()\n\t\t\t\t\t{\n\t\t\t\t\t\tpublic int compare(prism.Point o1, prism.Point o2)\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tif (o1.getCoord(0) == o2.getCoord(0))\n\t\t\t\t\t\t\t\treturn Double.compare(o1.getCoord(1), o2.getCoord(1));\n\t\t\t\t\t\t\telse\n\t\t\t\t\t\t\t\treturn Double.compare(o1.getCoord(0), o2.getCoord(0));\n\t\t\t\t\t\t};\n\t\t\t\t\t};\n\n\t\t\t\t\tCollections.sort(l, c);\n\n\t\t\t\t\tfor (prism.Point p : l) {\n\t\t\t\t\t\tprism.Point pReal = p.toRealProperties(tl.getOpsAndBoundsList());\n\t\t\t\t\t\tXYDataItem di = new XYDataItem(pReal.getCoord(0), pReal.getCoord(1));\n\t\t\t\t\t\tgraph.addPointToSeries(sk, di);\n\t\t\t\t\t}\n\t\t\t\t\tthis.getGraphHandler().addGraph(graph);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tTileList.clearStoredTileLists();\n\t\t}\n\t}\n\n\tpublic void a_cut()\n\t{\n\t\tjava.awt.datatransfer.Clipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();\n\t\t//java.awt.datatransfer.StringSelection selection = new java.awt.datatransfer.StringSelection(propList.getClipboardString());\n\t\t//clipboard.setContents(selection, null);\n\t\tclipboard.setContents(new GUIClipboardProperties(propList.getSelectedProperties()), null);\n\t\ta_delete();\n\t}\n\n\tpublic void a_copy()\n\t{\n\t\tjava.awt.datatransfer.Clipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();\n\t\t//java.awt.datatransfer.StringSelection selection = new java.awt.datatransfer.StringSelection(propList.getClipboardString());\n\t\t//clipboard.setContents(selection, null);\n\t\tclipboard.setContents(new GUIClipboardProperties(propList.getSelectedProperties()), null);\n\t}\n\n\tpublic void a_paste()\n\t{\n\t\tClipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();\n\t\tTransferable contents = clipboard.getContents(null);\n\n\t\tif (contents != null) {\n\t\t\tif (contents.isDataFlavorSupported(getGUIClipboardPropertiesDataFlavor())) {\n\t\t\t\ttry {\n\t\t\t\t\tGUIClipboardProperties gcp = (GUIClipboardProperties) contents.getTransferData(getGUIClipboardPropertiesDataFlavor());\n\t\t\t\t\tArrayList<GUIProperty> listOfProperties = gcp.getProperties();\n\t\t\t\t\tfor (int i = 0; i < listOfProperties.size(); i++) {\n\t\t\t\t\t\tGUIProperty property = (GUIProperty) listOfProperties.get(i);\n\t\t\t\t\t\tpropList.addProperty(property.getName(), property.getPropString(), property.getComment());\n\t\t\t\t\t\tsetModified(true);\n\t\t\t\t\t}\n\t\t\t\t} catch (UnsupportedFlavorException e) {\n\t\t\t\t} catch (IOException e) {\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\ttry {\n\t\t\t\t\tString text = (String) contents.getTransferData(java.awt.datatransfer.DataFlavor.stringFlavor);\n\t\t\t\t\tpropList.pastePropertiesString(text);\n\t\t\t\t\tsetModified(true);\n\t\t\t\t} catch (UnsupportedFlavorException e) {\n\t\t\t\t} catch (IOException e) {\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void a_delete()\n\t{\n\t\tpropList.deleteSelected();\n\t\tsetModified(true);\n\t}\n\n\tpublic void a_deleteAll()\n\t{\n\t\tpropList.deleteAll();\n\t\tsetModified(true);\n\t}\n\n\tpublic void a_newProperty()\n\t{\n\t\tGUIPropertyEditor ed = new GUIPropertyEditor(this, getInvalidPropertyStrategy());\n\t\ted.show();\n\t}\n\n\tpublic void a_editProperty()\n\t{\n\t\tint[] selected = propList.getSelectedIndices();\n\n\t\tfor (int i = 0; i < selected.length; i++) {\n\t\t\tGUIProperty gp = propList.getProperty(selected[i]);\n\t\t\tif (!gp.isBeingEdited()) {\n\t\t\t\tgp.setBeingEdited(true);\n\t\t\t\t// Force repaint because we modified the GUIProperty directly\n\t\t\t\trepaintList();\n\t\t\t\tGUIPropertyEditor ed = new GUIPropertyEditor(this, gp, getInvalidPropertyStrategy());\n\t\t\t\ted.show();\n\t\t\t}\n\t\t}\n\n\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t}\n\n\tpublic void a_selectAll()\n\t{\n\t\tpropList.selectAll();\n\t}\n\n\tpublic void a_addConstant()\n\t{\n\t\tconsTable.addNewConstant();\n\t}\n\n\tpublic void a_removeSelectedConstants()\n\t{\n\t\t// Note: Unlike for prop list, this is safe because constants can always be deleted\n\t\t//       (not the case properties - e.g. if they are being edited)\n\t\twhile (consTable.getSelectedRowCount() > 0) {\n\t\t\tconsTable.removeConstant(consTable.getSelectedRow());//for now\n\t\t}\n\t}\n\n\tpublic void a_addLabel()\n\t{\n\t\tlabTable.addNewLabel();\n\t}\n\n\tpublic void a_removeSelectedLabels()\n\t{\n\t\t// Note: Unlike for prop list, this is safe because constants can always be deleted\n\t\t//       (not the case properties - e.g. if they are being edited)\n\t\twhile (labTable.getSelectedRowCount() > 0) {\n\t\t\tlabTable.removeLabel(labTable.getSelectedRow());\n\t\t}\n\t}\n\n\tpublic void a_exportLabels(ModelExportTask.LabelExportSet exportLabelSet, ModelExportFormat exportFormat)\n\t{\n\t\tint res = JFileChooser.CANCEL_OPTION;\n\n\t\t// pop up dialog to select file\n\t\tswitch (exportFormat) {\n\t\t\tcase MATLAB:\n\t\t\t\tres = showSaveFileDialog(matlabFilter);\n\t\t\t\tbreak;\n\t\t\tcase EXPLICIT:\n\t\t\tdefault:\n\t\t\t\tres = showSaveFileDialog(labFilters.values(), labFilters.get(\"lab\"));\n\t\t\t\tbreak;\n\t\t}\n\t\tif (res != JFileChooser.APPROVE_OPTION) {\n\t\t\treturn;\n\t\t}\n\t\tconsTable.correctEditors();\n\t\tlabTable.correctEditors();\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Set flag, store export info\n\t\texportLabelsAfterReceiveParseNotification = true;\n\t\texportTask = new ModelExportTask(ModelExportTask.ModelExportEntity.LABELS, getChooserFile(), new ModelExportOptions(exportFormat));\n\t\texportTask.setLabelExportSet(exportLabelSet);\n\t\t// Request a parse\n\t\texportLabelsAfterReceiveParseNotification = true;\n\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.REQUEST_MODEL_PARSE));\n\t}\n\t\n\tpublic void exportLabelsAfterParse()\n\t{\n\t\t// Switch off flag\n\t\texportLabelsAfterReceiveParseNotification = false;\n\t\ttry {\n\t\t\t// are we in exact mode?\n\t\t\tboolean exact = getPrism().getSettings().getBoolean(PrismSettings.PRISM_EXACT_ENABLED);\n\n\t\t\t// Parse labels/constants\n\t\t\tparsedProperties = getPrism().parsePropertiesString(getLabelsString() + \"\\n\" + getConstantsString());\n\t\t\t// Query user for undefined constant values (if required)\n\t\t\tUndefinedConstants uCon = new UndefinedConstants(parsedModel, parsedProperties, true);\n\t\t\tuCon.setExactMode(exact);\n\t\t\tif (uCon.getMFNumUndefined() + uCon.getPFNumUndefined() > 0) {\n\t\t\t\t// Use previous constant values as defaults in dialog\n\t\t\t\tValues lastModelConstants = getPrism().getUndefinedModelValues();\n\t\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(this.getGUI(), uCon, lastModelConstants, pfConstants);\n\t\t\t\tif (result != GUIConstantsPicker.VALUES_DONE)\n\t\t\t\t\treturn;\n\t\t\t}\n\t\t\t// Store model/property constants\n\t\t\tpfConstants = uCon.getPFConstantValues();\n\t\t\t// currently, evaluate constants non-exact for model building\n\t\t\tgetPrism().setPRISMModelConstants(uCon.getMFConstantValues(), exact);\n\t\t\tif (exportTask.extraLabelsUsed()) {\n\t\t\t\tparsedProperties.setSomeUndefinedConstants(pfConstants, exact);\n\t\t\t\texportTask.setExtraLabelsSource(parsedProperties);\n\t\t\t}\n\t\t\t// If export is being done to log, switch view to log\n\t\t\tif (exportTask.getFile() == null) {\n\t\t\t\tlogToFront();\n\t\t\t}\n\t\t\t// Start export\n\t\t\tnew ExportBuiltModelThread(this, exportTask).start();\n\t\t} catch (PrismException e) {\n\t\t\terror(e.getMessage());\n\t\t\treturn;\n\t\t}\n\t}\n\n\tpublic void a_exportStrategy(StrategyExportType exportType)\n\t{\n\t\ta_exportStrategy(new StrategyExportOptions((exportType)));\n\t}\n\n\tpublic void a_exportStrategy(StrategyExportOptions exportOptions)\n\t{\n\t\t// Pop up dialog to select file\n\t\tint res = JFileChooser.CANCEL_OPTION;\n\t\tswitch (exportOptions.getType()) {\n\t\tcase ACTIONS:\n\t\t\tres = showSaveFileDialog(textFilter);\n\t\t\tbreak;\n\t\tcase INDUCED_MODEL:\n\t\t\tres = showSaveFileDialog(traFilters.values(), traFilters.get(\"tra\"));\n\t\t\tbreak;\n\t\tcase DOT_FILE:\n\t\t\tres = showSaveFileDialog(dotFilter);\n\t\t\tbreak;\n\t\tdefault:\n\t\t\tres = showSaveFileDialog(textFilter);\n\t\t\tbreak;\n\t\t}\n\t\tif (res != JFileChooser.APPROVE_OPTION)\n\t\t\treturn;\n\t\tFile file = getChooserFile();\n\t\t// Do export\n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\tExportStrategyThread t = new ExportStrategyThread(this, exportOptions, file);\n\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\tt.start();\n\t}\n\n\tpublic void a_viewStrategy(StrategyExportType exportType)\n\t{\n\t\ta_viewStrategy(new StrategyExportOptions((exportType)));\n\t}\n\n\tpublic void a_viewStrategy(StrategyExportOptions exportOptions)\n\t{\n\t\tlogToFront();\n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\tExportStrategyThread t = new ExportStrategyThread(this, exportOptions, null);\n\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\tt.start();\n\t}\n\n\tpublic void a_newExperiment()\n\t{\n\t\t// Reset warnings counter \n\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t// Start expt\n\t\texperimentAfterReceiveParseNotification = true;\n\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.REQUEST_MODEL_PARSE));\n\t}\n\n\tpublic void a_stopExperiment()\n\t{\n\t\texperiments.stop();\n\t}\n\n\tpublic void a_deleteExperiment()\n\t{\n\t\texperiments.deleteSelected();\n\t}\n\n\tpublic void a_viewResults()\n\t{\n\t\tGUIExperiment exp;\n\t\tint i, n, inds[];\n\n\t\t// get selected experiments\n\t\tn = experiments.getSelectedRowCount();\n\t\tif (n < 1)\n\t\t\treturn;\n\t\tinds = experiments.getSelectedRows();\n\t\t// show results dialog for reach one\n\t\tfor (i = 0; i < n; i++) {\n\t\t\texp = experiments.getExperiment(inds[i]);\n\t\t\tnew GUIResultsTable(this.getGUI(), this, exp).show();\n\t\t}\n\t}\n\n\tpublic void a_plotResults()\n\t{\n\t\tGUIExperiment exp;\n\t\tType type;\n\n\t\t// get experiment\n\t\tif (experiments.getSelectedRowCount() != 1)\n\t\t\treturn;\n\t\texp = experiments.getExperiment(experiments.getSelectedRow());\n\t\t// check its type\n\t\ttype = exp.getExpressionType();\n\t\tif (!(type instanceof TypeInt || type instanceof TypeDouble || type instanceof TypeInterval)) {\n\t\t\tmessage(\"Can only plot results if the property is of type int or double\");\n\t\t\treturn;\n\t\t}\n\t\t// make sure we can actually create a graph, i.e. that there is >1 result\n\t\tif (exp.getRangingConstants().size() == 0) {\n\t\t\tmessage(\"Cannot create a graph since there is only a single result.\");\n\t\t\treturn;\n\t\t}\n\n\t\t// launch dialog, plot series (modal)\n\t\tnew GUIGraphPicker(getGUI(), this, exp, graphHandler, true);\n\t}\n\n\tpublic void a_exportResults(ResultsExportShape exportShape)\n\t{\n\t\t// get selected experiments\n\t\tint n = experiments.getSelectedRowCount();\n\t\tif (n < 1) {\n\t\t\treturn;\n\t\t}\n\t\tGUIExperiment[] exps = new GUIExperiment[n];\n\t\tint[] inds = experiments.getSelectedRows();\n\t\tfor (int i = 0; i < n; i++)\n\t\t\texps[i] = experiments.getExperiment(inds[i]);\n\t\t// get filename to save\n\t\tif (showSaveFileDialog(exportShape.isCSV ? csvFilter : textFilter) == JFileChooser.APPROVE_OPTION) {\n\t\t\tFile file = getChooserFile();\n\t\t\tThread t = new ExportResultsThread(this, exps, file, exportShape);\n\t\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\t\tt.start();\n\t\t}\n\t}\n\n\tpublic void a_importResults(ResultsExportShape exportShape)\n\t{\n\t\t// get selected experiments\n\t\tif (showOpenFileDialog(csvFilter) == JFileChooser.APPROVE_OPTION) {\n\t\t\tFile file = getChooserFile();\n\t\t\tThread t = new ImportResultsThread(this, experiments, file);\n\t\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\t\tt.start();\n\t\t}\n\t}\n\n\t//METHODS TO IMPLEMENT GUIPlugin INTERFACE\n\n\tpublic boolean displaysTab()\n\t{\n\t\treturn true;\n\t}\n\n\tpublic JMenu getMenu()\n\t{\n\t\t// Not used\n\t\treturn null;\n\t}\n\n\tpublic List<JMenu> getMenus()\n\t{\n\t\tList<JMenu> menus = new ArrayList<>();\n\t\tmenus.add(propMenu);\n\t\tmenus.add(stratMenu);\n\t\treturn menus;\n\t}\n\n\tpublic String getTabText()\n\t{\n\t\treturn \"Properties\";\n\t}\n\n\tpublic JToolBar getToolBar()\n\t{\n\t\treturn null;\n\t}\n\n\tpublic String getXMLIDTag()\n\t{\n\t\treturn \"\";\n\t}\n\n\tpublic Object getXMLSaveTree()\n\t{\n\t\treturn null;\n\t}\n\n\tpublic void loadXML(Object c)\n\t{\n\t}\n\n\t// if return value is true, event should not be passed on to any more listeners\n\n\tpublic boolean processGUIEvent(GUIEvent e)\n\t{\n\t\tif (e instanceof GUIModelEvent) {\n\t\t\tGUIModelEvent me = (GUIModelEvent) e;\n\t\t\tif (me.getID() == GUIModelEvent.NEW_MODEL) {\n\t\t\t\t//New Model\n\t\t\t\tsetParsedModel(null);\n\t\t\t\tdoEnables();\n\t\t\t\t//newList();\n\t\t\t} else if (me.getID() == GUIModelEvent.MODEL_BUILT) {\n\t\t\t\tdoEnables();\n\t\t\t} else if (me.getID() == GUIModelEvent.MODEL_PARSED) {\n\t\t\t\tsetParsedModel(me.getModulesFile());\n\t\t\t\tcheckForPropertiesToLoad();\n\t\t\t\tif (verifyAfterReceiveParseNotification)\n\t\t\t\t\tverifyAfterParse();\n\t\t\t\tif (experimentAfterReceiveParseNotification)\n\t\t\t\t\texperimentAfterParse();\n\t\t\t\tif (simulateAfterReceiveParseNotification)\n\t\t\t\t\tsimulateAfterParse();\n\t\t\t\tif (exportLabelsAfterReceiveParseNotification)\n\t\t\t\t\texportLabelsAfterParse();\n\t\t\t} else if (me.getID() == GUIModelEvent.MODEL_PARSE_FAILED) {\n\t\t\t\targsPropertiesFile = null;\n\t\t\t\tverifyAfterReceiveParseNotification = false;\n\t\t\t\texperimentAfterReceiveParseNotification = false;\n\t\t\t\tsimulateAfterReceiveParseNotification = false;\n\t\t\t\texportLabelsAfterReceiveParseNotification = false;\n\t\t\t} else if (me.getID() == GUIModelEvent.NEW_LOAD_NOT_RELOAD_MODEL) {\n\t\t\t\tif (getPrism().getSettings().getBoolean(PrismSettings.PROPERTIES_CLEAR_LIST_ON_LOAD)) {\n\t\t\t\t\ta_newList();\n\t\t\t\t}\n\t\t\t}\n\t\t} else if (e instanceof GUIComputationEvent) {\n\t\t\tif (e.getID() == GUIComputationEvent.COMPUTATION_START) {\n\t\t\t\tsetComputing(true);\n\t\t\t} else if (e.getID() == GUIComputationEvent.COMPUTATION_DONE) {\n\t\t\t\tsetComputing(false);\n\t\t\t} else if (e.getID() == GUIComputationEvent.COMPUTATION_ERROR) {\n\t\t\t\tsetComputing(false);\n\t\t\t}\n\t\t} else if (e instanceof GUIClipboardEvent && super.getGUI().getFocussedPlugin() == this) {\n\t\t\tGUIClipboardEvent ce = (GUIClipboardEvent) e;\n\n\t\t\tif (ce.getComponent() == this || ce.getComponent() == propList) {\n\t\t\t\tif (!computing) {\n\t\t\t\t\tif (ce.getID() == GUIClipboardEvent.CUT) {\n\t\t\t\t\t\ta_cut();\n\t\t\t\t\t} else if (ce.getID() == GUIClipboardEvent.COPY) {\n\t\t\t\t\t\ta_copy();\n\t\t\t\t\t} else if (ce.getID() == GUIClipboardEvent.PASTE) {\n\t\t\t\t\t\ta_paste();\n\t\t\t\t\t} else if (ce.getID() == GUIClipboardEvent.DELETE) {\n\t\t\t\t\t\ta_delete();\n\t\t\t\t\t} else if (ce.getID() == GUIClipboardEvent.SELECT_ALL) {\n\t\t\t\t\t\ta_selectAll();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t}\n\t\t} else if (e instanceof GUIPropertiesEvent) {\n\t\t\tGUIPropertiesEvent pr = (GUIPropertiesEvent) e;\n\t\t\tif (pr.getID() == GUIPropertiesEvent.EXPERIMENT_START) {\n\t\t\t\tstopExperiment.setEnabled(true);\n\t\t\t} else if (pr.getID() == GUIPropertiesEvent.EXPERIMENT_END) {\n\t\t\t\tstopExperiment.setEnabled(false);\n\t\t\t} else if (pr.getID() == GUIPropertiesEvent.VERIFY_END) {\n\t\t\t\ta_verifyDone();\n\t\t\t}\n\t\t} else if (e instanceof GUIExitEvent) {\n\t\t\tif (e.getID() == GUIExitEvent.REQUEST_EXIT) {\n\t\t\t\tif (doModificationCheck() != CONTINUE) {\n\t\t\t\t\tnotifyEventListeners(new GUIExitEvent(GUIExitEvent.CANCEL_EXIT));\n\t\t\t\t\treturn true;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\tprivate void checkForPropertiesToLoad()\n\t{\n\t\tif (argsPropertiesFile != null) {\n\t\t\tThread t = new LoadPropertiesThread(this, new File(argsPropertiesFile));\n\t\t\tt.setPriority(Thread.NORM_PRIORITY);\n\t\t\tt.start();\n\t\t\t//we clear the variable to avoid loading property file every time a model is parsed.\n\t\t\targsPropertiesFile = null;\n\t\t}\n\t}\n\n\t//METHODS TO IMPLEMENT MouseListner INTERFACE\n\n\tpublic void mouseClicked(MouseEvent e)\n\t{\n\t\tremoveConstant.setEnabled(consTable.getSelectedRowCount() > 0);\n\t\tremoveLabel.setEnabled(labTable.getSelectedRowCount() > 0);\n\t\tif (!computing) {\n\t\t\tif (e.getClickCount() >= 2) {\n\t\t\t\tif (e.getSource() == propList) {\n\t\t\t\t\tint index = propList.locationToIndex(e.getPoint());\n\n\t\t\t\t\tif (index != -1) {\n\t\t\t\t\t\t// locationToIndex provides the index to the \"nearest\"\n\t\t\t\t\t\t// property. We check here if the cursor is actually on\n\t\t\t\t\t\t// the property.\n\t\t\t\t\t\tRectangle bounds = propList.getCellBounds(index, index);\n\t\t\t\t\t\tif (bounds != null && bounds.contains(e.getPoint())) {\n\t\t\t\t\t\t\t// Cursor is on the property: select and open editor\n\t\t\t\t\t\t\tpropList.setSelectedIndex(index);\n\t\t\t\t\t\t\ta_editProperty();\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\t// Cursor is not on the property: open new property editor\n\t\t\t\t\t\t\ta_newProperty();\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\t// there is no property yet, open new property editor\n\t\t\t\t\t\ta_newProperty();\n\t\t\t\t\t}\n\t\t\t\t} else if (e.getSource() == consTable || e.getSource() == constantsScroll) {\n\t\t\t\t\tif (consTable.rowAtPoint(e.getPoint()) == -1) {\n\t\t\t\t\t\t// double-click, not an existing row -> add a new constant\n\t\t\t\t\t\ta_addConstant();\n\t\t\t\t\t}\n\t\t\t\t} else if (e.getSource() == labTable || e.getSource() == labelsScroll) {\n\t\t\t\t\tif (labTable.rowAtPoint(e.getPoint()) == -1) {\n\t\t\t\t\t\t// double-click, not an existing row -> add a new label\n\t\t\t\t\t\ta_addLabel();\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void mouseEntered(MouseEvent e)\n\t{\n\t\tremoveConstant.setEnabled(consTable.getSelectedRowCount() > 0);\n\t\tremoveLabel.setEnabled(labTable.getSelectedRowCount() > 0);\n\t}\n\n\tpublic void mouseExited(MouseEvent e)\n\t{\n\t\tremoveConstant.setEnabled(consTable.getSelectedRowCount() > 0);\n\t\tremoveLabel.setEnabled(labTable.getSelectedRowCount() > 0);\n\t}\n\n\tpublic void mousePressed(MouseEvent e)\n\t{\n\t\tremoveConstant.setEnabled(consTable.getSelectedRowCount() > 0);\n\t\tremoveLabel.setEnabled(labTable.getSelectedRowCount() > 0);\n\t\tif (!computing) {\n\t\t\tif (e.isPopupTrigger() && e.getSource() == propList) {\n\t\t\t\tint index = propList.locationToIndex(e.getPoint());\n\t\t\t\t// if there are no properties selected, select the one under the popup\n\t\t\t\tif (propList.isSelectionEmpty()) {\n\t\t\t\t\tif (index != -1) {\n\t\t\t\t\t\tpropList.setSelectedIndex(index);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// if the property under the popup is not already selected, select just that one\n\t\t\t\t\tint[] sel = propList.getSelectedIndices();\n\t\t\t\t\tboolean valid = false;\n\t\t\t\t\tfor (int i = 0; i < sel.length; i++) {\n\t\t\t\t\t\tif (sel[i] == index) {\n\t\t\t\t\t\t\tvalid = true;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (!valid) {\n\t\t\t\t\t\tpropList.setSelectedIndex(index);\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// disable certain actions if any of the selected propeties are currently being edited\n\t\t\t\tint[] sel = propList.getSelectedIndices();\n\t\t\t\tboolean showDeleters = true;\n\t\t\t\tfor (int i = 0; i < sel.length; i++) {\n\t\t\t\t\tif (propList.getProperty(sel[i]).isBeingEdited()) {\n\t\t\t\t\t\tshowDeleters = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tverifySelected.setEnabled(propList.existsValidSelectedProperties());\n\t\t\t\tsimulate.setEnabled(propList.existsValidSimulatableSelectedProperties());\n\t\t\t\tdetails.setEnabled(propList.existsValidSelectedProperties());\n\t\t\t\teditProperty.setEnabled(propList.getSelectedProperties().size() > 0);\n\n\t\t\t\tnewExperiment.setEnabled(propList.getNumSelectedProperties() == 1 && propList.getValidSelectedProperties().size() == 1);\n\t\t\t\tparametric.setEnabled(propList.getNumSelectedProperties() == 1 && propList.getValidSelectedProperties().size() == 1);\n\n\t\t\t\tif (showDeleters == false) {\n\t\t\t\t\tsimulate.setEnabled(false);\n\t\t\t\t\tverifySelected.setEnabled(false);\n\t\t\t\t\tdetails.setEnabled(false);\n\t\t\t\t\teditProperty.setEnabled(false);\n\t\t\t\t\tnewExperiment.setEnabled(false);\n\t\t\t\t\tparametric.setEnabled(false);\n\t\t\t\t}\n\n\t\t\t\tpropertiesPopup.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t} else if (e.isPopupTrigger() && (e.getSource() == consTable || e.getSource() == constantsScroll)) {\n\t\t\t\tconstantsPopup.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t} else if (e.isPopupTrigger() && (e.getSource() == labTable || e.getSource() == labelsScroll)) {\n\t\t\t\tlabelsPopup.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t} else if (e.isPopupTrigger() && (e.getSource() == experiments || e.getSource() == expScroller)) {\n\t\t\t\tdoEnables();\n\t\t\t\tthis.experimentPopup.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic boolean canDoClipBoardAction(Action action)\n\t{\n\t\tif (computing)\n\t\t\treturn false;\n\n\t\t// disable certain actions if any of the selected propeties are currently being edited\n\t\tint[] sel = propList.getSelectedIndices();\n\t\tboolean showDeleters = true;\n\t\tfor (int i = 0; i < sel.length; i++) {\n\t\t\tif (propList.getProperty(sel[i]).isBeingEdited()) {\n\t\t\t\tshowDeleters = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\tif (action == GUIPrism.getClipboardPlugin().getPasteAction()) {\n\t\t\tClipboard clipboard = Toolkit.getDefaultToolkit().getSystemClipboard();\n\t\t\treturn (clipboard.getContents(null) != null);\n\t\t} else if (action == GUIPrism.getClipboardPlugin().getCutAction() || action == GUIPrism.getClipboardPlugin().getDeleteAction()) {\n\t\t\tif (!showDeleters)\n\t\t\t\treturn false;\n\t\t\treturn (propList.getSelectedProperties().size() > 0);\n\t\t} else if (action == GUIPrism.getClipboardPlugin().getCopyAction()) {\n\t\t\treturn (propList.getSelectedProperties().size() > 0);\n\t\t} else if (action == GUIPrism.getClipboardPlugin().getSelectAllAction()) {\n\t\t\treturn true;\n\t\t}\n\n\t\treturn false;\n\t}\n\n\tpublic void mouseReleased(MouseEvent e)\n\t{\n\t\tremoveConstant.setEnabled(consTable.getSelectedRowCount() > 0);\n\t\tremoveLabel.setEnabled(labTable.getSelectedRowCount() > 0);\n\t\tif (!computing) {\n\t\t\tif (e.isPopupTrigger() && e.getSource() == propList) {\n\t\t\t\tint index = propList.locationToIndex(e.getPoint());\n\t\t\t\t// if there are no properties selected, select the one under the popup\n\t\t\t\tif (propList.isSelectionEmpty()) {\n\t\t\t\t\tif (index != -1) {\n\t\t\t\t\t\tpropList.setSelectedIndex(index);\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\t// if the property under the popup is not already selected, select just that one\n\t\t\t\t\tint[] sel = propList.getSelectedIndices();\n\t\t\t\t\tboolean valid = false;\n\t\t\t\t\tfor (int i = 0; i < sel.length; i++) {\n\t\t\t\t\t\tif (sel[i] == index) {\n\t\t\t\t\t\t\tvalid = true;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\tif (!valid) {\n\t\t\t\t\t\tpropList.setSelectedIndex(index);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// disable certain actions if any of the selected propeties are currently being edited\n\t\t\t\tint[] sel = propList.getSelectedIndices();\n\t\t\t\tboolean showDeleters = true;\n\t\t\t\tfor (int i = 0; i < sel.length; i++) {\n\t\t\t\t\tif (propList.getProperty(sel[i]).isBeingEdited()) {\n\t\t\t\t\t\tshowDeleters = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tverifySelected.setEnabled(propList.existsValidSelectedProperties());\n\t\t\t\tsimulate.setEnabled(propList.existsValidSimulatableSelectedProperties());\n\t\t\t\tdetails.setEnabled(propList.existsValidSelectedProperties());\n\t\t\t\teditProperty.setEnabled(propList.getSelectedProperties().size() > 0);\n\t\t\t\tnewExperiment.setEnabled(propList.getNumSelectedProperties() == 1 && propList.getValidSelectedProperties().size() == 1);\n\t\t\t\tparametric.setEnabled(propList.getNumSelectedProperties() == 1 && propList.getValidSelectedProperties().size() == 1);\n\n\t\t\t\tif (showDeleters == false) {\n\t\t\t\t\tsimulate.setEnabled(false);\n\t\t\t\t\tverifySelected.setEnabled(false);\n\t\t\t\t\tdetails.setEnabled(false);\n\t\t\t\t\teditProperty.setEnabled(false);\n\t\t\t\t\tnewExperiment.setEnabled(false);\n\t\t\t\t\tparametric.setEnabled(false);\n\t\t\t\t}\n\n\t\t\t\tpropertiesPopup.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t} else if (e.isPopupTrigger() && (e.getSource() == consTable || e.getSource() == constantsScroll)) {\n\t\t\t\tconstantsPopup.show(e.getComponent(), e.getX(), e.getY());\n\n\t\t\t} else if (e.isPopupTrigger() && (e.getSource() == labTable || e.getSource() == labelsScroll)) {\n\t\t\t\tlabelsPopup.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t} else if (e.isPopupTrigger() && (e.getSource() == experiments || e.getSource() == expScroller)) {\n\t\t\t\tdoEnables();\n\t\t\t\tthis.experimentPopup.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void componentAdded(ContainerEvent e)\n\t{\n\t\t// notify GUIClipboard\n\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t}\n\n\tpublic void componentRemoved(ContainerEvent e)\n\t{\n\t\t// notify GUIClipboard\n\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t}\n\n\t//METHODS TO IMPLEMENT ListSelectionListener INTERFACE\n\tpublic void valueChanged(ListSelectionEvent e)\n\t{\n\t\tArrayList<GUIProperty> selectedProps = propList.getSelectedProperties();\n\n\t\t// disable certain actions if any of the selected properties are currently being edited\n\t\tboolean showDeleters = true;\n\t\tfor (int i = 0; i < selectedProps.size(); i++) {\n\t\t\tif (((GUIProperty) selectedProps.get(i)).isBeingEdited()) {\n\t\t\t\tshowDeleters = false;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\n\t\tverifySelected.setEnabled(propList.existsValidSelectedProperties());\n\t\tsimulate.setEnabled(propList.existsValidSimulatableSelectedProperties());\n\t\tdetails.setEnabled(propList.existsValidSelectedProperties());\n\t\teditProperty.setEnabled(propList.getSelectedProperties().size() > 0);\n\n\t\tif (showDeleters == false) {\n\t\t\tsimulate.setEnabled(false);\n\t\t\tverifySelected.setEnabled(false);\n\t\t\tdetails.setEnabled(false);\n\t\t\teditProperty.setEnabled(false);\n\t\t}\n\n\t\tupdateCommentLabel();\n\n\t\t//Now do the one for the constants table\n\n\t\tremoveConstant.setEnabled(consTable.getSelectedRowCount() > 0);\n\t\tremoveLabel.setEnabled(labTable.getSelectedRowCount() > 0);\n\n\t\t// notify GUIClipboard\n\t\tselectionChangeHandler.notifyListeners(new GUIEvent(1));\n\t}\n\n\t//CONSTRUCTOR HELPER METHODS\n\tJScrollPane constantsScroll, labelsScroll;\n\tJTextArea comLabel;\n\n\tprivate void initComponents()\n\t{\n\t\tsetupActions();\n\t\t//panel\n\t\tJSplitPane mainSplit = new JSplitPane();\n\t\t{\n\t\t\tJPanel left = new JPanel();\n\t\t\t{\n\t\t\t\tleft.setMinimumSize(new java.awt.Dimension(10, 10));\n\t\t\t\tJSplitPane leftSc = new JSplitPane();\n\t\t\t\t{\n\t\t\t\t\tJPanel topLeft = new JPanel();\n\t\t\t\t\t{\n\t\t\t\t\t\tJScrollPane propScroll = new JScrollPane();\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tpropList = new GUIPropertiesList(getPrism(), this);\n\t\t\t\t\t\t\tpropList.addListSelectionListener(this);\n\t\t\t\t\t\t\tpropList.addContainerListener(this);\n\t\t\t\t\t\t\tpropList.setToolTipText(\"Double-click or right-click here to create a new property\");\n\t\t\t\t\t\t\tpropScroll.setViewportView(propList);\n\t\t\t\t\t\t}\n\t\t\t\t\t\tJScrollPane comScroll = new JScrollPane();\n\t\t\t\t\t\tcomLabel = new JTextArea();\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tcomLabel.setRows(2);\n\t\t\t\t\t\t\tcomLabel.setEditable(false);\n\t\t\t\t\t\t\t//comLabel.setPreferredSize(new Dimension(300, 20));\n\t\t\t\t\t\t\t//comLabel.setMinimumSize(new Dimension(10,10));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tcomScroll.setViewportView(comLabel);\n\t\t\t\t\t\ttopLeft.setLayout(new BorderLayout());\n\t\t\t\t\t\ttopLeft.add(propScroll, BorderLayout.CENTER);\n\t\t\t\t\t\ttopLeft.add(comScroll, BorderLayout.SOUTH);\n\t\t\t\t\t\ttopLeft.setBorder(new TitledBorder(\"Properties\"));\n\t\t\t\t\t}\n\t\t\t\t\tJSplitPane bottomLeft = new JSplitPane();\n\t\t\t\t\t{\n\t\t\t\t\t\tconstantsScroll = new JScrollPane();\n\t\t\t\t\t\tconstantsScroll.setToolTipText(\"Double-click or right-click here to create a new constant\");\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tconsTable = new GUIPropConstantList(this);\n\t\t\t\t\t\t\tconsTable.setBackground(Color.white);\n\t\t\t\t\t\t\tconsTable.addMouseListener(this);\n\t\t\t\t\t\t\tconstantsScroll.setViewportView(consTable);\n\t\t\t\t\t\t\tconstantsScroll.addMouseListener(this);\n\t\t\t\t\t\t\tconstantsScroll.setBorder(new TitledBorder(\"Constants\"));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tlabelsScroll = new JScrollPane();\n\t\t\t\t\t\tlabelsScroll.setToolTipText(\"Double-click or right-click here to create a new label\");\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tlabTable = new GUIPropLabelList(this);\n\t\t\t\t\t\t\tlabTable.setBackground(Color.white);\n\t\t\t\t\t\t\tlabTable.addMouseListener(this);\n\t\t\t\t\t\t\tlabelsScroll.setViewportView(labTable);\n\t\t\t\t\t\t\tlabelsScroll.addMouseListener(this);\n\t\t\t\t\t\t\tlabelsScroll.setBorder(new TitledBorder(\"Labels\"));\n\t\t\t\t\t\t}\n\t\t\t\t\t\tbottomLeft.setOrientation(JSplitPane.VERTICAL_SPLIT);\n\t\t\t\t\t\tbottomLeft.setTopComponent(constantsScroll);\n\t\t\t\t\t\tbottomLeft.setBottomComponent(labelsScroll);\n\t\t\t\t\t\tbottomLeft.setDividerLocation(0.5);\n\t\t\t\t\t\tbottomLeft.setDividerSize(5);\n\t\t\t\t\t\tbottomLeft.setResizeWeight(0.5);\n\t\t\t\t\t}\n\t\t\t\t\tleftSc.setOrientation(JSplitPane.VERTICAL_SPLIT);\n\t\t\t\t\tleftSc.setTopComponent(topLeft);\n\t\t\t\t\tleftSc.setBottomComponent(bottomLeft);\n\t\t\t\t\tleftSc.setDividerLocation(0.5);\n\t\t\t\t\tleftSc.setDividerSize(5);\n\t\t\t\t\tleftSc.setResizeWeight(0.5);\n\n\t\t\t\t}\n\t\t\t\tleft.setLayout(new BorderLayout());\n\t\t\t\tleft.add(leftSc, BorderLayout.CENTER);\n\t\t\t}\n\t\t\tJPanel right = new JPanel();\n\t\t\t{\n\t\t\t\tJSplitPane rightSplit = new JSplitPane();\n\t\t\t\t{\n\t\t\t\t\tJPanel topRight = new JPanel();\n\t\t\t\t\t{\n\t\t\t\t\t\tJToolBar stopTool = new JToolBar();\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tJButton b = new JButton(stopExperiment);\n\t\t\t\t\t\t\tb.setToolTipText(\"Stop Current Experiment\");\n\t\t\t\t\t\t\tstopTool.add(b);\n\n\t\t\t\t\t\t\tstopTool.setFloatable(false);\n\t\t\t\t\t\t}\n\t\t\t\t\t\texpScroller = new JScrollPane();\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\texperiments = new GUIExperimentTable(this);\n\t\t\t\t\t\t\texperiments.addMouseListener(this);\n\t\t\t\t\t\t\texpScroller.addMouseListener(this);\n\t\t\t\t\t\t\texpScroller.setViewportView(experiments);\n\t\t\t\t\t\t}\n\t\t\t\t\t\ttopRight.setLayout(new BorderLayout());\n\t\t\t\t\t\ttopRight.add(stopTool, BorderLayout.NORTH);\n\t\t\t\t\t\ttopRight.add(expScroller, BorderLayout.CENTER);\n\t\t\t\t\t}\n\t\t\t\t\tJPanel bottomRight = new JPanel(new GridLayout(1, 1));\n\t\t\t\t\t{\n\t\t\t\t\t\tgraphHandler = new GUIGraphHandler(this.getGUI(), this, true);\n\t\t\t\t\t\tbottomRight.add(graphHandler);\n\n\t\t\t\t\t\tbottomRight.setPreferredSize(new Dimension(300, 300));\n\t\t\t\t\t\t//graphHandler.addGraph();\n\t\t\t\t\t\t//graphHandler.addGraph();\n\t\t\t\t\t}\n\t\t\t\t\trightSplit.setOrientation(JSplitPane.VERTICAL_SPLIT);\n\t\t\t\t\trightSplit.setTopComponent(topRight);\n\t\t\t\t\trightSplit.setBottomComponent(bottomRight);\n\t\t\t\t\trightSplit.setDividerLocation(0.5);\n\t\t\t\t\trightSplit.setDividerSize(5);\n\t\t\t\t\trightSplit.setResizeWeight(0.5);\n\t\t\t\t}\n\n\t\t\t\tright.setLayout(new BorderLayout());\n\t\t\t\tright.setBorder(new TitledBorder(\"Experiments\"));\n\t\t\t\tright.add(rightSplit, BorderLayout.CENTER);\n\t\t\t}\n\n\t\t\tmainSplit.setLeftComponent(left);\n\t\t\tmainSplit.setRightComponent(right);\n\t\t\tmainSplit.setDividerLocation(0.5);\n\t\t\tmainSplit.setOneTouchExpandable(true);\n\t\t\tmainSplit.setResizeWeight(0.5);\n\t\t}\n\n\t\tJPanel topPanel = new JPanel();\n\t\t{\n\t\t\tfileTextField = new JTextField();\n\t\t\t{\n\t\t\t\tfileTextField.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n\t\t\t\tfileTextField.setBorder(new javax.swing.border.EtchedBorder());\n\t\t\t\tfileTextField.setMinimumSize(new java.awt.Dimension(40, 25));\n\t\t\t\tfileTextField.setEditable(false);\n\t\t\t\tfileTextField.setBackground(null);\n\t\t\t}\n\n\t\t\t//progress = new JProgressBar(0, 100);\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\t//topPanel.add(progress, BorderLayout.WEST);\n\t\t\ttopPanel.add(fileTextField, BorderLayout.CENTER);\n\t\t}\n\t\tsetLayout(new BorderLayout());\n\t\tadd(mainSplit, BorderLayout.CENTER);\n\t\tadd(topPanel, BorderLayout.NORTH);\n\t\t//menus\n\t\tpropMenu = new JMenu(\"Properties\");\n\t\t{\n\t\t\tpropMenu.add(newProps);\n\t\t\tpropMenu.add(new JSeparator());\n\t\t\tpropMenu.add(openProps);\n\t\t\tpropMenu.add(insertProps);\n\t\t\tpropMenu.add(new JSeparator());\n\t\t\tpropMenu.add(saveProps);\n\t\t\tpropMenu.add(savePropsAs);\n\t\t\tpropMenu.add(new JSeparator());\n\t\t\tpropMenu.add(verifySelected);\n\t\t\tpropMenu.add(simulate);\n\t\t\tpropMenu.add(newExperiment);\n\t\t\t//propMenu.add(parametric);\n\t\t\tJMenu exportlabelsMenu = new JMenu(\"Export labels\");\n\t\t\texportlabelsMenu.setMnemonic('E');\n\t\t\texportlabelsMenu.setIcon(GUIPrism.getIconFromImage(\"smallExport.png\"));\n\t\t\texportlabelsMenu.add(exportLabelsPlain);\n\t\t\texportlabelsMenu.add(exportModelLabelsPlain);\n\t\t\texportlabelsMenu.add(exportLabelsMatlab);\n\t\t\texportlabelsMenu.add(exportModelLabelsMatlab);\n\t\t\tpropMenu.add(exportlabelsMenu);\n\t\t\tpropMenu.setMnemonic('P');\n\t\t}\n\t\tstratMenu = new JMenu(\"Strategies\");\n\t\t{\n\t\t\tJCheckBoxMenuItem genStratCheckBox = new JCheckBoxMenuItem(generateStrategy);\n\t\t\tgenStratCheckBox.putClientProperty(\"CheckBoxMenuItem.doNotCloseOnMouseClick\", true);\n\t\t\tstratMenu.add(genStratCheckBox);\n\t\t\tstratMenu.add(createStrategyExportMenu());\n\t\t\tstratMenu.add(createStrategyViewMenu());\n\t\t\tstratMenu.add(simulateStrategy);\n\t\t\tstratMenu.setMnemonic('T');\n\t\t}\n\t\tcreatePopups();\n\t\t//file filters\n\t\tpropsFilter = new FileNameExtensionFilter(\"PRISM properties (*.props, *.pctl, *.csl)\", \"props\", \"pctl\", \"csl\");\n\t\ttraFilters = new HashMap<String,FileFilter>();\n\t\ttraFilters.put(\"tra\", new FileNameExtensionFilter(\"Transition matrix files (*.tra)\", \"tra\"));\n\t\ttraFilters.put(\"txt\", new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\"));\n\t\tlabFilters = new HashMap<String,FileFilter>();\n\t\tlabFilters.put(\"lab\", new FileNameExtensionFilter(\"Label files (*.lab)\", \"lab\"));\n\t\tlabFilters.put(\"txt\", new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\"));\n\t\ttextFilter =  new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\");\n\t\tcsvFilter =  new FileNameExtensionFilter(\"Comma-separated values (*.csv)\", \"csv\");\n\t\tmatlabFilter = new FileNameExtensionFilter(\"Matlab files (*.m)\", \"m\");\n\t\tdotFilter = new FileNameExtensionFilter(\"Dot files (*.dot)\", \"dot\");\n\t}\n\n\tprivate JMenu createStrategyExportMenu()\n\t{\n\t\tJMenu exportStrategyMenu = new JMenu(\"Export strategy\");\n\t\texportStrategyMenu.setMnemonic('E');\n\t\texportStrategyMenu.setIcon(GUIPrism.getIconFromImage(\"smallExport.png\"));\n\t\texportStrategyMenu.add(exportStrategyActionsStates);\n\t\texportStrategyMenu.add(exportStrategyActions);\n\t\texportStrategyMenu.add(exportStrategyInducedRestrict);\n\t\texportStrategyMenu.add(exportStrategyInducedReduce);\n\t\texportStrategyMenu.add(exportStrategyInducedDot);\n\t\treturn exportStrategyMenu;\n\t}\n\n\tprivate JMenu createStrategyViewMenu()\n\t{\n\t\tJMenu exportStrategyMenu = new JMenu(\"View strategy\");\n\t\texportStrategyMenu.setMnemonic('V');\n\t\texportStrategyMenu.setIcon(GUIPrism.getIconFromImage(\"smallView.png\"));\n\t\texportStrategyMenu.add(viewStrategyActionsStates);\n\t\texportStrategyMenu.add(viewStrategyActions);\n\t\texportStrategyMenu.add(viewStrategyInducedRestrict);\n\t\texportStrategyMenu.add(viewStrategyInducedReduce);\n\t\treturn exportStrategyMenu;\n\t}\n\n\tprivate void createPopups()\n\t{\n\t\tpropertiesPopup = new JPopupMenu();\n\n\t\tpropertiesPopup.add(editProperty);\n\t\tpropertiesPopup.add(newProperty);\n\t\tpropertiesPopup.add(new JSeparator());\n\t\tpropertiesPopup.add(verifySelected);\n\t\tpropertiesPopup.add(simulate);\n\t\tpropertiesPopup.add(newExperiment);\n\t\t//propertiesPopup.add(parametric);\n\t\tpropertiesPopup.add(details);\n\t\tstratSubMenu = new JMenu(\"Strategies\");\n\t\tstratSubMenu.setMnemonic('S');\n\t\tstratSubMenu.setIcon(GUIPrism.getIconFromImage(\"smallStrategy.png\"));\n\t\tJCheckBoxMenuItem genStratCheckBox = new JCheckBoxMenuItem(generateStrategy);\n\t\tgenStratCheckBox.putClientProperty(\"CheckBoxMenuItem.doNotCloseOnMouseClick\", true);\n\t\tstratSubMenu.add(genStratCheckBox);\n\t\tstratSubMenu.add(createStrategyExportMenu());\n\t\tstratSubMenu.add(createStrategyViewMenu());\n\t\tstratSubMenu.add(simulateStrategy);\n\t\tpropertiesPopup.add(stratSubMenu);\n\t\tpropertiesPopup.add(new JSeparator());\n\t\tpropertiesPopup.add(GUIPrism.getClipboardPlugin().getCutAction());\n\t\tpropertiesPopup.add(GUIPrism.getClipboardPlugin().getCopyAction());\n\t\tpropertiesPopup.add(GUIPrism.getClipboardPlugin().getPasteAction());\n\t\tpropertiesPopup.add(GUIPrism.getClipboardPlugin().getDeleteAction());\n\t\tpropertiesPopup.add(new JSeparator());\n\t\tpropertiesPopup.add(GUIPrism.getClipboardPlugin().getSelectAllAction());\n\n\t\tconstantsPopup = new JPopupMenu();\n\n\t\tconstantsPopup.add(newConstant);\n\t\tconstantsPopup.add(removeConstant);\n\n\t\tlabelsPopup = new JPopupMenu();\n\t\tlabelsPopup.add(newLabel);\n\t\tlabelsPopup.add(removeLabel);\n\n\t\tconsTable.addMouseListener(this);\n\t\tpropList.addMouseListener(this);\n\n\t\texperimentPopup = new JPopupMenu();\n\n\t\texperimentPopup.add(newExperiment);\n\t\texperimentPopup.add(deleteExperiment);\n\t\texperimentPopup.add(new JSeparator());\n\t\texperimentPopup.add(viewResults);\n\t\texperimentPopup.add(plotResults);\n\t\tJMenu exportResultsMenu = new JMenu(\"Export results\");\n\t\texportResultsMenu.setMnemonic('E');\n\t\texportResultsMenu.setIcon(GUIPrism.getIconFromImage(\"smallExport.png\"));\n\t\texportResultsMenu.add(exportResultsListText);\n\t\texportResultsMenu.add(exportResultsListCSV);\n\t\texportResultsMenu.add(exportResultsMatrixText);\n\t\texportResultsMenu.add(exportResultsMatrixCSV);\n\t\texportResultsMenu.add(exportResultsDataFrameCSV);\n\t\texportResultsMenu.add(exportResultsComment);\n\t\texperimentPopup.add(exportResultsMenu);\n\t\tJMenu importResultsMenu = new JMenu(\"Import results\");\n\t\timportResultsMenu.setMnemonic('I');\n\t\timportResultsMenu.setIcon(GUIPrism.getIconFromImage(\"smallAdd.png\"));\n\t\timportResultsMenu.add(importResultsDataFrameCSV);\n\t\texperimentPopup.add(importResultsMenu);\n\t}\n\n\tprivate void setupActions()\n\t{\n\n\t\tnewProps = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_newList();\n\t\t\t}\n\t\t};\n\t\tnewProps.putValue(Action.LONG_DESCRIPTION, \"Clears the current properties list, and the current active properties list.\");\n\t\t//newProps.putValue(Action.SHORT_DESCRIPTION, \"New properties list\");\n\t\tnewProps.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_N);\n\t\tnewProps.putValue(Action.NAME, \"New properties list\");\n\t\tnewProps.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallNew.png\"));\n\t\tnewProps.putValue(Action.ACCELERATOR_KEY,\n\t\t\t\tKeyStroke.getKeyStroke(KeyEvent.VK_N, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask() | InputEvent.SHIFT_MASK));\n\n\t\topenProps = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_open();\n\t\t\t}\n\t\t};\n\t\topenProps.putValue(Action.LONG_DESCRIPTION, \"Opens a properties list, checking that it is valid according to the current parsed model\");\n\t\t//openProps.putValue(Action.SHORT_DESCRIPTION, \"Open properties list\");\n\t\topenProps.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_O);\n\t\topenProps.putValue(Action.NAME, \"Open properties list...\");\n\t\topenProps.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallOpen.png\"));\n\t\topenProps.putValue(Action.ACCELERATOR_KEY,\n\t\t\t\tKeyStroke.getKeyStroke(KeyEvent.VK_O, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask() | InputEvent.SHIFT_MASK));\n\n\t\tsaveProps = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_save();\n\t\t\t}\n\t\t};\n\t\tsaveProps.putValue(Action.LONG_DESCRIPTION,\n\t\t\t\t\"Saves all properties to the current active properties list, if non exists the user is prompted with a dialog.\");\n\t\t// saveProps.putValue(Action.SHORT_DESCRIPTION, \"Save properties list\");\n\t\tsaveProps.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_S);\n\t\tsaveProps.putValue(Action.NAME, \"Save properties list\");\n\t\tsaveProps.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSave.png\"));\n\t\tsaveProps.putValue(Action.ACCELERATOR_KEY,\n\t\t\t\tKeyStroke.getKeyStroke(KeyEvent.VK_S, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask() | InputEvent.SHIFT_MASK));\n\n\t\tsavePropsAs = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_saveAs();\n\t\t\t}\n\t\t};\n\t\tsavePropsAs.putValue(Action.LONG_DESCRIPTION, \"Saves all properties to a new file selected by the user from a dialog.\");\n\t\t//savePropsAs.putValue(Action.SHORT_DESCRIPTION, \"Save properties list As...\");\n\t\tsavePropsAs.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_A);\n\t\tsavePropsAs.putValue(Action.NAME, \"Save properties list as...\");\n\t\tsavePropsAs.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSaveAs.png\"));\n\n\t\tinsertProps = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_insert();\n\t\t\t}\n\t\t};\n\t\tinsertProps.putValue(Action.LONG_DESCRIPTION,\n\t\t\t\t\"Inserts properties from user selected file into the properties list.  The active property file remains the same however.\");\n\t\t//insertProps.putValue(Action.SHORT_DESCRIPTION, \"Insert properties list\");\n\t\tinsertProps.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_I);\n\t\tinsertProps.putValue(Action.NAME, \"Insert properties list...\");\n\t\tinsertProps.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallAdd.png\"));\n\n\t\tsimulate = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_simulateSelected();\n\t\t\t}\n\t\t};\n\t\tsimulate.putValue(Action.LONG_DESCRIPTION, \"Calls the PRISM simulator to approximately model check the selected properties against the parsed model.\");\n\t\tsimulate.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_S);\n\t\tsimulate.putValue(Action.NAME, \"Simulate\");\n\t\tsimulate.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSimulate.png\"));\n\t\tsimulate.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F6, 0));\n\n\t\tdetails = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_detailSelected();\n\t\t\t}\n\t\t};\n\t\tdetails.putValue(Action.LONG_DESCRIPTION, \"Shows the details for the currently selected properties in a dialog box.\");\n\t\tdetails.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_D);\n\t\tdetails.putValue(Action.NAME, \"Show details\");\n\t\tdetails.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDetails.png\"));\n\n\t\tverifySelected = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_verifySelected();\n\t\t\t}\n\t\t};\n\t\tverifySelected\n\t\t\t\t.putValue(\n\t\t\t\t\t\tAction.LONG_DESCRIPTION,\n\t\t\t\t\t\t\"Model checks the selected properties against the model that is built.  If there is no built model, the parsed model is automatically built.  If the parsed model has changed since the last build, the user is prompted as to whether they wish to re-build the model.  If the model text has been modified since the last build, the user is asked whether they want to re-parse and re-build.\");\n\t\t//verifySelected.putValue(Action.SHORT_DESCRIPTION, \"Verify Selected Properties\");\n\t\tverifySelected.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_V);\n\t\tverifySelected.putValue(Action.NAME, \"Verify\");\n\t\tverifySelected.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallTick.png\"));\n\t\tverifySelected.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F5, 0));\n\n\t\tnewProperty = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_newProperty();\n\t\t\t}\n\t\t};\n\t\tnewProperty.putValue(Action.LONG_DESCRIPTION, \"Brings up a dialog to add a new property to the list.\");\n\t\tnewProperty.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_D);\n\t\tnewProperty.putValue(Action.NAME, \"Add\");\n\t\tnewProperty.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallAdd.png\"));\n\n\t\teditProperty = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_editProperty();\n\t\t\t}\n\t\t};\n\t\teditProperty.putValue(Action.LONG_DESCRIPTION, \"Brings up a dialog to edit a selected property.\");\n\t\teditProperty.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_E);\n\t\teditProperty.putValue(Action.NAME, \"Edit\");\n\t\teditProperty.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallEdit.png\"));\n\n\t\tgenerateStrategy = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tBoolean sel = (Boolean) getValue(Action.SELECTED_KEY);\n\t\t\t\tif (sel != null) {\n\t\t\t\t\tgetGUI().getPrism().setGenStrat(sel.booleanValue());\n\t\t\t\t}\n\t\t\t}\n\t\t};\n\t\tgenerateStrategy.putValue(Action.SELECTED_KEY, getPrism().getGenStrat());\n\t\tgenerateStrategy.putValue(Action.LONG_DESCRIPTION, \"Whether or not strategy generation is enabled\");\n\t\tgenerateStrategy.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_G);\n\t\tgenerateStrategy.putValue(Action.NAME, \"Generate strategy\");\n\t\tgenerateStrategy.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallBuild.png\"));\n\t\t\n\t\texportStrategyActions = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportStrategy(new StrategyExportOptions(StrategyExportType.ACTIONS).setShowStates(false));\n\t\t\t}\n\t\t};\n\t\texportStrategyActions.putValue(Action.LONG_DESCRIPTION, \"Export the current strategy to a file as a list of actions\");\n\t\texportStrategyActions.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_C);\n\t\texportStrategyActions.putValue(Action.NAME, \"Action list\");\n\t\texportStrategyActions.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportStrategyActionsStates = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportStrategy(new StrategyExportOptions(StrategyExportType.ACTIONS).setShowStates(true));\n\t\t\t}\n\t\t};\n\t\texportStrategyActionsStates.putValue(Action.LONG_DESCRIPTION, \"Export the current strategy to a file as a list of actions (with states)\");\n\t\texportStrategyActionsStates.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_A);\n\t\texportStrategyActionsStates.putValue(Action.NAME, \"Action list (with states)\");\n\t\texportStrategyActionsStates.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\texportStrategyInducedRestrict = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportStrategy(new StrategyExportOptions(StrategyExportType.INDUCED_MODEL).setMode(StrategyExportOptions.InducedModelMode.RESTRICT));\n\t\t\t}\n\t\t};\n\t\texportStrategyInducedRestrict.putValue(Action.LONG_DESCRIPTION, \"Export the (restricted) model induced by the current strategy to a transitions file\");\n\t\texportStrategyInducedRestrict.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_M);\n\t\texportStrategyInducedRestrict.putValue(Action.NAME, \"Induced model (restricted)\");\n\t\texportStrategyInducedRestrict.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportStrategyInducedReduce = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportStrategy(new StrategyExportOptions(StrategyExportType.INDUCED_MODEL).setMode(StrategyExportOptions.InducedModelMode.REDUCE));\n\t\t\t}\n\t\t};\n\t\texportStrategyInducedReduce.putValue(Action.LONG_DESCRIPTION, \"Export the (reduced) model induced by the current strategy to a transitions file\");\n\t\texportStrategyInducedReduce.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_R);\n\t\texportStrategyInducedReduce.putValue(Action.NAME, \"Induced model (reduced)\");\n\t\texportStrategyInducedReduce.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportStrategyInducedDot = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportStrategy(StrategyExportType.DOT_FILE);\n\t\t\t}\n\t\t};\n\t\texportStrategyInducedDot.putValue(Action.LONG_DESCRIPTION, \"Export the model induced by the current strategy to a Dot file\");\n\t\texportStrategyInducedDot.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_D);\n\t\texportStrategyInducedDot.putValue(Action.NAME, \"Dot file\");\n\t\texportStrategyInducedDot.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileDot.png\"));\n\n\t\tviewStrategyActions = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewStrategy(new StrategyExportOptions(StrategyExportType.ACTIONS).setShowStates(false));\n\t\t\t}\n\t\t};\n\t\tviewStrategyActions.putValue(Action.LONG_DESCRIPTION, \"Print the current strategy to the log as a list of actions\");\n\t\tviewStrategyActions.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_C);\n\t\tviewStrategyActions.putValue(Action.NAME, \"Action list\");\n\t\tviewStrategyActions.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\tviewStrategyActionsStates = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewStrategy(new StrategyExportOptions(StrategyExportType.ACTIONS).setShowStates(true));\n\t\t\t}\n\t\t};\n\t\tviewStrategyActionsStates.putValue(Action.LONG_DESCRIPTION, \"Print the current strategy to the log as a list of actions (with states)\");\n\t\tviewStrategyActionsStates.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_A);\n\t\tviewStrategyActionsStates.putValue(Action.NAME, \"Action list (with states)\");\n\t\tviewStrategyActionsStates.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\tviewStrategyInducedRestrict = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewStrategy(new StrategyExportOptions(StrategyExportType.INDUCED_MODEL).setMode(StrategyExportOptions.InducedModelMode.RESTRICT));\n\t\t\t}\n\t\t};\n\t\tviewStrategyInducedRestrict.putValue(Action.LONG_DESCRIPTION, \"Print the (restricted) model induced by the current strategy to the log\");\n\t\tviewStrategyInducedRestrict.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_M);\n\t\tviewStrategyInducedRestrict.putValue(Action.NAME, \"Induced model (restricted)\");\n\t\tviewStrategyInducedRestrict.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\tviewStrategyInducedReduce = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewStrategy(new StrategyExportOptions(StrategyExportType.INDUCED_MODEL).setMode(StrategyExportOptions.InducedModelMode.REDUCE));\n\t\t\t}\n\t\t};\n\t\tviewStrategyInducedReduce.putValue(Action.LONG_DESCRIPTION, \"Print the (reduced) model induced by the current strategy to the log\");\n\t\tviewStrategyInducedReduce.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_R);\n\t\tviewStrategyInducedReduce.putValue(Action.NAME, \"Induced model (reduced)\");\n\t\tviewStrategyInducedReduce.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\tsimulateStrategy = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tsimulator.tabToFront();\n\t\t\t\tsimulator.a_newPath(false);\n\t\t\t}\n\t\t};\n\t\tsimulateStrategy.putValue(Action.LONG_DESCRIPTION, \"Examine the current strategy in the simulator\");\n\t\tsimulateStrategy.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_S);\n\t\tsimulateStrategy.putValue(Action.NAME, \"Simulate strategy\");\n\t\tsimulateStrategy.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallSimulate.png\"));\n\n\t\tnewConstant = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_addConstant();\n\t\t\t}\n\t\t};\n\t\tnewConstant.putValue(Action.LONG_DESCRIPTION, \"Adds a new constant to the constants list\");\n\t\tnewConstant.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_D);\n\t\tnewConstant.putValue(Action.NAME, \"Add constant\");\n\t\tnewConstant.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallAdd.png\"));\n\n\t\tremoveConstant = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_removeSelectedConstants();\n\t\t\t}\n\t\t};\n\t\tremoveConstant.putValue(Action.LONG_DESCRIPTION, \"Deletes selected constants\");\n\t\tremoveConstant.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_D);\n\t\tremoveConstant.putValue(Action.NAME, \"Delete constant\");\n\t\tremoveConstant.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDelete.png\"));\n\n\t\tnewLabel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_addLabel();\n\t\t\t}\n\t\t};\n\t\tnewLabel.putValue(Action.LONG_DESCRIPTION, \"Adds a new Label to the Labels list\");\n\t\tnewLabel.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_D);\n\t\tnewLabel.putValue(Action.NAME, \"Add label\");\n\t\tnewLabel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallAdd.png\"));\n\n\t\tremoveLabel = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_removeSelectedLabels();\n\t\t\t}\n\t\t};\n\t\tremoveLabel.putValue(Action.LONG_DESCRIPTION, \"Deletes selected Labels\");\n\t\tremoveLabel.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_D);\n\t\tremoveLabel.putValue(Action.NAME, \"Delete label\");\n\t\tremoveLabel.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDelete.png\"));\n\n\t\tnewExperiment = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_newExperiment();\n\t\t\t}\n\t\t};\n\t\tnewExperiment.putValue(Action.LONG_DESCRIPTION, \"Creates a new experiment\");\n\t\tnewExperiment.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_N);\n\t\tnewExperiment.putValue(Action.NAME, \"New experiment\");\n\t\tnewExperiment.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallExperiment.png\"));\n\t\tnewExperiment.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F7, 0));\n\n\t\tdeleteExperiment = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_deleteExperiment();\n\t\t\t}\n\t\t};\n\t\tdeleteExperiment.putValue(Action.LONG_DESCRIPTION, \"Deletes the selected experiment\");\n\t\tdeleteExperiment.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_D);\n\t\tdeleteExperiment.putValue(Action.NAME, \"Delete experiment\");\n\t\tdeleteExperiment.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDelete.png\"));\n\n\t\tviewResults = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_viewResults();\n\t\t\t}\n\t\t};\n\t\tviewResults.putValue(Action.LONG_DESCRIPTION, \"View the results of this experiment\");\n\t\tviewResults.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_V);\n\t\tviewResults.putValue(Action.NAME, \"View results\");\n\t\tviewResults.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallView.png\"));\n\n\t\tplotResults = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_plotResults();\n\t\t\t}\n\t\t};\n\t\tplotResults.putValue(Action.LONG_DESCRIPTION, \"Plot the results of this experiment in a graph series\");\n\t\tplotResults.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_P);\n\t\tplotResults.putValue(Action.NAME, \"Plot results\");\n\t\tplotResults.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileGraph.png\"));\n\n\t\tparametric = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_newExperiment();\n\t\t\t}\n\t\t};\n\t\tparametric.putValue(Action.LONG_DESCRIPTION, \"Perform parametric model checking\");\n\t\tparametric.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_P);\n\t\tparametric.putValue(Action.NAME, \"Parametric\");\n\t\tparametric.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileGraph.png\"));\n\n\t\texportResultsListText = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportResults(ResultsExportShape.LIST_PLAIN);\n\t\t\t}\n\t\t};\n\t\texportResultsListText.putValue(Action.LONG_DESCRIPTION, \"Export the results of this experiment as list to a plain text file\");\n\t\texportResultsListText.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_L);\n\t\texportResultsListText.putValue(Action.NAME, \"List (plain text)\");\n\t\texportResultsListText.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallList.png\"));\n\n\t\texportResultsListCSV = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportResults(ResultsExportShape.LIST_CSV);\n\t\t\t}\n\t\t};\n\t\texportResultsListCSV.putValue(Action.LONG_DESCRIPTION, \"Export the results of this experiment as list to a CSV file\");\n\t\texportResultsListCSV.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_L);\n\t\texportResultsListCSV.putValue(Action.NAME, \"List (CSV)\");\n\t\texportResultsListCSV.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallList.png\"));\n\n\t\texportResultsMatrixText = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportResults(ResultsExportShape.MATRIX_PLAIN);\n\t\t\t}\n\t\t};\n\t\texportResultsMatrixText.putValue(Action.LONG_DESCRIPTION, \"Export the results of this experiment as matrix to a plain text file\");\n\t\texportResultsMatrixText.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_M);\n\t\texportResultsMatrixText.putValue(Action.NAME, \"Matrix (plain text)\");\n\t\texportResultsMatrixText.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportResultsMatrixCSV = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportResults(ResultsExportShape.MATRIX_CSV);\n\t\t\t}\n\t\t};\n\t\texportResultsMatrixCSV.putValue(Action.LONG_DESCRIPTION, \"Export the results of this experiment as matrix to a CSV file\");\n\t\texportResultsMatrixCSV.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_M);\n\t\texportResultsMatrixCSV.putValue(Action.NAME, \"Matrix (CSV)\");\n\t\texportResultsMatrixCSV.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallMatrix.png\"));\n\n\t\texportResultsDataFrameCSV = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportResults(ResultsExportShape.DATA_FRAME);\n\t\t\t}\n\t\t};\n\t\texportResultsDataFrameCSV.putValue(Action.LONG_DESCRIPTION, \"Export the results of this experiment as data frame to a CSV file\");\n\t\texportResultsDataFrameCSV.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_F);\n\t\texportResultsDataFrameCSV.putValue(Action.NAME, \"Data Frame (CSV)\");\n\t\texportResultsDataFrameCSV.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDataFrame.png\"));\n\n\t\texportResultsComment = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportResults(ResultsExportShape.COMMENT);\n\t\t\t}\n\t\t};\n\t\texportResultsComment.putValue(Action.LONG_DESCRIPTION, \"Export the results of this experiment as comment in a properties file\");\n\t\texportResultsComment.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_C);\n\t\texportResultsComment.putValue(Action.NAME, \"Comment\");\n\t\texportResultsComment.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallComment.png\"));\n\n\t\timportResultsDataFrameCSV = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_importResults(ResultsExportShape.DATA_FRAME);\n\t\t\t}\n\t\t};\n\t\timportResultsDataFrameCSV.putValue(Action.LONG_DESCRIPTION, \"Import results of an experiment from a data frame in a CSV file\");\n\t\timportResultsDataFrameCSV.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_F);\n\t\timportResultsDataFrameCSV.putValue(Action.NAME, \"Data Frame (CSV)\");\n\t\timportResultsDataFrameCSV.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallDataFrame.png\"));\n\n\t\texportLabelsPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportLabels(ModelExportTask.LabelExportSet.EXTRA, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportLabelsPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the property file's labels and their satisfying states to a plain text file\");\n\t\texportLabelsPlain.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_P);\n\t\texportLabelsPlain.putValue(Action.NAME, \"Plain text file\");\n\t\texportLabelsPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileText.png\"));\n\n\t\texportModelLabelsPlain = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportLabels(ModelExportTask.LabelExportSet.ALL, ModelExportFormat.EXPLICIT);\n\t\t\t}\n\t\t};\n\t\texportModelLabelsPlain.putValue(Action.LONG_DESCRIPTION, \"Exports the model and property file's labels and their satisfying states to a plain text file\");\n\t\texportModelLabelsPlain.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_L);\n\t\texportModelLabelsPlain.putValue(Action.NAME, \"Plain text file (+ model labels)\");\n\t\texportModelLabelsPlain.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileText.png\"));\n\n\t\texportLabelsMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportLabels(ModelExportTask.LabelExportSet.EXTRA, ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportLabelsMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the property file's labels and their satisfying states to a Matlab file\");\n\t\texportLabelsMatlab.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_M);\n\t\texportLabelsMatlab.putValue(Action.NAME, \"Matlab file\");\n\t\texportLabelsMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileMatlab.png\"));\n\n\t\texportModelLabelsMatlab = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportLabels(ModelExportTask.LabelExportSet.ALL, ModelExportFormat.MATLAB);\n\t\t\t}\n\t\t};\n\t\texportModelLabelsMatlab.putValue(Action.LONG_DESCRIPTION, \"Exports the model and property file's labels and their satisfying states to a Matlab file\");\n\t\texportModelLabelsMatlab.putValue(Action.MNEMONIC_KEY, KeyEvent.VK_A);\n\t\texportModelLabelsMatlab.putValue(Action.NAME, \"Matlab file (+ model labels)\");\n\t\texportModelLabelsMatlab.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileMatlab.png\"));\n\n\t\tstopExperiment = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_stopExperiment();\n\t\t\t}\n\t\t};\n\t\tstopExperiment.putValue(Action.LONG_DESCRIPTION, \"Stops the Experiment that is currently running\");\n\t\tstopExperiment.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStop.png\"));\n\t\tstopExperiment.setEnabled(false);\n\t}\n\n\t/**\n\t * Getter for property propList.\n\t * @return Value of property propList.\n\t */\n\tpublic userinterface.properties.GUIPropertiesList getPropList()\n\t{\n\t\treturn propList;\n\t}\n\n\t/**\n\t * Getter for property consTable.\n\t * @return Value of property consTable.\n\t */\n\tpublic userinterface.properties.GUIPropConstantList getConsTable()\n\t{\n\t\treturn consTable;\n\t}\n\n\t/**\n\t * Getter for property labTable.\n\t * @return Value of property labTable.\n\t */\n\tpublic userinterface.properties.GUIPropLabelList getLabTable()\n\t{\n\t\treturn labTable;\n\t}\n\n\tpublic void notifySettings(PrismSettings settings)\n\t{\n\t\tdisplayFontFast = settings.getFontColorPair(PrismSettings.PROPERTIES_FONT).f;\n\t\tsetFont(displayFontFast);\n\t\tbackgroundFast = new Color(202, 225, 255);\n\t\twarningFast = settings.getColor(PrismSettings.PROPERTIES_WARNING_COLOUR);\n\t\trepaint();\n\t}\n\n\tpublic static DataFlavor getGUIClipboardPropertiesDataFlavor()\n\t{\n\t\treturn new DataFlavor(GUIClipboardProperties.class, \"PRISM Property List\");\n\t}\n\n\t/**\n\t * A class that allows sets of properties to be put on the clipboard.\n\t */\n\tpublic class GUIClipboardProperties implements Transferable\n\t{\n\t\tprivate ArrayList<GUIProperty> listOfProperties;\n\t\tprivate StringSelection stringRepresentation;\n\n\t\tpublic GUIClipboardProperties(ArrayList<GUIProperty> listOfProperties)\n\t\t{\n\t\t\tthis.listOfProperties = listOfProperties;\n\t\t\tString tmpString = \"\";\n\t\t\tfor (int i = 0; i < listOfProperties.size(); i++) {\n\t\t\t\tGUIProperty gp = listOfProperties.get(i);\n\t\t\t\tif (gp.getComment().trim().length() > 0) {\n\t\t\t\t\ttmpString += \"//\" + gp.getComment() + \"\\n\";\n\t\t\t\t}\n\t\t\t\ttmpString += gp.getPropString();\n\t\t\t\tif (i != listOfProperties.size() - 1)\n\t\t\t\t\ttmpString += \"\\n\";\n\t\t\t}\n\n\t\t\tstringRepresentation = new StringSelection(tmpString);\n\t\t}\n\n\t\tpublic Object getTransferData(DataFlavor flavor) throws UnsupportedFlavorException, IOException\n\t\t{\n\t\t\tif (flavor.getRepresentationClass() == this.getClass()) {\n\t\t\t\treturn this;\n\t\t\t} else {\n\t\t\t\treturn this.stringRepresentation.getTransferData(flavor);\n\t\t\t}\n\t\t}\n\n\t\tpublic DataFlavor[] getTransferDataFlavors()\n\t\t{\n\t\t\tDataFlavor[] stringFlavors = stringRepresentation.getTransferDataFlavors();\n\n\t\t\tDataFlavor[] allFlavors = new DataFlavor[stringFlavors.length + 1];\n\t\t\tallFlavors[0] = GUIMultiProperties.getGUIClipboardPropertiesDataFlavor();\n\n\t\t\tfor (int i = 0; i < stringFlavors.length; i++) {\n\t\t\t\tallFlavors[i + 1] = stringFlavors[i];\n\t\t\t}\n\n\t\t\treturn allFlavors;\n\t\t}\n\n\t\tpublic boolean isDataFlavorSupported(DataFlavor flavor)\n\t\t{\n\t\t\treturn (stringRepresentation.isDataFlavorSupported(flavor) || flavor.equals(GUIMultiProperties.getGUIClipboardPropertiesDataFlavor()));\n\t\t}\n\n\t\tpublic ArrayList<GUIProperty> getProperties()\n\t\t{\n\t\t\treturn listOfProperties;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIPropConstantList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.util.*;\nimport java.awt.*;\nimport javax.swing.*;\nimport javax.swing.table.*;\n\nimport parser.ast.*;\nimport parser.type.*;\nimport prism.*;\n\npublic class GUIPropConstantList extends JTable\n{\n\t\n\tprivate PropConstantModel theModel;\n\tprivate GUIMultiProperties parent;\n\t\n\t/** Creates a new instance of GUIPropConstantList */\n\tpublic GUIPropConstantList(GUIMultiProperties parent)\n\t{\n\t\tsuper();\n\t\tthis.parent = parent;\n\t\ttheModel = new PropConstantModel();\n\t\tsetModel(theModel);\n\t\tsetEditorAndRenderer();\n\t}\n\t\n\t/** Override set font to update row heights at same time */\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\tsetRowHeight(getFontMetrics(font).getHeight() + 4);\n\t}\n\n\tprotected void setEditorAndRenderer()\n\t{\n\t\tJComboBox typeChooser = new JComboBox();\n\t\ttypeChooser.addItem(new String(\"int\"));\n\t\ttypeChooser.addItem(new String(\"double\"));\n\t\ttypeChooser.addItem(new String(\"bool\"));\n\t\tTableCellEditor typeEditor = new DefaultCellEditor(typeChooser);\n\t\tTableColumn column = getColumnModel().getColumn(1);\n\t\tcolumn.setCellEditor(typeEditor);\n\t\ttry { setDefaultRenderer(Class.forName(\"java.lang.Object\"), new TheCellRenderer()); } catch (ClassNotFoundException e) {}\n\t}\n\t\n\tpublic void correctEditors()\n\t{\n\t\tif(this.getCellEditor() != null)\n\t\t{\n\t\t\tgetCellEditor().stopCellEditing();\n\t\t}\n\t}\n\t\n\tpublic void newList()\n\t{\n\t\ttheModel.newList();\n\t\tsetEditorAndRenderer();\n\t}\n\t\n\tpublic int getNumConstants()\n\t{\n\t\treturn theModel.getNumConstants();\n\t}\n\t\n\tpublic void addNewConstant()\n\t{\n\t\ttheModel.addConstant();\n\t\ttheModel.validateConstants();\n\t}\n\t\n\tpublic void removeConstant(int index)\n\t{\n\t\t// Stop any editing that i staking place\n\t\t// (in case it is on cells we are about to delete)\n\t\tCellEditor ce = getCellEditor();\n\t\tif (ce != null) {\n\t\t\tce.cancelCellEditing();\n\t\t}\n\t\t// do the remove\n\t\ttheModel.removeConstant(index);\n\t\ttheModel.validateConstants();\n\t}\n\t\n\tpublic void addPropertiesFile(PropertiesFile pf)\n\t{\n\t\tConstantList cl = pf.getConstantList();\n\t\tint i, n;\n\t\tExpression expr;\n\t\tn = cl.size();\n\t\tfor(i = 0; i < n; i++)\n\t\t{\n\t\t\texpr = cl.getConstant(i);\n\t\t\ttheModel.addConstant(new GUIConstant(parent, cl.getConstantName(i), (expr==null)?\"\":expr.toString(), cl.getConstantType(i)));\n\t\t}\n\t\t//  Don't validate until all constants added (might be dependent on each other)\n\t\ttheModel.validateConstants();\n\t}\n\t\n\t/** Validate the constant list\n\t    NB: Don't call it \"validate()\" to avoid overwriting Swing methods */\n\t\n\tpublic void validateConstants()\n\t{\n\t\ttheModel.validateConstants();\n\t}\n\t\n\t/** Is the constant list valid? */\t\n\t// Changed: isValid is a method of java.awt.Component\n\tpublic boolean isConstantListValid()\n\t{\n\t\tif (theModel.error != null) return false;\n\t\tint i, n;\n\t\tn = theModel.getNumConstants();\n\t\tfor(i = 0; i < n; i++) {\n\t\t\tif (!theModel.getConstant(i).isParseable()) return false;\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t/** Return string representing PRISM code for all constants in this list */\n\t\n\tpublic String getConstantsString()\n\t{\n\t\treturn theModel.toString();\n\t}\n\t\n\t/** Return string representing PRISM code for all valid constants in this list */\n\t\n\tpublic String getValidConstantsString()\n\t{\n\t\treturn theModel.validToString();\n\t}\n\t\n\t/* Table model for the constant list */\n\t\n\tclass PropConstantModel extends AbstractTableModel\n\t{\n\t\tArrayList constants; // The list of constants\n\t\tint conCount; // Counter used to generate new default names for constants\n\t\tException error; // Any error that occurs when all constants are parsed together\n\t\t\n\t\tpublic PropConstantModel()\n\t\t{\n\t\t\tconstants = new ArrayList();\n\t\t\tconCount = 0;\n\t\t\terror = null;\n\t\t}\n\t\t\n\t\t/* Acesssor methods */\n\t\t\n\t\tpublic int getNumConstants()\n\t\t{\n\t\t\treturn constants.size();\n\t\t}\n\t\t\n\t\tpublic GUIConstant getConstant(int i)\n\t\t{\n\t\t\treturn (GUIConstant)constants.get(i);\n\t\t}\n\t\t\n\t\tpublic Exception getError()\n\t\t{\n\t\t\treturn error;\n\t\t}\n\t\t\n\t\tpublic int getRowCount()\n\t\t{\n\t\t\treturn constants.size();\n\t\t}\n\t\t\n\t\tpublic int getColumnCount()\n\t\t{\n\t\t\treturn 3;\n\t\t}\n\t\t\n\t\tpublic Object getValueAt(int row, int column)\n\t\t{\n\t\t\tGUIConstant con = getConstant(row);\n\t\t\tswitch(column)\n\t\t\t{\n\t\t\t\tcase 0: return con.name;\n\t\t\t\tcase 1: return con.type.getTypeString();\n\t\t\t\tcase 2: return con.constant;\n\t\t\t\tdefault: return \"\";\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic String getColumnName(int columnIndex)\n\t\t{\n\t\t\tswitch(columnIndex)\n\t\t\t{\n\t\t\t\tcase 0: return \"Name\";\n\t\t\t\tcase 1: return \"Type\";\n\t\t\t\tcase 2: return \"Value\";\n\t\t\t\tdefault: return \"\";\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic boolean isCellEditable(int row, int column)\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t/** Return string representing PRISM code for all constants in this table model */\n\t\t\n\t\tpublic String toString()\n\t\t{\n\t\t\tString str = \"\";\n\t\t\t\n\t\t\tfor(int i = 0; i < getNumConstants(); i++)\n\t\t\t{\n\t\t\t\tGUIConstant gc = getConstant(i);\n\t\t\t\tstr+=gc.toString()+\"\\n\";\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\t\t\n\t\t/** Return string representing PRISM code for all valid constants in this table model */\n\t\t\n\t\tpublic String validToString()\n\t\t{\n\t\t\tif (error != null) return \"\";\n\t\t\telse return parseableToString();\n\t\t}\n\t\t\n\t\t/** Return string representing PRISM code for all parseable constants in this table model */\n\t\t\n\t\tpublic String parseableToString()\n\t\t{\n\t\t\tint i, n;\n\t\t\tGUIConstant gc;\n\t\t\tString str = \"\";\n\t\t\tn = getNumConstants();\n\t\t\tfor(i = 0; i < n; i++) {\n\t\t\t\tgc = getConstant(i);\n\t\t\t\tif (gc.isParseable()) str+=gc.toString()+\"\\n\";\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\t\t\n\t\t/* Methods to modify table model */\n\t\t\n\t\tpublic void newList()\n\t\t{\n\t\t\tconstants = new ArrayList();\n\t\t\tfireTableStructureChanged();\n\t\t\tparent.constantListChanged();\n\t\t}\n\t\t\n\t\t/** Add a new (default-valued) constant to the list.\n\t\t    You should call validateConstants() after calling this. */\n\t\t\n\t\tpublic void addConstant()\n\t\t{\n\t\t\taddConstant(new GUIConstant(parent, \"C\"+conCount, \"\", TypeInt.getInstance()));\n\t\t\tconCount++;\n\t\t}\n\t\t\n\t\t/** Add a new constant to the list.\n\t\t    You should call validateConstants() after calling this. */\n\t\t\n\t\tpublic void addConstant(GUIConstant cons)\n\t\t{\n\t\t\tcons.parse();\n\t\t\tconstants.add(cons);\n\t\t\tfireTableRowsInserted(constants.size()-1, constants.size()-1);\n\t\t\tparent.constantListChanged();\n\t\t}\n\t\t\n\t\t/** Remove a constant from the list.\n\t\t    You should call validateConstants() after calling this. */\n\t\t\n\t\tpublic void removeConstant(int index)\n\t\t{\n\t\t\tconstants.remove(index);\n\t\t\tfireTableRowsDeleted(index,index);\n\t\t\tparent.constantListChanged();\n\t\t}\n\t\t\n\t\t/** This is called directly by the GUI (when the table is edited) */\n\t\t\n\t\tpublic void setValueAt(Object aValue, int rowIndex, int columnIndex)\n\t\t{\n\t\t\tGUIConstant gc = getConstant(rowIndex);\n\t\t\tswitch(columnIndex)\n\t\t\t{\n\t\t\t\tcase 0:\n\t\t\t\t{\n\t\t\t\t\tif(!gc.name.equals((String)aValue))\n\t\t\t\t\t{\n\t\t\t\t\t\tgc.name = (String)aValue;\n\t\t\t\t\t\tgc.parse();\n\t\t\t\t\t\tvalidateConstants();\n\t\t\t\t\t\tparent.constantListChanged();\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tcase 1:\n\t\t\t\t{\n\t\t\t\t\tType newType = TypeInt.getInstance();\n\t\t\t\t\tif(((String)aValue).equals(\"double\"))newType = TypeDouble.getInstance();\n\t\t\t\t\telse if(((String)aValue).equals(\"bool\"))newType = TypeBool.getInstance();\n\t\t\t\t\tif(newType != gc.type) // if there was a change\n\t\t\t\t\t{\n\t\t\t\t\t\tgc.type = newType;\n\t\t\t\t\t\tgc.parse();\n\t\t\t\t\t\tvalidateConstants();\n\t\t\t\t\t\tparent.constantListChanged();\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tcase 2:\n\t\t\t\t{\n\t\t\t\t\tif (!gc.constant.equals((String)aValue))\n\t\t\t\t\t{\n\t\t\t\t\t\tgc.constant = (String)aValue;\n\t\t\t\t\t\tgc.parse();\n\t\t\t\t\t\tvalidateConstants();\n\t\t\t\t\t\tparent.constantListChanged();\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t/** Validate the constant list\n\t\t    NB: Don't call it \"validate()\" to avoid overwriting Swing methods */\n\t\t\n\t\tpublic void validateConstants()\n\t\t{\n\t\t\ttry {\n\t\t\t\terror = null;\n\t\t\t\tparent.getPrism().parsePropertiesString(parseableToString());\n\t\t\t}\n\t\t\tcatch (PrismException e) {\n\t\t\t\terror = e;\n\t\t\t}\n\t\t\tfireTableDataChanged();\n\t\t}\n\t}\n\t\n\tclass TheCellRenderer extends DefaultTableCellRenderer\n\t{\n\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) \n\t\t{\n\t\t\tComponent cell = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);\n\t\t\tGUIConstant gc = theModel.getConstant(row);\n\t\t\t// If the constant has a parse error, show that\n\t\t\tif (!gc.isParseable()) {\n\t\t\t\tsetBackground(isSelected ? parent.getSelectionColor() : parent.getWarningColor());\n\t\t\t\tsetForeground(Color.red);\n\t\t\t\tsetToolTipText(gc.parseError.toString());\n\t\t\t}\n\t\t\t// If not but there is a \"global\" error for the whole list, show that\n\t\t\telse if (theModel.error != null) {\n\t\t\t\tsetBackground(isSelected ? parent.getSelectionColor() : parent.getWarningColor());\n\t\t\t\tsetForeground(Color.red);\n\t\t\t\tsetToolTipText(theModel.error.toString());\n\t\t\t}\n\t\t\t// Otherwise everything is fine\n\t\t\telse {\n\t\t\t\tsetBackground(isSelected ? parent.getSelectionColor() : Color.white);\n\t\t\t\tsetForeground(Color.black);\n\t\t\t\tsetToolTipText(gc.toString());\n\t\t\t}\n\t\t\treturn cell;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIPropLabelList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.awt.Color;\nimport java.awt.Component;\nimport java.awt.Font;\nimport java.util.ArrayList;\n\nimport javax.swing.CellEditor;\nimport javax.swing.JTable;\nimport javax.swing.table.AbstractTableModel;\nimport javax.swing.table.DefaultTableCellRenderer;\n\nimport parser.ast.LabelList;\nimport parser.ast.PropertiesFile;\nimport prism.PrismException;\n\npublic class GUIPropLabelList extends JTable\n{\n\t\n\tprivate PropLabelModel theModel;\n\tprivate GUIMultiProperties parent;\n\t\n\t/** Creates a new instance of GUIPropLabelList */\n\tpublic GUIPropLabelList(GUIMultiProperties parent)\n\t{\n\t\tsuper();\n\t\tthis.parent = parent;\n\t\ttheModel = new PropLabelModel();\n\t\tsetModel(theModel);\n\t\ttry { setDefaultRenderer(Class.forName(\"java.lang.Object\"), new TheCellRenderer()); } catch (ClassNotFoundException e) {}\n\t}\n\t\n\t/** Override set font to update row heights at same time */\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\tsetRowHeight(getFontMetrics(font).getHeight() + 4);\n\t}\n\n\tpublic void correctEditors()\n\t{\n\t\tif(this.getCellEditor() != null)\n\t\t{\n\t\t\tgetCellEditor().stopCellEditing();\n\t\t}\n\t}\n\t\n\tpublic void newList()\n\t{\n\t\ttheModel.newList();\n\t}\n\t\n\tpublic int getNumLabels()\n\t{\n\t\treturn theModel.getNumLabels();\n\t}\n\t\n\tpublic GUILabel getLabel(int i)\n\t{\n\t    return theModel.getLabel(i);\n\t}\n\t\n\tpublic void addNewLabel()\n\t{\n\t\ttheModel.addLabel();\n\t\ttheModel.validateLabels();\n\t}\n\t\n\tpublic void removeLabel(int index)\n\t{\n\t\t// Stop any editing that i staking place\n\t\t// (in case it is on cells we are about to delete)\n\t\tCellEditor ce = getCellEditor();\n\t\tif (ce != null) {\n\t\t\tce.cancelCellEditing();\n\t\t}\n\t\t// do the remove\n\t\ttheModel.removeLabel(index);\n\t\ttheModel.validateLabels();\n\t}\n\t\n\tpublic void addPropertiesFile(PropertiesFile pf)\n\t{\n\t\tLabelList ll = pf.getLabelList();\n\t\tint i, n;\n\t\tn = ll.size();\n\t\tfor(i = 0; i < n; i++)\n\t\t{\n\t\t\tGUILabel lab = new GUILabel(parent, ll.getLabelName(i), ll.getLabel(i).toString());\n\t\t\ttheModel.addLabel(lab);\n\t\t}\n\t\ttheModel.validateLabels();\n\t}\n\t\n\t/** Validate the label list\n\t    NB: Don't call it \"validate()\" to avoid overwriting Swing methods */\n\t\n\tpublic void validateLabels()\n\t{\n\t\ttheModel.validateLabels();\n\t}\n\t\n\t/** Is the label list valid? */\n\t\n\tpublic boolean isPropLabelListValid()\n\t{\n\t\tif (theModel.error != null) return false;\n\t\tint i, n;\n\t\tn = theModel.getNumLabels();\n\t\tfor(i = 0; i < n; i++) {\n\t\t\tif (!theModel.getLabel(i).isParseable()) return false;\n\t\t}\n\t\treturn true;\n\t}\n\t\n\t/** Return string representing PRISM code for all labels in this list */\n\t\n\tpublic String getLabelsString()\n\t{\n\t\treturn theModel.toString();\n\t}\n\t\n\t/** Return string representing PRISM code for all valid Labels in this list */\n\t\n\tpublic String getValidLabelsString()\n\t{\n\t\treturn theModel.validToString();\n\t}\n\t\n\t/* Table model for the label list */\n\t\n\tclass PropLabelModel extends AbstractTableModel\n\t{\n\t\tArrayList labels; // The list of labels\n\t\tint labCount; // Counter used to generate new default names for labels\n\t\tException error; // Any error that occurs when all labels are parsed together\n\t\t\n\t\tpublic PropLabelModel()\n\t\t{\n\t\t\tlabels = new ArrayList();\n\t\t\tlabCount = 0;\n\t\t\terror = null;\n\t\t}\n\t\t\n\t\t/* Acesssor methods */\n\t\t\n\t\tpublic int getNumLabels()\n\t\t{\n\t\t\treturn labels.size();\n\t\t}\n\t\t\n\t\tpublic GUILabel getLabel(int i)\n\t\t{\n\t\t\treturn (GUILabel)labels.get(i);\n\t\t}\n\t\t\n\t\tpublic Exception getError()\n\t\t{\n\t\t\treturn error;\n\t\t}\n\t\t\n\t\tpublic int getRowCount()\n\t\t{\n\t\t\treturn labels.size();\n\t\t}\n\t\t\n\t\tpublic int getColumnCount()\n\t\t{\n\t\t\treturn 2;\n\t\t}\n\t\t\n\t\tpublic Object getValueAt(int row, int column)\n\t\t{\n\t\t\tGUILabel lab = getLabel(row);\n\t\t\tswitch(column)\n\t\t\t{\n\t\t\t\tcase 0: return lab.getNameString();\n\t\t\t\tcase 1: return lab.getValueString();\n\t\t\t\tdefault: return \"\";\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic String getColumnName(int columnIndex)\n\t\t{\n\t\t\tswitch(columnIndex)\n\t\t\t{\n\t\t\t\tcase 0: return \"Name\";\n\t\t\t\tcase 1: return \"Definition\";\n\t\t\t\tdefault: return \"\";\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic boolean isCellEditable(int row, int column)\n\t\t{\n\t\t\treturn true;\n\t\t}\n\t\t\n\t\t/** Return string representing PRISM code for all labels in this table model */\n\t\t\n\t\tpublic String toString()\n\t\t{\n\t\t\tString str = \"\";\n\t\t\t\n\t\t\tfor(int i = 0; i < getNumLabels(); i++)\n\t\t\t{\n\t\t\t\tGUILabel gl = getLabel(i);\n\t\t\t\tstr+=gl.toString()+\"\\n\";\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\t\t\n\t\t/** Return string representing PRISM code for all valid labels in this table model */\n\t\t\n\t\tpublic String validToString()\n\t\t{\n\t\t\tif (error != null) return \"\";\n\t\t\telse return parseableToString();\n\t\t}\n\t\t\n\t\t/** Return string representing PRISM code for all parseable labels in this table model */\n\t\t\n\t\tpublic String parseableToString()\n\t\t{\n\t\t\tint i, n;\n\t\t\tGUILabel gl;\n\t\t\tString str = \"\";\n\t\t\tn = getNumLabels();\n\t\t\tfor(i = 0; i < n; i++) {\n\t\t\t\tgl = getLabel(i);\n\t\t\t\tif (gl.isParseable()) str+=gl.toString()+\"\\n\";\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\t\t\n\t\t/* Methods to modify table model */\n\t\t\n\t\tpublic void newList()\n\t\t{\n\t\t\tlabels = new ArrayList();\n\t\t\tfireTableStructureChanged();\n\t\t\tparent.labelListChanged();\n\t\t}\n\t\t\n\t\t/** Add a new (default-valued) label to the list.\n\t\t    You should call validateLabels() after calling this. */\n\t\t\n\t\tpublic void addLabel()\n\t\t{\n\t\t\taddLabel(new GUILabel(parent, \"L\"+labCount, \"true\"));\n\t\t\tlabCount++;\n\t\t}\n\t\t\n\t\t/** Add a new label to the list.\n\t\t    You should call validateLabels() after calling this. */\n\t\t\n\t\tpublic void addLabel(GUILabel lab)\n\t\t{\n\t\t\tlab.parse();\n\t\t\tlabels.add(lab);\n\t\t\tfireTableRowsInserted(labels.size()-1, labels.size()-1);\n\t\t\tparent.labelListChanged();\n\t\t}\n\t\t\n\t\t/** Remove a label from the list.\n\t\t    You should call validateLabels() after calling this. */\n\t\t\n\t\tpublic void removeLabel(int index)\n\t\t{\n\t\t\tlabels.remove(index);\n\t\t\tfireTableRowsDeleted(index,index);\n\t\t\tparent.labelListChanged();\n\t\t}\n\t\t\n\t\t/** This is called directly by the GUI (when the table is edited) */\n\t\t\n\t\tpublic void setValueAt(Object aValue, int rowIndex, int columnIndex)\n\t\t{\n\t\t\tGUILabel gl = getLabel(rowIndex);\n\t\t\tswitch(columnIndex)\n\t\t\t{\n\t\t\t\tcase 0:\n\t\t\t\t{\n\t\t\t\t\tif(!gl.name.equals((String)aValue))\n\t\t\t\t\t{\n\t\t\t\t\t\tgl.name = (String)aValue;\n\t\t\t\t\t\tgl.parse();\n\t\t\t\t\t\tvalidateLabels();\n\t\t\t\t\t\tparent.labelListChanged();\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tcase 1:\n\t\t\t\t{\n\t\t\t\t\tif(!gl.label.equals((String)aValue))\n\t\t\t\t\t{\n\t\t\t\t\t\tgl.label = (String)aValue;\n\t\t\t\t\t\tgl.parse();\n\t\t\t\t\t\tvalidateLabels();\n\t\t\t\t\t\tparent.labelListChanged();\n\t\t\t\t\t}\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\t/** Validate the label list\n\t\t    NB: Don't call it \"validate()\" to avoid overwriting Swing methods */\n\t\t\n\t\tpublic void validateLabels()\n\t\t{\n\t\t\ttry {\n\t\t\t\terror = null;\n\t\t\t\tparent.getPrism().parsePropertiesString(parent.getConstantsString()+\"\\n\"+parseableToString());\n\t\t\t}\n\t\t\tcatch (PrismException e) {\n\t\t\t\terror = e;\n\t\t\t}\n\t\t\tfireTableDataChanged();\n\t\t}\n\t}\n\t\n\tclass TheCellRenderer extends DefaultTableCellRenderer\n\t{\n\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) \n\t\t{\n\t\t\tComponent cell = super.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);\n\t\t\tGUILabel gl = theModel.getLabel(row);\n\t\t\t// If the label has a parse error, show that\n\t\t\tif (!gl.isParseable()) {\n\t\t\t\tsetBackground(isSelected ? parent.getSelectionColor() : parent.getWarningColor());\n\t\t\t\tsetForeground(Color.red);\n\t\t\t\tsetToolTipText(gl.parseError.toString());\n\t\t\t}\n\t\t\t// If not but there is a \"global\" error for the whole list, show that\n\t\t\telse if (theModel.error != null) {\n\t\t\t\tsetBackground(isSelected ? parent.getSelectionColor() : parent.getWarningColor());\n\t\t\t\tsetForeground(Color.red);\n\t\t\t\tsetToolTipText(theModel.error.toString());\n\t\t\t}\n\t\t\t// Otherwise everything is fine\n\t\t\telse {\n\t\t\t\tsetBackground(isSelected ? parent.getSelectionColor() : Color.white);\n\t\t\t\tsetForeground(Color.black);\n\t\t\t\tsetToolTipText(gl.toString());\n\t\t\t}\n\t\t\treturn cell;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIPropertiesEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport userinterface.util.*;\nimport parser.*;\n\npublic class GUIPropertiesEvent extends GUIEvent\n{\n    public static final int REQUEST_MODEL_BUILD = 0;\n    public static final int REQUEST_MODEL_PARSE = 1;\n    public static final int EXPERIMENT_START =3;\n    public static final int EXPERIMENT_END = 4;\n    public static final int PROPERTIES_LIST_CHANGED = 5;\n    public static final int VERIFY_END = 6;\n    //private UndefinedConstants mfUndefined;\n    private Values buildValues;\n    \n    /** Creates a new instance of GUIPropertiesEvent */\n    public GUIPropertiesEvent(int id)\n    {\n        super(id);\n    }\n    \n    public GUIPropertiesEvent(int id, Values buildValues)\n    {\n        super(id);\n        this.buildValues = buildValues;\n    }\n    \n    public Values getBuildValues()\n    {\n        return buildValues;\n    }\n    /*\n    public GUIPropertiesEvent(int id, UndefinedConstants mfUndefined)\n    {\n        super(id);\n        this.mfUndefined = mfUndefined;\n    }\n    \n    public UndefinedConstants getMFUndefined()\n    {\n        return mfUndefined;\n    }*/\n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIPropertiesList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.io.*;\nimport java.util.*;\nimport java.util.List;\nimport java.awt.*;\nimport java.awt.event.*;\nimport javax.swing.*;\n\nimport parser.*;\nimport parser.ast.*;\nimport prism.*;\n\npublic class GUIPropertiesList extends JList implements KeyListener\n{\n\t//STATICS\n\n\tprivate static int counter = 0;\n\n\t//ATTRIBUTES\n\n\tprivate Prism prism;\n\tprivate GUIMultiProperties parent;\n\n\tprivate DefaultListModel listModel;\n\n\tprivate PictureCellRenderer rend;\n\n\t//CONSTRUCTORS\n\n\t/** Creates a new instance of GUIPropertiesList */\n\tpublic GUIPropertiesList(Prism prism, GUIMultiProperties parent)\n\t{\n\t\tthis.prism = prism;\n\t\tthis.parent = parent;\n\n\t\tlistModel = new DefaultListModel();\n\t\tsetModel(listModel);\n\n\t\trend = new PictureCellRenderer();\n\t\tsetCellRenderer(rend);\n\n\t\taddKeyListener(this);\n\t\tsetSelectionMode(ListSelectionModel.MULTIPLE_INTERVAL_SELECTION);\n\n\t\tgetInputMap().put(KeyStroke.getKeyStroke(KeyEvent.VK_C, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()), \"none\");\n\t}\n\n\t/** Override set font to update row heights at same time */\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\t// Note: minimum of 20 since icons are 16x16\n\t\tif (font != null)\n\t\t\tsetFixedCellHeight(Math.max(20, getFontMetrics(font).getHeight() + 4));\n\t}\n\n\t//ACCESS METHODS\n\n\tpublic int getNumProperties()\n\t{\n\t\treturn listModel.size();\n\t}\n\n\t/**\n\t * Get the ith property in the list.\n\t */\n\tpublic GUIProperty getProperty(int i)\n\t{\n\t\treturn (GUIProperty) listModel.getElementAt(i);\n\t}\n\t\n\t/**\n\t * Returns all properties in this list that have\n\t * non-null name.\n\t */\n\tpublic List<GUIProperty> getAllNamedProperties() {\n\t\tArrayList<GUIProperty> ret = new ArrayList<GUIProperty>();\n\t\tfor (int i = 0; i < getNumProperties(); i++) {\n\t\t\tif (getProperty(i).getName() != null)\n\t\t\t\tret.add(getProperty(i));\n\t\t}\n\t\t\n\t\treturn ret;\n\t}\n\t\n\t/**\n\t * Looks up a property with the specified name and returns it. If\n\t * such a property does not exist, returns null;\n\t */\n\tpublic GUIProperty getPropertyByName(String s) {\n\t\tfor (int i = 0; i < getNumProperties(); i++) {\n\t\t\tGUIProperty p = getProperty(i);\n\t\t\tif (p.getName() != null && p.getName().equals(s)) {\n\t\t\t\treturn p;\n\t\t\t}\n\t\t}\n\t\t\n\t\treturn null;\n\t}\n\n\t/**\n\t * Check that all properties in the list are valid.\n\t */\n\tpublic boolean allPropertiesAreValid()\n\t{\n\t\tfor (int i = 0; i < getNumProperties(); i++) {\n\t\t\tif (!getProperty(i).isValid())\n\t\t\t\treturn false;\n\t\t}\n\t\treturn true;\n\t}\n\n\t/**\n\t * Get the number of properties currently selected in the list.\n\t */\n\tpublic int getNumSelectedProperties()\n\t{\n\t\treturn getSelectedIndices().length;\n\t}\n\n\t/**\n\t * Get a list of the properties currently selected in the list.\n\t */\n\tpublic ArrayList<GUIProperty> getSelectedProperties()\n\t{\n\t\tArrayList<GUIProperty> gps = new ArrayList<GUIProperty>();\n\t\tint[] ind = getSelectedIndices();\n\t\tfor (int i = 0; i < ind.length; i++) {\n\t\t\tgps.add(getProperty(ind[i]));\n\t\t}\n\t\treturn gps;\n\t}\n\n\t/**\n\t * Check if there are any valid properties currently selected in the list.\n\t */\n\tpublic boolean existsValidSelectedProperties()\n\t{\n\t\tif (parent.getParsedModel() == null)\n\t\t\treturn false;\n\t\tint[] ind = getSelectedIndices();\n\t\tfor (int i = 0; i < ind.length; i++) {\n\t\t\tif (getProperty(ind[i]).isValid()) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get a list of the valid properties currently selected in the list.\n\t */\n\tpublic ArrayList<GUIProperty> getValidSelectedProperties()\n\t{\n\t\tArrayList<GUIProperty> gps = new ArrayList<GUIProperty>();\n\t\tif (parent.getParsedModel() == null)\n\t\t\treturn gps;\n\t\tint[] ind = getSelectedIndices();\n\t\tfor (int i = 0; i < ind.length; i++) {\n\t\t\tGUIProperty gp = getProperty(ind[i]);\n\t\t\tif (gp.isValid()) {\n\t\t\t\tgps.add(gp);\n\t\t\t}\n\t\t}\n\t\treturn gps;\n\t}\n\n\t/**\n\t * Get a string comprising concatenation of all valid properties currently selected in the list\n\t * together with all properties these reference (even indirectly). The properties which are not\n\t * selected, but referenced, are guarranteed to be first in the string.\n\t */\n\tpublic String getValidSelectedAndReferencedString()\n\t{\n\t\tString str = \"\";\n\t\tArrayList<GUIProperty> gps = getValidSelectedProperties();\n\t\t\n\t\t//strings will contain all relevant named properties, first selected, then refernced\n\t\tVector<String> strings = new Vector<String>(); \n\t\t\n\t\tfor (GUIProperty p : gps) { \n\t\t\t//add even null\n\t\t\tstrings.add(p.getName());\n\t\t}\n\t\t\n\t\tfor (GUIProperty p : gps) { \n\t\t\tfor (String s : p.getReferencedNames())\n\t\t\t\tif (!strings.contains(s))\n\t\t\t\t\tstrings.add(s);\n\t\t}\n\t\t\n\t\tVector<GUIProperty> referencedProps = new Vector<GUIProperty>();\n\n\t\t//turn referenced strings to props.\n\t\tint i = gps.size();\n\t\twhile (i < strings.size()) {\n\t\t\tGUIProperty p = getPropertyByName(strings.get(i));\n\t\t\tif (p != null) {\n\t\t\t\treferencedProps.add(p);\n\t\t\t\tfor (String s : p.getReferencedNames())\n\t\t\t\t\tif (!strings.contains(s))\n\t\t\t\t\t\tstrings.add(s);\n\t\t\t} //we don't need to care about null case, parser will find an error later.\n\t\t\ti++;\n\t\t}\n\t\t\n\t\t//add all named properties\n\t\tString namedString = \"\";\n\t\t//Add named properties\n\t\tfor (GUIProperty p : referencedProps) {\n\t\t\t\tnamedString += \"\\\"\" + p.getName() + \"\\\" : \" + p.getPropString() + \"\\n\";\n\t\t}\n\t\t\n\t\tfor (GUIProperty gp : gps) {\n\t\t\tif (gp.getName() != null) {\n\t\t\t\tstr += \"\\\"\" + gp.getName() + \"\\\" : \";\n\t\t\t}\n\t\t\tstr += gp.getPropString() + \"\\n\";\n\t\t}\n\t\treturn namedString + str;\n\t}\n\n\t/**\n\t * Check if there are any valid and simulate-able properties currently selected in the list.\n\t */\n\tpublic boolean existsValidSimulatableSelectedProperties()\n\t{\n\t\tif (parent.getParsedModel() == null)\n\t\t\treturn false;\n\t\tint[] ind = getSelectedIndices();\n\t\tfor (int i = 0; i < ind.length; i++) {\n\t\t\tif (getProperty(ind[i]).isValidForSimulation()) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\t/**\n\t * Get a list of the valid and simulate-able properties currently selected in the list.\n\t */\n\tpublic ArrayList<GUIProperty> getValidSimulatableSelectedProperties()\n\t{\n\t\tArrayList<GUIProperty> gps = new ArrayList<GUIProperty>();\n\t\tif (parent.getParsedModel() == null)\n\t\t\treturn gps;\n\t\tint[] ind = getSelectedIndices();\n\t\tfor (int i = 0; i < ind.length; i++) {\n\t\t\tGUIProperty gp = getProperty(ind[i]);\n\t\t\tif (gp.isValidForSimulation()) {\n\t\t\t\tgps.add(gp);\n\t\t\t}\n\t\t}\n\t\treturn gps;\n\t}\n\n\tpublic int getIndexOf(String id)\n\t{\n\t\tint index = -1;\n\t\tfor (int i = 0; i < getNumProperties(); i++) {\n\t\t\tString str = getProperty(i).getID();\n\t\t\tif (id.equals(str)) {\n\t\t\t\tindex = i;\n\t\t\t\tbreak;\n\t\t\t}\n\t\t}\n\t\treturn index;\n\t}\n\n\t//Used for cut and copy\n\tpublic String getClipboardString()\n\t{\n\t\tint[] ind = getSelectedIndices();\n\t\tString str = \"\";\n\t\tfor (int i = 0; i < ind.length; i++) {\n\t\t\tGUIProperty gp = getProperty(i);\n\t\t\tstr += gp.getPropString();\n\t\t\tif (i != ind.length - 1)\n\t\t\t\tstr += \"\\n\";\n\t\t}\n\t\treturn str;\n\t}\n\n\t/* UPDATE METHODS */\n\tpublic void addProperty(String propString, String comment)\n\t{\n\t\tif (propString.matches(\"\\\"[^\\\"]*\\\"[ ]*:.*\")) {\n\t\t\t//the string contains property name\n\t\t\tint start = propString.indexOf('\"') + 1;\n\t\t\tint end = propString.indexOf('\"', start);\n\t\t\tString name = propString.substring(start,end);\n\t\t\tint colon = propString.indexOf(':') + 1;\n\t\t\tString actualPropString = propString.substring(colon).trim();\n\t\t\t\n\t\t\taddProperty(name, actualPropString, comment);\n\t\t} else {\n\t\t\taddProperty(null, propString, comment);\n\t\t}\n\t}\n\n\tpublic void addProperty(String name, String propString, String comment)\n\t{\n\t\tcounter++;\n\t\tGUIProperty gp = new GUIProperty(prism, this, \"PROPERTY\" + counter, propString, name, comment);\n\t\tlistModel.addElement(gp);\n\t\tvalidateProperties();\n\t}\n\n\tpublic void setProperty(int index, String name, String propString, String comment)\n\t{\n\t\tcounter++;\n\t\tGUIProperty gp = new GUIProperty(prism, this, \"PROPERTY\" + counter, propString, name, comment);\n\t\tlistModel.setElementAt(gp, index);\n\t\tvalidateProperties();\n\t}\n\n\t/** Used for pasting */\n\tpublic void pastePropertiesString(String str)\n\t{\n\t\tStringTokenizer sto = new StringTokenizer(str, \"\\n\");\n\t\twhile (sto.hasMoreTokens()) {\n\t\t\tString token = sto.nextToken();\n\n\t\t\t// Make sure it isn't comment we are pasting\n\t\t\tif (token.indexOf(\"//\") != 0)\n\t\t\t\taddProperty(token, \"\");\n\t\t}\n\t}\n\n\tpublic void addPropertiesFile(PropertiesFile pf)\n\t{\n\t\tfor (int i = 0; i < pf.getNumProperties(); i++) {\n\t\t\tString nam = pf.getPropertyName(i);\n\t\t\tString str = pf.getProperty(i).toString();\n\t\t\tString com = pf.getPropertyComment(i);\n\t\t\taddProperty(nam, str, com);\n\t\t}\n\t}\n\n\tpublic boolean deleteProperty(int index)\n\t{\n\t\tGUIProperty gp = getProperty(index);\n\t\tif (!gp.isBeingEdited()) {\n\t\t\tlistModel.removeElementAt(index);\n\t\t\tvalidateProperties();\n\t\t\treturn true;\n\t\t} else\n\t\t\treturn false;\n\t}\n\n\tpublic void deleteSelected()\n\t{\n\t\twhile (!isSelectionEmpty()) {\n\t\t\tboolean deleted = deleteProperty(getSelectedIndex());\n\t\t\tif (!deleted) {\n\t\t\t\t//if not deleted, unselect, so the rest can!!\n\t\t\t\tint[] ind = getSelectedIndices();\n\t\t\t\tint[] newInd = new int[ind.length - 1];\n\t\t\t\tint c = 0;\n\t\t\t\tfor (int i = 0; i < ind.length; i++) {\n\t\t\t\t\tif (ind[i] != getSelectedIndex()) {\n\t\t\t\t\t\tnewInd[c] = ind[i];\n\t\t\t\t\t\tc++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tsetSelectedIndices(newInd);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void deleteAll()\n\t{\n\t\tselectAll();\n\t\tdeleteSelected();\n\t}\n\n\tpublic void selectAll()\n\t{\n\t\tif (getNumProperties() > 0) {\n\t\t\tsetSelectionInterval(0, getNumProperties() - 1);\n\t\t}\n\t}\n\n\t/** Validate all the properties in the list\n\t    NB: Don't call it \"validate()\" to avoid overwriting Swing methods */\n\n\tpublic void validateProperties()\n\t{\n\t\tList<GUIProperty> list = new ArrayList<GUIProperty>();\n\t\tfor (int i = 0; i < getNumProperties(); i++) {\n\t\t\tGUIProperty p = getProperty(i);\n\t\t\tp.makeInvalid();\n\t\t\tlist.add(p);\n\t\t}\n\t\t\n\t\tboolean changed;\n\t\tdo {\n\t\t\tchanged = false;\n\t\t\tint i = 0;\n\t\t\twhile (i < list.size()) {\n\t\t\t\tGUIProperty p = list.get(i);\n\t\t\t\tp.parse(parent.getConstantsString(), parent.getLabelsString());\n\t\t\t\tif (p.isValid()) {\n\t\t\t\t\tlist.remove(i);\n\t\t\t\t\tchanged = true;\n\t\t\t\t} else {\n\t\t\t\t\ti++;\n\t\t\t\t}\n\t\t\t}\n\t\t} while (changed && list.size() > 0);\n\t\t// Force repaint because we modified a GUIProperty directly\n\t\trepaint();\n\t}\n\n\t// convert to string which can be written to a file\n\n\tpublic String toFileString(File f, GUIPropConstantList consList, GUIPropLabelList labList)\n\t{\n\t\tint numProp;\n\t\tString s;\n\t\tint i;\n\n\t\ts = \"\";\n\t\tif (consList.getNumConstants() > 0) {\n\t\t\ts += consList.getConstantsString() + \"\\n\";\n\t\t}\n\t\tif (labList.getNumLabels() > 0) {\n\t\t\ts += labList.getLabelsString() + \"\\n\";\n\t\t}\n\t\tnumProp = getNumProperties();\n\t\tfor (i = 0; i < numProp; i++) {\n\t\t\tGUIProperty gp = getProperty(i);\n\t\t\tif (gp.getComment().length() > 0)\n\t\t\t\ts += PrismParser.slashCommentBlock(gp.getComment());\n\t\t\ts += gp.getPropString() + \"\\n\\n\";\n\t\t}\n\n\t\treturn s;\n\t}\n\n\t//REQUIRED TO IMPLEMENT KEYLISTENER\n\n\tpublic void keyPressed(KeyEvent e)\n\t{\n\t\tif (e.getModifiers() == KeyEvent.CTRL_MASK) {\n\t\t\tif (e.getKeyCode() == KeyEvent.VK_C) {\n\t\t\t\tparent.a_copy();\n\t\t\t} else if (e.getKeyCode() == KeyEvent.VK_V) {\n\t\t\t\tparent.a_paste();\n\t\t\t} else if (e.getKeyCode() == KeyEvent.VK_X) {\n\t\t\t\tparent.a_cut();\n\t\t\t} else if (e.getKeyCode() == KeyEvent.VK_D) {\n\t\t\t\tparent.a_delete();\n\t\t\t} else if (e.getKeyCode() == KeyEvent.VK_A) {\n\t\t\t\tparent.a_selectAll();\n\t\t\t}\n\t\t}\n\t\tif (e.getKeyCode() == KeyEvent.VK_DELETE) {\n\t\t\tparent.a_delete();\n\t\t}\n\t}\n\n\tpublic void keyReleased(KeyEvent e)\n\t{\n\t}\n\n\tpublic void keyTyped(KeyEvent e)\n\t{\n\t}\n\n\t//RENDERERS\n\n\tclass PictureCellRenderer extends JLabel implements ListCellRenderer\n\t{\n\t\tString toolTip;\n\n\t\tpublic PictureCellRenderer()\n\t\t{\n\t\t\ttoolTip = \"\";\n\t\t\tsetOpaque(true);\n\t\t}\n\n\t\tpublic String getToolTipText()\n\t\t{\n\t\t\treturn toolTip;\n\t\t}\n\n\t\tpublic Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus)\n\t\t{\n\t\t\tsetBorder(new BottomBorder());\n\t\t\tGUIProperty p = getProperty(index);\n\n\t\t\t// tooltip\n\t\t\ttoolTip = p.getToolTipText();\n\n\t\t\t// text\n\t\t\tsetText(p.toString());\n\n\t\t\t// icon\n\t\t\tsetIcon(p.getImage());\n\n\t\t\t// foreground/background colours\n\t\t\tif (isSelected) {\n\t\t\t\tsetBackground(parent.getSelectionColor());\n\t\t\t\tsetForeground(p.isValid() ? Color.black : Color.red);\n\t\t\t} else {\n\t\t\t\tif (!p.isValid()) {\n\t\t\t\t\tsetBackground(parent.getWarningColor());\n\t\t\t\t\tsetForeground(Color.red);\n\t\t\t\t} else {\n\t\t\t\t\tsetBackground(Color.white);\n\t\t\t\t\tsetForeground(Color.black);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif (p.isBeingEdited()) {\n\t\t\t\tsetBackground(Color.lightGray);\n\t\t\t}\n\n\t\t\treturn this;\n\t\t}\n\t}\n\n\tclass BottomBorder implements javax.swing.border.Border\n\t{\n\t\tpublic Insets getBorderInsets(Component c)\n\t\t{\n\t\t\treturn new Insets(0, 0, 0, 0);\n\t\t}\n\n\t\tpublic boolean isBorderOpaque()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\tpublic void paintBorder(Component c, Graphics g, int x, int y, int width, int height)\n\t\t{\n\t\t\tg.setColor(Color.lightGray);\n\t\t\tg.drawLine(x, (y + height - 1), (x + width), (y + height - 1));\n\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.util.List;\nimport java.util.Vector;\n\nimport javax.swing.ImageIcon;\n\nimport param.BigRational;\nimport parser.Values;\nimport parser.ast.Expression;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport prism.Interval;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.Result;\nimport prism.TileList;\nimport userinterface.GUIPrism;\n\n/**\n * Encapsulates a property in the list in the GUI \"Properties\" tab.\n */\npublic class GUIProperty\n{\n\t//Constants\n\n\t/** A property state constant image */\n\tpublic static final ImageIcon IMAGE_NOT_DONE = GUIPrism.getIconFromImage(\"smallFilePrism.png\");\n\t/** A property state constant image */\n\tpublic static final ImageIcon IMAGE_DOING = GUIPrism.getIconFromImage(\"smallClockAnim1.png\");\n\t/** A property state constant image */\n\tpublic static final ImageIcon IMAGE_TICK = GUIPrism.getIconFromImage(\"smallTick.png\");\n\t/** A property state constant image */\n\tpublic static final ImageIcon IMAGE_CROSS = GUIPrism.getIconFromImage(\"smallCross.png\");\n\t/** A property state constant image */\n\tpublic static final ImageIcon IMAGE_ERROR = GUIPrism.getIconFromImage(\"smallError.png\");\n\t/** A property state constant image */\n\tpublic static final ImageIcon IMAGE_INVALID = GUIPrism.getIconFromImage(\"smallWarning.png\");\n\t/** A property state constant image */\n\tpublic static final ImageIcon IMAGE_NUMBER = GUIPrism.getIconFromImage(\"smallCompute.png\");\n\t/** A property state constant image */\n\tpublic static final ImageIcon IMAGE_PARETO = GUIPrism.getIconFromImage(\"smallPareto.png\");\n\t\n\t/** Property status */\n\tpublic static final int STATUS_NOT_DONE = 0;\n\t/** Property status */\n\tpublic static final int STATUS_DOING = 1;\n\t/** Property status */\n\tpublic static final int STATUS_PARSE_ERROR = 2;\n\t/** Property status */\n\tpublic static final int STATUS_RESULT_ERROR = 3;\n\t/** Property status */\n\tpublic static final int STATUS_RESULT_TRUE = 4;\n\t/** Property status */\n\tpublic static final int STATUS_RESULT_FALSE = 5;\n\t/** Property status */\n\tpublic static final int STATUS_RESULT_NUMBER = 6;\n\t/** Property status */\n\tpublic static final int STATUS_RESULT_PARETO = 7;\n\n\t//ATTRIBUTES\n\n\tprivate Prism prism; // Required for parsing\n\n\tprivate String id; // Unique ID\n\tprivate int status; // Status - see constants above\n\tprivate ImageIcon doingImage; // Image when in DOING state - can be modified externally for animations\n\tprivate boolean beingEdited; // Is this property currently being edited?\n\n\tprivate String propString; // String representing the property\n\tprivate Expression expr; // The parsed property (null if invalid)\n\tprivate String comment; // The property's comment\n\n\tprivate Result result; // Result of model checking etc. (if done, null if not)\n\tprivate int numberOfWarnings; // Result of model checking etc. (if done, null if not)\n\tprivate String parseError; // Parse error (if property is invalid)\n\n\tprivate String method; // Method used (verification, simulation)\n\tprivate String constantsString; // Constant values used\n\tprivate String name;\n\tprivate List<String> referencedNames;\n\t\n\tprivate GUIPropertiesList propList; // to be able to get named properties\n\n\t/** Creates a new instance of GUIProperty */\n\tpublic GUIProperty(Prism prism, GUIPropertiesList propList, String id, String propString, String name, String comment)\n\t{\n\t\tthis.prism = prism;\n\t\tthis.propList = propList;\n\t\t\n\t\tthis.id = id;\n\t\tstatus = STATUS_NOT_DONE;\n\t\tdoingImage = IMAGE_DOING;\n\t\tbeingEdited = false;\n\n\t\tthis.propString = propString;\n\t\texpr = null;\n\t\tthis.comment = comment;\n\t\tthis.name = name;\n\n\t\tresult = null;\n\t\tparseError = \"\";\n\t\tmethod = \"<none>\";\n\t\tconstantsString = \"<none>\";\n\t}\n\n\t//ACCESS METHODS\n\n\tpublic String getID()\n\t{\n\t\treturn id;\n\t}\n\n\tpublic int getStatus()\n\t{\n\t\treturn status;\n\t}\n\n\tpublic ImageIcon getImage()\n\t{\n\t\tswitch (status) {\n\t\tcase STATUS_NOT_DONE:\n\t\t\treturn IMAGE_NOT_DONE;\n\t\tcase STATUS_DOING:\n\t\t\treturn doingImage;\n\t\tcase STATUS_PARSE_ERROR:\n\t\t\treturn IMAGE_INVALID;\n\t\tcase STATUS_RESULT_ERROR:\n\t\t\treturn IMAGE_ERROR;\n\t\tcase STATUS_RESULT_TRUE:\n\t\t\treturn IMAGE_TICK;\n\t\tcase STATUS_RESULT_FALSE:\n\t\t\treturn IMAGE_CROSS;\n\t\tcase STATUS_RESULT_NUMBER:\n\t\t\treturn IMAGE_NUMBER;\n\t\tcase STATUS_RESULT_PARETO:\n\t\t\treturn IMAGE_PARETO;\n\t\tdefault:\n\t\t\treturn IMAGE_NOT_DONE;\n\t\t}\n\t}\n\n\tpublic boolean isBeingEdited()\n\t{\n\t\treturn beingEdited;\n\t}\n\n\tpublic String getPropString()\n\t{\n\t\treturn propString;\n\t}\n\t\n\t/**\n\t * Returns the name of this property, or {@code null} if the property\n\t * has no name.\n\t */\n\tpublic String getName()\n\t{\n\t\treturn this.name;\n\t}\n\t\n\t/**\n\t * If the property is valid (see {@link #isValid()}), returns a\n\t * (potentialy empty) vector containing names of properties\n\t * this property references.\n\t * <p/>\n\t * If the property is not valid, returns {@code null}.\n\t */\n\tpublic List<String> getReferencedNames()\n\t{\n\t\treturn this.referencedNames;\n\t}\n\n\tpublic Expression getProperty()\n\t{\n\t\treturn expr;\n\t}\n\n\tpublic String getComment()\n\t{\n\t\treturn comment;\n\t}\n\n\t/**\n\t * Is this property valid? i.e. Did it parse OK last time it was parsed?\n\t */\n\tpublic boolean isValid()\n\t{\n\t\treturn expr != null;\n\t}\n\n\t/**\n\t * Forgets the validity state of the property, i.e. {@link #isValid()} will\n\t * be returning {@code false} until property is parsed OK again.\n\t * @return\n\t */\n\tpublic void makeInvalid() {\n\t\tthis.expr = null;\n\t\tthis.referencedNames = null;\n\t}\n\t\n\t/**\n\t * Is this property both valid (i.e. parsed OK last time it was checked)\n\t * and suitable approximate verification through simulation?\n\t */\n\tpublic boolean isValidForSimulation()\n\t{\n\t\treturn isValid() && prism.isPropertyOKForSimulation(expr);\n\t}\n\n\tpublic Result getResult()\n\t{\n\t\treturn result;\n\t}\n\t\n\tpublic int getNumberOfWarnings()\n\t{\n\t\treturn this.numberOfWarnings;\n\t}\n\n\n\tpublic String getResultString()\n\t{\n\t\treturn result == null ? \"Unknown\" : result.getResultString();\n\t}\n\n\tpublic String getToolTipText()\n\t{\n\t\tswitch (status) {\n\t\tcase STATUS_DOING:\n\t\t\treturn \"In progress...\";\n\t\tcase STATUS_PARSE_ERROR:\n\t\t\treturn \"Invalid property: \" + parseError;\n\t\tcase STATUS_RESULT_ERROR:\n\t\t\treturn getResultString();\n\t\tdefault:\n\t\t\treturn \"<html>Result: \" + getResultString().replaceAll(\"\\n\", \"<br/>\") + \"</html>\";\n\t\t}\n\t}\n\n\tpublic String getConstantsString()\n\t{\n\t\treturn constantsString;\n\t}\n\n\tpublic String getMethodString()\n\t{\n\t\treturn method;\n\t}\n\n\tpublic String toString()\n\t{\n\t\treturn ((this.name != null) ? (\"\\\"\" + this.name + \"\\\" : \") : \"\") + propString;\n\t}\n\n\t//UPDATE METHODS\n\n\tpublic void setStatus(int status)\n\t{\n\t\tthis.status = status;\n\t}\n\n\tpublic void setDoingImage(ImageIcon image)\n\t{\n\t\tdoingImage = image;\n\t}\n\n\tpublic void setPropStringAndName(String propString, String name, ModulesFile m, String constantsString, String labelString)\n\t{\n\t\tthis.propString = propString;\n\t\tthis.name = name;\n\t\tsetStatus(STATUS_NOT_DONE);\n\t\tpropList.validateProperties();\n\t}\n\n\tpublic void setComment(String comment)\n\t{\n\t\tthis.comment = comment;\n\t}\n\n\tpublic void setBeingEdited(boolean beingEdited)\n\t{\n\t\tthis.beingEdited = beingEdited;\n\t}\n\n\tpublic void setResult(Result res)\n\t{\n\t\tresult = res;\n\t\tif (result.getResult() instanceof Boolean) {\n\t\t\tif (((Boolean) result.getResult()).booleanValue()) {\n\t\t\t\tsetStatus(STATUS_RESULT_TRUE);\n\t\t\t} else {\n\t\t\t\tsetStatus(STATUS_RESULT_FALSE);\n\t\t\t}\n\t\t} else if (result.getResult() instanceof Integer) {\n\t\t\tsetStatus(STATUS_RESULT_NUMBER);\n\t\t} else if (result.getResult() instanceof Double) {\n\t\t\tsetStatus(STATUS_RESULT_NUMBER);\n\t\t} else if (result.getResult() instanceof BigRational) {\n\t\t\tsetStatus(STATUS_RESULT_NUMBER);\n\t\t} else if (result.getResult() instanceof Interval) {\n\t\t\tsetStatus(STATUS_RESULT_NUMBER);\n\t\t} else if (result.getResult() instanceof Exception) {\n\t\t\tsetStatus(STATUS_RESULT_ERROR);\n\t\t} else if (result.getResult() instanceof TileList) {\n\t\t\tsetStatus(STATUS_RESULT_PARETO);\n\t\t} else {\n\t\t\tsetStatus(STATUS_NOT_DONE);\n\t\t\tresult = null;\n\t\t}\n\t}\n\t\n\tpublic void setNumberOfWarnings(int n)\n\t{\n\t\tthis.numberOfWarnings = n;\n\t}\n\n\tpublic void setMethodString(String method)\n\t{\n\t\tthis.method = (method == null) ? \"<none>\" : method;\n\t}\n\n\tpublic void setConstants(Values mfConstants, Values pfConstants)\n\t{\n\t\tif (mfConstants != null && mfConstants.getNumValues() > 0) {\n\t\t\tconstantsString = mfConstants.toString();\n\t\t\tif (pfConstants != null && pfConstants.getNumValues() > 0)\n\t\t\t\tconstantsString += \", \" + pfConstants.toString();\n\t\t} else if (pfConstants != null && pfConstants.getNumValues() > 0) {\n\t\t\tconstantsString = pfConstants.toString();\n\t\t} else {\n\t\t\tconstantsString = \"<none>\";\n\t\t}\n\t}\n\n\tpublic void parse(String constantsString, String labelString)\n\t{\n\t\tif (propString == null || constantsString == null || labelString == null) {\n\t\t\texpr = null;\n\t\t\tsetStatus(STATUS_PARSE_ERROR);\n\t\t\tparseError = \"(Unexpected) Properties, constants or labels are null\";\n\t\t\treturn;\n\t\t}\n\t\ttry {\n\t\t\t//Parse constants and labels\n\t\t\tboolean couldBeNoConstantsOrLabels = false;\n\t\t\tPropertiesFile fConLab = null;\n\t\t\ttry {\n\t\t\t\tfConLab = prism.parsePropertiesString(constantsString + \"\\n\" + labelString);\n\t\t\t} catch (PrismException e) {\n\t\t\t\tcouldBeNoConstantsOrLabels = true;\n\t\t\t}\n\t\t\t\n\t\t\tString namedString = \"\";\n\t\t\tint namedCount = 0;\n\t\t\t//Add named properties\n\t\t\tfor (GUIProperty namedProp : this.propList.getAllNamedProperties()) {\n\t\t\t\t\n\t\t\t\tif (namedProp.isValid() &&\n\t\t\t\t\t\t(this.name == null || !this.name.equals(namedProp.getName()))) {\n\t\t\t\t\tnamedCount++;\n\t\t\t\t\tnamedString += \"\\\"\" + namedProp.getName() + \"\\\" : \" + namedProp.getPropString() + \"\\n\";\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t//Parse all together\n\t\t\tString withConsLabs = constantsString + \"\\n\" + labelString + \"\\n\" + namedString + propString;\n\t\t\tPropertiesFile ff = prism.parsePropertiesString(withConsLabs);\n\t\t\t\n\t\t\t//Validation of number of properties\n\t\t\tif (ff.getNumProperties() <= namedCount)\n\t\t\t\tthrow new PrismException(\"Empty Property\");\n\t\t\telse if (ff.getNumProperties() > namedCount + 1)\n\t\t\t\tthrow new PrismException(\"Contains Multiple Properties\");\n\n\t\t\t//Validation of constants and labels\n\t\t\tif (!couldBeNoConstantsOrLabels) {\n\t\t\t\tif (ff.getConstantList().size() != fConLab.getConstantList().size())\n\t\t\t\t\tthrow new PrismException(\"Contains constants\");\n\t\t\t\tif (ff.getLabelList().size() != fConLab.getLabelList().size())\n\t\t\t\t\tthrow new PrismException(\"Contains labels\");\n\t\t\t} else {\n\t\t\t\tif (ff.getConstantList().size() != 0)\n\t\t\t\t\tthrow new PrismException(\"Contains constants\");\n\t\t\t\tif (ff.getLabelList().size() != 0)\n\t\t\t\t\tthrow new PrismException(\"Contains labels\");\n\t\t\t}\n\t\t\t//Now set the property\n\t\t\texpr = ff.getProperty(namedCount);\n\t\t\tparseError = \"(Unexpected) no error!\";\n\t\t\t// if status was previously a parse error, reset status.\n\t\t\t// otherwise, don't set status - reparse doesn't mean existing results should be lost\n\t\t\tif (getStatus() == STATUS_PARSE_ERROR)\n\t\t\t\tsetStatus(STATUS_NOT_DONE);\n\t\t\t\n\t\t\t// get the referenced names\n\t\t\tthis.referencedNames = ff.getPropertyObject(namedCount).getAllPropRefsRecursively(ff); \n\t\t\t\n\t\t} catch (PrismException ex) {\n\t\t\tthis.expr = null;\n\t\t\tthis.referencedNames = null;\n\t\t\tsetStatus(STATUS_PARSE_ERROR);\n\t\t\tparseError = ex.getMessage();\n\t\t}\n\t}\n\t\n\t@Override\n\tpublic int hashCode()\n\t{\n\t\treturn (this.propString != null) ? this.propString.length() : 0;\n\t}\n\t\n\t@Override\n\tpublic boolean equals(Object obj)\n\t{\n\t\tif (!(obj instanceof GUIProperty))\n\t\t\treturn false;\n\t\t\n\t\treturn this.id.equals(((GUIProperty) obj).id);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIPropertyEditor.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <Properties>\n    <Property name=\"resizable\" type=\"boolean\" value=\"false\"/>\n  </Properties>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,26,0,0,3,47\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel5\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel6\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"1.0\" weightY=\"1.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JToolBar\" name=\"jToolBar1\">\n              <Properties>\n                <Property name=\"floatable\" type=\"boolean\" value=\"false\"/>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"North\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\"/>\n              <SubComponents>\n                <Component class=\"javax.swing.JButton\" name=\"cut\">\n                  <Properties>\n                    <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.openide.explorer.propertysheet.editors.IconEditor\">\n                      <Image iconType=\"3\" name=\"/images/smallCut.gif\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"copy\">\n                  <Properties>\n                    <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.openide.explorer.propertysheet.editors.IconEditor\">\n                      <Image iconType=\"3\" name=\"/images/smallCopy.gif\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"paste\">\n                  <Properties>\n                    <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.openide.explorer.propertysheet.editors.IconEditor\">\n                      <Image iconType=\"3\" name=\"/images/smallPaste.gif\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                </Component>\n              </SubComponents>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel7\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel9\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"4\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel10\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"2\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JTextField\" name=\"propertyText\">\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"1\" gridWidth=\"10\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"1.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"jLabel1\">\n                  <Properties>\n                    <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n                      <ComponentRef name=\"propertyText\"/>\n                    </Property>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Property:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel8\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JButton\" name=\"trueButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"true\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[123, 25]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"andButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"And\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[123, 25]\"/>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"andButtonActionPerformed\"/>\n                  </Events>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"5\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"notButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Not\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[123, 25]\"/>\n                    </Property>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"notButtonActionPerformed\"/>\n                  </Events>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"7\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"untilButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Until\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[123, 25]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"9\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"steadyStateButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Steady-state\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[123, 25]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"11\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"falseButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"false\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[123, 25]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"5\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"orButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Or\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[123, 25]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"5\" gridY=\"5\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"nextButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Next\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[123, 25]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"7\" gridY=\"5\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"boundedUntilButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Bounded Until\"/>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"9\" gridY=\"5\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.2\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel11\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel12\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"6\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel13\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"8\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel14\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"10\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel15\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[10, 5]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"4\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel16\">\n                  <Properties>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[10, 20]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                </Container>\n                <Component class=\"javax.swing.JLabel\" name=\"jLabel2\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Comment:\"/>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"1\" gridY=\"7\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"11\" weightX=\"0.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane1\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"7\" gridWidth=\"10\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"1.0\" weightY=\"0.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                  <SubComponents>\n                    <Component class=\"javax.swing.JTextArea\" name=\"commentTextArea\">\n                      <Properties>\n                        <Property name=\"rows\" type=\"int\" value=\"3\"/>\n                      </Properties>\n                    </Component>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n        <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n      </Layout>\n      <SubComponents>\n        <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n          <Properties>\n            <Property name=\"mnemonic\" type=\"int\" value=\"79\"/>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n          </Events>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n        </Component>\n        <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n          <Properties>\n            <Property name=\"mnemonic\" type=\"int\" value=\"67\"/>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n          </Properties>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n        </Component>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIPropertyEditor.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vojtech Forejt <vojtech.forejt@cs.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport userinterface.*;\nimport parser.ast.*;\nimport prism.*;\nimport java.awt.event.*;\nimport javax.swing.*;\nimport java.awt.*;\n\npublic class GUIPropertyEditor extends javax.swing.JDialog implements ActionListener, KeyListener\n{\n\t\n\t//Constants\n\t\n\tprivate static final int START = 0;\n\tprivate static final int CURSOR = 1;\n\tprivate static final int END = 2;\n\t\n\t//Statics\n\tprivate static int noOpen = 0;\n\t\n\t//Attributes\n\t\n\tprivate GUIPrism parent;\n\tprivate GUIMultiProperties props;\n\tprivate boolean dispose = false;\n\tprivate String id;\n\tprivate int propertyInvalidStrategy = GUIMultiProperties.WARN_INVALID_PROPS;\n\t\n\t//Constructors\n\t\n\t/** Creates a new GUIPropertyEditor with its parent GUIPrism, a boolean stating\n\t * whether the dialog should be modal and a Vector of properties to be displayed\n\t * for user browsing/copying.\n\t */\n\tpublic GUIPropertyEditor(GUIMultiProperties props,int strategy) //Adding constructor\n\t{\n\t\tthis(props, null, strategy);\n\t}\n\t\n\t/** Creates a new GUIPropertyEditor with its parent GUIPrism, a boolean stating\n\t * whether the dialog should be modal, a Vector of properties to be displayed\n\t * for user browsing/copying and a string showing the default value of the\n\t * property text box.\n\t */\n\tpublic GUIPropertyEditor(GUIMultiProperties props, GUIProperty prop, int strategy) //Editing constructor\n\t{\n\t\tsuper(props.getGUI(), false);\n\t\tthis.props = props;\n\t\tthis.parent = props.getGUI();\n\t\tthis.propertyInvalidStrategy = strategy;\n\t\tinitComponents();\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t\t//propertyList.setListData(props);\n\t\tif(prop == null)\n\t\t{\n\t\t\tthis.id = \"new\";\n\t\t\tpropertyText.setText(\"\");\n\t\t\tcommentTextArea.setText(\"\");\n\t\t}\n\t\telse\n\t\t{\n\t\t\tthis.id = prop.getID();\n\t\t\t\n\t\t\tString namePart = (prop.getName() != null) ? (\"\\\"\" + prop.getName() + \"\\\" : \") : \"\";\n\t\t\t\n\t\t\tpropertyText.setText(namePart + prop.getPropString());\n\t\t\tcommentTextArea.setText(prop.getComment());\n\t\t}\n\t\taddActionListeners();\n\t\tpropertyText.setFont(new Font(\"Monospaced\", Font.PLAIN, 12));\n\t\t\n\t\tsetTitle(\"Property Editor\");\n\t\t\n\t}\n\t\n\t//Update methods\n\t\n\tpublic void show()\n\t{\n\t\tnoOpen++;\n\t\tsetLocation(getX()+(noOpen*50), getY()+(noOpen*50));\n\t\t\n\t\tsuper.show();\n\n\t\t// Request that the initial focus is placed on the property text field\n\t\t// when the dialog is shown.\n\t\t// This is not guaranteed to work, but if it does then it's\n\t\t// convenient for the user...\n\t\tif (propertyText != null)  // should exist, but be careful nonetheless\n\t\t\tpropertyText.requestFocusInWindow();\n\t}\n\t\n\tpublic void dispose()\n\t{\n\t\tnoOpen--;\n\t\tsuper.dispose();\n\t}\n\t\n\tprivate void addString(String str, int position)\n\t{\n\t\tif(position == START)\n\t\t{\n\t\t\tpropertyText.setText(str+propertyText.getText());\n\t\t\tpropertyText.setCaretPosition(str.length());\n\t\t}\n\t\telse if(position == END)\n\t\t{\n\t\t\tpropertyText.setText(propertyText.getText() + str);\n\t\t}\n\t\telse // position == CURSOR\n\t\t{\n\t\t\tint curs = propertyText.getCaretPosition();\n\t\t\tint length = propertyText.getText().length();\n\t\t\tString s = propertyText.getText().substring(0, curs);\n\t\t\tString t = propertyText.getText().substring(curs, length);\n\t\t\tpropertyText.setText(s + str + t);\n\t\t\tpropertyText.setCaretPosition(s.length()+str.length());\n\t\t}\n\t\tpropertyText.requestFocus();\n\t}\n\t\n\tprivate void addString(String str, int position, int relativeCursorPosition)\n\t{\n\t\tint curs;\n\t\tif(position == START) curs = 0;\n\t\telse if(position == END) curs = propertyText.getText().length();\n\t\telse curs = propertyText.getCaretPosition(); // must be curs\n\t\taddString(str, position);\n\t\tpropertyText.setCaretPosition(curs+ relativeCursorPosition);\n\t\tpropertyText.requestFocus();\n\t}\n\tprivate void removeCharAt(int pos)\n\t{\n\t\tString str = propertyText.getText();\n\t\tString first = str.substring(0,pos);\n\t\tString last = str.substring(pos+1, str.length());\n\t\tpropertyText.setText(first+last);\n\t}\n\t\n\t//Listener Methods\n\t\n\t/** Needed to implement ActionListener interface.  Is called when a button is\n\t * pressed.  According to which button is pressed, this adds content to the text\n\t * box in an \"intelligent\" way.\n\t * @param e generated by a button press.\n\t */\n\tpublic void actionPerformed(ActionEvent e)\n\t{\n\t\tif(e.getSource() == trueButton)\n\t\t{\n\t\t\tint num = propertyText.getCaretPosition();\n\t\t\t\n\t\t\tif(num > 0 && propertyText.getText().charAt(num-1) == '(')\n\t\t\t{\n\t\t\t\tif(propertyText.getText().charAt(num) == ')')\n\t\t\t\t{\n\t\t\t\t\tremoveCharAt(num-1);\n\t\t\t\t\tremoveCharAt(num-1);\n\t\t\t\t\tpropertyText.setCaretPosition(num-1);\n\t\t\t\t\taddString(\"true\", CURSOR);\n\t\t\t\t\tpropertyText.setCaretPosition(num+3);\n\t\t\t\t}\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\tpropertyText.setCaretPosition(num);\n\t\t\t\taddString(\"true\", CURSOR);\n\t\t\t\tpropertyText.setCaretPosition(num+4);\n\t\t\t}\n\t\t}\n\t\telse if(e.getSource() == falseButton)\n\t\t{\n\t\t\tint num = propertyText.getCaretPosition();\n\t\t\t\n\t\t\tif(num > 0 && propertyText.getText().charAt(num-1) == '(')\n\t\t\t{\n\t\t\t\tif(propertyText.getText().charAt(num) == ')')\n\t\t\t\t{\n\t\t\t\t\tremoveCharAt(num-1);\n\t\t\t\t\tremoveCharAt(num-1);\n\t\t\t\t\tpropertyText.setCaretPosition(num-1);\n\t\t\t\t\taddString(\"false\", CURSOR);\n\t\t\t\t\tpropertyText.setCaretPosition(num+4);\n\t\t\t\t}\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\tpropertyText.setCaretPosition(num);\n\t\t\t\taddString(\"false\", CURSOR);\n\t\t\t\tpropertyText.setCaretPosition(num+5);\n\t\t\t}\n\t\t}\n\t\telse if(e.getSource() == andButton)\n\t\t{\n\t\t\tif(propertyText.getSelectedText() == null)\n\t\t\t{\n\t\t\t\taddString(\"() & ()\", CURSOR, 1);\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\tint start = propertyText.getSelectionStart();\n\t\t\t\tint end = propertyText.getSelectionEnd();\n\t\t\t\tint length = propertyText.getSelectedText().length();\n\t\t\t\tboolean shouldDo = false;\n\t\t\t\tint open = 0;\n\t\t\t\tint closed = 0;\n\t\t\t\tint opensq = 0;\n\t\t\t\tint closedsq = 0;\n\t\t\t\tfor(int i = 0; i < end-start; i++)\n\t\t\t\t{\n\t\t\t\t\tif(propertyText.getSelectedText().charAt(i) == '(') open++;\n\t\t\t\t\telse if (propertyText.getSelectedText().charAt(i) == ')') closed++;\n\t\t\t\t\telse\t  if(propertyText.getSelectedText().charAt(i) == '[') opensq++;\n\t\t\t\t\telse\t  if(propertyText.getSelectedText().charAt(i) == ']') closedsq++;\n\t\t\t\t}\n\t\t\t\tif((open == closed) && (opensq == closedsq)) shouldDo = true;\n\t\t\t\tif(shouldDo)\n\t\t\t\t{\n\t\t\t\t\tpropertyText.setCaretPosition(start);\n\t\t\t\t\taddString(\"(\", CURSOR, 0);\n\t\t\t\t\tpropertyText.setCaretPosition(end+1);\n\t\t\t\t\taddString(\") & ()\",CURSOR, 0);\n\t\t\t\t\t\n\t\t\t\t\tint caret = propertyText.getCaretPosition();\n\t\t\t\t\tboolean found = false;\n\t\t\t\t\tint i = caret;\n\t\t\t\t\tfor(i = caret; i < propertyText.getText().length(); i++)\n\t\t\t\t\t{\n\t\t\t\t\t\tif(propertyText.getText().charAt(i) == '(')\n\t\t\t\t\t\t{found = true; break;}\n\t\t\t\t\t}\n\t\t\t\t\tif(found)\n\t\t\t\t\t{\n\t\t\t\t\t\tpropertyText.setCaretPosition(i+1);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\telse if(e.getSource() == orButton)\n\t\t{\n\t\t\tif(propertyText.getSelectedText() == null)\n\t\t\t{\n\t\t\t\taddString(\"() | ()\", CURSOR, 1);\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\tint start = propertyText.getSelectionStart();\n\t\t\t\tint end = propertyText.getSelectionEnd();\n\t\t\t\tint length = propertyText.getSelectedText().length();\n\t\t\t\tboolean shouldDo = false;\n\t\t\t\tint open = 0;\n\t\t\t\tint closed = 0;\n\t\t\t\tint opensq = 0;\n\t\t\t\tint closedsq = 0;\n\t\t\t\tfor(int i = 0; i < end-start; i++)\n\t\t\t\t{\n\t\t\t\t\tif(propertyText.getSelectedText().charAt(i) == '(') open++;\n\t\t\t\t\telse if (propertyText.getSelectedText().charAt(i) == ')') closed++;\n\t\t\t\t\telse\t  if(propertyText.getSelectedText().charAt(i) == '[') opensq++;\n\t\t\t\t\telse\t  if(propertyText.getSelectedText().charAt(i) == ']') closedsq++;\n\t\t\t\t}\n\t\t\t\tif((open == closed) && (opensq == closedsq)) shouldDo = true;\n\t\t\t\tif(shouldDo)\n\t\t\t\t{\n\t\t\t\t\tpropertyText.setCaretPosition(start);\n\t\t\t\t\taddString(\"(\", CURSOR, 0);\n\t\t\t\t\tpropertyText.setCaretPosition(end+1);\n\t\t\t\t\taddString(\") | ()\",CURSOR, 0);\n\t\t\t\t\t\n\t\t\t\t\tint caret = propertyText.getCaretPosition();\n\t\t\t\t\tboolean found = false;\n\t\t\t\t\tint i = caret;\n\t\t\t\t\tfor(i = caret; i < propertyText.getText().length(); i++)\n\t\t\t\t\t{\n\t\t\t\t\t\tif(propertyText.getText().charAt(i) == '(')\n\t\t\t\t\t\t{found = true; break;}\n\t\t\t\t\t}\n\t\t\t\t\tif(found)\n\t\t\t\t\t{\n\t\t\t\t\t\tpropertyText.setCaretPosition(i+1);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\telse if(e.getSource() == notButton)\n\t\t{\n\t\t\tif(propertyText.getSelectedText() == null)\n\t\t\t{\n\t\t\t\taddString(\"!()\", CURSOR, 2);\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t\tint start = propertyText.getSelectionStart();\n\t\t\t\tint end = propertyText.getSelectionEnd();\n\t\t\t\tint length = propertyText.getSelectedText().length();\n\t\t\t\tboolean shouldDo = false;\n\t\t\t\tint open = 0;\n\t\t\t\tint closed = 0;\n\t\t\t\tint opensq = 0;\n\t\t\t\tint closedsq = 0;\n\t\t\t\tfor(int i = 0; i < end-start; i++)\n\t\t\t\t{\n\t\t\t\t\tif(propertyText.getSelectedText().charAt(i) == '(') open++;\n\t\t\t\t\telse if (propertyText.getSelectedText().charAt(i) == ')') closed++;\n\t\t\t\t\telse\t  if(propertyText.getSelectedText().charAt(i) == '[') opensq++;\n\t\t\t\t\telse\t  if(propertyText.getSelectedText().charAt(i) == ']') closedsq++;\n\t\t\t\t}\n\t\t\t\tif((open == closed) && (opensq == closedsq)) shouldDo = true;\n\t\t\t\tif(shouldDo)\n\t\t\t\t{\n\t\t\t\t\tpropertyText.setCaretPosition(start);\n\t\t\t\t\taddString(\"!(\", CURSOR, 0);\n\t\t\t\t\tpropertyText.setCaretPosition(end+2);\n\t\t\t\t\taddString(\")\",CURSOR, 0);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\telse if(e.getSource() == nextButton)\n\t\t{\n\t\t\tint curs = propertyText.getCaretPosition();\n\t\t\taddString(\"P><p [ X () ]\", CURSOR, 1);\n\t\t\tpropertyText.select(curs+1, curs+4);\n\t\t}\n\t\telse if(e.getSource() == untilButton)\n\t\t{\n\t\t\tint curs = propertyText.getCaretPosition();\n\t\t\taddString(\"P><p [ () U () ]\", CURSOR, 1);\n\t\t\tpropertyText.select(curs+1, curs+4);\n\t\t}\n\t\telse if(e.getSource() == boundedUntilButton)\n\t\t{\n\t\t\tint curs = propertyText.getCaretPosition();\n\t\t\taddString(\"P><p [ () U<=k () ]\", CURSOR, 1);\n\t\t\tpropertyText.select(curs+1, curs+4);\n\t\t}\n\t\telse if(e.getSource() == steadyStateButton)\n\t\t{\n\t\t\tint curs = propertyText.getCaretPosition();\n\t\t\taddString(\"S><p [ () ]\", CURSOR, 1);\n\t\t\tpropertyText.select(curs+1, curs+4);\n\t\t}\n\t\telse if(e.getSource() == cut)\n\t\t{\n\t\t\tif(propertyText.getSelectedText() != null)\n\t\t\t{\n\t\t\t\tpropertyText.cut();\n\t\t\t\tpropertyText.requestFocus();\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t}\n\t\t}\n\t\telse if(e.getSource() == copy)\n\t\t{\n\t\t\tif(propertyText.getSelectedText() != null)\n\t\t\t{\n\t\t\t\tpropertyText.copy();\n\t\t\t\tpropertyText.requestFocus();\n\t\t\t}\n\t\t\telse\n\t\t\t{\n\t\t\t}\n\t\t}\n\t\telse if(e.getSource() == paste)\n\t\t{\n\t\t\t\n\t\t\tpropertyText.paste();\n\t\t\tpropertyText.requestFocus();\n\t\t}\n\t\tif (e.getSource() == okayButton)\n\t\t{\n\t\t\t//okayButtonActionPerformed(e);\n\t\t}\n\t\telse if(e.getSource() == cancelButton)\n\t\t{\n\t\t\tsetVisible(false);\n\t\t\tprops.cancelProperty(id);\n\t\t\tdispose();\n\t\t}\n\t\t\n\t}\n\t\n\t/** Needed to implement the KeyListener interface.  This method looks for the\n\t * 'enter' key.  If the 'enter' key is pressed, the cursor position shifts to the\n\t * next sensible location in the property expression.\n\t * @param e generated by a key press in the text box\n\t */\n\tpublic void keyPressed(KeyEvent e)\n\t{\n\t\t\n\t\tif(e.getKeyCode() == KeyEvent.VK_ENTER)\n\t\t{\n\t\t\tint caret = propertyText.getCaretPosition();\n\t\t\tboolean found = false;\n\t\t\tboolean k\t = false;\n\t\t\tint i = caret;\n\t\t\tfor(i = caret; i < propertyText.getText().length(); i++)\n\t\t\t{\n\t\t\t\tif(propertyText.getText().charAt(i) == '(')\n\t\t\t\t{found = true; break;}\n\t\t\t\tif(propertyText.getText().charAt(i) == 'k')\n\t\t\t\t{found = true; k = true; break;}\n\t\t\t}\n\t\t\tif(found)\n\t\t\t{\n\t\t\t\tif(k)\n\t\t\t\t{\n\t\t\t\t\tpropertyText.setCaretPosition(i);\n\t\t\t\t\tpropertyText.select(i, i+1);\n\t\t\t\t}\n\t\t\t\telse\n\t\t\t\t{\n\t\t\t\t\tpropertyText.setCaretPosition(i+1);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\tif(e.getKeyCode() == KeyEvent.VK_ESCAPE)\n\t\t{\n\t\t\tsetVisible(false);\n\t\t\tprops.cancelProperty(id);\n\t\t\tdispose();\n\t\t}\n\t}\n\t\n\t/** Needed to implement the KeyListener interface.\n\t * @param e generated by a key press in the text box\n\t */\n\tpublic void keyReleased(KeyEvent e)\n\t{\n\t\t\n\t}\n\t\n\t/** Needed to implement the KeyListener interface.\n\t * @param e generated by a key press in the text box\n\t */\n\tpublic void keyTyped(KeyEvent e)\n\t{\n\t\t//System.out.println(\"keytyped\");\n\t\t\n\t}\n\t\n\tprivate void addActionListeners()\n\t{\n\t\ttrueButton.addActionListener(this);\n\t\tfalseButton.addActionListener(this);\n\t\tandButton.addActionListener(this);\n\t\torButton.addActionListener(this);\n\t\tnotButton.addActionListener(this);\n\t\tnextButton.addActionListener(this);\n\t\tboundedUntilButton.addActionListener(this);\n\t\tuntilButton.addActionListener(this);\n\t\tsteadyStateButton.addActionListener(this);\n\t\tpropertyText.addKeyListener(this);\n\t\tthis.addKeyListener(this);\n\t\t\n\t\tcut.addActionListener(this);\n\t\tcopy.addActionListener(this);\n\t\tpaste.addActionListener(this);\n\t\t\n\t\tokayButton.addActionListener(this);\n\t\tcancelButton.addActionListener(this);\n\t}\n\t\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n    private void initComponents() {//GEN-BEGIN:initComponents\n        java.awt.GridBagConstraints gridBagConstraints;\n\n        jPanel1 = new javax.swing.JPanel();\n        jPanel3 = new javax.swing.JPanel();\n        jPanel4 = new javax.swing.JPanel();\n        jPanel5 = new javax.swing.JPanel();\n        jPanel6 = new javax.swing.JPanel();\n        jToolBar1 = new javax.swing.JToolBar();\n        cut = new javax.swing.JButton();\n        copy = new javax.swing.JButton();\n        paste = new javax.swing.JButton();\n        jPanel7 = new javax.swing.JPanel();\n        jPanel9 = new javax.swing.JPanel();\n        jPanel10 = new javax.swing.JPanel();\n        propertyText = new javax.swing.JTextField();\n        jLabel1 = new javax.swing.JLabel();\n        jPanel8 = new javax.swing.JPanel();\n        trueButton = new javax.swing.JButton();\n        andButton = new javax.swing.JButton();\n        notButton = new javax.swing.JButton();\n        untilButton = new javax.swing.JButton();\n        steadyStateButton = new javax.swing.JButton();\n        falseButton = new javax.swing.JButton();\n        orButton = new javax.swing.JButton();\n        nextButton = new javax.swing.JButton();\n        boundedUntilButton = new javax.swing.JButton();\n        jPanel11 = new javax.swing.JPanel();\n        jPanel12 = new javax.swing.JPanel();\n        jPanel13 = new javax.swing.JPanel();\n        jPanel14 = new javax.swing.JPanel();\n        jPanel15 = new javax.swing.JPanel();\n        jPanel16 = new javax.swing.JPanel();\n        jLabel2 = new javax.swing.JLabel();\n        jScrollPane1 = new javax.swing.JScrollPane();\n        commentTextArea = new javax.swing.JTextArea();\n        jPanel2 = new javax.swing.JPanel();\n        okayButton = new javax.swing.JButton();\n        cancelButton = new javax.swing.JButton();\n\n        setResizable(false);\n        addWindowListener(new java.awt.event.WindowAdapter() {\n            public void windowClosing(java.awt.event.WindowEvent evt) {\n                closeDialog(evt);\n            }\n        });\n\n        jPanel1.setLayout(new java.awt.GridBagLayout());\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n        jPanel1.add(jPanel3, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 2;\n        gridBagConstraints.gridy = 0;\n        jPanel1.add(jPanel4, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 2;\n        jPanel1.add(jPanel5, gridBagConstraints);\n\n        jPanel6.setLayout(new java.awt.BorderLayout());\n\n        jToolBar1.setFloatable(false);\n        cut.setIcon(GUIPrism.getIconFromImage(\"smallCut.png\"));\n        jToolBar1.add(cut);\n\n        copy.setIcon(GUIPrism.getIconFromImage(\"smallCopy.png\"));\n        jToolBar1.add(copy);\n\n        paste.setIcon(GUIPrism.getIconFromImage(\"smallPaste.png\"));\n        jToolBar1.add(paste);\n\n        jPanel6.add(jToolBar1, java.awt.BorderLayout.NORTH);\n\n        jPanel7.setLayout(new java.awt.GridBagLayout());\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 4;\n        gridBagConstraints.gridy = 0;\n        jPanel7.add(jPanel9, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 2;\n        gridBagConstraints.gridy = 1;\n        jPanel7.add(jPanel10, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 3;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.gridwidth = 10;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.weightx = 1.0;\n        jPanel7.add(propertyText, gridBagConstraints);\n\n        jLabel1.setLabelFor(propertyText);\n        jLabel1.setText(\"Property:\");\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        jPanel7.add(jLabel1, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 2;\n        jPanel7.add(jPanel8, gridBagConstraints);\n\n        trueButton.setText(\"true\");\n        trueButton.setPreferredSize(new java.awt.Dimension(123, 25));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 3;\n        gridBagConstraints.gridy = 3;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(trueButton, gridBagConstraints);\n\n        andButton.setText(\"And\");\n        andButton.setPreferredSize(new java.awt.Dimension(123, 25));\n        andButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                andButtonActionPerformed(evt);\n            }\n        });\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 5;\n        gridBagConstraints.gridy = 3;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(andButton, gridBagConstraints);\n\n        notButton.setText(\"Not\");\n        notButton.setPreferredSize(new java.awt.Dimension(123, 25));\n        notButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                notButtonActionPerformed(evt);\n            }\n        });\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 7;\n        gridBagConstraints.gridy = 3;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(notButton, gridBagConstraints);\n\n        untilButton.setText(\"Until\");\n        untilButton.setPreferredSize(new java.awt.Dimension(123, 25));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 9;\n        gridBagConstraints.gridy = 3;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(untilButton, gridBagConstraints);\n\n        steadyStateButton.setText(\"Steady-state\");\n        steadyStateButton.setPreferredSize(new java.awt.Dimension(123, 25));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 11;\n        gridBagConstraints.gridy = 3;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(steadyStateButton, gridBagConstraints);\n\n        falseButton.setText(\"false\");\n        falseButton.setPreferredSize(new java.awt.Dimension(123, 25));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 3;\n        gridBagConstraints.gridy = 5;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(falseButton, gridBagConstraints);\n\n        orButton.setText(\"Or\");\n        orButton.setPreferredSize(new java.awt.Dimension(123, 25));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 5;\n        gridBagConstraints.gridy = 5;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(orButton, gridBagConstraints);\n\n        nextButton.setText(\"Next\");\n        nextButton.setPreferredSize(new java.awt.Dimension(123, 25));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 7;\n        gridBagConstraints.gridy = 5;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(nextButton, gridBagConstraints);\n\n        boundedUntilButton.setText(\"Bounded Until\");\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 9;\n        gridBagConstraints.gridy = 5;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.2;\n        jPanel7.add(boundedUntilButton, gridBagConstraints);\n\n        jPanel7.add(jPanel11, new java.awt.GridBagConstraints());\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 6;\n        gridBagConstraints.gridy = 0;\n        jPanel7.add(jPanel12, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 8;\n        gridBagConstraints.gridy = 0;\n        jPanel7.add(jPanel13, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 10;\n        gridBagConstraints.gridy = 0;\n        jPanel7.add(jPanel14, gridBagConstraints);\n\n        jPanel15.setPreferredSize(new java.awt.Dimension(10, 5));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 4;\n        jPanel7.add(jPanel15, gridBagConstraints);\n\n        jPanel16.setPreferredSize(new java.awt.Dimension(10, 20));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 6;\n        jPanel7.add(jPanel16, gridBagConstraints);\n\n        jLabel2.setText(\"Comment:\");\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 7;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.NORTH;\n        jPanel7.add(jLabel2, gridBagConstraints);\n\n        commentTextArea.setRows(3);\n        jScrollPane1.setViewportView(commentTextArea);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 3;\n        gridBagConstraints.gridy = 7;\n        gridBagConstraints.gridwidth = 10;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n        gridBagConstraints.weightx = 1.0;\n        jPanel7.add(jScrollPane1, gridBagConstraints);\n\n        jPanel6.add(jPanel7, java.awt.BorderLayout.CENTER);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n        gridBagConstraints.weightx = 1.0;\n        gridBagConstraints.weighty = 1.0;\n        jPanel1.add(jPanel6, gridBagConstraints);\n\n        getContentPane().add(jPanel1, java.awt.BorderLayout.CENTER);\n\n        jPanel2.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n        okayButton.setMnemonic('O');\n        okayButton.setText(\"Okay\");\n        okayButton.addActionListener(new java.awt.event.ActionListener() {\n            public void actionPerformed(java.awt.event.ActionEvent evt) {\n                okayButtonActionPerformed(evt);\n            }\n        });\n\n        jPanel2.add(okayButton);\n\n        cancelButton.setMnemonic('C');\n        cancelButton.setText(\"Cancel\");\n        jPanel2.add(cancelButton);\n\n        getContentPane().add(jPanel2, java.awt.BorderLayout.SOUTH);\n        \n        pack();\n    }//GEN-END:initComponents\n\n    private void andButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_andButtonActionPerformed\n        // Add your handling code here:\n    }//GEN-LAST:event_andButtonActionPerformed\n\n    private void notButtonActionPerformed(java.awt.event.ActionEvent evt) {//GEN-FIRST:event_notButtonActionPerformed\n        // Add your handling code here:\n    }//GEN-LAST:event_notButtonActionPerformed\n\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\t\tboolean valid = false;\n\t\tint noLabels = 0;\n\t\tint noConstants = 0;\n\t\t\n\t\ttry\n\t\t{\n\t\t\t//Parse constants and labels\n\t\t\tPropertiesFile fConLab = props.getPrism().parsePropertiesString(props.getLabelsString()+\"\\n\"+props.getConstantsString());\n\t\t\tnoConstants = fConLab.getConstantList().size();\n\t\t\tnoLabels = fConLab.getLabelList().size();\n\t\t\t\n\t\t\tString namedString = \"\";\n\t\t\tint namedCount = 0;\n\t\t\t//Add named properties\n\t\t\tfor (GUIProperty namedProp : this.props.getPropList().getAllNamedProperties()) {\n\t\t\t\tif (namedProp.isValid() && this.id != null && !this.id.equals(namedProp.getID())) {\n\t\t\t\t\tnamedCount++;\n\t\t\t\t\tnamedString += \"\\\"\" + namedProp.getName() + \"\\\" : \" + namedProp.getPropString() + \"\\n\";\n\t\t\t\t}\n\t\t\t}\n\t\t\t\n\t\t\t//Parse all together\n\t\t\tString withConsLabs = props.getConstantsString()+\"\\n\"+props.getLabelsString()+namedString+propertyText.getText();\n\t\t\tPropertiesFile ff = props.getPrism().parsePropertiesString(withConsLabs);\n\t\t\t\n\t\t\t//Validation of number of properties\n\t\t\tif(ff.getNumProperties() <= namedCount) throw new PrismException(\"Empty property\");\n\t\t\telse if(ff.getNumProperties() > namedCount + 1) throw new PrismException(\"Contains multiple properties\");\n\t\t\t\n\t\t\t//Validation of constants and labels\n\t\t\tif(ff.getConstantList().size() != noConstants) throw new PrismException(\"Contains constants\");\n\t\t\tif(ff.getLabelList().size() != noLabels) throw new PrismException(\"Contains labels\");\n\t\t\t\n\t\t\tvalid = true;\n\t\t}\n\t\t// catch and deal with exceptions\n\t\tcatch(prism.PrismException ex)\n\t\t{\n\t\t\tswitch(propertyInvalidStrategy)\n\t\t\t{\n\t\t\t\tcase GUIMultiProperties.WARN_INVALID_PROPS:\n\t\t\t\t{\n\t\t\t\t\tString[] choices = {\"Yes\", \"No\"};\n\t\t\t\t\tint choice = -1;\n\t\t\t\t\tchoice = props.optionPane(\"Error: \"+ex.getMessage()+\"\\nAre you sure you want to continue?\", \"Question\", JOptionPane.YES_NO_OPTION, JOptionPane.QUESTION_MESSAGE, choices, choices[0]);\n\t\t\t\t\tvalid = (choice == 0);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t\tcase GUIMultiProperties.NEVER_INVALID_PROPS:\n\t\t\t\t{\n\t\t\t\t\tparent.errorDialog(\"Error: \"+ex.getMessage());\n\t\t\t\t\tvalid = false;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tif(valid)\n\t\t{\n\t\t\tsetVisible(false);\n\t\t\tprops.changeProperty(propertyText.getText(), commentTextArea.getText(), id);\n\t\t\tdispose();\n\t\t}\n\t}//GEN-LAST:event_okayButtonActionPerformed\n\t\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tprops.cancelProperty(id);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JButton andButton;\n    private javax.swing.JButton boundedUntilButton;\n    private javax.swing.JButton cancelButton;\n    private javax.swing.JTextArea commentTextArea;\n    private javax.swing.JButton copy;\n    private javax.swing.JButton cut;\n    private javax.swing.JButton falseButton;\n    private javax.swing.JLabel jLabel1;\n    private javax.swing.JLabel jLabel2;\n    private javax.swing.JPanel jPanel1;\n    private javax.swing.JPanel jPanel10;\n    private javax.swing.JPanel jPanel11;\n    private javax.swing.JPanel jPanel12;\n    private javax.swing.JPanel jPanel13;\n    private javax.swing.JPanel jPanel14;\n    private javax.swing.JPanel jPanel15;\n    private javax.swing.JPanel jPanel16;\n    private javax.swing.JPanel jPanel2;\n    private javax.swing.JPanel jPanel3;\n    private javax.swing.JPanel jPanel4;\n    private javax.swing.JPanel jPanel5;\n    private javax.swing.JPanel jPanel6;\n    private javax.swing.JPanel jPanel7;\n    private javax.swing.JPanel jPanel8;\n    private javax.swing.JPanel jPanel9;\n    private javax.swing.JScrollPane jScrollPane1;\n    private javax.swing.JToolBar jToolBar1;\n    private javax.swing.JButton nextButton;\n    private javax.swing.JButton notButton;\n    private javax.swing.JButton okayButton;\n    private javax.swing.JButton orButton;\n    private javax.swing.JButton paste;\n    private javax.swing.JTextField propertyText;\n    private javax.swing.JButton steadyStateButton;\n    private javax.swing.JButton trueButton;\n    private javax.swing.JButton untilButton;\n    // End of variables declaration//GEN-END:variables\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIPropertyResultDialog.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <Properties>\n    <Property name=\"defaultCloseOperation\" type=\"int\" value=\"2\"/>\n  </Properties>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,2,58\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n        <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n      </Layout>\n      <SubComponents>\n        <Component class=\"javax.swing.JButton\" name=\"jButton1\">\n          <Properties>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"jButton1ActionPerformed\"/>\n          </Events>\n        </Component>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel10\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n          <Properties>\n            <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n              <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n            </Property>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n                <LineBorder roundedCorners=\"true\"/>\n              </Border>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n          <SubComponents>\n            <Component class=\"javax.swing.JLabel\" name=\"jLabel1\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Property:\"/>\n              </Properties>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"&#xa;Font cur = jLabel1.getFont();&#xa;jLabel1.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"2\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Component class=\"javax.swing.JLabel\" name=\"propertyLabel\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"dummydummydummydummydummydummy\"/>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"2\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Component class=\"javax.swing.JLabel\" name=\"jLabel3\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Defined constants:\"/>\n              </Properties>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"cur = jLabel3.getFont();&#xa;jLabel3.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"1\" gridY=\"4\" gridWidth=\"2\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Component class=\"javax.swing.JLabel\" name=\"constantsLabel\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"dummy dummy dummy dummy dummy dummy dummy dummy dummy\"/>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"2\" gridY=\"5\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Component class=\"javax.swing.JLabel\" name=\"jLabel5\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Method:\"/>\n              </Properties>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"cur = jLabel5.getFont();&#xa;jLabel5.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"1\" gridY=\"7\" gridWidth=\"2\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[20, 10]\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"1\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Component class=\"javax.swing.JLabel\" name=\"methodLabel\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"dummy dummy dummy dummy dummy dummy dummy dummy dummy\"/>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"2\" gridY=\"8\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel5\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"0\" gridY=\"3\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel6\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"0\" gridY=\"6\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel7\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"3\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Component class=\"javax.swing.JLabel\" name=\"jLabel8\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Result:\"/>\n              </Properties>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"cur = jLabel8.getFont();&#xa;jLabel8.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"1\" gridY=\"10\" gridWidth=\"2\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Component class=\"javax.swing.JLabel\" name=\"resultLabel\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"dummy dummy dummy dummy dummy dummy dummy dummy dummy\"/>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"2\" gridY=\"11\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel8\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"0\" gridY=\"9\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel9\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                  <GridBagConstraints gridX=\"0\" gridY=\"12\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel11\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel12\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"0\" gridY=\"2\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel13\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n              <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIPropertyResultDialog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.awt.Font;\n\npublic class GUIPropertyResultDialog extends javax.swing.JDialog\n{\n\tprivate static int noOpen = 0;\n\t\n\tprivate GUIProperty gp;\n\tprivate GUIMultiProperties gmp;\n\t\n\t/** Creates new form GUIPropertyResultDialog */\n\tpublic GUIPropertyResultDialog(java.awt.Frame parent, GUIMultiProperties gmp, GUIProperty gp)\n\t{\n\t\tsuper(parent, false);\n\t\t\n\t\tinitComponents();\n\t\tgetRootPane().setDefaultButton(jButton1);\n\t\tsetTitle(\"Property Details\");\n\n\t\tif (!(\"Result\".equals(gp.getProperty().getResultName())))\n\t\t\tjLabel8.setText(\"Result (\"+gp.getProperty().getResultName().toLowerCase()+\"):\");\n\t\t\n\t\tpropertyLabel.setText(gp.getPropString());\n\t\tconstantsLabel.setText(gp.getConstantsString());\n\t\tmethodLabel.setText(gp.getMethodString());\n\t\tresultLabel.setText(\"<html>\" + gp.getResultString().replaceAll(\"\\n\", \"<br/>\") + \"</html>\");\n\t\tif (gp.getNumberOfWarnings() == 0) {\n\t\t\twarningLabel.setText(\"\");\n\t\t} else if (gp.getNumberOfWarnings() == 1) {\n\t\t\twarningLabel.setText(gp.getNumberOfWarnings() + \" warning (see log)\");\n\t\t} else {\n\t\t\twarningLabel.setText(gp.getNumberOfWarnings() + \" warnings (see log)\");\n\t\t}\n\t\t\t\n\t\tthis.gp = gp;\n\t\tthis.gmp = gmp;\n\t\t\n\t\tpack();\n\t\tsetLocation(getParent().getX(), getParent().getY());\n\t}\n\t\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\tprivate void initComponents()//GEN-BEGIN:initComponents\n\t{\n\t\tjava.awt.GridBagConstraints gridBagConstraints;\n\n\t\tjPanel2 = new javax.swing.JPanel();\n\t\tjButton1 = new javax.swing.JButton();\n\t\tjPanel10 = new javax.swing.JPanel();\n\t\tjPanel1 = new javax.swing.JPanel();\n\t\tjLabel1 = new javax.swing.JLabel();\n\n\t\tFont cur = jLabel1.getFont();\n\t\tjLabel1.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\n\t\tpropertyLabel = new javax.swing.JLabel();\n\t\tjLabel3 = new javax.swing.JLabel();\n\t\tcur = jLabel3.getFont();\n\t\tjLabel3.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\n\t\tconstantsLabel = new javax.swing.JLabel();\n\t\tjLabel5 = new javax.swing.JLabel();\n\t\tcur = jLabel5.getFont();\n\t\tjLabel5.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\n\t\tjPanel3 = new javax.swing.JPanel();\n\t\tmethodLabel = new javax.swing.JLabel();\n\t\tjPanel4 = new javax.swing.JPanel();\n\t\tjPanel5 = new javax.swing.JPanel();\n\t\tjPanel6 = new javax.swing.JPanel();\n\t\tjPanel7 = new javax.swing.JPanel();\n\t\tjLabel8 = new javax.swing.JLabel();\n\t\tcur = jLabel8.getFont();\n\t\tjLabel8.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\n\t\tresultLabel = new javax.swing.JLabel();\n\t\tjPanel8 = new javax.swing.JPanel();\n\t\twarningLabel = new javax.swing.JLabel();\n\t\tcur = warningLabel.getFont();\n\t\twarningLabel.setFont(new Font(cur.getName(), Font.BOLD, cur.getSize()));\n\t\tjPanel14 = new javax.swing.JPanel();\n\t\tjPanel9 = new javax.swing.JPanel();\n\t\tjPanel11 = new javax.swing.JPanel();\n\t\tjPanel12 = new javax.swing.JPanel();\n\t\tjPanel13 = new javax.swing.JPanel();\n\n        addWindowListener(new java.awt.event.WindowAdapter() {\n            public void windowClosing(java.awt.event.WindowEvent evt) {\n                closeDialog();\n            }\n        });\n        \n\t\tjPanel2.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tjButton1.setText(\"Okay\");\n\t\tjButton1.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tjButton1ActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tjPanel2.add(jButton1);\n\n\t\tgetContentPane().add(jPanel2, java.awt.BorderLayout.SOUTH);\n\t\t\n\t\tjPanel10.setLayout(new java.awt.GridBagLayout());\n\n\t\tjPanel1.setLayout(new java.awt.GridBagLayout());\n\n\t\tjPanel1.setBackground(new java.awt.Color(255, 255, 255));\n\t\tjPanel1.setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0), 1, true));\n\t\tjLabel1.setText(\"Property:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(jLabel1, gridBagConstraints);\n\n\t\tpropertyLabel.setText(\"dummydummydummydummydummydummy\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 2;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(propertyLabel, gridBagConstraints);\n\n\t\tjLabel3.setText(\"Defined constants:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 4;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(jLabel3, gridBagConstraints);\n\n\t\tconstantsLabel.setText(\"dummy dummy dummy dummy dummy dummy dummy dummy dummy\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 5;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(constantsLabel, gridBagConstraints);\n\n\t\tjLabel5.setText(\"Method:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 7;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(jLabel5, gridBagConstraints);\n\n\t\tjPanel3.setBackground(new java.awt.Color(255, 255, 255));\n\t\tjPanel3.setPreferredSize(new java.awt.Dimension(20, 10));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 2;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(jPanel3, gridBagConstraints);\n\n\t\tmethodLabel.setText(\"dummy dummy dummy dummy dummy dummy dummy dummy dummy\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 8;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(methodLabel, gridBagConstraints);\n\n\t\tjPanel4.setBackground(new java.awt.Color(255, 255, 255));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel1.add(jPanel4, gridBagConstraints);\n\n\t\tjPanel5.setBackground(new java.awt.Color(255, 255, 255));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 3;\n\t\tjPanel1.add(jPanel5, gridBagConstraints);\n\n\t\tjPanel6.setBackground(new java.awt.Color(255, 255, 255));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 6;\n\t\tjPanel1.add(jPanel6, gridBagConstraints);\n\n\t\tjPanel7.setBackground(new java.awt.Color(255, 255, 255));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel1.add(jPanel7, gridBagConstraints);\n\n\t\tjLabel8.setText(\"Result:\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 10;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(jLabel8, gridBagConstraints);\n\n\t\tresultLabel.setText(\"dummy dummy dummy dummy dummy dummy dummy dummy dummy\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 11;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(resultLabel, gridBagConstraints);\n\n\t\tjPanel8.setBackground(new java.awt.Color(255, 255, 255));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 9;\n\t\tjPanel1.add(jPanel8, gridBagConstraints);\n\n\t\tjPanel9.setBackground(new java.awt.Color(255, 255, 255));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 12;\n\t\tjPanel1.add(jPanel9, gridBagConstraints);\n\t\t\n\t\twarningLabel.setText(\"dummy dummy\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 13;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n\t\tjPanel1.add(warningLabel, gridBagConstraints);\n\n\t\tjPanel14.setBackground(new java.awt.Color(255, 255, 255));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 14;\n\t\tjPanel1.add(jPanel14, gridBagConstraints);\n\t\t\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 1;\n\t\tgridBagConstraints.gridy = 1;\n\t\tjPanel10.add(jPanel1, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel10.add(jPanel11, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 2;\n\t\tjPanel10.add(jPanel12, gridBagConstraints);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 0;\n\t\tjPanel10.add(jPanel13, gridBagConstraints);\n\n\t\tgetContentPane().add(jPanel10, java.awt.BorderLayout.CENTER);\n\n\t\tpack();\n\t}//GEN-END:initComponents\n\n\tprivate void jButton1ActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_jButton1ActionPerformed\n\t{//GEN-HEADEREND:event_jButton1ActionPerformed\n\t\tcloseDialog();\n\t}//GEN-LAST:event_jButton1ActionPerformed\n\t\n\t/** Closes the dialog */\n\tprivate void closeDialog()\n\t{\n\t\tgp.setBeingEdited(false);\n\t\tgmp.repaintList();\n\t\tsetVisible(false);\n\t\tdispose();\n\t}\n\n\tpublic void display()\n\t{\n\t\tnoOpen++;\n\t\tsetLocation(getX()+(noOpen*50), getY()+(noOpen*50));\n\t\tsuper.setVisible(true);\n\t}\n\t\n\tpublic void dispose()\n\t{\n\t\tnoOpen--;\n\t\tsuper.dispose();\n\t}\n\t\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tprivate javax.swing.JLabel constantsLabel;\n\tprivate javax.swing.JButton jButton1;\n\tprivate javax.swing.JLabel jLabel1;\n\tprivate javax.swing.JLabel jLabel3;\n\tprivate javax.swing.JLabel jLabel5;\n\tprivate javax.swing.JLabel jLabel8;\n\tprivate javax.swing.JLabel warningLabel;\n\tprivate javax.swing.JPanel jPanel1;\n\tprivate javax.swing.JPanel jPanel10;\n\tprivate javax.swing.JPanel jPanel11;\n\tprivate javax.swing.JPanel jPanel12;\n\tprivate javax.swing.JPanel jPanel13;\n\tprivate javax.swing.JPanel jPanel14;\n\tprivate javax.swing.JPanel jPanel2;\n\tprivate javax.swing.JPanel jPanel3;\n\tprivate javax.swing.JPanel jPanel4;\n\tprivate javax.swing.JPanel jPanel5;\n\tprivate javax.swing.JPanel jPanel6;\n\tprivate javax.swing.JPanel jPanel7;\n\tprivate javax.swing.JPanel jPanel8;\n\tprivate javax.swing.JPanel jPanel9;\n\tprivate javax.swing.JLabel methodLabel;\n\tprivate javax.swing.JLabel propertyLabel;\n\tprivate javax.swing.JLabel resultLabel;\n\t// End of variables declaration//GEN-END:variables\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GUIResultsTable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport javax.swing.table.*;\nimport java.util.*; \nimport userinterface.*;\n\npublic class GUIResultsTable extends javax.swing.JDialog\n{\n\tprivate static int noOpen = 0;\n\t\n\tprivate GUIMultiProperties guiProps;\n\tprivate GUIExperiment exp;\n\t\n\tprivate JPanel topPanel;\n\tprivate JButton closeButton;\n\t\n\tprivate JScrollPane scroller;\n\tprivate JTable table;\n\tprivate ResultsTableModel tableModel;\n\t\n\t/** Creates a new instance of GUIResultsTable */\n\tpublic GUIResultsTable(GUIPrism parent, GUIMultiProperties guiProps, GUIExperiment exp)\n\t{\n\t\tsuper(parent, \"Experiment Results\", false);\n\t\tthis.guiProps = guiProps;\n\t\tthis.exp = exp;\n\t\t\n\t\t//setup table\n\t\ttableModel = new ResultsTableModel(exp);\n\t\ttable = new JTable();\n\t\ttable.setModel(tableModel);\n\t\ttable.setCellSelectionEnabled(true);\n\t\ttable.setRowHeight(getFontMetrics(table.getFont()).getHeight() + 4);\n\t\t\n\t\t//initialise\n\t\tinitComponents();\n\t\tgetRootPane().setDefaultButton(closeButton);\n\t\tsetResizable(true);\n\t\tpack();\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t}\n\n\t/** This method is called from within the constructor to initialize the form. */\n\t\n\tprivate void initComponents()\n\t{\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog();\n\t\t\t}\n\t\t});\n\t\t\n\t\tJLabel topLabel = new JLabel(\"Results of \\'\" + exp.getExpressionString() + \"\\' for \\'\" + exp.getDefinedConstantsString() + \"\\'\"); \n\t\t\t\t\n\t\tJPanel tmpPanel = new JPanel();\n\t\ttmpPanel.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));\n\t\t\n\t\ttmpPanel.setLayout(new BorderLayout(10, 10));\n\t\ttmpPanel.add(topLabel, BorderLayout.NORTH);\n\t\ttmpPanel.add(topLabel, BorderLayout.NORTH);\n\t\t\n\t\ttopPanel = new JPanel();\n\t\ttopPanel.setBorder(new TitledBorder(\"Results\"));\n\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\n\t\tJPanel borderPanel = new JPanel();\n\t\tborderPanel.setBorder(BorderFactory.createEmptyBorder(10, 10, 10, 10));\n\t\tborderPanel.setLayout(new BorderLayout());\n\t\t\n\t\tJScrollPane sp = new JScrollPane();\n\t\tsp.setViewportView(table);\n\t\tborderPanel.add(sp, BorderLayout.CENTER);\n\t\ttopPanel.add(borderPanel);\n\t\ttopPanel.setPreferredSize(new Dimension(500,200));\n\t\t\n\t\ttmpPanel.add(topPanel, BorderLayout.CENTER);\n\t\t\n\t\tJPanel tmpPanel2 = new JPanel();\n\t\ttmpPanel2.setLayout(new BorderLayout());\n\t\t\t\n\t\tcloseButton = new JButton(\"Close\");\n\n\t\tcloseButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog();\n\t\t\t}\n\t\t});\n\t\t\n\t\ttmpPanel2.add(closeButton, BorderLayout.EAST);\t\t\n\t\t\n\t\ttmpPanel.add(tmpPanel2, BorderLayout.SOUTH);\n\t\tthis.getContentPane().add(tmpPanel);\n\t}\n\n\tpublic void show()\n\t{\n\t\tnoOpen++;\n\t\tsetLocation(getX()+(noOpen*50), getY()+(noOpen*50));\n\t\tsuper.show();\n\t}\n\t\n\tpublic void dispose()\n\t{\n\t\tnoOpen--;\n\t\tsuper.dispose();\n\t}\n\t\n\tprivate void closeDialog()\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}\n\n\tclass ResultsTableModel extends AbstractTableModel\n\t{\n\t\tString headings[];\n\t\tArrayList cells;\n\t\tint numRows, numCols;\n\t\t\n\t\tpublic ResultsTableModel(GUIExperiment exp)\n\t\t{\n\t\t\theadings = exp.getResults().getHeadingsArray();\n\t\t\tcells = exp.getResults().toArrayList();\n\t\t\tnumRows = cells.size();\n\t\t\tnumCols = headings.length;\n\t\t\t//prop = new ArrayList();\n\t\t}\n\n\t\tpublic String getColumnName(int j)\n\t\t{\n\t\t\treturn headings[j];\n\t\t}\n\n\t\tpublic int getColumnCount()\n\t\t{\n\t\t\treturn numCols;\n\t\t}\n\n\t\tpublic int getRowCount()\n\t\t{\n\t\t\treturn numRows;\n\t\t}\n\n\t\tpublic Object getValueAt(int i, int j)\n\t\t{\n\t\t\tString[] line = (String[])cells.get(i);\n\t\t\tif (j<line.length) return line[j];\n\t\t\treturn \"?\";\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GraphConstantHeader.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n  <Properties>\n    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n      <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n        <LineBorder/>\n      </Border>\n    </Property>\n    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n      <Dimension value=\"[300, 17]\"/>\n    </Property>\n  </Properties>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,39,0,0,1,52\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel1\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Name\"/>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[30, 15]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[30, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"1\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.3\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"2\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel2\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Type\"/>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[50, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"4\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JLabel\" name=\"jLabel3\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Value\"/>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[10, 15]\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"6\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.7\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/properties/GraphConstantHeader.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.awt.*;\n\npublic class GraphConstantHeader extends javax.swing.JPanel\n{\n    \n    /** Creates new form ConstantLine */\n    public GraphConstantHeader()\n    {\n\t\tinitComponents();\n\t\tsetPreferredSize(new Dimension(1, getFontMetrics(getFont()).getHeight() + 4));\n    }\n    \n    public void setEnabled(boolean b)\n    {\n        super.setEnabled(b);\n        jLabel1.setEnabled(b);\n        jLabel2.setEnabled(b);\n        jLabel3.setEnabled(b);\n    }\n    /** This method is called from within the constructor to\n     * initialize the form.\n     * WARNING: Do NOT modify this code. The content of this method is\n     * always regenerated by the Form Editor.\n     */\n    private void initComponents()//GEN-BEGIN:initComponents\n    {\n        java.awt.GridBagConstraints gridBagConstraints;\n\n        jPanel1 = new javax.swing.JPanel();\n        jLabel1 = new javax.swing.JLabel();\n        jPanel2 = new javax.swing.JPanel();\n        jLabel2 = new javax.swing.JLabel();\n        jPanel3 = new javax.swing.JPanel();\n        jLabel3 = new javax.swing.JLabel();\n\n        setLayout(new java.awt.GridBagLayout());\n\n        setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0)));\n        setPreferredSize(new java.awt.Dimension(300, 17));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 1;\n        add(jPanel1, gridBagConstraints);\n\n        jLabel1.setText(\"Name\");\n        jLabel1.setMinimumSize(new java.awt.Dimension(30, 15));\n        jLabel1.setPreferredSize(new java.awt.Dimension(30, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.3;\n        add(jLabel1, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 2;\n        gridBagConstraints.gridy = 1;\n        add(jPanel2, gridBagConstraints);\n\n        jLabel2.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel2.setText(\"Type\");\n        jLabel2.setPreferredSize(new java.awt.Dimension(50, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 3;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        add(jLabel2, gridBagConstraints);\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 4;\n        gridBagConstraints.gridy = 1;\n        add(jPanel3, gridBagConstraints);\n\n        jLabel3.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n        jLabel3.setText(\"Value\");\n        jLabel3.setPreferredSize(new java.awt.Dimension(10, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 6;\n        gridBagConstraints.gridy = 1;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.7;\n        add(jLabel3, gridBagConstraints);\n\n    }//GEN-END:initComponents\n    \n    \n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JLabel jLabel1;\n    private javax.swing.JLabel jLabel2;\n    private javax.swing.JLabel jLabel3;\n    private javax.swing.JPanel jPanel1;\n    private javax.swing.JPanel jPanel2;\n    private javax.swing.JPanel jPanel3;\n    // End of variables declaration//GEN-END:variables\n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GraphConstantLine.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n  <NonVisualComponents>\n    <Component class=\"javax.swing.ButtonGroup\" name=\"choiceButtonGroup\">\n    </Component>\n    <Component class=\"javax.swing.JComboBox\" name=\"boolSingleValueCombo\">\n      <Properties>\n        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n        </Property>\n        <Property name=\"model\" type=\"javax.swing.ComboBoxModel\" editor=\"org.netbeans.modules.form.editors2.ComboBoxModelEditor\">\n          <StringArray count=\"2\">\n            <StringItem index=\"0\" value=\"true\"/>\n            <StringItem index=\"1\" value=\"false\"/>\n          </StringArray>\n        </Property>\n        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[4, 19]\"/>\n        </Property>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[4, 19]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"sizerPanel\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n  </NonVisualComponents>\n  <Properties>\n    <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n      <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n    </Property>\n    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n      <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n        <LineBorder/>\n      </Border>\n    </Property>\n    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n      <Dimension value=\"[300, 26]\"/>\n    </Property>\n  </Properties>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,36,0,0,1,68\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <Properties>\n        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JLabel\" name=\"nameLabel\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"a\"/>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[30, 15]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"1\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.3\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n      <Properties>\n        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JLabel\" name=\"typeLabel\">\n      <Properties>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"double\"/>\n        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n          <Dimension value=\"[50, 15]\"/>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"3\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"17\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n      <Properties>\n        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"4\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n    </Container>\n    <Component class=\"javax.swing.JComboBox\" name=\"valuePicker\">\n      <Properties>\n        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n        </Property>\n      </Properties>\n      <Events>\n        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"valuePickerActionPerformed\"/>\n      </Events>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n          <GridBagConstraints gridX=\"6\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"2\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.7\" weightY=\"0.0\"/>\n        </Constraint>\n      </Constraints>\n    </Component>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/properties/GraphConstantLine.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport java.awt.Color;\nimport java.awt.Component;\nimport java.awt.Graphics;\nimport java.awt.Insets;\nimport java.text.DecimalFormat;\nimport java.text.NumberFormat;\nimport java.util.Locale;\n\nimport javax.swing.DefaultListCellRenderer;\nimport javax.swing.Icon;\nimport javax.swing.JList;\nimport javax.swing.UIManager;\n\nimport parser.type.*;\nimport prism.DefinedConstant;\n\npublic class GraphConstantLine extends javax.swing.JPanel\n{\n    public static final String SINGLE_DEFAULT = \"0\";\n    public static final String RANGE_START_DEFAULT = \"0\";\n    public static final String RANGE_END_DEFAULT = \"1\";\n    public static final String STEP_DEFAULT = \"1\";\n    \n    private DefinedConstant dc;\n    private GUIGraphPicker parent;\n    private Type type;\n    \n    /** Creates new form ConstantLine */\n    public GraphConstantLine(DefinedConstant dc, GUIGraphPicker parent)\n    {\n        this.dc = dc;\n        this.parent = parent;\n        \n        initComponents();\n        this.valuePicker.setRenderer(new DefaultListCellRenderer()\n        {\n            public Component getListCellRendererComponent(JList list, Object obj, int i, boolean selection, boolean hasFocus)\n            {\n                if(obj instanceof Double)\n                {\n                    setComponentOrientation(list.getComponentOrientation());\n                    if (selection)\n                    {\n                        setBackground(list.getSelectionBackground());\n                        setForeground(list.getSelectionForeground());\n                    }\n                    else\n                    {\n                        setBackground(list.getBackground());\n                        setForeground(list.getForeground());\n                    }\n                    \n                    if (obj instanceof Icon)\n                    {\n                        setIcon((Icon)obj);\n                        setText(\"\");\n                    }\n                    else\n                    {\n                        setIcon(null);\n                        String str;\n                        Double d = (Double) obj;\n                        NumberFormat n = DecimalFormat.getInstance(Locale.UK);\n                        n.setMaximumFractionDigits(6);\n                        str = n.format(d.doubleValue());\n                        setText((obj == null) ? \"\" : str);\n                    }\n                    \n                    setEnabled(list.isEnabled());\n                    setFont(list.getFont());\n                    setBorder((hasFocus) ? UIManager.getBorder(\"List.focusCellHighlightBorder\") : noFocusBorder);\n                    \n                    return this;\n                }\n                else\n                {\n                    return super.getListCellRendererComponent(list, obj, i, selection, hasFocus);\n                }\n            }\n        });\n        setBorder(new BottomBorder());\n        setConstName(dc.getName());\n        setConstType(dc.getType());\n        init();\n    }\n    \n    private void init()\n    {\n        \n        valuePicker.addItem(\"All series\");\n        \n        for(int i = 0; i < dc.getNumSteps(); i++)\n        {\n            valuePicker.addItem(dc.getValue(i));\n        }\n        \n        \n    }\n    \n    public void setConstName(String str)\n    {\n        nameLabel.setText(str);\n    }\n    \n    public void setConstType(Type type)\n    {\n    \tthis.type = type;\n    \tif (type instanceof TypeDouble) {\n    \t\ttypeLabel.setText(\"double\");\n    \t} else if (type instanceof TypeInt) {\n    \t\ttypeLabel.setText(\"int\");\n    \t} else {\n    \t\ttypeLabel.setText(\"unknown\");\n        }\n    }\n    \n    public void setEnabled(boolean b)\n    {\n        //System.out.println(\"setEnabloed called on a GraphConstantPickerList\");\n        super.setEnabled(b);\n        nameLabel.setEnabled(b);\n        typeLabel.setEnabled(b);\n        valuePicker.setEnabled(b);\n        if(b)\n        {\n            setBackground(Color.white);\n            jPanel1.setBackground(Color.white);\n            jPanel2.setBackground(Color.white);\n            jPanel3.setBackground(Color.white);\n        }\n        else\n        {\n            setBackground(Color.lightGray);\n            jPanel1.setBackground(Color.lightGray);\n            jPanel2.setBackground(Color.lightGray);\n            jPanel3.setBackground(Color.lightGray);\n        }\n    }\n    \n    //ACCESS METHODS\n    \n    \n    public String getName()\n    {\n        return nameLabel.getText();\n    }\n    \n    public Object getSelectedValue()\n    {\n        return valuePicker.getSelectedItem();\n    }\n    \n    public DefinedConstant getDC()\n    {\n        return dc;\n    }\n    \n    \n    /** This method is called from within the constructor to\n     * initialize the form.\n     * WARNING: Do NOT modify this code. The content of this method is\n     * always regenerated by the Form Editor.\n     */\n    private void initComponents()//GEN-BEGIN:initComponents\n    {\n        java.awt.GridBagConstraints gridBagConstraints;\n\n        choiceButtonGroup = new javax.swing.ButtonGroup();\n        boolSingleValueCombo = new javax.swing.JComboBox();\n        sizerPanel = new javax.swing.JPanel();\n        jPanel1 = new javax.swing.JPanel();\n        nameLabel = new javax.swing.JLabel();\n        jPanel2 = new javax.swing.JPanel();\n        typeLabel = new javax.swing.JLabel();\n        jPanel3 = new javax.swing.JPanel();\n        valuePicker = new javax.swing.JComboBox();\n\n        boolSingleValueCombo.setBackground(new java.awt.Color(255, 255, 255));\n        boolSingleValueCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"true\", \"false\" }));\n        boolSingleValueCombo.setMinimumSize(new java.awt.Dimension(4, 19));\n        boolSingleValueCombo.setPreferredSize(new java.awt.Dimension(4, 19));\n\n        setLayout(new java.awt.GridBagLayout());\n\n        setBackground(new java.awt.Color(255, 255, 255));\n        setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0)));\n        setPreferredSize(new java.awt.Dimension(300, 26));\n        jPanel1.setBackground(new java.awt.Color(255, 255, 255));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 0;\n        gridBagConstraints.gridy = 0;\n        add(jPanel1, gridBagConstraints);\n\n        nameLabel.setText(\"a\");\n        nameLabel.setPreferredSize(new java.awt.Dimension(30, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 1;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        gridBagConstraints.weightx = 0.3;\n        add(nameLabel, gridBagConstraints);\n\n        jPanel2.setBackground(new java.awt.Color(255, 255, 255));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 2;\n        gridBagConstraints.gridy = 0;\n        add(jPanel2, gridBagConstraints);\n\n        typeLabel.setText(\"double\");\n        typeLabel.setPreferredSize(new java.awt.Dimension(50, 15));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 3;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.anchor = java.awt.GridBagConstraints.WEST;\n        add(typeLabel, gridBagConstraints);\n\n        jPanel3.setBackground(new java.awt.Color(255, 255, 255));\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 4;\n        gridBagConstraints.gridy = 0;\n        add(jPanel3, gridBagConstraints);\n\n        valuePicker.setBackground(new java.awt.Color(255, 255, 255));\n        valuePicker.addActionListener(new java.awt.event.ActionListener()\n        {\n            public void actionPerformed(java.awt.event.ActionEvent evt)\n            {\n                valuePickerActionPerformed(evt);\n            }\n        });\n\n        gridBagConstraints = new java.awt.GridBagConstraints();\n        gridBagConstraints.gridx = 6;\n        gridBagConstraints.gridy = 0;\n        gridBagConstraints.fill = java.awt.GridBagConstraints.HORIZONTAL;\n        gridBagConstraints.weightx = 0.7;\n        add(valuePicker, gridBagConstraints);\n\n    }//GEN-END:initComponents\n    \n    private void valuePickerActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_valuePickerActionPerformed\n    {//GEN-HEADEREND:event_valuePickerActionPerformed\n        parent.resetAutoSeriesName();\n    }//GEN-LAST:event_valuePickerActionPerformed\n    \n    \n    // Variables declaration - do not modify//GEN-BEGIN:variables\n    private javax.swing.JComboBox boolSingleValueCombo;\n    private javax.swing.ButtonGroup choiceButtonGroup;\n    private javax.swing.JPanel jPanel1;\n    private javax.swing.JPanel jPanel2;\n    private javax.swing.JPanel jPanel3;\n    private javax.swing.JLabel nameLabel;\n    private javax.swing.JPanel sizerPanel;\n    private javax.swing.JLabel typeLabel;\n    private javax.swing.JComboBox valuePicker;\n    // End of variables declaration//GEN-END:variables\n    \n    class BottomBorder implements javax.swing.border.Border\n    {\n        public Insets getBorderInsets(Component c)\n        {\n            return new Insets(0,0,1,0);\n        }\n        \n        public boolean isBorderOpaque()\n        {\n            return true;\n        }\n        \n        public void paintBorder(Component c, Graphics g, int x, int y, int width, int height)\n        {\n            g.setColor(Color.lightGray);\n            g.drawLine(x,(y+height-1), (x+width), (y+height-1));\n            \n        }\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/GraphConstantPickerList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties;\n\nimport javax.swing.*;\nimport java.util.*;\nimport java.awt.*;\n\npublic class GraphConstantPickerList extends JPanel implements Scrollable\n{\n    \n    private ArrayList rows;\n    private JPanel nextPanel;\n    \n    /** Creates a new instance of ConstantPickerList */\n    public GraphConstantPickerList()\n    {\n\tsetLayout(new BorderLayout());\n\tnextPanel = new JPanel();\n\tnextPanel.setLayout(new BorderLayout());\n\tadd(nextPanel, BorderLayout.CENTER);\n\trows = new ArrayList();\n    }\n    \n    public void addConstant(GraphConstantLine pl)\n    {\n\trows.add(pl);\n\tnextPanel.add(pl, BorderLayout.NORTH);\n\tJPanel np = new JPanel();\n\tnp.setLayout(new BorderLayout());\n\tnextPanel.add(np, BorderLayout.CENTER);\n\tnextPanel = np;\n    }\n    \n    public void disableLine(int index)\n    {\n        for(int i = 0; i < rows.size(); i++)\n        {\n            getConstantLine(i).setEnabled(true);\n        }\n        getConstantLine(index).setEnabled(false);\n    }\n    \n    public Dimension getPreferredScrollableViewportSize()\n    {\n\treturn getPreferredSize();\n    }\n    \n    public int getScrollableBlockIncrement(Rectangle visibleRect, int orientation, int direction)\n    {\n\treturn 20;\n    }\n    \n    public boolean getScrollableTracksViewportHeight()\n    {\n\treturn false;\n    }\n    \n    public boolean getScrollableTracksViewportWidth()\n    {\n\treturn true;\n    }\n    \n    public int getScrollableUnitIncrement(Rectangle visibleRect, int orientation, int direction)\n    {\n\treturn 40;\n    }\n    \n    public int getNumConstants()\n    {\n\treturn rows.size();\n    }\n    \n    public GraphConstantLine getConstantLine(int i)\n    {\n\treturn (GraphConstantLine)rows.get(i);\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/computation/ExportResultsThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties.computation;\n\nimport userinterface.properties.*;\nimport java.io.*;\nimport java.util.Arrays;\nimport java.util.List;\nimport java.util.stream.Collectors;\n\nimport javax.swing.*;\n\nimport parser.ast.Property;\nimport prism.ResultsCollection;\nimport prism.ResultsExporter.ResultsExportShape;\nimport userinterface.util.*;\n\npublic class ExportResultsThread extends Thread\n{\n\tprivate GUIMultiProperties parent;\n\tprivate GUIExperiment exps[];\n\tprivate File file;\n\tprivate ResultsExportShape exportShape;\n\n\t/** Creates a new instance of ExportResultsThread */\n\tpublic ExportResultsThread(GUIMultiProperties parent, GUIExperiment exp, File file)\n\t{\n\t\tthis(parent, new GUIExperiment[] {exp}, file );\n\t}\n\t\n\t/** Creates a new instance of ExportResultsThread */\n\tpublic ExportResultsThread(GUIMultiProperties parent, GUIExperiment exps[], File file)\n\t{\n\t\tthis(parent, exps, file, ResultsExportShape.LIST_PLAIN);\n\t}\n\t\n\t/** Creates a new instance of ExportResultsThread */\n\tpublic ExportResultsThread(GUIMultiProperties parent, GUIExperiment exps[], File file, ResultsExportShape exportShape)\n\t{\n\t\tthis.parent = parent;\n\t\tthis.exps = exps;\n\t\tthis.file = file;\n\t\tthis.exportShape = exportShape;\n\t}\n\t\n\tpublic void run()\n\t{\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\t\tparent.startProgress();\n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, parent));\n\t\t\t\t\tparent.setTaskBarText(\"Exporting results...\");\n\t\t\t}\n\t\t});\n\n\t\tList<Property> properties = Arrays.stream(exps).map(GUIExperiment::getProperty).collect(Collectors.toList());\n\t\tList<ResultsCollection> results = Arrays.stream(exps).map(GUIExperiment::getResults).collect(Collectors.toList());\n\n\t\tString error = null;\n\t\ttry {\n\t\t\tfile.createNewFile(); // create file if not already present\n\t\t\tPrintWriter out = new PrintWriter(file);\n\t\t\texportShape.getExporter().printResults(results, properties, out);\n\t\t\tout.close();\n\t\t\tif (out.checkError()) {\n\t\t\t\t// PrintWriter hides exceptions in print methods and close()\n\t\t\t\terror = \"Could not export results: unknown IO exception\";\n\t\t\t}\n\t\t} catch (IOException e) {\n\t\t\terror = \"Could not export results: \" + e.getMessage();\n\t\t}\n\t\tif (error != null) {\n\t\t\tfinal String msg = error; // Copy error message since an enclosed variable must be final\n\t\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tparent.stopProgress(); \n\t\t\t\t\tparent.setTaskBarText(\"Exporting results... error.\");\n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, parent));\n\t\t\t\t\tparent.error(\"Could not export results: \" + msg);\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\t//Computation successful, notify the user interface\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\t\tparent.stopProgress();\n\t\t\t\t\tparent.setTaskBarText(\"Exporting results... done.\");\n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, parent));\n\t\t\t}\n\t\t});\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/computation/ExportStrategyThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2022-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties.computation;\n\nimport java.io.File;\nimport java.io.FileNotFoundException;\n\nimport javax.swing.SwingUtilities;\n\nimport strat.StrategyExportOptions;\nimport userinterface.GUIComputationThread;\nimport userinterface.GUIPlugin;\nimport userinterface.util.GUIComputationEvent;\n\n/**\n * Thread that performs export of a strategy.\n */\npublic class ExportStrategyThread extends GUIComputationThread\n{\n\tprivate StrategyExportOptions exportOptions;\n\tprivate File exportFile;\n\n\t/** Creates a new instance of ExportStrategyThread */\n\tpublic ExportStrategyThread(GUIPlugin plug, StrategyExportOptions exportOptions, File exportFile)\n\t{\n\t\tsuper(plug);\n\t\tthis.exportOptions = exportOptions;\n\t\tthis.exportFile = exportFile;\n\t}\n\n\tpublic void run()\n\t{\n\t\ttry {\n\t\t\t// Notify the interface of the start of computation\n\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tplug.startProgress();\n\t\t\t\t\tplug.setTaskBarText(\"Exporting...\");\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, plug));\n\t\t\t\t}\n\t\t\t});\n\n\t\t\t// Do export\n\t\t\ttry {\n\t\t\t\tprism.exportStrategy(exportOptions, exportFile);\n\t\t\t} catch (FileNotFoundException e) {\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t\t{\n\t\t\t\t\tpublic void run()\n\t\t\t\t\t{\n\t\t\t\t\t\tplug.stopProgress();\n\t\t\t\t\t\tplug.setTaskBarText(\"Exporting... error.\");\n\t\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\t\terror(\"Could not export to file \\\"\" + exportFile + \"\\\"\");\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\treturn;\n\t\t\t} catch (Throwable e2) {\n\t\t\t\terror(e2);\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t\t{\n\t\t\t\t\tpublic void run()\n\t\t\t\t\t{\n\t\t\t\t\t\tplug.stopProgress();\n\t\t\t\t\t\tplug.setTaskBarText(\"Exporting... error.\");\n\t\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, plug));\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\treturn;\n\t\t\t}\n\n\t\t\t//If we get here export was successful, notify interface\n\t\t\tSwingUtilities.invokeAndWait(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tplug.stopProgress();\n\t\t\t\t\tplug.setTaskBarText(\"Exporting... done.\");\n\t\t\t\t\tplug.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, plug));\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\t\t// catch and ignore any thread exceptions\n\t\tcatch (java.lang.InterruptedException e) {\n\t\t} catch (java.lang.reflect.InvocationTargetException e) {\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/computation/ImportResultsThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2021-\n//\tAuthors:\n//\t* Steffen Märcker <steffen.maercker@tu-dresden.de> (TU Dresden)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties.computation;\n\nimport userinterface.properties.*;\nimport java.io.*;\nimport java.util.Map.Entry;\n\nimport javax.swing.*;\n\nimport csv.CsvFormatException;\nimport parser.ast.Property;\nimport prism.PrismLangException;\nimport prism.ResultsImporter;\nimport prism.ResultsImporter.RawResultsCollection;\nimport userinterface.util.*;\n\n/**\n * Thread that runs the import or experiment data from a file.\n */\npublic class ImportResultsThread extends Thread\n{\n\tprivate final GUIMultiProperties parent;\n\tprivate final File file;\n\tprivate final GUIExperimentTable table;\n\n\t/** Creates a new instance of ImportResultsThread */\n\tpublic ImportResultsThread(GUIMultiProperties parent, GUIExperimentTable table, File file)\n\t{\n\t\tthis.parent = parent;\n\t\tthis.table = table;\n\t\tthis.file = file;\n\t}\n\n\tpublic void run()\n\t{\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\t\tparent.startProgress();\n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, parent));\n\t\t\t\t\tparent.setTaskBarText(\"Importing results...\");\n\t\t\t}\n\t\t});\n\n\t\tString error = null;\n\t\ttry {\n\t\t\tFileReader reader = new FileReader(file);\n\t\t\tResultsImporter importer = new ResultsImporter(new BufferedReader(reader));\n\t\t\tfor (Entry<Property, RawResultsCollection> result : importer) {\n\t\t\t\ttable.importExperiment(result.getKey(), result.getValue().toResultsCollection());\n\t\t\t}\n\t\t} catch (FileNotFoundException e) {\n\t\t\terror = \"Could not export results: \" + e.getMessage();\n\t\t} catch (IOException e) {\n\t\t\terror = \"Could not read results file: \" + e.getMessage();\n\t\t} catch (CsvFormatException e) {\n\t\t\terror = \"Malformatted CSV results file: \" + e.getMessage();\n\t\t} catch (PrismLangException e) {\n\t\t\terror = \"Syntax error in results file: \" + e.getMessage();\n\t\t}\n\t\tif (error != null) {\n\t\t\tString msg = error; // Copy error message since an enclosed variable must be final\n\t\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t\t{\n\t\t\t\tpublic void run()\n\t\t\t\t{\n\t\t\t\t\tparent.stopProgress(); \n\t\t\t\t\tparent.setTaskBarText(\"Importing results... error.\");\n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, parent));\n\t\t\t\t\tparent.error(\"Could not import results: \" + msg);\n\t\t\t\t}\n\t\t\t});\n\t\t}\n\n\t\t//Computation successful, notify the user interface\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\t\tparent.stopProgress();\n\t\t\t\t\tparent.setTaskBarText(\"Importing results... done.\");\n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, parent));\n\t\t\t}\n\t\t});\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/computation/LoadPropertiesThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties.computation;\n\nimport java.io.*;\nimport javax.swing.*;\n\nimport userinterface.properties.*;\nimport userinterface.util.*;\nimport prism.*;\nimport parser.ast.*;\n\npublic class LoadPropertiesThread extends Thread\n{\n\tprivate GUIMultiProperties parent;\n\tprivate Prism pri;\n\tprivate File file;\n\tprivate PropertiesFile props = null;\n\tprivate boolean isInsert = false;\n\tprivate Exception ex;\n\t\n\t/** Creates a new instance of LoadPropertiesThread */\n\tpublic LoadPropertiesThread(GUIMultiProperties parent, File file)\n\t{\n\t   this(parent, file, false);\n\t}\n\t\n\tpublic LoadPropertiesThread(GUIMultiProperties parent, File file, boolean isInsert)\n\t{\n\t\tthis.parent = parent;\n\t\tthis.file = file;\n\t\tthis.pri = parent.getPrism();\n\t\tthis.isInsert = isInsert; \n\t}\n\t\n\tpublic void run()\n\t{\n\t\ttry\n\t\t{\n\t\t\t//notify interface of start of computation\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\tparent.startProgress();\n\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, parent));\n\t\t\t\tparent.setTaskBarText(\"Loading properties...\");\n\t\t\t}});\n\t\t\t\n\t\t\t// do parsing\n\t\t\ttry {\n\t\t\t\tprops = pri.parsePropertiesFile(file, false);\n\t\t\t}\n\t\t\t//If there was a problem with the loading, notify the interface.\n\t\t\tcatch (FileNotFoundException e) {\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\t\tparent.stopProgress(); \n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, parent));\n\t\t\t\t\tparent.setTaskBarText(\"Loading properties... error.\");\n\t\t\t\t\tparent.error(\"Could not open file \\\"\" + file + \"\\\"\");\n\t\t\t\t}});\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tcatch (PrismException e) {\n\t\t\t\tex = e;\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\t\tparent.stopProgress(); \n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, parent));\n\t\t\t\t\tparent.setTaskBarText(\"Loading properties... error.\");\n\t\t\t\t\tparent.error(ex.getMessage());\n\t\t\t\t}});\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t\n\t\t\t//If we get here, the load has been successful, notify the interface and tell the handler.\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\tparent.stopProgress(); \n\t\t\t\tparent.setTaskBarText(\"Loading properties... done.\");\n\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, parent));\n\t\t\t\tif(isInsert)\n\t\t\t\t\tparent.propertyInsertSuccessful(props);\n\t\t\t\telse\n\t\t\t\t\tparent.propertyLoadSuccessful(props, file);\n\t\t\t}});\n\t\t}\n\t\t// catch and ignore any thread exceptions\n\t\tcatch (java.lang.InterruptedException e) {}\n\t\tcatch (java.lang.reflect.InvocationTargetException e) {}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/computation/ModelCheckThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties.computation;\n\nimport java.util.ArrayList;\n\nimport javax.swing.ImageIcon;\nimport javax.swing.SwingUtilities;\n\nimport parser.ast.PropertiesFile;\nimport prism.PrismException;\nimport prism.Result;\nimport userinterface.GUIComputationThread;\nimport userinterface.GUIPrism;\nimport userinterface.properties.GUIMultiProperties;\nimport userinterface.properties.GUIPropertiesEvent;\nimport userinterface.properties.GUIProperty;\nimport userinterface.util.GUIComputationEvent;\n\n/**\n * Thread that executes model checking of a property via PRISM.\n */\npublic class ModelCheckThread extends GUIComputationThread\n{\n\t// Access to GUI (to send notifications etc.)\n\tprivate GUIMultiProperties parent;\n\t// Properties file and GUI properties (these are assumed to match)\n\t// (Also need properties file for access to constants/labels/etc.)\n\tprivate PropertiesFile propertiesFile;\n\tprivate ArrayList<GUIProperty> guiProps;\n\n\t/**\n\t * Create a new instance of ModelCheckThread (where a Model has been built)\n\t */\n\tpublic ModelCheckThread(GUIMultiProperties parent, PropertiesFile propertiesFile, ArrayList<GUIProperty> guiProps)\n\t{\n\t\tsuper(parent);\n\t\tthis.parent = parent;\n\t\tthis.propertiesFile = propertiesFile;\n\t\tthis.guiProps = guiProps;\n\t}\n\n\tpublic void run()\n\t{\n\t\t// Notify user interface of the start of computation\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tparent.startProgress();\n\t\t\t\tparent.setTaskBarText(\"Verifying properties...\");\n\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, parent));\n\t\t\t}\n\t\t});\n\n\t\tResult result = null;\n\n\t\t// Set icon for all properties to be verified to a clock\n\t\tfor (int i = 0; i < guiProps.size(); i++) {\n\t\t\tGUIProperty gp = guiProps.get(i);\n\t\t\tgp.setStatus(GUIProperty.STATUS_DOING);\n\t\t\tparent.repaintList();\n\t\t}\n\n\t\tIconThread ic = new IconThread(null);\n\n\t\t//numAuxiliary is the number of properties we don't check but that are contained because\n\t\t//they are referenced. These are at the beginning of the file.\n\t\tint numAuxiliary = propertiesFile.getNumProperties() - guiProps.size();\n\t\t// Work through list of properties\n\t\tfor (int i = numAuxiliary; i < propertiesFile.getNumProperties(); i++) {\n\n\t\t\t// Get ith property\n\t\t\tGUIProperty gp = guiProps.get(i - numAuxiliary);\n\t\t\t// Animate it's clock icon\n\t\t\tic = new IconThread(gp);\n\t\t\tic.start();\n\n\t\t\t// Do model checking\n\t\t\ttry {\n\t\t\t\tresult = prism.modelCheck(propertiesFile, propertiesFile.getPropertyObject(i));\n\t\t\t} catch (Exception e) {\n\t\t\t\tresult = new Result(e);\n\t\t\t\terror(e);\n\t\t\t} catch (StackOverflowError e) {\n\t\t\t\t// convert the StackOverflowError to a PrismException, as the result handling\n\t\t\t\t// expects Exception instead of Error objects\n\t\t\t\tresult = new Result(new PrismException(\"Stack overflow\"));\n\t\t\t\terror(e);\n\t\t\t}\n\t\t\tic.interrupt();\n\t\t\ttry {\n\t\t\t\tic.join();\n\t\t\t} catch (InterruptedException e) {\n\t\t\t}\n\t\t\t//while(!ic.canContinue){}\n\t\t\tgp.setResult(result);\n\t\t\tgp.setMethodString(\"Verification\");\n\t\t\tgp.setNumberOfWarnings(prism.getMainLog().getNumberOfWarnings());\n\n\t\t\tparent.repaintList();\n\t\t}\n\n\t\t// Notify user interface of the end of computation\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tparent.stopProgress();\n\t\t\t\tparent.setTaskBarText(\"Verifying properties... done.\");\n\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, parent));\n\t\t\t\tparent.notifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.VERIFY_END));\n\t\t\t}\n\t\t});\n\t}\n\n\t// Clock animation icon\n\tclass IconThread extends Thread\n\t{\n\t\tGUIProperty gp;\n\t\tImageIcon[] images;\n\t\tboolean canContinue = false;\n\n\t\tpublic IconThread(GUIProperty gp)\n\t\t{\n\t\t\tthis.gp = gp;\n\t\t\timages = new ImageIcon[8];\n\t\t\timages[0] = GUIPrism.getIconFromImage(\"smallClockAnim1.png\");\n\t\t\timages[1] = GUIPrism.getIconFromImage(\"smallClockAnim2.png\");\n\t\t\timages[2] = GUIPrism.getIconFromImage(\"smallClockAnim3.png\");\n\t\t\timages[3] = GUIPrism.getIconFromImage(\"smallClockAnim4.png\");\n\t\t\timages[4] = GUIPrism.getIconFromImage(\"smallClockAnim5.png\");\n\t\t\timages[5] = GUIPrism.getIconFromImage(\"smallClockAnim6.png\");\n\t\t\timages[6] = GUIPrism.getIconFromImage(\"smallClockAnim7.png\");\n\t\t\timages[7] = GUIPrism.getIconFromImage(\"smallClockAnim8.png\");\n\t\t}\n\n\t\tpublic void run()\n\t\t{\n\t\t\ttry {\n\t\t\t\tint counter = 0;\n\t\t\t\twhile (!interrupted() && gp != null) {\n\t\t\t\t\tcounter++;\n\t\t\t\t\tcounter = counter % 8;\n\t\t\t\t\tgp.setDoingImage(images[counter]);\n\t\t\t\t\tparent.repaintList();\n\t\t\t\t\tsleep(150);\n\t\t\t\t}\n\t\t\t} catch (InterruptedException e) {\n\t\t\t}\n\t\t\tcanContinue = true;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/computation/SavePropertiesThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties.computation;\n\nimport userinterface.properties.*;\nimport userinterface.util.*;\nimport java.io.*;\nimport javax.swing.*;\n\npublic class SavePropertiesThread extends Thread\n{\n\tprivate GUIMultiProperties parent;\n\tprivate GUIPropertiesList propList;\n\tprivate GUIPropConstantList consList;\n\tprivate GUIPropLabelList labList;\n\tprivate File f;\n\tprivate Exception saveError;\n\t\n\t/** Creates a new instance of SavePropertiesThread */\n\tpublic SavePropertiesThread(GUIMultiProperties parent, GUIPropertiesList propList, GUIPropConstantList consList, GUIPropLabelList labList, File f)\n\t{\n\t\tthis.parent = parent;\n\t\tthis.propList = propList;\n\t\tthis.consList = consList;\n\t\tthis.labList = labList;\n\t\tthis.f = f;\n\t}\n\t\n\tpublic void run()\n\t{\n\t\ttry\n\t\t{\n\t\t\t//notify interface of start of computation\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\tparent.startProgress();\n\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, parent));\n\t\t\t\tparent.setTaskBarText(\"Saving properties...\");\n\t\t\t}});\n\t\t\t\n\t\t\t// do output to file\n\t\t\ttry {\n\t\t\t\tPrintWriter out = new PrintWriter(new FileWriter(f));\n\t\t\t\tout.print(propList.toFileString(f, consList, labList));\n\t\t\t\tout.flush();\n\t\t\t\tout.close();\n\t\t\t}\n\t\t\t//If there was a problem with the save, notify the interface.\n\t\t\tcatch (IOException e) {\n\t\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\t\tparent.stopProgress(); \n\t\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_ERROR, parent));\n\t\t\t\t\tparent.setTaskBarText(\"Saving properties... error.\");\n\t\t\t\t\tparent.error(\"Could not save to file \\\"\" + f + \"\\\"\");\n\t\t\t\t}});\n\t\t\t\treturn;\n\t\t\t}\n\t\t\t\n\t\t\t//Computation successful, notify the user interface\n\t\t\tSwingUtilities.invokeAndWait(new Runnable() { public void run() {\n\t\t\t\tparent.stopProgress(); \n\t\t\t\tparent.setTaskBarText(\"Saving properties... done.\");\n\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, parent));\n\t\t\t\tparent.propertySaveSuccessful(f);\n\t\t\t}});\n\t\t}\n\t\t// catch and ignore any thread exceptions\n\t\tcatch (java.lang.InterruptedException e) {}\n\t\tcatch (java.lang.reflect.InvocationTargetException e) {}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/computation/SimulateModelCheckThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Vincent Nimal <vincent.nimal@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.properties.computation;\n\nimport java.util.*;\nimport javax.swing.*;\n\nimport parser.*;\nimport parser.ast.*;\nimport prism.*;\nimport simulator.method.SimulationMethod;\nimport userinterface.*;\nimport userinterface.util.*;\nimport userinterface.properties.*;\n\n/**\n * Thread that executes approximate (simulation-based) model checking of a property via PRISM.\n * Model should have been loaded into PRISM already. Supplied are:\n * properties file (constants defined), list of properties to\n * be (approximately) verified and initial state (default/random if null).\n */\npublic class SimulateModelCheckThread extends GUIComputationThread\n{\n\tprivate GUIMultiProperties parent;\n\tprivate PropertiesFile pf;\n\tprivate ArrayList<GUIProperty> guiProps;\n\tprivate Values definedPFConstants;\n\tprivate long maxPathLength;\n\tprivate SimulationInformation info;\n\n\t/** Creates a new instance of SimulateModelCheckThread */\n\tpublic SimulateModelCheckThread(GUIMultiProperties parent, PropertiesFile prFi, ArrayList<GUIProperty> guiProps,\n\t\t\tValues definedPFConstants, SimulationInformation info)\n\t{\n\t\tsuper(parent);\n\t\tthis.parent = parent;\n\t\tthis.pf = prFi;\n\t\tthis.guiProps = guiProps;\n\t\tthis.definedPFConstants = definedPFConstants;\n\t\tthis.info = info;\n\t\tthis.maxPathLength = info.getMaxPathLength();\n\t}\n\n\tpublic void run()\n\t{\n\t\tboolean allAtOnce = prism.getSettings().getBoolean(PrismSettings.SIMULATOR_SIMULTANEOUS);\n\n\t\tSimulationMethod method = info.createSimulationMethod();\n\n\t\t//Notify user interface of the start of computation\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tparent.startProgress();\n\t\t\t\tparent.setTaskBarText(\"Checking properties using simulation...\");\n\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_START, parent));\n\t\t\t}\n\t\t});\n\n\t\t//Set icon for all properties to be verified to a clock\n\t\tfor (int i = 0; i < guiProps.size(); i++) {\n\t\t\tGUIProperty gp = guiProps.get(i);\n\t\t\tgp.setStatus(GUIProperty.STATUS_DOING);\n\t\t\tparent.repaintList();\n\t\t}\n\n\t\t// do all at once if requested\n\t\tif (allAtOnce) {\n\t\t\tResult results[] = null;\n\t\t\tException resultError = null;\n\t\t\tArrayList<Expression> properties = new ArrayList<Expression>();\n\t\t\tArrayList<IconThread> clkThreads = new ArrayList<IconThread>();\n\t\t\tfor (int i = 0; i < guiProps.size(); i++) {\n\t\t\t\tGUIProperty gp = guiProps.get(i);\n\t\t\t\tproperties.add(gp.getProperty());\n\t\t\t\tIconThread ict = new IconThread(gp);\n\t\t\t\tict.start();\n\t\t\t\tclkThreads.add(ict);\n\t\t\t}\n\n\t\t\ttry {\n\t\t\t\t// convert initial Values -> State\n\t\t\t\t// (remember: null means use default or pick randomly)\n\t\t\t\tparser.State initialState;\n\t\t\t\tif (info.getInitialState() == null) {\n\t\t\t\t\tinitialState = null;\n\t\t\t\t} else {\n\t\t\t\t\tinitialState = new parser.State(info.getInitialState(), prism.getPRISMModel());\n\t\t\t\t}\n\t\t\t\t// do simulation\n\t\t\t\tresults = prism.modelCheckSimulatorSimultaneously(pf, properties, definedPFConstants, initialState, maxPathLength, method);\n\t\t\t\tmethod.reset();\n\t\t\t} catch (Exception e) {\n\t\t\t\t// in the case of an error which affects all props, store/report it\n\t\t\t\tresultError = e;\n\t\t\t\terror(e);\n\t\t\t} catch (StackOverflowError e) {\n\t\t\t\t// in the case of an error which affects all props, store/report it\n\t\t\t\t// convert to a PrismException for result\n\t\t\t\tresultError = new PrismException(\"Stack overflow\");\n\t\t\t\terror(e);\n\t\t\t}\n\t\t\t//after collecting the results stop all of the clock icons\n\t\t\tfor (int i = 0; i < clkThreads.size(); i++) {\n\t\t\t\tIconThread ict = (IconThread) clkThreads.get(i);\n\t\t\t\tict.interrupt();\n\t\t\t\twhile (!ict.canContinue) {\n\t\t\t\t\ttry {\n\t\t\t\t\t\tThread.sleep(10);\n\t\t\t\t\t} catch (InterruptedException e) {\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// store results\n\t\t\tModelType currentModelType = prism.getModelType();\n\t\t\tString methodString = \"Simulation\";\n\t\t\tif (currentModelType.nondeterministic() && currentModelType.removeNondeterminism() != currentModelType) {\n\t\t\t\tmethodString += \" (nondeterminism in \" + currentModelType.name() + \" resolved uniformly)\";\n\t\t\t}\n\n\t\t\tfor (int i = 0; i < guiProps.size(); i++) {\n\t\t\t\tGUIProperty gp = guiProps.get(i);\n\t\t\t\tgp.setResult((results == null) ? new Result(resultError) : results[i]);\n\t\t\t\tgp.setMethodString(methodString);\n\t\t\t\tgp.setNumberOfWarnings(prism.getMainLog().getNumberOfWarnings());\n\t\t\t}\n\t\t}\n\t\t// do each property individually\n\t\telse {\n\t\t\tResult result = null;\n\t\t\tfor (int i = 0; i < pf.getNumProperties(); i++) {\n\t\t\t\t// get property\n\t\t\t\tGUIProperty gp = guiProps.get(i);\n\t\t\t\t// animate it's clock icon\n\t\t\t\tIconThread ict = new IconThread(gp);\n\t\t\t\tict.start();\n\t\t\t\t// do model checking\n\t\t\t\ttry {\n\t\t\t\t\t// convert initial Values -> State\n\t\t\t\t\t// (remember: null means use default or pick randomly)\n\t\t\t\t\tparser.State initialState;\n\t\t\t\t\tif (info.getInitialState() == null) {\n\t\t\t\t\t\tinitialState = null;\n\t\t\t\t\t} else {\n\t\t\t\t\t\tinitialState = new parser.State(info.getInitialState(), prism.getPRISMModel());\n\t\t\t\t\t}\n\t\t\t\t\t// do simulation\n\t\t\t\t\tresult = prism.modelCheckSimulator(pf, pf.getProperty(i), definedPFConstants, initialState, maxPathLength, method);\n\t\t\t\t\tmethod.reset();\n\t\t\t\t} catch (Exception e) {\n\t\t\t\t\tresult = new Result(e);\n\t\t\t\t\terror(e);\n\t\t\t\t} catch (StackOverflowError e) {\n\t\t\t\t\t// store as PrismException in result\n\t\t\t\t\tresult = new Result(new PrismException(\"Stack overflow\"));\n\t\t\t\t\terror(e);\n\t\t\t\t}\n\t\t\t\tict.interrupt();\n\t\t\t\twhile (!ict.canContinue) {\n\t\t\t\t\ttry {\n\t\t\t\t\t\tThread.sleep(10);\n\t\t\t\t\t} catch (InterruptedException e) {\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tgp.setResult(result);\n\t\t\t\tgp.setMethodString(\"Simulation\");\n\n\t\t\t\tparent.repaintList();\n\t\t\t}\n\t\t}\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\tparent.stopProgress();\n\t\t\t\tparent.setTaskBarText(\"Checking properties using simulation... done.\");\n\t\t\t\tparent.notifyEventListeners(new GUIComputationEvent(GUIComputationEvent.COMPUTATION_DONE, parent));\n\t\t\t\tparent.notifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.VERIFY_END));\n\t\t\t}\n\t\t});\n\t}\n\n\tclass IconThread extends Thread\n\t{\n\t\tGUIProperty gp;\n\t\tImageIcon[] images;\n\t\tboolean canContinue = false;\n\n\t\tpublic IconThread(GUIProperty gp)\n\t\t{\n\t\t\tthis.gp = gp;\n\t\t\timages = new ImageIcon[8];\n\t\t\timages[0] = GUIPrism.getIconFromImage(\"smallClockAnim1.png\");\n\t\t\timages[1] = GUIPrism.getIconFromImage(\"smallClockAnim2.png\");\n\t\t\timages[2] = GUIPrism.getIconFromImage(\"smallClockAnim3.png\");\n\t\t\timages[3] = GUIPrism.getIconFromImage(\"smallClockAnim4.png\");\n\t\t\timages[4] = GUIPrism.getIconFromImage(\"smallClockAnim5.png\");\n\t\t\timages[5] = GUIPrism.getIconFromImage(\"smallClockAnim6.png\");\n\t\t\timages[6] = GUIPrism.getIconFromImage(\"smallClockAnim7.png\");\n\t\t\timages[7] = GUIPrism.getIconFromImage(\"smallClockAnim8.png\");\n\t\t}\n\n\t\tpublic void run()\n\t\t{\n\t\t\ttry {\n\t\t\t\tint counter = 0;\n\t\t\t\twhile (!interrupted() && gp != null) {\n\t\t\t\t\t//System.out.println(\"counter = \" + counter);\n\t\t\t\t\tcounter++;\n\t\t\t\t\tcounter = counter % 8;\n\t\t\t\t\tgp.setDoingImage(images[counter]);\n\t\t\t\t\tparent.repaintList();\n\t\t\t\t\tsleep(150);\n\t\t\t\t}\n\t\t\t} catch (InterruptedException e) {\n\t\t\t} finally {\n\t\t\t\tcanContinue = true;\n\t\t\t}\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/properties/computation/package-info.java",
    "content": "/**\n * Computation threads for model checking functionality in the GUI (\"Properties\" tab)\n */\npackage userinterface.properties.computation;\n"
  },
  {
    "path": "prism/src/userinterface/properties/package-info.java",
    "content": "/**\n * Model checking functionality in the GUI (\"Properties\" tab)\n */\npackage userinterface.properties;\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUIInitialStatePicker.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.2\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"2\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,46,0,0,2,38\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"allPanel\">\n      <Properties>\n        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n          </Border>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"bottomPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"South\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"buttonPanel\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"East\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n                <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n              </Layout>\n              <SubComponents>\n                <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n              </SubComponents>\n            </Container>\n            <Component class=\"javax.swing.JCheckBox\" name=\"optionCheckBox\">\n              <Properties>\n                <Property name=\"label\" type=\"java.lang.String\" value=\"Always prompt for initial state on path creation\"/>\n              </Properties>\n              <AccessibilityProperties>\n                <Property name=\"AccessibleContext.accessibleName\" type=\"java.lang.String\" value=\"optionCheckBox\"/>\n              </AccessibilityProperties>\n              <Events>\n                <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"optionCheckBoxActionPerformed\"/>\n              </Events>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"West\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                <TitledBorder title=\"Initial state\"/>\n              </Border>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"innerPanel\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUIInitialStatePicker.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport java.awt.Dimension;\nimport java.awt.Rectangle;\nimport java.awt.event.KeyEvent;\nimport java.awt.event.KeyListener;\n\nimport javax.swing.DefaultListSelectionModel;\nimport javax.swing.JScrollPane;\nimport javax.swing.JTable;\nimport javax.swing.table.AbstractTableModel;\n\nimport parser.State;\nimport parser.Values;\nimport parser.ast.Expression;\nimport prism.ModelGenerator;\nimport prism.Prism;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport simulator.SimulatorEngine;\nimport userinterface.GUIPrism;\n\n@SuppressWarnings(\"serial\")\npublic class GUIInitialStatePicker extends javax.swing.JDialog implements KeyListener\n{\n\t//STATICS    \n\tpublic static final int NO_VALUES = 0;\n\tpublic static final int VALUES_DONE = 1;\n\tpublic static final int CANCELLED = 2;\n\n\t//ATTRIBUTES    \n\tprivate boolean cancelled = true;\n\n\tprivate JTable initValuesTable;\n\tprivate DefineValuesTable initValuesModel;\n\n\tprivate GUIPrism gui;\n\tprivate ModelGenerator<Double> modelGen;\n\tprivate int numVars;\n\t\n\tprivate State initialState;\n\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tprivate javax.swing.JPanel allPanel;\n\tprivate javax.swing.JPanel bottomPanel;\n\tprivate javax.swing.JPanel buttonPanel;\n\tprivate javax.swing.JButton cancelButton;\n\tprivate javax.swing.JPanel innerPanel;\n\tprivate javax.swing.JButton okayButton;\n\tprivate javax.swing.JCheckBox optionCheckBox;\n\tprivate javax.swing.JPanel topPanel;\n\n\t// End of variables declaration//GEN-END:variables\n\n\t/** Creates new form GUIConstantsPicker */\n\tpublic GUIInitialStatePicker(GUIPrism parent, SimulatorEngine engine, Values initialStateValues)\n\t{\n\t\tsuper(parent, \"Initial State for Simulation\", true);\n\n\t\tthis.gui = parent;\n\t\tthis.modelGen = engine.getModel();\n\t\tthis.numVars = modelGen.getNumVars();\n\n\t\t//setup tables\n\t\tinitValuesModel = new DefineValuesTable();\n\t\tinitValuesTable = new JTable();\n\t\tinitValuesTable.setModel(initValuesModel);\n\t\tinitValuesTable.setSelectionMode(DefaultListSelectionModel.SINGLE_INTERVAL_SELECTION);\n\t\tinitValuesTable.setCellSelectionEnabled(true);\n\t\tinitValuesTable.setRowHeight(getFontMetrics(initValuesTable.getFont()).getHeight() + 4);\n\n\t\t//initialise\n\t\tinitComponents();\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\t\tinitTable();\n\t\tinitValues(initialStateValues);\n\n\t\tsuper.setBounds(new Rectangle(550, 300));\n\t\tsetResizable(true);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t}\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\t// <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n\tprivate void initComponents()\n\t{\n\t\tallPanel = new javax.swing.JPanel();\n\t\tbottomPanel = new javax.swing.JPanel();\n\t\tbuttonPanel = new javax.swing.JPanel();\n\t\tokayButton = new javax.swing.JButton();\n\t\tcancelButton = new javax.swing.JButton();\n\t\toptionCheckBox = new javax.swing.JCheckBox();\n\t\ttopPanel = new javax.swing.JPanel();\n\t\tinnerPanel = new javax.swing.JPanel();\n\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\n\t\tallPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tallPanel.setBorder(new javax.swing.border.EmptyBorder(new java.awt.Insets(5, 5, 5, 5)));\n\t\tbottomPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tbuttonPanel.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tokayButton.setText(\"Okay\");\n\t\tokayButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tokayButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tbuttonPanel.add(okayButton);\n\n\t\tcancelButton.setText(\"Cancel\");\n\t\tcancelButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tcancelButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tbuttonPanel.add(cancelButton);\n\n\t\tbottomPanel.add(buttonPanel, java.awt.BorderLayout.EAST);\n\n\t\toptionCheckBox.setText(\"Always prompt for initial state on path creation\");\n\t\toptionCheckBox.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\toptionCheckBoxActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\t//bottomPanel.add(optionCheckBox, java.awt.BorderLayout.WEST);\n\t\toptionCheckBox.getAccessibleContext().setAccessibleName(\"optionCheckBox\");\n\n\t\tallPanel.add(bottomPanel, java.awt.BorderLayout.SOUTH);\n\n\t\ttopPanel.setLayout(new java.awt.BorderLayout());\n\n\t\ttopPanel.setBorder(new javax.swing.border.TitledBorder(\"Initial state\"));\n\t\tinnerPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tinnerPanel.setBorder(new javax.swing.border.EmptyBorder(new java.awt.Insets(5, 5, 5, 5)));\n\t\ttopPanel.add(innerPanel, java.awt.BorderLayout.CENTER);\n\n\t\tallPanel.add(topPanel, java.awt.BorderLayout.CENTER);\n\n\t\tgetContentPane().add(allPanel, java.awt.BorderLayout.CENTER);\n\n\t}\n\n\t// </editor-fold>//GEN-END:initComponents\n\n\tprivate void optionCheckBoxActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_optionCheckBoxActionPerformed\n\t// TODO add your handling code here:\n\t}//GEN-LAST:event_optionCheckBoxActionPerformed\n\n\tprivate void initTable()\n\t{\n\t\tJScrollPane sp = new JScrollPane();\n\t\tsp.setViewportView(initValuesTable);\n\t\tinnerPanel.add(sp);\n\t\tinnerPanel.setPreferredSize(new Dimension(300, 300));\n\t}\n\n\tprivate void initValues(Values initialStateValues)\n\t{\n\t\ttry {\n\t\t\tboolean match = false;\n\t\t\t// If values have been passed in, see if they match the model\n\t\t\t// And if so, store them in the table\n\t\t\tif (initialStateValues != null) {\n\t\t\t\tmatch = true;\n\t\t\t\tif (initialStateValues.getNumValues() != numVars) {\n\t\t\t\t\tmatch = false;\n\t\t\t\t} else {\n\t\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\t\tString varName = modelGen.getVarName(i);\n\t\t\t\t\t\tif (!initialStateValues.contains(varName)) {\n\t\t\t\t\t\t\tmatch = false;\n\t\t\t\t\t\t\tbreak;\n\t\t\t\t\t\t} else {\n\t\t\t\t\t\t\ttry {\n\t\t\t\t\t\t\t\tObject value = initialStateValues.getValueOf(varName);\n\t\t\t\t\t\t\t\tvalue = modelGen.getVarType(i).castValueTo(value);\n\t\t\t\t\t\t\t\tinitValuesModel.setValue(i, value);\n\t\t\t\t\t\t\t} catch (PrismLangException e) {\n\t\t\t\t\t\t\t\tmatch = false;\n\t\t\t\t\t\t\t}\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Otherwise get default initial state for model and store in the table\n\t\t\tif (!match) {\n\t\t\t\tState defaultInitialState = modelGen.getInitialState();\n\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\tinitValuesModel.setValue(i, defaultInitialState.varValues[i]);\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\tgui.errorDialog(\"Error choosing initial state: \" + e.getMessage());\n\t\t}\n\t}\n\n\t/** Call this static method to construct a new GUIValuesPicker to define\n\t *  initialState.  If you don't want any default values, then pass in null for\n\t *  initDefaults\n\t */\n\tpublic static State defineInitalValuesWithDialog(GUIPrism parent, SimulatorEngine engine, Values initDefaults)\n\t{\n\t\treturn new GUIInitialStatePicker(parent, engine, initDefaults).defineValues();\n\t}\n\n\tpublic State defineValues()\n\t{\n\t\tsetVisible(true);\n\t\tif (cancelled)\n\t\t\treturn null;\n\t\telse\n\t\t\treturn initialState;\n\t}\n\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\t\tif (initValuesTable.getCellEditor() != null) {\n\t\t\tinitValuesTable.getCellEditor().stopCellEditing();\n\t\t}\n\n\t\tString varName = \"\";\n\t\tString valueString = \"\";\n\t\ttry {\n\t\t\tState newInitialState = new State(numVars);\n\t\t\t// check each variable value\n\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\tvarName = modelGen.getVarName(i);\n\t\t\t\tvalueString = initValuesModel.getValue(i).toString();\n\t\t\t\tExpression valueExpr = Prism.parseSingleExpressionString(valueString);\n\t\t\t\tif (!valueExpr.isConstant()) {\n\t\t\t\t\tthrow new PrismException(\"Not constant\");\n\t\t\t\t}\n\t\t\t\tObject valueObj = valueExpr.evaluate();\n\t\t\t\tif (!modelGen.getVarType(i).canCastTypeTo(valueExpr.getType())) {\n\t\t\t\t\tthrow new PrismException(\"Type mismatch\");\n\t\t\t\t}\n\t\t\t\tvalueObj = modelGen.getVarType(i).castValueTo(valueObj);\n\t\t\t\tnewInitialState.varValues[i] = valueObj;\n\t\t\t}\n\t\t\tinitialState = newInitialState;\n\t\t\tcancelled = false;\n\t\t\tdispose();\n\t\t} catch (PrismException e) {\n\t\t\tgui.errorDialog(\"Invalid value \\\"\" + valueString + \"\\\" for variable \" + varName + \": \" + e.getMessage());\n\t\t}\n\t}//GEN-LAST:event_okayButtonActionPerformed\n\n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\t\tdispose();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\n\tpublic void keyPressed(KeyEvent e)\n\t{\n\t}\n\n\tpublic void keyReleased(KeyEvent e)\n\t{\n\n\t}\n\n\tpublic void keyTyped(KeyEvent e)\n\t{\n\n\t}\n\n\tclass DefineValuesTable extends AbstractTableModel\n\t{\n\t\tObject[] values;\n\n\t\tpublic DefineValuesTable()\n\t\t{\n\t\t\tvalues = new Object[numVars];\n\t\t}\n\n\t\tpublic void setValue(int i, Object value)\n\t\t{\n\t\t\tvalues[i] = value;\n\t\t\tfireTableRowsInserted(i, i);\n\t\t}\n\n\t\tpublic Object getValue(int i)\n\t\t{\n\t\t\treturn values[i];\n\t\t}\n\n\t\tpublic int getColumnCount()\n\t\t{\n\t\t\treturn 3;\n\t\t}\n\n\t\tpublic int getRowCount()\n\t\t{\n\t\t\treturn numVars;\n\t\t}\n\n\t\tpublic Object getValueAt(int rowIndex, int columnIndex)\n\t\t{\n\t\t\ttry {\n\t\t\t\tswitch (columnIndex) {\n\t\t\t\tcase 0:\n\t\t\t\t\treturn modelGen.getVarName(rowIndex);\n\t\t\t\tcase 1:\n\t\t\t\t\treturn modelGen.getVarType(rowIndex);\n\t\t\t\tcase 2:\n\t\t\t\t\treturn values[rowIndex].toString();\n\t\t\t\tdefault:\n\t\t\t\t\treturn \"\";\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\n\t\tpublic String getColumnName(int columnIndex)\n\t\t{\n\t\t\tswitch (columnIndex) {\n\t\t\tcase 0:\n\t\t\t\treturn \"Name\";\n\t\t\tcase 1:\n\t\t\t\treturn \"Type\";\n\t\t\tcase 2:\n\t\t\t\treturn \"Value\";\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\n\t\tpublic boolean isCellEditable(int rowIndex, int columnIndex)\n\t\t{\n\t\t\tif (columnIndex == 2)\n\t\t\t\treturn true;\n\t\t\telse\n\t\t\t\treturn false;\n\t\t}\n\n\t\tpublic void setValueAt(Object aValue, int rowIndex, int columnIndex)\n\t\t{\n\t\t\tif (columnIndex == 2) {\n\t\t\t\tvalues[rowIndex] = aValue;\n\t\t\t\tfireTableCellUpdated(rowIndex, columnIndex);\n\t\t\t}\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\tString str = \"\";\n\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\tstr += modelGen.getVarName(i) + \"=\" + values[i].toString();\n\t\t\t\tif (i < numVars - 1) {\n\t\t\t\t\tstr += \",\";\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn str;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUIPathPlotDialog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport java.awt.BorderLayout;\nimport java.awt.FlowLayout;\nimport java.awt.GridBagConstraints;\nimport java.awt.GridBagLayout;\nimport java.awt.Insets;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.ActionListener;\nimport java.awt.event.KeyEvent;\nimport java.util.Vector;\n\nimport javax.swing.ButtonGroup;\nimport javax.swing.DefaultComboBoxModel;\nimport javax.swing.JButton;\nimport javax.swing.JCheckBox;\nimport javax.swing.JComboBox;\nimport javax.swing.JComponent;\nimport javax.swing.JDialog;\nimport javax.swing.JLabel;\nimport javax.swing.JPanel;\nimport javax.swing.JRadioButton;\nimport javax.swing.JRootPane;\nimport javax.swing.JScrollPane;\nimport javax.swing.JTabbedPane;\nimport javax.swing.JTextField;\nimport javax.swing.KeyStroke;\nimport javax.swing.border.EmptyBorder;\n\nimport parser.ast.ModulesFile;\nimport prism.PrismSettings;\nimport userinterface.CheckBoxList;\nimport userinterface.GUIPrism;\n\n@SuppressWarnings(\"serial\")\npublic class GUIPathPlotDialog extends JDialog\n{\n\t// ComboBox enums\n\n\tpublic enum SimulateChoice {\n\t\tSTEP, TIME;\n\t\tpublic String toString()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\tcase STEP:\n\t\t\t\treturn \"Up to step\";\n\t\t\tcase TIME:\n\t\t\t\treturn \"Up to time\";\n\t\t\tdefault:\n\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t};\n\n\tpublic enum ShowChoice {\n\t\tALL_STEPS, SNAPSHOTS;\n\t\tpublic String toString()\n\t\t{\n\t\t\tswitch (this) {\n\t\t\tcase ALL_STEPS:\n\t\t\t\treturn \"All steps\";\n\t\t\tcase SNAPSHOTS:\n\t\t\t\treturn \"Snapshots\";\n\t\t\tdefault:\n\t\t\t\treturn this.toString();\n\t\t\t}\n\t\t}\n\t};\n\n\t// Static instance\n\tprivate static GUIPathPlotDialog instance = null;\n\n\t// State\n\tprivate GUIPrism gui;\n\tprivate GUISimulator guiSim;\n\tprivate ModulesFile modulesFile;\n\tprivate boolean cancelled;\n\tprivate String simPathString;\n\tprivate long maxPathLength;\n\n\t// GUI objects\n\tprivate final JPanel topPanel = new JPanel();\n\tprivate JTextField textFieldTime;\n\tprivate JTextField textFieldInterval;\n\tprivate JLabel lblInterval;\n\tprivate JComboBox comboBoxShow;\n\tprivate JComboBox comboBoxSimulate;\n\tprivate JButton okButton;\n\tprivate JButton cancelButton;\n\tprivate JTabbedPane tabbedPane;\n\tprivate JPanel varsPanel;\n\tprivate CheckBoxList varsCheckList;\n\tprivate Vector<JCheckBox> varsCheckBoxes;\n\tprivate JPanel varsRadios;\n\tprivate JRadioButton rdbtnVarsAll;\n\tprivate JRadioButton rdbtnVarsSelected;\n\tprivate final ButtonGroup buttonGroupVars = new ButtonGroup();\n\tprivate JPanel rewardsPanel;\n\tprivate JLabel lblVarsShow;\n\tprivate JRadioButton rdbtnVarsNone;\n\tprivate JPanel bottomPanel;\n\tprivate JPanel mainPanel;\n\tprivate JCheckBox chckbxStrategy;\n\tprivate JCheckBox chckbxChanges;\n\tprivate JPanel rewardsRadios;\n\tprivate JLabel lblRewardsShow;\n\tprivate JRadioButton rdbtnRewardsAll;\n\tprivate JRadioButton rdbtnRewardsNone;\n\tprivate final ButtonGroup buttonGroupRewards = new ButtonGroup();\n\tprivate JLabel lblMaximumPathLength;\n\tprivate JTextField textFieldMaxLen;\n\n\t/**\n\t * Show \"Path Plot Details\" dialog, return the dialog.\n\t * Returns null if the dialog was cancelled.\n\t */\n\tpublic static GUIPathPlotDialog showDialog(GUIPrism parent, GUISimulator guiSim, ModulesFile modulesFile)\n\t{\n\t\tGUIPathPlotDialog dialog = getInstance(parent, guiSim, modulesFile);\n\t\tdialog.doEnables();\n\t\tdialog.setVisible(true);\n\t\treturn dialog.wasCancelled() ? null : dialog;\n\t}\n\n\t/**\n\t * Show \"Path Plot Details\" dialog, return settings as a simpath string.\n\t * Returns null if the dialog was cancelled.\n\t */\n\tpublic static String getPathPlotSettings(GUIPrism parent, GUISimulator guiSim, ModulesFile modulesFile)\n\t{\n\t\tGUIPathPlotDialog dialog = getInstance(parent, guiSim, modulesFile);\n\t\tdialog.doEnables();\n\t\tdialog.setVisible(true);\n\t\treturn dialog.wasCancelled() ? null : dialog.getSimPathString();\n\t}\n\n\t/**\n\t * Get static instance, creating if necessary.\n\t */\n\tprivate static GUIPathPlotDialog getInstance(GUIPrism parent, GUISimulator guiSim, ModulesFile modulesFile)\n\t{\n\t\tif (instance != null && instance.gui == parent && instance.modulesFile == modulesFile)\n\t\t\treturn instance;\n\t\telse {\n\t\t\tinstance = new GUIPathPlotDialog(parent, guiSim, modulesFile);\n\t\t\treturn instance;\n\t\t}\n\t}\n\n\tpublic boolean wasCancelled()\n\t{\n\t\treturn cancelled;\n\t}\n\n\tpublic String getSimPathString()\n\t{\n\t\treturn simPathString;\n\t}\n\n\tpublic long getMaxPathLength()\n\t{\n\t\treturn maxPathLength;\n\t}\n\n\t/**\n\t * Create the dialog.\n\t */\n\tpublic GUIPathPlotDialog(GUIPrism parent, GUISimulator guiSim, ModulesFile modulesFile)\n\t{\n\t\tsuper(parent, \"Path Plot Details\", true);\n\t\tthis.gui = parent;\n\t\tthis.guiSim = guiSim;\n\t\tthis.modulesFile = modulesFile;\n\t\tsetBounds(100, 100, 361, 401);\n\t\tgetContentPane().setLayout(new BorderLayout());\n\t\t{\n\t\t\tJPanel buttonPane = new JPanel();\n\t\t\tbuttonPane.setLayout(new FlowLayout(FlowLayout.RIGHT));\n\t\t\tgetContentPane().add(buttonPane, BorderLayout.SOUTH);\n\t\t\t{\n\t\t\t\tokButton = new JButton(\"OK\");\n\t\t\t\tokButton.setActionCommand(\"OK\");\n\t\t\t\tokButton.addActionListener(new ActionListener()\n\t\t\t\t{\n\t\t\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t\t\t{\n\t\t\t\t\t\tokButtonActionPerformed(e);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\tbuttonPane.add(okButton);\n\t\t\t\tgetRootPane().setDefaultButton(okButton);\n\t\t\t}\n\t\t\t{\n\t\t\t\tcancelButton = new JButton(\"Cancel\");\n\t\t\t\tcancelButton.addActionListener(new ActionListener()\n\t\t\t\t{\n\t\t\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t\t\t{\n\t\t\t\t\t\tcancelButtonActionPerformed(e);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\tcancelButton.setActionCommand(\"Cancel\");\n\t\t\t\tbuttonPane.add(cancelButton);\n\t\t\t}\n\t\t}\n\t\tthis.getRootPane().setDefaultButton(okButton);\n\t\t{\n\t\t\tmainPanel = new JPanel();\n\t\t\tgetContentPane().add(mainPanel, BorderLayout.CENTER);\n\t\t\tGridBagLayout gbl_mainPanel = new GridBagLayout();\n\t\t\tgbl_mainPanel.columnWidths = new int[] { 329, 0 };\n\t\t\tgbl_mainPanel.rowHeights = new int[] { 103, 0, 0 };\n\t\t\tgbl_mainPanel.columnWeights = new double[] { 0.0, Double.MIN_VALUE };\n\t\t\tgbl_mainPanel.rowWeights = new double[] { 0.0, 0.0, Double.MIN_VALUE };\n\t\t\tmainPanel.setLayout(gbl_mainPanel);\n\t\t\tmainPanel.setBorder(new EmptyBorder(10, 10, 10, 10));\n\t\t\tGridBagConstraints gbc_topPanel = new GridBagConstraints();\n\t\t\tgbc_topPanel.insets = new Insets(0, 0, 5, 0);\n\t\t\tgbc_topPanel.gridx = 0;\n\t\t\tgbc_topPanel.gridy = 0;\n\t\t\tmainPanel.add(topPanel, gbc_topPanel);\n\t\t\tGridBagLayout gbl_topPanel = new GridBagLayout();\n\t\t\tgbl_topPanel.columnWidths = new int[] { 50, 0, 0, 60, 0 };\n\t\t\tgbl_topPanel.rowHeights = new int[] { 0, 0, 0, 0, 0 };\n\t\t\tgbl_topPanel.columnWeights = new double[] { 0.0, 0.0, 1.0, 0.0, Double.MIN_VALUE };\n\t\t\tgbl_topPanel.rowWeights = new double[] { 0.0, 0.0, 0.0, 0.0, Double.MIN_VALUE };\n\t\t\ttopPanel.setLayout(gbl_topPanel);\n\t\t\t{\n\t\t\t\tJLabel lblSimulate = new JLabel(\"Simulate:\");\n\t\t\t\tGridBagConstraints gbc_lblSimulate = new GridBagConstraints();\n\t\t\t\tgbc_lblSimulate.insets = new Insets(0, 0, 5, 5);\n\t\t\t\tgbc_lblSimulate.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_lblSimulate.gridx = 0;\n\t\t\t\tgbc_lblSimulate.gridy = 0;\n\t\t\t\ttopPanel.add(lblSimulate, gbc_lblSimulate);\n\t\t\t}\n\t\t\t{\n\t\t\t\tcomboBoxSimulate = new JComboBox();\n\t\t\t\tcomboBoxSimulate.setModel(new DefaultComboBoxModel(SimulateChoice.values()));\n\t\t\t\tGridBagConstraints gbc_comboBoxSimulate = new GridBagConstraints();\n\t\t\t\tgbc_comboBoxSimulate.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_comboBoxSimulate.insets = new Insets(0, 0, 5, 5);\n\t\t\t\tgbc_comboBoxSimulate.gridx = 1;\n\t\t\t\tgbc_comboBoxSimulate.gridy = 0;\n\t\t\t\ttopPanel.add(comboBoxSimulate, gbc_comboBoxSimulate);\n\t\t\t}\n\t\t\t{\n\t\t\t\ttextFieldTime = new JTextField();\n\t\t\t\tGridBagConstraints gbc_textFieldTime = new GridBagConstraints();\n\t\t\t\tgbc_textFieldTime.fill = GridBagConstraints.HORIZONTAL;\n\t\t\t\tgbc_textFieldTime.insets = new Insets(0, 0, 5, 5);\n\t\t\t\tgbc_textFieldTime.gridx = 2;\n\t\t\t\tgbc_textFieldTime.gridy = 0;\n\t\t\t\ttopPanel.add(textFieldTime, gbc_textFieldTime);\n\t\t\t\ttextFieldTime.setColumns(5);\n\t\t\t}\n\t\t\t{\n\t\t\t\tJLabel lblShow = new JLabel(\"Sample:\");\n\t\t\t\tGridBagConstraints gbc_lblShow = new GridBagConstraints();\n\t\t\t\tgbc_lblShow.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_lblShow.insets = new Insets(0, 0, 5, 5);\n\t\t\t\tgbc_lblShow.gridx = 0;\n\t\t\t\tgbc_lblShow.gridy = 1;\n\t\t\t\ttopPanel.add(lblShow, gbc_lblShow);\n\t\t\t}\n\t\t\t{\n\t\t\t\tcomboBoxShow = new JComboBox();\n\t\t\t\tcomboBoxShow.addActionListener(new ActionListener()\n\t\t\t\t{\n\t\t\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t\t\t{\n\t\t\t\t\t\tcomboBoxShowActionPerformed(e);\n\t\t\t\t\t}\n\t\t\t\t});\n\t\t\t\tcomboBoxShow.setModel(new DefaultComboBoxModel(ShowChoice.values()));\n\t\t\t\tGridBagConstraints gbc_comboBoxShow = new GridBagConstraints();\n\t\t\t\tgbc_comboBoxShow.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_comboBoxShow.insets = new Insets(0, 0, 5, 5);\n\t\t\t\tgbc_comboBoxShow.gridx = 1;\n\t\t\t\tgbc_comboBoxShow.gridy = 1;\n\t\t\t\ttopPanel.add(comboBoxShow, gbc_comboBoxShow);\n\t\t\t}\n\t\t\t{\n\t\t\t\tlblInterval = new JLabel(\"of interval\");\n\t\t\t\tGridBagConstraints gbc_lblInterval = new GridBagConstraints();\n\t\t\t\tgbc_lblInterval.insets = new Insets(0, 0, 5, 5);\n\t\t\t\tgbc_lblInterval.gridx = 2;\n\t\t\t\tgbc_lblInterval.gridy = 1;\n\t\t\t\ttopPanel.add(lblInterval, gbc_lblInterval);\n\t\t\t}\n\t\t\t{\n\t\t\t\ttextFieldInterval = new JTextField();\n\t\t\t\tGridBagConstraints gbc_textFieldInterval = new GridBagConstraints();\n\t\t\t\tgbc_textFieldInterval.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_textFieldInterval.insets = new Insets(0, 0, 5, 0);\n\t\t\t\tgbc_textFieldInterval.gridx = 3;\n\t\t\t\tgbc_textFieldInterval.gridy = 1;\n\t\t\t\ttopPanel.add(textFieldInterval, gbc_textFieldInterval);\n\t\t\t\ttextFieldInterval.setColumns(5);\n\t\t\t}\n\t\t\t{\n\t\t\t\tchckbxStrategy = new JCheckBox(\"Enforce strategy\");\n\t\t\t\tGridBagConstraints gbc_chckbxStrategy = new GridBagConstraints();\n\t\t\t\tgbc_chckbxStrategy.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_chckbxStrategy.gridwidth = 2;\n\t\t\t\tgbc_chckbxStrategy.insets = new Insets(0, 0, 5, 5);\n\t\t\t\tgbc_chckbxStrategy.gridx = 0;\n\t\t\t\tgbc_chckbxStrategy.gridy = 2;\n\t\t\t\ttopPanel.add(chckbxStrategy, gbc_chckbxStrategy);\n\t\t\t}\n\t\t\t{\n\t\t\t\tchckbxChanges = new JCheckBox(\"Plot changes only\");\n\t\t\t\tGridBagConstraints gbc_chckbxChanges = new GridBagConstraints();\n\t\t\t\tgbc_chckbxChanges.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_chckbxChanges.gridwidth = 2;\n\t\t\t\tgbc_chckbxChanges.insets = new Insets(0, 0, 5, 5);\n\t\t\t\tgbc_chckbxChanges.gridx = 2;\n\t\t\t\tgbc_chckbxChanges.gridy = 2;\n\t\t\t\ttopPanel.add(chckbxChanges, gbc_chckbxChanges);\n\t\t\t}\n\t\t\t{\n\t\t\t\tlblMaximumPathLength = new JLabel(\"Maximum path length:\");\n\t\t\t\tGridBagConstraints gbc_lblMaximumPathLength = new GridBagConstraints();\n\t\t\t\tgbc_lblMaximumPathLength.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_lblMaximumPathLength.gridwidth = 2;\n\t\t\t\tgbc_lblMaximumPathLength.insets = new Insets(0, 0, 0, 5);\n\t\t\t\tgbc_lblMaximumPathLength.gridx = 0;\n\t\t\t\tgbc_lblMaximumPathLength.gridy = 3;\n\t\t\t\ttopPanel.add(lblMaximumPathLength, gbc_lblMaximumPathLength);\n\t\t\t}\n\t\t\t{\n\t\t\t\ttextFieldMaxLen = new JTextField();\n\t\t\t\tGridBagConstraints gbc_textFieldMaxLen = new GridBagConstraints();\n\t\t\t\tgbc_textFieldMaxLen.anchor = GridBagConstraints.WEST;\n\t\t\t\tgbc_textFieldMaxLen.gridwidth = 2;\n\t\t\t\tgbc_textFieldMaxLen.insets = new Insets(0, 0, 0, 5);\n\t\t\t\tgbc_textFieldMaxLen.gridx = 2;\n\t\t\t\tgbc_textFieldMaxLen.gridy = 3;\n\t\t\t\ttopPanel.add(textFieldMaxLen, gbc_textFieldMaxLen);\n\t\t\t\ttextFieldMaxLen.setColumns(8);\n\t\t\t}\n\t\t\t{\n\t\t\t\tbottomPanel = new JPanel();\n\t\t\t\tGridBagConstraints gbc_bottomPanel = new GridBagConstraints();\n\t\t\t\tgbc_bottomPanel.fill = GridBagConstraints.VERTICAL;\n\t\t\t\tgbc_bottomPanel.gridx = 0;\n\t\t\t\tgbc_bottomPanel.gridy = 1;\n\t\t\t\tmainPanel.add(bottomPanel, gbc_bottomPanel);\n\t\t\t\tGridBagLayout gbl_bottomPanel = new GridBagLayout();\n\t\t\t\tgbl_bottomPanel.columnWidths = new int[] { 20, 0 };\n\t\t\t\tgbl_bottomPanel.rowHeights = new int[] { 120, 0 };\n\t\t\t\tgbl_bottomPanel.columnWeights = new double[] { 0.0, Double.MIN_VALUE };\n\t\t\t\tgbl_bottomPanel.rowWeights = new double[] { 0.0, Double.MIN_VALUE };\n\t\t\t\tbottomPanel.setLayout(gbl_bottomPanel);\n\t\t\t\ttabbedPane = new JTabbedPane(JTabbedPane.TOP);\n\t\t\t\tGridBagConstraints gbc_tabbedPane = new GridBagConstraints();\n\t\t\t\tgbc_tabbedPane.fill = GridBagConstraints.HORIZONTAL;\n\t\t\t\tgbc_tabbedPane.gridx = 0;\n\t\t\t\tgbc_tabbedPane.gridy = 0;\n\t\t\t\tbottomPanel.add(tabbedPane, gbc_tabbedPane);\n\t\t\t\t{\n\t\t\t\t\tvarsPanel = new JPanel();\n\t\t\t\t\ttabbedPane.addTab(\"Variables\", null, varsPanel, null);\n\t\t\t\t\tGridBagLayout gbl_varsPanel = new GridBagLayout();\n\t\t\t\t\tgbl_varsPanel.columnWidths = new int[] { 260, 0 };\n\t\t\t\t\tgbl_varsPanel.rowHeights = new int[] { 33, 10, 0 };\n\t\t\t\t\tgbl_varsPanel.columnWeights = new double[] { 0.0, Double.MIN_VALUE };\n\t\t\t\t\tgbl_varsPanel.rowWeights = new double[] { 0.0, 0.0, Double.MIN_VALUE };\n\t\t\t\t\tvarsPanel.setLayout(gbl_varsPanel);\n\t\t\t\t\t{\n\t\t\t\t\t\tvarsRadios = new JPanel();\n\t\t\t\t\t\tFlowLayout fl_varsRadios = (FlowLayout) varsRadios.getLayout();\n\t\t\t\t\t\tfl_varsRadios.setAlignment(FlowLayout.LEFT);\n\t\t\t\t\t\tGridBagConstraints gbc_varsRadios = new GridBagConstraints();\n\t\t\t\t\t\tgbc_varsRadios.anchor = GridBagConstraints.NORTHWEST;\n\t\t\t\t\t\tgbc_varsRadios.insets = new Insets(0, 0, 5, 0);\n\t\t\t\t\t\tgbc_varsRadios.gridx = 0;\n\t\t\t\t\t\tgbc_varsRadios.gridy = 0;\n\t\t\t\t\t\tvarsPanel.add(varsRadios, gbc_varsRadios);\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tlblVarsShow = new JLabel(\"Show:\");\n\t\t\t\t\t\t\tvarsRadios.add(lblVarsShow);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\trdbtnVarsAll = new JRadioButton(\"All\");\n\t\t\t\t\t\t\tbuttonGroupVars.add(rdbtnVarsAll);\n\t\t\t\t\t\t\trdbtnVarsAll.addActionListener(new ActionListener()\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t\tdoEnables();\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\tvarsRadios.add(rdbtnVarsAll);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\trdbtnVarsNone = new JRadioButton(\"None\");\n\t\t\t\t\t\t\tbuttonGroupVars.add(rdbtnVarsNone);\n\t\t\t\t\t\t\trdbtnVarsNone.addActionListener(new ActionListener()\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t\tdoEnables();\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\tvarsRadios.add(rdbtnVarsNone);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\trdbtnVarsSelected = new JRadioButton(\"Selected\");\n\t\t\t\t\t\t\tbuttonGroupVars.add(rdbtnVarsSelected);\n\t\t\t\t\t\t\trdbtnVarsSelected.addActionListener(new ActionListener()\n\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t\t\t\t\t\t{\n\t\t\t\t\t\t\t\t\tdoEnables();\n\t\t\t\t\t\t\t\t}\n\t\t\t\t\t\t\t});\n\t\t\t\t\t\t\tvarsRadios.add(rdbtnVarsSelected);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t{\n\t\t\t\t\t\tJScrollPane varsScroll = new JScrollPane();\n\t\t\t\t\t\tvarsCheckList = new CheckBoxList();\n\t\t\t\t\t\tvarsScroll.setViewportView(varsCheckList);\n\t\t\t\t\t\tvarsCheckBoxes = new Vector<JCheckBox>();\n\t\t\t\t\t\tvarsCheckList.setListData(varsCheckBoxes);\n\t\t\t\t\t\tGridBagConstraints gbc_varsScroll = new GridBagConstraints();\n\t\t\t\t\t\tgbc_varsScroll.anchor = GridBagConstraints.NORTH;\n\t\t\t\t\t\tgbc_varsScroll.fill = GridBagConstraints.HORIZONTAL;\n\t\t\t\t\t\tgbc_varsScroll.gridx = 0;\n\t\t\t\t\t\tgbc_varsScroll.gridy = 1;\n\t\t\t\t\t\tvarsPanel.add(varsScroll, gbc_varsScroll);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t{\n\t\t\t\t\trewardsPanel = new JPanel();\n\t\t\t\t\ttabbedPane.addTab(\"Rewards\", null, rewardsPanel, null);\n\t\t\t\t\t{\n\t\t\t\t\t\trewardsRadios = new JPanel();\n\t\t\t\t\t\trewardsPanel.add(rewardsRadios);\n\t\t\t\t\t\trewardsRadios.setLayout(new FlowLayout(FlowLayout.CENTER, 5, 5));\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\tlblRewardsShow = new JLabel(\"Show:\");\n\t\t\t\t\t\t\trewardsRadios.add(lblRewardsShow);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\trdbtnRewardsAll = new JRadioButton(\"All\");\n\t\t\t\t\t\t\tbuttonGroupRewards.add(rdbtnRewardsAll);\n\t\t\t\t\t\t\trewardsRadios.add(rdbtnRewardsAll);\n\t\t\t\t\t\t}\n\t\t\t\t\t\t{\n\t\t\t\t\t\t\trdbtnRewardsNone = new JRadioButton(\"None\");\n\t\t\t\t\t\t\tbuttonGroupRewards.add(rdbtnRewardsNone);\n\t\t\t\t\t\t\trewardsRadios.add(rdbtnRewardsNone);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tinitComponents();\n\t}\n\n\tprivate void initComponents()\n\t{\n\t\tif (modulesFile.getModelType().continuousTime()) {\n\t\t\tcomboBoxSimulate.setSelectedItem(SimulateChoice.TIME);\n\t\t\tcomboBoxShow.setSelectedItem(ShowChoice.SNAPSHOTS);\n\t\t\ttextFieldTime.setText(\"10.0\");\n\t\t\ttextFieldInterval.setText(\"0.1\");\n\t\t} else {\n\t\t\tcomboBoxSimulate.setSelectedItem(SimulateChoice.STEP);\n\t\t\tcomboBoxShow.setSelectedItem(ShowChoice.ALL_STEPS);\n\t\t\ttextFieldTime.setText(\"100\");\n\t\t\ttextFieldInterval.setText(\"\");\n\t\t}\n\t\tchckbxStrategy.setSelected(true);\n\t\tchckbxChanges.setSelected(true);\n\t\ttextFieldMaxLen.setText(\"\" + gui.getPrism().getSettings().getLong(PrismSettings.SIMULATOR_DEFAULT_MAX_PATH));\n\t\trdbtnVarsAll.setSelected(true);\n\t\tfor (int i = 0; i < modulesFile.getNumVars(); i++) {\n\t\t\tvarsCheckBoxes.add(new JCheckBox(modulesFile.getVarName(i)));\n\t\t}\n\t\t//\n\t\tsetDefaultCloseOperation(JDialog.DISPOSE_ON_CLOSE);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t\tpack();\n\t\tdoEnables();\n\t\tcancelled = true;\n\t}\n\n\tprivate void doEnables()\n\t{\n\t\tif ((ShowChoice) comboBoxShow.getSelectedItem() == ShowChoice.SNAPSHOTS) {\n\t\t\tlblInterval.setEnabled(true);\n\t\t\ttextFieldInterval.setEnabled(true);\n\t\t} else {\n\t\t\tlblInterval.setEnabled(false);\n\t\t\ttextFieldInterval.setEnabled(false);\n\t\t}\n\t\tchckbxStrategy.setEnabled(guiSim.getSimulatorEngine().hasStrategyInfo());\n\t\t// Variable list enabled iff \"show selected\"\n\t\tif (rdbtnVarsSelected.isSelected()) {\n\t\t\tvarsCheckList.setEnabled(true);\n\t\t\tfor (JCheckBox cb : varsCheckBoxes) {\n\t\t\t\tcb.setEnabled(true);\n\t\t\t}\n\t\t} else {\n\t\t\tvarsCheckList.setEnabled(false);\n\t\t\tfor (JCheckBox cb : varsCheckBoxes) {\n\t\t\t\tcb.setEnabled(false);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void comboBoxShowActionPerformed(ActionEvent e)\n\t{\n\t\tdoEnables();\n\t}\n\n\tpublic void okButtonActionPerformed(ActionEvent event)\n\t{\n\t\t// Validate inputs and build simpath string, store max path len\n\t\tsimPathString = \"\";\n\t\tswitch ((SimulateChoice) comboBoxSimulate.getSelectedItem()) {\n\t\tcase STEP:\n\t\t\ttry {\n\t\t\t\tint i = Integer.parseInt(textFieldTime.getText());\n\t\t\t\tif (i < 0)\n\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\tsimPathString += i;\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tgui.errorDialog(\"Invalid number of steps \\\"\" + textFieldTime.getText() + \"\\\"\");\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tbreak;\n\t\tcase TIME:\n\t\t\ttry {\n\t\t\t\tdouble d = Double.parseDouble(textFieldTime.getText());\n\t\t\t\tif (d < 0)\n\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\tsimPathString += \"time=\" + d;\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tgui.errorDialog(\"Invalid time \\\"\" + textFieldTime.getText() + \"\\\"\");\n\t\t\t\treturn;\n\t\t\t}\n\t\t\tbreak;\n\t\t}\n\t\tif ((ShowChoice) comboBoxShow.getSelectedItem() == ShowChoice.SNAPSHOTS) {\n\t\t\ttry {\n\t\t\t\tdouble d = Double.parseDouble(textFieldInterval.getText());\n\t\t\t\tif (d < 0)\n\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\tsimPathString += \",snapshot=\" + d;\n\t\t\t} catch (NumberFormatException e) {\n\t\t\t\tgui.errorDialog(\"Invalid time interval \\\"\" + textFieldInterval.getText() + \"\\\"\");\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\tguiSim.getSimulatorEngine().setStrategyEnforced(chckbxChanges.isSelected());\n\t\tif (chckbxChanges.isSelected()) {\n\t\t\tsimPathString += \",changes=true\";\n\t\t}\n\t\tif (rdbtnVarsNone.isSelected()) {\n\t\t\tsimPathString += \",vars=()\";\n\t\t} else if (rdbtnVarsSelected.isSelected()) {\n\t\t\tString s = \"\";\n\t\t\tfor (JCheckBox cb : varsCheckBoxes) {\n\t\t\t\tif (cb.isSelected()) {\n\t\t\t\t\ts += \",\" + cb.getText();\n\t\t\t\t}\n\t\t\t}\n\t\t\tsimPathString += \",vars=(\" + s + \")\";\n\t\t}\n\t\tsimPathString += \",rewards=\" + rdbtnRewardsAll.isSelected();\n\t\ttry {\n\t\t\tlong l = Long.parseLong(textFieldMaxLen.getText());\n\t\t\tif (l < 0)\n\t\t\t\tthrow new NumberFormatException();\n\t\t\tmaxPathLength = l;\n\t\t} catch (NumberFormatException e) {\n\t\t\tgui.errorDialog(\"Invalid maximum path length \\\"\" + textFieldMaxLen.getText() + \"\\\"\");\n\t\t\treturn;\n\t\t}\n\t\t\n\t\tcancelled = false;\n\t\tdispose();\n\t}\n\n\tpublic void cancelButtonActionPerformed(ActionEvent e)\n\t{\n\t\tcancelled = true;\n\t\tdispose();\n\t}\n\n\t// Close when Escape pressed\n\tprotected JRootPane createRootPane()\n\t{\n\t\tActionListener actionListener = new ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent actionEvent)\n\t\t\t{\n\t\t\t\tcancelled = true;\n\t\t\t\tdispose();\n\t\t\t}\n\t\t};\n\t\tKeyStroke stroke = KeyStroke.getKeyStroke(KeyEvent.VK_ESCAPE, 0);\n\t\tJRootPane rootPane = new JRootPane();\n\t\trootPane.registerKeyboardAction(actionListener, stroke, JComponent.WHEN_IN_FOCUSED_WINDOW);\n\t\treturn rootPane;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUISimLabelList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport java.awt.*;\nimport javax.swing.*;\n\nimport parser.ast.*;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport userinterface.properties.*;\nimport simulator.*;\n\n/**\n * List of labels in the simulator GUI.\n */\npublic class GUISimLabelList extends JList\n{\n\t// Default serial ID\n\tprivate static final long serialVersionUID = 1L;\n\t// Background colour of selected list items\n\tprivate static final Color background = new Color(202, 225, 255);\n\t// Pointers to simulator and GUI\n\tprivate GUISimulator sim;\n\tprivate SimulatorEngine engine;\n\t// The list of labels\n\tprivate DefaultListModel listModel;\n\n\t/**\n\t * Create a new instance of GUISimLabelList\n\t */\n\tpublic GUISimLabelList(GUISimulator sim)\n\t{\n\t\tthis.sim = sim;\n\t\tthis.engine = sim.getPrism().getSimulator();\n\t\tlistModel = new DefaultListModel();\n\t\tsetModel(listModel);\n\t\tsetCellRenderer(new SimLabelRenderer());\n\t}\n\n\t/**\n\t * Clear the list of labels.\n\t */\n\tpublic void clearLabels()\n\t{\n\t\tlistModel.clear();\n\t}\n\n\t/**\n\t * Add a (model file) label to the list.\n\t * Any required formulas/labels will be in the associated model, already in the simulator.\n\t */\n\tpublic void addModelLabel(String name, Expression expr)\n\t{\n\t\ttry {\n\t\t\tint index = engine.addLabel(expr);\n\t\t\tSimLabel sl = new SimLabel(name, index);\n\t\t\tlistModel.addElement(sl);\n\t\t}\n\t\tcatch (PrismLangException e) {\n\t\t\t// Silently ignore any problems - just don't add label to list\n\t\t}\n\t}\n\n\t/**\n\t * Add a (properties file) label to the list.\n\t * The associated properties file is also (optionally) passed in so that\n\t * any required formulas/labels (not in the model file) can be obtained.\n\t */\n\tpublic void addPropertyLabel(String name, Expression expr, PropertiesFile pf)\n\t{\n\t\ttry {\n\t\t\tint index = engine.addLabel(expr, pf);\n\t\t\tSimLabel sl = new SimLabel(name, index);\n\t\t\tlistModel.addElement(sl);\n\t\t}\n\t\tcatch (PrismLangException e) {\n\t\t\t// Silently ignore any problems - just don't add label to list\n\t\t}\n\t}\n\n\t/**\n\t * Add the special deadlock/init labels to the list.\n\t */\n\tpublic void addDeadlockAndInit()\n\t{\n\t\tlistModel.addElement(new InitSimLabel());\n\t\tlistModel.addElement(new DeadlockSimLabel());\n\t}\n\n\t/**\n\t * Class to store a normal label, that has been loaded into the simulator.\n\t */\n\tclass SimLabel\n\t{\n\t\t// Label name\n\t\tprivate String name;\n\t\t// Index of the label in the simulator engine\n\t\tprivate int index;\n\n\t\tpublic SimLabel(String name, int index)\n\t\t{\n\t\t\tthis.name = name;\n\t\t\tthis.index = index;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn name;\n\t\t}\n\n\t\t/**\n\t\t * Get the value of the label in the current state of the simulator.\n\t\t * 1 denotes true, 0 false, and -1 error/unknown\n\t\t */\n\t\tpublic int getResult()\n\t\t{\n\t\t\ttry {\n\t\t\t\tboolean b = engine.queryLabel(index);\n\t\t\t\treturn b ? 1 : 0;\n\t\t\t} catch (PrismLangException e) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Get the value of the label in a particular step of the current simulator path.\n\t\t * 1 denotes true, 0 false, and -1 error/unknown\n\t\t */\n\t\tpublic int getResult(int step)\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn engine.queryLabel(index, step) ? 1 : 0;\n\t\t\t} catch (PrismLangException e) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Class to store the special \"init\" label.\n\t */\n\tclass InitSimLabel extends SimLabel\n\t{\n\t\tpublic InitSimLabel()\n\t\t{\n\t\t\tsuper(\"init\", 0);\n\t\t}\n\n\t\t@Override\n\t\tpublic int getResult()\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn engine.queryIsInitial() ? 1 : 0;\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic int getResult(int step)\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn engine.queryIsInitial(step) ? 1 : 0;\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Class to store the special \"deadlock\" label.\n\t */\n\tclass DeadlockSimLabel extends SimLabel\n\t{\n\t\tpublic DeadlockSimLabel()\n\t\t{\n\t\t\tsuper(\"deadlock\", 0);\n\t\t}\n\n\t\t@Override\n\t\tpublic int getResult()\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn engine.queryIsDeadlock() ? 1 : 0;\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic int getResult(int step)\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn engine.queryIsDeadlock(step) ? 1 : 0;\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\t}\n\n\t// RENDERERS\n\n\tclass SimLabelRenderer extends JLabel implements ListCellRenderer\n\t{\n\t\t// Default serial ID\n\t\tprivate static final long serialVersionUID = 1L;\n\t\t// Tooltip text\n\t\tprivate String text;\n\n\t\tpublic SimLabelRenderer()\n\t\t{\n\t\t\tsetOpaque(true);\n\t\t\ttext = \"Unknown\";\n\t\t}\n\n\t\tpublic String getToolTipText()\n\t\t{\n\t\t\treturn text;\n\t\t}\n\n\t\tpublic Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus)\n\t\t{\n\t\t\tsetBorder(new BottomBorder());\n\t\t\t// Get label\n\t\t\tSimLabel l = (SimLabel) value;\n\t\t\tsetText(l.toString());\n\t\t\t// Extract value of label (either for current state or an earlier path step).\n\t\t\tint val = sim.isOldUpdate() ? l.getResult(sim.getOldUpdateStep()) : l.getResult();\n\t\t\tswitch (val) {\n\t\t\tcase 1:\n\t\t\t\ttext = \"True\";\n\t\t\t\tsetIcon(GUIProperty.IMAGE_TICK);\n\t\t\t\tbreak;\n\t\t\tcase 0:\n\t\t\t\ttext = \"False\";\n\t\t\t\tsetIcon(GUIProperty.IMAGE_CROSS);\n\t\t\t\tbreak;\n\t\t\tdefault:\n\t\t\t\ttext = \"Unknown\";\n\t\t\t\tsetIcon(GUIProperty.IMAGE_NOT_DONE);\n\t\t\t\tbreak;\n\t\t\t}\n\t\t\t// Set BG colour\n\t\t\tsetBackground(isSelected ? background : Color.white);\n\t\t\trepaint();\n\t\t\treturn this;\n\t\t}\n\n\t}\n\n\tclass BottomBorder implements javax.swing.border.Border\n\t{\n\t\tpublic Insets getBorderInsets(Component c)\n\t\t{\n\t\t\treturn new Insets(0, 0, 0, 0);\n\t\t}\n\n\t\tpublic boolean isBorderOpaque()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\tpublic void paintBorder(Component c, Graphics g, int x, int y, int width, int height)\n\t\t{\n\t\t\tg.setColor(Color.lightGray);\n\t\t\tg.drawLine(x, (y + height - 1), (x + width), (y + height - 1));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUISimPathFormulaeList.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport java.awt.*;\nimport javax.swing.*;\n\nimport parser.ast.*;\nimport prism.PrismException;\nimport userinterface.properties.*;\nimport simulator.*;\n\n@SuppressWarnings(\"serial\")\npublic class GUISimPathFormulaeList extends JList<GUISimPathFormulaeList.SimPathFormula>\n{\n\n\tprivate GUISimulator guiSim;\n\tprivate SimulatorEngine engine;\n\tprivate DefaultListModel<SimPathFormula> listModel;\n\n\t/** Creates a new instance of GUISimPathFormulaeList */\n\tpublic GUISimPathFormulaeList(GUISimulator guiSim)\n\t{\n\t\tthis.guiSim = guiSim;\n\t\tthis.engine = guiSim.getPrism().getSimulator();\n\t\tlistModel = new DefaultListModel<>();\n\t\tsetModel(listModel);\n\n\t\tsetCellRenderer(new SimPathFormulaRenderer());\n\t}\n\n\tpublic void clearList()\n\t{\n\t\tlistModel.clear();\n\t}\n\n\t// TODO: cut (subsumed by below)\n\tpublic void addRewardFormula(ExpressionReward rew)\n\t{\n\t\tString str = rew.getExpression().toString();\n\n\t\tfor (int i = 0; i < listModel.getSize(); i++) {\n\t\t\tif (listModel.getElementAt(i).toString().equals(str))\n\t\t\t\treturn;// if this already is in here, do not add it\n\t\t}\n\n\t\t// TODO: re-enable\n\t\tlong pathPointer = -1;//engine.addExpressionReward(rew);\n\t\tif (pathPointer <= 0)\n\t\t\treturn;\n\t\tint index = -1;//engine.findPathFormulaIndex(pathPointer);\n\n\t\tSimPathFormula form = new SimPathFormula(str, index);\n\t\tlistModel.addElement(form);\n\t}\n\n\tpublic void addProperty(Expression prop, PropertiesFile propertiesFile)\n\t{\n\t\ttry {\n\t\t\t//String str = prop.getExpression().toString();\n\t\t\tString str;\n\t\t\tif (prop instanceof ExpressionProb) {\n\t\t\t\t// for a P expression, only display the inner path formula\n\t\t\t\tstr = ((ExpressionProb)prop).getExpression().toString();\n\t\t\t} else {\n\t\t\t\tstr = prop.toString();\n\t\t\t}\n\t\t\tfor (int i = 0; i < listModel.getSize(); i++) {\n\t\t\t\tif (listModel.getElementAt(i).toString().equals(str))\n\t\t\t\t\treturn;// if this already is in here, do not add it\n\t\t\t}\n\t\t\tint index = engine.addProperty(prop, propertiesFile);\n\t\t\tSimPathFormula form = new SimPathFormula(str, index);\n\t\t\tlistModel.addElement(form);\n\t\t}\n\t\tcatch (PrismException e) {\n\t\t\t// Silently ignore any problems - just don't add label to list\n\t\t}\n\t}\n\n\tclass SimPathFormula\n\t{\n\t\tString pathFormula;\n\t\tint pathFormulaIndex;\n\n\t\tpublic SimPathFormula(String pathFormula, int pathFormulaIndex)\n\t\t{\n\t\t\tthis.pathFormula = pathFormula;\n\t\t\tthis.pathFormulaIndex = pathFormulaIndex;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn pathFormula;\n\t\t}\n\n\t\tpublic Object getResult()\n\t\t{\n\t\t\treturn engine.queryProperty(pathFormulaIndex);\n\t\t}\n\t}\n\n\t// RENDERERS\n\n\t@SuppressWarnings(\"serial\")\n\tclass SimPathFormulaRenderer extends JLabel implements ListCellRenderer<SimPathFormula>\n\t{\n\t\tString lastText;\n\n\t\tpublic SimPathFormulaRenderer()\n\t\t{\n\t\t\tsetOpaque(true);\n\t\t\tlastText = \"Unknown\";\n\t\t}\n\n\t\tpublic String getToolTipText()\n\t\t{\n\t\t\treturn lastText;\n\t\t}\n\n\t\tpublic Component getListCellRendererComponent(JList<? extends SimPathFormula> list, SimPathFormula value, int index, boolean isSelected,\n\t\t\t\tboolean cellHasFocus)\n\t\t{\n\t\t\tsetBorder(new BottomBorder());\n\t\t\tSimPathFormula l = (SimPathFormula) value;\n\n\t\t\tsetText(l.toString());\n\n\t\t\tObject result = l.getResult();\n\n\t\t\tif (result instanceof Boolean) {\n\t\t\t\tlastText = ((Boolean) result).booleanValue() ? \"True\" : \"False\";\n\t\t\t\tsetIcon(((Boolean) result).booleanValue() ? GUIProperty.IMAGE_TICK : GUIProperty.IMAGE_CROSS);\n\t\t\t} else if (result != null) {\n\t\t\t\tlastText = result.toString();\n\t\t\t\tsetIcon(GUIProperty.IMAGE_NUMBER);\n\t\t\t} else {\n\t\t\t\tlastText = \"Unknown\";\n\t\t\t\tsetIcon(GUIProperty.IMAGE_NOT_DONE);\n\t\t\t}\n\n\t\t\tsetBackground(Color.white);\n\n\t\t\trepaint();\n\t\t\treturn this;\n\t\t}\n\n\t}\n\n\tclass BottomBorder implements javax.swing.border.Border\n\t{\n\t\tpublic Insets getBorderInsets(Component c)\n\t\t{\n\t\t\treturn new Insets(0, 0, 0, 0);\n\t\t}\n\n\t\tpublic boolean isBorderOpaque()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\tpublic void paintBorder(Component c, Graphics g, int x, int y, int width, int height)\n\t\t{\n\t\t\tg.setColor(Color.lightGray);\n\t\t\tg.drawLine(x, (y + height - 1), (x + width), (y + height - 1));\n\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUISimulator.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n  <NonVisualComponents>\n    <Component class=\"javax.swing.ButtonGroup\" name=\"buttonGroup1\">\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"innerButtonPanel\">\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n        <Property name=\"columns\" type=\"int\" value=\"2\"/>\n        <Property name=\"horizontalGap\" type=\"int\" value=\"10\"/>\n        <Property name=\"rows\" type=\"int\" value=\"2\"/>\n        <Property name=\"verticalGap\" type=\"int\" value=\"10\"/>\n      </Layout>\n      <SubComponents>\n        <Component class=\"javax.swing.JButton\" name=\"newPathButton\">\n          <Properties>\n            <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.netbeans.modules.form.editors2.IconEditor\">\n              <Image iconType=\"2\" name=\"\"/>\n            </Property>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"New Path\"/>\n            <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"New Path\"/>\n            <Property name=\"horizontalAlignment\" type=\"int\" value=\"10\"/>\n            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[119, 28]\"/>\n            </Property>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"newPathButtonActionPerformed\"/>\n          </Events>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n          </AuxValues>\n        </Component>\n        <Component class=\"javax.swing.JButton\" name=\"resetPathButton\">\n          <Properties>\n            <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.netbeans.modules.form.editors2.IconEditor\">\n              <Image iconType=\"2\" name=\"\"/>\n            </Property>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Reset Path\"/>\n            <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"Reset Path\"/>\n            <Property name=\"horizontalAlignment\" type=\"int\" value=\"10\"/>\n            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[119, 28]\"/>\n            </Property>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"resetPathButtonActionPerformed\"/>\n          </Events>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n          </AuxValues>\n        </Component>\n        <Component class=\"javax.swing.JButton\" name=\"exportPathButton\">\n          <Properties>\n            <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.netbeans.modules.form.editors2.IconEditor\">\n              <Image iconType=\"2\" name=\"\"/>\n            </Property>\n            <Property name=\"text\" type=\"java.lang.String\" value=\"Export Path\"/>\n            <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"Export Path\"/>\n            <Property name=\"horizontalAlignment\" type=\"int\" value=\"10\"/>\n            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[119, 28]\"/>\n            </Property>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"exportPathButtonActionPerformed\"/>\n          </Events>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n          </AuxValues>\n        </Component>\n        <Component class=\"javax.swing.JButton\" name=\"configureViewButton\">\n          <Properties>\n            <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.netbeans.modules.form.editors2.IconEditor\">\n              <Image iconType=\"2\" name=\"\"/>\n            </Property>\n            <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"Export Path\"/>\n            <Property name=\"actionCommand\" type=\"java.lang.String\" value=\"Configure View\"/>\n            <Property name=\"horizontalAlignment\" type=\"int\" value=\"10\"/>\n            <Property name=\"label\" type=\"java.lang.String\" value=\"Configure View\"/>\n            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[119, 28]\"/>\n            </Property>\n          </Properties>\n          <Events>\n            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"configureViewButtonActionPerformed\"/>\n          </Events>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n          </AuxValues>\n        </Component>\n      </SubComponents>\n    </Container>\n    <Component class=\"javax.swing.JTable\" name=\"pathTable\">\n      <Properties>\n        <Property name=\"model\" type=\"javax.swing.table.TableModel\" editor=\"org.netbeans.modules.form.editors2.TableModelEditor\">\n          <Table columnCount=\"4\" rowCount=\"4\">\n            <Column editable=\"true\" title=\"Title 1\" type=\"java.lang.Object\"/>\n            <Column editable=\"true\" title=\"Title 2\" type=\"java.lang.Object\"/>\n            <Column editable=\"true\" title=\"Title 3\" type=\"java.lang.Object\"/>\n            <Column editable=\"true\" title=\"Title 4\" type=\"java.lang.Object\"/>\n          </Table>\n        </Property>\n      </Properties>\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"pathTable = new GUISimulatorPathTable(this, pathTableModel, engine);&#xa;\"/>\n      </AuxValues>\n    </Component>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel2\">\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JSplitPane\" name=\"jSplitPane1\">\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                  <JSplitPaneConstraints position=\"left\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel4\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                  <JSplitPaneConstraints position=\"right\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </NonVisualComponents>\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,3,7,0,0,3,102\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"allPanel\">\n      <Properties>\n        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n          </Border>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JSplitPane\" name=\"horizontalSplit\">\n          <Properties>\n            <Property name=\"dividerLocation\" type=\"int\" value=\"211\"/>\n            <Property name=\"orientation\" type=\"int\" value=\"0\"/>\n            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n              <Dimension value=\"[0, 0]\"/>\n            </Property>\n            <Property name=\"oneTouchExpandable\" type=\"boolean\" value=\"true\"/>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                  </Border>\n                </Property>\n                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[300, 10]\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[302, 591]\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                  <JSplitPaneConstraints position=\"left\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JSplitPane\" name=\"topSplit\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"null\"/>\n                    </Property>\n                    <Property name=\"dividerLocation\" type=\"int\" value=\"600\"/>\n                    <Property name=\"resizeWeight\" type=\"double\" value=\"0.75\"/>\n                    <Property name=\"continuousLayout\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"doubleBuffered\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[0, 0]\"/>\n                    </Property>\n                    <Property name=\"oneTouchExpandable\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[0, 0]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"Center\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JTabbedPane\" name=\"tabbedPane\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"0\" left=\"10\" right=\"0\" top=\"0\"/>\n                          </Border>\n                        </Property>\n                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                          <Dimension value=\"[0, 0]\"/>\n                        </Property>\n                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                          <Dimension value=\"[0, 50]\"/>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                          <JSplitPaneConstraints position=\"right\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\"/>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JPanel\" name=\"outerStateLabelPanel\">\n                          <Properties>\n                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                              </Border>\n                            </Property>\n                            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[34, 0]\"/>\n                            </Property>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n                              <JTabbedPaneConstraints tabName=\"State labels\">\n                                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"State labels\"/>\n                              </JTabbedPaneConstraints>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JScrollPane\" name=\"stateLabelScrollPane\">\n                              <Properties>\n                                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[24, 0]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"Center\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                              <SubComponents>\n                                <Component class=\"javax.swing.JList\" name=\"stateLabelList\">\n                                  <AuxValues>\n                                    <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"stateLabelList = new GUISimLabelFormulaeList(this);\"/>\n                                  </AuxValues>\n                                </Component>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                        <Container class=\"javax.swing.JPanel\" name=\"outerPathFormulaePanel\">\n                          <Properties>\n                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                              </Border>\n                            </Property>\n                            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[34, 0]\"/>\n                            </Property>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n                              <JTabbedPaneConstraints tabName=\"Path formulae\">\n                                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Path formulae\"/>\n                              </JTabbedPaneConstraints>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JScrollPane\" name=\"pathFormulaeScrollPane\">\n                              <Properties>\n                                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[24, 0]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"Center\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                              <SubComponents>\n                                <Component class=\"javax.swing.JList\" name=\"pathFormulaeList\">\n                                  <AuxValues>\n                                    <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"pathFormulaeList = new GUISimPathFormulaeList(this);\"/>\n                                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                                  </AuxValues>\n                                </Component>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                        <Container class=\"javax.swing.JPanel\" name=\"informationPanel\">\n                          <Properties>\n                            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[211, 0]\"/>\n                            </Property>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n                              <JTabbedPaneConstraints tabName=\"Path information\">\n                                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Path information\"/>\n                              </JTabbedPaneConstraints>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"innerInformationPanel\">\n                              <Properties>\n                                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                                  </Border>\n                                </Property>\n                                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[211, 0]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"North\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\">\n                                <Property name=\"axis\" type=\"int\" value=\"1\"/>\n                              </Layout>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JPanel\" name=\"topLabels\">\n                                  <Properties>\n                                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                      <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                        <EmptyBorder bottom=\"0\" left=\"5\" right=\"5\" top=\"5\"/>\n                                      </Border>\n                                    </Property>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[201, 0]\"/>\n                                    </Property>\n                                  </Properties>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                                    <Property name=\"columns\" type=\"int\" value=\"3\"/>\n                                    <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                                    <Property name=\"rows\" type=\"int\" value=\"1\"/>\n                                  </Layout>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JLabel\" name=\"modelType\">\n                                      <Properties>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Model Type:\"/>\n                                      </Properties>\n                                      <AuxValues>\n                                        <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"modelType.setFont(this.getFont().deriveFont(Font.BOLD));\"/>\n                                      </AuxValues>\n                                    </Component>\n                                    <Component class=\"javax.swing.JLabel\" name=\"definedConstants\">\n                                      <Properties>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Defined Constants:\"/>\n                                      </Properties>\n                                      <AuxValues>\n                                        <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"definedConstants.setFont(this.getFont().deriveFont(Font.BOLD));\"/>\n                                      </AuxValues>\n                                    </Component>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"topValues\">\n                                  <Properties>\n                                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                      <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                        <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"0\"/>\n                                      </Border>\n                                    </Property>\n                                  </Properties>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                                    <Property name=\"columns\" type=\"int\" value=\"3\"/>\n                                    <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                                    <Property name=\"rows\" type=\"int\" value=\"1\"/>\n                                  </Layout>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JLabel\" name=\"modelTypeLabel\">\n                                      <Properties>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Unknown\"/>\n                                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                            <EmptyBorder bottom=\"0\" left=\"10\" right=\"0\" top=\"0\"/>\n                                          </Border>\n                                        </Property>\n                                      </Properties>\n                                    </Component>\n                                    <Component class=\"javax.swing.JLabel\" name=\"definedConstantsLabel\">\n                                      <Properties>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Unknown\"/>\n                                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                            <EmptyBorder bottom=\"0\" left=\"10\" right=\"0\" top=\"0\"/>\n                                          </Border>\n                                        </Property>\n                                      </Properties>\n                                    </Component>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"bottomLabels\">\n                                  <Properties>\n                                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                      <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                        <EmptyBorder bottom=\"0\" left=\"5\" right=\"5\" top=\"5\"/>\n                                      </Border>\n                                    </Property>\n                                  </Properties>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                                    <Property name=\"columns\" type=\"int\" value=\"3\"/>\n                                    <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                                    <Property name=\"rows\" type=\"int\" value=\"1\"/>\n                                  </Layout>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JLabel\" name=\"pathLength\">\n                                      <Properties>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Path Length:\"/>\n                                      </Properties>\n                                      <AuxValues>\n                                        <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"pathLength.setFont(this.getFont().deriveFont(Font.BOLD));\"/>\n                                      </AuxValues>\n                                    </Component>\n                                    <Component class=\"javax.swing.JLabel\" name=\"totalTime\">\n                                      <Properties>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Total Time:\"/>\n                                      </Properties>\n                                      <AuxValues>\n                                        <AuxValue name=\"JavaCodeGenerator_InitCodePost\" type=\"java.lang.String\" value=\"totalTime.setFont(this.getFont().deriveFont(Font.BOLD));\"/>\n                                      </AuxValues>\n                                    </Component>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"bottomValues\">\n                                  <Properties>\n                                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                      <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                        <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"0\"/>\n                                      </Border>\n                                    </Property>\n                                  </Properties>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                                    <Property name=\"columns\" type=\"int\" value=\"3\"/>\n                                    <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                                    <Property name=\"rows\" type=\"int\" value=\"1\"/>\n                                  </Layout>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JLabel\" name=\"pathLengthLabel\">\n                                      <Properties>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"0\"/>\n                                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                            <EmptyBorder bottom=\"0\" left=\"10\" right=\"0\" top=\"0\"/>\n                                          </Border>\n                                        </Property>\n                                      </Properties>\n                                    </Component>\n                                    <Component class=\"javax.swing.JLabel\" name=\"totalTimeLabel\">\n                                      <Properties>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"0.0\"/>\n                                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                            <EmptyBorder bottom=\"0\" left=\"10\" right=\"0\" top=\"0\"/>\n                                          </Border>\n                                        </Property>\n                                      </Properties>\n                                    </Component>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                      </SubComponents>\n                    </Container>\n                    <Container class=\"javax.swing.JPanel\" name=\"outerTopLeftPanel\">\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                          <JSplitPaneConstraints position=\"left\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JPanel\" name=\"topLeftPanel\">\n                          <Properties>\n                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                <EmptyBorder bottom=\"0\" left=\"0\" right=\"10\" top=\"0\"/>\n                              </Border>\n                            </Property>\n                            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[0, 0]\"/>\n                            </Property>\n                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[0, 0]\"/>\n                            </Property>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"Center\"/>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"innerTopLeftPanel\">\n                              <Properties>\n                                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[50, 0]\"/>\n                                </Property>\n                                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[302, 50]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"Center\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\">\n                                <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                                <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                              </Layout>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JPanel\" name=\"outerLeftExplorePanel\">\n                                  <Properties>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[129, 0]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Container class=\"javax.swing.JPanel\" name=\"leftExplorePanel\">\n                                      <Properties>\n                                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[129, 0]\"/>\n                                        </Property>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"North\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\">\n                                        <Property name=\"axis\" type=\"int\" value=\"1\"/>\n                                      </Layout>\n                                      <SubComponents>\n                                        <Container class=\"javax.swing.JPanel\" name=\"automaticExplorationPanel\">\n                                          <Properties>\n                                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                              <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                                                <TitledBorder title=\"Automatic exploration\"/>\n                                              </Border>\n                                            </Property>\n                                            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                              <Dimension value=\"[129, 0]\"/>\n                                            </Property>\n                                          </Properties>\n\n                                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                          <SubComponents>\n                                            <Container class=\"javax.swing.JPanel\" name=\"innerAutomaticExplorationPanel\">\n                                              <Properties>\n                                                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                                                  </Border>\n                                                </Property>\n                                                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                  <Dimension value=\"[117, 0]\"/>\n                                                </Property>\n                                              </Properties>\n                                              <Constraints>\n                                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                                  <BorderConstraints direction=\"North\"/>\n                                                </Constraint>\n                                              </Constraints>\n\n                                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                                                <Property name=\"columns\" type=\"int\" value=\"1\"/>\n                                                <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                                                <Property name=\"rows\" type=\"int\" value=\"2\"/>\n                                                <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                                              </Layout>\n                                              <SubComponents>\n                                                <Component class=\"javax.swing.JButton\" name=\"randomExplorationButton\">\n                                                  <Properties>\n                                                    <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.netbeans.modules.form.editors2.IconEditor\">\n                                                      <Image iconType=\"2\" name=\"\"/>\n                                                    </Property>\n                                                    <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"Make a number of random automatic updates\"/>\n                                                    <Property name=\"horizontalAlignment\" type=\"int\" value=\"10\"/>\n                                                    <Property name=\"label\" type=\"java.lang.String\" value=\"Simulate\"/>\n                                                    <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                      <Dimension value=\"[220, 23]\"/>\n                                                    </Property>\n                                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                      <Dimension value=\"[50, 23]\"/>\n                                                    </Property>\n                                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                      <Dimension value=\"[160, 23]\"/>\n                                                    </Property>\n                                                  </Properties>\n                                                  <Events>\n                                                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"randomExplorationButtonActionPerformed\"/>\n                                                  </Events>\n                                                  <AuxValues>\n                                                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                                                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                                                  </AuxValues>\n                                                </Component>\n                                                <Container class=\"javax.swing.JPanel\" name=\"noStepsExplorePanel\">\n                                                  <Properties>\n                                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                      <Dimension value=\"[107, 0]\"/>\n                                                    </Property>\n                                                  </Properties>\n\n                                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n                                                  <SubComponents>\n                                                    <Component class=\"javax.swing.JComboBox\" name=\"typeExploreCombo\">\n                                                      <Properties>\n                                                        <Property name=\"model\" type=\"javax.swing.ComboBoxModel\" editor=\"org.netbeans.modules.form.editors2.ComboBoxModelEditor\">\n                                                          <StringArray count=\"3\">\n                                                            <StringItem index=\"0\" value=\"Num. steps\"/>\n                                                            <StringItem index=\"1\" value=\"Upto state\"/>\n                                                            <StringItem index=\"2\" value=\"Max. time\"/>\n                                                          </StringArray>\n                                                        </Property>\n                                                        <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"\"/>\n                                                      </Properties>\n                                                      <Constraints>\n                                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                                                          <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"5\" anchor=\"10\" weightX=\"2.0\" weightY=\"0.0\"/>\n                                                        </Constraint>\n                                                      </Constraints>\n                                                    </Component>\n                                                    <Component class=\"javax.swing.JTextField\" name=\"inputExploreField\">\n                                                      <Properties>\n                                                        <Property name=\"text\" type=\"java.lang.String\" value=\"1\"/>\n                                                        <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"\"/>\n                                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                          <Dimension value=\"[60, 19]\"/>\n                                                        </Property>\n                                                      </Properties>\n                                                      <Events>\n                                                        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"inputExploreFieldActionPerformed\"/>\n                                                      </Events>\n                                                      <AuxValues>\n                                                        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                                                        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                                                      </AuxValues>\n                                                      <Constraints>\n                                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                                                          <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.25\" weightY=\"0.0\"/>\n                                                        </Constraint>\n                                                      </Constraints>\n                                                    </Component>\n                                                  </SubComponents>\n                                                </Container>\n                                              </SubComponents>\n                                            </Container>\n                                          </SubComponents>\n                                        </Container>\n                                        <Container class=\"javax.swing.JPanel\" name=\"backtrackPanel\">\n                                          <Properties>\n                                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                              <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                                                <TitledBorder title=\"Backtracking\"/>\n                                              </Border>\n                                            </Property>\n                                            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                              <Dimension value=\"[129, 0]\"/>\n                                            </Property>\n                                          </Properties>\n\n                                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                          <SubComponents>\n                                            <Container class=\"javax.swing.JPanel\" name=\"innerBacktrackPanel\">\n                                              <Properties>\n                                                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                                                  </Border>\n                                                </Property>\n                                                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                  <Dimension value=\"[117, 0]\"/>\n                                                </Property>\n                                              </Properties>\n                                              <Constraints>\n                                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                                  <BorderConstraints direction=\"Center\"/>\n                                                </Constraint>\n                                              </Constraints>\n\n                                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                                                <Property name=\"columns\" type=\"int\" value=\"1\"/>\n                                                <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                                                <Property name=\"rows\" type=\"int\" value=\"2\"/>\n                                                <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                                              </Layout>\n                                              <SubComponents>\n                                                <Component class=\"javax.swing.JButton\" name=\"backtrackButton\">\n                                                  <Properties>\n                                                    <Property name=\"icon\" type=\"javax.swing.Icon\" editor=\"org.netbeans.modules.form.editors2.IconEditor\">\n                                                      <Image iconType=\"2\" name=\"\"/>\n                                                    </Property>\n                                                    <Property name=\"text\" type=\"java.lang.String\" value=\"Backtrack\"/>\n                                                    <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"Backtrack to a certain state in your path\"/>\n                                                    <Property name=\"horizontalAlignment\" type=\"int\" value=\"10\"/>\n                                                    <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                      <Dimension value=\"[220, 23]\"/>\n                                                    </Property>\n                                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                      <Dimension value=\"[50, 23]\"/>\n                                                    </Property>\n                                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                      <Dimension value=\"[160, 23]\"/>\n                                                    </Property>\n                                                  </Properties>\n                                                  <Events>\n                                                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"backtrackButtonActionPerformed\"/>\n                                                  </Events>\n                                                  <AuxValues>\n                                                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                                                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                                                  </AuxValues>\n                                                </Component>\n                                                <Container class=\"javax.swing.JPanel\" name=\"noStepsBacktrackPanel\">\n                                                  <Properties>\n                                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                      <Dimension value=\"[107, 0]\"/>\n                                                    </Property>\n                                                  </Properties>\n\n                                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n                                                  <SubComponents>\n                                                    <Component class=\"javax.swing.JComboBox\" name=\"typeBacktrackCombo\">\n                                                      <Properties>\n                                                        <Property name=\"model\" type=\"javax.swing.ComboBoxModel\" editor=\"org.netbeans.modules.form.editors2.ComboBoxModelEditor\">\n                                                          <StringArray count=\"2\">\n                                                            <StringItem index=\"0\" value=\"Num. steps\"/>\n                                                            <StringItem index=\"1\" value=\"To state\"/>\n                                                          </StringArray>\n                                                        </Property>\n                                                      </Properties>\n                                                      <Constraints>\n                                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                                                          <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"5\" anchor=\"10\" weightX=\"2.0\" weightY=\"0.0\"/>\n                                                        </Constraint>\n                                                      </Constraints>\n                                                    </Component>\n                                                    <Component class=\"javax.swing.JTextField\" name=\"inputBacktrackField\">\n                                                      <Properties>\n                                                        <Property name=\"text\" type=\"java.lang.String\" value=\"1\"/>\n                                                        <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"\"/>\n                                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                                          <Dimension value=\"[60, 19]\"/>\n                                                        </Property>\n                                                      </Properties>\n                                                      <Events>\n                                                        <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"inputBacktrackFieldActionPerformed\"/>\n                                                      </Events>\n                                                      <AuxValues>\n                                                        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                                                        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                                                      </AuxValues>\n                                                      <Constraints>\n                                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                                                          <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.25\" weightY=\"0.0\"/>\n                                                        </Constraint>\n                                                      </Constraints>\n                                                    </Component>\n                                                  </SubComponents>\n                                                </Container>\n                                              </SubComponents>\n                                            </Container>\n                                          </SubComponents>\n                                        </Container>\n                                      </SubComponents>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"manualUpdatesPanel\">\n                                  <Properties>\n                                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                                        <TitledBorder title=\"Manual exploration\"/>\n                                      </Border>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[60, 60]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Container class=\"javax.swing.JPanel\" name=\"innerManualUpdatesPanel\">\n                                      <Properties>\n                                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                                          </Border>\n                                        </Property>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                      <SubComponents>\n                                        <Container class=\"javax.swing.JScrollPane\" name=\"manualUpdateTableScrollPane\">\n                                          <Properties>\n                                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                                <EmptyBorder bottom=\"0\" left=\"0\" right=\"0\" top=\"0\"/>\n                                              </Border>\n                                            </Property>\n                                          </Properties>\n                                          <Constraints>\n                                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                              <BorderConstraints direction=\"Center\"/>\n                                            </Constraint>\n                                          </Constraints>\n\n                                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                          <SubComponents>\n                                            <Component class=\"javax.swing.JTable\" name=\"currentUpdatesTable\">\n                                              <Properties>\n                                                <Property name=\"model\" type=\"javax.swing.table.TableModel\" editor=\"org.netbeans.modules.form.editors2.TableModelEditor\">\n                                                  <Table columnCount=\"4\" rowCount=\"4\">\n                                                    <Column editable=\"true\" title=\"Title 1\" type=\"java.lang.Object\"/>\n                                                    <Column editable=\"true\" title=\"Title 2\" type=\"java.lang.Object\"/>\n                                                    <Column editable=\"true\" title=\"Title 3\" type=\"java.lang.Object\"/>\n                                                    <Column editable=\"true\" title=\"Title 4\" type=\"java.lang.Object\"/>\n                                                  </Table>\n                                                </Property>\n                                                <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"Double click on an update to manually execute the update\"/>\n                                              </Properties>\n                                              <AuxValues>\n                                                <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"currentUpdatesTable = new GUISimulatorUpdatesTable(updateTableModel, this);\"/>\n                                                <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                                                <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                                              </AuxValues>\n                                            </Component>\n                                          </SubComponents>\n                                        </Container>\n                                        <Container class=\"javax.swing.JPanel\" name=\"autoTimeCheckPanel\">\n                                          <Properties>\n                                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                                <EmptyBorder bottom=\"0\" left=\"0\" right=\"0\" top=\"5\"/>\n                                              </Border>\n                                            </Property>\n                                          </Properties>\n                                          <Constraints>\n                                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                              <BorderConstraints direction=\"South\"/>\n                                            </Constraint>\n                                          </Constraints>\n\n                                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                          <SubComponents>\n                                            <Component class=\"javax.swing.JCheckBox\" name=\"autoTimeCheck\">\n                                              <Properties>\n                                                <Property name=\"text\" type=\"java.lang.String\" value=\"Generate time automatically\"/>\n                                                <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"When not selected, you will be prompted to manually enter the time spent in states\"/>\n                                                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                                                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                                    <EmptyBorder bottom=\"0\" left=\"0\" right=\"0\" top=\"0\"/>\n                                                  </Border>\n                                                </Property>\n                                                <Property name=\"horizontalAlignment\" type=\"int\" value=\"4\"/>\n                                                <Property name=\"margin\" type=\"java.awt.Insets\" editor=\"org.netbeans.beaninfo.editors.InsetsEditor\">\n                                                  <Insets value=\"[0, 0, 0, 0]\"/>\n                                                </Property>\n                                              </Properties>\n                                              <Constraints>\n                                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                                  <BorderConstraints direction=\"East\"/>\n                                                </Constraint>\n                                              </Constraints>\n                                            </Component>\n                                          </SubComponents>\n                                        </Container>\n                                      </SubComponents>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"outerBottomPanel\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                  <JSplitPaneConstraints position=\"bottom\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"bottomPanel\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Path\"/>\n                      </Border>\n                    </Property>\n                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[42, 0]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"Center\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JScrollPane\" name=\"tableScroll\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JPanel\" name=\"pathTablePlaceHolder\">\n                          <Properties>\n                            <Property name=\"toolTipText\" type=\"java.lang.String\" value=\"Double-click or right-click to create a new path\"/>\n                          </Properties>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                        </Container>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUISimulator.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport java.awt.Font;\nimport java.awt.Rectangle;\nimport java.awt.Toolkit;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.ComponentAdapter;\nimport java.awt.event.ComponentEvent;\nimport java.awt.event.InputEvent;\nimport java.awt.event.ItemEvent;\nimport java.awt.event.ItemListener;\nimport java.awt.event.KeyAdapter;\nimport java.awt.event.KeyEvent;\nimport java.awt.event.MouseAdapter;\nimport java.awt.event.MouseEvent;\nimport java.awt.event.MouseListener;\nimport java.util.ArrayList;\nimport java.util.List;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.Action;\nimport javax.swing.DefaultComboBoxModel;\nimport javax.swing.JComboBox;\nimport javax.swing.JFileChooser;\nimport javax.swing.JList;\nimport javax.swing.JMenu;\nimport javax.swing.JPopupMenu;\nimport javax.swing.JScrollPane;\nimport javax.swing.JTable;\nimport javax.swing.KeyStroke;\nimport javax.swing.ListSelectionModel;\nimport javax.swing.event.ListSelectionEvent;\nimport javax.swing.event.ListSelectionListener;\nimport javax.swing.filechooser.FileFilter;\nimport javax.swing.filechooser.FileNameExtensionFilter;\nimport javax.swing.table.AbstractTableModel;\nimport javax.swing.table.TableColumn;\nimport javax.swing.table.TableColumnModel;\n\nimport parser.State;\nimport parser.Values;\nimport parser.ast.LabelList;\nimport parser.ast.ModulesFile;\nimport parser.ast.PropertiesFile;\nimport prism.PrismException;\nimport prism.PrismLangException;\nimport prism.PrismSettings;\nimport prism.PrismSettingsListener;\nimport prism.PrismUtils;\nimport prism.UndefinedConstants;\nimport simulator.PathFullInfo;\nimport simulator.SimulatorEngine;\nimport userinterface.GUIConstantsPicker;\nimport userinterface.GUIPlugin;\nimport userinterface.GUIPrism;\nimport userinterface.graph.Graph;\nimport userinterface.model.GUIModelEvent;\nimport userinterface.model.GUIMultiModel;\nimport userinterface.properties.GUIMultiProperties;\nimport userinterface.properties.GUIPropertiesEvent;\nimport userinterface.properties.GUIPropertiesList;\nimport userinterface.properties.GUIProperty;\nimport userinterface.util.GUIComputationEvent;\nimport userinterface.util.GUIEvent;\nimport userinterface.util.GUIExitEvent;\n\n@SuppressWarnings(\"serial\")\npublic class GUISimulator extends GUIPlugin implements MouseListener, ListSelectionListener, PrismSettingsListener\n{\n\tprivate static final long serialVersionUID = 1L;\n\n\t// Links to other parts of the GUI\n\tprivate GUIMultiProperties guiProp;\n\tprivate GUIMultiModel guiMultiModel;\n\n\t/** Underlying simulator */\n\tprivate SimulatorEngine engine;\n\n\t// GUI components\n\tprivate UpdateTableModel updateTableModel;\n\tprivate GUISimulatorPathTableModel pathTableModel;\n\n\t// Menus/actions/etc.\n\tprivate JMenu simulatorMenu;\n\tprivate JPopupMenu pathPopupMenu;\n\tprivate FileFilter textFilter;\n\tprivate Action randomExploration, backtrack, backtrackToHere, removeToHere, newPath, newPathFromState, newPathPlot, newPathPlotFromState, resetPath,\n\t\t\texportPath, plotPath, configureView;\n\n\t//Current State\n\tprivate boolean pathActive;\n\tprivate ModulesFile parsedModel;\n\tprivate boolean newPathAfterReceiveParseNotification, newPathPlotAfterReceiveParseNotification;\n\tprivate boolean chooseInitialState;\n\tprivate boolean stratShow;\n\n\tprivate Values lastPropertyConstants, lastInitialStateValues;\n\tprivate boolean computing;\n\n\t// Config/options\n\tprivate boolean displayStyleFast;\n\tprivate boolean displayPathLoops;\n\tprivate SimulationView view;\n\n\t/**\n\t * Creates a new instance of GUISimulator\n\t */\n\tpublic GUISimulator(GUIPrism gui)\n\t{\n\t\tsuper(gui, true);\n\t\tthis.engine = gui.getPrism().getSimulator();\n\n\t\tview = new SimulationView(this, gui.getPrism().getSettings());\n\t\tpathTableModel = new GUISimulatorPathTableModel(this, view);\n\n\t\tupdateTableModel = new UpdateTableModel();\n\n\t\tinitComponents();\n\t\tinitPopups();\n\n\t\tdoEnables();\n\n\t\thorizontalSplit.setDividerLocation((int) leftExplorePanel.getPreferredSize().getHeight() + 11);\n\n\t\trandomExplorationButton.setIcon(GUIPrism.getIconFromImage(\"smallPlayerFwd.png\"));\n\t\tbacktrackButton.setIcon(GUIPrism.getIconFromImage(\"smallPlayerRew.png\"));\n\n\t\tpathTable.getSelectionModel().addListSelectionListener(this);\n\n\t\tpathTable.addMouseListener(this);\n\t\tpathTable.getTableHeader().addMouseListener(this);\n\t\ttableScroll.addMouseListener(this);\n\n\t\tpathTable.getTableHeader().setReorderingAllowed(true);\n\n\t\tpathTable.addComponentListener(new ComponentAdapter()\n\t\t{\n\t\t\tpublic void componentResized(ComponentEvent e)\n\t\t\t{\n\t\t\t\tsortOutColumnSizes();\n\t\t\t}\n\t\t});\n\n\t\tpathTablePlaceHolder.addMouseListener(this);\n\n\t\tview.refreshToDefaultView(pathActive, parsedModel);\n\n\t\tsetPathActive(false);\n\t\tdoEnables();\n\n\t\t//options = new GUISimulatorOptions(this);\n\n\t\tcurrentUpdatesTable.setModel(updateTableModel);\n\t\tcurrentUpdatesTable.addMouseListener(new MouseAdapter()\n\t\t{\n\t\t\tpublic void mouseClicked(MouseEvent e)\n\t\t\t{\n\t\t\t\tif (e.getClickCount() == 2 && currentUpdatesTable.isEnabled()) {\n\t\t\t\t\ta_manualUpdate();\n\t\t\t\t\tcurrentUpdatesTable.requestFocus();\n\t\t\t\t} else if (e.getClickCount() == 2 && !currentUpdatesTable.isEnabled()) {\n\t\t\t\t\tGUISimulator.this.warning(\"Simulation\",\n\t\t\t\t\t\t\t\"These are updates from earlier in the path.\\nSelect the last state in the path table to continue exploration\");\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\tcurrentUpdatesTable.addKeyListener(new KeyAdapter()\n\t\t{\n\t\t\tpublic void keyPressed(KeyEvent e)\n\t\t\t{\n\t\t\t\tif (e.getKeyCode() == KeyEvent.VK_ENTER && currentUpdatesTable.isEnabled()) {\n\t\t\t\t\ta_manualUpdate();\n\t\t\t\t\tcurrentUpdatesTable.requestFocus();\n\t\t\t\t}\n\n\t\t\t}\n\t\t});\n\n\t\tpathTable.setModel(pathTableModel);\n\n\t\tlastPropertyConstants = null;\n\n\t\tlastInitialStateValues = null;\n\n\t\ttableScroll.setRowHeaderView(((GUISimulatorPathTable) pathTable).getPathLoopIndicator());\n\t\tmanualUpdateTableScrollPane.setRowHeaderView(((GUISimulatorUpdatesTable) currentUpdatesTable).getUpdateRowHeader());\n\n\t\ttableScroll.setHorizontalScrollBarPolicy(JScrollPane.HORIZONTAL_SCROLLBAR_AS_NEEDED);\n\t\tstateLabelList.setSelectionMode(ListSelectionModel.SINGLE_SELECTION);\n\n\t\tstateLabelList.addListSelectionListener(new ListSelectionListener()\n\t\t{\n\t\t\tpublic void valueChanged(ListSelectionEvent e)\n\t\t\t{\n\t\t\t\tpathTable.repaint();\n\t\t\t}\n\t\t});\n\n\t\tmodelTypeLabel.setText(\"Unknown\");\n\t\ttotalTimeLabel.setText(formatDouble(0.0));\n\t\tpathLengthLabel.setText(\"0\");\n\n\t\ttextFilter = new FileNameExtensionFilter(\"Plain text files (*.txt)\", \"txt\");\n\n\t\tdisplayStyleFast = true;\n\t\tdisplayPathLoops = true;\n\n\t\tautoTimeCheck.setSelected(true);\n\t\tcurrentUpdatesTable.requestFocus();\n\n\t\tmanualUpdateTableScrollPane.setToolTipText(\"Double-click or right-click below to create a new path\");\n\t}\n\n\tpublic void setGUIMultiModel(GUIMultiModel guiMultiModel)\n\t{\n\t\tthis.guiMultiModel = guiMultiModel;\n\t}\n\n\tpublic void setGUIProb(GUIMultiProperties guiProp)\n\t{\n\t\tthis.guiProp = guiProp;\n\t}\n\n\tpublic SimulatorEngine getSimulatorEngine()\n\t{\n\t\treturn engine;\n\t}\n\n\tpublic JList getStateLabelList()\n\t{\n\t\treturn stateLabelList;\n\t}\n\n\tpublic String getTotalRewardLabelString()\n\t{\n\t\tint i, n;\n\t\tString s;\n\t\tn = parsedModel.getNumRewardStructs();\n\t\ts = \"<html>\";\n\t\tfor (i = 0; i < n; i++) {\n\t\t\ts += engine.getTotalCumulativeRewardForPath(i);\n\t\t\tif (i < n - 1)\n\t\t\t\ts += \",<br>\";\n\t\t}\n\t\ts += \"</html>\";\n\t\treturn s;\n\t}\n\n\t/**\n\t * Update all fields in the \"Path information\" box.\n\t */\n\tprivate void updatePathInfoAll(UndefinedConstants uCon)\n\t{\n\t\tmodelTypeLabel.setText(parsedModel == null ? \"Unknown\" : parsedModel.getTypeString());\n\t\tString constantsString = uCon == null ? \"\" : uCon.getDefinedConstantsString();\n\t\tdefinedConstantsLabel.setText((constantsString.length() == 0) ? \"None\" : constantsString);\n\t\tpathLengthLabel.setText(pathActive ? \"\" + engine.getPathSize() : \"0\");\n\t\ttotalTimeLabel.setText(pathActive ? formatDouble(engine.getTotalTimeForPath()) : \"0\");\n\t}\n\n\t/**\n\t * Update path length/time fields in the \"Path information\" box.\n\t */\n\tprivate void updatePathInfo()\n\t{\n\t\tpathLengthLabel.setText(pathActive ? \"\" + engine.getPathSize() : \"0\");\n\t\ttotalTimeLabel.setText(pathActive ? formatDouble(engine.getTotalTimeForPath()) : \"0\");\n\t}\n\n\t/**\n\t * Repaint state label and path formulae lists.\n\t */\n\tprivate void repaintLists()\n\t{\n\t\tstateLabelList.repaint();\n\t\tpathFormulaeList.repaint();\n\t}\n\n\t/**\n\t * React to a new model being loaded into the GUI.\n\t */\n\tpublic void a_clearModel()\n\t{\n\t\t// Blank out path table\n\t\ttableScroll.setViewportView(pathTablePlaceHolder);\n\t\t// Update model/path/tables/lists\n\t\tsetPathActive(false);\n\t\tsetParsedModel(null);\n\t\tpathTableModel.restartPathTable();\n\t\tupdateTableModel.restartUpdatesTable();\n\t\t((GUISimLabelList) stateLabelList).clearLabels();\n\t\t((GUISimPathFormulaeList) pathFormulaeList).clearList();\n\t\t// Update display\n\t\trepaintLists();\n\t\tupdatePathInfoAll(null);\n\t\tdoEnables();\n\t}\n\n\tpublic void a_loadModulesFile(ModulesFile mf)\n\t{\n\t\t// Update model/path/tables/lists\n\t\tsetPathActive(false);\n\t\tsetParsedModel(mf);\n\t\tpathTableModel.restartPathTable();\n\t\tupdateTableModel.restartUpdatesTable();\n\t\t((GUISimLabelList) stateLabelList).clearLabels();\n\t\t((GUISimPathFormulaeList) pathFormulaeList).clearList();\n\t\t// Update display\n\t\trepaintLists();\n\t\tupdatePathInfoAll(null);\n\t\tdoEnables();\n\t\t// Populate controls based on model type\n\t\ttypeExploreCombo.removeAllItems();\n\t\ttypeExploreCombo.addItem(\"Steps\");\n\t\ttypeExploreCombo.addItem(\"Up to step\");\n\t\tif (mf != null && mf.getModelType().continuousTime()) {\n\t\t\ttypeExploreCombo.addItem(\"Time\");\n\t\t\ttypeExploreCombo.addItem(\"Up to time\");\n\t\t}\n\t\ttypeBacktrackCombo.setEnabled(false);\n\t\ttypeBacktrackCombo.removeAllItems();\n\t\ttypeBacktrackCombo.addItem(\"Steps\");\n\t\ttypeBacktrackCombo.addItem(\"Back to step\");\n\t\tif (mf != null && mf.getModelType().continuousTime()) {\n\t\t\ttypeBacktrackCombo.addItem(\"Time\");\n\t\t\ttypeBacktrackCombo.addItem(\"Back to time\");\n\t\t}\n\t}\n\n\tpublic void a_clearPath()\n\t{\n\t\t// Update path/tables/lists\n\t\tsetPathActive(false);\n\t\tpathTableModel.restartPathTable();\n\t\tupdateTableModel.restartUpdatesTable();\n\t\t((GUISimLabelList) stateLabelList).clearLabels();\n\t\t((GUISimPathFormulaeList) pathFormulaeList).clearList();\n\t\t// Update display\n\t\trepaintLists();\n\t\tupdatePathInfoAll(null);\n\t\tdoEnables();\n\t}\n\n\tpublic void a_newPath(boolean chooseInitialState)\n\t{\n\t\t// Request a parse\n\t\tnewPathAfterReceiveParseNotification = true;\n\t\tthis.chooseInitialState = chooseInitialState;\n\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.REQUEST_MODEL_PARSE));\n\t}\n\n\tpublic void newPathAfterParse()\n\t{\n\t\tnewPathAfterReceiveParseNotification = false;\n\t\tState initialState;\n\t\ttry {\n\t\t\t// Check model is simulate-able\n\t\t\t// (bail out now else causes problems below)\n\t\t\tgetPrism().checkModelForSimulation();\n\n\t\t\t// get properties constants/labels\n\t\t\tPropertiesFile pf;\n\t\t\ttry {\n\t\t\t\tpf = getPrism().parsePropertiesString(guiProp.getConstantsString().toString() + guiProp.getLabelsString());\n\t\t\t} catch (PrismLangException e) {\n\t\t\t\t// ignore properties if they don't parse\n\t\t\t\tpf = null; //if any problems\n\t\t\t}\n\n\t\t\t// if necessary, get values for undefined constants from user\n\t\t\t// (for now, just get constants needed for properties file labels)\n\t\t\t// TODO: find a way to also get constants for any (path) props we need\n\t\t\t//       (for path formulae display)\n\t\t\tUndefinedConstants uCon = new UndefinedConstants(parsedModel, pf, true);\n\t\t\tif (uCon.getMFNumUndefined() + uCon.getPFNumUndefined() > 0) {\n\t\t\t\tValues lastModelConstants = getPrism().getUndefinedModelValues();\n\t\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(getGUI(), uCon, lastModelConstants, lastPropertyConstants);\n\t\t\t\tif (result != GUIConstantsPicker.VALUES_DONE)\n\t\t\t\t\treturn;\n\t\t\t}\n\t\t\t// remember constant values for next time\n\t\t\tlastPropertyConstants = uCon.getPFConstantValues();\n\t\t\t// store constants (currently, compute non-exact for simulation)\n\t\t\tgetPrism().setPRISMModelConstants(uCon.getMFConstantValues(), false);\n\t\t\tpf.setSomeUndefinedConstants(lastPropertyConstants, false);\n\n\t\t\t// check here for possibility of multiple initial states\n\t\t\t// (not supported yet) to avoid problems below\n\t\t\tif (parsedModel.getInitialStates() != null) {\n\t\t\t\tthrow new PrismException(\"The simulator does not yet handle models with multiple initial states\");\n\t\t\t}\n\n\t\t\t// Load model into the simulator\n\t\t\tgetPrism().loadModelIntoSimulator();\n\t\t\tgetPrism().loadStrategyIntoSimulator();\n\t\t\t\n\t\t\t// do we need to ask for an initial state for simulation?\n\t\t\t// no: just use default/random\n\t\t\tif (!chooseInitialState) {\n\t\t\t\tinitialState = null;\n\t\t\t}\n\t\t\t// yes: user chooses \n\t\t\telse {\n\t\t\t\tinitialState = a_chooseInitialState();\n\t\t\t\t// if user clicked cancel from dialog, bail out\n\t\t\t\tif (initialState == null) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Insert path table\n\t\t\ttableScroll.setViewportView(pathTable);\n\n\t\t\tdisplayPathLoops = true;\n\t\t\t\n\t\t\t// Create a new path in the simulator and add labels/properties\n\t\t\tengine.createNewPath();\n\t\t\tsetPathActive(true);\n\t\t\trepopulateFormulae(pf);\n\t\t\tengine.initialisePath(initialState);\n\t\t\t// Query transitions, just to trigger any errors\n\t\t\tengine.getNumTransitions();\n\t\t\t// Update model/path/tables/lists\n\t\t\tif (engine.hasStrategyInfo()) {\n\t\t\t\tstratCombo.setSelectedItem(\"Enforce\");\n\t\t\t}\n\t\t\tpathTableModel.setPath(engine.getPathFull());\n\t\t\tpathTableModel.restartPathTable();\n\t\t\tpathTable.getSelectionModel().setSelectionInterval(0, 0);\n\t\t\tupdateTableModel.restartUpdatesTable();\n\t\t\t// Update display\n\t\t\trepaintLists();\n\t\t\tupdatePathInfoAll(uCon);\n\t\t\tdoEnables();\n\n\t\t\t// store initial state for next time\n\t\t\t// (but as Values in case variables change)\n\t\t\tlastInitialStateValues = new Values(initialState, engine.getModel());\n\n\t\t\tif (getPrism().getSettings().getBoolean(PrismSettings.SIMULATOR_NEW_PATH_ASK_VIEW)) {\n\t\t\t\tnew GUIViewDialog(getGUI(), pathTableModel.getView(), pathTableModel);\n\t\t\t}\n\n\t\t} catch (PrismException e) {\n\t\t\tsetPathActive(false);\n\t\t\tthis.error(e.getMessage());\n\t\t\tif (e instanceof PrismLangException) {\n\t\t\t\tguiMultiModel.getHandler().modelParseFailed((PrismLangException) e, false);\n\t\t\t\tguiMultiModel.tabToFront();\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic State a_chooseInitialState() throws PrismLangException\n\t{\n\t\treturn GUIInitialStatePicker.defineInitalValuesWithDialog(getGUI(), engine, lastInitialStateValues);\n\t}\n\n\t/** Explore a number of steps. */\n\tpublic void a_autoStep(int noSteps)\n\t{\n\t\t// Check if we should stop because the path is looping\n\t\tif (stopBecausePathLooping()) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Execute the steps, first updating the available transitions if needed\n\t\ttry {\n\t\t\tsetComputing(true);\n\t\t\tif (isOldUpdate()) {\n\t\t\t\tengine.computeTransitionsForCurrentState();\n\t\t\t}\n\t\t\tengine.automaticTransitions(noSteps, displayPathLoops);\n\t\t} catch (PrismException e) {\n\t\t\t// If there is an error, report it, update displays and stop\n\t\t\t// (otherwise error might get reported for a second time below)\n\t\t\tupdatePathDisplay(true);\n\t\t\tupdateTableModel.updateUpdatesTable();\n\t\t\treportErrorDuringSimulation(e);\n\t\t\treturn;\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\n\t\t// Update the displays and report any errors in the new current state\n\t\tupdatePathDisplay(true);\n\t\tupdateTableModel.updateUpdatesTable();\n\t\tcheckForErrorsInTransitions();\n\t}\n\n\t/** Explore an amount of time. */\n\tpublic void a_autoStep(double time)\n\t{\n\t\t// Check if we should stop because the path is looping\n\t\tif (stopBecausePathLooping()) {\n\t\t\treturn;\n\t\t}\n\n\t\t// Execute the steps, first updating the available transitions if needed\n\t\ttry {\n\t\t\tsetComputing(true);\n\t\t\tif (isOldUpdate()) {\n\t\t\t\tengine.computeTransitionsForCurrentState();\n\t\t\t}\n\t\t\tengine.automaticTransitions(time, displayPathLoops);\n\t\t} catch (PrismException e) {\n\t\t\t// If there is an error, report it, update displays and stop\n\t\t\t// (otherwise error might get reported for a second time below)\n\t\t\tupdatePathDisplay(true);\n\t\t\tupdateTableModel.updateUpdatesTable();\n\t\t\treportErrorDuringSimulation(e);\n\t\t\treturn;\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\n\t\t// Update the displays and report any errors in the new current state\n\t\tupdatePathDisplay(true);\n\t\tupdateTableModel.updateUpdatesTable();\n\t\tcheckForErrorsInTransitions();\n\t}\n\n\t/** Backtrack to a certain time. */\n\tpublic void a_backTrack(double time)\n\t{\n\t\t// Do the backtracking\n\t\ttry {\n\t\t\tsetComputing(true);\n\t\t\tengine.backtrackTo(time);\n\t\t} catch (PrismException e) {\n\t\t\t// If there is an error, report it (and then carry on updating display etc.)\n\t\t\treportErrorDuringSimulation(e);\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\t\t// Update the displays\n\t\tupdatePathDisplay(false);\n\t\tupdateTableModel.updateUpdatesTable();\n\t}\n\n\t/** Backtrack to a certain step. */\n\tpublic void a_backTrack(int step)\n\t{\n\t\t// Do the backtracking\n\t\ttry {\n\t\t\tsetComputing(true);\n\t\t\tengine.backtrackTo(step);\n\t\t} catch (PrismException e) {\n\t\t\t// If there is an error, report it (and then carry on updating display etc.)\n\t\t\treportErrorDuringSimulation(e);\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\t\t// Update the displays\n\t\tupdatePathDisplay(false);\n\t\tupdateTableModel.updateUpdatesTable();\n\t}\n\n\t/** Backtrack to the start of the path. */\n\tpublic void a_restartPath()\n\t{\n\t\t// Do the restart\n\t\ttry {\n\t\t\tsetComputing(true);\n\t\t\tengine.backtrackTo(0);\n\t\t} catch (PrismException e) {\n\t\t\t// If there is an error, report it (and then carry on updating display etc.)\n\t\t\treportErrorDuringSimulation(e);\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\t\t// Update the displays\n\t\tupdatePathDisplay(false);\n\t\tupdateTableModel.updateUpdatesTable();\n\t}\n\n\t/** Remove the prefix of the current path up to the given path step. */\n\tpublic void a_removePreceding(int step)\n\t{\n\t\t// Do the prefix removal\n\t\ttry {\n\t\t\tsetComputing(true);\n\t\t\tengine.removePrecedingStates(step);\n\t\t} catch (PrismException e) {\n\t\t\t// If there is an error, report it (and then carry on updating display etc.)\n\t\t\treportErrorDuringSimulation(e);\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\t\t// Update the displays\n\t\tupdatePathDisplay(false);\n\t\tupdateTableModel.updateUpdatesTable();\n\t}\n\n\t/** Execute a user specified transition. */\n\tpublic void a_manualUpdate()\n\t{\n\t\t// Check that we need to continue\n\t\tif (currentUpdatesTable.getSelectedRow() == -1) {\n\t\t\treportErrorDuringSimulation(new PrismException(\"No current update is selected\"));\n\t\t\treturn;\n\t\t}\n\t\tif (engine.hasStrategyInfo() && engine.isStrategyEnforced()) {\n\t\t\ttry {\n\t\t\t\tif (!engine.isTransitionEnabledByStrategy(currentUpdatesTable.getSelectedRow())) {\n\t\t\t\t\tif (questionYesNo(\"This update is not selected by the current strategy. Execute it anyway?\") != 0) {\n\t\t\t\t\t\treturn;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t} catch (PrismException e) {\n\t\t\t\treportErrorDuringSimulation(e);\n\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\t\tif (stopBecausePathLooping()) {\n\t\t\treturn;\n\t\t}\n\t\t\n\t\t// Get time\n\t\tdouble time = -1;\n\t\tif (parsedModel.getModelType().continuousTime()) {\n\t\t\tif (!autoTimeCheck.isSelected()) {\n\t\t\t\ttime = GUITimeDialog.askTime(this.getGUI(), this);\n\t\t\t\tif (time < 0.0d) // dialog cancelled\n\t\t\t\t\treturn;\n\t\t\t}\n\t\t}\n\n\t\t// Execute the transition\n\t\ttry {\n\t\t\tsetComputing(true);\n\t\t\tif (parsedModel.getModelType().continuousTime() && time != -1) {\n\t\t\t\tengine.manualTransition(currentUpdatesTable.getSelectedRow(), time);\n\t\t\t} else {\n\t\t\t\tengine.manualTransition(currentUpdatesTable.getSelectedRow());\n\t\t\t}\n\t\t} catch (PrismException e) {\n\t\t\t// If there is an error, report it (and then carry on updating display etc.)\n\t\t\treportErrorDuringSimulation(e);\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\n\t\t// Update the displays and report any errors in the new current state\n\t\tupdatePathDisplay(true);\n\t\tupdateTableModel.updateUpdatesTable();\n\t\tcheckForErrorsInTransitions();\n\t}\n\n\tpublic void a_loadPath(PathFullInfo pathNew)\n\t{\n\t\ttry {\n\t\t\t// get properties constants/labels\n\t\t\tPropertiesFile pf;\n\t\t\ttry {\n\t\t\t\tpf = getPrism().parsePropertiesString(guiProp.getConstantsString().toString() + guiProp.getLabelsString());\n\t\t\t} catch (PrismLangException e) {\n\t\t\t\t// ignore properties if they don't parse\n\t\t\t\tpf = null; //if any problems\n\t\t\t}\n\t\t\t// Insert path table\n\t\t\ttableScroll.setViewportView(pathTable);\n\n\t\t\tdisplayPathLoops = true;\n\n\t\t\t// Load new path into the simulator\n\t\t\tgetPrism().loadModelIntoSimulator();\n\t\t\tengine.createNewPath();\n\t\t\tsetPathActive(true);\n\t\t\trepopulateFormulae(pf);\n\t\t\tengine.loadPath(pathNew);\n\t\t\t// Update model/path/tables/lists\n\t\t\tpathTableModel.setPath(engine.getPathFull());\n\t\t\tpathTableModel.restartPathTable();\n\t\t\tint last = pathTable.getRowCount() - 1;\n\t\t\tpathTable.getSelectionModel().setSelectionInterval(last, last);\n\t\t\tupdateTableModel.restartUpdatesTable();\n\t\t\t// Update display\n\t\t\trepaintLists();\n\t\t\tupdatePathInfoAll(null);\n\t\t\tdoEnables();\n\n\t\t} catch (PrismException e) {\n\t\t\tthis.error(e.getMessage());\n\t\t\tsetComputing(false);\n\t\t}\n\t}\n\n\tpublic void a_exportPath()\n\t{\n\t\ttry {\n\t\t\tboolean exportRewards = false;\n\t\t\tif (parsedModel != null && parsedModel.getNumRewardStructs() > 0) {\n\t\t\t\texportRewards = (question(\"Export the path with or without reward information?\", new String[]{\"With rewards\", \"Without rewards\"}) == 0);\n\t\t\t}\n\n\t\t\tif (showSaveFileDialog(textFilter) != JFileChooser.APPROVE_OPTION)\n\t\t\t\treturn;\n\n\t\t\tsetComputing(true);\n\t\t\tengine.exportPath(getChooserFile(), exportRewards);\n\t\t} catch (PrismException e) {\n\t\t\terror(e.getMessage());\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\t}\n\n\tpublic void a_plotPath()\n\t{\n\t\ttry {\n\t\t\tsetComputing(true);\n\t\t\tguiProp.tabToFront();\n\t\t\tGraph graphModel = new Graph();\n\t\t\tguiProp.getGraphHandler().addGraph(graphModel);\n\t\t\tengine.plotPath(graphModel);\n\t\t} catch (PrismException e) {\n\t\t\terror(e.getMessage());\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\t}\n\n\tpublic void a_newPathPlot(boolean chooseInitialState)\n\t{\n\t\t// Request a parse\n\t\tnewPathPlotAfterReceiveParseNotification = true;\n\t\tthis.chooseInitialState = chooseInitialState;\n\t\tnotifyEventListeners(new GUIPropertiesEvent(GUIPropertiesEvent.REQUEST_MODEL_PARSE));\n\t}\n\n\tpublic void newPathPlotAfterParse()\n\t{\n\t\tnewPathPlotAfterReceiveParseNotification = false;\n\t\tState initialState;\n\t\ttry {\n\t\t\t// Check model is simulate-able\n\t\t\t// (bail out now else causes problems below)\n\t\t\tgetPrism().checkModelForSimulation();\n\n\t\t\t// if necessary, get values for undefined constants from user\n\t\t\tUndefinedConstants uCon = new UndefinedConstants(parsedModel, null);\n\t\t\tif (uCon.getMFNumUndefined() > 0) {\n\t\t\t\tValues lastModelConstants = getPrism().getUndefinedModelValues();\n\t\t\t\tint result = GUIConstantsPicker.defineConstantsWithDialog(getGUI(), uCon, lastModelConstants, lastPropertyConstants);\n\t\t\t\tif (result != GUIConstantsPicker.VALUES_DONE)\n\t\t\t\t\treturn;\n\t\t\t}\n\t\t\t// store constants (currently, compute non-exact for simulation)\n\t\t\tgetPrism().setPRISMModelConstants(uCon.getMFConstantValues(), false);\n\n\t\t\t// Load model into the simulator\n\t\t\tgetPrism().loadModelIntoSimulator();\n\t\t\tgetPrism().loadStrategyIntoSimulator();\n\t\t\t\n\t\t\t// do we need to ask for an initial state for simulation?\n\t\t\t// no: just use default/random\n\t\t\tif (!chooseInitialState) {\n\t\t\t\tinitialState = null;\n\t\t\t}\n\t\t\t// yes: user chooses \n\t\t\telse {\n\t\t\t\tinitialState = a_chooseInitialState();\n\t\t\t\t// if user clicked cancel from dialog, bail out\n\t\t\t\tif (initialState == null) {\n\t\t\t\t\treturn;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Get path details from dialog\n\t\t\tGUIPathPlotDialog pathPlotDialog = GUIPathPlotDialog.showDialog(getGUI(), this, parsedModel);\n\t\t\tif (pathPlotDialog == null)\n\t\t\t\treturn;\n\t\t\tString simPathDetails = pathPlotDialog.getSimPathString();\n\t\t\tif (simPathDetails == null)\n\t\t\t\treturn;\n\t\t\tlong maxPathLength = pathPlotDialog.getMaxPathLength();\n\n\t\t\t// Create a new path in the simulator and plot it\n\t\t\ta_clearPath();\n\t\t\tsetComputing(true);\n\t\t\tguiProp.tabToFront();\n\t\t\tGraph graphModel = new Graph();\n\t\t\tguiProp.getGraphHandler().addGraph(graphModel);\n\t\t\tgetPrism().getMainLog().resetNumberOfWarnings();\n\t\t\tnew SimPathPlotThread(this, engine, initialState, simPathDetails, maxPathLength, graphModel).start();\n\n\t\t\t// store initial state for next time\n\t\t\t// (but as Values in case variables change)\n\t\t\tlastInitialStateValues = new Values(initialState, engine.getModel());\n\n\t\t} catch (PrismException e) {\n\t\t\tthis.error(e.getMessage());\n\t\t\tif (e instanceof PrismLangException) {\n\t\t\t\tguiMultiModel.getHandler().modelParseFailed((PrismLangException) e, false);\n\t\t\t\tguiMultiModel.tabToFront();\n\t\t\t}\n\t\t} finally {\n\t\t\tsetComputing(false);\n\t\t}\n\t}\n\n\tpublic void a_configureView()\n\t{\n\t\tnew GUIViewDialog(getGUI(), pathTableModel.getView(), pathTableModel);\n\t}\n\n\t/**\n\t * Should we stop simulating because the path is showing a loop?\n\t * Also check with the user if they want to continue regardless.\n\t */\n\tprivate boolean stopBecausePathLooping()\n\t{\n\t\tif (displayPathLoops && pathTableModel.isPathLooping()) {\n\t\t\tif (questionYesNo(\n\t\t\t\t\t\"The current path contains a deterministic loop. \\nDo you wish to disable detection of such loops and extend the path anyway?\") == 0) {\n\t\t\t\tdisplayPathLoops = false;\n\t\t\t\tpathTable.repaint();\n\t\t\t\treturn false;\n\t\t\t} else {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\t\n\t/**\n\t * Update the path display after an update\n\t */\n\tprivate void updatePathDisplay(boolean scrollToVisible)\n\t{\n\t\t// Update the main path table\n\t\tpathTableModel.updatePathTable();\n\t\tif (scrollToVisible) {\n\t\t\tint height = (int) pathTable.getPreferredSize().getHeight();\n\t\t\tint width = (int) pathTable.getPreferredSize().getWidth();\n\t\t\tpathTable.scrollRectToVisible(new Rectangle(0, height - 10, width, height));\n\t\t}\n\t\t// Update other path info displays\n\t\trepaintLists();\n\t\tupdatePathInfo();\n\t}\n\t\n\t/**\n\t * Check for any problems with the transitions in the current state.\n\t * and report the error to the user if there is one.\n\t */\n\tprivate void checkForErrorsInTransitions()\n\t{\n\t\ttry {\n\t\t\t// Query transitions, as a way to trigger any errors\n\t\t\tengine.getNumTransitions();\n\t\t} catch (PrismException e) {\n\t\t\treportErrorDuringSimulation(e);\n\t\t}\n\t}\n\t\n\t/**\n\t * Report an error if it occurs during simulation.\n\t */\n\tprivate void reportErrorDuringSimulation(PrismException e)\n\t{\n\t\t// Error popup\n\t\tthis.error(e.getMessage());\n\t\t// For model errors, also show in model editor\n\t\tif (e instanceof PrismLangException && ((PrismLangException) e).getASTElement().hasPosition()) {\n\t\t\tguiMultiModel.getHandler().modelParseFailed((PrismLangException) e, false);\n\t\t\tguiMultiModel.tabToFront();\n\t\t}\n\t}\n\t\n\t/**\n\t * Re-populate lists of labels and path formulas.\n\t * Labels are taken from current model and passed in properties file. \n\t * Path formulas are taken from the passed in properties file. \n\t */\n\tprivate void repopulateFormulae(PropertiesFile propertiesFile)\n\t{\n\t\t// Labels\n\t\tGUISimLabelList theStateLabelList = (GUISimLabelList) stateLabelList;\n\t\ttheStateLabelList.clearLabels();\n\t\tif (pathActive) {\n\t\t\t// Add the default labels: \"init\" and \"deadlock\"\n\t\t\ttheStateLabelList.addDeadlockAndInit();\n\t\t\tif (parsedModel != null) {\n\t\t\t\t// Add labels from model\n\t\t\t\tLabelList labelList1 = parsedModel.getLabelList();\n\t\t\t\tfor (int i = 0; i < labelList1.size(); i++) {\n\t\t\t\t\ttheStateLabelList.addModelLabel(labelList1.getLabelName(i), labelList1.getLabel(i));\n\t\t\t\t}\n\t\t\t\t// Add labels from properties file\n\t\t\t\tLabelList labelList2 = propertiesFile.getLabelList();\n\t\t\t\tfor (int i = 0; i < labelList2.size(); i++) {\n\t\t\t\t\ttheStateLabelList.addPropertyLabel(labelList2.getLabelName(i), labelList2.getLabel(i), propertiesFile);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\t// Path formulae\n\t\t// TODO: Currently, path formulae containing undefined property constants\n\t\t// are ignored. It would be better if the user is queried\n\t\t// for any necessary undefined constants, too.\n\t\tGUISimPathFormulaeList thePathFormulaeList = (GUISimPathFormulaeList) pathFormulaeList;\n\t\tthePathFormulaeList.clearList();\n\t\tif (pathActive) {\n\t\t\t// Go through the property list from the Properties tab of GUI\n\t\t\tGUIPropertiesList gpl = guiProp.getPropList();\n\t\t\tfor (int i = 0; i < gpl.getNumProperties(); i++) {\n\t\t\t\tGUIProperty gp = gpl.getProperty(i);\n\n\t\t\t\t// obtain constants in property\n\t\t\t\tList<String> propertyConstants = gp.getProperty().getAllConstants();\n\t\t\t\tboolean allConstantsDefined = true;\n\t\t\t\tfor (String propertyConstant : propertyConstants) {\n\t\t\t\t\tif (!parsedModel.isDefinedConstant(propertyConstant) &&\n\t\t\t\t\t    !propertiesFile.isDefinedConstant(propertyConstant)) {\n\t\t\t\t\t\t// we found one that has not been defined in the model\n\t\t\t\t\t\t// or the property file\n\t\t\t\t\t\tallConstantsDefined = false;\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t// If the property has no unresolved constants\n\t\t\t\t// and is simulate-able...\n\t\t\t\tif (allConstantsDefined &&\n\t\t\t\t    gp.isValidForSimulation()) {\n\t\t\t\t\t// Add them to the list\n\t\t\t\t\tthePathFormulaeList.addProperty(gp.getProperty(), propertiesFile);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\t//METHODS TO IMPLEMENT THE GUIPLUGIN INTERFACE\n\n\tpublic boolean displaysTab()\n\t{\n\t\treturn true;\n\t}\n\n\tpublic javax.swing.JMenu getMenu()\n\t{\n\t\treturn simulatorMenu;\n\t}\n\n\tpublic String getTabText()\n\t{\n\t\treturn \"Simulator\";\n\t}\n\n\tpublic javax.swing.JToolBar getToolBar()\n\t{\n\t\treturn null;\n\t}\n\n\tpublic String getXMLIDTag()\n\t{\n\t\treturn \"\";\n\t}\n\n\tpublic Object getXMLSaveTree()\n\t{\n\t\treturn null;\n\t}\n\n\tpublic void loadXML(Object c)\n\t{\n\t}\n\n\t@Override\n\tpublic boolean processGUIEvent(GUIEvent e)\n\t{\n\t\tif (e instanceof GUIModelEvent) {\n\t\t\tGUIModelEvent me = (GUIModelEvent) e;\n\t\t\tif (me.getID() == GUIModelEvent.NEW_MODEL) {\n\t\t\t\ta_clearModel();\n\t\t\t} else if (me.getID() == GUIModelEvent.MODEL_PARSED) {\n\t\t\t\ta_loadModulesFile(me.getModulesFile());\n\t\t\t\tdoEnables();\n\t\t\t\tif (newPathAfterReceiveParseNotification)\n\t\t\t\t\tnewPathAfterParse();\n\t\t\t\tif (newPathPlotAfterReceiveParseNotification)\n\t\t\t\t\tnewPathPlotAfterParse();\n\t\t\t} else if (me.getID() == GUIModelEvent.MODEL_PARSE_FAILED) {\n\t\t\t\tnewPathAfterReceiveParseNotification = false;\n\t\t\t\tnewPathPlotAfterReceiveParseNotification = false;\n\t\t\t}\n\n\t\t} else if (e instanceof GUIComputationEvent) {\n\t\t\tif (e.getID() == GUIComputationEvent.COMPUTATION_START) {\n\t\t\t\tsetComputing(true);\n\t\t\t} else if (e.getID() == GUIComputationEvent.COMPUTATION_DONE) {\n\t\t\t\tsetComputing(false);\n\t\t\t} else if (e.getID() == GUIComputationEvent.COMPUTATION_ERROR) {\n\t\t\t\tsetComputing(false);\n\t\t\t}\n\n\t\t} else if (e instanceof GUIPropertiesEvent) {\n\t\t\tif (e.getID() == GUIPropertiesEvent.PROPERTIES_LIST_CHANGED) {\n\t\t\t\t//repopulateFormulae();\n\t\t\t}\n\t\t} else if (e instanceof GUIExitEvent) {\n\t\t\tif (e.getID() == GUIExitEvent.REQUEST_EXIT) {\n\n\t\t\t}\n\t\t}\n\t\treturn false;\n\t}\n\n\tpublic void takeCLArgs(String[] args)\n\t{\n\t}\n\n\tprotected void doEnables()\n\t{\n\t\tnewPath.setEnabled(parsedModel != null && !computing);\n\t\tnewPathFromState.setEnabled(parsedModel != null && !computing);\n\t\tnewPathPlot.setEnabled(parsedModel != null && !computing);\n\t\tnewPathPlotFromState.setEnabled(parsedModel != null && !computing);\n\t\tresetPath.setEnabled(pathActive && !computing);\n\t\texportPath.setEnabled(pathActive && !computing);\n\t\tplotPath.setEnabled(pathActive && !computing);\n\t\trandomExploration.setEnabled(pathActive && !computing);\n\t\tbacktrack.setEnabled(pathActive && !computing);\n\t\tconfigureView.setEnabled(pathActive && !computing);\n\n\t\trandomExplorationButton.setEnabled(pathActive && !computing);\n\t\tbacktrackButton.setEnabled(pathActive && !computing);\n\n\t\tinputExploreField.setEnabled(pathActive);\n\t\tinputBacktrackField.setEnabled(pathActive);\n\n\t\ttypeExploreCombo.setEnabled(pathActive);\n\t\ttypeBacktrackCombo.setEnabled(pathActive);\n\t\t\n\t\tstratCombo.setEnabled(parsedModel != null && !computing && engine.hasStrategyInfo());\n\n\t\tcurrentUpdatesTable.setEnabled(pathActive && !computing);\n\t\tcurrentUpdatesTable.setToolTipText(currentUpdatesTable.isEnabled() ? \"Double click on an update to manually execute it\" : null);\n\t\tautoTimeCheck.setEnabled(pathActive && parsedModel != null && parsedModel.getModelType().continuousTime());\n\n\t\t//resetPathButton.setEnabled(pathActive && !computing);\n\t\t//exportPathButton.setEnabled(pathActive && !computing);\n\t\t//configureViewButton.setEnabled(pathActive && !computing);\n\n\t\t//newPath.setEnabled(parsedModel != null && !computing);\n\t\t//newPathFromState.setEnabled(parsedModel != null && !computing);\n\t\t//newPathButton.setEnabled(parsedModel != null && !computing);\n\n\t\tmodelType.setEnabled(parsedModel != null);\n\t\tmodelTypeLabel.setEnabled(parsedModel != null);\n\n\t\ttotalTime.setEnabled(pathActive && parsedModel != null && parsedModel.getModelType().continuousTime());\n\t\ttotalTimeLabel.setEnabled(pathActive && parsedModel != null && parsedModel.getModelType().continuousTime());\n\n\t\tpathLength.setEnabled(pathActive);\n\t\tpathLengthLabel.setEnabled(pathActive);\n\n\t\tdefinedConstants.setEnabled(pathActive);\n\t\tdefinedConstantsLabel.setEnabled(pathActive);\n\n\t}\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\t// <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n\tprivate void initComponents()\n\t{\n\t\tjava.awt.GridBagConstraints gridBagConstraints;\n\n\t\tbuttonGroup1 = new javax.swing.ButtonGroup();\n\t\tinnerButtonPanel = new javax.swing.JPanel();\n\t\tnewPathButton = new javax.swing.JButton();\n\t\tresetPathButton = new javax.swing.JButton();\n\t\texportPathButton = new javax.swing.JButton();\n\t\tconfigureViewButton = new javax.swing.JButton();\n\t\tpathTable = new javax.swing.JTable();\n\t\tpathTable = new GUISimulatorPathTable(this, pathTableModel, engine);\n\n\t\tjPanel2 = new javax.swing.JPanel();\n\t\tjSplitPane1 = new javax.swing.JSplitPane();\n\t\tjPanel3 = new javax.swing.JPanel();\n\t\tjPanel4 = new javax.swing.JPanel();\n\t\tallPanel = new javax.swing.JPanel();\n\t\thorizontalSplit = new javax.swing.JSplitPane();\n\t\ttopPanel = new javax.swing.JPanel();\n\t\ttopSplit = new javax.swing.JSplitPane();\n\t\ttabbedPane = new javax.swing.JTabbedPane();\n\t\touterStateLabelPanel = new javax.swing.JPanel();\n\t\tstateLabelScrollPane = new javax.swing.JScrollPane();\n\t\tstateLabelList = new javax.swing.JList();\n\t\tstateLabelList = new GUISimLabelList(this);\n\t\touterPathFormulaePanel = new javax.swing.JPanel();\n\t\tpathFormulaeScrollPane = new javax.swing.JScrollPane();\n\t\tpathFormulaeList = new javax.swing.JList();\n\t\tpathFormulaeList = new GUISimPathFormulaeList(this);\n\t\tinformationPanel = new javax.swing.JPanel();\n\t\tinnerInformationPanel = new javax.swing.JPanel();\n\t\ttopLabels = new javax.swing.JPanel();\n\t\tmodelType = new javax.swing.JLabel();\n\t\tdefinedConstants = new javax.swing.JLabel();\n\t\ttopValues = new javax.swing.JPanel();\n\t\tmodelTypeLabel = new javax.swing.JLabel();\n\t\tdefinedConstantsLabel = new javax.swing.JLabel();\n\t\tbottomLabels = new javax.swing.JPanel();\n\t\tpathLength = new javax.swing.JLabel();\n\t\ttotalTime = new javax.swing.JLabel();\n\t\tbottomValues = new javax.swing.JPanel();\n\t\tpathLengthLabel = new javax.swing.JLabel();\n\t\ttotalTimeLabel = new javax.swing.JLabel();\n\t\touterTopLeftPanel = new javax.swing.JPanel();\n\t\ttopLeftPanel = new javax.swing.JPanel();\n\t\tinnerTopLeftPanel = new javax.swing.JPanel();\n\t\touterLeftExplorePanel = new javax.swing.JPanel();\n\t\tleftExplorePanel = new javax.swing.JPanel();\n\t\tautomaticExplorationPanel = new javax.swing.JPanel();\n\t\tinnerAutomaticExplorationPanel = new javax.swing.JPanel();\n\t\trandomExplorationButton = new javax.swing.JButton();\n\t\tnoStepsExplorePanel = new javax.swing.JPanel();\n\t\ttypeExploreCombo = new javax.swing.JComboBox();\n\t\tinputExploreField = new javax.swing.JTextField();\n\t\tbacktrackPanel = new javax.swing.JPanel();\n\t\tinnerBacktrackPanel = new javax.swing.JPanel();\n\t\tbacktrackButton = new javax.swing.JButton();\n\t\tnoStepsBacktrackPanel = new javax.swing.JPanel();\n\t\ttypeBacktrackCombo = new javax.swing.JComboBox();\n\t\tinputBacktrackField = new javax.swing.JTextField();\n\t\tstrategyPanel = new javax.swing.JPanel();\n\t\tinnerStrategyPanel = new javax.swing.JPanel();\n\t\tstratCombo = new JComboBox<>();\n\t\tmanualUpdatesPanel = new javax.swing.JPanel();\n\t\tinnerManualUpdatesPanel = new javax.swing.JPanel();\n\t\tmanualUpdateTableScrollPane = new javax.swing.JScrollPane();\n\t\tcurrentUpdatesTable = new javax.swing.JTable();\n\t\tcurrentUpdatesTable = new GUISimulatorUpdatesTable(updateTableModel, this);\n\t\tautoTimeCheckPanel = new javax.swing.JPanel();\n\t\tautoTimeCheck = new javax.swing.JCheckBox();\n\t\touterBottomPanel = new javax.swing.JPanel();\n\t\tbottomPanel = new javax.swing.JPanel();\n\t\ttableScroll = new javax.swing.JScrollPane();\n\t\tpathTablePlaceHolder = new javax.swing.JPanel();\n\n\t\tinnerButtonPanel.setLayout(new java.awt.GridLayout(2, 2, 10, 10));\n\n\t\tnewPathButton.setIcon(new javax.swing.ImageIcon(\"\"));\n\t\tnewPathButton.setText(\"New path\");\n\t\tnewPathButton.setToolTipText(\"New path\");\n\t\tnewPathButton.setHorizontalAlignment(javax.swing.SwingConstants.LEADING);\n\t\tnewPathButton.setPreferredSize(new java.awt.Dimension(119, 28));\n\t\tnewPathButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tnewPathButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tinnerButtonPanel.add(newPathButton);\n\n\t\tresetPathButton.setIcon(new javax.swing.ImageIcon(\"\"));\n\t\tresetPathButton.setText(\"Reset path\");\n\t\tresetPathButton.setToolTipText(\"Reset path\");\n\t\tresetPathButton.setHorizontalAlignment(javax.swing.SwingConstants.LEADING);\n\t\tresetPathButton.setPreferredSize(new java.awt.Dimension(119, 28));\n\t\tresetPathButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tresetPathButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tinnerButtonPanel.add(resetPathButton);\n\n\t\texportPathButton.setIcon(new javax.swing.ImageIcon(\"\"));\n\t\texportPathButton.setText(\"Export path\");\n\t\texportPathButton.setToolTipText(\"Export path\");\n\t\texportPathButton.setHorizontalAlignment(javax.swing.SwingConstants.LEADING);\n\t\texportPathButton.setPreferredSize(new java.awt.Dimension(119, 28));\n\t\texportPathButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\texportPathButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tinnerButtonPanel.add(exportPathButton);\n\n\t\tconfigureViewButton.setIcon(new javax.swing.ImageIcon(\"\"));\n\t\tconfigureViewButton.setToolTipText(\"Export path\");\n\t\tconfigureViewButton.setActionCommand(\"Configure view\");\n\t\tconfigureViewButton.setHorizontalAlignment(javax.swing.SwingConstants.LEADING);\n\t\tconfigureViewButton.setText(\"Configure view\");\n\t\tconfigureViewButton.setPreferredSize(new java.awt.Dimension(119, 28));\n\t\tconfigureViewButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tconfigureViewButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tinnerButtonPanel.add(configureViewButton);\n\n\t\tpathTable.setModel(new javax.swing.table.DefaultTableModel(new Object[][] { { null, null, null, null }, { null, null, null, null },\n\t\t\t\t{ null, null, null, null }, { null, null, null, null } }, new String[] { \"Title 1\", \"Title 2\", \"Title 3\", \"Title 4\" }));\n\t\tjSplitPane1.setLeftComponent(jPanel3);\n\n\t\tjSplitPane1.setRightComponent(jPanel4);\n\n\t\tjPanel2.add(jSplitPane1);\n\n\t\tsetLayout(new java.awt.BorderLayout());\n\n\t\tallPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tallPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\thorizontalSplit.setDividerLocation(211);\n\t\thorizontalSplit.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);\n\t\thorizontalSplit.setMinimumSize(new java.awt.Dimension(0, 0));\n\t\thorizontalSplit.setOneTouchExpandable(true);\n\t\ttopPanel.setLayout(new java.awt.BorderLayout());\n\n\t\ttopPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\ttopPanel.setMinimumSize(new java.awt.Dimension(300, 10));\n\t\ttopPanel.setPreferredSize(new java.awt.Dimension(302, 591));\n\t\ttopSplit.setBorder(null);\n\t\ttopSplit.setDividerLocation(600);\n\t\ttopSplit.setResizeWeight(0.75);\n\t\ttopSplit.setContinuousLayout(true);\n\t\ttopSplit.setDoubleBuffered(true);\n\t\ttopSplit.setMinimumSize(new java.awt.Dimension(0, 0));\n\t\ttopSplit.setOneTouchExpandable(true);\n\t\ttopSplit.setPreferredSize(new java.awt.Dimension(0, 0));\n\t\ttabbedPane.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 10, 0, 0));\n\t\ttabbedPane.setMinimumSize(new java.awt.Dimension(0, 0));\n\t\ttabbedPane.setPreferredSize(new java.awt.Dimension(0, 50));\n\t\touterStateLabelPanel.setLayout(new java.awt.BorderLayout());\n\n\t\touterStateLabelPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\touterStateLabelPanel.setMinimumSize(new java.awt.Dimension(34, 0));\n\t\tstateLabelScrollPane.setMinimumSize(new java.awt.Dimension(24, 0));\n\t\tstateLabelScrollPane.setViewportView(stateLabelList);\n\n\t\touterStateLabelPanel.add(stateLabelScrollPane, java.awt.BorderLayout.CENTER);\n\n\t\ttabbedPane.addTab(\"State labels\", outerStateLabelPanel);\n\n\t\touterPathFormulaePanel.setLayout(new java.awt.BorderLayout());\n\n\t\touterPathFormulaePanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\touterPathFormulaePanel.setMinimumSize(new java.awt.Dimension(34, 0));\n\t\tpathFormulaeScrollPane.setMinimumSize(new java.awt.Dimension(24, 0));\n\t\tpathFormulaeScrollPane.setViewportView(pathFormulaeList);\n\n\t\touterPathFormulaePanel.add(pathFormulaeScrollPane, java.awt.BorderLayout.CENTER);\n\n\t\ttabbedPane.addTab(\"Path formulae\", outerPathFormulaePanel);\n\n\t\tinformationPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tinformationPanel.setMinimumSize(new java.awt.Dimension(211, 0));\n\t\tinnerInformationPanel.setLayout(new javax.swing.BoxLayout(innerInformationPanel, javax.swing.BoxLayout.Y_AXIS));\n\n\t\tinnerInformationPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tinnerInformationPanel.setMinimumSize(new java.awt.Dimension(211, 0));\n\t\ttopLabels.setLayout(new java.awt.GridLayout(1, 3, 5, 0));\n\n\t\ttopLabels.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 0, 5));\n\t\ttopLabels.setMinimumSize(new java.awt.Dimension(201, 0));\n\t\tmodelType.setText(\"Model Type:\");\n\t\tmodelType.setFont(this.getFont().deriveFont(Font.BOLD));\n\t\ttopLabels.add(modelType);\n\n\t\tdefinedConstants.setText(\"Defined Constants:\");\n\t\tdefinedConstants.setFont(this.getFont().deriveFont(Font.BOLD));\n\t\ttopLabels.add(definedConstants);\n\n\t\tinnerInformationPanel.add(topLabels);\n\n\t\ttopValues.setLayout(new java.awt.GridLayout(1, 3, 5, 0));\n\n\t\ttopValues.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 5, 5, 5));\n\t\tmodelTypeLabel.setText(\"Unknown\");\n\t\tmodelTypeLabel.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 10, 0, 0));\n\t\ttopValues.add(modelTypeLabel);\n\n\t\tdefinedConstantsLabel.setText(\"Unknown\");\n\t\tdefinedConstantsLabel.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 10, 0, 0));\n\t\ttopValues.add(definedConstantsLabel);\n\n\t\tinnerInformationPanel.add(topValues);\n\n\t\tbottomLabels.setLayout(new java.awt.GridLayout(1, 3, 5, 0));\n\n\t\tbottomLabels.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 0, 5));\n\t\tpathLength.setText(\"Path Length:\");\n\t\tpathLength.setFont(this.getFont().deriveFont(Font.BOLD));\n\t\tbottomLabels.add(pathLength);\n\n\t\ttotalTime.setText(\"Total Time:\");\n\t\ttotalTime.setFont(this.getFont().deriveFont(Font.BOLD));\n\t\tbottomLabels.add(totalTime);\n\n\t\tinnerInformationPanel.add(bottomLabels);\n\n\t\tbottomValues.setLayout(new java.awt.GridLayout(1, 3, 5, 0));\n\n\t\tbottomValues.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 5, 5, 5));\n\t\tpathLengthLabel.setText(\"0\");\n\t\tpathLengthLabel.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 10, 0, 0));\n\t\tbottomValues.add(pathLengthLabel);\n\n\t\ttotalTimeLabel.setText(\"0.0\");\n\t\ttotalTimeLabel.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 10, 0, 0));\n\t\tbottomValues.add(totalTimeLabel);\n\n\t\tinnerInformationPanel.add(bottomValues);\n\n\t\tinformationPanel.add(innerInformationPanel, java.awt.BorderLayout.NORTH);\n\n\t\ttabbedPane.addTab(\"Path information\", informationPanel);\n\n\t\ttopSplit.setRightComponent(tabbedPane);\n\n\t\touterTopLeftPanel.setLayout(new java.awt.BorderLayout());\n\n\t\ttopLeftPanel.setLayout(new java.awt.BorderLayout());\n\n\t\ttopLeftPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 10));\n\t\ttopLeftPanel.setMinimumSize(new java.awt.Dimension(0, 0));\n\t\ttopLeftPanel.setPreferredSize(new java.awt.Dimension(0, 0));\n\t\tinnerTopLeftPanel.setLayout(new java.awt.BorderLayout(5, 5));\n\n\t\tinnerTopLeftPanel.setMinimumSize(new java.awt.Dimension(50, 0));\n\t\tinnerTopLeftPanel.setPreferredSize(new java.awt.Dimension(302, 50));\n\t\touterLeftExplorePanel.setLayout(new java.awt.BorderLayout());\n\n\t\touterLeftExplorePanel.setMinimumSize(new java.awt.Dimension(129, 0));\n\t\tleftExplorePanel.setLayout(new javax.swing.BoxLayout(leftExplorePanel, javax.swing.BoxLayout.Y_AXIS));\n\n\t\tleftExplorePanel.setMinimumSize(new java.awt.Dimension(129, 0));\n\t\tautomaticExplorationPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tautomaticExplorationPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Automatic exploration\"));\n\t\tautomaticExplorationPanel.setMinimumSize(new java.awt.Dimension(129, 0));\n\t\tinnerAutomaticExplorationPanel.setLayout(new java.awt.GridLayout(2, 1, 5, 5));\n\n\t\tinnerAutomaticExplorationPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tinnerAutomaticExplorationPanel.setMinimumSize(new java.awt.Dimension(117, 0));\n\t\trandomExplorationButton.setIcon(new javax.swing.ImageIcon(\"\"));\n\t\trandomExplorationButton.setToolTipText(\"Make a number of random automatic updates\");\n\t\trandomExplorationButton.setHorizontalAlignment(javax.swing.SwingConstants.LEADING);\n\t\trandomExplorationButton.setText(\"Simulate\");\n\t\trandomExplorationButton.setMaximumSize(new java.awt.Dimension(220, 23));\n\t\trandomExplorationButton.setMinimumSize(new java.awt.Dimension(50, 23));\n\t\trandomExplorationButton.setPreferredSize(new java.awt.Dimension(160, 23));\n\t\trandomExplorationButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\trandomExplorationButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tinnerAutomaticExplorationPanel.add(randomExplorationButton);\n\n\t\tnoStepsExplorePanel.setLayout(new java.awt.GridBagLayout());\n\n\t\tnoStepsExplorePanel.setMinimumSize(new java.awt.Dimension(107, 0));\n\t\ttypeExploreCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"Num. steps\", \"Upto state\", \"Max. time\" }));\n\t\ttypeExploreCombo.setToolTipText(\"\");\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 2.0;\n\t\tgridBagConstraints.insets = new java.awt.Insets(0, 0, 0, 5);\n\t\tnoStepsExplorePanel.add(typeExploreCombo, gridBagConstraints);\n\n\t\tinputExploreField.setText(\"1\");\n\t\tinputExploreField.setToolTipText(\"\");\n\t\tinputExploreField.setPreferredSize(new java.awt.Dimension(60, 19));\n\t\tinputExploreField.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tinputExploreFieldActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 0.25;\n\t\tnoStepsExplorePanel.add(inputExploreField, gridBagConstraints);\n\n\t\tinnerAutomaticExplorationPanel.add(noStepsExplorePanel);\n\n\t\tautomaticExplorationPanel.add(innerAutomaticExplorationPanel, java.awt.BorderLayout.NORTH);\n\n\t\tleftExplorePanel.add(automaticExplorationPanel);\n\n\t\tbacktrackPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tbacktrackPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Backtracking\"));\n\t\tbacktrackPanel.setMinimumSize(new java.awt.Dimension(129, 0));\n\t\tinnerBacktrackPanel.setLayout(new java.awt.GridLayout(2, 1, 5, 5));\n\n\t\tinnerBacktrackPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tinnerBacktrackPanel.setMinimumSize(new java.awt.Dimension(117, 0));\n\t\tbacktrackButton.setIcon(new javax.swing.ImageIcon(\"\"));\n\t\tbacktrackButton.setText(\"Backtrack\");\n\t\tbacktrackButton.setToolTipText(\"Backtrack to a certain state in your path\");\n\t\tbacktrackButton.setHorizontalAlignment(javax.swing.SwingConstants.LEADING);\n\t\tbacktrackButton.setMaximumSize(new java.awt.Dimension(220, 23));\n\t\tbacktrackButton.setMinimumSize(new java.awt.Dimension(50, 23));\n\t\tbacktrackButton.setPreferredSize(new java.awt.Dimension(160, 23));\n\t\tbacktrackButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tbacktrackButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tinnerBacktrackPanel.add(backtrackButton);\n\n\t\tnoStepsBacktrackPanel.setLayout(new java.awt.GridBagLayout());\n\n\t\tnoStepsBacktrackPanel.setMinimumSize(new java.awt.Dimension(107, 0));\n\t\ttypeBacktrackCombo.setModel(new javax.swing.DefaultComboBoxModel(new String[] { \"Num. steps\", \"To state\" }));\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 2.0;\n\t\tgridBagConstraints.insets = new java.awt.Insets(0, 0, 0, 5);\n\t\tnoStepsBacktrackPanel.add(typeBacktrackCombo, gridBagConstraints);\n\n\t\tinputBacktrackField.setText(\"1\");\n\t\tinputBacktrackField.setToolTipText(\"\");\n\t\tinputBacktrackField.setPreferredSize(new java.awt.Dimension(60, 19));\n\t\tinputBacktrackField.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tinputBacktrackFieldActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 0.25;\n\t\tnoStepsBacktrackPanel.add(inputBacktrackField, gridBagConstraints);\n\n\t\tinnerBacktrackPanel.add(noStepsBacktrackPanel);\n\n\t\tbacktrackPanel.add(innerBacktrackPanel, java.awt.BorderLayout.CENTER);\n\n\t\tleftExplorePanel.add(backtrackPanel);\n\n\t\tstrategyPanel.setLayout(new java.awt.BorderLayout());\n\t\tstrategyPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Strategy\"));\n\t\tstrategyPanel.setMinimumSize(new java.awt.Dimension(129, 0));\n\t\tinnerStrategyPanel.setLayout(new java.awt.GridLayout(1, 1, 5, 5));\n\t\tinnerStrategyPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tinnerStrategyPanel.setMinimumSize(new java.awt.Dimension(117, 0));\n\t\tstratCombo.setModel(new DefaultComboBoxModel<>(new String[] { \"Hide\", \"Show\", \"Enforce\" }));\n\t\tstratCombo.setToolTipText(\"How to treat current strategy\");\n\t\tstratCombo.addItemListener(new ItemListener() {\n\t\t\tpublic void itemStateChanged(ItemEvent e)\n\t\t\t{\n\t\t\t\tif (e.getStateChange() == ItemEvent.SELECTED) {\n\t\t\t\t\tswitch (e.getItem().toString()) {\n\t\t\t\t\tcase \"Hide\":\n\t\t\t\t\t\tstratShow = false;\n\t\t\t\t\t\tengine.setStrategyEnforced(false);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase \"Show\":\n\t\t\t\t\t\tstratShow = true;\n\t\t\t\t\t\tengine.setStrategyEnforced(false);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\tcase \"Enforce\":\n\t\t\t\t\t\tstratShow = true;\n\t\t\t\t\t\tengine.setStrategyEnforced(true);\n\t\t\t\t\t\tbreak;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tupdateTableModel.updateUpdatesTable(pathTable);\n\t\t\t\tpathTableModel.updatePathTable();\n\t\t\t}\n\t\t});\n\t\t\n\t\tinnerStrategyPanel.add(stratCombo);\n\t\tstrategyPanel.add(innerStrategyPanel, java.awt.BorderLayout.CENTER);\n\t\tleftExplorePanel.add(strategyPanel);\n\n\t\touterLeftExplorePanel.add(leftExplorePanel, java.awt.BorderLayout.NORTH);\n\n\t\tinnerTopLeftPanel.add(outerLeftExplorePanel, java.awt.BorderLayout.WEST);\n\n\t\tmanualUpdatesPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tmanualUpdatesPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Manual exploration\"));\n\t\tmanualUpdatesPanel.setPreferredSize(new java.awt.Dimension(60, 60));\n\t\tinnerManualUpdatesPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tinnerManualUpdatesPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tmanualUpdateTableScrollPane.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0));\n\t\tcurrentUpdatesTable.setModel(new javax.swing.table.DefaultTableModel(new Object[][] { { null, null, null, null }, { null, null, null, null },\n\t\t\t\t{ null, null, null, null }, { null, null, null, null } }, new String[] { \"Title 1\", \"Title 2\", \"Title 3\", \"Title 4\" }));\n\t\tmanualUpdateTableScrollPane.setViewportView(currentUpdatesTable);\n\n\t\tinnerManualUpdatesPanel.add(manualUpdateTableScrollPane, java.awt.BorderLayout.CENTER);\n\n\t\tautoTimeCheckPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tautoTimeCheckPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 0, 0, 0));\n\t\tautoTimeCheck.setText(\"Generate time automatically\");\n\t\tautoTimeCheck.setToolTipText(\"When not selected, you will be prompted to manually enter the time spent in states\");\n\t\tautoTimeCheck.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0));\n\t\tautoTimeCheck.setHorizontalAlignment(javax.swing.SwingConstants.RIGHT);\n\t\tautoTimeCheck.setMargin(new java.awt.Insets(0, 0, 0, 0));\n\t\tautoTimeCheckPanel.add(autoTimeCheck, java.awt.BorderLayout.EAST);\n\n\t\tinnerManualUpdatesPanel.add(autoTimeCheckPanel, java.awt.BorderLayout.SOUTH);\n\n\t\tmanualUpdatesPanel.add(innerManualUpdatesPanel, java.awt.BorderLayout.CENTER);\n\n\t\tinnerTopLeftPanel.add(manualUpdatesPanel, java.awt.BorderLayout.CENTER);\n\n\t\ttopLeftPanel.add(innerTopLeftPanel, java.awt.BorderLayout.CENTER);\n\n\t\touterTopLeftPanel.add(topLeftPanel, java.awt.BorderLayout.CENTER);\n\n\t\ttopSplit.setLeftComponent(outerTopLeftPanel);\n\n\t\ttopPanel.add(topSplit, java.awt.BorderLayout.CENTER);\n\n\t\thorizontalSplit.setLeftComponent(topPanel);\n\n\t\touterBottomPanel.setLayout(new java.awt.BorderLayout());\n\n\t\touterBottomPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tbottomPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tbottomPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Path\"));\n\t\tbottomPanel.setMinimumSize(new java.awt.Dimension(42, 0));\n\t\ttableScroll.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tpathTablePlaceHolder.setToolTipText(\"Double-click or right-click to create a new path\");\n\t\ttableScroll.setViewportView(pathTablePlaceHolder);\n\n\t\tbottomPanel.add(tableScroll, java.awt.BorderLayout.CENTER);\n\n\t\touterBottomPanel.add(bottomPanel, java.awt.BorderLayout.CENTER);\n\n\t\thorizontalSplit.setBottomComponent(outerBottomPanel);\n\n\t\tallPanel.add(horizontalSplit, java.awt.BorderLayout.CENTER);\n\n\t\tadd(allPanel, java.awt.BorderLayout.CENTER);\n\n\t}// </editor-fold>//GEN-END:initComponents\n\n\t/** Override set font to set pass on to path table and header (which may not be visible yet) */\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\tif (pathTable != null)\n\t\t\tpathTable.setFont(font);\n\t}\n\n\tprivate void inputBacktrackFieldActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_inputBacktrackFieldActionPerformed\n\t\t// TODO add your handling code here:\n\t}//GEN-LAST:event_inputBacktrackFieldActionPerformed\n\n\tprivate void backtrackButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_backtrackButtonActionPerformed\n\n\t\ttry {\n\t\t\t// Backtrack a specified number of steps\n\t\t\tif (typeBacktrackCombo.getSelectedIndex() == 0) {\n\t\t\t\ttry {\n\t\t\t\t\tint noSteps = Integer.parseInt(inputBacktrackField.getText().trim());\n\t\t\t\t\t// Number must be >=0\n\t\t\t\t\tif (noSteps < 0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t// If number is too big, just set as max possible (i.e. path size)\n\t\t\t\t\tif (noSteps > engine.getPathSize())\n\t\t\t\t\t\tnoSteps = (int) engine.getPathSize();\n\t\t\t\t\t// If number is 0, nothing to do\n\t\t\t\t\telse if (noSteps == 0)\n\t\t\t\t\t\treturn;\n\t\t\t\t\t// Do backtrack\n\t\t\t\t\ta_backTrack((int)(engine.getPathSize() - noSteps));\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tString msg = \"The \\\"\" + typeBacktrackCombo.getSelectedItem() + \"\\\" parameter is invalid: \";\n\t\t\t\t\tmsg += \"it should be a positive integer\";\n\t\t\t\t\tthrow new PrismException(msg);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Backtrack to a specified step index\n\t\t\telse if (typeBacktrackCombo.getSelectedIndex() == 1) {\n\t\t\t\ttry {\n\t\t\t\t\tint toState = Integer.parseInt(inputBacktrackField.getText().trim());\n\t\t\t\t\t// Number must be a valid state index\n\t\t\t\t\tif (toState < 0 || toState > engine.getPathSize())\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t// Do backtrack\n\t\t\t\t\ta_backTrack(toState);\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tString msg = \"The \\\"\" + typeBacktrackCombo.getSelectedItem() + \"\\\" parameter is invalid: \";\n\t\t\t\t\tmsg += \"it should be between 0 and \" + (engine.getPathSize() - 1);\n\t\t\t\t\tthrow new PrismException(msg);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Backtrack for a specific amount of time\n\t\t\telse if (typeBacktrackCombo.getSelectedIndex() == 2) {\n\t\t\t\ttry {\n\t\t\t\t\tdouble time = Double.parseDouble(inputBacktrackField.getText().trim());\n\t\t\t\t\t// Time must be >=0\n\t\t\t\t\tif (time < 0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t// If time is too big, just set as max possible (i.e. total path time)\n\t\t\t\t\tif (time >= engine.getTotalTimeForPath())\n\t\t\t\t\t\ttime = engine.getTotalTimeForPath();\n\t\t\t\t\t// Do backtrack\n\t\t\t\t\ta_backTrack(engine.getTotalTimeForPath() - time);\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tString msg = \"The \\\"\" + typeBacktrackCombo.getSelectedItem() + \"\\\" parameter is invalid: \";\n\t\t\t\t\tmsg += \"it should be a positive double\";\n\t\t\t\t\tthrow new PrismException(msg);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Backtrack to a specified point in time\n\t\t\telse if (typeBacktrackCombo.getSelectedIndex() == 3) {\n\t\t\t\ttry {\n\t\t\t\t\tdouble time = Double.parseDouble(inputBacktrackField.getText().trim());\n\t\t\t\t\t// Must be a valid time point in path\n\t\t\t\t\tif (time < 0 || time >= engine.getTotalTimeForPath())\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t// Do backtrack\n\t\t\t\t\ta_backTrack(time);\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tString msg = \"The \\\"\" + typeBacktrackCombo.getSelectedItem() + \"\\\" parameter is invalid: \";\n\t\t\t\t\tmsg += \"it should be between 0 and \" + (engine.getTotalTimeForPath());\n\t\t\t\t\tthrow new PrismException(msg);\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (PrismException se) {\n\t\t\tthis.error(se.getMessage());\n\t\t}\n\t}//GEN-LAST:event_backtrackButtonActionPerformed\n\n\tprivate void configureViewButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_configureViewButtonActionPerformed\n\t\ta_configureView();\n\t}//GEN-LAST:event_configureViewButtonActionPerformed\n\n\tprivate void initPopups()\n\t{\n\t\tnewPath = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGUISimulator.this.tabToFront();\n\t\t\t\ta_newPath(false);\n\t\t\t}\n\t\t};\n\n\t\tnewPath.putValue(Action.LONG_DESCRIPTION, \"Creates a new path.\");\n\t\tnewPath.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_N));\n\t\tnewPath.putValue(Action.NAME, \"New path\");\n\t\tnewPath.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\t\tnewPath.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F8, 0));\n\n\t\tnewPathFromState = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tGUISimulator.this.tabToFront();\n\t\t\t\ta_newPath(true);\n\t\t\t}\n\t\t};\n\n\t\tnewPathFromState.putValue(Action.LONG_DESCRIPTION, \"Creates a new path from a chosen state.\");\n\t\t//newPathFromState.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_N));\n\t\tnewPathFromState.putValue(Action.NAME, \"New path from state\");\n\t\tnewPathFromState.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallStates.png\"));\n\n\t\tnewPathPlot = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_newPathPlot(false);\n\t\t\t}\n\t\t};\n\t\tnewPathPlot.putValue(Action.LONG_DESCRIPTION, \"Creates and plots a new path.\");\n\t\t//newPathPlot.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_N));\n\t\tnewPathPlot.putValue(Action.NAME, \"Plot new path\");\n\t\tnewPathPlot.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileGraph.png\"));\n\t\tnewPathPlot.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F8, Toolkit.getDefaultToolkit().getMenuShortcutKeyMask()));\n\n\t\tnewPathPlotFromState = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_newPathPlot(true);\n\t\t\t}\n\t\t};\n\t\tnewPathPlotFromState.putValue(Action.LONG_DESCRIPTION, \"Creates and plots a new path from a chosen state.\");\n\t\t//newPathPlotFromState.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_N));\n\t\tnewPathPlotFromState.putValue(Action.NAME, \"Plot new path from state\");\n\t\tnewPathPlotFromState.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileGraph.png\"));\n\n\t\tresetPath = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_restartPath();\n\t\t\t}\n\t\t};\n\n\t\tresetPath.putValue(Action.LONG_DESCRIPTION, \"Resets the path.\");\n\t\tresetPath.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_R));\n\t\tresetPath.putValue(Action.NAME, \"Reset path\");\n\t\tresetPath.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPlayerStart.png\"));\n\t\tresetPath.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F8, InputEvent.SHIFT_DOWN_MASK));\n\n\t\texportPath = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_exportPath();\n\t\t\t}\n\t\t};\n\n\t\texportPath.putValue(Action.LONG_DESCRIPTION, \"Exports the path.\");\n\t\texportPath.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_X));\n\t\texportPath.putValue(Action.NAME, \"Export path\");\n\t\texportPath.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallExport.png\"));\n\n\t\tplotPath = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_plotPath();\n\t\t\t}\n\t\t};\n\t\tplotPath.putValue(Action.LONG_DESCRIPTION, \"Plots the path on a graph.\");\n\t\tplotPath.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_P));\n\t\tplotPath.putValue(Action.NAME, \"Plot path\");\n\t\tplotPath.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallFileGraph.png\"));\n\n\t\trandomExploration = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\trandomExplorationButtonActionPerformed(e);\n\t\t\t}\n\t\t};\n\t\trandomExploration.putValue(Action.LONG_DESCRIPTION, \"Extends the path by simulating.\");\n\t\trandomExploration.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_S));\n\t\trandomExploration.putValue(Action.NAME, \"Simulate\");\n\t\trandomExploration.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPlayerFwd.png\"));\n\t\trandomExploration.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F9, 0));\n\n\t\tbacktrack = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tbacktrackButtonActionPerformed(e);\n\t\t\t}\n\t\t};\n\t\tbacktrack.putValue(Action.LONG_DESCRIPTION, \"Backtracks the path.\");\n\t\tbacktrack.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_K));\n\t\tbacktrack.putValue(Action.NAME, \"Backtrack\");\n\t\tbacktrack.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPlayerRew.png\"));\n\t\tbacktrack.putValue(Action.ACCELERATOR_KEY, KeyStroke.getKeyStroke(KeyEvent.VK_F9, InputEvent.SHIFT_DOWN_MASK));\n\n\t\tbacktrackToHere = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_backTrack(pathTable.getSelectedRow());\n\t\t\t}\n\t\t};\n\t\tbacktrackToHere.putValue(Action.LONG_DESCRIPTION, \"Backtracks the path to the selected state.\");\n\t\tbacktrackToHere.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_B));\n\t\tbacktrackToHere.putValue(Action.NAME, \"Backtrack to here\");\n\t\tbacktrackToHere.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallPlayerRew.png\"));\n\n\t\tremoveToHere = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_removePreceding(pathTable.getSelectedRow());\n\t\t\t}\n\t\t};\n\t\tremoveToHere.putValue(Action.LONG_DESCRIPTION, \"Removes states preceding the selected state from the path.\");\n\t\tremoveToHere.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_R));\n\t\tremoveToHere.putValue(Action.NAME, \"Remove preceding steps\");\n\t\tremoveToHere.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallRemove.png\"));\n\n\t\tconfigureView = new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\ta_configureView();\n\t\t\t}\n\t\t};\n\t\tconfigureView.putValue(Action.LONG_DESCRIPTION, \"Configures the view.\");\n\t\tconfigureView.putValue(Action.MNEMONIC_KEY, Integer.valueOf(KeyEvent.VK_C));\n\t\tconfigureView.putValue(Action.NAME, \"Configure view\");\n\t\tconfigureView.putValue(Action.SMALL_ICON, GUIPrism.getIconFromImage(\"smallOptions.png\"));\n\n\t\tpathPopupMenu = new JPopupMenu();\n\t\tpathPopupMenu.add(newPath);\n\t\tpathPopupMenu.add(newPathFromState);\n\t\tpathPopupMenu.add(newPathPlot);\n\t\tpathPopupMenu.add(newPathPlotFromState);\n\t\tpathPopupMenu.addSeparator();\n\t\tpathPopupMenu.add(resetPath);\n\t\tpathPopupMenu.add(exportPath);\n\t\tpathPopupMenu.add(plotPath);\n\t\tpathPopupMenu.addSeparator();\n\t\tpathPopupMenu.add(randomExploration);\n\t\tpathPopupMenu.add(backtrack);\n\t\tpathPopupMenu.add(backtrackToHere);\n\t\tpathPopupMenu.add(removeToHere);\n\t\tpathPopupMenu.addSeparator();\n\t\tpathPopupMenu.add(configureView);\n\n\t\tsimulatorMenu = new JMenu(\"Simulator\");\n\t\tsimulatorMenu.add(newPath);\n\t\tsimulatorMenu.add(newPathFromState);\n\t\tsimulatorMenu.add(newPathPlot);\n\t\tsimulatorMenu.add(newPathPlotFromState);\n\t\tsimulatorMenu.addSeparator();\n\t\tsimulatorMenu.add(resetPath);\n\t\tsimulatorMenu.add(exportPath);\n\t\tsimulatorMenu.add(plotPath);\n\t\tsimulatorMenu.addSeparator();\n\t\tsimulatorMenu.add(randomExploration);\n\t\tsimulatorMenu.add(backtrack);\n\t\tsimulatorMenu.addSeparator();\n\t\tsimulatorMenu.add(configureView);\n\n\t\tsimulatorMenu.setMnemonic('S');\n\t}\n\n\tprivate void exportPathButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_exportPathButtonActionPerformed\n\t{//GEN-HEADEREND:event_exportPathButtonActionPerformed\n\t\ta_exportPath();\n\t}//GEN-LAST:event_exportPathButtonActionPerformed\n\n\tprivate void resetPathButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_resetPathButtonActionPerformed\n\t{//GEN-HEADEREND:event_resetPathButtonActionPerformed\n\t\ta_restartPath();\n\t}//GEN-LAST:event_resetPathButtonActionPerformed\n\n\tprivate void inputExploreFieldActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_inputExploreFieldActionPerformed\n\n\t}//GEN-LAST:event_inputExploreFieldActionPerformed\n\n\tprivate void randomExplorationButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_randomExplorationButtonActionPerformed\n\n\t\ttry {\n\t\t\t// Simulate a specified number of steps\n\t\t\tif (typeExploreCombo.getSelectedIndex() == 0) {\n\t\t\t\ttry {\n\t\t\t\t\tint noSteps = Integer.parseInt(inputExploreField.getText().trim());\n\t\t\t\t\t// Number must be >0\n\t\t\t\t\tif (noSteps <= 0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t// Do simulation\n\t\t\t\t\ta_autoStep(noSteps);\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tString msg = \"The \\\"\" + typeExploreCombo.getSelectedItem() + \"\\\" parameter is invalid: \";\n\t\t\t\t\tmsg += \"it should be a positive integer\";\n\t\t\t\t\tthrow new PrismException(msg);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Simulate up until a specified step index \n\t\t\telse if (typeExploreCombo.getSelectedIndex() == 1) {\n\t\t\t\ttry {\n\t\t\t\t\tint uptoState = Integer.parseInt(inputExploreField.getText().trim());\n\t\t\t\t\t// Index must exceed current path length\n\t\t\t\t\tif (uptoState <= engine.getPathSize())\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t// Do simulation\n\t\t\t\t\ta_autoStep((int)(uptoState - engine.getPathSize()));\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tString msg = \"The \\\"\" + typeExploreCombo.getSelectedItem() + \"\\\" parameter is invalid: \";\n\t\t\t\t\tmsg += \"it should be greater than \" + engine.getPathSize();\n\t\t\t\t\tthrow new PrismException(msg);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Simulate for a specified amount of time\n\t\t\telse if (typeExploreCombo.getSelectedIndex() == 2) {\n\t\t\t\ttry {\n\t\t\t\t\tdouble time = Double.parseDouble(inputExploreField.getText().trim());\n\t\t\t\t\t// Time must be >=0\n\t\t\t\t\tif (time < 0.0)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t// Do simulation\n\t\t\t\t\ta_autoStep(time);\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tString msg = \"The \\\"\" + typeExploreCombo.getSelectedItem() + \"\\\" parameter is invalid: \";\n\t\t\t\t\tmsg += \"it should be a positive double\";\n\t\t\t\t\tthrow new PrismException(msg);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Simulate up until a specified point in time\n\t\t\telse if (typeExploreCombo.getSelectedIndex() == 3) {\n\t\t\t\tdouble currentTime = engine.getTotalTimeForPath();\n\t\t\t\ttry {\n\t\t\t\t\tdouble time = Double.parseDouble(inputExploreField.getText().trim());\n\t\t\t\t\t// Time must exceed current total path time\n\t\t\t\t\tif (time <= currentTime)\n\t\t\t\t\t\tthrow new NumberFormatException();\n\t\t\t\t\t// Do simulation\n\t\t\t\t\ta_autoStep(time - currentTime);\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tString msg = \"The \\\"\" + typeExploreCombo.getSelectedItem() + \"\\\" parameter is invalid: \";\n\t\t\t\t\tmsg += \"it should be greater than \" + currentTime;\n\t\t\t\t\tthrow new PrismException(msg);\n\t\t\t\t}\n\t\t\t}\n\n\t\t} catch (PrismException se) {\n\t\t\tthis.error(se.getMessage());\n\t\t}\n\t}//GEN-LAST:event_randomExplorationButtonActionPerformed\n\n\tprivate void newPathButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_newPathButtonActionPerformed\n\t{//GEN-HEADEREND:event_newPathButtonActionPerformed\n\t\ta_newPath(false);\n\t}//GEN-LAST:event_newPathButtonActionPerformed\n\n\t/**\n\t * Getter for property pathActive.\n\t * @return Value of property pathActive.\n\t */\n\tpublic boolean isPathActive()\n\t{\n\t\treturn pathActive;\n\t}\n\n\t/**\n\t * Setter for property pathActive.\n\t * @param pathActive New value of property pathActive.\n\t */\n\tpublic void setPathActive(boolean pathActive)\n\t{\n\t\tthis.pathActive = pathActive;\n\t\tpathTableModel.setPathActive(pathActive);\n\t}\n\n\t/**\n\t * Setter for property parsedModel.\n\t * @param pathActive New value of property pathActive.\n\t */\n\tpublic void setParsedModel(ModulesFile parsedModel)\n\t{\n\t\tthis.parsedModel = parsedModel;\n\t\tpathTableModel.setParsedModel(parsedModel);\n\t\tpathTableModel.setModelInfo(parsedModel);\n\t}\n\n\t/**\n\t * Getter for property computing.\n\t * @return Value of property computing.\n\t */\n\tpublic boolean isComputing()\n\t{\n\t\treturn computing;\n\t}\n\n\t/**\n\t * Setter for property computing.\n\t * @param computing New value of property computing.\n\t */\n\tpublic void setComputing(boolean computing)\n\t{\n\t\tthis.computing = computing;\n\t\tdoEnables();\n\t}\n\n\tpublic void mouseClicked(MouseEvent e)\n\t{\n\t}\n\n\tpublic void mouseEntered(MouseEvent e)\n\t{\n\t}\n\n\tpublic void mouseExited(MouseEvent e)\n\t{\n\t}\n\n\tpublic void mousePressed(MouseEvent e)\n\t{\n\t\tdoPopupDetection(e);\n\t}\n\n\tpublic void mouseReleased(MouseEvent e)\n\t{\n\t\tdoPopupDetection(e);\n\t}\n\n\tpublic void doPopupDetection(MouseEvent e)\n\t{\n\t\tif (!computing) {\n\t\t\tif (e.getClickCount() == 2 && (e.getSource() == pathTablePlaceHolder || e.getSource() == tableScroll)) {\n\t\t\t\tif (newPath.isEnabled())\n\t\t\t\t\ta_newPath(false);\n\t\t\t} else if (e.isPopupTrigger()\n\t\t\t\t\t&& (e.getSource() == pathTablePlaceHolder || e.getSource() == pathTable || e.getSource() == pathTable.getTableHeader() || e.getSource() == tableScroll)) {\n\t\t\t\trandomExploration\n\t\t\t\t\t\t.setEnabled(!(e.getSource() == pathTable.getTableHeader() || e.getSource() == pathTablePlaceHolder || e.getSource() == tableScroll));\n\t\t\t\tbacktrack.setEnabled(!(e.getSource() == pathTable.getTableHeader() || e.getSource() == pathTablePlaceHolder || e.getSource() == tableScroll));\n\t\t\t\tbacktrackToHere\n\t\t\t\t\t\t.setEnabled(!(e.getSource() == pathTable.getTableHeader() || e.getSource() == pathTablePlaceHolder || e.getSource() == tableScroll));\n\t\t\t\tremoveToHere\n\t\t\t\t\t\t.setEnabled(!(e.getSource() == pathTable.getTableHeader() || e.getSource() == pathTablePlaceHolder || e.getSource() == tableScroll));\n\t\t\t\tdoEnables();\n\t\t\t\tint index = pathTable.rowAtPoint(e.getPoint());\n\t\t\t\tpathTable.getSelectionModel().setSelectionInterval(index, index);\n\t\t\t\tpathPopupMenu.show(e.getComponent(), e.getX(), e.getY());\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void insertTableColumn(TableColumn column)\n\t{\n\t\tint i = 1;\n\t\tint j = 1;\n\n\t\tString text = (String) column.getHeaderValue();\n\n\t\twhile (j <= pathTable.getColumnCount() && i < pathTableModel.getColumnCount()) {\n\t\t\tif (j == pathTable.getColumnCount()) {\n\t\t\t\t// Found the location\n\t\t\t\tpathTable.addColumn(column);\n\n\t\t\t\tbreak;\n\t\t\t} else {\n\t\t\t\tString tcj = pathTable.getColumnName(j);\n\t\t\t\tString tci = pathTableModel.getColumnName(i);\n\n\t\t\t\tif (tci.equals(text)) {\n\t\t\t\t\t// Found the location\n\t\t\t\t\tpathTable.addColumn(column);\n\n\t\t\t\t\t// Move to location\n\t\t\t\t\tif (j != pathTable.getColumnCount() - 1)\n\t\t\t\t\t\tpathTable.moveColumn(pathTable.getColumnCount() - 1, j);\n\t\t\t\t\tbreak;\n\t\t\t\t} else {\n\t\t\t\t\ti++;\n\n\t\t\t\t\tif (tci.equals(tcj)) {\n\t\t\t\t\t\tj++;\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void showColumn(int i)\n\t{\n\n\t}\n\n\t/**\n\t * Getter for property displayStyle.\n\t * @return Value of property displayStyle.\n\t */\n\tpublic boolean isDisplayStyle()\n\t{\n\t\treturn displayStyleFast;\n\t}\n\n\t/**\n\t * Setter for property displayStyle.\n\t * @param displayStyle New value of property displayStyle.\n\t */\n\tpublic void setDisplayStyle(boolean displayStyle) throws PrismException\n\t{\n\n\t\tgetPrism().getSettings().set(PrismSettings.SIMULATOR_RENDER_ALL_VALUES, Integer.valueOf(displayStyle ? 0 : 1));\n\n\t}\n\n\t/**\n\t * Getter for property displayPathLoops.\n\t * @return Value of property displayPathLoops.\n\t */\n\tpublic boolean isDisplayPathLoops()\n\t{\n\t\treturn displayPathLoops;\n\t}\n\n\t/**\n\t * Setter for property displayStyle.\n\t * @param b New value of property displayStyle.\n\t */\n\tpublic void setDisplayPathLoops(boolean b) throws PrismException\n\t{\n\t\tdisplayPathLoops = b;\n\t\t//getPrism().getSettings().set(PrismSettings.SIMULATOR_????, Boolean.valueOf(b));\n\t}\n\n\tpublic ModulesFile getModulesFile()\n\t{\n\t\treturn parsedModel;\n\t}\n\n\t/**\n\t * Respond to selections of rows in the path table: update transition list.\n\t */\n\tpublic void valueChanged(ListSelectionEvent e)\n\t{\n\t\t// If no rows are selected, make the last (current) state selected and proceed\n\t\tif (pathTable.getSelectedRowCount() == 0) {\n\t\t\tint last = pathTable.getRowCount() - 1;\n\t\t\tpathTable.getSelectionModel().setSelectionInterval(last, last);\n\t\t}\n\t\t// Update transition table according to reflect currently selected step\n\t\tupdateTableModel.updateUpdatesTable(pathTable);\n\t\tstateLabelList.repaint();\n\t\tpathFormulaeList.repaint();\n\t}\n\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tprivate javax.swing.JPanel allPanel;\n\tprivate javax.swing.JCheckBox autoTimeCheck;\n\tprivate javax.swing.JPanel autoTimeCheckPanel;\n\tprivate javax.swing.JPanel automaticExplorationPanel;\n\tjavax.swing.JButton backtrackButton;\n\tprivate javax.swing.JPanel backtrackPanel;\n\tprivate javax.swing.JPanel strategyPanel;\n\tprivate javax.swing.JPanel bottomLabels;\n\tprivate javax.swing.JPanel bottomPanel;\n\tprivate javax.swing.JPanel bottomValues;\n\tprivate javax.swing.ButtonGroup buttonGroup1;\n\tjavax.swing.JButton configureViewButton;\n\tjavax.swing.JTable currentUpdatesTable;\n\tprivate javax.swing.JLabel definedConstants;\n\tprivate javax.swing.JLabel definedConstantsLabel;\n\tjavax.swing.JButton exportPathButton;\n\tprivate javax.swing.JSplitPane horizontalSplit;\n\tprivate javax.swing.JPanel informationPanel;\n\tprivate javax.swing.JPanel innerAutomaticExplorationPanel;\n\tprivate javax.swing.JPanel innerBacktrackPanel;\n\tprivate javax.swing.JPanel innerStrategyPanel;\n\tprivate javax.swing.JPanel innerButtonPanel;\n\tprivate javax.swing.JPanel innerInformationPanel;\n\tprivate javax.swing.JPanel innerManualUpdatesPanel;\n\tprivate javax.swing.JPanel innerTopLeftPanel;\n\tjavax.swing.JTextField inputBacktrackField;\n\tjavax.swing.JTextField inputExploreField;\n\tprivate javax.swing.JPanel jPanel2;\n\tprivate javax.swing.JPanel jPanel3;\n\tprivate javax.swing.JPanel jPanel4;\n\tprivate javax.swing.JSplitPane jSplitPane1;\n\tprivate javax.swing.JPanel leftExplorePanel;\n\tprivate javax.swing.JScrollPane manualUpdateTableScrollPane;\n\tprivate javax.swing.JPanel manualUpdatesPanel;\n\tprivate javax.swing.JLabel modelType;\n\tprivate javax.swing.JLabel modelTypeLabel;\n\tjavax.swing.JButton newPathButton;\n\tprivate javax.swing.JPanel noStepsBacktrackPanel;\n\tprivate javax.swing.JPanel noStepsExplorePanel;\n\tprivate javax.swing.JPanel outerBottomPanel;\n\tprivate javax.swing.JPanel outerLeftExplorePanel;\n\tprivate javax.swing.JPanel outerPathFormulaePanel;\n\tprivate javax.swing.JPanel outerStateLabelPanel;\n\tprivate javax.swing.JPanel outerTopLeftPanel;\n\tjavax.swing.JList pathFormulaeList;\n\tprivate javax.swing.JScrollPane pathFormulaeScrollPane;\n\tprivate javax.swing.JLabel pathLength;\n\tprivate javax.swing.JLabel pathLengthLabel;\n\tprivate javax.swing.JTable pathTable;\n\tprivate javax.swing.JPanel pathTablePlaceHolder;\n\tjavax.swing.JButton randomExplorationButton;\n\tjavax.swing.JButton resetPathButton;\n\tprivate javax.swing.JList stateLabelList;\n\tprivate javax.swing.JScrollPane stateLabelScrollPane;\n\tprivate javax.swing.JTabbedPane tabbedPane;\n\tprivate javax.swing.JScrollPane tableScroll;\n\tprivate javax.swing.JPanel topLabels;\n\tprivate javax.swing.JPanel topLeftPanel;\n\tprivate javax.swing.JPanel topPanel;\n\tprivate javax.swing.JSplitPane topSplit;\n\tprivate javax.swing.JPanel topValues;\n\tprivate javax.swing.JLabel totalTime;\n\tprivate javax.swing.JLabel totalTimeLabel;\n\tprivate javax.swing.JComboBox typeBacktrackCombo;\n\tprivate javax.swing.JComboBox typeExploreCombo;\n\tprivate javax.swing.JComboBox<String> stratCombo;\n\n\t// End of variables declaration//GEN-END:variables\n\n\tpublic void sortOutColumnSizes()\n\t{\n\t\tint prevWidth = pathTable.getWidth();\n\n\t\tTableColumnModel cm = pathTable.getColumnModel();\n\n\t\tfor (int i = 0; i < cm.getColumnCount(); i++) {\n\t\t\tTableColumn tc = cm.getColumn(i);\n\n\t\t\ttc.setMinWidth(50);\n\t\t}\n\n\t\tif (50 * cm.getColumnCount() > tableScroll.getWidth()) {\n\t\t\tpathTable.setAutoResizeMode(JTable.AUTO_RESIZE_OFF);\n\n\t\t} else\n\t\t\tpathTable.setAutoResizeMode(JTable.AUTO_RESIZE_SUBSEQUENT_COLUMNS);\n\t}\n\n\tpublic boolean isOldUpdate()\n\t{\n\t\treturn this.updateTableModel.oldUpdate;\n\t}\n\n\tpublic int getOldUpdateStep()\n\t{\n\t\treturn updateTableModel.oldStep;\n\t}\n\n\tpublic boolean usingChangeRenderer()\n\t{\n\t\treturn ((GUISimulatorPathTable) pathTable).usingChangeRenderer();\n\t}\n\n\tpublic void setRenderer(boolean displayStyleFast)\n\t{\n\t\tif (displayStyleFast) {\n\t\t\t((GUISimulatorPathTable) pathTable).switchToChangeRenderer();\n\t\t} else {\n\t\t\t((GUISimulatorPathTable) pathTable).switchToBoringRenderer();\n\t\t}\n\n\t\t//displayPathLoops = settings.getBoolean(PrismSettings.SIMULATOR_???);\n\n\t\trepaint();\n\t}\n\n\tpublic boolean isStrategyShown()\n\t{\n\t\treturn stratShow;\n\t}\n\t\n\tenum UpdateTableModelColumn {\n\t\tSTRAT, ACTION, PROB, UPDATE\n\t};\n\t\n\tclass UpdateTableModel extends AbstractTableModel\n\t{\n\t\tprivate List<UpdateTableModelColumn> visibleColumns = new ArrayList<>();\n\t\tpublic boolean oldUpdate;\n\t\tprivate int oldStep;\n\n\t\tpublic UpdateTableModel()\n\t\t{\n\t\t\tsuper();\n\t\t\toldUpdate = false;\n\t\t\toldStep = -1;\n\t\t}\n\n\t\t@Override\n\t\tpublic int getColumnCount()\n\t\t{\n\t\t\tif (pathActive) {\n\t\t\t\treturn visibleColumns.size();\n\t\t\t} else {\n\t\t\t\treturn 0;\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic int getRowCount()\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn pathActive ? engine.getNumTransitions() : 0;\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn 0;\n\t\t\t}\n\t\t}\n\n\t\t@Override\n\t\tpublic Object getValueAt(int rowIndex, int columnIndex)\n\t\t{\n\t\t\tif (pathActive && columnIndex < visibleColumns.size()) {\n\t\t\t\ttry {\n\t\t\t\t\tswitch (visibleColumns.get(columnIndex)) {\n\t\t\t\t\tcase STRAT:\n\t\t\t\t\t\treturn engine.getStrategyDecisionString(rowIndex);\n\t\t\t\t\tcase ACTION:\n\t\t\t\t\t\treturn engine.getTransitionActionDescription(rowIndex);\n\t\t\t\t\tcase PROB:\n\t\t\t\t\t\treturn engine.getTransitionProbabilityString(rowIndex);\n\t\t\t\t\tcase UPDATE:\n\t\t\t\t\t\treturn engine.getTransitionUpdateString(rowIndex);\n\t\t\t\t\tdefault:\n\t\t\t\t\t\treturn \"\";\n\t\t\t\t\t}\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\treturn \"\";\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn \"\";\n\t\t}\n\n\t\t@Override\n\t\tpublic String getColumnName(int columnIndex)\n\t\t{\n\t\t\tif (pathActive && columnIndex < visibleColumns.size()) {\n\t\t\t\tswitch (visibleColumns.get(columnIndex)) {\n\t\t\t\tcase STRAT:\n\t\t\t\t\treturn \"Strategy\";\n\t\t\t\tcase ACTION:\n\t\t\t\t\treturn engine.getModel().getActionStringDescription();\n\t\t\t\tcase PROB:\n\t\t\t\t\treturn parsedModel == null ? \"Probability\" : parsedModel.getModelType().probabilityOrRate();\n\t\t\t\tcase UPDATE:\n\t\t\t\t\treturn \"Update\";\n\t\t\t\tdefault:\n\t\t\t\t\treturn \"\";\n\t\t\t\t}\n\t\t\t}\n\t\t\treturn \"\";\n\t\t}\n\n\t\t/**\n\t\t * Update the updates table to display the available transitions in the current path step.\n\t\t */\n\t\tpublic void updateUpdatesTable()\n\t\t{\n\t\t\t// Re-compute the transitions if the table was showing old choices\n\t\t\tif (isOldUpdate()) {\n\t\t\t\ttry {\n\t\t\t\t\toldUpdate = false;\n\t\t\t\t\toldStep = -1;\n\t\t\t\t\tengine.computeTransitionsForCurrentState();\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t// Silently ignore errors - would have been reported\n\t\t\t\t\t// when the state was first arrived at\n\t\t\t\t}\n\t\t\t}\n\t\t\tsetVisibleColumns();\n\t\t\tdoEnables();\n\t\t\tfireTableStructureChanged();\n\t\t\tfireTableDataChanged();\n\t\t\tcurrentUpdatesTable.setEnabled(true);\n\t\t\tcurrentUpdatesTable.setToolTipText(\"Double click on an update to manually execute it\");\n\t\t\tif (getRowCount() > 0) {\n\t\t\t\tcurrentUpdatesTable.getSelectionModel().setSelectionInterval(0, 0);\n\t\t\t}\n\t\t}\n\n\t\t/**\n\t\t * Update the updates table to display the available transitions in the currently selected path step.\n\t\t */\n\t\tpublic void updateUpdatesTable(JTable pathTable)\n\t\t{\n\t\t\t// If current (or no) state selected, do update for current path state\n\t\t\tint step = pathTable.getSelectedRow();\n\t\t\tif (step == -1 || step == pathTable.getRowCount() - 1) {\n\t\t\t\tupdateUpdatesTable();\n\t\t\t} else {\n\t\t\t\t// Otherwise, compute transitions for the requested step\n\t\t\t\toldUpdate = true;\n\t\t\t\toldStep = step;\n\t\t\t\ttry {\n\t\t\t\t\tengine.computeTransitionsForStep(oldStep);\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t// Silently ignore errors - would have been reported\n\t\t\t\t\t// when the state was first arrived at\n\t\t\t\t}\n\t\t\t\tsetVisibleColumns();\n\t\t\t\tdoEnables();\n\t\t\t\tfireTableStructureChanged();\n\t\t\t\tfireTableDataChanged();\n\t\t\t\tcurrentUpdatesTable.setEnabled(false);\n\t\t\t\tcurrentUpdatesTable.setToolTipText(null);\n\t\t\t\tif (getRowCount() > 0) {\n\t\t\t\t\tint selectThis = engine.getChoiceOfPathStep(oldStep);\n\t\t\t\t\tcurrentUpdatesTable.getSelectionModel().setSelectionInterval(selectThis, selectThis);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic void setVisibleColumns()\n\t\t{\n\t\t\tvisibleColumns.clear();\n\t\t\tif (stratShow && engine.hasStrategyInfo()) {\n\t\t\t\tvisibleColumns.add(UpdateTableModelColumn.STRAT);\n\t\t\t}\n\t\t\tvisibleColumns.add(UpdateTableModelColumn.ACTION);\n\t\t\tif (parsedModel != null && parsedModel.getModelType().isProbabilistic()) {\n\t\t\t\tvisibleColumns.add(UpdateTableModelColumn.PROB);\n\t\t\t}\n\t\t\tvisibleColumns.add(UpdateTableModelColumn.UPDATE);\n\t\t}\n\t\t\n\t\tpublic void restartUpdatesTable()\n\t\t{\n\t\t\tfireTableStructureChanged();\n\t\t\tif (getRowCount() > 0) {\n\t\t\t\toldUpdate = false;\n\t\t\t\toldStep = -1;\n\t\t\t\tcurrentUpdatesTable.getSelectionModel().setSelectionInterval(0, 0);\n\t\t\t}\n\t\t}\n\n\t\tpublic int getChoiceIndexOf(int row)\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn engine.getChoiceIndexOfTransition(row);\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn -1;\n\t\t\t}\n\t\t}\n\n\t\tpublic boolean isEnabledByStrategy(int row)\n\t\t{\n\t\t\ttry {\n\t\t\t\treturn engine.isTransitionEnabledByStrategy(row);\n\t\t\t} catch (PrismException e) {\n\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\t\t\n\t\tpublic boolean isNondetModel()\n\t\t{\n\t\t\treturn engine.getModel().getModelType().nondeterministic();\n\t\t}\n\t}\n\t\n\tpublic void notifySettings(PrismSettings settings)\n\t{\n\t\tdisplayStyleFast = settings.getInteger(PrismSettings.SIMULATOR_RENDER_ALL_VALUES) == 0;\n\n\t\t/*if (displayStyleFast != view.isChangeRenderer()) {\n\t\t\tString[] answers = { \"Yes\", \"No\" };\n\t\t\tif (GUISimulator.this.question(\"You have changed the default rendering style of paths. Do you wish \\nto reflect this in your current trace?\",\n\t\t\t\t\tanswers, 0) == 0) {\n\t\t\t\tview.setRenderer(displayStyleFast);\n\t\t\t}\n\t\t}*/\n\t}\n\n\t/**\n\t * Utility function to format floating point numbers with a precision of 6 decimal places.\n\t */\n\tpublic String formatDouble(double d)\n\t{\n\t\treturn PrismUtils.formatDouble(6, d);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUISimulatorPathTable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport javax.swing.*;\nimport javax.swing.table.*;\nimport java.awt.*;\nimport java.awt.geom.*;\nimport java.awt.font.*;\n\nimport simulator.*;\nimport userinterface.util.*;\nimport userinterface.simulator.SimulationView.*;\n\npublic class GUISimulatorPathTable extends GUIGroupedTable\n{\n\tprivate static final long serialVersionUID = 1L;\n\n\t// Simulator\n\tprivate GUISimulator simulator;\n\t// Table model\n\tprivate GUISimulatorPathTableModel ptm;\n\t// Component on left hand side to show path loops\n\tprivate JList<String> loopIndicator;\n\tprivate LoopIndicatorListModel loopIndicatorModel;\n\n\t/** Creates a new instance of GUISimulatorPathTable */\n\tpublic GUISimulatorPathTable(GUISimulator simulator, GUISimulatorPathTableModel ptm, SimulatorEngine engine)\n\t{\n\t\tsuper(ptm);\n\t\tthis.ptm = ptm;\n\t\tthis.simulator = simulator;\n\n\t\t// Table\n\t\tsetColumnSelectionAllowed(false);\n\t\tgetSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_SELECTION);\n\t\tsetDefaultRenderer(Object.class, new PathChangeTableRenderer(true));\n\t\t// Loop indicator\n\t\tloopIndicatorModel = new LoopIndicatorListModel();\n\t\tloopIndicator = new JList<>(loopIndicatorModel);\n\t\tloopIndicator.setBackground(new JPanel().getBackground());\n\t\tloopIndicator.setFixedCellWidth(25);\n\t\tloopIndicator.setFixedCellHeight(getRowHeight());\n\t\tloopIndicator.setCellRenderer(new LoopIndicatorRenderer(this));\n\t}\n\n\t/** Override set font to set row height(s) */\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\tsetRowHeight(getFontMetrics(font).getHeight() + 4);\n\t\tif (loopIndicator != null)\n\t\t\tloopIndicator.setFixedCellHeight(getRowHeight());\n\t}\n\n\tpublic boolean usingChangeRenderer()\n\t{\n\t\treturn ((PathChangeTableRenderer) getDefaultRenderer(Object.class)).onlyShowChange();\n\t}\n\n\tpublic void switchToChangeRenderer()\n\t{\n\t\tsetDefaultRenderer(Object.class, new PathChangeTableRenderer(true));\n\t\trepaint();\n\t}\n\n\tpublic void switchToBoringRenderer()\n\t{\n\t\tsetDefaultRenderer(Object.class, new PathChangeTableRenderer(false));\n\t\trepaint();\n\t}\n\n\tpublic void paintComponent(Graphics g)\n\t{\n\t\tsuper.paintComponent(g);\n\t\tloopIndicatorModel.updateIndicator();\n\t}\n\n\tpublic Component getPathLoopIndicator()\n\t{\n\t\treturn loopIndicator;\n\t}\n\n\t// Cell renderer for list representing loop indicator (left of path table)\n\n\tclass LoopIndicatorRenderer extends JPanel implements ListCellRenderer<String>\n\t{\n\t\tprivate static final long serialVersionUID = 1L;\n\n\t\tboolean startLoop, midLoop, endLoop;\n\n\t\tLoopIndicatorRenderer(JTable table)\n\t\t{\n\t\t\t/*JTableHeader header = table.getTableHeader();\n\t\t\t setOpaque(true);\n\t\t\t setBorder(UIManager.getBorder(\"TableHeader.cellBorder\"));\n\t\t\t setHorizontalAlignment(CENTER);\n\t\t\t setForeground(header.getForeground());\n\t\t\t setBackground(header.getBackground());\n\t\t\t setFont(header.getFont());*/\n\t\t}\n\n\t\tpublic Component getListCellRendererComponent(JList<? extends String> list, String value, int index, boolean isSelected, boolean cellHasFocus)\n\t\t{\n\t\t\t//setText((value == null) ? \"\" : value.toString());\n\t\t\t//setBorder(new LineBorder(Color.black, 1));\n\t\t\tif (ptm.isPathLooping()) {\n\t\t\t\tif (index == ptm.getLoopEnd() && index == ptm.getLoopStart()) {\n\t\t\t\t\tstartLoop = true;\n\t\t\t\t\tendLoop = true;\n\t\t\t\t\tmidLoop = false;\n\t\t\t\t} else if (index == ptm.getLoopEnd()) {\n\t\t\t\t\tstartLoop = false;\n\t\t\t\t\tmidLoop = false;\n\t\t\t\t\tendLoop = true;\n\t\t\t\t} else if (index == ptm.getLoopStart()) {\n\t\t\t\t\tstartLoop = true;\n\t\t\t\t\tmidLoop = false;\n\t\t\t\t\tendLoop = false;\n\t\t\t\t} else if (index > ptm.getLoopStart() && index < ptm.getLoopEnd()) {\n\t\t\t\t\tstartLoop = false;\n\t\t\t\t\tmidLoop = true;\n\t\t\t\t\tendLoop = false;\n\t\t\t\t} else {\n\t\t\t\t\tstartLoop = false;\n\t\t\t\t\tmidLoop = false;\n\t\t\t\t\tendLoop = false;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tstartLoop = false;\n\t\t\t\tmidLoop = false;\n\t\t\t\tendLoop = false;\n\t\t\t}\n\n\t\t\treturn this;\n\t\t}\n\n\t\tpublic void paintComponent(Graphics g)\n\t\t{\n\t\t\tGraphics2D g2 = (Graphics2D) g;\n\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);\n\t\t\tg2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\n\t\t\tg2.setColor(getBackground());\n\t\t\tg2.fillRect(0, 0, getWidth(), getHeight());\n\n\t\t\tif (!simulator.isDisplayPathLoops())\n\t\t\t\treturn;\n\n\t\t\tg2.setColor(Color.black);\n\t\t\tif (startLoop && endLoop) {\n\t\t\t\tGeneralPath gp = new GeneralPath();\n\t\t\t\tgp.moveTo(getWidth(), (getHeight() / 2) + 5);\n\t\t\t\tgp.lineTo((getWidth() / 2) + 5, (getHeight() / 2) + 5);\n\t\t\t\tgp.quadTo(getWidth() / 2, (getHeight() / 2) + 5, getWidth() / 2, (getHeight() / 2));\n\t\t\t\tgp.quadTo(getWidth() / 2, (getHeight() / 2) - 5, (getWidth() / 2) + 5, (getHeight() / 2) - 5);\n\t\t\t\tgp.lineTo((getWidth()), (getHeight() / 2) - 5);\n\t\t\t\tg2.draw(gp);\n\t\t\t\tgp = new GeneralPath();\n\t\t\t\tgp.moveTo(getWidth(), (getHeight() / 2) - 5);\n\t\t\t\tgp.lineTo(getWidth() - 5, (getHeight() / 2) - 8);\n\t\t\t\tgp.lineTo(getWidth() - 5, (getHeight() / 2) - 2);\n\t\t\t\tgp.closePath();\n\t\t\t\tg2.fill(gp);\n\t\t\t} else if (startLoop) {\n\t\t\t\tGeneralPath gp = new GeneralPath();\n\t\t\t\tgp.moveTo(getWidth(), getHeight() / 2);\n\t\t\t\tgp.lineTo((getWidth() / 2) + 5, getHeight() / 2);\n\t\t\t\tgp.quadTo(getWidth() / 2, getHeight() / 2, getWidth() / 2, (getHeight() / 2) + 5);\n\t\t\t\tgp.lineTo(getWidth() / 2, getHeight());\n\t\t\t\tg2.draw(gp);\n\t\t\t\tgp = new GeneralPath();\n\t\t\t\tgp.moveTo(getWidth(), getHeight() / 2);\n\t\t\t\tgp.lineTo(getWidth() - 5, (getHeight() / 2) - 3);\n\t\t\t\tgp.lineTo(getWidth() - 5, (getHeight() / 2) + 3);\n\t\t\t\tgp.closePath();\n\t\t\t\tg2.fill(gp);\n\t\t\t} else if (midLoop) {\n\t\t\t\tg2.drawLine(getWidth() / 2, 0, getWidth() / 2, getHeight());\n\t\t\t} else if (endLoop) {\n\t\t\t\tGeneralPath gp = new GeneralPath();\n\t\t\t\tgp.moveTo(getWidth(), getHeight() / 2);\n\t\t\t\tgp.lineTo((getWidth() / 2) + 5, getHeight() / 2);\n\t\t\t\tgp.quadTo(getWidth() / 2, getHeight() / 2, getWidth() / 2, (getHeight() / 2) - 5);\n\t\t\t\tgp.lineTo(getWidth() / 2, 0);\n\t\t\t\tg2.draw(gp);\n\t\t\t}\n\t\t}\n\t}\n\n\t// Model for list representing loop indicator\n\n\tclass LoopIndicatorListModel extends AbstractListModel<String>\n\t{\n\t\tprivate static final long serialVersionUID = 1L;\n\n\t\tpublic String getElementAt(int index)\n\t\t{\n\t\t\treturn \"\";\n\t\t}\n\n\t\tpublic int getSize()\n\t\t{\n\t\t\treturn ptm.getRowCount();\n\t\t}\n\n\t\tpublic void updateIndicator()\n\t\t{\n\t\t\tfireContentsChanged(this, 0, ptm.getRowCount());\n\t\t}\n\n\t}\n\n\t// Renderer for cells in path table\n\n\tclass PathChangeCellRenderer extends JPanel\n\t{\n\t\tprivate static final long serialVersionUID = 1L;\n\n\t\tprivate PathChangeTableRenderer pctr;\n\n\t\tprivate Object value;\n\t\tprivate String stringValue;\n\n\t\tprivate boolean isSelected;\n\n\t\tpublic PathChangeCellRenderer(PathChangeTableRenderer pctr, Object value, boolean isSelected, int row)\n\t\t{\n\t\t\tsuper();\n\t\t\tthis.pctr = pctr;\n\t\t\tthis.value = value;\n\t\t\tthis.isSelected = isSelected;\n\n\t\t\tif (value instanceof ActionValue) {\n\t\t\t\tActionValue actionValue = (ActionValue) value;\n\t\t\t\tif (actionValue.isActionValueUnknown()) {\n\t\t\t\t\t// unused:\n\t\t\t\t\tstringValue = \"?\";\n\t\t\t\t\tthis.setToolTipText(\"Module name or [action] label for transition from state \" + (row - 1) + \" to \" + (row) + \" (not yet known)\");\n\t\t\t\t} else {\n\t\t\t\t\tstringValue = actionValue.getValue();\n\t\t\t\t\tString tooltip;\n\t\t\t\t\tif (row == 0) {\n\t\t\t\t\t\ttooltip = null;\n\t\t\t\t\t} else {\n\t\t\t\t\t\ttooltip = \"Module name or [action] label for transition from state \" + (row - 1) + \" to \" + (row);\n\t\t\t\t\t}\n\t\t\t\t\tthis.setToolTipText(tooltip);\n\t\t\t\t}\n\t\t\t} else if (value instanceof TimeValue) {\n\t\t\t\tTimeValue timeValue = (TimeValue) value;\n\t\t\t\tif (timeValue.isTimeValueUnknown()) {\n\t\t\t\t\tstringValue = \"?\";\n\t\t\t\t\tif (timeValue.isCumulative())\n\t\t\t\t\t\tthis.setToolTipText(\"Cumulative time up until entering state \" + (row) + \" (not yet known)\");\n\t\t\t\t\telse\n\t\t\t\t\t\tthis.setToolTipText(\"Time spent in state \" + (row) + \" (not yet known)\");\n\t\t\t\t} else {\n\t\t\t\t\tstringValue = (simulator.formatDouble((Double) timeValue.getValue()));\n\t\t\t\t\tif (timeValue.isCumulative())\n\t\t\t\t\t\tthis.setToolTipText(\"Cumulative time up until entering state \" + (row));\n\t\t\t\t\telse\n\t\t\t\t\t\tthis.setToolTipText(\"Time spent in state \" + (row));\n\t\t\t\t}\n\t\t\t} else if (value instanceof VariableValue) {\n\t\t\t\tVariableValue variableValue = (VariableValue) value;\n\t\t\t\tstringValue = (variableValue.getValue() instanceof Double) ? (simulator.formatDouble(((Double) variableValue.getValue()))) : variableValue\n\t\t\t\t\t\t.getValue().toString();\n\n\t\t\t\tthis.setToolTipText(\"Value of variable \\\"\" + variableValue.getVariable().getName() + \"\\\" in state \" + (row));\n\t\t\t} else if (value instanceof RewardStructureValue) {\n\t\t\t\tRewardStructureValue rewardValue = (RewardStructureValue) value;\n\t\t\t\tString rewardName = rewardValue.getRewardStructureColumn().getRewardStructure().getColumnName();\n\n\t\t\t\tif (rewardValue.isRewardValueUnknown()) {\n\t\t\t\t\tstringValue = \"?\";\n\n\t\t\t\t\tif (rewardValue.getRewardStructureColumn().isCumulativeReward())\n\t\t\t\t\t\tthis.setToolTipText(\"Cumulative reward of reward structure \" + rewardName + \" up until state \" + (row) + \" (not yet known)\");\n\t\t\t\t\tif (rewardValue.getRewardStructureColumn().isStateReward())\n\t\t\t\t\t\tthis.setToolTipText(\"State reward of reward structure \" + rewardName + \" in state \" + (row) + \" (not yet known)\");\n\t\t\t\t\tif (rewardValue.getRewardStructureColumn().isTransitionReward())\n\t\t\t\t\t\tthis.setToolTipText(\"Transition reward of reward structure \" + rewardName + \" from state \" + (row) + \" to \" + (row + 1)\n\t\t\t\t\t\t\t\t+ \" (not yet known)\");\n\t\t\t\t} else {\n\t\t\t\t\tstringValue = simulator.formatDouble(rewardValue.getRewardValue());\n\n\t\t\t\t\tif (rewardValue.getRewardStructureColumn().isCumulativeReward())\n\t\t\t\t\t\tthis.setToolTipText(\"Cumulative reward of reward structure \" + rewardName + \" up until state \" + (row));\n\t\t\t\t\tif (rewardValue.getRewardStructureColumn().isStateReward())\n\t\t\t\t\t\tthis.setToolTipText(\"State reward of reward structure \" + rewardName + \" in state \" + (row));\n\t\t\t\t\tif (rewardValue.getRewardStructureColumn().isTransitionReward())\n\t\t\t\t\t\tthis.setToolTipText(\"Transition reward of reward structure \" + rewardName + \" from state \" + (row) + \" to \" + (row + 1));\n\t\t\t\t}\n\t\t\t} else if (value instanceof MemoryValue) {\n\t\t\t\tMemoryValue memoryValue = (MemoryValue) value;\n\t\t\t\tif (memoryValue.isMemoryValueUnknown()) {\n\t\t\t\t\tstringValue = \"?\";\n\t\t\t\t\tthis.setToolTipText(\"Memory of strategy in state \" + (row) + \" (not yet known)\");\n\t\t\t\t} else {\n\t\t\t\t\tstringValue = memoryValue.getValue().toString();\n\t\t\t\t\tthis.setToolTipText(\"Memory of strategy in state \" + (row));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tstringValue = value.toString();\n\t\t\t\tthis.setToolTipText(\"State \" + row);\n\t\t\t}\n\t\t}\n\n\t\tpublic void paintComponent(Graphics g)\n\t\t{\n\t\t\tsuper.paintComponent(g);\n\n\t\t\tRectangle rect;\n\t\t\tint width, height, x, y;\n\n\t\t\t// Get graphics context\n\t\t\tGraphics2D g2 = (Graphics2D) g;\n\t\t\t// Get some info about the string\n\t\t\trect = getStringBounds(stringValue, g2);\n\t\t\twidth = (int) Math.ceil(rect.getWidth());\n\t\t\theight = (int) Math.ceil(rect.getHeight());\n\n\t\t\t// Variable value\n\t\t\tif (value instanceof VariableValue) {\n\t\t\t\tVariableValue variableValue = (VariableValue) value;\n\t\t\t\t// Position (horiz centred, vert centred)\n\t\t\t\tx = (getWidth() / 2) - (width / 2);\n\t\t\t\ty = (getHeight() / 2) + (height / 2);\n\t\t\t\t// Prepare box/colour\n\t\t\t\tRoundRectangle2D.Double rec = new RoundRectangle2D.Double(x - 5, 2, width + 10, getHeight() - 5, 8, 8);\n\t\t\t\tColor color = (variableValue.hasChanged()) ? (Color.black) : (Color.lightGray);\n\t\t\t\t// \"Render changes\" view\n\t\t\t\tif (pctr.onlyShowChange()) {\n\t\t\t\t\t// Vertical line in background\n\t\t\t\t\tg2.setColor(Color.black);\n\t\t\t\t\tg2.drawLine(getWidth() / 2, 0, getWidth() / 2, getHeight());\n\t\t\t\t\t// Only display box/value if there was a change\n\t\t\t\t\tif (isSelected || variableValue.hasChanged()) {\n\t\t\t\t\t\tg2.setColor(Color.white);\n\t\t\t\t\t\tg2.fill(rec);\n\t\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);\n\t\t\t\t\t\tg2.setColor(color);\n\t\t\t\t\t\tg2.draw(rec);\n\t\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);\n\t\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\t\t\t\tg2.drawString(stringValue, x, y);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// \"Render all values\" view\n\t\t\t\telse {\n\t\t\t\t\t// Just display value\n\t\t\t\t\tg2.setColor(color);\n\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);\n\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\t\t\tg2.drawString(stringValue, x, y);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Reward value\n\t\t\telse if (value instanceof RewardStructureValue) {\n\t\t\t\tRewardStructureValue rewardValue = (RewardStructureValue) value;\n\t\t\t\t// Default case (everything except cumulative time)\n\t\t\t\tif (!(ptm.canShowTime() && rewardValue.getRewardStructureColumn().isCumulativeReward())) {\n\t\t\t\t\t// Position (horiz centred, vert centred)\n\t\t\t\t\tx = (getWidth() / 2) - (width / 2);\n\t\t\t\t\ty = (getHeight() / 2) + (height / 2);\n\t\t\t\t\t// Prepare box/colour\n\t\t\t\t\tRoundRectangle2D.Double rec = new RoundRectangle2D.Double(x - 5, 2, width + 10, getHeight() - 5, 8, 8);\n\t\t\t\t\tColor color = (rewardValue.hasChanged() || rewardValue.isRewardValueUnknown()) ? (Color.black) : (Color.lightGray);\n\t\t\t\t\t// \"Render changes\" view\n\t\t\t\t\tif (pctr.onlyShowChange()) {\n\t\t\t\t\t\t// Vertical line in background\n\t\t\t\t\t\tg2.setColor(Color.black);\n\t\t\t\t\t\tg2.drawLine(getWidth() / 2, 0, getWidth() / 2, getHeight());\n\t\t\t\t\t\t// Only display box/value if there was a change\n\t\t\t\t\t\tif ((isSelected || rewardValue.hasChanged())) {\n\t\t\t\t\t\t\tg2.setColor(Color.white);\n\t\t\t\t\t\t\tg2.fill(rec);\n\t\t\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);\n\t\t\t\t\t\t\tg2.setColor(color);\n\t\t\t\t\t\t\tg2.draw(rec);\n\t\t\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);\n\t\t\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\t\t\t\t\tg2.drawString(stringValue, x, y);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t\t// \"Render all values\" view\n\t\t\t\t\telse {\n\t\t\t\t\t\t// Just display value\n\t\t\t\t\t\tg2.setColor(color);\n\t\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);\n\t\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\t\t\t\tg2.drawString(stringValue, x, y);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t// For continuous-time cumulative rewards, we left-align (like for display of time)\n\t\t\t\telse {\n\t\t\t\t\t// Position (left aligned, vert centred)\n\t\t\t\t\tx = 3;\n\t\t\t\t\ty = (getHeight() / 2) + (height / 2);\n\t\t\t\t\t// Write text\n\t\t\t\t\tg2.setColor(Color.black);\n\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);\n\t\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\t\t\tg2.drawString(stringValue, x, y);\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Time value\n\t\t\telse if (value instanceof TimeValue) {\n\t\t\t\t// Position (left aligned, vert centred)\n\t\t\t\tx = 3;\n\t\t\t\ty = (getHeight() / 2) + (height / 2);\n\t\t\t\t// Write text\n\t\t\t\tg2.setColor(Color.black);\n\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);\n\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\t\tg2.drawString(stringValue, x, y);\n\t\t\t}\n\t\t\t// Anything else (including ActionValue)\n\t\t\telse {\n\t\t\t\t// Position (horiz centred, vert centred)\n\t\t\t\tx = (getWidth() / 2) - (width / 2);\n\t\t\t\ty = (getHeight() / 2) + (height / 2);\n\t\t\t\t// Write value\n\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_OFF);\n\t\t\t\tg2.setRenderingHint(RenderingHints.KEY_TEXT_ANTIALIASING, RenderingHints.VALUE_TEXT_ANTIALIAS_ON);\n\t\t\t\tg2.setColor(Color.black);\n\t\t\t\tg2.drawString(stringValue, x, y);\n\t\t\t}\n\t\t}\n\t}\n\n\tclass PathChangeTableRenderer implements TableCellRenderer\n\t{\n\t\tprivate boolean onlyShowChange;\n\n\t\tprivate Color defaultColor;\n\n\t\tprivate Color selectedColor;\n\t\tprivate Color labelColor;\n\t\tprivate Color selectedLabelColor;\n\n\t\tpublic PathChangeTableRenderer(boolean onlyShowChange)\n\t\t{\n\t\t\tsuper();\n\n\t\t\tthis.onlyShowChange = onlyShowChange;\n\n\t\t\tdefaultColor = Color.white;\n\n\t\t\tselectedColor = new Color(defaultColor.getRed() - 20, defaultColor.getGreen() - 20, defaultColor.getBlue());\n\t\t\tselectedLabelColor = new Color(selectedColor.getRed() - 20, selectedColor.getGreen(), selectedColor.getBlue() - 20);\n\t\t\tlabelColor = new Color(defaultColor.getRed() - 50, defaultColor.getGreen(), defaultColor.getBlue() - 50);\n\n\t\t}\n\n\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t\t{\n\t\t\tPathChangeCellRenderer pctr = new PathChangeCellRenderer(this, value, isSelected, row);\n\n\t\t\tboolean shouldColourRow = ptm.shouldColourRow(row);\n\n\t\t\tColor backGround = defaultColor;\n\n\t\t\tif (isSelected && !shouldColourRow)\n\t\t\t\tbackGround = selectedColor;\n\t\t\telse if (isSelected && shouldColourRow)\n\t\t\t\tbackGround = selectedLabelColor;\n\t\t\telse if (!isSelected && shouldColourRow)\n\t\t\t\tbackGround = labelColor;\n\n\t\t\tpctr.setBackground(backGround);\n\n\t\t\treturn pctr;\n\t\t}\n\n\t\tpublic boolean onlyShowChange()\n\t\t{\n\t\t\treturn onlyShowChange;\n\t\t}\n\t}\n\n\t/** Method which computes rectangle bounds of a string for a given Graphics2D object\n\t */\n\tpublic static Rectangle getStringBounds(String s, Graphics2D g2)\n\t{\n\t\t// catch special cases...\n\t\t// ...TextLayout constructor crashes with null or zero-length string\n\t\tif (s == null)\n\t\t\treturn new Rectangle(0, 0);\n\t\tif (s.length() == 0)\n\t\t\treturn new Rectangle(0, 0);\n\t\tTextLayout layout = new TextLayout(s, g2.getFont(), g2.getFontRenderContext());\n\t\treturn layout.getOutline(new AffineTransform()).getBounds();\n\t}\n\n\t/** Method which computes width of a string for a given Graphics2D object\n\t */\n\tpublic static double getStringWidth(String s, Graphics2D g2)\n\t{\n\t\treturn getStringBounds(s, g2).getWidth();\n\t}\n\n\t/** Method which computes height of a string for a given Graphics2D object\n\t */\n\tpublic static double getStringHeight(String s, Graphics2D g2)\n\t{\n\t\treturn getStringBounds(s, g2).getHeight();\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUISimulatorPathTableModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.Observable;\nimport java.util.Observer;\n\nimport javax.swing.table.AbstractTableModel;\n\nimport parser.ast.ModulesFile;\nimport prism.ModelInfo;\nimport simulator.PathFullInfo;\nimport strat.StrategyGenerator;\nimport userinterface.simulator.SimulationView.ActionValue;\nimport userinterface.simulator.SimulationView.MemoryValue;\nimport userinterface.simulator.SimulationView.Observ;\nimport userinterface.simulator.SimulationView.RewardStructureColumn;\nimport userinterface.simulator.SimulationView.RewardStructureValue;\nimport userinterface.simulator.SimulationView.TimeValue;\nimport userinterface.simulator.SimulationView.Variable;\nimport userinterface.simulator.SimulationView.VariableValue;\nimport userinterface.util.GUIGroupedTableModel;\n\npublic class GUISimulatorPathTableModel extends AbstractTableModel implements GUIGroupedTableModel, Observer\n{\n\tprivate static final long serialVersionUID = 1L;\n\n\tenum PathTableModelGroupType {\n\t\tSTEP, TIME, VARIABLES, OBSERVABLES, REWARDS, STRATEGY\n\t};\n\t\n\tenum GUISimulatorPathTableModelColumn {\n\t\tACTION, STEP, TIME_CUMUL, TIME, VARIABLE, OBSERVABLE, REWARD, MEMORY\n\t};\n\t\n\tclass PathTableModelGroup {\n\t\tpublic PathTableModelGroupType type;\n\t\tpublic Object info;\n\t\tpublic int lastCol;\n\t\tpublic PathTableModelGroup(PathTableModelGroupType type, Object info, int lastCol)\n\t\t{\n\t\t\tthis.type = type;\n\t\t\tthis.info = info;\n\t\t\tthis.lastCol = lastCol;\n\t\t}\n\t}\n\t\n\tclass PathTableModelColumn {\n\t\tpublic GUISimulatorPathTableModelColumn type;\n\t\tpublic Object info;\n\t\tpublic PathTableModelColumn(GUISimulatorPathTableModelColumn type, Object info)\n\t\t{\n\t\t\tthis.type = type;\n\t\t\tthis.info = info;\n\t\t}\n\t}\n\t\n\tprivate GUISimulator simulator;\n\tprivate SimulationView view;\n\tprivate List<PathTableModelGroup> visibleGroups;\n\tprivate List<PathTableModelColumn> visibleColumns;\n\n\tprivate boolean pathActive;\n\tprivate ModulesFile parsedModel;\n\tprivate ModelInfo modelInfo;\n\tprivate PathFullInfo path; \n\n\tprivate RewardStructureValue rewardStructureValue;\n\tprivate VariableValue variableValue;\n\tprivate TimeValue timeValue;\n\tprivate ActionValue actionValue;\n\tprivate MemoryValue memoryValue;\n\n\tpublic GUISimulatorPathTableModel(GUISimulator simulator, SimulationView view)\n\t{\n\t\tthis.simulator = simulator;\n\t\tthis.view = view;\n\t\tthis.view.addObserver(this);\n\t\tvisibleGroups = new ArrayList<>();\n\t\tvisibleColumns = new ArrayList<>();\n\t\trewardStructureValue = view.new RewardStructureValue(null, null);\n\t\tvariableValue = view.new VariableValue(null, null);\n\t}\n\n\tpublic void setPathActive(boolean pathActive)\n\t{\n\t\tthis.pathActive = pathActive;\n\t}\n\n\tpublic void setPath(PathFullInfo path)\n\t{\n\t\tthis.path = path;\n\t}\n\n\tpublic void setParsedModel(ModulesFile parsedModel)\n\t{\n\t\tthis.parsedModel = parsedModel;\n\t}\n\n\tpublic void setModelInfo(ModelInfo modelInfo)\n\t{\n\t\tthis.modelInfo = modelInfo;\n\t}\n\n\tpublic boolean canShowTime()\n\t{\n\t\treturn modelInfo.getModelType().continuousTime();\n\t}\n\n\t@Override\n\tpublic int getGroupCount()\n\t{\n\t\tif (!pathActive) {\n\t\t\treturn 0;\n\t\t} else {\n\t\t\treturn visibleGroups.size();\n\t\t}\n\t}\n\n\t@Override\n\tpublic void update(Observable o, Object arg)\n\t{\n\t\tif (o == view) {\n\t\t\tsetVisibleColumnsAndGroups();\n\t\t\tfireTableStructureChanged();\n\n\t\t\t//Sort out the minimum widths for each column\n\t\t\tsimulator.sortOutColumnSizes();\n\t\t}\n\t}\n\n\t@Override\n\tpublic String getGroupName(int groupIndex)\n\t{\n\t\tif (!pathActive) {\n\t\t\treturn \"\";\n\t\t} else {\n\t\t\tswitch (visibleGroups.get(groupIndex).type) {\n\t\t\tcase STEP:\n\t\t\t\treturn \"Step\";\n\t\t\tcase TIME:\n\t\t\t\treturn \"Time\";\n\t\t\tcase VARIABLES:\n\t\t\t\tint module = (Integer) visibleGroups.get(groupIndex).info;\n\t\t\t\treturn module == -1 ? \"Globals\" : modelInfo.getModuleName(module);\n\t\t\tcase OBSERVABLES:\n\t\t\t\treturn \"Observables\";\n\t\t\tcase REWARDS:\n\t\t\t\treturn \"Rewards\";\n\t\t\tcase STRATEGY:\n\t\t\t\treturn \"Strategy\";\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic String getGroupToolTip(int groupIndex)\n\t{\n\t\tif (!pathActive) {\n\t\t\treturn \"\";\n\t\t} else {\n\t\t\tswitch (visibleGroups.get(groupIndex).type) {\n\t\t\tcase STEP:\n\t\t\t\treturn null;\n\t\t\tcase TIME:\n\t\t\t\treturn null;\n\t\t\tcase VARIABLES:\n\t\t\t\tint module = (Integer) visibleGroups.get(groupIndex).info;\n\t\t\t\treturn module == -1 ? \"Global variables\" : \"Variables of module \" + modelInfo.getModuleName(module);\n\t\t\tcase OBSERVABLES:\n\t\t\t\treturn null;\n\t\t\tcase REWARDS:\n\t\t\t\treturn \"State, transition and cumulative rewards\";\n\t\t\tcase STRATEGY:\n\t\t\t\treturn \"Status of current strategy\";\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\t}\n\n\t@Override\n\tpublic int getLastColumnOfGroup(int groupIndex)\n\t{\n\t\tif (!pathActive) {\n\t\t\treturn 0;\n\t\t} else {\n\t\t\treturn visibleGroups.get(groupIndex).lastCol;\n\t\t}\n\t}\n\n\t@Override\n\tpublic int getColumnCount()\n\t{\n\t\tif (!pathActive) {\n\t\t\treturn 0;\n\t\t} else {\n\t\t\treturn visibleColumns.size();\n\t\t}\n\t}\n\n\t@Override\n\tpublic int getRowCount()\n\t{\n\t\t// Return current path size if there is an active path.\n\t\treturn (pathActive ? (int) path.size() + 1 : 0);\n\t}\n\n\tpublic boolean shouldColourRow(int row)\n\t{\n\t\tint selection = simulator.getStateLabelList().getSelectedIndex();\n\t\tif (selection != -1) {\n\t\t\tGUISimLabelList.SimLabel label = (GUISimLabelList.SimLabel) simulator.getStateLabelList().getModel().getElementAt(selection);\n\t\t\tif (row == getRowCount() - 1) {\n\t\t\t\tif (label.getResult() == 1)\n\t\t\t\t\treturn true;\n\t\t\t} else {\n\t\t\t\tif (label.getResult(row) == 1)\n\t\t\t\t\treturn true;\n\t\t\t}\n\t\t}\n\n\t\treturn false;\n\t}\n\n\t@Override\n\tpublic String getColumnName(int columnIndex)\n\t{\n\t\tif (pathActive) {\n\t\t\tswitch (visibleColumns.get(columnIndex).type) {\n\t\t\tcase ACTION:\n\t\t\t\treturn modelInfo.getActionStringDescription();\n\t\t\tcase STEP:\n\t\t\t\treturn \"#\";\n\t\t\tcase TIME_CUMUL:\n\t\t\t\treturn \"Time (+)\";\n\t\t\tcase TIME:\n\t\t\t\treturn \"Time\";\n\t\t\tcase VARIABLE:\n\t\t\t\tVariable var = (Variable) visibleColumns.get(columnIndex).info;\n\t\t\t\treturn var.toString();\n\t\t\tcase OBSERVABLE:\n\t\t\t\tObserv obs = (Observ) visibleColumns.get(columnIndex).info;\n\t\t\t\treturn obs.toString();\n\t\t\tcase REWARD:\n\t\t\t\tRewardStructureColumn rewardColumn = (RewardStructureColumn) visibleColumns.get(columnIndex).info;\n\t\t\t\treturn rewardColumn.getColumnName();\n\t\t\tcase MEMORY:\n\t\t\t\treturn \"Memory\";\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\t\treturn \"\";\n\t}\n\n\t@Override\n\tpublic String getColumnToolTip(int columnIndex)\n\t{\n\t\tif (pathActive) {\n\t\t\tswitch (visibleColumns.get(columnIndex).type) {\n\t\t\tcase ACTION:\n\t\t\t\treturn \"Module name or [action] label\";\n\t\t\tcase STEP:\n\t\t\t\treturn \"Index of state in path\";\n\t\t\tcase TIME_CUMUL:\n\t\t\t\treturn \"Cumulative time\";\n\t\t\tcase TIME:\n\t\t\t\treturn \"Time spent in state\";\n\t\t\tcase VARIABLE:\n\t\t\t\tVariable var = (Variable) visibleColumns.get(columnIndex).info;\n\t\t\t\treturn \"Value of variable \" + var.toString();\n\t\t\tcase OBSERVABLE:\n\t\t\t\tObserv obs = (Observ) visibleColumns.get(columnIndex).info;\n\t\t\t\treturn \"Value of observable \" + obs.toString();\n\t\t\tcase REWARD:\n\t\t\t\tRewardStructureColumn rewardColumn = (RewardStructureColumn) visibleColumns.get(columnIndex).info;\n\t\t\t\tString rewardName = rewardColumn.getRewardStructure().getColumnName();\n\t\t\t\tif (rewardColumn.isStateReward()) {\n\t\t\t\t\treturn \"State reward of reward structure \" + rewardName;\n\t\t\t\t}\n\t\t\t\tif (rewardColumn.isTransitionReward()) {\n\t\t\t\t\treturn \"Transition reward of reward structure \" + rewardName;\n\t\t\t\t}\n\t\t\t\tif (rewardColumn.isCumulativeReward()) {\n\t\t\t\t\treturn \"Cumulative reward of reward structure \" + rewardName;\n\t\t\t\t}\n\t\t\tcase MEMORY:\n\t\t\t\treturn \"Memory of current strategy\";\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\t\treturn \"\";\n\t}\n\n\t@Override\n\tpublic Object getValueAt(int rowIndex, int columnIndex)\n\t{\n\t\tif (pathActive) {\n\t\t\tswitch (visibleColumns.get(columnIndex).type) {\n\t\t\tcase ACTION:\n\t\t\t\t// The action column\n\t\t\t\tactionValue = view.new ActionValue(rowIndex == 0 ? \"\" : path.getActionString(rowIndex - 1));\n\t\t\t\tactionValue.setActionValueUnknown(false);\n\t\t\t\treturn actionValue;\n\t\t\tcase STEP:\n\t\t\t\t// The step column\n\t\t\t\treturn \"\" + rowIndex;\n\t\t\tcase TIME_CUMUL:\n\t\t\t\t// Cumulative time column\n\t\t\t\ttimeValue = view.new TimeValue(path.getCumulativeTime(rowIndex), true);\n\t\t\t\ttimeValue.setTimeValueUnknown(rowIndex > path.size()); // Never unknown\n\t\t\t\treturn timeValue;\n\t\t\tcase TIME:\n\t\t\t\t// Time column\n\t\t\t\ttimeValue = view.new TimeValue(path.getTime(rowIndex), false);\n\t\t\t\ttimeValue.setTimeValueUnknown(rowIndex >= path.size());\n\t\t\t\treturn timeValue;\n\t\t\tcase VARIABLE:\n\t\t\t\t// A variable column\n\t\t\t\tVariable var = (Variable) visibleColumns.get(columnIndex).info;\n\t\t\t\tObject result = path.getState(rowIndex).varValues[var.getIndex()];\n\t\t\t\tvariableValue.setVariable(var);\n\t\t\t\tvariableValue.setValue(result);\n\t\t\t\tvariableValue.setChanged(rowIndex == 0 || !path.getState(rowIndex - 1).varValues[var.getIndex()].equals(result));\n\t\t\t\treturn variableValue;\n\t\t\tcase OBSERVABLE:\n\t\t\t\t// An observable column\n\t\t\t\tObserv obs = (Observ) visibleColumns.get(columnIndex).info;\n\t\t\t\tObject resultO = path.getObservation(rowIndex).varValues[obs.getIndex()];\n\t\t\t\tvariableValue.setVariable(obs);\n\t\t\t\tvariableValue.setValue(resultO);\n\t\t\t\tvariableValue.setChanged(rowIndex == 0 || !path.getObservation(rowIndex - 1).varValues[obs.getIndex()].equals(resultO));\n\t\t\t\treturn variableValue;\n\t\t\tcase REWARD:\n\t\t\t\t// A reward column\n\t\t\t\tRewardStructureColumn rewardColumn = (RewardStructureColumn) visibleColumns.get(columnIndex).info;\n\t\t\t\trewardStructureValue.setRewardStructureColumn(rewardColumn);\n\t\t\t\trewardStructureValue.setRewardValueUnknown(false);\n\t\t\t\t// A state reward column\n\t\t\t\tif (rewardColumn.isStateReward()) {\n\t\t\t\t\tdouble value = path.getStateReward(rowIndex, rewardColumn.getRewardStructure().getIndex());\n\t\t\t\t\trewardStructureValue.setChanged(rowIndex == 0 || value != path.getStateReward(rowIndex - 1, rewardColumn.getRewardStructure().getIndex()));\n\t\t\t\t\trewardStructureValue.setRewardValue(value);\n\t\t\t\t\trewardStructureValue.setRewardValueUnknown(rowIndex > path.size()); // Never unknown\n\t\t\t\t}\n\t\t\t\t// A transition reward column\n\t\t\t\telse if (rewardColumn.isTransitionReward()) {\n\t\t\t\t\tdouble value = path.getTransitionReward(rowIndex, rewardColumn.getRewardStructure().getIndex());\n\t\t\t\t\trewardStructureValue.setChanged(rowIndex == 0 || value != path.getTransitionReward(rowIndex - 1, rewardColumn.getRewardStructure().getIndex()));\n\t\t\t\t\trewardStructureValue.setRewardValue(value);\n\t\t\t\t\trewardStructureValue.setRewardValueUnknown(rowIndex >= path.size());\n\t\t\t\t}\n\t\t\t\t// A cumulative reward column\n\t\t\t\telse {\n\t\t\t\t\tdouble value = path.getCumulativeReward(rowIndex, rewardColumn.getRewardStructure().getIndex());\n\t\t\t\t\trewardStructureValue.setChanged(rowIndex == 0 || value != (path.getCumulativeReward(rowIndex - 1, rewardColumn.getRewardStructure().getIndex())));\n\t\t\t\t\trewardStructureValue.setRewardValue(value);\n\t\t\t\t\trewardStructureValue.setRewardValueUnknown(rowIndex > path.size()); // Never unknown\n\t\t\t\t}\n\t\t\t\treturn rewardStructureValue;\n\t\t\tcase MEMORY:\n\t\t\t\tint memory = path.getStrategyMemory(rowIndex);\n\t\t\t\tString memoryString = simulator.getSimulatorEngine().getStrategy().getMemoryString(memory);\n\t\t\t\tmemoryValue = view.new MemoryValue(memoryString);\n\t\t\t\tmemoryValue.setMemoryValueUnknown(rowIndex > path.size()); // Never unknown\n\t\t\t\treturn memoryValue;\n\t\t\tdefault:\n\t\t\t\treturn \"\";\n\t\t\t}\n\t\t}\n\t\treturn \"\";\n\t}\n\n\t/** \n\t * Method is called when a new path is created.\n\t * The structure of the path may be for a different model etc.\n\t */\n\tpublic void restartPathTable()\n\t{\n\t\tview.refreshToDefaultView(pathActive, parsedModel);\n\t\t// NB: since we observe view, the above will trigger update(),\n\t\t// which calls setVisibleColumns() etc.\n\t}\n\n\t/** \n\t * Method is called whenever a path is modified.\n\t */\n\tpublic void updatePathTable()\n\t{\n\t\tsetVisibleColumnsAndGroups();\n\t\tfireTableStructureChanged();\n\t\tfireTableDataChanged();\n\t}\n\n\t/**\n\t * Set up the info about table columns/groups\n\t */\n\tpublic void setVisibleColumnsAndGroups()\n\t{\n\t\tvisibleColumns.clear();\n\t\tvisibleGroups.clear();\n\t\tif (pathActive) {\n\t\t\t// Step\n\t\t\tif (view.showActions() || view.showSteps()) {\n\t\t\t\tif (view.showActions()) {\n\t\t\t\t\tvisibleColumns.add(new PathTableModelColumn(GUISimulatorPathTableModelColumn.ACTION, null));\n\t\t\t\t}\n\t\t\t\tif (view.showSteps()) {\n\t\t\t\t\tvisibleColumns.add(new PathTableModelColumn(GUISimulatorPathTableModelColumn.STEP, null));\n\t\t\t\t}\n\t\t\t\tvisibleGroups.add(new PathTableModelGroup(PathTableModelGroupType.STEP, null, visibleColumns.size() - 1));\n\t\t\t}\n\t\t\t// Time\n\t\t\tif (canShowTime() && (view.showTime() || view.showCumulativeTime())) {\n\t\t\t\tif (view.showCumulativeTime()) {\n\t\t\t\t\tvisibleColumns.add(new PathTableModelColumn(GUISimulatorPathTableModelColumn.TIME_CUMUL, null));\n\t\t\t\t}\n\t\t\t\tif (view.showTime()) {\n\t\t\t\t\tvisibleColumns.add(new PathTableModelColumn(GUISimulatorPathTableModelColumn.TIME, null));\n\t\t\t\t}\n\t\t\t\tvisibleGroups.add(new PathTableModelGroup(PathTableModelGroupType.TIME, null, visibleColumns.size() - 1));\n\t\t\t}\n\t\t\t// Variables\n\t\t\tif (view.getVisibleVariables().size() > 0) {\n\t\t\t\tint numVars = view.getVisibleVariables().size();\n\t\t\t\tfor (int i = 0; i < numVars; i++) {\n\t\t\t\t\tVariable v = view.getVisibleVariables().get(i);\n\t\t\t\t\tvisibleColumns.add(new PathTableModelColumn(GUISimulatorPathTableModelColumn.VARIABLE, v));\n\t\t\t\t\t// If module changes between vars (or this is last var), put these ones in a column group\n\t\t\t\t\tif ((i == numVars - 1) || (v.getModuleIndex() != view.getVisibleVariables().get(i + 1).getModuleIndex())) {\n\t\t\t\t\t\tvisibleGroups.add(new PathTableModelGroup(PathTableModelGroupType.VARIABLES, v.getModuleIndex(), visibleColumns.size() - 1));\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Variables\n\t\t\tif (view.getVisibleObservables().size() > 0) {\n\t\t\t\tfor (Observ o : view.getVisibleObservables()) {\n\t\t\t\t\tvisibleColumns.add(new PathTableModelColumn(GUISimulatorPathTableModelColumn.OBSERVABLE, o));\n\t\t\t\t}\n\t\t\t\tvisibleGroups.add(new PathTableModelGroup(PathTableModelGroupType.OBSERVABLES, null, visibleColumns.size() - 1));\n\t\t\t}\n\t\t\t// Rewards\n\t\t\tif (view.getVisibleRewardColumns().size() > 0) {\n\t\t\t\tfor (RewardStructureColumn rsc : view.getVisibleRewardColumns()) {\n\t\t\t\t\tvisibleColumns.add(new PathTableModelColumn(GUISimulatorPathTableModelColumn.REWARD, rsc));\n\t\t\t\t}\n\t\t\t\tvisibleGroups.add(new PathTableModelGroup(PathTableModelGroupType.REWARDS, null, visibleColumns.size() - 1));\n\t\t\t}\n\t\t\t// Strategy\n\t\t\tif (simulator.isStrategyShown()) {\n\t\t\t\tStrategyGenerator stratGen = simulator.getSimulatorEngine().getStrategy();\n\t\t\t\tif (stratGen != null && stratGen.hasMemory()) {\n\t\t\t\t\tvisibleColumns.add(new PathTableModelColumn(GUISimulatorPathTableModelColumn.MEMORY, null));\n\t\t\t\t\tvisibleGroups.add(new PathTableModelGroup(PathTableModelGroupType.STRATEGY, null, visibleColumns.size() - 1));\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\t\n\tpublic boolean isPathLooping()\n\t{\n\t\treturn path.isLooping();\n\t}\n\n\tpublic int getLoopStart()\n\t{\n\t\treturn (int) path.loopStart();\n\t}\n\n\tpublic int getLoopEnd()\n\t{\n\t\treturn (int) path.loopEnd();\n\t}\n\n\tpublic SimulationView getView()\n\t{\n\t\treturn view;\n\t}\n\n\tpublic void setView(SimulationView view)\n\t{\n\t\tthis.view.deleteObserver(this);\n\t\tthis.view = view;\n\t\tthis.view.addObserver(this);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUISimulatorUpdatesTable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport java.awt.Color;\nimport java.awt.Component;\nimport java.awt.Font;\nimport java.awt.event.ActionEvent;\nimport java.awt.event.KeyEvent;\n\nimport javax.swing.AbstractAction;\nimport javax.swing.AbstractListModel;\nimport javax.swing.ActionMap;\nimport javax.swing.ComponentInputMap;\nimport javax.swing.ImageIcon;\nimport javax.swing.InputMap;\nimport javax.swing.JButton;\nimport javax.swing.JComponent;\nimport javax.swing.JList;\nimport javax.swing.JPanel;\nimport javax.swing.JTable;\nimport javax.swing.JTextField;\nimport javax.swing.KeyStroke;\nimport javax.swing.ListCellRenderer;\nimport javax.swing.ListSelectionModel;\nimport javax.swing.border.EmptyBorder;\nimport javax.swing.event.ListSelectionEvent;\nimport javax.swing.event.ListSelectionListener;\nimport javax.swing.table.TableCellRenderer;\n\nimport userinterface.GUIPrism;\n\n@SuppressWarnings(\"serial\")\npublic class GUISimulatorUpdatesTable extends JTable implements ListSelectionListener\n{\n\tpublic static Color[] DISTRIBUTION_COLOURS = {\n\t\tnew Color(255, 255, 255), // white\n\t\tnew Color(253, 255, 201) // yellow\n\t};\n\tpublic static Color[] DISABLED_COLOURS = {\n\t\tnew Color(210, 210, 210), // pale grey\n\t\tnew Color(190, 190, 190) // pale-ish grey\n\t};\n\t\n\tprivate GUISimulator.UpdateTableModel utm;\n\n\tprivate UpdateHeaderListModel headerModel;\n\tprivate JList<String> header;\n\tprivate UpdateHeaderRenderer updateHeaderRenderer;\n\tprivate UpdateTableRenderer updateTableRenderer;\n\n\tprivate GUISimulator sim;\n\n\t/** Creates a new instance of GUISimulatorUpdatesTable */\n\tpublic GUISimulatorUpdatesTable(GUISimulator.UpdateTableModel utm, GUISimulator sim)\n\t{\n\t\tsuper(utm);\n\t\tthis.sim = sim;\n\t\tthis.utm = utm;\n\n\t\tthis.getSelectionModel().addListSelectionListener(this);\n\n\t\tsetColumnSelectionAllowed(false);\n\t\tgetSelectionModel().setSelectionMode(ListSelectionModel.SINGLE_SELECTION);\n\n\t\theaderModel = new UpdateHeaderListModel();\n\t\tJList<String> rowHeader = new JList<>(headerModel);\n\n\t\trowHeader.setBackground(new JPanel().getBackground());\n\n\t\trowHeader.setFixedCellWidth(15);\n\n\t\trowHeader.setFixedCellHeight(getRowHeight());\n\t\t//+ getRowMargin());\n\t\t//getIntercellSpacing().height);\n\t\tupdateHeaderRenderer = new UpdateHeaderRenderer(this);\n\t\trowHeader.setCellRenderer(updateHeaderRenderer);\n\n\t\tthis.header = rowHeader;\n\n\t\tupdateTableRenderer = new UpdateTableRenderer();\n\t\tsetDefaultRenderer(Object.class, updateTableRenderer);\n\n\t\tsetAutoResizeMode(JTable.AUTO_RESIZE_LAST_COLUMN);\n\n\t\tInputMap inputMap = new ComponentInputMap(this);\n\n\t\tinputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_DOWN, 0), \"Down\");\n\t\tinputMap.put(KeyStroke.getKeyStroke(KeyEvent.VK_UP, 0), \"Up\");\n\n\t\tActionMap actionMap = new ActionMap();\n\n\t\tactionMap.put(\"Down\", new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tint selectedRow = GUISimulatorUpdatesTable.this.getSelectedRow();\n\t\t\t\tif (selectedRow != -1) {\n\t\t\t\t\tif (selectedRow < GUISimulatorUpdatesTable.this.getRowCount() - 1)\n\t\t\t\t\t\tGUISimulatorUpdatesTable.this.getSelectionModel().setSelectionInterval(selectedRow + 1, selectedRow + 1);\n\t\t\t\t\telse\n\t\t\t\t\t\tGUISimulatorUpdatesTable.this.getSelectionModel().setSelectionInterval(0, 0);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\tactionMap.put(\"Up\", new AbstractAction()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\tint selectedRow = GUISimulatorUpdatesTable.this.getSelectedRow();\n\t\t\t\tif (selectedRow != -1) {\n\t\t\t\t\tif (selectedRow >= 1)\n\t\t\t\t\t\tGUISimulatorUpdatesTable.this.getSelectionModel().setSelectionInterval(selectedRow - 1, selectedRow - 1);\n\t\t\t\t\telse\n\t\t\t\t\t\tGUISimulatorUpdatesTable.this.getSelectionModel().setSelectionInterval(GUISimulatorUpdatesTable.this.getRowCount() - 1,\n\t\t\t\t\t\t\t\tGUISimulatorUpdatesTable.this.getRowCount() - 1);\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\n\t\tthis.setInputMap(JComponent.WHEN_FOCUSED, inputMap);\n\t\tthis.setActionMap(actionMap);\n\t}\n\n\t/** Override set font to pass changes onto renderer(s) and set row height */\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\tif (updateTableRenderer != null)\n\t\t\tupdateTableRenderer.setFont(font);\n\t\tsetRowHeight(getFontMetrics(font).getHeight() + 4);\n\t\tif (header != null)\n\t\t\theader.setFixedCellHeight(getRowHeight());\n\t}\n\n\tpublic void valueChanged(ListSelectionEvent e)\n\t{\n\t\tif (headerModel != null)\n\t\t\theaderModel.updateHeader();\n\t\trepaint();\n\t}\n\n\tpublic JList<String> getUpdateRowHeader()\n\t{\n\t\treturn header;\n\t}\n\n\tclass UpdateTableRenderer implements TableCellRenderer\n\t{\n\t\tJTextField renderer;\n\n\t\tpublic UpdateTableRenderer()\n\t\t{\n\t\t\trenderer = new JTextField(\"\");\n\t\t}\n\n\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t\t{\n\t\t\t// Pick colour for row\n\t\t\tColor bgCol;\n\t\t\t// Enabled\n\t\t\tif (!sim.isStrategyShown() || utm.isEnabledByStrategy(row)) {\n\t\t\t\t// Colours alternate for nondet models\n\t\t\t\tif (utm.isNondetModel()) {\n\t\t\t\t\tbgCol = DISTRIBUTION_COLOURS[utm.getChoiceIndexOf(row) % 2];\n\t\t\t\t} else {\n\t\t\t\t\tbgCol = DISTRIBUTION_COLOURS[0];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Disabled\n\t\t\telse {\n\t\t\t\t// Colours alternate for nondet models\n\t\t\t\tif (utm.isNondetModel()) {\n\t\t\t\t\tbgCol = DISABLED_COLOURS[utm.getChoiceIndexOf(row) % 2];\n\t\t\t\t} else {\n\t\t\t\t\tbgCol = DISABLED_COLOURS[0];\n\t\t\t\t}\n\t\t\t}\n\t\t\t// Darker (blue) shade if row is selected\n\t\t\tif (isSelected) {\n\t\t\t\tbgCol = new Color(bgCol.getRed() - 20, bgCol.getGreen() - 20, bgCol.getBlue());\n\t\t\t}\n\t\t\t// Slightly darker if an old update\n\t\t\tif (utm.oldUpdate) {\n\t\t\t\tbgCol = new Color(bgCol.getRed() - 7, bgCol.getGreen() - 7, bgCol.getBlue() - 7);\n\t\t\t}\n\t\t\trenderer.setText(value == null ? \"\" : value.toString());\n\t\t\trenderer.setBackground(bgCol);\n\t\t\trenderer.setBorder(new EmptyBorder(1, 1, 1, 1));\n\t\t\treturn renderer;\n\t\t}\n\n\t\tpublic void setFont(Font font)\n\t\t{\n\t\t\trenderer.setFont(font);\n\t\t}\n\t}\n\n\tclass UpdateHeaderRenderer extends JButton implements ListCellRenderer<String>\n\t{\n\n\t\tImageIcon selectedIcon;\n\t\tImageIcon selectedDisabledIcon;\n\n\t\tUpdateHeaderRenderer(JTable table)\n\t\t{\n\t\t\t/*JTableHeader header = table.getTableHeader();\n\t\t\t setOpaque(true);\n\t\t\t setBorder(UIManager.getBorder(\"TableHeader.cellBorder\"));\n\t\t\t setHorizontalAlignment(CENTER);\n\t\t\t setForeground(header.getForeground());\n\t\t\t setBackground(header.getBackground());\n\t\t\t setFont(header.getFont());*/\n\t\t\tsetBorder(null);\n\t\t\tselectedIcon = GUIPrism.getIconFromImage(\"smallItemSelected.png\");\n\t\t\tselectedDisabledIcon = GUIPrism.getIconFromImage(\"smallItemSelectedDisabled.png\");\n\t\t}\n\n\t\t@Override\n\t\tpublic Component getListCellRendererComponent(JList<? extends String> list, String value, int index, boolean isSelected, boolean cellHasFocus)\n\t\t{\n\t\t\tsetBorder(null);\n\t\t\tif (getSelectedRow() == index) {\n\t\t\t\tif (GUISimulatorUpdatesTable.this.isEnabled())\n\t\t\t\t\tsetIcon(selectedIcon);\n\t\t\t\telse\n\t\t\t\t\tsetIcon(selectedDisabledIcon);\n\t\t\t} else {\n\t\t\t\tsetIcon(null);\n\t\t\t}\n\t\t\treturn this;\n\t\t}\n\t}\n\n\tclass UpdateHeaderListModel extends AbstractListModel<String>\n\t{\n\t\tpublic String getElementAt(int index)\n\t\t{\n\t\t\treturn \"\" + index;\n\t\t}\n\n\t\tpublic int getSize()\n\t\t{\n\t\t\treturn utm.getRowCount();\n\t\t}\n\n\t\tpublic void updateHeader()\n\t\t{\n\t\t\tfireContentsChanged(this, 0, utm.getRowCount());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUITimeDialog.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"2\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,0,-81,0,0,1,-95\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"allPanel\">\n      <Properties>\n        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n          </Border>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"bottomPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"South\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Component class=\"javax.swing.JLabel\" name=\"warningLabel\">\n              <Properties>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Please enter a valid positive double\"/>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"0\" left=\"5\" right=\"0\" top=\"0\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n            <Container class=\"javax.swing.JPanel\" name=\"buttonPanel\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"East\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n                <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n              </Layout>\n              <SubComponents>\n                <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n          <Properties>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                <TitledBorder title=\"Time spent in state\"/>\n              </Border>\n            </Property>\n          </Properties>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"timeInputPanel\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"North\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                <Property name=\"columns\" type=\"int\" value=\"2\"/>\n                <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                <Property name=\"rows\" type=\"int\" value=\"1\"/>\n                <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n              </Layout>\n              <SubComponents>\n                <Component class=\"javax.swing.JLabel\" name=\"inputLabel\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Provide a time:\"/>\n                  </Properties>\n                </Component>\n                <Component class=\"javax.swing.JTextField\" name=\"timeInputField\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"1.0\"/>\n                  </Properties>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUITimeDialog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport javax.swing.*;\n\nimport java.awt.*;\nimport javax.swing.event.DocumentEvent;\nimport javax.swing.event.DocumentListener;\nimport userinterface.*;\n\npublic class GUITimeDialog extends JDialog\n{\n\tprivate static final long serialVersionUID = 1L;\n\t\n\t//ATTRIBUTES    \n\tprivate double time;\n\tprivate boolean cancelled;\n\n\tprivate static double lastTime = 1.0d;\n\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tprivate javax.swing.JPanel allPanel;\n\tprivate javax.swing.JPanel bottomPanel;\n\tprivate javax.swing.JPanel buttonPanel;\n\tprivate javax.swing.JButton cancelButton;\n\tprivate javax.swing.JLabel inputLabel;\n\tprivate javax.swing.JButton okayButton;\n\tprivate javax.swing.JTextField timeInputField;\n\tprivate javax.swing.JPanel timeInputPanel;\n\tprivate javax.swing.JPanel topPanel;\n\tprivate javax.swing.JLabel warningLabel;\n\n\t// End of variables declaration//GEN-END:variables\n\n\t/** Creates new form GUIConstantsPicker */\n\tprivate GUITimeDialog(GUIPrism parent, GUISimulator simulator)\n\t{\n\t\tsuper(parent, \"Provide a time\", true);\n\n\t\t//initialise\n\t\tinitComponents();\n\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\n\t\tthis.time = lastTime;\n\t\tthis.cancelled = false;\n\n\t\tthis.timeInputField.setText(\"\" + time);\n\n\t\tthis.warningLabel.setIcon(GUIPrism.getIconFromImage(\"smallError.png\"));\n\t\tthis.warningLabel.setVisible(false);\n\n\t\tthis.timeInputField.getDocument().addDocumentListener(new DocumentListener()\n\t\t{\n\t\t\tpublic void changedUpdate(DocumentEvent e)\n\t\t\t{\n\t\t\t\ttry {\n\t\t\t\t\tDouble.parseDouble(timeInputField.getText());\n\t\t\t\t\tGUITimeDialog.this.warningLabel.setVisible(false);\n\t\t\t\t\tGUITimeDialog.this.okayButton.setEnabled(true);\n\t\t\t\t} catch (NumberFormatException nfe) {\n\t\t\t\t\tGUITimeDialog.this.warningLabel.setVisible(true);\n\t\t\t\t\tGUITimeDialog.this.okayButton.setEnabled(false);\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tpublic void removeUpdate(DocumentEvent e)\n\t\t\t{\n\t\t\t\tchangedUpdate(e);\n\t\t\t}\n\n\t\t\tpublic void insertUpdate(DocumentEvent e)\n\t\t\t{\n\t\t\t\tchangedUpdate(e);\n\t\t\t}\n\t\t});\n\n\t\tsuper.setBounds(new Rectangle(550, 300));\n\t\tsetResizable(true);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\n\t\tthis.setVisible(true);\n\t}\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\t// <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n\tprivate void initComponents()\n\t{\n\t\tallPanel = new javax.swing.JPanel();\n\t\tbottomPanel = new javax.swing.JPanel();\n\t\twarningLabel = new javax.swing.JLabel();\n\t\tbuttonPanel = new javax.swing.JPanel();\n\t\tokayButton = new javax.swing.JButton();\n\t\tcancelButton = new javax.swing.JButton();\n\t\ttopPanel = new javax.swing.JPanel();\n\t\ttimeInputPanel = new javax.swing.JPanel();\n\t\tinputLabel = new javax.swing.JLabel();\n\t\ttimeInputField = new javax.swing.JTextField();\n\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\n\t\tallPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tallPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tbottomPanel.setLayout(new java.awt.BorderLayout());\n\n\t\twarningLabel.setText(\"Please enter a valid positive double\");\n\t\twarningLabel.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 5, 0, 0));\n\t\tbottomPanel.add(warningLabel, java.awt.BorderLayout.CENTER);\n\n\t\tbuttonPanel.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tokayButton.setText(\"Okay\");\n\t\tokayButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tokayButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tbuttonPanel.add(okayButton);\n\n\t\tcancelButton.setText(\"Cancel\");\n\t\tcancelButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tcancelButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tbuttonPanel.add(cancelButton);\n\n\t\tbottomPanel.add(buttonPanel, java.awt.BorderLayout.EAST);\n\n\t\tallPanel.add(bottomPanel, java.awt.BorderLayout.SOUTH);\n\n\t\ttopPanel.setLayout(new java.awt.BorderLayout());\n\n\t\ttopPanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Time spent in state\"));\n\t\ttimeInputPanel.setLayout(new java.awt.GridLayout(1, 2, 5, 5));\n\n\t\ttimeInputPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tinputLabel.setText(\"Provide a time:\");\n\t\ttimeInputPanel.add(inputLabel);\n\n\t\ttimeInputField.setText(\"1.0\");\n\t\ttimeInputPanel.add(timeInputField);\n\n\t\ttopPanel.add(timeInputPanel, java.awt.BorderLayout.NORTH);\n\n\t\tallPanel.add(topPanel, java.awt.BorderLayout.CENTER);\n\n\t\tgetContentPane().add(allPanel, java.awt.BorderLayout.CENTER);\n\n\t}// </editor-fold>//GEN-END:initComponents\n\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\t\ttry {\n\t\t\ttime = Double.parseDouble(timeInputField.getText());\n\t\t} catch (NumberFormatException nfe) { // Shouldn't happen.\n\t\t\tcancelled = true;\n\t\t}\n\t\tdispose();\n\t}//GEN-LAST:event_okayButtonActionPerformed\n\n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\t\tcancelled = true;\n\t\tdispose();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\n\tpublic boolean isCancelled()\n\t{\n\t\treturn cancelled;\n\t}\n\n\tpublic double getTime()\n\t{\n\t\treturn time;\n\t}\n\n\t/** Returns a time, or -1 for cancel. */\n\tpublic static double askTime(GUIPrism prism, GUISimulator simulator)\n\t{\n\t\tGUITimeDialog dialog = new GUITimeDialog(prism, simulator);\n\n\t\tif (dialog.isCancelled()) {\n\t\t\treturn -1;\n\t\t} else {\n\t\t\tGUITimeDialog.lastTime = dialog.time;\n\t\t\treturn dialog.time;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUIViewDialog.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.2\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <NonVisualComponents>\n    <Component class=\"javax.swing.JLabel\" name=\"visibleLabel\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"0\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Visible Variables\"/>\n      </Properties>\n    </Component>\n    <Component class=\"javax.swing.JLabel\" name=\"hiddenLabel\">\n      <Properties>\n        <Property name=\"horizontalAlignment\" type=\"int\" value=\"0\"/>\n        <Property name=\"text\" type=\"java.lang.String\" value=\"Hidden Variables\"/>\n      </Properties>\n    </Component>\n    <Component class=\"javax.swing.ButtonGroup\" name=\"pathStyle\">\n    </Component>\n  </NonVisualComponents>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"2\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"FormSettings_generateMnemonicsCode\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_listenerGenerationStyle\" type=\"java.lang.Integer\" value=\"0\"/>\n    <AuxValue name=\"FormSettings_variablesLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n    <AuxValue name=\"FormSettings_variablesModifier\" type=\"java.lang.Integer\" value=\"2\"/>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,44,0,0,2,38\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"allPanel\">\n      <Properties>\n        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n          </Border>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"bottomPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"South\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"buttonPanel\">\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"East\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n                <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n              </Layout>\n              <SubComponents>\n                <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Okay\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"okayButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n                <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n                  <Properties>\n                    <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n                  </Properties>\n                  <Events>\n                    <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"cancelButtonActionPerformed\"/>\n                  </Events>\n                </Component>\n              </SubComponents>\n            </Container>\n            <Component class=\"javax.swing.JCheckBox\" name=\"optionCheckBox\">\n              <Properties>\n                <Property name=\"label\" type=\"java.lang.String\" value=\"Always prompt for view configuration on path creation\"/>\n              </Properties>\n              <AccessibilityProperties>\n                <Property name=\"AccessibleContext.accessibleName\" type=\"java.lang.String\" value=\"optionCheckBox\"/>\n              </AccessibilityProperties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"West\"/>\n                </Constraint>\n              </Constraints>\n            </Component>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JTabbedPane\" name=\"variableTabPane\">\n      <Properties>\n        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n          </Border>\n        </Property>\n      </Properties>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"variableTabPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Variable visibility\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Variable visibility\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"variablePanel\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"leftVariableColumn\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Visible variables\"/>\n                      </Border>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"2\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.5\" weightY=\"1.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"leftVariablePanel\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\">\n                        <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                      </Layout>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JScrollPane\" name=\"visibleVariableScrollList\">\n                          <Properties>\n                            <Property name=\"horizontalScrollBarPolicy\" type=\"int\" value=\"31\"/>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"Center\"/>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                          <SubComponents>\n                            <Component class=\"javax.swing.JList\" name=\"visibleVariableList\">\n                            </Component>\n                          </SubComponents>\n                        </Container>\n                        <Component class=\"javax.swing.JButton\" name=\"selectAllVisibleVariablesButton\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Select All\"/>\n                          </Properties>\n                          <Events>\n                            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"selectAllVisibleVariablesButtonActionPerformed\"/>\n                          </Events>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"South\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"centerVariableColumn\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"3\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"1.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"centerVariablePanel\">\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n                      <SubComponents>\n                        <Component class=\"javax.swing.JButton\" name=\"makeVariableVisibleButton\">\n                          <Events>\n                            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"makeVariableVisibleButtonActionPerformed\"/>\n                          </Events>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                              <GridBagConstraints gridX=\"0\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"5\" insetsTop=\"3\" insetsLeft=\"10\" insetsBottom=\"3\" insetsRight=\"10\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                        <Component class=\"javax.swing.JButton\" name=\"makeVariableHiddenButton\">\n                          <Events>\n                            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"makeVariableHiddenButtonActionPerformed\"/>\n                          </Events>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                              <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"5\" insetsTop=\"3\" insetsLeft=\"10\" insetsBottom=\"3\" insetsRight=\"10\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"rightVariableColumn\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Hidden variables\"/>\n                      </Border>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"0\" gridWidth=\"2\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.5\" weightY=\"1.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"rightVariablePanel\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\">\n                        <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                      </Layout>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JScrollPane\" name=\"hiddenVariableScrollList\">\n                          <Properties>\n                            <Property name=\"horizontalScrollBarPolicy\" type=\"int\" value=\"31\"/>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"Center\"/>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                          <SubComponents>\n                            <Component class=\"javax.swing.JList\" name=\"hiddenVariableList\">\n                            </Component>\n                          </SubComponents>\n                        </Container>\n                        <Component class=\"javax.swing.JButton\" name=\"selectAllHiddenVariablesButton\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Select All\"/>\n                          </Properties>\n                          <Events>\n                            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"selectAllHiddenVariablesButtonActionPerformed\"/>\n                          </Events>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"South\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"rewardTabPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Reward visibility\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Reward visibility\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"rewardPanel\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"leftRewardColumn\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Visible reward structures\"/>\n                      </Border>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"0\" gridY=\"0\" gridWidth=\"2\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.5\" weightY=\"1.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"leftRewardPanel\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\">\n                        <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                      </Layout>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JScrollPane\" name=\"visibleRewardScrollList\">\n                          <Properties>\n                            <Property name=\"horizontalScrollBarPolicy\" type=\"int\" value=\"31\"/>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"Center\"/>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                          <SubComponents>\n                            <Component class=\"javax.swing.JList\" name=\"visibleRewardList\">\n                            </Component>\n                          </SubComponents>\n                        </Container>\n                        <Component class=\"javax.swing.JButton\" name=\"selectAllVisibleRewardsButton\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Select All\"/>\n                          </Properties>\n                          <Events>\n                            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"selectAllVisibleRewardsButtonActionPerformed\"/>\n                          </Events>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"South\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"centerRewardColumn\">\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"2\" gridY=\"0\" gridWidth=\"1\" gridHeight=\"1\" fill=\"3\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.0\" weightY=\"1.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"centerRewardPanel\">\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\"/>\n                      <SubComponents>\n                        <Component class=\"javax.swing.JButton\" name=\"makeRewardVisibleButton\">\n                          <Events>\n                            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"makeRewardVisibleButtonActionPerformed\"/>\n                          </Events>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                              <GridBagConstraints gridX=\"0\" gridY=\"1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"5\" insetsTop=\"3\" insetsLeft=\"10\" insetsBottom=\"3\" insetsRight=\"10\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                        <Component class=\"javax.swing.JButton\" name=\"makeRewardHiddenButton\">\n                          <Events>\n                            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"makeRewardHiddenButtonActionPerformed\"/>\n                          </Events>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                              <GridBagConstraints gridX=\"-1\" gridY=\"-1\" gridWidth=\"1\" gridHeight=\"1\" fill=\"0\" ipadX=\"5\" ipadY=\"5\" insetsTop=\"3\" insetsLeft=\"10\" insetsBottom=\"3\" insetsRight=\"10\" anchor=\"10\" weightX=\"0.0\" weightY=\"0.0\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"rightRewardColumn\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Hidden reward structures\"/>\n                      </Border>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignGridBagLayout$GridBagConstraintsDescription\">\n                      <GridBagConstraints gridX=\"3\" gridY=\"0\" gridWidth=\"2\" gridHeight=\"1\" fill=\"1\" ipadX=\"0\" ipadY=\"0\" insetsTop=\"0\" insetsLeft=\"0\" insetsBottom=\"0\" insetsRight=\"0\" anchor=\"10\" weightX=\"0.5\" weightY=\"1.0\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"rightRewardPanel\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\">\n                        <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                      </Layout>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JScrollPane\" name=\"hiddenRewardScrollList\">\n                          <Properties>\n                            <Property name=\"horizontalScrollBarPolicy\" type=\"int\" value=\"31\"/>\n                          </Properties>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"Center\"/>\n                            </Constraint>\n                          </Constraints>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                          <SubComponents>\n                            <Component class=\"javax.swing.JList\" name=\"hiddenRewardList\">\n                            </Component>\n                          </SubComponents>\n                        </Container>\n                        <Component class=\"javax.swing.JButton\" name=\"selectAllHiddenRewardsButton\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Select All\"/>\n                          </Properties>\n                          <Events>\n                            <EventHandler event=\"actionPerformed\" listener=\"java.awt.event.ActionListener\" parameters=\"java.awt.event.ActionEvent\" handler=\"selectAllHiddenRewardsButtonActionPerformed\"/>\n                          </Events>\n                          <Constraints>\n                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                              <BorderConstraints direction=\"South\"/>\n                            </Constraint>\n                          </Constraints>\n                        </Component>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"otherTabPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Other\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Other\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"boxPanel\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                    <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                  </Border>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"North\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\">\n                <Property name=\"axis\" type=\"int\" value=\"1\"/>\n              </Layout>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"innerTimePanel\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Time properties\"/>\n                      </Border>\n                    </Property>\n                  </Properties>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"topInnerTimePanel\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"North\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                        <Property name=\"columns\" type=\"int\" value=\"1\"/>\n                        <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                        <Property name=\"rows\" type=\"int\" value=\"2\"/>\n                        <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                      </Layout>\n                      <SubComponents>\n                        <Component class=\"javax.swing.JCheckBox\" name=\"showTimeCheckBox\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Show the time spent in states\"/>\n                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                <EmptyBorder bottom=\"0\" left=\"0\" right=\"0\" top=\"0\"/>\n                              </Border>\n                            </Property>\n                            <Property name=\"margin\" type=\"java.awt.Insets\" editor=\"org.netbeans.beaninfo.editors.InsetsEditor\">\n                              <Insets value=\"[0, 0, 0, 0]\"/>\n                            </Property>\n                          </Properties>\n                          <AccessibilityProperties>\n                            <Property name=\"AccessibleContext.accessibleName\" type=\"java.lang.String\" value=\"\"/>\n                          </AccessibilityProperties>\n                        </Component>\n                        <Component class=\"javax.swing.JCheckBox\" name=\"showCumulativeTimeCheckBox\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Show the cumulative time\"/>\n                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                <EmptyBorder bottom=\"0\" left=\"0\" right=\"0\" top=\"0\"/>\n                              </Border>\n                            </Property>\n                            <Property name=\"margin\" type=\"java.awt.Insets\" editor=\"org.netbeans.beaninfo.editors.InsetsEditor\">\n                              <Insets value=\"[0, 0, 0, 0]\"/>\n                            </Property>\n                          </Properties>\n                        </Component>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"pathStylePanel\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Path style\"/>\n                      </Border>\n                    </Property>\n                  </Properties>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"innerPathStylePanel\">\n                      <Properties>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                            <EmptyBorder bottom=\"5\" left=\"5\" right=\"5\" top=\"5\"/>\n                          </Border>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"North\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n                        <Property name=\"columns\" type=\"int\" value=\"1\"/>\n                        <Property name=\"horizontalGap\" type=\"int\" value=\"5\"/>\n                        <Property name=\"rows\" type=\"int\" value=\"2\"/>\n                        <Property name=\"verticalGap\" type=\"int\" value=\"5\"/>\n                      </Layout>\n                      <SubComponents>\n                        <Component class=\"javax.swing.JRadioButton\" name=\"changeRenderingButton\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Render changes\"/>\n                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                <EmptyBorder bottom=\"0\" left=\"0\" right=\"0\" top=\"0\"/>\n                              </Border>\n                            </Property>\n                            <Property name=\"margin\" type=\"java.awt.Insets\" editor=\"org.netbeans.beaninfo.editors.InsetsEditor\">\n                              <Insets value=\"[0, 0, 0, 0]\"/>\n                            </Property>\n                          </Properties>\n                        </Component>\n                        <Component class=\"javax.swing.JRadioButton\" name=\"renderAllButton\">\n                          <Properties>\n                            <Property name=\"text\" type=\"java.lang.String\" value=\"Render all values\"/>\n                            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                              <Border info=\"org.netbeans.modules.form.compat2.border.EmptyBorderInfo\">\n                                <EmptyBorder bottom=\"0\" left=\"0\" right=\"0\" top=\"0\"/>\n                              </Border>\n                            </Property>\n                            <Property name=\"margin\" type=\"java.awt.Insets\" editor=\"org.netbeans.beaninfo.editors.InsetsEditor\">\n                              <Insets value=\"[0, 0, 0, 0]\"/>\n                            </Property>\n                          </Properties>\n                        </Component>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/simulator/GUIViewDialog.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport prism.*;\n\nimport javax.swing.*;\n\nimport java.awt.*;\nimport java.util.*;\nimport java.awt.event.*;\nimport userinterface.*;\nimport userinterface.simulator.SimulationView.Variable;\nimport userinterface.simulator.SimulationView.*;\n\npublic class GUIViewDialog extends JDialog implements KeyListener\n{\n\tprivate static final long serialVersionUID = 1L;\n\n\t//ATTRIBUTES    \n\tprivate boolean askOption;\n\n\tprivate GUIPrism gui;\n\n\tprivate SimulationView view;\n\n\tprivate VariableListModel visibleVariableListModel;\n\tprivate VariableListModel hiddenVariableListModel;\n\n\tprivate RewardListModel visibleRewardListModel;\n\tprivate RewardListModel hiddenRewardListModel;\n\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tprivate javax.swing.JPanel allPanel;\n\tprivate javax.swing.JPanel bottomPanel;\n\tprivate javax.swing.JPanel boxPanel;\n\tprivate javax.swing.JPanel buttonPanel;\n\tprivate javax.swing.JButton cancelButton;\n\tprivate javax.swing.JPanel centerRewardColumn;\n\tprivate javax.swing.JPanel centerRewardPanel;\n\tprivate javax.swing.JPanel centerVariableColumn;\n\tprivate javax.swing.JPanel centerVariablePanel;\n\tprivate javax.swing.JRadioButton changeRenderingButton;\n\tprivate javax.swing.JLabel hiddenLabel;\n\tprivate javax.swing.JList hiddenRewardList;\n\tprivate javax.swing.JScrollPane hiddenRewardScrollList;\n\tprivate javax.swing.JList hiddenVariableList;\n\tprivate javax.swing.JScrollPane hiddenVariableScrollList;\n\tprivate javax.swing.JPanel innerPathStylePanel;\n\tprivate javax.swing.JPanel innerTimePanel;\n\tprivate javax.swing.JPanel leftRewardColumn;\n\tprivate javax.swing.JPanel leftRewardPanel;\n\tprivate javax.swing.JPanel leftVariableColumn;\n\tprivate javax.swing.JPanel leftVariablePanel;\n\tprivate javax.swing.JButton makeRewardHiddenButton;\n\tprivate javax.swing.JButton makeRewardVisibleButton;\n\tprivate javax.swing.JButton makeVariableHiddenButton;\n\tprivate javax.swing.JButton makeVariableVisibleButton;\n\tprivate javax.swing.JButton okayButton;\n\tprivate javax.swing.JCheckBox optionCheckBox;\n\tprivate javax.swing.JPanel otherTabPanel;\n\tprivate javax.swing.ButtonGroup pathStyle;\n\tprivate javax.swing.JPanel pathStylePanel;\n\tprivate javax.swing.JRadioButton renderAllButton;\n\tprivate javax.swing.JPanel rewardPanel;\n\tprivate javax.swing.JPanel rewardTabPanel;\n\tprivate javax.swing.JPanel rightRewardColumn;\n\tprivate javax.swing.JPanel rightRewardPanel;\n\tprivate javax.swing.JPanel rightVariableColumn;\n\tprivate javax.swing.JPanel rightVariablePanel;\n\tprivate javax.swing.JButton selectAllHiddenRewardsButton;\n\tprivate javax.swing.JButton selectAllHiddenVariablesButton;\n\tprivate javax.swing.JButton selectAllVisibleRewardsButton;\n\tprivate javax.swing.JButton selectAllVisibleVariablesButton;\n\tprivate javax.swing.JCheckBox showCumulativeTimeCheckBox;\n\tprivate javax.swing.JCheckBox showTimeCheckBox;\n\tprivate javax.swing.JPanel topInnerTimePanel;\n\tprivate javax.swing.JPanel variablePanel;\n\tprivate javax.swing.JTabbedPane variableTabPane;\n\tprivate javax.swing.JPanel variableTabPanel;\n\tprivate javax.swing.JLabel visibleLabel;\n\tprivate javax.swing.JList visibleRewardList;\n\tprivate javax.swing.JScrollPane visibleRewardScrollList;\n\tprivate javax.swing.JList visibleVariableList;\n\tprivate javax.swing.JScrollPane visibleVariableScrollList;\n\n\t// End of variables declaration//GEN-END:variables\n\n\t/**\n\t * Creates new form GUIViewDialog\n\t */\n\tpublic GUIViewDialog(GUIPrism parent, SimulationView view, GUISimulatorPathTableModel pathTableModel)\n\t{\n\t\tsuper(parent, \"Configure View for Simulation\", true);\n\n\t\tthis.gui = parent;\n\t\tthis.view = view;\n\n\t\t//initialise\n\t\tinitComponents();\n\n\t\tthis.getRootPane().setDefaultButton(okayButton);\n\n\t\tsuper.setBounds(new Rectangle(550, 300));\n\t\tsetResizable(true);\n\t\tsetLocationRelativeTo(getParent()); // centre\n\n\t\tthis.askOption = gui.getPrism().getSettings().getBoolean(PrismSettings.SIMULATOR_NEW_PATH_ASK_VIEW);\n\t\toptionCheckBox.setSelected(this.askOption);\n\n\t\tshowTimeCheckBox.setSelected(view.showTime());\n\t\tshowCumulativeTimeCheckBox.setSelected(view.showCumulativeTime());\n\n\t\tvisibleVariableListModel = new VariableListModel(view.getVisibleVariables());\n\t\thiddenVariableListModel = new VariableListModel(view.getHiddenVariables());\n\n\t\tvisibleVariableList.setModel(visibleVariableListModel);\n\t\thiddenVariableList.setModel(hiddenVariableListModel);\n\n\t\tArrayList<RewardListItem> visibleRewardColumn = new ArrayList<RewardListItem>();\n\t\tArrayList<RewardListItem> hiddenRewardColumn = new ArrayList<RewardListItem>();\n\n\t\tfor (RewardStructure reward : view.getRewards()) {\n\t\t\thiddenRewardColumn.add(new RewardListItem(reward, false));\n\t\t\thiddenRewardColumn.add(new RewardListItem(reward, true));\n\t\t}\n\n\t\tfor (RewardStructureColumn rewardColumn : view.getVisibleRewardColumns()) {\n\t\t\tfor (RewardListItem rewardListItem : hiddenRewardColumn) {\n\t\t\t\tif (rewardColumn.getRewardStructure().equals(rewardListItem.getRewardStructure())\n\t\t\t\t\t\t&& rewardColumn.isCumulativeReward() == rewardListItem.isCumulative()) {\n\t\t\t\t\tvisibleRewardColumn.add(rewardListItem);\n\t\t\t\t\thiddenRewardColumn.remove(rewardListItem);\n\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tvisibleRewardListModel = new RewardListModel(visibleRewardColumn);\n\t\thiddenRewardListModel = new RewardListModel(hiddenRewardColumn);\n\n\t\tvisibleRewardList.setModel(visibleRewardListModel);\n\t\thiddenRewardList.setModel(hiddenRewardListModel);\n\n\t\tshowCumulativeTimeCheckBox.setEnabled(pathTableModel.canShowTime());\n\t\tshowTimeCheckBox.setEnabled(pathTableModel.canShowTime());\n\n\t\tpathStyle.add(renderAllButton);\n\t\tpathStyle.add(changeRenderingButton);\n\n\t\trenderAllButton.setSelected(!view.isChangeRenderer());\n\t\tchangeRenderingButton.setSelected(view.isChangeRenderer());\n\n\t\tmakeVariableHiddenButton.setIcon(GUIPrism.getIconFromImage(\"smallArrowRight.png\"));\n\t\tmakeRewardHiddenButton.setIcon(GUIPrism.getIconFromImage(\"smallArrowRight.png\"));\n\n\t\tmakeVariableVisibleButton.setIcon(GUIPrism.getIconFromImage(\"smallArrowLeft.png\"));\n\t\tmakeRewardVisibleButton.setIcon(GUIPrism.getIconFromImage(\"smallArrowLeft.png\"));\n\n\t\tthis.setVisible(true);\n\t}\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\t// <editor-fold defaultstate=\"collapsed\" desc=\" Generated Code \">//GEN-BEGIN:initComponents\n\tprivate void initComponents()\n\t{\n\t\tjava.awt.GridBagConstraints gridBagConstraints;\n\n\t\tvisibleLabel = new javax.swing.JLabel();\n\t\thiddenLabel = new javax.swing.JLabel();\n\t\tpathStyle = new javax.swing.ButtonGroup();\n\t\tallPanel = new javax.swing.JPanel();\n\t\tbottomPanel = new javax.swing.JPanel();\n\t\tbuttonPanel = new javax.swing.JPanel();\n\t\tokayButton = new javax.swing.JButton();\n\t\tcancelButton = new javax.swing.JButton();\n\t\toptionCheckBox = new javax.swing.JCheckBox();\n\t\tvariableTabPane = new javax.swing.JTabbedPane();\n\t\tvariableTabPanel = new javax.swing.JPanel();\n\t\tvariablePanel = new javax.swing.JPanel();\n\t\tleftVariableColumn = new javax.swing.JPanel();\n\t\tleftVariablePanel = new javax.swing.JPanel();\n\t\tvisibleVariableScrollList = new javax.swing.JScrollPane();\n\t\tvisibleVariableList = new javax.swing.JList();\n\t\tselectAllVisibleVariablesButton = new javax.swing.JButton();\n\t\tcenterVariableColumn = new javax.swing.JPanel();\n\t\tcenterVariablePanel = new javax.swing.JPanel();\n\t\tmakeVariableVisibleButton = new javax.swing.JButton();\n\t\tmakeVariableHiddenButton = new javax.swing.JButton();\n\t\trightVariableColumn = new javax.swing.JPanel();\n\t\trightVariablePanel = new javax.swing.JPanel();\n\t\thiddenVariableScrollList = new javax.swing.JScrollPane();\n\t\thiddenVariableList = new javax.swing.JList();\n\t\tselectAllHiddenVariablesButton = new javax.swing.JButton();\n\t\trewardTabPanel = new javax.swing.JPanel();\n\t\trewardPanel = new javax.swing.JPanel();\n\t\tleftRewardColumn = new javax.swing.JPanel();\n\t\tleftRewardPanel = new javax.swing.JPanel();\n\t\tvisibleRewardScrollList = new javax.swing.JScrollPane();\n\t\tvisibleRewardList = new javax.swing.JList();\n\t\tselectAllVisibleRewardsButton = new javax.swing.JButton();\n\t\tcenterRewardColumn = new javax.swing.JPanel();\n\t\tcenterRewardPanel = new javax.swing.JPanel();\n\t\tmakeRewardVisibleButton = new javax.swing.JButton();\n\t\tmakeRewardHiddenButton = new javax.swing.JButton();\n\t\trightRewardColumn = new javax.swing.JPanel();\n\t\trightRewardPanel = new javax.swing.JPanel();\n\t\thiddenRewardScrollList = new javax.swing.JScrollPane();\n\t\thiddenRewardList = new javax.swing.JList();\n\t\tselectAllHiddenRewardsButton = new javax.swing.JButton();\n\t\totherTabPanel = new javax.swing.JPanel();\n\t\tboxPanel = new javax.swing.JPanel();\n\t\tinnerTimePanel = new javax.swing.JPanel();\n\t\ttopInnerTimePanel = new javax.swing.JPanel();\n\t\tshowTimeCheckBox = new javax.swing.JCheckBox();\n\t\tshowCumulativeTimeCheckBox = new javax.swing.JCheckBox();\n\t\tpathStylePanel = new javax.swing.JPanel();\n\t\tinnerPathStylePanel = new javax.swing.JPanel();\n\t\tchangeRenderingButton = new javax.swing.JRadioButton();\n\t\trenderAllButton = new javax.swing.JRadioButton();\n\n\t\tvisibleLabel.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);\n\t\tvisibleLabel.setText(\"Visible Variables\");\n\t\thiddenLabel.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);\n\t\thiddenLabel.setText(\"Hidden Variables\");\n\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\n\t\tallPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tallPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tbottomPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tbuttonPanel.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tokayButton.setText(\"Okay\");\n\t\tokayButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tokayButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tbuttonPanel.add(okayButton);\n\n\t\tcancelButton.setText(\"Cancel\");\n\t\tcancelButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tcancelButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tbuttonPanel.add(cancelButton);\n\n\t\tbottomPanel.add(buttonPanel, java.awt.BorderLayout.EAST);\n\n\t\toptionCheckBox.setText(\"Always prompt for view configuration on path creation\");\n\t\tbottomPanel.add(optionCheckBox, java.awt.BorderLayout.WEST);\n\t\toptionCheckBox.getAccessibleContext().setAccessibleName(\"optionCheckBox\");\n\n\t\tallPanel.add(bottomPanel, java.awt.BorderLayout.SOUTH);\n\n\t\tgetContentPane().add(allPanel, java.awt.BorderLayout.SOUTH);\n\n\t\tvariableTabPane.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tvariableTabPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tvariablePanel.setLayout(new java.awt.GridBagLayout());\n\n\t\tvariablePanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tleftVariableColumn.setLayout(new java.awt.BorderLayout());\n\n\t\tleftVariableColumn.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Visible variables\"));\n\t\tleftVariablePanel.setLayout(new java.awt.BorderLayout(0, 5));\n\n\t\tleftVariablePanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tvisibleVariableScrollList.setHorizontalScrollBarPolicy(javax.swing.ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);\n\t\tvisibleVariableScrollList.setViewportView(visibleVariableList);\n\n\t\tleftVariablePanel.add(visibleVariableScrollList, java.awt.BorderLayout.CENTER);\n\n\t\tselectAllVisibleVariablesButton.setText(\"Select All\");\n\t\tselectAllVisibleVariablesButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tselectAllVisibleVariablesButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tleftVariablePanel.add(selectAllVisibleVariablesButton, java.awt.BorderLayout.SOUTH);\n\n\t\tleftVariableColumn.add(leftVariablePanel, java.awt.BorderLayout.CENTER);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 0.5;\n\t\tgridBagConstraints.weighty = 1.0;\n\t\tvariablePanel.add(leftVariableColumn, gridBagConstraints);\n\n\t\tcenterVariableColumn.setLayout(new java.awt.BorderLayout());\n\n\t\tcenterVariablePanel.setLayout(new java.awt.GridBagLayout());\n\n\t\tmakeVariableVisibleButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tmakeVariableVisibleButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.ipadx = 5;\n\t\tgridBagConstraints.ipady = 5;\n\t\tgridBagConstraints.insets = new java.awt.Insets(3, 10, 3, 10);\n\t\tcenterVariablePanel.add(makeVariableVisibleButton, gridBagConstraints);\n\n\t\tmakeVariableHiddenButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tmakeVariableHiddenButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.ipadx = 5;\n\t\tgridBagConstraints.ipady = 5;\n\t\tgridBagConstraints.insets = new java.awt.Insets(3, 10, 3, 10);\n\t\tcenterVariablePanel.add(makeVariableHiddenButton, gridBagConstraints);\n\n\t\tcenterVariableColumn.add(centerVariablePanel, java.awt.BorderLayout.CENTER);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 0;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.VERTICAL;\n\t\tgridBagConstraints.weighty = 1.0;\n\t\tvariablePanel.add(centerVariableColumn, gridBagConstraints);\n\n\t\trightVariableColumn.setLayout(new java.awt.BorderLayout());\n\n\t\trightVariableColumn.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Hidden variables\"));\n\t\trightVariablePanel.setLayout(new java.awt.BorderLayout(0, 5));\n\n\t\trightVariablePanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\thiddenVariableScrollList.setHorizontalScrollBarPolicy(javax.swing.ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);\n\t\thiddenVariableScrollList.setViewportView(hiddenVariableList);\n\n\t\trightVariablePanel.add(hiddenVariableScrollList, java.awt.BorderLayout.CENTER);\n\n\t\tselectAllHiddenVariablesButton.setText(\"Select All\");\n\t\tselectAllHiddenVariablesButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tselectAllHiddenVariablesButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\trightVariablePanel.add(selectAllHiddenVariablesButton, java.awt.BorderLayout.SOUTH);\n\n\t\trightVariableColumn.add(rightVariablePanel, java.awt.BorderLayout.CENTER);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 0;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 0.5;\n\t\tgridBagConstraints.weighty = 1.0;\n\t\tvariablePanel.add(rightVariableColumn, gridBagConstraints);\n\n\t\tvariableTabPanel.add(variablePanel, java.awt.BorderLayout.CENTER);\n\n\t\tvariableTabPane.addTab(\"Variable visibility\", variableTabPanel);\n\n\t\trewardTabPanel.setLayout(new java.awt.BorderLayout());\n\n\t\trewardPanel.setLayout(new java.awt.GridBagLayout());\n\n\t\trewardPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tleftRewardColumn.setLayout(new java.awt.BorderLayout());\n\n\t\tleftRewardColumn.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Visible reward structures\"));\n\t\tleftRewardPanel.setLayout(new java.awt.BorderLayout(0, 5));\n\n\t\tleftRewardPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tvisibleRewardScrollList.setHorizontalScrollBarPolicy(javax.swing.ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);\n\t\tvisibleRewardScrollList.setViewportView(visibleRewardList);\n\n\t\tleftRewardPanel.add(visibleRewardScrollList, java.awt.BorderLayout.CENTER);\n\n\t\tselectAllVisibleRewardsButton.setText(\"Select All\");\n\t\tselectAllVisibleRewardsButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tselectAllVisibleRewardsButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tleftRewardPanel.add(selectAllVisibleRewardsButton, java.awt.BorderLayout.SOUTH);\n\n\t\tleftRewardColumn.add(leftRewardPanel, java.awt.BorderLayout.CENTER);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 0;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 0.5;\n\t\tgridBagConstraints.weighty = 1.0;\n\t\trewardPanel.add(leftRewardColumn, gridBagConstraints);\n\n\t\tcenterRewardColumn.setLayout(new java.awt.BorderLayout());\n\n\t\tcenterRewardPanel.setLayout(new java.awt.GridBagLayout());\n\n\t\tmakeRewardVisibleButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tmakeRewardVisibleButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 0;\n\t\tgridBagConstraints.gridy = 1;\n\t\tgridBagConstraints.ipadx = 5;\n\t\tgridBagConstraints.ipady = 5;\n\t\tgridBagConstraints.insets = new java.awt.Insets(3, 10, 3, 10);\n\t\tcenterRewardPanel.add(makeRewardVisibleButton, gridBagConstraints);\n\n\t\tmakeRewardHiddenButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tmakeRewardHiddenButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.ipadx = 5;\n\t\tgridBagConstraints.ipady = 5;\n\t\tgridBagConstraints.insets = new java.awt.Insets(3, 10, 3, 10);\n\t\tcenterRewardPanel.add(makeRewardHiddenButton, gridBagConstraints);\n\n\t\tcenterRewardColumn.add(centerRewardPanel, java.awt.BorderLayout.CENTER);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 2;\n\t\tgridBagConstraints.gridy = 0;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.VERTICAL;\n\t\tgridBagConstraints.weighty = 1.0;\n\t\trewardPanel.add(centerRewardColumn, gridBagConstraints);\n\n\t\trightRewardColumn.setLayout(new java.awt.BorderLayout());\n\n\t\trightRewardColumn.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Hidden reward structures\"));\n\t\trightRewardPanel.setLayout(new java.awt.BorderLayout(0, 5));\n\n\t\trightRewardPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\thiddenRewardScrollList.setHorizontalScrollBarPolicy(javax.swing.ScrollPaneConstants.HORIZONTAL_SCROLLBAR_NEVER);\n\t\thiddenRewardScrollList.setViewportView(hiddenRewardList);\n\n\t\trightRewardPanel.add(hiddenRewardScrollList, java.awt.BorderLayout.CENTER);\n\n\t\tselectAllHiddenRewardsButton.setText(\"Select All\");\n\t\tselectAllHiddenRewardsButton.addActionListener(new java.awt.event.ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(java.awt.event.ActionEvent evt)\n\t\t\t{\n\t\t\t\tselectAllHiddenRewardsButtonActionPerformed(evt);\n\t\t\t}\n\t\t});\n\n\t\trightRewardPanel.add(selectAllHiddenRewardsButton, java.awt.BorderLayout.SOUTH);\n\n\t\trightRewardColumn.add(rightRewardPanel, java.awt.BorderLayout.CENTER);\n\n\t\tgridBagConstraints = new java.awt.GridBagConstraints();\n\t\tgridBagConstraints.gridx = 3;\n\t\tgridBagConstraints.gridy = 0;\n\t\tgridBagConstraints.gridwidth = 2;\n\t\tgridBagConstraints.fill = java.awt.GridBagConstraints.BOTH;\n\t\tgridBagConstraints.weightx = 0.5;\n\t\tgridBagConstraints.weighty = 1.0;\n\t\trewardPanel.add(rightRewardColumn, gridBagConstraints);\n\n\t\trewardTabPanel.add(rewardPanel, java.awt.BorderLayout.CENTER);\n\n\t\tvariableTabPane.addTab(\"Reward visibility\", rewardTabPanel);\n\n\t\totherTabPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tboxPanel.setLayout(new javax.swing.BoxLayout(boxPanel, javax.swing.BoxLayout.Y_AXIS));\n\n\t\tboxPanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tinnerTimePanel.setLayout(new java.awt.BorderLayout());\n\n\t\tinnerTimePanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Time properties\"));\n\t\ttopInnerTimePanel.setLayout(new java.awt.GridLayout(2, 1, 5, 5));\n\n\t\ttopInnerTimePanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tshowTimeCheckBox.setText(\"Show the time spent in states\");\n\t\tshowTimeCheckBox.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0));\n\t\tshowTimeCheckBox.setMargin(new java.awt.Insets(0, 0, 0, 0));\n\t\ttopInnerTimePanel.add(showTimeCheckBox);\n\t\tshowTimeCheckBox.getAccessibleContext().setAccessibleName(\"\");\n\n\t\tshowCumulativeTimeCheckBox.setText(\"Show the cumulative time\");\n\t\tshowCumulativeTimeCheckBox.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0));\n\t\tshowCumulativeTimeCheckBox.setMargin(new java.awt.Insets(0, 0, 0, 0));\n\t\ttopInnerTimePanel.add(showCumulativeTimeCheckBox);\n\n\t\tinnerTimePanel.add(topInnerTimePanel, java.awt.BorderLayout.NORTH);\n\n\t\tboxPanel.add(innerTimePanel);\n\n\t\tpathStylePanel.setLayout(new java.awt.BorderLayout());\n\n\t\tpathStylePanel.setBorder(javax.swing.BorderFactory.createTitledBorder(\"Path style\"));\n\t\tinnerPathStylePanel.setLayout(new java.awt.GridLayout(2, 1, 5, 5));\n\n\t\tinnerPathStylePanel.setBorder(javax.swing.BorderFactory.createEmptyBorder(5, 5, 5, 5));\n\t\tchangeRenderingButton.setText(\"Render changes\");\n\t\tchangeRenderingButton.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0));\n\t\tchangeRenderingButton.setMargin(new java.awt.Insets(0, 0, 0, 0));\n\t\tinnerPathStylePanel.add(changeRenderingButton);\n\n\t\trenderAllButton.setText(\"Render all values\");\n\t\trenderAllButton.setBorder(javax.swing.BorderFactory.createEmptyBorder(0, 0, 0, 0));\n\t\trenderAllButton.setMargin(new java.awt.Insets(0, 0, 0, 0));\n\t\tinnerPathStylePanel.add(renderAllButton);\n\n\t\tpathStylePanel.add(innerPathStylePanel, java.awt.BorderLayout.NORTH);\n\n\t\tboxPanel.add(pathStylePanel);\n\n\t\totherTabPanel.add(boxPanel, java.awt.BorderLayout.NORTH);\n\n\t\tvariableTabPane.addTab(\"Other\", otherTabPanel);\n\n\t\tgetContentPane().add(variableTabPane, java.awt.BorderLayout.CENTER);\n\n\t}// </editor-fold>//GEN-END:initComponents\n\n\tprivate void selectAllHiddenRewardsButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_selectAllHiddenRewardsButtonActionPerformed\n\t\tint[] indices = new int[hiddenRewardListModel.getSize()];\n\t\tfor (int i = 0; i < indices.length; i++)\n\t\t\tindices[i] = i;\n\n\t\thiddenRewardList.setSelectedIndices(indices);\n\t}//GEN-LAST:event_selectAllHiddenRewardsButtonActionPerformed\n\n\tprivate void makeRewardHiddenButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_makeRewardHiddenButtonActionPerformed\n\t\tint[] indices = visibleRewardList.getSelectedIndices();\n\n\t\tfor (int i = indices.length - 1; i >= 0; i--) {\n\t\t\tRewardListItem rew = (RewardListItem) visibleRewardListModel.get(indices[i]);\n\n\t\t\tvisibleRewardListModel.removeReward(rew);\n\t\t\thiddenRewardListModel.addReward(rew);\n\t\t}\n\t}//GEN-LAST:event_makeRewardHiddenButtonActionPerformed\n\n\tprivate void makeRewardVisibleButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_makeRewardVisibleButtonActionPerformed\n\t\tint[] indices = hiddenRewardList.getSelectedIndices();\n\t\tfor (int i = indices.length - 1; i >= 0; i--) {\n\t\t\tRewardListItem rew = (RewardListItem) hiddenRewardListModel.get(indices[i]);\n\t\t\thiddenRewardListModel.removeReward(rew);\n\t\t\tvisibleRewardListModel.addReward(rew);\n\t\t}\n\t}//GEN-LAST:event_makeRewardVisibleButtonActionPerformed\n\n\tprivate void selectAllVisibleRewardsButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_selectAllVisibleRewardsButtonActionPerformed\n\t\tint[] indices = new int[visibleRewardListModel.getSize()];\n\t\tfor (int i = 0; i < indices.length; i++)\n\t\t\tindices[i] = i;\n\t\tvisibleRewardList.setSelectedIndices(indices);\n\t}//GEN-LAST:event_selectAllVisibleRewardsButtonActionPerformed\n\n\tprivate void selectAllVisibleVariablesButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_selectAllVisibleVariablesButtonActionPerformed\n\t\tint[] indices = new int[visibleVariableListModel.getSize()];\n\t\tfor (int i = 0; i < indices.length; i++)\n\t\t\tindices[i] = i;\n\t\tvisibleVariableList.setSelectedIndices(indices);\n\t}//GEN-LAST:event_selectAllVisibleVariablesButtonActionPerformed\n\n\tprivate void selectAllHiddenVariablesButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_selectAllHiddenVariablesButtonActionPerformed\n\t\tint[] indices = new int[hiddenVariableListModel.getSize()];\n\t\tfor (int i = 0; i < indices.length; i++)\n\t\t\tindices[i] = i;\n\n\t\thiddenVariableList.setSelectedIndices(indices);\n\n\t}//GEN-LAST:event_selectAllHiddenVariablesButtonActionPerformed\n\n\tprivate void makeVariableVisibleButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_makeVariableVisibleButtonActionPerformed\n\t\tint[] indices = hiddenVariableList.getSelectedIndices();\n\n\t\tfor (int i = indices.length - 1; i >= 0; i--) {\n\t\t\tVariable var = (Variable) hiddenVariableListModel.get(indices[i]);\n\n\t\t\thiddenVariableListModel.removeVariable(var);\n\t\t\tvisibleVariableListModel.addVariable(var);\n\t\t}\n\t}//GEN-LAST:event_makeVariableVisibleButtonActionPerformed\n\n\tprivate void makeVariableHiddenButtonActionPerformed(java.awt.event.ActionEvent evt)\n\t{//GEN-FIRST:event_makeVariableHiddenButtonActionPerformed\n\t\tint[] indices = visibleVariableList.getSelectedIndices();\n\n\t\tfor (int i = indices.length - 1; i >= 0; i--) {\n\t\t\tVariable var = (Variable) visibleVariableListModel.get(indices[i]);\n\n\t\t\tvisibleVariableListModel.removeVariable(var);\n\t\t\thiddenVariableListModel.addVariable(var);\n\t\t}\n\t}//GEN-LAST:event_makeVariableHiddenButtonActionPerformed\n\n\tprivate void okayButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_okayButtonActionPerformed\n\t{//GEN-HEADEREND:event_okayButtonActionPerformed\n\n\t\tif (optionCheckBox.isSelected() != this.askOption) {\n\t\t\tthis.askOption = !this.askOption;\n\n\t\t\ttry {\n\t\t\t\tgui.getPrism().getSettings().set(PrismSettings.SIMULATOR_NEW_PATH_ASK_VIEW, this.askOption);\n\t\t\t} catch (PrismException e) {\n\t\t\t}\n\t\t}\n\n\t\tview.showTime(showTimeCheckBox.isSelected());\n\t\tview.showCumulativeTime(showCumulativeTimeCheckBox.isSelected());\n\t\tview.setVariableVisibility(visibleVariableListModel.getVariables(), hiddenVariableListModel.getVariables());\n\t\tview.setRenderer(changeRenderingButton.isSelected());\n\t\tview.setVisibleRewardListItems(visibleRewardListModel.getRewards());\n\n\t\tdispose();\n\t}//GEN-LAST:event_okayButtonActionPerformed\n\n\tprivate void cancelButtonActionPerformed(java.awt.event.ActionEvent evt)//GEN-FIRST:event_cancelButtonActionPerformed\n\t{//GEN-HEADEREND:event_cancelButtonActionPerformed\n\t\tdispose();\n\t}//GEN-LAST:event_cancelButtonActionPerformed\n\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\n\tpublic void keyPressed(KeyEvent e)\n\t{\n\t}\n\n\tpublic void keyReleased(KeyEvent e)\n\t{\n\n\t}\n\n\tpublic void keyTyped(KeyEvent e)\n\t{\n\n\t}\n\n\tclass VariableListModel extends DefaultListModel\n\t{\n\t\tprivate static final long serialVersionUID = 1L;\n\n\t\tpublic VariableListModel(ArrayList<Variable> variables)\n\t\t{\n\t\t\tsuper();\n\t\t\tfor (int i = 0; i < variables.size(); i++) {\n\t\t\t\tsuper.add(i, variables.get(i));\n\t\t\t}\n\t\t}\n\n\t\tpublic void removeVariable(Variable variable)\n\t\t{\n\t\t\tfor (int i = 0; i < super.getSize(); i++) {\n\t\t\t\tVariable var = (Variable) super.getElementAt(i);\n\t\t\t\tif (var.equals(variable)) {\n\t\t\t\t\tsuper.remove(i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tpublic void addVariable(Variable variable)\n\t\t{\n\t\t\tint i = 0;\n\n\t\t\twhile (i < super.getSize() && ((Variable) super.getElementAt(i)).getIndex() < variable.getIndex()) {\n\t\t\t\ti++;\n\t\t\t}\n\n\t\t\tsuper.add(i, variable);\n\t\t}\n\n\t\tpublic ArrayList<Variable> getVariables()\n\t\t{\n\t\t\tArrayList<Variable> list = new ArrayList<Variable>();\n\t\t\tfor (int i = 0; i < super.getSize(); i++) {\n\t\t\t\tlist.add((Variable) super.getElementAt(i));\n\t\t\t}\n\n\t\t\treturn list;\n\t\t}\n\t}\n\n\tclass RewardListItem\n\t{\n\t\tprivate RewardStructure rewardStructure;\n\t\tprivate boolean isCumulative;\n\n\t\tpublic RewardListItem(RewardStructure rewardStructure, boolean isCumulative)\n\t\t{\n\t\t\tthis.rewardStructure = rewardStructure;\n\t\t\tthis.isCumulative = isCumulative;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\tString res = rewardStructure.toString();\n\t\t\tif (isCumulative)\n\t\t\t\treturn res + \" (cumulative)\";\n\t\t\telse {\n\t\t\t\tif (!rewardStructure.isStateEmpty() && !rewardStructure.isTransitionEmpty())\n\t\t\t\t\treturn res + \" (state and transition)\";\n\t\t\t\telse if (!rewardStructure.isStateEmpty())\n\t\t\t\t\treturn res + \" (state)\";\n\t\t\t\telse if (!rewardStructure.isTransitionEmpty())\n\t\t\t\t\treturn res + \" (transition)\";\n\t\t\t\telse\n\t\t\t\t\treturn res + \" (empty)\";\n\t\t\t}\n\t\t}\n\n\t\tpublic boolean isCumulative()\n\t\t{\n\t\t\treturn isCumulative;\n\t\t}\n\n\t\tpublic void setCumulative(boolean isCumulative)\n\t\t{\n\t\t\tthis.isCumulative = isCumulative;\n\t\t}\n\n\t\tpublic RewardStructure getRewardStructure()\n\t\t{\n\t\t\treturn rewardStructure;\n\t\t}\n\n\t\tpublic void setRewardStructure(RewardStructure rewardStructure)\n\t\t{\n\t\t\tthis.rewardStructure = rewardStructure;\n\t\t}\n\n\t\tpublic boolean equals(Object obj)\n\t\t{\n\t\t\tif (obj instanceof RewardListItem) {\n\t\t\t\tRewardListItem item = (RewardListItem) obj;\n\t\t\t\treturn (item.getRewardStructure().equals(this.rewardStructure) && item.isCumulative() == isCumulative);\n\t\t\t}\n\n\t\t\treturn false;\n\t\t}\n\t}\n\n\tclass RewardListModel extends DefaultListModel\n\t{\n\t\tprivate static final long serialVersionUID = 1L;\n\n\t\tpublic RewardListModel(ArrayList<RewardListItem> rewardListItems)\n\t\t{\n\t\t\tfor (int i = 0; i < rewardListItems.size(); i++) {\n\t\t\t\tsuper.add(i, rewardListItems.get(i));\n\n\t\t\t}\n\t\t}\n\n\t\tpublic void removeReward(RewardListItem reward)\n\t\t{\n\t\t\tfor (int i = 0; i < super.getSize(); i++) {\n\t\t\t\tRewardListItem rew = (RewardListItem) super.getElementAt(i);\n\t\t\t\tif (rew.equals(reward)) {\n\t\t\t\t\tsuper.remove(i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tpublic void addReward(RewardListItem reward)\n\t\t{\n\t\t\tint i = 0;\n\n\t\t\twhile (i < super.getSize() && ((RewardListItem) super.getElementAt(i)).getRewardStructure().getIndex() < reward.getRewardStructure().getIndex()) {\n\t\t\t\ti++;\n\t\t\t}\n\n\t\t\tif (i < super.getSize() && ((RewardListItem) super.getElementAt(i)).getRewardStructure().getIndex() == reward.getRewardStructure().getIndex()\n\t\t\t\t\t&& reward.isCumulative()) {\n\t\t\t\ti++;\n\t\t\t}\n\n\t\t\tsuper.add(i, reward);\n\t\t}\n\n\t\tpublic ArrayList<RewardListItem> getRewards()\n\t\t{\n\t\t\tArrayList<RewardListItem> list = new ArrayList<RewardListItem>();\n\t\t\tfor (int i = 0; i < super.getSize(); i++) {\n\t\t\t\tlist.add((RewardListItem) super.getElementAt(i));\n\t\t\t}\n\n\t\t\treturn list;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/SimPathPlotThread.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Dave Parker <d.a.parker@cs.bham.ac.uk> (University of Birmingham/Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport javax.swing.SwingUtilities;\n\nimport prism.PrismException;\nimport simulator.GenerateSimulationPath;\nimport simulator.SimulatorEngine;\nimport userinterface.GUIComputationThread;\nimport userinterface.graph.Graph;\n\npublic class SimPathPlotThread extends GUIComputationThread\n{\n\tprivate SimulatorEngine engine;\n\tprivate parser.State initialState;\n\tprivate String simPathDetails;\n\tprivate long maxPathLength;\n\tprivate Graph graphModel;\n\n\tpublic SimPathPlotThread(GUISimulator guiSim, SimulatorEngine engine, parser.State initialState, String simPathDetails,\n\t\t\tlong maxPathLength, Graph graphModel)\n\t{\n\t\tsuper(guiSim);\n\t\tthis.engine = engine;\n\t\tthis.initialState = initialState;\n\t\tthis.simPathDetails = simPathDetails;\n\t\tthis.maxPathLength = maxPathLength;\n\t\tthis.graphModel = graphModel;\n\t}\n\n\tpublic void run()\n\t{\n\t\tSwingUtilities.invokeLater(new Runnable()\n\t\t{\n\t\t\tpublic void run()\n\t\t\t{\n\t\t\t\ttry {\n\t\t\t\t\tGenerateSimulationPath genPath = new GenerateSimulationPath(engine, prism.getMainLog());\n\t\t\t\t\tgenPath.generateAndPlotSimulationPath(initialState, simPathDetails, maxPathLength, graphModel);\n\t\t\t\t\tif (genPath.getNumWarnings() > 0) {\n\t\t\t\t\t\tfor (String msg : genPath.getWarnings()) {\n\t\t\t\t\t\t\tplug.warning(msg);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\terror(e.getMessage());\n\t\t\t\t}\n\t\t\t}\n\t\t});\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/SimulationView.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.simulator;\n\nimport java.util.ArrayList;\nimport java.util.Observable;\nimport java.util.TreeSet;\n\nimport parser.ast.ModulesFile;\nimport parser.ast.RewardStruct;\nimport parser.type.Type;\nimport prism.PrismException;\nimport prism.PrismSettings;\nimport userinterface.simulator.GUIViewDialog.RewardListItem;\n\n/**\n * Class storing information about the view configuration for a path in the simulator.\n */\npublic class SimulationView extends Observable\n{\n\tprivate GUISimulator simulator;\n\n\tprivate ArrayList<Variable> visibleVariables;\n\tprivate ArrayList<Variable> hiddenVariables;\n\n\tprivate ArrayList<Observ> visibleObservables;\n\t\n\tprivate ArrayList<RewardStructureColumn> visibleRewardColumns;\n\tprivate ArrayList<RewardStructure> rewards;\n\n\tprivate boolean stepsVisible;\n\tprivate boolean actionsVisible;\n\tprivate boolean showTime;\n\tprivate boolean showCumulativeTime;\n\tprivate boolean useChangeRenderer;\n\n\tpublic SimulationView(GUISimulator simulator, PrismSettings settings)\n\t{\n\t\tthis.simulator = simulator;\n\n\t\tthis.visibleVariables = new ArrayList<Variable>();\n\t\tthis.hiddenVariables = new ArrayList<Variable>();\n\t\tthis.visibleObservables = new ArrayList<>();\n\t\tthis.visibleRewardColumns = new ArrayList<RewardStructureColumn>();\n\t\tthis.rewards = new ArrayList<RewardStructure>();\n\n\t\tthis.stepsVisible = true;\n\t\tthis.actionsVisible = true;\n\t\tthis.showTime = false;\n\t\tthis.showCumulativeTime = true;\n\n\t\tuseChangeRenderer = (settings.getInteger(PrismSettings.SIMULATOR_RENDER_ALL_VALUES) == 0);\n\n\t}\n\n\tpublic boolean showSteps()\n\t{\n\t\treturn stepsVisible;\n\t}\n\n\tpublic void showSteps(boolean stepsVisible)\n\t{\n\t\tthis.stepsVisible = stepsVisible;\n\n\t\tthis.setChanged();\n\t\tthis.notifyObservers();\n\t}\n\n\tpublic boolean showActions()\n\t{\n\t\treturn actionsVisible;\n\t}\n\n\tpublic void showActions(boolean actionsVisible)\n\t{\n\t\tthis.actionsVisible = actionsVisible;\n\n\t\tthis.setChanged();\n\t\tthis.notifyObservers();\n\t}\n\n\tpublic boolean showTime()\n\t{\n\t\treturn showTime;\n\t}\n\n\tpublic boolean showCumulativeTime()\n\t{\n\t\treturn showCumulativeTime;\n\t}\n\n\tpublic void showTime(boolean showTime)\n\t{\n\t\tthis.showTime = showTime;\n\n\t\tthis.setChanged();\n\t\tthis.notifyObservers();\n\t}\n\n\tpublic void showCumulativeTime(boolean showCumulativeTime)\n\t{\n\t\tthis.showCumulativeTime = showCumulativeTime;\n\n\t\tthis.setChanged();\n\t\tthis.notifyObservers();\n\t}\n\n\tpublic ArrayList<Variable> getVisibleVariables()\n\t{\n\t\treturn visibleVariables;\n\t}\n\n\tpublic ArrayList<Variable> getHiddenVariables()\n\t{\n\t\treturn hiddenVariables;\n\t}\n\n\tpublic void setVariableVisibility(ArrayList<Variable> visibleVariables, ArrayList<Variable> hiddenVariables)\n\t{\n\t\tthis.visibleVariables = visibleVariables;\n\t\tthis.hiddenVariables = hiddenVariables;\n\n\t\tthis.setChanged();\n\t\tthis.notifyObservers();\n\t}\n\n\tpublic ArrayList<Observ> getVisibleObservables()\n\t{\n\t\treturn visibleObservables;\n\t}\n\n\tpublic ArrayList<RewardStructureColumn> getVisibleRewardColumns()\n\t{\n\t\treturn visibleRewardColumns;\n\t}\n\n\tpublic void setVisibleRewardListItems(ArrayList<RewardListItem> visibleRewardListItems)\n\t{\n\t\tArrayList<RewardStructureColumn> visibleRewardColumns = new ArrayList<RewardStructureColumn>();\n\n\t\tfor (RewardListItem item : visibleRewardListItems) {\n\t\t\tif (item.isCumulative())\n\t\t\t\tvisibleRewardColumns.add(new RewardStructureColumn(item.getRewardStructure(), RewardStructureColumn.CUMULATIVE_REWARD));\n\t\t\telse {\n\t\t\t\tif (!item.getRewardStructure().isStateEmpty())\n\t\t\t\t\tvisibleRewardColumns.add(new RewardStructureColumn(item.getRewardStructure(), RewardStructureColumn.STATE_REWARD));\n\t\t\t\tif (!item.getRewardStructure().isTransitionEmpty())\n\t\t\t\t\tvisibleRewardColumns.add(new RewardStructureColumn(item.getRewardStructure(), RewardStructureColumn.TRANSITION_REWARD));\n\t\t\t}\n\t\t}\n\n\t\tthis.visibleRewardColumns = visibleRewardColumns;\n\n\t\tthis.setChanged();\n\t\tthis.notifyObservers();\n\t}\n\n\tpublic ArrayList<RewardStructure> getRewards()\n\t{\n\t\treturn rewards;\n\t}\n\n\tpublic boolean isChangeRenderer()\n\t{\n\t\treturn useChangeRenderer;\n\t}\n\n\tpublic void setRenderer(boolean isChangeRenderer)\n\t{\n\t\tif (useChangeRenderer != isChangeRenderer) {\n\t\t\tuseChangeRenderer = isChangeRenderer;\n\t\t\tsimulator.setRenderer(useChangeRenderer);\n\t\t}\n\t}\n\n\tpublic void refreshToDefaultView(boolean pathActive, ModulesFile parsedModel)\n\t{\n\t\tboolean canUseCurrentView = false;\n\t\tif (!pathActive && useChangeRenderer != simulator.usingChangeRenderer()) {\n\t\t\tsimulator.setRenderer(useChangeRenderer);\n\t\t}\n\n\t\t// First see if we can get away with using current settings...\n\t\t/*boolean canUseCurrentView = true;\n\t\tif (!pathActive) {\n\t\t\tcanUseCurrentView = false;\n\t\t} else {\n\t\t\tif (useChangeRenderer != simulator.usingChangeRenderer()) {\n\t\t\t\tsimulator.setRenderer(useChangeRenderer);\n\t\t\t}\n\n\t\t\ttry {\n\t\t\t\t\n\t\t\t// Time-wise we have a problem.\n\t\t\tif (!parsedModel.getModelType().continuousTime() && (showTime || showCumulativeTime))\n\t\t\t\tcanUseCurrentView = false;\n\n\t\t\t// Make a set of all variable names.\n\t\t\tTreeSet<String> allVarNames = new TreeSet<String>();\n\t\t\tfor (Variable var : visibleVariables)\n\t\t\t\tallVarNames.add(var.getName());\n\t\t\tfor (Variable var : hiddenVariables)\n\t\t\t\tallVarNames.add(var.getName());\n\t\t\t\n\t\t\t// Cannot use current view if a variable is not there.\n\t\t\tfor (int i = 0; i < parsedModel.getNumVars(); i++) {\n\t\t\t\tif (!allVarNames.remove(parsedModel.getVarName(i))) {\n\t\t\t\t\tcanUseCurrentView = false;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Cannot use current view if we have too many variables.\n\t\t\tif (allVarNames.size() > 0)\n\t\t\t\tcanUseCurrentView = false;\n\n\t\t\t// Make a set of all observable names.\n\t\t\tTreeSet<String> allObsNames = new TreeSet<String>();\n\t\t\tfor (Observ obs : visibleObservables)\n\t\t\t\tallObsNames.add(obs.getName());\n\t\t\t\n\t\t\t// Cannot use current view if an observable is not there.\n\t\t\tfor (int i = 0; i < parsedModel.getNumObservables(); i++) {\n\t\t\t\tif (!allObsNames.remove(parsedModel.getObservableName(i))) {\n\t\t\t\t\tcanUseCurrentView = false;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t// Cannot use current view if we have too many observable.\n\t\t\tif (allObsNames.size() > 0)\n\t\t\t\tcanUseCurrentView = false;\n\n\t\t\t// Make a list of all reward structures\n\t\t\tArrayList<RewardStructure> allrew = new ArrayList<RewardStructure>();\n\t\t\tfor (RewardStructure rew : rewards) {\n\t\t\t\tallrew.add(rew);\n\t\t\t}\n\n\t\t\tfor (int r = 0; r < parsedModel.getNumRewardStructs(); r++) {\n\t\t\t\tRewardStruct rewardStruct = parsedModel.getRewardStruct(r);\n\t\t\t\tString rewardName = rewardStruct.getName();\n\t\t\t\tboolean hasStates = parsedModel.getRewardStruct(r).getNumStateItems() != 0;\n\t\t\t\tboolean hasTrans = parsedModel.getRewardStruct(r).getNumTransItems() != 0;\n\t\t\t\tboolean foundReward = false;\n\n\t\t\t\tfor (RewardStructure rew : rewards) {\n\t\t\t\t\tif (rew.isStateEmpty() == !hasStates && rew.isTransitionEmpty() == !hasTrans\n\t\t\t\t\t\t\t&& ((rew.getName() == null && rewardName.equals(\"\")) || (rew.getName() != null && rew.getName().equals(rewardName)))) {\n\t\t\t\t\t\tallrew.remove(rew);\n\t\t\t\t\t\tfoundReward = true;\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\tif (!foundReward)\n\t\t\t\t\tcanUseCurrentView = false;\n\t\t\t}\n\n\t\t\tif (allrew.size() > 0)\n\t\t\t\tcanUseCurrentView = false;\n\t\t\t\n\t\t\t} catch (PrismException e) {\n\t\t\t\tcanUseCurrentView = false;\n\t\t\t}\n\t\t}*/\n\n\t\tif (!canUseCurrentView && pathActive) {\n\t\t\tvisibleVariables.clear();\n\t\t\thiddenVariables.clear();\n\t\t\tvisibleObservables.clear();\n\t\t\tvisibleRewardColumns.clear();\n\t\t\trewards.clear();\n\t\t\t{\n\t\t\t\tfor (int i = 0; i < parsedModel.getNumVars(); i++) {\n\t\t\t\t\tvisibleVariables.add(new Variable(i, parsedModel.getVarName(i), parsedModel.getVarType(i), parsedModel.getVarModuleIndex(i)));\n\t\t\t\t}\n\t\t\t\tfor (int i = 0; i < parsedModel.getNumObservables(); i++) {\n\t\t\t\t\ttry { \n\t\t\t\t\t\tvisibleObservables.add(new Observ(i, parsedModel.getObservableName(i), parsedModel.getObservableType(i)));\n\t\t\t\t\t} catch (PrismException e) {\n\t\t\t\t\t\t// Don't add if error (should not happen)\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\tfor (int r = 0; r < parsedModel.getNumRewardStructs(); r++) {\n\t\t\t\t\tRewardStruct rewardStruct = parsedModel.getRewardStruct(r);\n\t\t\t\t\tString rewardName = rewardStruct.getName();\n\n\t\t\t\t\tif (rewardName.trim().length() == 0) {\n\t\t\t\t\t\trewardName = null;\n\t\t\t\t\t}\n\n\t\t\t\t\tRewardStructure rewardStructure = new RewardStructure(r, rewardName, parsedModel.getRewardStruct(r).getNumStateItems() == 0, parsedModel\n\t\t\t\t\t\t\t.getRewardStruct(r).getNumTransItems() == 0);\n\n\t\t\t\t\tif (!rewardStructure.isStateEmpty() || !rewardStructure.isTransitionEmpty())\n\t\t\t\t\t\trewards.add(rewardStructure);\n\n\t\t\t\t\tif (!rewardStructure.isStateEmpty())\n\t\t\t\t\t\tvisibleRewardColumns.add(new RewardStructureColumn(rewardStructure, RewardStructureColumn.STATE_REWARD));\n\n\t\t\t\t\tif (!rewardStructure.isTransitionEmpty())\n\t\t\t\t\t\tvisibleRewardColumns.add(new RewardStructureColumn(rewardStructure, RewardStructureColumn.TRANSITION_REWARD));\n\t\t\t\t}\n\n\t\t\t}\n\t\t}\n\t\tthis.setChanged();\n\t\tthis.notifyObservers();\n\n\t}\n\n\t/**\n\t * Represents a variable in the model.\n\t */\n\tpublic class Variable\n\t{\n\t\tprotected int index;\n\t\tprotected String name;\n\t\tprotected Type type;\n\t\tprotected int moduleIndex;\n\n\t\tpublic Variable(int index, String name, Type type, int moduleIndex)\n\t\t{\n\t\t\tthis.index = index;\n\t\t\tthis.name = name;\n\t\t\tthis.type = type;\n\t\t\tthis.moduleIndex = moduleIndex;\n\t\t}\n\n\t\tpublic int getIndex()\n\t\t{\n\t\t\treturn index;\n\t\t}\n\n\t\tpublic String getName()\n\t\t{\n\t\t\treturn name;\n\t\t}\n\n\t\tpublic Type getType()\n\t\t{\n\t\t\treturn type;\n\t\t}\n\n\t\tpublic int getModuleIndex()\n\t\t{\n\t\t\treturn moduleIndex;\n\t\t}\n\t\t\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn name;\n\t\t}\n\n\t\tpublic boolean equals(Object o)\n\t\t{\n\t\t\treturn (o instanceof Variable && ((Variable) o).getIndex() == index);\n\t\t}\n\t}\n\n\tpublic class VariableValue\n\t{\n\t\tprivate Variable variable;\n\t\tprivate Object value;\n\t\tprivate boolean hasChanged;\n\n\t\tpublic VariableValue(Variable variable, Object value)\n\t\t{\n\t\t\tthis.variable = variable;\n\t\t\tthis.value = value;\n\t\t\tthis.hasChanged = true;\n\t\t}\n\n\t\tpublic Object getValue()\n\t\t{\n\t\t\treturn value;\n\t\t}\n\n\t\tpublic void setValue(Object value)\n\t\t{\n\t\t\tthis.value = value;\n\t\t}\n\n\t\tpublic Variable getVariable()\n\t\t{\n\t\t\treturn variable;\n\t\t}\n\n\t\tpublic void setVariable(Variable variable)\n\t\t{\n\t\t\tthis.variable = variable;\n\t\t}\n\n\t\tpublic boolean hasChanged()\n\t\t{\n\t\t\treturn hasChanged;\n\t\t}\n\n\t\tpublic void setChanged(boolean hasChanged)\n\t\t{\n\t\t\tthis.hasChanged = hasChanged;\n\t\t}\n\t}\n\n\tpublic class Observ extends Variable\n\t{\n\t\tpublic Observ(int index, String name, Type type)\n\t\t{\n\t\t\tsuper(index, name, type, -1);\n\t\t}\n\t\t\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn \"\\\"\" + name + \"\\\"\";\n\t\t}\n\t}\n\t\n\tpublic class ActionValue\n\t{\n\t\tprivate String value;\n\t\tprivate boolean actionValueUnknown;\n\n\t\tpublic ActionValue(String value)\n\t\t{\n\t\t\tthis.value = value;\n\t\t}\n\n\t\tpublic String getValue()\n\t\t{\n\t\t\treturn value;\n\t\t}\n\n\t\tpublic void setValue(String value)\n\t\t{\n\t\t\tthis.value = value;\n\t\t}\n\n\t\tpublic void setActionValueUnknown(boolean unknown)\n\t\t{\n\t\t\tthis.actionValueUnknown = unknown;\n\t\t}\n\n\t\tpublic boolean isActionValueUnknown()\n\t\t{\n\t\t\treturn this.actionValueUnknown;\n\t\t}\n\t}\n\n\tpublic class TimeValue\n\t{\n\t\tprivate Double value;\n\t\tprivate boolean timeValueUnknown;\n\t\tprivate boolean isCumulative;\n\n\t\tpublic TimeValue(Double value, boolean isCumulative)\n\t\t{\n\t\t\tthis.value = value;\n\t\t\tthis.isCumulative = isCumulative;\n\t\t}\n\n\t\tpublic Double getValue()\n\t\t{\n\t\t\treturn value;\n\t\t}\n\n\t\tpublic void setValue(Double value)\n\t\t{\n\t\t\tthis.value = value;\n\t\t}\n\n\t\tpublic void setTimeValueUnknown(boolean unknown)\n\t\t{\n\t\t\tthis.timeValueUnknown = unknown;\n\t\t}\n\n\t\tpublic boolean isTimeValueUnknown()\n\t\t{\n\t\t\treturn this.timeValueUnknown;\n\t\t}\n\n\t\tpublic boolean isCumulative()\n\t\t{\n\t\t\treturn isCumulative;\n\t\t}\n\n\t\tpublic void setCumulative(boolean isCumulative)\n\t\t{\n\t\t\tthis.isCumulative = isCumulative;\n\t\t}\n\t}\n\n\t/**\n\t * Represents a reward structure in the model.\n\t */\n\tpublic class RewardStructure\n\t{\n\t\tprivate int index;\n\t\tprivate String name;\n\n\t\tprivate boolean stateEmpty;\n\t\tprivate boolean transitionEmpty;\n\n\t\tpublic RewardStructure(int index, String name, boolean stateEmpty, boolean transitionEmpty)\n\t\t{\n\t\t\tthis.index = index;\n\t\t\tthis.name = name;\n\t\t\tthis.stateEmpty = stateEmpty;\n\t\t\tthis.transitionEmpty = transitionEmpty;\n\t\t}\n\n\t\tpublic int getIndex()\n\t\t{\n\t\t\treturn index;\n\t\t}\n\n\t\tpublic String getName()\n\t\t{\n\t\t\treturn name;\n\t\t}\n\n\t\tpublic String getColumnName()\n\t\t{\n\t\t\tif (name == null) {\n\t\t\t\treturn \"\" + (index + 1);\n\t\t\t} else {\n\t\t\t\treturn \"\\\"\" + name + \"\\\"\";\n\t\t\t}\n\t\t}\n\n\t\tpublic boolean isStateEmpty()\n\t\t{\n\t\t\treturn stateEmpty;\n\t\t}\n\n\t\tpublic boolean isTransitionEmpty()\n\t\t{\n\t\t\treturn transitionEmpty;\n\t\t}\n\n\t\tpublic boolean isCumulative()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\tif (name != null) {\n\t\t\t\treturn \"\" + (index + 1) + \": \\\"\" + name + \"\\\"\";\n\t\t\t} else {\n\t\t\t\treturn \"\" + (index + 1) + \": <unnamed>\";\n\t\t\t}\n\t\t}\n\n\t\tpublic boolean equals(Object o)\n\t\t{\n\t\t\treturn (o instanceof RewardStructure && ((RewardStructure) o).getIndex() == index && ((RewardStructure) o).isCumulative() == isCumulative());\n\t\t}\n\t}\n\n\tpublic class RewardStructureColumn\n\t{\n\t\tpublic static final int STATE_REWARD = 0;\n\t\tpublic static final int TRANSITION_REWARD = 1;\n\t\tpublic static final int CUMULATIVE_REWARD = 2;\n\n\t\tprivate RewardStructure rewardStructure;\n\t\tprivate int type;\n\n\t\tpublic RewardStructureColumn(RewardStructure rewardStructure, int type)\n\t\t{\n\t\t\tthis.rewardStructure = rewardStructure;\n\t\t\tthis.type = type;\n\t\t}\n\n\t\tpublic String getColumnName()\n\t\t{\n\t\t\tswitch (type) {\n\t\t\tcase (STATE_REWARD):\n\t\t\t\treturn rewardStructure.getColumnName();\n\t\t\tcase (TRANSITION_REWARD):\n\t\t\t\treturn \"[ \" + rewardStructure.getColumnName() + \" ]\";\n\t\t\tcase (CUMULATIVE_REWARD):\n\t\t\t\treturn rewardStructure.getColumnName() + \" (+)\";\n\t\t\t}\n\t\t\treturn \"\";\n\t\t}\n\n\t\tpublic RewardStructure getRewardStructure()\n\t\t{\n\t\t\treturn rewardStructure;\n\t\t}\n\n\t\tpublic void setRewardStructure(RewardStructure rewardStructure)\n\t\t{\n\t\t\tthis.rewardStructure = rewardStructure;\n\t\t}\n\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn getColumnName();\n\t\t}\n\n\t\tpublic boolean isStateReward()\n\t\t{\n\t\t\treturn this.type == RewardStructureColumn.STATE_REWARD;\n\t\t}\n\n\t\tpublic boolean isTransitionReward()\n\t\t{\n\t\t\treturn this.type == RewardStructureColumn.TRANSITION_REWARD;\n\t\t}\n\n\t\tpublic boolean isCumulativeReward()\n\t\t{\n\t\t\treturn this.type == RewardStructureColumn.CUMULATIVE_REWARD;\n\t\t}\n\n\t\tpublic void setStateReward()\n\t\t{\n\t\t\tthis.type = RewardStructureColumn.STATE_REWARD;\n\t\t}\n\n\t\tpublic void setTransitionReward()\n\t\t{\n\t\t\tthis.type = RewardStructureColumn.TRANSITION_REWARD;\n\t\t}\n\n\t\tpublic void setCumulativeReward()\n\t\t{\n\t\t\tthis.type = RewardStructureColumn.CUMULATIVE_REWARD;\n\t\t}\n\t}\n\n\tpublic class RewardStructureValue\n\t{\n\t\tprivate RewardStructureColumn rewardStructureColumn;\n\t\tprivate Double rewardValue;\n\t\tprivate boolean hasChanged;\n\n\t\tprivate boolean rewardValueUnknown;\n\n\t\tpublic RewardStructureValue(RewardStructureColumn rewardStructureColumn, Double rewardValue)\n\t\t{\n\t\t\tthis.rewardStructureColumn = rewardStructureColumn;\n\t\t\tthis.rewardValue = rewardValue;\n\t\t\tthis.hasChanged = true;\n\n\t\t\tthis.rewardValueUnknown = false;\n\t\t}\n\n\t\tpublic RewardStructureColumn getRewardStructureColumn()\n\t\t{\n\t\t\treturn rewardStructureColumn;\n\t\t}\n\n\t\tpublic void setRewardStructureColumn(RewardStructureColumn rewardStructureColumn)\n\t\t{\n\t\t\tthis.rewardStructureColumn = rewardStructureColumn;\n\t\t}\n\n\t\tpublic Double getRewardValue()\n\t\t{\n\t\t\treturn rewardValue;\n\t\t}\n\n\t\tpublic void setRewardValue(Double rewardValue)\n\t\t{\n\t\t\tthis.rewardValue = rewardValue;\n\t\t}\n\n\t\tpublic void setRewardValueUnknown(boolean unknown)\n\t\t{\n\t\t\tthis.rewardValueUnknown = unknown;\n\t\t}\n\n\t\tpublic boolean isRewardValueUnknown()\n\t\t{\n\t\t\treturn this.rewardValueUnknown;\n\t\t}\n\n\t\tpublic boolean hasChanged()\n\t\t{\n\t\t\treturn hasChanged;\n\t\t}\n\n\t\tpublic void setChanged(boolean hasChanged)\n\t\t{\n\t\t\tthis.hasChanged = hasChanged;\n\t\t}\n\t}\n\t\n\tpublic class MemoryValue\n\t{\n\t\tprivate Object value;\n\t\tprivate boolean memoryValueUnknown;\n\n\t\tpublic MemoryValue(Object value)\n\t\t{\n\t\t\tthis.value = value;\n\t\t}\n\n\t\tpublic Object getValue()\n\t\t{\n\t\t\treturn value;\n\t\t}\n\n\t\tpublic void setValue(Object value)\n\t\t{\n\t\t\tthis.value = value;\n\t\t}\n\t\t\n\t\tpublic void setMemoryValueUnknown(boolean unknown)\n\t\t{\n\t\t\tthis.memoryValueUnknown = unknown;\n\t\t}\n\n\t\tpublic boolean isMemoryValueUnknown()\n\t\t{\n\t\t\treturn this.memoryValueUnknown;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/simulator/package-info.java",
    "content": "/**\n * The user interface to the simulator supplied in the GUI.\n */\npackage userinterface.simulator;\n"
  },
  {
    "path": "prism/src/userinterface/util/BooleanProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport javax.swing.border.*;\nimport java.awt.event.*;\n\npublic class BooleanProperty extends SingleProperty\n{\n    JPanel pan = new JPanel();\n    JCheckBox renderer = new JCheckBox();\n    \n    /** Creates a new instance of BooleanProperty */\n    public BooleanProperty(PropertyOwner owner,String name, boolean property)\n    {\n        this(owner, name, property, \"\");\n    }\n    \n    public BooleanProperty(PropertyOwner owner,String name, boolean property, String comment)\n    {\n        super(owner, name, Boolean.valueOf(property), \"\", false, comment);\n        //FlowLayout fl = new FlowLayout(FlowLayout.CENTER, 0, 0);\n        pan.setLayout(new GridBagLayout());\n        renderer.setBorder(null);\n        pan.add(renderer);\n    }\n    \n    public void setBoolValue(boolean property)\n    {\n        try\n        {\n            setProperty(Boolean.valueOf(property));\n        }\n        catch(PropertyException e)\n        {\n            //This will NEVER happen! (hopefully!)\n        }\n    }\n    \n    public boolean getBoolValue()\n    {\n        return ((Boolean)getProperty()).booleanValue();\n    }\n    \n    public void setProperty(Object property) throws PropertyException\n    {\n        //System.out.println(\"setting bool property\");\n        if(property instanceof Boolean)\n            super.setProperty(property);\n        else if(property instanceof String)\n        {\n            if(property.toString().equals(\"true\") || property.toString().equals(\"false\"))\n                super.setProperty(Boolean.valueOf(Boolean.getBoolean((String)property)));\n            return;\n            \n        }\n        else\n        {\n            throw new PropertyException(\"Value must be of type Boolean\");\n        }\n        \n    }\n\n\tpublic void setEnabled(boolean enabled)\n\t{\n\t\tsuper.setEnabled(enabled);\n\n\t\tif(renderer!=null)renderer.setEnabled(enabled);\n\t}\n    \n    \n    public Component getTableCellRendererComponent(JTable table, Object value,\n    boolean isSelected, boolean hasFocus, int row, int column)\n    {\n        renderer.setOpaque(true);\n        renderer.setSelected(getBoolValue());\n        if (isSelected)\n        {\n            renderer.setForeground(table.getSelectionForeground());\n            renderer.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            renderer.setForeground(table.getForeground());\n            renderer.setBackground(table.getBackground());\n        }\n        \n        if (hasFocus)\n        {\n            pan.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n            if (table.isCellEditable(row, column))\n            {\n                pan.setForeground( UIManager.getColor(\"Table.focusCellForeground\") );\n                pan.setBackground( UIManager.getColor(\"Table.focusCellBackground\") );\n            }\n        } \n        else\n        {\n            pan.setBorder(new EmptyBorder(0, 2, 2, 1));\n            pan.setForeground( UIManager.getColor(\"Table.focusCellForeground\") );\n                pan.setBackground( UIManager.getColor(\"Table.focusCellBackground\") );\n        }\n        \n        if(!isEnabled())\n        {\n            pan.setBackground(Color.lightGray);\n            renderer.setEnabled(false);\n        }\n        else\n        {\n            renderer.setEnabled(true);\n        }\n        \n        return pan;\n    }\n    \n    public Component getTableCellRendererComponentMulti(JTable table, Object value,\n        boolean isSelected, boolean hasFocus, int row, int column, boolean allTheSame)\n    {\n        \n        if(allTheSame) \n            return getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);\n        \n        renderer.setOpaque(true);\n        renderer.setSelected(getBoolValue());\n        if (isSelected)\n        {\n            \n            renderer.setBackground(table.getSelectionBackground());\n        }\n        else\n        {\n            \n            renderer.setBackground(table.getBackground());\n        }\n        \n        if (hasFocus)\n        {\n            pan.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n            if (table.isCellEditable(row, column))\n            {\n                pan.setForeground( UIManager.getColor(\"Table.focusCellForeground\") );\n                pan.setBackground( new Color(240,240,240) );\n            }\n        } \n        else\n        {\n            pan.setBorder(new EmptyBorder(0, 2, 2, 1));\n            pan.setForeground( UIManager.getColor(\"Table.focusCellForeground\") );\n            pan.setBackground( new Color(240,240,240) );\n        }\n        \n        //renderer.setEnabled(false);\n        \n        \n        return pan;\n    }\n    \n    //THIS WILL NEED TO OVERRIDE THE EDITOR\n    public Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column) \n    {\n        renderer.setSelected(getBoolValue());\n        pan.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        \n                pan.setForeground( UIManager.getColor(\"Table.focusCellForeground\") );\n                pan.setBackground( UIManager.getColor(\"Table.focusCellBackground\") );\n           if(!isEnabled())\n        {\n            pan.setBackground(Color.lightGray);\n            renderer.setEnabled(false);\n        }\n        else\n        {\n            renderer.setEnabled(true);\n        }\n        return pan;\n    }\n    \n    public Component getTableCellEditorComponentMulti(JTable table, Object value, boolean isSelected, int row, int column, boolean allTheSame) \n    {\n        if(allTheSame)\n        {\n            return getTableCellEditorComponent(table, value, isSelected, row, column);\n        }\n        //renderer.setSelected(getBoolValue());\n        pan.setBorder( UIManager.getBorder(\"Table.focusCellHighlightBorder\") );\n        \n                pan.setForeground( UIManager.getColor(\"Table.focusCellForeground\") );\n                pan.setBackground( new Color(240,240,240));\n            if(!isEnabled())\n        {\n            pan.setBackground(Color.lightGray);\n            renderer.setEnabled(false);\n        }\n        else\n        {\n            renderer.setEnabled(true);\n        }\n        return pan;\n    }\n    \n    public Boolean getEditorValue()\n    {\n        \n        return Boolean.valueOf(renderer.isSelected()); \n    }\n    \n    public void addListenerToEditor(ActionListener e)\n    {\n        renderer.addActionListener(e);\n    }\n    \n    public void removeListenerFromEditor(ActionListener e)\n    {\n        renderer.removeActionListener(e);\n    }\n    \n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/util/ChoiceProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.util.*;\nimport javax.swing.*;\nimport java.awt.*;\nimport java.awt.event.*;\n\npublic class ChoiceProperty extends SingleProperty\n{\n\tprivate ArrayList<String> properties;\n\tprivate int currIndex;\n\n\t//if this variable is set to false, this means extra choices can be added.\n\tprivate boolean fixedSize;\n\n\t//Editor\n\tprivate DefaultComboBoxModel listModel;\n\tprivate JComboBox editor;\n\n\t/** Creates a new instance of DoubleProperty */\n\tpublic ChoiceProperty(PropertyOwner owner, String name, String[] props, int startIndex)\n\t{\n\t\tthis(owner, name, props, startIndex, \"\");\n\t}\n\n\tpublic ChoiceProperty(PropertyOwner owner, String name, String[] props, int startIndex, String comment)\n\t{\n\t\tsuper(owner, name, props[startIndex], \"\", false, comment);\n\t\tproperties = new ArrayList<String>();\n\t\tfor (int i = 0; i < props.length; i++) {\n\t\t\tproperties.add(props[i]);\n\t\t}\n\t\tthis.currIndex = startIndex;\n\t\tthis.fixedSize = true;\n\n\t\tlistModel = new DefaultComboBoxModel(props);\n\t\teditor = new JComboBox(listModel);\n\t\teditor.setEditable(false);\n\t\tFont f = editor.getFont();\n\t\teditor.setFont(new Font(f.getName(), Font.PLAIN, f.getSize()));\n\t\teditor.setBackground(Color.WHITE);\n\t\teditor.setBorder(null);\n\n\t\tpan.setLayout(new BorderLayout());\n\t\tpan.add(editor, BorderLayout.CENTER);\n\n\t}\n\n\tpublic String getValue()\n\t{\n\t\tString val;\n\t\ttry {\n\t\t\tval = (String) super.getProperty();\n\t\t} catch (Exception e) {\n\t\t\tval = properties.get(currIndex);\n\t\t\ttry {\n\t\t\t\tsetProperty(val);\n\t\t\t} catch (Exception ex) {\n\t\t\t\t//do nothing\n\t\t\t}\n\t\t}\n\t\treturn val;\n\t}\n\n\tpublic int getNumChoices()\n\t{\n\t\tif (properties == null)\n\t\t\treturn 0;\n\t\treturn properties.size();\n\t}\n\n\tpublic String getChoice(int i)\n\t{\n\t\treturn properties.get(i);\n\t}\n\n\tpublic int getCurrentIndex()\n\t{\n\t\treturn currIndex;\n\t}\n\n\tpublic void setSelectedIndex(int i) throws PropertyException\n\t{\n\t\tcurrIndex = i;\n\t\tsetProperty(properties.get(i), true);\n\t}\n\n\tpublic void setEnabled(boolean enabled)\n\t{\n\t\tsuper.setEnabled(enabled);\n\n\t\tif (editor != null)\n\t\t\teditor.setEnabled(enabled);\n\t}\n\n\t/*  \n\t *  This method first checks whether the property is a string.\n\t *  If the string is a valid choice, then that choice is selected\n\t *  If not, if this ChoiceProperty is not a fixed size, the new \n\t *  choice is added.  Any problems cause a PropertyException\n\t */\n\tpublic void setProperty(Object property, boolean notifyObservers) throws PropertyException\n\t{\n\t\tif (properties == null)\n\t\t\tproperties = new ArrayList<String>();\n\t\tif (listModel == null)\n\t\t\tlistModel = new DefaultComboBoxModel();\n\t\tif (property instanceof String) {\n\t\t\tString comp = (String) property;\n\t\t\tboolean found = false;\n\t\t\tfor (int i = 0; i < getNumChoices(); i++) {\n\t\t\t\tif (getChoice(i).equals(comp)) {\n\t\t\t\t\tcurrIndex = i;\n\n\t\t\t\t\tsuper.setProperty(getChoice(i), notifyObservers);\n\t\t\t\t\tfound = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!found) {\n\t\t\t\tif (isFixedSize()) {\n\t\t\t\t\tthrow new PropertyException(\"Unknown property String\");\n\t\t\t\t} else {\n\t\t\t\t\tproperties.add(comp);\n\t\t\t\t\tcurrIndex = properties.size() - 1;\n\t\t\t\t\tlistModel.addElement(comp);\n\t\t\t\t\tsuper.setProperty(getChoice(currIndex), notifyObservers);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\telse {\n\t\t\tthrow new PropertyException(\"Value must be a String\");\n\t\t}\n\n\t}\n\n\t/**\n\t * Getter for property fixedSize.\n\t * @return Value of property fixedSize.\n\t */\n\tpublic boolean isFixedSize()\n\t{\n\t\treturn fixedSize;\n\t}\n\n\t/**\n\t * Setter for property fixedSize.\n\t * @param fixedSize New value of property fixedSize.\n\t */\n\tpublic void setFixedSize(boolean fixedSize)\n\t{\n\t\tthis.fixedSize = fixedSize;\n\t\teditor.setEditable(!fixedSize);\n\t}\n\n\tJPanel pan = new JPanel();\n\n\t//THIS WILL NEED TO OVERRIDE THE EDITOR\n\tpublic Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column)\n\t{\n\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\treturn pan;\n\t}\n\n\tpublic Component getTableCellEditorComponentMulti(JTable table, Object value, boolean isSelected, int row, int column, boolean allTheSame)\n\t{\n\t\tif (allTheSame) {\n\t\t\treturn getTableCellEditorComponent(table, value, isSelected, row, column);\n\t\t}\n\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\teditor.setBackground(new Color(240, 240, 240));\n\n\t\treturn pan;\n\t}\n\n\tpublic String getEditorValue()\n\t{\n\n\t\treturn (String) editor.getSelectedItem();\n\t}\n\n\tpublic void addListenerToEditor(ActionListener e)\n\t{\n\t\teditor.addActionListener(e);\n\t}\n\n\tpublic void removeListenerFromEditor(ActionListener e)\n\t{\n\t\teditor.removeActionListener(e);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/ColourProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.awt.*;\nimport javax.swing.*;\nimport java.awt.event.*;\nimport javax.swing.border.*;\nimport java.util.*;\n\npublic class ColourProperty extends SingleProperty\n{\n\tprivate ArrayList<ActionListener> actionListeners;\n\n\t/** Creates a new instance of FontProperty */\n\tpublic ColourProperty(PropertyOwner owner, String name, Color property)\n\t{\n\t\tthis(owner, name, property, \"\");\n\t}\n\n\tpublic ColourProperty(PropertyOwner owner, String name, Color property, String comment)\n\t{\n\t\tsuper(owner, name, property, \"\", false, comment);\n\t\t//FlowLayout fl = new FlowLayout(FlowLayout.CENTER, 0, 0);\n\t\tpan.setLayout(new BorderLayout());\n\t\trenderer.setBorder(null);\n\t\tpan.add(renderer);\n\n\t\tactionListeners = new ArrayList<ActionListener>();\n\n\t\tedit = new JButton(\"...\");\n\t\tedit.setPreferredSize(new Dimension(20, 30));\n\n\t\teditValue = Color.BLACK;\n\n\t\tedit.addActionListener(new ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\t//editValue = chart.ChartColorChooser.showDialog(GUIPrism.getGUI(), \"Choose Colour\", editValue);\n\t\t\t\tfireActionPerformed(e);\n\t\t\t}\n\n\t\t});\n\t}\n\n\tpublic void setColor(Color property)\n\t{\n\t\ttry {\n\t\t\tsetProperty(property);\n\t\t} catch (PropertyException e) {\n\t\t\t//This will NEVER happen! (hopefully!)\n\t\t}\n\t}\n\n\tpublic Color getColor()\n\t{\n\t\treturn (Color) getProperty();\n\t}\n\n\tpublic void setProperty(Object property) throws PropertyException\n\t{\n\t\tif (property instanceof Color)\n\t\t\tsuper.setProperty(property);\n\t\telse {\n\t\t\tthrow new PropertyException(\"Value must be of type Color\");\n\t\t}\n\n\t}\n\n\tpublic void setEnabled(boolean enabled)\n\t{\n\t\tsuper.setEnabled(enabled);\n\n\t\tif (renderer != null)\n\t\t\trenderer.setEnabled(enabled);\n\t\tif (edit != null)\n\t\t\tedit.setEnabled(enabled);\n\t}\n\n\tJPanel pan = new JPanel();\n\tJPanel renderer = new JPanel();\n\n\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t{\n\t\tif (editDocked)\n\t\t\t;\n\t\t{\n\t\t\tpan.remove(edit);\n\t\t\teditDocked = false;\n\t\t}\n\n\t\trenderer.setOpaque(true);\n\t\trenderer.setBackground(getColor());\n\n\t\tif (hasFocus) {\n\t\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t}\n\t\t} else {\n\t\t\tpan.setBorder(new EmptyBorder(0, 2, 2, 1));\n\t\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t}\n\n\t\treturn pan;\n\t}\n\n\tpublic Component getTableCellRendererComponentMulti(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column,\n\t\t\tboolean allTheSame)\n\t{\n\t\tif (allTheSame) {\n\t\t\treturn getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);\n\t\t} else {\n\t\t\tif (editDocked)\n\t\t\t\t;\n\t\t\t{\n\t\t\t\tpan.remove(edit);\n\t\t\t\teditDocked = false;\n\t\t\t}\n\n\t\t\trenderer.setOpaque(true);\n\t\t\trenderer.setBackground(new Color(240, 240, 240));\n\n\t\t\tif (hasFocus) {\n\t\t\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tpan.setBorder(new EmptyBorder(0, 2, 2, 1));\n\t\t\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t}\n\t\t\treturn pan;\n\t\t}\n\t}\n\n\tJButton edit;\n\tboolean editDocked = false;\n\n\t//THIS WILL NEED TO OVERRIDE THE EDITOR\n\tpublic Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column)\n\t{\n\t\teditValue = getColor();\n\t\tif (!editDocked) {\n\t\t\tpan.add(edit, BorderLayout.EAST);\n\t\t\teditDocked = true;\n\t\t}\n\t\t//renderer.setSelected(getBoolValue());\n\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\n\t\treturn pan;\n\t}\n\n\tpublic Component getTableCellEditorComponentMulti(JTable table, Object value, boolean isSelected, int row, int column, boolean allTheSame)\n\t{\n\t\tif (allTheSame) {\n\t\t\treturn getTableCellEditorComponent(table, value, isSelected, row, column);\n\t\t}\n\t\teditValue = getColor();\n\t\tif (!editDocked) {\n\t\t\tpan.add(edit, BorderLayout.EAST);\n\t\t\teditDocked = true;\n\t\t}\n\n\t\trenderer.setBackground(new Color(240, 240, 240));\n\t\t//renderer.setSelected(getBoolValue());\n\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\n\t\treturn pan;\n\t}\n\n\tpublic Color getEditorValue()\n\t{\n\t\treturn editValue;\n\t}\n\n\tprivate Color editValue;\n\n\tpublic void addListenerToEditor(ActionListener e)\n\t{\n\t\tactionListeners.add(e);\n\t}\n\n\tpublic void removeListenerFromEditor(ActionListener e)\n\t{\n\t\tactionListeners.remove(e);\n\t}\n\n\tpublic void fireActionPerformed(ActionEvent e)\n\t{\n\t\tfor (int i = 0; i < actionListeners.size(); i++) {\n\t\t\tactionListeners.get(i).actionPerformed(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/DoubleProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\npublic class DoubleProperty extends SingleProperty\n{\n    /** Creates a new instance of DoubleProperty */\n    public DoubleProperty(PropertyOwner owner,String name, double property)\n    {\n        this(owner, name, property, \"\");\n    }\n    \n    public DoubleProperty(PropertyOwner owner,String name, double property, String comment)\n    {\n        super(owner,name, Double.valueOf(property), \"\", false, comment);\n    }\n    \n    public void setValue(double property)\n    {\n        setValue(property, true);\n    }\n    \n    public void setValue(double property, boolean notifyObservers)\n    {\n        try\n        {\n            setProperty(Double.valueOf(property), notifyObservers);\n        }\n        catch(PropertyException e)\n        {\n            //This will NEVER happen! (hopefully!)\n        }\n    }\n    \n    public double getValue()\n    {\n        return ((Double)getProperty()).doubleValue();\n    }\n    \n    public void setProperty(Object property) throws PropertyException\n    {\n        setProperty(property, true);\n    }\n    \n    public void setProperty(Object property, boolean notifyObservers) throws PropertyException\n    {\n        if(property instanceof Double)\n            super.setProperty(property, notifyObservers);\n        else if(property instanceof String)\n        {\n            try\n            {\n            \n                super.setProperty(Double.valueOf(Double.parseDouble((String)property)), notifyObservers);\n                return;\n            }\n            catch(NumberFormatException e)\n            {\n                throw new PropertyException(\"The format of this number is incorrect: \"+(String)property);\n            }\n        }\n        else \n        {\n            throw new PropertyException(\"Value must be a real number\");\n        }\n        \n    }\n\n\t\n    \n   /* public Component getTableCellRendererComponent(JTable table, Object value,\n        boolean isSelected, boolean hasFocus, int row, int column)\n    {\n        return new DefaultTableCellRenderer().getTableCellRendererComponent\n        (table, value, isSelected, hasFocus, row, column);\n    }*/\n    \n    //THIS WILL NEED TO OVERRIDE THE EDITOR\n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/util/ExpressionProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.awt.Color;\nimport java.awt.Component;\nimport java.awt.Insets;\n\nimport javax.swing.JTable;\nimport javax.swing.JTextArea;\nimport javax.swing.UIManager;\nimport javax.swing.border.EmptyBorder;\n\nimport prism.Prism;\nimport prism.PrismLangException;\n\n/**\n * This does not store an expression, it actually maintains a string which is\n * tested for its validity with the PRISM parser\n */\npublic class ExpressionProperty extends SingleProperty\n{\n\n\tprotected Prism pr;\n\n\tprivate boolean valid;\n\n\t/** Creates a new instance of ExpressionProperty */\n\tpublic ExpressionProperty(PropertyOwner owner, String name, String value, Prism pr)\n\t{\n\t\tthis(owner, name, value, \"\", pr);\n\t}\n\n\tpublic ExpressionProperty(PropertyOwner owner, String name, String value, String comment, Prism pr)\n\t{\n\t\tsuper(owner, name, \"\", \"\", true, comment);\n\t\tthis.pr = pr;\n\t\tvalid = true;\n\t\tarea = new JTextArea();\n\t\tarea.setLineWrap(false);\n\t\tarea.setOpaque(true);\n\t\ttry {\n\t\t\tsetProperty(value);\n\t\t} catch (Exception e) {\n\t\t}\n\t}\n\n\tpublic String getExpression()\n\t{\n\t\treturn (String) getProperty();\n\t}\n\n\tpublic void setProperty(Object property) throws PropertyException\n\t{\n\t\tString expression = property.toString();\n\t\ttry {\n\t\t\tif (pr == null)\n\t\t\t\tthrow new PrismLangException(\"\");\n\t\t\tif (!expression.equals(\"\")) {\n\t\t\t\tPrism.parseSingleExpressionString(expression);\n\t\t\t}\n\t\t\tvalid = true;\n\t\t} catch (PrismLangException e) {\n\t\t\tvalid = false;\n\t\t}\n\t\tsuper.setProperty(property);\n\t}\n\n\tpublic void setEnabled(boolean enabled)\n\t{\n\t\tsuper.setEnabled(enabled);\n\n\t\tif (area != null)\n\t\t\tarea.setEnabled(enabled);\n\t}\n\n\tJTextArea area;\n\n\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t{\n\t\t////System.out.println(\"rendering \"+value.toString());\n\t\tif (isSelected) {\n\t\t\tarea.setForeground(table.getSelectionForeground());\n\t\t\tarea.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\tarea.setForeground(table.getForeground());\n\t\t\tarea.setBackground(table.getBackground());\n\t\t}\n\n\t\tarea.setFont(table.getFont());\n\n\t\tif (hasFocus) {\n\t\t\tarea.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\tarea.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\tarea.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t}\n\t\t} else {\n\t\t\tarea.setBorder(new EmptyBorder(0, 2, 2, 1));\n\t\t}\n\t\t//area.setBackground( Color.yellow);\n\t\tarea.setMargin(new Insets(0, 2, 4, 2));\n\t\tarea.setText((value == null) ? \"\" : toString());\n\n\t\tif (!valid) {\n\t\t\tarea.setForeground(Color.red);\n\n\t\t}\n\t\treturn area;\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/FontChooser.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JDialogFormInfo\">\n  <Properties>\n    <Property name=\"resizable\" type=\"boolean\" value=\"false\"/>\n  </Properties>\n  <SyntheticProperties>\n    <SyntheticProperty name=\"formSizePolicy\" type=\"int\" value=\"1\"/>\n  </SyntheticProperties>\n  <Events>\n    <EventHandler event=\"windowClosing\" listener=\"java.awt.event.WindowListener\" parameters=\"java.awt.event.WindowEvent\" handler=\"closeDialog\"/>\n  </Events>\n  <AuxValues>\n    <AuxValue name=\"designerSize\" type=\"java.awt.Dimension\" value=\"-84,-19,0,5,115,114,0,18,106,97,118,97,46,97,119,116,46,68,105,109,101,110,115,105,111,110,65,-114,-39,-41,-84,95,68,20,2,0,2,73,0,6,104,101,105,103,104,116,73,0,5,119,105,100,116,104,120,112,0,0,1,-102,0,0,1,-85\"/>\n  </AuxValues>\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JTabbedPane\" name=\"theTabs\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"North\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"fontPanel\">\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Font\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Font\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel35\">\n              <Properties>\n                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[450, 2147483647]\"/>\n                </Property>\n              </Properties>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                  <BorderConstraints direction=\"Center\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n              <SubComponents>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel36\">\n                  <Properties>\n                    <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[450, 100]\"/>\n                    </Property>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[450, 100]\"/>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"Center\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Container class=\"javax.swing.JPanel\" name=\"jPanel37\">\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"Center\"/>\n                        </Constraint>\n                      </Constraints>\n\n                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\"/>\n                      <SubComponents>\n                        <Container class=\"javax.swing.JPanel\" name=\"jPanel38\">\n                          <Properties>\n                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[200, 183]\"/>\n                            </Property>\n                          </Properties>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel39\">\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"North\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Component class=\"javax.swing.JTextField\" name=\"fontBox\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n                                </Component>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel40\">\n                                  <Properties>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 10]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 10]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel41\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"North\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JLabel\" name=\"jLabel4\">\n                                      <Properties>\n                                        <Property name=\"displayedMnemonic\" type=\"int\" value=\"70\"/>\n                                        <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                                          <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                                        </Property>\n                                        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n                                          <ComponentRef name=\"fontList\"/>\n                                        </Property>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Font:\"/>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n                                    </Component>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel42\">\n                                      <Properties>\n                                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"West\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel43\">\n                              <Properties>\n                                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[269, 100]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"Center\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane4\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JList\" name=\"fontList\">\n                                    </Component>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel44\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                        <Container class=\"javax.swing.JPanel\" name=\"jPanel45\">\n                          <Properties>\n                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[100, 163]\"/>\n                            </Property>\n                          </Properties>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBoxLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel46\">\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel47\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"North\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JTextField\" name=\"styleBox\">\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n                                    </Component>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel48\">\n                                      <Properties>\n                                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"West\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                    </Container>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel49\">\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"North\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                      <SubComponents>\n                                        <Component class=\"javax.swing.JLabel\" name=\"jLabel5\">\n                                          <Properties>\n                                            <Property name=\"displayedMnemonic\" type=\"int\" value=\"121\"/>\n                                            <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                                              <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                                            </Property>\n                                            <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                            <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n                                              <ComponentRef name=\"styleList\"/>\n                                            </Property>\n                                            <Property name=\"text\" type=\"java.lang.String\" value=\"Font style:\"/>\n                                          </Properties>\n                                          <Constraints>\n                                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                              <BorderConstraints direction=\"Center\"/>\n                                            </Constraint>\n                                          </Constraints>\n                                        </Component>\n                                        <Container class=\"javax.swing.JPanel\" name=\"jPanel50\">\n                                          <Properties>\n                                            <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                              <Dimension value=\"[5, 10]\"/>\n                                            </Property>\n                                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                              <Dimension value=\"[5, 10]\"/>\n                                            </Property>\n                                          </Properties>\n                                          <Constraints>\n                                            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                              <BorderConstraints direction=\"West\"/>\n                                            </Constraint>\n                                          </Constraints>\n\n                                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                        </Container>\n                                      </SubComponents>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel51\">\n                                  <Properties>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[269, 100]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane5\">\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                      <SubComponents>\n                                        <Component class=\"javax.swing.JList\" name=\"styleList\">\n                                        </Component>\n                                      </SubComponents>\n                                    </Container>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel52\">\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"West\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                        <Container class=\"javax.swing.JPanel\" name=\"jPanel53\">\n                          <Properties>\n                            <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                              <Dimension value=\"[100, 163]\"/>\n                            </Property>\n                          </Properties>\n\n                          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                          <SubComponents>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel54\">\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"North\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Component class=\"javax.swing.JTextField\" name=\"sizeBox\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n                                </Component>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel55\">\n                                  <Properties>\n                                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 10]\"/>\n                                    </Property>\n                                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                      <Dimension value=\"[5, 10]\"/>\n                                    </Property>\n                                  </Properties>\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel56\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"North\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JLabel\" name=\"jLabel6\">\n                                      <Properties>\n                                        <Property name=\"displayedMnemonic\" type=\"int\" value=\"83\"/>\n                                        <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                                          <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                                        </Property>\n                                        <Property name=\"horizontalAlignment\" type=\"int\" value=\"2\"/>\n                                        <Property name=\"labelFor\" type=\"java.awt.Component\" editor=\"org.netbeans.modules.form.ComponentChooserEditor\">\n                                          <ComponentRef name=\"sizeList\"/>\n                                        </Property>\n                                        <Property name=\"text\" type=\"java.lang.String\" value=\"Size:\"/>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"Center\"/>\n                                        </Constraint>\n                                      </Constraints>\n                                    </Component>\n                                    <Container class=\"javax.swing.JPanel\" name=\"jPanel57\">\n                                      <Properties>\n                                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                          <Dimension value=\"[5, 10]\"/>\n                                        </Property>\n                                      </Properties>\n                                      <Constraints>\n                                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                          <BorderConstraints direction=\"West\"/>\n                                        </Constraint>\n                                      </Constraints>\n\n                                      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                    </Container>\n                                  </SubComponents>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                            <Container class=\"javax.swing.JPanel\" name=\"jPanel58\">\n                              <Properties>\n                                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                                  <Dimension value=\"[269, 100]\"/>\n                                </Property>\n                              </Properties>\n                              <Constraints>\n                                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                  <BorderConstraints direction=\"Center\"/>\n                                </Constraint>\n                              </Constraints>\n\n                              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                              <SubComponents>\n                                <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane6\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"Center\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n                                  <SubComponents>\n                                    <Component class=\"javax.swing.JList\" name=\"sizeList\">\n                                    </Component>\n                                  </SubComponents>\n                                </Container>\n                                <Container class=\"javax.swing.JPanel\" name=\"jPanel59\">\n                                  <Constraints>\n                                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                                      <BorderConstraints direction=\"West\"/>\n                                    </Constraint>\n                                  </Constraints>\n\n                                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\"/>\n                                </Container>\n                              </SubComponents>\n                            </Container>\n                          </SubComponents>\n                        </Container>\n                      </SubComponents>\n                    </Container>\n                  </SubComponents>\n                </Container>\n                <Container class=\"javax.swing.JPanel\" name=\"jPanel60\">\n                  <Properties>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"org.netbeans.modules.form.compat2.border.TitledBorderInfo\">\n                        <TitledBorder title=\"Preview\">\n                          <Font PropertyName=\"font\" name=\"Dialog\" size=\"12\" style=\"0\"/>\n                        </TitledBorder>\n                      </Border>\n                    </Property>\n                  </Properties>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"South\"/>\n                    </Constraint>\n                  </Constraints>\n\n                  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n                  <SubComponents>\n                    <Component class=\"javax.swing.JLabel\" name=\"previewLabel\">\n                      <Properties>\n                        <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                          <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                        </Property>\n                        <Property name=\"horizontalAlignment\" type=\"int\" value=\"0\"/>\n                        <Property name=\"text\" type=\"java.lang.String\" value=\"AaBbCcDdEeFf123456789!&quot;£$%^\"/>\n                        <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                          <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n                            <LineBorder/>\n                          </Border>\n                        </Property>\n                        <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                          <Dimension value=\"[207, 75]\"/>\n                        </Property>\n                        <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                          <Dimension value=\"[207, 75]\"/>\n                        </Property>\n                        <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                          <Dimension value=\"[207, 75]\"/>\n                        </Property>\n                      </Properties>\n                      <Constraints>\n                        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                          <BorderConstraints direction=\"North\"/>\n                        </Constraint>\n                      </Constraints>\n                    </Component>\n                  </SubComponents>\n                </Container>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n        <Component class=\"javax.swing.JColorChooser\" name=\"colorChooser\">\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"4\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JTabbedPaneSupportLayout$JTabbedPaneConstraintsDescription\">\n              <JTabbedPaneConstraints tabName=\"Colour\">\n                <Property name=\"tabTitle\" type=\"java.lang.String\" value=\"Colour\"/>\n              </JTabbedPaneConstraints>\n            </Constraint>\n          </Constraints>\n        </Component>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel32\">\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"South\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignGridLayout\">\n        <Property name=\"columns\" type=\"int\" value=\"0\"/>\n        <Property name=\"rows\" type=\"int\" value=\"1\"/>\n      </Layout>\n      <SubComponents>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel33\">\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n            <Property name=\"alignment\" type=\"int\" value=\"0\"/>\n          </Layout>\n          <SubComponents>\n            <Component class=\"javax.swing.JButton\" name=\"defaultButton\">\n              <Properties>\n                <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                  <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                </Property>\n                <Property name=\"mnemonic\" type=\"int\" value=\"68\"/>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Default...\"/>\n              </Properties>\n            </Component>\n          </SubComponents>\n        </Container>\n        <Container class=\"javax.swing.JPanel\" name=\"jPanel34\">\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignFlowLayout\">\n            <Property name=\"alignment\" type=\"int\" value=\"2\"/>\n          </Layout>\n          <SubComponents>\n            <Component class=\"javax.swing.JButton\" name=\"okayButton\">\n              <Properties>\n                <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                  <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                </Property>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"OK\"/>\n                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n              </Properties>\n            </Component>\n            <Component class=\"javax.swing.JButton\" name=\"cancelButton\">\n              <Properties>\n                <Property name=\"font\" type=\"java.awt.Font\" editor=\"org.netbeans.beaninfo.editors.FontEditor\">\n                  <Font name=\"Dialog\" size=\"12\" style=\"0\"/>\n                </Property>\n                <Property name=\"text\" type=\"java.lang.String\" value=\"Cancel\"/>\n                <Property name=\"maximumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[89, 25]\"/>\n                </Property>\n              </Properties>\n            </Component>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/util/FontChooser.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.awt.*;\nimport javax.swing.*;\nimport javax.swing.event.*;\nimport java.awt.event.*;\n\n@SuppressWarnings(\"serial\")\npublic class FontChooser extends javax.swing.JDialog implements ListSelectionListener, ActionListener, FocusListener, ChangeListener\n{\n\tprotected Font lastFont;\n\tprotected Color lastColor;\n\tprotected Font defaultFont;\n\tprotected Color defaultColor;\n\tprotected boolean shouldReturn;\n\n\t/** Creates new form FontChooser */\n\tpublic FontChooser(java.awt.Frame parent)\n\t{\n\t\tsuper(parent, true);\n\t\tinitComponents();\n\t\tpreviewLabel.setBackground(Color.white);\n\t\tdoListModels();\n\t\tdoListeners();\n\t\tshouldReturn = true;\n\t}\n\n\tpublic FontChooser(Dialog parent)\n\t{\n\t\tsuper(parent, true);\n\t\tinitComponents();\n\t\tpreviewLabel.setBackground(Color.white);\n\t\tdoListModels();\n\t\tdoListeners();\n\t\tshouldReturn = true;\n\t\tsetLocationRelativeTo(getParent()); // centre\n\t}\n\n\tpublic static FontColorPair getFont(Dialog parent, Font startFont, Color startColor, Font defaultFont, Color defaultColor)\n\t{\n\t\tFontChooser choose = new FontChooser(parent);\n\n\t\tchoose.shouldReturn = true;\n\t\tchoose.defaultFont = defaultFont;\n\t\tchoose.defaultColor = defaultColor;\n\t\tchoose.lastColor = startColor;\n\t\tchoose.lastFont = startFont;\n\t\tchoose.colorChooser.setColor(choose.lastColor);\n\t\tchoose.setFont(choose.lastFont);\n\t\tchoose.updatePreview();\n\t\tchoose.setVisible(true);\n\n\t\tFontColorPair pair = new FontColorPair();\n\t\tpair.f = choose.lastFont;\n\t\tpair.c = choose.lastColor;\n\n\t\tif (choose.shouldReturn)\n\t\t\treturn pair;\n\t\telse\n\t\t\treturn null;\n\t}\n\n\tpublic static FontColorPair getFont(Frame parent, Font startFont, Color startColor, Font defaultFont, Color defaultColor)\n\t{\n\t\tFontChooser choose = new FontChooser(parent);\n\n\t\tchoose.shouldReturn = true;\n\t\tchoose.defaultFont = defaultFont;\n\t\tchoose.defaultColor = defaultColor;\n\t\tchoose.lastColor = startColor;\n\t\tchoose.lastFont = startFont;\n\t\tchoose.colorChooser.setColor(choose.lastColor);\n\t\tchoose.setFont(choose.lastFont);\n\t\tchoose.updatePreview();\n\t\tchoose.setVisible(true);\n\n\t\tFontColorPair pair = new FontColorPair();\n\t\tpair.f = choose.lastFont;\n\t\tpair.c = choose.lastColor;\n\n\t\tif (choose.shouldReturn)\n\t\t\treturn pair;\n\t\telse\n\t\t\treturn null;\n\t}\n\n\tprivate void doListModels()\n\t{\n\t\tGraphicsEnvironment ge = GraphicsEnvironment.getLocalGraphicsEnvironment();\n\t\tString[] allFonts = ge.getAvailableFontFamilyNames();\n\t\t//Font[]allFonts = ge.getAllFonts();\n\t\tString[] styles = { \"Plain\", \"Bold\", \"Italic\", \"Bold Italic\" };\n\t\tString[] sizes = { \"8\", \"9\", \"10\", \"11\", \"12\", \"14\", \"16\", \"18\", \"20\" };\n\n\t\tDefaultComboBoxModel fontModel = new DefaultComboBoxModel(allFonts);\n\t\tDefaultComboBoxModel styleModel = new DefaultComboBoxModel(styles);\n\t\tDefaultComboBoxModel sizeModel = new DefaultComboBoxModel(sizes);\n\n\t\tfontList.setModel(fontModel);\n\t\tstyleList.setModel(styleModel);\n\t\tsizeList.setModel(sizeModel);\n\t}\n\n\tprivate void doListeners()\n\t{\n\t\tfontList.addListSelectionListener(this);\n\t\tstyleList.addListSelectionListener(this);\n\t\tsizeList.addListSelectionListener(this);\n\n\t\tfontBox.addActionListener(this);\n\t\tstyleBox.addActionListener(this);\n\t\tsizeBox.addActionListener(this);\n\n\t\tokayButton.addActionListener(this);\n\t\tcancelButton.addActionListener(this);\n\t\tdefaultButton.addActionListener(this);\n\n\t\tfontPanel.addFocusListener(this);\n\t\ttheTabs.addChangeListener(this);\n\n\t}\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\tprivate void initComponents()//GEN-BEGIN:initComponents\n\t{\n\t\ttheTabs = new javax.swing.JTabbedPane();\n\t\tfontPanel = new javax.swing.JPanel();\n\t\tjPanel35 = new javax.swing.JPanel();\n\t\tjPanel36 = new javax.swing.JPanel();\n\t\tjPanel37 = new javax.swing.JPanel();\n\t\tjPanel38 = new javax.swing.JPanel();\n\t\tjPanel39 = new javax.swing.JPanel();\n\t\tfontBox = new javax.swing.JTextField();\n\t\tjPanel40 = new javax.swing.JPanel();\n\t\tjPanel41 = new javax.swing.JPanel();\n\t\tjLabel4 = new javax.swing.JLabel();\n\t\tjPanel42 = new javax.swing.JPanel();\n\t\tjPanel43 = new javax.swing.JPanel();\n\t\tjScrollPane4 = new javax.swing.JScrollPane();\n\t\tfontList = new javax.swing.JList();\n\t\tjPanel44 = new javax.swing.JPanel();\n\t\tjPanel45 = new javax.swing.JPanel();\n\t\tjPanel46 = new javax.swing.JPanel();\n\t\tjPanel47 = new javax.swing.JPanel();\n\t\tstyleBox = new javax.swing.JTextField();\n\t\tjPanel48 = new javax.swing.JPanel();\n\t\tjPanel49 = new javax.swing.JPanel();\n\t\tjLabel5 = new javax.swing.JLabel();\n\t\tjPanel50 = new javax.swing.JPanel();\n\t\tjPanel51 = new javax.swing.JPanel();\n\t\tjScrollPane5 = new javax.swing.JScrollPane();\n\t\tstyleList = new javax.swing.JList();\n\t\tjPanel52 = new javax.swing.JPanel();\n\t\tjPanel53 = new javax.swing.JPanel();\n\t\tjPanel54 = new javax.swing.JPanel();\n\t\tsizeBox = new javax.swing.JTextField();\n\t\tjPanel55 = new javax.swing.JPanel();\n\t\tjPanel56 = new javax.swing.JPanel();\n\t\tjLabel6 = new javax.swing.JLabel();\n\t\tjPanel57 = new javax.swing.JPanel();\n\t\tjPanel58 = new javax.swing.JPanel();\n\t\tjScrollPane6 = new javax.swing.JScrollPane();\n\t\tsizeList = new javax.swing.JList();\n\t\tjPanel59 = new javax.swing.JPanel();\n\t\tjPanel60 = new javax.swing.JPanel();\n\t\tpreviewLabel = new javax.swing.JLabel();\n\t\tcolorChooser = new javax.swing.JColorChooser();\n\t\tjPanel32 = new javax.swing.JPanel();\n\t\tjPanel33 = new javax.swing.JPanel();\n\t\tdefaultButton = new javax.swing.JButton();\n\t\tjPanel34 = new javax.swing.JPanel();\n\t\tokayButton = new javax.swing.JButton();\n\t\tcancelButton = new javax.swing.JButton();\n\n\t\tsetResizable(false);\n\t\taddWindowListener(new java.awt.event.WindowAdapter()\n\t\t{\n\t\t\tpublic void windowClosing(java.awt.event.WindowEvent evt)\n\t\t\t{\n\t\t\t\tcloseDialog(evt);\n\t\t\t}\n\t\t});\n\n\t\tfontPanel.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel35.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel35.setMaximumSize(new java.awt.Dimension(450, 2147483647));\n\t\tjPanel36.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel36.setMaximumSize(new java.awt.Dimension(450, 100));\n\t\tjPanel36.setPreferredSize(new java.awt.Dimension(450, 100));\n\t\tjPanel37.setLayout(new javax.swing.BoxLayout(jPanel37, javax.swing.BoxLayout.X_AXIS));\n\n\t\tjPanel38.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel38.setPreferredSize(new java.awt.Dimension(200, 183));\n\t\tjPanel39.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel39.add(fontBox, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel40.setMinimumSize(new java.awt.Dimension(5, 10));\n\t\tjPanel40.setPreferredSize(new java.awt.Dimension(5, 10));\n\t\tjPanel39.add(jPanel40, java.awt.BorderLayout.WEST);\n\n\t\tjPanel41.setLayout(new java.awt.BorderLayout());\n\n\t\tjLabel4.setDisplayedMnemonic('F');\n\t\tjLabel4.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n\t\tjLabel4.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n\t\tjLabel4.setLabelFor(fontList);\n\t\tjLabel4.setText(\"Font:\");\n\t\tjPanel41.add(jLabel4, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel42.setMinimumSize(new java.awt.Dimension(5, 10));\n\t\tjPanel42.setPreferredSize(new java.awt.Dimension(5, 10));\n\t\tjPanel41.add(jPanel42, java.awt.BorderLayout.WEST);\n\n\t\tjPanel39.add(jPanel41, java.awt.BorderLayout.NORTH);\n\n\t\tjPanel38.add(jPanel39, java.awt.BorderLayout.NORTH);\n\n\t\tjPanel43.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel43.setPreferredSize(new java.awt.Dimension(269, 100));\n\t\tjScrollPane4.setViewportView(fontList);\n\n\t\tjPanel43.add(jScrollPane4, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel43.add(jPanel44, java.awt.BorderLayout.WEST);\n\n\t\tjPanel38.add(jPanel43, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel37.add(jPanel38);\n\n\t\tjPanel45.setLayout(new javax.swing.BoxLayout(jPanel45, javax.swing.BoxLayout.X_AXIS));\n\n\t\tjPanel45.setPreferredSize(new java.awt.Dimension(100, 163));\n\t\tjPanel46.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel47.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel47.add(styleBox, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel48.setMinimumSize(new java.awt.Dimension(5, 10));\n\t\tjPanel48.setPreferredSize(new java.awt.Dimension(5, 10));\n\t\tjPanel47.add(jPanel48, java.awt.BorderLayout.WEST);\n\n\t\tjPanel49.setLayout(new java.awt.BorderLayout());\n\n\t\tjLabel5.setDisplayedMnemonic('y');\n\t\tjLabel5.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n\t\tjLabel5.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n\t\tjLabel5.setLabelFor(styleList);\n\t\tjLabel5.setText(\"Font style:\");\n\t\tjPanel49.add(jLabel5, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel50.setMinimumSize(new java.awt.Dimension(5, 10));\n\t\tjPanel50.setPreferredSize(new java.awt.Dimension(5, 10));\n\t\tjPanel49.add(jPanel50, java.awt.BorderLayout.WEST);\n\n\t\tjPanel47.add(jPanel49, java.awt.BorderLayout.NORTH);\n\n\t\tjPanel46.add(jPanel47, java.awt.BorderLayout.NORTH);\n\n\t\tjPanel51.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel51.setPreferredSize(new java.awt.Dimension(269, 100));\n\t\tjScrollPane5.setViewportView(styleList);\n\n\t\tjPanel51.add(jScrollPane5, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel51.add(jPanel52, java.awt.BorderLayout.WEST);\n\n\t\tjPanel46.add(jPanel51, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel45.add(jPanel46);\n\n\t\tjPanel37.add(jPanel45);\n\n\t\tjPanel53.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel53.setPreferredSize(new java.awt.Dimension(100, 163));\n\t\tjPanel54.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel54.add(sizeBox, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel55.setMinimumSize(new java.awt.Dimension(5, 10));\n\t\tjPanel55.setPreferredSize(new java.awt.Dimension(5, 10));\n\t\tjPanel54.add(jPanel55, java.awt.BorderLayout.WEST);\n\n\t\tjPanel56.setLayout(new java.awt.BorderLayout());\n\n\t\tjLabel6.setDisplayedMnemonic('S');\n\t\tjLabel6.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n\t\tjLabel6.setHorizontalAlignment(javax.swing.SwingConstants.LEFT);\n\t\tjLabel6.setLabelFor(sizeList);\n\t\tjLabel6.setText(\"Size:\");\n\t\tjPanel56.add(jLabel6, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel57.setMinimumSize(new java.awt.Dimension(5, 10));\n\t\tjPanel57.setPreferredSize(new java.awt.Dimension(5, 10));\n\t\tjPanel56.add(jPanel57, java.awt.BorderLayout.WEST);\n\n\t\tjPanel54.add(jPanel56, java.awt.BorderLayout.NORTH);\n\n\t\tjPanel53.add(jPanel54, java.awt.BorderLayout.NORTH);\n\n\t\tjPanel58.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel58.setPreferredSize(new java.awt.Dimension(269, 100));\n\t\tjScrollPane6.setViewportView(sizeList);\n\n\t\tjPanel58.add(jScrollPane6, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel58.add(jPanel59, java.awt.BorderLayout.WEST);\n\n\t\tjPanel53.add(jPanel58, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel37.add(jPanel53);\n\n\t\tjPanel36.add(jPanel37, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel35.add(jPanel36, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel60.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel60.setBorder(new javax.swing.border.TitledBorder(null, \"Preview\", javax.swing.border.TitledBorder.DEFAULT_JUSTIFICATION,\n\t\t\t\tjavax.swing.border.TitledBorder.DEFAULT_POSITION, new java.awt.Font(\"Dialog\", 0, 12)));\n\t\tpreviewLabel.setBackground(new java.awt.Color(255, 255, 255));\n\t\tpreviewLabel.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);\n\t\tpreviewLabel.setText(\"AaBbCcDdEeFf123456789!\\\"\\u00a3$%^\");\n\t\tpreviewLabel.setBorder(new javax.swing.border.LineBorder(new java.awt.Color(0, 0, 0)));\n\t\tpreviewLabel.setMaximumSize(new java.awt.Dimension(207, 75));\n\t\tpreviewLabel.setMinimumSize(new java.awt.Dimension(207, 75));\n\t\tpreviewLabel.setPreferredSize(new java.awt.Dimension(207, 75));\n\t\tjPanel60.add(previewLabel, java.awt.BorderLayout.NORTH);\n\n\t\tjPanel35.add(jPanel60, java.awt.BorderLayout.SOUTH);\n\n\t\tfontPanel.add(jPanel35, java.awt.BorderLayout.CENTER);\n\n\t\ttheTabs.addTab(\"Font\", fontPanel);\n\n\t\ttheTabs.addTab(\"Colour\", colorChooser);\n\n\t\tgetContentPane().add(theTabs, java.awt.BorderLayout.NORTH);\n\n\t\tjPanel32.setLayout(new java.awt.GridLayout(1, 0));\n\n\t\tjPanel33.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.LEFT));\n\n\t\tdefaultButton.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n\t\tdefaultButton.setMnemonic('D');\n\t\tdefaultButton.setText(\"Default...\");\n\t\tjPanel33.add(defaultButton);\n\n\t\tjPanel32.add(jPanel33);\n\n\t\tjPanel34.setLayout(new java.awt.FlowLayout(java.awt.FlowLayout.RIGHT));\n\n\t\tokayButton.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n\t\tokayButton.setText(\"OK\");\n\t\tokayButton.setMaximumSize(new java.awt.Dimension(89, 25));\n\t\tokayButton.setMinimumSize(new java.awt.Dimension(89, 25));\n\t\tokayButton.setPreferredSize(new java.awt.Dimension(89, 25));\n\t\tjPanel34.add(okayButton);\n\n\t\tcancelButton.setFont(new java.awt.Font(\"Dialog\", 0, 12));\n\t\tcancelButton.setText(\"Cancel\");\n\t\tcancelButton.setMaximumSize(new java.awt.Dimension(89, 25));\n\t\tcancelButton.setMinimumSize(new java.awt.Dimension(89, 25));\n\t\tcancelButton.setPreferredSize(new java.awt.Dimension(89, 25));\n\t\tjPanel34.add(cancelButton);\n\n\t\tjPanel32.add(jPanel34);\n\n\t\tgetContentPane().add(jPanel32, java.awt.BorderLayout.SOUTH);\n\n\t\tpack();\n\t}//GEN-END:initComponents\n\n\t/** Closes the dialog */\n\tprivate void closeDialog(java.awt.event.WindowEvent evt)//GEN-FIRST:event_closeDialog\n\t{\n\t\tsetVisible(false);\n\t\tdispose();\n\t}//GEN-LAST:event_closeDialog\n\n\t/**\n\t * @param args the command line arguments\n\t */\n\tpublic static void main(String args[])\n\t{\n\t\tnew FontChooser(new javax.swing.JFrame()).setVisible(true);\n\t}\n\n\tpublic void caretUpdate(CaretEvent e)\n\t{/*\n\t\t   if(e.getSource() == fontBox)\n\t\t   {\n\t\t       String str = fontBox.getText();\n\t\t       for(int i = 0; i < fontList.getModel().getSize(); i++)\n\t\t       {\n\t\t           String listStr = (String)fontList.getModel().getElementAt(i);\n\t\t           if(listStr.startsWith(str))\n\t\t           {\n\t\t               fontList.setSelectedIndex(i);\n\t\t               break;\n\t\t           }\n\t\t       }\n\t\t   }*/\n\t}\n\n\tpublic void actionPerformed(ActionEvent e)\n\t{\n\t\tif (e.getSource() == fontBox) {\n\t\t\tString str = fontBox.getText();\n\t\t\tfor (int i = 0; i < fontList.getModel().getSize(); i++) {\n\t\t\t\tString listStr = ((String) fontList.getModel().getElementAt(i)).toLowerCase();\n\n\t\t\t\tif (listStr.startsWith(str.toLowerCase())) {\n\t\t\t\t\tObject value = fontList.getModel().getElementAt(i);\n\t\t\t\t\tfontList.setSelectedValue(value, true);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\ttempValue = (String) fontList.getSelectedValue();\n\t\t\tif (tempValue != null) {\n\t\t\t\tfontBox.setText(tempValue);\n\t\t\t} else\n\t\t\t\tfontBox.setText(\"\");\n\t\t} else if (e.getSource() == styleBox) {\n\t\t\tString str = styleBox.getText();\n\t\t\tfor (int i = 0; i < styleList.getModel().getSize(); i++) {\n\t\t\t\tString listStr = ((String) styleList.getModel().getElementAt(i)).toLowerCase();\n\n\t\t\t\tif (listStr.startsWith(str.toLowerCase())) {\n\t\t\t\t\tObject value = styleList.getModel().getElementAt(i);\n\t\t\t\t\tstyleList.setSelectedValue(value, true);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\ttempValue = (String) styleList.getSelectedValue();\n\t\t\tif (tempValue != null) {\n\t\t\t\tfontBox.setText(tempValue);\n\t\t\t} else\n\t\t\t\tfontBox.setText(\"\");\n\t\t} else if (e.getSource() == sizeBox) {\n\t\t\tString str = sizeBox.getText();\n\t\t\tboolean found = false;\n\t\t\tfor (int i = 0; i < sizeList.getModel().getSize(); i++) {\n\t\t\t\tString listStr = ((String) sizeList.getModel().getElementAt(i)).toLowerCase();\n\n\t\t\t\tif (listStr.startsWith(str.toLowerCase())) {\n\t\t\t\t\tfound = true;\n\t\t\t\t\tObject value = sizeList.getModel().getElementAt(i);\n\t\t\t\t\tsizeList.setSelectedValue(value, true);\n\t\t\t\t\ttempValue = (String) sizeList.getSelectedValue();\n\t\t\t\t\tif (tempValue != null) {\n\t\t\t\t\t\tsizeBox.setText(tempValue);\n\t\t\t\t\t} else\n\t\t\t\t\t\tsizeBox.setText(\"\");\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!found) {\n\t\t\t\tsizeList.setSelectedIndex(-1);\n\t\t\t}\n\n\t\t} else if (e.getSource() == defaultButton) {\n\t\t\tif (defaultFont != null && defaultColor != null) {\n\t\t\t\tsetFont(defaultFont);\n\t\t\t\tcolorChooser.setColor(defaultColor);\n\t\t\t\tlastColor = colorChooser.getColor();\n\n\t\t\t\tupdatePreview();\n\t\t\t}\n\t\t} else if (e.getSource() == okayButton) {\n\t\t\tsetVisible(false);\n\t\t} else if (e.getSource() == cancelButton) {\n\t\t\tshouldReturn = false;\n\t\t\tsetVisible(false);\n\t\t}\n\n\t\tif (fontValid()) {\n\t\t\tthis.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n\t\t\tthis.lastColor = colorChooser.getColor();\n\n\t\t\tupdatePreview();\n\t\t}\n\t}\n\n\tpublic String getFontName()\n\t{\n\t\treturn fontBox.getText();\n\t}\n\n\tpublic int getFontStyle()\n\t{\n\t\tint style = Font.PLAIN;\n\t\tswitch (styleList.getSelectedIndex()) {\n\t\tcase 0:\n\t\t\tstyle = Font.PLAIN;\n\t\t\tbreak;\n\t\tcase 1:\n\t\t\tstyle = Font.BOLD;\n\t\t\tbreak;\n\t\tcase 2:\n\t\t\tstyle = Font.ITALIC;\n\t\t\tbreak;\n\t\tcase 3:\n\t\t\tstyle = Font.BOLD | Font.ITALIC;\n\t\t}\n\t\treturn style;\n\t}\n\n\tpublic int getFontSize()\n\t{\n\t\tint size = 12;\n\t\ttry {\n\t\t\tsize = Integer.parseInt(sizeBox.getText());\n\t\t} catch (NumberFormatException e) {\n\t\t}\n\t\treturn size;\n\t}\n\n\tpublic boolean fontValid()\n\t{\n\t\tboolean valid = false;\n\n\t\tString str = fontBox.getText();\n\t\tfor (int i = 0; i < fontList.getModel().getSize(); i++) {\n\t\t\tString listStr = ((String) fontList.getModel().getElementAt(i)).toLowerCase();\n\n\t\t\tif (listStr.startsWith(str.toLowerCase())) {\n\t\t\t\tvalid = true;\n\t\t\t}\n\t\t}\n\t\tif (!valid)\n\t\t\treturn false;\n\n\t\treturn valid;\n\t}\n\n\tpublic void setFont(Font f)\n\t{\n\t\tif (f != null) {\n\t\t\tString str = f.getName();\n\t\t\tint style = f.getStyle();\n\t\t\tString size = \"\" + f.getSize();\n\n\t\t\tfor (int i = 0; i < fontList.getModel().getSize(); i++) {\n\t\t\t\tString listStr = ((String) fontList.getModel().getElementAt(i)).toLowerCase();\n\n\t\t\t\tif (listStr.equals(str.toLowerCase())) {\n\t\t\t\t\tObject value = fontList.getModel().getElementAt(i);\n\t\t\t\t\tfontList.setSelectedValue(value, true);\n\t\t\t\t\tfontBox.setText((String) value);\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tswitch (style) {\n\t\t\tcase Font.PLAIN:\n\t\t\t\tstyleList.setSelectedIndex(0);\n\t\t\t\tbreak;\n\t\t\tcase Font.ITALIC:\n\t\t\t\tstyleList.setSelectedIndex(2);\n\t\t\t\tbreak;\n\t\t\tcase Font.BOLD:\n\t\t\t\tstyleList.setSelectedIndex(1);\n\t\t\t\tbreak;\n\t\t\tcase Font.BOLD | Font.ITALIC:\n\t\t\t\tstyleList.setSelectedIndex(3);\n\t\t\t\tbreak;\n\t\t\t}\n\n\t\t\tboolean found = false;\n\t\t\tfor (int i = 0; i < sizeList.getModel().getSize(); i++) {\n\t\t\t\tString listStr = ((String) sizeList.getModel().getElementAt(i)).toLowerCase();\n\n\t\t\t\tif (listStr.equals(size.toLowerCase())) {\n\t\t\t\t\tObject value = sizeList.getModel().getElementAt(i);\n\t\t\t\t\tsizeList.setSelectedValue(value, true);\n\t\t\t\t\tsizeBox.setText((String) value);\n\t\t\t\t\tfound = true;\n\t\t\t\t\tbreak;\n\t\t\t\t}\n\t\t\t}\n\t\t\tif (!found) {\n\t\t\t\tsizeBox.setText(size);\n\t\t\t}\n\n\t\t}\n\t}\n\n\tString tempValue;\n\n\tpublic void valueChanged(ListSelectionEvent e)\n\t{\n\t\tif (e.getSource() == fontList) {\n\t\t\ttempValue = (String) fontList.getSelectedValue();\n\t\t\tif (tempValue != null) {\n\t\t\t\tfontBox.setText(tempValue);\n\t\t\t} else\n\t\t\t\tfontBox.setText(\"\");\n\t\t} else if (e.getSource() == styleList) {\n\t\t\ttempValue = (String) styleList.getSelectedValue();\n\t\t\tif (tempValue != null) {\n\t\t\t\tstyleBox.setText(tempValue);\n\t\t\t} else\n\t\t\t\tstyleBox.setText(\"\");\n\t\t} else if (e.getSource() == sizeList) {\n\t\t\ttempValue = (String) sizeList.getSelectedValue();\n\t\t\tif (tempValue != null) {\n\t\t\t\tsizeBox.setText(tempValue);\n\t\t\t} else\n\t\t\t\tsizeBox.setText(\"\");\n\t\t}\n\n\t\tif (fontValid()) {\n\t\t\tthis.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n\t\t\tthis.lastColor = colorChooser.getColor();\n\n\t\t\tupdatePreview();\n\t\t}\n\t}\n\n\tpublic void updatePreview()\n\t{\n\t\tif (lastFont != null && lastColor != null) {\n\t\t\tpreviewLabel.setForeground(lastColor);\n\t\t\tpreviewLabel.setFont(lastFont);\n\t\t}\n\t}\n\n\tpublic void focusGained(FocusEvent e)\n\t{\n\t\tif (fontValid()) {\n\t\t\tthis.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n\t\t\tthis.lastColor = colorChooser.getColor();\n\n\t\t\tupdatePreview();\n\t\t}\n\t}\n\n\tpublic void focusLost(FocusEvent e)\n\t{\n\t\tif (fontValid()) {\n\t\t\tthis.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n\t\t\tthis.lastColor = colorChooser.getColor();\n\n\t\t\tupdatePreview();\n\t\t}\n\t}\n\n\tpublic void stateChanged(ChangeEvent e)\n\t{\n\t\tif (fontValid()) {\n\t\t\tthis.lastFont = new Font(getFontName(), getFontStyle(), getFontSize());\n\t\t\tthis.lastColor = colorChooser.getColor();\n\n\t\t\tupdatePreview();\n\t\t}\n\t}\n\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tprivate javax.swing.JButton cancelButton;\n\tprotected javax.swing.JColorChooser colorChooser;\n\tprivate javax.swing.JButton defaultButton;\n\tprivate javax.swing.JTextField fontBox;\n\tprivate javax.swing.JList fontList;\n\tprivate javax.swing.JPanel fontPanel;\n\tprivate javax.swing.JLabel jLabel4;\n\tprivate javax.swing.JLabel jLabel5;\n\tprivate javax.swing.JLabel jLabel6;\n\tprivate javax.swing.JPanel jPanel32;\n\tprivate javax.swing.JPanel jPanel33;\n\tprivate javax.swing.JPanel jPanel34;\n\tprivate javax.swing.JPanel jPanel35;\n\tprivate javax.swing.JPanel jPanel36;\n\tprivate javax.swing.JPanel jPanel37;\n\tprivate javax.swing.JPanel jPanel38;\n\tprivate javax.swing.JPanel jPanel39;\n\tprivate javax.swing.JPanel jPanel40;\n\tprivate javax.swing.JPanel jPanel41;\n\tprivate javax.swing.JPanel jPanel42;\n\tprivate javax.swing.JPanel jPanel43;\n\tprivate javax.swing.JPanel jPanel44;\n\tprivate javax.swing.JPanel jPanel45;\n\tprivate javax.swing.JPanel jPanel46;\n\tprivate javax.swing.JPanel jPanel47;\n\tprivate javax.swing.JPanel jPanel48;\n\tprivate javax.swing.JPanel jPanel49;\n\tprivate javax.swing.JPanel jPanel50;\n\tprivate javax.swing.JPanel jPanel51;\n\tprivate javax.swing.JPanel jPanel52;\n\tprivate javax.swing.JPanel jPanel53;\n\tprivate javax.swing.JPanel jPanel54;\n\tprivate javax.swing.JPanel jPanel55;\n\tprivate javax.swing.JPanel jPanel56;\n\tprivate javax.swing.JPanel jPanel57;\n\tprivate javax.swing.JPanel jPanel58;\n\tprivate javax.swing.JPanel jPanel59;\n\tprivate javax.swing.JPanel jPanel60;\n\tprivate javax.swing.JScrollPane jScrollPane4;\n\tprivate javax.swing.JScrollPane jScrollPane5;\n\tprivate javax.swing.JScrollPane jScrollPane6;\n\tprivate javax.swing.JButton okayButton;\n\tprivate javax.swing.JLabel previewLabel;\n\tprivate javax.swing.JTextField sizeBox;\n\tprivate javax.swing.JList sizeList;\n\tprivate javax.swing.JTextField styleBox;\n\tprivate javax.swing.JList styleList;\n\tprivate javax.swing.JTabbedPane theTabs;\n\t// End of variables declaration//GEN-END:variables\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/FontColorPair.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.awt.*;\n\npublic class FontColorPair\n    {\n        \n        public FontColorPair(Font f, Color c)\n        {\n            this.f = f;\n            this.c = c;\n        }\n        public FontColorPair()\n        {\n           \n        }\n        public Font f;\n        public Color c;\n    }\n"
  },
  {
    "path": "prism/src/userinterface/util/FontColorProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.awt.*;\nimport javax.swing.*;\nimport java.awt.event.*;\nimport javax.swing.border.*;\nimport userinterface.*;\nimport java.util.*;\n\npublic class FontColorProperty extends SingleProperty\n{\n\n\tprivate ArrayList<ActionListener> actionListeners;\n\n\t/** Creates a new instance of FontProperty */\n\tpublic FontColorProperty(PropertyOwner owner, String name, FontColorPair property)\n\t{\n\t\tthis(owner, name, property, \"\");\n\t}\n\n\tpublic FontColorProperty(PropertyOwner owner, String name, FontColorPair property, String comment)\n\t{\n\t\tsuper(owner, name, property, \"\", false, comment);\n\t\t//FlowLayout fl = new FlowLayout(FlowLayout.CENTER, 0, 0);\n\t\tpan.setLayout(new BorderLayout());\n\t\trenderer.setBorder(null);\n\t\tpan.add(renderer);\n\n\t\tactionListeners = new ArrayList<ActionListener>();\n\n\t\tedit = new JButton(\"...\");\n\t\tedit.setPreferredSize(new Dimension(20, 30));\n\n\t\teditValue = new FontColorPair(new Font(\"monospaced\", Font.PLAIN, 12), Color.black);\n\n\t\tedit.addActionListener(new ActionListener()\n\t\t{\n\t\t\tpublic void actionPerformed(ActionEvent e)\n\t\t\t{\n\t\t\t\teditValue = FontChooser.getFont(GUIPrism.getGUI(), getFontColorPair().f, getFontColorPair().c, getFontColorPair().f, getFontColorPair().c);\n\t\t\t\tfireActionPerformed(e);\n\t\t\t}\n\n\t\t});\n\t}\n\n\tpublic void setFontColorPair(FontColorPair property)\n\t{\n\t\ttry {\n\t\t\tsetProperty(property);\n\t\t} catch (PropertyException e) {\n\t\t\t//This will NEVER happen! (hopefully!)\n\t\t}\n\t}\n\n\tpublic FontColorPair getFontColorPair()\n\t{\n\t\treturn (FontColorPair) getProperty();\n\t}\n\n\tpublic void setProperty(Object property) throws PropertyException\n\t{\n\t\tif (property instanceof FontColorPair)\n\t\t\tsuper.setProperty(property);\n\t\telse {\n\t\t\tthrow new PropertyException(\"Value must be of type FontColorPair\");\n\t\t}\n\n\t}\n\n\tpublic void setEnabled(boolean enabled)\n\t{\n\t\tsuper.setEnabled(enabled);\n\n\t\tif (renderer != null)\n\t\t\trenderer.setEnabled(enabled);\n\t\tif (edit != null)\n\t\t\tedit.setEnabled(enabled);\n\t}\n\n\tJPanel pan = new JPanel();\n\tJLabel renderer = new JLabel();\n\n\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t{\n\t\tif (editDocked)\n\t\t\t;\n\t\t{\n\t\t\tpan.remove(edit);\n\t\t\teditDocked = false;\n\t\t}\n\n\t\trenderer.setOpaque(true);\n\t\trenderer.setFont(getFontColorPair().f);\n\t\trenderer.setHorizontalTextPosition(SwingConstants.LEFT);\n\t\trenderer.setText(getFontColorPair().f.getFontName() + \" \" + getFontColorPair().f.getSize());\n\n\t\tif (isSelected) {\n\t\t\trenderer.setForeground(getFontColorPair().c);\n\t\t\trenderer.setBackground(table.getSelectionBackground());\n\t\t} else {\n\t\t\trenderer.setForeground(getFontColorPair().c);\n\t\t\trenderer.setBackground(table.getBackground());\n\t\t}\n\n\t\tif (hasFocus) {\n\t\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t}\n\t\t} else {\n\t\t\tpan.setBorder(new EmptyBorder(0, 2, 2, 1));\n\t\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t}\n\n\t\treturn pan;\n\t}\n\n\tpublic Component getTableCellRendererComponentMulti(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column,\n\t\t\tboolean allTheSame)\n\t{\n\t\tif (allTheSame) {\n\t\t\treturn getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);\n\t\t} else {\n\t\t\tif (editDocked)\n\t\t\t\t;\n\t\t\t{\n\t\t\t\tpan.remove(edit);\n\t\t\t\teditDocked = false;\n\t\t\t}\n\n\t\t\trenderer.setOpaque(true);\n\t\t\trenderer.setFont(pan.getFont());\n\t\t\trenderer.setText(\"...\");\n\n\t\t\tif (isSelected) {\n\t\t\t\trenderer.setForeground(Color.lightGray);\n\t\t\t\trenderer.setBackground(table.getSelectionBackground());\n\t\t\t} else {\n\t\t\t\trenderer.setForeground(Color.lightGray);\n\t\t\t\trenderer.setBackground(table.getBackground());\n\t\t\t}\n\n\t\t\tif (hasFocus) {\n\t\t\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tpan.setBorder(new EmptyBorder(0, 2, 2, 1));\n\t\t\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t}\n\n\t\t\treturn pan;\n\t\t}\n\t}\n\n\tJButton edit;\n\tboolean editDocked = false;\n\n\t//THIS WILL NEED TO OVERRIDE THE EDITOR\n\tpublic Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column)\n\t{\n\t\teditValue = getFontColorPair();\n\t\tif (!editDocked) {\n\t\t\tpan.add(edit, BorderLayout.EAST);\n\t\t\teditDocked = true;\n\t\t}\n\t\t//renderer.setSelected(getBoolValue());\n\t\tpan.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\tpan.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\tpan.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\n\t\treturn pan;\n\t}\n\n\tpublic FontColorPair getEditorValue()\n\t{\n\n\t\treturn editValue;\n\t}\n\n\tprivate FontColorPair editValue;\n\n\tpublic void addListenerToEditor(ActionListener e)\n\t{\n\t\tactionListeners.add(e);\n\t}\n\n\tpublic void removeListenerFromEditor(ActionListener e)\n\t{\n\t\tactionListeners.remove(e);\n\t}\n\n\tpublic void fireActionPerformed(ActionEvent e)\n\t{\n\t\tfor (int i = 0; i < actionListeners.size(); i++) {\n\t\t\tactionListeners.get(i).actionPerformed(e);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIComputationEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport userinterface.*;\n\npublic class GUIComputationEvent extends GUIEvent\n{\n    //CONSTANTS\n    public static final int COMPUTATION_START = 0;\n    public static final int COMPUTATION_DONE = 1;\n    public static final int COMPUTATION_ERROR = 2;\n    \n    private GUIPlugin source;\n    \n    /** Creates a new instance of GUIComputationEvent */\n    public GUIComputationEvent(int id, GUIPlugin source)\n    {\n        super(id);\n        this.source = source;\n    }\n    \n    public GUIPlugin getSource()\n    {\n        return source;\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\npublic class GUIEvent\n{\n    private Object data;\n    private int id;\n    \n    /** Creates a new instance of GUIEvent */\n    public GUIEvent(int id)\n    {\n        this.id = id;\n    }\n    \n    public GUIEvent(int id, Object data)\n    {\n        this.data = data;\n        this.id = id;\n    }\n    \n    //ACCESS METHODS\n    \n    public int getID()\n    {\n        return id;\n    }\n    \n    public Object getData()\n    {\n        return data;\n    }   \n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIEventHandler.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\nimport java.util.*;\nimport userinterface.*;\n\npublic class GUIEventHandler\n{\n\tpublic GUIPrism gui;\n\tpublic ArrayList<GUIEventListener> listeners;\n\t\n\t/** Creates a new instance of GUIEventHandler */\n\tpublic GUIEventHandler(GUIPrism gui)\n\t{\n\t\tthis.gui = gui;\n\t\tlisteners = new ArrayList<GUIEventListener>();\n\t}\n\t\n\tpublic void addListener(GUIEventListener listen)\n\t{\n\t\tlisteners.add(listen);\n\t}\n\t\n\tpublic void notifyListeners(GUIEvent e)\n\t{\n\t\tboolean res = false;\n\t\t// notify plugins\n\t\tfor(int i = 0; i < listeners.size(); i++)\n\t\t{\n\t\t\tGUIEventListener lis = listeners.get(i);\n\t\t\tres = lis.processGUIEvent(e);\n\t\t\tif (res) break;\n\t\t}\n\t\t// notify gui itself\n\t\tif (gui != null && !res) gui.processGUIEvent(e);\n\t}\n\t\n\tpublic boolean removeListener(GUIEventListener listen)\n\t{\n\t\treturn listeners.remove(listen);\n\t}\n\t\n\tpublic void clear()\n\t{\n\t\tlisteners.clear();\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIEventListener.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\npublic interface GUIEventListener\n{\n    // implementation returns false by default,\n    // unless event should not be passed on to any more listeners,\n    // in which case it returns true\n    public boolean processGUIEvent(GUIEvent e);\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIException.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\n@SuppressWarnings(\"serial\")\npublic class GUIException extends java.lang.Exception\n{\n    /**\n     * Creates a new instance of <code>GUIException</code> without detail message.\n     */\n    public GUIException()\n    {\n    }\n    \n    /**\n     * Constructs an instance of <code>GUIException</code> with the specified detail message.\n     * @param msg the detail message.\n     */\n    public GUIException(String msg)\n    {\n        super(msg);\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIExitEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\npublic class GUIExitEvent extends GUIEvent\n{\n    // CONSTANTS\n    public static final int REQUEST_EXIT = 0;\n    public static final int CANCEL_EXIT = 1;\n    \n    /** Creates a new instance of GUIExitEvent */\n    public GUIExitEvent(int id)\n    {\n        super(id);\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIGroupedTable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.awt.*;\nimport javax.swing.*;\nimport javax.swing.table.*;\n\nimport java.util.*;\n\n/**\n * A table object that is capable of grouping headers, effectively by means of two JTableHeader\n * Objects on top of each other.\n */\n@SuppressWarnings(\"serial\")\npublic class GUIGroupedTable extends JTable\n{\n\t/**\n\t * Creates a new GUIGroupedTable.\n\t * @param tableModel The (grouped) table data model on which to base this table. \n\t */\n\tpublic GUIGroupedTable(GUIGroupedTableModel tableModel)\n\t{\n\t\tsuper(tableModel);\n\t}\n\n\t/**\n\t * The default TableColumnModel Object (and the only valid one) is a GUIGroupedColumnModel Object.\n\t * @see javax.swing.JTable#createDefaultColumnModel()\n\t */\n\t@Override\n\tprotected TableColumnModel createDefaultColumnModel()\n\t{\n\t\treturn new GUIGroupedTableColumnModel();\n\t}\n\n\t/** \n\t * Given a GUIGroupedTableModel, this function creates a GUIGroupedColumnModel.\n\t * This function is called by JTable when the structure of the table changes, such that\n\t * it is not necessary to worry about the header.\n\t * @see javax.swing.JTable#createDefaultColumnsFromModel()\n\t */\n\t@Override\n\tpublic void createDefaultColumnsFromModel()\n\t{\n\t\tGUIGroupedTableColumnModel groupedColumnModel = (GUIGroupedTableColumnModel) columnModel;\n\n\t\tgroupedColumnModel.clear();\n\n\t\tif (dataModel != null && dataModel instanceof GUIGroupedTableModel && columnModel instanceof GUIGroupedTableColumnModel) {\n\t\t\tGUIGroupedTableModel groupedDataModel = (GUIGroupedTableModel) dataModel;\n\n\t\t\tint group = 0;\n\t\t\tint element = 0;\n\n\t\t\t// Add a group every iteration\n\t\t\twhile (group < groupedDataModel.getGroupCount() && element < groupedDataModel.getColumnCount()) {\n\t\t\t\tArrayList<TableColumn> groupElements = new ArrayList<TableColumn>();\n\n\t\t\t\t// Add an element every iteration\n\t\t\t\twhile (groupedDataModel.getLastColumnOfGroup(group) >= element) {\n\t\t\t\t\tTableColumn elementColumn = new TableColumn(element);\n\t\t\t\t\telementColumn.setHeaderValue(groupedDataModel.getColumnName(element));\n\t\t\t\t\tgroupElements.add(elementColumn);\n\t\t\t\t\telement++;\n\t\t\t\t}\n\n\t\t\t\tTableColumn groupColumn = new TableColumn(group);\n\t\t\t\tgroupColumn.setHeaderValue(groupedDataModel.getGroupName(group));\n\t\t\t\tgroup++;\n\n\t\t\t\tgroupedColumnModel.addColumnGroup(groupColumn, groupElements);\n\t\t\t}\n\t\t}\n\t}\n\n\t/**\n\t * Creates a default table header from the current column model.\n\t * Also called by JTable such that there is no need to worry about headers once you implemented\n\t * GUIGroupedTableModel.\n\t * @see javax.swing.JTable#createDefaultTableHeader()\n\t */\n\t@Override\n\tprotected JTableHeader createDefaultTableHeader()\n\t{\n\n\t\tGUIGroupedTableHeader header = null;\n\n\t\tif (columnModel != null && columnModel instanceof GUIGroupedTableColumnModel)\n\t\t\theader = new GUIGroupedTableHeader((GUIGroupedTableColumnModel) columnModel, (GUIGroupedTableModel) this.getModel(), this);\n\t\telse\n\t\t\theader = new GUIGroupedTableHeader(new GUIGroupedTableColumnModel(), (GUIGroupedTableModel) this.getModel(), this);\n\n\t\theader.setTable(this);\n\n\t\treturn header;\n\t}\n\n\t/** Override set font to set row height(s) */\n\t@Override\n\tpublic void setFont(Font font)\n\t{\n\t\tsuper.setFont(font);\n\t\tsetRowHeight(getFontMetrics(font).getHeight() + 4);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIGroupedTableColumnModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.util.*;\nimport javax.swing.event.*;\nimport javax.swing.table.*;\n\n/**\n * The TableColumnModel with the addition of Groups. A group is a set of columns. The set of columns \n * belonging to each group are disjoint and non-empty (!). \n */\n@SuppressWarnings(\"serial\")\npublic class GUIGroupedTableColumnModel extends DefaultTableColumnModel implements TableColumnModelListener\n{\n\t//private DefaultTableColumnModel elementTableColumnModel;\n\tprivate DefaultTableColumnModel groupTableColumnModel;\n\n\t// The nth element is the index of the last element in the nth group.\n\tprivate ArrayList<Integer> lastColumn;\n\n\t/**\n\t * Creates a new GUIGroupedTableModel with no groups.\n\t */\n\tpublic GUIGroupedTableColumnModel()\n\t{\n\t\tlastColumn = new ArrayList<Integer>();\n\n\t\t//this.elementTableColumnModel = new DefaultTableColumnModel();\n\t\tthis.groupTableColumnModel = new DefaultTableColumnModel();\n\t}\n\n\t/**\n\t * Returns The columns of all groups in terms of a DefaultTableColumnModel.\n\t * @return The columns of all groups in terms of a DefaultTableColumnModel.\n\t */\n\tpublic DefaultTableColumnModel getGroupTableColumnModel()\n\t{\n\t\treturn groupTableColumnModel;\n\t}\n\n\t/**\n\t * Adds a group to this grouped column model.\n\t * @param groupColumn A TableColumn representing all of the group.\n\t * @param elementColumns An ArrayList of TableColumns representing the columns of this group in the model.\n\t */\n\tpublic void addColumnGroup(TableColumn groupColumn, ArrayList<TableColumn> elementColumns)\n\t{\n\t\tgroupTableColumnModel.addColumn(groupColumn);\n\n\t\tfor (int i = 0; i < elementColumns.size(); i++) {\n\t\t\tthis.addColumn(elementColumns.get(i));\n\t\t}\n\n\t\tlastColumn.add(Integer.valueOf(this.getColumnCount() - 1));\n\t\tupdateGroups();\n\t}\n\n\t/**\n\t * A function that updates the widths of the group columns. \n\t */\n\tpublic void updateGroups()\n\t{\n\t\tint group = 0;\n\t\tint groupWidth = 0;\n\n\t\tfor (int i = 0; i < this.getColumnCount(); i++) {\n\t\t\tgroupWidth += this.getColumn(i).getWidth();\n\n\t\t\t// If this is the last column of a group.\n\t\t\tif (i == lastColumn.get(group).intValue()) {\n\t\t\t\twhile (group < groupTableColumnModel.getColumnCount() && i == lastColumn.get(group).intValue()) {\n\t\t\t\t\tgroupTableColumnModel.getColumn(group).setWidth(groupWidth);\n\n\t\t\t\t\tgroupWidth = 0;\n\t\t\t\t\tgroup++;\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void columnAdded(TableColumnModelEvent e)\n\t{\n\t}\n\n\tpublic void columnMarginChanged(ChangeEvent e)\n\t{\n\t}\n\n\tpublic void columnMoved(TableColumnModelEvent e)\n\t{\n\t}\n\n\tpublic void columnRemoved(TableColumnModelEvent e)\n\t{\n\t}\n\n\tpublic void columnSelectionChanged(ListSelectionEvent e)\n\t{\n\t}\n\n\t/**\n\t * If something changed in the columns of the table, then adjust the group widths.\n\t */\n\t@Override\n\tprotected void fireColumnMarginChanged()\n\t{\n\t\t// Size must have changed then.\n\t\tupdateGroups();\n\t\tsuper.fireColumnMarginChanged();\n\t}\n\n\t/** \n\t * Empties this GUIGroupedTableColumnModel.\n\t */\n\tpublic void clear()\n\t{\n\t\twhile (this.getColumnCount() > 0) {\n\t\t\tthis.removeColumn(this.getColumn(0));\n\t\t}\n\n\t\twhile (groupTableColumnModel.getColumnCount() > 0) {\n\t\t\tgroupTableColumnModel.removeColumn(groupTableColumnModel.getColumn(0));\n\t\t}\n\n\t\tthis.lastColumn.clear();\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIGroupedTableHeader.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.awt.*;\nimport java.awt.event.*;\n\nimport javax.swing.*;\nimport javax.swing.event.*;\nimport javax.swing.table.*;\n\n/**\n * An object to represent a grouped TableHeader. It extends JTableHeader, but actually consists of two separate\n * JTableHeaders. Some of this could be tidied up, but it is build more or less to Swings concepts.\n */\n@SuppressWarnings(\"serial\")\npublic class GUIGroupedTableHeader extends JTableHeader implements TableColumnModelListener, MouseListener\n{\n\tprivate JTableHeader bottomHeader;\n\tprivate JTableHeader topHeader;\n\tprivate GUIGroupedTableModel tableModel;\n    \n\t/**\n\t * Creates a new GUIGroupedTableHeader.\n\t * @param model The column model that is the basis of this table header (must be grouped).\n\t */\n\tpublic GUIGroupedTableHeader(GUIGroupedTableColumnModel model, GUIGroupedTableModel tableModel, GUIGroupedTable table)\n\t{\n\t\tsuper();\n\t\tremoveAll();\n\t\t\n\t\tthis.tableModel = tableModel;\n\t\t\t\t\t\t\n\t\ttopHeader = new JTableHeader(model.getGroupTableColumnModel());\n\t\ttopHeader.setResizingAllowed(false);\n\t\ttopHeader.setReorderingAllowed(false);\n\t\t\n\t\tfinal TableCellRenderer renderer = topHeader.getDefaultRenderer();\n\t\ttopHeader.setDefaultRenderer(new TableCellRenderer() {\n\t\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column) \n\t\t\t{\n\t\t\t\tComponent component = renderer.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);\n\t\t\t\tcomponent.setFont(topHeader.getFont().deriveFont(Font.BOLD));\n\t\t\t\treturn component;\n\t\t\t}\n\t\t});\n\t\t\n\t\tbottomHeader = new JTableHeader(model);\n\t\tbottomHeader.setReorderingAllowed(false);\n\t\t\n\t\ttopHeader.setTable(table);\n\t\tbottomHeader.setTable(table);\n\t\t\n\t\tsetLayout(new GridLayout(2,1));\n\t\t\t\t\t\n\t\tadd(topHeader);\n\t\tadd(bottomHeader);\t\t\n\t\t\n\t\tmodel.updateGroups();\n\t\t\t\t\t\n\t\tComponent[] cs = this.getComponents();\n\t\tfor (int i = 0; i < cs.length; i++) \n\t\t{\n\t\t    cs[i].addMouseListener(this);\n\t\t}\n\t\t\n\t\ttopHeader.addMouseMotionListener(new MouseMotionAdapter()\n\t\t{\n\t\t\tprivate TableColumn lastColumn;\n\t\t\t\n\t\t\tpublic void mouseMoved(MouseEvent e) \n\t\t\t{\t\t\t\n\t\t\t\tbottomHeader.setToolTipText(null);\n\t\t\t\t\n\t\t\t\tTableColumn currentColumn;\n\t\t\t\t\n\t\t\t\tint column = topHeader.getColumnModel().getColumnIndexAtX(e.getX());\n\t    \n\t            if (column >= 0) \n\t            {\n\t                currentColumn = topHeader.getColumnModel().getColumn(column);\n\t                \n\t                if (currentColumn != lastColumn) \n\t\t            {\t         \n\t                \ttopHeader.setToolTipText((GUIGroupedTableHeader.this).tableModel.getGroupToolTip(column));\n\t\t                lastColumn = currentColumn;\n\t\t            }\t               \n\t            }\t            \n\t\t\t}\n\t\t});\n\t\tbottomHeader.addMouseMotionListener(new MouseMotionAdapter()\n\t\t{\n\t\t\tprivate TableColumn lastColumn;\n\t\t\t\n\t\t\tpublic void mouseMoved(MouseEvent e) \n\t\t\t{\t\t\t\n\t\t\t\ttopHeader.setToolTipText(null);\n\t\t\t\t\n\t\t\t\tTableColumn currentColumn;\n\t\t\t\t\n\t\t\t\tint column = bottomHeader.getColumnModel().getColumnIndexAtX(e.getX());\n\t    \n\t            if (column >= 0) \n\t            {\n\t                currentColumn = bottomHeader.getColumnModel().getColumn(column);\n\t                \n\t                if (currentColumn != lastColumn) \n\t\t            {\t         \n\t                \tbottomHeader.setToolTipText((GUIGroupedTableHeader.this).tableModel.getColumnToolTip(column));\n\t\t                lastColumn = currentColumn;\n\t\t            }\t               \n\t            }\t            \n\t\t\t}\n\t\t});\n\t\t\n\t\t//topHeader.setToolTipText(null);\n\t\t//bottomHeader.setToolTipText(null);\n\t}\n\t\n\t@Override\n\tpublic Dimension getPreferredSize()\n\t{\n\t\treturn new Dimension(bottomHeader.getPreferredSize().width, bottomHeader.getPreferredSize().height * 2);\n\t}\n\t\n\t@Override\n\tpublic Dimension getMinimumSize()\n\t{\n\t\treturn new Dimension(bottomHeader.getMinimumSize().width, bottomHeader.getMinimumSize().height * 2);\n\t}\n\t\n\t@Override\n\tpublic Dimension getMaximumSize()\n\t{\n\t\treturn new Dimension(bottomHeader.getMaximumSize().width, bottomHeader.getMaximumSize().height * 2);\n\t}\n\t\n\t/**\n\t * A fairly ugly hack to prevent a CellRenderer to be added to this container. More elegant solutions are welcome.\n\t * @see java.awt.Container#addImpl(java.awt.Component, java.lang.Object, int)\n\t */\n\t@Override\n    protected void addImpl(Component comp, Object constraints, int index) {\n\t    // TODO Auto-generated method stub\n\t\tif (this.getComponents().length < 2)\n\t\t{\n\t\t\tsuper.addImpl(comp, constraints, index);\n\t\t}\n    }\n\n\t/**\n\t * Overwritten to never allow reordering.\n\t * @see javax.swing.table.JTableHeader#setReorderingAllowed(boolean)\n\t */\n\t@Override\n\tpublic void setReorderingAllowed(boolean reorderingAllowed) {\t\t\t\n\t\tsuper.setReorderingAllowed(false);\n\t}\n\n\t/**\n\t * Overwritten to always return the resizing column of the bottom JTableHeader.\n\t * @see javax.swing.table.JTableHeader#getResizingColumn()\n\t */\n\t@Override\n\tpublic TableColumn getResizingColumn() \n\t{\n\t\treturn bottomHeader.getResizingColumn();\t\t\t\n\t}\n\t\n    /** \n     * Overwritten to give the JTableHeaders a change to resize as well.\n     * @see javax.swing.table.JTableHeader#resizeAndRepaint()\n     */\n    /*@Override\n    public void resizeAndRepaint() \n    {   \t\n    \tif (topHeader != null && bottomHeader != null)\n    \t{\n    \t\tthis.doLayout();\n    \t}   \n    \t\n\t    super.resizeAndRepaint();\t   \n    }*/\n   \n\t/**\n\t * Set the column model.\n\t * @param columnModel The grouped column model to use.\n\t */\n\tpublic void setColumnModel(GUIGroupedTableColumnModel columnModel) {\n\t    \n    \ttopHeader.setColumnModel(columnModel.getGroupTableColumnModel());\n    \tbottomHeader.setColumnModel(columnModel);   \t\n    \t    \t\n    \tthis.resizeAndRepaint();\n    \t\n    \tcolumnModel.updateGroups();\n\t    super.setColumnModel(columnModel);\n    }\n\n\t/** \n\t * Overwritten to catch events of child components.\n\t */\n\tpublic void mouseClicked(MouseEvent e) {\n\t\tthis.dispatchEvent(new MouseEvent(this, e.getID(), e.getWhen(), e.getModifiers(), e.getX(), e.getY() + ((Component)e.getSource()).getBounds().y, e.getClickCount(), e.isPopupTrigger()));\n    }\n\n\t/** \n\t * Overwritten to catch events of child components.\n\t */\n\tpublic void mouseEntered(MouseEvent e) {\n\t\tthis.dispatchEvent(new MouseEvent(this, e.getID(), e.getWhen(), e.getModifiers(), e.getX(), e.getY() + ((Component)e.getSource()).getBounds().y, e.getClickCount(), e.isPopupTrigger()));    \n\t}\n\n\t/** \n\t * Overwritten to catch events of child components.\n\t */\n\tpublic void mouseExited(MouseEvent e) {\n\t\tthis.dispatchEvent(new MouseEvent(this, e.getID(), e.getWhen(), e.getModifiers(), e.getX(), e.getY() + ((Component)e.getSource()).getBounds().y, e.getClickCount(), e.isPopupTrigger()));    \n\t}\n\n\t/** \n\t * Overwritten to catch events of child components.\n\t */\n\tpublic void mousePressed(MouseEvent e) {\n\t\tthis.dispatchEvent(new MouseEvent(this, e.getID(), e.getWhen(), e.getModifiers(), e.getX(), e.getY() + ((Component)e.getSource()).getBounds().y, e.getClickCount(), e.isPopupTrigger()));    \n\t}\n\n\t/** \n\t * Overwritten to catch events of child components.\n\t */\n\tpublic void mouseReleased(MouseEvent e) {\n\t\tthis.dispatchEvent(new MouseEvent(this, e.getID(), e.getWhen(), e.getModifiers(), e.getX(), e.getY() + ((Component)e.getSource()).getBounds().y, e.getClickCount(), e.isPopupTrigger()));    \n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIGroupedTableModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport javax.swing.table.TableModel;\n\n/**\n * An interface which extends {@link TableModel} such that also group information can \n * be extracted automatically. Note that groups are always non-empty.\n */\npublic interface GUIGroupedTableModel extends TableModel\n{\n\t/**\n\t * @return The number of groups in this model.\n\t */\n\tpublic int getGroupCount();\n\t\n\t/**\n\t * Retrieves the name of a group.\n\t * @param groupIndex The index of a group.\n\t * @return The name of the nth group, where n = groupIndex.\n\t * @see #getColumnName(int columnIndex). \n\t */\n\tpublic String getGroupName(int groupIndex);\n\t\t\n\t/**\n\t * Retrieves the index of the last `normal' column in a group.\n\t * @param groupIndex The index of a group.\n\t * @return The index of the last column in this group.\n\t */\n\tpublic int getLastColumnOfGroup(int groupIndex);\t\n\t\n\t/**\n\t * Retrieves the tooltip to be set for a group.\n\t * @param groupIndex The index of a group.\n\t * @return The tooltip text for a group, or null.\n\t */\n\tpublic String getGroupToolTip(int groupIndex);\n\n\t/**\n\t * Retrieves the tooltip to be set for a column.\n\t * @param columnIndex The index of a column.\n\t * @return The tooltip text for a column, or null.\n\t */\n\tpublic String getColumnToolTip(int columnIndex)\t;\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUILogEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\npublic class GUILogEvent extends GUIEvent\n{\n    public static final int PRINTLN = 0;\n    public static final int PRINT = 1;\n    public static final int PRINTSEPARATOR = 2;\n    public static final int PRINTWARNING = 3;\n    \n    /**\n     * Constructs an instance of <code>GUILogEvent</code> with the specified detail message.\n     * @param message the detail message.\n     */\n    public GUILogEvent(int type, Object message)\n    {\n        super(type, message);\n    }\n    \n    public GUILogEvent(int type, int message)\n    {\n        super(type, Integer.valueOf(message));\n    }\n    \n    public GUILogEvent(int type, double message)\n    {\n        super(type, Double.valueOf(message));\n    }\n    \n    public GUILogEvent(int type, float message)\n    {\n        super(type, Float.valueOf(message));\n    }\n    \n    public GUILogEvent(int type, long message)\n    {\n        super(type, Long.valueOf(message));\n    }\n    \n    public GUILogEvent(int type, short message)\n    {\n        super(type, Short.valueOf(message));\n    }\n    \n    public GUILogEvent(int type, byte message)\n    {\n        super(type, Byte.valueOf(message));\n    }\n    \n    public GUILogEvent(int type, boolean message)\n    {\n        super(type, Boolean.valueOf(message));\n    }\n    \n    public GUILogEvent(Object message)\n    {\n        this(PRINTLN, message);\n    }\n    \n    public GUILogEvent(int message)\n    {\n        this(PRINTLN, Integer.valueOf(message));\n    }\n    \n    public GUILogEvent(double message)\n    {\n        this(PRINTLN, Double.valueOf(message));\n    }\n    \n    public GUILogEvent(float message)\n    {\n        this(PRINTLN, Float.valueOf(message));\n    }\n    \n    public GUILogEvent(long message)\n    {\n        this(PRINTLN, Long.valueOf(message));\n    }\n    \n    public GUILogEvent(short message)\n    {\n        this(PRINTLN, Short.valueOf(message));\n    }\n    \n    public GUILogEvent(byte message)\n    {\n        this(PRINTLN, Byte.valueOf(message));\n    }\n    \n    public GUILogEvent(boolean message)\n    {\n        this(PRINTLN, Boolean.valueOf(message));\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIUndoManager.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//  * Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport javax.swing.event.UndoableEditEvent;\nimport javax.swing.event.UndoableEditListener;\nimport javax.swing.undo.CannotRedoException;\nimport javax.swing.undo.CannotUndoException;\nimport javax.swing.undo.UndoManager;\nimport javax.swing.undo.UndoableEdit;\n\nimport userinterface.GUIPrism;\n\npublic class GUIUndoManager extends GUIEventHandler implements UndoableEditListener\n{\n\tprivate UndoManager undoManager;\n\t\n\tpublic GUIUndoManager(GUIPrism gui) \n\t{\n\t\tsuper(gui);\t\n\t\tundoManager = new UndoManager();\n\t}\n\n\tpublic boolean addEdit(UndoableEdit anEdit) \n\t{\n\t\tboolean result = undoManager.addEdit(anEdit);\n\t\tif (result)\n\t\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.UNDOABLE_EVENT));\n\t\treturn result;\n\t}\n\n\tpublic boolean canRedo() \n\t{\n\t\treturn undoManager.canRedo();\n\t}\n\n\tpublic boolean canUndo() \n\t{\n\t\treturn undoManager.canUndo();\n\t}\n\n\tpublic boolean canUndoOrRedo() \n\t{\n\t\treturn undoManager.canUndoOrRedo();\n\t}\n\n\tpublic void die() \n\t{\n\t\tundoManager.die();\n\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.DIED));\n\t}\n\n\tpublic void discardAllEdits() \n\t{\n\t\tundoManager.discardAllEdits();\n\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.DISCARD_ALL));\n\t}\n\n\tpublic void end() \n\t{\n\t\tundoManager.end();\n\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.DIED));\n\t}\n\n\tpublic boolean equals(Object obj) \n\t{\n\t\treturn undoManager.equals(obj);\n\t}\n\n\tpublic int getLimit() \n\t{\n\t\treturn undoManager.getLimit();\n\t}\n\n\tpublic String getPresentationName() \n\t{\n\t\treturn undoManager.getPresentationName();\n\t}\n\n\tpublic String getRedoPresentationName() \n\t{\n\t\treturn undoManager.getRedoPresentationName();\n\t}\n\n\tpublic String getUndoOrRedoPresentationName() \n\t{\n\t\treturn undoManager.getUndoOrRedoPresentationName();\n\t}\n\n\tpublic String getUndoPresentationName() \n\t{\n\t\treturn undoManager.getUndoPresentationName();\n\t}\n\n\tpublic int hashCode() \n\t{\n\t\treturn undoManager.hashCode();\n\t}\n\n\tpublic boolean isInProgress() \n\t{\n\t\treturn undoManager.isInProgress();\n\t}\n\n\tpublic boolean isSignificant() \n\t{\n\t\treturn undoManager.isSignificant();\n\t}\n\n\tpublic void redo() throws CannotRedoException {\n\t\tundoManager.redo();\n\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.REDO));\n\t}\n\n\tpublic boolean replaceEdit(UndoableEdit anEdit) {\n\t\treturn false;\n\t}\n\n\tpublic void setLimit(int l) {\n\t\tundoManager.setLimit(l);\n\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.LIMIT_CHANGE));\n\t}\n\n\tpublic String toString() {\n\t\treturn undoManager.toString();\n\t}\n\n\tpublic void undo() throws CannotUndoException {\n\t\tundoManager.undo();\n\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.UNDO));\n\t}\n\n\tpublic void undoableEditHappened(UndoableEditEvent e) {\n\t\tundoManager.undoableEditHappened(e);\n\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.UNDOABLE_EVENT));\n\t}\n\n\tpublic void undoOrRedo() throws CannotRedoException, CannotUndoException {\n\t\tundoManager.undoOrRedo();\n\t\tnotifyListeners(new GUIUndoManagerEvent(GUIUndoManagerEvent.UNDO));\t\t\n\t}\n\t\n\t\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/GUIUndoManagerEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//  * Mark Kattenbelt <mark.kattenbelt@comlab.ox.ac.uk> (University of Oxford)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport userinterface.GUIPlugin;\n\npublic class GUIUndoManagerEvent extends GUIEvent \n{\n\tpublic static final int UNDO = 0;\n\tpublic static final int REDO = 1; \n\tpublic static final int UNDOABLE_EVENT = 2;\n\tpublic static final int DISCARD_ALL = 3;\n\tpublic static final int LIMIT_CHANGE = 4;\n\tpublic static final int DIED = 5;\n\t\n\tpublic GUIUndoManagerEvent(int id, GUIPlugin comp) \n\t{\n\t\tsuper(id, comp);\n\t}\n\n\tpublic GUIUndoManagerEvent(int id) \n\t{\n\t\tsuper(id);\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/MultipleProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.util.*;\nimport java.awt.*;\nimport javax.swing.*;\n\n/**\n * Represents more than one single property when it is selected.\n */\npublic class MultipleProperty\n{\n    private ArrayList<SingleProperty> properties;\n    \n    /** Creates a new instance of MultipleProperty */\n    public MultipleProperty(ArrayList<SingleProperty> properties)\n    {\n        this.properties = properties;\n    }\n    \n    public boolean isMultiline()\n    {\n        return getProperty(0).isMultiline();\n    }\n    \n    public SingleProperty getProperty(int i)\n    {\n        return properties.get(i);\n    }\n    \n    public int getNumProperties()\n    {\n        return properties.size();\n    }\n    \n    public boolean allTheSame()\n    {\n        String value = getProperty(0).toString();\n        \n        for(int i = 1; i < getNumProperties(); i++)\n        {\n            String temp = getProperty(i).toString();\n            if(!temp.equals(value))\n            {\n                return false;\n            }\n        }\n        return true;\n    }\n    \n    public String toString()\n    {\n        \n        String value = getProperty(0).toString();\n        \n        for(int i = 1; i < getNumProperties(); i++)\n        {\n            String temp = getProperty(i).toString();\n            if(!temp.equals(value))\n            {\n                value = \"...\";\n                break;\n            }\n        }\n        return value;\n    }\n    \n    public Component getTableCellRendererComponentMulti(JTable table, Object value,\n        boolean isSelected, boolean hasFocus, int row, int column)\n    {\n        return getProperty(0).getTableCellRendererComponentMulti(table, value, isSelected, hasFocus, row, column, allTheSame());\n    }\n    \n    /**\n     * Getter for property properties.\n     * @return Value of property properties.\n     */\n    public ArrayList<SingleProperty> getProperties()\n    {\n        return properties;\n    }\n    \n    \n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/util/PresentationMetalTheme.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport javax.swing.plaf.*;\nimport javax.swing.plaf.metal.*;\nimport java.awt.*;\n\n/**\n * This class overrides DefaultMetalTheme to change the fonts for components and\n * menus to a bigger size suitable for presentations.\n */\npublic class PresentationMetalTheme extends DefaultMetalTheme\n{\n    \n    private FontUIResource f;\n    public PresentationMetalTheme(int sizeChange)\n    {\n        FontUIResource fr = super.getControlTextFont();\n        String st = fr.getFontName();\n        ////System.out.println(\"st = \"+st);\n        st = \"Dialog.PLAIN\";\n        \n        f = new FontUIResource(st, Font.PLAIN, 11+sizeChange);\n    }\n    \n    /** Overrides the superclass's getMenuTextFont method by returning a larger font. */    \n    public FontUIResource getMenuTextFont() \n    { \n        return f;\n    }\n    \n    /** Overrides the superclass's getControlTextFont() method to return a larger font. */    \n    public FontUIResource getControlTextFont() \n    {\n        return f;\n    }\n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/util/PropertyConstants.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\npublic final class PropertyConstants\n{\n    public static final int STATE = 0;\n    public static final int TRANSITION = 1;\n    public static final int NAIL = 2;\n    public static final int DECISION = 3;\n    public static final int PROBTRANSITION = 4;\n    public static final int BRANCHTRANSITION = 5;\n    public static final int GRAPH = 6;\n    public static final int AXIS = 7;\n    public static final int SERIES = 8;\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/PropertyException.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\n@SuppressWarnings(\"serial\")\npublic class PropertyException extends Exception\n{\n    /** Creates a new instance of PropertyException */\n    public PropertyException(String desc)\n    {\n        super(desc);\n    }\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/PropertyOwner.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.util.*;\n\npublic interface PropertyOwner extends Comparable<Object>\n{\n\t// One for each type of owner\n\tpublic int getUniquePropertyID();\n\n\t// One for each owner\n\t// This will be displayed when only\n\t// this owner is being displayed.\n\tpublic String getDescriptor();\n\n\t// One for each type of property collection\n\t// When only one owner is being displayed,\n\t// we see the result of this method, and then\n\t// the result of getDescriptor.\n\t// If there is more than one owner being\n\t// displayed, we see the number of\n\t// owners, then the result of this method\n\t// followed by an \"s\".\n\tpublic String getClassDescriptor();\n\n\tpublic int getNumProperties();\n\n\tpublic SingleProperty getProperty(int index);\n\n\tpublic void registerObserver(Observer obs);\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/PropertyTable.form",
    "content": "<?xml version=\"1.0\" encoding=\"UTF-8\" ?>\n\n<Form version=\"1.0\" type=\"org.netbeans.modules.form.forminfo.JPanelFormInfo\">\n\n  <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n  <SubComponents>\n    <Container class=\"javax.swing.JPanel\" name=\"jPanel1\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"true\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"Center\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Container class=\"javax.swing.JSplitPane\" name=\"jSplitPane1\">\n          <Properties>\n            <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n              <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n            </Property>\n            <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n              <Border info=\"null\"/>\n            </Property>\n            <Property name=\"dividerSize\" type=\"int\" value=\"3\"/>\n            <Property name=\"orientation\" type=\"int\" value=\"0\"/>\n            <Property name=\"resizeWeight\" type=\"double\" value=\"1.0\"/>\n            <Property name=\"oneTouchExpandable\" type=\"boolean\" value=\"true\"/>\n          </Properties>\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"true\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"Center\"/>\n            </Constraint>\n          </Constraints>\n\n          <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\"/>\n          <SubComponents>\n            <Container class=\"javax.swing.JScrollPane\" name=\"jScrollPane1\">\n              <Properties>\n                <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                  <Color blue=\"ff\" green=\"ff\" red=\"ff\" type=\"rgb\"/>\n                </Property>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n                    <LineBorder>\n                      <Color PropertyName=\"color\" blue=\"80\" green=\"80\" id=\"Text Inactive Text\" palette=\"2\" red=\"80\" type=\"palette\"/>\n                    </LineBorder>\n                  </Border>\n                </Property>\n                <Property name=\"horizontalScrollBarPolicy\" type=\"int\" value=\"31\"/>\n              </Properties>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_CreateCodePost\" type=\"java.lang.String\" value=\"jScrollPane1.getViewport().setBackground(Color.white);\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                  <JSplitPaneConstraints position=\"left\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.support.JScrollPaneSupportLayout\"/>\n              <SubComponents>\n                <Component class=\"javax.swing.JTable\" name=\"theTable\">\n                  <Properties>\n                    <Property name=\"model\" type=\"javax.swing.table.TableModel\" editor=\"org.netbeans.modules.form.editors2.TableModelEditor\">\n                      <Table columnCount=\"4\" rowCount=\"4\">\n                        <Column editable=\"true\" title=\"Title 1\" type=\"java.lang.Object\"/>\n                        <Column editable=\"true\" title=\"Title 2\" type=\"java.lang.Object\"/>\n                        <Column editable=\"true\" title=\"Title 3\" type=\"java.lang.Object\"/>\n                        <Column editable=\"true\" title=\"Title 4\" type=\"java.lang.Object\"/>\n                      </Table>\n                    </Property>\n                    <Property name=\"doubleBuffered\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"gridColor\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                      <Color blue=\"c5\" green=\"c5\" red=\"c6\" type=\"rgb\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_CreateCodeCustom\" type=\"java.lang.String\" value=\"new JTable()&#xa;            {&#xa;                //This method is a fix from http://www.codeguru.com/java/articles/180.shtml by Zafir Anjum, cheers!&#xa;                //this is required because there is a bug in JTable where the &#xa;                //just saying tableScroll.setColumnHeader(null); does not work as it should&#xa;                //Unfortunately, it overrides a deprecated API, so let&apos;s hope they &#xa;                //sort it out by Java 5.0, nice one Sun...&#xa;                protected void configureEnclosingScrollPane()&#xa;                {&#xa;                    Container p = getParent();&#xa;                    if (p instanceof JViewport)&#xa;                    {&#xa;                        Container gp = p.getParent();&#xa;                        if (gp instanceof JScrollPane)&#xa;                        {&#xa;                            JScrollPane scrollPane = (JScrollPane)gp;&#xa;                            // Make certain we are the viewPort&apos;s view and not, for&#xa;                            // example, the rowHeaderView of the scrollPane -&#xa;                            // an implementor of fixed columns might do this.&#xa;                            JViewport viewport = scrollPane.getViewport();&#xa;                            if (viewport == null || viewport.getView() != this)&#xa;                            {&#xa;                                return;&#xa;                            }&#xa;                            //                scrollPane.setColumnHeaderView(getTableHeader());&#xa;                            scrollPane.getViewport().setBackingStoreEnabled(true);&#xa;                            scrollPane.setBorder(UIManager.getBorder(&quot;Table.scrollPaneBorder&quot;));&#xa;                        }&#xa;                    }&#xa;                }&#xa;                &#xa;            };&#xa;            theTable.setModel(theModel);&#xa;            theTable.setSelectionMode(DefaultListSelectionModel.SINGLE_SELECTION);&#xa;            theTable.setRowSelectionAllowed(false);&#xa;            theTable.setColumnSelectionAllowed(false);&#xa;            theTable.setCellSelectionEnabled(true);\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                </Component>\n              </SubComponents>\n            </Container>\n            <Container class=\"javax.swing.JPanel\" name=\"jPanel3\">\n              <Properties>\n                <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                  <Border info=\"org.netbeans.modules.form.compat2.border.LineBorderInfo\">\n                    <LineBorder>\n                      <Color PropertyName=\"color\" blue=\"80\" green=\"80\" id=\"Inactive Caption\" palette=\"2\" red=\"80\" type=\"palette\"/>\n                    </LineBorder>\n                  </Border>\n                </Property>\n                <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[10, 75]\"/>\n                </Property>\n                <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                  <Dimension value=\"[100, 75]\"/>\n                </Property>\n              </Properties>\n              <AuxValues>\n                <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"true\"/>\n              </AuxValues>\n              <Constraints>\n                <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout\" value=\"org.netbeans.modules.form.compat2.layouts.support.JSplitPaneSupportLayout$JSplitPaneConstraintsDescription\">\n                  <JSplitPaneConstraints position=\"right\"/>\n                </Constraint>\n              </Constraints>\n\n              <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n              <SubComponents>\n                <Component class=\"javax.swing.JTextArea\" name=\"commentText\">\n                  <Properties>\n                    <Property name=\"background\" type=\"java.awt.Color\" editor=\"org.netbeans.beaninfo.editors.ColorEditor\">\n                      <Color blue=\"cc\" green=\"cc\" id=\"Panel.background\" palette=\"3\" red=\"cc\" type=\"palette\"/>\n                    </Property>\n                    <Property name=\"columns\" type=\"int\" value=\"1\"/>\n                    <Property name=\"editable\" type=\"boolean\" value=\"false\"/>\n                    <Property name=\"lineWrap\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"wrapStyleWord\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"border\" type=\"javax.swing.border.Border\" editor=\"org.netbeans.modules.form.editors2.BorderEditor\">\n                      <Border info=\"null\"/>\n                    </Property>\n                    <Property name=\"doubleBuffered\" type=\"boolean\" value=\"true\"/>\n                    <Property name=\"focusable\" type=\"boolean\" value=\"false\"/>\n                    <Property name=\"minimumSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[100, 75]\"/>\n                    </Property>\n                    <Property name=\"preferredSize\" type=\"java.awt.Dimension\" editor=\"org.netbeans.beaninfo.editors.DimensionEditor\">\n                      <Dimension value=\"[100, 75]\"/>\n                    </Property>\n                  </Properties>\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"Center\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n                <Component class=\"javax.swing.JLabel\" name=\"commentLabel\">\n                  <AuxValues>\n                    <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n                    <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n                  </AuxValues>\n                  <Constraints>\n                    <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n                      <BorderConstraints direction=\"North\"/>\n                    </Constraint>\n                  </Constraints>\n                </Component>\n              </SubComponents>\n            </Container>\n          </SubComponents>\n        </Container>\n      </SubComponents>\n    </Container>\n    <Container class=\"javax.swing.JPanel\" name=\"topPanel\">\n      <AuxValues>\n        <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n        <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n      </AuxValues>\n      <Constraints>\n        <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n          <BorderConstraints direction=\"North\"/>\n        </Constraint>\n      </Constraints>\n\n      <Layout class=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\"/>\n      <SubComponents>\n        <Component class=\"javax.swing.JComboBox\" name=\"theCombo\">\n          <AuxValues>\n            <AuxValue name=\"JavaCodeGenerator_VariableModifier\" type=\"java.lang.Integer\" value=\"0\"/>\n            <AuxValue name=\"JavaCodeGenerator_VariableLocal\" type=\"java.lang.Boolean\" value=\"false\"/>\n          </AuxValues>\n          <Constraints>\n            <Constraint layoutClass=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout\" value=\"org.netbeans.modules.form.compat2.layouts.DesignBorderLayout$BorderConstraintsDescription\">\n              <BorderConstraints direction=\"North\"/>\n            </Constraint>\n          </Constraints>\n        </Component>\n      </SubComponents>\n    </Container>\n  </SubComponents>\n</Form>\n"
  },
  {
    "path": "prism/src/userinterface/util/PropertyTable.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport javax.swing.*;\nimport javax.swing.event.*;\nimport java.awt.*;\nimport java.awt.event.*;\nimport java.util.*;\nimport javax.swing.table.*;\nimport javax.swing.border.*;\nimport javax.swing.text.*;\n\n@SuppressWarnings(\"serial\")\npublic class PropertyTable extends JPanel implements ListSelectionListener, TableModelListener, ItemListener\n{\n\tprivate PropertyTableModel theModel;\n\n\tprivate int lineWidth;\n\n\t/** Creates new form PropertyTable */\n\tpublic PropertyTable(PropertyTableModel theModel)\n\t{\n\t\tsuper();\n\n\t\tthis.theModel = theModel;\n\t\tinitComponents();\n\n\t\ttheModel.setJTable(theTable);\n\t\ttheModel.addTableModelListener(this);\n\t\tlineWidth = theTable.getRowHeight();\n\t\ttheTable.setModel(theModel);\n\t\ttheTable.setRowSelectionAllowed(true);\n\t\ttheTable.setColumnSelectionAllowed(false);\n\t\ttheTable.setCellSelectionEnabled(false);\n\t\ttheTable.getSelectionModel().addListSelectionListener(this);\n\t\ttheTable.setAutoResizeMode(JTable.AUTO_RESIZE_LAST_COLUMN);\n\t\ttheCombo.setModel(theModel.getComboModel());\n\t\ttheCombo.addItemListener(this);\n\n\t\ttheTable.getColumnModel().getColumn(0).setMinWidth(30);\n\t\t//theTable.getColumnModel().getColumn(0).setResizable(false);\n\n\t\t//int lines = 2;\n\t\t//theTable.setRowHeight( theTable.getRowHeight() * lines);\n\n\t\tTableColumn column = theTable.getColumnModel().getColumn(1);\n\t\tcolumn.setCellRenderer(new PropertyCellRenderer());\n\t\tsetCurrEditor(new PropertyTable.PropertyCellEditor());\n\n\t\tfor (int i = 0; i < theModel.getRowCount(); i++) {\n\t\t\t////System.out.println(\"Row \"+i);\n\t\t\t//int lines = 1;\n\n\t\t\t//if (theModel.getValueAt(i, 1) instanceof SingleProperty)\n\t\t\t\t//lines = getNumLines(value);\n\t\t\t//theTable.setRowHeight(i, (lineWidth*lines)+2);\n\t\t\t//int heightWanted = (int)area.getPreferredSize().getHeight();\n\t\t\t//      if(heightWanted != theTable.getRowHeight(row));\n\t\t\t//    theTable.setRowHeight(row, heightWanted);\n\t\t}\n\n\t\tdoChoiceBox();\n\n\t\tcommentLabel.setFont(new Font(\"serif\", Font.BOLD, 12));\n\t\t//theTable.setDefaultRenderer(String.class, new MultiLineCellRenderer());\n\t\t//theTable.setAutoResizeMode(JTable.AUTO_RESIZE_LAST_COLUMN);\n\t}\n\n\tpublic void setNameColumnWidth(int width)\n\t{\n\t\t//theTable.getColumnModel().getColumn(0).setMinWidth(width);\n\t\t//theTable.getColumnModel().getColumn(0).setMaxWidth(width);\n\t\t//theTable.getColumnModel().getColumn(0).setPreferredWidth(width);\n\t\t//theTable.getColumnModel().getColumn(0).setMaxWidth(width);\n\t\t//theTable.repaint();\n\t}\n\n\tprivate void doChoiceBox()\n\t{\n\t\tif (theModel.getNumGroups() == 0) {\n\t\t\ttopPanel.removeAll();\n\t\t\tJLabel lab = new JLabel(\"\");\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\ttopPanel.add(lab, BorderLayout.CENTER);\n\t\t} else if (theModel.getNumGroups() == 1) {\n\t\t\ttopPanel.removeAll();\n\t\t\tJLabel lab = new JLabel(theCombo.getModel().getElementAt(0).toString());\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\ttopPanel.add(lab, BorderLayout.CENTER);\n\t\t} else {\n\t\t\ttopPanel.removeAll();\n\t\t\ttopPanel.setLayout(new BorderLayout());\n\t\t\ttopPanel.add(theCombo, BorderLayout.CENTER);\n\t\t}\n\t\tthis.revalidate();\n\t}\n\n\tpublic void stopEditing()\n\t{\n\t\tif (ce != null)\n\t\t\tce.stopEditing();\n\t}\n\n\tpublic void setCurrEditor(PropertyTable.PropertyCellEditor ce)\n\t{\n\t\tTableColumn column = theTable.getColumnModel().getColumn(1);\n\t\tcolumn.setCellEditor(ce);\n\t\t//if(this.ce != ce) System.out.println(\"THE CURREDITOR HAS CHANGED\");\n\n\t\tthis.ce = ce;\n\t}\n\n\tprivate PropertyTable.PropertyCellEditor ce;\n\n\t/** This method is called from within the constructor to\n\t * initialize the form.\n\t * WARNING: Do NOT modify this code. The content of this method is\n\t * always regenerated by the Form Editor.\n\t */\n\tprivate void initComponents()//GEN-BEGIN:initComponents\n\t{\n\t\tjavax.swing.JPanel jPanel1;\n\t\tjavax.swing.JPanel jPanel3;\n\t\tjavax.swing.JScrollPane jScrollPane1;\n\t\tjavax.swing.JSplitPane jSplitPane1;\n\n\t\tjPanel1 = new javax.swing.JPanel();\n\t\tjSplitPane1 = new javax.swing.JSplitPane();\n\t\tjScrollPane1 = new javax.swing.JScrollPane();\n\t\tjScrollPane1.getViewport().setBackground(Color.white);\n\t\ttheTable = new JTable()\n\t\t{\n\n\t\t\t//This method is a fix from http://www.codeguru.com/java/articles/180.shtml by Zafir Anjum, cheers!\n\t\t\t//this is required because there is a bug in JTable where the\n\t\t\t//just saying tableScroll.setColumnHeader(null); does not work as it should\n\t\t\t//Unfortunately, it overrides a deprecated API, so let's hope they\n\t\t\t//sort it out by Java 5.0, nice one Sun...\n\t\t\t//Addition (6th December 2004) This is no longer needed,\n\t\t\t/*protected void configureEnclosingScrollPane()\n\t\t\t{\n\t\t\t    Container p = getParent();\n\t\t\t    if (p instanceof JViewport)\n\t\t\t    {\n\t\t\t        Container gp = p.getParent();\n\t\t\t        if (gp instanceof JScrollPane)\n\t\t\t        {\n\t\t\t            JScrollPane scrollPane = (JScrollPane)gp;\n\t\t\t            // Make certain we are the viewPort's view and not, for\n\t\t\t            // example, the rowHeaderView of the scrollPane -\n\t\t\t            // an implementor of fixed columns might do this.\n\t\t\t            JViewport viewport = scrollPane.getViewport();\n\t\t\t            if (viewport == null || viewport.getView() != this)\n\t\t\t            {\n\t\t\t                return;\n\t\t\t            }\n\t\t\t            //                scrollPane.setColumnHeaderView(getTableHeader());\n\t\t\t            scrollPane.getViewport().setBackingStoreEnabled(true);\n\t\t\t            scrollPane.setBorder(UIManager.getBorder(\"Table.scrollPaneBorder\"));\n\t\t\t        }\n\t\t\t    }\n\t\t\t}*/\n\n\t\t};\n\t\ttheTable.setModel(theModel);\n\t\ttheTable.setSelectionMode(DefaultListSelectionModel.SINGLE_SELECTION);\n\t\ttheTable.setRowSelectionAllowed(false);\n\t\ttheTable.setColumnSelectionAllowed(false);\n\t\ttheTable.setCellSelectionEnabled(true);\n\t\tjPanel3 = new javax.swing.JPanel();\n\t\tcommentText = new javax.swing.JTextArea();\n\t\tcommentLabel = new javax.swing.JLabel();\n\t\ttopPanel = new javax.swing.JPanel();\n\t\ttheCombo = new javax.swing.JComboBox();\n\n\t\tsetLayout(new java.awt.BorderLayout());\n\n\t\tjPanel1.setLayout(new java.awt.BorderLayout());\n\n\t\tjSplitPane1.setBackground(new java.awt.Color(255, 255, 255));\n\t\tjSplitPane1.setBorder(null);\n\t\tjSplitPane1.setDividerSize(3);\n\t\tjSplitPane1.setOrientation(javax.swing.JSplitPane.VERTICAL_SPLIT);\n\t\tjSplitPane1.setResizeWeight(1.0);\n\t\tjSplitPane1.setOneTouchExpandable(true);\n\t\tjScrollPane1.setBackground(new java.awt.Color(255, 255, 255));\n\t\tjScrollPane1.setBorder(new javax.swing.border.LineBorder(java.awt.SystemColor.textInactiveText));\n\t\tjScrollPane1.setHorizontalScrollBarPolicy(javax.swing.JScrollPane.HORIZONTAL_SCROLLBAR_NEVER);\n\t\ttheTable.setModel(new javax.swing.table.DefaultTableModel(new Object[][] { { null, null, null, null }, { null, null, null, null },\n\t\t\t\t{ null, null, null, null }, { null, null, null, null } }, new String[] { \"Title 1\", \"Title 2\", \"Title 3\", \"Title 4\" }));\n\t\ttheTable.setDoubleBuffered(true);\n\t\ttheTable.setGridColor(new java.awt.Color(198, 197, 197));\n\t\tjScrollPane1.setViewportView(theTable);\n\n\t\tjSplitPane1.setLeftComponent(jScrollPane1);\n\n\t\tjPanel3.setLayout(new java.awt.BorderLayout());\n\n\t\tjPanel3.setBorder(new javax.swing.border.LineBorder(java.awt.SystemColor.inactiveCaption));\n\t\tjPanel3.setMinimumSize(new java.awt.Dimension(10, 75));\n\t\tjPanel3.setPreferredSize(new java.awt.Dimension(100, 75));\n\t\tcommentText.setBackground(javax.swing.UIManager.getDefaults().getColor(\"Panel.background\"));\n\t\tcommentText.setColumns(1);\n\t\tcommentText.setEditable(false);\n\t\tcommentText.setLineWrap(true);\n\t\tcommentText.setWrapStyleWord(true);\n\t\tcommentText.setBorder(null);\n\t\tcommentText.setDoubleBuffered(true);\n\t\tcommentText.setFocusable(false);\n\t\tcommentText.setMinimumSize(new java.awt.Dimension(100, 75));\n\t\tcommentText.setPreferredSize(new java.awt.Dimension(100, 75));\n\t\tjPanel3.add(commentText, java.awt.BorderLayout.CENTER);\n\n\t\tjPanel3.add(commentLabel, java.awt.BorderLayout.NORTH);\n\n\t\tjSplitPane1.setRightComponent(jPanel3);\n\n\t\tjPanel1.add(jSplitPane1, java.awt.BorderLayout.CENTER);\n\n\t\tadd(jPanel1, java.awt.BorderLayout.CENTER);\n\n\t\ttopPanel.setLayout(new java.awt.BorderLayout());\n\n\t\ttopPanel.add(theCombo, java.awt.BorderLayout.NORTH);\n\n\t\tadd(topPanel, java.awt.BorderLayout.NORTH);\n\n\t}//GEN-END:initComponents\n\n\tpublic void valueChanged(ListSelectionEvent e)\n\t{\n\t\tSingleProperty selected = theModel.getSelectedProperty(theTable.getSelectedRow());\n\n\t\tif (selected != null) {\n\t\t\tcommentLabel.setText(selected.getName());\n\t\t\tcommentText.setText(selected.getComment());\n\t\t} else {\n\t\t\tcommentLabel.setText(\"\");\n\t\t\tcommentText.setText(\"\");\n\t\t}\n\n\t\tfor (int i = 0; i < theModel.getRowCount(); i++) {\n\t\t\tint lines = 1;\n\t\t\tif (theModel.getValueAt(i, 1) instanceof FontColorProperty) {\n\t\t\t\tint height = ((FontColorProperty) theModel.getValueAt(i, 1)).getFontColorPair().f.getSize();\n\t\t\t\theight = Math.max(height, (lineWidth - 2));\n\t\t\t\ttheTable.setRowHeight(i, (height * lines) + 4);\n\t\t\t} else if (theModel.getValueAt(i, 1) instanceof SingleProperty) {\n\t\t\t\t//lines = getNumLines(value);\n\t\t\t\t//int heightWanted = \n\t\t\t\t//theTable.setRowHeight(i, (lineWidth*lines)+2);\n\t\t\t}\n\t\t}\n\t}\n\n\tpublic void tableChanged(TableModelEvent e)\n\t{\n\t\tCellEditor ce = theTable.getCellEditor();\n\t\tif (ce != null)\n\t\t\tce.cancelCellEditing();\n\t\ttheCombo.setModel(theModel.getComboModel());\n\t\tfor (int i = 0; i < theModel.getRowCount(); i++) {\n\t\t\t////System.out.println(\"Row \"+i);\n\t\t\tString value = theModel.getValueAt(i, 1).toString();\n\t\t\tint lines = 1;\n\n\t\t\tif (theModel.getValueAt(i, 1) instanceof FontColorProperty) {\n\t\t\t\tint height = ((FontColorProperty) theModel.getValueAt(i, 1)).getFontColorPair().f.getSize();\n\n\t\t\t\theight = Math.max(height, (lineWidth - 2));\n\t\t\t\ttheTable.setRowHeight(i, (height * lines) + 4);\n\t\t\t} else if (theModel.getValueAt(i, 1) instanceof SingleProperty) {\n\t\t\t\t//lines = getNumLines(value);\n\t\t\t\t//theTable.setRowHeight(i, (lineWidth*lines)+2);\n\t\t\t\t//int heightWanted = (int)area.getPreferredSize().getHeight();\n\t\t\t\t///  if(heightWanted != theTable.getRowHeight(row));\n\t\t\t\t// theTable.setRowHeight(row, heightWanted);\n\t\t\t} else if (theModel.getValueAt(i, 1) instanceof MultipleProperty) {\n\t\t\t\tlines = getNumLines(value);\n\t\t\t\ttheTable.setRowHeight(i, (lineWidth * lines) + 2);\n\t\t\t}\n\n\t\t}\n\t\tdoChoiceBox();\n\t\t//theTable.s\n\t}\n\n\tpublic static int getNumLines(String str)\n\t{\n\t\tint count = 1;\n\t\tfor (int i = 0; i < str.length(); i++) {\n\t\t\tchar curr = str.charAt(i);\n\t\t\tif (curr == '\\n')\n\t\t\t\tcount++;\n\t\t}\n\t\t////System.out.println(\"count = \"+count);\n\t\treturn count;\n\t}\n\n\tpublic void itemStateChanged(ItemEvent e)\n\t{\n\t\ttheModel.setCurrentGroup(theCombo.getSelectedIndex());\n\t}\n\n\t// Variables declaration - do not modify//GEN-BEGIN:variables\n\tjavax.swing.JLabel commentLabel;\n\tjavax.swing.JTextArea commentText;\n\tjavax.swing.JComboBox theCombo;\n\tjavax.swing.JTable theTable;\n\tjavax.swing.JPanel topPanel;\n\n\t// End of variables declaration//GEN-END:variables\n\n\tpublic class PropertyCellEditor extends AbstractCellEditor implements TableCellEditor, CaretListener, KeyListener, ActionListener\n\t{\n\t\tJTextArea area; //For multiline SingleProperties\n\t\tJTextField field; //For single line SingleProperties\n\t\tboolean isMultiLine;\n\t\tint currentRow;\n\t\tBooleanProperty boolProp = null;\n\t\tFontColorProperty fcProp = null;\n\t\tChoiceProperty chProp = null;\n\t\tColourProperty colProp = null;\n\n\t\tpublic PropertyCellEditor()\n\t\t{\n\t\t\t//System.out.println(\"Instantiating new CELLEDITOR\");\n\t\t\tarea = new JTextArea();\n\t\t\tfield = new JTextField();\n\t\t\tarea.setLineWrap(true);\n\t\t\tarea.setWrapStyleWord(true);\n\t\t\tarea.setOpaque(true);\n\t\t\tfield.setOpaque(true);\n\t\t\tfield.addCaretListener(this);\n\t\t\tarea.addCaretListener(this);\n\t\t\tarea.addKeyListener(this);\n\n\t\t\tarea.setBackground(Color.white);\n\t\t\tsetCurrEditor(this);\n\t\t}\n\n\t\tpublic void stopEditing()\n\t\t{\n\t\t\t//System.out.println(field.getParent().toString());\n\t\t\t//if(field != null) System.out.println(\"This should stop the editing of the box \" +field.getText());\n\t\t\tsuper.stopCellEditing();\n\t\t}\n\n\t\tpublic boolean shouldSelectCell(EventObject anEvent)\n\t\t{\n\t\t\tarea.selectAll();\n\t\t\tfield.selectAll();\n\t\t\treturn true;\n\t\t}\n\n\t\tpublic Object getCellEditorValue()\n\t\t{\n\t\t\tif (boolProp != null) {\n\t\t\t\t//System.out.println(\"getting boolean cell editor value\");\n\t\t\t\tboolProp.removeListenerFromEditor(this);\n\t\t\t\treturn boolProp.getEditorValue();\n\t\t\t}\n\t\t\tif (fcProp != null) {\n\t\t\t\t//System.out.println(\"getting font colour cell editor value\");\n\t\t\t\tfcProp.removeListenerFromEditor(this);\n\t\t\t\treturn fcProp.getEditorValue();\n\t\t\t}\n\t\t\tif (chProp != null) {\n\t\t\t\t//System.out.println(\"getting choice cell editor value\");\n\t\t\t\tchProp.removeListenerFromEditor(this);\n\t\t\t\treturn chProp.getEditorValue();\n\t\t\t}\n\t\t\tif (colProp != null) {\n\t\t\t\tcolProp.removeListenerFromEditor(this);\n\t\t\t\treturn colProp.getEditorValue();\n\t\t\t}\n\t\t\tif (isMultiLine)\n\t\t\t\treturn area.getText();\n\t\t\telse\n\t\t\t\treturn field.getText();\n\t\t}\n\n\t\tpublic Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column)\n\t\t{\n\t\t\t//System.out.println(\"Calling getTableCellEditorComponent()\");\n\t\t\tcurrentRow = row;\n\t\t\tboolProp = null;\n\t\t\tfcProp = null;\n\t\t\tchProp = null;\n\t\t\tcolProp = null;\n\t\t\tif (value instanceof BooleanProperty) {\n\t\t\t\tboolProp = (BooleanProperty) value;\n\t\t\t\tboolProp.addListenerToEditor(this);\n\t\t\t\treturn boolProp.getTableCellEditorComponent(table, value, isSelected, row, column);\n\t\t\t} else if (value instanceof FontColorProperty) {\n\t\t\t\tfcProp = (FontColorProperty) value;\n\t\t\t\tfcProp.addListenerToEditor(this);\n\t\t\t\treturn fcProp.getTableCellEditorComponent(table, value, isSelected, row, column);\n\t\t\t} else if (value instanceof ChoiceProperty) {\n\t\t\t\tchProp = (ChoiceProperty) value;\n\t\t\t\tchProp.addListenerToEditor(this);\n\t\t\t\treturn chProp.getTableCellEditorComponent(table, value, isSelected, row, column);\n\t\t\t} else if (value instanceof ColourProperty) {\n\t\t\t\tcolProp = (ColourProperty) value;\n\t\t\t\tcolProp.addListenerToEditor(this);\n\t\t\t\treturn colProp.getTableCellEditorComponent(table, value, isSelected, row, column);\n\t\t\t} else if (value instanceof SingleProperty) {\n\n\t\t\t\tSingleProperty sp = (SingleProperty) value;\n\t\t\t\tif (!sp.isMultiline()) {\n\t\t\t\t\tif (!sp.isEnabled()) {/*\n\t\t\t\t\t\t\t\t\t\t\tarea.setBackground(new Color(250,250,250));\n\t\t\t\t\t\t\t\t\t\t\tarea.setForeground(Color.darkGray);\n\t\t\t\t\t\t\t\t\t\t\tfield.setBackground(new Color(250,250,250));\n\t\t\t\t\t\t\t\t\t\t\tfield.setForeground(Color.darkGray);\n\t\t\t\t\t\t\t\t\t\t\t*/\n\t\t\t\t\t\tfield.setEnabled(false);\n\t\t\t\t\t\tarea.setEnabled(false);\n\t\t\t\t\t\tfield.setEditable(false);\n\t\t\t\t\t\tarea.setEditable(false);\n\t\t\t\t\t\tfield.setCaretColor(Color.white);\n\t\t\t\t\t\tarea.setCaretColor(Color.white);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tfield.setEnabled(true);\n\t\t\t\t\t\tarea.setEnabled(true);\n\t\t\t\t\t\tfield.setEditable(true);\n\t\t\t\t\t\tarea.setEditable(true);\n\t\t\t\t\t\tfield.setCaretColor(Color.black);\n\t\t\t\t\t\tfield.setCaretColor(Color.black);\n\t\t\t\t\t}\n\t\t\t\t\tfield.setFont(table.getFont());\n\t\t\t\t\tfield.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\t\tfield.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\t\tfield.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\tfield.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\t\tfield.setText((value == null) ? \"\" : value.toString());\n\t\t\t\t\tisMultiLine = false;\n\t\t\t\t\treturn field;\n\t\t\t\t} else {\n\t\t\t\t\tif (!sp.isEnabled()) {/*\n\t\t\t\t\t\t\t\t\t\t\tarea.setBackground(new Color(250,250,250));\n\t\t\t\t\t\t\t\t\t\t\tarea.setForeground(Color.darkGray);\n\t\t\t\t\t\t\t\t\t\t\tfield.setBackground(new Color(250,250,250));\n\t\t\t\t\t\t\t\t\t\t\tfield.setForeground(Color.darkGray);\n\t\t\t\t\t\t\t\t\t\t\t*/\n\t\t\t\t\t\tfield.setEnabled(false);\n\t\t\t\t\t\tarea.setEnabled(false);\n\t\t\t\t\t\tfield.setEditable(false);\n\t\t\t\t\t\tarea.setEditable(false);\n\t\t\t\t\t\tfield.setCaretColor(Color.white);\n\t\t\t\t\t\tarea.setCaretColor(Color.white);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tfield.setEnabled(true);\n\t\t\t\t\t\tarea.setEnabled(true);\n\t\t\t\t\t\tfield.setEditable(true);\n\t\t\t\t\t\tarea.setEditable(true);\n\t\t\t\t\t\tfield.setCaretColor(Color.black);\n\t\t\t\t\t\tarea.setCaretColor(Color.black);\n\t\t\t\t\t}\n\t\t\t\t\tarea.setFont(table.getFont());\n\t\t\t\t\tarea.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\t\tarea.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\t\tarea.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\tarea.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\t\tarea.setText((value == null) ? \"\" : value.toString());\n\t\t\t\t\ttheTable.setEditingRow(row);\n\t\t\t\t\tisMultiLine = true;\n\t\t\t\t\treturn area;\n\t\t\t\t}\n\t\t\t} else if (value instanceof MultipleProperty) {\n\t\t\t\tMultipleProperty sp = (MultipleProperty) value;\n\t\t\t\tif (sp.getProperty(0) instanceof BooleanProperty) {\n\t\t\t\t\tboolProp = (BooleanProperty) sp.getProperty(0);\n\t\t\t\t\tboolProp.addListenerToEditor(this);\n\t\t\t\t\treturn boolProp.getTableCellEditorComponentMulti(table, value, isSelected, row, column, sp.allTheSame());\n\t\t\t\t} else if (sp.getProperty(0) instanceof FontColorProperty) {\n\t\t\t\t\tfcProp = (FontColorProperty) sp.getProperty(0);\n\t\t\t\t\tfcProp.addListenerToEditor(this);\n\t\t\t\t\treturn fcProp.getTableCellEditorComponentMulti(table, value, isSelected, row, column, sp.allTheSame());\n\t\t\t\t} else if (sp.getProperty(0) instanceof ChoiceProperty) {\n\t\t\t\t\tchProp = (ChoiceProperty) sp.getProperty(0);\n\t\t\t\t\tchProp.addListenerToEditor(this);\n\t\t\t\t\treturn chProp.getTableCellEditorComponentMulti(table, value, isSelected, row, column, sp.allTheSame());\n\t\t\t\t} else if (sp.getProperty(0) instanceof ColourProperty) {\n\t\t\t\t\tcolProp = (ColourProperty) sp.getProperty(0);\n\t\t\t\t\tcolProp.addListenerToEditor(this);\n\t\t\t\t\treturn colProp.getTableCellEditorComponentMulti(table, value, isSelected, row, column, sp.allTheSame());\n\t\t\t\t}\n\n\t\t\t\tif (!sp.isMultiline()) {\n\t\t\t\t\tfield.setFont(table.getFont());\n\t\t\t\t\tfield.setForeground(Color.lightGray);\n\t\t\t\t\tfield.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\tfield.setForeground(Color.lightGray);\n\t\t\t\t\tif (!sp.allTheSame())\n\t\t\t\t\t\tfield.setBackground(new Color(240, 240, 240));\n\t\t\t\t\tfield.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\t\tfield.setText((value == null) ? \"\" : value.toString());\n\t\t\t\t\tisMultiLine = false;\n\t\t\t\t\treturn field;\n\t\t\t\t} else {\n\t\t\t\t\tarea.setFont(table.getFont());\n\t\t\t\t\tarea.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\t\tarea.setForeground(Color.lightGray);\n\t\t\t\t\tarea.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\tarea.setForeground(Color.lightGray);\n\t\t\t\t\tif (!sp.allTheSame())\n\t\t\t\t\t\tarea.setBackground(new Color(240, 240, 240));\n\t\t\t\t\tarea.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\t\tarea.setText((value == null) ? \"\" : value.toString());\n\t\t\t\t\tisMultiLine = true;\n\t\t\t\t\treturn area;\n\t\t\t\t}\n\t\t\t} else\n\t\t\t\treturn new JLabel(\"ERROR\");\n\t\t}\n\n\t\tpublic void caretUpdate(CaretEvent e)\n\t\t{\n\n\t\t\t//System.out.println(\"caret update\");\n\t\t\tif (e.getSource() == field) {\n\t\t\t\tfield.getCaret().setVisible(true);\n\t\t\t}\n\t\t\tif (e.getSource() == area) {\n\t\t\t\t//System.out.println(\"area\");\n\t\t\t\tarea.getCaret().setVisible(true);\n\t\t\t\t//theTable.setRowHeight(currentRow, (area.getLineCount()*lineWidth)+2);\n\t\t\t\tint heightWanted = (int) area.getPreferredSize().getHeight();\n\t\t\t\tif (heightWanted != theTable.getRowHeight(currentRow))\n\t\t\t\t\ttheTable.setRowHeight(currentRow, heightWanted);\n\n\t\t\t}\n\t\t}\n\n\t\tpublic void keyPressed(KeyEvent e)\n\t\t{\n\t\t\tif (e.getSource() == area) {\n\t\t\t\ttry {\n\t\t\t\t\tint startOfLastLine = area.getLineStartOffset(area.getLineCount() - 1);\n\t\t\t\t\tint endOfFirstLine = area.getLineEndOffset(0);\n\t\t\t\t\tint currentPosition = area.getCaretPosition();\n\t\t\t\t\tif (e.getKeyCode() == KeyEvent.VK_UP) {\n\t\t\t\t\t\tif (currentPosition < endOfFirstLine) {\n\t\t\t\t\t\t\t//System.out.println(\"should move up\");\n\t\t\t\t\t\t\tthis.stopCellEditing();\n\n\t\t\t\t\t\t\tint newPosition = (currentRow - 1);\n\t\t\t\t\t\t\tif (newPosition < 0)\n\t\t\t\t\t\t\t\tnewPosition = theTable.getRowCount() - 1;\n\t\t\t\t\t\t\ttheTable.getSelectionModel().setSelectionInterval(newPosition, newPosition);\n\t\t\t\t\t\t} else if (area.getText().length() == 0) {\n\t\t\t\t\t\t\tthis.stopCellEditing();\n\n\t\t\t\t\t\t\tint newPosition = (currentRow - 1);\n\t\t\t\t\t\t\tif (newPosition < 0)\n\t\t\t\t\t\t\t\tnewPosition = theTable.getRowCount() - 1;\n\t\t\t\t\t\t\ttheTable.getSelectionModel().setSelectionInterval(newPosition, newPosition);\n\t\t\t\t\t\t}\n\t\t\t\t\t} else if (e.getKeyCode() == KeyEvent.VK_DOWN) {\n\t\t\t\t\t\tif (currentPosition > startOfLastLine) {\n\t\t\t\t\t\t\t//System.out.println(\"should move down\");\n\t\t\t\t\t\t\tthis.stopCellEditing();\n\t\t\t\t\t\t\tint newPosition = (currentRow + 1) % theTable.getRowCount();\n\t\t\t\t\t\t\ttheTable.getSelectionModel().setSelectionInterval(newPosition, newPosition);\n\t\t\t\t\t\t} else if (area.getText().length() == 0) {\n\t\t\t\t\t\t\tthis.stopCellEditing();\n\t\t\t\t\t\t\tint newPosition = (currentRow + 1) % theTable.getRowCount();\n\t\t\t\t\t\t\ttheTable.getSelectionModel().setSelectionInterval(newPosition, newPosition);\n\t\t\t\t\t\t}\n\t\t\t\t\t}\n\t\t\t\t} catch (BadLocationException ex) {\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\n\t\tpublic void keyReleased(KeyEvent e)\n\t\t{\n\t\t}\n\n\t\tpublic void keyTyped(KeyEvent e)\n\t\t{\n\t\t}\n\n\t\tpublic void actionPerformed(ActionEvent e)\n\t\t{\n\t\t\tstopCellEditing();\n\t\t}\n\n\t}\n\n\t//Uses different renderers for different types of property\n\tclass PropertyCellRenderer implements TableCellRenderer\n\t{\n\t\tJTextArea area;\n\t\tJTextField field;\n\n\t\tpublic PropertyCellRenderer()\n\t\t{\n\t\t\tarea = new JTextArea();\n\t\t\tfield = new JTextField();\n\t\t\tarea.setLineWrap(false);\n\t\t\tarea.setOpaque(true);\n\t\t\tfield.setOpaque(true);\n\t\t\t//area.setWrapStyleWord(f);\n\t\t}\n\n\t\tpublic Component getTableCellRendererComponent(JTable table, Object value, boolean isSelected, boolean hasFocus, int row, int column)\n\t\t{\n\t\t\t////System.out.println(\"rendering \"+value.toString());\n\t\t\tif (isSelected) {\n\t\t\t\tarea.setForeground(table.getSelectionForeground());\n\t\t\t\tarea.setBackground(table.getSelectionBackground());\n\t\t\t\tfield.setForeground(table.getSelectionForeground());\n\t\t\t\tfield.setBackground(table.getSelectionBackground());\n\t\t\t} else {\n\t\t\t\tarea.setForeground(table.getForeground());\n\t\t\t\tarea.setBackground(Color.white);\n\t\t\t\tfield.setForeground(table.getForeground());\n\t\t\t\tfield.setBackground(Color.white);\n\t\t\t}\n\n\t\t\tif (value instanceof SingleProperty) {\n\t\t\t\tSingleProperty sp = (SingleProperty) value;\n\t\t\t\tComponent c = sp.getTableCellRendererComponent(table, value, isSelected, hasFocus, row, column);\n\t\t\t\tif (c != null)\n\t\t\t\t\treturn c;\n\n\t\t\t\tif (!sp.isEnabled()) {/*\n\t\t\t\t\t\t\t\t\t\t   area.setBackground(new Color(250,250,250));\n\t\t\t\t\t\t\t\t\t\t   area.setForeground(Color.darkGray);\n\t\t\t\t\t\t\t\t\t\t   field.setBackground(new Color(250,250,250));\n\t\t\t\t\t\t\t\t\t\t   field.setForeground(Color.darkGray);\n\t\t\t\t\t\t\t\t\t\t*/\n\t\t\t\t\tfield.setEnabled(false);\n\t\t\t\t\tarea.setEnabled(false);\n\t\t\t\t\tfield.setEditable(false);\n\t\t\t\t\tarea.setEditable(false);\n\t\t\t\t\tfield.setCaretColor(Color.white);\n\t\t\t\t\tarea.setCaretColor(Color.white);\n\t\t\t\t} else {\n\t\t\t\t\tfield.setEnabled(true);\n\t\t\t\t\tarea.setEnabled(true);\n\t\t\t\t\tfield.setEditable(true);\n\t\t\t\t\tarea.setEditable(true);\n\t\t\t\t\tfield.setCaretColor(Color.black);\n\t\t\t\t\tarea.setCaretColor(Color.black);\n\t\t\t\t}\n\t\t\t\t////System.out.println(\"Rendering: \"+sp.getName()+\" \"+sp.toString()+ \" multiline = \"+sp.isMultiline());\n\t\t\t\tif (!sp.isMultiline()) {\n\t\t\t\t\tfield.setFont(table.getFont());\n\n\t\t\t\t\tif (hasFocus) {\n\t\t\t\t\t\tfield.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\t\t\t\tfield.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\t\t\t\tfield.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tfield.setBorder(new EmptyBorder(1, 2, 2, 1));\n\t\t\t\t\t}\n\t\t\t\t\tfield.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\t\tfield.setText((value == null) ? \"\" : value.toString());\n\t\t\t\t\treturn field;\n\t\t\t\t} else {\n\t\t\t\t\tarea.setFont(table.getFont());\n\n\t\t\t\t\tif (hasFocus) {\n\t\t\t\t\t\tarea.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\t\t\t\tarea.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\t\t\t\tarea.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tarea.setBorder(new EmptyBorder(0, 2, 2, 1));\n\t\t\t\t\t}\n\t\t\t\t\t//area.setBackground( Color.yellow);\n\t\t\t\t\tarea.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\t\tarea.setText((value == null) ? \"\" : value.toString());\n\n\t\t\t\t\tint heightWanted = (int) area.getPreferredSize().getHeight();\n\t\t\t\t\tif (heightWanted != theTable.getRowHeight(row))\n\t\t\t\t\t\ttheTable.setRowHeight(row, heightWanted);\n\t\t\t\t\treturn area;\n\t\t\t\t}\n\t\t\t} else if (value instanceof MultipleProperty) {\n\t\t\t\tMultipleProperty sp = (MultipleProperty) value;\n\t\t\t\t////System.out.println(\"Rendering:mult \"+sp.getName()+\" \"+sp.toString()+ \" multiline = \"+sp.isMultiline());\n\t\t\t\tComponent c = sp.getTableCellRendererComponentMulti(table, value, isSelected, hasFocus, row, column);\n\t\t\t\tif (c != null)\n\t\t\t\t\treturn c;\n\n\t\t\t\tif (!sp.isMultiline()) {\n\t\t\t\t\tfield.setFont(table.getFont());\n\n\t\t\t\t\tif (hasFocus) {\n\t\t\t\t\t\tfield.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\t\t\t\tfield.setForeground(Color.lightGray);\n\t\t\t\t\t\t\tfield.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tfield.setBorder(new EmptyBorder(1, 2, 2, 1));\n\t\t\t\t\t}\n\n\t\t\t\t\tif (!sp.allTheSame()) {\n\t\t\t\t\t\tfield.setBackground(new Color(240, 240, 240));\n\t\t\t\t\t\tfield.setForeground(Color.lightGray);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tfield.setForeground(Color.black);\n\t\t\t\t\t}\n\t\t\t\t\tfield.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\t\tfield.setText((value == null) ? \"\" : value.toString());\n\t\t\t\t\treturn field;\n\t\t\t\t} else {\n\t\t\t\t\tarea.setFont(table.getFont());\n\n\t\t\t\t\tif (hasFocus) {\n\t\t\t\t\t\tarea.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\t\t\t\tarea.setForeground(Color.lightGray);\n\t\t\t\t\t\t\tarea.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\t\t}\n\t\t\t\t\t} else {\n\t\t\t\t\t\tarea.setBorder(new EmptyBorder(0, 2, 2, 1));\n\t\t\t\t\t}\n\n\t\t\t\t\tif (!sp.allTheSame()) {\n\t\t\t\t\t\tarea.setBackground(new Color(240, 240, 240));\n\t\t\t\t\t\tarea.setForeground(Color.lightGray);\n\t\t\t\t\t} else {\n\t\t\t\t\t\tarea.setForeground(Color.black);\n\t\t\t\t\t}\n\t\t\t\t\t//area.setBackground(Color.yellow);\n\t\t\t\t\tarea.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\t\tarea.setText((value == null) ? \"\" : value.toString());\n\t\t\t\t\treturn area;\n\t\t\t\t}\n\t\t\t} else {\n\t\t\t\tfield.setFont(table.getFont());\n\n\t\t\t\tif (hasFocus) {\n\t\t\t\t\tfield.setBorder(UIManager.getBorder(\"Table.focusCellHighlightBorder\"));\n\t\t\t\t\tif (table.isCellEditable(row, column)) {\n\t\t\t\t\t\tfield.setForeground(UIManager.getColor(\"Table.focusCellForeground\"));\n\t\t\t\t\t\tfield.setBackground(UIManager.getColor(\"Table.focusCellBackground\"));\n\t\t\t\t\t}\n\t\t\t\t} else {\n\t\t\t\t\tfield.setBorder(new EmptyBorder(1, 2, 2, 1));\n\t\t\t\t}\n\t\t\t\tfield.setMargin(new Insets(0, 2, 4, 2));\n\t\t\t\tfield.setText((value == null) ? \"\" : value.toString());\n\t\t\t\treturn field;\n\t\t\t}\n\t\t}\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/PropertyTableModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport javax.swing.table.*;\nimport javax.swing.*;\nimport java.util.*;\n\n@SuppressWarnings(\"serial\")\npublic class PropertyTableModel extends AbstractTableModel implements Observer\n{\n\t//All of the data\n\tprivate ArrayList<PropertyOwner> owners;\n\n\t//Current sorted data\n\tprivate ArrayList<String> groupNames;\n\tprivate ArrayList<Integer> groupStarts;\n\tprivate ArrayList<Integer> groupSizes;\n\tprivate int currentGroup;\n\n\tprivate DefaultComboBoxModel comboModel;\n\n\tprivate JTable theTable;\n\n\tpublic PropertyTableModel()\n\t{\n\t\tsuper();\n\t\tthis.theTable = null;\n\t\tgroupNames = new ArrayList<String>();\n\t\tgroupStarts = new ArrayList<Integer>();\n\t\tgroupSizes = new ArrayList<Integer>();\n\t\towners = new ArrayList<PropertyOwner>();\n\t\tcomboModel = new DefaultComboBoxModel();\n\t}\n\n\tpublic void setJTable(JTable tab)\n\t{\n\t\tthis.theTable = tab;\n\t}\n\n\tpublic void setOwners(ArrayList<PropertyOwner> owners)\n\t{\n\t\tthis.owners = owners;\n\t\tCollections.sort(owners);\n\n\t\tIterator<PropertyOwner> it = owners.iterator();\n\t\tPropertyOwner last = null;\n\t\tint currGroupCount = 0;\n\t\tString tempName = \"\";\n\t\tgroupNames = new ArrayList<String>();\n\t\tgroupStarts = new ArrayList<Integer>();\n\t\tgroupSizes = new ArrayList<Integer>();\n\t\tint index = 0;\n\n\t\tString ownerList = \"\";\n\t\twhile (it.hasNext()) {\n\n\t\t\tPropertyOwner po = (PropertyOwner) it.next();\n\t\t\tfor (int i = 0; i < po.getNumProperties(); i++) {\n\t\t\t\tpo.getProperty(i).addObserver(this);\n\t\t\t\tpo.getProperty(i).setOwningModel(this);\n\t\t\t}\n\t\t\tif (last == null) {\n\t\t\t\t//this is the first group\n\t\t\t\tcurrGroupCount++;\n\t\t\t\tif (!po.getDescriptor().equals(\"\"))\n\t\t\t\t\townerList += \"\\'\" + po.getDescriptor() + \"\\'\";\n\t\t\t\ttempName = po.getClassDescriptor();//+\" \\'\"+po.getDescriptor()+\"\\'\";\n\t\t\t\tgroupStarts.add(Integer.valueOf(0));\n\t\t\t} else if (po.getUniquePropertyID() == last.getUniquePropertyID()) {\n\t\t\t\t//this is for the second or after in the sequence\n\t\t\t\tcurrGroupCount++;\n\t\t\t\t//tempName = \"\"+currGroupCount+\" \"+po.getClassDescriptor()+\"s\";\n\t\t\t\tif (!po.getClassDescriptor().endsWith(\"s\"))\n\t\t\t\t\ttempName = po.getClassDescriptor() + \"s\";\n\t\t\t\tif (!po.getDescriptor().equals(\"\"))\n\t\t\t\t\townerList += \", \\'\" + po.getDescriptor() + \"\\'\";\n\t\t\t} else {\n\t\t\t\t//this starts a new group\n\t\t\t\ttempName += \" \" + ownerList + \"\";\n\t\t\t\townerList = \"\";\n\t\t\t\tgroupNames.add(tempName);\n\t\t\t\tgroupSizes.add(Integer.valueOf(currGroupCount));\n\t\t\t\tcurrGroupCount = 0;\n\t\t\t\tcurrGroupCount++;\n\t\t\t\townerList += po.getDescriptor();\n\t\t\t\tif (!po.getDescriptor().equals(\"\"))\n\t\t\t\t\ttempName = po.getClassDescriptor() + \" \\'\" + po.getDescriptor() + \"\\'\";\n\t\t\t\tgroupStarts.add(Integer.valueOf(index));\n\t\t\t}\n\t\t\tlast = po;\n\t\t\tindex++;\n\t\t}\n\t\tif (owners.size() != 0) {\n\t\t\ttempName += \" \" + ownerList + \"\";\n\t\t\tgroupNames.add(tempName);\n\t\t\tgroupSizes.add(Integer.valueOf(currGroupCount));\n\t\t}\n\t\tif (currentGroup > owners.size() - 1)\n\t\t\tcurrentGroup = 0;\n\t\tcomboModel = new DefaultComboBoxModel(groupNames.toArray());\n\t\tfireTableDataChanged();\n\t}\n\n\tpublic String getGroupName(int i)\n\t{\n\t\treturn groupNames.get(i);\n\t}\n\n\tpublic int getNumGroupNames()\n\t{\n\t\treturn groupNames.size();\n\t}\n\n\tpublic int getRowCount()\n\t{\n\t\tif (groupNames.size() == 0)\n\t\t\treturn 0;\n\t\tPropertyOwner firstInGroup = owners.get(groupStarts.get(currentGroup).intValue());\n\t\treturn firstInGroup.getNumProperties();\n\t}\n\n\tpublic int getColumnCount()\n\t{\n\t\treturn 2;\n\t}\n\n\tpublic String getColumnName(int column)\n\t{\n\t\tif (column == 0)\n\t\t\treturn \"Property\";\n\t\telse\n\t\t\treturn \"Value\";\n\t}\n\n\tpublic Object getValueAt(int row, int column)\n\t{\n\t\tif (column == 0) {\n\t\t\tPropertyOwner firstInGroup = owners.get(groupStarts.get(currentGroup).intValue());\n\t\t\treturn firstInGroup.getProperty(row).getName();\n\t\t} else {\n\n\t\t\t//Simple if the selected owner group has only 1 member\n\t\t\tif (getCurrentGroupSize() == 1) {\n\t\t\t\tPropertyOwner firstInGroup = getOwner(getCurrentGroupStart());\n\t\t\t\treturn firstInGroup.getProperty(row);\n\t\t\t} else {\n\t\t\t\tArrayList<SingleProperty> currProps = new ArrayList<SingleProperty>();\n\t\t\t\tfor (int i = getCurrentGroupStart(); i < getCurrentGroupStart() + getCurrentGroupSize(); i++) {\n\t\t\t\t\tPropertyOwner prop = getOwner(i);\n\t\t\t\t\tcurrProps.add(prop.getProperty(row));\n\t\t\t\t}\n\t\t\t\tMultipleProperty mult = new MultipleProperty(currProps);\n\t\t\t\treturn mult;\n\t\t\t}\n\n\t\t}\n\t}\n\n\tpublic boolean isCellEditable(int row, int column)\n\t{\n\t\tif (column == 0) {\n\t\t\treturn false;\n\t\t} else {\n\t\t\treturn getSelectedProperty(column).isEnabled();\n\t\t}\n\t}\n\n\tpublic SingleProperty getSelectedProperty(int listIndex)\n\t{\n\t\tif (listIndex < 0)\n\t\t\treturn null;\n\t\tPropertyOwner firstInGroup = getOwner(getCurrentGroupStart());\n\t\treturn firstInGroup.getProperty(listIndex);\n\n\t}\n\n\tpublic void setValueAt(Object obj, int row, int column)\n\t{\n\t\ttry {\n\t\t\t//Simple if the selected owner group has only 1 member\n\t\t\tif (column == 1) {\n\t\t\t\tif (getCurrentGroupSize() == 1) {\n\t\t\t\t\tPropertyOwner firstInGroup = getOwner(getCurrentGroupStart());\n\t\t\t\t\tfirstInGroup.getProperty(row).setProperty(obj);\n\t\t\t\t} else {\n\n\t\t\t\t\tfor (int i = getCurrentGroupStart(); i < getCurrentGroupStart() + getCurrentGroupSize(); i++) {\n\t\t\t\t\t\tPropertyOwner prop = getOwner(i);\n\t\t\t\t\t\tprop.getProperty(row).setProperty(obj);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t}\n\t\t} catch (PropertyException e) {\n\t\t\t//Will have to give a dialog\n\t\t}\n\t}\n\n\t/** Getter for property currentGroup.\n\t * @return Value of property currentGroup.\n\t *\n\t */\n\tpublic int getCurrentGroup()\n\t{\n\t\treturn currentGroup;\n\t}\n\n\tprotected int getCurrentGroupSize()\n\t{\n\t\treturn groupSizes.get(currentGroup).intValue();\n\t}\n\n\tprotected int getCurrentGroupStart()\n\t{\n\t\treturn groupStarts.get(currentGroup).intValue();\n\t}\n\n\tprotected String getCurrentGroupName()\n\t{\n\t\treturn groupNames.get(currentGroup);\n\t}\n\n\tprotected PropertyOwner getOwner(int i)\n\t{\n\t\treturn owners.get(i);\n\t}\n\n\tpublic int getNumGroups()\n\t{\n\t\treturn groupNames.size();\n\t}\n\n\t/** Setter for property currentGroup.\n\t * @param currentGroup New value of property currentGroup.\n\t *\n\t */\n\tpublic void setCurrentGroup(int currentGroup)\n\t{\n\t\tthis.currentGroup = currentGroup;\n\t\tfireTableDataChanged();\n\t}\n\n\tpublic static void printArray(ArrayList<?> a)\n\t{\n\t\tSystem.out.print(\"(\");\n\t\tfor (int i = 0; i < a.size(); i++)\n\t\t\tSystem.out.print(a.get(i) + \" \");\n\t\t//System.out.println(\")\");\n\t}\n\n\t/**\n\t * Getter for property comboModel.\n\t * @return Value of property comboModel.\n\t */\n\tpublic DefaultComboBoxModel getComboModel()\n\t{\n\t\treturn comboModel;\n\t}\n\n\tpublic void update(Observable o, Object arg)\n\t{\n\t\tfireTableDataChanged();\n\t\trepaintTable();\n\t}\n\n\tpublic void repaintTable()\n\t{\n\t\tif (theTable != null)\n\t\t\ttheTable.repaint();\n\t}\n\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/SelectionEvent.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.util.ArrayList;\n\npublic class SelectionEvent\n{\n\tprivate ArrayList<PropertyOwner> selectedItems;\n\n\t/**\n\t * Creates a new instance of SelectionEvent \n\t */\n\tpublic SelectionEvent(ArrayList<PropertyOwner> selectedItems)\n\t{\n\t\tthis.selectedItems = selectedItems;\n\t}\n\n\t/**\n\t * Getter for property selectedItems.\n\t * @return Value of property selectedItems.\n\t */\n\tpublic ArrayList<PropertyOwner> getSelectedItems()\n\t{\n\t\treturn selectedItems;\n\t}\n\n\tpublic PropertyOwner getSelectedItem(int i)\n\t{\n\t\treturn selectedItems.get(i);\n\t}\n\n\tpublic int getSelectionSize()\n\t{\n\t\treturn selectedItems.size();\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/SelectionListener.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\nimport java.util.EventListener;\n\npublic interface SelectionListener extends EventListener\n{\n    public void selectionPerformed(SelectionEvent e);\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/SelectionModel.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport java.util.ArrayList;\nimport java.util.*;\n\n/**\n * Handles the selection of PropertyOwners\n */\npublic abstract class SelectionModel extends Observable\n{\n\n\tprivate ArrayList<SelectionListener> listeners;\n\tprivate ArrayList<PropertyOwner> currentSelection;\n\n\tpublic SelectionModel()\n\t{\n\t\tlisteners = new ArrayList<SelectionListener>();\n\t\tcurrentSelection = new ArrayList<PropertyOwner>();\n\t}\n\n\tpublic void addSelectionListener(SelectionListener s)\n\t{\n\t\tlisteners.add(s);\n\t}\n\n\tpublic void removeSelectionListener(SelectionListener s)\n\t{\n\t\tlisteners.remove(s);\n\t}\n\n\tpublic void fireSelectionChanged()\n\t{\n\t\tSelectionEvent event = new SelectionEvent(getCurrentSelection());\n\t\tSelectionListener sl;\n\n\t\tfor (int i = 0; i < listeners.size(); i++) {\n\t\t\tsl = listeners.get(i);\n\t\t\tsl.selectionPerformed(event);\n\t\t}\n\t}\n\n\tpublic ArrayList<PropertyOwner> getCurrentSelection()\n\t{\n\t\treturn currentSelection;\n\t}\n\n\tpublic PropertyOwner getSelectedItem(int i)\n\t{\n\t\treturn currentSelection.get(i);\n\t}\n\n\tpublic int getSelectionSize()\n\t{\n\t\treturn currentSelection.size();\n\t}\n\n\tprotected void addToSelection(PropertyOwner owner, boolean fireEvent)\n\t{\n\t\tif (!currentSelection.contains(owner))\n\t\t\tcurrentSelection.add(owner);\n\n\t\tif (fireEvent)\n\t\t\tfireSelectionChanged();\n\t}\n\n\tprotected void removeFromSelection(PropertyOwner owner, boolean fireEvent)\n\t{\n\t\tif (currentSelection.contains(owner))\n\t\t\tcurrentSelection.remove(owner);\n\n\t\tif (fireEvent)\n\t\t\tfireSelectionChanged();\n\t}\n\n\tprotected void clearSelection(boolean fireEvent)\n\t{\n\t\tcurrentSelection.clear();\n\n\t\tif (fireEvent)\n\t\t\tfireSelectionChanged();\n\t}\n\n\tprotected void setSelection(ArrayList<PropertyOwner> a, boolean fireEvent)\n\t{\n\t\tcurrentSelection = a;\n\n\t\tif (fireEvent)\n\t\t\tfireSelectionChanged();\n\t}\n}\n"
  },
  {
    "path": "prism/src/userinterface/util/SingleProperty.java",
    "content": "//==============================================================================\n//\t\n//\tCopyright (c) 2002-\n//\tAuthors:\n//\t* Andrew Hinton <ug60axh@cs.bham.ac.uk> (University of Birmingham)\n//\t* Dave Parker <david.parker@comlab.ox.ac.uk> (University of Oxford, formerly University of Birmingham)\n//\t\n//------------------------------------------------------------------------------\n//\t\n//\tThis file is part of PRISM.\n//\t\n//\tPRISM is free software; you can redistribute it and/or modify\n//\tit under the terms of the GNU General Public License as published by\n//\tthe Free Software Foundation; either version 2 of the License, or\n//\t(at your option) any later version.\n//\t\n//\tPRISM is distributed in the hope that it will be useful,\n//\tbut WITHOUT ANY WARRANTY; without even the implied warranty of\n//\tMERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n//\tGNU General Public License for more details.\n//\t\n//\tYou should have received a copy of the GNU General Public License\n//\talong with PRISM; if not, write to the Free Software Foundation,\n//\tInc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA\n//\t\n//==============================================================================\n\npackage userinterface.util;\n\nimport javax.swing.*;\nimport java.awt.*;\nimport java.util.*;\n\npublic class SingleProperty extends Observable \n{\n    protected String name;\n    protected Object property;\n    protected boolean multiline;\n    protected String description;\n    protected String comment;\n    protected boolean editableWhenMultiple;\n    protected PropertyOwner owner;\n    protected boolean enabled;\n    \n    /** Creates a new instance of SingleProperty */\n    public SingleProperty(PropertyOwner owner, String name, Object property)\n    {\n        this(owner, name, property, \"\", false, \"\");\n    }\n    \n    public SingleProperty(PropertyOwner owner,String name, Object property, String description)\n    {\n        this(owner,name, property, description, false, \"\");\n    }\n    \n    public SingleProperty(PropertyOwner owner,String name, Object property, boolean multiline)\n    {\n        this(owner,name, property, \"\", multiline, \"\");\n    }\n    \n    public SingleProperty(PropertyOwner owner,String name, Object property, String description, boolean multiline, String comment)\n    {\n        setOwner(owner);\n        setName(name);\n        try\n        {\n        setProperty(property);\n        }\n        catch(PropertyException e)\n        {\n            property = new String(\"INVALID\"); //default if the constructor is wrong\n        }\n        setDescription(description);\n        setMultiline(multiline);\n        setEditableWhenMultiple(true);\n        setComment(comment);\n        setEnabled(true);\n    }\n    \n    /**\n     * Getter for property name.\n     * @return Value of property name.\n     */\n    public java.lang.String getName()\n    {\n        return name;\n    }\n    \n    /**\n     * Setter for property name.\n     * @param name New value of property name.\n     */\n    public void setName(java.lang.String name)\n    {\n        this.name = name;\n        setChanged();\n        notifyObservers(null);\n    }\n    \n    /**\n     * Getter for property property.\n     * @return Value of property property.\n     */\n    public java.lang.Object getProperty()\n    {\n        return property;\n    }\n    \n    /**\n     * Setter for property property.\n     * @param property New value of property property.\n     */\n    public void setProperty(java.lang.Object property) throws PropertyException\n    {\n        setProperty(property, true);\n    }\n    \n    public void setProperty(Object property, boolean notifyObservers) throws PropertyException\n    {\n\t\t//System.out.println(\"Setting property \"+property.toString());\n        if(property == null) return; //protection\n\t\tif(property.toString().equals(\"...\")) return;\n        this.property = property;\n        if(notifyObservers)\n        {\n            setChanged();\n            notifyObservers(null);\n        }\n    }\n    \n    /**\n     * Getter for property multiline.\n     * @return Value of property multiline.\n     */\n    public boolean isMultiline()\n    {\n        return multiline;\n    }\n    \n    /**\n     * Setter for property multiline.\n     * @param multiline New value of property multiline.\n     */\n    public void setMultiline(boolean multiline)\n    {\n            this.multiline = multiline;\n            setChanged();\n            notifyObservers(null);\n    }\n    \n    /**\n     * Getter for property description.\n     * @return Value of property description.\n     */\n    public java.lang.String getDescription()\n    {\n        return description;\n    }\n    \n    /**\n     * Setter for property description.\n     * @param description New value of property description.\n     */\n    public void setDescription(java.lang.String description)\n    {\n        this.description = description;\n        setChanged();\n        notifyObservers(null);\n    }\n    \n    /** Getter for property editableWhenMultiple.\n     * @return Value of property editableWhenMultiple.\n     *\n     */\n    public boolean isEditableWhenMultiple()\n    {\n        return editableWhenMultiple;\n    }\n    \n    /** Setter for property editableWhenMultiple.\n     * @param editableWhenMultiple New value of property editableWhenMultiple.\n     *\n     */\n    public void setEditableWhenMultiple(boolean editableWhenMultiple)\n    {\n        this.editableWhenMultiple = editableWhenMultiple;\n        setChanged();\n        notifyObservers(null);\n    }\n    \n    /** Getter for property comment.\n     * @return Value of property comment.\n     *\n     */\n    public java.lang.String getComment()\n    {\n        return comment;\n    }\n    \n    /** Setter for property comment.\n     * @param comment New value of property comment.\n     *\n     */\n    public void setComment(java.lang.String comment)\n    {\n        this.comment = comment;\n        setChanged();\n        notifyObservers(null);\n    }\n    \n    public String toString()\n    {\n        return property.toString();\n    }\n    \n    \n    // This can be overridden in subclasses to provide a different renderer if required\n    public Component getTableCellRendererComponent(JTable table, Object value,\n        boolean isSelected, boolean hasFocus, int row, int column)\n    {\n        return null;\n    }\n    \n    public Component getTableCellRendererComponentMulti(JTable table, Object value,\n        boolean isSelected, boolean hasFocus, int row, int column, boolean allTheSame)\n    {\n        return null;\n    }\n    \n    //WILL NEED EDITOR TOO\n    \n    public Component getTableCellEditorComponent(JTable table, Object value, boolean isSelected, int row, int column) \n    {\n        return null;\n    }\n    \n    public Component getTableCellEditorComponentMulti(JTable table, Object value, boolean isSelected, int row, int column, boolean allTheSame) \n    {\n        return null;\n    }\n    \n    /** Getter for property owner.\n     * @return Value of property owner.\n     *\n     */\n    public userinterface.util.PropertyOwner getOwner()\n    {\n        return owner;\n    }\n    \n    /** Setter for property owner.\n     * @param owner New value of property owner.\n     *\n     */\n    public void setOwner(userinterface.util.PropertyOwner owner)\n    {\n        this.owner = owner;\n    }\n    \n    /** Getter for property enabled.\n     * @return Value of property enabled.\n     *\n     */\n    public boolean isEnabled()\n    {\n        return enabled;\n    }\n    \n    /** Setter for property enabled.\n     * @param enabled New value of property enabled.\n     *\n     */\n    public void setEnabled(boolean enabled)\n    {\n        this.enabled = enabled;\n\t\tif(ptm != null)ptm.repaintTable();\n    }\n\tprivate PropertyTableModel ptm;\n\n\tpublic void setOwningModel(PropertyTableModel ptm)\n\t{\n\t\tthis.ptm = ptm;\n\t}\n    \n}\n"
  },
  {
    "path": "prism/src/userinterface/util/package-info.java",
    "content": "/**\n * Various utility classes for the graphical user interface (GUI).\n */\npackage userinterface.util;\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/ArrayIteratorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.NoSuchElementException;\nimport java.util.Optional;\nimport java.util.function.Supplier;\n\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static org.junit.jupiter.api.Assertions.*;\n\ninterface ArrayIteratorTest\n{\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testNextIndex(Supplier<? extends ArrayIterator<?>> supplier)\n\t{\n\t\tArrayIterator<?> iterator = supplier.get();\n\t\tfor (int i=0; iterator.hasNext(); i++) {\n\t\t\tassertEquals(i, iterator.nextIndex());\n\t\t\titerator.next();\n\t\t}\n\t\tassertThrows(NoSuchElementException.class, iterator::nextIndex);\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements ArrayIteratorTest, FunctionalIteratorTest.Of<Object,ArrayIterator.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic ArrayIterator.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\treturn new ArrayIterator.Of<>(objects);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\tpublic void testOfArray(Object[] array)\n\t\t{\n\t\t\tArrayIterator.Of<Object> iterator = new ArrayIterator.Of<>(array);\n\t\t\tObject[] actual = iterator.collect(new Object[array.length]);\n\t\t\tassertArrayEquals(array, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\tpublic void testOfArrayIntInt_All(Object[] array)\n\t\t{\n\t\t\tArrayIterator.Of<Object> expected = new ArrayIterator.Of<>(array);\n\t\t\tArrayIterator.Of<Object> actual = new ArrayIterator.Of<>(array, 0, array.length);\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getMultitonArraysAsArguments\"})\n\t\tpublic void testOfArrayIntInt_Range(Object[] array)\n\t\t{\n\t\t\tFunctionalIterable<Object> expected = new Range(1, array.length - 1).map((int i) -> array[i]);\n\t\t\tArrayIterator.Of<Object> actual = new ArrayIterator.Of<>(array, 1, array.length - 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOf_Errors()\n\t\t{\n\t\t\tOptional<Object[]> any = getMultitonArraysOfObject().findAny();\n\t\t\tassert any.isPresent();\n\t\t\tObject[] array = any.get();\n\t\t\tint length = array.length;\n\t\t\tassertThrows(NullPointerException.class, () -> new ArrayIterator.Of<>((Object[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> new ArrayIterator.Of<>(null, 0, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.Of<>(array, -1, -1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.Of<>(array, -1, length));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.Of<>(array, 1, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.Of<>(array, 0, length+1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.Of<>(array, length+1, length+1));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements ArrayIteratorTest, FunctionalPrimitiveIteratorTest.OfDouble<ArrayIterator.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic ArrayIterator.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\treturn new ArrayIterator.OfDouble(numbers);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfDouble\", \"getSingletonArraysOfDouble\", \"getMultitonArraysOfDouble\"})\n\t\tpublic void testOfDouble(double[] array)\n\t\t{\n\t\t\tArrayIterator.OfDouble iterator = new ArrayIterator.OfDouble(array);\n\t\t\tdouble[] actual = iterator.collect(new double[array.length]);\n\t\t\tassertArrayEquals(array, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfDouble\", \"getSingletonArraysOfDouble\", \"getMultitonArraysOfDouble\"})\n\t\tpublic void testOfDoubleArrayIntInt_All(double[] array)\n\t\t{\n\t\t\tArrayIterator.OfDouble expected = new ArrayIterator.OfDouble(array);\n\t\t\tArrayIterator.OfDouble actual = new ArrayIterator.OfDouble(array, 0, array.length);\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getMultitonArraysOfDouble\"})\n\t\tpublic void testOfDoubleArrayIntInt_Range(double[] array)\n\t\t{\n\t\t\tFunctionalPrimitiveIterable.OfDouble expected = new Range(1, array.length - 1).mapToDouble((int i) -> array[i]);\n\t\t\tArrayIterator.OfDouble actual = new ArrayIterator.OfDouble(array, 1, array.length - 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Errors()\n\t\t{\n\t\t\tOptional<double[]> any = getMultitonArraysOfDouble().findAny();\n\t\t\tassert any.isPresent();\n\t\t\tdouble[] array = any.get();\n\t\t\tint length = array.length;\n\t\t\tassertThrows(NullPointerException.class, () -> new ArrayIterator.OfDouble((double[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> new ArrayIterator.OfDouble(null, 0, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfDouble(array, -1, -1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfDouble(array, -1, length));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfDouble(array, 1, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfDouble(array, 0, length+1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfDouble(array, length+1, length+1));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements ArrayIteratorTest, FunctionalPrimitiveIteratorTest.OfInt<ArrayIterator.OfInt>\n\t{\n\t\t@Override\n\t\tpublic ArrayIterator.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\treturn new ArrayIterator.OfInt(numbers);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfInt\", \"getSingletonArraysOfInt\", \"getMultitonArraysOfInt\"})\n\t\tpublic void testOfInt(int[] array)\n\t\t{\n\t\t\tArrayIterator.OfInt iterator = new ArrayIterator.OfInt(array);\n\t\t\tint[] actual = iterator.collect(new int[array.length]);\n\t\t\tassertArrayEquals(array, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfInt\", \"getSingletonArraysOfInt\", \"getMultitonArraysOfInt\"})\n\t\tpublic void testOfIntArrayIntInt_All(int[] array)\n\t\t{\n\t\t\tArrayIterator.OfInt expected = new ArrayIterator.OfInt(array);\n\t\t\tArrayIterator.OfInt actual = new ArrayIterator.OfInt(array, 0, array.length);\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getMultitonArraysOfInt\"})\n\t\tpublic void testOfIntArrayIntInt_Range(int[] array)\n\t\t{\n\t\t\tFunctionalPrimitiveIterable.OfInt expected = new Range(1, array.length - 1).mapToInt((int i) -> array[i]);\n\t\t\tArrayIterator.OfInt actual = new ArrayIterator.OfInt(array, 1, array.length - 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfInt_Errors()\n\t\t{\n\t\t\tOptional<int[]> any = getMultitonArraysOfInt().findAny();\n\t\t\tassert any.isPresent();\n\t\t\tint[] array = any.get();\n\t\t\tint length = array.length;\n\t\t\tassertThrows(NullPointerException.class, () -> new ArrayIterator.OfInt((int[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> new ArrayIterator.OfInt(null, 0, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfInt(array, -1, -1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfInt(array, -1, length));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfInt(array, 1, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfInt(array, 0, length+1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfInt(array, length+1, length+1));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements ArrayIteratorTest, FunctionalPrimitiveIteratorTest.OfLong<ArrayIterator.OfLong>\n\t{\n\t\t@Override\n\t\tpublic ArrayIterator.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\treturn new ArrayIterator.OfLong(numbers);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfLong\", \"getSingletonArraysOfLong\", \"getMultitonArraysOfLong\"})\n\t\tpublic void testOfLong(long[] array)\n\t\t{\n\t\t\tArrayIterator.OfLong iterator = new ArrayIterator.OfLong(array);\n\t\t\tlong[] actual = iterator.collect(new long[array.length]);\n\t\t\tassertArrayEquals(array, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfLong\", \"getSingletonArraysOfLong\", \"getMultitonArraysOfLong\"})\n\t\tpublic void testOfLongArrayIntInt_All(long[] array)\n\t\t{\n\t\t\tArrayIterator.OfLong expected = new ArrayIterator.OfLong(array);\n\t\t\tArrayIterator.OfLong actual = new ArrayIterator.OfLong(array, 0, array.length);\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getMultitonArraysOfLong\"})\n\t\tpublic void testOfLongArrayIntInt_Range(long[] array)\n\t\t{\n\t\t\tFunctionalPrimitiveIterable.OfLong expected = new Range(1, array.length - 1).mapToLong((int i) -> array[i]);\n\t\t\tArrayIterator.OfLong actual = new ArrayIterator.OfLong(array, 1, array.length - 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfLong_Errors()\n\t\t{\n\t\t\tOptional<long[]> any = getMultitonArraysOfLong().findAny();\n\t\t\tassert any.isPresent();\n\t\t\tlong[] array = any.get();\n\t\t\tint length = array.length;\n\t\t\tassertThrows(NullPointerException.class, () -> new ArrayIterator.OfLong((long[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> new ArrayIterator.OfLong(null, 0, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfLong(array, -1, -1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfLong(array, -1, length));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfLong(array, 1, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfLong(array, 0, length+1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new ArrayIterator.OfLong(array, length+1, length+1));\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/unit-tests/common/iterable/Assertions.java",
    "content": "package common.iterable;\n\nimport java.util.Iterator;\nimport java.util.NoSuchElementException;\nimport java.util.PrimitiveIterator;\n\nimport static org.junit.jupiter.api.Assertions.*;\n\npublic class Assertions\n{\n\t/**\n\t * Assert two double values are equals while assuming -0.0 == +0.0 and NaN == NaN.\n\t */\n\tprotected static void assertDoubleEquals(double expected, double actual)\n\t{\n\t\tassertTrue(expected == actual || Double.isNaN(expected) && Double.isNaN(actual));\n\t}\n\n\tpublic static void assertIterableEquals(PrimitiveIterable.OfDouble expected, PrimitiveIterable.OfDouble actual)\n\t{\n\t\tassertIteratorEquals(expected.iterator(), actual.iterator());\n\t}\n\n\tpublic static void assertIterableEquals(PrimitiveIterable.OfInt expected, PrimitiveIterable.OfInt actual)\n\t{\n\t\tassertIteratorEquals(expected.iterator(), actual.iterator());\n\t}\n\n\tpublic static void assertIterableEquals(PrimitiveIterable.OfLong expected, PrimitiveIterable.OfLong actual)\n\t{\n\t\tassertIteratorEquals(expected.iterator(), actual.iterator());\n\t}\n\n\tpublic static void assertIteratorEquals(Iterator<?> expected, Iterator<?> actual)\n\t{\n\t\twhile(expected.hasNext() && actual.hasNext()) {\n\t\t\tassertEquals(expected.next(), actual.next());\n\t\t}\n\t\tassertFalse(expected.hasNext());\n\t\tassertFalse(actual.hasNext());\n\t\tassertThrows(NoSuchElementException.class, expected::next);\n\t\tassertThrows(NoSuchElementException.class, actual::next);\n\t}\n\n\tpublic static void assertIteratorEquals(PrimitiveIterator.OfDouble expected, PrimitiveIterator.OfDouble actual)\n\t{\n\t\twhile(expected.hasNext() && actual.hasNext()) {\n\t\t\tdouble exp = expected.nextDouble();\n\t\t\tdouble act = actual.nextDouble();\n\t\t\tassertDoubleEquals(exp, act);\n\t\t}\n\t\tassertFalse(expected.hasNext());\n\t\tassertFalse(actual.hasNext());\n\t\tassertThrows(NoSuchElementException.class, expected::next);\n\t\tassertThrows(NoSuchElementException.class, actual::next);\n\t}\n\n\tpublic static void assertIteratorEquals(PrimitiveIterator.OfInt expected, PrimitiveIterator.OfInt actual)\n\t{\n\t\twhile(expected.hasNext() && actual.hasNext()) {\n\t\t\tassertEquals(expected.nextInt(), actual.nextInt());\n\t\t}\n\t\tassertFalse(expected.hasNext());\n\t\tassertFalse(actual.hasNext());\n\t\tassertThrows(NoSuchElementException.class, expected::next);\n\t\tassertThrows(NoSuchElementException.class, actual::next);\n\t}\n\n\tpublic static void assertIteratorEquals(PrimitiveIterator.OfLong expected, PrimitiveIterator.OfLong actual)\n\t{\n\t\twhile(expected.hasNext() && actual.hasNext()) {\n\t\t\tassertEquals(expected.nextLong(), actual.nextLong());\n\t\t}\n\t\tassertFalse(expected.hasNext());\n\t\tassertFalse(actual.hasNext());\n\t\tassertThrows(NoSuchElementException.class, expected::next);\n\t\tassertThrows(NoSuchElementException.class, actual::next);\n\t}\n\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/ChainedIterableTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.function.Supplier;\nimport java.util.stream.Stream;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static common.iterable.Reducible.*;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\ninterface ChainedIterableTest\n{\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements ChainedIterableTest, FunctionalIterableTest.Of<Object,ChainedIterable.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic ChainedIterable.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\tprotected Stream<FunctionalIterable<Iterable<Object>>> split(Object[] objects)\n\t\t{\n\t\t\t// 1. whole sequence\n\t\t\tFunctionalIterable<Iterable<Object>> complete = FunctionalIterable.of(Arrays.asList(objects));\n\t\t\t// 2. split & pad with empty\n\t\t\tList<Object> empty = Collections.emptyList();\n\t\t\tint l1 = objects.length / 2;\n\t\t\tObject[] first = new Object[l1];\n\t\t\tSystem.arraycopy(objects, 0, first, 0, l1);\n\t\t\tint l2 = objects.length - l1;\n\t\t\tObject[] second = new Object[l2];\n\t\t\tSystem.arraycopy(objects, l1, second, 0, l2);\n\t\t\tFunctionalIterable<Iterable<Object>>  chunks = FunctionalIterable.of(empty, Arrays.asList(first), empty, Arrays.asList(second), empty);\n\t\t\treturn Stream.of(complete, chunks);\n\t\t}\n\n\t\tpublic Stream<FunctionalIterable<Iterable<Object>>> getChains()\n\t\t{\n\t\t\treturn getArraysOfObject().flatMap(this::split);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.Of<Object>>> getDuplicatesReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<Iterable<Object>>> splits = getDuplicatesArraysOfObject().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.Of<>(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.Of<Object>>> getEmptyReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<Iterable<Object>>> splits = getEmptyArraysOfObject().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.Of<>(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.Of<Object>>> getSingletonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<Iterable<Object>>> splits = getSingletonArraysOfObject().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.Of<>(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.Of<Object>>> getMultitonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<Iterable<Object>>> splits = getMultitonArraysOfObject().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.Of<>(args));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getChains\")\n\t\tpublic void testOf(Iterable<FunctionalIterable<Object>> chain)\n\t\t{\n\t\t\tList<Object> expected = new ArrayList<>();\n\t\t\tfor (Iterable<?> iterable : chain) {\n\t\t\t\tfor (Object each : iterable) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tChainedIterable.Of<Object> actual = new ChainedIterable.Of<>(chain);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOf_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new ChainedIterable.Of<>(null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements ChainedIterableTest, FunctionalPrimitiveIterableTest.OfDouble<ChainedIterable.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic ChainedIterable.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\tprotected Stream<FunctionalIterable<PrimitiveIterable.OfDouble>> split(double[] numbers)\n\t\t{\n\t\t\t// 1. whole sequence\n\t\t\tFunctionalIterable<PrimitiveIterable.OfDouble> complete = FunctionalIterable.of(new IterableArray.OfDouble(numbers));\n\t\t\t// 2. split & pad with empty\n\t\t\tEmptyIterable.OfDouble empty = EmptyIterable.ofDouble();\n\t\t\tint l1 = numbers.length / 2;\n\t\t\tdouble[] first = new double[l1];\n\t\t\tSystem.arraycopy(numbers, 0, first, 0, l1);\n\t\t\tint l2 = numbers.length - l1;\n\t\t\tdouble[] second = new double[l2];\n\t\t\tSystem.arraycopy(numbers, l1, second, 0, l2);\n\t\t\tFunctionalIterable<PrimitiveIterable.OfDouble>  chunks = FunctionalIterable.of(empty, new IterableArray.OfDouble(first), empty, new IterableArray.OfDouble(second), empty);\n\t\t\treturn Stream.of(complete, chunks);\n\t\t}\n\n\t\tpublic Stream<FunctionalIterable<PrimitiveIterable.OfDouble>> getChains()\n\t\t{\n\t\t\treturn getArraysOfDouble().flatMap(this::split);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfDouble>> getDuplicatesReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfDouble>> splits = getDuplicatesArraysOfDouble().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfDouble(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfDouble>> getEmptyReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfDouble>> splits = getEmptyArraysOfDouble().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfDouble(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfDouble>> getSingletonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfDouble>> splits = getSingletonArraysOfDouble().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfDouble(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfDouble>> getMultitonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfDouble>> splits = getMultitonArraysOfDouble().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfDouble(args));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getChains\")\n\t\tpublic void testOf(FunctionalIterable<PrimitiveIterable.OfDouble> chain)\n\t\t{\n\t\t\tList<Double> expected = new ArrayList<>();\n\t\t\tfor (Iterable<Double> iterable : chain) {\n\t\t\t\tfor (Double each : iterable) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tChainedIterable.OfDouble actual = new ChainedIterable.OfDouble(chain);\n\t\t\tassertIterableEquals(unboxDouble(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new ChainedIterable.OfDouble(null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements ChainedIterableTest, FunctionalPrimitiveIterableTest.OfInt<ChainedIterable.OfInt>\n\t{\n\t\t@Override\n\t\tpublic ChainedIterable.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\tprotected Stream<FunctionalIterable<PrimitiveIterable.OfInt>> split(int[] numbers)\n\t\t{\n\t\t\t// 1. whole sequence\n\t\t\tFunctionalIterable<PrimitiveIterable.OfInt> complete = FunctionalIterable.of(new IterableArray.OfInt(numbers));\n\t\t\t// 2. split & pad with empty\n\t\t\tEmptyIterable.OfInt empty = EmptyIterable.ofInt();\n\t\t\tint l1 = numbers.length / 2;\n\t\t\tint[] first = new int[l1];\n\t\t\tSystem.arraycopy(numbers, 0, first, 0, l1);\n\t\t\tint l2 = numbers.length - l1;\n\t\t\tint[] second = new int[l2];\n\t\t\tSystem.arraycopy(numbers, l1, second, 0, l2);\n\t\t\tFunctionalIterable<PrimitiveIterable.OfInt>  chunks = FunctionalIterable.of(empty, new IterableArray.OfInt(first), empty, new IterableArray.OfInt(second), empty);\n\t\t\treturn Stream.of(complete, chunks);\n\t\t}\n\n\t\tpublic Stream<FunctionalIterable<PrimitiveIterable.OfInt>> getChains()\n\t\t{\n\t\t\treturn getArraysOfInt().flatMap(this::split);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfInt>> getDuplicatesReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfInt>> splits = getDuplicatesArraysOfInt().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfInt(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfInt>> getEmptyReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfInt>> splits = getEmptyArraysOfInt().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfInt(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfInt>> getSingletonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfInt>> splits = getSingletonArraysOfInt().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfInt(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfInt>> getMultitonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfInt>> splits = getMultitonArraysOfInt().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfInt(args));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getChains\")\n\t\tpublic void testOf(FunctionalIterable<PrimitiveIterable.OfInt> chain)\n\t\t{\n\t\t\tList<Integer> expected = new ArrayList<>();\n\t\t\tfor (Iterable<Integer> iterable : chain) {\n\t\t\t\tfor (Integer each : iterable) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tChainedIterable.OfInt actual = new ChainedIterable.OfInt(chain);\n\t\t\tassertIterableEquals(unboxInt(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new ChainedIterable.OfInt(null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements ChainedIterableTest, FunctionalPrimitiveIterableTest.OfLong<ChainedIterable.OfLong>\n\t{\n\t\t@Override\n\t\tpublic ChainedIterable.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\tprotected Stream<FunctionalIterable<PrimitiveIterable.OfLong>> split(long[] numbers)\n\t\t{\n\t\t\t// 1. whole sequence\n\t\t\tFunctionalIterable<PrimitiveIterable.OfLong> complete = FunctionalIterable.of(new IterableArray.OfLong(numbers));\n\t\t\t// 2. split & pad with empty\n\t\t\tEmptyIterable.OfLong empty = EmptyIterable.ofLong();\n\t\t\tint l1 = numbers.length / 2;\n\t\t\tlong[] first = new long[l1];\n\t\t\tSystem.arraycopy(numbers, 0, first, 0, l1);\n\t\t\tint l2 = numbers.length - l1;\n\t\t\tlong[] second = new long[l2];\n\t\t\tSystem.arraycopy(numbers, l1, second, 0, l2);\n\t\t\tFunctionalIterable<PrimitiveIterable.OfLong>  chunks = FunctionalIterable.of(empty, new IterableArray.OfLong(first), empty, new IterableArray.OfLong(second), empty);\n\t\t\treturn Stream.of(complete, chunks);\n\t\t}\n\n\t\tpublic Stream<FunctionalIterable<PrimitiveIterable.OfLong>> getChains()\n\t\t{\n\t\t\treturn getArraysOfLong().flatMap(this::split);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfLong>> getDuplicatesReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfLong>> splits = getDuplicatesArraysOfLong().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfLong(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfLong>> getEmptyReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfLong>> splits = getEmptyArraysOfLong().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfLong(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfLong>> getSingletonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfLong>> splits = getSingletonArraysOfLong().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfLong(args));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterable.OfLong>> getMultitonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfLong>> splits = getMultitonArraysOfLong().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterable.OfLong(args));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getChains\")\n\t\tpublic void testOf(FunctionalIterable<PrimitiveIterable.OfLong> chain)\n\t\t{\n\t\t\tList<Long> expected = new ArrayList<>();\n\t\t\tfor (Iterable<Long> iterable : chain) {\n\t\t\t\tfor (Long each : iterable) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tChainedIterable.OfLong actual = new ChainedIterable.OfLong(chain);\n\t\t\tassertIterableEquals(unboxLong(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new ChainedIterable.OfLong(null));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/ChainedIteratorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.function.Supplier;\nimport java.util.stream.Stream;\n\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\ninterface ChainedIteratorTest\n{\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements ChainedIteratorTest, FunctionalIteratorTest.Of<Object,ChainedIterator.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic ChainedIterator.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\tprotected Stream<FunctionalIterable<Iterable<Object>>> split(Object[] objects)\n\t\t{\n\t\t\t// 1. whole sequence\n\t\t\tFunctionalIterable<Iterable<Object>> complete = FunctionalIterable.of(Arrays.asList(objects));\n\t\t\t// 2. split & pad with empty\n\t\t\tList<Object> empty = Collections.emptyList();\n\t\t\tint l1 = objects.length / 2;\n\t\t\tObject[] first = new Object[l1];\n\t\t\tSystem.arraycopy(objects, 0, first, 0, l1);\n\t\t\tint l2 = objects.length - l1;\n\t\t\tObject[] second = new Object[l2];\n\t\t\tSystem.arraycopy(objects, l1, second, 0, l2);\n\t\t\tFunctionalIterable<Iterable<Object>>  chunks = FunctionalIterable.of(empty, Arrays.asList(first), empty, Arrays.asList(second), empty);\n\t\t\treturn Stream.of(complete, chunks);\n\t\t}\n\n\t\tpublic Stream<FunctionalIterable<Iterable<Object>>> getChains()\n\t\t{\n\t\t\treturn getArraysOfObject().flatMap(this::split);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.Of<Object>>> getDuplicatesReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<Iterable<Object>>> splits = getDuplicatesArraysOfObject().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.Of<>(args.map(Iterable::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.Of<Object>>> getEmptyReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<Iterable<Object>>> splits = getEmptyArraysOfObject().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.Of<>(args.map(Iterable::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.Of<Object>>> getSingletonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<Iterable<Object>>> splits = getSingletonArraysOfObject().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.Of<>(args.map(Iterable::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.Of<Object>>> getMultitonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<Iterable<Object>>> splits = getMultitonArraysOfObject().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.Of<>(args.map(Iterable::iterator).iterator()));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getChains\")\n\t\tpublic void testOf(FunctionalIterable<Iterable<Object>> chain)\n\t\t{\n\t\t\tList<Object> expected = new ArrayList<>();\n\t\t\tfor (Iterable<?> iterable : chain) {\n\t\t\t\tfor (Object each : iterable) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tFunctionalIterator<Iterator<Object>> iterators = Reducible.extend(chain.iterator()).map(Iterable::iterator);\n\t\t\tChainedIterator.Of<Object> actual = new ChainedIterator.Of<>(iterators);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOf_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new ChainedIterator.Of<>(null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements ChainedIteratorTest, FunctionalPrimitiveIteratorTest.OfDouble<ChainedIterator.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic ChainedIterator.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\tprotected Stream<FunctionalIterable<PrimitiveIterable.OfDouble>> split(double[] numbers)\n\t\t{\n\t\t\t// 1. whole sequence\n\t\t\tFunctionalIterable<PrimitiveIterable.OfDouble> complete = FunctionalIterable.of(new IterableArray.OfDouble(numbers));\n\t\t\t// 2. split & pad with empty\n\t\t\tEmptyIterable.OfDouble empty = EmptyIterable.ofDouble();\n\t\t\tint l1 = numbers.length / 2;\n\t\t\tdouble[] first = new double[l1];\n\t\t\tSystem.arraycopy(numbers, 0, first, 0, l1);\n\t\t\tint l2 = numbers.length - l1;\n\t\t\tdouble[] second = new double[l2];\n\t\t\tSystem.arraycopy(numbers, l1, second, 0, l2);\n\t\t\tFunctionalIterable<PrimitiveIterable.OfDouble>  chunks = FunctionalIterable.of(empty, new IterableArray.OfDouble(first), empty, new IterableArray.OfDouble(second), empty);\n\t\t\treturn Stream.of(complete, chunks);\n\t\t}\n\n\t\tpublic Stream<FunctionalIterable<PrimitiveIterable.OfDouble>> getChains()\n\t\t{\n\t\t\treturn getArraysOfDouble().flatMap(this::split);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfDouble>> getDuplicatesReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfDouble>> splits = getDuplicatesArraysOfDouble().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfDouble(args.map(PrimitiveIterable.OfDouble::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfDouble>> getEmptyReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfDouble>> splits = getEmptyArraysOfDouble().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfDouble(args.map(PrimitiveIterable.OfDouble::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfDouble>> getSingletonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfDouble>> splits = getSingletonArraysOfDouble().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfDouble(args.map(PrimitiveIterable.OfDouble::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfDouble>> getMultitonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfDouble>> splits = getMultitonArraysOfDouble().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfDouble(args.map(PrimitiveIterable.OfDouble::iterator).iterator()));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getChains\")\n\t\tpublic void testOf(FunctionalIterable<PrimitiveIterable.OfDouble> chain)\n\t\t{\n\t\t\tList<Double> expected = new ArrayList<>();\n\t\t\tfor (Iterable<Double> iterable : chain) {\n\t\t\t\tfor (Double each : iterable) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tFunctionalIterator<PrimitiveIterator.OfDouble> iterators = Reducible.extend(chain.iterator()).map(PrimitiveIterable.OfDouble::iterator);\n\t\t\tChainedIterator.OfDouble actual = new ChainedIterator.OfDouble(iterators);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new ChainedIterator.OfDouble(null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements ChainedIteratorTest, FunctionalPrimitiveIteratorTest.OfInt<ChainedIterator.OfInt>\n\t{\n\t\t@Override\n\t\tpublic ChainedIterator.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\tprotected Stream<FunctionalIterable<PrimitiveIterable.OfInt>> split(int[] numbers)\n\t\t{\n\t\t\t// 1. whole sequence\n\t\t\tFunctionalIterable<PrimitiveIterable.OfInt> complete = FunctionalIterable.of(new IterableArray.OfInt(numbers));\n\t\t\t// 2. split & pad with empty\n\t\t\tEmptyIterable.OfInt empty = EmptyIterable.ofInt();\n\t\t\tint l1 = numbers.length / 2;\n\t\t\tint[] first = new int[l1];\n\t\t\tSystem.arraycopy(numbers, 0, first, 0, l1);\n\t\t\tint l2 = numbers.length - l1;\n\t\t\tint[] second = new int[l2];\n\t\t\tSystem.arraycopy(numbers, l1, second, 0, l2);\n\t\t\tFunctionalIterable<PrimitiveIterable.OfInt>  chunks = FunctionalIterable.of(empty, new IterableArray.OfInt(first), empty, new IterableArray.OfInt(second), empty);\n\t\t\treturn Stream.of(complete, chunks);\n\t\t}\n\n\t\tpublic Stream<FunctionalIterable<PrimitiveIterable.OfInt>> getChains()\n\t\t{\n\t\t\treturn getArraysOfInt().flatMap(this::split);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfInt>> getDuplicatesReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfInt>> splits = getDuplicatesArraysOfInt().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfInt(args.map(PrimitiveIterable.OfInt::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfInt>> getEmptyReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfInt>> splits = getEmptyArraysOfInt().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfInt(args.map(PrimitiveIterable.OfInt::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfInt>> getSingletonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfInt>> splits = getSingletonArraysOfInt().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfInt(args.map(PrimitiveIterable.OfInt::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfInt>> getMultitonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfInt>> splits = getMultitonArraysOfInt().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfInt(args.map(PrimitiveIterable.OfInt::iterator).iterator()));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getChains\")\n\t\tpublic void testOf(FunctionalIterable<PrimitiveIterable.OfInt> chain)\n\t\t{\n\t\t\tList<Integer> expected = new ArrayList<>();\n\t\t\tfor (Iterable<Integer> iterable : chain) {\n\t\t\t\tfor (Integer each : iterable) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tFunctionalIterator<PrimitiveIterator.OfInt> iterators = Reducible.extend(chain.iterator()).map(PrimitiveIterable.OfInt::iterator);\n\t\t\tChainedIterator.OfInt actual = new ChainedIterator.OfInt(iterators);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new ChainedIterator.OfInt(null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements ChainedIteratorTest, FunctionalPrimitiveIteratorTest.OfLong<ChainedIterator.OfLong>\n\t{\n\t\t@Override\n\t\tpublic ChainedIterator.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\tprotected Stream<FunctionalIterable<PrimitiveIterable.OfLong>> split(long[] numbers)\n\t\t{\n\t\t\t// 1. whole sequence\n\t\t\tFunctionalIterable<PrimitiveIterable.OfLong> complete = FunctionalIterable.of(new IterableArray.OfLong(numbers));\n\t\t\t// 2. split & pad with empty\n\t\t\tEmptyIterable.OfLong empty = EmptyIterable.ofLong();\n\t\t\tint l1 = numbers.length / 2;\n\t\t\tlong[] first = new long[l1];\n\t\t\tSystem.arraycopy(numbers, 0, first, 0, l1);\n\t\t\tint l2 = numbers.length - l1;\n\t\t\tlong[] second = new long[l2];\n\t\t\tSystem.arraycopy(numbers, l1, second, 0, l2);\n\t\t\tFunctionalIterable<PrimitiveIterable.OfLong>  chunks = FunctionalIterable.of(empty, new IterableArray.OfLong(first), empty, new IterableArray.OfLong(second), empty);\n\t\t\treturn Stream.of(complete, chunks);\n\t\t}\n\n\t\tpublic Stream<Iterable<PrimitiveIterable.OfLong>> getChains()\n\t\t{\n\t\t\treturn getArraysOfLong().flatMap(this::split);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfLong>> getDuplicatesReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfLong>> splits = getDuplicatesArraysOfLong().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfLong(args.map(PrimitiveIterable.OfLong::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfLong>> getEmptyReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfLong>> splits = getEmptyArraysOfLong().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfLong(args.map(PrimitiveIterable.OfLong::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfLong>> getSingletonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfLong>> splits = getSingletonArraysOfLong().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfLong(args.map(PrimitiveIterable.OfLong::iterator).iterator()));\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<ChainedIterator.OfLong>> getMultitonReducibles()\n\t\t{\n\t\t\tStream<FunctionalIterable<PrimitiveIterable.OfLong>> splits = getMultitonArraysOfLong().flatMap(this::split);\n\t\t\treturn splits.map(args -> () -> new ChainedIterator.OfLong(args.map(PrimitiveIterable.OfLong::iterator).iterator()));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getChains\")\n\t\tpublic void testOf(FunctionalIterable<PrimitiveIterable.OfLong> chain)\n\t\t{\n\t\t\tList<Long> expected = new ArrayList<>();\n\t\t\tfor (Iterable<Long> iterable : chain) {\n\t\t\t\tfor (Long each : iterable) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tFunctionalIterator<PrimitiveIterator.OfLong> iterators = Reducible.extend(chain.iterator()).map(PrimitiveIterable.OfLong::iterator);\n\t\t\tChainedIterator.OfLong actual = new ChainedIterator.OfLong(iterators);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new ChainedIterator.OfLong(null));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/DistinctTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.stream.Stream;\n\nimport static org.junit.jupiter.api.Assertions.*;\n\npublic interface DistinctTest<E, T extends Distinct<E>>\n{\n\tT getDistinct();\n\n\tboolean test(T distinct, E element);\n\n\tStream<FunctionalIterable<E>> getElements();\n\n\t@ParameterizedTest\n\t@MethodSource(\"getElements\")\n\tdefault void testGetSeen(FunctionalIterable<E> elements)\n\t{\n\t\tT distinct = getDistinct();\n\t\tassertTrue(distinct.getSeen().isEmpty());\n\t\tfor (E e : elements) {\n\t\t\ttest(distinct, e);\n\t\t\ttest(distinct, e);\n\t\t}\n\t\tFunctionalIterable<E> seen = distinct.getSeen();\n\t\tfor (E e : elements) {\n\t\t\tassertTrue(seen.contains(e));\n\t\t}\n\t\tfor (E e : seen) {\n\t\t\tassertTrue(elements.contains(e));\n\t\t}\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getElements\")\n\tdefault void testTest(FunctionalIterable<E> elements)\n\t{\n\t\tT distinct = getDistinct();\n\t\tfor (E e : elements) {\n\t\t\tassertTrue(test(distinct, e));\n\t\t\tassertFalse(test(distinct, e));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements DistinctTest<String, Distinct.Of<String>>\n\t{\n\t\t@Override\n\t\tpublic Distinct.Of<String> getDistinct()\n\t\t{\n\t\t\treturn new Distinct.Of<>();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean test(Distinct.Of<String> distinct, String element)\n\t\t{\n\t\t\treturn distinct.test(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<FunctionalIterable<String>> getElements()\n\t\t{\n\t\t\treturn Stream.of(new IterableArray.Of<>(\"first\", \"second\", \"third\"));\n\t\t}\n\t}\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements DistinctTest<Double, Distinct.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic Distinct.OfDouble getDistinct()\n\t\t{\n\t\t\treturn new Distinct.OfDouble();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean test(Distinct.OfDouble distinct, Double element)\n\t\t{\n\t\t\treturn distinct.test(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<FunctionalIterable<Double>> getElements()\n\t\t{\n\t\t\treturn Stream.of(new IterableArray.Of<>(Double.NEGATIVE_INFINITY, Double.POSITIVE_INFINITY, Double.NaN, 0.0, 1.0, 2.0, 3.0));\n\t\t}\n\n\t\t@Test\n\t\tpublic void testTest_PositiveZero()\n\t\t{\n\t\t\tDistinct.OfDouble distinct = getDistinct();\n\t\t\tassertTrue(distinct.test(+0.0));\n\t\t\tassertFalse(distinct.test(+0.0));\n\t\t\tassertFalse(distinct.test(-0.0));\n\t\t}\n\n\t\t@Test\n\t\tpublic void testTest_NegativeZero()\n\t\t{\n\t\t\tDistinct.OfDouble distinct = getDistinct();\n\t\t\tassertTrue(distinct.test(+0.0));\n\t\t\tassertFalse(distinct.test(-0.0));\n\t\t\tassertFalse(distinct.test(+0.0));\n\t\t}\n\t}\n\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements DistinctTest<Integer, Distinct.OfInt>\n\t{\n\t\t@Override\n\t\tpublic Distinct.OfInt getDistinct()\n\t\t{\n\t\t\treturn new Distinct.OfInt();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean test(Distinct.OfInt distinct, Integer element)\n\t\t{\n\t\t\treturn distinct.test(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<FunctionalIterable<Integer>> getElements()\n\t\t{\n\t\t\treturn Stream.of(new IterableArray.Of<>(1, 2, 3));\n\t\t}\n\t}\n\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements DistinctTest<Long, Distinct.OfLong>\n\t{\n\t\t@Override\n\t\tpublic Distinct.OfLong getDistinct()\n\t\t{\n\t\t\treturn new Distinct.OfLong();\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean test(Distinct.OfLong distinct, Long element)\n\t\t{\n\t\t\treturn distinct.test(element);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<FunctionalIterable<Long>> getElements()\n\t\t{\n\t\t\treturn Stream.of(new IterableArray.Of<>(1L, 2L, 3L));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/EmptyIterableTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.TestInstance;\n\nimport java.util.function.Supplier;\nimport java.util.stream.Stream;\n\ninterface EmptyIterableTest<E, T extends EmptyIterable<E>> extends FunctionalIterableTest<E,T>\n{\n\t@Override\n\tdefault void testAllMatch(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testAnyMatch(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testDetect_Multiton(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testDetect_Singleton(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testFlatMapToNull(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testNoneMatch(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testIsEmpty_NonEmpty(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testReduceBinaryOperatorOfE_Singleton(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testReduceBinaryOperatorOfE_Multiton(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testReduceBinary_ResultNull(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements EmptyIterableTest<Object,EmptyIterable.Of<Object>>, FunctionalIterableTest.Of<Object,EmptyIterable.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic EmptyIterable.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tassert objects.length == 0 : \"empty array expected\";\n\t\t\treturn EmptyIterable.of();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.Of<Object>>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.Of<Object>>> getSingletonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.Of<Object>>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements EmptyIterableTest<Double,EmptyIterable.OfDouble>, FunctionalPrimitiveIterableTest.OfDouble<EmptyIterable.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic EmptyIterable.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 0 : \"empty array expected\";\n\t\t\treturn EmptyIterable.ofDouble();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfDouble>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfDouble>> getSingletonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfDouble>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatchDoublePredicate(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testAnyMatchDoublePredicate(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectDoublePredicate_Multiton(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectDoublePredicate_Singleton(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testFlatMapDoubleToNull(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Singleton(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Singleton(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchDoublePredicate(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Singleton(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Multiton(Supplier<EmptyIterable.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements EmptyIterableTest<Integer,EmptyIterable.OfInt>, FunctionalPrimitiveIterableTest.OfInt<EmptyIterable.OfInt>\n\t{\n\t\t@Override\n\t\tpublic EmptyIterable.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 0 : \"empty array expected\";\n\t\t\treturn EmptyIterable.ofInt();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfInt>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfInt>> getSingletonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfInt>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatchIntPredicate(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testAnyMatchIntPredicate(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectIntPredicate_Multiton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectIntPredicate_Singleton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testFlatMapIntToNull(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Singleton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Singleton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchIntPredicate(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Singleton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Multiton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceIntBinaryOperator_Singleton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceIntBinaryOperator_Multiton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Singleton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Multiton(Supplier<EmptyIterable.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements EmptyIterableTest<Long,EmptyIterable.OfLong>, FunctionalPrimitiveIterableTest.OfLong<EmptyIterable.OfLong>\n\t{\n\t\t@Override\n\t\tpublic EmptyIterable.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 0 : \"empty array expected\";\n\t\t\treturn EmptyIterable.ofLong();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfLong>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfLong>> getSingletonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterable.OfLong>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatchLongPredicate(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testAnyMatch(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testAnyMatchLongPredicate(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectLongPredicate_Multiton(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectLongPredicate_Singleton(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testFlatMapLongToNull(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Singleton(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Singleton(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchLongPredicate(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Singleton(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Multiton(Supplier<EmptyIterable.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\t}\n}"
  },
  {
    "path": "prism/unit-tests/common/iterable/EmptyIteratorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.TestInstance;\n\nimport java.util.function.Supplier;\nimport java.util.stream.Stream;\n\ninterface EmptyIteratorTest<E, T extends EmptyIterator<E>> extends FunctionalIteratorTest<E,T>\n{\n\t@Override\n\tdefault void testAllMatch(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testAnyMatch(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testDetect_Multiton(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testDetect_Singleton(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testFlatMapToNull(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testNoneMatch(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testIsEmpty_NonEmpty(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testReduceBinaryOperatorOfE_Singleton(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testReduceBinaryOperatorOfE_Multiton(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\t@Override\n\tdefault void testReduceBinary_ResultNull(Supplier<T> supplier)\n\t{ /* empty reducibles hold no value */ }\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements EmptyIteratorTest<Object,EmptyIterator.Of<Object>>, FunctionalIteratorTest.Of<Object,EmptyIterator.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic EmptyIterator.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tassert objects.length == 0 : \"empty array expected\";\n\t\t\treturn EmptyIterator.of();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.Of<Object>>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.Of<Object>>> getSingletonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.Of<Object>>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements EmptyIteratorTest<Double,EmptyIterator.OfDouble>, FunctionalPrimitiveIteratorTest.OfDouble<EmptyIterator.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic EmptyIterator.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 0 : \"empty array expected\";\n\t\t\treturn EmptyIterator.ofDouble();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfDouble>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfDouble>> getSingletonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfDouble>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatchDoublePredicate(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testAnyMatchDoublePredicate(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectDoublePredicate_Multiton(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectDoublePredicate_Singleton(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testFlatMapDoubleToNull(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Singleton(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Singleton(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchDoublePredicate(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Singleton(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Multiton(Supplier<EmptyIterator.OfDouble> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements EmptyIteratorTest<Integer,EmptyIterator.OfInt>, FunctionalPrimitiveIteratorTest.OfInt<EmptyIterator.OfInt>\n\t{\n\t\t@Override\n\t\tpublic EmptyIterator.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 0 : \"empty array expected\";\n\t\t\treturn EmptyIterator.ofInt();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfInt>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfInt>> getSingletonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfInt>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatchIntPredicate(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testAnyMatchIntPredicate(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectIntPredicate_Multiton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectIntPredicate_Singleton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testFlatMapIntToNull(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Singleton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Singleton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchIntPredicate(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Singleton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Multiton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceIntBinaryOperator_Singleton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceIntBinaryOperator_Multiton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Singleton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Multiton(Supplier<EmptyIterator.OfInt> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements EmptyIteratorTest<Long,EmptyIterator.OfLong>, FunctionalPrimitiveIteratorTest.OfLong<EmptyIterator.OfLong>\n\t{\n\t\t@Override\n\t\tpublic EmptyIterator.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 0 : \"empty array expected\";\n\t\t\treturn EmptyIterator.ofLong();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfLong>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfLong>> getSingletonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<EmptyIterator.OfLong>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatchLongPredicate(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testAnyMatch(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testAnyMatchLongPredicate(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectLongPredicate_Multiton(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testDetectLongPredicate_Singleton(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testFlatMapLongToNull(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Singleton(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Singleton(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchLongPredicate(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Singleton(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Multiton(Supplier<EmptyIterator.OfLong> supplier)\n\t\t{ /* empty reducibles hold no value */ }\n\t}\n}"
  },
  {
    "path": "prism/unit-tests/common/iterable/FilteringIterableTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\ninterface FilteringIterableTest\n{\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements FilteringIterableTest, FunctionalIterableTest.Of<Object,FilteringIterable.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic FilteringIterable.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\treturn new FilteringIterable.Of<>(FunctionalIterable.of(objects), e -> true);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\tvoid testOf(Object[] objects)\n\t\t{\n\t\t\tArrayList<Object> expected = new ArrayList<>();\n\t\t\tint c = 0;\n\t\t\tfor (Object each : objects) {\n\t\t\t\tif (c++ % 2 == 0) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tIterable<Object> iterable = Arrays.asList(objects);\n\t\t\tFunctionalIterable<Object> actual = new FilteringIterable.Of<>(iterable, expected::contains);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOf_Null()\n\t\t{\n\t\t\tEmptyIterable.Of<Object> iterable = EmptyIterable.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterable.Of<>(null, e -> true));\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterable.Of<>(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements FilteringIterableTest, FunctionalPrimitiveIterableTest.OfDouble<FilteringIterable.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic FilteringIterable.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\treturn new FilteringIterable.OfDouble(FunctionalIterable.ofDouble(numbers), e -> true);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testOfDouble(double[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tint c = 0;\n\t\t\tfor (double d : numbers) {\n\t\t\t\tif (c++ % 2 == 0) {\n\t\t\t\t\texpected.add(d);\n\t\t\t\t}\n\t\t\t}\n\t\t\tIterableArray.OfDouble iterable = new IterableArray.OfDouble(numbers);\n\t\t\tFunctionalPrimitiveIterable.OfDouble actual = new FilteringIterable.OfDouble(iterable, expected::contains);\n\t\t\tassertIterableEquals(unboxDouble(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tEmptyIterable.OfDouble iterable = EmptyIterable.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterable.OfDouble(null, e -> true));\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterable.OfDouble(iterable, null));\n\t\t}\n\t}\n\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements FilteringIterableTest, FunctionalPrimitiveIterableTest.OfInt<FilteringIterable.OfInt>\n\t{\n\t\t@Override\n\t\tpublic FilteringIterable.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\treturn new FilteringIterable.OfInt(FunctionalIterable.ofInt(numbers), e -> true);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testOfInt(int[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tint c = 0;\n\t\t\tfor (int i : numbers) {\n\t\t\t\tif (c++ % 2 == 0) {\n\t\t\t\t\texpected.add(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\tIterableArray.OfInt iterable = new IterableArray.OfInt(numbers);\n\t\t\tFunctionalPrimitiveIterable.OfInt actual = new FilteringIterable.OfInt(iterable, expected::contains);\n\t\t\tassertIterableEquals(unboxInt(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfInt_Null()\n\t\t{\n\t\t\tEmptyIterable.OfInt iterable = EmptyIterable.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterable.OfInt(null, e -> true));\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterable.OfInt(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements FilteringIterableTest, FunctionalPrimitiveIterableTest.OfLong<FilteringIterable.OfLong>\n\t{\n\t\t@Override\n\t\tpublic FilteringIterable.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\treturn new FilteringIterable.OfLong(FunctionalIterable.ofLong(numbers), e -> true);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testOfLong(long[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tint c = 0;\n\t\t\tfor (Long i : numbers) {\n\t\t\t\tif (c++ % 2 == 0) {\n\t\t\t\t\texpected.add(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\tIterableArray.OfLong iterable = new IterableArray.OfLong(numbers);\n\t\t\tFunctionalPrimitiveIterable.OfLong actual = new FilteringIterable.OfLong(iterable, expected::contains);\n\t\t\tassertIterableEquals(unboxLong(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfLong_Null()\n\t\t{\n\t\t\tEmptyIterable.OfLong iterable = EmptyIterable.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterable.OfLong(null, e -> true));\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterable.OfLong(iterable, null));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/FilteringIteratorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.ArrayList;\nimport java.util.Arrays;\nimport java.util.Iterator;\n\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\ninterface FilteringIteratorTest\n{\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements FilteringIteratorTest, FunctionalIteratorTest.Of<Object,FilteringIterator.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic FilteringIterator.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\treturn new FilteringIterator.Of<>(FunctionalIterator.of(objects), e -> true);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\tvoid testOf(Object[] objects)\n\t\t{\n\t\t\tArrayList<Object> expected = new ArrayList<>();\n\t\t\tint c = 0;\n\t\t\tfor (Object each : objects) {\n\t\t\t\tif (c++ % 2 == 0) {\n\t\t\t\t\texpected.add(each);\n\t\t\t\t}\n\t\t\t}\n\t\t\tIterator<Object> iterator = Arrays.asList(objects).iterator();\n\t\t\tFunctionalIterator<Object> actual = new FilteringIterator.Of<>(iterator, expected::contains);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOf_Null()\n\t\t{\n\t\t\tEmptyIterator.Of<Object> iterator = EmptyIterator.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterator.Of<>(null, e -> true));\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterator.Of<>(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements FilteringIteratorTest, FunctionalPrimitiveIteratorTest.OfDouble<FilteringIterator.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic FilteringIterator.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\treturn new FilteringIterator.OfDouble(FunctionalIterator.ofDouble(numbers), e -> true);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testOfDouble(double[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tint c = 0;\n\t\t\tfor (double d : numbers) {\n\t\t\t\tif (c++ % 2 == 0) {\n\t\t\t\t\texpected.add(d);\n\t\t\t\t}\n\t\t\t}\n\t\t\tArrayIterator.OfDouble iterator = new ArrayIterator.OfDouble(numbers);\n\t\t\tFunctionalPrimitiveIterator.OfDouble actual = new FilteringIterator.OfDouble(iterator, expected::contains);\n\t\t\tassertIteratorEquals(unboxDouble(expected.iterator()), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tEmptyIterator.OfDouble iterator = EmptyIterator.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterator.OfDouble(null, e -> true));\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterator.OfDouble(iterator, null));\n\t\t}\n\t}\n\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements FilteringIteratorTest, FunctionalPrimitiveIteratorTest.OfInt<FilteringIterator.OfInt>\n\t{\n\t\t@Override\n\t\tpublic FilteringIterator.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\treturn new FilteringIterator.OfInt(FunctionalIterator.ofInt(numbers), e -> true);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testOfInt(int[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tint c = 0;\n\t\t\tfor (int i : numbers) {\n\t\t\t\tif (c++ % 2 == 0) {\n\t\t\t\t\texpected.add(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\tArrayIterator.OfInt iterator = new ArrayIterator.OfInt(numbers);\n\t\t\tFunctionalPrimitiveIterator.OfInt actual = new FilteringIterator.OfInt(iterator, expected::contains);\n\t\t\tassertIteratorEquals(unboxInt(expected.iterator()), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfInt_Null()\n\t\t{\n\t\t\tEmptyIterator.OfInt iterator = EmptyIterator.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterator.OfInt(null, e -> true));\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterator.OfInt(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements FilteringIteratorTest, FunctionalPrimitiveIteratorTest.OfLong<FilteringIterator.OfLong>\n\t{\n\t\t@Override\n\t\tpublic FilteringIterator.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\treturn new FilteringIterator.OfLong(FunctionalIterator.ofLong(numbers), e -> true);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testOfLong(long[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tint c = 0;\n\t\t\tfor (Long i : numbers) {\n\t\t\t\tif (c++ % 2 == 0) {\n\t\t\t\t\texpected.add(i);\n\t\t\t\t}\n\t\t\t}\n\t\t\tArrayIterator.OfLong iterator = new ArrayIterator.OfLong(numbers);\n\t\t\tFunctionalPrimitiveIterator.OfLong actual = new FilteringIterator.OfLong(iterator, expected::contains);\n\t\t\tassertIteratorEquals(unboxLong(expected.iterator()), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfLong_Null()\n\t\t{\n\t\t\tEmptyIterator.OfLong iterator = EmptyIterator.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterator.OfLong(null, e -> true));\n\t\t\tassertThrows(NullPointerException.class, () -> new FilteringIterator.OfLong(iterator, null));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/FunctionalIterableStaticTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.stream.Stream;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.*;\n\nclass FunctionalIterableStaticTest\n{\n\tstatic Stream<Iterable<Object>> getIterables()\n\t{\n\t\treturn Stream.of(Collections.singleton(null),\n\t\t\t\tCollections.emptyList(),\n\t\t\t\tCollections.singleton(\"one\"),\n\t\t\t\tArrays.asList(\"one\", \"two\", \"three\"));\n\t}\n\n\tstatic Stream<Iterable<Double>> getIterablesDouble()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t\t\tCollections.singleton(1.0),\n\t\t\t\tArrays.asList(1.0, 2.0, 3.0));\n\t}\n\n\tstatic Stream<Iterable<Integer>> getIterablesInt()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t\t\tCollections.singleton(1),\n\t\t\t\tArrays.asList(1, 2, 3));\n\t}\n\n\tstatic Stream<Iterable<Long>> getIterablesLong()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t\t\tCollections.singleton(1L),\n\t\t\t\tArrays.asList(1L, 2L, 3L));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterables\")\n\tvoid testOf(Iterable<Object> iterable)\n\t{\n\t\tFunctionalIterable<Object> expected = Reducible.extend(iterable);\n\t\tObject[] arguments = new Object[Math.toIntExact(expected.count())];\n\t\texpected.collect(arguments);\n\t\tFunctionalIterable<Object> actual = FunctionalIterable.of(arguments);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testOfTypes()\n\t{\n\t\tassertTrue(FunctionalIterable.of() instanceof EmptyIterable.Of);\n\t\tassertTrue(FunctionalIterable.of(\"first\") instanceof SingletonIterable.Of);\n\t}\n\n\t@Test\n\tvoid testOf_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> FunctionalIterable.of((Object[]) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\tvoid testOfDouble(Iterable<Double> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfDouble expected = Reducible.unboxDouble(iterable);\n\t\tdouble[] arguments = new double[Math.toIntExact(expected.count())];\n\t\texpected.collect(arguments);\n\t\tFunctionalPrimitiveIterable.OfDouble actual = FunctionalIterable.ofDouble(arguments);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tstatic void testOfDoubleTypes()\n\t{\n\t\tassertTrue(FunctionalIterable.ofDouble() instanceof EmptyIterable.OfDouble);\n\t\tassertTrue(FunctionalIterable.ofDouble(1.0) instanceof SingletonIterable.Of);\n\t}\n\n\t@Test\n\tvoid testOfDouble_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> FunctionalIterable.ofDouble((double[]) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\tvoid testOfInt(Iterable<Integer> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfInt expected = Reducible.unboxInt(iterable);\n\t\tint[] arguments = new int[Math.toIntExact(expected.count())];\n\t\texpected.collect(arguments);\n\t\tFunctionalPrimitiveIterable.OfInt actual = FunctionalIterable.ofInt(arguments);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testOfIntTypes()\n\t{\n\t\tassertTrue(FunctionalIterable.ofInt() instanceof EmptyIterable.OfInt);\n\t\tassertTrue(FunctionalIterable.ofInt(1) instanceof SingletonIterable.OfInt);\n\t}\n\n\t@Test\n\tvoid testOfInt_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> FunctionalIterable.ofInt((int[])null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\tvoid testOfLong(Iterable<Long> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfLong expected = Reducible.unboxLong(iterable);\n\t\tlong[] arguments = new long[Math.toIntExact(expected.count())];\n\t\texpected.collect(arguments);\n\t\tFunctionalPrimitiveIterable.OfLong actual = FunctionalIterable.ofLong(arguments);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testOfLongTypes()\n\t{\n\t\tassertTrue(FunctionalIterable.ofLong() instanceof EmptyIterable.OfLong);\n\t\tassertTrue(FunctionalIterable.ofLong(1L) instanceof SingletonIterable.OfLong);\n\t}\n\n\t@Test\n\tvoid testOfLong_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> FunctionalIterable.ofLong((long[]) null));\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/FunctionalIterableTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.DisplayName;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.function.Supplier;\n\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.*;\n\npublic interface FunctionalIterableTest<E, T extends FunctionalIterable<E>> extends ReducibleTest<E, T>\n{\n\t@ParameterizedTest\n\t@MethodSource({\"getReducibles\"})\n\t@Override\n\tdefault void testConcat(Supplier<T> supplier)\n\t{\n\t\tArrayList<Object> expected = supplier.get().collect(new ArrayList<>());\n\t\tsupplier.get().collect(expected);\n\t\tFunctionalIterable<E> actual = supplier.get().concat(supplier.get());\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testFlatMap(Supplier<T> supplier)\n\t{\n\t\tFunctionalIterable<String> expected = supplier.get().map(String::valueOf);\n\t\tFunctionalIterable<String> actual = supplier.get().flatMap(e -> new SingletonIterable.Of<>(String.valueOf(e)));\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testFlatMapToDouble(Supplier<T> supplier)\n\t{\n\t\tRange range = new Range((int) supplier.get().count());\n\t\tPrimitiveIterable.OfDouble expected = unboxDouble(range.map((int i) -> (double) i));\n\t\tRange.RangeIterator index = range.iterator();\n\t\tPrimitiveIterable.OfDouble actual = supplier.get().flatMapToDouble(e -> new SingletonIterable.OfDouble(index.next()));\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testFlatMapToInt(Supplier<T> supplier)\n\t{\n\t\tRange expected = new Range((int) supplier.get().count());\n\t\tRange.RangeIterator index = expected.iterator();\n\t\tPrimitiveIterable.OfInt actual = supplier.get().flatMapToInt(e -> new SingletonIterable.OfInt(index.next()));\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testFlatMapToLong(Supplier<T> supplier)\n\t{\n\t\tRange range = new Range((int) supplier.get().count());\n\t\tPrimitiveIterable.OfLong expected = unboxLong(range.map((int i) -> (long) i));\n\t\tRange.RangeIterator index = range.iterator();\n\t\tPrimitiveIterable.OfLong actual = supplier.get().flatMapToLong(e -> new SingletonIterable.OfLong(index.next()));\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getSingletonReducibles\")\n\t@Override\n\tdefault void testFlatMapToNull(Supplier<T> supplier)\n\t{\n\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMap(e -> null).consume());\n\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToDouble(e -> null).consume());\n\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToInt(e -> null).consume());\n\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToLong(e -> null).consume());\n\t}\n\n\t@Test\n\t@Override\n\tdefault void testFlatMap_Null()\n\t{\n\t\tFunctionalIterable<E> iterator = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> iterator.flatMap(null));\n\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToDouble(null));\n\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToInt(null));\n\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToLong(null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@DisplayName(\"forEach yields same sequence as the underlying iterator.\")\n\t@Override\n\tdefault void testForEach(Supplier<T> supplier)\n\t{\n\t\tT expected = supplier.get();\n\t\tList<Object> actual = new ArrayList<>();\n\t\tsupplier.get().forEach(actual::add);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\n\n\tinterface Of<E, T extends FunctionalIterable<E>> extends FunctionalIterableTest<E, T>, ReducibleTest.Of<E, T>\n\t{\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/FunctionalIteratorStaticTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.stream.Stream;\n\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static org.junit.jupiter.api.Assertions.*;\n\nclass FunctionalIteratorStaticTest\n{\n\tstatic Stream<Iterable<Object>> getIterables()\n\t{\n\t\treturn Stream.of(Collections.singleton(null),\n\t\t\t\tCollections.emptyList(),\n\t\t\t\tCollections.singleton(\"one\"),\n\t\t\t\tArrays.asList(\"one\", \"two\", \"three\"));\n\t}\n\n\tstatic Stream<Iterable<Double>> getIterablesDouble()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t\t\tCollections.singleton(1.0),\n\t\t\t\tArrays.asList(1.0, 2.0, 3.0));\n\t}\n\n\tstatic Stream<Iterable<Integer>> getIterablesInt()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t\t\tCollections.singleton(1),\n\t\t\t\tArrays.asList(1, 2, 3));\n\t}\n\n\tstatic Stream<Iterable<Long>> getIterablesLong()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t\t\tCollections.singleton(1L),\n\t\t\t\tArrays.asList(1L, 2L, 3L));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterables\")\n\tvoid testOf(Iterable<Object> iterable)\n\t{\n\t\tFunctionalIterable<Object> expected = Reducible.extend(iterable);\n\t\tObject[] arguments = new Object[Math.toIntExact(expected.count())];\n\t\texpected.collect(arguments);\n\t\tFunctionalIterator<Object> actual = FunctionalIterator.of(arguments);\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@Test\n\tvoid testOfTypes()\n\t{\n\t\tassertTrue(FunctionalIterator.of() instanceof EmptyIterator.Of);\n\t\tassertTrue(FunctionalIterator.of(\"first\") instanceof SingletonIterator.Of);\n\t}\n\n\t@Test\n\tvoid testOf_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> FunctionalIterator.of((Object[]) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\tvoid testOfDouble(Iterable<Double> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfDouble expected = Reducible.unboxDouble(iterable);\n\t\tdouble[] arguments = new double[Math.toIntExact(expected.count())];\n\t\texpected.collect(arguments);\n\t\tFunctionalPrimitiveIterator.OfDouble actual = FunctionalIterator.ofDouble(arguments);\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@Test\n\tstatic void testOfDoubleTypes()\n\t{\n\t\tassertTrue(FunctionalIterator.ofDouble() instanceof EmptyIterator.OfDouble);\n\t\tassertTrue(FunctionalIterator.ofDouble(1.0) instanceof SingletonIterator.Of);\n\t}\n\n\t@Test\n\tvoid testOfDouble_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> FunctionalIterator.ofDouble((double[]) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\tvoid testOfInt(Iterable<Integer> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfInt expected = Reducible.unboxInt(iterable);\n\t\tint[] arguments = new int[Math.toIntExact(expected.count())];\n\t\texpected.collect(arguments);\n\t\tFunctionalPrimitiveIterator.OfInt actual = FunctionalIterator.ofInt(arguments);\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@Test\n\tvoid testOfIntTypes()\n\t{\n\t\tassertTrue(FunctionalIterator.ofInt() instanceof EmptyIterator.OfInt);\n\t\tassertTrue(FunctionalIterator.ofInt(1) instanceof SingletonIterator.OfInt);\n\t}\n\n\t@Test\n\tvoid testOfInt_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> FunctionalIterator.ofInt((int[]) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\tvoid testOfLong(Iterable<Long> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfLong expected = Reducible.unboxLong(iterable);\n\t\tlong[] arguments = new long[Math.toIntExact(expected.count())];\n\t\texpected.collect(arguments);\n\t\tFunctionalPrimitiveIterator.OfLong actual = FunctionalIterator.ofLong(arguments);\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@Test\n\tvoid testOfLongTypes()\n\t{\n\t\tassertTrue(FunctionalIterator.ofLong() instanceof EmptyIterator.OfLong);\n\t\tassertTrue(FunctionalIterator.ofLong(1L) instanceof SingletonIterator.OfLong);\n\t}\n\n\t@Test\n\tvoid testOfLong_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> FunctionalIterator.ofLong((long[]) null));\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/FunctionalIteratorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.DisplayName;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.function.Supplier;\n\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.*;\n\npublic interface FunctionalIteratorTest<E, T extends FunctionalIterator<E>> extends ReducibleTest<E, T>\n{\n\t/**\n\t * Collect elements from an iterator without using method from Reducible.\n\t *\n\t * @param supplier the supplier yielding the iterator\n\t * @return a {@link List} of the iterator elements\n\t */\n\tdefault List<E> collectElements(Supplier<T> supplier)\n\t{\n\t\tArrayList<E> elements = new ArrayList<>();\n\t\tfor (Iterator<E> iterator = supplier.get(); iterator.hasNext();) {\n\t\t\telements.add(iterator.next());\n\t\t}\n\t\treturn elements;\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@DisplayName(\"release() empties the iterator.\")\n\tdefault void testRelease(Supplier<T> supplier)\n\t{\n\t\tFunctionalIterator<?> iterator = supplier.get();\n\t\titerator.release();\n\t\tassertFalse(iterator.hasNext(), \"Expected no next element after release()\");\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testUnwrap(Supplier<T> supplier)\n\t{\n\t\tFunctionalIterator<?> iterator = supplier.get();\n\t\tassertIteratorEquals(supplier.get(), iterator.unwrap());\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testRequireNext(Supplier<T> supplier)\n\t{\n\t\tFunctionalIterator<E> iterator = supplier.get().consume();\n\t\tassertThrows(NoSuchElementException.class, iterator::requireNext);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testConsume(Supplier<T> supplier)\n\t{\n\t\tReducibleTest.super.testConsume(supplier);\n\t\t// Just test that the iterator is empty after calling #consume.\n\t\t// There is no way to test whether consume does anything beyond this.\n\t\tFunctionalIterator<E> iterator = supplier.get().consume();\n\t\tassertTrue(iterator.isEmpty(), \"Expected empty iterator after consume()\");\n\t\tassertFalse(iterator.hasNext(), \"Expected no next element after consume()\");\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getReducibles\"})\n\t@Override\n\tdefault void testConcat(Supplier<T> supplier)\n\t{\n\t\tArrayList<Object> expected = supplier.get().collect(new ArrayList<>());\n\t\tsupplier.get().collect(expected);\n\t\tFunctionalIterator<E> actual = supplier.get().concat(supplier.get());\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testFlatMap(Supplier<T> supplier)\n\t{\n\t\tFunctionalIterator<String> expected = supplier.get().map(String::valueOf);\n\t\tFunctionalIterator<String> actual = supplier.get().flatMap(e -> new SingletonIterator.Of<>(String.valueOf(e)));\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testFlatMapToDouble(Supplier<T> supplier)\n\t{\n\t\tRange range = new Range((int) supplier.get().count());\n\t\tPrimitiveIterator.OfDouble expected = unboxDouble(range.iterator().map((int i) -> (double) i));\n\t\tRange.RangeIterator index = range.iterator();\n\t\tPrimitiveIterator.OfDouble actual = supplier.get().flatMapToDouble(e -> new SingletonIterator.OfDouble(index.next()));\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testFlatMapToInt(Supplier<T> supplier)\n\t{\n\t\tRange range = new Range((int) supplier.get().count());\n\t\tPrimitiveIterator.OfInt expected = range.iterator();\n\t\tRange.RangeIterator index = range.iterator();\n\t\tPrimitiveIterator.OfInt actual = supplier.get().flatMapToInt(e -> new SingletonIterator.OfInt(index.next()));\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@Override\n\tdefault void testFlatMapToLong(Supplier<T> supplier)\n\t{\n\t\tRange range = new Range((int) supplier.get().count());\n\t\tPrimitiveIterator.OfLong expected = unboxLong(range.iterator().map((int i) -> (long) i));\n\t\tRange.RangeIterator index = range.iterator();\n\t\tPrimitiveIterator.OfLong actual = supplier.get().flatMapToLong(e -> new SingletonIterator.OfLong(index.next()));\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getSingletonReducibles\")\n\t@Override\n\tdefault void testFlatMapToNull(Supplier<T> supplier)\n\t{\n\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMap(e -> null).consume());\n\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToDouble(e -> null).consume());\n\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToInt(e -> null).consume());\n\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToLong(e -> null).consume());\n\t}\n\n\t@Test\n\t@Override\n\tdefault void testFlatMap_Null()\n\t{\n\t\tFunctionalIterator<E> iterator = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> iterator.flatMap(null));\n\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToDouble(null));\n\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToInt(null));\n\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToLong(null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@DisplayName(\"forEach yields same sequence as the underlying iterator.\")\n\t@Override\n\tdefault void testForEach(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = collectElements(supplier);\n\t\tList<Object> actual = new ArrayList<>();\n\t\tsupplier.get().forEach(actual::add);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\t@DisplayName(\"forEachRemaining() yields same sequence as the underlying iterator.\")\n\tdefault void testForEachRemaining(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = collectElements(supplier);\n\t\tList<Object> actual = new ArrayList<>();\n\t\tsupplier.get().forEachRemaining(actual::add);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tdefault void testForEachRemaining_Null()\n\t{\n\t\tFunctionalIterator<E> iterator = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> iterator.forEachRemaining(null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testIsEmpty(Supplier<T> supplier)\n\t{\n\t\tT iterator = supplier.get();\n\t\tassertTrue(iterator.isEmpty() ^ iterator.hasNext());\n\t}\n\n\n\n\tinterface Of<E, T extends FunctionalIterator<E>> extends FunctionalIteratorTest<E, T>, ReducibleTest.Of<E, T>\n\t{\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/FunctionalPrimitiveIterableTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.DisplayName;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.function.*;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.*;\n\npublic interface FunctionalPrimitiveIterableTest\n{\n\tinterface OfDouble<T extends FunctionalPrimitiveIterable.OfDouble> extends FunctionalIterableTest<Double,T>, PrimitiveReducibleTest.OfDouble<T>\n\t{\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapDoubleToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tFunctionalIterable<String> expected = supplier.get().map((DoubleFunction<String>) String::valueOf);\n\t\t\tIterable<String> actual = supplier.get().flatMap((double d) -> List.of(String.valueOf(d)));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapDoubleToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfDouble expected = range.mapToDouble((int i) -> (double) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterable.OfDouble actual = supplier.get().flatMapToDouble((double d) -> new SingletonIterable.OfDouble(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapDoubleToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange expected = new Range((int) supplier.get().count());\n\t\t\tRange.RangeIterator index = expected.iterator();\n\t\t\tPrimitiveIterable.OfInt actual = supplier.get().flatMapToInt((double d) -> new SingletonIterable.OfInt(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapDoubleToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfLong expected = range.mapToLong((int i) -> (long) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterable.OfLong actual = supplier.get().flatMapToLong((double d) -> new SingletonIterable.OfLong(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testFlatMapDoubleToNull(Supplier<T> supplier)\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMap((double d) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToDouble((double d) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToInt((double d) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToLong((double d) -> null).consume());\n\t\t}\n\n\t\t@Test\n\t\tdefault void testFlatMapOfDouble_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMap((DoubleFunction<? extends Iterable<?>>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToDouble((DoubleFunction<PrimitiveIterable.OfDouble>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToInt((DoubleFunction<PrimitiveIterable.OfInt>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToLong((DoubleFunction<PrimitiveIterable.OfLong>) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEach() yields same sequence as the underlying iterator.\")\n\t\t@Override\n\t\tdefault void testForEachDoubleConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tT expected = supplier.get();\n\t\t\tList<Double> actual = new ArrayList<>();\n\t\t\tsupplier.get().forEach((DoubleConsumer) actual::add);\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testConcatTypes()\n\t\t{\n\t\t\t// primitive with boxed signature\n\t\t\tFunctionalIterable<Double> primitive = getAnyReducible();\n\t\t\tassertTrue(getAnyReducible().concat(primitive) instanceof FunctionalPrimitiveIterable.OfDouble);\n\t\t\t// boxed\n\t\t\tFunctionalIterable<Double> boxed = getAnyReducible().map((DoubleFunction<Double>) Double::valueOf);\n\t\t\tassertFalse(getAnyReducible().concat(boxed) instanceof FunctionalPrimitiveIterable.OfDouble);\n\t\t}\n\t}\n\n\n\n\tinterface OfInt<T extends FunctionalPrimitiveIterable.OfInt> extends FunctionalIterableTest<Integer,T>, PrimitiveReducibleTest.OfInt<T>\n\t{\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapIntToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tFunctionalIterable<String> expected = supplier.get().map((IntFunction<String>) String::valueOf);\n\t\t\tFunctionalIterable<String> actual = supplier.get().flatMap((int i) -> List.of(String.valueOf(i)));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapIntToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfDouble expected = range.mapToDouble((int i) -> (double) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterable.OfDouble actual = supplier.get().flatMapToDouble((int i) -> new SingletonIterable.OfDouble(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapIntToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange expected = new Range((int) supplier.get().count());\n\t\t\tRange.RangeIterator index = expected.iterator();\n\t\t\tPrimitiveIterable.OfInt actual = supplier.get().flatMapToInt((int i) -> new SingletonIterable.OfInt(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapIntToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfLong expected = range.mapToLong((int i) -> (long) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterable.OfLong actual = supplier.get().flatMapToLong((int i) -> new SingletonIterable.OfLong(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testFlatMapIntToNull(Supplier<T> supplier)\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMap((int i) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToDouble((int i) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToInt((int i) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToLong((int i) -> null).consume());\n\t\t}\n\n\t\t@Test\n\t\tdefault void testFlatMapOfInt_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMap((IntFunction<? extends Iterable<?>>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToDouble((IntFunction<PrimitiveIterable.OfDouble>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToInt((IntFunction<PrimitiveIterable.OfInt>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToLong((IntFunction<PrimitiveIterable.OfLong>) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEach() yields same sequence as the underlying iterator.\")\n\t\t@Override\n\t\tdefault void testForEachIntConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tT expected = supplier.get();\n\t\t\tList<Integer> actual = new ArrayList<>();\n\t\t\tsupplier.get().forEach((IntConsumer) actual::add);\n\t\t\tassertIterableEquals(unboxInt(expected), unboxInt(actual));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testConcatTypes()\n\t\t{\n\t\t\t// primitive with boxed signature\n\t\t\tFunctionalIterable<Integer> primitive = getAnyReducible();\n\t\t\tassertTrue(getAnyReducible().concat(primitive) instanceof FunctionalPrimitiveIterable.OfInt);\n\t\t\t// boxed\n\t\t\tFunctionalIterable<Integer> boxed = getAnyReducible().map((IntFunction<Integer>) Integer::valueOf);\n\t\t\tassertFalse(getAnyReducible().concat(boxed) instanceof FunctionalPrimitiveIterable.OfInt);\n\t\t}\n\t}\n\n\n\n\tinterface OfLong<T extends FunctionalPrimitiveIterable.OfLong> extends FunctionalIterableTest<Long,T>, PrimitiveReducibleTest.OfLong<T>\n\t{\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapLongToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tFunctionalIterable<String> expected = supplier.get().map((LongFunction<String>) String::valueOf);\n\t\t\tFunctionalIterable<String> actual = supplier.get().flatMap((long l) -> List.of(String.valueOf(l)));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapLongToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfDouble expected = range.mapToDouble((int i) -> (double) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterable.OfDouble actual = supplier.get().flatMapToDouble((long l) -> new SingletonIterable.OfDouble(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapLongToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange expected = new Range((int) supplier.get().count());\n\t\t\tRange.RangeIterator index = expected.iterator();\n\t\t\tPrimitiveIterable.OfInt actual = supplier.get().flatMapToInt((long l) -> new SingletonIterable.OfInt(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapLongToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfLong expected = range.mapToLong((int i) -> (long) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterable.OfLong actual = supplier.get().flatMapToLong((long l) -> new SingletonIterable.OfLong(index.next()));\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testFlatMapLongToNull(Supplier<T> supplier)\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMap((long l) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToDouble((long l) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToInt((long l) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToLong((long l) -> null).consume());\n\t\t}\n\n\t\t@Test\n\t\tdefault void testFlatMapOfLong_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMap((LongFunction<? extends Iterable<?>>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToDouble((LongFunction<PrimitiveIterable.OfDouble>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToInt((LongFunction<PrimitiveIterable.OfInt>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToLong((LongFunction<PrimitiveIterable.OfLong>) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEach() yields same sequence as the underlying iterator.\")\n\t\t@Override\n\t\tdefault void testForEachLongConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tT expected = supplier.get();\n\t\t\tList<Long> actual = new ArrayList<>();\n\t\t\tsupplier.get().forEach((LongConsumer) actual::add);\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testConcatTypes()\n\t\t{\n\t\t\t// primitive with boxed signature\n\t\t\tFunctionalIterable<Long> primitive = getAnyReducible();\n\t\t\tassertTrue(getAnyReducible().concat(primitive) instanceof FunctionalPrimitiveIterable.OfLong);\n\t\t\t// boxed\n\t\t\tFunctionalIterable<Long> boxed = getAnyReducible().map((LongFunction<Long>) Long::valueOf);\n\t\t\tassertFalse(getAnyReducible().concat(boxed) instanceof FunctionalPrimitiveIterable.OfLong);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/FunctionalPrimitiveIteratorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.DisplayName;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.function.*;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static common.iterable.Assertions.*;\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.*;\n\npublic interface FunctionalPrimitiveIteratorTest\n{\n\tinterface OfDouble<T extends FunctionalPrimitiveIterator.OfDouble> extends FunctionalIteratorTest<Double,T>, PrimitiveReducibleTest.OfDouble<T>\n\t{\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapDoubleToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tFunctionalIterator<String> expected = supplier.get().map((DoubleFunction<String>) String::valueOf);\n\t\t\tIterator<String> actual = supplier.get().flatMap((double d) -> List.of(String.valueOf(d)).iterator());\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapDoubleToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfDouble expected = range.iterator().mapToDouble((int i) -> (double) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfDouble actual = supplier.get().flatMapToDouble((double d) -> new SingletonIterator.OfDouble(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapDoubleToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfInt expected = range.iterator();\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfInt actual = supplier.get().flatMapToInt((double d) -> new SingletonIterator.OfInt(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapDoubleToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfLong expected = range.iterator().mapToLong((int i) -> (long) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfLong actual = supplier.get().flatMapToLong((double d) -> new SingletonIterator.OfLong(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testFlatMapDoubleToNull(Supplier<T> supplier)\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMap((double d) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToDouble((double d) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToInt((double d) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToLong((double d) -> null).consume());\n\t\t}\n\n\t\t@Test\n\t\t@Override\n\t\tdefault void testFlatMapOfDouble_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMap((DoubleFunction<? extends Iterator<?>>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToDouble((DoubleFunction<PrimitiveIterator.OfDouble>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToInt((DoubleFunction<PrimitiveIterator.OfInt>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToLong((DoubleFunction<PrimitiveIterator.OfLong>) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEach() yields same sequence as forEachRemaining().\")\n\t\t@Override\n\t\tdefault void testForEachDoubleConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEachRemaining((DoubleConsumer) expected::add);\n\t\t\tT iterator = supplier.get();\n\t\t\tList<Double> actual = new ArrayList<>();\n\t\t\titerator.forEach((DoubleConsumer) actual::add);\n\t\t\tassertTrue(iterator.isEmpty());\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEachRemaining() yields same sequence as the underlying iterator.\")\n\t\tdefault void testForEachRemainingDoubleConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = collectElements(supplier);\n\t\t\tT iterator = supplier.get();\n\t\t\tList<Double> actual = new ArrayList<>();\n\t\t\titerator.forEachRemaining((DoubleConsumer) actual::add);\n\t\t\tassertTrue(iterator.isEmpty());\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testForEachRemainingDoubleConsumer_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.forEachRemaining((DoubleConsumer) null));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testConcatTypes()\n\t\t{\n\t\t\t// primitive with boxed signature\n\t\t\tFunctionalIterator<Double> primitive = getAnyReducible();\n\t\t\tassertTrue(getAnyReducible().concat(primitive) instanceof FunctionalPrimitiveIterator.OfDouble);\n\t\t\t// boxed\n\t\t\tFunctionalIterator<Double> boxed = getAnyReducible().map((DoubleFunction<Double>) Double::valueOf);\n\t\t\tassertFalse(getAnyReducible().concat(boxed) instanceof FunctionalPrimitiveIterator.OfDouble);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMin_Consumed(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalDouble expected = OptionalDouble.empty();\n\t\t\tOptionalDouble actual = supplier.get().consume().min();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMax_Consumed(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalDouble expected = OptionalDouble.empty();\n\t\t\tOptionalDouble actual = supplier.get().consume().max();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\t}\n\n\n\n\tinterface OfInt<T extends FunctionalPrimitiveIterator.OfInt> extends FunctionalIteratorTest<Integer,T>, PrimitiveReducibleTest.OfInt<T>\n\t{\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapIntToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tFunctionalIterator<String> expected = supplier.get().map((IntFunction<String>) String::valueOf);\n\t\t\tIterator<String> actual = supplier.get().flatMap((int i) -> List.of(String.valueOf(i)).iterator());\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapIntToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfDouble expected = range.iterator().mapToDouble((int i) -> (double) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfDouble actual = supplier.get().flatMapToDouble((int i) -> new SingletonIterator.OfDouble(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapIntToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfInt expected = range.iterator();\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfInt actual = supplier.get().flatMapToInt((int i) -> new SingletonIterator.OfInt(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapIntToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfLong expected = range.iterator().mapToLong((int i) -> (long) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfLong actual = supplier.get().flatMapToLong((int i) -> new SingletonIterator.OfLong(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testFlatMapIntToNull(Supplier<T> supplier)\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMap((int i) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToDouble((int i) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToInt((int i) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToLong((int i) -> null).consume());\n\t\t}\n\n\t\t@Test\n\t\tdefault void testFlatMapOfInt_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMap((IntFunction<? extends Iterator<?>>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToDouble((IntFunction<PrimitiveIterator.OfDouble>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToInt((IntFunction<PrimitiveIterator.OfInt>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToLong((IntFunction<PrimitiveIterator.OfLong>) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEach() yields same sequence as the underlying iterator.\")\n\t\t@Override\n\t\tdefault void testForEachIntConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Integer> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEachRemaining((IntConsumer) expected::add);\n\t\t\tT iterator = supplier.get();\n\t\t\tList<Integer> actual = new ArrayList<>();\n\t\t\titerator.forEach((IntConsumer) actual::add);\n\t\t\tassertTrue(iterator.isEmpty());\n\t\t\tassertIterableEquals(unboxInt(expected), unboxInt(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEachRemaining() yields same sequence as the underlying iterator.\")\n\t\tdefault void testForEachRemainingIntConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Integer> expected = collectElements(supplier);\n\t\t\tList<Integer> actual = new ArrayList<>();\n\t\t\tsupplier.get().forEachRemaining((IntConsumer) actual::add);\n\t\t\tassertIterableEquals(unboxInt(expected), unboxInt(actual));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testForEachRemainingIntConsumer_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.forEachRemaining((IntConsumer) null));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testConcatTypes()\n\t\t{\n\t\t\t// primitive with boxed signature\n\t\t\tFunctionalIterator<Integer> primitive = getAnyReducible();\n\t\t\tassertTrue(getAnyReducible().concat(primitive) instanceof FunctionalPrimitiveIterator.OfInt);\n\t\t\t// boxed\n\t\t\tFunctionalIterator<Integer> boxed = getAnyReducible().map((IntFunction<Integer>) Integer::valueOf);\n\t\t\tassertFalse(getAnyReducible().concat(boxed) instanceof FunctionalPrimitiveIterator.OfInt);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMin_Consumed(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalInt expected = OptionalInt.empty();\n\t\t\tOptionalInt actual = supplier.get().consume().min();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMax_Consumed(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalInt expected = OptionalInt.empty();\n\t\t\tOptionalInt actual = supplier.get().consume().max();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\t}\n\n\n\n\tinterface OfLong<T extends FunctionalPrimitiveIterator.OfLong> extends FunctionalIteratorTest<Long,T>, PrimitiveReducibleTest.OfLong<T>\n\t{\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapLongToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tFunctionalIterator<String> expected = supplier.get().map((LongFunction<String>) String::valueOf);\n\t\t\tIterator<String> actual = supplier.get().flatMap((long l) -> List.of(String.valueOf(l)).iterator());\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapLongToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfDouble expected = range.iterator().mapToDouble((int i) -> (double) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfDouble actual = supplier.get().flatMapToDouble((long l) -> new SingletonIterator.OfDouble(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapLongToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfInt expected = range.iterator();\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfInt actual = supplier.get().flatMapToInt((long l) -> new SingletonIterator.OfInt(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFlatMapLongToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterator.OfLong expected = range.iterator().mapToLong((int i) -> (long) i);\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveIterator.OfLong actual = supplier.get().flatMapToLong((long l) -> new SingletonIterator.OfLong(index.next()));\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testFlatMapLongToNull(Supplier<T> supplier)\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMap((long l) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToDouble((long l) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToInt((long l) -> null).consume());\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().flatMapToLong((long l) -> null).consume());\n\t\t}\n\n\t\t@Test\n\t\tdefault void testFlatMapOfLong_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMap((LongFunction<? extends Iterator<?>>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToDouble((LongFunction<PrimitiveIterator.OfDouble>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToInt((LongFunction<PrimitiveIterator.OfInt>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.flatMapToLong((LongFunction<PrimitiveIterator.OfLong>) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEach() yields same sequence as the underlying iterator.\")\n\t\t@Override\n\t\tdefault void testForEachLongConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Long> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEachRemaining((LongConsumer) expected::add);\n\t\t\tT iterator = supplier.get();\n\t\t\tList<Long> actual = new ArrayList<>();\n\t\t\titerator.forEach((LongConsumer) actual::add);\n\t\t\tassertTrue(iterator.isEmpty());\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@DisplayName(\"forEachRemaining() yields same sequence as the underlying iterator.\")\n\t\tdefault void testForEachRemainingLongConsumer(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Long> expected = collectElements(supplier);\n\t\t\tList<Long> actual = new ArrayList<>();\n\t\t\tsupplier.get().forEachRemaining((LongConsumer) actual::add);\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testForEachRemainingLongConsumer_Null()\n\t\t{\n\t\t\tT iterator = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> iterator.forEachRemaining((LongConsumer) null));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testConcatTypes()\n\t\t{\n\t\t\t// primitive with boxed signature\n\t\t\tFunctionalIterator<Long> primitive = getAnyReducible();\n\t\t\tassertTrue(getAnyReducible().concat(primitive) instanceof FunctionalPrimitiveIterator.OfLong);\n\t\t\t// boxed\n\t\t\tFunctionalIterator<Long> boxed = getAnyReducible().map((LongFunction<Long>) Long::valueOf);\n\t\t\tassertFalse(getAnyReducible().concat(boxed) instanceof FunctionalPrimitiveIterator.OfLong);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMin_Consumed(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalLong expected = OptionalLong.empty();\n\t\t\tOptionalLong actual = supplier.get().consume().min();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMax_Consumed(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalLong expected = OptionalLong.empty();\n\t\t\tOptionalLong actual = supplier.get().consume().max();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/IterableAdaptorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.DisplayName;\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\nclass IterableAdaptorTest\n{\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements FunctionalIterableTest.Of<Object,IterableAdaptor.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic IterableAdaptor.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\treturn new IterableAdaptor.Of<>(Arrays.asList(objects));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\t@DisplayName(\"Adaptor yields same sequence as the underlying iterator.\")\n\t\tpublic void testOf(Object[] objects)\n\t\t{\n\t\t\tList<Object> expected = Arrays.asList(objects);\n\t\t\tIterableAdaptor.Of<Object> actual = new IterableAdaptor.Of<>(expected);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\t@DisplayName(\"Adapter on null throws NullPointerException.\")\n\t\tpublic void testOf_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableAdaptor.Of<>(null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements FunctionalPrimitiveIterableTest.OfDouble<IterableAdaptor.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic IterableAdaptor.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfDouble iterable = asNonFunctionalIterable(numbers);\n\t\t\treturn new IterableAdaptor.OfDouble(iterable);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\t@DisplayName(\"Adaptor yields same sequence as the underlying iterator.\")\n\t\tpublic void testOfDouble(double[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfDouble expected = asNonFunctionalIterable(numbers);\n\t\t\tIterableAdaptor.OfDouble actual = new IterableAdaptor.OfDouble(expected);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\t@DisplayName(\"Adapter on null throws NullPointerException.\")\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableAdaptor.OfDouble(null));\n\t\t}\n\n\t\tprivate PrimitiveIterable.OfDouble asNonFunctionalIterable(double[] numbers)\n\t\t{\n\t\t\tList<Double> boxed = FunctionalIterator.ofDouble(numbers).collect(new ArrayList<>());\n\t\t\treturn PrimitiveIterable.unboxDouble(boxed);\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements FunctionalPrimitiveIterableTest.OfInt<IterableAdaptor.OfInt>\n\t{\n\t\t@Override\n\t\tpublic IterableAdaptor.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfInt iterable = asNonFunctionalIterable(numbers);\n\t\t\treturn new IterableAdaptor.OfInt(iterable);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\t@DisplayName(\"Adaptor yields same sequence as the underlying iterator.\")\n\t\tpublic void testOfInt(int[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfInt expected = asNonFunctionalIterable(numbers);\n\t\t\tIterableAdaptor.OfInt actual = new IterableAdaptor.OfInt(expected);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\t@DisplayName(\"Adapter on null throws NullPointerException.\")\n\t\tpublic void testOfInt_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableAdaptor.OfInt(null));\n\t\t}\n\n\t\tprivate PrimitiveIterable.OfInt asNonFunctionalIterable(int[] numbers)\n\t\t{\n\t\t\tList<Integer> boxed = FunctionalIterator.ofInt(numbers).collect(new ArrayList<>());\n\t\t\treturn PrimitiveIterable.unboxInt(boxed);\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements FunctionalPrimitiveIterableTest.OfLong<IterableAdaptor.OfLong>\n\t{\n\t\t@Override\n\t\tpublic IterableAdaptor.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfLong iterable = asNonFunctionalIterable(numbers);\n\t\t\treturn new IterableAdaptor.OfLong(iterable);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\t@DisplayName(\"Adaptor yields same sequence as the underlying iterator.\")\n\t\tpublic void testOfLong(long[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfLong expected = asNonFunctionalIterable(numbers);\n\t\t\tIterableAdaptor.OfLong actual = new IterableAdaptor.OfLong(expected);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\t@DisplayName(\"Adapter on null throws NullPointerException.\")\n\t\tpublic void testOfLong_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableAdaptor.OfLong(null));\n\t\t}\n\n\t\tprivate PrimitiveIterable.OfLong asNonFunctionalIterable(long[] numbers)\n\t\t{\n\t\t\tList<Long> boxed = FunctionalIterator.ofLong(numbers).collect(new ArrayList<>());\n\t\t\treturn PrimitiveIterable.unboxLong(boxed);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/IterableArrayTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.Optional;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.assertArrayEquals;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\ninterface IterableArrayTest\n{\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements IterableArrayTest, FunctionalIterableTest.Of<Object,IterableArray.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic IterableArray.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\treturn new IterableArray.Of<>(objects);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\tpublic void testOfArray(Object[] array)\n\t\t{\n\t\t\tIterableArray.Of<Object> iterator = new IterableArray.Of<>(array);\n\t\t\tObject[] actual = iterator.collect(new Object[array.length]);\n\t\t\tassertArrayEquals(array, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\tpublic void testOfArrayIntInt_All(Object[] array)\n\t\t{\n\t\t\tIterableArray.Of<Object> expected = new IterableArray.Of<>(array);\n\t\t\tIterableArray.Of<Object> actual = new IterableArray.Of<>(array, 0, array.length);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getMultitonArraysAsArguments\"})\n\t\tpublic void testOfArrayIntInt_Range(Object[] array)\n\t\t{\n\t\t\tFunctionalIterable<Object> expected = new Range(1, array.length - 1).map((int i) -> array[i]);\n\t\t\tIterableArray.Of<Object> actual = new IterableArray.Of<>(array, 1, array.length - 1);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOf_Errors()\n\t\t{\n\t\t\tOptional<Object[]> any = getMultitonArraysOfObject().findAny();\n\t\t\tassert any.isPresent();\n\t\t\tObject[] array = any.get();\n\t\t\tint length = array.length;\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableArray.Of<>((Object[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableArray.Of<>(null, 0, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.Of<>(array, -1, -1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.Of<>(array, -1, length));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.Of<>(array, 1, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.Of<>(array, 0, length+1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.Of<>(array, length+1, length+1));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements IterableArrayTest, FunctionalPrimitiveIterableTest.OfDouble<IterableArray.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic IterableArray.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\treturn new IterableArray.OfDouble(numbers);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfDouble\", \"getSingletonArraysOfDouble\", \"getMultitonArraysOfDouble\"})\n\t\tpublic void testOfDouble(double[] array)\n\t\t{\n\t\t\tIterableArray.OfDouble iterator = new IterableArray.OfDouble(array);\n\t\t\tdouble[] actual = iterator.collect(new double[array.length]);\n\t\t\tassertArrayEquals(array, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfDouble\", \"getSingletonArraysOfDouble\", \"getMultitonArraysOfDouble\"})\n\t\tpublic void testOfDoubleArrayIntInt_All(double[] array)\n\t\t{\n\t\t\tIterableArray.OfDouble expected = new IterableArray.OfDouble(array);\n\t\t\tIterableArray.OfDouble actual = new IterableArray.OfDouble(array, 0, array.length);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getMultitonArraysOfDouble\"})\n\t\tpublic void testOfDoubleArrayIntInt_Range(double[] array)\n\t\t{\n\t\t\tFunctionalPrimitiveIterable.OfDouble expected = new Range(1, array.length - 1).mapToDouble((int i) -> array[i]);\n\t\t\tIterableArray.OfDouble actual = new IterableArray.OfDouble(array, 1, array.length - 1);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfDouble_Errors()\n\t\t{\n\t\t\tOptional<double[]> any = getMultitonArraysOfDouble().findAny();\n\t\t\tassert any.isPresent();\n\t\t\tdouble[] array = any.get();\n\t\t\tint length = array.length;\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableArray.OfDouble((double[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableArray.OfDouble(null, 0, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfDouble(array, -1, -1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfDouble(array, -1, length));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfDouble(array, 1, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfDouble(array, 0, length+1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfDouble(array, length+1, length+1));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements IterableArrayTest, FunctionalPrimitiveIterableTest.OfInt<IterableArray.OfInt>\n\t{\n\t\t@Override\n\t\tpublic IterableArray.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\treturn new IterableArray.OfInt(numbers);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfInt\", \"getSingletonArraysOfInt\", \"getMultitonArraysOfInt\"})\n\t\tpublic void testOfInt(int[] array)\n\t\t{\n\t\t\tIterableArray.OfInt iterator = new IterableArray.OfInt(array);\n\t\t\tint[] actual = iterator.collect(new int[array.length]);\n\t\t\tassertArrayEquals(array, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfInt\", \"getSingletonArraysOfInt\", \"getMultitonArraysOfInt\"})\n\t\tpublic void testOfIntArrayIntInt_All(int[] array)\n\t\t{\n\t\t\tIterableArray.OfInt expected = new IterableArray.OfInt(array);\n\t\t\tIterableArray.OfInt actual = new IterableArray.OfInt(array, 0, array.length);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getMultitonArraysOfInt\"})\n\t\tpublic void testOfIntArrayIntInt_Range(int[] array)\n\t\t{\n\t\t\tFunctionalPrimitiveIterable.OfInt expected = new Range(1, array.length - 1).mapToInt((int i) -> array[i]);\n\t\t\tIterableArray.OfInt actual = new IterableArray.OfInt(array, 1, array.length - 1);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfInt_Errors()\n\t\t{\n\t\t\tOptional<int[]> any = getMultitonArraysOfInt().findAny();\n\t\t\tassert any.isPresent();\n\t\t\tint[] array = any.get();\n\t\t\tint length = array.length;\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableArray.OfInt((int[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableArray.OfInt(null, 0, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfInt(array, -1, -1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfInt(array, -1, length));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfInt(array, 1, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfInt(array, 0, length+1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfInt(array, length+1, length+1));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements IterableArrayTest, FunctionalPrimitiveIterableTest.OfLong<IterableArray.OfLong>\n\t{\n\t\t@Override\n\t\tpublic IterableArray.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\treturn new IterableArray.OfLong(numbers);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfLong\", \"getSingletonArraysOfLong\", \"getMultitonArraysOfLong\"})\n\t\tpublic void testOfLong(long[] array)\n\t\t{\n\t\t\tIterableArray.OfLong iterator = new IterableArray.OfLong(array);\n\t\t\tlong[] actual = iterator.collect(new long[array.length]);\n\t\t\tassertArrayEquals(array, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getEmptyArraysOfLong\", \"getSingletonArraysOfLong\", \"getMultitonArraysOfLong\"})\n\t\tpublic void testOfLongArrayIntInt_All(long[] array)\n\t\t{\n\t\t\tIterableArray.OfLong expected = new IterableArray.OfLong(array);\n\t\t\tIterableArray.OfLong actual = new IterableArray.OfLong(array, 0, array.length);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getMultitonArraysOfLong\"})\n\t\tpublic void testOfLongArrayIntInt_Range(long[] array)\n\t\t{\n\t\t\tFunctionalPrimitiveIterable.OfLong expected = new Range(1, array.length - 1).mapToLong((int i) -> array[i]);\n\t\t\tIterableArray.OfLong actual = new IterableArray.OfLong(array, 1, array.length - 1);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOfLong_Errors()\n\t\t{\n\t\t\tOptional<long[]> any = getMultitonArraysOfLong().findAny();\n\t\t\tassert any.isPresent();\n\t\t\tlong[] array = any.get();\n\t\t\tint length = array.length;\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableArray.OfLong((long[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> new IterableArray.OfLong(null, 0, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfLong(array, -1, -1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfLong(array, -1, length));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfLong(array, 1, 0));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfLong(array, 0, length+1));\n\t\t\tassertThrows(IndexOutOfBoundsException.class, () -> new IterableArray.OfLong(array, length+1, length+1));\n\t\t}\n\t}\n}"
  },
  {
    "path": "prism/unit-tests/common/iterable/IteratorAdaptorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.DisplayName;\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.api.TestInstance.Lifecycle;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\n\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static org.junit.jupiter.api.Assertions.assertSame;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\nclass IteratorAdaptorTest\n{\n\t@Nested\n\t@TestInstance(Lifecycle.PER_CLASS)\n\tclass Of implements FunctionalIteratorTest.Of<Object,IteratorAdaptor.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic IteratorAdaptor.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\treturn new IteratorAdaptor.Of<>(Arrays.asList(objects).iterator());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\t@DisplayName(\"Adaptor yields same sequence as the underlying iterator.\")\n\t\tpublic void testOf(Object[] objects)\n\t\t{\n\t\t\tList<Object> iterable = Arrays.asList(objects);\n\t\t\tIterator<Object> expected = iterable.iterator();\n\t\t\tIteratorAdaptor.Of<Object> actual = new IteratorAdaptor.Of<>(iterable.iterator());\n\t\t\tassertIteratorEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\t@DisplayName(\"Adapter on null throws NullPointerException.\")\n\t\tpublic void testOf_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new IteratorAdaptor.Of<>(null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\t@DisplayName(\"unwrap() answers the underlying iterator.\")\n\t\tpublic void testUnwrap(Object[] objects)\n\t\t{\n\t\t\tIterator<Object> expected = Arrays.asList(objects).iterator();\n\t\t\tIterator<Object> actual = new IteratorAdaptor.Of<>(expected).unwrap();\n\t\t\tassertSame(expected, actual);\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(Lifecycle.PER_CLASS)\n\tclass OfDouble implements FunctionalPrimitiveIteratorTest.OfDouble<IteratorAdaptor.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic IteratorAdaptor.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfDouble iterable = asNonFunctionalIterable(numbers);\n\t\t\treturn new IteratorAdaptor.OfDouble(iterable.iterator());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\t@DisplayName(\"Adaptor yields same sequence as the underlying iterator.\")\n\t\tpublic void testOfDouble(double[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfDouble expected = asNonFunctionalIterable(numbers);\n\t\t\tIteratorAdaptor.OfDouble actual = new IteratorAdaptor.OfDouble(expected.iterator());\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\t@DisplayName(\"Adapter on null throws NullPointerException.\")\n\t\tpublic void testOfDouble_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new IteratorAdaptor.OfDouble(null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\t@DisplayName(\"unwrap() answers the underlying iterator.\")\n\t\tpublic void testUnwrap(double[] numbers)\n\t\t{\n\t\t\tPrimitiveIterator.OfDouble expected = asNonFunctionalIterable(numbers).iterator();\n\t\t\tPrimitiveIterator.OfDouble actual = new IteratorAdaptor.OfDouble(expected).unwrap();\n\t\t\tassertSame(expected, actual);\n\t\t}\n\n\t\tprivate PrimitiveIterable.OfDouble asNonFunctionalIterable(double[] numbers)\n\t\t{\n\t\t\tList<Double> boxed = FunctionalIterator.ofDouble(numbers).collect(new ArrayList<>());\n\t\t\treturn PrimitiveIterable.unboxDouble(boxed);\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(Lifecycle.PER_CLASS)\n\tclass OfInt implements FunctionalPrimitiveIteratorTest.OfInt<IteratorAdaptor.OfInt>\n\t{\n\t\t@Override\n\t\tpublic IteratorAdaptor.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfInt iterable = asNonFunctionalIterable(numbers);\n\t\t\treturn new IteratorAdaptor.OfInt(iterable.iterator());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\t@DisplayName(\"Adaptor yields same sequence as the underlying iterator.\")\n\t\tpublic void testOfInt(int[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfInt expected = asNonFunctionalIterable(numbers);\n\t\t\tIteratorAdaptor.OfInt actual = new IteratorAdaptor.OfInt(expected.iterator());\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\t@DisplayName(\"Adapter on null throws NullPointerException.\")\n\t\tpublic void testOfInt_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new IteratorAdaptor.OfInt(null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\t@DisplayName(\"unwrap() answers the underlying iterator.\")\n\t\tpublic void testUnwrap(int[] numbers)\n\t\t{\n\t\t\tPrimitiveIterator.OfInt expected = asNonFunctionalIterable(numbers).iterator();\n\t\t\tPrimitiveIterator.OfInt actual = new IteratorAdaptor.OfInt(expected).unwrap();\n\t\t\tassertSame(expected, actual);\n\t\t}\n\n\t\tprivate PrimitiveIterable.OfInt asNonFunctionalIterable(int[] numbers)\n\t\t{\n\t\t\tList<Integer> boxed = FunctionalIterator.ofInt(numbers).collect(new ArrayList<>());\n\t\t\treturn PrimitiveIterable.unboxInt(boxed);\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(Lifecycle.PER_CLASS)\n\tclass OfLong implements FunctionalPrimitiveIteratorTest.OfLong<IteratorAdaptor.OfLong>\n\t{\n\t\t@Override\n\t\tpublic IteratorAdaptor.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfLong iterable = asNonFunctionalIterable(numbers);\n\t\t\treturn new IteratorAdaptor.OfLong(iterable.iterator());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\t@DisplayName(\"Adaptor yields same sequence as the underlying iterator.\")\n\t\tpublic void testOfLong(long[] numbers)\n\t\t{\n\t\t\tPrimitiveIterable.OfLong expected = asNonFunctionalIterable(numbers);\n\t\t\tIteratorAdaptor.OfLong actual = new IteratorAdaptor.OfLong(expected.iterator());\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\t@DisplayName(\"Adapter on null throws NullPointerException.\")\n\t\tpublic void testOfLong_Null()\n\t\t{\n\t\t\tassertThrows(NullPointerException.class, () -> new IteratorAdaptor.OfLong(null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\t@DisplayName(\"unwrap() answers the underlying iterator.\")\n\t\tpublic void testUnwrap(long[] numbers)\n\t\t{\n\t\t\tPrimitiveIterator.OfLong expected = asNonFunctionalIterable(numbers).iterator();\n\t\t\tPrimitiveIterator.OfLong actual = new IteratorAdaptor.OfLong(expected).unwrap();\n\t\t\tassertSame(expected, actual);\n\t\t}\n\n\t\tprivate PrimitiveIterable.OfLong asNonFunctionalIterable(long[] numbers)\n\t\t{\n\t\t\tList<Long> boxed = FunctionalIterator.ofLong(numbers).collect(new ArrayList<>());\n\t\t\treturn PrimitiveIterable.unboxLong(boxed);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/MappingIterableTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\ninterface MappingIterableTest\n{\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass ObjToObj implements MappingIterableTest, FunctionalIterableTest.Of<Object,MappingIterable.ObjToObj<Object,Object>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.ObjToObj<Object, Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tMap<Object, Object> lookup = new LinkedHashMap<>();\n\t\t\tfor (int i=0, length=objects.length; i<length; i++) {\n\t\t\t\tlookup.put(objects[i], objects[length-1-i]);\n\t\t\t}\n\t\t\treturn new MappingIterable.ObjToObj<>(lookup.keySet(), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\tvoid testOf(Object[] objects)\n\t\t{\n\t\t\tArrayList<String> expected = new ArrayList<>();\n\t\t\tfor (Object each : objects) {\n\t\t\t\texpected.add(Objects.toString(each));\n\t\t\t}\n\t\t\tIterable<Object> iterable = new IterableArray.Of<>(objects);\n\t\t\tIterable<String> actual = new MappingIterable.ObjToObj<>(iterable, Objects::toString);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOf_Null()\n\t\t{\n\t\t\tEmptyIterable.Of<Object> iterable = EmptyIterable.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.ObjToObj<>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.ObjToObj<>(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass ObjToDouble implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfDouble<MappingIterable.ObjToDouble<Double>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.ObjToDouble<Double> getReducible(double[] numbers)\n\t\t{\n\t\t\tList<Double> boxed = FunctionalIterable.ofDouble(numbers).collect(new ArrayList<>());\n\t\t\treturn new MappingIterable.ObjToDouble<>(boxed, Double::doubleValue);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testObjToDouble(double[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add(d);\n\t\t\t}\n\t\t\tFunctionalPrimitiveIterable.OfDouble actual = new MappingIterable.ObjToDouble<>(expected, each -> each);\n\t\t\tassertIterableEquals(unboxDouble(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testObjToDouble_Null()\n\t\t{\n\t\t\tEmptyIterable.Of<Double> iterable = EmptyIterable.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.ObjToDouble<Double>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.ObjToDouble<>(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass ObjToInt implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfInt<MappingIterable.ObjToInt<Integer>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.ObjToInt<Integer> getReducible(int[] numbers)\n\t\t{\n\t\t\tList<Integer> boxed = FunctionalIterable.ofInt(numbers).collect(new ArrayList<>());\n\t\t\treturn new MappingIterable.ObjToInt<>(boxed, Integer::intValue);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testObjToInt(int[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add(i);\n\t\t\t}\n\t\t\tFunctionalPrimitiveIterable.OfInt actual = new MappingIterable.ObjToInt<>(expected, each -> each);\n\t\t\tassertIterableEquals(unboxInt(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testObjToInt_Null()\n\t\t{\n\t\t\tEmptyIterable.Of<Integer> iterable = EmptyIterable.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.ObjToInt<Integer>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.ObjToInt<>(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass ObjToLong implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfLong<MappingIterable.ObjToLong<Long>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.ObjToLong<Long> getReducible(long[] numbers)\n\t\t{\n\t\t\tList<Long> boxed = FunctionalIterable.ofLong(numbers).collect(new ArrayList<>());\n\t\t\treturn new MappingIterable.ObjToLong<>(boxed, Long::longValue);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testObjToLong(long[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add(l);\n\t\t\t}\n\t\t\tFunctionalPrimitiveIterable.OfLong actual = new MappingIterable.ObjToLong<>(expected, each -> each);\n\t\t\tassertIterableEquals(unboxLong(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testObjToLong_Null()\n\t\t{\n\t\t\tEmptyIterable.Of<Long> iterable = EmptyIterable.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.ObjToLong<Long>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.ObjToLong<>(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass DoubleToObj implements MappingIterableTest, FunctionalIterableTest.Of<Object,MappingIterable.DoubleToObj<Object>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.DoubleToObj<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tMap<Double, Object> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.of(objects).reduce(1.5, (d, e) -> {lookup.put(d, e); return d + 1;});\n\t\t\treturn new MappingIterable.DoubleToObj<>(unboxDouble(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testDoubleToObj(double[] numbers)\n\t\t{\n\t\t\tArrayList<String> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add(Objects.toString(d));\n\t\t\t}\n\t\t\tIterableArray.OfDouble iterable = new IterableArray.OfDouble(numbers);\n\t\t\tIterable<String> actual = new MappingIterable.DoubleToObj<>(iterable, Objects::toString);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testDoubleToObj_Null()\n\t\t{\n\t\t\tEmptyIterable.OfDouble iterable = EmptyIterable.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.DoubleToObj<>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.DoubleToObj<>(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass DoubleToDouble implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfDouble<MappingIterable.DoubleToDouble>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.DoubleToDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tMap<Double, Double> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofDouble(numbers).reduce(1.5, (double d, double e) -> {lookup.put(d, e); return d + 1;});\n\t\t\treturn new MappingIterable.DoubleToDouble(unboxDouble(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testDoubleToDouble(double[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add(d + 1.0);\n\t\t\t}\n\t\t\tIterableArray.OfDouble iterable = new IterableArray.OfDouble(numbers);\n\t\t\tPrimitiveIterable.OfDouble actual = new MappingIterable.DoubleToDouble(iterable, d -> d + 1.0);\n\t\t\tassertIterableEquals(unboxDouble(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testDoubleToDouble_Null()\n\t\t{\n\t\t\tEmptyIterable.OfDouble iterable = EmptyIterable.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.DoubleToDouble(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.DoubleToDouble(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass DoubleToInt implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfInt<MappingIterable.DoubleToInt>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.DoubleToInt getReducible(int[] numbers)\n\t\t{\n\t\t\tMap<Double, Integer> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofInt(numbers).reduce(1.5, (Double d, Integer e) -> {lookup.put(d, e); return d + 1;});\n\t\t\treturn new MappingIterable.DoubleToInt(unboxDouble(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testDoubleToInt(double[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add((int) d + 1);\n\t\t\t}\n\t\t\tIterableArray.OfDouble iterable = new IterableArray.OfDouble(numbers);\n\t\t\tPrimitiveIterable.OfInt actual = new MappingIterable.DoubleToInt(iterable, d -> (int) d + 1);\n\t\t\tassertIterableEquals(unboxInt(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testDoubleToInt_Null()\n\t\t{\n\t\t\tEmptyIterable.OfDouble iterable = EmptyIterable.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.DoubleToInt(null, each -> (int) each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.DoubleToInt(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass DoubleToLong implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfLong<MappingIterable.DoubleToLong>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.DoubleToLong getReducible(long[] numbers)\n\t\t{\n\t\t\tMap<Double, Long> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofLong(numbers).reduce(1.5, (double d, long e) -> {lookup.put(d, e); return d + 1;});\n\t\t\treturn new MappingIterable.DoubleToLong(unboxDouble(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testDoubleToLong(double[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add((long) d + 1);\n\t\t\t}\n\t\t\tIterableArray.OfDouble iterable = new IterableArray.OfDouble(numbers);\n\t\t\tPrimitiveIterable.OfLong actual = new MappingIterable.DoubleToLong(iterable, d -> (long) d + 1);\n\t\t\tassertIterableEquals(unboxLong(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testDoubleToLong_Null()\n\t\t{\n\t\t\tEmptyIterable.OfDouble iterable = EmptyIterable.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.DoubleToLong(null, each -> (long) each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.DoubleToLong(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass IntToObj implements MappingIterableTest, FunctionalIterableTest.Of<Object,MappingIterable.IntToObj<Object>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.IntToObj<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tMap<Integer, Object> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.of(objects).reduce(1, (int i, Object e) -> {lookup.put(i, e); return i + 1;});\n\t\t\treturn new MappingIterable.IntToObj<>(unboxInt(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testIntToObj(int[] numbers)\n\t\t{\n\t\t\tArrayList<String> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add(Objects.toString(i));\n\t\t\t}\n\t\t\tIterableArray.OfInt iterable = new IterableArray.OfInt(numbers);\n\t\t\tIterable<String> actual = new MappingIterable.IntToObj<>(iterable, Objects::toString);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testIntToObj_Null()\n\t\t{\n\t\t\tEmptyIterable.OfInt iterable = EmptyIterable.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.IntToObj<>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.IntToObj<>(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass IntToDouble implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfDouble<MappingIterable.IntToDouble>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.IntToDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tMap<Integer, Double> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofDouble(numbers).reduce(1, (int i, double e) -> {lookup.put(i, e); return i + 1;});\n\t\t\treturn new MappingIterable.IntToDouble(unboxInt(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testIntToDouble(int[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add(i + 1.0);\n\t\t\t}\n\t\t\tIterableArray.OfInt iterable = new IterableArray.OfInt(numbers);\n\t\t\tPrimitiveIterable.OfDouble actual = new MappingIterable.IntToDouble(iterable, i -> i + 1.0);\n\t\t\tassertIterableEquals(unboxDouble(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testIntToDouble_Null()\n\t\t{\n\t\t\tEmptyIterable.OfInt iterable = EmptyIterable.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.IntToDouble(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.IntToDouble(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass IntToInt implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfInt<MappingIterable.IntToInt>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.IntToInt getReducible(int[] numbers)\n\t\t{\n\t\t\tMap<Integer, Integer> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofInt(numbers).reduce(1, (int i, int e) -> {lookup.put(i, e); return i + 1;});\n\t\t\treturn new MappingIterable.IntToInt(unboxInt(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testIntToInt(int[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add(i + 1);\n\t\t\t}\n\t\t\tIterableArray.OfInt iterable = new IterableArray.OfInt(numbers);\n\t\t\tPrimitiveIterable.OfInt actual = new MappingIterable.IntToInt(iterable, i -> i + 1);\n\t\t\tassertIterableEquals(unboxInt(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testIntToInt_Null()\n\t\t{\n\t\t\tEmptyIterable.OfInt iterable = EmptyIterable.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.IntToInt(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.IntToInt(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass IntToLong implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfLong<MappingIterable.IntToLong>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.IntToLong getReducible(long[] numbers)\n\t\t{\n\t\t\tMap<Integer, Long> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofLong(numbers).reduce(1, (Integer i, Long e) -> {lookup.put(i, e); return i + 1;});\n\t\t\treturn new MappingIterable.IntToLong(unboxInt(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testIntToLong(int[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add((long) i + 1);\n\t\t\t}\n\t\t\tIterableArray.OfInt iterable = new IterableArray.OfInt(numbers);\n\t\t\tPrimitiveIterable.OfLong actual = new MappingIterable.IntToLong(iterable, i -> (long) i + 1);\n\t\t\tassertIterableEquals(unboxLong(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testIntToLong_Null()\n\t\t{\n\t\t\tEmptyIterable.OfInt iterable = EmptyIterable.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.IntToLong(null, each -> (long) each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.IntToLong(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass LongToObj implements MappingIterableTest, FunctionalIterableTest.Of<Object,MappingIterable.LongToObj<Object>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.LongToObj<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tMap<Long, Object> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.of(objects).reduce(1L, (long l, Object e) -> {lookup.put(l, e); return l + 1;});\n\t\t\treturn new MappingIterable.LongToObj<>(unboxLong(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testLongToObj(long[] numbers)\n\t\t{\n\t\t\tArrayList<String> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add(Objects.toString(l));\n\t\t\t}\n\t\t\tIterableArray.OfLong iterable = new IterableArray.OfLong(numbers);\n\t\t\tIterable<String> actual = new MappingIterable.LongToObj<>(iterable, Objects::toString);\n\t\t\tassertIterableEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testLongToObj_Null()\n\t\t{\n\t\t\tEmptyIterable.OfLong iterable = EmptyIterable.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.LongToObj<>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.LongToObj<>(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass LongToDouble implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfDouble<MappingIterable.LongToDouble>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.LongToDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tMap<Long, Double> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofDouble(numbers).reduce(1L, (long l, double e) -> {lookup.put(l, e); return l + 1;});\n\t\t\treturn new MappingIterable.LongToDouble(unboxLong(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testLongToDouble(long[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add(l + 1.0);\n\t\t\t}\n\t\t\tIterableArray.OfLong iterable = new IterableArray.OfLong(numbers);\n\t\t\tPrimitiveIterable.OfDouble actual = new MappingIterable.LongToDouble(iterable, l -> l + 1.0);\n\t\t\tassertIterableEquals(unboxDouble(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testLongToDouble_Null()\n\t\t{\n\t\t\tEmptyIterable.OfLong iterable = EmptyIterable.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.LongToDouble(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.LongToDouble(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass LongToInt implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfInt<MappingIterable.LongToInt>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.LongToInt getReducible(int[] numbers)\n\t\t{\n\t\t\tMap<Long, Integer> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofInt(numbers).reduce(1L, (Long l, Integer e) -> {lookup.put(l, e); return l + 1;});\n\t\t\treturn new MappingIterable.LongToInt(unboxLong(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testLongToInt(long[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add((int) l + 1);\n\t\t\t}\n\t\t\tIterableArray.OfLong iterable = new IterableArray.OfLong(numbers);\n\t\t\tPrimitiveIterable.OfInt actual = new MappingIterable.LongToInt(iterable, l -> (int) l + 1);\n\t\t\tassertIterableEquals(unboxInt(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testLongToInt_Null()\n\t\t{\n\t\t\tEmptyIterable.OfLong iterable = EmptyIterable.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.LongToInt(null, each -> (int) each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.LongToInt(iterable, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass LongToLong implements MappingIterableTest, FunctionalPrimitiveIterableTest.OfLong<MappingIterable.LongToLong>\n\t{\n\t\t@Override\n\t\tpublic MappingIterable.LongToLong getReducible(long[] numbers)\n\t\t{\n\t\t\tMap<Long, Long> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterable.ofLong(numbers).reduce(1L, (long l, long e) -> {lookup.put(l, e); return l + 1;});\n\t\t\treturn new MappingIterable.LongToLong(unboxLong(lookup.keySet()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testLongToLong(long[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add(l + 1);\n\t\t\t}\n\t\t\tIterableArray.OfLong iterable = new IterableArray.OfLong(numbers);\n\t\t\tPrimitiveIterable.OfLong actual = new MappingIterable.LongToLong(iterable, l -> l + 1);\n\t\t\tassertIterableEquals(unboxLong(expected), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testLongToLong_Null()\n\t\t{\n\t\t\tEmptyIterable.OfLong iterable = EmptyIterable.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.LongToLong(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterable.LongToLong(iterable, null));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/MappingIteratorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\n\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\ninterface MappingIteratorTest\n{\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass ObjToObj implements MappingIteratorTest, FunctionalIteratorTest.Of<Object,MappingIterator.ObjToObj<Object,Object>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.ObjToObj<Object, Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tMap<Object, Object> lookup = new LinkedHashMap<>();\n\t\t\tfor (int i=0, length=objects.length; i<length; i++) {\n\t\t\t\tlookup.put(objects[i], objects[length-1-i]);\n\t\t\t}\n\t\t\treturn new MappingIterator.ObjToObj<>(lookup.keySet().iterator(), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysAsArguments\")\n\t\tvoid testOf(Object[] objects)\n\t\t{\n\t\t\tArrayList<String> expected = new ArrayList<>();\n\t\t\tfor (Object each : objects) {\n\t\t\t\texpected.add(Objects.toString(each));\n\t\t\t}\n\t\t\tIterator<Object> iterator = new ArrayIterator.Of<>(objects);\n\t\t\tIterator<String> actual = new MappingIterator.ObjToObj<>(iterator, Objects::toString);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testOf_Null()\n\t\t{\n\t\t\tIterator<Object> iterator = EmptyIterator.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.ObjToObj<>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.ObjToObj<>(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass ObjToDouble implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfDouble<MappingIterator.ObjToDouble<Double>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.ObjToDouble<Double> getReducible(double[] numbers)\n\t\t{\n\t\t\tList<Double> boxed = FunctionalIterator.ofDouble(numbers).collect(new ArrayList<>());\n\t\t\treturn new MappingIterator.ObjToDouble<>(boxed.iterator(), Double::doubleValue);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testObjToDouble(double[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add(d);\n\t\t\t}\n\t\t\tIterator<Double> iterator = expected.iterator();\n\t\t\tFunctionalPrimitiveIterator.OfDouble actual = new MappingIterator.ObjToDouble<>(iterator, each -> each);\n\t\t\tassertIteratorEquals(unboxDouble(expected.iterator()), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testObjToDouble_Null()\n\t\t{\n\t\t\tIterator<Double> iterator = EmptyIterator.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.ObjToDouble<Double>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.ObjToDouble<>(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass ObjToInt implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfInt<MappingIterator.ObjToInt<Integer>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.ObjToInt<Integer> getReducible(int[] numbers)\n\t\t{\n\t\t\tList<Integer> boxed = FunctionalIterator.ofInt(numbers).collect(new ArrayList<>());\n\t\t\treturn new MappingIterator.ObjToInt<>(boxed.iterator(), Integer::intValue);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testObjToInt(int[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add(i);\n\t\t\t}\n\t\t\tIterator<Integer> iterator = expected.iterator();\n\t\t\tFunctionalPrimitiveIterator.OfInt actual = new MappingIterator.ObjToInt<>(iterator, each -> each);\n\t\t\tassertIteratorEquals(unboxInt(expected.iterator()), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testObjToInt_Null()\n\t\t{\n\t\t\tIterator<Integer> iterator = EmptyIterator.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.ObjToInt<Integer>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.ObjToInt<>(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass ObjToLong implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfLong<MappingIterator.ObjToLong<Long>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.ObjToLong<Long> getReducible(long[] numbers)\n\t\t{\n\t\t\tList<Long> boxed = FunctionalIterator.ofLong(numbers).collect(new ArrayList<>());\n\t\t\treturn new MappingIterator.ObjToLong<>(boxed.iterator(), Long::longValue);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testObjToLong(long[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add(l);\n\t\t\t}\n\t\t\tIterator<Long> iterator = expected.iterator();\n\t\t\tFunctionalPrimitiveIterator.OfLong actual = new MappingIterator.ObjToLong<>(iterator, each -> each);\n\t\t\tassertIteratorEquals(unboxLong(expected.iterator()), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testObjToLong_Null()\n\t\t{\n\t\t\tIterator<Long> iterator = EmptyIterator.of();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.ObjToLong<Long>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.ObjToLong<>(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass DoubleToObj implements MappingIteratorTest, FunctionalIteratorTest.Of<Object,MappingIterator.DoubleToObj<Object>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.DoubleToObj<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tMap<Double, Object> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.of(objects).reduce(1.5, (d, e) -> {lookup.put(d, e); return d + 1;});\n\t\t\treturn new MappingIterator.DoubleToObj<>(unboxDouble(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testDoubleToObj(double[] numbers)\n\t\t{\n\t\t\tArrayList<String> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add(Objects.toString(d));\n\t\t\t}\n\t\t\tArrayIterator.OfDouble iterator = new ArrayIterator.OfDouble(numbers);\n\t\t\tIterator<String> actual = new MappingIterator.DoubleToObj<>(iterator, Objects::toString);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testDoubleToObj_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfDouble iterator = EmptyIterator.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.DoubleToObj<>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.DoubleToObj<>(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass DoubleToDouble implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfDouble<MappingIterator.DoubleToDouble>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.DoubleToDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tMap<Double, Double> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofDouble(numbers).reduce(1.5, (double d, double e) -> {lookup.put(d, e); return d + 1;});\n\t\t\treturn new MappingIterator.DoubleToDouble(unboxDouble(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testDoubleToDouble(double[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add(d + 1.0);\n\t\t\t}\n\t\t\tArrayIterator.OfDouble iterator = new ArrayIterator.OfDouble(numbers);\n\t\t\tPrimitiveIterator.OfDouble actual = new MappingIterator.DoubleToDouble(iterator, d -> d + 1.0);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testDoubleToDouble_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfDouble iterator = EmptyIterator.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.DoubleToDouble(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.DoubleToDouble(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass DoubleToInt implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfInt<MappingIterator.DoubleToInt>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.DoubleToInt getReducible(int[] numbers)\n\t\t{\n\t\t\tMap<Double, Integer> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofInt(numbers).reduce(1.5, (Double d, Integer e) -> {lookup.put(d, e); return d + 1;});\n\t\t\treturn new MappingIterator.DoubleToInt(unboxDouble(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testDoubleToInt(double[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add((int) d + 1);\n\t\t\t}\n\t\t\tArrayIterator.OfDouble iterator = new ArrayIterator.OfDouble(numbers);\n\t\t\tPrimitiveIterator.OfInt actual = new MappingIterator.DoubleToInt(iterator, d -> (int) d + 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testDoubleToInt_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfDouble iterator = EmptyIterator.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.DoubleToInt(null, each -> (int) each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.DoubleToInt(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass DoubleToLong implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfLong<MappingIterator.DoubleToLong>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.DoubleToLong getReducible(long[] numbers)\n\t\t{\n\t\t\tMap<Double, Long> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofLong(numbers).reduce(1.5, (double d, long e) -> {lookup.put(d, e); return d + 1;});\n\t\t\treturn new MappingIterator.DoubleToLong(unboxDouble(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfDouble\")\n\t\tpublic void testDoubleToLong(double[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tfor (double d : numbers) {\n\t\t\t\texpected.add((long) d + 1);\n\t\t\t}\n\t\t\tArrayIterator.OfDouble iterator = new ArrayIterator.OfDouble(numbers);\n\t\t\tPrimitiveIterator.OfLong actual = new MappingIterator.DoubleToLong(iterator, d -> (long) d + 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testDoubleToLong_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfDouble iterator = EmptyIterator.ofDouble();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.DoubleToLong(null, each -> (long) each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.DoubleToLong(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass IntToObj implements MappingIteratorTest, FunctionalIteratorTest.Of<Object,MappingIterator.IntToObj<Object>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.IntToObj<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tMap<Integer, Object> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.of(objects).reduce(1, (int i, Object e) -> {lookup.put(i, e); return i + 1;});\n\t\t\treturn new MappingIterator.IntToObj<>(unboxInt(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testIntToObj(int[] numbers)\n\t\t{\n\t\t\tArrayList<String> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add(Objects.toString(i));\n\t\t\t}\n\t\t\tArrayIterator.OfInt iterator = new ArrayIterator.OfInt(numbers);\n\t\t\tIterator<String> actual = new MappingIterator.IntToObj<>(iterator, Objects::toString);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testIntToObj_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfInt iterator = EmptyIterator.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.IntToObj<>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.IntToObj<>(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass IntToDouble implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfDouble<MappingIterator.IntToDouble>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.IntToDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tMap<Integer, Double> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofDouble(numbers).reduce(1, (int i, double e) -> {lookup.put(i, e); return i + 1;});\n\t\t\treturn new MappingIterator.IntToDouble(unboxInt(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testIntToDouble(int[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add(i + 1.0);\n\t\t\t}\n\t\t\tArrayIterator.OfInt iterator = new ArrayIterator.OfInt(numbers);\n\t\t\tPrimitiveIterator.OfDouble actual = new MappingIterator.IntToDouble(iterator, i -> i + 1.0);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testIntToDouble_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfInt iterator = EmptyIterator.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.IntToDouble(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.IntToDouble(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass IntToInt implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfInt<MappingIterator.IntToInt>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.IntToInt getReducible(int[] numbers)\n\t\t{\n\t\t\tMap<Integer, Integer> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofInt(numbers).reduce(1, (int i, int e) -> {lookup.put(i, e); return i + 1;});\n\t\t\treturn new MappingIterator.IntToInt(unboxInt(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testIntToInt(int[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add(i + 1);\n\t\t\t}\n\t\t\tArrayIterator.OfInt iterator = new ArrayIterator.OfInt(numbers);\n\t\t\tPrimitiveIterator.OfInt actual = new MappingIterator.IntToInt(iterator, i -> i + 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testIntToInt_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfInt iterator = EmptyIterator.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.IntToInt(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.IntToInt(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass IntToLong implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfLong<MappingIterator.IntToLong>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.IntToLong getReducible(long[] numbers)\n\t\t{\n\t\t\tMap<Integer, Long> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofLong(numbers).reduce(1, (Integer i, Long e) -> {lookup.put(i, e); return i + 1;});\n\t\t\treturn new MappingIterator.IntToLong(unboxInt(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfInt\")\n\t\tpublic void testIntToLong(int[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tfor (int i : numbers) {\n\t\t\t\texpected.add((long) i + 1);\n\t\t\t}\n\t\t\tArrayIterator.OfInt iterator = new ArrayIterator.OfInt(numbers);\n\t\t\tPrimitiveIterator.OfLong actual = new MappingIterator.IntToLong(iterator, i -> (long) i + 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testIntToLong_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfInt iterator = EmptyIterator.ofInt();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.IntToLong(null, each -> (long) each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.IntToLong(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass LongToObj implements MappingIteratorTest, FunctionalIteratorTest.Of<Object,MappingIterator.LongToObj<Object>>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.LongToObj<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tMap<Long, Object> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.of(objects).reduce(1L, (long l, Object e) -> {lookup.put(l, e); return l + 1;});\n\t\t\treturn new MappingIterator.LongToObj<>(unboxLong(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testLongToObj(long[] numbers)\n\t\t{\n\t\t\tArrayList<String> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add(Objects.toString(l));\n\t\t\t}\n\t\t\tArrayIterator.OfLong iterator = new ArrayIterator.OfLong(numbers);\n\t\t\tIterator<String> actual = new MappingIterator.LongToObj<>(iterator, Objects::toString);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testLongToObj_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfLong iterator = EmptyIterator.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.LongToObj<>(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.LongToObj<>(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass LongToDouble implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfDouble<MappingIterator.LongToDouble>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.LongToDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tMap<Long, Double> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofDouble(numbers).reduce(1L, (long l, double e) -> {lookup.put(l, e); return l + 1;});\n\t\t\treturn new MappingIterator.LongToDouble(unboxLong(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testLongToDouble(long[] numbers)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add(l + 1.0);\n\t\t\t}\n\t\t\tArrayIterator.OfLong iterator = new ArrayIterator.OfLong(numbers);\n\t\t\tPrimitiveIterator.OfDouble actual = new MappingIterator.LongToDouble(iterator, l -> l + 1.0);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testLongToDouble_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfLong iterator = EmptyIterator.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.LongToDouble(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.LongToDouble(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass LongToInt implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfInt<MappingIterator.LongToInt>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.LongToInt getReducible(int[] numbers)\n\t\t{\n\t\t\tMap<Long, Integer> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofInt(numbers).reduce(1L, (Long l, Integer e) -> {lookup.put(l, e); return l + 1;});\n\t\t\treturn new MappingIterator.LongToInt(unboxLong(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testLongToInt(long[] numbers)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add((int) l + 1);\n\t\t\t}\n\t\t\tArrayIterator.OfLong iterator = new ArrayIterator.OfLong(numbers);\n\t\t\tPrimitiveIterator.OfInt actual = new MappingIterator.LongToInt(iterator, l -> (int) l + 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testLongToInt_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfLong iterator = EmptyIterator.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.LongToInt(null, each -> (int) each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.LongToInt(iterator, null));\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass LongToLong implements MappingIteratorTest, FunctionalPrimitiveIteratorTest.OfLong<MappingIterator.LongToLong>\n\t{\n\t\t@Override\n\t\tpublic MappingIterator.LongToLong getReducible(long[] numbers)\n\t\t{\n\t\t\tMap<Long, Long> lookup = new LinkedHashMap<>();\n\t\t\tFunctionalIterator.ofLong(numbers).reduce(1L, (long l, long e) -> {lookup.put(l, e); return l + 1;});\n\t\t\treturn new MappingIterator.LongToLong(unboxLong(lookup.keySet().iterator()), lookup::get);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getArraysOfLong\")\n\t\tpublic void testLongToLong(long[] numbers)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tfor (long l : numbers) {\n\t\t\t\texpected.add(l + 1);\n\t\t\t}\n\t\t\tArrayIterator.OfLong iterator = new ArrayIterator.OfLong(numbers);\n\t\t\tPrimitiveIterator.OfLong actual = new MappingIterator.LongToLong(iterator, l -> l + 1);\n\t\t\tassertIteratorEquals(expected.iterator(), actual);\n\t\t}\n\n\t\t@Test\n\t\tpublic void testLongToLong_Null()\n\t\t{\n\t\t\tPrimitiveIterator.OfLong iterator = EmptyIterator.ofLong();\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.LongToLong(null, each -> each));\n\t\t\tassertThrows(NullPointerException.class, () -> new MappingIterator.LongToLong(iterator, null));\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/PrimitiveIterableTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Test;\n\nimport java.util.Arrays;\nimport java.util.Iterator;\nimport java.util.List;\nimport java.util.PrimitiveIterator;\n\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static org.junit.jupiter.api.Assertions.assertEquals;\nimport static org.junit.jupiter.api.Assertions.assertThrows;\n\npublic class PrimitiveIterableTest\n{\n\t@Test\n\tpublic void testUnboxDoubleIterable()\n\t{\n\t\tIterable<Double> numbers = List.of(0.0, 1.0, 2.0);\n\t\tPrimitiveIterable.OfDouble actual = PrimitiveIterable.unboxDouble(numbers);\n\t\tPrimitiveIterator.OfDouble expected = PrimitiveIterable.unboxDouble(numbers.iterator());\n\t\tassertIteratorEquals(expected, actual.iterator());\n\t}\n\n\t@Test\n\tpublic void testUnboxDoubleIterator()\n\t{\n\t\tIterable<Double> numbers = List.of(0.0, 1.0, 2.0);\n\t\tPrimitiveIterator.OfDouble actual = PrimitiveIterable.unboxDouble(numbers).iterator();\n\t\tfor (double d : numbers) {\n\t\t\tassertEquals(d, actual.nextDouble());\n\t\t}\n\t}\n\n\t@Test\n\tpublic void testUnboxDoubleIterator_NullValues()\n\t{\n\t\tIterable<Double> numbers = Arrays.asList(new Double[] {null});\n\t\tPrimitiveIterator.OfDouble actual = PrimitiveIterable.unboxDouble(numbers).iterator();\n\t\tassertThrows(NullPointerException.class, actual::nextDouble);\n\t}\n\n\t@Test\n\tpublic void testUnboxDouble_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> PrimitiveIterable.unboxDouble((Iterator<Double>) null));\n\t\tassertThrows(NullPointerException.class, () -> PrimitiveIterable.unboxDouble((Iterable<Double>) null));\n\t}\n\n\t@Test\n\tpublic void testUnboxIntIterable()\n\t{\n\t\tIterable<Integer> numbers = List.of(0, 1, 2);\n\t\tPrimitiveIterable.OfInt actual = PrimitiveIterable.unboxInt(numbers);\n\t\tPrimitiveIterator.OfInt expected = PrimitiveIterable.unboxInt(numbers.iterator());\n\t\tassertIteratorEquals(expected, actual.iterator());\n\t}\n\n\t@Test\n\tpublic void testUnboxIntIterator()\n\t{\n\t\tIterable<Integer> numbers = List.of(0, 1, 2);\n\t\tPrimitiveIterator.OfInt actual = PrimitiveIterable.unboxInt(numbers).iterator();\n\t\tfor (int i : numbers) {\n\t\t\tassertEquals(i, actual.nextInt());\n\t\t}\n\t}\n\n\t@Test\n\tpublic void testUnboxIntIterator_NullValues()\n\t{\n\t\tIterable<Integer> numbers = Arrays.asList(new Integer[] {null});\n\t\tPrimitiveIterator.OfInt actual = PrimitiveIterable.unboxInt(numbers).iterator();\n\t\tassertThrows(NullPointerException.class, actual::nextInt);\n\t}\n\n\t@Test\n\tpublic void testUnboxInt_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> PrimitiveIterable.unboxInt((Iterator<Integer>) null));\n\t\tassertThrows(NullPointerException.class, () -> PrimitiveIterable.unboxInt((Iterable<Integer>) null));\n\t}\n\n\t@Test\n\tpublic void testLongDoubleIterable()\n\t{\n\t\tIterable<Long> numbers = List.of(0L, 1L, 2L);\n\t\tPrimitiveIterable.OfLong actual = PrimitiveIterable.unboxLong(numbers);\n\t\tPrimitiveIterator.OfLong expected = PrimitiveIterable.unboxLong(numbers.iterator());\n\t\tassertIteratorEquals(expected, actual.iterator());\n\t}\n\n\t@Test\n\tpublic void testUnboxLongIterator()\n\t{\n\t\tIterable<Long> numbers = List.of(0L, 1L, 2L);\n\t\tPrimitiveIterator.OfLong actual = PrimitiveIterable.unboxLong(numbers).iterator();\n\t\tfor (long l : numbers) {\n\t\t\tassertEquals(l, actual.nextLong());\n\t\t}\n\t}\n\n\t@Test\n\tpublic void testUnboxLongIterator_NullValues()\n\t{\n\t\tIterable<Long> numbers = Arrays.asList(new Long[] {null});\n\t\tPrimitiveIterator.OfLong actual = PrimitiveIterable.unboxLong(numbers).iterator();\n\t\tassertThrows(NullPointerException.class, actual::nextLong);\n\t}\n\n\t@Test\n\tpublic void testUnboxLong_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> PrimitiveIterable.unboxLong((Iterator<Long>) null));\n\t\tassertThrows(NullPointerException.class, () -> PrimitiveIterable.unboxLong((Iterable<Long>) null));\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/PrimitiveReducibleTest.java",
    "content": "package common.iterable;\n\nimport common.functions.DoubleLongToDoubleFunction;\nimport common.functions.IntDoubleToIntFunction;\nimport common.functions.IntLongToIntFunction;\nimport common.functions.LongDoubleToLongFunction;\nimport common.functions.ObjDoubleFunction;\nimport common.functions.ObjIntFunction;\nimport common.functions.ObjLongFunction;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.function.*;\nimport java.util.stream.Stream;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static common.iterable.Assertions.*;\nimport static common.iterable.PrimitiveIterable.*;\nimport static org.junit.jupiter.api.Assertions.*;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\n\npublic interface PrimitiveReducibleTest\n{\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tinterface OfDouble<T extends PrimitiveReducible.OfDouble<?>> extends ReducibleTest<Double, T>\n\t{\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn getDuplicatesArraysOfDouble().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getEmptyReducibles()\n\t\t{\n\t\t\treturn getEmptyArraysOfDouble().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getSingletonReducibles()\n\t\t{\n\t\t\treturn getSingletonArraysOfDouble().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getMultitonReducibles()\n\t\t{\n\t\t\treturn getMultitonArraysOfDouble().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\tT getReducible(double[] arguments);\n\n\t\t@Override\n\t\tdefault Iterable<Object> getExcluded(T reducible)\n\t\t{\n\t\t\tList<Double> candidates = getExclusionListOfDouble();\n\t\t\treducible.forEach((double d) -> {\n\t\t\t\tcandidates.remove(d);\n\t\t\t\tif (d == 0.0) {\n\t\t\t\t\tcandidates.remove(-1 * d);\n\t\t\t\t}\n\t\t\t});\n\t\t\tList<Object> excluded = new ArrayList<>();\n\t\t\texcluded.addAll(getUniqueObjects());\n\t\t\texcluded.addAll(candidates);\n\t\t\treturn excluded;\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectDoubleArray(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count();\n\t\t\tdouble[] expected = new double[n];\n\t\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\t\tsupplier.get().forEach((double d) -> expected[index.nextInt()] = d);\n\t\t\tdouble[] actual = supplier.get().collect(new double[n]);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectDoubleArrayOffset(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), offset = 2, tail = 3;\n\t\t\tdouble[] expected = new double[offset + n + tail];\n\t\t\tRange.RangeIterator index = new Range(offset, offset + n).iterator();\n\t\t\tsupplier.get().forEach((double d) -> expected[index.nextInt()] = d);\n\t\t\tdouble[] actual = supplier.get().collect(new double[offset + n + tail], offset);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCollectOfDouble_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collect((double[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collect((double[]) null, 0));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectAndCountDoubleArray(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), tail = 3;\n\t\t\tdouble[] expected = new double[n + tail];\n\t\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\t\tsupplier.get().forEach((double d) -> expected[index.nextInt()] = d);\n\t\t\tdouble[] actual = new double[n + tail];\n\t\t\tlong count = supplier.get().collectAndCount(actual);\n\t\t\tassertEquals(n, count);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectAndCountDoubleArrayOffset(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), offset = 2, tail = 3;\n\t\t\tdouble[] expected = new double[offset + n + tail];\n\t\t\tRange.RangeIterator index = new Range(offset, offset + n).iterator();\n\t\t\tsupplier.get().forEach((double d) -> expected[index.nextInt()] = d);\n\t\t\tdouble[] actual = new double[offset + n + tail];\n\t\t\tlong count = supplier.get().collectAndCount(actual, offset);\n\t\t\tassertEquals(n, count);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCollectAndCountOfDouble_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((double[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((double[]) null, 0));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getReducibles\", \"getDuplicatesReducibles\"})\n\t\t@Override\n\t\tdefault void testCollectDistinct(Supplier<T> supplier)\n\t\t{\n\t\t\tSet<Double> expected = new HashSet<>();\n\t\t\tsupplier.get().forEach((double d) -> {\n\t\t\t\tif (!expected.contains(d) && !(d == 0.0 && expected.contains(-1.0 * d))) {\n\t\t\t\t\texpected.add(d);\n\t\t\t\t}\n\t\t\t});\n\t\t\tList<Double> actual = supplier.get().collectDistinct().collect(new ArrayList<>());\n\t\t\tassertTrue(expected.containsAll(actual), \"actual =< expected\");\n\t\t\tassertTrue(actual.containsAll(expected), \"actual >= expected\");\n\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFilterDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tArrayList<Double> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEach((double d) -> {\n\t\t\t\tif (d % 2 == 0) {\n\t\t\t\t\texpected.add(d);\n\t\t\t\t}\n\t\t\t});\n\t\t\tPrimitiveReducible.OfDouble<?> actual = supplier.get().filter((double d) -> d % 2 == 0);\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testFilterOfDouble_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.filter((DoublePredicate) null));\n\t\t}\n\n\t\tvoid testFlatMapDoubleToObj(Supplier<T> supplier);\n\n\t\tvoid testFlatMapDoubleToDouble(Supplier<T> supplier);\n\n\t\tvoid testFlatMapDoubleToInt(Supplier<T> supplier);\n\n\t\tvoid testFlatMapDoubleToLong(Supplier<T> supplier);\n\n\t\tvoid testFlatMapDoubleToNull(Supplier<T> supplier);\n\n\t\tvoid testFlatMapOfDouble_Null();\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapDoubleToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tString prefix = \"Item: \";\n\t\t\tList<String> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEach((double d) -> expected.add(prefix + d));\n\t\t\tReducible<String, ?> actual = supplier.get().map((double d) -> prefix + d);\n\t\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapDoubleToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfDouble expected = unboxDouble(range.map((int i) -> (double) i));\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveReducible.OfDouble<?> actual = supplier.get().mapToDouble((double d) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxDouble(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapDoubleToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange expected = new Range((int) supplier.get().count());\n\t\t\tRange.RangeIterator index = expected.iterator();\n\t\t\tPrimitiveReducible.OfInt<?> actual = supplier.get().mapToInt((double d) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxInt(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapDoubleToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfLong expected = unboxLong(range.map((int i) -> (long) i));\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveReducible.OfLong<?> actual = supplier.get().mapToLong((double d) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxLong(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testMapOfDouble_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.map((DoubleFunction<?>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToDouble((DoubleUnaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToInt((DoubleToIntFunction) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToLong((DoubleToLongFunction) null));\n\t\t}\n\n\t\tvoid testForEachDoubleConsumer(Supplier<T> supplier);\n\n\t\t@Test\n\t\tdefault void testForEachDoubleConsumer_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.forEach((DoubleConsumer) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testReduceDoubleBinaryOperator_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tDoubleBinaryOperator dummy = (res, each) -> Double.MIN_VALUE;\n\t\t\tOptionalDouble actual = supplier.get().reduce(dummy);\n\t\t\tassertEquals(OptionalDouble.empty(), actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testReduceDoubleBinaryOperator_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tDoubleBinaryOperator dummy = (res, each) -> Double.MIN_VALUE;\n\t\t\tdouble expected = supplier.get().detect((double d) -> true);\n\t\t\tOptionalDouble actual = supplier.get().reduce(dummy);\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected, actual.getAsDouble());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testReduceDoubleBinaryOperator_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tList<Double> actual = new ArrayList<>();\n\t\t\tdouble probe = -31; // \"unique\" value\n\t\t\tDoubleBinaryOperator collect = (res, each) -> {\n\t\t\t\tif (actual.isEmpty()) {\n\t\t\t\t\tactual.add(res);\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn probe;\n\t\t\t\t} else {\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn res;\n\t\t\t\t}\n\t\t\t};\n\t\t\tOptionalDouble result = supplier.get().reduce(collect);\n\t\t\tassertTrue(result.isPresent());\n\t\t\tassertEquals(probe, result.getAsDouble());\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testReduceIntDoubleToIntFunction(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tint init = Integer.MIN_VALUE;\n\t\t\tList<Double> actual = new ArrayList<>();\n\t\t\tIntDoubleToIntFunction collect = (res, each) -> {actual.add(each); return res;};\n\t\t\tint result = supplier.get().reduce(init, collect);\n\t\t\tassertEquals(init, result);\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testReduceLongDoubleToLongFunction(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tlong init = Long.MIN_VALUE;\n\t\t\tList<Double> actual = new ArrayList<>();\n\t\t\tLongDoubleToLongFunction collect = (res, each) -> {actual.add(each); return res;};\n\t\t\tlong result = supplier.get().reduce(init, collect);\n\t\t\tassertEquals(init, result);\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testReduceObjDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tObjDoubleFunction<List<Double>, List<Double>> collect = (seq, each) -> {seq.add(each); return seq;};\n\t\t\tList<Double> actual = supplier.get().reduce(new ArrayList<>(), collect);\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual));\n\t\t\tassertDoesNotThrow(() -> supplier.get().reduce(null, (Object obj, double each) -> null));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testReduceOfDouble_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce((DoubleBinaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(new Object(), (ObjDoubleFunction<Object, Object>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0.0, (DoubleBinaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0, (IntDoubleToIntFunction) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0L, (LongDoubleToLongFunction) null));\n\t\t}\n\n\t\tvoid testConcatTypes();\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getReducibles\", \"getDuplicatesReducibles\"})\n\t\t@Override\n\t\tdefault void testDistinct(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEach((double d) -> {\n\t\t\t\tif (!expected.contains(d) && !(d == 0.0 && expected.contains(-1.0 * d))) {\n\t\t\t\t\texpected.add(d);\n\t\t\t\t}\n\t\t\t});\n\t\t\tList<Double> actual = supplier.get().distinct().collect(new ArrayList<>());\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getReducibles\", \"getDuplicatesReducibles\"})\n\t\tdefault void testDedupe(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEach((double d) -> {\n\t\t\t\tif (expected.isEmpty()) {\n\t\t\t\t\texpected.add(d);\n\t\t\t\t} else {\n\t\t\t\t\tdouble last = expected.get(expected.size() - 1);\n\t\t\t\t\tif (last != d && !(Double.isNaN(last) && Double.isNaN(d))) {\n\t\t\t\t\t\texpected.add(d);\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t});\n\t\t\tList<Double> actual = supplier.get().dedupe().collect(new ArrayList<>());\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testAllMatchDoublePredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match all elements\n\t\t\tassertTrue(supplier.get().allMatch((double each) -> true), \"Expected allMatch() == true\");\n\t\t\t// match not all elements\n\t\t\tDoublePredicate matchNotAll = new DoublePredicate() {\n\t\t\t\t// match: no element if singleton, otherwise every odd element\n\t\t\t\tboolean flag = supplier.get().count() == 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(double d)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertFalse(supplier.get().allMatch(matchNotAll), \"Expected allMatch() == false\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testAllMatchDoublePredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((double each) -> false), \"Exepted allMatch() == true if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testAllMatchDoublePredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.allMatch((DoublePredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testAnyMatchDoublePredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match no element\n\t\t\tassertFalse(supplier.get().anyMatch((double each) -> false), \"Expected anyMatch() == false\");\n\t\t\t// match some elements\n\t\t\tDoublePredicate matchSome = new DoublePredicate() {\n\t\t\t\t// match: first element if singleton, otherwise every even element\n\t\t\t\tboolean flag = supplier.get().count() > 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(double d)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertTrue(supplier.get().anyMatch(matchSome), \"Expected anyMatch() == true\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testAnyMatchDoublePredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((double each) -> true), \"Exepted anyMatch() == false if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testAnyMatchDoublePredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.anyMatch((DoublePredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testNoneMatchDoublePredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match no element\n\t\t\tassertTrue(supplier.get().noneMatch((double each) -> false), \"Expected noneMatch() == true\");\n\t\t\t// match some elements\n\t\t\tDoublePredicate matchSome = new DoublePredicate() {\n\t\t\t\t// match: first element if singleton, otherwise every even element\n\t\t\t\tboolean flag = supplier.get().count() > 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(double d)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertFalse(supplier.get().noneMatch(matchSome), \"Expected noneMatch() == false\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testNoneMatchDoublePredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((double each) -> false), \"Exepted noneMatch() == false if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testNoneMatchDoublePredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.noneMatch((DoublePredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@Override\n\t\tdefault void testContains(Supplier<T> supplier)\n\t\t{\n\t\t\tassertFalse(supplier.get().contains(null));\n\t\t\ttestContainsDouble(supplier);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testContainsDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> numbers = supplier.get().collect(new ArrayList<>());\n\t\t\tfor (Double each : numbers) { // boxed double to trigger contains(Double d)\n\t\t\t\tassertTrue(supplier.get().contains(each), \"Expected contains(\" + each + \") == true\");\n\t\t\t\tif (each == 0.0) {\n\t\t\t\t\tassertTrue(supplier.get().contains(-1.0 * each), \"Expected contains(\" + (-1.0 * each) + \") == true\");\n\t\t\t\t}\n\t\t\t}\n\t\t\tfor (Object each : getExcluded(supplier.get())) { // boxed double to trigger contains(Double d)\n\t\t\t\tassertFalse(supplier.get().contains(each), \"Expected contains(\" + each + \") == false\");\n\t\t\t}\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCountDoublePredicate(Supplier<T> supplier)\n\t\t{\n\t\t\tlong[] expected = new long[] {0L};\n\t\t\tsupplier.get().forEach((double d) -> {\n\t\t\t\tif (d % 2 == 1) {\n\t\t\t\t\texpected[0]++;\n\t\t\t\t}\n\t\t\t});\n\t\t\tDoublePredicate odd = d -> d % 2 == 1;\n\t\t\tlong actual = supplier.get().count(odd);\n\t\t\tassertEquals(expected[0], actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCountDoublePredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.count((DoublePredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testDetectDoublePredicate_AllFalse(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = supplier.get();\n\t\t\tassertThrows(NoSuchElementException.class, () -> reducible.detect((double each) -> false));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testDetectDoublePredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = supplier.get();\n\t\t\tassertThrows(NoSuchElementException.class, () -> reducible.detect((double each) -> true));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testDetectDoublePredicate_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\t// match first element\n\t\t\tdouble expected = supplier.get().collect(new ArrayList<>()).get(0);\n\t\t\tdouble actual = supplier.get().detect((double each) -> true);\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testDetectDoublePredicate_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\t// match second element\n\t\t\tdouble expected = supplier.get().collect(new ArrayList<>()).get(1);\n\t\t\tDoublePredicate second = new DoublePredicate() {\n\t\t\t\tboolean flag = true;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(double d)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tdouble actual = supplier.get().detect(second);\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testDetectDoublePredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfDouble<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.detect((DoublePredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testMin_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalDouble expected = OptionalDouble.empty();\n\t\t\tOptionalDouble actual = supplier.get().min();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testMin_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalDouble expected = OptionalDouble.of(supplier.get().detect((double d) -> true));\n\t\t\tOptionalDouble actual = supplier.get().min();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertDoubleEquals(expected.getAsDouble(), actual.getAsDouble());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testMin_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tdouble[] expected = new double[] {supplier.get().detect((double d) -> true)};\n\t\t\tsupplier.get().forEach((double d) -> expected[0] = Math.min(expected[0], d));\n\t\t\tOptionalDouble actual = supplier.get().min();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertDoubleEquals(expected[0], actual.getAsDouble());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testMax_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalDouble expected = OptionalDouble.empty();\n\t\t\tOptionalDouble actual = supplier.get().max();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testMax_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalDouble expected = OptionalDouble.of(supplier.get().detect((double d) -> true));\n\t\t\tOptionalDouble actual = supplier.get().max();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertDoubleEquals(expected.getAsDouble(), actual.getAsDouble());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testMax_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tdouble[] expected = new double[] {supplier.get().detect((double d) -> true)};\n\t\t\tsupplier.get().forEach((double d) -> expected[0] = Math.max(expected[0], d));\n\t\t\tOptionalDouble actual = supplier.get().max();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertDoubleEquals(expected[0], actual.getAsDouble());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getReducibles\"})\n\t\tdefault void testSum(Supplier<T> supplier)\n\t\t{\n\t\t\tdouble[] expected = new double[] {0.0};\n\t\t\tsupplier.get().forEach((double d) -> expected[0] += d);\n\t\t\tdouble actual = supplier.get().sum();\n\t\t\tassertEquals(expected[0], actual, 1e-15);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testSum_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tdouble expected = 0.0;\n\t\t\tdouble actual = supplier.get().sum();\n\t\t\tassertDoubleEquals(expected, actual);\n\t\t}\n\t}\n\n\n\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tinterface OfInt<T extends PrimitiveReducible.OfInt<?>> extends ReducibleTest<Integer, T>\n\t{\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn getDuplicatesArraysOfInt().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getEmptyReducibles()\n\t\t{\n\t\t\treturn getEmptyArraysOfInt().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getSingletonReducibles()\n\t\t{\n\t\t\treturn getSingletonArraysOfInt().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getMultitonReducibles()\n\t\t{\n\t\t\treturn getMultitonArraysOfInt().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\tT getReducible(int[] arguments);\n\n\t\t@Override\n\t\tdefault Iterable<Object> getExcluded(T reducible)\n\t\t{\n\t\t\tList<Integer> candidates = getExclusionListOfInt();\n\t\t\treducible.forEach((Consumer<Integer>) candidates::remove);\n\t\t\tList<Object> excluded = new ArrayList<>();\n\t\t\texcluded.addAll(getUniqueObjects());\n\t\t\texcluded.addAll(candidates);\n\t\t\treturn excluded;\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectIntArray(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count();\n\t\t\tint[] expected = new int[n];\n\t\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\t\tsupplier.get().forEach((int e) -> expected[index.nextInt()] = e);\n\t\t\tint[] actual = supplier.get().collect(new int[n]);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectIntArrayOffset(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), offset = 2, tail = 3;\n\t\t\tint[] expected = new int[offset + n + tail];\n\t\t\tRange.RangeIterator index = new Range(offset, offset + n).iterator();\n\t\t\tsupplier.get().forEach((int i) -> expected[index.nextInt()] = i);\n\t\t\tint[] actual = supplier.get().collect(new int[offset + n + tail], offset);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectBitSet(Supplier<T> supplier)\n\t\t{\n\t\t\tBitSet expected = new BitSet();\n\t\t\tsupplier.get().forEach((int i) -> {if (i >= 0) expected.set(i);});\n\t\t\tBitSet actual = supplier.get().filter((int i) -> i >= 0).collect(new BitSet());\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCollectOfInt_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collect((int[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collect((int[]) null, 0));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collect((BitSet) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectAndCountIntArray(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), tail = 3;\n\t\t\tint[] expected = new int[n + tail];\n\t\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\t\tsupplier.get().forEach((int i) -> expected[index.nextInt()] = i);\n\t\t\tint[] actual = new int[n + tail];\n\t\t\tlong count = supplier.get().collectAndCount(actual);\n\t\t\tassertEquals(n, count);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectAndCountIntArrayOffset(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), offset = 2, tail = 3;\n\t\t\tint[] expected = new int[offset + n + tail];\n\t\t\tRange.RangeIterator index = new Range(offset, offset + n).iterator();\n\t\t\tsupplier.get().forEach((int i) -> expected[index.nextInt()] = i);\n\t\t\tint[] actual = new int[offset + n + tail];\n\t\t\tlong count = supplier.get().collectAndCount(actual, offset);\n\t\t\tassertEquals(n, count);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectAndCountBitSet(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().filter((int i) -> i >= 0).count();\n\t\t\tBitSet expected = new BitSet();\n\t\t\tsupplier.get().forEach((int i) -> {if (i >= 0) expected.set(i);});\n\t\t\tBitSet actual = new BitSet();\n\t\t\tlong count = supplier.get().filter((int i) -> i >= 0).collectAndCount(actual);\n\t\t\tassertEquals(n, count);\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCollectAndCountOfInt_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((int[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((int[]) null, 0));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((BitSet) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFilterInt(Supplier<T> supplier)\n\t\t{\n\t\t\tArrayList<Integer> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEach((int i) -> {\n\t\t\t\tif (i % 2 == 0) {\n\t\t\t\t\texpected.add(i);\n\t\t\t\t}\n\t\t\t});\n\t\t\tPrimitiveReducible.OfInt<?> actual = supplier.get().filter((int i) -> i % 2 == 0);\n\t\t\tassertIterableEquals(unboxInt(expected), unboxInt(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testFilterOfInt_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.filter((IntPredicate) null));\n\t\t}\n\n\t\tvoid testFlatMapIntToObj(Supplier<T> supplier);\n\n\t\tvoid testFlatMapIntToDouble(Supplier<T> supplier);\n\n\t\tvoid testFlatMapIntToInt(Supplier<T> supplier);\n\n\t\tvoid testFlatMapIntToLong(Supplier<T> supplier);\n\n\t\tvoid testFlatMapIntToNull(Supplier<T> supplier);\n\n\t\tvoid testFlatMapOfInt_Null();\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapIntToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tString prefix = \"Item: \";\n\t\t\tList<String> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEach((int i) -> expected.add(prefix + i));\n\t\t\tReducible<String, ?> actual = supplier.get().map((int i) -> prefix + i);\n\t\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapIntToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfDouble expected = unboxDouble(range.map((int i) -> (double) i));\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveReducible.OfDouble<?> actual = supplier.get().mapToDouble((int i) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxDouble(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapIntToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange expected = new Range((int) supplier.get().count());\n\t\t\tRange.RangeIterator index = expected.iterator();\n\t\t\tPrimitiveReducible.OfInt<?> actual = supplier.get().mapToInt((int i) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxInt(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfLong expected = unboxLong(range.map((int i) -> (long) i));\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveReducible.OfLong<?> actual = supplier.get().mapToLong((int i) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxLong(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testMapOfInt_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.map((IntFunction<?>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToDouble((IntToDoubleFunction) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToInt((IntUnaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToLong((IntToLongFunction) null));\n\t\t}\n\n\t\tvoid testForEachIntConsumer(Supplier<T> supplier);\n\n\t\t@Test\n\t\tdefault void testForEachIntConsumer_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.forEach((IntConsumer) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testReduceIntBinaryOperator_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tIntBinaryOperator dummy = (res, each) -> Integer.MIN_VALUE;\n\t\t\tOptionalInt actual = supplier.get().reduce(dummy);\n\t\t\tassertEquals(OptionalInt.empty(), actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testReduceIntBinaryOperator_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tIntBinaryOperator dummy = (res, each) -> Integer.MIN_VALUE;\n\t\t\tint expected = supplier.get().detect((int i) -> true);\n\t\t\tOptionalInt actual = supplier.get().reduce(dummy);\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected, actual.getAsInt());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testReduceIntBinaryOperator_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Integer> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tList<Integer> actual = new ArrayList<>();\n\t\t\tint probe = -31; // \"unique\" value\n\t\t\tIntBinaryOperator collect = (res, each) -> {\n\t\t\t\tif (actual.isEmpty()) {\n\t\t\t\t\tactual.add(res);\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn probe;\n\t\t\t\t} else {\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn res;\n\t\t\t\t}\n\t\t\t};\n\t\t\tOptionalInt result = supplier.get().reduce(collect);\n\t\t\tassertTrue(result.isPresent());\n\t\t\tassertEquals(probe, result.getAsInt());\n\t\t\tassertIterableEquals(unboxInt(expected), unboxInt(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testReduceDoubleBinaryOperator_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tDoubleBinaryOperator dummy = (res, each) -> Double.MIN_VALUE;\n\t\t\tOptionalDouble actual = supplier.get().reduce(dummy);\n\t\t\tassertEquals(OptionalDouble.empty(), actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testReduceDoubleBinaryOperator_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tDoubleBinaryOperator dummy = (res, each) -> Double.MIN_VALUE;\n\t\t\tdouble expected = supplier.get().detect((int i) -> true);\n\t\t\tOptionalDouble actual = supplier.get().reduce(dummy);\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected, actual.getAsDouble());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testReduceDoubleBinaryOperator_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Double> expected = supplier.get().mapToDouble((int i) -> (double) i).collect(new ArrayList<>());\n\t\t\tList<Double> actual = new ArrayList<>();\n\t\t\tdouble probe = -31; // \"unique\" value\n\t\t\tDoubleBinaryOperator collect = (res, each) -> {\n\t\t\t\tif (actual.isEmpty()) {\n\t\t\t\t\tactual.add(res);\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn probe;\n\t\t\t\t} else {\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn res;\n\t\t\t\t}\n\t\t\t};\n\t\t\tOptionalDouble result = supplier.get().reduce(collect);\n\t\t\tassertTrue(result.isPresent());\n\t\t\tassertEquals(probe, result.getAsDouble());\n\t\t\tassertIterableEquals(unboxDouble(expected), unboxDouble(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testReduceLongBinaryOperator_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tLongBinaryOperator dummy = (res, each) -> Long.MIN_VALUE;\n\t\t\tOptionalLong actual = supplier.get().reduce(dummy);\n\t\t\tassertEquals(OptionalLong.empty(), actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testReduceLongBinaryOperator_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tLongBinaryOperator dummy = (res, each) -> Long.MIN_VALUE;\n\t\t\tlong expected = supplier.get().detect((int i) -> true);\n\t\t\tOptionalLong actual = supplier.get().reduce(dummy);\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected, actual.getAsLong());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testReduceLongBinaryOperator_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Long> expected = supplier.get().mapToLong((int i) -> (long) i).collect(new ArrayList<>());\n\t\t\tList<Long> actual = new ArrayList<>();\n\t\t\tlong probe = -31; // \"unique\" value\n\t\t\tLongBinaryOperator collect = (res, each) -> {\n\t\t\t\tif (actual.isEmpty()) {\n\t\t\t\t\tactual.add(res);\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn probe;\n\t\t\t\t} else {\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn res;\n\t\t\t\t}\n\t\t\t};\n\t\t\tOptionalLong result = supplier.get().reduce(collect);\n\t\t\tassertTrue(result.isPresent());\n\t\t\tassertEquals(probe, result.getAsLong());\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testReduceObjIntFunction(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Integer> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tObjIntFunction<List<Integer>, List<Integer>> collect = (seq, each) -> {seq.add(each); return seq;};\n\t\t\tList<Integer> actual = supplier.get().reduce(new ArrayList<>(), collect);\n\t\t\tassertIterableEquals(unboxInt(expected), unboxInt(actual));\n\t\t\tassertDoesNotThrow(() -> supplier.get().reduce(null, (Object obj, int each) -> null));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testReduceOfInt_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce((DoubleBinaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce((IntBinaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce((LongBinaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(new Object(), (ObjIntFunction<Object, Object>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0.0, (DoubleBinaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0, (IntBinaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0L, (LongBinaryOperator) null));\n\t\t}\n\n\t\tvoid testConcatTypes();\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testAllMatchIntPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match all elements\n\t\t\tassertTrue(supplier.get().allMatch((int each) -> true), \"Expected allMatch() == true\");\n\t\t\t// match not all elements\n\t\t\tIntPredicate matchNotAll = new IntPredicate() {\n\t\t\t\t// match: no element if singleton, otherwise every odd element\n\t\t\t\tboolean flag = supplier.get().count() == 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(int i)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertFalse(supplier.get().allMatch(matchNotAll), \"Expected allMatch() == false\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testAllMatchIntPredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((int each) -> false), \"Exepted allMatch() == true if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testAllMatchIntPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.allMatch((IntPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testAnyMatchIntPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match no element\n\t\t\tassertFalse(supplier.get().anyMatch((int each) -> false), \"Expected anyMatch() == false\");\n\t\t\t// match some elements\n\t\t\tIntPredicate matchSome = new IntPredicate() {\n\t\t\t\t// match: first element if singleton, otherwise every even element\n\t\t\t\tboolean flag = supplier.get().count() > 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(int i)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertTrue(supplier.get().anyMatch(matchSome), \"Expected anyMatch() == true\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testAnyMatchIntPredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((int each) -> true), \"Exepted anyMatch() == false if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testAnyMatchIntPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.anyMatch((IntPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testNoneMatchIntPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match no element\n\t\t\tassertTrue(supplier.get().noneMatch((int each) -> false), \"Expected noneMatch() == true\");\n\t\t\t// match some elements\n\t\t\tIntPredicate matchSome = new IntPredicate() {\n\t\t\t\t// match: first element if singleton, otherwise every even element\n\t\t\t\tboolean flag = supplier.get().count() > 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(int i)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertFalse(supplier.get().noneMatch(matchSome), \"Expected noneMatch() == false\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testNoneMatchIntPredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((int each) -> false), \"Exepted noneMatch() == false if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testNoneMatchIntPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.noneMatch((IntPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@Override\n\t\tdefault void testContains(Supplier<T> supplier)\n\t\t{\n\t\t\tassertFalse(supplier.get().contains(null), \"Expected contains(null) == false\");\n\t\t\ttestContainsInt(supplier);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testContainsInt(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Integer> numbers = supplier.get().collect(new ArrayList<>());\n\t\t\tfor (Integer each : numbers) { // boxed int to trigger contains(Integer i)\n\t\t\t\tassertTrue(supplier.get().contains(each), \"Expected contains(\" + each + \") == true\");\n\t\t\t}\n\t\t\tfor (Object each : getExcluded(supplier.get())) { // boxed int to trigger contains(Integer i)\n\t\t\t\tassertFalse(supplier.get().contains(each), \"Expected contains(\" + each + \") == false\");\n\t\t\t}\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCountIntPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\tlong[] expected = new long[] {0L};\n\t\t\tsupplier.get().forEach((int i) -> {\n\t\t\t\tif (i % 2 == 1) {\n\t\t\t\t\texpected[0]++;\n\t\t\t\t}\n\t\t\t});\n\t\t\tIntPredicate odd = i -> i % 2 == 1;\n\t\t\tlong actual = supplier.get().count(odd);\n\t\t\tassertEquals(expected[0], actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCountIntPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.count((IntPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testDetectIntPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = supplier.get();\n\t\t\tassertThrows(NoSuchElementException.class, () -> reducible.detect((int each) -> false));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testDetectIntPredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = supplier.get();\n\t\t\tassertThrows(NoSuchElementException.class, () -> reducible.detect((int each) -> true));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testDetectIntPredicate_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\t// match first element\n\t\t\tint expected = supplier.get().collect(new ArrayList<>()).get(0);\n\t\t\tint actual = supplier.get().detect((int each) -> true);\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testDetectIntPredicate_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\t// match second element\n\t\t\tint expected = supplier.get().collect(new ArrayList<>()).get(1);\n\t\t\tIntPredicate second = new IntPredicate() {\n\t\t\t\tboolean flag = true;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(int i)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tint actual = supplier.get().detect(second);\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testDetectIntPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfInt<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.detect((IntPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testMin_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalInt expected = OptionalInt.empty();\n\t\t\tOptionalInt actual = supplier.get().min();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testMin_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalInt expected = OptionalInt.of(supplier.get().detect((int i) -> true));\n\t\t\tOptionalInt actual = supplier.get().min();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected.getAsInt(), actual.getAsInt());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testMin_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tint[] expected = new int[] {supplier.get().detect((int i) -> true)};\n\t\t\tsupplier.get().forEach((int i) -> expected[0] = Math.min(expected[0], i));\n\t\t\tOptionalInt actual = supplier.get().min();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected[0], actual.getAsInt());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testMax_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalInt expected = OptionalInt.empty();\n\t\t\tOptionalInt actual = supplier.get().max();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testMax_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalInt expected = OptionalInt.of(supplier.get().detect((int i) -> true));\n\t\t\tOptionalInt actual = supplier.get().max();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected.getAsInt(), actual.getAsInt());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testMax_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tint[] expected = new int[] {supplier.get().detect((int i) -> true)};\n\t\t\tsupplier.get().forEach((int i) -> expected[0] = Math.max(expected[0], i));\n\t\t\tOptionalInt actual = supplier.get().max();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected[0], actual.getAsInt());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testSum(Supplier<T> supplier)\n\t\t{\n\t\t\tlong[] expected = new long[] {0L};\n\t\t\tsupplier.get().forEach((int i) -> expected[0] += i);\n\t\t\tlong actual = supplier.get().sum();\n\t\t\tassertEquals(expected[0], actual);\n\t\t}\n\t}\n\n\n\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tinterface OfLong<T extends PrimitiveReducible.OfLong<?>> extends ReducibleTest<Long, T>\n\t{\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn getDuplicatesArraysOfLong().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getEmptyReducibles()\n\t\t{\n\t\t\treturn getEmptyArraysOfLong().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getSingletonReducibles()\n\t\t{\n\t\t\treturn getSingletonArraysOfLong().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getMultitonReducibles()\n\t\t{\n\t\t\treturn getMultitonArraysOfLong().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\tT getReducible(long[] numbers);\n\n\t\t@Override\n\t\tdefault Iterable<Object> getExcluded(T reducible)\n\t\t{\n\t\t\tList<Long> candidates = getExclusionListOfLong();\n\t\t\treducible.forEach((Consumer<Long>) candidates::remove);\n\t\t\tList<Object> excluded = new ArrayList<>();\n\t\t\texcluded.addAll(getUniqueObjects());\n\t\t\texcluded.addAll(candidates);\n\t\t\treturn excluded;\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectLongArray(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count();\n\t\t\tlong[] expected = new long[n];\n\t\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\t\tsupplier.get().forEach((long l) -> expected[index.nextInt()] = l);\n\t\t\tlong[] actual = supplier.get().collect(new long[n]);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectLongArrayOffset(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), offset = 2, tail = 3;\n\t\t\tlong[] expected = new long[offset + n + tail];\n\t\t\tRange.RangeIterator index = new Range(offset, offset + n).iterator();\n\t\t\tsupplier.get().forEach((long l) -> expected[index.nextInt()] = l);\n\t\t\tlong[] actual = supplier.get().collect(new long[offset + n + tail], offset);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCollectOfLong_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collect((long[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collect((long[]) null, 0));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectAndCountLongArray(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), tail = 3;\n\t\t\tlong[] expected = new long[n + tail];\n\t\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\t\tsupplier.get().forEach((long l) -> expected[index.nextInt()] = l);\n\t\t\tlong[] actual = new long[n + tail];\n\t\t\tlong count = supplier.get().collectAndCount(actual);\n\t\t\tassertEquals(n, count);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCollectAndCountArrayOffset(Supplier<T> supplier)\n\t\t{\n\t\t\tint n = (int) supplier.get().count(), offset = 2, tail = 3;\n\t\t\tlong[] expected = new long[offset + n + tail];\n\t\t\tRange.RangeIterator index = new Range(offset, offset + n).iterator();\n\t\t\tsupplier.get().forEach((long l) -> expected[index.nextInt()] = l);\n\t\t\tlong[] actual = new long[offset + n + tail];\n\t\t\tlong count = supplier.get().collectAndCount(actual, offset);\n\t\t\tassertEquals(n, count);\n\t\t\tassertArrayEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCollectAndCountOfLong_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((long[]) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((long[]) null, 0));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testFilterLong(Supplier<T> supplier)\n\t\t{\n\t\t\tArrayList<Long> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEach((long l) -> {\n\t\t\t\tif (l % 2 == 0) {\n\t\t\t\t\texpected.add(l);\n\t\t\t\t}\n\t\t\t});\n\t\t\tPrimitiveReducible.OfLong<?> actual = supplier.get().filter((long l) -> l % 2 == 0);\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testFilterOfLong_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.filter((LongPredicate) null));\n\t\t}\n\n\t\tvoid testFlatMapLongToObj(Supplier<T> supplier);\n\n\t\tvoid testFlatMapLongToDouble(Supplier<T> supplier);\n\n\t\tvoid testFlatMapLongToInt(Supplier<T> supplier);\n\n\t\tvoid testFlatMapLongToLong(Supplier<T> supplier);\n\n\t\tvoid testFlatMapLongToNull(Supplier<T> supplier);\n\n\t\tvoid testFlatMapOfLong_Null();\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapLongToObj(Supplier<T> supplier)\n\t\t{\n\t\t\tString prefix = \"Item: \";\n\t\t\tList<String> expected = new ArrayList<>();\n\t\t\tsupplier.get().forEach((long l) -> expected.add(prefix + l));\n\t\t\tReducible<String, ?> actual = supplier.get().map((long l) -> prefix + l);\n\t\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapLongToDouble(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfDouble expected = unboxDouble(range.map((int i) -> (double) i));\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveReducible.OfDouble<?> actual = supplier.get().mapToDouble((long l) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxDouble(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapLongToInt(Supplier<T> supplier)\n\t\t{\n\t\t\tRange expected = new Range((int) supplier.get().count());\n\t\t\tRange.RangeIterator index = expected.iterator();\n\t\t\tPrimitiveReducible.OfInt<?> actual = supplier.get().mapToInt((long l) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxInt(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testMapToLong(Supplier<T> supplier)\n\t\t{\n\t\t\tRange range = new Range((int) supplier.get().count());\n\t\t\tPrimitiveIterable.OfLong expected = unboxLong(range.map((int i) -> (long) i));\n\t\t\tRange.RangeIterator index = range.iterator();\n\t\t\tPrimitiveReducible.OfLong<?> actual = supplier.get().mapToLong((long l) -> index.next());\n\t\t\tassertIterableEquals(expected, unboxLong(actual.collect(new ArrayList<>())));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testMapOfLong_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.map((LongFunction<?>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToDouble((LongToDoubleFunction) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToInt((LongToIntFunction) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.mapToLong((LongUnaryOperator) null));\n\t\t}\n\n\t\tvoid testForEachLongConsumer(Supplier<T> supplier);\n\n\t\t@Test\n\t\tdefault void testForEachLongConsumer_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.forEach((LongConsumer) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testReduceLongBinaryOperator_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tLongBinaryOperator dummy = (res, each) -> Long.MIN_VALUE;\n\t\t\tOptionalLong actual = supplier.get().reduce(dummy);\n\t\t\tassertEquals(OptionalLong.empty(), actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testReduceLongBinaryOperator_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tLongBinaryOperator dummy = (res, each) -> Long.MIN_VALUE;\n\t\t\tlong expected = supplier.get().detect((long l) -> true);\n\t\t\tOptionalLong actual = supplier.get().reduce(dummy);\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected, actual.getAsLong());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testReduceLongBinaryOperator_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Long> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tList<Long> actual = new ArrayList<>();\n\t\t\tlong probe = -31; // \"unique\" value\n\t\t\tLongBinaryOperator collect = (res, each) -> {\n\t\t\t\tif (actual.isEmpty()) {\n\t\t\t\t\tactual.add(res);\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn probe;\n\t\t\t\t} else {\n\t\t\t\t\tactual.add(each);\n\t\t\t\t\treturn res;\n\t\t\t\t}\n\t\t\t};\n\t\t\tOptionalLong result = supplier.get().reduce(collect);\n\t\t\tassertTrue(result.isPresent());\n\t\t\tassertEquals(probe, result.getAsLong());\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testReduceDoubleLongToDoubleFunction(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Long> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tdouble init = Double.MIN_VALUE;\n\t\t\tList<Long> actual = new ArrayList<>();\n\t\t\tDoubleLongToDoubleFunction collect = (res, each) -> {actual.add(each); return res;};\n\t\t\tdouble result = supplier.get().reduce(init, collect);\n\t\t\tassertEquals(init, result);\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testReduceIntLongToIntFunction(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Long> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tint init = Integer.MIN_VALUE;\n\t\t\tList<Long> actual = new ArrayList<>();\n\t\t\tIntLongToIntFunction collect = (res, each) -> {actual.add(each); return res;};\n\t\t\tint result = supplier.get().reduce(init, collect);\n\t\t\tassertEquals(init, result);\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testReduceObjLong(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Long> expected = supplier.get().collect(new ArrayList<>());\n\t\t\tObjLongFunction<List<Long>, List<Long>> collect = (seq, each) -> {seq.add(each); return seq;};\n\t\t\tList<Long> actual = supplier.get().reduce(new ArrayList<>(), collect);\n\t\t\tassertIterableEquals(unboxLong(expected), unboxLong(actual));\n\t\t\tassertDoesNotThrow(() -> supplier.get().reduce(null, (Object obj, long each) -> null));\n\t\t}\n\n\t\t@Test\n\t\tdefault void testReduceOfLong_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce((LongBinaryOperator) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(new Object(), (ObjLongFunction<Object, Object>) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0.0, (DoubleLongToDoubleFunction) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0, (IntLongToIntFunction) null));\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0L, (LongBinaryOperator) null));\n\t\t}\n\n\t\tvoid testConcatTypes();\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testAllMatchLongPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match all elements\n\t\t\tassertTrue(supplier.get().allMatch((long each) -> true), \"Expected allMatch() == true\");\n\t\t\t// match not all elements\n\t\t\tLongPredicate matchNotAll = new LongPredicate() {\n\t\t\t\t// match: no element if singleton, otherwise every odd element\n\t\t\t\tboolean flag = supplier.get().count() == 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(long i)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertFalse(supplier.get().allMatch(matchNotAll), \"Expected allMatch() == false\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testAllMatchLongPredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((long each) -> false), \"Exepted allMatch() == true if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testAllMatchLongPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.allMatch((LongPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testAnyMatchLongPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match no element\n\t\t\tassertFalse(supplier.get().anyMatch((long each) -> false), \"Expected anyMatch() == false\");\n\t\t\t// match some elements\n\t\t\tLongPredicate matchSome = new LongPredicate() {\n\t\t\t\t// match: first element if singleton, otherwise every even element\n\t\t\t\tboolean flag = supplier.get().count() > 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(long i)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertTrue(supplier.get().anyMatch(matchSome), \"Expected anyMatch() == true\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testAnyMatchLongPredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((long each) -> true), \"Exepted anyMatch() == false if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testAnyMatchLongPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.anyMatch((LongPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\t\tdefault void testNoneMatchLongPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\t// match no element\n\t\t\tassertTrue(supplier.get().noneMatch((long each) -> false), \"Expected noneMatch() == true\");\n\t\t\t// match some elements\n\t\t\tLongPredicate matchSome = new LongPredicate() {\n\t\t\t\t// match: first element if singleton, otherwise every even element\n\t\t\t\tboolean flag = supplier.get().count() > 1;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(long i)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tassertFalse(supplier.get().noneMatch(matchSome), \"Expected noneMatch() == false\");\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testNoneMatchLongPredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = supplier.get();\n\t\t\tassertTrue(reducible.allMatch((long each) -> false), \"Exepted noneMatch() == false if iterator is empty\");\n\t\t}\n\n\t\t@Test\n\t\tdefault void testNoneMatchLongPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.noneMatch((LongPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\t@Override\n\t\tdefault void testContains(Supplier<T> supplier)\n\t\t{\n\t\t\tassertFalse(supplier.get().contains(null), \"Expected contains(null) == false\");\n\t\t\ttestContainsLong(supplier);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testContainsLong(Supplier<T> supplier)\n\t\t{\n\t\t\tList<Long> numbers = supplier.get().collect(new ArrayList<>());\n\t\t\tfor (Long each : numbers) { // boxed long to trigger contains(Long l)\n\t\t\t\tassertTrue(supplier.get().contains(each), \"Expected contains(\" + each + \") == true\");\n\t\t\t}\n\t\t\tfor (Object each : getExcluded(supplier.get())) { // boxed long to trigger contains(Long l)\n\t\t\t\tassertFalse(supplier.get().contains(each), \"Expected contains(\" + each + \") == false\");\n\t\t\t}\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testCountLongPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\tlong[] expected = new long[] {0L};\n\t\t\tsupplier.get().forEach((long l) -> {\n\t\t\t\tif (l % 2 == 1) {\n\t\t\t\t\texpected[0]++;\n\t\t\t\t}\n\t\t\t});\n\t\t\tLongPredicate odd = l -> l % 2 == 1;\n\t\t\tlong actual = supplier.get().count(odd);\n\t\t\tassertEquals(expected[0], actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testCountLongPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.count((LongPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testDetectLongPredicate(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = supplier.get();\n\t\t\tassertThrows(NoSuchElementException.class, () -> reducible.detect((long each) -> false));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testDetectLongPredicate_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = supplier.get();\n\t\t\tassertThrows(NoSuchElementException.class, () -> reducible.detect((long each) -> true));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testDetectLongPredicate_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\t// match first element\n\t\t\tlong expected = supplier.get().collect(new ArrayList<>()).get(0);\n\t\t\tlong actual = supplier.get().detect((long each) -> true);\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testDetectLongPredicate_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\t// match second element\n\t\t\tlong expected = supplier.get().collect(new ArrayList<>()).get(1);\n\t\t\tLongPredicate second = new LongPredicate() {\n\t\t\t\tboolean flag = true;\n\t\t\t\t@Override\n\t\t\t\tpublic boolean test(long l)\n\t\t\t\t{\n\t\t\t\t\tflag = !flag;\n\t\t\t\t\treturn flag;\n\t\t\t\t}\n\t\t\t};\n\t\t\tlong actual = supplier.get().detect(second);\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@Test\n\t\tdefault void testDetectLongPredicate_Null()\n\t\t{\n\t\t\tPrimitiveReducible.OfLong<?> reducible = getAnyReducible();\n\t\t\tassertThrows(NullPointerException.class, () -> reducible.detect((LongPredicate) null));\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testMin_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalLong expected = OptionalLong.empty();\n\t\t\tOptionalLong actual = supplier.get().min();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testMin_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalLong expected = OptionalLong.of(supplier.get().detect((long l) -> true));\n\t\t\tOptionalLong actual = supplier.get().min();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected.getAsLong(), actual.getAsLong());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testMin_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tlong[] expected = new long[] {supplier.get().detect((long l) -> true)};\n\t\t\tsupplier.get().forEach((long l) -> expected[0] = Math.min(expected[0], l));\n\t\t\tOptionalLong actual = supplier.get().min();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected[0], actual.getAsLong());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getEmptyReducibles\")\n\t\tdefault void testMax_Empty(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalLong expected = OptionalLong.empty();\n\t\t\tOptionalLong actual = supplier.get().max();\n\t\t\tassertEquals(expected, actual);\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getSingletonReducibles\")\n\t\tdefault void testMax_Singleton(Supplier<T> supplier)\n\t\t{\n\t\t\tOptionalLong expected = OptionalLong.of(supplier.get().detect((long l) -> true));\n\t\t\tOptionalLong actual = supplier.get().max();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected.getAsLong(), actual.getAsLong());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getMultitonReducibles\")\n\t\tdefault void testMax_Multiton(Supplier<T> supplier)\n\t\t{\n\t\t\tlong[] expected = new long[] {supplier.get().detect((long l) -> true)};\n\t\t\tsupplier.get().forEach((long l) -> expected[0] = Math.max(expected[0], l));\n\t\t\tOptionalLong actual = supplier.get().max();\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected[0], actual.getAsLong());\n\t\t}\n\n\t\t@ParameterizedTest\n\t\t@MethodSource(\"getReducibles\")\n\t\tdefault void testSum(Supplier<T> supplier)\n\t\t{\n\t\t\tlong[] expected = new long[] {0L};\n\t\t\tsupplier.get().forEach((long l) -> expected[0] += l);\n\t\t\tlong actual = supplier.get().sum();\n\t\t\tassertEquals(expected[0], actual);\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/RangeTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.api.TestInstance;\nimport org.junit.jupiter.api.TestInstance.Lifecycle;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.Arguments;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.ArrayList;\nimport java.util.List;\nimport java.util.PrimitiveIterator;\nimport java.util.function.Supplier;\nimport java.util.stream.Stream;\n\nimport static common.iterable.PrimitiveReducibleTest.*;\nimport static org.junit.jupiter.api.Assertions.*;\n\nclass RangeTest implements FunctionalPrimitiveIterableTest.OfInt<Range>\n{\n\tstatic Range asRange(Arguments args)\n\t{\n\t\tObject[] params = args.get();\n\t\treturn new Range((Integer) params[0], (Integer) params[1], (Integer) params[2]);\n\t}\n\n\tstatic Stream<Arguments> getEmptyRangeArguments()\n\t{\n\t\treturn Stream.of(Arguments.of(0, 0, 1),\n\t\t\t\tArguments.of(0, 0, -1),\n\t\t\t\tArguments.of(Integer.MAX_VALUE, Integer.MAX_VALUE, 1),\n\t\t\t\tArguments.of(Integer.MIN_VALUE, Integer.MIN_VALUE, -1));\n\t}\n\n\tstatic Stream<Arguments> getSingletonRangeArguments()\n\t{\n\t\treturn Stream.of(Arguments.of(0, 1, 1),\n\t\t\t\tArguments.of(0, -1, -1),\n\t\t\t\tArguments.of(Integer.MAX_VALUE-1, Integer.MAX_VALUE, 1),\n\t\t\t\tArguments.of(Integer.MIN_VALUE+1, Integer.MIN_VALUE, -1));\n\t}\n\n\tstatic Stream<Arguments> getMultitonRangeArguments()\n\t{\n\t\treturn Stream.of(Arguments.of(0, 10, 1),\n\t\t\t\tArguments.of(0, -10, -1),\n\t\t\t\tArguments.of(-10, 10, 3),\n\t\t\t\tArguments.of(10, -10, -3),\n\t\t\t\tArguments.of(Integer.MIN_VALUE, Integer.MIN_VALUE+20, 7),\n\t\t\t\tArguments.of(Integer.MAX_VALUE, Integer.MAX_VALUE-20, -7));\n\t}\n\n\t@Override\n\tpublic Range getReducible(int[] arguments)\n\t{\n\t\tthrow new RuntimeException(\"Should not be called\");\n\t}\n\n\t@Override\n\tpublic Stream<Supplier<Range>> getDuplicatesReducibles()\n\t{\n\t\treturn Stream.empty();\n\t}\n\n\t@Override\n\tpublic Stream<Supplier<Range>> getEmptyReducibles()\n\t{\n\t\treturn getEmptyRangeArguments().map(args -> () -> asRange(args));\n\t}\n\n\t@Override\n\tpublic Stream<Supplier<Range>> getSingletonReducibles()\n\t{\n\t\treturn getSingletonRangeArguments().map(args -> () -> asRange(args));\n\t}\n\n\t@Override\n\tpublic Stream<Supplier<Range>> getMultitonReducibles()\n\t{\n\t\treturn getMultitonRangeArguments().map(args -> () -> asRange(args));\n\t}\n\n\t@Override\n\tpublic Iterable<Object> getExcluded(Range range)\n\t{\n\t\tList<Object> excluded = new ArrayList<>();\n\t\texcluded.addAll(getUniqueObjects());\n\t\t// add lower and upper bounds\n\t\trange.min().ifPresent(min -> {\n\t\t\tif (min > Integer.MIN_VALUE) {\n\t\t\t\texcluded.add(min - 1);\n\t\t\t\texcluded.add(Integer.MIN_VALUE);\n\t\t\t}\n\t\t});\n\t\trange.max().ifPresent(max -> {\n\t\t\tif (max < Integer.MAX_VALUE) {\n\t\t\t\texcluded.add(max + 1);\n\t\t\t\texcluded.add(Integer.MAX_VALUE);\n\t\t\t}\n\t\t});\n\t\t// add ints between first and last that are no steps\n\t\tif (range.isAscending()) {\n\t\t\tfor (int i = range.first; i <= range.last; i++) {\n\t\t\t\tif ((i - range.first) % range.step != 0) {\n\t\t\t\t\texcluded.add((Integer) i);\n\t\t\t\t}\n\t\t\t}\n\t\t} else {\n\t\t\tfor (int i = range.first; i >= range.last; i--) {\n\t\t\t\tif ((i - range.first) % range.step != 0) {\n\t\t\t\t\texcluded.add((Integer) i);\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t\treturn excluded;\n\t}\n\n\tpublic static void assertEqualsClosedForLoop(int start, int stop, int step, Range actual)\n\t{\n\t\tassertEqualsClosedForLoop(start, stop, step, actual.iterator());\n\t}\n\n\tpublic static void assertEqualsOpenForLoop(int start, int stop, int step, Range actual)\n\t{\n\t\tassertEqualsOpenForLoop(start, stop, step, actual.iterator());\n\t}\n\n\tpublic static void assertEqualsClosedForLoop(int start, int stop, int step, PrimitiveIterator.OfInt actual)\n\t{\n\t\tif (step > 0) {\n\t\t\t// closed ascending loop: <=\n\t\t\tfor (int i = start; i <= stop; i = Math.addExact(i, step)) {\n\t\t\t\tassertEquals(i, actual.nextInt());\n\t\t\t}\n\t\t} else if (step < 0) {\n\t\t\t// open descending loop: >=\n\t\t\tfor (int i = start; i >= stop; i = Math.addExact(i, step)) {\n\t\t\t\tassertEquals(i, actual.nextInt());\n\t\t\t}\n\t\t} else {\n\t\t\tfail(\"expected step != 0\");\n\t\t}\n\t\tassertFalse(actual.hasNext(), \"Expected exhausted iterator\");\n\t}\n\n\tpublic static void assertEqualsOpenForLoop(int start, int stop, int step, PrimitiveIterator.OfInt actual)\n\t{\n\t\tif (step > 0) {\n\t\t\t// open ascending loop: <\n\t\t\tfor (int i = start; i < stop; i = Math.addExact(i, step)) {\n\t\t\t\tassertEquals(i, actual.nextInt());\n\t\t\t}\n\t\t} else if (step < 0) {\n\t\t\t// open descending loop: >\n\t\t\tfor (int i = start; i > stop; i = Math.addExact(i, step)) {\n\t\t\t\tassertEquals(i, actual.nextInt());\n\t\t\t}\n\t\t} else {\n\t\t\tfail(\"expected step != 0\");\n\t\t}\n\t\tassertFalse(actual.hasNext(), \"Expected exhausted iterator\");\n\t}\n\n\t/**\n\t * Test method for {@link common.iterable.Range#closed(int)}.\n\t */\n\t@ParameterizedTest\n\t@MethodSource({\"getEmptyRangeArguments\", \"getSingletonRangeArguments\", \"getMultitonRangeArguments\"})\n\tvoid testClosedInt(int start, int stop, int step)\n\t{\n\t\tif (step > 0 && start == 0) {\n\t\t\t// range with positive step width starting at 0\n\t\t\t// adjust stop to maybe be included\n\t\t\tint closed = (step > 0) ? stop - 1 : stop + 1;\n\t\t\tRange actual = Range.closed(closed);\n\t\t\tassertEqualsClosedForLoop(0, closed, 1, actual);\n\t\t}\n\t}\n\n\t/**\n\t * Test method for {@link common.iterable.Range#closed(int, int)}.\n\t */\n\t@ParameterizedTest\n\t@MethodSource({\"getEmptyRangeArguments\", \"getSingletonRangeArguments\", \"getMultitonRangeArguments\"})\n\tvoid testClosedIntInt(int start, int stop, int step)\n\t{\n\t\tif (step > 0) {\n\t\t\t// range with positive step width\n\t\t\t// adjust stop to maybe be included\n\t\t\tint closed = (step > 0) ? stop - 1 : stop + 1;\n\t\t\tRange actual = Range.closed(start, closed);\n\t\t\tassertEqualsClosedForLoop(start, closed, 1, actual);\n\t\t}\n\t}\n\n\t/**\n\t * Test method for {@link common.iterable.Range#closed(int, int, int)}.\n\t */\n\t@ParameterizedTest\n\t@MethodSource({\"getEmptyRangeArguments\", \"getSingletonRangeArguments\", \"getMultitonRangeArguments\"})\n\tvoid testClosedIntIntInt(int start, int stop, int step)\n\t{\n\t\t// adjust stop to maybe be included\n\t\tint closed = (step > 0) ? stop - 1 : stop + 1;\n\t\tRange actual = Range.closed(start, closed, step);\n\t\tassertEqualsClosedForLoop(start, closed, step, actual);\n\t}\n\n\t/**\n\t * Test method for {@link common.iterable.Range#Range(int)}.\n\t */\n\t@ParameterizedTest\n\t@MethodSource({\"getEmptyRangeArguments\", \"getSingletonRangeArguments\", \"getMultitonRangeArguments\"})\n\tvoid testRangeInt(int start, int stop, int step)\n\t{\n\t\tif (step > 0 && start == 0) {\n\t\t\t// range with positive step width starting at 0\n\t\t\tRange actual = new Range(stop);\n\t\t\tassertEqualsOpenForLoop(0, stop, 1, actual);\n\t\t}\n\t}\n\n\t/**\n\t * Test method for {@link common.iterable.Range#Range(int, int)}.\n\t */\n\t@ParameterizedTest\n\t@MethodSource({\"getEmptyRangeArguments\", \"getSingletonRangeArguments\", \"getMultitonRangeArguments\"})\n\tvoid testRangeIntInt(int start, int stop, int step)\n\t{\n\t\tif (step > 0) {\n\t\t\t// range with positive step width\n\t\t\tRange actual = new Range(start, stop);\n\t\t\tassertEqualsOpenForLoop(start, stop, 1, actual);\n\t\t}\n\t}\n\n\t/**\n\t * Test method for {@link common.iterable.Range#Range(int, int, int, boolean)}.\n\t */\n\t@ParameterizedTest\n\t@MethodSource({\"getEmptyRangeArguments\", \"getSingletonRangeArguments\", \"getMultitonRangeArguments\"})\n\tvoid testRangeIntIntInt(int start, int stop, int step)\n\t{\n\t\tRange actual = new Range(start, stop, step);\n\t\tassertEqualsOpenForLoop(start, stop, step, actual);\n\t}\n\n\t@Test\n\tvoid testRangeStepZero()\n\t{\n\t\tassertThrows(IllegalArgumentException.class, () -> new Range(1, 2, 0));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tvoid testIsAscending(Supplier<Range> supplier)\n\t{\n\t\tRange range = supplier.get();\n\t\tif (range.isEmpty() || range.isSingleton()) {\n\t\t\tassertTrue(range.isAscending());\n\t\t} else if (range.step > 0) {\n\t\t\tassertTrue(range.isAscending());\n\t\t} else if(range.step < 0) {\n\t\t\tassertFalse(range.isAscending());\n\t\t} else {\n\t\t\tfail(\"expected step != 0\");\n\t\t}\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tvoid testIsSingleton(Supplier<Range> supplier)\n\t{\n\t\tRange range = supplier.get();\n\t\tassertTrue(range.count() !=1 ^ range.isSingleton());\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tvoid testReversed(Supplier<Range> supplier)\n\t{\n\t\tRange range = supplier.get();\n\t\tif (range.first == Integer.MIN_VALUE && !range.isEmpty()) {\n\t\t\t// reverse() at min value throws\n\t\t\tassertThrows(ArithmeticException.class, range::reversed);\n\t\t} else if (range.first == Integer.MAX_VALUE && !range.isEmpty()) {\n\t\t\t// reverse() at min value throws\n\t\t\tassertThrows(ArithmeticException.class, range::reversed);\n\t\t} else {\n\t\t\tassertEqualsClosedForLoop(range.last, range.first, -range.step, range.reversed());\n\t\t}\n\t}\n\n\t/**\n\t * Test method for {@link common.iterable.Range#toString()}.\n\t */\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tvoid testToString(Supplier<Range> supplier)\n\t{\n\t\tRange range = supplier.get();\n\t\tString expected = \"Range.closed(\" + range.first + \", \" + range.last + \", \" + range.step + \")\";\n\t\tString actual = range.toString();\n\t\tassertEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testEqualsAndHash()\n\t{\n\t\tRange range = Range.closed(-2, 4, 3); // {-2, 1, 4}\n\n\t\t// equal to itself\n\t\tassertEquals(range, range);\n\n\t\t// equal to a clone\n\t\tRange clone = Range.closed(-2, 4, 3);\n\t\tassertEquals(range, clone);\n\t\tassertEquals(range.hashCode(), clone.hashCode());\n\n\t\t// not equal to null or other type\n\t\tassertFalse(range.equals(null));\n\t\tassertFalse(range.equals(\"no\"));\n\n\t\t// not equal to an arbitrary range\n\t\tRange otherStart = Range.closed(-5, 4, 3); // {-5, -2, 1, 4}\n\t\tassertNotEquals(otherStart, range);\n\t\tRange otherStop = Range.closed(-2, 7, 3); // {-2, 1, 4, 7}\n\t\tassertNotEquals(otherStop, range);\n\t\tRange otherStep = Range.closed(-2, 4, 2); // {-2, 0, 2, 4}\n\t\tassertNotEquals(otherStep, range);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getEmptyRangeArguments\"})\n\tvoid testEqualsAndHashEmpty(int start, int stop, int step)\n\t{\n\t\tRange expected = new Range(0);\n\t\tRange actual = new Range(start, stop, step);\n\t\tassertEquals(expected, actual);\n\t\tassertEquals(expected.hashCode(), actual.hashCode());\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getSingletonRangeArguments\"})\n\tvoid testEqualsAndHashSingleton(int start, int stop, int step)\n\t{\n\t\tRange expected = new Range(start, stop, step > 0 ? 1 : -1);\n\t\tRange actual = new Range(start, stop, step);\n\t\tassertEquals(expected, actual);\n\t\tassertEquals(expected.hashCode(), actual.hashCode());\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(Lifecycle.PER_CLASS)\n\tclass RangeIteratorTest implements FunctionalPrimitiveIteratorTest.OfInt<Range.RangeIterator>\n\t{\n\t\t@Override\n\t\tpublic Range.RangeIterator getReducible(int[] arguments)\n\t\t{\n\t\t\tthrow new RuntimeException(\"Should not be called\");\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<Range.RangeIterator>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<Range.RangeIterator>> getEmptyReducibles()\n\t\t{\n\t\t\treturn getEmptyRangeArguments().map(args -> () -> asRange(args).iterator());\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<Range.RangeIterator>> getSingletonReducibles()\n\t\t{\n\t\t\treturn getSingletonRangeArguments().map(args -> () -> asRange(args).iterator());\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<Range.RangeIterator>> getMultitonReducibles()\n\t\t{\n\t\t\treturn getMultitonRangeArguments().map(args -> () -> asRange(args).iterator());\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/ReducibleStaticTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.DisplayName;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.stream.Stream;\n\nimport static common.iterable.Assertions.assertIterableEquals;\nimport static common.iterable.Assertions.assertIteratorEquals;\nimport static org.junit.jupiter.api.Assertions.assertIterableEquals;\nimport static org.junit.jupiter.api.Assertions.*;\n\nclass ReducibleStaticTest\n{\n\tstatic Stream<Iterable<Object>> getIterables()\n\t{\n\t\treturn Stream.of(Collections.singleton(null),\n\t\t                 Collections.emptyList(),\n\t\t                 Collections.singleton(\"one\"),\n\t\t                 Arrays.asList(\"one\", \"two\", \"three\"));\n\t}\n\n\tstatic <T> Stream<Iterable<T>> getIterablesNull()\n\t{\n\t\treturn Stream.of(Collections.singleton(null));\n\t}\n\n\tstatic Stream<Iterable<Double>> getIterablesDouble()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t                 Collections.singleton(1.0),\n\t\t                 Arrays.asList(1.0, 2.0, 3.0));\n\t}\n\n\tstatic Stream<Iterable<Integer>> getIterablesInt()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t                 Collections.singleton(1),\n\t\t                 Arrays.asList(1, 2, 3));\n\t}\n\n\tstatic Stream<Iterable<Long>> getIterablesLong()\n\t{\n\t\treturn Stream.of(Collections.emptyList(),\n\t\t                 Collections.singleton(1L),\n\t\t                 Arrays.asList(1L, 2L, 3L));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterables\")\n\t@DisplayName(\"extend() yields same sequence as the underlying iterable.\")\n\tvoid testExtendIterable(Iterable<?> iterable)\n\t{\n\t\tFunctionalIterable<?> actual = Reducible.extend(iterable);\n\t\tassertIterableEquals(iterable, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterables\")\n\t@DisplayName(\"extend() yields same sequence as the underlying iterator.\")\n\tvoid testExtendIterator(Iterable<?> iterable)\n\t{\n\t\tIterator<?> expected = iterable.iterator();\n\t\tFunctionalIterator<?> actual = Reducible.extend(iterable.iterator());\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterables\")\n\t@DisplayName(\"extend() does not extend a FunctionalIterable.\")\n\tvoid testExtendFunctionalIterable(Iterable<?> iterable)\n\t{\n\t\tIterable<?> expected = Reducible.extend(iterable);\n\t\tFunctionalIterable<?> actual = Reducible.extend(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterables\")\n\t@DisplayName(\"extend() does not extend a FunctionalIterator.\")\n\tvoid testExtendFunctionalIterator(Iterable<?> iterable)\n\t{\n\t\tIterator<?> expected = Reducible.extend(iterable.iterator());\n\t\tFunctionalIterator<?> actual = Reducible.extend(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\t@DisplayName(\"extend() does not extend a FunctionalPrimitiveIterable.OfDouble.\")\n\tvoid testExtendFunctionalPrimitiveIterableOfDouble(Iterable<Double> iterable)\n\t{\n\t\tPrimitiveIterable.OfDouble expected = Reducible.extend(PrimitiveIterable.unboxDouble(iterable));\n\t\tFunctionalIterable<Double> functional = Reducible.extend(expected);\n\t\tassertSame(expected, functional);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\t@DisplayName(\"extend() does not extend a FunctionalPrimitiveIterator.OfDouble.\")\n\tvoid testExtendFunctionalPrimitiveIteratorOfDouble(Iterable<Double> iterable)\n\t{\n\t\tPrimitiveIterator.OfDouble expected = Reducible.extend(PrimitiveIterable.unboxDouble(iterable.iterator()));\n\t\tFunctionalIterator<Double> actual = Reducible.extend(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\t@DisplayName(\"extend() does not extend a FunctionalPrimitiveIterable.OfInt.\")\n\tvoid testExtendFunctionalPrimitiveIterableOfInt(Iterable<Integer> iterable)\n\t{\n\t\tPrimitiveIterable.OfInt expected = Reducible.extend(PrimitiveIterable.unboxInt(iterable));\n\t\tFunctionalIterable<Integer> actual = Reducible.extend(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\t@DisplayName(\"extend() does not extend a FunctionalPrimitiveIterator.OfInt.\")\n\tvoid testExtendFunctionalPrimitiveIteratorOfInt(Iterable<Integer> iterable)\n\t{\n\t\tPrimitiveIterator.OfInt expected = Reducible.extend(PrimitiveIterable.unboxInt(iterable.iterator()));\n\t\tFunctionalIterator<Integer> actual = Reducible.extend(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\t@DisplayName(\"extend() does not extend a FunctionalPrimitiveIterable.OfLong.\")\n\tvoid testExtendFunctionalPrimitiveIterableOfLong(Iterable<Long> iterable)\n\t{\n\t\tPrimitiveIterable.OfLong expected = Reducible.extend(PrimitiveIterable.unboxLong(iterable));\n\t\tFunctionalIterable<Long> actual = Reducible.extend(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\t@DisplayName(\"extend() does not extend a FunctionalPrimitiveIterator.OfLong.\")\n\tvoid testExtendFunctionalPrimitiveIteratorOfLong(Iterable<Long> iterable)\n\t{\n\t\tPrimitiveIterator.OfLong expected = Reducible.extend(PrimitiveIterable.unboxLong(iterable).iterator());\n\t\tFunctionalIterator<Long> actual = Reducible.extend(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\t@DisplayName(\"extend() extends OfDouble to FunctionalPrimitiveIterable.\")\n\tvoid testExtendPrimitiveIterableOfDouble(Iterable<Double> iterable)\n\t{\n\t\tIterable<Double> primitive = PrimitiveIterable.unboxDouble(iterable);\n\t\tFunctionalIterable<Double> actual = Reducible.extend(primitive);\n\t\tassertTrue(actual instanceof FunctionalPrimitiveIterable);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\t@DisplayName(\"extend() extends OfDouble to FunctionalPrimitiveIterator.\")\n\tvoid testExtendPrimitiveIteratorOfDouble(Iterable<Double> iterable)\n\t{\n\t\tIterator<Double> primitive = PrimitiveIterable.unboxDouble(iterable).iterator();\n\t\tFunctionalIterator<Double> actual = Reducible.extend(primitive);\n\t\tassertTrue(actual instanceof FunctionalPrimitiveIterator);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\t@DisplayName(\"extend() extends OfInt to FunctionalPrimitiveIterable.\")\n\tvoid testExtendPrimitiveIterableOfInt(Iterable<Integer> iterable)\n\t{\n\t\tIterable<Integer> primitive = PrimitiveIterable.unboxInt(iterable);\n\t\tFunctionalIterable<Integer> actual = Reducible.extend(primitive);\n\t\tassertTrue(actual instanceof FunctionalPrimitiveIterable);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\t@DisplayName(\"extend() extends OfInt to FunctionalPrimitiveIterator.\")\n\tvoid testExtendPrimitiveIteratorOfInt(Iterable<Integer> iterable)\n\t{\n\t\tIterator<Integer> primitive = PrimitiveIterable.unboxInt(iterable.iterator());\n\t\tFunctionalIterator<Integer> actual = Reducible.extend(primitive);\n\t\tassertTrue(actual instanceof FunctionalPrimitiveIterator);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\t@DisplayName(\"extend() extends OfLong to FunctionalPrimitiveIterable.\")\n\tvoid testExtendPrimitiveIterableOfLong(Iterable<Long> iterable)\n\t{\n\t\tIterable<Long> primitive = PrimitiveIterable.unboxLong(iterable);\n\t\tFunctionalIterable<Long> actual = Reducible.extend(primitive);\n\t\tassertTrue(actual instanceof FunctionalPrimitiveIterable);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\t@DisplayName(\"extend() extends OfLong to FunctionalPrimitiveIterator.\")\n\tvoid testExtendPrimitiveIteratorOfLong(Iterable<Long> iterable)\n\t{\n\t\tIterator<Long> primitive = PrimitiveIterable.unboxLong(iterable).iterator();\n\t\tFunctionalIterator<Long> actual = Reducible.extend(primitive);\n\t\tassertTrue(actual instanceof FunctionalPrimitiveIterator);\n\t}\n\n\t@Test\n\t@DisplayName(\"extend() with null throws NullPointerException.\")\n\tvoid testExtendIterable_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.extend((Iterable<?>) null));\n\t}\n\n\t@Test\n\t@DisplayName(\"extend() with null throws NullPointerException.\")\n\tvoid testExtendIterator_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.extend((Iterator<?>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterables\")\n\tvoid testConcatIterable(Iterable<?> iterable)\n\t{\n\t\tArrayList<Object> expected = new ArrayList<>();\n\t\titerable.forEach(expected::add);\n\t\titerable.forEach(expected::add);\n\t\tFunctionalIterable<Object> actual = Reducible.concat(List.of(iterable, iterable));\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterables\")\n\tvoid testConcatIterator(Iterable<?> iterable)\n\t{\n\t\tArrayList<Object> expected = new ArrayList<>();\n\t\titerable.forEach(expected::add);\n\t\titerable.forEach(expected::add);\n\t\tFunctionalIterator<Object> actual = Reducible.concat(List.of(iterable.iterator(), iterable.iterator()).iterator());\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@Test\n\tvoid testConcatIterable_Empty()\n\t{\n\t\tEmptyIterable<Object> expected = EmptyIterable.of();\n\t\tIterable<Object> actual = Reducible.concat(EmptyIterable.of());\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testConcatIterator_Empty()\n\t{\n\t\tEmptyIterator<Object> expected = EmptyIterator.of();\n\t\tIterator<Object> actual = Reducible.concat(EmptyIterator.of());\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testConcatIterable_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concat((Iterable<Iterable<?>>) null));\n\t}\n\n\t@Test\n\tvoid testConcatIterator_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concat((Iterator<Iterator<?>>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\tvoid testConcatIterable_NullValues(Iterable<Iterable<?>> iterable)\n\t{\n\t\tFunctionalIterable<Object> result = Reducible.concat(iterable);\n\t\tassertThrows(NullPointerException.class, result::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\tvoid testConcatIterator_NullValues(Iterable<Iterator<?>> iterable)\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concat(iterable.iterator()));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\tvoid testConcatDoubleIterable(Iterable<Double> iterable)\n\t{\n\t\tArrayList<Double> expectedBoxed = new ArrayList<>();\n\t\titerable.forEach(expectedBoxed::add);\n\t\titerable.forEach(expectedBoxed::add);\n\t\tFunctionalPrimitiveIterable.OfDouble expected = Reducible.unboxDouble(expectedBoxed);\n\t\tFunctionalPrimitiveIterable.OfDouble unboxed = Reducible.unboxDouble(iterable);\n\t\tFunctionalPrimitiveIterable.OfDouble actual = Reducible.concatDouble(List.of(unboxed, unboxed));\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\tvoid testConcatDoubleIterator(Iterable<Double> iterable)\n\t{\n\t\tArrayList<Double> expectedBoxed = new ArrayList<>();\n\t\titerable.forEach(expectedBoxed::add);\n\t\titerable.forEach(expectedBoxed::add);\n\t\tFunctionalPrimitiveIterable.OfDouble expected = Reducible.unboxDouble(expectedBoxed);\n\t\tFunctionalPrimitiveIterable.OfDouble unboxed = Reducible.unboxDouble(iterable);\n\t\tFunctionalPrimitiveIterator.OfDouble actual = Reducible.concatDouble(List.of(unboxed.iterator(), unboxed.iterator()).iterator());\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@Test\n\tvoid testConcatDoubleIterable_Empty()\n\t{\n\t\tEmptyIterable.OfDouble expected = EmptyIterable.ofDouble();\n\t\tFunctionalPrimitiveIterable.OfDouble actual = Reducible.concatDouble(EmptyIterable.of());\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testConcatDoubleIterator_Empty()\n\t{\n\t\tEmptyIterator.OfDouble expected = EmptyIterator.ofDouble();\n\t\tFunctionalPrimitiveIterator.OfDouble actual = Reducible.concatDouble(EmptyIterator.of());\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testConcatDoubleIterable_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concatDouble((Iterable<PrimitiveIterable.OfDouble>) null));\n\t}\n\n\t@Test\n\tvoid testConcatDoubleIterator_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concat((Iterator<PrimitiveIterator.OfDouble>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\tvoid testConcatDoubleIterable_NullValues(Iterable<PrimitiveIterable.OfDouble> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfDouble result = Reducible.concatDouble(iterable);\n\t\tassertThrows(NullPointerException.class, result::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\tvoid testConcatDoubleIterator_NullValues(Iterable<PrimitiveIterator.OfDouble> iterable)\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concatDouble(iterable.iterator()));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\tvoid testConcatIntIterable(Iterable<Integer> iterable)\n\t{\n\t\tArrayList<Integer> expectedBoxed = new ArrayList<>();\n\t\titerable.forEach(expectedBoxed::add);\n\t\titerable.forEach(expectedBoxed::add);\n\t\tFunctionalPrimitiveIterable.OfInt expected = Reducible.unboxInt(expectedBoxed);\n\t\tFunctionalPrimitiveIterable.OfInt unboxed = Reducible.unboxInt(iterable);\n\t\tFunctionalPrimitiveIterable.OfInt actual = Reducible.concatInt(List.of(unboxed, unboxed));\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\tvoid testConcatIntIterator(Iterable<Integer> iterable)\n\t{\n\t\tArrayList<Integer> expectedBoxed = new ArrayList<>();\n\t\titerable.forEach(expectedBoxed::add);\n\t\titerable.forEach(expectedBoxed::add);\n\t\tFunctionalPrimitiveIterable.OfInt expected = Reducible.unboxInt(expectedBoxed);\n\t\tFunctionalPrimitiveIterable.OfInt unboxed = Reducible.unboxInt(iterable);\n\t\tFunctionalPrimitiveIterator.OfInt actual = Reducible.concatInt(List.of(unboxed.iterator(), unboxed.iterator()).iterator());\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@Test\n\tvoid testConcatIntIterable_Empty()\n\t{\n\t\tEmptyIterable.OfInt expected = EmptyIterable.ofInt();\n\t\tFunctionalPrimitiveIterable.OfInt actual = Reducible.concatInt(EmptyIterable.of());\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testConcatIntIterator_Empty()\n\t{\n\t\tEmptyIterator.OfInt expected = EmptyIterator.ofInt();\n\t\tFunctionalPrimitiveIterator.OfInt actual = Reducible.concatInt(EmptyIterator.of());\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testConcatIntIterable_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concatInt((Iterable<PrimitiveIterable.OfInt>) null));\n\t}\n\n\t@Test\n\tvoid testConcatIntIterator_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concat((Iterator<PrimitiveIterator.OfInt>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\tvoid testConcatIntIterable_NullValues(Iterable<PrimitiveIterable.OfInt> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfInt result = Reducible.concatInt(iterable);\n\t\tassertThrows(NullPointerException.class, result::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\tvoid testConcatIntIterator_NullValues(Iterable<PrimitiveIterator.OfInt> iterable)\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concatInt(iterable.iterator()));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\tvoid testConcatLongIterable(Iterable<Long> iterable)\n\t{\n\t\tArrayList<Long> expectedBoxed = new ArrayList<>();\n\t\titerable.forEach(expectedBoxed::add);\n\t\titerable.forEach(expectedBoxed::add);\n\t\tFunctionalPrimitiveIterable.OfLong expected = Reducible.unboxLong(expectedBoxed);\n\t\tFunctionalPrimitiveIterable.OfLong unboxed = Reducible.unboxLong(iterable);\n\t\tFunctionalPrimitiveIterable.OfLong actual = Reducible.concatLong(List.of(unboxed, unboxed));\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\tvoid testConcatLongIterator(Iterable<Long> iterable)\n\t{\n\t\tArrayList<Long> expectedBoxed = new ArrayList<>();\n\t\titerable.forEach(expectedBoxed::add);\n\t\titerable.forEach(expectedBoxed::add);\n\t\tFunctionalPrimitiveIterable.OfLong expected = Reducible.unboxLong(expectedBoxed);\n\t\tFunctionalPrimitiveIterable.OfLong unboxed = Reducible.unboxLong(iterable);\n\t\tFunctionalPrimitiveIterator.OfLong actual = Reducible.concatLong(List.of(unboxed.iterator(), unboxed.iterator()).iterator());\n\t\tassertIteratorEquals(expected.iterator(), actual);\n\t}\n\n\t@Test\n\tvoid testConcatLongIterable_Empty()\n\t{\n\t\tEmptyIterable.OfLong expected = EmptyIterable.ofLong();\n\t\tFunctionalPrimitiveIterable.OfLong actual = Reducible.concatLong(EmptyIterable.of());\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testConcatLongIterator_Empty()\n\t{\n\t\tEmptyIterator.OfLong expected = EmptyIterator.ofLong();\n\t\tFunctionalPrimitiveIterator.OfLong actual = Reducible.concatLong(EmptyIterator.of());\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@Test\n\tvoid testConcatLongIterable_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concatLong((Iterable<PrimitiveIterable.OfLong>) null));\n\t}\n\n\t@Test\n\tvoid testConcatLongIterator_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concat((Iterator<PrimitiveIterator.OfLong>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\tvoid testConcatLongIterable_NullValues(Iterable<PrimitiveIterable.OfLong> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfLong result = Reducible.concatLong(iterable);\n\t\tassertThrows(NullPointerException.class, result::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\tvoid testConcatLongIterator_NullValues(Iterable<PrimitiveIterator.OfLong> iterable)\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.concatLong(iterable.iterator()));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\t@DisplayName(\"unboxDouble() yields same sequence as the underlying iterable.\")\n\tvoid testUnboxDoubleIterable(Iterable<Double> iterable)\n\t{\n\t\tPrimitiveIterable.OfDouble expected = PrimitiveIterable.unboxDouble(iterable);\n\t\tFunctionalPrimitiveIterable.OfDouble actual = Reducible.unboxDouble(iterable);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\t@DisplayName(\"unboxDouble() yields same sequence as the underlying iterator.\")\n\tvoid testUnboxDoubleIterator(Iterable<Double> iterable)\n\t{\n\t\tPrimitiveIterator.OfDouble expected = PrimitiveIterable.unboxDouble(iterable.iterator());\n\t\tFunctionalPrimitiveIterator.OfDouble actual = Reducible.unboxDouble(iterable.iterator());\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\t@DisplayName(\"unboxDouble() does not unbox a FunctionalPrimitiveIterable.OfDouble.\")\n\tvoid testUnboxDoubleIterableOfDouble(Iterable<Double> iterable)\n\t{\n\t\tPrimitiveIterable.OfDouble expected = Reducible.extend(PrimitiveIterable.unboxDouble(iterable));\n\t\tFunctionalPrimitiveIterable.OfDouble actual = Reducible.unboxDouble(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesDouble\")\n\t@DisplayName(\"unboxDouble() does not unbox a FunctionalPrimitiveIterator.OfDouble.\")\n\tvoid testUnboxDoubleIteratorOfDouble(Iterable<Double> iterable)\n\t{\n\t\tPrimitiveIterator.OfDouble expected = Reducible.extend(PrimitiveIterable.unboxDouble(iterable.iterator()));\n\t\tFunctionalPrimitiveIterator.OfDouble actual = Reducible.unboxDouble(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@Test\n\t@DisplayName(\"unboxDouble() with null throws NullPointerException.\")\n\tvoid testUnboxDoubleIterable_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.unboxDouble((Iterable<Double>) null));\n\t}\n\n\t@Test\n\t@DisplayName(\"unboxDouble() with null throws NullPointerException.\")\n\tvoid testUnboxDoubleIterator_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.unboxDouble((Iterator<Double>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\t@DisplayName(\"unboxDouble() with an Iterable containing null throws NullPointerException.\")\n\tvoid testUnboxDoubleIterable_NullValues(Iterable<Double> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfDouble primitive = Reducible.unboxDouble(iterable);\n\t\tassertThrows(NullPointerException.class, primitive::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\t@DisplayName(\"unboxDouble() with an Iterator containing null throws NullPointerException.\")\n\tvoid testUnboxDoubleIterator_NullValues(Iterable<Double> iterable)\n\t{\n\t\tFunctionalPrimitiveIterator.OfDouble primitive = Reducible.unboxDouble(iterable.iterator());\n\t\tassertThrows(NullPointerException.class, primitive::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\t@DisplayName(\"unboxInt() yields same sequence as the underlying iterable.\")\n\tvoid testUnboxIntIterable(Iterable<Integer> iterable)\n\t{\n\t\tPrimitiveIterable.OfInt expected = PrimitiveIterable.unboxInt(iterable);\n\t\tFunctionalPrimitiveIterable.OfInt actual = Reducible.unboxInt(iterable);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\t@DisplayName(\"unboxInt() yields same sequence as the underlying iterator.\")\n\tvoid testUnboxIntIterator(Iterable<Integer> iterable)\n\t{\n\t\tPrimitiveIterator.OfInt expected = PrimitiveIterable.unboxInt(iterable.iterator());\n\t\tFunctionalPrimitiveIterator.OfInt actual = Reducible.unboxInt(iterable.iterator());\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\t@DisplayName(\"unboxInt() does not unbox a FunctionalPrimitiveIterable.OfInt.\")\n\tvoid testUnboxIntIterableOfInt(Iterable<Integer> iterable)\n\t{\n\t\tPrimitiveIterable.OfInt expected = Reducible.extend(PrimitiveIterable.unboxInt(iterable));\n\t\tFunctionalPrimitiveIterable.OfInt actual = Reducible.unboxInt(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesInt\")\n\t@DisplayName(\"unboxInt() does not unbox a FunctionalPrimitiveIterator.OfInt.\")\n\tvoid testUnboxIntIteratorOfInt(Iterable<Integer> iterable)\n\t{\n\t\tPrimitiveIterator.OfInt expected = Reducible.extend(PrimitiveIterable.unboxInt(iterable.iterator()));\n\t\tFunctionalPrimitiveIterator.OfInt actual = Reducible.unboxInt(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@Test\n\t@DisplayName(\"unboxInt() with null throws NullPointerException.\")\n\tvoid testUnboxIntIterable_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.unboxInt((Iterable<Integer>) null));\n\t}\n\n\t@Test\n\t@DisplayName(\"unboxInt() with null throws NullPointerException.\")\n\tvoid testUnboxIntIterator_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.unboxInt((Iterator<Integer>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\t@DisplayName(\"unboxInt() with an Iterable containing null throws NullPointerException.\")\n\tvoid testUnboxIntIterable_NullValues(Iterable<Integer> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfInt primitive = Reducible.unboxInt(iterable);\n\t\tassertThrows(NullPointerException.class, primitive::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\t@DisplayName(\"unboxInt() with an Iterator containing null throws NullPointerException.\")\n\tvoid testUnboxIntIterator_NullValues(Iterable<Integer> iterable)\n\t{\n\t\tFunctionalPrimitiveIterator.OfInt primitive = Reducible.unboxInt(iterable.iterator());\n\t\tassertThrows(NullPointerException.class, primitive::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\t@DisplayName(\"unboxLong() yields same sequence as the underlying iterable.\")\n\tvoid testUnboxLongIterable(Iterable<Long> iterable)\n\t{\n\t\tPrimitiveIterable.OfLong expected = PrimitiveIterable.unboxLong(iterable);\n\t\tFunctionalPrimitiveIterable.OfLong actual = Reducible.unboxLong(iterable);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\t@DisplayName(\"unboxLong() yields same sequence as the underlying iterator.\")\n\tvoid testUnboxLong(Iterable<Long> iterable)\n\t{\n\t\tPrimitiveIterator.OfLong expected = PrimitiveIterable.unboxLong(iterable.iterator());\n\t\tFunctionalPrimitiveIterator.OfLong actual = Reducible.unboxLong(iterable.iterator());\n\t\tassertIteratorEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\t@DisplayName(\"unboxLong() does not unbox a FunctionalPrimitiveIterable.OfDouble.\")\n\tvoid testUnboxLongIterableOfLong(Iterable<Long> iterable)\n\t{\n\t\tPrimitiveIterable.OfLong expected = Reducible.extend(PrimitiveIterable.unboxLong(iterable));\n\t\tFunctionalPrimitiveIterable.OfLong actual = Reducible.unboxLong(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesLong\")\n\t@DisplayName(\"unboxLong() does not unbox a FunctionalPrimitiveIterator.OfDouble.\")\n\tvoid testUnboxLongIteratorOfLong(Iterable<Long> iterable)\n\t{\n\t\tPrimitiveIterator.OfLong expected = Reducible.extend(PrimitiveIterable.unboxLong(iterable.iterator()));\n\t\tFunctionalPrimitiveIterator.OfLong actual = Reducible.unboxLong(expected);\n\t\tassertSame(expected, actual);\n\t}\n\n\t@Test\n\t@DisplayName(\"unboxLong() with null throws NullPointerException.\")\n\tvoid testUnboxLongIterable_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.unboxLong((Iterable<Long>) null));\n\t}\n\n\t@Test\n\t@DisplayName(\"unboxLong() with null throws NullPointerException.\")\n\tvoid testUnboxLongIterator_Null()\n\t{\n\t\tassertThrows(NullPointerException.class, () -> Reducible.unboxLong((Iterator<Long>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\t@DisplayName(\"unboxInt() with an Iterable containing null throws NullPointerException.\")\n\tvoid testUnboxLongIterable_NullValues(Iterable<Long> iterable)\n\t{\n\t\tFunctionalPrimitiveIterable.OfLong primitive = Reducible.unboxLong(iterable);\n\t\tassertThrows(NullPointerException.class, primitive::consume);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getIterablesNull\")\n\t@DisplayName(\"unboxInt() with an Iterator containing null throws NullPointerException.\")\n\tvoid testUnboxLongIterator_NullValues(Iterable<Long> iterable)\n\t{\n\t\tFunctionalPrimitiveIterator.OfLong primitive = Reducible.unboxLong(iterable.iterator());\n\t\tassertThrows(NullPointerException.class, primitive::consume);\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/ReducibleTest.java",
    "content": "package common.iterable;\n\nimport common.functions.DoubleObjToDoubleFunction;\nimport common.functions.IntObjToIntFunction;\nimport common.functions.LongObjToLongFunction;\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.Arguments;\nimport org.junit.jupiter.params.provider.MethodSource;\n\nimport java.util.*;\nimport java.util.function.*;\nimport java.util.stream.Stream;\n\nimport static org.junit.jupiter.api.Assertions.*;\n\npublic interface ReducibleTest<E, T extends Reducible<E, ?>>\n{\n\tdefault T getAnyReducible()\n\t{\n\t\tOptional<Supplier<T>> any = getReducibles().findAny();\n\t\tassert any.isPresent();\n\t\treturn any.get().get();\n\t}\n\n\tdefault Stream<Supplier<T>> getReducibles()\n\t{\n\t\treturn Stream.concat(Stream.concat(getEmptyReducibles(), getSingletonReducibles()), getMultitonReducibles());\n\t}\n\n\tStream<Supplier<T>> getDuplicatesReducibles();\n\n\tStream<Supplier<T>> getEmptyReducibles();\n\n\tStream<Supplier<T>> getSingletonReducibles();\n\n\tStream<Supplier<T>> getMultitonReducibles();\n\n\tIterable<Object> getExcluded(T reducible);\n\n\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCollectArray(Supplier<T> supplier)\n\t{\n\t\tint n = (int) supplier.get().count();\n\t\tObject[] expected = new Object[n];\n\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\tsupplier.get().forEach(e -> expected[index.nextInt()] = e);\n\t\tObject[] actual = supplier.get().collect((E[]) new Object[n]);  // exploit that E[] is Object[] at runtime\n\t\tassertArrayEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCollectArrayOffset(Supplier<T> supplier)\n\t{\n\t\tint n = (int) supplier.get().count(), offset = 2, tail = 3;\n\t\tObject[] expected = new Object[offset + n + tail];\n\t\tRange.RangeIterator index = new Range(offset, offset + n).iterator();\n\t\tsupplier.get().forEach(e -> expected[index.nextInt()] = e);\n\t\tObject[] actual = supplier.get().collect((E[]) new Object[offset + n + tail], offset);  // exploit that E[] is Object[] at runtime\n\t\tassertArrayEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCollectCollection(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = new ArrayList<>();\n\t\tsupplier.get().forEach(expected::add);\n\t\tList<E> actual = supplier.get().collect(new ArrayList<>());\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCollectSupplier(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = new ArrayList<>();\n\t\tsupplier.get().forEach(expected::add);\n\t\tList<E> actual = supplier.get().collect((Supplier<? extends List<E>>) ArrayList::new);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tdefault void testCollect_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.collect((E[]) null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.collect(null, 0));\n\t\tassertThrows(NullPointerException.class, () -> reducible.collect((Collection<? super E>) null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.collect((Supplier<? extends Collection<? super E>>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCollectAndCountArray(Supplier<T> supplier)\n\t{\n\t\tint n = (int) supplier.get().count(), tail = 3;\n\t\tObject[] expected = new Object[n + tail];\n\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\tsupplier.get().forEach(e -> expected[index.nextInt()] = e);\n\t\tObject[] actual = new Object[n + tail];\n\t\tlong count = supplier.get().collectAndCount((E[]) actual);  // exploit that E[] is Object[] at runtime\n\t\tassertEquals(n, count);\n\t\tassertArrayEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCollectAndCountArrayOffset(Supplier<T> supplier)\n\t{\n\t\tint n = (int) supplier.get().count(), offset = 2, tail = 3;\n\t\tObject[] expected = new Object[offset + n + tail];\n\t\tRange.RangeIterator index = new Range(offset, offset + n).iterator();\n\t\tsupplier.get().forEach(e -> expected[index.nextInt()] = e);\n\t\tObject[] actual = new Object[offset + n + tail];\n\t\tlong count = supplier.get().collectAndCount((E[]) actual, offset);  // exploit that E[] is Object[] at runtime\n\t\tassertEquals(n, count);\n\t\tassertArrayEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCollectAndCountCollection(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = new ArrayList<>();\n\t\tsupplier.get().forEach(expected::add);\n\t\tList<E> actual = new ArrayList<>();\n\t\tlong count = supplier.get().collectAndCount(actual);\n\t\tassertEquals(expected.size(), count);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tdefault void testCollectAndCount_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((E[]) null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount(null, 0));\n\t\tassertThrows(NullPointerException.class, () -> reducible.collectAndCount((Collection<? super E>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getReducibles\", \"getDuplicatesReducibles\"})\n\tdefault void testCollectDistinct(Supplier<T> supplier)\n\t{\n\t\tSet<E> expected = new HashSet<>();\n\t\tsupplier.get().forEach(expected::add);\n\t\tList<E> actual = supplier.get().collectDistinct().collect(new ArrayList<>());\n\t\tassertTrue(expected.containsAll(actual), \"actual =< expected\");\n\t\tassertTrue(actual.containsAll(expected), \"actual >= expected\");\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testConsume(Supplier<T> supplier)\n\t{\n\t\t// Just test that consume yields the receiver.\n\t\t// There is no way to test whether consume does anything beyond this.\n\t\tT expected = supplier.get();\n\t\tReducible<E, ?> actual = expected.consume();\n\t\tassertSame(expected, actual);\n\t}\n\n\tvoid testConcat(Supplier<T> supplier);\n\n\t@ParameterizedTest\n\t@MethodSource({\"getReducibles\", \"getDuplicatesReducibles\"})\n\tdefault void testDistinct(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = new ArrayList<>();\n\t\tsupplier.get().forEach(e -> {if (! expected.contains(e)) expected.add(e);});\n\t\tList<E> actual = supplier.get().distinct().collect(new ArrayList<>());\n\t\tassertEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getReducibles\", \"getDuplicatesReducibles\"})\n\tdefault void testDedupe(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = new ArrayList<>();\n\t\tsupplier.get().forEach(e -> {\n\t\t\tObject last = expected.isEmpty() ? new Object() : expected.get(expected.size() - 1);\n\t\t\tif (! Objects.equals(last, e)) {\n\t\t\t\texpected.add(e);\n\t\t\t}\n\t\t});\n\t\tList<Object> actual = supplier.get().dedupe().collect(new ArrayList<>());\n\t\tassertEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testFilter(Supplier<T> supplier)\n\t{\n\t\tArrayList<E> expected = new ArrayList<>();\n\t\tint n = supplier.get().reduce(0, (int c, E e) -> {\n\t\t\tif (c % 2 == 0) expected.add(e);\n\t\t\treturn ++c;\n\t\t});\n\t\tRange.RangeIterator index = new Range(n).iterator();\n\t\tReducible<E, ?> actual = supplier.get().filter(e -> index.nextInt() % 2 == 0);\n\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t}\n\n\t@Test\n\tdefault void testFilter_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.filter(null));\n\t}\n\n\tvoid testFlatMap(Supplier<T> supplier);\n\n\tvoid testFlatMapToDouble(Supplier<T> supplier);\n\n\tvoid testFlatMapToInt(Supplier<T> supplier);\n\n\tvoid testFlatMapToLong(Supplier<T> supplier);\n\n\tvoid testFlatMapToNull(Supplier<T> supplier);\n\n\tvoid testFlatMap_Null();\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testMap(Supplier<T> supplier)\n\t{\n\t\tString prefix = \"Item: \";\n\t\tList<String> expected = new ArrayList<>();\n\t\tsupplier.get().forEach(e -> expected.add(prefix + e));\n\t\tReducible<String, ?> actual = supplier.get().map(e -> prefix + e);\n\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testMapToDouble(Supplier<T> supplier)\n\t{\n\t\tRange range = new Range((int) supplier.get().count());\n\t\tFunctionalIterable<Double> expected = range.map((int i) -> (double) i);\n\t\tRange.RangeIterator index = range.iterator();\n\t\tPrimitiveReducible.OfDouble<?> actual = supplier.get().mapToDouble(e -> index.next());\n\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testMapToInt(Supplier<T> supplier)\n\t{\n\t\tRange expected = new Range((int) supplier.get().count());\n\t\tRange.RangeIterator index = expected.iterator();\n\t\tPrimitiveReducible.OfInt<?> actual = supplier.get().mapToInt(e -> index.next());\n\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testMapToLong(Supplier<T> supplier)\n\t{\n\t\tRange range = new Range((int) supplier.get().count());\n\t\tFunctionalIterable<Long> expected = range.map((int i) -> (long) i);\n\t\tRange.RangeIterator index = range.iterator();\n\t\tPrimitiveReducible.OfLong<?> actual = supplier.get().mapToLong(e -> index.next());\n\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t}\n\n\t@Test\n\tdefault void testMap_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.map(null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.mapToDouble(null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.mapToInt(null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.mapToLong(null));\n\t}\n\n\tvoid testForEach(Supplier<T> supplier);\n\n\t@Test\n\tdefault void testForEach_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.forEach(null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getEmptyReducibles\")\n\tdefault void testIsEmpty_Empty(Supplier<T> supplier)\n\t{\n\t\tassertTrue(supplier.get().isEmpty());\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\tdefault void testIsEmpty_NonEmpty(Supplier<T> supplier)\n\t{\n\t\tassertFalse(supplier.get().isEmpty());\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getEmptyReducibles\")\n\tdefault void testReduceBinaryOperatorOfE_Empty(Supplier<T> supplier)\n\t{\n\t\tBinaryOperator<E> nop = (res, each) -> null;\n\t\tOptional<E> actual = supplier.get().reduce(nop);\n\t\tassertEquals(Optional.empty(), actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getSingletonReducibles\")\n\tdefault void testReduceBinaryOperatorOfE_Singleton(Supplier<T> supplier)\n\t{\n\t\tBinaryOperator<E> nop = (res, each) -> null;\n\t\tE expected = supplier.get().detect(e -> true);\n\t\tif (expected == null) {\n\t\t\tassertThrows(NullPointerException.class, () -> supplier.get().reduce(nop));\n\t\t} else {\n\t\t\tOptional<E> actual = supplier.get().reduce(nop);\n\t\t\tassertTrue(actual.isPresent());\n\t\t\tassertEquals(expected, actual.get());\n\t\t}\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getMultitonReducibles\")\n\tdefault void testReduceBinaryOperatorOfE_Multiton(Supplier<T> supplier)\n\t{\n\t\tArrayList<E> expected = supplier.get().collect(new ArrayList<>());\n\t\tList<E> actual = new ArrayList<>();\n\t\tE probe = (E) new Object(); // \"unique\" value, exploit that E is Object at runtime\n\t\tBinaryOperator<E> collect = (res, each) -> {\n\t\t\tif (actual.isEmpty()) {\n\t\t\t\tactual.add(res);\n\t\t\t\tactual.add(each);\n\t\t\t\treturn (E) probe;\n\t\t\t} else {\n\t\t\t\tactual.add(each);\n\t\t\t\treturn res;\n\t\t\t}\n\t\t};\n\t\tOptional<E> result = supplier.get().reduce(collect);\n\t\tassertTrue(result.isPresent());\n\t\tassertEquals(probe, result.get());\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getMultitonReducibles\")\n\tdefault void testReduceBinary_ResultNull(Supplier<T> supplier)\n\t{\n\t\tReducible<E, ?> reducible = supplier.get();\n\t\tassertThrows(NullPointerException.class, () -> reducible.reduce((res, each) -> null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testReduce(Supplier<T> supplier)\n\t{\n\t\tArrayList<E> expected = supplier.get().collect(new ArrayList<>());\n\t\tBiFunction<List<E>, E, List<E>> collect = (seq, each) -> {seq.add(each); return seq;};\n\t\tList<E> actual = supplier.get().reduce(new ArrayList<>(), collect);\n\t\tassertIterableEquals(expected, actual);\n\t\tassertDoesNotThrow(() -> supplier.get().reduce(null, (obj, each) -> null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testReduceDouble(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = supplier.get().collect(new ArrayList<>());\n\t\tList<E> actual = new ArrayList<>();\n\t\tDoubleObjToDoubleFunction<E> collect = (res, each) -> {actual.add(each); return res;};\n\t\tdouble result = supplier.get().reduce(Double.MIN_VALUE, collect);\n\t\tassertEquals(Double.MIN_VALUE, result);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testReduceInt(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = supplier.get().collect(new ArrayList<>());\n\t\tList<E> actual = new ArrayList<>();\n\t\tIntObjToIntFunction<E> collect = (res, each) -> {actual.add(each); return res;};\n\t\tint result = supplier.get().reduce(Integer.MIN_VALUE, collect);\n\t\tassertEquals(Integer.MIN_VALUE, result);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testReduceLong(Supplier<T> supplier)\n\t{\n\t\tList<E> expected = supplier.get().collect(new ArrayList<>());\n\t\tList<E> actual = new ArrayList<>();\n\t\tLongObjToLongFunction<E> collect = (res, each) -> {actual.add(each); return res;};\n\t\tlong result = supplier.get().reduce(Long.MIN_VALUE, collect);\n\t\tassertEquals(Long.MIN_VALUE, result);\n\t\tassertIterableEquals(expected, actual);\n\t}\n\n\t@Test\n\tdefault void testReduce_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(new Object(),null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0.0, null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0, (IntObjToIntFunction<? super E>) null));\n\t\tassertThrows(NullPointerException.class, () -> reducible.reduce(0L, (LongObjToLongFunction<? super E>) null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testNonNull(Supplier<T> supplier)\n\t{\n\t\tList<Object> expected = new ArrayList<>();\n\t\tsupplier.get().forEach(e -> {if (e != null) expected.add(e);});\n\t\tReducible<E, ?> actual = supplier.get().nonNull();\n\t\tassertIterableEquals(expected, actual.collect(new ArrayList<>()));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\tdefault void testAllMatch(Supplier<T> supplier)\n\t{\n\t\t// match all elements\n\t\tassertTrue(supplier.get().allMatch(each -> true), \"Expected allMatch() == true\");\n\t\t// match not all elements\n\t\tPredicate<E> matchNotAll = new Predicate<>() {\n\t\t\t// match: no element if singleton, otherwise every odd element\n\t\t\tboolean flag = supplier.get().count() == 1;\n\t\t\t@Override\n\t\t\tpublic boolean test(E t)\n\t\t\t{\n\t\t\t\tflag = !flag;\n\t\t\t\treturn flag;\n\t\t\t}\n\t\t};\n\t\tassertFalse(supplier.get().allMatch(matchNotAll), \"Expected allMatch() == false\");\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getEmptyReducibles\")\n\tdefault void testAllMatch_Empty(Supplier<T> supplier)\n\t{\n\t\tReducible<E, ?> reducible = supplier.get();\n\t\tassertTrue(reducible.allMatch(each -> false), \"Exepted allMatch() == true if reducible is empty\");\n\t}\n\n\t@Test\n\tdefault void testAllMatch_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.allMatch(null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\tdefault void testAnyMatch(Supplier<T> supplier)\n\t{\n\t\t// match no element\n\t\tassertFalse(supplier.get().anyMatch(each -> false), \"Expected anyMatch() == false\");\n\t\t// match some elements\n\t\tPredicate<E> matchSome = new Predicate<>() {\n\t\t\t// match: first element if singleton, otherwise every even element\n\t\t\tboolean flag = supplier.get().count() > 1;\n\t\t\t@Override\n\t\t\tpublic boolean test(E t)\n\t\t\t{\n\t\t\t\tflag = !flag;\n\t\t\t\treturn flag;\n\t\t\t}\n\t\t};\n\t\tassertTrue(supplier.get().anyMatch(matchSome), \"Expected anyMatch() == true\");\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getEmptyReducibles\")\n\tdefault void testAnyMatch_Empty(Supplier<T> supplier)\n\t{\n\t\tReducible<E, ?> reducible = supplier.get();\n\t\tassertFalse(reducible.anyMatch(each -> true), \"Exepted anyMatch() == false if reducible is empty\");\n\t}\n\n\t@Test\n\tdefault void testAnyMatch_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.anyMatch(null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource({\"getSingletonReducibles\", \"getMultitonReducibles\"})\n\tdefault void testNoneMatch(Supplier<T> supplier)\n\t{\n\t\t// match no element\n\t\tassertTrue(supplier.get().noneMatch(each -> false), \"Expected noneMatch() == true\");\n\t\t// match some elements\n\t\tPredicate<E> matchSome = new Predicate<>() {\n\t\t\t// match: first element if singleton, otherwise every even element\n\t\t\tboolean flag = supplier.get().count() > 1;\n\t\t\t@Override\n\t\t\tpublic boolean test(E t)\n\t\t\t{\n\t\t\t\tflag = !flag;\n\t\t\t\treturn flag;\n\t\t\t}\n\t\t};\n\t\tassertFalse(supplier.get().noneMatch(matchSome), \"Expected noneMatch() == false\");\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getEmptyReducibles\")\n\tdefault void testNoneMatch_Empty(Supplier<T> supplier)\n\t{\n\t\tReducible<E, ?> reducible = supplier.get();\n\t\tassertTrue(reducible.allMatch(each -> false), \"Exepted noneMatch() == false if iterator is empty\");\n\t}\n\n\t@Test\n\tdefault void testNoneMatch_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.noneMatch(null));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testAsString(Supplier<T> supplier)\n\t{\n\t\tString expected = \"[\" + supplier.get().reduce(\"\", (str, each) -> str + (str.isEmpty() ? \"\" : \", \") + each) + \"]\";\n\t\tString actual = supplier.get().asString();\n\t\tassertEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testContains(Supplier<T> supplier)\n\t{\n\t\tArrayList<E> elements = supplier.get().collect(new ArrayList<>());\n\t\tfor (E each : elements) {\n\t\t\tassertTrue(supplier.get().contains(each), \"Expected contains(\" + each + \") == true\");\n\t\t}\n\t\tfor (Object each : getExcluded(supplier.get())) {\n\t\t\tassertFalse(supplier.get().contains(each), \"Expected contains(\" + each + \") == false\");\n\t\t}\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCount(Supplier<T> supplier)\n\t{\n\t\tArrayList<E> elements = supplier.get().collect(new ArrayList<>());\n\t\tlong expected = elements.size();\n\t\tlong actual = supplier.get().count();\n\t\tassertEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testCountPredicate(Supplier<T> supplier)\n\t{\n\t\tArrayList<E> elements = supplier.get().collect(new ArrayList<>());\n\t\tlong expected = (elements.size() + 1) / 2;\n\t\tPredicate<E> odd = new Predicate<>() {\n\t\t\tint i = 1;\n\t\t\t@Override\n\t\t\tpublic boolean test(E t)\n\t\t\t{\n\t\t\t\treturn i++ % 2 == 1;\n\t\t\t}\n\t\t};\n\t\tlong actual = supplier.get().count(odd);\n\t\tassertEquals(expected, actual);\n\t}\n\n\t@Test\n\tdefault void testCountPredicate_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.count(null));\n\t}\n\n\n\t@ParameterizedTest\n\t@MethodSource(\"getReducibles\")\n\tdefault void testDetect_AllFalse(Supplier<T> supplier)\n\t{\n\t\tReducible<E, ?> reducible = supplier.get();\n\t\tassertThrows(NoSuchElementException.class, () -> reducible.detect(each -> false));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getEmptyReducibles\")\n\tdefault void testDetect_Empty(Supplier<T> supplier)\n\t{\n\t\tReducible<E, ?> reducible = supplier.get();\n\t\tassertThrows(NoSuchElementException.class, () -> reducible.detect(each -> true));\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getSingletonReducibles\")\n\tdefault void testDetect_Singleton(Supplier<T> supplier)\n\t{\n\t\t// match first element\n\t\tE expected = supplier.get().collect(new ArrayList<>()).get(0);\n\t\tE actual = supplier.get().detect(each -> true);\n\t\tassertEquals(expected, actual);\n\t}\n\n\t@ParameterizedTest\n\t@MethodSource(\"getMultitonReducibles\")\n\tdefault void testDetect_Multiton(Supplier<T> supplier)\n\t{\n\t\t// match second element\n\t\tE expected = supplier.get().collect(new ArrayList<>()).get(1);\n\t\tPredicate<E> second = new Predicate<>() {\n\t\t\tboolean flag = true;\n\t\t\t@Override\n\t\t\tpublic boolean test(E each)\n\t\t\t{\n\t\t\t\tflag = !flag;\n\t\t\t\treturn flag;\n\t\t\t}\n\t\t};\n\t\tE actual = supplier.get().detect(second);\n\t\tassertEquals(expected, actual);\n\t}\n\n\t@Test\n\tdefault void testDetect_Null()\n\t{\n\t\tReducible<E, ?> reducible = getAnyReducible();\n\t\tassertThrows(NullPointerException.class, () -> reducible.detect(null));\n\t}\n\n\n\n\tinterface Of<E, T extends Reducible<E, ?>> extends ReducibleTest<E, T>\n\t{\n\t\tT getReducible(Object[] objects);\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn getDuplicatesArraysOfObject().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getEmptyReducibles()\n\t\t{\n\t\t\treturn getEmptyArraysOfObject().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getSingletonReducibles()\n\t\t{\n\t\t\treturn getSingletonArraysOfObject().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Stream<Supplier<T>> getMultitonReducibles()\n\t\t{\n\t\t\treturn getMultitonArraysOfObject().map(args-> () -> getReducible(args));\n\t\t}\n\n\t\t@Override\n\t\tdefault Iterable<Object> getExcluded(T iterable)\n\t\t{\n\t\t\treturn getUniqueObjects();\n\t\t}\n\t}\n\n\n\n\t// Test-data sets\n\n\tdefault Stream<Object[]> getArraysOfObject()\n\t{\n\t\treturn Stream.concat(Stream.concat(getEmptyArraysOfObject(), getSingletonArraysOfObject()), getMultitonArraysOfObject());\n\t}\n\n\t/* Workaround to pass Object[] as argument */\n\tdefault Stream<Arguments> getArraysAsArguments()\n\t{\n\t\treturn getArraysOfObject().map(array -> Arguments.of((Object) array));\n\t}\n\n\tdefault Stream<Object[]> getDuplicatesArraysOfObject()\n\t{\n\t\treturn Stream.of(\n\t\t\t\tnew Object[] {null, null,\n\t\t\t\t\t\t\"first\", \"first\",\n\t\t\t\t\t\t\"second\", \"second\"},\n\t\t\t\tnew Object[] {null, null,\n\t\t\t\t\t\t\"first\", \"first\",\n\t\t\t\t\t\t\"third\", \"third\",\n\t\t\t\t\t\t\"first\", \"first\",\n\t\t\t\t\t\tnull, null});\n\t}\n\n\tdefault Stream<Object[]> getEmptyArraysOfObject()\n\t{\n\t\treturn Stream.<Object[]>of(new Object[] {});\n\t}\n\n\tdefault Stream<Object[]> getSingletonArraysOfObject()\n\t{\n\t\treturn Stream.of(new Object[] {\"first\"},\n\t\t\t\tnew Object[] {null});\n\t}\n\n\tdefault Stream<Object[]> getMultitonArraysOfObject()\n\t{\n\t\treturn Stream.of(new Object[] {\"first\", \"second\", \"third\"},\n\t\t\t\tnew Object[] {null, \"first\", null, \"second\", null, \"third\", null});\n\t}\n\n\t/* Workaround to pass Object[] as argument */\n\tdefault Stream<Arguments> getMultitonArraysAsArguments()\n\t{\n\t\treturn getMultitonArraysOfObject().map(array -> Arguments.of((Object) array));\n\t}\n\n\tdefault List<Object> getUniqueObjects()\n\t{\n\t\treturn List.of(new Object(), new Object(), new Object());\n\t}\n\n\tdefault Stream<double[]> getArraysOfDouble()\n\t{\n\t\treturn Stream.concat(Stream.concat(getEmptyArraysOfDouble(), getSingletonArraysOfDouble()), getMultitonArraysOfDouble());\n\t}\n\n\tdefault Stream<double[]> getDuplicatesArraysOfDouble()\n\t{\n\t\treturn Stream.of(new double[] {-3.5, -3.5,\n\t\t\t\t\t\t-2.0, -2.0,\n\t\t\t\t\t\t-1.0, -1.0,\n\t\t\t\t\t\t-0.0, +0.0,\n\t\t\t\t\t\t+1.0, +1.0,\n\t\t\t\t\t\t+2.0, +2.0,\n\t\t\t\t\t\t+3.5, +3.5},\n\t\t\t\tnew double[] {Double.NaN, Double.NaN,\n\t\t\t\t\t\tDouble.MIN_VALUE, Double.MIN_VALUE,\n\t\t\t\t\t\tDouble.MIN_NORMAL, Double.MIN_NORMAL,\n\t\t\t\t\t\tDouble.MAX_VALUE, Double.MAX_VALUE,\n\t\t\t\t\t\tDouble.NEGATIVE_INFINITY, Double.NEGATIVE_INFINITY,\n\t\t\t\t\t\tDouble.POSITIVE_INFINITY, Double.POSITIVE_INFINITY,\n\t\t\t\t\t\tDouble.NEGATIVE_INFINITY, Double.NEGATIVE_INFINITY,\n\t\t\t\t\t\tDouble.MAX_VALUE, Double.MAX_VALUE,\n\t\t\t\t\t\tDouble.MIN_NORMAL, Double.MIN_NORMAL,\n\t\t\t\t\t\tDouble.MIN_VALUE, Double.MIN_VALUE,\n\t\t\t\t\t\tDouble.NaN, Double.NaN});\n\t}\n\n\tdefault Stream<double[]> getEmptyArraysOfDouble()\n\t{\n\t\treturn Stream.of(new double[] {});\n\t}\n\n\tdefault Stream<double[]> getSingletonArraysOfDouble()\n\t{\n\t\treturn Stream.of(new double[] {1.0});\n\t}\n\n\tdefault Stream<double[]> getMultitonArraysOfDouble()\n\t{\n\t\treturn Stream.of(new double[] {-3.5, -2.0, -1.0, 0.0, 1.0, 2.0, 3.5},\n\t\t\t\tnew double[] {Double.NaN,\n\t\t\t\t\t\tDouble.MIN_VALUE,\n\t\t\t\t\t\tDouble.MIN_NORMAL,\n\t\t\t\t\t\tDouble.MAX_VALUE,\n\t\t\t\t\t\tDouble.NEGATIVE_INFINITY,\n\t\t\t\t\t\tDouble.POSITIVE_INFINITY,});\n\t}\n\n\tdefault List<Double> getExclusionListOfDouble()\n\t{\n\t\tList<Double> excluded = new ArrayList<>();\n\t\texcluded.add(Double.NaN);\n\t\texcluded.add(Double.NEGATIVE_INFINITY);\n\t\texcluded.add(-100000000.0);\n\t\texcluded.add(-10000.0);\n\t\texcluded.add(-100.0);\n\t\texcluded.add(-10.0);\n\t\texcluded.add(-2.0);\n\t\texcluded.add(-1.0);\n\t\texcluded.add(-0.0);\n\t\texcluded.add(+0.0);\n\t\texcluded.add(Double.MIN_VALUE);\n\t\texcluded.add(Double.MIN_NORMAL);\n\t\texcluded.add(1.0);\n\t\texcluded.add(2.0);\n\t\texcluded.add(10.0);\n\t\texcluded.add(100.0);\n\t\texcluded.add(10000.0);\n\t\texcluded.add(100000000.0);\n\t\texcluded.add(Double.MAX_VALUE);\n\t\texcluded.add(Double.POSITIVE_INFINITY);\n\t\treturn excluded;\n\t}\n\n\tdefault Stream<int[]> getArraysOfInt()\n\t{\n\t\treturn Stream.concat(Stream.concat(getEmptyArraysOfInt(), getSingletonArraysOfInt()), getMultitonArraysOfInt());\n\t}\n\n\tdefault Stream<int[]> getDuplicatesArraysOfInt()\n\t{\n\t\treturn Stream.of(new int[] {-3, -3,\n\t\t\t\t\t\t-1, -1,\n\t\t\t\t\t\t-2, -2,\n\t\t\t\t\t\t-0, +0,\n\t\t\t\t\t\t+1, +1,\n\t\t\t\t\t\t+2, +2,\n\t\t\t\t\t\t+3, +3},\n\t\t\t\tnew int[] {Integer.MIN_VALUE, Integer.MIN_VALUE,\n\t\t\t\t\t\tInteger.MAX_VALUE, Integer.MAX_VALUE,\n\t\t\t\t\t\tInteger.MIN_VALUE, Integer.MIN_VALUE});\n\t}\n\n\tdefault Stream<int[]> getEmptyArraysOfInt()\n\t{\n\t\treturn Stream.of(new int[] {});\n\t}\n\n\tdefault Stream<int[]> getSingletonArraysOfInt()\n\t{\n\t\treturn Stream.of(new int[] {1});\n\t}\n\n\tdefault Stream<int[]> getMultitonArraysOfInt()\n\t{\n\t\treturn Stream.of(new int[] {-3, -2, -1, 0, 1, 2, 3},\n\t\t\t\tnew int[] {Integer.MIN_VALUE, Integer.MAX_VALUE});\n\t}\n\n\tdefault List<Integer> getExclusionListOfInt()\n\t{\n\t\tList<Integer> excluded = new ArrayList<>();\n\t\texcluded.add(Integer.MIN_VALUE);\n\t\texcluded.add(-100000000);\n\t\texcluded.add(-10000);\n\t\texcluded.add(-100);\n\t\texcluded.add(-10);\n\t\texcluded.add(-2);\n\t\texcluded.add(-1);\n\t\texcluded.add(0);\n\t\texcluded.add(1);\n\t\texcluded.add(2);\n\t\texcluded.add(10);\n\t\texcluded.add(100);\n\t\texcluded.add(10000);\n\t\texcluded.add(100000000);\n\t\texcluded.add(Integer.MAX_VALUE);\n\t\treturn excluded;\n\t}\n\n\tdefault Stream<long[]> getArraysOfLong()\n\t{\n\t\treturn Stream.concat(Stream.concat(getEmptyArraysOfLong(), getSingletonArraysOfLong()), getMultitonArraysOfLong());\n\t}\n\n\tdefault Stream<long []> getDuplicatesArraysOfLong()\n\t{\n\t\treturn Stream.of(new long [] {-3L, -3L,\n\t\t\t\t\t\t-2L, -2L,\n\t\t\t\t\t\t-1L, -1L,\n\t\t\t\t\t\t-0L, +0L,\n\t\t\t\t\t\t+1L, +1L,\n\t\t\t\t\t\t+2L, +2L,\n\t\t\t\t\t\t+3L, +3L},\n\t\t\t\tnew long[] {Long.MIN_VALUE, Long.MIN_VALUE,\n\t\t\t\t\t\tLong.MAX_VALUE, Long.MAX_VALUE,\n\t\t\t\t\t\tLong.MIN_VALUE, Long.MIN_VALUE});\n\t}\n\n\tdefault Stream<long []> getEmptyArraysOfLong()\n\t{\n\t\treturn Stream.of(new long [] {});\n\t}\n\n\tdefault Stream<long []> getSingletonArraysOfLong()\n\t{\n\t\treturn Stream.of(new long [] {1L});\n\t}\n\n\tdefault Stream<long []> getMultitonArraysOfLong()\n\t{\n\t\treturn Stream.of(new long [] {-3L, -2L, -1L, 0L, 1L, 2L, 3L},\n\t\t\t\tnew long[] {Long.MIN_VALUE, Long.MAX_VALUE});\n\t}\n\n\tdefault List<Long> getExclusionListOfLong()\n\t{\n\t\tList<Long> excluded = new ArrayList<>();\n\t\texcluded.add(Long.MIN_VALUE);\n\t\texcluded.add(-100000000L);\n\t\texcluded.add(-10000L);\n\t\texcluded.add(-100L);\n\t\texcluded.add(-10L);\n\t\texcluded.add(-2L);\n\t\texcluded.add(-1L);\n\t\texcluded.add(0L);\n\t\texcluded.add(1L);\n\t\texcluded.add(2L);\n\t\texcluded.add(10L);\n\t\texcluded.add(100L);\n\t\texcluded.add(10000L);\n\t\texcluded.add(100000000L);\n\t\texcluded.add(Long.MAX_VALUE);\n\t\treturn excluded;\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/SingletonIterableTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.TestInstance;\n\nimport java.util.function.Supplier;\nimport java.util.stream.Stream;\n\ninterface SingletonIterableTest<E, T extends SingletonIterable<E>> extends FunctionalIterableTest<E,T>\n{\n\t@Override\n\tdefault void testAllMatch_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testAnyMatch_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testDetect_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testDetect_Multiton(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testNoneMatch_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testIsEmpty_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testReduceBinary_ResultNull(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */}\n\n\t@Override\n\tdefault void testReduceBinaryOperatorOfE_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testReduceBinaryOperatorOfE_Multiton(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements SingletonIterableTest<Object,SingletonIterable.Of<Object>>, FunctionalIterableTest.Of<Object,SingletonIterable.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic SingletonIterable.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tassert objects.length == 1 : \"singleton array expected\";\n\t\t\treturn new SingletonIterable.Of<>(objects[0]);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.Of<Object>>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.Of<Object>>> getEmptyReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.Of<Object>>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements SingletonIterableTest<Double,SingletonIterable.OfDouble>, FunctionalPrimitiveIterableTest.OfDouble<SingletonIterable.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic SingletonIterable.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 1 : \"singleton array expected\";\n\t\t\treturn new SingletonIterable.OfDouble(numbers[0]);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfDouble>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfDouble>> getEmptyReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfDouble>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatch_Empty(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testAllMatchDoublePredicate_Empty(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectDoublePredicate_Empty(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectDoublePredicate_Multiton(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchDoublePredicate_Empty(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Empty(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Multiton(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testSum_Empty(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Empty(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Empty(Supplier<SingletonIterable.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements SingletonIterableTest<Integer,SingletonIterable.OfInt>, FunctionalPrimitiveIterableTest.OfInt<SingletonIterable.OfInt>\n\t{\n\t\t@Override\n\t\tpublic SingletonIterable.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 1 : \"singleton array expected\";\n\t\t\treturn new SingletonIterable.OfInt(numbers[0]);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfInt>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfInt>> getEmptyReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfInt>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatch_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testAllMatchIntPredicate_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectIntPredicate_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectIntPredicate_Multiton(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchIntPredicate_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Multiton(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceIntBinaryOperator_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceIntBinaryOperator_Multiton(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Multiton(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Empty(Supplier<SingletonIterable.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements SingletonIterableTest<Long,SingletonIterable.OfLong>, FunctionalPrimitiveIterableTest.OfLong<SingletonIterable.OfLong>\n\t{\n\t\t@Override\n\t\tpublic SingletonIterable.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 1 : \"singleton array expected\";\n\t\t\treturn new SingletonIterable.OfLong(numbers[0]);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfLong>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfLong>> getEmptyReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterable.OfLong>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatchLongPredicate_Empty(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectLongPredicate_Empty(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectLongPredicate_Multiton(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchLongPredicate_Empty(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Empty(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Multiton(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Empty(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Empty(Supplier<SingletonIterable.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/common/iterable/SingletonIteratorTest.java",
    "content": "package common.iterable;\n\nimport org.junit.jupiter.api.Nested;\nimport org.junit.jupiter.api.TestInstance;\n\nimport java.util.function.Supplier;\nimport java.util.stream.Stream;\n\ninterface SingletonIteratorTest<E, T extends SingletonIterator<E>> extends FunctionalIteratorTest<E,T>\n{\n\t@Override\n\tdefault void testAllMatch_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testAnyMatch_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testDetect_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testDetect_Multiton(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testNoneMatch_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testIsEmpty_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testReduceBinary_ResultNull(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */}\n\n\t@Override\n\tdefault void testReduceBinaryOperatorOfE_Empty(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\t@Override\n\tdefault void testReduceBinaryOperatorOfE_Multiton(Supplier<T> supplier)\n\t{ /* singletons hold exactly one value */ }\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass Of implements SingletonIteratorTest<Object,SingletonIterator.Of<Object>>, FunctionalIteratorTest.Of<Object,SingletonIterator.Of<Object>>\n\t{\n\t\t@Override\n\t\tpublic SingletonIterator.Of<Object> getReducible(Object[] objects)\n\t\t{\n\t\t\tassert objects.length == 1 : \"singleton array expected\";\n\t\t\treturn new SingletonIterator.Of<>(objects[0]);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.Of<Object>>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.Of<Object>>> getEmptyReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.Of<Object>>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfDouble implements SingletonIteratorTest<Double,SingletonIterator.OfDouble>, FunctionalPrimitiveIteratorTest.OfDouble<SingletonIterator.OfDouble>\n\t{\n\t\t@Override\n\t\tpublic SingletonIterator.OfDouble getReducible(double[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 1 : \"singleton array expected\";\n\t\t\treturn new SingletonIterator.OfDouble(numbers[0]);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfDouble>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfDouble>> getEmptyReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfDouble>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatch_Empty(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testAllMatchDoublePredicate_Empty(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectDoublePredicate_Empty(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectDoublePredicate_Multiton(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchDoublePredicate_Empty(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Empty(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Multiton(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testSum_Empty(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Empty(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Empty(Supplier<SingletonIterator.OfDouble> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfInt implements SingletonIteratorTest<Integer,SingletonIterator.OfInt>, FunctionalPrimitiveIteratorTest.OfInt<SingletonIterator.OfInt>\n\t{\n\t\t@Override\n\t\tpublic SingletonIterator.OfInt getReducible(int[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 1 : \"singleton array expected\";\n\t\t\treturn new SingletonIterator.OfInt(numbers[0]);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfInt>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfInt>> getEmptyReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfInt>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatch_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testAllMatchIntPredicate_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectIntPredicate_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectIntPredicate_Multiton(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchIntPredicate_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceDoubleBinaryOperator_Multiton(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceIntBinaryOperator_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceIntBinaryOperator_Multiton(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Multiton(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Empty(Supplier<SingletonIterator.OfInt> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\t}\n\n\n\n\t@Nested\n\t@TestInstance(TestInstance.Lifecycle.PER_CLASS)\n\tclass OfLong implements SingletonIteratorTest<Long,SingletonIterator.OfLong>, FunctionalPrimitiveIteratorTest.OfLong<SingletonIterator.OfLong>\n\t{\n\t\t@Override\n\t\tpublic SingletonIterator.OfLong getReducible(long[] numbers)\n\t\t{\n\t\t\tassert numbers.length == 1 : \"singleton array expected\";\n\t\t\treturn new SingletonIterator.OfLong(numbers[0]);\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfLong>> getDuplicatesReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfLong>> getEmptyReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic Stream<Supplier<SingletonIterator.OfLong>> getMultitonReducibles()\n\t\t{\n\t\t\treturn Stream.empty();\n\t\t}\n\n\t\t@Override\n\t\tpublic void testAllMatchLongPredicate_Empty(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectLongPredicate_Empty(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testDetectLongPredicate_Multiton(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Multiton(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Multiton(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testNoneMatchLongPredicate_Empty(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Empty(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testReduceLongBinaryOperator_Multiton(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMin_Empty(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\n\t\t@Override\n\t\tpublic void testMax_Empty(Supplier<SingletonIterator.OfLong> supplier)\n\t\t{ /* singletons hold exactly one value */ }\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/csv/CsvReaderTest.java",
    "content": "package csv;\n\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.ValueSource;\n\nimport java.io.IOException;\nimport java.io.StringReader;\nimport java.util.ArrayList;\nimport java.util.Iterator;\n\nimport static csv.BasicReader.CR;\nimport static csv.BasicReader.LF;\nimport static csv.CsvReader.COMMA;\nimport static csv.CsvReader.CR_LF;\nimport static org.junit.jupiter.api.Assertions.*;\n\n/**\n * Test whether {@link CsvReader} behaves according to to RFC 4180.\n *\n * @see <a href=\"https://tools.ietf.org/html/rfc4180\">RFC 4180</a>\n */\npublic class CsvReaderTest\n{\n\t// Test parameters\n\n\t@ParameterizedTest\n\t@ValueSource(ints = {',', ',', ' ', '\\t'})\n\tpublic void testFieldSeparator(int eof) throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsDefault();\n\n\t\tBasicReader csv = getCsvDefault().convert(',').to(eof);\n\n\t\tCsvReader reader = new CsvReader(csv, false, true, true, eof, CR_LF);\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@ParameterizedTest\n\t@ValueSource(ints = {CR, LF, CR_LF})\n\tpublic void testLineSeparator(int eol) throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsDefault();\n\n\t\tBasicReader csv = getCsvDefault();\n\t\tif (eol != CR_LF) {\n\t\t\tcsv = csv.convert(CR, LF).to(eol);\n\t\t}\n\n\t\tCsvReader reader = new CsvReader(csv, false, true, true, COMMA, eol);\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testLineSeparatorErrorUnknown()\n\t{\n\t\tassertThrows(IllegalArgumentException.class, () -> new CsvReader(null, COMMA, 5));\n\t}\n\n\t@Test\n\tpublic void testFixNumFieldsTrue() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader readerSame = new CsvReader(getCsvEmptyLastLine());\n\t\tassertDoesNotThrow(() -> readerSame.iterator().forEachRemaining(r -> {return;}));\n\t}\n\n\t@Test\n\tpublic void testFixNumFieldsTrueErrorDifferentNumberOfFields() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader readerDiff = new CsvReader(getCsvDiffNumFields());\n\t\tassertThrows(CsvFormatException.class, () -> readerDiff.iterator().forEachRemaining(r -> {return;}));\n\t}\n\n\t@Test\n\tpublic void testFixNumFieldsFalse() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader readerDiff = new CsvReader(getCsvDiffNumFields(), true, false, true);\n\t\tassertDoesNotThrow(() -> readerDiff.iterator().forEachRemaining(r -> {return;}));\n\t}\n\n\t@Test\n\tpublic void testHasHeaderTrue() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsDefault();\n\n\t\tCsvReader reader = new CsvReader(getCsvDefault());\n\t\tassertArrayEquals(expected.remove(0), reader.getHeader());\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testHasHeaderTrueErrorEmptyCsv() throws IOException, CsvFormatException\n\t{\n\t\tassertThrows(CsvFormatException.class, () -> new CsvReader(getCsvEmpty()));\n\n\t\tassertThrows(CsvFormatException.class, () -> new CsvReader(getCsvNoRecords()));\n\t}\n\n\t@Test\n\tpublic void testHasHeaderTrueErrorNoRecords() throws IOException, CsvFormatException\n\t{\n\t\tassertThrows(CsvFormatException.class, () -> new CsvReader(getCsvNoRecords()));\n\t}\n\n\t@Test\n\tpublic void testHasHeaderFalse() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsDefault();\n\n\t\tCsvReader reader = new CsvReader(getCsvDefault(), false, true, true);\n\t\tassertArrayEquals(null, reader.getHeader());\n\t\tassertRecordsEquals(expected, reader);\n\n\t\tassertDoesNotThrow(() -> new CsvReader(getCsvEmpty(), false, true, true));\n\n\t\tassertDoesNotThrow(() -> new CsvReader(getCsvNoRecords(), false, true, true));\n\t}\n\n\t@Test\n\tpublic void testDistinctFieldNamesTrue() throws IOException, CsvFormatException\n\t{\n\t\tassertDoesNotThrow(() -> new CsvReader(getCsvDefault()));\n\t}\n\n\t@Test\n\tpublic void testDistinctFieldNamesTrueErrorSameName() throws IOException, CsvFormatException\n\t{\n\t\tassertThrows(CsvFormatException.class, () -> new CsvReader(getCsvSameNames()));\n\t}\n\n\t@Test\n\tpublic void testDistinctFieldNamesFalse() throws IOException, CsvFormatException\n\t{\n\t\tBasicReader sameNames = getCsvSameNames();\n\t\tassertDoesNotThrow(() -> new CsvReader(sameNames, true, true, false));\n\t}\n\n\t// Test csv contents\n\n\t@Test\n\tpublic void testDoubleQuotes() throws IOException, CsvFormatException\n\t{\n\t\tBasicReader csv = getBasicReader(\"\\\"\\\"\\\"quo\\\"\\\"tes\\\"\\\"\\\",misc\");\n\t\tCsvReader reader = new CsvReader(csv, false, true, true);\n\t\tassertArrayEquals(new String[] {\"\\\"quo\\\"tes\\\"\", \"misc\"}, reader.nextRecord());\n\t\tassertFalse(reader.hasNextRecord());\n\t}\n\n\t@Test\n\tpublic void testDoubleQuotesErrorInNonQuotedField() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader reader = new CsvReader(getBasicReader(\"quo\\\"\\\"tes,misc\"), false, true, true);\n\t\tassertThrows(CsvFormatException.class, reader::nextRecord);\n\t}\n\n\t@Test\n\tpublic void testDoubleQuotesErrorNotQuoted() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader reader = new CsvReader(getBasicReader(\"\\\"quo\\\"tes,misc\\\"\"), false, true, true);\n\t\tassertThrows(CsvFormatException.class, reader::nextRecord);\n\t}\n\n\n\t@Test\n\tpublic void testEmptyCsv() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = new ArrayList<>();\n\t\texpected.add(new String[]{\"\"});\n\n\t\tCsvReader reader = new CsvReader(getCsvEmpty(), false, true, true);\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testEmptyFields() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsEmptyFields();\n\n\t\tCsvReader reader = new CsvReader(getCsvEmptyFields());\n\t\tassertArrayEquals(expected.remove(0), reader.header);\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testEndWithEmptyLine() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsDefault();\n\n\t\tCsvReader reader = new CsvReader(getCsvEmptyLastLine());\n\t\tassertArrayEquals(expected.remove(0), reader.getHeader());\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testEndWithoutNoEmptyLine() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsDefault();\n\n\t\tCsvReader reader = new CsvReader(getCsvDefault());\n\t\tassertArrayEquals(expected.remove(0), reader.getHeader());\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testGetNumberOfFieldsNotFixed() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader reader = new CsvReader(getCsvDefault(), false, false, true);\n\t\tassertEquals(-1, reader.getNumberOfFields());\n\t\twhile (reader.hasNextRecord()) {\n\t\t\treader.nextRecord();\n\t\t\tassertEquals(-1, reader.getNumberOfFields());\n\t\t}\n\t}\n\n\t@Test\n\tpublic void testGetNumberOfFieldsFixedWithHeader() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader reader = new CsvReader(getCsvDefault());\n\t\tassertEquals(2, reader.getNumberOfFields());\n\t\twhile (reader.hasNextRecord()) {\n\t\t\treader.nextRecord();\n\t\t\tassertEquals(2, reader.getNumberOfFields());\n\t\t}\n\t}\n\n\t@Test\n\tpublic void testGetNumberOfFieldsFixedWithoutHeader() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader readerFixedWithoutHeader = new CsvReader(getCsvDefault(), false, true, true);\n\t\tassertEquals(0, readerFixedWithoutHeader.getNumberOfFields());\n\t\twhile (readerFixedWithoutHeader.hasNextRecord()) {\n\t\t\treaderFixedWithoutHeader.nextRecord();\n\t\t\tassertEquals(2, readerFixedWithoutHeader.getNumberOfFields());\n\t\t}\n\t}\n\n\t@Test\n\tpublic void testQuotedFields() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsDefault();\n\n\t\tCsvReader reader = new CsvReader(getCsvQuotedFields());\n\t\tassertArrayEquals(expected.remove(0), reader.header);\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testQuotedFieldsComma() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsComma();\n\n\t\tCsvReader reader = new CsvReader(getCsvComma());\n\t\tassertArrayEquals(expected.remove(0), reader.header);\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testQuotedFieldsCrLf() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsCrLf();\n\n\t\tCsvReader reader = new CsvReader(getCsvCrLf());\n\t\tassertArrayEquals(expected.remove(0), reader.header);\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t@Test\n\tpublic void testQuotedFieldsErrorNotClosed() throws IOException, CsvFormatException\n\t{\n\t\tCsvReader reader = new CsvReader(getBasicReader(\"\\\"quotes,misc\"), false, true, true);\n\t\tassertThrows(CsvFormatException.class, reader::nextRecord);\n\t}\n\n\t@Test\n\tpublic void testQuotedEmptyFields() throws IOException, CsvFormatException\n\t{\n\t\tArrayList<String[]> expected = getRecordsEmptyFields();\n\n\t\tCsvReader reader = new CsvReader(getCsvQuotedEmptyFields());\n\t\tassertArrayEquals(expected.remove(0), reader.header);\n\t\tassertRecordsEquals(expected, reader);\n\t}\n\n\t// CSV test data\n\n\tpublic static ArrayList<String[]> getRecordsDefault()\n\t{\n\t\tArrayList<String[]> expected = new ArrayList<>();\n\t\texpected.add(new String[]{\"h1\", \"h2\"});\n\t\texpected.add(new String[]{\"f11\", \"f12\"});\n\t\texpected.add(new String[]{\"f21\", \"f22\"});\n\t\treturn expected;\n\t}\n\n\tpublic static ArrayList<String[]> getRecordsEmptyFields()\n\t{\n\t\tArrayList<String[]> expected = new ArrayList<>();\n\t\texpected.add(new String[]{\"h1\", \"\", \"h3\"});\n\t\texpected.add(new String[]{\"\", \"f12\", \"f13\"});\n\t\texpected.add(new String[]{\"f21\", \"\", \"f23\"});\n\t\texpected.add(new String[]{\"f31\", \"f32\", \"\"});\n\t\treturn expected;\n\t}\n\n\tpublic static ArrayList<String[]> getRecordsComma()\n\t{\n\t\tArrayList<String[]> expected = new ArrayList<>();\n\t\texpected.add(new String[]{\"h1\", \"h2\"});\n\t\texpected.add(new String[]{\"f1,1\", \"f12\"});\n\t\texpected.add(new String[]{\"f21\", \"f2,2\"});\n\t\treturn expected;\n\t}\n\n\tpublic static ArrayList<String[]> getRecordsCrLf()\n\t{\n\t\tArrayList<String[]> expected = new ArrayList<>();\n\t\texpected.add(new String[]{\"h1\", \"h2\"});\n\t\texpected.add(new String[]{\"f1\\r\\n1\", \"f12\"});\n\t\texpected.add(new String[]{\"f21\", \"f2\\r\\n2\"});\n\t\treturn expected;\n\t}\n\n\tpublic static BasicReader getCsvDefault()\n\t{\n\t\treturn getBasicReader(\"h1,h2\\r\\nf11,f12\\r\\nf21,f22\");\n\t}\n\n\tpublic static BasicReader getCsvEmpty()\n\t{\n\t\treturn getBasicReader(\"\");\n\t}\n\n\tpublic static BasicReader getCsvEmptyFields()\n\t{\n\t\treturn getBasicReader(\"h1,,h3\\r\\n,f12,f13\\r\\nf21,,f23\\r\\nf31,f32,\");\n\t}\n\n\tpublic static BasicReader getCsvComma()\n\t{\n\t\treturn getBasicReader(\"h1,h2\\r\\n\\\"f1,1\\\",f12\\r\\nf21,\\\"f2,2\\\"\");\n\t}\n\n\tpublic static BasicReader getCsvCrLf()\n\t{\n\t\treturn getBasicReader(\"h1,h2\\r\\n\\\"f1\\r\\n1\\\",f12\\r\\nf21,\\\"f2\\r\\n2\\\"\");\n\t}\n\n\tpublic static BasicReader getCsvQuotedFields()\n\t{\n\t\treturn getBasicReader(\"\\\"h1\\\",\\\"h2\\\"\\r\\n\\\"f11\\\",\\\"f12\\\"\\r\\n\\\"f21\\\",\\\"f22\\\"\");\n\t}\n\n\tpublic static BasicReader getCsvQuotedEmptyFields()\n\t{\n\t\treturn getBasicReader(\"\\\"h1\\\",\\\"\\\",\\\"h3\\\"\\r\\n\\\"\\\",\\\"f12\\\",\\\"f13\\\"\\r\\n\\\"f21\\\",\\\"\\\",\\\"f23\\\"\\r\\n\\\"f31\\\",\\\"f32\\\",\\\"\\\"\");\n\t}\n\n\tpublic static BasicReader getCsvEmptyLastLine()\n\t{\n\t\treturn getBasicReader(\"h1,h2\\r\\nf11,f12\\r\\nf21,f22\\r\\n\");\n\t}\n\n\tpublic static BasicReader getCsvNoRecords()\n\t{\n\t\treturn getBasicReader(\"h1,h2\\r\\n\");\n\t}\n\n\tpublic static BasicReader getCsvDiffNumFields()\n\t{\n\t\treturn getBasicReader(\"h1,h2\\r\\nf11,f12\\r\\nf21\\r\\n\");\n\t}\n\n\tpublic static BasicReader getCsvSameNames()\n\t{\n\t\treturn getBasicReader(\"h1,h1\\r\\nf11,f12\\r\\nf21\\r\\n\");\n\t}\n\n\tpublic static BasicReader.Wrapper getBasicReader(String csv)\n\t{\n\t\treturn BasicReader.wrap(new StringReader(csv));\n\t}\n\n\t// Assert methods\n\n\tpublic static void assertRecordsEquals(Iterable<String[]> expected, Iterable<String[]> actual)\n\t{\n\t\tIterator<String[]> expectedIterator = expected.iterator();\n\t\tIterator<String[]> actualIterator = actual.iterator();\n\t\twhile (expectedIterator.hasNext() && actualIterator.hasNext()) {\n\t\t\tassertArrayEquals(expectedIterator.next(), actualIterator.next());\n\t\t}\n\t\tassertFalse(expectedIterator.hasNext());\n\t\tassertFalse(actualIterator.hasNext());\n\t}\n}"
  },
  {
    "path": "prism/unit-tests/param/BigRationalTest.java",
    "content": "package param;\n\nimport org.junit.jupiter.api.Test;\n\nimport java.math.BigInteger;\nimport java.util.BitSet;\n\nimport static org.junit.jupiter.api.Assertions.assertEquals;\n\npublic class BigRationalTest\n{\n\t@Test\n\tpublic void testBigRationalDouble()\n\t{\n\t\t// constants\n\t\tassertEquals(BigRational.ZERO, new BigRational(0.0));\n\t\tassertEquals(BigRational.ONE, new BigRational(1.0));\n\t\tassertEquals(BigRational.ONE.negate(), new BigRational(-1.0));\n\t\tassertEquals(BigRational.HALF, new BigRational(0.5));\n\t\tassertEquals(BigRational.HALF.negate(), new BigRational(-0.5));\n\n\t\t// double +/- 0.1: +/- 0x1.999999999999ap-4\n\t\tBigRational pointOne = new BigRational(new BigInteger(\"1999999999999a\", 16), BigInteger.ONE.shiftLeft(4+52));\n\t\tassertEquals(pointOne, new BigRational(0.1));\n\t\tassertEquals(pointOne.negate(), new BigRational(-0.1));\n\n\t\t// largest/smallest fraction: +/- 0x1.fffffffffffffp51\n\t\tBigRational maxFrac = new BigRational(new BigInteger(\"1fffffffffffff\", 16), BigInteger.TWO);\n\t\tassertEquals(maxFrac, new BigRational(0x1.fffffffffffffp51));\n\t\tassertEquals(maxFrac.negate(), new BigRational(-0x1.fffffffffffffp51));\n\n\t\t// largest/smallest non-fraction: +/- 1.0p52\n\t\tBigRational nonFrac = new BigRational(new BigInteger(\"10000000000000\", 16));\n\t\tassertEquals(nonFrac, new BigRational(0x1.0p52));\n\t\tassertEquals(nonFrac.negate(), new BigRational(-0x1.0p52));\n\n\t\t// largest/smallest integer: +/- 0x1.fffffffffffffp+1023\n\t\tBigRational maxInt = new BigRational(new BigInteger(\"1fffffffffffff\", 16).shiftLeft(1023-52));\n\t\tassertEquals(maxInt, new BigRational(Double.MAX_VALUE));\n\t\tassertEquals(maxInt.negate(), new BigRational(-Double.MAX_VALUE));\n\n\t\t// smallest absolute value:  +/- 0x0.0000000000001p-1022\n\t\tBigRational absMin = new BigRational(BigInteger.ONE, BigInteger.ONE.shiftLeft(1022+52));\n\t\tassertEquals(absMin, new BigRational(Double.MIN_VALUE));\n\t\tassertEquals(absMin.negate(), new BigRational(-Double.MIN_VALUE));\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/parser/ast/ExpressionBinaryOpShortCircuitTest.java",
    "content": "package parser.ast;\n\nimport static org.junit.jupiter.api.Assertions.*;\nimport static parser.ast.ExpressionBinaryOp.IMPLIES;\nimport static parser.ast.ExpressionBinaryOp.OR;\nimport static parser.ast.ExpressionBinaryOp.AND;\n\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.CsvSource;\nimport parser.EvaluateContext;\nimport parser.visitor.ASTVisitor;\nimport parser.visitor.DeepCopy;\nimport prism.PrismLangException;\n\nimport java.util.Objects;\n\n/**\n * Test whether short-circuiting is exploited during expression evaluation.\n */\npublic class ExpressionBinaryOpShortCircuitTest\n{\n\t// Dummy context for #evaluate\n\tEvaluateContext ec = new EvaluateContext()\n\t{\n\t\t@Override\n\t\tpublic Object getVarValue(String name, int index)\n\t\t{\n\t\t\treturn null;\n\t\t}\n\t};\n\n\t@ParameterizedTest\n\t@CsvSource({\"false, false\", \"false, true\", \"true, false\", \"true, true\"})\n\tpublic void testEvaluateImplies(boolean v1, boolean v2) throws PrismLangException\n\t{\n\t\tExpressionMock op1 = new ExpressionMock(v1);\n\t\tExpressionMock op2 = new ExpressionMock(v2);\n\n\t\tassertEquals(!v1 || v2, new ExpressionBinaryOp(IMPLIES, op1, op2).evaluate(ec));\n\t}\n\n\t@ParameterizedTest\n\t@CsvSource({\"false, false\", \"false, true\"})\n\tpublic void testShortCircuitImplies(boolean v1, boolean v2) throws PrismLangException\n\t{\n\t\tExpressionMock op1 = new ExpressionMock(v1);\n\t\tExpressionMock op2 = new ExpressionMock(v2);\n\n\t\tnew ExpressionBinaryOp(IMPLIES, op1, op2).evaluate(ec);\n\t\tassertFalse(op1.isEvaluated() && op2.isEvaluated());\n\t}\n\n\t@ParameterizedTest\n\t@CsvSource({\"false, false\", \"false, true\", \"true, false\", \"true, true\"})\n\tpublic void testEvaluateOr(boolean v1, boolean v2) throws PrismLangException\n\t{\n\t\tExpressionMock op1 = new ExpressionMock(v1);\n\t\tExpressionMock op2 = new ExpressionMock(v2);\n\n\t\tassertEquals(v1 || v2, new ExpressionBinaryOp(OR, op1, op2).evaluate(ec));\n\t}\n\n\t@ParameterizedTest\n\t@CsvSource({\"true, false\", \"true, true\"})\n\tpublic void testShortCircuitOr(boolean v1, boolean v2) throws PrismLangException\n\t{\n\t\tExpressionMock op1 = new ExpressionMock(v1);\n\t\tExpressionMock op2 = new ExpressionMock(v2);\n\n\t\tnew ExpressionBinaryOp(OR, op1, op2).evaluate(ec);\n\t\tassertFalse(op1.isEvaluated() && op2.isEvaluated());\n\t}\n\n\t@ParameterizedTest\n\t@CsvSource({\"false, false\", \"false, true\", \"true, false\", \"true, true\"})\n\tpublic void testEvaluateAnd(boolean v1, boolean v2) throws PrismLangException\n\t{\n\t\tExpressionMock op1 = new ExpressionMock(v1);\n\t\tExpressionMock op2 = new ExpressionMock(v2);\n\n\t\tassertEquals(v1 && v2, new ExpressionBinaryOp(AND, op1, op2).evaluate(ec));\n\t}\n\n\t@ParameterizedTest\n\t@CsvSource({\"false, false\", \"false, true\"})\n\tpublic void testShortCircuitAnd(boolean v1, boolean v2) throws PrismLangException\n\t{\n\t\tExpressionMock op1 = new ExpressionMock(v1);\n\t\tExpressionMock op2 = new ExpressionMock(v2);\n\n\t\tnew ExpressionBinaryOp(AND, op1, op2).evaluate(ec);\n\t\tassertFalse(op1.isEvaluated() && op2.isEvaluated());\n\t}\n\n\n\t/**\n\t * Mocked expression signaling whether #evaluate was invoked or not.\n\t */\n\tpublic static class ExpressionMock extends Expression\n\t{\n\t\tprotected boolean evaluated = false;\n\t\tprotected Object value;\n\n\t\tpublic ExpressionMock(Object value)\n\t\t{\n\t\t\tthis.value = Objects.requireNonNull(value);\n\t\t}\n\n\t\tpublic boolean isEvaluated()\n\t\t{\n\t\t\treturn evaluated;\n\t\t}\n\n\t\t@Override\n\t\tpublic Object accept(ASTVisitor v) throws PrismLangException\n\t\t{\n\t\t\treturn null;\n\t\t}\n\n\t\t@Override\n\t\tpublic ExpressionMock deepCopy(DeepCopy copier)\n\t\t{\n\t\t\treturn this;\n\t\t}\n\n\t\t@Override\n\t\tpublic String toString()\n\t\t{\n\t\t\treturn \"Evaluated? \" + evaluated;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isConstant()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean isProposition()\n\t\t{\n\t\t\treturn true;\n\t\t}\n\n\t\t@Override\n\t\tpublic Object evaluate(EvaluateContext ec) throws PrismLangException\n\t\t{\n\t\t\tevaluated = true;\n\t\t\treturn value;\n\t\t}\n\n\t\t@Override\n\t\tpublic boolean returnsSingleValue()\n\t\t{\n\t\t\treturn false;\n\t\t}\n\n\t\t@Override\n\t\tpublic Expression deepCopy()\n\t\t{\n\t\t\treturn this;\n\t\t}\n\t}\n}\n"
  },
  {
    "path": "prism/unit-tests/prism/PrismUtilsTest.java",
    "content": "package prism;\n\nimport static org.junit.jupiter.api.Assertions.assertEquals;\nimport static prism.PrismUtils.formatDouble;\n\nimport org.junit.jupiter.api.Test;\nimport org.junit.jupiter.params.ParameterizedTest;\nimport org.junit.jupiter.params.provider.ValueSource;\n\npublic class PrismUtilsTest\n{\n\t@Test\n\tpublic void testCompareVersions()\n\t{\n\t\t String v[] =  { \"1\", \"2.0\", \"2.1-dev\", \"2.1-dev.r6666\", \"2.1-dev1\", \"2.1-dev2\", \"2.1.alpha\", \"2.1.alpha.r5555\", \"2.1.alpha.r5557\", \"2.1.beta\", \"2.1.beta4\", \"2.1\", \"2.1.post\", \"2.1.post1\", \"2.1.post2\", \"2.1.2\", \"2.9\", \"3\", \"3.4\"};\n\t\t for (int i = 0; i < v.length; i++) {\n\t\t\t for (int j = 0; j < v.length; j++) {\n\t\t\t\t int d = PrismUtils.compareVersions(v[i], v[j]);\n\t\t\t\t assertEquals(Integer.compare(i, j), d, v[i] + \" ? \" + v[j]);\n\t\t\t }\n\t\t }\n\t}\n\n\t@Test\n\tpublic void testCompareVersionsLegacyDotDevIsPost()\n\t{\n\t\tassertEquals(0, PrismUtils.compareVersions(\"2.1.dev\", \"2.1.post\"));\n\t\tassertEquals(0, PrismUtils.compareVersions(\"2.1.dev2\", \"2.1.post2\"));\n\t\tassertEquals(1, PrismUtils.compareVersions(\"2.1.dev\", \"2.1\"));\n\t\tassertEquals(-1, PrismUtils.compareVersions(\"2.1-dev\", \"2.1\"));\n\t}\n\n\t@Test\n\tpublic void testCompareVersionsSupportsDashSeparator()\n\t{\n\t\tassertEquals(0, PrismUtils.compareVersions(\"2.1.1-beta\", \"2.1.1.beta\"));\n\t\tassertEquals(0, PrismUtils.compareVersions(\"2.1-alpha-r5555\", \"2.1.alpha.r5555\"));\n\t\tassertEquals(-1, PrismUtils.compareVersions(\"2.1.1-beta\", \"2.1.1\"));\n\t\tassertEquals(-1, PrismUtils.compareVersions(\"2.1.1-dev1\", \"2.1.1\"));\n\t\tassertEquals(1, PrismUtils.compareVersions(\"2.1.1-post1\", \"2.1.1\"));\n\t}\n\n\t@Test\n\tpublic void testFormatDouble()\n\t{\n\t\t// Special values\n\t\tassertEquals(\"NaN\", formatDouble(Double.NaN));\n\t\tassertEquals(\"-Infinity\", formatDouble(Double.NEGATIVE_INFINITY));\n\t\tassertEquals(\"Infinity\", formatDouble(Double.POSITIVE_INFINITY));\n\t\t// Rounding if number of significant digits > precision\n\t\tassertEquals(\"123457\", formatDouble(6, 123456.7));\n\t\tassertEquals(\"1.23457e-05\", formatDouble(6, 0.00001234567));\n\t\t// Small numbers\n\t\tassertEquals(\"0.0001\", formatDouble(6, 0.0001));\n\t\tassertEquals(\"1e-05\", formatDouble(6, 0.00001));\n\t\tassertEquals(\"1.23456e-05\", formatDouble(6, 0.0000123456));\n\t\t// Big numbers\n\t\tassertEquals(\"999999\", formatDouble(6, 999999.0));\n\t\tassertEquals(\"1e+06\", formatDouble(6, 999999.9));\n\t\tassertEquals(\"1.23457e+06\", formatDouble(6, 1234567.8));\n\t}\n\n\t@ParameterizedTest\n\t@ValueSource(doubles = {Double.NaN, Double.NEGATIVE_INFINITY, Double.POSITIVE_INFINITY, Double.MIN_VALUE, Double.MIN_NORMAL, Double.MAX_VALUE})\n\tpublic void testFormatDoubleDefaultPrecision(double d)\n\t{\n\t\tString serialized = PrismUtils.formatDouble(d);\n\t\tdouble parsed = Double.parseDouble(serialized);\n\t\tassertEquals(d, parsed);\n\t}\n}\n"
  },
  {
    "path": "prism-examples/README.txt",
    "content": "This directory contains a selection of examples for PRISM.\r\nEach example is in a separate subdirectory, and these are\r\ngrouped by type of model (e.g. DTMC, CTMC, MDP).\r\nFor every one, there is a README file, giving more information,\r\nand an auto file, which lists the command-line instructions\r\nthat can be used to run PRISM on the example.\r\n"
  },
  {
    "path": "prism-examples/ctmcs/cell/README.txt",
    "content": "This case study is based on a single cell in a wireless communication network. It is taken from [HMPT00].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/cell.php\r\n\r\n=====================================================================================\r\n\r\n[HMPT00]\r\nG. Haring, R. Marie, R. Puigjaner and K. Trivedi\r\nLoss formulae and their application to optimization for cellular networks\r\nIEEE Transaction on Vehicular Technology, 50(3):664 -673, 2000\r\n"
  },
  {
    "path": "prism-examples/ctmcs/cell/auto",
    "content": "#!/bin/csh\n\nforeach N ( 50 100 200 300 400 500 )\n\tprism cell.sm cell.csl -const N=$N,T=0.5 -sor\nend\n"
  },
  {
    "path": "prism-examples/ctmcs/cell/cell.csl",
    "content": "const double T; // time bound\n\n// the maximum probability that a hand off call can be dropped within t time units (assuming a guarded channel is free)\nP=?[ true U<=T (n=N) {n<N}{max} ]\n\n// the maximum probability that a call can be dropped within t time units (assuming a non-guarded channel is free)\nP=?[ true U<=T (n>=N*0.8) {n<N*0.8}{max} ]\n\n// the minimum probability that a cell will be accepted within T time units (assuming no channels are free)\nP=?[ true U<=T (n<N*0.8) {n=N}{min} ]\n\n// the expected number of calls at time T\nR{\"calls\"}=? [ I=T ]\n\n// the probability that in the long run any call can be dropped\nS=? [ n<N*0.8 ]\n\n// the expected number calls in the cell in the long run\nR{\"calls\"}=? [ S ]\n\n\n"
  },
  {
    "path": "prism-examples/ctmcs/cell/cell.sm",
    "content": "// single cell in wireless communication network [HMPT01]\n// gxn/dxp 5/3/01\n\nctmc\n\nconst int N; // N - number of channels\nconst double lambda1=49; // arrival rate of new calls\nconst double lambda2=21; // arrival rate of hand-off calls\nconst double mu=1; // departure rate of calls\n\nmodule cell\n\t\n\tn : [0..N]; // number of calls in the cell\n\t\n\t// arrival of new call\n\t[] (n<N*0.8) -> lambda1 : (n'=n+1);\n\t// arrival of hand of call\n\t[] (n<N) -> lambda2 : (n'=n+1);\n\t// completion of call or mobile departs cell\n\t[] (n>0) -> n*mu : (n'=n-1);\n\t\nendmodule\n\n// rewards - number calls in the cell\nrewards \"calls\"\n\ttrue : n;\nendrewards\n"
  },
  {
    "path": "prism-examples/ctmcs/cluster/README.txt",
    "content": "This case study is based on a dependable cluster of workstations, taken from [HHK00].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/cluster.php\r\n\r\n=====================================================================================\r\n\r\n[HHK00]\r\nB. Haverkort, H. Hermanns and J.-P. Katoen\r\nOn the use of model checking techniques for dependability evaluation\r\nIn Proc. 19th IEEE Symposium on Reliable Distributed Systems (SRDS'00), 228-237, 2000\r\n"
  },
  {
    "path": "prism-examples/ctmcs/cluster/auto",
    "content": "#!/bin/csh\n\nforeach N (4 8 16 32) #64 128 256 512)\n\tprism cluster.sm cluster.csl -const N=$N,T=10 -jor\nend\n"
  },
  {
    "path": "prism-examples/ctmcs/cluster/cluster.csl",
    "content": "// Properties based on those from [HHK00]\n\nconst double T;\n\n// In the long run, the probability that premium QoS will be delivered\nS=? [ \"premium\" ]\n\n// In the long run, the chance that QoS is below minimum\nS=? [ !\"minimum\" ]\n\n// The system will always be able to offer premium QoS at some point in the future\nP>=1 [ true U \"premium\" ]\n\n// The chance that QoS drops below minimum quality within T time units\n// (from the initial state)\nP=? [ true U<=T !\"minimum\" ]\n\n// If facing insufficient QoS, the maximum probability of facing\n// the same problem after T time units\nP=? [ true U[T,T] !\"minimum\"  {!\"minimum\"}{max} ]\n\n// The minimum probability of going from minimum QoS to premium QoS\n// within T time units\nP=? [ true U<=T \"premium\" {\"minimum\"}{min} ]\n\n// The minimum probability of going from minimum QoS to premium QoS\n// within T time units without violating the minimum QoS constraint along the way\nP=? [ \"minimum\" U<=T \"premium\" {\"minimum\"}{min} ]\n\n// The maximum probability that it takes more than T time units\n// to recover from insufficient QoS\nP=? [ !\"minimum\" U>=T \"minimum\" {!\"minimum\"}{max} ]\n\n// The minimum percentage of operational workstations at time T\n// when starting from below minimum QoS\nR{\"percent_op\"}=?[ I=T {!\"minimum\"}{min} ]\n\n// The expected time (from the initial state)\n// that the system spends below minimum QoS until time T\nR{\"time_not_min\"}=?[ C<=T ]\n\n// The expected number of repairs by time T (starting in the initial state)\nR{\"num_repairs\"}=?[ C<=T ]\n\n"
  },
  {
    "path": "prism-examples/ctmcs/cluster/cluster.sm",
    "content": "// Workstation cluster [HHK00]\n// dxp/gxn 11/01/00\n\nctmc\n\nconst int N; // Number of workstations in each cluster\nconst int left_mx = N; // Number of work stations in left cluster\nconst int right_mx = N; // Number of work stations in right cluster\n\n// Failure rates\nconst double ws_fail = 1/500; // Single workstation: average time to fail = 500 hrs\nconst double switch_fail = 1/4000; // Switch: average time to fail = 4000 hrs\nconst double line_fail = 1/5000; // Backbone: average time to fail = 5000 hrs\n\n// Left cluster\nmodule Left \n\t\n\tleft_n : [0..left_mx] init left_mx; // Number of workstations operational\n\tleft : bool; // Being repaired?\n\t\n\t[startLeft] !left & (left_n<left_mx) -> 1 : (left'=true);\n\t[repairLeft] left & (left_n<left_mx) -> 1 : (left'=false) & (left_n'=left_n+1);\n\t[] (left_n>0) -> ws_fail*left_n : (left_n'=left_n-1);\n\t\nendmodule\n\n// Right cluster\nmodule Right = Left[left_n=right_n,\n                    left=right,\n                    left_mx=right_mx,\n                    startLeft=startRight,\n                    repairLeft=repairRight ]\nendmodule\n\n// Repair unit\nmodule Repairman\n\t\n\tr : bool; // Repairing?\n\t\n\t[startLeft]    !r -> 10 : (r'=true); // Inspect Left \n\t[startRight]   !r -> 10 : (r'=true); // Inspect Right \n\t[startToLeft]  !r -> 10 : (r'=true); // Inspect ToLeft\n\t[startToRight] !r -> 10 : (r'=true); // Inspect ToRight \n\t[startLine]    !r -> 10 : (r'=true); // Inspect Line \n\t\n\t[repairLeft]    r -> 2     : (r'=false); // Repair Left \n\t[repairRight]   r -> 2     : (r'=false); // Repair Right\n\t[repairToLeft]  r -> 0.25  : (r'=false); // Repair ToLeft\n\t[repairToRight] r -> 0.25  : (r'=false); // Repair ToRight\n\t[repairLine]    r -> 0.125 : (r'=false); // Repair Line\n\t\nendmodule\n\n// Line/backbone\nmodule Line \n\t\n\tline :   bool; // Being repaired?\n\tline_n : bool init true; // Working?\n\t\n\t[startLine] !line & !line_n -> 1 : (line'=true);\n\t[repairLine] line & !line_n -> 1 : (line'=false) & (line_n'=true);\n\t[] line_n -> line_fail : (line_n'=false);\n\t\nendmodule\n\n// Left switch\nmodule ToLeft = Line[line=toleft,\n                     line_n=toleft_n,\n                     line_fail=switch_fail,\n                     startLine=startToLeft,\n                     repairLine=repairToLeft ]\nendmodule\n\n// Right switch\nmodule ToRight = Line[line=toright,\n                      line_n=toright_n,\n                      line_fail=switch_fail,\n                      startLine=startToRight,\n                      repairLine=repairToRight ]\nendmodule\n\n// Formulas + labels\n\n// Minimum QoS requires 3/4 connected workstations operational\nconst int k = floor(0.75*N);\n// left_operational_i : left_n>=i & toleft_n\n// right_operational_i : right_n>=i & toright_n\n// operational_i : (left_n+right_n)>=i & toleft_n & line_n & toright_n\n// minimum_k : left_operational_k | right_operational_k | operational_k\nformula minimum = (left_n>=k & toleft_n) | \n                  (right_n>=k & toright_n) | \n                  ((left_n+right_n)>=k & toleft_n & line_n & toright_n);\nlabel \"minimum\" = (left_n>=k & toleft_n) | (right_n>=k & toright_n) | ((left_n+right_n)>=k & toleft_n & line_n & toright_n);\n// premium = minimum_N\nlabel \"premium\" = (left_n>=left_mx & toleft_n) | (right_n>=right_mx & toright_n) | ((left_n+right_n)>=left_mx & toleft_n & line_n & toright_n);\n\n// Reward structures\n\n// Percentage of operational workstations stations\nrewards \"percent_op\"\n\ttrue : 100*(left_n+right_n)/(2*N);\nendrewards\n\n// Time that the system is not delivering at least minimum QoS\nrewards \"time_not_min\"\n\t!minimum : 1; \nendrewards\n\n// Number of repairs\nrewards \"num_repairs\"\n\t[repairLeft]    true : 1;\n\t[repairRight]   true : 1;\n\t[repairToLeft]  true : 1;\n\t[repairToRight] true : 1;\n\t[repairLine]    true : 1;\nendrewards\n"
  },
  {
    "path": "prism-examples/ctmcs/embedded/README.txt",
    "content": "This case study models a simple embedded system, as described in [KNP04c].\r\nIt is closely based on the example of [MCT94].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/embedded.php\r\n\r\n=====================================================================================\r\n\r\n[KNP04c]\r\nM. Kwiatkowska, G. Norman and D. Parker\r\nController Dependability Analysis By Probabilistic Model Checking\r\nIn Proc. 11th IFAC Symposium on Information Control Problems in Manufacturing (INCOM'04), 2004\r\n\r\n[MCT94]\r\nJ. Muppala, G. Ciardo and K. Trivedi\r\nStochastic reward nets for reliability prediction\r\nCommunications in Reliability, Maintainability and Serviceability 1(2):9-20, 1994\r\n"
  },
  {
    "path": "prism-examples/ctmcs/embedded/auto",
    "content": "#!/bin/csh\n\nprism embedded.sm embedded.csl -prop 1 -const MAX_COUNT=2,T=12 -s\nprism embedded.sm embedded.csl -prop 2 -const MAX_COUNT=2,T=12 -s\nprism embedded.sm embedded.csl -prop 3 -const MAX_COUNT=2,T=12 -s\nprism embedded.sm embedded.csl -prop 4 -const MAX_COUNT=2,T=12 -s\nprism embedded.sm embedded.csl -prop 5 -const MAX_COUNT=2,T=12 -s\n\nprism embedded.sm embedded.csl -prop 6 -const MAX_COUNT=2,T=14 -s -epsilon 1e-8\nprism embedded.sm embedded.csl -prop 7 -const MAX_COUNT=2,T=14 -s -epsilon 1e-8\nprism embedded.sm embedded.csl -prop 8 -const MAX_COUNT=2,T=14 -s -epsilon 1e-8\nprism embedded.sm embedded.csl -prop 9 -const MAX_COUNT=2,T=14 -s -epsilon 1e-8\nprism embedded.sm embedded.csl -prop 10 -const MAX_COUNT=2,T=14 -s -epsilon 1e-8\n\nprism embedded.sm embedded.csl -prop 11 -const MAX_COUNT=2,T=0 -s\nprism embedded.sm embedded.csl -prop 12 -const MAX_COUNT=2,T=0 -s\nprism embedded.sm embedded.csl -prop 13 -const MAX_COUNT=2,T=0 -s\nprism embedded.sm embedded.csl -prop 14 -const MAX_COUNT=2,T=0 -s\n\nprism embedded.sm embedded.csl -prop 15 -const MAX_COUNT=2,T=12 -s -epsilon 1e-8\nprism embedded.sm embedded.csl -prop 16 -const MAX_COUNT=2,T=12 -s -epsilon 1e-8\nprism embedded.sm embedded.csl -prop 17 -const MAX_COUNT=2,T=12 -s -epsilon 1e-8\n\nprism embedded.sm embedded.csl -prop 18 -const MAX_COUNT=2,T=12 -s -epsilon 1e-8\nprism embedded.sm embedded.csl -prop 19 -const MAX_COUNT=2,T=12 -s -epsilon 1e-8\n"
  },
  {
    "path": "prism-examples/ctmcs/embedded/embedded.csl",
    "content": "const double T; // time bound\r\n\r\n// causes of failues\nlabel \"fail_sensors\" = i=2&s<MIN_SENSORS; // sensors have failed\r\nlabel \"fail_actuators\" = o=2&a<MIN_ACTUATORS; // actuators have failed\r\nlabel \"fail_io\" = count=MAX_COUNT+1; // IO has failed\r\nlabel \"fail_main\" = m=0; // ,main processor has failed\n\n// system status\r\nlabel \"down\" = (i=2&s<MIN_SENSORS)|(count=MAX_COUNT+1)|(o=2&a<MIN_ACTUATORS)|(m=0); // system has shutdown\r\nlabel \"danger\" = !down & (i=1 | o=1); // transient fault has occured\r\nlabel \"up\" = !down & !danger; // system is operational\r\n\r\n// Probability of any failure occurring within T hours\r\nP=? [ true U<=(T*3600) \"down\" ]\r\n\r\n// Probability of each failure type occurring first (within T hours)\r\nP=? [ !\"down\" U<=(T*3600) \"fail_sensors\" ]\r\nP=? [ !\"down\" U<=(T*3600) \"fail_actuators\" ]\r\nP=? [ !\"down\" U<=(T*3600) \"fail_io\" ]\r\nP=? [ !\"down\" U<=(T*3600) \"fail_main\" ]\r\n\r\n// Probability of any failure occurring within T days\r\nP=? [ true U<=(T*3600*24) \"down\" ]\r\n\n// Probability of each failure type occurring first (within T days)\r\nP=? [ !\"down\" U<=(T*3600*24) \"fail_sensors\" ]\r\nP=? [ !\"down\" U<=(T*3600*24) \"fail_actuators\" ]\r\nP=? [ !\"down\" U<=(T*3600*24) \"fail_io\" ]\r\nP=? [ !\"down\" U<=(T*3600*24) \"fail_main\" ]\r\n\r\n\r\n// Long-run probability of each failure type occurring\r\nP=? [ !\"down\" U \"fail_sensors\" ]\r\nP=? [ !\"down\" U \"fail_actuators\" ]\r\nP=? [ !\"down\" U \"fail_io\" ]\r\nP=? [ !\"down\" U \"fail_main\" ]\r\n\r\n// Expected time spent in \"up\"/\"danger\"/\"down\" by time T\r\nR{\"up\"}=? [ C<=(T*3600) ]\r\nR{\"danger\"}=? [ C<=(T*3600) ]\r\nR{\"down\"}=? [ C<=(T*3600) ]\r\n\r\n// Expected time spent in \"up\"/\"danger\" before \"down\"\r\nR{\"up\"}=? [ F \"down\" ]\nR{\"danger\"}=? [ F \"down\" ]\n"
  },
  {
    "path": "prism-examples/ctmcs/embedded/embedded.sm",
    "content": "ctmc\r\n\r\n// constants\r\nconst int MAX_COUNT;\r\nconst int MIN_SENSORS = 2;\r\nconst int MIN_ACTUATORS = 1;\r\n\r\n// rates\r\nconst double lambda_p = 1/(365*24*60*60); // 1 year\r\nconst double lambda_s = 1/(30*24*60*60); // 1 month\r\nconst double lambda_a = 1/(2*30*24*60*60); // 2 months\r\nconst double tau = 1/60; // 1 min\r\nconst double delta_f = 1/(24*60*60); // 1 day\r\nconst double delta_r = 1/30; // 30 secs\r\n\r\n// sensors\r\nmodule sensors\r\n\t\r\n\ts : [0..3] init 3; // number of sensors working\r\n\t\r\n\t[] s>1 -> s*lambda_s : (s'=s-1); // failure of a single sensor\r\n\t\r\nendmodule\r\n\r\n// input processor\r\n// (takes data from sensors and passes onto main processor)\r\nmodule proci\r\n\t\r\n\ti : [0..2] init 2; // 2=ok, 1=transient fault, 0=failed\r\n\t\r\n\t[] i>0 & s>=MIN_SENSORS -> lambda_p : (i'=0); // failure of processor\r\n\t[] i=2 & s>=MIN_SENSORS -> delta_f : (i'=1); // transient fault\r\n\t[input_reboot] i=1 & s>=MIN_SENSORS -> delta_r : (i'=2); // reboot after transient fault\r\n\t\r\nendmodule\r\n\r\n// actuators\r\nmodule actuators\r\n\t\r\n\ta : [0..2] init 2; // number of actuators working\r\n\t\r\n\t[] a>0 -> a*lambda_a : (a'=a-1); // failure of a single actuator\r\n\t\r\nendmodule\r\n\r\n// output processor\r\n// (receives instructions from main processor and passes onto actuators)\r\nmodule proco = proci [ i=o, s=a, input_reboot=output_reboot, MIN_SENSORS=MIN_ACTUATORS ] endmodule\r\n\r\n// main processor\r\n// (takes data from proci, processes it, and passes instructions to proco)\r\nmodule procm\r\n\t\r\n\tm : [0..1] init 1; // 1=ok, 0=failed\r\n\tcount : [0..MAX_COUNT+1] init 0; // number of consecutive skipped cycles\r\n\t\r\n\t// failure of processor\r\n\t[] m=1 -> lambda_p : (m'=0);\r\n\t// processing completed before timer expires - reset skipped cycle counter\r\n\t[timeout]  comp -> tau : (count'=0);\r\n\t// processing not completed before timer expires - increment skipped cycle counter\r\n\t[timeout] !comp -> tau : (count'=min(count+1, MAX_COUNT+1));\r\n\t\r\nendmodule\r\n\r\n// connecting bus\r\nmodule bus\r\n\t\r\n\t// flags\r\n\t// main processor has processed data from input processor\r\n\t// and sent corresponding instructions to output processor (since last timeout)\r\n\tcomp : bool init true; \r\n\t// input processor has data ready to send\r\n\treqi : bool init true; \r\n\t// output processor has instructions ready to be processed\r\n\treqo : bool init false;\r\n\t\r\n\t// input processor reboots\r\n\t[input_reboot]  true -> 1 :\r\n\t// performs a computation if has already done so or\r\n\t// it is up and ouput clear (i.e. nothing waiting)\r\n\t(comp'=(comp | (m=1 & !reqo))) \r\n\t// up therefore something to process\r\n\t& (reqi'=true)\r\n\t// something to process if not functioning and either\r\n\t// there is something already pending\r\n\t// or the main processor sends a request\r\n\t& (reqo'=!(o=2 & a>=1) & (reqo | m=1));\r\n\t\r\n\t// output processor reboots\r\n\t[output_reboot] true -> 1 :\r\n\t// performs a computation if it has already or\r\n\t// something waiting and is up\r\n\t// (can be processes as the output has come up and cleared pending requests)\r\n\t(comp'=(comp | (reqi & m=1)))\r\n\t// something to process it they are up or\r\n\t// there was already something and the main processor acts\r\n\t// (output now up must be due to main processor being down)\r\n\t& (reqi'=(i=2 & s>=2) | (reqi & m=0))\r\n\t// output and actuators up therefore nothing can be pending\r\n\t& (reqo'=false);\r\n\t\r\n\t// main processor times out\r\n\t[timeout] true -> 1 :\r\n\t// performs a computation if it is up something was pending\r\n\t// and nothing is waiting for the output\r\n\t(comp'=(reqi & !reqo & m=1))\r\n\t// something to process if up or\r\n\t// already something and main process cannot act \r\n\t// (down or outputs pending)\r\n\t& (reqi'=(i=2 & s>=2) | (reqi & (reqo | m=0)))\r\n\t// something to process if they are not functioning and \r\n\t// either something is already pending\r\n\t// or the main processor acts\r\n\t& (reqo'=!(o=2 & a>=1) & (reqo | (reqi & m=1)));\r\n\t\r\nendmodule\r\n\n// the system is down\nformula down = (i=2&s<MIN_SENSORS)|(count=MAX_COUNT+1)|(o=2&a<MIN_ACTUATORS)|(m=0);\n// transient failure has occured but the system is not down\r\nformula danger = !down & (i=1 | o=1);\n// the system is operational\r\nformula up = !down & !danger;\r\n\n// reward structures\n\r\nrewards \"up\"\r\n\tup : 1/3600;\r\nendrewards\n\rrewards \"danger\"\r\n\tdanger : 1/3600;\r\nendrewards\r\nrewards \"down\"\r\n\tdown : 1/3600;\r\nendrewards\n"
  },
  {
    "path": "prism-examples/ctmcs/fms/README.txt",
    "content": "This case study is based on the flexible manufacturing system of [CT93].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/fms.php\r\n\r\n=====================================================================================\r\n\r\n[CT93]\r\nG. Ciardo and K.S. Trivedi\r\nA decomposition approach for stochastic reward networks\r\nPerformance Evaluation, 18(1):37-59, 1993\r\n"
  },
  {
    "path": "prism-examples/ctmcs/fms/auto",
    "content": "#!/bin/csh\n\nforeach n (1 2 3 4 5 6)\n\tprism fms.sm fms.csl -const n=$n -bgs\nend\n"
  },
  {
    "path": "prism-examples/ctmcs/fms/fms.csl",
    "content": "// expected throughput of each machine\nR{\"throughput_m1\"}=?  [ S ]\nR{\"throughput_m2\"}=?  [ S ]\nR{\"throughput_m3\"}=?  [ S ]\nR{\"throughput_m12\"}=? [ S ]\n\n// expected productivity of the system\nR{\"productivity\"}=? [ S ]\n\n"
  },
  {
    "path": "prism-examples/ctmcs/fms/fms.sm",
    "content": "// flexible manufacturing system [CT93]\r\n// gxn/dxp 11/06/01\r\n\r\nctmc // model is a ctmc\r\n\nconst int n; // number of tokens\r\n\r\n// rates from Pi equal #(Pi) * min(1, np/r)\r\n// where np = (3n)/2 and r = P1+P2+P3+P12\r\nconst int np=floor((3*n)/2);\r\nformula r = P1+P2+P3+P12;\r\n\r\nmodule machine1\r\n\t\r\n\tP1 : [0..n] init n;\r\n\tP1wM1 : [0..n];\r\n\tP1M1 : [0..3];\r\n\tP1d : [0..n];\r\n\tP1s : [0..n];\r\n\tP1wP2 : [0..n];\r\n\tM1 : [0..3] init 3;   \r\n\t\r\n\t[t1] (P1>0) & (M1>0) & (P1M1<3)  -> P1*min(1,np/r) : (P1'=P1-1) & (P1M1'=P1M1+1) & (M1'=M1-1);\r\n\t[t1] (P1>0) & (M1=0) & (P1wM1<n) -> P1*min(1,np/r) : (P1'=P1-1) & (P1wM1'=P1wM1+1);\r\n\t\r\n\t[] (P1M1>0) & (P1wM1=0) & (M1<3) & (P1s<n) -> 0.2*P1M1 : (P1M1'=P1M1-1) & (M1'=M1+1) & (P1s'=P1s+1);\r\n\t[] (P1M1>0) & (P1wM1>0) & (P1s<n) -> 0.2*P1M1 : (P1wM1'=P1wM1-1) & (P1s'=P1s+1);\r\n\t\r\n\t[] (P1M1>0) & (P2wP1=0) & (P1wM1=0) & (M1<3) & (P1wP2<n) -> 0.05*P1M1 : (P1M1'=P1M1-1) & (M1'=M1+1) & (P1wP2'=P1wP2+1);\r\n\t[] (P1M1>0) & (P2wP1=0) & (P1wM1>0) & (P1wP2<n) -> 0.05*P1M1 : (P1wM1'=P1wM1-1) & (P1wP2'=P1wP2+1);\r\n\t\r\n\t[p1p2] (P1M1>0) & (P2wP1>0) & (P1wM1=0) & (M1<3) -> 0.05*P1M1 : (P1M1'=P1M1-1) & (M1'=M1+1);\r\n\t[p1p2] (P1M1>0) & (P2wP1>0) & (P1wM1>0) -> 0.05*P1M1 : (P1wM1'=P1wM1-1);\r\n\t\r\n\t[p1p2] (P1wP2>0)  -> 1: (P1wP2'=P1wP2-1);\r\n\t[]     (P1s>0) & (P1+P1s<=n) -> 1/60 : (P1s'=0) & (P1'=P1+P1s);\r\n\t[fp12] (P1+P12s<=n) -> 1: (P1'=P1+P12s);\r\n\t\r\nendmodule\r\n\r\nmodule machine2\r\n\t\r\n\tP2 : [0..n] init n;\r\n\tP2wM2 : [0..n];\r\n\tP2M2 : [0..1];\r\n\tP2s : [0..n];\r\n\tP2wP1 : [0..n];\r\n\tM2 : [0..1] init 1;\r\n\t\r\n\t[t2] (P2>0) & (M2>0) & (P2M2<1)  -> P2*min(1,np/r) : (P2'=P2-1) & (P2M2'=P2M2+1) & (M2'=M2-1);\r\n\t[t2] (P2>0) & (M2=0) & (P2wM2<n) -> P2*min(1,np/r) : (P2'=P2-1) & (P2wM2'=P2wM2+1);\r\n\t\r\n\t[] (P2M2>0) & (P2wM2=0) & (M2<1) & (P2s<n) -> 0.1 : (P2M2'=P2M2-1) & (M2'=M2+1) & (P2s'=P2s+1);\r\n\t[] (P2M2>0) & (P2wM2>0) & (P2s<n) -> 0.1 : (P2wM2'=P2wM2-1) & (P2s'=P2s+1);\r\n\t\r\n\t[] (P2M2>0) & (P1wP2=0) & (P2wM2=0) & (M2<1) & (P2wP1<n) -> 1/15: (P2M2'=P2M2-1) & (M2'=M2+1) & (P2wP1'=P2wP1+1);\r\n\t[] (P2M2>0) & (P1wP2=0) & (P2wM2>0) & (P2wP1<n) -> 1/15: (P2wM2'=P2wM2-1) & (P2wP1'=P2wP1+1);\r\n\t\r\n\t[p1p2] (P2M2>0) & (P1wP2>0) & (P2wM2=0) & (M2<1) -> 1/15: (P2M2'=P2M2-1) & (M2'=M2+1);\r\n\t[p1p2] (P2M2>0) & (P1wP2>0) & (P2wM2>0) -> 1/15: (P2wM2'=P2wM2-1);\r\n\t\r\n\t[p1p2] (P2wP1>0) -> 1 : (P2wP1'=P2wP1-1);\r\n\t[]     (P2s>0) & (P2+P2s<=n) -> 1/60 : (P2s'=0) & (P2'=P2+P2s);\r\n\t[fp12] (P2+P12s<=n) -> 1 : (P2'=P2+P12s);\r\n\t[p2p3] (M2>0) -> 1 : (M2'=M2);\r\n\t\r\nendmodule\r\n\r\nmodule machine3 \r\n\t\r\n\tP3 : [0..n] init n;\r\n\tP3M2 : [0..n];\r\n\tP3s : [0..n];\r\n\t\r\n\t[t3] (P3>0) & (P3M2<n) -> P3*min(1,np/r) : (P3'=P3-1) & (P3M2'=P3M2+1);\r\n\t\r\n\t[p2p3] (P3M2>0) & (P3s<n) -> 1/2 : (P3M2'=P3M2-1) & (P3s'=P3s+1);\r\n\t[]     (P3s>0) & (P3+P3s<=n) -> 1/60 : (P3s'=0) & (P3'=P3+P3s);\r\n\t\r\nendmodule\r\n\r\nmodule machine12\r\n\t\r\n\tP12 : [0..n];\r\n\tP12wM3 : [0..n];\r\n\tP12M3 : [0..2];\r\n\tP12s : [0..n];\r\n\tM3 : [0..2] init 2;\r\n\t\r\n\t[p1p2] (P12<n) -> 1: (P12'=P12+1);\r\n\t\r\n\t[t12] (P12>0) & (M3>0) & (P12M3<2) -> P12*min(1,np/r) : (P12'=P12-1) & (P12M3'=P12M3+1) & (M3'=M3-1);\r\n\t[t12] (P12>0) & (M3=0) & (P12wM3<n) -> P12*min(1,np/r) : (P12'=P12-1) & (P12wM3'=P12wM3+1);\r\n\t\r\n\t[] (P12M3>0) & (P12wM3=0) & (P12s<n) & (M3<2) -> P12M3 : (P12M3'=P12M3-1) & (P12s'=P12s+1) & (M3'=M3+1);\r\n\t[] (P12M3>0) & (P12wM3>0) & (P12s<n) -> P12M3 : (P12wM3'=P12wM3-1) & (P12s'=P12s+1);\r\n\t\r\n\t[fp12] (P12s>0) -> 1/60 : (P12s'=0);\r\n\t\r\nendmodule\r\n\n// reward structures\n\n// throughput of machine1\r\nrewards \"throughput_m1\"\r\n\t[t1]  true : 1;\t\r\nendrewards\r\n// throughput of machine2\r\nrewards \"throughput_m2\"\r\n\t[t2]  true : 1;\t\r\nendrewards\r\n// throughput of machine3\r\nrewards \"throughput_m3\"\r\n\t[t3]  true : 1;\t\r\nendrewards\r\n// throughput of machine12\nrewards \"throughput_m12\"\r\n\t[t12]  true : 1;\t\r\nendrewards\r\n// productivity of the system\nrewards \"productivity\"\r\n\t[t1]  true : 400;\r\n\t[t2]  true : 600;\r\n\t[t3]  true : 100;\r\n\t[t12] true : 1100;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/kanban/README.txt",
    "content": "This case study is based on the Kanban flexible manufacturing system of [CT96].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/kanban.php\r\n\r\n=====================================================================================\r\n\r\n[CT96]\r\nG. Ciardo and M. Tilgner\r\nOn the use of Kronecker Operators for the Solution of Generalized Stochastic Petri Nets\r\nICASE Report No. 96-35, 1996\r\n"
  },
  {
    "path": "prism-examples/ctmcs/kanban/auto",
    "content": "#!/bin/csh\n\nforeach t (1 2 3 4) # 5 6 7 8)\n\tprism kanban.sm kanban.csl -const t=$t -jor\nend\n"
  },
  {
    "path": "prism-examples/ctmcs/kanban/kanban.csl",
    "content": "// expected number of tokens in each cell\nR{\"tokens_cell1\"}=? [ S ]\nR{\"tokens_cell2\"}=? [ S ]\nR{\"tokens_cell3\"}=? [ S ]\nR{\"tokens_cell4\"}=? [ S ]\n\n// expected throughput of the system\nR{\"throughput\"}=? [ S ]\n"
  },
  {
    "path": "prism-examples/ctmcs/kanban/kanban.sm",
    "content": "// kanban manufacturing example [CT96]\r\n// dxp/gxn 3/2/00\r\n\r\nctmc\r\n\r\n// number of tokens \r\nconst int t; \r\n\r\n// rates\r\nconst double in1      = 1.0;\r\nconst double out4     = 0.9;\r\nconst double synch123 = 0.4;\r\nconst double synch234 = 0.5;\r\nconst double back     = 0.3;\r\nconst double redo1    = 0.36;\r\nconst double redo2    = 0.42;\r\nconst double redo3    = 0.39;\r\nconst double redo4    = 0.33;\r\nconst double ok1      = 0.84;\r\nconst double ok2      = 0.98;\r\nconst double ok3      = 0.91;\r\nconst double ok4      = 0.77;\r\n\r\nmodule k1\r\n\r\n\tw1 : [0..t];\r\n\tx1 : [0..t];\r\n\ty1 : [0..t];\r\n\tz1 : [0..t];\r\n\t\r\n\t[in]   (w1<t) & (x1<t) -> in1 \t : (w1'=w1+1) & (x1'=x1+1);\r\n\t[]   (x1>0) & (y1<t) -> redo1\t : (x1'=x1-1) & (y1'=y1+1);\r\n\t[]   (x1>0) & (z1<t) -> ok1 \t : (x1'=x1-1) & (z1'=z1+1);\r\n\t[]   (y1>0) & (x1<t) -> back\t : (y1'=y1-1) & (x1'=x1+1);\r\n\t[s1] (z1>0) & (w1>0) -> synch123 : (z1'=z1-1) & (w1'=w1-1);\r\n\r\nendmodule\r\n\r\nmodule k2\r\n\r\n\tw2 : [0..t];\r\n\tx2 : [0..t];\r\n\ty2 : [0..t];\r\n\tz2 : [0..t];\r\n\t\r\n\t[s1] (w2<t) & (x2<t) -> 1\t : (w2'=w2+1) & (x2'=x2+1);\r\n\t[]   (x2>0) & (y2<t) -> redo2 : (x2'=x2-1) & (y2'=y2+1);\r\n\t[]   (x2>0) & (z2<t) -> ok2   : (x2'=x2-1) & (z2'=z2+1);\r\n\t[]   (y2>0) & (x2<t) -> back  : (y2'=y2-1) & (x2'=x2+1);\r\n\t[s2] (z2>0) & (w2>0) -> 1\t : (z2'=z2-1) & (w2'=w2-1);\r\n\r\nendmodule\r\n\r\nmodule k3\r\n\r\n\tw3 : [0..t];\r\n\tx3 : [0..t];\r\n\ty3 : [0..t];\r\n\tz3 : [0..t];\r\n\t\r\n\t[s1] (w3<t) & (x3<t) -> 1\t : (w3'=w3+1) & (x3'=x3+1);\r\n\t[]   (x3>0) & (y3<t) -> redo3 : (x3'=x3-1) & (y3'=y3+1);\r\n\t[]   (x3>0) & (z3<t) -> ok3   : (x3'=x3-1) & (z3'=z3+1);\r\n\t[]   (y3>0) & (x3<t) -> back  : (y3'=y3-1) & (x3'=x3+1);\r\n\t[s2] (z3>0) & (w3>0) -> 1\t : (z3'=z3-1) & (w3'=w3-1);\r\n\r\n\r\nendmodule\r\n\r\nmodule k4\r\n\r\n\tw4 : [0..t];\r\n\tx4 : [0..t];\r\n\ty4 : [0..t];\r\n\tz4 : [0..t];\r\n\t\r\n\t[s2] (w4<t) & (x4<t) -> synch234 : (w4'=w4+1) & (x4'=x4+1);\r\n\t[]   (x4>0) & (y4<t) -> redo4\t: (x4'=x4-1) & (y4'=y4+1);\r\n\t[]   (x4>0) & (z4<t) -> ok4  \t: (x4'=x4-1) & (z4'=z4+1);\r\n\t[]   (y4>0) & (x4<t) -> back \t: (y4'=y4-1) & (x4'=x4+1);\r\n\t[]   (z4>0) & (w4>0) -> out4 \t: (z4'=z4-1) & (w4'=w4-1);\r\n\r\nendmodule\r\n\n// reward structures\n\n// tokens in cell1\nrewards \"tokens_cell1\"\n\ttrue : x1+y1+z1;\nendrewards\n\n// tokens in cell2\nrewards \"tokens_cell2\"\n\ttrue : x2+y2+z2;\nendrewards\n\n// tokens in cell3\nrewards \"tokens_cell3\"\n\ttrue : x3+y3+z3;\nendrewards\n\n// tokens in cell4\nrewards \"tokens_cell4\"\n\ttrue : x4+y4+z4;\nendrewards\n\n// throughput of the system\r\nrewards \"throughput\"\r\n\t[in] true : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/.autopp",
    "content": "#!/bin/csh\n\nforeach N (4 5)\n  foreach K (4 5 6 7 8)\n\techo \"Generating for N=$N, K=$K\"\n    prismpp .peer2peerN_K.sm.pp $N $K  >! peer2peer\"$N\"_\"$K\".sm\n\tunix2dos peer2peer\"$N\"_\"$K\".sm\n  end\nend\n\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/.peer2peerN_K.sm.pp",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\n// gxn/dxp Jan 2006\n\nctmc\n\n#const N#\n#const K#\n// N=#N# clients, K=#K# blocks to be downloaded\n// Actually there are N+1=#N+1# clients, one of which has all blocks initially\n\n// Rate of block download for a single source\nconst double mu=2;\n\n// Rate of download of block i:\n// A client can download from the single client which starts with all blocks\n// or from anyone that has subsequently downloaded it.\n// Total number of concurrent downloads for each block is 4.\n#for j=1:K#\nformula rate#j#=mu*(1+min(3,#+ i=1:N#b#i##j##end#));\n#end#\n\n// client 1\nmodule client1\n\t\n\t// bij - has client i downloaded block j yet?\n\t#for j=1:K#\n\tb1#j# : [0..1];\n\t#end#\n\t\n\t// Downloading of each block (see rate computations above)\n\t#for j=1:K#\n\t[] b1#j#=0 -> rate#j# : (b1#j#'=1);\n\t#end#\n\t\nendmodule\n\n// construct remaining clients through renaming\n#for i=2:N#\nmodule client#i#=client1[b11=b#i#1#for j=2:K#,b1#j#=b#i##j##end#,b#i#1=b11#for j=2:K#,b#i##j#=b1#j##end#] endmodule\n#end#\n\n// labels\n#for i=1:N#\nlabel \"done#i#\" = #+ j=1:K#b#i##j##end# = #K#; // client #i# has received all blocks\n#end#\nlabel \"done\" = #+ i=1:N#(#+ j=1:K#b#i##j##end#)#end# = #N*K#; // all clients have received all blocks\n\n// reward: fraction of blocks received\nrewards \"frac_rec\"\n#for i=1:N#\n\ttrue : ((#+ j=1:K#b#i##j##end#)/#K#)/#N#;\n#end#\nendrewards\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/README.txt",
    "content": "This case study models a very simple peer-to-peer protocol, loosely based on BitTorrent.\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/peer2peer.php\r\n\r\n=====================================================================================\r\n\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/auto",
    "content": "#!/bin/csh\n\nforeach N (4 5)\n  foreach K (4) # 5 6 7 8)\n    prism peer2peer\"$N\"_\"$K\".sm peer2peer.csl -fixdl -const T=1.1\n  end\nend\n\n\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer.csl",
    "content": "const double T; // time bound\n\n// probability that all clients have received all blocks by time T\nP=? [ true U<=T  \"done\"  ]\n\n// expected fraction of blocks received by time T\nR=? [ I=T ]\n\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer4_4.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=4 clients, K=4 blocks to be downloaded\r\n// Actually there are N+1=5 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b21=b11,b22=b12,b23=b13,b24=b14] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b31=b11,b32=b12,b33=b13,b34=b14] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b41=b11,b42=b12,b43=b13,b44=b14] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14 = 4; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24 = 4; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34 = 4; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44 = 4; // client 4 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14)+(b21+b22+b23+b24)+(b31+b32+b33+b34)+(b41+b42+b43+b44) = 16; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14)/4)/4;\r\n\ttrue : ((b21+b22+b23+b24)/4)/4;\r\n\ttrue : ((b31+b32+b33+b34)/4)/4;\r\n\ttrue : ((b41+b42+b43+b44)/4)/4;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer4_5.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=4 clients, K=5 blocks to be downloaded\r\n// Actually there are N+1=5 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44));\r\nformula rate5=mu*(1+min(3,b15+b25+b35+b45));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\tb15 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t[] b15=0 -> rate5 : (b15'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b15=b25,b21=b11,b22=b12,b23=b13,b24=b14,b25=b15] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b15=b35,b31=b11,b32=b12,b33=b13,b34=b14,b35=b15] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b15=b45,b41=b11,b42=b12,b43=b13,b44=b14,b45=b15] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14+b15 = 5; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24+b25 = 5; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34+b35 = 5; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44+b45 = 5; // client 4 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14+b15)+(b21+b22+b23+b24+b25)+(b31+b32+b33+b34+b35)+(b41+b42+b43+b44+b45) = 20; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14+b15)/5)/4;\r\n\ttrue : ((b21+b22+b23+b24+b25)/5)/4;\r\n\ttrue : ((b31+b32+b33+b34+b35)/5)/4;\r\n\ttrue : ((b41+b42+b43+b44+b45)/5)/4;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer4_6.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=4 clients, K=6 blocks to be downloaded\r\n// Actually there are N+1=5 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44));\r\nformula rate5=mu*(1+min(3,b15+b25+b35+b45));\r\nformula rate6=mu*(1+min(3,b16+b26+b36+b46));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\tb15 : [0..1];\r\n\tb16 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t[] b15=0 -> rate5 : (b15'=1);\r\n\t[] b16=0 -> rate6 : (b16'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b15=b25,b16=b26,b21=b11,b22=b12,b23=b13,b24=b14,b25=b15,b26=b16] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b15=b35,b16=b36,b31=b11,b32=b12,b33=b13,b34=b14,b35=b15,b36=b16] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b15=b45,b16=b46,b41=b11,b42=b12,b43=b13,b44=b14,b45=b15,b46=b16] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14+b15+b16 = 6; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24+b25+b26 = 6; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34+b35+b36 = 6; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44+b45+b46 = 6; // client 4 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14+b15+b16)+(b21+b22+b23+b24+b25+b26)+(b31+b32+b33+b34+b35+b36)+(b41+b42+b43+b44+b45+b46) = 24; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14+b15+b16)/6)/4;\r\n\ttrue : ((b21+b22+b23+b24+b25+b26)/6)/4;\r\n\ttrue : ((b31+b32+b33+b34+b35+b36)/6)/4;\r\n\ttrue : ((b41+b42+b43+b44+b45+b46)/6)/4;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer4_7.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=4 clients, K=7 blocks to be downloaded\r\n// Actually there are N+1=5 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44));\r\nformula rate5=mu*(1+min(3,b15+b25+b35+b45));\r\nformula rate6=mu*(1+min(3,b16+b26+b36+b46));\r\nformula rate7=mu*(1+min(3,b17+b27+b37+b47));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\tb15 : [0..1];\r\n\tb16 : [0..1];\r\n\tb17 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t[] b15=0 -> rate5 : (b15'=1);\r\n\t[] b16=0 -> rate6 : (b16'=1);\r\n\t[] b17=0 -> rate7 : (b17'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b15=b25,b16=b26,b17=b27,b21=b11,b22=b12,b23=b13,b24=b14,b25=b15,b26=b16,b27=b17] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b15=b35,b16=b36,b17=b37,b31=b11,b32=b12,b33=b13,b34=b14,b35=b15,b36=b16,b37=b17] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b15=b45,b16=b46,b17=b47,b41=b11,b42=b12,b43=b13,b44=b14,b45=b15,b46=b16,b47=b17] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14+b15+b16+b17 = 7; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24+b25+b26+b27 = 7; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34+b35+b36+b37 = 7; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44+b45+b46+b47 = 7; // client 4 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14+b15+b16+b17)+(b21+b22+b23+b24+b25+b26+b27)+(b31+b32+b33+b34+b35+b36+b37)+(b41+b42+b43+b44+b45+b46+b47) = 28; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14+b15+b16+b17)/7)/4;\r\n\ttrue : ((b21+b22+b23+b24+b25+b26+b27)/7)/4;\r\n\ttrue : ((b31+b32+b33+b34+b35+b36+b37)/7)/4;\r\n\ttrue : ((b41+b42+b43+b44+b45+b46+b47)/7)/4;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer4_8.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=4 clients, K=8 blocks to be downloaded\r\n// Actually there are N+1=5 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44));\r\nformula rate5=mu*(1+min(3,b15+b25+b35+b45));\r\nformula rate6=mu*(1+min(3,b16+b26+b36+b46));\r\nformula rate7=mu*(1+min(3,b17+b27+b37+b47));\r\nformula rate8=mu*(1+min(3,b18+b28+b38+b48));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\tb15 : [0..1];\r\n\tb16 : [0..1];\r\n\tb17 : [0..1];\r\n\tb18 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t[] b15=0 -> rate5 : (b15'=1);\r\n\t[] b16=0 -> rate6 : (b16'=1);\r\n\t[] b17=0 -> rate7 : (b17'=1);\r\n\t[] b18=0 -> rate8 : (b18'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b15=b25,b16=b26,b17=b27,b18=b28,b21=b11,b22=b12,b23=b13,b24=b14,b25=b15,b26=b16,b27=b17,b28=b18] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b15=b35,b16=b36,b17=b37,b18=b38,b31=b11,b32=b12,b33=b13,b34=b14,b35=b15,b36=b16,b37=b17,b38=b18] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b15=b45,b16=b46,b17=b47,b18=b48,b41=b11,b42=b12,b43=b13,b44=b14,b45=b15,b46=b16,b47=b17,b48=b18] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14+b15+b16+b17+b18 = 8; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24+b25+b26+b27+b28 = 8; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34+b35+b36+b37+b38 = 8; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44+b45+b46+b47+b48 = 8; // client 4 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14+b15+b16+b17+b18)+(b21+b22+b23+b24+b25+b26+b27+b28)+(b31+b32+b33+b34+b35+b36+b37+b38)+(b41+b42+b43+b44+b45+b46+b47+b48) = 32; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14+b15+b16+b17+b18)/8)/4;\r\n\ttrue : ((b21+b22+b23+b24+b25+b26+b27+b28)/8)/4;\r\n\ttrue : ((b31+b32+b33+b34+b35+b36+b37+b38)/8)/4;\r\n\ttrue : ((b41+b42+b43+b44+b45+b46+b47+b48)/8)/4;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer5_4.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=5 clients, K=4 blocks to be downloaded\r\n// Actually there are N+1=6 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41+b51));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42+b52));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43+b53));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44+b54));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b21=b11,b22=b12,b23=b13,b24=b14] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b31=b11,b32=b12,b33=b13,b34=b14] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b41=b11,b42=b12,b43=b13,b44=b14] endmodule\r\nmodule client5=client1[b11=b51,b12=b52,b13=b53,b14=b54,b51=b11,b52=b12,b53=b13,b54=b14] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14 = 4; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24 = 4; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34 = 4; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44 = 4; // client 4 has received all blocks\r\nlabel \"done5\" = b51+b52+b53+b54 = 4; // client 5 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14)+(b21+b22+b23+b24)+(b31+b32+b33+b34)+(b41+b42+b43+b44)+(b51+b52+b53+b54) = 20; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14)/4)/5;\r\n\ttrue : ((b21+b22+b23+b24)/4)/5;\r\n\ttrue : ((b31+b32+b33+b34)/4)/5;\r\n\ttrue : ((b41+b42+b43+b44)/4)/5;\r\n\ttrue : ((b51+b52+b53+b54)/4)/5;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer5_5.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=5 clients, K=5 blocks to be downloaded\r\n// Actually there are N+1=6 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41+b51));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42+b52));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43+b53));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44+b54));\r\nformula rate5=mu*(1+min(3,b15+b25+b35+b45+b55));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\tb15 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t[] b15=0 -> rate5 : (b15'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b15=b25,b21=b11,b22=b12,b23=b13,b24=b14,b25=b15] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b15=b35,b31=b11,b32=b12,b33=b13,b34=b14,b35=b15] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b15=b45,b41=b11,b42=b12,b43=b13,b44=b14,b45=b15] endmodule\r\nmodule client5=client1[b11=b51,b12=b52,b13=b53,b14=b54,b15=b55,b51=b11,b52=b12,b53=b13,b54=b14,b55=b15] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14+b15 = 5; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24+b25 = 5; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34+b35 = 5; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44+b45 = 5; // client 4 has received all blocks\r\nlabel \"done5\" = b51+b52+b53+b54+b55 = 5; // client 5 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14+b15)+(b21+b22+b23+b24+b25)+(b31+b32+b33+b34+b35)+(b41+b42+b43+b44+b45)+(b51+b52+b53+b54+b55) = 25; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14+b15)/5)/5;\r\n\ttrue : ((b21+b22+b23+b24+b25)/5)/5;\r\n\ttrue : ((b31+b32+b33+b34+b35)/5)/5;\r\n\ttrue : ((b41+b42+b43+b44+b45)/5)/5;\r\n\ttrue : ((b51+b52+b53+b54+b55)/5)/5;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer5_6.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=5 clients, K=6 blocks to be downloaded\r\n// Actually there are N+1=6 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41+b51));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42+b52));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43+b53));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44+b54));\r\nformula rate5=mu*(1+min(3,b15+b25+b35+b45+b55));\r\nformula rate6=mu*(1+min(3,b16+b26+b36+b46+b56));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\tb15 : [0..1];\r\n\tb16 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t[] b15=0 -> rate5 : (b15'=1);\r\n\t[] b16=0 -> rate6 : (b16'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b15=b25,b16=b26,b21=b11,b22=b12,b23=b13,b24=b14,b25=b15,b26=b16] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b15=b35,b16=b36,b31=b11,b32=b12,b33=b13,b34=b14,b35=b15,b36=b16] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b15=b45,b16=b46,b41=b11,b42=b12,b43=b13,b44=b14,b45=b15,b46=b16] endmodule\r\nmodule client5=client1[b11=b51,b12=b52,b13=b53,b14=b54,b15=b55,b16=b56,b51=b11,b52=b12,b53=b13,b54=b14,b55=b15,b56=b16] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14+b15+b16 = 6; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24+b25+b26 = 6; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34+b35+b36 = 6; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44+b45+b46 = 6; // client 4 has received all blocks\r\nlabel \"done5\" = b51+b52+b53+b54+b55+b56 = 6; // client 5 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14+b15+b16)+(b21+b22+b23+b24+b25+b26)+(b31+b32+b33+b34+b35+b36)+(b41+b42+b43+b44+b45+b46)+(b51+b52+b53+b54+b55+b56) = 30; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14+b15+b16)/6)/5;\r\n\ttrue : ((b21+b22+b23+b24+b25+b26)/6)/5;\r\n\ttrue : ((b31+b32+b33+b34+b35+b36)/6)/5;\r\n\ttrue : ((b41+b42+b43+b44+b45+b46)/6)/5;\r\n\ttrue : ((b51+b52+b53+b54+b55+b56)/6)/5;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer5_7.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=5 clients, K=7 blocks to be downloaded\r\n// Actually there are N+1=6 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41+b51));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42+b52));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43+b53));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44+b54));\r\nformula rate5=mu*(1+min(3,b15+b25+b35+b45+b55));\r\nformula rate6=mu*(1+min(3,b16+b26+b36+b46+b56));\r\nformula rate7=mu*(1+min(3,b17+b27+b37+b47+b57));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\tb15 : [0..1];\r\n\tb16 : [0..1];\r\n\tb17 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t[] b15=0 -> rate5 : (b15'=1);\r\n\t[] b16=0 -> rate6 : (b16'=1);\r\n\t[] b17=0 -> rate7 : (b17'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b15=b25,b16=b26,b17=b27,b21=b11,b22=b12,b23=b13,b24=b14,b25=b15,b26=b16,b27=b17] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b15=b35,b16=b36,b17=b37,b31=b11,b32=b12,b33=b13,b34=b14,b35=b15,b36=b16,b37=b17] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b15=b45,b16=b46,b17=b47,b41=b11,b42=b12,b43=b13,b44=b14,b45=b15,b46=b16,b47=b17] endmodule\r\nmodule client5=client1[b11=b51,b12=b52,b13=b53,b14=b54,b15=b55,b16=b56,b17=b57,b51=b11,b52=b12,b53=b13,b54=b14,b55=b15,b56=b16,b57=b17] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14+b15+b16+b17 = 7; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24+b25+b26+b27 = 7; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34+b35+b36+b37 = 7; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44+b45+b46+b47 = 7; // client 4 has received all blocks\r\nlabel \"done5\" = b51+b52+b53+b54+b55+b56+b57 = 7; // client 5 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14+b15+b16+b17)+(b21+b22+b23+b24+b25+b26+b27)+(b31+b32+b33+b34+b35+b36+b37)+(b41+b42+b43+b44+b45+b46+b47)+(b51+b52+b53+b54+b55+b56+b57) = 35; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14+b15+b16+b17)/7)/5;\r\n\ttrue : ((b21+b22+b23+b24+b25+b26+b27)/7)/5;\r\n\ttrue : ((b31+b32+b33+b34+b35+b36+b37)/7)/5;\r\n\ttrue : ((b41+b42+b43+b44+b45+b46+b47)/7)/5;\r\n\ttrue : ((b51+b52+b53+b54+b55+b56+b57)/7)/5;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/peer2peer/peer2peer5_8.sm",
    "content": "// Simple peer-to-peer file distribution protocol based on BitTorrent\r\n// gxn/dxp Jan 2006\r\n\r\nctmc\r\n\r\n// N=5 clients, K=8 blocks to be downloaded\r\n// Actually there are N+1=6 clients, one of which has all blocks initially\r\n\r\n// Rate of block download for a single source\r\nconst double mu=2;\r\n\r\n// Rate of download of block i:\r\n// A client can download from the single client which starts with all blocks\r\n// or from anyone that has subsequently downloaded it.\r\n// Total number of concurrent downloads for each block is 4.\r\nformula rate1=mu*(1+min(3,b11+b21+b31+b41+b51));\r\nformula rate2=mu*(1+min(3,b12+b22+b32+b42+b52));\r\nformula rate3=mu*(1+min(3,b13+b23+b33+b43+b53));\r\nformula rate4=mu*(1+min(3,b14+b24+b34+b44+b54));\r\nformula rate5=mu*(1+min(3,b15+b25+b35+b45+b55));\r\nformula rate6=mu*(1+min(3,b16+b26+b36+b46+b56));\r\nformula rate7=mu*(1+min(3,b17+b27+b37+b47+b57));\r\nformula rate8=mu*(1+min(3,b18+b28+b38+b48+b58));\r\n\r\n// client 1\r\nmodule client1\r\n\t\r\n\t// bij - has client i downloaded block j yet?\r\n\tb11 : [0..1];\r\n\tb12 : [0..1];\r\n\tb13 : [0..1];\r\n\tb14 : [0..1];\r\n\tb15 : [0..1];\r\n\tb16 : [0..1];\r\n\tb17 : [0..1];\r\n\tb18 : [0..1];\r\n\t\r\n\t// Downloading of each block (see rate computations above)\r\n\t[] b11=0 -> rate1 : (b11'=1);\r\n\t[] b12=0 -> rate2 : (b12'=1);\r\n\t[] b13=0 -> rate3 : (b13'=1);\r\n\t[] b14=0 -> rate4 : (b14'=1);\r\n\t[] b15=0 -> rate5 : (b15'=1);\r\n\t[] b16=0 -> rate6 : (b16'=1);\r\n\t[] b17=0 -> rate7 : (b17'=1);\r\n\t[] b18=0 -> rate8 : (b18'=1);\r\n\t\r\nendmodule\r\n\r\n// construct remaining clients through renaming\r\nmodule client2=client1[b11=b21,b12=b22,b13=b23,b14=b24,b15=b25,b16=b26,b17=b27,b18=b28,b21=b11,b22=b12,b23=b13,b24=b14,b25=b15,b26=b16,b27=b17,b28=b18] endmodule\r\nmodule client3=client1[b11=b31,b12=b32,b13=b33,b14=b34,b15=b35,b16=b36,b17=b37,b18=b38,b31=b11,b32=b12,b33=b13,b34=b14,b35=b15,b36=b16,b37=b17,b38=b18] endmodule\r\nmodule client4=client1[b11=b41,b12=b42,b13=b43,b14=b44,b15=b45,b16=b46,b17=b47,b18=b48,b41=b11,b42=b12,b43=b13,b44=b14,b45=b15,b46=b16,b47=b17,b48=b18] endmodule\r\nmodule client5=client1[b11=b51,b12=b52,b13=b53,b14=b54,b15=b55,b16=b56,b17=b57,b18=b58,b51=b11,b52=b12,b53=b13,b54=b14,b55=b15,b56=b16,b57=b17,b58=b18] endmodule\r\n\r\n// labels\r\nlabel \"done1\" = b11+b12+b13+b14+b15+b16+b17+b18 = 8; // client 1 has received all blocks\r\nlabel \"done2\" = b21+b22+b23+b24+b25+b26+b27+b28 = 8; // client 2 has received all blocks\r\nlabel \"done3\" = b31+b32+b33+b34+b35+b36+b37+b38 = 8; // client 3 has received all blocks\r\nlabel \"done4\" = b41+b42+b43+b44+b45+b46+b47+b48 = 8; // client 4 has received all blocks\r\nlabel \"done5\" = b51+b52+b53+b54+b55+b56+b57+b58 = 8; // client 5 has received all blocks\r\nlabel \"done\" = (b11+b12+b13+b14+b15+b16+b17+b18)+(b21+b22+b23+b24+b25+b26+b27+b28)+(b31+b32+b33+b34+b35+b36+b37+b38)+(b41+b42+b43+b44+b45+b46+b47+b48)+(b51+b52+b53+b54+b55+b56+b57+b58) = 40; // all clients have received all blocks\r\n\r\n// reward: fraction of blocks received\r\nrewards \"frac_rec\"\r\n\ttrue : ((b11+b12+b13+b14+b15+b16+b17+b18)/8)/5;\r\n\ttrue : ((b21+b22+b23+b24+b25+b26+b27+b28)/8)/5;\r\n\ttrue : ((b31+b32+b33+b34+b35+b36+b37+b38)/8)/5;\r\n\ttrue : ((b41+b42+b43+b44+b45+b46+b47+b48)/8)/5;\r\n\ttrue : ((b51+b52+b53+b54+b55+b56+b57+b58)/8)/5;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/.autopp",
    "content": "#!/bin/csh\n\nforeach N (2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20)\n    echo \"Generating for N=$N\"\n    prismpp .pollN.sm.pp $N  >! poll\"$N\".sm\n    unix2dos poll\"$N\".sm\nend\n\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/.pollN.sm.pp",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\n#const N#\r\nconst int N = #N#;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..#N#]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t#for i=1:N-1#\r\n\t[loop#i#a] (s=#i#)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop#i#b] (s=#i#)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve#i#] (s=#i#)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t#end#\r\n\t[loop#N#a] (s=#N#)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop#N#b] (s=#N#)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve#N#] (s=#N#)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\n\r\n#for i=2:N#\r\nmodule station#i# = station1 [ s1=s#i#, loop1a=loop#i#a, loop1b=loop#i#b, serve1=serve#i# ] endmodule\r\n#end#\r\n// (cumulative) rewards\r\n\n// expected time station 1 is waiting to be served\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/README.txt",
    "content": "This case study is based on a cyclic server polling system, taken from [IT90].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/polling.php\r\n\r\n=====================================================================================\r\n\r\n[IT90]\r\nO. Ibe and K. Trivedi\r\nStochastic Petri Net Models of Polling Systems\r\nIn IEEE Journal on Selected Areas in Communications,8(9):1649-1657, 1990\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/auto",
    "content": "#!/bin/csh\n\nprism poll2.sm  poll.csl -const T=50\nprism poll3.sm  poll.csl -const T=50\nprism poll4.sm  poll.csl -const T=50\nprism poll5.sm  poll.csl -const T=50\nprism poll6.sm  poll.csl -const T=50\nprism poll7.sm  poll.csl -const T=50\nprism poll8.sm  poll.csl -const T=50\nprism poll9.sm  poll.csl -const T=50\n#prism poll10.sm poll.csl -const T=50\n#prism poll11.sm poll.csl -const T=50\n#prism poll12.sm poll.csl -const T=50\n#prism poll13.sm poll.csl -const T=50\n#prism poll14.sm poll.csl -const T=50\n#prism poll15.sm poll.csl -const T=50\n#prism poll16.sm poll.csl -const T=50\n#prism poll17.sm poll.csl -const T=50\n#prism poll18.sm poll.csl -const T=50\n#prism poll19.sm poll.csl -const T=50\n#prism poll20.sm poll.csl -const T=50\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll.csl",
    "content": "// Time bound\nconst double T;\r\n\n// Probability that in the long run station 1 is awaiting service \r\nS=? [ s1=1 & !(s=1 & a=1) ]\r\n\r\n// Probability that in the long run station 1 is idle \r\nS=? [ s1=0 ] \r\n\r\n// Once a station becomes full, the minimum probability it will eventually be polled\r\nP=? [ true U (s=1 & a=0) {s1=1}{min} ]\r\n\r\n// Probability, from the inital state, that station 1 is served before station 2\r\nP=? [ !(s=2 & a=1) U (s=1 & a=1) ]\r\n\r\n// Probability that station 1 will be polled within T time units\r\nP=?[ true U<=T (s=1 & a=0) ]\r\n\r\n// Expected time station 1 is waiting to be served\nR{\"waiting\"}=?[C<=T] \n\r\n// Expected number of times station1 is served\nR{\"served\"}=?[C<=T]\n\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll10.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 10;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..10]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll11.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 11;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..11]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll12.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 12;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..12]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll13.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 13;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..13]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop13a] (s=13)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop13b] (s=13)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve13] (s=13)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\nmodule station13 = station1 [ s1=s13, loop1a=loop13a, loop1b=loop13b, serve1=serve13 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll14.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 14;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..14]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop13a] (s=13)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop13b] (s=13)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve13] (s=13)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop14a] (s=14)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop14b] (s=14)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve14] (s=14)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\nmodule station13 = station1 [ s1=s13, loop1a=loop13a, loop1b=loop13b, serve1=serve13 ] endmodule\r\nmodule station14 = station1 [ s1=s14, loop1a=loop14a, loop1b=loop14b, serve1=serve14 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll15.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 15;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..15]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop13a] (s=13)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop13b] (s=13)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve13] (s=13)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop14a] (s=14)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop14b] (s=14)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve14] (s=14)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop15a] (s=15)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop15b] (s=15)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve15] (s=15)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\nmodule station13 = station1 [ s1=s13, loop1a=loop13a, loop1b=loop13b, serve1=serve13 ] endmodule\r\nmodule station14 = station1 [ s1=s14, loop1a=loop14a, loop1b=loop14b, serve1=serve14 ] endmodule\r\nmodule station15 = station1 [ s1=s15, loop1a=loop15a, loop1b=loop15b, serve1=serve15 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll16.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 16;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..16]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop13a] (s=13)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop13b] (s=13)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve13] (s=13)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop14a] (s=14)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop14b] (s=14)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve14] (s=14)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop15a] (s=15)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop15b] (s=15)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve15] (s=15)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop16a] (s=16)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop16b] (s=16)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve16] (s=16)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\nmodule station13 = station1 [ s1=s13, loop1a=loop13a, loop1b=loop13b, serve1=serve13 ] endmodule\r\nmodule station14 = station1 [ s1=s14, loop1a=loop14a, loop1b=loop14b, serve1=serve14 ] endmodule\r\nmodule station15 = station1 [ s1=s15, loop1a=loop15a, loop1b=loop15b, serve1=serve15 ] endmodule\r\nmodule station16 = station1 [ s1=s16, loop1a=loop16a, loop1b=loop16b, serve1=serve16 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll17.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 17;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..17]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop13a] (s=13)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop13b] (s=13)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve13] (s=13)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop14a] (s=14)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop14b] (s=14)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve14] (s=14)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop15a] (s=15)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop15b] (s=15)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve15] (s=15)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop16a] (s=16)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop16b] (s=16)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve16] (s=16)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop17a] (s=17)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop17b] (s=17)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve17] (s=17)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\nmodule station13 = station1 [ s1=s13, loop1a=loop13a, loop1b=loop13b, serve1=serve13 ] endmodule\r\nmodule station14 = station1 [ s1=s14, loop1a=loop14a, loop1b=loop14b, serve1=serve14 ] endmodule\r\nmodule station15 = station1 [ s1=s15, loop1a=loop15a, loop1b=loop15b, serve1=serve15 ] endmodule\r\nmodule station16 = station1 [ s1=s16, loop1a=loop16a, loop1b=loop16b, serve1=serve16 ] endmodule\r\nmodule station17 = station1 [ s1=s17, loop1a=loop17a, loop1b=loop17b, serve1=serve17 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll18.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 18;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..18]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop13a] (s=13)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop13b] (s=13)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve13] (s=13)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop14a] (s=14)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop14b] (s=14)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve14] (s=14)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop15a] (s=15)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop15b] (s=15)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve15] (s=15)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop16a] (s=16)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop16b] (s=16)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve16] (s=16)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop17a] (s=17)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop17b] (s=17)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve17] (s=17)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop18a] (s=18)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop18b] (s=18)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve18] (s=18)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\nmodule station13 = station1 [ s1=s13, loop1a=loop13a, loop1b=loop13b, serve1=serve13 ] endmodule\r\nmodule station14 = station1 [ s1=s14, loop1a=loop14a, loop1b=loop14b, serve1=serve14 ] endmodule\r\nmodule station15 = station1 [ s1=s15, loop1a=loop15a, loop1b=loop15b, serve1=serve15 ] endmodule\r\nmodule station16 = station1 [ s1=s16, loop1a=loop16a, loop1b=loop16b, serve1=serve16 ] endmodule\r\nmodule station17 = station1 [ s1=s17, loop1a=loop17a, loop1b=loop17b, serve1=serve17 ] endmodule\r\nmodule station18 = station1 [ s1=s18, loop1a=loop18a, loop1b=loop18b, serve1=serve18 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll19.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 19;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..19]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop13a] (s=13)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop13b] (s=13)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve13] (s=13)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop14a] (s=14)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop14b] (s=14)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve14] (s=14)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop15a] (s=15)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop15b] (s=15)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve15] (s=15)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop16a] (s=16)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop16b] (s=16)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve16] (s=16)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop17a] (s=17)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop17b] (s=17)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve17] (s=17)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop18a] (s=18)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop18b] (s=18)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve18] (s=18)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop19a] (s=19)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop19b] (s=19)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve19] (s=19)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\nmodule station13 = station1 [ s1=s13, loop1a=loop13a, loop1b=loop13b, serve1=serve13 ] endmodule\r\nmodule station14 = station1 [ s1=s14, loop1a=loop14a, loop1b=loop14b, serve1=serve14 ] endmodule\r\nmodule station15 = station1 [ s1=s15, loop1a=loop15a, loop1b=loop15b, serve1=serve15 ] endmodule\r\nmodule station16 = station1 [ s1=s16, loop1a=loop16a, loop1b=loop16b, serve1=serve16 ] endmodule\r\nmodule station17 = station1 [ s1=s17, loop1a=loop17a, loop1b=loop17b, serve1=serve17 ] endmodule\r\nmodule station18 = station1 [ s1=s18, loop1a=loop18a, loop1b=loop18b, serve1=serve18 ] endmodule\r\nmodule station19 = station1 [ s1=s19, loop1a=loop19a, loop1b=loop19b, serve1=serve19 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll2.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 2;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..2]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll20.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 20;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..20]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop10a] (s=10)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop10b] (s=10)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve10] (s=10)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop11a] (s=11)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop11b] (s=11)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve11] (s=11)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop12a] (s=12)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop12b] (s=12)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve12] (s=12)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop13a] (s=13)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop13b] (s=13)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve13] (s=13)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop14a] (s=14)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop14b] (s=14)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve14] (s=14)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop15a] (s=15)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop15b] (s=15)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve15] (s=15)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop16a] (s=16)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop16b] (s=16)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve16] (s=16)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop17a] (s=17)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop17b] (s=17)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve17] (s=17)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop18a] (s=18)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop18b] (s=18)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve18] (s=18)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop19a] (s=19)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop19b] (s=19)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve19] (s=19)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop20a] (s=20)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop20b] (s=20)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve20] (s=20)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\nmodule station10 = station1 [ s1=s10, loop1a=loop10a, loop1b=loop10b, serve1=serve10 ] endmodule\r\nmodule station11 = station1 [ s1=s11, loop1a=loop11a, loop1b=loop11b, serve1=serve11 ] endmodule\r\nmodule station12 = station1 [ s1=s12, loop1a=loop12a, loop1b=loop12b, serve1=serve12 ] endmodule\r\nmodule station13 = station1 [ s1=s13, loop1a=loop13a, loop1b=loop13b, serve1=serve13 ] endmodule\r\nmodule station14 = station1 [ s1=s14, loop1a=loop14a, loop1b=loop14b, serve1=serve14 ] endmodule\r\nmodule station15 = station1 [ s1=s15, loop1a=loop15a, loop1b=loop15b, serve1=serve15 ] endmodule\r\nmodule station16 = station1 [ s1=s16, loop1a=loop16a, loop1b=loop16b, serve1=serve16 ] endmodule\r\nmodule station17 = station1 [ s1=s17, loop1a=loop17a, loop1b=loop17b, serve1=serve17 ] endmodule\r\nmodule station18 = station1 [ s1=s18, loop1a=loop18a, loop1b=loop18b, serve1=serve18 ] endmodule\r\nmodule station19 = station1 [ s1=s19, loop1a=loop19a, loop1b=loop19b, serve1=serve19 ] endmodule\r\nmodule station20 = station1 [ s1=s20, loop1a=loop20a, loop1b=loop20b, serve1=serve20 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll3.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 3;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..3]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll4.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 4;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..4]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll5.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 5;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..5]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll6.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 6;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..6]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll7.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 7;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..7]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll8.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 8;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..8]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/polling/poll9.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 9;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..9]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop6a] (s=6)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop6b] (s=6)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve6] (s=6)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop7a] (s=7)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop7b] (s=7)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve7] (s=7)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop8a] (s=8)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop8b] (s=8)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve8] (s=8)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop9a] (s=9)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop9b] (s=9)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve9] (s=9)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\nmodule station6 = station1 [ s1=s6, loop1a=loop6a, loop1b=loop6b, serve1=serve6 ] endmodule\r\nmodule station7 = station1 [ s1=s7, loop1a=loop7a, loop1b=loop7b, serve1=serve7 ] endmodule\r\nmodule station8 = station1 [ s1=s8, loop1a=loop8a, loop1b=loop8b, serve1=serve8 ] endmodule\r\nmodule station9 = station1 [ s1=s9, loop1a=loop9a, loop1b=loop9b, serve1=serve9 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ctmcs/tandem/README.txt",
    "content": "This case study is based on a simple tandem queueing network, taken from [HMKS99].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/tandem.php\r\n\r\n=====================================================================================\r\n\r\n[HMKS99]\r\nH. Hermanns, J. Meyer-Kayser and M. Siegle\r\nMulti-Terminal Binary Decision Diagrams to Represent and Analyse Continuous Time Markov Chains\r\nIn Proc. 3rd International Workshop on the Numerical Solution of Markov Chains, pp. 188-207, 1999\r\n"
  },
  {
    "path": "prism-examples/ctmcs/tandem/auto",
    "content": "#!/bin/csh\n\nforeach c ( 3 7 15 31 63 127 255 ) #511 1023 2047 4095 8191 )\n\tprism tandem.sm tandem.csl -const T=1,c=$c\nend\n"
  },
  {
    "path": "prism-examples/ctmcs/tandem/tandem.csl",
    "content": "const double T;\r\n\r\n// long run expected customers in the network\r\nR=?[S]\r\n\r\n// probability network becomes full in T time units\r\nP=? [ true U<=T sc=c & sm=c & ph=2 ]\r\n\r\n// probability first queue becomes full in T time units\r\nP=? [ true U<=T sc=c ]\r\n\r\n// the minimimum probability of leaving a situation where the second queue is entirely populated within T time units\r\nP=? [ sm=c U<=T sm<c {sm=c}{min} ]\r\n\r\n// expected number of customers in the network\r\nR=?[I=T]\r\n"
  },
  {
    "path": "prism-examples/ctmcs/tandem/tandem.sm",
    "content": "// tandem queueing network [HKMKS99]\r\n// gxn/dxp 25/01/00\r\n\r\nctmc\r\n\r\nconst int c; // queue capacity\r\n\r\nconst double lambda = 4*c;\r\nconst double mu1a = 0.1*2;\r\nconst double mu1b = 0.9*2;\r\nconst double mu2 = 2;\r\nconst double kappa = 4;\r\n\r\nmodule serverC\r\n\t\r\n\tsc : [0..c];\r\n\tph : [1..2];\r\n\t\r\n\t[] (sc<c) -> lambda: (sc'=sc+1); \r\n\t[route] (sc>0) & (ph=1) -> mu1b: (sc'=sc-1);\r\n\t[] (sc>0) & (ph=1) -> mu1a: (ph'=2); \r\n\t[route] (sc>0) & (ph=2) -> mu2: (ph'=1) & (sc'=sc-1);\r\n\t\r\nendmodule  \r\n\r\nmodule serverM\r\n\t\r\n\tsm : [0..c];\r\n\t\r\n\t[route]\t(sm<c) -> 1: (sm'=sm+1);\r\n\t[] (sm>0) -> kappa: (sm'=sm-1);\r\n\t\r\nendmodule\r\n\r\n// reward - number of customers in network\r\nrewards \"customers\"\r\n\ttrue : sc + sm;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/dtmcs/brp/README.txt",
    "content": "This case study is based on the bounded retransmission protocol (BRP) [HSV94], a variant of the alternating bit protocol.\r\n\r\nIts parameters are:\r\n\r\n  N = number of chunks in a file\r\n  MAX = maximum number of retransmissions\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/brp.php\r\n\r\n=====================================================================================\r\n\r\n[HSV94]\r\nL. Helmink, M. Sellink and F Vaandrager\r\nProof checking a data link protocol\r\nIn Proc. Types for Proofs and Programs (TYPES'93), LNCS 806, pp 127-165, Springer-Verlag, 1994\r\n"
  },
  {
    "path": "prism-examples/dtmcs/brp/auto",
    "content": "#!/bin/csh\n\nforeach N (16 32 64)\n\tforeach MAX (2 3 4 5)\n\t\tprism brp.pm brp.pctl -const N=$N,MAX=$MAX -fixdl\n\tend\nend\n"
  },
  {
    "path": "prism-examples/dtmcs/brp/brp.pctl",
    "content": "// properties taken from [D'AJJL01]\r\n\r\n// property A\r\nP=? [ true U srep=1 & rrep=3 & recv ];\r\n\r\n// property B\r\nP=? [ true U srep=3 & !(rrep=3) & recv ];\r\n\r\n// property 1\r\nP=? [ true U s=5 ];\r\n\r\n// property 2\r\nP=? [ true U s=5 & srep=2 ];\r\n\r\n// property 3\r\nP=? [ true U s=5 & srep=1 & i>8 ];\r\n\r\n// property 4\r\nP=? [ true U !(srep=0) & !recv ];\r\n// rewards\nR=? [ F \"deadlock\" ];\n"
  },
  {
    "path": "prism-examples/dtmcs/brp/brp.pm",
    "content": "// bounded retransmission protocol [D'AJJL01]\r\n// gxn/dxp 23/05/2001\r\n\r\ndtmc\r\n\r\n// number of chunks\r\nconst int N;\r\n// maximum number of retransmissions\r\nconst int MAX;\r\n\r\nmodule sender\r\n\r\n\ts : [0..6];\r\n\t// 0 idle\r\n\t// 1 next_frame\t\r\n\t// 2 wait_ack\r\n\t// 3 retransmit\r\n\t// 4 success\r\n\t// 5 error\r\n\t// 6 wait sync\r\n\tsrep : [0..3];\r\n\t// 0 bottom\r\n\t// 1 not ok (nok)\r\n\t// 2 do not know (dk)\r\n\t// 3 ok (ok)\r\n\tnrtr : [0..MAX];\r\n\ti : [0..N];\r\n\tbs : bool;\r\n\ts_ab : bool;\r\n\tfs : bool;\r\n\tls : bool;\r\n\t\r\n\t// idle\r\n\t[NewFile] (s=0) -> (s'=1) & (i'=1) & (srep'=0);\r\n\t// next_frame\r\n\t[aF] (s=1) -> (s'=2) & (fs'=(i=1)) & (ls'=(i=N)) & (bs'=s_ab) & (nrtr'=0);\r\n\t// wait_ack\r\n\t[aB] (s=2) -> (s'=4) & (s_ab'=!s_ab);\r\n\t[TO_Msg] (s=2) -> (s'=3);\r\n\t[TO_Ack] (s=2) -> (s'=3);\r\n\t// retransmit\r\n\t[aF] (s=3) & (nrtr<MAX) -> (s'=2) & (fs'=(i=1)) & (ls'=(i=N)) & (bs'=s_ab) & (nrtr'=nrtr+1);\r\n\t[] (s=3) & (nrtr=MAX) & (i<N) -> (s'=5) & (srep'=1);\r\n\t[] (s=3) & (nrtr=MAX) & (i=N) -> (s'=5) & (srep'=2);\r\n\t// success\r\n\t[] (s=4) & (i<N) -> (s'=1) & (i'=i+1);\r\n\t[] (s=4) & (i=N) -> (s'=0) & (srep'=3);\r\n\t// error\r\n\t[SyncWait] (s=5) -> (s'=6); \r\n\t// wait sync\r\n\t[SyncWait] (s=6) -> (s'=0) & (s_ab'=false); \r\n\t\r\nendmodule\r\n\r\nmodule receiver\r\n\r\n\tr : [0..5];\r\n\t// 0 new_file\r\n\t// 1 fst_safe\r\n\t// 2 frame_received\r\n\t// 3 frame_reported\r\n\t// 4 idle\r\n\t// 5 resync\r\n\trrep : [0..4];\r\n\t// 0 bottom\r\n\t// 1 fst\r\n\t// 2 inc\r\n\t// 3 ok\r\n\t// 4 nok\r\n\tfr : bool;\r\n\tlr : bool;\r\n\tbr : bool;\r\n\tr_ab : bool;\r\n\trecv : bool;\r\n\t\r\n\t\r\n\t// new_file\r\n\t[SyncWait] (r=0) -> (r'=0);\r\n\t[aG] (r=0) -> (r'=1) & (fr'=fs) & (lr'=ls) & (br'=bs) & (recv'=T);\r\n\t// fst_safe_frame\r\n\t[] (r=1) -> (r'=2) & (r_ab'=br);\r\n\t// frame_received\r\n\t[] (r=2) & (r_ab=br) & (fr=true) & (lr=false)  -> (r'=3) & (rrep'=1);\r\n\t[] (r=2) & (r_ab=br) & (fr=false) & (lr=false) -> (r'=3) & (rrep'=2);\r\n\t[] (r=2) & (r_ab=br) & (fr=false) & (lr=true)  -> (r'=3) & (rrep'=3);\r\n\t[aA] (r=2) & !(r_ab=br) -> (r'=4);  \r\n\t// frame_reported\r\n\t[aA] (r=3) -> (r'=4) & (r_ab'=!r_ab);\r\n\t// idle\r\n\t[aG] (r=4) -> (r'=2) & (fr'=fs) & (lr'=ls) & (br'=bs) & (recv'=T);\r\n\t[SyncWait] (r=4) & (ls=true) -> (r'=5);\r\n\t[SyncWait] (r=4) & (ls=false) -> (r'=5) & (rrep'=4);\r\n\t// resync\r\n\t[SyncWait] (r=5) -> (r'=0) & (rrep'=0);\r\n\t\r\nendmodule\r\n\t\r\nmodule checker // prevents more than one frame being set\r\n\r\n\tT : bool;\r\n\t\r\n\t[NewFile] (T=false) -> (T'=true);\r\n\t\r\nendmodule\r\n\r\nmodule\tchannelK\r\n\r\n\tk : [0..2];\r\n\t\r\n\t// idle\r\n\t[aF] (k=0) -> 0.98 : (k'=1) + 0.02 : (k'=2);\r\n\t// sending\r\n\t[aG] (k=1) -> (k'=0);\r\n\t// lost\r\n\t[TO_Msg] (k=2) -> (k'=0);\r\n\t\r\nendmodule\r\n\r\nmodule\tchannelL\r\n\r\n\tl : [0..2];\r\n\t\r\n\t// idle\r\n\t[aA] (l=0) -> 0.99 : (l'=1) + 0.01 : (l'=2);\r\n\t// sending\r\n\t[aB] (l=1) -> (l'=0);\r\n\t// lost\r\n\t[TO_Ack] (l=2) -> (l'=0);\r\n\t\r\nendmodule\n\nrewards\n\t[aF] i=1 : 1;\nendrewards\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 5 7 9 11 13 15 17 19 21 )\n\techo \"Generating for N=$N\"\n\tprismpp .hermanN.pm.pp $N >! herman$N.pm\n\tunix2dos herman$N.pm\n\t#prismpp .hermanNmod.pm.pp $N >! herman\"$N\"mod.pm\n\t#unix2dos herman\"$N\"mod.pm\nend\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/.hermanN.pm.pp",
    "content": "#const N#\r\n// herman's self stabilising algorithm [Her90]\n// gxn/dxp 13/07/02\n\n// the procotol is synchronous with no nondeterminism (a DTMC)\ndtmc\n\nconst double p = 0.5;\n\n// module for process 1\nmodule process1\n\n\t// Boolean variable for process 1\n\tx1 : [0..1];\n\t\n\t[step]  (x1=x#N#) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x#N#) -> (x1'=x#N#);\r\n\t\nendmodule\n\n// add further processes through renaming\r\n#for i=2:N#\r\nmodule process#i# = process1 [ x1=x#i#, x#N#=x#i-1# ] endmodule\r\n#end#\r\n\n// cost - 1 in each state (expected number of steps)\nrewards \"steps\"\n\ttrue : 1;\nendrewards\n\n// set of initial states: all (i.e. any possible initial configuration of tokens)\ninit\n\ttrue\nendinit\n\n// formula, for use in properties: number of tokens\n// (i.e. number of processes that have the same value as the process to their left)\nformula num_tokens = #+ i=1:N#(x#i#=x#func(mod, i, N)+1#?1:0)#end#;\n\n// label - stable configurations (1 token)\nlabel \"stable\" = num_tokens=1;\n\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/README.txt",
    "content": "This case study is based on Herman's self-stabilising algorithm [Her90].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/self-stabilisation.php\r\n\r\n=====================================================================================\r\n\r\n[Her90]\r\nT. Herman\r\nProbabilistic self-stabilization\r\nIn Information Processing Letters, 35(2):63-67, 1990\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/auto",
    "content": "#!/bin/csh\n\nprism herman7.pm herman.pctl -prop 1 -const k=0,K=0\nprism herman7.pm herman.pctl -prop 2 -const k=0,K=0\nprism herman7.pm herman.pctl -prop 3 -const k=1:2:7,K=0\nprism herman7.pm herman.pctl -prop 4 -const k=1:2:7,K=0\nprism herman7.pm herman.pctl -prop 5 -const k=0,K=1:1:100\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman.pctl",
    "content": "const int k; // number of tokens\nconst int K; // number of steps\n\n// labels\nlabel \"k_tokens\" = num_tokens=k; // configurations with k tokens\n\n// From any configuration, a stable configuration is reached with probability 1\nfilter(forall, \"init\" => P>=1 [ F \"stable\" ])\n\n// Maximum expected time to reach a stable configuration (for all configurations)\nR=? [ F \"stable\" {\"init\"}{max} ]\n\n// Maximum/minimum expected time to reach a stable configuration (for all k-token configurations)\nR=? [ F \"stable\" {\"k_tokens\"}{max} ]\nR=? [ F \"stable\" {\"k_tokens\"}{min} ]\n\n// Minimum probability reached a stable configuration within K steps (for all configurations)\nP=? [ F<=K \"stable\" {\"init\"}{min} ]\n\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman11.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x11) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x11) -> (x1'=x11);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x11=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x11=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x11=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x11=x4 ] endmodule\r\nmodule process6 = process1 [ x1=x6, x11=x5 ] endmodule\r\nmodule process7 = process1 [ x1=x7, x11=x6 ] endmodule\r\nmodule process8 = process1 [ x1=x8, x11=x7 ] endmodule\r\nmodule process9 = process1 [ x1=x9, x11=x8 ] endmodule\r\nmodule process10 = process1 [ x1=x10, x11=x9 ] endmodule\r\nmodule process11 = process1 [ x1=x11, x11=x10 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x6?1:0)+(x6=x7?1:0)+(x7=x8?1:0)+(x8=x9?1:0)+(x9=x10?1:0)+(x10=x11?1:0)+(x11=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman13.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x13) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x13) -> (x1'=x13);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x13=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x13=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x13=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x13=x4 ] endmodule\r\nmodule process6 = process1 [ x1=x6, x13=x5 ] endmodule\r\nmodule process7 = process1 [ x1=x7, x13=x6 ] endmodule\r\nmodule process8 = process1 [ x1=x8, x13=x7 ] endmodule\r\nmodule process9 = process1 [ x1=x9, x13=x8 ] endmodule\r\nmodule process10 = process1 [ x1=x10, x13=x9 ] endmodule\r\nmodule process11 = process1 [ x1=x11, x13=x10 ] endmodule\r\nmodule process12 = process1 [ x1=x12, x13=x11 ] endmodule\r\nmodule process13 = process1 [ x1=x13, x13=x12 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x6?1:0)+(x6=x7?1:0)+(x7=x8?1:0)+(x8=x9?1:0)+(x9=x10?1:0)+(x10=x11?1:0)+(x11=x12?1:0)+(x12=x13?1:0)+(x13=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman15.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x15) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x15) -> (x1'=x15);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x15=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x15=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x15=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x15=x4 ] endmodule\r\nmodule process6 = process1 [ x1=x6, x15=x5 ] endmodule\r\nmodule process7 = process1 [ x1=x7, x15=x6 ] endmodule\r\nmodule process8 = process1 [ x1=x8, x15=x7 ] endmodule\r\nmodule process9 = process1 [ x1=x9, x15=x8 ] endmodule\r\nmodule process10 = process1 [ x1=x10, x15=x9 ] endmodule\r\nmodule process11 = process1 [ x1=x11, x15=x10 ] endmodule\r\nmodule process12 = process1 [ x1=x12, x15=x11 ] endmodule\r\nmodule process13 = process1 [ x1=x13, x15=x12 ] endmodule\r\nmodule process14 = process1 [ x1=x14, x15=x13 ] endmodule\r\nmodule process15 = process1 [ x1=x15, x15=x14 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x6?1:0)+(x6=x7?1:0)+(x7=x8?1:0)+(x8=x9?1:0)+(x9=x10?1:0)+(x10=x11?1:0)+(x11=x12?1:0)+(x12=x13?1:0)+(x13=x14?1:0)+(x14=x15?1:0)+(x15=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman17.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x17) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x17) -> (x1'=x17);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x17=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x17=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x17=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x17=x4 ] endmodule\r\nmodule process6 = process1 [ x1=x6, x17=x5 ] endmodule\r\nmodule process7 = process1 [ x1=x7, x17=x6 ] endmodule\r\nmodule process8 = process1 [ x1=x8, x17=x7 ] endmodule\r\nmodule process9 = process1 [ x1=x9, x17=x8 ] endmodule\r\nmodule process10 = process1 [ x1=x10, x17=x9 ] endmodule\r\nmodule process11 = process1 [ x1=x11, x17=x10 ] endmodule\r\nmodule process12 = process1 [ x1=x12, x17=x11 ] endmodule\r\nmodule process13 = process1 [ x1=x13, x17=x12 ] endmodule\r\nmodule process14 = process1 [ x1=x14, x17=x13 ] endmodule\r\nmodule process15 = process1 [ x1=x15, x17=x14 ] endmodule\r\nmodule process16 = process1 [ x1=x16, x17=x15 ] endmodule\r\nmodule process17 = process1 [ x1=x17, x17=x16 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x6?1:0)+(x6=x7?1:0)+(x7=x8?1:0)+(x8=x9?1:0)+(x9=x10?1:0)+(x10=x11?1:0)+(x11=x12?1:0)+(x12=x13?1:0)+(x13=x14?1:0)+(x14=x15?1:0)+(x15=x16?1:0)+(x16=x17?1:0)+(x17=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman19.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x19) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x19) -> (x1'=x19);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x19=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x19=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x19=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x19=x4 ] endmodule\r\nmodule process6 = process1 [ x1=x6, x19=x5 ] endmodule\r\nmodule process7 = process1 [ x1=x7, x19=x6 ] endmodule\r\nmodule process8 = process1 [ x1=x8, x19=x7 ] endmodule\r\nmodule process9 = process1 [ x1=x9, x19=x8 ] endmodule\r\nmodule process10 = process1 [ x1=x10, x19=x9 ] endmodule\r\nmodule process11 = process1 [ x1=x11, x19=x10 ] endmodule\r\nmodule process12 = process1 [ x1=x12, x19=x11 ] endmodule\r\nmodule process13 = process1 [ x1=x13, x19=x12 ] endmodule\r\nmodule process14 = process1 [ x1=x14, x19=x13 ] endmodule\r\nmodule process15 = process1 [ x1=x15, x19=x14 ] endmodule\r\nmodule process16 = process1 [ x1=x16, x19=x15 ] endmodule\r\nmodule process17 = process1 [ x1=x17, x19=x16 ] endmodule\r\nmodule process18 = process1 [ x1=x18, x19=x17 ] endmodule\r\nmodule process19 = process1 [ x1=x19, x19=x18 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x6?1:0)+(x6=x7?1:0)+(x7=x8?1:0)+(x8=x9?1:0)+(x9=x10?1:0)+(x10=x11?1:0)+(x11=x12?1:0)+(x12=x13?1:0)+(x13=x14?1:0)+(x14=x15?1:0)+(x15=x16?1:0)+(x16=x17?1:0)+(x17=x18?1:0)+(x18=x19?1:0)+(x19=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman21.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x21) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x21) -> (x1'=x21);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x21=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x21=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x21=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x21=x4 ] endmodule\r\nmodule process6 = process1 [ x1=x6, x21=x5 ] endmodule\r\nmodule process7 = process1 [ x1=x7, x21=x6 ] endmodule\r\nmodule process8 = process1 [ x1=x8, x21=x7 ] endmodule\r\nmodule process9 = process1 [ x1=x9, x21=x8 ] endmodule\r\nmodule process10 = process1 [ x1=x10, x21=x9 ] endmodule\r\nmodule process11 = process1 [ x1=x11, x21=x10 ] endmodule\r\nmodule process12 = process1 [ x1=x12, x21=x11 ] endmodule\r\nmodule process13 = process1 [ x1=x13, x21=x12 ] endmodule\r\nmodule process14 = process1 [ x1=x14, x21=x13 ] endmodule\r\nmodule process15 = process1 [ x1=x15, x21=x14 ] endmodule\r\nmodule process16 = process1 [ x1=x16, x21=x15 ] endmodule\r\nmodule process17 = process1 [ x1=x17, x21=x16 ] endmodule\r\nmodule process18 = process1 [ x1=x18, x21=x17 ] endmodule\r\nmodule process19 = process1 [ x1=x19, x21=x18 ] endmodule\r\nmodule process20 = process1 [ x1=x20, x21=x19 ] endmodule\r\nmodule process21 = process1 [ x1=x21, x21=x20 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x6?1:0)+(x6=x7?1:0)+(x7=x8?1:0)+(x8=x9?1:0)+(x9=x10?1:0)+(x10=x11?1:0)+(x11=x12?1:0)+(x12=x13?1:0)+(x13=x14?1:0)+(x14=x15?1:0)+(x15=x16?1:0)+(x16=x17?1:0)+(x17=x18?1:0)+(x18=x19?1:0)+(x19=x20?1:0)+(x20=x21?1:0)+(x21=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman3.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x3) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x3) -> (x1'=x3);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x3=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x3=x2 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman5.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x5) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x5) -> (x1'=x5);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x5=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x5=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x5=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x5=x4 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman7.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x7) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x7) -> (x1'=x7);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x7=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x7=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x7=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x7=x4 ] endmodule\r\nmodule process6 = process1 [ x1=x6, x7=x5 ] endmodule\r\nmodule process7 = process1 [ x1=x7, x7=x6 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x6?1:0)+(x6=x7?1:0)+(x7=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/herman/herman9.pm",
    "content": "// herman's self stabilising algorithm [Her90]\r\n// gxn/dxp 13/07/02\r\n\r\n// the procotol is synchronous with no nondeterminism (a DTMC)\r\ndtmc\r\n\r\nconst double p = 0.5;\r\n\r\n// module for process 1\r\nmodule process1\r\n\r\n\t// Boolean variable for process 1\r\n\tx1 : [0..1];\r\n\t\r\n\t[step]  (x1=x9) -> p : (x1'=0) + 1-p : (x1'=1);\r\n\t[step] !(x1=x9) -> (x1'=x9);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ x1=x2, x9=x1 ] endmodule\r\nmodule process3 = process1 [ x1=x3, x9=x2 ] endmodule\r\nmodule process4 = process1 [ x1=x4, x9=x3 ] endmodule\r\nmodule process5 = process1 [ x1=x5, x9=x4 ] endmodule\r\nmodule process6 = process1 [ x1=x6, x9=x5 ] endmodule\r\nmodule process7 = process1 [ x1=x7, x9=x6 ] endmodule\r\nmodule process8 = process1 [ x1=x8, x9=x7 ] endmodule\r\nmodule process9 = process1 [ x1=x9, x9=x8 ] endmodule\r\n\r\n// cost - 1 in each state (expected number of steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// set of initial states: all (i.e. any possible initial configuration of tokens)\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\n// (i.e. number of processes that have the same value as the process to their left)\r\nformula num_tokens = (x1=x2?1:0)+(x2=x3?1:0)+(x3=x4?1:0)+(x4=x5?1:0)+(x5=x6?1:0)+(x6=x7?1:0)+(x7=x8?1:0)+(x8=x9?1:0)+(x9=x1?1:0);\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 6 )\n  foreach K ( 2 3 4 5 6 8 )\n    echo \"Generating for N=$N, K=$K\"\n    prismpp .leaderN_K.pm.pp $N $K >! leader\"$N\"_\"$K\".pm\n    unix2dos leader\"$N\"_\"$K\".pm\n  end\nend\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/.leaderN_K.pm.pp",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\n#const N#\nconst N = #N#; // number of processes\r\n#const K#\nconst K = #K#; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] #| i=1:N#u#i##end# -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(#| i=1:N#u#i##end#) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)#for i=1:K-1#\n\t             + 1/K : (s1'=1) & (p1'=#i#) & (v1'=#i#) & (u1'=true)#end#;\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\n#for i=2:N#\nmodule process#i# = process1 [ s1=s#i#,p1=p#i#,v1=v#i#,u1=u#i#,v2=v#mod(i,N)+1# ] endmodule\r\n#end#\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\n\r\n// labels\nlabel \"elected\" = #& i=1:N#s#i#=3#end#;\n\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/README.txt",
    "content": "This case study is based on the synchronous leader election protocol of Itai & Rodeh [IR90].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/synchronous_leader.php\r\n\r\n=====================================================================================\r\n\r\n[IR90]\r\nA. Itai and M. Rodeh\r\nSymmetry Breaking in Distributed Networks\r\nIn Information and Computation, 88:60-97, 1990\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/auto",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 ) # 6 )\n  foreach K ( 2 3 4 ) # 5 6 8 )\n    prism leader\"$N\"_\"$K\".pm leader.pctl -const L=1\n  end\nend\n\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader.pctl",
    "content": "const int L;\r\n\r\n// Probability that a leader is eventually elected\r\nP=? [ F \"elected\" ]\r\n\r\n// Probability that a leader is elected within L rounds\r\nP=? [ F<=(L*(N+1)) \"elected\" ]\r\n\r\n// Expected time (num. rounds) to elect a leader\r\nR{\"num_rounds\"}=? [ F \"elected\" ]\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader3_2.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 3; // number of processes\r\nconst K = 2; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader3_3.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 3; // number of processes\r\nconst K = 3; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader3_4.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 3; // number of processes\r\nconst K = 4; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader3_5.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 3; // number of processes\r\nconst K = 5; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader3_6.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 3; // number of processes\r\nconst K = 6; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=5) & (v1'=5) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader3_8.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 3; // number of processes\r\nconst K = 8; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=5) & (v1'=5) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=6) & (v1'=6) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=7) & (v1'=7) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader4_2.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 4; // number of processes\r\nconst K = 2; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader4_3.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 4; // number of processes\r\nconst K = 3; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader4_4.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 4; // number of processes\r\nconst K = 4; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader4_5.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 4; // number of processes\r\nconst K = 5; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader4_6.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 4; // number of processes\r\nconst K = 6; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=5) & (v1'=5) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader4_8.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 4; // number of processes\r\nconst K = 8; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=5) & (v1'=5) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=6) & (v1'=6) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=7) & (v1'=7) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader5_2.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 5; // number of processes\r\nconst K = 2; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader5_3.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 5; // number of processes\r\nconst K = 3; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader5_4.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 5; // number of processes\r\nconst K = 4; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader5_5.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 5; // number of processes\r\nconst K = 5; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader5_6.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 5; // number of processes\r\nconst K = 6; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=5) & (v1'=5) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader5_8.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 5; // number of processes\r\nconst K = 8; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=5) & (v1'=5) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=6) & (v1'=6) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=7) & (v1'=7) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader6_2.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 6; // number of processes\r\nconst K = 2; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5|u6 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5|u6) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v6 ] endmodule\r\nmodule process6 = process1 [ s1=s6,p1=p6,v1=v6,u1=u6,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3&s6=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader6_3.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 6; // number of processes\r\nconst K = 3; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5|u6 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5|u6) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v6 ] endmodule\r\nmodule process6 = process1 [ s1=s6,p1=p6,v1=v6,u1=u6,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3&s6=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader6_4.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 6; // number of processes\r\nconst K = 4; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5|u6 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5|u6) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v6 ] endmodule\r\nmodule process6 = process1 [ s1=s6,p1=p6,v1=v6,u1=u6,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3&s6=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader6_5.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 6; // number of processes\r\nconst K = 5; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5|u6 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5|u6) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v6 ] endmodule\r\nmodule process6 = process1 [ s1=s6,p1=p6,v1=v6,u1=u6,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3&s6=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader6_6.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 6; // number of processes\r\nconst K = 6; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5|u6 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5|u6) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=5) & (v1'=5) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v6 ] endmodule\r\nmodule process6 = process1 [ s1=s6,p1=p6,v1=v6,u1=u6,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3&s6=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/dtmcs/leader_sync/leader6_8.pm",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 6; // number of processes\r\nconst K = 8; // range of probabilistic choice\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3|u4|u5|u6 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3|u4|u5|u6) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> 1/K : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=2) & (v1'=2) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=3) & (v1'=3) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=4) & (v1'=4) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=5) & (v1'=5) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=6) & (v1'=6) & (u1'=true)\r\n\t             + 1/K : (s1'=1) & (p1'=7) & (v1'=7) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v4 ] endmodule\r\nmodule process4 = process1 [ s1=s4,p1=p4,v1=v4,u1=u4,v2=v5 ] endmodule\r\nmodule process5 = process1 [ s1=s5,p1=p5,v1=v5,u1=u5,v2=v6 ] endmodule\r\nmodule process6 = process1 [ s1=s6,p1=p6,v1=v6,u1=u6,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3&s4=3&s5=3&s6=3;\r\n\r\n"
  },
  {
    "path": "prism-examples/imdps/consensus/README.txt",
    "content": "This case study is based on the shared coin protocol from the\nrandomised consensus algorithm of Aspnes and Herlihy [AH90].\n\nThe models here are interval MDPs which consider the effect of unreliable or\nadversarial behaviour in the form of a biased coin instead of a fair coin [PLSS13].\n\nThese extend the MDP version, the files for which can be found in ../../mdps/consensus.\n\n=====================================================================================\n\nPARAMETERS:\n\nK: parameter of the random walk in the coin protocol\nbias: half-width of the interval for the coin toss probability\n\n=====================================================================================\n\n[AH90]\nJ. Aspnes and M. Herlihy.\nFast randomized consensus using shared memory.\nJournal of Algorithms, 15(1):441-460, 1990.\n\n[PLSS13]\nA. Puggelli, W. Li, A. L. Sangiovanni-Vincentelli and S. A. Seshia\nPolynomial-Time Verification of PCTL Properties of MDPs with Convex Uncertainties\nIn Proc. 25th International Conference on Computer Aided Verification (CAV'13), 2013.\n"
  },
  {
    "path": "prism-examples/imdps/consensus/auto",
    "content": "#!/bin/csh\n\nprism coin2.prism coin.props -const K=2,bias1=0.01\nprism coin2.prism coin.props -const K=4,bias1=0.01\n\nprism coin4.prism coin.props -const K=2,bias1=0.01\nprism coin4.prism coin.props -const K=4,bias1=0.01\n"
  },
  {
    "path": "prism-examples/imdps/consensus/coin.props",
    "content": "// C2 (minimum probability that the protocol finishes with all coins equal to v) (v=1,2)\n// Results are same for v=1 and v=2 by symmetry\n// Analytic bound is (K-1)/(2*K)\nPminmin=? [ F \"finished\"&\"all_coins_equal_1\" ];\nPminmax=? [ F \"finished\"&\"all_coins_equal_1\" ];\n"
  },
  {
    "path": "prism-examples/imdps/consensus/coin2.prism",
    "content": "// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \r\n// gxn/dxp 20/11/00\r\n\r\nmdp\r\n\r\n// constants\r\nconst int N=2;\r\nconst int K;\r\nconst int range = 2*(K+1)*N;\r\nconst int counter_init = (K+1)*N;\r\nconst int left = N;\r\nconst int right = 2*(K+1)*N - N;\r\n\r\n// Only process 1 is biased\r\nconst double bias1;\r\nconst double bias2 = 0.0;\r\n\r\n// shared coin\r\nglobal counter : [0..range] init counter_init;\r\n\r\nmodule process1\r\n\t\r\n\t// program counter\r\n\tpc1 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin1 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc1=0)  -> [0.5-bias1,0.5+bias1] : (coin1'=0) & (pc1'=1) + [0.5-bias1,0.5+bias1] : (coin1'=1) & (pc1'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\r\n\t// decide heads\r\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\r\n\t// flip again\r\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc1=3) -> (pc1'=3);\r\n\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1[pc1=pc2,coin1=coin2,bias1=bias2] endmodule\r\n\r\n// labels\r\nlabel \"finished\" = pc1=3 & pc2=3 ;\r\nlabel \"all_coins_equal_0\" = coin1=0 & coin2=0 ;\r\nlabel \"all_coins_equal_1\" = coin1=1 & coin2=1 ;\r\nlabel \"agree\" = coin1=coin2 ;\r\n\r\n// rewards\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/imdps/consensus/coin4.prism",
    "content": "// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \r\n// gxn/dxp 20/11/00\r\n\r\nmdp\r\n\r\n// constants\r\nconst int N=4;\r\nconst int K;\r\nconst int range = 2*(K+1)*N;\r\nconst int counter_init = (K+1)*N;\r\nconst int left = N;\r\nconst int right = 2*(K+1)*N - N;\r\n\r\n// Only process 1 is biased\r\nconst double bias1;\r\nconst double bias2 = 0.0;\r\nconst double bias3 = 0.0;\r\nconst double bias4 = 0.0;\r\n\r\n// shared coin\r\nglobal counter : [0..range] init counter_init;\r\n\r\nmodule process1\r\n\t\r\n\t// program counter\r\n\tpc1 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin1 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc1=0)  -> [0.5-bias1,0.5+bias1] : (coin1'=0) & (pc1'=1) + [0.5-bias1,0.5+bias1] : (coin1'=1) & (pc1'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\r\n\t// decide heads\r\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\r\n\t// flip again\r\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc1=3) -> (pc1'=3);\r\n\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1[pc1=pc2,coin1=coin2,bias1=bias2] endmodule\r\nmodule process3 = process1[pc1=pc3,coin1=coin3,bias1=bias3] endmodule\r\nmodule process4 = process1[pc1=pc4,coin1=coin4,bias1=bias4] endmodule\r\n\r\n// labels\r\nlabel \"finished\" = pc1=3 & pc2=3 & pc3=3 & pc4=3 ;\r\nlabel \"all_coins_equal_0\" = coin1=0 & coin2=0 & coin3=0 & coin4=0 ;\r\nlabel \"all_coins_equal_1\" = coin1=1 & coin2=1 & coin3=1 & coin4=1 ;\r\nlabel \"agree\" = coin1=coin2 & coin2=coin3 & coin3=coin4 ;\r\n\r\n// rewards\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/imdps/simple/robot.prism",
    "content": "mdp\r\n\r\nconst double delta;\r\nconst double p = 0.5-delta;\r\nconst double q = 0.5+delta;\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> [0.8,0.9]:(s'=2) + [0.1,0.2]:(s'=1);\r\n[south] s=1 -> [p,q]:(s'=4) + [1-q,1-p]:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-examples/imdps/simple/robot.props",
    "content": "// Max probability of reaching goal1 (worst-case)\nPmaxmin=? [ F \"goal1\" ];\n\n// Max probability of reaching goal1 (best-case)\nPmaxmax=? [ F \"goal1\" ];\n\n// Min expected time to reach a goal (worst-case)\nRminmax=? [ F \"goal1\"|\"goal2\" ];\n\n// Min expected time to reach a goal (best-case)\nRminmin=? [ F \"goal1\"|\"goal2\" ];\n"
  },
  {
    "path": "prism-examples/mdps/consensus/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 2 4 6 8 10 )\n  echo \"Generating for N=$N\"\n  prismpp .coinN.nm.pp $N >! coin\"$N\".nm\n  unix2dos coin\"$N\".nm\nend\n\n"
  },
  {
    "path": "prism-examples/mdps/consensus/.coinN.nm.pp",
    "content": "#const N#\n// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \n// gxn/dxp 20/11/00\n\nmdp\n\n// constants\nconst int N=#N#;\nconst int K;\nconst int range = 2*(K+1)*N;\nconst int counter_init = (K+1)*N;\nconst int left = N;\nconst int right = 2*(K+1)*N - N;\n\n// shared coin\nglobal counter : [0..range] init counter_init;\n\nmodule process1\n\t\n\t// program counter\n\tpc1 : [0..3];\n\t// 0 - flip\n\t// 1 - write \n\t// 2 - check\n\t// 3 - finished\n\t\n\t// local coin\n\tcoin1 : [0..1];\t\n\n\t// flip coin\n\t[] (pc1=0)  -> 0.5 : (coin1'=0) & (pc1'=1) + 0.5 : (coin1'=1) & (pc1'=1);\n\t// write tails -1  (reset coin to add regularity)\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\n\t// write heads +1 (reset coin to add regularity)\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\n\t// check\n\t// decide tails\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\n\t// decide heads\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\n\t// flip again\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\n\t// loop (all loop together when done)\n\t[done] (pc1=3) -> (pc1'=3);\n\nendmodule\n\n// construct remaining processes through renaming\n#for i=2:N#\nmodule process#i# = process1[pc1=pc#i#,coin1=coin#i#] endmodule\n#end#\n\n// labels\nlabel \"finished\" =#& i=1:N# pc#i#=3 #end#;\nlabel \"all_coins_equal_0\" =#& i=1:N# coin#i#=0 #end#;\nlabel \"all_coins_equal_1\" =#& i=1:N# coin#i#=1 #end#;\nlabel \"agree\" =#& i=1:N-1# coin#i#=coin#i+1# #end#;\n\n// rewards\nrewards \"steps\"\n\ttrue : 1;\nendrewards\n\n"
  },
  {
    "path": "prism-examples/mdps/consensus/README.txt",
    "content": "This case study is based on the shared coin protocol from the randomised consensus algorithm of Aspnes and Herlihy [AH90].\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/consensus_prism.php\r\n\r\n=====================================================================================\r\n\r\n[AH90]\r\nJ. Aspnes and M. Herlihy.\nFast randomized consensus using shared memory.\nJournal of Algorithms, 15(1):441-460, 1990.\n\n"
  },
  {
    "path": "prism-examples/mdps/consensus/auto",
    "content": "#!/bin/csh\n\nprism coin2.nm coin.pctl -const K=2,k=10 -m\nprism coin2.nm coin.pctl -const K=4,k=10 -m\n#prism coin2.nm coin.pctl -const K=8,k=10 -m -maxiters 100000\n#prism coin2.nm coin.pctl -const K=16,k=10 -m -maxiters 100000\n\nprism coin4.nm coin.pctl -const K=2,k=10 -m\nprism coin4.nm coin.pctl -const K=4,k=10 -m\n\n#prism coin6.nm coin.pctl -const K=2,k=10 -m\n\n#prism coin8.nm coin.pctl -const K=2,k=10 -m\n\n#prism coin10.nm coin.pctl -const K=2,k=10 -m\n\n"
  },
  {
    "path": "prism-examples/mdps/consensus/coin.pctl",
    "content": "const int k;\n\n// C1 (with probability 1, all N processes finish the protocol)\nP>=1 [ F \"finished\" ]\n\n// C2 (minimum probability that the protocol finishes with all coins equal to v) (v=1,2)\n// Results are same for v=1 and v=2 by symmetry\n// Analytic bound is (K-1)/(2*K)\nPmin=? [ F \"finished\"&\"all_coins_equal_0\" ]\nPmin=? [ F \"finished\"&\"all_coins_equal_1\" ]\n\n// Max probability of finishing protocol with coins not all equal\nPmax=? [ F \"finished\"&!\"agree\" ]\n\n// Min/max probability of finishing within k steps\nPmin=? [ F<=k \"finished\" ]\nPmax=? [ F<=k \"finished\" ]\n\n// Min/max expected steps to finish\nR{\"steps\"}min=? [ F \"finished\" ]\nR{\"steps\"}max=? [ F \"finished\" ]\n\n"
  },
  {
    "path": "prism-examples/mdps/consensus/coin10.nm",
    "content": "// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \r\n// gxn/dxp 20/11/00\r\n\r\nmdp\r\n\r\n// constants\r\nconst int N=10;\r\nconst int K;\r\nconst int range = 2*(K+1)*N;\r\nconst int counter_init = (K+1)*N;\r\nconst int left = N;\r\nconst int right = 2*(K+1)*N - N;\r\n\r\n// shared coin\r\nglobal counter : [0..range] init counter_init;\r\n\r\nmodule process1\r\n\t\r\n\t// program counter\r\n\tpc1 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin1 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc1=0)  -> 0.5 : (coin1'=0) & (pc1'=1) + 0.5 : (coin1'=1) & (pc1'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\r\n\t// decide heads\r\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\r\n\t// flip again\r\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc1=3) -> (pc1'=3);\r\n\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1[pc1=pc2,coin1=coin2] endmodule\r\nmodule process3 = process1[pc1=pc3,coin1=coin3] endmodule\r\nmodule process4 = process1[pc1=pc4,coin1=coin4] endmodule\r\nmodule process5 = process1[pc1=pc5,coin1=coin5] endmodule\r\nmodule process6 = process1[pc1=pc6,coin1=coin6] endmodule\r\nmodule process7 = process1[pc1=pc7,coin1=coin7] endmodule\r\nmodule process8 = process1[pc1=pc8,coin1=coin8] endmodule\r\nmodule process9 = process1[pc1=pc9,coin1=coin9] endmodule\r\nmodule process10 = process1[pc1=pc10,coin1=coin10] endmodule\r\n\r\n// labels\r\nlabel \"finished\" = pc1=3 & pc2=3 & pc3=3 & pc4=3 & pc5=3 & pc6=3 & pc7=3 & pc8=3 & pc9=3 & pc10=3 ;\r\nlabel \"all_coins_equal_0\" = coin1=0 & coin2=0 & coin3=0 & coin4=0 & coin5=0 & coin6=0 & coin7=0 & coin8=0 & coin9=0 & coin10=0 ;\r\nlabel \"all_coins_equal_1\" = coin1=1 & coin2=1 & coin3=1 & coin4=1 & coin5=1 & coin6=1 & coin7=1 & coin8=1 & coin9=1 & coin10=1 ;\r\nlabel \"agree\" = coin1=coin2 & coin2=coin3 & coin3=coin4 & coin4=coin5 & coin5=coin6 & coin6=coin7 & coin7=coin8 & coin8=coin9 & coin9=coin10 ;\r\n\r\n// rewards\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/consensus/coin2.nm",
    "content": "// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \r\n// gxn/dxp 20/11/00\r\n\r\nmdp\r\n\r\n// constants\r\nconst int N=2;\r\nconst int K;\r\nconst int range = 2*(K+1)*N;\r\nconst int counter_init = (K+1)*N;\r\nconst int left = N;\r\nconst int right = 2*(K+1)*N - N;\r\n\r\n// shared coin\r\nglobal counter : [0..range] init counter_init;\r\n\r\nmodule process1\r\n\t\r\n\t// program counter\r\n\tpc1 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin1 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc1=0)  -> 0.5 : (coin1'=0) & (pc1'=1) + 0.5 : (coin1'=1) & (pc1'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\r\n\t// decide heads\r\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\r\n\t// flip again\r\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc1=3) -> (pc1'=3);\r\n\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1[pc1=pc2,coin1=coin2] endmodule\r\n\r\n// labels\r\nlabel \"finished\" = pc1=3 & pc2=3 ;\r\nlabel \"all_coins_equal_0\" = coin1=0 & coin2=0 ;\r\nlabel \"all_coins_equal_1\" = coin1=1 & coin2=1 ;\r\nlabel \"agree\" = coin1=coin2 ;\r\n\r\n// rewards\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/consensus/coin4.nm",
    "content": "// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \r\n// gxn/dxp 20/11/00\r\n\r\nmdp\r\n\r\n// constants\r\nconst int N=4;\r\nconst int K;\r\nconst int range = 2*(K+1)*N;\r\nconst int counter_init = (K+1)*N;\r\nconst int left = N;\r\nconst int right = 2*(K+1)*N - N;\r\n\r\n// shared coin\r\nglobal counter : [0..range] init counter_init;\r\n\r\nmodule process1\r\n\t\r\n\t// program counter\r\n\tpc1 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin1 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc1=0)  -> 0.5 : (coin1'=0) & (pc1'=1) + 0.5 : (coin1'=1) & (pc1'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\r\n\t// decide heads\r\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\r\n\t// flip again\r\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc1=3) -> (pc1'=3);\r\n\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1[pc1=pc2,coin1=coin2] endmodule\r\nmodule process3 = process1[pc1=pc3,coin1=coin3] endmodule\r\nmodule process4 = process1[pc1=pc4,coin1=coin4] endmodule\r\n\r\n// labels\r\nlabel \"finished\" = pc1=3 & pc2=3 & pc3=3 & pc4=3 ;\r\nlabel \"all_coins_equal_0\" = coin1=0 & coin2=0 & coin3=0 & coin4=0 ;\r\nlabel \"all_coins_equal_1\" = coin1=1 & coin2=1 & coin3=1 & coin4=1 ;\r\nlabel \"agree\" = coin1=coin2 & coin2=coin3 & coin3=coin4 ;\r\n\r\n// rewards\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/consensus/coin6.nm",
    "content": "// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \r\n// gxn/dxp 20/11/00\r\n\r\nmdp\r\n\r\n// constants\r\nconst int N=6;\r\nconst int K;\r\nconst int range = 2*(K+1)*N;\r\nconst int counter_init = (K+1)*N;\r\nconst int left = N;\r\nconst int right = 2*(K+1)*N - N;\r\n\r\n// shared coin\r\nglobal counter : [0..range] init counter_init;\r\n\r\nmodule process1\r\n\t\r\n\t// program counter\r\n\tpc1 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin1 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc1=0)  -> 0.5 : (coin1'=0) & (pc1'=1) + 0.5 : (coin1'=1) & (pc1'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\r\n\t// decide heads\r\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\r\n\t// flip again\r\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc1=3) -> (pc1'=3);\r\n\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1[pc1=pc2,coin1=coin2] endmodule\r\nmodule process3 = process1[pc1=pc3,coin1=coin3] endmodule\r\nmodule process4 = process1[pc1=pc4,coin1=coin4] endmodule\r\nmodule process5 = process1[pc1=pc5,coin1=coin5] endmodule\r\nmodule process6 = process1[pc1=pc6,coin1=coin6] endmodule\r\n\r\n// labels\r\nlabel \"finished\" = pc1=3 & pc2=3 & pc3=3 & pc4=3 & pc5=3 & pc6=3 ;\r\nlabel \"all_coins_equal_0\" = coin1=0 & coin2=0 & coin3=0 & coin4=0 & coin5=0 & coin6=0 ;\r\nlabel \"all_coins_equal_1\" = coin1=1 & coin2=1 & coin3=1 & coin4=1 & coin5=1 & coin6=1 ;\r\nlabel \"agree\" = coin1=coin2 & coin2=coin3 & coin3=coin4 & coin4=coin5 & coin5=coin6 ;\r\n\r\n// rewards\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/consensus/coin8.nm",
    "content": "// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \r\n// gxn/dxp 20/11/00\r\n\r\nmdp\r\n\r\n// constants\r\nconst int N=8;\r\nconst int K;\r\nconst int range = 2*(K+1)*N;\r\nconst int counter_init = (K+1)*N;\r\nconst int left = N;\r\nconst int right = 2*(K+1)*N - N;\r\n\r\n// shared coin\r\nglobal counter : [0..range] init counter_init;\r\n\r\nmodule process1\r\n\t\r\n\t// program counter\r\n\tpc1 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin1 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc1=0)  -> 0.5 : (coin1'=0) & (pc1'=1) + 0.5 : (coin1'=1) & (pc1'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\r\n\t// decide heads\r\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\r\n\t// flip again\r\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc1=3) -> (pc1'=3);\r\n\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1[pc1=pc2,coin1=coin2] endmodule\r\nmodule process3 = process1[pc1=pc3,coin1=coin3] endmodule\r\nmodule process4 = process1[pc1=pc4,coin1=coin4] endmodule\r\nmodule process5 = process1[pc1=pc5,coin1=coin5] endmodule\r\nmodule process6 = process1[pc1=pc6,coin1=coin6] endmodule\r\nmodule process7 = process1[pc1=pc7,coin1=coin7] endmodule\r\nmodule process8 = process1[pc1=pc8,coin1=coin8] endmodule\r\n\r\n// labels\r\nlabel \"finished\" = pc1=3 & pc2=3 & pc3=3 & pc4=3 & pc5=3 & pc6=3 & pc7=3 & pc8=3 ;\r\nlabel \"all_coins_equal_0\" = coin1=0 & coin2=0 & coin3=0 & coin4=0 & coin5=0 & coin6=0 & coin7=0 & coin8=0 ;\r\nlabel \"all_coins_equal_1\" = coin1=1 & coin2=1 & coin3=1 & coin4=1 & coin5=1 & coin6=1 & coin7=1 & coin8=1 ;\r\nlabel \"agree\" = coin1=coin2 & coin2=coin3 & coin3=coin4 & coin4=coin5 & coin5=coin6 & coin6=coin7 & coin7=coin8 ;\r\n\r\n// rewards\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/csma/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 2 3 4 )\n  foreach K ( 2 4 6 )\n    echo \"Generating for N=$N and K=$K\"\n    prismpp .csmaN_K.nm.pp $N $K >! csma$N\"_\"$K.nm\n  end\nend\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/.csmaN_K.nm.pp",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\n#const N#\nconst int N = #N#; // number of processes\n#const K#\nconst int K = #K#; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t#for i=1:N#\n\t[send#i#] (b=0) -> (b'=1);\n\t#end#\n\t\n\t// a sender sends (bus busy - collision)\n\t#for i=1:N#\n\t[send#i#] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t#end#\n\t\n\t// finish sending\n\t#for i=1:N#\n\t[end#i#] (b=1) -> (b'=0) & (y1'=0);\n\t#end#\n\t\n\t// bus busy\n\t#for i=1:N#\n\t[busy#i#] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t#end#\n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t#for i=1:K#\n\t#const i2=floor(pow(2,i))#\n\t[] s1=2 & cd1=#i# -> #+ j=0:i2-1# 1/#i2# : (s1'=3) & (bc1'=#j#) #end#;\n\t#end#\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\n#for i=2:N#\nmodule station#i#=station1[s1=s#i#,x1=x#i#,cd1=cd#i#,bc1=bc#i#,send1=send#i#,busy1=busy#i#,end1=end#i#] endmodule\n#end#\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = #& i=1:N#s#i#=4#end#;\nlabel \"one_delivered\" = #| i=1:N#s#i#=4#end#;\nlabel \"collision_max_backoff\" = #| i=1:N#(cd#i#=K & s#i#=1 & b=2)#end#;\nformula min_backoff_after_success = min(#, i=1:N#s#i#=4?cd#i#:K+1#end#);\nformula min_collisions = min(#, i=1:N#cd#i##end#);\nformula max_collisions = max(#, i=1:N#cd#i##end#);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/README.txt",
    "content": "This case study concerns the IEEE 802.3 CSMA/CD (Carrier Sense, Multiple Access with Collision Detection) protocol\r\n\nmodel files csmaN_K.nm\nproperty file: csma.pctl\n\nwhere N is the number of stations and K is the maximum backoff\n\r\nFor more information on the probabilistic timed automata see: http://www.prismmodelchecker.org/casestudies/csma.php\n\nThe PRISM model uses the integer semantics given in [KNPS06].\n\n=====================================================================================\n\n[KNPS06]\nM. Kwiatkowska, G. Norman, D. Parker and J. Sproston\nPerformance Analysis of Probabilistic Timed Automata using Digital Clocks\nFormal Methods in System Design, 29:33-78, 2006\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/csma/auto",
    "content": "#!/bin/csh\n\nprism csma2_2.nm csma.pctl -const k=1 -s\nprism csma2_4.nm csma.pctl -const k=1 -s\nprism csma2_6.nm csma.pctl -const k=1 -s\nprism csma3_2.nm csma.pctl -const k=1 -s\nprism csma3_4.nm csma.pctl -const k=1 -s\n#prism csma3_6.nm csma.pctl -const k=1 -s\nprism csma4_2.nm csma.pctl -const k=1 -s\n#prism csma4_4.nm csma.pctl -const k=1 -s\n#prism csma4_6.nm csma.pctl -const k=1 -s\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma.pctl",
    "content": "const int k;\n\n// expected time for all messages to be sent\nR{\"time\"}min=?[ F \"all_delivered\" ]\nR{\"time\"}max=?[ F \"all_delivered\" ]\n\n// expected time for one message to be sent\nRmin=?[ F \"one_delivered\" ]\nRmax=?[ F \"one_delivered\" ]\n\n// message of some station eventually delivered before k backoffs\nPmin=?[ F min_backoff_after_success<=k ]\nPmax=?[ F min_backoff_after_success<=k ]\n\n// probability all sent successfully before a collision with max backoff \nPmin=?[ !\"collision_max_backoff\" U \"all_delivered\" ]\nPmax=?[ !\"collision_max_backoff\" U \"all_delivered\" ]\n\n// probability some station suffers at least k collisions\nPmin=?[ F max_collisions>=k ]\nPmax=?[ F max_collisions>=k ]\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma2_2.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 2; // number of processes\nconst int K = 2; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4;\nlabel \"one_delivered\" = s1=4|s2=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1);\nformula min_collisions = min(cd1,cd2);\nformula max_collisions = max(cd1,cd2);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma2_4.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 2; // number of processes\nconst int K = 4; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t[] s1=2 & cd1=3 ->  1/8 : (s1'=3) & (bc1'=0) + 1/8 : (s1'=3) & (bc1'=1) + 1/8 : (s1'=3) & (bc1'=2) + 1/8 : (s1'=3) & (bc1'=3) + 1/8 : (s1'=3) & (bc1'=4) + 1/8 : (s1'=3) & (bc1'=5) + 1/8 : (s1'=3) & (bc1'=6) + 1/8 : (s1'=3) & (bc1'=7) ;\n\t[] s1=2 & cd1=4 ->  1/16 : (s1'=3) & (bc1'=0) + 1/16 : (s1'=3) & (bc1'=1) + 1/16 : (s1'=3) & (bc1'=2) + 1/16 : (s1'=3) & (bc1'=3) + 1/16 : (s1'=3) & (bc1'=4) + 1/16 : (s1'=3) & (bc1'=5) + 1/16 : (s1'=3) & (bc1'=6) + 1/16 : (s1'=3) & (bc1'=7) + 1/16 : (s1'=3) & (bc1'=8) + 1/16 : (s1'=3) & (bc1'=9) + 1/16 : (s1'=3) & (bc1'=10) + 1/16 : (s1'=3) & (bc1'=11) + 1/16 : (s1'=3) & (bc1'=12) + 1/16 : (s1'=3) & (bc1'=13) + 1/16 : (s1'=3) & (bc1'=14) + 1/16 : (s1'=3) & (bc1'=15) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4;\nlabel \"one_delivered\" = s1=4|s2=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1);\nformula min_collisions = min(cd1,cd2);\nformula max_collisions = max(cd1,cd2);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma2_6.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 2; // number of processes\nconst int K = 6; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t[] s1=2 & cd1=3 ->  1/8 : (s1'=3) & (bc1'=0) + 1/8 : (s1'=3) & (bc1'=1) + 1/8 : (s1'=3) & (bc1'=2) + 1/8 : (s1'=3) & (bc1'=3) + 1/8 : (s1'=3) & (bc1'=4) + 1/8 : (s1'=3) & (bc1'=5) + 1/8 : (s1'=3) & (bc1'=6) + 1/8 : (s1'=3) & (bc1'=7) ;\n\t[] s1=2 & cd1=4 ->  1/16 : (s1'=3) & (bc1'=0) + 1/16 : (s1'=3) & (bc1'=1) + 1/16 : (s1'=3) & (bc1'=2) + 1/16 : (s1'=3) & (bc1'=3) + 1/16 : (s1'=3) & (bc1'=4) + 1/16 : (s1'=3) & (bc1'=5) + 1/16 : (s1'=3) & (bc1'=6) + 1/16 : (s1'=3) & (bc1'=7) + 1/16 : (s1'=3) & (bc1'=8) + 1/16 : (s1'=3) & (bc1'=9) + 1/16 : (s1'=3) & (bc1'=10) + 1/16 : (s1'=3) & (bc1'=11) + 1/16 : (s1'=3) & (bc1'=12) + 1/16 : (s1'=3) & (bc1'=13) + 1/16 : (s1'=3) & (bc1'=14) + 1/16 : (s1'=3) & (bc1'=15) ;\n\t[] s1=2 & cd1=5 ->  1/32 : (s1'=3) & (bc1'=0) + 1/32 : (s1'=3) & (bc1'=1) + 1/32 : (s1'=3) & (bc1'=2) + 1/32 : (s1'=3) & (bc1'=3) + 1/32 : (s1'=3) & (bc1'=4) + 1/32 : (s1'=3) & (bc1'=5) + 1/32 : (s1'=3) & (bc1'=6) + 1/32 : (s1'=3) & (bc1'=7) + 1/32 : (s1'=3) & (bc1'=8) + 1/32 : (s1'=3) & (bc1'=9) + 1/32 : (s1'=3) & (bc1'=10) + 1/32 : (s1'=3) & (bc1'=11) + 1/32 : (s1'=3) & (bc1'=12) + 1/32 : (s1'=3) & (bc1'=13) + 1/32 : (s1'=3) & (bc1'=14) + 1/32 : (s1'=3) & (bc1'=15) + 1/32 : (s1'=3) & (bc1'=16) + 1/32 : (s1'=3) & (bc1'=17) + 1/32 : (s1'=3) & (bc1'=18) + 1/32 : (s1'=3) & (bc1'=19) + 1/32 : (s1'=3) & (bc1'=20) + 1/32 : (s1'=3) & (bc1'=21) + 1/32 : (s1'=3) & (bc1'=22) + 1/32 : (s1'=3) & (bc1'=23) + 1/32 : (s1'=3) & (bc1'=24) + 1/32 : (s1'=3) & (bc1'=25) + 1/32 : (s1'=3) & (bc1'=26) + 1/32 : (s1'=3) & (bc1'=27) + 1/32 : (s1'=3) & (bc1'=28) + 1/32 : (s1'=3) & (bc1'=29) + 1/32 : (s1'=3) & (bc1'=30) + 1/32 : (s1'=3) & (bc1'=31) ;\n\t[] s1=2 & cd1=6 ->  1/64 : (s1'=3) & (bc1'=0) + 1/64 : (s1'=3) & (bc1'=1) + 1/64 : (s1'=3) & (bc1'=2) + 1/64 : (s1'=3) & (bc1'=3) + 1/64 : (s1'=3) & (bc1'=4) + 1/64 : (s1'=3) & (bc1'=5) + 1/64 : (s1'=3) & (bc1'=6) + 1/64 : (s1'=3) & (bc1'=7) + 1/64 : (s1'=3) & (bc1'=8) + 1/64 : (s1'=3) & (bc1'=9) + 1/64 : (s1'=3) & (bc1'=10) + 1/64 : (s1'=3) & (bc1'=11) + 1/64 : (s1'=3) & (bc1'=12) + 1/64 : (s1'=3) & (bc1'=13) + 1/64 : (s1'=3) & (bc1'=14) + 1/64 : (s1'=3) & (bc1'=15) + 1/64 : (s1'=3) & (bc1'=16) + 1/64 : (s1'=3) & (bc1'=17) + 1/64 : (s1'=3) & (bc1'=18) + 1/64 : (s1'=3) & (bc1'=19) + 1/64 : (s1'=3) & (bc1'=20) + 1/64 : (s1'=3) & (bc1'=21) + 1/64 : (s1'=3) & (bc1'=22) + 1/64 : (s1'=3) & (bc1'=23) + 1/64 : (s1'=3) & (bc1'=24) + 1/64 : (s1'=3) & (bc1'=25) + 1/64 : (s1'=3) & (bc1'=26) + 1/64 : (s1'=3) & (bc1'=27) + 1/64 : (s1'=3) & (bc1'=28) + 1/64 : (s1'=3) & (bc1'=29) + 1/64 : (s1'=3) & (bc1'=30) + 1/64 : (s1'=3) & (bc1'=31) + 1/64 : (s1'=3) & (bc1'=32) + 1/64 : (s1'=3) & (bc1'=33) + 1/64 : (s1'=3) & (bc1'=34) + 1/64 : (s1'=3) & (bc1'=35) + 1/64 : (s1'=3) & (bc1'=36) + 1/64 : (s1'=3) & (bc1'=37) + 1/64 : (s1'=3) & (bc1'=38) + 1/64 : (s1'=3) & (bc1'=39) + 1/64 : (s1'=3) & (bc1'=40) + 1/64 : (s1'=3) & (bc1'=41) + 1/64 : (s1'=3) & (bc1'=42) + 1/64 : (s1'=3) & (bc1'=43) + 1/64 : (s1'=3) & (bc1'=44) + 1/64 : (s1'=3) & (bc1'=45) + 1/64 : (s1'=3) & (bc1'=46) + 1/64 : (s1'=3) & (bc1'=47) + 1/64 : (s1'=3) & (bc1'=48) + 1/64 : (s1'=3) & (bc1'=49) + 1/64 : (s1'=3) & (bc1'=50) + 1/64 : (s1'=3) & (bc1'=51) + 1/64 : (s1'=3) & (bc1'=52) + 1/64 : (s1'=3) & (bc1'=53) + 1/64 : (s1'=3) & (bc1'=54) + 1/64 : (s1'=3) & (bc1'=55) + 1/64 : (s1'=3) & (bc1'=56) + 1/64 : (s1'=3) & (bc1'=57) + 1/64 : (s1'=3) & (bc1'=58) + 1/64 : (s1'=3) & (bc1'=59) + 1/64 : (s1'=3) & (bc1'=60) + 1/64 : (s1'=3) & (bc1'=61) + 1/64 : (s1'=3) & (bc1'=62) + 1/64 : (s1'=3) & (bc1'=63) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4;\nlabel \"one_delivered\" = s1=4|s2=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1);\nformula min_collisions = min(cd1,cd2);\nformula max_collisions = max(cd1,cd2);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma3_2.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 3; // number of processes\nconst int K = 2; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t[send3] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send3] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t[end3] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy3] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\nmodule station3=station1[s1=s3,x1=x3,cd1=cd3,bc1=bc3,send1=send3,busy1=busy3,end1=end3] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4&s3=4;\nlabel \"one_delivered\" = s1=4|s2=4|s3=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2)|(cd3=K & s3=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1,s3=4?cd3:K+1);\nformula min_collisions = min(cd1,cd2,cd3);\nformula max_collisions = max(cd1,cd2,cd3);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma3_4.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 3; // number of processes\nconst int K = 4; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t[send3] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send3] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t[end3] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy3] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t[] s1=2 & cd1=3 ->  1/8 : (s1'=3) & (bc1'=0) + 1/8 : (s1'=3) & (bc1'=1) + 1/8 : (s1'=3) & (bc1'=2) + 1/8 : (s1'=3) & (bc1'=3) + 1/8 : (s1'=3) & (bc1'=4) + 1/8 : (s1'=3) & (bc1'=5) + 1/8 : (s1'=3) & (bc1'=6) + 1/8 : (s1'=3) & (bc1'=7) ;\n\t[] s1=2 & cd1=4 ->  1/16 : (s1'=3) & (bc1'=0) + 1/16 : (s1'=3) & (bc1'=1) + 1/16 : (s1'=3) & (bc1'=2) + 1/16 : (s1'=3) & (bc1'=3) + 1/16 : (s1'=3) & (bc1'=4) + 1/16 : (s1'=3) & (bc1'=5) + 1/16 : (s1'=3) & (bc1'=6) + 1/16 : (s1'=3) & (bc1'=7) + 1/16 : (s1'=3) & (bc1'=8) + 1/16 : (s1'=3) & (bc1'=9) + 1/16 : (s1'=3) & (bc1'=10) + 1/16 : (s1'=3) & (bc1'=11) + 1/16 : (s1'=3) & (bc1'=12) + 1/16 : (s1'=3) & (bc1'=13) + 1/16 : (s1'=3) & (bc1'=14) + 1/16 : (s1'=3) & (bc1'=15) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\nmodule station3=station1[s1=s3,x1=x3,cd1=cd3,bc1=bc3,send1=send3,busy1=busy3,end1=end3] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4&s3=4;\nlabel \"one_delivered\" = s1=4|s2=4|s3=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2)|(cd3=K & s3=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1,s3=4?cd3:K+1);\nformula min_collisions = min(cd1,cd2,cd3);\nformula max_collisions = max(cd1,cd2,cd3);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma3_6.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 3; // number of processes\nconst int K = 6; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t[send3] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send3] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t[end3] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy3] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t[] s1=2 & cd1=3 ->  1/8 : (s1'=3) & (bc1'=0) + 1/8 : (s1'=3) & (bc1'=1) + 1/8 : (s1'=3) & (bc1'=2) + 1/8 : (s1'=3) & (bc1'=3) + 1/8 : (s1'=3) & (bc1'=4) + 1/8 : (s1'=3) & (bc1'=5) + 1/8 : (s1'=3) & (bc1'=6) + 1/8 : (s1'=3) & (bc1'=7) ;\n\t[] s1=2 & cd1=4 ->  1/16 : (s1'=3) & (bc1'=0) + 1/16 : (s1'=3) & (bc1'=1) + 1/16 : (s1'=3) & (bc1'=2) + 1/16 : (s1'=3) & (bc1'=3) + 1/16 : (s1'=3) & (bc1'=4) + 1/16 : (s1'=3) & (bc1'=5) + 1/16 : (s1'=3) & (bc1'=6) + 1/16 : (s1'=3) & (bc1'=7) + 1/16 : (s1'=3) & (bc1'=8) + 1/16 : (s1'=3) & (bc1'=9) + 1/16 : (s1'=3) & (bc1'=10) + 1/16 : (s1'=3) & (bc1'=11) + 1/16 : (s1'=3) & (bc1'=12) + 1/16 : (s1'=3) & (bc1'=13) + 1/16 : (s1'=3) & (bc1'=14) + 1/16 : (s1'=3) & (bc1'=15) ;\n\t[] s1=2 & cd1=5 ->  1/32 : (s1'=3) & (bc1'=0) + 1/32 : (s1'=3) & (bc1'=1) + 1/32 : (s1'=3) & (bc1'=2) + 1/32 : (s1'=3) & (bc1'=3) + 1/32 : (s1'=3) & (bc1'=4) + 1/32 : (s1'=3) & (bc1'=5) + 1/32 : (s1'=3) & (bc1'=6) + 1/32 : (s1'=3) & (bc1'=7) + 1/32 : (s1'=3) & (bc1'=8) + 1/32 : (s1'=3) & (bc1'=9) + 1/32 : (s1'=3) & (bc1'=10) + 1/32 : (s1'=3) & (bc1'=11) + 1/32 : (s1'=3) & (bc1'=12) + 1/32 : (s1'=3) & (bc1'=13) + 1/32 : (s1'=3) & (bc1'=14) + 1/32 : (s1'=3) & (bc1'=15) + 1/32 : (s1'=3) & (bc1'=16) + 1/32 : (s1'=3) & (bc1'=17) + 1/32 : (s1'=3) & (bc1'=18) + 1/32 : (s1'=3) & (bc1'=19) + 1/32 : (s1'=3) & (bc1'=20) + 1/32 : (s1'=3) & (bc1'=21) + 1/32 : (s1'=3) & (bc1'=22) + 1/32 : (s1'=3) & (bc1'=23) + 1/32 : (s1'=3) & (bc1'=24) + 1/32 : (s1'=3) & (bc1'=25) + 1/32 : (s1'=3) & (bc1'=26) + 1/32 : (s1'=3) & (bc1'=27) + 1/32 : (s1'=3) & (bc1'=28) + 1/32 : (s1'=3) & (bc1'=29) + 1/32 : (s1'=3) & (bc1'=30) + 1/32 : (s1'=3) & (bc1'=31) ;\n\t[] s1=2 & cd1=6 ->  1/64 : (s1'=3) & (bc1'=0) + 1/64 : (s1'=3) & (bc1'=1) + 1/64 : (s1'=3) & (bc1'=2) + 1/64 : (s1'=3) & (bc1'=3) + 1/64 : (s1'=3) & (bc1'=4) + 1/64 : (s1'=3) & (bc1'=5) + 1/64 : (s1'=3) & (bc1'=6) + 1/64 : (s1'=3) & (bc1'=7) + 1/64 : (s1'=3) & (bc1'=8) + 1/64 : (s1'=3) & (bc1'=9) + 1/64 : (s1'=3) & (bc1'=10) + 1/64 : (s1'=3) & (bc1'=11) + 1/64 : (s1'=3) & (bc1'=12) + 1/64 : (s1'=3) & (bc1'=13) + 1/64 : (s1'=3) & (bc1'=14) + 1/64 : (s1'=3) & (bc1'=15) + 1/64 : (s1'=3) & (bc1'=16) + 1/64 : (s1'=3) & (bc1'=17) + 1/64 : (s1'=3) & (bc1'=18) + 1/64 : (s1'=3) & (bc1'=19) + 1/64 : (s1'=3) & (bc1'=20) + 1/64 : (s1'=3) & (bc1'=21) + 1/64 : (s1'=3) & (bc1'=22) + 1/64 : (s1'=3) & (bc1'=23) + 1/64 : (s1'=3) & (bc1'=24) + 1/64 : (s1'=3) & (bc1'=25) + 1/64 : (s1'=3) & (bc1'=26) + 1/64 : (s1'=3) & (bc1'=27) + 1/64 : (s1'=3) & (bc1'=28) + 1/64 : (s1'=3) & (bc1'=29) + 1/64 : (s1'=3) & (bc1'=30) + 1/64 : (s1'=3) & (bc1'=31) + 1/64 : (s1'=3) & (bc1'=32) + 1/64 : (s1'=3) & (bc1'=33) + 1/64 : (s1'=3) & (bc1'=34) + 1/64 : (s1'=3) & (bc1'=35) + 1/64 : (s1'=3) & (bc1'=36) + 1/64 : (s1'=3) & (bc1'=37) + 1/64 : (s1'=3) & (bc1'=38) + 1/64 : (s1'=3) & (bc1'=39) + 1/64 : (s1'=3) & (bc1'=40) + 1/64 : (s1'=3) & (bc1'=41) + 1/64 : (s1'=3) & (bc1'=42) + 1/64 : (s1'=3) & (bc1'=43) + 1/64 : (s1'=3) & (bc1'=44) + 1/64 : (s1'=3) & (bc1'=45) + 1/64 : (s1'=3) & (bc1'=46) + 1/64 : (s1'=3) & (bc1'=47) + 1/64 : (s1'=3) & (bc1'=48) + 1/64 : (s1'=3) & (bc1'=49) + 1/64 : (s1'=3) & (bc1'=50) + 1/64 : (s1'=3) & (bc1'=51) + 1/64 : (s1'=3) & (bc1'=52) + 1/64 : (s1'=3) & (bc1'=53) + 1/64 : (s1'=3) & (bc1'=54) + 1/64 : (s1'=3) & (bc1'=55) + 1/64 : (s1'=3) & (bc1'=56) + 1/64 : (s1'=3) & (bc1'=57) + 1/64 : (s1'=3) & (bc1'=58) + 1/64 : (s1'=3) & (bc1'=59) + 1/64 : (s1'=3) & (bc1'=60) + 1/64 : (s1'=3) & (bc1'=61) + 1/64 : (s1'=3) & (bc1'=62) + 1/64 : (s1'=3) & (bc1'=63) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\nmodule station3=station1[s1=s3,x1=x3,cd1=cd3,bc1=bc3,send1=send3,busy1=busy3,end1=end3] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4&s3=4;\nlabel \"one_delivered\" = s1=4|s2=4|s3=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2)|(cd3=K & s3=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1,s3=4?cd3:K+1);\nformula min_collisions = min(cd1,cd2,cd3);\nformula max_collisions = max(cd1,cd2,cd3);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma4_2.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 4; // number of processes\nconst int K = 2; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t[send3] (b=0) -> (b'=1);\n\t[send4] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send3] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send4] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t[end3] (b=1) -> (b'=0) & (y1'=0);\n\t[end4] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy3] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy4] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\nmodule station3=station1[s1=s3,x1=x3,cd1=cd3,bc1=bc3,send1=send3,busy1=busy3,end1=end3] endmodule\nmodule station4=station1[s1=s4,x1=x4,cd1=cd4,bc1=bc4,send1=send4,busy1=busy4,end1=end4] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4&s3=4&s4=4;\nlabel \"one_delivered\" = s1=4|s2=4|s3=4|s4=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2)|(cd3=K & s3=1 & b=2)|(cd4=K & s4=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1,s3=4?cd3:K+1,s4=4?cd4:K+1);\nformula min_collisions = min(cd1,cd2,cd3,cd4);\nformula max_collisions = max(cd1,cd2,cd3,cd4);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma4_4.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 4; // number of processes\nconst int K = 4; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t[send3] (b=0) -> (b'=1);\n\t[send4] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send3] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send4] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t[end3] (b=1) -> (b'=0) & (y1'=0);\n\t[end4] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy3] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy4] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t[] s1=2 & cd1=3 ->  1/8 : (s1'=3) & (bc1'=0) + 1/8 : (s1'=3) & (bc1'=1) + 1/8 : (s1'=3) & (bc1'=2) + 1/8 : (s1'=3) & (bc1'=3) + 1/8 : (s1'=3) & (bc1'=4) + 1/8 : (s1'=3) & (bc1'=5) + 1/8 : (s1'=3) & (bc1'=6) + 1/8 : (s1'=3) & (bc1'=7) ;\n\t[] s1=2 & cd1=4 ->  1/16 : (s1'=3) & (bc1'=0) + 1/16 : (s1'=3) & (bc1'=1) + 1/16 : (s1'=3) & (bc1'=2) + 1/16 : (s1'=3) & (bc1'=3) + 1/16 : (s1'=3) & (bc1'=4) + 1/16 : (s1'=3) & (bc1'=5) + 1/16 : (s1'=3) & (bc1'=6) + 1/16 : (s1'=3) & (bc1'=7) + 1/16 : (s1'=3) & (bc1'=8) + 1/16 : (s1'=3) & (bc1'=9) + 1/16 : (s1'=3) & (bc1'=10) + 1/16 : (s1'=3) & (bc1'=11) + 1/16 : (s1'=3) & (bc1'=12) + 1/16 : (s1'=3) & (bc1'=13) + 1/16 : (s1'=3) & (bc1'=14) + 1/16 : (s1'=3) & (bc1'=15) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\nmodule station3=station1[s1=s3,x1=x3,cd1=cd3,bc1=bc3,send1=send3,busy1=busy3,end1=end3] endmodule\nmodule station4=station1[s1=s4,x1=x4,cd1=cd4,bc1=bc4,send1=send4,busy1=busy4,end1=end4] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4&s3=4&s4=4;\nlabel \"one_delivered\" = s1=4|s2=4|s3=4|s4=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2)|(cd3=K & s3=1 & b=2)|(cd4=K & s4=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1,s3=4?cd3:K+1,s4=4?cd4:K+1);\nformula min_collisions = min(cd1,cd2,cd3,cd4);\nformula max_collisions = max(cd1,cd2,cd3,cd4);\n\n"
  },
  {
    "path": "prism-examples/mdps/csma/csma4_6.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\n// gxn/dxp 04/12/01\n\nmdp\n\n// note made changes since cannot have strict inequalities\n// in digital clocks approach and suppose a station only sends one message\n\n// actual parameters\nconst int N = 4; // number of processes\nconst int K = 6; // exponential backoff limit\nconst int slot = 2*sigma; // length of slot\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\n//const int lambda=782;\n//const int sigma=26;\n\n// simplified parameters scaled\nconst int sigma=1; // time for messages to propagate along the bus\nconst int lambda=30; // time to send a message\n\n//----------------------------------------------------------------------------------------------------------------------------\n// the bus\nmodule bus\n\t\n\tb : [0..2];\n\t// b=0 - idle\n\t// b=1 - active\n\t// b=2 - collision\n\t\n\t// clocks of bus\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\n\t\n\t// a sender sends (ok - no other message being sent)\n\t[send1] (b=0) -> (b'=1);\n\t[send2] (b=0) -> (b'=1);\n\t[send3] (b=0) -> (b'=1);\n\t[send4] (b=0) -> (b'=1);\n\t\n\t// a sender sends (bus busy - collision)\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send3] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t[send4] (b=1|b=2) & (y1<sigma) -> (b'=2);\n\t\n\t// finish sending\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\n\t[end3] (b=1) -> (b'=0) & (y1'=0);\n\t[end4] (b=1) -> (b'=0) & (y1'=0);\n\t\n\t// bus busy\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy3] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t[busy4] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \n\t\n\t// collision detected\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\n\t\n\t// time passage\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\n\t\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n// model of first sender\nmodule station1\n\t\n\t// LOCAL STATE\n\ts1 : [0..5];\n\t// s1=0 - initial state\n\t// s1=1 - transmit\n\t// s1=2 - collision (set backoff)\n\t// s1=3 - wait (bus busy)\n\t// s1=4 - successfully sent\n\t\n\t// LOCAL CLOCK\n\tx1 : [0..max(lambda,slot)];\n\t\n\t// BACKOFF COUNTER (number of slots to wait)\n\tbc1 : [0..M];\n\t\n\t// COLLISION COUNTER\n\tcd1 : [0..K];\n\t\n\t// start sending\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\n\t\n\t// transmitting\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\n\t\n\t// set backoff (no time can pass in this state)\n\t// probability depends on which transmission this is (cd1)\n\t[] s1=2 & cd1=1 ->  1/2 : (s1'=3) & (bc1'=0) + 1/2 : (s1'=3) & (bc1'=1) ;\n\t[] s1=2 & cd1=2 ->  1/4 : (s1'=3) & (bc1'=0) + 1/4 : (s1'=3) & (bc1'=1) + 1/4 : (s1'=3) & (bc1'=2) + 1/4 : (s1'=3) & (bc1'=3) ;\n\t[] s1=2 & cd1=3 ->  1/8 : (s1'=3) & (bc1'=0) + 1/8 : (s1'=3) & (bc1'=1) + 1/8 : (s1'=3) & (bc1'=2) + 1/8 : (s1'=3) & (bc1'=3) + 1/8 : (s1'=3) & (bc1'=4) + 1/8 : (s1'=3) & (bc1'=5) + 1/8 : (s1'=3) & (bc1'=6) + 1/8 : (s1'=3) & (bc1'=7) ;\n\t[] s1=2 & cd1=4 ->  1/16 : (s1'=3) & (bc1'=0) + 1/16 : (s1'=3) & (bc1'=1) + 1/16 : (s1'=3) & (bc1'=2) + 1/16 : (s1'=3) & (bc1'=3) + 1/16 : (s1'=3) & (bc1'=4) + 1/16 : (s1'=3) & (bc1'=5) + 1/16 : (s1'=3) & (bc1'=6) + 1/16 : (s1'=3) & (bc1'=7) + 1/16 : (s1'=3) & (bc1'=8) + 1/16 : (s1'=3) & (bc1'=9) + 1/16 : (s1'=3) & (bc1'=10) + 1/16 : (s1'=3) & (bc1'=11) + 1/16 : (s1'=3) & (bc1'=12) + 1/16 : (s1'=3) & (bc1'=13) + 1/16 : (s1'=3) & (bc1'=14) + 1/16 : (s1'=3) & (bc1'=15) ;\n\t[] s1=2 & cd1=5 ->  1/32 : (s1'=3) & (bc1'=0) + 1/32 : (s1'=3) & (bc1'=1) + 1/32 : (s1'=3) & (bc1'=2) + 1/32 : (s1'=3) & (bc1'=3) + 1/32 : (s1'=3) & (bc1'=4) + 1/32 : (s1'=3) & (bc1'=5) + 1/32 : (s1'=3) & (bc1'=6) + 1/32 : (s1'=3) & (bc1'=7) + 1/32 : (s1'=3) & (bc1'=8) + 1/32 : (s1'=3) & (bc1'=9) + 1/32 : (s1'=3) & (bc1'=10) + 1/32 : (s1'=3) & (bc1'=11) + 1/32 : (s1'=3) & (bc1'=12) + 1/32 : (s1'=3) & (bc1'=13) + 1/32 : (s1'=3) & (bc1'=14) + 1/32 : (s1'=3) & (bc1'=15) + 1/32 : (s1'=3) & (bc1'=16) + 1/32 : (s1'=3) & (bc1'=17) + 1/32 : (s1'=3) & (bc1'=18) + 1/32 : (s1'=3) & (bc1'=19) + 1/32 : (s1'=3) & (bc1'=20) + 1/32 : (s1'=3) & (bc1'=21) + 1/32 : (s1'=3) & (bc1'=22) + 1/32 : (s1'=3) & (bc1'=23) + 1/32 : (s1'=3) & (bc1'=24) + 1/32 : (s1'=3) & (bc1'=25) + 1/32 : (s1'=3) & (bc1'=26) + 1/32 : (s1'=3) & (bc1'=27) + 1/32 : (s1'=3) & (bc1'=28) + 1/32 : (s1'=3) & (bc1'=29) + 1/32 : (s1'=3) & (bc1'=30) + 1/32 : (s1'=3) & (bc1'=31) ;\n\t[] s1=2 & cd1=6 ->  1/64 : (s1'=3) & (bc1'=0) + 1/64 : (s1'=3) & (bc1'=1) + 1/64 : (s1'=3) & (bc1'=2) + 1/64 : (s1'=3) & (bc1'=3) + 1/64 : (s1'=3) & (bc1'=4) + 1/64 : (s1'=3) & (bc1'=5) + 1/64 : (s1'=3) & (bc1'=6) + 1/64 : (s1'=3) & (bc1'=7) + 1/64 : (s1'=3) & (bc1'=8) + 1/64 : (s1'=3) & (bc1'=9) + 1/64 : (s1'=3) & (bc1'=10) + 1/64 : (s1'=3) & (bc1'=11) + 1/64 : (s1'=3) & (bc1'=12) + 1/64 : (s1'=3) & (bc1'=13) + 1/64 : (s1'=3) & (bc1'=14) + 1/64 : (s1'=3) & (bc1'=15) + 1/64 : (s1'=3) & (bc1'=16) + 1/64 : (s1'=3) & (bc1'=17) + 1/64 : (s1'=3) & (bc1'=18) + 1/64 : (s1'=3) & (bc1'=19) + 1/64 : (s1'=3) & (bc1'=20) + 1/64 : (s1'=3) & (bc1'=21) + 1/64 : (s1'=3) & (bc1'=22) + 1/64 : (s1'=3) & (bc1'=23) + 1/64 : (s1'=3) & (bc1'=24) + 1/64 : (s1'=3) & (bc1'=25) + 1/64 : (s1'=3) & (bc1'=26) + 1/64 : (s1'=3) & (bc1'=27) + 1/64 : (s1'=3) & (bc1'=28) + 1/64 : (s1'=3) & (bc1'=29) + 1/64 : (s1'=3) & (bc1'=30) + 1/64 : (s1'=3) & (bc1'=31) + 1/64 : (s1'=3) & (bc1'=32) + 1/64 : (s1'=3) & (bc1'=33) + 1/64 : (s1'=3) & (bc1'=34) + 1/64 : (s1'=3) & (bc1'=35) + 1/64 : (s1'=3) & (bc1'=36) + 1/64 : (s1'=3) & (bc1'=37) + 1/64 : (s1'=3) & (bc1'=38) + 1/64 : (s1'=3) & (bc1'=39) + 1/64 : (s1'=3) & (bc1'=40) + 1/64 : (s1'=3) & (bc1'=41) + 1/64 : (s1'=3) & (bc1'=42) + 1/64 : (s1'=3) & (bc1'=43) + 1/64 : (s1'=3) & (bc1'=44) + 1/64 : (s1'=3) & (bc1'=45) + 1/64 : (s1'=3) & (bc1'=46) + 1/64 : (s1'=3) & (bc1'=47) + 1/64 : (s1'=3) & (bc1'=48) + 1/64 : (s1'=3) & (bc1'=49) + 1/64 : (s1'=3) & (bc1'=50) + 1/64 : (s1'=3) & (bc1'=51) + 1/64 : (s1'=3) & (bc1'=52) + 1/64 : (s1'=3) & (bc1'=53) + 1/64 : (s1'=3) & (bc1'=54) + 1/64 : (s1'=3) & (bc1'=55) + 1/64 : (s1'=3) & (bc1'=56) + 1/64 : (s1'=3) & (bc1'=57) + 1/64 : (s1'=3) & (bc1'=58) + 1/64 : (s1'=3) & (bc1'=59) + 1/64 : (s1'=3) & (bc1'=60) + 1/64 : (s1'=3) & (bc1'=61) + 1/64 : (s1'=3) & (bc1'=62) + 1/64 : (s1'=3) & (bc1'=63) ;\n\t\n\t// wait until backoff counter reaches 0 then send again\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\n\t\n\t// once finished nothing matters\n\t[time] (s1>=4) -> (x1'=0);\n\nendmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\nmodule station3=station1[s1=s3,x1=x3,cd1=cd3,bc1=bc3,send1=send3,busy1=busy3,end1=end3] endmodule\nmodule station4=station1[s1=s4,x1=x4,cd1=cd4,bc1=bc4,send1=send4,busy1=busy4,end1=end4] endmodule\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward structure for expected time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// labels/formulae\nlabel \"all_delivered\" = s1=4&s2=4&s3=4&s4=4;\nlabel \"one_delivered\" = s1=4|s2=4|s3=4|s4=4;\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2)|(cd3=K & s3=1 & b=2)|(cd4=K & s4=1 & b=2);\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1,s3=4?cd3:K+1,s4=4?cd4:K+1);\nformula min_collisions = min(cd1,cd2,cd3,cd4);\nformula max_collisions = max(cd1,cd2,cd3,cd4);\n\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 6 7 8 9 10 15 )\n\techo \"Generating for N=$N\"\n\tprismpp .dining_cryptN.nm.pp $N >! dining_crypt$N.nm\n\tunix2dos dining_crypt$N.nm\nend\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/.dining_cryptN.nm.pp",
    "content": "#const N#\n// model of dining cryptographers\n// gxn/dxp 15/11/06\n\nmdp\n\n// number of cryptographers\nconst int N = #N#;\n\r\n// constants used in renaming (identities of cryptographers)\n#for i=1:N#\nconst int p#i# = #i#;\n#end#\n\n// global variable which decides who pays\n// (0 - master pays, i=1..N - cryptographer i pays)\nglobal pay : [0..N];\n\n// module for first cryptographer\nmodule crypt1\n\t\n\tcoin1 : [0..2]; // value of its coin\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\n\t\n\t// flip coin\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\n\t\n\t// make statement (once relevant coins have been flipped)\n\t// agree (coins the same and does not pay)\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\n\t// disagree (coins different and does not pay)\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\n\t// disagree (coins the same and pays)\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\n\t// agree (coins different and pays)\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\n\t\n\t// synchronising loop when finished to avoid deadlock\n\t[done] s1=1 -> true;\n\nendmodule\n\n// construct further cryptographers with renaming\n#for i=2:N#\nmodule crypt#i# = crypt1 [ coin1=coin#i#, s1=s#i#, agree1=agree#i#, p1=p#i#, coin2=coin#func(mod,i,N)+1# ] endmodule\n#end#\n\n// set of initial states\n// (cryptographers in their initial state, \"pay\" can be anything)\ninit #& i=1:N# coin#i#=0&s#i#=0&agree#i#=0 #end# endinit\n\n// unique integer representing outcome\r\nformula outcome = #+ j=1:N# #func(floor,func(pow,2,N-j))#*agree#j# #end#;\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, #+ j=1:N#agree#j##end#, 2);\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = #& i=1:N#s#i#=1#end#;\r\n// label denoting states where number of \"agree\"s is even\nlabel \"even\" = func(mod,(#+ i=1:N#agree#i##end#),2)=0;\r\n// label denoting states where number of \"agree\"s is even\nlabel \"odd\" = func(mod,(#+ i=1:N#agree#i##end#),2)=1;\r\n\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/README.txt",
    "content": "This case study is based on the well known dining cryptographers problem [Cha88].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/dining_crypt.php\r\n\r\n=====================================================================================\r\n\r\n[Cha88]\r\nD. Chaum\nThe Dining Cryptographers Problem: Unconditional Sender and Recipient Untraceability\nJournal of Cryptology, vol. 1, pp 65-75, 1988\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/anonymity.pctl",
    "content": "const int k;\r\n\n// Anonymity - check for k=0..2^N - both min/max should be the same and equal to 1/2^(N-1) or 0\n// (depending on the parity of the number of bits in the binary representation of outcome)\r\nPmin=? [ F \"done\" & outcome = k {\"init\"&pay>0}{min} ]\r\nPmax=? [ F \"done\" & outcome = k {\"init\"&pay>0}{max} ]\r\n\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/auto",
    "content": "#!/bin/csh\n\nprism dining_crypt3.nm  correctness.pctl\nprism dining_crypt4.nm  correctness.pctl\nprism dining_crypt5.nm  correctness.pctl\nprism dining_crypt6.nm  correctness.pctl\nprism dining_crypt7.nm  correctness.pctl\n#prism dining_crypt8.nm  correctness.pctl\n#prism dining_crypt9.nm  correctness.pctl\n#prism dining_crypt10.nm correctness.pctl\n#prism dining_crypt15.nm correctness.pctl\n\nprism dining_crypt3.nm  anonymity.pctl -const k=0:7 -m -nopre -exportresults stdout\nprism dining_crypt4.nm  anonymity.pctl -const k=0:15 -m -nopre -exportresults stdout\n\nprism dining_crypt5.nm  anonymity.pctl -const k=0 -m -nopre\nprism dining_crypt6.nm  anonymity.pctl -const k=1 -m -nopre\nprism dining_crypt7.nm  anonymity.pctl -const k=0 -m -nopre\n#prism dining_crypt8.nm  anonymity.pctl -const k=1 -m -nopre\n#prism dining_crypt9.nm  anonymity.pctl -const k=0 -m -nopre\n#prism dining_crypt10.nm anonymity.pctl -const k=1 -m -nopre\n#prism dining_crypt15.nm anonymity.pctl -const k=0 -m -nopre\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/correctness.pctl",
    "content": "// Correctness for the case where the master pays\n// (final parity of number of number of \"agrees\"s matches that of N)\nfilter(forall, (pay=0) => P>=1 [ F \"done\" & parity=func(mod, N, 2) ])\n\n// Correctness for the case where a cryptographer pays\n// (final parity of number of number of \"agrees\"s does not match that of N)\nfilter(forall, (pay>0) => P>=1 [ F \"done\" & parity!=func(mod, N, 2) ])\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt10.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 10;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\nconst int p4 = 4;\r\nconst int p5 = 5;\r\nconst int p6 = 6;\r\nconst int p7 = 7;\r\nconst int p8 = 8;\r\nconst int p9 = 9;\r\nconst int p10 = 10;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin4 ] endmodule\r\nmodule crypt4 = crypt1 [ coin1=coin4, s1=s4, agree1=agree4, p1=p4, coin2=coin5 ] endmodule\r\nmodule crypt5 = crypt1 [ coin1=coin5, s1=s5, agree1=agree5, p1=p5, coin2=coin6 ] endmodule\r\nmodule crypt6 = crypt1 [ coin1=coin6, s1=s6, agree1=agree6, p1=p6, coin2=coin7 ] endmodule\r\nmodule crypt7 = crypt1 [ coin1=coin7, s1=s7, agree1=agree7, p1=p7, coin2=coin8 ] endmodule\r\nmodule crypt8 = crypt1 [ coin1=coin8, s1=s8, agree1=agree8, p1=p8, coin2=coin9 ] endmodule\r\nmodule crypt9 = crypt1 [ coin1=coin9, s1=s9, agree1=agree9, p1=p9, coin2=coin10 ] endmodule\r\nmodule crypt10 = crypt1 [ coin1=coin10, s1=s10, agree1=agree10, p1=p10, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0 & coin4=0&s4=0&agree4=0 & coin5=0&s5=0&agree5=0 & coin6=0&s6=0&agree6=0 & coin7=0&s7=0&agree7=0 & coin8=0&s8=0&agree8=0 & coin9=0&s9=0&agree9=0 & coin10=0&s10=0&agree10=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  512*agree1 + 256*agree2 + 128*agree3 + 64*agree4 + 32*agree5 + 16*agree6 + 8*agree7 + 4*agree8 + 2*agree9 + 1*agree10 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9+agree10, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1&s4=1&s5=1&s6=1&s7=1&s8=1&s9=1&s10=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9+agree10),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9+agree10),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt15.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 15;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\nconst int p4 = 4;\r\nconst int p5 = 5;\r\nconst int p6 = 6;\r\nconst int p7 = 7;\r\nconst int p8 = 8;\r\nconst int p9 = 9;\r\nconst int p10 = 10;\r\nconst int p11 = 11;\r\nconst int p12 = 12;\r\nconst int p13 = 13;\r\nconst int p14 = 14;\r\nconst int p15 = 15;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin4 ] endmodule\r\nmodule crypt4 = crypt1 [ coin1=coin4, s1=s4, agree1=agree4, p1=p4, coin2=coin5 ] endmodule\r\nmodule crypt5 = crypt1 [ coin1=coin5, s1=s5, agree1=agree5, p1=p5, coin2=coin6 ] endmodule\r\nmodule crypt6 = crypt1 [ coin1=coin6, s1=s6, agree1=agree6, p1=p6, coin2=coin7 ] endmodule\r\nmodule crypt7 = crypt1 [ coin1=coin7, s1=s7, agree1=agree7, p1=p7, coin2=coin8 ] endmodule\r\nmodule crypt8 = crypt1 [ coin1=coin8, s1=s8, agree1=agree8, p1=p8, coin2=coin9 ] endmodule\r\nmodule crypt9 = crypt1 [ coin1=coin9, s1=s9, agree1=agree9, p1=p9, coin2=coin10 ] endmodule\r\nmodule crypt10 = crypt1 [ coin1=coin10, s1=s10, agree1=agree10, p1=p10, coin2=coin11 ] endmodule\r\nmodule crypt11 = crypt1 [ coin1=coin11, s1=s11, agree1=agree11, p1=p11, coin2=coin12 ] endmodule\r\nmodule crypt12 = crypt1 [ coin1=coin12, s1=s12, agree1=agree12, p1=p12, coin2=coin13 ] endmodule\r\nmodule crypt13 = crypt1 [ coin1=coin13, s1=s13, agree1=agree13, p1=p13, coin2=coin14 ] endmodule\r\nmodule crypt14 = crypt1 [ coin1=coin14, s1=s14, agree1=agree14, p1=p14, coin2=coin15 ] endmodule\r\nmodule crypt15 = crypt1 [ coin1=coin15, s1=s15, agree1=agree15, p1=p15, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0 & coin4=0&s4=0&agree4=0 & coin5=0&s5=0&agree5=0 & coin6=0&s6=0&agree6=0 & coin7=0&s7=0&agree7=0 & coin8=0&s8=0&agree8=0 & coin9=0&s9=0&agree9=0 & coin10=0&s10=0&agree10=0 & coin11=0&s11=0&agree11=0 & coin12=0&s12=0&agree12=0 & coin13=0&s13=0&agree13=0 & coin14=0&s14=0&agree14=0 & coin15=0&s15=0&agree15=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  16384*agree1 + 8192*agree2 + 4096*agree3 + 2048*agree4 + 1024*agree5 + 512*agree6 + 256*agree7 + 128*agree8 + 64*agree9 + 32*agree10 + 16*agree11 + 8*agree12 + 4*agree13 + 2*agree14 + 1*agree15 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9+agree10+agree11+agree12+agree13+agree14+agree15, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1&s4=1&s5=1&s6=1&s7=1&s8=1&s9=1&s10=1&s11=1&s12=1&s13=1&s14=1&s15=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9+agree10+agree11+agree12+agree13+agree14+agree15),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9+agree10+agree11+agree12+agree13+agree14+agree15),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt3.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 3;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  4*agree1 + 2*agree2 + 1*agree3 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt4.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 4;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\nconst int p4 = 4;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin4 ] endmodule\r\nmodule crypt4 = crypt1 [ coin1=coin4, s1=s4, agree1=agree4, p1=p4, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0 & coin4=0&s4=0&agree4=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  8*agree1 + 4*agree2 + 2*agree3 + 1*agree4 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3+agree4, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1&s4=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3+agree4),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3+agree4),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt5.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 5;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\nconst int p4 = 4;\r\nconst int p5 = 5;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin4 ] endmodule\r\nmodule crypt4 = crypt1 [ coin1=coin4, s1=s4, agree1=agree4, p1=p4, coin2=coin5 ] endmodule\r\nmodule crypt5 = crypt1 [ coin1=coin5, s1=s5, agree1=agree5, p1=p5, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0 & coin4=0&s4=0&agree4=0 & coin5=0&s5=0&agree5=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  16*agree1 + 8*agree2 + 4*agree3 + 2*agree4 + 1*agree5 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3+agree4+agree5, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1&s4=1&s5=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3+agree4+agree5),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3+agree4+agree5),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt6.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 6;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\nconst int p4 = 4;\r\nconst int p5 = 5;\r\nconst int p6 = 6;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin4 ] endmodule\r\nmodule crypt4 = crypt1 [ coin1=coin4, s1=s4, agree1=agree4, p1=p4, coin2=coin5 ] endmodule\r\nmodule crypt5 = crypt1 [ coin1=coin5, s1=s5, agree1=agree5, p1=p5, coin2=coin6 ] endmodule\r\nmodule crypt6 = crypt1 [ coin1=coin6, s1=s6, agree1=agree6, p1=p6, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0 & coin4=0&s4=0&agree4=0 & coin5=0&s5=0&agree5=0 & coin6=0&s6=0&agree6=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  32*agree1 + 16*agree2 + 8*agree3 + 4*agree4 + 2*agree5 + 1*agree6 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3+agree4+agree5+agree6, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1&s4=1&s5=1&s6=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt7.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 7;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\nconst int p4 = 4;\r\nconst int p5 = 5;\r\nconst int p6 = 6;\r\nconst int p7 = 7;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin4 ] endmodule\r\nmodule crypt4 = crypt1 [ coin1=coin4, s1=s4, agree1=agree4, p1=p4, coin2=coin5 ] endmodule\r\nmodule crypt5 = crypt1 [ coin1=coin5, s1=s5, agree1=agree5, p1=p5, coin2=coin6 ] endmodule\r\nmodule crypt6 = crypt1 [ coin1=coin6, s1=s6, agree1=agree6, p1=p6, coin2=coin7 ] endmodule\r\nmodule crypt7 = crypt1 [ coin1=coin7, s1=s7, agree1=agree7, p1=p7, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0 & coin4=0&s4=0&agree4=0 & coin5=0&s5=0&agree5=0 & coin6=0&s6=0&agree6=0 & coin7=0&s7=0&agree7=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  64*agree1 + 32*agree2 + 16*agree3 + 8*agree4 + 4*agree5 + 2*agree6 + 1*agree7 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3+agree4+agree5+agree6+agree7, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1&s4=1&s5=1&s6=1&s7=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt8.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 8;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\nconst int p4 = 4;\r\nconst int p5 = 5;\r\nconst int p6 = 6;\r\nconst int p7 = 7;\r\nconst int p8 = 8;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin4 ] endmodule\r\nmodule crypt4 = crypt1 [ coin1=coin4, s1=s4, agree1=agree4, p1=p4, coin2=coin5 ] endmodule\r\nmodule crypt5 = crypt1 [ coin1=coin5, s1=s5, agree1=agree5, p1=p5, coin2=coin6 ] endmodule\r\nmodule crypt6 = crypt1 [ coin1=coin6, s1=s6, agree1=agree6, p1=p6, coin2=coin7 ] endmodule\r\nmodule crypt7 = crypt1 [ coin1=coin7, s1=s7, agree1=agree7, p1=p7, coin2=coin8 ] endmodule\r\nmodule crypt8 = crypt1 [ coin1=coin8, s1=s8, agree1=agree8, p1=p8, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0 & coin4=0&s4=0&agree4=0 & coin5=0&s5=0&agree5=0 & coin6=0&s6=0&agree6=0 & coin7=0&s7=0&agree7=0 & coin8=0&s8=0&agree8=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  128*agree1 + 64*agree2 + 32*agree3 + 16*agree4 + 8*agree5 + 4*agree6 + 2*agree7 + 1*agree8 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1&s4=1&s5=1&s6=1&s7=1&s8=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/dining_crypt/dining_crypt9.nm",
    "content": "// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 9;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\nconst int p4 = 4;\r\nconst int p5 = 5;\r\nconst int p6 = 6;\r\nconst int p7 = 7;\r\nconst int p8 = 8;\r\nconst int p9 = 9;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin4 ] endmodule\r\nmodule crypt4 = crypt1 [ coin1=coin4, s1=s4, agree1=agree4, p1=p4, coin2=coin5 ] endmodule\r\nmodule crypt5 = crypt1 [ coin1=coin5, s1=s5, agree1=agree5, p1=p5, coin2=coin6 ] endmodule\r\nmodule crypt6 = crypt1 [ coin1=coin6, s1=s6, agree1=agree6, p1=p6, coin2=coin7 ] endmodule\r\nmodule crypt7 = crypt1 [ coin1=coin7, s1=s7, agree1=agree7, p1=p7, coin2=coin8 ] endmodule\r\nmodule crypt8 = crypt1 [ coin1=coin8, s1=s8, agree1=agree8, p1=p8, coin2=coin9 ] endmodule\r\nmodule crypt9 = crypt1 [ coin1=coin9, s1=s9, agree1=agree9, p1=p9, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0 & coin4=0&s4=0&agree4=0 & coin5=0&s5=0&agree5=0 & coin6=0&s6=0&agree6=0 & coin7=0&s7=0&agree7=0 & coin8=0&s8=0&agree8=0 & coin9=0&s9=0&agree9=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  256*agree1 + 128*agree2 + 64*agree3 + 32*agree4 + 16*agree5 + 8*agree6 + 4*agree7 + 2*agree8 + 1*agree9 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1&s4=1&s5=1&s6=1&s7=1&s8=1&s9=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3+agree4+agree5+agree6+agree7+agree8+agree9),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/firewire/README.txt",
    "content": "This case study concerns the Tree Identify Protocol of the IEEE 1394 High Performance Serial Bus (called ``FireWire'').\n\nThese are MDP models, manually constructed from probabilistic timed automaton (PTA) models,\nusing the \"digital clocks\" semantics [KNPS06]. You can also find the PTA models, in the directory ../pta/firewire.\n\nWe consider the following probabilistic timed automata models of the root contention part of the \ntree identify protocol, which are based on probabilistic I/O automata models presented in [SV99].\n\nimpl: which consists of the parallel composition of two nodes (Node1 and Node2),\n      and two communication channels (Wire12 for messages from Node1 to Node2,\n      and Wire21 for messages from Node2 to Node1) and corresponds to the \n      system Impl of [SV99]. \n\nabst: which is represented by a single probabilistic timed automaton and is an abstraction of Impl \n      based on the the probabilistic I/O automaton I1 of [SV99].\n\nFor more information, see: http://www.prismmodelchecker.org/casestudies/firewire.php\n\n=====================================================================================\n\n[SV99]\nM. Stoelinga and F. Vaandrager\nRoot Contention in IEEE 1394\nIn Proc.  5th AMAST Workshop on Real-Time and Probabilistic Systems (ARTS'99), pp. 53-74, 1999\n(Available as Volume 1601 of LNCS, (c) Springer Verlag)\n\n[KNPS06]\nM. Kwiatkowska, G. Norman, D. Parker and J. Sproston\nPerformance Analysis of Probabilistic Timed Automata using Digital Clocks\nFormal Methods in System Design, 29:33-78, 2006"
  },
  {
    "path": "prism-examples/mdps/firewire/abst/auto",
    "content": "#!/bin/csh\n\n# liveness\nprism firewire.nm liveness.pctl -const delay=36,fast=0.5\n\n# maximum expected time\nprism firewire.nm expected.pctl -const delay=3,fast=0.2:0.1:0.8 -prop 1\nprism firewire.nm expected.pctl -const delay=36,fast=0.2:0.1:0.8  -prop 1\n\n# maximum expected time\nprism firewire.nm expected.pctl -const delay=3,fast=0.2:0.1:0.8 -prop 2 \nprism firewire.nm expected.pctl -const delay=36,fast=0.2:0.1:0.8 -prop 2 \n\n# deadline properties\nforeach deadline (200 300 400 500 600) # 800 1000)\n\tprism deadline.nm deadline.pctl -const deadline=$deadline,delay=36,fast=0.5 -m\nend\n"
  },
  {
    "path": "prism-examples/mdps/firewire/abst/deadline.nm",
    "content": "// integer semantics version of abstract firewire protocol\n// with clock for deadline properties\r\n// gxn 23/05/2001\r\n\r\nmdp\r\n\r\n// deadline\nconst int deadline;\nconst int ky = deadline;\n// wire delay (based on max length of wire)\nconst int delay;\n// probability of choosing fast\nconst double fast;\nconst double slow = 1-fast;\n\n// maximal constant\nconst int kx = 167;\n\nmodule abstract_firewire\n\t\n\t// deadline clock\n\ty : [0..ky+1];\n\t\n\t// model clock \n\tx : [0..kx+1];\n\t\n\t// local state\n\ts : [0..11];\n\t// 0 -start_start\n\t// 1 -fast_start\n\t// 2 -start_fast\n\t// 3 -start_slow\n\t// 4 -slow_start\n\t// 5 -fast_fast\n\t// 6 -fast_slow\n\t// 7 -slow_fast\n\t// 8 -slow_slow\n\t// 9 -seldone\n\t// 10 -done_before\n\t// 11 -done_after\n\t\n\t// initial state\n\t[] (s=0) & (x<delay) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=0) -> fast : (s'=1) + slow : (s'=4);\n\t[] (s=0) -> fast : (s'=2) + slow : (s'=3);\n\t// fast_start\n\t[] (s=1) & (x<delay) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=1) -> fast : (s'=5) & (x'=0) + slow : (s'=6) & (x'=0);\n\t// start_fast\n\t[] (s=2) & (x<delay) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=2) -> fast : (s'=5) & (x'=0) + slow : (s'=7) & (x'=0);\n\t// start_slow\n\t[] (s=3) & (x<delay) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=3) -> fast : (s'=6) & (x'=0) + slow : (s'=8) & (x'=0);\n\t// slow_start\n\t[] (s=4) & (x<delay) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=4) -> fast : (s'=7) & (x'=0) + slow : (s'=8) & (x'=0);\n\t// fast_fast\n\t[] (s=5) & (x<85) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=5) & (x>=76) -> (s'=0) & (x'=0);\n\t[] (s=5) & (x>=76-delay) -> (s'=9) & (x'=0);\n\t// fast_slow\n\t[] (s=6) & (x<167) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=6) & (x>=159-delay) -> (s'=9) & (x'=0);\n\t// slow_fast\n\t[] (s=7) & (x<167) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=7) & (x>=159-delay) -> (s'=9) & (x'=0);\n\t// slow_slow\n\t[] (s=8) & (x<167) -> (x'=min(x+1,kx+1)) & (y'=min(y+1,ky+1));\n\t[] (s=8) & (x>=159) -> (s'=0) & (x'=0);\n\t[] (s=8) & (x>=159-delay) -> (s'=9) & (x'=0);\n\t\n\t// move to deadline exceeded when y>=deadline\n\t[] (y<=deadline) & (s=9) -> (s'=10) & (y'=0);\n\t[] (y>deadline) & (s=9) -> (s'=11) & (y'=0);\n\t// done\n\t[] (s>=10) -> true;\n\t\nendmodule\r\n"
  },
  {
    "path": "prism-examples/mdps/firewire/abst/deadline.pctl",
    "content": "// deadline property\r\nPmin=?[ true U (s=10) ]\r\n"
  },
  {
    "path": "prism-examples/mdps/firewire/abst/expected.pctl",
    "content": "// maximum expected time\nR{\"time\"}min=?[F (s=9) ]\n// maximum expected rounds\nR{\"rounds\"}max=?[F (s=9) ]\n"
  },
  {
    "path": "prism-examples/mdps/firewire/abst/firewire.nm",
    "content": "// integer semantics version of abstract firewire protocol\r\n// gxn 23/05/2001\r\n\r\nmdp\r\n\n// wire delay\nconst int delay;\n\n// probability of choosing fast and slow\nconst double fast;\nconst double slow = 1-fast;\n\r\n// largest constant the clock of the system is compared to\r\nconst int kx = 167;\r\n\r\nmodule abstract_firewire\n\t\n\t// clock \n\tx : [0..kx+1];\n\t\n\t// local state\n\ts : [0..9];\n\t// 0 -start_start\n\t// 1 -fast_start\n\t// 2 -start_fast\n\t// 3 -start_slow\n\t// 4 -slow_start\n\t// 5 -fast_fast\n\t// 6 -fast_slow\n\t// 7 -slow_fast\n\t// 8 -slow_slow\n\t// 9 -done\n\t\n\t// initial state\n\t[time] s=0 & x<delay -> (x'=min(x+1,kx+1));\n\t[round] s=0 -> fast : (s'=1) + slow : (s'=4);\n\t[round] s=0 -> fast : (s'=2) + slow : (s'=3);\n\t// fast_start\n\t[time] s=1 & x<delay -> (x'=min(x+1,kx+1));\n\t[] s=1 -> fast : (s'=5) & (x'=0) + slow : (s'=6) & (x'=0);\n\t// start_fast\n\t[time] s=2 & x<delay -> (x'=min(x+1,kx+1));\n\t[] s=2 -> fast : (s'=5) & (x'=0) + slow : (s'=7) & (x'=0);\n\t// start_slow\n\t[time] s=3 & x<delay -> (x'=min(x+1,kx+1));\n\t[] s=3 -> fast : (s'=6) & (x'=0) + slow : (s'=8) & (x'=0);\n\t// slow_start\n\t[time] s=4 & x<delay -> (x'=min(x+1,kx+1));\n\t[] s=4 -> fast : (s'=7) & (x'=0) + slow : (s'=8) & (x'=0);\n\t// fast_fast\n\t[time] s=5 & (x<85) -> (x'=min(x+1,kx+1));\n\t[] s=5 & (x>=76) -> (s'=0) & (x'=0);\n\t[] s=5 & (x>=76-delay) -> (s'=9) & (x'=0);\n\t// fast_slow\n\t[time] s=6 & x<167 -> (x'=min(x+1,kx+1));\n\t[] s=6 & x>=159-delay -> (s'=9) & (x'=0);\n\t// slow_fast\n\t[time] s=7 & x<167 -> (x'=min(x+1,kx+1));\n\t[] s=7 & x>=159-delay -> (s'=9) & (x'=0);\n\t// slow_slow\n\t[time] s=8 & x<167 -> (x'=min(x+1,kx+1));\n\t[] s=8 & x>=159 -> (s'=0) & (x'=0);\n\t[] s=8 & x>=159-delay -> (s'=9) & (x'=0);\n\t// done\n\t[] s=9 -> (s'=s);\n\t\nendmodule\n\n//reward structures\n// time\nrewards \"time\"\n\t[time] true : 1;\nendrewards\n// number of rounds\nrewards \"rounds\"\n\t[round] true : 1;\nendrewards\r\n"
  },
  {
    "path": "prism-examples/mdps/firewire/abst/liveness.pctl",
    "content": "// liveness property (eventually a process is made the leader)\r\nP>=1 [ F (s=9) ]\r\n"
  },
  {
    "path": "prism-examples/mdps/firewire/impl/auto",
    "content": "#!/bin/csh\n\n# liveness\nprism firewire.nm liveness.pctl -const delay=36,fast=0.5 -m\n\n# maximum expected time\nprism firewire.nm expected.pctl -const delay=3,fast=0.2:0.1:0.8 -prop 1 -s\n#prism firewire.nm expected.pctl -const delay=36,fast=0.2:0.1:0.8 -prop 1 =m\n\n# maximum expected time sending\nprism firewire.nm expected.pctl -const delay=3,fast=0.2:0.1:0.8 -prop 2 -s\n#prism firewire.nm expected.pctl -const delay=36,fast=0.2:0.1:0.8 -prop 2 -m\n\n# deadline properties\nforeach deadline (200 300 400) # 500 600 800 1000)\n\tprism deadline.nm deadline.pctl -const deadline=$deadline,delay=3,fast=0.5 -s\n#\tprism deadline.nm deadline.pctl -const deadline=$deadline,delay=36,fast=0.5 -m\nend\n\n"
  },
  {
    "path": "prism-examples/mdps/firewire/impl/deadline.nm",
    "content": "// full firewire protocol with integer semantics\r\n// dxp/gxn 14/06/01\r\n\r\n// CLOCKS\r\n// x1 clock for node1\r\n// x2 clock for node2\r\n// y1 and y2 clocks for wire12\r\n// z1 and z2 clocks for wire21\r\n\r\n// deadline\r\nconst int deadline;\r\n\r\n// maximum and minimum delays\r\n// for fast\r\nconst int rc_fast_max = 85;\r\nconst int rc_fast_min = 76;\r\n// for slow\r\nconst int rc_slow_max = 167;\r\nconst int rc_slow_min = 159;\r\n// wire\nconst int delay;\n// probability of chooisng fast\nconst double fast;\nconst double slow=1-fast;\n\r\nmodule wire12\n\t\n\tw12 : [0..10];\n\t// 0 - empty\n\t// 1 -\trec_req\n\t// 2 -  rec_req_ack\n\t// 3 -\trec_ack\n\t// 4 -\trec_ack_idle\n\t// 5 -\trec_idle\n\t// 6 -\trec_idle_req\n\t// 7 -\trec_ack_req\n\t// 8 -\trec_req_idle\n\t// 9 -\trec_idle_ack\n\t\n\t// clock for wire12\n\ty1 : [0..37];\n\ty2 : [0..37];\n\t\n\t// empty\n\t// do not need y1 and y2 to increase as always reset when this state is left\n\t// similarly can reset y1 and y2 when we re-enter this state\n\t[snd_req12]  (w12=0) -> (w12'=1) & (y1'=0) & (y2'=0);\n\t[snd_ack12]  (w12=0) -> (w12'=3) & (y1'=0) & (y2'=0);\n\t[snd_idle12] (w12=0) -> (w12'=5) & (y1'=0) & (y2'=0);\n\t[time]       (w12=0) -> (w12'=w12);\n\t// rec_req\n\t[snd_req12]  (w12=1) -> (w12'=1);\n\t[rec_req12]  (w12=1) -> (w12'=0) & (y1'=0) & (y2'=0);\n\t[snd_ack12]  (w12=1) -> (w12'=2) & (y2'=0);\n\t[snd_idle12] (w12=1) -> (w12'=8) & (y2'=0);\n\t[time]       (w12=1) & (y2<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t// rec_req_ack\n\t[snd_ack12] (w12=2) -> (w12'=2);\n\t[rec_req12] (w12=2) -> (w12'=3);\n\t[time]      (w12=2) & (y1<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t// rec_ack\n\t[snd_ack12]  (w12=3) -> (w12'=3);\n\t[rec_ack12]  (w12=3) -> (w12'=0) & (y1'=0) & (y2'=0);\n\t[snd_idle12] (w12=3) -> (w12'=4) & (y2'=0);\n\t[snd_req12]  (w12=3) -> (w12'=7) & (y2'=0);\n\t[time]       (w12=3) & (y2<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t// rec_ack_idle\n\t[snd_idle12] (w12=4) -> (w12'=4);\n\t[rec_ack12]  (w12=4)  -> (w12'=5);\n\t[time]       (w12=4) & (y1<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t// rec_idle\n\t[snd_idle12] (w12=5) -> (w12'=5);\n\t[rec_idle12] (w12=5) -> (w12'=0) & (y1'=0) & (y2'=0);\n\t[snd_req12]  (w12=5) -> (w12'=6) & (y2'=0);\n\t[snd_ack12]  (w12=5) -> (w12'=9) & (y2'=0);\n\t[time]       (w12=5) & (y2<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t// rec_idle_req\n\t[snd_req12]  (w12=6)  -> (w12'=6);\n\t[rec_idle12] (w12=6) -> (w12'=1);\n\t[time]       (w12=6) & (y1<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t// rec_ack_req\n\t[snd_req12] (w12=7) -> (w12'=7);\n\t[rec_ack12] (w12=7) -> (w12'=1);\n\t[time]      (w12=7) & (y1<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t// rec_req_idle\n\t[snd_idle12] (w12=8) -> (w12'=8);\n\t[rec_req12]  (w12=8)  -> (w12'=5);\n\t[time]       (w12=8) & (y1<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t// rec_idle_ack\n\t[snd_ack12]  (w12=9)  -> (w12'=9);\n\t[rec_idle12] (w12=9) -> (w12'=3);\n\t[time]       (w12=9) & (y1<delay) ->  (y1'=min(y1+1,37)) & (y2'=min(y2+1,37));\n\t\nendmodule\n\nmodule node1\n\n\t// clock for node1\n\tx1 : [0..168];\n\t// local state\n\ts1 : [0..8];\n\t// 0 - root contention\n\t// 1 - rec_idle\n\t// 2 - rec_req_fast\n\t// 3 - rec_req_slow\n\t// 4 - rec_idle_fast\n\t// 5 - rec_idle_slow\n\t// 6 - snd_req\n\t// 7- almost_root\n\t// 8 - almost_child\n\t\n\t// added resets to x1 when not considered again until after rest\n\t\n\t// root contention (immediate state)\n\t[snd_idle12] (s1=0) -> fast : (s1'=2) & (x1'=0) +  slow : (s1'=3) & (x1'=0);\n\t[rec_idle21] (s1=0) -> (s1'=1);\n\t// rec_idle (immediate state)\n\t[snd_idle12] (s1=1) -> fast : (s1'=4) & (x1'=0) +  slow : (s1'=5) & (x1'=0);\n\t[rec_req21]  (s1=1) -> (s1'=0);\n\t// rec_req_fast\n\t[rec_idle21] (s1=2) -> (s1'=4);\n\t[snd_ack12]  (s1=2) & (x1>=rc_fast_min) -> (s1'=7) & (x1'=0);\n\t[time]       (s1=2) & (x1<rc_fast_max) -> (x1'=min(x1+1,168));\n\t// rec_req_slow\n\t[rec_idle21] (s1=3) -> (s1'=5);\n\t[snd_ack12]  (s1=3) & (x1>=rc_slow_min) -> (s1'=7) & (x1'=0);\n\t[time]       (s1=3) & (x1<rc_slow_max) -> (x1'=min(x1+1,168));\n\t// rec_idle_fast\n\t[rec_req21] (s1=4) -> (s1'=2);\n\t[snd_req12] (s1=4) & (x1>=rc_fast_min) -> (s1'=6) & (x1'=0);\n\t[time]      (s1=4) & (x1<rc_fast_max) -> (x1'=min(x1+1,168));\n\t// rec_idle_slow\n\t[rec_req21] (s1=5) -> (s1'=3);\n\t[snd_req12] (s1=5) & (x1>=rc_slow_min) -> (s1'=6) & (x1'=0);\n\t[time]      (s1=5) & (x1<rc_slow_max) -> (x1'=min(x1+1,168));\n\t// snd_req \n\t// do not use x1 until reset (in state 0 or in state 1) so do not need to increase x1\n\t// also can set x1 to 0 upon entering this state\n\t[rec_req21] (s1=6) -> (s1'=0);\n\t[rec_ack21] (s1=6) -> (s1'=8);\n\t[time]      (s1=6) -> (s1'=s1);\n\t// almost root (immediate) \n\t// loop in final states to remove deadlock\n\t// (wait until both process have decided otherwise need fairness)\n\t[] (s1=7) & (s2=8) -> (s1'=s1);\n\t[time] (s1=7) -> (s1'=s1);\n\t[] (s1=8) & (s2=7) -> (s1'=s1);\n\t[time] (s1=8) -> (s1'=s1);\n\t\nendmodule\n\n// wire21\nmodule wire21=wire12[w12=w21, y1=z1, y2=z2, snd_req12=snd_req21, snd_idle12=snd_idle21, snd_ack12=snd_ack21, \n                                            rec_req12=rec_req21, rec_idle12=rec_idle21, rec_ack12=rec_ack21] endmodule\n\n// node2\nmodule node2=node1[s1=s2, s2=s1, x1=x2, rec_req21=rec_req12, rec_idle21=rec_idle12, rec_ack21=rec_ack12, \n                                        snd_req12=snd_req21, snd_idle12=snd_idle21, snd_ack12=snd_ack21] endmodule\n\r\n// timer\r\nmodule timer\r\n\t\r\n\t// global time\r\n\tt : [0..deadline+1];\r\n\t\r\n\t// time increases\r\n\t[time] (t<deadline) -> (t'=min(t+1,deadline+1));\r\n\t// loop when time passes deadline\r\n\t[] (t>=deadline) -> (t'=t);\r\n\t// note that since we are finding the minimum probability\r\n\t// when t>=deadline  the adversary which gives the minimum probability\r\n\t// will always choose this transition, and hence the states of the \r\n\t// nodes and the wires will no longer change \r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-examples/mdps/firewire/impl/deadline.pctl",
    "content": "// time bound property\r\nPmin=? [ true U ( (s1=8) & (s2=7) ) | ( (s1=7) & (s2=8) ) ]\r\n"
  },
  {
    "path": "prism-examples/mdps/firewire/impl/expected.pctl",
    "content": "// maximum expected time\nR{\"time\"}min=?[F ((s1=8) & (s2=7)) | ((s1=7) & (s2=8)) ]\n// maximum expected rounds\nR{\"time_sending\"}max=?[F ((s1=8) & (s2=7)) | ((s1=7) & (s2=8)) ]\n"
  },
  {
    "path": "prism-examples/mdps/firewire/impl/firewire.nm",
    "content": "// firewire protocol with integer semantics\n// dxp/gxn 14/06/01\n\n// CLOCKS\n// x1 (x2) clock for node1 (node2)\n// y1 and y2 (z1 and z2) clocks for wire12 (wire21)\n\n// maximum and minimum delays\n// fast\nconst int rc_fast_max = 85;\nconst int rc_fast_min = 76;\n// slow\nconst int rc_slow_max = 167;\nconst int rc_slow_min = 159;\n// delay caused by the wire length\nconst int delay;\n// probability of choosing fast\nconst double fast;\nconst double slow=1-fast;\n\nmodule wire12\n\t\n\t// local state\n\tw12 : [0..9];\n\t// 0 - empty\n\t// 1 -\trec_req\n\t// 2 -  rec_req_ack\n\t// 3 -\trec_ack\n\t// 4 -\trec_ack_idle\n\t// 5 -\trec_idle\n\t// 6 -\trec_idle_req\n\t// 7 -\trec_ack_req\n\t// 8 -\trec_req_idle\n\t// 9 -\trec_idle_ack\n\t\n\t// clock for wire12\n\ty1 : [0..delay+1];\n\ty2 : [0..delay+1];\n\n\t// empty\n\t// do not need y1 and y2 to increase as always reset when this state is left\n\t// similarly can reset y1 and y2 when we re-enter this state\n\t[snd_req12]  w12=0 -> (w12'=1) & (y1'=0) & (y2'=0);\n\t[snd_ack12]  w12=0 -> (w12'=3) & (y1'=0) & (y2'=0);\n\t[snd_idle12] w12=0 -> (w12'=5) & (y1'=0) & (y2'=0);\n\t[time]       w12=0 -> (w12'=w12);\t\n\t// rec_req\n\t[snd_req12]  w12=1 -> (w12'=1);\n\t[rec_req12]  w12=1 -> (w12'=0) & (y1'=0) & (y2'=0);\n\t[snd_ack12]  w12=1 -> (w12'=2) & (y2'=0);\n\t[snd_idle12] w12=1 -> (w12'=8) & (y2'=0);\n\t[time]       w12=1 & y2<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t// rec_req_ack\n\t[snd_ack12] w12=2 -> (w12'=2);\n\t[rec_req12] w12=2 -> (w12'=3);\n\t[time]      w12=2 & y1<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t// rec_ack\n\t[snd_ack12]  w12=3 -> (w12'=3);\n\t[rec_ack12]  w12=3 -> (w12'=0) & (y1'=0) & (y2'=0);\n\t[snd_idle12] w12=3 -> (w12'=4) & (y2'=0);\n\t[snd_req12]  w12=3 -> (w12'=7) & (y2'=0);\n\t[time]       w12=3 & y2<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t// rec_ack_idle\n\t[snd_idle12] w12=4 -> (w12'=4);\n\t[rec_ack12]  w12=4 -> (w12'=5);\n\t[time]       w12=4 & y1<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t// rec_idle\n\t[snd_idle12] w12=5 -> (w12'=5);\n\t[rec_idle12] w12=5 -> (w12'=0) & (y1'=0) & (y2'=0);\n\t[snd_req12]  w12=5 -> (w12'=6) & (y2'=0);\n\t[snd_ack12]  w12=5 -> (w12'=9) & (y2'=0);\n\t[time]       w12=5 & y2<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t// rec_idle_req\n\t[snd_req12]  w12=6 -> (w12'=6);\n\t[rec_idle12] w12=6 -> (w12'=1);\n\t[time]       w12=6 & y1<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t// rec_ack_req\n\t[snd_req12] w12=7 -> (w12'=7);\n\t[rec_ack12] w12=7 -> (w12'=1);\n\t[time]      w12=7 & y1<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t// rec_req_idle\n\t[snd_idle12] w12=8 -> (w12'=8);\n\t[rec_req12]  w12=8 -> (w12'=5);\n\t[time]       w12=8 & y1<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t// rec_idle_ack\n\t[snd_ack12]  w12=9 -> (w12'=9);\n\t[rec_idle12] w12=9 -> (w12'=3);\n\t[time]       w12=9 & y1<delay ->  (y1'=min(y1+1,delay+1)) & (y2'=min(y2+1,delay+1));\n\t\nendmodule\n\nmodule node1\n\t\n\t// clock for node1\n\tx1 : [0..168];\n\t\n\t// local state\n\ts1 : [0..8];\n\t// 0 - root contention\n\t// 1 - rec_idle\n\t// 2 - rec_req_fast\n\t// 3 - rec_req_slow\n\t// 4 - rec_idle_fast\n\t// 5 - rec_idle_slow\n\t// 6 - snd_req\n\t// 7- almost_root\n\t// 8 - almost_child\n\t\n\t// added resets to x1 when not considered again until after rest\n\t// removed root and child (using almost root and almost child)\n\t\n\t// root contention immediate state)\n\t[snd_idle12] s1=0 -> fast : (s1'=2) & (x1'=0) +  slow : (s1'=3) & (x1'=0);\n\t[rec_idle21] s1=0 -> (s1'=1);\n\t// rec_idle immediate state)\n\t[snd_idle12] s1=1 -> fast : (s1'=4) & (x1'=0) +  slow : (s1'=5) & (x1'=0);\n\t[rec_req21]  s1=1 -> (s1'=0);\n\t// rec_req_fast\n\t[rec_idle21] s1=2 -> (s1'=4);\t\n\t[snd_ack12]  s1=2 & x1>=rc_fast_min -> (s1'=7) & (x1'=0);\n\t[time]       s1=2 & x1<rc_fast_max -> (x1'=min(x1+1,168));\n\t// rec_req_slow\n\t[rec_idle21] s1=3 -> (s1'=5);\n\t[snd_ack12]  s1=3 & x1>=rc_slow_min -> (s1'=7) & (x1'=0);\n\t[time]       s1=3 & x1<rc_slow_max -> (x1'=min(x1+1,168));\n\t// rec_idle_fast\n\t[rec_req21] s1=4 -> (s1'=2);\n\t[snd_req12] s1=4 & x1>=rc_fast_min -> (s1'=6) & (x1'=0);\n\t[time]      s1=4 & x1<rc_fast_max -> (x1'=min(x1+1,168));\n\t// rec_idle_slow\n\t[rec_req21] s1=5 -> (s1'=3);\n\t[snd_req12] s1=5 & x1>=rc_slow_min -> (s1'=6) & (x1'=0);\n\t[time]      s1=5 & x1<rc_slow_max -> (x1'=min(x1+1,168));\n\t// snd_req \n\t// do not use x1 until reset (in state 0 or in state 1) so do not need to increase x1\n\t// also can set x1 to 0 upon entering this state\n\t[rec_req21] s1=6 -> (s1'=0);\n\t[rec_ack21] s1=6 -> (s1'=8);\n\t[time]      s1=6 -> (s1'=s1);\n\t// almost root (immediate) \n\t// loop in final states to remove deadlock\n\t[] s1=7 & s2=8 -> (s1'=s1);\n\t[] s1=8 & s2=7 -> (s1'=s1);\n\t[time] s1=7 -> (s1'=s1);\n\t[time] s1=8 -> (s1'=s1);\n\t\nendmodule\n\n// construct remaining automata through renaming\nmodule wire21=wire12[w12=w21, y1=z1, y2=z2, \n\tsnd_req12=snd_req21, snd_idle12=snd_idle21, snd_ack12=snd_ack21,\n\trec_req12=rec_req21, rec_idle12=rec_idle21, rec_ack12=rec_ack21]\nendmodule\nmodule node2=node1[s1=s2, s2=s1, x1=x2, \n\trec_req21=rec_req12, rec_idle21=rec_idle12, rec_ack21=rec_ack12,\n\tsnd_req12=snd_req21, snd_idle12=snd_idle21, snd_ack12=snd_ack21]\nendmodule\n\n// reward structures\n// time\nrewards \"time\"\t\n\t[time] true : 1;\nendrewards\n// time nodes sending\nrewards \"time_sending\"\n\t[time] (w12>0 | w21>0) : 1;\nendrewards\n"
  },
  {
    "path": "prism-examples/mdps/firewire/impl/liveness.pctl",
    "content": "// liveness\r\nP>=1 [ F ((s1=8) & (s2=7)) | ((s1=7) & (s2=8)) ]\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 6 7 8 9 10 )\n  echo \"Generating for N=$N\"\n  prismpp .leaderN.nm.pp $N >! leader\"$N\".nm\n  unix2dos  leader\"$N\".nm\nend\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/.leaderN.nm.pp",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\n\n#const N#\nconst N= #N#; // number of processes\r\n\n//----------------------------------------------------------------------------------------------------------------------------\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..#N#-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p#N#1] (s1=1) & (receive1=0) & !( (p1=0) & (p#N#=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p#N#1] (s1=1) & (receive1=0) & (p1=0) & (p#N#=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c#N#1] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c#N#1] (s1=2) & (receive1=1) & (sent1=2) & (c#N#=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c#N#1] (s1=2) & (receive1=1) & (sent1=2) & (c#N#<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p#N#1] (s1=3) & (receive1=0) -> (p1'=p#N#) & (receive1'=1);\r\n\t// receive counter\r\n\t[c#N#1] (s1=3) & (receive1=1) & (c#N#<N-1) -> (c1'=c#N#+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// construct further stations through renaming\n#for i=2:N#\nmodule process#i#=process1[s1=s#i#,p1=p#i#,c1=c#i#,sent1=sent#i#,receive1=receive#i#,p12=p#i##mod(i,N)+1#,p#N#1=p#mod(i-2,N)+1##i#,c12=c#i##mod(i,N)+1#,c#N#1=c#mod(i-2,N)+1##i#,p#N#=p#mod(i-2,N)+1#,c#N#=c#mod(i-2,N)+1#] endmodule\r\n#end#\n\n//----------------------------------------------------------------------------------------------------------------------------\n\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\n\n//----------------------------------------------------------------------------------------------------------------------------\nformula leaders = #+ i=1:N#(s#i#=4?1:0)#end#;\nlabel \"elected\" = #| i=1:N#s#i#=4#end#;\n\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/README.txt",
    "content": "This case study is based on the asynchronous leader election protocol of Itai & Rodeh [IR90].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/asynchronous_leader.php\r\n\r\n=====================================================================================\r\n\r\n[IR90]\r\nA. Itai and M. Rodeh\r\nSymmetry Breaking in Distributed Networks\r\nIn Information and Computation, 88:60-97, 1990\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/auto",
    "content": "#!/bin/csh\n\nprism leader3.nm leader.pctl -const K=1 -m\nprism leader4.nm leader.pctl -const K=1 -m\nprism leader5.nm leader.pctl -const K=1 -m\n#prism leader6.nm leader.pctl -const K=1 -m\n#prism leader7.nm leader.pctl -const K=1 -m\n#prism leader8.nm leader.pctl -const K=1 -m\n#prism leader9.nm leader.pctl -const K=1 -m\n#prism leader10.nm leader.pctl -const K=1 -m\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader.pctl",
    "content": "// only one leader is elected\r\nfiter(forall, leaders<=1)\r\n\r\n// with probability 1 eventually a leader is elected\r\nP>=1 [ F \"elected\" ]\r\n\r\n// min/max probability leader is elected within K steps\r\nconst int K;\r\nPmin=? [ F<=K \"elected\" ]\r\nPmax=? [ F<=K \"elected\" ]\r\n\r\n// the min/max expected time to elect a leader\r\nRmin=? [ F \"elected\" ]\r\nRmax=? [ F \"elected\" ]\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader10.nm",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\r\n\r\nconst N= 10; // number of processes\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..10-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p101] (s1=1) & (receive1=0) & !( (p1=0) & (p10=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p101] (s1=1) & (receive1=0) & (p1=0) & (p10=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c101] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c101] (s1=2) & (receive1=1) & (sent1=2) & (c10=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c101] (s1=2) & (receive1=1) & (sent1=2) & (c10<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p101] (s1=3) & (receive1=0) -> (p1'=p10) & (receive1'=1);\r\n\t// receive counter\r\n\t[c101] (s1=3) & (receive1=1) & (c10<N-1) -> (c1'=c10+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule process2=process1[s1=s2,p1=p2,c1=c2,sent1=sent2,receive1=receive2,p12=p23,p101=p12,c12=c23,c101=c12,p10=p1,c10=c1] endmodule\r\nmodule process3=process1[s1=s3,p1=p3,c1=c3,sent1=sent3,receive1=receive3,p12=p34,p101=p23,c12=c34,c101=c23,p10=p2,c10=c2] endmodule\r\nmodule process4=process1[s1=s4,p1=p4,c1=c4,sent1=sent4,receive1=receive4,p12=p45,p101=p34,c12=c45,c101=c34,p10=p3,c10=c3] endmodule\r\nmodule process5=process1[s1=s5,p1=p5,c1=c5,sent1=sent5,receive1=receive5,p12=p56,p101=p45,c12=c56,c101=c45,p10=p4,c10=c4] endmodule\r\nmodule process6=process1[s1=s6,p1=p6,c1=c6,sent1=sent6,receive1=receive6,p12=p67,p101=p56,c12=c67,c101=c56,p10=p5,c10=c5] endmodule\r\nmodule process7=process1[s1=s7,p1=p7,c1=c7,sent1=sent7,receive1=receive7,p12=p78,p101=p67,c12=c78,c101=c67,p10=p6,c10=c6] endmodule\r\nmodule process8=process1[s1=s8,p1=p8,c1=c8,sent1=sent8,receive1=receive8,p12=p89,p101=p78,c12=c89,c101=c78,p10=p7,c10=c7] endmodule\r\nmodule process9=process1[s1=s9,p1=p9,c1=c9,sent1=sent9,receive1=receive9,p12=p910,p101=p89,c12=c910,c101=c89,p10=p8,c10=c8] endmodule\r\nmodule process10=process1[s1=s10,p1=p10,c1=c10,sent1=sent10,receive1=receive10,p12=p101,p101=p910,c12=c101,c101=c910,p10=p9,c10=c9] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nformula leaders = (s1=4?1:0)+(s2=4?1:0)+(s3=4?1:0)+(s4=4?1:0)+(s5=4?1:0)+(s6=4?1:0)+(s7=4?1:0)+(s8=4?1:0)+(s9=4?1:0)+(s10=4?1:0);\r\nlabel \"elected\" = s1=4|s2=4|s3=4|s4=4|s5=4|s6=4|s7=4|s8=4|s9=4|s10=4;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader3.nm",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\r\n\r\nconst N= 3; // number of processes\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..3-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p31] (s1=1) & (receive1=0) & !( (p1=0) & (p3=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p31] (s1=1) & (receive1=0) & (p1=0) & (p3=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c31] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c31] (s1=2) & (receive1=1) & (sent1=2) & (c3=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c31] (s1=2) & (receive1=1) & (sent1=2) & (c3<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p31] (s1=3) & (receive1=0) -> (p1'=p3) & (receive1'=1);\r\n\t// receive counter\r\n\t[c31] (s1=3) & (receive1=1) & (c3<N-1) -> (c1'=c3+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule process2=process1[s1=s2,p1=p2,c1=c2,sent1=sent2,receive1=receive2,p12=p23,p31=p12,c12=c23,c31=c12,p3=p1,c3=c1] endmodule\r\nmodule process3=process1[s1=s3,p1=p3,c1=c3,sent1=sent3,receive1=receive3,p12=p31,p31=p23,c12=c31,c31=c23,p3=p2,c3=c2] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nformula leaders = (s1=4?1:0)+(s2=4?1:0)+(s3=4?1:0);\r\nlabel \"elected\" = s1=4|s2=4|s3=4;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader4.nm",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\r\n\r\nconst N= 4; // number of processes\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..4-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p41] (s1=1) & (receive1=0) & !( (p1=0) & (p4=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p41] (s1=1) & (receive1=0) & (p1=0) & (p4=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c41] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c41] (s1=2) & (receive1=1) & (sent1=2) & (c4=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c41] (s1=2) & (receive1=1) & (sent1=2) & (c4<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p41] (s1=3) & (receive1=0) -> (p1'=p4) & (receive1'=1);\r\n\t// receive counter\r\n\t[c41] (s1=3) & (receive1=1) & (c4<N-1) -> (c1'=c4+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule process2=process1[s1=s2,p1=p2,c1=c2,sent1=sent2,receive1=receive2,p12=p23,p41=p12,c12=c23,c41=c12,p4=p1,c4=c1] endmodule\r\nmodule process3=process1[s1=s3,p1=p3,c1=c3,sent1=sent3,receive1=receive3,p12=p34,p41=p23,c12=c34,c41=c23,p4=p2,c4=c2] endmodule\r\nmodule process4=process1[s1=s4,p1=p4,c1=c4,sent1=sent4,receive1=receive4,p12=p41,p41=p34,c12=c41,c41=c34,p4=p3,c4=c3] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nformula leaders = (s1=4?1:0)+(s2=4?1:0)+(s3=4?1:0)+(s4=4?1:0);\r\nlabel \"elected\" = s1=4|s2=4|s3=4|s4=4;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader5.nm",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\r\n\r\nconst N= 5; // number of processes\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..5-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p51] (s1=1) & (receive1=0) & !( (p1=0) & (p5=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p51] (s1=1) & (receive1=0) & (p1=0) & (p5=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c51] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c51] (s1=2) & (receive1=1) & (sent1=2) & (c5=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c51] (s1=2) & (receive1=1) & (sent1=2) & (c5<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p51] (s1=3) & (receive1=0) -> (p1'=p5) & (receive1'=1);\r\n\t// receive counter\r\n\t[c51] (s1=3) & (receive1=1) & (c5<N-1) -> (c1'=c5+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule process2=process1[s1=s2,p1=p2,c1=c2,sent1=sent2,receive1=receive2,p12=p23,p51=p12,c12=c23,c51=c12,p5=p1,c5=c1] endmodule\r\nmodule process3=process1[s1=s3,p1=p3,c1=c3,sent1=sent3,receive1=receive3,p12=p34,p51=p23,c12=c34,c51=c23,p5=p2,c5=c2] endmodule\r\nmodule process4=process1[s1=s4,p1=p4,c1=c4,sent1=sent4,receive1=receive4,p12=p45,p51=p34,c12=c45,c51=c34,p5=p3,c5=c3] endmodule\r\nmodule process5=process1[s1=s5,p1=p5,c1=c5,sent1=sent5,receive1=receive5,p12=p51,p51=p45,c12=c51,c51=c45,p5=p4,c5=c4] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nformula leaders = (s1=4?1:0)+(s2=4?1:0)+(s3=4?1:0)+(s4=4?1:0)+(s5=4?1:0);\r\nlabel \"elected\" = s1=4|s2=4|s3=4|s4=4|s5=4;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader6.nm",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\r\n\r\nconst N= 6; // number of processes\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..6-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p61] (s1=1) & (receive1=0) & !( (p1=0) & (p6=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p61] (s1=1) & (receive1=0) & (p1=0) & (p6=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c61] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c61] (s1=2) & (receive1=1) & (sent1=2) & (c6=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c61] (s1=2) & (receive1=1) & (sent1=2) & (c6<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p61] (s1=3) & (receive1=0) -> (p1'=p6) & (receive1'=1);\r\n\t// receive counter\r\n\t[c61] (s1=3) & (receive1=1) & (c6<N-1) -> (c1'=c6+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule process2=process1[s1=s2,p1=p2,c1=c2,sent1=sent2,receive1=receive2,p12=p23,p61=p12,c12=c23,c61=c12,p6=p1,c6=c1] endmodule\r\nmodule process3=process1[s1=s3,p1=p3,c1=c3,sent1=sent3,receive1=receive3,p12=p34,p61=p23,c12=c34,c61=c23,p6=p2,c6=c2] endmodule\r\nmodule process4=process1[s1=s4,p1=p4,c1=c4,sent1=sent4,receive1=receive4,p12=p45,p61=p34,c12=c45,c61=c34,p6=p3,c6=c3] endmodule\r\nmodule process5=process1[s1=s5,p1=p5,c1=c5,sent1=sent5,receive1=receive5,p12=p56,p61=p45,c12=c56,c61=c45,p6=p4,c6=c4] endmodule\r\nmodule process6=process1[s1=s6,p1=p6,c1=c6,sent1=sent6,receive1=receive6,p12=p61,p61=p56,c12=c61,c61=c56,p6=p5,c6=c5] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nformula leaders = (s1=4?1:0)+(s2=4?1:0)+(s3=4?1:0)+(s4=4?1:0)+(s5=4?1:0)+(s6=4?1:0);\r\nlabel \"elected\" = s1=4|s2=4|s3=4|s4=4|s5=4|s6=4;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader7.nm",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\r\n\r\nconst N= 7; // number of processes\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..7-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p71] (s1=1) & (receive1=0) & !( (p1=0) & (p7=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p71] (s1=1) & (receive1=0) & (p1=0) & (p7=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c71] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c71] (s1=2) & (receive1=1) & (sent1=2) & (c7=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c71] (s1=2) & (receive1=1) & (sent1=2) & (c7<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p71] (s1=3) & (receive1=0) -> (p1'=p7) & (receive1'=1);\r\n\t// receive counter\r\n\t[c71] (s1=3) & (receive1=1) & (c7<N-1) -> (c1'=c7+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule process2=process1[s1=s2,p1=p2,c1=c2,sent1=sent2,receive1=receive2,p12=p23,p71=p12,c12=c23,c71=c12,p7=p1,c7=c1] endmodule\r\nmodule process3=process1[s1=s3,p1=p3,c1=c3,sent1=sent3,receive1=receive3,p12=p34,p71=p23,c12=c34,c71=c23,p7=p2,c7=c2] endmodule\r\nmodule process4=process1[s1=s4,p1=p4,c1=c4,sent1=sent4,receive1=receive4,p12=p45,p71=p34,c12=c45,c71=c34,p7=p3,c7=c3] endmodule\r\nmodule process5=process1[s1=s5,p1=p5,c1=c5,sent1=sent5,receive1=receive5,p12=p56,p71=p45,c12=c56,c71=c45,p7=p4,c7=c4] endmodule\r\nmodule process6=process1[s1=s6,p1=p6,c1=c6,sent1=sent6,receive1=receive6,p12=p67,p71=p56,c12=c67,c71=c56,p7=p5,c7=c5] endmodule\r\nmodule process7=process1[s1=s7,p1=p7,c1=c7,sent1=sent7,receive1=receive7,p12=p71,p71=p67,c12=c71,c71=c67,p7=p6,c7=c6] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nformula leaders = (s1=4?1:0)+(s2=4?1:0)+(s3=4?1:0)+(s4=4?1:0)+(s5=4?1:0)+(s6=4?1:0)+(s7=4?1:0);\r\nlabel \"elected\" = s1=4|s2=4|s3=4|s4=4|s5=4|s6=4|s7=4;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader8.nm",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\r\n\r\nconst N= 8; // number of processes\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..8-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p81] (s1=1) & (receive1=0) & !( (p1=0) & (p8=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p81] (s1=1) & (receive1=0) & (p1=0) & (p8=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c81] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c81] (s1=2) & (receive1=1) & (sent1=2) & (c8=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c81] (s1=2) & (receive1=1) & (sent1=2) & (c8<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p81] (s1=3) & (receive1=0) -> (p1'=p8) & (receive1'=1);\r\n\t// receive counter\r\n\t[c81] (s1=3) & (receive1=1) & (c8<N-1) -> (c1'=c8+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule process2=process1[s1=s2,p1=p2,c1=c2,sent1=sent2,receive1=receive2,p12=p23,p81=p12,c12=c23,c81=c12,p8=p1,c8=c1] endmodule\r\nmodule process3=process1[s1=s3,p1=p3,c1=c3,sent1=sent3,receive1=receive3,p12=p34,p81=p23,c12=c34,c81=c23,p8=p2,c8=c2] endmodule\r\nmodule process4=process1[s1=s4,p1=p4,c1=c4,sent1=sent4,receive1=receive4,p12=p45,p81=p34,c12=c45,c81=c34,p8=p3,c8=c3] endmodule\r\nmodule process5=process1[s1=s5,p1=p5,c1=c5,sent1=sent5,receive1=receive5,p12=p56,p81=p45,c12=c56,c81=c45,p8=p4,c8=c4] endmodule\r\nmodule process6=process1[s1=s6,p1=p6,c1=c6,sent1=sent6,receive1=receive6,p12=p67,p81=p56,c12=c67,c81=c56,p8=p5,c8=c5] endmodule\r\nmodule process7=process1[s1=s7,p1=p7,c1=c7,sent1=sent7,receive1=receive7,p12=p78,p81=p67,c12=c78,c81=c67,p8=p6,c8=c6] endmodule\r\nmodule process8=process1[s1=s8,p1=p8,c1=c8,sent1=sent8,receive1=receive8,p12=p81,p81=p78,c12=c81,c81=c78,p8=p7,c8=c7] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nformula leaders = (s1=4?1:0)+(s2=4?1:0)+(s3=4?1:0)+(s4=4?1:0)+(s5=4?1:0)+(s6=4?1:0)+(s7=4?1:0)+(s8=4?1:0);\r\nlabel \"elected\" = s1=4|s2=4|s3=4|s4=4|s5=4|s6=4|s7=4|s8=4;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/leader_async/leader9.nm",
    "content": "// asynchronous leader election\r\n// 4 processes\r\n// gxn/dxp 29/01/01\r\n\r\nmdp\r\n\r\nconst N= 9; // number of processes\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nmodule process1\r\n\t\r\n\t// COUNTER\r\n\tc1 : [0..9-1];\r\n\t\r\n\t// STATES\r\n\ts1 : [0..4];\r\n\t// 0  make choice\r\n\t// 1 have not received neighbours choice\r\n\t// 2 active\r\n\t// 3 inactive\r\n\t// 4 leader\r\n\t\r\n\t// PREFERENCE\r\n\tp1 : [0..1];\r\n\t\r\n\t// VARIABLES FOR SENDING AND RECEIVING\r\n\treceive1 : [0..2];\r\n\t// not received anything\r\n\t// received choice\r\n\t// received counter\r\n\tsent1 : [0..2];\r\n\t// not send anything\r\n\t// sent choice\r\n\t// sent counter\r\n\t\r\n\t// pick value\r\n\t[] (s1=0) -> 0.5 : (s1'=1) & (p1'=0) + 0.5 : (s1'=1) & (p1'=1);\r\n\t\r\n\t// send preference\r\n\t[p12] (s1=1) & (sent1=0) -> (sent1'=1);\r\n\t// receive preference\r\n\t// stay active\r\n\t[p91] (s1=1) & (receive1=0) & !( (p1=0) & (p9=1) ) -> (s1'=2) & (receive1'=1);\r\n\t// become inactive\r\n\t[p91] (s1=1) & (receive1=0) & (p1=0) & (p9=1) -> (s1'=3) & (receive1'=1);\r\n\t\r\n\t// send preference (can now reset preference)\r\n\t[p12] (s1=2) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (already sent preference)\r\n\t// not received counter yet\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=1) -> (sent1'=2);\r\n\t// received counter (pick again)\r\n\t[c12] (s1=2) & (sent1=1) & (receive1=2) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive counter and not sent yet (note in this case do not pass it on as will send own counter)\r\n\t[c91] (s1=2) & (receive1=1) & (sent1<2) -> (receive1'=2);\r\n\t// receive counter and sent counter\r\n\t// only active process (decide)\r\n\t[c91] (s1=2) & (receive1=1) & (sent1=2) & (c9=N-1) -> (s1'=4) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t// other active process (pick again)\r\n\t[c91] (s1=2) & (receive1=1) & (sent1=2) & (c9<N-1) -> (s1'=0) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// send preference (must have received preference) and can now reset\r\n\t[p12] (s1=3) & (receive1>0) & (sent1=0) -> (sent1'=1) & (p1'=0);\r\n\t// send counter (must have received counter first) and can now reset\r\n\t[c12] (s1=3) & (receive1=2) & (sent1=1) ->  (s1'=3) & (p1'=0) & (c1'=0) & (sent1'=0) & (receive1'=0);\r\n\t\r\n\t// receive preference\r\n\t[p91] (s1=3) & (receive1=0) -> (p1'=p9) & (receive1'=1);\r\n\t// receive counter\r\n\t[c91] (s1=3) & (receive1=1) & (c9<N-1) -> (c1'=c9+1) & (receive1'=2);\r\n\t\t\r\n\t// done\r\n\t[done] (s1=4) -> (s1'=s1);\r\n\t// add loop for processes who are inactive\r\n\t[done] (s1=3) -> (s1'=s1);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule process2=process1[s1=s2,p1=p2,c1=c2,sent1=sent2,receive1=receive2,p12=p23,p91=p12,c12=c23,c91=c12,p9=p1,c9=c1] endmodule\r\nmodule process3=process1[s1=s3,p1=p3,c1=c3,sent1=sent3,receive1=receive3,p12=p34,p91=p23,c12=c34,c91=c23,p9=p2,c9=c2] endmodule\r\nmodule process4=process1[s1=s4,p1=p4,c1=c4,sent1=sent4,receive1=receive4,p12=p45,p91=p34,c12=c45,c91=c34,p9=p3,c9=c3] endmodule\r\nmodule process5=process1[s1=s5,p1=p5,c1=c5,sent1=sent5,receive1=receive5,p12=p56,p91=p45,c12=c56,c91=c45,p9=p4,c9=c4] endmodule\r\nmodule process6=process1[s1=s6,p1=p6,c1=c6,sent1=sent6,receive1=receive6,p12=p67,p91=p56,c12=c67,c91=c56,p9=p5,c9=c5] endmodule\r\nmodule process7=process1[s1=s7,p1=p7,c1=c7,sent1=sent7,receive1=receive7,p12=p78,p91=p67,c12=c78,c91=c67,p9=p6,c9=c6] endmodule\r\nmodule process8=process1[s1=s8,p1=p8,c1=c8,sent1=sent8,receive1=receive8,p12=p89,p91=p78,c12=c89,c91=c78,p9=p7,c9=c7] endmodule\r\nmodule process9=process1[s1=s9,p1=p9,c1=c9,sent1=sent9,receive1=receive9,p12=p91,p91=p89,c12=c91,c91=c89,p9=p8,c9=c8] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward - expected number of rounds (equals the number of times a process receives a counter)\r\nrewards\r\n\t[c12] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\nformula leaders = (s1=4?1:0)+(s2=4?1:0)+(s3=4?1:0)+(s4=4?1:0)+(s5=4?1:0)+(s6=4?1:0)+(s7=4?1:0)+(s8=4?1:0)+(s9=4?1:0);\r\nlabel \"elected\" = s1=4|s2=4|s3=4|s4=4|s5=4|s6=4|s7=4|s8=4|s9=4;\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/mutual/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 8 10 )\n  echo \"Generating for N=$N\"\n  prismpp .mutualN.nm.pp $N >! mutual\"$N\".nm\n  unix2dos mutual\"$N\".nm\nend\n"
  },
  {
    "path": "prism-examples/mdps/mutual/.mutualN.nm.pp",
    "content": "#const N#\n// mutual exclusion [PZ82]\r\n// dxp/gxn 19/12/99\r\n\r\nmdp\r\n\r\n// atomic formula\n// none in low, high, tie\nformula none_lht = #& i=2:N#!(p#i#>=4&p#i#<=13)#end#;\n// some in admit\nformula some_a   = #| i=2:N#(p#i#>=14&p#i#<=15)#end#;\n// some in high, admit\nformula some_ha  = #| i=2:N#(p#i#>=4&p#i#<=5|p#i#>=10&p#i#<=15)#end#;\n// none in high, tie, admit\nformula none_hta = #& i=2:N#(p#i#>=0&p#i#<=3|p#i#>=7&p#i#<=8)#end#;\n// none in enter\nformula none_e   = #& i=2:N#!(p#i#>=2&p#i#<=3)#end#;\n\n\r\nmodule process1\r\n\r\n\tp1: [0..15];\r\n\t\r\n\t[] p1=0 -> (p1'=0);\r\n\t[] p1=0 -> (p1'=1);\r\n\t[] p1=1 -> (p1'=2);\r\n\t[] p1=2 &  (none_lht | some_a) -> (p1'=3);\r\n\t[] p1=2 & !(none_lht | some_a) -> (p1'=2);\r\n\t[] p1=3 -> (p1'=4);\r\n\t[] p1=3 -> (p1'=7);\r\n\t[] p1=4 &  some_ha -> (p1'=5);\r\n\t[] p1=4 & !some_ha -> (p1'=10);\r\n\t[] p1=5 -> (p1'=6);\r\n\t[] p1=6 &  some_ha -> (p1'=6);\r\n\t[] p1=6 & !some_ha -> (p1'=9);\r\n\t[] p1=7 &  none_hta -> (p1'=8);\r\n\t[] p1=7 & !none_hta -> (p1'=7);\r\n\t[] p1=8  -> (p1'=9);\r\n\t[] p1=9  -> 0.5 : (p1'=4) + 0.5 : (p1'=7);\r\n\t[] p1=10 -> (p1'=11);\r\n\t[] p1=11 &  none_lht -> (p1'=13);\r\n\t[] p1=11 & !none_lht -> (p1'=12);\r\n\t[] p1=12 -> (p1'=0);\r\n\t[] p1=13 -> (p1'=14);\r\n\t[] p1=14 &  none_e -> (p1'=15);\r\n\t[] p1=14 & !none_e -> (p1'=14);\r\n\t[] p1=15 -> (p1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\n\n#for i=2:N#\r\nmodule process#i# = process1 [ p1=p#i#, p#i#=p1 ] endmodule\n#end#\n\n// formulas/labels for properties\n\n// number of procs in critical section\nformula num_crit = #+ i=1:N#p#1#>9?1:0#end#;\n// some process is between 4 and 13\nlabel \"some_4_13\"  = #| i=1:N#(p#i#>=4&p#i#<=13)#end#;\n// some process is in 14\nlabel \"some_14\"    = #| i=1:N#(p#i#=14)#end#;\n\n\n"
  },
  {
    "path": "prism-examples/mdps/mutual/README.txt",
    "content": "This case study is based on Pnueli and Zuck's [PZ86] probabilistic symmetric solution to the n-process mutual exclusion problem.\r\n\r\nFor reference, these are the local states of each process:\r\n\r\nNo:\tNo:\tDescription:\t\t\tState:\r\n--------------------------------------------------------------\r\n0\t0\tidle\t\t\t\tuninterested\r\n1\t1\ttrying\t\t\t\tuninterested\r\n2\t2\ttrying\t\t\t\tenter \r\n3\t3\ttrying\t\t\t\tenter \r\n4\t7\ttrying\t\t\t\thigh\r\n5\t8\ttrying\t\t\t\thigh\r\n6\t9\ttrying\t\t\t\ttie\r\n7\t10\ttrying\t\t\t\tlow\r\n8\t11\ttrying\t\t\t\tlow\r\n9\t12\ttrying\t\t\t\ttie\r\n10\t13\tin critical section\t\thigh\r\n11\t14\tin critical section\t\thigh\r\n12\t15\tin critical section\t\thigh\r\n13\t17\tin critical section\t\thigh\r\n14\t18\tleaving\tcritical section\tadmit\r\n15\t19\tleaving\tcritical section\tadmit\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/mutual.php\r\n\r\n=====================================================================================\r\n\r\n[PZ86]\r\nA. Pnueli and L. Zuck\r\nVerification of Multiprocess Probabilistic Protocols\r\nDistributed Computing, 1(1):53-72, 1986\r\n"
  },
  {
    "path": "prism-examples/mdps/mutual/auto",
    "content": "#!/bin/csh\n\nprism mutual3.nm mutual.pctl -fair\nprism mutual4.nm mutual.pctl -fair\nprism mutual5.nm mutual.pctl -fair\nprism mutual8.nm mutual.pctl -fair\nprism mutual10.nm mutual.pctl -fair\n"
  },
  {
    "path": "prism-examples/mdps/mutual/mutual.pctl",
    "content": "// Theorem 1 (mutual exclusion)\n\nfilter(forall, num_crit <= 1)\n\n// Lemma C\n// If the crical section is occupied then eventually it becomes clear\n\nfilter(forall, num_crit > 0 => P>=1 [ F num_crit = 0 ])\n\n// Lemma D\n// If a process is between 4 and 13 (in our version) then eventually some process gets to 14\n\nfilter(forall, \"some_4_13\" => P>=1 [ F \"some_14\" ])\n\n// Theorem 2 (liveness)\n// If process 1 tries then eventually it enters the critical section\n\nfilter(forall, p1=1 => P>=1 [ F p1=10 ])\n"
  },
  {
    "path": "prism-examples/mdps/mutual/mutual10.nm",
    "content": "// mutual exclusion [PZ82]\r\n// dxp/gxn 19/12/99\r\n\r\nmdp\r\n\r\n// atomic formula\r\n// none in low, high, tie\r\nformula none_lht = !(p2>=4&p2<=13)&!(p3>=4&p3<=13)&!(p4>=4&p4<=13)&!(p5>=4&p5<=13)&!(p6>=4&p6<=13)&!(p7>=4&p7<=13)&!(p8>=4&p8<=13)&!(p9>=4&p9<=13)&!(p10>=4&p10<=13);\r\n// some in admit\r\nformula some_a   = (p2>=14&p2<=15)|(p3>=14&p3<=15)|(p4>=14&p4<=15)|(p5>=14&p5<=15)|(p6>=14&p6<=15)|(p7>=14&p7<=15)|(p8>=14&p8<=15)|(p9>=14&p9<=15)|(p10>=14&p10<=15);\r\n// some in high, admit\r\nformula some_ha  = (p2>=4&p2<=5|p2>=10&p2<=15)|(p3>=4&p3<=5|p3>=10&p3<=15)|(p4>=4&p4<=5|p4>=10&p4<=15)|(p5>=4&p5<=5|p5>=10&p5<=15)|(p6>=4&p6<=5|p6>=10&p6<=15)|(p7>=4&p7<=5|p7>=10&p7<=15)|(p8>=4&p8<=5|p8>=10&p8<=15)|(p9>=4&p9<=5|p9>=10&p9<=15)|(p10>=4&p10<=5|p10>=10&p10<=15);\r\n// none in high, tie, admit\r\nformula none_hta = (p2>=0&p2<=3|p2>=7&p2<=8)&(p3>=0&p3<=3|p3>=7&p3<=8)&(p4>=0&p4<=3|p4>=7&p4<=8)&(p5>=0&p5<=3|p5>=7&p5<=8)&(p6>=0&p6<=3|p6>=7&p6<=8)&(p7>=0&p7<=3|p7>=7&p7<=8)&(p8>=0&p8<=3|p8>=7&p8<=8)&(p9>=0&p9<=3|p9>=7&p9<=8)&(p10>=0&p10<=3|p10>=7&p10<=8);\r\n// none in enter\r\nformula none_e   = !(p2>=2&p2<=3)&!(p3>=2&p3<=3)&!(p4>=2&p4<=3)&!(p5>=2&p5<=3)&!(p6>=2&p6<=3)&!(p7>=2&p7<=3)&!(p8>=2&p8<=3)&!(p9>=2&p9<=3)&!(p10>=2&p10<=3);\r\n\r\n\r\nmodule process1\r\n\r\n\tp1: [0..15];\r\n\t\r\n\t[] p1=0 -> (p1'=0);\r\n\t[] p1=0 -> (p1'=1);\r\n\t[] p1=1 -> (p1'=2);\r\n\t[] p1=2 &  (none_lht | some_a) -> (p1'=3);\r\n\t[] p1=2 & !(none_lht | some_a) -> (p1'=2);\r\n\t[] p1=3 -> (p1'=4);\r\n\t[] p1=3 -> (p1'=7);\r\n\t[] p1=4 &  some_ha -> (p1'=5);\r\n\t[] p1=4 & !some_ha -> (p1'=10);\r\n\t[] p1=5 -> (p1'=6);\r\n\t[] p1=6 &  some_ha -> (p1'=6);\r\n\t[] p1=6 & !some_ha -> (p1'=9);\r\n\t[] p1=7 &  none_hta -> (p1'=8);\r\n\t[] p1=7 & !none_hta -> (p1'=7);\r\n\t[] p1=8  -> (p1'=9);\r\n\t[] p1=9  -> 0.5 : (p1'=4) + 0.5 : (p1'=7);\r\n\t[] p1=10 -> (p1'=11);\r\n\t[] p1=11 &  none_lht -> (p1'=13);\r\n\t[] p1=11 & !none_lht -> (p1'=12);\r\n\t[] p1=12 -> (p1'=0);\r\n\t[] p1=13 -> (p1'=14);\r\n\t[] p1=14 &  none_e -> (p1'=15);\r\n\t[] p1=14 & !none_e -> (p1'=14);\r\n\t[] p1=15 -> (p1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\n\r\nmodule process2 = process1 [ p1=p2, p2=p1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p3=p1 ] endmodule\r\nmodule process4 = process1 [ p1=p4, p4=p1 ] endmodule\r\nmodule process5 = process1 [ p1=p5, p5=p1 ] endmodule\r\nmodule process6 = process1 [ p1=p6, p6=p1 ] endmodule\r\nmodule process7 = process1 [ p1=p7, p7=p1 ] endmodule\r\nmodule process8 = process1 [ p1=p8, p8=p1 ] endmodule\r\nmodule process9 = process1 [ p1=p9, p9=p1 ] endmodule\r\nmodule process10 = process1 [ p1=p10, p10=p1 ] endmodule\r\n\r\n// formulas/labels for properties\r\n\r\n// number of procs in critical section\r\nformula num_crit = p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0;\r\n// some process is between 4 and 13\r\nlabel \"some_4_13\"  = (p1>=4&p1<=13)|(p2>=4&p2<=13)|(p3>=4&p3<=13)|(p4>=4&p4<=13)|(p5>=4&p5<=13)|(p6>=4&p6<=13)|(p7>=4&p7<=13)|(p8>=4&p8<=13)|(p9>=4&p9<=13)|(p10>=4&p10<=13);\r\n// some process is in 14\r\nlabel \"some_14\"    = (p1=14)|(p2=14)|(p3=14)|(p4=14)|(p5=14)|(p6=14)|(p7=14)|(p8=14)|(p9=14)|(p10=14);\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/mutual/mutual3.nm",
    "content": "// mutual exclusion [PZ82]\r\n// dxp/gxn 19/12/99\r\n\r\nmdp\r\n\r\n// atomic formula\r\n// none in low, high, tie\r\nformula none_lht = !(p2>=4&p2<=13)&!(p3>=4&p3<=13);\r\n// some in admit\r\nformula some_a   = (p2>=14&p2<=15)|(p3>=14&p3<=15);\r\n// some in high, admit\r\nformula some_ha  = (p2>=4&p2<=5|p2>=10&p2<=15)|(p3>=4&p3<=5|p3>=10&p3<=15);\r\n// none in high, tie, admit\r\nformula none_hta = (p2>=0&p2<=3|p2>=7&p2<=8)&(p3>=0&p3<=3|p3>=7&p3<=8);\r\n// none in enter\r\nformula none_e   = !(p2>=2&p2<=3)&!(p3>=2&p3<=3);\r\n\r\n\r\nmodule process1\r\n\r\n\tp1: [0..15];\r\n\t\r\n\t[] p1=0 -> (p1'=0);\r\n\t[] p1=0 -> (p1'=1);\r\n\t[] p1=1 -> (p1'=2);\r\n\t[] p1=2 &  (none_lht | some_a) -> (p1'=3);\r\n\t[] p1=2 & !(none_lht | some_a) -> (p1'=2);\r\n\t[] p1=3 -> (p1'=4);\r\n\t[] p1=3 -> (p1'=7);\r\n\t[] p1=4 &  some_ha -> (p1'=5);\r\n\t[] p1=4 & !some_ha -> (p1'=10);\r\n\t[] p1=5 -> (p1'=6);\r\n\t[] p1=6 &  some_ha -> (p1'=6);\r\n\t[] p1=6 & !some_ha -> (p1'=9);\r\n\t[] p1=7 &  none_hta -> (p1'=8);\r\n\t[] p1=7 & !none_hta -> (p1'=7);\r\n\t[] p1=8  -> (p1'=9);\r\n\t[] p1=9  -> 0.5 : (p1'=4) + 0.5 : (p1'=7);\r\n\t[] p1=10 -> (p1'=11);\r\n\t[] p1=11 &  none_lht -> (p1'=13);\r\n\t[] p1=11 & !none_lht -> (p1'=12);\r\n\t[] p1=12 -> (p1'=0);\r\n\t[] p1=13 -> (p1'=14);\r\n\t[] p1=14 &  none_e -> (p1'=15);\r\n\t[] p1=14 & !none_e -> (p1'=14);\r\n\t[] p1=15 -> (p1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\n\r\nmodule process2 = process1 [ p1=p2, p2=p1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p3=p1 ] endmodule\r\n\r\n// formulas/labels for properties\r\n\r\n// number of procs in critical section\r\nformula num_crit = p1>9?1:0+p1>9?1:0+p1>9?1:0;\r\n// some process is between 4 and 13\r\nlabel \"some_4_13\"  = (p1>=4&p1<=13)|(p2>=4&p2<=13)|(p3>=4&p3<=13);\r\n// some process is in 14\r\nlabel \"some_14\"    = (p1=14)|(p2=14)|(p3=14);\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/mutual/mutual4.nm",
    "content": "// mutual exclusion [PZ82]\r\n// dxp/gxn 19/12/99\r\n\r\nmdp\r\n\r\n// atomic formula\r\n// none in low, high, tie\r\nformula none_lht = !(p2>=4&p2<=13)&!(p3>=4&p3<=13)&!(p4>=4&p4<=13);\r\n// some in admit\r\nformula some_a   = (p2>=14&p2<=15)|(p3>=14&p3<=15)|(p4>=14&p4<=15);\r\n// some in high, admit\r\nformula some_ha  = (p2>=4&p2<=5|p2>=10&p2<=15)|(p3>=4&p3<=5|p3>=10&p3<=15)|(p4>=4&p4<=5|p4>=10&p4<=15);\r\n// none in high, tie, admit\r\nformula none_hta = (p2>=0&p2<=3|p2>=7&p2<=8)&(p3>=0&p3<=3|p3>=7&p3<=8)&(p4>=0&p4<=3|p4>=7&p4<=8);\r\n// none in enter\r\nformula none_e   = !(p2>=2&p2<=3)&!(p3>=2&p3<=3)&!(p4>=2&p4<=3);\r\n\r\n\r\nmodule process1\r\n\r\n\tp1: [0..15];\r\n\t\r\n\t[] p1=0 -> (p1'=0);\r\n\t[] p1=0 -> (p1'=1);\r\n\t[] p1=1 -> (p1'=2);\r\n\t[] p1=2 &  (none_lht | some_a) -> (p1'=3);\r\n\t[] p1=2 & !(none_lht | some_a) -> (p1'=2);\r\n\t[] p1=3 -> (p1'=4);\r\n\t[] p1=3 -> (p1'=7);\r\n\t[] p1=4 &  some_ha -> (p1'=5);\r\n\t[] p1=4 & !some_ha -> (p1'=10);\r\n\t[] p1=5 -> (p1'=6);\r\n\t[] p1=6 &  some_ha -> (p1'=6);\r\n\t[] p1=6 & !some_ha -> (p1'=9);\r\n\t[] p1=7 &  none_hta -> (p1'=8);\r\n\t[] p1=7 & !none_hta -> (p1'=7);\r\n\t[] p1=8  -> (p1'=9);\r\n\t[] p1=9  -> 0.5 : (p1'=4) + 0.5 : (p1'=7);\r\n\t[] p1=10 -> (p1'=11);\r\n\t[] p1=11 &  none_lht -> (p1'=13);\r\n\t[] p1=11 & !none_lht -> (p1'=12);\r\n\t[] p1=12 -> (p1'=0);\r\n\t[] p1=13 -> (p1'=14);\r\n\t[] p1=14 &  none_e -> (p1'=15);\r\n\t[] p1=14 & !none_e -> (p1'=14);\r\n\t[] p1=15 -> (p1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\n\r\nmodule process2 = process1 [ p1=p2, p2=p1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p3=p1 ] endmodule\r\nmodule process4 = process1 [ p1=p4, p4=p1 ] endmodule\r\n\r\n// formulas/labels for properties\r\n\r\n// number of procs in critical section\r\nformula num_crit = p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0;\r\n// some process is between 4 and 13\r\nlabel \"some_4_13\"  = (p1>=4&p1<=13)|(p2>=4&p2<=13)|(p3>=4&p3<=13)|(p4>=4&p4<=13);\r\n// some process is in 14\r\nlabel \"some_14\"    = (p1=14)|(p2=14)|(p3=14)|(p4=14);\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/mutual/mutual5.nm",
    "content": "// mutual exclusion [PZ82]\r\n// dxp/gxn 19/12/99\r\n\r\nmdp\r\n\r\n// atomic formula\r\n// none in low, high, tie\r\nformula none_lht = !(p2>=4&p2<=13)&!(p3>=4&p3<=13)&!(p4>=4&p4<=13)&!(p5>=4&p5<=13);\r\n// some in admit\r\nformula some_a   = (p2>=14&p2<=15)|(p3>=14&p3<=15)|(p4>=14&p4<=15)|(p5>=14&p5<=15);\r\n// some in high, admit\r\nformula some_ha  = (p2>=4&p2<=5|p2>=10&p2<=15)|(p3>=4&p3<=5|p3>=10&p3<=15)|(p4>=4&p4<=5|p4>=10&p4<=15)|(p5>=4&p5<=5|p5>=10&p5<=15);\r\n// none in high, tie, admit\r\nformula none_hta = (p2>=0&p2<=3|p2>=7&p2<=8)&(p3>=0&p3<=3|p3>=7&p3<=8)&(p4>=0&p4<=3|p4>=7&p4<=8)&(p5>=0&p5<=3|p5>=7&p5<=8);\r\n// none in enter\r\nformula none_e   = !(p2>=2&p2<=3)&!(p3>=2&p3<=3)&!(p4>=2&p4<=3)&!(p5>=2&p5<=3);\r\n\r\n\r\nmodule process1\r\n\r\n\tp1: [0..15];\r\n\t\r\n\t[] p1=0 -> (p1'=0);\r\n\t[] p1=0 -> (p1'=1);\r\n\t[] p1=1 -> (p1'=2);\r\n\t[] p1=2 &  (none_lht | some_a) -> (p1'=3);\r\n\t[] p1=2 & !(none_lht | some_a) -> (p1'=2);\r\n\t[] p1=3 -> (p1'=4);\r\n\t[] p1=3 -> (p1'=7);\r\n\t[] p1=4 &  some_ha -> (p1'=5);\r\n\t[] p1=4 & !some_ha -> (p1'=10);\r\n\t[] p1=5 -> (p1'=6);\r\n\t[] p1=6 &  some_ha -> (p1'=6);\r\n\t[] p1=6 & !some_ha -> (p1'=9);\r\n\t[] p1=7 &  none_hta -> (p1'=8);\r\n\t[] p1=7 & !none_hta -> (p1'=7);\r\n\t[] p1=8  -> (p1'=9);\r\n\t[] p1=9  -> 0.5 : (p1'=4) + 0.5 : (p1'=7);\r\n\t[] p1=10 -> (p1'=11);\r\n\t[] p1=11 &  none_lht -> (p1'=13);\r\n\t[] p1=11 & !none_lht -> (p1'=12);\r\n\t[] p1=12 -> (p1'=0);\r\n\t[] p1=13 -> (p1'=14);\r\n\t[] p1=14 &  none_e -> (p1'=15);\r\n\t[] p1=14 & !none_e -> (p1'=14);\r\n\t[] p1=15 -> (p1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\n\r\nmodule process2 = process1 [ p1=p2, p2=p1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p3=p1 ] endmodule\r\nmodule process4 = process1 [ p1=p4, p4=p1 ] endmodule\r\nmodule process5 = process1 [ p1=p5, p5=p1 ] endmodule\r\n\r\n// formulas/labels for properties\r\n\r\n// number of procs in critical section\r\nformula num_crit = p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0;\r\n// some process is between 4 and 13\r\nlabel \"some_4_13\"  = (p1>=4&p1<=13)|(p2>=4&p2<=13)|(p3>=4&p3<=13)|(p4>=4&p4<=13)|(p5>=4&p5<=13);\r\n// some process is in 14\r\nlabel \"some_14\"    = (p1=14)|(p2=14)|(p3=14)|(p4=14)|(p5=14);\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/mutual/mutual8.nm",
    "content": "// mutual exclusion [PZ82]\r\n// dxp/gxn 19/12/99\r\n\r\nmdp\r\n\r\n// atomic formula\r\n// none in low, high, tie\r\nformula none_lht = !(p2>=4&p2<=13)&!(p3>=4&p3<=13)&!(p4>=4&p4<=13)&!(p5>=4&p5<=13)&!(p6>=4&p6<=13)&!(p7>=4&p7<=13)&!(p8>=4&p8<=13);\r\n// some in admit\r\nformula some_a   = (p2>=14&p2<=15)|(p3>=14&p3<=15)|(p4>=14&p4<=15)|(p5>=14&p5<=15)|(p6>=14&p6<=15)|(p7>=14&p7<=15)|(p8>=14&p8<=15);\r\n// some in high, admit\r\nformula some_ha  = (p2>=4&p2<=5|p2>=10&p2<=15)|(p3>=4&p3<=5|p3>=10&p3<=15)|(p4>=4&p4<=5|p4>=10&p4<=15)|(p5>=4&p5<=5|p5>=10&p5<=15)|(p6>=4&p6<=5|p6>=10&p6<=15)|(p7>=4&p7<=5|p7>=10&p7<=15)|(p8>=4&p8<=5|p8>=10&p8<=15);\r\n// none in high, tie, admit\r\nformula none_hta = (p2>=0&p2<=3|p2>=7&p2<=8)&(p3>=0&p3<=3|p3>=7&p3<=8)&(p4>=0&p4<=3|p4>=7&p4<=8)&(p5>=0&p5<=3|p5>=7&p5<=8)&(p6>=0&p6<=3|p6>=7&p6<=8)&(p7>=0&p7<=3|p7>=7&p7<=8)&(p8>=0&p8<=3|p8>=7&p8<=8);\r\n// none in enter\r\nformula none_e   = !(p2>=2&p2<=3)&!(p3>=2&p3<=3)&!(p4>=2&p4<=3)&!(p5>=2&p5<=3)&!(p6>=2&p6<=3)&!(p7>=2&p7<=3)&!(p8>=2&p8<=3);\r\n\r\n\r\nmodule process1\r\n\r\n\tp1: [0..15];\r\n\t\r\n\t[] p1=0 -> (p1'=0);\r\n\t[] p1=0 -> (p1'=1);\r\n\t[] p1=1 -> (p1'=2);\r\n\t[] p1=2 &  (none_lht | some_a) -> (p1'=3);\r\n\t[] p1=2 & !(none_lht | some_a) -> (p1'=2);\r\n\t[] p1=3 -> (p1'=4);\r\n\t[] p1=3 -> (p1'=7);\r\n\t[] p1=4 &  some_ha -> (p1'=5);\r\n\t[] p1=4 & !some_ha -> (p1'=10);\r\n\t[] p1=5 -> (p1'=6);\r\n\t[] p1=6 &  some_ha -> (p1'=6);\r\n\t[] p1=6 & !some_ha -> (p1'=9);\r\n\t[] p1=7 &  none_hta -> (p1'=8);\r\n\t[] p1=7 & !none_hta -> (p1'=7);\r\n\t[] p1=8  -> (p1'=9);\r\n\t[] p1=9  -> 0.5 : (p1'=4) + 0.5 : (p1'=7);\r\n\t[] p1=10 -> (p1'=11);\r\n\t[] p1=11 &  none_lht -> (p1'=13);\r\n\t[] p1=11 & !none_lht -> (p1'=12);\r\n\t[] p1=12 -> (p1'=0);\r\n\t[] p1=13 -> (p1'=14);\r\n\t[] p1=14 &  none_e -> (p1'=15);\r\n\t[] p1=14 & !none_e -> (p1'=14);\r\n\t[] p1=15 -> (p1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\n\r\nmodule process2 = process1 [ p1=p2, p2=p1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p3=p1 ] endmodule\r\nmodule process4 = process1 [ p1=p4, p4=p1 ] endmodule\r\nmodule process5 = process1 [ p1=p5, p5=p1 ] endmodule\r\nmodule process6 = process1 [ p1=p6, p6=p1 ] endmodule\r\nmodule process7 = process1 [ p1=p7, p7=p1 ] endmodule\r\nmodule process8 = process1 [ p1=p8, p8=p1 ] endmodule\r\n\r\n// formulas/labels for properties\r\n\r\n// number of procs in critical section\r\nformula num_crit = p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0+p1>9?1:0;\r\n// some process is between 4 and 13\r\nlabel \"some_4_13\"  = (p1>=4&p1<=13)|(p2>=4&p2<=13)|(p3>=4&p3<=13)|(p4>=4&p4<=13)|(p5>=4&p5<=13)|(p6>=4&p6<=13)|(p7>=4&p7<=13)|(p8>=4&p8<=13);\r\n// some process is in 14\r\nlabel \"some_14\"    = (p1=14)|(p2=14)|(p3=14)|(p4=14)|(p5=14)|(p6=14)|(p7=14)|(p8=14);\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 6 7 8 9 10 )\n  echo \"Generating for N=$N\"\n  prismpp .phil-nofairN.nm.pp $N >! phil-nofair\"$N\".nm\n  unix2dos phil-nofair\"$N\".nm\nend\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/.phil-nofairN.nm.pp",
    "content": "#const N#\r\n// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p#N#>=0&p#N#<=3)|p#N#=5|p#N#=7|p#N#=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\n#for i=2:N#\r\nmodule phil#i# = phil1 [ p1=p#i#, p2=p#mod(i,N)+1#, p#N#=p#mod(i-2,N)+1# ] endmodule\r\n#end#\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = #| i=1:N#((p#i#>0)&(p#i#<8))#end#;\r\nlabel \"eat\" = #| i=1:N#((p#i#>=8)&(p#i#<=9))#end#;\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/README.txt",
    "content": "This case study is based on Lehmann and Rabin's solution to the well known dining philosophers problem [LR81].\r\nIt considers the version presented in [DFP04] which removes the need to consider 'fairness' assumptions on the scheduling mechanism.\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/phil.php\r\n\r\n=====================================================================================\r\n\r\n[LR81]\r\nD. Lehmann and M. Rabin\r\nOn the Advantages of Free Choice: A Symmetric Fully Distributed Solution to the Dining Philosophers Problem (Extended Abstract)\r\nIn Proc. 8th Symposium on Principles of Programming Languages, pp. 133-138, 1981\r\n\r\n[DFP04]\r\nM. Duflot, L. Fribourg and C. Picaronny\r\nRandomized dining philosophers without fairness assumption\r\nDistributed Computing, 17(1):65-76, 2004\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/auto",
    "content": "#!/bin/csh\n\nprism phil-nofair3.nm  phil.pctl -const K=1 -m\nprism phil-nofair4.nm  phil.pctl -const K=1 -m\n#prism phil-nofair5.nm  phil.pctl -const K=1 -m\n#prism phil-nofair6.nm  phil.pctl -const K=1 -m\n#prism phil-nofair7.nm  phil.pctl -const K=1 -m\n#prism phil-nofair8.nm  phil.pctl -const K=1 -m\n#prism phil-nofair9.nm  phil.pctl -const K=1 -m\n#prism phil-nofair10.nm phil.pctl -const K=1 -m\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil-nofair10.nm",
    "content": "// randomized dining philosophers [LR81]\n// dxp/gxn 23/01/02\n\n// model which does not require fairness\n// remove the possibility of loops:\n// (1) cannot stay in thinking \n// (2) if first fork not free then cannot move (another philosopher must more)\n\nmdp\n\n// atomic formulae \n// left fork free and right fork free resp.\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\nformula rfree = (p10>=0&p10<=3)|p10=5|p10=7|p10=11;\n\nmodule phil1\n\n\tp1: [0..11];\n\n\t[] p1=0 -> (p1'=1); // trying\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\n\t[] p1=6  -> (p1'=1); // put down left\n\t[] p1=7  -> (p1'=1); // put down right\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \n\t[] p1=9  -> (p1'=11); // finished eating and put down right\n\t[] p1=10 -> (p1'=0); // put down right and return to think\n\t[] p1=11 -> (p1'=0); // put down left and return to think\n\nendmodule\n\n// construct further modules through renaming\nmodule phil2 = phil1 [ p1=p2, p2=p3, p10=p1 ] endmodule\nmodule phil3 = phil1 [ p1=p3, p2=p4, p10=p2 ] endmodule\nmodule phil4 = phil1 [ p1=p4, p2=p5, p10=p3 ] endmodule\nmodule phil5 = phil1 [ p1=p5, p2=p6, p10=p4 ] endmodule\nmodule phil6 = phil1 [ p1=p6, p2=p7, p10=p5 ] endmodule\nmodule phil7 = phil1 [ p1=p7, p2=p8, p10=p6 ] endmodule\nmodule phil8 = phil1 [ p1=p8, p2=p9, p10=p7 ] endmodule\nmodule phil9 = phil1 [ p1=p9, p2=p10, p10=p8 ] endmodule\nmodule phil10 = phil1 [ p1=p10, p2=p1, p10=p9 ] endmodule\n\n// rewards (number of steps)\nrewards \"num_steps\"\n\t[] true : 1;\nendrewards\n// labels\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8))|((p9>0)&(p9<8))|((p10>0)&(p10<8));\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9))|((p9>=8)&(p9<=9))|((p10>=8)&(p10<=9));\n\n\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil-nofair3.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p3>=0&p3<=3)|p3=5|p3=7|p3=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p3=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p1, p3=p2 ] endmodule\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9));\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil-nofair4.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p4>=0&p4<=3)|p4=5|p4=7|p4=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p4=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p4=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p1, p4=p3 ] endmodule\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9));\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil-nofair5.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p5>=0&p5<=3)|p5=5|p5=7|p5=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p5=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p5=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p5=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p1, p5=p4 ] endmodule\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9));\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil-nofair6.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p6>=0&p6<=3)|p6=5|p6=7|p6=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p6=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p6=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p6=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p6=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p1, p6=p5 ] endmodule\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9));\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil-nofair7.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p7>=0&p7<=3)|p7=5|p7=7|p7=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p7=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p7=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p7=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p7=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p7=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p1, p7=p6 ] endmodule\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9));\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil-nofair8.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p8>=0&p8<=3)|p8=5|p8=7|p8=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p8=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p8=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p8=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p8=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p8=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p8, p8=p6 ] endmodule\r\nmodule phil8 = phil1 [ p1=p8, p2=p1, p8=p7 ] endmodule\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9));\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil-nofair9.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p9>=0&p9<=3)|p9=5|p9=7|p9=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p9=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p9=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p9=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p9=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p9=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p8, p9=p6 ] endmodule\r\nmodule phil8 = phil1 [ p1=p8, p2=p9, p9=p7 ] endmodule\r\nmodule phil9 = phil1 [ p1=p9, p2=p1, p9=p8 ] endmodule\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8))|((p9>0)&(p9<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9))|((p9>=8)&(p9<=9));\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/nofair/phil.pctl",
    "content": "const int K;\n\n// Liveness (if a philosopher is hungry then eventually some philosopher eats)\n\nfilter(forall, \"hungry\" => P>=1 [ F \"eat\"])\n\n\n// Bounded until (minimum probability, from a state where someone\n// is hungry, that a philosopher will eat within K steps)\n\nPmin=? [ F<=K \"eat\" {\"hungry\"}{min} ]\n\n\n// Expected time (from a state where someone is hungry, the maximum\n// expected number of steps until a philosopher eats)\n\nR{\"num_steps\"}max=? [ F \"eat\" {\"hungry\"}{max} ]\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 6 7 8 9 10 15 20 25 30 )\n  echo \"Generating for N=$N\"\n  prismpp .philN.nm.pp $N >! phil\"$N\".nm\n  unix2dos phil\"$N\".nm\nend\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/.philN.nm.pp",
    "content": "#const N#\n// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\nformula rfree = (p#N#>=0&p#N#<=3)|p#N#=5|p#N#=7|p#N#=11;\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\n#for i=2:N#\r\nmodule phil#i# = phil1 [ p1=p#i#, p2=p#mod(i,N)+1#, p#N#=p#mod(i-2,N)+1# ] endmodule\r\n#end#\n\n// labels\nlabel \"hungry\" = #| i=1:N#((p#i#>0)&(p#i#<8))#end#;\r\nlabel \"eat\" = #| i=1:N#((p#i#>=8)&(p#i#<=9))#end#;\r\n\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/README.txt",
    "content": "This case study is based on Lehmann and Rabin's solution to the well known dining philosophers problem [LR81].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/phil.php\r\n\r\n=====================================================================================\r\n\r\n[LR81]\r\nD. Lehmann and M. Rabin\r\nOn the Advantages of Free Choice: A Symmetric Fully Distributed Solution to the Dining Philosophers Problem (Extended Abstract)\r\nIn Proc. 8th Symposium on Principles of Programming Languages, pp. 133-138, 1981\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/auto",
    "content": "#!/bin/csh\n\nprism phil3.nm  phil.pctl  -fair -m\nprism phil4.nm  phil.pctl  -fair -m\nprism phil5.nm  phil.pctl  -fair -m\nprism phil6.nm  phil.pctl  -fair -m\nprism phil7.nm  phil.pctl  -fair -m\nprism phil8.nm  phil.pctl  -fair -m\nprism phil9.nm  phil.pctl  -fair -m\n#prism phil10.nm phil.pctl -fair -m\n#prism phil15.nm phil.pctl -fair -m\n#prism phil20.nm phil.pctl -fair -m\n#prism phil25.nm phil.pctl -fair -m\n#prism phil30.nm phil.pctl -fair -m\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil.pctl",
    "content": "// Liveness (if a philosopher is hungry then eventually some philosopher eats)\r\nfilter(forall, \"hungry\" => P>=1 [ F \"eat\" ])\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil10.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p10>=0&p10<=3)|p10=5|p10=7|p10=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p10=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p10=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p10=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p10=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p10=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p8, p10=p6 ] endmodule\r\nmodule phil8 = phil1 [ p1=p8, p2=p9, p10=p7 ] endmodule\r\nmodule phil9 = phil1 [ p1=p9, p2=p10, p10=p8 ] endmodule\r\nmodule phil10 = phil1 [ p1=p10, p2=p1, p10=p9 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8))|((p9>0)&(p9<8))|((p10>0)&(p10<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9))|((p9>=8)&(p9<=9))|((p10>=8)&(p10<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil15.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p15>=0&p15<=3)|p15=5|p15=7|p15=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p15=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p15=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p15=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p15=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p15=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p8, p15=p6 ] endmodule\r\nmodule phil8 = phil1 [ p1=p8, p2=p9, p15=p7 ] endmodule\r\nmodule phil9 = phil1 [ p1=p9, p2=p10, p15=p8 ] endmodule\r\nmodule phil10 = phil1 [ p1=p10, p2=p11, p15=p9 ] endmodule\r\nmodule phil11 = phil1 [ p1=p11, p2=p12, p15=p10 ] endmodule\r\nmodule phil12 = phil1 [ p1=p12, p2=p13, p15=p11 ] endmodule\r\nmodule phil13 = phil1 [ p1=p13, p2=p14, p15=p12 ] endmodule\r\nmodule phil14 = phil1 [ p1=p14, p2=p15, p15=p13 ] endmodule\r\nmodule phil15 = phil1 [ p1=p15, p2=p1, p15=p14 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8))|((p9>0)&(p9<8))|((p10>0)&(p10<8))|((p11>0)&(p11<8))|((p12>0)&(p12<8))|((p13>0)&(p13<8))|((p14>0)&(p14<8))|((p15>0)&(p15<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9))|((p9>=8)&(p9<=9))|((p10>=8)&(p10<=9))|((p11>=8)&(p11<=9))|((p12>=8)&(p12<=9))|((p13>=8)&(p13<=9))|((p14>=8)&(p14<=9))|((p15>=8)&(p15<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil20.nm",
    "content": "// randomized dining philosophers [LR81]\n// dxp/gxn 12/12/99\n// atomic formulae \n// left fork free and right fork free resp.\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\nformula rfree = (p20>=0&p20<=3)|p20=5|p20=7|p20=11;\n\nmodule phil1\n\n\tp1: [0..11];\n\n\t[] p1=0 -> (p1'=0); // stay thinking\n\t[] p1=0 -> (p1'=1); // trying\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\n\t[] p1=6  -> (p1'=1); // put down left\n\t[] p1=7  -> (p1'=1); // put down right\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \n\t[] p1=9  -> (p1'=11); // finished eating and put down right\n\t[] p1=10 -> (p1'=0); // put down right and return to think\n\t[] p1=11 -> (p1'=0); // put down left and return to think\n\nendmodule\n\n// construct further modules through renaming\nmodule phil2 = phil1 [ p1=p2, p2=p3, p20=p1 ] endmodule\nmodule phil3 = phil1 [ p1=p3, p2=p4, p20=p2 ] endmodule\nmodule phil4 = phil1 [ p1=p4, p2=p5, p20=p3 ] endmodule\nmodule phil5 = phil1 [ p1=p5, p2=p6, p20=p4 ] endmodule\nmodule phil6 = phil1 [ p1=p6, p2=p7, p20=p5 ] endmodule\nmodule phil7 = phil1 [ p1=p7, p2=p8, p20=p6 ] endmodule\nmodule phil8 = phil1 [ p1=p8, p2=p9, p20=p7 ] endmodule\nmodule phil9 = phil1 [ p1=p9, p2=p10, p20=p8 ] endmodule\nmodule phil10 = phil1 [ p1=p10, p2=p11, p20=p9 ] endmodule\nmodule phil11 = phil1 [ p1=p11, p2=p12, p20=p10 ] endmodule\nmodule phil12 = phil1 [ p1=p12, p2=p13, p20=p11 ] endmodule\nmodule phil13 = phil1 [ p1=p13, p2=p14, p20=p12 ] endmodule\nmodule phil14 = phil1 [ p1=p14, p2=p15, p20=p13 ] endmodule\nmodule phil15 = phil1 [ p1=p15, p2=p16, p20=p14 ] endmodule\nmodule phil16 = phil1 [ p1=p16, p2=p17, p20=p15 ] endmodule\nmodule phil17 = phil1 [ p1=p17, p2=p18, p20=p16 ] endmodule\nmodule phil18 = phil1 [ p1=p18, p2=p19, p20=p17 ] endmodule\nmodule phil19 = phil1 [ p1=p19, p2=p20, p20=p18 ] endmodule\nmodule phil20 = phil1 [ p1=p20, p2=p1, p20=p19 ] endmodule\n\n// labels\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8))|((p9>0)&(p9<8))|((p10>0)&(p10<8))|((p11>0)&(p11<8))|((p12>0)&(p12<8))|((p13>0)&(p13<8))|((p14>0)&(p14<8))|((p15>0)&(p15<8))|((p16>0)&(p16<8))|((p17>0)&(p17<8))|((p18>0)&(p18<8))|((p19>0)&(p19<8))|((p20>0)&(p20<8));\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9))|((p9>=8)&(p9<=9))|((p10>=8)&(p10<=9))|((p11>=8)&(p11<=9))|((p12>=8)&(p12<=9))|((p13>=8)&(p13<=9))|((p14>=8)&(p14<=9))|((p15>=8)&(p15<=9))|((p16>=8)&(p16<=9))|((p17>=8)&(p17<=9))|((p18>=8)&(p18<=9))|((p19>=8)&(p19<=9))|((p20>=8)&(p20<=9));\n\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil25.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p25>=0&p25<=3)|p25=5|p25=7|p25=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p25=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p25=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p25=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p25=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p25=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p8, p25=p6 ] endmodule\r\nmodule phil8 = phil1 [ p1=p8, p2=p9, p25=p7 ] endmodule\r\nmodule phil9 = phil1 [ p1=p9, p2=p10, p25=p8 ] endmodule\r\nmodule phil10 = phil1 [ p1=p10, p2=p11, p25=p9 ] endmodule\r\nmodule phil11 = phil1 [ p1=p11, p2=p12, p25=p10 ] endmodule\r\nmodule phil12 = phil1 [ p1=p12, p2=p13, p25=p11 ] endmodule\r\nmodule phil13 = phil1 [ p1=p13, p2=p14, p25=p12 ] endmodule\r\nmodule phil14 = phil1 [ p1=p14, p2=p15, p25=p13 ] endmodule\r\nmodule phil15 = phil1 [ p1=p15, p2=p16, p25=p14 ] endmodule\r\nmodule phil16 = phil1 [ p1=p16, p2=p17, p25=p15 ] endmodule\r\nmodule phil17 = phil1 [ p1=p17, p2=p18, p25=p16 ] endmodule\r\nmodule phil18 = phil1 [ p1=p18, p2=p19, p25=p17 ] endmodule\r\nmodule phil19 = phil1 [ p1=p19, p2=p20, p25=p18 ] endmodule\r\nmodule phil20 = phil1 [ p1=p20, p2=p21, p25=p19 ] endmodule\r\nmodule phil21 = phil1 [ p1=p21, p2=p22, p25=p20 ] endmodule\r\nmodule phil22 = phil1 [ p1=p22, p2=p23, p25=p21 ] endmodule\r\nmodule phil23 = phil1 [ p1=p23, p2=p24, p25=p22 ] endmodule\r\nmodule phil24 = phil1 [ p1=p24, p2=p25, p25=p23 ] endmodule\r\nmodule phil25 = phil1 [ p1=p25, p2=p1, p25=p24 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8))|((p9>0)&(p9<8))|((p10>0)&(p10<8))|((p11>0)&(p11<8))|((p12>0)&(p12<8))|((p13>0)&(p13<8))|((p14>0)&(p14<8))|((p15>0)&(p15<8))|((p16>0)&(p16<8))|((p17>0)&(p17<8))|((p18>0)&(p18<8))|((p19>0)&(p19<8))|((p20>0)&(p20<8))|((p21>0)&(p21<8))|((p22>0)&(p22<8))|((p23>0)&(p23<8))|((p24>0)&(p24<8))|((p25>0)&(p25<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9))|((p9>=8)&(p9<=9))|((p10>=8)&(p10<=9))|((p11>=8)&(p11<=9))|((p12>=8)&(p12<=9))|((p13>=8)&(p13<=9))|((p14>=8)&(p14<=9))|((p15>=8)&(p15<=9))|((p16>=8)&(p16<=9))|((p17>=8)&(p17<=9))|((p18>=8)&(p18<=9))|((p19>=8)&(p19<=9))|((p20>=8)&(p20<=9))|((p21>=8)&(p21<=9))|((p22>=8)&(p22<=9))|((p23>=8)&(p23<=9))|((p24>=8)&(p24<=9))|((p25>=8)&(p25<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil3.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p3>=0&p3<=3)|p3=5|p3=7|p3=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p3=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p1, p3=p2 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil30.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p30>=0&p30<=3)|p30=5|p30=7|p30=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p30=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p30=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p30=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p30=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p30=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p8, p30=p6 ] endmodule\r\nmodule phil8 = phil1 [ p1=p8, p2=p9, p30=p7 ] endmodule\r\nmodule phil9 = phil1 [ p1=p9, p2=p10, p30=p8 ] endmodule\r\nmodule phil10 = phil1 [ p1=p10, p2=p11, p30=p9 ] endmodule\r\nmodule phil11 = phil1 [ p1=p11, p2=p12, p30=p10 ] endmodule\r\nmodule phil12 = phil1 [ p1=p12, p2=p13, p30=p11 ] endmodule\r\nmodule phil13 = phil1 [ p1=p13, p2=p14, p30=p12 ] endmodule\r\nmodule phil14 = phil1 [ p1=p14, p2=p15, p30=p13 ] endmodule\r\nmodule phil15 = phil1 [ p1=p15, p2=p16, p30=p14 ] endmodule\r\nmodule phil16 = phil1 [ p1=p16, p2=p17, p30=p15 ] endmodule\r\nmodule phil17 = phil1 [ p1=p17, p2=p18, p30=p16 ] endmodule\r\nmodule phil18 = phil1 [ p1=p18, p2=p19, p30=p17 ] endmodule\r\nmodule phil19 = phil1 [ p1=p19, p2=p20, p30=p18 ] endmodule\r\nmodule phil20 = phil1 [ p1=p20, p2=p21, p30=p19 ] endmodule\r\nmodule phil21 = phil1 [ p1=p21, p2=p22, p30=p20 ] endmodule\r\nmodule phil22 = phil1 [ p1=p22, p2=p23, p30=p21 ] endmodule\r\nmodule phil23 = phil1 [ p1=p23, p2=p24, p30=p22 ] endmodule\r\nmodule phil24 = phil1 [ p1=p24, p2=p25, p30=p23 ] endmodule\r\nmodule phil25 = phil1 [ p1=p25, p2=p26, p30=p24 ] endmodule\r\nmodule phil26 = phil1 [ p1=p26, p2=p27, p30=p25 ] endmodule\r\nmodule phil27 = phil1 [ p1=p27, p2=p28, p30=p26 ] endmodule\r\nmodule phil28 = phil1 [ p1=p28, p2=p29, p30=p27 ] endmodule\r\nmodule phil29 = phil1 [ p1=p29, p2=p30, p30=p28 ] endmodule\r\nmodule phil30 = phil1 [ p1=p30, p2=p1, p30=p29 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8))|((p9>0)&(p9<8))|((p10>0)&(p10<8))|((p11>0)&(p11<8))|((p12>0)&(p12<8))|((p13>0)&(p13<8))|((p14>0)&(p14<8))|((p15>0)&(p15<8))|((p16>0)&(p16<8))|((p17>0)&(p17<8))|((p18>0)&(p18<8))|((p19>0)&(p19<8))|((p20>0)&(p20<8))|((p21>0)&(p21<8))|((p22>0)&(p22<8))|((p23>0)&(p23<8))|((p24>0)&(p24<8))|((p25>0)&(p25<8))|((p26>0)&(p26<8))|((p27>0)&(p27<8))|((p28>0)&(p28<8))|((p29>0)&(p29<8))|((p30>0)&(p30<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9))|((p9>=8)&(p9<=9))|((p10>=8)&(p10<=9))|((p11>=8)&(p11<=9))|((p12>=8)&(p12<=9))|((p13>=8)&(p13<=9))|((p14>=8)&(p14<=9))|((p15>=8)&(p15<=9))|((p16>=8)&(p16<=9))|((p17>=8)&(p17<=9))|((p18>=8)&(p18<=9))|((p19>=8)&(p19<=9))|((p20>=8)&(p20<=9))|((p21>=8)&(p21<=9))|((p22>=8)&(p22<=9))|((p23>=8)&(p23<=9))|((p24>=8)&(p24<=9))|((p25>=8)&(p25<=9))|((p26>=8)&(p26<=9))|((p27>=8)&(p27<=9))|((p28>=8)&(p28<=9))|((p29>=8)&(p29<=9))|((p30>=8)&(p30<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil4.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p4>=0&p4<=3)|p4=5|p4=7|p4=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p4=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p4=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p1, p4=p3 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil5.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p5>=0&p5<=3)|p5=5|p5=7|p5=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p5=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p5=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p5=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p1, p5=p4 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil6.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p6>=0&p6<=3)|p6=5|p6=7|p6=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p6=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p6=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p6=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p6=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p1, p6=p5 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil7.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p7>=0&p7<=3)|p7=5|p7=7|p7=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p7=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p7=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p7=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p7=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p7=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p1, p7=p6 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil8.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p8>=0&p8<=3)|p8=5|p8=7|p8=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p8=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p8=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p8=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p8=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p8=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p8, p8=p6 ] endmodule\r\nmodule phil8 = phil1 [ p1=p8, p2=p1, p8=p7 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil/original/phil9.nm",
    "content": "// randomized dining philosophers [LR81]\r\n// dxp/gxn 12/12/99\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p9>=0&p9<=3)|p9=5|p9=7|p9=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=0); // stay thinking\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=2 &  !lfree -> (p1'=2); // left not free\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=3 &  !rfree -> (p1'=3); // right not free\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p9=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p4, p9=p2 ] endmodule\r\nmodule phil4 = phil1 [ p1=p4, p2=p5, p9=p3 ] endmodule\r\nmodule phil5 = phil1 [ p1=p5, p2=p6, p9=p4 ] endmodule\r\nmodule phil6 = phil1 [ p1=p6, p2=p7, p9=p5 ] endmodule\r\nmodule phil7 = phil1 [ p1=p7, p2=p8, p9=p6 ] endmodule\r\nmodule phil8 = phil1 [ p1=p8, p2=p9, p9=p7 ] endmodule\r\nmodule phil9 = phil1 [ p1=p9, p2=p1, p9=p8 ] endmodule\r\n\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8))|((p4>0)&(p4<8))|((p5>0)&(p5<8))|((p6>0)&(p6<8))|((p7>0)&(p7<8))|((p8>0)&(p8<8))|((p9>0)&(p9<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9))|((p4>=8)&(p4<=9))|((p5>=8)&(p5<=9))|((p6>=8)&(p6<=9))|((p7>=8)&(p7<=9))|((p8>=8)&(p8<=9))|((p9>=8)&(p9<=9));\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/phil_lss/README.txt",
    "content": "This case study is based on Lehmann and Rabin's solution to the well known dining philosophers problem [LR81]\r\nand the analysis of this algorithm by Lynch, Saias and Segala [LSS94].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/phil_lss.php\r\n\r\n=====================================================================================\r\n\r\n[LR81]\r\nD. Lehmann and M. Rabin\r\nOn the Advantages of Free Choice: A Symmetric Fully Distributed Solution to the Dining Philosophers Problem (Extended Abstract)\r\nIn Proc. 8th Symposium on Principles of Programming Languages, pp. 133-138, 1981\r\n\r\nLSS94]\r\nN. Lynch, I. Saias and R. Segala\r\nProving Time Bounds for Randomized Distributed Algorithms\r\nIn Proc. 13th ACM Symposium on Principles of Distributed Computing, pp. 314-323, 1994\r\n"
  },
  {
    "path": "prism-examples/mdps/phil_lss/auto",
    "content": "#!/bin/csh\n\nprism phil_lss3.nm phil_lss3.pctl -const K=3:6,L=1 -m\n#prism phil_lss4.nm phil_lss4.pctl -const K=4:5,L=1 -m\n"
  },
  {
    "path": "prism-examples/mdps/phil_lss/phil_lss3.nm",
    "content": "// Lehmann-Rabin algorithm [LR82] (dining philosophers)\r\n// we suppose an action takes 1 time unit \r\n// an a process can wait at most K time units before making a transition\r\n// gxn/dxp 01/02/00\r\n\r\nmdp\r\n\r\n// CONSTANTS\r\nconst K;\r\n\r\n// COUNTER FORMULAE\r\n// ci number of steps since process last moved\r\n// removing trying and remainder states since\r\n// these are controlled by the process not the adversary\r\n\r\n// process can go if it does not stop one of the other processes round counter reaching K+1\r\n// added complication if two processes counter equals K-1, then if neither makes a transition\r\n// both reach K, and hence one must reach K+1 which we must disallow\r\nformula can1 = !((c2=K) | (c3=K) | ((c2=K-1) & (c3=K-1)));\r\nformula can2 = !((c1=K) | (c3=K) | ((c1=K-1) & (c3=K-1)));\r\nformula can3 = !((c1=K) | (c2=K) | ((c1=K-1) & (c2=K-1)));\r\n\r\n// when a process moves the counters of the other processes increase \r\n// but only when they are not in trying or remainder\r\nformula count1  = (p1!=13) & (p1!=0);\r\nformula count2  = (p2!=13) & (p2!=0);\r\nformula count3  = (p3!=13) & (p3!=0);\r\nformula ncount1 = (p1=13) | (p1=0);\r\nformula ncount2 = (p2=13) | (p2=0);\r\nformula ncount3 = (p3=13) | (p3=0);\r\n\r\nmodule counter\r\n\r\n\tc1 : [0..K];\r\n\tc2 : [0..K];\r\n\tc3 : [0..K];\r\n\t\r\n\t// process 1 moves\t\r\n\t[s1] count2  & count3  & can1 -> (c1'=0) & (c2'=c2+1) & (c3'=c3+1);\t\r\n\t[s1] ncount2 & count3  & can1 -> (c1'=0) & (c3'=c3+1);\t\r\n\t[s1] count2  & ncount3 & can1 -> (c1'=0) & (c2'=c2+1);\t\r\n\t[s1] ncount2 & ncount3 & can1 -> (c1'=0);\t\r\n\t// process 2 moves\r\n\t[s2] count1  & count3  & can2 -> (c2'=0) & (c1'=c1+1) & (c3'=c3+1);\t\r\n\t[s2] ncount1 & count3  & can2 -> (c2'=0) & (c3'=c3+1);\t\r\n\t[s2] count1  & ncount3 & can2 -> (c2'=0) & (c1'=c1+1);\t\r\n\t[s2] ncount1 & ncount3 & can2 -> (c2'=0);\t\r\n\t// process 3 moves\r\n\t[s3] count1  & count2  & can3 -> (c3'=0) & (c1'=c1+1) & (c2'=c2+1);\r\n\t[s3] ncount1 & count2  & can3 -> (c3'=0) & (c2'=c2+1);\r\n\t[s3] count1  & ncount2 & can3 -> (c3'=0) & (c1'=c1+1);\r\n\t[s3] ncount1 & ncount2 & can3 -> (c3'=0);\r\n\t\r\nendmodule\r\n \r\n// PHILOSOPHER 1\r\n// atomic formule \r\n// left fork and right fork free resp.\r\nformula lfree = p2>=0&p2<=4|p2=6|p2=11|p2=13;\r\nformula rfree = p3>=0&p3<=3|p3=5|p3=7|p3=12|p3=13;\r\n\r\nmodule phil1\r\n\r\n\tp1 : [0..13];\r\n\r\n\t[s1] (p1=0) -> (p1'=0); // try \r\n\t[s1] (p1=0) -> (p1'=1);\r\n\t[s1] (p1=1) -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // flip\r\n\t[s1] (p1=2) &  lfree -> (p1'=4); // wl and l free\r\n\t[s1] (p1=2) & !lfree -> (p1'=2); // wl and l taken\r\n\t[s1] (p1=3) &  rfree -> (p1'=5); // wr and r free\r\n\t[s1] (p1=3) & !rfree -> (p1'=3); // wr and r taken\r\n\t[s1] (p1=4) &  rfree -> (p1'=8); // l and r free\r\n\t[s1] (p1=4) & !rfree -> (p1'=6); // l and r taken\r\n\t[s1] (p1=5) &  lfree -> (p1'=8); // r and l free\r\n\t[s1] (p1=5) & !lfree -> (p1'=7); // r and l taken\r\n\t[s1] (p1=6)  -> (p1'=1); // nr\r\n\t[s1] (p1=7)  -> (p1'=1); // nl\r\n\t[s1] (p1=8)  -> (p1'=9); // pre_crit\r\n\t[s1] (p1=9)  -> (p1'=10); // crit\r\n\t[s1] (p1=10) -> (p1'=11); // exit\r\n\t[s1] (p1=10) -> (p1'=12);\r\n\t[s1] (p1=11) -> (p1'=13); // put down left first\r\n\t[s1] (p1=12) -> (p1'=13); // put down right first\r\n\t[s1] (p1=13) -> (p1'=0); // remainder\r\n\t[s1] (p1=13) -> (p1'=13);\r\n\r\nendmodule\r\n\r\n// construct further processes through renaming\r\nmodule phil2=phil1 [p1=p2, p2=p3, p3=p1, s1=s2] endmodule\r\nmodule phil3=phil1 [p1=p3, p2=p1, p3=p2, s1=s3] endmodule\r\n\r\n// reward structure - number of steps\r\nrewards \"steps\"\r\n\t[s1] true : 1;\r\n\t[s2] true : 1;\r\n\t[s3] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/mdps/phil_lss/phil_lss3.pctl",
    "content": "const int L; // discrete time bound\n\nlabel \"trying\" = ((p1>0) & (p1<8))  | ((p2>0) & (p2<8)) | ((p3>0) & (p3<8)); // philosopher in its trying region\nlabel \"entered\" = ((p1>7) & (p1<13)) | ((p2>7) & (p2<13)) | ((p3>7) & (p3<13)); // philosopher in its critical section\n\n// lockout free\nfilter(forall, \"trying\" =>  P>=1 [ true U \"entered\" ])\n\n// bounded until: minimum probability (from a state where a process is in its trying region) that some process enters its critical section within k steps\nPmin=? [ true U<=L \"entered\" {\"trying\"}{min} ]\n\n// expected time: maximum expected time (from a state where a process is in its trying region) that some process enters its critical section\nRmax=? [ F \"entered\" {\"trying\"}{max} ]\n"
  },
  {
    "path": "prism-examples/mdps/phil_lss/phil_lss4.nm",
    "content": "// Lehmann-Rabin algorithm [LR82] (dining philosophers)\r\n// we suppose an action takes 1 time unit \r\n// an a process can wait at most K time units before making a transition\r\n// gxn/dxp 01/02/00\r\n\r\nmdp\r\n\r\n// CONSTANTS\r\nconst K;\r\n\r\n// COUNTER FORMULAE\r\n// ci number of steps since process last moved\r\n// removing trying and remainder states since\r\n// these are controlled by the process not the adversary\r\n\r\n// process can go if it does not stop one of the other processes round counter reaching n+1\r\n// added complication if two processes counter equals n-1, then if neither makes a transition\r\n// both reach n, and hence one must reach n+1 which we must disallow\r\n\r\nformula can1 = !((c2=K) | (c3=K) | (c4=K) | ((c2=K-1) & (c3=K-1)) | ((c2=K-1) & (c4=K-1)) | ((c3=K-1) & (c4=K-1)) | ((c2=K-2) & (c3=K-2) & (c4=K-2)));\r\nformula can2 = !((c1=K) | (c3=K) | (c4=K) | ((c1=K-1) & (c3=K-1)) | ((c1=K-1) & (c4=K-1)) | ((c3=K-1) & (c4=K-1)) | ((c1=K-2) & (c3=K-2) & (c4=K-2)));\r\nformula can3 = !((c1=K) | (c2=K) | (c4=K) | ((c1=K-1) & (c2=K-1)) | ((c1=K-1) & (c4=K-1)) | ((c2=K-1) & (c4=K-1)) | ((c1=K-2) & (c2=K-2) & (c4=K-2)));\r\nformula can4 = !((c1=K) | (c2=K) | (c3=K) | ((c1=K-1) & (c2=K-1)) | ((c1=K-1) & (c3=K-1)) | ((c2=K-1) & (c3=K-1)) | ((c1=K-2) & (c2=K-2) & (c3=K-2)));\r\n\r\n// when a process moves the counters of the other processes increase \r\n// but only when they are not in trying or remainder\r\n\r\nformula count1  = (p1!=13) & (p1!=0);\r\nformula count2  = (p2!=13) & (p2!=0);\r\nformula count3  = (p3!=13) & (p3!=0);\r\nformula count4  = (p4!=13) & (p4!=0);\r\nformula ncount1 = (p1=13) | (p1=0);\r\nformula ncount2 = (p2=13) | (p2=0);\r\nformula ncount3 = (p3=13) | (p3=0);\r\nformula ncount4 = (p4=13) | (p4=0);\r\n\r\nmodule counter\r\n\r\n\tc1 : [0..K];\r\n\tc2 : [0..K];\r\n\tc3 : [0..K];\r\n\tc4 : [0..K];\r\n\t\r\n\t// process 1 moves\r\n\t[s1] can1 & ncount2 & ncount3 & ncount4 -> (c1'=0);\r\n\t[s1] can1 & ncount2 & ncount3 &  count4 -> (c1'=0) & (c4'=c4+1);\r\n\t[s1] can1 & ncount2 &  count3 & ncount4 -> (c1'=0) & (c3'=c3+1);\r\n\t[s1] can1 & ncount2 &  count3 &  count4 -> (c1'=0) & (c3'=c3+1) & (c4'=c4+1);\r\n\t[s1] can1 &  count2 & ncount3 & ncount4 -> (c1'=0) & (c2'=c2+1);\r\n\t[s1] can1 &  count2 & ncount3 &  count4 -> (c1'=0) & (c2'=c2+1) & (c4'=c4+1);\r\n\t[s1] can1 &  count2 &  count3 & ncount4 -> (c1'=0) & (c2'=c2+1) & (c3'=c3+1);\r\n\t[s1] can1 &  count2 &  count3 &  count4 -> (c1'=0) & (c2'=c2+1) & (c3'=c3+1) & (c4'=c4+1);\r\n\t// process 2 moves\r\n\t[s2] can2 & ncount1 & ncount3 & ncount4 -> (c2'=0);\r\n\t[s2] can2 & ncount1 & ncount3 &  count4 -> (c2'=0) & (c4'=c4+1);\r\n\t[s2] can2 & ncount1 &  count3 & ncount4 -> (c2'=0) & (c3'=c3+1);\r\n\t[s2] can2 & ncount1 &  count3 &  count4 -> (c2'=0) & (c3'=c3+1) & (c4'=c4+1);\r\n\t[s2] can2 &  count1 & ncount3 & ncount4 -> (c2'=0) & (c1'=c1+1);\r\n\t[s2] can2 &  count1 & ncount3 &  count4 -> (c2'=0) & (c1'=c1+1) & (c4'=c4+1);\r\n\t[s2] can2 &  count1 &  count3 & ncount4 -> (c2'=0) & (c1'=c1+1) & (c3'=c3+1);\r\n\t[s2] can2 &  count1 &  count3 &  count4 -> (c2'=0) & (c1'=c1+1) & (c3'=c3+1) & (c4'=c4+1);\r\n\t// process 3 moves\r\n\t[s3] can3 & ncount1 & ncount2 & ncount4 -> (c3'=0);\r\n\t[s3] can3 & ncount1 & ncount2 &  count4 -> (c3'=0) & (c4'=c4+1);\r\n\t[s3] can3 & ncount1 &  count2 & ncount4 -> (c3'=0) & (c2'=c2+1);\r\n\t[s3] can3 & ncount1 &  count2 &  count4 -> (c3'=0) & (c2'=c2+1) & (c4'=c4+1);\r\n\t[s3] can3 &  count1 & ncount2 & ncount4 -> (c3'=0) & (c1'=c1+1);\r\n\t[s3] can3 &  count1 & ncount2 &  count4 -> (c3'=0) & (c1'=c1+1) & (c4'=c4+1);\r\n\t[s3] can3 &  count1 &  count2 & ncount4 -> (c3'=0) & (c1'=c1+1) & (c2'=c2+1);\r\n\t[s3] can3 &  count1 &  count2 &  count4 -> (c3'=0) & (c1'=c1+1) & (c2'=c2+1) & (c4'=c4+1);\r\n\t// process 4 moves\r\n\t[s4] can4 & ncount1 & ncount2 & ncount3 -> (c4'=0);\r\n\t[s4] can4 & ncount1 & ncount2 &  count3 -> (c4'=0) & (c3'=c3+1);\r\n\t[s4] can4 & ncount1 &  count2 & ncount3 -> (c4'=0) & (c2'=c2+1);\r\n\t[s4] can4 & ncount1 &  count2 &  count3 -> (c4'=0) & (c2'=c2+1) & (c3'=c3+1);\r\n\t[s4] can4 &  count1 & ncount2 & ncount3 -> (c4'=0) & (c1'=c1+1);\r\n\t[s4] can4 &  count1 & ncount2 &  count3 -> (c4'=0) & (c1'=c1+1) & (c3'=c3+1);\r\n\t[s4] can4 &  count1 &  count2 & ncount3 -> (c4'=0) & (c1'=c1+1) & (c2'=c2+1);\r\n\t[s4] can4 &  count1 &  count2 &  count3 -> (c4'=0) & (c1'=c1+1) & (c2'=c2+1) & (c3'=c3+1);\r\n\t\r\nendmodule\r\n \r\n// PHILOSOPHER 1\r\n// atomic formule \r\n// left fork and right fork free resp.\r\nformula lfree = p2>=0&p2<=4|p2=6|p2=11|p2=13;\r\nformula rfree = p3>=0&p3<=3|p3=5|p3=7|p3=12|p3=13;\r\n\r\nmodule phil1\r\n\r\n\tp1 : [0..13];\r\n\r\n\t[s1] (p1=0) -> (p1'=0); // try \r\n\t[s1] (p1=0) -> (p1'=1);\r\n\t[s1] (p1=1) -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // flip\r\n\t[s1] (p1=2) &  lfree -> (p1'=4); // wl and l free\r\n\t[s1] (p1=2) & !lfree -> (p1'=2); // wl and l taken\r\n\t[s1] (p1=3) &  rfree -> (p1'=5); // wr and r free\r\n\t[s1] (p1=3) & !rfree -> (p1'=3); // wr and r taken\r\n\t[s1] (p1=4) &  rfree -> (p1'=8); // l and r free\r\n\t[s1] (p1=4) & !rfree -> (p1'=6); // l and r taken\r\n\t[s1] (p1=5) &  lfree -> (p1'=8); // r and l free\r\n\t[s1] (p1=5) & !lfree -> (p1'=7); // r and l taken\r\n\t[s1] (p1=6)  -> (p1'=1); // nr\r\n\t[s1] (p1=7)  -> (p1'=1); // nl\r\n\t[s1] (p1=8)  -> (p1'=9); // pre_crit\r\n\t[s1] (p1=9)  -> (p1'=10); // crit\r\n\t[s1] (p1=10) -> (p1'=11); // exit\r\n\t[s1] (p1=10) -> (p1'=12);\r\n\t[s1] (p1=11) -> (p1'=13); // put down left first\r\n\t[s1] (p1=12) -> (p1'=13); // put down right first\r\n\t[s1] (p1=13) -> (p1'=0); // remainder\r\n\t[s1] (p1=13) -> (p1'=13);\r\n\r\nendmodule\r\n\r\n// construct further processes through renaming\r\nmodule phil2=phil1 [p1=p2, p2=p3, p3=p4, p4=p1, s1=s2] endmodule\r\nmodule phil3=phil1 [p1=p3, p2=p4, p3=p1, p4=p2, s1=s3] endmodule\r\nmodule phil4=phil1 [p1=p4, p2=p1, p3=p2, p4=p3, s1=s4] endmodule\r\n\r\n// reward structure - number of steps\r\nrewards \"steps\"\r\n\t[s1] true : 1;\r\n\t[s2] true : 1;\r\n\t[s3] true : 1;\r\n\t[s4] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/mdps/phil_lss/phil_lss4.pctl",
    "content": "const int L; // discrete time bound\n\nlabel \"trying\" = ((p1>0) & (p1<8))  | ((p2>0) & (p2<8)) | ((p3>0) & (p3<8)) | ((p4>0) & (p4<8)); // philosopher in its trying region\nlabel \"entered\" = ((p1>7) & (p1<13)) | ((p2>7) & (p2<13)) | ((p3>7) & (p3<13)) | ((p4>7) & (p4<13)); // philosopher in its critical section\n\n// lockout free\nfilter(forall, \"trying\" =>  P>=1 [ true U \"entered\" ])\n\n// bounded until: minimum probability (from a state where a process is in its trying region) that some process enters its critical section within k steps\nPmin=? [ F<=L \"entered\" {\"trying\"}{min} ]\n\n// expected time: maximum expected time (from a state where a process is in its trying region) that some process enters its critical section\nRmax=? [ F \"entered\" {\"trying\"}{max} ]\n"
  },
  {
    "path": "prism-examples/mdps/rabin/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 6 7 8 9 10 )\n\techo \"Generating for N=$N\"\n\tprismpp .rabinN.nm.pp $N >! rabin$N.nm\n\tunix2dos rabin$N.nm\nend\n"
  },
  {
    "path": "prism-examples/mdps/rabin/.rabinN.nm.pp",
    "content": "#const N#\n#const K=4+func(ceil,func(log,N,2))#\n// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\n\n// to remove the need for fairness constraints for this model it is sufficent\n// to remove the self loops from the model \n\n// the step corresponding to a process making a draw has been split into two steps\n// to allow us to identify states where a process will draw without knowing the value\n// randomly drawn\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\n// (i.e. no other process can move one the first step has been made)\n// as for example otherwise an adversary can prevent the process from actually drawing\n// in the current round by not scheduling it after it has performed the first step\n\r\nmdp\r\n\n// size of shared counter\nconst int K = #K#; // 4+ceil(log_2 N)\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\n// formula to keep drawing phase atomic\n// (a process can only move if no other process is in the middle of drawing)\nformula go = (#& i=2:N#draw#i#=0#end#);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 ->#+ i=1:K-1# #1/func(floor,func(pow,2,i))# : (b1'=#i#) & (r1'=r) & (b'=max(b,#i#)) & (draw1'=0)\n\t         #end#+ #1/func(floor,func(pow,2,K-1))# : (b1'=#K#) & (r1'=r) & (b'=max(b,#K#)) & (draw1'=0);\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\n#for i=2:N#\r\nmodule process#i# = process1 [p1=p#i#, b1=b#i#, r1=r#i#, draw1=draw#i#, draw#i#=draw1 ] endmodule\r#end#\r\n\n// formulas/labels for use in properties:\n\n// number of processes in critical section\nformula num_procs_in_crit = #+ i=1:N#(p#i#=2?1:0)#end#;\n\n// one of the processes is trying\r\nlabel \"one_trying\" = #| i=1:N#p#i#=1#end#;\n\n// one of the processes is in the critical section\nlabel \"one_critical\" = #| i=1:N#p#i#=2#end#;\n\n// maximum current draw of the processes\nformula maxb = max(b1#for i=2:N#,b#i##end#);\r\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/README.txt",
    "content": "This case study is based on Rabin's solution to the well known mutual exclusion problem [Rab82].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/rabin.php\n\r\n=====================================================================================\r\n\r\n[Rab82]\r\nM. Rabin\r\nN-Process Mutual Exclusion with Bounded Waiting by 4log2N-Valued Shared Variable\r\nJournal of Computer and System Sciences, 25(1):66-75, 1982\r\n\r\n\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/auto",
    "content": "#!/bin/csh\n\nprism rabin3.nm rabin.pctl -m\nprism rabin4.nm rabin.pctl -m\nprism rabin5.nm rabin.pctl -m\nprism rabin6.nm rabin.pctl -m\nprism rabin7.nm rabin.pctl -m\nprism rabin8.nm rabin.pctl -m\n#prism rabin9.nm rabin.pctl -m\n#prism rabin10.nm rabin.pctl -m\n\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin.pctl",
    "content": "// Mutual exclusion: at any time t there is at most one process in its critical section phase\nfilter(forall, num_procs_in_crit <= 1)\n\n// Liveness: if a process is trying, then eventually a process enters the critical section\nfilter(forall, \"one_trying\" => P>=1 [ F \"one_critical\" ])\n\n\n// weaker version of k-bounded waiting: minimum probability process enters the criticial section given it draws\nPmin=?[ !\"one_critical\" U (p1=2) {draw1=1 & !\"one_critical\"}{min} ]\n// filter expresses the fact that we are only interested in the probability for states in which\n// - process is going to make a draw (draw1=1)\n// - no process is in the critical section (otherwise probability is clearly 0)\n// and we take the minimum value over this set of states\n\n// probability above is zero which is due to the fact that in certain states the adversary can\n// use the values of the draw variables of other processes to prevent the process from entering\n// the criticial section\n// this does not quite disprove Rabin's bounded waiting property as one is starting\n// from the state the process decides to enter the round and one does not take into account\n// the probability of reaching this state (this does have an influence as the results\n// for the properties below show that to get the probability 0 one of the other processes\n//must have already randomly picked a high value for its bi)\n\n// to demonstrate this fact we restrict attention to states where these values\n// are restricted,i.e. where the values of the bi variables are bounded\nconst int k;\n\rPmin=?[ !\"one_critical\" U (p1=2) {draw1=1 & !\"one_critical\" & maxb<=k}{min} ]\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin10.nm",
    "content": "// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\r\n\r\n// to remove the need for fairness constraints for this model it is sufficent\r\n// to remove the self loops from the model \r\n\r\n// the step corresponding to a process making a draw has been split into two steps\r\n// to allow us to identify states where a process will draw without knowing the value\r\n// randomly drawn\r\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\r\n// (i.e. no other process can move one the first step has been made)\r\n// as for example otherwise an adversary can prevent the process from actually drawing\r\n// in the current round by not scheduling it after it has performed the first step\r\n\r\nmdp\r\n\r\n// size of shared counter\r\nconst int K = 8; // 4+ceil(log_2 N)\r\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\r\n// formula to keep drawing phase atomic\r\n// (a process can only move if no other process is in the middle of drawing)\r\nformula go = (draw2=0&draw3=0&draw4=0&draw5=0&draw6=0&draw7=0&draw8=0&draw9=0&draw10=0);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\r\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\r\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 -> 0.5 : (b1'=1) & (r1'=r) & (b'=max(b,1)) & (draw1'=0)\r\n\t         + 0.25 : (b1'=2) & (r1'=r) & (b'=max(b,2)) & (draw1'=0)\r\n\t         + 0.125 : (b1'=3) & (r1'=r) & (b'=max(b,3)) & (draw1'=0)\r\n\t         + 0.0625 : (b1'=4) & (r1'=r) & (b'=max(b,4)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=5) & (r1'=r) & (b'=max(b,5)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=6) & (r1'=r) & (b'=max(b,6)) & (draw1'=0)\r\n\t         + 0.0078125 : (b1'=7) & (r1'=r) & (b'=max(b,7)) & (draw1'=0)\r\n\t         + 0.0078125 : (b1'=8) & (r1'=r) & (b'=max(b,8)) & (draw1'=0);\r\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule process2 = process1 [p1=p2, b1=b2, r1=r2, draw1=draw2, draw2=draw1 ] endmodule\r\nmodule process3 = process1 [p1=p3, b1=b3, r1=r3, draw1=draw3, draw3=draw1 ] endmodule\r\nmodule process4 = process1 [p1=p4, b1=b4, r1=r4, draw1=draw4, draw4=draw1 ] endmodule\r\nmodule process5 = process1 [p1=p5, b1=b5, r1=r5, draw1=draw5, draw5=draw1 ] endmodule\r\nmodule process6 = process1 [p1=p6, b1=b6, r1=r6, draw1=draw6, draw6=draw1 ] endmodule\r\nmodule process7 = process1 [p1=p7, b1=b7, r1=r7, draw1=draw7, draw7=draw1 ] endmodule\r\nmodule process8 = process1 [p1=p8, b1=b8, r1=r8, draw1=draw8, draw8=draw1 ] endmodule\r\nmodule process9 = process1 [p1=p9, b1=b9, r1=r9, draw1=draw9, draw9=draw1 ] endmodule\r\nmodule process10 = process1 [p1=p10, b1=b10, r1=r10, draw1=draw10, draw10=draw1 ] endmodule\r\n\r\n// formulas/labels for use in properties:\r\n\r\n// number of processes in critical section\r\nformula num_procs_in_crit = (p1=2?1:0)+(p2=2?1:0)+(p3=2?1:0)+(p4=2?1:0)+(p5=2?1:0)+(p6=2?1:0)+(p7=2?1:0)+(p8=2?1:0)+(p9=2?1:0)+(p10=2?1:0);\r\n\r\n// one of the processes is trying\r\nlabel \"one_trying\" = p1=1|p2=1|p3=1|p4=1|p5=1|p6=1|p7=1|p8=1|p9=1|p10=1;\r\n\r\n// one of the processes is in the critical section\r\nlabel \"one_critical\" = p1=2|p2=2|p3=2|p4=2|p5=2|p6=2|p7=2|p8=2|p9=2|p10=2;\r\n\r\n// maximum current draw of the processes\r\nformula maxb = max(b1,b2,b3,b4,b5,b6,b7,b8,b9,b10);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin3.nm",
    "content": "// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\r\n\r\n// to remove the need for fairness constraints for this model it is sufficent\r\n// to remove the self loops from the model \r\n\r\n// the step corresponding to a process making a draw has been split into two steps\r\n// to allow us to identify states where a process will draw without knowing the value\r\n// randomly drawn\r\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\r\n// (i.e. no other process can move one the first step has been made)\r\n// as for example otherwise an adversary can prevent the process from actually drawing\r\n// in the current round by not scheduling it after it has performed the first step\r\n\r\nmdp\r\n\r\n// size of shared counter\r\nconst int K = 6; // 4+ceil(log_2 N)\r\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\r\n// formula to keep drawing phase atomic\r\n// (a process can only move if no other process is in the middle of drawing)\r\nformula go = (draw2=0&draw3=0);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\r\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\r\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 -> 0.5 : (b1'=1) & (r1'=r) & (b'=max(b,1)) & (draw1'=0)\r\n\t         + 0.25 : (b1'=2) & (r1'=r) & (b'=max(b,2)) & (draw1'=0)\r\n\t         + 0.125 : (b1'=3) & (r1'=r) & (b'=max(b,3)) & (draw1'=0)\r\n\t         + 0.0625 : (b1'=4) & (r1'=r) & (b'=max(b,4)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=5) & (r1'=r) & (b'=max(b,5)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=6) & (r1'=r) & (b'=max(b,6)) & (draw1'=0);\r\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule process2 = process1 [p1=p2, b1=b2, r1=r2, draw1=draw2, draw2=draw1 ] endmodule\r\nmodule process3 = process1 [p1=p3, b1=b3, r1=r3, draw1=draw3, draw3=draw1 ] endmodule\r\n\r\n// formulas/labels for use in properties:\r\n\r\n// number of processes in critical section\r\nformula num_procs_in_crit = (p1=2?1:0)+(p2=2?1:0)+(p3=2?1:0);\r\n\r\n// one of the processes is trying\r\nlabel \"one_trying\" = p1=1|p2=1|p3=1;\r\n\r\n// one of the processes is in the critical section\r\nlabel \"one_critical\" = p1=2|p2=2|p3=2;\r\n\r\n// maximum current draw of the processes\r\nformula maxb = max(b1,b2,b3);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin4.nm",
    "content": "// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\r\n\r\n// to remove the need for fairness constraints for this model it is sufficent\r\n// to remove the self loops from the model \r\n\r\n// the step corresponding to a process making a draw has been split into two steps\r\n// to allow us to identify states where a process will draw without knowing the value\r\n// randomly drawn\r\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\r\n// (i.e. no other process can move one the first step has been made)\r\n// as for example otherwise an adversary can prevent the process from actually drawing\r\n// in the current round by not scheduling it after it has performed the first step\r\n\r\nmdp\r\n\r\n// size of shared counter\r\nconst int K = 6; // 4+ceil(log_2 N)\r\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\r\n// formula to keep drawing phase atomic\r\n// (a process can only move if no other process is in the middle of drawing)\r\nformula go = (draw2=0&draw3=0&draw4=0);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\r\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\r\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 -> 0.5 : (b1'=1) & (r1'=r) & (b'=max(b,1)) & (draw1'=0)\r\n\t         + 0.25 : (b1'=2) & (r1'=r) & (b'=max(b,2)) & (draw1'=0)\r\n\t         + 0.125 : (b1'=3) & (r1'=r) & (b'=max(b,3)) & (draw1'=0)\r\n\t         + 0.0625 : (b1'=4) & (r1'=r) & (b'=max(b,4)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=5) & (r1'=r) & (b'=max(b,5)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=6) & (r1'=r) & (b'=max(b,6)) & (draw1'=0);\r\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule process2 = process1 [p1=p2, b1=b2, r1=r2, draw1=draw2, draw2=draw1 ] endmodule\r\nmodule process3 = process1 [p1=p3, b1=b3, r1=r3, draw1=draw3, draw3=draw1 ] endmodule\r\nmodule process4 = process1 [p1=p4, b1=b4, r1=r4, draw1=draw4, draw4=draw1 ] endmodule\r\n\r\n// formulas/labels for use in properties:\r\n\r\n// number of processes in critical section\r\nformula num_procs_in_crit = (p1=2?1:0)+(p2=2?1:0)+(p3=2?1:0)+(p4=2?1:0);\r\n\r\n// one of the processes is trying\r\nlabel \"one_trying\" = p1=1|p2=1|p3=1|p4=1;\r\n\r\n// one of the processes is in the critical section\r\nlabel \"one_critical\" = p1=2|p2=2|p3=2|p4=2;\r\n\r\n// maximum current draw of the processes\r\nformula maxb = max(b1,b2,b3,b4);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin5.nm",
    "content": "// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\r\n\r\n// to remove the need for fairness constraints for this model it is sufficent\r\n// to remove the self loops from the model \r\n\r\n// the step corresponding to a process making a draw has been split into two steps\r\n// to allow us to identify states where a process will draw without knowing the value\r\n// randomly drawn\r\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\r\n// (i.e. no other process can move one the first step has been made)\r\n// as for example otherwise an adversary can prevent the process from actually drawing\r\n// in the current round by not scheduling it after it has performed the first step\r\n\r\nmdp\r\n\r\n// size of shared counter\r\nconst int K = 7; // 4+ceil(log_2 N)\r\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\r\n// formula to keep drawing phase atomic\r\n// (a process can only move if no other process is in the middle of drawing)\r\nformula go = (draw2=0&draw3=0&draw4=0&draw5=0);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\r\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\r\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 -> 0.5 : (b1'=1) & (r1'=r) & (b'=max(b,1)) & (draw1'=0)\r\n\t         + 0.25 : (b1'=2) & (r1'=r) & (b'=max(b,2)) & (draw1'=0)\r\n\t         + 0.125 : (b1'=3) & (r1'=r) & (b'=max(b,3)) & (draw1'=0)\r\n\t         + 0.0625 : (b1'=4) & (r1'=r) & (b'=max(b,4)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=5) & (r1'=r) & (b'=max(b,5)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=6) & (r1'=r) & (b'=max(b,6)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=7) & (r1'=r) & (b'=max(b,7)) & (draw1'=0);\r\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule process2 = process1 [p1=p2, b1=b2, r1=r2, draw1=draw2, draw2=draw1 ] endmodule\r\nmodule process3 = process1 [p1=p3, b1=b3, r1=r3, draw1=draw3, draw3=draw1 ] endmodule\r\nmodule process4 = process1 [p1=p4, b1=b4, r1=r4, draw1=draw4, draw4=draw1 ] endmodule\r\nmodule process5 = process1 [p1=p5, b1=b5, r1=r5, draw1=draw5, draw5=draw1 ] endmodule\r\n\r\n// formulas/labels for use in properties:\r\n\r\n// number of processes in critical section\r\nformula num_procs_in_crit = (p1=2?1:0)+(p2=2?1:0)+(p3=2?1:0)+(p4=2?1:0)+(p5=2?1:0);\r\n\r\n// one of the processes is trying\r\nlabel \"one_trying\" = p1=1|p2=1|p3=1|p4=1|p5=1;\r\n\r\n// one of the processes is in the critical section\r\nlabel \"one_critical\" = p1=2|p2=2|p3=2|p4=2|p5=2;\r\n\r\n// maximum current draw of the processes\r\nformula maxb = max(b1,b2,b3,b4,b5);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin6.nm",
    "content": "// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\r\n\r\n// to remove the need for fairness constraints for this model it is sufficent\r\n// to remove the self loops from the model \r\n\r\n// the step corresponding to a process making a draw has been split into two steps\r\n// to allow us to identify states where a process will draw without knowing the value\r\n// randomly drawn\r\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\r\n// (i.e. no other process can move one the first step has been made)\r\n// as for example otherwise an adversary can prevent the process from actually drawing\r\n// in the current round by not scheduling it after it has performed the first step\r\n\r\nmdp\r\n\r\n// size of shared counter\r\nconst int K = 7; // 4+ceil(log_2 N)\r\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\r\n// formula to keep drawing phase atomic\r\n// (a process can only move if no other process is in the middle of drawing)\r\nformula go = (draw2=0&draw3=0&draw4=0&draw5=0&draw6=0);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\r\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\r\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 -> 0.5 : (b1'=1) & (r1'=r) & (b'=max(b,1)) & (draw1'=0)\r\n\t         + 0.25 : (b1'=2) & (r1'=r) & (b'=max(b,2)) & (draw1'=0)\r\n\t         + 0.125 : (b1'=3) & (r1'=r) & (b'=max(b,3)) & (draw1'=0)\r\n\t         + 0.0625 : (b1'=4) & (r1'=r) & (b'=max(b,4)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=5) & (r1'=r) & (b'=max(b,5)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=6) & (r1'=r) & (b'=max(b,6)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=7) & (r1'=r) & (b'=max(b,7)) & (draw1'=0);\r\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule process2 = process1 [p1=p2, b1=b2, r1=r2, draw1=draw2, draw2=draw1 ] endmodule\r\nmodule process3 = process1 [p1=p3, b1=b3, r1=r3, draw1=draw3, draw3=draw1 ] endmodule\r\nmodule process4 = process1 [p1=p4, b1=b4, r1=r4, draw1=draw4, draw4=draw1 ] endmodule\r\nmodule process5 = process1 [p1=p5, b1=b5, r1=r5, draw1=draw5, draw5=draw1 ] endmodule\r\nmodule process6 = process1 [p1=p6, b1=b6, r1=r6, draw1=draw6, draw6=draw1 ] endmodule\r\n\r\n// formulas/labels for use in properties:\r\n\r\n// number of processes in critical section\r\nformula num_procs_in_crit = (p1=2?1:0)+(p2=2?1:0)+(p3=2?1:0)+(p4=2?1:0)+(p5=2?1:0)+(p6=2?1:0);\r\n\r\n// one of the processes is trying\r\nlabel \"one_trying\" = p1=1|p2=1|p3=1|p4=1|p5=1|p6=1;\r\n\r\n// one of the processes is in the critical section\r\nlabel \"one_critical\" = p1=2|p2=2|p3=2|p4=2|p5=2|p6=2;\r\n\r\n// maximum current draw of the processes\r\nformula maxb = max(b1,b2,b3,b4,b5,b6);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin7.nm",
    "content": "// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\r\n\r\n// to remove the need for fairness constraints for this model it is sufficent\r\n// to remove the self loops from the model \r\n\r\n// the step corresponding to a process making a draw has been split into two steps\r\n// to allow us to identify states where a process will draw without knowing the value\r\n// randomly drawn\r\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\r\n// (i.e. no other process can move one the first step has been made)\r\n// as for example otherwise an adversary can prevent the process from actually drawing\r\n// in the current round by not scheduling it after it has performed the first step\r\n\r\nmdp\r\n\r\n// size of shared counter\r\nconst int K = 7; // 4+ceil(log_2 N)\r\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\r\n// formula to keep drawing phase atomic\r\n// (a process can only move if no other process is in the middle of drawing)\r\nformula go = (draw2=0&draw3=0&draw4=0&draw5=0&draw6=0&draw7=0);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\r\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\r\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 -> 0.5 : (b1'=1) & (r1'=r) & (b'=max(b,1)) & (draw1'=0)\r\n\t         + 0.25 : (b1'=2) & (r1'=r) & (b'=max(b,2)) & (draw1'=0)\r\n\t         + 0.125 : (b1'=3) & (r1'=r) & (b'=max(b,3)) & (draw1'=0)\r\n\t         + 0.0625 : (b1'=4) & (r1'=r) & (b'=max(b,4)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=5) & (r1'=r) & (b'=max(b,5)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=6) & (r1'=r) & (b'=max(b,6)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=7) & (r1'=r) & (b'=max(b,7)) & (draw1'=0);\r\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule process2 = process1 [p1=p2, b1=b2, r1=r2, draw1=draw2, draw2=draw1 ] endmodule\r\nmodule process3 = process1 [p1=p3, b1=b3, r1=r3, draw1=draw3, draw3=draw1 ] endmodule\r\nmodule process4 = process1 [p1=p4, b1=b4, r1=r4, draw1=draw4, draw4=draw1 ] endmodule\r\nmodule process5 = process1 [p1=p5, b1=b5, r1=r5, draw1=draw5, draw5=draw1 ] endmodule\r\nmodule process6 = process1 [p1=p6, b1=b6, r1=r6, draw1=draw6, draw6=draw1 ] endmodule\r\nmodule process7 = process1 [p1=p7, b1=b7, r1=r7, draw1=draw7, draw7=draw1 ] endmodule\r\n\r\n// formulas/labels for use in properties:\r\n\r\n// number of processes in critical section\r\nformula num_procs_in_crit = (p1=2?1:0)+(p2=2?1:0)+(p3=2?1:0)+(p4=2?1:0)+(p5=2?1:0)+(p6=2?1:0)+(p7=2?1:0);\r\n\r\n// one of the processes is trying\r\nlabel \"one_trying\" = p1=1|p2=1|p3=1|p4=1|p5=1|p6=1|p7=1;\r\n\r\n// one of the processes is in the critical section\r\nlabel \"one_critical\" = p1=2|p2=2|p3=2|p4=2|p5=2|p6=2|p7=2;\r\n\r\n// maximum current draw of the processes\r\nformula maxb = max(b1,b2,b3,b4,b5,b6,b7);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin8.nm",
    "content": "// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\r\n\r\n// to remove the need for fairness constraints for this model it is sufficent\r\n// to remove the self loops from the model \r\n\r\n// the step corresponding to a process making a draw has been split into two steps\r\n// to allow us to identify states where a process will draw without knowing the value\r\n// randomly drawn\r\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\r\n// (i.e. no other process can move one the first step has been made)\r\n// as for example otherwise an adversary can prevent the process from actually drawing\r\n// in the current round by not scheduling it after it has performed the first step\r\n\r\nmdp\r\n\r\n// size of shared counter\r\nconst int K = 7; // 4+ceil(log_2 N)\r\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\r\n// formula to keep drawing phase atomic\r\n// (a process can only move if no other process is in the middle of drawing)\r\nformula go = (draw2=0&draw3=0&draw4=0&draw5=0&draw6=0&draw7=0&draw8=0);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\r\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\r\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 -> 0.5 : (b1'=1) & (r1'=r) & (b'=max(b,1)) & (draw1'=0)\r\n\t         + 0.25 : (b1'=2) & (r1'=r) & (b'=max(b,2)) & (draw1'=0)\r\n\t         + 0.125 : (b1'=3) & (r1'=r) & (b'=max(b,3)) & (draw1'=0)\r\n\t         + 0.0625 : (b1'=4) & (r1'=r) & (b'=max(b,4)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=5) & (r1'=r) & (b'=max(b,5)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=6) & (r1'=r) & (b'=max(b,6)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=7) & (r1'=r) & (b'=max(b,7)) & (draw1'=0);\r\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule process2 = process1 [p1=p2, b1=b2, r1=r2, draw1=draw2, draw2=draw1 ] endmodule\r\nmodule process3 = process1 [p1=p3, b1=b3, r1=r3, draw1=draw3, draw3=draw1 ] endmodule\r\nmodule process4 = process1 [p1=p4, b1=b4, r1=r4, draw1=draw4, draw4=draw1 ] endmodule\r\nmodule process5 = process1 [p1=p5, b1=b5, r1=r5, draw1=draw5, draw5=draw1 ] endmodule\r\nmodule process6 = process1 [p1=p6, b1=b6, r1=r6, draw1=draw6, draw6=draw1 ] endmodule\r\nmodule process7 = process1 [p1=p7, b1=b7, r1=r7, draw1=draw7, draw7=draw1 ] endmodule\r\nmodule process8 = process1 [p1=p8, b1=b8, r1=r8, draw1=draw8, draw8=draw1 ] endmodule\r\n\r\n// formulas/labels for use in properties:\r\n\r\n// number of processes in critical section\r\nformula num_procs_in_crit = (p1=2?1:0)+(p2=2?1:0)+(p3=2?1:0)+(p4=2?1:0)+(p5=2?1:0)+(p6=2?1:0)+(p7=2?1:0)+(p8=2?1:0);\r\n\r\n// one of the processes is trying\r\nlabel \"one_trying\" = p1=1|p2=1|p3=1|p4=1|p5=1|p6=1|p7=1|p8=1;\r\n\r\n// one of the processes is in the critical section\r\nlabel \"one_critical\" = p1=2|p2=2|p3=2|p4=2|p5=2|p6=2|p7=2|p8=2;\r\n\r\n// maximum current draw of the processes\r\nformula maxb = max(b1,b2,b3,b4,b5,b6,b7,b8);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/rabin/rabin9.nm",
    "content": "// N-processor mutual exclusion [Rab82]\r\n// gxn/dxp 03/12/08\r\n\r\n// to remove the need for fairness constraints for this model it is sufficent\r\n// to remove the self loops from the model \r\n\r\n// the step corresponding to a process making a draw has been split into two steps\r\n// to allow us to identify states where a process will draw without knowing the value\r\n// randomly drawn\r\n// to correctly model the protocol and prevent erroneous behaviour, the two steps are atomic\r\n// (i.e. no other process can move one the first step has been made)\r\n// as for example otherwise an adversary can prevent the process from actually drawing\r\n// in the current round by not scheduling it after it has performed the first step\r\n\r\nmdp\r\n\r\n// size of shared counter\r\nconst int K = 8; // 4+ceil(log_2 N)\r\n\r\n// global variables (all modules can read and write)\r\nglobal c : [0..1]; // 0/1 critical section free/taken\r\nglobal b : [0..K]; // current highest draw\r\nglobal r : [1..2]; // current round\r\n\r\n// formula for process 1 drawing\r\nformula draw = p1=1 & (b<b1 | r!=r1);\r\n\r\n// formula to keep drawing phase atomic\r\n// (a process can only move if no other process is in the middle of drawing)\r\nformula go = (draw2=0&draw3=0&draw4=0&draw5=0&draw6=0&draw7=0&draw8=0&draw9=0);\r\n\r\nmodule process1\r\n\r\n\tp1 : [0..2]; // local state\r\n\t//  0 remainder\r\n\t//  1 trying\r\n\t//  2 critical section\r\n\tb1 : [0..K]; // current draw: bi\r\n\tr1 : [0..2]; // current round: ri\r\n\tdraw1 : [0..1]; // performed first step of drawing phase\r\n\r\n\t// remain in remainder\r\n\t// [] go & p1=0 -> (p1'=0);\r\n\t// enter trying\r\n\t[] go & p1=0 -> (p1'=1);\r\n\t// make a draw\r\n\t[] go & draw & draw1=0 -> (draw1'=1);\r\n\t[] draw1=1 -> 0.5 : (b1'=1) & (r1'=r) & (b'=max(b,1)) & (draw1'=0)\r\n\t         + 0.25 : (b1'=2) & (r1'=r) & (b'=max(b,2)) & (draw1'=0)\r\n\t         + 0.125 : (b1'=3) & (r1'=r) & (b'=max(b,3)) & (draw1'=0)\r\n\t         + 0.0625 : (b1'=4) & (r1'=r) & (b'=max(b,4)) & (draw1'=0)\r\n\t         + 0.03125 : (b1'=5) & (r1'=r) & (b'=max(b,5)) & (draw1'=0)\r\n\t         + 0.015625 : (b1'=6) & (r1'=r) & (b'=max(b,6)) & (draw1'=0)\r\n\t         + 0.0078125 : (b1'=7) & (r1'=r) & (b'=max(b,7)) & (draw1'=0)\r\n\t         + 0.0078125 : (b1'=8) & (r1'=r) & (b'=max(b,8)) & (draw1'=0);\r\n\t// enter critical section and randomly set r to 1 or 2\r\n\t[] go & p1=1 & b=b1 & r=r1 & c=0 -> 0.5 : (r'=1) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2)\r\n\t                                  + 0.5 : (r'=2) & (c'=1) & (b'=0) & (b1'=0) & (r1'=0) & (p1'=2);\r\n\t// loop when trying and cannot make a draw or enter critical section\r\n\t// [] go & p1=1 & r1=r & b1<=b & ((c=0 & b1!=b) | c=1) -> (p1'=p1);\r\n\t// leave crictical section\r\n\t[] go & p1=2 -> (p1'=0) & (c'=0);\r\n\t// stay in critical section\r\n\t// [] go & p1=2 -> (p1'=2);\r\n\t\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule process2 = process1 [p1=p2, b1=b2, r1=r2, draw1=draw2, draw2=draw1 ] endmodule\r\nmodule process3 = process1 [p1=p3, b1=b3, r1=r3, draw1=draw3, draw3=draw1 ] endmodule\r\nmodule process4 = process1 [p1=p4, b1=b4, r1=r4, draw1=draw4, draw4=draw1 ] endmodule\r\nmodule process5 = process1 [p1=p5, b1=b5, r1=r5, draw1=draw5, draw5=draw1 ] endmodule\r\nmodule process6 = process1 [p1=p6, b1=b6, r1=r6, draw1=draw6, draw6=draw1 ] endmodule\r\nmodule process7 = process1 [p1=p7, b1=b7, r1=r7, draw1=draw7, draw7=draw1 ] endmodule\r\nmodule process8 = process1 [p1=p8, b1=b8, r1=r8, draw1=draw8, draw8=draw1 ] endmodule\r\nmodule process9 = process1 [p1=p9, b1=b9, r1=r9, draw1=draw9, draw9=draw1 ] endmodule\r\n\r\n// formulas/labels for use in properties:\r\n\r\n// number of processes in critical section\r\nformula num_procs_in_crit = (p1=2?1:0)+(p2=2?1:0)+(p3=2?1:0)+(p4=2?1:0)+(p5=2?1:0)+(p6=2?1:0)+(p7=2?1:0)+(p8=2?1:0)+(p9=2?1:0);\r\n\r\n// one of the processes is trying\r\nlabel \"one_trying\" = p1=1|p2=1|p3=1|p4=1|p5=1|p6=1|p7=1|p8=1|p9=1;\r\n\r\n// one of the processes is in the critical section\r\nlabel \"one_critical\" = p1=2|p2=2|p3=2|p4=2|p5=2|p6=2|p7=2|p8=2|p9=2;\r\n\r\n// maximum current draw of the processes\r\nformula maxb = max(b1,b2,b3,b4,b5,b6,b7,b8,b9);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 5 7 9 11 )\n\techo \"Generating for N=$N\"\n\tprismpp .beauquierN.nm.pp $N >! beauquier$N.nm\n\tunix2dos beauquier$N.nm\nend\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/.beauquierN.nm.pp",
    "content": "#const N#\r\n// self stabilisation algorithm Beauquier, Gradinariu and Johnen\r\n// gxn/dxp 18/07/02\r\n\r\nmdp\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\td1 : bool; // probabilistic variable\r\n\tp1 : bool; // deterministic variable\r\n\t\r\n\t[] d1=d#N# &  p1=p#N# -> 0.5 : (d1'=!d1) & (p1'=p1) + 0.5 : (d1'=!d1) & (p1'=!p1);\r\n\t[] d1=d#N# & !p1=p#N# -> (d1'=!d1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\n#for i=2:N#\r\nmodule process#i# = process1 [ p1=p#i#, p#N#=p#i-1#, d1=d#i#, d#N#=d#i-1# ] endmodule\r\n#end#\r\n\r\n// cost - 1 in each state (expected steps)\nrewards \"steps\"\n\ttrue : 1;\nendrewards\n\n// initial states - any state with more than 1 token, that is all states\r\ninit\n\ttrue\nendinit\n\n// formula, for use in properties: number of tokens\nformula num_tokens = #+ i=1:N#(p#i#=p#func(mod, i, N)+1#?1:0)#end#;\n\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/README.txt",
    "content": "This case study is based on Beauquier, Gradinariu and Johnen's self-stabilising algorithm [BGJ99].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/self-stabilisation.php\r\n\r\n=====================================================================================\r\n\r\n[BGJ99]\r\nJ. Beauquier, M. Gradinariu and C. Johnen\r\nMemory space requirements for self-stabilizing leader election protocols\r\nIn Proc. ACM Symposium on Principles of Distributed Computing, pp. 199-208, ACM Press, 1999\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/auto",
    "content": "#!/bin/csh\n\nprism beauquier3.nm beauquier.pctl -prop 1 -const k=0,K=0\nprism beauquier3.nm beauquier.pctl -prop 2 -const k=0,K=0 -m\nprism beauquier3.nm beauquier.pctl -prop 3 -const k=1:2:3,K=0 -m\nprism beauquier3.nm beauquier.pctl -prop 4 -const k=1:2:3,K=0 -m\nprism beauquier3.nm beauquier.pctl -prop 5 -const k=3,K=1:1:100 -m\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/beauquier.pctl",
    "content": "const int k; // number of tokens\nconst int K; // number of steps\n\n// labels\nlabel \"k_tokens\" = num_tokens=k; // configurations with k tokens\nlabel \"stable\" = num_tokens=1;   // stable configurations (1 token)\n\n// From any configuration, a stable configuration is reached with probability 1\nfilter(forall, \"init\" => P>=1 [ F \"stable\" ])\n\n// Maximum expected time to reach a stable configuration (for all configurations)\nRmax=? [ F \"stable\" {\"init\"}{max} ]\n\n// Maximum/minimum expected time to reach a stable configuration (for all k-token configurations)\nRmax=? [ F \"stable\" {\"k_tokens\"}{max} ]\nRmin=? [ F \"stable\" {\"k_tokens\"}{min} ]\n\n// Minimum probability reached a stable configuration within K steps (for all configurations)\nPmin=? [ F<=K \"stable\" {\"init\"}{min} ]\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/beauquier11.nm",
    "content": "// self stabilisation algorithm Beauquier, Gradinariu and Johnen\r\n// gxn/dxp 18/07/02\r\n\r\nmdp\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\td1 : bool; // probabilistic variable\r\n\tp1 : bool; // deterministic variable\r\n\t\r\n\t[] d1=d11 &  p1=p11 -> 0.5 : (d1'=!d1) & (p1'=p1) + 0.5 : (d1'=!d1) & (p1'=!p1);\r\n\t[] d1=d11 & !p1=p11 -> (d1'=!d1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ p1=p2, p11=p1, d1=d2, d11=d1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p11=p2, d1=d3, d11=d2 ] endmodule\r\nmodule process4 = process1 [ p1=p4, p11=p3, d1=d4, d11=d3 ] endmodule\r\nmodule process5 = process1 [ p1=p5, p11=p4, d1=d5, d11=d4 ] endmodule\r\nmodule process6 = process1 [ p1=p6, p11=p5, d1=d6, d11=d5 ] endmodule\r\nmodule process7 = process1 [ p1=p7, p11=p6, d1=d7, d11=d6 ] endmodule\r\nmodule process8 = process1 [ p1=p8, p11=p7, d1=d8, d11=d7 ] endmodule\r\nmodule process9 = process1 [ p1=p9, p11=p8, d1=d9, d11=d8 ] endmodule\r\nmodule process10 = process1 [ p1=p10, p11=p9, d1=d10, d11=d9 ] endmodule\r\nmodule process11 = process1 [ p1=p11, p11=p10, d1=d11, d11=d10 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// initial states - any state with more than 1 token, that is all states\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\nformula num_tokens = (p1=p2?1:0)+(p2=p3?1:0)+(p3=p4?1:0)+(p4=p5?1:0)+(p5=p6?1:0)+(p6=p7?1:0)+(p7=p8?1:0)+(p8=p9?1:0)+(p9=p10?1:0)+(p10=p11?1:0)+(p11=p1?1:0);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/beauquier3.nm",
    "content": "// self stabilisation algorithm Beauquier, Gradinariu and Johnen\r\n// gxn/dxp 18/07/02\r\n\r\nmdp\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\td1 : bool; // probabilistic variable\r\n\tp1 : bool; // deterministic variable\r\n\t\r\n\t[] d1=d3 &  p1=p3 -> 0.5 : (d1'=!d1) & (p1'=p1) + 0.5 : (d1'=!d1) & (p1'=!p1);\r\n\t[] d1=d3 & !p1=p3 -> (d1'=!d1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ p1=p2, p3=p1, d1=d2, d3=d1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p3=p2, d1=d3, d3=d2 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// initial states - any state with more than 1 token, that is all states\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\nformula num_tokens = (p1=p2?1:0)+(p2=p3?1:0)+(p3=p1?1:0);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/beauquier5.nm",
    "content": "// self stabilisation algorithm Beauquier, Gradinariu and Johnen\r\n// gxn/dxp 18/07/02\r\n\r\nmdp\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\td1 : bool; // probabilistic variable\r\n\tp1 : bool; // deterministic variable\r\n\t\r\n\t[] d1=d5 &  p1=p5 -> 0.5 : (d1'=!d1) & (p1'=p1) + 0.5 : (d1'=!d1) & (p1'=!p1);\r\n\t[] d1=d5 & !p1=p5 -> (d1'=!d1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ p1=p2, p5=p1, d1=d2, d5=d1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p5=p2, d1=d3, d5=d2 ] endmodule\r\nmodule process4 = process1 [ p1=p4, p5=p3, d1=d4, d5=d3 ] endmodule\r\nmodule process5 = process1 [ p1=p5, p5=p4, d1=d5, d5=d4 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// initial states - any state with more than 1 token, that is all states\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\nformula num_tokens = (p1=p2?1:0)+(p2=p3?1:0)+(p3=p4?1:0)+(p4=p5?1:0)+(p5=p1?1:0);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/beauquier7.nm",
    "content": "// self stabilisation algorithm Beauquier, Gradinariu and Johnen\r\n// gxn/dxp 18/07/02\r\n\r\nmdp\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\td1 : bool; // probabilistic variable\r\n\tp1 : bool; // deterministic variable\r\n\t\r\n\t[] d1=d7 &  p1=p7 -> 0.5 : (d1'=!d1) & (p1'=p1) + 0.5 : (d1'=!d1) & (p1'=!p1);\r\n\t[] d1=d7 & !p1=p7 -> (d1'=!d1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ p1=p2, p7=p1, d1=d2, d7=d1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p7=p2, d1=d3, d7=d2 ] endmodule\r\nmodule process4 = process1 [ p1=p4, p7=p3, d1=d4, d7=d3 ] endmodule\r\nmodule process5 = process1 [ p1=p5, p7=p4, d1=d5, d7=d4 ] endmodule\r\nmodule process6 = process1 [ p1=p6, p7=p5, d1=d6, d7=d5 ] endmodule\r\nmodule process7 = process1 [ p1=p7, p7=p6, d1=d7, d7=d6 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// initial states - any state with more than 1 token, that is all states\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\nformula num_tokens = (p1=p2?1:0)+(p2=p3?1:0)+(p3=p4?1:0)+(p4=p5?1:0)+(p5=p6?1:0)+(p6=p7?1:0)+(p7=p1?1:0);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/beauquier/beauquier9.nm",
    "content": "// self stabilisation algorithm Beauquier, Gradinariu and Johnen\r\n// gxn/dxp 18/07/02\r\n\r\nmdp\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\td1 : bool; // probabilistic variable\r\n\tp1 : bool; // deterministic variable\r\n\t\r\n\t[] d1=d9 &  p1=p9 -> 0.5 : (d1'=!d1) & (p1'=p1) + 0.5 : (d1'=!d1) & (p1'=!p1);\r\n\t[] d1=d9 & !p1=p9 -> (d1'=!d1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ p1=p2, p9=p1, d1=d2, d9=d1 ] endmodule\r\nmodule process3 = process1 [ p1=p3, p9=p2, d1=d3, d9=d2 ] endmodule\r\nmodule process4 = process1 [ p1=p4, p9=p3, d1=d4, d9=d3 ] endmodule\r\nmodule process5 = process1 [ p1=p5, p9=p4, d1=d5, d9=d4 ] endmodule\r\nmodule process6 = process1 [ p1=p6, p9=p5, d1=d6, d9=d5 ] endmodule\r\nmodule process7 = process1 [ p1=p7, p9=p6, d1=d7, d9=d6 ] endmodule\r\nmodule process8 = process1 [ p1=p8, p9=p7, d1=d8, d9=d7 ] endmodule\r\nmodule process9 = process1 [ p1=p9, p9=p8, d1=d9, d9=d8 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// initial states - any state with more than 1 token, that is all states\r\ninit\r\n\ttrue\r\nendinit\r\n\r\n// formula, for use in properties: number of tokens\r\nformula num_tokens = (p1=p2?1:0)+(p2=p3?1:0)+(p3=p4?1:0)+(p4=p5?1:0)+(p5=p6?1:0)+(p6=p7?1:0)+(p7=p8?1:0)+(p8=p9?1:0)+(p9=p1?1:0);\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/.autopp",
    "content": "#!/bin/csh\n\nforeach N ( 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 )\n\techo \"Generating for N=$N\"\n\tprismpp .ijN.nm.pp $N >! ij$N.nm\n\tunix2dos ij$N.nm\nend\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/.ijN.nm.pp",
    "content": "#const N#\r\n// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\n#for i=1:N#\r\nglobal q#i#  : [0..1];\r\n#end#\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q#N#'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\n#for i=2:N#\r\nmodule process#i# = process1 [ q1=q#i#, q2=q#func(mod,i,N)+1#, q#N#=q#i-1# ] endmodule\r\n#end#\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = #+ i=1:N#q#i##end#;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/README.txt",
    "content": "This case study is based on Israeli and Jalfon's self-stabilising algorithm [IJ90].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/self-stabilisation.php\r\n\r\n=====================================================================================\r\n\r\n[IJ90]\r\nA. Israeli and M. Jalfon\r\nToken management schemes and random walks yeild self-stabilizating mutual exclusion\r\nIn Proc. ACM Symposium on Principles of Distributed Computing, pp. 119-131, 1990\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/auto",
    "content": "#!/bin/csh\n\nprism ij3.nm ij.pctl -prop 1 -const k=0,K=0\nprism ij3.nm ij.pctl -prop 2 -const k=0,K=0 -m\nprism ij3.nm ij.pctl -prop 3 -const k=1:1:3,K=0 -m\nprism ij3.nm ij.pctl -prop 4 -const k=1:1:3,K=0 -m\nprism ij3.nm ij.pctl -prop 5 -const k=0,K=1:1:100 -m\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij.pctl",
    "content": "const int k; // number of tokens\nconst int K; // number of steps\n\n// labels\nlabel \"k_tokens\" = num_tokens=k; // configurations with k tokens\n\n// From any configuration, a stable configuration is reached with probability 1\nfilter(forall, \"init\" => P>=1 [ F \"stable\" ])\n\n// Maximum expected time to reach a stable configuration (for all configurations)\nRmax=? [ F \"stable\" {\"init\"}{max} ]\n\n// Maximum/minimum expected time to reach a stable configuration (for all k-token configurations)\nRmax=? [ F \"stable\" {\"k_tokens\"}{max} ]\nRmin=? [ F \"stable\" {\"k_tokens\"}{min} ]\n\n// Minimum probability reached a stable configuration within K steps (for all configurations)\nPmin=? [ F<=K \"stable\" {\"init\"}{min} ]\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij10.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q10'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q10=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q10=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q10=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q10=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q10=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q10=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q10=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q10=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q1, q10=q9 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij11.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q11'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q11=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q11=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q11=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q11=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q11=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q11=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q11=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q11=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q11=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q1, q11=q10 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij12.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q12'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q12=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q12=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q12=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q12=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q12=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q12=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q12=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q12=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q12=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q12=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q1, q12=q11 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij13.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q13'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q13=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q13=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q13=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q13=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q13=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q13=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q13=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q13=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q13=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q13=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q13=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q1, q13=q12 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij14.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\nglobal q14  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q14'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q14=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q14=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q14=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q14=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q14=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q14=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q14=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q14=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q14=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q14=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q14=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q14, q14=q12 ] endmodule\r\nmodule process14 = process1 [ q1=q14, q2=q1, q14=q13 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13+q14;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij15.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\nglobal q14  : [0..1];\r\nglobal q15  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q15'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q15=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q15=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q15=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q15=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q15=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q15=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q15=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q15=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q15=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q15=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q15=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q14, q15=q12 ] endmodule\r\nmodule process14 = process1 [ q1=q14, q2=q15, q15=q13 ] endmodule\r\nmodule process15 = process1 [ q1=q15, q2=q1, q15=q14 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13+q14+q15;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij16.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\nglobal q14  : [0..1];\r\nglobal q15  : [0..1];\r\nglobal q16  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q16'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q16=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q16=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q16=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q16=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q16=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q16=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q16=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q16=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q16=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q16=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q16=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q14, q16=q12 ] endmodule\r\nmodule process14 = process1 [ q1=q14, q2=q15, q16=q13 ] endmodule\r\nmodule process15 = process1 [ q1=q15, q2=q16, q16=q14 ] endmodule\r\nmodule process16 = process1 [ q1=q16, q2=q1, q16=q15 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13+q14+q15+q16;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij17.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\nglobal q14  : [0..1];\r\nglobal q15  : [0..1];\r\nglobal q16  : [0..1];\r\nglobal q17  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q17'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q17=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q17=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q17=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q17=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q17=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q17=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q17=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q17=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q17=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q17=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q17=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q14, q17=q12 ] endmodule\r\nmodule process14 = process1 [ q1=q14, q2=q15, q17=q13 ] endmodule\r\nmodule process15 = process1 [ q1=q15, q2=q16, q17=q14 ] endmodule\r\nmodule process16 = process1 [ q1=q16, q2=q17, q17=q15 ] endmodule\r\nmodule process17 = process1 [ q1=q17, q2=q1, q17=q16 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13+q14+q15+q16+q17;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij18.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\nglobal q14  : [0..1];\r\nglobal q15  : [0..1];\r\nglobal q16  : [0..1];\r\nglobal q17  : [0..1];\r\nglobal q18  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q18'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q18=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q18=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q18=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q18=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q18=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q18=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q18=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q18=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q18=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q18=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q18=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q14, q18=q12 ] endmodule\r\nmodule process14 = process1 [ q1=q14, q2=q15, q18=q13 ] endmodule\r\nmodule process15 = process1 [ q1=q15, q2=q16, q18=q14 ] endmodule\r\nmodule process16 = process1 [ q1=q16, q2=q17, q18=q15 ] endmodule\r\nmodule process17 = process1 [ q1=q17, q2=q18, q18=q16 ] endmodule\r\nmodule process18 = process1 [ q1=q18, q2=q1, q18=q17 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13+q14+q15+q16+q17+q18;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij19.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\nglobal q14  : [0..1];\r\nglobal q15  : [0..1];\r\nglobal q16  : [0..1];\r\nglobal q17  : [0..1];\r\nglobal q18  : [0..1];\r\nglobal q19  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q19'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q19=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q19=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q19=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q19=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q19=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q19=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q19=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q19=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q19=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q19=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q19=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q14, q19=q12 ] endmodule\r\nmodule process14 = process1 [ q1=q14, q2=q15, q19=q13 ] endmodule\r\nmodule process15 = process1 [ q1=q15, q2=q16, q19=q14 ] endmodule\r\nmodule process16 = process1 [ q1=q16, q2=q17, q19=q15 ] endmodule\r\nmodule process17 = process1 [ q1=q17, q2=q18, q19=q16 ] endmodule\r\nmodule process18 = process1 [ q1=q18, q2=q19, q19=q17 ] endmodule\r\nmodule process19 = process1 [ q1=q19, q2=q1, q19=q18 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13+q14+q15+q16+q17+q18+q19;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij20.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\nglobal q14  : [0..1];\r\nglobal q15  : [0..1];\r\nglobal q16  : [0..1];\r\nglobal q17  : [0..1];\r\nglobal q18  : [0..1];\r\nglobal q19  : [0..1];\r\nglobal q20  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q20'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q20=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q20=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q20=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q20=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q20=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q20=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q20=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q20=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q20=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q20=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q20=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q14, q20=q12 ] endmodule\r\nmodule process14 = process1 [ q1=q14, q2=q15, q20=q13 ] endmodule\r\nmodule process15 = process1 [ q1=q15, q2=q16, q20=q14 ] endmodule\r\nmodule process16 = process1 [ q1=q16, q2=q17, q20=q15 ] endmodule\r\nmodule process17 = process1 [ q1=q17, q2=q18, q20=q16 ] endmodule\r\nmodule process18 = process1 [ q1=q18, q2=q19, q20=q17 ] endmodule\r\nmodule process19 = process1 [ q1=q19, q2=q20, q20=q18 ] endmodule\r\nmodule process20 = process1 [ q1=q20, q2=q1, q20=q19 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13+q14+q15+q16+q17+q18+q19+q20;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij21.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\nglobal q10  : [0..1];\r\nglobal q11  : [0..1];\r\nglobal q12  : [0..1];\r\nglobal q13  : [0..1];\r\nglobal q14  : [0..1];\r\nglobal q15  : [0..1];\r\nglobal q16  : [0..1];\r\nglobal q17  : [0..1];\r\nglobal q18  : [0..1];\r\nglobal q19  : [0..1];\r\nglobal q20  : [0..1];\r\nglobal q21  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q21'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q21=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q21=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q21=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q21=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q21=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q21=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q21=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q10, q21=q8 ] endmodule\r\nmodule process10 = process1 [ q1=q10, q2=q11, q21=q9 ] endmodule\r\nmodule process11 = process1 [ q1=q11, q2=q12, q21=q10 ] endmodule\r\nmodule process12 = process1 [ q1=q12, q2=q13, q21=q11 ] endmodule\r\nmodule process13 = process1 [ q1=q13, q2=q14, q21=q12 ] endmodule\r\nmodule process14 = process1 [ q1=q14, q2=q15, q21=q13 ] endmodule\r\nmodule process15 = process1 [ q1=q15, q2=q16, q21=q14 ] endmodule\r\nmodule process16 = process1 [ q1=q16, q2=q17, q21=q15 ] endmodule\r\nmodule process17 = process1 [ q1=q17, q2=q18, q21=q16 ] endmodule\r\nmodule process18 = process1 [ q1=q18, q2=q19, q21=q17 ] endmodule\r\nmodule process19 = process1 [ q1=q19, q2=q20, q21=q18 ] endmodule\r\nmodule process20 = process1 [ q1=q20, q2=q21, q21=q19 ] endmodule\r\nmodule process21 = process1 [ q1=q21, q2=q1, q21=q20 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9+q10+q11+q12+q13+q14+q15+q16+q17+q18+q19+q20+q21;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij3.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q3'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q3=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q1, q3=q2 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij4.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q4'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q4=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q4=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q1, q4=q3 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij5.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q5'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q5=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q5=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q5=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q1, q5=q4 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij6.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q6'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q6=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q6=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q6=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q6=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q1, q6=q5 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij7.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q7'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q7=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q7=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q7=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q7=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q7=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q1, q7=q6 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij8.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q8'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q8=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q8=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q8=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q8=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q8=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q8=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q1, q8=q7 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/self-stabilisation/israeli-jalfon/ij9.nm",
    "content": "// Israeli-Jalfon self stabilising algorithm\r\n// dxp/gxn 10/06/02\r\n\r\nmdp\r\n\r\n// variables to represent whether a process has a token or not\r\n// note they are global because they can be updated by other processes\r\nglobal q1  : [0..1];\r\nglobal q2  : [0..1];\r\nglobal q3  : [0..1];\r\nglobal q4  : [0..1];\r\nglobal q5  : [0..1];\r\nglobal q6  : [0..1];\r\nglobal q7  : [0..1];\r\nglobal q8  : [0..1];\r\nglobal q9  : [0..1];\r\n\r\n// module of process 1\r\nmodule process1\r\n\t\r\n\t[] (q1=1) -> 0.5 : (q1'=0) & (q9'=1) + 0.5 : (q1'=0) & (q2'=1);\r\n\t\r\nendmodule\r\n\r\n// add further processes through renaming\r\nmodule process2 = process1 [ q1=q2, q2=q3, q9=q1 ] endmodule\r\nmodule process3 = process1 [ q1=q3, q2=q4, q9=q2 ] endmodule\r\nmodule process4 = process1 [ q1=q4, q2=q5, q9=q3 ] endmodule\r\nmodule process5 = process1 [ q1=q5, q2=q6, q9=q4 ] endmodule\r\nmodule process6 = process1 [ q1=q6, q2=q7, q9=q5 ] endmodule\r\nmodule process7 = process1 [ q1=q7, q2=q8, q9=q6 ] endmodule\r\nmodule process8 = process1 [ q1=q8, q2=q9, q9=q7 ] endmodule\r\nmodule process9 = process1 [ q1=q9, q2=q1, q9=q8 ] endmodule\r\n\r\n// cost - 1 in each state (expected steps)\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// formula, for use here and in properties: number of tokens\r\nformula num_tokens = q1+q2+q3+q4+q5+q6+q7+q8+q9;\r\n\r\n// label - stable configurations (1 token)\r\nlabel \"stable\" = num_tokens=1;\r\n\r\n// initial states (at least one token)\r\ninit\r\n\tnum_tokens >= 1\r\nendinit\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/wlan/README.txt",
    "content": "This case study concerns the IEEE 802.11 Wireless LAN\n\nWe consider the scenario where two stations trying to send packets simultaneously.\n\nThe PRISM model is taken from [KNS02a] using the integer semantics given in [KNS06]. In the model one time unit\ncorresponds to 50μs and to ensure integer bounds, where neccessary, scaling lower bound constraints down and\nupper bound constraints up to sensure a sound abstraction.\n\r\nFor more information on the probabilistic timed automata see: http://www.prismmodelchecker.org/casestudies/wlan.php\n\nPARAMETERS\n\nwlanK.nm - K is the maximum value of a stations backoff counter where 6 is specified in the standard\nTRANS_TIME_MAX - maximum time to send a packet where (after scaling) 315 specified in the standard\nCOL=2: in collosion model to count number collisions (parameter k in the property files must be less than or equal to COL)\nDEADLINE: in time_bounded model is the deadline\n\n=====================================================================================\n\n[KNS02a]\nM. Kwiatkowska and G. Norman and J. Sproston\nProbabilistic Model Checking of the {IEEE} 802.11 Wireless Local Area Network Protocol\nProc. 2nd Joint International Workshop on Process Algebra and Probabilistic Methods,\nPerformance Modeling and Verification (PAPM/PROBMIV'02)}, volume 2399 of LNCS,\npages 169-187, Springer, 2002.\n\n[KNPS06]\nM. Kwiatkowska, G. Norman, D. Parker and J. Sproston\nPerformance Analysis of Probabilistic Timed Automata using Digital Clocks\nFormal Methods in System Design, 29:33-78, 2006\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/mdps/wlan/auto",
    "content": "#!/bin/csh\n\nprism wlan0.nm wlan.pctl -const TRANS_TIME_MAX=10,k=2 -m\nprism wlan1.nm wlan.pctl -const TRANS_TIME_MAX=10,k=2 -m\nprism wlan2.nm wlan.pctl -const TRANS_TIME_MAX=10,k=2 -m\n#prism wlan3.nm wlan.pctl -const TRANS_TIME_MAX=10,k=2 -m\n#prism wlan4.nm wlan.pctl -const TRANS_TIME_MAX=10,k=2 -m\n#prism wlan5.nm wlan.pctl -const TRANS_TIME_MAX=10,k=2 -m\n#prism wlan6.nm wlan.pctl -const TRANS_TIME_MAX=10,k=2 -m\n\n\n# probability collide\nprism wlan0_collide.nm wlan_collide.pctl -const COL=2,TRANS_TIME_MAX=10,k=2\nprism wlan1_collide.nm wlan_collide.pctl -const COL=2,TRANS_TIME_MAX=10,k=2\nprism wlan2_collide.nm wlan_collide.pctl -const COL=2,TRANS_TIME_MAX=10,k=2\n#prism wlan3_collide.nm wlan_collide.pctl -const COL=2,TRANS_TIME_MAX=10,k=2\n#prism wlan4_collide.nm wlan_collide.pctl -const COL=2,TRANS_TIME_MAX=10,k=2\n#prism wlan5_collide.nm wlan_collide.pctl -const COL=2,TRANS_TIME_MAX=10,k=2\n#prism wlan6_collide.nm wlan_collide.pctl -const COL=2,TRANS_TIME_MAX=10,k=2\n\n# time bounded\nprism wlan0_time_bounded.nm wlan_time_bounded.pctl -const TRANS_TIME_MAX=10,DEADLINE=100 -nopre -m -prop 3\nprism wlan1_time_bounded.nm wlan_time_bounded.pctl -const TRANS_TIME_MAX=10,DEADLINE=100 -nopre -m -prop 3\nprism wlan2_time_bounded.nm wlan_time_bounded.pctl -const TRANS_TIME_MAX=10,DEADLINE=100 -nopre -m -prop 3\n#prism wlan3_time_bounded.nm wlan_time_bounded.pctl -const TRANS_TIME_MAX=10,DEADLINE=100 -nopre -m -prop 3\n#prism wlan4_time_bounded.nm wlan_time_bounded.pctl -const TRANS_TIME_MAX=10,DEADLINE=100 -nopre -m -prop 3\n#prism wlan5_time_bounded.nm wlan_time_bounded.pctl -const TRANS_TIME_MAX=10,DEADLINE=100 -nopre -m -prop 3\n#prism wlan6_time_bounded.nm wlan_time_bounded.pctl -const TRANS_TIME_MAX=10,DEADLINE=100 -nopre -m -prop 3\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan.pctl",
    "content": "// with probability 1, eventually both stations have sent their packet correctly\nP>=1 [ true U s1=12 & s2=12 ];\n\n// maximum probability that either station's backoff counter reaches k\nconst int k;\nPmax=? [ true U bc1=k | bc2=k ];\n\n// maximum expected number of collisions\nR{\"collisions\"}max=? [ F s1=12 & s2=12 ]; // both send correctly\n\n// maximum expected time \nR{\"time\"}max=? [ F s1=12 & s2=12 ]; // both send correctly\nR{\"time\"}max=? [ F s1=12 | s2=12 ]; // either sends correctly\nR{\"time\"}max=? [ F s1=12 ]; // station 1 sends correctly\n\n// maximum expected cost\nR{\"cost\"}max=? [ F s1=12 & s2=12 ]; // both send correctly\nR{\"cost\"}max=? [ F s1=12 | s2=12 ]; // either sends\nR{\"cost\"}max=? [ F s1=12 ]; // station 1 sends correctly\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan0.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =16\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 0;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..1]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..1];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\n\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n// reward structures\n\n// number of collisions\nrewards \"collisions\"\n\t[send1] c1=0 & c2>0 : 1; // station one starts transmitting and station two is already transmitting\n\t[send2] c2=0 & c1>0 : 1; // station two starts transmitting and station one is already transmitting\nendrewards\n\n// reward structure for expected time\n// recall one time unit equals ASLOT(=50μs)\nrewards \"time\"\n\t[time] true : 50;\nendrewards\n\n// reward strcuture for expected cost\n// cost (per time unit) is set to:\n// 1 in locations where the channel is free,\n// 10 in locations where the channel is in use and a message is being sent correctly\n// 1000 in locations where a station is sending a garbled message\n// 2000 in locations where both stations are sending garbled messages\nrewards\t\"cost\"\n\t[time] c1=0 & c2=0 : 50;\n\t[time] c1+c2=1 : 50*10;\n\t[time] c1=1 & c2=1 : 50*20;\n\t[time] c1=0 & c2=2 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=0 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=2 & bc1=0 & bc2=0 : 50*20;\n\t[time] c1=0 & c2=2 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=0 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=2 & (bc1>0 | bc2>0) : 50*2000;\nendrewards\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan0_collide.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// COLLISIONS\nconst int COL; // maximum number of collisions\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =16\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 0;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// number of collisions\n\tcol : [0..COL];\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..1]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..1];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\n\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan0_time_bounded.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =16\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 0;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..1]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..1];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\n\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\nconst int DEADLINE;\n\n// timer\nmodule timer\n\t// global time\n\tt : [0..DEADLINE];\n\t\n\t[time] (t<DEADLINE) -> (t'=min(t+1,DEADLINE));\n\t// loop when time passes DEADLINE to prevent further transitions\n\t[] (t>=DEADLINE) -> (t'=t);\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan1.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =31\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 1;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..1]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// chEck channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n// reward structures\n\n// number of collisions\nrewards \"collisions\"\n\t[send1] c1=0 & c2>0 : 1; // station one starts transmitting and station two is already transmitting\n\t[send2] c2=0 & c1>0 : 1; // station two starts transmitting and station one is already transmitting\nendrewards\n\n// reward structure for expected time\n// recall one time unit equals ASLOT(=50μs)\nrewards \"time\"\n\t[time] true : 50;\nendrewards\n\n// reward strcuture for expected cost\n// cost (per time unit) is set to:\n// 1 in locations where the channel is free,\n// 10 in locations where the channel is in use and a message is being sent correctly\n// 1000 in locations where a station is sending a garbled message\n// 2000 in locations where both stations are sending garbled messages\nrewards\t\"cost\"\n\t[time] c1=0 & c2=0 : 50;\n\t[time] c1+c2=1 : 50*10;\n\t[time] c1=1 & c2=1 : 50*20;\n\t[time] c1=0 & c2=2 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=0 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=2 & bc1=0 & bc2=0 : 50*20;\n\t[time] c1=0 & c2=2 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=0 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=2 & (bc1>0 | bc2>0) : 50*2000;\nendrewards\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan1_collide.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// COLLISIONS\nconst int COL; // maximum number of collisions\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =31\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 1;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// number of collisions\n\tcol : [0..COL];\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..1]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// chEck channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan1_time_bounded.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =31\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 1;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..1]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// chEck channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\nconst int DEADLINE;\n\n// timer\nmodule timer\n\t// global time\n\tt : [0..DEADLINE];\n\t\n\t[time] (t<DEADLINE) -> (t'=min(t+1,DEADLINE));\n\t// loop when time passes DEADLINE to prevent further transitions\n\t[] (t>=DEADLINE) -> (t'=t);\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan2.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =63\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 2;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..3]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n// reward structures\n\n// number of collisions\nrewards \"collisions\"\n\t[send1] c1=0 & c2>0 : 1; // station one starts transmitting and station two is already transmitting\n\t[send2] c2=0 & c1>0 : 1; // station two starts transmitting and station one is already transmitting\nendrewards\n\n// reward structure for expected time\n// recall one time unit equals ASLOT(=50μs)\nrewards \"time\"\n\t[time] true : 50;\nendrewards\n\n// reward strcuture for expected cost\n// cost (per time unit) is set to:\n// 1 in locations where the channel is free,\n// 10 in locations where the channel is in use and a message is being sent correctly\n// 1000 in locations where a station is sending a garbled message\n// 2000 in locations where both stations are sending garbled messages\nrewards\t\"cost\"\n\t[time] c1=0 & c2=0 : 50;\n\t[time] c1+c2=1 : 50*10;\n\t[time] c1=1 & c2=1 : 50*20;\n\t[time] c1=0 & c2=2 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=0 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=2 & bc1=0 & bc2=0 : 50*20;\n\t[time] c1=0 & c2=2 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=0 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=2 & (bc1>0 | bc2>0) : 50*2000;\nendrewards\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan2_collide.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// COLLISIONS\nconst int COL; // maximum number of collisions\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =63\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 2;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// number of collisions\n\tcol : [0..COL];\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..3]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan2_time_bounded.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =63\n// this means that MAX_BACKOFF IS 2\nconst MAX_BACKOFF = 2;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..3]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\nconst int DEADLINE;\n\n// timer\nmodule timer\n\t// global time\n\tt : [0..DEADLINE];\n\t\n\t[time] (t<DEADLINE) -> (t'=min(t+1,DEADLINE));\n\t// loop when time passes DEADLINE to prevent further transitions\n\t[] (t>=DEADLINE) -> (t'=t);\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan3.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =127\n// this means that MAX_BACKOFF IS 3\nconst MAX_BACKOFF = 3;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..7]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n// reward structures\n\n// number of collisions\nrewards \"collisions\"\n\t[send1] c1=0 & c2>0 : 1; // station one starts transmitting and station two is already transmitting\n\t[send2] c2=0 & c1>0 : 1; // station two starts transmitting and station one is already transmitting\nendrewards\n\n// reward structure for expected time\n// recall one time unit equals ASLOT(=50μs)\nrewards \"time\"\n\t[time] true : 50;\nendrewards\n\n// reward strcuture for expected cost\n// cost (per time unit) is set to:\n// 1 in locations where the channel is free,\n// 10 in locations where the channel is in use and a message is being sent correctly\n// 1000 in locations where a station is sending a garbled message\n// 2000 in locations where both stations are sending garbled messages\nrewards\t\"cost\"\n\t[time] c1=0 & c2=0 : 50;\n\t[time] c1+c2=1 : 50*10;\n\t[time] c1=1 & c2=1 : 50*20;\n\t[time] c1=0 & c2=2 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=0 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=2 & bc1=0 & bc2=0 : 50*20;\n\t[time] c1=0 & c2=2 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=0 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=2 & (bc1>0 | bc2>0) : 50*2000;\nendrewards\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan3_collide.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// COLLISIONS\nconst int COL; // maximum number of collisions\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =127\n// this means that MAX_BACKOFF IS 3\nconst MAX_BACKOFF = 3;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// number of collisions\n\tcol : [0..COL];\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..7]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan3_time_bounded.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =127\n// this means that MAX_BACKOFF IS 3\nconst MAX_BACKOFF = 3;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..7]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\nconst int DEADLINE;\n\n// timer\nmodule timer\n\t// global time\n\tt : [0..DEADLINE];\n\t\n\t[time] (t<DEADLINE) -> (t'=min(t+1,DEADLINE));\n\t// loop when time passes DEADLINE to prevent further transitions\n\t[] (t>=DEADLINE) -> (t'=t);\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan4.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =255\n// this means that MAX_BACKOFF IS 4\nconst MAX_BACKOFF = 4;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..15]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n// reward structures\n\n// number of collisions\nrewards \"collisions\"\n\t[send1] c1=0 & c2>0 : 1; // station one starts transmitting and station two is already transmitting\n\t[send2] c2=0 & c1>0 : 1; // station two starts transmitting and station one is already transmitting\nendrewards\n\n// reward structure for expected time\n// recall one time unit equals ASLOT(=50μs)\nrewards \"time\"\n\t[time] true : 50;\nendrewards\n\n// reward strcuture for expected cost\n// cost (per time unit) is set to:\n// 1 in locations where the channel is free,\n// 10 in locations where the channel is in use and a message is being sent correctly\n// 1000 in locations where a station is sending a garbled message\n// 2000 in locations where both stations are sending garbled messages\nrewards\t\"cost\"\n\t[time] c1=0 & c2=0 : 50;\n\t[time] c1+c2=1 : 50*10;\n\t[time] c1=1 & c2=1 : 50*20;\n\t[time] c1=0 & c2=2 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=0 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=2 & bc1=0 & bc2=0 : 50*20;\n\t[time] c1=0 & c2=2 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=0 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=2 & (bc1>0 | bc2>0) : 50*2000;\nendrewards\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan4_collide.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// COLLISIONS\nconst int COL; // maximum number of collisions\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =255\n// this means that MAX_BACKOFF IS 4\nconst MAX_BACKOFF = 4;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// number of collisions\n\tcol : [0..COL];\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..15]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan4_time_bounded.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =255\n// this means that MAX_BACKOFF IS 4\nconst MAX_BACKOFF = 4;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..15]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\nconst int DEADLINE;\n\n// timer\nmodule timer\n\t// global time\n\tt : [0..DEADLINE];\n\t\n\t[time] (t<DEADLINE) -> (t'=min(t+1,DEADLINE));\n\t// loop when time passes DEADLINE to prevent further transitions\n\t[] (t>=DEADLINE) -> (t'=t);\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan5.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =511\n// this means that MAX_BACKOFF IS 5\nconst MAX_BACKOFF = 5;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..31]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 5\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=5 -> 1/32 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t \n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n// reward structures\n\n// number of collisions\nrewards \"collisions\"\n\t[send1] c1=0 & c2>0 : 1; // station one starts transmitting and station two is already transmitting\n\t[send2] c2=0 & c1>0 : 1; // station two starts transmitting and station one is already transmitting\nendrewards\n\n// reward structure for expected time\n// recall one time unit equals ASLOT(=50μs)\nrewards \"time\"\n\t[time] true : 50;\nendrewards\n\n// reward strcuture for expected cost\n// cost (per time unit) is set to:\n// 1 in locations where the channel is free,\n// 10 in locations where the channel is in use and a message is being sent correctly\n// 1000 in locations where a station is sending a garbled message\n// 2000 in locations where both stations are sending garbled messages\nrewards\t\"cost\"\n\t[time] c1=0 & c2=0 : 50;\n\t[time] c1+c2=1 : 50*10;\n\t[time] c1=1 & c2=1 : 50*20;\n\t[time] c1=0 & c2=2 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=0 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=2 & bc1=0 & bc2=0 : 50*20;\n\t[time] c1=0 & c2=2 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=0 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=2 & (bc1>0 | bc2>0) : 50*2000;\nendrewards\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan5_collide.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// COLLISIONS\nconst int COL; // maximum number of collisions\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =511\n// this means that MAX_BACKOFF IS 5\nconst MAX_BACKOFF = 5;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// number of collisions\n\tcol : [0..COL];\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..31]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 5\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=5 -> 1/32 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t \n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan5_time_bounded.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =511\n// this means that MAX_BACKOFF IS 5\nconst MAX_BACKOFF = 5;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..31]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 5\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=5 -> 1/32 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t \n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\nconst int DEADLINE;\n\n// timer\nmodule timer\n\t// global time\n\tt : [0..DEADLINE];\n\t\n\t[time] (t<DEADLINE) -> (t'=min(t+1,DEADLINE));\n\t// loop when time passes DEADLINE to prevent further transitions\n\t[] (t>=DEADLINE) -> (t'=t);\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan6.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =1023\n// this means that MAX_BACKOFF IS 6\nconst MAX_BACKOFF = 6;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..63]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 5\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=5 -> 1/32 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t \n\t// backoff counter 6\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=6 -> 1/64 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=32) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=33) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=34) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=35) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=36) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=37) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=38) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=39) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=40) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=41) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=42) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=43) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=44) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=45) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=46) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=47) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=48) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=49) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=50) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=51) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=52) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=53) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=54) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=55) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=56) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=57) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=58) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=59) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=60) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=61) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=62) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=63) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n// reward structures\n\n// number of collisions\nrewards \"collisions\"\n\t[send1] c1=0 & c2>0 : 1; // station one starts transmitting and station two is already transmitting\n\t[send2] c2=0 & c1>0 : 1; // station two starts transmitting and station one is already transmitting\nendrewards\n\n// reward structure for expected time\n// recall one time unit equals ASLOT(=50μs)\nrewards \"time\"\n\t[time] true : 50;\nendrewards\n\n// reward strcuture for expected cost\n// cost (per time unit) is set to:\n// 1 in locations where the channel is free,\n// 10 in locations where the channel is in use and a message is being sent correctly\n// 1000 in locations where a station is sending a garbled message\n// 2000 in locations where both stations are sending garbled messages\nrewards\t\"cost\"\n\t[time] c1=0 & c2=0 : 50;\n\t[time] c1+c2=1 : 50*10;\n\t[time] c1=1 & c2=1 : 50*20;\n\t[time] c1=0 & c2=2 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=0 & bc1=0 & bc2=0 : 50*10;\n\t[time] c1=2 & c2=2 & bc1=0 & bc2=0 : 50*20;\n\t[time] c1=0 & c2=2 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=0 & (bc1>0 | bc2>0) : 50*1000;\n\t[time] c1=2 & c2=2 & (bc1>0 | bc2>0) : 50*2000;\nendrewards\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan6_collide.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// COLLISIONS\nconst int COL; // maximum number of collisions\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =1023\n// this means that MAX_BACKOFF IS 6\nconst MAX_BACKOFF = 6;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// number of collisions\n\tcol : [0..COL];\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2) & (col'=min(col+1,COL));\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..63]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 5\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=5 -> 1/32 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t \n\t// backoff counter 6\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=6 -> 1/64 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=32) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=33) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=34) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=35) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=36) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=37) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=38) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=39) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=40) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=41) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=42) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=43) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=44) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=45) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=46) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=47) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=48) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=49) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=50) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=51) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=52) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=53) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=54) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=55) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=56) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=57) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=58) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=59) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=60) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=61) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=62) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=63) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan6_time_bounded.nm",
    "content": "// WLAN PROTOCOL (two stations)\n// discrete time model\n// gxn/jzs 20/02/02\n\n// TIMING CONSTRAINTS\n// we have used the FHSS parameters\n// then scaled by the value of ASLOTTIME\nconst ASLOTTIME = 1;\nconst DIFS = 3; // due to scaling can be either 2 or 3 which is modelled by a non-deterministic choice\nconst VULN = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\nconst TRANS_TIME_MAX; // scaling up\nconst TRANS_TIME_MIN = 4; // scaling down\nconst ACK_TO = 6; \nconst ACK = 4; // due to scaling can be either 3 or 4 which is modelled by a non-deterministic choice\nconst SIFS = 1; // due to scaling can be either 0 or 1 which is modelled by a non-deterministic choice\n// maximum constant used in timing constraints + 1\nconst TIME_MAX = max(ACK_TO,TRANS_TIME_MAX)+1;\n\n// CONTENTION WINDOW\n// CWMIN =15 & CWMAX =1023\n// this means that MAX_BACKOFF IS 6\nconst MAX_BACKOFF = 6;\n\n//-----------------------------------------------------------------//\n// THE MEDIUM/CHANNEL\n\n// FORMULAE FOR THE CHANNEL\n// channel is busy\nformula busy = c1>0 | c2>0;\n// channel is free\nformula free = c1=0 & c2=0;\n\nmodule medium\n\t\n\t// medium status \n\tc1 : [0..2];\n\tc2 : [0..2];\n\t// ci corresponds to messages associated with station i\n\t// 0 nothing being sent\n\t// 1 being sent correctly\n\t// 2 being sent garbled\t  \n\t\n\t// begin sending message and nothing else currently being sent\n\t[send1] c1=0 & c2=0 -> (c1'=1);\n\t[send2] c2=0 & c1=0 -> (c2'=1);\n\t\n\t// begin sending message and  something is already being sent\n\t// in this case both messages become garbled\n\t[send1] c1=0 & c2>0 -> (c1'=2) & (c2'=2);\n\t[send2] c2=0 & c1>0 -> (c1'=2) & (c2'=2);\n\t\n\t// finish sending message\n\t[finish1] c1>0 -> (c1'=0);\n\t[finish2] c2>0 -> (c2'=0);\n\nendmodule\n\n//-----------------------------------------------------------------//\n// STATION 1\nmodule station1\n\t// clock for station 1\n\tx1 : [0..TIME_MAX];\n\t\n\t// local state\n\ts1 : [1..12];\n\t// 1 sense\n\t// 2 wait until free before setting backoff\n\t// 3 wait for DIFS then set slot\n\t// 4 set backoff \n\t// 5 backoff\n\t// 6 wait until free in backoff\n\t// 7 wait for DIFS then resume backoff\n\t// 8 vulnerable \n\t// 9 transmit\n\t// 11 wait for SIFS and then ACK\n\t// 10 wait for ACT_TO \n\t// 12 done\n\t// BACKOFF\n\t// separate into slots\n\tslot1 : [0..63]; \n\tbackoff1 : [0..15];\n\t\n\t// BACKOFF COUNTER\n\tbc1 : [0..MAX_BACKOFF];\n\t// SENSE\n\t// let time pass\n\t[time] s1=1 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// ready to transmit\n\t[] s1=1 & (x1=DIFS | x1=DIFS-1) -> (s1'=8) & (x1'=0);\n\t// found channel busy so wait until free\n\t[] s1=1 & busy -> (s1'=2) & (x1'=0);\n\t// WAIT UNTIL FREE BEFORE SETTING BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=2 & busy -> (s1'=2);\n\t// find that channel is free so check its free for DIFS before setting backoff\n\t[] s1=2 & free -> (s1'=3);\n\t// WAIT FOR DIFS THEN SET BACKOFF\n\t// let time pass\n\t[time] s1=3 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// found channel busy so wait until free\n\t[] s1=3 & busy -> (s1'=2) & (x1'=0);\n\t// start backoff  first uniformly choose slot\n\t// backoff counter 0\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=0 -> (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 1\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=1 -> 1/2 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/2 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 2\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=2 -> 1/4 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/4 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 3\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=3 -> 1/8 : (s1'=4) & (x1'=0) & (slot1'=0) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=1) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=2) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=3) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=4) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=5) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=6) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/8 : (s1'=4) & (x1'=0) & (slot1'=7) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 4\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=4 -> 1/16 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/16 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// backoff counter 5\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=5 -> 1/32 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/32 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t\t \n\t// backoff counter 6\n\t[] s1=3 & (x1=DIFS | x1=DIFS-1) & bc1=6 -> 1/64 : (s1'=4) & (x1'=0) & (slot1'=0 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=1 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=2 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=3 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=4 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=5 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=6 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=7 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=8 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=9 ) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=10) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=11) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=12) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=13) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=14) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=15) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=16) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=17) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=18) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=19) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=20) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=21) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=22) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=23) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=24) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=25) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=26) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=27) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=28) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=29) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=30) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=31) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=32) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=33) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=34) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=35) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=36) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=37) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=38) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=39) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=40) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=41) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=42) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=43) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=44) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=45) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=46) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=47) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=48) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=49) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=50) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=51) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=52) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=53) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=54) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=55) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=56) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=57) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=58) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=59) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=60) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=61) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=62) & (bc1'=min(bc1+1,MAX_BACKOFF))\n\t                                         + 1/64 : (s1'=4) & (x1'=0) & (slot1'=63) & (bc1'=min(bc1+1,MAX_BACKOFF));\n\t// SET BACKOFF (no time can pass)\n\t// chosen slot now set backoff\n\t[] s1=4 -> 1/16 : (s1'=5) & (backoff1'=0 )\n\t         + 1/16 : (s1'=5) & (backoff1'=1 )\n\t         + 1/16 : (s1'=5) & (backoff1'=2 )\n\t         + 1/16 : (s1'=5) & (backoff1'=3 )\n\t         + 1/16 : (s1'=5) & (backoff1'=4 )\n\t         + 1/16 : (s1'=5) & (backoff1'=5 )\n\t         + 1/16 : (s1'=5) & (backoff1'=6 )\n\t         + 1/16 : (s1'=5) & (backoff1'=7 )\n\t         + 1/16 : (s1'=5) & (backoff1'=8 )\n\t         + 1/16 : (s1'=5) & (backoff1'=9 )\n\t         + 1/16 : (s1'=5) & (backoff1'=10)\n\t         + 1/16 : (s1'=5) & (backoff1'=11)\n\t         + 1/16 : (s1'=5) & (backoff1'=12)\n\t         + 1/16 : (s1'=5) & (backoff1'=13)\n\t         + 1/16 : (s1'=5) & (backoff1'=14)\n\t         + 1/16 : (s1'=5) & (backoff1'=15);\n\t// BACKOFF\n\t// let time pass\n\t[time] s1=5 & x1<ASLOTTIME & free -> (x1'=min(x1+1,TIME_MAX));\n\t// decrement backoff\n\t[] s1=5 & x1=ASLOTTIME & backoff1>0 -> (s1'=5) & (x1'=0) & (backoff1'=backoff1-1);\t\n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1>0 -> (s1'=5) & (x1'=0) & (backoff1'=15) & (slot1'=slot1-1);\t\n\t// finish backoff \n\t[] s1=5 & x1=ASLOTTIME & backoff1=0 & slot1=0 -> (s1'=8) & (x1'=0);\n\t// found channel busy\n\t[] s1=5 & busy -> (s1'=6) & (x1'=0);\n\t// WAIT UNTIL FREE IN BACKOFF\n\t// let time pass (no need for the clock x1 to change)\n\t[time] s1=6 & busy -> (s1'=6);\n\t// find that channel is free\n\t[] s1=6 & free -> (s1'=7);\n\t\n\t// WAIT FOR DIFS THEN RESUME BACKOFF\n\t// let time pass\n\t[time] s1=7 & x1<DIFS & free -> (x1'=min(x1+1,TIME_MAX));\n\t// resume backoff (start again from previous backoff)\n\t[] s1=7 & (x1=DIFS | x1=DIFS-1) -> (s1'=5) & (x1'=0);\n\t// found channel busy\n\t[] s1=7 & busy -> (s1'=6) & (x1'=0);\n\t\n\t// VULNERABLE\n\t// let time pass\n\t[time] s1=8 & x1<VULN -> (x1'=min(x1+1,TIME_MAX));\n\t// move to transmit\n\t[send1] s1=8 & (x1=VULN | x1=VULN-1) -> (s1'=9) & (x1'=0);\n\t// TRANSMIT\n\t// let time pass\n\t[time] s1=9 & x1<TRANS_TIME_MAX -> (x1'=min(x1+1,TIME_MAX));\n\t// finish transmission successful\t\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=1 -> (s1'=10) & (x1'=0);\n\t// finish transmission garbled\n\t[finish1] s1=9 & x1>=TRANS_TIME_MIN & c1=2 -> (s1'=11) & (x1'=0);\n\t// WAIT FOR SIFS THEN WAIT FOR ACK\n\t\n\t// WAIT FOR SIFS i.e. c1=0\n\t// check channel and busy: go into backoff\n\t[] s1=10 & c1=0 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=10 & c1=0 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t// following guard is always false as SIFS=1\n\t// [time] s1=10 & c1=0 & x1>0 & x1<SIFS -> (x1'=min(x1+1,TIME_MAX));\n\t// ack is sent after SIFS (since SIFS-1=0 add condition that channel is free)\n\t[send1] s1=10 & c1=0 & (x1=SIFS | (x1=SIFS-1 & free)) -> (s1'=10) & (x1'=0);\n\t\n\t// WAIT FOR ACK i.e. c1=1\n\t// let time pass\n\t[time] s1=10 & c1=1 & x1<ACK -> (x1'=min(x1+1,TIME_MAX));\n\t// get acknowledgement so packet sent correctly and move to done\n\t[finish1] s1=10 & c1=1 & (x1=ACK | x1=ACK-1) -> (s1'=12) & (x1'=0) & (bc1'=0);\n\t\n\t// WAIT FOR ACK_TO\n\t// check channel and busy: go into backoff\n\t[] s1=11 & x1=0 & busy -> (s1'=2);\n\t// check channel and free: let time pass\n\t[time] s1=11 & x1=0 & free -> (x1'=min(x1+1,TIME_MAX));\n\t// let time pass\n\t[time] s1=11 & x1>0 & x1<ACK_TO -> (x1'=min(x1+1,TIME_MAX));\n\t// no acknowledgement (go to backoff waiting DIFS first)\n\t[] s1=11 & x1=ACK_TO -> (s1'=3) & (x1'=0);\n\t\t\n\t// DONE\n\t[time] s1=12 -> (s1'=12);\nendmodule\t\n\n// ---------------------------------------------------------------------------- //\n// STATION 2 (rename STATION 1)\nmodule \nstation2=station1[x1=x2, \n                  s1=s2,\n\t\t\t\t  s2=s1,\n\t\t\t\t  c1=c2,\n\t\t\t\t  c2=c1, \n\t\t\t\t  slot1=slot2, \n\t\t\t\t  backoff1=backoff2, \n\t\t\t\t  bc1=bc2, \n\t\t\t\t  send1=send2, \n\t\t\t\t  finish1=finish2] \nendmodule\n// ---------------------------------------------------------------------------- //\nconst int DEADLINE;\n\n// timer\nmodule timer\n\t// global time\n\tt : [0..DEADLINE];\n\t\n\t[time] (t<DEADLINE) -> (t'=min(t+1,DEADLINE));\n\t// loop when time passes DEADLINE to prevent further transitions\n\t[] (t>=DEADLINE) -> (t'=t);\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan_collide.pctl",
    "content": "const int k;\n\n// max probability stations collide\n// (min is always zero)\nPmax=?[ true U col=k ]\n\n"
  },
  {
    "path": "prism-examples/mdps/wlan/wlan_time_bounded.pctl",
    "content": "// A STATION SEND THEIR PACKET EVENTUALLY\n// minimum probability\nPmin=? [ true U s1=12 & s2=12 ]\nPmin=? [ true U s1=12 | s2=12 ]\nPmin=? [ true U s1=12 ]\n"
  },
  {
    "path": "prism-examples/mdps/zeroconf/README.txt",
    "content": "This case study concerns the IPv4 Zeroconf Protocol [CAG02]\n\nWe consider the probabilistic timed automata models presented in [KNPS06] using\nthe integer semantics also presented in the paper.\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/zeroconf.php\r\n\n=====================================================================================\r\n\nPARAMETERS\nreset: reset is true/false dependent on whether the reset/norest model is to be analysed\nloss: probability of message (0.1, 0.01, 0.001 and 0)\nK: number of probes (4 in standard) 1:1:8\nN: number of concrete hosts, e.g. 20 or 1000 for small/large network\nerr: error cost from 1e+6 to 1e+12\nbound: time bound from 0:50 (then set T to be 1+maximum value of bound in experiment)\n\n=====================================================================================\r\n\r\n[CAG02]\nS. Cheshire and B. Adoba and E. Gutterman\nDynamic configuration of {IPv}4 link local addresses\nAvailable from http://www.ietf.org/rfc/rfc3927.txt\n\n[KNPS06]\nM. Kwiatkowska, G. Norman, D. Parker and J. Sproston\nPerformance Analysis of Probabilistic Timed Automata using Digital Clocks\nFormal Methods in System Design, 29:33-78, 2006\n\n"
  },
  {
    "path": "prism-examples/mdps/zeroconf/auto",
    "content": "#!/bin/csh\n \n# example command for minimum probabilistic reachability\nprism zeroconf.nm zeroconf.pctl -const N=1000,K=4,err=0,reset=true  -prop 1 \nprism zeroconf.nm zeroconf.pctl -const N=1000,K=4,err=0,reset=false -prop 1\n\n# example command for maximum probabilistic reachability\nprism zeroconf.nm zeroconf.pctl -const N=1000,K=4,err=0,reset=true  -prop 1 \nprism zeroconf.nm zeroconf.pctl -const N=1000,K=4,err=0,reset=false -prop 1\n\n# example command for minimum expected reachability\nprism zeroconf.nm zeroconf.pctl -const N=1000,K=4,err=0,reset=true  -prop 1 \nprism zeroconf.nm zeroconf.pctl -const N=1000,K=4,err=0,reset=false -prop 1\n\n# example command for maximum expected reachability\nprism zeroconf.nm zeroconf.pctl -const N=1000,K=4,err=0,reset=true  -prop 1 \nprism zeroconf.nm zeroconf.pctl -const N=1000,K=4,err=0,reset=false -prop 1\n\n# example command for time bounded reachability\nprism zeroconf_time_bounded.nm zeroconf_time_bounded.pctl -const N=1000,K=1,T=11,bound=10,reset=true -fixdl\nprism zeroconf_time_bounded.nm zeroconf_time_bounded.pctl -const N=1000,K=1,T=11,bound=10,reset=false -fixdl\n\n"
  },
  {
    "path": "prism-examples/mdps/zeroconf/zeroconf.nm",
    "content": "// IPv4: PTA model with digitial clocks\n// one concrete host attempting to choose an ip address \n// when a number of (abstract) hosts have already got ip addresses\n// gxn/dxp/jzs 02/05/03\n\n// reset or noreset model\nconst bool reset;\n\n//-------------------------------------------------------------\n\n// we suppose that\n// - the abstract hosts have already picked their addresses \n//   and always defend their addresses\n// - the concrete host never picks the same ip address twice \n//   (this can happen only with a verys small probability)\n\n// under these assumptions we do not need message types because:\n// 1) since messages to the concrete host will never be a probe, \n//    this host will react to all messages in the same way\n// 2) since the abstract hosts always defend their addresses, \n//    all messages from the host will get an arp reply if the ip matches\n\n// following from the above assumptions we require only three abstract IP addresses\n// (0,1 and 2) which correspond to the following sets of IP addresses:\n\n// 0 - the IP addresses of the abstract hosts which the concrete host \n//     previously tried to configure\n// 1 - an IP address of an abstract host which the concrete host is \n//     currently trying to configure\n// 2 - a fresh IP address which the concrete host is currently trying to configure\n\n// if the host picks an address that is being used it may end up picking another ip address\n// in which case there may still be messages corresponding to the old ip address\n// to be sent both from and to the host which the host should now disregard\n// (since it will never pick the same ip address)\n\n// to deal with this situation: when a host picks a new ip address we reconfigure the \n// messages that are still be be sent or are being sent by changing the ip address to 0 \n// (an old ip address of the host)\n\n// all the messages from the abstract hosts for the 'old' address (in fact the\n// set of old addresses since it may have started again more than once)  \n// can arrive in any order since they are equivalent to the host - it ignores then all\n\n// also the messages for the old and new address will come from different hosts\n// (the ones with that ip address) which we model by allowing them to arrive in any order\n// i.e. not neccessarily in the order they where sent\n\n//-------------------------------------------------------------\n// model is an mdp\nmdp\n\n//-------------------------------------------------------------\n// VARIABLES\nconst int N; // number of abstract hosts\nconst int K; // number of probes to send\nconst double loss = 0.1; // probability of message loss\n\n// PROBABILITIES\nconst double old = N/65024; // probability pick an ip address being used\nconst double new = (1-old); // probability pick a new ip address\n\n// TIMING CONSTANTS\nconst int CONSEC = 2;  // time interval between sending consecutive probles \nconst int TRANSTIME = 1; // upper bound on transmission time delay\nconst int LONGWAIT = 60; // minimum time delay after a high number of address collisions\nconst int DEFEND = 10;\n\nconst int TIME_MAX_X = 60; // max value of clock x\nconst int TIME_MAX_Y = 10; // max value of clock y\nconst int TIME_MAX_Z = 1;  // max value of clock z\n\n// OTHER CONSTANTS\nconst int MAXCOLL = 10;  // maximum number of collisions before long wait\n// size of buffers for other hosts\nconst int B0 = 20;  // buffer size for one abstract host\nconst int B1 = 8;  // buffer sizes for all abstract hosts\n\n//-------------------------------------------------------------\n// ENVIRONMENT - models: medium, output buffer of concrete host and all other hosts\nmodule environment\n\t\n\t// buffer of concrete host\n\tb_ip7 : [0..2]; // ip address of message in buffer position 8\n\tb_ip6 : [0..2]; // ip address of message in buffer position 7\n\tb_ip5 : [0..2]; // ip address of message in buffer position 6\n\tb_ip4 : [0..2]; // ip address of message in buffer position 5\n\tb_ip3 : [0..2]; // ip address of message in buffer position 4\n\tb_ip2 : [0..2]; // ip address of message in buffer position 3\n\tb_ip1 : [0..2]; // ip address of message in buffer position 2\n\tb_ip0 : [0..2]; // ip address of message in buffer position 1\n\tn : [0..8]; // number of places in the buffer used (from host)\n\t\n\t// messages to be sent from abstract hosts to concrete host\n\tn0  : [0..B0]; // number of messages which do not have the host's current ip address\n\tn1  : [0..B1]; // number of messages which have the host's current ip address\n\t\n\tb : [0..2]; // local state\n\t// 0 - idle\n\t// 1 - sending message from concrete host \n\t// 2 - sending message from abstract host\n\t\n\tz : [0..1]; // clock of environment (needed for the time to send a message)\n\t\n\tip_mess : [0..2]; // ip in the current message being sent\n\t// 0 - different from concrete host\n\t// 1 - same as the concrete host and in use\n\t// 2 - same as the concrete host and not in use\n\t\n\t// RESET/RECONFIG: when host is about to choose new ip address\n\t// suppose that the host cannot choose the same ip address\n\t// (since happens with very small probability). \n\t// Therefore all messages will have a different ip address, \n\t// i.e. all n1 messages become n0 ones.\n\t// Note this include any message currently being sent (ip is set to zero 0)\n\t[reset] true -> (n1'=0) & (n0'=min(B0,n0+n1)) // abstract buffers \n\t               & (ip_mess'=0) // message being set\n\t               & (n'=(reset)?0:n) // concrete buffer (remove this update to get NO_RESET model)\n\t               & (b_ip7'=0) \n\t               & (b_ip6'=0) \n\t               & (b_ip5'=0) \n\t               & (b_ip4'=0) \n\t               & (b_ip3'=0) \n\t               & (b_ip2'=0) \n\t               & (b_ip1'=0) \n\t               & (b_ip0'=0);\n\t// note: prevent anything else from happening when reconfiguration needs to take place\n\t\n\t// time passage (only if no messages to send or sending a message)\n\t[time] l>0 & b=0 & n=0 & n0=0 & n1=0 -> (b'=b); // cannot send a message\n\t[time] l>0 & b>0 & z<1 -> (z'=min(z+1,TIME_MAX_Z)); // sending a message\n\t\n\t// get messages to be sent (so message has same ip address as host)\n\t[send] l>0 & n=0 -> (b_ip0'=ip) & (n'=n+1);\n\t[send] l>0 & n=1 -> (b_ip1'=ip) & (n'=n+1);\n\t[send] l>0 & n=2 -> (b_ip2'=ip) & (n'=n+1);\n\t[send] l>0 & n=3 -> (b_ip3'=ip) & (n'=n+1);\n\t[send] l>0 & n=4 -> (b_ip4'=ip) & (n'=n+1);\n\t[send] l>0 & n=5 -> (b_ip5'=ip) & (n'=n+1);\n\t[send] l>0 & n=6 -> (b_ip6'=ip) & (n'=n+1);\n\t[send] l>0 & n=7 -> (b_ip7'=ip) & (n'=n+1);\n\t[send] l>0 & n=8 -> (n'=n); // buffer full so lose message\n\t\n\t// start sending message from host\n\t[] l>0 & b=0 & n>0 -> (1-loss) : (b'=1) & (ip_mess'=b_ip0) \n\t                                & (n'=n-1)\n\t                                & (b_ip7'=0) \n\t                                & (b_ip6'=b_ip7) \n\t                                & (b_ip5'=b_ip6) \n\t                                & (b_ip4'=b_ip5) \n\t                                & (b_ip3'=b_ip4) \n\t                                & (b_ip2'=b_ip3) \n\t                                & (b_ip1'=b_ip2) \n\t                                & (b_ip0'=b_ip1) // send message\n\t                         + loss : (n'=n-1)\n\t                                & (b_ip7'=0) \n\t                                & (b_ip6'=b_ip7) \n\t                                & (b_ip5'=b_ip6) \n\t                                & (b_ip4'=b_ip5) \n\t                                & (b_ip3'=b_ip4) \n\t                                & (b_ip2'=b_ip3) \n\t                                & (b_ip1'=b_ip2) \n\t                                & (b_ip0'=b_ip1); // lose message\n\t\n\t// start sending message to host\n\t[] l>0 & b=0 & n0>0 -> (1-loss) : (b'=2) & (ip_mess'=0) & (n0'=n0-1) + loss : (n0'=n0-1); // different ip\n\t[] l>0 & b=0 & n1>0 -> (1-loss) : (b'=2) & (ip_mess'=1) & (n1'=n1-1) + loss : (n1'=n1-1); // same ip\n\t\n\t// finish sending message from host\n\t[] l>0 & b=1 & ip_mess=0 -> (b'=0) & (z'=0) & (n0'=min(n0+1,B0)) & (ip_mess'=0);\n\t[] l>0 & b=1 & ip_mess=1 -> (b'=0) & (z'=0) & (n1'=min(n1+1,B1)) & (ip_mess'=0);\n\t[] l>0 & b=1 & ip_mess=2 -> (b'=0) & (z'=0) & (ip_mess'=0);\n\t\n\t// finish sending message to host\n\t[rec] l>0 & b=2 -> (b'=0) & (z'=0) & (ip_mess'=0);\n\t\nendmodule\n\n//-------------------------------------------------------------\n// CONCRETE HOST\nmodule host0\n\t\n\tx : [0..TIME_MAX_X]; // first clock of the host\n\ty : [0..TIME_MAX_Y]; // second clock of the host\n\t\n\tcoll : [0..MAXCOLL]; // number of address collisions\n\tprobes : [0..K]; // counter (number of probes sent)\n\tmess : [0..1]; // need to send a message or not\n\tdefend : [0..1]; // defend (if =1, try to defend IP address)\n\t\n\tip : [1..2]; // ip address (1 - in use & 2 - fresh)\n\t\n\tl : [0..4] init 1; // location\n\t// 0 : RECONFIGURE \n\t// 1 : RANDOM\n\t// 2 : WAITSP\n\t// 3 : WAITSG \n\t// 4 : USE\n\t\n\t// RECONFIGURE\n\t[reset] l=0 -> (l'=1);\n\t\n\t// RANDOM (choose IP address)\n\t[rec] (l=1) -> true; // get message (ignore since have no ip address)\n\t// small number of collisions (choose straight away)\n\t[] l=1 & coll<MAXCOLL -> 1/3*old : (l'=2) & (ip'=1) & (x'=0) \n\t\t                     + 1/3*old : (l'=2) & (ip'=1) & (x'=1) \n\t\t                     + 1/3*old : (l'=2) & (ip'=1) & (x'=2) \n\t\t                     + 1/3*new : (l'=2) & (ip'=2) & (x'=0) \n\t\t                     + 1/3*new : (l'=2) & (ip'=2) & (x'=1) \n\t\t                     + 1/3*new : (l'=2) & (ip'=2) & (x'=2); \n\t// large number of collisions: (wait for LONGWAIT)\n\t[time] l=1 & coll=MAXCOLL & x<LONGWAIT -> (x'=min(x+1,TIME_MAX_X));\n\t[]     l=1 & coll=MAXCOLL & x=LONGWAIT -> 1/3*old : (l'=2) & (ip'=1) & (x'=0) \n\t\t\t                                   + 1/3*old : (l'=2) & (ip'=1) & (x'=1) \n\t\t\t                                   + 1/3*old : (l'=2) & (ip'=1) & (x'=2) \n\t\t\t                                   + 1/3*new : (l'=2) & (ip'=2) & (x'=0) \n\t\t\t                                   + 1/3*new : (l'=2) & (ip'=2) & (x'=1) \n\t\t\t                                   + 1/3*new : (l'=2) & (ip'=2) & (x'=2);\n\t\n\t// WAITSP \n\t// let time pass\n\t[time]  l=2 & x<2 -> (x'=min(x+1,2));\n\t// send probe\n\t[send] l=2 & x=2  & probes<K -> (x'=0) & (probes'=probes+1);\n\t// sent K probes and waited 2 seconds\n\t[] l=2 & x=2 & probes=K -> (l'=3) & (probes'=0) & (coll'=0) & (x'=0);\n\t// get message and ip does not match: ignore\n\t[rec] l=2 & ip_mess!=ip -> (l'=l);\n\t// get a message with matching ip: reconfigure\n\t[rec] l=2 & ip_mess=ip -> (l'=0) & (coll'=min(coll+1,MAXCOLL)) & (x'=0) & (probes'=0);\n\t\n\t// WAITSG (sends two gratuitious arp probes)\n\t// time passage\n\t[time] l=3 & mess=0 & defend=0 & x<CONSEC -> (x'=min(x+1,TIME_MAX_X)); \n\t[time] l=3 & mess=0 & defend=1 & x<CONSEC -> (x'=min(x+1,TIME_MAX_X)) & (y'=min(y+1,DEFEND));\n\t\n\t// receive message and same ip: defend\n\t[rec] l=3 & mess=0 & ip_mess=ip & (defend=0 | y>=DEFEND) -> (defend'=1) & (mess'=1) & (y'=0);\n\t// receive message and same ip: defer\n\t[rec] l=3 & mess=0 & ip_mess=ip & (defend=0 | y<DEFEND) -> (l'=0) & (probes'=0) & (defend'=0) & (x'=0) & (y'=0);\n\t// receive message and different ip\n\t[rec] l=3 & mess=0 & ip_mess!=ip -> (l'=l);\n\t\n\t\t\n\t// send probe reply or message for defence\n\t[send] l=3 & mess=1 -> (mess'=0);\n\t// send first gratuitous arp message\n\t[send] l=3 & mess=0 & x=CONSEC & probes<1 -> (x'=0) & (probes'=probes+1);\n\t// send second gratuitous arp message (move to use)\n\t[send] l=3 & mess=0 & x=CONSEC & probes=1 -> (l'=4) & (x'=0) & (y'=0) & (probes'=0);\n\t\n\t// USE (only interested in reaching this state so do not need to add anything here)\n\t[] l=4 -> true;\n\t\nendmodule\n\n//-------------------------------------------------------------\n\n// reward structure\nconst double err; // cost associated with using a IP address already in use\n\nrewards\n\t[time] true : 1;\n\t[send] l=3 & mess=0 & y=CONSEC & probes=1 & ip=1 : err;\nendrewards\n\n"
  },
  {
    "path": "prism-examples/mdps/zeroconf/zeroconf.pctl",
    "content": "// min/max probability of configuring correctly\nPmin=?[ true U (l=4 & ip=1) ]\nPmax=?[ true U (l=4 & ip=1) ]\n\n// min/max expected cost of configuring\nRmin=?[ F l=4 ]\nRmax=?[ F l=4 ]\n\n"
  },
  {
    "path": "prism-examples/mdps/zeroconf/zeroconf_time_bounded.nm",
    "content": "// IPv4: PTA model with digitial clocks\n// one concrete host attempting to choose an ip address \n// when a number of (abstract) hosts have already got ip addresses\n// gxn/dxp/jzs 02/05/03\n\n// reset or noreset model\nconst bool reset;\nconst int T;\n\n//-------------------------------------------------------------\n\n// we suppose that\n// - the abstract hosts have already picked their addresses \n//   and always defend their addresses\n// - the concrete host never picks the same ip address twice \n//   (this can happen only with a verys small probability)\n\n// under these assumptions we do not need message types because:\n// 1) since messages to the concrete host will never be a probe, \n//    this host will react to all messages in the same way\n// 2) since the abstract hosts always defend their addresses, \n//    all messages from the host will get an arp reply if the ip matches\n\n// following from the above assumptions we require only three abstract IP addresses\n// (0,1 and 2) which correspond to the following sets of IP addresses:\n\n// 0 - the IP addresses of the abstract hosts which the concrete host \n//     previously tried to configure\n// 1 - an IP address of an abstract host which the concrete host is \n//     currently trying to configure\n// 2 - a fresh IP address which the concrete host is currently trying to configure\n\n// if the host picks an address that is being used it may end up picking another ip address\n// in which case there may still be messages corresponding to the old ip address\n// to be sent both from and to the host which the host should now disregard\n// (since it will never pick the same ip address)\n\n// to deal with this situation: when a host picks a new ip address we reconfigure the \n// messages that are still be be sent or are being sent by changing the ip address to 0 \n// (an old ip address of the host)\n\n// all the messages from the abstract hosts for the 'old' address (in fact the\n// set of old addresses since it may have started again more than once)  \n// can arrive in any order since they are equivalent to the host - it ignores then all\n\n// also the messages for the old and new address will come from different hosts\n// (the ones with that ip address) which we model by allowing them to arrive in any order\n// i.e. not neccessarily in the order they where sent\n\n//-------------------------------------------------------------\n// model is an mdp\nmdp\n\n//-------------------------------------------------------------\n// VARIABLES\nconst int N; // number of abstract hosts\nconst int K; // number of probes to send\nconst double loss = 0.1; // probability of message loss\n\n// PROBABILITIES\nconst double old = N/65024; // probability pick an ip address being used\nconst double new = (1-old); // probability pick a new ip address\n\n// TIMING CONSTANTS\nconst int CONSEC = 2;  // time interval between sending consecutive probles \nconst int TRANSTIME = 1; // upper bound on transmission time delay\nconst int LONGWAIT = 60; // minimum time delay after a high number of address collisions\nconst int DEFEND = 10;\n\nconst int TIME_MAX_X = 60; // max value of clock x\nconst int TIME_MAX_Y = 10; // max value of clock y\nconst int TIME_MAX_Z = 1;  // max value of clock z\n\n// OTHER CONSTANTS\nconst int MAXCOLL = 10;  // maximum number of collisions before long wait\n// size of buffers for other hosts\nconst int B0 = 20;  // buffer size for one abstract host\nconst int B1 = 8;  // buffer sizes for all abstract hosts\n\n//-------------------------------------------------------------\n// ENVIRONMENT - models: medium, output buffer of concrete host and all other hosts\nmodule environment\n\t\n\t// buffer of concrete host\n\tb_ip7 : [0..2]; // ip address of message in buffer position 8\n\tb_ip6 : [0..2]; // ip address of message in buffer position 7\n\tb_ip5 : [0..2]; // ip address of message in buffer position 6\n\tb_ip4 : [0..2]; // ip address of message in buffer position 5\n\tb_ip3 : [0..2]; // ip address of message in buffer position 4\n\tb_ip2 : [0..2]; // ip address of message in buffer position 3\n\tb_ip1 : [0..2]; // ip address of message in buffer position 2\n\tb_ip0 : [0..2]; // ip address of message in buffer position 1\n\tn : [0..8]; // number of places in the buffer used (from host)\n\t\n\t// messages to be sent from abstract hosts to concrete host\n\tn0  : [0..B0]; // number of messages which do not have the host's current ip address\n\tn1  : [0..B1]; // number of messages which have the host's current ip address\n\t\n\tb : [0..2]; // local state\n\t// 0 - idle\n\t// 1 - sending message from concrete host \n\t// 2 - sending message from abstract host\n\t\n\tz : [0..1]; // clock of environment (needed for the time to send a message)\n\t\n\tip_mess : [0..2]; // ip in the current message being sent\n\t// 0 - different from concrete host\n\t// 1 - same as the concrete host and in use\n\t// 2 - same as the concrete host and not in use\n\t\n\t// RESET/RECONFIG: when host is about to choose new ip address\n\t// suppose that the host cannot choose the same ip address\n\t// (since happens with very small probability). \n\t// Therefore all messages will have a different ip address, \n\t// i.e. all n1 messages become n0 ones.\n\t// Note this include any message currently being sent (ip is set to zero 0)\n\t[reset] true -> (n1'=0) & (n0'=min(B0,n0+n1)) // abstract buffers \n\t               & (ip_mess'=0) // message being set\n\t               & (n'=(reset)?0:n) // concrete buffer (remove this update to get NO_RESET model)\n\t               & (b_ip7'=0) \n\t               & (b_ip6'=0) \n\t               & (b_ip5'=0) \n\t               & (b_ip4'=0) \n\t               & (b_ip3'=0) \n\t               & (b_ip2'=0) \n\t               & (b_ip1'=0) \n\t               & (b_ip0'=0);\n\t// note: prevent anything else from happening when reconfiguration needs to take place\n\t\n\t// time passage (only if no messages to send or sending a message)\n\t[time] l>0 & b=0 & n=0 & n0=0 & n1=0 -> (b'=b); // cannot send a message\n\t[time] l>0 & b>0 & z<1 -> (z'=min(z+1,TIME_MAX_Z)); // sending a message\n\t\n\t// get messages to be sent (so message has same ip address as host)\n\t[send] l>0 & n=0 -> (b_ip0'=ip) & (n'=n+1);\n\t[send] l>0 & n=1 -> (b_ip1'=ip) & (n'=n+1);\n\t[send] l>0 & n=2 -> (b_ip2'=ip) & (n'=n+1);\n\t[send] l>0 & n=3 -> (b_ip3'=ip) & (n'=n+1);\n\t[send] l>0 & n=4 -> (b_ip4'=ip) & (n'=n+1);\n\t[send] l>0 & n=5 -> (b_ip5'=ip) & (n'=n+1);\n\t[send] l>0 & n=6 -> (b_ip6'=ip) & (n'=n+1);\n\t[send] l>0 & n=7 -> (b_ip7'=ip) & (n'=n+1);\n\t[send] l>0 & n=8 -> (n'=n); // buffer full so lose message\n\t\n\t// start sending message from host\n\t[] l>0 & b=0 & n>0 -> (1-loss) : (b'=1) & (ip_mess'=b_ip0) \n\t                                & (n'=n-1)\n\t                                & (b_ip7'=0) \n\t                                & (b_ip6'=b_ip7) \n\t                                & (b_ip5'=b_ip6) \n\t                                & (b_ip4'=b_ip5) \n\t                                & (b_ip3'=b_ip4) \n\t                                & (b_ip2'=b_ip3) \n\t                                & (b_ip1'=b_ip2) \n\t                                & (b_ip0'=b_ip1) // send message\n\t                         + loss : (n'=n-1)\n\t                                & (b_ip7'=0) \n\t                                & (b_ip6'=b_ip7) \n\t                                & (b_ip5'=b_ip6) \n\t                                & (b_ip4'=b_ip5) \n\t                                & (b_ip3'=b_ip4) \n\t                                & (b_ip2'=b_ip3) \n\t                                & (b_ip1'=b_ip2) \n\t                                & (b_ip0'=b_ip1); // lose message\n\t\n\t// start sending message to host\n\t[] l>0 & b=0 & n0>0 -> (1-loss) : (b'=2) & (ip_mess'=0) & (n0'=n0-1) + loss : (n0'=n0-1); // different ip\n\t[] l>0 & b=0 & n1>0 -> (1-loss) : (b'=2) & (ip_mess'=1) & (n1'=n1-1) + loss : (n1'=n1-1); // same ip\n\t\n\t// finish sending message from host\n\t[] l>0 & b=1 & ip_mess=0 -> (b'=0) & (z'=0) & (n0'=min(n0+1,B0)) & (ip_mess'=0);\n\t[] l>0 & b=1 & ip_mess=1 -> (b'=0) & (z'=0) & (n1'=min(n1+1,B1)) & (ip_mess'=0);\n\t[] l>0 & b=1 & ip_mess=2 -> (b'=0) & (z'=0) & (ip_mess'=0);\n\t\n\t// finish sending message to host\n\t[rec] l>0 & b=2 -> (b'=0) & (z'=0) & (ip_mess'=0);\n\t\nendmodule\n\n//-------------------------------------------------------------\n// CONCRETE HOST\nmodule host0\n\t\n\tx : [0..TIME_MAX_X]; // first clock of the host\n\ty : [0..TIME_MAX_Y]; // second clock of the host\n\t\n\tcoll : [0..MAXCOLL]; // number of address collisions\n\tprobes : [0..K]; // counter (number of probes sent)\n\tmess : [0..1]; // need to send a message or not\n\tdefend : [0..1]; // defend (if =1, try to defend IP address)\n\t\n\tip : [1..2]; // ip address (1 - in use & 2 - fresh)\n\t\n\tl : [0..4] init 1; // location\n\t// 0 : RECONFIGURE \n\t// 1 : RANDOM\n\t// 2 : WAITSP\n\t// 3 : WAITSG \n\t// 4 : USE\n\t\n\t// RECONFIGURE\n\t[reset] l=0 -> (l'=1);\n\t\n\t// RANDOM (choose IP address)\n\t[rec] (l=1) -> true; // get message (ignore since have no ip address)\n\t// small number of collisions (choose straight away)\n\t[] l=1 & coll<MAXCOLL -> 1/3*old : (l'=2) & (ip'=1) & (x'=0) \n\t\t                     + 1/3*old : (l'=2) & (ip'=1) & (x'=1) \n\t\t                     + 1/3*old : (l'=2) & (ip'=1) & (x'=2) \n\t\t                     + 1/3*new : (l'=2) & (ip'=2) & (x'=0) \n\t\t                     + 1/3*new : (l'=2) & (ip'=2) & (x'=1) \n\t\t                     + 1/3*new : (l'=2) & (ip'=2) & (x'=2); \n\t// large number of collisions: (wait for LONGWAIT)\n\t[time] l=1 & coll=MAXCOLL & x<LONGWAIT -> (x'=min(x+1,TIME_MAX_X));\n\t[]     l=1 & coll=MAXCOLL & x=LONGWAIT -> 1/3*old : (l'=2) & (ip'=1) & (x'=0) \n\t\t\t                                   + 1/3*old : (l'=2) & (ip'=1) & (x'=1) \n\t\t\t                                   + 1/3*old : (l'=2) & (ip'=1) & (x'=2) \n\t\t\t                                   + 1/3*new : (l'=2) & (ip'=2) & (x'=0) \n\t\t\t                                   + 1/3*new : (l'=2) & (ip'=2) & (x'=1) \n\t\t\t                                   + 1/3*new : (l'=2) & (ip'=2) & (x'=2);\n\t\n\t// WAITSP \n\t// let time pass\n\t[time]  l=2 & x<2 -> (x'=min(x+1,2));\n\t// send probe\n\t[send] l=2 & x=2  & probes<K -> (x'=0) & (probes'=probes+1);\n\t// sent K probes and waited 2 seconds\n\t[] l=2 & x=2 & probes=K -> (l'=3) & (probes'=0) & (coll'=0) & (x'=0);\n\t// get message and ip does not match: ignore\n\t[rec] l=2 & ip_mess!=ip -> (l'=l);\n\t// get a message with matching ip: reconfigure\n\t[rec] l=2 & ip_mess=ip -> (l'=0) & (coll'=min(coll+1,MAXCOLL)) & (x'=0) & (probes'=0);\n\t\n\t// WAITSG (sends two gratuitious arp probes)\n\t// time passage\n\t[time] l=3 & mess=0 & defend=0 & x<CONSEC -> (x'=min(x+1,TIME_MAX_X)); \n\t[time] l=3 & mess=0 & defend=1 & x<CONSEC -> (x'=min(x+1,TIME_MAX_X)) & (y'=min(y+1,DEFEND));\n\t\n\t// receive message and same ip: defend\n\t[rec] l=3 & mess=0 & ip_mess=ip & (defend=0 | y>=DEFEND) -> (defend'=1) & (mess'=1) & (y'=0);\n\t// receive message and same ip: defer\n\t[rec] l=3 & mess=0 & ip_mess=ip & (defend=0 | y<DEFEND) -> (l'=0) & (probes'=0) & (defend'=0) & (x'=0) & (y'=0);\n\t// receive message and different ip\n\t[rec] l=3 & mess=0 & ip_mess!=ip -> (l'=l);\n\t\n\t\t\n\t// send probe reply or message for defence\n\t[send] l=3 & mess=1 -> (mess'=0);\n\t// send first gratuitous arp message\n\t[send] l=3 & mess=0 & x=CONSEC & probes<1 -> (x'=0) & (probes'=probes+1);\n\t// send second gratuitous arp message (move to use)\n\t[send] l=3 & mess=0 & x=CONSEC & probes=1 -> (l'=4) & (x'=0) & (y'=0) & (probes'=0);\n\t\n\t// USE (only interested in reaching this state so do not need to add anything here)\n\t[] l=4 -> true;\n\t\nendmodule\n\n//-------------------------------------------------------------\n\n// timer\nmodule timer\n\n\tt : [0..T+1];\n\t\n\t[time] t<=T -> (t'=min(t+1,T+1));\n\t[done] l=4 -> (t'=T+1);\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/mdps/zeroconf/zeroconf_time_bounded.pctl",
    "content": "// probability of using fresh ip address within time T\nconst int bound;\nPmin=?[ !(l=4 & ip=2) U t>bound ]\nPmax=?[ !(l=4 & ip=2) U t>bound ]\n"
  },
  {
    "path": "prism-examples/pepa/PC-LAN4.pepa",
    "content": "% a PC-LAN as described in lecture notes from the University of Edinburgh lecture course `Modelling and Simulation'\r\n\t   \r\nlambda = 0.01;                            \r\nmu = 0.1;\r\nomega = 1.0;\r\n\r\n#PC10 = (arrive,lambda).PC11 + (walkon2,infty).PC10;\r\n#PC11 = (serve1,infty).PC10;\r\n\r\n#PC20 = (arrive,lambda).PC21 + (walkon3,infty).PC20;\r\n#PC21 = (serve2,infty).PC20;\r\n\r\n#PC30 = (arrive,lambda).PC31 + (walkon4,infty).PC30;\r\n#PC31 = (serve3,infty).PC30;\r\n\r\n#PC40 = (arrive,lambda).PC41 + (walkon1,infty).PC40;\r\n#PC41 = (serve4,infty).PC40;\r\n\r\n#S1 = (walkon2,omega).S2 + (serve1,mu).T2;\r\n#S2 = (walkon3,omega).S3 + (serve2,mu).T3;\r\n#S3 = (walkon4,omega).S4 + (serve3,mu).T4;\r\n#S4 = (walkon1,omega).S1 + (serve4,mu).T1;\r\n\r\n#T1 = (walk1,omega).S1;\r\n#T2 = (walk2,omega).S2;\r\n#T3 = (walk3,omega).S3;\r\n#T4 = (walk4,omega).S4;\r\n\r\n\r\n(PC10 <> PC20 <> PC30 <> PC40) <walkon1,walkon2,walkon3,walkon4,serve1,serve2,serve3,serve4> S1\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/pepa/PC-LAN6.pepa",
    "content": "% a PC-LAN as described in lecture notes from the University of Edinburgh lecture course `Modelling and Simulation'\r\n\r\nlambda = 0.01;                            \r\nmu = 0.1;\r\nomega = 1.0;\r\n\r\n#PC10 = (arrive,lambda).PC11 + (walkon2,infty).PC10;\r\n#PC11 = (serve1,infty).PC10;\r\n\r\n#PC20 = (arrive,lambda).PC21 + (walkon3,infty).PC20;\r\n#PC21 = (serve2,infty).PC20;\r\n\r\n#PC30 = (arrive,lambda).PC31 + (walkon4,infty).PC30;\r\n#PC31 = (serve3,infty).PC30;\r\n\r\n#PC40 = (arrive,lambda).PC41 + (walkon5,infty).PC40;\r\n#PC41 = (serve4,infty).PC40;\r\n\r\n#PC50 = (arrive,lambda).PC51 + (walkon6,infty).PC50;\r\n#PC51 = (serve5,infty).PC50;\r\n\r\n#PC60 = (arrive,lambda).PC61 + (walkon1,infty).PC60;\r\n#PC61 = (serve6,infty).PC60;\r\n\r\n#S1 = (walkon2,omega).S2 + (serve1,mu).T2;\r\n#S2 = (walkon3,omega).S3 + (serve2,mu).T3;\r\n#S3 = (walkon4,omega).S4 + (serve3,mu).T4;\r\n#S4 = (walkon5,omega).S5 + (serve4,mu).T5;\r\n#S5 = (walkon6,omega).S6 + (serve5,mu).T6;\r\n#S6 = (walkon1,omega).S1 + (serve6,mu).T1;\r\n\r\n#T1 = (walk1,omega).S1;\r\n#T2 = (walk2,omega).S2;\r\n#T3 = (walk3,omega).S3;\r\n#T4 = (walk4,omega).S4;\r\n#T5 = (walk5,omega).S5;\r\n#T6 = (walk6,omega).S6;\r\n\r\n(PC10 <> PC20 <> PC30 <> PC40 <> PC50 <> PC60) <walkon1,walkon2,walkon3,walkon4,walkon5,walkon6,serve1,serve2,serve3,serve4,serve5,serve6> S1\r\n"
  },
  {
    "path": "prism-examples/pepa/README.txt",
    "content": "These examples are adapted from those on the PEPA webpage:\r\n\r\nhttp://www.dcs.ed.ac.uk/pepa/examples.html\r\n"
  },
  {
    "path": "prism-examples/pepa/auto",
    "content": "#!/bin/csh\n\nprism -importpepa badge.pepa -ss\nprism -importpepa PC-LAN4.pepa -ss\nprism -importpepa PC-LAN6.pepa -ss\n"
  },
  {
    "path": "prism-examples/pepa/badge.pepa",
    "content": "% A small model (72 states) of a location tracking system based on \r\n% active badges made by Stephen Gilmore, Jane Hillston and \r\n% Graham Clark.  The paper ``Specifying performance measures for\r\n% PEPA'' appeared in the proceedings of Fifth International AMAST \r\n% Workshop on Real-Time and Probabilistic Systems, Bamberg 1999.\r\n% The proceedings were published as Springer-Verlag LNCS 1601.\r\n\r\nm = 0.1;\r\nr = 2.5;\r\ns = 45.0;\r\n\r\n#P14 = (reg14, r).P14 + (move15, m).P15;\r\n#P15 = (reg15, r).P15 + (move14, m).P14 + (move16, m).P16;\r\n#P16 = (reg16, r).P16 + (move15, m).P15;\r\n\r\n#S14 = (reg14, infty).T14;\r\n#S15 = (reg15, infty).T15;\r\n#S16 = (reg16, infty).T16;\r\n\r\n#T14 = (rep14, s).S14;\r\n#T15 = (rep15, s).S15;\r\n#T16 = (rep16, s).S16;\r\n\r\n#DB14 = (rep14,infty).DB14 + (rep15,infty).DB15 + (rep16,infty).DB16;\r\n#DB15 = (rep14,infty).DB14 + (rep15,infty).DB15 + (rep16,infty).DB16;\r\n#DB16 = (rep14,infty).DB14 + (rep15,infty).DB15 + (rep16,infty).DB16;\r\n\r\n( P14 <reg14,reg15,reg16> (S14 <> S15 <> S16) ) <rep14, rep15, rep16> DB14\r\n"
  },
  {
    "path": "prism-examples/pomdps/crypt/README.txt",
    "content": "This case study concerns the dining cryptographers protocol [Cha88].\n\nThis is a POMDP model, described in [NPZ17].\n\n=====================================================================================\n\n[NPZ17]\nGethin Norman, David Parker and Xueyi Zou\nVerification and Control of Partially Observable Probabilistic Systems\nReal-Time Systems, 53(3), pages 354-402, Springer, 2017\n\n[Cha88]\nD. Chaum\nThe dining cryptographers problem: Unconditional sender and recipient untraceability\nJournal of Cryptology 1, 65–75, 1988\n"
  },
  {
    "path": "prism-examples/pomdps/crypt/auto",
    "content": "#!/bin/bash\n\nprism crypt3.prism crypt.props -gridresolution 8\nprism crypt4.prism crypt.props -gridresolution 8\nprism crypt5.prism crypt.props -gridresolution 8\nprism crypt6.prism crypt.props -gridresolution 8\n"
  },
  {
    "path": "prism-examples/pomdps/crypt/crypt.props",
    "content": "// Minimum probability to guess correctly which cryptographer paid\nPmin=? [ F correct=1 ]\n\n// Maximum probability to guess correctly which cryptographer paid\nPmax=? [ F correct=1 ]\n\n\n\n"
  },
  {
    "path": "prism-examples/pomdps/crypt/crypt3.prism",
    "content": "// dining cryptographers\n// gxn 27/01/16\n\n// pomdp model\npomdp\n\n// observable variables (for crypt3)\n// the announcements of all cryptographers \n// only its own coin and the coin of its left neighbour\n// if it guesses correctly (this is the target so needs to be observable)\n// also local states of modules this only indicates:\n// - if a cryptographer has announced\n// - if the master has made its choice\nobservables\n\tcoin1, coin3, m, s1, s2, s3, guess, correct, agree1, agree2, agree3\nendobservables\n\n// constants used in renaming\nconst int p1=1;\nconst int p2=2;\nconst int p3=3;\n\nmodule master\n\t\n\tm : [0..1]; // local state (has chosen who pays)\n\tpay : [1..3]; // who actually pays\n\t\n\t// randomly choose who pays\n\t[] m=0 -> 1/2 : (m'=1) & (pay'=1) + 1/2 : (m'=1) & (pay'=2);\n\t\n\t// test cases\n\t//[] m=0 -> (m'=1); // master pays\n\t//[] m=0 -> (m'=1) & (pay'=1); // crypt 1 pays\n\t//[] m=0 -> (m'=1) & (pay'=2); // crypt 2 pays\n\t//[] m=0 -> (m'=1) & (pay'=3); // crypt 3 pays\n\t\nendmodule\n\nmodule crypt1\n\t\n\tcoin1 : [0..2]; // value of coin\n\ts1 : [0..1]; // local state (has announced yet)\n\tagree1 : [0..1]; // agree or not\n\t\n\t// flip coin and share values\n\t[flip] m=1 & coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// does not pay\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay!=p1) -> (s1'=1) & (agree1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\n\t// pays\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay=p1) -> (s1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1) -> (s1'=1) & (agree1'=1);\n\n\t// when everyone has announced\n\t[done] s1=1 -> true;\n\nendmodule\n\n// construct further cryptographers through renaming\nmodule crypt2 =crypt1[coin1=coin2, s1=s2, p1=p2, agree1=agree2, coin2=coin3, choose1=choose2 ] endmodule\n\n// the cryptographer that guesses who pays\nmodule crypt3\n\t\n\tcoin3 : [0..2];\n\ts3 : [0..2];\n\tagree3 : [0..1];\n\tguess : [0..3];\n\tcorrect : [0..1];\n\t\n\t// flip coin\n\t[flip] m=1 & coin3=0 -> 0.5 : (coin3'=1) + 0.5 : (coin3'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// assume does not pay\n\t[choose3] s3=0 & coin3>0 & coin1>0 & coin3=coin1 -> (s3'=1) & (agree3'=1);\n\t[choose3] s3=0 & coin3>0 & coin1>0 & !(coin3=coin1) -> (s3'=1);\n\t// pays\n\t[choose3] s3=0 & coin3>0 & coin1>0 & coin3=coin1 & (pay=p3) -> (s3'=1);\n\t[choose3] s3=0 & coin3>0 & coin1>0 & !(coin3=coin1) & (pay=p3) -> (s3'=1) & (agree3'=1);\n\t\n\t// after everyone has announced guess who payed\n\t[done] s3=1 -> (s3'=2);\n\t[guess1] s3=2 & guess=0 -> (guess'=1);\n\t[guess2] s3=2 & guess=0 -> (guess'=2);\n\t\n\t// check whether guessed correctly\n\t[check] s3=2 & guess>0 & guess=pay -> (correct'=1);\n\t[check] s3=2 & guess>0 & !(guess=pay) -> true;\n\nendmodule\n"
  },
  {
    "path": "prism-examples/pomdps/crypt/crypt4.prism",
    "content": "// dining cryptographers\n// gxn 27/01/16\n\n// pomdp model\npomdp\n\n// observable variables (for crypt4)\n// the announcements of all cryptographers \n// only its own coin and the coin of its left neighbour\n// if it guesses correctly (this is the target so needs to be observable)\n// also local states of modules this only indicates:\n// - if a cryptographer has announced\n// - if the master has made its choice\nobservables\n\tcoin1, coin4, m, s1, s2, s3, s4, guess, correct, agree1, agree2, agree3, agree4\nendobservables\n\n// constants used in renaming\nconst int p1=1;\nconst int p2=2;\nconst int p3=3;\nconst int p4=4;\n\nmodule master\n\t\n\tm : [0..1]; // local state (has chosen who pays)\n\tpay : [1..4]; // who actually pays\n\t\n\t// randomly choose who pays\n\t[] m=0 -> 1/3 : (m'=1) & (pay'=1) + 1/3 : (m'=1) & (pay'=2) + 1/3 : (m'=1) & (pay'=3);\n\t\n\t// test cases\n\t//[] m=0 -> (m'=1); // master pays\n\t//[] m=0 -> (m'=1) & (pay'=1); // crypt 1 pays\n\t//[] m=0 -> (m'=1) & (pay'=2); // crypt 2 pays\n\t//[] m=0 -> (m'=1) & (pay'=3); // crypt 3 pays\n\t//[] m=0 -> (m'=1) & (pay'=4); // crypt 4 pays\n\t\nendmodule\n\nmodule crypt1\n\t\n\tcoin1 : [0..2]; // value of coin\n\ts1 : [0..1]; // local state (has announced yet)\n\tagree1 : [0..1]; // agree or not\n\t\n\t// flip coin and share values\n\t[flip] m=1 & coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// does not pay\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay!=p1) -> (s1'=1) & (agree1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\n\t// pays\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay=p1) -> (s1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1) -> (s1'=1) & (agree1'=1);\n\n\t// when everyone has announced\n\t[done] s1=1 -> true;\n\nendmodule\n\n// construct further cryptographers through renaming\nmodule crypt2 =crypt1[coin1=coin2, s1=s2, p1=p2, agree1=agree2, coin2=coin3, choose1=choose2 ] endmodule\nmodule crypt3 =crypt1[coin1=coin3, s1=s3, p1=p3, agree1=agree3, coin2=coin4, choose1=choose3 ] endmodule\n\n// the cryptographer that guesses who pays\nmodule crypt4\n\t\n\tcoin4 : [0..2];\n\ts4 : [0..2];\n\tagree4 : [0..1];\n\tguess : [0..3];\n\tcorrect : [0..1];\n\t\n\t// flip coin\n\t[flip] m=1 & coin4=0 -> 0.5 : (coin4'=1) + 0.5 : (coin4'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// assume does not pay\n\t[choose4] s4=0 & coin4>0 & coin1>0 & coin4=coin1 -> (s4'=1) & (agree4'=1);\n\t[choose4] s4=0 & coin4>0 & coin1>0 & !(coin4=coin1) -> (s4'=1);\n\t// pays\n\t[choose4] s4=0 & coin4>0 & coin1>0 & coin4=coin1 & (pay=p4) -> (s4'=1);\n\t[choose4] s4=0 & coin4>0 & coin1>0 & !(coin4=coin1) & (pay=p4) -> (s4'=1) & (agree4'=1);\n\t\n\t// after everyone has announced guess who payed\n\t[done] s4=1 -> (s4'=2);\n\t[guess1] s4=2 & guess=0 -> (guess'=1);\n\t[guess2] s4=2 & guess=0 -> (guess'=2);\n\t[guess3] s4=2 & guess=0 -> (guess'=3);\n\t\n\t// check whether guessed correctly\n\t[check] s4=2 & guess>0 & guess=pay -> (correct'=1);\n\t[check] s4=2 & guess>0 & !(guess=pay) -> true;\n\nendmodule\n"
  },
  {
    "path": "prism-examples/pomdps/crypt/crypt5.prism",
    "content": "// dining cryptographers\n// gxn 27/01/16\n\n// pomdp model\npomdp\n\n// observable variables (for crypt5)\n// the announcements of all cryptographers \n// only its own coin and the coin of its left neighbour\n// if it guesses correctly (this is the target so needs to be observable)\n// also local states of modules this only indicates:\n// - if a cryptographer has announced\n// - if the master has made its choice\nobservables\n\tcoin1, coin5, m, s1, s2, s3, s4, s5, guess, correct, agree1, agree2, agree3, agree4, agree5\nendobservables\n\n// constants used in renaming\nconst int p1=1;\nconst int p2=2;\nconst int p3=3;\nconst int p4=4;\nconst int p5=5;\n\nmodule master\n\t\n\tm : [0..1]; // local state (has chosen who pays)\n\tpay : [1..4]; // who actually pays\n\t\n\t// randomly choose who pays\n\t[] m=0 -> 1/4 : (m'=1) & (pay'=1) + 1/4 : (m'=1) & (pay'=2) + 1/4 : (m'=1) & (pay'=3) + 1/4 : (m'=1) & (pay'=4);\n\t\n\t// test cases\n\t//[] m=0 -> (m'=1); // master pays\n\t//[] m=0 -> (m'=1) & (pay'=1); // crypt 1 pays\n\t//[] m=0 -> (m'=1) & (pay'=2); // crypt 2 pays\n\t//[] m=0 -> (m'=1) & (pay'=3); // crypt 3 pays\n\t//[] m=0 -> (m'=1) & (pay'=4); // crypt 4 pays\n\t\nendmodule\n\nmodule crypt1\n\t\n\tcoin1 : [0..2]; // value of coin\n\ts1 : [0..1]; // local state (has announced yet)\n\tagree1 : [0..1]; // agree or not\n\t\n\t// flip coin and share values\n\t[flip] m=1 & coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// does not pay\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay!=p1) -> (s1'=1) & (agree1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\n\t// pays\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay=p1) -> (s1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1) -> (s1'=1) & (agree1'=1);\n\n\t// when everyone has announced\n\t[done] s1=1 -> true;\n\nendmodule\n\n// construct further cryptographers through renaming\nmodule crypt2 =crypt1[coin1=coin2, s1=s2, p1=p2, agree1=agree2, coin2=coin3, choose1=choose2 ] endmodule\nmodule crypt3 =crypt1[coin1=coin3, s1=s3, p1=p3, agree1=agree3, coin2=coin4, choose1=choose3 ] endmodule\nmodule crypt4 =crypt1[coin1=coin4, s1=s4, p1=p4, agree1=agree4, coin2=coin5, choose1=choose4 ] endmodule\n\n// the cryptographer that guesses who pays\nmodule crypt5\n\t\n\tcoin5 : [0..2];\n\ts5 : [0..2];\n\tagree5 : [0..1];\n\tguess : [0..3];\n\tcorrect : [0..1];\n\t\n\t// flip coin\n\t[flip] m=1 & coin5=0 -> 0.5 : (coin5'=1) + 0.5 : (coin5'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// assume does not pay\n\t[choose5] s5=0 & coin5>0 & coin1>0 & coin5=coin1 -> (s5'=1) & (agree5'=1);\n\t[choose5] s5=0 & coin5>0 & coin1>0 & !(coin5=coin1) -> (s5'=1);\n\t// pays\n\t[choose5] s5=0 & coin5>0 & coin1>0 & coin5=coin1 & (pay=p5) -> (s5'=1);\n\t[choose5] s5=0 & coin5>0 & coin1>0 & !(coin5=coin1) & (pay=p5) -> (s5'=1) & (agree5'=1);\n\t\n\t// after everyone has announced guess who payed\n\t[done] s5=1 -> (s5'=2);\n\t[guess1] s5=2 & guess=0 -> (guess'=1);\n\t[guess2] s5=2 & guess=0 -> (guess'=2);\n\t[guess3] s5=2 & guess=0 -> (guess'=3);\n\t[guess4] s5=2 & guess=0 -> (guess'=4);\n\t\n\t// check whether guessed correctly\n\t[check] s5=2 & guess>0 & guess=pay -> (correct'=1);\n\t[check] s5=2 & guess>0 & !(guess=pay) -> true;\n\nendmodule\n"
  },
  {
    "path": "prism-examples/pomdps/crypt/crypt6.prism",
    "content": "// dining cryptographers\n// gxn 27/01/16\n\n// pomdp model\npomdp\n\n// observable variables (for crypt6)\n// the announcements of all cryptographers \n// only its own coin and the coin of its left neighbour\n// if it guesses correctly (this is the target so needs to be observable)\n// also local states of modules this only indicates:\n// - if a cryptographer has announced\n// - if the master has made its choice\nobservables\n\tcoin1, coin6, m, s1, s2, s3, s4, s5, s6, guess, correct, agree1, agree2, agree3, agree4, agree5, agree6\nendobservables\n\n// constants used in renaming\nconst int p1=1;\nconst int p2=2;\nconst int p3=3;\nconst int p4=4;\nconst int p5=5;\nconst int p6=6;\n\nmodule master\n\t\n\tm : [0..1]; // local state (has chosen who pays)\n\tpay : [1..6]; // who actually pays\n\t\n\t// randomly choose who pays\n\t[] m=0 -> 1/5 : (m'=1) & (pay'=1) + 1/5 : (m'=1) & (pay'=2) + 1/5 : (m'=1) & (pay'=3) + 1/5 : (m'=1) & (pay'=4) + 1/5 : (m'=1) & (pay'=5);\n\t\n\t// test cases\n\t//[] m=0 -> (m'=1); // master pays\n\t//[] m=0 -> (m'=1) & (pay'=1); // crypt 1 pays\n\t//[] m=0 -> (m'=1) & (pay'=2); // crypt 2 pays\n\t//[] m=0 -> (m'=1) & (pay'=3); // crypt 3 pays\n\t//[] m=0 -> (m'=1) & (pay'=4); // crypt 4 pays\n\t//[] m=0 -> (m'=1) & (pay'=5); // crypt 5 pays\n\t\nendmodule\n\nmodule crypt1\n\t\n\tcoin1 : [0..2]; // value of coin\n\ts1 : [0..1]; // local state (has announced yet)\n\tagree1 : [0..1]; // agree or not\n\t\n\t// flip coin and share values\n\t[flip] m=1 & coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// does not pay\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay!=p1) -> (s1'=1) & (agree1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\n\t// pays\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay=p1) -> (s1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1) -> (s1'=1) & (agree1'=1);\n\t// when everyone has announced\n\t[done] s1=1 -> true;\n\nendmodule\n\n// construct further cryptographers through renaming\nmodule crypt2 =crypt1[coin1=coin2, s1=s2, p1=p2, agree1=agree2, coin2=coin3, choose1=choose2 ] endmodule\nmodule crypt3 =crypt1[coin1=coin3, s1=s3, p1=p3, agree1=agree3, coin2=coin4, choose1=choose3 ] endmodule\nmodule crypt4 =crypt1[coin1=coin4, s1=s4, p1=p4, agree1=agree4, coin2=coin5, choose1=choose4 ] endmodule\nmodule crypt5 =crypt1[coin1=coin5, s1=s5, p1=p5, agree1=agree5, coin2=coin6, choose1=choose5 ] endmodule\n\n// the cryptographer that guesses who pays\nmodule crypt6\n\t\n\tcoin6 : [0..2];\n\ts6 : [0..2];\n\tagree6 : [0..1];\n\tguess : [0..5];\n\tcorrect : [0..1];\n\t\n\t// flip coin\n\t[flip] m=1 & coin6=0 -> 0.5 : (coin6'=1) + 0.5 : (coin6'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// assume does not pay\n\t[choose6] s6=0 & coin6>0 & coin1>0 & coin6=coin1 -> (s6'=1) & (agree6'=1);\n\t[choose6] s6=0 & coin6>0 & coin1>0 & !(coin6=coin1) -> (s6'=1);\n\t// pays\n\t[choose6] s6=0 & coin6>0 & coin1>0 & coin6=coin1 & (pay=p6) -> (s6'=1);\n\t[choose6] s6=0 & coin6>0 & coin1>0 & !(coin6=coin1) & (pay=p6) -> (s6'=1) & (agree6'=1);\n\t\n\t// after everyone has announced guess who payed\n\t[done] s6=1 -> (s6'=2);\n\t[guess1] s6=2 & guess=0 -> (guess'=1);\n\t[guess2] s6=2 & guess=0 -> (guess'=2);\n\t[guess3] s6=2 & guess=0 -> (guess'=3);\n\t[guess4] s6=2 & guess=0 -> (guess'=4);\n\t[guess5] s6=2 & guess=0 -> (guess'=5);\n\t\n\t// check whether guessed correctly\n\t[check] s6=2 & guess>0 & guess=pay -> (correct'=1);\n\t[check] s6=2 & guess>0 & !(guess=pay) -> true;\n\nendmodule\n"
  },
  {
    "path": "prism-examples/pomdps/gridworld/3x3grid.prism",
    "content": "// 3x3 grid\n// based on Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n\npomdp\n\nconst int N = 3; // grid size\n\n// only the target is observable which is in the south east corner\n// (also if the initialisation step has been done)\nformula target = x=N-1 & y=0;\nobservable \"target\" = target;\nobservable \"started\" = started;\n\nmodule grid\n\t\n\tx : [0..N-1]; // x coordinate\n\ty : [0..N-1]; // y coordinate\n\tstarted : bool; // initialised?\n\t\n\t// initially randomly placed within the grid (not at the target)\n\t[] !started -> 1/8 : (started'=true) & (x'=0) & (y'=0)\n\t\t\t+ 1/8 : (started'=true) & (x'=0) & (y'=1)\n\t\t\t+ 1/8 : (started'=true) & (x'=0) & (y'=2)\n\t\t\t+ 1/8 : (started'=true) & (x'=1) & (y'=0)\n\t\t\t+ 1/8 : (started'=true) & (x'=1) & (y'=1)\n\t\t\t+ 1/8 : (started'=true) & (x'=1) & (y'=2)\n\t\t\t// + 1/8 : (started'=true) & (x'=2) & (y'=0) the target\n\t\t\t+ 1/8 : (started'=true) & (x'=2) & (y'=1)\n\t\t\t+ 1/8 : (started'=true) & (x'=2) & (y'=2);\n\t\t\t\n\t// move around the grid\n\t[east] started & !target -> (x'=min(x+1,N-1));\n\t[west] started & !target -> (x'=max(x-1,0));\n\t[north] started & !target -> (x'=min(y+1,N-1));\n\t[south] started & !target -> (y'=max(y-1,0));\n\t\n\t// reached target\n\t[done] target -> true;\n\t\nendmodule\n\n// reward structure for number of steps to reach the target\nrewards\n        [east] true : 1;\n        [west] true : 1;\n        [north] true : 1;\n        [south] true : 1;\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/gridworld/3x3grid_bounded.prism",
    "content": "// 3x3 grid (for step bounded properties)\n// based on Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n\npomdp\n\nconst int N = 3; // grid size\nconst int K; // step bound in property\n\n// only the target is observable which is in the south east corner\n// (also if the initialisation step has been done and the step count)\nformula target = x=N-1 & y=0;\nobservable \"target\" = target;\nobservable \"started\" = started;\nobservable \"k\" = k;\n\nmodule grid\n\t\n\tx : [0..N-1]; // x coordinate\n\ty : [0..N-1]; // y coordinate\n\tstarted : bool; // initialised?\n\t\n\t// initially randomly placed within the grid (not at the target)\n\t[] !started -> 1/8 : (started'=true) & (x'=0) & (y'=0)\n\t\t\t+ 1/8 : (started'=true) & (x'=0) & (y'=1)\n\t\t\t+ 1/8 : (started'=true) & (x'=0) & (y'=2)\n\t\t\t+ 1/8 : (started'=true) & (x'=1) & (y'=0)\n\t\t\t+ 1/8 : (started'=true) & (x'=1) & (y'=1)\n\t\t\t+ 1/8 : (started'=true) & (x'=1) & (y'=2)\n\t\t\t// + 1/8 : (started'=true) & (x'=2) & (y'=0) the target\n\t\t\t+ 1/8 : (started'=true) & (x'=2) & (y'=1)\n\t\t\t+ 1/8 : (started'=true) & (x'=2) & (y'=2);\n\t\t\t\n\t// move around the grid\n\t[east] started & !target -> (x'=min(x+1,N-1));\n\t[west] started & !target -> (x'=max(x-1,0));\n\t[north] started & !target -> (x'=min(y+1,N-1));\n\t[south] started & !target -> (y'=max(y-1,0));\n\t\n\t// reached target\n\t[done] target -> true;\n\t\nendmodule\n\n// module for the step bound\nmodule bound\n\n\tk : [0..K];\n\t\n\t[east] k<K -> (k'=k+1);\n\t[west] k<K -> (k'=k+1);\n\t[north] k<K -> (k'=k+1);\n\t[south] k<K -> (k'=k+1);\n\t\n\t[] k=K -> true;\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/pomdps/gridworld/4x4grid.prism",
    "content": "// 4x4 grid\n// from Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n\npomdp\n\nconst int N = 4; // grid size\n\n// only the target is observable which is in the south east corner\n// (also if the initialisation step has been done)\nformula target = x=N-1 & y=0;\nobservable \"target\" = target;\nobservable \"started\" = started;\n\nmodule grid\n\t\n\tx : [0..N-1]; // x coordinate\n\ty : [0..N-1]; // y coordinate\n\tstarted : bool; // initialised?\n\t\n\t// initially randomly placed within the grid (not at the target)\n\t[] !started -> 1/15 : (started'=true) & (x'=0) & (y'=0)\n\t\t\t+ 1/15 : (started'=true) & (x'=0) & (y'=1)\n\t\t\t+ 1/15 : (started'=true) & (x'=0) & (y'=2)\n\t\t\t+ 1/15 : (started'=true) & (x'=0) & (y'=3)\n\t\t\t+ 1/15 : (started'=true) & (x'=1) & (y'=0)\n\t\t\t+ 1/15 : (started'=true) & (x'=1) & (y'=1)\n\t\t\t+ 1/15 : (started'=true) & (x'=1) & (y'=2)\n\t\t\t+ 1/15 : (started'=true) & (x'=1) & (y'=3)\t\n\t\t\t+ 1/15 : (started'=true) & (x'=2) & (y'=0)\n\t\t\t+ 1/15 : (started'=true) & (x'=2) & (y'=1)\n\t\t\t+ 1/15 : (started'=true) & (x'=2) & (y'=2)\n\t\t\t+ 1/15 : (started'=true) & (x'=2) & (y'=3)\t\n\t\t\t// + 1/15 : (started'=true) & (x'=3) & (y'=0) the target\n\t\t\t+ 1/15 : (started'=true) & (x'=3) & (y'=1)\n\t\t\t+ 1/15 : (started'=true) & (x'=3) & (y'=2)\n\t\t\t+ 1/15 : (started'=true) & (x'=3) & (y'=3);\n\t\t\t\n\t// move around the grid\n\t[east] started & !target -> (x'=min(x+1,N-1));\n\t[west] started & !target -> (x'=max(x-1,0));\n\t[north] started & !target -> (x'=min(y+1,N-1));\n\t[south] started & !target -> (y'=max(y-1,0));\n\t\n\t// reached target\n\t[done] target -> true;\n\t\nendmodule\n\n// reward structure for number of steps to reach the target\nrewards\n        [east] true : 1;\n        [west] true : 1;\n        [north] true : 1;\n        [south] true : 1;\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/gridworld/4x4grid_bounded.prism",
    "content": "// 4x4 grid (for step bounded properties)\n// based on Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n// gxn 29/01/16\n\npomdp\n\nconst int N = 4; // grid size\nconst int K; // step bound in property\n\n// only the target is observable which is in the south east corner\n// (also if the initialisation step has been done and the step count)\nformula target = x=N-1 & y=0;\nobservable \"target\" = target;\nobservable \"started\" = started;\nobservable \"k\" = k;\n\nmodule grid\n\t\n\tx : [0..N-1]; // x coordinate\n\ty : [0..N-1]; // y coordinate\n\tstarted : bool; // initialised?\n\t\n\t// initially randomly placed within the grid (not at the target)\n\t[] !started -> 1/15 : (started'=true) & (x'=0) & (y'=0)\n\t\t\t+ 1/15 : (started'=true) & (x'=0) & (y'=1)\n\t\t\t+ 1/15 : (started'=true) & (x'=0) & (y'=2)\n\t\t\t+ 1/15 : (started'=true) & (x'=0) & (y'=3)\n\t\t\t+ 1/15 : (started'=true) & (x'=1) & (y'=0)\n\t\t\t+ 1/15 : (started'=true) & (x'=1) & (y'=1)\n\t\t\t+ 1/15 : (started'=true) & (x'=1) & (y'=2)\n\t\t\t+ 1/15 : (started'=true) & (x'=1) & (y'=3)\t\n\t\t\t+ 1/15 : (started'=true) & (x'=2) & (y'=0)\n\t\t\t+ 1/15 : (started'=true) & (x'=2) & (y'=1)\n\t\t\t+ 1/15 : (started'=true) & (x'=2) & (y'=2)\n\t\t\t+ 1/15 : (started'=true) & (x'=2) & (y'=3)\t\n\t\t\t// + 1/15 : (started'=true) & (x'=3) & (y'=0) the target\n\t\t\t+ 1/15 : (started'=true) & (x'=3) & (y'=1)\n\t\t\t+ 1/15 : (started'=true) & (x'=3) & (y'=2)\n\t\t\t+ 1/15 : (started'=true) & (x'=3) & (y'=3);\n\t\t\t\n\t// move around the grid\n\t[east] started & !target -> (x'=min(x+1,N-1));\n\t[west] started & !target -> (x'=max(x-1,0));\n\t[north] started & !target -> (x'=min(y+1,N-1));\n\t[south] started & !target -> (y'=max(y-1,0));\n\t\n\t// reached target\n\t[done] target -> true;\n\t\nendmodule\n\n// module for the step bound\nmodule bound\n\n\tk : [0..K];\n\t\n\t[east] k<K -> (k'=k+1);\n\t[west] k<K -> (k'=k+1);\n\t[north] k<K -> (k'=k+1);\n\t[south] k<K -> (k'=k+1);\n\t\n\t[] k=K -> true;\n\t\nendmodule\n"
  },
  {
    "path": "prism-examples/pomdps/gridworld/README.txt",
    "content": "This case study concerns a grid-world robot from [LCK95].\n\nThis is a POMDP model, described in [NPZ17].\n\n=====================================================================================\n\n[LCK95]\nM. Littman, A. Cassandra and L. Kaelbling\nLearning policies for partially observable environments: Scaling up.\nTech. Rep. CS-95-11, Department of Computer Science, Brown University, 1995\n\n[NPZ17]\nGethin Norman, David Parker and Xueyi Zou\nVerification and Control of Partially Observable Probabilistic Systems\nReal-Time Systems, 53(3), pages 354-402, Springer, 2017\n"
  },
  {
    "path": "prism-examples/pomdps/gridworld/auto",
    "content": "#!/bin/bash\n\nprism 3x3grid.prism grid.props\nprism 4x4grid.prism grid.props\n\nprism 3x3grid_bounded.prism grid_bounded.props -const K=2\nprism 4x4grid_bounded.prism grid_bounded.props -const K=2\n"
  },
  {
    "path": "prism-examples/pomdps/gridworld/grid.props",
    "content": "// Minimum steps to reach goal\nRmin=? [ F \"target\" ]\n"
  },
  {
    "path": "prism-examples/pomdps/gridworld/grid_bounded.props",
    "content": "// Maximum probability to reach goal (for use with step bound property)\nPmax=? [ F \"target\" ]\n"
  },
  {
    "path": "prism-examples/pomdps/network/README.txt",
    "content": "This case study concerns wireless downlink scheduling of traffic to a number\nof different users with hard deadlines and where packets have priorities.\n\nThis is a POMDP model, described in [NPZ17], and based on [YMZ11].\n\nModel variants:\n* without priorities: network2.prism and network3.prism\n* without priorities and no idling: network2_noidle.prism and network3_noidle.prism\n* with priorities: network2_priorities.prism and network3_priorities.prism\n* with priorities and no idling: network2_priorities_noidle.prism and network3_priorities_noidle.prism\n\nProperty files: network.props and network_priorities.props\n\n=====================================================================================\n\nPARAMETERS:\n\nT: number of slots per time period\nK: number of time periods\n\n=====================================================================================\n\n[NPZ17]\nGethin Norman, David Parker and Xueyi Zou\nVerification and Control of Partially Observable Probabilistic Systems\nReal-Time Systems, 53(3), pages 354-402, Springer, 2017\n\n[YMZ11]\nL. Yang, S. Murugesan and J. Zhang\nReal-time scheduling over Markovian channels: When partial observability meets hard deadlines\nIn Proc. Global Telecommunications Conference (GLOBECOM’11), pp. 1–5, 2011\n"
  },
  {
    "path": "prism-examples/pomdps/network/auto",
    "content": "#!/bin/bash\n\n# Without priorities\n\nprism network2.prism -const K=20,T=2 network.props\n#prism network3.prism -const K=20,T=2 network.props\n\nprism network2_noidle.prism -const K=20,T=2 network.props\n#prism network3_noidle.prism -const K=20,T=2 network.props\n\n# With priorities\n\nprism network2_priorities.prism -const K=20,T=2 network_priorities.props\n#prism network3_priorities.prism -const K=20,T#=2 network_priorities.props\n\nprism network2_priorities_noidle.prism -const K=20,T=2 network_priorities.props\n#prism network3_priorities_noidle.prism -const K=20,T=2 network_priorities.props\n"
  },
  {
    "path": "prism-examples/pomdps/network/network.props",
    "content": "// Minimum number of dropped packets\nR{\"dropped_packets\"}min=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// Maximum number of packets sent (dual property)\nR{\"packets_sent\"}max=?[F sched=0 & t=T-1 & k=K-1 ]\n"
  },
  {
    "path": "prism-examples/pomdps/network/network2.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2 //, chan1, chan2\nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\n\t// loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/network/network2_noidle.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2 //, chan1, chan2\nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 & packet1=0 & packet2=0 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\n\t// loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/network/network2_priorities.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2, priority1, priority2 //, chan1, chan2, \nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\n    // loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\n\n// priority of packets for first channel\nmodule priority1\n\n\tpriority1 : [0..3];\n\t\n\t// new period so new packet and randomly assign priority\n\t[slot] t=0 -> 0.1 : (priority1'=1) + 0.3 : (priority1'=2) + 0.6 : (priority1'=3);\n\t// priority already assigned for this period\n\t[slot] t>0 -> true;\n\t\n\t// reset priority when packet has been sent\n\t[send1] chan1=0 -> true;\n\t[send1] chan1=1 -> (priority1'=0);\n\t\nendmodule\n\n// construct further priorities through renaming\nmodule priority2 = priority1[priority1=priority2,chan1=chan2,send1=send2] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\nendrewards\n\nconst double beta=1; // discount factor\n\n// (discounted) reward structure based on priorities \nrewards \"priority\"\n\t[send1] chan1=1 & priority1=1 :  1 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=1 :  1 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=2 : 10 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=2 : 10 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=3 : 20 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=3 : 20 * pow(beta,t + k*T);\nendrewards"
  },
  {
    "path": "prism-examples/pomdps/network/network2_priorities_noidle.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2, priority1, priority2 //, chan1, chan2, \nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 & packet1=0 & packet2=0 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\n    // loop when finished\n    [] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,chan1=chan2] endmodule\n\n// priority of packets for first channel\nmodule priority1\n\n\tpriority1 : [0..3];\n\t\n\t// new period so new packet and randomly assign priority\n\t[slot] t=0 -> 0.1 : (priority1'=1) + 0.3 : (priority1'=2) + 0.6 : (priority1'=3);\n\t// priority already assigned for this period\n\t[slot] t>0 -> true;\n\t\n\t// reset priority when packet has been sent\n\t[send1] chan1=0 -> true;\n\t[send1] chan1=1 -> (priority1'=0);\n\t\nendmodule\n\n// construct further priorities through renaming\nmodule priority2 = priority1[priority1=priority2,chan1=chan2,send1=send2] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,send1=send2,p1=p2,r1=r2] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\nendrewards\n\nconst double beta=1; // discount factor\n\n// (discounted) reward structure based on priorities \nrewards \"priority\"\n\t[send1] chan1=1 & priority1=1 :  1 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=1 :  1 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=2 : 10 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=2 : 10 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=3 : 20 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=3 : 20 * pow(beta,t + k*T);\nendrewards"
  },
  {
    "path": "prism-examples/pomdps/network/network3.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2, packet3 //, chan1, chan2, chan3\nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n// channel of user 3\nconst double p3 = 0.7; // prob remain on\nconst double r3 = 0.3; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\t[send3] sched=1 -> (sched'=0);\n\n\t// loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\nmodule packet3=packet1[packet1=packet3,send1=send3,chan1=chan3] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\nmodule channel3=channel1[chan1=chan3,p1=p3,r1=r3] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send3] t=T-1 & k=K-1 & chan3=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1) + ((packet3=0)?0:1);\n\t[send3] t=T-1 & k=K-1 & chan3=1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\n\t[send3] chan3=1 : 1;\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/network/network3_noidle.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2, packet3 //, chan1, chan2, chan3\nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n// channel of user 3\nconst double p3 = 0.7; // prob remain on\nconst double r3 = 0.3; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 & packet1=0 & packet2=0 & packet3=0 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\t[send3] sched=1 -> (sched'=0);\n\n\t// loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\n\t\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\nmodule packet3=packet1[packet1=packet3,send1=send3,chan1=chan3] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\nmodule channel3=channel1[chan1=chan3,p1=p3,r1=r3] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send3] t=T-1 & k=K-1 & chan3=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1) + ((packet3=0)?0:1);\n\t[send3] t=T-1 & k=K-1 & chan3=1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\n\t[send3] chan3=1 : 1;\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/network/network3_priorities.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2, packet3, priority1, priority2, priority3 //, chan1, chan2, chan3\nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n// channel of user 3\nconst double p3 = 0.7; // prob remain on\nconst double r3 = 0.3; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\t[send3] sched=1 -> (sched'=0);\n\n\t// loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\t\n\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\nmodule packet3=packet1[packet1=packet3,send1=send3,chan1=chan3] endmodule\n\n// priority of the packets for channel 1\nmodule priority1\n\n\tpriority1 : [0..3];\n\t\n\t// new period so new packet and randomly assign priority\n\t[slot] t=0 -> 0.1 : (priority1'=1) + 0.3 : (priority1'=2) + 0.6 : (priority1'=3);\n\t// priority already assigned for this period\n\t[slot] t>0 -> true;\n\t\n\t// reset priority when packet has been sent\n\t[send1] chan1=0 -> true;\n\t[send1] chan1=1 -> (priority1'=0);\n\t\nendmodule\n\n// construct further priorities through renaming\nmodule priority2 = priority1[priority1=priority2,chan1=chan2,send1=send2] endmodule\nmodule priority3 = priority1[priority1=priority3,chan1=chan3,send1=send3] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\nmodule channel3=channel1[chan1=chan3,p1=p3,r1=r3] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send3] t=T-1 & k=K-1 & chan3=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1) + ((packet3=0)?0:1);\n\t[send3] t=T-1 & k=K-1 & chan3=1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\n\t[send3] chan3=1 : 1;\nendrewards\n\nconst double beta=1; // discount factor\n\n// (discounted) reward structure based on priorities\nrewards \"priority\"\n\t[send1] chan1=1 & priority1=1 : 1 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=1 : 1 * pow(beta,t + k*T);\n\t[send3] chan3=1 & priority3=1 : 1 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=2 : 10 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=2 : 10 * pow(beta,t + k*T);\n\t[send3] chan3=1 & priority3=2 : 10 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=3 : 20 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=3 : 20 * pow(beta,t + k*T);\n\t[send3] chan3=1 & priority3=3 : 20 * pow(beta,t + k*T);\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/network/network3_priorities_noidle.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2, packet3, priority1, priority2, priority3 //, chan1, chan2, chan3\nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n// channel of user 3\nconst double p3 = 0.7; // prob remain on\nconst double r3 = 0.3; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 & packet1=0 & packet2=0 & packet3=0 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\t[send3] sched=1 -> (sched'=0);\n\n\t// loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\t\n\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\nmodule packet3=packet1[packet1=packet3,send1=send3,chan1=chan3] endmodule\n\n// priority of the packets for channel 1\nmodule priority1\n\n\tpriority1 : [0..3];\n\t\n\t// new period so new packet and randomly assign priority\n\t[slot] t=0 -> 0.1 : (priority1'=1) + 0.3 : (priority1'=2) + 0.6 : (priority1'=3);\n\t// priority already assigned for this period\n\t[slot] t>0 -> true;\n\t\n\t// reset priority when packet has been sent\n\t[send1] chan1=0 -> true;\n\t[send1] chan1=1 -> (priority1'=0);\n\t\nendmodule\n\n// construct further priorities through renaming\nmodule priority2 = priority1[priority1=priority2,chan1=chan2,send1=send2] endmodule\nmodule priority3 = priority1[priority1=priority3,chan1=chan3,send1=send3] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\nmodule channel3=channel1[chan1=chan3,p1=p3,r1=r3] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send3] t=T-1 & k=K-1 & chan3=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1) + ((packet3=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1) + ((packet3=0)?0:1);\n\t[send3] t=T-1 & k=K-1 & chan3=1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\n\t[send3] chan3=1 : 1;\nendrewards\n\nconst double beta=1; // discount factor\n\n// (discounted) reward structure based on priorities\nrewards \"priority\"\n\t[send1] chan1=1 & priority1=1 : 1 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=1 : 1 * pow(beta,t + k*T);\n\t[send3] chan3=1 & priority3=1 : 1 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=2 : 10 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=2 : 10 * pow(beta,t + k*T);\n\t[send3] chan3=1 & priority3=2 : 10 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=3 : 20 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=3 : 20 * pow(beta,t + k*T);\n\t[send3] chan3=1 & priority3=3 : 20 * pow(beta,t + k*T);\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/network/network_priorities.props",
    "content": "// Minimum number of dropped packets\nR{\"dropped_packets\"}min=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// Maximum number of packets sent (dual property)\nR{\"packets_sent\"}max=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// Maximum reward (based on priorities)\nR{\"priority\"}max=?[F sched=0 & t=T-1 & k=K-1 ]"
  },
  {
    "path": "prism-examples/pomdps/simple/guess-multi.prism",
    "content": "// Simple POMDP guessing a hidden variable (multiple attempts)\n\npomdp\n\n// Number of guesses allowed (N=1,2,3,4)\nconst int N;\n\nobservables s, g endobservables\n\nmodule M\n\n\ts : [0..3]; // state\n\th : [0..3]; // hidden var\n\tg : [0..N] init N; // num guesses left\n\n\t// Assign hidden variable randomly\n\t[toss] s=0 -> 0.1:(s'=1)&(h'=1) + 0.3:(s'=1)&(h'=2) + 0.6:(s'=1)&(h'=3);\n\t// Guess the value of the hidden variable\n\t[guess1] s=1&g>0 -> (s'=(h=1)?2:s) & (g'=g-1);\n\t[guess2] s=1&g>0 -> (s'=(h=2)?2:s) & (g'=g-1);\n\t[guess3] s=1&g>0 -> (s'=(h=3)?2:s) & (g'=g-1);\n\t// No more guesses left\n\t[timeup] s=1&g=0 -> (s'=3);\n\t// Done\n\t[loop] s=2 -> true;\n\nendmodule\n\nlabel \"correct\" = s=2;\n\n// Number of guesses made\nrewards \"guesses\"\n\t[guess1] true : 1;\n\t[guess2] true : 1;\n\t[guess3] true : 1;\nendrewards\n\n"
  },
  {
    "path": "prism-examples/pomdps/simple/guess-multi.props",
    "content": "// Maximum probability of guessing the value correctly\n// (should be 1 for N>=3)\nPmax=? [ F \"correct\" ];\n\n// Minimum expected number of guesses before guessing the value correctly\n// (will be infinite for N<3)\nR{\"guesses\"}min=? [ F \"correct\" ];\n"
  },
  {
    "path": "prism-examples/pomdps/simple/guess.prism",
    "content": "// Simple POMDP guessing a hidden variable\n\npomdp\n\nobservables s endobservables\n\nmodule M\n\n\ts : [0..3]; // state\n\th : [0..3]; // hidden var\n\n\t// Assign hidden variable randomly\n\t[toss] s=0 -> 0.1:(s'=1)&(h'=1) + 0.3:(s'=1)&(h'=2) + 0.6:(s'=1)&(h'=3);\n\t// Guess the value of the hidden variable\n\t[guess1] s=1 -> (s'=(h=1)?2:3);\n\t[guess2] s=1 -> (s'=(h=2)?2:3);\n\t[guess3] s=1 -> (s'=(h=3)?2:3);\n\t// Done\n\t[loop] s=2 -> true;\n\nendmodule\n\nlabel \"correct\" = s=2;\n"
  },
  {
    "path": "prism-examples/pomdps/simple/guess.props",
    "content": "// Maximum probability of guessing the value correctly\n// (equals the probability of the most likely value)\nPmax=? [ F \"correct\" ];\n"
  },
  {
    "path": "prism-examples/pomdps/simple/maze.prism",
    "content": "// maze example (POMDP)\n// Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n// gxn 29/01/16\n\n// state space (value of variable \"s\")\n\n//  0  1  2  3  4\n//  5     6     7\n//  8     10    9\n\n// 10 is the target\n\npomdp\n\n// can observe the walls and target\nobservable \"west\" = s=0|s=5|s=6|s=7|s=8|s=9|s=10; // wall to the west\nobservable \"east\" = s=4|s=5|s=6|s=7|s=8|s=9|s=10; // wall to the east\nobservable \"north\" = s=0|s=1|s=2|s=3|s=4; // wall to the north\nobservable \"south\" = s=1|s=3|s=8|s=9|s=10; // wall to the south\nobservable \"target\" = s=10; //target\n\nmodule maze\n\n\ts : [-1..10];\n\t\n\t// initialisation\n\t[] s=-1 -> 0.1 : (s'=0)\n\t\t\t + 0.1 : (s'=1)\n\t\t\t + 0.1 : (s'=2)\n\t\t\t + 0.1 : (s'=3)\n\t\t\t + 0.1 : (s'=4)\n\t\t\t + 0.1 : (s'=5)\n\t\t\t + 0.1 : (s'=6)\n\t\t\t + 0.1 : (s'=7)\n\t\t\t + 0.1 : (s'=8)\n\t\t\t + 0.1 : (s'=9);\n\t\n\t// moving around the maze\n\n\t[east] s=0 -> (s'=1);\n\t[south] s=0 -> (s'=5);\n\n\t[east] s=1 -> (s'=2);\n\t[west] s=1 -> (s'=0);\n\n\t[east] s=2 -> (s'=3);\n\t[west] s=2 -> (s'=1);\n\t[south] s=2 -> (s'=6);\n\n\t[east] s=3 -> (s'=4);\n\t[west] s=3 -> (s'=2);\n\n\t[west] s=4 -> (s'=3);\n\t[south] s=4 -> (s'=7);\n\n\t[north] s=5 -> (s'=0);\n\t[south] s=5 -> (s'=8);\n\n\t[north] s=6 -> (s'=2);\n\t[south] s=6 -> (s'=10);\n\n\t[north] s=7 -> (s'=4);\n\t[south] s=7 -> (s'=9);\n\n\t[north] s=8 -> (s'=5);\n\n\t[north] s=9 -> (s'=7);\n\n\t// loop when we reach the target\n\t[done] s=10 -> true;\n\nendmodule\n\n// reward structure (number of steps to reach the target)\nrewards\n\n\t[east] true : 1;\n\t[west] true : 1;\n\t[north] true : 1;\n\t[south] true : 1;\n\nendrewards\n"
  },
  {
    "path": "prism-examples/pomdps/simple/maze.props",
    "content": "// Minimum expected number of steps to reach the target\nRmin=? [ F \"target\" ]\n"
  },
  {
    "path": "prism-examples/pomdps/simple/maze2.prism",
    "content": "// maze example (POMDP)\n// slightly extends that presented in\n// Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n// gxn 29/01/16\n\n// state space (value of variable \"s\")\n\n//  0  1  2  3  4\n//  5     6     7\n//  8     9    10\n// 11     13   12\n\n// 13 is the target\n\npomdp\n\n// can observe the walls and target\nobservable \"west\" = s=0|s=5|s=6|s=7|s=8|s=9|s=10|s=11|s=12|s=13; // wall to the west\nobservable \"east\" = s=4|s=5|s=6|s=7|s=8|s=9|s=10|s=10|s=11|s=12|s=13; // wall to the east\nobservable \"north\" = s=0|s=1|s=2|s=3|s=4; // wall to the north\nobservable \"south\" = s=1|s=3|s=11|s=12|s=13; // wall to the south\nobservable \"target\" = s=13; //target\n\nmodule maze\n\n\ts : [-1..13];\n\t\n\t// initialisation\n\t[] s=-1 -> 1/13 : (s'=0)\n\t\t\t + 1/13 : (s'=1)\n\t\t\t + 1/13 : (s'=2)\n\t\t\t + 1/13 : (s'=3)\n\t\t\t + 1/13 : (s'=4)\n\t\t\t + 1/13 : (s'=5)\n\t\t\t + 1/13 : (s'=6)\n\t\t\t + 1/13 : (s'=7)\n\t\t\t + 1/13 : (s'=8)\n\t\t\t + 1/13 : (s'=9)\n\t\t\t + 1/13 : (s'=10)\n\t\t\t + 1/13 : (s'=11)\n\t\t\t + 1/13 : (s'=12);\n\t\n\t// moving around the maze\n\t\n\t[east] s=0 -> (s'=1);\n\t[south] s=0 -> (s'=5);\n\n\t[east] s=1 -> (s'=2);\n\t[west] s=1 -> (s'=0);\n\n\t[east] s=2 -> (s'=3);\n\t[west] s=2 -> (s'=1);\n\t[south] s=2 -> (s'=6);\n\n\t[east] s=3 -> (s'=4);\n\t[west] s=3 -> (s'=2);\n\n\t[west] s=4 -> (s'=3);\n\t[south] s=4 -> (s'=7);\n\n\t[north] s=5 -> (s'=0);\n\t[south] s=5 -> (s'=8);\n\n\t[north] s=6 -> (s'=2);\n\t[south] s=6 -> (s'=9);\n\n\t[north] s=7 -> (s'=4);\n\t[south] s=7 -> (s'=10);\n\n\t[north] s=8 -> (s'=5);\n\t[south] s=8 -> (s'=11);\n\n\t[north] s=9 -> (s'=6);\n\t[south] s=9 -> (s'=13);\n\n\t[north] s=10 -> (s'=7);\n\t[south] s=10 -> (s'=12);\n\n\t[north] s=11 -> (s'=8);\n\n\t[north] s=12 -> (s'=10);\n\n\t// loop when we reach the target\n\t[done] s=13 -> true;\n\nendmodule\n\n// reward structure (number of steps to reach the target)\nrewards\n\n\t[east] true : 1;\n\t[west] true : 1;\n\t[north] true : 1;\n\t[south] true : 1;\n\nendrewards\n"
  },
  {
    "path": "prism-examples/poptas/pump/README.txt",
    "content": "This case study concerns the NRL (Naval Research Laboratory) pump,\nwhich is designed to provide reliable and secure communication over networks of\nnodes with 'high' and 'low' security levels, preventing the channel leaking\ninformation through the timing of messages and acknowledgements. \n\nIt is modelled as a partially observable probabilistic timed automaton (POPTA),\nas described in [NPZ17]. This extends the PTA model of [LMS+14].\nThe design of the NRL pump itself is presented in [KMM98].\n\n=====================================================================================\n\nPARAMETERS:\n\nh0: delay added when high sends a 0\nh1: delay added when high sends a 1\nN: number of messages low can send before guessing\n\n=====================================================================================\n\n[KMM98]\nM. Kang, A. Moore and I. Moskowitz\nDesign and assurance strategy for the NRL pump\nComputer 31(4), 56–64,1998\n\n[LMS+14]\nR. Lanotte, A. Maggiolo-Schettini, S. Tini, A. Troina and E. Tronci\nAutomatic analysis of the NRL pump\nENTCS, 99:245–266, 2014\n\n[NPZ17]\nGethin Norman, David Parker and Xueyi Zou\nVerification and Control of Partially Observable Probabilistic Systems\nReal-Time Systems, 53(3), pages 354-402, Springer, 2017\n"
  },
  {
    "path": "prism-examples/poptas/pump/auto",
    "content": "#!/bin/bash\n\nprism pump.prism pump.props -prop 1 -const h0=2,h1=16,N=2 -gridresolution 40\nprism pump.prism pump.props -prop 1 -const h0=2,h1=16,N=16 -gridresolution 2\n\nprism pump.prism pump.props -prop 2 -const h0=2,h1=16,N=2 -gridresolution 40\nprism pump.prism pump.props -prop 2 -const h0=2,h1=16,N=16 -gridresolution 2\n\nprism pump.prism pump.props -prop 3 -const h0=2,h1=16,N=2,D=25 -gridresolution 40\nprism pump.prism pump.props -prop 3 -const h0=2,h1=16,N=16,D=25 -gridresolution 2\n\nprism pump.prism pump.props -prop 4 -const h0=2,h1=16,N=2,D=25 -gridresolution 40\nprism pump.prism pump.props -prop 4 -const h0=2,h1=16,N=16,D=25 -gridresolution 2\n\n# expected time (slow to converge)\n# prism pump.prism pump.props -prop 5 -const h0=2,h1=16,N=2 -gridresolution 40\n# prism pump.prism pump.props -prop 5 -const h0=2,h1=16,N=16 -gridresolution 2\n# prism pump.prism pump.props -prop 6 -const h0=2,h1=16,N=2 -gridresolution 40\n# prism pump.prism pump.props -prop 6 -const h0=2,h1=16,N=16 -gridresolution 2\n"
  },
  {
    "path": "prism-examples/poptas/pump/pump.prism",
    "content": "// POPTA model of NRL pump\r\n// dxp/gxn 28/08/14\r\n\r\n// high is trying to send either 0 or 1 to low through a number of messages\r\n// we assume high uses delays h0 and h1 to transmit either 0 or 1\r\n// also assume high always sends with this delay\r\n// so this is the average recorded by the pump\r\n// low sends repeated messages to try and figure out what high is transmitting\r\n// based on the time until it receives acks for the messages from the pump\r\n\r\n// model is a POPTA\r\npopta\r\n\r\n// can see the state of the pump and its local variables and all clocks\r\nobservables\r\n\th, p, l, m, guess, correct, x, y\r\nendobservables\r\n\r\n// delays for high sending 0 and 1 (both need to be >1)\r\nconst int h0;\r\nconst int h1;\r\n\r\n// number of messages low can send before guessing\r\nconst int N;\r\n\r\n// timeout for low (means a nack and low resends message)\r\nconst int Tout = 10;\r\n\r\n// we do not need to model high getting messages and sending acks\r\n// as we assume the delay is fixed (depending on what it is trying to send to low)\r\n// and only the average time for high to respond influence the time the pump\r\n// delays before sending acks to low\r\n\r\nmodule high\r\n\r\n\th : [0..1] init 0; // local state\r\n\t// 0 choose bit\r\n\t// 1 done\r\n\t\r\n\tbit : [-1..1] init -1; // bit high is trying transmit\r\n\r\n\t// randomly choose bit it is trying to send to low\r\n\t[] h=0 -> 1/2 : (h'=1)&(bit'=0) + 1/2 : (h'=1)&(bit'=1);\r\n\r\nendmodule\r\n\r\nmodule pump\r\n\t\r\n\tp : [0..2] init 0; // local state\r\n\t// 0 get message from low\r\n\t// 1 delaying before ack\r\n\t// 2 sending ack\r\n\t\r\n\ty : clock; // the pump's clock\r\n\r\n\tinvariant\r\n    \t(p=0 => true) &\r\n    \t(p=1 => y<=1) &\r\n        (p=2 => y<=0)\r\n    endinvariant\r\n\t\r\n\t// get message from low (need high to choose first)\r\n\t[mess_l] p=0 & bit>=0 -> (p'=1) & (y'=0);\r\n\t\r\n\t// random delay before ack based on average from high\r\n\t// this would be letting time pass PTA model\r\n\t[] p=1 & bit=0 & y=1 -> 1/h0 : (p'=2) & (y'=0) + (1 - 1/h0) : (p'=1) & (y'=0); // av. response high equals h0\t\r\n\t[] p=1 & bit=1 & y=1 -> 1/h1 : (p'=2) & (y'=0) + (1 - 1/h1) : (p'=1) & (y'=0); // av. response high equals h1\r\n\r\n\t// receives a new message from low\r\n\t// this means low timed out (nack)\r\n\t// so delete old message and start sending an ack for the new message\r\n\t[mess_l] p>0 -> (p'=0) & (y'=0);\r\n\t\r\n\t// send ack (immediately)\r\n\t[ack_l] p=2 -> (p'=0);\r\n\t\r\nendmodule\r\n\r\nmodule low\r\n\r\n\tl : [0..3] init 0; // local state of low\r\n\t// 0 send message\r\n\t// 1 waiting for ack\r\n\t// 2 guess/check value\r\n\t// 3 done\r\n\t\r\n\tm : [0..N] init 1; // messages low can send before guessing\r\n\tguess : [-1..1] init -1; // guess low makes\r\n\tcorrect : [0..1] init 0; // is it correct or not\r\n\r\n\tx : clock; // low's clock\r\n\r\n\tinvariant\r\n    \t(l=0 => x<=0) &\r\n    \t(l=1 => x<=Tout) &\r\n        (l=2 => x<=0) &\r\n        (l=3 => true)\r\n    endinvariant\r\n\r\n\t[mess_l] l=0 -> (l'=1) & (x'=0); // low immediately sends message and waits for an ack\r\n\t[ack_l] l=1 & m<N & x<=Tout -> (l'=0) & (m'=m+1) & (x'=0); // ack (more to send) \r\n\t[ack_l] l=1 & m=N & x<=Tout -> (l'=2) & (x'=0); // ack (time to guess)\r\n\t[nack_l] l=1 & x=Tout -> (l'=0) & (x'=0); // timeout (nack)\r\n\t\t\r\n\t// when finished sending immediately guess value high was trying to send\r\n\t[guess0] l=2 & guess=-1 & x=0 -> (guess'=0);\r\n\t[guess1] l=2 & guess=-1 & x=0 -> (guess'=1);\r\n\t// and then immediately check if it is correct\r\n\t[] l=2 & guess>=0 & guess=bit  & x=0 -> (l'=3) & (correct'=1);\r\n\t[] l=2 & guess>=0 & guess!=bit & x=0 -> (l'=3);\r\n\t\r\nendmodule\r\n\r\n// reward structures\r\n// time\r\nrewards \"time\"\r\n        true : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/poptas/pump/pump.props",
    "content": "const int D;\n\n// Minimum probability low guesses correctly\nPmin=? [ F correct=1 ]\n\n// Maximum probability low guesses correctly\nPmax=? [ F correct=1 ]\n\n// Minimum probability low guesses correctly within time D\nPmin=? [ F<=D correct=1 ]\n\n// Maximum probability low guesses correctly within time D\nPmax=? [ F<=D correct=1 ]\n\n// Minimum expected time to send all messages\nRmin=? [ F l=2 ]\n\n// Minimum expected time to send all messages\nRmin=? [ F l=2 ]\n"
  },
  {
    "path": "prism-examples/poptas/repudiation/README.txt",
    "content": "This case study concerns the non-repudiation protocol of Markowitch & Roggeman [MR99].\n\nThe models here are partially observable probabilistic timed automata (POPTAs),\nas described in [NPZ17]. These extend the the probabilistic timed automaton (PTA)\nversion from [NPS13], the files for which can be found in ../../ptas/repudiation.\nBoth are extensions of the PTA model developed in [LMST04].\n\nFor more information, see: http://www.prismmodelchecker.org/casestudies/nonrepudiation.php\n\n=====================================================================================\n\nPARAMETERS:\n\nK: the originator randomly selects an integer over the range 1,...,K\n\n=====================================================================================\n\n[LMST04]\nR. Lanotte, A. Maggiolo-Schettini and A. Troina\nAutomatic Analysis of a Non-Repudiation Protocol\nIn Proc. 2nd International Workshop on Quantitative Aspects of Programming Languages (QAPL'04), 2004\n(available as ENTCS, vol. 112, pp. 113–129, 2005)\n\n[MR99]\nO. Markowitch and Y. Roggeman\nProbabilistic non-repudiation without trusted third party\nIn Proc. 2nd Workshop on Security in Communication Networks, 1999\n\n[NPS13]\nGethin Norman, David Parker and Jeremy Sproston\nModel Checking for Probabilistic Timed Automata\nFormal Methods in System Design, 43(2), pages 164-190, Springer, 2013\n\n[NPZ17]\nGethin Norman, David Parker and Xueyi Zou\nVerification and Control of Partially Observable Probabilistic Systems\nReal-Time Systems, 53(3), pages 354-402, Springer, 2017\n"
  },
  {
    "path": "prism-examples/poptas/repudiation/auto",
    "content": "#!/bin/bash\n\n# basic model\n\nprism repudiation.prism repudiation.props -const K=4 -gridresolution 12\nprism repudiation.prism repudiation.props -const K=8 -gridresolution 4\n\n# complex model\n\nprism repudiation_complex.prism repudiation.props -const K=4 -gridresolution 12\nprism repudiation_complex.prism repudiation.props -const K=8 -gridresolution 4\n"
  },
  {
    "path": "prism-examples/poptas/repudiation/repudiation.prism",
    "content": "// non-repudiation protocol (with malicious recipient) \r\n// Markowitch & Roggeman [MR99]\r\n// POPTA model based on the PTA model in:\r\n// G. Norman, D. Parker and J. Sproston\r\n// Model checking for probabilistic timed automata\r\n// Formal Methods in System Design 43(2):164–190 (2013)\r\n// dxp/gxn 04/09/14\r\n\r\npopta\r\n\r\n// observable variables (N is hidden)\r\nobservables\r\n        last, r, mess, ack, o, x, y\r\nendobservables\r\n\r\n// constants\r\nconst K; // range N is chosen over\r\nconst int ad = 1; // min time to send an ack\r\nconst int AD = 4; // deadline (if ack not arrived then end protocol)\r\n\r\nmodule originator\r\n\r\n\t// location of originator\r\n\to : [0..4];\r\n\t// 0 - init\r\n\t// 1 - send\r\n\t// 2 - waiting\r\n\t// 3 - finished\r\n\t// 4 - error\r\n\r\n\tN : [0..K]; // number of messages \r\n\tack : [0..K]; // number of acks the originator has received\r\n\r\n\tx : clock;\r\n\r\n\tinvariant\r\n\t\t(o=0 => true) &\r\n\t\t(o=1 => x<=0) &\r\n\t\t(o=2 => x<=AD) &\r\n\t\t(o=3 => true)\r\n\tendinvariant\r\n\r\n\t// init\r\n\t//  get request (so set K)\r\n\t[req] o=0 & K=1 ->  1/K : (o'=1) & (N'=1);\r\n\t[req] o=0 & K=2 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2);\r\n\t[req] o=0 & K=3 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3);\r\n\t\r\n\t[req] o=0 & K=4 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4);\r\n\t[req] o=0 & K=5 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=5);\r\n\t[req] o=0 & K=6 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=5)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=6);\r\n\t[req] o=0 & K=7 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=5)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=6)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=7);\r\n\t[req] o=0 & K=8 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=5)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=6)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=7)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=8);\r\n\t\r\n\t// send\r\n\t[message] o=1 & x<=0 -> (o'=2); // send first message immediately\r\n\t\r\n\t// waiting\r\n\t// ack arrives\r\n\t[ack] o=2 & ack<N-1 & x<=AD -> (o'=1) & (ack'=min(ack+1,K)) & (x'=0); // not last\r\n\t[ack] o=2 & ack=N-1 & x<=AD -> (o'=3) & (ack'=min(ack+1,K)) & (x'=0); // last\r\n\t// no ack arrives within time bound\r\n\t[noack] o=2 & x>=AD -> (o'=3) & (x'=0); // ack not arrived within expected interval (stop) \r\n\t\t\r\nendmodule\r\n\r\n\r\nmodule malicious_recipient\r\n\r\n\tr : [0..3];\r\n\t// 0 initial state\r\n\t// 1 receive messages\r\n\t// 2 send acks\r\n\t// 3 recipient stops (either protocol finished or malicious behaviour)\r\n\t\t\r\n\tmess : [0..K]; // number of mess the originator has received\r\n\tlast : [0..1]; // protocol is unfair\r\n\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t\t(r=0 => y<=0) &\r\n\t\t(r=1 => true) &\r\n\t\t(r=2 => true) &\r\n\t\t(r=3 => y<=0) &\r\n\t\t(r=4 => true)\r\n\tendinvariant\r\n\r\n\t[req] r=0 & y=0 -> (r'=1); // initiate protocol\r\n\t[message] r=1 -> (r'=2) & (y'=0) & (mess'=min(mess+1,K)); // receive message\r\n\t[ack] r=2 & y>=ad -> (r'=1) & (y'=0); // send ack\r\n\t// decode (can only do this once as takes too long to start sending acks again)\r\n\t[] r=2 -> (r'=3);\r\n\r\n\t// decode yields message\r\n\t[] r=3 & mess=N & ack<N -> (r'=4) & (last'=1); // unfair\r\n\t[] r=3 & !(mess=N & ack<N) -> (r'=4); // fair\r\n\r\nendmodule\r\n\r\n// unfair state reached\r\nlabel \"unfair\" = last=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/poptas/repudiation/repudiation.props",
    "content": "// Maximum probability that malicious recepient gains information\r\nPmax=? [ F \"unfair\" ]\r\n\r\n"
  },
  {
    "path": "prism-examples/poptas/repudiation/repudiation_complex.prism",
    "content": "// non-repudiation protocol (with malicious recipient with decoder) \r\n// Markowitch & Roggeman [MR99]\r\n// POPTA model based on the PTA model in:\r\n// G. Norman, D. Parker and J. Sproston\r\n// Model checking for probabilistic timed automata\r\n// Formal Methods in System Design 43(2):164–190 (2013)\r\n// dxp/gxn 04/09/14\r\n\r\npopta\r\n\r\n// observable variables (N is hidden)\r\nobservables\r\n        last, r, mess, ack, o, x, y\r\nendobservables\r\n\r\n// constants\r\nconst K; // range N is chosen over\r\nconst int ad = 1; // min time to send an ack\r\nconst int AD = 4; // deadline (if ack not arrived then end protocol)\r\n\r\nmodule originator\r\n\r\n\t// location of originator\r\n\to : [0..4];\r\n\t// 0 - init\r\n\t// 1 - send\r\n\t// 2 - waiting\r\n\t// 3 - finished\r\n\t// 4 - error\r\n\r\n\tN : [0..K]; // number of messages \r\n\tack : [0..K]; // number of acks the originator has received\r\n\r\n\tx : clock;\r\n\r\n\tinvariant\r\n\t\t(o=0 => true) &\r\n\t\t(o=1 => x<=0) &\r\n\t\t(o=2 => x<=AD) &\r\n\t\t(o=3 => true) &\r\n\t\t(o=4 => true)\r\n\tendinvariant\r\n\r\n\t// init\r\n\t[req] o=0 & K=1 ->  1/K : (o'=1) & (N'=1);\r\n\t[req] o=0 & K=2 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2);\r\n\t[req] o=0 & K=3 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3);\r\n\t\r\n\t[req] o=0 & K=4 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4);\r\n\t[req] o=0 & K=5 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=5);\r\n\t[req] o=0 & K=6 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=5)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=6);\r\n\t[req] o=0 & K=7 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=5)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=6)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=7);\r\n\t[req] o=0 & K=8 ->  1/K : (o'=1) & (N'=1)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=2)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=3)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=4)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=5)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=6)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=7)\r\n\t\t\t\t+ 1/K : (o'=1) & (N'=8);\r\n\t\r\n\t// send\r\n\t[message] o=1 & x<=0 -> (o'=2); // send message immediately\r\n\t\r\n\t// waiting\r\n\t// ack arrives\r\n\t[ack] o=2 & ack<N-1 & x<=AD -> (o'=1) & (ack'=min(ack+1,K)) & (x'=0); // not last\r\n\t[ack] o=2 & ack=N-1 & x<=AD -> (o'=3) & (ack'=min(ack+1,K)) & (x'=0); // last\r\n\t// no ack arrives within time bound\r\n\t[noack] o=2 & x>=AD -> (o'=4) & (x'=0); // ack not arrived within expected interval (stop) \r\n\t\r\nendmodule\r\n\r\nmodule malicious_recipient\r\n\r\n\tr : [0..6];\r\n\t// 0 - request\r\n\t// 1 - wait\r\n\t// 2 - ack\r\n\t// 3 - decode1 // decode probabilistically\r\n\t// 4 - decode3 // decode correctly\r\n\t// 5 - send act (after successfully decoded and not last)\r\n\t// 6 - decoded\r\n\r\n\tmess : [0..K]; // number of mess the originator has received\r\n\r\n\tlast : [0..1]; // message is last\r\n\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t\t(r=0 => y<=0) &\r\n\t\t(r=1 => true) &\r\n\t\t(r=2 => true) &\r\n\t\t(r=3 => y<=4) &\r\n\t\t(r=4 => y<=AD+1) &\r\n\t\t(r=5 => y<=0) &\r\n\t\t(r=6 => true)\r\n\tendinvariant\r\n\r\n\t[req] r=0 & y=0 -> (r'=1); // initiate protocol\r\n\t[message] r=1 -> (r'=2) & (y'=0) & (mess'=min(mess+1,K)); // receive message\r\n\t[ack] r=2 & y>=ad -> (r'=1); // send ack\r\n\t\r\n\t// try and decode\r\n\t[decp] r=2 -> (r'=3); // decode probabilistically\r\n\t[dec] r=2 -> (r'=4); // decode correctly\r\n\t\r\n\t// decoding probabilistically (if fails can try again or send ack)\r\n\t[] r=3 & y>=3 -> 0.75 : (r'=2) & (y'=0) + 0.25 : (r'=5) & (y'=0);\r\n\t[] r=4 & y>=AD+1 -> (r'=5) & (y'=0);\r\n\r\n\t// decode yields message so stop (immediate)\r\n\t[] r=5 & mess=N & ack<N & y<=0 -> (r'=6) & (last'=1); // unfair\r\n\t[] r=5 & mess=N & ack=N & y<=0 -> (r'=6); // fair\r\n\t// decode noes not yield message as not last so continue (immediate)\r\n\t[] r=5 & mess<N & y<=0 -> (r'=2); // unfair\r\n\r\nendmodule\r\n\r\n// unfair state reached\r\nlabel \"unfair\" = last=1;\r\n\r\n"
  },
  {
    "path": "prism-examples/poptas/simple/example1.prism",
    "content": "// Example 1 from\r\n// \"Verification and Control of Partially Observable Probabilistic Real-Time Systems\"\r\n// Norman/Parker/Zou, FORMATS 2015\r\n// Or Example 3 from\r\n// \"Verification and Control of Partially Observable Probabilistic Systems\"\r\n// Norman/Parker/Zou, Real-Time Systems, 53(3), 2017\r\n\r\npopta\r\n\r\nobservables\r\n\tx, y, o\r\nendobservables\r\n\r\nmodule M\r\n\r\n\tl : [0..5] init 0;\r\n\to : [0..4] init 0; // 0, 1&2, 3, 4, 5\r\n\tx : clock;\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t\t(l=0 => x<=1) &\r\n\t\t(l=1 => true) &\r\n\t\t(l=2 => true) &\r\n\t\t(l=3 => true) &\r\n\t\t(l=4 => true) &\r\n\t\t(l=5 => true)\r\n\tendinvariant\r\n\r\n\t[a0] l=0 & x>=1 -> 1/2 : (l'=1)&(o'=1) + 1/2 : (l'=2)&(o'=1);\r\n\t[a] l=1 -> (l'=3)&(o'=2);\r\n\t[a] l=2 -> (l'=4)&(o'=3)&(x'=0);\r\n\t[b] l=3 & y=1 -> (l'=5)&(o'=4);\r\n\t[b] l=4 & y=2 & x=0 -> (l'=5)&(o'=4);\r\n\r\nendmodule\r\n\r\nlabel \"goal\" = o=4;\r\n"
  },
  {
    "path": "prism-examples/poptas/simple/example1.props",
    "content": "Pmax=? [ F \"goal\" ]\r\n"
  },
  {
    "path": "prism-examples/poptas/simple/example2.prism",
    "content": "// Example 2 from\r\n// \"Verification and Control of Partially Observable Probabilistic Real-Time Systems\"\r\n// Norman/Parker/Zou, FORMATS 2015\r\n// Or Example 4 from\r\n// \"Verification and Control of Partially Observable Probabilistic Systems\"\r\n// Norman/Parker/Zou, Real-Time Systems, 53(3), 2017\r\n\r\npopta\r\n\r\nobservables x, o endobservables\r\n\r\nmodule M\r\n\r\n\tx : clock;\r\n\tl : [0..3] init 0;\r\n\to : [0..2] init 0; // 0, 1&2, 3\r\n\r\n\tinvariant\r\n\t\t(l=0 => x<=1) &\r\n\t\t(l=1 => x<=2) &\r\n\t\t(l=2 => x<=2) &\r\n\t\t(l=3 => true)\r\n\tendinvariant\r\n\r\n\t[a0] l=0 & x<=1 -> 1/2 : (l'=1)&(o'=1) + 1/2 : (l'=2)&(o'=1)&(x'=0);\r\n\t\r\n\t[a1] l=1 & x<=2 -> (l'=3)&(o'=2);\r\n\t[a2] l=1 & x<=2 -> (l'=3)&(o'=2);\r\n\t\r\n\t[a1] l=2 & x<=2 -> (l'=3)&(o'=2);\r\n\t[a2] l=2 & x<=2 -> (l'=3)&(o'=2);\r\n\r\nendmodule\r\n\r\nlabel \"goal\" = o=2;\r\n\r\nrewards\r\n\t[a2] l=1 : 1;\r\n\t[a1] l=2 : 1;\r\n\tl=0 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/poptas/simple/example2.props",
    "content": "Rmin=? [ F \"goal\" ]\r\n"
  },
  {
    "path": "prism-examples/poptas/task_graph/README.txt",
    "content": "This case study concerns the problem of scheduling tasks between several processors.\n\nThe models here are partially observable probabilistic timed automata (POPTAs),\nas described in [NPZ17]. These extend the the probabilistic timed automaton (PTA)\nversion from [NPS13]. Both are extensions of the timed automaton example from [BFLM11].\n\nFor more information, see: http://www.prismmodelchecker.org/casestudies/task_graph.php\n\n=====================================================================================\n\n[BFLM11]\nP. Bouyer, U. Fahrenberg, K. Larsen and N. Markey\nQuantitative Analysis of Real-Time Systems Using Priced Timed Automata\nCommunications of the ACM, 54(9), pages 78-87, 2011\n\n[KNP19]\nMarta Kwiatkowska, Gethin Norman and David Parker\nVerification and Control of Turn-Based Probabilistic Real-Time Games\nIn The Art of Modelling Computational Systems: A Journey from Logic and Concurrency to Security and Privacy (Essays Dedicated to Catuscia Palamidessi on the Occasion of Her 60th Birthday), volume 11760 of LNCS, pages 379-396, Springer, 2019\n\n[NPS13]\nGethin Norman, David Parker and Jeremy Sproston\nModel Checking for Probabilistic Timed Automata\nFormal Methods in System Design, 43(2), pages 164-190, Springer, 2013\n\n[NPZ17]\nGethin Norman, David Parker and Xueyi Zou\nVerification and Control of Partially Observable Probabilistic Systems\nReal-Time Systems, 53(3), pages 354-402, Springer, 2017\n"
  },
  {
    "path": "prism-examples/poptas/task_graph/auto",
    "content": "#!/bin/bash\n\n# basic model\n\nprism task_graph.prism task_graph.props -prop 1 -const sleep=0.25 -gridresolution 2\nprism task_graph.prism task_graph.props -prop 1 -const sleep=0.5 -gridresolution 2\nprism task_graph.prism task_graph.props -prop 1 -const sleep=0.75 -gridresolution 2\n\nprism task_graph.prism task_graph.props -prop 2 -const sleep=0.25 -gridresolution 2\nprism task_graph.prism task_graph.props -prop 2 -const sleep=0.5 -gridresolution 2\nprism task_graph.prism task_graph.props -prop 2 -const sleep=0.75 -gridresolution 2\n\n# random delay model\n\nprism task_graph_prob.prism task_graph.props -prop 1 -const sleep=0.25 -gridresolution 2\nprism task_graph_prob.prism task_graph.props -prop 1 -const sleep=0.5 -gridresolution 2\nprism task_graph_prob.prism task_graph.props -prop 1 -const sleep=0.75 -gridresolution 2\n\nprism task_graph_prob.prism task_graph.props -prop 2 -const sleep=0.25 -gridresolution 2\nprism task_graph_prob.prism task_graph.props -prop 2 -const sleep=0.5 -gridresolution 2\nprism task_graph_prob.prism task_graph.props -prop 2 -const sleep=0.75 -gridresolution 2\n"
  },
  {
    "path": "prism-examples/poptas/task_graph/task_graph.prism",
    "content": "// POPTA extension of basic scheduler model from\r\n// G. Norman, D. Parker and J. Sproston\r\n// Model Checking for Probabilistic Timed Automata\r\n// Formal Methods in System Design, 43(2):164-190, 2013\r\n// added when a task is finished the first processor can enter a lower power state\r\n// (consumes less power but longer to next perform tasks as has to warm up first)\r\n\r\npopta\r\n\r\n// sleep variable of processor 1 is hidden\r\nobservables\r\n        task1, task2, task3, task4, task5, task6, p1, p2, x1, x2 //,sleep1\r\nendobservables\r\n\r\nconst double sleep; // probability P1 sleeps after finishing a task\r\n\r\nmodule scheduler\r\n\r\n\t// task status: 0 - not started, 1|2 - on processor 1|2, 3 - finished\r\n\ttask1 : [0..3]; // A+B\r\n\ttask2 : [0..3]; // CxD\r\n\ttask3 : [0..3]; // Cx(A+B)\r\n\ttask4 : [0..3]; // (A+B)+(CxD)\r\n\ttask5 : [0..3]; // DxCx(A+B)\r\n\ttask6 : [0..3]; // (DxCx(A+B)) + ((A+B)+(CxD))\r\n\t\r\n\t// start task 1\r\n\t[p1_add1] task1=0 -> (task1'=1);\r\n\t[p2_add1] task1=0 -> (task1'=2);\r\n\r\n\t// start task 2\r\n\t[p1_mult2] task2=0 -> (task2'=1);\r\n\t[p2_mult2] task2=0 -> (task2'=2);\r\n\t\r\n\t// start task 3 (must wait for task 1 to complete)\r\n\t[p1_mult3] task3=0 & task1=3 -> (task3'=1);\r\n\t[p2_mult3] task3=0 & task1=3 -> (task3'=2);\r\n\r\n\t// start task 4 (must wait for tasks 1 and 2 to complete)\r\n\t[p1_add4] task4=0 & task1=3 & task2=3 -> (task4'=1);\r\n\t[p2_add4] task4=0 & task1=3 & task2=3 -> (task4'=2);\r\n\t\r\n\t// start task 5 (must wait for task 3 to complete)\r\n\t[p1_mult5] task5=0 & task3=3 -> (task5'=1);\r\n\t[p2_mult5] task5=0 & task3=3 -> (task5'=2);\r\n\t\r\n\t// start task 6 (must wait for tasks 4 and 5 to complete)\r\n\t[p1_add6] task6=0 & task4=3 & task5=3 -> (task6'=1);\r\n\t[p2_add6] task6=0 & task4=3 & task5=3 -> (task6'=2);\r\n\t\r\n\t// a task finishes on processor 1\r\n\t[p1_done] task1=1 -> (task1'=3);\r\n\t[p1_done] task2=1 -> (task2'=3);\r\n\t[p1_done] task3=1 -> (task3'=3);\r\n\t[p1_done] task4=1 -> (task4'=3);\r\n\t[p1_done] task5=1 -> (task5'=3);\r\n\t[p1_done] task6=1 -> (task6'=3);\r\n\r\n\t// a task finishes on processor 2\r\n\t[p2_done] task1=2 -> (task1'=3);\r\n\t[p2_done] task2=2 -> (task2'=3);\r\n\t[p2_done] task3=2 -> (task3'=3);\r\n\t[p2_done] task4=2 -> (task4'=3);\r\n\t[p2_done] task5=2 -> (task5'=3);\r\n\t[p2_done] task6=2 -> (task6'=3);\r\n\t\r\nendmodule\r\n\t\r\n// processor 1\r\nmodule P1\r\n\r\n\tp1 : [0..5]; \r\n\t// 0 - initial location\r\n\t// 1 - inactive (idle or sleep)\r\n\t// 2,3 - waking (adding and multiplying) \r\n\t// 4 - adding\r\n\t// 5 - multiplying\r\n\tsleep1 : [0..1]; // when processor is in sleep mode\r\n\tx1 : clock; // local clock\r\n\t\r\n\tinvariant\r\n        (p1=0 => x1<=0) &\r\n        (p1=1 => true)  &\r\n        (p1=2 => x1<=4) &\r\n        (p1=3 => x1<=4) &\r\n        (p1=4 => x1<=2) &\r\n        (p1=5 => x1<=3)\r\n    endinvariant\r\n\r\n\t// initialise\r\n\t[start] p1=0 -> 0.5 : (p1'=1) & (sleep1'=0) + 0.5 : (p1'=1) & (sleep1'=1);\r\n\t\r\n\t// start from sleep state\r\n\t[p1_add1]  p1=1 & sleep1=1 -> (p1'=2) & (x1'=0) & (sleep1'=0); // add\r\n\t[p1_add4]  p1=1 & sleep1=1 -> (p1'=2) & (x1'=0) & (sleep1'=0); // add\r\n\t[p1_add6]  p1=1 & sleep1=1 -> (p1'=2) & (x1'=0) & (sleep1'=0); // add\r\n\t[p1_mult2] p1=1 & sleep1=1 -> (p1'=3) & (x1'=0) & (sleep1'=0); // multiply\r\n\t[p1_mult3] p1=1 & sleep1=1 -> (p1'=3) & (x1'=0) & (sleep1'=0); // multiply\r\n\t[p1_mult5] p1=1 & sleep1=1 -> (p1'=3) & (x1'=0) & (sleep1'=0); // multiply\r\n\r\n\t// start from idle state\r\n\t[p1_add1]  p1=1 & sleep1=0 -> (p1'=4) & (x1'=0); // add\r\n\t[p1_add4]  p1=1 & sleep1=0 -> (p1'=4) & (x1'=0); // add\r\n\t[p1_add6]  p1=1 & sleep1=0 -> (p1'=4) & (x1'=0); // add\r\n\t[p1_mult2] p1=1 & sleep1=0 -> (p1'=5) & (x1'=0); // multiply\r\n\t[p1_mult3] p1=1 & sleep1=0 -> (p1'=5) & (x1'=0); // multiply\r\n\t[p1_mult5] p1=1 & sleep1=0 -> (p1'=5) & (x1'=0); // multiply\r\n\r\n\t// wake from sleep\r\n\t[p1] p1=2 & x1=4 -> (p1'=4) & (x1'=0); // add\r\n\t[p1] p1=3 & x1=4 -> (p1'=5) & (x1'=0); // multiply\r\n\r\n\t// finish\r\n\t[p1_done] p1=4 & x1=2 -> (1-sleep) : (p1'=1) \r\n\t\t\t\t\t\t\t   + sleep : (p1'=1) & (sleep1'=1); // add\r\n\t[p1_done] p1=5 & x1=3 -> (1-sleep) : (p1'=1)\r\n\t\t\t\t\t\t\t   + sleep : (p1'=1) & (sleep1'=1);  // multiply\r\n\r\nendmodule\r\n\r\n// processor 2\r\nmodule P2\r\n\r\n\tp2 : [0..2]; // 0 - idle, 1 - add, 2 - multiply\r\n\tx2 : clock;\r\n\t\r\n\tinvariant\r\n        (p2=1 => x2<=5) &\r\n        (p2=2 => x2<=7)\r\n    endinvariant\r\n\t\r\n\t// start\r\n\t[p2_add1]  p2=0 -> (p2'=1) & (x2'=0); // add\r\n\t[p2_add4]  p2=0 -> (p2'=1) & (x2'=0); // add\r\n\t[p2_add6]  p2=0 -> (p2'=1) & (x2'=0); // add\r\n\t[p2_mult2] p2=0 -> (p2'=2) & (x2'=0); // multiply\r\n\t[p2_mult3] p2=0 -> (p2'=2) & (x2'=0); // multiply\r\n\t[p2_mult5] p2=0 -> (p2'=2) & (x2'=0); // multiply\r\n\r\n\t// finish\r\n\t[p2_done] p2=1 & x2=5 -> (p2'=0); // add\r\n\t[p2_done] p2=2 & x2=7 -> (p2'=0); // multiply\r\n\r\nendmodule\r\n\r\n// reward structures\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// energy\r\nrewards \"energy\"\r\n\r\n\tp1=0 & sleep1=1 : 1/1000;\r\n\tp1=0 & sleep1=0 : 10/1000;\r\n\tp1>0 : 90/1000;\r\n\tp2=0 : 20/1000;\r\n\tp2>0 : 30/1000;\r\n\t\r\nendrewards\r\n\r\nlabel \"tasks_complete\" = (task1=3) & (task2=3) & (task3=3) & (task4=3) & (task5=3) & (task6=3);"
  },
  {
    "path": "prism-examples/poptas/task_graph/task_graph.props",
    "content": "// Minimum expected time to complete all tasks\nR{\"time\"}min=? [ F \"tasks_complete\" ]; \n\n// Minimum expected energy to complete all tasks\nR{\"energy\"}min=? [ F \"tasks_complete\" ]; \n"
  },
  {
    "path": "prism-examples/poptas/task_graph/task_graph_prob.prism",
    "content": "// POPTA extension of random delay scheduler model from\r\n// G. Norman, D. Parker and J. Sproston\r\n// Model Checking for Probabilistic Timed Automata.\r\n// Formal Methods in System Design, 43(2):164-190, 2013\r\n// added when a task is finished the first processor can enter a lower power state\r\n// (consumes less power but longer to next perform tasks as has to warm up first)\r\n\r\npopta\r\n\r\n// sleep variable of processor 1 is hidden\r\nobservables\r\n        task1, task2, task3, task4, task5, task6, p1, p2, x1, x2, c1, c2 //, sleep1\r\nendobservables\r\n\r\nconst double sleep; // probability P1 sleeps after finishing a task\r\n\r\nmodule scheduler\r\n\r\n\t// task status: 0 - not started, 1|2 - on processor 1|2, 3 - finished\r\n\ttask1 : [0..3]; // A+B\r\n\ttask2 : [0..3]; // CxD\r\n\ttask3 : [0..3]; // Cx(A+B)\r\n\ttask4 : [0..3]; // (A+B)+(CxD)\r\n\ttask5 : [0..3]; // DxCx(A+B)\r\n\ttask6 : [0..3]; // (DxCx(A+B)) + ((A+B)+(CxD))\r\n\t\r\n\t// start task 1\r\n\t[p1_add1] task1=0 -> (task1'=1);\r\n\t[p2_add1] task1=0 -> (task1'=2);\r\n\r\n\t// start task 2\r\n\t[p1_mult2] task2=0 -> (task2'=1);\r\n\t[p2_mult2] task2=0 -> (task2'=2);\r\n\t\r\n\t// start task 3 (must wait for task 1 to complete)\r\n\t[p1_mult3] task3=0 & task1=3 -> (task3'=1);\r\n\t[p2_mult3] task3=0 & task1=3 -> (task3'=2);\r\n\r\n\t// start task 4 (must wait for tasks 1 and 2 to complete)\r\n\t[p1_add4] task4=0 & task1=3 & task2=3 -> (task4'=1);\r\n\t[p2_add4] task4=0 & task1=3 & task2=3 -> (task4'=2);\r\n\t\r\n\t// start task 5 (must wait for task 3 to complete)\r\n\t[p1_mult5] task5=0 & task3=3 -> (task5'=1);\r\n\t[p2_mult5] task5=0 & task3=3 -> (task5'=2);\r\n\t\r\n\t// start task 6 (must wait for tasks 4 and 5 to complete)\r\n\t[p1_add6] task6=0 & task4=3 & task5=3 -> (task6'=1);\r\n\t[p2_add6] task6=0 & task4=3 & task5=3 -> (task6'=2);\r\n\t\r\n\t// a task finishes on processor 1\r\n\t[p1_done] task1=1 -> (task1'=3);\r\n\t[p1_done] task2=1 -> (task2'=3);\r\n\t[p1_done] task3=1 -> (task3'=3);\r\n\t[p1_done] task4=1 -> (task4'=3);\r\n\t[p1_done] task5=1 -> (task5'=3);\r\n\t[p1_done] task6=1 -> (task6'=3);\r\n\r\n\t// a task finishes on processor 2\r\n\t[p2_done] task1=2 -> (task1'=3);\r\n\t[p2_done] task2=2 -> (task2'=3);\r\n\t[p2_done] task3=2 -> (task3'=3);\r\n\t[p2_done] task4=2 -> (task4'=3);\r\n\t[p2_done] task5=2 -> (task5'=3);\r\n\t[p2_done] task6=2 -> (task6'=3);\r\n\t\r\nendmodule\r\n\t\r\n// processor 1\r\nmodule P1\r\n\r\n\tp1 : [0..6];\r\n\t// 0 - initial location\r\n\t// 1 - inactive (idle or sleep)\r\n\t// 2,3 - waking (adding and multiplying) \r\n\t// 4 - adding\r\n\t// 5 - multiplying\r\n\t// 6 - done\r\n\r\n\tc1 : [0..2]; // used for the randomised delay\r\n\tsleep1 : [0..1]; // when processor is in sleep mode\r\n\tx1 : clock; // local clock\r\n\t\r\n\tinvariant\r\n\t\t(p1=0 => x1<=0) &\r\n        (p1=1 => true)  &\r\n        (p1=2 => x1<=4) &\r\n        (p1=3 => x1<=4) &\r\n        (p1=4 => x1<=1) &\r\n        ((p1=5 & c1=0) => x1<=2) &\r\n        ((p1=5 & c1>0) => x1<=1) &\r\n        (p1=6 => x1<=0)\r\n    endinvariant\r\n\r\n\t// initialise\r\n\t[start] p1=0 -> 0.5 : (p1'=1) & (sleep1'=0) + 0.5 : (p1'=1) & (sleep1'=1);\r\n\r\n\t// start from sleep state\r\n\t[p1_add1]  p1=1 & sleep1=1 -> (p1'=2) & (x1'=0) & (sleep1'=0); // add\r\n\t[p1_add4]  p1=1 & sleep1=1 -> (p1'=2) & (x1'=0) & (sleep1'=0); // add\r\n\t[p1_add6]  p1=1 & sleep1=1 -> (p1'=2) & (x1'=0) & (sleep1'=0); // add\r\n\t[p1_mult2] p1=1 & sleep1=1 -> (p1'=3) & (x1'=0) & (sleep1'=0); // multiply\r\n\t[p1_mult3] p1=1 & sleep1=1 -> (p1'=3) & (x1'=0) & (sleep1'=0); // multiply\r\n\t[p1_mult5] p1=1 & sleep1=1 -> (p1'=3) & (x1'=0) & (sleep1'=0); // multiply\r\n\r\n\t// start from idle state\r\n\t[p1_add1]  p1=1 & sleep1=0 -> (p1'=4) & (x1'=0); // add\r\n\t[p1_add4]  p1=1 & sleep1=0 -> (p1'=4) & (x1'=0); // add\r\n\t[p1_add6]  p1=1 & sleep1=0 -> (p1'=4) & (x1'=0); // add\r\n\t[p1_mult2] p1=1 & sleep1=0 -> (p1'=5) & (x1'=0); // multiply\r\n\t[p1_mult3] p1=1 & sleep1=0 -> (p1'=5) & (x1'=0); // multiply\r\n\t[p1_mult5] p1=1 & sleep1=0 -> (p1'=5) & (x1'=0); // multiply\r\n\r\n\t// wake from sleep\r\n\t[p1] p1=2 & x1=4 -> (p1'=4) & (x1'=0); // add\r\n\t[p1] p1=3 & x1=4 -> (p1'=5) & (x1'=0); // multiply\r\n\r\n\t// adding\r\n\t[p1] p1=4 & x1=1 & c1=0 -> 1/3 : (p1'=6) & (x1'=0) & (c1'=0) \r\n\t                               + 2/3 : (c1'=1) & (x1'=0);\r\n\t[p1] p1=4 & x1=1 & c1=1 -> 1/2 : (p1'=6) & (x1'=0) & (c1'=0) \r\n\t                               + 1/2 : (c1'=2) & (x1'=0);\r\n\t[p1] p1=4 & x1=1 & c1=2 -> (p1'=6) & (x1'=0) & (c1'=0);\r\n\r\n\t// multiplying\r\n\t[p1] p1=5 & x1=2 & c1=0 -> 1/3 : (p1'=6) & (x1'=0) & (c1'=0) \r\n\t                               + 2/3 : (c1'=1) & (x1'=0);\r\n\t[p1] p1=5 & x1=1 & c1=1 -> 1/2 : (p1'=6) & (x1'=0) & (c1'=0) \r\n\t                               + 1/2 : (c1'=2) & (x1'=0);\r\n\t[p1] p1=5 & x1=1 & c1=2 -> (p1'=6) & (x1'=0) & (c1'=0);\r\n\t\r\n\t// done\r\n\t[p1_done] p1=6 -> (1-sleep) : (p1'=1) + sleep : (p1'=1) & (sleep1'=1);\r\n\t\r\nendmodule\r\n\r\n// processor 2\r\nmodule P2\r\n\r\n\tp2 : [0..3];\r\n\tc2 : [0..2];\r\n\tx2 : clock;\r\n\t\r\n\tinvariant\r\n       (p1=1 => true)  &\r\n    \t((p2=1 & c2=0) => x2<=4) &\r\n        ((p2=1  & c2>0)=> x2<=1) &\r\n        ((p2=2 & c2=0) => x2<=6) &\r\n        ((p2=2 & c2>0) => x2<=1) &\r\n        (p2=3 => x2<=0)\r\n    endinvariant\r\n\r\n\t// addition\r\n\t[p2_add1] (p2=0) -> (p2'=1) & (x2'=0); // start\r\n\t[p2_add4] (p2=0) -> (p2'=1) & (x2'=0); // start\r\n\t[p2_add6] (p2=0) -> (p2'=1) & (x2'=0); // start\r\n\t[p2] (p2=1) & (x2=4) & (c2=0) -> 1/3 : (p2'=3) & (x2'=0) & (c2'=0) + 2/3 : (c2'=1) & (x2'=0);\r\n\t[p2] (p2=1) & (x2=1) & (c2=1) -> 1/2 : (p2'=3) & (x2'=0) & (c2'=0) + 1/2 : (c2'=2) & (x2'=0);\r\n\t[p2_done] (p2=1) & (x2=1) & (c2=2) -> (p2'=0) & (x2'=0) & (c2'=0);\r\n\r\n\t// multi\r\n\t[p2_mult2] (p2=0) -> (p2'=2) & (x2'=0); // start\r\n\t[p2_mult3] (p2=0) -> (p2'=2) & (x2'=0); // start\r\n\t[p2_mult5] (p2=0) -> (p2'=2) & (x2'=0); // start\r\n\t[p2] (p2=2) & (x2=6) & (c2=0) -> 1/3 : (p2'=3) & (x2'=0) & (c2'=0) + 2/3 : (c2'=1) & (x2'=0);\r\n\t[p2] (p2=2) & (x2=1) & (c2=1) -> 1/2 : (p2'=3) & (x2'=0) & (c2'=0) + 1/2 : (c2'=2) & (x2'=0);\r\n\t[p2_done] (p2=2) & (x2=1) & (c2=2) -> (p2'=0) & (x2'=0) & (c2'=0);\r\n\r\n\t// done\r\n\t[p2_done] (p2=3) -> (p2'=0);  // finish\r\n\t\r\nendmodule\r\n\r\n// reward structures\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// energy\r\nrewards \"energy\"\r\n\tp1=0 & sleep1=1 : 1/1000;\r\n\tp1=0 & sleep1=0 : 10/1000;\r\n\tp1>0 : 90/1000;\r\n\tp2=0 : 20/1000;\r\n\tp2>0 : 30/1000;\r\nendrewards\r\n\r\nlabel \"tasks_complete\" = (task6=3);"
  },
  {
    "path": "prism-examples/ptas/csma/abst/.args",
    "content": "-aroptions refine=all,nopre\n"
  },
  {
    "path": "prism-examples/ptas/csma/abst/.models",
    "content": "csma.nm -const bmax=1\n\n"
  },
  {
    "path": "prism-examples/ptas/csma/abst/.props",
    "content": "eventually.pctl\ndeadline.pctl -const T=1000\ndeadline.pctl -const T=2000\ndeadline.pctl -const T=3000\n"
  },
  {
    "path": "prism-examples/ptas/csma/abst/auto",
    "content": "#!/bin/csh\n\nprism csma.nm -const K=1 eventually.pctl -aroptions refine=all,nopre,opt\n\nprism csma.nm -const K=1 deadline.pctl -const T=1000 -aroptions refine=all,nopre,opt\nprism csma.nm -const K=1 deadline.pctl -const T=2000 -aroptions refine=all,nopre,opt\nprism csma.nm -const K=1 deadline.pctl -const T=3000 -aroptions refine=all,nopre,opt\n"
  },
  {
    "path": "prism-examples/ptas/csma/abst/csma.nm",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model adapted to model a single station\r\n// gxn/dxp 04/12/01\r\n\r\npta\r\n\r\n// note made changes since cannot have strict inequalities\r\n// in digital clocks approach and suppose a station only sends one message\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// actual parameters\r\nconst int K; // exponential backoff limit (sometimes called bmax)\r\nconst int slot=2*sigma; // length of slot\r\nconst int sigma=26;\r\nconst int lambda=808;\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// the bus\r\nmodule bus\r\n\t\r\n\tb : [0..2];\r\n\t// b=0 - idle\r\n\t// b=1 - active\r\n\t// b=2 - collision\r\n\t\r\n\t// clock of bus\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t\t(b=0 => true) &\r\n\t\t(b=1 => true) &\r\n\t\t(b=2 => y<=sigma)\r\n\tendinvariant\r\n\t\r\n\t// station starts sending\r\n\t[send1] (b=0) -> (b'=1) & (y'=0); // no message being sent\r\n\t[send2] (b=0) -> (b'=1) & (y'=0); // no message being sent\r\n\r\n\t[send1] (b=1) & (y<sigma) -> (b'=2) & (y'=0); // message being sent (move to collision)\r\n\t[send2] (b=1) & (y<sigma) -> (b'=2) & (y'=0); // message being sent (move to collision)\r\n\t\r\n\t// message being sent\r\n\t[busy1]  (b=1) & (y>=sigma) -> (b'=1); \r\n\t[busy2]  (b=1) & (y>=sigma) -> (b'=1); \r\n\t\r\n\t// station finishes\r\n\t[end1] (b=1) -> (b'=0) & (y'=0);\r\n\t[end2] (b=1) -> (b'=0) & (y'=0);\r\n\t\r\n\t// collision detected\r\n\t[cd] (b=2) & (y<=sigma) -> (b'=0) & (y'=0);\r\n\t\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// model of first sender\r\nmodule station1\r\n\t\r\n\t// LOCAL STATE\r\n\ts1 : [0..4];\r\n\t// s1=0 - initial state\r\n\t// s1=1 - transmit\r\n\t// s1=2 - collision (set backoff)\r\n\t// s1=3 - wait (bus busy)\r\n\t// s1=4 -done (since sending only one message)\r\n\t// LOCAL CLOCK\r\n\tx1 : clock;\r\n\t// COLLISION COUNTER\r\n\tcd1 : [0..K];\r\n\r\n\tinvariant\r\n\t\t(s1=0 => x1=0) &\r\n\t\t(s1=1 => x1<=lambda) &\r\n\t\t(s1=2 => x1=0) &\r\n\t\t(s1=3 => x1<=pow(2, cd1)*slot) &\r\n\t\t(s1=4 => true)\r\n\tendinvariant\r\n\r\n\t// start sending\r\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\r\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\r\n\t\r\n\t// transmitting\r\n\t[end1] (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\r\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected\r\n\t\r\n\t// set backoff (no time can pass in this state)\r\n\t// first retransmission\r\n\t[] s1=2 & cd1=1 -> 1/2 : (s1'=3) & (x1'=0*slot) \r\n\t                 + 1/2 : (s1'=3) & (x1'=1*slot);\r\n\t// second retransmission\r\n\t[] s1=2 & cd1=2 -> 1/4 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=3*slot);\r\n\t// thrid retransmission\r\n\t[] s1=2 & cd1=3 -> 1/8 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=7*slot);\r\n\t// fourth retransmission \r\n\t[] s1=2 & cd1=4 -> 1/16 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=15*slot);\r\n\t\r\n\t// finished backoff\r\n\t[send1] (s1=3) & (x1=pow(2, cd1)*slot) -> (s1'=1) & (x1'=0); // channel free\r\n\t[busy1] (s1=3) & (x1=pow(2, cd1)*slot) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // channel busy\r\n\t\r\n\t// once finished nothing matters\r\n\t[done] (s1=4) -> true;\r\n\t\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// LABELS\r\n\r\nlabel \"done\" = s1=4 & s2=4;\r\n"
  },
  {
    "path": "prism-examples/ptas/csma/abst/deadline.pctl",
    "content": "const int T;\r\n\r\nPmin=? [ F<=T \"done\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/csma/abst/eventually.pctl",
    "content": "Pmin=? [ F \"done\" ]\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/csma/full/.args",
    "content": "-aroptions refine=all,nopre\n"
  },
  {
    "path": "prism-examples/ptas/csma/full/.models",
    "content": "csma.nm -const bmax=2,K=4\ncsma.nm -const bmax=2,K=8\ncsma.nm -const bmax=4,K=4\ncsma.nm -const bmax=4,K=8\n\n"
  },
  {
    "path": "prism-examples/ptas/csma/full/.props",
    "content": "collisions.pctl\n"
  },
  {
    "path": "prism-examples/ptas/csma/full/auto",
    "content": "#!/bin/csh\n\nprism csma.nm collisions.pctl -const K=2,COL=4 -aroptions refine=all,nopre,opt\nprism csma.nm collisions.pctl -const K=2,COL=8 -aroptions refine=all,nopre,opt\nprism csma.nm collisions.pctl -const K=4,COL=4 -aroptions refine=all,nopre,opt\nprism csma.nm collisions.pctl -const K=4,COL=8 -aroptions refine=all,nopre,opt\n\n#prism csma.nm time.pctl -const K=1,COL=0 -aroptions refine=all,nopre,opt\n#prism csma.nm time.pctl -const K=2,COL=0 -aroptions refine=all,nopre,opt\n#prism csma.nm time.pctl -const K=3,COL=0 -aroptions refine=all,nopre,opt\n#prism csma.nm time.pctl -const K=4,COL=0 -aroptions refine=all,nopre,opt\n"
  },
  {
    "path": "prism-examples/ptas/csma/full/collisions.pctl",
    "content": "Pmax=?[F \"cmax\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/csma/full/csma.nm",
    "content": "// CSMA/CD protocol - two stations (PTA model using digital clocks)\r\n// gxn/mxd 31/05/05\r\n\r\n// based on kronos (non-probabilistic) TA model and that which appears in:\r\n// M. Duflot, L. Fribourg, T. Hrault, R. Lassaigne, F. Magniette, S. Messika, S. Peyronnet and C. Picaronny\r\n// Probabilistic model checking of the CSMA/CD protocol using PRISM and APMC\r\n// In Proc. AVoCS'04, 2004\r\n\r\npta\r\n\r\n// PARAMETERS\r\n\r\n// parameters\r\nconst int sigma=26; // time for messages to propagate along the bus\r\nconst int lambda=808; // time to send a message\r\nconst int delay=26; // wire delay\r\nconst int slot=2*sigma; // size of back off slot\r\n\r\nconst int K; // exponential backoff limit (sometimes called bmax)\r\nconst int M=pow(2,K)-1; // max number of slots to wait\r\n\r\nconst int COL; // max number of collisions (called K in an old version of this model)\r\n\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// collision counter\r\nmodule collisions\r\n\r\n\tc : [0..max(1,COL)];\r\n\r\n\t[csend1] true -> (c'=min(COL,c+1));\r\n\t[csend2] true -> (c'=min(COL,c+1));\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// the bus\r\nmodule bus\r\n\t\r\n\tb : [0..4];\r\n\t// b=0 - idle\r\n\t// b=1 - active\r\n\t// b=2 - collision\r\n\t// b=3 - collision1\r\n\t// b=4 - collision2\r\n\t\r\n\ty1 : clock; // clock of bus\r\n\ty2 : clock; // clock of bus\r\n\r\n\tinvariant\r\n\t\t(b=0 => true) &\r\n\t\t(b=1 => true) &\r\n\t\t(b=2 => y1<=delay & y2<=delay) &\r\n\t\t(b=3 => y1<=delay) &\r\n\t\t(b=4 => y2<=delay)\r\n\tendinvariant\r\n\t\r\n\t// stations starts sending\r\n\t[send1] b=0 -> (b'=1) & (y1'=0); // no message being sent\r\n\t[send2] b=0 -> (b'=1) & (y2'=0); // no message being sent\r\n\t\r\n\t// collision occurs\r\n\t[csend1] b=1 & y2<=delay -> (b'=2) & (y1'=0); // message being sent (move to collision)\r\n\t[csend2] b=1 & y1<=delay -> (b'=2) & (y2'=0); // message being sent (move to collision)\r\n\t\r\n\t// message being sent\r\n\t[busy1] b=1 & y2>delay -> (b'=1);\r\n\t[busy2] b=1 & y1>delay -> (b'=1);\r\n\t\r\n\t// station finishes\r\n\t[end1] b=1 -> (b'=0) & (y1'=0);\r\n\t[end2] b=1 -> (b'=0) & (y2'=0);\r\n\t\r\n\t// collision detected\r\n\t[cd1] b=2 & y1>=delay -> (b'=4); // station one detects collision before station two\r\n\t[cd2] b=2 & y2>=delay -> (b'=3); // station two detects collision before station one\r\n\r\n\t[cd1] b=3 & y1>=delay -> (b'=0) & (y1'=0) & (y2'=0); // station one detects collision after station two\r\n\t[cd2] b=4 & y2>=delay -> (b'=0) & (y1'=0) & (y2'=0); // station two detects collision after station one\r\n\t\t\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// STATION 1\r\nmodule station1\r\n\t\r\n\t// LOCAL STATE\r\n\ts1 : [0..4];\r\n\t// s1=0 - initial state\r\n\t// s1=1 - transmit\r\n\t// s1=2 - collision (set backoff)\r\n\t// s1=3 - wait (bus busy)\r\n\t// s1=4 - done (since sending only one message)\r\n\t\r\n\tx1 : clock; // local clock\r\n\r\n\tcd1 : [0..K]; // collision counter\r\n\r\n\tinvariant\r\n\t\t(s1=0 => x1<=delay) &\r\n\t\t(s1=1 => x1<=lambda) &\r\n\t\t(s1=2 => x1<=0) &\r\n\t\t(s1=3 => x1<=pow(2,cd1)*slot) &\r\n\t\t(s1=4 => true)\r\n\tendinvariant\r\n\t\r\n\t// start sending (make sure there is a collision, i.e. start before x1 equals delay)\r\n\t[send1]  s1=0 -> (s1'=1) & (x1'=0); // start sending\r\n\t[csend1] s1=0 -> (s1'=1) & (x1'=0); // start sending\r\n\t[busy1] s1=0 -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\r\n\t\r\n\t// transmitting\r\n\t[end1] s1=1 & x1=lambda -> (s1'=4) & (x1'=0); // finished\r\n\t[cd1] s1=1 -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected\r\n\t\r\n\t// set backoff (no time can pass in this state)\r\n\t// first retransmission\r\n\t[] s1=2 & cd1=1 -> 1/2 : (s1'=3) & (x1'=0*slot) \r\n\t                 + 1/2 : (s1'=3) & (x1'=1*slot);\r\n\t// second retransmission\r\n\t[] s1=2 & cd1=2 -> 1/4 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=3*slot);\r\n\t// third retransmission\r\n\t[] s1=2 & cd1=3 -> 1/8 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=7*slot);\r\n\t// fourth retransmission \r\n\t[] s1=2 & cd1=4 -> 1/16 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=15*slot);\r\n\t// fifth retransmission\r\n\t[] s1=2 & cd1=5 -> 1/32 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=31*slot);\r\n\t// sixth retransmission\r\n\t[] s1=2 & cd1=6 -> 1/64 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=31*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=32*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=33*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=34*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=35*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=36*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=37*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=38*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=39*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=40*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=41*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=42*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=43*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=44*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=45*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=46*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=47*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=48*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=49*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=50*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=51*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=52*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=53*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=54*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=55*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=56*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=57*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=58*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=59*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=60*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=61*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=62*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=63*slot);\r\n\t// seventh retransmission\r\n\t[] s1=2 & cd1=7 -> 1/128 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=31*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=32*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=33*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=34*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=35*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=36*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=37*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=38*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=39*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=40*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=41*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=42*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=43*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=44*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=45*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=46*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=47*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=48*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=49*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=50*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=51*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=52*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=53*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=54*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=55*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=56*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=57*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=58*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=59*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=60*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=61*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=62*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=63*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=64*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=65*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=66*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=67*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=68*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=69*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=70*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=71*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=72*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=73*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=74*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=75*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=76*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=77*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=78*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=79*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=80*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=81*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=82*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=83*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=84*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=85*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=86*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=87*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=88*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=89*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=90*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=91*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=92*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=93*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=94*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=95*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=96*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=97*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=98*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=99*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=100*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=101*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=102*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=103*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=104*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=105*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=106*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=107*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=108*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=109*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=110*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=111*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=112*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=113*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=114*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=115*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=116*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=117*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=118*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=119*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=120*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=121*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=122*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=123*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=124*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=125*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=126*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=127*slot);\r\n\t// eigth retransmission\r\n\t[] s1=2 & cd1=8 -> 1/256 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=31*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=32*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=33*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=34*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=35*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=36*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=37*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=38*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=39*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=40*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=41*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=42*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=43*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=44*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=45*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=46*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=47*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=48*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=49*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=50*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=51*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=52*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=53*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=54*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=55*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=56*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=57*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=58*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=59*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=60*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=61*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=62*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=63*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=64*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=65*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=66*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=67*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=68*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=69*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=70*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=71*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=72*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=73*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=74*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=75*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=76*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=77*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=78*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=79*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=80*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=81*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=82*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=83*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=84*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=85*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=86*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=87*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=88*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=89*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=90*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=91*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=92*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=93*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=94*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=95*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=96*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=97*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=98*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=99*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=100*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=101*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=102*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=103*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=104*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=105*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=106*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=107*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=108*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=109*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=110*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=111*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=112*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=113*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=114*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=115*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=116*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=117*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=118*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=119*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=120*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=121*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=122*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=123*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=124*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=125*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=126*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=127*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=128*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=129*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=130*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=131*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=132*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=133*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=134*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=135*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=136*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=137*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=138*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=139*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=140*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=141*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=142*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=143*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=144*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=145*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=146*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=147*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=148*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=149*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=150*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=151*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=152*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=153*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=154*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=155*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=156*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=157*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=158*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=159*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=160*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=161*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=162*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=163*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=164*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=165*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=166*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=167*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=168*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=169*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=170*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=171*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=172*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=173*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=174*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=175*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=176*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=177*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=178*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=179*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=180*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=181*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=182*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=183*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=184*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=185*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=186*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=187*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=188*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=189*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=190*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=191*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=192*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=193*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=194*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=195*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=196*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=197*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=198*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=199*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=200*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=201*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=202*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=203*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=204*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=205*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=206*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=207*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=208*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=209*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=210*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=211*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=212*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=213*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=214*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=215*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=216*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=217*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=218*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=219*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=220*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=221*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=222*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=223*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=224*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=225*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=226*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=227*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=228*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=229*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=230*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=231*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=232*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=233*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=234*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=235*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=236*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=237*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=238*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=239*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=240*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=241*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=242*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=243*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=244*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=245*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=246*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=247*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=248*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=249*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=250*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=251*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=252*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=253*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=254*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=255*slot);\r\n\t// ninth retransmission\r\n\t[] s1=2 & cd1=9 -> 1/512 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=31*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=32*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=33*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=34*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=35*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=36*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=37*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=38*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=39*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=40*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=41*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=42*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=43*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=44*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=45*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=46*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=47*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=48*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=49*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=50*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=51*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=52*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=53*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=54*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=55*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=56*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=57*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=58*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=59*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=60*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=61*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=62*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=63*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=64*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=65*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=66*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=67*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=68*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=69*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=70*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=71*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=72*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=73*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=74*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=75*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=76*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=77*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=78*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=79*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=80*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=81*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=82*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=83*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=84*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=85*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=86*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=87*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=88*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=89*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=90*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=91*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=92*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=93*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=94*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=95*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=96*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=97*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=98*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=99*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=100*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=101*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=102*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=103*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=104*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=105*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=106*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=107*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=108*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=109*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=110*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=111*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=112*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=113*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=114*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=115*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=116*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=117*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=118*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=119*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=120*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=121*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=122*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=123*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=124*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=125*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=126*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=127*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=128*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=129*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=130*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=131*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=132*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=133*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=134*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=135*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=136*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=137*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=138*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=139*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=140*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=141*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=142*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=143*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=144*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=145*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=146*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=147*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=148*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=149*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=150*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=151*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=152*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=153*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=154*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=155*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=156*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=157*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=158*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=159*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=160*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=161*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=162*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=163*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=164*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=165*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=166*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=167*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=168*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=169*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=170*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=171*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=172*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=173*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=174*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=175*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=176*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=177*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=178*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=179*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=180*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=181*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=182*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=183*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=184*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=185*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=186*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=187*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=188*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=189*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=190*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=191*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=192*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=193*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=194*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=195*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=196*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=197*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=198*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=199*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=200*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=201*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=202*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=203*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=204*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=205*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=206*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=207*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=208*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=209*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=210*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=211*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=212*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=213*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=214*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=215*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=216*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=217*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=218*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=219*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=220*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=221*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=222*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=223*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=224*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=225*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=226*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=227*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=228*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=229*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=230*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=231*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=232*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=233*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=234*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=235*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=236*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=237*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=238*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=239*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=240*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=241*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=242*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=243*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=244*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=245*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=246*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=247*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=248*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=249*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=250*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=251*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=252*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=253*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=254*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=255*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=256*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=257*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=258*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=259*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=260*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=261*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=262*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=263*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=264*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=265*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=266*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=267*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=268*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=269*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=270*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=271*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=272*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=273*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=274*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=275*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=276*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=277*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=278*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=279*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=280*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=281*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=282*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=283*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=284*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=285*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=286*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=287*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=288*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=289*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=290*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=291*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=292*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=293*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=294*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=295*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=296*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=297*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=298*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=299*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=300*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=301*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=302*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=303*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=304*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=305*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=306*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=307*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=308*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=309*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=310*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=311*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=312*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=313*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=314*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=315*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=316*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=317*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=318*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=319*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=320*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=321*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=322*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=323*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=324*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=325*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=326*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=327*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=328*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=329*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=330*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=331*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=332*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=333*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=334*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=335*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=336*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=337*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=338*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=339*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=340*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=341*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=342*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=343*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=344*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=345*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=346*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=347*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=348*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=349*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=350*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=351*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=352*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=353*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=354*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=355*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=356*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=357*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=358*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=359*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=360*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=361*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=362*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=363*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=364*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=365*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=366*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=367*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=368*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=369*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=370*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=371*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=372*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=373*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=374*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=375*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=376*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=377*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=378*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=379*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=380*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=381*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=382*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=383*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=384*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=385*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=386*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=387*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=388*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=389*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=390*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=391*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=392*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=393*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=394*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=395*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=396*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=397*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=398*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=399*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=400*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=401*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=402*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=403*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=404*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=405*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=406*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=407*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=408*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=409*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=410*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=411*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=412*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=413*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=414*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=415*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=416*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=417*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=418*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=419*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=420*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=421*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=422*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=423*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=424*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=425*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=426*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=427*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=428*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=429*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=430*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=431*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=432*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=433*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=434*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=435*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=436*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=437*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=438*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=439*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=440*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=441*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=442*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=443*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=444*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=445*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=446*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=447*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=448*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=449*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=450*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=451*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=452*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=453*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=454*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=455*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=456*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=457*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=458*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=459*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=460*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=461*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=462*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=463*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=464*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=465*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=466*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=467*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=468*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=469*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=470*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=471*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=472*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=473*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=474*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=475*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=476*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=477*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=478*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=479*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=480*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=481*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=482*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=483*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=484*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=485*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=486*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=487*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=488*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=489*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=490*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=491*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=492*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=493*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=494*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=495*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=496*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=497*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=498*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=499*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=500*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=501*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=502*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=503*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=504*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=505*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=506*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=507*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=508*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=509*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=510*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=511*slot);\r\n\t// tenth (or more) retransmission\r\n\t[] s1=2 & cd1=10 -> 1/1024 : (s1'=3) & (x1'=0*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=2*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=3*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=4*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=5*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=6*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=7*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=8*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=9*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=10*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=11*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=12*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=13*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=14*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=15*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=16*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=17*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=18*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=19*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=20*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=21*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=22*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=23*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=24*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=25*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=26*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=27*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=28*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=29*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=30*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=31*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=32*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=33*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=34*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=35*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=36*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=37*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=38*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=39*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=40*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=41*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=42*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=43*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=44*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=45*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=46*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=47*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=48*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=49*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=50*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=51*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=52*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=53*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=54*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=55*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=56*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=57*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=58*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=59*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=60*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=61*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=62*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=63*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=64*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=65*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=66*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=67*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=68*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=69*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=70*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=71*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=72*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=73*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=74*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=75*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=76*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=77*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=78*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=79*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=80*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=81*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=82*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=83*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=84*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=85*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=86*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=87*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=88*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=89*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=90*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=91*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=92*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=93*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=94*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=95*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=96*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=97*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=98*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=99*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=100*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=101*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=102*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=103*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=104*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=105*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=106*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=107*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=108*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=109*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=110*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=111*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=112*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=113*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=114*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=115*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=116*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=117*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=118*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=119*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=120*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=121*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=122*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=123*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=124*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=125*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=126*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=127*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=128*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=129*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=130*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=131*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=132*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=133*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=134*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=135*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=136*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=137*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=138*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=139*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=140*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=141*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=142*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=143*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=144*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=145*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=146*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=147*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=148*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=149*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=150*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=151*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=152*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=153*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=154*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=155*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=156*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=157*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=158*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=159*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=160*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=161*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=162*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=163*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=164*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=165*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=166*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=167*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=168*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=169*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=170*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=171*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=172*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=173*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=174*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=175*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=176*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=177*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=178*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=179*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=180*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=181*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=182*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=183*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=184*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=185*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=186*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=187*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=188*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=189*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=190*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=191*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=192*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=193*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=194*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=195*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=196*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=197*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=198*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=199*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=200*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=201*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=202*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=203*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=204*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=205*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=206*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=207*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=208*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=209*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=210*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=211*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=212*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=213*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=214*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=215*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=216*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=217*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=218*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=219*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=220*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=221*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=222*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=223*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=224*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=225*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=226*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=227*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=228*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=229*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=230*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=231*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=232*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=233*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=234*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=235*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=236*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=237*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=238*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=239*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=240*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=241*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=242*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=243*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=244*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=245*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=246*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=247*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=248*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=249*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=250*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=251*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=252*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=253*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=254*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=255*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=256*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=257*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=258*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=259*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=260*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=261*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=262*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=263*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=264*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=265*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=266*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=267*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=268*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=269*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=270*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=271*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=272*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=273*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=274*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=275*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=276*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=277*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=278*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=279*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=280*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=281*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=282*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=283*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=284*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=285*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=286*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=287*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=288*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=289*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=290*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=291*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=292*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=293*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=294*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=295*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=296*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=297*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=298*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=299*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=300*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=301*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=302*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=303*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=304*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=305*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=306*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=307*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=308*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=309*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=310*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=311*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=312*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=313*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=314*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=315*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=316*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=317*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=318*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=319*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=320*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=321*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=322*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=323*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=324*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=325*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=326*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=327*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=328*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=329*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=330*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=331*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=332*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=333*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=334*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=335*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=336*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=337*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=338*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=339*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=340*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=341*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=342*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=343*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=344*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=345*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=346*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=347*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=348*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=349*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=350*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=351*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=352*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=353*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=354*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=355*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=356*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=357*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=358*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=359*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=360*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=361*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=362*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=363*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=364*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=365*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=366*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=367*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=368*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=369*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=370*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=371*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=372*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=373*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=374*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=375*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=376*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=377*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=378*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=379*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=380*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=381*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=382*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=383*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=384*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=385*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=386*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=387*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=388*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=389*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=390*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=391*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=392*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=393*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=394*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=395*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=396*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=397*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=398*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=399*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=400*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=401*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=402*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=403*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=404*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=405*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=406*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=407*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=408*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=409*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=410*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=411*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=412*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=413*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=414*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=415*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=416*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=417*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=418*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=419*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=420*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=421*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=422*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=423*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=424*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=425*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=426*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=427*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=428*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=429*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=430*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=431*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=432*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=433*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=434*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=435*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=436*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=437*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=438*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=439*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=440*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=441*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=442*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=443*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=444*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=445*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=446*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=447*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=448*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=449*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=450*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=451*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=452*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=453*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=454*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=455*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=456*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=457*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=458*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=459*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=460*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=461*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=462*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=463*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=464*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=465*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=466*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=467*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=468*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=469*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=470*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=471*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=472*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=473*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=474*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=475*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=476*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=477*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=478*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=479*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=480*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=481*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=482*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=483*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=484*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=485*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=486*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=487*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=488*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=489*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=490*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=491*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=492*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=493*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=494*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=495*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=496*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=497*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=498*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=499*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=500*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=501*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=502*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=503*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=504*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=505*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=506*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=507*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=508*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=509*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=510*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=511*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=512*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=513*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=514*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=515*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=516*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=517*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=518*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=519*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=520*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=521*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=522*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=523*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=524*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=525*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=526*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=527*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=528*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=529*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=530*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=531*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=532*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=533*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=534*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=535*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=536*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=537*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=538*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=539*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=540*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=541*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=542*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=543*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=544*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=545*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=546*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=547*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=548*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=549*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=550*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=551*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=552*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=553*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=554*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=555*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=556*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=557*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=558*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=559*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=560*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=561*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=562*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=563*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=564*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=565*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=566*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=567*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=568*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=569*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=570*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=571*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=572*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=573*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=574*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=575*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=576*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=577*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=578*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=579*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=580*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=581*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=582*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=583*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=584*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=585*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=586*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=587*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=588*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=589*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=590*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=591*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=592*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=593*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=594*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=595*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=596*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=597*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=598*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=599*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=600*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=601*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=602*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=603*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=604*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=605*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=606*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=607*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=608*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=609*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=610*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=611*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=612*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=613*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=614*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=615*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=616*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=617*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=618*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=619*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=620*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=621*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=622*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=623*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=624*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=625*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=626*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=627*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=628*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=629*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=630*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=631*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=632*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=633*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=634*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=635*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=636*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=637*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=638*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=639*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=640*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=641*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=642*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=643*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=644*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=645*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=646*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=647*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=648*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=649*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=650*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=651*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=652*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=653*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=654*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=655*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=656*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=657*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=658*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=659*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=660*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=661*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=662*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=663*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=664*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=665*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=666*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=667*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=668*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=669*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=670*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=671*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=672*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=673*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=674*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=675*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=676*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=677*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=678*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=679*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=680*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=681*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=682*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=683*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=684*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=685*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=686*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=687*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=688*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=689*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=690*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=691*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=692*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=693*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=694*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=695*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=696*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=697*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=698*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=699*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=700*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=701*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=702*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=703*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=704*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=705*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=706*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=707*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=708*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=709*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=710*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=711*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=712*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=713*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=714*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=715*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=716*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=717*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=718*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=719*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=720*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=721*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=722*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=723*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=724*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=725*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=726*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=727*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=728*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=729*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=730*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=731*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=732*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=733*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=734*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=735*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=736*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=737*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=738*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=739*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=740*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=741*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=742*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=743*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=744*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=745*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=746*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=747*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=748*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=749*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=750*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=751*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=752*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=753*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=754*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=755*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=756*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=757*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=758*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=759*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=760*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=761*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=762*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=763*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=764*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=765*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=766*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=767*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=768*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=769*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=770*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=771*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=772*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=773*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=774*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=775*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=776*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=777*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=778*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=779*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=780*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=781*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=782*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=783*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=784*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=785*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=786*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=787*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=788*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=789*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=790*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=791*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=792*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=793*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=794*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=795*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=796*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=797*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=798*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=799*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=800*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=801*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=802*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=803*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=804*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=805*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=806*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=807*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=808*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=809*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=810*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=811*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=812*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=813*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=814*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=815*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=816*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=817*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=818*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=819*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=820*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=821*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=822*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=823*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=824*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=825*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=826*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=827*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=828*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=829*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=830*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=831*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=832*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=833*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=834*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=835*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=836*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=837*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=838*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=839*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=840*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=841*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=842*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=843*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=844*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=845*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=846*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=847*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=848*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=849*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=850*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=851*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=852*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=853*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=854*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=855*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=856*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=857*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=858*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=859*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=860*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=861*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=862*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=863*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=864*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=865*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=866*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=867*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=868*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=869*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=870*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=871*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=872*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=873*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=874*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=875*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=876*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=877*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=878*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=879*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=880*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=881*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=882*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=883*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=884*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=885*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=886*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=887*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=888*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=889*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=890*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=891*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=892*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=893*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=894*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=895*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=896*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=897*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=898*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=899*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=900*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=901*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=902*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=903*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=904*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=905*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=906*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=907*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=908*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=909*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=910*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=911*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=912*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=913*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=914*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=915*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=916*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=917*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=918*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=919*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=920*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=921*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=922*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=923*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=924*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=925*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=926*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=927*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=928*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=929*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=930*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=931*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=932*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=933*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=934*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=935*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=936*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=937*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=938*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=939*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=940*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=941*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=942*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=943*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=944*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=945*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=946*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=947*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=948*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=949*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=950*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=951*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=952*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=953*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=954*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=955*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=956*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=957*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=958*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=959*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=960*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=961*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=962*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=963*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=964*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=965*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=966*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=967*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=968*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=969*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=970*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=971*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=972*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=973*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=974*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=975*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=976*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=977*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=978*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=979*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=980*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=981*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=982*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=983*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=984*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=985*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=986*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=987*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=988*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=989*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=990*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=991*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=992*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=993*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=994*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=995*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=996*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=997*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=998*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=999*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1000*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1001*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1002*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1003*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1004*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1005*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1006*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1007*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1008*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1009*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1010*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1011*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1012*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1013*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1014*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1015*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1016*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1017*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1018*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1019*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1020*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1021*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1022*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1023*slot);\r\n\t\r\n\t// wait until backoff counter reaches 0 then send again\r\n\t[send1]  s1=3 & x1=pow(2,cd1)*slot -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\r\n\t[csend1] s1=3 & x1=pow(2,cd1)*slot -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\r\n\t[busy1]  s1=3 & x1=pow(2,cd1)*slot  -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\r\n\t\r\n\t// once finished loop (wait for other station to finish)\r\n\t[done] s1=4 -> (s1'=4);\r\n\r\nendmodule\r\n\r\n// construct station 2 through renaming\r\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,send1=send2,csend1=csend2,busy1=busy2,end1=end2] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// REWARD STRUCTURES\r\n\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// number of collisions\r\nrewards \"collisions\"\r\n\t[csend1] true : 1;\r\n\t[csend2] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// LABELS\r\n\r\nlabel \"s1_done\" = s1=4;\r\nlabel \"s2_done\" = s2=4;\r\nlabel \"done\" = s1=4 & s2=4;\r\nlabel \"cmax\" = c=COL;\r\n"
  },
  {
    "path": "prism-examples/ptas/csma/full/eventually.pctl",
    "content": "Pmin=?[ F \"s1_done\"]\r\nPmin=?[ F \"s2_done\"]\r\nPmin=?[ F \"done\" ]\r\nPmin=?[ F cd1=2 ]\r\nPmax=?[ F cd1=2 ]\r\n"
  },
  {
    "path": "prism-examples/ptas/csma/full/time.pctl",
    "content": "R{\"time\"}min=? [ F \"done\" ]\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/README.txt",
    "content": "This case study concerns the Tree Identify Protocol of the IEEE 1394 High Performance Serial Bus (called ``FireWire'').\r\n\r\nThese are probabilistic timed automaton (PTA) models. You can also find, in the directory ../../firewire,\r\nmanually-created MDP models for this case study, built using the \"digital clocks\" semantics [KNPS06].\r\n\r\nWe consider the following probabilistic timed automata models of the root contention part of the \r\ntree identify protocol, which are based on probabilistic I/O automata models presented in [SV99].\r\n\r\nimpl: which consists of the parallel composition of two nodes (Node1 and Node2),\r\n      and two communication channels (Wire12 for messages from Node1 to Node2,\r\n      and Wire21 for messages from Node2 to Node1) and corresponds to the \r\n      system Impl of [SV99]. \r\n\r\nabst: which is represented by a single probabilistic timed automaton and is an abstraction of Impl \r\n      based on the the probabilistic I/O automaton I1 of [SV99].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/firewire.php\r\n\r\n=====================================================================================\r\n\r\n[SV99]\r\nM. Stoelinga and F. Vaandrager\r\nRoot Contention in IEEE 1394\r\nIn Proc.  5th AMAST Workshop on Real-Time and Probabilistic Systems (ARTS'99), pp. 53-74, 1999\r\n(Available as Volume 1601 of LNCS, (c) Springer Verlag)\r\n\r\n[KNPS06]\r\nM. Kwiatkowska, G. Norman, D. Parker and J. Sproston\r\nPerformance Analysis of Probabilistic Timed Automata using Digital Clocks\r\nFormal Methods in System Design, 29:33-78, 2006"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/.args",
    "content": "-aroptions refine=all,nopre\n"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/.models",
    "content": "#firewire.nm -const delay=30\nfirewire.nm -const delay=360\n\n"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/.props",
    "content": "eventually.pctl\ndeadline.pctl -const T=5000\ndeadline.pctl -const T=10000\ndeadline.pctl -const T=20000\n"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/auto",
    "content": "#!/bin/csh\n\nprism firewire.nm eventually.pctl -const delay=360 -aroptions nopre,refine=all,opt\n\nprism firewire.nm deadline.pctl -const delay=360,T=5000 -aroptions nopre,refine=all,opt\nprism firewire.nm deadline.pctl -const delay=360,T=10000 -aroptions nopre,refine=all,opt\nprism firewire.nm deadline.pctl -const delay=360,T=20000 -aroptions nopre,refine=all,opt\n\n#prism firewire.nm time.pctl -const delay=360 -aroptions nopre,refine=all,opt\n"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/deadline-max.pctl",
    "content": "// Maximum probability that a leader has been elected by deadline T\r\nPmax=? [ F \"done_after\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/deadline.pctl",
    "content": "const int T;\r\n\r\n// Minimum probability that a leader has been elected by deadline T\r\nPmin=? [ F<=T \"done\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/eventually.pctl",
    "content": "// Minimum probability that a leader is eventually elected\r\nPmin=? [ F \"done\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/firewire.nm",
    "content": "// Abstract model of Firewire protocol (PTA model)\r\n// dxp/gxn 08/07/09\r\n\r\npta\r\n\r\n// maximum and minimum delays\r\n// fast\r\nconst int rc_fast_max = 850;\r\nconst int rc_fast_min = 760;\r\n// slow\r\nconst int rc_slow_max = 1670;\r\nconst int rc_slow_min = 1590;\r\n// delay caused by the wire length\r\nconst int delay;\r\n// probability of choosing fast and slow\r\nconst double fast = 0.5;\r\nconst double slow = 1-fast;\r\n\r\nmodule abstract_firewire\r\n\r\n\t// clock \r\n\tx : clock;\r\n\t// local state\r\n\ts : [0..9];\r\n\t// 0 - start_start\r\n\t// 1 - fast_start\r\n\t// 2 - start_fast\r\n\t// 3 - start_slow\r\n\t// 4 - slow_start\r\n\t// 5 - fast_fast\r\n\t// 6 - fast_slow\r\n\t// 7 - slow_fast\r\n\t// 8 - slow_slow\r\n\t// 9 - done\r\n\r\n\t// clock invariant\r\n\tinvariant\r\n\t\t(s=0 => x<=delay) &\r\n\t\t(s=1 => x<=delay) &\r\n\t\t(s=2 => x<=delay) &\r\n\t\t(s=3 => x<=delay) &\r\n\t\t(s=4 => x<=delay) &\r\n\t\t(s=5 => x<=rc_fast_max) &\r\n\t\t(s=6 => x<=rc_slow_max) &\r\n\t\t(s=7 => x<=rc_slow_max) &\r\n\t\t(s=8 => x<=rc_slow_max)\r\n\tendinvariant\r\n\t\r\n\t// start_start (initial state)\r\n\t[] s=0 -> fast : (s'=1) + slow : (s'=4);\r\n\t[] s=0 -> fast : (s'=2) + slow : (s'=3);\r\n\t// fast_start\r\n\t[] s=1 -> fast : (s'=5) & (x'=0) + slow : (s'=6) & (x'=0);\r\n\t// start_fast\r\n\t[] s=2 -> fast : (s'=5) & (x'=0) + slow : (s'=7) & (x'=0);\r\n\t// start_slow\r\n\t[] s=3 -> fast : (s'=6) & (x'=0) + slow : (s'=8) & (x'=0);\r\n\t// slow_start\r\n\t[] s=4 -> fast : (s'=7) & (x'=0) + slow : (s'=8) & (x'=0);\r\n\t// fast_fast\r\n\t[] s=5 & (x>=rc_fast_min)       -> (s'=0) & (x'=0);\r\n\t[] s=5 & (x>=rc_fast_min-delay) -> (s'=9) & (x'=0);\r\n\t// fast_slow\r\n\t[] s=6 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// slow_fast\r\n\t[] s=7 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// slow_slow\r\n\t[] s=8 & x>=rc_slow_min       -> (s'=0) & (x'=0);\r\n\t[] s=8 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// done\r\n\t[] s=9 -> true;\r\n\t\r\nendmodule\r\n\r\n// labels\r\nlabel \"done\" = (s=9);\r\n\r\n// reward structures\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/abst/time.pctl",
    "content": "// Maximum expected time to elect a leader\r\nR{\"time\"}max=? [ F \"done\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/impl/.args",
    "content": "-aroptions refine=all,nopre\n"
  },
  {
    "path": "prism-examples/ptas/firewire/impl/.models",
    "content": "#firewire.nm -const delay=30\nfirewire.nm -const delay=360\n\n"
  },
  {
    "path": "prism-examples/ptas/firewire/impl/.props",
    "content": "eventually.pctl\ndeadline.pctl -const T=2500\ndeadline.pctl -const T=5000\ndeadline.pctl -const T=7500\n"
  },
  {
    "path": "prism-examples/ptas/firewire/impl/auto",
    "content": "#!/bin/csh\n\nprism firewire.nm eventually.pctl -const delay=360 -aroptions nopre,refine=all,opt\n\nprism firewire.nm deadline.pctl -const delay=360,T=2500 -aroptions nopre,refine=all,opt\nprism firewire.nm deadline.pctl -const delay=360,T=5000 -aroptions nopre,refine=all,opt\nprism firewire.nm deadline.pctl -const delay=360,T=7500 -aroptions nopre,refine=all,opt\n"
  },
  {
    "path": "prism-examples/ptas/firewire/impl/deadline.pctl",
    "content": "const int T;\r\n\r\n// Minimum probability that a leader has been elected by deadline T\r\nPmin=? [ F<=T \"done\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/impl/eventually.pctl",
    "content": "// Minimum probability that a leader is eventually elected\r\nPmin=? [ F \"done\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/impl/firewire.nm",
    "content": "// Firewire protocol (PTA model)\r\n// dxp/gxn 08/07/09\r\n\r\npta\r\n\r\n// CLOCKS\r\n// x1 (x2) clock for node1 (node2)\r\n// y1 and y2 (z1 and z2) clocks for wire12 (wire21)\r\n\r\n// maximum and minimum delays\r\n// fast\r\nconst int rc_fast_max = 850;\r\nconst int rc_fast_min = 760;\r\n// slow\r\nconst int rc_slow_max = 1670;\r\nconst int rc_slow_min = 1590;\r\n// delay caused by the wire length\r\nconst int delay;\r\n// probability of choosing fast and slow\r\nconst double fast = 0.5;\r\nconst double slow = 1-fast;\r\n\r\nmodule wire12\r\n\t\r\n\t// local state\r\n\tw12 : [0..9];\r\n\t// 0 - empty\r\n\t// 1 - rec_req\r\n\t// 2 - rec_req_ack\r\n\t// 3 - rec_ack\r\n\t// 4 - rec_ack_idle\r\n\t// 5 - rec_idle\r\n\t// 6 - rec_idle_req\r\n\t// 7 - rec_ack_req\r\n\t// 8 - rec_req_idle\r\n\t// 9 - rec_idle_ack\r\n\t\r\n\t// clock for wire12\r\n\ty1 : clock;\r\n\ty2 : clock;\r\n\r\n\t// clock invariant\r\n\tinvariant\r\n\t    (w12=1 => y2<=delay)\r\n\t  & (w12=2 => y1<=delay)\r\n\t  & (w12=3 => y2<=delay)\r\n\t  & (w12=4 => y1<=delay)\r\n\t  & (w12=5 => y2<=delay)\r\n\t  & (w12=6 => y1<=delay)\r\n\t  & (w12=7 => y1<=delay)\r\n\t  & (w12=8 => y1<=delay)\r\n\t  & (w12=9 => y1<=delay)\r\n\tendinvariant\r\n\r\n\t// empty\r\n\t// do not need y1 and y2 to increase as always reset when this state is left\r\n\t// similarly can reset y1 and y2 when we re-enter this state\r\n\t[snd_req12]  w12=0 -> (w12'=1) & (y1'=0) & (y2'=0);\r\n\t[snd_ack12]  w12=0 -> (w12'=3) & (y1'=0) & (y2'=0);\r\n\t[snd_idle12] w12=0 -> (w12'=5) & (y1'=0) & (y2'=0);\r\n\t// rec_req\r\n\t[snd_req12]  w12=1 -> (w12'=1);\r\n\t[rec_req12]  w12=1 -> (w12'=0) & (y1'=0) & (y2'=0);\r\n\t[snd_ack12]  w12=1 -> (w12'=2) & (y2'=0);\r\n\t[snd_idle12] w12=1 -> (w12'=8) & (y2'=0);\r\n\t// rec_req_ack\r\n\t[snd_ack12] w12=2 -> (w12'=2);\r\n\t[rec_req12] w12=2 -> (w12'=3);\r\n\t// rec_ack\r\n\t[snd_ack12]  w12=3 -> (w12'=3);\r\n\t[rec_ack12]  w12=3 -> (w12'=0) & (y1'=0) & (y2'=0);\r\n\t[snd_idle12] w12=3 -> (w12'=4) & (y2'=0);\r\n\t[snd_req12]  w12=3 -> (w12'=7) & (y2'=0);\r\n\t// rec_ack_idle\r\n\t[snd_idle12] w12=4 -> (w12'=4);\r\n\t[rec_ack12]  w12=4 -> (w12'=5);\r\n\t// rec_idle\r\n\t[snd_idle12] w12=5 -> (w12'=5);\r\n\t[rec_idle12] w12=5 -> (w12'=0) & (y1'=0) & (y2'=0);\r\n\t[snd_req12]  w12=5 -> (w12'=6) & (y2'=0);\r\n\t[snd_ack12]  w12=5 -> (w12'=9) & (y2'=0);\r\n\t// rec_idle_req\r\n\t[snd_req12]  w12=6 -> (w12'=6);\r\n\t[rec_idle12] w12=6 -> (w12'=1);\r\n\t// rec_ack_req\r\n\t[snd_req12] w12=7 -> (w12'=7);\r\n\t[rec_ack12] w12=7 -> (w12'=1);\r\n\t// rec_req_idle\r\n\t[snd_idle12] w12=8 -> (w12'=8);\r\n\t[rec_req12]  w12=8 -> (w12'=5);\r\n\t// rec_idle_ack\r\n\t[snd_ack12]  w12=9 -> (w12'=9);\r\n\t[rec_idle12] w12=9 -> (w12'=3);\r\n\t\r\nendmodule\r\n\r\nmodule node1\r\n\t\r\n\t// clock for node1\r\n\tx1 : clock;\r\n\t\r\n\t// local state\r\n\ts1 : [0..8];\r\n\t// 0 - root contention\r\n\t// 1 - rec_idle\r\n\t// 2 - rec_req_fast\r\n\t// 3 - rec_req_slow\r\n\t// 4 - rec_idle_fast\r\n\t// 5 - rec_idle_slow\r\n\t// 6 - snd_req\r\n\t// 7 - almost_root\r\n\t// 8 - almost_child\r\n\t\r\n\t// clock invariant\r\n\tinvariant\r\n\t    (s1=2 => x1<=rc_fast_max)\r\n\t  & (s1=3 => x1<=rc_slow_max)\r\n\t  & (s1=4 => x1<=rc_fast_max)\r\n\t  & (s1=5 => x1<=rc_slow_max)\r\n\t  // urgency:\r\n\t  & (s1=0 => x1<=0)\r\n\t  & (s1=1 => x1<=0)\r\n\tendinvariant\r\n\t\r\n\t// added resets to x1 when not considered again until after rest\r\n\t// removed root and child (using almost root and almost child)\r\n\t\r\n\t// root contention immediate state)\r\n\t[snd_idle12] s1=0 & x1=0 -> fast : (s1'=2) +  slow : (s1'=3);\r\n\t[rec_idle21] s1=0 & x1=0 -> (s1'=1);\r\n\t// rec_idle immediate state)\r\n\t[snd_idle12] s1=1 & x1=0 -> fast : (s1'=4) +  slow : (s1'=5);\r\n\t[rec_req21]  s1=1 & x1=0 -> (s1'=0);\r\n\t// rec_req_fast\r\n\t[rec_idle21] s1=2 -> (s1'=4);\t\r\n\t[snd_ack12]  s1=2 & x1>=rc_fast_min -> (s1'=7) & (x1'=0);\r\n\t// rec_req_slow\r\n\t[rec_idle21] s1=3 -> (s1'=5);\r\n\t[snd_ack12]  s1=3 & x1>=rc_slow_min -> (s1'=7) & (x1'=0);\r\n\t// rec_idle_fast\r\n\t[rec_req21] s1=4 -> (s1'=2);\r\n\t[snd_req12] s1=4 & x1>=rc_fast_min -> (s1'=6) & (x1'=0);\r\n\t// rec_idle_slow\r\n\t[rec_req21] s1=5 -> (s1'=3);\r\n\t[snd_req12] s1=5 & x1>=rc_slow_min -> (s1'=6) & (x1'=0);\r\n\t// snd_req \r\n\t// do not use x1 until reset (in state 0 or in state 1) so do not need to increase x1\r\n\t// also can set x1 to 0 upon entering this state\r\n\t[rec_req21] s1=6 -> (s1'=0) & (x1'=0);\r\n\t[rec_ack21] s1=6 -> (s1'=8) & (x1'=0);\r\n\t// almost root or almost child (immediate) \r\n\t// loop in final states to remove deadlock\r\n\t[loop] s1=7 -> true;\r\n\t[loop] s1=8 -> true;\r\n\t\r\nendmodule\r\n\r\n// construct remaining automata through renaming\r\nmodule wire21=wire12[w12=w21, y1=z1, y2=z2, \r\n\tsnd_req12=snd_req21, snd_idle12=snd_idle21, snd_ack12=snd_ack21,\r\n\trec_req12=rec_req21, rec_idle12=rec_idle21, rec_ack12=rec_ack21]\r\nendmodule\r\nmodule node2=node1[s1=s2, s2=s1, x1=x2, \r\n\trec_req21=rec_req12, rec_idle21=rec_idle12, rec_ack21=rec_ack12,\r\n\tsnd_req12=snd_req21, snd_idle12=snd_idle21, snd_ack12=snd_ack21]\r\nendmodule\r\n\r\n// labels\r\nlabel \"done\" = (s1=8 & s2=7) | (s1=7 & s2=8);\r\n\r\n// reward structures\r\n// time\r\nrewards \"time\"\t\r\n\ttrue : 1;\r\nendrewards\r\n// time nodes sending\r\nrewards \"time_sending\"\r\n\t(w12>0 | w21>0) : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/ptas/firewire/impl/time.pctl",
    "content": "// Maximum expected time to elect a leader\r\nR{\"time\"}min=? [ F \"done\" ]\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/honest/.args",
    "content": "-aroptions refine=all,nopre\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/honest/.models",
    "content": "repudiation.nm\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/honest/.props",
    "content": "eventually.pctl\ndeadline.pctl -const T=40\ndeadline.pctl -const T=80\ndeadline.pctl -const T=100\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/honest/auto",
    "content": "#!/bin/csh\n\nprism repudiation.nm eventually.pctl -aroptions refine=all,opt\n\nprism repudiation.nm deadline.pctl -aroptions refine=all,opt -const T=40\nprism repudiation.nm deadline.pctl -aroptions refine=all,opt -const T=80\nprism repudiation.nm deadline.pctl -aroptions refine=all,opt -const T=100\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/honest/deadline.pctl",
    "content": "const int T;\r\n\r\n// Minimum probability that protocol terminates successfully by the deadline\r\nPmin=? [ F<T \"terminated_successfully\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/honest/eventually.pctl",
    "content": "// Minimum probability that the protocol terminates successfully\r\nPmin=? [ F \"terminated_successfully\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/honest/repudiation.nm",
    "content": "pta\r\n\r\nmodule originator\r\n\to : [0..12];\r\n\t// 0 - init\r\n\t// 1 - send\r\n\t// 2 - wait\r\n\t// 3 - last\r\n\t// 4 - early\r\n\t// 5 - error\r\n\t// 6 - sent_random\r\n\t// 7 - sent_last\r\n\t// 8 - done\r\n\t// 9 - done_early\r\n\t// 10 - done_error\r\n\t// 11 - wait_random\r\n\t// 12 - wait_last\r\n\r\n\tx : clock;\r\n\r\n\tinvariant\r\n\t\t(o=0 => true) &\r\n\t\t(o=1 => x<=0) &\r\n\t\t(o=2 => x<=5) & // x<=AD+1\r\n\t\t(o=3 => x<=0) &\r\n\t\t(o=4 => x<=0) &\r\n\t\t(o=5 => x<=0) &\r\n\t\t(o=6 => true) &\r\n\t\t(o=7 => true) &\r\n\t\t(o=8 => true) &\r\n\t\t(o=9 => true) &\r\n\t\t(o=10 => true) &\r\n\t\t(o=11 => x<=5) & // x<=AD+1\r\n\t\t(o=12 => x<=5) // x<=AD+1\r\n\tendinvariant\r\n\r\n\t[req] o=0 -> (o'=1) & (x'=0);\r\n\t[message] o=1 & x<=0 -> (o'=2);\r\n\t[ack]  o=2 & (x>=1 & x<=4) -> 0.9 : (o'=1) & (x'=0) + 0.1 :  (o'=3) & (x'=0); // guard x>=ad,x<=AD\r\n\t[] o=2 & x>4 -> 0.9 : (o'=1) & (x'=0) + 0.1 :  (o'=3) & (x'=0); // guard x>AD\r\n\t[decode] o=2 -> 0.9 : (o'=6) + 0.1 :  (o'=7);\r\n\t[finished] o=3 -> (o'=8) & (x'=0);\r\n\r\n\t[] o=8 -> (o'=8);\r\n\t[] o=9 -> (o'=9);\r\n\t[] o=10 -> (o'=10);\r\n\r\n\t[stop] o=4 -> (o'=9); \r\n\t[error] o=5 -> (o'=10);\r\n\r\n\t[decoded_random] o=6 -> (o'=11);\r\n\t[decoded_last] o=7 -> (o'=12);\r\n\r\n\t[ack] o=11 & (x>=1 & x<=4) -> (o'=1) & (x'=0);  // guard x>=ad,x<=AD\r\n\t[stop] o=11 & x>4 ->  (o'=9) & (x'=0); \r\n\r\n\t[ack] o=12 & (x>=1 & x<=4) -> (o'=3) & (x'=0);  // guard x>=ad,x<=AD\r\n\t[stop] o=12  & x>4 -> (o'=10) & (x'=0); \r\n\r\nendmodule\r\n\r\nmodule recipient\r\n\r\n\tr : [0..3];\r\n\t// 0 - request\r\n\t// 1 - wait\r\n\t// 2 - ack\r\n\t// 3 - done\r\n\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t\t(r=0 => y<=0) &\r\n\t\t(r=1 => true) &\r\n\t\t(r=2 => y<=4) &\r\n\t\t(r=3 => true)\r\n\tendinvariant\r\n\r\n\t[req] r=0 & y=0 -> (r'=1);\r\n\t[message] r=1 -> (r'=2) & (y'=0);\r\n\t[finished] r=1 -> (r'=3);\r\n\t[ack] r=2 & (y>=1 & y<=4) -> (r'=1) & (y'=0);\r\n\r\n\t// honest recipient never tries decoding but added actions to final state\r\n\t// so the same originator is used for honest and malicious recipient\r\n\t[decode] r=3 -> (r'=3);\r\n\t[decoded_random] r=3 -> (r'=3);\r\n\t[decoded_last] r=3 -> (r'=3);\r\n\r\nendmodule\r\n\r\nlabel \"terminated_successfully\" = o=8;\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/malicious/.args",
    "content": "-aroptions refine=all,nopre\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/malicious/.models",
    "content": "repudiation.nm\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/malicious/.props",
    "content": "eventually.pctl\ndeadline.pctl -const T=5\ndeadline.pctl -const T=10\ndeadline.pctl -const T=20\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/malicious/auto",
    "content": "#!/bin/csh\n\nprism repudiation.nm eventually.pctl -aroptions refine=all,opt\n\nprism repudiation.nm deadline.pctl -aroptions refine=all,opt -const T=5\nprism repudiation.nm deadline.pctl -aroptions refine=all,opt -const T=10\nprism repudiation.nm deadline.pctl -aroptions refine=all,opt -const T=20\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/malicious/deadline.pctl",
    "content": "const int T;\r\n\r\n// Maximum probability that malicious recepient gains information by deadline T\r\nPmax=? [ F<T \"gains_information\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/malicious/eventually.pctl",
    "content": "// Maximum probability that malicious recepient gains information\r\nPmax=? [ F \"gains_information\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/repudiation/malicious/repudiation.nm",
    "content": "pta\r\n\r\nmodule originator\r\n\r\n\to : [0..12];\r\n\t// 0 - init\r\n\t// 1 - send\r\n\t// 2 - wait\r\n\t// 3 - last\r\n\t// 4 - early\r\n\t// 5 - error\r\n\t// 6 - sent_random\r\n\t// 7 - sent_last\r\n\t// 8 - done\r\n\t// 9 - done_early\r\n\t// 10 - done_error\r\n\t// 11 - wait_random\r\n\t// 12 - wait_last\r\n\r\n\tx : clock;\r\n\r\n\tinvariant\r\n\t\t(o=0 => true) &\r\n\t\t(o=1 => x<=0) &\r\n\t\t(o=2 => x<=5) & // x<=AD+1\r\n\t\t(o=3 => x<=0) &\r\n\t\t(o=4 => x<=0) &\r\n\t\t(o=5 => x<=0) &\r\n\t\t(o=6 => true) &\r\n\t\t(o=7 => true) &\r\n\t\t(o=8 => true) &\r\n\t\t(o=9 => true) &\r\n\t\t(o=10 => true) &\r\n\t\t(o=11 => x<=5) & // x<=AD+1\r\n\t\t(o=12 => x<=5) // x<=AD+1\r\n\tendinvariant\r\n\r\n\t[req] o=0 -> (o'=1) & (x'=0);\r\n\t[message] o=1 & x<=0 -> (o'=2);\r\n\t[ack]  o=2 & (x>=1 & x<=4) -> 0.9 : (o'=1) & (x'=0) + 0.1 :  (o'=3) & (x'=0); // guard x>=ad,x<=AD\r\n\t[] o=2 & x>4 -> 0.9 : (o'=4) & (x'=0) + 0.1 :  (o'=5) & (x'=0); // guard x>AD\r\n\t[decode] o=2 -> 0.9 : (o'=6) + 0.1 :  (o'=7);\r\n\t[finished] o=3 -> (o'=8) & (x'=0);\r\n\r\n\t[] o=8 -> (o'=8);\r\n\t[] o=9 -> (o'=9);\r\n\t[] o=10 -> (o'=10);\r\n\r\n\t[stop] o=4 -> (o'=9); \r\n\t[error] o=5 -> (o'=10);\r\n\r\n\t[decoded_random] o=6 -> (o'=11);\r\n\t[decoded_last] o=7 -> (o'=12);\r\n\r\n\t[ack] o=11 & (x>=1 & x<=4) -> (o'=1) & (x'=0);  // guard x>=ad,x<=AD\r\n\t[stop] o=11 & x>4 ->  (o'=9) & (x'=0); \r\n\r\n\t[ack] o=12 & (x>=1 & x<=4) -> (o'=3) & (x'=0);  // guard x>=ad,x<=AD\r\n\t[stop] o=12  & x>4 -> (o'=10) & (x'=0); \r\n\r\nendmodule\r\n\r\nmodule recipient\r\n\r\n\tr : [0..9];\r\n\t// 0 - request\r\n\t// 1 - wait\r\n\t// 2 - ack\r\n\t// 3 - done\r\n\t// 4 - decode1\r\n\t// 5 - decode2\r\n\t// 6 - terminate\r\n\t// 7 - decode\r\n\t// 8 - decoded\r\n\t// 9 - random\r\n\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t\t(r=0 => y<=0) &\r\n\t\t(r=1 => true) &\r\n\t\t(r=2 => true) &\r\n\t\t(r=3 => true) &\r\n\t\t(r=4 => y<=1) &\r\n\t\t(r=5 => y<=3) &\r\n\t\t(r=6 => true) &\r\n\t\t(r=7 => y<=0) &\r\n\t\t(r=8 => y<=0) &\r\n\t\t(r=9 => y<=0)\r\n\tendinvariant\r\n\r\n\t[req] r=0 & y=0 -> (r'=1);\r\n\t[message] r=1 -> (r'=2) & (y'=0);\r\n\t[finished] r=1 -> (r'=3);\r\n\r\n\t[ack] r=2 -> (r'=1);\r\n\t[] r=2 -> (r'=4) & (y'=0);\r\n\t[] r=2 -> (r'=5) & (y'=0);\r\n\t[] r=2 -> (r'=6);\r\n\r\n\t[] r=3 -> (r'=3);\r\n\t[] r=6 -> (r'=6);\r\n\r\n\t[] r=4 & y=1 -> 0.01 : (r'=7) & (y'=0) + 0.99 : (r'=2) & (y'=0);\r\n\t[] r=5 & y=3 -> 0.05 : (r'=7) & (y'=0) + 0.95 : (r'=2) & (y'=0);\r\n\r\n\t[decode] r=7 & y=0 -> (r'=8);\r\n\t[decoded_random] r=8 & y=0 -> (r'=9);\r\n\t[decoded_last] r=8 & y=0 -> (r'=6);\r\n\t[ack] r=9 -> (r'=1);\r\n\t[] r=9 -> (r'=6);\r\n\r\nendmodule\r\n\r\nlabel \"gains_information\" = o=10;\r\n\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/simple/auto",
    "content": "#!/bin/csh\n\nprism formats09.nm formats09.pctl -prop 1 -aroptions refine=first\n"
  },
  {
    "path": "prism-examples/ptas/simple/formats09.nm",
    "content": "// PTA used as running example in FORMATS'09 paper\r\n\r\npta\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\tx : clock;\r\n\ty : clock;\r\n\t\r\n\t[] s=0 -> 0.6 : (s'=1) + 0.4 : (s'=2)&(x'=0);\r\n\t[] s=1 & x=0 -> (s'=3);\r\n\t[] s=1 & y>2 -> (s'=1)&(y'=0);\r\n\t[] s=2 & x=0 & y=1 -> (s'=3)&(y'=0);\r\n\t[] s=2 & x>2 -> (s'=1)&(y'=0);\r\n\t[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"target\" = s=3;\r\nlabel \"end\" = s=3 | s=1;\r\n\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/simple/formats09.pctl",
    "content": "Pmax=? [ F \"target\" ]\r\n\r\n// Rmin=? [ F \"end\" ]\r\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/.args",
    "content": "-aroptions refine=all,nopre\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/.models",
    "content": "zeroconf.nm\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/.props",
    "content": "incorrect.pctl\ndeadline.pctl -const T=100\ndeadline.pctl -const T=150\ndeadline.pctl -const T=200\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/auto",
    "content": "#!/bin/csh\n\nprism zeroconf.nm incorrect.pctl -aroptions refine=all,nopre,opt\n\nprism zeroconf.nm deadline.pctl -const T=100 -aroptions refine=all,nopre,opt\nprism zeroconf.nm deadline.pctl -const T=150 -aroptions refine=all,nopre,opt\nprism zeroconf.nm deadline.pctl -const T=200 -aroptions refine=all,nopre,opt\n\n#prism zeroconf.nm time.pctl -aroptions refine=all,nopre,opt\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/deadline.pctl",
    "content": "const int T;\r\n\r\n// Maximum probability of configuring incorrectly (using unfresh address) by time T\r\nPmax=? [ F<=T \"incorrect\" ]\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/eventually.pctl",
    "content": "// Maximum probably use unfresh address\r\nPmax=? [ F \"done\" ]\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/incorrect.pctl",
    "content": "// Maximum probability of configuring incorrectly (using unfresh address)\r\nPmax=? [ F \"incorrect\" ]\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/time.pctl",
    "content": "// Maximum expected time to elect a leader\r\nR{\"time\"}max=? [ F \"done\" ]\r\n\r\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/used.pctl",
    "content": "P=?[ F s=2 & ip=2 ]\r\n"
  },
  {
    "path": "prism-examples/ptas/zeroconf/zeroconf.nm",
    "content": "// prism model of pta version of zeroconf\r\n// using digitial clocks\r\n\r\npta\r\n\r\nmodule sender\r\n\r\n\ts : [0..2]; //local state\r\n\tprobes : [0..4]; // probes sent\r\n\tip : [0..2]; // ip address not chosen, fresh or in use\r\n\tx : clock; // local clock\r\n\r\n\tinvariant\r\n\t(s=0 => x<=0) &\r\n\t(s=1 => x<=20) &\r\n\t(s=2 => true)\r\n\tendinvariant\r\n\r\n\t// selct probe\t\r\n\t// [] s=0 -> 0.99969242125984251969 : (s'=1) & (ip'=0) + 0.00030757874015748031 : (s'=1) & (ip'=1);\r\n\t[] s=0 -> 0.5 : (s'=1) & (ip'=1) + 0.5 : (s'=1) & (ip'=2);\r\n\t// send probes\r\n\t[send_used]  s=1 & x=20 & ip=2 & probes<4 -> (probes'=probes+1) & (x'=0);\t\r\n\t[send_fresh] s=1 & x=20 & ip=1 & probes<4 -> (probes'=probes+1) & (x'=0);\r\n\t[] s=1 & x=20 & probes=4 -> (s'=2) & (x'=0);\r\n\t[recv] s=1 -> (s'=0) & (x'=0) & (ip'=0) & (probes'=0);\r\n\t[] s=2 -> true;\r\n\r\nendmodule\r\n\r\nmodule environment\r\n\t\r\n\te : [0..2]; // ready, send reply\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t(e=0 => true) &\r\n\t(e>=1 => y<=5)\r\n\tendinvariant\r\n\r\n\t[send_fresh] e=0 -> true;\r\n\t[send_used]  e=0 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=1) & (y'=0);\r\n\t[] e=1 & y>=1 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=2) & (y'=0);\r\n\t[recv] e=2 & y>=1 -> (e'=0) & (y'=0);\r\n\r\nendmodule\r\n\r\n\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\nlabel \"incorrect\" = s=2 & ip=2;\r\nlabel \"done\" = s=2;\r\n\r\n"
  },
  {
    "path": "prism-examples/simple/dice/README.txt",
    "content": "This case study is based on probabilistic algorithms due to Knuth [KY76] which model 6-sided dice using fair coins.\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/dice.php\r\n\r\n=====================================================================================\r\n\r\n[KY76]\r\nD. E. Knuth and A. C. Yao\r\nThe complexity of nonuniform random number generation\r\nIn J. F. Traub, editor, Algorithms and Complexity: New Directions and Recent Results, Academic Press, New York, 1976\r\n"
  },
  {
    "path": "prism-examples/simple/dice/auto",
    "content": "#!/bin/csh\n\nprism dice.pm dice.pctl -const x=3 \n\nprism two_dice.nm two_dice.pctl -prop 1 -const x=2:12\nprism two_dice.nm two_dice.pctl -prop 2 -const x=2:12\nprism two_dice.nm two_dice.pctl -prop 3 -const x=0 -m\nprism two_dice.nm two_dice.pctl -prop 4 -const x=0 -m\n\nprism two_dice_knuth.pm two_dice_knuth.pctl -prop 1 -const x=2:12\nprism two_dice_knuth.pm two_dice_knuth.pctl -prop 2 -const x=0\n"
  },
  {
    "path": "prism-examples/simple/dice/dice.pctl",
    "content": "const int x;\n\n// Is probability of throwing x > 0.1?\nP>0.1 [ F s=7 & d=x ]\n\n// Probability of throwing 6?\nP=? [ F s=7 & d=6 ]\n\n// Probability of throwing x?\nP=? [ F s=7 & d=x ]\n\n// Expected number of coin flips to complete?\nR=? [ F s=7 ]\n"
  },
  {
    "path": "prism-examples/simple/dice/dice.pm",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/simple/dice/two_dice.nm",
    "content": "mdp\r\n\r\nmodule die1\r\n\r\n\t// local state\r\n\ts1 : [0..7] init 0;\r\n\t// value of the die\r\n\td1 : [0..6] init 0;\r\n\t\r\n\t[] s1=0 -> 0.5 : (s1'=1) + 0.5 : (s1'=2);\r\n\t[] s1=1 -> 0.5 : (s1'=3) + 0.5 : (s1'=4);\r\n\t[] s1=2 -> 0.5 : (s1'=5) + 0.5 : (s1'=6);\r\n\t[] s1=3 -> 0.5 : (s1'=1) + 0.5 : (s1'=7) & (d1'=1);\r\n\t[] s1=4 -> 0.5 : (s1'=7) & (d1'=2) + 0.5 : (s1'=7) & (d1'=3);\r\n\t[] s1=5 -> 0.5 : (s1'=7) & (d1'=4) + 0.5 : (s1'=7) & (d1'=5);\r\n\t[] s1=6 -> 0.5 : (s1'=2) + 0.5 : (s1'=7) & (d1'=6);\r\n\t[] s1=7 & s2=7 -> (s1'=7);\r\n\t\r\nendmodule\r\n\r\nmodule die2 = die1 [ s1=s2, s2=s1, d1=d2 ] endmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] !(s1=7 & s2=7) : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/simple/dice/two_dice.pctl",
    "content": "const int x;\r\n\r\n// probability of throwing x\r\nPmin=? [ F s1=7 & s2=7 & d1+d2=x ]\r\nPmax=? [ F s1=7 & s2=7 & d1+d2=x ]\r\n\r\n// min/max expected cost to complete\r\nRmin=? [ F s1=7 & s2=7 ]\r\nRmax=? [ F s1=7 & s2=7 ]\r\n"
  },
  {
    "path": "prism-examples/simple/dice/two_dice_knuth.pctl",
    "content": "const int x;\r\n\r\n// probability of throwing x\r\nP=? [ F s=34 & d=x ]\r\n\r\n// expected coin flips\r\nR=? [ F s=34 ]\r\n"
  },
  {
    "path": "prism-examples/simple/dice/two_dice_knuth.pm",
    "content": "// optimal program for the sum of two dice\r\n\r\ndtmc\r\n\r\nmodule sum_of_two_dice\r\n\t\r\n\t// local state\r\n\ts : [0..34] init 0;\r\n\t// total of two dice\r\n\td : [0..12] init 0;\r\n\t\r\n\t[] s=0  -> 0.5 : (s'=1)  + 0.5 : (s'=2);\r\n\t[] s=1  -> 0.5 : (s'=3)  + 0.5 : (s'=4);\r\n\t[] s=2  -> 0.5 : (s'=5)  + 0.5 : (s'=6);\r\n\t[] s=3  -> 0.5 : (s'=7)  + 0.5 : (s'=34) & (d'=6);\r\n\t[] s=4  -> 0.5 : (s'=8)  + 0.5 : (s'=34) & (d'=7);\r\n\t[] s=5  -> 0.5 : (s'=9)  + 0.5 : (s'=34) & (d'=8);\r\n\t[] s=6  -> 0.5 : (s'=10) + 0.5 : (s'=11);\r\n\t[] s=7  -> 0.5 : (s'=12) + 0.5 : (s'=34) & (d'=4);\r\n\t[] s=8  -> 0.5 : (s'=13) + 0.5 : (s'=34) & (d'=5);\r\n\t[] s=9  -> 0.5 : (s'=14) + 0.5 : (s'=34) & (d'=9);\r\n\t[] s=10 -> 0.5 : (s'=15) + 0.5 : (s'=34) & (d'=10);\r\n\t[] s=11 -> 0.5 : (s'=16) + 0.5 : (s'=17);\r\n\t[] s=12 -> 0.5 : (s'=18) + 0.5 : (s'=34) & (d'=3);\r\n\t[] s=13 -> 0.5 : (s'=19) + 0.5 : (s'=34) & (d'=5);\r\n\t[] s=14 -> 0.5 : (s'=20) + 0.5 : (s'=34) & (d'=7);\r\n\t[] s=15 -> 0.5 : (s'=21) + 0.5 : (s'=34) & (d'=9);\r\n\t[] s=16 -> 0.5 : (s'=22) + 0.5 : (s'=34) & (d'=11);\r\n\t[] s=17 -> 0.5 : (s'=23) + 0.5 : (s'=24);\r\n\t[] s=18 -> 0.5 : (s'=25) + 0.5 : (s'=34) & (d'=2);\r\n\t[] s=19 -> 0.5 : (s'=26) + 0.5 : (s'=34) & (d'=3);\r\n\t[] s=20 -> 0.5 : (s'=27) + 0.5 : (s'=34) & (d'=4);\r\n\t[] s=21 -> 0.5 : (s'=34) & (d'=5) + 0.5 : (s'=34) & (d'=9);\r\n\t[] s=22 -> 0.5 : (s'=28) + 0.5 : (s'=34) & (d'=10);\r\n\t[] s=23 -> 0.5 : (s'=29) + 0.5 : (s'=34) & (d'=11);\r\n\t[] s=24 -> 0.5 : (s'=30) + 0.5 : (s'=34) & (d'=12);\r\n\t[] s=25 -> 0.5 : (s'=1)  + 0.5 : (s'=34) & (d'=2);\r\n\t[] s=26 -> 0.5 : (s'=31) + 0.5 : (s'=34) & (d'=3);\r\n\t[] s=27 -> 0.5 : (s'=32) + 0.5 : (s'=34) & (d'=6);\r\n\t[] s=28 -> 0.5 : (s'=34) & (d'=7) + 0.5 : (s'=34) & (d'=8);\r\n\t[] s=29 -> 0.5 : (s'=33) + 0.5 : (s'=34) & (d'=11);\r\n\t[] s=30 -> 0.5 : (s'=2)  + 0.5 : (s'=34) & (d'=12);\r\n\t[] s=31 -> 0.5 : (s'=34) & (d'=2) + 0.5 : (s'=34) & (d'=4);\r\n\t[] s=32 -> 0.5 : (s'=34) & (d'=6) + 0.5 : (s'=34) & (d'=8);\r\n\t[] s=33 -> 0.5 : (s'=34) & (d'=10) + 0.5 : (s'=34) & (d'=12);\r\n\t[] s=34 -> (s'=34);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<34 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/simple/molecules/README.txt",
    "content": "This case study models several simple molecular reactions:\r\n\r\n * Na + Cl <-> Na+ + Cl-\r\n * K + Na + 2Cl <-> K+ + Na- + 2Cl-\r\n * Mg + 2Cl <-> Mg+2 + 2Cl-\r\n \r\nThese are taken from Ehud Shapiro's lecture notes on Biomolecular Processes as Concurrent Computation [Sha].\r\n\r\nFor more information, see: http://www.prismmodelchecker.org/casestudies/molecules.php\r\n\r\n=====================================================================================\r\n\r\n[Sha]\r\n\"Biomolecular Processes as Concurrent Computation\" course material\r\nhttp://www.wisdom.weizmann.ac.il/~biopsi/bpcc2001/\r\n"
  },
  {
    "path": "prism-examples/simple/molecules/auto",
    "content": "#!/bin/csh\n\nprism nacl.sm nacl.csl -prop 1 -const N1=10,N2=10,T=0:0.001:0.006,i=4\nprism nacl.sm nacl.csl -prop 2 -const N1=10,N2=10,T=0:0.001:0.006,i=0\nprism nacl.sm nacl.csl -prop 3 -const N1=10,N2=10,T=0,i=0 -gs\n\nprism knacl.sm knacl.csl -prop 1 -const N1=10,N2=10,N3=10,T=0:0.001:0.006,i=4,\nprism knacl.sm knacl.csl -prop 2 -const N1=10,N2=10,N3=10,T=0:0.001:0.006,i=4,\nprism knacl.sm knacl.csl -prop 3 -const N1=10,N2=10,N3=10,T=0:0.001:0.006,i=0,\nprism knacl.sm knacl.csl -prop 4 -const N1=10,N2=10,N3=10,T=0:0.001:0.006,i=0,\nprism knacl.sm knacl.csl -prop 5 -const N1=10,N2=10,N3=10,T=0,i=0 -gs\nprism knacl.sm knacl.csl -prop 6 -const N1=10,N2=10,N3=10,T=0,i=0 -gs\n\nprism mc.sm mc.csl -prop 1 -const N1=10,N2=10,T=0:0.001:0.006,i=4\nprism mc.sm mc.csl -prop 2 -const N1=10,N2=10,T=0:0.001:0.006,i=4\nprism mc.sm mc.csl -prop 3 -const N1=10,N2=10,T=0:0.001:0.006,i=4\nprism mc.sm mc.csl -prop 4 -const N1=10,N2=10,T=0:0.001:0.006,i=0\nprism mc.sm mc.csl -prop 5 -const N1=10,N2=10,T=0:0.001:0.006,i=0\nprism mc.sm mc.csl -prop 6 -const N1=10,N2=10,T=0:0.001:0.006,i=0\nprism mc.sm mc.csl -prop 7 -const N1=10,N2=10,T=0,i=0 -gs\nprism mc.sm mc.csl -prop 8 -const N1=10,N2=10,T=0,i=0 -gs\nprism mc.sm mc.csl -prop 9 -const N1=10,N2=10,T=0,i=0 -gs\n\n"
  },
  {
    "path": "prism-examples/simple/molecules/knacl.csl",
    "content": "// Constants:\r\nconst double T; // time instant\r\nconst int i; // number of molecules\r\n\r\n// Probability of there being i Na/K molecules at time T?\r\nP=? [ true U[T,T] na=i ]\r\nP=? [ true U[T,T] k=i ]\r\n\r\n// Expected percentage of Na/K molecules at time T?\r\nR{\"percentage_na\"}=? [ I=T ]\r\nR{\"percentage_k\"}=? [ I=T ]\r\n\r\n// Expected long-run percentage of Na/K molecules?\r\nR{\"percentage_na\"}=? [ S ]\r\nR{\"percentage_k\"}=? [ S ]\r\n"
  },
  {
    "path": "prism-examples/simple/molecules/knacl.sm",
    "content": "// K + Na + 2Cl <--> K+ + Na+ + 2Cl- \r\n// dxp/gxn 04/10/04\r\n\r\n// ctmc model\r\nctmc\r\n\r\n// constants\r\nconst int N1; // number of Na molecules\r\nconst int N2; // number of Cl molecules\r\nconst int N3; // number of K molecules\r\n\r\n// Na and Na+ module\r\nmodule na\r\n\t\r\n\tna : [0..N1] init N1;\r\n\t// total number of Na and Na+ molecules is fixed at N1\r\n\t// na is the number of Na molecules \r\n\t// therefore N1-na gives the number of Na+ molecules\r\n\t\r\n\t[e1] na>0  ->     na  : (na'=na-1);\r\n\t[e2] na<N1 -> (N1-na) : (na'=na+1);\r\n\t\r\nendmodule\r\n\r\n// Cl and Cl- module\r\nmodule cl\r\n\t\r\n\tcl : [0..N2] init N2;\r\n\t// total number of Cl and Cl- molecules is fixed at N2\r\n\t// cl is the number of Cl molecules \r\n\t// therefore N2-cl is the number of Cl- molecules\r\n\t\r\n\t// reactions with Cl\r\n\t[e1] cl>0  ->     cl  : (cl'=cl-1);\r\n\t[e3] cl>0  ->     cl  : (cl'=cl-1);\r\n\t// reactions with CL-\r\n\t[e2] cl<N2 -> (N2-cl) : (cl'=cl+1);\r\n\t[e4] cl<N2 -> (N2-cl) : (cl'=cl+1);\r\n\t\r\nendmodule\r\n\r\n// K and K+ module\r\nmodule k\r\n\t\r\n\tk : [0..N3] init N3;\r\n\t// total number of K and K+ molecules is fixed at N3\r\n\t// k is the number of K molecules \r\n\t// therefore N3-k gives the number of K+ molecules\r\n\t\r\n\t[e3] k>0  ->     k  : (k'=k-1);\r\n\t[e4] k<N3 -> (N3-k) : (k'=k+1);\r\n\t\r\nendmodule\r\n\r\n// base rates\r\nconst double e1rate = 100; // Na + Cl  -> Na+ + Cl-\r\nconst double e2rate = 10;  // Na+ + Cl- -> Na + Cl\r\nconst double e3rate = 30;  // K + Cl  -> K+ + Cl-\r\nconst double e4rate = 20;  // K+ + Cl- -> K + Cl\r\n\r\n// module representing the base rates of reactions\r\nmodule base_rates\r\n\t\r\n\tdummy : bool; // dummy variable\r\n\t\r\n\t[e1] true -> e1rate : true;\r\n\t[e2] true -> e2rate : true;\r\n\t[e3] true -> e3rate : true;\r\n\t[e4] true -> e4rate : true;\r\n\t\r\nendmodule\r\n\r\n// reward structure (percentage of Na)\r\nrewards \"percentage_na\"\r\n\ttrue : 100*na/N1;\t\r\nendrewards\r\n\n// reward structure (percentage of K)\r\nrewards \"percentage_k\"\r\n\ttrue : 100*k/N3;\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/simple/molecules/mc.csl",
    "content": "// Constants:\r\nconst double T; // time instant\r\nconst int i; // number of molecules\r\n\r\n// Probability of there being i Mg/Mg+/Mg+2 molecules at time T?\r\nP=? [ true U[T,T] mg=i ]\r\nP=? [ true U[T,T] mg_p=i ]\r\nP=? [ true U[T,T] N1-(mg_p+mg)=i ]\r\n\r\n// Expected percentage of Mg/Mg+/Mg+2 molecules at time T?\r\nR{\"percentage_mg\"}=? [ I=T ]\r\nR{\"percentage_mgplus\"}=? [ I=T ]\r\nR{\"percentage_mgplus2\"}=? [ I=T ]\r\n\r\n// Expected long-run percentage of Mg/Mg+/Mg+2 molecules?\r\nR{\"percentage_mg\"}=? [ S ]\r\nR{\"percentage_mgplus\"}=? [ S ]\r\nR{\"percentage_mgplus2\"}=? [ S ]\r\n"
  },
  {
    "path": "prism-examples/simple/molecules/mc.sm",
    "content": "// Mg + 2Cl <--> Mg+2 + 2Cl-\r\n// dxp/gxn 04/10/04\r\n\r\n// ctmc model\r\nctmc\r\n\r\n// constants\r\nconst int N1; // number of Mg molecules\r\nconst int N2; // number of Cl molecules\r\n\r\n\r\n// Cl and Cl- module\r\nmodule cl\r\n\t\r\n\tcl : [0..N2] init N2;\r\n\t// total number of Cl and Cl- molecules is fixed at N2\r\n\t// cl is the number of Cl molecules \r\n\t// therefore N2-cl is the number of Cl- molecules\r\n\t\r\n\t// reactions with Cl\r\n\t[e1] cl>0  ->     cl  : (cl'=cl-1);\r\n\t[e2] cl>0  ->     cl  : (cl'=cl-1);\r\n\t// reactions with CL-\r\n\t[e3] cl<N2 -> (N2-cl) : (cl'=cl+1);\r\n\t[e4] cl<N2 -> (N2-cl) : (cl'=cl+1);\r\n\t\r\nendmodule\r\n\r\n// Mg, Mg+ and Mg+2 module\r\nmodule mg\r\n\t\r\n\tmg   : [0..N1] init N1;\r\n\tmg_p : [0..N1] init 0;\r\n\t// total number of Mg and Mg+ and Mg+2 molecules is fixed at N1\r\n\t// mg is the number of Mg molecules \r\n\t// mg_p is the number of Mg molecules \r\n\t// therefore N1-(mg+mg+) gives the number of Mg+2 molecules\r\n\t\r\n\t[e1] mg>0 & mg_p<N1 -> mg   : (mg'=mg-1) & (mg_p'=mg_p+1);\r\n\t[e2] mg_p>0         -> mg_p : (mg_p'=mg_p-1);\r\n\t[e3] mg_p>0 & mg<N1 -> mg_p : (mg'=mg+1) & (mg_p'=mg_p-1);\r\n\t[e4] mg_p+mg<N1     -> N1-(mg_p+mg) : (mg_p'=mg_p+1);\r\n\t\r\nendmodule\r\n\r\n\r\n// base rates\r\nconst double e1rate = 10;  // Mg   + Cl  --> Mg+ + Cl-\r\nconst double e2rate = 100; // Mg+  + Cl  --> Mg+2 + Cl-\r\nconst double e3rate = 50;  // Mg+  + Cl- --> Mg + Cl\r\nconst double e4rate = 5;   // Mg+2 + Cl- --> Mg+ + Cl-\r\n\r\n// module representing the base rates of reactions\r\nmodule base_rates\r\n\t\r\n\tdummy : bool; // dummy variable\r\n\t\r\n\t[e1] true -> e1rate : true;\r\n\t[e2] true -> e2rate : true;\r\n\t[e3] true -> e3rate : true;\r\n\t[e4] true -> e4rate : true;\r\n\t\r\nendmodule\r\n\r\n// reward structur: percentage of Mg molecules\r\nrewards \"percentage_mg\"\n\ttrue : 100*mg/N1;\r\nendrewards\n\r\n// reward structur: percentage of Mg+ molecules\r\nrewards \"percentage_mgplus\"\n\ttrue : 100*mg_p/N1;\r\nendrewards\r\n\n// reward structur: percentage of Mg+2 molecules\r\nrewards \"percentage_mgplus2\"\n\ttrue : max(100*(N1-(mg_p+mg))/N1,0);\r\nendrewards\r\n"
  },
  {
    "path": "prism-examples/simple/molecules/nacl.csl",
    "content": "// Constants:\r\nconst double T; // time instant\r\nconst int i; // number of molecules\r\n\r\n// Probability of there being i Na molecules at time T?\r\nP=? [ true U[T,T] na=i ]\r\n\r\n// Expected percentage of Na molecules at time T?\r\nR=? [ I=T ]\r\n\r\n// Expected long-run percentage of Na molecules?\r\nR=? [ S ]\r\n"
  },
  {
    "path": "prism-examples/simple/molecules/nacl.sm",
    "content": "// Na + Cl <--> Na+ + Cl- \r\n// dxp/gxn 09/06/04\r\n\r\n// ctmc model\r\nctmc\r\n\r\n// constants\r\nconst int N1; // number of Na molecules\r\nconst int N2; // number of Cl molecules\r\n\r\n// Na and Na+ module\r\nmodule na\r\n\t\r\n\tna : [0..N1] init N1;\r\n\t// total number of Na and Na+ molecules is fixed at N1\r\n\t// na is the number of Na molecules \r\n\t// therefore N1-na gives the number of Na+ molecules\r\n\t\r\n\t[e1] na>0  ->     na  : (na'=na-1);\r\n\t[e2] na<N1 -> (N1-na) : (na'=na+1);\r\n\t\r\nendmodule\r\n\r\n// Cl and Cl- module\r\nmodule cl\r\n\t\r\n\tcl : [0..N2] init N2;\r\n\t// total number of Cl and Cl- molecules is fixed at N2\r\n\t// cl is the number of Cl molecules \r\n\t// therefore N2-cl is the number of Cl- molecules\r\n\t\r\n\t[e1] cl>0  ->     cl  : (cl'=cl-1);\r\n\t[e2] cl<N2 -> (N2-cl) : (cl'=cl+1);\r\n\t\r\nendmodule\r\n\r\n// base rates\r\nconst double e1rate = 100; // Na + Cl -> Na+ + Cl-\r\nconst double e2rate = 10; // Na+ + Cl- -> Na + Cl\r\n\r\n// module representing the base rates of reactions\r\nmodule base_rates\r\n\t\r\n\t[e1] true -> e1rate : true;\r\n\t[e2] true -> e2rate : true;\r\n\t\r\nendmodule\r\n\r\n// rewards: \"percentage of Na molecules present (out of all Na/Na+ molecules)\"\r\nrewards \"percentage_na\"\r\n\ttrue : 100*na/N1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/README.md",
    "content": "# PRISM Regression Tests\r\n\r\nThis is the PRISM Regression Test Suite, a collection of probabilistic model checking\r\ntasks that PRISM can perform, along with their expected result/output.\r\n\r\nMost tests take the form of a PRISM model file (e.g. test.nm),\r\nusually with an accompanying property file with a matching name (e.g. test.nm.props).\r\nCommand-line switches that need to be passed to PRISM to run the test\r\ncan be included in a separate .args file, again with matching name (e.g. test.nm.props.args).\r\n\r\nThe tests are executed by running PRISM in test mode 'prism -test'.\r\nThis looks for a comment of the form '// RESULT: xxx' preceding each property\r\nand then checks agains the expected result (xxx) after model checking.\r\nSee e.g. the files example.nm and example.nm.props in this directory.\r\n\r\nUse the prism-test script (in etc/scripts/) to automate test execution.\r\n(In fact, this works via the prism-auto script, also in etc/scripts.)\r\nYou can give prism-test either a specific property file (test.nm.props)\r\nor a model file (test.nm), which runs all tests for that model.\r\nAlternatively, pass prism-test a directory, which is searched recursively for tests.\r\nFor example:\r\n\r\n* prism-test pmc/lec12mdp.nm.props\r\n* prism-test pmc/lec12mdp.nm\r\n* prism-test pmc\r\n\r\nCurrent test sets are:\r\n\r\n* functionality/ : currently partial coverage of PRISM's functionality\r\n* bugfixes/ : examples based on previously fixed bugs\r\n* papers/ : tutorial/toy examples from papers\r\n* pmc/ : examples from Probabilistic Model Checking lecture course\r\n* contrib/ : test contributed by others\r\n\r\nSee here for more details:\r\n\r\n* https://github.com/prismmodelchecker/prism/wiki/Regression-Testing\r\n"
  },
  {
    "path": "prism-tests/all-engines.args",
    "content": "-explicit\n-explicit -ii -maxiters 100000\n-explicit -ii -topological -maxiters 100000\n-mtbdd\n-mtbdd -ii -maxiters 100000 -cuddepsilon 1E-20\n-hybrid\n-hybrid -ii -maxiters 100000\n-sparse\n-sparse -ii -maxiters 100000\n-exact\n"
  },
  {
    "path": "prism-tests/bugfixes/advgenexplicit.nm",
    "content": "// Bug fixed in trunk rev 3629\n// Explicit engine fails for strat gen on Pmin=? [ F s=1 ]\n\nmdp\n\nmodule M1\n\n\ts : [0..2];\n\n\t[a] s=0 -> 0.5:(s'=1) + 0.5:(s'=2);\n\t[b] s=0 -> 1:(s'=2); // this is optimal\n\n\t[c] s>0 -> true;\n\nendmodule\n\n"
  },
  {
    "path": "prism-tests/bugfixes/advgenexplicit.nm.props",
    "content": "// RESULT: 0\nPmin=? [ F s=1 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/advgenexplicit.nm.props.adv.tra",
    "content": "3 3\n0 2 1 b\n1 1 1 c\n2 2 1 c\n"
  },
  {
    "path": "prism-tests/bugfixes/advgenexplicit.nm.props.args",
    "content": "-exportstrat advgenexplicit.nm.props.adv.tra -ex\n-exportstrat advgenexplicit.nm.props.adv.tra -nopre -ex\n"
  },
  {
    "path": "prism-tests/bugfixes/advgenexplicit2.nm",
    "content": "// Bug fixed in trunk rev 3691\r\n// Explicit engine fails for strat gen on Pmin=? [ F s=3 ]\r\n\r\nmdp\r\n\r\nmodule M1\r\n\r\n\ts : [0..3];\r\n\r\n\t[a] s=0 -> 0.5:(s'=1) + 0.5:(s'=2);\r\n\t[b] s=0 -> 1:(s'=2); // this is optimal in s=0\r\n\t[c] s=1 -> (s'=3);\r\n\t\r\n\t[d] s>1 -> true;\r\n\r\nendmodule\r\n\r\n// Pmin=? [ F s=3 ]\r\n"
  },
  {
    "path": "prism-tests/bugfixes/advgenexplicit2.nm.props",
    "content": "// RESULT: 0\nPmin=? [ F s=3 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/advgenexplicit2.nm.props.adv.tra",
    "content": "4 4\n0 2 1 b\n1 3 1 c\n2 2 1 d\n3 3 1 d\n"
  },
  {
    "path": "prism-tests/bugfixes/advgenexplicit2.nm.props.args",
    "content": "-exportstrat advgenexplicit2.nm.props.adv.tra -ex\n-exportstrat advgenexplicit2.nm.props.adv.tra -nopre -ex\n"
  },
  {
    "path": "prism-tests/bugfixes/boolean-constant-issue-232.prism",
    "content": "// A simple model that depends on an undefined boolean constant\nmdp\n\nconst bool flag;\n\nmodule Boolean\n  b : bool init flag;\nendmodule"
  },
  {
    "path": "prism-tests/bugfixes/boolean-constant-issue-232.prism.args",
    "content": "-const flag=false -exportresults boolean-constant-issue-232.prism.dataframe.csv:dataframe"
  },
  {
    "path": "prism-tests/bugfixes/boolean-constant-issue-232.prism.dataframe.csv",
    "content": "Property,Result\nProperty_1,false\n"
  },
  {
    "path": "prism-tests/bugfixes/boolean-constant-issue-232.prism.props",
    "content": "// A simple property to trigger model checking\n// RESULT (flag=true): true\n// RESULT (flag=false): false\nb"
  },
  {
    "path": "prism-tests/bugfixes/constantsandspeciallabels.pm",
    "content": "// Constant/label bug fixed in trunk rev 4085\r\n\r\ndtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t//[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/constantsandspeciallabels.pm.props",
    "content": "const int x;\r\n\r\n// RESULT (x=3): 1/6\r\nP=? [ F \"deadlock\" & d=x ];\r\n"
  },
  {
    "path": "prism-tests/bugfixes/constantsandspeciallabels.pm.props.args",
    "content": "-fixdl -const x=3\n"
  },
  {
    "path": "prism-tests/bugfixes/constantsinpropfiles.pm",
    "content": "// Constant bug fixed in trunk rev 4460\r\n\r\ndtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/constantsinpropfiles.pm.props",
    "content": "const int x;\r\nconst int y = x;\r\nconst int z = y;\r\n\r\n// RESULT (x=3): 1/6\r\nP=? [ F d=z ];\r\n"
  },
  {
    "path": "prism-tests/bugfixes/constantsinpropfiles.pm.props.args",
    "content": "-const x=3\n"
  },
  {
    "path": "prism-tests/bugfixes/cosafe+nested.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\ts<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/cosafe+nested.prism.props",
    "content": "// RESULT: 1\nR=?[ X F R>0[C<=1] ]\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-1.sm",
    "content": "// test case for fast adaptive uniformisation bug (ignoring transitions)\n\nctmc\n\nmodule m1\n  s: [0..2] init 0;\n\n  [] s=0 -> 1:(s'=1) + 2:(s'=2);\n  [] s>0 -> 1:true;\nendmodule\n\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-1.sm.props",
    "content": "const double T;\n\n// RESULT (T=1): 0.3167376343237416\n// RESULT (T=2): 0.332507070725914\n// RESULT (T=3): 0.33329218265878835\n// RESULT (T=4): 0.3333312759432579\n// RESULT (T=5): 0.33333321817286715\nP=? [ F=T s=1 ];\n\n// RESULT (T=1): 0.6334752686474832\n// RESULT (T=2): 0.665014141451828\n// RESULT (T=3): 0.6665843653175767\n// RESULT (T=4): 0.6666625518865158\n// RESULT (T=5): 0.6666664363457\nP=? [ F=T s=2 ];\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-1.sm.props.args",
    "content": "-const T=1:1:5 -transientmethod unif\n-const T=1:1:5 -transientmethod fau\n\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-2.sm",
    "content": "// test correct handling of multiple enabled commands in CTMC when using fast adaptive uniformisation\n\nctmc\n\nmodule m1\n  s: [0..4] init 0;\n\n  [a] s=0 -> 1:(s'=1) + 2:(s'=2);\n  [b] s=0 -> 3:(s'=3) + 4:(s'=4);\n  [] s>0 -> 1:true;\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-2.sm.props",
    "content": "const double T;\n\n// RESULT (T=0.2): 0.08646646794\n// RESULT (T=0.4): 0.09816843470\n// RESULT (T=0.6): 0.09975212121\n// RESULT (T=0.8): 0.09996644936\n// RESULT (T=1.0): 0.09999545617\nP=? [ F=T s=1 ];\n\n// RESULT (T=0.2): 0.1729329358997\n// RESULT (T=0.4): 0.1963368694095\n// RESULT (T=0.6): 0.1995042424355\n// RESULT (T=0.8): 0.1999328987210\n// RESULT (T=1.0): 0.1999909123404\nP=? [ F=T s=2 ];\n\n\n// RESULT (T=0.2): 0.2593994038496\n// RESULT (T=0.4): 0.2945053041143\n// RESULT (T=0.6): 0.2992563636533\n// RESULT (T=0.8): 0.2998993480815\n// RESULT (T=1.0): 0.2999863685106\nP=? [ F=T s=3 ];\n\n\n// RESULT (T=0.2): 0.3458658717995\n// RESULT (T=0.4): 0.3926737388191\n// RESULT (T=0.6): 0.3990084848710\n// RESULT (T=0.8): 0.3998657974421\n// RESULT (T=1.0): 0.3999818246808\nP=? [ F=T s=4 ];\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-2.sm.props.args",
    "content": "-const T=0.2:0.2:1 -transientmethod unif\n-const T=0.2:0.2:1 -transientmethod fau\n\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-npe.sm",
    "content": "// test for null-pointer exception fix in fast adaptive uniformisation (cumulative reward operator)\n\nctmc\n\nmodule m1\n  s: [0..1] init 0;\n\n  [] s=0 -> 2:(s'=1);\nendmodule\n\nrewards \"steps\"\n  [] true : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-npe.sm.props",
    "content": "const double T;\n\n// RESULT (T=1): 0.8646645498740888\n// RESULT (T=2): 0.9816832980524708\n// RESULT (T=3): 0.9975207981483099\n// RESULT (T=4): 0.9996641287431798\n// RESULT (T=5): 0.9999538916843567\nR=? [ C<=T ];\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-fau-npe.sm.props.args",
    "content": "-const T=1:1:5 -transientmethod unif\n-const T=1:1:5 -transientmethod fau\n\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-until.sm",
    "content": "// Bug fix (CTMC until in the explicit engine)\r\n// Fixed in svn rev 9699\r\n// This is just the standard \"embedded\" benchmark model.\r\n\r\nctmc\r\n\r\n// constants\r\nconst int MAX_COUNT;\r\nconst int MIN_SENSORS = 2;\r\nconst int MIN_ACTUATORS = 1;\r\n\r\n// rates\r\nconst double lambda_p = 1/(365*24*60*60); // 1 year\r\nconst double lambda_s = 1/(30*24*60*60); // 1 month\r\nconst double lambda_a = 1/(2*30*24*60*60); // 2 months\r\nconst double tau = 1/60; // 1 min\r\nconst double delta_f = 1/(24*60*60); // 1 day\r\nconst double delta_r = 1/30; // 30 secs\r\n\r\n// sensors\r\nmodule sensors\r\n\t\r\n\ts : [0..3] init 3; // number of sensors working\r\n\t\r\n\t[] s>1 -> s*lambda_s : (s'=s-1); // failure of a single sensor\r\n\t\r\nendmodule\r\n\r\n// input processor\r\n// (takes data from sensors and passes onto main processor)\r\nmodule proci\r\n\t\r\n\ti : [0..2] init 2; // 2=ok, 1=transient fault, 0=failed\r\n\t\r\n\t[] i>0 & s>=MIN_SENSORS -> lambda_p : (i'=0); // failure of processor\r\n\t[] i=2 & s>=MIN_SENSORS -> delta_f : (i'=1); // transient fault\r\n\t[input_reboot] i=1 & s>=MIN_SENSORS -> delta_r : (i'=2); // reboot after transient fault\r\n\t\r\nendmodule\r\n\r\n// actuators\r\nmodule actuators\r\n\t\r\n\ta : [0..2] init 2; // number of actuators working\r\n\t\r\n\t[] a>0 -> a*lambda_a : (a'=a-1); // failure of a single actuator\r\n\t\r\nendmodule\r\n\r\n// output processor\r\n// (receives instructions from main processor and passes onto actuators)\r\nmodule proco = proci [ i=o, s=a, input_reboot=output_reboot, MIN_SENSORS=MIN_ACTUATORS ] endmodule\r\n\r\n// main processor\r\n// (takes data from proci, processes it, and passes instructions to proco)\r\nmodule procm\r\n\t\r\n\tm : [0..1] init 1; // 1=ok, 0=failed\r\n\tcount : [0..MAX_COUNT+1] init 0; // number of consecutive skipped cycles\r\n\t\r\n\t// failure of processor\r\n\t[] m=1 -> lambda_p : (m'=0);\r\n\t// processing completed before timer expires - reset skipped cycle counter\r\n\t[timeout]  comp -> tau : (count'=0);\r\n\t// processing not completed before timer expires - increment skipped cycle counter\r\n\t[timeout] !comp -> tau : (count'=min(count+1, MAX_COUNT+1));\r\n\t\r\nendmodule\r\n\r\n// connecting bus\r\nmodule bus\r\n\t\r\n\t// flags\r\n\t// main processor has processed data from input processor\r\n\t// and sent corresponding instructions to output processor (since last timeout)\r\n\tcomp : bool init true; \r\n\t// input processor has data ready to send\r\n\treqi : bool init true; \r\n\t// output processor has instructions ready to be processed\r\n\treqo : bool init false;\r\n\t\r\n\t// input processor reboots\r\n\t[input_reboot]  true -> 1 :\r\n\t// performs a computation if has already done so or\r\n\t// it is up and ouput clear (i.e. nothing waiting)\r\n\t(comp'=(comp | (m=1 & !reqo))) \r\n\t// up therefore something to process\r\n\t& (reqi'=true)\r\n\t// something to process if not functioning and either\r\n\t// there is something already pending\r\n\t// or the main processor sends a request\r\n\t& (reqo'=!(o=2 & a>=1) & (reqo | m=1));\r\n\t\r\n\t// output processor reboots\r\n\t[output_reboot] true -> 1 :\r\n\t// performs a computation if it has already or\r\n\t// something waiting and is up\r\n\t// (can be processes as the output has come up and cleared pending requests)\r\n\t(comp'=(comp | (reqi & m=1)))\r\n\t// something to process it they are up or\r\n\t// there was already something and the main processor acts\r\n\t// (output now up must be due to main processor being down)\r\n\t& (reqi'=(i=2 & s>=2) | (reqi & m=0))\r\n\t// output and actuators up therefore nothing can be pending\r\n\t& (reqo'=false);\r\n\t\r\n\t// main processor times out\r\n\t[timeout] true -> 1 :\r\n\t// performs a computation if it is up something was pending\r\n\t// and nothing is waiting for the output\r\n\t(comp'=(reqi & !reqo & m=1))\r\n\t// something to process if up or\r\n\t// already something and main process cannot act \r\n\t// (down or outputs pending)\r\n\t& (reqi'=(i=2 & s>=2) | (reqi & (reqo | m=0)))\r\n\t// something to process if they are not functioning and \r\n\t// either something is already pending\r\n\t// or the main processor acts\r\n\t& (reqo'=!(o=2 & a>=1) & (reqo | (reqi & m=1)));\r\n\t\r\nendmodule\r\n\r\n\r\n// the system is down\r\nformula down = (i=2&s<MIN_SENSORS)|(count=MAX_COUNT+1)|(o=2&a<MIN_ACTUATORS)|(m=0);\r\n// transient failure has occured but the system is not down\r\nformula danger = !down & (i=1 | o=1);\r\n// the system is operational\r\nformula up = !down & !danger;\r\n\r\n\r\n// reward structures\r\n\r\nrewards \"up\"\r\n\tup : 1/3600;\r\nendrewards\r\n\r\nrewards \"danger\"\r\n\tdanger : 1/3600;\r\nendrewards\r\nrewards \"down\"\r\n\tdown : 1/3600;\r\nendrewards\r\n\r\n//labels\r\n// causes of failues\r\nlabel \"fail_sensors\" = i=2&s<MIN_SENSORS; // sensors have failed\r\nlabel \"fail_actuators\" = o=2&a<MIN_ACTUATORS; // actuators have failed\r\nlabel \"fail_io\" = count=MAX_COUNT+1; // IO has failed\r\nlabel \"fail_main\" = m=0; // ,main processor has failed\r\n\r\n// system status\r\nlabel \"down\" = (i=2&s<MIN_SENSORS)|(count=MAX_COUNT+1)|(o=2&a<MIN_ACTUATORS)|(m=0); // system has shutdown\r\nlabel \"danger\" = !down & (i=1 | o=1); // transient fault has occured\r\nlabel \"up\" = !down & !danger; // system is operational\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-until.sm.props",
    "content": "// RESULT: ~0.6213837\nP=? [ !\"down\" U \"fail_sensors\" ]\n\n// test case for lower bound until problem (explicit engine, fixed in SVN 11768)\n// RESULT: ~0.6213837\nP=? [ !\"down\" U>=0 \"fail_sensors\" ]\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmc-until.sm.props.args",
    "content": "-const MAX_COUNT=2 -e 1e-8 -ex -ex\n-const MAX_COUNT=2 -e 1e-8 -ex -h\n-const MAX_COUNT=2 -e 1e-8 -ex -s\n-const MAX_COUNT=2 -e 1e-8 -ex -m\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmcltlexplicit.sm",
    "content": "// Fixed in trunk svn rev 9356:\r\n// DRA-product and accepting BSCC calculcations on embedded DTMC\r\n\r\n// Fixed in trunk svn rev 11168:\r\n// Nested formulas have to be computed in the original CTMC\r\n\r\nctmc\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\t\r\n\t[arrive] x<3 -> 1.5 : (x'=x+1);\r\n\t[serve] x>0 -> 3 : (x'=x-1);\r\n\r\nendmodule\r\n\r\nlabel \"empty\" = x=0;\r\nlabel \"full\" = x=3;\r\n\r\nrewards \"serve\"\r\n\t[serve] true : 1;\r\nendrewards\r\n\r\nrewards \"queue\"\r\n\ttrue : x;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmcltlexplicit.sm.props",
    "content": "// trigger LTL engine\n\n// RESULT: 1/3\nP=? [ (X \"full\") & true {x=2} ]\n\n\n// checks for nested formulas:\n\n// RESULT: 0.77686982\nP=? [ F<1 x=1 ]\n// RESULT: 0.0794343\nP=? [ F<1 \"full\" ]\n\n// RESULT: 0.0\nP=?[ P>0.8 [ F<1 x=1 ] ]\n\n// RESULT: 1.0\nP=?[ P>0.75 [ F<1 x=1 ] ]\n\n// RESULT: 1.0\nP=?[ P>0.2 [ F<1 x=1 ] ]\n\n// RESULT: 0.0\nP=?[ X P>0.8 [ F<1 \"full\"] ]\n// RESULT: 0.0\nP=?[ (X P>0.8 [ F<1 \"full\"]) & true ]\n\n// RESULT: 1.0\nP=?[ X P>0.05 [ F<1 \"full\" ] ]\n// RESULT: 1.0\nP=?[ (X P>0.05 [ F<1 \"full\" ]) & true ]\n\n// RESULT: 1.0\nP=?[ X P>0.01 [ F<1 \"full\" ] ]\n// RESULT: 1.0\nP=?[ (X P>0.01 [ F<1 \"full\" ]) & true ]\n\n// RESULT: 1.0\nP=?[ P>0[ F<0.5 \"full\" ] ]\n// RESULT: 1.0\nP=?[ (X P>0.05[ F<0.5 \"full\" ]) & true ]\n\n// RESULT: 1/9\nP=?[ X X X (P>=1 [ \"full\"] & P>0.1[ F<2 P>=0.5[ X \"empty\"] ]) ]\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmcltlexplicit.sm.props.args",
    "content": "-ex\n-h\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmcnextexplicit.sm",
    "content": "// Explicit engine CTMC next bug fixed in rev 6173\r\n\r\nctmc\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\t\r\n\t[arrive] x<3 -> 1.5 : (x'=x+1);\r\n\t[serve] x>0 -> 3 : (x'=x-1);\r\n\r\nendmodule\r\n\r\nlabel \"empty\" = x=0;\r\nlabel \"full\" = x=3;\r\n\r\nrewards \"serve\"\r\n\t[serve] true : 1;\r\nendrewards\r\n\r\nrewards \"queue\"\r\n\ttrue : x;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmcnextexplicit.sm.props",
    "content": "// RESULT: 1/3\nP=? [ X \"full\" {x=2} ]\n"
  },
  {
    "path": "prism-tests/bugfixes/ctmcnextexplicit.sm.props.args",
    "content": "-ex\n"
  },
  {
    "path": "prism-tests/bugfixes/deadlock-rewards-issue-29.prism",
    "content": "// test case for github issue #29\n// transitions added for deadlock removal should not get rewards\n\nmdp\n\nmodule M1\n  s: [0..1] init 0;\n\n  // deadlock for state 1\n  [] s=0 -> 1:(s'=1);\nendmodule\n\nrewards \"r\"\n  [] true: 2;\nendrewards\n"
  },
  {
    "path": "prism-tests/bugfixes/deadlock-rewards-issue-29.prism.mc.props",
    "content": "// total reward\n// RESULT: 2.0\nR=?[ C ]\n"
  },
  {
    "path": "prism-tests/bugfixes/deadlock-rewards-issue-29.prism.mc.props.args",
    "content": "# As a CTMC\n-ctmc -ex\n-ctmc -mtbdd\n-ctmc -hybrid\n-ctmc -sparse\n\n# As a DTMC\n-dtmc -ex\n-dtmc -mtbdd\n-dtmc -hybrid\n-dtmc -sparse\n"
  },
  {
    "path": "prism-tests/bugfixes/deadlock-rewards-issue-29.prism.props",
    "content": "// total reward\n// RESULT: 2.0\nRmax=?[ C ]\n\n// RESULT: 2.0\nRmin=?[ C ]\n"
  },
  {
    "path": "prism-tests/bugfixes/deadlock-rewards-issue-29.prism.props.args",
    "content": "-ex\n-mtbdd\n-hybrid\n-sparse\n"
  },
  {
    "path": "prism-tests/bugfixes/dice-pow.pm.unused",
    "content": "// Test model that breaks following undefined-constant changes in rev 3319\r\n// Fixed in rev 4249.\r\n\r\n// Test disabled currently since it *should* throw an error\r\n\r\ndtmc\r\n\r\nconst double some = pow(1);\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/digitalclocksmaxclockzero.nm",
    "content": "// Bug fixed in trunk rev 3520 : GCD computation when max clock constraint is 0\r\n\r\npta\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\tx : clock;\r\n\t\r\n\tinvariant\r\n\t\t  (s=0 => x=0)\r\n\t\t//& (s=3 => x>=1)\r\n\tendinvariant\r\n\t\r\n\t[] s=0 -> (s'=1);\r\n\t[] s=1 & x<=0 -> (s'=3);\r\n\t[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"target\" = s=3;\r\n\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/bugfixes/digitalclocksmaxclockzero.nm.props",
    "content": "// RESULT: 1.0\r\nPmax=? [ F \"target\" ]\r\n"
  },
  {
    "path": "prism-tests/bugfixes/digitalclocksmaxclockzero.nm.props.args",
    "content": "-ptamethod digital\n"
  },
  {
    "path": "prism-tests/bugfixes/dtmc-bounded-explicit.pm",
    "content": "// Silly bug found by Marcus Daum\r\n// Fixed in svn rev 6795\r\n\r\ndtmc\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\t\r\n\t[] x=0 -> (x'=1);\r\n\t[] x=1 -> 0.01 : (x'=1) + 0.01 : (x'=2) + 0.98 : (x'=3);\r\n\t[] x=2 -> (x'=0);\r\n\t[] x=3 -> (x'=3);\r\n\r\nendmodule\r\n\r\nlabel \"try\" = x=1;\r\nlabel \"fail\" = x=2;\r\nlabel \"succ\" = x=3;\r\n\r\nrewards\r\n\tx=1 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/dtmc-bounded-explicit.pm.props",
    "content": "\t// RESULT: 1.0\n\tR=? [ C<=2 ];\n\t\n\t// RESULT: 0.0001\n\tR=? [ I=2 {x=1} ];\n"
  },
  {
    "path": "prism-tests/bugfixes/dtmc-globally.prism",
    "content": "// Checking a bug fix that appeared (in prism-games) when refactoring\r\n// min/max probability computation\r\n\r\ndtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/dtmc-globally.prism.props",
    "content": "// RESULT: 2/3\nP=?[G d<5]\n"
  },
  {
    "path": "prism-tests/bugfixes/dtmc-globally.prism.props.args",
    "content": "-ex\n-m\n"
  },
  {
    "path": "prism-tests/bugfixes/dtmc-normalise-simulator.pm",
    "content": "// Bug fixed in rev 7797:\r\n// simulator was normalising DTMC bu dividing by number of choices\r\n// (which was inconsistent with symbolic construction when using -noprobchecks)\r\n\r\n// Discrete-time Markov chain model\r\ndtmc\r\n\r\n// Number of fitness levels: n\r\nconst int n = 3;\r\n\r\n// Total number of agents/particles: k\r\nconst int k = 3;\r\n\r\nmodule tournament\r\n\r\n\t// Counters: ci = number of agents/particles with fitness i\r\n\tc1 : [0..k] init 1;\r\n\tc2 : [0..k] init 1;\r\n\tc3 : [0..k] init 1;\r\n\t\r\n\t// Possible reactions between agents/particles\r\n\t// Each possible pairwise collision\r\n\t[r12] c1>0 & c2>0 & c2<k -> 2*c1*c2: (c1'=c1-1) & (c2'=c2+1);\r\n\t[r13] c1>0 & c3>0 & c3<k -> 2*c1*c3: (c1'=c1-1) & (c3'=c3+1);\r\n\t[r23] c2>0 & c3>0 & c3<k -> 2*c2*c3: (c2'=c2-1) & (c3'=c3+1);\r\n\t// Collision between 2 identical agents/particles\r\n\t[r11] c1>1 -> c1*(c1-1): true;\r\n\t[r22] c2>1 -> c2*(c2-1): true;\r\n\t[r33] c3>1 -> c3*(c3-1): true;\r\n\t\r\nendmodule\r\n\r\n// Labels (atomic propositions) for properties:\r\n\r\n// Finished: all agents/particles have maximum fitness\r\nlabel \"done\" = c3>=k;\r\n\r\n// Reward structure used to reason about passage of time (discrete steps)\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/dtmc-normalise-simulator.pm.props",
    "content": "// RESULT: 1/3\nP=? [ X c1=1 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/dtmc-normalise-simulator.pm.props.args",
    "content": "-noprobchecks\n-noprobchecks -ex\n"
  },
  {
    "path": "prism-tests/bugfixes/dupevarinupdate.pm.notused",
    "content": "// This should result in error\r\n// But we don't have a way to specify that in the test suite yet...\r\n\r\ndtmc\r\n\r\nmodule M\r\n\r\n\ts : [0..7] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1)&(s'=0) + 0.5 : (s'=2);\r\n\t[] s>0 -> true;\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/exact-pow.prism",
    "content": "dtmc\n\nmodule M\n\n\ts : [0..2] init 0;\n\t\n\t[] s=0 -> pow(1/4,1/2) : (s'=1) + 1-pow(1/4,1/2) : (s'=2);\n\t[] s>0 -> true;\n\t\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/exact-pow.prism.props",
    "content": "// RESULT:Error:fractional (NB: would be 1/2)\nP=?[X s=1];\n"
  },
  {
    "path": "prism-tests/bugfixes/exact-pow.prism.props.args",
    "content": "-exact\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-bscc-rabin.pm",
    "content": "// Bug in Rabin check for explicit engine\r\n// Reported by Joachim Klein\r\n// Fixed in rev 9501\r\n\r\ndtmc\r\n\r\nmodule M1\r\n  s : [0..1] init 0;\r\n\r\n  [] s=0 -> 1:(s'=1);\r\n  [] s=1 -> 1:(s'=1);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-bscc-rabin.pm.props",
    "content": "// RESULT: 1.0\nP=?[(G (s=0)) | (F G (s=1))]\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-bscc-rabin.pm.props.args",
    "content": "-ex\n-h\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-initial-bscc-steady-1-issue-56.pm",
    "content": "// test case for github issue #56\n// all states are initial and are in their own BSCC,\n// so \"all initial states in the same BSCC\" does not apply\n\ndtmc\n\ninit true endinit\n\nmodule m\n    s: [0..1];\n  [] true -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-initial-bscc-steady-1-issue-56.pm.auto",
    "content": "-explicit -steadystate -exportsteadystate explicit-initial-bscc-steady-1-issue-56.pm.ss\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-initial-bscc-steady-1-issue-56.pm.ss",
    "content": "0.5\n0.5\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-mdpsimple-mvmultjacsingle.nm",
    "content": "// Fixed in trunk svn rev 9359\r\n// Bug in explicit.MDPSimple.mvMultJacSingle computation\r\n// Test case triggers the bug for policy iteration + LTL, as result of DRA-product is MDPSimple\r\n\r\nmdp\r\n\r\nlabel \"goal\" = s=7 | s=3;\r\n\r\nmodule m1\r\n  s : [0..9] init 0;\r\n\r\n  [a] s=0 ->   1:(s'=1);\r\n  [b] s=0 -> 0.9:(s'=3) + 0.1:(s'=2);\r\n\r\n  [a] s=1 ->   1:(s'=4);\r\n  [b] s=1 -> 0.2:(s'=2) + 0.8:(s'=3);\r\n\r\n  [a] s=2 ->   1:(s'=2);\r\n\r\n  [a] s=3 ->   1:(s'=3);\r\n\r\n  [a] s=4 ->   1:(s'=5);\r\n  [b] s=4 -> 0.3:(s'=6) + 0.7:(s'=7);\r\n\r\n  [a] s=5 ->   1:(s'=8);\r\n  [b] s=5 -> 0.6:(s'=3) + 0.4:(s'=2);\r\n\r\n  [a] s=6 ->   1:(s'=6);\r\n\r\n  [a] s=7 ->   1:(s'=7);\r\n\r\n  [a] s=8 ->   1:(s'=9);\r\n  [b] s=8 -> 0.5:(s'=3) + 0.5:(s'=2);\r\n\r\n  [a] s=9 ->   1:(s'=2);\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-mdpsimple-mvmultjacsingle.nm.props",
    "content": "// MDPSparse used for first formula (simple path formula), LTL-product (second formula) generates MDPSimple\n\n// RESULT : 0.9\nPmax=?[ F \"goal\" ]\n\n// RESULT : 0.9\nPmax=?[ (F \"goal\") & true]\n\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-mdpsimple-mvmultjacsingle.nm.props.args",
    "content": "-ex -politer\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-rew-npe.pm",
    "content": "// Bug (NPE) in explicit engine when creating rewards\r\n// Fixed in trunk svn rev 6704\r\n\r\nmdp\r\nconst STEPS_TO_GOAL = 3;\r\n\r\nmodule Walker\r\n\ttime: [0..STEPS_TO_GOAL] init 0;\r\n\tgoal: bool init false;\r\n\t[tick] time<STEPS_TO_GOAL & !goal\t->\t(time'=time+1);\r\n\t[reach] time=STEPS_TO_GOAL & !goal\t->\t(goal'=true) & (time'=0);\r\n\t[doSelfLoop] goal\t->\ttrue;\r\nendmodule\r\n\r\nrewards \"rew\"\r\n\t!goal: 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/explicit-rew-npe.pm.props",
    "content": "// RESULT: 4.0\nRmin=? [ F goal ]"
  },
  {
    "path": "prism-tests/bugfixes/explicit-rew-npe.pm.props.args",
    "content": "-ex\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/importexport.auto",
    "content": "# Reduce precision for some tests due to minor differences between the engines\n\n-exportmodelprecision 16 -importmodel rare.pm.all -exportmodel rare.pm.all\n-exportmodelprecision 16 -importmodel rare.pm.all -exportmodel rare.pm.all -ex\n\n-exportmodelprecision 16 -importmodel rare.nm.all -exportmodel rare.nm.all\n-exportmodelprecision 16 -importmodel rare.nm.all -exportmodel rare.nm.all -ex\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm",
    "content": "mdp\n\nconst double p = 1e-13;\n\nmodule rare\n  rare : bool init false;\n\n  [tick] !rare -> p:   (rare' = true)\n                + 1-p: true;\n  [tick] rare  -> true;\nendmodule\n\nrewards\n  rare:  1-p;\n  !rare: p;\n//  [tick] rare:  1-p;\n//  [tick] !rare: p; // omitted because p^2 is too small and disappears\nendrewards"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.args",
    "content": "-explicit\n-mtbdd\n-sparse\n-hybrid"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.importexport.auto",
    "content": "# Reduce precision for some tests due to minor differences between the engines\n\n-exportmodelprecision 16 -exportmodel rare.nm.all\n-exportmodelprecision 16 -exportmodel rare.nm.all -ex\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.props",
    "content": "// RESULT (p=1e-13): 1.0\nPmax=? [F rare];\n\n// RESULT (p=1e-13): true\n0.99 <= Rmin=? [F rare];\n\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.props.args",
    "content": "-gs"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.srew",
    "content": "# Reward structure\n# State rewards\n2 2\n0 1e-13\n1 0.9999999999999\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.sta",
    "content": "(rare)\n0:(false)\n1:(true)\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.tra",
    "content": "2 2 3\n0 0 0 0.9999999999999 tick\n0 0 1 1e-13 tick\n1 0 1 1 tick\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.nm.trew",
    "content": "# Reward structure\n# Transition rewards\n2 2 0\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm",
    "content": "dtmc\n\nconst double p = 1e-13;\n\nmodule rare\n  rare : bool init false;\n\n  [tick] !rare -> p:   (rare' = true)\n                + 1-p: true;\n  [tick] rare  -> true;\nendmodule\n\nrewards\n  rare:  1-p;\n  !rare: p;\n//  [tick] rare:  1-p;\n//  [tick] !rare: p; // omitted because p^2 is too small and disappears\nendrewards\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm.args",
    "content": "-explicit\n-mtbdd\n-sparse\n-hybrid"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm.importexport.auto",
    "content": "# Reduce precision for some tests due to minor differences between the engines\n\n-exportmodelprecision 16 -exportmodel rare.pm.all\n-exportmodelprecision 16 -exportmodel rare.pm.all -ex\n\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm.props",
    "content": "// RESULT (p=1e-13): 1.0\nP=? [F rare];\n\n// RESULT (p=1e-13): true\nR>=0.99 [F rare];\n\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm.srew",
    "content": "# Reward structure\n# State rewards\n2 2\n0 1e-13\n1 0.9999999999999\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm.sta",
    "content": "(rare)\n0:(false)\n1:(true)\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm.tra",
    "content": "2 3\n0 0 0.9999999999999 tick\n0 1 1e-13 tick\n1 1 1 tick\n"
  },
  {
    "path": "prism-tests/bugfixes/export-precision/rare.pm.trew",
    "content": "# Reward structure\n# Transition rewards\n2 0\n"
  },
  {
    "path": "prism-tests/bugfixes/filters+statesOfInterest.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/filters+statesOfInterest.prism.args",
    "content": "-ex\n-m\n-s\n-h\n"
  },
  {
    "path": "prism-tests/bugfixes/filters+statesOfInterest.prism.props",
    "content": "// Bug fix test case for filters; see commit for details\n// The \"0.0+\" is needed because of missing integer-valued vector export\n\n// RESULT: 13\n0.0 + filter(sum, filter(count, true, P>0[ X F s=7]), s=2);\n"
  },
  {
    "path": "prism-tests/bugfixes/filters+statesOfInterest.prism.props.args",
    "content": "-exportvector filters+statesOfInterest.prism.props.txt\n"
  },
  {
    "path": "prism-tests/bugfixes/filters+statesOfInterest.prism.props.txt",
    "content": "13.0\n13.0\n13.0\n13.0\n13.0\n13.0\n13.0\n13.0\n13.0\n13.0\n13.0\n13.0\n13.0\n"
  },
  {
    "path": "prism-tests/bugfixes/imdp-reach-with-infty.prism",
    "content": "// Bug fix for IMDPs where Rmin is finite but Rmax is infty\n\nmodule M\n\n\ts:[0..10];\n\t\n\t[a] s=0 -> [1,1]:(s'=1);\n\t[b] s=0 -> [1,1]:(s'=3);\n\t\n\t[a] s=0 -> [0.5,0.6]:(s'=1) + [0.4,0.5]:(s'=2);\n\t[b] s=0 -> [0.5,0.6]:(s'=3) + [0.4,0.5]:(s'=4);\n\t\n\t[c] s>0 -> true;\n\t\nendmodule\n\t\nrewards true : 1; endrewards\n\nlabel \"target\" = s=3 | s=4;\n"
  },
  {
    "path": "prism-tests/bugfixes/imdp-reach-with-infty.prism.props",
    "content": "// RESULT: 1\nRminmin=?[F \"target\"];\n\n// RESULT: 1\nRminmax=?[F \"target\"];\n"
  },
  {
    "path": "prism-tests/bugfixes/invalidrewardindexsim.sm",
    "content": "// Bug fixed in svn rev 5420\r\n\r\n// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 2;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..2]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/invalidrewardindexsim.sm.props",
    "content": "// RESULT: Error:Invalid\nR{0}=?[I=0.1]\n\n// RESULT: Error:Invalid\nR{3}=?[I=0.1]\n"
  },
  {
    "path": "prism-tests/bugfixes/invalidrewardindexsim.sm.props.args",
    "content": "# Originally a simulation bug, but now test on all engines\n-sim\n-ex\n-h\n"
  },
  {
    "path": "prism-tests/bugfixes/jltlbug1.nm",
    "content": "// LTL-to-DRA bug fix (svn rev 9109)\r\n// Bug (and fix) reported by Joachim Klein\r\n\r\ndtmc\r\n\r\nlabel \"a\" = s=0;\r\nlabel \"b\" = s=1;\r\n\r\nmodule simple\r\n  s: [0..1] init 0;\r\n\r\n  [] true -> 0.5:(s'=0) + 0.5:(s'=1);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/jltlbug1.nm.props",
    "content": "// RESULT: 1\nP=? [ G (\"a\" => ((\"a\" W \"b\") W \"b\")) ]\n"
  },
  {
    "path": "prism-tests/bugfixes/jltlbug2.nm",
    "content": "// LTL-to-DRA bug fix (svn rev XX)\r\n// Bug reported by Brian Logan\r\n\r\ndtmc\r\n\r\nmodule bug\r\n\r\n  r : bool init true;\r\n  v : bool init false;\r\n  d : bool init false;\r\n  f : bool init false;\r\n  h : bool init false;\r\n\r\n  // Transitions for all tracks\r\n  [] r -> 0.104:(r'=true) + \r\n       \t  0.279:(r'=false) & (h'=true) + \r\n\t  0.403:(r'=false) & (v'=true) + \r\n\t  0.060:(r'=false) & (f'=true) + \r\n\t  0.154:(r'=false) & (d'=true);\r\n\r\n  // reduced to 0.395 to workaround rounding error summing to >1\r\n  [] v -> 0.395:(v'=true) + \r\n       \t  0.187:(v'=false) & (r'=true) + \r\n\t  0.284:(v'=false) & (h'=true) + \r\n\t  0.052:(v'=false) & (f'=true) + \r\n\t  0.082:(v'=false) & (d'=true);\r\n\r\n  [] d -> 0.344:(d'=true) + \r\n       \t  0.625:(d'=false) & (h'=true) + \r\n\t  0.031:(d'=false) & (f'=true);\r\n\r\n  [] f -> 1.0:(f'=false) & (h'=true);\r\n\r\n  [] h -> 1.0:(h'=true);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/jltlbug2.nm.props",
    "content": "// RESULT: 0.7153645909\r\nP=? [ r & (G (!(r & (X r)) & !(v & (X v)))) ]\r\n\r\n// RESULT: 0.0502790849\r\nP=? [ r & (F (v & (F r))) & ((r | v) U (r & (X h))) ]\r\n\r\n// RESULT: 0.0227393815\r\nP=? [ r & (G (!(r & (X r)) & !(v & (X v)))) & (F (v & (F r))) & ((r | v) U (r & (X h))) ]\r\n"
  },
  {
    "path": "prism-tests/bugfixes/jltlbug3.nm",
    "content": "// LTL-to-DRA bug fix (svn rev 9109)\r\n// Bug (and fix) reported by Andrea Turrini\r\n\r\n// model of dining cryptographers\r\n// gxn/dxp 15/11/06\r\n\r\nmdp\r\n\r\n// number of cryptographers\r\nconst int N = 3;\r\n\r\n// constants used in renaming (identities of cryptographers)\r\nconst int p1 = 1;\r\nconst int p2 = 2;\r\nconst int p3 = 3;\r\n\r\n// global variable which decides who pays\r\n// (0 - master pays, i=1..N - cryptographer i pays)\r\nglobal pay : [0..N];\r\n\r\n// module for first cryptographer\r\nmodule crypt1\r\n\t\r\n\tcoin1 : [0..2]; // value of its coin\r\n\ts1 : [0..1]; // its status (0 = not done, 1 = done)\r\n\tagree1 : [0..1]; // what it states (0 = disagree, 1 = agree)\r\n\t\r\n\t// flip coin\r\n\t[] coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\r\n\t\r\n\t// make statement (once relevant coins have been flipped)\r\n\t// agree (coins the same and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay!=p1) -> (s1'=1) & (agree1'=1);\r\n\t// disagree (coins different and does not pay)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\r\n\t// disagree (coins the same and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & coin1=coin2    & (pay=p1)  -> (s1'=1);\r\n\t// agree (coins different and pays)\r\n\t[] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1)  -> (s1'=1) & (agree1'=1);\r\n\t\r\n\t// synchronising loop when finished to avoid deadlock\r\n\t[done] s1=1 -> true;\r\n\r\nendmodule\r\n\r\n// construct further cryptographers with renaming\r\nmodule crypt2 = crypt1 [ coin1=coin2, s1=s2, agree1=agree2, p1=p2, coin2=coin3 ] endmodule\r\nmodule crypt3 = crypt1 [ coin1=coin3, s1=s3, agree1=agree3, p1=p3, coin2=coin1 ] endmodule\r\n\r\n// set of initial states\r\n// (cryptographers in their initial state, \"pay\" can be anything)\r\ninit  coin1=0&s1=0&agree1=0 & coin2=0&s2=0&agree2=0 & coin3=0&s3=0&agree3=0  endinit\r\n\r\n// unique integer representing outcome\r\nformula outcome =  4*agree1 + 2*agree2 + 1*agree3 ;\r\n\r\n// parity of number of \"agree\"s (0 = even, 1 = odd)\r\nformula parity = func(mod, agree1+agree2+agree3, 2);\r\n\r\n// label denoting states where protocol has finished\r\nlabel \"done\" = s1=1&s2=1&s3=1;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"even\" = func(mod,(agree1+agree2+agree3),2)=0;\r\n// label denoting states where number of \"agree\"s is even\r\nlabel \"odd\" = func(mod,(agree1+agree2+agree3),2)=1;\r\n\r\n"
  },
  {
    "path": "prism-tests/bugfixes/jltlbug3.nm.props",
    "content": "// RESULT: 1\nfilter(max, Pmax=? [ G ((\"done\"&(X (F \"even\")))=>(\"done\"&(X (\"done\" U \"even\")))) ])\n"
  },
  {
    "path": "prism-tests/bugfixes/jltlbug4.nm",
    "content": "// LTL-to-DRA bug fix (svn rev 9109)\r\n// Bug reported by Moritz Hahn\r\n\r\n// randomized dining philosophers [LR81]\r\n// dxp/gxn 23/01/02\r\n\r\n// model which does not require fairness\r\n// remove the possibility of loops:\r\n// (1) cannot stay in thinking \r\n// (2) if first fork not free then cannot move (another philosopher must more)\r\n\r\nmdp\r\n\r\n// atomic formulae \r\n// left fork free and right fork free resp.\r\nformula lfree = (p2>=0&p2<=4)|p2=6|p2=10;\r\nformula rfree = (p3>=0&p3<=3)|p3=5|p3=7|p3=11;\r\n\r\nmodule phil1\r\n\r\n\tp1: [0..11];\r\n\r\n\t[] p1=0 -> (p1'=1); // trying\r\n\t[] p1=1 -> 0.5 : (p1'=2) + 0.5 : (p1'=3); // draw randomly\r\n\t[] p1=2 &  lfree -> (p1'=4); // pick up left\r\n\t[] p1=3 &  rfree -> (p1'=5); // pick up right\r\n\t[] p1=4 &  rfree -> (p1'=8); // pick up right (got left)\r\n\t[] p1=4 & !rfree -> (p1'=6); // right not free (got left)\r\n\t[] p1=5 &  lfree -> (p1'=8); // pick up left (got right)\r\n\t[] p1=5 & !lfree -> (p1'=7); // left not free (got right)\r\n\t[] p1=6  -> (p1'=1); // put down left\r\n\t[] p1=7  -> (p1'=1); // put down right\r\n\t[] p1=8  -> (p1'=9); // move to eating (got forks)\r\n\t[] p1=9  -> (p1'=10); // finished eating and put down left \r\n\t[] p1=9  -> (p1'=11); // finished eating and put down right\r\n\t[] p1=10 -> (p1'=0); // put down right and return to think\r\n\t[] p1=11 -> (p1'=0); // put down left and return to think\r\n\r\nendmodule\r\n\r\n// construct further modules through renaming\r\nmodule phil2 = phil1 [ p1=p2, p2=p3, p3=p1 ] endmodule\r\nmodule phil3 = phil1 [ p1=p3, p2=p1, p3=p2 ] endmodule\r\n\r\n// rewards (number of steps)\r\nrewards \"num_steps\"\r\n\t[] true : 1;\r\nendrewards\r\n// labels\r\nlabel \"hungry\" = ((p1>0)&(p1<8))|((p2>0)&(p2<8))|((p3>0)&(p3<8));\r\nlabel \"eat\" = ((p1>=8)&(p1<=9))|((p2>=8)&(p2<=9))|((p3>=8)&(p3<=9));\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/bugfixes/jltlbug4.nm.props",
    "content": "// RESULT: 1\nPmin=? [ F(G(\"hungry\" => (F(\"eat\")))) | (F(G(\"hungry\"))) ]\n"
  },
  {
    "path": "prism-tests/bugfixes/lanechange_mdp.prism",
    "content": "// Bug fix test for: https://github.com/prismmodelchecker/prism/issues/15\n\n// Lane change mdp.\n\nmdp\n\n// Repair variable p is the probability of staying in the same\n// state even after giving a turn signal.\nconst double p;\n\n// States/actions.\nmodule lanechange\n        state : [1..4] init 1;\n\n\t// 1: Init lane change.\n\t[drive] (state=1) -> (state'=1);\n\t[turn] (state=1) -> (state'=2);\n\n\t// 2: Do lane change.\n\t[drive] (state=2) -> (state'=2);\n\t[turn] (state=2) -> p: (state'=2) + (1-p): (state'=4);\n\t[abort] (state=2) -> (state'=3);\n\n\t// 3: Abort lane change.\n\t[] (state=3) -> true;\n\n\t// 4: In new lane.\n\t[] (state=4) -> true;\nendmodule\n\n// Reward, associated with the states.\nrewards\n\tstate=1 : 0.2;\n\tstate=2 : 0.3;\n\tstate=3 : 0.05;\n\tstate=4 : 0.1;\nendrewards\n\n// Labels.\nlabel \"changed\" = state=4;\nlabel \"abandoned\" = state=3;\n"
  },
  {
    "path": "prism-tests/bugfixes/lanechange_mdp.prism.props",
    "content": "// RESULT: (5-2*p)/(10-10*p)\nRmin=?[ F \"changed\" ]\n"
  },
  {
    "path": "prism-tests/bugfixes/lanechange_mdp.prism.props.args",
    "content": "-param p=0:1\n-exact -const p=0:0.1:1\n-const p=0:0.1:1\n"
  },
  {
    "path": "prism-tests/bugfixes/largedoubles.prism",
    "content": "// Bug triggered by very large doubles being stored incorrectly in CUDD\n// (fixed in svn rev 10872)\n\nmdp\n\nconst int XX;\n\nmodule clk\n\ttime : [0..6] init 3;\n\t[tack] time=3 -> (time'=4);\nendmodule\n\nmodule env\n\ts : [0..5] init 3;\nendmodule\n\nmodule sys\n\tss : [1..3] init 1;\n\td : [1..5] init 3;\nendmodule\n\nconst double DBL_MAX = 1.5e+200;\n\nformula iam = (s = 0 ? 0.355159 : 0) + (s = 1 ? 0.162756 : 0) + (s = 2 ? 0.0876354 : 0) + (s = 3 ? 0.0494423 : 0) + (s = 4 ? 0.0295989 : 0) + (s = 5 ? 0.0259923 : 0);\nformula df = (d - 1) / 4;\nformula lambda = 1 / (iam * ss);\nformula beta = 0.5 * 0.0856328 + (1-df) * 0.0177031;\nformula rho = lambda * beta;\nformula cs2 = (0.5 * 0.00733298 + 0.5 * 0.000313401) / pow(beta, 2);\nformula t = beta + beta * (rho / (1 - rho)) * (1 + cs2) / 2;\nformula uTotal = ((true ? DBL_MAX : t) = DBL_MAX) ? 1:0;\n\nrewards \"util\"\n\t[tack] true : 2000 + (uTotal);\nendrewards\n\nlabel \"final\" = time=6;\n"
  },
  {
    "path": "prism-tests/bugfixes/largedoubles.prism.props",
    "content": "// Bug triggered by very large doubles being stored incorrectly in CUDD\n// (fixed in svn rev 10872)\n\n// RESULT (XX=1): 2001.0\n// RESULT (XX=2): 2001.0\nRmax=? [ C<=1 ]\n "
  },
  {
    "path": "prism-tests/bugfixes/largedoubles.prism.props.args",
    "content": "-const XX=1:2 -s\n"
  },
  {
    "path": "prism-tests/bugfixes/ltl-dag.nm",
    "content": "mdp\r\n\r\nmodule die1\r\n\r\n\t// local state\r\n\ts1 : [0..7] init 0;\r\n\t// value of the die\r\n\td1 : [0..6] init 0;\r\n\t\r\n\t[] s1=0 -> 0.5 : (s1'=1) + 0.5 : (s1'=2);\r\n\t[] s1=1 -> 0.5 : (s1'=3) + 0.5 : (s1'=4);\r\n\t[] s1=2 -> 0.5 : (s1'=5) + 0.5 : (s1'=6);\r\n\t[] s1=3 -> 0.5 : (s1'=1) + 0.5 : (s1'=7) & (d1'=1);\r\n\t[] s1=4 -> 0.5 : (s1'=7) & (d1'=2) + 0.5 : (s1'=7) & (d1'=3);\r\n\t[] s1=5 -> 0.5 : (s1'=7) & (d1'=4) + 0.5 : (s1'=7) & (d1'=5);\r\n\t[] s1=6 -> 0.5 : (s1'=2) + 0.5 : (s1'=7) & (d1'=6);\r\n\t[] s1=7 & s2=7 -> (s1'=7);\r\n\t\r\nendmodule\r\n\r\nmodule die2 = die1 [ s1=s2, s2=s1, d1=d2 ] endmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] !(s1=7 & s2=7) : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ltl-dag.nm.props",
    "content": "// bugfix: SimpleLTL.simplify() requires that the formula is a tree, i.e., no sharing of subtrees.\n// Fix (SVN rev: 10894) ensures that SimpleLTL is a tree (regression due to rev 10565).\n// Without the fix, the Pmin formula has result 1.0.\n//\n// Model: two_dice.nm\n\n// RESULT: 0.0\nPmax=?[ (X (s1=7)) | (X (X s1=7)) ]\n\n// RESULT: 0.0\nPmin=?[ (X (s1=7)) | (X (X s1=7)) ]\n\n"
  },
  {
    "path": "prism-tests/bugfixes/ltl.nm",
    "content": "// LTL bug(s) fixed in trunk rev 2201\r\n\r\nmdp\r\n\r\nmodule test\r\n\r\n\tx : [0..2];\r\n\t\r\n\t[] x=0 -> true;\r\n\t[] x=0 -> 0.5 : (x'=1) + 0.5: (x'=2);\r\n\t[] x=1 -> (x'=0);\r\n\t[] x=2 -> true;\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ltl.nm.props",
    "content": "// RESULT: 0.0\nPmax=? [ G F (x=1) ];\n"
  },
  {
    "path": "prism-tests/bugfixes/ltlexplicit.nm",
    "content": "// LTL bug fix in explicit engine (fixed in svn rev 9093)\r\n\r\nmdp\r\n \r\nmodule tree_160000\r\ns:[1..13] init 1;\r\n\r\n[r1]s=1 -> 1011/3406:(s'=2) +  2395/3406:(s'=3);\r\n[r2]s=1 -> 968/3276:(s'=4) +  2308/3276:(s'=5);\r\n[r2]s=2 -> 122/261:(s'=6) +  139/261:(s'=7);\r\n[r1]s=4 -> 123/239:(s'=8) +  116/239:(s'=9);\r\n[r4]s=6 -> 14/35:(s'=10) +  21/35:(s'=11);\r\n[r4]s=8 -> 14/32:(s'=12) +  18/32:(s'=13);\r\n[r1]s=3 -> 1:(s'=3);\r\n[r1]s=5 -> 1:(s'=5);\r\n[r1]s=7 -> 1:(s'=7);\r\n[r1]s=9 -> 1:(s'=9);\r\n[r1]s=10 -> 1:(s'=10);\r\n[r1]s=11 -> 1:(s'=11);\r\n[r1]s=12 -> 1:(s'=12);\r\n[r1]s=13 -> 1:(s'=13);\r\nendmodule\r\n\r\nlabel \"o_000\" = s=1;\r\nlabel \"o_010\" = s=4;\r\nlabel \"o_100\" = s=2;\r\nlabel \"o_110\" = s=8|s=6;\r\nlabel \"o_Pr0\" = s=11|s=13;\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ltlexplicit.nm.props",
    "content": "// RESULT: 2143152/25054848  ( = 968/3276 * 123/239 * 18/32, i.e. approx. 0.085538)\nPmax=? [( (X ( X  ( \"o_110\"))) &  (X ( X  ( X ( \"o_Pr0\"))))) ]\n\n// RESULT: 119064/782964  ( = 968/3276 * 123/239, i.e. approx. 0.152068)\nPmax=? [ (X ( X  ( \"o_110\")))  ]\n\n// RESULT: 2143152/25054848  ( = 968/3276 * 123/239 * 18/32, i.e. approx. 0.085538)\nPmax=? [  (X ( X  ( X ( \"o_Pr0\")))) ]\n"
  },
  {
    "path": "prism-tests/bugfixes/ltlexplicit.nm.props.args",
    "content": "-h\n-ex\n"
  },
  {
    "path": "prism-tests/bugfixes/ltlproposition.prism",
    "content": "// Trivial LTL formula (proposition)\r\n// Accidentally disabled by previous over-zealous type checking\r\n// Fixed in svn rev 7723\r\n\r\ndtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ltlproposition.prism.props",
    "content": "// RESULT: 0\nP=? [ s=1 ]\n\n// RESULT: 1\nP=? [ s=0 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/mdp-action-storage-bug.prism",
    "content": "mdp\n\nmodule M\n\n\ts:[0..3];\n\t\n\t[a] s=0 -> (s'=2);\n\t[b] s=2 -> (s'=1);\n\nendmodule\n\n"
  },
  {
    "path": "prism-tests/bugfixes/mdp-action-storage-bug.prism.props",
    "content": "// RESULT: true\nP>=1 [ F s=1 ];\n"
  },
  {
    "path": "prism-tests/bugfixes/mdp-action-storage-bug.prism.props.args",
    "content": "-ex\n-m\n"
  },
  {
    "path": "prism-tests/bugfixes/mdp-rewards-gs-loops.nm",
    "content": "// Bug in Gauss-Seidel solution of MDP expected reward to a target for models with self-loops\n// (spotted by Joachim Klein)\n// Fixed in svn rev 11841\n\nmdp\n\nmodule M1\n s: [0..1] init 0;\n\n [] s=0 -> 1/2:(s'=0) + 1/2:(s'=1);\n [] s=1 -> true;\nendmodule\n\nrewards\n s=0 : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/bugfixes/mdp-rewards-gs-loops.nm.props",
    "content": "// RESULT: 2.0\nRmax=? [ F s=1 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/mdp-rewards-gs-loops.nm.props.args",
    "content": "-ex -gs\n"
  },
  {
    "path": "prism-tests/bugfixes/multi-valiter-loops.nm",
    "content": "// Bug fixed in svn rev 11061\r\n// Value iteration multi-objective was removing self-loops\r\n// in situations where it should not be\r\n\r\nmdp\r\n\r\nmodule m\r\n\ts : [0..1];\r\n\r\n\t[] s=0 -> (s'=0);\r\n\t[a] s=0 -> (s'=1);\r\n\t[] s=1 -> (s'=1);\r\n\r\nendmodule\r\n\r\nrewards \"R1\"\r\n\t[a] s=0 : 2;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/multi-valiter-loops.nm.props",
    "content": "// RESULT: 0.0\nmulti(R{\"R1\"}min=? [ C ])\n"
  },
  {
    "path": "prism-tests/bugfixes/multi-valiter-loops.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/bugfixes/multi-valiter-pareto-min-zero.nm",
    "content": "// Bug fixed in svn rev 11059\n// Value iteration multi-objective Pareto generation was using wrong direction vector in some cases\n\n\nmdp\n\nconst double pse = 0.2;\nconst double pusb = 0.6;\nconst double prav = 0.7;\nconst double pef = 0.75;\nconst double prc = 0.85;\n\n//player a\n//attacker, [doAttackSE], [dontDoAttackSE], [doAttackUSB], [dontDoAttackUSB],\n//[doAttackEF], [dontDoAttackEF],\n//[prob_SE_OR_USB], [prob_NRAV], [prob_NRC_AND_EF],\n//[succeed] , [fail]\n//endplayer\n\n//player d\n//[doDefenceRAV], [dontDoDefenceRAV], [doDefenceRC], [dontDoDefenceRC]\n//endplayer\n\nmodule attacker\n\ns:[0..8];\n\ndoSE : bool init false;\ndoUSB : bool init false;\ndoRAV : bool init false;\ndoRC : bool init false;\ndoEF : bool init false;\n\n//subtree t_SU = SE_OR_USB\nsuccess_t_SU : bool init false;\n//subtree t_VF = SE_OR_USB_AND_NRAV\nsuccess_t_VF : bool init false;\n//whole tree\nsuccess_Root : bool init false;\n\n//nondeterministic transactions of sub-tree SE_OR_USB\n[doAttackSE_USB] s=0 -> (s'=1)&(doSE'=true)&(doUSB'=true);\n[doAttackSE] s=0 -> (s'=1)&(doSE'=true);\n[doAttackUSB] s=0 -> (s'=1)&(doUSB'=true);\n[dontDoAttackSE_USB] s=0 -> (s'=1);\n\n\n//probabilistic transactions of sub-tree SE_OR_USB (t_SU)\n[prob_SE_OR_USB] s=1 & doSE=true & doUSB=true -> 1-(1-pse)*(1-pusb):(s'=2)&(success_t_SU'=true) + (1-pse)*(1-pusb):(s'=2)&(success_t_SU'=false);\n[prob_SE_OR_USB] s=1 & doSE=true & doUSB=false -> pse:(s'=2)&(success_t_SU'=true) + (1-pse):(s'=2)&(success_t_SU'=false);\n[prob_SE_OR_USB] s=1 & doSE=false & doUSB=true -> pusb:(s'=2)&(success_t_SU'=true) + (1-pusb):(s'=2)&(success_t_SU'=false);\n[prob_SE_OR_USB] s=1 & doSE=false & doUSB=false -> (s'=2)&(success_t_SU'=false);\n\n//nondeterministic transactions of sub-tree NEG_RAV\n[doDefenceRAV] s=2 ->(s'=3)&(doRAV'=true);\n//[dontDoDefenceRAV] s=2 -> (s'=3);\n\n//probabilistic transactions of sub-tree NEG_RAV (t_VF)\n[prob_NRAV] s=3 & success_t_SU=true & doRAV=true -> (1-prav):(s'=4)&(success_t_VF'=true) + prav:(s'=4)&(success_t_VF'=false);\n[prob_NRAV] s=3 & success_t_SU=true & doRAV=false -> (s'=4)&(success_t_VF'=true);\n[prob_NRAV] s=3 & success_t_SU=false  -> (s'=4)&(success_t_VF'=false);\n\n//nondeterministic transactions of sub-tree EF_AND_NEG_RC\n[doDefenceRC] s=4 -> (s'=5)&(doRC'=true);\n//[dontDoDefenceRC] s=4 -> (s'=5)&(doRC'=false);\n\n[doAttackEF] s=5 -> (s'=6)&(doEF'=true);\n[dontDoAttackEF] s=5 -> (s'=6)&(doEF'=false);\n\n//probabilistic transactions of sub-tree EF_AND_NEG_RC\n[prob_NRC_AND_EF] s=6 & success_t_VF=true & doRC=true & doEF=true -> pef*(1-prc):(s'=7)&(success_Root'=true) + 1-pef*(1-prc):(s'=7)&(success_Root'=false);\n//[prob_NRC_AND_EF] s=6 & success_t_VF=true & doRC=true & doEF=false ->(s'=7)&(success_Root'=false);\n[prob_NRC_AND_EF] s=6 & success_t_VF=true & doRC=false & doEF=true -> pef:(s'=7)&(success_Root'=true) + (1-pef):(s'=7)&(success_Root'=false);\n[prob_NRC_AND_EF] s=6 & success_t_VF=true & doEF=false -> (s'=7)&(success_Root'=false);\n[prob_NRC_AND_EF] s=6 & success_t_VF=false -> (s'=7)&(success_Root'=false);\n\n\n[succeed] s=7&success_Root=true -> (s'=8);\n[fail] s=7&success_Root=false -> (s'=8);\n\nendmodule\n\n\n//success state for an attacker\nlabel \"success\" = s=8&success_Root=true;\nlabel \"end\" = s=8;\n\nrewards \"cost\"\n[doAttackSE_USB] true:10;\n[doAttackSE] true:2;\n[doAttackUSB] true:8;\n[doAttackEF] true:5;\nendrewards\n\nrewards \"success\"\n[succeed] true:1;\nendrewards\n\n\n"
  },
  {
    "path": "prism-tests/bugfixes/multi-valiter-pareto-min-zero.nm.props",
    "content": "//RESULT: [(0.0,0.0),(2.3,0.00675),(8.9,0.02025),(11.02,0.02295)]\nmulti(R{\"cost\"}min=? [ C ], R{\"success\"}max=? [ C ])\n"
  },
  {
    "path": "prism-tests/bugfixes/multi-valiter-pareto-min-zero.nm.props.args",
    "content": "-paretoepsilon 10e-5\n"
  },
  {
    "path": "prism-tests/bugfixes/param-not-equal.prism",
    "content": "// test case for the fix in SVN r11976\n// handling of != operator by parametric / exact engine in state formulas\n\ndtmc\n\nmodule M1\n  s: [0..3] init 0;\n  t: [0..3] init 1;\n\n  // overlapping actions in DTMC: if both [a] and [b] are enabled, each is taken with\n  // probability 1/2\n  [a] s < 3 -> 1/2:(s'=s+1) + 1/2:(s'=s);\n  [b] t < 3 -> 1/2:(t'=t+1) + 1/2:(t'=t);\n\n  [c] s=3 & t=3 -> 1:true;\nendmodule"
  },
  {
    "path": "prism-tests/bugfixes/param-not-equal.prism.args",
    "content": "-explicit\n-exact\n"
  },
  {
    "path": "prism-tests/bugfixes/param-not-equal.prism.props",
    "content": "// test case for the fix in SVN r11976\n// handling of != operator by parametric / exact engine in state formulas\n//\n// first property had result of 0 before fix, the second (equivalent) property had the correct result\n\n// RESULT: 3/8\nP=?[ (s!=t) U s=3 ]\n\n// RESULT: 3/8\nP=?[ !(s=t) U s=3 ]"
  },
  {
    "path": "prism-tests/bugfixes/param-reach-inf.prism",
    "content": "// Bug fix test for: https://github.com/prismmodelchecker/prism/issues/4\r\n\r\ndtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/param-reach-inf.prism.props",
    "content": "// RESULT: 11/3\nR=? [ F s=7 ]\n\n// RESULT: Infinity\nR=? [ F d=6 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/param-reach-inf.prism.props.args",
    "content": "-exact\n-h\n"
  },
  {
    "path": "prism-tests/bugfixes/ptaalphabet.nm",
    "content": "// dtmc // Pmax =? [ F seenA ] = 0.0 Pmax =? [ F seenB ] = 0.0\npta // Pmax =? [ F seenA ] = 1.0 Pmax =? [ F seenB ] = 0.0\n\nmodule AA\nseenA: bool init false;\n\n[fire] true -> (seenA'=true);\nendmodule\n\nmodule BB\nseenB: bool init false;\n\n[fire] false -> (seenB'=true);\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/ptaalphabet.nm.props",
    "content": "// RESULT: 0.0\nPmax=? [ F seenA ];\n\n// RESULT: 0.0\nPmax=? [ F seenB ];\n"
  },
  {
    "path": "prism-tests/bugfixes/ptaalphabet.nm.props.args",
    "content": "-ptamethod games\n-ptamethod digital\n-ptamethod backwards\n-mdp\n-mdp -ex\n"
  },
  {
    "path": "prism-tests/bugfixes/ptabounded.nm",
    "content": "// PTA time-bounded bug fixed in trunk rev 2253\r\n\r\npta\r\n\r\nmodule M\r\n\t\r\n\ts:[0..6] init 0;\r\n\tx: clock;\r\n\t\r\n\tinvariant\r\n\t\t(true => x<=5)\r\n\tendinvariant\r\n\t\r\n\t[] s=0 & x>=5 -> 0.5:(s'=1)&(x'=0) + 0.5:(s'=2)&(x'=0);\r\n\t[] s=1 & x>=1 -> 0.5:(s'=3)&(x'=0)+ 0.5:(s'=4)&(x'=0);\r\n\t[] s=2 & x>=5 -> 0.5:(s'=5)&(x'=0) + 0.5:(s'=6)&(x'=0);\r\n\t[] s>2 & x>=5 -> (s'=s)&(x'=0);\r\n\t\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ptabounded.nm.props",
    "content": "\t// RESULT: 0.5\n\tPmax=? [ F<=6 ((s=3)|(s=4)) ];\n"
  },
  {
    "path": "prism-tests/bugfixes/ptaboundedinitial.nm",
    "content": "// PTA time-bounded bug fixed in trunk rev 11569\r\n// (and related catch of negative time bounds fixed in rev 11570)\r\n\r\npta\r\n\r\nmodule M\r\n\t\r\n\ts:[0..6] init 0;\r\n\tx: clock;\r\n\t\r\n\tinvariant\r\n\t\t(true => x<=5)\r\n\tendinvariant\r\n\t\r\n\t[] s=0 & x>=5 -> 0.5:(s'=1)&(x'=0) + 0.5:(s'=2)&(x'=0);\r\n\t[] s=1 & x>=1 -> 0.5:(s'=3)&(x'=0)+ 0.5:(s'=4)&(x'=0);\r\n\t[] s=2 & x>=5 -> 0.5:(s'=5)&(x'=0) + 0.5:(s'=6)&(x'=0);\r\n\t[] s>2 & x>=5 -> (s'=s)&(x'=0);\r\n\t\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ptaboundedinitial.nm.props",
    "content": "// RESULT: 1.0\nPmax=? [ F<=6 s=0 ];\n\n// RESULT: 1.0\nPmax=? [ F<=1 s=0 ];\n\n// RESULT: 1.0\nPmax=? [ F<=0 s=0 ];\n\n// RESULT: Error:Negative\nPmax=? [ F<0 s=0 ];\n\n// RESULT: Error:Negative\nPmax=? [ F< -1 s=0 ]; \n"
  },
  {
    "path": "prism-tests/bugfixes/ptarewardsdigital.nm",
    "content": "// Bug fixed in rev 5523\r\n// (GCD omitted from rewards in digital clocks translation)\r\n\r\npta\r\n\r\nconst double read_failure = 0.1;\r\n\r\nmodule power_model\r\n\r\n    p : [0..1] init 0;\r\n    \r\n    invariant\r\n        (p=0 => true) &\r\n        (p=1 => true)\r\n    endinvariant\r\n\r\n    [open] p=0 -> (p'=0);\r\n    [close] p=0 -> (p'=0);\r\n\r\n    [read_start] p=0 -> (p'=1);\r\n    [read_stop] p=1 -> (p'=0);\r\n\r\nendmodule\r\n\r\nmodule trace\r\n\r\n    t : [0..4] init 0;\r\n    c : clock;\r\n    \r\n    invariant\r\n\r\n    (t=0 => c <=0) &\r\n        (t=1 => c >= 0 & c<=5) &\r\n        (t=2 => c>=5 & c<=15) &\r\n    (t=3 => c<=15) &\r\n    (t=4 => c<=15)\r\n\r\n    endinvariant\r\n\r\n    [open] t=0 -> (t'=1);\r\n   \r\n    [read_start] t=1 & c=5 -> read_failure:(t'=1) + (1-read_failure):(t'=2);\r\n    [read_stop] t=2 & c=15 -> (t'=3);\r\n    [read_stop] t=1 -> (t'=1);\r\n\r\n    //[read_start] t=1 -> read_failure:(t'=1) + (1-read_failure):(t'=2);\r\n    //[read_stop] t=2 -> (t'=3);\r\n    //[read_stop] t=1 -> (t'=1);\r\n\r\n    [close] t=3 -> (t'=4);\r\n    [] t=4 -> (t'=4);\r\n\r\nendmodule\r\n\r\nlabel \"target\" = (p = 0 & t=4);\r\n\r\nrewards \r\n\r\n    p=0 & t=1 : 105;\r\n    p=1 & t=2 : 105;\r\n\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ptarewardsdigital.nm.props",
    "content": "// RESULT: 525\nRmin=?[F p=1&t=2]\n"
  },
  {
    "path": "prism-tests/bugfixes/ptarewardsdigital.nm.props.args",
    "content": "-ptamethod digital\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithiteguard.nm",
    "content": "// Bug fixed in SVN rev 11214\n// Previously, the if-then-else (ITE) guard was not simplified,\n// leading to an invalid clock constraint\n\npta\n\nmodule M\n    s : [0..1] init 0;\n    x : clock;\n\n    [a] (s=0?true:false) & (x<=1) -> (s'=1);\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithiteguard.nm.props",
    "content": "// RESULT: 1.0\nPmax=?[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithmaxclockzero.nm",
    "content": "// Bug fixed in rev 5582\r\n// (c-closure on empty zone breaks when max clock constraint constant is 0)\r\n\r\npta\r\n\r\nmodule never_enabled_action\r\ns : [0..3];\r\nx : clock;\r\ny : clock;\r\n\r\ninvariant\r\n (s=0 => x=0 & y=0)\r\nendinvariant\r\n\r\n[] s=0 -> (s'=1);\r\n[] s=1 & x=y -> (s'=2);\r\n[] s= 1 & x < y -> (s'=3);\r\n[] s=2 -> true;\r\n[] s=3 -> true;\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithmaxclockzero.nm.props",
    "content": "// RESULT: 0.0\nPmax=? [F s=3]\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithpropconst.nm",
    "content": "// PTA model checking bug fixed in trunk rev 3262\r\n// (incorrect processing of constants in props files, for PTA m/c)\r\n\r\npta\r\n\r\n// maximum and minimum delays\r\n// fast\r\nconst int rc_fast_max = 850;\r\nconst int rc_fast_min = 760;\r\n// slow\r\nconst int rc_slow_max = 1670;\r\nconst int rc_slow_min = 1590;\r\n// delay caused by the wire length\r\nconst int delay = 3;\r\n// probability of choosing fast and slow\r\nconst double fast = 0.5;\r\nconst double slow = 1-fast;\r\n\r\nmodule abstract_firewire\r\n\r\n\t// clock \r\n\tx : clock;\r\n\t// local state\r\n\ts : [0..9];\r\n\t// 0 - start_start\r\n\t// 1 - fast_start\r\n\t// 2 - start_fast\r\n\t// 3 - start_slow\r\n\t// 4 - slow_start\r\n\t// 5 - fast_fast\r\n\t// 6 - fast_slow\r\n\t// 7 - slow_fast\r\n\t// 8 - slow_slow\r\n\t// 9 - done\r\n\r\n\t// clock invariant\r\n\tinvariant\r\n\t\t(s=0 => x<=delay) &\r\n\t\t(s=1 => x<=delay) &\r\n\t\t(s=2 => x<=delay) &\r\n\t\t(s=3 => x<=delay) &\r\n\t\t(s=4 => x<=delay) &\r\n\t\t(s=5 => x<=rc_fast_max) &\r\n\t\t(s=6 => x<=rc_slow_max) &\r\n\t\t(s=7 => x<=rc_slow_max) &\r\n\t\t(s=8 => x<=rc_slow_max) &\r\n\t\t(s=9 => x<=0)\r\n\tendinvariant\r\n\t\r\n\t// start_start (initial state)\r\n\t[] s=0 -> fast : (s'=1) + slow : (s'=4);\r\n\t[] s=0 -> fast : (s'=2) + slow : (s'=3);\r\n\t// fast_start\r\n\t[] s=1 -> fast : (s'=5) & (x'=0) + slow : (s'=6) & (x'=0);\r\n\t// start_fast\r\n\t[] s=2 -> fast : (s'=5) & (x'=0) + slow : (s'=7) & (x'=0);\r\n\t// start_slow\r\n\t[] s=3 -> fast : (s'=6) & (x'=0) + slow : (s'=8) & (x'=0);\r\n\t// slow_start\r\n\t[] s=4 -> fast : (s'=7) & (x'=0) + slow : (s'=8) & (x'=0);\r\n\t// fast_fast\r\n\t[] s=5 & (x>=rc_fast_min)       -> (s'=0) & (x'=0);\r\n\t[] s=5 & (x>=rc_fast_min-delay) -> (s'=9) & (x'=0);\r\n\t// fast_slow\r\n\t[] s=6 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// slow_fast\r\n\t[] s=7 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// slow_slow\r\n\t[] s=8 & x>=rc_slow_min       -> (s'=0) & (x'=0);\r\n\t[] s=8 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// done\r\n\t[] s=9 -> true;\r\n\t\r\nendmodule\r\n\r\n// labels\r\nlabel \"done\" = (s=9);\r\n\r\n// reward structures\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithpropconst.nm.props",
    "content": "const int T;\n\n// Minimum probability that a leader is eventually elected\n// RESULT: ?\nPmax=? [ F<=T \"done\" ]\n\n// Maximum expected time to elect a leader\n// RESULT: 1379.5\nR{\"time\"}min=? [ F \"done\" ]\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithpropconst.nm.props.args",
    "content": "-prop 2 -ptamethod digital -s\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithstateprobs.nm",
    "content": "// Bug fixed in SVN rev 11215\n// Probabilities that reference state variables were not correctly\n// translated in the transformation to a location-based model\n\npta\n\nmodule M\n  s : [0..2];\n  x : clock;\n\n  invariant\n    true => x<=1\n  endinvariant\n\n  // ITE for probabilities\n  [a] true & x=1 -> (s=0 ? 0.5 : 0.25):(s'=0)&(x'=0) + (s=0 ? 0.5 : 0.75):(s'=2)&(x'=0);\n\n  // direct reference to state variable values in probabilities\n  [b] s<=1 & x=1 -> (1-s):(s'=1)&(x'=0) + s:(s'=0)&(x'=0);\n\n  // implicit probability (checks that 'null' probability is properly handled)\n  [c] s=2 & x=1 -> (s'=2)&(x'=0);\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/ptawithstateprobs.nm.props",
    "content": "// RESULT: 1.0 \nPmax=?[ F s=2 ]\n\n// RESULT: 0.0 \nPmin=?[ F s=2 ]\n\n// RESULT: 0.0 \nPmax=?[ F<1 s=2 ]\n\n// RESULT: 0.5\nPmax=?[ F<=1 s=2 ]\n\n// RESULT: 0.75\nPmax=?[ F<=2 s=2 ]\n\n// RESULT: 0.875\nPmax=?[ F<=3 s=2 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/resultspecconstants.pm",
    "content": "// prism-auto bug fix: make sure constants pre-defined in model\r\n// and properties file are available for RESULT specification\r\n// (fixed in svn rev 10302)\r\n\r\ndtmc\r\n\r\nconst int start = 0;\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init start;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/resultspecconstants.pm.props",
    "content": "const int end = 7;\nconst int x;\n\n// Probability of throwing x?\n// RESULT (start=0,end=7,x=6): 1/6\nP=? [ F s=end & d=x ]\n"
  },
  {
    "path": "prism-tests/bugfixes/resultspecconstants.pm.props.args",
    "content": "-const x=6\n"
  },
  {
    "path": "prism-tests/bugfixes/rewpoliter.nm",
    "content": "// Policy iteration bug fixed in revision 7669\r\n\r\nmdp\r\n\r\nmodule strips\r\nstate : [ 0 .. 5 ] init 0;\r\n\r\n[ takebox ] state=0 -> 1: (state'=1) ;\r\n[ askforhelp ] state=0 -> 0.4: (state'=2)  + 0.6: (state'=0) ;\r\n[ takeboxwithhelp ] state=2 -> 1: (state'=3) ;\r\n[ takebox ] state=2 -> 1: (state'=3) ;\r\n[ askforhelp ] state=2 -> 0.4: (state'=2)  + 0.6: (state'=2) ;\r\n[ takebananas6 ] state=3 -> 0.3: (state'=4)  + 0.5: (state'=3)  + 0.2: (state'=1) ;\r\n[ takeboxwithhelp ] state=3 -> 1: (state'=3) ;\r\n[ takebox ] state=3 -> 1: (state'=3) ;\r\n[ takebananas1 ] state=3 -> 0.1: (state'=4)  + 0.9: (state'=3) ;\r\n[ askforhelp ] state=3 -> 0.4: (state'=3)  + 0.6: (state'=3) ;\r\n[ takebox ] state=1 -> 1: (state'=1) ;\r\n[ takebananas1 ] state=1 -> 0.1: (state'=5)  + 0.9: (state'=1) ;\r\n[ askforhelp ] state=1 -> 0.4: (state'=3)  + 0.6: (state'=1) ;\r\nendmodule\r\n\r\nrewards\r\n[ takebox ] true : 8;\r\n[ askforhelp ] true : 5;\r\n[ takeboxwithhelp ] true : 4;\r\n[ takebananas6 ] true : 3;\r\n[ takebananas1 ] true : 3;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/rewpoliter.nm.props",
    "content": "// RESULT: 209/6\nRmin=? [ F state=4 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/rewpoliter.nm.props.args",
    "content": "-politer\n"
  },
  {
    "path": "prism-tests/bugfixes/rewpoliter2.nm",
    "content": "// Policy iteration bug fixed in revision 7707\r\n\r\nmdp\r\n\r\nmodule strips\r\nstate : [ 0 .. 4 ] init 0;\r\n\r\n[ takestick ] state=0 -> 1: (state'=1) ;\r\n[ askforhelp ] state=0 -> 0.4: (state'=2)  + 0.6: (state'=0) ;\r\n[ takestick ] state=2 -> 1: (state'=3) ;\r\n[ leavehelp ] state=2 -> 1: (state'=0) ;\r\n[ takebananas2 ] state=3 -> 0.2: (state'=4)  + 0.8: (state'=3) ;\r\n[ dropstick ] state=3 -> 1: (state'=2) ;\r\n[ leavehelp ] state=3 -> 1: (state'=1) ;\r\n[ askforhelpwithstick ] state=1 -> 0.8: (state'=3)  + 0.2: (state'=1) ;\r\n[ askforhelp ] state=1 -> 0.4: (state'=3)  + 0.6: (state'=1) ;\r\n[ dropstick ] state=1 -> 1: (state'=0) ;\r\nendmodule\r\n\r\nrewards \"cost\"\r\n[ takestick ] true : 5;\r\n[ askforhelp ] true : 8;\r\n[ leavehelp ] true : 1;\r\n[ takebananas2 ] true : 3;\r\n[ askforhelpwithstick ] true : 8;\r\n[ dropstick ] true : 1;\r\nendrewards\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/bugfixes/rewpoliter2.nm.props",
    "content": "// RESULT: 30\nRmin=? [ F state=4 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/rewpoliter2.nm.props.args",
    "content": "-politer\n"
  },
  {
    "path": "prism-tests/bugfixes/samplerboundeduntildisc.pm",
    "content": "// Fix for the handling of strict/non-strict in simulation based bounded until fixed in revision 9163\r\n\r\ndtmc \r\n\r\nmodule m1\r\n  s : [0..4] init 0;\r\n\r\n  [] s<4 -> 1 : (s'=s+1);\r\n  [] s=4 -> 1 : (s'=s);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/bugfixes/samplerboundeduntildisc.pm.props",
    "content": "// Fix for the handling of strict/non-strict in simulation based bounded until fixed in revision 9163\n\n// RESULT: Error\nP=?[ G<0 s<2]\n\n// RESULT: 1.0\nP=?[ G<1 s<2]\n\n// RESULT: 1.0\nP=?[ G<2 s<2]\n\n// RESULT: 0.0\nP=?[ G<3 s<2]\n\n// RESULT: 0.0\nP=?[ G<4 s<2]\n\n\n\n// RESULT: 1.0\nP=?[ G<=0 s<2]\n\n// RESULT: 1.0\nP=?[ G<=1 s<2]\n\n// RESULT: 0.0\nP=?[ G<=2 s<2]\n\n// RESULT: 0.0\nP=?[ G<=3 s<2]\n\n// RESULT: 0.0\nP=?[ G<=4 s<2]\n\n"
  },
  {
    "path": "prism-tests/bugfixes/samplerboundeduntildisc.pm.props.args",
    "content": "-sim\n"
  },
  {
    "path": "prism-tests/bugfixes/sim-ctmc-until-false.prism",
    "content": "// Fix for bug reported here:\r\n// https://groups.google.com/g/prismmodelchecker/c/5GyC-LJu_2U\r\n// Simulation bug, but should be be deterministically 0\r\n\r\n// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 2;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..2]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/bugfixes/sim-ctmc-until-false.prism.props",
    "content": "// RESULT: 0.0\nP=?[ false U<=1 (s=2 & a=0) ];\n"
  },
  {
    "path": "prism-tests/bugfixes/sim-ctmc-until-false.prism.props.args",
    "content": "-sim\n-ex\n"
  },
  {
    "path": "prism-tests/bugfixes/simplify-unary-minus-issue-34.prism",
    "content": "// Test case for https://github.com/prismmodelchecker/prism/issues/34\n//   Expression simplification for 0-x does not preserve type\n//   Error during model building (explicit), simulation\n\ndtmc\n\nmodule M1\n   s : [0..1] init 0;\n\n   [] true -> 1/2:(s'=0) + 1/2:(s'=max(1,0-s));\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/simplify-unary-minus-issue-34.prism.args",
    "content": "-explicit\n-hybrid\n-mtbdd\n-sparse\n-exact\n"
  },
  {
    "path": "prism-tests/bugfixes/simplify-unary-minus-issue-34.prism.props",
    "content": "// RESULT: 1\nP=?[F s=1]\n"
  },
  {
    "path": "prism-tests/bugfixes/simplify_implies.prism",
    "content": "// Bug in handling of implication in explicit engine (from Philipp Chrszon) (fixed in rev 9374)\n\ndtmc\n\nmodule test\n    s : bool init false;\n\n    [] s => false -> (s' = true);\n    [] s          -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/simplify_implies.prism.props",
    "content": "// RESULT: 1.0\nP=? [ F (s) ]\n"
  },
  {
    "path": "prism-tests/bugfixes/simplify_implies.prism.props.args",
    "content": "-m\n-ex\n"
  },
  {
    "path": "prism-tests/bugfixes/stratgenreach.nm",
    "content": "// bugfix: -exportstrat for MDP using -sparse, missing restriction\n// to reachable state space when initializing strategy storage vector\n\n// NB: this test is temporarily not testing what it is supposed to,\n// since -exportstrat currently forces a switch to the explicit engine\n\nmdp\n\nmodule m \n  s: [0..2] init 0;\n\n  [a] s=0 -> 1/2:(s'=0) + 1/2:(s'=1);\n  [b] s=0 -> 1/3:(s'=2) + 2/3:(s'=1);\nendmodule\n"
  },
  {
    "path": "prism-tests/bugfixes/stratgenreach.nm.props",
    "content": "// RESULT: 1.0\nPmax=?[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/bugfixes/stratgenreach.nm.props.args",
    "content": "-sparse -exportstrat stratgenreach.nm.props.strat:states=false\n"
  },
  {
    "path": "prism-tests/bugfixes/stratgenreach.nm.props.strat",
    "content": "0=a\n"
  },
  {
    "path": "prism-tests/bugfixes/supersimple.pm",
    "content": "// A very very simple model, that can be used with multiple different tests\r\n// that do not depend on too much model structure\r\n\r\ndtmc\r\n\r\nmodule M\r\n\r\n\ts : [0..3] init 0;\r\n\t\r\n\t[] s=0 -> 0.6 : (s'=1) + 0.4 : (s'=2);\r\n\t[] s>0 -> true;\r\n\t\r\nendmodule\r\n\r\nrewards\r\n\ttrue : 1;\r\nendrewards\r\n\r\nlabel \"a\" = s=1;\r\nlabel \"b\" = s=2;\r\n"
  },
  {
    "path": "prism-tests/bugfixes/supersimple.pm.boundedltl.props",
    "content": "// Bug fix in svn rev 11036\n// (the first of these used to be mis-detected as timed LTL properties)\n\n// RESULT: true\nP>0.5 [ X F P>0 [ F<=4 \"a\" ] ]\n// RESULT: true\nP>=1 [ F<=1 P>0 [ X F \"a\" ] ]\n// RESULT: true\nP>0.5 [ F>=1 P>0 [ X F \"a\" ] ]\n\n// These ones *should* fail for now\n// since there is no support for timed LTL currently\n\n// RESULT: Error:not,supported\nP>0.5 [ X F P>0 [ X F<=4 \"a\" ] ]\n// RESULT: Error:not,supported\nP>0.5 [ X F<=1 P>0 [ X F \"a\" ] ]\n// RESULT: Error:not,supported\nP>0.5 [ X F P>0 [ X F<=1 \"a\" ] ]\n"
  },
  {
    "path": "prism-tests/bugfixes/supersimple.pm.boundedltl.props.args",
    "content": "-dtmc\n-ctmc\n-mdp\n"
  },
  {
    "path": "prism-tests/bugfixes/trafileinit.auto",
    "content": "-importmodel trafileinit.tra,lab -exportmodel trafileinit.tra,lab\n-importmodel trafileinit.tra,lab -exportmodel trafileinit.tra,lab -ex\n"
  },
  {
    "path": "prism-tests/bugfixes/trafileinit.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"p2win\" 3=\"done\" 4=\"p1win\"\n0: 2 3\n1: 0\n3: 3 4\n"
  },
  {
    "path": "prism-tests/bugfixes/trafileinit.tra",
    "content": "4 6 9\n0 0 0 1 p\n1 0 2 1 a21\n1 1 2 1 a22\n2 0 1 0.5 a11\n2 0 2 0.5 a11\n2 1 0 0.3 a12\n2 1 2 0.3 a12\n2 1 3 0.4 a12\n3 0 3 1 p\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-01.pm",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-01.pm.props",
    "content": "const int x = 5;\n\n// Is probability of throwing x > 0.1?\n// RESULT: true\nP>0.1 [ F s=7 & d=x ]\n\n// Probability of throwing 6?\n// RESULT: 1/6\nP=? [ F s=7 & d=6 ]\n\n// Probability of throwing x?\n// RESULT: 1/6\nP=? [ F s=7 & d=x ]\n\n// Expected number of coin flips to complete?\n// RESULT: 11/3\nR=? [ F s=7 ]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-02.pm",
    "content": "\r\ndtmc\r\n\r\nmodule dice\r\n    \r\n    s : [0..7] init 0;\r\n    d : [0..6] init 0;\r\n\r\n    [] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n    [] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n    [] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n    [] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n    [] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n    [] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n    [] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n    [] s=7 -> (s'=7);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-02.pm.props",
    "content": "const int x; // unused (Hubert Garavel)\n\n// RESULT : 1/6\nP=? [ F s=7 & d=1 ]\n\n// RESULT : 1/6\nP=? [ F s=7 & d=2 ]\n\n// RESULT : 1/6\nP=? [ F s=7 & d=3 ]\n\n// RESULT : 1/6\nP=? [ F s=7 & d=4 ]\n\n// RESULT : 1/6\nP=? [ F s=7 & d=5 ]\n\n// RESULT : 1/6\nP=? [ F s=7 & d=6 ]\n\n// RESULT : 1/6\nS=? [ s=7 & d=1 ]\n\n// RESULT : 1/6\nS=? [ s=7 & d=2 ]\n\n// RESULT : 1/6\nS=? [ s=7 & d=3 ]\n\n// RESULT : 1/6\nS=? [ s=7 & d=4 ]\n\n// RESULT : 1/6\nS=? [ s=7 & d=5 ]\n\n// RESULT : 1/6\nS=? [ s=7 & d=6 ]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-03.pm",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-03.pm.props",
    "content": "\n\n// Probability of throwing 1?\n// RESULT : 1/6\nS=? [s=7 & d=1 ]\n\n// Probability of throwing 2?\n// RESULT : 1/6\nS=? [s=7 & d=2 ]\n\n// Probability of throwing 3?\n// RESULT : 1/6\nS=? [s=7 & d=3 ]\n\n// Probability of throwing 4?\n// RESULT : 1/6\nS=? [s=7 & d=4 ]\n\n// Probability of throwing 5?\n// RESULT : 1/6\nS=? [s=7 & d=5 ]\n\n// Probability of throwing 6?\n// RESULT : 1/6\nS=? [s=7 & d=6 ]\n\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-04.pm",
    "content": "// Challenge 5 Model\r\n\r\ndtmc\r\n\r\nmodule dice\r\n\r\n\tx : [0..12] init 0;\r\n\r\n\t[] x=0 -> 0.5:(x'=1) + 0.5:(x'=2);\r\n\t[] x=1 -> 0.5:(x'=3) + 0.5:(x'=4);\r\n\t[] x=3 -> 0.5:(x'=1) + 0.5:(x'=7);\r\n\t[] x=7 -> (x'=7);\r\n\t[] x=4 -> 0.5:(x'=8) + 0.5:(x'=9);\r\n\t[] x=8 -> (x'=8);\r\n\t[] x=9 -> (x'=9);\r\n\r\n\t[] x=2 -> 0.5:(x'=5) + 0.5:(x'=6);\r\n\t[] x=5 -> 0.5:(x'=10) + 0.5:(x'=11);\r\n\t[] x=10 -> (x'=10);\r\n\t[] x=11 -> (x'=11);\r\n\t[] x=6 -> 0.5:(x'=2) + 0.5:(x'=12);\r\n\t[] x=12 -> (x'=12);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-04.pm.props",
    "content": "//Challenge 5 - Property\n\n// RESULT: true\nS<=0.166667 [ x=7 ] &\nS>=0.166665 [ x=7 ]\n&\nS<=0.166667 [ x=8 ] &\nS>=0.166665 [ x=8 ]\n&\nS<=0.166667 [ x=9 ] &\nS>=0.166665 [ x=9 ]\n&\nS<=0.166667 [ x=10 ] &\nS>=0.166665 [ x=10 ]\n&\nS<=0.166667 [ x=11 ] &\nS>=0.166665 [ x=11 ]\n&\nS<=0.166667 [ x=12 ] &\nS>=0.166665 [ x=12 ]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-05.pm",
    "content": "dtmc\r\n\r\nmodule DICE\r\n\ts : [0..12];\r\n[] s=0->0.5:(s'=1) + 0.5:(s'=2);\r\n[] s=1->0.5:(s'=3) + 0.5:(s'=4);\r\n[] s=2->0.5:(s'=5) + 0.5:(s'=6);\r\n[] s=3->0.5:(s'=1) + 0.5:(s'=7);\r\n[] s=4->0.5:(s'=8) + 0.5:(s'=9);\r\n[] s=5->0.5:(s'=10) + 0.5:(s'=11);\r\n[] s=6->0.5:(s'=12) + 0.5:(s'=2);\r\n\r\n[] s=7->(s'=7);\r\n[] s=8->(s'=8);\r\n[] s=9->(s'=9);\r\n[] s=10->(s'=10);\r\n[] s=11->(s'=11);\r\n[] s=12->(s'=12);\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-05.pm.props",
    "content": "\n// RESULT: 1/6\nP=? [ F s=7 ]\n\n// RESULT: 1/6\nP=? [ F s=8 ]\n\n// RESULT: 1/6\nP=? [ F s=9 ]\n\n// RESULT: 1/6\nP=? [ F s=10 ]\n\n// RESULT: 1/6\nP=? [ F s=11 ]\n\n// RESULT: 1/6\nP=? [ F s=12 ]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-06.pm",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\ts : [0..7] init 0;\r\n\tvalue : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (value'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (value'=2) + 0.5 : (s'=7) & (value'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (value'=4) + 0.5 : (s'=7) & (value'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (value'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-06.pm.props",
    "content": "const int x = 3;\r\n\r\n// RESULT : 1/6\r\nP=? [ F s=7 & value=x ]\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-07.pm",
    "content": "dtmc\r\n\r\nmodule dice\r\n\r\ns : [0..7] init 0;\r\nvalue : [0..6] init 0;\r\n\t\r\n[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (value'=1);\r\n[] s=4 -> 0.5 : (s'=7) & (value'=2) + 0.5 : (s'=7) & (value'=3);\r\n[] s=5 -> 0.5 : (s'=7) & (value'=4) + 0.5 : (s'=7) & (value'=5);\r\n[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (value'=6);\r\n[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-07.pm.props",
    "content": "\r\n// RESULT: 1/6\r\nS=? [ s=7 & value=1 ]\r\n\r\n// RESULT: 1/6\r\nS=? [ s=7 & value=2 ]\r\n\r\n// RESULT: 1/6\r\nS=? [ s=7 & value=3 ]\r\n\r\n// RESULT: 1/6\r\nS=? [ s=7 & value=4 ]\r\n\r\n// RESULT: 1/6\r\nS=? [ s=7 & value=5 ]\r\n\r\n// RESULT: 1/6\r\nS=? [ s=7 & value=6 ]\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-08.pm",
    "content": "module DICE\r\ns : [0..12];\r\n[] s=0->0.5:(s'=1) + 0.5:(s'=2);\r\n[] s=1->0.5:(s'=3) + 0.5:(s'=4);\r\n[] s=2->0.5:(s'=5) + 0.5:(s'=6);\r\n[] s=3->0.5:(s'=1) + 0.5:(s'=7);\r\n[] s=4->0.5:(s'=8) + 0.5:(s'=9);\r\n[] s=5->0.5:(s'=10) + 0.5:(s'=11);\r\n[] s=6->0.5:(s'=12) + 0.5:(s'=2);\r\n[] s=7->(s'=7);\r\n[] s=8->(s'=8);\r\n[] s=9->(s'=9);\r\n[] s=10->(s'=10);\r\n[] s=11->(s'=11);\r\n[] s=12->(s'=12);\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-08.pm.props",
    "content": "const int x = 4;\n\n// RESULT : 1/3\nPmin=? [ F s=x ]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-09.pm",
    "content": "// Question 3 of Applied Concurrency Theory Project 3\r\n\r\ndtmc\r\n\r\nconst double a = 0.01;\r\nconst double b = 0.05;\r\n\r\nmodule Generator\r\n\r\n  x : [0..1];\r\n\r\n[] true -> 0.5:(x'=0) + 0.5:(x'=1);\r\n\r\nendmodule\r\n\r\n\r\nmodule Line1\r\n\r\n  y : [0..1];\r\n  error_1 : bool;\r\n  error_last_1  : bool;\r\n\r\n  [] x=0 & error_1 -> (1-a):(y'=0) & (error_1'=false) & (error_last_1'=true)\r\n          + a:(y'=1) & (error_1'=true) & (error_last_1'=true);\r\n  [] x=0 & !error_1 -> (1-a):(y'=0) & (error_1'=false) & (error_last_1'=false)\r\n          + a:(y'=1) & (error_1'=true) & (error_last_1'=false);\r\n  [] x=1 & error_1 -> (1-b):(y'=1) & (error_1'=false) & (error_last_1'=true)\r\n          + b:(y'=0) & (error_1'=true) & (error_last_1'=true);\r\n  [] x=1 & !error_1 -> (1-b):(y'=1) & (error_1'=false) & (error_last_1'=false)\r\n          + b:(y'=0) & (error_1'=true) & (error_last_1'=false);\r\n\r\nendmodule\r\n\r\n\r\nmodule Line2\r\n\r\n  z : [0..1];\r\n  error_2 : bool;\r\n\r\n  [] y=0 -> (1-a):(z'=0) & (error_2'=false)\r\n          + a:(z'=1) & (error_2'=true);\r\n  [] y=1 -> (1-b):(z'=1) & (error_2'=false)\r\n          + b:(z'=0) & (error_2'=true);\r\n\r\nendmodule\r\n\r\n\r\ninit (x=0) & (error_1=false) & (error_last_1=false) & (error_2=false)  endinit\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-09.pm.props",
    "content": "\n// RESULT: 0.03000000042158528\n\"error_line_1\" : S=? [ error_1 {\"init\"}{min} ]\n\n// RESULT: 0.029200001350718534\n\"error_line_2\" : S=? [ error_2 {\"init\"}{min} ]\n\n// RESULT: 0.05740099996352296\n\"error_line_1xor2\" : S=? [ error_last_1 <=> !error_2 {\"init\"}{min} ]\n\n// RESULT: 0.058300499978873876\n\"error_line_1or2\" : S=? [ error_last_1 | error_2 {\"init\"}{min} ]\n\n// RESULT: 8.99500015350916E-4\n\"error_line_1and2\" : S=? [ error_last_1 & error_2 {\"init\"}{min} ]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-10.pm",
    "content": "\r\ndtmc\r\n\r\nconst double a = 0.01;\r\nconst double b = 0.05;\r\n\r\ninit\r\ntrue\r\nendinit\r\n\r\nmodule Channel\r\ns : [0..1];\r\n[] s=0 -> a : (s'=1) + 1-a : (s'=0);\r\n[] s=1 -> b : (s'=0) + 1-b : (s'=1);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-10.pm.props",
    "content": "\n// RESULT : 5/6\nS=? [s = 0 {\"init\"}{max}]\n\n// RESULT : 1/6\nS=? [s = 1 {\"init\"}{max}]\n\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-10.pm.props.args",
    "content": "-gaussseidel -e 1e-7\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-11.pm",
    "content": "dtmc\r\n\r\nconst double a = 0.01;\r\nconst double b = 0.05;\r\n\r\n// init \r\n// true \r\n// endinit\r\n\r\nmodule Sender\r\nx : [0..1] init 0; \r\n[] true -> 0.5 : (x'=0) + 0.5 : (x'=1);\r\nendmodule\r\n\r\nmodule Channel1\r\ny : [0..1] init 0;\r\n[] (x=0) -> a:(y'=1) + 1-a : (y'=0);\r\n[] (x=1) -> b:(y'=0) + 1-b : (y'=1); \r\nendmodule\r\n\r\nmodule Channel2\r\nz : [0..1] init 0;\r\n[] (y=0) -> a:(z'=1) + 1-a : (z'=0);\r\n[] (y=1) -> b:(z'=0) + 1-b : (z'=1); \r\nendmodule\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-11.pm.props",
    "content": "\n// RESULT : 0.5\nS=?[x = 0]\n\n// RESULT : 0.265\nS=?[x != y]\n\n// RESULT : 0.38955\nS=?[x != z]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-12.pm",
    "content": "dtmc\r\n\r\nmodule chan1\r\n\ts : [0..1];\r\n\t[] s=0 -> 0.99 : (s'=0) + 0.01 : (s'=1);\r\n\t[] s=1 -> 0.05 : (s'=0) + 0.95 : (s'=1);\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-12.pm.props",
    "content": "\n// RESULT : 5/6\nS=? [s=0]\n\n// RESULT : 1/6\nS=? [s=1]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-12.pm.props.args",
    "content": "-gaussseidel -e 1e-7\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-13.pm",
    "content": "dtmc\r\n\r\nmodule GENERATOR\r\n\tx : [0..1] init 0;\r\n\t[] x=0 -> 0.5 : (x'=0) + 0.5 : (x'=1);\r\n\t[] x=1 -> 0.5 : (x'=0) + 0.5 : (x'=1);\r\nendmodule\r\n\r\nmodule LINE1\r\n\ty : [0..1];\r\n\t[] x=0 -> 0.99 : (y'=0) + 0.01 : (y'=1);\r\n\t[] x=1 -> 0.05 : (y'=0) + 0.95 : (y'=1);\r\nendmodule\r\n\r\nmodule LINE2\r\n\tz : [0..1];\r\n\t[] y=0 -> (z'=0);\r\n\t[] y=1 -> (z'=1);\r\nendmodule"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-13.pm.props",
    "content": "\n// RESULT : 0.265\nS=? [ x!=y ]\n\n// RESULT : 0.194375\nS=? [ y!=z ]\n\n// RESULT : 0.2265625\nS=? [x!=z & x!=y]\n\n// RESULT : 0.0384375\nS=? [x=z & x!=y]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-14.pm",
    "content": "dtmc\r\n\r\nconst double a = 0.01;\r\nconst double b = 0.05;\r\n\r\ninit\r\n\ts=0 | s=1\r\nendinit\r\n\r\nmodule chan\r\ns : [0..1];\r\n\r\n[] s=0 -> 1-a: (s'=0)\r\n\t+ a: (s'=1);\r\n[] s=1 -> 1-b: (s'=1)\r\n\t+ b: (s'=0);\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-14.pm.props",
    "content": "// RESULT : 5/6\nS=? [s=0 {\"init\"}{min}]\n\n// RESULT : 1/6\nS=? [s=1 {\"init\"}{min}]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-14.pm.props.args",
    "content": "-gaussseidel -e 1e-7\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-15.pm",
    "content": "\r\ndtmc\r\n\r\nconst double a = 0.01;\r\nconst double b = 0.05;\r\n\r\ninit\r\n        (x=0)\r\nendinit\r\n\r\nmodule generator\r\nx : [0..1];\r\n\r\n[] x=0 | x=1 -> 1/2: (x'=0)\r\n\t\t+ 1/2: (x'=1);\r\nendmodule\r\n\r\nmodule line1\r\ny : [0..1];\r\n\r\n[] x=0 -> 1-a: (y'=0)\r\n        + a: (y'=1);\r\n[] x=1 -> 1-b: (y'=1)\r\n        + b: (y'=0);\r\nendmodule\r\n\r\nmodule line2\r\nz : [0..1];\r\n\r\n[] y=0 -> 1-a: (z'=0)\r\n        + a: (z'=1);\r\n[] y=1 -> 1-b: (z'=1)\r\n        + b: (z'=0);\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-15.pm.props",
    "content": "// RESULT : 0.26499994880454214\nS=? [x != y {\"init\"}{min}]\n\n// RESULT : 0.2119125122358965\nS=? [y != z {\"init\"}{min}]\n\n// RESULT : 0.3895499480066543\nS=? [(x != y & y = z) | (x = y & y != z) {\"init\"}{min}]\n\n// RESULT : 0.04368125651689213\nS=? [x != y & y != z {\"init\"}{min}]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-16.pm",
    "content": "dtmc \r\n\r\nconst double a = 0.01;\r\nconst double b = 0.05;\r\n\r\n\r\nmodule chan1\r\n    s : [0..1];\r\n\r\n    [] s=0 -> 1-a : (s'=0) + a : (s'=1);\r\n    [] s=1 -> 1-b : (s'=1) + b : (s'=0);\r\n\r\nendmodule\r\n\r\ninit s=0 | s=1 endinit\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-16.pm.props",
    "content": "\n// RESULT : 5/6\nS=? [s=0 {\"init\"}{min}]\n\n// RESULT : 1/6\nS=? [s=1 {\"init\"}{min}]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-16.pm.props.args",
    "content": "-gaussseidel -e 1e-7\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-17.pm",
    "content": "dtmc\r\n\r\nconst double a = 0.01;\r\nconst double b = 0.05;\r\n\r\nmodule generator\r\n    x : [0..1] init 0;\r\n    i : bool init false;\r\n\r\n    [] x=0 -> 0.5 : (x'=0) & (i'=true) + 0.5 : (x'=1) & (i'=true);\r\n    [] x=1 -> 0.5 : (x'=0) & (i'=true) + 0.5 : (x'=1) & (i'=true);\r\nendmodule\r\n\r\nmodule line1\r\n    \r\n    y : [0..1];\r\n    e1 : bool init false;\r\n    ee1 : bool init false;\r\n\r\n    [] x=0 -> 1-a : (y'=0) & (e1'=false) & (ee1'=e1) + a : (y'=1) & (e1'=true) & (ee1'=e1);\r\n    [] x=1 -> 1-b : (y'=1) & (e1'=false) & (ee1'=e1) + b : (y'=0) & (e1'=true) & (ee1'=e1);\r\n\r\nendmodule\r\n\r\nmodule line2\r\n    \r\n    z : [0..1];\r\n    e2 : bool init false;\r\n\r\n    [] y=0 & i=true -> 1-a : (z'=0) & (e2'=false) + a : (z'=1) & (e2'=true);\r\n    [] y=1 & i=true -> 1-b : (z'=1) & (e2'=false) + b : (z'=0) & (e2'=true);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-17.pm.props",
    "content": "\n// RESULT : 0.03\nS=? [e1]\n\n// RESULT : 0.0292\nS=? [e2]\n\n// RESULT : 0.057401\nS=? [(!ee1 & e2)|(ee1&!e2)]\n\n// RESULT : 8.995E-4\nS=? [(ee1 & e2)]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-18.pm",
    "content": "dtmc\r\n\r\nmodule chan1\r\n\t// local state\r\n\ts : [0..1];\r\n\t\r\n\t[] s=0 -> 0.01 : (s'=1) + 0.99 : (s'=0);\r\n\t[] s=1 -> 0.05 : (s'=0) + 0.95 : (s'=1);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-18.pm.props",
    "content": "\n\n// Steady state probability of being in State 0\n// RESULT : 5/6\nS=? [s=0 ]\n\n// Steady state probability of being in State 1\n// RESULT : 1/6\nS=? [s=1 ]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-18.pm.props.args",
    "content": "-gaussseidel -e 1e-7\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-19.pm",
    "content": "dtmc\r\n\r\nconst double a = 0.23;\r\n\r\nconst double b = 0.41;\r\n\r\n// init \r\n// true \r\n// endinit\r\n\r\nmodule Sender\r\nx : [0..1] init 0; // init 0;\r\n[] true -> 0.5 : (x'=0) + 0.5 : (x'=1);\r\nendmodule\r\n\r\nmodule Channel1\r\ny : [0..1] init 0;\r\n[] (y=0) & (x=0) -> a:(y'=1) + 1-a : (y'=0);\r\n[] (y=1) & (x=1) -> b:(y'=0) + 1-b : (y'=1); \r\nendmodule\r\n\r\nmodule Channel2\r\nz : [0..1] init 0;\r\n[] (z=0) & (y=0) -> a:(z'=1) + 1-a : (z'=0);\r\n[] (z=1) & (y=1) -> b:(z'=0) + 1-b : (z'=1); \r\nendmodule\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-19.pm.props",
    "content": "\n// RESULT : ~0.530487009959398\nS=? [x = 0]\n\n// RESULT : ~0.5220657596380086\nS=? [x = y]\n\n// RESULT : ~0.3406646324774578\nS=? [y = z]\n\n// RESULT : ~0.4177711482230605\nS=? [x = z]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-19.pm.props.args",
    "content": "-gaussseidel\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-20.pm",
    "content": "dtmc\r\n\r\nmodule Generator\r\n\t// local state\r\n\tx : [0..1] init 0;\t\r\n\t[] x=0 -> 0.5 : (x'=1) + 0.5 : (x'=0);\r\n\t[] x=1 -> 0.5 : (x'=1) + 0.5 : (x'=0);\r\nendmodule\r\n\r\n\r\nmodule Line1\r\n\t// local state\r\n\ty : [0..1];\r\n\t//[] x=0 -> 1 : (y'=0);\r\n\t//[] x=1 -> 1 : (y'=1);\r\n\t[] x=0 -> 0.01 : (y'=1) + 0.99 : (y'=0);\r\n\t[] x=1 -> 0.05 : (y'=0) + 0.95 : (y'=1);\r\nendmodule\r\n\r\n\r\n\r\nmodule Line2\r\n\t// local state\r\n\tz : [0..1];\r\n\t//[] y=0 -> 1 : (z'=0);\r\n\t//[] y=1 -> 1 : (z'=1);\r\n\t[] y=0 -> 0.01 : (z'=1) + 0.99 : (z'=0);\r\n\t[] y=1 -> 0.05 : (z'=0) + 0.95 : (z'=1);\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-20.pm.props",
    "content": "//Error after line 1\n// RESULT : 0.265\nS=? [ x!=y ]\n\n//between the output of line1 and line 2\n// RESULT : 0.2119125\nS=? [ y!=z ]\n\n// after l1 + l2 with single transmission error either in l1 or l2\n// RESULT : 0.22131875\nS=? [x!=z & x!=y]\n\n//after l1+l2 with double transmission error in line1 and line 2\n// RESULT : 0.04368125\nS=? [x=z & x!=y]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-21.pm",
    "content": "//Project 3, Question 1\r\n\r\ndtmc\r\n\r\n\tconst double a = 0.01;\r\n\tconst double b = 0.05;\r\n\r\nmodule chan1\r\n\r\n\tx : [0..1];\r\n\r\n\t[] x=0 -> a:(x'=1) + 1-a:(x'=0);\r\n\t[] x=1 -> b:(x'=0) + 1-b:(x'=1);\r\n\r\nendmodule\r\n\r\ninit x=0 | x=1 endinit\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-21.pm.props",
    "content": "//Project 3, Question 2\n\n// RESULT : 5/6\nS=? [ x=0 {\"init\"}{min} ];\n\n// RESULT : 1/6\nS=? [ x=1 {\"init\"}{min} ];\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-21.pm.props.args",
    "content": "-gaussseidel -e 1e-7\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-22.pm",
    "content": "//Project 3, Question 3\r\n\r\ndtmc\r\n\r\n\tconst double a = 0.01;\r\n\tconst double b = 0.05;\r\n\r\nmodule Generator\r\n\tx:[0..1] init 0;\r\n\r\n\t[]true -> 0.5:(x'=0) + 0.5:(x'=1);\r\nendmodule\r\n\r\nmodule Line1\r\n\ty:[0..1];\r\n\terror1prev:bool init false;\r\n\terror1:bool init false;\r\n\tassigned_y:bool init false;\r\n\t\r\n\t[]x=0 -> a:(y'=1) & (error1prev'=error1) & (error1'=true) & (assigned_y'=true) + 1-a:(y'=0) & (error1prev'=error1) & (error1'=false) & (assigned_y'=true);\r\n\t[]x=1 -> b:(y'=0) & (error1prev'=error1) & (error1'=true) & (assigned_y'=true) + 1-b:(y'=1) & (error1prev'=error1) & (error1'=false) & (assigned_y'=true);\r\n\r\nendmodule\r\n\r\nmodule Line2\r\n\tz:[0..1];\r\n\terror2prev:bool init false;\r\n\terror2:bool init false;\r\n\t\r\n\t[]assigned_y & y=0 -> a:(z'=1) & (error2prev'=error2) & (error2'=true) + 1-a:(z'=0) & (error2prev'=error2) & (error2'=false);\r\n\t[]assigned_y & y=1 -> b:(z'=0) & (error2prev'=error2) & (error2'=true) + 1-b:(z'=1) & (error2prev'=error2) & (error2'=false);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-22.pm.props",
    "content": "//Project 3, Question 4\n\n// RESULT : 0.03\nS=? [ error1 ]\n\n// RESULT : 0.0292\nS=? [ error2 ]\n\n// RESULT : 0.057401\nS=? [ (!error1prev & error2) | (error1prev & !error2) ]\n\n// RESULT : 8.995E-4\nS=? [ error1prev & error2 ]\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-23.pm",
    "content": "dtmc\r\n\r\nmodule Sender\r\nx : [0..1] init 0; \r\n[] true -> 0.5 : (x'=0) + 0.5 : (x'=1);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-23.pm.props",
    "content": "\n// RESULT : 0.5\nS=? [x = 0]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-24.pm",
    "content": "dtmc\r\n\r\nmodule Sender\r\nx : [0..1] init 0; \r\n[] x = 0 -> 1 : (x'=1);\r\n[] x = 1 -> 1 : (x'=0);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-24.pm.props",
    "content": "\n// RESULT : 0.5\nS=? [x = 1]\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-25.pm",
    "content": "dtmc\r\n\r\nconst double a = 0.01;\r\nconst double b = 0.05;\r\n\r\ninit \r\ntrue\r\nendinit\r\n\r\nmodule Channel\r\ns : [0..1];\r\n[] s=0 -> a : (s'=1) + 1-a : (s'=0);\r\n[] s=1 -> b : (s'=0) + 1-b : (s'=1); \r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-25.pm.props",
    "content": "\n// RESULT : 5/6\nS=? [s = 0 {\"init\"}{min}]\n\n// RESULT : 1/6\nS=? [s = 1 {\"init\"}{min}]\n\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-25.pm.props.args",
    "content": "-gaussseidel -e 1e-7\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-26.pm",
    "content": "dtmc\r\n\r\nconst double a = 0.23;\r\n\r\nconst double b = 0.41;\r\n\r\n// init \r\n// true \r\n// endinit\r\n\r\nglobal x : [0..1] init 0; // init 0;\r\nglobal y : [0..1] init 0;\r\nglobal z : [0..1] init 0;\r\n\r\nmodule Sender\r\n[] true -> 0.5 : (x'=0) + 0.5 : (x'=1);\r\nendmodule\r\n\r\n// module Sender\r\n// [] true -> 0.5 : (y'=0) + 0.5 : (y'=1);\r\n// endmodule\r\n\r\nmodule Channel1\r\ns : [0..1] init 0;\r\n[] (s=0) & (x=0) -> a:(s'=1)&(y'=1) + 1-a : (s'=0)&(y'=0);\r\n[] (s=1) & (x=1) -> b:(s'=0)&(y'=0) + 1-b : (s'=1)&(y'=1); \r\nendmodule\r\n\r\nmodule Channel2\r\nt : [0..1] init 0;\r\n[] (t=0) & (y=0) -> a:(t'=1)&(z'=1) + 1-a : (t'=0)&(z'=0);\r\n[] (t=1) & (y=1) -> b:(t'=0)&(z'=0) + 1-b : (t'=1)&(z'=1); \r\nendmodule\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-26.pm.props",
    "content": "\n// long run probability that s = 0\n// RESULT: ~0.6209277663961226\nS=? [s = 0]\n\n// = b / (a+b)\n\n\n// long run probability that s = 1\n// RESULT: ~0.3790722336038772\nS=? [s = 1]\n\n// = a / (a+b)\n\n\n"
  },
  {
    "path": "prism-tests/contrib/garavel/HG-26.pm.props.args",
    "content": "-gaussseidel\n"
  },
  {
    "path": "prism-tests/contrib/garavel/NOTES.txt",
    "content": "Some tests contributed by Hubert Garavel.\r\n(Also by Alexander Graf-Brioll and their students)\r\nDTMC examples + variations on the dice example.\r\nDerived from the \"Applied Concurrency Theory\" lecture given in Saarland.\r\n"
  },
  {
    "path": "prism-tests/example.nm",
    "content": "// Tiny MDP example for example test\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\ns:[0..3];\r\n\r\n[a] s=0 -> 1:(s'=1);\r\n[b] s=1 -> 0.7:(s'=0) + 0.3:(s'=1);\r\n[c] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n[a] s=2 -> 1:(s'=2);\r\n[a] s=3 -> 1:(s'=3);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/example.nm.props",
    "content": "// Example properties to illustrate regression tests\n\n// RESULT: 0.5\nPmax=? [ F s=2 ];\n\n// RESULT: true\nP<0.6 [ F s=2 ];\n\n// RESULT: 2\nceil(Pmax=? [ F s=2 ]) + 1;\n\n// RESULT: Error\nPmax=? [ F<=(-1) s=2 ];\n"
  },
  {
    "path": "prism-tests/functionality/compute/dtmc.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/compute/dtmc.prism.auto",
    "content": "-tr 5 -exporttransient dtmc.prism.transient5.txt -h\n-tr 5 -exporttransient dtmc.prism.transient5.txt -ex\n-ss -exportsteadystate dtmc.prism.steadystate.txt -h\n-ss -exportsteadystate dtmc.prism.steadystate.txt -ex\n\n"
  },
  {
    "path": "prism-tests/functionality/compute/dtmc.prism.steadystate.txt",
    "content": "0.0\n0.0\n0.0\n0.0\n0.0\n0.0\n0.0\n0.16666650772094727\n0.16666650772094727\n0.16666650772094727\n0.16666650772094727\n0.16666650772094727\n0.16666650772094727\n"
  },
  {
    "path": "prism-tests/functionality/compute/dtmc.prism.transient5.txt",
    "content": "0=0.0\n1=0.03125\n2=0.03125\n3=0.0\n4=0.0\n5=0.0\n6=0.0\n7=0.15625\n8=0.15625\n9=0.15625\n10=0.15625\n11=0.15625\n12=0.15625\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm",
    "content": "// Workstation cluster [HHK00]\r\n// dxp/gxn 11/01/00\r\n\r\nctmc\r\n\r\nconst int N; // Number of workstations in each cluster\r\nconst int left_mx = N; // Number of work stations in left cluster\r\nconst int right_mx = N; // Number of work stations in right cluster\r\n\r\n// Failure rates\r\nconst double ws_fail = 1/500; // Single workstation: average time to fail = 500 hrs\r\nconst double switch_fail = 1/4000; // Switch: average time to fail = 4000 hrs\r\nconst double line_fail = 1/5000; // Backbone: average time to fail = 5000 hrs\r\n\r\n// Left cluster\r\nmodule Left \r\n\t\r\n\tleft_n : [0..left_mx] init left_mx; // Number of workstations operational\r\n\tleft : bool; // Being repaired?\r\n\t\r\n\t[startLeft] !left & (left_n<left_mx) -> 1 : (left'=true);\r\n\t[repairLeft] left & (left_n<left_mx) -> 1 : (left'=false) & (left_n'=left_n+1);\r\n\t[] (left_n>0) -> ws_fail*left_n : (left_n'=left_n-1);\r\n\t\r\nendmodule\r\n\r\n// Right cluster\r\nmodule Right = Left[left_n=right_n,\r\n                    left=right,\r\n                    left_mx=right_mx,\r\n                    startLeft=startRight,\r\n                    repairLeft=repairRight ]\r\nendmodule\r\n\r\n// Repair unit\r\nmodule Repairman\r\n\t\r\n\tr : bool; // Repairing?\r\n\t\r\n\t[startLeft]    !r -> 10 : (r'=true); // Inspect Left \r\n\t[startRight]   !r -> 10 : (r'=true); // Inspect Right \r\n\t[startToLeft]  !r -> 10 : (r'=true); // Inspect ToLeft\r\n\t[startToRight] !r -> 10 : (r'=true); // Inspect ToRight \r\n\t[startLine]    !r -> 10 : (r'=true); // Inspect Line \r\n\t\r\n\t[repairLeft]    r -> 2     : (r'=false); // Repair Left \r\n\t[repairRight]   r -> 2     : (r'=false); // Repair Right\r\n\t[repairToLeft]  r -> 0.25  : (r'=false); // Repair ToLeft\r\n\t[repairToRight] r -> 0.25  : (r'=false); // Repair ToRight\r\n\t[repairLine]    r -> 0.125 : (r'=false); // Repair Line\r\n\t\r\nendmodule\r\n\r\n// Line/backbone\r\nmodule Line \r\n\t\r\n\tline :   bool; // Being repaired?\r\n\tline_n : bool init true; // Working?\r\n\t\r\n\t[startLine] !line & !line_n -> 1 : (line'=true);\r\n\t[repairLine] line & !line_n -> 1 : (line'=false) & (line_n'=true);\r\n\t[] line_n -> line_fail : (line_n'=false);\r\n\t\r\nendmodule\r\n\r\n// Left switch\r\nmodule ToLeft = Line[line=toleft,\r\n                     line_n=toleft_n,\r\n                     line_fail=switch_fail,\r\n                     startLine=startToLeft,\r\n                     repairLine=repairToLeft ]\r\nendmodule\r\n\r\n// Right switch\r\nmodule ToRight = Line[line=toright,\r\n                      line_n=toright_n,\r\n                      line_fail=switch_fail,\r\n                      startLine=startToRight,\r\n                      repairLine=repairToRight ]\r\nendmodule\r\n\r\n// Formulas + labels\r\n\r\n// Minimum QoS requires 3/4 connected workstations operational\r\nconst int k = floor(0.75*N);\r\n// left_operational_i : left_n>=i & toleft_n\r\n// right_operational_i : right_n>=i & toright_n\r\n// operational_i : (left_n+right_n)>=i & toleft_n & line_n & toright_n\r\n// minimum_k : left_operational_k | right_operational_k | operational_k\r\nformula minimum = (left_n>=k & toleft_n) | \r\n                  (right_n>=k & toright_n) | \r\n                  ((left_n+right_n)>=k & toleft_n & line_n & toright_n);\r\nlabel \"minimum\" = (left_n>=k & toleft_n) | (right_n>=k & toright_n) | ((left_n+right_n)>=k & toleft_n & line_n & toright_n);\r\n// premium = minimum_N\r\nlabel \"premium\" = (left_n>=left_mx & toleft_n) | (right_n>=right_mx & toright_n) | ((left_n+right_n)>=left_mx & toleft_n & line_n & toright_n);\r\n\r\n// Reward structures\r\n\r\n// Percentage of operational workstations stations\r\nrewards \"percent_op\"\r\n\ttrue : 100*(left_n+right_n)/(2*N);\r\nendrewards\r\n\r\n// Time that the system is not delivering at least minimum QoS\r\nrewards \"time_not_min\"\r\n\t!minimum : 1; \r\nendrewards\r\n\r\n// Number of repairs\r\nrewards \"num_repairs\"\r\n\t[repairLeft]    true : 1;\r\n\t[repairRight]   true : 1;\r\n\t[repairToLeft]  true : 1;\r\n\t[repairToRight] true : 1;\r\n\t[repairLine]    true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.args",
    "content": "-const N=2\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"minimum\" 3=\"premium\"\n29: 2\n31: 2\n33: 2\n35: 2\n39: 2\n43: 2\n45: 2\n47: 2\n49: 2\n51: 2\n53: 2\n55: 2\n57: 2 3\n59: 2 3\n61: 2 3\n63: 2 3\n67: 2 3\n71: 2 3\n73: 2 3\n75: 2 3\n85: 2\n87: 2\n89: 2\n91: 2\n93: 2 3\n95: 2 3\n97: 2 3\n99: 2 3\n102: 2\n103: 2\n106: 2\n107: 2\n109: 2\n113: 2\n118: 2\n119: 2\n122: 2\n123: 2\n126: 2\n127: 2\n129: 2\n130: 2\n131: 2\n133: 2\n134: 2\n135: 2 3\n137: 2\n139: 2\n141: 2\n143: 2\n145: 2\n146: 2\n147: 2\n149: 2\n150: 2\n151: 2\n153: 2\n154: 2\n155: 2 3\n157: 2 3\n158: 2\n159: 2 3\n161: 2 3\n162: 2\n163: 2 3\n165: 2\n167: 2 3\n169: 2\n171: 2 3\n173: 2 3\n174: 2\n175: 2 3\n178: 2\n179: 2\n182: 2\n183: 2\n185: 2\n186: 2\n187: 2\n189: 2\n190: 2\n191: 2 3\n193: 2 3\n194: 2\n195: 2 3\n197: 2 3\n198: 2\n199: 2 3\n202: 2 3\n203: 2 3\n206: 2 3\n207: 2 3\n209: 2 3\n213: 2 3\n218: 2 3\n219: 2 3\n222: 2 3\n223: 2 3\n226: 2 3\n227: 2 3\n229: 2\n230: 2 3\n231: 2 3\n233: 2\n234: 2 3\n235: 2 3\n237: 2 3\n239: 2\n241: 2 3\n243: 2\n245: 2\n246: 2 3\n247: 2 3\n249: 2\n250: 2 3\n251: 2 3\n253: 2\n254: 2 3\n255: 2 3\n257: 2 3\n258: 2 3\n259: 2 3\n261: 2 3\n262: 2 3\n263: 0 2 3\n265: 2 3\n267: 2 3\n269: 2 3\n271: 2 3\n273: 2 3\n274: 2 3\n275: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact.sta",
    "content": "(left_n,left,right_n,right,r,line,line_n,toleft,toleft_n,toright,toright_n)\n0:(0,false,0,false,false,false,false,false,false,false,false)\n1:(0,false,0,false,false,false,false,false,false,false,true)\n2:(0,false,0,false,false,false,false,false,true,false,false)\n3:(0,false,0,false,false,false,false,false,true,false,true)\n4:(0,false,0,false,false,false,true,false,false,false,false)\n5:(0,false,0,false,false,false,true,false,false,false,true)\n6:(0,false,0,false,false,false,true,false,true,false,false)\n7:(0,false,0,false,false,false,true,false,true,false,true)\n8:(0,false,0,false,true,false,false,false,false,true,false)\n9:(0,false,0,false,true,false,false,false,true,true,false)\n10:(0,false,0,false,true,false,false,true,false,false,false)\n11:(0,false,0,false,true,false,false,true,false,false,true)\n12:(0,false,0,false,true,false,true,false,false,true,false)\n13:(0,false,0,false,true,false,true,false,true,true,false)\n14:(0,false,0,false,true,false,true,true,false,false,false)\n15:(0,false,0,false,true,false,true,true,false,false,true)\n16:(0,false,0,false,true,true,false,false,false,false,false)\n17:(0,false,0,false,true,true,false,false,false,false,true)\n18:(0,false,0,false,true,true,false,false,true,false,false)\n19:(0,false,0,false,true,true,false,false,true,false,true)\n20:(0,false,0,true,true,false,false,false,false,false,false)\n21:(0,false,0,true,true,false,false,false,false,false,true)\n22:(0,false,0,true,true,false,false,false,true,false,false)\n23:(0,false,0,true,true,false,false,false,true,false,true)\n24:(0,false,0,true,true,false,true,false,false,false,false)\n25:(0,false,0,true,true,false,true,false,false,false,true)\n26:(0,false,0,true,true,false,true,false,true,false,false)\n27:(0,false,0,true,true,false,true,false,true,false,true)\n28:(0,false,1,false,false,false,false,false,false,false,false)\n29:(0,false,1,false,false,false,false,false,false,false,true)\n30:(0,false,1,false,false,false,false,false,true,false,false)\n31:(0,false,1,false,false,false,false,false,true,false,true)\n32:(0,false,1,false,false,false,true,false,false,false,false)\n33:(0,false,1,false,false,false,true,false,false,false,true)\n34:(0,false,1,false,false,false,true,false,true,false,false)\n35:(0,false,1,false,false,false,true,false,true,false,true)\n36:(0,false,1,false,true,false,false,false,false,true,false)\n37:(0,false,1,false,true,false,false,false,true,true,false)\n38:(0,false,1,false,true,false,false,true,false,false,false)\n39:(0,false,1,false,true,false,false,true,false,false,true)\n40:(0,false,1,false,true,false,true,false,false,true,false)\n41:(0,false,1,false,true,false,true,false,true,true,false)\n42:(0,false,1,false,true,false,true,true,false,false,false)\n43:(0,false,1,false,true,false,true,true,false,false,true)\n44:(0,false,1,false,true,true,false,false,false,false,false)\n45:(0,false,1,false,true,true,false,false,false,false,true)\n46:(0,false,1,false,true,true,false,false,true,false,false)\n47:(0,false,1,false,true,true,false,false,true,false,true)\n48:(0,false,1,true,true,false,false,false,false,false,false)\n49:(0,false,1,true,true,false,false,false,false,false,true)\n50:(0,false,1,true,true,false,false,false,true,false,false)\n51:(0,false,1,true,true,false,false,false,true,false,true)\n52:(0,false,1,true,true,false,true,false,false,false,false)\n53:(0,false,1,true,true,false,true,false,false,false,true)\n54:(0,false,1,true,true,false,true,false,true,false,false)\n55:(0,false,1,true,true,false,true,false,true,false,true)\n56:(0,false,2,false,false,false,false,false,false,false,false)\n57:(0,false,2,false,false,false,false,false,false,false,true)\n58:(0,false,2,false,false,false,false,false,true,false,false)\n59:(0,false,2,false,false,false,false,false,true,false,true)\n60:(0,false,2,false,false,false,true,false,false,false,false)\n61:(0,false,2,false,false,false,true,false,false,false,true)\n62:(0,false,2,false,false,false,true,false,true,false,false)\n63:(0,false,2,false,false,false,true,false,true,false,true)\n64:(0,false,2,false,true,false,false,false,false,true,false)\n65:(0,false,2,false,true,false,false,false,true,true,false)\n66:(0,false,2,false,true,false,false,true,false,false,false)\n67:(0,false,2,false,true,false,false,true,false,false,true)\n68:(0,false,2,false,true,false,true,false,false,true,false)\n69:(0,false,2,false,true,false,true,false,true,true,false)\n70:(0,false,2,false,true,false,true,true,false,false,false)\n71:(0,false,2,false,true,false,true,true,false,false,true)\n72:(0,false,2,false,true,true,false,false,false,false,false)\n73:(0,false,2,false,true,true,false,false,false,false,true)\n74:(0,false,2,false,true,true,false,false,true,false,false)\n75:(0,false,2,false,true,true,false,false,true,false,true)\n76:(0,true,0,false,true,false,false,false,false,false,false)\n77:(0,true,0,false,true,false,false,false,false,false,true)\n78:(0,true,0,false,true,false,false,false,true,false,false)\n79:(0,true,0,false,true,false,false,false,true,false,true)\n80:(0,true,0,false,true,false,true,false,false,false,false)\n81:(0,true,0,false,true,false,true,false,false,false,true)\n82:(0,true,0,false,true,false,true,false,true,false,false)\n83:(0,true,0,false,true,false,true,false,true,false,true)\n84:(0,true,1,false,true,false,false,false,false,false,false)\n85:(0,true,1,false,true,false,false,false,false,false,true)\n86:(0,true,1,false,true,false,false,false,true,false,false)\n87:(0,true,1,false,true,false,false,false,true,false,true)\n88:(0,true,1,false,true,false,true,false,false,false,false)\n89:(0,true,1,false,true,false,true,false,false,false,true)\n90:(0,true,1,false,true,false,true,false,true,false,false)\n91:(0,true,1,false,true,false,true,false,true,false,true)\n92:(0,true,2,false,true,false,false,false,false,false,false)\n93:(0,true,2,false,true,false,false,false,false,false,true)\n94:(0,true,2,false,true,false,false,false,true,false,false)\n95:(0,true,2,false,true,false,false,false,true,false,true)\n96:(0,true,2,false,true,false,true,false,false,false,false)\n97:(0,true,2,false,true,false,true,false,false,false,true)\n98:(0,true,2,false,true,false,true,false,true,false,false)\n99:(0,true,2,false,true,false,true,false,true,false,true)\n100:(1,false,0,false,false,false,false,false,false,false,false)\n101:(1,false,0,false,false,false,false,false,false,false,true)\n102:(1,false,0,false,false,false,false,false,true,false,false)\n103:(1,false,0,false,false,false,false,false,true,false,true)\n104:(1,false,0,false,false,false,true,false,false,false,false)\n105:(1,false,0,false,false,false,true,false,false,false,true)\n106:(1,false,0,false,false,false,true,false,true,false,false)\n107:(1,false,0,false,false,false,true,false,true,false,true)\n108:(1,false,0,false,true,false,false,false,false,true,false)\n109:(1,false,0,false,true,false,false,false,true,true,false)\n110:(1,false,0,false,true,false,false,true,false,false,false)\n111:(1,false,0,false,true,false,false,true,false,false,true)\n112:(1,false,0,false,true,false,true,false,false,true,false)\n113:(1,false,0,false,true,false,true,false,true,true,false)\n114:(1,false,0,false,true,false,true,true,false,false,false)\n115:(1,false,0,false,true,false,true,true,false,false,true)\n116:(1,false,0,false,true,true,false,false,false,false,false)\n117:(1,false,0,false,true,true,false,false,false,false,true)\n118:(1,false,0,false,true,true,false,false,true,false,false)\n119:(1,false,0,false,true,true,false,false,true,false,true)\n120:(1,false,0,true,true,false,false,false,false,false,false)\n121:(1,false,0,true,true,false,false,false,false,false,true)\n122:(1,false,0,true,true,false,false,false,true,false,false)\n123:(1,false,0,true,true,false,false,false,true,false,true)\n124:(1,false,0,true,true,false,true,false,false,false,false)\n125:(1,false,0,true,true,false,true,false,false,false,true)\n126:(1,false,0,true,true,false,true,false,true,false,false)\n127:(1,false,0,true,true,false,true,false,true,false,true)\n128:(1,false,1,false,false,false,false,false,false,false,false)\n129:(1,false,1,false,false,false,false,false,false,false,true)\n130:(1,false,1,false,false,false,false,false,true,false,false)\n131:(1,false,1,false,false,false,false,false,true,false,true)\n132:(1,false,1,false,false,false,true,false,false,false,false)\n133:(1,false,1,false,false,false,true,false,false,false,true)\n134:(1,false,1,false,false,false,true,false,true,false,false)\n135:(1,false,1,false,false,false,true,false,true,false,true)\n136:(1,false,1,false,true,false,false,false,false,true,false)\n137:(1,false,1,false,true,false,false,false,true,true,false)\n138:(1,false,1,false,true,false,false,true,false,false,false)\n139:(1,false,1,false,true,false,false,true,false,false,true)\n140:(1,false,1,false,true,false,true,false,false,true,false)\n141:(1,false,1,false,true,false,true,false,true,true,false)\n142:(1,false,1,false,true,false,true,true,false,false,false)\n143:(1,false,1,false,true,false,true,true,false,false,true)\n144:(1,false,1,false,true,true,false,false,false,false,false)\n145:(1,false,1,false,true,true,false,false,false,false,true)\n146:(1,false,1,false,true,true,false,false,true,false,false)\n147:(1,false,1,false,true,true,false,false,true,false,true)\n148:(1,false,1,true,true,false,false,false,false,false,false)\n149:(1,false,1,true,true,false,false,false,false,false,true)\n150:(1,false,1,true,true,false,false,false,true,false,false)\n151:(1,false,1,true,true,false,false,false,true,false,true)\n152:(1,false,1,true,true,false,true,false,false,false,false)\n153:(1,false,1,true,true,false,true,false,false,false,true)\n154:(1,false,1,true,true,false,true,false,true,false,false)\n155:(1,false,1,true,true,false,true,false,true,false,true)\n156:(1,false,2,false,false,false,false,false,false,false,false)\n157:(1,false,2,false,false,false,false,false,false,false,true)\n158:(1,false,2,false,false,false,false,false,true,false,false)\n159:(1,false,2,false,false,false,false,false,true,false,true)\n160:(1,false,2,false,false,false,true,false,false,false,false)\n161:(1,false,2,false,false,false,true,false,false,false,true)\n162:(1,false,2,false,false,false,true,false,true,false,false)\n163:(1,false,2,false,false,false,true,false,true,false,true)\n164:(1,false,2,false,true,false,false,false,false,true,false)\n165:(1,false,2,false,true,false,false,false,true,true,false)\n166:(1,false,2,false,true,false,false,true,false,false,false)\n167:(1,false,2,false,true,false,false,true,false,false,true)\n168:(1,false,2,false,true,false,true,false,false,true,false)\n169:(1,false,2,false,true,false,true,false,true,true,false)\n170:(1,false,2,false,true,false,true,true,false,false,false)\n171:(1,false,2,false,true,false,true,true,false,false,true)\n172:(1,false,2,false,true,true,false,false,false,false,false)\n173:(1,false,2,false,true,true,false,false,false,false,true)\n174:(1,false,2,false,true,true,false,false,true,false,false)\n175:(1,false,2,false,true,true,false,false,true,false,true)\n176:(1,true,0,false,true,false,false,false,false,false,false)\n177:(1,true,0,false,true,false,false,false,false,false,true)\n178:(1,true,0,false,true,false,false,false,true,false,false)\n179:(1,true,0,false,true,false,false,false,true,false,true)\n180:(1,true,0,false,true,false,true,false,false,false,false)\n181:(1,true,0,false,true,false,true,false,false,false,true)\n182:(1,true,0,false,true,false,true,false,true,false,false)\n183:(1,true,0,false,true,false,true,false,true,false,true)\n184:(1,true,1,false,true,false,false,false,false,false,false)\n185:(1,true,1,false,true,false,false,false,false,false,true)\n186:(1,true,1,false,true,false,false,false,true,false,false)\n187:(1,true,1,false,true,false,false,false,true,false,true)\n188:(1,true,1,false,true,false,true,false,false,false,false)\n189:(1,true,1,false,true,false,true,false,false,false,true)\n190:(1,true,1,false,true,false,true,false,true,false,false)\n191:(1,true,1,false,true,false,true,false,true,false,true)\n192:(1,true,2,false,true,false,false,false,false,false,false)\n193:(1,true,2,false,true,false,false,false,false,false,true)\n194:(1,true,2,false,true,false,false,false,true,false,false)\n195:(1,true,2,false,true,false,false,false,true,false,true)\n196:(1,true,2,false,true,false,true,false,false,false,false)\n197:(1,true,2,false,true,false,true,false,false,false,true)\n198:(1,true,2,false,true,false,true,false,true,false,false)\n199:(1,true,2,false,true,false,true,false,true,false,true)\n200:(2,false,0,false,false,false,false,false,false,false,false)\n201:(2,false,0,false,false,false,false,false,false,false,true)\n202:(2,false,0,false,false,false,false,false,true,false,false)\n203:(2,false,0,false,false,false,false,false,true,false,true)\n204:(2,false,0,false,false,false,true,false,false,false,false)\n205:(2,false,0,false,false,false,true,false,false,false,true)\n206:(2,false,0,false,false,false,true,false,true,false,false)\n207:(2,false,0,false,false,false,true,false,true,false,true)\n208:(2,false,0,false,true,false,false,false,false,true,false)\n209:(2,false,0,false,true,false,false,false,true,true,false)\n210:(2,false,0,false,true,false,false,true,false,false,false)\n211:(2,false,0,false,true,false,false,true,false,false,true)\n212:(2,false,0,false,true,false,true,false,false,true,false)\n213:(2,false,0,false,true,false,true,false,true,true,false)\n214:(2,false,0,false,true,false,true,true,false,false,false)\n215:(2,false,0,false,true,false,true,true,false,false,true)\n216:(2,false,0,false,true,true,false,false,false,false,false)\n217:(2,false,0,false,true,true,false,false,false,false,true)\n218:(2,false,0,false,true,true,false,false,true,false,false)\n219:(2,false,0,false,true,true,false,false,true,false,true)\n220:(2,false,0,true,true,false,false,false,false,false,false)\n221:(2,false,0,true,true,false,false,false,false,false,true)\n222:(2,false,0,true,true,false,false,false,true,false,false)\n223:(2,false,0,true,true,false,false,false,true,false,true)\n224:(2,false,0,true,true,false,true,false,false,false,false)\n225:(2,false,0,true,true,false,true,false,false,false,true)\n226:(2,false,0,true,true,false,true,false,true,false,false)\n227:(2,false,0,true,true,false,true,false,true,false,true)\n228:(2,false,1,false,false,false,false,false,false,false,false)\n229:(2,false,1,false,false,false,false,false,false,false,true)\n230:(2,false,1,false,false,false,false,false,true,false,false)\n231:(2,false,1,false,false,false,false,false,true,false,true)\n232:(2,false,1,false,false,false,true,false,false,false,false)\n233:(2,false,1,false,false,false,true,false,false,false,true)\n234:(2,false,1,false,false,false,true,false,true,false,false)\n235:(2,false,1,false,false,false,true,false,true,false,true)\n236:(2,false,1,false,true,false,false,false,false,true,false)\n237:(2,false,1,false,true,false,false,false,true,true,false)\n238:(2,false,1,false,true,false,false,true,false,false,false)\n239:(2,false,1,false,true,false,false,true,false,false,true)\n240:(2,false,1,false,true,false,true,false,false,true,false)\n241:(2,false,1,false,true,false,true,false,true,true,false)\n242:(2,false,1,false,true,false,true,true,false,false,false)\n243:(2,false,1,false,true,false,true,true,false,false,true)\n244:(2,false,1,false,true,true,false,false,false,false,false)\n245:(2,false,1,false,true,true,false,false,false,false,true)\n246:(2,false,1,false,true,true,false,false,true,false,false)\n247:(2,false,1,false,true,true,false,false,true,false,true)\n248:(2,false,1,true,true,false,false,false,false,false,false)\n249:(2,false,1,true,true,false,false,false,false,false,true)\n250:(2,false,1,true,true,false,false,false,true,false,false)\n251:(2,false,1,true,true,false,false,false,true,false,true)\n252:(2,false,1,true,true,false,true,false,false,false,false)\n253:(2,false,1,true,true,false,true,false,false,false,true)\n254:(2,false,1,true,true,false,true,false,true,false,false)\n255:(2,false,1,true,true,false,true,false,true,false,true)\n256:(2,false,2,false,false,false,false,false,false,false,false)\n257:(2,false,2,false,false,false,false,false,false,false,true)\n258:(2,false,2,false,false,false,false,false,true,false,false)\n259:(2,false,2,false,false,false,false,false,true,false,true)\n260:(2,false,2,false,false,false,true,false,false,false,false)\n261:(2,false,2,false,false,false,true,false,false,false,true)\n262:(2,false,2,false,false,false,true,false,true,false,false)\n263:(2,false,2,false,false,false,true,false,true,false,true)\n264:(2,false,2,false,true,false,false,false,false,true,false)\n265:(2,false,2,false,true,false,false,false,true,true,false)\n266:(2,false,2,false,true,false,false,true,false,false,false)\n267:(2,false,2,false,true,false,false,true,false,false,true)\n268:(2,false,2,false,true,false,true,false,false,true,false)\n269:(2,false,2,false,true,false,true,false,true,true,false)\n270:(2,false,2,false,true,false,true,true,false,false,false)\n271:(2,false,2,false,true,false,true,true,false,false,true)\n272:(2,false,2,false,true,true,false,false,false,false,false)\n273:(2,false,2,false,true,true,false,false,false,false,true)\n274:(2,false,2,false,true,true,false,false,true,false,false)\n275:(2,false,2,false,true,true,false,false,true,false,true)\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact.tra",
    "content": "276 1120\n0 8 10 startToRight\n0 10 10 startToLeft\n0 16 10 startLine\n0 20 10 startRight\n0 76 10 startLeft\n1 0 1/4000\n1 11 10 startToLeft\n1 17 10 startLine\n1 21 10 startRight\n1 77 10 startLeft\n2 0 1/4000\n2 9 10 startToRight\n2 18 10 startLine\n2 22 10 startRight\n2 78 10 startLeft\n3 1 1/4000\n3 2 1/4000\n3 19 10 startLine\n3 23 10 startRight\n3 79 10 startLeft\n4 0 1/5000\n4 12 10 startToRight\n4 14 10 startToLeft\n4 24 10 startRight\n4 80 10 startLeft\n5 1 1/5000\n5 4 1/4000\n5 15 10 startToLeft\n5 25 10 startRight\n5 81 10 startLeft\n6 2 1/5000\n6 4 1/4000\n6 13 10 startToRight\n6 26 10 startRight\n6 82 10 startLeft\n7 3 1/5000\n7 5 1/4000\n7 6 1/4000\n7 27 10 startRight\n7 83 10 startLeft\n8 1 1/4 repairToRight\n9 3 1/4 repairToRight\n9 8 1/4000\n10 2 1/4 repairToLeft\n11 3 1/4 repairToLeft\n11 10 1/4000\n12 5 1/4 repairToRight\n12 8 1/5000\n13 7 1/4 repairToRight\n13 9 1/5000\n13 12 1/4000\n14 6 1/4 repairToLeft\n14 10 1/5000\n15 7 1/4 repairToLeft\n15 11 1/5000\n15 14 1/4000\n16 4 1/8 repairLine\n17 5 1/8 repairLine\n17 16 1/4000\n18 6 1/8 repairLine\n18 16 1/4000\n19 7 1/8 repairLine\n19 17 1/4000\n19 18 1/4000\n20 28 2 repairRight\n21 20 1/4000\n21 29 2 repairRight\n22 20 1/4000\n22 30 2 repairRight\n23 21 1/4000\n23 22 1/4000\n23 31 2 repairRight\n24 20 1/5000\n24 32 2 repairRight\n25 21 1/5000\n25 24 1/4000\n25 33 2 repairRight\n26 22 1/5000\n26 24 1/4000\n26 34 2 repairRight\n27 23 1/5000\n27 25 1/4000\n27 26 1/4000\n27 35 2 repairRight\n28 0 1/500\n28 36 10 startToRight\n28 38 10 startToLeft\n28 44 10 startLine\n28 48 10 startRight\n28 84 10 startLeft\n29 1 1/500\n29 28 1/4000\n29 39 10 startToLeft\n29 45 10 startLine\n29 49 10 startRight\n29 85 10 startLeft\n30 2 1/500\n30 28 1/4000\n30 37 10 startToRight\n30 46 10 startLine\n30 50 10 startRight\n30 86 10 startLeft\n31 3 1/500\n31 29 1/4000\n31 30 1/4000\n31 47 10 startLine\n31 51 10 startRight\n31 87 10 startLeft\n32 4 1/500\n32 28 1/5000\n32 40 10 startToRight\n32 42 10 startToLeft\n32 52 10 startRight\n32 88 10 startLeft\n33 5 1/500\n33 29 1/5000\n33 32 1/4000\n33 43 10 startToLeft\n33 53 10 startRight\n33 89 10 startLeft\n34 6 1/500\n34 30 1/5000\n34 32 1/4000\n34 41 10 startToRight\n34 54 10 startRight\n34 90 10 startLeft\n35 7 1/500\n35 31 1/5000\n35 33 1/4000\n35 34 1/4000\n35 55 10 startRight\n35 91 10 startLeft\n36 8 1/500\n36 29 1/4 repairToRight\n37 9 1/500\n37 31 1/4 repairToRight\n37 36 1/4000\n38 10 1/500\n38 30 1/4 repairToLeft\n39 11 1/500\n39 31 1/4 repairToLeft\n39 38 1/4000\n40 12 1/500\n40 33 1/4 repairToRight\n40 36 1/5000\n41 13 1/500\n41 35 1/4 repairToRight\n41 37 1/5000\n41 40 1/4000\n42 14 1/500\n42 34 1/4 repairToLeft\n42 38 1/5000\n43 15 1/500\n43 35 1/4 repairToLeft\n43 39 1/5000\n43 42 1/4000\n44 16 1/500\n44 32 1/8 repairLine\n45 17 1/500\n45 33 1/8 repairLine\n45 44 1/4000\n46 18 1/500\n46 34 1/8 repairLine\n46 44 1/4000\n47 19 1/500\n47 35 1/8 repairLine\n47 45 1/4000\n47 46 1/4000\n48 20 1/500\n48 56 2 repairRight\n49 21 1/500\n49 48 1/4000\n49 57 2 repairRight\n50 22 1/500\n50 48 1/4000\n50 58 2 repairRight\n51 23 1/500\n51 49 1/4000\n51 50 1/4000\n51 59 2 repairRight\n52 24 1/500\n52 48 1/5000\n52 60 2 repairRight\n53 25 1/500\n53 49 1/5000\n53 52 1/4000\n53 61 2 repairRight\n54 26 1/500\n54 50 1/5000\n54 52 1/4000\n54 62 2 repairRight\n55 27 1/500\n55 51 1/5000\n55 53 1/4000\n55 54 1/4000\n55 63 2 repairRight\n56 28 1/250\n56 64 10 startToRight\n56 66 10 startToLeft\n56 72 10 startLine\n56 92 10 startLeft\n57 29 1/250\n57 56 1/4000\n57 67 10 startToLeft\n57 73 10 startLine\n57 93 10 startLeft\n58 30 1/250\n58 56 1/4000\n58 65 10 startToRight\n58 74 10 startLine\n58 94 10 startLeft\n59 31 1/250\n59 57 1/4000\n59 58 1/4000\n59 75 10 startLine\n59 95 10 startLeft\n60 32 1/250\n60 56 1/5000\n60 68 10 startToRight\n60 70 10 startToLeft\n60 96 10 startLeft\n61 33 1/250\n61 57 1/5000\n61 60 1/4000\n61 71 10 startToLeft\n61 97 10 startLeft\n62 34 1/250\n62 58 1/5000\n62 60 1/4000\n62 69 10 startToRight\n62 98 10 startLeft\n63 35 1/250\n63 59 1/5000\n63 61 1/4000\n63 62 1/4000\n63 99 10 startLeft\n64 36 1/250\n64 57 1/4 repairToRight\n65 37 1/250\n65 59 1/4 repairToRight\n65 64 1/4000\n66 38 1/250\n66 58 1/4 repairToLeft\n67 39 1/250\n67 59 1/4 repairToLeft\n67 66 1/4000\n68 40 1/250\n68 61 1/4 repairToRight\n68 64 1/5000\n69 41 1/250\n69 63 1/4 repairToRight\n69 65 1/5000\n69 68 1/4000\n70 42 1/250\n70 62 1/4 repairToLeft\n70 66 1/5000\n71 43 1/250\n71 63 1/4 repairToLeft\n71 67 1/5000\n71 70 1/4000\n72 44 1/250\n72 60 1/8 repairLine\n73 45 1/250\n73 61 1/8 repairLine\n73 72 1/4000\n74 46 1/250\n74 62 1/8 repairLine\n74 72 1/4000\n75 47 1/250\n75 63 1/8 repairLine\n75 73 1/4000\n75 74 1/4000\n76 100 2 repairLeft\n77 76 1/4000\n77 101 2 repairLeft\n78 76 1/4000\n78 102 2 repairLeft\n79 77 1/4000\n79 78 1/4000\n79 103 2 repairLeft\n80 76 1/5000\n80 104 2 repairLeft\n81 77 1/5000\n81 80 1/4000\n81 105 2 repairLeft\n82 78 1/5000\n82 80 1/4000\n82 106 2 repairLeft\n83 79 1/5000\n83 81 1/4000\n83 82 1/4000\n83 107 2 repairLeft\n84 76 1/500\n84 128 2 repairLeft\n85 77 1/500\n85 84 1/4000\n85 129 2 repairLeft\n86 78 1/500\n86 84 1/4000\n86 130 2 repairLeft\n87 79 1/500\n87 85 1/4000\n87 86 1/4000\n87 131 2 repairLeft\n88 80 1/500\n88 84 1/5000\n88 132 2 repairLeft\n89 81 1/500\n89 85 1/5000\n89 88 1/4000\n89 133 2 repairLeft\n90 82 1/500\n90 86 1/5000\n90 88 1/4000\n90 134 2 repairLeft\n91 83 1/500\n91 87 1/5000\n91 89 1/4000\n91 90 1/4000\n91 135 2 repairLeft\n92 84 1/250\n92 156 2 repairLeft\n93 85 1/250\n93 92 1/4000\n93 157 2 repairLeft\n94 86 1/250\n94 92 1/4000\n94 158 2 repairLeft\n95 87 1/250\n95 93 1/4000\n95 94 1/4000\n95 159 2 repairLeft\n96 88 1/250\n96 92 1/5000\n96 160 2 repairLeft\n97 89 1/250\n97 93 1/5000\n97 96 1/4000\n97 161 2 repairLeft\n98 90 1/250\n98 94 1/5000\n98 96 1/4000\n98 162 2 repairLeft\n99 91 1/250\n99 95 1/5000\n99 97 1/4000\n99 98 1/4000\n99 163 2 repairLeft\n100 0 1/500\n100 108 10 startToRight\n100 110 10 startToLeft\n100 116 10 startLine\n100 120 10 startRight\n100 176 10 startLeft\n101 1 1/500\n101 100 1/4000\n101 111 10 startToLeft\n101 117 10 startLine\n101 121 10 startRight\n101 177 10 startLeft\n102 2 1/500\n102 100 1/4000\n102 109 10 startToRight\n102 118 10 startLine\n102 122 10 startRight\n102 178 10 startLeft\n103 3 1/500\n103 101 1/4000\n103 102 1/4000\n103 119 10 startLine\n103 123 10 startRight\n103 179 10 startLeft\n104 4 1/500\n104 100 1/5000\n104 112 10 startToRight\n104 114 10 startToLeft\n104 124 10 startRight\n104 180 10 startLeft\n105 5 1/500\n105 101 1/5000\n105 104 1/4000\n105 115 10 startToLeft\n105 125 10 startRight\n105 181 10 startLeft\n106 6 1/500\n106 102 1/5000\n106 104 1/4000\n106 113 10 startToRight\n106 126 10 startRight\n106 182 10 startLeft\n107 7 1/500\n107 103 1/5000\n107 105 1/4000\n107 106 1/4000\n107 127 10 startRight\n107 183 10 startLeft\n108 8 1/500\n108 101 1/4 repairToRight\n109 9 1/500\n109 103 1/4 repairToRight\n109 108 1/4000\n110 10 1/500\n110 102 1/4 repairToLeft\n111 11 1/500\n111 103 1/4 repairToLeft\n111 110 1/4000\n112 12 1/500\n112 105 1/4 repairToRight\n112 108 1/5000\n113 13 1/500\n113 107 1/4 repairToRight\n113 109 1/5000\n113 112 1/4000\n114 14 1/500\n114 106 1/4 repairToLeft\n114 110 1/5000\n115 15 1/500\n115 107 1/4 repairToLeft\n115 111 1/5000\n115 114 1/4000\n116 16 1/500\n116 104 1/8 repairLine\n117 17 1/500\n117 105 1/8 repairLine\n117 116 1/4000\n118 18 1/500\n118 106 1/8 repairLine\n118 116 1/4000\n119 19 1/500\n119 107 1/8 repairLine\n119 117 1/4000\n119 118 1/4000\n120 20 1/500\n120 128 2 repairRight\n121 21 1/500\n121 120 1/4000\n121 129 2 repairRight\n122 22 1/500\n122 120 1/4000\n122 130 2 repairRight\n123 23 1/500\n123 121 1/4000\n123 122 1/4000\n123 131 2 repairRight\n124 24 1/500\n124 120 1/5000\n124 132 2 repairRight\n125 25 1/500\n125 121 1/5000\n125 124 1/4000\n125 133 2 repairRight\n126 26 1/500\n126 122 1/5000\n126 124 1/4000\n126 134 2 repairRight\n127 27 1/500\n127 123 1/5000\n127 125 1/4000\n127 126 1/4000\n127 135 2 repairRight\n128 28 1/500\n128 100 1/500\n128 136 10 startToRight\n128 138 10 startToLeft\n128 144 10 startLine\n128 148 10 startRight\n128 184 10 startLeft\n129 29 1/500\n129 101 1/500\n129 128 1/4000\n129 139 10 startToLeft\n129 145 10 startLine\n129 149 10 startRight\n129 185 10 startLeft\n130 30 1/500\n130 102 1/500\n130 128 1/4000\n130 137 10 startToRight\n130 146 10 startLine\n130 150 10 startRight\n130 186 10 startLeft\n131 31 1/500\n131 103 1/500\n131 129 1/4000\n131 130 1/4000\n131 147 10 startLine\n131 151 10 startRight\n131 187 10 startLeft\n132 32 1/500\n132 104 1/500\n132 128 1/5000\n132 140 10 startToRight\n132 142 10 startToLeft\n132 152 10 startRight\n132 188 10 startLeft\n133 33 1/500\n133 105 1/500\n133 129 1/5000\n133 132 1/4000\n133 143 10 startToLeft\n133 153 10 startRight\n133 189 10 startLeft\n134 34 1/500\n134 106 1/500\n134 130 1/5000\n134 132 1/4000\n134 141 10 startToRight\n134 154 10 startRight\n134 190 10 startLeft\n135 35 1/500\n135 107 1/500\n135 131 1/5000\n135 133 1/4000\n135 134 1/4000\n135 155 10 startRight\n135 191 10 startLeft\n136 36 1/500\n136 108 1/500\n136 129 1/4 repairToRight\n137 37 1/500\n137 109 1/500\n137 131 1/4 repairToRight\n137 136 1/4000\n138 38 1/500\n138 110 1/500\n138 130 1/4 repairToLeft\n139 39 1/500\n139 111 1/500\n139 131 1/4 repairToLeft\n139 138 1/4000\n140 40 1/500\n140 112 1/500\n140 133 1/4 repairToRight\n140 136 1/5000\n141 41 1/500\n141 113 1/500\n141 135 1/4 repairToRight\n141 137 1/5000\n141 140 1/4000\n142 42 1/500\n142 114 1/500\n142 134 1/4 repairToLeft\n142 138 1/5000\n143 43 1/500\n143 115 1/500\n143 135 1/4 repairToLeft\n143 139 1/5000\n143 142 1/4000\n144 44 1/500\n144 116 1/500\n144 132 1/8 repairLine\n145 45 1/500\n145 117 1/500\n145 133 1/8 repairLine\n145 144 1/4000\n146 46 1/500\n146 118 1/500\n146 134 1/8 repairLine\n146 144 1/4000\n147 47 1/500\n147 119 1/500\n147 135 1/8 repairLine\n147 145 1/4000\n147 146 1/4000\n148 48 1/500\n148 120 1/500\n148 156 2 repairRight\n149 49 1/500\n149 121 1/500\n149 148 1/4000\n149 157 2 repairRight\n150 50 1/500\n150 122 1/500\n150 148 1/4000\n150 158 2 repairRight\n151 51 1/500\n151 123 1/500\n151 149 1/4000\n151 150 1/4000\n151 159 2 repairRight\n152 52 1/500\n152 124 1/500\n152 148 1/5000\n152 160 2 repairRight\n153 53 1/500\n153 125 1/500\n153 149 1/5000\n153 152 1/4000\n153 161 2 repairRight\n154 54 1/500\n154 126 1/500\n154 150 1/5000\n154 152 1/4000\n154 162 2 repairRight\n155 55 1/500\n155 127 1/500\n155 151 1/5000\n155 153 1/4000\n155 154 1/4000\n155 163 2 repairRight\n156 56 1/500\n156 128 1/250\n156 164 10 startToRight\n156 166 10 startToLeft\n156 172 10 startLine\n156 192 10 startLeft\n157 57 1/500\n157 129 1/250\n157 156 1/4000\n157 167 10 startToLeft\n157 173 10 startLine\n157 193 10 startLeft\n158 58 1/500\n158 130 1/250\n158 156 1/4000\n158 165 10 startToRight\n158 174 10 startLine\n158 194 10 startLeft\n159 59 1/500\n159 131 1/250\n159 157 1/4000\n159 158 1/4000\n159 175 10 startLine\n159 195 10 startLeft\n160 60 1/500\n160 132 1/250\n160 156 1/5000\n160 168 10 startToRight\n160 170 10 startToLeft\n160 196 10 startLeft\n161 61 1/500\n161 133 1/250\n161 157 1/5000\n161 160 1/4000\n161 171 10 startToLeft\n161 197 10 startLeft\n162 62 1/500\n162 134 1/250\n162 158 1/5000\n162 160 1/4000\n162 169 10 startToRight\n162 198 10 startLeft\n163 63 1/500\n163 135 1/250\n163 159 1/5000\n163 161 1/4000\n163 162 1/4000\n163 199 10 startLeft\n164 64 1/500\n164 136 1/250\n164 157 1/4 repairToRight\n165 65 1/500\n165 137 1/250\n165 159 1/4 repairToRight\n165 164 1/4000\n166 66 1/500\n166 138 1/250\n166 158 1/4 repairToLeft\n167 67 1/500\n167 139 1/250\n167 159 1/4 repairToLeft\n167 166 1/4000\n168 68 1/500\n168 140 1/250\n168 161 1/4 repairToRight\n168 164 1/5000\n169 69 1/500\n169 141 1/250\n169 163 1/4 repairToRight\n169 165 1/5000\n169 168 1/4000\n170 70 1/500\n170 142 1/250\n170 162 1/4 repairToLeft\n170 166 1/5000\n171 71 1/500\n171 143 1/250\n171 163 1/4 repairToLeft\n171 167 1/5000\n171 170 1/4000\n172 72 1/500\n172 144 1/250\n172 160 1/8 repairLine\n173 73 1/500\n173 145 1/250\n173 161 1/8 repairLine\n173 172 1/4000\n174 74 1/500\n174 146 1/250\n174 162 1/8 repairLine\n174 172 1/4000\n175 75 1/500\n175 147 1/250\n175 163 1/8 repairLine\n175 173 1/4000\n175 174 1/4000\n176 76 1/500\n176 200 2 repairLeft\n177 77 1/500\n177 176 1/4000\n177 201 2 repairLeft\n178 78 1/500\n178 176 1/4000\n178 202 2 repairLeft\n179 79 1/500\n179 177 1/4000\n179 178 1/4000\n179 203 2 repairLeft\n180 80 1/500\n180 176 1/5000\n180 204 2 repairLeft\n181 81 1/500\n181 177 1/5000\n181 180 1/4000\n181 205 2 repairLeft\n182 82 1/500\n182 178 1/5000\n182 180 1/4000\n182 206 2 repairLeft\n183 83 1/500\n183 179 1/5000\n183 181 1/4000\n183 182 1/4000\n183 207 2 repairLeft\n184 84 1/500\n184 176 1/500\n184 228 2 repairLeft\n185 85 1/500\n185 177 1/500\n185 184 1/4000\n185 229 2 repairLeft\n186 86 1/500\n186 178 1/500\n186 184 1/4000\n186 230 2 repairLeft\n187 87 1/500\n187 179 1/500\n187 185 1/4000\n187 186 1/4000\n187 231 2 repairLeft\n188 88 1/500\n188 180 1/500\n188 184 1/5000\n188 232 2 repairLeft\n189 89 1/500\n189 181 1/500\n189 185 1/5000\n189 188 1/4000\n189 233 2 repairLeft\n190 90 1/500\n190 182 1/500\n190 186 1/5000\n190 188 1/4000\n190 234 2 repairLeft\n191 91 1/500\n191 183 1/500\n191 187 1/5000\n191 189 1/4000\n191 190 1/4000\n191 235 2 repairLeft\n192 92 1/500\n192 184 1/250\n192 256 2 repairLeft\n193 93 1/500\n193 185 1/250\n193 192 1/4000\n193 257 2 repairLeft\n194 94 1/500\n194 186 1/250\n194 192 1/4000\n194 258 2 repairLeft\n195 95 1/500\n195 187 1/250\n195 193 1/4000\n195 194 1/4000\n195 259 2 repairLeft\n196 96 1/500\n196 188 1/250\n196 192 1/5000\n196 260 2 repairLeft\n197 97 1/500\n197 189 1/250\n197 193 1/5000\n197 196 1/4000\n197 261 2 repairLeft\n198 98 1/500\n198 190 1/250\n198 194 1/5000\n198 196 1/4000\n198 262 2 repairLeft\n199 99 1/500\n199 191 1/250\n199 195 1/5000\n199 197 1/4000\n199 198 1/4000\n199 263 2 repairLeft\n200 100 1/250\n200 208 10 startToRight\n200 210 10 startToLeft\n200 216 10 startLine\n200 220 10 startRight\n201 101 1/250\n201 200 1/4000\n201 211 10 startToLeft\n201 217 10 startLine\n201 221 10 startRight\n202 102 1/250\n202 200 1/4000\n202 209 10 startToRight\n202 218 10 startLine\n202 222 10 startRight\n203 103 1/250\n203 201 1/4000\n203 202 1/4000\n203 219 10 startLine\n203 223 10 startRight\n204 104 1/250\n204 200 1/5000\n204 212 10 startToRight\n204 214 10 startToLeft\n204 224 10 startRight\n205 105 1/250\n205 201 1/5000\n205 204 1/4000\n205 215 10 startToLeft\n205 225 10 startRight\n206 106 1/250\n206 202 1/5000\n206 204 1/4000\n206 213 10 startToRight\n206 226 10 startRight\n207 107 1/250\n207 203 1/5000\n207 205 1/4000\n207 206 1/4000\n207 227 10 startRight\n208 108 1/250\n208 201 1/4 repairToRight\n209 109 1/250\n209 203 1/4 repairToRight\n209 208 1/4000\n210 110 1/250\n210 202 1/4 repairToLeft\n211 111 1/250\n211 203 1/4 repairToLeft\n211 210 1/4000\n212 112 1/250\n212 205 1/4 repairToRight\n212 208 1/5000\n213 113 1/250\n213 207 1/4 repairToRight\n213 209 1/5000\n213 212 1/4000\n214 114 1/250\n214 206 1/4 repairToLeft\n214 210 1/5000\n215 115 1/250\n215 207 1/4 repairToLeft\n215 211 1/5000\n215 214 1/4000\n216 116 1/250\n216 204 1/8 repairLine\n217 117 1/250\n217 205 1/8 repairLine\n217 216 1/4000\n218 118 1/250\n218 206 1/8 repairLine\n218 216 1/4000\n219 119 1/250\n219 207 1/8 repairLine\n219 217 1/4000\n219 218 1/4000\n220 120 1/250\n220 228 2 repairRight\n221 121 1/250\n221 220 1/4000\n221 229 2 repairRight\n222 122 1/250\n222 220 1/4000\n222 230 2 repairRight\n223 123 1/250\n223 221 1/4000\n223 222 1/4000\n223 231 2 repairRight\n224 124 1/250\n224 220 1/5000\n224 232 2 repairRight\n225 125 1/250\n225 221 1/5000\n225 224 1/4000\n225 233 2 repairRight\n226 126 1/250\n226 222 1/5000\n226 224 1/4000\n226 234 2 repairRight\n227 127 1/250\n227 223 1/5000\n227 225 1/4000\n227 226 1/4000\n227 235 2 repairRight\n228 128 1/250\n228 200 1/500\n228 236 10 startToRight\n228 238 10 startToLeft\n228 244 10 startLine\n228 248 10 startRight\n229 129 1/250\n229 201 1/500\n229 228 1/4000\n229 239 10 startToLeft\n229 245 10 startLine\n229 249 10 startRight\n230 130 1/250\n230 202 1/500\n230 228 1/4000\n230 237 10 startToRight\n230 246 10 startLine\n230 250 10 startRight\n231 131 1/250\n231 203 1/500\n231 229 1/4000\n231 230 1/4000\n231 247 10 startLine\n231 251 10 startRight\n232 132 1/250\n232 204 1/500\n232 228 1/5000\n232 240 10 startToRight\n232 242 10 startToLeft\n232 252 10 startRight\n233 133 1/250\n233 205 1/500\n233 229 1/5000\n233 232 1/4000\n233 243 10 startToLeft\n233 253 10 startRight\n234 134 1/250\n234 206 1/500\n234 230 1/5000\n234 232 1/4000\n234 241 10 startToRight\n234 254 10 startRight\n235 135 1/250\n235 207 1/500\n235 231 1/5000\n235 233 1/4000\n235 234 1/4000\n235 255 10 startRight\n236 136 1/250\n236 208 1/500\n236 229 1/4 repairToRight\n237 137 1/250\n237 209 1/500\n237 231 1/4 repairToRight\n237 236 1/4000\n238 138 1/250\n238 210 1/500\n238 230 1/4 repairToLeft\n239 139 1/250\n239 211 1/500\n239 231 1/4 repairToLeft\n239 238 1/4000\n240 140 1/250\n240 212 1/500\n240 233 1/4 repairToRight\n240 236 1/5000\n241 141 1/250\n241 213 1/500\n241 235 1/4 repairToRight\n241 237 1/5000\n241 240 1/4000\n242 142 1/250\n242 214 1/500\n242 234 1/4 repairToLeft\n242 238 1/5000\n243 143 1/250\n243 215 1/500\n243 235 1/4 repairToLeft\n243 239 1/5000\n243 242 1/4000\n244 144 1/250\n244 216 1/500\n244 232 1/8 repairLine\n245 145 1/250\n245 217 1/500\n245 233 1/8 repairLine\n245 244 1/4000\n246 146 1/250\n246 218 1/500\n246 234 1/8 repairLine\n246 244 1/4000\n247 147 1/250\n247 219 1/500\n247 235 1/8 repairLine\n247 245 1/4000\n247 246 1/4000\n248 148 1/250\n248 220 1/500\n248 256 2 repairRight\n249 149 1/250\n249 221 1/500\n249 248 1/4000\n249 257 2 repairRight\n250 150 1/250\n250 222 1/500\n250 248 1/4000\n250 258 2 repairRight\n251 151 1/250\n251 223 1/500\n251 249 1/4000\n251 250 1/4000\n251 259 2 repairRight\n252 152 1/250\n252 224 1/500\n252 248 1/5000\n252 260 2 repairRight\n253 153 1/250\n253 225 1/500\n253 249 1/5000\n253 252 1/4000\n253 261 2 repairRight\n254 154 1/250\n254 226 1/500\n254 250 1/5000\n254 252 1/4000\n254 262 2 repairRight\n255 155 1/250\n255 227 1/500\n255 251 1/5000\n255 253 1/4000\n255 254 1/4000\n255 263 2 repairRight\n256 156 1/250\n256 228 1/250\n256 264 10 startToRight\n256 266 10 startToLeft\n256 272 10 startLine\n257 157 1/250\n257 229 1/250\n257 256 1/4000\n257 267 10 startToLeft\n257 273 10 startLine\n258 158 1/250\n258 230 1/250\n258 256 1/4000\n258 265 10 startToRight\n258 274 10 startLine\n259 159 1/250\n259 231 1/250\n259 257 1/4000\n259 258 1/4000\n259 275 10 startLine\n260 160 1/250\n260 232 1/250\n260 256 1/5000\n260 268 10 startToRight\n260 270 10 startToLeft\n261 161 1/250\n261 233 1/250\n261 257 1/5000\n261 260 1/4000\n261 271 10 startToLeft\n262 162 1/250\n262 234 1/250\n262 258 1/5000\n262 260 1/4000\n262 269 10 startToRight\n263 163 1/250\n263 235 1/250\n263 259 1/5000\n263 261 1/4000\n263 262 1/4000\n264 164 1/250\n264 236 1/250\n264 257 1/4 repairToRight\n265 165 1/250\n265 237 1/250\n265 259 1/4 repairToRight\n265 264 1/4000\n266 166 1/250\n266 238 1/250\n266 258 1/4 repairToLeft\n267 167 1/250\n267 239 1/250\n267 259 1/4 repairToLeft\n267 266 1/4000\n268 168 1/250\n268 240 1/250\n268 261 1/4 repairToRight\n268 264 1/5000\n269 169 1/250\n269 241 1/250\n269 263 1/4 repairToRight\n269 265 1/5000\n269 268 1/4000\n270 170 1/250\n270 242 1/250\n270 262 1/4 repairToLeft\n270 266 1/5000\n271 171 1/250\n271 243 1/250\n271 263 1/4 repairToLeft\n271 267 1/5000\n271 270 1/4000\n272 172 1/250\n272 244 1/250\n272 260 1/8 repairLine\n273 173 1/250\n273 245 1/250\n273 261 1/8 repairLine\n273 272 1/4000\n274 174 1/250\n274 246 1/250\n274 262 1/8 repairLine\n274 272 1/4000\n275 175 1/250\n275 247 1/250\n275 263 1/8 repairLine\n275 273 1/4000\n275 274 1/4000\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact1.srew",
    "content": "# Reward structure \"percent_op\"\n# State rewards\n276 240\n28 25\n29 25\n30 25\n31 25\n32 25\n33 25\n34 25\n35 25\n36 25\n37 25\n38 25\n39 25\n40 25\n41 25\n42 25\n43 25\n44 25\n45 25\n46 25\n47 25\n48 25\n49 25\n50 25\n51 25\n52 25\n53 25\n54 25\n55 25\n56 50\n57 50\n58 50\n59 50\n60 50\n61 50\n62 50\n63 50\n64 50\n65 50\n66 50\n67 50\n68 50\n69 50\n70 50\n71 50\n72 50\n73 50\n74 50\n75 50\n84 25\n85 25\n86 25\n87 25\n88 25\n89 25\n90 25\n91 25\n92 50\n93 50\n94 50\n95 50\n96 50\n97 50\n98 50\n99 50\n100 25\n101 25\n102 25\n103 25\n104 25\n105 25\n106 25\n107 25\n108 25\n109 25\n110 25\n111 25\n112 25\n113 25\n114 25\n115 25\n116 25\n117 25\n118 25\n119 25\n120 25\n121 25\n122 25\n123 25\n124 25\n125 25\n126 25\n127 25\n128 50\n129 50\n130 50\n131 50\n132 50\n133 50\n134 50\n135 50\n136 50\n137 50\n138 50\n139 50\n140 50\n141 50\n142 50\n143 50\n144 50\n145 50\n146 50\n147 50\n148 50\n149 50\n150 50\n151 50\n152 50\n153 50\n154 50\n155 50\n156 75\n157 75\n158 75\n159 75\n160 75\n161 75\n162 75\n163 75\n164 75\n165 75\n166 75\n167 75\n168 75\n169 75\n170 75\n171 75\n172 75\n173 75\n174 75\n175 75\n176 25\n177 25\n178 25\n179 25\n180 25\n181 25\n182 25\n183 25\n184 50\n185 50\n186 50\n187 50\n188 50\n189 50\n190 50\n191 50\n192 75\n193 75\n194 75\n195 75\n196 75\n197 75\n198 75\n199 75\n200 50\n201 50\n202 50\n203 50\n204 50\n205 50\n206 50\n207 50\n208 50\n209 50\n210 50\n211 50\n212 50\n213 50\n214 50\n215 50\n216 50\n217 50\n218 50\n219 50\n220 50\n221 50\n222 50\n223 50\n224 50\n225 50\n226 50\n227 50\n228 75\n229 75\n230 75\n231 75\n232 75\n233 75\n234 75\n235 75\n236 75\n237 75\n238 75\n239 75\n240 75\n241 75\n242 75\n243 75\n244 75\n245 75\n246 75\n247 75\n248 75\n249 75\n250 75\n251 75\n252 75\n253 75\n254 75\n255 75\n256 100\n257 100\n258 100\n259 100\n260 100\n261 100\n262 100\n263 100\n264 100\n265 100\n266 100\n267 100\n268 100\n269 100\n270 100\n271 100\n272 100\n273 100\n274 100\n275 100\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact1.trew",
    "content": "# Reward structure \"percent_op\"\n# Transition rewards\n276 0\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact2.srew",
    "content": "# Reward structure \"time_not_min\"\n# State rewards\n276 144\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n6 1\n7 1\n8 1\n9 1\n10 1\n11 1\n12 1\n13 1\n14 1\n15 1\n16 1\n17 1\n18 1\n19 1\n20 1\n21 1\n22 1\n23 1\n24 1\n25 1\n26 1\n27 1\n28 1\n30 1\n32 1\n34 1\n36 1\n37 1\n38 1\n40 1\n41 1\n42 1\n44 1\n46 1\n48 1\n50 1\n52 1\n54 1\n56 1\n58 1\n60 1\n62 1\n64 1\n65 1\n66 1\n68 1\n69 1\n70 1\n72 1\n74 1\n76 1\n77 1\n78 1\n79 1\n80 1\n81 1\n82 1\n83 1\n84 1\n86 1\n88 1\n90 1\n92 1\n94 1\n96 1\n98 1\n100 1\n101 1\n104 1\n105 1\n108 1\n110 1\n111 1\n112 1\n114 1\n115 1\n116 1\n117 1\n120 1\n121 1\n124 1\n125 1\n128 1\n132 1\n136 1\n138 1\n140 1\n142 1\n144 1\n148 1\n152 1\n156 1\n160 1\n164 1\n166 1\n168 1\n170 1\n172 1\n176 1\n177 1\n180 1\n181 1\n184 1\n188 1\n192 1\n196 1\n200 1\n201 1\n204 1\n205 1\n208 1\n210 1\n211 1\n212 1\n214 1\n215 1\n216 1\n217 1\n220 1\n221 1\n224 1\n225 1\n228 1\n232 1\n236 1\n238 1\n240 1\n242 1\n244 1\n248 1\n252 1\n256 1\n260 1\n264 1\n266 1\n268 1\n270 1\n272 1\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact2.trew",
    "content": "# Reward structure \"time_not_min\"\n# Transition rewards\n276 0\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact3.srew",
    "content": "# Reward structure \"num_repairs\"\n# State rewards\n276 0\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exact3.trew",
    "content": "# Reward structure \"num_repairs\"\n# Transition rewards\n276 204\n8 1 1\n9 3 1\n10 2 1\n11 3 1\n12 5 1\n13 7 1\n14 6 1\n15 7 1\n16 4 1\n17 5 1\n18 6 1\n19 7 1\n20 28 1\n21 29 1\n22 30 1\n23 31 1\n24 32 1\n25 33 1\n26 34 1\n27 35 1\n36 29 1\n37 31 1\n38 30 1\n39 31 1\n40 33 1\n41 35 1\n42 34 1\n43 35 1\n44 32 1\n45 33 1\n46 34 1\n47 35 1\n48 56 1\n49 57 1\n50 58 1\n51 59 1\n52 60 1\n53 61 1\n54 62 1\n55 63 1\n64 57 1\n65 59 1\n66 58 1\n67 59 1\n68 61 1\n69 63 1\n70 62 1\n71 63 1\n72 60 1\n73 61 1\n74 62 1\n75 63 1\n76 100 1\n77 101 1\n78 102 1\n79 103 1\n80 104 1\n81 105 1\n82 106 1\n83 107 1\n84 128 1\n85 129 1\n86 130 1\n87 131 1\n88 132 1\n89 133 1\n90 134 1\n91 135 1\n92 156 1\n93 157 1\n94 158 1\n95 159 1\n96 160 1\n97 161 1\n98 162 1\n99 163 1\n108 101 1\n109 103 1\n110 102 1\n111 103 1\n112 105 1\n113 107 1\n114 106 1\n115 107 1\n116 104 1\n117 105 1\n118 106 1\n119 107 1\n120 128 1\n121 129 1\n122 130 1\n123 131 1\n124 132 1\n125 133 1\n126 134 1\n127 135 1\n136 129 1\n137 131 1\n138 130 1\n139 131 1\n140 133 1\n141 135 1\n142 134 1\n143 135 1\n144 132 1\n145 133 1\n146 134 1\n147 135 1\n148 156 1\n149 157 1\n150 158 1\n151 159 1\n152 160 1\n153 161 1\n154 162 1\n155 163 1\n164 157 1\n165 159 1\n166 158 1\n167 159 1\n168 161 1\n169 163 1\n170 162 1\n171 163 1\n172 160 1\n173 161 1\n174 162 1\n175 163 1\n176 200 1\n177 201 1\n178 202 1\n179 203 1\n180 204 1\n181 205 1\n182 206 1\n183 207 1\n184 228 1\n185 229 1\n186 230 1\n187 231 1\n188 232 1\n189 233 1\n190 234 1\n191 235 1\n192 256 1\n193 257 1\n194 258 1\n195 259 1\n196 260 1\n197 261 1\n198 262 1\n199 263 1\n208 201 1\n209 203 1\n210 202 1\n211 203 1\n212 205 1\n213 207 1\n214 206 1\n215 207 1\n216 204 1\n217 205 1\n218 206 1\n219 207 1\n220 228 1\n221 229 1\n222 230 1\n223 231 1\n224 232 1\n225 233 1\n226 234 1\n227 235 1\n236 229 1\n237 231 1\n238 230 1\n239 231 1\n240 233 1\n241 235 1\n242 234 1\n243 235 1\n244 232 1\n245 233 1\n246 234 1\n247 235 1\n248 256 1\n249 257 1\n250 258 1\n251 259 1\n252 260 1\n253 261 1\n254 262 1\n255 263 1\n264 257 1\n265 259 1\n266 258 1\n267 259 1\n268 261 1\n269 263 1\n270 262 1\n271 263 1\n272 260 1\n273 261 1\n274 262 1\n275 263 1\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.exportmodel.auto",
    "content": "# Reduce precision for some tests due to minor differences between the engines\n\n# Export all model info in different formats\n\n-exportmodel cluster.sm.all:actions=false\n-exportmodel cluster.sm.matlab.all:matlab,actions=false\n-exportmodel cluster.sm.rows.all:rows,actions=false\n\n# Export model info separately (for a few formats)\n\n-exportmodel cluster.sm.tra:actions=false\n-exportmodel cluster.sm.lab\n-exportmodel cluster.sm.sta\n-exportmodel cluster.sm.srew\n-exportmodel cluster.sm.trew\n\n# Export model info - explicit engine\n\n-exportmodel cluster.sm.all:actions=false -ex\n\n-exportmodel cluster.sm.tra:actions=false -ex\n-exportmodel cluster.sm.sta -ex\n-exportmodel cluster.sm.lab -ex\n-exportmodel cluster.sm.srew -ex\n-exportmodel cluster.sm.trew -ex\n\n# Export model info - exact\n\n-exportmodel cluster.sm.exact.all -exact\n\n-exportmodel cluster.sm.exact.tra -exact\n-exportmodel cluster.sm.exact.sta -exact\n-exportmodel cluster.sm.exact.lab -exact\n-exportmodel cluster.sm.exact.srew -exact\n-exportmodel cluster.sm.exact.trew -exact\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"minimum\" 3=\"premium\"\n29: 2\n31: 2\n33: 2\n35: 2\n39: 2\n43: 2\n45: 2\n47: 2\n49: 2\n51: 2\n53: 2\n55: 2\n57: 2 3\n59: 2 3\n61: 2 3\n63: 2 3\n67: 2 3\n71: 2 3\n73: 2 3\n75: 2 3\n85: 2\n87: 2\n89: 2\n91: 2\n93: 2 3\n95: 2 3\n97: 2 3\n99: 2 3\n102: 2\n103: 2\n106: 2\n107: 2\n109: 2\n113: 2\n118: 2\n119: 2\n122: 2\n123: 2\n126: 2\n127: 2\n129: 2\n130: 2\n131: 2\n133: 2\n134: 2\n135: 2 3\n137: 2\n139: 2\n141: 2\n143: 2\n145: 2\n146: 2\n147: 2\n149: 2\n150: 2\n151: 2\n153: 2\n154: 2\n155: 2 3\n157: 2 3\n158: 2\n159: 2 3\n161: 2 3\n162: 2\n163: 2 3\n165: 2\n167: 2 3\n169: 2\n171: 2 3\n173: 2 3\n174: 2\n175: 2 3\n178: 2\n179: 2\n182: 2\n183: 2\n185: 2\n186: 2\n187: 2\n189: 2\n190: 2\n191: 2 3\n193: 2 3\n194: 2\n195: 2 3\n197: 2 3\n198: 2\n199: 2 3\n202: 2 3\n203: 2 3\n206: 2 3\n207: 2 3\n209: 2 3\n213: 2 3\n218: 2 3\n219: 2 3\n222: 2 3\n223: 2 3\n226: 2 3\n227: 2 3\n229: 2\n230: 2 3\n231: 2 3\n233: 2\n234: 2 3\n235: 2 3\n237: 2 3\n239: 2\n241: 2 3\n243: 2\n245: 2\n246: 2 3\n247: 2 3\n249: 2\n250: 2 3\n251: 2 3\n253: 2\n254: 2 3\n255: 2 3\n257: 2 3\n258: 2 3\n259: 2 3\n261: 2 3\n262: 2 3\n263: 0 2 3\n265: 2 3\n267: 2 3\n269: 2 3\n271: 2 3\n273: 2 3\n274: 2 3\n275: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab.lab",
    "content": "l_init=sparse(276,1);\nl_deadlock=sparse(276,1);\nl_minimum=sparse(276,1);\nl_premium=sparse(276,1);\n\nl_minimum(30)=1;\nl_minimum(32)=1;\nl_minimum(34)=1;\nl_minimum(36)=1;\nl_minimum(40)=1;\nl_minimum(44)=1;\nl_minimum(46)=1;\nl_minimum(48)=1;\nl_minimum(50)=1;\nl_minimum(52)=1;\nl_minimum(54)=1;\nl_minimum(56)=1;\nl_minimum(58)=1;\nl_premium(58)=1;\nl_minimum(60)=1;\nl_premium(60)=1;\nl_minimum(62)=1;\nl_premium(62)=1;\nl_minimum(64)=1;\nl_premium(64)=1;\nl_minimum(68)=1;\nl_premium(68)=1;\nl_minimum(72)=1;\nl_premium(72)=1;\nl_minimum(74)=1;\nl_premium(74)=1;\nl_minimum(76)=1;\nl_premium(76)=1;\nl_minimum(86)=1;\nl_minimum(88)=1;\nl_minimum(90)=1;\nl_minimum(92)=1;\nl_minimum(94)=1;\nl_premium(94)=1;\nl_minimum(96)=1;\nl_premium(96)=1;\nl_minimum(98)=1;\nl_premium(98)=1;\nl_minimum(100)=1;\nl_premium(100)=1;\nl_minimum(103)=1;\nl_minimum(104)=1;\nl_minimum(107)=1;\nl_minimum(108)=1;\nl_minimum(110)=1;\nl_minimum(114)=1;\nl_minimum(119)=1;\nl_minimum(120)=1;\nl_minimum(123)=1;\nl_minimum(124)=1;\nl_minimum(127)=1;\nl_minimum(128)=1;\nl_minimum(130)=1;\nl_minimum(131)=1;\nl_minimum(132)=1;\nl_minimum(134)=1;\nl_minimum(135)=1;\nl_minimum(136)=1;\nl_premium(136)=1;\nl_minimum(138)=1;\nl_minimum(140)=1;\nl_minimum(142)=1;\nl_minimum(144)=1;\nl_minimum(146)=1;\nl_minimum(147)=1;\nl_minimum(148)=1;\nl_minimum(150)=1;\nl_minimum(151)=1;\nl_minimum(152)=1;\nl_minimum(154)=1;\nl_minimum(155)=1;\nl_minimum(156)=1;\nl_premium(156)=1;\nl_minimum(158)=1;\nl_premium(158)=1;\nl_minimum(159)=1;\nl_minimum(160)=1;\nl_premium(160)=1;\nl_minimum(162)=1;\nl_premium(162)=1;\nl_minimum(163)=1;\nl_minimum(164)=1;\nl_premium(164)=1;\nl_minimum(166)=1;\nl_minimum(168)=1;\nl_premium(168)=1;\nl_minimum(170)=1;\nl_minimum(172)=1;\nl_premium(172)=1;\nl_minimum(174)=1;\nl_premium(174)=1;\nl_minimum(175)=1;\nl_minimum(176)=1;\nl_premium(176)=1;\nl_minimum(179)=1;\nl_minimum(180)=1;\nl_minimum(183)=1;\nl_minimum(184)=1;\nl_minimum(186)=1;\nl_minimum(187)=1;\nl_minimum(188)=1;\nl_minimum(190)=1;\nl_minimum(191)=1;\nl_minimum(192)=1;\nl_premium(192)=1;\nl_minimum(194)=1;\nl_premium(194)=1;\nl_minimum(195)=1;\nl_minimum(196)=1;\nl_premium(196)=1;\nl_minimum(198)=1;\nl_premium(198)=1;\nl_minimum(199)=1;\nl_minimum(200)=1;\nl_premium(200)=1;\nl_minimum(203)=1;\nl_premium(203)=1;\nl_minimum(204)=1;\nl_premium(204)=1;\nl_minimum(207)=1;\nl_premium(207)=1;\nl_minimum(208)=1;\nl_premium(208)=1;\nl_minimum(210)=1;\nl_premium(210)=1;\nl_minimum(214)=1;\nl_premium(214)=1;\nl_minimum(219)=1;\nl_premium(219)=1;\nl_minimum(220)=1;\nl_premium(220)=1;\nl_minimum(223)=1;\nl_premium(223)=1;\nl_minimum(224)=1;\nl_premium(224)=1;\nl_minimum(227)=1;\nl_premium(227)=1;\nl_minimum(228)=1;\nl_premium(228)=1;\nl_minimum(230)=1;\nl_minimum(231)=1;\nl_premium(231)=1;\nl_minimum(232)=1;\nl_premium(232)=1;\nl_minimum(234)=1;\nl_minimum(235)=1;\nl_premium(235)=1;\nl_minimum(236)=1;\nl_premium(236)=1;\nl_minimum(238)=1;\nl_premium(238)=1;\nl_minimum(240)=1;\nl_minimum(242)=1;\nl_premium(242)=1;\nl_minimum(244)=1;\nl_minimum(246)=1;\nl_minimum(247)=1;\nl_premium(247)=1;\nl_minimum(248)=1;\nl_premium(248)=1;\nl_minimum(250)=1;\nl_minimum(251)=1;\nl_premium(251)=1;\nl_minimum(252)=1;\nl_premium(252)=1;\nl_minimum(254)=1;\nl_minimum(255)=1;\nl_premium(255)=1;\nl_minimum(256)=1;\nl_premium(256)=1;\nl_minimum(258)=1;\nl_premium(258)=1;\nl_minimum(259)=1;\nl_premium(259)=1;\nl_minimum(260)=1;\nl_premium(260)=1;\nl_minimum(262)=1;\nl_premium(262)=1;\nl_minimum(263)=1;\nl_premium(263)=1;\nl_init(264)=1;\nl_minimum(264)=1;\nl_premium(264)=1;\nl_minimum(266)=1;\nl_premium(266)=1;\nl_minimum(268)=1;\nl_premium(268)=1;\nl_minimum(270)=1;\nl_premium(270)=1;\nl_minimum(272)=1;\nl_premium(272)=1;\nl_minimum(274)=1;\nl_premium(274)=1;\nl_minimum(275)=1;\nl_premium(275)=1;\nl_minimum(276)=1;\nl_premium(276)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab.sta",
    "content": "% (left_n,left,right_n,right,r,line,line_n,toleft,toleft_n,toright,toright_n)\nstates=[\n0,false,0,false,false,false,false,false,false,false,false\n0,false,0,false,false,false,false,false,false,false,true\n0,false,0,false,false,false,false,false,true,false,false\n0,false,0,false,false,false,false,false,true,false,true\n0,false,0,false,false,false,true,false,false,false,false\n0,false,0,false,false,false,true,false,false,false,true\n0,false,0,false,false,false,true,false,true,false,false\n0,false,0,false,false,false,true,false,true,false,true\n0,false,0,false,true,false,false,false,false,true,false\n0,false,0,false,true,false,false,false,true,true,false\n0,false,0,false,true,false,false,true,false,false,false\n0,false,0,false,true,false,false,true,false,false,true\n0,false,0,false,true,false,true,false,false,true,false\n0,false,0,false,true,false,true,false,true,true,false\n0,false,0,false,true,false,true,true,false,false,false\n0,false,0,false,true,false,true,true,false,false,true\n0,false,0,false,true,true,false,false,false,false,false\n0,false,0,false,true,true,false,false,false,false,true\n0,false,0,false,true,true,false,false,true,false,false\n0,false,0,false,true,true,false,false,true,false,true\n0,false,0,true,true,false,false,false,false,false,false\n0,false,0,true,true,false,false,false,false,false,true\n0,false,0,true,true,false,false,false,true,false,false\n0,false,0,true,true,false,false,false,true,false,true\n0,false,0,true,true,false,true,false,false,false,false\n0,false,0,true,true,false,true,false,false,false,true\n0,false,0,true,true,false,true,false,true,false,false\n0,false,0,true,true,false,true,false,true,false,true\n0,false,1,false,false,false,false,false,false,false,false\n0,false,1,false,false,false,false,false,false,false,true\n0,false,1,false,false,false,false,false,true,false,false\n0,false,1,false,false,false,false,false,true,false,true\n0,false,1,false,false,false,true,false,false,false,false\n0,false,1,false,false,false,true,false,false,false,true\n0,false,1,false,false,false,true,false,true,false,false\n0,false,1,false,false,false,true,false,true,false,true\n0,false,1,false,true,false,false,false,false,true,false\n0,false,1,false,true,false,false,false,true,true,false\n0,false,1,false,true,false,false,true,false,false,false\n0,false,1,false,true,false,false,true,false,false,true\n0,false,1,false,true,false,true,false,false,true,false\n0,false,1,false,true,false,true,false,true,true,false\n0,false,1,false,true,false,true,true,false,false,false\n0,false,1,false,true,false,true,true,false,false,true\n0,false,1,false,true,true,false,false,false,false,false\n0,false,1,false,true,true,false,false,false,false,true\n0,false,1,false,true,true,false,false,true,false,false\n0,false,1,false,true,true,false,false,true,false,true\n0,false,1,true,true,false,false,false,false,false,false\n0,false,1,true,true,false,false,false,false,false,true\n0,false,1,true,true,false,false,false,true,false,false\n0,false,1,true,true,false,false,false,true,false,true\n0,false,1,true,true,false,true,false,false,false,false\n0,false,1,true,true,false,true,false,false,false,true\n0,false,1,true,true,false,true,false,true,false,false\n0,false,1,true,true,false,true,false,true,false,true\n0,false,2,false,false,false,false,false,false,false,false\n0,false,2,false,false,false,false,false,false,false,true\n0,false,2,false,false,false,false,false,true,false,false\n0,false,2,false,false,false,false,false,true,false,true\n0,false,2,false,false,false,true,false,false,false,false\n0,false,2,false,false,false,true,false,false,false,true\n0,false,2,false,false,false,true,false,true,false,false\n0,false,2,false,false,false,true,false,true,false,true\n0,false,2,false,true,false,false,false,false,true,false\n0,false,2,false,true,false,false,false,true,true,false\n0,false,2,false,true,false,false,true,false,false,false\n0,false,2,false,true,false,false,true,false,false,true\n0,false,2,false,true,false,true,false,false,true,false\n0,false,2,false,true,false,true,false,true,true,false\n0,false,2,false,true,false,true,true,false,false,false\n0,false,2,false,true,false,true,true,false,false,true\n0,false,2,false,true,true,false,false,false,false,false\n0,false,2,false,true,true,false,false,false,false,true\n0,false,2,false,true,true,false,false,true,false,false\n0,false,2,false,true,true,false,false,true,false,true\n0,true,0,false,true,false,false,false,false,false,false\n0,true,0,false,true,false,false,false,false,false,true\n0,true,0,false,true,false,false,false,true,false,false\n0,true,0,false,true,false,false,false,true,false,true\n0,true,0,false,true,false,true,false,false,false,false\n0,true,0,false,true,false,true,false,false,false,true\n0,true,0,false,true,false,true,false,true,false,false\n0,true,0,false,true,false,true,false,true,false,true\n0,true,1,false,true,false,false,false,false,false,false\n0,true,1,false,true,false,false,false,false,false,true\n0,true,1,false,true,false,false,false,true,false,false\n0,true,1,false,true,false,false,false,true,false,true\n0,true,1,false,true,false,true,false,false,false,false\n0,true,1,false,true,false,true,false,false,false,true\n0,true,1,false,true,false,true,false,true,false,false\n0,true,1,false,true,false,true,false,true,false,true\n0,true,2,false,true,false,false,false,false,false,false\n0,true,2,false,true,false,false,false,false,false,true\n0,true,2,false,true,false,false,false,true,false,false\n0,true,2,false,true,false,false,false,true,false,true\n0,true,2,false,true,false,true,false,false,false,false\n0,true,2,false,true,false,true,false,false,false,true\n0,true,2,false,true,false,true,false,true,false,false\n0,true,2,false,true,false,true,false,true,false,true\n1,false,0,false,false,false,false,false,false,false,false\n1,false,0,false,false,false,false,false,false,false,true\n1,false,0,false,false,false,false,false,true,false,false\n1,false,0,false,false,false,false,false,true,false,true\n1,false,0,false,false,false,true,false,false,false,false\n1,false,0,false,false,false,true,false,false,false,true\n1,false,0,false,false,false,true,false,true,false,false\n1,false,0,false,false,false,true,false,true,false,true\n1,false,0,false,true,false,false,false,false,true,false\n1,false,0,false,true,false,false,false,true,true,false\n1,false,0,false,true,false,false,true,false,false,false\n1,false,0,false,true,false,false,true,false,false,true\n1,false,0,false,true,false,true,false,false,true,false\n1,false,0,false,true,false,true,false,true,true,false\n1,false,0,false,true,false,true,true,false,false,false\n1,false,0,false,true,false,true,true,false,false,true\n1,false,0,false,true,true,false,false,false,false,false\n1,false,0,false,true,true,false,false,false,false,true\n1,false,0,false,true,true,false,false,true,false,false\n1,false,0,false,true,true,false,false,true,false,true\n1,false,0,true,true,false,false,false,false,false,false\n1,false,0,true,true,false,false,false,false,false,true\n1,false,0,true,true,false,false,false,true,false,false\n1,false,0,true,true,false,false,false,true,false,true\n1,false,0,true,true,false,true,false,false,false,false\n1,false,0,true,true,false,true,false,false,false,true\n1,false,0,true,true,false,true,false,true,false,false\n1,false,0,true,true,false,true,false,true,false,true\n1,false,1,false,false,false,false,false,false,false,false\n1,false,1,false,false,false,false,false,false,false,true\n1,false,1,false,false,false,false,false,true,false,false\n1,false,1,false,false,false,false,false,true,false,true\n1,false,1,false,false,false,true,false,false,false,false\n1,false,1,false,false,false,true,false,false,false,true\n1,false,1,false,false,false,true,false,true,false,false\n1,false,1,false,false,false,true,false,true,false,true\n1,false,1,false,true,false,false,false,false,true,false\n1,false,1,false,true,false,false,false,true,true,false\n1,false,1,false,true,false,false,true,false,false,false\n1,false,1,false,true,false,false,true,false,false,true\n1,false,1,false,true,false,true,false,false,true,false\n1,false,1,false,true,false,true,false,true,true,false\n1,false,1,false,true,false,true,true,false,false,false\n1,false,1,false,true,false,true,true,false,false,true\n1,false,1,false,true,true,false,false,false,false,false\n1,false,1,false,true,true,false,false,false,false,true\n1,false,1,false,true,true,false,false,true,false,false\n1,false,1,false,true,true,false,false,true,false,true\n1,false,1,true,true,false,false,false,false,false,false\n1,false,1,true,true,false,false,false,false,false,true\n1,false,1,true,true,false,false,false,true,false,false\n1,false,1,true,true,false,false,false,true,false,true\n1,false,1,true,true,false,true,false,false,false,false\n1,false,1,true,true,false,true,false,false,false,true\n1,false,1,true,true,false,true,false,true,false,false\n1,false,1,true,true,false,true,false,true,false,true\n1,false,2,false,false,false,false,false,false,false,false\n1,false,2,false,false,false,false,false,false,false,true\n1,false,2,false,false,false,false,false,true,false,false\n1,false,2,false,false,false,false,false,true,false,true\n1,false,2,false,false,false,true,false,false,false,false\n1,false,2,false,false,false,true,false,false,false,true\n1,false,2,false,false,false,true,false,true,false,false\n1,false,2,false,false,false,true,false,true,false,true\n1,false,2,false,true,false,false,false,false,true,false\n1,false,2,false,true,false,false,false,true,true,false\n1,false,2,false,true,false,false,true,false,false,false\n1,false,2,false,true,false,false,true,false,false,true\n1,false,2,false,true,false,true,false,false,true,false\n1,false,2,false,true,false,true,false,true,true,false\n1,false,2,false,true,false,true,true,false,false,false\n1,false,2,false,true,false,true,true,false,false,true\n1,false,2,false,true,true,false,false,false,false,false\n1,false,2,false,true,true,false,false,false,false,true\n1,false,2,false,true,true,false,false,true,false,false\n1,false,2,false,true,true,false,false,true,false,true\n1,true,0,false,true,false,false,false,false,false,false\n1,true,0,false,true,false,false,false,false,false,true\n1,true,0,false,true,false,false,false,true,false,false\n1,true,0,false,true,false,false,false,true,false,true\n1,true,0,false,true,false,true,false,false,false,false\n1,true,0,false,true,false,true,false,false,false,true\n1,true,0,false,true,false,true,false,true,false,false\n1,true,0,false,true,false,true,false,true,false,true\n1,true,1,false,true,false,false,false,false,false,false\n1,true,1,false,true,false,false,false,false,false,true\n1,true,1,false,true,false,false,false,true,false,false\n1,true,1,false,true,false,false,false,true,false,true\n1,true,1,false,true,false,true,false,false,false,false\n1,true,1,false,true,false,true,false,false,false,true\n1,true,1,false,true,false,true,false,true,false,false\n1,true,1,false,true,false,true,false,true,false,true\n1,true,2,false,true,false,false,false,false,false,false\n1,true,2,false,true,false,false,false,false,false,true\n1,true,2,false,true,false,false,false,true,false,false\n1,true,2,false,true,false,false,false,true,false,true\n1,true,2,false,true,false,true,false,false,false,false\n1,true,2,false,true,false,true,false,false,false,true\n1,true,2,false,true,false,true,false,true,false,false\n1,true,2,false,true,false,true,false,true,false,true\n2,false,0,false,false,false,false,false,false,false,false\n2,false,0,false,false,false,false,false,false,false,true\n2,false,0,false,false,false,false,false,true,false,false\n2,false,0,false,false,false,false,false,true,false,true\n2,false,0,false,false,false,true,false,false,false,false\n2,false,0,false,false,false,true,false,false,false,true\n2,false,0,false,false,false,true,false,true,false,false\n2,false,0,false,false,false,true,false,true,false,true\n2,false,0,false,true,false,false,false,false,true,false\n2,false,0,false,true,false,false,false,true,true,false\n2,false,0,false,true,false,false,true,false,false,false\n2,false,0,false,true,false,false,true,false,false,true\n2,false,0,false,true,false,true,false,false,true,false\n2,false,0,false,true,false,true,false,true,true,false\n2,false,0,false,true,false,true,true,false,false,false\n2,false,0,false,true,false,true,true,false,false,true\n2,false,0,false,true,true,false,false,false,false,false\n2,false,0,false,true,true,false,false,false,false,true\n2,false,0,false,true,true,false,false,true,false,false\n2,false,0,false,true,true,false,false,true,false,true\n2,false,0,true,true,false,false,false,false,false,false\n2,false,0,true,true,false,false,false,false,false,true\n2,false,0,true,true,false,false,false,true,false,false\n2,false,0,true,true,false,false,false,true,false,true\n2,false,0,true,true,false,true,false,false,false,false\n2,false,0,true,true,false,true,false,false,false,true\n2,false,0,true,true,false,true,false,true,false,false\n2,false,0,true,true,false,true,false,true,false,true\n2,false,1,false,false,false,false,false,false,false,false\n2,false,1,false,false,false,false,false,false,false,true\n2,false,1,false,false,false,false,false,true,false,false\n2,false,1,false,false,false,false,false,true,false,true\n2,false,1,false,false,false,true,false,false,false,false\n2,false,1,false,false,false,true,false,false,false,true\n2,false,1,false,false,false,true,false,true,false,false\n2,false,1,false,false,false,true,false,true,false,true\n2,false,1,false,true,false,false,false,false,true,false\n2,false,1,false,true,false,false,false,true,true,false\n2,false,1,false,true,false,false,true,false,false,false\n2,false,1,false,true,false,false,true,false,false,true\n2,false,1,false,true,false,true,false,false,true,false\n2,false,1,false,true,false,true,false,true,true,false\n2,false,1,false,true,false,true,true,false,false,false\n2,false,1,false,true,false,true,true,false,false,true\n2,false,1,false,true,true,false,false,false,false,false\n2,false,1,false,true,true,false,false,false,false,true\n2,false,1,false,true,true,false,false,true,false,false\n2,false,1,false,true,true,false,false,true,false,true\n2,false,1,true,true,false,false,false,false,false,false\n2,false,1,true,true,false,false,false,false,false,true\n2,false,1,true,true,false,false,false,true,false,false\n2,false,1,true,true,false,false,false,true,false,true\n2,false,1,true,true,false,true,false,false,false,false\n2,false,1,true,true,false,true,false,false,false,true\n2,false,1,true,true,false,true,false,true,false,false\n2,false,1,true,true,false,true,false,true,false,true\n2,false,2,false,false,false,false,false,false,false,false\n2,false,2,false,false,false,false,false,false,false,true\n2,false,2,false,false,false,false,false,true,false,false\n2,false,2,false,false,false,false,false,true,false,true\n2,false,2,false,false,false,true,false,false,false,false\n2,false,2,false,false,false,true,false,false,false,true\n2,false,2,false,false,false,true,false,true,false,false\n2,false,2,false,false,false,true,false,true,false,true\n2,false,2,false,true,false,false,false,false,true,false\n2,false,2,false,true,false,false,false,true,true,false\n2,false,2,false,true,false,false,true,false,false,false\n2,false,2,false,true,false,false,true,false,false,true\n2,false,2,false,true,false,true,false,false,true,false\n2,false,2,false,true,false,true,false,true,true,false\n2,false,2,false,true,false,true,true,false,false,false\n2,false,2,false,true,false,true,true,false,false,true\n2,false,2,false,true,true,false,false,false,false,false\n2,false,2,false,true,true,false,false,false,false,true\n2,false,2,false,true,true,false,false,true,false,false\n2,false,2,false,true,true,false,false,true,false,true\n];\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab.tra",
    "content": "R = sparse(276,276);\nR(1,9)=10;\nR(1,11)=10;\nR(1,17)=10;\nR(1,21)=10;\nR(1,77)=10;\nR(2,1)=0.00025;\nR(2,12)=10;\nR(2,18)=10;\nR(2,22)=10;\nR(2,78)=10;\nR(3,1)=0.00025;\nR(3,10)=10;\nR(3,19)=10;\nR(3,23)=10;\nR(3,79)=10;\nR(4,2)=0.00025;\nR(4,3)=0.00025;\nR(4,20)=10;\nR(4,24)=10;\nR(4,80)=10;\nR(5,1)=0.0002;\nR(5,13)=10;\nR(5,15)=10;\nR(5,25)=10;\nR(5,81)=10;\nR(6,2)=0.0002;\nR(6,5)=0.00025;\nR(6,16)=10;\nR(6,26)=10;\nR(6,82)=10;\nR(7,3)=0.0002;\nR(7,5)=0.00025;\nR(7,14)=10;\nR(7,27)=10;\nR(7,83)=10;\nR(8,4)=0.0002;\nR(8,6)=0.00025;\nR(8,7)=0.00025;\nR(8,28)=10;\nR(8,84)=10;\nR(9,2)=0.25;\nR(10,4)=0.25;\nR(10,9)=0.00025;\nR(11,3)=0.25;\nR(12,4)=0.25;\nR(12,11)=0.00025;\nR(13,6)=0.25;\nR(13,9)=0.0002;\nR(14,8)=0.25;\nR(14,10)=0.0002;\nR(14,13)=0.00025;\nR(15,7)=0.25;\nR(15,11)=0.0002;\nR(16,8)=0.25;\nR(16,12)=0.0002;\nR(16,15)=0.00025;\nR(17,5)=0.125;\nR(18,6)=0.125;\nR(18,17)=0.00025;\nR(19,7)=0.125;\nR(19,17)=0.00025;\nR(20,8)=0.125;\nR(20,18)=0.00025;\nR(20,19)=0.00025;\nR(21,29)=2;\nR(22,21)=0.00025;\nR(22,30)=2;\nR(23,21)=0.00025;\nR(23,31)=2;\nR(24,22)=0.00025;\nR(24,23)=0.00025;\nR(24,32)=2;\nR(25,21)=0.0002;\nR(25,33)=2;\nR(26,22)=0.0002;\nR(26,25)=0.00025;\nR(26,34)=2;\nR(27,23)=0.0002;\nR(27,25)=0.00025;\nR(27,35)=2;\nR(28,24)=0.0002;\nR(28,26)=0.00025;\nR(28,27)=0.00025;\nR(28,36)=2;\nR(29,1)=0.002;\nR(29,37)=10;\nR(29,39)=10;\nR(29,45)=10;\nR(29,49)=10;\nR(29,85)=10;\nR(30,2)=0.002;\nR(30,29)=0.00025;\nR(30,40)=10;\nR(30,46)=10;\nR(30,50)=10;\nR(30,86)=10;\nR(31,3)=0.002;\nR(31,29)=0.00025;\nR(31,38)=10;\nR(31,47)=10;\nR(31,51)=10;\nR(31,87)=10;\nR(32,4)=0.002;\nR(32,30)=0.00025;\nR(32,31)=0.00025;\nR(32,48)=10;\nR(32,52)=10;\nR(32,88)=10;\nR(33,5)=0.002;\nR(33,29)=0.0002;\nR(33,41)=10;\nR(33,43)=10;\nR(33,53)=10;\nR(33,89)=10;\nR(34,6)=0.002;\nR(34,30)=0.0002;\nR(34,33)=0.00025;\nR(34,44)=10;\nR(34,54)=10;\nR(34,90)=10;\nR(35,7)=0.002;\nR(35,31)=0.0002;\nR(35,33)=0.00025;\nR(35,42)=10;\nR(35,55)=10;\nR(35,91)=10;\nR(36,8)=0.002;\nR(36,32)=0.0002;\nR(36,34)=0.00025;\nR(36,35)=0.00025;\nR(36,56)=10;\nR(36,92)=10;\nR(37,9)=0.002;\nR(37,30)=0.25;\nR(38,10)=0.002;\nR(38,32)=0.25;\nR(38,37)=0.00025;\nR(39,11)=0.002;\nR(39,31)=0.25;\nR(40,12)=0.002;\nR(40,32)=0.25;\nR(40,39)=0.00025;\nR(41,13)=0.002;\nR(41,34)=0.25;\nR(41,37)=0.0002;\nR(42,14)=0.002;\nR(42,36)=0.25;\nR(42,38)=0.0002;\nR(42,41)=0.00025;\nR(43,15)=0.002;\nR(43,35)=0.25;\nR(43,39)=0.0002;\nR(44,16)=0.002;\nR(44,36)=0.25;\nR(44,40)=0.0002;\nR(44,43)=0.00025;\nR(45,17)=0.002;\nR(45,33)=0.125;\nR(46,18)=0.002;\nR(46,34)=0.125;\nR(46,45)=0.00025;\nR(47,19)=0.002;\nR(47,35)=0.125;\nR(47,45)=0.00025;\nR(48,20)=0.002;\nR(48,36)=0.125;\nR(48,46)=0.00025;\nR(48,47)=0.00025;\nR(49,21)=0.002;\nR(49,57)=2;\nR(50,22)=0.002;\nR(50,49)=0.00025;\nR(50,58)=2;\nR(51,23)=0.002;\nR(51,49)=0.00025;\nR(51,59)=2;\nR(52,24)=0.002;\nR(52,50)=0.00025;\nR(52,51)=0.00025;\nR(52,60)=2;\nR(53,25)=0.002;\nR(53,49)=0.0002;\nR(53,61)=2;\nR(54,26)=0.002;\nR(54,50)=0.0002;\nR(54,53)=0.00025;\nR(54,62)=2;\nR(55,27)=0.002;\nR(55,51)=0.0002;\nR(55,53)=0.00025;\nR(55,63)=2;\nR(56,28)=0.002;\nR(56,52)=0.0002;\nR(56,54)=0.00025;\nR(56,55)=0.00025;\nR(56,64)=2;\nR(57,29)=0.004;\nR(57,65)=10;\nR(57,67)=10;\nR(57,73)=10;\nR(57,93)=10;\nR(58,30)=0.004;\nR(58,57)=0.00025;\nR(58,68)=10;\nR(58,74)=10;\nR(58,94)=10;\nR(59,31)=0.004;\nR(59,57)=0.00025;\nR(59,66)=10;\nR(59,75)=10;\nR(59,95)=10;\nR(60,32)=0.004;\nR(60,58)=0.00025;\nR(60,59)=0.00025;\nR(60,76)=10;\nR(60,96)=10;\nR(61,33)=0.004;\nR(61,57)=0.0002;\nR(61,69)=10;\nR(61,71)=10;\nR(61,97)=10;\nR(62,34)=0.004;\nR(62,58)=0.0002;\nR(62,61)=0.00025;\nR(62,72)=10;\nR(62,98)=10;\nR(63,35)=0.004;\nR(63,59)=0.0002;\nR(63,61)=0.00025;\nR(63,70)=10;\nR(63,99)=10;\nR(64,36)=0.004;\nR(64,60)=0.0002;\nR(64,62)=0.00025;\nR(64,63)=0.00025;\nR(64,100)=10;\nR(65,37)=0.004;\nR(65,58)=0.25;\nR(66,38)=0.004;\nR(66,60)=0.25;\nR(66,65)=0.00025;\nR(67,39)=0.004;\nR(67,59)=0.25;\nR(68,40)=0.004;\nR(68,60)=0.25;\nR(68,67)=0.00025;\nR(69,41)=0.004;\nR(69,62)=0.25;\nR(69,65)=0.0002;\nR(70,42)=0.004;\nR(70,64)=0.25;\nR(70,66)=0.0002;\nR(70,69)=0.00025;\nR(71,43)=0.004;\nR(71,63)=0.25;\nR(71,67)=0.0002;\nR(72,44)=0.004;\nR(72,64)=0.25;\nR(72,68)=0.0002;\nR(72,71)=0.00025;\nR(73,45)=0.004;\nR(73,61)=0.125;\nR(74,46)=0.004;\nR(74,62)=0.125;\nR(74,73)=0.00025;\nR(75,47)=0.004;\nR(75,63)=0.125;\nR(75,73)=0.00025;\nR(76,48)=0.004;\nR(76,64)=0.125;\nR(76,74)=0.00025;\nR(76,75)=0.00025;\nR(77,101)=2;\nR(78,77)=0.00025;\nR(78,102)=2;\nR(79,77)=0.00025;\nR(79,103)=2;\nR(80,78)=0.00025;\nR(80,79)=0.00025;\nR(80,104)=2;\nR(81,77)=0.0002;\nR(81,105)=2;\nR(82,78)=0.0002;\nR(82,81)=0.00025;\nR(82,106)=2;\nR(83,79)=0.0002;\nR(83,81)=0.00025;\nR(83,107)=2;\nR(84,80)=0.0002;\nR(84,82)=0.00025;\nR(84,83)=0.00025;\nR(84,108)=2;\nR(85,77)=0.002;\nR(85,129)=2;\nR(86,78)=0.002;\nR(86,85)=0.00025;\nR(86,130)=2;\nR(87,79)=0.002;\nR(87,85)=0.00025;\nR(87,131)=2;\nR(88,80)=0.002;\nR(88,86)=0.00025;\nR(88,87)=0.00025;\nR(88,132)=2;\nR(89,81)=0.002;\nR(89,85)=0.0002;\nR(89,133)=2;\nR(90,82)=0.002;\nR(90,86)=0.0002;\nR(90,89)=0.00025;\nR(90,134)=2;\nR(91,83)=0.002;\nR(91,87)=0.0002;\nR(91,89)=0.00025;\nR(91,135)=2;\nR(92,84)=0.002;\nR(92,88)=0.0002;\nR(92,90)=0.00025;\nR(92,91)=0.00025;\nR(92,136)=2;\nR(93,85)=0.004;\nR(93,157)=2;\nR(94,86)=0.004;\nR(94,93)=0.00025;\nR(94,158)=2;\nR(95,87)=0.004;\nR(95,93)=0.00025;\nR(95,159)=2;\nR(96,88)=0.004;\nR(96,94)=0.00025;\nR(96,95)=0.00025;\nR(96,160)=2;\nR(97,89)=0.004;\nR(97,93)=0.0002;\nR(97,161)=2;\nR(98,90)=0.004;\nR(98,94)=0.0002;\nR(98,97)=0.00025;\nR(98,162)=2;\nR(99,91)=0.004;\nR(99,95)=0.0002;\nR(99,97)=0.00025;\nR(99,163)=2;\nR(100,92)=0.004;\nR(100,96)=0.0002;\nR(100,98)=0.00025;\nR(100,99)=0.00025;\nR(100,164)=2;\nR(101,1)=0.002;\nR(101,109)=10;\nR(101,111)=10;\nR(101,117)=10;\nR(101,121)=10;\nR(101,177)=10;\nR(102,2)=0.002;\nR(102,101)=0.00025;\nR(102,112)=10;\nR(102,118)=10;\nR(102,122)=10;\nR(102,178)=10;\nR(103,3)=0.002;\nR(103,101)=0.00025;\nR(103,110)=10;\nR(103,119)=10;\nR(103,123)=10;\nR(103,179)=10;\nR(104,4)=0.002;\nR(104,102)=0.00025;\nR(104,103)=0.00025;\nR(104,120)=10;\nR(104,124)=10;\nR(104,180)=10;\nR(105,5)=0.002;\nR(105,101)=0.0002;\nR(105,113)=10;\nR(105,115)=10;\nR(105,125)=10;\nR(105,181)=10;\nR(106,6)=0.002;\nR(106,102)=0.0002;\nR(106,105)=0.00025;\nR(106,116)=10;\nR(106,126)=10;\nR(106,182)=10;\nR(107,7)=0.002;\nR(107,103)=0.0002;\nR(107,105)=0.00025;\nR(107,114)=10;\nR(107,127)=10;\nR(107,183)=10;\nR(108,8)=0.002;\nR(108,104)=0.0002;\nR(108,106)=0.00025;\nR(108,107)=0.00025;\nR(108,128)=10;\nR(108,184)=10;\nR(109,9)=0.002;\nR(109,102)=0.25;\nR(110,10)=0.002;\nR(110,104)=0.25;\nR(110,109)=0.00025;\nR(111,11)=0.002;\nR(111,103)=0.25;\nR(112,12)=0.002;\nR(112,104)=0.25;\nR(112,111)=0.00025;\nR(113,13)=0.002;\nR(113,106)=0.25;\nR(113,109)=0.0002;\nR(114,14)=0.002;\nR(114,108)=0.25;\nR(114,110)=0.0002;\nR(114,113)=0.00025;\nR(115,15)=0.002;\nR(115,107)=0.25;\nR(115,111)=0.0002;\nR(116,16)=0.002;\nR(116,108)=0.25;\nR(116,112)=0.0002;\nR(116,115)=0.00025;\nR(117,17)=0.002;\nR(117,105)=0.125;\nR(118,18)=0.002;\nR(118,106)=0.125;\nR(118,117)=0.00025;\nR(119,19)=0.002;\nR(119,107)=0.125;\nR(119,117)=0.00025;\nR(120,20)=0.002;\nR(120,108)=0.125;\nR(120,118)=0.00025;\nR(120,119)=0.00025;\nR(121,21)=0.002;\nR(121,129)=2;\nR(122,22)=0.002;\nR(122,121)=0.00025;\nR(122,130)=2;\nR(123,23)=0.002;\nR(123,121)=0.00025;\nR(123,131)=2;\nR(124,24)=0.002;\nR(124,122)=0.00025;\nR(124,123)=0.00025;\nR(124,132)=2;\nR(125,25)=0.002;\nR(125,121)=0.0002;\nR(125,133)=2;\nR(126,26)=0.002;\nR(126,122)=0.0002;\nR(126,125)=0.00025;\nR(126,134)=2;\nR(127,27)=0.002;\nR(127,123)=0.0002;\nR(127,125)=0.00025;\nR(127,135)=2;\nR(128,28)=0.002;\nR(128,124)=0.0002;\nR(128,126)=0.00025;\nR(128,127)=0.00025;\nR(128,136)=2;\nR(129,29)=0.002;\nR(129,101)=0.002;\nR(129,137)=10;\nR(129,139)=10;\nR(129,145)=10;\nR(129,149)=10;\nR(129,185)=10;\nR(130,30)=0.002;\nR(130,102)=0.002;\nR(130,129)=0.00025;\nR(130,140)=10;\nR(130,146)=10;\nR(130,150)=10;\nR(130,186)=10;\nR(131,31)=0.002;\nR(131,103)=0.002;\nR(131,129)=0.00025;\nR(131,138)=10;\nR(131,147)=10;\nR(131,151)=10;\nR(131,187)=10;\nR(132,32)=0.002;\nR(132,104)=0.002;\nR(132,130)=0.00025;\nR(132,131)=0.00025;\nR(132,148)=10;\nR(132,152)=10;\nR(132,188)=10;\nR(133,33)=0.002;\nR(133,105)=0.002;\nR(133,129)=0.0002;\nR(133,141)=10;\nR(133,143)=10;\nR(133,153)=10;\nR(133,189)=10;\nR(134,34)=0.002;\nR(134,106)=0.002;\nR(134,130)=0.0002;\nR(134,133)=0.00025;\nR(134,144)=10;\nR(134,154)=10;\nR(134,190)=10;\nR(135,35)=0.002;\nR(135,107)=0.002;\nR(135,131)=0.0002;\nR(135,133)=0.00025;\nR(135,142)=10;\nR(135,155)=10;\nR(135,191)=10;\nR(136,36)=0.002;\nR(136,108)=0.002;\nR(136,132)=0.0002;\nR(136,134)=0.00025;\nR(136,135)=0.00025;\nR(136,156)=10;\nR(136,192)=10;\nR(137,37)=0.002;\nR(137,109)=0.002;\nR(137,130)=0.25;\nR(138,38)=0.002;\nR(138,110)=0.002;\nR(138,132)=0.25;\nR(138,137)=0.00025;\nR(139,39)=0.002;\nR(139,111)=0.002;\nR(139,131)=0.25;\nR(140,40)=0.002;\nR(140,112)=0.002;\nR(140,132)=0.25;\nR(140,139)=0.00025;\nR(141,41)=0.002;\nR(141,113)=0.002;\nR(141,134)=0.25;\nR(141,137)=0.0002;\nR(142,42)=0.002;\nR(142,114)=0.002;\nR(142,136)=0.25;\nR(142,138)=0.0002;\nR(142,141)=0.00025;\nR(143,43)=0.002;\nR(143,115)=0.002;\nR(143,135)=0.25;\nR(143,139)=0.0002;\nR(144,44)=0.002;\nR(144,116)=0.002;\nR(144,136)=0.25;\nR(144,140)=0.0002;\nR(144,143)=0.00025;\nR(145,45)=0.002;\nR(145,117)=0.002;\nR(145,133)=0.125;\nR(146,46)=0.002;\nR(146,118)=0.002;\nR(146,134)=0.125;\nR(146,145)=0.00025;\nR(147,47)=0.002;\nR(147,119)=0.002;\nR(147,135)=0.125;\nR(147,145)=0.00025;\nR(148,48)=0.002;\nR(148,120)=0.002;\nR(148,136)=0.125;\nR(148,146)=0.00025;\nR(148,147)=0.00025;\nR(149,49)=0.002;\nR(149,121)=0.002;\nR(149,157)=2;\nR(150,50)=0.002;\nR(150,122)=0.002;\nR(150,149)=0.00025;\nR(150,158)=2;\nR(151,51)=0.002;\nR(151,123)=0.002;\nR(151,149)=0.00025;\nR(151,159)=2;\nR(152,52)=0.002;\nR(152,124)=0.002;\nR(152,150)=0.00025;\nR(152,151)=0.00025;\nR(152,160)=2;\nR(153,53)=0.002;\nR(153,125)=0.002;\nR(153,149)=0.0002;\nR(153,161)=2;\nR(154,54)=0.002;\nR(154,126)=0.002;\nR(154,150)=0.0002;\nR(154,153)=0.00025;\nR(154,162)=2;\nR(155,55)=0.002;\nR(155,127)=0.002;\nR(155,151)=0.0002;\nR(155,153)=0.00025;\nR(155,163)=2;\nR(156,56)=0.002;\nR(156,128)=0.002;\nR(156,152)=0.0002;\nR(156,154)=0.00025;\nR(156,155)=0.00025;\nR(156,164)=2;\nR(157,57)=0.002;\nR(157,129)=0.004;\nR(157,165)=10;\nR(157,167)=10;\nR(157,173)=10;\nR(157,193)=10;\nR(158,58)=0.002;\nR(158,130)=0.004;\nR(158,157)=0.00025;\nR(158,168)=10;\nR(158,174)=10;\nR(158,194)=10;\nR(159,59)=0.002;\nR(159,131)=0.004;\nR(159,157)=0.00025;\nR(159,166)=10;\nR(159,175)=10;\nR(159,195)=10;\nR(160,60)=0.002;\nR(160,132)=0.004;\nR(160,158)=0.00025;\nR(160,159)=0.00025;\nR(160,176)=10;\nR(160,196)=10;\nR(161,61)=0.002;\nR(161,133)=0.004;\nR(161,157)=0.0002;\nR(161,169)=10;\nR(161,171)=10;\nR(161,197)=10;\nR(162,62)=0.002;\nR(162,134)=0.004;\nR(162,158)=0.0002;\nR(162,161)=0.00025;\nR(162,172)=10;\nR(162,198)=10;\nR(163,63)=0.002;\nR(163,135)=0.004;\nR(163,159)=0.0002;\nR(163,161)=0.00025;\nR(163,170)=10;\nR(163,199)=10;\nR(164,64)=0.002;\nR(164,136)=0.004;\nR(164,160)=0.0002;\nR(164,162)=0.00025;\nR(164,163)=0.00025;\nR(164,200)=10;\nR(165,65)=0.002;\nR(165,137)=0.004;\nR(165,158)=0.25;\nR(166,66)=0.002;\nR(166,138)=0.004;\nR(166,160)=0.25;\nR(166,165)=0.00025;\nR(167,67)=0.002;\nR(167,139)=0.004;\nR(167,159)=0.25;\nR(168,68)=0.002;\nR(168,140)=0.004;\nR(168,160)=0.25;\nR(168,167)=0.00025;\nR(169,69)=0.002;\nR(169,141)=0.004;\nR(169,162)=0.25;\nR(169,165)=0.0002;\nR(170,70)=0.002;\nR(170,142)=0.004;\nR(170,164)=0.25;\nR(170,166)=0.0002;\nR(170,169)=0.00025;\nR(171,71)=0.002;\nR(171,143)=0.004;\nR(171,163)=0.25;\nR(171,167)=0.0002;\nR(172,72)=0.002;\nR(172,144)=0.004;\nR(172,164)=0.25;\nR(172,168)=0.0002;\nR(172,171)=0.00025;\nR(173,73)=0.002;\nR(173,145)=0.004;\nR(173,161)=0.125;\nR(174,74)=0.002;\nR(174,146)=0.004;\nR(174,162)=0.125;\nR(174,173)=0.00025;\nR(175,75)=0.002;\nR(175,147)=0.004;\nR(175,163)=0.125;\nR(175,173)=0.00025;\nR(176,76)=0.002;\nR(176,148)=0.004;\nR(176,164)=0.125;\nR(176,174)=0.00025;\nR(176,175)=0.00025;\nR(177,77)=0.002;\nR(177,201)=2;\nR(178,78)=0.002;\nR(178,177)=0.00025;\nR(178,202)=2;\nR(179,79)=0.002;\nR(179,177)=0.00025;\nR(179,203)=2;\nR(180,80)=0.002;\nR(180,178)=0.00025;\nR(180,179)=0.00025;\nR(180,204)=2;\nR(181,81)=0.002;\nR(181,177)=0.0002;\nR(181,205)=2;\nR(182,82)=0.002;\nR(182,178)=0.0002;\nR(182,181)=0.00025;\nR(182,206)=2;\nR(183,83)=0.002;\nR(183,179)=0.0002;\nR(183,181)=0.00025;\nR(183,207)=2;\nR(184,84)=0.002;\nR(184,180)=0.0002;\nR(184,182)=0.00025;\nR(184,183)=0.00025;\nR(184,208)=2;\nR(185,85)=0.002;\nR(185,177)=0.002;\nR(185,229)=2;\nR(186,86)=0.002;\nR(186,178)=0.002;\nR(186,185)=0.00025;\nR(186,230)=2;\nR(187,87)=0.002;\nR(187,179)=0.002;\nR(187,185)=0.00025;\nR(187,231)=2;\nR(188,88)=0.002;\nR(188,180)=0.002;\nR(188,186)=0.00025;\nR(188,187)=0.00025;\nR(188,232)=2;\nR(189,89)=0.002;\nR(189,181)=0.002;\nR(189,185)=0.0002;\nR(189,233)=2;\nR(190,90)=0.002;\nR(190,182)=0.002;\nR(190,186)=0.0002;\nR(190,189)=0.00025;\nR(190,234)=2;\nR(191,91)=0.002;\nR(191,183)=0.002;\nR(191,187)=0.0002;\nR(191,189)=0.00025;\nR(191,235)=2;\nR(192,92)=0.002;\nR(192,184)=0.002;\nR(192,188)=0.0002;\nR(192,190)=0.00025;\nR(192,191)=0.00025;\nR(192,236)=2;\nR(193,93)=0.002;\nR(193,185)=0.004;\nR(193,257)=2;\nR(194,94)=0.002;\nR(194,186)=0.004;\nR(194,193)=0.00025;\nR(194,258)=2;\nR(195,95)=0.002;\nR(195,187)=0.004;\nR(195,193)=0.00025;\nR(195,259)=2;\nR(196,96)=0.002;\nR(196,188)=0.004;\nR(196,194)=0.00025;\nR(196,195)=0.00025;\nR(196,260)=2;\nR(197,97)=0.002;\nR(197,189)=0.004;\nR(197,193)=0.0002;\nR(197,261)=2;\nR(198,98)=0.002;\nR(198,190)=0.004;\nR(198,194)=0.0002;\nR(198,197)=0.00025;\nR(198,262)=2;\nR(199,99)=0.002;\nR(199,191)=0.004;\nR(199,195)=0.0002;\nR(199,197)=0.00025;\nR(199,263)=2;\nR(200,100)=0.002;\nR(200,192)=0.004;\nR(200,196)=0.0002;\nR(200,198)=0.00025;\nR(200,199)=0.00025;\nR(200,264)=2;\nR(201,101)=0.004;\nR(201,209)=10;\nR(201,211)=10;\nR(201,217)=10;\nR(201,221)=10;\nR(202,102)=0.004;\nR(202,201)=0.00025;\nR(202,212)=10;\nR(202,218)=10;\nR(202,222)=10;\nR(203,103)=0.004;\nR(203,201)=0.00025;\nR(203,210)=10;\nR(203,219)=10;\nR(203,223)=10;\nR(204,104)=0.004;\nR(204,202)=0.00025;\nR(204,203)=0.00025;\nR(204,220)=10;\nR(204,224)=10;\nR(205,105)=0.004;\nR(205,201)=0.0002;\nR(205,213)=10;\nR(205,215)=10;\nR(205,225)=10;\nR(206,106)=0.004;\nR(206,202)=0.0002;\nR(206,205)=0.00025;\nR(206,216)=10;\nR(206,226)=10;\nR(207,107)=0.004;\nR(207,203)=0.0002;\nR(207,205)=0.00025;\nR(207,214)=10;\nR(207,227)=10;\nR(208,108)=0.004;\nR(208,204)=0.0002;\nR(208,206)=0.00025;\nR(208,207)=0.00025;\nR(208,228)=10;\nR(209,109)=0.004;\nR(209,202)=0.25;\nR(210,110)=0.004;\nR(210,204)=0.25;\nR(210,209)=0.00025;\nR(211,111)=0.004;\nR(211,203)=0.25;\nR(212,112)=0.004;\nR(212,204)=0.25;\nR(212,211)=0.00025;\nR(213,113)=0.004;\nR(213,206)=0.25;\nR(213,209)=0.0002;\nR(214,114)=0.004;\nR(214,208)=0.25;\nR(214,210)=0.0002;\nR(214,213)=0.00025;\nR(215,115)=0.004;\nR(215,207)=0.25;\nR(215,211)=0.0002;\nR(216,116)=0.004;\nR(216,208)=0.25;\nR(216,212)=0.0002;\nR(216,215)=0.00025;\nR(217,117)=0.004;\nR(217,205)=0.125;\nR(218,118)=0.004;\nR(218,206)=0.125;\nR(218,217)=0.00025;\nR(219,119)=0.004;\nR(219,207)=0.125;\nR(219,217)=0.00025;\nR(220,120)=0.004;\nR(220,208)=0.125;\nR(220,218)=0.00025;\nR(220,219)=0.00025;\nR(221,121)=0.004;\nR(221,229)=2;\nR(222,122)=0.004;\nR(222,221)=0.00025;\nR(222,230)=2;\nR(223,123)=0.004;\nR(223,221)=0.00025;\nR(223,231)=2;\nR(224,124)=0.004;\nR(224,222)=0.00025;\nR(224,223)=0.00025;\nR(224,232)=2;\nR(225,125)=0.004;\nR(225,221)=0.0002;\nR(225,233)=2;\nR(226,126)=0.004;\nR(226,222)=0.0002;\nR(226,225)=0.00025;\nR(226,234)=2;\nR(227,127)=0.004;\nR(227,223)=0.0002;\nR(227,225)=0.00025;\nR(227,235)=2;\nR(228,128)=0.004;\nR(228,224)=0.0002;\nR(228,226)=0.00025;\nR(228,227)=0.00025;\nR(228,236)=2;\nR(229,129)=0.004;\nR(229,201)=0.002;\nR(229,237)=10;\nR(229,239)=10;\nR(229,245)=10;\nR(229,249)=10;\nR(230,130)=0.004;\nR(230,202)=0.002;\nR(230,229)=0.00025;\nR(230,240)=10;\nR(230,246)=10;\nR(230,250)=10;\nR(231,131)=0.004;\nR(231,203)=0.002;\nR(231,229)=0.00025;\nR(231,238)=10;\nR(231,247)=10;\nR(231,251)=10;\nR(232,132)=0.004;\nR(232,204)=0.002;\nR(232,230)=0.00025;\nR(232,231)=0.00025;\nR(232,248)=10;\nR(232,252)=10;\nR(233,133)=0.004;\nR(233,205)=0.002;\nR(233,229)=0.0002;\nR(233,241)=10;\nR(233,243)=10;\nR(233,253)=10;\nR(234,134)=0.004;\nR(234,206)=0.002;\nR(234,230)=0.0002;\nR(234,233)=0.00025;\nR(234,244)=10;\nR(234,254)=10;\nR(235,135)=0.004;\nR(235,207)=0.002;\nR(235,231)=0.0002;\nR(235,233)=0.00025;\nR(235,242)=10;\nR(235,255)=10;\nR(236,136)=0.004;\nR(236,208)=0.002;\nR(236,232)=0.0002;\nR(236,234)=0.00025;\nR(236,235)=0.00025;\nR(236,256)=10;\nR(237,137)=0.004;\nR(237,209)=0.002;\nR(237,230)=0.25;\nR(238,138)=0.004;\nR(238,210)=0.002;\nR(238,232)=0.25;\nR(238,237)=0.00025;\nR(239,139)=0.004;\nR(239,211)=0.002;\nR(239,231)=0.25;\nR(240,140)=0.004;\nR(240,212)=0.002;\nR(240,232)=0.25;\nR(240,239)=0.00025;\nR(241,141)=0.004;\nR(241,213)=0.002;\nR(241,234)=0.25;\nR(241,237)=0.0002;\nR(242,142)=0.004;\nR(242,214)=0.002;\nR(242,236)=0.25;\nR(242,238)=0.0002;\nR(242,241)=0.00025;\nR(243,143)=0.004;\nR(243,215)=0.002;\nR(243,235)=0.25;\nR(243,239)=0.0002;\nR(244,144)=0.004;\nR(244,216)=0.002;\nR(244,236)=0.25;\nR(244,240)=0.0002;\nR(244,243)=0.00025;\nR(245,145)=0.004;\nR(245,217)=0.002;\nR(245,233)=0.125;\nR(246,146)=0.004;\nR(246,218)=0.002;\nR(246,234)=0.125;\nR(246,245)=0.00025;\nR(247,147)=0.004;\nR(247,219)=0.002;\nR(247,235)=0.125;\nR(247,245)=0.00025;\nR(248,148)=0.004;\nR(248,220)=0.002;\nR(248,236)=0.125;\nR(248,246)=0.00025;\nR(248,247)=0.00025;\nR(249,149)=0.004;\nR(249,221)=0.002;\nR(249,257)=2;\nR(250,150)=0.004;\nR(250,222)=0.002;\nR(250,249)=0.00025;\nR(250,258)=2;\nR(251,151)=0.004;\nR(251,223)=0.002;\nR(251,249)=0.00025;\nR(251,259)=2;\nR(252,152)=0.004;\nR(252,224)=0.002;\nR(252,250)=0.00025;\nR(252,251)=0.00025;\nR(252,260)=2;\nR(253,153)=0.004;\nR(253,225)=0.002;\nR(253,249)=0.0002;\nR(253,261)=2;\nR(254,154)=0.004;\nR(254,226)=0.002;\nR(254,250)=0.0002;\nR(254,253)=0.00025;\nR(254,262)=2;\nR(255,155)=0.004;\nR(255,227)=0.002;\nR(255,251)=0.0002;\nR(255,253)=0.00025;\nR(255,263)=2;\nR(256,156)=0.004;\nR(256,228)=0.002;\nR(256,252)=0.0002;\nR(256,254)=0.00025;\nR(256,255)=0.00025;\nR(256,264)=2;\nR(257,157)=0.004;\nR(257,229)=0.004;\nR(257,265)=10;\nR(257,267)=10;\nR(257,273)=10;\nR(258,158)=0.004;\nR(258,230)=0.004;\nR(258,257)=0.00025;\nR(258,268)=10;\nR(258,274)=10;\nR(259,159)=0.004;\nR(259,231)=0.004;\nR(259,257)=0.00025;\nR(259,266)=10;\nR(259,275)=10;\nR(260,160)=0.004;\nR(260,232)=0.004;\nR(260,258)=0.00025;\nR(260,259)=0.00025;\nR(260,276)=10;\nR(261,161)=0.004;\nR(261,233)=0.004;\nR(261,257)=0.0002;\nR(261,269)=10;\nR(261,271)=10;\nR(262,162)=0.004;\nR(262,234)=0.004;\nR(262,258)=0.0002;\nR(262,261)=0.00025;\nR(262,272)=10;\nR(263,163)=0.004;\nR(263,235)=0.004;\nR(263,259)=0.0002;\nR(263,261)=0.00025;\nR(263,270)=10;\nR(264,164)=0.004;\nR(264,236)=0.004;\nR(264,260)=0.0002;\nR(264,262)=0.00025;\nR(264,263)=0.00025;\nR(265,165)=0.004;\nR(265,237)=0.004;\nR(265,258)=0.25;\nR(266,166)=0.004;\nR(266,238)=0.004;\nR(266,260)=0.25;\nR(266,265)=0.00025;\nR(267,167)=0.004;\nR(267,239)=0.004;\nR(267,259)=0.25;\nR(268,168)=0.004;\nR(268,240)=0.004;\nR(268,260)=0.25;\nR(268,267)=0.00025;\nR(269,169)=0.004;\nR(269,241)=0.004;\nR(269,262)=0.25;\nR(269,265)=0.0002;\nR(270,170)=0.004;\nR(270,242)=0.004;\nR(270,264)=0.25;\nR(270,266)=0.0002;\nR(270,269)=0.00025;\nR(271,171)=0.004;\nR(271,243)=0.004;\nR(271,263)=0.25;\nR(271,267)=0.0002;\nR(272,172)=0.004;\nR(272,244)=0.004;\nR(272,264)=0.25;\nR(272,268)=0.0002;\nR(272,271)=0.00025;\nR(273,173)=0.004;\nR(273,245)=0.004;\nR(273,261)=0.125;\nR(274,174)=0.004;\nR(274,246)=0.004;\nR(274,262)=0.125;\nR(274,273)=0.00025;\nR(275,175)=0.004;\nR(275,247)=0.004;\nR(275,263)=0.125;\nR(275,273)=0.00025;\nR(276,176)=0.004;\nR(276,248)=0.004;\nR(276,264)=0.125;\nR(276,274)=0.00025;\nR(276,275)=0.00025;\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab1.srew",
    "content": "c1 = sparse(276,1);\nc1(29)=25;\nc1(30)=25;\nc1(31)=25;\nc1(32)=25;\nc1(33)=25;\nc1(34)=25;\nc1(35)=25;\nc1(36)=25;\nc1(37)=25;\nc1(38)=25;\nc1(39)=25;\nc1(40)=25;\nc1(41)=25;\nc1(42)=25;\nc1(43)=25;\nc1(44)=25;\nc1(45)=25;\nc1(46)=25;\nc1(47)=25;\nc1(48)=25;\nc1(49)=25;\nc1(50)=25;\nc1(51)=25;\nc1(52)=25;\nc1(53)=25;\nc1(54)=25;\nc1(55)=25;\nc1(56)=25;\nc1(57)=50;\nc1(58)=50;\nc1(59)=50;\nc1(60)=50;\nc1(61)=50;\nc1(62)=50;\nc1(63)=50;\nc1(64)=50;\nc1(65)=50;\nc1(66)=50;\nc1(67)=50;\nc1(68)=50;\nc1(69)=50;\nc1(70)=50;\nc1(71)=50;\nc1(72)=50;\nc1(73)=50;\nc1(74)=50;\nc1(75)=50;\nc1(76)=50;\nc1(85)=25;\nc1(86)=25;\nc1(87)=25;\nc1(88)=25;\nc1(89)=25;\nc1(90)=25;\nc1(91)=25;\nc1(92)=25;\nc1(93)=50;\nc1(94)=50;\nc1(95)=50;\nc1(96)=50;\nc1(97)=50;\nc1(98)=50;\nc1(99)=50;\nc1(100)=50;\nc1(101)=25;\nc1(102)=25;\nc1(103)=25;\nc1(104)=25;\nc1(105)=25;\nc1(106)=25;\nc1(107)=25;\nc1(108)=25;\nc1(109)=25;\nc1(110)=25;\nc1(111)=25;\nc1(112)=25;\nc1(113)=25;\nc1(114)=25;\nc1(115)=25;\nc1(116)=25;\nc1(117)=25;\nc1(118)=25;\nc1(119)=25;\nc1(120)=25;\nc1(121)=25;\nc1(122)=25;\nc1(123)=25;\nc1(124)=25;\nc1(125)=25;\nc1(126)=25;\nc1(127)=25;\nc1(128)=25;\nc1(129)=50;\nc1(130)=50;\nc1(131)=50;\nc1(132)=50;\nc1(133)=50;\nc1(134)=50;\nc1(135)=50;\nc1(136)=50;\nc1(137)=50;\nc1(138)=50;\nc1(139)=50;\nc1(140)=50;\nc1(141)=50;\nc1(142)=50;\nc1(143)=50;\nc1(144)=50;\nc1(145)=50;\nc1(146)=50;\nc1(147)=50;\nc1(148)=50;\nc1(149)=50;\nc1(150)=50;\nc1(151)=50;\nc1(152)=50;\nc1(153)=50;\nc1(154)=50;\nc1(155)=50;\nc1(156)=50;\nc1(157)=75;\nc1(158)=75;\nc1(159)=75;\nc1(160)=75;\nc1(161)=75;\nc1(162)=75;\nc1(163)=75;\nc1(164)=75;\nc1(165)=75;\nc1(166)=75;\nc1(167)=75;\nc1(168)=75;\nc1(169)=75;\nc1(170)=75;\nc1(171)=75;\nc1(172)=75;\nc1(173)=75;\nc1(174)=75;\nc1(175)=75;\nc1(176)=75;\nc1(177)=25;\nc1(178)=25;\nc1(179)=25;\nc1(180)=25;\nc1(181)=25;\nc1(182)=25;\nc1(183)=25;\nc1(184)=25;\nc1(185)=50;\nc1(186)=50;\nc1(187)=50;\nc1(188)=50;\nc1(189)=50;\nc1(190)=50;\nc1(191)=50;\nc1(192)=50;\nc1(193)=75;\nc1(194)=75;\nc1(195)=75;\nc1(196)=75;\nc1(197)=75;\nc1(198)=75;\nc1(199)=75;\nc1(200)=75;\nc1(201)=50;\nc1(202)=50;\nc1(203)=50;\nc1(204)=50;\nc1(205)=50;\nc1(206)=50;\nc1(207)=50;\nc1(208)=50;\nc1(209)=50;\nc1(210)=50;\nc1(211)=50;\nc1(212)=50;\nc1(213)=50;\nc1(214)=50;\nc1(215)=50;\nc1(216)=50;\nc1(217)=50;\nc1(218)=50;\nc1(219)=50;\nc1(220)=50;\nc1(221)=50;\nc1(222)=50;\nc1(223)=50;\nc1(224)=50;\nc1(225)=50;\nc1(226)=50;\nc1(227)=50;\nc1(228)=50;\nc1(229)=75;\nc1(230)=75;\nc1(231)=75;\nc1(232)=75;\nc1(233)=75;\nc1(234)=75;\nc1(235)=75;\nc1(236)=75;\nc1(237)=75;\nc1(238)=75;\nc1(239)=75;\nc1(240)=75;\nc1(241)=75;\nc1(242)=75;\nc1(243)=75;\nc1(244)=75;\nc1(245)=75;\nc1(246)=75;\nc1(247)=75;\nc1(248)=75;\nc1(249)=75;\nc1(250)=75;\nc1(251)=75;\nc1(252)=75;\nc1(253)=75;\nc1(254)=75;\nc1(255)=75;\nc1(256)=75;\nc1(257)=100;\nc1(258)=100;\nc1(259)=100;\nc1(260)=100;\nc1(261)=100;\nc1(262)=100;\nc1(263)=100;\nc1(264)=100;\nc1(265)=100;\nc1(266)=100;\nc1(267)=100;\nc1(268)=100;\nc1(269)=100;\nc1(270)=100;\nc1(271)=100;\nc1(272)=100;\nc1(273)=100;\nc1(274)=100;\nc1(275)=100;\nc1(276)=100;\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab1.trew",
    "content": "C1 = sparse(276,276);\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab2.srew",
    "content": "c2 = sparse(276,1);\nc2(1)=1;\nc2(2)=1;\nc2(3)=1;\nc2(4)=1;\nc2(5)=1;\nc2(6)=1;\nc2(7)=1;\nc2(8)=1;\nc2(9)=1;\nc2(10)=1;\nc2(11)=1;\nc2(12)=1;\nc2(13)=1;\nc2(14)=1;\nc2(15)=1;\nc2(16)=1;\nc2(17)=1;\nc2(18)=1;\nc2(19)=1;\nc2(20)=1;\nc2(21)=1;\nc2(22)=1;\nc2(23)=1;\nc2(24)=1;\nc2(25)=1;\nc2(26)=1;\nc2(27)=1;\nc2(28)=1;\nc2(29)=1;\nc2(31)=1;\nc2(33)=1;\nc2(35)=1;\nc2(37)=1;\nc2(38)=1;\nc2(39)=1;\nc2(41)=1;\nc2(42)=1;\nc2(43)=1;\nc2(45)=1;\nc2(47)=1;\nc2(49)=1;\nc2(51)=1;\nc2(53)=1;\nc2(55)=1;\nc2(57)=1;\nc2(59)=1;\nc2(61)=1;\nc2(63)=1;\nc2(65)=1;\nc2(66)=1;\nc2(67)=1;\nc2(69)=1;\nc2(70)=1;\nc2(71)=1;\nc2(73)=1;\nc2(75)=1;\nc2(77)=1;\nc2(78)=1;\nc2(79)=1;\nc2(80)=1;\nc2(81)=1;\nc2(82)=1;\nc2(83)=1;\nc2(84)=1;\nc2(85)=1;\nc2(87)=1;\nc2(89)=1;\nc2(91)=1;\nc2(93)=1;\nc2(95)=1;\nc2(97)=1;\nc2(99)=1;\nc2(101)=1;\nc2(102)=1;\nc2(105)=1;\nc2(106)=1;\nc2(109)=1;\nc2(111)=1;\nc2(112)=1;\nc2(113)=1;\nc2(115)=1;\nc2(116)=1;\nc2(117)=1;\nc2(118)=1;\nc2(121)=1;\nc2(122)=1;\nc2(125)=1;\nc2(126)=1;\nc2(129)=1;\nc2(133)=1;\nc2(137)=1;\nc2(139)=1;\nc2(141)=1;\nc2(143)=1;\nc2(145)=1;\nc2(149)=1;\nc2(153)=1;\nc2(157)=1;\nc2(161)=1;\nc2(165)=1;\nc2(167)=1;\nc2(169)=1;\nc2(171)=1;\nc2(173)=1;\nc2(177)=1;\nc2(178)=1;\nc2(181)=1;\nc2(182)=1;\nc2(185)=1;\nc2(189)=1;\nc2(193)=1;\nc2(197)=1;\nc2(201)=1;\nc2(202)=1;\nc2(205)=1;\nc2(206)=1;\nc2(209)=1;\nc2(211)=1;\nc2(212)=1;\nc2(213)=1;\nc2(215)=1;\nc2(216)=1;\nc2(217)=1;\nc2(218)=1;\nc2(221)=1;\nc2(222)=1;\nc2(225)=1;\nc2(226)=1;\nc2(229)=1;\nc2(233)=1;\nc2(237)=1;\nc2(239)=1;\nc2(241)=1;\nc2(243)=1;\nc2(245)=1;\nc2(249)=1;\nc2(253)=1;\nc2(257)=1;\nc2(261)=1;\nc2(265)=1;\nc2(267)=1;\nc2(269)=1;\nc2(271)=1;\nc2(273)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab2.trew",
    "content": "C2 = sparse(276,276);\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab3.srew",
    "content": "c3 = sparse(276,1);\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.matlab3.trew",
    "content": "C3 = sparse(276,276);\nC3(9,2)=1;\nC3(10,4)=1;\nC3(11,3)=1;\nC3(12,4)=1;\nC3(13,6)=1;\nC3(14,8)=1;\nC3(15,7)=1;\nC3(16,8)=1;\nC3(17,5)=1;\nC3(18,6)=1;\nC3(19,7)=1;\nC3(20,8)=1;\nC3(21,29)=1;\nC3(22,30)=1;\nC3(23,31)=1;\nC3(24,32)=1;\nC3(25,33)=1;\nC3(26,34)=1;\nC3(27,35)=1;\nC3(28,36)=1;\nC3(37,30)=1;\nC3(38,32)=1;\nC3(39,31)=1;\nC3(40,32)=1;\nC3(41,34)=1;\nC3(42,36)=1;\nC3(43,35)=1;\nC3(44,36)=1;\nC3(45,33)=1;\nC3(46,34)=1;\nC3(47,35)=1;\nC3(48,36)=1;\nC3(49,57)=1;\nC3(50,58)=1;\nC3(51,59)=1;\nC3(52,60)=1;\nC3(53,61)=1;\nC3(54,62)=1;\nC3(55,63)=1;\nC3(56,64)=1;\nC3(65,58)=1;\nC3(66,60)=1;\nC3(67,59)=1;\nC3(68,60)=1;\nC3(69,62)=1;\nC3(70,64)=1;\nC3(71,63)=1;\nC3(72,64)=1;\nC3(73,61)=1;\nC3(74,62)=1;\nC3(75,63)=1;\nC3(76,64)=1;\nC3(77,101)=1;\nC3(78,102)=1;\nC3(79,103)=1;\nC3(80,104)=1;\nC3(81,105)=1;\nC3(82,106)=1;\nC3(83,107)=1;\nC3(84,108)=1;\nC3(85,129)=1;\nC3(86,130)=1;\nC3(87,131)=1;\nC3(88,132)=1;\nC3(89,133)=1;\nC3(90,134)=1;\nC3(91,135)=1;\nC3(92,136)=1;\nC3(93,157)=1;\nC3(94,158)=1;\nC3(95,159)=1;\nC3(96,160)=1;\nC3(97,161)=1;\nC3(98,162)=1;\nC3(99,163)=1;\nC3(100,164)=1;\nC3(109,102)=1;\nC3(110,104)=1;\nC3(111,103)=1;\nC3(112,104)=1;\nC3(113,106)=1;\nC3(114,108)=1;\nC3(115,107)=1;\nC3(116,108)=1;\nC3(117,105)=1;\nC3(118,106)=1;\nC3(119,107)=1;\nC3(120,108)=1;\nC3(121,129)=1;\nC3(122,130)=1;\nC3(123,131)=1;\nC3(124,132)=1;\nC3(125,133)=1;\nC3(126,134)=1;\nC3(127,135)=1;\nC3(128,136)=1;\nC3(137,130)=1;\nC3(138,132)=1;\nC3(139,131)=1;\nC3(140,132)=1;\nC3(141,134)=1;\nC3(142,136)=1;\nC3(143,135)=1;\nC3(144,136)=1;\nC3(145,133)=1;\nC3(146,134)=1;\nC3(147,135)=1;\nC3(148,136)=1;\nC3(149,157)=1;\nC3(150,158)=1;\nC3(151,159)=1;\nC3(152,160)=1;\nC3(153,161)=1;\nC3(154,162)=1;\nC3(155,163)=1;\nC3(156,164)=1;\nC3(165,158)=1;\nC3(166,160)=1;\nC3(167,159)=1;\nC3(168,160)=1;\nC3(169,162)=1;\nC3(170,164)=1;\nC3(171,163)=1;\nC3(172,164)=1;\nC3(173,161)=1;\nC3(174,162)=1;\nC3(175,163)=1;\nC3(176,164)=1;\nC3(177,201)=1;\nC3(178,202)=1;\nC3(179,203)=1;\nC3(180,204)=1;\nC3(181,205)=1;\nC3(182,206)=1;\nC3(183,207)=1;\nC3(184,208)=1;\nC3(185,229)=1;\nC3(186,230)=1;\nC3(187,231)=1;\nC3(188,232)=1;\nC3(189,233)=1;\nC3(190,234)=1;\nC3(191,235)=1;\nC3(192,236)=1;\nC3(193,257)=1;\nC3(194,258)=1;\nC3(195,259)=1;\nC3(196,260)=1;\nC3(197,261)=1;\nC3(198,262)=1;\nC3(199,263)=1;\nC3(200,264)=1;\nC3(209,202)=1;\nC3(210,204)=1;\nC3(211,203)=1;\nC3(212,204)=1;\nC3(213,206)=1;\nC3(214,208)=1;\nC3(215,207)=1;\nC3(216,208)=1;\nC3(217,205)=1;\nC3(218,206)=1;\nC3(219,207)=1;\nC3(220,208)=1;\nC3(221,229)=1;\nC3(222,230)=1;\nC3(223,231)=1;\nC3(224,232)=1;\nC3(225,233)=1;\nC3(226,234)=1;\nC3(227,235)=1;\nC3(228,236)=1;\nC3(237,230)=1;\nC3(238,232)=1;\nC3(239,231)=1;\nC3(240,232)=1;\nC3(241,234)=1;\nC3(242,236)=1;\nC3(243,235)=1;\nC3(244,236)=1;\nC3(245,233)=1;\nC3(246,234)=1;\nC3(247,235)=1;\nC3(248,236)=1;\nC3(249,257)=1;\nC3(250,258)=1;\nC3(251,259)=1;\nC3(252,260)=1;\nC3(253,261)=1;\nC3(254,262)=1;\nC3(255,263)=1;\nC3(256,264)=1;\nC3(265,258)=1;\nC3(266,260)=1;\nC3(267,259)=1;\nC3(268,260)=1;\nC3(269,262)=1;\nC3(270,264)=1;\nC3(271,263)=1;\nC3(272,264)=1;\nC3(273,261)=1;\nC3(274,262)=1;\nC3(275,263)=1;\nC3(276,264)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"minimum\" 3=\"premium\"\n29: 2\n31: 2\n33: 2\n35: 2\n39: 2\n43: 2\n45: 2\n47: 2\n49: 2\n51: 2\n53: 2\n55: 2\n57: 2 3\n59: 2 3\n61: 2 3\n63: 2 3\n67: 2 3\n71: 2 3\n73: 2 3\n75: 2 3\n85: 2\n87: 2\n89: 2\n91: 2\n93: 2 3\n95: 2 3\n97: 2 3\n99: 2 3\n102: 2\n103: 2\n106: 2\n107: 2\n109: 2\n113: 2\n118: 2\n119: 2\n122: 2\n123: 2\n126: 2\n127: 2\n129: 2\n130: 2\n131: 2\n133: 2\n134: 2\n135: 2 3\n137: 2\n139: 2\n141: 2\n143: 2\n145: 2\n146: 2\n147: 2\n149: 2\n150: 2\n151: 2\n153: 2\n154: 2\n155: 2 3\n157: 2 3\n158: 2\n159: 2 3\n161: 2 3\n162: 2\n163: 2 3\n165: 2\n167: 2 3\n169: 2\n171: 2 3\n173: 2 3\n174: 2\n175: 2 3\n178: 2\n179: 2\n182: 2\n183: 2\n185: 2\n186: 2\n187: 2\n189: 2\n190: 2\n191: 2 3\n193: 2 3\n194: 2\n195: 2 3\n197: 2 3\n198: 2\n199: 2 3\n202: 2 3\n203: 2 3\n206: 2 3\n207: 2 3\n209: 2 3\n213: 2 3\n218: 2 3\n219: 2 3\n222: 2 3\n223: 2 3\n226: 2 3\n227: 2 3\n229: 2\n230: 2 3\n231: 2 3\n233: 2\n234: 2 3\n235: 2 3\n237: 2 3\n239: 2\n241: 2 3\n243: 2\n245: 2\n246: 2 3\n247: 2 3\n249: 2\n250: 2 3\n251: 2 3\n253: 2\n254: 2 3\n255: 2 3\n257: 2 3\n258: 2 3\n259: 2 3\n261: 2 3\n262: 2 3\n263: 0 2 3\n265: 2 3\n267: 2 3\n269: 2 3\n271: 2 3\n273: 2 3\n274: 2 3\n275: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows.sta",
    "content": "(left_n,left,right_n,right,r,line,line_n,toleft,toleft_n,toright,toright_n)\n0:(0,false,0,false,false,false,false,false,false,false,false)\n1:(0,false,0,false,false,false,false,false,false,false,true)\n2:(0,false,0,false,false,false,false,false,true,false,false)\n3:(0,false,0,false,false,false,false,false,true,false,true)\n4:(0,false,0,false,false,false,true,false,false,false,false)\n5:(0,false,0,false,false,false,true,false,false,false,true)\n6:(0,false,0,false,false,false,true,false,true,false,false)\n7:(0,false,0,false,false,false,true,false,true,false,true)\n8:(0,false,0,false,true,false,false,false,false,true,false)\n9:(0,false,0,false,true,false,false,false,true,true,false)\n10:(0,false,0,false,true,false,false,true,false,false,false)\n11:(0,false,0,false,true,false,false,true,false,false,true)\n12:(0,false,0,false,true,false,true,false,false,true,false)\n13:(0,false,0,false,true,false,true,false,true,true,false)\n14:(0,false,0,false,true,false,true,true,false,false,false)\n15:(0,false,0,false,true,false,true,true,false,false,true)\n16:(0,false,0,false,true,true,false,false,false,false,false)\n17:(0,false,0,false,true,true,false,false,false,false,true)\n18:(0,false,0,false,true,true,false,false,true,false,false)\n19:(0,false,0,false,true,true,false,false,true,false,true)\n20:(0,false,0,true,true,false,false,false,false,false,false)\n21:(0,false,0,true,true,false,false,false,false,false,true)\n22:(0,false,0,true,true,false,false,false,true,false,false)\n23:(0,false,0,true,true,false,false,false,true,false,true)\n24:(0,false,0,true,true,false,true,false,false,false,false)\n25:(0,false,0,true,true,false,true,false,false,false,true)\n26:(0,false,0,true,true,false,true,false,true,false,false)\n27:(0,false,0,true,true,false,true,false,true,false,true)\n28:(0,false,1,false,false,false,false,false,false,false,false)\n29:(0,false,1,false,false,false,false,false,false,false,true)\n30:(0,false,1,false,false,false,false,false,true,false,false)\n31:(0,false,1,false,false,false,false,false,true,false,true)\n32:(0,false,1,false,false,false,true,false,false,false,false)\n33:(0,false,1,false,false,false,true,false,false,false,true)\n34:(0,false,1,false,false,false,true,false,true,false,false)\n35:(0,false,1,false,false,false,true,false,true,false,true)\n36:(0,false,1,false,true,false,false,false,false,true,false)\n37:(0,false,1,false,true,false,false,false,true,true,false)\n38:(0,false,1,false,true,false,false,true,false,false,false)\n39:(0,false,1,false,true,false,false,true,false,false,true)\n40:(0,false,1,false,true,false,true,false,false,true,false)\n41:(0,false,1,false,true,false,true,false,true,true,false)\n42:(0,false,1,false,true,false,true,true,false,false,false)\n43:(0,false,1,false,true,false,true,true,false,false,true)\n44:(0,false,1,false,true,true,false,false,false,false,false)\n45:(0,false,1,false,true,true,false,false,false,false,true)\n46:(0,false,1,false,true,true,false,false,true,false,false)\n47:(0,false,1,false,true,true,false,false,true,false,true)\n48:(0,false,1,true,true,false,false,false,false,false,false)\n49:(0,false,1,true,true,false,false,false,false,false,true)\n50:(0,false,1,true,true,false,false,false,true,false,false)\n51:(0,false,1,true,true,false,false,false,true,false,true)\n52:(0,false,1,true,true,false,true,false,false,false,false)\n53:(0,false,1,true,true,false,true,false,false,false,true)\n54:(0,false,1,true,true,false,true,false,true,false,false)\n55:(0,false,1,true,true,false,true,false,true,false,true)\n56:(0,false,2,false,false,false,false,false,false,false,false)\n57:(0,false,2,false,false,false,false,false,false,false,true)\n58:(0,false,2,false,false,false,false,false,true,false,false)\n59:(0,false,2,false,false,false,false,false,true,false,true)\n60:(0,false,2,false,false,false,true,false,false,false,false)\n61:(0,false,2,false,false,false,true,false,false,false,true)\n62:(0,false,2,false,false,false,true,false,true,false,false)\n63:(0,false,2,false,false,false,true,false,true,false,true)\n64:(0,false,2,false,true,false,false,false,false,true,false)\n65:(0,false,2,false,true,false,false,false,true,true,false)\n66:(0,false,2,false,true,false,false,true,false,false,false)\n67:(0,false,2,false,true,false,false,true,false,false,true)\n68:(0,false,2,false,true,false,true,false,false,true,false)\n69:(0,false,2,false,true,false,true,false,true,true,false)\n70:(0,false,2,false,true,false,true,true,false,false,false)\n71:(0,false,2,false,true,false,true,true,false,false,true)\n72:(0,false,2,false,true,true,false,false,false,false,false)\n73:(0,false,2,false,true,true,false,false,false,false,true)\n74:(0,false,2,false,true,true,false,false,true,false,false)\n75:(0,false,2,false,true,true,false,false,true,false,true)\n76:(0,true,0,false,true,false,false,false,false,false,false)\n77:(0,true,0,false,true,false,false,false,false,false,true)\n78:(0,true,0,false,true,false,false,false,true,false,false)\n79:(0,true,0,false,true,false,false,false,true,false,true)\n80:(0,true,0,false,true,false,true,false,false,false,false)\n81:(0,true,0,false,true,false,true,false,false,false,true)\n82:(0,true,0,false,true,false,true,false,true,false,false)\n83:(0,true,0,false,true,false,true,false,true,false,true)\n84:(0,true,1,false,true,false,false,false,false,false,false)\n85:(0,true,1,false,true,false,false,false,false,false,true)\n86:(0,true,1,false,true,false,false,false,true,false,false)\n87:(0,true,1,false,true,false,false,false,true,false,true)\n88:(0,true,1,false,true,false,true,false,false,false,false)\n89:(0,true,1,false,true,false,true,false,false,false,true)\n90:(0,true,1,false,true,false,true,false,true,false,false)\n91:(0,true,1,false,true,false,true,false,true,false,true)\n92:(0,true,2,false,true,false,false,false,false,false,false)\n93:(0,true,2,false,true,false,false,false,false,false,true)\n94:(0,true,2,false,true,false,false,false,true,false,false)\n95:(0,true,2,false,true,false,false,false,true,false,true)\n96:(0,true,2,false,true,false,true,false,false,false,false)\n97:(0,true,2,false,true,false,true,false,false,false,true)\n98:(0,true,2,false,true,false,true,false,true,false,false)\n99:(0,true,2,false,true,false,true,false,true,false,true)\n100:(1,false,0,false,false,false,false,false,false,false,false)\n101:(1,false,0,false,false,false,false,false,false,false,true)\n102:(1,false,0,false,false,false,false,false,true,false,false)\n103:(1,false,0,false,false,false,false,false,true,false,true)\n104:(1,false,0,false,false,false,true,false,false,false,false)\n105:(1,false,0,false,false,false,true,false,false,false,true)\n106:(1,false,0,false,false,false,true,false,true,false,false)\n107:(1,false,0,false,false,false,true,false,true,false,true)\n108:(1,false,0,false,true,false,false,false,false,true,false)\n109:(1,false,0,false,true,false,false,false,true,true,false)\n110:(1,false,0,false,true,false,false,true,false,false,false)\n111:(1,false,0,false,true,false,false,true,false,false,true)\n112:(1,false,0,false,true,false,true,false,false,true,false)\n113:(1,false,0,false,true,false,true,false,true,true,false)\n114:(1,false,0,false,true,false,true,true,false,false,false)\n115:(1,false,0,false,true,false,true,true,false,false,true)\n116:(1,false,0,false,true,true,false,false,false,false,false)\n117:(1,false,0,false,true,true,false,false,false,false,true)\n118:(1,false,0,false,true,true,false,false,true,false,false)\n119:(1,false,0,false,true,true,false,false,true,false,true)\n120:(1,false,0,true,true,false,false,false,false,false,false)\n121:(1,false,0,true,true,false,false,false,false,false,true)\n122:(1,false,0,true,true,false,false,false,true,false,false)\n123:(1,false,0,true,true,false,false,false,true,false,true)\n124:(1,false,0,true,true,false,true,false,false,false,false)\n125:(1,false,0,true,true,false,true,false,false,false,true)\n126:(1,false,0,true,true,false,true,false,true,false,false)\n127:(1,false,0,true,true,false,true,false,true,false,true)\n128:(1,false,1,false,false,false,false,false,false,false,false)\n129:(1,false,1,false,false,false,false,false,false,false,true)\n130:(1,false,1,false,false,false,false,false,true,false,false)\n131:(1,false,1,false,false,false,false,false,true,false,true)\n132:(1,false,1,false,false,false,true,false,false,false,false)\n133:(1,false,1,false,false,false,true,false,false,false,true)\n134:(1,false,1,false,false,false,true,false,true,false,false)\n135:(1,false,1,false,false,false,true,false,true,false,true)\n136:(1,false,1,false,true,false,false,false,false,true,false)\n137:(1,false,1,false,true,false,false,false,true,true,false)\n138:(1,false,1,false,true,false,false,true,false,false,false)\n139:(1,false,1,false,true,false,false,true,false,false,true)\n140:(1,false,1,false,true,false,true,false,false,true,false)\n141:(1,false,1,false,true,false,true,false,true,true,false)\n142:(1,false,1,false,true,false,true,true,false,false,false)\n143:(1,false,1,false,true,false,true,true,false,false,true)\n144:(1,false,1,false,true,true,false,false,false,false,false)\n145:(1,false,1,false,true,true,false,false,false,false,true)\n146:(1,false,1,false,true,true,false,false,true,false,false)\n147:(1,false,1,false,true,true,false,false,true,false,true)\n148:(1,false,1,true,true,false,false,false,false,false,false)\n149:(1,false,1,true,true,false,false,false,false,false,true)\n150:(1,false,1,true,true,false,false,false,true,false,false)\n151:(1,false,1,true,true,false,false,false,true,false,true)\n152:(1,false,1,true,true,false,true,false,false,false,false)\n153:(1,false,1,true,true,false,true,false,false,false,true)\n154:(1,false,1,true,true,false,true,false,true,false,false)\n155:(1,false,1,true,true,false,true,false,true,false,true)\n156:(1,false,2,false,false,false,false,false,false,false,false)\n157:(1,false,2,false,false,false,false,false,false,false,true)\n158:(1,false,2,false,false,false,false,false,true,false,false)\n159:(1,false,2,false,false,false,false,false,true,false,true)\n160:(1,false,2,false,false,false,true,false,false,false,false)\n161:(1,false,2,false,false,false,true,false,false,false,true)\n162:(1,false,2,false,false,false,true,false,true,false,false)\n163:(1,false,2,false,false,false,true,false,true,false,true)\n164:(1,false,2,false,true,false,false,false,false,true,false)\n165:(1,false,2,false,true,false,false,false,true,true,false)\n166:(1,false,2,false,true,false,false,true,false,false,false)\n167:(1,false,2,false,true,false,false,true,false,false,true)\n168:(1,false,2,false,true,false,true,false,false,true,false)\n169:(1,false,2,false,true,false,true,false,true,true,false)\n170:(1,false,2,false,true,false,true,true,false,false,false)\n171:(1,false,2,false,true,false,true,true,false,false,true)\n172:(1,false,2,false,true,true,false,false,false,false,false)\n173:(1,false,2,false,true,true,false,false,false,false,true)\n174:(1,false,2,false,true,true,false,false,true,false,false)\n175:(1,false,2,false,true,true,false,false,true,false,true)\n176:(1,true,0,false,true,false,false,false,false,false,false)\n177:(1,true,0,false,true,false,false,false,false,false,true)\n178:(1,true,0,false,true,false,false,false,true,false,false)\n179:(1,true,0,false,true,false,false,false,true,false,true)\n180:(1,true,0,false,true,false,true,false,false,false,false)\n181:(1,true,0,false,true,false,true,false,false,false,true)\n182:(1,true,0,false,true,false,true,false,true,false,false)\n183:(1,true,0,false,true,false,true,false,true,false,true)\n184:(1,true,1,false,true,false,false,false,false,false,false)\n185:(1,true,1,false,true,false,false,false,false,false,true)\n186:(1,true,1,false,true,false,false,false,true,false,false)\n187:(1,true,1,false,true,false,false,false,true,false,true)\n188:(1,true,1,false,true,false,true,false,false,false,false)\n189:(1,true,1,false,true,false,true,false,false,false,true)\n190:(1,true,1,false,true,false,true,false,true,false,false)\n191:(1,true,1,false,true,false,true,false,true,false,true)\n192:(1,true,2,false,true,false,false,false,false,false,false)\n193:(1,true,2,false,true,false,false,false,false,false,true)\n194:(1,true,2,false,true,false,false,false,true,false,false)\n195:(1,true,2,false,true,false,false,false,true,false,true)\n196:(1,true,2,false,true,false,true,false,false,false,false)\n197:(1,true,2,false,true,false,true,false,false,false,true)\n198:(1,true,2,false,true,false,true,false,true,false,false)\n199:(1,true,2,false,true,false,true,false,true,false,true)\n200:(2,false,0,false,false,false,false,false,false,false,false)\n201:(2,false,0,false,false,false,false,false,false,false,true)\n202:(2,false,0,false,false,false,false,false,true,false,false)\n203:(2,false,0,false,false,false,false,false,true,false,true)\n204:(2,false,0,false,false,false,true,false,false,false,false)\n205:(2,false,0,false,false,false,true,false,false,false,true)\n206:(2,false,0,false,false,false,true,false,true,false,false)\n207:(2,false,0,false,false,false,true,false,true,false,true)\n208:(2,false,0,false,true,false,false,false,false,true,false)\n209:(2,false,0,false,true,false,false,false,true,true,false)\n210:(2,false,0,false,true,false,false,true,false,false,false)\n211:(2,false,0,false,true,false,false,true,false,false,true)\n212:(2,false,0,false,true,false,true,false,false,true,false)\n213:(2,false,0,false,true,false,true,false,true,true,false)\n214:(2,false,0,false,true,false,true,true,false,false,false)\n215:(2,false,0,false,true,false,true,true,false,false,true)\n216:(2,false,0,false,true,true,false,false,false,false,false)\n217:(2,false,0,false,true,true,false,false,false,false,true)\n218:(2,false,0,false,true,true,false,false,true,false,false)\n219:(2,false,0,false,true,true,false,false,true,false,true)\n220:(2,false,0,true,true,false,false,false,false,false,false)\n221:(2,false,0,true,true,false,false,false,false,false,true)\n222:(2,false,0,true,true,false,false,false,true,false,false)\n223:(2,false,0,true,true,false,false,false,true,false,true)\n224:(2,false,0,true,true,false,true,false,false,false,false)\n225:(2,false,0,true,true,false,true,false,false,false,true)\n226:(2,false,0,true,true,false,true,false,true,false,false)\n227:(2,false,0,true,true,false,true,false,true,false,true)\n228:(2,false,1,false,false,false,false,false,false,false,false)\n229:(2,false,1,false,false,false,false,false,false,false,true)\n230:(2,false,1,false,false,false,false,false,true,false,false)\n231:(2,false,1,false,false,false,false,false,true,false,true)\n232:(2,false,1,false,false,false,true,false,false,false,false)\n233:(2,false,1,false,false,false,true,false,false,false,true)\n234:(2,false,1,false,false,false,true,false,true,false,false)\n235:(2,false,1,false,false,false,true,false,true,false,true)\n236:(2,false,1,false,true,false,false,false,false,true,false)\n237:(2,false,1,false,true,false,false,false,true,true,false)\n238:(2,false,1,false,true,false,false,true,false,false,false)\n239:(2,false,1,false,true,false,false,true,false,false,true)\n240:(2,false,1,false,true,false,true,false,false,true,false)\n241:(2,false,1,false,true,false,true,false,true,true,false)\n242:(2,false,1,false,true,false,true,true,false,false,false)\n243:(2,false,1,false,true,false,true,true,false,false,true)\n244:(2,false,1,false,true,true,false,false,false,false,false)\n245:(2,false,1,false,true,true,false,false,false,false,true)\n246:(2,false,1,false,true,true,false,false,true,false,false)\n247:(2,false,1,false,true,true,false,false,true,false,true)\n248:(2,false,1,true,true,false,false,false,false,false,false)\n249:(2,false,1,true,true,false,false,false,false,false,true)\n250:(2,false,1,true,true,false,false,false,true,false,false)\n251:(2,false,1,true,true,false,false,false,true,false,true)\n252:(2,false,1,true,true,false,true,false,false,false,false)\n253:(2,false,1,true,true,false,true,false,false,false,true)\n254:(2,false,1,true,true,false,true,false,true,false,false)\n255:(2,false,1,true,true,false,true,false,true,false,true)\n256:(2,false,2,false,false,false,false,false,false,false,false)\n257:(2,false,2,false,false,false,false,false,false,false,true)\n258:(2,false,2,false,false,false,false,false,true,false,false)\n259:(2,false,2,false,false,false,false,false,true,false,true)\n260:(2,false,2,false,false,false,true,false,false,false,false)\n261:(2,false,2,false,false,false,true,false,false,false,true)\n262:(2,false,2,false,false,false,true,false,true,false,false)\n263:(2,false,2,false,false,false,true,false,true,false,true)\n264:(2,false,2,false,true,false,false,false,false,true,false)\n265:(2,false,2,false,true,false,false,false,true,true,false)\n266:(2,false,2,false,true,false,false,true,false,false,false)\n267:(2,false,2,false,true,false,false,true,false,false,true)\n268:(2,false,2,false,true,false,true,false,false,true,false)\n269:(2,false,2,false,true,false,true,false,true,true,false)\n270:(2,false,2,false,true,false,true,true,false,false,false)\n271:(2,false,2,false,true,false,true,true,false,false,true)\n272:(2,false,2,false,true,true,false,false,false,false,false)\n273:(2,false,2,false,true,true,false,false,false,false,true)\n274:(2,false,2,false,true,true,false,false,true,false,false)\n275:(2,false,2,false,true,true,false,false,true,false,true)\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows.tra",
    "content": "276 1120\n0 10:8 10:10 10:16 10:20 10:76\n1 0.00025:0 10:11 10:17 10:21 10:77\n2 0.00025:0 10:9 10:18 10:22 10:78\n3 0.00025:1 0.00025:2 10:19 10:23 10:79\n4 0.0002:0 10:12 10:14 10:24 10:80\n5 0.0002:1 0.00025:4 10:15 10:25 10:81\n6 0.0002:2 0.00025:4 10:13 10:26 10:82\n7 0.0002:3 0.00025:5 0.00025:6 10:27 10:83\n8 0.25:1\n9 0.25:3 0.00025:8\n10 0.25:2\n11 0.25:3 0.00025:10\n12 0.25:5 0.0002:8\n13 0.25:7 0.0002:9 0.00025:12\n14 0.25:6 0.0002:10\n15 0.25:7 0.0002:11 0.00025:14\n16 0.125:4\n17 0.125:5 0.00025:16\n18 0.125:6 0.00025:16\n19 0.125:7 0.00025:17 0.00025:18\n20 2:28\n21 0.00025:20 2:29\n22 0.00025:20 2:30\n23 0.00025:21 0.00025:22 2:31\n24 0.0002:20 2:32\n25 0.0002:21 0.00025:24 2:33\n26 0.0002:22 0.00025:24 2:34\n27 0.0002:23 0.00025:25 0.00025:26 2:35\n28 0.002:0 10:36 10:38 10:44 10:48 10:84\n29 0.002:1 0.00025:28 10:39 10:45 10:49 10:85\n30 0.002:2 0.00025:28 10:37 10:46 10:50 10:86\n31 0.002:3 0.00025:29 0.00025:30 10:47 10:51 10:87\n32 0.002:4 0.0002:28 10:40 10:42 10:52 10:88\n33 0.002:5 0.0002:29 0.00025:32 10:43 10:53 10:89\n34 0.002:6 0.0002:30 0.00025:32 10:41 10:54 10:90\n35 0.002:7 0.0002:31 0.00025:33 0.00025:34 10:55 10:91\n36 0.002:8 0.25:29\n37 0.002:9 0.25:31 0.00025:36\n38 0.002:10 0.25:30\n39 0.002:11 0.25:31 0.00025:38\n40 0.002:12 0.25:33 0.0002:36\n41 0.002:13 0.25:35 0.0002:37 0.00025:40\n42 0.002:14 0.25:34 0.0002:38\n43 0.002:15 0.25:35 0.0002:39 0.00025:42\n44 0.002:16 0.125:32\n45 0.002:17 0.125:33 0.00025:44\n46 0.002:18 0.125:34 0.00025:44\n47 0.002:19 0.125:35 0.00025:45 0.00025:46\n48 0.002:20 2:56\n49 0.002:21 0.00025:48 2:57\n50 0.002:22 0.00025:48 2:58\n51 0.002:23 0.00025:49 0.00025:50 2:59\n52 0.002:24 0.0002:48 2:60\n53 0.002:25 0.0002:49 0.00025:52 2:61\n54 0.002:26 0.0002:50 0.00025:52 2:62\n55 0.002:27 0.0002:51 0.00025:53 0.00025:54 2:63\n56 0.004:28 10:64 10:66 10:72 10:92\n57 0.004:29 0.00025:56 10:67 10:73 10:93\n58 0.004:30 0.00025:56 10:65 10:74 10:94\n59 0.004:31 0.00025:57 0.00025:58 10:75 10:95\n60 0.004:32 0.0002:56 10:68 10:70 10:96\n61 0.004:33 0.0002:57 0.00025:60 10:71 10:97\n62 0.004:34 0.0002:58 0.00025:60 10:69 10:98\n63 0.004:35 0.0002:59 0.00025:61 0.00025:62 10:99\n64 0.004:36 0.25:57\n65 0.004:37 0.25:59 0.00025:64\n66 0.004:38 0.25:58\n67 0.004:39 0.25:59 0.00025:66\n68 0.004:40 0.25:61 0.0002:64\n69 0.004:41 0.25:63 0.0002:65 0.00025:68\n70 0.004:42 0.25:62 0.0002:66\n71 0.004:43 0.25:63 0.0002:67 0.00025:70\n72 0.004:44 0.125:60\n73 0.004:45 0.125:61 0.00025:72\n74 0.004:46 0.125:62 0.00025:72\n75 0.004:47 0.125:63 0.00025:73 0.00025:74\n76 2:100\n77 0.00025:76 2:101\n78 0.00025:76 2:102\n79 0.00025:77 0.00025:78 2:103\n80 0.0002:76 2:104\n81 0.0002:77 0.00025:80 2:105\n82 0.0002:78 0.00025:80 2:106\n83 0.0002:79 0.00025:81 0.00025:82 2:107\n84 0.002:76 2:128\n85 0.002:77 0.00025:84 2:129\n86 0.002:78 0.00025:84 2:130\n87 0.002:79 0.00025:85 0.00025:86 2:131\n88 0.002:80 0.0002:84 2:132\n89 0.002:81 0.0002:85 0.00025:88 2:133\n90 0.002:82 0.0002:86 0.00025:88 2:134\n91 0.002:83 0.0002:87 0.00025:89 0.00025:90 2:135\n92 0.004:84 2:156\n93 0.004:85 0.00025:92 2:157\n94 0.004:86 0.00025:92 2:158\n95 0.004:87 0.00025:93 0.00025:94 2:159\n96 0.004:88 0.0002:92 2:160\n97 0.004:89 0.0002:93 0.00025:96 2:161\n98 0.004:90 0.0002:94 0.00025:96 2:162\n99 0.004:91 0.0002:95 0.00025:97 0.00025:98 2:163\n100 0.002:0 10:108 10:110 10:116 10:120 10:176\n101 0.002:1 0.00025:100 10:111 10:117 10:121 10:177\n102 0.002:2 0.00025:100 10:109 10:118 10:122 10:178\n103 0.002:3 0.00025:101 0.00025:102 10:119 10:123 10:179\n104 0.002:4 0.0002:100 10:112 10:114 10:124 10:180\n105 0.002:5 0.0002:101 0.00025:104 10:115 10:125 10:181\n106 0.002:6 0.0002:102 0.00025:104 10:113 10:126 10:182\n107 0.002:7 0.0002:103 0.00025:105 0.00025:106 10:127 10:183\n108 0.002:8 0.25:101\n109 0.002:9 0.25:103 0.00025:108\n110 0.002:10 0.25:102\n111 0.002:11 0.25:103 0.00025:110\n112 0.002:12 0.25:105 0.0002:108\n113 0.002:13 0.25:107 0.0002:109 0.00025:112\n114 0.002:14 0.25:106 0.0002:110\n115 0.002:15 0.25:107 0.0002:111 0.00025:114\n116 0.002:16 0.125:104\n117 0.002:17 0.125:105 0.00025:116\n118 0.002:18 0.125:106 0.00025:116\n119 0.002:19 0.125:107 0.00025:117 0.00025:118\n120 0.002:20 2:128\n121 0.002:21 0.00025:120 2:129\n122 0.002:22 0.00025:120 2:130\n123 0.002:23 0.00025:121 0.00025:122 2:131\n124 0.002:24 0.0002:120 2:132\n125 0.002:25 0.0002:121 0.00025:124 2:133\n126 0.002:26 0.0002:122 0.00025:124 2:134\n127 0.002:27 0.0002:123 0.00025:125 0.00025:126 2:135\n128 0.002:28 0.002:100 10:136 10:138 10:144 10:148 10:184\n129 0.002:29 0.002:101 0.00025:128 10:139 10:145 10:149 10:185\n130 0.002:30 0.002:102 0.00025:128 10:137 10:146 10:150 10:186\n131 0.002:31 0.002:103 0.00025:129 0.00025:130 10:147 10:151 10:187\n132 0.002:32 0.002:104 0.0002:128 10:140 10:142 10:152 10:188\n133 0.002:33 0.002:105 0.0002:129 0.00025:132 10:143 10:153 10:189\n134 0.002:34 0.002:106 0.0002:130 0.00025:132 10:141 10:154 10:190\n135 0.002:35 0.002:107 0.0002:131 0.00025:133 0.00025:134 10:155 10:191\n136 0.002:36 0.002:108 0.25:129\n137 0.002:37 0.002:109 0.25:131 0.00025:136\n138 0.002:38 0.002:110 0.25:130\n139 0.002:39 0.002:111 0.25:131 0.00025:138\n140 0.002:40 0.002:112 0.25:133 0.0002:136\n141 0.002:41 0.002:113 0.25:135 0.0002:137 0.00025:140\n142 0.002:42 0.002:114 0.25:134 0.0002:138\n143 0.002:43 0.002:115 0.25:135 0.0002:139 0.00025:142\n144 0.002:44 0.002:116 0.125:132\n145 0.002:45 0.002:117 0.125:133 0.00025:144\n146 0.002:46 0.002:118 0.125:134 0.00025:144\n147 0.002:47 0.002:119 0.125:135 0.00025:145 0.00025:146\n148 0.002:48 0.002:120 2:156\n149 0.002:49 0.002:121 0.00025:148 2:157\n150 0.002:50 0.002:122 0.00025:148 2:158\n151 0.002:51 0.002:123 0.00025:149 0.00025:150 2:159\n152 0.002:52 0.002:124 0.0002:148 2:160\n153 0.002:53 0.002:125 0.0002:149 0.00025:152 2:161\n154 0.002:54 0.002:126 0.0002:150 0.00025:152 2:162\n155 0.002:55 0.002:127 0.0002:151 0.00025:153 0.00025:154 2:163\n156 0.002:56 0.004:128 10:164 10:166 10:172 10:192\n157 0.002:57 0.004:129 0.00025:156 10:167 10:173 10:193\n158 0.002:58 0.004:130 0.00025:156 10:165 10:174 10:194\n159 0.002:59 0.004:131 0.00025:157 0.00025:158 10:175 10:195\n160 0.002:60 0.004:132 0.0002:156 10:168 10:170 10:196\n161 0.002:61 0.004:133 0.0002:157 0.00025:160 10:171 10:197\n162 0.002:62 0.004:134 0.0002:158 0.00025:160 10:169 10:198\n163 0.002:63 0.004:135 0.0002:159 0.00025:161 0.00025:162 10:199\n164 0.002:64 0.004:136 0.25:157\n165 0.002:65 0.004:137 0.25:159 0.00025:164\n166 0.002:66 0.004:138 0.25:158\n167 0.002:67 0.004:139 0.25:159 0.00025:166\n168 0.002:68 0.004:140 0.25:161 0.0002:164\n169 0.002:69 0.004:141 0.25:163 0.0002:165 0.00025:168\n170 0.002:70 0.004:142 0.25:162 0.0002:166\n171 0.002:71 0.004:143 0.25:163 0.0002:167 0.00025:170\n172 0.002:72 0.004:144 0.125:160\n173 0.002:73 0.004:145 0.125:161 0.00025:172\n174 0.002:74 0.004:146 0.125:162 0.00025:172\n175 0.002:75 0.004:147 0.125:163 0.00025:173 0.00025:174\n176 0.002:76 2:200\n177 0.002:77 0.00025:176 2:201\n178 0.002:78 0.00025:176 2:202\n179 0.002:79 0.00025:177 0.00025:178 2:203\n180 0.002:80 0.0002:176 2:204\n181 0.002:81 0.0002:177 0.00025:180 2:205\n182 0.002:82 0.0002:178 0.00025:180 2:206\n183 0.002:83 0.0002:179 0.00025:181 0.00025:182 2:207\n184 0.002:84 0.002:176 2:228\n185 0.002:85 0.002:177 0.00025:184 2:229\n186 0.002:86 0.002:178 0.00025:184 2:230\n187 0.002:87 0.002:179 0.00025:185 0.00025:186 2:231\n188 0.002:88 0.002:180 0.0002:184 2:232\n189 0.002:89 0.002:181 0.0002:185 0.00025:188 2:233\n190 0.002:90 0.002:182 0.0002:186 0.00025:188 2:234\n191 0.002:91 0.002:183 0.0002:187 0.00025:189 0.00025:190 2:235\n192 0.002:92 0.004:184 2:256\n193 0.002:93 0.004:185 0.00025:192 2:257\n194 0.002:94 0.004:186 0.00025:192 2:258\n195 0.002:95 0.004:187 0.00025:193 0.00025:194 2:259\n196 0.002:96 0.004:188 0.0002:192 2:260\n197 0.002:97 0.004:189 0.0002:193 0.00025:196 2:261\n198 0.002:98 0.004:190 0.0002:194 0.00025:196 2:262\n199 0.002:99 0.004:191 0.0002:195 0.00025:197 0.00025:198 2:263\n200 0.004:100 10:208 10:210 10:216 10:220\n201 0.004:101 0.00025:200 10:211 10:217 10:221\n202 0.004:102 0.00025:200 10:209 10:218 10:222\n203 0.004:103 0.00025:201 0.00025:202 10:219 10:223\n204 0.004:104 0.0002:200 10:212 10:214 10:224\n205 0.004:105 0.0002:201 0.00025:204 10:215 10:225\n206 0.004:106 0.0002:202 0.00025:204 10:213 10:226\n207 0.004:107 0.0002:203 0.00025:205 0.00025:206 10:227\n208 0.004:108 0.25:201\n209 0.004:109 0.25:203 0.00025:208\n210 0.004:110 0.25:202\n211 0.004:111 0.25:203 0.00025:210\n212 0.004:112 0.25:205 0.0002:208\n213 0.004:113 0.25:207 0.0002:209 0.00025:212\n214 0.004:114 0.25:206 0.0002:210\n215 0.004:115 0.25:207 0.0002:211 0.00025:214\n216 0.004:116 0.125:204\n217 0.004:117 0.125:205 0.00025:216\n218 0.004:118 0.125:206 0.00025:216\n219 0.004:119 0.125:207 0.00025:217 0.00025:218\n220 0.004:120 2:228\n221 0.004:121 0.00025:220 2:229\n222 0.004:122 0.00025:220 2:230\n223 0.004:123 0.00025:221 0.00025:222 2:231\n224 0.004:124 0.0002:220 2:232\n225 0.004:125 0.0002:221 0.00025:224 2:233\n226 0.004:126 0.0002:222 0.00025:224 2:234\n227 0.004:127 0.0002:223 0.00025:225 0.00025:226 2:235\n228 0.004:128 0.002:200 10:236 10:238 10:244 10:248\n229 0.004:129 0.002:201 0.00025:228 10:239 10:245 10:249\n230 0.004:130 0.002:202 0.00025:228 10:237 10:246 10:250\n231 0.004:131 0.002:203 0.00025:229 0.00025:230 10:247 10:251\n232 0.004:132 0.002:204 0.0002:228 10:240 10:242 10:252\n233 0.004:133 0.002:205 0.0002:229 0.00025:232 10:243 10:253\n234 0.004:134 0.002:206 0.0002:230 0.00025:232 10:241 10:254\n235 0.004:135 0.002:207 0.0002:231 0.00025:233 0.00025:234 10:255\n236 0.004:136 0.002:208 0.25:229\n237 0.004:137 0.002:209 0.25:231 0.00025:236\n238 0.004:138 0.002:210 0.25:230\n239 0.004:139 0.002:211 0.25:231 0.00025:238\n240 0.004:140 0.002:212 0.25:233 0.0002:236\n241 0.004:141 0.002:213 0.25:235 0.0002:237 0.00025:240\n242 0.004:142 0.002:214 0.25:234 0.0002:238\n243 0.004:143 0.002:215 0.25:235 0.0002:239 0.00025:242\n244 0.004:144 0.002:216 0.125:232\n245 0.004:145 0.002:217 0.125:233 0.00025:244\n246 0.004:146 0.002:218 0.125:234 0.00025:244\n247 0.004:147 0.002:219 0.125:235 0.00025:245 0.00025:246\n248 0.004:148 0.002:220 2:256\n249 0.004:149 0.002:221 0.00025:248 2:257\n250 0.004:150 0.002:222 0.00025:248 2:258\n251 0.004:151 0.002:223 0.00025:249 0.00025:250 2:259\n252 0.004:152 0.002:224 0.0002:248 2:260\n253 0.004:153 0.002:225 0.0002:249 0.00025:252 2:261\n254 0.004:154 0.002:226 0.0002:250 0.00025:252 2:262\n255 0.004:155 0.002:227 0.0002:251 0.00025:253 0.00025:254 2:263\n256 0.004:156 0.004:228 10:264 10:266 10:272\n257 0.004:157 0.004:229 0.00025:256 10:267 10:273\n258 0.004:158 0.004:230 0.00025:256 10:265 10:274\n259 0.004:159 0.004:231 0.00025:257 0.00025:258 10:275\n260 0.004:160 0.004:232 0.0002:256 10:268 10:270\n261 0.004:161 0.004:233 0.0002:257 0.00025:260 10:271\n262 0.004:162 0.004:234 0.0002:258 0.00025:260 10:269\n263 0.004:163 0.004:235 0.0002:259 0.00025:261 0.00025:262\n264 0.004:164 0.004:236 0.25:257\n265 0.004:165 0.004:237 0.25:259 0.00025:264\n266 0.004:166 0.004:238 0.25:258\n267 0.004:167 0.004:239 0.25:259 0.00025:266\n268 0.004:168 0.004:240 0.25:261 0.0002:264\n269 0.004:169 0.004:241 0.25:263 0.0002:265 0.00025:268\n270 0.004:170 0.004:242 0.25:262 0.0002:266\n271 0.004:171 0.004:243 0.25:263 0.0002:267 0.00025:270\n272 0.004:172 0.004:244 0.125:260\n273 0.004:173 0.004:245 0.125:261 0.00025:272\n274 0.004:174 0.004:246 0.125:262 0.00025:272\n275 0.004:175 0.004:247 0.125:263 0.00025:273 0.00025:274\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows1.srew",
    "content": "# Reward structure \"percent_op\"\n# State rewards\n276 240\n28 25\n29 25\n30 25\n31 25\n32 25\n33 25\n34 25\n35 25\n36 25\n37 25\n38 25\n39 25\n40 25\n41 25\n42 25\n43 25\n44 25\n45 25\n46 25\n47 25\n48 25\n49 25\n50 25\n51 25\n52 25\n53 25\n54 25\n55 25\n56 50\n57 50\n58 50\n59 50\n60 50\n61 50\n62 50\n63 50\n64 50\n65 50\n66 50\n67 50\n68 50\n69 50\n70 50\n71 50\n72 50\n73 50\n74 50\n75 50\n84 25\n85 25\n86 25\n87 25\n88 25\n89 25\n90 25\n91 25\n92 50\n93 50\n94 50\n95 50\n96 50\n97 50\n98 50\n99 50\n100 25\n101 25\n102 25\n103 25\n104 25\n105 25\n106 25\n107 25\n108 25\n109 25\n110 25\n111 25\n112 25\n113 25\n114 25\n115 25\n116 25\n117 25\n118 25\n119 25\n120 25\n121 25\n122 25\n123 25\n124 25\n125 25\n126 25\n127 25\n128 50\n129 50\n130 50\n131 50\n132 50\n133 50\n134 50\n135 50\n136 50\n137 50\n138 50\n139 50\n140 50\n141 50\n142 50\n143 50\n144 50\n145 50\n146 50\n147 50\n148 50\n149 50\n150 50\n151 50\n152 50\n153 50\n154 50\n155 50\n156 75\n157 75\n158 75\n159 75\n160 75\n161 75\n162 75\n163 75\n164 75\n165 75\n166 75\n167 75\n168 75\n169 75\n170 75\n171 75\n172 75\n173 75\n174 75\n175 75\n176 25\n177 25\n178 25\n179 25\n180 25\n181 25\n182 25\n183 25\n184 50\n185 50\n186 50\n187 50\n188 50\n189 50\n190 50\n191 50\n192 75\n193 75\n194 75\n195 75\n196 75\n197 75\n198 75\n199 75\n200 50\n201 50\n202 50\n203 50\n204 50\n205 50\n206 50\n207 50\n208 50\n209 50\n210 50\n211 50\n212 50\n213 50\n214 50\n215 50\n216 50\n217 50\n218 50\n219 50\n220 50\n221 50\n222 50\n223 50\n224 50\n225 50\n226 50\n227 50\n228 75\n229 75\n230 75\n231 75\n232 75\n233 75\n234 75\n235 75\n236 75\n237 75\n238 75\n239 75\n240 75\n241 75\n242 75\n243 75\n244 75\n245 75\n246 75\n247 75\n248 75\n249 75\n250 75\n251 75\n252 75\n253 75\n254 75\n255 75\n256 100\n257 100\n258 100\n259 100\n260 100\n261 100\n262 100\n263 100\n264 100\n265 100\n266 100\n267 100\n268 100\n269 100\n270 100\n271 100\n272 100\n273 100\n274 100\n275 100\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows1.trew",
    "content": "276 0\n0\n1\n2\n3\n4\n5\n6\n7\n8\n9\n10\n11\n12\n13\n14\n15\n16\n17\n18\n19\n20\n21\n22\n23\n24\n25\n26\n27\n28\n29\n30\n31\n32\n33\n34\n35\n36\n37\n38\n39\n40\n41\n42\n43\n44\n45\n46\n47\n48\n49\n50\n51\n52\n53\n54\n55\n56\n57\n58\n59\n60\n61\n62\n63\n64\n65\n66\n67\n68\n69\n70\n71\n72\n73\n74\n75\n76\n77\n78\n79\n80\n81\n82\n83\n84\n85\n86\n87\n88\n89\n90\n91\n92\n93\n94\n95\n96\n97\n98\n99\n100\n101\n102\n103\n104\n105\n106\n107\n108\n109\n110\n111\n112\n113\n114\n115\n116\n117\n118\n119\n120\n121\n122\n123\n124\n125\n126\n127\n128\n129\n130\n131\n132\n133\n134\n135\n136\n137\n138\n139\n140\n141\n142\n143\n144\n145\n146\n147\n148\n149\n150\n151\n152\n153\n154\n155\n156\n157\n158\n159\n160\n161\n162\n163\n164\n165\n166\n167\n168\n169\n170\n171\n172\n173\n174\n175\n176\n177\n178\n179\n180\n181\n182\n183\n184\n185\n186\n187\n188\n189\n190\n191\n192\n193\n194\n195\n196\n197\n198\n199\n200\n201\n202\n203\n204\n205\n206\n207\n208\n209\n210\n211\n212\n213\n214\n215\n216\n217\n218\n219\n220\n221\n222\n223\n224\n225\n226\n227\n228\n229\n230\n231\n232\n233\n234\n235\n236\n237\n238\n239\n240\n241\n242\n243\n244\n245\n246\n247\n248\n249\n250\n251\n252\n253\n254\n255\n256\n257\n258\n259\n260\n261\n262\n263\n264\n265\n266\n267\n268\n269\n270\n271\n272\n273\n274\n275\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows2.srew",
    "content": "# Reward structure \"time_not_min\"\n# State rewards\n276 144\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n6 1\n7 1\n8 1\n9 1\n10 1\n11 1\n12 1\n13 1\n14 1\n15 1\n16 1\n17 1\n18 1\n19 1\n20 1\n21 1\n22 1\n23 1\n24 1\n25 1\n26 1\n27 1\n28 1\n30 1\n32 1\n34 1\n36 1\n37 1\n38 1\n40 1\n41 1\n42 1\n44 1\n46 1\n48 1\n50 1\n52 1\n54 1\n56 1\n58 1\n60 1\n62 1\n64 1\n65 1\n66 1\n68 1\n69 1\n70 1\n72 1\n74 1\n76 1\n77 1\n78 1\n79 1\n80 1\n81 1\n82 1\n83 1\n84 1\n86 1\n88 1\n90 1\n92 1\n94 1\n96 1\n98 1\n100 1\n101 1\n104 1\n105 1\n108 1\n110 1\n111 1\n112 1\n114 1\n115 1\n116 1\n117 1\n120 1\n121 1\n124 1\n125 1\n128 1\n132 1\n136 1\n138 1\n140 1\n142 1\n144 1\n148 1\n152 1\n156 1\n160 1\n164 1\n166 1\n168 1\n170 1\n172 1\n176 1\n177 1\n180 1\n181 1\n184 1\n188 1\n192 1\n196 1\n200 1\n201 1\n204 1\n205 1\n208 1\n210 1\n211 1\n212 1\n214 1\n215 1\n216 1\n217 1\n220 1\n221 1\n224 1\n225 1\n228 1\n232 1\n236 1\n238 1\n240 1\n242 1\n244 1\n248 1\n252 1\n256 1\n260 1\n264 1\n266 1\n268 1\n270 1\n272 1\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows2.trew",
    "content": "276 0\n0\n1\n2\n3\n4\n5\n6\n7\n8\n9\n10\n11\n12\n13\n14\n15\n16\n17\n18\n19\n20\n21\n22\n23\n24\n25\n26\n27\n28\n29\n30\n31\n32\n33\n34\n35\n36\n37\n38\n39\n40\n41\n42\n43\n44\n45\n46\n47\n48\n49\n50\n51\n52\n53\n54\n55\n56\n57\n58\n59\n60\n61\n62\n63\n64\n65\n66\n67\n68\n69\n70\n71\n72\n73\n74\n75\n76\n77\n78\n79\n80\n81\n82\n83\n84\n85\n86\n87\n88\n89\n90\n91\n92\n93\n94\n95\n96\n97\n98\n99\n100\n101\n102\n103\n104\n105\n106\n107\n108\n109\n110\n111\n112\n113\n114\n115\n116\n117\n118\n119\n120\n121\n122\n123\n124\n125\n126\n127\n128\n129\n130\n131\n132\n133\n134\n135\n136\n137\n138\n139\n140\n141\n142\n143\n144\n145\n146\n147\n148\n149\n150\n151\n152\n153\n154\n155\n156\n157\n158\n159\n160\n161\n162\n163\n164\n165\n166\n167\n168\n169\n170\n171\n172\n173\n174\n175\n176\n177\n178\n179\n180\n181\n182\n183\n184\n185\n186\n187\n188\n189\n190\n191\n192\n193\n194\n195\n196\n197\n198\n199\n200\n201\n202\n203\n204\n205\n206\n207\n208\n209\n210\n211\n212\n213\n214\n215\n216\n217\n218\n219\n220\n221\n222\n223\n224\n225\n226\n227\n228\n229\n230\n231\n232\n233\n234\n235\n236\n237\n238\n239\n240\n241\n242\n243\n244\n245\n246\n247\n248\n249\n250\n251\n252\n253\n254\n255\n256\n257\n258\n259\n260\n261\n262\n263\n264\n265\n266\n267\n268\n269\n270\n271\n272\n273\n274\n275\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows3.srew",
    "content": "# Reward structure \"num_repairs\"\n# State rewards\n276 0\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.rows3.trew",
    "content": "276 204\n0\n1\n2\n3\n4\n5\n6\n7\n8 1:1\n9 1:3\n10 1:2\n11 1:3\n12 1:5\n13 1:7\n14 1:6\n15 1:7\n16 1:4\n17 1:5\n18 1:6\n19 1:7\n20 1:28\n21 1:29\n22 1:30\n23 1:31\n24 1:32\n25 1:33\n26 1:34\n27 1:35\n28\n29\n30\n31\n32\n33\n34\n35\n36 1:29\n37 1:31\n38 1:30\n39 1:31\n40 1:33\n41 1:35\n42 1:34\n43 1:35\n44 1:32\n45 1:33\n46 1:34\n47 1:35\n48 1:56\n49 1:57\n50 1:58\n51 1:59\n52 1:60\n53 1:61\n54 1:62\n55 1:63\n56\n57\n58\n59\n60\n61\n62\n63\n64 1:57\n65 1:59\n66 1:58\n67 1:59\n68 1:61\n69 1:63\n70 1:62\n71 1:63\n72 1:60\n73 1:61\n74 1:62\n75 1:63\n76 1:100\n77 1:101\n78 1:102\n79 1:103\n80 1:104\n81 1:105\n82 1:106\n83 1:107\n84 1:128\n85 1:129\n86 1:130\n87 1:131\n88 1:132\n89 1:133\n90 1:134\n91 1:135\n92 1:156\n93 1:157\n94 1:158\n95 1:159\n96 1:160\n97 1:161\n98 1:162\n99 1:163\n100\n101\n102\n103\n104\n105\n106\n107\n108 1:101\n109 1:103\n110 1:102\n111 1:103\n112 1:105\n113 1:107\n114 1:106\n115 1:107\n116 1:104\n117 1:105\n118 1:106\n119 1:107\n120 1:128\n121 1:129\n122 1:130\n123 1:131\n124 1:132\n125 1:133\n126 1:134\n127 1:135\n128\n129\n130\n131\n132\n133\n134\n135\n136 1:129\n137 1:131\n138 1:130\n139 1:131\n140 1:133\n141 1:135\n142 1:134\n143 1:135\n144 1:132\n145 1:133\n146 1:134\n147 1:135\n148 1:156\n149 1:157\n150 1:158\n151 1:159\n152 1:160\n153 1:161\n154 1:162\n155 1:163\n156\n157\n158\n159\n160\n161\n162\n163\n164 1:157\n165 1:159\n166 1:158\n167 1:159\n168 1:161\n169 1:163\n170 1:162\n171 1:163\n172 1:160\n173 1:161\n174 1:162\n175 1:163\n176 1:200\n177 1:201\n178 1:202\n179 1:203\n180 1:204\n181 1:205\n182 1:206\n183 1:207\n184 1:228\n185 1:229\n186 1:230\n187 1:231\n188 1:232\n189 1:233\n190 1:234\n191 1:235\n192 1:256\n193 1:257\n194 1:258\n195 1:259\n196 1:260\n197 1:261\n198 1:262\n199 1:263\n200\n201\n202\n203\n204\n205\n206\n207\n208 1:201\n209 1:203\n210 1:202\n211 1:203\n212 1:205\n213 1:207\n214 1:206\n215 1:207\n216 1:204\n217 1:205\n218 1:206\n219 1:207\n220 1:228\n221 1:229\n222 1:230\n223 1:231\n224 1:232\n225 1:233\n226 1:234\n227 1:235\n228\n229\n230\n231\n232\n233\n234\n235\n236 1:229\n237 1:231\n238 1:230\n239 1:231\n240 1:233\n241 1:235\n242 1:234\n243 1:235\n244 1:232\n245 1:233\n246 1:234\n247 1:235\n248 1:256\n249 1:257\n250 1:258\n251 1:259\n252 1:260\n253 1:261\n254 1:262\n255 1:263\n256\n257\n258\n259\n260\n261\n262\n263\n264 1:257\n265 1:259\n266 1:258\n267 1:259\n268 1:261\n269 1:263\n270 1:262\n271 1:263\n272 1:260\n273 1:261\n274 1:262\n275 1:263\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.sta",
    "content": "(left_n,left,right_n,right,r,line,line_n,toleft,toleft_n,toright,toright_n)\n0:(0,false,0,false,false,false,false,false,false,false,false)\n1:(0,false,0,false,false,false,false,false,false,false,true)\n2:(0,false,0,false,false,false,false,false,true,false,false)\n3:(0,false,0,false,false,false,false,false,true,false,true)\n4:(0,false,0,false,false,false,true,false,false,false,false)\n5:(0,false,0,false,false,false,true,false,false,false,true)\n6:(0,false,0,false,false,false,true,false,true,false,false)\n7:(0,false,0,false,false,false,true,false,true,false,true)\n8:(0,false,0,false,true,false,false,false,false,true,false)\n9:(0,false,0,false,true,false,false,false,true,true,false)\n10:(0,false,0,false,true,false,false,true,false,false,false)\n11:(0,false,0,false,true,false,false,true,false,false,true)\n12:(0,false,0,false,true,false,true,false,false,true,false)\n13:(0,false,0,false,true,false,true,false,true,true,false)\n14:(0,false,0,false,true,false,true,true,false,false,false)\n15:(0,false,0,false,true,false,true,true,false,false,true)\n16:(0,false,0,false,true,true,false,false,false,false,false)\n17:(0,false,0,false,true,true,false,false,false,false,true)\n18:(0,false,0,false,true,true,false,false,true,false,false)\n19:(0,false,0,false,true,true,false,false,true,false,true)\n20:(0,false,0,true,true,false,false,false,false,false,false)\n21:(0,false,0,true,true,false,false,false,false,false,true)\n22:(0,false,0,true,true,false,false,false,true,false,false)\n23:(0,false,0,true,true,false,false,false,true,false,true)\n24:(0,false,0,true,true,false,true,false,false,false,false)\n25:(0,false,0,true,true,false,true,false,false,false,true)\n26:(0,false,0,true,true,false,true,false,true,false,false)\n27:(0,false,0,true,true,false,true,false,true,false,true)\n28:(0,false,1,false,false,false,false,false,false,false,false)\n29:(0,false,1,false,false,false,false,false,false,false,true)\n30:(0,false,1,false,false,false,false,false,true,false,false)\n31:(0,false,1,false,false,false,false,false,true,false,true)\n32:(0,false,1,false,false,false,true,false,false,false,false)\n33:(0,false,1,false,false,false,true,false,false,false,true)\n34:(0,false,1,false,false,false,true,false,true,false,false)\n35:(0,false,1,false,false,false,true,false,true,false,true)\n36:(0,false,1,false,true,false,false,false,false,true,false)\n37:(0,false,1,false,true,false,false,false,true,true,false)\n38:(0,false,1,false,true,false,false,true,false,false,false)\n39:(0,false,1,false,true,false,false,true,false,false,true)\n40:(0,false,1,false,true,false,true,false,false,true,false)\n41:(0,false,1,false,true,false,true,false,true,true,false)\n42:(0,false,1,false,true,false,true,true,false,false,false)\n43:(0,false,1,false,true,false,true,true,false,false,true)\n44:(0,false,1,false,true,true,false,false,false,false,false)\n45:(0,false,1,false,true,true,false,false,false,false,true)\n46:(0,false,1,false,true,true,false,false,true,false,false)\n47:(0,false,1,false,true,true,false,false,true,false,true)\n48:(0,false,1,true,true,false,false,false,false,false,false)\n49:(0,false,1,true,true,false,false,false,false,false,true)\n50:(0,false,1,true,true,false,false,false,true,false,false)\n51:(0,false,1,true,true,false,false,false,true,false,true)\n52:(0,false,1,true,true,false,true,false,false,false,false)\n53:(0,false,1,true,true,false,true,false,false,false,true)\n54:(0,false,1,true,true,false,true,false,true,false,false)\n55:(0,false,1,true,true,false,true,false,true,false,true)\n56:(0,false,2,false,false,false,false,false,false,false,false)\n57:(0,false,2,false,false,false,false,false,false,false,true)\n58:(0,false,2,false,false,false,false,false,true,false,false)\n59:(0,false,2,false,false,false,false,false,true,false,true)\n60:(0,false,2,false,false,false,true,false,false,false,false)\n61:(0,false,2,false,false,false,true,false,false,false,true)\n62:(0,false,2,false,false,false,true,false,true,false,false)\n63:(0,false,2,false,false,false,true,false,true,false,true)\n64:(0,false,2,false,true,false,false,false,false,true,false)\n65:(0,false,2,false,true,false,false,false,true,true,false)\n66:(0,false,2,false,true,false,false,true,false,false,false)\n67:(0,false,2,false,true,false,false,true,false,false,true)\n68:(0,false,2,false,true,false,true,false,false,true,false)\n69:(0,false,2,false,true,false,true,false,true,true,false)\n70:(0,false,2,false,true,false,true,true,false,false,false)\n71:(0,false,2,false,true,false,true,true,false,false,true)\n72:(0,false,2,false,true,true,false,false,false,false,false)\n73:(0,false,2,false,true,true,false,false,false,false,true)\n74:(0,false,2,false,true,true,false,false,true,false,false)\n75:(0,false,2,false,true,true,false,false,true,false,true)\n76:(0,true,0,false,true,false,false,false,false,false,false)\n77:(0,true,0,false,true,false,false,false,false,false,true)\n78:(0,true,0,false,true,false,false,false,true,false,false)\n79:(0,true,0,false,true,false,false,false,true,false,true)\n80:(0,true,0,false,true,false,true,false,false,false,false)\n81:(0,true,0,false,true,false,true,false,false,false,true)\n82:(0,true,0,false,true,false,true,false,true,false,false)\n83:(0,true,0,false,true,false,true,false,true,false,true)\n84:(0,true,1,false,true,false,false,false,false,false,false)\n85:(0,true,1,false,true,false,false,false,false,false,true)\n86:(0,true,1,false,true,false,false,false,true,false,false)\n87:(0,true,1,false,true,false,false,false,true,false,true)\n88:(0,true,1,false,true,false,true,false,false,false,false)\n89:(0,true,1,false,true,false,true,false,false,false,true)\n90:(0,true,1,false,true,false,true,false,true,false,false)\n91:(0,true,1,false,true,false,true,false,true,false,true)\n92:(0,true,2,false,true,false,false,false,false,false,false)\n93:(0,true,2,false,true,false,false,false,false,false,true)\n94:(0,true,2,false,true,false,false,false,true,false,false)\n95:(0,true,2,false,true,false,false,false,true,false,true)\n96:(0,true,2,false,true,false,true,false,false,false,false)\n97:(0,true,2,false,true,false,true,false,false,false,true)\n98:(0,true,2,false,true,false,true,false,true,false,false)\n99:(0,true,2,false,true,false,true,false,true,false,true)\n100:(1,false,0,false,false,false,false,false,false,false,false)\n101:(1,false,0,false,false,false,false,false,false,false,true)\n102:(1,false,0,false,false,false,false,false,true,false,false)\n103:(1,false,0,false,false,false,false,false,true,false,true)\n104:(1,false,0,false,false,false,true,false,false,false,false)\n105:(1,false,0,false,false,false,true,false,false,false,true)\n106:(1,false,0,false,false,false,true,false,true,false,false)\n107:(1,false,0,false,false,false,true,false,true,false,true)\n108:(1,false,0,false,true,false,false,false,false,true,false)\n109:(1,false,0,false,true,false,false,false,true,true,false)\n110:(1,false,0,false,true,false,false,true,false,false,false)\n111:(1,false,0,false,true,false,false,true,false,false,true)\n112:(1,false,0,false,true,false,true,false,false,true,false)\n113:(1,false,0,false,true,false,true,false,true,true,false)\n114:(1,false,0,false,true,false,true,true,false,false,false)\n115:(1,false,0,false,true,false,true,true,false,false,true)\n116:(1,false,0,false,true,true,false,false,false,false,false)\n117:(1,false,0,false,true,true,false,false,false,false,true)\n118:(1,false,0,false,true,true,false,false,true,false,false)\n119:(1,false,0,false,true,true,false,false,true,false,true)\n120:(1,false,0,true,true,false,false,false,false,false,false)\n121:(1,false,0,true,true,false,false,false,false,false,true)\n122:(1,false,0,true,true,false,false,false,true,false,false)\n123:(1,false,0,true,true,false,false,false,true,false,true)\n124:(1,false,0,true,true,false,true,false,false,false,false)\n125:(1,false,0,true,true,false,true,false,false,false,true)\n126:(1,false,0,true,true,false,true,false,true,false,false)\n127:(1,false,0,true,true,false,true,false,true,false,true)\n128:(1,false,1,false,false,false,false,false,false,false,false)\n129:(1,false,1,false,false,false,false,false,false,false,true)\n130:(1,false,1,false,false,false,false,false,true,false,false)\n131:(1,false,1,false,false,false,false,false,true,false,true)\n132:(1,false,1,false,false,false,true,false,false,false,false)\n133:(1,false,1,false,false,false,true,false,false,false,true)\n134:(1,false,1,false,false,false,true,false,true,false,false)\n135:(1,false,1,false,false,false,true,false,true,false,true)\n136:(1,false,1,false,true,false,false,false,false,true,false)\n137:(1,false,1,false,true,false,false,false,true,true,false)\n138:(1,false,1,false,true,false,false,true,false,false,false)\n139:(1,false,1,false,true,false,false,true,false,false,true)\n140:(1,false,1,false,true,false,true,false,false,true,false)\n141:(1,false,1,false,true,false,true,false,true,true,false)\n142:(1,false,1,false,true,false,true,true,false,false,false)\n143:(1,false,1,false,true,false,true,true,false,false,true)\n144:(1,false,1,false,true,true,false,false,false,false,false)\n145:(1,false,1,false,true,true,false,false,false,false,true)\n146:(1,false,1,false,true,true,false,false,true,false,false)\n147:(1,false,1,false,true,true,false,false,true,false,true)\n148:(1,false,1,true,true,false,false,false,false,false,false)\n149:(1,false,1,true,true,false,false,false,false,false,true)\n150:(1,false,1,true,true,false,false,false,true,false,false)\n151:(1,false,1,true,true,false,false,false,true,false,true)\n152:(1,false,1,true,true,false,true,false,false,false,false)\n153:(1,false,1,true,true,false,true,false,false,false,true)\n154:(1,false,1,true,true,false,true,false,true,false,false)\n155:(1,false,1,true,true,false,true,false,true,false,true)\n156:(1,false,2,false,false,false,false,false,false,false,false)\n157:(1,false,2,false,false,false,false,false,false,false,true)\n158:(1,false,2,false,false,false,false,false,true,false,false)\n159:(1,false,2,false,false,false,false,false,true,false,true)\n160:(1,false,2,false,false,false,true,false,false,false,false)\n161:(1,false,2,false,false,false,true,false,false,false,true)\n162:(1,false,2,false,false,false,true,false,true,false,false)\n163:(1,false,2,false,false,false,true,false,true,false,true)\n164:(1,false,2,false,true,false,false,false,false,true,false)\n165:(1,false,2,false,true,false,false,false,true,true,false)\n166:(1,false,2,false,true,false,false,true,false,false,false)\n167:(1,false,2,false,true,false,false,true,false,false,true)\n168:(1,false,2,false,true,false,true,false,false,true,false)\n169:(1,false,2,false,true,false,true,false,true,true,false)\n170:(1,false,2,false,true,false,true,true,false,false,false)\n171:(1,false,2,false,true,false,true,true,false,false,true)\n172:(1,false,2,false,true,true,false,false,false,false,false)\n173:(1,false,2,false,true,true,false,false,false,false,true)\n174:(1,false,2,false,true,true,false,false,true,false,false)\n175:(1,false,2,false,true,true,false,false,true,false,true)\n176:(1,true,0,false,true,false,false,false,false,false,false)\n177:(1,true,0,false,true,false,false,false,false,false,true)\n178:(1,true,0,false,true,false,false,false,true,false,false)\n179:(1,true,0,false,true,false,false,false,true,false,true)\n180:(1,true,0,false,true,false,true,false,false,false,false)\n181:(1,true,0,false,true,false,true,false,false,false,true)\n182:(1,true,0,false,true,false,true,false,true,false,false)\n183:(1,true,0,false,true,false,true,false,true,false,true)\n184:(1,true,1,false,true,false,false,false,false,false,false)\n185:(1,true,1,false,true,false,false,false,false,false,true)\n186:(1,true,1,false,true,false,false,false,true,false,false)\n187:(1,true,1,false,true,false,false,false,true,false,true)\n188:(1,true,1,false,true,false,true,false,false,false,false)\n189:(1,true,1,false,true,false,true,false,false,false,true)\n190:(1,true,1,false,true,false,true,false,true,false,false)\n191:(1,true,1,false,true,false,true,false,true,false,true)\n192:(1,true,2,false,true,false,false,false,false,false,false)\n193:(1,true,2,false,true,false,false,false,false,false,true)\n194:(1,true,2,false,true,false,false,false,true,false,false)\n195:(1,true,2,false,true,false,false,false,true,false,true)\n196:(1,true,2,false,true,false,true,false,false,false,false)\n197:(1,true,2,false,true,false,true,false,false,false,true)\n198:(1,true,2,false,true,false,true,false,true,false,false)\n199:(1,true,2,false,true,false,true,false,true,false,true)\n200:(2,false,0,false,false,false,false,false,false,false,false)\n201:(2,false,0,false,false,false,false,false,false,false,true)\n202:(2,false,0,false,false,false,false,false,true,false,false)\n203:(2,false,0,false,false,false,false,false,true,false,true)\n204:(2,false,0,false,false,false,true,false,false,false,false)\n205:(2,false,0,false,false,false,true,false,false,false,true)\n206:(2,false,0,false,false,false,true,false,true,false,false)\n207:(2,false,0,false,false,false,true,false,true,false,true)\n208:(2,false,0,false,true,false,false,false,false,true,false)\n209:(2,false,0,false,true,false,false,false,true,true,false)\n210:(2,false,0,false,true,false,false,true,false,false,false)\n211:(2,false,0,false,true,false,false,true,false,false,true)\n212:(2,false,0,false,true,false,true,false,false,true,false)\n213:(2,false,0,false,true,false,true,false,true,true,false)\n214:(2,false,0,false,true,false,true,true,false,false,false)\n215:(2,false,0,false,true,false,true,true,false,false,true)\n216:(2,false,0,false,true,true,false,false,false,false,false)\n217:(2,false,0,false,true,true,false,false,false,false,true)\n218:(2,false,0,false,true,true,false,false,true,false,false)\n219:(2,false,0,false,true,true,false,false,true,false,true)\n220:(2,false,0,true,true,false,false,false,false,false,false)\n221:(2,false,0,true,true,false,false,false,false,false,true)\n222:(2,false,0,true,true,false,false,false,true,false,false)\n223:(2,false,0,true,true,false,false,false,true,false,true)\n224:(2,false,0,true,true,false,true,false,false,false,false)\n225:(2,false,0,true,true,false,true,false,false,false,true)\n226:(2,false,0,true,true,false,true,false,true,false,false)\n227:(2,false,0,true,true,false,true,false,true,false,true)\n228:(2,false,1,false,false,false,false,false,false,false,false)\n229:(2,false,1,false,false,false,false,false,false,false,true)\n230:(2,false,1,false,false,false,false,false,true,false,false)\n231:(2,false,1,false,false,false,false,false,true,false,true)\n232:(2,false,1,false,false,false,true,false,false,false,false)\n233:(2,false,1,false,false,false,true,false,false,false,true)\n234:(2,false,1,false,false,false,true,false,true,false,false)\n235:(2,false,1,false,false,false,true,false,true,false,true)\n236:(2,false,1,false,true,false,false,false,false,true,false)\n237:(2,false,1,false,true,false,false,false,true,true,false)\n238:(2,false,1,false,true,false,false,true,false,false,false)\n239:(2,false,1,false,true,false,false,true,false,false,true)\n240:(2,false,1,false,true,false,true,false,false,true,false)\n241:(2,false,1,false,true,false,true,false,true,true,false)\n242:(2,false,1,false,true,false,true,true,false,false,false)\n243:(2,false,1,false,true,false,true,true,false,false,true)\n244:(2,false,1,false,true,true,false,false,false,false,false)\n245:(2,false,1,false,true,true,false,false,false,false,true)\n246:(2,false,1,false,true,true,false,false,true,false,false)\n247:(2,false,1,false,true,true,false,false,true,false,true)\n248:(2,false,1,true,true,false,false,false,false,false,false)\n249:(2,false,1,true,true,false,false,false,false,false,true)\n250:(2,false,1,true,true,false,false,false,true,false,false)\n251:(2,false,1,true,true,false,false,false,true,false,true)\n252:(2,false,1,true,true,false,true,false,false,false,false)\n253:(2,false,1,true,true,false,true,false,false,false,true)\n254:(2,false,1,true,true,false,true,false,true,false,false)\n255:(2,false,1,true,true,false,true,false,true,false,true)\n256:(2,false,2,false,false,false,false,false,false,false,false)\n257:(2,false,2,false,false,false,false,false,false,false,true)\n258:(2,false,2,false,false,false,false,false,true,false,false)\n259:(2,false,2,false,false,false,false,false,true,false,true)\n260:(2,false,2,false,false,false,true,false,false,false,false)\n261:(2,false,2,false,false,false,true,false,false,false,true)\n262:(2,false,2,false,false,false,true,false,true,false,false)\n263:(2,false,2,false,false,false,true,false,true,false,true)\n264:(2,false,2,false,true,false,false,false,false,true,false)\n265:(2,false,2,false,true,false,false,false,true,true,false)\n266:(2,false,2,false,true,false,false,true,false,false,false)\n267:(2,false,2,false,true,false,false,true,false,false,true)\n268:(2,false,2,false,true,false,true,false,false,true,false)\n269:(2,false,2,false,true,false,true,false,true,true,false)\n270:(2,false,2,false,true,false,true,true,false,false,false)\n271:(2,false,2,false,true,false,true,true,false,false,true)\n272:(2,false,2,false,true,true,false,false,false,false,false)\n273:(2,false,2,false,true,true,false,false,false,false,true)\n274:(2,false,2,false,true,true,false,false,true,false,false)\n275:(2,false,2,false,true,true,false,false,true,false,true)\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm.tra",
    "content": "276 1120\n0 8 10\n0 10 10\n0 16 10\n0 20 10\n0 76 10\n1 0 0.00025\n1 11 10\n1 17 10\n1 21 10\n1 77 10\n2 0 0.00025\n2 9 10\n2 18 10\n2 22 10\n2 78 10\n3 1 0.00025\n3 2 0.00025\n3 19 10\n3 23 10\n3 79 10\n4 0 0.0002\n4 12 10\n4 14 10\n4 24 10\n4 80 10\n5 1 0.0002\n5 4 0.00025\n5 15 10\n5 25 10\n5 81 10\n6 2 0.0002\n6 4 0.00025\n6 13 10\n6 26 10\n6 82 10\n7 3 0.0002\n7 5 0.00025\n7 6 0.00025\n7 27 10\n7 83 10\n8 1 0.25\n9 3 0.25\n9 8 0.00025\n10 2 0.25\n11 3 0.25\n11 10 0.00025\n12 5 0.25\n12 8 0.0002\n13 7 0.25\n13 9 0.0002\n13 12 0.00025\n14 6 0.25\n14 10 0.0002\n15 7 0.25\n15 11 0.0002\n15 14 0.00025\n16 4 0.125\n17 5 0.125\n17 16 0.00025\n18 6 0.125\n18 16 0.00025\n19 7 0.125\n19 17 0.00025\n19 18 0.00025\n20 28 2\n21 20 0.00025\n21 29 2\n22 20 0.00025\n22 30 2\n23 21 0.00025\n23 22 0.00025\n23 31 2\n24 20 0.0002\n24 32 2\n25 21 0.0002\n25 24 0.00025\n25 33 2\n26 22 0.0002\n26 24 0.00025\n26 34 2\n27 23 0.0002\n27 25 0.00025\n27 26 0.00025\n27 35 2\n28 0 0.002\n28 36 10\n28 38 10\n28 44 10\n28 48 10\n28 84 10\n29 1 0.002\n29 28 0.00025\n29 39 10\n29 45 10\n29 49 10\n29 85 10\n30 2 0.002\n30 28 0.00025\n30 37 10\n30 46 10\n30 50 10\n30 86 10\n31 3 0.002\n31 29 0.00025\n31 30 0.00025\n31 47 10\n31 51 10\n31 87 10\n32 4 0.002\n32 28 0.0002\n32 40 10\n32 42 10\n32 52 10\n32 88 10\n33 5 0.002\n33 29 0.0002\n33 32 0.00025\n33 43 10\n33 53 10\n33 89 10\n34 6 0.002\n34 30 0.0002\n34 32 0.00025\n34 41 10\n34 54 10\n34 90 10\n35 7 0.002\n35 31 0.0002\n35 33 0.00025\n35 34 0.00025\n35 55 10\n35 91 10\n36 8 0.002\n36 29 0.25\n37 9 0.002\n37 31 0.25\n37 36 0.00025\n38 10 0.002\n38 30 0.25\n39 11 0.002\n39 31 0.25\n39 38 0.00025\n40 12 0.002\n40 33 0.25\n40 36 0.0002\n41 13 0.002\n41 35 0.25\n41 37 0.0002\n41 40 0.00025\n42 14 0.002\n42 34 0.25\n42 38 0.0002\n43 15 0.002\n43 35 0.25\n43 39 0.0002\n43 42 0.00025\n44 16 0.002\n44 32 0.125\n45 17 0.002\n45 33 0.125\n45 44 0.00025\n46 18 0.002\n46 34 0.125\n46 44 0.00025\n47 19 0.002\n47 35 0.125\n47 45 0.00025\n47 46 0.00025\n48 20 0.002\n48 56 2\n49 21 0.002\n49 48 0.00025\n49 57 2\n50 22 0.002\n50 48 0.00025\n50 58 2\n51 23 0.002\n51 49 0.00025\n51 50 0.00025\n51 59 2\n52 24 0.002\n52 48 0.0002\n52 60 2\n53 25 0.002\n53 49 0.0002\n53 52 0.00025\n53 61 2\n54 26 0.002\n54 50 0.0002\n54 52 0.00025\n54 62 2\n55 27 0.002\n55 51 0.0002\n55 53 0.00025\n55 54 0.00025\n55 63 2\n56 28 0.004\n56 64 10\n56 66 10\n56 72 10\n56 92 10\n57 29 0.004\n57 56 0.00025\n57 67 10\n57 73 10\n57 93 10\n58 30 0.004\n58 56 0.00025\n58 65 10\n58 74 10\n58 94 10\n59 31 0.004\n59 57 0.00025\n59 58 0.00025\n59 75 10\n59 95 10\n60 32 0.004\n60 56 0.0002\n60 68 10\n60 70 10\n60 96 10\n61 33 0.004\n61 57 0.0002\n61 60 0.00025\n61 71 10\n61 97 10\n62 34 0.004\n62 58 0.0002\n62 60 0.00025\n62 69 10\n62 98 10\n63 35 0.004\n63 59 0.0002\n63 61 0.00025\n63 62 0.00025\n63 99 10\n64 36 0.004\n64 57 0.25\n65 37 0.004\n65 59 0.25\n65 64 0.00025\n66 38 0.004\n66 58 0.25\n67 39 0.004\n67 59 0.25\n67 66 0.00025\n68 40 0.004\n68 61 0.25\n68 64 0.0002\n69 41 0.004\n69 63 0.25\n69 65 0.0002\n69 68 0.00025\n70 42 0.004\n70 62 0.25\n70 66 0.0002\n71 43 0.004\n71 63 0.25\n71 67 0.0002\n71 70 0.00025\n72 44 0.004\n72 60 0.125\n73 45 0.004\n73 61 0.125\n73 72 0.00025\n74 46 0.004\n74 62 0.125\n74 72 0.00025\n75 47 0.004\n75 63 0.125\n75 73 0.00025\n75 74 0.00025\n76 100 2\n77 76 0.00025\n77 101 2\n78 76 0.00025\n78 102 2\n79 77 0.00025\n79 78 0.00025\n79 103 2\n80 76 0.0002\n80 104 2\n81 77 0.0002\n81 80 0.00025\n81 105 2\n82 78 0.0002\n82 80 0.00025\n82 106 2\n83 79 0.0002\n83 81 0.00025\n83 82 0.00025\n83 107 2\n84 76 0.002\n84 128 2\n85 77 0.002\n85 84 0.00025\n85 129 2\n86 78 0.002\n86 84 0.00025\n86 130 2\n87 79 0.002\n87 85 0.00025\n87 86 0.00025\n87 131 2\n88 80 0.002\n88 84 0.0002\n88 132 2\n89 81 0.002\n89 85 0.0002\n89 88 0.00025\n89 133 2\n90 82 0.002\n90 86 0.0002\n90 88 0.00025\n90 134 2\n91 83 0.002\n91 87 0.0002\n91 89 0.00025\n91 90 0.00025\n91 135 2\n92 84 0.004\n92 156 2\n93 85 0.004\n93 92 0.00025\n93 157 2\n94 86 0.004\n94 92 0.00025\n94 158 2\n95 87 0.004\n95 93 0.00025\n95 94 0.00025\n95 159 2\n96 88 0.004\n96 92 0.0002\n96 160 2\n97 89 0.004\n97 93 0.0002\n97 96 0.00025\n97 161 2\n98 90 0.004\n98 94 0.0002\n98 96 0.00025\n98 162 2\n99 91 0.004\n99 95 0.0002\n99 97 0.00025\n99 98 0.00025\n99 163 2\n100 0 0.002\n100 108 10\n100 110 10\n100 116 10\n100 120 10\n100 176 10\n101 1 0.002\n101 100 0.00025\n101 111 10\n101 117 10\n101 121 10\n101 177 10\n102 2 0.002\n102 100 0.00025\n102 109 10\n102 118 10\n102 122 10\n102 178 10\n103 3 0.002\n103 101 0.00025\n103 102 0.00025\n103 119 10\n103 123 10\n103 179 10\n104 4 0.002\n104 100 0.0002\n104 112 10\n104 114 10\n104 124 10\n104 180 10\n105 5 0.002\n105 101 0.0002\n105 104 0.00025\n105 115 10\n105 125 10\n105 181 10\n106 6 0.002\n106 102 0.0002\n106 104 0.00025\n106 113 10\n106 126 10\n106 182 10\n107 7 0.002\n107 103 0.0002\n107 105 0.00025\n107 106 0.00025\n107 127 10\n107 183 10\n108 8 0.002\n108 101 0.25\n109 9 0.002\n109 103 0.25\n109 108 0.00025\n110 10 0.002\n110 102 0.25\n111 11 0.002\n111 103 0.25\n111 110 0.00025\n112 12 0.002\n112 105 0.25\n112 108 0.0002\n113 13 0.002\n113 107 0.25\n113 109 0.0002\n113 112 0.00025\n114 14 0.002\n114 106 0.25\n114 110 0.0002\n115 15 0.002\n115 107 0.25\n115 111 0.0002\n115 114 0.00025\n116 16 0.002\n116 104 0.125\n117 17 0.002\n117 105 0.125\n117 116 0.00025\n118 18 0.002\n118 106 0.125\n118 116 0.00025\n119 19 0.002\n119 107 0.125\n119 117 0.00025\n119 118 0.00025\n120 20 0.002\n120 128 2\n121 21 0.002\n121 120 0.00025\n121 129 2\n122 22 0.002\n122 120 0.00025\n122 130 2\n123 23 0.002\n123 121 0.00025\n123 122 0.00025\n123 131 2\n124 24 0.002\n124 120 0.0002\n124 132 2\n125 25 0.002\n125 121 0.0002\n125 124 0.00025\n125 133 2\n126 26 0.002\n126 122 0.0002\n126 124 0.00025\n126 134 2\n127 27 0.002\n127 123 0.0002\n127 125 0.00025\n127 126 0.00025\n127 135 2\n128 28 0.002\n128 100 0.002\n128 136 10\n128 138 10\n128 144 10\n128 148 10\n128 184 10\n129 29 0.002\n129 101 0.002\n129 128 0.00025\n129 139 10\n129 145 10\n129 149 10\n129 185 10\n130 30 0.002\n130 102 0.002\n130 128 0.00025\n130 137 10\n130 146 10\n130 150 10\n130 186 10\n131 31 0.002\n131 103 0.002\n131 129 0.00025\n131 130 0.00025\n131 147 10\n131 151 10\n131 187 10\n132 32 0.002\n132 104 0.002\n132 128 0.0002\n132 140 10\n132 142 10\n132 152 10\n132 188 10\n133 33 0.002\n133 105 0.002\n133 129 0.0002\n133 132 0.00025\n133 143 10\n133 153 10\n133 189 10\n134 34 0.002\n134 106 0.002\n134 130 0.0002\n134 132 0.00025\n134 141 10\n134 154 10\n134 190 10\n135 35 0.002\n135 107 0.002\n135 131 0.0002\n135 133 0.00025\n135 134 0.00025\n135 155 10\n135 191 10\n136 36 0.002\n136 108 0.002\n136 129 0.25\n137 37 0.002\n137 109 0.002\n137 131 0.25\n137 136 0.00025\n138 38 0.002\n138 110 0.002\n138 130 0.25\n139 39 0.002\n139 111 0.002\n139 131 0.25\n139 138 0.00025\n140 40 0.002\n140 112 0.002\n140 133 0.25\n140 136 0.0002\n141 41 0.002\n141 113 0.002\n141 135 0.25\n141 137 0.0002\n141 140 0.00025\n142 42 0.002\n142 114 0.002\n142 134 0.25\n142 138 0.0002\n143 43 0.002\n143 115 0.002\n143 135 0.25\n143 139 0.0002\n143 142 0.00025\n144 44 0.002\n144 116 0.002\n144 132 0.125\n145 45 0.002\n145 117 0.002\n145 133 0.125\n145 144 0.00025\n146 46 0.002\n146 118 0.002\n146 134 0.125\n146 144 0.00025\n147 47 0.002\n147 119 0.002\n147 135 0.125\n147 145 0.00025\n147 146 0.00025\n148 48 0.002\n148 120 0.002\n148 156 2\n149 49 0.002\n149 121 0.002\n149 148 0.00025\n149 157 2\n150 50 0.002\n150 122 0.002\n150 148 0.00025\n150 158 2\n151 51 0.002\n151 123 0.002\n151 149 0.00025\n151 150 0.00025\n151 159 2\n152 52 0.002\n152 124 0.002\n152 148 0.0002\n152 160 2\n153 53 0.002\n153 125 0.002\n153 149 0.0002\n153 152 0.00025\n153 161 2\n154 54 0.002\n154 126 0.002\n154 150 0.0002\n154 152 0.00025\n154 162 2\n155 55 0.002\n155 127 0.002\n155 151 0.0002\n155 153 0.00025\n155 154 0.00025\n155 163 2\n156 56 0.002\n156 128 0.004\n156 164 10\n156 166 10\n156 172 10\n156 192 10\n157 57 0.002\n157 129 0.004\n157 156 0.00025\n157 167 10\n157 173 10\n157 193 10\n158 58 0.002\n158 130 0.004\n158 156 0.00025\n158 165 10\n158 174 10\n158 194 10\n159 59 0.002\n159 131 0.004\n159 157 0.00025\n159 158 0.00025\n159 175 10\n159 195 10\n160 60 0.002\n160 132 0.004\n160 156 0.0002\n160 168 10\n160 170 10\n160 196 10\n161 61 0.002\n161 133 0.004\n161 157 0.0002\n161 160 0.00025\n161 171 10\n161 197 10\n162 62 0.002\n162 134 0.004\n162 158 0.0002\n162 160 0.00025\n162 169 10\n162 198 10\n163 63 0.002\n163 135 0.004\n163 159 0.0002\n163 161 0.00025\n163 162 0.00025\n163 199 10\n164 64 0.002\n164 136 0.004\n164 157 0.25\n165 65 0.002\n165 137 0.004\n165 159 0.25\n165 164 0.00025\n166 66 0.002\n166 138 0.004\n166 158 0.25\n167 67 0.002\n167 139 0.004\n167 159 0.25\n167 166 0.00025\n168 68 0.002\n168 140 0.004\n168 161 0.25\n168 164 0.0002\n169 69 0.002\n169 141 0.004\n169 163 0.25\n169 165 0.0002\n169 168 0.00025\n170 70 0.002\n170 142 0.004\n170 162 0.25\n170 166 0.0002\n171 71 0.002\n171 143 0.004\n171 163 0.25\n171 167 0.0002\n171 170 0.00025\n172 72 0.002\n172 144 0.004\n172 160 0.125\n173 73 0.002\n173 145 0.004\n173 161 0.125\n173 172 0.00025\n174 74 0.002\n174 146 0.004\n174 162 0.125\n174 172 0.00025\n175 75 0.002\n175 147 0.004\n175 163 0.125\n175 173 0.00025\n175 174 0.00025\n176 76 0.002\n176 200 2\n177 77 0.002\n177 176 0.00025\n177 201 2\n178 78 0.002\n178 176 0.00025\n178 202 2\n179 79 0.002\n179 177 0.00025\n179 178 0.00025\n179 203 2\n180 80 0.002\n180 176 0.0002\n180 204 2\n181 81 0.002\n181 177 0.0002\n181 180 0.00025\n181 205 2\n182 82 0.002\n182 178 0.0002\n182 180 0.00025\n182 206 2\n183 83 0.002\n183 179 0.0002\n183 181 0.00025\n183 182 0.00025\n183 207 2\n184 84 0.002\n184 176 0.002\n184 228 2\n185 85 0.002\n185 177 0.002\n185 184 0.00025\n185 229 2\n186 86 0.002\n186 178 0.002\n186 184 0.00025\n186 230 2\n187 87 0.002\n187 179 0.002\n187 185 0.00025\n187 186 0.00025\n187 231 2\n188 88 0.002\n188 180 0.002\n188 184 0.0002\n188 232 2\n189 89 0.002\n189 181 0.002\n189 185 0.0002\n189 188 0.00025\n189 233 2\n190 90 0.002\n190 182 0.002\n190 186 0.0002\n190 188 0.00025\n190 234 2\n191 91 0.002\n191 183 0.002\n191 187 0.0002\n191 189 0.00025\n191 190 0.00025\n191 235 2\n192 92 0.002\n192 184 0.004\n192 256 2\n193 93 0.002\n193 185 0.004\n193 192 0.00025\n193 257 2\n194 94 0.002\n194 186 0.004\n194 192 0.00025\n194 258 2\n195 95 0.002\n195 187 0.004\n195 193 0.00025\n195 194 0.00025\n195 259 2\n196 96 0.002\n196 188 0.004\n196 192 0.0002\n196 260 2\n197 97 0.002\n197 189 0.004\n197 193 0.0002\n197 196 0.00025\n197 261 2\n198 98 0.002\n198 190 0.004\n198 194 0.0002\n198 196 0.00025\n198 262 2\n199 99 0.002\n199 191 0.004\n199 195 0.0002\n199 197 0.00025\n199 198 0.00025\n199 263 2\n200 100 0.004\n200 208 10\n200 210 10\n200 216 10\n200 220 10\n201 101 0.004\n201 200 0.00025\n201 211 10\n201 217 10\n201 221 10\n202 102 0.004\n202 200 0.00025\n202 209 10\n202 218 10\n202 222 10\n203 103 0.004\n203 201 0.00025\n203 202 0.00025\n203 219 10\n203 223 10\n204 104 0.004\n204 200 0.0002\n204 212 10\n204 214 10\n204 224 10\n205 105 0.004\n205 201 0.0002\n205 204 0.00025\n205 215 10\n205 225 10\n206 106 0.004\n206 202 0.0002\n206 204 0.00025\n206 213 10\n206 226 10\n207 107 0.004\n207 203 0.0002\n207 205 0.00025\n207 206 0.00025\n207 227 10\n208 108 0.004\n208 201 0.25\n209 109 0.004\n209 203 0.25\n209 208 0.00025\n210 110 0.004\n210 202 0.25\n211 111 0.004\n211 203 0.25\n211 210 0.00025\n212 112 0.004\n212 205 0.25\n212 208 0.0002\n213 113 0.004\n213 207 0.25\n213 209 0.0002\n213 212 0.00025\n214 114 0.004\n214 206 0.25\n214 210 0.0002\n215 115 0.004\n215 207 0.25\n215 211 0.0002\n215 214 0.00025\n216 116 0.004\n216 204 0.125\n217 117 0.004\n217 205 0.125\n217 216 0.00025\n218 118 0.004\n218 206 0.125\n218 216 0.00025\n219 119 0.004\n219 207 0.125\n219 217 0.00025\n219 218 0.00025\n220 120 0.004\n220 228 2\n221 121 0.004\n221 220 0.00025\n221 229 2\n222 122 0.004\n222 220 0.00025\n222 230 2\n223 123 0.004\n223 221 0.00025\n223 222 0.00025\n223 231 2\n224 124 0.004\n224 220 0.0002\n224 232 2\n225 125 0.004\n225 221 0.0002\n225 224 0.00025\n225 233 2\n226 126 0.004\n226 222 0.0002\n226 224 0.00025\n226 234 2\n227 127 0.004\n227 223 0.0002\n227 225 0.00025\n227 226 0.00025\n227 235 2\n228 128 0.004\n228 200 0.002\n228 236 10\n228 238 10\n228 244 10\n228 248 10\n229 129 0.004\n229 201 0.002\n229 228 0.00025\n229 239 10\n229 245 10\n229 249 10\n230 130 0.004\n230 202 0.002\n230 228 0.00025\n230 237 10\n230 246 10\n230 250 10\n231 131 0.004\n231 203 0.002\n231 229 0.00025\n231 230 0.00025\n231 247 10\n231 251 10\n232 132 0.004\n232 204 0.002\n232 228 0.0002\n232 240 10\n232 242 10\n232 252 10\n233 133 0.004\n233 205 0.002\n233 229 0.0002\n233 232 0.00025\n233 243 10\n233 253 10\n234 134 0.004\n234 206 0.002\n234 230 0.0002\n234 232 0.00025\n234 241 10\n234 254 10\n235 135 0.004\n235 207 0.002\n235 231 0.0002\n235 233 0.00025\n235 234 0.00025\n235 255 10\n236 136 0.004\n236 208 0.002\n236 229 0.25\n237 137 0.004\n237 209 0.002\n237 231 0.25\n237 236 0.00025\n238 138 0.004\n238 210 0.002\n238 230 0.25\n239 139 0.004\n239 211 0.002\n239 231 0.25\n239 238 0.00025\n240 140 0.004\n240 212 0.002\n240 233 0.25\n240 236 0.0002\n241 141 0.004\n241 213 0.002\n241 235 0.25\n241 237 0.0002\n241 240 0.00025\n242 142 0.004\n242 214 0.002\n242 234 0.25\n242 238 0.0002\n243 143 0.004\n243 215 0.002\n243 235 0.25\n243 239 0.0002\n243 242 0.00025\n244 144 0.004\n244 216 0.002\n244 232 0.125\n245 145 0.004\n245 217 0.002\n245 233 0.125\n245 244 0.00025\n246 146 0.004\n246 218 0.002\n246 234 0.125\n246 244 0.00025\n247 147 0.004\n247 219 0.002\n247 235 0.125\n247 245 0.00025\n247 246 0.00025\n248 148 0.004\n248 220 0.002\n248 256 2\n249 149 0.004\n249 221 0.002\n249 248 0.00025\n249 257 2\n250 150 0.004\n250 222 0.002\n250 248 0.00025\n250 258 2\n251 151 0.004\n251 223 0.002\n251 249 0.00025\n251 250 0.00025\n251 259 2\n252 152 0.004\n252 224 0.002\n252 248 0.0002\n252 260 2\n253 153 0.004\n253 225 0.002\n253 249 0.0002\n253 252 0.00025\n253 261 2\n254 154 0.004\n254 226 0.002\n254 250 0.0002\n254 252 0.00025\n254 262 2\n255 155 0.004\n255 227 0.002\n255 251 0.0002\n255 253 0.00025\n255 254 0.00025\n255 263 2\n256 156 0.004\n256 228 0.004\n256 264 10\n256 266 10\n256 272 10\n257 157 0.004\n257 229 0.004\n257 256 0.00025\n257 267 10\n257 273 10\n258 158 0.004\n258 230 0.004\n258 256 0.00025\n258 265 10\n258 274 10\n259 159 0.004\n259 231 0.004\n259 257 0.00025\n259 258 0.00025\n259 275 10\n260 160 0.004\n260 232 0.004\n260 256 0.0002\n260 268 10\n260 270 10\n261 161 0.004\n261 233 0.004\n261 257 0.0002\n261 260 0.00025\n261 271 10\n262 162 0.004\n262 234 0.004\n262 258 0.0002\n262 260 0.00025\n262 269 10\n263 163 0.004\n263 235 0.004\n263 259 0.0002\n263 261 0.00025\n263 262 0.00025\n264 164 0.004\n264 236 0.004\n264 257 0.25\n265 165 0.004\n265 237 0.004\n265 259 0.25\n265 264 0.00025\n266 166 0.004\n266 238 0.004\n266 258 0.25\n267 167 0.004\n267 239 0.004\n267 259 0.25\n267 266 0.00025\n268 168 0.004\n268 240 0.004\n268 261 0.25\n268 264 0.0002\n269 169 0.004\n269 241 0.004\n269 263 0.25\n269 265 0.0002\n269 268 0.00025\n270 170 0.004\n270 242 0.004\n270 262 0.25\n270 266 0.0002\n271 171 0.004\n271 243 0.004\n271 263 0.25\n271 267 0.0002\n271 270 0.00025\n272 172 0.004\n272 244 0.004\n272 260 0.125\n273 173 0.004\n273 245 0.004\n273 261 0.125\n273 272 0.00025\n274 174 0.004\n274 246 0.004\n274 262 0.125\n274 272 0.00025\n275 175 0.004\n275 247 0.004\n275 263 0.125\n275 273 0.00025\n275 274 0.00025\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm1.srew",
    "content": "# Reward structure \"percent_op\"\n# State rewards\n276 240\n28 25\n29 25\n30 25\n31 25\n32 25\n33 25\n34 25\n35 25\n36 25\n37 25\n38 25\n39 25\n40 25\n41 25\n42 25\n43 25\n44 25\n45 25\n46 25\n47 25\n48 25\n49 25\n50 25\n51 25\n52 25\n53 25\n54 25\n55 25\n56 50\n57 50\n58 50\n59 50\n60 50\n61 50\n62 50\n63 50\n64 50\n65 50\n66 50\n67 50\n68 50\n69 50\n70 50\n71 50\n72 50\n73 50\n74 50\n75 50\n84 25\n85 25\n86 25\n87 25\n88 25\n89 25\n90 25\n91 25\n92 50\n93 50\n94 50\n95 50\n96 50\n97 50\n98 50\n99 50\n100 25\n101 25\n102 25\n103 25\n104 25\n105 25\n106 25\n107 25\n108 25\n109 25\n110 25\n111 25\n112 25\n113 25\n114 25\n115 25\n116 25\n117 25\n118 25\n119 25\n120 25\n121 25\n122 25\n123 25\n124 25\n125 25\n126 25\n127 25\n128 50\n129 50\n130 50\n131 50\n132 50\n133 50\n134 50\n135 50\n136 50\n137 50\n138 50\n139 50\n140 50\n141 50\n142 50\n143 50\n144 50\n145 50\n146 50\n147 50\n148 50\n149 50\n150 50\n151 50\n152 50\n153 50\n154 50\n155 50\n156 75\n157 75\n158 75\n159 75\n160 75\n161 75\n162 75\n163 75\n164 75\n165 75\n166 75\n167 75\n168 75\n169 75\n170 75\n171 75\n172 75\n173 75\n174 75\n175 75\n176 25\n177 25\n178 25\n179 25\n180 25\n181 25\n182 25\n183 25\n184 50\n185 50\n186 50\n187 50\n188 50\n189 50\n190 50\n191 50\n192 75\n193 75\n194 75\n195 75\n196 75\n197 75\n198 75\n199 75\n200 50\n201 50\n202 50\n203 50\n204 50\n205 50\n206 50\n207 50\n208 50\n209 50\n210 50\n211 50\n212 50\n213 50\n214 50\n215 50\n216 50\n217 50\n218 50\n219 50\n220 50\n221 50\n222 50\n223 50\n224 50\n225 50\n226 50\n227 50\n228 75\n229 75\n230 75\n231 75\n232 75\n233 75\n234 75\n235 75\n236 75\n237 75\n238 75\n239 75\n240 75\n241 75\n242 75\n243 75\n244 75\n245 75\n246 75\n247 75\n248 75\n249 75\n250 75\n251 75\n252 75\n253 75\n254 75\n255 75\n256 100\n257 100\n258 100\n259 100\n260 100\n261 100\n262 100\n263 100\n264 100\n265 100\n266 100\n267 100\n268 100\n269 100\n270 100\n271 100\n272 100\n273 100\n274 100\n275 100\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm1.trew",
    "content": "# Reward structure \"percent_op\"\n# Transition rewards\n276 0\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm2.srew",
    "content": "# Reward structure \"time_not_min\"\n# State rewards\n276 144\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n6 1\n7 1\n8 1\n9 1\n10 1\n11 1\n12 1\n13 1\n14 1\n15 1\n16 1\n17 1\n18 1\n19 1\n20 1\n21 1\n22 1\n23 1\n24 1\n25 1\n26 1\n27 1\n28 1\n30 1\n32 1\n34 1\n36 1\n37 1\n38 1\n40 1\n41 1\n42 1\n44 1\n46 1\n48 1\n50 1\n52 1\n54 1\n56 1\n58 1\n60 1\n62 1\n64 1\n65 1\n66 1\n68 1\n69 1\n70 1\n72 1\n74 1\n76 1\n77 1\n78 1\n79 1\n80 1\n81 1\n82 1\n83 1\n84 1\n86 1\n88 1\n90 1\n92 1\n94 1\n96 1\n98 1\n100 1\n101 1\n104 1\n105 1\n108 1\n110 1\n111 1\n112 1\n114 1\n115 1\n116 1\n117 1\n120 1\n121 1\n124 1\n125 1\n128 1\n132 1\n136 1\n138 1\n140 1\n142 1\n144 1\n148 1\n152 1\n156 1\n160 1\n164 1\n166 1\n168 1\n170 1\n172 1\n176 1\n177 1\n180 1\n181 1\n184 1\n188 1\n192 1\n196 1\n200 1\n201 1\n204 1\n205 1\n208 1\n210 1\n211 1\n212 1\n214 1\n215 1\n216 1\n217 1\n220 1\n221 1\n224 1\n225 1\n228 1\n232 1\n236 1\n238 1\n240 1\n242 1\n244 1\n248 1\n252 1\n256 1\n260 1\n264 1\n266 1\n268 1\n270 1\n272 1\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm2.trew",
    "content": "# Reward structure \"time_not_min\"\n# Transition rewards\n276 0\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm3.srew",
    "content": "# Reward structure \"num_repairs\"\n# State rewards\n276 0\n"
  },
  {
    "path": "prism-tests/functionality/export/ctmc/cluster.sm3.trew",
    "content": "# Reward structure \"num_repairs\"\n# Transition rewards\n276 204\n8 1 1\n9 3 1\n10 2 1\n11 3 1\n12 5 1\n13 7 1\n14 6 1\n15 7 1\n16 4 1\n17 5 1\n18 6 1\n19 7 1\n20 28 1\n21 29 1\n22 30 1\n23 31 1\n24 32 1\n25 33 1\n26 34 1\n27 35 1\n36 29 1\n37 31 1\n38 30 1\n39 31 1\n40 33 1\n41 35 1\n42 34 1\n43 35 1\n44 32 1\n45 33 1\n46 34 1\n47 35 1\n48 56 1\n49 57 1\n50 58 1\n51 59 1\n52 60 1\n53 61 1\n54 62 1\n55 63 1\n64 57 1\n65 59 1\n66 58 1\n67 59 1\n68 61 1\n69 63 1\n70 62 1\n71 63 1\n72 60 1\n73 61 1\n74 62 1\n75 63 1\n76 100 1\n77 101 1\n78 102 1\n79 103 1\n80 104 1\n81 105 1\n82 106 1\n83 107 1\n84 128 1\n85 129 1\n86 130 1\n87 131 1\n88 132 1\n89 133 1\n90 134 1\n91 135 1\n92 156 1\n93 157 1\n94 158 1\n95 159 1\n96 160 1\n97 161 1\n98 162 1\n99 163 1\n108 101 1\n109 103 1\n110 102 1\n111 103 1\n112 105 1\n113 107 1\n114 106 1\n115 107 1\n116 104 1\n117 105 1\n118 106 1\n119 107 1\n120 128 1\n121 129 1\n122 130 1\n123 131 1\n124 132 1\n125 133 1\n126 134 1\n127 135 1\n136 129 1\n137 131 1\n138 130 1\n139 131 1\n140 133 1\n141 135 1\n142 134 1\n143 135 1\n144 132 1\n145 133 1\n146 134 1\n147 135 1\n148 156 1\n149 157 1\n150 158 1\n151 159 1\n152 160 1\n153 161 1\n154 162 1\n155 163 1\n164 157 1\n165 159 1\n166 158 1\n167 159 1\n168 161 1\n169 163 1\n170 162 1\n171 163 1\n172 160 1\n173 161 1\n174 162 1\n175 163 1\n176 200 1\n177 201 1\n178 202 1\n179 203 1\n180 204 1\n181 205 1\n182 206 1\n183 207 1\n184 228 1\n185 229 1\n186 230 1\n187 231 1\n188 232 1\n189 233 1\n190 234 1\n191 235 1\n192 256 1\n193 257 1\n194 258 1\n195 259 1\n196 260 1\n197 261 1\n198 262 1\n199 263 1\n208 201 1\n209 203 1\n210 202 1\n211 203 1\n212 205 1\n213 207 1\n214 206 1\n215 207 1\n216 204 1\n217 205 1\n218 206 1\n219 207 1\n220 228 1\n221 229 1\n222 230 1\n223 231 1\n224 232 1\n225 233 1\n226 234 1\n227 235 1\n236 229 1\n237 231 1\n238 230 1\n239 231 1\n240 233 1\n241 235 1\n242 234 1\n243 235 1\n244 232 1\n245 233 1\n246 234 1\n247 235 1\n248 256 1\n249 257 1\n250 258 1\n251 259 1\n252 260 1\n253 261 1\n254 262 1\n255 263 1\n264 257 1\n265 259 1\n266 258 1\n267 259 1\n268 261 1\n269 263 1\n270 262 1\n271 263 1\n272 260 1\n273 261 1\n274 262 1\n275 263 1\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/cluster.sm",
    "content": "// Workstation cluster [HHK00]\r\n// dxp/gxn 11/01/00\r\n\r\nctmc\r\n\r\nconst int N; // Number of workstations in each cluster\r\nconst int left_mx = N; // Number of work stations in left cluster\r\nconst int right_mx = N; // Number of work stations in right cluster\r\n\r\n// Failure rates\r\nconst double ws_fail = 1/500; // Single workstation: average time to fail = 500 hrs\r\nconst double switch_fail = 1/4000; // Switch: average time to fail = 4000 hrs\r\nconst double line_fail = 1/5000; // Backbone: average time to fail = 5000 hrs\r\n\r\n// Left cluster\r\nmodule Left \r\n\t\r\n\tleft_n : [0..left_mx] init left_mx; // Number of workstations operational\r\n\tleft : bool; // Being repaired?\r\n\t\r\n\t[startLeft] !left & (left_n<left_mx) -> 1 : (left'=true);\r\n\t[repairLeft] left & (left_n<left_mx) -> 1 : (left'=false) & (left_n'=left_n+1);\r\n\t[] (left_n>0) -> ws_fail*left_n : (left_n'=left_n-1);\r\n\t\r\nendmodule\r\n\r\n// Right cluster\r\nmodule Right = Left[left_n=right_n,\r\n                    left=right,\r\n                    left_mx=right_mx,\r\n                    startLeft=startRight,\r\n                    repairLeft=repairRight ]\r\nendmodule\r\n\r\n// Repair unit\r\nmodule Repairman\r\n\t\r\n\tr : bool; // Repairing?\r\n\t\r\n\t[startLeft]    !r -> 10 : (r'=true); // Inspect Left \r\n\t[startRight]   !r -> 10 : (r'=true); // Inspect Right \r\n\t[startToLeft]  !r -> 10 : (r'=true); // Inspect ToLeft\r\n\t[startToRight] !r -> 10 : (r'=true); // Inspect ToRight \r\n\t[startLine]    !r -> 10 : (r'=true); // Inspect Line \r\n\t\r\n\t[repairLeft]    r -> 2     : (r'=false); // Repair Left \r\n\t[repairRight]   r -> 2     : (r'=false); // Repair Right\r\n\t[repairToLeft]  r -> 0.25  : (r'=false); // Repair ToLeft\r\n\t[repairToRight] r -> 0.25  : (r'=false); // Repair ToRight\r\n\t[repairLine]    r -> 0.125 : (r'=false); // Repair Line\r\n\t\r\nendmodule\r\n\r\n// Line/backbone\r\nmodule Line \r\n\t\r\n\tline :   bool; // Being repaired?\r\n\tline_n : bool init true; // Working?\r\n\t\r\n\t[startLine] !line & !line_n -> 1 : (line'=true);\r\n\t[repairLine] line & !line_n -> 1 : (line'=false) & (line_n'=true);\r\n\t[] line_n -> line_fail : (line_n'=false);\r\n\t\r\nendmodule\r\n\r\n// Left switch\r\nmodule ToLeft = Line[line=toleft,\r\n                     line_n=toleft_n,\r\n                     line_fail=switch_fail,\r\n                     startLine=startToLeft,\r\n                     repairLine=repairToLeft ]\r\nendmodule\r\n\r\n// Right switch\r\nmodule ToRight = Line[line=toright,\r\n                      line_n=toright_n,\r\n                      line_fail=switch_fail,\r\n                      startLine=startToRight,\r\n                      repairLine=repairToRight ]\r\nendmodule\r\n\r\n// Formulas + labels\r\n\r\n// Minimum QoS requires 3/4 connected workstations operational\r\nconst int k = floor(0.75*N);\r\n// left_operational_i : left_n>=i & toleft_n\r\n// right_operational_i : right_n>=i & toright_n\r\n// operational_i : (left_n+right_n)>=i & toleft_n & line_n & toright_n\r\n// minimum_k : left_operational_k | right_operational_k | operational_k\r\nformula minimum = (left_n>=k & toleft_n) | \r\n                  (right_n>=k & toright_n) | \r\n                  ((left_n+right_n)>=k & toleft_n & line_n & toright_n);\r\nlabel \"minimum\" = (left_n>=k & toleft_n) | (right_n>=k & toright_n) | ((left_n+right_n)>=k & toleft_n & line_n & toright_n);\r\n// premium = minimum_N\r\nlabel \"premium\" = (left_n>=left_mx & toleft_n) | (right_n>=right_mx & toright_n) | ((left_n+right_n)>=left_mx & toleft_n & line_n & toright_n);\r\n\r\n// Reward structures\r\n\r\n// Percentage of operational workstations stations\r\nrewards \"percent_op\"\r\n\ttrue : 100*(left_n+right_n)/(2*N);\r\nendrewards\r\n\r\n// Time that the system is not delivering at least minimum QoS\r\nrewards \"time_not_min\"\r\n\t!minimum : 1; \r\nendrewards\r\n\r\n// Number of repairs\r\nrewards \"num_repairs\"\r\n\t[repairLeft]    true : 1;\r\n\t[repairRight]   true : 1;\r\n\t[repairToLeft]  true : 1;\r\n\t[repairToRight] true : 1;\r\n\t[repairLine]    true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/cluster.sm.args",
    "content": "-const N=2\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/cluster.sm.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\"];\n0 -> 8 [label=\"10:startToRight\"];\n0 -> 10 [label=\"10:startToLeft\"];\n0 -> 16 [label=\"10:startLine\"];\n0 -> 20 [label=\"10:startRight\"];\n0 -> 76 [label=\"10:startLeft\"];\n1 [label=\"1\"];\n1 -> 0 [label=\"0.00025\"];\n1 -> 11 [label=\"10:startToLeft\"];\n1 -> 17 [label=\"10:startLine\"];\n1 -> 21 [label=\"10:startRight\"];\n1 -> 77 [label=\"10:startLeft\"];\n2 [label=\"2\"];\n2 -> 0 [label=\"0.00025\"];\n2 -> 9 [label=\"10:startToRight\"];\n2 -> 18 [label=\"10:startLine\"];\n2 -> 22 [label=\"10:startRight\"];\n2 -> 78 [label=\"10:startLeft\"];\n3 [label=\"3\"];\n3 -> 1 [label=\"0.00025\"];\n3 -> 2 [label=\"0.00025\"];\n3 -> 19 [label=\"10:startLine\"];\n3 -> 23 [label=\"10:startRight\"];\n3 -> 79 [label=\"10:startLeft\"];\n4 [label=\"4\"];\n4 -> 0 [label=\"0.0002\"];\n4 -> 12 [label=\"10:startToRight\"];\n4 -> 14 [label=\"10:startToLeft\"];\n4 -> 24 [label=\"10:startRight\"];\n4 -> 80 [label=\"10:startLeft\"];\n5 [label=\"5\"];\n5 -> 1 [label=\"0.0002\"];\n5 -> 4 [label=\"0.00025\"];\n5 -> 15 [label=\"10:startToLeft\"];\n5 -> 25 [label=\"10:startRight\"];\n5 -> 81 [label=\"10:startLeft\"];\n6 [label=\"6\"];\n6 -> 2 [label=\"0.0002\"];\n6 -> 4 [label=\"0.00025\"];\n6 -> 13 [label=\"10:startToRight\"];\n6 -> 26 [label=\"10:startRight\"];\n6 -> 82 [label=\"10:startLeft\"];\n7 [label=\"7\"];\n7 -> 3 [label=\"0.0002\"];\n7 -> 5 [label=\"0.00025\"];\n7 -> 6 [label=\"0.00025\"];\n7 -> 27 [label=\"10:startRight\"];\n7 -> 83 [label=\"10:startLeft\"];\n8 [label=\"8\"];\n8 -> 1 [label=\"0.25:repairToRight\"];\n9 [label=\"9\"];\n9 -> 3 [label=\"0.25:repairToRight\"];\n9 -> 8 [label=\"0.00025\"];\n10 [label=\"10\"];\n10 -> 2 [label=\"0.25:repairToLeft\"];\n11 [label=\"11\"];\n11 -> 3 [label=\"0.25:repairToLeft\"];\n11 -> 10 [label=\"0.00025\"];\n12 [label=\"12\"];\n12 -> 5 [label=\"0.25:repairToRight\"];\n12 -> 8 [label=\"0.0002\"];\n13 [label=\"13\"];\n13 -> 7 [label=\"0.25:repairToRight\"];\n13 -> 9 [label=\"0.0002\"];\n13 -> 12 [label=\"0.00025\"];\n14 [label=\"14\"];\n14 -> 6 [label=\"0.25:repairToLeft\"];\n14 -> 10 [label=\"0.0002\"];\n15 [label=\"15\"];\n15 -> 7 [label=\"0.25:repairToLeft\"];\n15 -> 11 [label=\"0.0002\"];\n15 -> 14 [label=\"0.00025\"];\n16 [label=\"16\"];\n16 -> 4 [label=\"0.125:repairLine\"];\n17 [label=\"17\"];\n17 -> 5 [label=\"0.125:repairLine\"];\n17 -> 16 [label=\"0.00025\"];\n18 [label=\"18\"];\n18 -> 6 [label=\"0.125:repairLine\"];\n18 -> 16 [label=\"0.00025\"];\n19 [label=\"19\"];\n19 -> 7 [label=\"0.125:repairLine\"];\n19 -> 17 [label=\"0.00025\"];\n19 -> 18 [label=\"0.00025\"];\n20 [label=\"20\"];\n20 -> 28 [label=\"2:repairRight\"];\n21 [label=\"21\"];\n21 -> 20 [label=\"0.00025\"];\n21 -> 29 [label=\"2:repairRight\"];\n22 [label=\"22\"];\n22 -> 20 [label=\"0.00025\"];\n22 -> 30 [label=\"2:repairRight\"];\n23 [label=\"23\"];\n23 -> 21 [label=\"0.00025\"];\n23 -> 22 [label=\"0.00025\"];\n23 -> 31 [label=\"2:repairRight\"];\n24 [label=\"24\"];\n24 -> 20 [label=\"0.0002\"];\n24 -> 32 [label=\"2:repairRight\"];\n25 [label=\"25\"];\n25 -> 21 [label=\"0.0002\"];\n25 -> 24 [label=\"0.00025\"];\n25 -> 33 [label=\"2:repairRight\"];\n26 [label=\"26\"];\n26 -> 22 [label=\"0.0002\"];\n26 -> 24 [label=\"0.00025\"];\n26 -> 34 [label=\"2:repairRight\"];\n27 [label=\"27\"];\n27 -> 23 [label=\"0.0002\"];\n27 -> 25 [label=\"0.00025\"];\n27 -> 26 [label=\"0.00025\"];\n27 -> 35 [label=\"2:repairRight\"];\n28 [label=\"28\"];\n28 -> 0 [label=\"0.002\"];\n28 -> 36 [label=\"10:startToRight\"];\n28 -> 38 [label=\"10:startToLeft\"];\n28 -> 44 [label=\"10:startLine\"];\n28 -> 48 [label=\"10:startRight\"];\n28 -> 84 [label=\"10:startLeft\"];\n29 [label=\"29\"];\n29 -> 1 [label=\"0.002\"];\n29 -> 28 [label=\"0.00025\"];\n29 -> 39 [label=\"10:startToLeft\"];\n29 -> 45 [label=\"10:startLine\"];\n29 -> 49 [label=\"10:startRight\"];\n29 -> 85 [label=\"10:startLeft\"];\n30 [label=\"30\"];\n30 -> 2 [label=\"0.002\"];\n30 -> 28 [label=\"0.00025\"];\n30 -> 37 [label=\"10:startToRight\"];\n30 -> 46 [label=\"10:startLine\"];\n30 -> 50 [label=\"10:startRight\"];\n30 -> 86 [label=\"10:startLeft\"];\n31 [label=\"31\"];\n31 -> 3 [label=\"0.002\"];\n31 -> 29 [label=\"0.00025\"];\n31 -> 30 [label=\"0.00025\"];\n31 -> 47 [label=\"10:startLine\"];\n31 -> 51 [label=\"10:startRight\"];\n31 -> 87 [label=\"10:startLeft\"];\n32 [label=\"32\"];\n32 -> 4 [label=\"0.002\"];\n32 -> 28 [label=\"0.0002\"];\n32 -> 40 [label=\"10:startToRight\"];\n32 -> 42 [label=\"10:startToLeft\"];\n32 -> 52 [label=\"10:startRight\"];\n32 -> 88 [label=\"10:startLeft\"];\n33 [label=\"33\"];\n33 -> 5 [label=\"0.002\"];\n33 -> 29 [label=\"0.0002\"];\n33 -> 32 [label=\"0.00025\"];\n33 -> 43 [label=\"10:startToLeft\"];\n33 -> 53 [label=\"10:startRight\"];\n33 -> 89 [label=\"10:startLeft\"];\n34 [label=\"34\"];\n34 -> 6 [label=\"0.002\"];\n34 -> 30 [label=\"0.0002\"];\n34 -> 32 [label=\"0.00025\"];\n34 -> 41 [label=\"10:startToRight\"];\n34 -> 54 [label=\"10:startRight\"];\n34 -> 90 [label=\"10:startLeft\"];\n35 [label=\"35\"];\n35 -> 7 [label=\"0.002\"];\n35 -> 31 [label=\"0.0002\"];\n35 -> 33 [label=\"0.00025\"];\n35 -> 34 [label=\"0.00025\"];\n35 -> 55 [label=\"10:startRight\"];\n35 -> 91 [label=\"10:startLeft\"];\n36 [label=\"36\"];\n36 -> 8 [label=\"0.002\"];\n36 -> 29 [label=\"0.25:repairToRight\"];\n37 [label=\"37\"];\n37 -> 9 [label=\"0.002\"];\n37 -> 31 [label=\"0.25:repairToRight\"];\n37 -> 36 [label=\"0.00025\"];\n38 [label=\"38\"];\n38 -> 10 [label=\"0.002\"];\n38 -> 30 [label=\"0.25:repairToLeft\"];\n39 [label=\"39\"];\n39 -> 11 [label=\"0.002\"];\n39 -> 31 [label=\"0.25:repairToLeft\"];\n39 -> 38 [label=\"0.00025\"];\n40 [label=\"40\"];\n40 -> 12 [label=\"0.002\"];\n40 -> 33 [label=\"0.25:repairToRight\"];\n40 -> 36 [label=\"0.0002\"];\n41 [label=\"41\"];\n41 -> 13 [label=\"0.002\"];\n41 -> 35 [label=\"0.25:repairToRight\"];\n41 -> 37 [label=\"0.0002\"];\n41 -> 40 [label=\"0.00025\"];\n42 [label=\"42\"];\n42 -> 14 [label=\"0.002\"];\n42 -> 34 [label=\"0.25:repairToLeft\"];\n42 -> 38 [label=\"0.0002\"];\n43 [label=\"43\"];\n43 -> 15 [label=\"0.002\"];\n43 -> 35 [label=\"0.25:repairToLeft\"];\n43 -> 39 [label=\"0.0002\"];\n43 -> 42 [label=\"0.00025\"];\n44 [label=\"44\"];\n44 -> 16 [label=\"0.002\"];\n44 -> 32 [label=\"0.125:repairLine\"];\n45 [label=\"45\"];\n45 -> 17 [label=\"0.002\"];\n45 -> 33 [label=\"0.125:repairLine\"];\n45 -> 44 [label=\"0.00025\"];\n46 [label=\"46\"];\n46 -> 18 [label=\"0.002\"];\n46 -> 34 [label=\"0.125:repairLine\"];\n46 -> 44 [label=\"0.00025\"];\n47 [label=\"47\"];\n47 -> 19 [label=\"0.002\"];\n47 -> 35 [label=\"0.125:repairLine\"];\n47 -> 45 [label=\"0.00025\"];\n47 -> 46 [label=\"0.00025\"];\n48 [label=\"48\"];\n48 -> 20 [label=\"0.002\"];\n48 -> 56 [label=\"2:repairRight\"];\n49 [label=\"49\"];\n49 -> 21 [label=\"0.002\"];\n49 -> 48 [label=\"0.00025\"];\n49 -> 57 [label=\"2:repairRight\"];\n50 [label=\"50\"];\n50 -> 22 [label=\"0.002\"];\n50 -> 48 [label=\"0.00025\"];\n50 -> 58 [label=\"2:repairRight\"];\n51 [label=\"51\"];\n51 -> 23 [label=\"0.002\"];\n51 -> 49 [label=\"0.00025\"];\n51 -> 50 [label=\"0.00025\"];\n51 -> 59 [label=\"2:repairRight\"];\n52 [label=\"52\"];\n52 -> 24 [label=\"0.002\"];\n52 -> 48 [label=\"0.0002\"];\n52 -> 60 [label=\"2:repairRight\"];\n53 [label=\"53\"];\n53 -> 25 [label=\"0.002\"];\n53 -> 49 [label=\"0.0002\"];\n53 -> 52 [label=\"0.00025\"];\n53 -> 61 [label=\"2:repairRight\"];\n54 [label=\"54\"];\n54 -> 26 [label=\"0.002\"];\n54 -> 50 [label=\"0.0002\"];\n54 -> 52 [label=\"0.00025\"];\n54 -> 62 [label=\"2:repairRight\"];\n55 [label=\"55\"];\n55 -> 27 [label=\"0.002\"];\n55 -> 51 [label=\"0.0002\"];\n55 -> 53 [label=\"0.00025\"];\n55 -> 54 [label=\"0.00025\"];\n55 -> 63 [label=\"2:repairRight\"];\n56 [label=\"56\"];\n56 -> 28 [label=\"0.004\"];\n56 -> 64 [label=\"10:startToRight\"];\n56 -> 66 [label=\"10:startToLeft\"];\n56 -> 72 [label=\"10:startLine\"];\n56 -> 92 [label=\"10:startLeft\"];\n57 [label=\"57\"];\n57 -> 29 [label=\"0.004\"];\n57 -> 56 [label=\"0.00025\"];\n57 -> 67 [label=\"10:startToLeft\"];\n57 -> 73 [label=\"10:startLine\"];\n57 -> 93 [label=\"10:startLeft\"];\n58 [label=\"58\"];\n58 -> 30 [label=\"0.004\"];\n58 -> 56 [label=\"0.00025\"];\n58 -> 65 [label=\"10:startToRight\"];\n58 -> 74 [label=\"10:startLine\"];\n58 -> 94 [label=\"10:startLeft\"];\n59 [label=\"59\"];\n59 -> 31 [label=\"0.004\"];\n59 -> 57 [label=\"0.00025\"];\n59 -> 58 [label=\"0.00025\"];\n59 -> 75 [label=\"10:startLine\"];\n59 -> 95 [label=\"10:startLeft\"];\n60 [label=\"60\"];\n60 -> 32 [label=\"0.004\"];\n60 -> 56 [label=\"0.0002\"];\n60 -> 68 [label=\"10:startToRight\"];\n60 -> 70 [label=\"10:startToLeft\"];\n60 -> 96 [label=\"10:startLeft\"];\n61 [label=\"61\"];\n61 -> 33 [label=\"0.004\"];\n61 -> 57 [label=\"0.0002\"];\n61 -> 60 [label=\"0.00025\"];\n61 -> 71 [label=\"10:startToLeft\"];\n61 -> 97 [label=\"10:startLeft\"];\n62 [label=\"62\"];\n62 -> 34 [label=\"0.004\"];\n62 -> 58 [label=\"0.0002\"];\n62 -> 60 [label=\"0.00025\"];\n62 -> 69 [label=\"10:startToRight\"];\n62 -> 98 [label=\"10:startLeft\"];\n63 [label=\"63\"];\n63 -> 35 [label=\"0.004\"];\n63 -> 59 [label=\"0.0002\"];\n63 -> 61 [label=\"0.00025\"];\n63 -> 62 [label=\"0.00025\"];\n63 -> 99 [label=\"10:startLeft\"];\n64 [label=\"64\"];\n64 -> 36 [label=\"0.004\"];\n64 -> 57 [label=\"0.25:repairToRight\"];\n65 [label=\"65\"];\n65 -> 37 [label=\"0.004\"];\n65 -> 59 [label=\"0.25:repairToRight\"];\n65 -> 64 [label=\"0.00025\"];\n66 [label=\"66\"];\n66 -> 38 [label=\"0.004\"];\n66 -> 58 [label=\"0.25:repairToLeft\"];\n67 [label=\"67\"];\n67 -> 39 [label=\"0.004\"];\n67 -> 59 [label=\"0.25:repairToLeft\"];\n67 -> 66 [label=\"0.00025\"];\n68 [label=\"68\"];\n68 -> 40 [label=\"0.004\"];\n68 -> 61 [label=\"0.25:repairToRight\"];\n68 -> 64 [label=\"0.0002\"];\n69 [label=\"69\"];\n69 -> 41 [label=\"0.004\"];\n69 -> 63 [label=\"0.25:repairToRight\"];\n69 -> 65 [label=\"0.0002\"];\n69 -> 68 [label=\"0.00025\"];\n70 [label=\"70\"];\n70 -> 42 [label=\"0.004\"];\n70 -> 62 [label=\"0.25:repairToLeft\"];\n70 -> 66 [label=\"0.0002\"];\n71 [label=\"71\"];\n71 -> 43 [label=\"0.004\"];\n71 -> 63 [label=\"0.25:repairToLeft\"];\n71 -> 67 [label=\"0.0002\"];\n71 -> 70 [label=\"0.00025\"];\n72 [label=\"72\"];\n72 -> 44 [label=\"0.004\"];\n72 -> 60 [label=\"0.125:repairLine\"];\n73 [label=\"73\"];\n73 -> 45 [label=\"0.004\"];\n73 -> 61 [label=\"0.125:repairLine\"];\n73 -> 72 [label=\"0.00025\"];\n74 [label=\"74\"];\n74 -> 46 [label=\"0.004\"];\n74 -> 62 [label=\"0.125:repairLine\"];\n74 -> 72 [label=\"0.00025\"];\n75 [label=\"75\"];\n75 -> 47 [label=\"0.004\"];\n75 -> 63 [label=\"0.125:repairLine\"];\n75 -> 73 [label=\"0.00025\"];\n75 -> 74 [label=\"0.00025\"];\n76 [label=\"76\"];\n76 -> 100 [label=\"2:repairLeft\"];\n77 [label=\"77\"];\n77 -> 76 [label=\"0.00025\"];\n77 -> 101 [label=\"2:repairLeft\"];\n78 [label=\"78\"];\n78 -> 76 [label=\"0.00025\"];\n78 -> 102 [label=\"2:repairLeft\"];\n79 [label=\"79\"];\n79 -> 77 [label=\"0.00025\"];\n79 -> 78 [label=\"0.00025\"];\n79 -> 103 [label=\"2:repairLeft\"];\n80 [label=\"80\"];\n80 -> 76 [label=\"0.0002\"];\n80 -> 104 [label=\"2:repairLeft\"];\n81 [label=\"81\"];\n81 -> 77 [label=\"0.0002\"];\n81 -> 80 [label=\"0.00025\"];\n81 -> 105 [label=\"2:repairLeft\"];\n82 [label=\"82\"];\n82 -> 78 [label=\"0.0002\"];\n82 -> 80 [label=\"0.00025\"];\n82 -> 106 [label=\"2:repairLeft\"];\n83 [label=\"83\"];\n83 -> 79 [label=\"0.0002\"];\n83 -> 81 [label=\"0.00025\"];\n83 -> 82 [label=\"0.00025\"];\n83 -> 107 [label=\"2:repairLeft\"];\n84 [label=\"84\"];\n84 -> 76 [label=\"0.002\"];\n84 -> 128 [label=\"2:repairLeft\"];\n85 [label=\"85\"];\n85 -> 77 [label=\"0.002\"];\n85 -> 84 [label=\"0.00025\"];\n85 -> 129 [label=\"2:repairLeft\"];\n86 [label=\"86\"];\n86 -> 78 [label=\"0.002\"];\n86 -> 84 [label=\"0.00025\"];\n86 -> 130 [label=\"2:repairLeft\"];\n87 [label=\"87\"];\n87 -> 79 [label=\"0.002\"];\n87 -> 85 [label=\"0.00025\"];\n87 -> 86 [label=\"0.00025\"];\n87 -> 131 [label=\"2:repairLeft\"];\n88 [label=\"88\"];\n88 -> 80 [label=\"0.002\"];\n88 -> 84 [label=\"0.0002\"];\n88 -> 132 [label=\"2:repairLeft\"];\n89 [label=\"89\"];\n89 -> 81 [label=\"0.002\"];\n89 -> 85 [label=\"0.0002\"];\n89 -> 88 [label=\"0.00025\"];\n89 -> 133 [label=\"2:repairLeft\"];\n90 [label=\"90\"];\n90 -> 82 [label=\"0.002\"];\n90 -> 86 [label=\"0.0002\"];\n90 -> 88 [label=\"0.00025\"];\n90 -> 134 [label=\"2:repairLeft\"];\n91 [label=\"91\"];\n91 -> 83 [label=\"0.002\"];\n91 -> 87 [label=\"0.0002\"];\n91 -> 89 [label=\"0.00025\"];\n91 -> 90 [label=\"0.00025\"];\n91 -> 135 [label=\"2:repairLeft\"];\n92 [label=\"92\"];\n92 -> 84 [label=\"0.004\"];\n92 -> 156 [label=\"2:repairLeft\"];\n93 [label=\"93\"];\n93 -> 85 [label=\"0.004\"];\n93 -> 92 [label=\"0.00025\"];\n93 -> 157 [label=\"2:repairLeft\"];\n94 [label=\"94\"];\n94 -> 86 [label=\"0.004\"];\n94 -> 92 [label=\"0.00025\"];\n94 -> 158 [label=\"2:repairLeft\"];\n95 [label=\"95\"];\n95 -> 87 [label=\"0.004\"];\n95 -> 93 [label=\"0.00025\"];\n95 -> 94 [label=\"0.00025\"];\n95 -> 159 [label=\"2:repairLeft\"];\n96 [label=\"96\"];\n96 -> 88 [label=\"0.004\"];\n96 -> 92 [label=\"0.0002\"];\n96 -> 160 [label=\"2:repairLeft\"];\n97 [label=\"97\"];\n97 -> 89 [label=\"0.004\"];\n97 -> 93 [label=\"0.0002\"];\n97 -> 96 [label=\"0.00025\"];\n97 -> 161 [label=\"2:repairLeft\"];\n98 [label=\"98\"];\n98 -> 90 [label=\"0.004\"];\n98 -> 94 [label=\"0.0002\"];\n98 -> 96 [label=\"0.00025\"];\n98 -> 162 [label=\"2:repairLeft\"];\n99 [label=\"99\"];\n99 -> 91 [label=\"0.004\"];\n99 -> 95 [label=\"0.0002\"];\n99 -> 97 [label=\"0.00025\"];\n99 -> 98 [label=\"0.00025\"];\n99 -> 163 [label=\"2:repairLeft\"];\n100 [label=\"100\"];\n100 -> 0 [label=\"0.002\"];\n100 -> 108 [label=\"10:startToRight\"];\n100 -> 110 [label=\"10:startToLeft\"];\n100 -> 116 [label=\"10:startLine\"];\n100 -> 120 [label=\"10:startRight\"];\n100 -> 176 [label=\"10:startLeft\"];\n101 [label=\"101\"];\n101 -> 1 [label=\"0.002\"];\n101 -> 100 [label=\"0.00025\"];\n101 -> 111 [label=\"10:startToLeft\"];\n101 -> 117 [label=\"10:startLine\"];\n101 -> 121 [label=\"10:startRight\"];\n101 -> 177 [label=\"10:startLeft\"];\n102 [label=\"102\"];\n102 -> 2 [label=\"0.002\"];\n102 -> 100 [label=\"0.00025\"];\n102 -> 109 [label=\"10:startToRight\"];\n102 -> 118 [label=\"10:startLine\"];\n102 -> 122 [label=\"10:startRight\"];\n102 -> 178 [label=\"10:startLeft\"];\n103 [label=\"103\"];\n103 -> 3 [label=\"0.002\"];\n103 -> 101 [label=\"0.00025\"];\n103 -> 102 [label=\"0.00025\"];\n103 -> 119 [label=\"10:startLine\"];\n103 -> 123 [label=\"10:startRight\"];\n103 -> 179 [label=\"10:startLeft\"];\n104 [label=\"104\"];\n104 -> 4 [label=\"0.002\"];\n104 -> 100 [label=\"0.0002\"];\n104 -> 112 [label=\"10:startToRight\"];\n104 -> 114 [label=\"10:startToLeft\"];\n104 -> 124 [label=\"10:startRight\"];\n104 -> 180 [label=\"10:startLeft\"];\n105 [label=\"105\"];\n105 -> 5 [label=\"0.002\"];\n105 -> 101 [label=\"0.0002\"];\n105 -> 104 [label=\"0.00025\"];\n105 -> 115 [label=\"10:startToLeft\"];\n105 -> 125 [label=\"10:startRight\"];\n105 -> 181 [label=\"10:startLeft\"];\n106 [label=\"106\"];\n106 -> 6 [label=\"0.002\"];\n106 -> 102 [label=\"0.0002\"];\n106 -> 104 [label=\"0.00025\"];\n106 -> 113 [label=\"10:startToRight\"];\n106 -> 126 [label=\"10:startRight\"];\n106 -> 182 [label=\"10:startLeft\"];\n107 [label=\"107\"];\n107 -> 7 [label=\"0.002\"];\n107 -> 103 [label=\"0.0002\"];\n107 -> 105 [label=\"0.00025\"];\n107 -> 106 [label=\"0.00025\"];\n107 -> 127 [label=\"10:startRight\"];\n107 -> 183 [label=\"10:startLeft\"];\n108 [label=\"108\"];\n108 -> 8 [label=\"0.002\"];\n108 -> 101 [label=\"0.25:repairToRight\"];\n109 [label=\"109\"];\n109 -> 9 [label=\"0.002\"];\n109 -> 103 [label=\"0.25:repairToRight\"];\n109 -> 108 [label=\"0.00025\"];\n110 [label=\"110\"];\n110 -> 10 [label=\"0.002\"];\n110 -> 102 [label=\"0.25:repairToLeft\"];\n111 [label=\"111\"];\n111 -> 11 [label=\"0.002\"];\n111 -> 103 [label=\"0.25:repairToLeft\"];\n111 -> 110 [label=\"0.00025\"];\n112 [label=\"112\"];\n112 -> 12 [label=\"0.002\"];\n112 -> 105 [label=\"0.25:repairToRight\"];\n112 -> 108 [label=\"0.0002\"];\n113 [label=\"113\"];\n113 -> 13 [label=\"0.002\"];\n113 -> 107 [label=\"0.25:repairToRight\"];\n113 -> 109 [label=\"0.0002\"];\n113 -> 112 [label=\"0.00025\"];\n114 [label=\"114\"];\n114 -> 14 [label=\"0.002\"];\n114 -> 106 [label=\"0.25:repairToLeft\"];\n114 -> 110 [label=\"0.0002\"];\n115 [label=\"115\"];\n115 -> 15 [label=\"0.002\"];\n115 -> 107 [label=\"0.25:repairToLeft\"];\n115 -> 111 [label=\"0.0002\"];\n115 -> 114 [label=\"0.00025\"];\n116 [label=\"116\"];\n116 -> 16 [label=\"0.002\"];\n116 -> 104 [label=\"0.125:repairLine\"];\n117 [label=\"117\"];\n117 -> 17 [label=\"0.002\"];\n117 -> 105 [label=\"0.125:repairLine\"];\n117 -> 116 [label=\"0.00025\"];\n118 [label=\"118\"];\n118 -> 18 [label=\"0.002\"];\n118 -> 106 [label=\"0.125:repairLine\"];\n118 -> 116 [label=\"0.00025\"];\n119 [label=\"119\"];\n119 -> 19 [label=\"0.002\"];\n119 -> 107 [label=\"0.125:repairLine\"];\n119 -> 117 [label=\"0.00025\"];\n119 -> 118 [label=\"0.00025\"];\n120 [label=\"120\"];\n120 -> 20 [label=\"0.002\"];\n120 -> 128 [label=\"2:repairRight\"];\n121 [label=\"121\"];\n121 -> 21 [label=\"0.002\"];\n121 -> 120 [label=\"0.00025\"];\n121 -> 129 [label=\"2:repairRight\"];\n122 [label=\"122\"];\n122 -> 22 [label=\"0.002\"];\n122 -> 120 [label=\"0.00025\"];\n122 -> 130 [label=\"2:repairRight\"];\n123 [label=\"123\"];\n123 -> 23 [label=\"0.002\"];\n123 -> 121 [label=\"0.00025\"];\n123 -> 122 [label=\"0.00025\"];\n123 -> 131 [label=\"2:repairRight\"];\n124 [label=\"124\"];\n124 -> 24 [label=\"0.002\"];\n124 -> 120 [label=\"0.0002\"];\n124 -> 132 [label=\"2:repairRight\"];\n125 [label=\"125\"];\n125 -> 25 [label=\"0.002\"];\n125 -> 121 [label=\"0.0002\"];\n125 -> 124 [label=\"0.00025\"];\n125 -> 133 [label=\"2:repairRight\"];\n126 [label=\"126\"];\n126 -> 26 [label=\"0.002\"];\n126 -> 122 [label=\"0.0002\"];\n126 -> 124 [label=\"0.00025\"];\n126 -> 134 [label=\"2:repairRight\"];\n127 [label=\"127\"];\n127 -> 27 [label=\"0.002\"];\n127 -> 123 [label=\"0.0002\"];\n127 -> 125 [label=\"0.00025\"];\n127 -> 126 [label=\"0.00025\"];\n127 -> 135 [label=\"2:repairRight\"];\n128 [label=\"128\"];\n128 -> 28 [label=\"0.002\"];\n128 -> 100 [label=\"0.002\"];\n128 -> 136 [label=\"10:startToRight\"];\n128 -> 138 [label=\"10:startToLeft\"];\n128 -> 144 [label=\"10:startLine\"];\n128 -> 148 [label=\"10:startRight\"];\n128 -> 184 [label=\"10:startLeft\"];\n129 [label=\"129\"];\n129 -> 29 [label=\"0.002\"];\n129 -> 101 [label=\"0.002\"];\n129 -> 128 [label=\"0.00025\"];\n129 -> 139 [label=\"10:startToLeft\"];\n129 -> 145 [label=\"10:startLine\"];\n129 -> 149 [label=\"10:startRight\"];\n129 -> 185 [label=\"10:startLeft\"];\n130 [label=\"130\"];\n130 -> 30 [label=\"0.002\"];\n130 -> 102 [label=\"0.002\"];\n130 -> 128 [label=\"0.00025\"];\n130 -> 137 [label=\"10:startToRight\"];\n130 -> 146 [label=\"10:startLine\"];\n130 -> 150 [label=\"10:startRight\"];\n130 -> 186 [label=\"10:startLeft\"];\n131 [label=\"131\"];\n131 -> 31 [label=\"0.002\"];\n131 -> 103 [label=\"0.002\"];\n131 -> 129 [label=\"0.00025\"];\n131 -> 130 [label=\"0.00025\"];\n131 -> 147 [label=\"10:startLine\"];\n131 -> 151 [label=\"10:startRight\"];\n131 -> 187 [label=\"10:startLeft\"];\n132 [label=\"132\"];\n132 -> 32 [label=\"0.002\"];\n132 -> 104 [label=\"0.002\"];\n132 -> 128 [label=\"0.0002\"];\n132 -> 140 [label=\"10:startToRight\"];\n132 -> 142 [label=\"10:startToLeft\"];\n132 -> 152 [label=\"10:startRight\"];\n132 -> 188 [label=\"10:startLeft\"];\n133 [label=\"133\"];\n133 -> 33 [label=\"0.002\"];\n133 -> 105 [label=\"0.002\"];\n133 -> 129 [label=\"0.0002\"];\n133 -> 132 [label=\"0.00025\"];\n133 -> 143 [label=\"10:startToLeft\"];\n133 -> 153 [label=\"10:startRight\"];\n133 -> 189 [label=\"10:startLeft\"];\n134 [label=\"134\"];\n134 -> 34 [label=\"0.002\"];\n134 -> 106 [label=\"0.002\"];\n134 -> 130 [label=\"0.0002\"];\n134 -> 132 [label=\"0.00025\"];\n134 -> 141 [label=\"10:startToRight\"];\n134 -> 154 [label=\"10:startRight\"];\n134 -> 190 [label=\"10:startLeft\"];\n135 [label=\"135\"];\n135 -> 35 [label=\"0.002\"];\n135 -> 107 [label=\"0.002\"];\n135 -> 131 [label=\"0.0002\"];\n135 -> 133 [label=\"0.00025\"];\n135 -> 134 [label=\"0.00025\"];\n135 -> 155 [label=\"10:startRight\"];\n135 -> 191 [label=\"10:startLeft\"];\n136 [label=\"136\"];\n136 -> 36 [label=\"0.002\"];\n136 -> 108 [label=\"0.002\"];\n136 -> 129 [label=\"0.25:repairToRight\"];\n137 [label=\"137\"];\n137 -> 37 [label=\"0.002\"];\n137 -> 109 [label=\"0.002\"];\n137 -> 131 [label=\"0.25:repairToRight\"];\n137 -> 136 [label=\"0.00025\"];\n138 [label=\"138\"];\n138 -> 38 [label=\"0.002\"];\n138 -> 110 [label=\"0.002\"];\n138 -> 130 [label=\"0.25:repairToLeft\"];\n139 [label=\"139\"];\n139 -> 39 [label=\"0.002\"];\n139 -> 111 [label=\"0.002\"];\n139 -> 131 [label=\"0.25:repairToLeft\"];\n139 -> 138 [label=\"0.00025\"];\n140 [label=\"140\"];\n140 -> 40 [label=\"0.002\"];\n140 -> 112 [label=\"0.002\"];\n140 -> 133 [label=\"0.25:repairToRight\"];\n140 -> 136 [label=\"0.0002\"];\n141 [label=\"141\"];\n141 -> 41 [label=\"0.002\"];\n141 -> 113 [label=\"0.002\"];\n141 -> 135 [label=\"0.25:repairToRight\"];\n141 -> 137 [label=\"0.0002\"];\n141 -> 140 [label=\"0.00025\"];\n142 [label=\"142\"];\n142 -> 42 [label=\"0.002\"];\n142 -> 114 [label=\"0.002\"];\n142 -> 134 [label=\"0.25:repairToLeft\"];\n142 -> 138 [label=\"0.0002\"];\n143 [label=\"143\"];\n143 -> 43 [label=\"0.002\"];\n143 -> 115 [label=\"0.002\"];\n143 -> 135 [label=\"0.25:repairToLeft\"];\n143 -> 139 [label=\"0.0002\"];\n143 -> 142 [label=\"0.00025\"];\n144 [label=\"144\"];\n144 -> 44 [label=\"0.002\"];\n144 -> 116 [label=\"0.002\"];\n144 -> 132 [label=\"0.125:repairLine\"];\n145 [label=\"145\"];\n145 -> 45 [label=\"0.002\"];\n145 -> 117 [label=\"0.002\"];\n145 -> 133 [label=\"0.125:repairLine\"];\n145 -> 144 [label=\"0.00025\"];\n146 [label=\"146\"];\n146 -> 46 [label=\"0.002\"];\n146 -> 118 [label=\"0.002\"];\n146 -> 134 [label=\"0.125:repairLine\"];\n146 -> 144 [label=\"0.00025\"];\n147 [label=\"147\"];\n147 -> 47 [label=\"0.002\"];\n147 -> 119 [label=\"0.002\"];\n147 -> 135 [label=\"0.125:repairLine\"];\n147 -> 145 [label=\"0.00025\"];\n147 -> 146 [label=\"0.00025\"];\n148 [label=\"148\"];\n148 -> 48 [label=\"0.002\"];\n148 -> 120 [label=\"0.002\"];\n148 -> 156 [label=\"2:repairRight\"];\n149 [label=\"149\"];\n149 -> 49 [label=\"0.002\"];\n149 -> 121 [label=\"0.002\"];\n149 -> 148 [label=\"0.00025\"];\n149 -> 157 [label=\"2:repairRight\"];\n150 [label=\"150\"];\n150 -> 50 [label=\"0.002\"];\n150 -> 122 [label=\"0.002\"];\n150 -> 148 [label=\"0.00025\"];\n150 -> 158 [label=\"2:repairRight\"];\n151 [label=\"151\"];\n151 -> 51 [label=\"0.002\"];\n151 -> 123 [label=\"0.002\"];\n151 -> 149 [label=\"0.00025\"];\n151 -> 150 [label=\"0.00025\"];\n151 -> 159 [label=\"2:repairRight\"];\n152 [label=\"152\"];\n152 -> 52 [label=\"0.002\"];\n152 -> 124 [label=\"0.002\"];\n152 -> 148 [label=\"0.0002\"];\n152 -> 160 [label=\"2:repairRight\"];\n153 [label=\"153\"];\n153 -> 53 [label=\"0.002\"];\n153 -> 125 [label=\"0.002\"];\n153 -> 149 [label=\"0.0002\"];\n153 -> 152 [label=\"0.00025\"];\n153 -> 161 [label=\"2:repairRight\"];\n154 [label=\"154\"];\n154 -> 54 [label=\"0.002\"];\n154 -> 126 [label=\"0.002\"];\n154 -> 150 [label=\"0.0002\"];\n154 -> 152 [label=\"0.00025\"];\n154 -> 162 [label=\"2:repairRight\"];\n155 [label=\"155\"];\n155 -> 55 [label=\"0.002\"];\n155 -> 127 [label=\"0.002\"];\n155 -> 151 [label=\"0.0002\"];\n155 -> 153 [label=\"0.00025\"];\n155 -> 154 [label=\"0.00025\"];\n155 -> 163 [label=\"2:repairRight\"];\n156 [label=\"156\"];\n156 -> 56 [label=\"0.002\"];\n156 -> 128 [label=\"0.004\"];\n156 -> 164 [label=\"10:startToRight\"];\n156 -> 166 [label=\"10:startToLeft\"];\n156 -> 172 [label=\"10:startLine\"];\n156 -> 192 [label=\"10:startLeft\"];\n157 [label=\"157\"];\n157 -> 57 [label=\"0.002\"];\n157 -> 129 [label=\"0.004\"];\n157 -> 156 [label=\"0.00025\"];\n157 -> 167 [label=\"10:startToLeft\"];\n157 -> 173 [label=\"10:startLine\"];\n157 -> 193 [label=\"10:startLeft\"];\n158 [label=\"158\"];\n158 -> 58 [label=\"0.002\"];\n158 -> 130 [label=\"0.004\"];\n158 -> 156 [label=\"0.00025\"];\n158 -> 165 [label=\"10:startToRight\"];\n158 -> 174 [label=\"10:startLine\"];\n158 -> 194 [label=\"10:startLeft\"];\n159 [label=\"159\"];\n159 -> 59 [label=\"0.002\"];\n159 -> 131 [label=\"0.004\"];\n159 -> 157 [label=\"0.00025\"];\n159 -> 158 [label=\"0.00025\"];\n159 -> 175 [label=\"10:startLine\"];\n159 -> 195 [label=\"10:startLeft\"];\n160 [label=\"160\"];\n160 -> 60 [label=\"0.002\"];\n160 -> 132 [label=\"0.004\"];\n160 -> 156 [label=\"0.0002\"];\n160 -> 168 [label=\"10:startToRight\"];\n160 -> 170 [label=\"10:startToLeft\"];\n160 -> 196 [label=\"10:startLeft\"];\n161 [label=\"161\"];\n161 -> 61 [label=\"0.002\"];\n161 -> 133 [label=\"0.004\"];\n161 -> 157 [label=\"0.0002\"];\n161 -> 160 [label=\"0.00025\"];\n161 -> 171 [label=\"10:startToLeft\"];\n161 -> 197 [label=\"10:startLeft\"];\n162 [label=\"162\"];\n162 -> 62 [label=\"0.002\"];\n162 -> 134 [label=\"0.004\"];\n162 -> 158 [label=\"0.0002\"];\n162 -> 160 [label=\"0.00025\"];\n162 -> 169 [label=\"10:startToRight\"];\n162 -> 198 [label=\"10:startLeft\"];\n163 [label=\"163\"];\n163 -> 63 [label=\"0.002\"];\n163 -> 135 [label=\"0.004\"];\n163 -> 159 [label=\"0.0002\"];\n163 -> 161 [label=\"0.00025\"];\n163 -> 162 [label=\"0.00025\"];\n163 -> 199 [label=\"10:startLeft\"];\n164 [label=\"164\"];\n164 -> 64 [label=\"0.002\"];\n164 -> 136 [label=\"0.004\"];\n164 -> 157 [label=\"0.25:repairToRight\"];\n165 [label=\"165\"];\n165 -> 65 [label=\"0.002\"];\n165 -> 137 [label=\"0.004\"];\n165 -> 159 [label=\"0.25:repairToRight\"];\n165 -> 164 [label=\"0.00025\"];\n166 [label=\"166\"];\n166 -> 66 [label=\"0.002\"];\n166 -> 138 [label=\"0.004\"];\n166 -> 158 [label=\"0.25:repairToLeft\"];\n167 [label=\"167\"];\n167 -> 67 [label=\"0.002\"];\n167 -> 139 [label=\"0.004\"];\n167 -> 159 [label=\"0.25:repairToLeft\"];\n167 -> 166 [label=\"0.00025\"];\n168 [label=\"168\"];\n168 -> 68 [label=\"0.002\"];\n168 -> 140 [label=\"0.004\"];\n168 -> 161 [label=\"0.25:repairToRight\"];\n168 -> 164 [label=\"0.0002\"];\n169 [label=\"169\"];\n169 -> 69 [label=\"0.002\"];\n169 -> 141 [label=\"0.004\"];\n169 -> 163 [label=\"0.25:repairToRight\"];\n169 -> 165 [label=\"0.0002\"];\n169 -> 168 [label=\"0.00025\"];\n170 [label=\"170\"];\n170 -> 70 [label=\"0.002\"];\n170 -> 142 [label=\"0.004\"];\n170 -> 162 [label=\"0.25:repairToLeft\"];\n170 -> 166 [label=\"0.0002\"];\n171 [label=\"171\"];\n171 -> 71 [label=\"0.002\"];\n171 -> 143 [label=\"0.004\"];\n171 -> 163 [label=\"0.25:repairToLeft\"];\n171 -> 167 [label=\"0.0002\"];\n171 -> 170 [label=\"0.00025\"];\n172 [label=\"172\"];\n172 -> 72 [label=\"0.002\"];\n172 -> 144 [label=\"0.004\"];\n172 -> 160 [label=\"0.125:repairLine\"];\n173 [label=\"173\"];\n173 -> 73 [label=\"0.002\"];\n173 -> 145 [label=\"0.004\"];\n173 -> 161 [label=\"0.125:repairLine\"];\n173 -> 172 [label=\"0.00025\"];\n174 [label=\"174\"];\n174 -> 74 [label=\"0.002\"];\n174 -> 146 [label=\"0.004\"];\n174 -> 162 [label=\"0.125:repairLine\"];\n174 -> 172 [label=\"0.00025\"];\n175 [label=\"175\"];\n175 -> 75 [label=\"0.002\"];\n175 -> 147 [label=\"0.004\"];\n175 -> 163 [label=\"0.125:repairLine\"];\n175 -> 173 [label=\"0.00025\"];\n175 -> 174 [label=\"0.00025\"];\n176 [label=\"176\"];\n176 -> 76 [label=\"0.002\"];\n176 -> 200 [label=\"2:repairLeft\"];\n177 [label=\"177\"];\n177 -> 77 [label=\"0.002\"];\n177 -> 176 [label=\"0.00025\"];\n177 -> 201 [label=\"2:repairLeft\"];\n178 [label=\"178\"];\n178 -> 78 [label=\"0.002\"];\n178 -> 176 [label=\"0.00025\"];\n178 -> 202 [label=\"2:repairLeft\"];\n179 [label=\"179\"];\n179 -> 79 [label=\"0.002\"];\n179 -> 177 [label=\"0.00025\"];\n179 -> 178 [label=\"0.00025\"];\n179 -> 203 [label=\"2:repairLeft\"];\n180 [label=\"180\"];\n180 -> 80 [label=\"0.002\"];\n180 -> 176 [label=\"0.0002\"];\n180 -> 204 [label=\"2:repairLeft\"];\n181 [label=\"181\"];\n181 -> 81 [label=\"0.002\"];\n181 -> 177 [label=\"0.0002\"];\n181 -> 180 [label=\"0.00025\"];\n181 -> 205 [label=\"2:repairLeft\"];\n182 [label=\"182\"];\n182 -> 82 [label=\"0.002\"];\n182 -> 178 [label=\"0.0002\"];\n182 -> 180 [label=\"0.00025\"];\n182 -> 206 [label=\"2:repairLeft\"];\n183 [label=\"183\"];\n183 -> 83 [label=\"0.002\"];\n183 -> 179 [label=\"0.0002\"];\n183 -> 181 [label=\"0.00025\"];\n183 -> 182 [label=\"0.00025\"];\n183 -> 207 [label=\"2:repairLeft\"];\n184 [label=\"184\"];\n184 -> 84 [label=\"0.002\"];\n184 -> 176 [label=\"0.002\"];\n184 -> 228 [label=\"2:repairLeft\"];\n185 [label=\"185\"];\n185 -> 85 [label=\"0.002\"];\n185 -> 177 [label=\"0.002\"];\n185 -> 184 [label=\"0.00025\"];\n185 -> 229 [label=\"2:repairLeft\"];\n186 [label=\"186\"];\n186 -> 86 [label=\"0.002\"];\n186 -> 178 [label=\"0.002\"];\n186 -> 184 [label=\"0.00025\"];\n186 -> 230 [label=\"2:repairLeft\"];\n187 [label=\"187\"];\n187 -> 87 [label=\"0.002\"];\n187 -> 179 [label=\"0.002\"];\n187 -> 185 [label=\"0.00025\"];\n187 -> 186 [label=\"0.00025\"];\n187 -> 231 [label=\"2:repairLeft\"];\n188 [label=\"188\"];\n188 -> 88 [label=\"0.002\"];\n188 -> 180 [label=\"0.002\"];\n188 -> 184 [label=\"0.0002\"];\n188 -> 232 [label=\"2:repairLeft\"];\n189 [label=\"189\"];\n189 -> 89 [label=\"0.002\"];\n189 -> 181 [label=\"0.002\"];\n189 -> 185 [label=\"0.0002\"];\n189 -> 188 [label=\"0.00025\"];\n189 -> 233 [label=\"2:repairLeft\"];\n190 [label=\"190\"];\n190 -> 90 [label=\"0.002\"];\n190 -> 182 [label=\"0.002\"];\n190 -> 186 [label=\"0.0002\"];\n190 -> 188 [label=\"0.00025\"];\n190 -> 234 [label=\"2:repairLeft\"];\n191 [label=\"191\"];\n191 -> 91 [label=\"0.002\"];\n191 -> 183 [label=\"0.002\"];\n191 -> 187 [label=\"0.0002\"];\n191 -> 189 [label=\"0.00025\"];\n191 -> 190 [label=\"0.00025\"];\n191 -> 235 [label=\"2:repairLeft\"];\n192 [label=\"192\"];\n192 -> 92 [label=\"0.002\"];\n192 -> 184 [label=\"0.004\"];\n192 -> 256 [label=\"2:repairLeft\"];\n193 [label=\"193\"];\n193 -> 93 [label=\"0.002\"];\n193 -> 185 [label=\"0.004\"];\n193 -> 192 [label=\"0.00025\"];\n193 -> 257 [label=\"2:repairLeft\"];\n194 [label=\"194\"];\n194 -> 94 [label=\"0.002\"];\n194 -> 186 [label=\"0.004\"];\n194 -> 192 [label=\"0.00025\"];\n194 -> 258 [label=\"2:repairLeft\"];\n195 [label=\"195\"];\n195 -> 95 [label=\"0.002\"];\n195 -> 187 [label=\"0.004\"];\n195 -> 193 [label=\"0.00025\"];\n195 -> 194 [label=\"0.00025\"];\n195 -> 259 [label=\"2:repairLeft\"];\n196 [label=\"196\"];\n196 -> 96 [label=\"0.002\"];\n196 -> 188 [label=\"0.004\"];\n196 -> 192 [label=\"0.0002\"];\n196 -> 260 [label=\"2:repairLeft\"];\n197 [label=\"197\"];\n197 -> 97 [label=\"0.002\"];\n197 -> 189 [label=\"0.004\"];\n197 -> 193 [label=\"0.0002\"];\n197 -> 196 [label=\"0.00025\"];\n197 -> 261 [label=\"2:repairLeft\"];\n198 [label=\"198\"];\n198 -> 98 [label=\"0.002\"];\n198 -> 190 [label=\"0.004\"];\n198 -> 194 [label=\"0.0002\"];\n198 -> 196 [label=\"0.00025\"];\n198 -> 262 [label=\"2:repairLeft\"];\n199 [label=\"199\"];\n199 -> 99 [label=\"0.002\"];\n199 -> 191 [label=\"0.004\"];\n199 -> 195 [label=\"0.0002\"];\n199 -> 197 [label=\"0.00025\"];\n199 -> 198 [label=\"0.00025\"];\n199 -> 263 [label=\"2:repairLeft\"];\n200 [label=\"200\"];\n200 -> 100 [label=\"0.004\"];\n200 -> 208 [label=\"10:startToRight\"];\n200 -> 210 [label=\"10:startToLeft\"];\n200 -> 216 [label=\"10:startLine\"];\n200 -> 220 [label=\"10:startRight\"];\n201 [label=\"201\"];\n201 -> 101 [label=\"0.004\"];\n201 -> 200 [label=\"0.00025\"];\n201 -> 211 [label=\"10:startToLeft\"];\n201 -> 217 [label=\"10:startLine\"];\n201 -> 221 [label=\"10:startRight\"];\n202 [label=\"202\"];\n202 -> 102 [label=\"0.004\"];\n202 -> 200 [label=\"0.00025\"];\n202 -> 209 [label=\"10:startToRight\"];\n202 -> 218 [label=\"10:startLine\"];\n202 -> 222 [label=\"10:startRight\"];\n203 [label=\"203\"];\n203 -> 103 [label=\"0.004\"];\n203 -> 201 [label=\"0.00025\"];\n203 -> 202 [label=\"0.00025\"];\n203 -> 219 [label=\"10:startLine\"];\n203 -> 223 [label=\"10:startRight\"];\n204 [label=\"204\"];\n204 -> 104 [label=\"0.004\"];\n204 -> 200 [label=\"0.0002\"];\n204 -> 212 [label=\"10:startToRight\"];\n204 -> 214 [label=\"10:startToLeft\"];\n204 -> 224 [label=\"10:startRight\"];\n205 [label=\"205\"];\n205 -> 105 [label=\"0.004\"];\n205 -> 201 [label=\"0.0002\"];\n205 -> 204 [label=\"0.00025\"];\n205 -> 215 [label=\"10:startToLeft\"];\n205 -> 225 [label=\"10:startRight\"];\n206 [label=\"206\"];\n206 -> 106 [label=\"0.004\"];\n206 -> 202 [label=\"0.0002\"];\n206 -> 204 [label=\"0.00025\"];\n206 -> 213 [label=\"10:startToRight\"];\n206 -> 226 [label=\"10:startRight\"];\n207 [label=\"207\"];\n207 -> 107 [label=\"0.004\"];\n207 -> 203 [label=\"0.0002\"];\n207 -> 205 [label=\"0.00025\"];\n207 -> 206 [label=\"0.00025\"];\n207 -> 227 [label=\"10:startRight\"];\n208 [label=\"208\"];\n208 -> 108 [label=\"0.004\"];\n208 -> 201 [label=\"0.25:repairToRight\"];\n209 [label=\"209\"];\n209 -> 109 [label=\"0.004\"];\n209 -> 203 [label=\"0.25:repairToRight\"];\n209 -> 208 [label=\"0.00025\"];\n210 [label=\"210\"];\n210 -> 110 [label=\"0.004\"];\n210 -> 202 [label=\"0.25:repairToLeft\"];\n211 [label=\"211\"];\n211 -> 111 [label=\"0.004\"];\n211 -> 203 [label=\"0.25:repairToLeft\"];\n211 -> 210 [label=\"0.00025\"];\n212 [label=\"212\"];\n212 -> 112 [label=\"0.004\"];\n212 -> 205 [label=\"0.25:repairToRight\"];\n212 -> 208 [label=\"0.0002\"];\n213 [label=\"213\"];\n213 -> 113 [label=\"0.004\"];\n213 -> 207 [label=\"0.25:repairToRight\"];\n213 -> 209 [label=\"0.0002\"];\n213 -> 212 [label=\"0.00025\"];\n214 [label=\"214\"];\n214 -> 114 [label=\"0.004\"];\n214 -> 206 [label=\"0.25:repairToLeft\"];\n214 -> 210 [label=\"0.0002\"];\n215 [label=\"215\"];\n215 -> 115 [label=\"0.004\"];\n215 -> 207 [label=\"0.25:repairToLeft\"];\n215 -> 211 [label=\"0.0002\"];\n215 -> 214 [label=\"0.00025\"];\n216 [label=\"216\"];\n216 -> 116 [label=\"0.004\"];\n216 -> 204 [label=\"0.125:repairLine\"];\n217 [label=\"217\"];\n217 -> 117 [label=\"0.004\"];\n217 -> 205 [label=\"0.125:repairLine\"];\n217 -> 216 [label=\"0.00025\"];\n218 [label=\"218\"];\n218 -> 118 [label=\"0.004\"];\n218 -> 206 [label=\"0.125:repairLine\"];\n218 -> 216 [label=\"0.00025\"];\n219 [label=\"219\"];\n219 -> 119 [label=\"0.004\"];\n219 -> 207 [label=\"0.125:repairLine\"];\n219 -> 217 [label=\"0.00025\"];\n219 -> 218 [label=\"0.00025\"];\n220 [label=\"220\"];\n220 -> 120 [label=\"0.004\"];\n220 -> 228 [label=\"2:repairRight\"];\n221 [label=\"221\"];\n221 -> 121 [label=\"0.004\"];\n221 -> 220 [label=\"0.00025\"];\n221 -> 229 [label=\"2:repairRight\"];\n222 [label=\"222\"];\n222 -> 122 [label=\"0.004\"];\n222 -> 220 [label=\"0.00025\"];\n222 -> 230 [label=\"2:repairRight\"];\n223 [label=\"223\"];\n223 -> 123 [label=\"0.004\"];\n223 -> 221 [label=\"0.00025\"];\n223 -> 222 [label=\"0.00025\"];\n223 -> 231 [label=\"2:repairRight\"];\n224 [label=\"224\"];\n224 -> 124 [label=\"0.004\"];\n224 -> 220 [label=\"0.0002\"];\n224 -> 232 [label=\"2:repairRight\"];\n225 [label=\"225\"];\n225 -> 125 [label=\"0.004\"];\n225 -> 221 [label=\"0.0002\"];\n225 -> 224 [label=\"0.00025\"];\n225 -> 233 [label=\"2:repairRight\"];\n226 [label=\"226\"];\n226 -> 126 [label=\"0.004\"];\n226 -> 222 [label=\"0.0002\"];\n226 -> 224 [label=\"0.00025\"];\n226 -> 234 [label=\"2:repairRight\"];\n227 [label=\"227\"];\n227 -> 127 [label=\"0.004\"];\n227 -> 223 [label=\"0.0002\"];\n227 -> 225 [label=\"0.00025\"];\n227 -> 226 [label=\"0.00025\"];\n227 -> 235 [label=\"2:repairRight\"];\n228 [label=\"228\"];\n228 -> 128 [label=\"0.004\"];\n228 -> 200 [label=\"0.002\"];\n228 -> 236 [label=\"10:startToRight\"];\n228 -> 238 [label=\"10:startToLeft\"];\n228 -> 244 [label=\"10:startLine\"];\n228 -> 248 [label=\"10:startRight\"];\n229 [label=\"229\"];\n229 -> 129 [label=\"0.004\"];\n229 -> 201 [label=\"0.002\"];\n229 -> 228 [label=\"0.00025\"];\n229 -> 239 [label=\"10:startToLeft\"];\n229 -> 245 [label=\"10:startLine\"];\n229 -> 249 [label=\"10:startRight\"];\n230 [label=\"230\"];\n230 -> 130 [label=\"0.004\"];\n230 -> 202 [label=\"0.002\"];\n230 -> 228 [label=\"0.00025\"];\n230 -> 237 [label=\"10:startToRight\"];\n230 -> 246 [label=\"10:startLine\"];\n230 -> 250 [label=\"10:startRight\"];\n231 [label=\"231\"];\n231 -> 131 [label=\"0.004\"];\n231 -> 203 [label=\"0.002\"];\n231 -> 229 [label=\"0.00025\"];\n231 -> 230 [label=\"0.00025\"];\n231 -> 247 [label=\"10:startLine\"];\n231 -> 251 [label=\"10:startRight\"];\n232 [label=\"232\"];\n232 -> 132 [label=\"0.004\"];\n232 -> 204 [label=\"0.002\"];\n232 -> 228 [label=\"0.0002\"];\n232 -> 240 [label=\"10:startToRight\"];\n232 -> 242 [label=\"10:startToLeft\"];\n232 -> 252 [label=\"10:startRight\"];\n233 [label=\"233\"];\n233 -> 133 [label=\"0.004\"];\n233 -> 205 [label=\"0.002\"];\n233 -> 229 [label=\"0.0002\"];\n233 -> 232 [label=\"0.00025\"];\n233 -> 243 [label=\"10:startToLeft\"];\n233 -> 253 [label=\"10:startRight\"];\n234 [label=\"234\"];\n234 -> 134 [label=\"0.004\"];\n234 -> 206 [label=\"0.002\"];\n234 -> 230 [label=\"0.0002\"];\n234 -> 232 [label=\"0.00025\"];\n234 -> 241 [label=\"10:startToRight\"];\n234 -> 254 [label=\"10:startRight\"];\n235 [label=\"235\"];\n235 -> 135 [label=\"0.004\"];\n235 -> 207 [label=\"0.002\"];\n235 -> 231 [label=\"0.0002\"];\n235 -> 233 [label=\"0.00025\"];\n235 -> 234 [label=\"0.00025\"];\n235 -> 255 [label=\"10:startRight\"];\n236 [label=\"236\"];\n236 -> 136 [label=\"0.004\"];\n236 -> 208 [label=\"0.002\"];\n236 -> 229 [label=\"0.25:repairToRight\"];\n237 [label=\"237\"];\n237 -> 137 [label=\"0.004\"];\n237 -> 209 [label=\"0.002\"];\n237 -> 231 [label=\"0.25:repairToRight\"];\n237 -> 236 [label=\"0.00025\"];\n238 [label=\"238\"];\n238 -> 138 [label=\"0.004\"];\n238 -> 210 [label=\"0.002\"];\n238 -> 230 [label=\"0.25:repairToLeft\"];\n239 [label=\"239\"];\n239 -> 139 [label=\"0.004\"];\n239 -> 211 [label=\"0.002\"];\n239 -> 231 [label=\"0.25:repairToLeft\"];\n239 -> 238 [label=\"0.00025\"];\n240 [label=\"240\"];\n240 -> 140 [label=\"0.004\"];\n240 -> 212 [label=\"0.002\"];\n240 -> 233 [label=\"0.25:repairToRight\"];\n240 -> 236 [label=\"0.0002\"];\n241 [label=\"241\"];\n241 -> 141 [label=\"0.004\"];\n241 -> 213 [label=\"0.002\"];\n241 -> 235 [label=\"0.25:repairToRight\"];\n241 -> 237 [label=\"0.0002\"];\n241 -> 240 [label=\"0.00025\"];\n242 [label=\"242\"];\n242 -> 142 [label=\"0.004\"];\n242 -> 214 [label=\"0.002\"];\n242 -> 234 [label=\"0.25:repairToLeft\"];\n242 -> 238 [label=\"0.0002\"];\n243 [label=\"243\"];\n243 -> 143 [label=\"0.004\"];\n243 -> 215 [label=\"0.002\"];\n243 -> 235 [label=\"0.25:repairToLeft\"];\n243 -> 239 [label=\"0.0002\"];\n243 -> 242 [label=\"0.00025\"];\n244 [label=\"244\"];\n244 -> 144 [label=\"0.004\"];\n244 -> 216 [label=\"0.002\"];\n244 -> 232 [label=\"0.125:repairLine\"];\n245 [label=\"245\"];\n245 -> 145 [label=\"0.004\"];\n245 -> 217 [label=\"0.002\"];\n245 -> 233 [label=\"0.125:repairLine\"];\n245 -> 244 [label=\"0.00025\"];\n246 [label=\"246\"];\n246 -> 146 [label=\"0.004\"];\n246 -> 218 [label=\"0.002\"];\n246 -> 234 [label=\"0.125:repairLine\"];\n246 -> 244 [label=\"0.00025\"];\n247 [label=\"247\"];\n247 -> 147 [label=\"0.004\"];\n247 -> 219 [label=\"0.002\"];\n247 -> 235 [label=\"0.125:repairLine\"];\n247 -> 245 [label=\"0.00025\"];\n247 -> 246 [label=\"0.00025\"];\n248 [label=\"248\"];\n248 -> 148 [label=\"0.004\"];\n248 -> 220 [label=\"0.002\"];\n248 -> 256 [label=\"2:repairRight\"];\n249 [label=\"249\"];\n249 -> 149 [label=\"0.004\"];\n249 -> 221 [label=\"0.002\"];\n249 -> 248 [label=\"0.00025\"];\n249 -> 257 [label=\"2:repairRight\"];\n250 [label=\"250\"];\n250 -> 150 [label=\"0.004\"];\n250 -> 222 [label=\"0.002\"];\n250 -> 248 [label=\"0.00025\"];\n250 -> 258 [label=\"2:repairRight\"];\n251 [label=\"251\"];\n251 -> 151 [label=\"0.004\"];\n251 -> 223 [label=\"0.002\"];\n251 -> 249 [label=\"0.00025\"];\n251 -> 250 [label=\"0.00025\"];\n251 -> 259 [label=\"2:repairRight\"];\n252 [label=\"252\"];\n252 -> 152 [label=\"0.004\"];\n252 -> 224 [label=\"0.002\"];\n252 -> 248 [label=\"0.0002\"];\n252 -> 260 [label=\"2:repairRight\"];\n253 [label=\"253\"];\n253 -> 153 [label=\"0.004\"];\n253 -> 225 [label=\"0.002\"];\n253 -> 249 [label=\"0.0002\"];\n253 -> 252 [label=\"0.00025\"];\n253 -> 261 [label=\"2:repairRight\"];\n254 [label=\"254\"];\n254 -> 154 [label=\"0.004\"];\n254 -> 226 [label=\"0.002\"];\n254 -> 250 [label=\"0.0002\"];\n254 -> 252 [label=\"0.00025\"];\n254 -> 262 [label=\"2:repairRight\"];\n255 [label=\"255\"];\n255 -> 155 [label=\"0.004\"];\n255 -> 227 [label=\"0.002\"];\n255 -> 251 [label=\"0.0002\"];\n255 -> 253 [label=\"0.00025\"];\n255 -> 254 [label=\"0.00025\"];\n255 -> 263 [label=\"2:repairRight\"];\n256 [label=\"256\"];\n256 -> 156 [label=\"0.004\"];\n256 -> 228 [label=\"0.004\"];\n256 -> 264 [label=\"10:startToRight\"];\n256 -> 266 [label=\"10:startToLeft\"];\n256 -> 272 [label=\"10:startLine\"];\n257 [label=\"257\"];\n257 -> 157 [label=\"0.004\"];\n257 -> 229 [label=\"0.004\"];\n257 -> 256 [label=\"0.00025\"];\n257 -> 267 [label=\"10:startToLeft\"];\n257 -> 273 [label=\"10:startLine\"];\n258 [label=\"258\"];\n258 -> 158 [label=\"0.004\"];\n258 -> 230 [label=\"0.004\"];\n258 -> 256 [label=\"0.00025\"];\n258 -> 265 [label=\"10:startToRight\"];\n258 -> 274 [label=\"10:startLine\"];\n259 [label=\"259\"];\n259 -> 159 [label=\"0.004\"];\n259 -> 231 [label=\"0.004\"];\n259 -> 257 [label=\"0.00025\"];\n259 -> 258 [label=\"0.00025\"];\n259 -> 275 [label=\"10:startLine\"];\n260 [label=\"260\"];\n260 -> 160 [label=\"0.004\"];\n260 -> 232 [label=\"0.004\"];\n260 -> 256 [label=\"0.0002\"];\n260 -> 268 [label=\"10:startToRight\"];\n260 -> 270 [label=\"10:startToLeft\"];\n261 [label=\"261\"];\n261 -> 161 [label=\"0.004\"];\n261 -> 233 [label=\"0.004\"];\n261 -> 257 [label=\"0.0002\"];\n261 -> 260 [label=\"0.00025\"];\n261 -> 271 [label=\"10:startToLeft\"];\n262 [label=\"262\"];\n262 -> 162 [label=\"0.004\"];\n262 -> 234 [label=\"0.004\"];\n262 -> 258 [label=\"0.0002\"];\n262 -> 260 [label=\"0.00025\"];\n262 -> 269 [label=\"10:startToRight\"];\n263 [label=\"263\"];\n263 -> 163 [label=\"0.004\"];\n263 -> 235 [label=\"0.004\"];\n263 -> 259 [label=\"0.0002\"];\n263 -> 261 [label=\"0.00025\"];\n263 -> 262 [label=\"0.00025\"];\n264 [label=\"264\"];\n264 -> 164 [label=\"0.004\"];\n264 -> 236 [label=\"0.004\"];\n264 -> 257 [label=\"0.25:repairToRight\"];\n265 [label=\"265\"];\n265 -> 165 [label=\"0.004\"];\n265 -> 237 [label=\"0.004\"];\n265 -> 259 [label=\"0.25:repairToRight\"];\n265 -> 264 [label=\"0.00025\"];\n266 [label=\"266\"];\n266 -> 166 [label=\"0.004\"];\n266 -> 238 [label=\"0.004\"];\n266 -> 258 [label=\"0.25:repairToLeft\"];\n267 [label=\"267\"];\n267 -> 167 [label=\"0.004\"];\n267 -> 239 [label=\"0.004\"];\n267 -> 259 [label=\"0.25:repairToLeft\"];\n267 -> 266 [label=\"0.00025\"];\n268 [label=\"268\"];\n268 -> 168 [label=\"0.004\"];\n268 -> 240 [label=\"0.004\"];\n268 -> 261 [label=\"0.25:repairToRight\"];\n268 -> 264 [label=\"0.0002\"];\n269 [label=\"269\"];\n269 -> 169 [label=\"0.004\"];\n269 -> 241 [label=\"0.004\"];\n269 -> 263 [label=\"0.25:repairToRight\"];\n269 -> 265 [label=\"0.0002\"];\n269 -> 268 [label=\"0.00025\"];\n270 [label=\"270\"];\n270 -> 170 [label=\"0.004\"];\n270 -> 242 [label=\"0.004\"];\n270 -> 262 [label=\"0.25:repairToLeft\"];\n270 -> 266 [label=\"0.0002\"];\n271 [label=\"271\"];\n271 -> 171 [label=\"0.004\"];\n271 -> 243 [label=\"0.004\"];\n271 -> 263 [label=\"0.25:repairToLeft\"];\n271 -> 267 [label=\"0.0002\"];\n271 -> 270 [label=\"0.00025\"];\n272 [label=\"272\"];\n272 -> 172 [label=\"0.004\"];\n272 -> 244 [label=\"0.004\"];\n272 -> 260 [label=\"0.125:repairLine\"];\n273 [label=\"273\"];\n273 -> 173 [label=\"0.004\"];\n273 -> 245 [label=\"0.004\"];\n273 -> 261 [label=\"0.125:repairLine\"];\n273 -> 272 [label=\"0.00025\"];\n274 [label=\"274\"];\n274 -> 174 [label=\"0.004\"];\n274 -> 246 [label=\"0.004\"];\n274 -> 262 [label=\"0.125:repairLine\"];\n274 -> 272 [label=\"0.00025\"];\n275 [label=\"275\"];\n275 -> 175 [label=\"0.004\"];\n275 -> 247 [label=\"0.004\"];\n275 -> 263 [label=\"0.125:repairLine\"];\n275 -> 273 [label=\"0.00025\"];\n275 -> 274 [label=\"0.00025\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/cluster.sm.dot.auto",
    "content": "-exporttransdot cluster.sm.dot -ex\n-exporttransdotstates cluster.sm.sta.dot -ex\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/cluster.sm.sta.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\\n(0,false,0,false,false,false,false,false,false,false,false)\"];\n0 -> 8 [label=\"10:startToRight\"];\n0 -> 10 [label=\"10:startToLeft\"];\n0 -> 16 [label=\"10:startLine\"];\n0 -> 20 [label=\"10:startRight\"];\n0 -> 76 [label=\"10:startLeft\"];\n1 [label=\"1\\n(0,false,0,false,false,false,false,false,false,false,true)\"];\n1 -> 0 [label=\"0.00025\"];\n1 -> 11 [label=\"10:startToLeft\"];\n1 -> 17 [label=\"10:startLine\"];\n1 -> 21 [label=\"10:startRight\"];\n1 -> 77 [label=\"10:startLeft\"];\n2 [label=\"2\\n(0,false,0,false,false,false,false,false,true,false,false)\"];\n2 -> 0 [label=\"0.00025\"];\n2 -> 9 [label=\"10:startToRight\"];\n2 -> 18 [label=\"10:startLine\"];\n2 -> 22 [label=\"10:startRight\"];\n2 -> 78 [label=\"10:startLeft\"];\n3 [label=\"3\\n(0,false,0,false,false,false,false,false,true,false,true)\"];\n3 -> 1 [label=\"0.00025\"];\n3 -> 2 [label=\"0.00025\"];\n3 -> 19 [label=\"10:startLine\"];\n3 -> 23 [label=\"10:startRight\"];\n3 -> 79 [label=\"10:startLeft\"];\n4 [label=\"4\\n(0,false,0,false,false,false,true,false,false,false,false)\"];\n4 -> 0 [label=\"0.0002\"];\n4 -> 12 [label=\"10:startToRight\"];\n4 -> 14 [label=\"10:startToLeft\"];\n4 -> 24 [label=\"10:startRight\"];\n4 -> 80 [label=\"10:startLeft\"];\n5 [label=\"5\\n(0,false,0,false,false,false,true,false,false,false,true)\"];\n5 -> 1 [label=\"0.0002\"];\n5 -> 4 [label=\"0.00025\"];\n5 -> 15 [label=\"10:startToLeft\"];\n5 -> 25 [label=\"10:startRight\"];\n5 -> 81 [label=\"10:startLeft\"];\n6 [label=\"6\\n(0,false,0,false,false,false,true,false,true,false,false)\"];\n6 -> 2 [label=\"0.0002\"];\n6 -> 4 [label=\"0.00025\"];\n6 -> 13 [label=\"10:startToRight\"];\n6 -> 26 [label=\"10:startRight\"];\n6 -> 82 [label=\"10:startLeft\"];\n7 [label=\"7\\n(0,false,0,false,false,false,true,false,true,false,true)\"];\n7 -> 3 [label=\"0.0002\"];\n7 -> 5 [label=\"0.00025\"];\n7 -> 6 [label=\"0.00025\"];\n7 -> 27 [label=\"10:startRight\"];\n7 -> 83 [label=\"10:startLeft\"];\n8 [label=\"8\\n(0,false,0,false,true,false,false,false,false,true,false)\"];\n8 -> 1 [label=\"0.25:repairToRight\"];\n9 [label=\"9\\n(0,false,0,false,true,false,false,false,true,true,false)\"];\n9 -> 3 [label=\"0.25:repairToRight\"];\n9 -> 8 [label=\"0.00025\"];\n10 [label=\"10\\n(0,false,0,false,true,false,false,true,false,false,false)\"];\n10 -> 2 [label=\"0.25:repairToLeft\"];\n11 [label=\"11\\n(0,false,0,false,true,false,false,true,false,false,true)\"];\n11 -> 3 [label=\"0.25:repairToLeft\"];\n11 -> 10 [label=\"0.00025\"];\n12 [label=\"12\\n(0,false,0,false,true,false,true,false,false,true,false)\"];\n12 -> 5 [label=\"0.25:repairToRight\"];\n12 -> 8 [label=\"0.0002\"];\n13 [label=\"13\\n(0,false,0,false,true,false,true,false,true,true,false)\"];\n13 -> 7 [label=\"0.25:repairToRight\"];\n13 -> 9 [label=\"0.0002\"];\n13 -> 12 [label=\"0.00025\"];\n14 [label=\"14\\n(0,false,0,false,true,false,true,true,false,false,false)\"];\n14 -> 6 [label=\"0.25:repairToLeft\"];\n14 -> 10 [label=\"0.0002\"];\n15 [label=\"15\\n(0,false,0,false,true,false,true,true,false,false,true)\"];\n15 -> 7 [label=\"0.25:repairToLeft\"];\n15 -> 11 [label=\"0.0002\"];\n15 -> 14 [label=\"0.00025\"];\n16 [label=\"16\\n(0,false,0,false,true,true,false,false,false,false,false)\"];\n16 -> 4 [label=\"0.125:repairLine\"];\n17 [label=\"17\\n(0,false,0,false,true,true,false,false,false,false,true)\"];\n17 -> 5 [label=\"0.125:repairLine\"];\n17 -> 16 [label=\"0.00025\"];\n18 [label=\"18\\n(0,false,0,false,true,true,false,false,true,false,false)\"];\n18 -> 6 [label=\"0.125:repairLine\"];\n18 -> 16 [label=\"0.00025\"];\n19 [label=\"19\\n(0,false,0,false,true,true,false,false,true,false,true)\"];\n19 -> 7 [label=\"0.125:repairLine\"];\n19 -> 17 [label=\"0.00025\"];\n19 -> 18 [label=\"0.00025\"];\n20 [label=\"20\\n(0,false,0,true,true,false,false,false,false,false,false)\"];\n20 -> 28 [label=\"2:repairRight\"];\n21 [label=\"21\\n(0,false,0,true,true,false,false,false,false,false,true)\"];\n21 -> 20 [label=\"0.00025\"];\n21 -> 29 [label=\"2:repairRight\"];\n22 [label=\"22\\n(0,false,0,true,true,false,false,false,true,false,false)\"];\n22 -> 20 [label=\"0.00025\"];\n22 -> 30 [label=\"2:repairRight\"];\n23 [label=\"23\\n(0,false,0,true,true,false,false,false,true,false,true)\"];\n23 -> 21 [label=\"0.00025\"];\n23 -> 22 [label=\"0.00025\"];\n23 -> 31 [label=\"2:repairRight\"];\n24 [label=\"24\\n(0,false,0,true,true,false,true,false,false,false,false)\"];\n24 -> 20 [label=\"0.0002\"];\n24 -> 32 [label=\"2:repairRight\"];\n25 [label=\"25\\n(0,false,0,true,true,false,true,false,false,false,true)\"];\n25 -> 21 [label=\"0.0002\"];\n25 -> 24 [label=\"0.00025\"];\n25 -> 33 [label=\"2:repairRight\"];\n26 [label=\"26\\n(0,false,0,true,true,false,true,false,true,false,false)\"];\n26 -> 22 [label=\"0.0002\"];\n26 -> 24 [label=\"0.00025\"];\n26 -> 34 [label=\"2:repairRight\"];\n27 [label=\"27\\n(0,false,0,true,true,false,true,false,true,false,true)\"];\n27 -> 23 [label=\"0.0002\"];\n27 -> 25 [label=\"0.00025\"];\n27 -> 26 [label=\"0.00025\"];\n27 -> 35 [label=\"2:repairRight\"];\n28 [label=\"28\\n(0,false,1,false,false,false,false,false,false,false,false)\"];\n28 -> 0 [label=\"0.002\"];\n28 -> 36 [label=\"10:startToRight\"];\n28 -> 38 [label=\"10:startToLeft\"];\n28 -> 44 [label=\"10:startLine\"];\n28 -> 48 [label=\"10:startRight\"];\n28 -> 84 [label=\"10:startLeft\"];\n29 [label=\"29\\n(0,false,1,false,false,false,false,false,false,false,true)\"];\n29 -> 1 [label=\"0.002\"];\n29 -> 28 [label=\"0.00025\"];\n29 -> 39 [label=\"10:startToLeft\"];\n29 -> 45 [label=\"10:startLine\"];\n29 -> 49 [label=\"10:startRight\"];\n29 -> 85 [label=\"10:startLeft\"];\n30 [label=\"30\\n(0,false,1,false,false,false,false,false,true,false,false)\"];\n30 -> 2 [label=\"0.002\"];\n30 -> 28 [label=\"0.00025\"];\n30 -> 37 [label=\"10:startToRight\"];\n30 -> 46 [label=\"10:startLine\"];\n30 -> 50 [label=\"10:startRight\"];\n30 -> 86 [label=\"10:startLeft\"];\n31 [label=\"31\\n(0,false,1,false,false,false,false,false,true,false,true)\"];\n31 -> 3 [label=\"0.002\"];\n31 -> 29 [label=\"0.00025\"];\n31 -> 30 [label=\"0.00025\"];\n31 -> 47 [label=\"10:startLine\"];\n31 -> 51 [label=\"10:startRight\"];\n31 -> 87 [label=\"10:startLeft\"];\n32 [label=\"32\\n(0,false,1,false,false,false,true,false,false,false,false)\"];\n32 -> 4 [label=\"0.002\"];\n32 -> 28 [label=\"0.0002\"];\n32 -> 40 [label=\"10:startToRight\"];\n32 -> 42 [label=\"10:startToLeft\"];\n32 -> 52 [label=\"10:startRight\"];\n32 -> 88 [label=\"10:startLeft\"];\n33 [label=\"33\\n(0,false,1,false,false,false,true,false,false,false,true)\"];\n33 -> 5 [label=\"0.002\"];\n33 -> 29 [label=\"0.0002\"];\n33 -> 32 [label=\"0.00025\"];\n33 -> 43 [label=\"10:startToLeft\"];\n33 -> 53 [label=\"10:startRight\"];\n33 -> 89 [label=\"10:startLeft\"];\n34 [label=\"34\\n(0,false,1,false,false,false,true,false,true,false,false)\"];\n34 -> 6 [label=\"0.002\"];\n34 -> 30 [label=\"0.0002\"];\n34 -> 32 [label=\"0.00025\"];\n34 -> 41 [label=\"10:startToRight\"];\n34 -> 54 [label=\"10:startRight\"];\n34 -> 90 [label=\"10:startLeft\"];\n35 [label=\"35\\n(0,false,1,false,false,false,true,false,true,false,true)\"];\n35 -> 7 [label=\"0.002\"];\n35 -> 31 [label=\"0.0002\"];\n35 -> 33 [label=\"0.00025\"];\n35 -> 34 [label=\"0.00025\"];\n35 -> 55 [label=\"10:startRight\"];\n35 -> 91 [label=\"10:startLeft\"];\n36 [label=\"36\\n(0,false,1,false,true,false,false,false,false,true,false)\"];\n36 -> 8 [label=\"0.002\"];\n36 -> 29 [label=\"0.25:repairToRight\"];\n37 [label=\"37\\n(0,false,1,false,true,false,false,false,true,true,false)\"];\n37 -> 9 [label=\"0.002\"];\n37 -> 31 [label=\"0.25:repairToRight\"];\n37 -> 36 [label=\"0.00025\"];\n38 [label=\"38\\n(0,false,1,false,true,false,false,true,false,false,false)\"];\n38 -> 10 [label=\"0.002\"];\n38 -> 30 [label=\"0.25:repairToLeft\"];\n39 [label=\"39\\n(0,false,1,false,true,false,false,true,false,false,true)\"];\n39 -> 11 [label=\"0.002\"];\n39 -> 31 [label=\"0.25:repairToLeft\"];\n39 -> 38 [label=\"0.00025\"];\n40 [label=\"40\\n(0,false,1,false,true,false,true,false,false,true,false)\"];\n40 -> 12 [label=\"0.002\"];\n40 -> 33 [label=\"0.25:repairToRight\"];\n40 -> 36 [label=\"0.0002\"];\n41 [label=\"41\\n(0,false,1,false,true,false,true,false,true,true,false)\"];\n41 -> 13 [label=\"0.002\"];\n41 -> 35 [label=\"0.25:repairToRight\"];\n41 -> 37 [label=\"0.0002\"];\n41 -> 40 [label=\"0.00025\"];\n42 [label=\"42\\n(0,false,1,false,true,false,true,true,false,false,false)\"];\n42 -> 14 [label=\"0.002\"];\n42 -> 34 [label=\"0.25:repairToLeft\"];\n42 -> 38 [label=\"0.0002\"];\n43 [label=\"43\\n(0,false,1,false,true,false,true,true,false,false,true)\"];\n43 -> 15 [label=\"0.002\"];\n43 -> 35 [label=\"0.25:repairToLeft\"];\n43 -> 39 [label=\"0.0002\"];\n43 -> 42 [label=\"0.00025\"];\n44 [label=\"44\\n(0,false,1,false,true,true,false,false,false,false,false)\"];\n44 -> 16 [label=\"0.002\"];\n44 -> 32 [label=\"0.125:repairLine\"];\n45 [label=\"45\\n(0,false,1,false,true,true,false,false,false,false,true)\"];\n45 -> 17 [label=\"0.002\"];\n45 -> 33 [label=\"0.125:repairLine\"];\n45 -> 44 [label=\"0.00025\"];\n46 [label=\"46\\n(0,false,1,false,true,true,false,false,true,false,false)\"];\n46 -> 18 [label=\"0.002\"];\n46 -> 34 [label=\"0.125:repairLine\"];\n46 -> 44 [label=\"0.00025\"];\n47 [label=\"47\\n(0,false,1,false,true,true,false,false,true,false,true)\"];\n47 -> 19 [label=\"0.002\"];\n47 -> 35 [label=\"0.125:repairLine\"];\n47 -> 45 [label=\"0.00025\"];\n47 -> 46 [label=\"0.00025\"];\n48 [label=\"48\\n(0,false,1,true,true,false,false,false,false,false,false)\"];\n48 -> 20 [label=\"0.002\"];\n48 -> 56 [label=\"2:repairRight\"];\n49 [label=\"49\\n(0,false,1,true,true,false,false,false,false,false,true)\"];\n49 -> 21 [label=\"0.002\"];\n49 -> 48 [label=\"0.00025\"];\n49 -> 57 [label=\"2:repairRight\"];\n50 [label=\"50\\n(0,false,1,true,true,false,false,false,true,false,false)\"];\n50 -> 22 [label=\"0.002\"];\n50 -> 48 [label=\"0.00025\"];\n50 -> 58 [label=\"2:repairRight\"];\n51 [label=\"51\\n(0,false,1,true,true,false,false,false,true,false,true)\"];\n51 -> 23 [label=\"0.002\"];\n51 -> 49 [label=\"0.00025\"];\n51 -> 50 [label=\"0.00025\"];\n51 -> 59 [label=\"2:repairRight\"];\n52 [label=\"52\\n(0,false,1,true,true,false,true,false,false,false,false)\"];\n52 -> 24 [label=\"0.002\"];\n52 -> 48 [label=\"0.0002\"];\n52 -> 60 [label=\"2:repairRight\"];\n53 [label=\"53\\n(0,false,1,true,true,false,true,false,false,false,true)\"];\n53 -> 25 [label=\"0.002\"];\n53 -> 49 [label=\"0.0002\"];\n53 -> 52 [label=\"0.00025\"];\n53 -> 61 [label=\"2:repairRight\"];\n54 [label=\"54\\n(0,false,1,true,true,false,true,false,true,false,false)\"];\n54 -> 26 [label=\"0.002\"];\n54 -> 50 [label=\"0.0002\"];\n54 -> 52 [label=\"0.00025\"];\n54 -> 62 [label=\"2:repairRight\"];\n55 [label=\"55\\n(0,false,1,true,true,false,true,false,true,false,true)\"];\n55 -> 27 [label=\"0.002\"];\n55 -> 51 [label=\"0.0002\"];\n55 -> 53 [label=\"0.00025\"];\n55 -> 54 [label=\"0.00025\"];\n55 -> 63 [label=\"2:repairRight\"];\n56 [label=\"56\\n(0,false,2,false,false,false,false,false,false,false,false)\"];\n56 -> 28 [label=\"0.004\"];\n56 -> 64 [label=\"10:startToRight\"];\n56 -> 66 [label=\"10:startToLeft\"];\n56 -> 72 [label=\"10:startLine\"];\n56 -> 92 [label=\"10:startLeft\"];\n57 [label=\"57\\n(0,false,2,false,false,false,false,false,false,false,true)\"];\n57 -> 29 [label=\"0.004\"];\n57 -> 56 [label=\"0.00025\"];\n57 -> 67 [label=\"10:startToLeft\"];\n57 -> 73 [label=\"10:startLine\"];\n57 -> 93 [label=\"10:startLeft\"];\n58 [label=\"58\\n(0,false,2,false,false,false,false,false,true,false,false)\"];\n58 -> 30 [label=\"0.004\"];\n58 -> 56 [label=\"0.00025\"];\n58 -> 65 [label=\"10:startToRight\"];\n58 -> 74 [label=\"10:startLine\"];\n58 -> 94 [label=\"10:startLeft\"];\n59 [label=\"59\\n(0,false,2,false,false,false,false,false,true,false,true)\"];\n59 -> 31 [label=\"0.004\"];\n59 -> 57 [label=\"0.00025\"];\n59 -> 58 [label=\"0.00025\"];\n59 -> 75 [label=\"10:startLine\"];\n59 -> 95 [label=\"10:startLeft\"];\n60 [label=\"60\\n(0,false,2,false,false,false,true,false,false,false,false)\"];\n60 -> 32 [label=\"0.004\"];\n60 -> 56 [label=\"0.0002\"];\n60 -> 68 [label=\"10:startToRight\"];\n60 -> 70 [label=\"10:startToLeft\"];\n60 -> 96 [label=\"10:startLeft\"];\n61 [label=\"61\\n(0,false,2,false,false,false,true,false,false,false,true)\"];\n61 -> 33 [label=\"0.004\"];\n61 -> 57 [label=\"0.0002\"];\n61 -> 60 [label=\"0.00025\"];\n61 -> 71 [label=\"10:startToLeft\"];\n61 -> 97 [label=\"10:startLeft\"];\n62 [label=\"62\\n(0,false,2,false,false,false,true,false,true,false,false)\"];\n62 -> 34 [label=\"0.004\"];\n62 -> 58 [label=\"0.0002\"];\n62 -> 60 [label=\"0.00025\"];\n62 -> 69 [label=\"10:startToRight\"];\n62 -> 98 [label=\"10:startLeft\"];\n63 [label=\"63\\n(0,false,2,false,false,false,true,false,true,false,true)\"];\n63 -> 35 [label=\"0.004\"];\n63 -> 59 [label=\"0.0002\"];\n63 -> 61 [label=\"0.00025\"];\n63 -> 62 [label=\"0.00025\"];\n63 -> 99 [label=\"10:startLeft\"];\n64 [label=\"64\\n(0,false,2,false,true,false,false,false,false,true,false)\"];\n64 -> 36 [label=\"0.004\"];\n64 -> 57 [label=\"0.25:repairToRight\"];\n65 [label=\"65\\n(0,false,2,false,true,false,false,false,true,true,false)\"];\n65 -> 37 [label=\"0.004\"];\n65 -> 59 [label=\"0.25:repairToRight\"];\n65 -> 64 [label=\"0.00025\"];\n66 [label=\"66\\n(0,false,2,false,true,false,false,true,false,false,false)\"];\n66 -> 38 [label=\"0.004\"];\n66 -> 58 [label=\"0.25:repairToLeft\"];\n67 [label=\"67\\n(0,false,2,false,true,false,false,true,false,false,true)\"];\n67 -> 39 [label=\"0.004\"];\n67 -> 59 [label=\"0.25:repairToLeft\"];\n67 -> 66 [label=\"0.00025\"];\n68 [label=\"68\\n(0,false,2,false,true,false,true,false,false,true,false)\"];\n68 -> 40 [label=\"0.004\"];\n68 -> 61 [label=\"0.25:repairToRight\"];\n68 -> 64 [label=\"0.0002\"];\n69 [label=\"69\\n(0,false,2,false,true,false,true,false,true,true,false)\"];\n69 -> 41 [label=\"0.004\"];\n69 -> 63 [label=\"0.25:repairToRight\"];\n69 -> 65 [label=\"0.0002\"];\n69 -> 68 [label=\"0.00025\"];\n70 [label=\"70\\n(0,false,2,false,true,false,true,true,false,false,false)\"];\n70 -> 42 [label=\"0.004\"];\n70 -> 62 [label=\"0.25:repairToLeft\"];\n70 -> 66 [label=\"0.0002\"];\n71 [label=\"71\\n(0,false,2,false,true,false,true,true,false,false,true)\"];\n71 -> 43 [label=\"0.004\"];\n71 -> 63 [label=\"0.25:repairToLeft\"];\n71 -> 67 [label=\"0.0002\"];\n71 -> 70 [label=\"0.00025\"];\n72 [label=\"72\\n(0,false,2,false,true,true,false,false,false,false,false)\"];\n72 -> 44 [label=\"0.004\"];\n72 -> 60 [label=\"0.125:repairLine\"];\n73 [label=\"73\\n(0,false,2,false,true,true,false,false,false,false,true)\"];\n73 -> 45 [label=\"0.004\"];\n73 -> 61 [label=\"0.125:repairLine\"];\n73 -> 72 [label=\"0.00025\"];\n74 [label=\"74\\n(0,false,2,false,true,true,false,false,true,false,false)\"];\n74 -> 46 [label=\"0.004\"];\n74 -> 62 [label=\"0.125:repairLine\"];\n74 -> 72 [label=\"0.00025\"];\n75 [label=\"75\\n(0,false,2,false,true,true,false,false,true,false,true)\"];\n75 -> 47 [label=\"0.004\"];\n75 -> 63 [label=\"0.125:repairLine\"];\n75 -> 73 [label=\"0.00025\"];\n75 -> 74 [label=\"0.00025\"];\n76 [label=\"76\\n(0,true,0,false,true,false,false,false,false,false,false)\"];\n76 -> 100 [label=\"2:repairLeft\"];\n77 [label=\"77\\n(0,true,0,false,true,false,false,false,false,false,true)\"];\n77 -> 76 [label=\"0.00025\"];\n77 -> 101 [label=\"2:repairLeft\"];\n78 [label=\"78\\n(0,true,0,false,true,false,false,false,true,false,false)\"];\n78 -> 76 [label=\"0.00025\"];\n78 -> 102 [label=\"2:repairLeft\"];\n79 [label=\"79\\n(0,true,0,false,true,false,false,false,true,false,true)\"];\n79 -> 77 [label=\"0.00025\"];\n79 -> 78 [label=\"0.00025\"];\n79 -> 103 [label=\"2:repairLeft\"];\n80 [label=\"80\\n(0,true,0,false,true,false,true,false,false,false,false)\"];\n80 -> 76 [label=\"0.0002\"];\n80 -> 104 [label=\"2:repairLeft\"];\n81 [label=\"81\\n(0,true,0,false,true,false,true,false,false,false,true)\"];\n81 -> 77 [label=\"0.0002\"];\n81 -> 80 [label=\"0.00025\"];\n81 -> 105 [label=\"2:repairLeft\"];\n82 [label=\"82\\n(0,true,0,false,true,false,true,false,true,false,false)\"];\n82 -> 78 [label=\"0.0002\"];\n82 -> 80 [label=\"0.00025\"];\n82 -> 106 [label=\"2:repairLeft\"];\n83 [label=\"83\\n(0,true,0,false,true,false,true,false,true,false,true)\"];\n83 -> 79 [label=\"0.0002\"];\n83 -> 81 [label=\"0.00025\"];\n83 -> 82 [label=\"0.00025\"];\n83 -> 107 [label=\"2:repairLeft\"];\n84 [label=\"84\\n(0,true,1,false,true,false,false,false,false,false,false)\"];\n84 -> 76 [label=\"0.002\"];\n84 -> 128 [label=\"2:repairLeft\"];\n85 [label=\"85\\n(0,true,1,false,true,false,false,false,false,false,true)\"];\n85 -> 77 [label=\"0.002\"];\n85 -> 84 [label=\"0.00025\"];\n85 -> 129 [label=\"2:repairLeft\"];\n86 [label=\"86\\n(0,true,1,false,true,false,false,false,true,false,false)\"];\n86 -> 78 [label=\"0.002\"];\n86 -> 84 [label=\"0.00025\"];\n86 -> 130 [label=\"2:repairLeft\"];\n87 [label=\"87\\n(0,true,1,false,true,false,false,false,true,false,true)\"];\n87 -> 79 [label=\"0.002\"];\n87 -> 85 [label=\"0.00025\"];\n87 -> 86 [label=\"0.00025\"];\n87 -> 131 [label=\"2:repairLeft\"];\n88 [label=\"88\\n(0,true,1,false,true,false,true,false,false,false,false)\"];\n88 -> 80 [label=\"0.002\"];\n88 -> 84 [label=\"0.0002\"];\n88 -> 132 [label=\"2:repairLeft\"];\n89 [label=\"89\\n(0,true,1,false,true,false,true,false,false,false,true)\"];\n89 -> 81 [label=\"0.002\"];\n89 -> 85 [label=\"0.0002\"];\n89 -> 88 [label=\"0.00025\"];\n89 -> 133 [label=\"2:repairLeft\"];\n90 [label=\"90\\n(0,true,1,false,true,false,true,false,true,false,false)\"];\n90 -> 82 [label=\"0.002\"];\n90 -> 86 [label=\"0.0002\"];\n90 -> 88 [label=\"0.00025\"];\n90 -> 134 [label=\"2:repairLeft\"];\n91 [label=\"91\\n(0,true,1,false,true,false,true,false,true,false,true)\"];\n91 -> 83 [label=\"0.002\"];\n91 -> 87 [label=\"0.0002\"];\n91 -> 89 [label=\"0.00025\"];\n91 -> 90 [label=\"0.00025\"];\n91 -> 135 [label=\"2:repairLeft\"];\n92 [label=\"92\\n(0,true,2,false,true,false,false,false,false,false,false)\"];\n92 -> 84 [label=\"0.004\"];\n92 -> 156 [label=\"2:repairLeft\"];\n93 [label=\"93\\n(0,true,2,false,true,false,false,false,false,false,true)\"];\n93 -> 85 [label=\"0.004\"];\n93 -> 92 [label=\"0.00025\"];\n93 -> 157 [label=\"2:repairLeft\"];\n94 [label=\"94\\n(0,true,2,false,true,false,false,false,true,false,false)\"];\n94 -> 86 [label=\"0.004\"];\n94 -> 92 [label=\"0.00025\"];\n94 -> 158 [label=\"2:repairLeft\"];\n95 [label=\"95\\n(0,true,2,false,true,false,false,false,true,false,true)\"];\n95 -> 87 [label=\"0.004\"];\n95 -> 93 [label=\"0.00025\"];\n95 -> 94 [label=\"0.00025\"];\n95 -> 159 [label=\"2:repairLeft\"];\n96 [label=\"96\\n(0,true,2,false,true,false,true,false,false,false,false)\"];\n96 -> 88 [label=\"0.004\"];\n96 -> 92 [label=\"0.0002\"];\n96 -> 160 [label=\"2:repairLeft\"];\n97 [label=\"97\\n(0,true,2,false,true,false,true,false,false,false,true)\"];\n97 -> 89 [label=\"0.004\"];\n97 -> 93 [label=\"0.0002\"];\n97 -> 96 [label=\"0.00025\"];\n97 -> 161 [label=\"2:repairLeft\"];\n98 [label=\"98\\n(0,true,2,false,true,false,true,false,true,false,false)\"];\n98 -> 90 [label=\"0.004\"];\n98 -> 94 [label=\"0.0002\"];\n98 -> 96 [label=\"0.00025\"];\n98 -> 162 [label=\"2:repairLeft\"];\n99 [label=\"99\\n(0,true,2,false,true,false,true,false,true,false,true)\"];\n99 -> 91 [label=\"0.004\"];\n99 -> 95 [label=\"0.0002\"];\n99 -> 97 [label=\"0.00025\"];\n99 -> 98 [label=\"0.00025\"];\n99 -> 163 [label=\"2:repairLeft\"];\n100 [label=\"100\\n(1,false,0,false,false,false,false,false,false,false,false)\"];\n100 -> 0 [label=\"0.002\"];\n100 -> 108 [label=\"10:startToRight\"];\n100 -> 110 [label=\"10:startToLeft\"];\n100 -> 116 [label=\"10:startLine\"];\n100 -> 120 [label=\"10:startRight\"];\n100 -> 176 [label=\"10:startLeft\"];\n101 [label=\"101\\n(1,false,0,false,false,false,false,false,false,false,true)\"];\n101 -> 1 [label=\"0.002\"];\n101 -> 100 [label=\"0.00025\"];\n101 -> 111 [label=\"10:startToLeft\"];\n101 -> 117 [label=\"10:startLine\"];\n101 -> 121 [label=\"10:startRight\"];\n101 -> 177 [label=\"10:startLeft\"];\n102 [label=\"102\\n(1,false,0,false,false,false,false,false,true,false,false)\"];\n102 -> 2 [label=\"0.002\"];\n102 -> 100 [label=\"0.00025\"];\n102 -> 109 [label=\"10:startToRight\"];\n102 -> 118 [label=\"10:startLine\"];\n102 -> 122 [label=\"10:startRight\"];\n102 -> 178 [label=\"10:startLeft\"];\n103 [label=\"103\\n(1,false,0,false,false,false,false,false,true,false,true)\"];\n103 -> 3 [label=\"0.002\"];\n103 -> 101 [label=\"0.00025\"];\n103 -> 102 [label=\"0.00025\"];\n103 -> 119 [label=\"10:startLine\"];\n103 -> 123 [label=\"10:startRight\"];\n103 -> 179 [label=\"10:startLeft\"];\n104 [label=\"104\\n(1,false,0,false,false,false,true,false,false,false,false)\"];\n104 -> 4 [label=\"0.002\"];\n104 -> 100 [label=\"0.0002\"];\n104 -> 112 [label=\"10:startToRight\"];\n104 -> 114 [label=\"10:startToLeft\"];\n104 -> 124 [label=\"10:startRight\"];\n104 -> 180 [label=\"10:startLeft\"];\n105 [label=\"105\\n(1,false,0,false,false,false,true,false,false,false,true)\"];\n105 -> 5 [label=\"0.002\"];\n105 -> 101 [label=\"0.0002\"];\n105 -> 104 [label=\"0.00025\"];\n105 -> 115 [label=\"10:startToLeft\"];\n105 -> 125 [label=\"10:startRight\"];\n105 -> 181 [label=\"10:startLeft\"];\n106 [label=\"106\\n(1,false,0,false,false,false,true,false,true,false,false)\"];\n106 -> 6 [label=\"0.002\"];\n106 -> 102 [label=\"0.0002\"];\n106 -> 104 [label=\"0.00025\"];\n106 -> 113 [label=\"10:startToRight\"];\n106 -> 126 [label=\"10:startRight\"];\n106 -> 182 [label=\"10:startLeft\"];\n107 [label=\"107\\n(1,false,0,false,false,false,true,false,true,false,true)\"];\n107 -> 7 [label=\"0.002\"];\n107 -> 103 [label=\"0.0002\"];\n107 -> 105 [label=\"0.00025\"];\n107 -> 106 [label=\"0.00025\"];\n107 -> 127 [label=\"10:startRight\"];\n107 -> 183 [label=\"10:startLeft\"];\n108 [label=\"108\\n(1,false,0,false,true,false,false,false,false,true,false)\"];\n108 -> 8 [label=\"0.002\"];\n108 -> 101 [label=\"0.25:repairToRight\"];\n109 [label=\"109\\n(1,false,0,false,true,false,false,false,true,true,false)\"];\n109 -> 9 [label=\"0.002\"];\n109 -> 103 [label=\"0.25:repairToRight\"];\n109 -> 108 [label=\"0.00025\"];\n110 [label=\"110\\n(1,false,0,false,true,false,false,true,false,false,false)\"];\n110 -> 10 [label=\"0.002\"];\n110 -> 102 [label=\"0.25:repairToLeft\"];\n111 [label=\"111\\n(1,false,0,false,true,false,false,true,false,false,true)\"];\n111 -> 11 [label=\"0.002\"];\n111 -> 103 [label=\"0.25:repairToLeft\"];\n111 -> 110 [label=\"0.00025\"];\n112 [label=\"112\\n(1,false,0,false,true,false,true,false,false,true,false)\"];\n112 -> 12 [label=\"0.002\"];\n112 -> 105 [label=\"0.25:repairToRight\"];\n112 -> 108 [label=\"0.0002\"];\n113 [label=\"113\\n(1,false,0,false,true,false,true,false,true,true,false)\"];\n113 -> 13 [label=\"0.002\"];\n113 -> 107 [label=\"0.25:repairToRight\"];\n113 -> 109 [label=\"0.0002\"];\n113 -> 112 [label=\"0.00025\"];\n114 [label=\"114\\n(1,false,0,false,true,false,true,true,false,false,false)\"];\n114 -> 14 [label=\"0.002\"];\n114 -> 106 [label=\"0.25:repairToLeft\"];\n114 -> 110 [label=\"0.0002\"];\n115 [label=\"115\\n(1,false,0,false,true,false,true,true,false,false,true)\"];\n115 -> 15 [label=\"0.002\"];\n115 -> 107 [label=\"0.25:repairToLeft\"];\n115 -> 111 [label=\"0.0002\"];\n115 -> 114 [label=\"0.00025\"];\n116 [label=\"116\\n(1,false,0,false,true,true,false,false,false,false,false)\"];\n116 -> 16 [label=\"0.002\"];\n116 -> 104 [label=\"0.125:repairLine\"];\n117 [label=\"117\\n(1,false,0,false,true,true,false,false,false,false,true)\"];\n117 -> 17 [label=\"0.002\"];\n117 -> 105 [label=\"0.125:repairLine\"];\n117 -> 116 [label=\"0.00025\"];\n118 [label=\"118\\n(1,false,0,false,true,true,false,false,true,false,false)\"];\n118 -> 18 [label=\"0.002\"];\n118 -> 106 [label=\"0.125:repairLine\"];\n118 -> 116 [label=\"0.00025\"];\n119 [label=\"119\\n(1,false,0,false,true,true,false,false,true,false,true)\"];\n119 -> 19 [label=\"0.002\"];\n119 -> 107 [label=\"0.125:repairLine\"];\n119 -> 117 [label=\"0.00025\"];\n119 -> 118 [label=\"0.00025\"];\n120 [label=\"120\\n(1,false,0,true,true,false,false,false,false,false,false)\"];\n120 -> 20 [label=\"0.002\"];\n120 -> 128 [label=\"2:repairRight\"];\n121 [label=\"121\\n(1,false,0,true,true,false,false,false,false,false,true)\"];\n121 -> 21 [label=\"0.002\"];\n121 -> 120 [label=\"0.00025\"];\n121 -> 129 [label=\"2:repairRight\"];\n122 [label=\"122\\n(1,false,0,true,true,false,false,false,true,false,false)\"];\n122 -> 22 [label=\"0.002\"];\n122 -> 120 [label=\"0.00025\"];\n122 -> 130 [label=\"2:repairRight\"];\n123 [label=\"123\\n(1,false,0,true,true,false,false,false,true,false,true)\"];\n123 -> 23 [label=\"0.002\"];\n123 -> 121 [label=\"0.00025\"];\n123 -> 122 [label=\"0.00025\"];\n123 -> 131 [label=\"2:repairRight\"];\n124 [label=\"124\\n(1,false,0,true,true,false,true,false,false,false,false)\"];\n124 -> 24 [label=\"0.002\"];\n124 -> 120 [label=\"0.0002\"];\n124 -> 132 [label=\"2:repairRight\"];\n125 [label=\"125\\n(1,false,0,true,true,false,true,false,false,false,true)\"];\n125 -> 25 [label=\"0.002\"];\n125 -> 121 [label=\"0.0002\"];\n125 -> 124 [label=\"0.00025\"];\n125 -> 133 [label=\"2:repairRight\"];\n126 [label=\"126\\n(1,false,0,true,true,false,true,false,true,false,false)\"];\n126 -> 26 [label=\"0.002\"];\n126 -> 122 [label=\"0.0002\"];\n126 -> 124 [label=\"0.00025\"];\n126 -> 134 [label=\"2:repairRight\"];\n127 [label=\"127\\n(1,false,0,true,true,false,true,false,true,false,true)\"];\n127 -> 27 [label=\"0.002\"];\n127 -> 123 [label=\"0.0002\"];\n127 -> 125 [label=\"0.00025\"];\n127 -> 126 [label=\"0.00025\"];\n127 -> 135 [label=\"2:repairRight\"];\n128 [label=\"128\\n(1,false,1,false,false,false,false,false,false,false,false)\"];\n128 -> 28 [label=\"0.002\"];\n128 -> 100 [label=\"0.002\"];\n128 -> 136 [label=\"10:startToRight\"];\n128 -> 138 [label=\"10:startToLeft\"];\n128 -> 144 [label=\"10:startLine\"];\n128 -> 148 [label=\"10:startRight\"];\n128 -> 184 [label=\"10:startLeft\"];\n129 [label=\"129\\n(1,false,1,false,false,false,false,false,false,false,true)\"];\n129 -> 29 [label=\"0.002\"];\n129 -> 101 [label=\"0.002\"];\n129 -> 128 [label=\"0.00025\"];\n129 -> 139 [label=\"10:startToLeft\"];\n129 -> 145 [label=\"10:startLine\"];\n129 -> 149 [label=\"10:startRight\"];\n129 -> 185 [label=\"10:startLeft\"];\n130 [label=\"130\\n(1,false,1,false,false,false,false,false,true,false,false)\"];\n130 -> 30 [label=\"0.002\"];\n130 -> 102 [label=\"0.002\"];\n130 -> 128 [label=\"0.00025\"];\n130 -> 137 [label=\"10:startToRight\"];\n130 -> 146 [label=\"10:startLine\"];\n130 -> 150 [label=\"10:startRight\"];\n130 -> 186 [label=\"10:startLeft\"];\n131 [label=\"131\\n(1,false,1,false,false,false,false,false,true,false,true)\"];\n131 -> 31 [label=\"0.002\"];\n131 -> 103 [label=\"0.002\"];\n131 -> 129 [label=\"0.00025\"];\n131 -> 130 [label=\"0.00025\"];\n131 -> 147 [label=\"10:startLine\"];\n131 -> 151 [label=\"10:startRight\"];\n131 -> 187 [label=\"10:startLeft\"];\n132 [label=\"132\\n(1,false,1,false,false,false,true,false,false,false,false)\"];\n132 -> 32 [label=\"0.002\"];\n132 -> 104 [label=\"0.002\"];\n132 -> 128 [label=\"0.0002\"];\n132 -> 140 [label=\"10:startToRight\"];\n132 -> 142 [label=\"10:startToLeft\"];\n132 -> 152 [label=\"10:startRight\"];\n132 -> 188 [label=\"10:startLeft\"];\n133 [label=\"133\\n(1,false,1,false,false,false,true,false,false,false,true)\"];\n133 -> 33 [label=\"0.002\"];\n133 -> 105 [label=\"0.002\"];\n133 -> 129 [label=\"0.0002\"];\n133 -> 132 [label=\"0.00025\"];\n133 -> 143 [label=\"10:startToLeft\"];\n133 -> 153 [label=\"10:startRight\"];\n133 -> 189 [label=\"10:startLeft\"];\n134 [label=\"134\\n(1,false,1,false,false,false,true,false,true,false,false)\"];\n134 -> 34 [label=\"0.002\"];\n134 -> 106 [label=\"0.002\"];\n134 -> 130 [label=\"0.0002\"];\n134 -> 132 [label=\"0.00025\"];\n134 -> 141 [label=\"10:startToRight\"];\n134 -> 154 [label=\"10:startRight\"];\n134 -> 190 [label=\"10:startLeft\"];\n135 [label=\"135\\n(1,false,1,false,false,false,true,false,true,false,true)\"];\n135 -> 35 [label=\"0.002\"];\n135 -> 107 [label=\"0.002\"];\n135 -> 131 [label=\"0.0002\"];\n135 -> 133 [label=\"0.00025\"];\n135 -> 134 [label=\"0.00025\"];\n135 -> 155 [label=\"10:startRight\"];\n135 -> 191 [label=\"10:startLeft\"];\n136 [label=\"136\\n(1,false,1,false,true,false,false,false,false,true,false)\"];\n136 -> 36 [label=\"0.002\"];\n136 -> 108 [label=\"0.002\"];\n136 -> 129 [label=\"0.25:repairToRight\"];\n137 [label=\"137\\n(1,false,1,false,true,false,false,false,true,true,false)\"];\n137 -> 37 [label=\"0.002\"];\n137 -> 109 [label=\"0.002\"];\n137 -> 131 [label=\"0.25:repairToRight\"];\n137 -> 136 [label=\"0.00025\"];\n138 [label=\"138\\n(1,false,1,false,true,false,false,true,false,false,false)\"];\n138 -> 38 [label=\"0.002\"];\n138 -> 110 [label=\"0.002\"];\n138 -> 130 [label=\"0.25:repairToLeft\"];\n139 [label=\"139\\n(1,false,1,false,true,false,false,true,false,false,true)\"];\n139 -> 39 [label=\"0.002\"];\n139 -> 111 [label=\"0.002\"];\n139 -> 131 [label=\"0.25:repairToLeft\"];\n139 -> 138 [label=\"0.00025\"];\n140 [label=\"140\\n(1,false,1,false,true,false,true,false,false,true,false)\"];\n140 -> 40 [label=\"0.002\"];\n140 -> 112 [label=\"0.002\"];\n140 -> 133 [label=\"0.25:repairToRight\"];\n140 -> 136 [label=\"0.0002\"];\n141 [label=\"141\\n(1,false,1,false,true,false,true,false,true,true,false)\"];\n141 -> 41 [label=\"0.002\"];\n141 -> 113 [label=\"0.002\"];\n141 -> 135 [label=\"0.25:repairToRight\"];\n141 -> 137 [label=\"0.0002\"];\n141 -> 140 [label=\"0.00025\"];\n142 [label=\"142\\n(1,false,1,false,true,false,true,true,false,false,false)\"];\n142 -> 42 [label=\"0.002\"];\n142 -> 114 [label=\"0.002\"];\n142 -> 134 [label=\"0.25:repairToLeft\"];\n142 -> 138 [label=\"0.0002\"];\n143 [label=\"143\\n(1,false,1,false,true,false,true,true,false,false,true)\"];\n143 -> 43 [label=\"0.002\"];\n143 -> 115 [label=\"0.002\"];\n143 -> 135 [label=\"0.25:repairToLeft\"];\n143 -> 139 [label=\"0.0002\"];\n143 -> 142 [label=\"0.00025\"];\n144 [label=\"144\\n(1,false,1,false,true,true,false,false,false,false,false)\"];\n144 -> 44 [label=\"0.002\"];\n144 -> 116 [label=\"0.002\"];\n144 -> 132 [label=\"0.125:repairLine\"];\n145 [label=\"145\\n(1,false,1,false,true,true,false,false,false,false,true)\"];\n145 -> 45 [label=\"0.002\"];\n145 -> 117 [label=\"0.002\"];\n145 -> 133 [label=\"0.125:repairLine\"];\n145 -> 144 [label=\"0.00025\"];\n146 [label=\"146\\n(1,false,1,false,true,true,false,false,true,false,false)\"];\n146 -> 46 [label=\"0.002\"];\n146 -> 118 [label=\"0.002\"];\n146 -> 134 [label=\"0.125:repairLine\"];\n146 -> 144 [label=\"0.00025\"];\n147 [label=\"147\\n(1,false,1,false,true,true,false,false,true,false,true)\"];\n147 -> 47 [label=\"0.002\"];\n147 -> 119 [label=\"0.002\"];\n147 -> 135 [label=\"0.125:repairLine\"];\n147 -> 145 [label=\"0.00025\"];\n147 -> 146 [label=\"0.00025\"];\n148 [label=\"148\\n(1,false,1,true,true,false,false,false,false,false,false)\"];\n148 -> 48 [label=\"0.002\"];\n148 -> 120 [label=\"0.002\"];\n148 -> 156 [label=\"2:repairRight\"];\n149 [label=\"149\\n(1,false,1,true,true,false,false,false,false,false,true)\"];\n149 -> 49 [label=\"0.002\"];\n149 -> 121 [label=\"0.002\"];\n149 -> 148 [label=\"0.00025\"];\n149 -> 157 [label=\"2:repairRight\"];\n150 [label=\"150\\n(1,false,1,true,true,false,false,false,true,false,false)\"];\n150 -> 50 [label=\"0.002\"];\n150 -> 122 [label=\"0.002\"];\n150 -> 148 [label=\"0.00025\"];\n150 -> 158 [label=\"2:repairRight\"];\n151 [label=\"151\\n(1,false,1,true,true,false,false,false,true,false,true)\"];\n151 -> 51 [label=\"0.002\"];\n151 -> 123 [label=\"0.002\"];\n151 -> 149 [label=\"0.00025\"];\n151 -> 150 [label=\"0.00025\"];\n151 -> 159 [label=\"2:repairRight\"];\n152 [label=\"152\\n(1,false,1,true,true,false,true,false,false,false,false)\"];\n152 -> 52 [label=\"0.002\"];\n152 -> 124 [label=\"0.002\"];\n152 -> 148 [label=\"0.0002\"];\n152 -> 160 [label=\"2:repairRight\"];\n153 [label=\"153\\n(1,false,1,true,true,false,true,false,false,false,true)\"];\n153 -> 53 [label=\"0.002\"];\n153 -> 125 [label=\"0.002\"];\n153 -> 149 [label=\"0.0002\"];\n153 -> 152 [label=\"0.00025\"];\n153 -> 161 [label=\"2:repairRight\"];\n154 [label=\"154\\n(1,false,1,true,true,false,true,false,true,false,false)\"];\n154 -> 54 [label=\"0.002\"];\n154 -> 126 [label=\"0.002\"];\n154 -> 150 [label=\"0.0002\"];\n154 -> 152 [label=\"0.00025\"];\n154 -> 162 [label=\"2:repairRight\"];\n155 [label=\"155\\n(1,false,1,true,true,false,true,false,true,false,true)\"];\n155 -> 55 [label=\"0.002\"];\n155 -> 127 [label=\"0.002\"];\n155 -> 151 [label=\"0.0002\"];\n155 -> 153 [label=\"0.00025\"];\n155 -> 154 [label=\"0.00025\"];\n155 -> 163 [label=\"2:repairRight\"];\n156 [label=\"156\\n(1,false,2,false,false,false,false,false,false,false,false)\"];\n156 -> 56 [label=\"0.002\"];\n156 -> 128 [label=\"0.004\"];\n156 -> 164 [label=\"10:startToRight\"];\n156 -> 166 [label=\"10:startToLeft\"];\n156 -> 172 [label=\"10:startLine\"];\n156 -> 192 [label=\"10:startLeft\"];\n157 [label=\"157\\n(1,false,2,false,false,false,false,false,false,false,true)\"];\n157 -> 57 [label=\"0.002\"];\n157 -> 129 [label=\"0.004\"];\n157 -> 156 [label=\"0.00025\"];\n157 -> 167 [label=\"10:startToLeft\"];\n157 -> 173 [label=\"10:startLine\"];\n157 -> 193 [label=\"10:startLeft\"];\n158 [label=\"158\\n(1,false,2,false,false,false,false,false,true,false,false)\"];\n158 -> 58 [label=\"0.002\"];\n158 -> 130 [label=\"0.004\"];\n158 -> 156 [label=\"0.00025\"];\n158 -> 165 [label=\"10:startToRight\"];\n158 -> 174 [label=\"10:startLine\"];\n158 -> 194 [label=\"10:startLeft\"];\n159 [label=\"159\\n(1,false,2,false,false,false,false,false,true,false,true)\"];\n159 -> 59 [label=\"0.002\"];\n159 -> 131 [label=\"0.004\"];\n159 -> 157 [label=\"0.00025\"];\n159 -> 158 [label=\"0.00025\"];\n159 -> 175 [label=\"10:startLine\"];\n159 -> 195 [label=\"10:startLeft\"];\n160 [label=\"160\\n(1,false,2,false,false,false,true,false,false,false,false)\"];\n160 -> 60 [label=\"0.002\"];\n160 -> 132 [label=\"0.004\"];\n160 -> 156 [label=\"0.0002\"];\n160 -> 168 [label=\"10:startToRight\"];\n160 -> 170 [label=\"10:startToLeft\"];\n160 -> 196 [label=\"10:startLeft\"];\n161 [label=\"161\\n(1,false,2,false,false,false,true,false,false,false,true)\"];\n161 -> 61 [label=\"0.002\"];\n161 -> 133 [label=\"0.004\"];\n161 -> 157 [label=\"0.0002\"];\n161 -> 160 [label=\"0.00025\"];\n161 -> 171 [label=\"10:startToLeft\"];\n161 -> 197 [label=\"10:startLeft\"];\n162 [label=\"162\\n(1,false,2,false,false,false,true,false,true,false,false)\"];\n162 -> 62 [label=\"0.002\"];\n162 -> 134 [label=\"0.004\"];\n162 -> 158 [label=\"0.0002\"];\n162 -> 160 [label=\"0.00025\"];\n162 -> 169 [label=\"10:startToRight\"];\n162 -> 198 [label=\"10:startLeft\"];\n163 [label=\"163\\n(1,false,2,false,false,false,true,false,true,false,true)\"];\n163 -> 63 [label=\"0.002\"];\n163 -> 135 [label=\"0.004\"];\n163 -> 159 [label=\"0.0002\"];\n163 -> 161 [label=\"0.00025\"];\n163 -> 162 [label=\"0.00025\"];\n163 -> 199 [label=\"10:startLeft\"];\n164 [label=\"164\\n(1,false,2,false,true,false,false,false,false,true,false)\"];\n164 -> 64 [label=\"0.002\"];\n164 -> 136 [label=\"0.004\"];\n164 -> 157 [label=\"0.25:repairToRight\"];\n165 [label=\"165\\n(1,false,2,false,true,false,false,false,true,true,false)\"];\n165 -> 65 [label=\"0.002\"];\n165 -> 137 [label=\"0.004\"];\n165 -> 159 [label=\"0.25:repairToRight\"];\n165 -> 164 [label=\"0.00025\"];\n166 [label=\"166\\n(1,false,2,false,true,false,false,true,false,false,false)\"];\n166 -> 66 [label=\"0.002\"];\n166 -> 138 [label=\"0.004\"];\n166 -> 158 [label=\"0.25:repairToLeft\"];\n167 [label=\"167\\n(1,false,2,false,true,false,false,true,false,false,true)\"];\n167 -> 67 [label=\"0.002\"];\n167 -> 139 [label=\"0.004\"];\n167 -> 159 [label=\"0.25:repairToLeft\"];\n167 -> 166 [label=\"0.00025\"];\n168 [label=\"168\\n(1,false,2,false,true,false,true,false,false,true,false)\"];\n168 -> 68 [label=\"0.002\"];\n168 -> 140 [label=\"0.004\"];\n168 -> 161 [label=\"0.25:repairToRight\"];\n168 -> 164 [label=\"0.0002\"];\n169 [label=\"169\\n(1,false,2,false,true,false,true,false,true,true,false)\"];\n169 -> 69 [label=\"0.002\"];\n169 -> 141 [label=\"0.004\"];\n169 -> 163 [label=\"0.25:repairToRight\"];\n169 -> 165 [label=\"0.0002\"];\n169 -> 168 [label=\"0.00025\"];\n170 [label=\"170\\n(1,false,2,false,true,false,true,true,false,false,false)\"];\n170 -> 70 [label=\"0.002\"];\n170 -> 142 [label=\"0.004\"];\n170 -> 162 [label=\"0.25:repairToLeft\"];\n170 -> 166 [label=\"0.0002\"];\n171 [label=\"171\\n(1,false,2,false,true,false,true,true,false,false,true)\"];\n171 -> 71 [label=\"0.002\"];\n171 -> 143 [label=\"0.004\"];\n171 -> 163 [label=\"0.25:repairToLeft\"];\n171 -> 167 [label=\"0.0002\"];\n171 -> 170 [label=\"0.00025\"];\n172 [label=\"172\\n(1,false,2,false,true,true,false,false,false,false,false)\"];\n172 -> 72 [label=\"0.002\"];\n172 -> 144 [label=\"0.004\"];\n172 -> 160 [label=\"0.125:repairLine\"];\n173 [label=\"173\\n(1,false,2,false,true,true,false,false,false,false,true)\"];\n173 -> 73 [label=\"0.002\"];\n173 -> 145 [label=\"0.004\"];\n173 -> 161 [label=\"0.125:repairLine\"];\n173 -> 172 [label=\"0.00025\"];\n174 [label=\"174\\n(1,false,2,false,true,true,false,false,true,false,false)\"];\n174 -> 74 [label=\"0.002\"];\n174 -> 146 [label=\"0.004\"];\n174 -> 162 [label=\"0.125:repairLine\"];\n174 -> 172 [label=\"0.00025\"];\n175 [label=\"175\\n(1,false,2,false,true,true,false,false,true,false,true)\"];\n175 -> 75 [label=\"0.002\"];\n175 -> 147 [label=\"0.004\"];\n175 -> 163 [label=\"0.125:repairLine\"];\n175 -> 173 [label=\"0.00025\"];\n175 -> 174 [label=\"0.00025\"];\n176 [label=\"176\\n(1,true,0,false,true,false,false,false,false,false,false)\"];\n176 -> 76 [label=\"0.002\"];\n176 -> 200 [label=\"2:repairLeft\"];\n177 [label=\"177\\n(1,true,0,false,true,false,false,false,false,false,true)\"];\n177 -> 77 [label=\"0.002\"];\n177 -> 176 [label=\"0.00025\"];\n177 -> 201 [label=\"2:repairLeft\"];\n178 [label=\"178\\n(1,true,0,false,true,false,false,false,true,false,false)\"];\n178 -> 78 [label=\"0.002\"];\n178 -> 176 [label=\"0.00025\"];\n178 -> 202 [label=\"2:repairLeft\"];\n179 [label=\"179\\n(1,true,0,false,true,false,false,false,true,false,true)\"];\n179 -> 79 [label=\"0.002\"];\n179 -> 177 [label=\"0.00025\"];\n179 -> 178 [label=\"0.00025\"];\n179 -> 203 [label=\"2:repairLeft\"];\n180 [label=\"180\\n(1,true,0,false,true,false,true,false,false,false,false)\"];\n180 -> 80 [label=\"0.002\"];\n180 -> 176 [label=\"0.0002\"];\n180 -> 204 [label=\"2:repairLeft\"];\n181 [label=\"181\\n(1,true,0,false,true,false,true,false,false,false,true)\"];\n181 -> 81 [label=\"0.002\"];\n181 -> 177 [label=\"0.0002\"];\n181 -> 180 [label=\"0.00025\"];\n181 -> 205 [label=\"2:repairLeft\"];\n182 [label=\"182\\n(1,true,0,false,true,false,true,false,true,false,false)\"];\n182 -> 82 [label=\"0.002\"];\n182 -> 178 [label=\"0.0002\"];\n182 -> 180 [label=\"0.00025\"];\n182 -> 206 [label=\"2:repairLeft\"];\n183 [label=\"183\\n(1,true,0,false,true,false,true,false,true,false,true)\"];\n183 -> 83 [label=\"0.002\"];\n183 -> 179 [label=\"0.0002\"];\n183 -> 181 [label=\"0.00025\"];\n183 -> 182 [label=\"0.00025\"];\n183 -> 207 [label=\"2:repairLeft\"];\n184 [label=\"184\\n(1,true,1,false,true,false,false,false,false,false,false)\"];\n184 -> 84 [label=\"0.002\"];\n184 -> 176 [label=\"0.002\"];\n184 -> 228 [label=\"2:repairLeft\"];\n185 [label=\"185\\n(1,true,1,false,true,false,false,false,false,false,true)\"];\n185 -> 85 [label=\"0.002\"];\n185 -> 177 [label=\"0.002\"];\n185 -> 184 [label=\"0.00025\"];\n185 -> 229 [label=\"2:repairLeft\"];\n186 [label=\"186\\n(1,true,1,false,true,false,false,false,true,false,false)\"];\n186 -> 86 [label=\"0.002\"];\n186 -> 178 [label=\"0.002\"];\n186 -> 184 [label=\"0.00025\"];\n186 -> 230 [label=\"2:repairLeft\"];\n187 [label=\"187\\n(1,true,1,false,true,false,false,false,true,false,true)\"];\n187 -> 87 [label=\"0.002\"];\n187 -> 179 [label=\"0.002\"];\n187 -> 185 [label=\"0.00025\"];\n187 -> 186 [label=\"0.00025\"];\n187 -> 231 [label=\"2:repairLeft\"];\n188 [label=\"188\\n(1,true,1,false,true,false,true,false,false,false,false)\"];\n188 -> 88 [label=\"0.002\"];\n188 -> 180 [label=\"0.002\"];\n188 -> 184 [label=\"0.0002\"];\n188 -> 232 [label=\"2:repairLeft\"];\n189 [label=\"189\\n(1,true,1,false,true,false,true,false,false,false,true)\"];\n189 -> 89 [label=\"0.002\"];\n189 -> 181 [label=\"0.002\"];\n189 -> 185 [label=\"0.0002\"];\n189 -> 188 [label=\"0.00025\"];\n189 -> 233 [label=\"2:repairLeft\"];\n190 [label=\"190\\n(1,true,1,false,true,false,true,false,true,false,false)\"];\n190 -> 90 [label=\"0.002\"];\n190 -> 182 [label=\"0.002\"];\n190 -> 186 [label=\"0.0002\"];\n190 -> 188 [label=\"0.00025\"];\n190 -> 234 [label=\"2:repairLeft\"];\n191 [label=\"191\\n(1,true,1,false,true,false,true,false,true,false,true)\"];\n191 -> 91 [label=\"0.002\"];\n191 -> 183 [label=\"0.002\"];\n191 -> 187 [label=\"0.0002\"];\n191 -> 189 [label=\"0.00025\"];\n191 -> 190 [label=\"0.00025\"];\n191 -> 235 [label=\"2:repairLeft\"];\n192 [label=\"192\\n(1,true,2,false,true,false,false,false,false,false,false)\"];\n192 -> 92 [label=\"0.002\"];\n192 -> 184 [label=\"0.004\"];\n192 -> 256 [label=\"2:repairLeft\"];\n193 [label=\"193\\n(1,true,2,false,true,false,false,false,false,false,true)\"];\n193 -> 93 [label=\"0.002\"];\n193 -> 185 [label=\"0.004\"];\n193 -> 192 [label=\"0.00025\"];\n193 -> 257 [label=\"2:repairLeft\"];\n194 [label=\"194\\n(1,true,2,false,true,false,false,false,true,false,false)\"];\n194 -> 94 [label=\"0.002\"];\n194 -> 186 [label=\"0.004\"];\n194 -> 192 [label=\"0.00025\"];\n194 -> 258 [label=\"2:repairLeft\"];\n195 [label=\"195\\n(1,true,2,false,true,false,false,false,true,false,true)\"];\n195 -> 95 [label=\"0.002\"];\n195 -> 187 [label=\"0.004\"];\n195 -> 193 [label=\"0.00025\"];\n195 -> 194 [label=\"0.00025\"];\n195 -> 259 [label=\"2:repairLeft\"];\n196 [label=\"196\\n(1,true,2,false,true,false,true,false,false,false,false)\"];\n196 -> 96 [label=\"0.002\"];\n196 -> 188 [label=\"0.004\"];\n196 -> 192 [label=\"0.0002\"];\n196 -> 260 [label=\"2:repairLeft\"];\n197 [label=\"197\\n(1,true,2,false,true,false,true,false,false,false,true)\"];\n197 -> 97 [label=\"0.002\"];\n197 -> 189 [label=\"0.004\"];\n197 -> 193 [label=\"0.0002\"];\n197 -> 196 [label=\"0.00025\"];\n197 -> 261 [label=\"2:repairLeft\"];\n198 [label=\"198\\n(1,true,2,false,true,false,true,false,true,false,false)\"];\n198 -> 98 [label=\"0.002\"];\n198 -> 190 [label=\"0.004\"];\n198 -> 194 [label=\"0.0002\"];\n198 -> 196 [label=\"0.00025\"];\n198 -> 262 [label=\"2:repairLeft\"];\n199 [label=\"199\\n(1,true,2,false,true,false,true,false,true,false,true)\"];\n199 -> 99 [label=\"0.002\"];\n199 -> 191 [label=\"0.004\"];\n199 -> 195 [label=\"0.0002\"];\n199 -> 197 [label=\"0.00025\"];\n199 -> 198 [label=\"0.00025\"];\n199 -> 263 [label=\"2:repairLeft\"];\n200 [label=\"200\\n(2,false,0,false,false,false,false,false,false,false,false)\"];\n200 -> 100 [label=\"0.004\"];\n200 -> 208 [label=\"10:startToRight\"];\n200 -> 210 [label=\"10:startToLeft\"];\n200 -> 216 [label=\"10:startLine\"];\n200 -> 220 [label=\"10:startRight\"];\n201 [label=\"201\\n(2,false,0,false,false,false,false,false,false,false,true)\"];\n201 -> 101 [label=\"0.004\"];\n201 -> 200 [label=\"0.00025\"];\n201 -> 211 [label=\"10:startToLeft\"];\n201 -> 217 [label=\"10:startLine\"];\n201 -> 221 [label=\"10:startRight\"];\n202 [label=\"202\\n(2,false,0,false,false,false,false,false,true,false,false)\"];\n202 -> 102 [label=\"0.004\"];\n202 -> 200 [label=\"0.00025\"];\n202 -> 209 [label=\"10:startToRight\"];\n202 -> 218 [label=\"10:startLine\"];\n202 -> 222 [label=\"10:startRight\"];\n203 [label=\"203\\n(2,false,0,false,false,false,false,false,true,false,true)\"];\n203 -> 103 [label=\"0.004\"];\n203 -> 201 [label=\"0.00025\"];\n203 -> 202 [label=\"0.00025\"];\n203 -> 219 [label=\"10:startLine\"];\n203 -> 223 [label=\"10:startRight\"];\n204 [label=\"204\\n(2,false,0,false,false,false,true,false,false,false,false)\"];\n204 -> 104 [label=\"0.004\"];\n204 -> 200 [label=\"0.0002\"];\n204 -> 212 [label=\"10:startToRight\"];\n204 -> 214 [label=\"10:startToLeft\"];\n204 -> 224 [label=\"10:startRight\"];\n205 [label=\"205\\n(2,false,0,false,false,false,true,false,false,false,true)\"];\n205 -> 105 [label=\"0.004\"];\n205 -> 201 [label=\"0.0002\"];\n205 -> 204 [label=\"0.00025\"];\n205 -> 215 [label=\"10:startToLeft\"];\n205 -> 225 [label=\"10:startRight\"];\n206 [label=\"206\\n(2,false,0,false,false,false,true,false,true,false,false)\"];\n206 -> 106 [label=\"0.004\"];\n206 -> 202 [label=\"0.0002\"];\n206 -> 204 [label=\"0.00025\"];\n206 -> 213 [label=\"10:startToRight\"];\n206 -> 226 [label=\"10:startRight\"];\n207 [label=\"207\\n(2,false,0,false,false,false,true,false,true,false,true)\"];\n207 -> 107 [label=\"0.004\"];\n207 -> 203 [label=\"0.0002\"];\n207 -> 205 [label=\"0.00025\"];\n207 -> 206 [label=\"0.00025\"];\n207 -> 227 [label=\"10:startRight\"];\n208 [label=\"208\\n(2,false,0,false,true,false,false,false,false,true,false)\"];\n208 -> 108 [label=\"0.004\"];\n208 -> 201 [label=\"0.25:repairToRight\"];\n209 [label=\"209\\n(2,false,0,false,true,false,false,false,true,true,false)\"];\n209 -> 109 [label=\"0.004\"];\n209 -> 203 [label=\"0.25:repairToRight\"];\n209 -> 208 [label=\"0.00025\"];\n210 [label=\"210\\n(2,false,0,false,true,false,false,true,false,false,false)\"];\n210 -> 110 [label=\"0.004\"];\n210 -> 202 [label=\"0.25:repairToLeft\"];\n211 [label=\"211\\n(2,false,0,false,true,false,false,true,false,false,true)\"];\n211 -> 111 [label=\"0.004\"];\n211 -> 203 [label=\"0.25:repairToLeft\"];\n211 -> 210 [label=\"0.00025\"];\n212 [label=\"212\\n(2,false,0,false,true,false,true,false,false,true,false)\"];\n212 -> 112 [label=\"0.004\"];\n212 -> 205 [label=\"0.25:repairToRight\"];\n212 -> 208 [label=\"0.0002\"];\n213 [label=\"213\\n(2,false,0,false,true,false,true,false,true,true,false)\"];\n213 -> 113 [label=\"0.004\"];\n213 -> 207 [label=\"0.25:repairToRight\"];\n213 -> 209 [label=\"0.0002\"];\n213 -> 212 [label=\"0.00025\"];\n214 [label=\"214\\n(2,false,0,false,true,false,true,true,false,false,false)\"];\n214 -> 114 [label=\"0.004\"];\n214 -> 206 [label=\"0.25:repairToLeft\"];\n214 -> 210 [label=\"0.0002\"];\n215 [label=\"215\\n(2,false,0,false,true,false,true,true,false,false,true)\"];\n215 -> 115 [label=\"0.004\"];\n215 -> 207 [label=\"0.25:repairToLeft\"];\n215 -> 211 [label=\"0.0002\"];\n215 -> 214 [label=\"0.00025\"];\n216 [label=\"216\\n(2,false,0,false,true,true,false,false,false,false,false)\"];\n216 -> 116 [label=\"0.004\"];\n216 -> 204 [label=\"0.125:repairLine\"];\n217 [label=\"217\\n(2,false,0,false,true,true,false,false,false,false,true)\"];\n217 -> 117 [label=\"0.004\"];\n217 -> 205 [label=\"0.125:repairLine\"];\n217 -> 216 [label=\"0.00025\"];\n218 [label=\"218\\n(2,false,0,false,true,true,false,false,true,false,false)\"];\n218 -> 118 [label=\"0.004\"];\n218 -> 206 [label=\"0.125:repairLine\"];\n218 -> 216 [label=\"0.00025\"];\n219 [label=\"219\\n(2,false,0,false,true,true,false,false,true,false,true)\"];\n219 -> 119 [label=\"0.004\"];\n219 -> 207 [label=\"0.125:repairLine\"];\n219 -> 217 [label=\"0.00025\"];\n219 -> 218 [label=\"0.00025\"];\n220 [label=\"220\\n(2,false,0,true,true,false,false,false,false,false,false)\"];\n220 -> 120 [label=\"0.004\"];\n220 -> 228 [label=\"2:repairRight\"];\n221 [label=\"221\\n(2,false,0,true,true,false,false,false,false,false,true)\"];\n221 -> 121 [label=\"0.004\"];\n221 -> 220 [label=\"0.00025\"];\n221 -> 229 [label=\"2:repairRight\"];\n222 [label=\"222\\n(2,false,0,true,true,false,false,false,true,false,false)\"];\n222 -> 122 [label=\"0.004\"];\n222 -> 220 [label=\"0.00025\"];\n222 -> 230 [label=\"2:repairRight\"];\n223 [label=\"223\\n(2,false,0,true,true,false,false,false,true,false,true)\"];\n223 -> 123 [label=\"0.004\"];\n223 -> 221 [label=\"0.00025\"];\n223 -> 222 [label=\"0.00025\"];\n223 -> 231 [label=\"2:repairRight\"];\n224 [label=\"224\\n(2,false,0,true,true,false,true,false,false,false,false)\"];\n224 -> 124 [label=\"0.004\"];\n224 -> 220 [label=\"0.0002\"];\n224 -> 232 [label=\"2:repairRight\"];\n225 [label=\"225\\n(2,false,0,true,true,false,true,false,false,false,true)\"];\n225 -> 125 [label=\"0.004\"];\n225 -> 221 [label=\"0.0002\"];\n225 -> 224 [label=\"0.00025\"];\n225 -> 233 [label=\"2:repairRight\"];\n226 [label=\"226\\n(2,false,0,true,true,false,true,false,true,false,false)\"];\n226 -> 126 [label=\"0.004\"];\n226 -> 222 [label=\"0.0002\"];\n226 -> 224 [label=\"0.00025\"];\n226 -> 234 [label=\"2:repairRight\"];\n227 [label=\"227\\n(2,false,0,true,true,false,true,false,true,false,true)\"];\n227 -> 127 [label=\"0.004\"];\n227 -> 223 [label=\"0.0002\"];\n227 -> 225 [label=\"0.00025\"];\n227 -> 226 [label=\"0.00025\"];\n227 -> 235 [label=\"2:repairRight\"];\n228 [label=\"228\\n(2,false,1,false,false,false,false,false,false,false,false)\"];\n228 -> 128 [label=\"0.004\"];\n228 -> 200 [label=\"0.002\"];\n228 -> 236 [label=\"10:startToRight\"];\n228 -> 238 [label=\"10:startToLeft\"];\n228 -> 244 [label=\"10:startLine\"];\n228 -> 248 [label=\"10:startRight\"];\n229 [label=\"229\\n(2,false,1,false,false,false,false,false,false,false,true)\"];\n229 -> 129 [label=\"0.004\"];\n229 -> 201 [label=\"0.002\"];\n229 -> 228 [label=\"0.00025\"];\n229 -> 239 [label=\"10:startToLeft\"];\n229 -> 245 [label=\"10:startLine\"];\n229 -> 249 [label=\"10:startRight\"];\n230 [label=\"230\\n(2,false,1,false,false,false,false,false,true,false,false)\"];\n230 -> 130 [label=\"0.004\"];\n230 -> 202 [label=\"0.002\"];\n230 -> 228 [label=\"0.00025\"];\n230 -> 237 [label=\"10:startToRight\"];\n230 -> 246 [label=\"10:startLine\"];\n230 -> 250 [label=\"10:startRight\"];\n231 [label=\"231\\n(2,false,1,false,false,false,false,false,true,false,true)\"];\n231 -> 131 [label=\"0.004\"];\n231 -> 203 [label=\"0.002\"];\n231 -> 229 [label=\"0.00025\"];\n231 -> 230 [label=\"0.00025\"];\n231 -> 247 [label=\"10:startLine\"];\n231 -> 251 [label=\"10:startRight\"];\n232 [label=\"232\\n(2,false,1,false,false,false,true,false,false,false,false)\"];\n232 -> 132 [label=\"0.004\"];\n232 -> 204 [label=\"0.002\"];\n232 -> 228 [label=\"0.0002\"];\n232 -> 240 [label=\"10:startToRight\"];\n232 -> 242 [label=\"10:startToLeft\"];\n232 -> 252 [label=\"10:startRight\"];\n233 [label=\"233\\n(2,false,1,false,false,false,true,false,false,false,true)\"];\n233 -> 133 [label=\"0.004\"];\n233 -> 205 [label=\"0.002\"];\n233 -> 229 [label=\"0.0002\"];\n233 -> 232 [label=\"0.00025\"];\n233 -> 243 [label=\"10:startToLeft\"];\n233 -> 253 [label=\"10:startRight\"];\n234 [label=\"234\\n(2,false,1,false,false,false,true,false,true,false,false)\"];\n234 -> 134 [label=\"0.004\"];\n234 -> 206 [label=\"0.002\"];\n234 -> 230 [label=\"0.0002\"];\n234 -> 232 [label=\"0.00025\"];\n234 -> 241 [label=\"10:startToRight\"];\n234 -> 254 [label=\"10:startRight\"];\n235 [label=\"235\\n(2,false,1,false,false,false,true,false,true,false,true)\"];\n235 -> 135 [label=\"0.004\"];\n235 -> 207 [label=\"0.002\"];\n235 -> 231 [label=\"0.0002\"];\n235 -> 233 [label=\"0.00025\"];\n235 -> 234 [label=\"0.00025\"];\n235 -> 255 [label=\"10:startRight\"];\n236 [label=\"236\\n(2,false,1,false,true,false,false,false,false,true,false)\"];\n236 -> 136 [label=\"0.004\"];\n236 -> 208 [label=\"0.002\"];\n236 -> 229 [label=\"0.25:repairToRight\"];\n237 [label=\"237\\n(2,false,1,false,true,false,false,false,true,true,false)\"];\n237 -> 137 [label=\"0.004\"];\n237 -> 209 [label=\"0.002\"];\n237 -> 231 [label=\"0.25:repairToRight\"];\n237 -> 236 [label=\"0.00025\"];\n238 [label=\"238\\n(2,false,1,false,true,false,false,true,false,false,false)\"];\n238 -> 138 [label=\"0.004\"];\n238 -> 210 [label=\"0.002\"];\n238 -> 230 [label=\"0.25:repairToLeft\"];\n239 [label=\"239\\n(2,false,1,false,true,false,false,true,false,false,true)\"];\n239 -> 139 [label=\"0.004\"];\n239 -> 211 [label=\"0.002\"];\n239 -> 231 [label=\"0.25:repairToLeft\"];\n239 -> 238 [label=\"0.00025\"];\n240 [label=\"240\\n(2,false,1,false,true,false,true,false,false,true,false)\"];\n240 -> 140 [label=\"0.004\"];\n240 -> 212 [label=\"0.002\"];\n240 -> 233 [label=\"0.25:repairToRight\"];\n240 -> 236 [label=\"0.0002\"];\n241 [label=\"241\\n(2,false,1,false,true,false,true,false,true,true,false)\"];\n241 -> 141 [label=\"0.004\"];\n241 -> 213 [label=\"0.002\"];\n241 -> 235 [label=\"0.25:repairToRight\"];\n241 -> 237 [label=\"0.0002\"];\n241 -> 240 [label=\"0.00025\"];\n242 [label=\"242\\n(2,false,1,false,true,false,true,true,false,false,false)\"];\n242 -> 142 [label=\"0.004\"];\n242 -> 214 [label=\"0.002\"];\n242 -> 234 [label=\"0.25:repairToLeft\"];\n242 -> 238 [label=\"0.0002\"];\n243 [label=\"243\\n(2,false,1,false,true,false,true,true,false,false,true)\"];\n243 -> 143 [label=\"0.004\"];\n243 -> 215 [label=\"0.002\"];\n243 -> 235 [label=\"0.25:repairToLeft\"];\n243 -> 239 [label=\"0.0002\"];\n243 -> 242 [label=\"0.00025\"];\n244 [label=\"244\\n(2,false,1,false,true,true,false,false,false,false,false)\"];\n244 -> 144 [label=\"0.004\"];\n244 -> 216 [label=\"0.002\"];\n244 -> 232 [label=\"0.125:repairLine\"];\n245 [label=\"245\\n(2,false,1,false,true,true,false,false,false,false,true)\"];\n245 -> 145 [label=\"0.004\"];\n245 -> 217 [label=\"0.002\"];\n245 -> 233 [label=\"0.125:repairLine\"];\n245 -> 244 [label=\"0.00025\"];\n246 [label=\"246\\n(2,false,1,false,true,true,false,false,true,false,false)\"];\n246 -> 146 [label=\"0.004\"];\n246 -> 218 [label=\"0.002\"];\n246 -> 234 [label=\"0.125:repairLine\"];\n246 -> 244 [label=\"0.00025\"];\n247 [label=\"247\\n(2,false,1,false,true,true,false,false,true,false,true)\"];\n247 -> 147 [label=\"0.004\"];\n247 -> 219 [label=\"0.002\"];\n247 -> 235 [label=\"0.125:repairLine\"];\n247 -> 245 [label=\"0.00025\"];\n247 -> 246 [label=\"0.00025\"];\n248 [label=\"248\\n(2,false,1,true,true,false,false,false,false,false,false)\"];\n248 -> 148 [label=\"0.004\"];\n248 -> 220 [label=\"0.002\"];\n248 -> 256 [label=\"2:repairRight\"];\n249 [label=\"249\\n(2,false,1,true,true,false,false,false,false,false,true)\"];\n249 -> 149 [label=\"0.004\"];\n249 -> 221 [label=\"0.002\"];\n249 -> 248 [label=\"0.00025\"];\n249 -> 257 [label=\"2:repairRight\"];\n250 [label=\"250\\n(2,false,1,true,true,false,false,false,true,false,false)\"];\n250 -> 150 [label=\"0.004\"];\n250 -> 222 [label=\"0.002\"];\n250 -> 248 [label=\"0.00025\"];\n250 -> 258 [label=\"2:repairRight\"];\n251 [label=\"251\\n(2,false,1,true,true,false,false,false,true,false,true)\"];\n251 -> 151 [label=\"0.004\"];\n251 -> 223 [label=\"0.002\"];\n251 -> 249 [label=\"0.00025\"];\n251 -> 250 [label=\"0.00025\"];\n251 -> 259 [label=\"2:repairRight\"];\n252 [label=\"252\\n(2,false,1,true,true,false,true,false,false,false,false)\"];\n252 -> 152 [label=\"0.004\"];\n252 -> 224 [label=\"0.002\"];\n252 -> 248 [label=\"0.0002\"];\n252 -> 260 [label=\"2:repairRight\"];\n253 [label=\"253\\n(2,false,1,true,true,false,true,false,false,false,true)\"];\n253 -> 153 [label=\"0.004\"];\n253 -> 225 [label=\"0.002\"];\n253 -> 249 [label=\"0.0002\"];\n253 -> 252 [label=\"0.00025\"];\n253 -> 261 [label=\"2:repairRight\"];\n254 [label=\"254\\n(2,false,1,true,true,false,true,false,true,false,false)\"];\n254 -> 154 [label=\"0.004\"];\n254 -> 226 [label=\"0.002\"];\n254 -> 250 [label=\"0.0002\"];\n254 -> 252 [label=\"0.00025\"];\n254 -> 262 [label=\"2:repairRight\"];\n255 [label=\"255\\n(2,false,1,true,true,false,true,false,true,false,true)\"];\n255 -> 155 [label=\"0.004\"];\n255 -> 227 [label=\"0.002\"];\n255 -> 251 [label=\"0.0002\"];\n255 -> 253 [label=\"0.00025\"];\n255 -> 254 [label=\"0.00025\"];\n255 -> 263 [label=\"2:repairRight\"];\n256 [label=\"256\\n(2,false,2,false,false,false,false,false,false,false,false)\"];\n256 -> 156 [label=\"0.004\"];\n256 -> 228 [label=\"0.004\"];\n256 -> 264 [label=\"10:startToRight\"];\n256 -> 266 [label=\"10:startToLeft\"];\n256 -> 272 [label=\"10:startLine\"];\n257 [label=\"257\\n(2,false,2,false,false,false,false,false,false,false,true)\"];\n257 -> 157 [label=\"0.004\"];\n257 -> 229 [label=\"0.004\"];\n257 -> 256 [label=\"0.00025\"];\n257 -> 267 [label=\"10:startToLeft\"];\n257 -> 273 [label=\"10:startLine\"];\n258 [label=\"258\\n(2,false,2,false,false,false,false,false,true,false,false)\"];\n258 -> 158 [label=\"0.004\"];\n258 -> 230 [label=\"0.004\"];\n258 -> 256 [label=\"0.00025\"];\n258 -> 265 [label=\"10:startToRight\"];\n258 -> 274 [label=\"10:startLine\"];\n259 [label=\"259\\n(2,false,2,false,false,false,false,false,true,false,true)\"];\n259 -> 159 [label=\"0.004\"];\n259 -> 231 [label=\"0.004\"];\n259 -> 257 [label=\"0.00025\"];\n259 -> 258 [label=\"0.00025\"];\n259 -> 275 [label=\"10:startLine\"];\n260 [label=\"260\\n(2,false,2,false,false,false,true,false,false,false,false)\"];\n260 -> 160 [label=\"0.004\"];\n260 -> 232 [label=\"0.004\"];\n260 -> 256 [label=\"0.0002\"];\n260 -> 268 [label=\"10:startToRight\"];\n260 -> 270 [label=\"10:startToLeft\"];\n261 [label=\"261\\n(2,false,2,false,false,false,true,false,false,false,true)\"];\n261 -> 161 [label=\"0.004\"];\n261 -> 233 [label=\"0.004\"];\n261 -> 257 [label=\"0.0002\"];\n261 -> 260 [label=\"0.00025\"];\n261 -> 271 [label=\"10:startToLeft\"];\n262 [label=\"262\\n(2,false,2,false,false,false,true,false,true,false,false)\"];\n262 -> 162 [label=\"0.004\"];\n262 -> 234 [label=\"0.004\"];\n262 -> 258 [label=\"0.0002\"];\n262 -> 260 [label=\"0.00025\"];\n262 -> 269 [label=\"10:startToRight\"];\n263 [label=\"263\\n(2,false,2,false,false,false,true,false,true,false,true)\"];\n263 -> 163 [label=\"0.004\"];\n263 -> 235 [label=\"0.004\"];\n263 -> 259 [label=\"0.0002\"];\n263 -> 261 [label=\"0.00025\"];\n263 -> 262 [label=\"0.00025\"];\n264 [label=\"264\\n(2,false,2,false,true,false,false,false,false,true,false)\"];\n264 -> 164 [label=\"0.004\"];\n264 -> 236 [label=\"0.004\"];\n264 -> 257 [label=\"0.25:repairToRight\"];\n265 [label=\"265\\n(2,false,2,false,true,false,false,false,true,true,false)\"];\n265 -> 165 [label=\"0.004\"];\n265 -> 237 [label=\"0.004\"];\n265 -> 259 [label=\"0.25:repairToRight\"];\n265 -> 264 [label=\"0.00025\"];\n266 [label=\"266\\n(2,false,2,false,true,false,false,true,false,false,false)\"];\n266 -> 166 [label=\"0.004\"];\n266 -> 238 [label=\"0.004\"];\n266 -> 258 [label=\"0.25:repairToLeft\"];\n267 [label=\"267\\n(2,false,2,false,true,false,false,true,false,false,true)\"];\n267 -> 167 [label=\"0.004\"];\n267 -> 239 [label=\"0.004\"];\n267 -> 259 [label=\"0.25:repairToLeft\"];\n267 -> 266 [label=\"0.00025\"];\n268 [label=\"268\\n(2,false,2,false,true,false,true,false,false,true,false)\"];\n268 -> 168 [label=\"0.004\"];\n268 -> 240 [label=\"0.004\"];\n268 -> 261 [label=\"0.25:repairToRight\"];\n268 -> 264 [label=\"0.0002\"];\n269 [label=\"269\\n(2,false,2,false,true,false,true,false,true,true,false)\"];\n269 -> 169 [label=\"0.004\"];\n269 -> 241 [label=\"0.004\"];\n269 -> 263 [label=\"0.25:repairToRight\"];\n269 -> 265 [label=\"0.0002\"];\n269 -> 268 [label=\"0.00025\"];\n270 [label=\"270\\n(2,false,2,false,true,false,true,true,false,false,false)\"];\n270 -> 170 [label=\"0.004\"];\n270 -> 242 [label=\"0.004\"];\n270 -> 262 [label=\"0.25:repairToLeft\"];\n270 -> 266 [label=\"0.0002\"];\n271 [label=\"271\\n(2,false,2,false,true,false,true,true,false,false,true)\"];\n271 -> 171 [label=\"0.004\"];\n271 -> 243 [label=\"0.004\"];\n271 -> 263 [label=\"0.25:repairToLeft\"];\n271 -> 267 [label=\"0.0002\"];\n271 -> 270 [label=\"0.00025\"];\n272 [label=\"272\\n(2,false,2,false,true,true,false,false,false,false,false)\"];\n272 -> 172 [label=\"0.004\"];\n272 -> 244 [label=\"0.004\"];\n272 -> 260 [label=\"0.125:repairLine\"];\n273 [label=\"273\\n(2,false,2,false,true,true,false,false,false,false,true)\"];\n273 -> 173 [label=\"0.004\"];\n273 -> 245 [label=\"0.004\"];\n273 -> 261 [label=\"0.125:repairLine\"];\n273 -> 272 [label=\"0.00025\"];\n274 [label=\"274\\n(2,false,2,false,true,true,false,false,true,false,false)\"];\n274 -> 174 [label=\"0.004\"];\n274 -> 246 [label=\"0.004\"];\n274 -> 262 [label=\"0.125:repairLine\"];\n274 -> 272 [label=\"0.00025\"];\n275 [label=\"275\\n(2,false,2,false,true,true,false,false,true,false,true)\"];\n275 -> 175 [label=\"0.004\"];\n275 -> 247 [label=\"0.004\"];\n275 -> 263 [label=\"0.125:repairLine\"];\n275 -> 273 [label=\"0.00025\"];\n275 -> 274 [label=\"0.00025\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/dice.pm",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/dice.pm.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\"];\n0 -> 1 [label=\"0.5\"];\n0 -> 2 [label=\"0.5\"];\n1 [label=\"1\"];\n1 -> 3 [label=\"0.5\"];\n1 -> 4 [label=\"0.5\"];\n2 [label=\"2\"];\n2 -> 5 [label=\"0.5\"];\n2 -> 6 [label=\"0.5\"];\n3 [label=\"3\"];\n3 -> 1 [label=\"0.5\"];\n3 -> 7 [label=\"0.5\"];\n4 [label=\"4\"];\n4 -> 8 [label=\"0.5\"];\n4 -> 9 [label=\"0.5\"];\n5 [label=\"5\"];\n5 -> 10 [label=\"0.5\"];\n5 -> 11 [label=\"0.5\"];\n6 [label=\"6\"];\n6 -> 2 [label=\"0.5\"];\n6 -> 12 [label=\"0.5\"];\n7 [label=\"7\"];\n7 -> 7 [label=\"1\"];\n8 [label=\"8\"];\n8 -> 8 [label=\"1\"];\n9 [label=\"9\"];\n9 -> 9 [label=\"1\"];\n10 [label=\"10\"];\n10 -> 10 [label=\"1\"];\n11 [label=\"11\"];\n11 -> 11 [label=\"1\"];\n12 [label=\"12\"];\n12 -> 12 [label=\"1\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/dice.pm.dot.auto",
    "content": "-exporttransdot dice.pm.dot -ex\n-exporttransdotstates dice.pm.sta.dot -ex\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/dice.pm.sta.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\\n(0,0)\"];\n0 -> 1 [label=\"0.5\"];\n0 -> 2 [label=\"0.5\"];\n1 [label=\"1\\n(1,0)\"];\n1 -> 3 [label=\"0.5\"];\n1 -> 4 [label=\"0.5\"];\n2 [label=\"2\\n(2,0)\"];\n2 -> 5 [label=\"0.5\"];\n2 -> 6 [label=\"0.5\"];\n3 [label=\"3\\n(3,0)\"];\n3 -> 1 [label=\"0.5\"];\n3 -> 7 [label=\"0.5\"];\n4 [label=\"4\\n(4,0)\"];\n4 -> 8 [label=\"0.5\"];\n4 -> 9 [label=\"0.5\"];\n5 [label=\"5\\n(5,0)\"];\n5 -> 10 [label=\"0.5\"];\n5 -> 11 [label=\"0.5\"];\n6 [label=\"6\\n(6,0)\"];\n6 -> 2 [label=\"0.5\"];\n6 -> 12 [label=\"0.5\"];\n7 [label=\"7\\n(7,1)\"];\n7 -> 7 [label=\"1\"];\n8 [label=\"8\\n(7,2)\"];\n8 -> 8 [label=\"1\"];\n9 [label=\"9\\n(7,3)\"];\n9 -> 9 [label=\"1\"];\n10 [label=\"10\\n(7,4)\"];\n10 -> 10 [label=\"1\"];\n11 [label=\"11\\n(7,5)\"];\n11 -> 11 [label=\"1\"];\n12 [label=\"12\\n(7,6)\"];\n12 -> 12 [label=\"1\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/dtmc_pctl.prism",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> [0.5,0.5]:(s'=1) + [0.5,0.5]:(s'=3);\r\n[] s=1 -> [0.5,0.5]:(s'=0) + [0.25,0.25]:(s'=2) + [0.25,0.25]:(s'=4);\r\n[r] s=2 -> [1,1]:(s'=5);\r\n[] s=3 -> [1,1]:(s'=3);\r\n[] s=4 -> [1,1]:(s'=4);\r\n[] s=5 -> [1,1]:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n\r\nrewards \"r\"\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/dtmc_pctl.prism.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\"];\n0 -> 1 [label=\"[0.5,0.5]\"];\n0 -> 3 [label=\"[0.5,0.5]\"];\n1 [label=\"1\"];\n1 -> 0 [label=\"[0.5,0.5]\"];\n1 -> 2 [label=\"[0.25,0.25]\"];\n1 -> 4 [label=\"[0.25,0.25]\"];\n2 [label=\"2\"];\n2 -> 5 [label=\"[1,1]:r\"];\n3 [label=\"3\"];\n3 -> 3 [label=\"[1,1]\"];\n4 [label=\"4\"];\n4 -> 4 [label=\"[1,1]\"];\n5 [label=\"5\"];\n5 -> 2 [label=\"[1,1]\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/dtmc_pctl.prism.dot.auto",
    "content": "-exporttransdot dtmc_pctl.prism.dot -ex\n-exporttransdotstates dtmc_pctl.prism.sta.dot -ex\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/dtmc_pctl.prism.sta.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\\n(0)\"];\n0 -> 1 [label=\"[0.5,0.5]\"];\n0 -> 3 [label=\"[0.5,0.5]\"];\n1 [label=\"1\\n(1)\"];\n1 -> 0 [label=\"[0.5,0.5]\"];\n1 -> 2 [label=\"[0.25,0.25]\"];\n1 -> 4 [label=\"[0.25,0.25]\"];\n2 [label=\"2\\n(2)\"];\n2 -> 5 [label=\"[1,1]:r\"];\n3 [label=\"3\\n(3)\"];\n3 -> 3 [label=\"[1,1]\"];\n4 [label=\"4\\n(4)\"];\n4 -> 4 [label=\"[1,1]\"];\n5 [label=\"5\\n(5)\"];\n5 -> 2 [label=\"[1,1]\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/irobot.prism",
    "content": "mdp\r\n\r\nconst double delta = 0.01;\r\nconst double p = 0.5-delta;\r\nconst double q = 0.5+delta;\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n//[east] s=1 -> 1:(s'=2);\r\n[east] s=1 -> [0.8,0.9]:(s'=2) + [0.1,0.2]:(s'=1);\r\n[south] s=1 -> [p,q]:(s'=4) + [1-q,1-p]:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n\r\nrewards \"energy\"\r\n\ttrue : 0.1;\r\n\ts<2 | s>3 : 2.2;\r\n\t[stuck] true : 3.5;\r\nendrewards\r\n\r\nrewards \"move\"\r\n\t[north] true : 1;\r\n\t[south] true : 1;\r\n\t[east] true : 1;\r\n\t[west] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/irobot.prism.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\"];\n0 -> n0_0  [label=\"0:east\",arrowhead=\"none\"];\nn0_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn0_0 -> 0 [label=\"[0.4,0.4]\"];\nn0_0 -> 1 [label=\"[0.6,0.6]\"];\n0 -> n0_1  [label=\"1:south\",arrowhead=\"none\"];\nn0_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn0_1 -> 1 [label=\"[0.1,0.1]\"];\nn0_1 -> 3 [label=\"[0.8,0.8]\"];\nn0_1 -> 4 [label=\"[0.1,0.1]\"];\n1 [label=\"1\"];\n1 -> n1_0  [label=\"0:east\",arrowhead=\"none\"];\nn1_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn1_0 -> 1 [label=\"[0.1,0.2]\"];\nn1_0 -> 2 [label=\"[0.8,0.9]\"];\n1 -> n1_1  [label=\"1:south\",arrowhead=\"none\"];\nn1_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn1_1 -> 2 [label=\"[0.49,0.51]\"];\nn1_1 -> 4 [label=\"[0.49,0.51]\"];\n2 [label=\"2\"];\n2 -> n2_0  [label=\"0:stuck\",arrowhead=\"none\"];\nn2_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn2_0 -> 2 [label=\"[1,1]\"];\n3 [label=\"3\"];\n3 -> n3_0  [label=\"0:stuck\",arrowhead=\"none\"];\nn3_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn3_0 -> 3 [label=\"[1,1]\"];\n4 [label=\"4\"];\n4 -> n4_0  [label=\"0:east\",arrowhead=\"none\"];\nn4_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn4_0 -> 5 [label=\"[1,1]\"];\n4 -> n4_1  [label=\"1:west\",arrowhead=\"none\"];\nn4_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn4_1 -> 3 [label=\"[0.6,0.6]\"];\nn4_1 -> 4 [label=\"[0.4,0.4]\"];\n5 [label=\"5\"];\n5 -> n5_0  [label=\"0:west\",arrowhead=\"none\"];\nn5_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn5_0 -> 4 [label=\"[1,1]\"];\n5 -> n5_1  [label=\"1:north\",arrowhead=\"none\"];\nn5_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn5_1 -> 2 [label=\"[0.9,0.9]\"];\nn5_1 -> 5 [label=\"[0.1,0.1]\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/irobot.prism.dot.auto",
    "content": "-exporttransdot irobot.prism.dot -ex\n-exporttransdotstates irobot.prism.sta.dot -ex\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/irobot.prism.sta.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\\n(0)\"];\n0 -> n0_0  [label=\"0:east\",arrowhead=\"none\"];\nn0_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn0_0 -> 0 [label=\"[0.4,0.4]\"];\nn0_0 -> 1 [label=\"[0.6,0.6]\"];\n0 -> n0_1  [label=\"1:south\",arrowhead=\"none\"];\nn0_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn0_1 -> 1 [label=\"[0.1,0.1]\"];\nn0_1 -> 3 [label=\"[0.8,0.8]\"];\nn0_1 -> 4 [label=\"[0.1,0.1]\"];\n1 [label=\"1\\n(1)\"];\n1 -> n1_0  [label=\"0:east\",arrowhead=\"none\"];\nn1_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn1_0 -> 1 [label=\"[0.1,0.2]\"];\nn1_0 -> 2 [label=\"[0.8,0.9]\"];\n1 -> n1_1  [label=\"1:south\",arrowhead=\"none\"];\nn1_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn1_1 -> 2 [label=\"[0.49,0.51]\"];\nn1_1 -> 4 [label=\"[0.49,0.51]\"];\n2 [label=\"2\\n(2)\"];\n2 -> n2_0  [label=\"0:stuck\",arrowhead=\"none\"];\nn2_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn2_0 -> 2 [label=\"[1,1]\"];\n3 [label=\"3\\n(3)\"];\n3 -> n3_0  [label=\"0:stuck\",arrowhead=\"none\"];\nn3_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn3_0 -> 3 [label=\"[1,1]\"];\n4 [label=\"4\\n(4)\"];\n4 -> n4_0  [label=\"0:east\",arrowhead=\"none\"];\nn4_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn4_0 -> 5 [label=\"[1,1]\"];\n4 -> n4_1  [label=\"1:west\",arrowhead=\"none\"];\nn4_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn4_1 -> 3 [label=\"[0.6,0.6]\"];\nn4_1 -> 4 [label=\"[0.4,0.4]\"];\n5 [label=\"5\\n(5)\"];\n5 -> n5_0  [label=\"0:west\",arrowhead=\"none\"];\nn5_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn5_0 -> 4 [label=\"[1,1]\"];\n5 -> n5_1  [label=\"1:north\",arrowhead=\"none\"];\nn5_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn5_1 -> 2 [label=\"[0.9,0.9]\"];\nn5_1 -> 5 [label=\"[0.1,0.1]\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/lec9ctl1.prism",
    "content": "// Simple LTS from Lec 9 of Computer-Aided Verification\r\n\r\nmodule M\r\n\r\ns:[0..3];\r\n\r\n[e] s=0 -> (s'=1);\r\n[f] s=0 -> (s'=2);\r\n[e] s=1 -> (s'=1);\r\n[f] s=1 -> (s'=3);\r\n[g] s=2 -> (s'=1);\r\n[g] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = s=0 | s=1;\r\nlabel \"b\" = s=0 | s=3;\r\n\r\nrewards \"r1\"\r\n\ts<2 : s;\r\nendrewards\r\n\r\nrewards \"r2\"\r\n\t[] s>=2 : s;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/lec9ctl1.prism.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\"];\n0 -> 1 [label=\"0:e\"];\n0 -> 2 [label=\"1:f\"];\n1 [label=\"1\"];\n1 -> 1 [label=\"0:e\"];\n1 -> 3 [label=\"1:f\"];\n2 [label=\"2\"];\n2 -> 1 [label=\"0:g\"];\n3 [label=\"3\"];\n3 -> 3 [label=\"0:g\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/lec9ctl1.prism.dot.auto",
    "content": "-exporttransdot lec9ctl1.prism.dot -ex\n-exporttransdotstates lec9ctl1.prism.sta.dot -ex\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/lec9ctl1.prism.sta.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\\n(0)\"];\n0 -> 1 [label=\"0:e\"];\n0 -> 2 [label=\"1:f\"];\n1 [label=\"1\\n(1)\"];\n1 -> 1 [label=\"0:e\"];\n1 -> 3 [label=\"1:f\"];\n2 [label=\"2\\n(2)\"];\n2 -> 1 [label=\"0:g\"];\n3 [label=\"3\\n(3)\"];\n3 -> 3 [label=\"0:g\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/robot.prism",
    "content": "mdp\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n\r\nrewards \"energy\"\r\n\ttrue : 0.1;\r\n\ts<2 | s>3 : 2.2;\r\n\t[stuck] true : 3.5;\r\nendrewards\r\n\r\nrewards \"move\"\r\n\t[north] true : 1;\r\n\t[south] true : 1;\r\n\t[east] true : 1;\r\n\t[west] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/robot.prism.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\"];\n0 -> n0_0  [label=\"0:east\",arrowhead=\"none\"];\nn0_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn0_0 -> 0 [label=\"0.4\"];\nn0_0 -> 1 [label=\"0.6\"];\n0 -> n0_1  [label=\"1:south\",arrowhead=\"none\"];\nn0_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn0_1 -> 1 [label=\"0.1\"];\nn0_1 -> 3 [label=\"0.8\"];\nn0_1 -> 4 [label=\"0.1\"];\n1 [label=\"1\"];\n1 -> n1_0  [label=\"0:east\",arrowhead=\"none\"];\nn1_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn1_0 -> 2 [label=\"1\"];\n1 -> n1_1  [label=\"1:south\",arrowhead=\"none\"];\nn1_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn1_1 -> 2 [label=\"0.5\"];\nn1_1 -> 4 [label=\"0.5\"];\n2 [label=\"2\"];\n2 -> n2_0  [label=\"0:stuck\",arrowhead=\"none\"];\nn2_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn2_0 -> 2 [label=\"1\"];\n3 [label=\"3\"];\n3 -> n3_0  [label=\"0:stuck\",arrowhead=\"none\"];\nn3_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn3_0 -> 3 [label=\"1\"];\n4 [label=\"4\"];\n4 -> n4_0  [label=\"0:east\",arrowhead=\"none\"];\nn4_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn4_0 -> 5 [label=\"1\"];\n4 -> n4_1  [label=\"1:west\",arrowhead=\"none\"];\nn4_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn4_1 -> 3 [label=\"0.6\"];\nn4_1 -> 4 [label=\"0.4\"];\n5 [label=\"5\"];\n5 -> n5_0  [label=\"0:west\",arrowhead=\"none\"];\nn5_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn5_0 -> 4 [label=\"1\"];\n5 -> n5_1  [label=\"1:north\",arrowhead=\"none\"];\nn5_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn5_1 -> 2 [label=\"0.9\"];\nn5_1 -> 5 [label=\"0.1\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/robot.prism.dot.auto",
    "content": "-exporttransdot robot.prism.dot -ex\n-exporttransdotstates robot.prism.sta.dot -ex\n"
  },
  {
    "path": "prism-tests/functionality/export/dot/robot.prism.sta.dot",
    "content": "digraph M {\nnode [label=\"\",shape=\"box\"];\n0 [label=\"0\\n(0)\"];\n0 -> n0_0  [label=\"0:east\",arrowhead=\"none\"];\nn0_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn0_0 -> 0 [label=\"0.4\"];\nn0_0 -> 1 [label=\"0.6\"];\n0 -> n0_1  [label=\"1:south\",arrowhead=\"none\"];\nn0_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn0_1 -> 1 [label=\"0.1\"];\nn0_1 -> 3 [label=\"0.8\"];\nn0_1 -> 4 [label=\"0.1\"];\n1 [label=\"1\\n(1)\"];\n1 -> n1_0  [label=\"0:east\",arrowhead=\"none\"];\nn1_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn1_0 -> 2 [label=\"1\"];\n1 -> n1_1  [label=\"1:south\",arrowhead=\"none\"];\nn1_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn1_1 -> 2 [label=\"0.5\"];\nn1_1 -> 4 [label=\"0.5\"];\n2 [label=\"2\\n(2)\"];\n2 -> n2_0  [label=\"0:stuck\",arrowhead=\"none\"];\nn2_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn2_0 -> 2 [label=\"1\"];\n3 [label=\"3\\n(3)\"];\n3 -> n3_0  [label=\"0:stuck\",arrowhead=\"none\"];\nn3_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn3_0 -> 3 [label=\"1\"];\n4 [label=\"4\\n(4)\"];\n4 -> n4_0  [label=\"0:east\",arrowhead=\"none\"];\nn4_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn4_0 -> 5 [label=\"1\"];\n4 -> n4_1  [label=\"1:west\",arrowhead=\"none\"];\nn4_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn4_1 -> 3 [label=\"0.6\"];\nn4_1 -> 4 [label=\"0.4\"];\n5 [label=\"5\\n(5)\"];\n5 -> n5_0  [label=\"0:west\",arrowhead=\"none\"];\nn5_0 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn5_0 -> 4 [label=\"1\"];\n5 -> n5_1  [label=\"1:north\",arrowhead=\"none\"];\nn5_1 [ shape=point,width=0.1,height=0.1,label=\"\" ];\nn5_1 -> 2 [label=\"0.9\"];\nn5_1 -> 5 [label=\"0.1\"];\n}\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nlabel \"end\" = s=7;\r\nlabel \"six\" = d=6;\r\n\r\n// Random reward struct: mix of state/transition rewards\r\nrewards \"r\"\r\n\ts=7 : d;\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.2.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"end\" 3=\"six\" 4=\"five\"\n0: 0\n7: 2\n8: 2\n9: 2\n10: 2\n11: 2 4\n12: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.3.lab",
    "content": "0=\"five\"\n11: 0\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.exact.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"end\" 3=\"six\"\n0: 0\n7: 2\n8: 2\n9: 2\n10: 2\n11: 2\n12: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.exact.srew",
    "content": "# Reward structure \"r\"\n# State rewards\n13 6\n7 1\n8 2\n9 3\n10 4\n11 5\n12 6\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.exact.sta",
    "content": "(s,d)\n0:(0,0)\n1:(1,0)\n2:(2,0)\n3:(3,0)\n4:(4,0)\n5:(5,0)\n6:(6,0)\n7:(7,1)\n8:(7,2)\n9:(7,3)\n10:(7,4)\n11:(7,5)\n12:(7,6)\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.exact.tra",
    "content": "13 20\n0 1 1/2\n0 2 1/2\n1 3 1/2\n1 4 1/2\n2 5 1/2\n2 6 1/2\n3 1 1/2\n3 7 1/2\n4 8 1/2\n4 9 1/2\n5 10 1/2\n5 11 1/2\n6 2 1/2\n6 12 1/2\n7 7 1\n8 8 1\n9 9 1\n10 10 1\n11 11 1\n12 12 1\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.exact.trew",
    "content": "# Reward structure \"r\"\n# Transition rewards\n13 14\n0 1 1\n0 2 1\n1 3 1\n1 4 1\n2 5 1\n2 6 1\n3 1 1\n3 7 1\n4 8 1\n4 9 1\n5 10 1\n5 11 1\n6 2 1\n6 12 1\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.exportmodel.auto",
    "content": "# Export all model info in different formats\n\n-exportmodel dice.pm.all\n-exportmodel dice.pm.matlab.all:matlab\n-exportmodel dice.pm.rows.all:rows\n\n# Export model info separately (for a few formats)\n\n-exportmodel dice.pm.tra\n-exportmodel dice.pm.lab\n-exportmodel dice.pm.sta\n-exportmodel dice.pm.srew\n-exportmodel dice.pm.trew\n\n# Export model info - explicit engine\n\n-exportmodel dice.pm.all:actions=false -ex\n-exportmodel dice.pm.tra:actions=false -ex\n-exportmodel dice.pm.sta -ex\n-exportmodel dice.pm.lab -ex\n-exportmodel dice.pm.srew -ex\n-exportmodel dice.pm.trew -ex\n\n# Export model info - exact\n\n-exportmodel dice.pm.exact.all -exact\n\n-exportmodel dice.pm.exact.tra -exact\n-exportmodel dice.pm.exact.srew -exact\n-exportmodel dice.pm.exact.trew -exact\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"end\" 3=\"six\"\n0: 0\n7: 2\n8: 2\n9: 2\n10: 2\n11: 2\n12: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.labels1.props",
    "content": "// Just using labels already in the model file\n\n// RESULT: 1/6\nP=? [ F \"six\" ]\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.labels1.props.args",
    "content": "-exportlabels dice.pm.lab\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.labels2.props",
    "content": "// Additional labels not in the model file\n\nlabel \"five\" = d=5;\n\n// RESULT: 1/6\nP=? [ F \"five\" ]\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.labels2.props.args",
    "content": "-exportlabels dice.pm.lab\n-exportmodel dice.pm.lab\n-exportlabels dice.pm.matlab.lab:matlab\n-exportmodel dice.pm.matlab.lab:matlab\n\n-exportlabels dice.pm.2.lab:proplabels\n-exportmodel dice.pm.2.lab:proplabels\n-exportlabels dice.pm.matlab.2.lab:proplabels,matlab\n-exportmodel dice.pm.matlab.2.lab:proplabels,matlab\n\n-exportproplabels dice.pm.3.lab\n-exportproplabels dice.pm.matlab.3.lab:matlab"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.matlab.2.lab",
    "content": "l_init=sparse(13,1);\nl_deadlock=sparse(13,1);\nl_end=sparse(13,1);\nl_six=sparse(13,1);\nl_five=sparse(13,1);\n\nl_init(1)=1;\nl_end(8)=1;\nl_end(9)=1;\nl_end(10)=1;\nl_end(11)=1;\nl_end(12)=1;\nl_five(12)=1;\nl_end(13)=1;\nl_six(13)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.matlab.3.lab",
    "content": "l_five=sparse(13,1);\n\nl_five(12)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.matlab.lab",
    "content": "l_init=sparse(13,1);\nl_deadlock=sparse(13,1);\nl_end=sparse(13,1);\nl_six=sparse(13,1);\n\nl_init(1)=1;\nl_end(8)=1;\nl_end(9)=1;\nl_end(10)=1;\nl_end(11)=1;\nl_end(12)=1;\nl_end(13)=1;\nl_six(13)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.matlab.srew",
    "content": "c1 = sparse(13,1);\nc1(8)=1;\nc1(9)=2;\nc1(10)=3;\nc1(11)=4;\nc1(12)=5;\nc1(13)=6;\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.matlab.sta",
    "content": "% (s,d)\nstates=[\n0,0\n1,0\n2,0\n3,0\n4,0\n5,0\n6,0\n7,1\n7,2\n7,3\n7,4\n7,5\n7,6\n];\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.matlab.tra",
    "content": "P = sparse(13,13);\nP(1,2)=0.5;\nP(1,3)=0.5;\nP(2,4)=0.5;\nP(2,5)=0.5;\nP(3,6)=0.5;\nP(3,7)=0.5;\nP(4,2)=0.5;\nP(4,8)=0.5;\nP(5,9)=0.5;\nP(5,10)=0.5;\nP(6,11)=0.5;\nP(6,12)=0.5;\nP(7,3)=0.5;\nP(7,13)=0.5;\nP(8,8)=1;\nP(9,9)=1;\nP(10,10)=1;\nP(11,11)=1;\nP(12,12)=1;\nP(13,13)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.matlab.trew",
    "content": "C1 = sparse(13,13);\nC1(1,2)=1;\nC1(1,3)=1;\nC1(2,4)=1;\nC1(2,5)=1;\nC1(3,6)=1;\nC1(3,7)=1;\nC1(4,2)=1;\nC1(4,8)=1;\nC1(5,9)=1;\nC1(5,10)=1;\nC1(6,11)=1;\nC1(6,12)=1;\nC1(7,3)=1;\nC1(7,13)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.rows.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"end\" 3=\"six\"\n0: 0\n7: 2\n8: 2\n9: 2\n10: 2\n11: 2\n12: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.rows.srew",
    "content": "# Reward structure \"r\"\n# State rewards\n13 6\n7 1\n8 2\n9 3\n10 4\n11 5\n12 6\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.rows.sta",
    "content": "(s,d)\n0:(0,0)\n1:(1,0)\n2:(2,0)\n3:(3,0)\n4:(4,0)\n5:(5,0)\n6:(6,0)\n7:(7,1)\n8:(7,2)\n9:(7,3)\n10:(7,4)\n11:(7,5)\n12:(7,6)\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.rows.tra",
    "content": "13 20\n0 0.5:1 0.5:2\n1 0.5:3 0.5:4\n2 0.5:5 0.5:6\n3 0.5:1 0.5:7\n4 0.5:8 0.5:9\n5 0.5:10 0.5:11\n6 0.5:2 0.5:12\n7 1:7\n8 1:8\n9 1:9\n10 1:10\n11 1:11\n12 1:12\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.rows.trew",
    "content": "13 14\n0 1:1 1:2\n1 1:3 1:4\n2 1:5 1:6\n3 1:1 1:7\n4 1:8 1:9\n5 1:10 1:11\n6 1:2 1:12\n7\n8\n9\n10\n11\n12\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.srew",
    "content": "# Reward structure \"r\"\n# State rewards\n13 6\n7 1\n8 2\n9 3\n10 4\n11 5\n12 6\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.sta",
    "content": "(s,d)\n0:(0,0)\n1:(1,0)\n2:(2,0)\n3:(3,0)\n4:(4,0)\n5:(5,0)\n6:(6,0)\n7:(7,1)\n8:(7,2)\n9:(7,3)\n10:(7,4)\n11:(7,5)\n12:(7,6)\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.tra",
    "content": "13 20\n0 1 0.5\n0 2 0.5\n1 3 0.5\n1 4 0.5\n2 5 0.5\n2 6 0.5\n3 1 0.5\n3 7 0.5\n4 8 0.5\n4 9 0.5\n5 10 0.5\n5 11 0.5\n6 2 0.5\n6 12 0.5\n7 7 1\n8 8 1\n9 9 1\n10 10 1\n11 11 1\n12 12 1\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/dice.pm.trew",
    "content": "# Reward structure \"r\"\n# Transition rewards\n13 14\n0 1 1\n0 2 1\n1 3 1\n1 4 1\n2 5 1\n2 6 1\n3 1 1\n3 7 1\n4 8 1\n4 9 1\n5 10 1\n5 11 1\n6 2 1\n6 12 1\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"r\"\r\n\ts=0 : 2;\r\n\t[] s<3 : s;\r\nendrewards\r\n\r\nrewards \"s\"\r\n\ts>=4 : 1;\r\nendrewards\r\n\r\nrewards\r\n\t[] s<3 : s;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm.exportmodel.auto",
    "content": "# Export all model info\n\n-exportmodel lec3.pm.all -h\n-exportmodel lec3.pm.all -m\n\n# Export model info separately\n\n-exportmodel lec3.pm.tra\n-exportmodel lec3.pm.lab\n-exportmodel lec3.pm.sta\n-exportmodel lec3.pm.srew\n-exportmodel lec3.pm.trew\n\n# Export model info - explicit engine\n\n-exportmodel lec3.pm.all -ex\n\n-exportmodel lec3.pm.tra -ex\n-exportmodel lec3.pm.sta -ex\n-exportmodel lec3.pm.lab -ex\n-exportmodel lec3.pm.srew -ex\n-exportmodel lec3.pm.trew -ex\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm.tra",
    "content": "6 9\n0 1 0.5\n0 3 0.5\n1 0 0.5\n1 2 0.25\n1 4 0.25\n2 5 1\n3 3 1\n4 4 1\n5 2 1\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm1.srew",
    "content": "# Reward structure \"r\"\n# State rewards\n6 1\n0 2\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm1.trew",
    "content": "# Reward structure \"r\"\n# Transition rewards\n6 4\n1 0 1\n1 2 1\n1 4 1\n2 5 2\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm2.srew",
    "content": "# Reward structure \"s\"\n# State rewards\n6 2\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm2.trew",
    "content": "# Reward structure \"s\"\n# Transition rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm3.srew",
    "content": "# Reward structure\n# State rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/export/dtmc/lec3.pm3.trew",
    "content": "# Reward structure\n# Transition rewards\n6 4\n1 0 1\n1 2 1\n1 4 1\n2 5 2\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> [0.5,0.5]:(s'=1) + [0.5,0.5]:(s'=3);\r\n[] s=1 -> [0.5,0.5]:(s'=0) + [0.25,0.25]:(s'=2) + [0.25,0.25]:(s'=4);\r\n[r] s=2 -> [1,1]:(s'=5);\r\n[] s=3 -> [1,1]:(s'=3);\r\n[] s=4 -> [1,1]:(s'=4);\r\n[] s=5 -> [1,1]:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n\r\nrewards \"r\"\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism.exportmodel.auto",
    "content": "# Export all model info in different formats\n\n-exportmodel dtmc_pctl.prism.all\n\n# Export model info separately (for a few formats)\n\n-exportmodel dtmc_pctl.prism.tra\n-exportmodel dtmc_pctl.prism.sta\n-exportmodel dtmc_pctl.prism.lab\n-exportmodel dtmc_pctl.prism.srew\n-exportmodel dtmc_pctl.prism.trew\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism.tra",
    "content": "6 9\n0 1 [0.5,0.5]\n0 3 [0.5,0.5]\n1 0 [0.5,0.5]\n1 2 [0.25,0.25]\n1 4 [0.25,0.25]\n2 5 [1,1] r\n3 3 [1,1]\n4 4 [1,1]\n5 2 [1,1]\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism1.srew",
    "content": "# Reward structure \"time\"\n# State rewards\n6 6\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism1.trew",
    "content": "# Reward structure \"time\"\n# Transition rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism2.srew",
    "content": "# Reward structure \"r\"\n# State rewards\n6 1\n4 3\n"
  },
  {
    "path": "prism-tests/functionality/export/idtmc/dtmc_pctl.prism2.trew",
    "content": "# Reward structure \"r\"\n# Transition rewards\n6 1\n2 5 17\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism",
    "content": "mdp\r\n\r\nconst double delta = 0.01;\r\nconst double p = 0.5-delta;\r\nconst double q = 0.5+delta;\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n//[east] s=1 -> 1:(s'=2);\r\n[east] s=1 -> [0.8,0.9]:(s'=2) + [0.1,0.2]:(s'=1);\r\n[south] s=1 -> [p,q]:(s'=4) + [1-q,1-p]:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n\r\nrewards \"energy\"\r\n\ttrue : 0.1;\r\n\ts<2 | s>3 : 2.2;\r\n\t[stuck] true : 3.5;\r\nendrewards\r\n\r\nrewards \"move\"\r\n\t[north] true : 1;\r\n\t[south] true : 1;\r\n\t[east] true : 1;\r\n\t[west] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism.exportmodel.auto",
    "content": "# Export all model info in different formats\n\n-exportmodel robot.prism.all\n\n# Export model info separately (for a few formats)\n\n-exportmodel robot.prism.tra\n-exportmodel robot.prism.sta\n-exportmodel robot.prism.lab\n-exportmodel robot.prism.srew\n-exportmodel robot.prism.trew\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"hazard\" 3=\"goal1\" 4=\"goal2\"\n0: 0\n1: 2\n2: 4\n3: 4\n5: 3\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism.tra",
    "content": "6 10 17\n0 0 0 [0.4,0.4] east\n0 0 1 [0.6,0.6] east\n0 1 1 [0.1,0.1] south\n0 1 3 [0.8,0.8] south\n0 1 4 [0.1,0.1] south\n1 0 1 [0.1,0.2] east\n1 0 2 [0.8,0.9] east\n1 1 2 [0.49,0.51] south\n1 1 4 [0.49,0.51] south\n2 0 2 [1,1] stuck\n3 0 3 [1,1] stuck\n4 0 5 [1,1] east\n4 1 3 [0.6,0.6] west\n4 1 4 [0.4,0.4] west\n5 0 4 [1,1] west\n5 1 2 [0.9,0.9] north\n5 1 5 [0.1,0.1] north\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism1.srew",
    "content": "# Reward structure \"time\"\n# State rewards\n6 6\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism1.trew",
    "content": "# Reward structure \"time\"\n# Transition rewards\n6 10 0\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism2.srew",
    "content": "# Reward structure \"energy\"\n# State rewards\n6 6\n0 2.3\n1 2.3\n2 0.1\n3 0.1\n4 2.3\n5 2.3\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism2.trew",
    "content": "# Reward structure \"energy\"\n# Transition rewards\n6 10 2\n2 0 2 3.5\n3 0 3 3.5\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism3.srew",
    "content": "# Reward structure \"move\"\n# State rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/export/imdp/robot.prism3.trew",
    "content": "# Reward structure \"move\"\n# Transition rewards\n6 10 15\n0 0 0 1\n0 0 1 1\n0 1 1 1\n0 1 3 1\n0 1 4 1\n1 0 1 1\n1 0 2 1\n1 1 2 1\n1 1 4 1\n4 0 5 1\n4 1 3 1\n4 1 4 1\n5 0 4 1\n5 1 2 1\n5 1 5 1\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism",
    "content": "// Simple LTS from Lec 9 of Computer-Aided Verification\r\n\r\nmodule M\r\n\r\ns:[0..3];\r\n\r\n[] s=0 -> (s'=1);\r\n[] s=0 -> (s'=2);\r\n[] s=1 -> (s'=1);\r\n[] s=1 -> (s'=3);\r\n[] s=2 -> (s'=1);\r\n[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = s=0 | s=1;\r\nlabel \"b\" = s=0 | s=3;\r\n\r\nrewards \"r1\"\r\n\ts<2 : s;\r\nendrewards\r\n\r\nrewards \"r2\"\r\n\t[] s>=2 : s;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism.exportmodel.auto",
    "content": "# Export all model info\n\n-exportmodel lec9ctl1.prism.all\n\n# Export model info separately\n\n-exportmodel lec9ctl1.prism.tra\n-exportmodel lec9ctl1.prism.lab\n-exportmodel lec9ctl1.prism.sta\n-exportmodel lec9ctl1.prism.srew\n-exportmodel lec9ctl1.prism.trew\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"a\" 3=\"b\"\n0: 0 2 3\n1: 2\n3: 3\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism.tra",
    "content": "4 6 6\n0 0 1\n0 1 2\n1 0 1\n1 1 3\n2 0 1\n3 0 3\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism1.srew",
    "content": "# Reward structure \"r1\"\n# State rewards\n4 1\n1 1\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism1.trew",
    "content": "# Reward structure \"r1\"\n# Transition rewards\n4 6 0\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism2.srew",
    "content": "# Reward structure \"r2\"\n# State rewards\n4 0\n"
  },
  {
    "path": "prism-tests/functionality/export/lts/lec9ctl1.prism2.trew",
    "content": "# Reward structure \"r2\"\n# Transition rewards\n4 6 2\n2 0 1 2\n3 0 3 3\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism",
    "content": "mdp\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n\r\nrewards \"energy\"\r\n\ttrue : 0.1;\r\n\ts<2 | s>3 : 2.2;\r\n\t[stuck] true : 3.5;\r\nendrewards\r\n\r\nrewards \"move\"\r\n\t[north] true : 1;\r\n\t[south] true : 1;\r\n\t[east] true : 1;\r\n\t[west] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"hazard\" 3=\"goal1\" 4=\"goal2\"\n0: 0\n1: 2\n2: 4\n3: 4\n5: 3\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact.tra",
    "content": "6 10 16\n0 0 0 2/5 east\n0 0 1 3/5 east\n0 1 1 1/10 south\n0 1 3 4/5 south\n0 1 4 1/10 south\n1 0 2 1 east\n1 1 2 1/2 south\n1 1 4 1/2 south\n2 0 2 1 stuck\n3 0 3 1 stuck\n4 0 5 1 east\n4 1 3 3/5 west\n4 1 4 2/5 west\n5 0 4 1 west\n5 1 2 9/10 north\n5 1 5 1/10 north\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact1.srew",
    "content": "# Reward structure \"time\"\n# State rewards\n6 6\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact1.trew",
    "content": "# Reward structure \"time\"\n# Transition rewards\n6 10 0\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact2.srew",
    "content": "# Reward structure \"energy\"\n# State rewards\n6 6\n0 23/10\n1 23/10\n2 1/10\n3 1/10\n4 23/10\n5 23/10\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact2.trew",
    "content": "# Reward structure \"energy\"\n# Transition rewards\n6 10 2\n2 0 2 7/2\n3 0 3 7/2\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact3.srew",
    "content": "# Reward structure \"move\"\n# State rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exact3.trew",
    "content": "# Reward structure \"move\"\n# Transition rewards\n6 10 14\n0 0 0 1\n0 0 1 1\n0 1 1 1\n0 1 3 1\n0 1 4 1\n1 0 2 1\n1 1 2 1\n1 1 4 1\n4 0 5 1\n4 1 3 1\n4 1 4 1\n5 0 4 1\n5 1 2 1\n5 1 5 1\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.exportmodel.auto",
    "content": "# Export all model info in different formats\n\n-exportmodel robot.prism.all\n-exportmodel robot.prism.matlab.all:matlab\n-exportmodel robot.prism.rows.all:rows\n\n# Export model info separately (for a few formats)\n\n-exportmodel robot.prism.tra\n-exportmodel robot.prism.lab\n-exportmodel robot.prism.sta\n-exportmodel robot.prism.srew\n-exportmodel robot.prism.trew\n\n# Export model info - explicit engine\n\n# -exportmodel robot.prism.tra -ex # order different\n-exportmodel robot.prism.sta -ex\n-exportmodel robot.prism.lab -ex\n-exportmodel robot.prism.srew -ex\n-exportmodel robot.prism.srew -ex\n#-exportmodel robot.prism.trew -ex # order different\n\n# Export model info - exact\n\n-exportmodel robot.prism.exact.all -exact\n-exportmodel robot.prism.exact.tra -exact\n-exportmodel robot.prism.exact.srew -exact\n-exportmodel robot.prism.exact.srew -exact\n-exportmodel robot.prism.exact.srew -exact\n-exportmodel robot.prism.exact.trew -exact\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"hazard\" 3=\"goal1\" 4=\"goal2\"\n0: 0\n1: 2\n2: 4\n3: 4\n5: 3\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab.lab",
    "content": "l_init=sparse(6,1);\nl_deadlock=sparse(6,1);\nl_hazard=sparse(6,1);\nl_goal1=sparse(6,1);\nl_goal2=sparse(6,1);\n\nl_init(1)=1;\nl_hazard(2)=1;\nl_goal2(3)=1;\nl_goal2(4)=1;\nl_goal1(6)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab.sta",
    "content": "% (s)\nstates=[\n0\n1\n2\n3\n4\n5\n];\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab.tra",
    "content": "S1 = sparse(6,6);\nS2 = sparse(6,6);\nS1(1,2)=0.1;\nS1(1,4)=0.8;\nS1(1,5)=0.1;\nS2(1,1)=0.4;\nS2(1,2)=0.6;\nS1(2,3)=0.5;\nS1(2,5)=0.5;\nS2(2,3)=1;\nS1(3,3)=1;\nS1(4,4)=1;\nS1(5,4)=0.6;\nS1(5,5)=0.4;\nS2(5,6)=1;\nS1(6,3)=0.9;\nS1(6,6)=0.1;\nS2(6,5)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab1.srew",
    "content": "c1 = sparse(6,1);\nc1(1)=1;\nc1(2)=1;\nc1(3)=1;\nc1(4)=1;\nc1(5)=1;\nc1(6)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab1.trew",
    "content": "C11 = sparse(6,6);\nC12 = sparse(6,6);\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab2.srew",
    "content": "c2 = sparse(6,1);\nc2(1)=2.3;\nc2(2)=2.3;\nc2(3)=0.1;\nc2(4)=0.1;\nc2(5)=2.3;\nc2(6)=2.3;\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab2.trew",
    "content": "C21 = sparse(6,6);\nC22 = sparse(6,6);\nC21(3,3)=3.5;\nC21(4,4)=3.5;\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab3.srew",
    "content": "c3 = sparse(6,1);\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.matlab3.trew",
    "content": "C31 = sparse(6,6);\nC32 = sparse(6,6);\nC31(1,2)=1;\nC31(1,4)=1;\nC31(1,5)=1;\nC32(1,1)=1;\nC32(1,2)=1;\nC31(2,3)=1;\nC31(2,5)=1;\nC32(2,3)=1;\nC31(5,4)=1;\nC31(5,5)=1;\nC32(5,6)=1;\nC31(6,3)=1;\nC31(6,6)=1;\nC32(6,5)=1;\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"hazard\" 3=\"goal1\" 4=\"goal2\"\n0: 0\n1: 2\n2: 4\n3: 4\n5: 3\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows.tra",
    "content": "6 10 16\n0 0.1:1 0.8:3 0.1:4 south\n0 0.4:0 0.6:1 east\n1 0.5:2 0.5:4 south\n1 1:2 east\n2 1:2 stuck\n3 1:3 stuck\n4 0.6:3 0.4:4 west\n4 1:5 east\n5 0.9:2 0.1:5 north\n5 1:4 west\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows1.srew",
    "content": "# Reward structure \"time\"\n# State rewards\n6 6\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows1.trew",
    "content": "6 10 0\n0\n0\n1\n1\n2\n3\n4\n4\n5\n5\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows2.srew",
    "content": "# Reward structure \"energy\"\n# State rewards\n6 6\n0 2.3\n1 2.3\n2 0.1\n3 0.1\n4 2.3\n5 2.3\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows2.trew",
    "content": "6 10 2\n0\n0\n1\n1\n2 3.5:2\n3 3.5:3\n4\n4\n5\n5\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows3.srew",
    "content": "# Reward structure \"move\"\n# State rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.rows3.trew",
    "content": "6 10 14\n0 1:1 1:3 1:4\n0 1:0 1:1\n1 1:2 1:4\n1 1:2\n2\n3\n4 1:3 1:4\n4 1:5\n5 1:2 1:5\n5 1:4\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism.tra",
    "content": "6 10 16\n0 0 1 0.1 south\n0 0 3 0.8 south\n0 0 4 0.1 south\n0 1 0 0.4 east\n0 1 1 0.6 east\n1 0 2 0.5 south\n1 0 4 0.5 south\n1 1 2 1 east\n2 0 2 1 stuck\n3 0 3 1 stuck\n4 0 3 0.6 west\n4 0 4 0.4 west\n4 1 5 1 east\n5 0 2 0.9 north\n5 0 5 0.1 north\n5 1 4 1 west\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism1.srew",
    "content": "# Reward structure \"time\"\n# State rewards\n6 6\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism1.trew",
    "content": "# Reward structure \"time\"\n# Transition rewards\n6 10 0\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism2.srew",
    "content": "# Reward structure \"energy\"\n# State rewards\n6 6\n0 2.3\n1 2.3\n2 0.1\n3 0.1\n4 2.3\n5 2.3\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism2.trew",
    "content": "# Reward structure \"energy\"\n# Transition rewards\n6 10 2\n2 0 2 3.5\n3 0 3 3.5\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism3.srew",
    "content": "# Reward structure \"move\"\n# State rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/export/mdp/robot.prism3.trew",
    "content": "# Reward structure \"move\"\n# Transition rewards\n6 10 14\n0 0 1 1\n0 0 3 1\n0 0 4 1\n0 1 0 1\n0 1 1 1\n1 0 2 1\n1 0 4 1\n1 1 2 1\n4 0 3 1\n4 0 4 1\n4 1 5 1\n5 0 2 1\n5 0 5 1\n5 1 4 1\n"
  },
  {
    "path": "prism-tests/functionality/export/pomdp/maze.prism",
    "content": "// maze example (POMDP)\n// Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n// gxn 29/01/16\n\n// state space (value of variable \"s\")\n\n//  0  1  2  3  4\n//  5     6     7\n//  8     10    9\n\n// 10 is the target\n\npomdp\n\n// can observe the walls and target\nobservable \"west\" = s=0|s=5|s=6|s=7|s=8|s=9|s=10; // wall to the west\nobservable \"east\" = s=4|s=5|s=6|s=7|s=8|s=9|s=10; // wall to the east\nobservable \"north\" = s=0|s=1|s=2|s=3|s=4; // wall to the north\nobservable \"south\" = s=1|s=3|s=8|s=9|s=10; // wall to the south\nobservable \"target\" = s=10; //target\n\nmodule maze\n\n\ts : [-1..10];\n\t\n\t// initialisation\n\t[] s=-1 -> 0.1 : (s'=0)\n\t\t\t + 0.1 : (s'=1)\n\t\t\t + 0.1 : (s'=2)\n\t\t\t + 0.1 : (s'=3)\n\t\t\t + 0.1 : (s'=4)\n\t\t\t + 0.1 : (s'=5)\n\t\t\t + 0.1 : (s'=6)\n\t\t\t + 0.1 : (s'=7)\n\t\t\t + 0.1 : (s'=8)\n\t\t\t + 0.1 : (s'=9);\n\t\n\t// moving around the maze\n\n\t[east] s=0 -> (s'=1);\n\t[south] s=0 -> (s'=5);\n\n\t[east] s=1 -> (s'=2);\n\t[west] s=1 -> (s'=0);\n\n\t[east] s=2 -> (s'=3);\n\t[west] s=2 -> (s'=1);\n\t[south] s=2 -> (s'=6);\n\n\t[east] s=3 -> (s'=4);\n\t[west] s=3 -> (s'=2);\n\n\t[west] s=4 -> (s'=3);\n\t[south] s=4 -> (s'=7);\n\n\t[north] s=5 -> (s'=0);\n\t[south] s=5 -> (s'=8);\n\n\t[north] s=6 -> (s'=2);\n\t[south] s=6 -> (s'=10);\n\n\t[north] s=7 -> (s'=4);\n\t[south] s=7 -> (s'=9);\n\n\t[north] s=8 -> (s'=5);\n\n\t[north] s=9 -> (s'=7);\n\n\t// loop when we reach the target\n\t[done] s=10 -> true;\n\nendmodule\n\n// reward structure (number of steps to reach the target)\nrewards\n\n\t[east] true : 1;\n\t[west] true : 1;\n\t[north] true : 1;\n\t[south] true : 1;\n\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/export/pomdp/maze.prism.exportmodel.auto",
    "content": "# Export all model info\n\n-exportmodel maze.prism.all\n\n# Export model info separately\n\n-exportmodel maze.prism.tra\n-exportmodel maze.prism.lab\n-exportmodel maze.prism.sta\n-exportmodel maze.prism.srew\n-exportmodel maze.prism.trew\n-exportmodel maze.prism.obs\n"
  },
  {
    "path": "prism-tests/functionality/export/pomdp/maze.prism.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/functionality/export/pomdp/maze.prism.obs",
    "content": "(west,east,north,south,target)\n0:(false,false,false,false,false)\n1:(true,false,true,false,false)\n2:(false,false,true,true,false)\n3:(false,false,true,false,false)\n4:(false,true,true,false,false)\n5:(true,true,false,false,false)\n6:(true,true,false,true,false)\n7:(true,true,false,true,true)\n"
  },
  {
    "path": "prism-tests/functionality/export/pomdp/maze.prism.srew",
    "content": "# Reward structure\n# State rewards\n12 0\n"
  },
  {
    "path": "prism-tests/functionality/export/pomdp/maze.prism.sta",
    "content": "(s)\n0:(-1)\n1:(0)\n2:(1)\n3:(2)\n4:(3)\n5:(4)\n6:(5)\n7:(6)\n8:(7)\n9:(8)\n10:(9)\n11:(10)\n"
  },
  {
    "path": "prism-tests/functionality/export/pomdp/maze.prism.tra",
    "content": "12 21 30 8\n- - 0 - 0\n0 0 1 0.1 1\n0 0 2 0.1 2\n0 0 3 0.1 3\n0 0 4 0.1 2\n0 0 5 0.1 4\n0 0 6 0.1 5\n0 0 7 0.1 5\n0 0 8 0.1 5\n0 0 9 0.1 6\n0 0 10 0.1 6\n1 0 2 1 2 east\n1 1 6 1 5 south\n2 0 3 1 3 east\n2 1 1 1 1 west\n3 0 4 1 2 east\n3 1 7 1 5 south\n3 2 2 1 2 west\n4 0 5 1 4 east\n4 1 3 1 3 west\n5 0 8 1 5 south\n5 1 4 1 2 west\n6 0 9 1 6 south\n6 1 1 1 1 north\n7 0 11 1 7 south\n7 1 3 1 3 north\n8 0 10 1 6 south\n8 1 5 1 4 north\n9 0 6 1 5 north\n10 0 8 1 5 north\n11 0 11 1 7 done\n"
  },
  {
    "path": "prism-tests/functionality/export/pomdp/maze.prism.trew",
    "content": "# Reward structure\n# Transition rewards\n12 21 19\n1 0 2 1\n1 1 6 1\n2 0 3 1\n2 1 1 1\n3 0 4 1\n3 1 7 1\n3 2 2 1\n4 0 5 1\n4 1 3 1\n5 0 8 1\n5 1 4 1\n6 0 9 1\n6 1 1 1\n7 0 11 1\n7 1 3 1\n8 0 10 1\n8 1 5 1\n9 0 6 1\n10 0 8 1\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm",
    "content": "// Model (and properties) hacked a bit to things that can be\r\n// reliably tested on both symbolic/explicit engines\r\n\r\ndtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\ts=0 : 1;\r\nendrewards\r\n\r\nconst AA;\r\nconst BB;\r\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.args",
    "content": "-h\n-ex\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props",
    "content": "const int x;\n\nlabel \"done\" = s=7;\n\n// RESULT (AA=0,BB=1,x=1): true\n// RESULT (AA=0,BB=1,x=2): true\n// RESULT (AA=0,BB=1,x=3): false\n// RESULT (AA=0,BB=2,x=1): true\n// RESULT (AA=0,BB=2,x=2): true\n// RESULT (AA=0,BB=2,x=3): false\n// RESULT (AA=1,BB=1,x=1): true\n// RESULT (AA=1,BB=1,x=2): true\n// RESULT (AA=1,BB=1,x=3): false\n// RESULT (AA=1,BB=2,x=1): true\n// RESULT (AA=1,BB=2,x=2): true\n// RESULT (AA=1,BB=2,x=3): false\n\"Property_1\": P>0.55 [ F s=7 & d>x ];\n\n// RESULT (AA=0,BB=1,x=1): 0.78125\n// RESULT (AA=0,BB=1,x=2): 0.625\n// RESULT (AA=0,BB=1,x=3): 0.46875\n// RESULT (AA=0,BB=2,x=1): 0.78125\n// RESULT (AA=0,BB=2,x=2): 0.625\n// RESULT (AA=0,BB=2,x=3): 0.46875\n// RESULT (AA=1,BB=1,x=1): 0.78125\n// RESULT (AA=1,BB=1,x=2): 0.625\n// RESULT (AA=1,BB=1,x=3): 0.46875\n// RESULT (AA=1,BB=2,x=1): 0.78125\n// RESULT (AA=1,BB=2,x=2): 0.625\n// RESULT (AA=1,BB=2,x=3): 0.46875\n\"Intriguing\": P=? [ F<=5 s=7 & d>x ];\n\n// RESULT (AA=0,BB=1,x=1): 0.78125\n// RESULT (AA=0,BB=1,x=2): 0.625\n// RESULT (AA=0,BB=1,x=3): 0.46875\n// RESULT (AA=0,BB=2,x=1): 0.78125\n// RESULT (AA=0,BB=2,x=2): 0.625\n// RESULT (AA=0,BB=2,x=3): 0.46875\n// RESULT (AA=1,BB=1,x=1): 0.78125\n// RESULT (AA=1,BB=1,x=2): 0.625\n// RESULT (AA=1,BB=1,x=3): 0.46875\n// RESULT (AA=1,BB=2,x=1): 0.78125\n// RESULT (AA=1,BB=2,x=2): 0.625\n// RESULT (AA=1,BB=2,x=3): 0.46875\nP=? [ F<=5 s=7 & d>x ];\n\n// RESULT (AA=0,BB=1,x=1): 1.0\n// RESULT (AA=0,BB=1,x=2): Infinity\n// RESULT (AA=0,BB=1,x=3): Infinity\n// RESULT (AA=0,BB=2,x=1): 1.0\n// RESULT (AA=0,BB=2,x=2): Infinity\n// RESULT (AA=0,BB=2,x=3): Infinity\n// RESULT (AA=1,BB=1,x=1): 1.0\n// RESULT (AA=1,BB=1,x=2): Infinity\n// RESULT (AA=1,BB=1,x=3): Infinity\n// RESULT (AA=1,BB=2,x=1): 1.0\n// RESULT (AA=1,BB=2,x=2): Infinity\n// RESULT (AA=1,BB=2,x=3): Infinity\nR=? [ F \"done\" & d>=x ];\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.1.comment.txt",
    "content": "// RESULT (AA=0,BB=1,x=1): true\n// RESULT (AA=0,BB=1,x=2): true\n// RESULT (AA=0,BB=1,x=3): false\n// RESULT (AA=0,BB=2,x=1): true\n// RESULT (AA=0,BB=2,x=2): true\n// RESULT (AA=0,BB=2,x=3): false\n// RESULT (AA=1,BB=1,x=1): true\n// RESULT (AA=1,BB=1,x=2): true\n// RESULT (AA=1,BB=1,x=3): false\n// RESULT (AA=1,BB=2,x=1): true\n// RESULT (AA=1,BB=2,x=2): true\n// RESULT (AA=1,BB=2,x=3): false\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.1.csv",
    "content": "AA,BB,x,Result\n0,1,1,true\n0,1,2,true\n0,1,3,false\n0,2,1,true\n0,2,2,true\n0,2,3,false\n1,1,1,true\n1,1,2,true\n1,1,3,false\n1,2,1,true\n1,2,2,true\n1,2,3,false\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.1.dataframe.csv",
    "content": "Property,AA,BB,x,Result\nProperty_1,0,1,1,true\nProperty_1,0,1,2,true\nProperty_1,0,1,3,false\nProperty_1,0,2,1,true\nProperty_1,0,2,2,true\nProperty_1,0,2,3,false\nProperty_1,1,1,1,true\nProperty_1,1,1,2,true\nProperty_1,1,1,3,false\nProperty_1,1,2,1,true\nProperty_1,1,2,2,true\nProperty_1,1,2,3,false\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.1.matrix.csv",
    "content": "\"AA=0, BB\\x\"\n,1,2,3\n1,true,true,false\n2,true,true,false\n\n\"AA=1, BB\\x\"\n,1,2,3\n1,true,true,false\n2,true,true,false\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.1.matrix.txt",
    "content": "AA=0, BB\\x:\n\t1\t2\t3\n1\ttrue\ttrue\tfalse\n2\ttrue\ttrue\tfalse\n\nAA=1, BB\\x:\n\t1\t2\t3\n1\ttrue\ttrue\tfalse\n2\ttrue\ttrue\tfalse\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.1.txt",
    "content": "AA\tBB\tx\tResult\n0\t1\t1\ttrue\n0\t1\t2\ttrue\n0\t1\t3\tfalse\n0\t2\t1\ttrue\n0\t2\t2\ttrue\n0\t2\t3\tfalse\n1\t1\t1\ttrue\n1\t1\t2\ttrue\n1\t1\t3\tfalse\n1\t2\t1\ttrue\n1\t2\t2\ttrue\n1\t2\t3\tfalse\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.all.comment.txt",
    "content": "// RESULT (AA=0,BB=1,x=1): true\n// RESULT (AA=0,BB=1,x=2): true\n// RESULT (AA=0,BB=1,x=3): false\n// RESULT (AA=0,BB=2,x=1): true\n// RESULT (AA=0,BB=2,x=2): true\n// RESULT (AA=0,BB=2,x=3): false\n// RESULT (AA=1,BB=1,x=1): true\n// RESULT (AA=1,BB=1,x=2): true\n// RESULT (AA=1,BB=1,x=3): false\n// RESULT (AA=1,BB=2,x=1): true\n// RESULT (AA=1,BB=2,x=2): true\n// RESULT (AA=1,BB=2,x=3): false\n\"Property_1\": P>0.55 [ F s=7&d>x ]\n\n// RESULT (AA=0,BB=1,x=1): 0.78125\n// RESULT (AA=0,BB=1,x=2): 0.625\n// RESULT (AA=0,BB=1,x=3): 0.46875\n// RESULT (AA=0,BB=2,x=1): 0.78125\n// RESULT (AA=0,BB=2,x=2): 0.625\n// RESULT (AA=0,BB=2,x=3): 0.46875\n// RESULT (AA=1,BB=1,x=1): 0.78125\n// RESULT (AA=1,BB=1,x=2): 0.625\n// RESULT (AA=1,BB=1,x=3): 0.46875\n// RESULT (AA=1,BB=2,x=1): 0.78125\n// RESULT (AA=1,BB=2,x=2): 0.625\n// RESULT (AA=1,BB=2,x=3): 0.46875\n\"Intriguing\": P=? [ F<=5 s=7&d>x ]\n\n// RESULT (AA=0,BB=1,x=1): 0.78125\n// RESULT (AA=0,BB=1,x=2): 0.625\n// RESULT (AA=0,BB=1,x=3): 0.46875\n// RESULT (AA=0,BB=2,x=1): 0.78125\n// RESULT (AA=0,BB=2,x=2): 0.625\n// RESULT (AA=0,BB=2,x=3): 0.46875\n// RESULT (AA=1,BB=1,x=1): 0.78125\n// RESULT (AA=1,BB=1,x=2): 0.625\n// RESULT (AA=1,BB=1,x=3): 0.46875\n// RESULT (AA=1,BB=2,x=1): 0.78125\n// RESULT (AA=1,BB=2,x=2): 0.625\n// RESULT (AA=1,BB=2,x=3): 0.46875\nP=? [ F<=5 s=7&d>x ]\n\n// RESULT (AA=0,BB=1,x=1): 1\n// RESULT (AA=0,BB=1,x=2): Infinity\n// RESULT (AA=0,BB=1,x=3): Infinity\n// RESULT (AA=0,BB=2,x=1): 1\n// RESULT (AA=0,BB=2,x=2): Infinity\n// RESULT (AA=0,BB=2,x=3): Infinity\n// RESULT (AA=1,BB=1,x=1): 1\n// RESULT (AA=1,BB=1,x=2): Infinity\n// RESULT (AA=1,BB=1,x=3): Infinity\n// RESULT (AA=1,BB=2,x=1): 1\n// RESULT (AA=1,BB=2,x=2): Infinity\n// RESULT (AA=1,BB=2,x=3): Infinity\nR=? [ F \"done\"&d>=x ]\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.all.csv",
    "content": "\"\"\"Property_1\"\": P>0.55 [ F s=7&d>x ]\"\nAA,BB,x,Result\n0,1,1,true\n0,1,2,true\n0,1,3,false\n0,2,1,true\n0,2,2,true\n0,2,3,false\n1,1,1,true\n1,1,2,true\n1,1,3,false\n1,2,1,true\n1,2,2,true\n1,2,3,false\n\n\"\"\"Intriguing\"\": P=? [ F<=5 s=7&d>x ]\"\nAA,BB,x,Result\n0,1,1,0.78125\n0,1,2,0.625\n0,1,3,0.46875\n0,2,1,0.78125\n0,2,2,0.625\n0,2,3,0.46875\n1,1,1,0.78125\n1,1,2,0.625\n1,1,3,0.46875\n1,2,1,0.78125\n1,2,2,0.625\n1,2,3,0.46875\n\n\"P=? [ F<=5 s=7&d>x ]\"\nAA,BB,x,Result\n0,1,1,0.78125\n0,1,2,0.625\n0,1,3,0.46875\n0,2,1,0.78125\n0,2,2,0.625\n0,2,3,0.46875\n1,1,1,0.78125\n1,1,2,0.625\n1,1,3,0.46875\n1,2,1,0.78125\n1,2,2,0.625\n1,2,3,0.46875\n\n\"R=? [ F \"\"done\"\"&d>=x ]\"\nAA,BB,x,Result\n0,1,1,1\n0,1,2,Infinity\n0,1,3,Infinity\n0,2,1,1\n0,2,2,Infinity\n0,2,3,Infinity\n1,1,1,1\n1,1,2,Infinity\n1,1,3,Infinity\n1,2,1,1\n1,2,2,Infinity\n1,2,3,Infinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.all.dataframe.csv",
    "content": "Property,AA,BB,x,Result\nProperty_1,0,1,1,true\nProperty_1,0,1,2,true\nProperty_1,0,1,3,false\nProperty_1,0,2,1,true\nProperty_1,0,2,2,true\nProperty_1,0,2,3,false\nProperty_1,1,1,1,true\nProperty_1,1,1,2,true\nProperty_1,1,1,3,false\nProperty_1,1,2,1,true\nProperty_1,1,2,2,true\nProperty_1,1,2,3,false\nIntriguing,0,1,1,0.78125\nIntriguing,0,1,2,0.625\nIntriguing,0,1,3,0.46875\nIntriguing,0,2,1,0.78125\nIntriguing,0,2,2,0.625\nIntriguing,0,2,3,0.46875\nIntriguing,1,1,1,0.78125\nIntriguing,1,1,2,0.625\nIntriguing,1,1,3,0.46875\nIntriguing,1,2,1,0.78125\nIntriguing,1,2,2,0.625\nIntriguing,1,2,3,0.46875\nProperty_3,0,1,1,0.78125\nProperty_3,0,1,2,0.625\nProperty_3,0,1,3,0.46875\nProperty_3,0,2,1,0.78125\nProperty_3,0,2,2,0.625\nProperty_3,0,2,3,0.46875\nProperty_3,1,1,1,0.78125\nProperty_3,1,1,2,0.625\nProperty_3,1,1,3,0.46875\nProperty_3,1,2,1,0.78125\nProperty_3,1,2,2,0.625\nProperty_3,1,2,3,0.46875\nProperty_4,0,1,1,1\nProperty_4,0,1,2,Infinity\nProperty_4,0,1,3,Infinity\nProperty_4,0,2,1,1\nProperty_4,0,2,2,Infinity\nProperty_4,0,2,3,Infinity\nProperty_4,1,1,1,1\nProperty_4,1,1,2,Infinity\nProperty_4,1,1,3,Infinity\nProperty_4,1,2,1,1\nProperty_4,1,2,2,Infinity\nProperty_4,1,2,3,Infinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.all.matrix.csv",
    "content": "\"\"\"Property_1\"\": P>0.55 [ F s=7&d>x ]\"\n\"AA=0, BB\\x\"\n,1,2,3\n1,true,true,false\n2,true,true,false\n\n\"AA=1, BB\\x\"\n,1,2,3\n1,true,true,false\n2,true,true,false\n\n\"\"\"Intriguing\"\": P=? [ F<=5 s=7&d>x ]\"\n\"AA=0, BB\\x\"\n,1,2,3\n1,0.78125,0.625,0.46875\n2,0.78125,0.625,0.46875\n\n\"AA=1, BB\\x\"\n,1,2,3\n1,0.78125,0.625,0.46875\n2,0.78125,0.625,0.46875\n\n\"P=? [ F<=5 s=7&d>x ]\"\n\"AA=0, BB\\x\"\n,1,2,3\n1,0.78125,0.625,0.46875\n2,0.78125,0.625,0.46875\n\n\"AA=1, BB\\x\"\n,1,2,3\n1,0.78125,0.625,0.46875\n2,0.78125,0.625,0.46875\n\n\"R=? [ F \"\"done\"\"&d>=x ]\"\n\"AA=0, BB\\x\"\n,1,2,3\n1,1,Infinity,Infinity\n2,1,Infinity,Infinity\n\n\"AA=1, BB\\x\"\n,1,2,3\n1,1,Infinity,Infinity\n2,1,Infinity,Infinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.all.matrix.txt",
    "content": "\"Property_1\": P>0.55 [ F s=7&d>x ]:\nAA=0, BB\\x:\n\t1\t2\t3\n1\ttrue\ttrue\tfalse\n2\ttrue\ttrue\tfalse\n\nAA=1, BB\\x:\n\t1\t2\t3\n1\ttrue\ttrue\tfalse\n2\ttrue\ttrue\tfalse\n\n\"Intriguing\": P=? [ F<=5 s=7&d>x ]:\nAA=0, BB\\x:\n\t1\t2\t3\n1\t0.78125\t0.625\t0.46875\n2\t0.78125\t0.625\t0.46875\n\nAA=1, BB\\x:\n\t1\t2\t3\n1\t0.78125\t0.625\t0.46875\n2\t0.78125\t0.625\t0.46875\n\nP=? [ F<=5 s=7&d>x ]:\nAA=0, BB\\x:\n\t1\t2\t3\n1\t0.78125\t0.625\t0.46875\n2\t0.78125\t0.625\t0.46875\n\nAA=1, BB\\x:\n\t1\t2\t3\n1\t0.78125\t0.625\t0.46875\n2\t0.78125\t0.625\t0.46875\n\nR=? [ F \"done\"&d>=x ]:\nAA=0, BB\\x:\n\t1\t2\t3\n1\t1\tInfinity\tInfinity\n2\t1\tInfinity\tInfinity\n\nAA=1, BB\\x:\n\t1\t2\t3\n1\t1\tInfinity\tInfinity\n2\t1\tInfinity\tInfinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.all.txt",
    "content": "\"Property_1\": P>0.55 [ F s=7&d>x ]:\nAA\tBB\tx\tResult\n0\t1\t1\ttrue\n0\t1\t2\ttrue\n0\t1\t3\tfalse\n0\t2\t1\ttrue\n0\t2\t2\ttrue\n0\t2\t3\tfalse\n1\t1\t1\ttrue\n1\t1\t2\ttrue\n1\t1\t3\tfalse\n1\t2\t1\ttrue\n1\t2\t2\ttrue\n1\t2\t3\tfalse\n\n\"Intriguing\": P=? [ F<=5 s=7&d>x ]:\nAA\tBB\tx\tResult\n0\t1\t1\t0.78125\n0\t1\t2\t0.625\n0\t1\t3\t0.46875\n0\t2\t1\t0.78125\n0\t2\t2\t0.625\n0\t2\t3\t0.46875\n1\t1\t1\t0.78125\n1\t1\t2\t0.625\n1\t1\t3\t0.46875\n1\t2\t1\t0.78125\n1\t2\t2\t0.625\n1\t2\t3\t0.46875\n\nP=? [ F<=5 s=7&d>x ]:\nAA\tBB\tx\tResult\n0\t1\t1\t0.78125\n0\t1\t2\t0.625\n0\t1\t3\t0.46875\n0\t2\t1\t0.78125\n0\t2\t2\t0.625\n0\t2\t3\t0.46875\n1\t1\t1\t0.78125\n1\t1\t2\t0.625\n1\t1\t3\t0.46875\n1\t2\t1\t0.78125\n1\t2\t2\t0.625\n1\t2\t3\t0.46875\n\nR=? [ F \"done\"&d>=x ]:\nAA\tBB\tx\tResult\n0\t1\t1\t1\n0\t1\t2\tInfinity\n0\t1\t3\tInfinity\n0\t2\t1\t1\n0\t2\t2\tInfinity\n0\t2\t3\tInfinity\n1\t1\t1\t1\n1\t1\t2\tInfinity\n1\t1\t3\tInfinity\n1\t2\t1\t1\n1\t2\t2\tInfinity\n1\t2\t3\tInfinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.args",
    "content": "-prop 1 -const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.1.txt\n-prop 1 -const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.1.csv:csv\n-prop 1 -const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.1.comment.txt:comment\n-prop 1 -const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.1.matrix.txt:matrix\n-prop 1 -const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.1.matrix.csv:matrix,csv\n-prop 1 -const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.1.dataframe.csv:dataframe\n-importresults exportresults.pm.props.1.dataframe.csv -exportresults exportresults.pm.props.1.dataframe.csv:dataframe\n\n-const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.all.txt\n-const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.all.csv:csv\n-const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.all.comment.txt:comment\n-const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.all.matrix.txt:matrix\n-const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.all.matrix.csv:matrix,csv\n-const AA=0:1,x=1:3,BB=1:2 -exportresults exportresults.pm.props.all.dataframe.csv:dataframe\n-importresults exportresults.pm.props.all.dataframe.csv -exportresults exportresults.pm.props.all.dataframe.csv:dataframe\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults.pm.props.out",
    "content": "P>0.1 [ F s=7&d=x ]:\nAA=0, BB\\x:\n\t1\t2\t3\n1\ttrue\ttrue\ttrue\n2\ttrue\ttrue\ttrue\n\nAA=1, BB\\x:\n\t1\t2\t3\n1\ttrue\ttrue\ttrue\n2\ttrue\ttrue\ttrue\n\nP=? [ F s=7&d=6 ]:\nAA\\BB:\n\t1\t2\n0\t0.16666650772094727\t0.16666650772094727\n1\t0.16666650772094727\t0.16666650772094727\n\nP=? [ F s=7&d=x ]:\nAA=0, BB\\x:\n\t1\t2\t3\n1\t0.16666650772094727\t0.16666650772094727\t0.16666650772094727\n2\t0.16666650772094727\t0.16666650772094727\t0.16666650772094727\n\nAA=1, BB\\x:\n\t1\t2\t3\n1\t0.16666650772094727\t0.16666650772094727\t0.16666650772094727\n2\t0.16666650772094727\t0.16666650772094727\t0.16666650772094727\n\nR=? [ F s=7 ]:\nAA\\BB:\n\t1\t2\n0\t3.6666650772094727\t3.6666650772094727\n1\t3.6666650772094727\t3.6666650772094727\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm",
    "content": "// Model (and properties) hacked a bit to things that can be\r\n// reliably tested on both symbolic/explicit engines\r\n\r\ndtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\ts=0 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.args",
    "content": "-h\n-ex\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props",
    "content": "const int x;\n\nlabel \"done\" = s=7;\n\n// RESULT (x=1): true\n// RESULT (x=2): true\n// RESULT (x=3): false\n\"Property_1\": P>0.55 [ F s=7 & d>x ];\n\n// RESULT: 0.46875\n\"Intriguing\": P=? [ F<=5 s=7 & d>3 ];\n\n// RESULT (x=1): 1.0\n// RESULT (x=2): Infinity\n// RESULT (x=3): Infinity\nR=? [ F \"done\" & d>=x ];\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.1.comment.txt",
    "content": "// RESULT (x=1): true\n// RESULT (x=2): true\n// RESULT (x=3): false\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.1.csv",
    "content": "x,Result\n1,true\n2,true\n3,false\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.1.dataframe.csv",
    "content": "Property,x,Result\nProperty_1,1,true\nProperty_1,2,true\nProperty_1,3,false\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.1.matrix.csv",
    "content": "\"x\"\n1,2,3\ntrue,true,false\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.1.matrix.txt",
    "content": "x:\n1\t2\t3\ntrue\ttrue\tfalse\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.1.txt",
    "content": "x\tResult\n1\ttrue\n2\ttrue\n3\tfalse\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.all.comment.txt",
    "content": "// RESULT (x=1): true\n// RESULT (x=2): true\n// RESULT (x=3): false\n\"Property_1\": P>0.55 [ F s=7&d>x ]\n\n// RESULT: 0.46875\n\"Intriguing\": P=? [ F<=5 s=7&d>3 ]\n\n// RESULT (x=1): 1\n// RESULT (x=2): Infinity\n// RESULT (x=3): Infinity\nR=? [ F \"done\"&d>=x ]\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.all.csv",
    "content": "\"\"\"Property_1\"\": P>0.55 [ F s=7&d>x ]\"\nx,Result\n1,true\n2,true\n3,false\n\n\"\"\"Intriguing\"\": P=? [ F<=5 s=7&d>3 ]\"\nResult\n0.46875\n\n\"R=? [ F \"\"done\"\"&d>=x ]\"\nx,Result\n1,1\n2,Infinity\n3,Infinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.all.dataframe.csv",
    "content": "Property,x,Result\nProperty_1,1,true\nProperty_1,2,true\nProperty_1,3,false\nIntriguing,,0.46875\nProperty_3,1,1\nProperty_3,2,Infinity\nProperty_3,3,Infinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.all.matrix.csv",
    "content": "\"\"\"Property_1\"\": P>0.55 [ F s=7&d>x ]\"\n\"x\"\n1,2,3\ntrue,true,false\n\n\"\"\"Intriguing\"\": P=? [ F<=5 s=7&d>3 ]\"\n0.46875\n\n\"R=? [ F \"\"done\"\"&d>=x ]\"\n\"x\"\n1,2,3\n1,Infinity,Infinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.all.matrix.txt",
    "content": "\"Property_1\": P>0.55 [ F s=7&d>x ]:\nx:\n1\t2\t3\ntrue\ttrue\tfalse\n\n\"Intriguing\": P=? [ F<=5 s=7&d>3 ]:\n0.46875\n\nR=? [ F \"done\"&d>=x ]:\nx:\n1\t2\t3\n1\tInfinity\tInfinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.all.txt",
    "content": "\"Property_1\": P>0.55 [ F s=7&d>x ]:\nx\tResult\n1\ttrue\n2\ttrue\n3\tfalse\n\n\"Intriguing\": P=? [ F<=5 s=7&d>3 ]:\nResult\n0.46875\n\nR=? [ F \"done\"&d>=x ]:\nx\tResult\n1\t1\n2\tInfinity\n3\tInfinity\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.args",
    "content": "-prop 1 -const x=1:3 -exportresults exportresults2.pm.props.1.txt\n-prop 1 -const x=1:3 -exportresults exportresults2.pm.props.1.csv:csv\n-prop 1 -const x=1:3 -exportresults exportresults2.pm.props.1.comment.txt:comment\n-prop 1 -const x=1:3 -exportresults exportresults2.pm.props.1.matrix.txt:matrix\n-prop 1 -const x=1:3 -exportresults exportresults2.pm.props.1.matrix.csv:matrix,csv\n-prop 1 -const x=1:3 -exportresults exportresults2.pm.props.1.dataframe.csv:dataframe\n-importresults exportresults2.pm.props.1.dataframe.csv -exportresults exportresults2.pm.props.1.dataframe.csv:dataframe\n\n-const x=1:3 -exportresults exportresults2.pm.props.all.txt\n-const x=1:3 -exportresults exportresults2.pm.props.all.csv:csv\n-const x=1:3 -exportresults exportresults2.pm.props.all.comment.txt:comment\n-const x=1:3 -exportresults exportresults2.pm.props.all.matrix.txt:matrix\n-const x=1:3 -exportresults exportresults2.pm.props.all.matrix.csv:matrix,csv\n-const x=1:3 -exportresults exportresults2.pm.props.all.dataframe.csv:dataframe\n-importresults exportresults2.pm.props.all.dataframe.csv -exportresults exportresults2.pm.props.all.dataframe.csv:dataframe\n\n-prop 1 -const x=1 -exportresults exportresults2.pm.props.single.1.txt\n-prop 1 -const x=1 -exportresults exportresults2.pm.props.single.1.csv:csv\n-prop 1 -const x=1 -exportresults exportresults2.pm.props.single.1.comment.txt:comment\n-prop 1 -const x=1 -exportresults exportresults2.pm.props.single.1.matrix.txt:matrix\n-prop 1 -const x=1 -exportresults exportresults2.pm.props.single.1.matrix.csv:matrix,csv\n-prop 1 -const x=1 -exportresults exportresults2.pm.props.single.1.dataframe.csv:dataframe\n-importresults exportresults2.pm.props.single.1.dataframe.csv -exportresults exportresults2.pm.props.single.1.dataframe.csv:dataframe\n\n-const x=1 -exportresults exportresults2.pm.props.single.all.txt\n-const x=1 -exportresults exportresults2.pm.props.single.all.csv:csv\n-const x=1 -exportresults exportresults2.pm.props.single.all.comment.txt:comment\n-const x=1 -exportresults exportresults2.pm.props.single.all.matrix.txt:matrix\n-const x=1 -exportresults exportresults2.pm.props.single.all.matrix.csv:matrix,csv\n-const x=1 -exportresults exportresults2.pm.props.single.all.dataframe.csv:dataframe\n-importresults exportresults2.pm.props.single.all.dataframe.csv -exportresults exportresults2.pm.props.single.all.dataframe.csv:dataframe\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.1.comment.txt",
    "content": "// RESULT (x=1): true\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.1.csv",
    "content": "Result\ntrue\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.1.dataframe.csv",
    "content": "Property,Result\nProperty_1,true\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.1.matrix.csv",
    "content": "true\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.1.matrix.txt",
    "content": "true\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.1.txt",
    "content": "Result\ntrue\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.all.comment.txt",
    "content": "// RESULT (x=1): true\n\"Property_1\": P>0.55 [ F s=7&d>x ]\n\n// RESULT: 0.46875\n\"Intriguing\": P=? [ F<=5 s=7&d>3 ]\n\n// RESULT (x=1): 1\nR=? [ F \"done\"&d>=x ]\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.all.csv",
    "content": "\"\"\"Property_1\"\": P>0.55 [ F s=7&d>x ]\"\nResult\ntrue\n\n\"\"\"Intriguing\"\": P=? [ F<=5 s=7&d>3 ]\"\nResult\n0.46875\n\n\"R=? [ F \"\"done\"\"&d>=x ]\"\nResult\n1\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.all.dataframe.csv",
    "content": "Property,Result\nProperty_1,true\nIntriguing,0.46875\nProperty_3,1\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.all.matrix.csv",
    "content": "\"\"\"Property_1\"\": P>0.55 [ F s=7&d>x ]\"\ntrue\n\n\"\"\"Intriguing\"\": P=? [ F<=5 s=7&d>3 ]\"\n0.46875\n\n\"R=? [ F \"\"done\"\"&d>=x ]\"\n1\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.all.matrix.txt",
    "content": "\"Property_1\": P>0.55 [ F s=7&d>x ]:\ntrue\n\n\"Intriguing\": P=? [ F<=5 s=7&d>3 ]:\n0.46875\n\nR=? [ F \"done\"&d>=x ]:\n1\n"
  },
  {
    "path": "prism-tests/functionality/export/results/exportresults2.pm.props.single.all.txt",
    "content": "\"Property_1\": P>0.55 [ F s=7&d>x ]:\nResult\ntrue\n\n\"Intriguing\": P=? [ F<=5 s=7&d>3 ]:\nResult\n0.46875\n\nR=? [ F \"done\"&d>=x ]:\nResult\n1\n"
  },
  {
    "path": "prism-tests/functionality/export/target/dice.pm",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/target/dice.pm.ltl.lab",
    "content": "0=\"init\" 1=\"target\"\n0: 1\n1: 1\n2: 0\n"
  },
  {
    "path": "prism-tests/functionality/export/target/dice.pm.ltl.props",
    "content": "// RESULT:1/3\n\"ltl\": P=? [ F X d>4 ]\n"
  },
  {
    "path": "prism-tests/functionality/export/target/dice.pm.ltl.props.args",
    "content": "-exporttarget dice.pm.ltl.lab\n"
  },
  {
    "path": "prism-tests/functionality/export/target/dice.pm.reach.lab",
    "content": "0=\"init\" 1=\"target\"\n0: 0\n11: 1\n12: 1\n"
  },
  {
    "path": "prism-tests/functionality/export/target/dice.pm.reach.props",
    "content": "// RESULT:1/3\n\"reach\": P=? [ F d>4 ]\n"
  },
  {
    "path": "prism-tests/functionality/export/target/dice.pm.reach.props.args",
    "content": "-exporttarget dice.pm.reach.lab\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.pm.ltl.lab",
    "content": "0=\"init\" 1=\"target\"\n0: 0\n4: 1\n5: 1\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.pm.ltl2.lab",
    "content": "0=\"init\" 1=\"target\"\n2: 1\n8: 1\n9: 0\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.pm.reach.lab",
    "content": "0=\"init\" 1=\"target\"\n0: 0\n5: 1\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.prism",
    "content": "mdp\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n\r\nrewards \"energy\"\r\n\ttrue : 0.1;\r\n\ts<2 | s>3 : 2.2;\r\n\t[stuck] true : 3.5;\r\nendrewards\r\n\r\nrewards \"move\"\r\n\t[north] true : 1;\r\n\t[south] true : 1;\r\n\t[east] true : 1;\r\n\t[west] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.prism.ltl.props",
    "content": "// RESULT: 0.5\n\"ltl\": Pmax=? [ G F \"goal1\" ]\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.prism.ltl.props.args",
    "content": "-exporttarget robot.pm.ltl.lab\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.prism.ltl2.props",
    "content": "// RESULT: 0.1\n\"ltl2\": Pmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.prism.ltl2.props.args",
    "content": "-exporttarget robot.pm.ltl2.lab\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.prism.reach.props",
    "content": "// RESULT: 0.5\n\"reach\": Pmax=? [ F \"goal1\" ]\n"
  },
  {
    "path": "prism-tests/functionality/export/target/robot.prism.reach.props.args",
    "content": "-exporttarget robot.pm.reach.lab\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism",
    "content": "dtmc\n\nconst int N;\n\nmodule M\n\n\tx : [-N..N] init 0;\n\t\n\t[] true -> 0.5:(x'=max(x-1,-N)) + 0.5:(x'=min(x+1,N));\n\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.1.props",
    "content": "// RESULT: 1.0\nP=? [ F<=3 x=0 ];\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.1.props.args",
    "content": "-const N=3 -exportvector exportvector.prism.1.props.txt\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.1.props.txt",
    "content": "0.125\n0.25\n0.625\n1.0\n0.625\n0.25\n0.125\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.2.props",
    "content": "// RESULT: 0.0\nP=? [ X X X x=0 ];\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.2.props.args",
    "content": "-const N=3 -exportvector exportvector.prism.2.props.txt\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.2.props.txt",
    "content": "0.125\n0.0\n0.375\n0.0\n0.375\n0.0\n0.125\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.3.props",
    "content": "// RESULT: 1.0\nfilter(sum, P=? [ X X X x=0 ]);\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.3.props.args",
    "content": "-const N=3 -exportvector exportvector.prism.3.props.txt\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.3.props.txt",
    "content": "1.0\n1.0\n1.0\n1.0\n1.0\n1.0\n1.0\n"
  },
  {
    "path": "prism-tests/functionality/export/vector/exportvector.prism.args",
    "content": "-ex\n-m\n-s\n-h\n"
  },
  {
    "path": "prism-tests/functionality/import/badge.pepa",
    "content": "% A small model (72 states) of a location tracking system based on \r\n% active badges made by Stephen Gilmore, Jane Hillston and \r\n% Graham Clark.  The paper ``Specifying performance measures for\r\n% PEPA'' appeared in the proceedings of Fifth International AMAST \r\n% Workshop on Real-Time and Probabilistic Systems, Bamberg 1999.\r\n% The proceedings were published as Springer-Verlag LNCS 1601.\r\n\r\nm = 0.1;\r\nr = 2.5;\r\ns = 45.0;\r\n\r\n#P14 = (reg14, r).P14 + (move15, m).P15;\r\n#P15 = (reg15, r).P15 + (move14, m).P14 + (move16, m).P16;\r\n#P16 = (reg16, r).P16 + (move15, m).P15;\r\n\r\n#S14 = (reg14, infty).T14;\r\n#S15 = (reg15, infty).T15;\r\n#S16 = (reg16, infty).T16;\r\n\r\n#T14 = (rep14, s).S14;\r\n#T15 = (rep15, s).S15;\r\n#T16 = (rep16, s).S16;\r\n\r\n#DB14 = (rep14,infty).DB14 + (rep15,infty).DB15 + (rep16,infty).DB16;\r\n#DB15 = (rep14,infty).DB14 + (rep15,infty).DB15 + (rep16,infty).DB16;\r\n#DB16 = (rep14,infty).DB14 + (rep15,infty).DB15 + (rep16,infty).DB16;\r\n\r\n( P14 <reg14,reg15,reg16> (S14 <> S15 <> S16) ) <rep14, rep15, rep16> DB14\r\n"
  },
  {
    "path": "prism-tests/functionality/import/badge.pepa.importexport.auto",
    "content": "-importpepa badge.pepa -exportmodel badge.pepa.sta,tra,lab\n"
  },
  {
    "path": "prism-tests/functionality/import/badge.pepa.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/functionality/import/badge.pepa.sta",
    "content": "(P14_STATE,S14_STATE,S15_STATE,S16_STATE,DB14_STATE)\n0:(0,0,0,0,0)\n1:(0,0,0,0,1)\n2:(0,0,0,0,2)\n3:(0,0,0,1,0)\n4:(0,0,0,1,1)\n5:(0,0,0,1,2)\n6:(0,0,1,0,0)\n7:(0,0,1,0,1)\n8:(0,0,1,0,2)\n9:(0,0,1,1,0)\n10:(0,0,1,1,1)\n11:(0,0,1,1,2)\n12:(0,1,0,0,0)\n13:(0,1,0,0,1)\n14:(0,1,0,0,2)\n15:(0,1,0,1,0)\n16:(0,1,0,1,1)\n17:(0,1,0,1,2)\n18:(0,1,1,0,0)\n19:(0,1,1,0,1)\n20:(0,1,1,0,2)\n21:(0,1,1,1,0)\n22:(0,1,1,1,1)\n23:(0,1,1,1,2)\n24:(1,0,0,0,0)\n25:(1,0,0,0,1)\n26:(1,0,0,0,2)\n27:(1,0,0,1,0)\n28:(1,0,0,1,1)\n29:(1,0,0,1,2)\n30:(1,0,1,0,0)\n31:(1,0,1,0,1)\n32:(1,0,1,0,2)\n33:(1,0,1,1,0)\n34:(1,0,1,1,1)\n35:(1,0,1,1,2)\n36:(1,1,0,0,0)\n37:(1,1,0,0,1)\n38:(1,1,0,0,2)\n39:(1,1,0,1,0)\n40:(1,1,0,1,1)\n41:(1,1,0,1,2)\n42:(1,1,1,0,0)\n43:(1,1,1,0,1)\n44:(1,1,1,0,2)\n45:(1,1,1,1,0)\n46:(1,1,1,1,1)\n47:(1,1,1,1,2)\n48:(2,0,0,0,0)\n49:(2,0,0,0,1)\n50:(2,0,0,0,2)\n51:(2,0,0,1,0)\n52:(2,0,0,1,1)\n53:(2,0,0,1,2)\n54:(2,0,1,0,0)\n55:(2,0,1,0,1)\n56:(2,0,1,0,2)\n57:(2,0,1,1,0)\n58:(2,0,1,1,1)\n59:(2,0,1,1,2)\n60:(2,1,0,0,0)\n61:(2,1,0,0,1)\n62:(2,1,0,0,2)\n63:(2,1,0,1,0)\n64:(2,1,0,1,1)\n65:(2,1,0,1,2)\n66:(2,1,1,0,0)\n67:(2,1,1,0,1)\n68:(2,1,1,0,2)\n69:(2,1,1,1,0)\n70:(2,1,1,1,1)\n71:(2,1,1,1,2)\n"
  },
  {
    "path": "prism-tests/functionality/import/badge.pepa.tra",
    "content": "72 240\n0 12 2.5 reg14\n0 24 0.1 move15\n1 13 2.5 reg14\n1 25 0.1 move15\n2 14 2.5 reg14\n2 26 0.1 move15\n3 15 2.5 reg14\n3 27 0.1 move15\n3 2 45 rep16\n4 16 2.5 reg14\n4 28 0.1 move15\n4 2 45 rep16\n5 17 2.5 reg14\n5 29 0.1 move15\n5 2 45 rep16\n6 18 2.5 reg14\n6 30 0.1 move15\n6 1 45 rep15\n7 19 2.5 reg14\n7 31 0.1 move15\n7 1 45 rep15\n8 20 2.5 reg14\n8 32 0.1 move15\n8 1 45 rep15\n9 21 2.5 reg14\n9 33 0.1 move15\n9 4 45 rep15\n9 8 45 rep16\n10 22 2.5 reg14\n10 34 0.1 move15\n10 4 45 rep15\n10 8 45 rep16\n11 23 2.5 reg14\n11 35 0.1 move15\n11 4 45 rep15\n11 8 45 rep16\n12 36 0.1 move15\n12 0 45 rep14\n13 37 0.1 move15\n13 0 45 rep14\n14 38 0.1 move15\n14 0 45 rep14\n15 39 0.1 move15\n15 3 45 rep14\n15 14 45 rep16\n16 40 0.1 move15\n16 3 45 rep14\n16 14 45 rep16\n17 41 0.1 move15\n17 3 45 rep14\n17 14 45 rep16\n18 42 0.1 move15\n18 6 45 rep14\n18 13 45 rep15\n19 43 0.1 move15\n19 6 45 rep14\n19 13 45 rep15\n20 44 0.1 move15\n20 6 45 rep14\n20 13 45 rep15\n21 45 0.1 move15\n21 9 45 rep14\n21 16 45 rep15\n21 20 45 rep16\n22 46 0.1 move15\n22 9 45 rep14\n22 16 45 rep15\n22 20 45 rep16\n23 47 0.1 move15\n23 9 45 rep14\n23 16 45 rep15\n23 20 45 rep16\n24 30 2.5 reg15\n24 0 0.1 move14\n24 48 0.1 move16\n25 31 2.5 reg15\n25 1 0.1 move14\n25 49 0.1 move16\n26 32 2.5 reg15\n26 2 0.1 move14\n26 50 0.1 move16\n27 33 2.5 reg15\n27 3 0.1 move14\n27 51 0.1 move16\n27 26 45 rep16\n28 34 2.5 reg15\n28 4 0.1 move14\n28 52 0.1 move16\n28 26 45 rep16\n29 35 2.5 reg15\n29 5 0.1 move14\n29 53 0.1 move16\n29 26 45 rep16\n30 6 0.1 move14\n30 54 0.1 move16\n30 25 45 rep15\n31 7 0.1 move14\n31 55 0.1 move16\n31 25 45 rep15\n32 8 0.1 move14\n32 56 0.1 move16\n32 25 45 rep15\n33 9 0.1 move14\n33 57 0.1 move16\n33 28 45 rep15\n33 32 45 rep16\n34 10 0.1 move14\n34 58 0.1 move16\n34 28 45 rep15\n34 32 45 rep16\n35 11 0.1 move14\n35 59 0.1 move16\n35 28 45 rep15\n35 32 45 rep16\n36 42 2.5 reg15\n36 12 0.1 move14\n36 60 0.1 move16\n36 24 45 rep14\n37 43 2.5 reg15\n37 13 0.1 move14\n37 61 0.1 move16\n37 24 45 rep14\n38 44 2.5 reg15\n38 14 0.1 move14\n38 62 0.1 move16\n38 24 45 rep14\n39 45 2.5 reg15\n39 15 0.1 move14\n39 63 0.1 move16\n39 27 45 rep14\n39 38 45 rep16\n40 46 2.5 reg15\n40 16 0.1 move14\n40 64 0.1 move16\n40 27 45 rep14\n40 38 45 rep16\n41 47 2.5 reg15\n41 17 0.1 move14\n41 65 0.1 move16\n41 27 45 rep14\n41 38 45 rep16\n42 18 0.1 move14\n42 66 0.1 move16\n42 30 45 rep14\n42 37 45 rep15\n43 19 0.1 move14\n43 67 0.1 move16\n43 30 45 rep14\n43 37 45 rep15\n44 20 0.1 move14\n44 68 0.1 move16\n44 30 45 rep14\n44 37 45 rep15\n45 21 0.1 move14\n45 69 0.1 move16\n45 33 45 rep14\n45 40 45 rep15\n45 44 45 rep16\n46 22 0.1 move14\n46 70 0.1 move16\n46 33 45 rep14\n46 40 45 rep15\n46 44 45 rep16\n47 23 0.1 move14\n47 71 0.1 move16\n47 33 45 rep14\n47 40 45 rep15\n47 44 45 rep16\n48 24 0.1 move15\n48 51 2.5 reg16\n49 25 0.1 move15\n49 52 2.5 reg16\n50 26 0.1 move15\n50 53 2.5 reg16\n51 27 0.1 move15\n51 50 45 rep16\n52 28 0.1 move15\n52 50 45 rep16\n53 29 0.1 move15\n53 50 45 rep16\n54 30 0.1 move15\n54 57 2.5 reg16\n54 49 45 rep15\n55 31 0.1 move15\n55 58 2.5 reg16\n55 49 45 rep15\n56 32 0.1 move15\n56 59 2.5 reg16\n56 49 45 rep15\n57 33 0.1 move15\n57 52 45 rep15\n57 56 45 rep16\n58 34 0.1 move15\n58 52 45 rep15\n58 56 45 rep16\n59 35 0.1 move15\n59 52 45 rep15\n59 56 45 rep16\n60 36 0.1 move15\n60 63 2.5 reg16\n60 48 45 rep14\n61 37 0.1 move15\n61 64 2.5 reg16\n61 48 45 rep14\n62 38 0.1 move15\n62 65 2.5 reg16\n62 48 45 rep14\n63 39 0.1 move15\n63 51 45 rep14\n63 62 45 rep16\n64 40 0.1 move15\n64 51 45 rep14\n64 62 45 rep16\n65 41 0.1 move15\n65 51 45 rep14\n65 62 45 rep16\n66 42 0.1 move15\n66 69 2.5 reg16\n66 54 45 rep14\n66 61 45 rep15\n67 43 0.1 move15\n67 70 2.5 reg16\n67 54 45 rep14\n67 61 45 rep15\n68 44 0.1 move15\n68 71 2.5 reg16\n68 54 45 rep14\n68 61 45 rep15\n69 45 0.1 move15\n69 57 45 rep14\n69 64 45 rep15\n69 68 45 rep16\n70 46 0.1 move15\n70 57 45 rep14\n70 64 45 rep15\n70 68 45 rep16\n71 47 0.1 move15\n71 57 45 rep14\n71 64 45 rep15\n71 68 45 rep16\n"
  },
  {
    "path": "prism-tests/functionality/import/dice-deadlock.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"end\" 3=\"six\"\n0: 0\n7: 1 2\n8: 1 2\n9: 1 2\n10: 1 2\n11: 1 2\n12: 1 2 3\n"
  },
  {
    "path": "prism-tests/functionality/import/dice-deadlock.pm.importexport.auto",
    "content": "-importmodel dice-deadlock.tra,lab -exportmodel dice-deadlock.tra,lab\n-importmodel dice-deadlock.tra,lab -exportmodel dice-deadlock.tra,lab -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/dice-deadlock.pm.orig",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 1/2 : (s'=1) + 1/2 : (s'=2);\r\n\t[] s=1 -> 1/2 : (s'=3) + 1/2 : (s'=4);\r\n\t[] s=2 -> 1/2 : (s'=5) + 1/2 : (s'=6);\r\n\t[] s=3 -> 1/2 : (s'=1) + 1/2 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 1/2 : (s'=7) & (d'=2) + 1/2 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 1/2 : (s'=7) & (d'=4) + 1/2 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 1/2 : (s'=2) + 1/2 : (s'=7) & (d'=6);\r\n//\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nlabel \"end\" = s=7;\r\nlabel \"six\" = d=6;\r\n\r\nrewards \"coin_flips\"\r\n\ts<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/import/dice-deadlock.tra",
    "content": "13 20\n0 1 0.5\n0 2 0.5\n1 3 0.5\n1 4 0.5\n2 5 0.5\n2 6 0.5\n3 1 0.5\n3 7 0.5\n4 8 0.5\n4 9 0.5\n5 10 0.5\n5 11 0.5\n6 2 0.5\n6 12 0.5\n7 7 1\n8 8 1\n9 9 1\n10 10 1\n11 11 1\n12 12 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.exact.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"end\" 3=\"six\"\n0: 0\n7: 2\n8: 2\n9: 2\n10: 2\n11: 2\n12: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.exact.srew",
    "content": "# Reward structure \"coin_flips\"\n# State rewards\n13 7\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n6 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.exact.sta",
    "content": "(s,d)\n0:(0,0)\n1:(1,0)\n2:(2,0)\n3:(3,0)\n4:(4,0)\n5:(5,0)\n6:(6,0)\n7:(7,1)\n8:(7,2)\n9:(7,3)\n10:(7,4)\n11:(7,5)\n12:(7,6)\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.exact.tra",
    "content": "13 20\n0 1 1/2\n0 2 1/2\n1 3 1/2\n1 4 1/2\n2 5 1/2\n2 6 1/2\n3 1 1/2\n3 7 1/2\n4 8 1/2\n4 9 1/2\n5 10 1/2\n5 11 1/2\n6 2 1/2\n6 12 1/2\n7 7 1\n8 8 1\n9 9 1\n10 10 1\n11 11 1\n12 12 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.exact.trew",
    "content": "# Reward structure \"coin_flips\"\n# Transition rewards\n13 0\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"end\" 3=\"six\"\n0: 0\n7: 2\n8: 2\n9: 2\n10: 2\n11: 2\n12: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.pm.importcheck.auto.disabled",
    "content": "-dtmc -importmodel dice.all dice.pm.props\n-dtmc -importmodel dice.all dice.pm.props -ex -prop 1\n-dtmc -importmodel dice.all dice.pm.props -ex -prop 2\n\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.pm.importexport.auto",
    "content": "-importmodel dice.all -exportmodel dice.all -ex\n-importmodel dice.all -exportmodel dice.all -h\n-importmodel dice.all -exportmodel dice.all -s\n\n# Partial\n-importmodel dice.tra,lab,srew -exportmodel dice.tra,lab,srew\n-importmodel dice.tra,sta,trew -exportmodel dice.tra,sta,trew\n\n# Import model info - exact\n-importmodel dice.all -exportmodel dice.exact.all -exact\n-importmodel dice.exact.all -exportmodel dice.exact.all -exact\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.pm.orig",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 1/2 : (s'=1) + 1/2 : (s'=2);\r\n\t[] s=1 -> 1/2 : (s'=3) + 1/2 : (s'=4);\r\n\t[] s=2 -> 1/2 : (s'=5) + 1/2 : (s'=6);\r\n\t[] s=3 -> 1/2 : (s'=1) + 1/2 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 1/2 : (s'=7) & (d'=2) + 1/2 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 1/2 : (s'=7) & (d'=4) + 1/2 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 1/2 : (s'=2) + 1/2 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nlabel \"end\" = s=7;\r\nlabel \"six\" = d=6;\r\n\r\nrewards \"coin_flips\"\r\n\ts<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.pm.props",
    "content": "// RESULT: 1/6\nP=? [ F d=6 ]\n\n// RESULT: 1/6\nP=? [ F \"six\" ]\n\n// RESULT: 11/3\nR=? [ F s=7 ]\n\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.srew",
    "content": "# Reward structure \"coin_flips\"\n# State rewards\n13 7\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n6 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.sta",
    "content": "(s,d)\n0:(0,0)\n1:(1,0)\n2:(2,0)\n3:(3,0)\n4:(4,0)\n5:(5,0)\n6:(6,0)\n7:(7,1)\n8:(7,2)\n9:(7,3)\n10:(7,4)\n11:(7,5)\n12:(7,6)\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.tra",
    "content": "13 20\n0 1 0.5\n0 2 0.5\n1 3 0.5\n1 4 0.5\n2 5 0.5\n2 6 0.5\n3 1 0.5\n3 7 0.5\n4 8 0.5\n4 9 0.5\n5 10 0.5\n5 11 0.5\n6 2 0.5\n6 12 0.5\n7 7 1\n8 8 1\n9 9 1\n10 10 1\n11 11 1\n12 12 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dice.trew",
    "content": "# Reward structure \"coin_flips\"\n# Transition rewards\n13 0\n"
  },
  {
    "path": "prism-tests/functionality/import/dice2.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"end\" 3=\"six\"\n0: 0\n7: 2\n8: 2\n9: 2\n10: 2\n11: 2\n12: 2 3\n"
  },
  {
    "path": "prism-tests/functionality/import/dice2.pm.importexport.auto",
    "content": "# No .sta file (bugfix regression check)\n\n-importmodel dice2.tra,lab,srew -exportmodel dice2.sta,tra,lab,srew\n-importmodel dice2.tra,lab,srew -exportmodel dice2.sta,tra,lab,srew -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/dice2.srew",
    "content": "# Reward structure \"coin_flips\"\n# State rewards\n13 7\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n6 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dice2.sta",
    "content": "(x)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n6:(6)\n7:(7)\n8:(8)\n9:(9)\n10:(10)\n11:(11)\n12:(12)\n"
  },
  {
    "path": "prism-tests/functionality/import/dice2.tra",
    "content": "13 20\n0 1 0.5\n0 2 0.5\n1 3 0.5\n1 4 0.5\n2 5 0.5\n2 6 0.5\n3 1 0.5\n3 7 0.5\n4 8 0.5\n4 9 0.5\n5 10 0.5\n5 11 0.5\n6 2 0.5\n6 12 0.5\n7 7 1\n8 8 1\n9 9 1\n10 10 1\n11 11 1\n12 12 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dtmc-deadlocks-fixed.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n2: 1\n3: 1\n5: 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dtmc-deadlocks-fixed.tra",
    "content": "6 8\n0 0 0.4 east\n0 1 0.6 east\n1 2 0.5 south\n1 4 0.5 south\n2 2 1\n3 3 1\n4 5 1 east\n5 5 1\n"
  },
  {
    "path": "prism-tests/functionality/import/dtmc-deadlocks.tra",
    "content": "6 5\n0 0 0.4 east\n0 1 0.6 east\n1 2 0.5 south\n1 4 0.5 south\n4 5 1 east\n"
  },
  {
    "path": "prism-tests/functionality/import/dtmc-deadlocks.tra.importexport.auto",
    "content": "-importmodel dtmc-deadlocks.tra -exportmodel dtmc-deadlocks-fixed.tra,lab -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/irobot.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"hazard\" 3=\"goal1\" 4=\"goal2\"\n0: 0\n1: 2\n2: 4\n3: 4\n5: 3\n"
  },
  {
    "path": "prism-tests/functionality/import/irobot.prism.importexport.auto",
    "content": "-importmodel irobot.all -exportmodel irobot.all -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/irobot.prism.orig",
    "content": "mdp\r\n\r\nconst double delta = 0.1;\r\nconst double p = 0.5-delta;\r\nconst double q = 0.5+delta;\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> [p,q]:(s'=4) + [1-q,1-p]:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/import/irobot.srew",
    "content": "# Reward structure \"time\"\n# State rewards\n6 6\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/import/irobot.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/import/irobot.tra",
    "content": "6 10 16\n0 0 0 [0.4,0.4] east\n0 0 1 [0.6,0.6] east\n0 1 1 [0.1,0.1] south\n0 1 3 [0.8,0.8] south\n0 1 4 [0.1,0.1] south\n1 0 2 [1,1] east\n1 1 2 [0.4,0.6] south\n1 1 4 [0.4,0.6] south\n2 0 2 [1,1] stuck\n3 0 3 [1,1] stuck\n4 0 5 [1,1] east\n4 1 3 [0.6,0.6] west\n4 1 4 [0.4,0.4] west\n5 0 4 [1,1] west\n5 1 2 [0.9,0.9] north\n5 1 5 [0.1,0.1] north\n"
  },
  {
    "path": "prism-tests/functionality/import/irobot.trew",
    "content": "# Reward structure \"time\"\n# Transition rewards\n6 10 0\n"
  },
  {
    "path": "prism-tests/functionality/import/lec3.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/functionality/import/lec3.pm.auto",
    "content": "-importmodel lec3.all -exportmodel lec3.all -ex\n-importmodel lec3.all -exportmodel lec3.all\n-importmodel lec3.tra,sta,lab,srew,trew -exportmodel lec3.tra,sta,lab,srew,trew -ex\n-importmodel lec3.tra,sta,lab,srew,trew -exportmodel lec3.tra,sta,lab,srew,trew\n"
  },
  {
    "path": "prism-tests/functionality/import/lec3.pm.orig",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"r\"\r\n\ts=0 : 2;\r\n\t[] s<3 : s;\r\nendrewards\r\n\r\nrewards \"s\"\r\n\ts>=4 : 1;\r\nendrewards\r\n\r\nrewards\r\n\t[] s<3 : s;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/import/lec3.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/import/lec3.tra",
    "content": "6 9\n0 1 0.5\n0 3 0.5\n1 0 0.5\n1 2 0.25\n1 4 0.25\n2 5 1\n3 3 1\n4 4 1\n5 2 1\n"
  },
  {
    "path": "prism-tests/functionality/import/lec31.srew",
    "content": "# Reward structure \"r\"\n# State rewards\n6 1\n0 2\n"
  },
  {
    "path": "prism-tests/functionality/import/lec31.trew",
    "content": "# Reward structure \"r\"\n# Transition rewards\n6 4\n1 0 1\n1 2 1\n1 4 1\n2 5 2\n"
  },
  {
    "path": "prism-tests/functionality/import/lec32.srew",
    "content": "# Reward structure \"s\"\n# State rewards\n6 2\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/import/lec32.trew",
    "content": "# Reward structure \"s\"\n# Transition rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/import/lec33.srew",
    "content": "# Reward structure\n# State rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/import/lec33.trew",
    "content": "# Reward structure\n# Transition rewards\n6 4\n1 0 1\n1 2 1\n1 4 1\n2 5 2\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl1.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"a\" 3=\"b\"\n0: 0 2 3\n1: 2\n3: 3\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl1.prism.importexport.auto",
    "content": "-importmodel lec9ctl1.all -exportmodel lec9ctl1.all\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl1.prism.orig",
    "content": "// Simple LTS from Lec 9 of Computer-Aided Verification\r\n\r\nmodule M\r\n\r\ns:[0..3];\r\n\r\n[] s=0 -> (s'=1);\r\n[] s=0 -> (s'=2);\r\n[] s=1 -> (s'=1);\r\n[] s=1 -> (s'=3);\r\n[] s=2 -> (s'=1);\r\n[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = s=0 | s=1;\r\nlabel \"b\" = s=0 | s=3;\r\n\r\nrewards \"r1\"\r\n\ts<2 : s;\r\nendrewards\r\n\r\nrewards \"r2\"\r\n\t[] s>=2 : s;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl1.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl1.tra",
    "content": "4 6 6\n0 0 1\n0 1 2\n1 0 1\n1 1 3\n2 0 1\n3 0 3\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl11.srew",
    "content": "# Reward structure \"r1\"\n# State rewards\n4 1\n1 1\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl11.trew",
    "content": "# Reward structure \"r1\"\n# Transition rewards\n4 6 0\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl12.srew",
    "content": "# Reward structure \"r2\"\n# State rewards\n4 0\n"
  },
  {
    "path": "prism-tests/functionality/import/lec9ctl12.trew",
    "content": "# Reward structure \"r2\"\n# Transition rewards\n4 6 2\n2 0 1 2\n3 0 3 3\n"
  },
  {
    "path": "prism-tests/functionality/import/maze.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/functionality/import/maze.obs",
    "content": "(west,east,north,south,target)\n0:(false,false,false,false,false)\n1:(true,false,true,false,false)\n2:(false,false,true,true,false)\n3:(false,false,true,false,false)\n4:(false,true,true,false,false)\n5:(true,true,false,false,false)\n6:(true,true,false,true,false)\n7:(true,true,false,true,true)\n"
  },
  {
    "path": "prism-tests/functionality/import/maze.prism.importexport.auto",
    "content": "-importmodel maze.all -exportmodel maze.all\n"
  },
  {
    "path": "prism-tests/functionality/import/maze.prism.orig",
    "content": "// maze example (POMDP)\n// Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n// gxn 29/01/16\n\n// state space (value of variable \"s\")\n\n//  0  1  2  3  4\n//  5     6     7\n//  8     10    9\n\n// 10 is the target\n\npomdp\n\n// can observe the walls and target\nobservable \"west\" = s=0|s=5|s=6|s=7|s=8|s=9|s=10; // wall to the west\nobservable \"east\" = s=4|s=5|s=6|s=7|s=8|s=9|s=10; // wall to the east\nobservable \"north\" = s=0|s=1|s=2|s=3|s=4; // wall to the north\nobservable \"south\" = s=1|s=3|s=8|s=9|s=10; // wall to the south\nobservable \"target\" = s=10; //target\n\nmodule maze\n\n\ts : [-1..10];\n\t\n\t// initialisation\n\t[] s=-1 -> 0.1 : (s'=0)\n\t\t\t + 0.1 : (s'=1)\n\t\t\t + 0.1 : (s'=2)\n\t\t\t + 0.1 : (s'=3)\n\t\t\t + 0.1 : (s'=4)\n\t\t\t + 0.1 : (s'=5)\n\t\t\t + 0.1 : (s'=6)\n\t\t\t + 0.1 : (s'=7)\n\t\t\t + 0.1 : (s'=8)\n\t\t\t + 0.1 : (s'=9);\n\t\n\t// moving around the maze\n\n\t[east] s=0 -> (s'=1);\n\t[south] s=0 -> (s'=5);\n\n\t[east] s=1 -> (s'=2);\n\t[west] s=1 -> (s'=0);\n\n\t[east] s=2 -> (s'=3);\n\t[west] s=2 -> (s'=1);\n\t[south] s=2 -> (s'=6);\n\n\t[east] s=3 -> (s'=4);\n\t[west] s=3 -> (s'=2);\n\n\t[west] s=4 -> (s'=3);\n\t[south] s=4 -> (s'=7);\n\n\t[north] s=5 -> (s'=0);\n\t[south] s=5 -> (s'=8);\n\n\t[north] s=6 -> (s'=2);\n\t[south] s=6 -> (s'=10);\n\n\t[north] s=7 -> (s'=4);\n\t[south] s=7 -> (s'=9);\n\n\t[north] s=8 -> (s'=5);\n\n\t[north] s=9 -> (s'=7);\n\n\t// loop when we reach the target\n\t[done] s=10 -> true;\n\nendmodule\n\n// reward structure (number of steps to reach the target)\nrewards\n\n\t[east] true : 1;\n\t[west] true : 1;\n\t[north] true : 1;\n\t[south] true : 1;\n\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/import/maze.srew",
    "content": "# Reward structure\n# State rewards\n12 0\n"
  },
  {
    "path": "prism-tests/functionality/import/maze.sta",
    "content": "(s)\n0:(-1)\n1:(0)\n2:(1)\n3:(2)\n4:(3)\n5:(4)\n6:(5)\n7:(6)\n8:(7)\n9:(8)\n10:(9)\n11:(10)\n"
  },
  {
    "path": "prism-tests/functionality/import/maze.tra",
    "content": "12 21 30 8\n- - 0 - 0\n0 0 1 0.1 1\n0 0 2 0.1 2\n0 0 3 0.1 3\n0 0 4 0.1 2\n0 0 5 0.1 4\n0 0 6 0.1 5\n0 0 7 0.1 5\n0 0 8 0.1 5\n0 0 9 0.1 6\n0 0 10 0.1 6\n1 0 2 1 2 east\n1 1 6 1 5 south\n2 0 3 1 3 east\n2 1 1 1 1 west\n3 0 4 1 2 east\n3 1 7 1 5 south\n3 2 2 1 2 west\n4 0 5 1 4 east\n4 1 3 1 3 west\n5 0 8 1 5 south\n5 1 4 1 2 west\n6 0 9 1 6 south\n6 1 1 1 1 north\n7 0 11 1 7 south\n7 1 3 1 3 north\n8 0 10 1 6 south\n8 1 5 1 4 north\n9 0 6 1 5 north\n10 0 8 1 5 north\n11 0 11 1 7 done\n"
  },
  {
    "path": "prism-tests/functionality/import/maze.trew",
    "content": "# Reward structure\n# Transition rewards\n12 21 19\n1 0 2 1\n1 1 6 1\n2 0 3 1\n2 1 1 1\n3 0 4 1\n3 1 7 1\n3 2 2 1\n4 0 5 1\n4 1 3 1\n5 0 8 1\n5 1 4 1\n6 0 9 1\n6 1 1 1\n7 0 11 1\n7 1 3 1\n8 0 10 1\n8 1 5 1\n9 0 6 1\n10 0 8 1\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp-deadlocks-fixed.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n2: 1\n3: 1\n5: 1\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp-deadlocks-fixed.tra",
    "content": "6 6 8\n0 0 0 0.4 east\n0 0 1 0.6 east\n1 0 2 0.5 south\n1 0 4 0.5 south\n2 0 2 1\n3 0 3 1\n4 0 5 1 east\n5 0 5 1\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp-deadlocks.tra",
    "content": "6 3 5\n0 0 0 0.4 east\n0 0 1 0.6 east\n1 0 2 0.5 south\n1 0 4 0.5 south\n4 0 5 1 east\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp-deadlocks.tra.importexport.auto",
    "content": "-importmodel mdp-deadlocks.tra -exportmodel mdp-deadlocks-fixed.tra,lab -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple.lab",
    "content": "0=\"init\" 1=\"deadlock\"\n0: 0\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple.prism.exportmodel.auto",
    "content": "-importmodel mdp_simple.all -exportmodel mdp_simple.all\n-importmodel mdp_simple.all -exportmodel mdp_simple.all -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple.prism.orig",
    "content": "mdp\r\n\r\nmodule m1\r\n\ts : [0..5];\r\n\tt : [0..2];\r\n\r\n\t[a] s=0 & t=0 -> (s'=1);\r\n\t[b] s=0 & t=0 -> 0.1 : (t'=1)&(s'=0) + 0.9 : (t'=2)&(s'=0);\r\n\r\n\t[a] s=1 & t=0 -> (s'=2);\r\n\t[b] s=1 & t=0 -> 0.2 : (t'=1)&(s'=0) + 0.8 : (t'=2)&(s'=0);\r\n\r\n\t[a] s=2 & t=0 -> (s'=3);\r\n\t[b] s=2 & t=0 -> 0.3 : (t'=1)&(s'=1) + 0.7 : (t'=2)&(s'=1);\r\n\r\n\t[a] s=3 & t=0 -> (s'=4);\r\n\t[b] s=3 & t=0 -> 0.4 : (t'=1)&(s'=0)+ 0.6 : (t'=2)&(s'=0);\r\n\r\n\t[a] s=4 & t=0 -> (s'=5);\r\n\t[b] s=4 & t=0 -> 0.5 : (t'=1)&(s'=0) + 0.5 : (t'=2)&(s'=0);\r\n\r\n\t[] s=5 & t=0 -> (t'=1)&(s'=0);\r\n\r\n\t[] t>0 -> true;\r\n\r\nendmodule\r\n\r\nrewards \r\n    mod(s,2)=0 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple.srew",
    "content": "# Reward structure\n# State rewards\n10 5\n0 1\n1 1\n2 1\n6 1\n8 1\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple.sta",
    "content": "(s,t)\n0:(0,0)\n1:(0,1)\n2:(0,2)\n3:(1,0)\n4:(1,1)\n5:(1,2)\n6:(2,0)\n7:(3,0)\n8:(4,0)\n9:(5,0)\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple.tra",
    "content": "10 15 20\n0 0 1 0.1 b\n0 0 2 0.9 b\n0 1 3 1 a\n1 0 1 1\n2 0 2 1\n3 0 1 0.2 b\n3 0 2 0.8 b\n3 1 6 1 a\n4 0 4 1\n5 0 5 1\n6 0 4 0.3 b\n6 0 5 0.7 b\n6 1 7 1 a\n7 0 1 0.4 b\n7 0 2 0.6 b\n7 1 8 1 a\n8 0 1 0.5 b\n8 0 2 0.5 b\n8 1 9 1 a\n9 0 1 1\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple.trew",
    "content": "# Reward structure\n# Transition rewards\n10 15 0\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple_mod.auto",
    "content": "-importmodel mdp_simple_mod.tra -exportmodel mdp_simple.tra\n"
  },
  {
    "path": "prism-tests/functionality/import/mdp_simple_mod.tra",
    "content": "10 15 20\n0 0 1 0.1 b\n0 0 2 0.9 b\n0 1 3 1 a\n1 0 1 1 \n2 0 2 1\n3 0 1 0.2 b\n3 0 2 0.8 b\n3 1 6 1 a\n4 0 4 1\n5 0 5 1\n6 0 4 0.3 b\n6 0 5 0.7 b\n6 1 7 1 a\n7 0 1 0.4 b\n7 0 2 0.6 b\n7 1 8 1 a\n8 0 1 0.5 b\n8 0 2 0.5 b\n8 1 9 1 a\n9 0 1 1\n"
  },
  {
    "path": "prism-tests/functionality/import/poll2.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"idle1\" 3=\"idle12\" 4=\"serve1\"\n0: 0 2 3\n1: 2\n4: 4\n5: 4\n6: 2 3\n7: 2\n10: 2\n"
  },
  {
    "path": "prism-tests/functionality/import/poll2.sm.importcheck.auto.disabled",
    "content": "-ctmc -importmodel poll2.all poll2.sm.props\n-ctmc -importmodel poll2.all poll2.sm.props -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/poll2.sm.importexport.auto",
    "content": "-importmodel poll2.all -exportmodel poll2.sta,tra,lab,srew\n-importmodel poll2.all -exportmodel poll2.sta,tra,lab,srew -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/poll2.sm.orig",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 2;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..2]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\n//rewards \"served\"\r\n//\t[serve1] true : 1;\r\n//endrewards\r\n\r\nlabel \"idle1\" = s1=0;\r\nlabel \"idle12\" = s1=0 & s2=0;\r\nlabel \"serve1\" = s=1 & a=1;\r\n"
  },
  {
    "path": "prism-tests/functionality/import/poll2.sm.props",
    "content": "// RESULT: 0.393469\nP=? [ F<=1 s1!=0 ]\n\n// RESULT: 0.393469\nP=? [ F<=1 !\"idle1\" ]\n"
  },
  {
    "path": "prism-tests/functionality/import/poll2.srew",
    "content": "# Reward structure\n# State rewards\n12 0\n"
  },
  {
    "path": "prism-tests/functionality/import/poll2.sta",
    "content": "(s,a,s1,s2)\n0:(1,0,0,0)\n1:(1,0,0,1)\n2:(1,0,1,0)\n3:(1,0,1,1)\n4:(1,1,1,0)\n5:(1,1,1,1)\n6:(2,0,0,0)\n7:(2,0,0,1)\n8:(2,0,1,0)\n9:(2,0,1,1)\n10:(2,1,0,1)\n11:(2,1,1,1)\n"
  },
  {
    "path": "prism-tests/functionality/import/poll2.tra",
    "content": "12 22\n0 1 0.5\n0 2 0.5\n0 6 200\n1 3 0.5\n1 7 200\n2 3 0.5\n2 4 200\n3 5 200\n4 5 0.5\n4 6 1\n5 7 1\n6 0 200\n6 7 0.5\n6 8 0.5\n7 9 0.5\n7 10 200\n8 2 200\n8 9 0.5\n9 11 200\n10 0 1\n10 11 0.5\n11 2 1\n"
  },
  {
    "path": "prism-tests/functionality/import/robot.lab",
    "content": "0=\"init\" 1=\"deadlock\" 2=\"hazard\" 3=\"goal1\" 4=\"goal2\"\n0: 0\n1: 2\n2: 4\n3: 4\n5: 3\n"
  },
  {
    "path": "prism-tests/functionality/import/robot.prism.importcheck.auto.disabled",
    "content": "-importmodel robot.all robot.prism.props\n-importmodel robot.all robot.prism.props -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/robot.prism.importexport.auto",
    "content": "-importmodel robot.all -exportmodel robot.all\n-importmodel robot.all -exportmodel robot.all -ex\n\n-importmodel robot.sta,tra,lab -exportmodel robot.sta,tra,lab\n-importmodel robot.sta,tra,lab -exportmodel robot.sta,tra,lab -ex\n"
  },
  {
    "path": "prism-tests/functionality/import/robot.prism.orig",
    "content": "mdp\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n\r\nrewards \"energy\"\r\n\ttrue : 0.1;\r\n\ts<2 | s>3 : 2.2;\r\n\t[stuck] true : 3.5;\r\nendrewards\r\n\r\nrewards \"move\"\r\n\t[north] true : 1;\r\n\t[south] true : 1;\r\n\t[east] true : 1;\r\n\t[west] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/import/robot.prism.props",
    "content": "// RESULT: Infinity\nRmin=? [ F \"goal1\" ]\n\n// RESULT: Infinity\nRmax=? [ F \"goal1\" ]\n\n// RESULT: 19/15\nRmin=? [ F \"goal2\" ]\n\n// RESULT: Infinity\nRmax=? [ F \"goal2\" ]\n\n// RESULT: 1.2\nRmin=? [ F (\"goal1\"|\"goal2\") ]\n\n// RESULT: 3.5\nRmax=? [ F (\"goal1\"|\"goal2\") ]\n"
  },
  {
    "path": "prism-tests/functionality/import/robot.sta",
    "content": "(s)\n0:(0)\n1:(1)\n2:(2)\n3:(3)\n4:(4)\n5:(5)\n"
  },
  {
    "path": "prism-tests/functionality/import/robot.tra",
    "content": "6 10 16\n0 0 1 0.1 south\n0 0 3 0.8 south\n0 0 4 0.1 south\n0 1 0 0.4 east\n0 1 1 0.6 east\n1 0 2 0.5 south\n1 0 4 0.5 south\n1 1 2 1 east\n2 0 2 1 stuck\n3 0 3 1 stuck\n4 0 3 0.6 west\n4 0 4 0.4 west\n4 1 5 1 east\n5 0 2 0.9 north\n5 0 5 0.1 north\n5 1 4 1 west\n"
  },
  {
    "path": "prism-tests/functionality/import/robot1.srew",
    "content": "# Reward structure \"time\"\n# State rewards\n6 6\n0 1\n1 1\n2 1\n3 1\n4 1\n5 1\n"
  },
  {
    "path": "prism-tests/functionality/import/robot1.trew",
    "content": "# Reward structure \"time\"\n# Transition rewards\n6 10 0\n"
  },
  {
    "path": "prism-tests/functionality/import/robot2.srew",
    "content": "# Reward structure \"energy\"\n# State rewards\n6 6\n0 2.3\n1 2.3\n2 0.1\n3 0.1\n4 2.3\n5 2.3\n"
  },
  {
    "path": "prism-tests/functionality/import/robot2.trew",
    "content": "# Reward structure \"energy\"\n# Transition rewards\n6 10 2\n2 0 2 3.5\n3 0 3 3.5\n"
  },
  {
    "path": "prism-tests/functionality/import/robot3.srew",
    "content": "# Reward structure \"move\"\n# State rewards\n6 0\n"
  },
  {
    "path": "prism-tests/functionality/import/robot3.trew",
    "content": "# Reward structure \"move\"\n# Transition rewards\n6 10 14\n0 0 1 1\n0 0 3 1\n0 0 4 1\n0 1 0 1\n0 1 1 1\n1 0 2 1\n1 0 4 1\n1 1 2 1\n4 0 3 1\n4 0 4 1\n4 1 5 1\n5 0 2 1\n5 0 5 1\n5 1 4 1\n"
  },
  {
    "path": "prism-tests/functionality/language/constrefs.prism",
    "content": "dtmc\r\n\r\nconst int N;\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5: (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/language/constrefs.prism.props",
    "content": "const int M = N;\nconst int x;\n\n// RESULT: 1/6\nP=? [ F s=7+M & d=x ]\n"
  },
  {
    "path": "prism-tests/functionality/language/constrefs.prism.props.args",
    "content": "-const N=0,x=6 -h\n-const N=0,x=6 -ex\n"
  },
  {
    "path": "prism-tests/functionality/language/func_power.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/language/func_power.prism.props",
    "content": "// Some tests of pow(), in each case:\n// * occurring in a constant (so Expression evaluation)\n// * occurring in a constant property (so probably model checking)\n// * occurring in a state-dependent property (so model checking, various engines)\n\n// RESULT: 1\n\"one\": s+1;\n\n// RESULT: 1\n\"one_s\": round(1+P=?[F<=1 d=6]);\n\n// RESULT: 1\n\"one_m\": round(P=?[F true]);\n\n// -------------------------\n\n// RESULT: 8\ncPow1; const int cPow1 = pow(2,3);\n\n// RESULT: 8\npow(2,3);\n\n// RESULT: 8\npow(2*\"one\", d+3);\n\n// RESULT: 8\npow(2*\"one_s\", d+3);\n\n// RESULT: 8\npow(2*\"one_m\", d+3);\n\n// -------------------------\n\n// RESULT: 1/4\ncPow2; const double cPow2 = pow(0.5, 2);\n\n// RESULT: 1/4\npow(0.5, 2);\n\n// RESULT: 1/4\npow(0.5*\"one\", d+2);\n\n// RESULT: 1/4\npow(0.5*\"one_s\", d+2);\n\n// RESULT: 1/4\npow(0.5*\"one_m\", d+2);\n\n// -------------------------\n\n// RESULT: 1/2\ncPow3; const double cPow3 = pow(2, -1.0);\n\n// RESULT: 1/2\npow(2, -1.0);\n\n// RESULT: 1/2\npow(2*\"one\", d-1.0);\n\n// RESULT: 1/2\npow(2*\"one_s\", d-1.0);\n\n// RESULT: 1/2\npow(2*\"one_m\", d-1.0);\n\n// -------------------------\n\n// Don't test errors for now - not done properly for symbolic/param\n\n// RESULT: Error\n//cPow4; const double cPow4 = pow(2,-1);\n\n// RESULT: Error:negative\n//pow(2, -1);\n\n// RESULT: Error:negative\n//pow(2*\"one\", d-1);\n\n// RESULT: Error:negative\n//pow(2*\"one_s\", d-1);\n\n// RESULT: Error:negative\n//pow(2*\"one_m\", d-1);\n\n// -------------------------\n"
  },
  {
    "path": "prism-tests/functionality/language/func_power.prism.props.args",
    "content": "-ex\n-exact\n-h\n-m\n-s\n"
  },
  {
    "path": "prism-tests/functionality/language/func_power.prism.root.props",
    "content": "// Some tests of pow(), in each case:\n// * occurring in a constant (so Expression evaluation)\n// * occurring in a constant property (so probably model checking)\n// * occurring in a state-dependent property (so model checking, various engines)\n\n// RESULT: 1\n\"one\": s+1;\n\n// RESULT: 1\n\"one_s\": round(1+P=?[F<=1 d=6]);\n\n// RESULT: 1\n\"one_m\": round(P=?[F true]);\n\n// -------------------------\n\n// RESULT: 1/2\ncPow4; const double cPow4 = pow(1/4, 1/2);\n\n// RESULT: 1/2\npow(1/4, 1/2);\n\n// RESULT: 1/2\npow(1/4*\"one\", d+1/2);\n\n// RESULT: 1/2\npow(1/4*\"one_s\", d+1/2);\n\n// RESULT: 1/2\npow(1/4*\"one_m\", d+1/2);\n\n// -------------------------\n"
  },
  {
    "path": "prism-tests/functionality/language/func_power.prism.root.props.args",
    "content": "-ex\n# -exact # no evaluation of roots as rationals\n-h\n-m\n"
  },
  {
    "path": "prism-tests/functionality/language/imdp-sync.prism",
    "content": "module M1\n\n\tx : [0..1];\n\t[a] x=0 -> [0.8,0.9]:(x'=0) + [0.1,0.2]:(x'=1);\n\t[b] x=1 -> true;\n\nendmodule\n\nmodule M2\n\n\ty : [0..1];\n\t[a] y=0 -> [0.8,0.9]:(y'=0) + [0.1,0.2]:(y'=1);\n\t[b] y=1 -> true;\n\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/language/imdp-sync.prism.auto",
    "content": "-exportmodel imdp-sync.tra -exportmodelprecision 15\n"
  },
  {
    "path": "prism-tests/functionality/language/imdp-sync.tra",
    "content": "4 4 7\n0 0 0 [0.64,0.81] a\n0 0 1 [0.08,0.18] a\n0 0 2 [0.08,0.18] a\n0 0 3 [0.01,0.04] a\n1 0 1 [1,1]\n2 0 2 [1,1]\n3 0 3 [1,1] b\n"
  },
  {
    "path": "prism-tests/functionality/language/infinite-rates.prism",
    "content": "// polling example [IT90]\n// gxn/dxp 26/01/00\n\nctmc\n\nconst int N = 2;\n\nconst double mu\t\t= 1/0;\nconst double gamma\t= 200;\nconst double lambda\t= mu/N;\n\nmodule server\n\t\n\ts : [1..2]; // station\n\ta : [0..1]; // action: 0=polling, 1=serving\n\t\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\n\t\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=1);\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\n\t\nendmodule\n\nmodule station1\n\t\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\n\t\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\n\t[]       (s1=0) -> lambda : (s1'=1);\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\n\t[serve1] (s1=1) -> 1 : (s1'=0);\n\t\nendmodule\n\n// construct further stations through renaming\n\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\n// (cumulative) rewards\n\n// expected time station 1 is waiting to be served\nrewards \"waiting\"\n\ts1=1 & !(s=1 & a=1) : 1;\nendrewards\n\n// expected number of times station 1 is served\nrewards \"served\"\n\t[serve1] true : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/language/infinite-rates.prism.props",
    "content": "// RESULT: Error\nP=? [ s1=1 ];\n"
  },
  {
    "path": "prism-tests/functionality/language/infinite-rates.prism.props.args",
    "content": "-s\n-ex\n"
  },
  {
    "path": "prism-tests/functionality/language/infinite-rewards.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\ts<7 : s/0;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/language/infinite-rewards.prism.props",
    "content": "// RESULT: Error\nR=? [F s=7];\n"
  },
  {
    "path": "prism-tests/functionality/language/infinite-rewards.prism.props.args",
    "content": "-s\n-ex\n"
  },
  {
    "path": "prism-tests/functionality/language/nan-rewards.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\ts<7 : 0/0;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/language/nan-rewards.prism.props",
    "content": "// RESULT: Error\nR=? [F s=7];\n"
  },
  {
    "path": "prism-tests/functionality/language/nan-rewards.prism.props.args",
    "content": "#-s\n-ex\n"
  },
  {
    "path": "prism-tests/functionality/language/negative-rewards.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t//s<7 : 2;\r\n\ts<7 : 1-2;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/language/negative-rewards.prism.props",
    "content": "// RESULT: Error\nR=? [F s=7];\n"
  },
  {
    "path": "prism-tests/functionality/language/negative-rewards.prism.props.args",
    "content": "-s\n-ex\n"
  },
  {
    "path": "prism-tests/functionality/language/power.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/language/power.prism.props",
    "content": "// Some tests of power operator, in each case:\n// * occurring in a constant (so Expression evaluation)\n// * occurring in a constant property (so probably model checking)\n// * occurring in a state-dependent property (so model checking, various engines)\n\n// RESULT: 1\n\"one\": s+1;\n\n// RESULT: 1\n\"one_s\": round(1+P=?[F<=1 d=6]);\n\n// RESULT: 1\n\"one_m\": round(P=?[F true]);\n\n// -------------------------\n\n// RESULT: 8\ncPow1; const int cPow1 = 2^3;\n\n// RESULT: 8\n2^3;\n\n// RESULT: 8\n(2*\"one\")^(d+3);\n\n// RESULT: 8\n(2*\"one_s\")^(d+3);\n\n// RESULT: 8\n(2*\"one_m\")^(d+3);\n\n// -------------------------\n\n// RESULT: 1/4\ncPow2; const double cPow2 = 0.5^2;\n\n// RESULT: 1/4\n0.5^2;\n\n// RESULT: 1/4\n(0.5*\"one\")^(d+2);\n\n// RESULT: 1/4\n(0.5*\"one_s\")^(d+2);\n\n// RESULT: 1/4\n(0.5*\"one_m\")^(d+2);\n\n// -------------------------\n\n// RESULT: 1/2\ncPow3; const double cPow3 = 2^-1.0;\n\n// RESULT: 1/2\n2^-1.0;\n\n// RESULT: 1/2\n(2*\"one\")^(d-1.0);\n\n// RESULT: 1/2\n(2*\"one_s\")^(d-1.0);\n\n// RESULT: 1/2\n(2*\"one_m\")^(d-1.0);\n\n// -------------------------\n\n// Don't test errors for now - not done properly for symbolic/param\n\n// RESULT: Error\n//cPow4; const double cPow4 = 2^-1;\n//cPow4; const double cPow4 = pow(2,-1);\n\n// RESULT: Error:negative\n//2^-1;\n\n// RESULT: Error:negative\n//(2*\"one\")^(d-1);\n\n// RESULT: Error:negative\n//(2*\"one_s\")^(d-1);\n\n// RESULT: Error:negative\n//(2*\"one_m\")^(d-1);\n\n// -------------------------\n"
  },
  {
    "path": "prism-tests/functionality/language/power.prism.props.args",
    "content": "-ex\n-exact\n-h\n-m\n"
  },
  {
    "path": "prism-tests/functionality/language/power.prism.root.props",
    "content": "// Some tests of power operator, in each case:\n// * occurring in a constant (so Expression evaluation)\n// * occurring in a constant property (so probably model checking)\n// * occurring in a state-dependent property (so model checking, various engines)\n\n// RESULT: 1\n\"one\": s+1;\n\n// RESULT: 1\n\"one_s\": round(1+P=?[F<=1 d=6]);\n\n// RESULT: 1\n\"one_m\": round(P=?[F true]);\n\n// -------------------------\n\n// RESULT: 1/2\ncPow4; const double cPow4 = (1/4)^(1/2);\n\n// RESULT: 1/2\n(1/4)^(1/2);\n\n// RESULT: 1/2\n(1/4*\"one\")^(d+1/2);\n\n// RESULT: 1/2\n(1/4*\"one_s\")^(d+1/2);\n\n// RESULT: 1/2\n(1/4*\"one_m\")^(d+1/2);\n\n// -------------------------\n"
  },
  {
    "path": "prism-tests/functionality/language/power.prism.root.props.args",
    "content": "-ex\n# -exact # no evaluation of roots as rationals\n-h\n-m\n"
  },
  {
    "path": "prism-tests/functionality/language/short-circuiting.prism",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/language/short-circuiting.prism.props",
    "content": "// Some tests of short-circuiting, in each case:\n// (i) occurring in a constant (so Expression evaluation)\n// (ii) occurring in a constant property (so model checking)\n// (iii) occurring in a state-dependent property (so model checking)\n\nconst int c = 0;\n\n// -------------------------\n\n// Baseline: should generate error\n\n// RESULT: Error:exponent\npow(2,c-1);\n\n// RESULT: Error:exponent\nfilter(forall, pow(2,s-1)>0);\n\n// -------------------------\n\n// Short-circuiting or prevents error\n\n// RESULT: true\ncOr; const bool cOr = c=0 | pow(2,c-1)>0;\n\n// RESULT: true\nc=0 | pow(2,c-1)>0;\n\n// RESULT: true\nfilter(forall, s=0 | pow(2,s-1)>0);\n\n// -------------------------\n\n// Short-circuiting and prevents error\n\n// RESULT: false\ncAnd; const bool cAnd = c!=0 & pow(2,c-1)>0;\n\n// RESULT: false\nc!=0 & pow(2,c-1)>0;\n\n// RESULT: false\nfilter(forall, s!=0 & pow(2,s-1)>0);\n\n// -------------------------\n\n// Short-circuiting implies prevents error\n\n// RESULT: true\ncImplies; const bool cImplies = c!=0 => pow(2,c-1)>0;\n\n// RESULT: true\nc!=0 => pow(2,c-1)>0;\n\n// RESULT: true\nfilter(forall, s!=0 => pow(2,s-1)>0);\n\n// -------------------------\n\n// Short-circuiting if-then-else prevents error\n\n// RESULT: 0\n//cITE; const int cITE = c>0 ? pow(2,c-1) : 0;\n\n// RESULT: 0\nc>0 ? pow(2,c-1) : 0;\n\n// RESULT: 447\nfilter(sum, s>0 ? pow(2,s-1) : 0);\n\n// -------------------------\n"
  },
  {
    "path": "prism-tests/functionality/language/short-circuiting.prism.props.args",
    "content": "-ex\n"
  },
  {
    "path": "prism-tests/functionality/language/system.sm",
    "content": "ctmc\n\nmodule M1\n\n\tx : [0..2];\n\n\t[a] x=0 -> (x'=1);\n\t[] x>0 -> true;\n\t\nendmodule\n\nmodule M2\n\n\ty : [0..2];\n\t\n\t[a] y=0 -> (y'=1);\n\t[] y>0 -> true;\n\t\nendmodule\n\nsystem\n\tM1 ||| M2\nendsystem\n"
  },
  {
    "path": "prism-tests/functionality/language/system.sm.exportmodel.auto",
    "content": "-exportmodel system.sm.sta,tra\n"
  },
  {
    "path": "prism-tests/functionality/language/system.sm.sta",
    "content": "(x,y)\n0:(0,0)\n1:(0,1)\n2:(1,0)\n3:(1,1)\n"
  },
  {
    "path": "prism-tests/functionality/language/system.sm.tra",
    "content": "4 7\n0 1 1 a\n0 2 1 a\n1 1 1\n1 3 1 a\n2 2 1\n2 3 1 a\n3 3 2\n"
  },
  {
    "path": "prism-tests/functionality/language/unary-min-max.prism",
    "content": "// Some tests of single-argument min/max, in each case:\n// (i) occurring in a constant (so Expression evaluation)\n// (ii) occuring in an update (so Expression evaluation)\n\ndtmc\n\nconst int zero = min(0);\nconst int one  = max(1); \n\nmodule test\n  n : [0..1] init zero;\n  m : [0..1] init one;\n\n  [] true -> (n' = min(m)) & (m' = max(n));\nendmodule"
  },
  {
    "path": "prism-tests/functionality/language/unary-min-max.prism.props",
    "content": "// Some tests of single-argument min/max, in each case:\n// (i) occurring in a constant (so Expression evaluation)\n// (ii) occurring in a constant property (so model checking)\n// (iii) occurring in a state-dependent property (so model checking)\n\nconst double cMin = min(2.72);\nconst double cMax = max(3.14);\n\n// RESULT: 0\nzero\n\n// RESULT: 1\none\n\n// RESULT: 2.72\nmin(2.72)\n\n// RESULT: 3.14\nmax(3.14)\n\n// RESULT: true\nfilter(forall, min(n,m)=0 & max(n,m)=1, true)\n\n"
  },
  {
    "path": "prism-tests/functionality/language/unary-min-max.prism.props.args",
    "content": "-ex\n-m"
  },
  {
    "path": "prism-tests/functionality/testing/normaltestwithrationalresult.prism",
    "content": "// bounded retransmission protocol [D'AJJL01]\r\n// gxn/dxp 23/05/2001\r\n\r\ndtmc\r\n\r\n// number of chunks\r\nconst int N = 16;\r\n// maximum number of retransmissions\r\nconst int MAX = 2;\r\n\r\nmodule sender\r\n\r\n\ts : [0..6];\r\n\t// 0 idle\r\n\t// 1 next_frame\t\r\n\t// 2 wait_ack\r\n\t// 3 retransmit\r\n\t// 4 success\r\n\t// 5 error\r\n\t// 6 wait sync\r\n\tsrep : [0..3];\r\n\t// 0 bottom\r\n\t// 1 not ok (nok)\r\n\t// 2 do not know (dk)\r\n\t// 3 ok (ok)\r\n\tnrtr : [0..MAX];\r\n\ti : [0..N];\r\n\tbs : bool;\r\n\ts_ab : bool;\r\n\tfs : bool;\r\n\tls : bool;\r\n\t\r\n\t// idle\r\n\t[NewFile] (s=0) -> (s'=1) & (i'=1) & (srep'=0);\r\n\t// next_frame\r\n\t[aF] (s=1) -> (s'=2) & (fs'=(i=1)) & (ls'=(i=N)) & (bs'=s_ab) & (nrtr'=0);\r\n\t// wait_ack\r\n\t[aB] (s=2) -> (s'=4) & (s_ab'=!s_ab);\r\n\t[TO_Msg] (s=2) -> (s'=3);\r\n\t[TO_Ack] (s=2) -> (s'=3);\r\n\t// retransmit\r\n\t[aF] (s=3) & (nrtr<MAX) -> (s'=2) & (fs'=(i=1)) & (ls'=(i=N)) & (bs'=s_ab) & (nrtr'=nrtr+1);\r\n\t[] (s=3) & (nrtr=MAX) & (i<N) -> (s'=5) & (srep'=1);\r\n\t[] (s=3) & (nrtr=MAX) & (i=N) -> (s'=5) & (srep'=2);\r\n\t// success\r\n\t[] (s=4) & (i<N) -> (s'=1) & (i'=i+1);\r\n\t[] (s=4) & (i=N) -> (s'=0) & (srep'=3);\r\n\t// error\r\n\t[SyncWait] (s=5) -> (s'=6); \r\n\t// wait sync\r\n\t[SyncWait] (s=6) -> (s'=0) & (s_ab'=false); \r\n\t\r\nendmodule\r\n\r\nmodule receiver\r\n\r\n\tr : [0..5];\r\n\t// 0 new_file\r\n\t// 1 fst_safe\r\n\t// 2 frame_received\r\n\t// 3 frame_reported\r\n\t// 4 idle\r\n\t// 5 resync\r\n\trrep : [0..4];\r\n\t// 0 bottom\r\n\t// 1 fst\r\n\t// 2 inc\r\n\t// 3 ok\r\n\t// 4 nok\r\n\tfr : bool;\r\n\tlr : bool;\r\n\tbr : bool;\r\n\tr_ab : bool;\r\n\trecv : bool;\r\n\t\r\n\t\r\n\t// new_file\r\n\t[SyncWait] (r=0) -> (r'=0);\r\n\t[aG] (r=0) -> (r'=1) & (fr'=fs) & (lr'=ls) & (br'=bs) & (recv'=T);\r\n\t// fst_safe_frame\r\n\t[] (r=1) -> (r'=2) & (r_ab'=br);\r\n\t// frame_received\r\n\t[] (r=2) & (r_ab=br) & (fr=true) & (lr=false)  -> (r'=3) & (rrep'=1);\r\n\t[] (r=2) & (r_ab=br) & (fr=false) & (lr=false) -> (r'=3) & (rrep'=2);\r\n\t[] (r=2) & (r_ab=br) & (fr=false) & (lr=true)  -> (r'=3) & (rrep'=3);\r\n\t[aA] (r=2) & !(r_ab=br) -> (r'=4);  \r\n\t// frame_reported\r\n\t[aA] (r=3) -> (r'=4) & (r_ab'=!r_ab);\r\n\t// idle\r\n\t[aG] (r=4) -> (r'=2) & (fr'=fs) & (lr'=ls) & (br'=bs) & (recv'=T);\r\n\t[SyncWait] (r=4) & (ls=true) -> (r'=5);\r\n\t[SyncWait] (r=4) & (ls=false) -> (r'=5) & (rrep'=4);\r\n\t// resync\r\n\t[SyncWait] (r=5) -> (r'=0) & (rrep'=0);\r\n\t\r\nendmodule\r\n\t\r\nmodule checker\r\n\r\n\tT : bool;\r\n\t\r\n//\t[NewFile] (T=false) -> (T'=false);\r\n\t[NewFile] (T=false) -> (T'=true);\r\n\t\r\nendmodule\r\n\r\nmodule\tchannelK\r\n\r\n\tk : [0..2];\r\n\t\r\n\t// idle\r\n\t[aF] (k=0) -> 0.98 : (k'=1) + 0.02 : (k'=2);\r\n\t// sending\r\n\t[aG] (k=1) -> (k'=0);\r\n\t// lost\r\n\t[TO_Msg] (k=2) -> (k'=0);\r\n\t\r\nendmodule\r\n\r\nmodule\tchannelL\r\n\r\n\tl : [0..2];\r\n\t\r\n\t// idle\r\n\t[aA] (l=0) -> 0.99 : (l'=1) + 0.01 : (l'=2);\r\n\t// sending\r\n\t[aB] (l=1) -> (l'=0);\r\n\t// lost\r\n\t[TO_Ack] (l=2) -> (l'=0);\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/testing/normaltestwithrationalresult.prism.props",
    "content": "// RESULT: 1503982516387544510687823213516750681753609533738014093985492327446021823341670745201522478360759626261166470522913554557570937367804047825330483938531949304640395637223627199/3552713678800500929355621337890625000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000\n\"p1\": P=? [ F s=5 ];\n\n// RESULT: -1503982516387544510687823213516750681753609533738014093985492327446021823341670745201522478360759626261166470522913554557570937367804047825330483938531949304640395637223627199/3552713678800500929355621337890625000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000000\n\"neg_p1\": -P=? [ F s=5 ];\n"
  },
  {
    "path": "prism-tests/functionality/testing/testing.prism",
    "content": "// dummy\n\nmodule M\n\n\tx : [0..1] init 0;\n\t\n\t[] x=0 -> 1.0:true;\n\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/testing/testing.prism.props",
    "content": "// Booleans\n\n// RESULT: true\ntrue;\n\n// RESULT: false\n!true;\n\n// Ints\n\n// RESULT: 7\n7;\n\n// RESULT: -7\n-7;\n\n// Doubles\n\n// RESULT: 3.14\n3.14;\n\n// RESULT: 1/2\n0.5;\n\n// RESULT: -1/2\n-0.5;\n\n// RESULT: Infinity\n1.0 / 0.0;\n\n// RESULT: +Infinity\n1.0 / 0.0;\n\n// RESULT: -Infinity\n-1.0 / 0.0;\n\n// RESULT: NaN\n(1.0 / 0.0) / (1.0 / 0.0);\n"
  },
  {
    "path": "prism-tests/functionality/testing/testing.prism.props.args",
    "content": "-h\n-ex\n-exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/bugfixes-ltl.nm",
    "content": "// LTL bug(s) fixed in trunk rev 2201\r\n\r\nmdp\r\n\r\nmodule test\r\n\r\n\tx : [0..2];\r\n\t\r\n\t[] x=0 -> true;\r\n\t[] x=0 -> 0.5 : (x'=1) + 0.5: (x'=2);\r\n\t[] x=1 -> (x'=0);\r\n\t[] x=2 -> true;\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/bugfixes-ltl.nm.props",
    "content": "// RESULT: 0.0\nPmax=? [ G F (x=1) ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/close_bounds.prism",
    "content": "dtmc\n\nconst bool exact;\n\nmodule die\n\n\t// local state\n\ts : [0..7] init 0;\n\t// value of the die\n\td : [0..6] init 0;\n\t\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\n\t[] s=7 -> (s'=7);\n\t\nendmodule\n\nrewards \"coin_flips\"\n\ts<7 : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/close_bounds.prism.props",
    "content": "const int x = 6;\n\n// RESULT: 1/6\nP=? [ F s=7 & d=x ]\n\n// RESULT: true\nP>=0.16666 [ F s=7 & d=x ]\n\n// RESULT (exact=false): Error \"accuracy\"\n// RESULT (exact=true): true\nP>=0.1666666666 [ F s=7 & d=x ]\n\n// RESULT (exact=false): Error \"accuracy\"\n// RESULT (exact=true): true\nP>=1/6 [ F s=7 & d=x ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/close_bounds.prism.props.args",
    "content": "-const exact=false -ii -e 1e-5 -ex\n-const exact=true -exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctl/ctl.prism",
    "content": "dtmc\r\n\r\nconst double p = 0.5;\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> p : (s'=1) + 1-p : (s'=2);\r\n\t[] s=1 -> p : (s'=3) + 1-p : (s'=4);\r\n\t[] s=2 -> p : (s'=5) + 1-p : (s'=6);\r\n\t[] s=3 -> p : (s'=1) + 1-p : (s'=7) & (d'=1);\r\n\t[] s=4 -> p : (s'=7) & (d'=2) + 1-p : (s'=7) & (d'=3);\r\n\t[] s=5 -> p : (s'=7) & (d'=4) + 1-p : (s'=7) & (d'=5);\r\n\t[] s=6 -> p : (s'=2) + 1-p : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctl/ctl.prism.props",
    "content": "// RESULT: true\nfilter(exists, E [ F s=7 & d=6 ], s>0)\n\n// RESULT: false\nE [ F s=7 & d=7 ]\n\n// RESULT: true\nE [ s<4 U d=1 ]\n\n// RESULT: false\nE [ s<4 U (s=7 & d!=1) ]\n\n// RESULT: false\nE [ s<4 U d=6 ]\n\n// RESULT: true\nA [ G s<=7 ]\n\n// RESULT: false\nA [ G s<=6 ]\n\n// RESULT: true\nE [ G s<=7 ]\n\n// RESULT: true\nE [ G s<=6 ]\n\n// RESULT: false\nE [ G s=0 ]\n\n// RESULT: true\nE [ G s<=3 ]\n\n// RESULT: false\nE [ G s!=0 ]\n\n// RESULT: true\nE [ X E [ G s!=0 ] ]\n\n// RESULT: true\nE [ X A [ G s!=0 ] ]\n\n// RESULT: true\nA [ X A [ G s!=0 ] ]\n\n// RESULT: true\nA [ X E [ G s!=0 ] ]\n\n\n// RESULT: true\nE [ F E [ G s=7 ] ]\n\n// RESULT: true\nE [ F A [ G s=7 ] ]\n\n// RESULT: false\nA [ F A [ G s=7 ] ]\n\n// RESULT: false\nA [ F E [ G s=7 ] ]\n\n// RESULT: false\nA [ s<7 U s=7 ]\n\n// RESULT: true\nE [ s<7 U s=7 ]\n\n// RESULT: true\nA [ s<7 W s=7 ]\n\n// RESULT: false\nA [ s<6 W s=7 ]\n\n// RESULT: true\nE [ s<6 W s=7 ]\n\n// RESULT: false\nA [ s<=1 W s=2 ]\n\n// RESULT: true\nA [ s=0 W (s=1 | s=2) ]\n\n// can stay globally below 7\n// RESULT: true\nE [ s=7 R s<7 ]\n\n// RESULT: false\nA [ s=7 R s<7 ]\n\n// RESULT: true\nE [ s=7 R s<=7 ]\n\n// RESULT: true\nA [ s=7 R s<=7 ]\n\n// RESULT: true\nE [ A [ X s=7 ] R s<6]\n\n// can not reach s=7 from anywhere in 2 steps\n// RESULT: false\nA [ G E [ X E [X A [ G s=7 ] ] ] ]\n\n// can reach s=7 from anywhere in 3 steps\n// RESULT: true\nA [ G E [ X E [X E [ X A [ G s=7 ] ] ] ] ]\n\n\n// computation of bounded temporal operators for\n// CTL path formulas currently unsupported\n// RESULT: ?\nE [ F<3 A [ G s=7 ] ]\n// RESULT: ?\nE [ G<3 s=0 ]\n// RESULT: ?\nE [ s=0 U<3 s=1 ]\n// RESULT: ?\nE [ s=0 R<3 s=1 ]\n// RESULT: ?\nE [ s=0 W<3 s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctl/ctl.prism.props.args",
    "content": "# we test all variants: consider as CTMC, DTMC and MDP, explicit and symbolic engines\n-ctmc -ex\n-dtmc -ex\n-mdp -ex\n-ctmc -mtbdd\n-dtmc -mtbdd\n-mdp -mtbdd\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmc_csl.sm",
    "content": "// Workstation cluster example - good range of CSL properties\r\n\r\nctmc\r\n\r\nconst int N=4; // Number of workstations in each cluster\r\nconst int left_mx = N; // Number of work stations in left cluster\r\nconst int right_mx = N; // Number of work stations in right cluster\r\n\r\n// Failure rates\r\nconst double ws_fail = 1/500; // Single workstation: average time to fail = 500 hrs\r\nconst double switch_fail = 1/4000; // Switch: average time to fail = 4000 hrs\r\nconst double line_fail = 1/5000; // Backbone: average time to fail = 5000 hrs\r\n\r\n// Left cluster\r\nmodule Left \r\n\t\r\n\tleft_n : [0..left_mx] init left_mx; // Number of workstations operational\r\n\tleft : bool; // Being repaired?\r\n\t\r\n\t[startLeft] !left & (left_n<left_mx) -> 1 : (left'=true);\r\n\t[repairLeft] left & (left_n<left_mx) -> 1 : (left'=false) & (left_n'=left_n+1);\r\n\t[] (left_n>0) -> ws_fail*left_n : (left_n'=left_n-1);\r\n\t\r\nendmodule\r\n\r\n// Right cluster\r\nmodule Right = Left[left_n=right_n,\r\n                    left=right,\r\n                    left_mx=right_mx,\r\n                    startLeft=startRight,\r\n                    repairLeft=repairRight ]\r\nendmodule\r\n\r\n// Repair unit\r\nmodule Repairman\r\n\t\r\n\tr : bool; // Repairing?\r\n\t\r\n\t[startLeft]    !r -> 10 : (r'=true); // Inspect Left \r\n\t[startRight]   !r -> 10 : (r'=true); // Inspect Right \r\n\t[startToLeft]  !r -> 10 : (r'=true); // Inspect ToLeft\r\n\t[startToRight] !r -> 10 : (r'=true); // Inspect ToRight \r\n\t[startLine]    !r -> 10 : (r'=true); // Inspect Line \r\n\t\r\n\t[repairLeft]    r -> 2     : (r'=false); // Repair Left \r\n\t[repairRight]   r -> 2     : (r'=false); // Repair Right\r\n\t[repairToLeft]  r -> 0.25  : (r'=false); // Repair ToLeft\r\n\t[repairToRight] r -> 0.25  : (r'=false); // Repair ToRight\r\n\t[repairLine]    r -> 0.125 : (r'=false); // Repair Line\r\n\t\r\nendmodule\r\n\r\n// Line/backbone\r\nmodule Line \r\n\t\r\n\tline :   bool; // Being repaired?\r\n\tline_n : bool init true; // Working?\r\n\t\r\n\t[startLine] !line & !line_n -> 1 : (line'=true);\r\n\t[repairLine] line & !line_n -> 1 : (line'=false) & (line_n'=true);\r\n\t[] line_n -> line_fail : (line_n'=false);\r\n\t\r\nendmodule\r\n\r\n// Left switch\r\nmodule ToLeft = Line[line=toleft,\r\n                     line_n=toleft_n,\r\n                     line_fail=switch_fail,\r\n                     startLine=startToLeft,\r\n                     repairLine=repairToLeft ]\r\nendmodule\r\n\r\n// Right switch\r\nmodule ToRight = Line[line=toright,\r\n                      line_n=toright_n,\r\n                      line_fail=switch_fail,\r\n                      startLine=startToRight,\r\n                      repairLine=repairToRight ]\r\nendmodule\r\n\r\n// Formulas + labels\r\n\r\n// Minimum QoS requires 3/4 connected workstations operational\r\nconst int k = floor(0.75*N);\r\n// left_operational_i : left_n>=i & toleft_n\r\n// right_operational_i : right_n>=i & toright_n\r\n// operational_i : (left_n+right_n)>=i & toleft_n & line_n & toright_n\r\n// minimum_k : left_operational_k | right_operational_k | operational_k\r\nformula minimum = (left_n>=k & toleft_n) | \r\n                  (right_n>=k & toright_n) | \r\n                  ((left_n+right_n)>=k & toleft_n & line_n & toright_n);\r\nlabel \"minimum\" = (left_n>=k & toleft_n) | (right_n>=k & toright_n) | ((left_n+right_n)>=k & toleft_n & line_n & toright_n);\r\n// premium = minimum_N\r\nlabel \"premium\" = (left_n>=left_mx & toleft_n) | (right_n>=right_mx & toright_n) | ((left_n+right_n)>=left_mx & toleft_n & line_n & toright_n);\r\n\r\n// Reward structures\r\n\r\n// Percentage of operational workstations stations\r\nrewards \"percent_op\"\r\n\ttrue : 100*(left_n+right_n)/(2*N);\r\nendrewards\r\n\r\n// Time that the system is not delivering at least minimum QoS\r\nrewards \"time_not_min\"\r\n\t!minimum : 1; \r\nendrewards\r\n\r\n// Number of repairs\r\nrewards \"num_repairs\"\r\n\t[repairLeft]    true : 1;\r\n\t[repairRight]   true : 1;\r\n\t[repairToLeft]  true : 1;\r\n\t[repairToRight] true : 1;\r\n\t[repairLine]    true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmc_csl.sm.props",
    "content": "\t// RESULT: 1\n\tP=? [ F \"premium\" ];\n\t\n\t// RESULT: 2.575834331129808E-9\n\tP=? [ F<=0.2 !\"minimum\" ];\n\t\n\t// RESULT: 2.587821746795989E-7\n\tP=? [ F<=2 !\"minimum\" ];\n\t\n\t// RESULT: 1.3126420636755083E-5\n\tP=? [ F<=20 !\"minimum\" ];\n\t\n\t// RESULT: 1.7751335826903441E-4\n\tP=? [ F<=200 !\"minimum\" ];\n\t\n\t// RESULT: 0.0018221051490216614\n\tP=? [ F<=2000 !\"minimum\" ];\n\t\n\t// RESULT: 0.9999999635780142\n\tP=? [ F[0.3,0.3] !\"minimum\"  {!\"minimum\"}{max} ];\n\t\n\t// RESULT: 0.9933696967082797\n\tP=? [ F[3,3] !\"minimum\"  {!\"minimum\"}{max} ];\n\t\n\t// RESULT: 0.10124016421845902\n\tP=? [ F[30,30] !\"minimum\"  {!\"minimum\"}{max} ];\n\t\n\t// RESULT: 0.0011006375189713275\n\tP=? [ F<=0.2 \"premium\" {\"minimum\"}{min} ];\n\t\n\t// RESULT: 0.08472606264690494\n\tP=? [ F<=2 \"premium\" {\"minimum\"}{min} ];\n\t\n\t// RESULT: 0.8656869444157752\n\tP=? [ F<=20 \"premium\" {\"minimum\"}{min} ];\n\t\n\t// RESULT: 0.02716568936043944\n\tP=? [ \"minimum\" U<=1 \"premium\" {\"minimum\"}{min} ];\n\t\n\t// RESULT: 0.7528670508736512\n\tP=? [ !\"minimum\" U>=10 \"minimum\" {!\"minimum\"}{max} ];\n\t\n\t// RESULT: 99.87733171389172\n\tR{\"percent_op\"}=?[ I=10 ];\n\n\t// RESULT: 0.003662017006365601\n\tR{\"time_not_min\"}=?[ C<=1000 ];\n\t\n\t// RESULT: 0.007787151838390689\n\tR{\"num_repairs\"}=?[ C<=1 ];\n\t\n\t// RESULT: 0.1539570981244814\n\tR{\"num_repairs\"}=?[ C<=10 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmc_csl.sm.slow.props",
    "content": "// transient props with large time bound\n// (need ss-detection disabling currently)\n\t\n\t// RESULT: 99.87507834359438\n\tR{\"percent_op\"}=?[ I=100 ];\n\t\n\t// RESULT: 99.87330029344373\n\tR{\"percent_op\"}=?[ I=100 {!\"minimum\"}{min} ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmc_csl.sm.slow.props.args",
    "content": "-nossdetect\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmc_csl.sm.ss.props",
    "content": "// steady-state props\n// (needs additional arguments)\n\n\t// RESULT: 0.9999212408513795\n\tS=? [ \"premium\" ];\n\t\n\t// RESULT: 3.7011298647145493E-6\n\tS=? [ !\"minimum\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmc_csl.sm.ss.props.args",
    "content": "-gs\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/fau/poll5.sm",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 5;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma\t= 200;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..5]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop3a] (s=3)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop3b] (s=3)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve3] (s=3)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop4a] (s=4)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop4b] (s=4)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve4] (s=4)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop5a] (s=5)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop5b] (s=5)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve5] (s=5)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\nmodule station3 = station1 [ s1=s3, loop1a=loop3a, loop1b=loop3b, serve1=serve3 ] endmodule\r\nmodule station4 = station1 [ s1=s4, loop1a=loop4a, loop1b=loop4b, serve1=serve4 ] endmodule\r\nmodule station5 = station1 [ s1=s5, loop1a=loop5a, loop1b=loop5b, serve1=serve5 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/fau/poll5.sm.props",
    "content": "const double T;\n\n// RESULT (T=0.02): 0.00398714\n// RESULT (T=0.04): 0.00790455\n// RESULT (T=0.06): 0.0117304\n// RESULT (T=0.08): 0.0154680\n// RESULT (T=0.10): 0.0191205\nP=? [ F=T s5=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/fau/poll5.sm.props.args",
    "content": "-const T=0.02:0.02:0.1 -transientmethod unif\n-const T=0.02:0.02:0.1 -transientmethod fau\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/cosafe/robot.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n// Multiply rates by 10 to help distinguish from original DTMC\r\n[south] s=0 -> 8:(s'=3) + 1:(s'=1) + 1:(s'=4);\r\n[east] s=1 -> 10:(s'=2);\r\n[stuck] s=2 -> 10:(s'=2);\r\n[stuck] s=3 -> 10:(s'=3);\r\n[east] s=4 -> 10:(s'=5);\r\n[north] s=5 -> 9:(s'=2) + 1:(s'=5);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/cosafe/robot.sm.cosafe.props",
    "content": "// RESULT: 0.12  //  = 1/10 * (1+(0.8*0+0.1*1+0.1*1))\nR=? [ (F \"goal1\") | (F \"goal2\") ]\n\n// RESULT: 0.12\nR=? [ X F (\"goal1\" | \"goal2\") ]\n\n// RESULT: 0.12\nR=? [ F X (\"goal1\" | \"goal2\") ]\n\n// RESULT: 0.2\nR=? [ X X (\"goal1\" | \"goal2\") ]\n\n// RESULT: Infinity\nR=? [ X X \"goal2\" ]\n\n// RESULT: 118/900\nR=? [ F \"goal2\" ]\n\n// RESULT: 118/900\nR=? [ (F \"goal2\") ]\n\n// RESULT: 118/900\nR=? [ s!=3 U \"goal2\" ]\n\n// RESULT: Error:co-safe\nR=? [ F G \"goal1\" ]\n\n// RESULT: Error:co-safe\nR=? [ F G \"goal1\" ]\n\n// RESULT: Error:co-safe\nR=? [ (G !\"hazard\")&(G F \"goal1\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/ctmc_rewards.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\t\r\n\t[] s=0 -> 5: (s'=1);\r\n\t[] s=1 -> 7: (s'=2);\r\n\t[] s=2 -> 11: (s'=3);\r\n\t[] s>2 -> 13: true;\r\n\r\nendmodule\r\n\r\nrewards \"a\"\r\n\ts=0: 2;\r\n\t[] s=0: 3;\r\n\ts=1: 5;\r\n\t[] s=1: 7;\r\n\ts=2: 11;\r\nendrewards\r\n\r\nrewards \"a_state\"\r\n\ts=0: 2;\r\n\ts=1: 5;\r\n\ts=2: 11;\r\nendrewards\r\n\r\nrewards \"b\"\r\n\ts=0: 2;\r\n\t[] s=0: 3;\r\n\ts=1: 5;\r\n\t[] s=1: 7;\r\n\ts=2: 11;\r\n\t[] s=3: 13;\r\n\ts=3: 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/ctmc_rewards.sm.cosafety.props",
    "content": "// RESULT: 0.0\nR{\"a\"}=? [ s>=0 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ true ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ !false ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ s>0 | s=0 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ s=0 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ F s=0 ];\n\n// RESULT: 3.4\nR{\"a\"}=? [ F s=1 ];\n\n// RESULT: 3+2/5+7+5/7\nR{\"a\"}=? [ F s=2 ];\n\n// RESULT: 3+2/5+7+5/7+1\nR{\"a\"}=? [ F s=3 ];\n\n// RESULT: 3.4\nR{\"a\"}=? [ X s>=0 ];\n\n// RESULT: 3.4\nR{\"a\"}=? [ X true ];\n\n// RESULT: Infinity\nR{\"a\"}=? [ ! (X true) ];\n\n// RESULT: 3.4\nR{\"a\"}=? [ ! (X false) ];\n\n// RESULT: 3+2/5+7+5/7\nR{\"a\"}=? [ X X s>=0 ];\n\n// RESULT: 3+2/5+7+5/7\nR{\"a\"}=? [ X X true ];\n\n// RESULT: 3+2/5+7+5/7+1\nR{\"a\"}=? [ X X X s>=0 ];\n\n// RESULT: 3+2/5+7+5/7+1\nR{\"a\"}=? [ X X X true ];\n\n// RESULT: 3+2/5+7+5/7+1\nR{\"a\"}=? [ X X X (true ? true : s>=0) ];\n\n// RESULT: 3+2/5+7+5/7+1\nR{\"a\"}=? [ X X X (false ? true : s>=0) ];\n\n// RESULT: Infinity\nR{\"a\"}=? [ X X X false ];\n\n\n\n// as above, but with only with state rewards\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ s>=0 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ true ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ !false ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ s>0 | s=0 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ s=0 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ F s=0 ];\n\n// RESULT: 0.4\nR{\"a_state\"}=? [ F s=1 ];\n\n// RESULT: 2/5+5/7\nR{\"a_state\"}=? [ F s=2 ];\n\n// RESULT: 2/5+5/7+1\nR{\"a_state\"}=? [ F s=3 ];\n\n// RESULT: 0.4\nR{\"a_state\"}=? [ X s>=0 ];\n\n// RESULT: 0.4\nR{\"a_state\"}=? [ X true ];\n\n// RESULT: Infinity\nR{\"a_state\"}=? [ ! (X true) ];\n\n// RESULT: 0.4\nR{\"a_state\"}=? [ ! (X false) ];\n\n// RESULT: 2/5+5/7\nR{\"a_state\"}=? [ X X s>=0 ];\n\n// RESULT: 2/5+5/7\nR{\"a_state\"}=? [ X X true ];\n\n// RESULT: 2/5+5/7+1\nR{\"a_state\"}=? [ X X X s>=0 ];\n\n// RESULT: 2/5+5/7+1\nR{\"a_state\"}=? [ X X X true ];\n\n// RESULT: 2/5+5/7+1\nR{\"a_state\"}=? [ X X X (true ? true : s>=0) ];\n\n// RESULT: 2/5+5/7+1\nR{\"a_state\"}=? [ X X X (false ? true : s>=0) ];\n\n// RESULT: Infinity\nR{\"a_state\"}=? [ X X X false ];\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/ctmc_rewards.sm.props",
    "content": "// RESULT: 0.0\nR{\"a\"}=? [ C<=0 ];\n// RESULT: 2.28944\nR{\"a\"}=? [ C<=0.1 ];\n// RESULT: 9.87621\nR{\"a\"}=? [ C<=0.5 ];\n// RESULT: 11.89005\nR{\"a\"}=? [ C<=1 ];\n// RESULT: 12.11429\nR{\"a\"}=? [ C<=10 ];\n// RESULT: 12.11429\nR{\"a\"}=? [ C<=100 ];\n\n// RESULT: 12.114285714285716\nR{\"a\"}=? [ C ];\n\n// RESULT: Infinity\nR{\"b\"}=? [ C ];\n\n// RESULT: 2.0\nR{\"a\"}=? [ I=0 ];\n// RESULT: 3.48854\nR{\"a\"}=? [ I=0.1 ]\n// RESULT: 2.05864\nR{\"a\"}=? [ I=0.5 ]\n// RESULT: 0.25886\nR{\"a\"}=? [ I=1 ]\n\n// RESULT: 0.0\nR{\"a\"}=? [ F s=0 ]\n// RESULT: 3.4\nR{\"a\"}=? [ F s=1 ]\n// RESULT: 389/35\nR{\"a\"}=? [ F s=2 ]\n// RESULT: 424/35\nR{\"a\"}=? [ F s>2 ]\n\n// RESULT: 0.0\nR{\"a\"}=? [ S ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ S ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/ctmc_rewards2.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n// Multiply rates by 10 to help distinguish from original DTMC\r\n[] s=0 -> 5:(s'=1) + 5:(s'=3);\r\n[] s=1 -> 5:(s'=0) + 2.5:(s'=2) + 2.5:(s'=4);\r\n[r] s=2 -> 10:(s'=5);\r\n[] s=3 -> 10:(s'=3);\r\n[] s=4 -> 10:(s'=4);\r\n[] s=5 -> 10:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n\r\nrewards \"r\"\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n\r\nrewards \"r2\"\r\ns=2 : 5;\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n\r\nrewards \"s\"\r\n  true : s;\r\nendrewards\r\n\r\nrewards \"s3\"\r\n  s>=3 : s;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/ctmc_rewards2.sm.props",
    "content": "// RESULT: 17/6\nR{\"r\"}=? [ F s>2 ]\n\n// RESULT: 175/60\nR{\"r2\"}=? [ F s>2 ]\n\n// RESULT: 13/60\nR{\"time\"}=? [ F s>2 ]\n\n// RESULT: 1\nR{\"time\"}=? [ S ]\n\n\n// RESULT: Infinity\nR{\"r\"}=? [ F s>3 ]\n\n// RESULT: 0.39912\nR{\"r\"}=? [ I=0.4 ]\n\n// RESULT: 143.46388878967119\nR{\"r\"}=? [ C<=10 ]\n\n// RESULT: Infinity\nR{\"r\"}=? [ C ]\n\n// RESULT: 44/3\nR{\"r\"}=? [ S ]\n\n\n// RESULT: 1/15\nR{\"s\"}=? [ F s>=2 ]\n\n// RESULT: Infinity\nR{\"s\"}=? [ F s>=5 ]\n\n// RESULT: Infinity\nR{\"s\"}=? [ C ]\n\n// RESULT: 3.25\nR{\"s\"}=? [ S ]\n\n\n// RESULT: 0\nR{\"s3\"}=? [ F s>=2 ]\n\n// RESULT: Infinity\nR{\"s3\"}=? [ F s>=5 ]\n\n// RESULT: Infinity\nR{\"s3\"}=? [ C ]\n\n// RESULT: 37/12\nR{\"s3\"}=? [ S ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/ctmc_rewards_bsccs.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\n\ts : [0..4];\r\n\t\r\n\t// Multiply rates by 10 to help distinguish from original DTMC\r\n\t[] s=0 -> 4:(s'=1) + 6:(s'=3);\r\n\t[] s=1 -> 10:(s'=2);\r\n\t[] s=2 -> 10:(s'=1);\r\n\t[] s=3 -> 10:(s'=4);\r\n\t[] s=4 -> 10:(s'=3);\r\n\r\nendmodule\r\n\r\nrewards \"a\"\r\n\ts=0: 2;\r\nendrewards\r\n\r\nrewards \"b\"\r\n\ts=0: 2;\r\n\ts=1: 5;\r\nendrewards\r\n\r\nrewards \"c\"\r\n\ts=0: 2;\r\n\t[] s=3: 5;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ctmcs/rewards/ctmc_rewards_bsccs.sm.props",
    "content": "// RESULT: 0.2\nR{\"a\"}=? [ F s>0 ];\n// RESULT: Infinity\nR{\"a\"}=? [ F s=1|s=2 ];\n// RESULT: Infinity\nR{\"a\"}=? [ F s=3|s=4 ];\n\n// RESULT: 0.2\nR{\"a\"}=? [ C ];\n// RESULT: Infinity\nR{\"b\"}=? [ C ];\n// RESULT: Infinity\nR{\"c\"}=? [ C ];\n\n// RESULT: Infinity\nfilter(state, R{\"b\"}=? [ C ], s=0);\n// RESULT: Infinity\nfilter(state, R{\"b\"}=? [ C ], s=1);\n// RESULT: Infinity\nfilter(state, R{\"b\"}=? [ C ], s=2);\n// RESULT: 0.0\nfilter(state, R{\"b\"}=? [ C ], s=3);\n// RESULT: 0.0\nfilter(state, R{\"b\"}=? [ C ], s=4);\n\n// RESULT: 0.0\nR{\"a\"}=? [ S ];\n// RESULT: 1.0\nR{\"b\"}=? [ S ];\n// RESULT: 15\nR{\"c\"}=? [ S ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/bounded-reach/bounded-reach-1.pm",
    "content": "// Simple linear DTMC for checking bounds in bounded until, etc\r\n\r\ndtmc\r\n\r\nmodule m1\r\n  s : [0..4] init 0;\r\n\r\n  [] s<4 -> 1 : (s'=s+1);\r\n  [] s=4 -> 1 : (s'=s);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/bounded-reach/bounded-reach-1.pm.props",
    "content": "const int k = 2;\n\n// ------ Bounds for Globally ----------------\n\n// RESULT: Error\nP=?[ G<0 s<2]\n// RESULT: 1.0\nP=?[ G<1 s<2]\n// RESULT: 1.0\nP=?[ G<2 s<2]\n// RESULT: 0.0\nP=?[ G<3 s<2]\n// RESULT: 0.0\nP=?[ G<4 s<2]\n\n\n// RESULT: 1.0\nP=?[ G<=0 s<2]\n// RESULT: 1.0\nP=?[ G<=1 s<2]\n// RESULT: 0.0\nP=?[ G<=2 s<2]\n// RESULT: 0.0\nP=?[ G<=3 s<2]\n// RESULT: 0.0\nP=?[ G<=4 s<2]\n\n\n// RESULT: 0.0\nP=?[ G>0 s>2]\n// RESULT: 0.0\nP=?[ G>1 s>2]\n// RESULT: 1.0\nP=?[ G>2 s>2]\n// RESULT: 1.0\nP=?[ G>3 s>2]\n// RESULT: 1.0\nP=?[ G>4 s>2]\n\n\n// RESULT: 0.0\nP=?[ G>=0 s>2]\n// RESULT: 0.0\nP=?[ G>=1 s>2]\n// RESULT: 0.0\nP=?[ G>=2 s>2]\n// RESULT: 1.0\nP=?[ G>=3 s>2]\n// RESULT: 1.0\nP=?[ G>=4 s>2]\n\n\n// RESULT: Error\nP=? [ G[1,0] true ]\n// RESULT: Error\nP=? [ G[-1,1] true ]\n// RESULT: 1.0\nP=? [ G[1,3] (s=1 | s=2 | s=3) ]\n// RESULT: 0.0\nP=? [ G[1,3] (s=1 | s=3) ]\n// RESULT: 1.0\nP=? [ G[1,3] (s>=1 | s<=3) ]\n\n\n// RESULT: 1.0\nP=? [ G=3 (s=3) ]\n// RESULT: 0.0\nP=? [ G=3 (s=2) ]\n\n// RESULT: 1.0\nP=? [ G=(k) (s=2) ]\n\n// ------ Bounds for Finally ----------------\n\n\n// RESULT: Error\nP=?[ F<0 s=2]\n// RESULT: 0.0\nP=?[ F<1 s=2]\n// RESULT: 0.0\nP=?[ F<2 s=2]\n// RESULT: 1.0\nP=?[ F<3 s=2]\n// RESULT: 1.0\nP=?[ F<4 s=2]\n\n\n// RESULT: 0.0\nP=?[ F<=0 s=2]\n// RESULT: 0.0\nP=?[ F<=1 s=2]\n// RESULT: 1.0\nP=?[ F<=2 s=2]\n// RESULT: 1.0\nP=?[ F<=3 s=2]\n// RESULT: 1.0\nP=?[ F<=4 s=2]\n\n\n// RESULT: 1.0\nP=?[ F>0 s=2]\n// RESULT: 1.0\nP=?[ F>1 s=2]\n// RESULT: 0.0\nP=?[ F>2 s=2]\n// RESULT: 0.0\nP=?[ F>3 s=2]\n// RESULT: 0.0\nP=?[ F>4 s=2]\n\n\n// RESULT: 1.0\nP=?[ F>=0 s=2]\n// RESULT: 1.0\nP=?[ F>=1 s=2]\n// RESULT: 1.0\nP=?[ F>=2 s=2]\n// RESULT: 0.0\nP=?[ F>=3 s=2]\n// RESULT: 0.0\nP=?[ F>=4 s=2]\n\n\n// RESULT: Error\nP=? [ F[1,0] true ]\n// RESULT: Error\nP=? [ F[-1,1] true ]\n// RESULT: 0.0\nP=? [ F[1,3] s=0 ]\n// RESULT: 1.0\nP=? [ F[1,3] s=1 ]\n// RESULT: 1.0\nP=? [ F[1,3] s=2 ]\n// RESULT: 1.0\nP=? [ F[1,3] s=3 ]\n// RESULT: 0.0\nP=? [ F[1,3] s=4 ]\n\n// RESULT: 0.0\nP=? [ F=2 s=1 ]\n// RESULT: 1.0\nP=? [ F=2 s=2 ]\n// RESULT: 0.0\nP=? [ F=2 s=3 ]\n\n\n\n// ------ Bounds for Until ----------------\n\n// RESULT: 0.0\nP=? [ s<2 U=2 s=1 ]\n// RESULT: 1.0\nP=? [ s<2 U=2 s=2 ]\n// RESULT: 0.0\nP=? [ s<2 U=2 s=3 ]\n// RESULT: 0.0\nP=? [ s<1 U=2 s=2 ]\n\n// RESULT: 0.0\nP=? [ s<2 U>2 s=2 ]\n// RESULT: 1.0\nP=? [ s<2 U>=2 s=2 ]\n\n// RESULT: 0.0\nP=? [ false U>=1 false ]\n// RESULT: 0.0\nP=? [ false U<1 false ]\n// RESULT: 0.0\nP=? [ true U>=1 false ]\n// RESULT: 0.0\nP=? [ true U<1 false ]\n\n// RESULT: 1.0\nP=? [ false U>=0 true ]\n// RESULT: 0.0\nP=? [ false U>0 true ]\n// RESULT: 1.0\nP=? [ true U>=0 true ]\n// RESULT: 1.0\nP=? [ true U>2 true ]\n\n// RESULT: 1.0\nP=? [ true U>=3 s=4 ]\n// RESULT: 0.0\nP=? [ true U>=3 s=2 ]\n\n// RESULT: 1.0\nP=? [ false U>=0 s=0 ]\n// RESULT: 0.0\nP=? [ false U>=0 s=1 ]\n// RESULT: 0.0\nP=? [ false U>0  s=0 ]\n\n// RESULT: 0.0\nP=? [ s=0 U>=0 false ]\n\n// RESULT: 1.0\nP=? [ s=1 U>=0 true ]\n// RESULT: 1.0\nP=? [ s=1 U<10 true ]\n// RESULT: 0.0\nP=? [ s=1 U>1 true ]\n// RESULT: 0.0\nP=? [ s<3 U>3 true ]\n// RESULT: 1.0\nP=? [ s<3 U>=3 true ]\n\n// RESULT: 1.0\nP=? [ s=1 U[0,10] true ]\n// RESULT: 0.0\nP=? [ s=1 U[2,10] true ]\n// RESULT: 0.0\nP=? [ s<3 U[4,10] true ]\n// RESULT: 1.0\nP=? [ s<3 U[3,10] true ]\n\n\n\n// test cases where the left and right operand\n// are the same\n// RESULT: 1.0\nP=? [ s<4 U[0,0] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[0,1] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[0,2] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[0,3] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[0,4] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[0,5] s<4 ]\n\n// RESULT: 1.0\nP=? [ s<4 U[0,4] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[1,4] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[2,4] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[3,4] s<4 ]\n// RESULT: 0.0\nP=? [ s<4 U[4,4] s<4 ]\n\n// RESULT: 1.0\nP=? [ s<4 U[0,5] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[1,5] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[2,5] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[3,5] s<4 ]\n// RESULT: 0.0\nP=? [ s<4 U[4,5] s<4 ]\n// RESULT: 0.0\nP=? [ s<4 U[5,5] s<4 ]\n\n// RESULT: 1.0\nP=? [ s<4 U[0,3] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[1,3] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[2,3] s<4 ]\n// RESULT: 1.0\nP=? [ s<4 U[3,3] s<4 ]\n\n\n// test cases where the left and right operand\n// are dual\n// RESULT: 0.0\nP=? [ s!=3 U[0,0] s=3 ]\n// RESULT: 0.0\nP=? [ s!=3 U[1,1] s=3 ]\n// RESULT: 0.0\nP=? [ s!=3 U[2,2] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[3,3] s=3 ]\n// RESULT: 0.0\nP=? [ s!=3 U[4,4] s=3 ]\n// RESULT: 0.0\nP=? [ s!=3 U[5,5] s=3 ]\n\n// RESULT: 0.0\nP=? [ s!=3 U[0,1] s=3 ]\n// RESULT: 0.0\nP=? [ s!=3 U[1,2] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[2,3] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[3,4] s=3 ]\n// RESULT: 0.0\nP=? [ s!=3 U[4,5] s=3 ]\n\n// RESULT: 0.0\nP=? [ s!=3 U[0,2] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[1,3] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[2,4] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[3,5] s=3 ]\n// RESULT: 0.0\nP=? [ s!=3 U[4,6] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[0,3] s=3 ]\n\n// RESULT: 1.0\nP=? [ s!=3 U[1,4] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[2,5] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[3,6] s=3 ]\n// RESULT: 0.0\nP=? [ s!=3 U[4,7] s=3 ]\n\n// RESULT: 1.0\nP=? [ s!=3 U[0,4] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[1,5] s=3 ]\n// RESULT: 1.0\nP=? [ s!=3 U[2,6] s=3 ]\n\n\n\n\n// ------ Bounds for Release ----------------\n// a R[l,u] b = !(!a U[l,u] !b)\n\n// RESULT: 1.0\nP=? [ false R<3 s<3 ]\n\n// RESULT: 0.0\nP=? [ false R<=3 s<3 ]\n\n// RESULT: 1.0\nP=? [ false R=3 s=3 ]\n\n// RESULT: 0.0\nP=? [ false R=3 s!=3 ]\n\n\n// RESULT: 1.0\nP=? [ false R<=1 true ]\n\n// RESULT: 1.0\nP=? [ false R>=1 true ]\n\n// RESULT: 1.0\nP=? [ false R[1,10] true ]\n\n// RESULT: 1.0\nP=? [ false R=2 true ]\n\n// RESULT: 0.0\nP=? [ false R<1 false ]\n\n// RESULT: 0.0\nP=? [ true R<1 false ]\n\n// RESULT: 1.0\nP=? [ true R>1 false ]\n\n// RESULT: 1.0\nP=? [ true R>1 false ]\n\n\n// RESULT: 1.0\nP=? [ s=4 R>1 s>1 ]\n\n// RESULT: 0.0\nP=? [ s=4 R>1 s>2 ]\n\n// RESULT: 1.0\nP=? [ s=4 R[1,3] (s>=1 & s<=3) ]\n\n// RESULT: 0.0\nP=? [ s=4 R[1,3] (s>=1 & s<3) ]\n\n// RESULT: 1.0\nP=? [ s=3 R[1,4] (s>=1 & s<=3) ]\n\n// RESULT: 0.0\nP=? [ s=3 R[1,4] (s>=1 & s<3) ]\n\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/bounded-reach/bounded-reach-2.pm",
    "content": "dtmc\r\n\r\nmodule m1\r\n   s : [0..7] init 0;\r\n   skip : [0..1] init 0;\r\n\r\n   [] skip=1 & s<6 -> 1/2 : (skip'=1) + 1/2 : (skip'=0)&(s'=s+1);\r\n\r\n   [] skip=0 & s<6 -> 1/2  : (s'=s+1) +   1/2  : (skip'=1);\r\n   [] skip=0 & s=6 -> (s'=7);\r\n   [] skip=0 & s=7 -> (s'=7);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/bounded-reach/bounded-reach-2.pm.props",
    "content": "// RESULT: 0.984375\nP=? [ F skip=1 ]\n\n// RESULT: 1.0\nP=? [ F s=6 ]\n\n// RESULT: 0.0\nP=? [ F=5 s=6 ]\n\n// RESULT: 0.015625\nP=? [ F=6 s=6 ]\n\n// RESULT: 0.046875\nP=? [ F=7 s=6 ]\n\n// RESULT: 0.08203125\nP=? [ F=8 s=6 ]\n\n// RESULT: 0.015625\nP=? [ (skip=0) U s=6 ]\n\n// RESULT: 0.0\nP=? [ (skip=0) U[10,20] s=6 ]\n\n// RESULT: 0.623046875\nP=? [ G>=10 s>4 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_pctl.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[r] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n\r\nrewards \"r\"\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_pctl.pm.props",
    "content": "\t// RESULT: 1/2\n\tP=? [ X s=1 ];\n\t\n\t// RESULT: 1/6\n\tP=? [ F s=2 ];\n\t\n\t// RESULT: 1/3\n\tP=? [ F s=2|s=4 ];\n\t\n\t// RESULT: 0\n\tP=? [ F<=0 s=2 ];\n\t\n\t// RESULT: 1/8\n\tP=? [ F<=2 s=2 ];\n\t\n\t// RESULT: 1/8\n\tP=? [ F<=3 s=2 ];\n\t\n\t// RESULT: 1/8\n\tP=? [ F<4 s=2 ];\n\t\n\t// RESULT: 0.16650390625\n\tP=? [ F<=10 s=2 ];\n\t\n\t// RESULT: 0\n\tP=? [ G s<2 ];\n\t\n\t// RESULT: 0.0625\n\tP=? [ G<=4 s<2 ];\n\t\n\t// RESULT: 1/2\n\tP=? [ s!=1 U s=3 ];\n\t\n\t// RESULT: 1/2\n\tP=? [ s!=1 U<=1 s=3 ];\n\t\n\t// RESULT: 1/2\n\tP=? [ s!=1 U<=8 s=3 ];\n\t\n\t// RESULT: 14.060546875\n\tR{\"r\"}=? [ C<=10 ];\n\t\n\t// RESULT: 23/12\n\tR{\"r\"}=? [ S ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_pctl.pm.props.args",
    "content": "# different engines and iteration methods:\n\n-ex -power\n-ex -jacobi\n-ex -gs\n-ex -bgs\n\n-s -power\n-s -jacobi\n-s -gs\n-s -bgs\n\n-h -power\n-h -jacobi\n-h -pgs\n\n-m -power\n-m -jacobi\n\n# and using interval iteration:\n\n-ii -ex -power\n-ii -ex -jacobi\n-ii -ex -gs\n-ii -ex -bgs\n\n-ii -s -power\n-ii -s -jacobi\n-ii -s -gs\n-ii -s -bgs\n\n-ii -h -power\n-ii -h -jacobi\n-ii -h -pgs\n\n-ii -m -power\n-ii -m -jacobi\n\n# and using -topological\n\n-ex -power -topological\n-ex -jacobi -topological\n-ex -gs -topological\n-ex -bgs -topological\n\n-ii -ex -power -topological\n-ii -ex -jacobi -topological\n-ii -ex -gs -topological\n-ii -ex -bgs -topological\n\n-exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_steady_1.pm",
    "content": "// simple sanity test case for DTMC steady state computations (2 BSCCs)\n\ndtmc\n\nmodule m1\n  s: [0..2] init 0;\n\n  [] s=0 -> 1/4:(s'=0) + 1/2:(s'=1) + 1/4:(s'=2);\n  [] s>0 -> true;\nendmodule\n\nmodule m2\n  t: [0..2] init 0;\n\n  [] true -> 1/2:(t'=0) + 1/4:(t'=1) + 1/4:(t'=2);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_steady_1.pm.props",
    "content": "// RESULT: 0\nS=?[ s=0 ];\n\n// RESULT: 0\nS=?[ s=0 & t=0 ];\n\n// RESULT: 1/3\nS=?[ s=1 & t=0 ];\n\n// RESULT: 1/6\nS=?[ s=1 & t=1 ];\n\n// RESULT: 1/6\nS=?[ s=1 & t=2 ];\n\n// RESULT: 1/6\nS=?[ s=2 & t=0 ];\n\n// RESULT: 1/12\nS=?[ s=2 & t=1 ];\n\n// RESULT: 1/12\nS=?[ s=2 & t=2 ];\n\n// RESULT: 1/2\nS=?[ t=0 ];\n\n// RESULT: 1/4\nS=?[ t=1 ];\n\n// RESULT: 1/4\nS=?[ t=1 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_steady_1.pm.props.args",
    "content": "-explicit\n-hybrid\n-sparse\n-mtbdd\n-exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_steady_2.pm",
    "content": "// simple test case for DTMC steady state computation (exhibits non-convergence using \"naive\" iteration)\n\ndtmc\n\nmodule m\n  s: [0..2] init 0;\n\n  [] s=0 -> 1/2:(s'=1) + 1/2:(s'=2);\n  [] s>0 -> (s'=0);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_steady_2.pm.props",
    "content": "// RESULT: 1\nS=?[ s=0 | s=1 | s=2 ];\n\n// RESULT: 1/2\nS=?[ s=0 ];\n\n// RESULT: 1/4\nS=?[ s=1 ];\n\n// RESULT: 1/4\nS=?[ s=2 ];\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/dtmc_steady_2.pm.props.args",
    "content": "# sanity check for convergence for the different engines\n# mtbdd/sparse/hybrid currently require the switch to the power method for convergence\n-mtbdd -power\n-sparse -power\n-hybrid -power\n-explicit\n-exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/jaeger.prism",
    "content": "dtmc\n \nmodule tree_160000\ns:[1..13] init 1;\n\n//[r1]s=1 -> 1011/3406:(s'=2) +  2395/3406:(s'=3);\n[r2]s=1 -> 968/3276:(s'=4) +  2308/3276:(s'=5);\n[r2]s=2 -> 122/261:(s'=6) +  139/261:(s'=7);\n[r1]s=4 -> 123/239:(s'=8) +  116/239:(s'=9);\n[r4]s=6 -> 14/35:(s'=10) +  21/35:(s'=11);\n[r4]s=8 -> 14/32:(s'=12) +  18/32:(s'=13);\n[r1]s=3 -> 1:(s'=3);\n[r1]s=5 -> 1:(s'=5);\n[r1]s=7 -> 1:(s'=7);\n[r1]s=9 -> 1:(s'=9);\n[r1]s=10 -> 1:(s'=10);\n[r1]s=11 -> 1:(s'=11);\n[r1]s=12 -> 1:(s'=12);\n[r1]s=13 -> 1:(s'=13);\nendmodule\n\nlabel \"o_000\" = s=1;\nlabel \"o_010\" = s=4;\nlabel \"o_100\" = s=2;\nlabel \"o_110\" = s=8|s=6;\nlabel \"o_Pr0\" = s=11|s=13;\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/jaeger.prism.props",
    "content": "// RESULT: 2143152/25054848  ( = 968/3276 * 123/239 * 18/32, i.e. approx. 0.085538)\nP=? [( (X ( X  ( \"o_110\"))) &  (X ( X  ( X ( \"o_Pr0\"))))) ]\n\n// RESULT: 119064/782964  ( = 968/3276 * 123/239, i.e. approx. 0.152068)\nP=? [ (X ( X  ( \"o_110\")))  ]\n\n// RESULT: 2143152/25054848  ( = 968/3276 * 123/239 * 18/32, i.e. approx. 0.085538)\nP=? [  (X ( X  ( X ( \"o_Pr0\")))) ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/jaeger.prism.props.args",
    "content": "-h\n-ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/lec15dtmc.pm",
    "content": "// Simple DTMC from Lec 15 of Probabilistic Model Checking\r\n\r\ndtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/lec15dtmc.pm.props",
    "content": "\t// RESULT: 1.0\n\tP=? [ G F s=3|s=4|s=5 ];\n\t\n\t// RESULT: 5/6 = 0.833333\n\tP=? [ G F s=3|s=4 ];\n\n\n\t// some more LTL formulas, combined with filters\n\n\t// RESULT: 1/6\n\tP=? [ G F (s=2 & (X s=5)) ];\n\n\t// RESULT: 1/6\n\tfilter(state, P=? [ G F (s=2 & (X s=5)) ], s=0);\n\n\t// RESULT: 1/3\n\tfilter(state, P=? [ G F (s=2 & (X s=5)) ], s=1);\n\n\t// RESULT: 1/6\n\tfilter(max, P=? [ G F (s=2 & (X s=5)) ], s=0 | s=4);\n\n\t// RESULT: 1/12\n\tfilter(avg, P=? [ G F (s=2 & (X s=5)) ], s=0 | s=4);\n\n\t// RESULT: 0.0\n\tfilter(state, P=? [ G F (s=2 & (X s=5)) ], s=4);\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/lec17dtmc.pm",
    "content": "// Simple DTMC from Lec 17 of Probabilistic Model Checking\r\n\r\ndtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.6:(s'=0) + 0.1:(s'=1) + 0.3:(s'=3);\r\n[] s=1 -> 0.2:(s'=3) + 0.3:(s'=4) + 0.5:(s'=2);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=4);\r\n[] s=4 -> 1:(s'=3);\r\n[] s=5 -> 0.1:(s'=2) + 0.9:(s'=5);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = s=2 | s=3 | s=5;\r\nlabel \"b\" = s=1;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/lec17dtmc.pm.nonprob.props",
    "content": "// non-probabilistic CTL*/LTL properties\n\n// --------------- non-probabilistic variants of lec17dtmc.pm.props -----\n// RESULT: true\nE [ G F \"a\" ];\n// RESULT: false\nA [ G F \"a\" ];\n\n// RESULT: true\nE [ (G !\"b\")&(G F \"a\") ];\n// RESULT: false\nA [ (G !\"b\")&(G F \"a\") ];\n\n// RESULT: true\nE [ F G \"a\" ];\n// RESULT: false\nA [ F G \"a\" ];\n\n// RESULT: true\nE [ (G (\"b\"=>(F (!\"b\"&\"a\"))))&(F G !\"b\") ];\n// RESULT: true\nA [ (G (\"b\"=>(F (!\"b\"&\"a\"))))&(F G !\"b\") ];\n\n// -------------- some basic tests ---------------------------------\n\n// RESULT: false\nA [ F (s=4 | s=5) ];\n// RESULT: true\nE [ F (s=4 | s=5) ];\n// RESULT: false\nA [ (F s=4) & (F s=5) ];\n// RESULT: false\nE [ (F s=4) & (F s=5) ];\n\n// RESULT: true\nA [ (G F (s=0 => s!=0)) => (F (s=4 | s=5)) ];\n// RESULT: true\nA [ (G F (s=0 => s!=0)) => ((F s=4) | (F s=5)) ];\n// RESULT: false\nA [ (G F (s=0 => s!=0)) => ((F s=4) & (F s=5)) ];\n\n// each state can reach s=2 or s=4 in one or two steps\n// RESULT: true\nfilter(forall, E[ X (s=2 | s=4 | (X (s=2 | s=4))) ], true);\n\n// variant not yet supported:\n// RESULT: Error:not supported\nfilter(forall, E[ F[1,2] (s=2 | s=4) ], true);\n\n// each state reaches s=2 or s=4 in one or two steps on every path\n// RESULT: false\nfilter(forall, A[ X (s=2 | s=4 | (X (s=2 | s=4))) ], true);\n\n// variant not yet supported:\n// RESULT: Error:not supported\nfilter(forall, A[ F[1,2] (s=2 | s=4) ], true);\n\n// RESULT: true\nfilter(exists, E[ F G s=0 ], true);\n// RESULT: false\nfilter(exists, A[ F G s=0 ], true);\n\n// ---- checking that product is correctly in sync -----\n// RESULT: true\nfilter(forall, E[ s=0 ], s=0);\n// RESULT: true\nfilter(forall, E[ s=1 ], s=1);\n// RESULT: true\nfilter(forall, E[ s=2 ], s=2);\n// RESULT: true\nfilter(forall, E[ s=3 ], s=3);\n// RESULT: true\nfilter(forall, E[ s=4 ], s=4);\n// RESULT: true\nfilter(forall, E[ s=5 ], s=5);\n\n// RESULT: true\nfilter(forall, A[ s=0 ], s=0);\n// RESULT: true\nfilter(forall, A[ s=1 ], s=1);\n// RESULT: true\nfilter(forall, A[ s=2 ], s=2);\n// RESULT: true\nfilter(forall, A[ s=3 ], s=3);\n// RESULT: true\nfilter(forall, A[ s=4 ], s=4);\n// RESULT: true\nfilter(forall, A[ s=5 ], s=5);\n\n// RESULT: true\nfilter(forall, A[ (X s=0) | (X s=1) | (X s=3)], s=0);\n// RESULT: true\nfilter(forall, A[ (X s=2) | (X s=3) | (X s=4) ], s=1);\n// RESULT: true\nfilter(forall, A[ (X s=5) ], s=2);\n// RESULT: true\nfilter(forall, A[ (X s=4) ], s=3);\n// RESULT: true\nfilter(forall, A[ (X s=3) ], s=4);\n// RESULT: true\nfilter(forall, A[ (X s=5) | (X s=2) ], s=5);\n\n// ----- nested ----------------------------\n\n// a path where there's always a path to go to s=4\n// does not necessarily end up there\n// RESULT: false\nA[ (G E[ F s=4 ]) => (F s=4) ]\n\n// however, there is such a path ...\n// RESULT: true\nE[ (G E[ F s=4 ]) => (F s=4) ]\n\n// and both can be satisfied simultaneously\n// RESULT: true\nE[ (G E[ F s=4 ]) & (F s=4) ]\n\n// on all paths that always have a chance to reach\n// s=4 either s=4 is seen infinitely often or\n// we always stay in s=0\n// RESULT: true\nA[ (G E[ F s=4 ]) => ((G F s=4) | (F G s=0)) ]\n\n// ---- does the product work with LTL simplification? --------\n\n// will be simplified to true, removing AP s=0\n// RESULT: true\nE[ true | (X s=0) ]\n\n// will be simplified to (s<4 & s=0) U s=4, reordering APs\n// RESULT: false\nE[ (s<4 U s=4) & (s=0 U s=4) ]\n\n// ---- trivial cases (true, false) --------\n\n// RESULT: true\nE[ true ];\n// RESULT: true\nA[ true ];\n\n// RESULT: false\nE[ false ];\n// RESULT: false\nA[ false ];\n\n// RESULT: true\nfilter(exists, E[ true ], true);\n// RESULT: true\nfilter(exists, A[ true ], true);\n// RESULT: true\nfilter(forall, E[ true ], true);\n// RESULT: true\nfilter(forall, A[ true ], true);\n\n// RESULT: false\nfilter(exists, E[ false ], true);\n// RESULT: false\nfilter(exists, A[ false ], true);\n// RESULT: false\nfilter(forall, E[ false ], true);\n// RESULT: false\nfilter(forall, A[ false ], true);\n\n// RESULT: true\nE[ G F true ];\n// RESULT: true\nA[ G F true ];\n\n// RESULT: false\nE[ G F false ];\n// RESULT: false\nA[ G F false ];\n\n// RESULT: true\nfilter(exists, E[ G F true ], true);\n// RESULT: true\nfilter(exists, A[ G F true ], true);\n// RESULT: true\nfilter(forall, E[ G F true ], true);\n// RESULT: true\nfilter(forall, A[ G F true ], true);\n\n// RESULT: false\nfilter(exists, E[ G F false ], true);\n// RESULT: false\nfilter(exists, A[ G F false ], true);\n// RESULT: false\nfilter(forall, E[ G F false ], true);\n// RESULT: false\nfilter(forall, A[ G F false ], true);\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/lec17dtmc.pm.nonprob.props.args",
    "content": "# explicit engine\n-ex\n\n# explicit engine, force LTL for all path formulas\n-ex -pathviaautomata\n\n# symbolic engine\n-mtbdd\n\n# explicit engine, treat as MDP\n-mdp -ex\n\n# explicit engine, treat as MDP, force LTL for all path formulas\n-mdp -ex -pathviaautomata\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/ltl/lec17dtmc.pm.props",
    "content": "\t// RESULT: 1\n\tP=? [ G F \"a\" ];\n\t\n\t// RESULT: 0.75\n\tP=? [ (G !\"b\")&(G F \"a\") ];\n\t\n\t// RESULT: 0.125\n\tP=? [ F G \"a\" ];\n\t\n\t// RESULT: 1\n\tP=? [ (G (\"b\"=>(F (!\"b\"&\"a\"))))&(F G !\"b\") ];\n\n\n\t// ---- does the product work with LTL simplification? --------\n\n\t// will be simplified to true, removing AP s=0\n\t// RESULT: true\n\tP>=1[ true | (X s=0) ]\n\n\t// will be simplified to (s<4 & s=0) U s=4, reordering APs\n\t// RESULT: true\n\tP<=0[ (s<4 U s=4) & (s=0 U s=4) ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/pctl/pctl-until.prism",
    "content": "dtmc\n\nmodule M\n\n    s : [0..4] init 0;\n\n    [] s=0 -> 1:(s'=1);\n\n    [] s=1 -> 0.6:(s'=2) + 0.4:(s'=3);\n\n    [] s=2 -> 1:(s'=2);\n    [] s=3 -> 1:(s'=3);\n    [] s=4 -> 1:(s'=4);\n\nendmodule\n\nlabel \"phi\" = s=0 | s=1 | s=3;\nlabel \"target\" = s=2;\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/pctl/pctl-until.prism.props",
    "content": "// RESULT: 0.6\nP=? [ \"phi\" U \"target\" ]\n\n// RESULT: 0\nP=? [ s=1 U \"target\" ]\n\n// RESULT: 0\nP=? [ \"phi\" U<=1 \"target\" ]\n\n// RESULT: 0.6\nP=? [ \"phi\" U<=2 \"target\" ]\n\n// RESULT: 0\nP=? [ \"phi\" U<2 \"target\" ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/pctl/pctl-until.prism.props.args",
    "content": "-h\n-s\n-m\n-ex -valiter\n-ex -gs\n-ex -ii\n\n-h -nopre\n-s -nopre\n-m -nopre\n-ex -valiter -nopre\n-ex -gs -nopre\n-ex -ii -nopre\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/cosafe/robot.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n//[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n//[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n//[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n//[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/cosafe/robot.pm.cosafe.props",
    "content": "// RESULT: 1.2  //  = 1+(0.8*0+0.1*1+0.1*1)   \nR=? [ (F \"goal1\") | (F \"goal2\") ]\n\n// RESULT: 1.2\nR=? [ X F (\"goal1\" | \"goal2\") ]\n\n// RESULT: 1.2\nR=? [ F X (\"goal1\" | \"goal2\") ]\n\n// RESULT: 2\nR=? [ X X (\"goal1\" | \"goal2\") ]\n\n// RESULT: Infinity\nR=? [ X X \"goal2\" ]\n\n// RESULT: 118/90\nR=? [ F \"goal2\" ]\n\n// RESULT: 118/90\nR=? [ (F \"goal2\") ]\n\n// RESULT: 118/90\nR=? [ s!=3 U \"goal2\" ]\n\n// RESULT: Error:co-safe\nR=? [ F G \"goal1\" ]\n\n// RESULT: Error:co-safe\nR=? [ F G \"goal1\" ]\n\n// RESULT: Error:co-safe\nR=? [ (G !\"hazard\")&(G F \"goal1\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/dtmc_rewards.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\t\r\n\t[] s=0 -> (s'=1);\r\n\t[] s=1 -> (s'=2);\r\n\t[] s=2 -> (s'=3);\r\n\t[] s>2 -> true;\r\n\r\nendmodule\r\n\r\nrewards \"a\"\r\n\ts=0: 2;\r\n\t[] s=0: 3;\r\n\ts=1: 5;\r\n\t[] s=1: 7;\r\n\ts=2: 11;\r\nendrewards\r\n\r\nrewards \"a_state\"\r\n\ts=0: 5;\r\n\ts=1: 12;\r\n\ts=2: 11;\r\nendrewards\r\n\r\nrewards \"b\"\r\n\ts=0: 2;\r\n\t[] s=0: 3;\r\n\ts=1: 5;\r\n\t[] s=1: 7;\r\n\ts=2: 11;\r\n\t[] s=3: 13;\r\n\ts=3: 17;\r\nendrewards\r\n\r\nrewards \"b_state\"\r\n\ts=0: 5;\r\n\ts=1: 12;\r\n\ts=2: 11;\r\n\ts=3: 30;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/dtmc_rewards.pm.cosafety.props",
    "content": "// RESULT: 0.0\nR{\"a\"}=? [ s>=0 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ true ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ !false ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ s>0 | s=0 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ s=0 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ F s=0 ];\n\n// RESULT: 5.0\nR{\"a\"}=? [ F s=1 ];\n\n// RESULT: 17.0\nR{\"a\"}=? [ F s=2 ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ F s=3 ];\n\n// RESULT: 5.0\nR{\"a\"}=? [ X s>=0 ];\n\n// RESULT: 5.0\nR{\"a\"}=? [ X true ];\n\n// RESULT: Infinity\nR{\"a\"}=? [ ! (X true) ];\n\n// RESULT: 5.0\nR{\"a\"}=? [ ! (X false) ];\n\n// RESULT: 17.0\nR{\"a\"}=? [ X X s>=0 ];\n\n// RESULT: 17.0\nR{\"a\"}=? [ X X true ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ X X X s>=0 ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ X X X true ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ X X X (true ? true : s>=0) ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ X X X (false ? true : s>=0) ];\n\n// RESULT: Infinity\nR{\"a\"}=? [ X X X false ];\n\n\n// nesting X and U...\n\n// RESULT: 0.0\nR{\"a\"}=? [ (X X true) U s=0 ];\n\n// RESULT: 17.0\nR{\"a\"}=? [ (X X true) U s=1 ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ (X X true) U s=2 ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ (X X true) U s=3 ];\n\n// RESULT: 58.0\nR{\"b\"}=? [ (X X true) U s=3 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ s=0 | (X true) ];\n\n\n// some more combinations...\n\n// RESULT: 12.0\nfilter(state, R{\"a\"}=? [ s=0 | (X true) ], s=1);\n\n// RESULT: 11.0\nfilter(state, R{\"a\"}=? [ s=0 | (X true) ], s=2);\n\n// RESULT: 0.0\nfilter(state, R{\"a\"}=? [ s=0 | (X true) ], s=3);\n\n// RESULT: 5.0\nfilter(state, R{\"a\"}=? [ (X s=1) | (X s=2) ], s=0);\n\n// RESULT: 12.0\nfilter(state, R{\"a\"}=? [ (X s=1) | (X s=2) ], s=1);\n\n// RESULT: Infinity\nfilter(state, R{\"a\"}=? [ (X s=1) | (X s=2) ], s=2);\n\n\n// nesting F and X\n\n// RESULT: 5.0\nR{\"a\"}=? [ F (X s=1) ];\n\n// RESULT: 17.0\nR{\"a\"}=? [ F (X s=2) ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ F (X s=3) ];\n\n// RESULT: 5.0\nR{\"a\"}=? [ F (s=0 & (X s=1)) ];\n\n// RESULT: 17.0\nR{\"a\"}=? [ F (s=1 & (X s=2)) ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ F (s=2 & (X s=3)) ];\n\n\n\n// the same as above, just using only state rewards\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ s>=0 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ true ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ !false ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ s>0 | s=0 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ s=0 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ F s=0 ];\n\n// RESULT: 5.0\nR{\"a_state\"}=? [ F s=1 ];\n\n// RESULT: 17.0\nR{\"a_state\"}=? [ F s=2 ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ F s=3 ];\n\n// RESULT: 5.0\nR{\"a_state\"}=? [ X s>=0 ];\n\n// RESULT: 5.0\nR{\"a_state\"}=? [ X true ];\n\n// RESULT: Infinity\nR{\"a_state\"}=? [ ! (X true) ];\n\n// RESULT: 5.0\nR{\"a_state\"}=? [ ! (X false) ];\n\n// RESULT: 17.0\nR{\"a_state\"}=? [ X X s>=0 ];\n\n// RESULT: 17.0\nR{\"a_state\"}=? [ X X true ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ X X X s>=0 ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ X X X true ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ X X X (true ? true : s>=0) ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ X X X (false ? true : s>=0) ];\n\n// RESULT: Infinity\nR{\"a_state\"}=? [ X X X false ];\n\n// nesting X and U...\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ (X X true) U s=0 ];\n\n// RESULT: 17.0\nR{\"a_state\"}=? [ (X X true) U s=1 ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ (X X true) U s=2 ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ (X X true) U s=3 ];\n\n// RESULT: 58.0\nR{\"b_state\"}=? [ (X X true) U s=3 ];\n\n\n// nesting X and U...\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ (X X true) U s=0 ];\n\n// RESULT: 17.0\nR{\"a_state\"}=? [ (X X true) U s=1 ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ (X X true) U s=2 ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ (X X true) U s=3 ];\n\n// RESULT: 58.0\nR{\"b_state\"}=? [ (X X true) U s=3 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ s=0 | (X true) ];\n\n\n// some more combinations...\n\n// RESULT: 12.0\nfilter(state, R{\"a_state\"}=? [ s=0 | (X true) ], s=1);\n\n// RESULT: 11.0\nfilter(state, R{\"a_state\"}=? [ s=0 | (X true) ], s=2);\n\n// RESULT: 0.0\nfilter(state, R{\"a_state\"}=? [ s=0 | (X true) ], s=3);\n\n// RESULT: 5.0\nfilter(state, R{\"a_state\"}=? [ (X s=1) | (X s=2) ], s=0);\n\n// RESULT: 12.0\nfilter(state, R{\"a_state\"}=? [ (X s=1) | (X s=2) ], s=1);\n\n// RESULT: Infinity\nfilter(state, R{\"a_state\"}=? [ (X s=1) | (X s=2) ], s=2);\n\n\n// nesting F and X\n\n// RESULT: 5.0\nR{\"a_state\"}=? [ F (X s=1) ];\n\n// RESULT: 17.0\nR{\"a_state\"}=? [ F (X s=2) ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ F (X s=3) ];\n\n// RESULT: 5.0\nR{\"a_state\"}=? [ F (s=0 & (X s=1)) ];\n\n// RESULT: 17.0\nR{\"a_state\"}=? [ F (s=1 & (X s=2)) ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ F (s=2 & (X s=3)) ];\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/dtmc_rewards.pm.props",
    "content": "// RESULT: 0.0\nR{\"a\"}=? [ C<=0 ];\n// RESULT: 5.0\nR{\"a\"}=? [ C<=1 ];\n// RESULT: 17.0\nR{\"a\"}=? [ C<=2 ];\n// RESULT: 28.0\nR{\"a\"}=? [ C<=3 ];\n\n// RESULT: 28.0\nR{\"a\"}=? [ C ];\n// RESULT: Infinity\nR{\"b\"}=? [ C ];\n\n// RESULT: 2.0\nR{\"a\"}=? [ I=0 ];\n// RESULT: 5.0\nR{\"a\"}=? [ I=1 ];\n// RESULT: 11.0\nR{\"a\"}=? [ I=2 ];\n// RESULT: 0.0\nR{\"a\"}=? [ I=3 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ F s=0 ];\n// RESULT: 5.0\nR{\"a\"}=? [ F s=1 ];\n// RESULT: 17.0\nR{\"a\"}=? [ F s=2 ];\n// RESULT: 28.0\nR{\"a\"}=? [ F s>2 ];\n\n// RESULT: 0.0\nR{\"a\"}=? [ S ];\n\n\n\n// same as above, using only state rewards\n// Note: I rewards are different from the results above\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ C<=0 ];\n// RESULT: 5.0\nR{\"a_state\"}=? [ C<=1 ];\n// RESULT: 17.0\nR{\"a_state\"}=? [ C<=2 ];\n// RESULT: 28.0\nR{\"a_state\"}=? [ C<=3 ];\n\n// RESULT: 28.0\nR{\"a_state\"}=? [ C ];\n// RESULT: Infinity\nR{\"b_state\"}=? [ C ];\n\n// RESULT: 5.0\nR{\"a_state\"}=? [ I=0 ];\n// RESULT: 12.0\nR{\"a_state\"}=? [ I=1 ];\n// RESULT: 11.0\nR{\"a_state\"}=? [ I=2 ];\n// RESULT: 0.0\nR{\"a_state\"}=? [ I=3 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ F s=0 ];\n// RESULT: 5.0\nR{\"a_state\"}=? [ F s=1 ];\n// RESULT: 17.0\nR{\"a_state\"}=? [ F s=2 ];\n// RESULT: 28.0\nR{\"a_state\"}=? [ F s>2 ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ S ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/dtmc_rewards2.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[r] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n\r\nrewards \"r\"\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/dtmc_rewards2.pm.props",
    "content": "\t// RESULT: 17/6\n\tR{\"r\"}=? [ F s>2 ];\n\t\n\t// RESULT: 13/6\n\tR{\"time\"}=? [ F s>2 ];\n\t\n\t// RESULT: Infinity\n\tR{\"r\"}=? [ F s>3 ];\n\t\n\t// RESULT: 15/32\n\tR{\"r\"}=? [ I=4 ];\n\t\n\t// RESULT: 14.060546875\n\tR{\"r\"}=? [ C<=10 ];\n\t\n\t// RESULT: Infinity\n\tR{\"r\"}=? [ C ];\n\t\n\t// RESULT: 23/12\n\tR{\"r\"}=? [ S ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/dtmc_rewards_bsccs.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\n\ts : [0..4];\r\n\t\r\n\t[] s=0 -> 0.4:(s'=1) + 0.6:(s'=3);\r\n\t[] s=1 -> (s'=2);\r\n\t[] s=2 -> (s'=1);\r\n\t[] s=3 -> (s'=4);\r\n\t[] s=4 -> (s'=3);\r\n\r\nendmodule\r\n\r\nrewards \"a\"\r\n\ts=0: 2;\r\nendrewards\r\n\r\nrewards \"b\"\r\n\ts=0: 2;\r\n\ts=1: 5;\r\nendrewards\r\n\r\nrewards \"c\"\r\n\ts=0: 2;\r\n\t[] s=3: 5;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/dtmcs/rewards/dtmc_rewards_bsccs.pm.props",
    "content": "// RESULT: 2.0\nR{\"a\"}=? [ F s>0 ];\n// RESULT: Infinity\nR{\"a\"}=? [ F s=1|s=2 ];\n// RESULT: Infinity\nR{\"a\"}=? [ F s=3|s=4 ];\n\n// RESULT: 2.0\nR{\"a\"}=? [ C ];\n// RESULT: Infinity\nR{\"b\"}=? [ C ];\n// RESULT: Infinity\nR{\"c\"}=? [ C ];\n\n// RESULT: Infinity\nfilter(state, R{\"b\"}=? [ C ], s=0);\n// RESULT: Infinity\nfilter(state, R{\"b\"}=? [ C ], s=1);\n// RESULT: Infinity\nfilter(state, R{\"b\"}=? [ C ], s=2);\n// RESULT: 0.0\nfilter(state, R{\"b\"}=? [ C ], s=3);\n// RESULT: 0.0\nfilter(state, R{\"b\"}=? [ C ], s=4);\n\n// RESULT: 0.0\nR{\"a\"}=? [ S ];\n// RESULT: 1.0\nR{\"b\"}=? [ S ];\n// RESULT: 1.5\nR{\"c\"}=? [ S ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-const-1.prism",
    "content": "// test case for setting exact external constants\n\ndtmc\n\nconst double p;\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..2] init 0;\n\n  [] s=0 -> p:(s'=1) + 1-p:(s'=2);\n  [] s>=1 -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-const-1.prism.props",
    "content": "// RESULT: 1/3\nP=?[ F s=1 ]\n\n// RESULT: false\nP>1/3[ F s=1 ]\n\n// RESULT: true\nP>=1/3[ F s=1 ]\n\n// RESULT: false\nP<1/3[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-const-1.prism.props.args",
    "content": "-const p=1/3,x=0 -exact\n-const p=1/3 -param x=0:1\n-const p=1/1/3,x=0 -exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-const-2.prism",
    "content": "// test case for exact constant evaluation\n\ndtmc\n\nconst double p = 1/3;\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..2] init 0;\n\n  [] s=0 -> p:(s'=1) + 1-p:(s'=2);\n  [] s>=1 -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-const-2.prism.props",
    "content": "// RESULT: 1/3\nP=?[ F s=1 ]\n\n// RESULT: false\nP>1/3[ F s=1 ]\n\n// RESULT: true\nP>=1/3[ F s=1 ]\n\n// RESULT: false\nP<1/3[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-const-2.prism.props.args",
    "content": "-const x=0 -exact\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-1.prism",
    "content": "// test case, check if double constants are evaluated exactly in exact / parametric mode\n\ndtmc\n\nconst double p = (1/3 = 0.333333333333333333333333 ? 1/2 : 0);\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..2] init 0;\n\n  [] s=0 -> p:(s'=1) + 1-p:(s'=2);\n  [] s>=1 -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-1.prism.props",
    "content": "// RESULT: 0\nP=?[ F s=1 ]\n\n// RESULT: false\nP>0[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-1.prism.props.args",
    "content": "-exact -const x=0\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-2.prism",
    "content": "// test case, check if int constants are evaluated exactly in exact / parametric mode\n\ndtmc\n\nconst int n = (1/3 = 0.333333333333333333333333 ? 1 : 2);\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..2] init 0;\n\n  [] s=0 -> 1/2:(s'=n) + 1/2:(s'=2);\n  [] s>=1 -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-2.prism.props",
    "content": "// RESULT: 0\nP=?[ F s=1 ]\n\n// RESULT: false\nP>0[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-2.prism.props.args",
    "content": "-exact -const x=0\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-3.prism",
    "content": "// test case, check if int expressions are evaluated exactly in exact / parametric mode\n\ndtmc\n\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..2] init 0;\n\n  [] s=0 -> 1/2:(s'=(1/3 = 0.333333333333333333333333 ? 1 : 2)) + 1/2:(s'=2);\n  [] s>=1 -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-3.prism.props",
    "content": "// RESULT: 0\nP=?[ F s=1 ]\n\n// RESULT: false\nP>0[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-3.prism.props.args",
    "content": "-exact -const x=0\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-4.prism",
    "content": "// test case, check if int expressions involving state variables are evaluated exactly in exact / parametric mode\n\ndtmc\n\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..2] init 0;\n\n  [] s=0 -> 1/2:(s'=((s+1)*1/3 = 0.333333333333333333333333 ? 1 : 2)) + 1/2:(s'=2);\n  [] s>=1 -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-4.prism.props",
    "content": "// RESULT: 0\nP=?[ F s=1 ]\n\n// RESULT: false\nP>0[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-4.prism.props.args",
    "content": "-exact -const x=0\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-5.prism",
    "content": "// test case, check if initial expressions are evaluated exactly in exact / parametric mode\n\ndtmc\n\nconst double x;  // dummy for parametric\n\nmodule M1\n  s1: [0..2] init (1/3 = 0.333333333333333333333333 ? 1 : 2);\n  s2: bool init (1/3 = 0.333333333333333333333333 ? true : false);\n\n  [] true -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-5.prism.props",
    "content": "// RESULT: 0\nP=?[ F s1=1 ]\n\n// RESULT: false\nP>0[ F s1=1 ]\n\n// RESULT: 0\nP=?[ F s2 ]\n\n// RESULT: false\nP>0[ F s2 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-5.prism.props.args",
    "content": "-exact -const x=0\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-6.prism",
    "content": "// test case, check if reward expressions are evaluated exactly in exact / parametric mode\n\nmdp\n\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..2] init 0;\n\n  [a] s=0 -> 1/2:(s'=1) + 1/2:(s'=2);\n  [] s>=1 -> true;\nendmodule\n\nrewards \"r\"\n  [a] true : (1/3 = 0.333333333333333333333333 ? 1 : 2);\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-6.prism.props",
    "content": "// RESULT: 2\nRmax=?[ F s>0 ]\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-6.prism.props.args",
    "content": "-exact -const x=0\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-7.prism",
    "content": "// test case, check if expressions in guards are evaluated exactly in exact / parametric mode\n\ndtmc\n\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..3] init 0;\n\n  // if the if part in the following guard expression is evaluated using\n  // default floating point arithmetic then, ultimately, from state s=0 there are\n  // two transitions, with prob 1/2 to either s=1 or s=2\n  [] s=(1/3 = 0.333333333333333333333333 ? 0 : 3) -> 1:(s'=1);\n  [] s=0 -> 1:(s'=2);\n\n  [] s>=1 -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-7.prism.props",
    "content": "// RESULT: 0\nP=?[ F s=1 ]\n\n// RESULT: false\nP>0[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-7.prism.props.args",
    "content": "-exact -const x=0\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-8.prism",
    "content": "// test case, check if guards in reward expressions are evaluated exactly in exact / parametric mode\n\nmdp\n\nconst double x;  // dummy for parametric\n\nmodule M1\n  s: [0..2] init 0;\n\n  [a] s=0 -> 1/2:(s'=1) + 1/2:(s'=2);\n  [] s>=1 -> true;\nendmodule\n\nrewards \"r\"\n  [a] s=(1/3 = 0.333333333333333333333333 ? 1 : 0) : 2;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-8.prism.props",
    "content": "// RESULT: 2\nRmax=?[ F s>0 ]\n\n// test case to check that arithmetic in the property is done exactly\n// RESULT: false\n(1/3 = 0.3333333333333333333333333333)\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-eval-8.prism.props.args",
    "content": "-exact -const x=0\n-param x=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-experiment-1.prism",
    "content": "// test case for experiments using fractional constants and fractional RESULTs in the property file\n\ndtmc\n\nconst double p;\n\nmodule M1\n  s: [0..2] init 0;\n\n  [] s=0 -> p:(s'=1) + 1-p:(s'=2);\n  [] s>=1 -> true;\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-experiment-1.prism.props",
    "content": "// RESULT(p=0): 0\n// RESULT(p=1/3): 1/3\n// RESULT(p=2/3): 2/3\n// RESULT(p=1): 1\nP=?[F s=1]\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-experiment-1.prism.props.args",
    "content": "-hybrid -const p=0:1/3:1\n-explicit -const p=0:1/3:1\n-exact -const p=0:1/3:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-literal.prism",
    "content": "// test case for exact handling of floating point literals\n\ndtmc\n\n// in exact mode, this literal should be kept with full precision\n// and not be approximated by 0.5, which would happen if it's converted to a double first\nconst double p = 0.500000000000000000000000000000001;\n\nconst double x;  // dummy, for parametric mode\n\nmodule M1\n  s: [0..2] init 0;\n\n  [] s=0 -> p:(s'=1) + (1-p):(s'=2);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-literal.prism.exact.props",
    "content": "// RESULT: 500000000000000000000000000000001/1000000000000000000000000000000000\nP=?[ F s=1 ]\n\n// RESULT: true\nP>1/2[ F s=1 ]\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/exact/exact-literal.prism.exact.props.args",
    "content": "--exact --const x=0\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/brp_int.prism",
    "content": "// bounded retransmission protocol [D'AJJL01]\r\n// gxn/dxp 23/05/2001\r\n\r\ndtmc\r\n\r\n// number of chunks\r\nconst int N;\r\n// maximum number of retransmissions\r\nconst int MAX;\r\n\r\nconst double err;\r\n\r\nmodule sender\r\n\r\n\ts : [0..6];\r\n\t// 0 idle\r\n\t// 1 next_frame\t\r\n\t// 2 wait_ack\r\n\t// 3 retransmit\r\n\t// 4 success\r\n\t// 5 error\r\n\t// 6 wait sync\r\n\tsrep : [0..3];\r\n\t// 0 bottom\r\n\t// 1 not ok (nok)\r\n\t// 2 do not know (dk)\r\n\t// 3 ok (ok)\r\n\tnrtr : [0..MAX];\r\n\ti : [0..N];\r\n\tbs : bool;\r\n\ts_ab : bool;\r\n\tfs : bool;\r\n\tls : bool;\r\n\t\r\n\t// idle\r\n\t[NewFile] (s=0) -> (s'=1) & (i'=1) & (srep'=0);\r\n\t// next_frame\r\n\t[aF] (s=1) -> (s'=2) & (fs'=(i=1)) & (ls'=(i=N)) & (bs'=s_ab) & (nrtr'=0);\r\n\t// wait_ack\r\n\t[aB] (s=2) -> (s'=4) & (s_ab'=!s_ab);\r\n\t[TO_Msg] (s=2) -> (s'=3);\r\n\t[TO_Ack] (s=2) -> (s'=3);\r\n\t// retransmit\r\n\t[aF] (s=3) & (nrtr<MAX) -> (s'=2) & (fs'=(i=1)) & (ls'=(i=N)) & (bs'=s_ab) & (nrtr'=nrtr+1);\r\n\t[] (s=3) & (nrtr=MAX) & (i<N) -> (s'=5) & (srep'=1);\r\n\t[] (s=3) & (nrtr=MAX) & (i=N) -> (s'=5) & (srep'=2);\r\n\t// success\r\n\t[] (s=4) & (i<N) -> (s'=1) & (i'=i+1);\r\n\t[] (s=4) & (i=N) -> (s'=0) & (srep'=3);\r\n\t// error\r\n\t[SyncWait] (s=5) -> (s'=6); \r\n\t// wait sync\r\n\t[SyncWait] (s=6) -> (s'=0) & (s_ab'=false); \r\n\t\r\nendmodule\r\n\r\nmodule receiver\r\n\r\n\tr : [0..5];\r\n\t// 0 new_file\r\n\t// 1 fst_safe\r\n\t// 2 frame_received\r\n\t// 3 frame_reported\r\n\t// 4 idle\r\n\t// 5 resync\r\n\trrep : [0..4];\r\n\t// 0 bottom\r\n\t// 1 fst\r\n\t// 2 inc\r\n\t// 3 ok\r\n\t// 4 nok\r\n\tfr : bool;\r\n\tlr : bool;\r\n\tbr : bool;\r\n\tr_ab : bool;\r\n\trecv : bool;\r\n\t\r\n\t\r\n\t// new_file\r\n\t[SyncWait] (r=0) -> (r'=0);\r\n\t[aG] (r=0) -> (r'=1) & (fr'=fs) & (lr'=ls) & (br'=bs) & (recv'=T);\r\n\t// fst_safe_frame\r\n\t[] (r=1) -> (r'=2) & (r_ab'=br);\r\n\t// frame_received\r\n\t[] (r=2) & (r_ab=br) & (fr=true) & (lr=false)  -> (r'=3) & (rrep'=1);\r\n\t[] (r=2) & (r_ab=br) & (fr=false) & (lr=false) -> (r'=3) & (rrep'=2);\r\n\t[] (r=2) & (r_ab=br) & (fr=false) & (lr=true)  -> (r'=3) & (rrep'=3);\r\n\t[aA] (r=2) & !(r_ab=br) -> (r'=4);  \r\n\t// frame_reported\r\n\t[aA] (r=3) -> (r'=4) & (r_ab'=!r_ab);\r\n\t// idle\r\n\t[aG] (r=4) -> (r'=2) & (fr'=fs) & (lr'=ls) & (br'=bs) & (recv'=T);\r\n\t[SyncWait] (r=4) & (ls=true) -> (r'=5);\r\n\t[SyncWait] (r=4) & (ls=false) -> (r'=5) & (rrep'=4);\r\n\t// resync\r\n\t[SyncWait] (r=5) -> (r'=0) & (rrep'=0);\r\n\t\r\nendmodule\r\n\t\r\nmodule checker\r\n\r\n\tT : bool;\r\n\t\r\n//\t[NewFile] (T=false) -> (T'=false);\r\n\t[NewFile] (T=false) -> (T'=true);\r\n\t\r\nendmodule\r\n\r\nmodule\tchannelK\r\n\r\n\tk : [0..2];\r\n\t\r\n\t// idle\r\n\t[aF] (k=0) -> [(1-err)*0.98, (1+err)*0.98] : (k'=1) + [(1-err)*0.02, (1+err)*0.02] : (k'=2);\r\n\t// sending\r\n\t[aG] (k=1) -> (k'=0);\r\n\t// lost\r\n\t[TO_Msg] (k=2) -> (k'=0);\r\n\t\r\nendmodule\r\n\r\nmodule\tchannelL\r\n\r\n\tl : [0..2];\r\n\t\r\n\t// idle\r\n\t[aA] (l=0) -> [(1-err)*0.99, (1+err)*0.99] : (l'=1) + [(1-err)*0.01, (1+err)*0.01] : (l'=2);\r\n\t// sending\r\n\t[aB] (l=1) -> (l'=0);\r\n\t// lost\r\n\t[TO_Ack] (l=2) -> (l'=0);\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/brp_int.prism.props",
    "content": "// RESULT (N=16,MAX=2,err=0.01): 4.108451315950149E-4\r\n// RESULT (N=16,MAX=3,err=0.01): 1.2123832682674567E-5\r\n// RESULT (N=16,MAX=4,err=0.01): 3.5770328950369254E-7\r\n// RESULT (N=16,MAX=5,err=0.01): 1.0553672425877384E-8\r\n// RESULT (N=32,MAX=2,err=0.01): 8.215214679223887E-4\r\n// RESULT (N=32,MAX=3,err=0.01): 2.424751834880762E-5\r\n// RESULT (N=32,MAX=4,err=0.01): 7.154064515366512E-7\r\n// RESULT (N=32,MAX=5,err=0.01): 2.1107344715746883E-8\r\n// RESULT (N=64,MAX=2,err=0.01): 0.0016423680383381618\r\n// RESULT (N=64,MAX=3,err=0.01): 4.849444875450165E-5\r\n// RESULT (N=64,MAX=4,err=0.01): 1.4308123878589935E-6\r\n// RESULT (N=64,MAX=5,err=0.01): 4.221468899151534E-8\r\n\"p1_min\": Pmin=? [ F s=5 ];\r\n\r\n// RESULT (N=16,MAX=2,err=0.01): 4.3607045383520796E-4\r\n// RESULT (N=16,MAX=3,err=0.01): 1.312657029099825E-5\r\n// RESULT (N=16,MAX=4,err=0.01): 3.950593541717136E-7\r\n// RESULT (N=16,MAX=5,err=0.01): 1.1889700569121855E-8\r\n// RESULT (N=32,MAX=2,err=0.01): 8.719507504132649E-4\r\n// RESULT (N=32,MAX=3,err=0.01): 2.6252968237514252E-5\r\n// RESULT (N=32,MAX=4,err=0.01): 7.901185528498484E-7\r\n// RESULT (N=32,MAX=5,err=0.01): 2.3779400963859668E-8\r\n// RESULT (N=64,MAX=2,err=0.01): 0.0017431411982773406\r\n// RESULT (N=64,MAX=3,err=0.01): 5.2505247250938087E-5\r\n// RESULT (N=64,MAX=4,err=0.01): 1.5802364767854307E-6\r\n// RESULT (N=64,MAX=5,err=0.01): 4.755880136549375E-8\r\n\"p1_max\": Pmax=? [ F s=5 ];\r\n\r\n// RESULT (N=16,MAX=2,err=0.01): 2.567226750562603E-5\r\n// RESULT (N=16,MAX=3,err=0.01): 7.577345229574669E-7\r\n// RESULT (N=16,MAX=4,err=0.01): 2.2356451074604786E-8\r\n// RESULT (N=16,MAX=5,err=0.01): 6.596045226939831E-10\r\n// RESULT (N=32,MAX=2,err=0.01): 2.566107256972064E-5\r\n// RESULT (N=32,MAX=3,err=0.01): 7.57724577392054E-7\r\n// RESULT (N=32,MAX=4,err=0.01): 2.2356442221484233E-8\r\n// RESULT (N=32,MAX=5,err=0.01): 6.596045145312226E-10\r\n// RESULT (N=64,MAX=2,err=0.01): 2.5638697371048286E-5\r\n// RESULT (N=64,MAX=3,err=0.01): 7.577046827197582E-7\r\n// RESULT (N=64,MAX=4,err=0.01): 2.235642455632081E-8\r\n// RESULT (N=64,MAX=5,err=0.01): 6.596044970266844E-10\r\n\"p2_min\": Pmin=? [ F s=5 & srep=2 ];\r\n\r\n// RESULT (N=16,MAX=2,err=0.01): 2.7249476182381116E-5\r\n// RESULT (N=16,MAX=3,err=0.01): 8.204063654865639E-7\r\n// RESULT (N=16,MAX=4,err=0.01): 2.4691205950966274E-8\r\n// RESULT (N=16,MAX=5,err=0.01): 7.431062812899422E-10\r\n// RESULT (N=32,MAX=2,err=0.01): 2.7238280851774565E-5\r\n// RESULT (N=32,MAX=3,err=0.01): 8.203964198712316E-7\r\n// RESULT (N=32,MAX=4,err=0.01): 2.4691197100388716E-8\r\n// RESULT (N=32,MAX=5,err=0.01): 7.431062745540553E-10\r\n// RESULT (N=64,MAX=2,err=0.01): 2.7215904014518398E-5\r\n// RESULT (N=64,MAX=3,err=0.01): 8.203765254741548E-7\r\n// RESULT (N=64,MAX=4,err=0.01): 2.4691179437374115E-8\r\n// RESULT (N=64,MAX=5,err=0.01): 7.431062572695873E-10\r\n\"p2_max\": Pmax=? [ F s=5 & srep=2 ];\r\n\r\n// RESULT (N=16,MAX=2,err=0.01): 7.762392000000002E-6\r\n// RESULT (N=16,MAX=3,err=0.01): 1.5369536160000006E-7\r\n// RESULT (N=16,MAX=4,err=0.01): 3.0431681596800015E-9\r\n// RESULT (N=16,MAX=5,err=0.01): 6.025472956166403E-11\r\n// RESULT (N=32,MAX=2,err=0.01): 7.762392000000002E-6\r\n// RESULT (N=32,MAX=3,err=0.01): 1.5369536160000006E-7\r\n// RESULT (N=32,MAX=4,err=0.01): 3.0431681596800015E-9\r\n// RESULT (N=32,MAX=5,err=0.01): 6.025472956166403E-11\r\n// RESULT (N=64,MAX=2,err=0.01): 7.762392000000002E-6\r\n// RESULT (N=64,MAX=3,err=0.01): 1.5369536160000006E-7\r\n// RESULT (N=64,MAX=4,err=0.01): 3.0431681596800015E-9\r\n// RESULT (N=64,MAX=5,err=0.01): 6.025472956166403E-11\r\n\"p4_min\": Pmin=? [ F !(srep=0) & !recv ];\r\n\r\n// RESULT (N=16,MAX=2,err=0.01): 8.242408E-6\r\n// RESULT (N=16,MAX=3,err=0.01): 1.6649664159999998E-7\r\n// RESULT (N=16,MAX=4,err=0.01): 3.3632321603199997E-9\r\n// RESULT (N=16,MAX=5,err=0.01): 6.793728963846399E-11\r\n// RESULT (N=32,MAX=2,err=0.01): 8.242408E-6\r\n// RESULT (N=32,MAX=3,err=0.01): 1.6649664159999998E-7\r\n// RESULT (N=32,MAX=4,err=0.01): 3.3632321603199997E-9\r\n// RESULT (N=32,MAX=5,err=0.01): 6.793728963846399E-11\r\n// RESULT (N=64,MAX=2,err=0.01): 8.242408E-6\r\n// RESULT (N=64,MAX=3,err=0.01): 1.6649664159999998E-7\r\n// RESULT (N=64,MAX=4,err=0.01): 3.3632321603199997E-9\r\n// RESULT (N=64,MAX=5,err=0.01): 6.793728963846399E-11\r\n\"p4_max\": Pmax=? [ F !(srep=0) & !recv ];\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/brp_int.prism.props.args",
    "content": "-fixdl -ex -const N=16 -const MAX=2 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=16 -const MAX=3 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=16 -const MAX=4 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=16 -const MAX=5 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=32 -const MAX=2 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=32 -const MAX=3 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=32 -const MAX=4 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=32 -const MAX=5 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=64 -const MAX=2 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=64 -const MAX=3 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=64 -const MAX=4 -epsilon 1e-8 -const err=0.01\r\n-fixdl -ex -const N=64 -const MAX=5 -epsilon 1e-8 -const err=0.01\r\n# -fixdl -ex -const N=16 -const MAX=2 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=16 -const MAX=3 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=16 -const MAX=4 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=16 -const MAX=5 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=32 -const MAX=2 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=32 -const MAX=3 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=32 -const MAX=4 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=32 -const MAX=5 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=64 -const MAX=2 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=64 -const MAX=3 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=64 -const MAX=4 -convprog Gurobi -const err=0.01\r\n# -fixdl -ex -const N=64 -const MAX=5 -convprog Gurobi -const err=0.01\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/crowds_int.prism",
    "content": "// CROWDS [Reiter,Rubin]\r\n// Vitaly Shmatikov, 2002\r\n\r\n// Note:\r\n// Change everything marked CWDSIZ when changing the size of the crowd\r\n// Change everything marked CWDMAX when increasing max size of the crowd\r\n\r\ndtmc\r\n\r\n// Probability of forwarding\r\nconst double PF = 0.8;\r\n\r\n// Probability that a crowd member is bad\r\nconst double  badC = 0.091;\r\n// const double  badC = 0.167;\r\n\r\nconst int TotalRuns; // Total number of protocol runs to analyze\r\nconst int CrowdSize; // CWDSIZ: actual number of good crowd members\r\nconst int MaxGood=20; // CWDMAX: maximum number of good crowd members\r\n\r\nconst double err;\r\n\r\n// Process definitions\r\nmodule crowds\r\n\r\n\t// Auxiliary variables\r\n\tlaunch:   bool init true;       // Start modeling?\r\n\tnew:      bool init false;      // Initialize a new protocol instance?\r\n\trunCount: [0..TotalRuns] init TotalRuns;   // Counts protocol instances\r\n\tstart:    bool init false;      // Start the protocol?\r\n\trun:      bool init false;      // Run the protocol?\r\n\tlastSeen: [0..MaxGood] init MaxGood;   // Last crowd member to touch msg\r\n\tgood:     bool init false;      // Crowd member is good?\r\n\tbad:      bool init false;      //              ... bad?\r\n\trecordLast: bool init false;    // Record last seen crowd member?\r\n\tbadObserve: bool init false;    // Bad members observes who sent msg?\r\n\tdeliver:  bool init false;      // Deliver message to destination?\r\n\tdone:     bool init false;      // Protocol instance finished?\r\n\r\n\t// Counters for attackers' observations\r\n\t// CWDMAX: 1 counter per each good crowd member\r\n\tobserve0:  [0..TotalRuns] init 0;\r\n\tobserve1:  [0..TotalRuns] init 0;\r\n\tobserve2:  [0..TotalRuns] init 0;\r\n\tobserve3:  [0..TotalRuns] init 0;\r\n\tobserve4:  [0..TotalRuns] init 0;\r\n\tobserve5:  [0..TotalRuns] init 0;\r\n\tobserve6:  [0..TotalRuns] init 0;\r\n\tobserve7:  [0..TotalRuns] init 0;\r\n\tobserve8:  [0..TotalRuns] init 0;\r\n\tobserve9:  [0..TotalRuns] init 0;\r\n\tobserve10: [0..TotalRuns] init 0;\r\n\tobserve11: [0..TotalRuns] init 0;\r\n\tobserve12: [0..TotalRuns] init 0;\r\n\tobserve13: [0..TotalRuns] init 0;\r\n\tobserve14: [0..TotalRuns] init 0;\r\n\tobserve15: [0..TotalRuns] init 0;\r\n\tobserve16: [0..TotalRuns] init 0;\r\n\tobserve17: [0..TotalRuns] init 0;\r\n\tobserve18: [0..TotalRuns] init 0;\r\n\tobserve19: [0..TotalRuns] init 0;\r\n\t\r\n\t[] launch -> (new'=true) & (runCount'=TotalRuns) & (launch'=false);\r\n\t// Set up a new protocol instance\r\n\t[] new & runCount>0 -> (runCount'=runCount-1) & (new'=false) & (start'=true);\r\n\t\r\n\t// SENDER\r\n\t// Start the protocol\r\n\t[] start -> (lastSeen'=0) & (run'=true) & (deliver'=false) & (start'=false);\r\n\t\r\n\t// CROWD MEMBERS\r\n\t// Good or bad crowd member?\r\n\t[] !good & !bad & !deliver & run ->\r\n\t             1-badC : (good'=true) & (recordLast'=true) & (run'=false) +\r\n\t               badC : (bad'=true)  & (badObserve'=true) & (run'=false);\r\n\r\n\t// GOOD MEMBERS\r\n\t// Forward with probability PF, else deliver\r\n\t[] good & !deliver & run -> PF : (good'=false) + 1-PF : (deliver'=true);\r\n\t// Record the last crowd member who touched the msg;\r\n\t// all good members may appear with equal probability\r\n\t//    Note: This is backward.  In the real protocol, each honest\r\n\t//          forwarder randomly chooses the next forwarder.\r\n\t//          Here, the identity of an honest forwarder is randomly\r\n\t//          chosen *after* it has forwarded the message.\r\n\t[] recordLast & CrowdSize=2 ->\r\n\t        [1/2*(1-err),1/2*(1+err)] : (lastSeen'=0) & (recordLast'=false) & (run'=true) +\r\n\t        [1/2*(1-err),1/2*(1+err)] : (lastSeen'=1) & (recordLast'=false) & (run'=true);\r\n\t[] recordLast & CrowdSize=4 ->\r\n\t        [1/4*(1-err),1/4*(1+err)] : (lastSeen'=0) & (recordLast'=false) & (run'=true) +\r\n\t        [1/4*(1-err),1/4*(1+err)] : (lastSeen'=1) & (recordLast'=false) & (run'=true) +\r\n\t        [1/4*(1-err),1/4*(1+err)] : (lastSeen'=2) & (recordLast'=false) & (run'=true) +\r\n\t        [1/4*(1-err),1/4*(1+err)] : (lastSeen'=3) & (recordLast'=false) & (run'=true);\r\n\t[] recordLast & CrowdSize=5 ->\r\n\t        [1/5*(1-err),1/5*(1+err)] : (lastSeen'=0) & (recordLast'=false) & (run'=true) +\r\n\t        [1/5*(1-err),1/5*(1+err)] : (lastSeen'=1) & (recordLast'=false) & (run'=true) +\r\n\t        [1/5*(1-err),1/5*(1+err)] : (lastSeen'=2) & (recordLast'=false) & (run'=true) +\r\n\t        [1/5*(1-err),1/5*(1+err)] : (lastSeen'=3) & (recordLast'=false) & (run'=true) +\r\n\t        [1/5*(1-err),1/5*(1+err)] : (lastSeen'=4) & (recordLast'=false) & (run'=true);\r\n\t[] recordLast & CrowdSize=10 ->\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=0) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=1) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=2) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=3) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=4) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=5) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=6) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=7) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=8) & (recordLast'=false) & (run'=true) +\r\n\t        [1/10*(1-err),1/10*(1+err)] : (lastSeen'=9) & (recordLast'=false) & (run'=true);\r\n\t[] recordLast & CrowdSize=15 ->\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=0)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=1)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=2)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=3)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=4)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=5)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=6)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=7)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=8)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=9)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=10) & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=11) & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=12) & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=13) & (recordLast'=false) & (run'=true) +\r\n\t        [1/15*(1-err),1/15*(1+err)] : (lastSeen'=14) & (recordLast'=false) & (run'=true);\r\n\t[] recordLast & CrowdSize=20 ->\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=0)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=1)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=2)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=3)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=4)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=5)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=6)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=7)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=8)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=9)  & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=10) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=11) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=12) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=13) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=14) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=15) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=16) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=17) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=18) & (recordLast'=false) & (run'=true) +\r\n\t        [1/20*(1-err),1/20*(1+err)] : (lastSeen'=19) & (recordLast'=false) & (run'=true);\r\n\t\r\n\t// BAD MEMBERS\r\n\t// Remember from whom the message was received and deliver\r\n\t// CWDMAX: 1 rule per each good crowd member\r\n\t[] lastSeen=0  & badObserve & observe0 <TotalRuns -> (observe0' =observe0 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=1  & badObserve & observe1 <TotalRuns -> (observe1' =observe1 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=2  & badObserve & observe2 <TotalRuns -> (observe2' =observe2 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=3  & badObserve & observe3 <TotalRuns -> (observe3' =observe3 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=4  & badObserve & observe4 <TotalRuns -> (observe4' =observe4 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=5  & badObserve & observe5 <TotalRuns -> (observe5' =observe5 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=6  & badObserve & observe6 <TotalRuns -> (observe6' =observe6 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=7  & badObserve & observe7 <TotalRuns -> (observe7' =observe7 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=8  & badObserve & observe8 <TotalRuns -> (observe8' =observe8 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=9  & badObserve & observe9 <TotalRuns -> (observe9' =observe9 +1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=10 & badObserve & observe10<TotalRuns -> (observe10'=observe10+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=11 & badObserve & observe11<TotalRuns -> (observe11'=observe11+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=12 & badObserve & observe12<TotalRuns -> (observe12'=observe12+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=13 & badObserve & observe13<TotalRuns -> (observe13'=observe13+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=14 & badObserve & observe14<TotalRuns -> (observe14'=observe14+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=15 & badObserve & observe15<TotalRuns -> (observe15'=observe15+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=16 & badObserve & observe16<TotalRuns -> (observe16'=observe16+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=17 & badObserve & observe17<TotalRuns -> (observe17'=observe17+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=18 & badObserve & observe18<TotalRuns -> (observe18'=observe18+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\t[] lastSeen=19 & badObserve & observe19<TotalRuns -> (observe19'=observe19+1) & (deliver'=true) & (run'=true) & (badObserve'=false);\r\n\r\n\t// RECIPIENT\r\n\t// Delivery to destination\r\n\t[] deliver & run -> (done'=true) & (deliver'=false) & (run'=false) & (good'=false) & (bad'=false);\r\n\t// Start a new instance\r\n\t[] done -> (new'=true) & (done'=false) & (run'=false) & (lastSeen'=MaxGood);\r\n\t\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/crowds_int.prism.props",
    "content": "// Probability that the adversary observes the real sender more than once\r\n// RESULT (TotalRuns=5,CrowdSize=4): 0.15670416461\r\n\"positive_min\": Pmin=? [ F observe0 > 1  ];\r\n\r\n// Probability that the adversary observes the real sender more than once\r\n// RESULT (TotalRuns=5,CrowdSize=4): 0.17915896132\r\n\"positive_max\": Pmax=? [ F observe0 > 1  ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/crowds_int.prism.props.args",
    "content": "-ex -const CrowdSize=4 -const TotalRuns=5 -const err=0.1 -epsilon 1e-8\r\n# -ex -const CrowdSize=4 -const TotalRuns=5 -const err=0.1 -convprog Gurobi\r\n# -ex -const CrowdSize=4 -const TotalRuns=5 -const err=0.1 -convprog lpsolve\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/dtmc_pctl.prism",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> [0.5,0.5]:(s'=1) + [0.5,0.5]:(s'=3);\r\n[] s=1 -> [0.5,0.5]:(s'=0) + [0.25,0.25]:(s'=2) + [0.25,0.25]:(s'=4);\r\n[r] s=2 -> [1,1]:(s'=5);\r\n[] s=3 -> [1,1]:(s'=3);\r\n[] s=4 -> [1,1]:(s'=4);\r\n[] s=5 -> [1,1]:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n\r\nrewards \"r\"\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/dtmc_pctl.prism.cosafe.props",
    "content": "// RESULT: 1\nPmin=? [ X F s>=2 ];\n\n// RESULT: 1\nPmax=? [ X F s>=2 ];\n\n// RESULT: 2\nRmin=? [ X F s>=2 ];\n\n// RESULT: 2\nRmax=? [ X F s>=2 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/dtmc_pctl.prism.props",
    "content": "\t// RESULT: 1/2\r\n\tPmin=? [ X s=1 ];\r\n\t\r\n\t// RESULT: 1/6\r\n\tPmin=? [ F s=2 ];\r\n\t\r\n\t// RESULT: 1/3\r\n\tPmin=? [ F s=2|s=4 ];\r\n\t\r\n\t// RESULT: 0\r\n\tPmin=? [ F<=0 s=2 ];\r\n\t\r\n\t// RESULT: 1/8\r\n\tPmin=? [ F<=2 s=2 ];\r\n\t\r\n\t// RESULT: 1/8\r\n\tPmin=? [ F<=3 s=2 ];\r\n\t\r\n\t// RESULT: 1/8\r\n\tPmin=? [ F<4 s=2 ];\r\n\t\r\n\t// RESULT: 0.16650390625\r\n\tPmin=? [ F<=10 s=2 ];\r\n\t\r\n\t// RESULT: 0\r\n\tPmin=? [ G s<2 ];\r\n\t\r\n\t// RESULT: 0.0625\r\n\tPmin=? [ G<=4 s<2 ];\r\n\t\r\n\t// RESULT: 1/2\r\n\tPmin=? [ s!=1 U s=3 ];\r\n\t\r\n\t// RESULT: 1/2\r\n\tPmin=? [ s!=1 U<=1 s=3 ];\r\n\t\r\n\t// RESULT: 1/2\r\n\tPmin=? [ s!=1 U<=8 s=3 ];\r\n\t\r\n\t// RESULT: 14.060546875\r\n\tR{\"r\"}min=? [ C<=10 ];\r\n\t\r\n\t// RESULT: 23/12\r\n\tR{\"r\"}min=? [ S ];\r\n\r\n// ---\r\n\r\n\t// RESULT: 1/2\r\n\tPmax=? [ X s=1 ];\r\n\t\r\n\t// RESULT: 1/6\r\n\tPmax=? [ F s=2 ];\r\n\t\r\n\t// RESULT: 1/3\r\n\tPmax=? [ F s=2|s=4 ];\r\n\t\r\n\t// RESULT: 0\r\n\tPmax=? [ F<=0 s=2 ];\r\n\t\r\n\t// RESULT: 1/8\r\n\tPmax=? [ F<=2 s=2 ];\r\n\t\r\n\t// RESULT: 1/8\r\n\tPmax=? [ F<=3 s=2 ];\r\n\t\r\n\t// RESULT: 1/8\r\n\tPmax=? [ F<4 s=2 ];\r\n\t\r\n\t// RESULT: 0.16650390625\r\n\tPmax=? [ F<=10 s=2 ];\r\n\t\r\n\t// RESULT: 0\r\n\tPmax=? [ G s<2 ];\r\n\t\r\n\t// RESULT: 0.0625\r\n\tPmax=? [ G<=4 s<2 ];\r\n\t\r\n\t// RESULT: 1/2\r\n\tPmax=? [ s!=1 U s=3 ];\r\n\t\r\n\t// RESULT: 1/2\r\n\tPmax=? [ s!=1 U<=1 s=3 ];\r\n\t\r\n\t// RESULT: 1/2\r\n\tPmax=? [ s!=1 U<=8 s=3 ];\r\n\t\r\n\t// RESULT: 14.060546875\r\n\tR{\"r\"}max=? [ C<=10 ];\r\n\t\r\n\t// RESULT: 23/12\r\n\tR{\"r\"}max=? [ S ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/egl_int.prism",
    "content": "// randomized protocol for signing contracts Even, Goldreich and Lempel\r\n\r\ndtmc\r\n\r\n// we now let B to makes his/her choices based on what he/she knows \r\n// to do this I have added non-determinism to the previous version\r\n// and changed the modules so that only \"B's view\" is visible\r\n// then reveal the values when B thinks he has an advantage\r\n\r\n// to model the non-deterministic behaviour of corrupt party (party B)\r\n// we have a set of possible initial states corresponding to what messages\r\n// he/she tries to over hear when sending - we could do this with nondeterminism \r\n// but it will just make the model less structured and B has to make the choices \r\n// at the start anyway since B's view at this point should tell him nothing\r\n// (we use the new construct init...endinit to specify the set of initial states)\r\n\r\n// note that certain variables that belong to a party appear in the other party's module\r\n// as this leads to a more structured model - without this PRISM runs out of memory\r\n\r\n// note we have included the case when B stops if he/she thinks that the protocol has reached \r\n// a state where he/she has an advantage\r\n\r\n// currently, this model only works for N up to 20\r\n\r\nconst int N; // number of pairs of secrets the party sends\r\nconst int L; // number of bits in each secret\r\n\r\nconst double err;\r\n\r\nmodule counter\r\n\t\r\n\tb : [1..L]; // counter for current bit to be send (used in phases 2 and 3)\r\n\tn : [0..max(N-1,1)]; // counter as parties send N messages in a row\r\n\tphase : [1..5]; // phase of the protocol\r\n\tparty : [1..2]; // which party moves\r\n\t// 1 first phase of the protocol (sending messages of the form OT(.,.,.,.)\r\n\t// 2 and 3 - second phase of the protocol (sending secretes 1..n and n+1..2n respectively)\r\n\t// 4 finished the protocol\r\n\t\r\n\t// FIRST PHASE\r\n\t[receiveB] phase=1 & party=1 -> (party'=2); // first A sends a message then B does\r\n\t[receiveA] phase=1 & party=2 & n<N-1 -> (party'=1) & (n'=n+1); // after B sends a message we move onto the next message\r\n\t[receiveA] phase=1 & party=2 & n=N-1 -> (party'=1) & (phase'=2) & (n'=0); // B has sent his final message - move to next phase\r\n\t// SECOND AND THIRD PHASES\r\n\t// when A sends\r\n\t[receiveB] ((phase)>=(2)&(phase)<=(3))& party=1 & n=0-> (party'=2); // A transmits bth bit of secrets 1..N or N=1..2N\r\n\t[receiveA] ((phase)>=(2)&(phase)<=(3))& party=2 & n<N-1-> (n'=n+1); // A transmits bth bit of secrets 1..N or N=1..2N\r\n\t[receiveA] ((phase)>=(2)&(phase)<=(3))& party=2 & n=N-1 -> (party'=1) & (n'=1); // finished for party A now move to party B\r\n\t// when A sends\r\n\t[receiveB] ((phase)>=(2)&(phase)<=(3))& party=1 & n<N-1 & n>0 -> (n'=n+1); // B transmits bth bit of secrets 1..N or N=1..2N\r\n\t[receiveB] ((phase)>=(2)&(phase)<=(3))& party=1 & n=N-1 & b<L -> (party'=1) & (n'=0) & (b'=b+1); // finished for party B move to next bit\r\n\t[receiveB] phase=2 & party=1 & n=N-1 & b=L -> (phase'=3) & (party'=1) & (n'=0) & (b'=1); // finished for party B move to next phase\r\n\t[receiveB] phase=3 & party=1 & n=N-1 & b=L -> (phase'=4); // finished protocol (reveal values)\r\n\t\r\n\t// FINISHED\r\n\t[] phase=4 -> (phase'=4); // loop\r\n\t\r\nendmodule\r\n\r\n// party A\r\nmodule partyA\r\n\t\r\n\t// bi the number of bits of B's ith secret A knows \r\n\t// (keep pairs of secrets together to give a more structured model)\r\n\tb0  : [0..L]; b20 : [0..L];\r\n\tb1  : [0..L]; b21 : [0..L];\r\n\tb2  : [0..L]; b22 : [0..L];\r\n\tb3  : [0..L]; b23 : [0..L];\r\n\tb4  : [0..L]; b24 : [0..L];\r\n\tb5  : [0..L]; b25 : [0..L];\r\n\tb6  : [0..L]; b26 : [0..L];\r\n\tb7  : [0..L]; b27 : [0..L];\r\n\tb8  : [0..L]; b28 : [0..L];\r\n\tb9  : [0..L]; b29 : [0..L];\r\n\tb10 : [0..L]; b30 : [0..L];\r\n\tb11 : [0..L]; b31 : [0..L];\r\n\tb12 : [0..L]; b32 : [0..L];\r\n\tb13 : [0..L]; b33 : [0..L];\r\n\tb14 : [0..L]; b34 : [0..L];\r\n\tb15 : [0..L]; b35 : [0..L];\r\n\tb16 : [0..L]; b36 : [0..L];\r\n\tb17 : [0..L]; b37 : [0..L];\r\n\tb18 : [0..L]; b38 : [0..L];\r\n\tb19 : [0..L]; b39 : [0..L];\r\n\t\r\n\t\r\n\t// first step (get either secret i or (N-1)+i with equal probability)\r\n\t[receiveA] phase=1 & n=0  -> [0.5*(1-err),0.5*(1+err)] : (b0'=L)  + [0.5*(1-err),0.5*(1+err)] : (b20'=L);\r\n\t[receiveA] phase=1 & n=1  -> [0.5*(1-err),0.5*(1+err)] : (b1'=L)  + [0.5*(1-err),0.5*(1+err)] : (b21'=L);\r\n\t[receiveA] phase=1 & n=2  -> [0.5*(1-err),0.5*(1+err)] : (b2'=L)  + [0.5*(1-err),0.5*(1+err)] : (b22'=L);\r\n\t[receiveA] phase=1 & n=3  -> [0.5*(1-err),0.5*(1+err)] : (b3'=L)  + [0.5*(1-err),0.5*(1+err)] : (b23'=L);\r\n\t[receiveA] phase=1 & n=4  -> [0.5*(1-err),0.5*(1+err)] : (b4'=L)  + [0.5*(1-err),0.5*(1+err)] : (b24'=L);\r\n\t[receiveA] phase=1 & n=5  -> [0.5*(1-err),0.5*(1+err)] : (b5'=L)  + [0.5*(1-err),0.5*(1+err)] : (b25'=L);\r\n\t[receiveA] phase=1 & n=6  -> [0.5*(1-err),0.5*(1+err)] : (b6'=L)  + [0.5*(1-err),0.5*(1+err)] : (b26'=L);\r\n\t[receiveA] phase=1 & n=7  -> [0.5*(1-err),0.5*(1+err)] : (b7'=L)  + [0.5*(1-err),0.5*(1+err)] : (b27'=L);\r\n\t[receiveA] phase=1 & n=8  -> [0.5*(1-err),0.5*(1+err)] : (b8'=L)  + [0.5*(1-err),0.5*(1+err)] : (b28'=L);\r\n\t[receiveA] phase=1 & n=9  -> [0.5*(1-err),0.5*(1+err)] : (b9'=L)  + [0.5*(1-err),0.5*(1+err)] : (b29'=L);\r\n\t[receiveA] phase=1 & n=10 -> [0.5*(1-err),0.5*(1+err)] : (b10'=L) + [0.5*(1-err),0.5*(1+err)] : (b30'=L);\r\n\t[receiveA] phase=1 & n=11 -> [0.5*(1-err),0.5*(1+err)] : (b11'=L) + [0.5*(1-err),0.5*(1+err)] : (b31'=L);\r\n\t[receiveA] phase=1 & n=12 -> [0.5*(1-err),0.5*(1+err)] : (b12'=L) + [0.5*(1-err),0.5*(1+err)] : (b32'=L);\r\n\t[receiveA] phase=1 & n=13 -> [0.5*(1-err),0.5*(1+err)] : (b13'=L) + [0.5*(1-err),0.5*(1+err)] : (b33'=L);\r\n\t[receiveA] phase=1 & n=14 -> [0.5*(1-err),0.5*(1+err)] : (b14'=L) + [0.5*(1-err),0.5*(1+err)] : (b34'=L);\r\n\t[receiveA] phase=1 & n=15 -> [0.5*(1-err),0.5*(1+err)] : (b15'=L) + [0.5*(1-err),0.5*(1+err)] : (b35'=L);\r\n\t[receiveA] phase=1 & n=16 -> [0.5*(1-err),0.5*(1+err)] : (b16'=L) + [0.5*(1-err),0.5*(1+err)] : (b36'=L);\r\n\t[receiveA] phase=1 & n=17 -> [0.5*(1-err),0.5*(1+err)] : (b17'=L) + [0.5*(1-err),0.5*(1+err)] : (b37'=L);\r\n\t[receiveA] phase=1 & n=18 -> [0.5*(1-err),0.5*(1+err)] : (b18'=L) + [0.5*(1-err),0.5*(1+err)] : (b38'=L);\r\n\t[receiveA] phase=1 & n=19 -> [0.5*(1-err),0.5*(1+err)] : (b19'=L) + [0.5*(1-err),0.5*(1+err)] : (b39'=L);\r\n\t// second step (secrets 0,...,N-1)\r\n\t[receiveA] phase=2 & n=0  -> (b0'=min(b0+1,L));\r\n\t[receiveA] phase=2 & n=1  -> (b1'=min(b1+1,L));\r\n\t[receiveA] phase=2 & n=2  -> (b2'=min(b2+1,L));\r\n\t[receiveA] phase=2 & n=3  -> (b3'=min(b3+1,L));\r\n\t[receiveA] phase=2 & n=4  -> (b4'=min(b4+1,L));\r\n\t[receiveA] phase=2 & n=5  -> (b5'=min(b5+1,L));\r\n\t[receiveA] phase=2 & n=6  -> (b6'=min(b6+1,L));\r\n\t[receiveA] phase=2 & n=7  -> (b7'=min(b7+1,L));\r\n\t[receiveA] phase=2 & n=8  -> (b8'=min(b8+1,L));\r\n\t[receiveA] phase=2 & n=9  -> (b9'=min(b9+1,L));\r\n\t[receiveA] phase=2 & n=10 -> (b10'=min(b10+1,L));\r\n\t[receiveA] phase=2 & n=11 -> (b11'=min(b11+1,L));\r\n\t[receiveA] phase=2 & n=12 -> (b12'=min(b12+1,L));\r\n\t[receiveA] phase=2 & n=13 -> (b13'=min(b13+1,L));\r\n\t[receiveA] phase=2 & n=14 -> (b14'=min(b14+1,L));\r\n\t[receiveA] phase=2 & n=15 -> (b15'=min(b15+1,L));\r\n\t[receiveA] phase=2 & n=16 -> (b16'=min(b16+1,L));\r\n\t[receiveA] phase=2 & n=17 -> (b17'=min(b17+1,L));\r\n\t[receiveA] phase=2 & n=18 -> (b18'=min(b18+1,L));\r\n\t[receiveA] phase=2 & n=19 -> (b19'=min(b19+1,L));\r\n\t// second step (secrets N,...,2N-1)\r\n\t[receiveA] phase=3 & n=0  -> (b20'=min(b20+1,L));\r\n\t[receiveA] phase=3 & n=1  -> (b21'=min(b21+1,L));\r\n\t[receiveA] phase=3 & n=2  -> (b22'=min(b22+1,L));\r\n\t[receiveA] phase=3 & n=3  -> (b23'=min(b23+1,L));\r\n\t[receiveA] phase=3 & n=4  -> (b24'=min(b24+1,L));\r\n\t[receiveA] phase=3 & n=5  -> (b25'=min(b25+1,L));\r\n\t[receiveA] phase=3 & n=6  -> (b26'=min(b26+1,L));\r\n\t[receiveA] phase=3 & n=7  -> (b27'=min(b27+1,L));\r\n\t[receiveA] phase=3 & n=8  -> (b28'=min(b28+1,L));\r\n\t[receiveA] phase=3 & n=9  -> (b29'=min(b29+1,L));\r\n\t[receiveA] phase=3 & n=10 -> (b30'=min(b30+1,L));\r\n\t[receiveA] phase=3 & n=11 -> (b31'=min(b31+1,L));\r\n\t[receiveA] phase=3 & n=12 -> (b32'=min(b32+1,L));\r\n\t[receiveA] phase=3 & n=13 -> (b33'=min(b33+1,L));\r\n\t[receiveA] phase=3 & n=14 -> (b34'=min(b34+1,L));\r\n\t[receiveA] phase=3 & n=15 -> (b35'=min(b35+1,L));\r\n\t[receiveA] phase=3 & n=16 -> (b36'=min(b36+1,L));\r\n\t[receiveA] phase=3 & n=17 -> (b37'=min(b37+1,L));\r\n\t[receiveA] phase=3 & n=18 -> (b38'=min(b38+1,L));\r\n\t[receiveA] phase=3 & n=19 -> (b39'=min(b39+1,L));\r\n\r\nendmodule\r\n\r\n// construct module for party B through renaming\r\nmodule partyB=partyA[b0 =a0 ,b1 =a1 ,b2 =a2 ,b3 =a3 ,b4 =a4 ,b5 =a5 ,b6 =a6 ,b7 =a7 ,b8 =a8 ,b9 =a9,\r\n                     b10=a10,b11=a11,b12=a12,b13=a13,b14=a14,b15=a15,b16=a16,b17=a17,b18=a18,b19=a19,\r\n                     b20=a20,b21=a21,b22=a22,b23=a23,b24=a24,b25=a25,b26=a26,b27=a27,b28=a28,b29=a29,\r\n                     b30=a30,b31=a31,b32=a32,b33=a33,b34=a34,b35=a35,b36=a36,b37=a37,b38=a38,b39=a39,\r\n                     receiveA=receiveB] \r\nendmodule\r\n\r\n// formulae\r\nformula kB = ( (a0=L  & a20=L)\r\n\t\t\t | (a1=L  & a21=L)\r\n\t\t\t | (a2=L  & a22=L)\r\n\t\t\t | (a3=L  & a23=L)\r\n\t\t\t | (a4=L  & a24=L)\r\n\t\t\t | (a5=L  & a25=L)\r\n\t\t\t | (a6=L  & a26=L)\r\n\t\t\t | (a7=L  & a27=L)\r\n\t\t\t | (a8=L  & a28=L)\r\n\t\t\t | (a9=L  & a29=L)\r\n\t\t\t | (a10=L & a30=L)\r\n\t\t\t | (a11=L & a31=L)\r\n\t\t\t | (a12=L & a32=L)\r\n\t\t\t | (a13=L & a33=L)\r\n\t\t\t | (a14=L & a34=L)\r\n\t\t\t | (a15=L & a35=L)\r\n\t\t\t | (a16=L & a36=L)\r\n\t\t\t | (a17=L & a37=L)\r\n\t\t\t | (a18=L & a38=L)\r\n\t\t\t | (a19=L & a39=L));\r\n\r\nformula kA = ( (b0=L  & b20=L)\r\n\t\t\t | (b1=L  & b21=L)\r\n\t\t\t | (b2=L  & b22=L)\r\n\t\t\t | (b3=L  & b23=L)\r\n\t\t\t | (b4=L  & b24=L)\r\n\t\t\t | (b5=L  & b25=L)\r\n\t\t\t | (b6=L  & b26=L)\r\n\t\t\t | (b7=L  & b27=L)\r\n\t\t\t | (b8=L  & b28=L)\r\n\t\t\t | (b9=L  & b29=L)\r\n\t\t\t | (b10=L & b30=L)\r\n\t\t\t | (b11=L & b31=L)\r\n\t\t\t | (b12=L & b32=L)\r\n\t\t\t | (b13=L & b33=L)\r\n\t\t\t | (b14=L & b34=L)\r\n\t\t\t | (b15=L & b35=L)\r\n\t\t\t | (b16=L & b36=L)\r\n\t\t\t | (b17=L & b37=L)\r\n\t\t\t | (b18=L & b38=L)\r\n\t\t\t | (b19=L & b39=L));\r\n\r\n// labels\r\nlabel \"knowB\" = kB;\r\nlabel \"knowA\" = kA;\r\n\r\n// reward structures\r\n\r\n// messages from B that A needs to knows a pair once B knows a pair\r\nrewards \"messages_A_needs\"\r\n\t[receiveA] kB & !kA : 1;\r\nendrewards\r\n\r\n// messages from A that B needs to knows a pair once A knows a pair\r\nrewards \"messages_B_needs\"\r\n\t[receiveA] kA & !kB : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/egl_int.prism.props",
    "content": "// Expected number of messages from B that A needs to knows a pair once B knows a pair\r\n// RESULT (N=4,L=4,err=0.1): ?\r\n\"messagesA_min\": R{\"messages_A_needs\"}min=? [ F phase=4 ];\r\n\r\n// Expected number of messages from B that A needs to knows a pair once B knows a pair\r\n// RESULT (N=4,L=4,err=0.1): ?\r\n\"messagesA_max\": R{\"messages_A_needs\"}max=? [ F phase=4 ];\r\n\r\n// Expected number of messages from A that B needs to knows a pair once A knows a pair\r\n// RESULT (N=4,L=4,err=0.1): ?\r\n\"messagesB_min\": R{\"messages_B_needs\"}min=? [ F phase=4 ];\r\n\r\n// Expected number of messages from A that B needs to knows a pair once A knows a pair\r\n// RESULT (N=4,L=4,err=0.1): ?\r\n\"messagesB_max\": R{\"messages_B_needs\"}max=? [ F phase=4 ];\r\n\r\n// Probability that party A is unfairly disadvantaged\r\n// RESULT (N=4,L=4,err=0.1): 0.4725534375\r\n\"unfairA_min\": Pmin=? [ F !\"knowA\" & \"knowB\" ];\r\n\r\n// Probability that party A is unfairly disadvantaged\r\n// RESULT (N=4,L=4,err=0.1): 0.5911778125\r\n\"unfairA_max\": Pmax=? [ F !\"knowA\" & \"knowB\" ];\r\n\r\n// Probability that party B is unfairly disadvantaged\r\n// RESULT (N=4,L=4,err=0.1): 0.4088221875\r\n\"unfairB_min\": Pmin=? [ F !\"knowB\" & \"knowA\" ];\r\n\r\n// Probability that party B is unfairly disadvantaged\r\n// RESULT (N=4,L=4,err=0.1): 0.5274465625\r\n\"unfairB_max\": Pmax=? [ F !\"knowB\" & \"knowA\" ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/egl_int.prism.props.args",
    "content": "# -ex -const N=4 -const L=4 -const err=0.1 -convprog Gurobi\r\n# -ex -const N=4 -const L=4 -const err=0.1 -convprog lpsolve\r\n-ex -const N=4 -const L=4 -const err=0.1 -epsilon 1e-8\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/leader3_2_int.prism",
    "content": "// synchronous leader election protocol  (itai & Rodeh)\r\n// dxp/gxn 25/01/01\r\n\r\ndtmc\r\n\r\n// CONSTANTS\r\nconst N = 3; // number of processes\r\nconst K = 2; // range of probabilistic choice\r\nconst double unc;\r\n\r\n// counter module used to count the number of processes that have been read\r\n// and to know when a process has decided\r\nmodule counter\r\n\t\r\n\t// counter (c=i  means process j reading process (i-1)+j next)\r\n\tc : [1..N-1];\r\n\t\r\n\t// reading\r\n\t[read] c<N-1 -> (c'=c+1);\r\n\t// finished reading\r\n\t[read] c=N-1 -> (c'=c);\r\n\t//decide\r\n\t[done] u1|u2|u3 -> (c'=c);\r\n\t// pick again reset counter \r\n\t[retry] !(u1|u2|u3) -> (c'=1);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (c'=c);\r\n\t\r\nendmodule\r\n\r\n//  processes form a ring and suppose:\r\n// process 1 reads process 2\r\n// process 2 reads process 3\r\n// process 3 reads process 1\r\nmodule process1\r\n\t\r\n\t// local state\r\n\ts1 : [0..3];\r\n\t// s1=0 make random choice\r\n\t// s1=1 reading\r\n\t// s1=2 deciding\r\n\t// s1=3 finished\r\n\t\r\n\t// has a unique id so far (initially true)\r\n\tu1 : bool;\r\n\t\r\n\t// value to be sent to next process in the ring (initially sets this to its own value)\r\n\tv1 : [0..K-1];\r\n\t\r\n\t// random choice\r\n\tp1 : [0..K-1];\r\n\t\r\n\t// pick value\r\n\t[pick] s1=0 -> [1/K-unc,1/K+unc] : (s1'=1) & (p1'=0) & (v1'=0) & (u1'=true)\r\n\t             + [1/K-unc,1/K+unc] : (s1'=1) & (p1'=1) & (v1'=1) & (u1'=true);\r\n\t// read\r\n\t[read] s1=1 &  u1 & c<N-1 -> (u1'=(p1!=v2)) & (v1'=v2);\r\n\t[read] s1=1 & !u1 & c<N-1 -> (u1'=false) & (v1'=v2) & (p1'=0);\r\n\t// read and move to decide\r\n\t[read] s1=1 &  u1 & c=N-1 -> (s1'=2) & (u1'=(p1!=v2)) & (v1'=0) & (p1'=0);\r\n\t[read] s1=1 & !u1 & c=N-1 -> (s1'=2) & (u1'=false) & (v1'=0);\r\n\t// deciding\r\n\t// done\r\n\t[done] s1=2 -> (s1'=3) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t//retry\r\n\t[retry] s1=2 -> (s1'=0) & (u1'=false) & (v1'=0) & (p1'=0);\r\n\t// loop (when finished to avoid deadlocks)\r\n\t[loop] s1=3 -> (s1'=3);\r\n\t\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\nmodule process2 = process1 [ s1=s2,p1=p2,v1=v2,u1=u2,v2=v3 ] endmodule\r\nmodule process3 = process1 [ s1=s3,p1=p3,v1=v3,u1=u3,v2=v1 ] endmodule\r\n\r\n// expected number of rounds\r\nrewards \"num_rounds\"\r\n\t[pick] true : 1;\r\nendrewards\r\n\r\n// expected number of rounds ())state rewards)\r\nrewards \"num_rounds_s\"\r\n\ts1=0 : 1;\r\nendrewards\r\n\r\n// labels\r\nlabel \"elected\" = s1=3&s2=3&s3=3;\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/leader3_2_int.prism.props",
    "content": "const int L=2;\r\n\r\n// Probability that a leader is eventually elected\r\n//RESULT (unc=0.1): 1.0\r\nPmin=? [ F \"elected\" ]\r\n//RESULT (unc=0.1): 1.0\r\nPmax=? [ F \"elected\" ]\r\n\r\n// Probability that a leader is elected within L rounds\r\n//RESULT (unc=0.1): 0.813376\r\nPmin=? [ F<=(L*(N+1)) \"elected\" ]\r\n//RESULT (unc=0.1): 0.983616\r\nPmax=? [ F<=(L*(N+1)) \"elected\" ]\r\n\r\n// Expected time (num. rounds) to elect a leader\r\n//RESULT (unc=0.1): 1.146788990825688\r\nR{\"num_rounds\"}min=? [ F \"elected\" ]\r\n//RESULT (unc=0.1): 1.76056338028169\r\nR{\"num_rounds\"}max=? [ F \"elected\" ]\r\n\r\n// Expected time (num. rounds) to elect a leader\r\n//RESULT (unc=0.1): 1.146788990825688\r\nR{\"num_rounds_s\"}min=? [ F \"elected\" ]\r\n//RESULT (unc=0.1): 1.76056338028169\r\nR{\"num_rounds_s\"}max=? [ F \"elected\" ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/leader3_2_int.prism.props.args",
    "content": "-const unc=0.1 -ex -epsilon 1e-8\r\n# -const unc=0.1 -ex -convprog Gurobi\r\n# -const unc=0.1 -ex -convprog lpsolve\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/nand_int.prism",
    "content": "// nand multiplex system\r\n// gxn/dxp 20/03/03\r\n\r\n// U (correctly) performs a random permutation of the outputs of the previous stage\r\n\r\ndtmc\r\n\r\nconst int N; // number of inputs in each bundle\r\nconst int K; // number of restorative stages\r\n\r\nconst int M = 2*K+1; // total number of multiplexing units\r\n\r\n// parameters taken from the following paper\r\n// A system architecture solution for unreliable nanoelectric devices\r\n// J. Han & P. Jonker\r\n// IEEEE trans. on nanotechnology vol 1(4) 2002\r\n\r\nconst double perr = 0.02; // probability nand works correctly\r\nconst double prob1 = 0.9; // probability initial inputs are stimulated\r\n\r\nconst double err;\r\nconst double err2;\r\n\r\n// model whole system as a single module by resuing variables \r\n// to decrease the state space\r\nmodule multiplex\r\n\r\n\tu : [1..M]; // number of stages\r\n\tc : [0..N]; // counter (number of copies of the nand done)\r\n\r\n\ts : [0..4]; // local state\r\n\t// 0 - initial state\r\n\t// 1 - set x inputs\r\n\t// 2 - set y inputs\r\n\t// 3 - set outputs\r\n\t// 4 - done\r\n\r\n\tz : [0..N]; // number of new outputs equal to 1\r\n\tzx : [0..N]; // number of old outputs equal to 1\r\n\tzy : [0..N]; // need second copy for y\r\n\t// initially 9 since initially probability of stimulated state is 0.9\r\n\r\n\tx : [0..1]; // value of first input\r\n\ty : [0..1]; // value of second input\r\n\t\r\n\t[] s=0 & (c<N) -> (s'=1); // do next nand if have not done N yet\r\n\t[] s=0 & (c=N) & (u<M) -> (s'=1) & (zx'=z) & (zy'=z) & (z'=0) & (u'=u+1) & (c'=0); // move on to next u if not finished\r\n\t[] s=0 & (c=N) & (u=M) -> (s'=4) & (zx'=0) & (zy'=0) & (x'=0) & (y'=0); // finished (so reset variables not needed to reduce state space)\r\n\r\n\t// choose x permute selection (have zx stimulated inputs)\r\n\t// note only need y to be random\t\r\n\t[] s=1 & u=1  -> [prob1*(1-err),prob1*(1+err)] : (x'=1) & (s'=2) + [(1-prob1)*(1-err),(1-prob1)*(1+err)] : (x'=0) & (s'=2); // initially random\r\n\t[] s=1 & u>1 & zx>0 -> (x'=1) & (s'=2) & (zx'=zx-1);\r\n\t[] s=1 & u>1 & zx=0 -> (x'=0) & (s'=2);\r\n\r\n\t// choose x randomly from selection (have zy stimulated inputs)\r\n\t[] s=2 & u=1 -> [prob1*(1-err),prob1*(1+err)] : (y'=1) & (s'=3) + [(1-prob1)*(1-err),(1-prob1)*(1+err)] : (y'=0) & (s'=3); // initially random\r\n\t[] s=2 & u>1 & zy<(N-c) & zy>0  -> [zy/(N-c)*(1-err),zy/(N-c)*(1+err)] : (y'=1) & (s'=3) & (zy'=zy-1) + [(1-(zy/(N-c)))*(1-err), (1-(zy/(N-c)))*(1+err)] : (y'=0) & (s'=3);\r\n\t[] s=2 & u>1 & zy=(N-c) & c<N -> 1 : (y'=1) & (s'=3) & (zy'=zy-1);\r\n\t[] s=2 & u>1 & zy=0 -> 1 : (y'=0) & (s'=3);\r\n\r\n\t// use nand gate\r\n\t[] s=3 & z<N & c<N -> [(1-perr)*(1-err2),(1-perr)*(1+err2)] : (z'=z+(1-x*y)) & (s'=0) & (c'=c+1) & (x'=0) & (y'=0) // not faulty\r\n\t         + [perr*(1-err2),perr*(1+err2)]    : (z'=z+(x*y))    & (s'=0) & (c'=c+1) & (x'=0) & (y'=0); // von neumann fault\r\n\t// [] s=3 & z<N -> [(1-perr)*(1-err2),(1-perr)*(1+err2)] : (z'=z+(1-x*y)) & (s'=0) & (c'=c+1) & (x'=0) & (y'=0) // not faulty\r\n\t//         + [perr*(1-err),perr*(1+err)]    : (z'=z+(x*y))    & (s'=0) & (c'=c+1) & (x'=0) & (y'=0); // von neumann fault\r\n\t\r\n\t[] s=4 -> true;\r\n\t\r\nendmodule\r\n\r\n// rewards: final value of gate\r\nrewards\r\n\t[] s=0 & (c=N) & (u=M) : z/N;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/nand_int.prism.props",
    "content": "// RESULT (N=2,K=1,err=0.02,err2=0.01): 0.733716191851539\r\n// RESULT (N=2,K=2,err=0.02,err2=0.01): 0.7356983736830808\r\n// RESULT (N=2,K=3,err=0.02,err2=0.01): 0.7177268839235367\r\n// RESULT (N=2,K=4,err=0.02,err2=0.01): 0.6969624030642517\r\n// RESULT (N=4,K=1,err=0.02,err2=0.01): 0.6252157540304918\r\n// RESULT (N=4,K=2,err=0.02,err2=0.01): 0.6341031018119253\r\n// RESULT (N=4,K=3,err=0.02,err2=0.01): 0.6298671562329033\r\n// RESULT (N=4,K=4,err=0.02,err2=0.01): 0.6202551185076227\r\n// RESULT (N=8,K=1,err=0.02,err2=0.01): 0.45773012680908504\r\n// RESULT (N=8,K=2,err=0.02,err2=0.01): 0.5136903158526614\r\n// RESULT (N=8,K=3,err=0.02,err2=0.01): 0.5340425222768378\r\n// RESULT (N=8,K=4,err=0.02,err2=0.01): 0.5411569072311269\r\n\"reliable_min\": Pmin=? [ F s=4 & z/N<0.1 ];\r\n\r\n// RESULT (N=2,K=1,err=0.02,err2=0.01): 0.7474829169400934\r\n// RESULT (N=2,K=2,err=0.02,err2=0.01): 0.7510358939252891\r\n// RESULT (N=2,K=3,err=0.02,err2=0.01): 0.7344341446696451\r\n// RESULT (N=2,K=4,err=0.02,err2=0.01): 0.7149154614919985\r\n// RESULT (N=4,K=1,err=0.02,err2=0.01): 0.6416662156184123\r\n// RESULT (N=4,K=2,err=0.02,err2=0.01): 0.653000428865136\r\n// RESULT (N=4,K=3,err=0.02,err2=0.01): 0.6507688417486568\r\n// RESULT (N=4,K=4,err=0.02,err2=0.01): 0.643032875486255\r\n// RESULT (N=8,K=1,err=0.02,err2=0.01): 0.4785787866638514\r\n// RESULT (N=8,K=2,err=0.02,err2=0.01): 0.535486966117679\r\n// RESULT (N=8,K=3,err=0.02,err2=0.01): 0.5563831152983048\r\n// RESULT (N=8,K=4,err=0.02,err2=0.01): 0.56416137152539\r\n\"reliable_max\": Pmax=? [ F s=4 & z/N<0.1 ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/nand_int.prism.props.args",
    "content": "-ex -const N=2 -const K=1 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=2 -const K=2 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=2 -const K=3 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=2 -const K=4 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=4 -const K=1 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=4 -const K=2 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=4 -const K=3 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=4 -const K=4 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=8 -const K=1 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=8 -const K=2 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=8 -const K=3 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n-ex -const N=8 -const K=4 -const err=0.02 -const err2=0.01 -epsilon 1e-8\r\n# -ex -const N=2 -const K=1 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=2 -const K=2 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=2 -const K=3 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=2 -const K=4 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=4 -const K=1 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=4 -const K=2 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=4 -const K=3 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=4 -const K=4 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=8 -const K=1 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=8 -const K=2 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=8 -const K=3 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n# -ex -const N=8 -const K=4 -const err=0.02 -const err2=0.01 -convprog Gurobi\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/robot-ltl.prism",
    "content": "dtmc\r\n\r\nconst double e;\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n//[east] s=0 -> [0.6-e,0.6+e]:(s'=1) + [0.4-e,0.4+e]:(s'=0);\r\n[south] s=0 -> [0.8-e,0.8+e]:(s'=3) + [0.1-e,0.1+e]:(s'=1) + [0.1-e,0.1+e]:(s'=4);\r\n//[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n//[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n//[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/robot-ltl.prism.args",
    "content": "-const e=0\n-const e=0.05\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/robot-ltl.prism.props",
    "content": "// RESULT (e=0): 0.15\n// RESULT (e=0.05): 0.1\nPmin=? [ G F \"goal1\" ]\n\n// RESULT (e=0): 0.15\n// RESULT (e=0.05): 0.2\nPmax=? [ G F \"goal1\" ]\n\n// RESULT (e=0): 0.1\n// RESULT (e=0.05): 0.05\nPmin=? [ (G !\"hazard\")&(G F \"goal1\") ]\n\n// RESULT (e=0): 0.1\n// RESULT (e=0.05): 0.15\nPmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n\n// RESULT (e=0): 0.9\n// RESULT (e=0.05): 0.85\nPmin=? [ !((G !\"hazard\")&(G F \"goal1\")) ]\n\n// RESULT (e=0): 0.9\n// RESULT (e=0.05): 0.95\nPmax=? [ !((G !\"hazard\")&(G F \"goal1\")) ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/test.prism",
    "content": "dtmc\r\n\r\nmodule M\r\n\t\r\n\ts : [0..3];\r\n\t\r\n\t[] s=0 -> [0.1,0.2]:(s'=1) + [0.8,0.9]:(s'=2);\r\n\t[] s>0 -> true;\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/idtmcs/test.prism.props",
    "content": "// RESULT: 0.1\r\nPmin=? [ F s=1 ]\r\n// RESULT: 0.2\r\nPmax=? [ F s=1 ]\r\n// RESULT: 0.8\r\nPmin=? [ F s=2 ]\r\n// RESULT: 0.9\r\nPmax=? [ F s=2 ]\r\n\r\n// RESULT: 0.8\r\nPmin=? [ (G! s=1) ]\r\n// RESULT: 0.9\r\nPmax=? [ (G! s=1) ]\r\n// RESULT: 0.1\r\nPmin=? [ (G! s=2) ]\r\n// RESULT: 0.2\r\nPmax=? [ (G! s=2) ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/coin2_int.prism",
    "content": "// COIN FLIPPING PROTOCOL FOR POLYNOMIAL RANDOMIZED CONSENSUS [AH90] \r\n// gxn/dxp 20/11/00\r\n\r\nmdp\r\n\r\n// constants\r\nconst int N=2;\r\nconst int K;\r\nconst int range = 2*(K+1)*N;\r\nconst int counter_init = (K+1)*N;\r\nconst int left = N;\r\nconst int right = 2*(K+1)*N - N;\r\nconst double bias = 0.1;\r\nconst double low = 0.5-bias;\r\nconst double high = 0.5+bias;\r\n//const int METHOD;\r\n\r\n// shared coin\r\nglobal counter : [0..range] init counter_init;\r\n\r\nmodule process1\r\n\t\r\n\t// program counter\r\n\tpc1 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin1 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc1=0)  -> [low,high] : (coin1'=0) & (pc1'=1) + [low,high] : (coin1'=1) & (pc1'=1);\r\n\t//[] (pc1=0)  -> 0.5 : (coin1'=0) & (pc1'=1) + 0.5 : (coin1'=1) & (pc1'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=0) & (counter>0) -> (counter'=counter-1) & (pc1'=2) & (coin1'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc1=1) & (coin1=1) & (counter<range) -> (counter'=counter+1) & (pc1'=2) & (coin1'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc1=2) & (counter<=left) -> (pc1'=3) & (coin1'=0);\r\n\t// decide heads\r\n\t[] (pc1=2) & (counter>=right) -> (pc1'=3) & (coin1'=1);\r\n\t// flip again\r\n\t[] (pc1=2) & (counter>left) & (counter<right) -> (pc1'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc1=3) -> (pc1'=3);\r\n\r\nendmodule\r\n\r\nmodule process2\r\n\t\r\n\t// program counter\r\n\tpc2 : [0..3];\r\n\t// 0 - flip\r\n\t// 1 - write \r\n\t// 2 - check\r\n\t// 3 - finished\r\n\t\r\n\t// local coin\r\n\tcoin2 : [0..1];\t\r\n\r\n\t// flip coin\r\n\t[] (pc2=0)  -> 0.5 : (coin2'=0) & (pc2'=1) + 0.5 : (coin2'=1) & (pc2'=1);\r\n\t// write tails -1  (reset coin to add regularity)\r\n\t[] (pc2=1) & (coin2=0) & (counter>0) -> (counter'=counter-1) & (pc2'=2) & (coin2'=0);\r\n\t// write heads +1 (reset coin to add regularity)\r\n\t[] (pc2=1) & (coin2=1) & (counter<range) -> (counter'=counter+1) & (pc2'=2) & (coin2'=0);\r\n\t// check\r\n\t// decide tails\r\n\t[] (pc2=2) & (counter<=left) -> (pc2'=3) & (coin2'=0);\r\n\t// decide heads\r\n\t[] (pc2=2) & (counter>=right) -> (pc2'=3) & (coin2'=1);\r\n\t// flip again\r\n\t[] (pc2=2) & (counter>left) & (counter<right) -> (pc2'=0);\r\n\t// loop (all loop together when done)\r\n\t[done] (pc2=3) -> (pc2'=3);\r\n\r\nendmodule\r\n\r\n// construct remaining processes through renaming\r\n//module process2 = process1[pc1=pc2,coin1=coin2] endmodule\r\n\r\n// labels\r\nlabel \"finished\" = pc1=3 & pc2=3 ;\r\nlabel \"all_coins_equal_0\" = coin1=0 & coin2=0 ;\r\nlabel \"all_coins_equal_1\" = coin1=1 & coin2=1 ;\r\nlabel \"agree\" = coin1=coin2 ;\r\n\r\n// rewards\r\nrewards \"steps\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/coin2_int.prism.props",
    "content": "const int k=100;\r\n\r\n// C1 (with probability 1, all N processes finish the protocol)\r\n//RESULT (K=2): true\r\nP>=1 [ F \"finished\" ]\r\n\r\n// C2 (minimum probability that the protocol finishes with all coins equal to v) (v=1,2)\r\n// Results are same for v=1 and v=2 by symmetry\r\n// Analytic bound is (K-1)/(2*K)\r\n//RESULT (K=2): 0.114195\r\nPminmin=? [ F \"finished\"&\"all_coins_equal_0\" ]\r\n//RESULT (K=2): 0.418800\r\nPminmax=? [ F \"finished\"&\"all_coins_equal_1\" ]\r\n//RESULT (K=2): false\r\nP>=0.12 [ F \"finished\" & \"all_coins_equal_0\" ]\r\n//RESULT (K=2): true\r\nP>=0.1 [ F \"finished\" & \"all_coins_equal_0\" ]\r\n\r\n// Max probability of finishing protocol with coins not all equal\r\n// RESULT (K=2): 0.101786\r\nPmaxmin=? [ F \"finished\"&!\"agree\" ]\r\n// RESULT (K=2): 0.324995\r\nPmaxmax=? [ F \"finished\"&!\"agree\" ]\r\n\r\n// Min/max probability of finishing within k steps\r\n//RESULT (K=2): 0.44490355232820333\r\nPminmin=? [ F<=k \"finished\" ]\r\n//RESULT (K=2): 0.7649865690618753\r\nPminmax=? [ F<=k \"finished\" ]\r\n//RESULT (K=2): 0.9041842818260193\r\nPmaxmin=? [ F<=k \"finished\" ]\r\n//RESULT (K=2): 0.9852687856874977\r\nPmaxmax=? [ F<=k \"finished\" ]\r\n\r\n// Min/max expected steps to finish\r\n//RESULT (K=2): 31.1111111111111\r\nR{\"steps\"}minmin=? [ F \"finished\" ]\r\n//RESULT (K=2): 48.0\r\nR{\"steps\"}minmax=? [ F \"finished\" ]\r\n\r\n//RESULT (K=2): 75.0\r\nR{\"steps\"}maxmin=? [ F \"finished\" ]\r\n//RESULT (K=2): 162.375\r\nR{\"steps\"}maxmax=? [ F \"finished\" ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/coin2_int.prism.props.args",
    "content": "-const K=2 -epsilon 1e-8\r\n# -const K=2 -convprog Gurobi\r\n# -const K=2 -convprog lpsolve\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/csma2_2_int.prism",
    "content": "// CSMA/CD protocol - probabilistic version of kronos model (3 stations)\r\n// gxn/dxp 04/12/01\r\n\r\nmdp\r\n\r\n// note made changes since cannot have strict inequalities\r\n// in digital clocks approach and suppose a station only sends one message\r\n\r\n// actual parameters\r\nconst int N = 2; // number of processes\r\nconst int K = 2; // exponential backoff limit\r\nconst int slot = 2*sigma; // length of slot\r\nconst int M = floor(pow(2, K))-1 ; // max number of slots to wait\r\n//const int lambda=782;\r\n//const int sigma=26;\r\n\r\n// simplified parameters scaled\r\nconst int sigma=1; // time for messages to propagate along the bus\r\nconst int lambda=30; // time to send a message\r\nconst double err;\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// the bus\r\nmodule bus\r\n\t\r\n\tb : [0..2];\r\n\t// b=0 - idle\r\n\t// b=1 - active\r\n\t// b=2 - collision\r\n\t\r\n\t// clocks of bus\r\n\ty1 : [0..sigma+1]; // time since first send (used find time until channel sensed busy)\r\n\ty2 : [0..sigma+1]; // time since second send (used to find time until collision detected)\r\n\t\r\n\t// a sender sends (ok - no other message being sent)\r\n\t[send1] (b=0) -> (b'=1);\r\n\t[send2] (b=0) -> (b'=1);\r\n\t\r\n\t// a sender sends (bus busy - collision)\r\n\t[send1] (b=1|b=2) & (y1<sigma) -> (b'=2);\r\n\t[send2] (b=1|b=2) & (y1<sigma) -> (b'=2);\r\n\t\r\n\t// finish sending\r\n\t[end1] (b=1) -> (b'=0) & (y1'=0);\r\n\t[end2] (b=1) -> (b'=0) & (y1'=0);\r\n\t\r\n\t// bus busy\r\n\t[busy1] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \r\n\t[busy2] (b=1|b=2) & (y1>=sigma) -> (b'=b);  \r\n\t\r\n\t// collision detected\r\n\t[cd] (b=2) & (y2<=sigma) -> (b'=0) & (y1'=0) & (y2'=0);\r\n\t\r\n\t// time passage\r\n\t[time] (b=0) -> (y1'=0); // value of y1/y2 does not matter in state 0\r\n\t[time] (b=1) -> (y1'=min(y1+1,sigma+1)); // no invariant in state 1\r\n\t[time] (b=2) & (y2<sigma) -> (y1'=min(y1+1,sigma+1)) & (y2'=min(y2+1,sigma+1)); // invariant in state 2 (time until collision detected)\r\n\t\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// model of first sender\r\nmodule station1\r\n\t\r\n\t// LOCAL STATE\r\n\ts1 : [0..5];\r\n\t// s1=0 - initial state\r\n\t// s1=1 - transmit\r\n\t// s1=2 - collision (set backoff)\r\n\t// s1=3 - wait (bus busy)\r\n\t// s1=4 - successfully sent\r\n\t\r\n\t// LOCAL CLOCK\r\n\tx1 : [0..max(lambda,slot)];\r\n\t\r\n\t// BACKOFF COUNTER (number of slots to wait)\r\n\tbc1 : [0..M];\r\n\t\r\n\t// COLLISION COUNTER\r\n\tcd1 : [0..K];\r\n\t\r\n\t// start sending\r\n\t[send1] (s1=0) -> (s1'=1) & (x1'=0); // start sending\r\n\t[busy1] (s1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\r\n\t\r\n\t// transmitting\r\n\t[time] (s1=1) & (x1<lambda) -> (x1'=min(x1+1,lambda)); // let time pass\r\n\t[end1]  (s1=1) & (x1=lambda) -> (s1'=4) & (x1'=0); // finished\r\n\t[cd]   (s1=1) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected (increment backoff counter)\r\n\t[cd] !(s1=1) -> (s1'=s1); // add loop for collision detection when not important\r\n\t\r\n\t// set backoff (no time can pass in this state)\r\n\t// probability depends on which transmission this is (cd1)\r\n\t[] s1=2 & cd1=1 ->  [1/2*(1-err),1/2*(1+err)] : (s1'=3) & (bc1'=0) + [1/2*(1-err),1/2*(1+err)] : (s1'=3) & (bc1'=1) ;\r\n\t[] s1=2 & cd1=2 ->  [1/4*(1-err),1/4*(1+err)] : (s1'=3) & (bc1'=0) + [1/4*(1-err),1/4*(1+err)] : (s1'=3) & (bc1'=1) + [1/4*(1-err),1/4*(1+err)] : (s1'=3) & (bc1'=2) + [1/4*(1-err),1/4*(1+err)] : (s1'=3) & (bc1'=3) ;\r\n\t\r\n\t// wait until backoff counter reaches 0 then send again\r\n\t[time] (s1=3) & (x1<slot) -> (x1'=x1+1); // let time pass (in slot)\r\n\t[time] (s1=3) & (x1=slot) & (bc1>0) -> (x1'=1) & (bc1'=bc1-1); // let time pass (move slots)\r\n\t[send1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\r\n\t[busy1] (s1=3) & (x1=slot) & (bc1=0) -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\r\n\t\r\n\t// once finished nothing matters\r\n\t[time] (s1>=4) -> (x1'=0);\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// construct further stations through renaming\r\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,bc1=bc2,send1=send2,busy1=busy2,end1=end2] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// reward structure for expected time\r\nrewards \"time\"\r\n\t[time] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n\r\n// labels/formulae\r\nlabel \"all_delivered\" = s1=4&s2=4;\r\nlabel \"one_delivered\" = s1=4|s2=4;\r\nlabel \"collision_max_backoff\" = (cd1=K & s1=1 & b=2)|(cd2=K & s2=1 & b=2);\r\nformula min_backoff_after_success = min(s1=4?cd1:K+1,s2=4?cd2:K+1);\r\nformula min_collisions = min(cd1,cd2);\r\nformula max_collisions = max(cd1,cd2);\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/csma2_2_int.prism.props",
    "content": "// Maximum probability all stations send successfully before a collision with max backoff \r\n//RESULT (err=0.2): 0.82\r\n\"all_before_max1\": Pmaxmin=? [ !\"collision_max_backoff\" U \"all_delivered\" ];\r\n//RESULT (err=0.2): 0.92\r\n\"all_before_max2\": Pmaxmax=? [ !\"collision_max_backoff\" U \"all_delivered\" ];\r\n\r\n// Minimum probability all stations send successfully before a collision with max backoff\r\n//RESULT (err=0.2): 0.82\r\n\"all_before_min1\": Pminmin=? [ !\"collision_max_backoff\" U \"all_delivered\" ];\r\n//RESULT (err=0.2): 0.92\r\n\"all_before_min2\": Pminmax=? [ !\"collision_max_backoff\" U \"all_delivered\" ];\r\n\r\n// Minimum expected time for all messages to be sent\r\n//RESULT (err=0.2): 65.56150885\r\n\"time_min1\": R{\"time\"}minmin=? [ F \"all_delivered\" ];\r\n//RESULT (err=0.2): 68.81219280798\r\n\"time_min2\": R{\"time\"}minmax=? [ F \"all_delivered\" ];\r\n\r\n// Maximum expected time for all messages to be sent\r\n//RESULT (err=0.2): 69.06092106902\r\n\"time_max1\": R{\"time\"}maxmin=? [ F \"all_delivered\" ];\r\n//RESULT (err=0.2): 72.6691525693\r\n\"time_max2\": R{\"time\"}maxmax=? [ F \"all_delivered\" ];\r\n\r\n// Minimum probability that some station eventually delivers with less than K backoffs\r\n//RESULT (err=0.2): 0.4\r\n\"some_before1\": Pminmin=? [ F min_backoff_after_success<K ];\r\n//RESULT (err=0.2): 0.6\r\n\"some_before2\": Pminmax=? [ F min_backoff_after_success<K ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/csma2_2_int.prism.props.args",
    "content": "-const err=0.2 -epsilon 1e-8\r\n# -const err=0.2 -convprog Gurobi\r\n# -const err=0.2 -convprog lpsolve\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/firewire_abst_int.prism",
    "content": "// integer semantics version of abstract firewire protocol\r\n// gxn 23/05/2001\r\n\r\nmdp\r\n\r\n// wire delay\r\nconst int delay;\r\n\r\n// probability of choosing fast and slow\r\nconst double fast = 0.5;\r\nconst double slow = 1-fast;\r\nconst double err;\r\n\r\n// largest constant the clock of the system is compared to\r\nconst int kx = 167;\r\n\r\nmodule abstract_firewire\r\n\t\r\n\t// clock \r\n\tx : [0..kx+1];\r\n\t\r\n\t// local state\r\n\ts : [0..9];\r\n\t// 0 -start_start\r\n\t// 1 -fast_start\r\n\t// 2 -start_fast\r\n\t// 3 -start_slow\r\n\t// 4 -slow_start\r\n\t// 5 -fast_fast\r\n\t// 6 -fast_slow\r\n\t// 7 -slow_fast\r\n\t// 8 -slow_slow\r\n\t// 9 -done\r\n\t\r\n\t// initial state\r\n\t[time] s=0 & x<delay -> (x'=min(x+1,kx+1));\r\n\t[round] s=0 -> [fast*(1-err),fast*(1+err)] : (s'=1) + [slow*(1-err),slow*(1+err)] : (s'=4);\r\n\t[round] s=0 -> [fast*(1-err),fast*(1+err)] : (s'=2) + [slow*(1-err),slow*(1+err)] : (s'=3);\r\n\t// fast_start\r\n\t[time] s=1 & x<delay -> (x'=min(x+1,kx+1));\r\n\t[] s=1 -> [fast*(1-err),fast*(1+err)] : (s'=5) & (x'=0) + [slow*(1-err),slow*(1+err)] : (s'=6) & (x'=0);\r\n\t// start_fast\r\n\t[time] s=2 & x<delay -> (x'=min(x+1,kx+1));\r\n\t[] s=2 -> [fast*(1-err),fast*(1+err)] : (s'=5) & (x'=0) + [slow*(1-err),slow*(1+err)] : (s'=7) & (x'=0);\r\n\t// start_slow\r\n\t[time] s=3 & x<delay -> (x'=min(x+1,kx+1));\r\n\t[] s=3 -> [fast*(1-err),fast*(1+err)] : (s'=6) & (x'=0) + [slow*(1-err),slow*(1+err)] : (s'=8) & (x'=0);\r\n\t// slow_start\r\n\t[time] s=4 & x<delay -> (x'=min(x+1,kx+1));\r\n\t[] s=4 -> [fast*(1-err),fast*(1+err)] : (s'=7) & (x'=0) + [slow*(1-err),slow*(1+err)] : (s'=8) & (x'=0);\r\n\t// fast_fast\r\n\t[time] s=5 & (x<85) -> (x'=min(x+1,kx+1));\r\n\t[] s=5 & (x>=76) -> (s'=0) & (x'=0);\r\n\t[] s=5 & (x>=76-delay) -> (s'=9) & (x'=0);\r\n\t// fast_slow\r\n\t[time] s=6 & x<167 -> (x'=min(x+1,kx+1));\r\n\t[] s=6 & x>=159-delay -> (s'=9) & (x'=0);\r\n\t// slow_fast\r\n\t[time] s=7 & x<167 -> (x'=min(x+1,kx+1));\r\n\t[] s=7 & x>=159-delay -> (s'=9) & (x'=0);\r\n\t// slow_slow\r\n\t[time] s=8 & x<167 -> (x'=min(x+1,kx+1));\r\n\t[] s=8 & x>=159 -> (s'=0) & (x'=0);\r\n\t[] s=8 & x>=159-delay -> (s'=9) & (x'=0);\r\n\t// done\r\n\t[] s=9 -> (s'=s);\r\n\t\r\nendmodule\r\n\r\n//reward structures\r\n// time\r\nrewards \"time\"\r\n\t[time] true : 1;\r\nendrewards\r\n// number of rounds\r\nrewards \"rounds\"\r\n\t[round] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/firewire_abst_int.prism.props",
    "content": "// Maximum expected rounds to elect a leader\r\n//RESULT (err=0.2,delay=10) : 5/3\r\n\"rounds1\": R{\"rounds\"}maxmin=? [ F (s=9) ];\r\n//RESULT (err=0.2,delay=10) : 5/2\r\n\"rounds2\": R{\"rounds\"}maxmax=? [ F (s=9) ];\r\n\r\n// Maximum expected time to elect a leader\r\n//RESULT (err=0.2,delay=10) : 262.2\r\n\"time_max1\": R{\"time\"}maxmin=? [ F (s=9) ];\r\n//RESULT (err=0.2,delay=10) : 393.3\r\n\"time_max2\": R{\"time\"}maxmax=? [ F (s=9) ];\r\n\r\n// Minimum expected time to elect a leader\r\n//RESULT (err=0.2,delay=10) : 119.12\r\n\"time_min1\": R{\"time\"}minmin=? [ F (s=9) ];\r\n//RESULT (err=0.2,delay=10) : 135.72\r\n\"time_min2\": R{\"time\"}minmax=? [ F (s=9) ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/firewire_abst_int.prism.props.args",
    "content": "-const err=0.2 -const delay=10 -epsilon 1e-8\r\n# -const err=0.2 -const delay=10 -convprog Gurobi\r\n# -const err=0.2 -const delay=10 -convprog lpsolve\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/robot-ltl.prism",
    "content": "mdp\r\n\r\nconst double e;\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> [0.6-e,0.6+e]:(s'=1) + [0.4-e,0.4+e]:(s'=0);\r\n[south] s=0 -> [0.8-e,0.8+e]:(s'=3) + [0.1-e,0.1+e]:(s'=1) + [0.1-e,0.1+e]:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/robot-ltl.prism.args",
    "content": "-const e=0\n-const e=0.05\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/robot-ltl.prism.props",
    "content": "// RESULT: 0.5\nPmaxmin=? [ G F \"goal1\" ]\n\n// RESULT: 0.5\nPmaxmax=? [ G F \"goal1\" ]\n\n// RESULT (e=0): 0.1\n// RESULT (e=0.05): 0.05\nPmaxmin=? [ (G !\"hazard\")&(G F \"goal1\") ]\n\n// RESULT (e=0): 0.1\n// RESULT (e=0.05): 0.15\nPmaxmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n\n// RESULT (e=0): 0.9\n// RESULT (e=0.05): 0.85\nPminmin=? [ !((G !\"hazard\")&(G F \"goal1\")) ]\n\n// RESULT (e=0): 0.9\n// RESULT (e=0.05): 0.95\nPminmax=? [ !((G !\"hazard\")&(G F \"goal1\")) ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/robot.prism",
    "content": "mdp\r\n\r\nconst double delta;\r\nconst double p = 0.5-delta;\r\nconst double q = 0.5+delta;\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n//[east] s=1 -> 1:(s'=2);\r\n[east] s=1 -> [0.8,0.9]:(s'=2) + [0.1,0.2]:(s'=1);\r\n[south] s=1 -> [p,q]:(s'=4) + [1-q,1-p]:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/robot.prism.cosafe.props",
    "content": "// RESULT: max(p,0.1+0.1*p)\nPmaxmin=? [ X F \"goal1\" ];\n\n// RESULT: q\nPmaxmax=? [ X F \"goal1\" ];\n\n// RESULT: min(109/90,6/5+p/10)  //  = min(1+(0.1*1+0.1*(10/9)),1+(0.1*1+0.1*(1+p)))\nRminmin=? [ X F \"goal1\"|\"goal2\" ];\n\n// RESULT: 98/80  // = 1+(0.1*1+0.1*(10/8))\nRminmax=? [ X F \"goal1\"|\"goal2\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/robot.prism.cosafe.props.args",
    "content": "-const delta=0.05:0.2:0.45\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/robot.prism.props",
    "content": "// RESULT: max(p,0.1+0.1*p)\r\nPmaxmin=? [ F \"goal1\" ];\r\n\r\n// RESULT: q\r\nPmaxmax=? [ F \"goal1\" ];\r\n\r\n// RESULT: min(109/90,6/5+p/10)  //  = min(1+(0.1*1+0.1*(10/9)),1+(0.1*1+0.1*(1+p)))\r\nRminmin=? [ F \"goal1\"|\"goal2\" ];\r\n\r\n// RESULT: 98/80  // = 1+(0.1*1+0.1*(10/8))\r\nRminmax=? [ F \"goal1\"|\"goal2\" ];\r\n\r\n// RESULT: 31/24  // = 1+(0.1*(10/6)+0.1*(10/8))\r\nRminmax=? [ F \"goal2\" ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/robot.prism.props.args",
    "content": "-const delta=0.05:0.2:0.45\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/zeroconf_dl_int.prism",
    "content": "// IPv4: PTA model with digitial clocks\r\n// one concrete host attempting to choose an ip address \r\n// when a number of (abstract) hosts have already got ip addresses\r\n// gxn/dxp/jzs 02/05/03\r\n\r\n// reset or noreset model\r\nconst bool reset;\r\nconst int deadline;\r\n\r\n//-------------------------------------------------------------\r\n\r\n// we suppose that\r\n// - the abstract hosts have already picked their addresses \r\n//   and always defend their addresses\r\n// - the concrete host never picks the same ip address twice \r\n//   (this can happen only with a verys small probability)\r\n\r\n// under these assumptions we do not need message types because:\r\n// 1) since messages to the concrete host will never be a probe, \r\n//    this host will react to all messages in the same way\r\n// 2) since the abstract hosts always defend their addresses, \r\n//    all messages from the host will get an arp reply if the ip matches\r\n\r\n// following from the above assumptions we require only three abstract IP addresses\r\n// (0,1 and 2) which correspond to the following sets of IP addresses:\r\n\r\n// 0 - the IP addresses of the abstract hosts which the concrete host \r\n//     previously tried to configure\r\n// 1 - an IP address of an abstract host which the concrete host is \r\n//     currently trying to configure\r\n// 2 - a fresh IP address which the concrete host is currently trying to configure\r\n\r\n// if the host picks an address that is being used it may end up picking another ip address\r\n// in which case there may still be messages corresponding to the old ip address\r\n// to be sent both from and to the host which the host should now disregard\r\n// (since it will never pick the same ip address)\r\n\r\n// to deal with this situation: when a host picks a new ip address we reconfigure the \r\n// messages that are still be be sent or are being sent by changing the ip address to 0 \r\n// (an old ip address of the host)\r\n\r\n// all the messages from the abstract hosts for the 'old' address (in fact the\r\n// set of old addresses since it may have started again more than once)  \r\n// can arrive in any order since they are equivalent to the host - it ignores then all\r\n\r\n// also the messages for the old and new address will come from different hosts\r\n// (the ones with that ip address) which we model by allowing them to arrive in any order\r\n// i.e. not neccessarily in the order they where sent\r\n\r\n//-------------------------------------------------------------\r\n// model is an mdp_mix\r\nmdp\r\n\r\n//-------------------------------------------------------------\r\n// VARIABLES\r\nconst int N; // number of abstract hosts\r\nconst int K; // number of probes to send\r\nconst double loss = 0.1; // probability of message loss\r\n\r\n// PROBABILITIES\r\nconst double old = N/65024; // probability pick an ip address being used\r\nconst double new = (1-old); // probability pick a new ip address\r\n\r\n// TIMING CONSTANTS\r\nconst int CONSEC = 2;  // time interval between sending consecutive probles \r\nconst int TRANSTIME = 1; // upper bound on transmission time delay\r\nconst int LONGWAIT = 60; // minimum time delay after a high number of address collisions\r\nconst int DEFEND = 10;\r\n\r\nconst int TIME_MAX_X = 60; // max value of clock x\r\nconst int TIME_MAX_Y = 10; // max value of clock y\r\nconst int TIME_MAX_Z = 1;  // max value of clock z\r\n\r\n// OTHER CONSTANTS\r\nconst int MAXCOLL = 10;  // maximum number of collisions before long wait\r\n// size of buffers for other hosts\r\nconst int B0 = 20;  // buffer size for one abstract host\r\nconst int B1 = 8;  // buffer sizes for all abstract hosts\r\nconst double err; // error in the estimation of the back-off scheme probabilities\r\n\r\n//-------------------------------------------------------------\r\n// ENVIRONMENT - models: medium, output buffer of concrete host and all other hosts\r\nmodule environment\r\n\t\r\n\t// buffer of concrete host\r\n\tb_ip7 : [0..2]; // ip address of message in buffer position 8\r\n\tb_ip6 : [0..2]; // ip address of message in buffer position 7\r\n\tb_ip5 : [0..2]; // ip address of message in buffer position 6\r\n\tb_ip4 : [0..2]; // ip address of message in buffer position 5\r\n\tb_ip3 : [0..2]; // ip address of message in buffer position 4\r\n\tb_ip2 : [0..2]; // ip address of message in buffer position 3\r\n\tb_ip1 : [0..2]; // ip address of message in buffer position 2\r\n\tb_ip0 : [0..2]; // ip address of message in buffer position 1\r\n\tn : [0..8]; // number of places in the buffer used (from host)\r\n\t\r\n\t// messages to be sent from abstract hosts to concrete host\r\n\tn0  : [0..B0]; // number of messages which do not have the host's current ip address\r\n\tn1  : [0..B1]; // number of messages which have the host's current ip address\r\n\t\r\n\tb : [0..2]; // local state\r\n\t// 0 - idle\r\n\t// 1 - sending message from concrete host \r\n\t// 2 - sending message from abstract host\r\n\t\r\n\tz : [0..1]; // clock of environment (needed for the time to send a message)\r\n\t\r\n\tip_mess : [0..2]; // ip in the current message being sent\r\n\t// 0 - different from concrete host\r\n\t// 1 - same as the concrete host and in use\r\n\t// 2 - same as the concrete host and not in use\r\n\t\r\n\t// RESET/RECONFIG: when host is about to choose new ip address\r\n\t// suppose that the host cannot choose the same ip address\r\n\t// (since happens with very small probability). \r\n\t// Therefore all messages will have a different ip address, \r\n\t// i.e. all n1 messages become n0 ones.\r\n\t// Note this include any message currently being sent (ip is set to zero 0)\r\n\t[reset] true -> (n1'=0) & (n0'=min(B0,n0+n1)) // abstract buffers \r\n\t               & (ip_mess'=0) // message being set\r\n\t               & (n'=(reset)?0:n) // concrete buffer (remove this update to get NO_RESET model)\r\n\t               & (b_ip7'=0) \r\n\t               & (b_ip6'=0) \r\n\t               & (b_ip5'=0) \r\n\t               & (b_ip4'=0) \r\n\t               & (b_ip3'=0) \r\n\t               & (b_ip2'=0) \r\n\t               & (b_ip1'=0) \r\n\t               & (b_ip0'=0);\r\n\t// note: prevent anything else from happening when reconfiguration needs to take place\r\n\t\r\n\t// time passage (only if no messages to send or sending a message)\r\n\t[time] l>0 & b=0 & n=0 & n0=0 & n1=0 -> (b'=b); // cannot send a message\r\n\t[time] l>0 & b>0 & z<1 -> (z'=min(z+1,TIME_MAX_Z)); // sending a message\r\n\t\r\n\t// get messages to be sent (so message has same ip address as host)\r\n\t[send] l>0 & n=0 -> (b_ip0'=ip) & (n'=n+1);\r\n\t[send] l>0 & n=1 -> (b_ip1'=ip) & (n'=n+1);\r\n\t[send] l>0 & n=2 -> (b_ip2'=ip) & (n'=n+1);\r\n\t[send] l>0 & n=3 -> (b_ip3'=ip) & (n'=n+1);\r\n\t[send] l>0 & n=4 -> (b_ip4'=ip) & (n'=n+1);\r\n\t[send] l>0 & n=5 -> (b_ip5'=ip) & (n'=n+1);\r\n\t[send] l>0 & n=6 -> (b_ip6'=ip) & (n'=n+1);\r\n\t[send] l>0 & n=7 -> (b_ip7'=ip) & (n'=n+1);\r\n\t[send] l>0 & n=8 -> (n'=n); // buffer full so lose message\r\n\t\r\n\t// start sending message from host\r\n\t[] l>0 & b=0 & n>0 -> [(1-loss)*(1-err),(1-loss)*(1+err)] : (b'=1) & (ip_mess'=b_ip0) \r\n\t                                & (n'=n-1)\r\n\t                                & (b_ip7'=0) \r\n\t                                & (b_ip6'=b_ip7) \r\n\t                                & (b_ip5'=b_ip6) \r\n\t                                & (b_ip4'=b_ip5) \r\n\t                                & (b_ip3'=b_ip4) \r\n\t                                & (b_ip2'=b_ip3) \r\n\t                                & (b_ip1'=b_ip2) \r\n\t                                & (b_ip0'=b_ip1) // send message\r\n\t                         + [loss*(1-err),loss*(1+err)] : (n'=n-1)\r\n\t                                & (b_ip7'=0) \r\n\t                                & (b_ip6'=b_ip7) \r\n\t                                & (b_ip5'=b_ip6) \r\n\t                                & (b_ip4'=b_ip5) \r\n\t                                & (b_ip3'=b_ip4) \r\n\t                                & (b_ip2'=b_ip3) \r\n\t                                & (b_ip1'=b_ip2) \r\n\t                                & (b_ip0'=b_ip1); // lose message\r\n\t\r\n\t// start sending message to host\r\n\t[] l>0 & b=0 & n0>0 -> [(1-loss)*(1-err),(1-loss)*(1+err)] : (b'=2) & (ip_mess'=0) & (n0'=n0-1) + [loss*(1-err),loss*(1+err)] : (n0'=n0-1); // different ip\r\n\t[] l>0 & b=0 & n1>0 -> [(1-loss)*(1-err),(1-loss)*(1+err)] : (b'=2) & (ip_mess'=1) & (n1'=n1-1) + [loss*(1-err),loss*(1+err)] : (n1'=n1-1); // same ip\r\n\t\r\n\t// finish sending message from host\r\n\t[] l>0 & b=1 & ip_mess=0 -> (b'=0) & (z'=0) & (n0'=min(n0+1,B0)) & (ip_mess'=0);\r\n\t[] l>0 & b=1 & ip_mess=1 -> (b'=0) & (z'=0) & (n1'=min(n1+1,B1)) & (ip_mess'=0);\r\n\t[] l>0 & b=1 & ip_mess=2 -> (b'=0) & (z'=0) & (ip_mess'=0);\r\n\t\r\n\t// finish sending message to host\r\n\t[rec] l>0 & b=2 -> (b'=0) & (z'=0) & (ip_mess'=0);\r\n\t\r\nendmodule\r\n\r\n//-------------------------------------------------------------\r\n// CONCRETE HOST\r\nmodule host0\r\n\t\r\n\tx : [0..TIME_MAX_X]; // first clock of the host\r\n\ty : [0..TIME_MAX_Y]; // second clock of the host\r\n\t\r\n\tcoll : [0..MAXCOLL]; // number of address collisions\r\n\tprobes : [0..K]; // counter (number of probes sent)\r\n\tmess : [0..1]; // need to send a message or not\r\n\tdefend : [0..1]; // defend (if =1, try to defend IP address)\r\n\t\r\n\tip : [1..2]; // ip address (1 - in use & 2 - fresh)\r\n\t\r\n\tl : [0..4] init 1; // location\r\n\t// 0 : RECONFIGURE \r\n\t// 1 : RANDOM\r\n\t// 2 : WAITSP\r\n\t// 3 : WAITSG \r\n\t// 4 : USE\r\n\t\r\n\t// RECONFIGURE\r\n\t[reset] l=0 -> (l'=1);\r\n\t\r\n\t// RANDOM (choose IP address)\r\n\t[rec] (l=1) -> true; // get message (ignore since have no ip address)\r\n\t// small number of collisions (choose straight away)\r\n\t[] l=1 & coll<MAXCOLL -> [1/3*old*(1-err),1/3*old*(1+err)] : (l'=2) & (ip'=1) & (x'=0) \r\n\t\t                     + [1/3*old*(1-err),1/3*old*(1+err)] : (l'=2) & (ip'=1) & (x'=1) \r\n\t\t                     + [1/3*old*(1-err),1/3*old*(1+err)] : (l'=2) & (ip'=1) & (x'=2) \r\n\t\t                     + [1/3*new*(1-err),1/3*new*(1+err)] : (l'=2) & (ip'=2) & (x'=0) \r\n\t\t                     + [1/3*new*(1-err),1/3*new*(1+err)] : (l'=2) & (ip'=2) & (x'=1) \r\n\t\t                     + [1/3*new*(1-err),1/3*new*(1+err)] : (l'=2) & (ip'=2) & (x'=2); \r\n\t// large number of collisions: (wait for LONGWAIT)\r\n\t[time] l=1 & coll=MAXCOLL & x<LONGWAIT -> (x'=min(x+1,TIME_MAX_X));\r\n\t[]     l=1 & coll=MAXCOLL & x=LONGWAIT -> [1/3*old*(1-err),1/3*old*(1+err)] : (l'=2) & (ip'=1) & (x'=0) \r\n\t\t\t                                   + [1/3*old*(1-err),1/3*old*(1+err)] : (l'=2) & (ip'=1) & (x'=1) \r\n\t\t\t                                   + [1/3*old*(1-err),1/3*old*(1+err)] : (l'=2) & (ip'=1) & (x'=2) \r\n\t\t\t                                   + [1/3*new*(1-err),1/3*new*(1+err)] : (l'=2) & (ip'=2) & (x'=0) \r\n\t\t\t                                   + [1/3*new*(1-err),1/3*new*(1+err)] : (l'=2) & (ip'=2) & (x'=1) \r\n\t\t\t                                   + [1/3*new*(1-err),1/3*new*(1+err)] : (l'=2) & (ip'=2) & (x'=2);\r\n\t\r\n\t// WAITSP \r\n\t// let time pass\r\n\t[time]  l=2 & x<2 -> (x'=min(x+1,2));\r\n\t// send probe\r\n\t[send] l=2 & x=2  & probes<K -> (x'=0) & (probes'=probes+1);\r\n\t// sent K probes and waited 2 seconds\r\n\t[] l=2 & x=2 & probes=K -> (l'=3) & (probes'=0) & (coll'=0) & (x'=0);\r\n\t// get message and ip does not match: ignore\r\n\t[rec] l=2 & ip_mess!=ip -> (l'=l);\r\n\t// get a message with matching ip: reconfigure\r\n\t[rec] l=2 & ip_mess=ip -> (l'=0) & (coll'=min(coll+1,MAXCOLL)) & (x'=0) & (probes'=0);\r\n\t\r\n\t// WAITSG (sends two gratuitious arp probes)\r\n\t// time passage\r\n\t[time] l=3 & mess=0 & defend=0 & x<CONSEC -> (x'=min(x+1,TIME_MAX_X)); \r\n\t[time] l=3 & mess=0 & defend=1 & x<CONSEC -> (x'=min(x+1,TIME_MAX_X)) & (y'=min(y+1,DEFEND));\r\n\t\r\n\t// receive message and same ip: defend\r\n\t[rec] l=3 & mess=0 & ip_mess=ip & (defend=0 | y>=DEFEND) -> (defend'=1) & (mess'=1) & (y'=0);\r\n\t// receive message and same ip: defer\r\n\t[rec] l=3 & mess=0 & ip_mess=ip & (defend=0 | y<DEFEND) -> (l'=0) & (probes'=0) & (defend'=0) & (x'=0) & (y'=0);\r\n\t// receive message and different ip\r\n\t[rec] l=3 & mess=0 & ip_mess!=ip -> (l'=l);\r\n\t\r\n\t\t\r\n\t// send probe reply or message for defence\r\n\t[send] l=3 & mess=1 -> (mess'=0);\r\n\t// send first gratuitous arp message\r\n\t[send] l=3 & mess=0 & x=CONSEC & probes<1 -> (x'=0) & (probes'=probes+1);\r\n\t// send second gratuitous arp message (move to use)\r\n\t[send] l=3 & mess=0 & x=CONSEC & probes=1 -> (l'=4) & (x'=0) & (y'=0) & (probes'=0);\r\n\t\r\n\t// USE (only interested in reaching this state so do not need to add anything here)\r\n\t[] l=4 -> true;\r\n\t\r\nendmodule\r\n\r\n//-------------------------------------------------------------\r\n\r\n// timer\r\nmodule timer\r\n\r\n\tt : [0..deadline+1];\r\n\t\r\n\t[time] t<=deadline -> (t'=min(t+1,deadline+1));\r\n\t[done] l=4 -> (t'=deadline+1);\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/zeroconf_dl_int.prism.props",
    "content": "// Minimum probability of not using fresh IP address within deadline\r\n// RESULT (err=0.05,N=200,K=5,reset=false,deadline=15):0.6507680573\r\n\"deadline_min1\": Pminmin=? [ !(l=4 & ip=2) U t>=deadline ];\r\n\r\n// Minimum probability of not using fresh IP address within deadline\r\n// RESULT (err=0.05,N=200,K=5,reset=false,deadline=15):0.6840604592\r\n\"deadline_min2\": Pminmax=? [ !(l=4 & ip=2) U t>=deadline ];\r\n\r\n// Maximum probability of not using fresh IP address within deadline\r\n// RESULT (err=0.05,N=200,K=5,reset=false,deadline=15):0.6510765255905512\r\n\"deadline_max1\": Pmaxmin=? [ !(l=4 & ip=2) U t>=deadline ];\r\n\r\n// Maximum probability of not using fresh IP address within deadline\r\n// RESULT (err=0.05,N=200,K=5,reset=false,deadline=15):0.6843073326771654\r\n\"deadline_max2\": Pmaxmax=? [ !(l=4 & ip=2) U t>=deadline ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/imdps/zeroconf_dl_int.prism.props.args",
    "content": "-const err=0.05,N=200,K=5,reset=false,deadline=15 -epsilon 1e-8\r\n# -const err=0.05,N=200,K=5,reset=false,deadline=15 -convprog Gurobi\r\n# -const err=0.05,N=200,K=5,reset=false,deadline=15 -convprog lpsolve\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ltss/lec9ctl1.prism",
    "content": "// Simple LTS from Lec 9 of Computer-Aided Verification\r\n\r\nmodule M\r\n\r\ns:[0..3];\r\n\r\n[] s=0 -> (s'=1);\r\n[] s=0 -> (s'=2);\r\n[] s=1 -> (s'=1);\r\n[] s=1 -> (s'=3);\r\n[] s=2 -> (s'=1);\r\n[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = s=0 | s=1;\r\nlabel \"b\" = s=0 | s=3;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ltss/lec9ctl1.prism.props",
    "content": "// Simple LTS from Lec 9 of Computer-Aided Verification\n\n// RESULT: ?\n\"ex\": A[ X \"a\" ] & E[ X !\"b\"];\n// RESULT: true\nfilter(forall, \"ex\" <=> (s=2));\n\n// RESULT: ?\n\"ex_lhs\": A[ X \"a\" ]\n// RESULT: true\nfilter(forall, \"ex_lhs\" <=> (s=2));\n\n// RESULT: ?\n\"ex_rhs\": E[ X !\"b\"];\n// RESULT: true\nfilter(forall, \"ex_rhs\" <=> (s=0|s=1|s=2));\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/bounded-reach/mdp_simple.nm",
    "content": "// Simple MDP tests cases, used during development of stochastic game model checking\r\n\r\nmdp\r\n\r\nmodule m1\r\n\ts : [0..5];\r\n\tt : [0..2];\r\n\r\n\t[] s=0 & t=0 -> (s'=1);\r\n\t[] s=0 & t=0 -> 0.1 : (t'=1)&(s'=0) + 0.9 : (t'=2)&(s'=0);\r\n\r\n\t[] s=1 & t=0 -> (s'=2);\r\n\t[] s=1 & t=0 -> 0.2 : (t'=1)&(s'=0) + 0.8 : (t'=2)&(s'=0);\r\n\r\n\t[] s=2 & t=0 -> (s'=3);\r\n\t[] s=2 & t=0 -> 0.3 : (t'=1)&(s'=1) + 0.7 : (t'=2)&(s'=1);\r\n\r\n\t[] s=3 & t=0 -> (s'=4);\r\n\t[] s=3 & t=0 -> 0.4 : (t'=1)&(s'=0)+ 0.6 : (t'=2)&(s'=0);\r\n\r\n\t[] s=4 & t=0 -> (s'=5);\r\n\t[] s=4 & t=0 -> 0.5 : (t'=1)&(s'=0) + 0.5 : (t'=2)&(s'=0);\r\n\r\n\t[] s=5 & t=0 -> (t'=1)&(s'=0);\r\n\r\n\t[] t>0 -> true;\r\n\r\nendmodule\r\n\r\nrewards \r\n    mod(s,2)=0 : 1;\r\nendrewards"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/bounded-reach/mdp_simple.nm.props",
    "content": "// RESULT: 0.1\nPmax=? [ F<=1 t=1 ]\n// RESULT: 0.1\nPmax=? [ true U<=1 t=1 ]\n// RESULT: 0.1\nPmax=? [ true U[0,1] t=1 ]\n// RESULT: 0.1\nPmax=? [ true U=1 t=1 ]\n\n// RESULT: 0.2\nPmax=? [ F<=2 t=1 ]\n// RESULT: 0.2\nPmax=? [ true U<=2 t=1 ]\n// RESULT: 0.2\nPmax=? [ true U[0,2] t=1 ]\n// RESULT: 0.2\nPmax=? [ true U=2 t=1 ]\n\n// RESULT: 0.4\nPmax=? [ F<=4 t=1 ]\n// RESULT: 0.4\nPmax=? [ true U<=4 t=1 ]\n// RESULT: 0.4\nPmax=? [ true U[0,4] t=1 ]\n// RESULT: 0.4\nPmax=? [ true U=4 t=1 ]\n\n// RESULT: 0.4\nPmax=? [ F<5 t=1 ]\n// RESULT: 0.4\nPmax=? [ true U<5 t=1 ]\n\n// RESULT: 0.0\nPmin=?[ F<=1 t=1 ]\n// RESULT: 0.0\nPmin=?[ F<=2 t=1 ]\n// RESULT: 0.0\nPmin=?[ F<=4 t=1 ]\n// RESULT: 0.1\nPmin=?[ F<=6 t=1 ]\n// RESULT: 0.1\nPmin=?[ F[2,6] t=1 ]\n// RESULT: 0.0\nPmin=?[ (t!=1) U[2,6] t=1 ]\n\n\n\n// RESULT: 0.9\nPmin=?[ G<=1 t!=1 ]\n// RESULT: 1.0\nPmax=?[ G<=1 t!=1 ]\n\n// RESULT: 0.8\nPmin=?[ G<=2 t!=1 ]\n// RESULT: 1.0\nPmax=?[ G<=2 t!=1 ]\n\n// RESULT: 0.7\nPmin=?[ G<=3 t!=1 ]\n// RESULT: 1.0\nPmax=?[ G<=3 t!=1 ]\n\n\n// RESULT: 0.6\nPmin=?[ G<=4 t!=1 ]\n// RESULT: 1.0\nPmax=?[ G<=4 t!=1 ]\n\n\n// RESULT: 0.5\nPmin=?[ G<=5 t!=1 ]\n// RESULT: 1.0\nPmax=?[ G<=5 t!=1 ]\n\n// RESULT: 0.5\nPmin=?[ G<6 t!=1 ]\n// RESULT: 1.0\nPmax=?[ G<6 t!=1 ]\n\n// RESULT: 0.0\nPmin=?[ G<=6 t!=1 ]\n// RESULT: 1.0\nPmax=?[ G<=5 t!=1 ]\n\n// RESULT: 0.9\nPmax=?[ G<=7 t!=1 ]\n\n\n// RESULT: 0.5\nPmin=?[ G[2,5] t!=1 ]\n\n\n// RESULT: 1.0\nPmax=? [ F>=1 t=1 ]\n// RESULT: 1.0\nPmax=? [ F>=2 t=1 ]\n// RESULT: 1.0\nPmax=? [ F>=3 t=1 ]\n// RESULT: 1.0\nPmax=? [ F>=4 t=1 ]\n// RESULT: 1.0\nPmax=? [ F>=5 t=1 ]\n// RESULT: 1.0\nPmax=? [ F>=6 t=1 ]\n\n// RESULT: 0.1\nPmin=? [ F>=1 t=1 ]\n\n// RESULT: 0.8\nPmin=? [ F>=2 t!=1 ]\n// RESULT: 0.7\nPmin=? [ F>=3 t!=1 ]\n// RESULT: 0.6\nPmin=? [ F>=4 t!=1 ]\n// RESULT: 0.5\nPmin=? [ F>=5 t!=1 ]\n// RESULT: 0.0\nPmin=? [ F>=6 t!=1 ]\n\n\n// RESULT: 0.9\nPmax=? [ G>=1 t!=1 ]\n// RESULT: 0.9\nPmax=? [ G>=2 t!=1 ]\n// RESULT: 0.9\nPmax=? [ G>=3 t!=1 ]\n// RESULT: 0.9\nPmax=? [ G>=4 t!=1 ]\n// RESULT: 0.9\nPmax=? [ G>=5 t!=1 ]\n// RESULT: 0.9\nPmax=? [ G>=6 t!=1 ]\n\n// RESULT: 0.3\nPmax=? [ s<=2 U t=1 ]\n// RESULT: 0.1\nPmax=? [ s<=2 U<=1 t=1 ]\n// RESULT: 0.2\nPmax=? [ s<=2 U<=2 t=1 ]\n// RESULT: 0.2\nPmax=? [ s<=2 U<3 t=1 ]\n// RESULT: 0.3\nPmax=? [ s<=2 U<=3 t=1 ]\n// RESULT: 0.3\nPmax=? [ s<=2 U<4 t=1 ]\n// RESULT: 0.3\nPmax=? [ s<=2 U<=4 t=1 ]\n// RESULT: 0.3\nPmax=? [ s<=2 U<=5 t=1 ]\n// RESULT: 0.3\nPmax=? [ s<=2 U<=6 t=1 ]\n\n// RESULT: 0.3\nPmax=? [ (s<=2 & t!=1) U t=1 ]\n// RESULT: 0.0\nPmax=? [ (s<=2 & t!=1) U[0,0] t=1 ]\n// RESULT: 0.1\nPmax=? [ (s<=2 & t!=1) U[0,1] t=1 ]\n// RESULT: 0.1\nPmax=? [ (s<=2 & t!=1) U[1,1] t=1 ]\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/coalition/robotmod.nm",
    "content": "mdp\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.55:(s'=4) + 0.45:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/coalition/robotmode.nm.props",
    "content": "// RESULT: 0\nPmin=? [ F \"goal1\" ]\n// RESULT: 0.55\nPmax=? [ F \"goal1\" ]\n// RESULT: true\nP>=0 [ F \"goal1\" ]\n// RESULT: false\nP>0 [ F \"goal1\" ]\n// RESULT: false\nP<0.5 [ F \"goal1\" ]\n// RESULT: true\nP<0.6 [ F \"goal1\" ]\n// RESULT: false\nP>0.6 [ F \"goal1\" ]\n// RESULT: 0\nPmin=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: 0.1\nPmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\nP>=0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\nP>0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\nP<0.05 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\nP<0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\nP>0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n\n// RESULT: 0\n[[*]] Pmin=? [ F \"goal1\" ]\n// RESULT: 0.55\n[[*]] Pmax=? [ F \"goal1\" ]\n// RESULT: true\n[[*]] P>=0 [ F \"goal1\" ]\n// RESULT: false\n[[*]] P>0 [ F \"goal1\" ]\n// RESULT: false\n[[*]] P<0.5 [ F \"goal1\" ]\n// RESULT: true\n[[*]] P<0.6 [ F \"goal1\" ]\n// RESULT: false\n[[*]] P>0.6 [ F \"goal1\" ]\n// RESULT: 0\n[[*]] Pmin=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: 0.1\n[[*]] Pmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n[[*]] P>=0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\n[[*]] P>0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\n[[*]] P<0.05 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n[[*]] P<0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\n[[*]] P>0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n\n// RESULT: 0\n<<*>> Pmin=? [ F \"goal1\" ]\n// RESULT: 0.55\n<<*>> Pmax=? [ F \"goal1\" ]\n// RESULT: true\n<<*>> P>=0 [ F \"goal1\" ]\n// RESULT: true\n<<*>> P>0 [ F \"goal1\" ]\n// RESULT: true\n<<*>> P<0.5 [ F \"goal1\" ]\n// RESULT: true\n<<*>> P<0.6 [ F \"goal1\" ]\n// RESULT: false\n<<*>> P>0.6 [ F \"goal1\" ]\n// RESULT: 0\n<<*>> Pmin=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: 0.1\n<<*>> Pmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n<<*>> P>=0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n<<*>> P>0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n<<*>> P<0.05 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n<<*>> P<0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\n<<*>> P>0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n\n// 1 player so <<*>> == [[]]\n\n// RESULT: 0\n[[]] Pmin=? [ F \"goal1\" ]\n// RESULT: 0.55\n[[]] Pmax=? [ F \"goal1\" ]\n// RESULT: true\n[[]] P>=0 [ F \"goal1\" ]\n// RESULT: true\n[[]] P>0 [ F \"goal1\" ]\n// RESULT: true\n[[]] P<0.5 [ F \"goal1\" ]\n// RESULT: true\n[[]] P<0.6 [ F \"goal1\" ]\n// RESULT: false\n[[]] P>0.6 [ F \"goal1\" ]\n// RESULT: 0\n[[]] Pmin=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: 0.1\n[[]] Pmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n[[]] P>=0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n[[]] P>0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n[[]] P<0.05 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n[[]] P<0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\n[[]] P>0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n\n// 1 player so [[*]] == <<>>\n\n// RESULT: 0\n[[*]] Pmin=? [ F \"goal1\" ]\n// RESULT: 0.55\n[[*]] Pmax=? [ F \"goal1\" ]\n// RESULT: true\n[[*]] P>=0 [ F \"goal1\" ]\n// RESULT: false\n[[*]] P>0 [ F \"goal1\" ]\n// RESULT: false\n[[*]] P<0.5 [ F \"goal1\" ]\n// RESULT: true\n[[*]] P<0.6 [ F \"goal1\" ]\n// RESULT: false\n[[*]] P>0.6 [ F \"goal1\" ]\n// RESULT: 0\n[[*]] Pmin=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: 0.1\n[[*]] Pmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n[[*]] P>=0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\n[[*]] P>0 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\n[[*]] P<0.05 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: true\n[[*]] P<0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n// RESULT: false\n[[*]] P>0.15 [ (G !\"hazard\")&(G F \"goal1\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/Bai98-ex9.4.12-p239.nm",
    "content": "// simple LTL/fairness example from Christel's thesis (p.239-240)\r\n\r\n// note that the product MDP in fig 9.15 is incorrect:\r\n// s_3,q_0 should be s_3,q_1\r\n// s_5,q_1 should be s_5,q_2\r\n// (and thus state s_5,q_1 disappears)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\ts : [1..5];\r\n\r\n\t[] (s=1) -> (s'=2);\r\n\t[] (s=2) -> (s'=2);\r\n\t[] (s=2) -> 0.5:(s'=3) + 0.5:(s'=4);\r\n\t[] (s=3) -> (s'=5);\r\n\t[] (s=4) -> (s'=5);\r\n\t[] (s=5) -> (s'=5);\r\n\t\r\nendmodule\r\n\r\nlabel \"a\" = s=3;\r\nlabel \"b\" = s=2 | s=5;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/Bai98-ex9.4.12-p239.nm.nofair.props",
    "content": "\t// RESULT: 0\n\tPmin=? [ F (\"a\" & (X \"b\")) ];\n\t// RESULT: 0.5\n\tPmax=? [ F (\"a\" & (X \"b\")) ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/Bai98-ex9.4.12-p239.nm.nofair.props.args",
    "content": "-nofair\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/Bai98-remark9.4.13-p240.nm",
    "content": "// another simple LTL example from Christel's thesis (p.240)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\ts : [1..3];\r\n\t\r\n\t// s\r\n\t[] (s=1) -> (s'=2);\r\n\t[] (s=1) -> (s'=3);\r\n\t// t\r\n\t[] (s=2) -> (s'=1);\r\n\t// u\r\n\t[] (s=3) -> (s'=3);\r\n\t\r\nendmodule\r\n\r\nlabel \"a\" = s=1 | s=2;\r\nlabel \"b\" = s=2;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/Bai98-remark9.4.13-p240.nm.nofair.props",
    "content": "\t// RESULT: 0\n\tPmin=? [ (X \"b\") => (G \"a\") ];\n\t// RESULT: 1\n\tPmax=? [ (X \"b\") => (G \"a\") ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/Bai98-remark9.4.13-p240.nm.nofair.props.args",
    "content": "-nofair\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/jaeger.prism",
    "content": "mdp\n \nmodule tree_160000\ns:[1..13] init 1;\n\n[r1]s=1 -> 1011/3406:(s'=2) +  2395/3406:(s'=3);\n[r2]s=1 -> 968/3276:(s'=4) +  2308/3276:(s'=5);\n[r2]s=2 -> 122/261:(s'=6) +  139/261:(s'=7);\n[r1]s=4 -> 123/239:(s'=8) +  116/239:(s'=9);\n[r4]s=6 -> 14/35:(s'=10) +  21/35:(s'=11);\n[r4]s=8 -> 14/32:(s'=12) +  18/32:(s'=13);\n[r1]s=3 -> 1:(s'=3);\n[r1]s=5 -> 1:(s'=5);\n[r1]s=7 -> 1:(s'=7);\n[r1]s=9 -> 1:(s'=9);\n[r1]s=10 -> 1:(s'=10);\n[r1]s=11 -> 1:(s'=11);\n[r1]s=12 -> 1:(s'=12);\n[r1]s=13 -> 1:(s'=13);\nendmodule\n\nlabel \"o_000\" = s=1;\nlabel \"o_010\" = s=4;\nlabel \"o_100\" = s=2;\nlabel \"o_110\" = s=8|s=6;\nlabel \"o_Pr0\" = s=11|s=13;\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/jaeger.prism.props",
    "content": "// RESULT: 2143152/25054848  ( = 968/3276 * 123/239 * 18/32, i.e. approx. 0.085538)\nPmax=? [( (X ( X  ( \"o_110\"))) &  (X ( X  ( X ( \"o_Pr0\"))))) ]\n\n// RESULT: 119064/782964  ( = 968/3276 * 123/239, i.e. approx. 0.152068)\nPmax=? [ (X ( X  ( \"o_110\")))  ]\n\n// RESULT: 2143152/25054848  ( = 968/3276 * 123/239 * 18/32, i.e. approx. 0.085538)\nPmax=? [  (X ( X  ( X ( \"o_Pr0\")))) ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/jaeger.prism.props.args",
    "content": "-h\n-ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/lec15mdp.nm",
    "content": "// Simple MDP from Lec 15 of Probabilistic Model Checking\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\ns:[0..8];\r\n\r\n[] s=0 -> 1:(s'=2);\r\n[] s=0 -> 0.6:(s'=0) + 0.3:(s'=1) + 0.1:(s'=2);\r\n[] s=1 -> 0.3:(s'=3) + 0.7:(s'=4);\r\n[] s=3 -> 1:(s'=4);\r\n[] s=4 -> 1:(s'=1);\r\n[] s=4 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=6);\r\n[] s=6 -> 1:(s'=6);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=5 -> 0.9:(s'=7) + 0.1:(s'=8);\r\n[] s=7 -> 1:(s'=5);\r\n[] s=8 -> 1:(s'=5);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/lec15mdp.nm.props",
    "content": "\t// RESULT: 0.75\n\tPmax=? [ G F s=4|s=6 ];\n\t\n\t// RESULT: false\n\tP>=1 [ G F s=1|s=4|s=6 ];\n\t\n\t// RESULT: 1.0\n\tPmin=? [ G F (s=1|s=4|s=6|s=7) ];\n\t\n\t// RESULT: 0.25\n\tPmin=? [ G F (s=1|s=6|s=7) ];\n\t\n\t// RESULT: 0.25\n\tPmin=? [ G F s=7 ];\n\t\n\t// RESULT: 0.25\n\tPmin=? [ G F s=7 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/lec18mdp.nm",
    "content": "// Simple MDP from Lec 18 of Probabilistic Model Checking\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n// note: restricted to part of mdp\r\ns:[0..8] init 1;\r\n\r\n[] s=0 -> 1:(s'=2);\r\n[] s=0 -> 0.6:(s'=0) + 0.3:(s'=1) + 0.1:(s'=2);\r\n[] s=1 -> 0.3:(s'=3) + 0.7:(s'=4);\r\n[] s=3 -> 1:(s'=4);\r\n[] s=4 -> 1:(s'=1);\r\n[] s=4 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=6);\r\n[] s=6 -> 1:(s'=6);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=5 -> 0.9:(s'=7) + 0.1:(s'=8);\r\n[] s=7 -> 1:(s'=5);\r\n[] s=8 -> 1:(s'=5);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/lec18mdp.nm.props",
    "content": "\t// RESULT: 0.7\n\tPmax=? [ (G !(s=3)) & (G F (s=6)) ];\n\t\n\t// RESULT: 0.0\n\tPmin=? [ (G !(s=3)) & (G F (s=6)) ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/robot.nm",
    "content": "mdp\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/robot.nm.props",
    "content": "// RESULT: 0.5\nPmax=? [ G F \"goal1\" ]\n\n// RESULT: 0.1\nPmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/robot.nm.props.args",
    "content": "-explicit\n-explicit -ii -maxiters 100000\n-explicit -ii -topological -maxiters 100000\n-mtbdd\n-mtbdd -ii -maxiters 100000 -cuddepsilon 1E-20\n-hybrid\n-hybrid -ii -maxiters 100000\n-sparse\n-sparse -ii -maxiters 100000\n-exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/running-ltl.nm",
    "content": "// Running example MDP (see Figure 2, p.6)\r\n// and DRA for LTL property \"F G go\" (see Figure 10, p.36)\r\n\r\nmdp\r\n\r\n// MDP M\r\nmodule M\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3];\r\n\t\r\n\t[go] s=0 -> (s'=1);\r\n\t[safe] s=1 -> 0.7:(s'=0) + 0.3:(s'=2);\r\n\t[risk] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n\t[finish] s=2 -> (s'=2);\r\n\t[stop] s=3 -> (s'=3);\r\n\t[reset] s=3 -> (s'=0);\r\n\r\nendmodule\r\n\r\n// DRA A_ltl for LTL property \"F G go\"\r\n// This is encoded as a PRISM module to allow action-based LTL \r\n// model checking: PRISM only supports state-based LTL currently\r\nmodule A_ltl\r\n\r\n\t// q=i for state q_i\r\n\tq : [0..1] init 0;\r\n\r\n\t[go] q=0 -> (q'=1);\r\n\t[safe] q=0 -> (q'=0);\r\n\t[risk] q=0 -> (q'=0);\r\n\t[finish] q=0 -> (q'=0);\r\n\t[stop] q=0 -> (q'=0);\r\n\t[reset] q=0 -> (q'=0);\r\n\r\n\t[go] q=1 -> (q'=1);\r\n\t[safe] q=1 -> (q'=0);\r\n\t[risk] q=1 -> (q'=0);\r\n\t[finish] q=1 -> (q'=0);\r\n\t[stop] q=1 -> (q'=0);\r\n\t[reset] q=1 -> (q'=0);\r\n\r\nendmodule\r\n\r\n// Accepting pair (L_1,K_1) = ({q_0},{q_1}) for the DRA\r\nlabel \"L1\" = q=0;\r\nlabel \"K1\" = q=1;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/running-ltl.nm.props",
    "content": "// ex 15\n// RESULT: 0\nPmax=? [ (F G !\"L1\") & (G F \"K1\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/running-ltl2.nm",
    "content": "// Running example MDP (see Figure 2, p.6)\r\n// and DRA for LTL property \"(F G finish) & (F risk)\" (see Figure 11, p.38)\r\n\r\nmdp\r\n\r\n// MDP M\r\nmodule M\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3];\r\n\t\r\n\t[go] s=0 -> (s'=1);\r\n\t[safe] s=1 -> 0.7:(s'=0) + 0.3:(s'=2);\r\n\t[risk] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n\t[finish] s=2 -> (s'=2);\r\n\t[stop] s=3 -> (s'=3);\r\n\t[reset] s=3 -> (s'=0);\r\n\r\nendmodule\r\n\r\n// DRA A_ltl for LTL property \"(F G finish) & (F risk)\"\r\n// This is encoded as a PRISM module to allow action-based LTL \r\n// model checking: PRISM only supports state-based LTL currently\r\nmodule A_ltl\r\n\r\n\t// q=i for state q_i\r\n\tq : [0..2];\r\n\t\r\n\t[go] q=0 -> (q'=0);\r\n\t[safe] q=0 -> (q'=0);\r\n\t[risk] q=0 -> (q'=1);\r\n\t[finish] q=0 -> (q'=0);\r\n\t[stop] q=0 -> (q'=0);\r\n\t[reset] q=0 -> (q'=0);\r\n\r\n\t[go] q=1 -> (q'=1);\r\n\t[safe] q=1 -> (q'=1);\r\n\t[risk] q=1 -> (q'=1);\r\n\t[finish] q=1 -> (q'=2);\r\n\t[stop] q=1 -> (q'=1);\r\n\t[reset] q=1 -> (q'=1);\r\n\r\n\t[go] q=2 -> (q'=1);\r\n\t[safe] q=2 -> (q'=1);\r\n\t[risk] q=2 -> (q'=1);\r\n\t[finish] q=2 -> (q'=2);\r\n\t[stop] q=2 -> (q'=1);\r\n\t[reset] q=2 -> (q'=1);\r\n\r\nendmodule\r\n\r\n// Accepting pair (L_1,K_1) = ({q_1},{q_2}) for the DRA\r\nlabel \"L1\" = q=1;\r\nlabel \"K1\" = q=2;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/running-ltl2.nm.props",
    "content": "// ex 16\n// RESULT: 1\nPmax=? [ (F G !\"L1\") & (G F \"K1\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/simple_ltl.nm",
    "content": "// Test file from Carlos\r\n\r\nmdp\r\n\r\nmodule test\r\n\r\n\t// local state\r\n\ts : [1..3] init 1;\r\n\r\n\t[a] s=1 -> 0.2 : (s'=2) + 0.8 : (s'=3);\r\n\t[b] s=1 -> 0.4 : (s'=2) + 0.6 : (s'=3);\r\n\t[c] s=1 -> 0.5 : (s'=2) + 0.5 : (s'=3);\r\n\t[] s=2 -> (s'=2);\r\n\t[] s=3 -> (s'=3);\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl/simple_ltl.nm.props",
    "content": "// Test file from Carlos\n\n// RESULT: 0.5\nPmax=? [ F (s=2) ]\n\n// RESULT: 0.2\nPmin=? [ F (s=2) ]\n\n// RESULT: 0.8\nPmax=? [ !(F (s=2)) ]\n\n// RESULT: 0.8\nPmax=? [ G (s=2 | (F s=3)) ]\n\n// RESULT: 0.8\nPmax=? [ (X s=2) => (G s=3) ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl-fair/Bai98-ex9.4.12-p239.nm",
    "content": "// simple LTL/fairness example from Christel's thesis (p.239-240)\r\n\r\n// note that the product MDP in fig 9.15 is incorrect:\r\n// s_3,q_0 should be s_3,q_1\r\n// s_5,q_1 should be s_5,q_2\r\n// (and thus state s_5,q_1 disappears)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\ts : [1..5];\r\n\r\n\t[] (s=1) -> (s'=2);\r\n\t[] (s=2) -> (s'=2);\r\n\t[] (s=2) -> 0.5:(s'=3) + 0.5:(s'=4);\r\n\t[] (s=3) -> (s'=5);\r\n\t[] (s=4) -> (s'=5);\r\n\t[] (s=5) -> (s'=5);\r\n\t\r\nendmodule\r\n\r\nlabel \"a\" = s=3;\r\nlabel \"b\" = s=2 | s=5;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl-fair/Bai98-ex9.4.12-p239.nm.fair.props",
    "content": "\t// RESULT: 0.5\n\tPmin=? [ F (\"a\" & (X \"b\")) ];\n\t// RESULT: 0.5\n\tPmax=? [ F (\"a\" & (X \"b\")) ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl-fair/Bai98-ex9.4.12-p239.nm.fair.props.args",
    "content": "-fair\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl-fair/Bai98-remark9.4.13-p240.nm",
    "content": "// another simple LTL example from Christel's thesis (p.240)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\ts : [1..3];\r\n\t\r\n\t// s\r\n\t[] (s=1) -> (s'=2);\r\n\t[] (s=1) -> (s'=3);\r\n\t// t\r\n\t[] (s=2) -> (s'=1);\r\n\t// u\r\n\t[] (s=3) -> (s'=3);\r\n\t\r\nendmodule\r\n\r\nlabel \"a\" = s=1 | s=2;\r\nlabel \"b\" = s=2;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl-fair/Bai98-remark9.4.13-p240.nm.fair.props",
    "content": "\t// RESULT: 0\n\tPmin=? [ (X \"b\") => (G \"a\") ];\n\t// RESULT: 1\n\tPmax=? [ (X \"b\") => (G \"a\") ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/ltl-fair/Bai98-remark9.4.13-p240.nm.fair.props.args",
    "content": "-fair\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/bug1.nm",
    "content": "// minimal model\n// showing bug inadvertently fixed in svn rev 10846\n// [from Joachim/Linda]\n\nmdp\n\nmodule a\n\ns: [0..2] init 0;\n\n[b] (s = 0) -> 0.4: (s' = 1) + 0.6: (s' = 2);\n[c] (s > 0) -> true;\n\nendmodule \n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/bug1.nm.props",
    "content": "// RESULT: 0.6\nmulti(Pmin=? [(F s=2)], P>=0 [true])\n\n// RESULT: 0.6\nmulti(Pmin=? [F s=2], P>=0 [true])\n\n// RESULT: 1.0\nmulti(Pmax=? [true], P>=0.01 [true]) \n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/bug1.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi3.nm",
    "content": "// POLYNOMIAL RANDOMIZED CONSENSUS [AH90]\r\n// three processes and three rounds\r\n// multi-objective model\r\n// gxn/dxp 01/10/09\r\n\r\nmdp\r\n\r\nconst int MAX=3;\r\n\r\n// need to turn these into local copies later so the reading phase is complete?\r\nformula leaders_agree1 = (p1=1 | r1<max(r1,r2,r3)) & (p2=1 | r2<max(r1,r2,r3)) & (p3=1 | r3<max(r1,r2,r3));\r\nformula leaders_agree2 = (p1=2 | r1<max(r1,r2,r3)) & (p2=2 | r2<max(r1,r2,r3)) & (p3=2 | r3<max(r1,r2,r3));\r\n\r\nformula decide1 = leaders_agree1 & (p1=1 | r1<max(r1,r2,r3)-1) & (p2=1 | r2<max(r1,r2,r3)-1) & (p3=1 | r3<max(r1,r2,r3)-1);\r\nformula decide2 = leaders_agree2 & (p1=2 | r1<max(r1,r2,r3)-1) & (p2=2 | r2<max(r1,r2,r3)-1) & (p3=2 | r3<max(r1,r2,r3)-1);\r\n\r\nmodule process1\r\n\r\n\ts1 : [0..5]; // local state\r\n\t// 0 initialise/read registers\r\n\t// 1 finish reading registers (make a decision)\r\n\t// 1 warn of change\r\n\t// 2 enter shared coin protocol\r\n\t// 4 finished\r\n\t// 5 error (reached max round and cannot decide)\r\n\tr1 : [0..MAX]; // round of the process\r\n\tp1 : [0..2]; // preference (0 corresponds to null)\r\n\r\n\t// nondeterministic choice as to initial preference\r\n\t[] s1=0 & r1=0 -> (p1'=1) & (r1'=1);\r\n\t[] s1=0 & r1=0 -> (p1'=2) & (r1'=1);\r\n\t\r\n\t// read registers (currently does nothing because read vs from other processes\r\n\t[] s1=0 & r1>0 & r1<=MAX -> (s1'=1);\r\n\t// maxke a decision\r\n\t[] s1=1 & decide1 -> (s1'=4) & (p1'=1);\r\n\t[] s1=1 & decide2 -> (s1'=4) & (p1'=2);\r\n\t[] s1=1 & r1<MAX & leaders_agree1 & !decide1 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[] s1=1 & r1<MAX & leaders_agree2 & !decide2 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[] s1=1 & r1<MAX & !(leaders_agree1 | leaders_agree2) -> (s1'=2) & (p1'=0);\r\n\t[] s1=1 & r1=MAX & !(decide1 | decide2) -> (s1'=5); // run out of rounds so error\r\n\t// enter the coin procotol for the current round\r\n\t[coin1_s1_start] s1=2 & r1=1 -> (s1'=3);\r\n\t[coin2_s1_start] s1=2 & r1=2 -> (s1'=3);\r\n\t// get response from the coin protocol\r\n\t[coin1_s1_p1] s1=3 & r1=1 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[coin1_s1_p2] s1=3 & r1=1 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[coin2_s1_end] s1=3 & r1=2 -> (s1'=0) & (r1'=r1+1);\r\n\t// done so loop\r\n\t[done] s1>=4 -> true; \r\n\r\nendmodule\r\n\r\nmodule process2 = process1[ s1=s2,\r\n\t\t\t\t\t\t\t\t\t\t\tp1=p2,p2=p3,p3=p1,\r\n\t\t\t\t\t\t\t\t\t\t\tr1=r2,r2=r3,r3=r1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_start=coin1_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_start=coin2_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p1=coin1_s2_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p2=coin1_s2_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_end=coin2_s2_end ]\r\nendmodule\r\n\r\nmodule process3 = process1[ s1=s3,\r\n\t\t\t\t\t\t\t\t\t\t\tp1=p3,p2=p1,p3=p2,\r\n\t\t\t\t\t\t\t\t\t\t\tr1=r3,r2=r1,r3=r2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_start=coin1_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_start=coin2_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p1=coin1_s3_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p2=coin1_s3_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_end=coin2_s3_end ]\r\nendmodule\r\n\r\nmodule coin1_error\r\n\t\r\n\tc1 : [0..1]; // 1 is the error state\r\n\tv1 : [0..2]; // value of the coin returned the first time\r\n\t\r\n\t// first returned value (any processes)\r\n\t[coin1_s1_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s2_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s3_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s1_p2] v1=0 -> (v1'=2);\r\n\t[coin1_s2_p2] v1=0 -> (v1'=2);\r\n\t[coin1_s3_p2] v1=0 -> (v1'=2);\r\n\t// later values returned\r\n\t[coin1_s1_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s2_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s3_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s1_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s2_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s3_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s1_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s2_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s3_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s1_p2] v1=1 -> (c1'=1); // error\r\n\t[coin1_s2_p2] v1=1 -> (c1'=1); // error\r\n\t[coin1_s3_p2] v1=1 -> (c1'=1); // error\r\n\r\nendmodule\r\n\r\n// coin 3 is of no use because of number of rounds\r\n\r\n// expected number of steps\r\nrewards \"steps\"\r\n\t[] true : 1;\r\n\r\n\t[coin1_s1_start] true : 1;\r\n\t[coin1_s2_start] true : 1;\r\n\t[coin1_s3_start] true : 1;\r\n\t[coin1_s1_p1] true : 1;\r\n\t[coin1_s1_p2] true : 1;\r\n\t[coin1_s2_p1] true : 1;\r\n\t[coin1_s2_p2] true : 1;\r\n\t[coin1_s3_p1] true : 1;\r\n\t[coin1_s3_p2] true : 1;\r\n\r\n\t[coin2_s1_start] true : 1;\r\n\t[coin2_s2_start] true : 1;\r\n\t[coin2_s3_start] true : 1;\r\n\t[coin2_s1_end] true : 1;\r\n\t[coin2_s2_end] true : 1;\r\n\t[coin2_s3_end] true : 1;\r\n\r\nendrewards"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi3.nm.props",
    "content": "// RESULT: 23.312188395624954\nmulti ( Rmax=? [ C ] , P>=1-0.031218839562495434 [ G (c1=0) ] )\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi3.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi4.nm",
    "content": "// POLYNOMIAL RANDOMIZED CONSENSUS [AH90]\r\n// three processes and four rounds\r\n// multi-objective model\r\n// gxn/dxp 01/10/09\r\n\r\nmdp\r\n\r\nconst int MAX=4;\r\n\r\n// need to turn these into local copies later so the reading phase is complete?\r\nformula leaders_agree1 = (p1=1 | r1<max(r1,r2,r3)) & (p2=1 | r2<max(r1,r2,r3)) & (p3=1 | r3<max(r1,r2,r3));\r\nformula leaders_agree2 = (p1=2 | r1<max(r1,r2,r3)) & (p2=2 | r2<max(r1,r2,r3)) & (p3=2 | r3<max(r1,r2,r3));\r\n\r\nformula decide1 = leaders_agree1 & (p1=1 | r1<max(r1,r2,r3)-1) & (p2=1 | r2<max(r1,r2,r3)-1) & (p3=1 | r3<max(r1,r2,r3)-1);\r\nformula decide2 = leaders_agree2 & (p1=2 | r1<max(r1,r2,r3)-1) & (p2=2 | r2<max(r1,r2,r3)-1) & (p3=2 | r3<max(r1,r2,r3)-1);\r\n\r\nmodule process1\r\n\r\n\ts1 : [0..5]; // local state\r\n\t// 0 initialise/read registers\r\n\t// 1 finish reading registers (make a decision)\r\n\t// 1 warn of change\r\n\t// 2 enter shared coin protocol\r\n\t// 4 finished\r\n\t// 5 error (reached max round and cannot decide)\r\n\tr1 : [0..MAX]; // round of the process\r\n\tp1 : [0..2]; // preference (0 corresponds to null)\r\n\r\n\t// nondeterministic choice as to initial preference\r\n\t[] s1=0 & r1=0 -> (p1'=1) & (r1'=1);\r\n\t[] s1=0 & r1=0 -> (p1'=2) & (r1'=1);\r\n\t\r\n\t// read registers (currently does nothing because read vs from other processes\r\n\t[] s1=0 & r1>0 & r1<=MAX -> (s1'=1);\r\n\t// maxke a decision\r\n\t[] s1=1 & decide1 -> (s1'=4) & (p1'=1);\r\n\t[] s1=1 & decide2 -> (s1'=4) & (p1'=2);\r\n\t[] s1=1 & r1<MAX & leaders_agree1 & !decide1 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[] s1=1 & r1<MAX & leaders_agree2 & !decide2 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[] s1=1 & r1<MAX & !(leaders_agree1 | leaders_agree2) -> (s1'=2) & (p1'=0);\r\n\t[] s1=1 & r1=MAX & !(decide1 | decide2) -> (s1'=5); // run out of rounds so error\r\n\t// enter the coin procotol for the current round\r\n\t[coin1_s1_start] s1=2 & r1=1 -> (s1'=3);\r\n\t[coin2_s1_start] s1=2 & r1=2 -> (s1'=3);\r\n\t[coin3_s1_start] s1=2 & r1=3 -> (s1'=3);\r\n\t// get response from the coin protocol\r\n\t[coin1_s1_p1] s1=3 & r1=1 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[coin1_s1_p2] s1=3 & r1=1 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[coin2_s1_p1] s1=3 & r1=2 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[coin2_s1_p2] s1=3 & r1=2 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[coin3_s1_end] s1=3 & r1=3 -> (s1'=0) & (r1'=r1+1);\r\n\t// done so loop\r\n\t[done] s1>=4 -> true; \r\n\r\nendmodule\r\n\r\nmodule process2 = process1[ s1=s2,\r\n\t\t\t\t\t\t\t\t\t\t\tp1=p2,p2=p3,p3=p1,\r\n\t\t\t\t\t\t\t\t\t\t\tr1=r2,r2=r3,r3=r1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_start=coin1_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_start=coin2_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_start=coin3_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p1=coin1_s2_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_p1=coin2_s2_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p2=coin1_s2_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_p2=coin2_s2_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_end=coin3_s2_end ]\r\nendmodule\r\n\r\nmodule process3 = process1[ s1=s3,\r\n\t\t\t\t\t\t\t\t\t\t\tp1=p3,p2=p1,p3=p2,\r\n\t\t\t\t\t\t\t\t\t\t\tr1=r3,r2=r1,r3=r2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_start=coin1_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_start=coin2_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_start=coin3_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p1=coin1_s3_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_p1=coin2_s3_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p2=coin1_s3_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_p2=coin2_s3_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_end=coin3_s3_end ]\r\nendmodule\r\n\r\nmodule coin1_error\r\n\t\r\n\tc1 : [0..1]; // 1 is the error state\r\n\tv1 : [0..2]; // value of the coin returned the first time\r\n\t\r\n\t// first returned value (any processes)\r\n\t[coin1_s1_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s2_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s3_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s1_p2] v1=0 -> (v1'=2);\r\n\t[coin1_s2_p2] v1=0 -> (v1'=2);\r\n\t[coin1_s3_p2] v1=0 -> (v1'=2);\r\n\t// later values returned\r\n\t[coin1_s1_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s2_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s3_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s1_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s2_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s3_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s1_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s2_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s3_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s1_p2] v1=1 -> (c1'=1); // error\r\n\t[coin1_s2_p2] v1=1 -> (c1'=1); // error\r\n\t[coin1_s3_p2] v1=1 -> (c1'=1); // error\r\n\r\nendmodule\r\n\r\nmodule coin2_error\r\n\t\r\n\tc2 : [0..1]; // 1 is the error state\r\n\tv2 : [0..2]; // value of the coin returned the first time\r\n\t\r\n\t// first returned value (any processes)\r\n\t[coin2_s1_p1] v2=0 -> (v2'=1);\r\n\t[coin2_s2_p1] v2=0 -> (v2'=1);\r\n\t[coin2_s3_p1] v2=0 -> (v2'=1);\r\n\t[coin2_s1_p2] v2=0 -> (v2'=2);\r\n\t[coin2_s2_p2] v2=0 -> (v2'=2);\r\n\t[coin2_s3_p2] v2=0 -> (v2'=2);\r\n\t// later values returned\r\n\t[coin2_s1_p1] v2=1 -> true; // good behaviour\r\n\t[coin2_s2_p1] v2=1 -> true; // good behaviour\r\n\t[coin2_s3_p1] v2=1 -> true; // good behaviour\r\n\t[coin2_s1_p2] v2=2 -> true; // good behaviour\r\n\t[coin2_s2_p2] v2=2 -> true; // good behaviour\r\n\t[coin2_s3_p2] v2=2 -> true; // good behaviour\r\n\t[coin2_s1_p1] v2=2 -> (c2'=1); // error\r\n\t[coin2_s2_p1] v2=2 -> (c2'=1); // error\r\n\t[coin2_s3_p1] v2=2 -> (c2'=1); // error\r\n\t[coin2_s1_p2] v2=1 -> (c2'=1); // error\r\n\t[coin2_s2_p2] v2=1 -> (c2'=1); // error\r\n\t[coin2_s3_p2] v2=1 -> (c2'=1); // error\r\n\r\nendmodule\r\n\r\n// coin 3 is of no use because of number of rounds\r\n\r\n// expected number of steps\r\nrewards \"steps\"\r\n\t[] true : 1;\r\n\r\n\t[coin1_s1_start] true : 1;\r\n\t[coin1_s2_start] true : 1;\r\n\t[coin1_s3_start] true : 1;\r\n\t[coin1_s1_p1] true : 1;\r\n\t[coin1_s1_p2] true : 1;\r\n\t[coin1_s2_p1] true : 1;\r\n\t[coin1_s2_p2] true : 1;\r\n\t[coin1_s3_p1] true : 1;\r\n\t[coin1_s3_p2] true : 1;\r\n\r\n\t[coin2_s1_start] true : 1;\r\n\t[coin2_s2_start] true : 1;\r\n\t[coin2_s3_start] true : 1;\r\n\t[coin2_s1_p1] true : 1;\r\n\t[coin2_s1_p2] true : 1;\r\n\t[coin2_s2_p1] true : 1;\r\n\t[coin2_s2_p2] true : 1;\r\n\t[coin2_s3_p1] true : 1;\r\n\t[coin2_s3_p2] true : 1;\r\n\r\n\t[coin3_s1_start] true : 1;\r\n\t[coin3_s2_start] true : 1;\r\n\t[coin3_s3_start] true : 1;\r\n\t[coin3_s1_end] true : 1;\r\n\t[coin3_s2_end] true : 1;\r\n\t[coin3_s3_end] true : 1;\r\n\r\nendrewards"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi4.nm.props",
    "content": "// RESULT: 28.039952620073397\nmulti ( Rmax=? [ C ] , P>=1-0.22908875545788154 [ G (c1=0) ] ,  P>=1-0.22908875545788154 [ G (c2=0) ] )\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi4.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi5.nm",
    "content": "// POLYNOMIAL RANDOMIZED CONSENSUS [AH90]\r\n// three processes and five rounds\r\n// multi-objective model\r\n// gxn/dxp 01/10/09\r\n\r\nmdp\r\n\r\nconst int MAX=5;\r\n\r\n// need to turn these into local copies later so the reading phase is complete?\r\nformula leaders_agree1 = (p1=1 | r1<max(r1,r2,r3)) & (p2=1 | r2<max(r1,r2,r3)) & (p3=1 | r3<max(r1,r2,r3));\r\nformula leaders_agree2 = (p1=2 | r1<max(r1,r2,r3)) & (p2=2 | r2<max(r1,r2,r3)) & (p3=2 | r3<max(r1,r2,r3));\r\n\r\nformula decide1 = leaders_agree1 & (p1=1 | r1<max(r1,r2,r3)-1) & (p2=1 | r2<max(r1,r2,r3)-1) & (p3=1 | r3<max(r1,r2,r3)-1);\r\nformula decide2 = leaders_agree2 & (p1=2 | r1<max(r1,r2,r3)-1) & (p2=2 | r2<max(r1,r2,r3)-1) & (p3=2 | r3<max(r1,r2,r3)-1);\r\n\r\nmodule process1\r\n\r\n\ts1 : [0..5]; // local state\r\n\t// 0 initialise/read registers\r\n\t// 1 finish reading registers (make a decision)\r\n\t// 1 warn of change\r\n\t// 2 enter shared coin protocol\r\n\t// 4 finished\r\n\t// 5 error (reached max round and cannot decide)\r\n\tr1 : [0..MAX]; // round of the process\r\n\tp1 : [0..2]; // preference (0 corresponds to null)\r\n\r\n\t// nondeterministic choice as to initial preference\r\n\t[] s1=0 & r1=0 -> (p1'=1) & (r1'=1);\r\n\t[] s1=0 & r1=0 -> (p1'=2) & (r1'=1);\r\n\t\r\n\t// read registers (currently does nothing because read vs from other processes\r\n\t[] s1=0 & r1>0 & r1<=MAX -> (s1'=1);\r\n\t// maxke a decision\r\n\t[] s1=1 & decide1 -> (s1'=4) & (p1'=1);\r\n\t[] s1=1 & decide2 -> (s1'=4) & (p1'=2);\r\n\t[] s1=1 & r1<MAX & leaders_agree1 & !decide1 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[] s1=1 & r1<MAX & leaders_agree2 & !decide2 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[] s1=1 & r1<MAX & !(leaders_agree1 | leaders_agree2) -> (s1'=2) & (p1'=0);\r\n\t[] s1=1 & r1=MAX & !(decide1 | decide2) -> (s1'=5); // run out of rounds so error\r\n\t// enter the coin procotol for the current round\r\n\t[coin1_s1_start] s1=2 & r1=1 -> (s1'=3);\r\n\t[coin2_s1_start] s1=2 & r1=2 -> (s1'=3);\r\n\t[coin3_s1_start] s1=2 & r1=3 -> (s1'=3);\r\n\t[coin4_s1_start] s1=2 & r1=4 -> (s1'=3);\r\n\t// get response from the coin protocol\r\n\t[coin1_s1_p1] s1=3 & r1=1 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[coin1_s1_p2] s1=3 & r1=1 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[coin2_s1_p1] s1=3 & r1=2 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[coin2_s1_p2] s1=3 & r1=2 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[coin3_s1_p1] s1=3 & r1=3 -> (s1'=0) & (p1'=1) & (r1'=r1+1);\r\n\t[coin3_s1_p2] s1=3 & r1=3 -> (s1'=0) & (p1'=2) & (r1'=r1+1);\r\n\t[coin4_s1_end] s1=3 & r1=4 -> (s1'=0) & (r1'=r1+1);\r\n\t// done so loop\r\n\t[done] s1>=4 -> true; \r\n\r\nendmodule\r\n\r\nmodule process2 = process1[ s1=s2,\r\n\t\t\t\t\t\t\t\t\t\t\tp1=p2,p2=p3,p3=p1,\r\n\t\t\t\t\t\t\t\t\t\t\tr1=r2,r2=r3,r3=r1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_start=coin1_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_start=coin2_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_start=coin3_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin4_s1_start=coin4_s2_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p1=coin1_s2_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_p1=coin2_s2_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_p1=coin3_s2_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p2=coin1_s2_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_p2=coin2_s2_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_p2=coin3_s2_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin4_s1_end=coin4_s2_end ]\r\nendmodule\r\n\r\nmodule process3 = process1[ s1=s3,\r\n\t\t\t\t\t\t\t\t\t\t\tp1=p3,p2=p1,p3=p2,\r\n\t\t\t\t\t\t\t\t\t\t\tr1=r3,r2=r1,r3=r2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_start=coin1_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_start=coin2_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_start=coin3_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin4_s1_start=coin4_s3_start,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p1=coin1_s3_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_p1=coin2_s3_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_p1=coin3_s3_p1,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin1_s1_p2=coin1_s3_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin2_s1_p2=coin2_s3_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin3_s1_p2=coin3_s3_p2,\r\n\t\t\t\t\t\t\t\t\t\t\tcoin4_s1_end=coin4_s3_end ]\r\nendmodule\r\n\r\nmodule coin1_error\r\n\t\r\n\tc1 : [0..1]; // 1 is the error state\r\n\tv1 : [0..2]; // value of the coin returned the first time\r\n\t\r\n\t// first returned value (any processes)\r\n\t[coin1_s1_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s2_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s3_p1] v1=0 -> (v1'=1);\r\n\t[coin1_s1_p2] v1=0 -> (v1'=2);\r\n\t[coin1_s2_p2] v1=0 -> (v1'=2);\r\n\t[coin1_s3_p2] v1=0 -> (v1'=2);\r\n\t// later values returned\r\n\t[coin1_s1_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s2_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s3_p1] v1=1 -> true; // good behaviour\r\n\t[coin1_s1_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s2_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s3_p2] v1=2 -> true; // good behaviour\r\n\t[coin1_s1_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s2_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s3_p1] v1=2 -> (c1'=1); // error\r\n\t[coin1_s1_p2] v1=1 -> (c1'=1); // error\r\n\t[coin1_s2_p2] v1=1 -> (c1'=1); // error\r\n\t[coin1_s3_p2] v1=1 -> (c1'=1); // error\r\n\r\nendmodule\r\n\r\nmodule coin2_error\r\n\t\r\n\tc2 : [0..1]; // 1 is the error state\r\n\tv2 : [0..2]; // value of the coin returned the first time\r\n\t\r\n\t// first returned value (any processes)\r\n\t[coin2_s1_p1] v2=0 -> (v2'=1);\r\n\t[coin2_s2_p1] v2=0 -> (v2'=1);\r\n\t[coin2_s3_p1] v2=0 -> (v2'=1);\r\n\t[coin2_s1_p2] v2=0 -> (v2'=2);\r\n\t[coin2_s2_p2] v2=0 -> (v2'=2);\r\n\t[coin2_s3_p2] v2=0 -> (v2'=2);\r\n\t// later values returned\r\n\t[coin2_s1_p1] v2=1 -> true; // good behaviour\r\n\t[coin2_s2_p1] v2=1 -> true; // good behaviour\r\n\t[coin2_s3_p1] v2=1 -> true; // good behaviour\r\n\t[coin2_s1_p2] v2=2 -> true; // good behaviour\r\n\t[coin2_s2_p2] v2=2 -> true; // good behaviour\r\n\t[coin2_s3_p2] v2=2 -> true; // good behaviour\r\n\t[coin2_s1_p1] v2=2 -> (c2'=1); // error\r\n\t[coin2_s2_p1] v2=2 -> (c2'=1); // error\r\n\t[coin2_s3_p1] v2=2 -> (c2'=1); // error\r\n\t[coin2_s1_p2] v2=1 -> (c2'=1); // error\r\n\t[coin2_s2_p2] v2=1 -> (c2'=1); // error\r\n\t[coin2_s3_p2] v2=1 -> (c2'=1); // error\r\n\r\nendmodule\r\n\r\nmodule coin3_error\r\n\t\r\n\tc3 : [0..1]; // 1 is the error state\r\n\tv3 : [0..2]; // value of the coin returned the first time\r\n\r\n\t// first returned value (any processes)\r\n\t[coin3_s1_p1] v3=0 -> (v3'=1);\r\n\t[coin3_s2_p1] v3=0 -> (v3'=1);\r\n\t[coin3_s3_p1] v3=0 -> (v3'=1);\r\n\t[coin3_s1_p2] v3=0 -> (v3'=2);\r\n\t[coin3_s2_p2] v3=0 -> (v3'=2);\r\n\t[coin3_s3_p2] v3=0 -> (v3'=2);\r\n\t// later values returned\r\n\t[coin3_s1_p1] v3=1 -> true; // good behaviour\r\n\t[coin3_s2_p1] v3=1 -> true; // good behaviour\r\n\t[coin3_s3_p1] v3=1 -> true; // good behaviour\r\n\t[coin3_s1_p2] v3=2 -> true; // good behaviour\r\n\t[coin3_s2_p2] v3=2 -> true; // good behaviour\r\n\t[coin3_s3_p2] v3=2 -> true; // good behaviour\r\n\t[coin3_s1_p1] v3=2 -> (c3'=1); // error\r\n\t[coin3_s2_p1] v3=2 -> (c3'=1); // error\r\n\t[coin3_s3_p1] v3=2 -> (c3'=1); // error\r\n\t[coin3_s1_p2] v3=1 -> (c3'=1); // error\r\n\t[coin3_s2_p2] v3=1 -> (c3'=1); // error\r\n\t[coin3_s3_p2] v3=1 -> (c3'=1); // error\r\n\r\nendmodule\r\n\r\n// coin 4 is of no use because of number of rounds\r\n\r\n// expected number of steps\r\nrewards \"steps\"\r\n\t[] true : 1;\r\n\r\n\t[coin1_s1_start] true : 1;\r\n\t[coin1_s2_start] true : 1;\r\n\t[coin1_s3_start] true : 1;\r\n\t[coin1_s1_p1] true : 1;\r\n\t[coin1_s1_p2] true : 1;\r\n\t[coin1_s2_p1] true : 1;\r\n\t[coin1_s2_p2] true : 1;\r\n\t[coin1_s3_p1] true : 1;\r\n\t[coin1_s3_p2] true : 1;\r\n\r\n\t[coin2_s1_start] true : 1;\r\n\t[coin2_s2_start] true : 1;\r\n\t[coin2_s3_start] true : 1;\r\n\t[coin2_s1_p1] true : 1;\r\n\t[coin2_s1_p2] true : 1;\r\n\t[coin2_s2_p1] true : 1;\r\n\t[coin2_s2_p2] true : 1;\r\n\t[coin2_s3_p1] true : 1;\r\n\t[coin2_s3_p2] true : 1;\r\n\r\n\t[coin3_s1_start] true : 1;\r\n\t[coin3_s2_start] true : 1;\r\n\t[coin3_s3_start] true : 1;\r\n\t[coin3_s1_p1] true : 1;\r\n\t[coin3_s1_p2] true : 1;\r\n\t[coin3_s2_p1] true : 1;\r\n\t[coin3_s2_p2] true : 1;\r\n\t[coin3_s3_p1] true : 1;\r\n\t[coin3_s3_p2] true : 1;\r\n\r\n\t[coin4_s1_start] true : 1;\r\n\t[coin4_s2_start] true : 1;\r\n\t[coin4_s3_start] true : 1;\r\n\t[coin4_s1_end] true : 1;\r\n\t[coin4_s2_end] true : 1;\r\n\t[coin4_s3_end] true : 1;\r\n\r\nendrewards"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi5.nm.props",
    "content": "// RESULT: 30.789017685568002\nmulti ( Rmax=? [ C ] , P>=1-0.22908875545788154 [ G (c1=0) ] ,  P>=1-0.22908875545788154 [ G (c2=0) ] ,  P>=1-0.22908875545788154 [ G (c3=0) ] )\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/consensus_multi5.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple11.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..2];\r\n\r\n\t[] s=0 -> (s'=1);\r\n\t[] s=1 -> (s'=2);\r\n\t[] s=2 -> (s'=2);\r\n\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple11.nm.props",
    "content": "// RESULT: true\nmulti(P>=1 [ F s=1 ],P>=1 [ F s=2 ])\n\n// RESULT: false\nmulti(P>=0.4 [ G F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: false\nmulti(P>=0.4 [ F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: NaN\nmulti(Pmax=? [ F s=2 ],P>=0.6 [ G F s=1 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple11.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple11.pctl",
    "content": "multi(P>=1 [ F s=1 ], P>=1 [ F s=2 ])\r\nmulti(P>=1 [ !(F s=1) ], P>=1 [ F s=2 ])\r\nmulti(P>=0.4 [ G F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(P>=0.4 [ F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(Pmax=? [ F s=2], P>=0.6 [ G F s=1 ])\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple2.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..2];\r\n\tp : [0..2];\r\n\r\n\t[a] s=0 -> 0.4 : (s'=1) & (p'=0) + 0.6 : (s'=1) & (p'=1);\r\n\t[b] s=0 -> 0.5 : (s'=1) & (p'=1) + 0.5 : (s'=1) & (p'=2);\r\n\t[c] s=0 -> 0.8 : (s'=1) & (p'=2) + 0.2 : (s'=1) & (p'=0);\r\n\t[] s>0 -> true;\r\n\r\nendmodule\r\n\r\nrewards \"R1\"\r\n\r\n\t[a] s=0 : 1;\r\n\t[b] s=0 : 2;\r\n\t[c] s=0 : 3;\r\n\r\nendrewards\r\n\r\nrewards \"R2\"\r\n\r\n        [a] s=0 : 1;\r\n        [b] s=0 : 1;\r\n        [c] s=0 : 1;\r\n\r\nendrewards\r\n\r\n\r\nrewards \"R3\"\r\n\r\n        [a] s=0 : 3;\r\n        [b] s=0 : 2;\r\n        [c] s=0 : 1;\r\n\r\nendrewards\r\n\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple2.nm.props",
    "content": "\n// RESULT: 3.0\nmulti(R{\"R1\"}max=? [ C ],P>=0.4 [ F s=1&p=2 ])\n\n// RESULT: 1.8\nmulti(Rmax=? [ C ],P>=0.52 [ F s=1&p=1 ],P>=0.4 [ F s=1&p=2 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple2.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple2.pctl",
    "content": "//Pmax=? [ F s=1 & p=1 ]\r\n//Pmax=? [ F s=1 & p=2 ]\r\n\r\n//Pmax=? [ s=1 & p=1 U s=1 & p=2 ]\r\n\r\n//multi(Pmax=? [ F s=1 & p=1 ], P>=0.4 [ F s=1 & p=2 ])\r\n\r\n//multi(P>=0.5 [ F s=1 & p=1 ], P>=0.5 [ F s=1 & p=2 ])\r\n\r\nmulti(R{\"R1\"}min=? [F s=1], P>=0.4 [ F s=1 & p=2 ])\r\nmulti(R{\"R1\"}max=? [F s=1], P>=0.4 [ F s=1 & p=2 ])\r\nmulti(Rmax=? [ F s=1 ], P>=0.52 [ F s=1 & p=1 ], P>=0.4 [ F s=1 & p=2 ])\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple3.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..2];\r\n\tp : [0..2];\r\n\r\n\t[] s=0 & p=0 -> (s'=0) & (p'=1);\r\n\t[] s=0 & p=1 -> (s'=1) & (p'=1);\r\n\t[] s=0 & p=1 -> (s'=0) & (p'=2);\r\n\t[] s=0 & p=1 -> (s'=0) & (p'=1);\r\n\t[] s=0 & p=2 -> (s'=2) & (p'=2);\r\n\t[] s=0 & p=2 -> (s'=0) & (p'=2);\r\n\t[] s>0 -> true;\r\n\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple3.nm.props",
    "content": "// RESULT: true\nmulti(P>=0.4 [ F s=1&p=1 ],P>=0.6 [ F s=2&p=2 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple3.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple4.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..2];\r\n\r\n\t[a] s=0 -> (s'=1);\r\n\t[] s=1 -> (s'=1);\r\n\t[b] s=1 -> (s'=2);\r\n\t[] s=2 -> (s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"R1\"\r\n\t[a] s=0 : 1;\r\n\t[b] s=1 : 2;\r\nendrewards\r\n\r\nrewards \"R2\"\r\n\t[a] s=0 : 2;\r\n\t[b] s=1 : 1;\r\nendrewards\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple4.nm.props",
    "content": "// RESULT: 2.2\nmulti(R{\"R1\"}max=? [ C ],P>=0.4 [ G F s=1 ],P>=0.6 [ G F s=2 ])\n\n// RESULT: 2.2\nmulti(R{\"R1\"}max=? [ C ],P>=0.4 [ G F s=1 ],P>=0.4 [ G F s=2 ])\n\n// RESULT: 2.6\nmulti(R{\"R2\"}max=? [ C ],P>=0.4 [ G F s=1 ],P>=0.4 [ G F s=2 ])\n\n// RESULT: true\nmulti(P>=0.4 [ G F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: true\nmulti(P>=0.4 [ F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: 0.4\nmulti(Pmax=? [ F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: 1.0\nmulti(R{\"R1\"}min=? [ C ], R{\"R2\"}>=0 [ C ])\n\n// RESULT: 3.0\nmulti(R{\"R1\"}max=? [ C ], R{\"R2\"}>=0 [ C ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple4.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple4.pctl",
    "content": "multi(R{\"R1\"}max=? [F s=1], P>=0.4 [ G F s=1], P>=0.6 [ G F s=2 ])\r\nmulti(R{\"R1\"}max=? [F s=1], P>=0.4 [ G F s=1], P>=0.4 [ G F s=2 ])\r\nmulti(R{\"R1\"}min=? [F s=1], P>=0.4 [ G F s=1], P>=0.6 [ G F s=2 ])\r\nmulti(R{\"R1\"}min=? [F s=1], P>=0.4 [ G F s=1], P>=0.4 [ G F s=2 ])\r\nmulti(R{\"R2\"}max=? [F s=1], P>=0.4 [ G F s=1], P>=0.4 [ G F s=2 ])\r\nmulti(R{\"R2\"}max=? [F s=1], R{\"R1\"}<=2 [F s=1], P>=0.4 [ G F s=1], P>=0.4 [ G F s=2 ])\r\nmulti(P>=0.4 [ G F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(P>=0.4 [ F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(Pmax=? [ F s=2], P>=0.6 [ G F s=1 ])\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple5.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..3];\r\n\r\n\t[] s=0 -> (s'=1);\r\n\t[] s=1 -> (s'=1);\r\n\t[] s=1 -> (s'=2);\r\n\t[] s=2 -> (s'=2);\r\n\t[] s=2 -> (s'=3);\r\n\t[] s=3 -> (s'=3);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple5.nm.props",
    "content": "// RESULT: true\nmulti(P>=0.4 [ G F s=1 ],P>=0.6 [ G F s=2 ])\n\n// RESULT: true\nmulti(P>=0.4 [ G F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: true\nmulti(P>=0.4 [ F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: 0.4\nmulti(Pmax=? [ F s=2 ],P>=0.6 [ G F s=1 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple5.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple5.pctl",
    "content": "multi(P>=0.4 [ G F s=1], P>=0.6 [ G F s=2 ])\r\nmulti(P>=0.4 [ G F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(P>=0.4 [ F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(Pmax=? [ F s=2], P>=0.6 [ G F s=1 ])\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple6.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..4];\r\n\r\n\t[] s=0 -> (s'=1);\r\n\t[] s=1 -> (s'=2);\r\n\t[] s=2 -> (s'=3);\r\n\t[] s=3 -> 0.4:(s'=2)+0.6:(s'=4);\r\n\t[] s=4 -> (s'=1);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple6.nm.props",
    "content": "// RESULT: true\nmulti(P>=0.4 [ G F s=1 ],P>=0.6 [ G F s=2 ])\n\n// RESULT: true\nmulti(P>=0.4 [ G F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: true\nmulti(P>=0.4 [ F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: 1.0\nmulti(Pmax=? [ F s=2 ],P>=0.6 [ G F s=1 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple6.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple6.pctl",
    "content": "multi(P>=0.4 [ G F s=1], P>=0.6 [ G F s=2 ])\r\nmulti(P>=0.4 [ G F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(P>=0.4 [ F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(Pmax=? [ F s=2], P>=0.6 [ G F s=1 ])\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple7.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..5];\r\n\r\n\t[] s=0 -> (s'=1);\r\n\r\n\t[] s=1 -> (s'=2);\r\n\t[a] s=1 -> (s'=5);\r\n\r\n\t[] s=2 -> (s'=3);\r\n\r\n\t[] s=3 -> (s'=4);\r\n\t[] s=3 -> (s'=2);\r\n\r\n\t[] s=4 -> (s'=1);\r\n\r\n\t[] s=5 -> (s'=5);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple7.nm.props",
    "content": "// RESULT: true\nmulti(P>=0.6 [ F s=2 ],P>=0.6 [ G F s=2 ])\n\n// RESULT: true\nmulti(P>=0.4 [ G F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: true\nmulti(P>=0.4 [ F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: 1.0\nmulti(Pmax=? [ F s=2 ],P>=0.6 [ G F s=1 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple7.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple7.pctl",
    "content": "multi(P>=0.6 [ F s=2], P>=0.6 [ G F s=2 ])\r\nmulti(P>=0.4 [ G F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(P>=0.4 [ F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(Pmax=? [ F s=2], P>=0.6 [ G F s=1 ])\r\nPmax=? [ G F s=2 ]\r\nPmax=? [ G F s=4 ]\r\nmulti(Pmax=? [ G F s=2 ])\r\nfairness(SF({s=1}, {[a]}))"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple9.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..3];\r\n\r\n\t[] s=0 -> (s'=1);\r\n\r\n\t[] s=1 -> (s'=2);\r\n\t[a] s=1 -> 0.4:(s'=2) + 0.6:(s'=3);\r\n\r\n\t[b] s=2 -> (s'=1);\r\n\r\n\t[] s=3 -> (s'=3);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple9.nm.props",
    "content": "// RESULT: true\nmulti(P>=0.6 [ F s=2 ],P>=0.6 [ G F s=2 ])\n\n// RESULT: true\nmulti(P>=0.4 [ G F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: true\nmulti(P>=0.4 [ F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: 1.0\nmulti(Pmax=? [ F s=2 ],P>=0.6 [ G F s=1 ])\n\n// RESULT: 1.0\nmulti(Pmax=? [ G F s=2 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/simple9.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test-cumulative1.nm",
    "content": "// Simple example test for step-bounded cumulative reward\r\n// The model is in fact a MC\r\n// We also check -lp although it does not support the feature, but the testing ensures that an exception (and not a wrong result) is given.\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\nx:[0..4] init 0;\r\n\r\n[a] x=0 -> (x'=1);\r\n[b] x=0 -> (x'=2);\r\n[c] x=0 -> (x'=3);\r\n[d] x=1 -> (x'=4);\r\n[e] x=2 -> (x'=4);\r\n[f] x=3 -> (x'=4);\r\n[] x=4 -> (x'=4);\r\n\r\nendmodule\r\n\r\nrewards \"R1\"\r\n [a] true : 1;\r\n [c] true : 0.5;\r\n [d] true : 1;\r\n [e] true : 3;\r\n [f] true : 2.4;\r\nendrewards\r\n\r\nrewards \"R2\"\r\n [a] true : 1;\r\n [c] true : 1;\r\n [d] true : 1;\r\n [e] true : 1;\r\n [f] true : 1;\r\nendrewards\r\n\r\nrewards \"R3\"\r\n [b] true : 1;\r\nendrewards\r\n\r\nrewards \"R4\"\r\n [f] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test-cumulative1.nm.props",
    "content": "// RESULT: true\nmulti(R{\"R1\"}>=2.9[C<=2],R{\"R2\"}>=2[C<=2])\n\n// RESULT: false\nmulti(R{\"R1\"}>=3[C<=2],R{\"R2\"}>=2[C<=2])\n\n// RESULT: 2.9\nmulti(R{\"R1\"}max=?[C<=2],R{\"R2\"}>=2[C<=2])\n\n// RESULT: 1.0\nmulti(R{\"R1\"}max=?[C<=1],R{\"R2\"}>=2[C<=2])\n\n// RESULT: 0.5\nmulti(R{\"R2\"}max=?[C<=1],R{\"R1\"}>=2.95[C<=2])\n\n// RESULT: 0.4\nmulti(R{\"R4\"}max=?[C<=2],R{\"R1\"}>=0.5[C<=1],R{\"R3\"}>=0.3[C<=2])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test-cumulative1.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test1.nm",
    "content": "// simple example where the values of y_{v,sigma} are > 1\r\n// example formula: multi(P>=0.3[F x=3],P>=0.75[F x=2])\r\n// only two points: [0.6,0.4], [0.0,1.0] \r\n\r\nmodule M\r\n\r\nx:[0..3] init 0;\r\n\r\n[] x=0 -> (x'=1);\r\n[a] x=1 -> 0.4 : (x'=2) + 0.6: (x'=3);\r\n[b] x=1 -> (x'=2);\r\n[] x=2 -> (x'=2);\r\n[] x=3 -> (x'=3);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test1.nm.props",
    "content": "// RESULT: false\nmulti(P>=0.3[F x=3],P>=0.75[F x=2])\n\n// RESULT: 0.25\nmulti(Pmax=? [F x=3],P>=0.75[F x=2])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test1.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test2.nm",
    "content": "// simple example where the values of y_{v,sigma} are > 1\r\n// example formula: multi(P>=0.3[F x=2],P>=0.75[F x=3],P>=0.1[F x=4])  -- false\r\n// example formula: multi(P>=0.1[F x=3],P>=0.1[F x=2],P>=0.1[F x=4]) -- true\r\n// only two points: [0.1,0.1,1.0], [1.0,0.1,0.1], [0.2,0.2,0.2]\r\n\r\nmodule M\r\n\r\nx:[0..6] init 0;\r\n\r\n[] x=0 -> (x'=1);\r\n[a] x=1 -> 0.1 : (x'=5) + 0.9:(x'=2);\r\n[b] x=1 -> 0.1 : (x'=5) + 0.9:(x'=3);\r\n[c] x=1 -> 0.2 : (x'=2) + 0.2:(x'=3) + 0.2:(x'=4) + 0.4:(x'=6);\r\n[] x>1 -> true;\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test2.nm.props",
    "content": "// RESULT: false\nmulti(P>=0.3[F x=2],P>=0.75[F x=3],P>=0.1[F x=4])\n\n// RESULT: NaN\nmulti(Pmax=?[F x=2],P>=0.75[F x=3],P>=0.1[F x=4])\n\n// RESULT: true\nmulti(P>=0.1[F x=3],P>=0.1[F x=2],P>=0.1[F x=4])\n\n//RESULT: 0.55\nmulti(Pmax=?[F x=3],P>=0.1[F x=2],P>=0.1[F x=4])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test2.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test3.nm",
    "content": "// simple example where the values of y_{v,sigma} are > 1\r\n// example formula: multi(P>=0.3[F x=3],P>=0.75[F x=2])\r\n// only two points: [0.6,0.4], [0.0,1.0] \r\n\r\nmodule M\r\n\r\nx:[0..3] init 0;\r\n\r\n[a] x=0 -> (x'=1);\r\n[a] x=1 -> 0.4 : (x'=2) + 0.6: (x'=3);\r\n[b] x=1 -> (x'=2);\r\n[] x=2 -> (x'=2);\r\n[] x=3 -> (x'=3);\r\n\r\nendmodule\r\n\r\nrewards \"total_time\"\r\n    [a] true : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test3.nm.props",
    "content": "// RESULT: NaN\nmulti(Rmax=? [C], P>=0.3[F x=3],P>=0.75[F x=2])\n\n// RESULT: 1.833333333333333\nmulti(Rmax=? [C], P>=0.3[F x=3],P>=0.5[F x=2])\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-general/test3.nm.props.args",
    "content": "-lp\n-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple11.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..2];\r\n\r\n\t[] s=0 -> (s'=1);\r\n\t[] s=1 -> (s'=2);\r\n\t[] s=2 -> (s'=2);\r\n\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple11.nm.props",
    "content": "// RESULT: [(1,1)]\nmulti(Pmax=? [ F s=1 ],Pmax=? [ F s=2 ])\n\n// RESULT: [(1,0)]\nmulti(Pmax=? [ G F s=2 ],Pmax=? [ G F s=1 ])\n\n// RESULT: [(1,1))]\nmulti(Pmax=? [ F s=1 ],Pmin=? [ F s=2 ])\n\n// RESULT: [(1,1)]\nmulti(Pmin=? [ F s=1 ],Pmax=? [ F s=2 ])\n\n// RESULT: [(1,1)]\nmulti(Pmin=? [ F s=1 ],Pmin=? [ F s=2 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple11.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple11.pctl",
    "content": "multi(P>=1 [ F s=1 ], P>=1 [ F s=2 ])\r\nmulti(P>=1 [ !(F s=1) ], P>=1 [ F s=2 ])\r\nmulti(P>=0.4 [ G F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(P>=0.4 [ F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(Pmax=? [ F s=2], P>=0.6 [ G F s=1 ])\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple2.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..2];\r\n\tp : [0..2];\r\n\r\n\t[a] s=0 -> 0.4 : (s'=1) & (p'=0) + 0.6 : (s'=1) & (p'=1);\r\n\t[b] s=0 -> 0.5 : (s'=1) & (p'=1) + 0.5 : (s'=1) & (p'=2);\r\n\t[c] s=0 -> 0.8 : (s'=1) & (p'=2) + 0.2 : (s'=1) & (p'=0);\r\n\t[] s>0 -> true;\r\n\r\nendmodule\r\n\r\nrewards \"R1\"\r\n\r\n\t[a] s=0 : 1;\r\n\t[b] s=0 : 2;\r\n\t[c] s=0 : 3;\r\n\r\nendrewards\r\n\r\nrewards \"R2\"\r\n\r\n        [a] s=0 : 1;\r\n        [b] s=0 : 1;\r\n        [c] s=0 : 1;\r\n\r\nendrewards\r\n\r\n\r\nrewards \"R3\"\r\n\r\n        [a] s=0 : 3;\r\n        [b] s=0 : 2;\r\n        [c] s=0 : 1;\r\n\r\nendrewards\r\n\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple2.nm.props",
    "content": "// RESULT: [(3,0.8)]\nmulti(R{\"R1\"}max=? [ C ],Pmax=? [ F s=1&p=2 ])\n\n// RESULT: [(2.0,0.5),(3,0),(1,0.8)]\nmulti(R{\"R3\"}max=? [ C ],Pmax=? [ F s=1&p=2 ])\n\n// RESULT: [(1.0,0.8)]\nmulti(R{\"R3\"}min=? [ C ],Pmax=? [ F s=1&p=2 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple2.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple2.pctl",
    "content": "//Pmax=? [ F s=1 & p=1 ]\r\n//Pmax=? [ F s=1 & p=2 ]\r\n\r\n//Pmax=? [ s=1 & p=1 U s=1 & p=2 ]\r\n\r\n//multi(Pmax=? [ F s=1 & p=1 ], P>=0.4 [ F s=1 & p=2 ])\r\n\r\n//multi(P>=0.5 [ F s=1 & p=1 ], P>=0.5 [ F s=1 & p=2 ])\r\n\r\nmulti(R{\"R1\"}min=? [F s=1], P>=0.4 [ F s=1 & p=2 ])\r\nmulti(R{\"R1\"}max=? [F s=1], P>=0.4 [ F s=1 & p=2 ])\r\nmulti(Rmax=? [ F s=1 ], P>=0.52 [ F s=1 & p=1 ], P>=0.4 [ F s=1 & p=2 ])\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple3.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..2];\r\n\tp : [0..2];\r\n\r\n\t[] s=0 & p=0 -> (s'=0) & (p'=1);\r\n\t[] s=0 & p=1 -> (s'=1) & (p'=1);\r\n\t[] s=0 & p=1 -> (s'=0) & (p'=2);\r\n\t[] s=0 & p=1 -> (s'=0) & (p'=1);\r\n\t[] s=0 & p=2 -> (s'=2) & (p'=2);\r\n\t[] s=0 & p=2 -> (s'=0) & (p'=2);\r\n\t[] s>0 -> true;\r\n\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple3.nm.props",
    "content": "// RESULT: [(1,0),(0,1)]\nmulti(Pmax=? [ F s=1&p=1 ],Pmax=? [ F s=2&p=2 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple3.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple4.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..2];\r\n\r\n\t[a] s=0 -> (s'=1);\r\n\t[] s=1 -> (s'=1);\r\n\t[b] s=1 -> (s'=2);\r\n\t[] s=2 -> (s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"R1\"\r\n\t[a] s=0 : 1;\r\n\t[b] s=1 : 2;\r\nendrewards\r\n\r\nrewards \"R2\"\r\n\t[a] s=0 : 2;\r\n\t[b] s=1 : 1;\r\nendrewards\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple4.nm.props",
    "content": "// RESULT: [(3,1)]\nmulti(R{\"R1\"}max=? [ C ],Pmax=? [ G F s=2 ])\n\n// RESULT: [(1,1),(3,0)]\nmulti(R{\"R1\"}max=? [ C ],Pmax=? [ G F s=1 ])\n\n// RESULT: [(1,1),(3,0)]\nmulti(R{\"R1\"}min=? [ C ],Pmin=? [ G F s=1 ])\n\n// RESULT: [(1,0)]\nmulti(R{\"R1\"}min=? [ C ],Pmin=? [ G F s=2 ])\n\n// RESULT: [(0,1)]\nmulti(Pmin=? [ G F s=2 ],R{\"R1\"}min=? [ C ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple4.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple4.pctl",
    "content": "multi(R{\"R1\"}max=? [F s=1], P>=0.4 [ G F s=1], P>=0.6 [ G F s=2 ])\r\nmulti(R{\"R1\"}max=? [F s=1], P>=0.4 [ G F s=1], P>=0.4 [ G F s=2 ])\r\nmulti(R{\"R1\"}min=? [F s=1], P>=0.4 [ G F s=1], P>=0.6 [ G F s=2 ])\r\nmulti(R{\"R1\"}min=? [F s=1], P>=0.4 [ G F s=1], P>=0.4 [ G F s=2 ])\r\nmulti(R{\"R2\"}max=? [F s=1], P>=0.4 [ G F s=1], P>=0.4 [ G F s=2 ])\r\nmulti(R{\"R2\"}max=? [F s=1], R{\"R1\"}<=2 [F s=1], P>=0.4 [ G F s=1], P>=0.4 [ G F s=2 ])\r\nmulti(P>=0.4 [ G F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(P>=0.4 [ F s=2], P>=0.6 [ G F s=1 ])\r\nmulti(Pmax=? [ F s=2], P>=0.6 [ G F s=1 ])\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple9.nm",
    "content": "mdp\r\n\r\nmodule m\r\n\ts : [0..3];\r\n\r\n\t[] s=0 -> (s'=1);\r\n\r\n\t[] s=1 -> (s'=2);\r\n\t[a] s=1 -> 0.4:(s'=2) + 0.6:(s'=3);\r\n\r\n\t[b] s=2 -> (s'=1);\r\n\r\n\t[] s=3 -> (s'=3);\r\nendmodule\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple9.nm.props",
    "content": "// RESULT: [(1,1)]\nmulti(Pmax=? [ F s=2 ],Pmax=? [ G F s=1 ])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/simple9.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test1.nm",
    "content": "// simple example where the values of y_{v,sigma} are > 1\r\n// example formula: multi(P>=0.3[F x=3],P>=0.75[F x=2])\r\n// only two points: [0.6,0.4], [0.0,1.0] \r\n\r\nmodule M\r\n\r\nx:[0..3] init 0;\r\n\r\n[] x=0 -> (x'=1);\r\n[a] x=1 -> 0.4 : (x'=2) + 0.6: (x'=3);\r\n[b] x=1 -> (x'=2);\r\n[] x=2 -> (x'=2);\r\n[] x=3 -> (x'=3);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test1.nm.props",
    "content": "// RESULT: [(0,1),(0.6,0.4)]\nmulti(Pmax=? [F x=3],Pmax=? [F x=2])\n\n// RESULT: [(0,1),(0.6,0.4)]\nmulti(Pmin=? [F x=3],Pmin=? [F x=2])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test1.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test2.nm",
    "content": "// simple example where the values of y_{v,sigma} are > 1\r\n// example formula: multi(P>=0.3[F x=2],P>=0.75[F x=3],P>=0.1[F x=4])  -- false\r\n// example formula: multi(P>=0.1[F x=3],P>=0.1[F x=2],P>=0.1[F x=4]) -- true\r\n// only two points: [0.1,0.1,1.0], [1.0,0.1,0.1], [0.2,0.2,0.2]\r\n\r\nmodule M\r\n\r\nx:[0..6] init 0;\r\n\r\n[] x=0 -> (x'=1);\r\n[a] x=1 -> 0.1 : (x'=5) + 0.9:(x'=2);\r\n[b] x=1 -> 0.1 : (x'=5) + 0.9:(x'=3);\r\n[c] x=1 -> 0.2 : (x'=2) + 0.2:(x'=3) + 0.2:(x'=4) + 0.4:(x'=6);\r\n[] x>1 -> true;\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test2.nm.props",
    "content": "//RESULT: [(0.9,0.0),(0.0,0.9)]\nmulti(Pmax=?[F x=3],Pmax=?[F x=2])\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test2.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test3.nm",
    "content": "// simple example where the values of y_{v,sigma} are > 1\r\n// example formula: multi(P>=0.3[F x=3],P>=0.75[F x=2])\r\n// only two points: [0.6,0.4], [0.0,1.0] \r\n\r\nmodule M\r\n\r\nx:[0..3] init 0;\r\n\r\n[a] x=0 -> (x'=1);\r\n[a] x=1 -> 0.4 : (x'=2) + 0.6: (x'=3);\r\n[b] x=1 -> (x'=2);\r\n[] x=2 -> (x'=2);\r\n[] x=3 -> (x'=3);\r\n\r\nendmodule\r\n\r\nrewards \"total_time\"\r\n    [a] true : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test3.nm.props",
    "content": "// RESULT: [(2,0.6)]\nmulti(Rmax=? [C], Pmax=?[F x=3])\n\n// RESULT: [(0.6,2)]\nmulti(Pmax=?[F x=3], Rmax=? [C])\n\n\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/multi-pareto/test3.nm.props.args",
    "content": "-valiter\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/pctl/pctl-until.prism",
    "content": "mdp\n\nmodule M\n\n    s : [0..4] init 0;\n\n    [] s=0 -> 1:(s'=1);\n\n    // Nondeterministic choice at s=1 gives different probabilities\n    // for satisfying phi U target.\n    [] s=1 -> 0.6:(s'=2) + 0.4:(s'=3);\n    [] s=1 -> 0.2:(s'=2) + 0.8:(s'=4);\n\n    [] s=2 -> 1:(s'=2);\n    [] s=3 -> 1:(s'=3);\n    [] s=4 -> 1:(s'=4);\n\nendmodule\n\nlabel \"phi\" = s=0 | s=1 | s=3;\nlabel \"target\" = s=2;\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/pctl/pctl-until.prism.props",
    "content": "// RESULT: 0.6\nPmax=? [ \"phi\" U \"target\" ]\n\n// RESULT: 0.2\nPmin=? [ \"phi\" U \"target\" ]\n\n// RESULT: 0\nPmax=? [ s=1 U \"target\" ]\n\n// RESULT: 0\nPmin=? [ s=1 U \"target\" ]\n\n// RESULT: 0\nPmax=? [ \"phi\" U<=1 \"target\" ]\n\n// RESULT: 0.6\nPmax=? [ \"phi\" U<=2 \"target\" ]\n\n// RESULT: 0.2\nPmin=? [ \"phi\" U<=2 \"target\" ]\n\n// RESULT: 0\nPmax=? [ \"phi\" U<2 \"target\" ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/pctl/pctl-until.prism.props.args",
    "content": "-h\n-s\n-m\n-ex -valiter\n-ex -gs\n-ex -ii\n\n-h -nopre\n-s -nopre\n-m -nopre\n-ex -valiter -nopre\n-ex -gs -nopre\n-ex -ii -nopre\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/reach/mdp_simple.nm",
    "content": "// Simple MDP tests cases, used during development of stochastic game model checking\r\n\r\nmdp\r\n\r\nmodule m1\r\n\ts : [0..5];\r\n\tt : [0..2];\r\n\r\n\t[] s=0 & t=0 -> (s'=1);\r\n\t[] s=0 & t=0 -> 0.1 : (t'=1)&(s'=0) + 0.9 : (t'=2)&(s'=0);\r\n\r\n\t[] s=1 & t=0 -> (s'=2);\r\n\t[] s=1 & t=0 -> 0.2 : (t'=1)&(s'=0) + 0.8 : (t'=2)&(s'=0);\r\n\r\n\t[] s=2 & t=0 -> (s'=3);\r\n\t[] s=2 & t=0 -> 0.3 : (t'=1)&(s'=1) + 0.7 : (t'=2)&(s'=1);\r\n\r\n\t[] s=3 & t=0 -> (s'=4);\r\n\t[] s=3 & t=0 -> 0.4 : (t'=1)&(s'=0)+ 0.6 : (t'=2)&(s'=0);\r\n\r\n\t[] s=4 & t=0 -> (s'=5);\r\n\t[] s=4 & t=0 -> 0.5 : (t'=1)&(s'=0) + 0.5 : (t'=2)&(s'=0);\r\n\r\n\t[] s=5 & t=0 -> (t'=1)&(s'=0);\r\n\r\n\t[] t>0 -> true;\r\n\r\nendmodule\r\n\r\nrewards \r\n    mod(s,2)=0 : 1;\r\nendrewards"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/reach/mdp_simple.nm.props",
    "content": "// RESULT: 1.0\nPmax=? [ F t=1 {s=0&t=0} ]\n\n// RESULT: 0.1\nPmin=? [ F t=1 ]\n\n// RESULT: 3.0\nRmax=? [ F t>0 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/reach/mdp_simple.nm.props.args",
    "content": "-s\n-m\n-h\n-ex -valiter\n-ex -gs\n-ex -politer\n-ex -modpoliter\n-s -ii\n-m -ii\n-h -ii\n-ex -valiter -ii\n-ex -gs -ii\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/reach/safety-fig9.nm",
    "content": "// MDP M_1 (see Figure 9, p.34) and DFA A_A^err (see Figure 8, p.32)\r\n\r\nmdp\r\n\r\n// M_1\r\nmodule M1\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3] init 0;\r\n\r\n\t[detect]   s=0 -> 0.8:(s'=1) + 0.2:(s'=2);\r\n\t[warn]     s=1 -> (s'=2);\r\n\t[shutdown] s=2 -> (s'=3);\r\n\t[off]      s=3 -> true;\r\n\r\nendmodule\r\n\r\n// DFA A_A^err for property Phi_A (\"never shutdown before warn\")\r\nmodule A_A_err\r\n\r\n\t// q=i for state q_i\r\n\tq : [0..2] init 0;\r\n\r\n\t[warn]     q=0 -> (q'=1);\r\n\t[shutdown] q=0 -> (q'=2);\r\n\r\n\t[warn]     q>=1 -> true;\r\n\t[shutdown] q>=1 -> true;\r\n\t\r\nendmodule\r\n\r\n// Accepting states for A_A^err\r\nlabel \"A_A_err_acc\" = q=2;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/reach/safety-fig9.nm.props",
    "content": "// ex 13\n// RESULT: 0.8\n1- Pmax=? [ F \"A_A_err_acc\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/cosafe/nav.nm",
    "content": "mdp\n \nmodule M \n \ns:[0..31] init 0;\n \n[goto_ChargingPoint_WayPoint1] s=0 -> 1:(s'=1);\n[goto_WayPoint1_ChargingPoint] s=1 -> 1:(s'=0);\n[goto_WayPoint1_WayPoint2] s=1 -> 1:(s'=2);\n[goto_WayPoint1_WayPoint7] s=1 -> 1:(s'=7);\n[goto_WayPoint1_WayPoint8] s=1 -> 1:(s'=8);\n[goto_WayPoint1_WayPoint18] s=1 -> 1:(s'=18);\n[goto_WayPoint1_WayPoint19] s=1 -> 1:(s'=19);\n[goto_WayPoint2_WayPoint1] s=2 -> 1:(s'=1);\n[goto_WayPoint2_WayPoint3] s=2 -> 1:(s'=3);\n[goto_WayPoint2_WayPoint4] s=2 -> 1:(s'=4);\n[goto_WayPoint2_WayPoint6] s=2 -> 1:(s'=6);\n[goto_WayPoint2_WayPoint7] s=2 -> 1:(s'=7);\n[goto_WayPoint2_WayPoint18] s=2 -> 1:(s'=18);\n[goto_WayPoint2_WayPoint19] s=2 -> 1:(s'=19);\n[goto_WayPoint3_WayPoint2] s=3 -> 1:(s'=2);\n[goto_WayPoint3_WayPoint4] s=3 -> 1:(s'=4);\n[goto_WayPoint3_WayPoint6] s=3 -> 1:(s'=6);\n[goto_WayPoint4_WayPoint2] s=4 -> 1:(s'=2);\n[goto_WayPoint4_WayPoint3] s=4 -> 1:(s'=3);\n[goto_WayPoint4_WayPoint5] s=4 -> 1:(s'=5);\n[goto_WayPoint4_WayPoint6] s=4 -> 1:(s'=6);\n[goto_WayPoint4_WayPoint7] s=4 -> 1:(s'=7);\n[goto_WayPoint5_WayPoint4] s=5 -> 1:(s'=4);\n[goto_WayPoint6_WayPoint2] s=6 -> 1:(s'=2);\n[goto_WayPoint6_WayPoint3] s=6 -> 1:(s'=3);\n[goto_WayPoint6_WayPoint4] s=6 -> 1:(s'=4);\n[goto_WayPoint6_WayPoint19] s=6 -> 1:(s'=19);\n[goto_WayPoint7_WayPoint1] s=7 -> 1:(s'=1);\n[goto_WayPoint7_WayPoint2] s=7 -> 1:(s'=2);\n[goto_WayPoint7_WayPoint4] s=7 -> 1:(s'=4);\n[goto_WayPoint7_WayPoint8] s=7 -> 1:(s'=8);\n[goto_WayPoint7_WayPoint18] s=7 -> 1:(s'=18);\n[goto_WayPoint7_WayPoint19] s=7 -> 1:(s'=19);\n[goto_WayPoint8_WayPoint1] s=8 -> 1:(s'=1);\n[goto_WayPoint8_WayPoint7] s=8 -> 1:(s'=7);\n[goto_WayPoint8_WayPoint9] s=8 -> 1:(s'=9);\n[goto_WayPoint8_WayPoint17] s=8 -> 1:(s'=17);\n[goto_WayPoint9_WayPoint8] s=9 -> 1:(s'=8);\n[goto_WayPoint9_WayPoint10] s=9 -> 1:(s'=10);\n[goto_WayPoint9_WayPoint16] s=9 -> 1:(s'=16);\n[goto_WayPoint9_WayPoint17] s=9 -> 1:(s'=17);\n[goto_WayPoint10_WayPoint9] s=10 -> 1:(s'=9);\n[goto_WayPoint10_WayPoint11] s=10 -> 1:(s'=11);\n[goto_WayPoint10_WayPoint13] s=10 -> 1:(s'=13);\n[goto_WayPoint10_WayPoint16] s=10 -> 1:(s'=16);\n[goto_WayPoint11_WayPoint10] s=11 -> 1:(s'=10);\n[goto_WayPoint11_WayPoint12] s=11 -> 1:(s'=12);\n[goto_WayPoint11_WayPoint13] s=11 -> 1:(s'=13);\n[goto_WayPoint11_WayPoint15] s=11 -> 1:(s'=15);\n[goto_WayPoint11_WayPoint31] s=11 -> 1:(s'=31);\n[goto_WayPoint12_WayPoint11] s=12 -> 1:(s'=11);\n[goto_WayPoint12_WayPoint13] s=12 -> 1:(s'=13);\n[goto_WayPoint12_WayPoint31] s=12 -> 1:(s'=31);\n[goto_WayPoint13_WayPoint10] s=13 -> 1:(s'=10);\n[goto_WayPoint13_WayPoint11] s=13 -> 1:(s'=11);\n[goto_WayPoint13_WayPoint12] s=13 -> 1:(s'=12);\n[goto_WayPoint13_WayPoint14] s=13 -> 0.6:(s'=14) + 0.4:(s'=10);\n[goto_WayPoint14_WayPoint13] s=14 -> 1:(s'=13);\n[goto_WayPoint15_WayPoint10] s=15 -> 1:(s'=10);\n[goto_WayPoint15_WayPoint11] s=15 -> 1:(s'=11);\n[goto_WayPoint15_WayPoint16] s=15 -> 1:(s'=16);\n[goto_WayPoint15_WayPoint31] s=15 -> 1:(s'=31);\n[goto_WayPoint16_WayPoint9] s=16 -> 1:(s'=9);\n[goto_WayPoint16_WayPoint10] s=16 -> 1:(s'=10);\n[goto_WayPoint16_WayPoint15] s=16 -> 1:(s'=15);\n[goto_WayPoint16_WayPoint17] s=16 -> 1:(s'=17);\n[goto_WayPoint17_WayPoint8] s=17 -> 1:(s'=8);\n[goto_WayPoint17_WayPoint9] s=17 -> 1:(s'=9);\n[goto_WayPoint17_WayPoint16] s=17 -> 1:(s'=16);\n[goto_WayPoint17_WayPoint18] s=17 -> 1:(s'=18);\n[goto_WayPoint18_WayPoint1] s=18 -> 1:(s'=1);\n[goto_WayPoint18_WayPoint2] s=18 -> 1:(s'=2);\n[goto_WayPoint18_WayPoint7] s=18 -> 1:(s'=7);\n[goto_WayPoint18_WayPoint17] s=18 -> 1:(s'=17);\n[goto_WayPoint19_WayPoint1] s=19 -> 1:(s'=1);\n[goto_WayPoint19_WayPoint2] s=19 -> 1:(s'=2);\n[goto_WayPoint19_WayPoint6] s=19 -> 1:(s'=6);\n[goto_WayPoint19_WayPoint7] s=19 -> 1:(s'=7);\n[goto_WayPoint19_WayPoint20] s=19 -> 1:(s'=20);\n[goto_WayPoint20_WayPoint19] s=20 -> 1:(s'=19);\n[goto_WayPoint20_WayPoint21] s=20 -> 1:(s'=21);\n[goto_WayPoint20_WayPoint23] s=20 -> 1:(s'=23);\n[goto_WayPoint20_WayPoint24] s=20 -> 1:(s'=24);\n[goto_WayPoint20_WayPoint25] s=20 -> 1:(s'=25);\n[goto_WayPoint21_WayPoint20] s=21 -> 1:(s'=20);\n[goto_WayPoint21_WayPoint22] s=21 -> 1:(s'=22);\n[goto_WayPoint21_WayPoint23] s=21 -> 1:(s'=23);\n[goto_WayPoint21_WayPoint24] s=21 -> 1.0:(s'=24);\n[goto_WayPoint21_WayPoint25] s=21 -> 1:(s'=25);\n[goto_WayPoint21_WayPoint26] s=21 -> 1:(s'=26);\n[goto_WayPoint22_WayPoint21] s=22 -> 1:(s'=21);\n[goto_WayPoint22_WayPoint23] s=22 -> 1:(s'=23);\n[goto_WayPoint22_WayPoint24] s=22 -> 1:(s'=24);\n[goto_WayPoint22_WayPoint26] s=22 -> 1:(s'=26);\n[goto_WayPoint22_WayPoint27] s=22 -> 1:(s'=27);\n[goto_WayPoint23_WayPoint20] s=23 -> 1:(s'=20);\n[goto_WayPoint23_WayPoint21] s=23 -> 1:(s'=21);\n[goto_WayPoint23_WayPoint22] s=23 -> 1:(s'=22);\n[goto_WayPoint23_WayPoint24] s=23 -> 1:(s'=24);\n[goto_WayPoint23_WayPoint25] s=23 -> 1:(s'=25);\n[goto_WayPoint24_WayPoint20] s=24 -> 1:(s'=20);\n[goto_WayPoint24_WayPoint21] s=24 -> 1.0:(s'=21);\n[goto_WayPoint24_WayPoint22] s=24 -> 1:(s'=22);\n[goto_WayPoint24_WayPoint23] s=24 -> 1:(s'=23);\n[goto_WayPoint24_WayPoint25] s=24 -> 1:(s'=25);\n[goto_WayPoint25_WayPoint20] s=25 -> 1:(s'=20);\n[goto_WayPoint25_WayPoint21] s=25 -> 1:(s'=21);\n[goto_WayPoint25_WayPoint23] s=25 -> 1:(s'=23);\n[goto_WayPoint25_WayPoint24] s=25 -> 1:(s'=24);\n[goto_WayPoint26_WayPoint21] s=26 -> 1:(s'=21);\n[goto_WayPoint26_WayPoint22] s=26 -> 1:(s'=22);\n[goto_WayPoint26_WayPoint27] s=26 -> 1:(s'=27);\n[goto_WayPoint26_WayPoint28] s=26 -> 1:(s'=28);\n[goto_WayPoint27_WayPoint22] s=27 -> 1:(s'=22);\n[goto_WayPoint27_WayPoint26] s=27 -> 1:(s'=26);\n[goto_WayPoint27_WayPoint28] s=27 -> 1:(s'=28);\n[goto_WayPoint28_WayPoint26] s=28 -> 1:(s'=26);\n[goto_WayPoint28_WayPoint27] s=28 -> 1:(s'=27);\n[goto_WayPoint28_WayPoint29] s=28 -> 1:(s'=29);\n[goto_WayPoint29_WayPoint28] s=29 -> 1:(s'=28);\n[goto_WayPoint29_WayPoint30] s=29 -> 1:(s'=30);\n[goto_WayPoint30_WayPoint29] s=30 -> 1:(s'=29);\n[goto_WayPoint30_WayPoint31] s=30 -> 1:(s'=31);\n[goto_WayPoint31_WayPoint11] s=31 -> 1:(s'=11);\n[goto_WayPoint31_WayPoint15] s=31 -> 1:(s'=15);\n[goto_WayPoint31_WayPoint30] s=31 -> 1:(s'=30);\n[cheap_and_dangerous] s=0 -> 0.1:(s'=14) + 0.9:(s'=10);\n\nendmodule\n\nlabel \"ChargingPoint\" = s=0;\nlabel \"WayPoint1\" = s=1;\nlabel \"WayPoint2\" = s=2;\nlabel \"WayPoint3\" = s=3;\nlabel \"WayPoint4\" = s=4;\nlabel \"WayPoint5\" = s=5;\nlabel \"WayPoint6\" = s=6;\nlabel \"WayPoint7\" = s=7;\nlabel \"WayPoint8\" = s=8;\nlabel \"WayPoint9\" = s=9;\nlabel \"WayPoint10\" = s=10;\nlabel \"WayPoint11\" = s=11;\nlabel \"WayPoint12\" = s=12;\nlabel \"WayPoint13\" = s=13;\nlabel \"WayPoint14\" = s=14;\nlabel \"WayPoint15\" = s=15;\nlabel \"WayPoint16\" = s=16;\nlabel \"WayPoint17\" = s=17;\nlabel \"WayPoint18\" = s=18;\nlabel \"WayPoint19\" = s=19;\nlabel \"WayPoint20\" = s=20;\nlabel \"WayPoint21\" = s=21;\nlabel \"WayPoint22\" = s=22;\nlabel \"WayPoint23\" = s=23;\nlabel \"WayPoint24\" = s=24;\nlabel \"WayPoint25\" = s=25;\nlabel \"WayPoint26\" = s=26;\nlabel \"WayPoint27\" = s=27;\nlabel \"WayPoint28\" = s=28;\nlabel \"WayPoint29\" = s=29;\nlabel \"WayPoint30\" = s=30;\nlabel \"WayPoint31\" = s=31;\n\nrewards \"time\"\n    [goto_ChargingPoint_WayPoint1] s=0:20;\n    [goto_WayPoint1_ChargingPoint] s=1:20;\n    [goto_WayPoint1_WayPoint2] s=1:20;\n    [goto_WayPoint1_WayPoint7] s=1:20;\n    [goto_WayPoint1_WayPoint8] s=1:20;\n    [goto_WayPoint1_WayPoint18] s=1:20;\n    [goto_WayPoint1_WayPoint19] s=1:20;\n    [goto_WayPoint2_WayPoint1] s=2:20;\n    [goto_WayPoint2_WayPoint3] s=2:20;\n    [goto_WayPoint2_WayPoint4] s=2:20;\n    [goto_WayPoint2_WayPoint6] s=2:20;\n    [goto_WayPoint2_WayPoint7] s=2:20;\n    [goto_WayPoint2_WayPoint18] s=2:20;\n    [goto_WayPoint2_WayPoint19] s=2:20;\n    [goto_WayPoint3_WayPoint2] s=3:20;\n    [goto_WayPoint3_WayPoint4] s=3:20;\n    [goto_WayPoint3_WayPoint6] s=3:20;\n    [goto_WayPoint4_WayPoint2] s=4:20;\n    [goto_WayPoint4_WayPoint3] s=4:20;\n    [goto_WayPoint4_WayPoint5] s=4:20;\n    [goto_WayPoint4_WayPoint6] s=4:20;\n    [goto_WayPoint4_WayPoint7] s=4:20;\n    [goto_WayPoint5_WayPoint4] s=5:20;\n    [goto_WayPoint6_WayPoint2] s=6:20;\n    [goto_WayPoint6_WayPoint3] s=6:20;\n    [goto_WayPoint6_WayPoint4] s=6:20;\n    [goto_WayPoint6_WayPoint19] s=6:20;\n    [goto_WayPoint7_WayPoint1] s=7:20;\n    [goto_WayPoint7_WayPoint2] s=7:20;\n    [goto_WayPoint7_WayPoint4] s=7:20;\n    [goto_WayPoint7_WayPoint8] s=7:20;\n    [goto_WayPoint7_WayPoint18] s=7:20;\n    [goto_WayPoint7_WayPoint19] s=7:20;\n    [goto_WayPoint8_WayPoint1] s=8:20;\n    [goto_WayPoint8_WayPoint7] s=8:20;\n    [goto_WayPoint8_WayPoint9] s=8:20;\n    [goto_WayPoint8_WayPoint17] s=8:20;\n    [goto_WayPoint9_WayPoint8] s=9:20;\n    [goto_WayPoint9_WayPoint10] s=9:20;\n    [goto_WayPoint9_WayPoint16] s=9:20;\n    [goto_WayPoint9_WayPoint17] s=9:20;\n    [goto_WayPoint10_WayPoint9] s=10:20;\n    [goto_WayPoint10_WayPoint11] s=10:20;\n    [goto_WayPoint10_WayPoint13] s=10:20;\n    [goto_WayPoint10_WayPoint16] s=10:20;\n    [goto_WayPoint11_WayPoint10] s=11:20;\n    [goto_WayPoint11_WayPoint12] s=11:20;\n    [goto_WayPoint11_WayPoint13] s=11:20;\n    [goto_WayPoint11_WayPoint15] s=11:20;\n    [goto_WayPoint11_WayPoint31] s=11:20;\n    [goto_WayPoint12_WayPoint11] s=12:20;\n    [goto_WayPoint12_WayPoint13] s=12:20;\n    [goto_WayPoint12_WayPoint31] s=12:20;\n    [goto_WayPoint13_WayPoint10] s=13:20;\n    [goto_WayPoint13_WayPoint11] s=13:20;\n    [goto_WayPoint13_WayPoint12] s=13:20;\n    [goto_WayPoint13_WayPoint14] s=13:20;\n    [goto_WayPoint14_WayPoint13] s=14:20;\n    [goto_WayPoint15_WayPoint10] s=15:20;\n    [goto_WayPoint15_WayPoint11] s=15:20;\n    [goto_WayPoint15_WayPoint16] s=15:20;\n    [goto_WayPoint15_WayPoint31] s=15:20;\n    [goto_WayPoint16_WayPoint9] s=16:20;\n    [goto_WayPoint16_WayPoint10] s=16:20;\n    [goto_WayPoint16_WayPoint15] s=16:20;\n    [goto_WayPoint16_WayPoint17] s=16:20;\n    [goto_WayPoint17_WayPoint8] s=17:20;\n    [goto_WayPoint17_WayPoint9] s=17:20;\n    [goto_WayPoint17_WayPoint16] s=17:20;\n    [goto_WayPoint17_WayPoint18] s=17:20;\n    [goto_WayPoint18_WayPoint1] s=18:20;\n    [goto_WayPoint18_WayPoint2] s=18:20;\n    [goto_WayPoint18_WayPoint7] s=18:20;\n    [goto_WayPoint18_WayPoint17] s=18:20;\n    [goto_WayPoint19_WayPoint1] s=19:20;\n    [goto_WayPoint19_WayPoint2] s=19:20;\n    [goto_WayPoint19_WayPoint6] s=19:20;\n    [goto_WayPoint19_WayPoint7] s=19:20;\n    [goto_WayPoint19_WayPoint20] s=19:20;\n    [goto_WayPoint20_WayPoint19] s=20:20;\n    [goto_WayPoint20_WayPoint21] s=20:20;\n    [goto_WayPoint20_WayPoint23] s=20:20;\n    [goto_WayPoint20_WayPoint24] s=20:20;\n    [goto_WayPoint20_WayPoint25] s=20:20;\n    [goto_WayPoint21_WayPoint20] s=21:20;\n    [goto_WayPoint21_WayPoint22] s=21:20;\n    [goto_WayPoint21_WayPoint23] s=21:20;\n    [goto_WayPoint21_WayPoint24] s=21:6.122148;\n    [goto_WayPoint21_WayPoint25] s=21:20;\n    [goto_WayPoint21_WayPoint26] s=21:20;\n    [goto_WayPoint22_WayPoint21] s=22:20;\n    [goto_WayPoint22_WayPoint23] s=22:20;\n    [goto_WayPoint22_WayPoint24] s=22:20;\n    [goto_WayPoint22_WayPoint26] s=22:20;\n    [goto_WayPoint22_WayPoint27] s=22:20;\n    [goto_WayPoint23_WayPoint20] s=23:20;\n    [goto_WayPoint23_WayPoint21] s=23:20;\n    [goto_WayPoint23_WayPoint22] s=23:20;\n    [goto_WayPoint23_WayPoint24] s=23:20;\n    [goto_WayPoint23_WayPoint25] s=23:20;\n    [goto_WayPoint24_WayPoint20] s=24:20;\n    [goto_WayPoint24_WayPoint21] s=24:6.563777;\n    [goto_WayPoint24_WayPoint22] s=24:20;\n    [goto_WayPoint24_WayPoint23] s=24:20;\n    [goto_WayPoint24_WayPoint25] s=24:20;\n    [goto_WayPoint25_WayPoint20] s=25:20;\n    [goto_WayPoint25_WayPoint21] s=25:20;\n    [goto_WayPoint25_WayPoint23] s=25:20;\n    [goto_WayPoint25_WayPoint24] s=25:20;\n    [goto_WayPoint26_WayPoint21] s=26:20;\n    [goto_WayPoint26_WayPoint22] s=26:20;\n    [goto_WayPoint26_WayPoint27] s=26:20;\n    [goto_WayPoint26_WayPoint28] s=26:20;\n    [goto_WayPoint27_WayPoint22] s=27:20;\n    [goto_WayPoint27_WayPoint26] s=27:20;\n    [goto_WayPoint27_WayPoint28] s=27:20;\n    [goto_WayPoint28_WayPoint26] s=28:20;\n    [goto_WayPoint28_WayPoint27] s=28:20;\n    [goto_WayPoint28_WayPoint29] s=28:20;\n    [goto_WayPoint29_WayPoint28] s=29:20;\n    [goto_WayPoint29_WayPoint30] s=29:20;\n    [goto_WayPoint30_WayPoint29] s=30:20;\n    [goto_WayPoint30_WayPoint31] s=30:20;\n    [goto_WayPoint31_WayPoint11] s=31:20;\n    [goto_WayPoint31_WayPoint15] s=31:20;\n    [goto_WayPoint31_WayPoint30] s=31:20;\n    [cheap_and_dangerous] s=0:1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/cosafe/nav.nm.props",
    "content": "// RESULT: 1\nPmax=? [ (!\"WayPoint7\" U \"WayPoint14\") ]\n\n// RESULT: 61\nR{\"time\"}min=? [ (!\"WayPoint7\" U \"WayPoint14\") ]\n\n// RESULT: Infinity\nR{\"time\"}min=? [ (!\"WayPoint10\" U \"WayPoint14\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/cosafe/robot.nm",
    "content": "mdp\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/cosafe/robot.nm.cosafe.props",
    "content": "// RESULT: 1.2  //  = 1+(0.8*0+0.1*1+0.1*1)   \nRmin=? [ (F \"goal1\") | (F \"goal2\") ]\n\n// RESULT: 3.5\nRmax=? [ (F \"goal1\") | (F \"goal2\") ]\n\n// RESULT: 1.2\nRmin=? [ X F (\"goal1\" | \"goal2\") ]\n\n// RESULT: 1.2\nRmin=? [ F X (\"goal1\" | \"goal2\") ]\n\n// RESULT: 2\nRmin=? [ X X (\"goal1\" | \"goal2\") ]\n\n// RESULT: Infinity\nRmin=? [ X X \"goal2\" ]\n\n// RESULT: 19/15\nRmin=? [ F \"goal2\" ]\n\n// RESULT: 19/15\nRmin=? [ (F \"goal2\") ]\n\n// RESULT: 19/15\nRmin=? [ s!=3 U \"goal2\" ]\n\n// RESULT: Error:co-safe\nRmin=? [ F G \"goal1\" ]\n\n// RESULT: Error:co-safe\nRmax=? [ F G \"goal1\" ]\n\n// RESULT: Error:co-safe\nRmax=? [ (G !\"hazard\")&(G F \"goal1\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/mdp_rewards.nm",
    "content": "mdp\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\t\r\n\t[go]  s=0 -> (s'=1);\r\n\t[mix] s=0 -> 1/2:(s'=1) + 1/2:(s'=s);\r\n\t[go]  s=1 -> (s'=2);\r\n\t[mix] s=1 -> 1/2:(s'=2) + 1/2:(s'=s);\r\n\t[go]  s=2 -> (s'=3);\r\n\t[mix] s=2 -> 1/2:(s'=3) + 1/2:(s'=s);\r\n\t[go] s>2 -> true;\r\n\r\nendmodule\r\n\r\nrewards \"a\"\r\n\ts=0: 2;\r\n\t[go] s=0: 3;\r\n\ts=1: 5;\r\n\t[go] s=1: 7;\r\n\ts=2: 11;\r\nendrewards\r\n\r\nrewards \"b\"\r\n\ts=0: 2;\r\n\t[] s=0: 3;\r\n\ts=1: 5;\r\n\t[] s=1: 7;\r\n\ts=2: 11;\r\n\t[] s=3: 13;\r\n\ts=3: 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/mdp_rewards.nm.cosafety.props",
    "content": "// RESULT: 0.0\nR{\"a\"}max=? [ s>=0 ];\n\n// RESULT: 0.0\nR{\"a\"}max=? [ true ];\n\n// RESULT: 0.0\nR{\"a\"}max=? [ !false ];\n\n// RESULT: 0.0\nR{\"a\"}max=? [ s>0 | s=0 ];\n\n// RESULT: 0.0\nR{\"a\"}max=? [ s=0 ];\n\n// RESULT: 0.0\nR{\"a\"}max=? [ F s=0 ];\n\n// RESULT: 5.0\nR{\"a\"}max=? [ F s=1 ];\n\n// RESULT: 17.0\nR{\"a\"}max=? [ F s=2 ];\n\n// RESULT: 39.0\nR{\"a\"}max=? [ F s=3 ];\n\n// RESULT: 5.0\nR{\"a\"}max=? [ X s>=0 ];\n\n// RESULT: 5.0\nR{\"a\"}max=? [ X true ];\n\n// RESULT: Infinity\nR{\"a\"}max=? [ ! (X true) ];\n\n// RESULT: 5.0\nR{\"a\"}max=? [ ! (X false) ];\n\n// RESULT: 17.0\nR{\"a\"}max=? [ X X s>=0 ];\n\n// RESULT: 17.0\nR{\"a\"}max=? [ X X true ];\n\n// RESULT: 28.0\nR{\"a\"}max=? [ X X X s>=0 ];\n\n// RESULT: 28.0\nR{\"a\"}max=? [ X X X true ];\n\n// RESULT: 28.0\nR{\"a\"}max=? [ X X X (true ? true : s>=0) ];\n\n// RESULT: 28.0\nR{\"a\"}max=? [ X X X (false ? true : s>=0) ];\n\n// RESULT: Infinity\nR{\"a\"}max=? [ X X X false ];\n\n\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/mdp_rewards.nm.props",
    "content": "// RESULT: 0.0\nR{\"a\"}max=? [ C<=0 ];\n// RESULT: 5.0\nR{\"a\"}max=? [ C<=1 ];\n// RESULT: 17.0\nR{\"a\"}max=? [ C<=2 ];\n// RESULT: 28.0\nR{\"a\"}max=? [ C<=3 ];\n\n// RESULT: 39.0\nR{\"a\"}max=? [ C ];\n// RESULT: Infinity\nR{\"b\"}max=? [ C ];\n\n// RESULT: 2.0\nR{\"a\"}max=? [ I=0 ];\n// RESULT: 5.0\nR{\"a\"}max=? [ I=1 ];\n// RESULT: 11.0\nR{\"a\"}max=? [ I=2 ];\n// RESULT: 9.625\nR{\"a\"}max=? [ I=3 ];\n\n// RESULT: 0.0\nR{\"a\"}max=? [ F s=0 ];\n// RESULT: 5.0\nR{\"a\"}max=? [ F s=1 ];\n// RESULT: 17.0\nR{\"a\"}max=? [ F s=2 ];\n// RESULT: 39.0\nR{\"a\"}max=? [ F s>2 ];\n\n\n\n\n\n// RESULT: 0.0\nR{\"a\"}min=? [ C<=0 ];\n// RESULT: 2.0\nR{\"a\"}min=? [ C<=1 ];\n// RESULT: 5.5\nR{\"a\"}min=? [ C<=2 ];\n// RESULT: 11.25\nR{\"a\"}min=? [ C<=3 ];\n\n// RESULT: 25.0\nR{\"a\"}min=? [ C ];\n// RESULT: Infinity\nR{\"b\"}min=? [ C ];\n\n// RESULT: 2.0\nR{\"a\"}min=? [ I=0 ];\n// RESULT: 3.5\nR{\"a\"}min=? [ I=1 ];\n// RESULT: 5.75\nR{\"a\"}min=? [ I=2 ];\n// RESULT: 0.0\nR{\"a\"}min=? [ I=3 ];\n\n// RESULT: 0.0\nR{\"a\"}min=? [ F s=0 ];\n// RESULT: 4.0\nR{\"a\"}min=? [ F s=1 ];\n// RESULT: 14.0\nR{\"a\"}min=? [ F s=2 ];\n// RESULT: 25.0\nR{\"a\"}min=? [ F s>2 ];\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/rewpoliter.nm",
    "content": "// A MDP + reachability reward property which\r\n// proved tricky for policy iteration: useful test case\r\n\r\nmdp\r\n\r\nmodule strips\r\ns : [ 0 .. 5 ] init 0;\r\n\r\n[ a ] s=0 -> 1: (s'=1) ;\r\n[ b ] s=0 -> 0.4: (s'=2)  + 0.6: (s'=0) ;\r\n[ c ] s=2 -> 1: (s'=3) ;\r\n[ a ] s=2 -> 1: (s'=3) ;\r\n[ b ] s=2 -> 0.4: (s'=2)  + 0.6: (s'=2) ;\r\n[ d ] s=3 -> 0.3: (s'=4)  + 0.5: (s'=3)  + 0.2: (s'=1) ;\r\n[ c ] s=3 -> 1: (s'=3) ;\r\n[ a ] s=3 -> 1: (s'=3) ;\r\n[ e ] s=3 -> 0.1: (s'=4)  + 0.9: (s'=3) ;\r\n[ b ] s=3 -> 0.4: (s'=3)  + 0.6: (s'=3) ;\r\n[ a ] s=1 -> 1: (s'=1) ;\r\n[ e ] s=1 -> 0.1: (s'=5)  + 0.9: (s'=1) ;\r\n[ b ] s=1 -> 0.4: (s'=3)  + 0.6: (s'=1) ;\r\nendmodule\r\n\r\nrewards \"cost\"\r\n[ a ] true : 8;\r\n[ b ] true : 5;\r\n[ c ] true : 4;\r\n[ d ] true : 3;\r\n[ e ] true : 3;\r\nendrewards\r\n\r\nrewards \"reward\"\r\n[ a ] true : 1;\r\n[ b ] true : 1;\r\n[ c ] true : 1;\r\n[ d ] true : 1;\r\n[ e ] true : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/rewpoliter.nm.props",
    "content": "// RESULT: 38\nRmin=? [ F s=5 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/rewpoliter.nm.props.args",
    "content": "-politer\n-valiter -s\n-valiter -m\n-valiter -h\n-valiter -ex\n-gs -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/robot.nm",
    "content": "mdp\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[east] s=0 -> 0.6:(s'=1) + 0.4:(s'=0);\r\n[south] s=0 -> 0.8:(s'=3) + 0.1:(s'=1) + 0.1:(s'=4);\r\n[east] s=1 -> 1:(s'=2);\r\n[south] s=1 -> 0.5:(s'=4) + 0.5:(s'=2);\r\n[stuck] s=2 -> 1:(s'=2);\r\n[stuck] s=3 -> 1:(s'=3);\r\n[east] s=4 -> 1:(s'=5);\r\n[west] s=4 -> 0.6:(s'=3) + 0.4:(s'=4);\r\n[north] s=5 -> 0.9:(s'=2) + 0.1:(s'=5);\r\n[west] s=5 -> 1:(s'=4);\r\n\r\nendmodule\r\n\r\nlabel \"hazard\" = s=1;\r\nlabel \"goal1\" = s=5;\r\nlabel \"goal2\" = s=2|s=3;\r\n\r\nrewards \"time\" true : 1; endrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/robot.nm.reach.props",
    "content": "// RESULT: Infinity\nRmin=? [ F \"goal1\" ]\n\n// RESULT: Infinity\nRmax=? [ F \"goal1\" ]\n\n// RESULT: 19/15\nRmin=? [ F \"goal2\" ]\n\n// RESULT: Infinity\nRmax=? [ F \"goal2\" ]\n\n// RESULT: 1.2\nRmin=? [ F (\"goal1\"|\"goal2\") ]\n\n// RESULT: 3.5\nRmax=? [ F (\"goal1\"|\"goal2\") ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/total-reward-1.nm",
    "content": "mdp\n\nmodule M\n  s: [0..1] init 0;\n\n  [a] s=0 -> 1:(s'=0);\n  [b] s=0 -> 1/2:(s'=0) + 1/2:(s'=1);\n  [c] s=0 -> 1:(s'=1);\n\n  [a] s=1 -> 1:(s'=0);\nendmodule\n\nrewards \"steps\"\n  true : 1;\nendrewards\n\nrewards \"s0\"\n  s=0 : 1;\nendrewards\n\nrewards \"s0_a\"\n  [a] s=0 : 2;\nendrewards\n\nrewards \"s0_b\"\n  [b] s=0 : 1/100000;\nendrewards\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/total-reward-1.nm.props",
    "content": "// RESULT: Infinity\nR{\"steps\"}max=?[ C ]\n\n// RESULT: Infinity\nR{\"s0\"}max=?[ C ]\n\n// RESULT: Infinity\nR{\"s0_a\"}max=?[ C ]\n\n// RESULT: Infinity\nR{\"s0_b\"}max=?[ C ]\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/total-reward-2.nm",
    "content": "mdp\n\nmodule M\n  s: [0..2] init 0;\n\n  [a] s=0 -> 1/3:(s'=0) + 1/3:(s'=1) + 1/3:(s'=2);\n  [b] s=0 -> 1:(s'=0);\n\n  [a] s=1 -> 1:(s'=1);\n  [a] s=2 -> 1:(s'=2);\nendmodule\n\nrewards \"steps\"\n  true : 1;\nendrewards\n\nrewards \"s0\"\n  s=0 : 1;\nendrewards\n\nrewards \"s0_a\"\n  [a] s=0 : 2;\nendrewards\n\nrewards \"s0_b\"\n  [b] s=0 : 1/100000;\nendrewards\n\nrewards \"s1\"\n  s=1 : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/total-reward-2.nm.props",
    "content": "// RESULT: Infinity\nR{\"steps\"}max=?[ C ]\n\n// RESULT: Infinity\nR{\"s0\"}max=?[ C ]\n\n\n// RESULT: 3\nR{\"s0_a\"}max=?[ C ]\n\n// RESULT: 3\nmulti(R{\"s0_a\"}max=?[ C ])\n\n// RESULT: Infinity\nR{\"s0_a\"}max=?[ F s=1 ]\n\n// RESULT: Infinity\nR{\"s0_a\"}max=?[ F (s=1 | s=2) ]\n\n\n// RESULT: Infinity\nR{\"s0_b\"}max=?[ C ]\n\n\n// RESULT: Infinity\nR{\"s1\"}max=?[ C ]\n\n// RESULT: 0\nfilter(state, R{\"s1\"}max=?[ C ], s=2)\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/total-reward-3.nm",
    "content": "mdp\n\nmodule M\n  s: [0..2] init 0;\n\n  [a] s=0 -> 1/3:(s'=0) + 1/3:(s'=1) + 1/3:(s'=2);\n  [b] s=0 -> 1:(s'=2);\n\n  [a] s=1 -> 1:(s'=1);\n  [a] s=2 -> 1:(s'=2);\nendmodule\n\nrewards \"steps\"\n  true : 1;\nendrewards\n\nrewards \"s0\"\n  s=0 : 1;\nendrewards\n\nrewards \"s0_a\"\n  [a] s=0 : 2;\nendrewards\n\nrewards \"s0_b\"\n  [b] s=0 : 1/100000;\nendrewards\n\nrewards \"s1\"\n  s=1 : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/mdps/rewards/total-reward-3.nm.props",
    "content": "// RESULT: Infinity\nR{\"steps\"}max=?[ C ]\n\n// RESULT: 1.5\nR{\"s0\"}max=?[ C ]\n\n\n// RESULT: 3\nR{\"s0_a\"}max=?[ C ]\n\n// RESULT: 3\nmulti(R{\"s0_a\"}max=?[ C ])\n\n// RESULT: Infinity\nR{\"s0_a\"}max=?[ F s=1 ]\n\n// RESULT: 3\nR{\"s0_a\"}max=?[ F (s=1 | s=2) ]\n\n\n// RESULT: 1.0E-5\nR{\"s0_b\"}max=?[ C ]\n\n\n// RESULT: Infinity\nR{\"s1\"}max=?[ C ]\n\n// RESULT: 0\nfilter(state, R{\"s1\"}max=?[ C ], s=2)\n"
  },
  {
    "path": "prism-tests/functionality/verify/multiple_bsccs_ss.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/multiple_bsccs_ss.pm.props",
    "content": "\t// RESULT: 0\n\tS=? [ s=0 ];\n\t// RESULT: 0\n\tS=? [ s=1 ];\n\t// RESULT: 1/12\n\tS=? [ s=2 ];\n\t// RESULT: 2/3\n\tS=? [ s=3 ];\n\t// RESULT: 1/6\n\tS=? [ s=4 ];\n\t// RESULT: 1/12\n\tS=? [ s=5 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/multiple_bsccs_ss.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 5:(s'=1) + 5:(s'=3);\r\n[] s=1 -> 5:(s'=0) + 2.5:(s'=2) + 2.5:(s'=4);\r\n[] s=2 -> 10:(s'=5);\r\n[] s=3 -> 10:(s'=3);\r\n[] s=4 -> 10:(s'=4);\r\n[] s=5 -> 10:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\n[] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/multiple_bsccs_ss.sm.props",
    "content": "\t// RESULT: 0\n\tS=? [ s=0 ];\n\t// RESULT: 0\n\tS=? [ s=1 ];\n\t// RESULT: 1/12\n\tS=? [ s=2 ];\n\t// RESULT: 2/3\n\tS=? [ s=3 ];\n\t// RESULT: 1/6\n\tS=? [ s=4 ];\n\t// RESULT: 1/12\n\tS=? [ s=5 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/multiple_bsccs_ss2.sm",
    "content": "// Example to check steady-state probability computation\r\n// on a CTMC comprising multiple bottom strongly connected components\r\n\r\n// Na + Cl <--> Na+ + Cl- \r\n// dxp/gxn 09/06/04\r\n\r\n// ctmc model\r\nctmc\r\n\r\n// constants\r\nconst int N1=10; // number of Na molecules\r\nconst int N2=N1; // number of Cl molecules\r\n\r\n// base rates\r\nconst double e1rate = 100; // Na + Cl -> Na+ + Cl-\r\nconst double e2rate = 10; // Na+ + Cl- -> Na + Cl\r\n\r\n// module representing the base rates of reactions\r\nmodule base_rates\r\n\t\r\n\tdummy : bool; // dummy variable\r\n\t\r\n\t[e1] true -> e1rate : true;\r\n\t[e2] true -> e2rate : true;\r\n\t\r\nendmodule\r\n\r\n// Na and Na+ module\r\nmodule na\r\n\t\r\n\tna : [0..N1+1] init 6;\r\n\t// total number of Na and Na+ molecules is fixed at N1\r\n\t// na is the number of Na molecules \r\n\t// therefore N1-na gives the number of Na+ molecules\r\n\t\r\n\t[] na=N1 & cl=N2 -> (na'=N1+1);\r\n\t[e1] na>0  ->     na  : (na'=na-1);\r\n\t[e2] na<N1-2 -> (N1-na) : (na'=na+1);\r\n\t\r\nendmodule\r\n\r\n// Cl and Cl- module\r\nmodule cl\r\n\t\r\n\tcl : [0..N2] init N1;\r\n\t// total number of Cl and Cl- molecules is fixed at N2\r\n\t// cl is the number of Cl molecules \r\n\t// therefore N2-cl is the number of Cl- molecules\r\n\t\r\n\t[e1] cl>0  ->     cl  : (cl'=cl-1);\r\n\t[e2] cl<N2 -> (N2-cl) : (cl'=cl+1);\r\n\t\r\nendmodule\r\n\r\nrewards\r\n\ttrue : 100*(na/N1);\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/multiple_bsccs_ss2.sm.props",
    "content": "\t// Use GS because Jacobi converges v slowly\n\t\n\t// RESULT: 3150000/19062347\n\tS=? [ na=2 ];\n\t// RESULT: 162702420/19062347\n\tR=? [ S ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/multiple_bsccs_ss2.sm.props.args",
    "content": "-gs\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/ctmcs/ctmc_rewards.prism",
    "content": "ctmc\r\n\r\nconst double x;\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\t\r\n\t[] s=0 -> x: (s'=1);\r\n\t[] s=1 -> 7: (s'=2);\r\n\t[] s=2 -> 11: (s'=3);\r\n\t[] s>2 -> 13: true;\r\n\r\nendmodule\r\n\r\nrewards \"a\"\r\n\ts=0: 2;\r\n//\t[] s=0: 3;\r\n\ts=1: 5;\r\n//\t[] s=1: 7;\r\n\ts=2: 11;\r\nendrewards\r\n\r\nrewards \"a_state\"\r\n\ts=0: 2;\r\n\ts=1: 5;\r\n\ts=2: 11;\r\nendrewards\r\n\r\nrewards \"b\"\r\n\ts=0: 2;\r\n\t[] s=0: 3;\r\n\ts=1: 5;\r\n\t[] s=1: 7;\r\n\ts=2: 11;\r\n\t[] s=3: 13;\r\n\ts=3: 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/ctmcs/ctmc_rewards.prism.args",
    "content": "-param x=1:10\n-const x=5 -exact\n-const x=5 -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/ctmcs/ctmc_rewards.prism.props",
    "content": "// RESULT: 0.0\nR{\"a\"}=? [ F s=0 ]\n// RESULT: 2/x\nR{\"a\"}=? [ F s=1 ]\n// RESULT: (5*x+14)/(7*x)\nR{\"a\"}=? [ F s=2 ]\n// RESULT: (12*x+14)/(7*x)\nR{\"a\"}=? [ F s>2 ]\n\n// RESULT: 0.0\nR{\"a\"}=? [ S ];\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ F s=0 ]\n// RESULT: 2/x\nR{\"a_state\"}=? [ F s=1 ]\n// RESULT: (5*x+14)/(7*x)\nR{\"a_state\"}=? [ F s=2 ]\n// RESULT: (12*x+14)/(7*x)\nR{\"a_state\"}=? [ F s>2 ]\n\n// RESULT: 0.0\nR{\"a_state\"}=? [ S ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/ctmcs/poll2.prism",
    "content": "// polling example [IT90]\r\n// gxn/dxp 26/01/00\r\n\r\nctmc\r\n\r\nconst int N = 2;\r\n\r\nconst double mu\t\t= 1;\r\nconst double gamma;\r\nconst double lambda\t= mu/N;\r\n\r\nmodule server\r\n\t\r\n\ts : [1..2]; // station\r\n\ta : [0..1]; // action: 0=polling, 1=serving\r\n\t\r\n\t[loop1a] (s=1)&(a=0) -> gamma\t: (s'=s+1);\r\n\t[loop1b] (s=1)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve1] (s=1)&(a=1) -> mu\t\t: (s'=s+1)&(a'=0);\r\n\t\r\n\t[loop2a] (s=2)&(a=0) -> gamma\t: (s'=1);\r\n\t[loop2b] (s=2)&(a=0) -> gamma\t: (a'=1);\r\n\t[serve2] (s=2)&(a=1) -> mu\t\t: (s'=1)&(a'=0);\r\n\t\r\nendmodule\r\n\r\nmodule station1\r\n\t\r\n\ts1 : [0..1]; // state of station: 0=empty, 1=full\r\n\t\r\n\t[loop1a] (s1=0) -> 1 : (s1'=0);\r\n\t[]       (s1=0) -> lambda : (s1'=1);\r\n\t[loop1b] (s1=1) -> 1 : (s1'=1);\r\n\t[serve1] (s1=1) -> 1 : (s1'=0);\r\n\t\r\nendmodule\r\n\r\n// construct further stations through renaming\r\n\r\nmodule station2 = station1 [ s1=s2, loop1a=loop2a, loop1b=loop2b, serve1=serve2 ] endmodule\r\n// (cumulative) rewards\r\n\r\n// expected time station 1 is waiting to be served\r\nrewards \"waiting\"\r\n\ts1=1 & !(s=1 & a=1) : 1;\r\nendrewards\r\n\r\n// expected number of times station 1 is served\r\nrewards \"served\"\r\n\t[serve1] true : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/ctmcs/poll2.prism.args",
    "content": "-param gamma=1:400\n-const gamma=200 -exact\n-const gamma=200 -ex -epsilon 1e-8\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/ctmcs/poll2.prism.props",
    "content": "// RESULT: (4*gamma^3+26*gamma^2+25*gamma+6)/(40*gamma^3+68*gamma^2+34*gamma+6)\nS=? [ s1=1 & !(s=1 & a=1) ];\n\n// RESULT: (12*gamma^3+14*gamma^2+3*gamma)/(20*gamma^3+34*gamma^2+17*gamma+3)\nS=? [ s1=0 ];\n\n// RESULT: (2*gamma^2+2*gamma+1)/(4*gamma^2+4*gamma+1)\nP=? [ !(s=2 & a=1) U (s=1 & a=1) ];\n\n// RESULT: (4*gamma^3+26*gamma^2+25*gamma+6)/(40*gamma^3+68*gamma^2+34*gamma+6)\nR{\"waiting\"}=?[ S ];\n\n// RESULT: (4*gamma^3*gamma+34*gamma^3+48*gamma^2+24*gamma+3)/(16*gamma^3*gamma+30*gamma^3+18*gamma^2+3*gamma)\nR{\"waiting\"}=?[ F (s=1 & a=1) ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_mult_param.prism",
    "content": "dtmc\r\n\r\nconst double p;\r\nconst double q;\r\nconst double r;\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> p : (s'=1) + 1-p : (s'=2);\r\n\t[] s=1 -> q^2 : (s'=3) + 1-q^2 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 2*r : (s'=7) & (d'=2) + 1-2*r : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_mult_param.prism.props",
    "content": "// RESULT: (p*q^2-4*p*q^2*r+4*p*r+q^2-2)/(q^2-2)\nP=?[F d>2];\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_mult_param.prism.props.args",
    "content": "-param p,q,r\n-const p=0.5,q=0.2,r=0.05 -exact\n-const p=0.5,q=0.2,r=0.05 -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_pctl.prism",
    "content": "dtmc\r\n\r\nconst double p;\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> p:(s'=1) + 1-p:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[r] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\nrewards \"time\"\r\ntrue : 1;\r\nendrewards\r\n\r\nrewards \"r\"\r\ns=4 : 3;\r\n[r] true : 17;\r\nendrewards\r\n\r\nrewards \"r2\"\r\ns=4 : 3;\r\ns=2 : 17;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_pctl.prism.props",
    "content": "// RESULT: -p/(2*p-4)\nP=? [ F s=2 ];\n\n// RESULT: -p/(p-2)\nP=? [ F s=2|s=4 ];\n\n// RESULT: 0\nP=? [ G s<2 ];\n\n// RESULT: 1-p\nP=? [ s!=1 U s=3 ];\n\n// RESULT: -23*p/(4*p-8)\nR{\"r\"}=? [ S ];\n\n// RESULT: -23*p/(4*p-8)\nR{\"r2\"}=? [ S ];\n\n// RESULT: (-2*p-2)/(p-2)\nR{\"time\"}=? [ F s>1 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_pctl.prism.props.args",
    "content": "-param p\n-const p=0.5 -exact\n-const p=0.5 -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_steady_1.prism",
    "content": "// simple sanity test case for DTMC steady state computations (2 BSCCs)\n\ndtmc\n\nconst double p;\n\nmodule m1\n  s: [0..2] init 0;\n\n  [] s=0 -> p:(s'=0) + 1-2*p:(s'=1) + p:(s'=2);\n  [] s>0 -> true;\nendmodule\n\nmodule m2\n  t: [0..2] init 0;\n\n  [] true -> 1/2:(t'=0) + 1/4:(t'=1) + 1/4:(t'=2);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_steady_1.prism.props",
    "content": "// RESULT: 0\nS=?[ s=0 ];\n\n// RESULT: 0\nS=?[ s=0 & t=0 ];\n\n// RESULT: (2*p-1)/(2*p-2)\nS=?[ s=1 & t=0 ];\n\n// RESULT: (2*p-1)/(4*p-4)\nS=?[ s=1 & t=1 ];\n\n// RESULT: -p/(4*p-4)\nS=?[ s=2 & t=2 ];\n\n// RESULT: 1/2\nS=?[ t=0 ];\n\n// RESULT: 1/4\nS=?[ t=1 ];\n\n// RESULT: 1/4\nS=?[ t=1 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_steady_1.prism.props.args",
    "content": "-param p\n-const p=0.5 -exact\n-const p=0.5 -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_steady_2.prism",
    "content": "// simple test case for DTMC steady state computation (exhibits non-convergence using \"naive\" iteration)\n\ndtmc\n\nconst double p;\n\nmodule m\n  s: [0..2] init 0;\n\n  [] s=0 -> p:(s'=1) + 1-p:(s'=2);\n  [] s>0 -> (s'=0);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_steady_2.prism.props",
    "content": "// RESULT: 1\nS=?[ s=0 | s=1 | s=2 ];\n\n// RESULT: 1/2\nS=?[ s=0 ];\n\n// RESULT: p/2\nS=?[ s=1 ];\n\n// RESULT: (1-p)/2\nS=?[ s=2 ];\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/dtmcs/dtmc_steady_2.prism.props.args",
    "content": "-param p\n-const p=0.5 -exact\n-const p=0.5 -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/mdps/mdp_simple.prism",
    "content": "// Simple MDP tests cases, used during development of stochastic game model checking\r\n\r\nmdp\r\n\r\nconst double p;\r\n\r\nmodule m1\r\n\ts : [0..5];\r\n\tt : [0..2];\r\n\r\n\t[] s=0 & t=0 -> (s'=1);\r\n\t[] s=0 & t=0 -> p : (t'=1)&(s'=0) + 1-p : (t'=2)&(s'=0);\r\n\r\n\t[] s=1 & t=0 -> (s'=2);\r\n\t[] s=1 & t=0 -> 2*p : (t'=1)&(s'=0) + 1-2*p : (t'=2)&(s'=0);\r\n\r\n\t[] s=2 & t=0 -> (s'=3);\r\n\t[] s=2 & t=0 -> 3*p : (t'=1)&(s'=1) + 1-3*p : (t'=2)&(s'=1);\r\n\r\n\t[] s=3 & t=0 -> (s'=4);\r\n\t[] s=3 & t=0 -> 4*p : (t'=1)&(s'=0)+ 1-4*p : (t'=2)&(s'=0);\r\n\r\n\t[] s=4 & t=0 -> (s'=5);\r\n\t[] s=4 & t=0 -> 0.5 : (t'=1)&(s'=0) + 0.5 : (t'=2)&(s'=0);\r\n\r\n\t[] s=5 -> p:(t'=1) + 1-p:(t'=0);\r\n\r\n\t[] t>0 -> true;\r\n\r\nendmodule\r\n\r\nrewards \r\n    mod(s,2)=0 : 1;\r\n    s=5 : 10;\r\nendrewards"
  },
  {
    "path": "prism-tests/functionality/verify/param/mdps/mdp_simple.prism.args",
    "content": "-param p=0:0.1\n-const p=0.1 -exact\n-const p=0.1 -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/mdps/mdp_simple.prism.props",
    "content": "// RESULT: 1.0\nPmax=? [ F t=1 {s=0&t=0} ];\n\n// RESULT: p\nPmin=? [ F t=1 ];\n\n// RESULT: (3*p+10)/p\nRmin=? [ F t=1 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/mdps/safety-fig9.prism",
    "content": "// MDP M_1 (see Figure 9, p.34) and DFA A_A^err (see Figure 8, p.32)\r\n\r\nmdp\r\n\r\nconst double p;\r\n\r\n// M_1\r\nmodule M1\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3] init 0;\r\n\r\n\t[detect]   s=0 -> 1-p:(s'=1) + p:(s'=2);\r\n\t[warn]     s=1 -> (s'=2);\r\n\t[shutdown] s=2 -> (s'=3);\r\n\t[off]      s=3 -> true;\r\n\r\nendmodule\r\n\r\n// DFA A_A^err for property Phi_A (\"never shutdown before warn\")\r\nmodule A_A_err\r\n\r\n\t// q=i for state q_i\r\n\tq : [0..2] init 0;\r\n\r\n\t[warn]     q=0 -> (q'=1);\r\n\t[shutdown] q=0 -> (q'=2);\r\n\r\n\t[warn]     q>=1 -> true;\r\n\t[shutdown] q>=1 -> true;\r\n\t\r\nendmodule\r\n\r\n// Accepting states for A_A^err\r\nlabel \"A_A_err_acc\" = q=2;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/mdps/safety-fig9.prism.args",
    "content": "-param p=0:0.1\n-const p=0.1 -exact\n-const p=0.1 -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/mdps/safety-fig9.prism.props",
    "content": "// ex 13\n// RESULT: 1-p\n1- Pmax=? [ F \"A_A_err_acc\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-complex-1.prism",
    "content": "// this is a test case to check that complex\n// probability expression are handled correctly\n\ndtmc\n\n// the param constant\nconst double p;\n\n// other constants\nconst int x = 3;\nconst double y = 1/3;\nconst double z;\n\nmodule M1\n  s: [0..10] init 0;\n\n  // ITE, depending on state value\n  [] s<=4 -> (s<3 ? p : 0.5):(s'=s+1) + (s<3 ? 1-p : 1/2):(s'=s); \n  // ITE, depending on state value and constant\n  [] s=5  -> (s>x ? p : 0.5):(s'=s+1) + (s>x ? 1-p : 1/2):(s'=s);\n  // min (over constants and state values)\n  [] s=6  -> (min(x,y,z,s)>0.1 ? p : 0.5):(s'=s+1) + (min(x,y,z,s)>0.1 ? 1-p : 1/2):(s'=s);\n  // max (over constants and state values)\n  [] s=7  -> (max(x,y,z,s)=7 ? p : 0.5):(s'=s+1) + (max(x,y,z,s)=7 ? 1-p : 1/2):(s'=s);\n  // floor\n  [] s=8  -> (floor(s+y)=8 ? p : 0.5):(s'=s+1) + (floor(s+y)=8 ? 1-p : 1/2):(s'=s);\n  // floor\n  [] s=9  -> (ceil(s+y)=10 ? p : 0.5):(s'=s+1) + (ceil(s+y)=10 ? 1-p : 1/2):(s'=s);\n  [] s=10  -> true;\nendmodule\n\nrewards\n  true : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-complex-1.prism.args",
    "content": "# parametric model checking\n-param p -const z=0.5\n# exact model checking, run experiment for 0.1,0.2,...,0.9\n-exact -const p=0.1:0.1:0.9,z=0.5\n# standard model checking, run experiment for 0.1,0.2,...,0.9\n-const p=0.1:0.1:0.9,z=0.5\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-complex-1.prism.props",
    "content": "// probability of reaching trap state\n// RESULT: 1\nP=?[ F s=10 ]\n\n// expected number of steps util reaching trap state\n// RESULT: 4+8/p\nR=?[ F s=10 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-consts.prism",
    "content": "// Test of constants in parametric model checking\r\n// (specifically, when a parameter is used indirectly,\r\n// within the definition of another constant)\r\n\r\ndtmc\r\n\r\nconst double p;\r\nconst double q = 1 - p;\r\n\r\nmodule M\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t\r\n\t[] s=0 -> q : (s'=1) + 1-q : (s'=2);\r\n\t[] s>0 -> true;\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-consts.prism.props",
    "content": "// RESULT: 1-p\nP=? [ F s=1 ];\n\n// RESULT: p\nP=? [ F s=2 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-consts.prism.props.args",
    "content": "-param p\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-ite.prism",
    "content": "dtmc\n\nconst double p;\nformula outcome = (s>0 ? s-1 : -1);\n\nmodule M1\n  s: [0..4] init 0;\n\n  [] s=0 -> 1/2:(s'=0) + 1/8:(s'=1) + 1/8:(s'=2) + 1/8:(s'=3) + 1/8:(s'=4);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-ite.prism.args",
    "content": "-exact -const p=0\n-param p=0:1\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-ite.prism.props",
    "content": "// test case: support for if-then-else and formulas in expressions (exact / parametric)\n\n// RESULT: 1/4\nP=?[F outcome=2]\n\n// RESULT: 0\nP=?[G outcome=-1]\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-simple.prism",
    "content": "// Trivial test of parametric model checking\r\n// (also tests a bugfix in the results testing when the result is just a lone parameter)\r\n\r\ndtmc\r\n\r\nconst double p;\r\n\r\nmodule M\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t\r\n\t[] s=0 -> p : (s'=1) + 1-p : (s'=2);\r\n\t[] s>0 -> true;\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-simple.prism.props",
    "content": "// RESULT: p\nP=? [ F s=1 ];\n\n// RESULT: 1-p\nP=? [ F s=2 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-simple.prism.props.args",
    "content": "-param p\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-assign.prism",
    "content": "dtmc\n\n// the param constant\nconst double p;\n\nmodule M1\n  s: [0..1] init 0;\n\n  // Unsupported: Can not use parametric constant in assignment\n  [] true -> 1:(s'=floor(p));\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-assign.prism.args",
    "content": "-param p\n-const p=0.5\n-const p=0.5 -exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-assign.prism.props",
    "content": "// RESULT(p=0.5): 1        ; for concrete constants, everything is fine\n// RESULT: Error           ; unsupported for parametric\nP=?[ G s=0 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-guard.prism",
    "content": "dtmc\n\n// the param constant\nconst double p;\n\nmodule M1\n  s: [0..1] init 0;\n\n  // Unsupported: Can not use parametric constant in guard\n  [] s<=floor(p) -> 1:(s'=1);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-guard.prism.args",
    "content": "-param p\n-const p=0.5\n-const p=0.5 -exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-guard.prism.props",
    "content": "// RESULT(p=0.5): 1        ; for concrete constants, everything is fine\n// RESULT: Error           ; unsupported for parametric\nP=?[ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-ite.prism",
    "content": "dtmc\n\n// the param constant\nconst double p;\n\nmodule M1\n  s: [0..1] init 0;\n\n  // Unsupported: Can not use parametric constant in the 'if' part of an\n  // ITE expression for probabilities\n  [] s<=1 -> (p>0.5 ? 1 : 0):(s'=1) + (p>0.5 ? 0 : 1):(s'=0);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-ite.prism.args",
    "content": "-param p\n-const p=0.5\n-const p=0.5 -exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-ite.prism.props",
    "content": "// RESULT(p=0.5): 0        ; for concrete constants, everything is fine\n// RESULT: Error           ; unsupported for parametric\nP=? [ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-max.prism",
    "content": "dtmc\n\n// the param constant\nconst double p;\n\nmodule M1\n  s: [0..2] init 0;\n\n  // Unsupported: Can not use parametric constant as argument in a max\n  // function for probabilities\n  [] s=0 -> max(p, 1/3):(s'=1) + 1-max(p, 1/3):(s'=2);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-max.prism.args",
    "content": "-param p\n-const p=0.5\n-const p=0.5 -exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-max.prism.props",
    "content": "// RESULT(p=0.5): 1/2      ; for concrete constants, everything is fine\n// RESULT: Error           ; unsupported for parametric\nP=? [ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-min.prism",
    "content": "dtmc\n\n// the param constant\nconst double p;\n\nmodule M1\n  s: [0..2] init 0;\n\n  // Unsupported: Can not use parametric constant as argument in a min\n  // function for probabilities\n  [] s=0 -> min(p, 1/3):(s'=1) + 1-min(p, 1/3):(s'=2);\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-min.prism.args",
    "content": "-param p\n-const p=0.5\n-const p=0.5 -exact\n"
  },
  {
    "path": "prism-tests/functionality/verify/param/param-unsupported-min.prism.props",
    "content": "// RESULT(p=0.5): 1/3      ; for concrete constants, everything is fine\n// RESULT: Error           ; unsupported for parametric\nP=? [ F s=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/3x3grid.prism",
    "content": "// 3x3 grid\n// based on Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n\npomdp\n\n// only the target is observable which is in the south east corner\nobservables\n\to\nendobservables\n\nmodule grid\n\t\n\tx : [0..2]; // x coordinate\n\ty : [0..2]; // y coordinate\n\to : [0..2]; // observables\n\t// 0 - initial observation\n\t// 1 - in the grid (not target)\n\t// 2 - observe target\n\t\n\t// initially randomly placed within the grid (not at the target)\n\t[] o=0 -> 1/8 : (o'=1) & (x'=0) & (y'=0)\n\t\t\t+ 1/8 : (o'=1) & (x'=0) & (y'=1)\n\t\t\t+ 1/8 : (o'=1) & (x'=0) & (y'=2)\n\t\t\t+ 1/8 : (o'=1) & (x'=1) & (y'=0)\n\t\t\t+ 1/8 : (o'=1) & (x'=1) & (y'=1)\n\t\t\t+ 1/8 : (o'=1) & (x'=1) & (y'=2)\n\t\t\t// + 1/8 : (o'=1) & (x'=2) & (y'=0) the target\n\t\t\t+ 1/8 : (o'=1) & (x'=2) & (y'=1)\n\t\t\t+ 1/8 : (o'=1) & (x'=2) & (y'=2);\n\t\t\t\n\t// move around the grid\n\t[east] o=1 & !(x=1 & y=0) -> (x'=min(x+1,2)); // not reached target\n\t[east] o=1 & x=1 & y=0 -> (x'=min(x+1,2)) & (o'=2);\n\t[west] o=1 -> (x'=max(x-1,0)); // not reached target\n\t[north] o=1 -> (x'=min(y+1,2)); // reached target\n\t[south] o=1 & !(x=2 & y=1) -> (y'=max(y-1,0)); // not reached target\n\t[south] o=1 & x=2 & y=1 -> (y'=max(y-1,0)) & (o'=2); // reached target\n\t\n\t// reached target\n\t[done] o=2 -> true;\n\t\nendmodule\n\n// reward structure for number of steps to reach the target\nrewards\n        [east] true : 1;\n        [west] true : 1;\n        [north] true : 1;\n        [south] true : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/3x3grid.prism.props",
    "content": "// minimum steps to reach goal\n// RESULT: [2.8496094277343733,2.8750000000000004] (grid resolution 16)\nRmin=?[F o=2 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/3x3grid_bounded.prism",
    "content": "// 3x3 grid (for step bounded properties)\n// based on Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n\npomdp\n\nconst int K; // step bound in property\n\n// only the target is observable which is in the south east corner\n// (and the step bound)\nobservables\n\to, k\nendobservables\n\nmodule grid\n\t\n\tx : [0..2]; // x coordinate\n\ty : [0..2]; // y coordinate\n\to : [0..2]; // observables\n\t// 0 - initial observation\n\t// 1 - in the grid (not target)\n\t// 2 - observe target\n\t\n\t// initially randomly placed within the grid (not at the target)\n\t[] o=0 -> 1/8 : (o'=1) & (x'=0) & (y'=0)\n\t\t\t+ 1/8 : (o'=1) & (x'=0) & (y'=1)\n\t\t\t+ 1/8 : (o'=1) & (x'=0) & (y'=2)\n\t\t\t+ 1/8 : (o'=1) & (x'=1) & (y'=0)\n\t\t\t+ 1/8 : (o'=1) & (x'=1) & (y'=1)\n\t\t\t+ 1/8 : (o'=1) & (x'=1) & (y'=2)\n\t\t\t// + 1/8 : (o'=1) & (x'=2) & (y'=0) the target\n\t\t\t+ 1/8 : (o'=1) & (x'=2) & (y'=1)\n\t\t\t+ 1/8 : (o'=1) & (x'=2) & (y'=2);\n\t\t\t\n\t// move around the grid\n\t[east] o=1 & !(x=1 & y=0) -> (x'=min(x+1,2)); // not reached target\n\t[east] o=1 & x=1 & y=0 -> (x'=min(x+1,2)) & (o'=2); // reached target\n\t[west] o=1 -> (x'=max(x-1,0)); // not reached target\n\t[north] o=1 -> (x'=min(y+1,2)); // reached target\n\t[south] o=1 & !(x=2 & y=1) -> (y'=max(y-1,0)); // not reached target\n\t[south] o=1 & x=2 & y=1 -> (y'=max(y-1,0)) & (o'=2); // reached target\n\t\n\t// reached target\n\t[done] o=2 -> true;\n\t \nendmodule\n\n// module for the step bound\nmodule bound\n\n\tk : [0..K];\n\t\n\t[east] k<K -> (k'=k+1);\n\t[west] k<K -> (k'=k+1);\n\t[north] k<K -> (k'=k+1);\n\t[south] k<K -> (k'=k+1);\n\t\n\t[] k=K -> true;\n\t\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/3x3grid_bounded.prism.args",
    "content": "-const K=2\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/3x3grid_bounded.prism.props",
    "content": "// max probability reach goal (use with step bound property)\n// RESULT (K=2): [0.37500000000000006,0.375000078125] (grid resolution 8)\nPmax=?[F o=2 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/crypt3.prism",
    "content": "// dining cryptographers\n// gxn 27/01/16\n\n// pomdp model\npomdp\n\n// observable variables (for crypt3)\n// the announcements of all cryptographers \n// only its own coin and the coin of its left neighbour\n// if it guesses correctly (this is the target so needs to be observable)\n// also local states of modules this only indicates:\n// - if a cryptographer has announced\n// - if the master has made its choice\nobservables\n\tcoin1, coin3, m, s1, s2, s3, guess, correct, agree1, agree2, agree3\nendobservables\n\n// constants used in renaming\nconst int p1=1;\nconst int p2=2;\nconst int p3=3;\n\nmodule master\n\t\n\tm : [0..1]; // local state (has chosen who pays)\n\tpay : [1..3]; // who actually pays\n\t\n\t// randomly choose who pays\n\t[] m=0 -> 1/2 : (m'=1) & (pay'=1) + 1/2 : (m'=1) & (pay'=2);\n\t\n\t// test cases\n\t//[] m=0 -> (m'=1); // master pays\n\t//[] m=0 -> (m'=1) & (pay'=1); // crypt 1 pays\n\t//[] m=0 -> (m'=1) & (pay'=2); // crypt 2 pays\n\t//[] m=0 -> (m'=1) & (pay'=3); // crypt 3 pays\n\t\nendmodule\n\nmodule crypt1\n\t\n\tcoin1 : [0..2]; // value of coin\n\ts1 : [0..1]; // local state (has announced yet)\n\tagree1 : [0..1]; // agree or not\n\t\n\t// flip coin and share values\n\t[flip] m=1 & coin1=0 -> 0.5 : (coin1'=1) + 0.5 : (coin1'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// does not pay\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay!=p1) -> (s1'=1) & (agree1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay!=p1) -> (s1'=1);\n\t// pays\n\t[choose1] s1=0 & coin1>0 & coin2>0 & coin1=coin2 & (pay=p1) -> (s1'=1);\n\t[choose1] s1=0 & coin1>0 & coin2>0 & !(coin1=coin2) & (pay=p1) -> (s1'=1) & (agree1'=1);\n\n\t// when everyone has announced\n\t[done] s1=1 -> true;\n\nendmodule\n\n// construct further cryptographers through renaming\nmodule crypt2 =crypt1[coin1=coin2, s1=s2, p1=p2, agree1=agree2, coin2=coin3, choose1=choose2 ] endmodule\n\n// the cryptographer that guesses who pays\nmodule crypt3\n\t\n\tcoin3 : [0..2];\n\ts3 : [0..2];\n\tagree3 : [0..1];\n\tguess : [0..3];\n\tcorrect : [0..1];\n\t\n\t// flip coin\n\t[flip] m=1 & coin3=0 -> 0.5 : (coin3'=1) + 0.5 : (coin3'=2);\n\t\n\t// make choice (once relevant coins have been flipped)\n\t// assume does not pay\n\t[choose3] s3=0 & coin3>0 & coin1>0 & coin3=coin1 -> (s3'=1) & (agree3'=1);\n\t[choose3] s3=0 & coin3>0 & coin1>0 & !(coin3=coin1) -> (s3'=1);\n\t// pays\n\t[choose3] s3=0 & coin3>0 & coin1>0 & coin3=coin1 & (pay=p3) -> (s3'=1);\n\t[choose3] s3=0 & coin3>0 & coin1>0 & !(coin3=coin1) & (pay=p3) -> (s3'=1) & (agree3'=1);\n\t\n\t// after everyone has announced guess who payed\n\t[done] s3=1 -> (s3'=2);\n\t[guess1] s3=2 & guess=0 -> (guess'=1);\n\t[guess2] s3=2 & guess=0 -> (guess'=2);\n\t\n\t// check whether guessed correctly\n\t[check] s3=2 & guess>0 & guess=pay -> (correct'=1);\n\t[check] s3=2 & guess>0 & !(guess=pay) -> true;\n\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/crypt3.prism.props",
    "content": "// minimum probability guess correctly which cryptographer paid\n// RESULT: 0.5\nPmin=? [ F correct=1 ]\n\n// maximum probability guess correctly which cryptographer paid\n// RESULT: 0.5\nPmax=? [ F correct=1 ]\n\n\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/guess-multi.prism",
    "content": "pomdp\n\nconst int N;\n\nmodule M\n\n\ts : [0..3]; // state\n\th : [0..3]; // hidden var\n\tg : [0..N] init N; // num guesses left\n\n\t[toss] s=0 -> 0.1:(s'=1)&(h'=1) + 0.3:(s'=1)&(h'=2) + 0.6:(s'=1)&(h'=3);\n\t[guess1] s=1&g>0 -> (s'=(h=1)?2:s) & (g'=g-1);\n\t[guess2] s=1&g>0 -> (s'=(h=2)?2:s) & (g'=g-1);\n\t[guess3] s=1&g>0 -> (s'=(h=3)?2:s) & (g'=g-1);\n\t[timeup] s=1&g=0 -> (s'=3);\n\t[loop] s=2 -> true;\n\nendmodule\n\nobservables s, g endobservables\n\nlabel \"correct\" = s=2;\n\nrewards \"guesses\"\n\t[guess1] true : 1;\n\t[guess2] true : 1;\n\t[guess3] true : 1;\nendrewards\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/guess-multi.prism.props",
    "content": "// RESULT (N=1): 0.6\n// RESULT (N=2): 0.9\n// RESULT (N=3): 1.0\n// RESULT (N=4): 1.0\nPmax=? [ F \"correct\" ];\n\n// RESULT (N=1): Infinity\n// RESULT (N=2): Infinity\n// RESULT (N=3): 1.5\n// RESULT (N=4): 1.5\nR{\"guesses\"}min=? [ F \"correct\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/guess-multi.prism.props.args",
    "content": "-const N=1\n-const N=2\n-const N=3\n-const N=4\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/guess.prism",
    "content": "pomdp\n\nconst double p = 0.2;\n\nmodule M\n\n\ts : [0..3]; // state\n\th : [0..3]; // hidden var\n\n\t[toss] s=0 -> 0.1:(s'=1)&(h'=1) + 0.3:(s'=1)&(h'=2) + 0.6:(s'=1)&(h'=3);\n\t//[loop] s=0 -> true; // uncommenting this gives bad bounds\n\t[guess1] s=1 -> (s'=(h=1)?2:3);\n\t[guess2] s=1 -> (s'=(h=2)?2:3);\n\t[guess3] s=1 -> (s'=(h=3)?2:3);\n\t[loop] s=2 -> true;\n\nendmodule\n\nobservables s endobservables\n\nlabel \"correct\" = s=2;\n\nrewards \"guesses\"\n\t[guess1] true : 1;\n\t[guess2] true : 1;\n\t[guess3] true : 1;\nendrewards\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/guess.prism.props",
    "content": "// RESULT: 0.6\nPmax=? [ F \"correct\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/maze.prism",
    "content": "// maze example (POMDP)\n// Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n// gxn 29/01/16\n\n// state space (value of variable \"s\")\n\n//  0  1  2  3  4\n//  5     6     7\n//  8     10    9\n\n// 10 is the target\n\npomdp\n\n// can observe the walls and target\nobservable \"west\" = s=0|s=5|s=6|s=7|s=8|s=9|s=10; // wall to the west\nobservable \"east\" = s=4|s=5|s=6|s=7|s=8|s=9|s=10; // wall to the east\nobservable \"north\" = s=0|s=1|s=2|s=3|s=4; // wall to the north\nobservable \"south\" = s=1|s=3|s=8|s=9|s=10; // wall to the south\nobservable \"target\" = s=10; //target\n\nmodule maze\n\n\ts : [-1..10];\n\t\n\t// initialisation\n\t[] s=-1 -> 0.1 : (s'=0)\n\t\t\t + 0.1 : (s'=1)\n\t\t\t + 0.1 : (s'=2)\n\t\t\t + 0.1 : (s'=3)\n\t\t\t + 0.1 : (s'=4)\n\t\t\t + 0.1 : (s'=5)\n\t\t\t + 0.1 : (s'=6)\n\t\t\t + 0.1 : (s'=7)\n\t\t\t + 0.1 : (s'=8)\n\t\t\t + 0.1 : (s'=9);\n\t\n\t// moving around the maze\n\n\t[east] s=0 -> (s'=1);\n\t[south] s=0 -> (s'=5);\n\n\t[east] s=1 -> (s'=2);\n\t[west] s=1 -> (s'=0);\n\n\t[east] s=2 -> (s'=3);\n\t[west] s=2 -> (s'=1);\n\t[south] s=2 -> (s'=6);\n\n\t[east] s=3 -> (s'=4);\n\t[west] s=3 -> (s'=2);\n\n\t[west] s=4 -> (s'=3);\n\t[south] s=4 -> (s'=7);\n\n\t[north] s=5 -> (s'=0);\n\t[south] s=5 -> (s'=8);\n\n\t[north] s=6 -> (s'=2);\n\t[south] s=6 -> (s'=10);\n\n\t[north] s=7 -> (s'=4);\n\t[south] s=7 -> (s'=9);\n\n\t[north] s=8 -> (s'=5);\n\n\t[north] s=9 -> (s'=7);\n\n\t// loop when we reach the target\n\t[done] s=10 -> true;\n\nendmodule\n\n// reward structure (number of steps to reach the target)\nrewards\n\n\t[east] true : 1;\n\t[west] true : 1;\n\t[north] true : 1;\n\t[south] true : 1;\n\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/maze.prism.props",
    "content": "// Minimum expected number of steps to reach the target\n// RESULT: 4.3\nRmin=? [ F \"target\" ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/maze2.prism",
    "content": "// maze example (POMDP)\n// slightly extends that presented in\n// Littman, Cassandra and Kaelbling\n// Learning policies for partially observable environments: Scaling up  \n// Technical Report CS, Brown University\n// gxn 29/01/16\n\n// state space (value of variable \"s\")\n\n//  0  1  2  3  4\n//  5     6     7\n//  8     9    10\n// 11     13   12\n\n// 13 is the target\n\npomdp\n\n// can observe the walls and target\nobservable \"west\" = s=0|s=5|s=6|s=7|s=8|s=9|s=10|s=11|s=12|s=13; // wall to the west\nobservable \"east\" = s=4|s=5|s=6|s=7|s=8|s=9|s=10|s=10|s=11|s=12|s=13; // wall to the east\nobservable \"north\" = s=0|s=1|s=2|s=3|s=4; // wall to the north\nobservable \"south\" = s=1|s=3|s=11|s=12|s=13; // wall to the south\nobservable \"target\" = s=13; //target\n\nmodule maze\n\n\ts : [-1..13];\n\t\n\t// initialisation\n\t[] s=-1 -> 1/13 : (s'=0)\n\t\t\t + 1/13 : (s'=1)\n\t\t\t + 1/13 : (s'=2)\n\t\t\t + 1/13 : (s'=3)\n\t\t\t + 1/13 : (s'=4)\n\t\t\t + 1/13 : (s'=5)\n\t\t\t + 1/13 : (s'=6)\n\t\t\t + 1/13 : (s'=7)\n\t\t\t + 1/13 : (s'=8)\n\t\t\t + 1/13 : (s'=9)\n\t\t\t + 1/13 : (s'=10)\n\t\t\t + 1/13 : (s'=11)\n\t\t\t + 1/13 : (s'=12);\n\t\n\t// moving around the maze\n\t\n\t[east] s=0 -> (s'=1);\n\t[south] s=0 -> (s'=5);\n\n\t[east] s=1 -> (s'=2);\n\t[west] s=1 -> (s'=0);\n\n\t[east] s=2 -> (s'=3);\n\t[west] s=2 -> (s'=1);\n\t[south] s=2 -> (s'=6);\n\n\t[east] s=3 -> (s'=4);\n\t[west] s=3 -> (s'=2);\n\n\t[west] s=4 -> (s'=3);\n\t[south] s=4 -> (s'=7);\n\n\t[north] s=5 -> (s'=0);\n\t[south] s=5 -> (s'=8);\n\n\t[north] s=6 -> (s'=2);\n\t[south] s=6 -> (s'=9);\n\n\t[north] s=7 -> (s'=4);\n\t[south] s=7 -> (s'=10);\n\n\t[north] s=8 -> (s'=5);\n\t[south] s=8 -> (s'=11);\n\n\t[north] s=9 -> (s'=6);\n\t[south] s=9 -> (s'=13);\n\n\t[north] s=10 -> (s'=7);\n\t[south] s=10 -> (s'=12);\n\n\t[north] s=11 -> (s'=8);\n\n\t[north] s=12 -> (s'=10);\n\n\t// loop when we reach the target\n\t[done] s=13 -> true;\n\nendmodule\n\n// reward structure (number of steps to reach the target)\nrewards\n\n\t[east] true : 1;\n\t[west] true : 1;\n\t[north] true : 1;\n\t[south] true : 1;\n\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/maze2.prism.props",
    "content": "// Minimum expected number of steps to reach the target\n// RESULT: [5.69230763076923,5.692307692307692] (grid resolution 20)\nRmin=? [ F \"target\" ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/maze2.prism.props.args",
    "content": "-gridresolution 20\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/mdp_simple.prism",
    "content": "// Simple MDP tests cases, used during development of stochastic game model checking\r\n// Converted to (special case of) POMDP for testing\r\n\r\npomdp\r\n\r\nobservables s, t endobservables\r\n\r\nmodule m1\r\n\ts : [0..5];\r\n\tt : [0..2];\r\n\r\n\t[a] s=0 & t=0 -> (s'=1);\r\n\t[b] s=0 & t=0 -> 0.1 : (t'=1)&(s'=0) + 0.9 : (t'=2)&(s'=0);\r\n\r\n\t[a] s=1 & t=0 -> (s'=2);\r\n\t[b] s=1 & t=0 -> 0.2 : (t'=1)&(s'=0) + 0.8 : (t'=2)&(s'=0);\r\n\r\n\t[a] s=2 & t=0 -> (s'=3);\r\n\t[b] s=2 & t=0 -> 0.3 : (t'=1)&(s'=1) + 0.7 : (t'=2)&(s'=1);\r\n\r\n\t[a] s=3 & t=0 -> (s'=4);\r\n\t[b] s=3 & t=0 -> 0.4 : (t'=1)&(s'=0)+ 0.6 : (t'=2)&(s'=0);\r\n\r\n\t[a] s=4 & t=0 -> (s'=5);\r\n\t[b] s=4 & t=0 -> 0.5 : (t'=1)&(s'=0) + 0.5 : (t'=2)&(s'=0);\r\n\r\n\t[] s=5 & t=0 -> (t'=1)&(s'=0);\r\n\r\n\t[] t>0 -> true;\r\n\r\nendmodule\r\n\r\nrewards \r\n    mod(s,2)=0 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/mdp_simple.prism.props",
    "content": "// RESULT: 1.0\nPmax=? [ F t=1 ];\n\n// RESULT: 0.1\nPmin=? [ F t=1 ];\n\n// RESULT: 0.3\nfilter(state, Pmin=? [ F t=1 ], s=2&t=0);\n\n// RESULT: 0.3\nPmax=? [ s<=2 U t=1 ];\n\n// RESULT: 3.0\nRmax=? [ F t>0 ];\n\n// RESULT: 2.0\nfilter(state, Rmax=? [ F t>0 ], s=2&t=0);\n\n// RESULT: 1.0\nRmin=? [ F t>0 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2 //, chan1, chan2\nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\n\t// loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2.prism.args",
    "content": "-const K=2,T=3\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2.prism.props",
    "content": "// minimum number of dropped packets\n// RESULT (K=2,T=3): [1.6572208448483332,1.6578400000000002] (grid resolution 50)\nR{\"dropped_packets\"}min=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// maximum number of packets sent (dual property)\n// RESULT (K=2,T=3): [2.3421600000000002,2.342779155151662] (grid resolution 50)\nR{\"packets_sent\"}max=?[F sched=0 & t=T-1 & k=K-1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_noidle.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2 //, chan1, chan2\nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 & packet1=0 & packet2=0 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\n\t// loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_noidle.prism.args",
    "content": "-const K=2,T=3\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_noidle.prism.props",
    "content": "// minimum number of dropped packets\n// RESULT (K=2,T=3): [1.6572208448483332,1.6578400000000002] (grid resolution 50)\nR{\"dropped_packets\"}min=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// maximum number of packets sent (dual property)\n// RESULT (K=2,T=3): [2.3421600000000002,2.342779155151662] (grid resolution 50)\nR{\"packets_sent\"}max=?[F sched=0 & t=T-1 & k=K-1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_priorities.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2, priority1, priority2 //, chan1, chan2, \nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\n    // loop when finished\n\t[] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,send1=send2,chan1=chan2] endmodule\n\n// priority of packets for first channel\nmodule priority1\n\n\tpriority1 : [0..3];\n\t\n\t// new period so new packet and randomly assign priority\n\t[slot] t=0 -> 0.1 : (priority1'=1) + 0.3 : (priority1'=2) + 0.6 : (priority1'=3);\n\t// priority already assigned for this period\n\t[slot] t>0 -> true;\n\t\n\t// reset priority when packet has been sent\n\t[send1] chan1=0 -> true;\n\t[send1] chan1=1 -> (priority1'=0);\n\t\nendmodule\n\n// construct further priorities through renaming\nmodule priority2 = priority1[priority1=priority2,chan1=chan2,send1=send2] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,p1=p2,r1=r2] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\nendrewards\n\nconst double beta=1; // discount factor\n\n// (discounted) reward structure based on priorities \nrewards \"priority\"\n\t[send1] chan1=1 & priority1=1 :  1 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=1 :  1 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=2 : 10 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=2 : 10 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=3 : 20 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=3 : 20 * pow(beta,t + k*T);\nendrewards"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_priorities.prism.args",
    "content": "-const K=2,T=3\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_priorities.prism.props",
    "content": "// minimum number of dropped packets\n// RESULT (K=2,T=3): [1.6560279993301588,1.6578400000000002] (grid resolution 20)\nR{\"dropped_packets\"}min=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// maximum number of packets sent (dual property)\n// RESULT (K=2,T=3): [2.3421600000000002,2.3439720006698384] (grid resolution 20)\nR{\"packets_sent\"}max=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// maximum reward (based on priorities)\n// RESULT (K=2,T=3): [36.321503131200004,36.33018249727175] (grid resolution 20)\nR{\"priority\"}max=?[F sched=0 & t=T-1 & k=K-1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_priorities_noidle.prism",
    "content": "// network unitization example with partially observable channels based on:\n// L. Yang, S. Murugesan and J. Zhang\n// Real-Kime Scheduling over Markovian Channels: When Partial Observability Meets Hard Deadlines\n// IEEE Global Kelecommunications Conference (GLOBECOM'11), pages 1-5, 2011\n\npomdp\n\nobservables\n\tsched, k, t, packet1, packet2, priority1, priority2 //, chan1, chan2, \nendobservables\n\n// timing constants\nconst int K; // total number of time periods\nconst int T; // number of slots per time period\n\n// probabilities that channels change states\n// channel of user 1\nconst double p1 = 0.8; // prob remain on\nconst double r1 = 0.2; // prob move from off to on\n// channel of user 2\nconst double p2 = 0.6; // prob remain on\nconst double r2 = 0.4; // prob move from off to on\n\n// scheduler\nmodule scheduler\n\n\tk : [0..K-1]; // current time period\n\tt : [0..T-1]; // correct slot\n\tsched : [0..1]; // local state\n\t\n\t// next slot/time period \n\t[slot] sched=0 & t<T-1 -> (sched'=1) & (t'=t+1);\n\t[slot] sched=0 & t=T-1 & k<K-1 -> (sched'=1) & (t'=0) & (k'=k+1);\n\n\t// make scheduling choice\n\t[idle]  sched=1 & packet1=0 & packet2=0 -> (sched'=0);\n\t[send1] sched=1 -> (sched'=0);\n\t[send2] sched=1 -> (sched'=0);\n\n    // loop when finished\n    [] sched=0 & t=T-1 & k=K-1 -> true;\n\t\nendmodule\n\n// packets for first channel\nmodule packet1\n\n\tpacket1 : [0..1]; // packet to send in current period\n\n\t// next slot\n\t[slot] t=0 -> (packet1'=1); // new period so new packet\n\t[slot] t>0 -> true;\n\t// sending\n\t[send1]\tpacket1=1 & chan1=1 -> (packet1'=0); // channel up\n\t[send1]\tpacket1=1 & chan1=0 -> true; // channel down\n\nendmodule\n\n// construct further channels' packets through renaming\nmodule packet2=packet1[packet1=packet2,chan1=chan2] endmodule\n\n// priority of packets for first channel\nmodule priority1\n\n\tpriority1 : [0..3];\n\t\n\t// new period so new packet and randomly assign priority\n\t[slot] t=0 -> 0.1 : (priority1'=1) + 0.3 : (priority1'=2) + 0.6 : (priority1'=3);\n\t// priority already assigned for this period\n\t[slot] t>0 -> true;\n\t\n\t// reset priority when packet has been sent\n\t[send1] chan1=0 -> true;\n\t[send1] chan1=1 -> (priority1'=0);\n\t\nendmodule\n\n// construct further priorities through renaming\nmodule priority2 = priority1[priority1=priority2,chan1=chan2,send1=send2] endmodule\n\n// first channel status\nmodule channel1\n\n\tchan1 : [0..1]; // status of channel (off/on)\n\n\t// initialise\n\t[slot] t=0 & k=0 -> 0.5 : (chan1'=0) + 0.5 : (chan1'=1);\n\t// next slot\n\t[slot] chan1=0 & !(t=0 & k=0) -> 1 - r1 : (chan1'=0) + r1 : (chan1'=1);\n\t[slot] chan1=1 & !(t=0 & k=0) -> 1 - p1 : (chan1'=0) + p1 : (chan1'=1);\n\nendmodule\n\n// construct further channels through renaming\nmodule channel2=channel1[chan1=chan2,send1=send2,p1=p2,r1=r2] endmodule\n\n// reward structure for number of dropped packets\n// (need to be careful as we update k and t at the start of the time slot)\nrewards \"dropped_packets\"\n\t[slot] t=0 & k>0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[idle] t=T-1 & k=K-1 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=0 : ((packet1=0)?0:1) + ((packet2=0)?0:1);\n\t[send1] t=T-1 & k=K-1 & chan1=1 : ((packet2=0)?0:1);\n\t[send2] t=T-1 & k=K-1 & chan2=1 : ((packet1=0)?0:1);\nendrewards\n\n// reward structure for number of sent packets\nrewards \"packets_sent\"\n\t[send1] chan1=1 : 1;\n\t[send2] chan2=1 : 1;\nendrewards\n\nconst double beta=1; // discount factor\n\n// (discounted) reward structure based on priorities \nrewards \"priority\"\n\t[send1] chan1=1 & priority1=1 :  1 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=1 :  1 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=2 : 10 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=2 : 10 * pow(beta,t + k*T);\n\t[send1] chan1=1 & priority1=3 : 20 * pow(beta,t + k*T);\n\t[send2] chan2=1 & priority2=3 : 20 * pow(beta,t + k*T);\nendrewards"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_priorities_noidle.prism.args",
    "content": "-const K=2,T=3\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/network2_priorities_noidle.prism.props",
    "content": "// minimum number of dropped packets\n// RESULT (K=2,T=3): [1.578,1.578000000041999] (grid resolution 20)\nR{\"dropped_packets\"}min=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// maximum number of packets sent (dual property)\n// RESULT (K=2,T=3): [2.66096,2.6646735594157978] (grid resolution 20)\nR{\"packets_sent\"}max=?[F sched=0 & t=T-1 & k=K-1 ]\n\n// maximum reward (based on priorities)\n// RESULT (K=2,T=3): [35.557181022719995,35.58142127696651] (grid resolution 20)\nR{\"priority\"}max=?[F sched=0 & t=T-1 & k=K-1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/nonobs-target.prism",
    "content": "pomdp\n\nobservables o endobservables\n\nmodule M\n\n\ts : [0..10];\n\to : [0..3];\n\t\n\t[] s=0 -> 0.5:(s'=1)&(o'=1) + 0.5:(s'=2)&(o'=1);\n\t[g1] o=1 -> (o'=(s=1)?2:3);\n\t[g2] o=1 -> (o'=(s=2)?2:3);\n//\t[] s=3 -> 0.5:(s'=4) + 0.5:(s'=5);\n\t[] o>=2 -> true;\n\t\t\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/nonobs-target.prism.props",
    "content": "// RESULT: 0.5\nPmax=? [ F o=2 ];\n\n// RESULT: Error:observable\nPmax=? [ F o>=2&s=2 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/pomdps/nonobs-target.prism.props.args",
    "content": "-gridresolution 50\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/example1.prism",
    "content": "// Example 1 from\r\n// \"Verification and Control of Partially Observable Probabilistic Real-Time Systems\"\r\n// Norman/Parker/Zou, FORMATS 2015\r\n// Or Example 3 from\r\n// \"Verification and Control of Partially Observable Probabilistic Systems\"\r\n// Norman/Parker/Zou, Real-Time Systems, 53(3), 2017\r\n\r\npopta\r\n\r\nobservables\r\n\tx, y, o\r\nendobservables\r\n\r\nmodule M\r\n\r\n\tl : [0..5] init 0;\r\n\to : [0..4] init 0; // 0, 1&2, 3, 4, 5\r\n\tx : clock;\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t\t(l=0 => x<=1) &\r\n\t\t(l=1 => true) &\r\n\t\t(l=2 => true) &\r\n\t\t(l=3 => true) &\r\n\t\t(l=4 => true) &\r\n\t\t(l=5 => true)\r\n\tendinvariant\r\n\r\n\t[a0] l=0 & x>=1 -> 1/2 : (l'=1)&(o'=1) + 1/2 : (l'=2)&(o'=1);\r\n\t[a] l=1 -> (l'=3)&(o'=2);\r\n\t[a] l=2 -> (l'=4)&(o'=3)&(x'=0);\r\n\t[b] l=3 & y=1 -> (l'=5)&(o'=4);\r\n\t[b] l=4 & y=2 & x=0 -> (l'=5)&(o'=4);\r\n\r\nendmodule\r\n\r\nlabel \"goal\" = o=4;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/example1.prism.props",
    "content": "// RESULT: 0.5\r\nPmax=? [ F \"goal\" ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/example2.prism",
    "content": "// Example 2 from\r\n// \"Verification and Control of Partially Observable Probabilistic Real-Time Systems\"\r\n// Norman/Parker/Zou, FORMATS 2015\r\n// Or Example 4 from\r\n// \"Verification and Control of Partially Observable Probabilistic Systems\"\r\n// Norman/Parker/Zou, Real-Time Systems, 53(3), 2017\r\n\r\npopta\r\n\r\nobservables x, o endobservables\r\n\r\nmodule M\r\n\r\n\tx : clock;\r\n\tl : [0..3] init 0;\r\n\to : [0..2] init 0; // 0, 1&2, 3\r\n\r\n\tinvariant\r\n\t\t(l=0 => x<=1) &\r\n\t\t(l=1 => x<=2) &\r\n\t\t(l=2 => x<=2) &\r\n\t\t(l=3 => true)\r\n\tendinvariant\r\n\r\n\t[a0] l=0 & x<=1 -> 1/2 : (l'=1)&(o'=1) + 1/2 : (l'=2)&(o'=1)&(x'=0);\r\n\t\r\n\t[a1] l=1 & x<=2 -> (l'=3)&(o'=2);\r\n\t[a2] l=1 & x<=2 -> (l'=3)&(o'=2);\r\n\t\r\n\t[a1] l=2 & x<=2 -> (l'=3)&(o'=2);\r\n\t[a2] l=2 & x<=2 -> (l'=3)&(o'=2);\r\n\r\nendmodule\r\n\r\nlabel \"goal\" = o=2;\r\n\r\nrewards\r\n\t[a2] l=1 : 1;\r\n\t[a1] l=2 : 1;\r\n\tl=0 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/example2.prism.props",
    "content": "// RESULT: 0.5\r\nRmin=? [ F \"goal\" ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/pump_popta.prism",
    "content": "// POPTA model of NRL pump\n// dxp/gxn 28/08/14\n\n// high is trying to send either 0 or 1 to low through a number of messages\n// we assume high uses delays h0 and h1 to transmit either 0 or 1\n// also assume high always sends with this delay\n// so this is the average recorded by the pump\n// low sends repeated messages to try and figure out what high is transmitting\n// based on the time until it receives acks for the messages from the pump\n\n// model is a POPTA\npopta\n\n// can see the state of the pump and its local variables and all clocks\nobservables\n\th, p, l, m, guess, correct, x, y\nendobservables\n\n// delays for high sending 0 and 1 (both need to be >1)\nconst int h0;\nconst int h1;\n\n// number of messages low can send before guessing\nconst int N;\n\n// timeout for low (means a nack and low resends message)\nconst int Tout = 10;\n\n// we do not need to model high getting messages and sending acks\n// as we assume the delay is fixed (depending on what it is trying to send to low)\n// and only the average time for high to respond influence the time the pump\n// delays before sending acks to low\n\nmodule high\n\n\th : [0..1] init 0; // local state\n\t// 0 choose bit\n\t// 1 done\n\t\n\tbit : [-1..1] init -1; // bit high is trying transmit\n\n\t// randomly choose bit it is trying to send to low\n\t[] h=0 -> 1/2 : (h'=1)&(bit'=0) + 1/2 : (h'=1)&(bit'=1);\n\nendmodule\n\nmodule pump\n\t\n\tp : [0..2] init 0; // local state\n\t// 0 get message from low\n\t// 1 delaying before ack\n\t// 2 sending ack\n\t\n\ty : clock; // the pump's clock\n\n\tinvariant\n    \t(p=0 => true) &\n    \t(p=1 => y<=1) &\n        (p=2 => y<=0)\n    endinvariant\n\t\n\t// get message from low (need high to choose first)\n\t[mess_l] p=0 & bit>=0 -> (p'=1) & (y'=0);\n\t\n\t// random delay before ack based on average from high\n\t// this would be letting time pass PTA model\n\t[] p=1 & bit=0 & y=1 -> 1/h0 : (p'=2) & (y'=0) + (1 - 1/h0) : (p'=1) & (y'=0); // av. response high equals h0\t\n\t[] p=1 & bit=1 & y=1 -> 1/h1 : (p'=2) & (y'=0) + (1 - 1/h1) : (p'=1) & (y'=0); // av. response high equals h1\n\n\t// receives a new message from low\n\t// this means low timed out (nack)\n\t// so delete old message and start sending an ack for the new message\n\t[mess_l] p>0 -> (p'=0) & (y'=0);\n\t\n\t// send ack (immediately)\n\t[ack_l] p=2 -> (p'=0);\n\t\nendmodule\n\nmodule low\n\n\tl : [0..3] init 0; // local state of low\n\t// 0 send message\n\t// 1 waiting for ack\n\t// 2 guess/check value\n\t// 3 done\n\t\n\tm : [0..N] init 1; // messages low can send before guessing\n\tguess : [-1..1] init -1; // guess low makes\n\tcorrect : [0..1] init 0; // is it correct or not\n\n\tx : clock; // low's clock\n\n\tinvariant\n    \t(l=0 => x<=0) &\n    \t(l=1 => x<=Tout) &\n        (l=2 => x<=0) &\n        (l=3 => true)\n    endinvariant\n\n\t[mess_l] l=0 -> (l'=1) & (x'=0); // low immediately sends message and waits for an ack\n\t[ack_l] l=1 & m<N & x<=Tout -> (l'=0) & (m'=m+1) & (x'=0); // ack (more to send) \n\t[ack_l] l=1 & m=N & x<=Tout -> (l'=2) & (x'=0); // ack (time to guess)\n\t[nack_l] l=1 & x=Tout -> (l'=0) & (x'=0); // timeout (nack)\n\t\t\n\t// when finished sending immediately guess value high was trying to send\n\t[guess0] l=2 & guess=-1 & x=0 -> (guess'=0);\n\t[guess1] l=2 & guess=-1 & x=0 -> (guess'=1);\n\t// and then immediately check if it is correct\n\t[] l=2 & guess>=0 & guess=bit  & x=0 -> (l'=3) & (correct'=1);\n\t[] l=2 & guess>=0 & guess!=bit & x=0 -> (l'=3);\n\t\nendmodule\n\n// reward structures\n// time\nrewards \"time\"\n        true : 1;\nendrewards\n\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/pump_popta.prism.args",
    "content": "-const h0=2,h1=16,N=3\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/pump_popta.prism.props",
    "content": "const int D;\n\n// RESULT (h0=2,h1=16,N=3): [0.020656523490556817,0.026807197082692098] (grid resolution 16)\nPmin=? [ F correct=1 ]\n\n// RESULT (h0=2,h1=16,N=3): [0.9731909334062754,0.9793309413525038] (grid resolution 16)\nPmax=? [ F correct=1 ]\n\n// RESULT (h0=2,h1=16,N=3,D=25): [0.022890048319850906,0.02541857957662759] (grid resolution 32)\nPmin=? [ F<=D correct=1 ]\n\n// RESULT (h0=2,h1=16,N=3,D=25): [0.5274229036098491,0.5301895230846264] (grid resolution 32)\nPmax=? [ F<=D correct=1 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/pump_popta.prism.props.args",
    "content": "-const D=25\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/pump_popta_deadline.prism",
    "content": "pomdp\n\n// can see the state of the pump and its local variables and all clocks\nobservables\n\th, p, l, m, guess, correct, x, y, t\nendobservables\n\nlabel \"invariants\" = (p=0=>true)&(p=1=>y<=1)&(p=2=>y<=0)&(l=0=>x<=0)&(l=1=>x<=Tout)&(l=2=>x<=0)&(l=3=>true);\n\nconst int h0;\nconst int h1;\nconst int N;\nconst int Tout = 10;\n\nconst int D; // deadline\nmodule timer\n\n\t// global time\n\tt : [0..D+1];\n        \n    // time increases\n    [time] (t<D) -> (t'=min(t+1,D+1));\n    // loop when deadline has passed\n    [] (t>D) -> (t'=t);\n        \nendmodule\n\n\nmodule high\n\n\th : [0..1] init 0;\n\tbit : [-1..1] init -1;\n\t[] h=0 -> 1/2 : (h'=1)&(bit'=0) + 1/2 : (h'=1)&(bit'=1);\n\t[time] true -> 1.0 : true;\n\nendmodule\n\nmodule pump\n\n\tp : [0..2] init 0;\n\ty : [0..2];\n\n\t[mess_l] p=0&bit>=0 -> (p'=1) & (y'=0);\n\t[] p=1&bit=0&y=1 -> 1/h0 : (p'=2) & (y'=0) + (1-1/h0) : (p'=1) & (y'=0);\n\t[] p=1&bit=1&y=1 -> 1/h1 : (p'=2) & (y'=0) + (1-1/h1) : (p'=1) & (y'=0);\n\t[mess_l] p>0 -> (p'=0) & (y'=0);\n\t[ack_l] p=2 -> (p'=0);\n\t[time] (p=0=>true)&(p=1=>y+1<=1)&(p=2=>y+1<=0) -> 1.0 : (y'=min(y+1, 2));\n\nendmodule\n\nmodule low\n\n\tl : [0..3] init 0;\n\tm : [0..N] init 1;\n\tguess : [-1..1] init -1;\n\tcorrect : [0..1] init 0;\n\tx : [0..11];\n\n\t[mess_l] l=0 -> (l'=1) & (x'=0);\n\t[ack_l] l=1&m<N&x<=Tout -> (l'=0) & (m'=m+1) & (x'=0);\n\t[ack_l] l=1&m=N&x<=Tout -> (l'=2) & (x'=0);\n\t[nack_l] l=1&x=Tout -> (l'=0) & (x'=0);\n\t[guess0] l=2&guess=-1&x=0 -> (guess'=0);\n\t[guess1] l=2&guess=-1&x=0 -> (guess'=1);\n\t[] l=2&guess>=0&guess=bit&x=0&t<=D -> (l'=3) & (correct'=1);\n\t[] l=2&guess>=0&guess!=bit&x=0&t<=D -> (l'=3);\n\t[time] (l=0=>x+1<=0)&(l=1=>x+1<=Tout)&(l=2=>x+1<=0)&(l=3=>true) -> 1.0 : (x'=min(x+1, 11));\n\nendmodule\n\nrewards \"time\" \n\n\t[time] true : 1;\n\nendrewards\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/pump_popta_deadline.prism.args",
    "content": "-const h0=2,h1=8,N=4,D=25\n"
  },
  {
    "path": "prism-tests/functionality/verify/poptas/pump_popta_deadline.prism.props",
    "content": "// RESULT (h0=2,h1=8,N=4,D=25): [0.04801036199374414,0.054256665101135595] (grid resolution 16)\nPmin=? [ F correct=1 ]\n\n// RESULT (h0=2,h1=8,N=4,D=25): [0.5777239051355592,0.5845244516132015] (grid resolution 16)\nPmax=? [ F correct=1 ]\n\n//Rmin=? [ F l=2 ]\n\n//Rmin=? [ F l=2 ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/propertyrefs-pta.nm",
    "content": "pta\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/propertyrefs-pta.nm.props",
    "content": "const int x = 6;\n\n// RESULT: 1/6\n\"six\": Pmax=? [ F s=7 & \"d6\" ];\n\n\"d6\": d=x;\n"
  },
  {
    "path": "prism-tests/functionality/verify/propertyrefs-pta.nm.props.args",
    "content": "-prop six\n"
  },
  {
    "path": "prism-tests/functionality/verify/propertyrefs.pm",
    "content": "dtmc\r\n\r\nmodule die\r\n\r\n\t// local state\r\n\ts : [0..7] init 0;\r\n\t// value of the die\r\n\td : [0..6] init 0;\r\n\t\r\n\t[] s=0 -> 0.5 : (s'=1) + 0.5 : (s'=2);\r\n\t[] s=1 -> 0.5 : (s'=3) + 0.5 : (s'=4);\r\n\t[] s=2 -> 0.5 : (s'=5) + 0.5 : (s'=6);\r\n\t[] s=3 -> 0.5 : (s'=1) + 0.5 : (s'=7) & (d'=1);\r\n\t[] s=4 -> 0.5 : (s'=7) & (d'=2) + 0.5 : (s'=7) & (d'=3);\r\n\t[] s=5 -> 0.5 : (s'=7) & (d'=4) + 0.5 : (s'=7) & (d'=5);\r\n\t[] s=6 -> 0.5 : (s'=2) + 0.5 : (s'=7) & (d'=6);\r\n\t[] s=7 -> (s'=7);\r\n\t\r\nendmodule\r\n\r\nrewards \"coin_flips\"\r\n\t[] s<7 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/propertyrefs.pm.props",
    "content": "const int x = 6;\n\n// RESULT: 0.5\n\"six\": P=? [ F s=7 & d=6 ] + \"x\";\n\n\"x\": P=? [ F s=7 & d=x ] + \"six2\";\n\n\"six2\": P=? [ F s=7 & d=6 ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/propertyrefs.pm.props.args",
    "content": "-prop six\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-diag.nm",
    "content": "// prism model of pta version of zeroconf\r\n// using digitial clocks\r\n\r\npta\r\n\r\nconst int probes_max = 4;\r\n\r\nmodule sender\r\n\r\n\ts : [0..2]; //local state\r\n\tprobes : [0..probes_max]; // probes sent\r\n\tip : [0..2]; // ip address not chosen, fresh or in use\r\n\tx : clock; // local clock\r\n\tz : clock; // local clock\r\n\r\n\tinvariant\r\n\t(s=0 => x<=z) &\r\n\t(s=1 => x<=20) &\r\n\t(s=2 => true)\r\n\tendinvariant\r\n\r\n\t// selct probe\t\r\n\t// [] s=0 -> 0.99969242125984251969 : (s'=1) & (ip'=0) + 0.00030757874015748031 : (s'=1) & (ip'=1);\r\n\t[] s=0 -> 0.5 : (s'=1) & (ip'=1) + 0.5 : (s'=1) & (ip'=2);\r\n\t// send probes\r\n\t[send_used]  s=1 & x=20 & ip=2 & probes<probes_max -> (probes'=probes+1) & (x'=0);\t\r\n\t[send_fresh] s=1 & x=20 & ip=1 & probes<probes_max -> (probes'=probes+1) & (x'=0);\r\n\t[] s=1 & x=20 & probes=probes_max -> (s'=2) & (x'=0);\r\n\t[recv] s=1 -> (s'=0) & (x'=0) & (ip'=0) & (probes'=0);\r\n\t[] s=2 -> true;\r\n\r\nendmodule\r\n\r\nmodule environment\r\n\t\r\n\te : [0..2]; // ready, send reply\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t(e=0 => true) &\r\n\t(e>=1 => y<=5)\r\n\tendinvariant\r\n\r\n\t[send_fresh] e=0 -> true;\r\n\t[send_used]  e=0 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=1) & (y'=0);\r\n\t[] e=1 & y>=1 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=2) & (y'=0);\r\n\t[recv] e=2 & y>=1 -> (e'=0) & (y'=0);\r\n\r\nendmodule\r\n\r\n\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n//label \"incorrect\" = s=2 & ip=2;\r\nlabel \"done\" = s=2;\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-diag.nm.props",
    "content": "// RESULT: Error:diagonal\r\n\"incorrect\": Pmax=? [ F s=2 & ip=2 ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-diag.nm.props.args",
    "content": "-ptamethod digital\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-diag2.nm",
    "content": "// PTA used as running example in FORMATS'09 paper\r\n// (modified version of)\r\n\r\npta\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\tx : clock;\r\n\ty : clock;\r\n\t\r\n\t[] s=0 -> 0.6 : (s'=1) + 0.4 : (s'=2)&(x'=0);\r\n\t[] s=1 & x=0 -> (s'=3);\r\n\t[] s=1 & y>=2 -> (s'=1)&(y'=0);\r\n\t[] s=2 & x=0 & y=1 -> (s'=3)&(y'=0);\r\n\t[] s=2 & x>=2 -> (s'=1)&(y'=0);\r\n\t[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"target\" = s=3;\r\nlabel \"end\" = s=3 | s=1;\r\n\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-diag2.nm.props",
    "content": "label \"target2\" = s=3 & x<=y;\r\n\r\nlabel \"target3\" = x=y;\r\n\r\n// RESULT: Error:diagonal\r\nPmax=? [ F \"target\" & x>=y ];\r\n\r\n// RESULT: Error:diagonal\r\nPmax=? [ F \"target2\" ];\r\n\r\n// RESULT: Error:diagonal\r\nPmax=? [ F \"target3\" ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-diag2.nm.props.args",
    "content": "-ptamethod digital\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-nested.nm",
    "content": "// Example showing that digital clocks can't do nested properties, from:\r\n// Marta Kwiatkowska, Gethin Norman, David Parker and Jeremy Sproston.\r\n// Performance Analysis of Probabilistic Timed Automata using Digital Clocks.\r\n// Formal Methods in System Design, 29, pages 33-78, Springer. August 2006.\r\n// (Fig 4, p.33)\r\n\r\n// The example is not actually used, since none of the implemented methods\r\n// can check nested properties\r\n\r\npta\r\n\r\nmodule M\r\n\r\n\tl : [0..1];\r\n\tx : clock;\r\n\r\n\tinvariant\r\n\t(l=0 => (x>=0 & x<=3)) &\r\n\t(l=2 => true)\r\n\tendinvariant\r\n\r\n\t[]  l=0 & x>=3 -> (l'=1);\r\n\t[]  l=0 & x<=3 -> (l'=1);\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-nested.nm.props",
    "content": "// RESULT: Error:nested\n//P<1 [ F P<1 [ F<=1 l=1 ] ];\n\n// RESULT: Error:nested\nP<1 [ F P<1 [ F l=1 ] ];\n\n// RESULT: Error:nested\nP<1 [ F R<1 [ F l=1 ] ];\n\n// RESULT: Error:nested\nR<1 [ F P<1 [ F l=1 ] ];\n\n// RESULT: Error:nested\nR<1 [ F R<1 [ F l=1 ] ];\n\n// RESULT: false\n\"inner\": P<1 [ F l=1 ];\n\n// RESULT: Error:nested\nPmax=? [ F \"inner\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-nested.nm.props.args",
    "content": "-ptamethod digital\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-strict.nm",
    "content": "// PTA used as running example in FORMATS'09 paper\r\n\r\npta\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\tx : clock;\r\n\ty : clock;\r\n\t\r\n\t[] s=0 -> 0.6 : (s'=1) + 0.4 : (s'=2)&(x'=0);\r\n\t[] s=1 & x=0 -> (s'=3);\r\n\t[] s=1 & y>2 -> (s'=1)&(y'=0);\r\n\t[] s=2 & x=0 & y=1 -> (s'=3)&(y'=0);\r\n\t[] s=2 & x>2 -> (s'=1)&(y'=0);\r\n\t[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"target\" = s=3;\r\nlabel \"end\" = s=3 | s=1;\r\n\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-strict.nm.props",
    "content": "// RESULT: Error:strict\r\nPmax=? [ F \"target\" ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-strict.nm.props.args",
    "content": "-ptamethod digital\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-strict2.nm",
    "content": "// PTA used as running example in FORMATS'09 paper\r\n// (modified version of)\r\n\r\npta\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\tx : clock;\r\n\ty : clock;\r\n\t\r\n\t[] s=0 -> 0.6 : (s'=1) + 0.4 : (s'=2)&(x'=0);\r\n\t[] s=1 & x=0 -> (s'=3);\r\n\t[] s=1 & y>=2 -> (s'=1)&(y'=0);\r\n\t[] s=2 & x=0 & y=1 -> (s'=3)&(y'=0);\r\n\t[] s=2 & x>=2 -> (s'=1)&(y'=0);\r\n\t[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"target\" = s=3;\r\nlabel \"end\" = s=3 | s=1;\r\n\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-strict2.nm.props",
    "content": "label \"target2\" = s=3 & x<2;\r\n\r\n// RESULT: 0.6\r\nPmax=? [ F \"target\" ]\r\n\r\n// RESULT: Error:strict\r\nPmax=? [ F (s=3 & x<2) ]\r\n\r\n// RESULT: Error:strict\r\nPmax=? [ F \"target2\" ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/digital-strict2.nm.props.args",
    "content": "-ptamethod digital\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/initstates.nm",
    "content": "// prism model of pta version of zeroconf\r\n// using digitial clocks\r\n\r\npta\r\n\r\nconst int probes_max = 4;\r\n\r\nmodule sender\r\n\r\n\ts : [0..2]; //local state\r\n\tprobes : [0..probes_max]; // probes sent\r\n\tip : [0..2]; // ip address not chosen, fresh or in use\r\n\tx : clock; // local clock\r\n\r\n\tinvariant\r\n\t(s=0 => x<=0) &\r\n\t(s=1 => x<=20) &\r\n\t(s=2 => true)\r\n\tendinvariant\r\n\r\n\t// selct probe\t\r\n\t// [] s=0 -> 0.99969242125984251969 : (s'=1) & (ip'=0) + 0.00030757874015748031 : (s'=1) & (ip'=1);\r\n\t[] s=0 -> 0.5 : (s'=1) & (ip'=1) + 0.5 : (s'=1) & (ip'=2);\r\n\t// send probes\r\n\t[send_used]  s=1 & x=20 & ip=2 & probes<probes_max -> (probes'=probes+1) & (x'=0);\t\r\n\t[send_fresh] s=1 & x=20 & ip=1 & probes<probes_max -> (probes'=probes+1) & (x'=0);\r\n\t[] s=1 & x=20 & probes=probes_max -> (s'=2) & (x'=0);\r\n\t[recv] s=1 -> (s'=0) & (x'=0) & (ip'=0) & (probes'=0);\r\n\t[] s=2 -> true;\r\n\r\nendmodule\r\n\r\nmodule environment\r\n\t\r\n\te : [0..2]; // ready, send reply\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t(e=0 => true) &\r\n\t(e>=1 => y<=5)\r\n\tendinvariant\r\n\r\n\t[send_fresh] e=0 -> true;\r\n\t[send_used]  e=0 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=1) & (y'=0);\r\n\t[] e=1 & y>=1 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=2) & (y'=0);\r\n\t[recv] e=2 & y>=1 -> (e'=0) & (y'=0);\r\n\r\nendmodule\r\n\r\n\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n//label \"incorrect\" = s=2 & ip=2;\r\nlabel \"done\" = s=2;\r\n\r\ninit true endinit\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/initstates.nm.props",
    "content": "// RESULT: Error:initial\r\n\"incorrect\": Pmax=? [ F s=2 & ip=2 ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/initstates.nm.props.args",
    "content": "-ptamethod games\n-ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/timelock.nm",
    "content": "// prism model of pta version of zeroconf\r\n// using digitial clocks\r\n\r\npta\r\n\r\nconst int probes_max = 4;\r\n\r\nmodule sender\r\n\r\n\ts : [0..2]; //local state\r\n\tprobes : [0..probes_max]; // probes sent\r\n\tip : [0..2]; // ip address not chosen, fresh or in use\r\n\tx : clock; // local clock\r\n\r\n\tinvariant\r\n\t(s=0 => x<=0) &\r\n\t(s=1 => x<=20) &\r\n\t(s=2 => true)\r\n\tendinvariant\r\n\r\n\t// selct probe\t\r\n\t// [] s=0 -> 0.99969242125984251969 : (s'=1) & (ip'=0) + 0.00030757874015748031 : (s'=1) & (ip'=1);\r\n\t[] s=0 -> 0.5 : (s'=1) & (ip'=1) + 0.5 : (s'=1) & (ip'=2);\r\n\t// send probes\r\n\t[send_used]  s=1 & x=20 & ip=2 & probes<probes_max -> (probes'=probes+1) & (x'=0);\t\r\n\t[send_fresh] s=1 & x=20 & ip=1 & probes<probes_max -> (probes'=probes+1) & (x'=0);\r\n\t//[] s=1 & x=20 & probes=probes_max -> (s'=2) & (x'=0);\r\n\t//[recv] s=1 -> (s'=0) & (x'=0) & (ip'=0) & (probes'=0);\r\n\t[] s=2 -> true;\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/timelock.nm.props",
    "content": "// RESULT: Error:timelock\r\n\"incorrect\": Pmax=? [ F s=2 & ip=2 ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/notallowed/timelock.nm.props.args",
    "content": "-ptamethod digital\n-ptamethod games\n# -ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/csma.nm",
    "content": "// CSMA/CD protocol - two stations (PTA model using digital clocks)\r\n// gxn/mxd 31/05/05\r\n\r\n// based on kronos (non-probabilistic) TA model and that which appears in:\r\n// M. Duflot, L. Fribourg, T. Hrault, R. Lassaigne, F. Magniette, S. Messika, S. Peyronnet and C. Picaronny\r\n// Probabilistic model checking of the CSMA/CD protocol using PRISM and APMC\r\n// In Proc. AVoCS'04, 2004\r\n\r\npta\r\n\r\n// PARAMETERS\r\n\r\n// parameters\r\nconst int sigma=26; // time for messages to propagate along the bus\r\nconst int lambda=808; // time to send a message\r\nconst int delay=26; // wire delay\r\nconst int slot=2*sigma; // size of back off slot\r\n\r\nconst int K; // exponential backoff limit (sometimes called bmax)\r\nconst int M=pow(2,K)-1; // max number of slots to wait\r\n\r\nconst int COL; // max number of collisions (called K in an old version of this model)\r\n\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// collision counter\r\nmodule collisions\r\n\r\n\tc : [0..max(1,COL)];\r\n\r\n\t[csend1] true -> (c'=min(COL,c+1));\r\n\t[csend2] true -> (c'=min(COL,c+1));\r\n\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// the bus\r\nmodule bus\r\n\t\r\n\tb : [0..4];\r\n\t// b=0 - idle\r\n\t// b=1 - active\r\n\t// b=2 - collision\r\n\t// b=3 - collision1\r\n\t// b=4 - collision2\r\n\t\r\n\ty1 : clock; // clock of bus\r\n\ty2 : clock; // clock of bus\r\n\r\n\tinvariant\r\n\t\t(b=0 => true) &\r\n\t\t(b=1 => true) &\r\n\t\t(b=2 => y1<=delay & y2<=delay) &\r\n\t\t(b=3 => y1<=delay) &\r\n\t\t(b=4 => y2<=delay)\r\n\tendinvariant\r\n\t\r\n\t// stations starts sending\r\n\t[send1] b=0 -> (b'=1) & (y1'=0); // no message being sent\r\n\t[send2] b=0 -> (b'=1) & (y2'=0); // no message being sent\r\n\t\r\n\t// collision occurs\r\n\t[csend1] b=1 & y2<=delay -> (b'=2) & (y1'=0); // message being sent (move to collision)\r\n\t[csend2] b=1 & y1<=delay -> (b'=2) & (y2'=0); // message being sent (move to collision)\r\n\t\r\n\t// message being sent\r\n\t[busy1] b=1 & y2>delay -> (b'=1);\r\n\t[busy2] b=1 & y1>delay -> (b'=1);\r\n\t\r\n\t// station finishes\r\n\t[end1] b=1 -> (b'=0) & (y1'=0);\r\n\t[end2] b=1 -> (b'=0) & (y2'=0);\r\n\t\r\n\t// collision detected\r\n\t[cd1] b=2 & y1>=delay -> (b'=4); // station one detects collision before station two\r\n\t[cd2] b=2 & y2>=delay -> (b'=3); // station two detects collision before station one\r\n\r\n\t[cd1] b=3 & y1>=delay -> (b'=0) & (y1'=0) & (y2'=0); // station one detects collision after station two\r\n\t[cd2] b=4 & y2>=delay -> (b'=0) & (y1'=0) & (y2'=0); // station two detects collision after station one\r\n\t\t\r\nendmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// STATION 1\r\nmodule station1\r\n\t\r\n\t// LOCAL STATE\r\n\ts1 : [0..4];\r\n\t// s1=0 - initial state\r\n\t// s1=1 - transmit\r\n\t// s1=2 - collision (set backoff)\r\n\t// s1=3 - wait (bus busy)\r\n\t// s1=4 - done (since sending only one message)\r\n\t\r\n\tx1 : clock; // local clock\r\n\r\n\tcd1 : [0..K]; // collision counter\r\n\r\n\tinvariant\r\n\t\t(s1=0 => x1<=delay) &\r\n\t\t(s1=1 => x1<=lambda) &\r\n\t\t(s1=2 => x1<=0) &\r\n\t\t(s1=3 => x1<=pow(2,cd1)*slot) &\r\n\t\t(s1=4 => true)\r\n\tendinvariant\r\n\t\r\n\t// start sending (make sure there is a collision, i.e. start before x1 equals delay)\r\n\t[send1]  s1=0 -> (s1'=1) & (x1'=0); // start sending\r\n\t[csend1] s1=0 -> (s1'=1) & (x1'=0); // start sending\r\n\t[busy1] s1=0 -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // detects channel is busy so go into backoff\r\n\t\r\n\t// transmitting\r\n\t[end1] s1=1 & x1=lambda -> (s1'=4) & (x1'=0); // finished\r\n\t[cd1] s1=1 -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // collision detected\r\n\t\r\n\t// set backoff (no time can pass in this state)\r\n\t// first retransmission\r\n\t[] s1=2 & cd1=1 -> 1/2 : (s1'=3) & (x1'=0*slot) \r\n\t                 + 1/2 : (s1'=3) & (x1'=1*slot);\r\n\t// second retransmission\r\n\t[] s1=2 & cd1=2 -> 1/4 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/4 : (s1'=3) & (x1'=3*slot);\r\n\t// third retransmission\r\n\t[] s1=2 & cd1=3 -> 1/8 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/8 : (s1'=3) & (x1'=7*slot);\r\n\t// fourth retransmission \r\n\t[] s1=2 & cd1=4 -> 1/16 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/16 : (s1'=3) & (x1'=15*slot);\r\n\t// fifth retransmission\r\n\t[] s1=2 & cd1=5 -> 1/32 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/32 : (s1'=3) & (x1'=31*slot);\r\n\t// sixth retransmission\r\n\t[] s1=2 & cd1=6 -> 1/64 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=31*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=32*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=33*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=34*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=35*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=36*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=37*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=38*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=39*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=40*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=41*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=42*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=43*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=44*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=45*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=46*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=47*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=48*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=49*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=50*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=51*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=52*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=53*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=54*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=55*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=56*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=57*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=58*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=59*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=60*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=61*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=62*slot)\r\n\t                 + 1/64 : (s1'=3) & (x1'=63*slot);\r\n\t// seventh retransmission\r\n\t[] s1=2 & cd1=7 -> 1/128 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=31*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=32*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=33*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=34*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=35*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=36*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=37*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=38*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=39*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=40*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=41*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=42*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=43*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=44*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=45*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=46*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=47*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=48*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=49*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=50*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=51*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=52*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=53*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=54*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=55*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=56*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=57*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=58*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=59*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=60*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=61*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=62*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=63*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=64*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=65*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=66*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=67*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=68*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=69*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=70*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=71*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=72*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=73*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=74*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=75*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=76*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=77*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=78*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=79*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=80*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=81*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=82*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=83*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=84*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=85*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=86*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=87*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=88*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=89*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=90*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=91*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=92*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=93*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=94*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=95*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=96*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=97*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=98*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=99*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=100*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=101*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=102*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=103*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=104*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=105*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=106*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=107*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=108*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=109*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=110*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=111*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=112*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=113*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=114*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=115*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=116*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=117*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=118*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=119*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=120*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=121*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=122*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=123*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=124*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=125*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=126*slot)\r\n\t                 + 1/128 : (s1'=3) & (x1'=127*slot);\r\n\t// eigth retransmission\r\n\t[] s1=2 & cd1=8 -> 1/256 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=31*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=32*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=33*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=34*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=35*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=36*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=37*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=38*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=39*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=40*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=41*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=42*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=43*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=44*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=45*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=46*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=47*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=48*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=49*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=50*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=51*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=52*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=53*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=54*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=55*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=56*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=57*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=58*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=59*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=60*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=61*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=62*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=63*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=64*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=65*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=66*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=67*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=68*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=69*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=70*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=71*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=72*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=73*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=74*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=75*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=76*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=77*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=78*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=79*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=80*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=81*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=82*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=83*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=84*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=85*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=86*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=87*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=88*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=89*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=90*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=91*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=92*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=93*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=94*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=95*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=96*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=97*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=98*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=99*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=100*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=101*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=102*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=103*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=104*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=105*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=106*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=107*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=108*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=109*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=110*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=111*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=112*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=113*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=114*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=115*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=116*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=117*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=118*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=119*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=120*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=121*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=122*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=123*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=124*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=125*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=126*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=127*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=128*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=129*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=130*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=131*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=132*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=133*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=134*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=135*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=136*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=137*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=138*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=139*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=140*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=141*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=142*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=143*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=144*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=145*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=146*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=147*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=148*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=149*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=150*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=151*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=152*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=153*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=154*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=155*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=156*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=157*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=158*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=159*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=160*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=161*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=162*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=163*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=164*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=165*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=166*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=167*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=168*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=169*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=170*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=171*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=172*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=173*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=174*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=175*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=176*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=177*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=178*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=179*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=180*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=181*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=182*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=183*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=184*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=185*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=186*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=187*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=188*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=189*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=190*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=191*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=192*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=193*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=194*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=195*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=196*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=197*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=198*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=199*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=200*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=201*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=202*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=203*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=204*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=205*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=206*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=207*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=208*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=209*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=210*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=211*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=212*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=213*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=214*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=215*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=216*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=217*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=218*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=219*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=220*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=221*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=222*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=223*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=224*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=225*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=226*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=227*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=228*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=229*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=230*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=231*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=232*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=233*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=234*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=235*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=236*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=237*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=238*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=239*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=240*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=241*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=242*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=243*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=244*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=245*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=246*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=247*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=248*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=249*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=250*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=251*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=252*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=253*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=254*slot)\r\n\t                 + 1/256 : (s1'=3) & (x1'=255*slot);\r\n\t// ninth retransmission\r\n\t[] s1=2 & cd1=9 -> 1/512 : (s1'=3) & (x1'=0*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=1*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=2*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=3*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=4*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=5*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=6*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=7*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=8*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=9*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=10*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=11*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=12*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=13*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=14*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=15*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=16*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=17*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=18*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=19*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=20*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=21*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=22*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=23*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=24*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=25*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=26*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=27*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=28*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=29*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=30*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=31*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=32*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=33*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=34*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=35*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=36*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=37*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=38*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=39*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=40*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=41*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=42*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=43*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=44*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=45*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=46*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=47*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=48*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=49*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=50*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=51*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=52*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=53*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=54*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=55*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=56*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=57*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=58*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=59*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=60*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=61*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=62*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=63*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=64*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=65*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=66*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=67*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=68*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=69*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=70*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=71*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=72*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=73*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=74*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=75*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=76*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=77*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=78*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=79*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=80*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=81*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=82*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=83*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=84*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=85*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=86*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=87*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=88*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=89*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=90*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=91*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=92*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=93*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=94*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=95*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=96*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=97*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=98*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=99*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=100*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=101*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=102*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=103*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=104*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=105*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=106*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=107*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=108*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=109*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=110*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=111*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=112*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=113*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=114*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=115*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=116*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=117*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=118*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=119*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=120*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=121*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=122*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=123*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=124*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=125*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=126*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=127*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=128*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=129*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=130*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=131*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=132*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=133*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=134*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=135*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=136*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=137*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=138*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=139*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=140*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=141*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=142*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=143*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=144*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=145*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=146*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=147*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=148*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=149*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=150*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=151*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=152*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=153*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=154*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=155*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=156*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=157*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=158*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=159*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=160*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=161*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=162*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=163*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=164*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=165*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=166*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=167*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=168*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=169*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=170*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=171*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=172*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=173*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=174*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=175*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=176*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=177*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=178*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=179*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=180*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=181*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=182*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=183*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=184*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=185*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=186*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=187*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=188*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=189*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=190*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=191*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=192*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=193*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=194*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=195*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=196*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=197*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=198*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=199*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=200*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=201*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=202*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=203*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=204*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=205*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=206*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=207*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=208*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=209*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=210*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=211*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=212*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=213*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=214*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=215*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=216*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=217*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=218*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=219*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=220*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=221*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=222*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=223*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=224*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=225*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=226*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=227*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=228*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=229*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=230*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=231*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=232*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=233*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=234*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=235*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=236*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=237*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=238*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=239*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=240*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=241*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=242*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=243*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=244*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=245*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=246*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=247*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=248*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=249*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=250*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=251*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=252*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=253*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=254*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=255*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=256*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=257*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=258*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=259*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=260*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=261*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=262*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=263*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=264*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=265*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=266*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=267*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=268*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=269*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=270*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=271*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=272*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=273*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=274*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=275*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=276*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=277*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=278*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=279*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=280*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=281*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=282*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=283*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=284*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=285*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=286*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=287*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=288*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=289*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=290*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=291*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=292*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=293*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=294*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=295*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=296*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=297*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=298*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=299*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=300*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=301*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=302*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=303*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=304*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=305*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=306*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=307*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=308*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=309*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=310*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=311*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=312*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=313*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=314*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=315*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=316*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=317*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=318*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=319*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=320*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=321*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=322*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=323*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=324*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=325*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=326*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=327*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=328*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=329*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=330*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=331*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=332*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=333*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=334*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=335*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=336*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=337*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=338*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=339*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=340*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=341*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=342*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=343*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=344*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=345*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=346*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=347*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=348*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=349*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=350*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=351*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=352*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=353*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=354*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=355*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=356*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=357*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=358*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=359*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=360*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=361*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=362*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=363*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=364*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=365*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=366*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=367*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=368*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=369*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=370*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=371*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=372*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=373*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=374*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=375*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=376*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=377*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=378*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=379*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=380*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=381*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=382*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=383*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=384*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=385*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=386*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=387*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=388*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=389*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=390*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=391*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=392*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=393*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=394*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=395*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=396*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=397*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=398*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=399*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=400*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=401*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=402*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=403*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=404*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=405*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=406*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=407*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=408*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=409*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=410*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=411*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=412*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=413*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=414*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=415*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=416*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=417*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=418*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=419*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=420*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=421*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=422*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=423*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=424*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=425*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=426*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=427*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=428*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=429*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=430*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=431*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=432*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=433*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=434*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=435*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=436*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=437*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=438*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=439*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=440*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=441*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=442*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=443*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=444*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=445*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=446*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=447*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=448*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=449*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=450*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=451*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=452*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=453*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=454*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=455*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=456*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=457*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=458*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=459*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=460*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=461*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=462*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=463*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=464*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=465*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=466*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=467*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=468*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=469*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=470*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=471*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=472*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=473*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=474*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=475*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=476*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=477*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=478*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=479*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=480*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=481*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=482*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=483*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=484*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=485*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=486*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=487*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=488*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=489*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=490*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=491*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=492*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=493*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=494*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=495*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=496*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=497*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=498*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=499*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=500*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=501*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=502*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=503*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=504*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=505*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=506*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=507*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=508*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=509*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=510*slot)\r\n\t                 + 1/512 : (s1'=3) & (x1'=511*slot);\r\n\t// tenth (or more) retransmission\r\n\t[] s1=2 & cd1=10 -> 1/1024 : (s1'=3) & (x1'=0*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=2*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=3*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=4*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=5*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=6*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=7*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=8*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=9*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=10*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=11*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=12*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=13*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=14*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=15*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=16*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=17*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=18*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=19*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=20*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=21*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=22*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=23*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=24*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=25*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=26*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=27*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=28*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=29*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=30*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=31*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=32*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=33*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=34*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=35*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=36*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=37*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=38*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=39*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=40*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=41*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=42*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=43*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=44*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=45*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=46*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=47*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=48*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=49*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=50*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=51*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=52*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=53*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=54*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=55*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=56*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=57*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=58*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=59*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=60*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=61*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=62*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=63*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=64*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=65*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=66*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=67*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=68*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=69*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=70*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=71*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=72*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=73*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=74*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=75*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=76*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=77*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=78*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=79*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=80*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=81*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=82*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=83*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=84*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=85*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=86*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=87*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=88*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=89*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=90*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=91*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=92*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=93*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=94*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=95*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=96*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=97*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=98*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=99*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=100*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=101*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=102*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=103*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=104*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=105*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=106*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=107*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=108*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=109*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=110*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=111*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=112*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=113*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=114*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=115*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=116*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=117*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=118*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=119*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=120*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=121*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=122*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=123*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=124*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=125*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=126*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=127*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=128*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=129*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=130*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=131*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=132*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=133*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=134*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=135*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=136*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=137*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=138*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=139*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=140*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=141*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=142*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=143*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=144*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=145*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=146*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=147*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=148*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=149*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=150*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=151*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=152*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=153*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=154*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=155*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=156*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=157*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=158*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=159*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=160*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=161*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=162*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=163*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=164*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=165*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=166*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=167*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=168*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=169*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=170*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=171*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=172*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=173*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=174*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=175*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=176*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=177*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=178*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=179*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=180*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=181*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=182*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=183*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=184*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=185*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=186*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=187*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=188*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=189*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=190*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=191*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=192*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=193*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=194*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=195*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=196*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=197*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=198*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=199*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=200*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=201*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=202*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=203*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=204*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=205*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=206*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=207*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=208*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=209*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=210*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=211*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=212*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=213*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=214*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=215*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=216*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=217*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=218*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=219*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=220*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=221*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=222*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=223*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=224*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=225*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=226*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=227*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=228*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=229*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=230*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=231*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=232*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=233*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=234*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=235*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=236*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=237*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=238*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=239*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=240*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=241*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=242*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=243*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=244*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=245*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=246*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=247*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=248*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=249*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=250*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=251*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=252*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=253*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=254*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=255*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=256*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=257*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=258*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=259*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=260*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=261*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=262*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=263*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=264*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=265*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=266*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=267*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=268*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=269*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=270*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=271*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=272*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=273*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=274*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=275*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=276*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=277*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=278*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=279*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=280*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=281*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=282*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=283*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=284*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=285*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=286*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=287*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=288*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=289*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=290*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=291*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=292*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=293*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=294*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=295*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=296*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=297*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=298*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=299*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=300*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=301*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=302*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=303*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=304*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=305*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=306*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=307*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=308*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=309*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=310*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=311*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=312*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=313*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=314*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=315*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=316*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=317*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=318*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=319*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=320*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=321*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=322*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=323*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=324*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=325*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=326*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=327*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=328*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=329*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=330*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=331*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=332*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=333*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=334*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=335*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=336*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=337*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=338*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=339*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=340*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=341*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=342*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=343*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=344*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=345*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=346*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=347*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=348*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=349*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=350*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=351*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=352*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=353*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=354*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=355*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=356*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=357*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=358*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=359*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=360*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=361*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=362*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=363*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=364*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=365*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=366*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=367*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=368*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=369*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=370*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=371*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=372*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=373*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=374*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=375*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=376*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=377*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=378*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=379*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=380*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=381*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=382*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=383*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=384*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=385*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=386*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=387*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=388*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=389*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=390*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=391*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=392*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=393*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=394*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=395*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=396*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=397*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=398*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=399*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=400*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=401*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=402*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=403*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=404*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=405*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=406*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=407*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=408*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=409*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=410*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=411*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=412*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=413*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=414*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=415*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=416*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=417*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=418*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=419*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=420*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=421*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=422*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=423*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=424*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=425*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=426*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=427*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=428*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=429*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=430*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=431*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=432*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=433*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=434*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=435*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=436*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=437*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=438*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=439*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=440*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=441*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=442*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=443*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=444*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=445*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=446*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=447*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=448*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=449*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=450*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=451*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=452*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=453*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=454*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=455*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=456*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=457*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=458*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=459*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=460*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=461*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=462*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=463*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=464*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=465*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=466*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=467*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=468*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=469*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=470*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=471*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=472*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=473*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=474*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=475*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=476*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=477*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=478*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=479*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=480*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=481*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=482*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=483*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=484*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=485*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=486*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=487*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=488*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=489*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=490*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=491*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=492*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=493*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=494*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=495*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=496*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=497*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=498*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=499*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=500*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=501*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=502*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=503*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=504*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=505*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=506*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=507*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=508*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=509*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=510*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=511*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=512*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=513*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=514*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=515*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=516*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=517*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=518*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=519*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=520*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=521*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=522*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=523*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=524*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=525*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=526*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=527*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=528*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=529*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=530*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=531*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=532*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=533*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=534*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=535*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=536*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=537*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=538*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=539*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=540*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=541*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=542*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=543*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=544*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=545*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=546*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=547*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=548*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=549*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=550*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=551*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=552*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=553*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=554*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=555*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=556*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=557*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=558*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=559*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=560*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=561*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=562*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=563*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=564*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=565*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=566*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=567*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=568*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=569*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=570*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=571*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=572*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=573*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=574*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=575*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=576*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=577*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=578*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=579*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=580*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=581*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=582*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=583*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=584*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=585*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=586*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=587*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=588*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=589*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=590*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=591*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=592*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=593*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=594*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=595*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=596*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=597*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=598*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=599*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=600*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=601*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=602*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=603*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=604*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=605*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=606*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=607*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=608*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=609*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=610*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=611*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=612*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=613*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=614*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=615*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=616*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=617*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=618*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=619*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=620*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=621*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=622*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=623*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=624*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=625*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=626*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=627*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=628*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=629*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=630*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=631*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=632*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=633*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=634*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=635*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=636*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=637*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=638*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=639*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=640*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=641*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=642*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=643*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=644*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=645*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=646*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=647*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=648*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=649*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=650*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=651*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=652*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=653*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=654*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=655*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=656*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=657*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=658*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=659*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=660*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=661*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=662*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=663*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=664*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=665*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=666*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=667*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=668*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=669*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=670*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=671*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=672*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=673*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=674*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=675*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=676*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=677*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=678*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=679*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=680*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=681*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=682*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=683*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=684*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=685*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=686*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=687*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=688*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=689*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=690*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=691*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=692*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=693*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=694*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=695*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=696*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=697*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=698*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=699*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=700*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=701*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=702*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=703*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=704*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=705*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=706*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=707*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=708*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=709*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=710*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=711*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=712*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=713*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=714*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=715*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=716*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=717*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=718*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=719*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=720*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=721*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=722*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=723*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=724*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=725*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=726*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=727*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=728*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=729*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=730*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=731*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=732*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=733*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=734*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=735*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=736*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=737*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=738*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=739*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=740*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=741*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=742*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=743*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=744*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=745*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=746*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=747*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=748*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=749*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=750*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=751*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=752*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=753*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=754*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=755*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=756*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=757*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=758*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=759*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=760*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=761*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=762*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=763*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=764*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=765*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=766*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=767*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=768*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=769*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=770*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=771*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=772*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=773*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=774*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=775*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=776*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=777*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=778*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=779*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=780*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=781*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=782*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=783*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=784*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=785*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=786*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=787*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=788*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=789*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=790*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=791*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=792*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=793*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=794*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=795*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=796*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=797*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=798*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=799*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=800*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=801*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=802*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=803*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=804*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=805*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=806*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=807*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=808*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=809*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=810*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=811*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=812*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=813*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=814*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=815*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=816*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=817*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=818*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=819*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=820*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=821*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=822*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=823*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=824*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=825*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=826*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=827*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=828*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=829*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=830*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=831*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=832*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=833*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=834*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=835*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=836*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=837*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=838*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=839*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=840*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=841*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=842*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=843*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=844*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=845*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=846*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=847*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=848*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=849*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=850*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=851*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=852*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=853*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=854*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=855*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=856*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=857*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=858*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=859*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=860*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=861*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=862*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=863*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=864*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=865*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=866*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=867*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=868*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=869*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=870*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=871*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=872*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=873*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=874*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=875*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=876*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=877*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=878*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=879*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=880*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=881*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=882*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=883*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=884*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=885*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=886*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=887*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=888*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=889*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=890*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=891*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=892*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=893*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=894*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=895*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=896*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=897*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=898*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=899*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=900*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=901*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=902*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=903*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=904*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=905*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=906*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=907*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=908*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=909*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=910*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=911*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=912*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=913*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=914*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=915*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=916*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=917*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=918*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=919*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=920*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=921*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=922*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=923*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=924*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=925*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=926*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=927*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=928*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=929*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=930*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=931*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=932*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=933*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=934*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=935*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=936*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=937*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=938*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=939*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=940*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=941*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=942*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=943*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=944*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=945*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=946*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=947*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=948*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=949*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=950*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=951*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=952*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=953*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=954*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=955*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=956*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=957*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=958*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=959*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=960*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=961*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=962*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=963*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=964*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=965*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=966*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=967*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=968*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=969*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=970*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=971*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=972*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=973*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=974*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=975*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=976*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=977*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=978*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=979*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=980*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=981*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=982*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=983*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=984*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=985*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=986*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=987*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=988*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=989*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=990*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=991*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=992*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=993*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=994*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=995*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=996*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=997*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=998*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=999*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1000*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1001*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1002*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1003*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1004*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1005*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1006*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1007*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1008*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1009*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1010*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1011*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1012*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1013*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1014*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1015*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1016*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1017*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1018*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1019*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1020*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1021*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1022*slot)\r\n\t                  + 1/1024 : (s1'=3) & (x1'=1023*slot);\r\n\t\r\n\t// wait until backoff counter reaches 0 then send again\r\n\t[send1]  s1=3 & x1=pow(2,cd1)*slot -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\r\n\t[csend1] s1=3 & x1=pow(2,cd1)*slot -> (s1'=1) & (x1'=0); // finished backoff (bus appears free)\r\n\t[busy1]  s1=3 & x1=pow(2,cd1)*slot  -> (s1'=2) & (x1'=0) & (cd1'=min(K,cd1+1)); // finished backoff (bus busy)\r\n\t\r\n\t// once finished loop (wait for other station to finish)\r\n\t[done] s1=4 -> (s1'=4);\r\n\r\nendmodule\r\n\r\n// construct station 2 through renaming\r\nmodule station2=station1[s1=s2,x1=x2,cd1=cd2,send1=send2,csend1=csend2,busy1=busy2,end1=end2] endmodule\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// REWARD STRUCTURES\r\n\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n// number of collisions\r\nrewards \"collisions\"\r\n\t[csend1] true : 1;\r\n\t[csend2] true : 1;\r\nendrewards\r\n\r\n//----------------------------------------------------------------------------------------------------------------------------\r\n// LABELS\r\n\r\nlabel \"s1_done\" = s1=4;\r\nlabel \"s2_done\" = s2=4;\r\nlabel \"done\" = s1=4 & s2=4;\r\nlabel \"cmax\" = c=COL;\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/csma.nm.args",
    "content": "-const K=2,COL=4\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/csma.nm.props",
    "content": "// Maximum probability that transmissions from stations collide COL times\r\n// RESULT (K=2,COL=4): 0.1435547\r\n\"collisions\": Pmax=? [ F \"cmax\" ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/csma.nm.props.args",
    "content": "#-ptamethod digital\n-ptamethod games\n-ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/firewire_abst.nm",
    "content": "// Abstract model of Firewire protocol (PTA model)\r\n// dxp/gxn 08/07/09\r\n\r\npta\r\n\r\n// maximum and minimum delays\r\n// fast\r\nconst int rc_fast_max = 850;\r\nconst int rc_fast_min = 760;\r\n// slow\r\nconst int rc_slow_max = 1670;\r\nconst int rc_slow_min = 1590;\r\n// delay caused by the wire length\r\nconst int delay;\r\n// probability of choosing fast and slow\r\nconst double fast = 0.5;\r\nconst double slow = 1-fast;\r\n\r\nmodule abstract_firewire\r\n\r\n\t// clock \r\n\tx : clock;\r\n\t// local state\r\n\ts : [0..9];\r\n\t// 0 - start_start\r\n\t// 1 - fast_start\r\n\t// 2 - start_fast\r\n\t// 3 - start_slow\r\n\t// 4 - slow_start\r\n\t// 5 - fast_fast\r\n\t// 6 - fast_slow\r\n\t// 7 - slow_fast\r\n\t// 8 - slow_slow\r\n\t// 9 - done\r\n\r\n\t// clock invariant\r\n\tinvariant\r\n\t\t(s=0 => x<=delay) &\r\n\t\t(s=1 => x<=delay) &\r\n\t\t(s=2 => x<=delay) &\r\n\t\t(s=3 => x<=delay) &\r\n\t\t(s=4 => x<=delay) &\r\n\t\t(s=5 => x<=rc_fast_max) &\r\n\t\t(s=6 => x<=rc_slow_max) &\r\n\t\t(s=7 => x<=rc_slow_max) &\r\n\t\t(s=8 => x<=rc_slow_max)\r\n\tendinvariant\r\n\t\r\n\t// start_start (initial state)\r\n\t[] s=0 -> fast : (s'=1) + slow : (s'=4);\r\n\t[] s=0 -> fast : (s'=2) + slow : (s'=3);\r\n\t// fast_start\r\n\t[] s=1 -> fast : (s'=5) & (x'=0) + slow : (s'=6) & (x'=0);\r\n\t// start_fast\r\n\t[] s=2 -> fast : (s'=5) & (x'=0) + slow : (s'=7) & (x'=0);\r\n\t// start_slow\r\n\t[] s=3 -> fast : (s'=6) & (x'=0) + slow : (s'=8) & (x'=0);\r\n\t// slow_start\r\n\t[] s=4 -> fast : (s'=7) & (x'=0) + slow : (s'=8) & (x'=0);\r\n\t// fast_fast\r\n\t[] s=5 & (x>=rc_fast_min)       -> (s'=0) & (x'=0);\r\n\t[] s=5 & (x>=rc_fast_min-delay) -> (s'=9) & (x'=0);\r\n\t// fast_slow\r\n\t[] s=6 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// slow_fast\r\n\t[] s=7 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// slow_slow\r\n\t[] s=8 & x>=rc_slow_min       -> (s'=0) & (x'=0);\r\n\t[] s=8 & x>=rc_slow_min-delay -> (s'=9) & (x'=0);\r\n\t// done\r\n\t[] s=9 -> true;\r\n\t\r\nendmodule\r\n\r\n// labels\r\nlabel \"done\" = (s=9);\r\n\r\n// reward structures\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/firewire_abst.nm.props",
    "content": "// Minimum probability that a leader is eventually elected\n// RESULT (delay=30): 1.0\n\"eventually\": Pmin=? [ F \"done\" ];\n\n// Minimum probability that a leader has been elected by time T\n// RESULT (delay=30): 0.8515625\n\"deadline_min\": Pmin=? [ F<=5000 \"done\" ];\n\n// Maximum probability that a leader has been elected by time T\n// RESULT (delay=30): 0.25\n\"deadline_max\": Pmax=? [ F<=750 \"done\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/firewire_abst.nm.props.args",
    "content": "-const delay=30 -const L=2 -ptamethod digital\n-const delay=30 -const L=2 -ptamethod digital -ex\n-const delay=30 -const L=2 -ptamethod digital -exact\n-const delay=30 -const L=2 -ptamethod games\n#-const delay=30 -const L=2 -ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/formats09.nm",
    "content": "// PTA used as running example in FORMATS'09 paper\r\n\r\npta\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\tx : clock;\r\n\ty : clock;\r\n\t\r\n\t[] s=0 -> 0.6 : (s'=1) + 0.4 : (s'=2)&(x'=0);\r\n\t[] s=1 & x=0 -> (s'=3);\r\n\t[] s=1 & y>2 -> (s'=1)&(y'=0);\r\n\t[] s=2 & x=0 & y=1 -> (s'=3)&(y'=0);\r\n\t[] s=2 & x>2 -> (s'=1)&(y'=0);\r\n\t[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"target\" = s=3;\r\nlabel \"end\" = s=3 | s=1;\r\n\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/formats09.nm.props",
    "content": "// RESULT: 0.6\r\nPmax=? [ F \"target\" ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/formats09.nm.props.args",
    "content": "#-ptamethod digital\n-ptamethod games\n-ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/nonlocalclock.nm",
    "content": "// prism model of pta version of zeroconf\r\n// using digitial clocks\r\n\r\npta\r\n\r\nconst int probes_max = 4;\r\n\r\nmodule sender\r\n\r\n\ts : [0..2]; //local state\r\n\tprobes : [0..probes_max]; // probes sent\r\n\tip : [0..2]; // ip address not chosen, fresh or in use\r\n\tx : clock; // local clock\r\n\r\n\tinvariant\r\n\t(s=0 => x<=0) &\r\n\t(s=1 => x<=20) &\r\n\t(s=2 => true)\r\n\tendinvariant\r\n\r\n\t// selct probe\t\r\n\t// [] s=0 -> 0.99969242125984251969 : (s'=1) & (ip'=0) + 0.00030757874015748031 : (s'=1) & (ip'=1);\r\n\t[] s=0 -> 0.5 : (s'=1) & (ip'=1) + 0.5 : (s'=1) & (ip'=2);\r\n\t// send probes\r\n\t[send_used]  s=1 & x=20 & ip=2 & probes<probes_max -> (probes'=probes+1) & (x'=0);\t\r\n\t[send_fresh] s=1 & x=20 & ip=1 & probes<probes_max -> (probes'=probes+1) & (x'=0);\r\n\t[] s=1 & x=20 & probes=probes_max -> (s'=2) & (x'=0);\r\n\t[recv] s=1 -> (s'=0) & (x'=0) & (ip'=0) & (probes'=0);\r\n\t[] s=2 -> true;\r\n\r\nendmodule\r\n\r\nmodule environment\r\n\t\r\n\te : [0..2]; // ready, send reply\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t(e=0 => true) &\r\n\t(e>=1 => y<=5)\r\n\tendinvariant\r\n\r\n\t[send_fresh] e=0 -> true;\r\n\t[send_used]  e=0 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=1) & (y'=0);\r\n\t[] e=1 & y>=1 & x>=0 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=2) & (y'=0);\r\n\t[recv] e=2 & y>=1 -> (e'=0) & (y'=0);\r\n\r\nendmodule\r\n\r\n\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n//label \"incorrect\" = s=2 & ip=2;\r\nlabel \"done\" = s=2;\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/nonlocalclock.nm.props",
    "content": "// RESULT: 130321/100130321\r\n\"incorrect\": Pmax=? [ F s=2 & ip=2 ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/nonlocalclock.nm.props.args",
    "content": "-const L=2 -ptamethod digital -e 1e-8\n-const L=2 -ptamethod digital -e 1e-8 -ex\n-const L=2 -ptamethod digital -exact\n-const L=2 -ptamethod games\n-const L=2 -ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/propconst.nm",
    "content": "pta\n\nmodule M\n\t\n\ts : [0..1];\n\tx : clock;\n\t\n\t[a] x>=4 -> (s'=1);\n\nendmodule\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/propconst.nm.props",
    "content": "const int K = 2;\nconst int L;\n\nlabel \"x3\" = x=3;\n\n// This tests clocks appearing in the property\n// (the use of digital clocks with -ex means that the expression\n//  is evaluated and all the types have to be correct)\n// RESULT: 1.0\nPmax=? [ F x>=2 ];\n\n// This tests that property is traversed for clock scaling\n// (GCD should be 1 in this case)\n// RESULT: 1.0\nPmax=? [ F x=3 ];\n\n// This also tests that property is traversed for clock scaling\n// (GCD is unaffected but clock max must be right to reach x=10)\n// RESULT: 1.0\nPmax=? [ F x=10 ];\n\n// This tests that properties file labels are traversed for clock scaling\n// (GCD should be 1 in this case)\n// RESULT: 1.0\nPmax=? [ F \"x3\" ];\n\n// This tests that property references are traversed for clock scaling\n// (GCD should be 1 in this case)\n// RESULT: 1.0\nPmax=? [ F \"p3\" ];\n\n// RESULT: ?\n\"p3\":x=3;\n\n// This tests (defined) constants from the prop file\n// RESULT: 1.0\nPmax=? [ F x>=K ];\n\n// This tests (undefined) constants from the prop file\n// RESULT: 1.0\nPmax=? [ F x>=L ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/propconst.nm.props.args",
    "content": "-ptamethod digital -const L=2\n-ptamethod digital -const L=2 -ex\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/pta-glob.prism",
    "content": "pta\r\n\r\nglobal x : clock;\r\n\r\nmodule M\r\n\r\n\ts : [0..3];\r\n\ty : clock;\r\n\t\r\n\t[] s=0 -> 0.6 : (s'=1) + 0.4 : (s'=2)&(x'=0);\r\n\t[] s=1 & x=0 -> (s'=3);\r\n\t[] s=1 & y>=3 -> (s'=1)&(y'=0);\r\n\t[] s=2 & x=0 & y=1 -> (s'=3)&(y'=0);\r\n\t[] s=2 & x>=3 -> (s'=1)&(y'=0);\r\n\t[] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"target\" = s=3;\r\nlabel \"end\" = s=3 | s=1;\r\n\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/pta-glob.prism.props",
    "content": "// RESULT: 0.6\r\nPmax=? [ F \"target\" ]\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/pta-glob.prism.props.args",
    "content": "#-ptamethod digital\n-ptamethod games\n-ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/repudiation_malicious.nm",
    "content": "pta\r\n\r\nmodule originator\r\n\r\n\to : [0..12];\r\n\t// 0 - init\r\n\t// 1 - send\r\n\t// 2 - wait\r\n\t// 3 - last\r\n\t// 4 - early\r\n\t// 5 - error\r\n\t// 6 - sent_random\r\n\t// 7 - sent_last\r\n\t// 8 - done\r\n\t// 9 - done_early\r\n\t// 10 - done_error\r\n\t// 11 - wait_random\r\n\t// 12 - wait_last\r\n\r\n\tx : clock;\r\n\r\n\tinvariant\r\n\t\t(o=0 => true) &\r\n\t\t(o=1 => x<=0) &\r\n\t\t(o=2 => x<=5) & // x<=AD+1\r\n\t\t(o=3 => x<=0) &\r\n\t\t(o=4 => x<=0) &\r\n\t\t(o=5 => x<=0) &\r\n\t\t(o=6 => true) &\r\n\t\t(o=7 => true) &\r\n\t\t(o=8 => true) &\r\n\t\t(o=9 => true) &\r\n\t\t(o=10 => true) &\r\n\t\t(o=11 => x<=5) & // x<=AD+1\r\n\t\t(o=12 => x<=5) // x<=AD+1\r\n\tendinvariant\r\n\r\n\t[req] o=0 -> (o'=1) & (x'=0);\r\n\t[message] o=1 & x<=0 -> (o'=2);\r\n\t[ack]  o=2 & (x>=1 & x<=4) -> 0.9 : (o'=1) & (x'=0) + 0.1 :  (o'=3) & (x'=0); // guard x>=ad,x<=AD\r\n\t[] o=2 & x>4 -> 0.9 : (o'=4) & (x'=0) + 0.1 :  (o'=5) & (x'=0); // guard x>AD\r\n\t[decode] o=2 -> 0.9 : (o'=6) + 0.1 :  (o'=7);\r\n\t[finished] o=3 -> (o'=8) & (x'=0);\r\n\r\n\t[] o=8 -> (o'=8);\r\n\t[] o=9 -> (o'=9);\r\n\t[] o=10 -> (o'=10);\r\n\r\n\t[stop] o=4 -> (o'=9); \r\n\t[error] o=5 -> (o'=10);\r\n\r\n\t[decoded_random] o=6 -> (o'=11);\r\n\t[decoded_last] o=7 -> (o'=12);\r\n\r\n\t[ack] o=11 & (x>=1 & x<=4) -> (o'=1) & (x'=0);  // guard x>=ad,x<=AD\r\n\t[stop] o=11 & x>4 ->  (o'=9) & (x'=0); \r\n\r\n\t[ack] o=12 & (x>=1 & x<=4) -> (o'=3) & (x'=0);  // guard x>=ad,x<=AD\r\n\t[stop] o=12  & x>4 -> (o'=10) & (x'=0); \r\n\r\nendmodule\r\n\r\nmodule recipient\r\n\r\n\tr : [0..9];\r\n\t// 0 - request\r\n\t// 1 - wait\r\n\t// 2 - ack\r\n\t// 3 - done\r\n\t// 4 - decode1\r\n\t// 5 - decode2\r\n\t// 6 - terminate\r\n\t// 7 - decode\r\n\t// 8 - decoded\r\n\t// 9 - random\r\n\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t\t(r=0 => y<=0) &\r\n\t\t(r=1 => true) &\r\n\t\t(r=2 => true) &\r\n\t\t(r=3 => true) &\r\n\t\t(r=4 => y<=1) &\r\n\t\t(r=5 => y<=3) &\r\n\t\t(r=6 => true) &\r\n\t\t(r=7 => y<=0) &\r\n\t\t(r=8 => y<=0) &\r\n\t\t(r=9 => y<=0)\r\n\tendinvariant\r\n\r\n\t[req] r=0 & y=0 -> (r'=1);\r\n\t[message] r=1 -> (r'=2) & (y'=0);\r\n\t[finished] r=1 -> (r'=3);\r\n\r\n\t[ack] r=2 -> (r'=1);\r\n\t[] r=2 -> (r'=4) & (y'=0);\r\n\t[] r=2 -> (r'=5) & (y'=0);\r\n\t[] r=2 -> (r'=6);\r\n\r\n\t[] r=3 -> (r'=3);\r\n\t[] r=6 -> (r'=6);\r\n\r\n\t[] r=4 & y=1 -> 0.01 : (r'=7) & (y'=0) + 0.99 : (r'=2) & (y'=0);\r\n\t[] r=5 & y=3 -> 0.05 : (r'=7) & (y'=0) + 0.95 : (r'=2) & (y'=0);\r\n\r\n\t[decode] r=7 & y=0 -> (r'=8);\r\n\t[decoded_random] r=8 & y=0 -> (r'=9);\r\n\t[decoded_last] r=8 & y=0 -> (r'=6);\r\n\t[ack] r=9 -> (r'=1);\r\n\t[] r=9 -> (r'=6);\r\n\r\nendmodule\r\n\r\nlabel \"gains_information\" = o=10;\r\n\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/repudiation_malicious.nm.props",
    "content": "// Maximum probability that the malicious recipient eventually gains information\r\n// RESULT: 0.105658\r\n\"eventually\": Pmax=? [ F \"gains_information\" ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/repudiation_malicious.nm.props.args",
    "content": "#-ptamethod digital\n-ptamethod games\n-ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/timebounded.nm",
    "content": "pta\n\nmodule M\n\t\n\ts : [0..1];\n\tx : clock;\n\t\n\t[a] s=0 & x=2 -> 0.5:(x'=0) + 0.5:(s'=1);\n\nendmodule\n\nlabel \"target\" = s=1;\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/timebounded.nm.props",
    "content": "const int K = 2;\nconst int L;\n\n// RESULT: 7/8\nPmax=? [ F<=6 s=1 ];\n\n// RESULT: 3/4\nPmax=? [ F<=4 \"target\" ];\n\n// RESULT: 1/2\nPmax=? [ F<=K \"target\" ];\n\n// RESULT: 1/2\nPmax=? [ F<=L \"target\" ];\n\n// RESULT: Error:upper\nPmax=? [ F>=2 \"target\" ];\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/timebounded.nm.props.args",
    "content": "-const L=2 -ptamethod digital\n-const L=2 -ptamethod digital -ex\n-const L=2 -ptamethod games\n-const L=2 -ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/zeroconf.nm",
    "content": "// prism model of pta version of zeroconf\r\n// using digitial clocks\r\n\r\npta\r\n\r\nconst int probes_max = 4;\r\n\r\nmodule sender\r\n\r\n\ts : [0..2]; //local state\r\n\tprobes : [0..probes_max]; // probes sent\r\n\tip : [0..2]; // ip address not chosen, fresh or in use\r\n\tx : clock; // local clock\r\n\r\n\tinvariant\r\n\t(s=0 => x<=0) &\r\n\t(s=1 => x<=20) &\r\n\t(s=2 => true)\r\n\tendinvariant\r\n\r\n\t// selct probe\t\r\n\t// [] s=0 -> 0.99969242125984251969 : (s'=1) & (ip'=0) + 0.00030757874015748031 : (s'=1) & (ip'=1);\r\n\t[] s=0 -> 0.5 : (s'=1) & (ip'=1) + 0.5 : (s'=1) & (ip'=2);\r\n\t// send probes\r\n\t[send_used]  s=1 & x=20 & ip=2 & probes<probes_max -> (probes'=probes+1) & (x'=0);\t\r\n\t[send_fresh] s=1 & x=20 & ip=1 & probes<probes_max -> (probes'=probes+1) & (x'=0);\r\n\t[] s=1 & x=20 & probes=probes_max -> (s'=2) & (x'=0);\r\n\t[recv] s=1 -> (s'=0) & (x'=0) & (ip'=0) & (probes'=0);\r\n\t[] s=2 -> true;\r\n\r\nendmodule\r\n\r\nmodule environment\r\n\t\r\n\te : [0..2]; // ready, send reply\r\n\ty : clock;\r\n\r\n\tinvariant\r\n\t(e=0 => true) &\r\n\t(e>=1 => y<=5)\r\n\tendinvariant\r\n\r\n\t[send_fresh] e=0 -> true;\r\n\t[send_used]  e=0 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=1) & (y'=0);\r\n\t[] e=1 & y>=1 -> 0.1 : (e'=0) & (y'=0) + 0.9 : (e'=2) & (y'=0);\r\n\t[recv] e=2 & y>=1 -> (e'=0) & (y'=0);\r\n\r\nendmodule\r\n\r\n\r\n// time\r\nrewards \"time\"\r\n\ttrue : 1;\r\nendrewards\r\n\r\n//label \"incorrect\" = s=2 & ip=2;\r\nlabel \"done\" = s=2;\r\n\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/zeroconf.nm.props",
    "content": "const int K=2;\r\nconst int L;\r\n\r\n// Maximum probability of configuring IP address incorrectly\r\n// RESULT: 130321/100130321\r\n\"incorrect\": Pmax=? [ F s=2 & ip=2 ];\r\n\r\n// As above but testing using constants\r\n// RESULT: 130321/100130321\r\nPmax=? [ F s=2 & ip=K ];\r\n\r\n// As above but testing using (undefined) constants\r\n// RESULT: 130321/100130321\r\nPmax=? [ F s=2 & ip=L ];\r\n\r\nconst int T = 150;\r\n\r\n// Maximum probability of configuring IP address incorrectly by time T\r\n// RESULT (T=100): 130321/200000000\r\n// RESULT (T=150): 8580204319/8000000000000\r\n// RESULT (T=200): 390893418881359/320000000000000000\r\n\"deadline\": Pmax=? [ F<=T s=2 & ip=2 ];\r\n"
  },
  {
    "path": "prism-tests/functionality/verify/ptas/reach/zeroconf.nm.props.args",
    "content": "-const L=2 -ptamethod digital -e 1e-8\n-const L=2 -ptamethod digital -e 1e-8 -ex\n-const L=2 -ptamethod digital -exact\n-const L=2 -ptamethod games\n-const L=2 -ptamethod backwards\n"
  },
  {
    "path": "prism-tests/functionality/verify/sim/chain.prism",
    "content": "// Completely deterministic model\n// used to do some sanity checks on statistical model checking\n\ndtmc\n\nconst int N = 10;\n\nmodule M\n\n\tx : [0..N];\n\t\n\t[] x<N -> (x'=x+1);\n\t[] x=N -> true;\n\nendmodule\n\nlabel \"end\" = x=N;\n"
  },
  {
    "path": "prism-tests/functionality/verify/sim/chain.prism.props",
    "content": "const int K = 0;\n\nlabel \"not_end\" = x<N;\n\n// RESULT: 1.0\nP=? [ F \"end\" ]\n\n// RESULT: 1.0\nP=? [ F x=(N+K) ]\n\n// RESULT: 0.0\nP=? [ F x=(N+K+1) ]\n\n// RESULT: 1.0\nP=? [ \"not_end\" U \"end\" ]\n"
  },
  {
    "path": "prism-tests/functionality/verify/sim/chain.prism.props.args",
    "content": "-sim\n-ex\n"
  },
  {
    "path": "prism-tests/papers/BKH99-Ex2.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\t\r\n\t[] x=0 -> 3 : (x'=1) + 3 : (x'=3);\r\n\t[] x=1 -> 1 : (x'=2);\r\n\t[] x=2 -> 0.5 : (x'=1);\r\n\t[] x=3 -> 2 : (x'=3);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = x=1 | x=3;\r\nlabel \"b\" = x=2 | x=3;\r\n"
  },
  {
    "path": "prism-tests/papers/BKH99-Ex2.sm.props",
    "content": "\t// NB: \"phi\" should be a subformula of the S operator\n\t// but it seems to be model checked wrongly in the paper\n\t// so we don't actually use it...\n\t// RESULT: ?\n\t\"phi\": (\"a\" & \"b\") | P<=0.8 [ \"a\" U<=2 \"b\" ];\n\t// RESULT: 5/6\n\tS=? [ x=2 | x=3 ];\n\t// RESULT: ?\n\t\"prop\" : S>0.5 [ x=2 | x=3 ];\n\t// RESULT: true\n\tfilter(forall, \"prop\" <=> true);\n"
  },
  {
    "path": "prism-tests/papers/BKH99-Ex2.sm.props.args",
    "content": "-gs\n"
  },
  {
    "path": "prism-tests/papers/BKH99-Ex3.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\t\r\n\t[] x=0 -> 3 : (x'=1) + 3 : (x'=3);\r\n\t[] x=1 -> 1 : (x'=2);\r\n\t[] x=2 -> 0.5 : (x'=1);\r\n\t[] x=3 -> 2 : (x'=3);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = x=1 | x=3;\r\nlabel \"b\" = x=2 | x=3;\r\n"
  },
  {
    "path": "prism-tests/papers/BKH99-Ex3.sm.props",
    "content": "\t// RESULT: 0.864664716763387 (1-e^-2)\n\tfilter(first, P=? [ \"a\" U<=2 \"b\" ], x=1);\n\t// RESULT: ?\n\t\"phi\": (\"a\" & \"b\") | P<=0.8 [ \"a\" U<=2 \"b\" ];\n\t// RESULT: true\n\tfilter(forall, \"phi\" <=> (x=0 | x=3));\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-ex9.4.12-p239.nm",
    "content": "// simple LTL/fairness example from Christel's thesis (p.239-240)\r\n\r\n// note that the product MDP in fig 9.15 is incorrect:\r\n// s_3,q_0 should be s_3,q_1\r\n// s_5,q_1 should be s_5,q_2\r\n// (and thus state s_5,q_1 disappears)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\ts : [1..5];\r\n\r\n\t[] (s=1) -> (s'=2);\r\n\t[] (s=2) -> (s'=2);\r\n\t[] (s=2) -> 0.5:(s'=3) + 0.5:(s'=4);\r\n\t[] (s=3) -> (s'=5);\r\n\t[] (s=4) -> (s'=5);\r\n\t[] (s=5) -> (s'=5);\r\n\t\r\nendmodule\r\n\r\nlabel \"a\" = s=3;\r\nlabel \"b\" = s=2 | s=5;\r\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-ex9.4.12-p239.nm.fair.props",
    "content": "\t// RESULT: 0.5\n\tPmin=? [ F (\"a\" & (X \"b\")) ];\n\t// RESULT: 0.5\n\tPmax=? [ F (\"a\" & (X \"b\")) ];\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-ex9.4.12-p239.nm.fair.props.args",
    "content": "-fair\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-ex9.4.12-p239.nm.nofair.props",
    "content": "\t// RESULT: 0\n\tPmin=? [ F (\"a\" & (X \"b\")) ];\n\t// RESULT: 0.5\n\tPmax=? [ F (\"a\" & (X \"b\")) ];\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-ex9.4.12-p239.nm.nofair.props.args",
    "content": "-nofair\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-remark9.4.13-p240.nm",
    "content": "// another simple LTL example from Christel's thesis (p.240)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\ts : [1..3];\r\n\t\r\n\t// s\r\n\t[] (s=1) -> (s'=2);\r\n\t[] (s=1) -> (s'=3);\r\n\t// t\r\n\t[] (s=2) -> (s'=1);\r\n\t// u\r\n\t[] (s=3) -> (s'=3);\r\n\t\r\nendmodule\r\n\r\nlabel \"a\" = s=1 | s=2;\r\nlabel \"b\" = s=2;\r\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-remark9.4.13-p240.nm.fair.props",
    "content": "\t// RESULT: 0\n\tPmin=? [ (X \"b\") => (G \"a\") ];\n\t// RESULT: 1\n\tPmax=? [ (X \"b\") => (G \"a\") ];\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-remark9.4.13-p240.nm.fair.props.args",
    "content": "-fair\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-remark9.4.13-p240.nm.nofair.props",
    "content": "\t// RESULT: 0\n\tPmin=? [ (X \"b\") => (G \"a\") ];\n\t// RESULT: 1\n\tPmax=? [ (X \"b\") => (G \"a\") ];\n"
  },
  {
    "path": "prism-tests/papers/Bai98/Bai98-remark9.4.13-p240.nm.nofair.props.args",
    "content": "-nofair\n"
  },
  {
    "path": "prism-tests/papers/DJJL01-Ex2.nm",
    "content": "mdp\r\n\r\nmodule M\r\n\r\n\tab : [0..1]; // 0=a, 1=b\r\n\tx  : [0..20];\r\n\t\r\n\t[] (ab=0) & (x>=20) -> (ab'=0);\r\n\t[] (ab=0) & (x<20) -> 0.5 : (x'=x+1) + 0.5 : (ab'=1);\r\n\t\r\n\t// fixdl\r\n\t[] (ab=1) -> true;\r\n\t\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/papers/DJJL01-Ex2.nm.props",
    "content": "\t// RESULT: 2.956390380859375E-5 (=31/(2^20))\n\tPmin=? [ F ab=1 & x>=15 {ab=0 & x=0} ];\n\t// RESULT: 2.956390380859375E-5 (=31/(2^20))\n\tPmax=? [ F ab=1 & x>=15 {ab=0 & x=0} ];\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/multiprod-fig15.nm",
    "content": "mdp\r\n\r\nmodule M\r\n\r\n\t// t=0,1,2 for t_0,t_1,t_2\r\n\t// t=3 for s_{1} and t=4 for s_{2}\r\n\tt : [0..4];\r\n\r\n\t[b2] t=0 -> 0.5:(t'=0) + 0.5:(t'=2);\r\n\t[b1] t=0 -> (t'=1);\r\n\t[b1] t=1 -> (t'=1);\r\n\t[b2] t=2 -> (t'=0);\r\n\t\r\n\t[a2] t=0 -> (t'=4);\r\n\t[a1] t=1 -> (t'=3);\r\n\t[a2] t=0 -> (t'=4);\r\n\t\r\n\t[] t=3|t=4 -> true;\r\n\r\nendmodule\r\n\r\nlabel \"T1\" = t=3;\r\nlabel \"T2\" = t=4;\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/parallel-fig16.nm",
    "content": "// Parallel composition of two PAs M_1/M_2 and DFA A_G^err (see Figure 16, p.46)\r\n\r\nmdp\r\n\r\n// M_1\r\nmodule M1\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3] init 0;\r\n\r\n\t[detect]   s=0 -> 0.8:(s'=1) + 0.2:(s'=2);\r\n\t[warn]     s=1 -> (s'=2);\r\n\t[shutdown] s=2 -> (s'=3);\r\n\t[off]      s=3 -> true;\r\n\r\nendmodule\r\n\r\n// M_2\r\nmodule M2\r\n\r\n\tt : [0..3] init 0;\r\n\r\n\t[warn]     t=0 -> (t'=1);\r\n\t[shutdown] t=0 -> 0.9:(t'=2) + 0.1:(t'=3);\r\n\t[shutdown] t=1 -> (t'=2);\r\n\t[off]      t=2 -> true;\r\n\t[fail]     t=3 -> true;\r\n\t\r\nendmodule\r\n\r\n// DFA A_G^err for safety property Phi_G (\"never fail\")\r\nmodule A_G_err\r\n\r\n\t// q=i for state q_i\r\n\tq : [3..4] init 3;\r\n\r\n\t[fail] q=3 -> (q'=4);\r\n\r\n\t[fail] q=4 -> true;\r\n\t\r\nendmodule\r\n\r\n// Accepting states for A_G^err\r\nlabel \"A_G_err_acc\" = q=4;\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/parallel-fig16.nm.props",
    "content": "// ex 18\n// RESULT: 0.98\n1 - Pmax=? [ F \"A_G_err_acc\" ]\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/rewards-fig6.nm",
    "content": "// MDP illustrating non-memoryless optimal rewards (see Figure 6)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..2];\r\n\t\r\n\t[b0] s=0 -> (s'=0);\r\n\t[a0] s=0 -> (s'=1);\r\n\t[a1] s=1 -> (s'=2);\r\n\t[a2] s=2 -> (s'=2);\r\n\r\nendmodule\r\n\r\nrewards\r\n\t// state rewards\r\n\ts=0 : 1;\r\n\ts=1 : 2;\r\n\t// transition rewards\r\n\t[b0] s=0 : 1;\r\n\t[a2] s=2 : 3;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/rewards-fig6.nm.props",
    "content": "// sec 5.1\n// RESULT: 2\nRmax=? [ I=3 ]\n\n// sec 5.2\n// RESULT: 5\nRmin=? [ C<=3 ]\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/rewards-fig6.nm.props.args",
    "content": "-s\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-ex7.nm",
    "content": "// Modified running example MDP (see Example 7, p.17)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3]; // \r\n\t\r\n\t[wait] s=0 -> (s'=0);\r\n\t[go] s=0 -> (s'=1);\r\n\t[safe] s=1 -> 0.7:(s'=0) + 0.3:(s'=2);\r\n\t[risk] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n\t[finish] s=2 -> (s'=2);\r\n\t[stop] s=3 -> (s'=3);\r\n\t[reset] s=3 -> (s'=0);\r\n\r\nendmodule\r\n\r\nrewards\r\n\t// state rewards\r\n\ts=0 : 1;\r\n\ts=1 : 2;\r\n\t// transition rewards\r\n\t[go] s=0 : 1;\r\n\t[safe] s=1 : 1;\r\n\t[risk] s=1 : 4;\r\n\t[reset] s=3 : 5;\r\nendrewards\r\n\r\nlabel \"initial\" = s=0;\r\nlabel \"succ\" = s=2;\r\nlabel \"fail\" = s=3;\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-ex7.nm.props",
    "content": "// ex 7 (ish)\n// RESULT: 1\nPmax=? [ F s=2 ]\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-fig2.nm",
    "content": "// Running example MDP (see Figure 2, p.6)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3];\r\n\t\r\n\t[go] s=0 -> (s'=1);\r\n\t[safe] s=1 -> 0.7:(s'=0) + 0.3:(s'=2);\r\n\t[risk] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n\t[finish] s=2 -> (s'=2);\r\n\t[stop] s=3 -> (s'=3);\r\n\t[reset] s=3 -> (s'=0);\r\n\r\nendmodule\r\n\r\nrewards\r\n\t// state rewards\r\n\ts=0 : 1;\r\n\ts=1 : 2;\r\n\t// transition rewards\r\n\t[go] s=0 : 1;\r\n\t[safe] s=1 : 1;\r\n\t[risk] s=1 : 4;\r\n\t[reset] s=3 : 5;\r\nendrewards\r\n\r\nlabel \"initial\" = s=0;\r\nlabel \"succ\" = s=2;\r\nlabel \"fail\" = s=3;\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-fig2.nm.props",
    "content": "\t// ex 4\n\t// RESULT: 0.5\n\tPmin=? [ F s=2 ]\n\t\n\t// ex 5\n\t// RESULT: 0.5\n\tPmax=? [ F s=3 ]\n\t\n\t// ex 8\n\t// RESULT: 2\n\tRmax=? [ I=1 ]\n\t// RESULT: 0.7\n\tRmax=? [ I=2 ]\n\t// RESULT: 1.4\n\tRmax=? [ I=3 ]\n\t// RESULT: 1\n\tRmax=? [ I=4 ]\n\t\n\t// ex 9\n\t// RESULT: 2\n\tRmax=? [ C<=1 ]\n\t// RESULT: 8\n\tRmax=? [ C<=2 ]\n\t// RESULT: 10.5\n\tRmax=? [ C<=3 ]\n\t// RESULT: 11.5\n\tRmax=? [ C<=4 ]\n\n\t// ex 11\n\t// RESULT: true\n\t\"ex11\": P<1 [ X (P>=0.5 [ !\"fail\" U \"initial\" ]) ]\n\t// RESULT: true\n\tfilter(forall, \"ex11\" <=> (s=0|s=1|s=2));\n\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-fig2.nm.props.args",
    "content": "-s\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-fig5.nm",
    "content": "// Modified running example MDP (see Figure 5, p.16)\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3]; // \r\n\t\r\n\t[go] s=0 -> (s'=1);\r\n\t[safe] s=1 -> 0.6:(s'=0) + 0.3:(s'=2) + 0.1:(s'=3);\r\n\t[risk] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n\t[finish] s=2 -> (s'=2);\r\n\t[stop] s=3 -> (s'=3);\r\n\r\nendmodule\r\n\r\nrewards\r\n\t// state rewards\r\n\ts=0 : 1;\r\n\ts=1 : 2;\r\n\t// transition rewards\r\n\t[go] s=0 : 1;\r\n\t[safe] s=1 : 1;\r\n\t[risk] s=1 : 4;\r\nendrewards\r\n\r\nlabel \"initial\" = s=0;\r\nlabel \"succ\" = s=2;\r\nlabel \"fail\" = s=3;\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-fig5.nm.props",
    "content": "// ex 6 (ish)\n// RESULT: 0.75\nPmax=? [ F s=2 ]\n\n// ex 10\n// RESULT: 8\nRmin=? [ F (s=2|s=3) ]\n// RESULT: 6\nRmin=? [ F (s=2|s=3) {s=1} ]\n// RESULT: 0\nRmin=? [ F (s=2|s=3) {s=2} ]\n\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-fig5.nm.props.args",
    "content": "-s\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-ltl.nm",
    "content": "// Running example MDP (see Figure 2, p.6)\r\n// and DRA for LTL property \"F G go\" (see Figure 10, p.36)\r\n\r\nmdp\r\n\r\n// MDP M\r\nmodule M\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3];\r\n\t\r\n\t[go] s=0 -> (s'=1);\r\n\t[safe] s=1 -> 0.7:(s'=0) + 0.3:(s'=2);\r\n\t[risk] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n\t[finish] s=2 -> (s'=2);\r\n\t[stop] s=3 -> (s'=3);\r\n\t[reset] s=3 -> (s'=0);\r\n\r\nendmodule\r\n\r\n// DRA A_ltl for LTL property \"F G go\"\r\n// This is encoded as a PRISM module to allow action-based LTL \r\n// model checking: PRISM only supports state-based LTL currently\r\nmodule A_ltl\r\n\r\n\t// q=i for state q_i\r\n\tq : [0..1] init 0;\r\n\r\n\t[go] q=0 -> (q'=1);\r\n\t[safe] q=0 -> (q'=0);\r\n\t[risk] q=0 -> (q'=0);\r\n\t[finish] q=0 -> (q'=0);\r\n\t[stop] q=0 -> (q'=0);\r\n\t[reset] q=0 -> (q'=0);\r\n\r\n\t[go] q=1 -> (q'=1);\r\n\t[safe] q=1 -> (q'=0);\r\n\t[risk] q=1 -> (q'=0);\r\n\t[finish] q=1 -> (q'=0);\r\n\t[stop] q=1 -> (q'=0);\r\n\t[reset] q=1 -> (q'=0);\r\n\r\nendmodule\r\n\r\n// Accepting pair (L_1,K_1) = ({q_0},{q_1}) for the DRA\r\nlabel \"L1\" = q=0;\r\nlabel \"K1\" = q=1;\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-ltl.nm.props",
    "content": "// ex 15\n// RESULT: 0\nPmax=? [ (F G !\"L1\") & (G F \"K1\") ]\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-ltl2.nm",
    "content": "// Running example MDP (see Figure 2, p.6)\r\n// and DRA for LTL property \"(F G finish) & (F risk)\" (see Figure 11, p.38)\r\n\r\nmdp\r\n\r\n// MDP M\r\nmodule M\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3];\r\n\t\r\n\t[go] s=0 -> (s'=1);\r\n\t[safe] s=1 -> 0.7:(s'=0) + 0.3:(s'=2);\r\n\t[risk] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n\t[finish] s=2 -> (s'=2);\r\n\t[stop] s=3 -> (s'=3);\r\n\t[reset] s=3 -> (s'=0);\r\n\r\nendmodule\r\n\r\n// DRA A_ltl for LTL property \"(F G finish) & (F risk)\"\r\n// This is encoded as a PRISM module to allow action-based LTL \r\n// model checking: PRISM only supports state-based LTL currently\r\nmodule A_ltl\r\n\r\n\t// q=i for state q_i\r\n\tq : [0..2];\r\n\t\r\n\t[go] q=0 -> (q'=0);\r\n\t[safe] q=0 -> (q'=0);\r\n\t[risk] q=0 -> (q'=1);\r\n\t[finish] q=0 -> (q'=0);\r\n\t[stop] q=0 -> (q'=0);\r\n\t[reset] q=0 -> (q'=0);\r\n\r\n\t[go] q=1 -> (q'=1);\r\n\t[safe] q=1 -> (q'=1);\r\n\t[risk] q=1 -> (q'=1);\r\n\t[finish] q=1 -> (q'=2);\r\n\t[stop] q=1 -> (q'=1);\r\n\t[reset] q=1 -> (q'=1);\r\n\r\n\t[go] q=2 -> (q'=1);\r\n\t[safe] q=2 -> (q'=1);\r\n\t[risk] q=2 -> (q'=1);\r\n\t[finish] q=2 -> (q'=2);\r\n\t[stop] q=2 -> (q'=1);\r\n\t[reset] q=2 -> (q'=1);\r\n\r\nendmodule\r\n\r\n// Accepting pair (L_1,K_1) = ({q_1},{q_2}) for the DRA\r\nlabel \"L1\" = q=1;\r\nlabel \"K1\" = q=2;\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/running-ltl2.nm.props",
    "content": "// ex 16\n// RESULT: 1\nPmax=? [ (F G !\"L1\") & (G F \"K1\") ]\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/safety-fig9.nm",
    "content": "// MDP M_1 (see Figure 9, p.34) and DFA A_A^err (see Figure 8, p.32)\r\n\r\nmdp\r\n\r\n// M_1\r\nmodule M1\r\n\r\n\t// s=i for state s_i\r\n\ts : [0..3] init 0;\r\n\r\n\t[detect]   s=0 -> 0.8:(s'=1) + 0.2:(s'=2);\r\n\t[warn]     s=1 -> (s'=2);\r\n\t[shutdown] s=2 -> (s'=3);\r\n\t[off]      s=3 -> true;\r\n\r\nendmodule\r\n\r\n// DFA A_A^err for property Phi_A (\"never shutdown before warn\")\r\nmodule A_A_err\r\n\r\n\t// q=i for state q_i\r\n\tq : [0..2] init 0;\r\n\r\n\t[warn]     q=0 -> (q'=1);\r\n\t[shutdown] q=0 -> (q'=2);\r\n\r\n\t[warn]     q>=1 -> true;\r\n\t[shutdown] q>=1 -> true;\r\n\t\r\nendmodule\r\n\r\n// Accepting states for A_A^err\r\nlabel \"A_A_err_acc\" = q=2;\r\n"
  },
  {
    "path": "prism-tests/papers/FKNP11-SFM11/safety-fig9.nm.props",
    "content": "// ex 13\n// RESULT: 0.8\n1- Pmax=? [ F \"A_A_err_acc\" ];\n"
  },
  {
    "path": "prism-tests/papers/KNP07a-SFM07/ctmc.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\t\r\n\t[arrive] x<3 -> 1.5 : (x'=x+1);\r\n\t[serve] x>0 -> 3 : (x'=x-1);\r\n\r\nendmodule\r\n\r\nlabel \"empty\" = x=0;\r\nlabel \"full\" = x=3;\r\n\r\nrewards \"serve\"\r\n\t[serve] true : 1;\r\nendrewards\r\n\r\nrewards \"queue\"\r\n\ttrue : x;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/papers/KNP07a-SFM07/ctmc.sm.props",
    "content": "\t// ex 15\n\t// RESULT: 1/3\n\tP=? [ X \"full\" {x=2} ];\n\t// RESULT: ?\n\t\"ex15\": P>=0.5 [ X \"full\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex15\" <=> false);\n\n\t// ex 16\n\t// RESULT: 0.6404780884740766\n\tP=? [ true U<=7.5 \"full\" {x=0} ];\n\t// RESULT: ?\n\t\"ex16\": P>0.65 [ true U<=7.5 \"full\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex16\" <=> (x=1|x=2|x=3));\n\t\n\t// ex 17\n\t// RESULT: 1/15\n\tS=? [ \"full\" ];\n\t// RESULT: ?\n\t\"ex17\": S<0.1 [ \"full\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex17\" <=> true);\n\t\n\t// ex 20\n\t// RESULT: 7.069019518168792\n\tR{\"serve\"}=? [ C<=5.5 ];\n\t// RESULT: ?\n\t\"ex20\": R{\"serve\"}>9 [ C<=5.5 ];\n\t// RESULT: true\n\tfilter(forall, \"ex20\" <=> (x=3));\n\t\n\t// ex 21\n\t// RESULT: 0.5929374064162124\n\tR{\"queue\"}=? [ I=1 ];\n\t// RESULT: ?\n\t\"ex21\": R{\"queue\"}<2 [ I=1 ];\n\t// RESULT: true\n\tfilter(forall, \"ex21\" <=> true);\n\t\n\t// ex 22\n\t// RESULT: 8\n\tR{\"serve\"}=? [ F \"full\" ];\n\t// RESULT: ?\n\t\"ex22\": R{\"serve\"}<7 [ F \"full\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex22\" <=> (x=2|x=3));\n\t\n\t// ex 23\n\t// RESULT: 7/5\n\tR{\"serve\"}=? [ S ];\n\t// RESULT: ?\n\t\"ex23a\": R{\"serve\"}>=1.5 [ S ];\n\t// RESULT: true\n\tfilter(forall, \"ex23a\" <=> false);\n\t// RESULT: 11/15\n\tR{\"queue\"}=? [ S ];\n\t// RESULT: ?\n\t\"ex23b\": R{\"queue\"}<=0.8[ S ];\n\t// RESULT: true\n\tfilter(forall, \"ex23b\" <=> true);\n"
  },
  {
    "path": "prism-tests/papers/KNP07a-SFM07/ctmc.sm.props.args",
    "content": "-gs\n"
  },
  {
    "path": "prism-tests/papers/KNP07a-SFM07/dtmc.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\t\r\n\t[] x=0 -> (x'=1);\r\n\t[] x=1 -> 0.01 : (x'=1) + 0.01 : (x'=2) + 0.98 : (x'=3);\r\n\t[] x=2 -> (x'=0);\r\n\t[] x=3 -> (x'=3);\r\n\r\nendmodule\r\n\r\nlabel \"try\" = x=1;\r\nlabel \"fail\" = x=2;\r\nlabel \"succ\" = x=3;\r\n\r\nrewards\r\n\tx=1 : 1;\r\nendrewards\r\n"
  },
  {
    "path": "prism-tests/papers/KNP07a-SFM07/dtmc.pm.props",
    "content": "\t// ex 4\n\t// RESULT: ?\n\t\"ex4\": P>=0.9 [ X (!\"try\")|\"succ\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex4\" <=> (x=1|x=2|x=3));\n\t\n\t// ex 5\n\t// RESULT: 0.9898\n\tP=? [ F<=2 \"succ\" {x=1} ];\n\t// RESULT: ?\n\t\"ex5\": P>0.98 [ F<=2 \"succ\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex5\" <=> (x=1|x=3));\n\t\n\t// ex 6\n\t// RESULT: ?\n\t\"ex6\": P>0.99 [ \"try\" U \"succ\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex6\" <=> (x=3));\n\t\n\t// ex 9\n\t// RESULT: ?\n\t\"ex9\": R>1 [ C<=2 ];\n\t// RESULT: true\n\tfilter(forall, \"ex9\" <=> (x=1));\n\t\n\t// ex 10\n\t// RESULT: 0.0001\n\tR=? [ I=2 {x=1} ];\n\t// RESULT: ?\n\t\"ex10\": R>0 [ I=2 ];\n\t// RESULT: true\n\tfilter(forall, \"ex10\" <=> (x=0|x=1|x=2));\n\t\n\t// ex 11\n\t// RESULT: 100/98\n\tR=? [ F \"succ\" ];\n\t// RESULT: ?\n\t\"ex11\": R<1 [ F \"succ\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex11\" <=> (x=3));\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.1.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\r\n\t[] (x=0) -> (x'=1);\r\n\t[] (x=1) -> 0.5:(x'=0) + 0.3:(x'=2) + 0.2:(x'=3);\r\n\t[] (x=2) -> (x'=2);\r\n\t[] (x=3) -> (x'=3);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.1.pm.props",
    "content": "\t// RESULT: 0.6\n\tP=? [ !(x=3) U (x=2) ];\n\t// RESULT: ?\n\t\"ex\": P>=0.5 [ !(x=3) U (x=2) ];\n\t// RESULT: true\n\tfilter(forall, \"ex\" <=> (x=0|x=1|x=2));\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.2.nm",
    "content": "mdp\r\n\r\nmodule M\r\n\r\n\tx : [0..3];\r\n\r\n\t[] (x=0) -> (x'=1);\r\n\t[] (x=1) -> (x'=0);\r\n\t[] (x=1) -> 0.6:(x'=2) + 0.4:(x'=3);\r\n\t[] (x=2) -> (x'=2);\r\n\t[] (x=3) -> (x'=3);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = x=2;\r\nlabel \"b\" = x=3;\r\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.2.nm.fair.props",
    "content": "\t// RESULT: 0.6\n\tPmax=? [ !\"b\" U \"a\" ];\n\t// RESULT: ?\n\t\"ex1f\": P<=0.5 [ !\"b\" U \"a\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex1f\" <=> (x=3));\n\n\t// RESULT: 0.6\n\tPmin=? [ !\"b\" U \"a\" ];\n\t// RESULT: ?\n\t\"ex2f\": P>=0.5 [ !\"b\" U \"a\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex2f\" <=> (x=0|x=1|x=2));\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.2.nm.fair.props.args",
    "content": "-fair\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.2.nm.nofair.props",
    "content": "\t// RESULT: 0.6\n\tPmax=? [ !\"b\" U \"a\" ];\n\t// RESULT: ?\n\t\"ex1\": P<=0.5 [ !\"b\" U \"a\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex1\" <=> (x=3));\n\n\t// RESULT: 0\n\tPmin=? [ !\"b\" U \"a\" ];\n\t// RESULT: ?\n\t\"ex2\": P>=0.5 [ !\"b\" U \"a\" ];\n\t// RESULT: true\n\tfilter(forall, \"ex2\" <=> (x=2));\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.2.nm.nofair.props.args",
    "content": "-nofair\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.3.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\n\tx : [0..2];\r\n\r\n\t[] (x=0) -> 4:(x'=1);\r\n\t[] (x=0) -> 7:(x'=2);\r\n\t[] (x=1) -> 5:(x'=0);\r\n\t[] (x=1) -> 3:(x'=2);\r\n\t[] (x=2) -> 4:(x'=1);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/papers/Par02/Par02-3.3.3.sm.props",
    "content": "\t// RESULT: 2/3\n\tS=? [ (x=0) | (x=2) ];\n\t// RESULT: ?\n\t\"ex\": S>=0.6 [ (x=0) | (x=2) ];\n\t// RESULT: true\n\tfilter(forall, \"ex\" <=> true);\n"
  },
  {
    "path": "prism-tests/pmc/lec12mdp.nm",
    "content": "// Simple MDPs from Lec 12 of Probabilistic Model Checking\r\n\r\nmdp\r\n\r\n// version: 1 or 2\r\n// TODO: enable both in .args file\r\nconst int version;\r\n\r\nmodule M\r\n\r\ns:[0..3];\r\n\r\n[a] s=0 -> 1:(s'=1);\r\n[b] s=1 -> 0.7:(s'=0) + 0.3:(s'=(version=1)?1:3);\r\n[c] s=1 -> 0.5:(s'=2) + 0.5:(s'=3);\r\n[a] s=2 -> 1:(s'=2);\r\n[a] s=3 -> 1:(s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"heads\" = s=2;\r\nlabel \"tails\" = s=3;\r\n"
  },
  {
    "path": "prism-tests/pmc/lec12mdp.nm.props",
    "content": "\t// RESULT (version=1): 0\n\t// RESULT (version=2): 0.5\n\tPmin=? [ F \"tails\" ];\n\n\t// RESULT (version=1): 0.5\n\t// RESULT (version=2): 1\n\tPmax=? [ F \"tails\" ];\n"
  },
  {
    "path": "prism-tests/pmc/lec12mdp.nm.props.args",
    "content": "-const version=1\n-const version=2\n"
  },
  {
    "path": "prism-tests/pmc/lec13and14mdp.nm",
    "content": "// Simple MDP from Lec 13 of Probabilistic Model Checking\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\ns:[0..3];\r\n\r\n[] s=0 -> 1:(s'=1);\r\n[] s=0 -> 0.25:(s'=0) + 0.5:(s'=2) + 0.25:(s'=3);\r\n[] s=1 -> 0.1:(s'=0) + 0.5:(s'=1) + 0.4:(s'=2);\r\n[] s=2 -> 1:(s'=2);\r\n[] s=3 -> 1:(s'=2);\r\n[] s=3 -> 1:(s'=3);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = s=2;\r\n"
  },
  {
    "path": "prism-tests/pmc/lec13and14mdp.nm.props",
    "content": "\t// RESULT: 2/3\n\tPmin=? [ F \"a\" ];\n\t// RESULT: 14/15\n\tPmin=? [ F \"a\" {s=1} ];\n\t// RESULT: 1\n\tPmax=? [ F \"a\" ];\n\t// RESULT: 1\n\tPmax=? [ F \"a\" {s=1} ];\n\t// RESULT: true\n\tfilter(forall, P>0.5 [ F \"a\" ] <=> (s=0|s=1|s=2));\n\t// RESULT: true\n\tfilter(forall, P<0.1 [ F \"a\" ] <=> false);\n\t// RESULT: true\n\tfilter(forall, P>0 [ F \"a\" ] <=> (s=0|s=1|s=2));\n"
  },
  {
    "path": "prism-tests/pmc/lec15dtmc.pm",
    "content": "// Simple DTMC from Lec 15 of Probabilistic Model Checking\r\n\r\ndtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/pmc/lec15dtmc.pm.props",
    "content": "\t// RESULT: 2/3\n\tP=? [F s=3 ];\n\t// RESULT: 1/6\n\tP=? [F s=4 ];\n\t// RESULT: 1/6\n\tP=? [F s=2|s=5 ];\n\t// RESULT: true\n\tP>=1 [ G F s=3|s=4|s=5 ];\n\t// RESULT: false\n\tP>=1 [ G F s=3|s=4 ];\n\t// RESULT: true\n\tfilter(first, P>=1 [ G F s=5 ], s=2);\n\t// RESULT: 5/6 = 0.833333\n\tP=? [ G F s=3|s=4 ];\n"
  },
  {
    "path": "prism-tests/pmc/lec15mdp.nm",
    "content": "// Simple MDP from Lec 15 of Probabilistic Model Checking\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\ns:[0..8];\r\n\r\n[] s=0 -> 1:(s'=2);\r\n[] s=0 -> 0.6:(s'=0) + 0.3:(s'=1) + 0.1:(s'=2);\r\n[] s=1 -> 0.3:(s'=3) + 0.7:(s'=4);\r\n[] s=3 -> 1:(s'=4);\r\n[] s=4 -> 1:(s'=1);\r\n[] s=4 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=6);\r\n[] s=6 -> 1:(s'=6);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=5 -> 0.9:(s'=7) + 0.1:(s'=8);\r\n[] s=7 -> 1:(s'=5);\r\n[] s=8 -> 1:(s'=5);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/pmc/lec15mdp.nm.props",
    "content": "\t// RESULT: 0.75\n\tPmax=? [ F s=3|s=4 ];\n\t// RESULT: 0.75\n\tPmax=? [ F s=1|s=3|s=4 ];\n\t// RESULT: 0.75\n\tPmax=? [ F s=6 ];\n\t// RESULT: 1\n\tPmax=? [ F s=5|s=7|s=8 ];\n\t// RESULT: 0.75\n\tPmax=? [ G F s=4|s=6 ];\n\t// RESULT: false\n\tP>=1 [ G F s=1|s=4|s=6 ];\n\t// RESULT: true\n\tP>=1 [ G F (s=1|s=4|s=6|s=7) ];\n\t// RESULT: false\n\tP>=1 [ G F (s=1|s=6|s=7) ];\n\t// RESULT: 0.25\n\tPmin=? [ G F s=7 ];\n\t// RESULT: true\n\tP>0 [ G F s=7 ];\n\t// RESULT: false\n\tP>0.3 [ G F s=7 ];\n"
  },
  {
    "path": "prism-tests/pmc/lec17dtmc.pm",
    "content": "// Simple DTMC from Lec 17 of Probabilistic Model Checking\r\n\r\ndtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.6:(s'=0) + 0.1:(s'=1) + 0.3:(s'=3);\r\n[] s=1 -> 0.2:(s'=3) + 0.3:(s'=4) + 0.5:(s'=2);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=4);\r\n[] s=4 -> 1:(s'=3);\r\n[] s=5 -> 0.1:(s'=2) + 0.9:(s'=5);\r\n\r\nendmodule\r\n\r\nlabel \"a\" = s=2 | s=3 | s=5;\r\nlabel \"b\" = s=1;\r\n"
  },
  {
    "path": "prism-tests/pmc/lec17dtmc.pm.props",
    "content": "\t// RESULT: 1\n\tP=? [ G F \"a\" ];\n\t// RESULT: 0.75\n\tP=? [ (G !\"b\")&(G F \"a\") ];\n\t// RESULT: 0.125\n\tP=? [ F G \"a\" ];\n\t// RESULT: 1\n\tP=? [ (G (\"b\"=>(F (!\"b\"&\"a\"))))&(F G !\"b\") ];\n\t// RESULT: true (should be satisfied by {1,2,5})\n\tfilter(forall, P>0.2 [ F G \"a\" ], s=1|s=2|s=5);\n\t// RESULT: true (should be satisfied by {1,2,5})\n\tfilter(count, P>0.2 [ F G \"a\" ]) = 3;\n"
  },
  {
    "path": "prism-tests/pmc/lec18mdp.nm",
    "content": "// Simple MDP from Lec 18 of Probabilistic Model Checking\r\n\r\nmdp\r\n\r\nmodule M\r\n\r\n// note: restricted to part of mdp\r\ns:[0..8] init 1;\r\n\r\n[] s=0 -> 1:(s'=2);\r\n[] s=0 -> 0.6:(s'=0) + 0.3:(s'=1) + 0.1:(s'=2);\r\n[] s=1 -> 0.3:(s'=3) + 0.7:(s'=4);\r\n[] s=3 -> 1:(s'=4);\r\n[] s=4 -> 1:(s'=1);\r\n[] s=4 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=6);\r\n[] s=6 -> 1:(s'=6);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=5 -> 0.9:(s'=7) + 0.1:(s'=8);\r\n[] s=7 -> 1:(s'=5);\r\n[] s=8 -> 1:(s'=5);\r\n\r\nendmodule\r\n"
  },
  {
    "path": "prism-tests/pmc/lec18mdp.nm.props",
    "content": "\t// RESULT: true (should be satisfied by {0,1})\n\tfilter(forall, P<0.8 [ (G !(s=3)) & (G F (s=6)) ], s=0|s=1);\n\t// RESULT: true (should be satisfied by {0,1})\n\tfilter(count, P<0.8 [ (G !(s=3)) & (G F (s=6)) ]) = 2;\n\t// RESULT: true (should be satisfied by {3})\n\tfilter(forall, P>0 [ (G !(s=3)) & (G F (s=6)) ], s=6);\n\t// RESULT: true (should be satisfied by {3})\n\tfilter(count, P>0 [ (G !(s=3)) & (G F (s=6)) ]) = 1;\n"
  },
  {
    "path": "prism-tests/pmc/lec3.pm",
    "content": "dtmc\r\n\r\nmodule M\r\n\r\ns:[0..5];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=3);\r\n[] s=1 -> 0.5:(s'=0) + 0.25:(s'=2) + 0.25:(s'=4);\r\n[] s=2 -> 1:(s'=5);\r\n[] s=3 -> 1:(s'=3);\r\n[] s=4 -> 1:(s'=4);\r\n[] s=5 -> 1:(s'=2);\r\n\r\nendmodule\r\n\r\n// No tests yet - used for transient/steady-state probs computation\r\n"
  },
  {
    "path": "prism-tests/pmc/lec4ctl.pm",
    "content": "// 3-state DTMC from Lec 4 of Probabilistic Model Checking\r\n\r\ndtmc\r\n\r\nmodule M\r\n\r\ns:[0..2];\r\n\r\n[] s=0 -> 0.5:(s'=1) + 0.5:(s'=2);\r\n[] s=1 -> (s'=0);\r\n[] s=2 -> true;\r\n\r\nendmodule\r\n\r\nlabel \"heads\" = s=1;\r\nlabel \"tails\" = s=2;\r\n"
  },
  {
    "path": "prism-tests/pmc/lec4ctl.pm.props",
    "content": "// RESULT: true\nP>=1 [ F \"tails\" ]\n\n// RESULT: false\nA [ F \"tails\" ]\n\n// RESULT: true\nP<=0 [ G !\"tails\" ]\n\n// RESULT: true\nE [ G !\"tails\" ]\n"
  },
  {
    "path": "prism-tests/pmc/lec9transient.sm",
    "content": "ctmc\r\n\r\nmodule M\r\n\r\nx:[0..1];\r\n\r\n[] x=0 -> 3: (x'=1);\r\n[] x=1 -> 2: (x'=0);\r\n\r\nendmodule\r\n\r\n// No tests yet - used for simple transient probs illustration\r\n"
  }
]